From 970fd563b28a04dc3a0a616cea469105900f4318 Mon Sep 17 00:00:00 2001 From: Kamron Batman <3953314+kamronbatman@users.noreply.github.com> Date: Sat, 15 Sep 2018 09:58:51 -0700 Subject: [PATCH] Fixes code according to modern code style. Fixes a few expression bugs. --- .editorconfig | 10 - Scripts/Accounting/AccessRestrictions.cs | 68 +- Scripts/Accounting/AccountAttackLimiter.cs | 180 +- Scripts/Accounting/AccountComment.cs | 110 +- Scripts/Accounting/AccountHandler.cs | 686 +- Scripts/Accounting/AccountTag.cs | 82 +- Scripts/Accounting/Accounts.cs | 142 +- Scripts/Accounting/Firewall.cs | 523 +- Scripts/Accounting/IPLimiter.cs | 73 +- Scripts/Commands/Add.cs | 1363 +- Scripts/Commands/Attributes.cs | 48 +- Scripts/Commands/Batch.cs | 818 +- Scripts/Commands/BoundingBoxPicker.cs | 105 +- Scripts/Commands/ConvertPlayers.cs | 156 +- Scripts/Commands/Decorate.cs | 2208 +- Scripts/Commands/DecorateMag.cs | 2202 +- Scripts/Commands/Docs.cs | 4835 ++-- Scripts/Commands/DragEffects.cs | 44 +- Scripts/Commands/Dupe.cs | 225 +- Scripts/Commands/ExportWSC.cs | 98 +- Scripts/Commands/GenCategorization.cs | 589 +- Scripts/Commands/GenTeleporter.cs | 2084 +- .../Commands/Generic/Commands/BaseCommand.cs | 245 +- Scripts/Commands/Generic/Commands/Commands.cs | 2199 +- .../Commands/Generic/Commands/DesignInsert.cs | 329 +- .../Commands/Generic/Commands/Interface.cs | 1119 +- .../Generic/Extensions/BaseExtension.cs | 188 +- .../Compilers/ConditionalCompiler.cs | 1072 +- .../Extensions/Compilers/DistinctCompiler.cs | 376 +- .../Extensions/Compilers/SortCompiler.cs | 250 +- .../Generic/Extensions/DistinctExtension.cs | 117 +- .../Generic/Extensions/LimitExtension.cs | 48 +- .../Generic/Extensions/SortExtension.cs | 152 +- .../Generic/Extensions/WhereExtension.cs | 58 +- .../Implementors/AreaCommandImplementor.cs | 107 +- .../Implementors/BaseCommandImplementor.cs | 483 +- .../ContainedCommandImplementor.cs | 120 +- .../Implementors/FacetCommandImplementor.cs | 48 +- .../Implementors/GlobalCommandImplementor.cs | 83 +- .../IPAddressCommandImplementor.cs | 94 +- .../Implementors/MultiCommandImplementor.cs | 123 +- .../Generic/Implementors/ObjectConditional.cs | 356 +- .../Implementors/OnlineCommandImplementor.cs | 95 +- .../Implementors/RangeCommandImplementor.cs | 126 +- .../Implementors/RegionCommandImplementor.cs | 93 +- .../Implementors/ScreenCommandImplementor.cs | 37 +- .../Implementors/SelfCommandImplementor.cs | 34 +- .../Implementors/SerialCommandImplementor.cs | 167 +- .../Implementors/SingleCommandImplementor.cs | 152 +- Scripts/Commands/Handlers.cs | 1857 +- Scripts/Commands/HelpInfo.cs | 662 +- Scripts/Commands/Logging.cs | 198 +- Scripts/Commands/Profiling.cs | 777 +- Scripts/Commands/Properties.cs | 1470 +- Scripts/Commands/ShardTime.cs | 26 +- Scripts/Commands/SignParser.cs | 227 +- Scripts/Commands/Skills.cs | 234 +- Scripts/Commands/SkillsMenu.cs | 60 +- Scripts/Commands/Statics.cs | 1092 +- Scripts/Commands/VisibilityList.cs | 241 +- Scripts/Commands/Wipe.cs | 153 +- Scripts/Context Menus/AddToParty.cs | 62 +- Scripts/Context Menus/AddToSpellbookEntry.cs | 94 +- Scripts/Context Menus/EatEntry.cs | 32 +- Scripts/Context Menus/EjectPlayer.cs | 40 +- Scripts/Context Menus/OpenBankEntry.cs | 38 +- Scripts/Context Menus/TeachEntry.cs | 41 +- Scripts/Engines/BulkOrders/Books/BOBFilter.cs | 96 +- .../Engines/BulkOrders/Books/BOBFilterGump.cs | 332 +- Scripts/Engines/BulkOrders/Books/BOBGump.cs | 1353 +- .../Engines/BulkOrders/Books/BOBLargeEntry.cs | 149 +- .../BulkOrders/Books/BOBLargeSubEntry.cs | 78 +- .../Engines/BulkOrders/Books/BOBSmallEntry.cs | 140 +- .../Engines/BulkOrders/Books/BODBuyGump.cs | 230 +- Scripts/Engines/BulkOrders/Books/BODType.cs | 10 +- .../Engines/BulkOrders/BulkMaterialType.cs | 68 +- .../Engines/BulkOrders/LargeBODAcceptGump.cs | 155 +- Scripts/Engines/BulkOrders/LargeBODGump.cs | 140 +- Scripts/Engines/BulkOrders/LargeBODTarget.cs | 28 +- Scripts/Engines/BulkOrders/LargeSmithBOD.cs | 228 +- Scripts/Engines/BulkOrders/LargeTailorBOD.cs | 237 +- Scripts/Engines/BulkOrders/Rewards.cs | 1448 +- Scripts/Engines/BulkOrders/SmallBOD.cs | 497 +- .../Engines/BulkOrders/SmallBODAcceptGump.cs | 136 +- Scripts/Engines/BulkOrders/SmallBODGump.cs | 113 +- Scripts/Engines/BulkOrders/SmallBODTarget.cs | 28 +- Scripts/Engines/BulkOrders/SmallSmithBOD.cs | 397 +- Scripts/Engines/BulkOrders/SmallTailorBOD.cs | 400 +- Scripts/Engines/CannedEvil/ChampionAltar.cs | 74 +- .../Engines/CannedEvil/ChampionPlatform.cs | 120 +- Scripts/Engines/CannedEvil/ChampionSkull.cs | 125 +- .../CannedEvil/ChampionSkullBrazier.cs | 288 +- .../CannedEvil/ChampionSkullPlatform.cs | 195 +- .../Engines/CannedEvil/ChampionSkullType.cs | 18 +- Scripts/Engines/CannedEvil/ChampionSpawn.cs | 2415 +- .../Engines/CannedEvil/ChampionSpawnType.cs | 220 +- Scripts/Engines/CannedEvil/HarrowerGate.cs | 80 +- Scripts/Engines/CannedEvil/RestartTimer.cs | 26 +- Scripts/Engines/CannedEvil/SliceTimer.cs | 26 +- Scripts/Engines/CannedEvil/StarRoomGate.cs | 156 +- Scripts/Engines/Chat/Channel.cs | 1032 +- Scripts/Engines/Chat/Chat.cs | 248 +- Scripts/Engines/Chat/ChatActionHandler.cs | 26 +- Scripts/Engines/Chat/ChatActionHandlers.cs | 561 +- Scripts/Engines/Chat/ChatCommand.cs | 86 +- Scripts/Engines/Chat/ChatUser.cs | 374 +- Scripts/Engines/Chat/Chatold.cs | 22 +- Scripts/Engines/Chat/Packets.cs | 37 +- Scripts/Engines/ConPVP/AcceptDuelGump.cs | 447 +- Scripts/Engines/ConPVP/Arena.cs | 1563 +- Scripts/Engines/ConPVP/ArenaGump.cs | 447 +- Scripts/Engines/ConPVP/BeginGump.cs | 96 +- Scripts/Engines/ConPVP/DuelContext.cs | 4694 ++-- Scripts/Engines/ConPVP/DuelContextGump.cs | 210 +- Scripts/Engines/ConPVP/DuelTeleporterAddon.cs | 148 +- Scripts/Engines/ConPVP/Games/BombingRun.cs | 3443 ++- Scripts/Engines/ConPVP/Games/CTF.cs | 2249 +- Scripts/Engines/ConPVP/Games/DoubleDom.cs | 2095 +- Scripts/Engines/ConPVP/Games/EventGame.cs | 114 +- Scripts/Engines/ConPVP/Games/KingOfTheHill.cs | 2366 +- Scripts/Engines/ConPVP/Ladder.cs | 727 +- Scripts/Engines/ConPVP/LadderGump.cs | 375 +- Scripts/Engines/ConPVP/Participant.cs | 353 +- Scripts/Engines/ConPVP/ParticipantGump.cs | 392 +- Scripts/Engines/ConPVP/PickRulesetGump.cs | 191 +- Scripts/Engines/ConPVP/Preferences.cs | 487 +- Scripts/Engines/ConPVP/ReadyGump.cs | 155 +- Scripts/Engines/ConPVP/ReadyUpGump.cs | 333 +- Scripts/Engines/ConPVP/Ruleset.cs | 140 +- Scripts/Engines/ConPVP/RulesetGump.cs | 201 +- Scripts/Engines/ConPVP/RulesetLayout.cs | 1482 +- Scripts/Engines/ConPVP/SafeZone.cs | 99 +- Scripts/Engines/ConPVP/Tournament.cs | 6808 +++--- Scripts/Engines/ConPVP/Trophy.cs | 169 +- Scripts/Engines/Craft/Core/CraftContext.cs | 78 +- Scripts/Engines/Craft/Core/CraftGroup.cs | 32 +- Scripts/Engines/Craft/Core/CraftGroupCol.cs | 73 +- Scripts/Engines/Craft/Core/CraftGump.cs | 1200 +- Scripts/Engines/Craft/Core/CraftGumpItem.cs | 454 +- Scripts/Engines/Craft/Core/CraftItem.cs | 2381 +- Scripts/Engines/Craft/Core/CraftItemCol.cs | 87 +- .../Craft/Core/CraftItemIDAttribute.cs | 18 +- Scripts/Engines/Craft/Core/CraftRes.cs | 62 +- Scripts/Engines/Craft/Core/CraftResCol.cs | 48 +- Scripts/Engines/Craft/Core/CraftSkill.cs | 24 +- Scripts/Engines/Craft/Core/CraftSkillCol.cs | 48 +- Scripts/Engines/Craft/Core/CraftSubRes.cs | 43 +- Scripts/Engines/Craft/Core/CraftSubResCol.cs | 81 +- Scripts/Engines/Craft/Core/CraftSystem.cs | 647 +- Scripts/Engines/Craft/Core/CustomCraft.cs | 41 +- Scripts/Engines/Craft/Core/Enhance.cs | 521 +- .../Engines/Craft/Core/QueryMakersMarkGump.cs | 74 +- Scripts/Engines/Craft/Core/Recipes.cs | 156 +- Scripts/Engines/Craft/Core/Repair.cs | 897 +- Scripts/Engines/Craft/Core/Resmelt.cs | 286 +- Scripts/Engines/Craft/DefAlchemy.cs | 284 +- Scripts/Engines/Craft/DefBlacksmithy.cs | 1496 +- Scripts/Engines/Craft/DefBowFletching.cs | 341 +- Scripts/Engines/Craft/DefCarpentry.cs | 1050 +- Scripts/Engines/Craft/DefCartography.cs | 121 +- Scripts/Engines/Craft/DefCooking.cs | 443 +- Scripts/Engines/Craft/DefGlassblowing.cs | 203 +- Scripts/Engines/Craft/DefInscription.cs | 667 +- Scripts/Engines/Craft/DefMasonry.cs | 224 +- Scripts/Engines/Craft/DefTailoring.cs | 812 +- Scripts/Engines/Craft/DefTinkering.cs | 1051 +- Scripts/Engines/Doom/GauntletSpawner.cs | 1030 +- .../Doom/LeverPuzzle/LeverPuzzleController.cs | 1347 +- .../Doom/LeverPuzzle/LeverPuzzleItems.cs | 350 +- .../Doom/LeverPuzzle/LeverPuzzleRegions.cs | 196 +- Scripts/Engines/Ethics/Core/Ethic.cs | 360 +- Scripts/Engines/Ethics/Core/Persistance.cs | 90 +- Scripts/Engines/Ethics/Core/Player.cs | 233 +- Scripts/Engines/Ethics/Core/Power.cs | 47 +- .../Ethics/Definitions/EthicDefinition.cs | 35 +- .../Ethics/Definitions/PowerDefinition.cs | 30 +- Scripts/Engines/Ethics/Evil/Ethic.cs | 54 +- .../Ethics/Evil/Mobiles/UnholyFamiliar.cs | 123 +- .../Ethics/Evil/Mobiles/UnholySteed.cs | 131 +- Scripts/Engines/Ethics/Evil/Powers/Blight.cs | 110 +- .../Ethics/Evil/Powers/SummonFamiliar.cs | 69 +- .../Engines/Ethics/Evil/Powers/UnholyItem.cs | 110 +- .../Engines/Ethics/Evil/Powers/UnholySense.cs | 145 +- .../Ethics/Evil/Powers/UnholyShield.cs | 52 +- .../Engines/Ethics/Evil/Powers/UnholySteed.cs | 70 +- .../Engines/Ethics/Evil/Powers/UnholyWord.cs | 32 +- .../Engines/Ethics/Evil/Powers/VileBlade.cs | 32 +- Scripts/Engines/Ethics/Hero/Ethic.cs | 58 +- .../Ethics/Hero/Mobiles/HolyFamiliar.cs | 123 +- .../Engines/Ethics/Hero/Mobiles/HolySteed.cs | 131 +- Scripts/Engines/Ethics/Hero/Powers/Bless.cs | 112 +- .../Engines/Ethics/Hero/Powers/HolyBlade.cs | 32 +- .../Engines/Ethics/Hero/Powers/HolyItem.cs | 110 +- .../Engines/Ethics/Hero/Powers/HolySense.cs | 145 +- .../Engines/Ethics/Hero/Powers/HolyShield.cs | 52 +- .../Engines/Ethics/Hero/Powers/HolySteed.cs | 70 +- .../Engines/Ethics/Hero/Powers/HolyWord.cs | 32 +- .../Ethics/Hero/Powers/SummonFamiliar.cs | 69 +- Scripts/Engines/Factions/Core/Election.cs | 1019 +- Scripts/Engines/Factions/Core/Faction.cs | 2736 ++- Scripts/Engines/Factions/Core/FactionItem.cs | 216 +- Scripts/Engines/Factions/Core/FactionState.cs | 452 +- Scripts/Engines/Factions/Core/Generator.cs | 110 +- Scripts/Engines/Factions/Core/GuardList.cs | 36 +- Scripts/Engines/Factions/Core/Keywords.cs | 247 +- .../Engines/Factions/Core/MerchantTitles.cs | 137 +- Scripts/Engines/Factions/Core/Persistance.cs | 132 +- Scripts/Engines/Factions/Core/PlayerState.cs | 457 +- Scripts/Engines/Factions/Core/Reflector.cs | 118 +- .../Engines/Factions/Core/SilverGivenEntry.cs | 24 +- .../Engines/Factions/Core/StrongholdRegion.cs | 54 +- Scripts/Engines/Factions/Core/Town.cs | 884 +- Scripts/Engines/Factions/Core/TownState.cs | 198 +- Scripts/Engines/Factions/Core/VendorList.cs | 38 +- .../Factions/Definitions/FactionDefinition.cs | 119 +- .../Definitions/FactionItemDefinition.cs | 70 +- .../Factions/Definitions/GuardDefinition.cs | 41 +- .../Factions/Definitions/RankDefinition.cs | 28 +- .../Definitions/StrongholdDefintion.cs | 28 +- .../Factions/Definitions/TownDefinition.cs | 67 +- .../Factions/Definitions/VendorDefinition.cs | 117 +- .../Engines/Factions/Gumps/ElectionGump.cs | 196 +- .../Factions/Gumps/ElectionManagementGump.cs | 363 +- Scripts/Engines/Factions/Gumps/FactionGump.cs | 68 +- .../Factions/Gumps/FactionImbueGump.cs | 155 +- .../Factions/Gumps/FactionStoneGump.cs | 582 +- Scripts/Engines/Factions/Gumps/FinanceGump.cs | 464 +- .../Factions/Gumps/HorseBreederGump.cs | 133 +- .../Engines/Factions/Gumps/JoinStoneGump.cs | 62 +- .../Factions/Gumps/LeaveFactionGump.cs | 144 +- Scripts/Engines/Factions/Gumps/SheriffGump.cs | 272 +- .../Engines/Factions/Gumps/TownStoneGump.cs | 352 +- Scripts/Engines/Factions/Gumps/VoteGump.cs | 90 +- .../Instances/Factions/CouncilOfMages.cs | 198 +- .../Factions/Instances/Factions/Minax.cs | 152 +- .../Instances/Factions/Shadowlords.cs | 152 +- .../Instances/Factions/TrueBritannians.cs | 162 +- .../Factions/Instances/Towns/Britain.cs | 42 +- .../Factions/Instances/Towns/Magincia.cs | 42 +- .../Engines/Factions/Instances/Towns/Minoc.cs | 42 +- .../Factions/Instances/Towns/Moonglow.cs | 42 +- .../Factions/Instances/Towns/SkaraBrae.cs | 42 +- .../Factions/Instances/Towns/Trinsic.cs | 42 +- .../Factions/Instances/Towns/Vesper.cs | 42 +- .../Engines/Factions/Instances/Towns/Yew.cs | 42 +- .../Engines/Factions/Items/BaseMonolith.cs | 202 +- .../Factions/Items/BaseSystemController.cs | 100 +- .../Engines/Factions/Items/FactionStone.cs | 165 +- Scripts/Engines/Factions/Items/JoinStone.cs | 120 +- .../Items/Power Faction Items/BloodRose.cs | 79 +- .../Power Faction Items/ClarityPotion.cs | 93 +- .../Power Faction Items/GemOfEmpowerment.cs | 67 +- .../Power Faction Items/PowerFactionItem.cs | 265 +- .../Items/Power Faction Items/StormsEye.cs | 169 +- .../Power Faction Items/UrnOfAscension.cs | 92 +- Scripts/Engines/Factions/Items/Sigil.cs | 860 +- Scripts/Engines/Factions/Items/Silver.cs | 78 +- .../Factions/Items/StrongholdMonolith.cs | 56 +- .../Engines/Factions/Items/TownMonolith.cs | 56 +- Scripts/Engines/Factions/Items/TownStone.cs | 128 +- .../Factions/Items/Traps/BaseFactionTrap.cs | 411 +- .../Items/Traps/BaseFactionTrapDeed.cs | 180 +- .../Items/Traps/FactionExplosionTrap.cs | 124 +- .../Factions/Items/Traps/FactionGasTrap.cs | 124 +- .../Factions/Items/Traps/FactionSawTrap.cs | 124 +- .../Factions/Items/Traps/FactionSpikeTrap.cs | 127 +- .../Items/Traps/FactionTrapRemovalKit.cs | 110 +- .../Factions/Mobiles/FactionWarHorse.cs | 166 +- .../Mobiles/Guards/BaseFactionGuard.cs | 985 +- .../Factions/Mobiles/Guards/GuardAI.cs | 1447 +- .../Engines/Factions/Mobiles/Guards/Orders.cs | 207 +- .../Mobiles/Guards/Types/FactionBerserker.cs | 104 +- .../Guards/Types/FactionDeathKnight.cs | 98 +- .../Mobiles/Guards/Types/FactionDragoon.cs | 104 +- .../Mobiles/Guards/Types/FactionHenchman.cs | 96 +- .../Mobiles/Guards/Types/FactionKnight.cs | 106 +- .../Mobiles/Guards/Types/FactionMercenary.cs | 94 +- .../Guards/Types/FactionNecromancer.cs | 96 +- .../Mobiles/Guards/Types/FactionPaladin.cs | 106 +- .../Mobiles/Guards/Types/FactionSorceress.cs | 104 +- .../Mobiles/Guards/Types/FactionWizard.cs | 98 +- .../Mobiles/Vendors/BaseFactionVendor.cs | 176 +- .../Mobiles/Vendors/FactionBoardVendor.cs | 102 +- .../Mobiles/Vendors/FactionBottleVendor.cs | 103 +- .../Mobiles/Vendors/FactionHorseVendor.cs | 115 +- .../Mobiles/Vendors/FactionOreVendor.cs | 105 +- .../Mobiles/Vendors/FactionReagentVendor.cs | 131 +- .../Harvest/Core/BonusHarvestResource.cs | 38 +- Scripts/Engines/Harvest/Core/HarvestBank.cs | 143 +- .../Engines/Harvest/Core/HarvestDefinition.cs | 234 +- .../Engines/Harvest/Core/HarvestResource.cs | 48 +- .../Engines/Harvest/Core/HarvestSoundTimer.cs | 51 +- Scripts/Engines/Harvest/Core/HarvestSystem.cs | 968 +- Scripts/Engines/Harvest/Core/HarvestTarget.cs | 171 +- Scripts/Engines/Harvest/Core/HarvestTimer.cs | 49 +- Scripts/Engines/Harvest/Core/HarvestVein.cs | 29 +- Scripts/Engines/Harvest/Fishing.cs | 1110 +- Scripts/Engines/Harvest/Lumberjacking.cs | 343 +- Scripts/Engines/Harvest/Mining.cs | 840 +- Scripts/Engines/Help/HelpGump.cs | 477 +- Scripts/Engines/Help/PagePrompt.cs | 35 +- Scripts/Engines/Help/PagePromptGump.cs | 86 +- Scripts/Engines/Help/PageQueue.cs | 637 +- Scripts/Engines/Help/PageQueueGump.cs | 1649 +- Scripts/Engines/Help/PageResponseGump.cs | 50 +- Scripts/Engines/Help/SpeechLog.cs | 218 +- Scripts/Engines/Help/SpeechLogGump.cs | 157 +- Scripts/Engines/Help/StuckMenu.cs | 473 +- .../Engines/Khaldun/Books/GrimmochJournal.cs | 1548 +- .../Engines/Khaldun/Books/LysanderNotebook.cs | 974 +- .../Engines/Khaldun/Books/TavarasJournal.cs | 2656 +- Scripts/Engines/Khaldun/KhaldunGen.cs | 330 +- .../Engines/Khaldun/KhaldunPitTeleporter.cs | 137 +- .../Khaldun/Mobiles/GrimmochDrummel.cs | 192 +- .../Khaldun/Mobiles/LysanderGathenwale.cs | 196 +- Scripts/Engines/Khaldun/Mobiles/MorgBergen.cs | 161 +- .../Engines/Khaldun/Mobiles/TavaraSewel.cs | 180 +- Scripts/Engines/Khaldun/PuzzleChest.cs | 1575 +- Scripts/Engines/Khaldun/RaisableItem.cs | 260 +- Scripts/Engines/Khaldun/RaiseSwitch.cs | 330 +- .../MLQuests/Definitions/AGhostOfCovetous.cs | Bin 17966 -> 18694 bytes .../MLQuests/Definitions/BaseEscort.cs | 32 +- .../Engines/MLQuests/Definitions/Bedlam.cs | 349 +- .../MLQuests/Definitions/BlightedGrove.cs | 438 +- .../Engines/MLQuests/Definitions/Britannia.cs | 303 +- .../Engines/MLQuests/Definitions/Heartwood.cs | 9212 +++---- .../Engines/MLQuests/Definitions/Heritage.cs | 1611 +- .../MLQuests/Definitions/HonestBeggar.cs | 243 +- .../Engines/MLQuests/Definitions/Ilshenar.cs | 538 +- .../Engines/MLQuests/Definitions/LostItems.cs | 97 +- Scripts/Engines/MLQuests/Definitions/Malas.cs | 136 +- .../MLQuests/Definitions/MistakenIdentity.cs | 546 +- .../Engines/MLQuests/Definitions/NewHaven.cs | 205 +- .../Definitions/NewHavenSkillTraining.cs | 4912 ++-- .../MLQuests/Definitions/NewHavenTraining.cs | 2028 +- .../Engines/MLQuests/Definitions/Sanctuary.cs | 2526 +- .../MLQuests/Definitions/Spellweaving.cs | 1398 +- .../MLQuests/Definitions/TheAncientWorld.cs | 243 +- .../MLQuests/Definitions/TownEscorts.cs | 216 +- .../MLQuests/Definitions/UnfadingMemories.cs | 293 +- .../Definitions/WarriorsOfTheGemKeeper.cs | 136 +- .../Engines/MLQuests/Gumps/BaseQuestGump.cs | 390 +- Scripts/Engines/MLQuests/Gumps/InfoNPCGump.cs | 26 +- .../MLQuests/Gumps/QuestCancelConfirmGump.cs | 153 +- .../MLQuests/Gumps/QuestConversationGump.cs | 28 +- .../MLQuests/Gumps/QuestLogDetailedGump.cs | 114 +- .../Engines/MLQuests/Gumps/QuestLogGump.cs | 115 +- .../Engines/MLQuests/Gumps/QuestOfferGump.cs | 84 +- .../MLQuests/Gumps/QuestReportBackGump.cs | 50 +- .../Engines/MLQuests/Gumps/QuestRewardGump.cs | 46 +- .../Engines/MLQuests/Gumps/RaceChangeGump.cs | 538 +- Scripts/Engines/MLQuests/IQuestGiver.cs | 16 +- Scripts/Engines/MLQuests/Items/ABauble.cs | 46 +- .../Items/APersonalLetterAddressedToAhie.cs | 58 +- .../MLQuests/Items/AlchemistsBandage.cs | 60 +- .../Engines/MLQuests/Items/AnOldNecklace.cs | 46 +- Scripts/Engines/MLQuests/Items/AnOldRing.cs | 46 +- .../Engines/MLQuests/Items/AndricSatchel.cs | 50 +- .../Engines/MLQuests/Items/AndrosGratitude.cs | 46 +- .../Engines/MLQuests/Items/AsandosSatchel.cs | 50 +- .../Items/BasinOfCrystalClearWater.cs | 58 +- .../MLQuests/Items/BedlamTeleporter.cs | 86 +- Scripts/Engines/MLQuests/Items/Bleach.cs | 46 +- .../Engines/MLQuests/Items/BridesLetter.cs | 58 +- .../CompletedTuitionReimbursementForm.cs | 58 +- .../MLQuests/Items/CraftmansSatchel.cs | 345 +- .../Engines/MLQuests/Items/CrateForSledge.cs | 58 +- .../Engines/MLQuests/Items/DreadSpiderSilk.cs | 60 +- .../Engines/MLQuests/Items/FragmentOfAMap.cs | 46 +- .../MLQuests/Items/FragmentOfAMapDelivery.cs | 58 +- .../MLQuests/Items/FriendOfTheLibraryToken.cs | 48 +- .../Items/FriendsOfTheLibraryApplication.cs | 58 +- Scripts/Engines/MLQuests/Items/GamanHorns.cs | 60 +- .../Engines/MLQuests/Items/GervisSatchel.cs | 50 +- .../Engines/MLQuests/Items/GiftForArielle.cs | 60 +- .../Engines/MLQuests/Items/HargroveSatchel.cs | 50 +- Scripts/Engines/MLQuests/Items/KirinBrains.cs | 48 +- .../Engines/MLQuests/Items/LowelSatchel.cs | 50 +- .../MLQuests/Items/MiniatureMushroom.cs | 46 +- .../MLQuests/Items/MirrorOfPurification.cs | 48 +- Scripts/Engines/MLQuests/Items/MuggSatchel.cs | 50 +- .../Engines/MLQuests/Items/NibbetSatchel.cs | 95 +- .../MLQuests/Items/NotarizedApplication.cs | 58 +- .../MLQuests/Items/OfficialSealingWax.cs | 60 +- .../MLQuests/Items/PeppercornFishsteak.cs | 46 +- Scripts/Engines/MLQuests/Items/PixieLeg.cs | 56 +- .../MLQuests/Items/PortraitOfTheBride.cs | 58 +- .../Engines/MLQuests/Items/PrismaticAmber.cs | 106 +- .../MLQuests/Items/PrismaticCrystal.cs | 105 +- .../Engines/MLQuests/Items/QuestGiverItem.cs | 244 +- .../Engines/MLQuests/Items/RedLeatherBook.cs | 46 +- .../Engines/MLQuests/Items/ReginasLetter.cs | 58 +- Scripts/Engines/MLQuests/Items/ReginasRing.cs | 58 +- Scripts/Engines/MLQuests/Items/RewardBags.cs | 316 +- .../Engines/MLQuests/Items/SadrahSatchel.cs | 50 +- .../Engines/MLQuests/Items/SapOfSosaria.cs | 58 +- .../MLQuests/Items/SealedNotesForJamal.cs | 60 +- .../Items/SealingWaxOrderAddressedToPetrus.cs | 58 +- .../Engines/MLQuests/Items/SeveredElfEars.cs | 56 +- .../MLQuests/Items/SeveredHumanEars.cs | 56 +- .../Items/SignedTuitionReimbursementForm.cs | 58 +- .../MLQuests/Items/SpecialTreatForDrithen.cs | 48 +- .../MLQuests/Items/SpeckledPoisonSac.cs | 46 +- .../Engines/MLQuests/Items/SpiritBottle.cs | 58 +- Scripts/Engines/MLQuests/Items/StoutWhip.cs | 46 +- .../MLQuests/Items/TaintedTreeSample.cs | 60 +- Scripts/Engines/MLQuests/Items/Teleporters.cs | 324 +- .../MLQuests/Items/TransparentHeart.cs | 48 +- .../Items/TuitionReimbursementForm.cs | 58 +- Scripts/Engines/MLQuests/Items/UnicornRibs.cs | 60 +- Scripts/Engines/MLQuests/MLQuest.cs | 454 +- Scripts/Engines/MLQuests/MLQuestContext.cs | 428 +- Scripts/Engines/MLQuests/MLQuestEntry.cs | 930 +- .../Engines/MLQuests/MLQuestPersistence.cs | 92 +- Scripts/Engines/MLQuests/MLQuestSystem.cs | 1391 +- .../Engines/MLQuests/Mobiles/BoonCollector.cs | 842 +- Scripts/Engines/MLQuests/Mobiles/SirHelper.cs | 199 +- .../MLQuests/Objectives/BaseObjective.cs | 294 +- .../MLQuests/Objectives/CollectObjective.cs | 351 +- .../MLQuests/Objectives/DeliverObjective.cs | 357 +- .../MLQuests/Objectives/EscortObjective.cs | 413 +- .../MLQuests/Objectives/GainSkillObjective.cs | 264 +- .../MLQuests/Objectives/KillObjective.cs | 235 +- Scripts/Engines/MLQuests/QuestArea.cs | 87 +- .../Engines/MLQuests/QuesterNameAttribute.cs | 50 +- .../Engines/MLQuests/Rewards/BaseReward.cs | 34 +- .../Engines/MLQuests/Rewards/DummyReward.cs | 26 +- .../Engines/MLQuests/Rewards/ItemReward.cs | 156 +- Scripts/Engines/MyRunUO/Config.cs | 67 +- .../Engines/MyRunUO/DatabaseCommandQueue.cs | 371 +- Scripts/Engines/MyRunUO/LayerComparer.cs | 137 +- Scripts/Engines/MyRunUO/MyRunUO.cs | 1382 +- Scripts/Engines/MyRunUO/MyRunUOStatus.cs | 107 +- Scripts/Engines/Party/AddPartyTarget.cs | 76 +- Scripts/Engines/Party/DeclineTimer.cs | 47 +- Scripts/Engines/Party/Packets.cs | 118 +- Scripts/Engines/Party/Party.cs | 934 +- Scripts/Engines/Party/PartyCommands.cs | 191 +- Scripts/Engines/Party/PartyMemberInfo.cs | 20 +- Scripts/Engines/Party/RemoveFromParty.cs | 44 +- Scripts/Engines/Party/RemovePartyTarget.cs | 41 +- Scripts/Engines/Pathing/FastAStarAlgorithm.cs | 505 +- Scripts/Engines/Pathing/FastMovement.cs | 1268 +- Scripts/Engines/Pathing/MoveResult.cs | 16 +- Scripts/Engines/Pathing/Movement.cs | 1166 +- Scripts/Engines/Pathing/MovementPath.cs | 236 +- Scripts/Engines/Pathing/PathAlgorithm.cs | 52 +- Scripts/Engines/Pathing/PathFollower.cs | 274 +- Scripts/Engines/Pathing/SlowAStarAlgorithm.cs | 407 +- Scripts/Engines/Plants/EmptyTheBowlGump.cs | 174 +- Scripts/Engines/Plants/MainPlantGump.cs | 841 +- .../Engines/Plants/MiscItems/FertileDirt.cs | 54 +- .../Engines/Plants/MiscItems/GreenThorns.cs | 1461 +- .../Engines/Plants/MiscItems/OrangePetals.cs | 208 +- Scripts/Engines/Plants/MiscItems/RedLeaves.cs | 160 +- .../Plants/MiscMobiles/GiantIceWorm.cs | 102 +- .../Plants/Network/DisplayHelpTopic.cs | 22 +- Scripts/Engines/Plants/PlantBowl.cs | 318 +- Scripts/Engines/Plants/PlantHue.cs | 286 +- Scripts/Engines/Plants/PlantItem.cs | 1119 +- Scripts/Engines/Plants/PlantPourTarget.cs | 49 +- Scripts/Engines/Plants/PlantResources.cs | 73 +- Scripts/Engines/Plants/PlantSystem.cs | 1367 +- Scripts/Engines/Plants/PlantType.cs | 630 +- Scripts/Engines/Plants/PollinateTarget.cs | 161 +- Scripts/Engines/Plants/ReproductionGump.cs | 429 +- Scripts/Engines/Plants/Seed.cs | 370 +- Scripts/Engines/Plants/SetToDecorativeGump.cs | 121 +- .../AmbitiousQueenQuest.cs | 184 +- .../Ambitious Solen Queen/Conversations.cs | 219 +- .../Mobiles/AmbitiousSolenQueen.cs | 318 +- .../Ambitious Solen Queen/Objectives.cs | 211 +- .../Quests/Collector/CollectorQuest.cs | 145 +- .../Engines/Quests/Collector/Conversations.cs | 638 +- .../Quests/Collector/Items/EnchantedPaints.cs | 200 +- .../Quests/Collector/Items/ImageType.cs | 169 +- .../Quests/Collector/Items/Obsidian.cs | 442 +- .../Quests/Collector/Items/PaintedImage.cs | 126 +- .../Quests/Collector/Mobiles/AlbertaGiacco.cs | 134 +- .../Collector/Mobiles/ElwoodMcCarrin.cs | 391 +- .../Quests/Collector/Mobiles/GabrielPiete.cs | 154 +- .../Quests/Collector/Mobiles/Impresario.cs | 251 +- .../Quests/Collector/Mobiles/TomasONeerlan.cs | 167 +- .../Engines/Quests/Collector/Objectives.cs | 784 +- Scripts/Engines/Quests/Core/BaseQuester.cs | 187 +- .../Quests/Core/Items/DynamicTeleporter.cs | 92 +- .../Quests/Core/Items/EnchantedSextant.cs | 322 +- .../Quests/Core/Items/HornOfRetreat.cs | 300 +- .../Engines/Quests/Core/Items/QuestItem.cs | 150 +- .../Engines/Quests/Core/QuestCallbackEntry.cs | 30 +- .../Engines/Quests/Core/QuestConversation.cs | 202 +- Scripts/Engines/Quests/Core/QuestItemInfo.cs | 78 +- Scripts/Engines/Quests/Core/QuestObjective.cs | 376 +- .../Engines/Quests/Core/QuestRestartInfo.cs | 44 +- .../Engines/Quests/Core/QuestSerializer.cs | 312 +- Scripts/Engines/Quests/Core/QuestSystem.cs | 1236 +- .../Quests/Core/Regions/CancelQuestRegion.cs | 54 +- .../Regions/QuestCompleteObjectiveRegion.cs | 54 +- .../Quests/Core/Regions/QuestNoEntryRegion.cs | 80 +- .../Quests/Core/Regions/QuestOfferRegion.cs | 56 +- .../Quests/Dark Tides/Conversations.cs | 378 +- .../Quests/Dark Tides/DarkTidesQuest.cs | 157 +- .../Dark Tides/Items/CrystalCaveBarrier.cs | 96 +- .../Quests/Dark Tides/Items/DarkTidesHorn.cs | 54 +- .../Dark Tides/Items/DarkTidesTeleporter.cs | 121 +- .../Quests/Dark Tides/Items/KronusScroll.cs | 257 +- .../Dark Tides/Items/KronusScrollBox.cs | 113 +- .../Quests/Dark Tides/Items/MaabusCoffin.cs | 226 +- .../Dark Tides/Items/ScrollOfAbraxus.cs | 218 +- .../Dark Tides/Items/VaultOfSecretsBarrier.cs | 68 +- .../Quests/Dark Tides/Mobiles/Horus.cs | 291 +- .../Quests/Dark Tides/Mobiles/Maabus.cs | 64 +- .../Quests/Dark Tides/Mobiles/Mardoth.cs | 355 +- .../Dark Tides/Mobiles/SummonedPaladin.cs | 351 +- .../Engines/Quests/Dark Tides/Objectives.cs | 826 +- .../Emino's Undertaking/Conversations.cs | 370 +- .../EminosUndertakingQuest.cs | 204 +- .../Items/BlueNinjaQuestTeleporter.cs | 68 +- .../Emino's Undertaking/Items/EminosKatana.cs | 60 +- .../Items/EminosKatanaChest.cs | 221 +- .../Items/GreenNinjaQuestTeleporter.cs | 68 +- .../Items/GuardianBarrier.cs | 104 +- .../Emino's Undertaking/Items/NoteForZoel.cs | 58 +- .../Items/WhiteNinjaQuestTeleporter.cs | 80 +- .../Emino's Undertaking/Mobiles/Emino.cs | 368 +- .../Mobiles/EnshroudedFigure.cs | 78 +- .../Emino's Undertaking/Mobiles/Henchman.cs | 76 +- .../Mobiles/HiddenFigure.cs | 135 +- .../Mobiles/JedahEntille.cs | 84 +- .../Emino's Undertaking/Mobiles/Zoel.cs | 204 +- .../Quests/Emino's Undertaking/Objectives.cs | 390 +- .../Quests/Haochi's Trials/Conversations.cs | 848 +- .../Haochi's Trials/HaochisTrialsQuest.cs | 186 +- .../Haochi's Trials/Items/HaochisKatana.cs | 56 +- .../Items/HaochisKatanaGenerator.cs | 124 +- .../Items/HaochisTreasureChest.cs | 145 +- .../Haochi's Trials/Items/HonorCandle.cs | 106 +- .../Haochi's Trials/Mobiles/CursedSoul.cs | 124 +- .../Haochi's Trials/Mobiles/DeadlyImp.cs | 118 +- .../Haochi's Trials/Mobiles/DiseasedCat.cs | 76 +- .../Haochi's Trials/Mobiles/FierceDragon.cs | 154 +- .../Quests/Haochi's Trials/Mobiles/Haochi.cs | 268 +- .../Mobiles/HaochisGuardsman.cs | 145 +- .../Haochi's Trials/Mobiles/InjuredWolf.cs | 82 +- .../Quests/Haochi's Trials/Mobiles/Relnia.cs | 158 +- .../Haochi's Trials/Mobiles/YoungNinja.cs | 94 +- .../Haochi's Trials/Mobiles/YoungRonin.cs | 110 +- .../Quests/Haochi's Trials/Objectives.cs | 736 +- .../Quests/Solen Matriarch/Conversations.cs | 336 +- .../Solen Matriarch/Mobiles/SolenMatriarch.cs | 496 +- .../Quests/Solen Matriarch/Objectives.cs | 258 +- .../Solen Matriarch/SolenMatriarchQuest.cs | 220 +- .../Study of the Solen Hive/Conversations.cs | 104 +- .../Mobiles/Naturalist.cs | 294 +- .../Study of the Solen Hive/NestArea.cs | 133 +- .../Study of the Solen Hive/Objectives.cs | 291 +- .../StudyOfSolenQuest.cs | 91 +- .../Terrible Hatchlings/Conversations.cs | 70 +- .../Mobiles/AnsellaGryen.cs | 232 +- .../Quests/Terrible Hatchlings/Objectives.cs | 228 +- .../TerribleHatchlingsQuest.cs | 65 +- .../Quests/The Summoning/Conversations.cs | 92 +- .../The Summoning/Items/BellOfTheDead.cs | 177 +- .../The Summoning/Items/ChylothShroud.cs | 44 +- .../The Summoning/Items/ChylothStaff.cs | 46 +- .../Quests/The Summoning/Items/GoldenSkull.cs | 50 +- .../The Summoning/Items/GrandGrimoire.cs | 52 +- .../The Summoning/Items/SummoningAltar.cs | 90 +- .../Quests/The Summoning/Mobiles/Chyloth.cs | 509 +- .../Quests/The Summoning/Mobiles/Victoria.cs | 234 +- .../Quests/The Summoning/Objectives.cs | 262 +- .../Quests/The Summoning/TheSummoningQuest.cs | 160 +- .../Quests/Uzeraan Turmoil/Conversations.cs | 1106 +- .../Quests/Uzeraan Turmoil/Items/Cannon.cs | 289 +- .../Uzeraan Turmoil/Items/DaemonBloodChest.cs | 102 +- .../Uzeraan Turmoil/Items/QuestDaemonBlood.cs | 54 +- .../Uzeraan Turmoil/Items/QuestDaemonBone.cs | 54 +- .../Uzeraan Turmoil/Items/QuestFertileDirt.cs | 54 +- .../Items/SchmendrickApprenticeCorpse.cs | 307 +- .../Items/SchmendrickScrollOfPower.cs | 56 +- .../Items/UzeraanTurmoilHorn.cs | 54 +- .../Items/UzeraanTurmoilTeleporter.cs | 116 +- .../Quests/Uzeraan Turmoil/Mobiles/Dryad.cs | 305 +- .../Uzeraan Turmoil/Mobiles/MansionGuard.cs | 114 +- .../Mobiles/MilitiaCanoneer.cs | 152 +- .../Uzeraan Turmoil/Mobiles/MilitiaFighter.cs | 240 +- .../Uzeraan Turmoil/Mobiles/Schmendrick.cs | 238 +- .../Quests/Uzeraan Turmoil/Mobiles/Uzeraan.cs | 726 +- .../Quests/Uzeraan Turmoil/Objectives.cs | 920 +- .../Uzeraan Turmoil/UzeraanTurmoilQuest.cs | 274 +- .../Quests/Witch Apprentice/Conversations.cs | 682 +- .../Quests/Witch Apprentice/Ingredient.cs | 177 +- .../Quests/Witch Apprentice/Items/Cauldron.cs | 44 +- .../Items/HagApprenticeCorpse.cs | 146 +- .../Witch Apprentice/Items/HagCauldron.cs | 55 +- .../Quests/Witch Apprentice/Items/HagStew.cs | 131 +- .../Witch Apprentice/Items/HangoverCure.cs | 130 +- .../Witch Apprentice/Items/MagicFlute.cs | 110 +- .../Witch Apprentice/Items/MoonfireBrew.cs | 46 +- .../Witch Apprentice/Mobiles/Blackheart.cs | 168 +- .../Witch Apprentice/Mobiles/Grizelda.cs | 364 +- .../Witch Apprentice/Mobiles/Zeefzorpul.cs | 66 +- .../Quests/Witch Apprentice/Objectives.cs | 871 +- .../Witch Apprentice/WitchApprenticeQuest.cs | 148 +- Scripts/Engines/RemoteAdmin/Network.cs | 458 +- Scripts/Engines/RemoteAdmin/PacketHandlers.cs | 423 +- Scripts/Engines/RemoteAdmin/Packets.cs | 262 +- .../Engines/RemoteAdmin/RemoteAdminLogging.cs | 146 +- .../Reports/Objects/Charts/BarGraph.cs | 438 +- .../Engines/Reports/Objects/Charts/Chart.cs | 80 +- .../Reports/Objects/Charts/ChartItem.cs | 66 +- .../Objects/Charts/ChartItemCollection.cs | 349 +- .../Reports/Objects/Charts/PieChart.cs | 66 +- .../Reports/Objects/Reports/ItemValue.cs | 85 +- .../Objects/Reports/ItemValueCollection.cs | 359 +- .../Engines/Reports/Objects/Reports/Report.cs | 110 +- .../Reports/Objects/Reports/ReportColumn.cs | 80 +- .../Objects/Reports/ReportColumnCollection.cs | 360 +- .../Reports/Objects/Reports/ReportItem.cs | 56 +- .../Objects/Reports/ReportItemCollection.cs | 370 +- .../Reports/Objects/Snapshots/Snapshot.cs | 74 +- .../Objects/Snapshots/SnapshotCollection.cs | 339 +- .../Objects/Snapshots/SnapshotHistory.cs | 88 +- .../Engines/Reports/Objects/Staffing/Info.cs | 142 +- .../Reports/Objects/Staffing/PageInfo.cs | 360 +- .../Objects/Staffing/PageInfoCollection.cs | 339 +- .../Reports/Objects/Staffing/QueueStatus.cs | 66 +- .../Objects/Staffing/QueueStatusCollection.cs | 340 +- .../Reports/Objects/Staffing/ResponseInfo.cs | 74 +- .../Staffing/ResponseInfoCollection.cs | 350 +- .../Reports/Objects/Staffing/StaffHistory.cs | 679 +- .../Reports/Persistance/PersistableObject.cs | 72 +- .../PersistableObjectCollection.cs | 350 +- .../Reports/Persistance/PersistableType.cs | 82 +- .../Reports/Persistance/PersistanceReader.cs | 167 +- .../Reports/Persistance/PersistanceWriter.cs | 194 +- .../Reports/Rendering/BarGraphRenderer.cs | 1813 +- .../Reports/Rendering/ChartRenderer.cs | 89 +- Scripts/Engines/Reports/Rendering/DataItem.cs | 122 +- .../Engines/Reports/Rendering/HtmlRenderer.cs | 946 +- .../Reports/Rendering/PieChartRenderer.cs | 422 +- Scripts/Engines/Reports/Reports.cs | 850 +- Scripts/Engines/Spawner/ProximitySpawner.cs | 200 +- Scripts/Engines/Spawner/Spawner.cs | 2228 +- Scripts/Engines/Spawner/SpawnerGump.cs | 493 +- Scripts/Engines/Spawner/SpawnerType.cs | 16 +- .../BasePigmentsOfTokuno.cs | 446 +- .../Treasures of Tokuno/GreaterArtifacts.cs | 1058 +- .../Treasures of Tokuno/LesserArtifacts.cs | 2032 +- .../Treasures of Tokuno/TreasuresOfTokuno.cs | 979 +- .../TreasuresOfTokunoPersistance.cs | 96 +- .../Character Statue Maker/CharacterStatue.cs | 1265 +- .../CharacterStatueMaker.cs | 274 +- .../CharacterStatuePlinth.cs | 187 +- .../Gumps/CharacterStatueGump.cs | 331 +- .../Character Statue Maker/Packets.cs | 36 +- .../Engines/VeteranRewards/RewardCategory.cs | 34 +- .../VeteranRewards/RewardChoiceGump.cs | 281 +- .../VeteranRewards/RewardConfirmGump.cs | 97 +- .../VeteranRewards/RewardDemolitionGump.cs | 109 +- Scripts/Engines/VeteranRewards/RewardEntry.cs | 124 +- Scripts/Engines/VeteranRewards/RewardList.cs | 24 +- .../VeteranRewards/RewardNoticeGump.cs | 48 +- .../VeteranRewards/RewardOptionGump.cs | 142 +- .../Engines/VeteranRewards/RewardSystem.cs | 1006 +- Scripts/Engines/Virtues/Compassion.cs | 62 +- Scripts/Engines/Virtues/Honor.cs | 815 +- Scripts/Engines/Virtues/Justice.cs | 392 +- Scripts/Engines/Virtues/Sacrifice.cs | 305 +- Scripts/Engines/Virtues/Valor.cs | 239 +- Scripts/Engines/Virtues/VirtueGump.cs | 296 +- Scripts/Engines/Virtues/VirtueHelper.cs | 255 +- Scripts/Engines/Virtues/VirtueInfoGump.cs | 168 +- Scripts/Engines/Virtues/VirtueStatusGump.cs | 178 +- Scripts/Gumps/AddDoorGump.cs | 197 +- Scripts/Gumps/AddGump.cs | 396 +- Scripts/Gumps/AdminGump.cs | 5990 ++--- Scripts/Gumps/BanDurationGump.cs | 396 +- Scripts/Gumps/BaseConfirmGump.cs | 148 +- Scripts/Gumps/BaseGridGump.cs | 279 +- Scripts/Gumps/BaseImageTileButtonsGump.cs | 199 +- Scripts/Gumps/CategorizedAddGump.cs | 643 +- Scripts/Gumps/ClientGump.cs | 470 +- Scripts/Gumps/CommentsGump.cs | 195 +- Scripts/Gumps/ConfirmBreakCrystalGump.cs | 78 +- Scripts/Gumps/ConfirmHeritageGump.cs | 117 +- Scripts/Gumps/ConfirmHouseResize.cs | 264 +- Scripts/Gumps/ConfirmReleaseGump.cs | 64 +- Scripts/Gumps/DawnsMusicBoxGump.cs | 127 +- Scripts/Gumps/Go/ChildNode.cs | 52 +- Scripts/Gumps/Go/GoGump.cs | 357 +- Scripts/Gumps/Go/LocationTree.cs | 52 +- Scripts/Gumps/Go/ParentNode.cs | 84 +- Scripts/Gumps/Guilds/DeclareFealtyGump.cs | 73 +- Scripts/Gumps/Guilds/GrantGuildTitleGump.cs | 82 +- Scripts/Gumps/Guilds/GuildAbbrvPrompt.cs | 78 +- Scripts/Gumps/Guilds/GuildAcceptWarGump.cs | 96 +- .../Gumps/Guilds/GuildAdminCandidatesGump.cs | 198 +- Scripts/Gumps/Guilds/GuildCandidatesGump.cs | 44 +- Scripts/Gumps/Guilds/GuildChangeTypeGump.cs | 144 +- Scripts/Gumps/Guilds/GuildCharterGump.cs | 97 +- Scripts/Gumps/Guilds/GuildCharterPrompt.cs | 62 +- Scripts/Gumps/Guilds/GuildDeclarePeaceGump.cs | 93 +- Scripts/Gumps/Guilds/GuildDeclareWarGump.cs | 144 +- Scripts/Gumps/Guilds/GuildDeclareWarPrompt.cs | 84 +- Scripts/Gumps/Guilds/GuildDismissGump.cs | 90 +- Scripts/Gumps/Guilds/GuildGump.cs | 340 +- Scripts/Gumps/Guilds/GuildListGump.cs | 90 +- Scripts/Gumps/Guilds/GuildMobileListGump.cs | 92 +- Scripts/Gumps/Guilds/GuildNamePrompt.cs | 78 +- Scripts/Gumps/Guilds/GuildRejectWarGump.cs | 92 +- .../Guilds/GuildRescindDeclarationGump.cs | 92 +- Scripts/Gumps/Guilds/GuildRosterGump.cs | 45 +- Scripts/Gumps/Guilds/GuildTitlePrompt.cs | 68 +- Scripts/Gumps/Guilds/GuildWarAdminGump.cs | 187 +- Scripts/Gumps/Guilds/GuildWarGump.cs | 150 +- Scripts/Gumps/Guilds/GuildWebsitePrompt.cs | 58 +- Scripts/Gumps/Guilds/GuildmasterGump.cs | 294 +- .../Guilds/New Guild System/AdvancedSearch.cs | 104 +- .../Guilds/New Guild System/BaseGuildGump.cs | 220 +- .../New Guild System/BaseGuildListGump.cs | 323 +- .../New Guild System/Create Guild Gump.cs | 172 +- .../Guilds/New Guild System/DiplomacyGump.cs | 486 +- .../Guilds/New Guild System/GuildInfoGump.cs | 314 +- .../GuildInvitationRequest.cs | 101 +- .../New Guild System/GuildMemberInfoGump.cs | 407 +- .../New Guild System/GuildRosterGump.cs | 430 +- .../Guilds/New Guild System/OtherGuildInfo.cs | 1177 +- .../New Guild System/War Declaration gump.cs | 225 +- Scripts/Gumps/Guilds/RecruitTarget.cs | 164 +- Scripts/Gumps/HeritageTokenGump.cs | 902 +- Scripts/Gumps/HonorSelf.cs | 46 +- Scripts/Gumps/HouseDemolishGump.cs | 257 +- Scripts/Gumps/HouseGump.cs | 1334 +- Scripts/Gumps/HouseGumpAOS.cs | 2934 +-- Scripts/Gumps/HouseTransferGump.cs | 88 +- Scripts/Gumps/NoticeGump.cs | 70 +- Scripts/Gumps/PetResurrectGump.cs | 121 +- Scripts/Gumps/PlayerVendorGumps.cs | 2063 +- Scripts/Gumps/PolymorphGump.cs | 398 +- Scripts/Gumps/Props/PropsConfig.cs | 59 +- Scripts/Gumps/Props/PropsGump.cs | 1453 +- Scripts/Gumps/Props/SetBodyGump.cs | 480 +- Scripts/Gumps/Props/SetCustomEnumGump.cs | 67 +- Scripts/Gumps/Props/SetGump.cs | 446 +- Scripts/Gumps/Props/SetListOptionGump.cs | 260 +- Scripts/Gumps/Props/SetObjectGump.cs | 481 +- Scripts/Gumps/Props/SetObjectTarget.cs | 106 +- Scripts/Gumps/Props/SetPoint2DGump.cs | 368 +- Scripts/Gumps/Props/SetPoint3DGump.cs | 379 +- Scripts/Gumps/Props/SetTimeSpanGump.cs | 369 +- Scripts/Gumps/ReclaimVendorGump.cs | 113 +- Scripts/Gumps/RewardGump.cs | 283 +- Scripts/Gumps/RunebookGump.cs | 883 +- Scripts/Gumps/SetSecureLevelGump.cs | 146 +- Scripts/Gumps/SkillsGump.cs | 1012 +- Scripts/Gumps/TithingGump.cs | 197 +- Scripts/Gumps/ToTAdminGump.cs | 253 +- Scripts/Gumps/VendorInventoryGump.cs | 178 +- Scripts/Gumps/ViewHousesGump.cs | 506 +- .../Christmas/2010/Addons/FireFliesDeed.cs | 452 +- .../Christmas/2010/Items/AngelDecoration.cs | 50 +- .../Christmas/2010/Items/RockingHorse.cs | 50 +- .../Easter/2011/Items/DragonEasterEgg.cs | 62 +- .../Halloween/2006/Engines/TrickOrTreat.cs | 570 +- .../Halloween/2006/Items/HalloweenPumpkin.cs | 143 +- .../Halloween/2006/Items/PumpkinScarecrow.cs | 48 +- .../Halloween/2006/Items/RuinedTapestry.cs | 48 +- .../Halloween/2006/Items/TwilightLantern.cs | 67 +- .../Halloween/2009/Engines/PumpkinPatch.cs | 110 +- .../Halloween/2009/Foods/CreepyCake.cs | 58 +- .../Halloween/2009/Foods/HarvestWine.cs | 60 +- .../Halloween/2009/Foods/MrPlainsCookies.cs | 54 +- .../Halloween/2009/Foods/MurkyMilk.cs | 66 +- .../Halloween/2009/Foods/PumpkinPizza.cs | 56 +- .../Halloween/2009/Items/GrimWarning.cs | 56 +- .../Halloween/2009/Items/SkullsOnPike.cs | 56 +- .../2010/Items/ChairInAGhostCostume.cs | 48 +- .../Halloween/2010/Items/ColoredSmallWebs.cs | 50 +- .../2010/Items/ExcellentIronMaiden.cs | 48 +- .../2010/Items/HalloweenGuillotine.cs | 46 +- .../Halloween/2011/Items/BasePaintedMask.cs | 111 +- .../Halloween/2011/Items/ClownMask.cs | 48 +- .../Halloween/2011/Items/DaemonMask.cs | 49 +- .../Halloween/2011/Items/PlagueMask.cs | 48 +- .../Halloween/2011/Mobiles/PumpkinHead.cs | 201 +- .../Halloween/2012/Items/EvilJesterMask.cs | 48 +- .../Halloween/2012/Items/PorcelainMask.cs | 48 +- .../Halloween/HolidaySettings.cs | 64 +- .../Halloween/Treats/Jellybeans.cs | 58 +- .../Halloween/Treats/Lollipops.cs | 60 +- .../Halloween/Treats/NougatSwirl.cs | 59 +- .../Holiday Stuff/Halloween/Treats/Taffy.cs | 58 +- .../Halloween/Treats/WrappedCandy.cs | 58 +- .../2010/Items/AnimatedHeartShapedBox.cs | 48 +- .../Valentine/2011/Items/StValentinesBears.cs | 468 +- .../Valentine/2012/Items/CupidStatue.cs | 52 +- .../Valentine/2012/Items/HeartShapedBox.cs | 80 +- Scripts/Items/Addons/AbbatoirAddon.cs | 106 +- Scripts/Items/Addons/AddonComponent.cs | 404 +- .../Items/Addons/AddonContainerComponent.cs | 229 +- .../Items/Addons/AlchemistTableEastAddon.cs | 90 +- .../Items/Addons/AlchemistTableSouthAddon.cs | 90 +- Scripts/Items/Addons/AnvilEastAddon.cs | 90 +- Scripts/Items/Addons/AnvilSouthAddon.cs | 90 +- .../Items/Addons/ArcaneBookshelfEastAddon.cs | 92 +- .../Items/Addons/ArcaneBookshelfSouthAddon.cs | 92 +- Scripts/Items/Addons/ArcaneCircleAddon.cs | 130 +- .../Items/Addons/ArcanistStatueEastAddon.cs | 90 +- .../Items/Addons/ArcanistStatueSouthAddon.cs | 90 +- Scripts/Items/Addons/BallotBox.cs | 729 +- Scripts/Items/Addons/BaseAddon.cs | 423 +- Scripts/Items/Addons/BaseAddonContainer.cs | 492 +- .../Items/Addons/BaseAddonContainerDeed.cs | 262 +- Scripts/Items/Addons/BaseAddonDeed.cs | 198 +- Scripts/Items/Addons/BearRugs.cs | 418 +- Scripts/Items/Addons/BloodPentagram.cs | 108 +- Scripts/Items/Addons/DartBoard.cs | 324 +- Scripts/Items/Addons/ElvenBedEastAddon.cs | 92 +- Scripts/Items/Addons/ElvenBedSouthAddon.cs | 92 +- Scripts/Items/Addons/ElvenDresserEastAddon.cs | 92 +- .../Items/Addons/ElvenDresserSouthAddon.cs | 92 +- Scripts/Items/Addons/ElvenForgeAddon.cs | 90 +- .../Items/Addons/ElvenLoveseatEastAddon.cs | 92 +- .../Items/Addons/ElvenLoveseatSouthAddon.cs | 92 +- .../Addons/ElvenSpinningwheelEastAddon.cs | 213 +- .../Addons/ElvenSpinningwheelSouthAddon.cs | 217 +- Scripts/Items/Addons/ElvenStoveEastAddon.cs | 90 +- Scripts/Items/Addons/ElvenStoveSouthAddon.cs | 90 +- .../Items/Addons/ElvenWashbasinEastAddon.cs | 92 +- .../Items/Addons/ElvenWashbasinSouthAddon.cs | 92 +- .../Items/Addons/FancyElvenTableEastAddon.cs | 94 +- .../Items/Addons/FancyElvenTableSouthAddon.cs | 94 +- Scripts/Items/Addons/FireColumnAddon.cs | 90 +- Scripts/Items/Addons/FlourMillEastAddon.cs | 331 +- Scripts/Items/Addons/FlourMillSouthAddon.cs | 310 +- Scripts/Items/Addons/FlowerTapestries.cs | 362 +- Scripts/Items/Addons/GiantWebs.cs | 318 +- Scripts/Items/Addons/GozaMats.cs | 1056 +- .../Addons/GrayBrickFireplaceEastAddon.cs | 92 +- .../Addons/GrayBrickFireplaceSouthAddon.cs | 92 +- Scripts/Items/Addons/JackOLantern.cs | 136 +- Scripts/Items/Addons/LargeBedEastAddon.cs | 96 +- Scripts/Items/Addons/LargeBedSouthAddon.cs | 96 +- Scripts/Items/Addons/LargeForgeEastAddon.cs | 96 +- Scripts/Items/Addons/LargeForgeSouthAddon.cs | 96 +- .../Items/Addons/LargeStoneTableEastAddon.cs | 106 +- .../Items/Addons/LargeStoneTableSouthAddon.cs | 106 +- Scripts/Items/Addons/LoomEastAddon.cs | 120 +- Scripts/Items/Addons/LoomSouthAddon.cs | 112 +- .../Items/Addons/MediumStoneTableEastAddon.cs | 104 +- .../Addons/MediumStoneTableSouthAddon.cs | 104 +- .../Items/Addons/OrnateElvenTableEastAddon.cs | 94 +- .../Addons/OrnateElvenTableSouthAddon.cs | 94 +- Scripts/Items/Addons/ParrotPerchAddon.cs | 90 +- Scripts/Items/Addons/PentagramAddon.cs | 106 +- Scripts/Items/Addons/PickpocketDips.cs | 391 +- Scripts/Items/Addons/PyramidAddon.cs | 82 +- Scripts/Items/Addons/RejuvinationAnkhs.cs | 271 +- Scripts/Items/Addons/SHTeleporter.cs | 865 +- .../Addons/SandstoneFireplaceEastAddon.cs | 92 +- .../Addons/SandstoneFireplaceSouthAddon.cs | 92 +- .../Items/Addons/SandstoneFountainAddon.cs | 74 +- Scripts/Items/Addons/SerpentPillarAddon.cs | 72 +- Scripts/Items/Addons/ShrineOfWisdomAddon.cs | 98 +- Scripts/Items/Addons/SkullPileAddon.cs | 58 +- Scripts/Items/Addons/SmallBedEastAddon.cs | 92 +- Scripts/Items/Addons/SmallBedSouthAddon.cs | 92 +- Scripts/Items/Addons/SmallForgeAddon.cs | 90 +- Scripts/Items/Addons/SolenAntHole.cs | 263 +- .../Items/Addons/SpinningwheelEastAddon.cs | 229 +- .../Items/Addons/SpinningwheelSouthAddon.cs | 217 +- .../Items/Addons/SquirrelStatueEastAddon.cs | 90 +- .../Items/Addons/SquirrelStatueSouthAddon.cs | 90 +- .../Items/Addons/StoneFireplaceEastAddon.cs | 92 +- .../Items/Addons/StoneFireplaceSouthAddon.cs | 92 +- Scripts/Items/Addons/StoneFountainAddon.cs | 74 +- Scripts/Items/Addons/StoneOvenEastAddon.cs | 92 +- Scripts/Items/Addons/StoneOvenSouthAddon.cs | 92 +- Scripts/Items/Addons/StretchedHides.cs | 354 +- Scripts/Items/Addons/TallElvenBedEastAddon.cs | 96 +- .../Items/Addons/TallElvenBedSouthAddon.cs | 96 +- Scripts/Items/Addons/Telescope.cs | 170 +- Scripts/Items/Addons/TrainingDummies.cs | 407 +- .../Items/Addons/WarriorStatueEastAddon.cs | 90 +- .../Items/Addons/WarriorStatueSouthAddon.cs | 90 +- Scripts/Items/Addons/WaterTroughEastAddon.cs | 102 +- Scripts/Items/Addons/WaterTroughSouthAddon.cs | 102 +- Scripts/Items/Addons/WaterVat.cs | 136 +- Scripts/Items/Aquarium/Aquarium.cs | 2271 +- Scripts/Items/Aquarium/AquariumFishingNet.cs | 307 +- Scripts/Items/Aquarium/AquariumFood.cs | 45 +- Scripts/Items/Aquarium/AquariumGump.cs | 133 +- Scripts/Items/Aquarium/AquariumState.cs | 126 +- Scripts/Items/Aquarium/BaseFish.cs | 132 +- .../Aquarium/Fish/AlbinoCourtesanFish.cs | 44 +- Scripts/Items/Aquarium/Fish/AlbinoFrog.cs | 46 +- .../Items/Aquarium/Fish/BritainCrownFish.cs | 44 +- Scripts/Items/Aquarium/Fish/FandancerFish.cs | 44 +- .../Items/Aquarium/Fish/GoldenBroadtail.cs | 44 +- Scripts/Items/Aquarium/Fish/Jellyfish.cs | 44 +- Scripts/Items/Aquarium/Fish/KillerFrog.cs | 44 +- Scripts/Items/Aquarium/Fish/LongClawCrab.cs | 46 +- .../Aquarium/Fish/MakotoCourtesanFish.cs | 44 +- Scripts/Items/Aquarium/Fish/MinocBlueFish.cs | 44 +- .../Items/Aquarium/Fish/NujelmHoneyFish.cs | 44 +- Scripts/Items/Aquarium/Fish/PurpleFrog.cs | 46 +- Scripts/Items/Aquarium/Fish/RedDartFish.cs | 44 +- Scripts/Items/Aquarium/Fish/Shrimp.cs | 44 +- .../Aquarium/Fish/SmallMouthSuckerFin.cs | 44 +- Scripts/Items/Aquarium/Fish/SpeckledCrab.cs | 44 +- .../Aquarium/Fish/SpinedScratcherFish.cs | 44 +- .../Items/Aquarium/Fish/SpottedBuccaneer.cs | 44 +- .../Items/Aquarium/Fish/VesperReefTiger.cs | 44 +- .../Items/Aquarium/Fish/YellowFinBluebelly.cs | 44 +- Scripts/Items/Aquarium/FishBowl.cs | 262 +- .../Items/Aquarium/Reward Fish/BrineShrimp.cs | 44 +- Scripts/Items/Aquarium/Reward Fish/Coral.cs | 44 +- .../Aquarium/Reward Fish/FullMoonFish.cs | 44 +- .../Items/Aquarium/Reward Fish/SeaHorse.cs | 44 +- .../Aquarium/Reward Fish/StrippedFlakeFish.cs | 44 +- .../Reward Fish/StrippedSosarianSwill.cs | 44 +- .../Items/Aquarium/Rewards/AquariumMessage.cs | 54 +- .../Rewards/CaptainBlackheartsFishingPole.cs | 54 +- .../Aquarium/Rewards/CraftysFishingHat.cs | 68 +- Scripts/Items/Aquarium/Rewards/FishBones.cs | 56 +- .../Items/Aquarium/Rewards/IslandStatue.cs | 56 +- Scripts/Items/Aquarium/Rewards/Shell.cs | 56 +- Scripts/Items/Aquarium/Rewards/ToyBoat.cs | 58 +- .../Aquarium/Rewards/WaterloggedBoots.cs | 78 +- Scripts/Items/Aquarium/VacationWafer.cs | 60 +- Scripts/Items/Armor/ArmorEnums.cs | 108 +- .../Items/Armor/Artifacts/ArmorOfFortune.cs | 60 +- .../Armor/Artifacts/Craftable/BrambleCoat.cs | 66 +- .../Artifacts/Craftable/IronwoodCrown.cs | 64 +- .../Artifacts/Craftable/SongWovenMantle.cs | 58 +- .../Artifacts/Craftable/SpellWovenBritches.cs | 58 +- .../Artifacts/Craftable/StitchersMittens.cs | 57 +- .../Armor/Artifacts/GauntletsOfNobility.cs | 76 +- .../Items/Armor/Artifacts/HelmOfInsight.cs | 66 +- .../Armor/Artifacts/HolyKnightsBreastplate.cs | 62 +- .../Armor/Artifacts/InquisitorsResolution.cs | 72 +- .../Items/Armor/Artifacts/JackalsCollar.cs | 74 +- .../Items/Armor/Artifacts/LeggingsOfBane.cs | 87 +- .../Items/Armor/Artifacts/MidnightBracers.cs | 64 +- .../Artifacts/OrnateCrownOfTheHarrower.cs | 72 +- .../Armor/Artifacts/ShadowDancerLeggings.cs | 80 +- Scripts/Items/Armor/Artifacts/TunicOfFire.cs | 80 +- .../Armor/Artifacts/VoiceOfTheFallenKing.cs | 76 +- Scripts/Items/Armor/BaseArmor.cs | 3246 +-- Scripts/Items/Armor/Bone/BoneArms.cs | 78 +- Scripts/Items/Armor/Bone/BoneChest.cs | 78 +- Scripts/Items/Armor/Bone/BoneGloves.cs | 78 +- Scripts/Items/Armor/Bone/BoneLegs.cs | 74 +- Scripts/Items/Armor/Chain/ChainChest.cs | 70 +- Scripts/Items/Armor/Chain/ChainHatsuburi.cs | 66 +- Scripts/Items/Armor/Chain/ChainLegs.cs | 70 +- Scripts/Items/Armor/DaemonBone/DaemonArms.cs | 86 +- Scripts/Items/Armor/DaemonBone/DaemonChest.cs | 86 +- .../Items/Armor/DaemonBone/DaemonGloves.cs | 86 +- Scripts/Items/Armor/DaemonBone/DaemonLegs.cs | 82 +- Scripts/Items/Armor/Dragon/DragonArms.cs | 76 +- Scripts/Items/Armor/Dragon/DragonChest.cs | 76 +- Scripts/Items/Armor/Dragon/DragonGloves.cs | 76 +- Scripts/Items/Armor/Dragon/DragonHelm.cs | 76 +- Scripts/Items/Armor/Dragon/DragonLegs.cs | 72 +- .../Armor/Glasses/AnthropomorphistGlasses.cs | 70 +- Scripts/Items/Armor/Glasses/ArtsGlasses.cs | 71 +- Scripts/Items/Armor/Glasses/ElvenGlasses.cs | 206 +- .../Items/Armor/Glasses/FoldedSteelGlasses.cs | 71 +- .../Items/Armor/Glasses/LightOfWayGlasses.cs | 71 +- Scripts/Items/Armor/Glasses/LyricalGlasses.cs | 71 +- .../Items/Armor/Glasses/MaceShieldGlasses.cs | 71 +- .../Items/Armor/Glasses/MaritimeGlasses.cs | 71 +- .../Items/Armor/Glasses/NecromanticGlasses.cs | 69 +- .../Items/Armor/Glasses/PoisonedGlasses.cs | 69 +- Scripts/Items/Armor/Glasses/TradeGlasses.cs | 63 +- .../Armor/Glasses/TreasureTrinketGlasses.cs | 71 +- Scripts/Items/Armor/Glasses/WizardsGlasses.cs | 71 +- Scripts/Items/Armor/Helmets/Bascinet.cs | 70 +- Scripts/Items/Armor/Helmets/BoneHelm.cs | 72 +- Scripts/Items/Armor/Helmets/ChainCoif.cs | 68 +- Scripts/Items/Armor/Helmets/Circlet.cs | 72 +- Scripts/Items/Armor/Helmets/CloseHelm.cs | 70 +- Scripts/Items/Armor/Helmets/DaemonHelm.cs | 84 +- Scripts/Items/Armor/Helmets/GemmedCirclet.cs | 72 +- Scripts/Items/Armor/Helmets/Helmet.cs | 70 +- Scripts/Items/Armor/Helmets/LeatherCap.cs | 76 +- Scripts/Items/Armor/Helmets/NorseHelm.cs | 70 +- Scripts/Items/Armor/Helmets/OrcHelm.cs | 75 +- Scripts/Items/Armor/Helmets/PlateHelm.cs | 72 +- Scripts/Items/Armor/Helmets/RavenHelm.cs | 70 +- Scripts/Items/Armor/Helmets/RoyalCirclet.cs | 72 +- Scripts/Items/Armor/Helmets/VultureHelm.cs | 70 +- Scripts/Items/Armor/Helmets/WingedHelm.cs | 70 +- .../Items/Armor/Leather/FemaleLeafChest.cs | 74 +- .../Items/Armor/Leather/FemaleLeatherChest.cs | 74 +- Scripts/Items/Armor/Leather/LeafArms.cs | 74 +- Scripts/Items/Armor/Leather/LeafChest.cs | 74 +- Scripts/Items/Armor/Leather/LeafGloves.cs | 226 +- Scripts/Items/Armor/Leather/LeafGorget.cs | 72 +- Scripts/Items/Armor/Leather/LeafLegs.cs | 74 +- Scripts/Items/Armor/Leather/LeafTonlet.cs | 74 +- Scripts/Items/Armor/Leather/LeatherArms.cs | 76 +- .../Items/Armor/Leather/LeatherBustierArms.cs | 74 +- Scripts/Items/Armor/Leather/LeatherChest.cs | 76 +- Scripts/Items/Armor/Leather/LeatherDo.cs | 70 +- Scripts/Items/Armor/Leather/LeatherGloves.cs | 224 +- Scripts/Items/Armor/Leather/LeatherGorget.cs | 70 +- Scripts/Items/Armor/Leather/LeatherHaidate.cs | 74 +- .../Items/Armor/Leather/LeatherHiroSode.cs | 70 +- Scripts/Items/Armor/Leather/LeatherJingasa.cs | 70 +- Scripts/Items/Armor/Leather/LeatherLegs.cs | 72 +- Scripts/Items/Armor/Leather/LeatherMempo.cs | 70 +- .../Items/Armor/Leather/LeatherNinjaHood.cs | 70 +- .../Items/Armor/Leather/LeatherNinjaJacket.cs | 70 +- .../Items/Armor/Leather/LeatherNinjaMitts.cs | 98 +- .../Items/Armor/Leather/LeatherNinjaPants.cs | 70 +- Scripts/Items/Armor/Leather/LeatherShorts.cs | 74 +- Scripts/Items/Armor/Leather/LeatherSkirt.cs | 78 +- Scripts/Items/Armor/Leather/LeatherSuneate.cs | 70 +- .../Armor/Plate/DecorativePlateKabuto.cs | 66 +- Scripts/Items/Armor/Plate/FemalePlateChest.cs | 76 +- .../Items/Armor/Plate/FemaleWoodlandChest.cs | 72 +- .../Items/Armor/Plate/HeavyPlateJingasa.cs | 66 +- .../Items/Armor/Plate/LightPlateJingasa.cs | 66 +- Scripts/Items/Armor/Plate/PlateArms.cs | 74 +- .../Items/Armor/Plate/PlateBattleKabuto.cs | 66 +- Scripts/Items/Armor/Plate/PlateChest.cs | 74 +- Scripts/Items/Armor/Plate/PlateDo.cs | 66 +- Scripts/Items/Armor/Plate/PlateGloves.cs | 74 +- Scripts/Items/Armor/Plate/PlateGorget.cs | 68 +- Scripts/Items/Armor/Plate/PlateHaidate.cs | 66 +- Scripts/Items/Armor/Plate/PlateHatsuburi.cs | 66 +- Scripts/Items/Armor/Plate/PlateHiroSode.cs | 66 +- Scripts/Items/Armor/Plate/PlateLegs.cs | 70 +- Scripts/Items/Armor/Plate/PlateMempo.cs | 66 +- Scripts/Items/Armor/Plate/PlateSuneate.cs | 66 +- .../Items/Armor/Plate/SmallPlateJingasa.cs | 66 +- .../Items/Armor/Plate/StandardPlateKabuto.cs | 66 +- Scripts/Items/Armor/Plate/WoodlandArms.cs | 70 +- Scripts/Items/Armor/Plate/WoodlandChest.cs | 70 +- Scripts/Items/Armor/Plate/WoodlandGloves.cs | 70 +- Scripts/Items/Armor/Plate/WoodlandGorget.cs | 72 +- Scripts/Items/Armor/Plate/WoodlandLegs.cs | 70 +- Scripts/Items/Armor/Ranger/RangerArms.cs | 78 +- Scripts/Items/Armor/Ranger/RangerChest.cs | 78 +- Scripts/Items/Armor/Ranger/RangerGloves.cs | 74 +- Scripts/Items/Armor/Ranger/RangerGorget.cs | 72 +- Scripts/Items/Armor/Ranger/RangerLegs.cs | 78 +- Scripts/Items/Armor/Ring/RingmailArms.cs | 74 +- Scripts/Items/Armor/Ring/RingmailChest.cs | 74 +- Scripts/Items/Armor/Ring/RingmailGloves.cs | 74 +- Scripts/Items/Armor/Ring/RingmailLegs.cs | 70 +- .../Items/Armor/Studded/FemaleStuddedChest.cs | 78 +- Scripts/Items/Armor/Studded/HideChest.cs | 74 +- .../Items/Armor/Studded/HideFemaleChest.cs | 76 +- Scripts/Items/Armor/Studded/HideGloves.cs | 74 +- Scripts/Items/Armor/Studded/HideGorget.cs | 78 +- Scripts/Items/Armor/Studded/HidePants.cs | 74 +- Scripts/Items/Armor/Studded/HidePauldrons.cs | 74 +- Scripts/Items/Armor/Studded/StuddedArms.cs | 76 +- .../Items/Armor/Studded/StuddedBustierArms.cs | 74 +- Scripts/Items/Armor/Studded/StuddedChest.cs | 76 +- Scripts/Items/Armor/Studded/StuddedDo.cs | 68 +- Scripts/Items/Armor/Studded/StuddedGloves.cs | 76 +- Scripts/Items/Armor/Studded/StuddedGorget.cs | 74 +- Scripts/Items/Armor/Studded/StuddedHaidate.cs | 68 +- .../Items/Armor/Studded/StuddedHiroSode.cs | 68 +- Scripts/Items/Armor/Studded/StuddedLegs.cs | 76 +- Scripts/Items/Armor/Studded/StuddedMempo.cs | 68 +- Scripts/Items/Armor/Studded/StuddedSuneate.cs | 68 +- Scripts/Items/Body Parts/BonePile.cs | 60 +- Scripts/Items/Body Parts/Head.cs | 182 +- Scripts/Items/Body Parts/LeftArm.cs | 40 +- Scripts/Items/Body Parts/LeftLeg.cs | 40 +- Scripts/Items/Body Parts/RibCage.cs | 60 +- Scripts/Items/Body Parts/RightArm.cs | 40 +- Scripts/Items/Body Parts/RightLeg.cs | 40 +- Scripts/Items/Body Parts/Torso.cs | 42 +- Scripts/Items/Books/BaseBook.cs | 971 +- Scripts/Items/Books/BlueBook.cs | 68 +- Scripts/Items/Books/BrownBook.cs | 65 +- .../Books/Defined/BlackthornWelcomeBook.cs | 570 +- Scripts/Items/Books/Defined/BookContent.cs | 77 +- Scripts/Items/Books/Defined/DrakovsJournal.cs | 234 +- Scripts/Items/Books/Defined/FropozJournal.cs | 336 +- Scripts/Items/Books/Defined/KaburJournal.cs | 506 +- Scripts/Items/Books/Defined/LibraryBooks.cs | 12468 +++++----- .../Items/Books/Defined/NewAquariumBook.cs | 240 +- .../Defined/TranslatedGargoyleJournal.cs | 300 +- Scripts/Items/Books/RedBook.cs | 65 +- Scripts/Items/Books/TanBook.cs | 65 +- .../Decorative/ArtifactLargeVase.cs | 42 +- .../Decorative/ArtifactVase.cs | 42 +- .../Decorative/DemonSkull.cs | 42 +- .../Decorative/DirtPatch.cs | 42 +- .../Decorative/EvilIdolSkull.cs | 44 +- .../Champion Artifacts/Decorative/Futon.cs | 72 +- .../Champion Artifacts/Decorative/LavaTile.cs | 42 +- .../Champion Artifacts/Decorative/Pier.cs | 85 +- .../Decorative/SkullPole.cs | 44 +- .../Decorative/SwampTile.cs | 42 +- .../TatteredAncientMummyWrapping.cs | 46 +- .../Decorative/WallBlood.cs | 44 +- .../Decorative/WaterTile.cs | 42 +- .../Champion Artifacts/Decorative/Web.cs | 59 +- .../Decorative/WindSpirit.cs | 44 +- .../Shared/ANecromancerShroud.cs | 54 +- .../Shared/BraveKnightOfTheBritannia.cs | 79 +- .../Shared/CaptainJohnsHat.cs | 72 +- .../Shared/DetectiveBoots.cs | 75 +- .../Champion Artifacts/Shared/DjinnisRing.cs | 54 +- .../Shared/EmbroideredOakLeafCloak.cs | 58 +- .../Shared/GauntletsOfAnger.cs | 68 +- .../LieutenantOfTheBritannianRoyalGuard.cs | 58 +- .../Shared/OblivionsNeedle.cs | 60 +- .../Shared/RoyalGuardSurvivalKnife.cs | 60 +- .../Shared/SamaritanRobe.cs | 54 +- .../Shared/TheMostKnowledgePerson.cs | 58 +- .../Shared/TheRobeOfBritanniaAri.cs | 56 +- .../Unique/AcidProofRobe.cs | 61 +- .../Items/Champion Artifacts/Unique/Calm.cs | 62 +- .../Unique/CrownOfTalKeesh.cs | 68 +- .../Champion Artifacts/Unique/FangOfRactus.cs | 64 +- .../Unique/GladiatorsCollar.cs | 68 +- .../Unique/OrcChieftainHelm.cs | 79 +- .../Items/Champion Artifacts/Unique/Pacify.cs | 64 +- .../Items/Champion Artifacts/Unique/Quell.cs | 64 +- .../Unique/ShroudOfDeceit.cs | 70 +- .../Items/Champion Artifacts/Unique/Subdue.cs | 64 +- .../Clothing/Artifacts/CrimsonCincture.cs | 53 +- .../Clothing/Artifacts/DivineCountenance.cs | 90 +- .../Items/Clothing/Artifacts/HatOfTheMagi.cs | 80 +- .../Clothing/Artifacts/HuntersHeaddress.cs | 79 +- .../Clothing/Artifacts/SpiritOfTheTotem.cs | 76 +- Scripts/Items/Clothing/BaseClothing.cs | 2028 +- Scripts/Items/Clothing/Cloaks.cs | 496 +- Scripts/Items/Clothing/Hats.cs | 2119 +- Scripts/Items/Clothing/MiddleTorso.cs | 468 +- Scripts/Items/Clothing/OuterLegs.cs | 256 +- Scripts/Items/Clothing/OuterTorso.cs | 1751 +- Scripts/Items/Clothing/Pants.cs | 256 +- Scripts/Items/Clothing/Shirts.cs | 315 +- Scripts/Items/Clothing/Shoes.cs | 926 +- Scripts/Items/Clothing/Waist.cs | 225 +- Scripts/Items/Construction/Ankhs.cs | 873 +- Scripts/Items/Construction/Chairs/Benchs.cs | 46 +- Scripts/Items/Construction/Chairs/Chairs.cs | 380 +- Scripts/Items/Construction/Chairs/Stools.cs | 96 +- Scripts/Items/Construction/Chairs/Thrones.cs | 100 +- .../Decorative/DecorativeShield.cs | 839 +- .../Decorative/DecorativeWeapon.cs | 963 +- .../Decorative/PaintingPortraits.cs | 306 +- .../Items/Construction/Decorative/Tapestry.cs | 1766 +- Scripts/Items/Construction/Doors/BaseDoor.cs | 1016 +- Scripts/Items/Construction/Doors/Doors.cs | 722 +- .../Items/Construction/Doors/HouseDoors.cs | 381 +- .../Items/Construction/Doors/Portcullis.cs | 86 +- .../Items/Construction/Doors/SecretDoors.cs | 246 +- Scripts/Items/Construction/Floors/Floors.cs | 1246 +- .../Items/Construction/Misc/BarrelParts.cs | 174 +- Scripts/Items/Construction/Misc/Easle.cs | 50 +- Scripts/Items/Construction/Misc/MeltedWax.cs | 48 +- Scripts/Items/Construction/Misc/MusicStand.cs | 102 +- Scripts/Items/Construction/Misc/Obelisk.cs | 46 +- Scripts/Items/Construction/Misc/Screens.cs | 95 +- Scripts/Items/Construction/Misc/Statues.cs | 692 +- Scripts/Items/Construction/Misc/Vase.cs | 126 +- Scripts/Items/Construction/Misc/Vines.cs | 60 +- .../Construction/Ruined/RuinedItemSingle.cs | 613 +- Scripts/Items/Construction/Signs/BaseSign.cs | 40 +- .../Items/Construction/Signs/LocalizedSign.cs | 89 +- Scripts/Items/Construction/Signs/Sign.cs | 186 +- .../Items/Construction/Signs/SubtextSign.cs | 106 +- Scripts/Items/Construction/Tables/Tables.cs | 241 +- .../Items/Construction/Tables/WritingTable.cs | 50 +- Scripts/Items/Construction/Walls/BaseWall.cs | 40 +- .../Items/Construction/Walls/DarkWoodWall.cs | 86 +- .../Construction/Walls/ThickGrayStoneWall.cs | 90 +- .../Items/Construction/Walls/ThinBrickWall.cs | 118 +- .../Items/Construction/Walls/ThinStoneWall.cs | 96 +- .../Construction/Walls/WhiteStoneWall.cs | 116 +- Scripts/Items/Containers/BaseTreasureChest.cs | 340 +- Scripts/Items/Containers/Container.cs | 1963 +- .../Items/Containers/FillableContainers.cs | 3048 +-- .../Items/Containers/FurnitureContainer.cs | 854 +- Scripts/Items/Containers/LockableContainer.cs | 612 +- Scripts/Items/Containers/MarkContainer.cs | 383 +- Scripts/Items/Containers/ParagonChest.cs | 361 +- Scripts/Items/Containers/SalvageBag.cs | 713 +- Scripts/Items/Containers/Strongbox.cs | 246 +- .../Items/Containers/TrappableContainer.cs | 346 +- Scripts/Items/Containers/TreasureChest.cs | 126 +- Scripts/Items/Containers/TreasureMapChest.cs | 1097 +- .../BaseDecorationArtifact.cs | 110 +- .../DoomDecorationArtifacts.cs | 1432 +- .../SEDecorationArtifacts.cs | 3352 +-- .../StealableArtifactsSpawner.cs | 773 +- Scripts/Items/Deeds/BarkeepContract.cs | 151 +- Scripts/Items/Deeds/ClothingBlessDeed.cs | 163 +- Scripts/Items/Deeds/CommodityDeed.cs | 410 +- Scripts/Items/Deeds/DragonBardingDeed.cs | 254 +- Scripts/Items/Deeds/HairRestylingDeed.cs | 269 +- Scripts/Items/Deeds/HolidayTreeDeed.cs | 234 +- Scripts/Items/Deeds/NameChangeDeed.cs | 185 +- Scripts/Items/Deeds/NewPlayerTicket.cs | 314 +- Scripts/Items/Deeds/VendorRentalContract.cs | 562 +- Scripts/Items/Facial/Beard.cs | 558 +- Scripts/Items/Facial/Hair.cs | 883 +- Scripts/Items/Farming/FarmableCabbage.cs | 68 +- Scripts/Items/Farming/FarmableCarrot.cs | 68 +- Scripts/Items/Farming/FarmableCotton.cs | 64 +- Scripts/Items/Farming/FarmableCrop.cs | 128 +- Scripts/Items/Farming/FarmableFlax.cs | 68 +- Scripts/Items/Farming/FarmableLettuce.cs | 68 +- Scripts/Items/Farming/FarmableOnion.cs | 68 +- Scripts/Items/Farming/FarmablePumpkin.cs | 72 +- Scripts/Items/Farming/FarmableTurnip.cs | 68 +- Scripts/Items/Farming/FarmableWheat.cs | 64 +- Scripts/Items/Food/Asian.cs | 700 +- Scripts/Items/Food/Beverage.cs | 2355 +- Scripts/Items/Food/BeverageEmpty.cs | 88 +- Scripts/Items/Food/Bowls.cs | 1054 +- Scripts/Items/Food/Chocolatiering.cs | 450 +- Scripts/Items/Food/CookableFood.cs | 1501 +- Scripts/Items/Food/Cooking.cs | 870 +- Scripts/Items/Food/Food.cs | 2455 +- Scripts/Items/Food/Fruits.cs | 1270 +- Scripts/Items/Food/Vegetables.cs | 342 +- Scripts/Items/Games/Backgammon.cs | 85 +- Scripts/Items/Games/BaseBoard.cs | 217 +- Scripts/Items/Games/BasePiece.cs | 149 +- Scripts/Items/Games/CheckerBoard.cs | 68 +- Scripts/Items/Games/CheckersPieces.cs | 80 +- Scripts/Items/Games/ChessPieces.cs | 482 +- Scripts/Items/Games/Chessboard.cs | 102 +- Scripts/Items/Games/Dices.cs | 78 +- .../Games/Mahjong/MahjongDealerIndicator.cs | 94 +- Scripts/Items/Games/Mahjong/MahjongDices.cs | 69 +- Scripts/Items/Games/Mahjong/MahjongEnums.cs | 102 +- Scripts/Items/Games/Mahjong/MahjongGame.cs | 427 +- .../Games/Mahjong/MahjongPacketHandlers.cs | 341 +- .../Items/Games/Mahjong/MahjongPieceDim.cs | 67 +- Scripts/Items/Games/Mahjong/MahjongPlayers.cs | 1026 +- Scripts/Items/Games/Mahjong/MahjongTile.cs | 132 +- .../Games/Mahjong/MahjongTileTypeGenerator.cs | 42 +- .../Mahjong/MahjongWallBreakIndicator.cs | 70 +- Scripts/Items/Games/Mahjong/Packets.cs | 317 +- Scripts/Items/Gems/Amber.cs | 55 +- Scripts/Items/Gems/Amethyst.cs | 55 +- Scripts/Items/Gems/Citrine.cs | 55 +- Scripts/Items/Gems/Diamond.cs | 55 +- Scripts/Items/Gems/Emerald.cs | 55 +- Scripts/Items/Gems/Ruby.cs | 55 +- Scripts/Items/Gems/Sapphire.cs | 55 +- Scripts/Items/Gems/StarSapphire.cs | 55 +- Scripts/Items/Gems/Tourmaline.cs | 55 +- Scripts/Items/Guilds/GuildDeed.cs | 226 +- Scripts/Items/Guilds/GuildTeleporter.cs | 156 +- Scripts/Items/Guilds/Guildstone.cs | 861 +- .../Jewels/Artifacts/BraceletOfHealth.cs | 52 +- .../Artifacts/Craftable/EssenceOfBattle.cs | 52 +- .../Artifacts/Craftable/PendantOfTheMagi.cs | 56 +- .../Artifacts/Craftable/ResillientBracer.cs | 56 +- .../Jewels/Artifacts/OrnamentOfTheMagician.cs | 62 +- .../Jewels/Artifacts/RingOfTheElements.cs | 58 +- .../Items/Jewels/Artifacts/RingOfTheVile.cs | 60 +- Scripts/Items/Jewels/BaseJewel.cs | 707 +- Scripts/Items/Jewels/Beads.cs | 42 +- Scripts/Items/Jewels/Bracelet.cs | 126 +- Scripts/Items/Jewels/Earrings.cs | 126 +- Scripts/Items/Jewels/Necklace.cs | 252 +- Scripts/Items/Jewels/Ring.cs | 126 +- Scripts/Items/Lights/BaseEquippableLight.cs | 100 +- Scripts/Items/Lights/BaseLight.cs | 340 +- Scripts/Items/Lights/Brazier.cs | 54 +- Scripts/Items/Lights/BrazierTall.cs | 54 +- Scripts/Items/Lights/Candelabra.cs | 104 +- Scripts/Items/Lights/CandelabraStand.cs | 54 +- Scripts/Items/Lights/Candle.cs | 60 +- Scripts/Items/Lights/CandleLarge.cs | 60 +- Scripts/Items/Lights/CandleLong.cs | 60 +- Scripts/Items/Lights/CandleShort.cs | 60 +- Scripts/Items/Lights/CandleSkull.cs | 90 +- Scripts/Items/Lights/DarkSource.cs | 44 +- Scripts/Items/Lights/HangingLantern.cs | 56 +- Scripts/Items/Lights/HeatingStand.cs | 92 +- Scripts/Items/Lights/LampPost1.cs | 56 +- Scripts/Items/Lights/LampPost2.cs | 56 +- Scripts/Items/Lights/LampPost3.cs | 56 +- Scripts/Items/Lights/Lantern.cs | 136 +- Scripts/Items/Lights/LightSource.cs | 44 +- Scripts/Items/Lights/PaperLantern.cs | 58 +- Scripts/Items/Lights/RedHangingLantern.cs | 122 +- Scripts/Items/Lights/RoundPaperLantern.cs | 58 +- Scripts/Items/Lights/ShojiLantern.cs | 58 +- Scripts/Items/Lights/Torch.cs | 93 +- Scripts/Items/Lights/WallSconce.cs | 128 +- Scripts/Items/Lights/WallTorch.cs | 128 +- Scripts/Items/Lights/WhiteHangingLantern.cs | 122 +- Scripts/Items/Maps/BlankMap.cs | 48 +- Scripts/Items/Maps/CityMap.cs | 72 +- Scripts/Items/Maps/IndecipherableMap.cs | 60 +- Scripts/Items/Maps/LocalMap.cs | 58 +- Scripts/Items/Maps/MapItem.cs | 731 +- Scripts/Items/Maps/PresetMap.cs | 244 +- Scripts/Items/Maps/SeaChart.cs | 72 +- Scripts/Items/Maps/TreasureMap.cs | 1903 +- Scripts/Items/Maps/WorldMap.cs | 70 +- .../Minor Artifacts/AdmiralsHeartyRum.cs | 46 +- .../Items/Minor Artifacts/AlchemistsBauble.cs | 54 +- .../Minor Artifacts/ArcticDeathDealer.cs | 73 +- Scripts/Items/Minor Artifacts/BlazeOfDeath.cs | 75 +- .../Items/Minor Artifacts/BowOfTheJukaKing.cs | 58 +- .../Items/Minor Artifacts/BurglarsBandana.cs | 84 +- .../Minor Artifacts/CandelabraOfSouls.cs | 44 +- .../CaptainQuacklebushsCutlass.cs | 64 +- .../Items/Minor Artifacts/CavortingClub.cs | 64 +- Scripts/Items/Minor Artifacts/ColdBlood.cs | 69 +- .../Items/Minor Artifacts/DreadPirateHat.cs | 88 +- .../Minor Artifacts/EnchantedTitanLegBone.cs | 60 +- .../Items/Minor Artifacts/GhostShipAnchor.cs | 50 +- .../Minor Artifacts/GlovesOfThePugilist.cs | 58 +- Scripts/Items/Minor Artifacts/GoldBricks.cs | 44 +- Scripts/Items/Minor Artifacts/GwennosHarp.cs | 54 +- .../Items/Minor Artifacts/HeartOfTheLion.cs | 68 +- Scripts/Items/Minor Artifacts/IolosLute.cs | 56 +- Scripts/Items/Minor Artifacts/LunaLance.cs | 60 +- .../Items/Minor Artifacts/ML/AegisOfGrace.cs | 70 +- .../Items/Minor Artifacts/ML/BladeDance.cs | 60 +- .../Minor Artifacts/ML/BloodwoodSpirit.cs | 64 +- .../Items/Minor Artifacts/ML/Bonesmasher.cs | 58 +- Scripts/Items/Minor Artifacts/ML/Boomstick.cs | 69 +- .../Minor Artifacts/ML/BrightsightLenses.cs | 76 +- .../Items/Minor Artifacts/ML/FeyLeggings.cs | 67 +- .../Items/Minor Artifacts/ML/FleshRipper.cs | 62 +- .../Minor Artifacts/ML/HelmOfSwiftness.cs | 68 +- .../ML/MelisandesCorrodedHatchet.cs | 56 +- .../Minor Artifacts/ML/PadsOfTheCuSidhe.cs | 44 +- .../Minor Artifacts/ML/QuiverOfElements.cs | 59 +- .../Items/Minor Artifacts/ML/QuiverOfRage.cs | 61 +- .../Items/Minor Artifacts/ML/RaedsGlory.cs | 60 +- .../Minor Artifacts/ML/RighteousAnger.cs | 58 +- .../Minor Artifacts/ML/RobeOfTheEclipse.cs | 52 +- .../Minor Artifacts/ML/RobeOfTheEquinox.cs | 54 +- .../Items/Minor Artifacts/ML/SoulSeeker.cs | 71 +- Scripts/Items/Minor Artifacts/ML/TalonBite.cs | 64 +- .../Items/Minor Artifacts/ML/TotemOfVoid.cs | 70 +- .../Items/Minor Artifacts/ML/WildfireBow.cs | 67 +- Scripts/Items/Minor Artifacts/ML/Windsong.cs | 56 +- Scripts/Items/Minor Artifacts/NightsKiss.cs | 60 +- .../NoxRangersHeavyCrossbow.cs | 73 +- Scripts/Items/Minor Artifacts/OrcishVisage.cs | 66 +- .../Minor Artifacts/PhillipsWoodenSteed.cs | 46 +- Scripts/Items/Minor Artifacts/PixieSwatter.cs | 73 +- .../Items/Minor Artifacts/PolarBearMask.cs | 74 +- .../Minor Artifacts/SeahorseStatuette.cs | 46 +- .../ShieldOfInvulnerability.cs | 76 +- .../Minor Artifacts/ShipModelOfTheHMSCape.cs | 46 +- Scripts/Items/Minor Artifacts/StaffOfPower.cs | 60 +- .../Items/Minor Artifacts/VioletCourage.cs | 68 +- .../Items/Minor Artifacts/WrathOfTheDryad.cs | 69 +- Scripts/Items/Misc/AcidSlime.cs | 155 +- Scripts/Items/Misc/ArcaneGem.cs | 343 +- Scripts/Items/Misc/BankCheck.cs | 383 +- .../Bedlam/GlobOfMonstreousInterredGrizzle.cs | 45 +- .../Misc/Bedlam/GrizzledSkullCollection.cs | 45 +- .../MonsterousInterredGrizzleMaggots.cs | 45 +- Scripts/Items/Misc/Bedlam/ResolvesBridle.cs | 45 +- .../Items/Misc/Bedlam/TombstoneOfTheDamned.cs | 45 +- Scripts/Items/Misc/Beeswax.cs | 55 +- .../Items/Misc/Blighted Grove/AbscessTail.cs | 49 +- .../Items/Misc/Blighted Grove/CoilsFang.cs | 49 +- .../Blighted Grove/EternallyCorruptTree.cs | 47 +- .../Items/Misc/Blighted Grove/HydraScale.cs | 49 +- .../Blighted Grove/MelisandesFermentedWine.cs | 74 +- .../Misc/Blighted Grove/MelisandesHairDye.cs | 145 +- .../Misc/Blighted Grove/SalivasFeather.cs | 49 +- .../Blighted Grove/SamplesOfCorruptedWater.cs | 47 +- .../Items/Misc/Blighted Grove/TaintedSeeds.cs | 49 +- .../Misc/Blighted Grove/ThorvaldsMedallion.cs | 49 +- .../Misc/Blighted Grove/ThrashersTail.cs | 49 +- Scripts/Items/Misc/Blocker.cs | 149 +- Scripts/Items/Misc/Blood.cs | 80 +- Scripts/Items/Misc/Bola.cs | 378 +- Scripts/Items/Misc/BolaBall.cs | 56 +- Scripts/Items/Misc/BulletinBoards.cs | 1135 +- Scripts/Items/Misc/ClockworkAssembly.cs | 213 +- Scripts/Items/Misc/CommunicationCrystals.cs | 909 +- Scripts/Items/Misc/Corpses/Corpse.cs | 2294 +- .../Items/Misc/Corpses/CorpseNameAttribute.cs | 18 +- Scripts/Items/Misc/Corpses/DecayedCorpse.cs | 167 +- Scripts/Items/Misc/Corpses/Packets.cs | 314 +- Scripts/Items/Misc/DeceitBrazier.cs | 362 +- Scripts/Items/Misc/EffectController.cs | 613 +- Scripts/Items/Misc/EffectItem.cs | 120 +- Scripts/Items/Misc/ExecutionersCap.cs | 42 +- Scripts/Items/Misc/Firebomb.cs | 466 +- Scripts/Items/Misc/FlippableAddonAttribute.cs | 181 +- Scripts/Items/Misc/FlippableAttribute.cs | 170 +- Scripts/Items/Misc/GlassItems.cs | 2425 +- Scripts/Items/Misc/Gold.cs | 196 +- Scripts/Items/Misc/Guillotine.cs | 167 +- Scripts/Items/Misc/HairDye.cs | 265 +- Scripts/Items/Misc/HoveringWisp.cs | 45 +- Scripts/Items/Misc/IDurability.cs | 28 +- Scripts/Items/Misc/InteriorDecorator.cs | 520 +- Scripts/Items/Misc/Key.cs | 813 +- Scripts/Items/Misc/KeyRing.cs | 302 +- Scripts/Items/Misc/LOSBlocker.cs | 161 +- .../Items/Misc/Labyrinth/MinotaurArtifact.cs | 54 +- Scripts/Items/Misc/Moonstone.cs | 335 +- Scripts/Items/Misc/MoonstoneGate.cs | 116 +- Scripts/Items/Misc/MorphItem.cs | 216 +- Scripts/Items/Misc/OilCloth.cs | 239 +- Scripts/Items/Misc/Origami.cs | 378 +- Scripts/Items/Misc/Painted Caves/GrobusFur.cs | 49 +- .../Misc/Painted Caves/PrimitiveFetish.cs | 49 +- .../Palace of Paroxysmus/AcidProofRope.cs | 47 +- .../ParoxysmusCorrodedStein.cs | 45 +- .../Palace of Paroxysmus/ParoxysmusDinner.cs | 45 +- .../StringOfPartsOfParoxysmusVictims.cs | 45 +- .../Palace of Paroxysmus/SweatOfParoxysmus.cs | 45 +- Scripts/Items/Misc/PlayerVendorDeed.cs | 166 +- Scripts/Items/Misc/PowerCrystal.cs | 58 +- Scripts/Items/Misc/PowerGenerator.cs | 1078 +- .../Prism of Light/CrystallineFragments.cs | 49 +- Scripts/Items/Misc/Prism of Light/IcyHeart.cs | 45 +- .../Items/Misc/Prism of Light/LuckyDagger.cs | 45 +- .../Misc/Prism of Light/ProtectorsEssence.cs | 45 +- .../Misc/Prism of Light/ShimmeringCrystal.cs | 60 +- Scripts/Items/Misc/PublicMoongate.cs | 825 +- Scripts/Items/Misc/Rares.cs | 1417 +- Scripts/Items/Misc/Scales.cs | 145 +- Scripts/Items/Misc/SerpentPillar.cs | 153 +- Scripts/Items/Misc/SpecialBeardDye.cs | 257 +- Scripts/Items/Misc/SpecialHairDye.cs | 258 +- Scripts/Items/Misc/Static.cs | 152 +- Scripts/Items/Misc/SwarmOfFlies.cs | 46 +- Scripts/Items/Misc/Teleporter.cs | 2287 +- .../Misc/The Citadel/DragonFlameSectBadge.cs | 47 +- .../Items/Misc/The Citadel/OrdersFromMinax.cs | 47 +- .../Misc/The Citadel/SerpentFangSectBadge.cs | 47 +- .../Misc/The Citadel/TigerClawSectBadge.cs | 47 +- .../TravestysCollectionOfShells.cs | 45 +- .../The Citadel/TravestysFineTeakwoodTray.cs | 45 +- .../The Citadel/TravestysSushiPreparations.cs | 45 +- Scripts/Items/Misc/TrashBarrel.cs | 219 +- Scripts/Items/Misc/TrashChest.cs | 84 +- Scripts/Items/Misc/TribalBerry.cs | 65 +- Scripts/Items/Misc/TribalPaint.cs | 141 +- .../Misc/Twisted Weald/HornOfTheDreadhorn.cs | 47 +- .../Twisted Weald/MangledHeadOfDreadhorn.cs | 47 +- .../Misc/Twisted Weald/TaintedMushroom.cs | 47 +- Scripts/Items/Misc/UnholyBone.cs | 192 +- Scripts/Items/Misc/WarningItem.cs | 326 +- Scripts/Items/Misc/Waypoint.cs | 245 +- Scripts/Items/Misc/WindChimes.cs | 288 +- .../New Haven Quest Rewards/AmeliasToolbox.cs | 48 +- .../ArmsOfArmstrong.cs | 60 +- .../BagOfNecromancerReagents.cs | 60 +- .../BagOfSmokeBombs.cs | 54 +- .../BraceletOfResilience.cs | 56 +- .../BulwarkLeggings.cs | 60 +- .../ChurchillsWarMace.cs | 54 +- .../ClaspOfConcentration.cs | 54 +- .../New Haven Quest Rewards/EmberStaff.cs | 56 +- .../EscutcheonDeAriadne.cs | 60 +- .../GlovesOfSafeguarding.cs | 60 +- .../HallowedSpellbook.cs | 48 +- .../HammerOfHephaestus.cs | 111 +- .../New Haven Quest Rewards/HealersTouch.cs | 60 +- .../New Haven Quest Rewards/Heartseeker.cs | 54 +- .../New Haven Quest Rewards/JacobsPickaxe.cs | 54 +- .../JocklesQuicksword.cs | 52 +- .../PhilosophersHat.cs | 60 +- .../New Haven Quest Rewards/RecarosRiposte.cs | 52 +- .../RingOfTheSavant.cs | 52 +- .../SilverSerpentBlade.cs | 52 +- .../New Haven Quest Rewards/TheDragonsTail.cs | 56 +- .../TunicOfGuarding.cs | 60 +- .../New Haven Quest Rewards/TwilightJacket.cs | 58 +- .../WalkersLeggings.cs | 56 +- .../Items/PlantsFlowers/Potted/EmptyPots.cs | 84 +- .../PlantsFlowers/Potted/PottedCactus.cs | 252 +- .../PlantsFlowers/Potted/PottedPlants.cs | 126 +- .../Items/PlantsFlowers/Potted/PottedTrees.cs | 84 +- Scripts/Items/Quivers/BaseQuiver.cs | 763 +- Scripts/Items/Quivers/ElvenQuiver.cs | 48 +- Scripts/Items/Quivers/QuiverOfBlight.cs | 57 +- Scripts/Items/Quivers/QuiverOfFire.cs | 57 +- Scripts/Items/Quivers/QuiverOfIce.cs | 57 +- Scripts/Items/Quivers/QuiverOfLightning.cs | 57 +- Scripts/Items/Resources/Arrows/Arrow.cs | 60 +- Scripts/Items/Resources/Arrows/Bolt.cs | 60 +- Scripts/Items/Resources/Arrows/Feather.cs | 61 +- Scripts/Items/Resources/Arrows/Shaft.cs | 60 +- .../Items/Resources/Blacksmithing/Ingots.cs | 844 +- Scripts/Items/Resources/Blacksmithing/Ore.cs | 1441 +- .../Items/Resources/Blacksmithing/Scales.cs | 514 +- Scripts/Items/Resources/Fishing/BigFish.cs | 123 +- Scripts/Items/Resources/Fishing/Fish.cs | 65 +- Scripts/Items/Resources/Fishing/MagicFish.cs | 297 +- Scripts/Items/Resources/Masonry/Granite.cs | 616 +- Scripts/Items/Resources/MiscMLResources.cs | 2087 +- .../Resources/Reagents/BagOfAllReagents.cs | 74 +- .../Resources/Reagents/BagOfNecroReagents.cs | 58 +- .../Items/Resources/Reagents/BagOfReagents.cs | 64 +- .../Items/Resources/Reagents/BaseReagent.cs | 50 +- Scripts/Items/Resources/Reagents/BatWing.cs | 53 +- .../Items/Resources/Reagents/BlackPearl.cs | 52 +- Scripts/Items/Resources/Reagents/Bloodmoss.cs | 53 +- .../Items/Resources/Reagents/DaemonBlood.cs | 53 +- .../Items/Resources/Reagents/DaemonBone.cs | 53 +- Scripts/Items/Resources/Reagents/DeadWood.cs | 52 +- .../Items/Resources/Reagents/DragonsBlood.cs | 60 +- Scripts/Items/Resources/Reagents/Garlic.cs | 53 +- Scripts/Items/Resources/Reagents/Ginseng.cs | 53 +- Scripts/Items/Resources/Reagents/GraveDust.cs | 53 +- .../Items/Resources/Reagents/MandrakeRoot.cs | 53 +- .../Items/Resources/Reagents/Nightshade.cs | 53 +- .../Items/Resources/Reagents/NoxCrystal.cs | 53 +- Scripts/Items/Resources/Reagents/PigIron.cs | 53 +- .../Items/Resources/Reagents/SpidersSilk.cs | 53 +- .../Items/Resources/Reagents/SulfurousAsh.cs | 53 +- Scripts/Items/Resources/Tailor/BoltOfCloth.cs | 96 +- Scripts/Items/Resources/Tailor/Bone.cs | 59 +- Scripts/Items/Resources/Tailor/Cloth.cs | 97 +- Scripts/Items/Resources/Tailor/Cotton.cs | 181 +- Scripts/Items/Resources/Tailor/Flax.cs | 167 +- Scripts/Items/Resources/Tailor/Hides.cs | 455 +- Scripts/Items/Resources/Tailor/Leathers.cs | 370 +- Scripts/Items/Resources/Tailor/UncutCloth.cs | 96 +- Scripts/Items/Resources/Tailor/Wool.cs | 250 +- .../Items/Resources/Tailor/YarnsAndThreads.cs | 366 +- Scripts/Items/Shields/Artifacts/Aegis.cs | 66 +- .../Items/Shields/Artifacts/ArcaneShield.cs | 66 +- Scripts/Items/Shields/BaseShield.cs | 288 +- Scripts/Items/Shields/BronzeShield.cs | 62 +- Scripts/Items/Shields/Buckler.cs | 62 +- Scripts/Items/Shields/ChaosShield.cs | 108 +- Scripts/Items/Shields/HeaterShield.cs | 62 +- Scripts/Items/Shields/MetalKiteShield.cs | 80 +- Scripts/Items/Shields/MetalShield.cs | 62 +- Scripts/Items/Shields/OrderShield.cs | 112 +- Scripts/Items/Shields/WoodenKiteShield.cs | 66 +- Scripts/Items/Shields/WoodenShield.cs | 62 +- .../Blacksmith Items/Misc/AnvilForge.cs | 92 +- .../Blacksmith Items/Misc/LargeForge.cs | 624 +- Scripts/Items/Skill Items/Camping/Bedroll.cs | 194 +- Scripts/Items/Skill Items/Camping/Campfire.cs | 306 +- Scripts/Items/Skill Items/Camping/Kindling.cs | 173 +- .../Skill Items/Carpenter Items/Board.cs | 641 +- .../Carpenter Items/TaxidermyKit.cs | 984 +- .../Items/Skill Items/Fishing/FishingPole.cs | 98 +- .../Fishing/Misc/MessageInABottle.cs | 169 +- Scripts/Items/Skill Items/Fishing/Misc/SOS.cs | 470 +- .../Items/Skill Items/Fishing/Misc/Sextant.cs | 245 +- .../Fishing/Misc/ShipwreckedItem.cs | 114 +- .../Fishing/Misc/SpecialFishingNet.cs | 811 +- .../Harvest Tools/BaseHarvestTool.cs | 395 +- .../Harvest Tools/GargoylesPickaxe.cs | 92 +- .../Harvest Tools/ProspectorsTool.cs | 281 +- .../Items/Skill Items/Harvest Tools/Shovel.cs | 54 +- .../Harvest Tools/SturdyPickaxe.cs | 86 +- .../Skill Items/Harvest Tools/SturdyShovel.cs | 58 +- Scripts/Items/Skill Items/Lumberjack/Log.cs | 597 +- .../Skill Items/Magical/BookOfBushido.cs | 62 +- .../Skill Items/Magical/BookOfChivalry.cs | 62 +- .../Skill Items/Magical/BookOfNinjitsu.cs | 63 +- .../Skill Items/Magical/Misc/BlankScroll.cs | 58 +- .../Items/Skill Items/Magical/Misc/Bottle.cs | 59 +- .../Skill Items/Magical/Misc/Moongate.cs | 759 +- .../Skill Items/Magical/Misc/PotionKeg.cs | 548 +- .../Skill Items/Magical/Misc/RecallRune.cs | 510 +- .../Skill Items/Magical/MysticSpellbook.cs | 66 +- .../Magical/NecromancerSpellbook.cs | 62 +- .../Potions/Agility Potions/AgilityPotion.cs | 46 +- .../Agility Potions/BaseAgilityPotion.cs | 86 +- .../Agility Potions/GreaterAgilityPotion.cs | 46 +- .../Skill Items/Magical/Potions/BasePotion.cs | 414 +- .../BaseConflagrationPotion.cs | 517 +- .../ConflagrationPotion.cs | 48 +- .../GreaterConflagrationPotion.cs | 48 +- .../BaseConfusionBlastPotion.cs | 288 +- .../ConfusionBlastPotion.cs | 46 +- .../GreaterConfusionBlastPotion.cs | 46 +- .../Potions/Cure Potions/BaseCurePotion.cs | 150 +- .../Potions/Cure Potions/CurePotion.cs | 72 +- .../Potions/Cure Potions/GreaterCurePotion.cs | 74 +- .../Potions/Cure Potions/LesserCurePotion.cs | 66 +- .../Magical/Potions/DarkglowPotion.cs | 52 +- .../Explosion Potions/BaseExplosionPotion.cs | 501 +- .../Explosion Potions/ExplosionPotion.cs | 46 +- .../GreaterExplosionPotion.cs | 46 +- .../LesserExplosionPotion.cs | 46 +- .../Potions/Heal Potions/BaseHealPotion.cs | 126 +- .../Potions/Heal Potions/GreaterHealPotion.cs | 48 +- .../Potions/Heal Potions/HealPotion.cs | 48 +- .../Potions/Heal Potions/LesserHealPotion.cs | 48 +- .../Magical/Potions/InvisibilityPotion.cs | 167 +- .../Skill Items/Magical/Potions/NightSight.cs | 76 +- .../Magical/Potions/ParasiticPotion.cs | 54 +- .../Poison Potions/BasePoisonPotion.cs | 68 +- .../Poison Potions/DeadlyPoisonPotion.cs | 48 +- .../Poison Potions/GreaterPoisonPotion.cs | 48 +- .../Poison Potions/LesserPoisonPotion.cs | 48 +- .../Potions/Poison Potions/PoisonPotion.cs | 48 +- .../Refresh Potions/BaseRefreshPotion.cs | 70 +- .../Potions/Refresh Potions/RefreshPotion.cs | 44 +- .../Refresh Potions/TotalRefreshPotion.cs | 44 +- .../Strength Potions/BaseStrengthPotion.cs | 86 +- .../Strength Potions/GreaterStrengthPotion.cs | 46 +- .../Strength Potions/StrengthPotion.cs | 46 +- Scripts/Items/Skill Items/Magical/Runebook.cs | 928 +- .../Scrolls/Eighth Circle/EarthquakeScroll.cs | 50 +- .../Eighth Circle/EnergyVortexScroll.cs | 50 +- .../Eighth Circle/ResurrectionScroll.cs | 50 +- .../Eighth Circle/SummonAirElementalScroll.cs | 50 +- .../Eighth Circle/SummonDaemonScroll.cs | 50 +- .../SummonEarthElementalScroll.cs | 50 +- .../SummonFireElementalScroll.cs | 50 +- .../SummonWaterElementalScroll.cs | 50 +- .../Fifth Circle/BladeSpiritsScroll.cs | 50 +- .../Scrolls/Fifth Circle/DispelFieldScroll.cs | 50 +- .../Scrolls/Fifth Circle/IncognitoScroll.cs | 50 +- .../Fifth Circle/MagicReflectScroll.cs | 50 +- .../Scrolls/Fifth Circle/MindBlastScroll.cs | 50 +- .../Scrolls/Fifth Circle/ParalyzeScroll.cs | 50 +- .../Scrolls/Fifth Circle/PoisonFieldScroll.cs | 50 +- .../Fifth Circle/SummonCreatureScroll.cs | 50 +- .../Scrolls/First Circle/ClumsyScroll.cs | 50 +- .../Scrolls/First Circle/CreateFoodScroll.cs | 50 +- .../Scrolls/First Circle/FeeblemindScroll.cs | 50 +- .../Scrolls/First Circle/HealScroll.cs | 50 +- .../Scrolls/First Circle/MagicArrowScroll.cs | 50 +- .../Scrolls/First Circle/NightSightScroll.cs | 50 +- .../First Circle/ReactiveArmorScroll.cs | 50 +- .../Scrolls/First Circle/WeakenScroll.cs | 50 +- .../Fourth Circle/ArchProtectionScroll.cs | 50 +- .../Scrolls/Fourth Circle/ArchcureScroll.cs | 50 +- .../Scrolls/Fourth Circle/CurseScroll.cs | 50 +- .../Scrolls/Fourth Circle/FireFieldScroll.cs | 50 +- .../Fourth Circle/GreaterHealScroll.cs | 50 +- .../Scrolls/Fourth Circle/LightningScroll.cs | 50 +- .../Scrolls/Fourth Circle/ManaDrainScroll.cs | 50 +- .../Scrolls/Fourth Circle/RecallScroll.cs | 50 +- .../Scrolls/Mysticism/AnimatedWeaponScroll.cs | 58 +- .../Scrolls/Mysticism/BombardScroll.cs | 58 +- .../Scrolls/Mysticism/CleansingWindsScroll.cs | 58 +- .../Scrolls/Mysticism/EagleStrikeScroll.cs | 58 +- .../Scrolls/Mysticism/EnchantScroll.cs | 58 +- .../Scrolls/Mysticism/HailStormScroll.cs | 58 +- .../Scrolls/Mysticism/HealingStoneScroll.cs | 58 +- .../Scrolls/Mysticism/MassSleepScroll.cs | 58 +- .../Scrolls/Mysticism/NetherBoltScroll.cs | 58 +- .../Scrolls/Mysticism/NetherCycloneScroll.cs | 58 +- .../Scrolls/Mysticism/PurgeMagicScroll.cs | 58 +- .../Scrolls/Mysticism/RisingColossusScroll.cs | 58 +- .../Magical/Scrolls/Mysticism/SleepScroll.cs | 58 +- .../Scrolls/Mysticism/SpellPlagueScroll.cs | 58 +- .../Scrolls/Mysticism/SpellTriggerScroll.cs | 58 +- .../Scrolls/Mysticism/StoneFormScroll.cs | 58 +- .../Scrolls/Necromancy/AnimateDeadScroll.cs | 50 +- .../Scrolls/Necromancy/BloodOathScroll.cs | 50 +- .../Scrolls/Necromancy/CorpseSkinScroll.cs | 50 +- .../Scrolls/Necromancy/CurseWeaponScroll.cs | 50 +- .../Scrolls/Necromancy/EvilOmenScroll.cs | 50 +- .../Scrolls/Necromancy/ExorcismScroll.cs | 48 +- .../Scrolls/Necromancy/HorrificBeastScroll.cs | 50 +- .../Scrolls/Necromancy/LichFormScroll.cs | 50 +- .../Scrolls/Necromancy/MindRotScroll.cs | 50 +- .../Scrolls/Necromancy/PainSpikeScroll.cs | 50 +- .../Scrolls/Necromancy/PoisonStrikeScroll.cs | 50 +- .../Scrolls/Necromancy/StrangleScroll.cs | 50 +- .../Necromancy/SummonFamiliarScroll.cs | 50 +- .../Necromancy/VampiricEmbraceScroll.cs | 50 +- .../Necromancy/VengefulSpiritScroll.cs | 50 +- .../Scrolls/Necromancy/WitherScroll.cs | 50 +- .../Scrolls/Necromancy/WraithFormScroll.cs | 50 +- .../Scrolls/Second Circle/AgilityScroll.cs | 50 +- .../Scrolls/Second Circle/CunningScroll.cs | 50 +- .../Scrolls/Second Circle/CureScroll.cs | 50 +- .../Scrolls/Second Circle/HarmScroll.cs | 50 +- .../Scrolls/Second Circle/MagicTrapScroll.cs | 50 +- .../Second Circle/MagicUnTrapScroll.cs | 50 +- .../Scrolls/Second Circle/ProtectionScroll.cs | 50 +- .../Scrolls/Second Circle/StrengthScroll.cs | 50 +- .../Seventh Circle/ChainLightningScroll.cs | 50 +- .../Seventh Circle/EnergyFieldScroll.cs | 50 +- .../Seventh Circle/FlamestrikeScroll.cs | 50 +- .../Seventh Circle/GateTravelScroll.cs | 50 +- .../Seventh Circle/ManaVampireScroll.cs | 50 +- .../Seventh Circle/MassDispelScroll.cs | 50 +- .../Seventh Circle/MeteorStormScroll.cs | 50 +- .../Scrolls/Seventh Circle/PolymorphScroll.cs | 50 +- .../Scrolls/Sixth Circle/DispelScroll.cs | 50 +- .../Scrolls/Sixth Circle/EnergyBoltScroll.cs | 50 +- .../Scrolls/Sixth Circle/ExplosionScroll.cs | 50 +- .../Sixth Circle/InvisibilityScroll.cs | 50 +- .../Scrolls/Sixth Circle/MarkScroll.cs | 50 +- .../Scrolls/Sixth Circle/MassCurseScroll.cs | 50 +- .../Sixth Circle/ParalyzeFieldSpell.cs | 50 +- .../Scrolls/Sixth Circle/RevealScroll.cs | 50 +- .../Magical/Scrolls/SpellScroll.cs | 125 +- .../Magical/Scrolls/SpellweavingScrolls.cs | 1118 +- .../Scrolls/Third Circle/BlessScroll.cs | 50 +- .../Scrolls/Third Circle/FireballScroll.cs | 50 +- .../Scrolls/Third Circle/MagicLockScroll.cs | 50 +- .../Scrolls/Third Circle/PoisonScroll.cs | 50 +- .../Scrolls/Third Circle/TelekinisisScroll.cs | 50 +- .../Scrolls/Third Circle/TeleportScroll.cs | 50 +- .../Scrolls/Third Circle/UnlockScroll.cs | 50 +- .../Scrolls/Third Circle/WallOfStoneScroll.cs | 50 +- .../Items/Skill Items/Magical/Spellbook.cs | 1662 +- .../Skill Items/Magical/SpellweavingBook.cs | 60 +- Scripts/Items/Skill Items/Misc/Bandage.cs | 1064 +- Scripts/Items/Skill Items/Misc/FireHorn.cs | 339 +- .../Items/Skill Items/Misc/RecipeScroll.cs | 190 +- Scripts/Items/Skill Items/Misc/RepairDeed.cs | 469 +- .../Musical Instruments/BambooFlute.cs | 46 +- .../Musical Instruments/BaseInstrument.cs | 1135 +- .../Skill Items/Musical Instruments/Drums.cs | 46 +- .../Skill Items/Musical Instruments/Harp.cs | 46 +- .../Musical Instruments/LapHarp.cs | 46 +- .../Skill Items/Musical Instruments/Lute.cs | 46 +- .../Musical Instruments/Tambourine.cs | 46 +- .../Musical Instruments/TambourineTassel.cs | 46 +- Scripts/Items/Skill Items/Ninjitsu/EggBomb.cs | 126 +- Scripts/Items/Skill Items/Ninjitsu/Fukiya.cs | 209 +- .../Items/Skill Items/Ninjitsu/FukiyaDarts.cs | 167 +- .../Skill Items/Ninjitsu/LeatherNinjaBelt.cs | 230 +- .../Skill Items/Ninjitsu/NinjaWeapons.cs | 542 +- .../Items/Skill Items/Ninjitsu/Shuriken.cs | 169 +- .../Items/Skill Items/Ninjitsu/SmokeBomb.cs | 116 +- .../Specialized/GlassblowingBook.cs | 89 +- .../Skill Items/Specialized/MasonryBook.cs | 89 +- Scripts/Items/Skill Items/Specialized/Sand.cs | 67 +- .../Skill Items/Specialized/SandMiningBook.cs | 89 +- .../Specialized/StoneMiningBook.cs | 88 +- .../Tailor Items/Dyetubs/BlackDyeTub.cs | 44 +- .../Tailor Items/Dyetubs/BlazeDyeTub.cs | 44 +- .../Tailor Items/Dyetubs/CustomHuePicker.cs | 351 +- .../Tailor Items/Dyetubs/DyeTub.cs | 440 +- .../Tailor Items/Dyetubs/FurnitureDyeTub.cs | 106 +- .../Tailor Items/Dyetubs/LeatherDyeTub.cs | 104 +- .../Dyetubs/MetallicClothDyetub.cs | 50 +- .../Tailor Items/Dyetubs/MetallicHuePicker.cs | 123 +- .../Dyetubs/MetallicLeatherDyeTub.cs | 64 +- .../Tailor Items/Dyetubs/RewardBlackDyeTub.cs | 98 +- .../Tailor Items/Dyetubs/RunebookDyeTub.cs | 104 +- .../Tailor Items/Dyetubs/SpecialDyeTub.cs | 94 +- .../Tailor Items/Dyetubs/StatuetteDyeTub.cs | 104 +- .../Tailor Items/Dyetubs/WhiteClothDyeTub.cs | 50 +- .../Dyetubs/WhiteLeatherDyeTub.cs | 56 +- .../Tailor Items/Misc/Dressform.cs | 44 +- .../Skill Items/Tailor Items/Misc/Dyes.cs | 187 +- .../Skill Items/Tailor Items/Misc/Scissors.cs | 194 +- .../Items/Skill Items/Thief/DisguiseKit.cs | 685 +- .../Skill Items/Thief/DisguisePersistance.cs | 120 +- Scripts/Items/Skill Items/Thief/LockPick.cs | 272 +- Scripts/Items/Skill Items/Tinkering/Axle.cs | 57 +- .../Items/Skill Items/Tinkering/AxleGears.cs | 57 +- .../Items/Skill Items/Tinkering/ClockFrame.cs | 57 +- .../Items/Skill Items/Tinkering/ClockParts.cs | 57 +- Scripts/Items/Skill Items/Tinkering/Clocks.cs | 324 +- Scripts/Items/Skill Items/Tinkering/Gears.cs | 57 +- Scripts/Items/Skill Items/Tinkering/Globe.cs | 42 +- Scripts/Items/Skill Items/Tinkering/Hinge.cs | 57 +- .../Skill Items/Tinkering/SextantParts.cs | 57 +- .../Items/Skill Items/Tinkering/Springs.cs | 57 +- .../Items/Skill Items/Tinkering/Spyglass.cs | 106 +- .../Items/Skill Items/Tinkering/Utensils.cs | 426 +- .../Items/Skill Items/Tools/BaseRunicTool.cs | 1603 +- Scripts/Items/Skill Items/Tools/BaseTool.cs | 324 +- Scripts/Items/Skill Items/Tools/Blowpipe.cs | 68 +- .../Items/Skill Items/Tools/DovetailSaw.cs | 62 +- Scripts/Items/Skill Items/Tools/DrawKnife.cs | 56 +- .../Items/Skill Items/Tools/FletcherTools.cs | 62 +- .../Items/Skill Items/Tools/FlourSifter.cs | 56 +- Scripts/Items/Skill Items/Tools/Froe.cs | 56 +- Scripts/Items/Skill Items/Tools/Hammer.cs | 56 +- Scripts/Items/Skill Items/Tools/Inshave.cs | 56 +- .../Items/Skill Items/Tools/JointingPlane.cs | 62 +- .../Skill Items/Tools/MalletAndChisel.cs | 56 +- .../Items/Skill Items/Tools/MapmakersPen.cs | 64 +- .../Items/Skill Items/Tools/MortarPestle.cs | 56 +- .../Items/Skill Items/Tools/MouldingPlane.cs | 58 +- Scripts/Items/Skill Items/Tools/Nails.cs | 58 +- Scripts/Items/Skill Items/Tools/RollingPin.cs | 56 +- .../Skill Items/Tools/RunicDovetailSaw.cs | 80 +- .../Skill Items/Tools/RunicFletcherTool.cs | 80 +- .../Items/Skill Items/Tools/RunicHammer.cs | 116 +- .../Items/Skill Items/Tools/RunicSewingKit.cs | 117 +- Scripts/Items/Skill Items/Tools/Saw.cs | 58 +- Scripts/Items/Skill Items/Tools/Scorp.cs | 56 +- Scripts/Items/Skill Items/Tools/ScribesPen.cs | 64 +- Scripts/Items/Skill Items/Tools/SewingKit.cs | 56 +- Scripts/Items/Skill Items/Tools/Skillet.cs | 58 +- .../Items/Skill Items/Tools/SledgeHammer.cs | 58 +- .../Items/Skill Items/Tools/SmithHammer.cs | 62 +- .../Items/Skill Items/Tools/SmoothingPlane.cs | 58 +- .../Items/Skill Items/Tools/TinkerTools.cs | 118 +- Scripts/Items/Skill Items/Tools/Tongs.cs | 58 +- .../11th Year promo/EarringsOfProtection.cs | 180 +- .../Dawn's Music Box/DawnsMusicBox.cs | 497 +- .../Dawn's Music Box/DawnsMusicGear.cs | 209 +- .../Dawn's Music Box/DawnsMusicInfo.cs | 34 +- .../8th Anniversary Items/DupresShield.cs | 72 +- .../8th Anniversary Items/FountainOfLife.cs | 410 +- .../8th Anniversary Items/OssianGrimoire.cs | 58 +- .../8th Anniversary Items/QuiverOfInfinity.cs | 62 +- .../8th Anniversary Items/Talismans.cs | 275 +- .../AoS Promotional/HoodedShroudOfShadows.cs | 66 +- .../Special/AoS Promotional/LuckyNecklace.cs | 52 +- .../BrokenArmoire.cs | 134 +- .../Broken Furniture Collection/BrokenBed.cs | 208 +- .../BrokenBookcase.cs | 134 +- .../BrokenChestOfDrawers.cs | 134 +- .../BrokenCoveredChair.cs | 134 +- .../BrokenFallenChair.cs | 138 +- .../BrokenVanity.cs | 201 +- .../StandingBrokenChair.cs | 134 +- .../Blacksmithy/AncientSmithyHammer.cs | 194 +- .../Blacksmithy/ColoredAnvil.cs | 60 +- .../Blacksmithy/GlovesOfMining.cs | 383 +- .../Blacksmithy/PowderOfTemperament.cs | 304 +- .../JesterHatofChuckles.cs | 70 +- .../AwesomeDisturbingPortrait.cs | 297 +- .../Evil Home Decor Collection/BedOfNails.cs | 304 +- .../Evil Home Decor Collection/BoneCouch.cs | 180 +- .../Evil Home Decor Collection/BoneTable.cs | 92 +- .../Evil Home Decor Collection/BoneThrone.cs | 148 +- .../CreepyPortrait.cs | 214 +- .../DisturbingPortrait.cs | 180 +- .../HauntedMirror.cs | 176 +- .../MountedPixieBlue.cs | 146 +- .../MountedPixieGreen.cs | 146 +- .../MountedPixieLime.cs | 146 +- .../MountedPixieOrange.cs | 146 +- .../MountedPixieWhite.cs | 146 +- .../SacrificialAltar.cs | 246 +- .../UnsettlingPortrait.cs | 186 +- .../Items/Special/Gifts/HearthOfHomeFire.cs | 198 +- Scripts/Items/Special/Gifts/HolySword.cs | 62 +- .../Items/Special/Gifts/LeggingsOfEmbers.cs | 68 +- Scripts/Items/Special/Gifts/RoseOfTrinsic.cs | 332 +- Scripts/Items/Special/Gifts/SamuraiHelm.cs | 74 +- .../Items/Special/Gifts/ShaminoCrossbow.cs | 60 +- .../Items/Special/Gifts/TapestryOfSosaria.cs | 112 +- .../Special/Heritage Items/AppleTrunk.cs | 92 +- .../Heritage Items/BlueDecorativeRug.cs | 108 +- .../Special/Heritage Items/BlueFancyRug.cs | 108 +- .../Special/Heritage Items/BluePlainRug.cs | 108 +- .../Special/Heritage Items/BoilingCauldron.cs | 102 +- .../Heritage Items/CherryBlossomTree.cs | 94 +- .../Heritage Items/CherryBlossomTrunk.cs | 92 +- .../Heritage Items/CinnamonFancyRug.cs | 108 +- .../Items/Special/Heritage Items/Curtains.cs | 320 +- .../Items/Special/Heritage Items/Fountain.cs | 90 +- .../Special/Heritage Items/FruitTrees.cs | 334 +- .../Heritage Items/GoldenDecorativeRug.cs | 108 +- .../Special/Heritage Items/Guillotine.cs | 272 +- .../Special/Heritage Items/HangingAxes.cs | 200 +- .../Special/Heritage Items/HangingSwords.cs | 201 +- .../Special/Heritage Items/HouseLadder.cs | 281 +- .../Special/Heritage Items/IronMaiden.cs | 213 +- .../Special/Heritage Items/LargeFishingNet.cs | 134 +- .../Special/Heritage Items/PeachTrunk.cs | 92 +- .../Special/Heritage Items/PinkFancyRug.cs | 108 +- .../Special/Heritage Items/RedPlainRug.cs | 108 +- .../Items/Special/Heritage Items/Scarecrow.cs | 134 +- .../Special/Heritage Items/SmallFishingNet.cs | 134 +- .../Items/Special/Heritage Items/Statue.cs | 204 +- .../Special/Heritage Items/SuitOfGoldArmor.cs | 134 +- .../Heritage Items/SuitOfSilverArmor.cs | 134 +- .../Heritage Items/TableWithBlueCloth.cs | 92 +- .../Heritage Items/TableWithOrangeCloth.cs | 92 +- .../Heritage Items/TableWithPurpleCloth.cs | 92 +- .../Heritage Items/TableWithRedCloth.cs | 92 +- .../Items/Special/Heritage Items/UnmadeBed.cs | 208 +- .../Items/Special/Heritage Items/Vanity.cs | 198 +- .../Items/Special/Heritage Items/WallTorch.cs | 174 +- .../Special/Heritage Items/WoodenCoffin.cs | 244 +- Scripts/Items/Special/HeritageToken.cs | 89 +- .../Special/Holiday/Christmas/HolidayTree.cs | 513 +- Scripts/Items/Special/Holiday/GiftBox.cs | 56 +- .../Special/Holiday/GingerBreadHouseDeed.cs | 103 +- Scripts/Items/Special/Holiday/HolidayBell.cs | 179 +- Scripts/Items/Special/Holiday/HolidayFoods.cs | 282 +- .../Items/Special/Holiday/HolidayGiftBoxes.cs | 369 +- .../Special/Holiday/HolidayPottedPlant.cs | 234 +- .../Items/Special/Holiday/HolidayTimepiece.cs | 56 +- Scripts/Items/Special/Holiday/Icecicles.cs | 269 +- Scripts/Items/Special/Holiday/IcyPatch.cs | 192 +- .../Items/Special/Holiday/PKHolidayStuff.cs | 148 +- Scripts/Items/Special/Holiday/Poinsettias.cs | 88 +- Scripts/Items/Special/Holiday/SnowGlobes.cs | 533 +- Scripts/Items/Special/Holiday/SnowPiles.cs | 64 +- Scripts/Items/Special/Holiday/SnowStatue.cs | 384 +- Scripts/Items/Special/Holiday/Snowflakes.cs | 88 +- Scripts/Items/Special/Holiday/Snowman.cs | 263 +- Scripts/Items/Special/Holiday/Stockings.cs | 99 +- .../Special/Holiday/WinterGiftPackage2003.cs | 50 +- Scripts/Items/Special/Holiday/Wreath.cs | 502 +- Scripts/Items/Special/Holiday/WristWatch.cs | 56 +- .../Special/House Raffle/HouseRaffleDeed.cs | 344 +- .../House Raffle/HouseRaffleManagementGump.cs | 575 +- .../Special/House Raffle/HouseRaffleRegion.cs | 88 +- .../Special/House Raffle/HouseRaffleStone.cs | 1357 +- .../Items/Special/ML/BaseImprisonedMobile.cs | 75 +- .../Items/Special/ML/GrizzledMareStatuette.cs | 109 +- Scripts/Items/Special/ML/MinotaurHedge.cs | 47 +- Scripts/Items/Special/ML/TormentedChains.cs | 47 +- Scripts/Items/Special/MiniHouses.cs | 381 +- Scripts/Items/Special/MonsterStatuette.cs | 521 +- .../Mutation Core/PlagueBeastBackpack.cs | 298 +- .../Special/Mutation Core/PlagueBeastBlood.cs | 170 +- .../Special/Mutation Core/PlagueBeastGland.cs | 48 +- .../Special/Mutation Core/PlagueBeastHeart.cs | 126 +- .../Mutation Core/PlagueBeastInnard.cs | 252 +- .../Mutation Core/PlagueBeastMutationCore.cs | 99 +- .../Mutation Core/PlagueBeastOrgans.cs | 1063 +- .../Special/Mutation Core/PlagueBeastVein.cs | 111 +- .../Rares/Containers/BaseWaterContainer.cs | 201 +- .../Items/Special/Rares/Containers/Bucket.cs | 66 +- .../Special/Rares/Containers/ClosedBarrel.cs | 48 +- .../Rares/Containers/UnfinishedBarrel.cs | 47 +- .../Special/Rares/Containers/WaterBarrel.cs | 68 +- .../Special/Rares/Containers/WaterTub.cs | 66 +- Scripts/Items/Special/Rares/Daily/DecoRock.cs | 47 +- .../Items/Special/Rares/Daily/DecoRock2.cs | 47 +- .../Items/Special/Rares/Daily/DecoRocks.cs | 47 +- .../Items/Special/Rares/Daily/DecoRocks2.cs | 47 +- .../Items/Special/Rares/Flowers/DecoFlower.cs | 47 +- .../Special/Rares/Flowers/DecoFlower2.cs | 47 +- .../Rares/Flowers/DecoRoseOfTrinsic.cs | 47 +- .../Rares/Flowers/DecoRoseOfTrinsic2.cs | 47 +- .../Rares/Flowers/DecoRoseOfTrinsic3.cs | 47 +- .../Special/Rares/Food/BottlesOfLiquor.cs | 47 +- Scripts/Items/Special/Rares/Food/Tray2.cs | 47 +- Scripts/Items/Special/Rares/Food/Trays.cs | 47 +- .../Special/Rares/Furniture/BrokenChair.cs | 47 +- .../Special/Rares/GamePieces/Checkers.cs | 47 +- .../Special/Rares/GamePieces/Checkers2.cs | 47 +- .../Special/Rares/GamePieces/Chessmen.cs | 47 +- .../Special/Rares/GamePieces/Chessmen2.cs | 47 +- .../Special/Rares/GamePieces/Chessmen3.cs | 47 +- .../Special/Rares/Ingots/DecoGoldIngot.cs | 47 +- .../Special/Rares/Ingots/DecoGoldIngot2.cs | 47 +- .../Special/Rares/Ingots/DecoGoldIngots.cs | 47 +- .../Special/Rares/Ingots/DecoGoldIngots2.cs | 47 +- .../Special/Rares/Ingots/DecoGoldIngots3.cs | 47 +- .../Special/Rares/Ingots/DecoGoldIngots4.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngot.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngot2.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngots.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngots2.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngots3.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngots4.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngots5.cs | 47 +- .../Special/Rares/Ingots/DecoIronIngots6.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngot.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngot2.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngots.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngots2.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngots3.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngots4.cs | 47 +- .../Special/Rares/Ingots/DecoSilverIngots5.cs | 47 +- Scripts/Items/Special/Rares/Jars/EmptyJars.cs | 241 +- Scripts/Items/Special/Rares/Jars/FullJars.cs | 144 +- .../Items/Special/Rares/Jars/HalfEmptyJars.cs | 240 +- .../Special/Rares/Magic/DecoCrystalBall.cs | 47 +- .../Special/Rares/Magic/DecoMagicalCrystal.cs | 47 +- .../Items/Special/Rares/Misc/DecoSpittoon.cs | 47 +- .../Rares/PaganReagents/DecoBlackmoor.cs | 47 +- .../Rares/PaganReagents/DecoBloodspawn.cs | 47 +- .../Rares/PaganReagents/DecoBrimstone.cs | 47 +- .../Rares/PaganReagents/DecoDragonsBlood.cs | 47 +- .../Rares/PaganReagents/DecoDragonsBlood2.cs | 47 +- .../Rares/PaganReagents/DecoEyeOfNewt.cs | 47 +- .../Special/Rares/PaganReagents/DecoGarlic.cs | 47 +- .../Rares/PaganReagents/DecoGarlic2.cs | 47 +- .../Rares/PaganReagents/DecoGarlicBulb.cs | 47 +- .../Rares/PaganReagents/DecoGarlicBulb2.cs | 47 +- .../Rares/PaganReagents/DecoGinseng.cs | 47 +- .../Rares/PaganReagents/DecoGinseng2.cs | 47 +- .../Rares/PaganReagents/DecoGinsengRoot.cs | 47 +- .../Rares/PaganReagents/DecoGinsengRoot2.cs | 47 +- .../Rares/PaganReagents/DecoMandrake.cs | 47 +- .../Rares/PaganReagents/DecoMandrake2.cs | 47 +- .../Rares/PaganReagents/DecoMandrake3.cs | 47 +- .../Rares/PaganReagents/DecoMandrakeRoot.cs | 47 +- .../Rares/PaganReagents/DecoMandrakeRoot2.cs | 47 +- .../Rares/PaganReagents/DecoNightshade.cs | 47 +- .../Rares/PaganReagents/DecoNightshade2.cs | 47 +- .../Rares/PaganReagents/DecoNightshade3.cs | 47 +- .../Rares/PaganReagents/DecoObsidian.cs | 47 +- .../Special/Rares/PaganReagents/DecoPumice.cs | 47 +- .../Rares/PaganReagents/DecoWyrmsHeart.cs | 47 +- .../Items/Special/Rares/PlayingCards/Cards.cs | 47 +- .../Special/Rares/PlayingCards/Cards2.cs | 47 +- .../Special/Rares/PlayingCards/Cards3.cs | 47 +- .../Special/Rares/PlayingCards/Cards4.cs | 47 +- .../Special/Rares/PlayingCards/Cards5.cs | 47 +- .../Rares/PlayingCards/PlayingCards.cs | 47 +- .../Rares/PlayingCards/PlayingCards2.cs | 47 +- Scripts/Items/Special/Rares/Stables/Bridle.cs | 47 +- .../Items/Special/Rares/Stables/Bridle2.cs | 47 +- .../Items/Special/Rares/Stables/DecoHay.cs | 47 +- .../Items/Special/Rares/Stables/DecoHay2.cs | 47 +- .../Special/Rares/Stables/DecoHorseDung.cs | 47 +- .../Rares/TarotCards/DecoDeckOfTarot.cs | 47 +- .../Rares/TarotCards/DecoDeckOfTarot2.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot2.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot3.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot4.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot5.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot6.cs | 47 +- .../Special/Rares/TarotCards/DecoTarot7.cs | 47 +- .../Items/Special/Rares/Tinker/ArrowShafts.cs | 47 +- .../Special/Rares/Tinker/CrossbowBolts.cs | 47 +- .../Special/Rares/Tinker/EmptyToolKit.cs | 47 +- .../Special/Rares/Tinker/EmptyToolKit2.cs | 47 +- .../Items/Special/Rares/Tinker/Lockpicks.cs | 47 +- Scripts/Items/Special/Rares/Tinker/ToolKit.cs | 47 +- Scripts/Items/Special/RewardCake.cs | 69 +- .../Items/Special/Solen Items/BagOfSending.cs | 469 +- .../Special/Solen Items/BallOfSummoning.cs | 918 +- .../Special/Solen Items/BraceletOfBinding.cs | 923 +- .../Special/Solen Items/MessageHelper.cs | 32 +- .../Solen Items/PowderOfTranslocation.cs | 196 +- .../Items/Special/Solen Items/ZoogiFungus.cs | 58 +- Scripts/Items/Special/SoulStone.cs | 1920 +- .../Special/Special Scrolls/PowerScroll.cs | 406 +- .../Special Scrolls/ScrollofAlacrity.cs | 206 +- .../Special Scrolls/ScrollofTranscendence.cs | 247 +- .../Special/Special Scrolls/SpecialScroll.cs | 256 +- .../Special/Special Scrolls/StatScroll.cs | 187 +- .../Valentines/2007/RedVelvetGiftBox.cs | 95 +- .../Special/Valentines/2007/RoseInAVase.cs | 52 +- .../Special/Valentines/2007/ValentinesCard.cs | 322 +- .../Veteran Rewards/AnkhOfSacrifice.cs | 542 +- .../Items/Special/Veteran Rewards/Banner.cs | 772 +- .../Veteran Rewards/BloodyPentagram.cs | 300 +- .../Items/Special/Veteran Rewards/Brazier.cs | 387 +- .../Items/Special/Veteran Rewards/Cannon.cs | 932 +- .../Veteran Rewards/CommodityDeedBox.cs | 100 +- .../Veteran Rewards/ContestMiniHouse.cs | 216 +- .../Veteran Rewards/DecorativeShield.cs | 808 +- .../Special/Veteran Rewards/FlamingHead.cs | 424 +- .../Veteran Rewards/HangingSkeleton.cs | 787 +- .../Special/Veteran Rewards/MiningCart.cs | 694 +- .../Special/Veteran Rewards/MinotaurStatue.cs | 293 +- .../Special/Veteran Rewards/PottedCactus.cs | 289 +- .../Special/Veteran Rewards/StoneAnkh.cs | 431 +- .../Special/Veteran Rewards/TreeStump.cs | 467 +- .../Special/Veteran Rewards/WallBanner.cs | 996 +- .../Veteran Rewards/WeaponEngravingTool.cs | 571 +- Scripts/Items/Suits/AdminRobe.cs | 40 +- Scripts/Items/Suits/BaseSuit.cs | 134 +- Scripts/Items/Suits/CounselorRobe.cs | 40 +- Scripts/Items/Suits/DeathShroud.cs | 40 +- Scripts/Items/Suits/DupreSuit.cs | 40 +- Scripts/Items/Suits/GMRobe.cs | 40 +- Scripts/Items/Suits/LordBlackthorneSuit.cs | 40 +- Scripts/Items/Suits/LordBritishSuit.cs | 40 +- Scripts/Items/Suits/SeerRobe.cs | 40 +- Scripts/Items/Talismans/BaseTalisman.cs | 2147 +- .../Items/Talismans/Items/EnchantedSwitch.cs | 46 +- Scripts/Items/Talismans/Items/HollowPrism.cs | 47 +- .../Items/Talismans/Items/JeweledFiligree.cs | 47 +- Scripts/Items/Talismans/Items/RunedPrism.cs | 47 +- Scripts/Items/Talismans/Items/RunedSwitch.cs | 126 +- Scripts/Items/Talismans/RandomTalisman.cs | 94 +- Scripts/Items/Talismans/TalismanAttribute.cs | 182 +- Scripts/Items/Talismans/TalismanSlayer.cs | 172 +- Scripts/Items/Talismans/TalismanSummons.cs | 1250 +- Scripts/Items/Traps/BaseTrap.cs | 125 +- Scripts/Items/Traps/FireColumnTrap.cs | 175 +- Scripts/Items/Traps/FlameSpurtTrap.cs | 263 +- Scripts/Items/Traps/GasTrap.cs | 178 +- Scripts/Items/Traps/GiantSpikeTrap.cs | 67 +- Scripts/Items/Traps/MushroomTrap.cs | 87 +- Scripts/Items/Traps/SawTrap.cs | 145 +- Scripts/Items/Traps/SpikeTrap.cs | 243 +- Scripts/Items/Traps/StoneFaceTrap.cs | 261 +- .../TreasureChests/TreasureChestLevel1.cs | 176 +- .../TreasureChests/TreasureChestLevel2.cs | 231 +- .../TreasureChests/TreasureChestLevel3.cs | 257 +- .../TreasureChests/TreasureChestLevel4.cs | 269 +- Scripts/Items/Wands/BaseWand.cs | 463 +- Scripts/Items/Wands/ClumsyWand.cs | 48 +- Scripts/Items/Wands/FeebleWand.cs | 48 +- Scripts/Items/Wands/FireballWand.cs | 48 +- Scripts/Items/Wands/GreaterHealWand.cs | 48 +- Scripts/Items/Wands/HarmWand.cs | 48 +- Scripts/Items/Wands/HealWand.cs | 48 +- Scripts/Items/Wands/IDWand.cs | 72 +- Scripts/Items/Wands/LightningWand.cs | 48 +- Scripts/Items/Wands/MagicArrowWand.cs | 48 +- Scripts/Items/Wands/ManaDrainWand.cs | 48 +- Scripts/Items/Wands/RandomWand.cs | 56 +- Scripts/Items/Wands/WandTarget.cs | 32 +- Scripts/Items/Wands/WeaknessWand.cs | 48 +- .../Items/Weapons/Abilities/ArmorIgnore.cs | 47 +- .../Items/Weapons/Abilities/ArmorPierce.cs | 62 +- .../Items/Weapons/Abilities/BleedAttack.cs | 193 +- Scripts/Items/Weapons/Abilities/Block.cs | 156 +- .../Items/Weapons/Abilities/ConcussionBlow.cs | 70 +- .../Items/Weapons/Abilities/CrushingBlow.cs | 47 +- .../Items/Weapons/Abilities/DefenseMastery.cs | 139 +- Scripts/Items/Weapons/Abilities/Disarm.cs | 116 +- Scripts/Items/Weapons/Abilities/Dismount.cs | 155 +- Scripts/Items/Weapons/Abilities/Disrobe.cs | 68 +- Scripts/Items/Weapons/Abilities/DoubleShot.cs | 97 +- .../Items/Weapons/Abilities/DoubleStrike.cs | 83 +- Scripts/Items/Weapons/Abilities/DualWield.cs | 109 +- Scripts/Items/Weapons/Abilities/Feint.cs | 112 +- .../Weapons/Abilities/FrenziedWhirlwind.cs | 241 +- .../Weapons/Abilities/InfectiousStrike.cs | 124 +- .../Items/Weapons/Abilities/MortalStrike.cs | 129 +- Scripts/Items/Weapons/Abilities/MovingShot.cs | 58 +- .../Items/Weapons/Abilities/NerveStrike.cs | 131 +- .../Items/Weapons/Abilities/ParalyzingBlow.cs | 186 +- .../Items/Weapons/Abilities/RidingSwipe.cs | 123 +- .../Items/Weapons/Abilities/ShadowStrike.cs | 83 +- .../Items/Weapons/Abilities/TalonStrike.cs | 155 +- .../Items/Weapons/Abilities/WeaponAbility.cs | 948 +- .../Weapons/Abilities/WhirlwindAttack.cs | 116 +- .../Weapons/Artifacts/AxeOfTheHeavens.cs | 60 +- .../Weapons/Artifacts/BladeOfInsanity.cs | 64 +- .../Weapons/Artifacts/BladeOfTheRighteous.cs | 68 +- .../Items/Weapons/Artifacts/BoneCrusher.cs | 68 +- .../Weapons/Artifacts/BreathOfTheDead.cs | 60 +- .../Items/Weapons/Artifacts/Frostbringer.cs | 69 +- .../Weapons/Artifacts/LegacyOfTheDreadLord.cs | 68 +- .../Items/Weapons/Artifacts/SerpentsFang.cs | 79 +- .../Items/Weapons/Artifacts/StaffOfTheMagi.cs | 79 +- .../Weapons/Artifacts/TheBeserkersMaul.cs | 56 +- .../Weapons/Artifacts/TheDragonSlayer.cs | 77 +- .../Items/Weapons/Artifacts/TheDryadBow.cs | 87 +- .../Items/Weapons/Artifacts/TheTaskmaster.cs | 71 +- .../Items/Weapons/Artifacts/TitansHammer.cs | 60 +- .../Items/Weapons/Artifacts/ZyronicClaw.cs | 75 +- Scripts/Items/Weapons/Axes/Axe.cs | 72 +- Scripts/Items/Weapons/Axes/BaseAxe.cs | 268 +- Scripts/Items/Weapons/Axes/BattleAxe.cs | 74 +- Scripts/Items/Weapons/Axes/DoubleAxe.cs | 72 +- Scripts/Items/Weapons/Axes/ExecutionersAxe.cs | 72 +- Scripts/Items/Weapons/Axes/GuardianAxe.cs | 48 +- Scripts/Items/Weapons/Axes/Hatchet.cs | 72 +- Scripts/Items/Weapons/Axes/HeavyOrnateAxe.cs | 46 +- Scripts/Items/Weapons/Axes/LargeBattleAxe.cs | 72 +- Scripts/Items/Weapons/Axes/Pickaxe.cs | 82 +- Scripts/Items/Weapons/Axes/SingingAxe.cs | 46 +- Scripts/Items/Weapons/Axes/ThunderingAxe.cs | 46 +- Scripts/Items/Weapons/Axes/TwoHandedAxe.cs | 72 +- Scripts/Items/Weapons/Axes/WarAxe.cs | 84 +- Scripts/Items/Weapons/BaseMeleeWeapon.cs | 94 +- Scripts/Items/Weapons/BaseWeapon.cs | 6649 ++--- Scripts/Items/Weapons/Fists.cs | 507 +- Scripts/Items/Weapons/HitLower.cs | 138 +- Scripts/Items/Weapons/Knives/BaseKnife.cs | 80 +- Scripts/Items/Weapons/Knives/ButcherKnife.cs | 72 +- Scripts/Items/Weapons/Knives/Cleaver.cs | 76 +- Scripts/Items/Weapons/Knives/Dagger.cs | 78 +- Scripts/Items/Weapons/Knives/SkinningKnife.cs | 72 +- .../Items/Weapons/Knives/ThrowingDagger.cs | 199 +- .../Artifacts/BlightGrippedLongbow.cs | 56 +- .../ML Weapons/Artifacts/ColdForgedBlade.cs | 67 +- .../ML Weapons/Artifacts/LuminousRuneBlade.cs | 67 +- .../Artifacts/OverseerSunderedBlade.cs | 69 +- .../ML Weapons/Artifacts/PhantomStaff.cs | 65 +- .../ML Weapons/Artifacts/RuneCarvingKnife.cs | 56 +- .../ML Weapons/Artifacts/ShardTrasher.cs | 56 +- .../Artifacts/SilvanisFeywoodBow.cs | 65 +- .../ML Weapons/Artifacts/TheNightReaper.cs | 56 +- .../Items/Weapons/ML Weapons/AssassinSpike.cs | 76 +- .../Weapons/ML Weapons/ButchersWarCleaver.cs | 54 +- .../Items/Weapons/ML Weapons/DiamondMace.cs | 72 +- .../ML Weapons/ElvenCompositeLongbow.cs | 82 +- .../Items/Weapons/ML Weapons/ElvenMachete.cs | 76 +- .../Weapons/ML Weapons/ElvenSpellblade.cs | 76 +- Scripts/Items/Weapons/ML Weapons/Leafblade.cs | 76 +- .../Weapons/ML Weapons/MagicalShortbow.cs | 80 +- Scripts/Items/Weapons/ML Weapons/OrnateAxe.cs | 76 +- .../Weapons/ML Weapons/RadiantScimitar.cs | 76 +- Scripts/Items/Weapons/ML Weapons/RuneBlade.cs | 78 +- .../Items/Weapons/ML Weapons/WarCleaver.cs | 82 +- Scripts/Items/Weapons/ML Weapons/WildStaff.cs | 72 +- Scripts/Items/Weapons/Maces/BaseBashing.cs | 87 +- Scripts/Items/Weapons/Maces/Club.cs | 72 +- Scripts/Items/Weapons/Maces/EmeraldMace.cs | 46 +- Scripts/Items/Weapons/Maces/FireworksWand.cs | 212 +- Scripts/Items/Weapons/Maces/HammerPick.cs | 74 +- Scripts/Items/Weapons/Maces/Mace.cs | 72 +- Scripts/Items/Weapons/Maces/MagicWand.cs | 70 +- Scripts/Items/Weapons/Maces/Maul.cs | 76 +- Scripts/Items/Weapons/Maces/RubyMace.cs | 46 +- Scripts/Items/Weapons/Maces/SapphireMace.cs | 46 +- Scripts/Items/Weapons/Maces/Scepter.cs | 72 +- .../Items/Weapons/Maces/SilverEtchedMace.cs | 46 +- Scripts/Items/Weapons/Maces/WarHammer.cs | 76 +- Scripts/Items/Weapons/Maces/WarMace.cs | 72 +- Scripts/Items/Weapons/PoleArms/Bardiche.cs | 72 +- Scripts/Items/Weapons/PoleArms/BasePoleArm.cs | 200 +- Scripts/Items/Weapons/PoleArms/Halberd.cs | 72 +- Scripts/Items/Weapons/PoleArms/Scythe.cs | 78 +- .../Items/Weapons/Ranged/AssassinsShortbow.cs | 48 +- Scripts/Items/Weapons/Ranged/BarbedLongbow.cs | 46 +- Scripts/Items/Weapons/Ranged/BaseRanged.cs | 371 +- Scripts/Items/Weapons/Ranged/Bow.cs | 88 +- Scripts/Items/Weapons/Ranged/CompositeBow.cs | 82 +- Scripts/Items/Weapons/Ranged/Crossbow.cs | 82 +- Scripts/Items/Weapons/Ranged/FrozenLongbow.cs | 48 +- Scripts/Items/Weapons/Ranged/HeavyCrossbow.cs | 82 +- Scripts/Items/Weapons/Ranged/JukaBow.cs | 151 +- .../Weapons/Ranged/LightweightShortbow.cs | 46 +- .../Items/Weapons/Ranged/LongbowOfMight.cs | 46 +- .../Items/Weapons/Ranged/MysticalShortbow.cs | 48 +- .../Items/Weapons/Ranged/RangersShortbow.cs | 46 +- .../Items/Weapons/Ranged/RepeatingCrossbow.cs | 80 +- Scripts/Items/Weapons/Ranged/SlayerLongbow.cs | 46 +- Scripts/Items/Weapons/SE Weapons/Bokuto.cs | 76 +- Scripts/Items/Weapons/SE Weapons/Daisho.cs | 78 +- Scripts/Items/Weapons/SE Weapons/Kama.cs | 84 +- Scripts/Items/Weapons/SE Weapons/Lajatang.cs | 84 +- Scripts/Items/Weapons/SE Weapons/NoDachi.cs | 78 +- Scripts/Items/Weapons/SE Weapons/Nunchaku.cs | 76 +- Scripts/Items/Weapons/SE Weapons/Sai.cs | 84 +- Scripts/Items/Weapons/SE Weapons/Tekagi.cs | 84 +- Scripts/Items/Weapons/SE Weapons/Tessen.cs | 80 +- Scripts/Items/Weapons/SE Weapons/Tetsubo.cs | 80 +- Scripts/Items/Weapons/SE Weapons/Wakizashi.cs | 78 +- Scripts/Items/Weapons/SE Weapons/Yumi.cs | 88 +- Scripts/Items/Weapons/SlayerEntry.cs | 174 +- Scripts/Items/Weapons/SlayerGroup.cs | 358 +- Scripts/Items/Weapons/SlayerName.cs | 62 +- .../Items/Weapons/SpearsAndForks/BaseSpear.cs | 87 +- .../Weapons/SpearsAndForks/BladedStaff.cs | 74 +- .../SpearsAndForks/DoubleBladedStaff.cs | 72 +- Scripts/Items/Weapons/SpearsAndForks/Pike.cs | 72 +- .../Items/Weapons/SpearsAndForks/Pitchfork.cs | 76 +- .../Weapons/SpearsAndForks/ShortSpear.cs | 74 +- Scripts/Items/Weapons/SpearsAndForks/Spear.cs | 72 +- .../Weapons/SpearsAndForks/TribalSpear.cs | 78 +- .../Items/Weapons/SpearsAndForks/WarFork.cs | 78 +- Scripts/Items/Weapons/Staves/BaseStaff.cs | 60 +- Scripts/Items/Weapons/Staves/BlackStaff.cs | 72 +- Scripts/Items/Weapons/Staves/GlacialStaff.cs | 55 +- Scripts/Items/Weapons/Staves/GnarledStaff.cs | 72 +- Scripts/Items/Weapons/Staves/QuarterStaff.cs | 72 +- .../Items/Weapons/Staves/ShepherdsCrook.cs | 269 +- .../Weapons/Swords/AdventurersMachete.cs | 46 +- Scripts/Items/Weapons/Swords/BaseSword.cs | 76 +- Scripts/Items/Weapons/Swords/BoneHarvester.cs | 76 +- Scripts/Items/Weapons/Swords/BoneMachete.cs | 94 +- Scripts/Items/Weapons/Swords/Broadsword.cs | 76 +- .../Weapons/Swords/ChargedAssassinSpike.cs | 46 +- .../Weapons/Swords/CorruptedRuneBlade.cs | 48 +- Scripts/Items/Weapons/Swords/CrescentBlade.cs | 76 +- Scripts/Items/Weapons/Swords/Cutlass.cs | 76 +- .../Items/Weapons/Swords/DarkglowScimitar.cs | 46 +- .../Items/Weapons/Swords/DiseasedMachete.cs | 46 +- .../Items/Weapons/Swords/FierySpellblade.cs | 46 +- Scripts/Items/Weapons/Swords/IcyScimitar.cs | 46 +- Scripts/Items/Weapons/Swords/IcySpellblade.cs | 46 +- Scripts/Items/Weapons/Swords/Katana.cs | 76 +- .../Items/Weapons/Swords/KnightsWarCleaver.cs | 46 +- Scripts/Items/Weapons/Swords/Kryss.cs | 86 +- Scripts/Items/Weapons/Swords/Lance.cs | 82 +- .../Items/Weapons/Swords/LeafbladeOfEase.cs | 46 +- Scripts/Items/Weapons/Swords/Longsword.cs | 76 +- Scripts/Items/Weapons/Swords/Luckblade.cs | 46 +- .../Items/Weapons/Swords/MacheteOfDefense.cs | 46 +- .../Weapons/Swords/MagekillerAssassinSpike.cs | 46 +- .../Weapons/Swords/MagekillerLeafblade.cs | 46 +- .../Items/Weapons/Swords/MagesRuneBlade.cs | 46 +- Scripts/Items/Weapons/Swords/OrcishMachete.cs | 48 +- .../Weapons/Swords/RuneBladeOfKnowledge.cs | 46 +- Scripts/Items/Weapons/Swords/Runesabre.cs | 48 +- Scripts/Items/Weapons/Swords/Scimitar.cs | 76 +- .../Weapons/Swords/SerratedWarCleaver.cs | 46 +- .../Weapons/Swords/SpellbladeOfDefense.cs | 46 +- Scripts/Items/Weapons/Swords/ThinLongsword.cs | 72 +- .../Items/Weapons/Swords/TrueAssassinSpike.cs | 48 +- Scripts/Items/Weapons/Swords/TrueLeafblade.cs | 46 +- .../Weapons/Swords/TrueRadiantScimitar.cs | 46 +- .../Items/Weapons/Swords/TrueSpellblade.cs | 48 +- .../Items/Weapons/Swords/TrueWarCleaver.cs | 48 +- .../Items/Weapons/Swords/TwinklingScimitar.cs | 46 +- Scripts/Items/Weapons/Swords/VikingSword.cs | 76 +- .../Weapons/Swords/WoundingAssassinSpike.cs | 46 +- Scripts/Items/Weapons/WeaponEnums.cs | 112 +- .../Items/Weapons/Wooden/AncientWildStaff.cs | 46 +- .../Weapons/Wooden/ArcanistsWildStaff.cs | 48 +- .../Items/Weapons/Wooden/HardenedWildStaff.cs | 46 +- .../Items/Weapons/Wooden/ThornedWildStaff.cs | 46 +- Scripts/Misc/AOS.cs | 2848 ++- Scripts/Misc/AccountPrompt.cs | 56 +- Scripts/Misc/Animations.cs | 44 +- Scripts/Misc/Assistants.cs | 287 +- Scripts/Misc/AttackMessage.cs | 84 +- Scripts/Misc/AutoRestart.cs | 118 +- Scripts/Misc/AutoSave.cs | 280 +- Scripts/Misc/Broadcasts.cs | 56 +- Scripts/Misc/BuffIcons.cs | 469 +- Scripts/Misc/CharacterCreation.cs | 3341 +-- Scripts/Misc/Cleanup.cs | 278 +- Scripts/Misc/ClientVerification.cs | 277 +- Scripts/Misc/CrashGuard.cs | 387 +- Scripts/Misc/CurrentExpansion.cs | 55 +- Scripts/Misc/DataPath.cs | 164 +- Scripts/Misc/DispellableAttribute.cs | 8 +- Scripts/Misc/DispellableFieldAttribute.cs | 8 +- Scripts/Misc/DoorGenerator.cs | 981 +- Scripts/Misc/Email.cs | 148 +- Scripts/Misc/Fastwalk.cs | 50 +- Scripts/Misc/FoodDecay.cs | 66 +- Scripts/Misc/Geometry.cs | 422 +- .../Gifts/Winter2004/DecorativeTopiary.cs | 64 +- .../Misc/Gifts/Winter2004/FestiveCactus.cs | 64 +- .../Winter2004/LightOfTheWinterSolstice.cs | 159 +- Scripts/Misc/Gifts/Winter2004/Mistletoe.cs | 522 +- .../Gifts/Winter2004/PileOfGlacialSnow.cs | 243 +- Scripts/Misc/Gifts/Winter2004/SnowPile.cs | 223 +- Scripts/Misc/Gifts/Winter2004/SnowyTree.cs | 66 +- Scripts/Misc/Gifts/Winter2004/Winter2004.cs | 66 +- Scripts/Misc/Guild.cs | 2901 +-- Scripts/Misc/HardwareInfo.cs | 256 +- Scripts/Misc/Keywords.cs | 92 +- Scripts/Misc/LanguageStatistics.cs | 618 +- Scripts/Misc/LightCycle.cs | 219 +- Scripts/Misc/LoginStats.cs | 43 +- Scripts/Misc/Loot.cs | 1572 +- Scripts/Misc/LootPack.cs | 1847 +- Scripts/Misc/MapDefinitions.cs | 83 +- Scripts/Misc/MapUO.cs | 197 +- Scripts/Misc/MondainsLegacy.cs | 124 +- Scripts/Misc/NameVerification.cs | 343 +- Scripts/Misc/Notoriety.cs | 706 +- Scripts/Misc/Paperdoll.cs | 43 +- Scripts/Misc/Poison.cs | 234 +- Scripts/Misc/ProfanityProtection.cs | 210 +- Scripts/Misc/Profile.cs | 136 +- Scripts/Misc/ProtocolExtensions.cs | 96 +- Scripts/Misc/RaceDefinitions.cs | 621 +- Scripts/Misc/RegenRates.cs | 310 +- Scripts/Misc/RenameRequests.cs | 81 +- Scripts/Misc/ServerList.cs | 314 +- Scripts/Misc/ShardPoller.cs | 1129 +- Scripts/Misc/ShrinkTable.cs | 124 +- Scripts/Misc/SkillCheck.cs | 764 +- Scripts/Misc/SocketOptions.cs | 51 +- Scripts/Misc/TextDefinition.cs | 350 +- Scripts/Misc/Titles.cs | 673 +- Scripts/Misc/ToggleItem.cs | 172 +- Scripts/Misc/TreasureMapProtection.cs | 115 +- Scripts/Misc/ValidationQueue.cs | 76 +- Scripts/Misc/VendorGenerator.cs | 943 +- Scripts/Misc/WebStatus.cs | 287 +- Scripts/Misc/WeightOverloading.cs | 190 +- Scripts/Misc/WelcomeTimer.cs | 85 +- Scripts/Misc/uoamVendors.cs | 608 +- Scripts/Mobiles/AI/AIControlMobileTarget.cs | 49 +- Scripts/Mobiles/AI/AnimalAI.cs | 198 +- Scripts/Mobiles/AI/ArcherAI.cs | 204 +- Scripts/Mobiles/AI/BaseAI.cs | 5555 ++--- Scripts/Mobiles/AI/BerserkAI.cs | 136 +- Scripts/Mobiles/AI/HealerAI.cs | 266 +- Scripts/Mobiles/AI/MageAI.cs | 2165 +- Scripts/Mobiles/AI/MeleeAI.cs | 277 +- Scripts/Mobiles/AI/OppositionGroup.cs | 214 +- Scripts/Mobiles/AI/PredatorAI.cs | 151 +- Scripts/Mobiles/AI/SpeedInfo.cs | 366 +- Scripts/Mobiles/AI/ThiefAI.cs | 301 +- Scripts/Mobiles/AI/VendorAI.cs | 230 +- Scripts/Mobiles/Animals/Bears/BlackBear.cs | 98 +- Scripts/Mobiles/Animals/Bears/BrownBear.cs | 96 +- Scripts/Mobiles/Animals/Bears/GrizzlyBear.cs | 100 +- Scripts/Mobiles/Animals/Bears/PolarBear.cs | 100 +- Scripts/Mobiles/Animals/Birds/Chicken.cs | 94 +- Scripts/Mobiles/Animals/Birds/Crane.cs | 124 +- Scripts/Mobiles/Animals/Birds/Eagle.cs | 102 +- Scripts/Mobiles/Animals/Birds/Phoenix.cs | 110 +- Scripts/Mobiles/Animals/Canines/DireWolf.cs | 104 +- Scripts/Mobiles/Animals/Canines/GreyWolf.cs | 102 +- Scripts/Mobiles/Animals/Canines/TimberWolf.cs | 102 +- Scripts/Mobiles/Animals/Canines/WhiteWolf.cs | 102 +- Scripts/Mobiles/Animals/Cows/Bull.cs | 98 +- Scripts/Mobiles/Animals/Cows/Cow.cs | 188 +- Scripts/Mobiles/Animals/Felines/Cougar.cs | 98 +- Scripts/Mobiles/Animals/Felines/HellCat.cs | 110 +- Scripts/Mobiles/Animals/Felines/Panther.cs | 100 +- .../Animals/Felines/PredatorHellCat.cs | 108 +- .../Mobiles/Animals/Felines/SnowLeopard.cs | 102 +- Scripts/Mobiles/Animals/Misc/Boar.cs | 92 +- Scripts/Mobiles/Animals/Misc/BullFrog.cs | 102 +- Scripts/Mobiles/Animals/Misc/Dolphin.cs | 130 +- Scripts/Mobiles/Animals/Misc/Gaman.cs | 144 +- Scripts/Mobiles/Animals/Misc/GiantToad.cs | 114 +- Scripts/Mobiles/Animals/Misc/Goat.cs | 90 +- Scripts/Mobiles/Animals/Misc/Gorilla.cs | 94 +- Scripts/Mobiles/Animals/Misc/GreatHart.cs | 116 +- Scripts/Mobiles/Animals/Misc/Hind.cs | 114 +- Scripts/Mobiles/Animals/Misc/Llama.cs | 90 +- Scripts/Mobiles/Animals/Misc/MountainGoat.cs | 98 +- Scripts/Mobiles/Animals/Misc/PackHorse.cs | 327 +- Scripts/Mobiles/Animals/Misc/PackLlama.cs | 206 +- Scripts/Mobiles/Animals/Misc/Pig.cs | 88 +- Scripts/Mobiles/Animals/Misc/Sheep.cs | 163 +- Scripts/Mobiles/Animals/Misc/Walrus.cs | 98 +- Scripts/Mobiles/Animals/Mounts/BaseMount.cs | 700 +- Scripts/Mobiles/Animals/Mounts/Beetle.cs | 258 +- .../Mobiles/Animals/Mounts/DesertOstard.cs | 95 +- Scripts/Mobiles/Animals/Mounts/Ethereals.cs | 1676 +- Scripts/Mobiles/Animals/Mounts/FireSteed.cs | 132 +- .../Mobiles/Animals/Mounts/ForestOstard.cs | 95 +- .../Mobiles/Animals/Mounts/FrenziedOstard.cs | 101 +- Scripts/Mobiles/Animals/Mounts/HellSteed.cs | 96 +- Scripts/Mobiles/Animals/Mounts/Hiryu.cs | 439 +- Scripts/Mobiles/Animals/Mounts/Horse.cs | 115 +- Scripts/Mobiles/Animals/Mounts/Kirin.cs | 195 +- Scripts/Mobiles/Animals/Mounts/LesserHiryu.cs | 413 +- Scripts/Mobiles/Animals/Mounts/Nightmare.cs | 193 +- .../Mobiles/Animals/Mounts/RidableLlama.cs | 101 +- Scripts/Mobiles/Animals/Mounts/Ridgeback.cs | 119 +- .../Mobiles/Animals/Mounts/SavageRidgeback.cs | 119 +- .../Animals/Mounts/ScaledSwampDragon.cs | 116 +- Scripts/Mobiles/Animals/Mounts/SeaHorse.cs | 61 +- Scripts/Mobiles/Animals/Mounts/SilverSteed.cs | 67 +- .../Mobiles/Animals/Mounts/SkeletalMount.cs | 110 +- Scripts/Mobiles/Animals/Mounts/SwampDragon.cs | 347 +- Scripts/Mobiles/Animals/Mounts/Unicorn.cs | 205 +- .../Animals/Mounts/War Horses/BaseWarHorse.cs | 90 +- .../Animals/Mounts/War Horses/CoMWarHorse.cs | 40 +- .../Mounts/War Horses/MinaxWarHorse.cs | 40 +- .../Animals/Mounts/War Horses/SLWarHorse.cs | 40 +- .../Animals/Mounts/War Horses/TBWarHorse.cs | 40 +- Scripts/Mobiles/Animals/Reptiles/Alligator.cs | 102 +- .../Mobiles/Animals/Reptiles/GiantSerpent.cs | 122 +- .../Mobiles/Animals/Reptiles/IceSerpent.cs | 162 +- Scripts/Mobiles/Animals/Reptiles/IceSnake.cs | 102 +- .../Mobiles/Animals/Reptiles/LavaLizard.cs | 110 +- .../Mobiles/Animals/Reptiles/LavaSerpent.cs | 116 +- Scripts/Mobiles/Animals/Reptiles/LavaSnake.cs | 104 +- .../Mobiles/Animals/Reptiles/SilverSerpent.cs | 117 +- Scripts/Mobiles/Animals/Reptiles/Snake.cs | 100 +- Scripts/Mobiles/Animals/Rodents/GiantRat.cs | 104 +- Scripts/Mobiles/Animals/Rodents/JackRabbit.cs | 116 +- Scripts/Mobiles/Animals/Rodents/Rabbit.cs | 116 +- Scripts/Mobiles/Animals/Rodents/SewerRat.cs | 102 +- Scripts/Mobiles/Animals/Slimes/Jwilson.cs | 106 +- .../Town Critters/(UO 3D Only) Parrot.cs | 108 +- Scripts/Mobiles/Animals/Town Critters/Bird.cs | 211 +- Scripts/Mobiles/Animals/Town Critters/Cat.cs | 94 +- Scripts/Mobiles/Animals/Town Critters/Dog.cs | 92 +- Scripts/Mobiles/Animals/Town Critters/Rat.cs | 98 +- Scripts/Mobiles/BaseCreature.cs | 10050 ++++---- Scripts/Mobiles/Familiars/BaseFamiliar.cs | 273 +- Scripts/Mobiles/Familiars/DarkWolf.cs | 108 +- Scripts/Mobiles/Familiars/DeathAdder.cs | 82 +- Scripts/Mobiles/Familiars/HordeMinion.cs | 284 +- Scripts/Mobiles/Familiars/ShadowWisp.cs | 158 +- Scripts/Mobiles/Familiars/VampireBat.cs | 80 +- Scripts/Mobiles/Guards/ArcherGuard.cs | 769 +- Scripts/Mobiles/Guards/BaseGuard.cs | 120 +- Scripts/Mobiles/Guards/WarriorGuard.cs | 742 +- Scripts/Mobiles/Healers/BaseHealer.cs | 246 +- Scripts/Mobiles/Healers/EvilHealer.cs | 102 +- .../Mobiles/Healers/EvilWanderingHealer.cs | 114 +- Scripts/Mobiles/Healers/FortuneTeller.cs | 122 +- Scripts/Mobiles/Healers/Healer.cs | 125 +- Scripts/Mobiles/Healers/PricedHealer.cs | 112 +- Scripts/Mobiles/Healers/WanderingHealer.cs | 111 +- Scripts/Mobiles/Monsters/AOS/AbysmalHorror.cs | 134 +- Scripts/Mobiles/Monsters/AOS/BoneDemon.cs | 112 +- .../Mobiles/Monsters/AOS/CrystalElemental.cs | 114 +- .../Mobiles/Monsters/AOS/DarknightCreeper.cs | 140 +- Scripts/Mobiles/Monsters/AOS/DemonKnight.cs | 459 +- Scripts/Mobiles/Monsters/AOS/Devourer.cs | 108 +- Scripts/Mobiles/Monsters/AOS/FleshGolem.cs | 102 +- Scripts/Mobiles/Monsters/AOS/FleshRenderer.cs | 172 +- Scripts/Mobiles/Monsters/AOS/Gibberling.cs | 104 +- Scripts/Mobiles/Monsters/AOS/GoreFiend.cs | 104 +- Scripts/Mobiles/Monsters/AOS/Impaler.cs | 136 +- .../Mobiles/Monsters/AOS/MoundOfMaggots.cs | 92 +- .../Mobiles/Monsters/AOS/PatchworkSkeleton.cs | 106 +- Scripts/Mobiles/Monsters/AOS/Ravager.cs | 98 +- Scripts/Mobiles/Monsters/AOS/Revenant.cs | 255 +- Scripts/Mobiles/Monsters/AOS/ShadowKnight.cs | 287 +- .../Mobiles/Monsters/AOS/SkitteringHopper.cs | 96 +- Scripts/Mobiles/Monsters/AOS/Treefellow.cs | 128 +- Scripts/Mobiles/Monsters/AOS/VampireBat.cs | 102 +- .../Mobiles/Monsters/AOS/WailingBanshee.cs | 104 +- .../Mobiles/Monsters/AOS/WandererOfTheVoid.cs | 114 +- Scripts/Mobiles/Monsters/Ants/AntLion.cs | 188 +- .../Ants/BlackSolenInfiltratorQueen.cs | 162 +- .../Ants/BlackSolenInfiltratorWarrior.cs | 164 +- .../Mobiles/Monsters/Ants/BlackSolenQueen.cs | 226 +- .../Monsters/Ants/BlackSolenWarrior.cs | 228 +- .../Mobiles/Monsters/Ants/BlackSolenWorker.cs | 162 +- .../Monsters/Ants/RedSolenInfiltratorQueen.cs | 160 +- .../Ants/RedSolenInfiltratorWarrior.cs | 163 +- .../Mobiles/Monsters/Ants/RedSolenQueen.cs | 226 +- .../Mobiles/Monsters/Ants/RedSolenWarrior.cs | 227 +- .../Mobiles/Monsters/Ants/RedSolenWorker.cs | 160 +- Scripts/Mobiles/Monsters/Ants/SolenHelper.cs | 134 +- .../Monsters/Arachnid/Magic/DreadSpider.cs | 112 +- .../Arachnid/Magic/TerathanAvenger.cs | 116 +- .../Arachnid/Magic/TerathanMatriarch.cs | 108 +- .../Monsters/Arachnid/Melee/FrostSpider.cs | 114 +- .../Arachnid/Melee/GiantBlackWidow.cs | 108 +- .../Monsters/Arachnid/Melee/GiantSpider.cs | 106 +- .../Monsters/Arachnid/Melee/TerathanDrone.cs | 108 +- .../Arachnid/Melee/TerathanWarrior.cs | 108 +- .../Monsters/Elemental/Magic/AcidElemental.cs | 128 +- .../Monsters/Elemental/Magic/AirElemental.cs | 122 +- .../Elemental/Magic/BloodElemental.cs | 106 +- .../Monsters/Elemental/Magic/Efreet.cs | 134 +- .../Monsters/Elemental/Magic/FireElemental.cs | 120 +- .../Monsters/Elemental/Magic/IceElemental.cs | 106 +- .../Elemental/Magic/PoisonElemental.cs | 120 +- .../Elemental/Magic/WaterElemental.cs | 114 +- .../Elemental/Melee/EarthElemental.cs | 116 +- .../Monsters/Elemental/Melee/SnowElemental.cs | 106 +- .../Monsters/Humanoid/Magic/AncientLich.cs | 162 +- .../Monsters/Humanoid/Magic/ArcaneDaemon.cs | 108 +- .../Mobiles/Monsters/Humanoid/Magic/Balron.cs | 119 +- .../Monsters/Humanoid/Magic/Betrayer.cs | 278 +- .../Mobiles/Monsters/Humanoid/Magic/Bogle.cs | 94 +- .../Monsters/Humanoid/Magic/BoneMagi.cs | 118 +- .../Mobiles/Monsters/Humanoid/Magic/Daemon.cs | 121 +- .../Monsters/Humanoid/Magic/ElderGazer.cs | 102 +- .../Monsters/Humanoid/Magic/EvilMage.cs | 111 +- .../Monsters/Humanoid/Magic/EvilMageLord.cs | 123 +- .../Monsters/Humanoid/Magic/FireGargoyle.cs | 111 +- .../Monsters/Humanoid/Magic/Gargoyle.cs | 108 +- .../Humanoid/Magic/GargoyleDestroyer.cs | 159 +- .../Humanoid/Magic/GargoyleEnforcer.cs | 116 +- .../Mobiles/Monsters/Humanoid/Magic/Gazer.cs | 104 +- .../Humanoid/Magic/GolemController.cs | 136 +- .../Monsters/Humanoid/Magic/IceFiend.cs | 104 +- .../Mobiles/Monsters/Humanoid/Magic/Imp.cs | 120 +- .../Mobiles/Monsters/Humanoid/Magic/Lich.cs | 122 +- .../Monsters/Humanoid/Magic/LichLord.cs | 120 +- .../Monsters/Humanoid/Magic/OrcishMage.cs | 156 +- .../Monsters/Humanoid/Magic/RatmanMage.cs | 124 +- .../Monsters/Humanoid/Magic/SavageShaman.cs | 457 +- .../Mobiles/Monsters/Humanoid/Magic/Shade.cs | 104 +- .../Monsters/Humanoid/Magic/SkeletalMage.cs | 116 +- .../Monsters/Humanoid/Magic/Spectre.cs | 104 +- .../Monsters/Humanoid/Magic/Succubus.cs | 176 +- .../Mobiles/Monsters/Humanoid/Magic/Titan.cs | 112 +- .../Mobiles/Monsters/Humanoid/Magic/Wraith.cs | 104 +- .../Monsters/Humanoid/Melee/ArcticOgreLord.cs | 102 +- .../Monsters/Humanoid/Melee/BoneKnight.cs | 136 +- .../Monsters/Humanoid/Melee/Brigand.cs | 162 +- .../Monsters/Humanoid/Melee/ChaosDaemon.cs | 102 +- .../Mobiles/Monsters/Humanoid/Melee/Cursed.cs | 124 +- .../Monsters/Humanoid/Melee/Cyclops.cs | 100 +- .../Monsters/Humanoid/Melee/Doppleganger.cs | 94 +- .../Monsters/Humanoid/Melee/ElfBrigand.cs | 196 +- .../Humanoid/Melee/EnslavedGargoyle.cs | 100 +- .../Mobiles/Monsters/Humanoid/Melee/Ettin.cs | 102 +- .../Monsters/Humanoid/Melee/Executioner.cs | 134 +- .../Monsters/Humanoid/Melee/FrostTroll.cs | 100 +- .../Monsters/Humanoid/Melee/GazerLarva.cs | 88 +- .../Mobiles/Monsters/Humanoid/Melee/Ghoul.cs | 100 +- .../Monsters/Humanoid/Melee/GreaterMongbat.cs | 100 +- .../Monsters/Humanoid/Melee/Guardian.cs | 135 +- .../Monsters/Humanoid/Melee/HeadlessOne.cs | 92 +- .../Monsters/Humanoid/Melee/HordeMinion.cs | 124 +- .../Monsters/Humanoid/Melee/Juggernaut.cs | 238 +- .../Humanoid/Melee/KhaldunRevenant.cs | 260 +- .../Humanoid/Melee/KhaldunSummoner.cs | 212 +- .../Monsters/Humanoid/Melee/KhaldunZealot.cs | 226 +- .../Mobiles/Monsters/Humanoid/Melee/Moloch.cs | 98 +- .../Monsters/Humanoid/Melee/Mongbat.cs | 98 +- .../Mobiles/Monsters/Humanoid/Melee/Mummy.cs | 113 +- .../Mobiles/Monsters/Humanoid/Melee/Ogre.cs | 104 +- .../Monsters/Humanoid/Melee/OgreLord.cs | 109 +- .../Mobiles/Monsters/Humanoid/Melee/Orc.cs | 192 +- .../Monsters/Humanoid/Melee/OrcBomber.cs | 231 +- .../Monsters/Humanoid/Melee/OrcBrute.cs | 232 +- .../Monsters/Humanoid/Melee/OrcCaptain.cs | 192 +- .../Monsters/Humanoid/Melee/OrcishLord.cs | 180 +- .../Mobiles/Monsters/Humanoid/Melee/Ratman.cs | 102 +- .../Monsters/Humanoid/Melee/RatmanArcher.cs | 120 +- .../Monsters/Humanoid/Melee/RestlessSoul.cs | 168 +- .../Monsters/Humanoid/Melee/RottingCorpse.cs | 112 +- .../Mobiles/Monsters/Humanoid/Melee/Savage.cs | 174 +- .../Monsters/Humanoid/Melee/SavageRider.cs | 186 +- .../Monsters/Humanoid/Melee/ShadowFiend.cs | 211 +- .../Monsters/Humanoid/Melee/SkeletalKnight.cs | 134 +- .../Monsters/Humanoid/Melee/Skeleton.cs | 124 +- .../Humanoid/Melee/SpawnedOrcishLord.cs | 63 +- .../Monsters/Humanoid/Melee/SpectralArmour.cs | 144 +- .../Monsters/Humanoid/Melee/StoneGargoyle.cs | 104 +- .../Monsters/Humanoid/Melee/StrongMongbat.cs | 98 +- .../Mobiles/Monsters/Humanoid/Melee/Troll.cs | 98 +- .../Mobiles/Monsters/Humanoid/Melee/Zombie.cs | 140 +- .../Monsters/LBR/Exodus/ExodusMinion.cs | 299 +- .../Monsters/LBR/Exodus/ExodusOverseer.cs | 285 +- .../Monsters/LBR/Jukas/ChaosDragoon.cs | 315 +- .../Monsters/LBR/Jukas/ChaosDragoonElite.cs | 377 +- .../Mobiles/Monsters/LBR/Jukas/JukaLord.cs | 190 +- .../Mobiles/Monsters/LBR/Jukas/JukaMage.cs | 300 +- .../Mobiles/Monsters/LBR/Jukas/JukaWarrior.cs | 198 +- .../Monsters/LBR/Meers/EnragedCreatures.cs | 469 +- .../Mobiles/Monsters/LBR/Meers/MeerCaptain.cs | 249 +- .../Mobiles/Monsters/LBR/Meers/MeerEternal.cs | 331 +- .../Mobiles/Monsters/LBR/Meers/MeerMage.cs | 353 +- .../Mobiles/Monsters/LBR/Meers/MeerWarrior.cs | 131 +- Scripts/Mobiles/Monsters/ML/Animal/CuSidhe.cs | 218 +- Scripts/Mobiles/Monsters/ML/Animal/Ferret.cs | 147 +- .../Monsters/ML/Animal/RagingGrizzlyBear.cs | 97 +- .../Mobiles/Monsters/ML/Animal/Squirrel.cs | 86 +- .../Monsters/ML/Bedlam/LadyJennifyr.cs | 201 +- .../Mobiles/Monsters/ML/Bedlam/LadyMarai.cs | 125 +- .../Monsters/ML/Bedlam/MasterJonath.cs | 142 +- .../Monsters/ML/Bedlam/MasterMikael.cs | 138 +- .../Monsters/ML/Bedlam/MasterTheophilus.cs | 135 +- .../Mobiles/Monsters/ML/Bedlam/RedDeath.cs | 138 +- .../Mobiles/Monsters/ML/Bedlam/SirPatrick.cs | 199 +- .../Monsters/ML/Blighted Grove/Abscess.cs | 112 +- .../Monsters/ML/Blighted Grove/Coil.cs | 155 +- .../ML/Blighted Grove/EnslavedSatyr.cs | 66 +- .../Monsters/ML/Blighted Grove/Hydra.cs | 134 +- .../Monsters/ML/Blighted Grove/InsaneDryad.cs | 70 +- .../Monsters/ML/Blighted Grove/Saliva.cs | 108 +- .../Monsters/ML/Blighted Grove/Tangle.cs | 110 +- .../Monsters/ML/Blighted Grove/Thrasher.cs | 111 +- .../ML/Humanoid/Magic/FetidEssence.cs | 168 +- .../ML/Humanoid/Magic/InterredGrizzle .cs | 276 +- .../Monsters/ML/Humanoid/Magic/MLDryad.cs | 239 +- .../Monsters/ML/Humanoid/Magic/Satyr.cs | 353 +- .../ML/Humanoid/Melee/CorruptedSoul.cs | 134 +- .../ML/Humanoid/Melee/FerelTreefellow.cs | 126 +- .../Monsters/ML/Humanoid/Melee/Minotaur.cs | 148 +- .../ML/Humanoid/Melee/MinotaurCaptain.cs | 148 +- .../ML/Humanoid/Melee/MinotaurScout.cs | 148 +- .../ML/Humanoid/Melee/PestilentBandage.cs | 120 +- .../ML/Humanoid/Melee/Tormented Minotaur.cs | 130 +- .../Monsters/ML/Humanoid/Melee/Troglodyte.cs | 114 +- .../Mobiles/Monsters/ML/Labyrinth/Miasma.cs | 177 +- Scripts/Mobiles/Monsters/ML/Labyrinth/Pyre.cs | 120 +- Scripts/Mobiles/Monsters/ML/Labyrinth/Rend.cs | 112 +- .../Monsters/ML/Misc/Magic/GreaterDragon.cs | 160 +- .../Monsters/ML/Misc/Melee/CorrosiveSlime.cs | 108 +- .../Monsters/ML/Misc/Melee/Reptalon.cs | 116 +- .../Monsters/ML/Painted Caves/Grobu.cs | 116 +- .../Mobiles/Monsters/ML/Painted Caves/Lurg.cs | 109 +- .../ML/Palace of Paroxysmus/Putrefier.cs | 138 +- .../ML/Prism of Light/CorporealBrume.cs | 122 +- .../ML/Prism of Light/CrystalDaemon.cs | 126 +- .../ML/Prism of Light/CrystalLatticeSeeker.cs | 257 +- .../ML/Prism of Light/CrystalSeaSerpent.cs | 102 +- .../ML/Prism of Light/CrystalVortex.cs | 141 +- .../Monsters/ML/Prism of Light/CrystalWisp.cs | 50 +- .../ML/Prism of Light/MantraEffervescence.cs | 104 +- .../Monsters/ML/Prism of Light/Protector.cs | 160 +- .../ML/Prism of Light/UnfrozenMummy.cs | 134 +- .../Monsters/ML/Sanctuary/Chiikkaha.cs | 84 +- .../Mobiles/Monsters/ML/Sanctuary/MougGuur.cs | 80 +- .../Mobiles/Monsters/ML/Sanctuary/Szavetra.cs | 88 +- .../Mobiles/Monsters/ML/Special/Ilhenir.cs | 871 +- .../Mobiles/Monsters/ML/Special/Meraktus.cs | 407 +- Scripts/Mobiles/Monsters/ML/Special/Twaulo.cs | 234 +- .../Monsters/ML/Twisted Weald/Changeling.cs | 490 +- .../Mobiles/Monsters/ML/Twisted Weald/Gnaw.cs | 120 +- .../Monsters/ML/Twisted Weald/Guile.cs | 130 +- .../Mobiles/Monsters/ML/Twisted Weald/Irk.cs | 128 +- .../Monsters/ML/Twisted Weald/LadyLissith.cs | 133 +- .../Monsters/ML/Twisted Weald/LadySabrix.cs | 145 +- .../Monsters/ML/Twisted Weald/Malefic.cs | 121 +- .../Mobiles/Monsters/ML/Twisted Weald/Silk.cs | 107 +- .../Monsters/ML/Twisted Weald/Spite.cs | 106 +- .../Monsters/ML/Twisted Weald/Swoop.cs | 267 +- .../Monsters/ML/Twisted Weald/Virulent.cs | 145 +- .../Monsters/Mammal/Melee/HellHound.cs | 104 +- .../Monsters/Mammal/Melee/VorpalBunny.cs | 208 +- .../Mobiles/Monsters/Misc/Magic/DarkWisp.cs | 115 +- .../Monsters/Misc/Magic/EtherealWarrior.cs | 220 +- Scripts/Mobiles/Monsters/Misc/Magic/Pixie.cs | 126 +- .../Mobiles/Monsters/Misc/Magic/ShadowWisp.cs | 136 +- Scripts/Mobiles/Monsters/Misc/Magic/Wisp.cs | 122 +- .../Monsters/Misc/Melee/AnimatedWeapon.cs | 172 +- .../Monsters/Misc/Melee/BladeSpirits.cs | 180 +- .../Mobiles/Monsters/Misc/Melee/Centaur.cs | 118 +- .../Monsters/Misc/Melee/EnergyVortex.cs | 216 +- .../Mobiles/Monsters/Misc/Melee/FrostOoze.cs | 90 +- Scripts/Mobiles/Monsters/Misc/Melee/Golem.cs | 352 +- .../Monsters/Misc/Melee/PlagueBeast.cs | 374 +- .../Monsters/Misc/Melee/PlagueBeastLord.cs | 695 +- .../Monsters/Misc/Melee/PlagueSpawn.cs | 212 +- .../Mobiles/Monsters/Misc/Melee/SandVortex.cs | 163 +- Scripts/Mobiles/Monsters/Misc/Melee/Slime.cs | 106 +- .../Ore Elementals/AgapiteElemental.cs | 114 +- .../Ore Elementals/BronzeElemental.cs | 118 +- .../Ore Elementals/CopperElemental.cs | 122 +- .../Ore Elementals/DullCopperElemental.cs | 114 +- .../Ore Elementals/GoldenElemental.cs | 114 +- .../Ore Elementals/ShadowIronElemental.cs | 146 +- .../Ore Elementals/ValoriteElemental.cs | 144 +- .../Ore Elementals/VeriteElemental.cs | 116 +- .../Mobiles/Monsters/Plant/Magic/Reaper.cs | 110 +- .../Mobiles/Monsters/Plant/Melee/BogThing.cs | 217 +- .../Mobiles/Monsters/Plant/Melee/Bogling.cs | 101 +- .../Mobiles/Monsters/Plant/Melee/Corpser.cs | 112 +- .../Mobiles/Monsters/Plant/Melee/Quagmire.cs | 112 +- .../Monsters/Plant/Melee/SwampTentacle.cs | 100 +- .../Monsters/Plant/Melee/WhippingVine.cs | 102 +- .../Monsters/Reptile/Magic/AncientWyrm.cs | 142 +- .../Monsters/Reptile/Magic/DeepSeaSerpent.cs | 116 +- .../Mobiles/Monsters/Reptile/Magic/Dragon.cs | 128 +- .../Monsters/Reptile/Magic/Leviathan.cs | 265 +- .../Reptile/Magic/OphidianArchmage.cs | 120 +- .../Monsters/Reptile/Magic/OphidianMage.cs | 122 +- .../Reptile/Magic/OphidianMatriarch.cs | 108 +- .../Monsters/Reptile/Magic/SeaSerpent.cs | 124 +- .../Reptile/Magic/SerpentineDragon.cs | 189 +- .../Monsters/Reptile/Magic/ShadowWyrm.cs | 142 +- .../Monsters/Reptile/Magic/SkeletalDragon.cs | 131 +- .../Monsters/Reptile/Magic/WhiteWyrm.cs | 128 +- .../Mobiles/Monsters/Reptile/Melee/Drake.cs | 124 +- .../Mobiles/Monsters/Reptile/Melee/Harpy.cs | 143 +- .../Mobiles/Monsters/Reptile/Melee/Kraken.cs | 114 +- .../Monsters/Reptile/Melee/Lizardman.cs | 102 +- .../Monsters/Reptile/Melee/OphidianKnight.cs | 120 +- .../Monsters/Reptile/Melee/OphidianWarrior.cs | 114 +- .../Monsters/Reptile/Melee/Scorpion.cs | 116 +- .../Monsters/Reptile/Melee/StoneHarpy.cs | 144 +- .../Mobiles/Monsters/Reptile/Melee/Wyvern.cs | 158 +- Scripts/Mobiles/Monsters/SE/BakeKitsune.cs | 447 +- .../Mobiles/Monsters/SE/DeathWatchBeetle.cs | 241 +- .../Monsters/SE/DeathWatchBeetleHatchling.cs | 184 +- Scripts/Mobiles/Monsters/SE/EliteNinja.cs | 198 +- Scripts/Mobiles/Monsters/SE/FanDancer.cs | 291 +- Scripts/Mobiles/Monsters/SE/FireBeetle.cs | 199 +- Scripts/Mobiles/Monsters/SE/Kappa.cs | 346 +- Scripts/Mobiles/Monsters/SE/KazeKemono.cs | 282 +- Scripts/Mobiles/Monsters/SE/LadyOfTheSnow.cs | 251 +- Scripts/Mobiles/Monsters/SE/Oni.cs | 166 +- Scripts/Mobiles/Monsters/SE/RaiJu.cs | 199 +- Scripts/Mobiles/Monsters/SE/RevenantLion.cs | 204 +- Scripts/Mobiles/Monsters/SE/Ronin.cs | 191 +- Scripts/Mobiles/Monsters/SE/RuneBeetle.cs | 388 +- Scripts/Mobiles/Monsters/SE/TsukiWolf.cs | 323 +- Scripts/Mobiles/Monsters/SE/Yamandon.cs | 327 +- Scripts/Mobiles/Monsters/SE/YomotsuElder.cs | 224 +- Scripts/Mobiles/Monsters/SE/YomotsuPriest.cs | 226 +- Scripts/Mobiles/Monsters/SE/YomotsuWarrior.cs | 212 +- .../Monsters/Summons/SummonedAirElemental.cs | 102 +- .../Monsters/Summons/SummonedDaemon.cs | 96 +- .../Summons/SummonedEarthElemental.cs | 86 +- .../Monsters/Summons/SummonedFireElemental.cs | 92 +- .../Summons/SummonedWaterElemental.cs | 96 +- Scripts/Mobiles/PlayerMobile.cs | 9424 +++---- Scripts/Mobiles/Special/Barracoon.cs | 366 +- Scripts/Mobiles/Special/BaseChampion.cs | 621 +- Scripts/Mobiles/Special/BaseShieldGuard.cs | 251 +- .../Mobiles/Special/CapturedHordeMinion.cs | 54 +- Scripts/Mobiles/Special/ChaosGuard.cs | 54 +- Scripts/Mobiles/Special/DarkGuardian.cs | 117 +- Scripts/Mobiles/Special/Dummy.cs | 214 +- Scripts/Mobiles/Special/DummySpecific.cs | 1562 +- Scripts/Mobiles/Special/Harrower.cs | 1240 +- Scripts/Mobiles/Special/HarrowerTentacles.cs | 307 +- Scripts/Mobiles/Special/LordOaks.cs | 359 +- Scripts/Mobiles/Special/Mephitis.cs | 126 +- Scripts/Mobiles/Special/Neira.cs | 530 +- Scripts/Mobiles/Special/OrderGuard.cs | 54 +- Scripts/Mobiles/Special/Paragon.cs | 327 +- Scripts/Mobiles/Special/Rikktor.cs | 245 +- Scripts/Mobiles/Special/Semidar.cs | 216 +- Scripts/Mobiles/Special/Serado.cs | 275 +- Scripts/Mobiles/Special/ServantOfSemidar.cs | 68 +- Scripts/Mobiles/Special/Silvani.cs | 198 +- Scripts/Mobiles/Special/Wanderer.cs | 99 +- Scripts/Mobiles/Townfolk/Actor.cs | 94 +- Scripts/Mobiles/Townfolk/Artist.cs | 101 +- Scripts/Mobiles/Townfolk/Banker.cs | 873 +- Scripts/Mobiles/Townfolk/BaseEscortable.cs | 1344 +- Scripts/Mobiles/Townfolk/BrideGroom.cs | 118 +- Scripts/Mobiles/Townfolk/EscortableMage.cs | 106 +- Scripts/Mobiles/Townfolk/Gypsy.cs | 136 +- Scripts/Mobiles/Townfolk/HarborMaster.cs | 105 +- Scripts/Mobiles/Townfolk/Merchant.cs | 124 +- Scripts/Mobiles/Townfolk/Messenger.cs | 134 +- Scripts/Mobiles/Townfolk/Minter.cs | 46 +- Scripts/Mobiles/Townfolk/Ninja.cs | 110 +- Scripts/Mobiles/Townfolk/Noble.cs | 120 +- Scripts/Mobiles/Townfolk/Peasant.cs | 115 +- Scripts/Mobiles/Townfolk/Prisoner.cs | 132 +- Scripts/Mobiles/Townfolk/Samurai.cs | 158 +- Scripts/Mobiles/Townfolk/Sculptor.cs | 95 +- Scripts/Mobiles/Townfolk/SeekerOfAdventure.cs | 142 +- Scripts/Mobiles/Townfolk/TownCrier.cs | 1017 +- Scripts/Mobiles/Vendors/AnimalBuy.cs | 24 +- Scripts/Mobiles/Vendors/BaseVendor.cs | 2859 +-- Scripts/Mobiles/Vendors/BeverageBuy.cs | 48 +- Scripts/Mobiles/Vendors/GenericBuy.cs | 584 +- Scripts/Mobiles/Vendors/NPC/Alchemist.cs | 74 +- Scripts/Mobiles/Vendors/NPC/AnimalTrainer.cs | 771 +- Scripts/Mobiles/Vendors/NPC/Architect.cs | 61 +- Scripts/Mobiles/Vendors/NPC/Armorer.cs | 155 +- Scripts/Mobiles/Vendors/NPC/Baker.cs | 57 +- Scripts/Mobiles/Vendors/NPC/Bard.cs | 69 +- Scripts/Mobiles/Vendors/NPC/Barkeeper.cs | 67 +- Scripts/Mobiles/Vendors/NPC/Beekeeper.cs | 57 +- Scripts/Mobiles/Vendors/NPC/Blacksmith.cs | 220 +- Scripts/Mobiles/Vendors/NPC/Bowyer.cs | 90 +- Scripts/Mobiles/Vendors/NPC/Butcher.cs | 72 +- Scripts/Mobiles/Vendors/NPC/Carpenter.cs | 80 +- Scripts/Mobiles/Vendors/NPC/Cobbler.cs | 61 +- Scripts/Mobiles/Vendors/NPC/Cook.cs | 74 +- .../Mobiles/Vendors/NPC/CustomHairstylist.cs | 1132 +- Scripts/Mobiles/Vendors/NPC/Farmer.cs | 80 +- Scripts/Mobiles/Vendors/NPC/Fisherman.cs | 70 +- Scripts/Mobiles/Vendors/NPC/Furtrader.cs | 63 +- Scripts/Mobiles/Vendors/NPC/Glassblower.cs | 69 +- Scripts/Mobiles/Vendors/NPC/GolemCrafter.cs | 61 +- .../NPC/Guildmasters/BardGuildmaster.cs | 56 +- .../NPC/Guildmasters/BaseGuildmaster.cs | 256 +- .../NPC/Guildmasters/BlacksmithGuildmaster.cs | 97 +- .../NPC/Guildmasters/FisherGuildmaster.cs | 46 +- .../NPC/Guildmasters/HealerGuildmaster.cs | 68 +- .../NPC/Guildmasters/MageGuildmaster.cs | 74 +- .../NPC/Guildmasters/MerchantGuildmaster.cs | 48 +- .../NPC/Guildmasters/MinerGuildmaster.cs | 48 +- .../NPC/Guildmasters/RangerGuildmaster.cs | 66 +- .../NPC/Guildmasters/TailorGuildmaster.cs | 46 +- .../NPC/Guildmasters/ThiefGuildmaster.cs | 195 +- .../NPC/Guildmasters/TinkerGuildmaster.cs | 127 +- .../NPC/Guildmasters/WarriorGuildmaster.cs | 58 +- .../Mobiles/Vendors/NPC/GypsyAnimalTrainer.cs | 102 +- Scripts/Mobiles/Vendors/NPC/GypsyBanker.cs | 118 +- Scripts/Mobiles/Vendors/NPC/GypsyMaiden.cs | 109 +- Scripts/Mobiles/Vendors/NPC/HairStylist.cs | 63 +- Scripts/Mobiles/Vendors/NPC/Herbalist.cs | 65 +- Scripts/Mobiles/Vendors/NPC/HolyMage.cs | 125 +- Scripts/Mobiles/Vendors/NPC/InnKeeper.cs | 65 +- Scripts/Mobiles/Vendors/NPC/IronWorker.cs | 175 +- Scripts/Mobiles/Vendors/NPC/Jeweler.cs | 55 +- .../Mobiles/Vendors/NPC/KeeperOfChivalry.cs | 141 +- Scripts/Mobiles/Vendors/NPC/LeatherWorker.cs | 65 +- Scripts/Mobiles/Vendors/NPC/Mage.cs | 82 +- Scripts/Mobiles/Vendors/NPC/Mapmaker.cs | 55 +- Scripts/Mobiles/Vendors/NPC/Miller.cs | 54 +- Scripts/Mobiles/Vendors/NPC/Miner.cs | 72 +- Scripts/Mobiles/Vendors/NPC/Monk.cs | 77 +- Scripts/Mobiles/Vendors/NPC/Provisioner.cs | 61 +- Scripts/Mobiles/Vendors/NPC/Rancher.cs | 61 +- Scripts/Mobiles/Vendors/NPC/Ranger.cs | 82 +- .../Mobiles/Vendors/NPC/RealEstateBroker.cs | 287 +- Scripts/Mobiles/Vendors/NPC/Scribe.cs | 111 +- Scripts/Mobiles/Vendors/NPC/Shipwright.cs | 72 +- Scripts/Mobiles/Vendors/NPC/StoneCrafter.cs | 71 +- Scripts/Mobiles/Vendors/NPC/Tailor.cs | 141 +- Scripts/Mobiles/Vendors/NPC/Tanner.cs | 57 +- Scripts/Mobiles/Vendors/NPC/TavernKeeper.cs | 68 +- Scripts/Mobiles/Vendors/NPC/Thief.cs | 82 +- Scripts/Mobiles/Vendors/NPC/Tinker.cs | 63 +- Scripts/Mobiles/Vendors/NPC/Vagabond.cs | 95 +- Scripts/Mobiles/Vendors/NPC/VarietyDealer.cs | 53 +- Scripts/Mobiles/Vendors/NPC/Veterinarian.cs | 57 +- Scripts/Mobiles/Vendors/NPC/Waiter.cs | 66 +- Scripts/Mobiles/Vendors/NPC/Weaponsmith.cs | 172 +- Scripts/Mobiles/Vendors/NPC/Weaver.cs | 141 +- Scripts/Mobiles/Vendors/PlayerBarkeeper.cs | 2024 +- Scripts/Mobiles/Vendors/PlayerVendor.cs | 3109 ++- Scripts/Mobiles/Vendors/PresetMapBuy.cs | 29 +- Scripts/Mobiles/Vendors/RentedVendor.cs | 741 +- .../Vendors/SBInfo/Armors/SBChainmailArmor.cs | 52 +- .../Vendors/SBInfo/Armors/SBHelmetArmor.cs | 68 +- .../Vendors/SBInfo/Armors/SBLeatherArmor.cs | 84 +- .../Vendors/SBInfo/Armors/SBMetalShields.cs | 64 +- .../Vendors/SBInfo/Armors/SBPlateArmor.cs | 63 +- .../Vendors/SBInfo/Armors/SBRingmailArmor.cs | 57 +- .../Vendors/SBInfo/Armors/SBStuddedArmor.cs | 68 +- .../Vendors/SBInfo/Armors/SBWoodenShields.cs | 44 +- Scripts/Mobiles/Vendors/SBInfo/SBAlchemist.cs | 118 +- .../Mobiles/Vendors/SBInfo/SBAnimalTrainer.cs | 68 +- Scripts/Mobiles/Vendors/SBInfo/SBArchitect.cs | 52 +- Scripts/Mobiles/Vendors/SBInfo/SBBaker.cs | 90 +- Scripts/Mobiles/Vendors/SBInfo/SBBanker.cs | 46 +- Scripts/Mobiles/Vendors/SBInfo/SBBard.cs | 58 +- Scripts/Mobiles/Vendors/SBInfo/SBBarkeeper.cs | 183 +- Scripts/Mobiles/Vendors/SBInfo/SBBeekeeper.cs | 48 +- .../Mobiles/Vendors/SBInfo/SBBlacksmith.cs | 386 +- Scripts/Mobiles/Vendors/SBInfo/SBBowyer.cs | 44 +- Scripts/Mobiles/Vendors/SBInfo/SBButcher.cs | 80 +- Scripts/Mobiles/Vendors/SBInfo/SBCarpenter.cs | 144 +- Scripts/Mobiles/Vendors/SBInfo/SBCobbler.cs | 56 +- Scripts/Mobiles/Vendors/SBInfo/SBCook.cs | 143 +- Scripts/Mobiles/Vendors/SBInfo/SBFarmer.cs | 125 +- Scripts/Mobiles/Vendors/SBInfo/SBFisherman.cs | 82 +- .../Mobiles/Vendors/SBInfo/SBFortuneTeller.cs | 44 +- Scripts/Mobiles/Vendors/SBInfo/SBFurtrader.cs | 44 +- .../Mobiles/Vendors/SBInfo/SBGlassblower.cs | 126 +- .../Mobiles/Vendors/SBInfo/SBHairStylist.cs | 52 +- Scripts/Mobiles/Vendors/SBInfo/SBHealer.cs | 60 +- Scripts/Mobiles/Vendors/SBInfo/SBHerbalist.cs | 68 +- Scripts/Mobiles/Vendors/SBInfo/SBHolyMage.cs | 138 +- Scripts/Mobiles/Vendors/SBInfo/SBHouseDeed.cs | 100 +- Scripts/Mobiles/Vendors/SBInfo/SBInfo.cs | 18 +- Scripts/Mobiles/Vendors/SBInfo/SBInnKeeper.cs | 193 +- Scripts/Mobiles/Vendors/SBInfo/SBJewel.cs | 126 +- .../Vendors/SBInfo/SBKeeperOfChivalry.cs | 39 +- .../Mobiles/Vendors/SBInfo/SBLeatherWorker.cs | 48 +- Scripts/Mobiles/Vendors/SBInfo/SBMage.cs | 208 +- Scripts/Mobiles/Vendors/SBInfo/SBMapmaker.cs | 66 +- Scripts/Mobiles/Vendors/SBInfo/SBMiller.cs | 48 +- Scripts/Mobiles/Vendors/SBInfo/SBMiner.cs | 68 +- Scripts/Mobiles/Vendors/SBInfo/SBMonk.cs | 39 +- Scripts/Mobiles/Vendors/SBInfo/SBNinja.cs | 39 +- .../Vendors/SBInfo/SBPlayerBarkeeper.cs | 69 +- .../Mobiles/Vendors/SBInfo/SBProvisioner.cs | 280 +- Scripts/Mobiles/Vendors/SBInfo/SBRancher.cs | 39 +- Scripts/Mobiles/Vendors/SBInfo/SBRanger.cs | 47 +- .../Vendors/SBInfo/SBRealEstateBroker.cs | 48 +- Scripts/Mobiles/Vendors/SBInfo/SBSECook.cs | 80 +- Scripts/Mobiles/Vendors/SBInfo/SBSEHats.cs | 52 +- Scripts/Mobiles/Vendors/SBInfo/SBSamurai.cs | 39 +- Scripts/Mobiles/Vendors/SBInfo/SBScribe.cs | 64 +- .../Mobiles/Vendors/SBInfo/SBShipwright.cs | 50 +- .../Mobiles/Vendors/SBInfo/SBSmithTools.cs | 49 +- .../Mobiles/Vendors/SBInfo/SBStoneCrafter.cs | 150 +- Scripts/Mobiles/Vendors/SBInfo/SBTailor.cs | 188 +- Scripts/Mobiles/Vendors/SBInfo/SBTanner.cs | 138 +- .../Mobiles/Vendors/SBInfo/SBTavernKeeper.cs | 187 +- Scripts/Mobiles/Vendors/SBInfo/SBThief.cs | 74 +- Scripts/Mobiles/Vendors/SBInfo/SBTinker.cs | 192 +- Scripts/Mobiles/Vendors/SBInfo/SBVagabond.cs | 122 +- .../Mobiles/Vendors/SBInfo/SBVarietyDealer.cs | 202 +- .../Mobiles/Vendors/SBInfo/SBVeterinarian.cs | 52 +- Scripts/Mobiles/Vendors/SBInfo/SBWaiter.cs | 90 +- .../Mobiles/Vendors/SBInfo/SBWeaponSmith.cs | 284 +- Scripts/Mobiles/Vendors/SBInfo/SBWeaver.cs | 85 +- .../Mobiles/Vendors/SBInfo/SE/SBSEArmor.cs | 73 +- .../Mobiles/Vendors/SBInfo/SE/SBSEBowyer.cs | 60 +- .../Vendors/SBInfo/SE/SBSECarpenter.cs | 58 +- Scripts/Mobiles/Vendors/SBInfo/SE/SBSEFood.cs | 56 +- .../Vendors/SBInfo/SE/SBSELeatherArmor.cs | 88 +- .../Mobiles/Vendors/SBInfo/SE/SBSEWeapons.cs | 81 +- .../Vendors/SBInfo/Weapons/SBAxeWeapon.cs | 73 +- .../Vendors/SBInfo/Weapons/SBKnifeWeapon.cs | 56 +- .../Vendors/SBInfo/Weapons/SBMaceWeapon.cs | 64 +- .../Vendors/SBInfo/Weapons/SBPoleArmWeapon.cs | 48 +- .../Vendors/SBInfo/Weapons/SBRangedWeapon.cs | 87 +- .../SBInfo/Weapons/SBSpearForkWeapon.cs | 52 +- .../Vendors/SBInfo/Weapons/SBStavesWeapon.cs | 56 +- .../Vendors/SBInfo/Weapons/SBSwordWeapon.cs | 114 +- Scripts/Mobiles/Vendors/VendorInventory.cs | 195 +- Scripts/Multis/BaseHouse.cs | 7268 +++--- Scripts/Multis/Boats/BaseBoat.cs | 3485 +-- Scripts/Multis/Boats/BaseBoatDeed.cs | 272 +- Scripts/Multis/Boats/BaseDockedBoat.cs | 295 +- Scripts/Multis/Boats/ConfirmDryDockGump.cs | 48 +- Scripts/Multis/Boats/Hold.cs | 178 +- Scripts/Multis/Boats/LargeBoat.cs | 146 +- Scripts/Multis/Boats/LargeDragonBoat.cs | 146 +- Scripts/Multis/Boats/MediumBoat.cs | 146 +- Scripts/Multis/Boats/MediumDragonBoat.cs | 146 +- Scripts/Multis/Boats/Plank.cs | 514 +- Scripts/Multis/Boats/RenameBoatPrompt.cs | 24 +- Scripts/Multis/Boats/SmallBoat.cs | 146 +- Scripts/Multis/Boats/SmallDragonBoat.cs | 146 +- Scripts/Multis/Boats/Strandedness.cs | 299 +- Scripts/Multis/Boats/TillerMan.cs | 188 +- Scripts/Multis/Camps/BankerCamp.cs | 62 +- Scripts/Multis/Camps/BaseCamp.cs | 302 +- Scripts/Multis/Camps/BrigandCamp.cs | 362 +- Scripts/Multis/Camps/HealerCamp.cs | 62 +- Scripts/Multis/Camps/LizardmenCamp.cs | 375 +- Scripts/Multis/Camps/MageCamp.cs | 62 +- Scripts/Multis/Camps/OrcCamp.cs | 373 +- Scripts/Multis/Camps/RatCamp.cs | 371 +- Scripts/Multis/ComponentVerification.cs | 371 +- Scripts/Multis/Deeds.cs | 1697 +- Scripts/Multis/DynamicDecay.cs | 94 +- Scripts/Multis/HouseFoundation.cs | 5036 ++-- Scripts/Multis/HousePlacement.cs | 613 +- Scripts/Multis/HousePlacementTool.cs | 1649 +- Scripts/Multis/HouseSign.cs | 459 +- Scripts/Multis/HouseTeleporter.cs | 266 +- Scripts/Multis/Houses.cs | 996 +- Scripts/Multis/MovingCrate.cs | 606 +- Scripts/Multis/PreviewHouse.cs | 202 +- Scripts/Properties/AssemblyInfo.cs | 2 +- Scripts/Regions/BaseRegion.cs | 1096 +- Scripts/Regions/DungeonRegion.cs | 67 +- Scripts/Regions/GreenAcres.cs | 51 +- Scripts/Regions/GuardedRegion.cs | 726 +- Scripts/Regions/HouseRegion.cs | 702 +- Scripts/Regions/Jail.cs | 84 +- Scripts/Regions/NoHousingRegion.cs | 32 +- Scripts/Regions/Spawning/SpawnDefinition.cs | 788 +- Scripts/Regions/Spawning/SpawnEntry.cs | 817 +- Scripts/Regions/Spawning/SpawnPersistence.cs | 94 +- Scripts/Regions/TownRegion.cs | 12 +- Scripts/Skills/Anatomy.cs | 139 +- Scripts/Skills/AnimalLore.cs | 715 +- Scripts/Skills/AnimalTaming.cs | 711 +- Scripts/Skills/ArmsLore.cs | 276 +- Scripts/Skills/Begging.cs | 279 +- Scripts/Skills/DetectHidden.cs | 158 +- Scripts/Skills/Discordance.cs | 438 +- Scripts/Skills/EvalInt.cs | 141 +- Scripts/Skills/ForensicEval.cs | 161 +- Scripts/Skills/Hiding.cs | 152 +- Scripts/Skills/Inscribe.cs | 282 +- Scripts/Skills/ItemIdentification.cs | 98 +- Scripts/Skills/Meditation.cs | 152 +- Scripts/Skills/Peacemaking.cs | 348 +- Scripts/Skills/Poisoning.cs | 298 +- Scripts/Skills/Provocation.cs | 286 +- Scripts/Skills/RemoveTrap.cs | 217 +- Scripts/Skills/Snooping.cs | 152 +- Scripts/Skills/SpiritSpeak.cs | 313 +- Scripts/Skills/Stealing.cs | 962 +- Scripts/Skills/Stealth.cs | 175 +- Scripts/Skills/TasteID.cs | 151 +- Scripts/Skills/Tracking.cs | 776 +- Scripts/SpecialSystems/Engines/GiftGiving.cs | 120 +- Scripts/SpecialSystems/Engines/ItemFixes.cs | 26 +- .../SpecialSystems/Engines/PreventInaccess.cs | 140 +- Scripts/SpecialSystems/Engines/TestCenter.cs | 397 +- .../Items/Resurrection/ResGate.cs | 80 +- .../Items/Stones/AlchemyStone.cs | 58 +- .../Items/Stones/GamblingStone.cs | 202 +- .../SpecialSystems/Items/Stones/IngotStone.cs | 58 +- .../SpecialSystems/Items/Stones/RegStone.cs | 58 +- .../Items/Stones/ScribeStone.cs | 58 +- .../SpecialSystems/Items/Stones/SmithStone.cs | 58 +- .../Items/Stones/TailorStone.cs | 58 +- .../Items/SupplyBags/AlchemyBag.cs | 60 +- .../Items/SupplyBags/BagOfIngots.cs | 77 +- .../Items/SupplyBags/ScribeBag.cs | 58 +- .../Items/SupplyBags/SmithBag.cs | 75 +- .../Items/SupplyBags/TailorBag.cs | 72 +- Scripts/Spells/Base/DisturbType.cs | 18 +- Scripts/Spells/Base/MagerySpell.cs | 152 +- Scripts/Spells/Base/SpecialMove.cs | 635 +- Scripts/Spells/Base/Spell.cs | 1606 +- Scripts/Spells/Base/SpellCircle.cs | 22 +- Scripts/Spells/Base/SpellHelper.cs | 2735 ++- Scripts/Spells/Base/SpellInfo.cs | 90 +- Scripts/Spells/Base/SpellRegistry.cs | 265 +- Scripts/Spells/Base/SpellState.cs | 16 +- Scripts/Spells/Bushido/Confidence.cs | 216 +- Scripts/Spells/Bushido/CounterAttack.cs | 154 +- Scripts/Spells/Bushido/Evasion.cs | 336 +- Scripts/Spells/Bushido/HonorableExecution.cs | 262 +- Scripts/Spells/Bushido/LightningStrike.cs | 111 +- Scripts/Spells/Bushido/MomentumStrike.cs | 97 +- Scripts/Spells/Bushido/SamuraiMove.cs | 18 +- Scripts/Spells/Bushido/SamuraiSpell.cs | 192 +- Scripts/Spells/Chivalry/CleanseByFire.cs | 194 +- Scripts/Spells/Chivalry/CloseWounds.cs | 191 +- Scripts/Spells/Chivalry/ConsecrateWeapon.cs | 162 +- Scripts/Spells/Chivalry/DispelEvil.cs | 167 +- Scripts/Spells/Chivalry/DivineFury.cs | 108 +- Scripts/Spells/Chivalry/EnemyOfOne.cs | 114 +- Scripts/Spells/Chivalry/HolyLight.cs | 96 +- Scripts/Spells/Chivalry/NobleSacrifice.cs | 263 +- Scripts/Spells/Chivalry/PaladinSpell.cs | 212 +- Scripts/Spells/Chivalry/RemoveCurse.cs | 222 +- Scripts/Spells/Chivalry/SacredJourney.cs | 349 +- Scripts/Spells/Eighth/AirElemental.cs | 80 +- Scripts/Spells/Eighth/EarthElemental.cs | 80 +- Scripts/Spells/Eighth/Earthquake.cs | 112 +- Scripts/Spells/Eighth/EnergyVortex.cs | 152 +- Scripts/Spells/Eighth/FireElemental.cs | 82 +- Scripts/Spells/Eighth/Resurrection.cs | 187 +- Scripts/Spells/Eighth/SummonDaemon.cs | 92 +- Scripts/Spells/Eighth/WaterElemental.cs | 80 +- Scripts/Spells/Fifth/BladeSpirits.cs | 162 +- Scripts/Spells/Fifth/DispelField.cs | 135 +- Scripts/Spells/Fifth/Incognito.cs | 299 +- Scripts/Spells/Fifth/MagicReflect.cs | 241 +- Scripts/Spells/Fifth/MindBlast.cs | 228 +- Scripts/Spells/Fifth/Paralyze.cs | 167 +- Scripts/Spells/Fifth/PoisonField.cs | 460 +- Scripts/Spells/Fifth/SummonCreature.cs | 149 +- Scripts/Spells/First/Clumsy.cs | 117 +- Scripts/Spells/First/CreateFood.cs | 137 +- Scripts/Spells/First/Feeblemind.cs | 117 +- Scripts/Spells/First/Heal.cs | 189 +- Scripts/Spells/First/MagicArrow.cs | 139 +- Scripts/Spells/First/NightSight.cs | 114 +- Scripts/Spells/First/ReactiveArmor.cs | 251 +- Scripts/Spells/First/Weaken.cs | 117 +- Scripts/Spells/Fourth/ArchCure.cs | 279 +- Scripts/Spells/Fourth/ArchProtection.cs | 262 +- Scripts/Spells/Fourth/Curse.cs | 163 +- Scripts/Spells/Fourth/FireField.cs | 601 +- Scripts/Spells/Fourth/GreaterHeal.cs | 171 +- Scripts/Spells/Fourth/Lightning.cs | 134 +- Scripts/Spells/Fourth/ManaDrain.cs | 199 +- Scripts/Spells/Fourth/Recall.cs | 359 +- .../Gargoyle/SpellDefinitions/FlySpell.cs | 149 +- Scripts/Spells/Initializer.cs | 362 +- .../Spells/Mysticism/AnimatedWeaponSpell.cs | 134 +- Scripts/Spells/Mysticism/EagleStrikeSpell.cs | 130 +- Scripts/Spells/Mysticism/HailStormSpell.cs | 218 +- Scripts/Spells/Mysticism/MysticSpell.cs | 142 +- .../Spells/Mysticism/NetherCycloneSpell.cs | 234 +- Scripts/Spells/Mysticism/SpellPlagueSpell.cs | 361 +- Scripts/Spells/Mysticism/StoneFormSpell.cs | 255 +- Scripts/Spells/Necromancy/AnimateDeadSpell.cs | 714 +- Scripts/Spells/Necromancy/BloodOathSpell.cs | 287 +- Scripts/Spells/Necromancy/CorpseSkin.cs | 232 +- Scripts/Spells/Necromancy/CurseWeapon.cs | 154 +- Scripts/Spells/Necromancy/EvilOmen.cs | 195 +- Scripts/Spells/Necromancy/Exorcism.cs | 304 +- Scripts/Spells/Necromancy/HorrificBeast.cs | 58 +- Scripts/Spells/Necromancy/LichForm.cs | 64 +- Scripts/Spells/Necromancy/MindRot.cs | 290 +- Scripts/Spells/Necromancy/NecromancerSpell.cs | 84 +- Scripts/Spells/Necromancy/PainSpike.cs | 203 +- Scripts/Spells/Necromancy/PoisonStrike.cs | 175 +- Scripts/Spells/Necromancy/Strangle.cs | 368 +- Scripts/Spells/Necromancy/SummonFamiliar.cs | 317 +- .../Spells/Necromancy/TransformationSpell.cs | 73 +- Scripts/Spells/Necromancy/VampiricEmbrace.cs | 80 +- Scripts/Spells/Necromancy/VengefulSpirit.cs | 145 +- Scripts/Spells/Necromancy/Wither.cs | 158 +- Scripts/Spells/Necromancy/WraithForm.cs | 72 +- Scripts/Spells/Ninjitsu/AnimalForm.cs | 1197 +- Scripts/Spells/Ninjitsu/Backstab.cs | 100 +- Scripts/Spells/Ninjitsu/DeathStrike.cs | 237 +- Scripts/Spells/Ninjitsu/FocusAttack.cs | 95 +- Scripts/Spells/Ninjitsu/KiAttack.cs | 208 +- Scripts/Spells/Ninjitsu/MirrorImage.cs | 390 +- Scripts/Spells/Ninjitsu/NinjaMove.cs | 18 +- Scripts/Spells/Ninjitsu/NinjaSpell.cs | 155 +- Scripts/Spells/Ninjitsu/ShadowJump.cs | 206 +- Scripts/Spells/Ninjitsu/SurpriseAttack.cs | 170 +- Scripts/Spells/Reagent.cs | 219 +- Scripts/Spells/Second/Agility.cs | 128 +- Scripts/Spells/Second/Cunning.cs | 128 +- Scripts/Spells/Second/Cure.cs | 159 +- Scripts/Spells/Second/Harm.cs | 169 +- Scripts/Spells/Second/MagicTrap.cs | 146 +- Scripts/Spells/Second/Protection.cs | 298 +- Scripts/Spells/Second/RemoveTrap.cs | 129 +- Scripts/Spells/Second/Strength.cs | 128 +- Scripts/Spells/Seventh/ChainLightning.cs | 215 +- Scripts/Spells/Seventh/EnergyField.cs | 313 +- Scripts/Spells/Seventh/FlameStrike.cs | 137 +- Scripts/Spells/Seventh/GateTravel.cs | 425 +- Scripts/Spells/Seventh/ManaVampire.cs | 183 +- Scripts/Spells/Seventh/MassDispel.cs | 166 +- Scripts/Spells/Seventh/MeteorSwarm.cs | 203 +- Scripts/Spells/Seventh/Polymorph.cs | 362 +- Scripts/Spells/Sixth/Dispel.cs | 132 +- Scripts/Spells/Sixth/EnergyBolt.cs | 144 +- Scripts/Spells/Sixth/Explosion.cs | 194 +- Scripts/Spells/Sixth/Invisibility.cs | 209 +- Scripts/Spells/Sixth/Mark.cs | 148 +- Scripts/Spells/Sixth/MassCurse.cs | 158 +- Scripts/Spells/Sixth/ParalyzeField.cs | 351 +- Scripts/Spells/Sixth/Reveal.cs | 181 +- Scripts/Spells/Spellweaving/ArcaneCircle.cs | 257 +- Scripts/Spells/Spellweaving/ArcaneForm.cs | 70 +- Scripts/Spells/Spellweaving/ArcaneSummon.cs | 78 +- Scripts/Spells/Spellweaving/ArcanistSpell.cs | 235 +- Scripts/Spells/Spellweaving/AttuneWeapon.cs | 193 +- Scripts/Spells/Spellweaving/EssenceOfWind.cs | 205 +- Scripts/Spells/Spellweaving/EtherealVoyage.cs | 122 +- Scripts/Spells/Spellweaving/GiftOfLife.cs | 332 +- Scripts/Spells/Spellweaving/GiftOfRenewal.cs | 280 +- .../Spells/Spellweaving/ImmolatingWeapon.cs | 201 +- .../Spells/Spellweaving/Items/ArcaneFocus.cs | 88 +- .../Spellweaving/Items/TransientItem.cs | 153 +- .../Spells/Spellweaving/Mobiles/ArcaneFey.cs | 96 +- .../Spellweaving/Mobiles/ArcaneFiend.cs | 98 +- .../Spells/Spellweaving/Mobiles/NatureFury.cs | 126 +- Scripts/Spells/Spellweaving/NatureFury.cs | 186 +- Scripts/Spells/Spellweaving/ReaperForm.cs | 76 +- Scripts/Spells/Spellweaving/SummonFey.cs | 65 +- Scripts/Spells/Spellweaving/SummonFiend.cs | 64 +- Scripts/Spells/Spellweaving/Thunderstorm.cs | 136 +- Scripts/Spells/Spellweaving/WordOfDeath.cs | 139 +- Scripts/Spells/Third/Bless.cs | 136 +- Scripts/Spells/Third/Fireball.cs | 136 +- Scripts/Spells/Third/MagicLock.cs | 137 +- Scripts/Spells/Third/Poison.cs | 233 +- Scripts/Spells/Third/Telekinesis.cs | 167 +- Scripts/Spells/Third/Teleport.cs | 230 +- Scripts/Spells/Third/Unlock.cs | 157 +- Scripts/Spells/Third/WallOfStone.cs | 331 +- Scripts/Spells/UnsummonTimer.cs | 32 +- Scripts/Targets/BladedItemTarget.cs | 191 +- Scripts/Targets/MoveTarget.cs | 73 +- Scripts/Targets/PickMoveTarget.cs | 34 +- Server/AggressorInfo.cs | 290 +- Server/AssemblyInfo.cs | 4 +- Server/Attributes.cs | 232 +- Server/BaseVendor.cs | 126 +- Server/Body.cs | 321 +- Server/ClientVersion.cs | 391 +- Server/Commands.cs | 356 +- Server/ContextMenus/ContextMenu.cs | 117 +- Server/ContextMenus/ContextMenuEntry.cs | 143 +- Server/ContextMenus/OpenBackpackEntry.cs | 24 +- Server/ContextMenus/PaperdollEntry.cs | 26 +- Server/Diagnostics/BaseProfile.cs | 87 +- Server/Diagnostics/GumpProfile.cs | 36 +- Server/Diagnostics/PacketProfile.cs | 120 +- Server/Diagnostics/TargetProfile.cs | 36 +- Server/Diagnostics/TimerProfile.cs | 51 +- Server/Effects.cs | 738 +- Server/EventLog.cs | 66 +- Server/EventSink.cs | 2078 +- Server/ExpansionInfo.cs | 600 +- Server/Geometry.cs | 1015 +- Server/Guild.cs | 163 +- Server/Gumps/Gump.cs | 741 +- Server/Gumps/GumpAlphaRegion.cs | 92 +- Server/Gumps/GumpBackground.cs | 108 +- Server/Gumps/GumpButton.cs | 166 +- Server/Gumps/GumpCheck.cs | 126 +- Server/Gumps/GumpEntry.cs | 86 +- Server/Gumps/GumpGroup.cs | 48 +- Server/Gumps/GumpHtml.cs | 140 +- Server/Gumps/GumpHtmlLocalized.cs | 349 +- Server/Gumps/GumpImage.cs | 114 +- Server/Gumps/GumpImageTileButton.cs | 258 +- Server/Gumps/GumpImageTiled.cs | 108 +- Server/Gumps/GumpItem.cs | 108 +- Server/Gumps/GumpItemProperty.cs | 50 +- Server/Gumps/GumpLabel.cs | 94 +- Server/Gumps/GumpLabelCropped.cs | 124 +- Server/Gumps/GumpPage.cs | 48 +- Server/Gumps/GumpRadio.cs | 126 +- Server/Gumps/GumpTextEntry.cs | 144 +- Server/Gumps/GumpTextEntryLimited.cs | 151 +- Server/Gumps/GumpTooltip.cs | 48 +- Server/Gumps/RelayInfo.cs | 80 +- Server/HuePicker.cs | 44 +- Server/IAccount.cs | 178 +- Server/IEntity.cs | 110 +- Server/Insensitive.cs | 72 +- Server/Interfaces.cs | 148 +- Server/Item.cs | 8867 +++---- Server/ItemBounds.cs | 55 +- Server/Items/BaseMulti.cs | 220 +- Server/Items/Container.cs | 3561 ++- Server/Items/Containers.cs | 189 +- Server/Items/SecureTradeContainer.cs | 170 +- Server/Items/VirtualCheck.cs | 730 +- Server/Items/VirtualHair.cs | 248 +- Server/KeywordList.cs | 79 +- Server/Main.cs | 1189 +- Server/Map.cs | 3009 ++- Server/Menus/IMenu.cs | 16 +- Server/Menus/ItemListMenu.cs | 92 +- Server/Menus/QuestionMenu.cs | 60 +- Server/Mobile.cs | 20354 ++++++++-------- Server/Movement.cs | 94 +- Server/MultiData.cs | 948 +- Server/NativeReader.cs | 95 +- Server/Network/BufferPool.cs | 120 +- Server/Network/ByteQueue.cs | 209 +- Server/Network/Compression.cs | 742 +- Server/Network/EncodedPacketHandler.cs | 26 +- Server/Network/EncodedReader.cs | 78 +- Server/Network/Listener.cs | 349 +- Server/Network/MessagePump.cs | 388 +- Server/Network/NetState.cs | 1573 +- Server/Network/PacketHandler.cs | 35 +- Server/Network/PacketHandlers.cs | 5286 ++-- Server/Network/PacketReader.cs | 630 +- Server/Network/PacketWriter.cs | 856 +- Server/Network/Packets.cs | 8775 +++---- Server/Network/SendQueue.cs | 292 +- Server/Notoriety.cs | 66 +- Server/ObjectPropertyList.cs | 257 +- Server/Party.cs | 22 +- Server/Persistence/BinaryMemoryWriter.cs | 89 +- Server/Persistence/DualSaveStrategy.cs | 42 +- Server/Persistence/DynamicSaveStrategy.cs | 412 +- Server/Persistence/FileOperations.cs | 116 +- Server/Persistence/FileQueue.cs | 306 +- Server/Persistence/ParallelSaveStrategy.cs | 477 +- Server/Persistence/Persistence.cs | 178 +- Server/Persistence/QueuedMemoryWriter.cs | 144 +- Server/Persistence/SaveMetrics.cs | 171 +- Server/Persistence/SaveStrategy.cs | 38 +- Server/Persistence/SequentialFileWriter.cs | 154 +- Server/Persistence/StandardSaveStrategy.cs | 275 +- Server/Point3DList.cs | 111 +- Server/Poison.cs | 218 +- Server/Prompt.cs | 36 +- Server/QuestArrow.cs | 115 +- Server/Race.cs | 227 +- Server/Random.cs | 1260 +- Server/Region.cs | 2343 +- Server/ScriptCompiler.cs | 1388 +- Server/Sector.cs | 445 +- Server/SecureTrade.cs | 850 +- Server/Serial.cs | 192 +- Server/Serialization.cs | 3885 ++- Server/Skills.cs | 2017 +- Server/Targeting/LandTarget.cs | 54 +- Server/Targeting/MultiTarget.cs | 42 +- Server/Targeting/StaticTarget.cs | 48 +- Server/Targeting/Target.cs | 443 +- Server/Targeting/TargetCancelType.cs | 14 +- Server/Targeting/TargetFlags.cs | 12 +- Server/TileData.cs | 506 +- Server/TileList.cs | 93 +- Server/TileMatrix.cs | 1067 +- Server/TileMatrixPatch.cs | 258 +- Server/Timer.cs | 1231 +- Server/Utility.cs | 2524 +- Server/VirtueInfo.cs | 224 +- Server/World.cs | 1344 +- 3324 files changed, 441118 insertions(+), 433755 deletions(-) delete mode 100644 .editorconfig diff --git a/.editorconfig b/.editorconfig deleted file mode 100644 index e7866c0e4..000000000 --- a/.editorconfig +++ /dev/null @@ -1,10 +0,0 @@ -# http://editorconfig.org -root=true - -[*] -indent_style = tab -tab_width = 4 -charset = utf-8 -trim_trailing_whitespace = true -insert_final_newline = true - diff --git a/Scripts/Accounting/AccessRestrictions.cs b/Scripts/Accounting/AccessRestrictions.cs index 66aa3606b..ee40c4d10 100644 --- a/Scripts/Accounting/AccessRestrictions.cs +++ b/Scripts/Accounting/AccessRestrictions.cs @@ -5,40 +5,42 @@ using Server.Misc; namespace Server { - public class AccessRestrictions - { - public static void Initialize() - { - EventSink.SocketConnect += EventSink_SocketConnect; - } - - private static void EventSink_SocketConnect( SocketConnectEventArgs e ) - { - try - { - IPAddress ip = ((IPEndPoint)e.Socket.RemoteEndPoint).Address; + public class AccessRestrictions + { + public static void Initialize() + { + EventSink.SocketConnect += EventSink_SocketConnect; + } - if ( Firewall.IsBlocked( ip ) ) - { - Console.WriteLine( "Client: {0}: Firewall blocked connection attempt.", ip ); - e.AllowConnection = false; - return; - } + private static void EventSink_SocketConnect(SocketConnectEventArgs e) + { + try + { + IPAddress ip = ((IPEndPoint)e.Socket.RemoteEndPoint).Address; - if ( IPLimiter.SocketBlock && !IPLimiter.Verify( ip ) ) - { - Console.WriteLine( "Client: {0}: Past IP limit threshold", ip ); + if (Firewall.IsBlocked(ip)) + { + Console.WriteLine("Client: {0}: Firewall blocked connection attempt.", ip); + e.AllowConnection = false; + return; + } - using ( StreamWriter op = new StreamWriter( "ipLimits.log", true ) ) - op.WriteLine( "{0}\tPast IP limit threshold\t{1}", ip, DateTime.UtcNow ); - - e.AllowConnection = false; - } - } - catch - { - e.AllowConnection = false; - } - } - } + if (IPLimiter.SocketBlock && !IPLimiter.Verify(ip)) + { + Console.WriteLine("Client: {0}: Past IP limit threshold", ip); + + using (StreamWriter op = new StreamWriter("ipLimits.log", true)) + { + op.WriteLine("{0}\tPast IP limit threshold\t{1}", ip, DateTime.UtcNow); + } + + e.AllowConnection = false; + } + } + catch + { + e.AllowConnection = false; + } + } + } } \ No newline at end of file diff --git a/Scripts/Accounting/AccountAttackLimiter.cs b/Scripts/Accounting/AccountAttackLimiter.cs index 87cfffedc..34df86f4e 100644 --- a/Scripts/Accounting/AccountAttackLimiter.cs +++ b/Scripts/Accounting/AccountAttackLimiter.cs @@ -6,121 +6,123 @@ using Server.Network; namespace Server.Accounting { - public class AccountAttackLimiter - { - public static bool Enabled = true; + public class AccountAttackLimiter + { + public static bool Enabled = true; - public static void Initialize() - { - if ( !Enabled ) - return; + private static List m_List = new List(); - PacketHandlers.RegisterThrottler( 0x80, Throttle_Callback ); - PacketHandlers.RegisterThrottler( 0x91, Throttle_Callback ); - PacketHandlers.RegisterThrottler( 0xCF, Throttle_Callback ); - } + public static void Initialize() + { + if (!Enabled) + return; - public static bool Throttle_Callback( NetState ns ) - { - InvalidAccountAccessLog accessLog = FindAccessLog( ns ); + PacketHandlers.RegisterThrottler(0x80, Throttle_Callback); + PacketHandlers.RegisterThrottler(0x91, Throttle_Callback); + PacketHandlers.RegisterThrottler(0xCF, Throttle_Callback); + } - if ( accessLog == null ) - return true; + public static bool Throttle_Callback(NetState ns) + { + InvalidAccountAccessLog accessLog = FindAccessLog(ns); - return ( DateTime.UtcNow >= (accessLog.LastAccessTime + ComputeThrottle( accessLog.Counts )) ); - } + if (accessLog == null) + return true; - private static List m_List = new List(); + return DateTime.UtcNow >= accessLog.LastAccessTime + ComputeThrottle(accessLog.Counts); + } - public static InvalidAccountAccessLog FindAccessLog( NetState ns ) - { - if ( ns == null ) - return null; + public static InvalidAccountAccessLog FindAccessLog(NetState ns) + { + if (ns == null) + return null; - IPAddress ipAddress = ns.Address; + IPAddress ipAddress = ns.Address; - for ( int i = 0; i < m_List.Count; ++i ) - { - InvalidAccountAccessLog accessLog = m_List[i]; + for (int i = 0; i < m_List.Count; ++i) + { + InvalidAccountAccessLog accessLog = m_List[i]; - if ( accessLog.HasExpired ) - m_List.RemoveAt( i-- ); - else if ( accessLog.Address.Equals( ipAddress ) ) - return accessLog; - } + if (accessLog.HasExpired) + m_List.RemoveAt(i--); + else if (accessLog.Address.Equals(ipAddress)) + return accessLog; + } - return null; - } + return null; + } - public static void RegisterInvalidAccess( NetState ns ) - { - if ( ns == null || !Enabled ) - return; + public static void RegisterInvalidAccess(NetState ns) + { + if (ns == null || !Enabled) + return; - InvalidAccountAccessLog accessLog = FindAccessLog( ns ); + InvalidAccountAccessLog accessLog = FindAccessLog(ns); - if ( accessLog == null ) - m_List.Add( accessLog = new InvalidAccountAccessLog( ns.Address ) ); + if (accessLog == null) + m_List.Add(accessLog = new InvalidAccountAccessLog(ns.Address)); - accessLog.Counts += 1; - accessLog.RefreshAccessTime(); + accessLog.Counts += 1; + accessLog.RefreshAccessTime(); - if ( accessLog.Counts >= 3 ) { - try { - using ( StreamWriter op = new StreamWriter( "throttle.log", true ) ) { - op.WriteLine( - "{0}\t{1}\t{2}", - DateTime.UtcNow, - ns, - accessLog.Counts - ); - } - } - catch { - } - } - } + if (accessLog.Counts >= 3) + try + { + using (StreamWriter op = new StreamWriter("throttle.log", true)) + { + op.WriteLine( + "{0}\t{1}\t{2}", + DateTime.UtcNow, + ns, + accessLog.Counts + ); + } + } + catch + { + } + } - public static TimeSpan ComputeThrottle( int counts ) - { - if ( counts >= 15 ) - return TimeSpan.FromMinutes( 5.0 ); + public static TimeSpan ComputeThrottle(int counts) + { + if (counts >= 15) + return TimeSpan.FromMinutes(5.0); - if ( counts >= 10 ) - return TimeSpan.FromMinutes( 1.0 ); + if (counts >= 10) + return TimeSpan.FromMinutes(1.0); - if ( counts >= 5 ) - return TimeSpan.FromSeconds( 20.0 ); + if (counts >= 5) + return TimeSpan.FromSeconds(20.0); - if ( counts >= 3 ) - return TimeSpan.FromSeconds( 10.0 ); + if (counts >= 3) + return TimeSpan.FromSeconds(10.0); - if ( counts >= 1 ) - return TimeSpan.FromSeconds( 2.0 ); + if (counts >= 1) + return TimeSpan.FromSeconds(2.0); - return TimeSpan.Zero; - } - } + return TimeSpan.Zero; + } + } - public class InvalidAccountAccessLog - { - public IPAddress Address { get; set; } + public class InvalidAccountAccessLog + { + public InvalidAccountAccessLog(IPAddress address) + { + Address = address; + RefreshAccessTime(); + } - public DateTime LastAccessTime { get; set; } + public IPAddress Address{ get; set; } - public bool HasExpired => ( DateTime.UtcNow >= ( LastAccessTime + TimeSpan.FromHours( 1.0 ) ) ); + public DateTime LastAccessTime{ get; set; } - public int Counts { get; set; } + public bool HasExpired => DateTime.UtcNow >= LastAccessTime + TimeSpan.FromHours(1.0); - public void RefreshAccessTime() - { - LastAccessTime = DateTime.UtcNow; - } + public int Counts{ get; set; } - public InvalidAccountAccessLog( IPAddress address ) - { - Address = address; - RefreshAccessTime(); - } - } + public void RefreshAccessTime() + { + LastAccessTime = DateTime.UtcNow; + } + } } \ No newline at end of file diff --git a/Scripts/Accounting/AccountComment.cs b/Scripts/Accounting/AccountComment.cs index e55d6db1f..2305d3272 100644 --- a/Scripts/Accounting/AccountComment.cs +++ b/Scripts/Accounting/AccountComment.cs @@ -3,67 +3,71 @@ using System.Xml; namespace Server.Accounting { - public class AccountComment - { - private string m_Content; + public class AccountComment + { + private string m_Content; - /// - /// A string representing who added this comment. - /// - public string AddedBy { get; } + /// + /// Constructs a new AccountComment instance. + /// + /// Initial AddedBy value. + /// Initial Content value. + public AccountComment(string addedBy, string content) + { + AddedBy = addedBy; + m_Content = content; + LastModified = DateTime.UtcNow; + } - /// - /// Gets or sets the body of this comment. Setting this value will reset LastModified. - /// - public string Content - { - get => m_Content; - set{ m_Content = value; LastModified = DateTime.UtcNow; } - } + /// + /// Deserializes an AccountComment instance from an xml element. + /// + /// The XmlElement instance from which to deserialize. + public AccountComment(XmlElement node) + { + AddedBy = Utility.GetAttribute(node, "addedBy", "empty"); + LastModified = Utility.GetXMLDateTime(Utility.GetAttribute(node, "lastModified"), DateTime.UtcNow); + m_Content = Utility.GetText(node, ""); + } - /// - /// The date and time when this account was last modified -or- the comment creation time, if never modified. - /// - public DateTime LastModified { get; private set; } + /// + /// A string representing who added this comment. + /// + public string AddedBy{ get; } - /// - /// Constructs a new AccountComment instance. - /// - /// Initial AddedBy value. - /// Initial Content value. - public AccountComment( string addedBy, string content ) - { - AddedBy = addedBy; - m_Content = content; - LastModified = DateTime.UtcNow; - } + /// + /// Gets or sets the body of this comment. Setting this value will reset LastModified. + /// + public string Content + { + get => m_Content; + set + { + m_Content = value; + LastModified = DateTime.UtcNow; + } + } - /// - /// Deserializes an AccountComment instance from an xml element. - /// - /// The XmlElement instance from which to deserialize. - public AccountComment( XmlElement node ) - { - AddedBy = Utility.GetAttribute( node, "addedBy", "empty" ); - LastModified = Utility.GetXMLDateTime( Utility.GetAttribute( node, "lastModified" ), DateTime.UtcNow ); - m_Content = Utility.GetText( node, "" ); - } + /// + /// The date and time when this account was last modified -or- the comment creation time, if never modified. + /// + public DateTime LastModified{ get; private set; } - /// - /// Serializes this AccountComment instance to an XmlTextWriter. - /// - /// The XmlTextWriter instance from which to serialize. - public void Save( XmlTextWriter xml ) - { - xml.WriteStartElement( "comment" ); + /// + /// Serializes this AccountComment instance to an XmlTextWriter. + /// + /// The XmlTextWriter instance from which to serialize. + public void Save(XmlTextWriter xml) + { + xml.WriteStartElement("comment"); - xml.WriteAttributeString( "addedBy", AddedBy ); + xml.WriteAttributeString("addedBy", AddedBy); - xml.WriteAttributeString( "lastModified", XmlConvert.ToString( LastModified, XmlDateTimeSerializationMode.Utc ) ); + xml.WriteAttributeString("lastModified", XmlConvert.ToString(LastModified, XmlDateTimeSerializationMode.Utc)); - xml.WriteString( m_Content ); + xml.WriteString(m_Content); - xml.WriteEndElement(); - } - } + xml.WriteEndElement(); + } + } } \ No newline at end of file diff --git a/Scripts/Accounting/AccountHandler.cs b/Scripts/Accounting/AccountHandler.cs index a6c2967db..76eaf1d5f 100644 --- a/Scripts/Accounting/AccountHandler.cs +++ b/Scripts/Accounting/AccountHandler.cs @@ -10,407 +10,417 @@ using Server.Regions; namespace Server.Misc { - public enum PasswordProtection - { - None, - Crypt, - NewCrypt - } + public enum PasswordProtection + { + None, + Crypt, + NewCrypt + } - public class AccountHandler - { - private static int MaxAccountsPerIP = 1; - private static bool AutoAccountCreation = true; - private static bool RestrictDeletion = !TestCenter.Enabled; - private static TimeSpan DeleteDelay = TimeSpan.FromDays( 7.0 ); + public class AccountHandler + { + private static int MaxAccountsPerIP = 1; + private static bool AutoAccountCreation = true; + private static bool RestrictDeletion = !TestCenter.Enabled; + private static TimeSpan DeleteDelay = TimeSpan.FromDays(7.0); - public static PasswordProtection ProtectPasswords = PasswordProtection.NewCrypt; + public static PasswordProtection ProtectPasswords = PasswordProtection.NewCrypt; - public static AccessLevel LockdownLevel { get; set; } + private static CityInfo[] StartingCities = + { + new CityInfo("New Haven", "New Haven Bank", 1150168, 3667, 2625, 0), + new CityInfo("Yew", "The Empath Abbey", 1075072, 633, 858, 0), + new CityInfo("Minoc", "The Barnacle", 1075073, 2476, 413, 15), + new CityInfo("Britain", "The Wayfarer's Inn", 1075074, 1602, 1591, 20), + new CityInfo("Moonglow", "The Scholars Inn", 1075075, 4408, 1168, 0), + new CityInfo("Trinsic", "The Traveler's Inn", 1075076, 1845, 2745, 0), + new CityInfo("Jhelom", "The Mercenary Inn", 1075078, 1374, 3826, 0), + new CityInfo("Skara Brae", "The Falconer's Inn", 1075079, 618, 2234, 0), + new CityInfo("Vesper", "The Ironwood Inn", 1075080, 2771, 976, 0) + }; - private static CityInfo[] StartingCities = { - new CityInfo( "New Haven", "New Haven Bank", 1150168, 3667, 2625, 0 ), - new CityInfo( "Yew", "The Empath Abbey", 1075072, 633, 858, 0 ), - new CityInfo( "Minoc", "The Barnacle", 1075073, 2476, 413, 15 ), - new CityInfo( "Britain", "The Wayfarer's Inn", 1075074, 1602, 1591, 20 ), - new CityInfo( "Moonglow", "The Scholars Inn", 1075075, 4408, 1168, 0 ), - new CityInfo( "Trinsic", "The Traveler's Inn", 1075076, 1845, 2745, 0 ), - new CityInfo( "Jhelom", "The Mercenary Inn", 1075078, 1374, 3826, 0 ), - new CityInfo( "Skara Brae", "The Falconer's Inn", 1075079, 618, 2234, 0 ), - new CityInfo( "Vesper", "The Ironwood Inn", 1075080, 2771, 976, 0 ) - }; + /* Old Haven/Magincia Locations + new CityInfo( "Britain", "Sweet Dreams Inn", 1496, 1628, 10 ); + // .. + // Trinsic + new CityInfo( "Magincia", "The Great Horns Tavern", 3734, 2222, 20 ), + // Jhelom + // .. + new CityInfo( "Haven", "Buckler's Hideaway", 3667, 2625, 0 ) - /* Old Haven/Magincia Locations - new CityInfo( "Britain", "Sweet Dreams Inn", 1496, 1628, 10 ); - // .. - // Trinsic - new CityInfo( "Magincia", "The Great Horns Tavern", 3734, 2222, 20 ), - // Jhelom - // .. - new CityInfo( "Haven", "Buckler's Hideaway", 3667, 2625, 0 ) + if ( Core.AOS ) + { + //CityInfo haven = new CityInfo( "Haven", "Uzeraan's Mansion", 3618, 2591, 0 ); + CityInfo haven = new CityInfo( "Haven", "Uzeraan's Mansion", 3503, 2574, 14 ); + StartingCities[StartingCities.Length - 1] = haven; + } + */ - if ( Core.AOS ) - { - //CityInfo haven = new CityInfo( "Haven", "Uzeraan's Mansion", 3618, 2591, 0 ); - CityInfo haven = new CityInfo( "Haven", "Uzeraan's Mansion", 3503, 2574, 14 ); - StartingCities[StartingCities.Length - 1] = haven; - } - */ + private static bool PasswordCommandEnabled = false; - private static bool PasswordCommandEnabled = false; + private static Dictionary m_IPTable; - public static void Initialize() - { - EventSink.DeleteRequest += EventSink_DeleteRequest; - EventSink.AccountLogin += EventSink_AccountLogin; - EventSink.GameLogin += EventSink_GameLogin; + private static readonly char[] m_ForbiddenChars = + { + '<', '>', ':', '"', '/', '\\', '|', '?', '*' + }; - if ( PasswordCommandEnabled ) - CommandSystem.Register( "Password", AccessLevel.Player, Password_OnCommand ); - } + public static AccessLevel LockdownLevel{ get; set; } - [Usage( "Password " )] - [Description( "Changes the password of the commanding players account. Requires the same C-class IP address as the account's creator." )] - public static void Password_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; + public static Dictionary IPTable + { + get + { + if (m_IPTable == null) + { + m_IPTable = new Dictionary(); - if ( !(from.Account is Account acct) ) - return; + foreach (Account a in Accounts.GetAccounts()) + if (a.LoginIPs.Length > 0) + { + IPAddress ip = a.LoginIPs[0]; - IPAddress[] accessList = acct.LoginIPs; + if (m_IPTable.ContainsKey(ip)) + m_IPTable[ip]++; + else + m_IPTable[ip] = 1; + } + } - if ( accessList.Length == 0 ) - return; + return m_IPTable; + } + } - NetState ns = from.NetState; + public static void Initialize() + { + EventSink.DeleteRequest += EventSink_DeleteRequest; + EventSink.AccountLogin += EventSink_AccountLogin; + EventSink.GameLogin += EventSink_GameLogin; - if ( ns == null ) - return; + if (PasswordCommandEnabled) + CommandSystem.Register("Password", AccessLevel.Player, Password_OnCommand); + } - if ( e.Length == 0 ) - { - from.SendMessage( "You must specify the new password." ); - return; - } - if ( e.Length == 1 ) - { - from.SendMessage( "To prevent potential typing mistakes, you must type the password twice. Use the format:" ); - from.SendMessage( "Password \"(newPassword)\" \"(repeated)\"" ); - return; - } + [Usage("Password ")] + [Description( + "Changes the password of the commanding players account. Requires the same C-class IP address as the account's creator.")] + public static void Password_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; - string pass = e.GetString( 0 ); - string pass2 = e.GetString( 1 ); + if (!(from.Account is Account acct)) + return; - if ( pass != pass2 ) - { - from.SendMessage( "The passwords do not match." ); - return; - } + IPAddress[] accessList = acct.LoginIPs; - bool isSafe = true; + if (accessList.Length == 0) + return; - for ( int i = 0; isSafe && i < pass.Length; ++i ) - isSafe = ( pass[i] >= 0x20 && pass[i] < 0x7F ); + NetState ns = from.NetState; - if ( !isSafe ) - { - from.SendMessage( "That is not a valid password." ); - return; - } + if (ns == null) + return; - try - { - IPAddress ipAddress = ns.Address; + if (e.Length == 0) + { + from.SendMessage("You must specify the new password."); + return; + } - if ( Utility.IPMatchClassC( accessList[0], ipAddress ) ) - { - acct.SetPassword( pass ); - from.SendMessage( "The password to your account has changed." ); - } - else - { - PageEntry entry = PageQueue.GetEntry( from ); + if (e.Length == 1) + { + from.SendMessage("To prevent potential typing mistakes, you must type the password twice. Use the format:"); + from.SendMessage("Password \"(newPassword)\" \"(repeated)\""); + return; + } - if ( entry != null ) - { - if ( entry.Message.StartsWith( "[Automated: Change Password]" ) ) - from.SendMessage( "You already have a password change request in the help system queue." ); - else - from.SendMessage( "Your IP address does not match that which created this account." ); - } - else if ( PageQueue.CheckAllowedToPage( from ) ) - { - from.SendMessage( "Your IP address does not match that which created this account. A page has been entered into the help system on your behalf." ); + string pass = e.GetString(0); + string pass2 = e.GetString(1); - from.SendLocalizedMessage( 501234, "", 0x35 ); /* The next available Counselor/Game Master will respond as soon as possible. + if (pass != pass2) + { + from.SendMessage("The passwords do not match."); + return; + } + + bool isSafe = true; + + for (int i = 0; isSafe && i < pass.Length; ++i) + isSafe = pass[i] >= 0x20 && pass[i] < 0x7F; + + if (!isSafe) + { + from.SendMessage("That is not a valid password."); + return; + } + + try + { + IPAddress ipAddress = ns.Address; + + if (Utility.IPMatchClassC(accessList[0], ipAddress)) + { + acct.SetPassword(pass); + from.SendMessage("The password to your account has changed."); + } + else + { + PageEntry entry = PageQueue.GetEntry(from); + + if (entry != null) + { + if (entry.Message.StartsWith("[Automated: Change Password]")) + from.SendMessage("You already have a password change request in the help system queue."); + else + from.SendMessage("Your IP address does not match that which created this account."); + } + else if (PageQueue.CheckAllowedToPage(from)) + { + from.SendMessage( + "Your IP address does not match that which created this account. A page has been entered into the help system on your behalf."); + + from.SendLocalizedMessage(501234, "", + 0x35); /* The next available Counselor/Game Master will respond as soon as possible. * Please check your Journal for messages every few minutes. */ - PageQueue.Enqueue( new PageEntry( from, - $"[Automated: Change Password]
Desired password: {pass}
Current IP address: {ipAddress}
Account IP address: {accessList[0]}", PageType.Account ) ); - } + PageQueue.Enqueue(new PageEntry(from, + $"[Automated: Change Password]
Desired password: {pass}
Current IP address: {ipAddress}
Account IP address: {accessList[0]}", + PageType.Account)); + } + } + } + catch + { + } + } - } - } - catch - { - } - } + private static void EventSink_DeleteRequest(DeleteRequestEventArgs e) + { + NetState state = e.State; + int index = e.Index; - private static void EventSink_DeleteRequest( DeleteRequestEventArgs e ) - { - NetState state = e.State; - int index = e.Index; + if (!(state.Account is Account acct)) + { + state.Dispose(); + } + else if (index < 0 || index >= acct.Length) + { + state.Send(new DeleteResult(DeleteResultType.BadRequest)); + state.Send(new CharacterListUpdate(acct)); + } + else + { + Mobile m = acct[index]; - if ( !(state.Account is Account acct) ) - { - state.Dispose(); - } - else if ( index < 0 || index >= acct.Length ) - { - state.Send( new DeleteResult( DeleteResultType.BadRequest ) ); - state.Send( new CharacterListUpdate( acct ) ); - } - else - { - Mobile m = acct[index]; + if (m == null) + { + state.Send(new DeleteResult(DeleteResultType.CharNotExist)); + state.Send(new CharacterListUpdate(acct)); + } + else if (m.NetState != null) + { + state.Send(new DeleteResult(DeleteResultType.CharBeingPlayed)); + state.Send(new CharacterListUpdate(acct)); + } + else if (RestrictDeletion && DateTime.UtcNow < m.CreationTime + DeleteDelay) + { + state.Send(new DeleteResult(DeleteResultType.CharTooYoung)); + state.Send(new CharacterListUpdate(acct)); + } + else if (m.AccessLevel == AccessLevel.Player && + Region.Find(m.LogoutLocation, m.LogoutMap).GetRegion(typeof(Jail)) != null + ) //Don't need to check current location, if netstate is null, they're logged out + { + state.Send(new DeleteResult(DeleteResultType.BadRequest)); + state.Send(new CharacterListUpdate(acct)); + } + else + { + Console.WriteLine("Client: {0}: Deleting character {1} (0x{2:X})", state, index, m.Serial.Value); - if ( m == null ) - { - state.Send( new DeleteResult( DeleteResultType.CharNotExist ) ); - state.Send( new CharacterListUpdate( acct ) ); - } - else if ( m.NetState != null ) - { - state.Send( new DeleteResult( DeleteResultType.CharBeingPlayed ) ); - state.Send( new CharacterListUpdate( acct ) ); - } - else if ( RestrictDeletion && DateTime.UtcNow < (m.CreationTime + DeleteDelay) ) - { - state.Send( new DeleteResult( DeleteResultType.CharTooYoung ) ); - state.Send( new CharacterListUpdate( acct ) ); - } - else if ( m.AccessLevel == AccessLevel.Player && Region.Find( m.LogoutLocation, m.LogoutMap ).GetRegion( typeof( Jail ) ) != null ) //Don't need to check current location, if netstate is null, they're logged out - { - state.Send( new DeleteResult( DeleteResultType.BadRequest ) ); - state.Send( new CharacterListUpdate( acct ) ); - } - else - { - Console.WriteLine( "Client: {0}: Deleting character {1} (0x{2:X})", state, index, m.Serial.Value ); + acct.Comments.Add(new AccountComment("System", $"Character #{index + 1} {m} deleted by {state}")); - acct.Comments.Add( new AccountComment( "System", $"Character #{index + 1} {m} deleted by {state}") ); + m.Delete(); + state.Send(new CharacterListUpdate(acct)); + } + } + } - m.Delete(); - state.Send( new CharacterListUpdate( acct ) ); - } - } - } + public static bool CanCreate(IPAddress ip) + { + if (!IPTable.ContainsKey(ip)) + return true; - public static bool CanCreate( IPAddress ip ) - { - if ( !IPTable.ContainsKey( ip ) ) - return true; + return IPTable[ip] < MaxAccountsPerIP; + } - return ( IPTable[ip] < MaxAccountsPerIP ); - } + private static bool IsForbiddenChar(char c) + { + for (int i = 0; i < m_ForbiddenChars.Length; ++i) + if (c == m_ForbiddenChars[i]) + return true; - private static Dictionary m_IPTable; + return false; + } - public static Dictionary IPTable - { - get - { - if ( m_IPTable == null ) - { - m_IPTable = new Dictionary(); + private static Account CreateAccount(NetState state, string un, string pw) + { + if (un.Length == 0 || pw.Length == 0) + return null; - foreach ( Account a in Accounts.GetAccounts() ) - if ( a.LoginIPs.Length > 0 ) - { - IPAddress ip = a.LoginIPs[0]; + bool isSafe = !(un.StartsWith(" ") || un.EndsWith(" ") || un.EndsWith(".")); - if ( m_IPTable.ContainsKey( ip ) ) - m_IPTable[ip]++; - else - m_IPTable[ip] = 1; - } - } + for (int i = 0; isSafe && i < un.Length; ++i) + isSafe = un[i] >= 0x20 && un[i] < 0x7F && !IsForbiddenChar(un[i]); - return m_IPTable; - } - } + for (int i = 0; isSafe && i < pw.Length; ++i) + isSafe = pw[i] >= 0x20 && pw[i] < 0x7F; - private static readonly char[] m_ForbiddenChars = { - '<', '>', ':', '"', '/', '\\', '|', '?', '*' - }; + if (!isSafe) + return null; - private static bool IsForbiddenChar( char c ) - { - for ( int i = 0; i < m_ForbiddenChars.Length; ++i ) - if ( c == m_ForbiddenChars[i] ) - return true; + if (!CanCreate(state.Address)) + { + Console.WriteLine("Login: {0}: Account '{1}' not created, ip already has {2} account{3}.", state, un, + MaxAccountsPerIP, MaxAccountsPerIP == 1 ? "" : "s"); + return null; + } - return false; - } + Console.WriteLine("Login: {0}: Creating new account '{1}'", state, un); - private static Account CreateAccount( NetState state, string un, string pw ) - { - if ( un.Length == 0 || pw.Length == 0 ) - return null; + Account a = new Account(un, pw); - bool isSafe = !( un.StartsWith( " " ) || un.EndsWith( " " ) || un.EndsWith( "." ) ); + return a; + } - for ( int i = 0; isSafe && i < un.Length; ++i ) - isSafe = ( un[i] >= 0x20 && un[i] < 0x7F && !IsForbiddenChar( un[i] ) ); + public static void EventSink_AccountLogin(AccountLoginEventArgs e) + { + if (!IPLimiter.SocketBlock && !IPLimiter.Verify(e.State.Address)) + { + e.Accepted = false; + e.RejectReason = ALRReason.InUse; - for ( int i = 0; isSafe && i < pw.Length; ++i ) - isSafe = ( pw[i] >= 0x20 && pw[i] < 0x7F ); + Console.WriteLine("Login: {0}: Past IP limit threshold", e.State); - if ( !isSafe ) - return null; + using (StreamWriter op = new StreamWriter("ipLimits.log", true)) + { + op.WriteLine("{0}\tPast IP limit threshold\t{1}", e.State, DateTime.UtcNow); + } - if ( !CanCreate( state.Address ) ) - { - Console.WriteLine( "Login: {0}: Account '{1}' not created, ip already has {2} account{3}.", state, un, MaxAccountsPerIP, MaxAccountsPerIP == 1 ? "" : "s" ); - return null; - } + return; + } - Console.WriteLine( "Login: {0}: Creating new account '{1}'", state, un ); + string un = e.Username; + string pw = e.Password; - Account a = new Account( un, pw ); + e.Accepted = false; - return a; - } + if (!(Accounts.GetAccount(un) is Account acct)) + { + if (AutoAccountCreation && un.Trim().Length > 0 + ) // To prevent someone from making an account of just '' or a bunch of meaningless spaces + { + e.State.Account = acct = CreateAccount(e.State, un, pw); + e.Accepted = acct?.CheckAccess(e.State) ?? false; - public static void EventSink_AccountLogin( AccountLoginEventArgs e ) - { - if ( !IPLimiter.SocketBlock && !IPLimiter.Verify( e.State.Address ) ) - { - e.Accepted = false; - e.RejectReason = ALRReason.InUse; + if (!e.Accepted) + e.RejectReason = ALRReason.BadComm; + } + else + { + Console.WriteLine("Login: {0}: Invalid username '{1}'", e.State, un); + e.RejectReason = ALRReason.Invalid; + } + } + else if (!acct.HasAccess(e.State)) + { + Console.WriteLine("Login: {0}: Access denied for '{1}'", e.State, un); + e.RejectReason = LockdownLevel > AccessLevel.Player ? ALRReason.BadComm : ALRReason.BadPass; + } + else if (!acct.CheckPassword(pw)) + { + Console.WriteLine("Login: {0}: Invalid password for '{1}'", e.State, un); + e.RejectReason = ALRReason.BadPass; + } + else if (acct.Banned) + { + Console.WriteLine("Login: {0}: Banned account '{1}'", e.State, un); + e.RejectReason = ALRReason.Blocked; + } + else + { + Console.WriteLine("Login: {0}: Valid credentials for '{1}'", e.State, un); + e.State.Account = acct; + e.Accepted = true; - Console.WriteLine( "Login: {0}: Past IP limit threshold", e.State ); + acct.LogAccess(e.State); + } - using ( StreamWriter op = new StreamWriter( "ipLimits.log", true ) ) - op.WriteLine( "{0}\tPast IP limit threshold\t{1}", e.State, DateTime.UtcNow ); + if (!e.Accepted) + AccountAttackLimiter.RegisterInvalidAccess(e.State); + } - return; - } + public static void EventSink_GameLogin(GameLoginEventArgs e) + { + if (!IPLimiter.SocketBlock && !IPLimiter.Verify(e.State.Address)) + { + e.Accepted = false; - string un = e.Username; - string pw = e.Password; + Console.WriteLine("Login: {0}: Past IP limit threshold", e.State); - e.Accepted = false; + using (StreamWriter op = new StreamWriter("ipLimits.log", true)) + { + op.WriteLine("{0}\tPast IP limit threshold\t{1}", e.State, DateTime.UtcNow); + } - if ( !(Accounts.GetAccount( un ) is Account acct) ) - { - if ( AutoAccountCreation && un.Trim().Length > 0 ) // To prevent someone from making an account of just '' or a bunch of meaningless spaces - { - e.State.Account = acct = CreateAccount( e.State, un, pw ); - e.Accepted = acct?.CheckAccess( e.State ) ?? false; + return; + } - if ( !e.Accepted ) - e.RejectReason = ALRReason.BadComm; - } - else - { - Console.WriteLine( "Login: {0}: Invalid username '{1}'", e.State, un ); - e.RejectReason = ALRReason.Invalid; - } - } - else if ( !acct.HasAccess( e.State ) ) - { - Console.WriteLine( "Login: {0}: Access denied for '{1}'", e.State, un ); - e.RejectReason = ( LockdownLevel > AccessLevel.Player ? ALRReason.BadComm : ALRReason.BadPass ); - } - else if ( !acct.CheckPassword( pw ) ) - { - Console.WriteLine( "Login: {0}: Invalid password for '{1}'", e.State, un ); - e.RejectReason = ALRReason.BadPass; - } - else if ( acct.Banned ) - { - Console.WriteLine( "Login: {0}: Banned account '{1}'", e.State, un ); - e.RejectReason = ALRReason.Blocked; - } - else - { - Console.WriteLine( "Login: {0}: Valid credentials for '{1}'", e.State, un ); - e.State.Account = acct; - e.Accepted = true; + string un = e.Username; + string pw = e.Password; - acct.LogAccess( e.State ); - } + if (!(Accounts.GetAccount(un) is Account acct)) + { + e.Accepted = false; + } + else if (!acct.HasAccess(e.State)) + { + Console.WriteLine("Login: {0}: Access denied for '{1}'", e.State, un); + e.Accepted = false; + } + else if (!acct.CheckPassword(pw)) + { + Console.WriteLine("Login: {0}: Invalid password for '{1}'", e.State, un); + e.Accepted = false; + } + else if (acct.Banned) + { + Console.WriteLine("Login: {0}: Banned account '{1}'", e.State, un); + e.Accepted = false; + } + else + { + acct.LogAccess(e.State); - if ( !e.Accepted ) - AccountAttackLimiter.RegisterInvalidAccess( e.State ); - } + Console.WriteLine("Login: {0}: Account '{1}' at character list", e.State, un); + e.State.Account = acct; + e.Accepted = true; + e.CityInfo = StartingCities; + } - public static void EventSink_GameLogin( GameLoginEventArgs e ) - { - if ( !IPLimiter.SocketBlock && !IPLimiter.Verify( e.State.Address ) ) - { - e.Accepted = false; + if (!e.Accepted) + AccountAttackLimiter.RegisterInvalidAccess(e.State); + } - Console.WriteLine( "Login: {0}: Past IP limit threshold", e.State ); + public static bool CheckAccount(Mobile mobCheck, Mobile accCheck) + { + if (accCheck?.Account is Account a) + for (int i = 0; i < a.Length; ++i) + if (a[i] == mobCheck) + return true; - using ( StreamWriter op = new StreamWriter( "ipLimits.log", true ) ) - op.WriteLine( "{0}\tPast IP limit threshold\t{1}", e.State, DateTime.UtcNow ); - - return; - } - - string un = e.Username; - string pw = e.Password; - - if ( !(Accounts.GetAccount( un ) is Account acct) ) - { - e.Accepted = false; - } - else if ( !acct.HasAccess( e.State ) ) - { - Console.WriteLine( "Login: {0}: Access denied for '{1}'", e.State, un ); - e.Accepted = false; - } - else if ( !acct.CheckPassword( pw ) ) - { - Console.WriteLine( "Login: {0}: Invalid password for '{1}'", e.State, un ); - e.Accepted = false; - } - else if ( acct.Banned ) - { - Console.WriteLine( "Login: {0}: Banned account '{1}'", e.State, un ); - e.Accepted = false; - } - else - { - acct.LogAccess( e.State ); - - Console.WriteLine( "Login: {0}: Account '{1}' at character list", e.State, un ); - e.State.Account = acct; - e.Accepted = true; - e.CityInfo = StartingCities; - } - - if ( !e.Accepted ) - AccountAttackLimiter.RegisterInvalidAccess( e.State ); - } - - public static bool CheckAccount( Mobile mobCheck, Mobile accCheck ) - { - if ( accCheck?.Account is Account a ) - { - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] == mobCheck ) - return true; - } - } - - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Accounting/AccountTag.cs b/Scripts/Accounting/AccountTag.cs index 5d7f17ebb..b67a20c1b 100644 --- a/Scripts/Accounting/AccountTag.cs +++ b/Scripts/Accounting/AccountTag.cs @@ -2,49 +2,49 @@ using System.Xml; namespace Server.Accounting { - public class AccountTag - { - /// - /// Gets or sets the name of this tag. - /// - public string Name { get; set; } + public class AccountTag + { + /// + /// Constructs a new AccountTag instance with a specific name and value. + /// + /// Initial name. + /// Initial value. + public AccountTag(string name, string value) + { + Name = name; + Value = value; + } - /// - /// Gets or sets the value of this tag. - /// - public string Value { get; set; } + /// + /// Deserializes an AccountTag instance from an xml element. + /// + /// The XmlElement instance from which to deserialize. + public AccountTag(XmlElement node) + { + Name = Utility.GetAttribute(node, "name", "empty"); + Value = Utility.GetText(node, ""); + } - /// - /// Constructs a new AccountTag instance with a specific name and value. - /// - /// Initial name. - /// Initial value. - public AccountTag( string name, string value ) - { - Name = name; - Value = value; - } + /// + /// Gets or sets the name of this tag. + /// + public string Name{ get; set; } - /// - /// Deserializes an AccountTag instance from an xml element. - /// - /// The XmlElement instance from which to deserialize. - public AccountTag( XmlElement node ) - { - Name = Utility.GetAttribute( node, "name", "empty" ); - Value = Utility.GetText( node, "" ); - } + /// + /// Gets or sets the value of this tag. + /// + public string Value{ get; set; } - /// - /// Serializes this AccountTag instance to an XmlTextWriter. - /// - /// The XmlTextWriter instance from which to serialize. - public void Save( XmlTextWriter xml ) - { - xml.WriteStartElement( "tag" ); - xml.WriteAttributeString( "name", Name ); - xml.WriteString( Value ); - xml.WriteEndElement(); - } - } + /// + /// Serializes this AccountTag instance to an XmlTextWriter. + /// + /// The XmlTextWriter instance from which to serialize. + public void Save(XmlTextWriter xml) + { + xml.WriteStartElement("tag"); + xml.WriteAttributeString("name", Name); + xml.WriteString(Value); + xml.WriteEndElement(); + } + } } \ No newline at end of file diff --git a/Scripts/Accounting/Accounts.cs b/Scripts/Accounting/Accounts.cs index 2c1f2eb09..0374fa1d0 100644 --- a/Scripts/Accounting/Accounts.cs +++ b/Scripts/Accounting/Accounts.cs @@ -5,99 +5,97 @@ using System.Xml; namespace Server.Accounting { - public class Accounts - { - private static Dictionary m_Accounts = new Dictionary(); + public class Accounts + { + private static Dictionary m_Accounts = new Dictionary(); - public static void Configure() - { - EventSink.WorldLoad += Load; - EventSink.WorldSave += Save; - } + static Accounts() + { + } - static Accounts() - { - } + public static int Count => m_Accounts.Count; - public static int Count => m_Accounts.Count; + public static void Configure() + { + EventSink.WorldLoad += Load; + EventSink.WorldSave += Save; + } - public static ICollection GetAccounts() - { - return m_Accounts.Values; - } + public static ICollection GetAccounts() + { + return m_Accounts.Values; + } - public static IAccount GetAccount( string username ) - { - m_Accounts.TryGetValue( username, out IAccount a ); + public static IAccount GetAccount(string username) + { + m_Accounts.TryGetValue(username, out IAccount a); - return a; - } + return a; + } - public static void Add( IAccount a ) - { - m_Accounts[a.Username] = a; - } + public static void Add(IAccount a) + { + m_Accounts[a.Username] = a; + } - public static void Remove( string username ) - { - m_Accounts.Remove( username ); - } + public static void Remove(string username) + { + m_Accounts.Remove(username); + } - public static void Load() - { - m_Accounts = new Dictionary( 32, StringComparer.OrdinalIgnoreCase ); + public static void Load() + { + m_Accounts = new Dictionary(32, StringComparer.OrdinalIgnoreCase); - string filePath = Path.Combine( "Saves/Accounts", "accounts.xml" ); + string filePath = Path.Combine("Saves/Accounts", "accounts.xml"); - if ( !File.Exists( filePath ) ) - return; + if (!File.Exists(filePath)) + return; - XmlDocument doc = new XmlDocument(); - doc.Load( filePath ); + XmlDocument doc = new XmlDocument(); + doc.Load(filePath); - XmlElement root = doc["accounts"]; + XmlElement root = doc["accounts"]; - foreach ( XmlElement account in root.GetElementsByTagName( "account" ) ) - { - try - { - Account acct = new Account( account ); - } - catch - { - Console.WriteLine( "Warning: Account instance load failed" ); - } - } - } + foreach (XmlElement account in root.GetElementsByTagName("account")) + try + { + Account acct = new Account(account); + } + catch + { + Console.WriteLine("Warning: Account instance load failed"); + } + } - public static void Save( WorldSaveEventArgs e ) - { - if ( !Directory.Exists( "Saves/Accounts" ) ) - Directory.CreateDirectory( "Saves/Accounts" ); + public static void Save(WorldSaveEventArgs e) + { + if (!Directory.Exists("Saves/Accounts")) + Directory.CreateDirectory("Saves/Accounts"); - string filePath = Path.Combine( "Saves/Accounts", "accounts.xml" ); + string filePath = Path.Combine("Saves/Accounts", "accounts.xml"); - using ( StreamWriter op = new StreamWriter( filePath ) ) - { - XmlTextWriter xml = new XmlTextWriter( op ); + using (StreamWriter op = new StreamWriter(filePath)) + { + XmlTextWriter xml = new XmlTextWriter(op); - xml.Formatting = Formatting.Indented; - xml.IndentChar = '\t'; - xml.Indentation = 1; + xml.Formatting = Formatting.Indented; + xml.IndentChar = '\t'; + xml.Indentation = 1; - xml.WriteStartDocument( true ); + xml.WriteStartDocument(true); - xml.WriteStartElement( "accounts" ); + xml.WriteStartElement("accounts"); - xml.WriteAttributeString( "count", m_Accounts.Count.ToString() ); + xml.WriteAttributeString("count", m_Accounts.Count.ToString()); - foreach ( Account a in GetAccounts() ) - a.Save( xml ); + foreach (Account a in GetAccounts()) + a.Save(xml); - xml.WriteEndElement(); + xml.WriteEndElement(); - xml.Close(); - } - } - } -} + xml.Close(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Accounting/Firewall.cs b/Scripts/Accounting/Firewall.cs index e7d444944..86e28014e 100644 --- a/Scripts/Accounting/Firewall.cs +++ b/Scripts/Accounting/Firewall.cs @@ -1,303 +1,156 @@ -using System; using System.Collections.Generic; using System.IO; using System.Net; namespace Server { - public class Firewall - { - #region Firewall Entries - public interface IFirewallEntry - { - bool IsBlocked( IPAddress address ); - } + public class Firewall + { + static Firewall() + { + List = new List(); - public class IPFirewallEntry : IFirewallEntry - { - IPAddress m_Address; - public IPFirewallEntry( IPAddress address ) - { - m_Address = address; - } + string path = "firewall.cfg"; - public bool IsBlocked( IPAddress address ) - { - return m_Address.Equals( address ); - } + if (File.Exists(path)) + using (StreamReader ip = new StreamReader(path)) + { + string line; - public override string ToString() - { - return m_Address.ToString(); - } + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); - public override bool Equals( object obj ) - { - if ( obj is IPAddress ) - { - return obj.Equals( m_Address ); - } - if ( obj is string s ) - { - if ( IPAddress.TryParse( s, out IPAddress otherAddress ) ) - return otherAddress.Equals( m_Address ); - } - else if ( obj is IPFirewallEntry entry ) - { - return m_Address.Equals( entry.m_Address ); - } + if (line.Length == 0) + continue; - return false; - } + List.Add(ToFirewallEntry(line)); - public override int GetHashCode() - { - return m_Address.GetHashCode(); - } - } + /* + object toAdd; - public class CIDRFirewallEntry : IFirewallEntry - { - IPAddress m_CIDRPrefix; - int m_CIDRLength; + IPAddress addr; + if ( IPAddress.TryParse( line, out addr ) ) + toAdd = addr; + else + toAdd = line; - public CIDRFirewallEntry( IPAddress cidrPrefix, int cidrLength ) - { - m_CIDRPrefix = cidrPrefix; - m_CIDRLength = cidrLength; - } + m_Blocked.Add( toAdd.ToString() ); + * */ + } + } + } - public bool IsBlocked( IPAddress address ) - { - return Utility.IPMatchCIDR( m_CIDRPrefix, address, m_CIDRLength ); - } + public static List List{ get; } - public override string ToString() - { - return $"{m_CIDRPrefix}/{m_CIDRLength}"; - } + public static IFirewallEntry ToFirewallEntry(object entry) + { + if (entry is IFirewallEntry firewallEntry) + return firewallEntry; + if (entry is IPAddress address) + return new IPFirewallEntry(address); + if (entry is string s) + return ToFirewallEntry(s); - public override bool Equals( object obj ) - { - if ( obj is string entry ) - { - string[] str = entry.Split( '/' ); + return null; + } - if ( str.Length == 2 ) - { - if ( IPAddress.TryParse( str[0], out IPAddress cidrPrefix ) ) - { - if ( int.TryParse( str[1], out int cidrLength ) ) - return m_CIDRPrefix.Equals( cidrPrefix ) && m_CIDRLength.Equals( cidrLength ); - } - } - } - else if ( obj is CIDRFirewallEntry cidrEntry ) - { - return m_CIDRPrefix.Equals( cidrEntry.m_CIDRPrefix ) && m_CIDRLength.Equals( cidrEntry.m_CIDRLength ); - } + public static IFirewallEntry ToFirewallEntry(string entry) + { + if (IPAddress.TryParse(entry, out IPAddress addr)) + return new IPFirewallEntry(addr); - return false; - } + //Try CIDR parse + string[] str = entry.Split('/'); - public override int GetHashCode() - { - return m_CIDRPrefix.GetHashCode() ^ m_CIDRLength.GetHashCode(); - } - } + if (str.Length == 2) + if (IPAddress.TryParse(str[0], out IPAddress cidrPrefix)) + if (int.TryParse(str[1], out int cidrLength)) + return new CIDRFirewallEntry(cidrPrefix, cidrLength); - public class WildcardIPFirewallEntry : IFirewallEntry - { - string m_Entry; + return new WildcardIPFirewallEntry(entry); + } - bool m_Valid = true; + public static void RemoveAt(int index) + { + List.RemoveAt(index); + Save(); + } - public WildcardIPFirewallEntry( string entry ) - { - m_Entry = entry; - } + public static void Remove(object obj) + { + IFirewallEntry entry = ToFirewallEntry(obj); - public bool IsBlocked( IPAddress address ) - { - if ( !m_Valid ) - return false; //Why process if it's invalid? it'll return false anyway after processing it. + if (entry != null) + { + List.Remove(entry); + Save(); + } + } - return Utility.IPMatch( m_Entry, address, ref m_Valid ); - } + public static void Add(object obj) + { + if (obj is IPAddress address) + Add(address); + else if (obj is string s) + Add(s); + else if (obj is IFirewallEntry entry) + Add(entry); + } - public override string ToString() - { - return m_Entry; - } + public static void Add(IFirewallEntry entry) + { + if (!List.Contains(entry)) + List.Add(entry); - public override bool Equals( object obj ) - { - if ( obj is string ) - return obj.Equals( m_Entry ); + Save(); + } - return obj is WildcardIPFirewallEntry entry && m_Entry.Equals( entry.m_Entry ); - } + public static void Add(string pattern) + { + IFirewallEntry entry = ToFirewallEntry(pattern); - public override int GetHashCode() - { - return m_Entry.GetHashCode(); - } - } - #endregion + if (!List.Contains(entry)) + List.Add(entry); - static Firewall() - { - List = new List(); + Save(); + } - string path = "firewall.cfg"; + public static void Add(IPAddress ip) + { + IFirewallEntry entry = new IPFirewallEntry(ip); - if ( File.Exists( path ) ) - { - using ( StreamReader ip = new StreamReader( path ) ) - { - string line; + if (!List.Contains(entry)) + List.Add(entry); - while ( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); + Save(); + } - if ( line.Length == 0 ) - continue; + public static void Save() + { + string path = "firewall.cfg"; - List.Add( ToFirewallEntry( line ) ); + using (StreamWriter op = new StreamWriter(path)) + { + for (int i = 0; i < List.Count; ++i) + op.WriteLine(List[i]); + } + } - /* - object toAdd; + public static bool IsBlocked(IPAddress ip) + { + for (int i = 0; i < List.Count; i++) + if (List[i].IsBlocked(ip)) + return true; - IPAddress addr; - if ( IPAddress.TryParse( line, out addr ) ) - toAdd = addr; - else - toAdd = line; + return false; + /* + bool contains = false; - m_Blocked.Add( toAdd.ToString() ); - * */ - } - } - } - } - - public static List List { get; } - - public static IFirewallEntry ToFirewallEntry( object entry ) - { - if ( entry is IFirewallEntry firewallEntry ) - return firewallEntry; - if ( entry is IPAddress address ) - return new IPFirewallEntry( address ); - if ( entry is string s ) - return ToFirewallEntry( s ); - - return null; - } - - public static IFirewallEntry ToFirewallEntry( string entry ) - { - if ( IPAddress.TryParse( entry, out IPAddress addr ) ) - return new IPFirewallEntry( addr ); - - //Try CIDR parse - string[] str = entry.Split( '/' ); - - if ( str.Length == 2 ) - { - if ( IPAddress.TryParse( str[0], out IPAddress cidrPrefix ) ) - { - if ( int.TryParse( str[1], out int cidrLength ) ) - return new CIDRFirewallEntry( cidrPrefix, cidrLength ); - } - } - - return new WildcardIPFirewallEntry( entry ); - } - - public static void RemoveAt( int index ) - { - List.RemoveAt( index ); - Save(); - } - - public static void Remove( object obj ) - { - IFirewallEntry entry = ToFirewallEntry( obj ); - - if ( entry != null ) - { - List.Remove( entry ); - Save(); - } - } - - public static void Add( object obj ) - { - if ( obj is IPAddress address ) - Add( address ); - else if ( obj is string s ) - Add( s ); - else if ( obj is IFirewallEntry entry ) - Add( entry ); - } - - public static void Add( IFirewallEntry entry ) - { - if ( !List.Contains( entry ) ) - List.Add( entry ); - - Save(); - } - - public static void Add( string pattern ) - { - IFirewallEntry entry = ToFirewallEntry( pattern ); - - if ( !List.Contains( entry ) ) - List.Add( entry ); - - Save(); - } - - public static void Add( IPAddress ip ) - { - IFirewallEntry entry = new IPFirewallEntry( ip ); - - if ( !List.Contains( entry ) ) - List.Add( entry ); - - Save(); - } - - public static void Save() - { - string path = "firewall.cfg"; - - using ( StreamWriter op = new StreamWriter( path ) ) - { - for ( int i = 0; i < List.Count; ++i ) - op.WriteLine( List[i] ); - } - } - - public static bool IsBlocked( IPAddress ip ) - { - for( int i = 0; i < List.Count; i++ ) - { - if ( List[i].IsBlocked( ip ) ) - return true; - } - - return false; - /* - bool contains = false; - - for ( int i = 0; !contains && i < m_Blocked.Count; ++i ) - { - if ( m_Blocked[i] is IPAddress ) - contains = ip.Equals( m_Blocked[i] ); + for ( int i = 0; !contains && i < m_Blocked.Count; ++i ) + { + if ( m_Blocked[i] is IPAddress ) + contains = ip.Equals( m_Blocked[i] ); else if ( m_Blocked[i] is String ) { string s = (string)m_Blocked[i]; @@ -307,10 +160,144 @@ namespace Server if ( !contains ) contains = Utility.IPMatch( s, ip ); } - } + } - return contains; - * */ - } - } -} + return contains; + * */ + } + + #region Firewall Entries + + public interface IFirewallEntry + { + bool IsBlocked(IPAddress address); + } + + public class IPFirewallEntry : IFirewallEntry + { + private IPAddress m_Address; + + public IPFirewallEntry(IPAddress address) + { + m_Address = address; + } + + public bool IsBlocked(IPAddress address) + { + return m_Address.Equals(address); + } + + public override string ToString() + { + return m_Address.ToString(); + } + + public override bool Equals(object obj) + { + if (obj is IPAddress) return obj.Equals(m_Address); + if (obj is string s) + { + if (IPAddress.TryParse(s, out IPAddress otherAddress)) + return otherAddress.Equals(m_Address); + } + else if (obj is IPFirewallEntry entry) + { + return m_Address.Equals(entry.m_Address); + } + + return false; + } + + public override int GetHashCode() + { + return m_Address.GetHashCode(); + } + } + + public class CIDRFirewallEntry : IFirewallEntry + { + private int m_CIDRLength; + private IPAddress m_CIDRPrefix; + + public CIDRFirewallEntry(IPAddress cidrPrefix, int cidrLength) + { + m_CIDRPrefix = cidrPrefix; + m_CIDRLength = cidrLength; + } + + public bool IsBlocked(IPAddress address) + { + return Utility.IPMatchCIDR(m_CIDRPrefix, address, m_CIDRLength); + } + + public override string ToString() + { + return $"{m_CIDRPrefix}/{m_CIDRLength}"; + } + + public override bool Equals(object obj) + { + if (obj is string entry) + { + string[] str = entry.Split('/'); + + if (str.Length == 2) + if (IPAddress.TryParse(str[0], out IPAddress cidrPrefix)) + if (int.TryParse(str[1], out int cidrLength)) + return m_CIDRPrefix.Equals(cidrPrefix) && m_CIDRLength.Equals(cidrLength); + } + else if (obj is CIDRFirewallEntry cidrEntry) + { + return m_CIDRPrefix.Equals(cidrEntry.m_CIDRPrefix) && m_CIDRLength.Equals(cidrEntry.m_CIDRLength); + } + + return false; + } + + public override int GetHashCode() + { + return m_CIDRPrefix.GetHashCode() ^ m_CIDRLength.GetHashCode(); + } + } + + public class WildcardIPFirewallEntry : IFirewallEntry + { + private string m_Entry; + + private bool m_Valid = true; + + public WildcardIPFirewallEntry(string entry) + { + m_Entry = entry; + } + + public bool IsBlocked(IPAddress address) + { + if (!m_Valid) + return false; //Why process if it's invalid? it'll return false anyway after processing it. + + return Utility.IPMatch(m_Entry, address, ref m_Valid); + } + + public override string ToString() + { + return m_Entry; + } + + public override bool Equals(object obj) + { + if (obj is string) + return obj.Equals(m_Entry); + + return obj is WildcardIPFirewallEntry entry && m_Entry.Equals(entry.m_Entry); + } + + public override int GetHashCode() + { + return m_Entry.GetHashCode(); + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Accounting/IPLimiter.cs b/Scripts/Accounting/IPLimiter.cs index 7a65c49e2..072ed9148 100644 --- a/Scripts/Accounting/IPLimiter.cs +++ b/Scripts/Accounting/IPLimiter.cs @@ -4,51 +4,50 @@ using Server.Network; namespace Server.Misc { - public class IPLimiter - { - public static bool Enabled = true; - public static bool SocketBlock = true; // true to block at connection, false to block at login request + public class IPLimiter + { + public static bool Enabled = true; + public static bool SocketBlock = true; // true to block at connection, false to block at login request - public static int MaxAddresses = 10; - - public static IPAddress[] Exemptions = { - //IPAddress.Parse( "127.0.0.1" ), - }; + public static int MaxAddresses = 10; - public static bool IsExempt( IPAddress ip ) - { - for ( int i = 0; i < Exemptions.Length; i++ ) - { - if ( ip.Equals( Exemptions[i] ) ) - return true; - } + public static IPAddress[] Exemptions = + { + //IPAddress.Parse( "127.0.0.1" ), + }; - return false; - } + public static bool IsExempt(IPAddress ip) + { + for (int i = 0; i < Exemptions.Length; i++) + if (ip.Equals(Exemptions[i])) + return true; - public static bool Verify( IPAddress ourAddress ) - { - if ( !Enabled || IsExempt( ourAddress ) ) - return true; + return false; + } - List netStates = NetState.Instances; + public static bool Verify(IPAddress ourAddress) + { + if (!Enabled || IsExempt(ourAddress)) + return true; - int count = 0; + List netStates = NetState.Instances; - for ( int i = 0; i < netStates.Count; ++i ) - { - NetState compState = netStates[i]; + int count = 0; - if ( ourAddress.Equals( compState.Address ) ) - { - ++count; + for (int i = 0; i < netStates.Count; ++i) + { + NetState compState = netStates[i]; - if ( count >= MaxAddresses ) - return false; - } - } + if (ourAddress.Equals(compState.Address)) + { + ++count; - return true; - } - } + if (count >= MaxAddresses) + return false; + } + } + + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Add.cs b/Scripts/Commands/Add.cs index eca95cc0e..eca389a5d 100644 --- a/Scripts/Commands/Add.cs +++ b/Scripts/Commands/Add.cs @@ -8,710 +8,721 @@ using CPA = Server.CommandPropertyAttribute; namespace Server.Commands { - public class Add - { - public static void Initialize() - { - CommandSystem.Register( "Tile", AccessLevel.GameMaster, Tile_OnCommand ); - CommandSystem.Register( "TileRXYZ", AccessLevel.GameMaster, TileRXYZ_OnCommand ); - CommandSystem.Register( "TileXYZ", AccessLevel.GameMaster, TileXYZ_OnCommand ); - CommandSystem.Register( "TileZ", AccessLevel.GameMaster, TileZ_OnCommand ); - CommandSystem.Register( "TileAvg", AccessLevel.GameMaster, TileAvg_OnCommand ); + public class Add + { + private static Type m_EntityType = typeof(IEntity); - CommandSystem.Register( "Outline", AccessLevel.GameMaster, Outline_OnCommand ); - CommandSystem.Register( "OutlineRXYZ", AccessLevel.GameMaster, OutlineRXYZ_OnCommand ); - CommandSystem.Register( "OutlineXYZ", AccessLevel.GameMaster, OutlineXYZ_OnCommand ); - CommandSystem.Register( "OutlineZ", AccessLevel.GameMaster, OutlineZ_OnCommand ); - CommandSystem.Register( "OutlineAvg", AccessLevel.GameMaster, OutlineAvg_OnCommand ); - } + private static Type m_ConstructibleType = typeof(ConstructibleAttribute); - public static void Invoke( Mobile from, Point3D start, Point3D end, string[] args ) - { - Invoke( from, start, end, args, null, false, false ); - } + private static Type m_EnumType = typeof(Enum); - public static void Invoke( Mobile from, Point3D start, Point3D end, string[] args, List packs ) - { - Invoke( from, start, end, args, packs, false, false ); - } + private static Type m_TypeType = typeof(Type); - public static void Invoke( Mobile from, Point3D start, Point3D end, string[] args, List packs, bool outline, bool mapAvg ) - { - StringBuilder sb = new StringBuilder(); + private static Type m_ParsableType = typeof(ParsableAttribute); - sb.AppendFormat( "{0} {1} building ", from.AccessLevel, CommandLogging.Format( from ) ); + private static Type[] m_ParseTypes = { typeof(string) }; + private static object[] m_ParseArgs = new object[1]; - if ( start == end ) - sb.AppendFormat( "at {0} in {1}", start, from.Map ); - else - sb.AppendFormat( "from {0} to {1} in {2}", start, end, from.Map ); + private static Type[] m_SignedNumerics = + { + typeof(long), + typeof(int), + typeof(short), + typeof(sbyte) + }; - sb.Append( ":" ); + private static Type[] m_UnsignedNumerics = + { + typeof(ulong), + typeof(uint), + typeof(ushort), + typeof(byte) + }; - for ( int i = 0; i < args.Length; ++i ) - sb.AppendFormat( " \"{0}\"", args[i] ); + public static void Initialize() + { + CommandSystem.Register("Tile", AccessLevel.GameMaster, Tile_OnCommand); + CommandSystem.Register("TileRXYZ", AccessLevel.GameMaster, TileRXYZ_OnCommand); + CommandSystem.Register("TileXYZ", AccessLevel.GameMaster, TileXYZ_OnCommand); + CommandSystem.Register("TileZ", AccessLevel.GameMaster, TileZ_OnCommand); + CommandSystem.Register("TileAvg", AccessLevel.GameMaster, TileAvg_OnCommand); - CommandLogging.WriteLine( from, sb.ToString() ); + CommandSystem.Register("Outline", AccessLevel.GameMaster, Outline_OnCommand); + CommandSystem.Register("OutlineRXYZ", AccessLevel.GameMaster, OutlineRXYZ_OnCommand); + CommandSystem.Register("OutlineXYZ", AccessLevel.GameMaster, OutlineXYZ_OnCommand); + CommandSystem.Register("OutlineZ", AccessLevel.GameMaster, OutlineZ_OnCommand); + CommandSystem.Register("OutlineAvg", AccessLevel.GameMaster, OutlineAvg_OnCommand); + } - string name = args[0]; + public static void Invoke(Mobile from, Point3D start, Point3D end, string[] args) + { + Invoke(from, start, end, args, null, false, false); + } - FixArgs( ref args ); + public static void Invoke(Mobile from, Point3D start, Point3D end, string[] args, List packs) + { + Invoke(from, start, end, args, packs, false, false); + } - string[,] props = null; + public static void Invoke(Mobile from, Point3D start, Point3D end, string[] args, List packs, + bool outline, bool mapAvg) + { + StringBuilder sb = new StringBuilder(); - for ( int i = 0; i < args.Length; ++i ) - { - if ( Insensitive.Equals( args[i], "set" ) ) - { - int remains = args.Length - i - 1; - - if ( remains >= 2 ) - { - props = new string[remains / 2, 2]; - - remains /= 2; - - for ( int j = 0; j < remains; ++j ) - { - props[j, 0] = args[i + (j * 2) + 1]; - props[j, 1] = args[i + (j * 2) + 2]; - } + sb.AppendFormat("{0} {1} building ", from.AccessLevel, CommandLogging.Format(from)); - FixSetString( ref args, i ); - } - - break; - } - } + if (start == end) + sb.AppendFormat("at {0} in {1}", start, from.Map); + else + sb.AppendFormat("from {0} to {1} in {2}", start, end, from.Map); - Type type = ScriptCompiler.FindTypeByName( name ); + sb.Append(":"); - if ( !IsEntity( type ) ) { - from.SendMessage( "No type with that name was found." ); - return; - } + for (int i = 0; i < args.Length; ++i) + sb.AppendFormat(" \"{0}\"", args[i]); - DateTime time = DateTime.UtcNow; + CommandLogging.WriteLine(from, sb.ToString()); - int built = BuildObjects( from, type, start, end, args, props, packs, outline, mapAvg ); + string name = args[0]; - if ( built > 0 ) - from.SendMessage( "{0} object{1} generated in {2:F1} seconds.", built, built != 1 ? "s" : "", (DateTime.UtcNow - time).TotalSeconds ); - else - SendUsage( type, from ); - } + FixArgs(ref args); - public static void FixSetString( ref string[] args, int index ) - { - string[] old = args; - args = new string[index]; + string[,] props = null; - Array.Copy( old, 0, args, 0, index ); - } + for (int i = 0; i < args.Length; ++i) + if (Insensitive.Equals(args[i], "set")) + { + int remains = args.Length - i - 1; + + if (remains >= 2) + { + props = new string[remains / 2, 2]; + + remains /= 2; + + for (int j = 0; j < remains; ++j) + { + props[j, 0] = args[i + j * 2 + 1]; + props[j, 1] = args[i + j * 2 + 2]; + } + + FixSetString(ref args, i); + } - public static void FixArgs( ref string[] args ) - { - string[] old = args; - args = new string[args.Length - 1]; + break; + } - Array.Copy( old, 1, args, 0, args.Length ); - } + Type type = ScriptCompiler.FindTypeByName(name); - public static int BuildObjects( Mobile from, Type type, Point3D start, Point3D end, string[] args, string[,] props, List packs ) - { - return BuildObjects( from, type, start, end, args, props, packs, false, false ); - } + if (!IsEntity(type)) + { + from.SendMessage("No type with that name was found."); + return; + } + + DateTime time = DateTime.UtcNow; + + int built = BuildObjects(from, type, start, end, args, props, packs, outline, mapAvg); + + if (built > 0) + from.SendMessage("{0} object{1} generated in {2:F1} seconds.", built, built != 1 ? "s" : "", + (DateTime.UtcNow - time).TotalSeconds); + else + SendUsage(type, from); + } - public static int BuildObjects( Mobile from, Type type, Point3D start, Point3D end, string[] args, string[,] props, List packs, bool outline, bool mapAvg ) - { - Utility.FixPoints( ref start, ref end ); + public static void FixSetString(ref string[] args, int index) + { + string[] old = args; + args = new string[index]; - PropertyInfo[] realProps = null; + Array.Copy(old, 0, args, 0, index); + } - if ( props != null ) - { - realProps = new PropertyInfo[props.GetLength( 0 )]; + public static void FixArgs(ref string[] args) + { + string[] old = args; + args = new string[args.Length - 1]; - PropertyInfo[] allProps = type.GetProperties( BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public ); + Array.Copy(old, 1, args, 0, args.Length); + } - for ( int i = 0; i < realProps.Length; ++i ) - { - PropertyInfo thisProp = null; + public static int BuildObjects(Mobile from, Type type, Point3D start, Point3D end, string[] args, string[,] props, + List packs) + { + return BuildObjects(from, type, start, end, args, props, packs, false, false); + } - string propName = props[i, 0]; + public static int BuildObjects(Mobile from, Type type, Point3D start, Point3D end, string[] args, string[,] props, + List packs, bool outline, bool mapAvg) + { + Utility.FixPoints(ref start, ref end); - for ( int j = 0; thisProp == null && j < allProps.Length; ++j ) - { - if ( Insensitive.Equals( propName, allProps[j].Name ) ) - thisProp = allProps[j]; - } - - if ( thisProp == null ) - { - from.SendMessage( "Property not found: {0}", propName ); - } - else - { - CPA attr = Properties.GetCPA( thisProp ); - - if ( attr == null ) - from.SendMessage( "Property ({0}) not found.", propName ); - else if ( from.AccessLevel < attr.WriteLevel ) - from.SendMessage( "Setting this property ({0}) requires at least {1} access level.", propName, Mobile.GetAccessLevelName( attr.WriteLevel ) ); - else if ( !thisProp.CanWrite || attr.ReadOnly ) - from.SendMessage( "Property ({0}) is read only.", propName ); - else - realProps[i] = thisProp; - } - } - } - - ConstructorInfo[] ctors = type.GetConstructors(); - - for ( int i = 0; i < ctors.Length; ++i ) - { - ConstructorInfo ctor = ctors[i]; - - if ( !IsConstructible( ctor, from.AccessLevel ) ) - continue; - - ParameterInfo[] paramList = ctor.GetParameters(); - - if ( args.Length == paramList.Length ) - { - object[] paramValues = ParseValues( paramList, args ); - - if ( paramValues == null ) - continue; - - int built = Build( from, start, end, ctor, paramValues, props, realProps, packs, outline, mapAvg ); - - if ( built > 0 ) - return built; - } - } - - return 0; - } - - public static object[] ParseValues( ParameterInfo[] paramList, string[] args ) - { - object[] values = new object[args.Length]; - - for ( int i = 0; i < args.Length; ++i ) - { - object value = ParseValue( paramList[i].ParameterType, args[i] ); - - if ( value != null ) - values[i] = value; - else - return null; - } - - return values; - } - - public static object ParseValue( Type type, string value ) - { - try - { - if ( IsEnum( type ) ) - { - return Enum.Parse( type, value, true ); - } - - if ( IsType( type ) ) - { - return ScriptCompiler.FindTypeByName( value ); - } - if ( IsParsable( type ) ) - { - return ParseParsable( type, value ); - } - object obj = value; - - if ( value != null && value.StartsWith( "0x" ) ) - { - if ( IsSignedNumeric( type ) ) - obj = Convert.ToInt64( value.Substring( 2 ), 16 ); - else if ( IsUnsignedNumeric( type ) ) - obj = Convert.ToUInt64( value.Substring( 2 ), 16 ); - - obj = Convert.ToInt32( value.Substring( 2 ), 16 ); - } - - if ( obj == null && !type.IsValueType ) - return null; - return Convert.ChangeType( obj, type ); - } - catch - { - return null; - } - } - - public static IEntity Build( Mobile from, ConstructorInfo ctor, object[] values, string[,] props, PropertyInfo[] realProps, ref bool sendError ) - { - object built = ctor.Invoke( values ); - - if ( built != null && realProps != null ) - { - bool hadError = false; - - for ( int i = 0; i < realProps.Length; ++i ) - { - if ( realProps[i] == null ) - continue; - - string result = Properties.InternalSetValue( from, built, built, realProps[i], props[i, 1], props[i, 1], false ); - - if ( result != "Property has been set." ) - { - if ( sendError ) - from.SendMessage( result ); - - hadError = true; - } - } - - if ( hadError ) - sendError = false; - } - - return (IEntity)built; - } - - public static int Build( Mobile from, Point3D start, Point3D end, ConstructorInfo ctor, object[] values, string[,] props, PropertyInfo[] realProps, List packs ) - { - return Build( from, start, end, ctor, values, props, realProps, packs, false, false ); - } - - public static int Build( Mobile from, Point3D start, Point3D end, ConstructorInfo ctor, object[] values, string[,] props, PropertyInfo[] realProps, List packs, bool outline, bool mapAvg ) - { - try - { - Map map = from.Map; - - int width = end.X - start.X + 1; - int height = end.Y - start.Y + 1; - - if ( outline && ( width < 3 || height < 3 ) ) - outline = false; - - int objectCount; - - if ( packs != null ) - objectCount = packs.Count; - else if ( outline ) - objectCount = ( width + height - 2 ) * 2; - else - objectCount = width * height; - - if ( objectCount >= 20 ) - from.SendMessage( "Constructing {0} objects, please wait.", objectCount ); - - bool sendError = true; - - StringBuilder sb = new StringBuilder(); - sb.Append( "Serials: " ); - - if ( packs != null ) - { - for ( int i = 0; i < packs.Count; ++i ) - { - IEntity built = Build( from, ctor, values, props, realProps, ref sendError ); - - sb.AppendFormat( "0x{0:X}; ", built.Serial.Value ); - - if ( built is Item item ) { - packs[i].DropItem( item ); - } - else if ( built is Mobile m ) { - m.MoveToWorld( new Point3D( start.X, start.Y, start.Z ), map ); - } - } - } - else - { - int z = start.Z; - - for ( int x = start.X; x <= end.X; ++x ) - { - for ( int y = start.Y; y <= end.Y; ++y ) - { - if ( outline && x != start.X && x != end.X && y != start.Y && y != end.Y ) - continue; - - if ( mapAvg ) - z = map.GetAverageZ( x, y ); - - IEntity built = Build( from, ctor, values, props, realProps, ref sendError ); - - sb.AppendFormat( "0x{0:X}; ", built.Serial.Value ); - - if ( built is Item item ) { - item.MoveToWorld( new Point3D( x, y, z ), map ); - } - else if ( built is Mobile m ) { - m.MoveToWorld( new Point3D( x, y, z ), map ); - } - } - } - } - - CommandLogging.WriteLine( from, sb.ToString() ); - - return objectCount; - } - catch ( Exception ex ) - { - Console.WriteLine(ex); - return 0; - } - } - - public static void SendUsage( Type type, Mobile from ) - { - ConstructorInfo[] ctors = type.GetConstructors(); - bool foundCtor = false; - - for ( int i = 0; i < ctors.Length; ++i ) - { - ConstructorInfo ctor = ctors[i]; - - if ( !IsConstructible( ctor, from.AccessLevel ) ) - continue; - - if ( !foundCtor ) - { - foundCtor = true; - from.SendMessage( "Usage:" ); - } - - SendCtor( type, ctor, from ); - } - - if ( !foundCtor ) - from.SendMessage( "That type is not marked constructible." ); - } - - public static void SendCtor( Type type, ConstructorInfo ctor, Mobile from ) - { - ParameterInfo[] paramList = ctor.GetParameters(); - - StringBuilder sb = new StringBuilder(); - - sb.Append( type.Name ); - - for ( int i = 0; i < paramList.Length; ++i ) - { - if ( i != 0 ) - sb.Append( ',' ); - - sb.Append( ' ' ); - - sb.Append( paramList[i].ParameterType.Name ); - sb.Append( ' ' ); - sb.Append( paramList[i].Name ); - } - - from.SendMessage( sb.ToString() ); - } - - public class AddTarget : Target - { - private string[] m_Args; - - public AddTarget( string[] args ) : base( -1, true, TargetFlags.None ) - { - m_Args = args; - } - - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D p ) - { - if ( p is Item item ) - p = item.GetWorldTop(); - else if ( p is Mobile m ) - p = m.Location; - - Point3D point = new Point3D( p ); - Add.Invoke( from, point, point, m_Args ); - } - } - } - - private enum TileZType - { - Start, - Fixed, - MapAverage - } - - private class TileState - { - public TileZType m_ZType; - public int m_FixedZ; - public string[] m_Args; - public bool m_Outline; - - public TileState( TileZType zType, int fixedZ, string[] args, bool outline ) - { - m_ZType = zType; - m_FixedZ = fixedZ; - m_Args = args; - m_Outline = outline; - } - } - - private static void TileBox_Callback( Mobile from, Map map, Point3D start, Point3D end, object state ) - { - TileState ts = (TileState)state; - bool mapAvg = false; - - switch ( ts.m_ZType ) - { - case TileZType.Fixed: - { - start.Z = end.Z = ts.m_FixedZ; - break; - } - case TileZType.MapAverage: - { - mapAvg = true; - break; - } - } - - Invoke( from, start, end, ts.m_Args, null, ts.m_Outline, mapAvg ); - } - - private static void Internal_OnCommand( CommandEventArgs e, bool outline ) - { - if ( e.Length >= 1 ) - BoundingBoxPicker.Begin( e.Mobile, TileBox_Callback, new TileState( TileZType.Start, 0, e.Arguments, outline ) ); - else - e.Mobile.SendMessage( "Format: {0} [params] [set {{ ...}}]", outline ? "Outline" : "Tile" ); - } - - private static void InternalRXYZ_OnCommand( CommandEventArgs e, bool outline ) - { - if ( e.Length >= 6 ) - { - Point3D p = new Point3D( e.Mobile.X + e.GetInt32( 0 ), e.Mobile.Y + e.GetInt32( 1 ), e.Mobile.Z + e.GetInt32( 4 ) ); - Point3D p2 = new Point3D( p.X + e.GetInt32( 2 ) - 1, p.Y + e.GetInt32( 3 ) - 1, p.Z ); - - string[] subArgs = new string[e.Length - 5]; - - for ( int i = 0; i < subArgs.Length; ++i ) - subArgs[i] = e.Arguments[i + 5]; - - Invoke( e.Mobile, p, p2, subArgs, null, outline, false ); - } - else - { - e.Mobile.SendMessage( "Format: {0}RXYZ [params] [set {{ ...}}]", outline ? "Outline" : "Tile" ); - } - } - - private static void InternalXYZ_OnCommand( CommandEventArgs e, bool outline ) - { - if ( e.Length >= 6 ) - { - Point3D p = new Point3D( e.GetInt32( 0 ), e.GetInt32( 1 ), e.GetInt32( 4 ) ); - Point3D p2 = new Point3D( p.X + e.GetInt32( 2 ) - 1, p.Y + e.GetInt32( 3 ) - 1, e.GetInt32( 4 ) ); - - string[] subArgs = new string[e.Length - 5]; - - for ( int i = 0; i < subArgs.Length; ++i ) - subArgs[i] = e.Arguments[i + 5]; - - Invoke( e.Mobile, p, p2, subArgs, null, outline, false ); - } - else - { - e.Mobile.SendMessage( "Format: {0}XYZ [params] [set {{ ...}}]", outline ? "Outline" : "Tile" ); - } - } - - private static void InternalZ_OnCommand( CommandEventArgs e, bool outline ) - { - if ( e.Length >= 2 ) - { - string[] subArgs = new string[e.Length - 1]; - - for ( int i = 0; i < subArgs.Length; ++i ) - subArgs[i] = e.Arguments[i + 1]; - - BoundingBoxPicker.Begin( e.Mobile, TileBox_Callback, new TileState( TileZType.Fixed, e.GetInt32( 0 ), subArgs, outline ) ); - } - else - { - e.Mobile.SendMessage( "Format: {0}Z [params] [set {{ ...}}]", outline ? "Outline" : "Tile" ); - } - } - - private static void InternalAvg_OnCommand( CommandEventArgs e, bool outline ) - { - if ( e.Length >= 1 ) - BoundingBoxPicker.Begin( e.Mobile, TileBox_Callback, new TileState( TileZType.MapAverage, 0, e.Arguments, outline ) ); - else - e.Mobile.SendMessage( "Format: {0}Avg [params] [set {{ ...}}]", outline ? "Outline" : "Tile" ); - } - - [Usage( "Tile [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name into a targeted bounding box. Optional constructor parameters. Optional set property list." )] - public static void Tile_OnCommand( CommandEventArgs e ) - { - Internal_OnCommand( e, false ); - } - - [Usage( "TileRXYZ [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name into a given bounding box, (x, y) parameters are relative to your characters position. Optional constructor parameters. Optional set property list." )] - public static void TileRXYZ_OnCommand( CommandEventArgs e ) - { - InternalRXYZ_OnCommand( e, false ); - } - - [Usage( "TileXYZ [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name into a given bounding box. Optional constructor parameters. Optional set property list." )] - public static void TileXYZ_OnCommand( CommandEventArgs e ) - { - InternalXYZ_OnCommand( e, false ); - } - - [Usage( "TileZ [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name into a targeted bounding box at a fixed Z location. Optional constructor parameters. Optional set property list." )] - public static void TileZ_OnCommand( CommandEventArgs e ) - { - InternalZ_OnCommand( e, false ); - } - - [Usage( "TileAvg [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name into a targeted bounding box on the map's average Z elevation. Optional constructor parameters. Optional set property list." )] - public static void TileAvg_OnCommand( CommandEventArgs e ) - { - InternalAvg_OnCommand( e, false ); - } - - [Usage( "Outline [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name around a targeted bounding box. Optional constructor parameters. Optional set property list." )] - public static void Outline_OnCommand( CommandEventArgs e ) - { - Internal_OnCommand( e, true ); - } - - [Usage( "OutlineRXYZ [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name around a given bounding box, (x, y) parameters are relative to your characters position. Optional constructor parameters. Optional set property list." )] - public static void OutlineRXYZ_OnCommand( CommandEventArgs e ) - { - InternalRXYZ_OnCommand( e, true ); - } - - [Usage( "OutlineXYZ [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name around a given bounding box. Optional constructor parameters. Optional set property list." )] - public static void OutlineXYZ_OnCommand( CommandEventArgs e ) - { - InternalXYZ_OnCommand( e, true ); - } - - [Usage( "OutlineZ [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name around a targeted bounding box at a fixed Z location. Optional constructor parameters. Optional set property list." )] - public static void OutlineZ_OnCommand( CommandEventArgs e ) - { - InternalZ_OnCommand( e, true ); - } - - [Usage( "OutlineAvg [params] [set { ...}]" )] - [Description( "Tiles an item or npc by name around a targeted bounding box on the map's average Z elevation. Optional constructor parameters. Optional set property list." )] - public static void OutlineAvg_OnCommand( CommandEventArgs e ) - { - InternalAvg_OnCommand( e, true ); - } - - private static Type m_EntityType = typeof( IEntity ); - - public static bool IsEntity( Type t ) - { - return m_EntityType.IsAssignableFrom( t ); - } - - private static Type m_ConstructibleType = typeof( ConstructibleAttribute ); - - public static bool IsConstructible( ConstructorInfo ctor, AccessLevel accessLevel ) - { - object[] attrs = ctor.GetCustomAttributes( m_ConstructibleType, false ); - - if ( attrs.Length == 0 ) - return false; - - return accessLevel >= ((ConstructibleAttribute)attrs[0]).AccessLevel; - } - - private static Type m_EnumType = typeof( Enum ); - - public static bool IsEnum( Type type ) - { - return type.IsSubclassOf( m_EnumType ); - } - - private static Type m_TypeType = typeof( Type ); - - public static bool IsType( Type type ) - { - return ( type == m_TypeType || type.IsSubclassOf( m_TypeType ) ); - } - - private static Type m_ParsableType = typeof( ParsableAttribute ); - - public static bool IsParsable( Type type ) - { - return type.IsDefined( m_ParsableType, false ); - } - - private static Type[] m_ParseTypes = { typeof( string ) }; - private static object[] m_ParseArgs = new object[1]; - - public static object ParseParsable( Type type, string value ) - { - MethodInfo method = type.GetMethod( "Parse", m_ParseTypes ); - - m_ParseArgs[0] = value; - - return method.Invoke( null, m_ParseArgs ); - } - - private static Type[] m_SignedNumerics = { - typeof( long ), - typeof( int ), - typeof( short ), - typeof( sbyte ) - }; - - public static bool IsSignedNumeric( Type type ) - { - for ( int i = 0; i < m_SignedNumerics.Length; ++i ) - if ( type == m_SignedNumerics[i] ) - return true; - - return false; - } - - private static Type[] m_UnsignedNumerics = { - typeof( ulong ), - typeof( uint ), - typeof( ushort ), - typeof( byte ) - }; - - public static bool IsUnsignedNumeric( Type type ) - { - for ( int i = 0; i < m_UnsignedNumerics.Length; ++i ) - if ( type == m_UnsignedNumerics[i] ) - return true; - - return false; - } - } -} + PropertyInfo[] realProps = null; + + if (props != null) + { + realProps = new PropertyInfo[props.GetLength(0)]; + + PropertyInfo[] allProps = + type.GetProperties(BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public); + + for (int i = 0; i < realProps.Length; ++i) + { + PropertyInfo thisProp = null; + + string propName = props[i, 0]; + + for (int j = 0; thisProp == null && j < allProps.Length; ++j) + if (Insensitive.Equals(propName, allProps[j].Name)) + thisProp = allProps[j]; + + if (thisProp == null) + { + from.SendMessage("Property not found: {0}", propName); + } + else + { + CPA attr = Properties.GetCPA(thisProp); + + if (attr == null) + from.SendMessage("Property ({0}) not found.", propName); + else if (from.AccessLevel < attr.WriteLevel) + from.SendMessage("Setting this property ({0}) requires at least {1} access level.", propName, + Mobile.GetAccessLevelName(attr.WriteLevel)); + else if (!thisProp.CanWrite || attr.ReadOnly) + from.SendMessage("Property ({0}) is read only.", propName); + else + realProps[i] = thisProp; + } + } + } + + ConstructorInfo[] ctors = type.GetConstructors(); + + for (int i = 0; i < ctors.Length; ++i) + { + ConstructorInfo ctor = ctors[i]; + + if (!IsConstructible(ctor, from.AccessLevel)) + continue; + + ParameterInfo[] paramList = ctor.GetParameters(); + + if (args.Length == paramList.Length) + { + object[] paramValues = ParseValues(paramList, args); + + if (paramValues == null) + continue; + + int built = Build(from, start, end, ctor, paramValues, props, realProps, packs, outline, mapAvg); + + if (built > 0) + return built; + } + } + + return 0; + } + + public static object[] ParseValues(ParameterInfo[] paramList, string[] args) + { + object[] values = new object[args.Length]; + + for (int i = 0; i < args.Length; ++i) + { + object value = ParseValue(paramList[i].ParameterType, args[i]); + + if (value != null) + values[i] = value; + else + return null; + } + + return values; + } + + public static object ParseValue(Type type, string value) + { + try + { + if (IsEnum(type)) return Enum.Parse(type, value, true); + + if (IsType(type)) return ScriptCompiler.FindTypeByName(value); + if (IsParsable(type)) return ParseParsable(type, value); + object obj = value; + + if (value != null && value.StartsWith("0x")) + { + if (IsSignedNumeric(type)) + obj = Convert.ToInt64(value.Substring(2), 16); + else if (IsUnsignedNumeric(type)) + obj = Convert.ToUInt64(value.Substring(2), 16); + + obj = Convert.ToInt32(value.Substring(2), 16); + } + + if (obj == null && !type.IsValueType) + return null; + return Convert.ChangeType(obj, type); + } + catch + { + return null; + } + } + + public static IEntity Build(Mobile from, ConstructorInfo ctor, object[] values, string[,] props, + PropertyInfo[] realProps, ref bool sendError) + { + object built = ctor.Invoke(values); + + if (built != null && realProps != null) + { + bool hadError = false; + + for (int i = 0; i < realProps.Length; ++i) + { + if (realProps[i] == null) + continue; + + string result = + Properties.InternalSetValue(from, built, built, realProps[i], props[i, 1], props[i, 1], false); + + if (result != "Property has been set.") + { + if (sendError) + from.SendMessage(result); + + hadError = true; + } + } + + if (hadError) + sendError = false; + } + + return (IEntity)built; + } + + public static int Build(Mobile from, Point3D start, Point3D end, ConstructorInfo ctor, object[] values, + string[,] props, PropertyInfo[] realProps, List packs) + { + return Build(from, start, end, ctor, values, props, realProps, packs, false, false); + } + + public static int Build(Mobile from, Point3D start, Point3D end, ConstructorInfo ctor, object[] values, + string[,] props, PropertyInfo[] realProps, List packs, bool outline, bool mapAvg) + { + try + { + Map map = from.Map; + + int width = end.X - start.X + 1; + int height = end.Y - start.Y + 1; + + if (outline && (width < 3 || height < 3)) + outline = false; + + int objectCount; + + if (packs != null) + objectCount = packs.Count; + else if (outline) + objectCount = (width + height - 2) * 2; + else + objectCount = width * height; + + if (objectCount >= 20) + from.SendMessage("Constructing {0} objects, please wait.", objectCount); + + bool sendError = true; + + StringBuilder sb = new StringBuilder(); + sb.Append("Serials: "); + + if (packs != null) + { + for (int i = 0; i < packs.Count; ++i) + { + IEntity built = Build(from, ctor, values, props, realProps, ref sendError); + + sb.AppendFormat("0x{0:X}; ", built.Serial.Value); + + if (built is Item item) + packs[i].DropItem(item); + else if (built is Mobile m) m.MoveToWorld(new Point3D(start.X, start.Y, start.Z), map); + } + } + else + { + int z = start.Z; + + for (int x = start.X; x <= end.X; ++x) + for (int y = start.Y; y <= end.Y; ++y) + { + if (outline && x != start.X && x != end.X && y != start.Y && y != end.Y) + continue; + + if (mapAvg) + z = map.GetAverageZ(x, y); + + IEntity built = Build(from, ctor, values, props, realProps, ref sendError); + + sb.AppendFormat("0x{0:X}; ", built.Serial.Value); + + if (built is Item item) + item.MoveToWorld(new Point3D(x, y, z), map); + else if (built is Mobile m) m.MoveToWorld(new Point3D(x, y, z), map); + } + } + + CommandLogging.WriteLine(from, sb.ToString()); + + return objectCount; + } + catch (Exception ex) + { + Console.WriteLine(ex); + return 0; + } + } + + public static void SendUsage(Type type, Mobile from) + { + ConstructorInfo[] ctors = type.GetConstructors(); + bool foundCtor = false; + + for (int i = 0; i < ctors.Length; ++i) + { + ConstructorInfo ctor = ctors[i]; + + if (!IsConstructible(ctor, from.AccessLevel)) + continue; + + if (!foundCtor) + { + foundCtor = true; + from.SendMessage("Usage:"); + } + + SendCtor(type, ctor, from); + } + + if (!foundCtor) + from.SendMessage("That type is not marked constructible."); + } + + public static void SendCtor(Type type, ConstructorInfo ctor, Mobile from) + { + ParameterInfo[] paramList = ctor.GetParameters(); + + StringBuilder sb = new StringBuilder(); + + sb.Append(type.Name); + + for (int i = 0; i < paramList.Length; ++i) + { + if (i != 0) + sb.Append(','); + + sb.Append(' '); + + sb.Append(paramList[i].ParameterType.Name); + sb.Append(' '); + sb.Append(paramList[i].Name); + } + + from.SendMessage(sb.ToString()); + } + + private static void TileBox_Callback(Mobile from, Map map, Point3D start, Point3D end, object state) + { + TileState ts = (TileState)state; + bool mapAvg = false; + + switch (ts.m_ZType) + { + case TileZType.Fixed: + { + start.Z = end.Z = ts.m_FixedZ; + break; + } + case TileZType.MapAverage: + { + mapAvg = true; + break; + } + } + + Invoke(from, start, end, ts.m_Args, null, ts.m_Outline, mapAvg); + } + + private static void Internal_OnCommand(CommandEventArgs e, bool outline) + { + if (e.Length >= 1) + BoundingBoxPicker.Begin(e.Mobile, TileBox_Callback, new TileState(TileZType.Start, 0, e.Arguments, outline)); + else + e.Mobile.SendMessage("Format: {0} [params] [set {{ ...}}]", + outline ? "Outline" : "Tile"); + } + + private static void InternalRXYZ_OnCommand(CommandEventArgs e, bool outline) + { + if (e.Length >= 6) + { + Point3D p = new Point3D(e.Mobile.X + e.GetInt32(0), e.Mobile.Y + e.GetInt32(1), e.Mobile.Z + e.GetInt32(4)); + Point3D p2 = new Point3D(p.X + e.GetInt32(2) - 1, p.Y + e.GetInt32(3) - 1, p.Z); + + string[] subArgs = new string[e.Length - 5]; + + for (int i = 0; i < subArgs.Length; ++i) + subArgs[i] = e.Arguments[i + 5]; + + Invoke(e.Mobile, p, p2, subArgs, null, outline, false); + } + else + { + e.Mobile.SendMessage( + "Format: {0}RXYZ [params] [set {{ ...}}]", + outline ? "Outline" : "Tile"); + } + } + + private static void InternalXYZ_OnCommand(CommandEventArgs e, bool outline) + { + if (e.Length >= 6) + { + Point3D p = new Point3D(e.GetInt32(0), e.GetInt32(1), e.GetInt32(4)); + Point3D p2 = new Point3D(p.X + e.GetInt32(2) - 1, p.Y + e.GetInt32(3) - 1, e.GetInt32(4)); + + string[] subArgs = new string[e.Length - 5]; + + for (int i = 0; i < subArgs.Length; ++i) + subArgs[i] = e.Arguments[i + 5]; + + Invoke(e.Mobile, p, p2, subArgs, null, outline, false); + } + else + { + e.Mobile.SendMessage( + "Format: {0}XYZ [params] [set {{ ...}}]", + outline ? "Outline" : "Tile"); + } + } + + private static void InternalZ_OnCommand(CommandEventArgs e, bool outline) + { + if (e.Length >= 2) + { + string[] subArgs = new string[e.Length - 1]; + + for (int i = 0; i < subArgs.Length; ++i) + subArgs[i] = e.Arguments[i + 1]; + + BoundingBoxPicker.Begin(e.Mobile, TileBox_Callback, + new TileState(TileZType.Fixed, e.GetInt32(0), subArgs, outline)); + } + else + { + e.Mobile.SendMessage("Format: {0}Z [params] [set {{ ...}}]", + outline ? "Outline" : "Tile"); + } + } + + private static void InternalAvg_OnCommand(CommandEventArgs e, bool outline) + { + if (e.Length >= 1) + BoundingBoxPicker.Begin(e.Mobile, TileBox_Callback, + new TileState(TileZType.MapAverage, 0, e.Arguments, outline)); + else + e.Mobile.SendMessage("Format: {0}Avg [params] [set {{ ...}}]", + outline ? "Outline" : "Tile"); + } + + [Usage("Tile [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name into a targeted bounding box. Optional constructor parameters. Optional set property list.")] + public static void Tile_OnCommand(CommandEventArgs e) + { + Internal_OnCommand(e, false); + } + + [Usage("TileRXYZ [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name into a given bounding box, (x, y) parameters are relative to your characters position. Optional constructor parameters. Optional set property list.")] + public static void TileRXYZ_OnCommand(CommandEventArgs e) + { + InternalRXYZ_OnCommand(e, false); + } + + [Usage("TileXYZ [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name into a given bounding box. Optional constructor parameters. Optional set property list.")] + public static void TileXYZ_OnCommand(CommandEventArgs e) + { + InternalXYZ_OnCommand(e, false); + } + + [Usage("TileZ [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name into a targeted bounding box at a fixed Z location. Optional constructor parameters. Optional set property list.")] + public static void TileZ_OnCommand(CommandEventArgs e) + { + InternalZ_OnCommand(e, false); + } + + [Usage("TileAvg [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name into a targeted bounding box on the map's average Z elevation. Optional constructor parameters. Optional set property list.")] + public static void TileAvg_OnCommand(CommandEventArgs e) + { + InternalAvg_OnCommand(e, false); + } + + [Usage("Outline [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name around a targeted bounding box. Optional constructor parameters. Optional set property list.")] + public static void Outline_OnCommand(CommandEventArgs e) + { + Internal_OnCommand(e, true); + } + + [Usage("OutlineRXYZ [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name around a given bounding box, (x, y) parameters are relative to your characters position. Optional constructor parameters. Optional set property list.")] + public static void OutlineRXYZ_OnCommand(CommandEventArgs e) + { + InternalRXYZ_OnCommand(e, true); + } + + [Usage("OutlineXYZ [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name around a given bounding box. Optional constructor parameters. Optional set property list.")] + public static void OutlineXYZ_OnCommand(CommandEventArgs e) + { + InternalXYZ_OnCommand(e, true); + } + + [Usage("OutlineZ [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name around a targeted bounding box at a fixed Z location. Optional constructor parameters. Optional set property list.")] + public static void OutlineZ_OnCommand(CommandEventArgs e) + { + InternalZ_OnCommand(e, true); + } + + [Usage("OutlineAvg [params] [set { ...}]")] + [Description( + "Tiles an item or npc by name around a targeted bounding box on the map's average Z elevation. Optional constructor parameters. Optional set property list.")] + public static void OutlineAvg_OnCommand(CommandEventArgs e) + { + InternalAvg_OnCommand(e, true); + } + + public static bool IsEntity(Type t) + { + return m_EntityType.IsAssignableFrom(t); + } + + public static bool IsConstructible(ConstructorInfo ctor, AccessLevel accessLevel) + { + object[] attrs = ctor.GetCustomAttributes(m_ConstructibleType, false); + + if (attrs.Length == 0) + return false; + + return accessLevel >= ((ConstructibleAttribute)attrs[0]).AccessLevel; + } + + public static bool IsEnum(Type type) + { + return type.IsSubclassOf(m_EnumType); + } + + public static bool IsType(Type type) + { + return type == m_TypeType || type.IsSubclassOf(m_TypeType); + } + + public static bool IsParsable(Type type) + { + return type.IsDefined(m_ParsableType, false); + } + + public static object ParseParsable(Type type, string value) + { + MethodInfo method = type.GetMethod("Parse", m_ParseTypes); + + m_ParseArgs[0] = value; + + return method.Invoke(null, m_ParseArgs); + } + + public static bool IsSignedNumeric(Type type) + { + for (int i = 0; i < m_SignedNumerics.Length; ++i) + if (type == m_SignedNumerics[i]) + return true; + + return false; + } + + public static bool IsUnsignedNumeric(Type type) + { + for (int i = 0; i < m_UnsignedNumerics.Length; ++i) + if (type == m_UnsignedNumerics[i]) + return true; + + return false; + } + + public class AddTarget : Target + { + private string[] m_Args; + + public AddTarget(string[] args) : base(-1, true, TargetFlags.None) + { + m_Args = args; + } + + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D p) + { + if (p is Item item) + p = item.GetWorldTop(); + else if (p is Mobile m) + p = m.Location; + + Point3D point = new Point3D(p); + Add.Invoke(from, point, point, m_Args); + } + } + } + + private enum TileZType + { + Start, + Fixed, + MapAverage + } + + private class TileState + { + public string[] m_Args; + public int m_FixedZ; + public bool m_Outline; + public TileZType m_ZType; + + public TileState(TileZType zType, int fixedZ, string[] args, bool outline) + { + m_ZType = zType; + m_FixedZ = fixedZ; + m_Args = args; + m_Outline = outline; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Attributes.cs b/Scripts/Commands/Attributes.cs index cdaa4d0d0..b51fd21f5 100644 --- a/Scripts/Commands/Attributes.cs +++ b/Scripts/Commands/Attributes.cs @@ -2,33 +2,33 @@ using System; namespace Server { - public class UsageAttribute : Attribute - { - public string Usage { get; } + public class UsageAttribute : Attribute + { + public UsageAttribute(string usage) + { + Usage = usage; + } - public UsageAttribute( string usage ) - { - Usage = usage; - } - } + public string Usage{ get; } + } - public class DescriptionAttribute : Attribute - { - public string Description { get; } + public class DescriptionAttribute : Attribute + { + public DescriptionAttribute(string description) + { + Description = description; + } - public DescriptionAttribute( string description ) - { - Description = description; - } - } + public string Description{ get; } + } - public class AliasesAttribute : Attribute - { - public string[] Aliases { get; } + public class AliasesAttribute : Attribute + { + public AliasesAttribute(params string[] aliases) + { + Aliases = aliases; + } - public AliasesAttribute( params string[] aliases ) - { - Aliases = aliases; - } - } + public string[] Aliases{ get; } + } } \ No newline at end of file diff --git a/Scripts/Commands/Batch.cs b/Scripts/Commands/Batch.cs index 5b937d566..3a24772ad 100644 --- a/Scripts/Commands/Batch.cs +++ b/Scripts/Commands/Batch.cs @@ -1,423 +1,423 @@ using System; -using System.Reflection; using System.Collections; +using System.Reflection; +using Server.Commands.Generic; using Server.Gumps; using Server.Network; -using Server.Commands.Generic; namespace Server.Commands { - public class Batch : BaseCommand - { - public BaseCommandImplementor Scope { get; set; } + public class Batch : BaseCommand + { + public Batch() + { + Commands = new[] { "Batch" }; + ListOptimized = true; - public string Condition { get; set; } + BatchCommands = new ArrayList(); + Condition = ""; + } - public ArrayList BatchCommands { get; } + public BaseCommandImplementor Scope{ get; set; } - public Batch() - { - Commands = new[]{ "Batch" }; - ListOptimized = true; + public string Condition{ get; set; } - BatchCommands = new ArrayList(); - Condition = ""; - } + public ArrayList BatchCommands{ get; } - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - if ( list.Count == 0 ) - { - LogFailure( "Nothing was found to use this command on." ); - return; - } + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + if (list.Count == 0) + { + LogFailure("Nothing was found to use this command on."); + return; + } - try - { - BaseCommand[] commands = new BaseCommand[BatchCommands.Count]; - CommandEventArgs[] eventArgs = new CommandEventArgs[BatchCommands.Count]; + try + { + BaseCommand[] commands = new BaseCommand[BatchCommands.Count]; + CommandEventArgs[] eventArgs = new CommandEventArgs[BatchCommands.Count]; - for ( int i = 0; i < BatchCommands.Count; ++i ) - { - BatchCommand bc = (BatchCommand)BatchCommands[i]; - - bc.GetDetails( out string commandString, out string argString, out string[] args ); - - BaseCommand command = Scope.Commands[commandString]; - - commands[i] = command; - eventArgs[i] = new CommandEventArgs( e.Mobile, commandString, argString, args ); - - if ( command == null ) - { - e.Mobile.SendMessage( "That is either an invalid command name or one that does not support this modifier: {0}.", commandString ); - return; - } - - if ( e.Mobile.AccessLevel < command.AccessLevel ) - { - e.Mobile.SendMessage( "You do not have access to that command: {0}.", commandString ); - return; - } - if ( !command.ValidateArgs( Scope, eventArgs[i] ) ) - { - return; - } - } - - for ( int i = 0; i < commands.Length; ++i ) - { - BaseCommand command = commands[i]; - BatchCommand bc = (BatchCommand)BatchCommands[i]; - - if ( list.Count > 20 ) - CommandLogging.Enabled = false; - - ArrayList usedList; - - if ( Utility.InsensitiveCompare( bc.Object, "Current" ) == 0 ) - { - usedList = list; - } - else - { - Hashtable propertyChains = new Hashtable(); - - usedList = new ArrayList( list.Count ); - - for ( int j = 0; j < list.Count; ++j ) - { - object obj = list[j]; - - if ( obj == null ) - continue; - - Type type = obj.GetType(); - - PropertyInfo[] chain = (PropertyInfo[])propertyChains[type]; - - string failReason = ""; - - if ( chain == null && !propertyChains.Contains( type ) ) - propertyChains[type] = chain = Properties.GetPropertyInfoChain( e.Mobile, type, bc.Object, PropertyAccess.Read, ref failReason ); - - if ( chain == null ) - continue; - - PropertyInfo endProp = Properties.GetPropertyInfo( ref obj, chain, ref failReason ); - - if ( endProp == null ) - continue; - - try - { - obj = endProp.GetValue( obj, null ); - - if ( obj != null ) - usedList.Add( obj ); - } - catch - { - } - } - } - - command.ExecuteList( eventArgs[i], usedList ); - - if ( list.Count > 20 ) - CommandLogging.Enabled = true; - - command.Flush( e.Mobile, list.Count > 20 ); - } - } - catch ( Exception ex ) - { - e.Mobile.SendMessage( ex.Message ); - } - } - - public bool Run( Mobile from ) - { - if ( Scope == null ) - { - from.SendMessage( "You must select the batch command scope." ); - return false; - } - - if ( Condition.Length > 0 && !Scope.SupportsConditionals ) - { - from.SendMessage( "This command scope does not support conditionals." ); - return false; - } - if ( Condition.Length > 0 && !Utility.InsensitiveStartsWith( Condition, "where" ) ) - { - from.SendMessage( "The condition field must start with \"where\"." ); - return false; - } - - string[] args = CommandSystem.Split( Condition ); - - Scope.Process( from, this, args ); - - return true; - } - - public static void Initialize() - { - CommandSystem.Register( "Batch", AccessLevel.Counselor, Batch_OnCommand ); - } - - [Usage( "Batch" )] - [Description( "Allows multiple commands to be run at the same time." )] - public static void Batch_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendGump( new BatchGump( e.Mobile, new Batch() ) ); - } - } - - public class BatchCommand - { - public string Command { get; set; } - - public string Object { get; set; } - - public void GetDetails( out string command, out string argString, out string[] args ) - { - int indexOf = Command.IndexOf( ' ' ); - - if ( indexOf >= 0 ) - { - argString = Command.Substring( indexOf + 1 ); - - command = Command.Substring( 0, indexOf ); - args = CommandSystem.Split( argString ); - } - else - { - argString = ""; - command = Command.ToLower(); - args = new string[0]; - } - } - - public BatchCommand( string command, string obj ) - { - Command = command; - Object = obj; - } - } - - public class BatchGump : BaseGridGump - { - private Mobile m_From; - private Batch m_Batch; - - public BatchGump( Mobile from, Batch batch ) : base( 30, 30 ) - { - m_From = from; - m_Batch = batch; - - Render(); - } - - public void Render() - { - AddNewPage(); - - /* Header */ - AddEntryHeader( 20 ); - AddEntryHtml( 180, Center( "Batch Commands" ) ); - AddEntryHeader( 20 ); - AddNewLine(); - - AddEntryHeader( 9 ); - AddEntryLabel( 191, "Run Batch" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, GetButtonID( 1, 0, 0 ), ArrowRightWidth, ArrowRightHeight ); - AddNewLine(); - - AddBlankLine(); - - /* Scope */ - AddEntryHeader( 20 ); - AddEntryHtml( 180, Center( "Scope" ) ); - AddEntryHeader( 20 ); - AddNewLine(); - - AddEntryHeader( 9 ); - AddEntryLabel( 191, m_Batch.Scope == null ? "Select Scope" : m_Batch.Scope.Accessors[0] ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, GetButtonID( 1, 0, 1 ), ArrowRightWidth, ArrowRightHeight ); - AddNewLine(); - - AddBlankLine(); - - /* Condition */ - AddEntryHeader( 20 ); - AddEntryHtml( 180, Center( "Condition" ) ); - AddEntryHeader( 20 ); - AddNewLine(); - - AddEntryHeader( 9 ); - AddEntryText( 202, 0, m_Batch.Condition ); - AddEntryHeader( 9 ); - AddNewLine(); - - AddBlankLine(); - - /* Commands */ - AddEntryHeader( 20 ); - AddEntryHtml( 180, Center( "Commands" ) ); - AddEntryHeader( 20 ); - - for ( int i = 0; i < m_Batch.BatchCommands.Count; ++i ) - { - BatchCommand bc = (BatchCommand)m_Batch.BatchCommands[i]; - - AddNewLine(); - - AddImageTiled( CurrentX, CurrentY, 9, 2, 0x24A8 ); - AddImageTiled( CurrentX, CurrentY + 2, 2, EntryHeight + OffsetSize + EntryHeight - 4, 0x24A8 ); - AddImageTiled( CurrentX, CurrentY + EntryHeight + OffsetSize + EntryHeight - 2, 9, 2, 0x24A8 ); - AddImageTiled( CurrentX + 3, CurrentY + 3, 6, EntryHeight + EntryHeight - 4 - OffsetSize, HeaderGumpID ); - - IncreaseX( 9 ); - AddEntryText( 202, 1+(i*2), bc.Command ); - AddEntryHeader( 9, 2 ); - - AddNewLine(); - - IncreaseX( 9 ); - AddEntryText( 202, 2+(i*2), bc.Object ); - } - - AddNewLine(); - - AddEntryHeader( 9 ); - AddEntryLabel( 191, "Add New Command" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, GetButtonID( 1, 0, 2 ), ArrowRightWidth, ArrowRightHeight ); - - FinishPage(); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !SplitButtonID( info.ButtonID, 1, out int type, out int index ) ) - return; - - TextRelay entry = info.GetTextEntry( 0 ); - - if ( entry != null ) - m_Batch.Condition = entry.Text; - - for ( int i = m_Batch.BatchCommands.Count - 1; i >= 0; --i ) - { - BatchCommand sc = (BatchCommand)m_Batch.BatchCommands[i]; - - entry = info.GetTextEntry( 1 + (i * 2) ); - - if ( entry != null ) - sc.Command = entry.Text; - - entry = info.GetTextEntry( 2 + (i * 2) ); - - if ( entry != null ) - sc.Object = entry.Text; - - if ( sc.Command.Length == 0 && sc.Object.Length == 0 ) - m_Batch.BatchCommands.RemoveAt( i ); - } - - switch ( type ) - { - case 0: // main - { - switch ( index ) - { - case 0: // run - { - m_Batch.Run( m_From ); - break; - } - case 1: // set scope - { - m_From.SendGump( new BatchScopeGump( m_From, m_Batch ) ); - return; - } - case 2: // add command - { - m_Batch.BatchCommands.Add( new BatchCommand( "", "" ) ); - break; - } - } - - break; - } - } - - m_From.SendGump( new BatchGump( m_From, m_Batch ) ); - } - } - - public class BatchScopeGump : BaseGridGump - { - private Mobile m_From; - private Batch m_Batch; - - public BatchScopeGump( Mobile from, Batch batch ) : base( 30, 30 ) - { - m_From = from; - m_Batch = batch; - - Render(); - } - - public void Render() - { - AddNewPage(); - - /* Header */ - AddEntryHeader( 20 ); - AddEntryHtml( 140, Center( "Change Scope" ) ); - AddEntryHeader( 20 ); - - /* Options */ - for ( int i = 0; i < BaseCommandImplementor.Implementors.Count; ++i ) - { - BaseCommandImplementor impl = BaseCommandImplementor.Implementors[i]; - - if ( m_From.AccessLevel < impl.AccessLevel ) - continue; - - AddNewLine(); - - AddEntryLabel( 20 + OffsetSize + 140, impl.Accessors[0] ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, GetButtonID( 1, 0, i ), ArrowRightWidth, ArrowRightHeight ); - } - - FinishPage(); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( SplitButtonID( info.ButtonID, 1, out int type, out int index ) ) - { - switch ( type ) - { - case 0: - { - if ( index < BaseCommandImplementor.Implementors.Count ) - { - BaseCommandImplementor impl = BaseCommandImplementor.Implementors[index]; - - if ( m_From.AccessLevel >= impl.AccessLevel ) - m_Batch.Scope = impl; - } - - break; - } - } - } - - m_From.SendGump( new BatchGump( m_From, m_Batch ) ); - } - } -} + for (int i = 0; i < BatchCommands.Count; ++i) + { + BatchCommand bc = (BatchCommand)BatchCommands[i]; + + bc.GetDetails(out string commandString, out string argString, out string[] args); + + BaseCommand command = Scope.Commands[commandString]; + + commands[i] = command; + eventArgs[i] = new CommandEventArgs(e.Mobile, commandString, argString, args); + + if (command == null) + { + e.Mobile.SendMessage( + "That is either an invalid command name or one that does not support this modifier: {0}.", + commandString); + return; + } + + if (e.Mobile.AccessLevel < command.AccessLevel) + { + e.Mobile.SendMessage("You do not have access to that command: {0}.", commandString); + return; + } + + if (!command.ValidateArgs(Scope, eventArgs[i])) return; + } + + for (int i = 0; i < commands.Length; ++i) + { + BaseCommand command = commands[i]; + BatchCommand bc = (BatchCommand)BatchCommands[i]; + + if (list.Count > 20) + CommandLogging.Enabled = false; + + ArrayList usedList; + + if (Utility.InsensitiveCompare(bc.Object, "Current") == 0) + { + usedList = list; + } + else + { + Hashtable propertyChains = new Hashtable(); + + usedList = new ArrayList(list.Count); + + for (int j = 0; j < list.Count; ++j) + { + object obj = list[j]; + + if (obj == null) + continue; + + Type type = obj.GetType(); + + PropertyInfo[] chain = (PropertyInfo[])propertyChains[type]; + + string failReason = ""; + + if (chain == null && !propertyChains.Contains(type)) + propertyChains[type] = chain = Properties.GetPropertyInfoChain(e.Mobile, type, bc.Object, + PropertyAccess.Read, ref failReason); + + if (chain == null) + continue; + + PropertyInfo endProp = Properties.GetPropertyInfo(ref obj, chain, ref failReason); + + if (endProp == null) + continue; + + try + { + obj = endProp.GetValue(obj, null); + + if (obj != null) + usedList.Add(obj); + } + catch + { + } + } + } + + command.ExecuteList(eventArgs[i], usedList); + + if (list.Count > 20) + CommandLogging.Enabled = true; + + command.Flush(e.Mobile, list.Count > 20); + } + } + catch (Exception ex) + { + e.Mobile.SendMessage(ex.Message); + } + } + + public bool Run(Mobile from) + { + if (Scope == null) + { + from.SendMessage("You must select the batch command scope."); + return false; + } + + if (Condition.Length > 0 && !Scope.SupportsConditionals) + { + from.SendMessage("This command scope does not support conditionals."); + return false; + } + + if (Condition.Length > 0 && !Utility.InsensitiveStartsWith(Condition, "where")) + { + from.SendMessage("The condition field must start with \"where\"."); + return false; + } + + string[] args = CommandSystem.Split(Condition); + + Scope.Process(from, this, args); + + return true; + } + + public static void Initialize() + { + CommandSystem.Register("Batch", AccessLevel.Counselor, Batch_OnCommand); + } + + [Usage("Batch")] + [Description("Allows multiple commands to be run at the same time.")] + public static void Batch_OnCommand(CommandEventArgs e) + { + e.Mobile.SendGump(new BatchGump(e.Mobile, new Batch())); + } + } + + public class BatchCommand + { + public BatchCommand(string command, string obj) + { + Command = command; + Object = obj; + } + + public string Command{ get; set; } + + public string Object{ get; set; } + + public void GetDetails(out string command, out string argString, out string[] args) + { + int indexOf = Command.IndexOf(' '); + + if (indexOf >= 0) + { + argString = Command.Substring(indexOf + 1); + + command = Command.Substring(0, indexOf); + args = CommandSystem.Split(argString); + } + else + { + argString = ""; + command = Command.ToLower(); + args = new string[0]; + } + } + } + + public class BatchGump : BaseGridGump + { + private Batch m_Batch; + private Mobile m_From; + + public BatchGump(Mobile from, Batch batch) : base(30, 30) + { + m_From = from; + m_Batch = batch; + + Render(); + } + + public void Render() + { + AddNewPage(); + + /* Header */ + AddEntryHeader(20); + AddEntryHtml(180, Center("Batch Commands")); + AddEntryHeader(20); + AddNewLine(); + + AddEntryHeader(9); + AddEntryLabel(191, "Run Batch"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, GetButtonID(1, 0, 0), ArrowRightWidth, ArrowRightHeight); + AddNewLine(); + + AddBlankLine(); + + /* Scope */ + AddEntryHeader(20); + AddEntryHtml(180, Center("Scope")); + AddEntryHeader(20); + AddNewLine(); + + AddEntryHeader(9); + AddEntryLabel(191, m_Batch.Scope == null ? "Select Scope" : m_Batch.Scope.Accessors[0]); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, GetButtonID(1, 0, 1), ArrowRightWidth, ArrowRightHeight); + AddNewLine(); + + AddBlankLine(); + + /* Condition */ + AddEntryHeader(20); + AddEntryHtml(180, Center("Condition")); + AddEntryHeader(20); + AddNewLine(); + + AddEntryHeader(9); + AddEntryText(202, 0, m_Batch.Condition); + AddEntryHeader(9); + AddNewLine(); + + AddBlankLine(); + + /* Commands */ + AddEntryHeader(20); + AddEntryHtml(180, Center("Commands")); + AddEntryHeader(20); + + for (int i = 0; i < m_Batch.BatchCommands.Count; ++i) + { + BatchCommand bc = (BatchCommand)m_Batch.BatchCommands[i]; + + AddNewLine(); + + AddImageTiled(CurrentX, CurrentY, 9, 2, 0x24A8); + AddImageTiled(CurrentX, CurrentY + 2, 2, EntryHeight + OffsetSize + EntryHeight - 4, 0x24A8); + AddImageTiled(CurrentX, CurrentY + EntryHeight + OffsetSize + EntryHeight - 2, 9, 2, 0x24A8); + AddImageTiled(CurrentX + 3, CurrentY + 3, 6, EntryHeight + EntryHeight - 4 - OffsetSize, HeaderGumpID); + + IncreaseX(9); + AddEntryText(202, 1 + i * 2, bc.Command); + AddEntryHeader(9, 2); + + AddNewLine(); + + IncreaseX(9); + AddEntryText(202, 2 + i * 2, bc.Object); + } + + AddNewLine(); + + AddEntryHeader(9); + AddEntryLabel(191, "Add New Command"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, GetButtonID(1, 0, 2), ArrowRightWidth, ArrowRightHeight); + + FinishPage(); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!SplitButtonID(info.ButtonID, 1, out int type, out int index)) + return; + + TextRelay entry = info.GetTextEntry(0); + + if (entry != null) + m_Batch.Condition = entry.Text; + + for (int i = m_Batch.BatchCommands.Count - 1; i >= 0; --i) + { + BatchCommand sc = (BatchCommand)m_Batch.BatchCommands[i]; + + entry = info.GetTextEntry(1 + i * 2); + + if (entry != null) + sc.Command = entry.Text; + + entry = info.GetTextEntry(2 + i * 2); + + if (entry != null) + sc.Object = entry.Text; + + if (sc.Command.Length == 0 && sc.Object.Length == 0) + m_Batch.BatchCommands.RemoveAt(i); + } + + switch (type) + { + case 0: // main + { + switch (index) + { + case 0: // run + { + m_Batch.Run(m_From); + break; + } + case 1: // set scope + { + m_From.SendGump(new BatchScopeGump(m_From, m_Batch)); + return; + } + case 2: // add command + { + m_Batch.BatchCommands.Add(new BatchCommand("", "")); + break; + } + } + + break; + } + } + + m_From.SendGump(new BatchGump(m_From, m_Batch)); + } + } + + public class BatchScopeGump : BaseGridGump + { + private Batch m_Batch; + private Mobile m_From; + + public BatchScopeGump(Mobile from, Batch batch) : base(30, 30) + { + m_From = from; + m_Batch = batch; + + Render(); + } + + public void Render() + { + AddNewPage(); + + /* Header */ + AddEntryHeader(20); + AddEntryHtml(140, Center("Change Scope")); + AddEntryHeader(20); + + /* Options */ + for (int i = 0; i < BaseCommandImplementor.Implementors.Count; ++i) + { + BaseCommandImplementor impl = BaseCommandImplementor.Implementors[i]; + + if (m_From.AccessLevel < impl.AccessLevel) + continue; + + AddNewLine(); + + AddEntryLabel(20 + OffsetSize + 140, impl.Accessors[0]); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, GetButtonID(1, 0, i), ArrowRightWidth, ArrowRightHeight); + } + + FinishPage(); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (SplitButtonID(info.ButtonID, 1, out int type, out int index)) + switch (type) + { + case 0: + { + if (index < BaseCommandImplementor.Implementors.Count) + { + BaseCommandImplementor impl = BaseCommandImplementor.Implementors[index]; + + if (m_From.AccessLevel >= impl.AccessLevel) + m_Batch.Scope = impl; + } + + break; + } + } + + m_From.SendGump(new BatchGump(m_From, m_Batch)); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/BoundingBoxPicker.cs b/Scripts/Commands/BoundingBoxPicker.cs index 26a949864..83db542d8 100644 --- a/Scripts/Commands/BoundingBoxPicker.cs +++ b/Scripts/Commands/BoundingBoxPicker.cs @@ -2,64 +2,65 @@ using Server.Targeting; namespace Server { - public delegate void BoundingBoxCallback( Mobile from, Map map, Point3D start, Point3D end, object state ); + public delegate void BoundingBoxCallback(Mobile from, Map map, Point3D start, Point3D end, object state); - public class BoundingBoxPicker - { - public static void Begin( Mobile from, BoundingBoxCallback callback, object state ) - { - from.SendMessage( "Target the first location of the bounding box." ); - from.Target = new PickTarget( callback, state ); - } + public class BoundingBoxPicker + { + public static void Begin(Mobile from, BoundingBoxCallback callback, object state) + { + from.SendMessage("Target the first location of the bounding box."); + from.Target = new PickTarget(callback, state); + } - private class PickTarget : Target - { - private Point3D m_Store; - private bool m_First; - private Map m_Map; - private BoundingBoxCallback m_Callback; - private object m_State; + private class PickTarget : Target + { + private BoundingBoxCallback m_Callback; + private bool m_First; + private Map m_Map; + private object m_State; + private Point3D m_Store; - public PickTarget( BoundingBoxCallback callback, object state ) : this( Point3D.Zero, true, null, callback, state ) - { - } + public PickTarget(BoundingBoxCallback callback, object state) : this(Point3D.Zero, true, null, callback, state) + { + } - public PickTarget( Point3D store, bool first, Map map, BoundingBoxCallback callback, object state ) : base( -1, true, TargetFlags.None ) - { - m_Store = store; - m_First = first; - m_Map = map; - m_Callback = callback; - m_State = state; - } + public PickTarget(Point3D store, bool first, Map map, BoundingBoxCallback callback, object state) : base(-1, + true, TargetFlags.None) + { + m_Store = store; + m_First = first; + m_Map = map; + m_Callback = callback; + m_State = state; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !(targeted is IPoint3D p) ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (!(targeted is IPoint3D p)) + return; - if ( p is Item item ) - p = item.GetWorldTop(); + if (p is Item item) + p = item.GetWorldTop(); - if ( m_First ) - { - from.SendMessage( "Target another location to complete the bounding box." ); - from.Target = new PickTarget( new Point3D( p ), false, from.Map, m_Callback, m_State ); - } - else if ( from.Map != m_Map ) - { - from.SendMessage( "Both locations must reside on the same map." ); - } - else if ( m_Map != null && m_Map != Map.Internal && m_Callback != null ) - { - Point3D start = m_Store; - Point3D end = new Point3D( p ); + if (m_First) + { + from.SendMessage("Target another location to complete the bounding box."); + from.Target = new PickTarget(new Point3D(p), false, from.Map, m_Callback, m_State); + } + else if (from.Map != m_Map) + { + from.SendMessage("Both locations must reside on the same map."); + } + else if (m_Map != null && m_Map != Map.Internal && m_Callback != null) + { + Point3D start = m_Store; + Point3D end = new Point3D(p); - Utility.FixPoints( ref start, ref end ); + Utility.FixPoints(ref start, ref end); - m_Callback( from, m_Map, start, end, m_State ); - } - } - } - } -} + m_Callback(from, m_Map, start, end, m_State); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/ConvertPlayers.cs b/Scripts/Commands/ConvertPlayers.cs index 88b382291..faddf9fb3 100644 --- a/Scripts/Commands/ConvertPlayers.cs +++ b/Scripts/Commands/ConvertPlayers.cs @@ -6,84 +6,82 @@ using Server.Network; namespace Server.Commands { - public class ConvertPlayers - { - public static void Initialize() - { - CommandSystem.Register( "ConvertPlayers", AccessLevel.Administrator, Convert_OnCommand ); - } - - public static void Convert_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( "Converting all players to PlayerMobile. You will be disconnected. Please Restart the server after the world has finished saving." ); - List mobs = new List( World.Mobiles.Values ); - int count = 0; - - foreach ( Mobile m in mobs ) - { - if ( m.Player && !(m is PlayerMobile ) ) - { - count++; - m.NetState?.Dispose(); + public class ConvertPlayers + { + public static void Initialize() + { + CommandSystem.Register("ConvertPlayers", AccessLevel.Administrator, Convert_OnCommand); + } - PlayerMobile pm = new PlayerMobile( m.Serial ); - pm.DefaultMobileInit(); - - List copy = new List( m.Items ); - for (int i=0;i 0 ) - { - NetState.ProcessDisposedQueue(); - World.Save(); - - Console.WriteLine( "{0} players have been converted to PlayerMobile. {1}.", count, Core.Service ? "The server is now restarting" : "Press any key to restart the server" ); - - if ( !Core.Service ) - Console.ReadKey( true ); + public static void Convert_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage( + "Converting all players to PlayerMobile. You will be disconnected. Please Restart the server after the world has finished saving."); + List mobs = new List(World.Mobiles.Values); + int count = 0; - Core.Kill( true ); - } - else - { - e.Mobile.SendMessage( "Couldn't find any Players to convert." ); - } - } - - private static void CopyProps( Mobile to, Mobile from ) - { - Type type = typeof( Mobile ); - - PropertyInfo[] props = type.GetProperties( BindingFlags.Public | BindingFlags.Instance ); - - for (int p=0;p copy = new List(m.Items); + for (int i = 0; i < copy.Count; i++) + pm.AddItem(copy[i]); + + CopyProps(pm, m); + + for (int i = 0; i < m.Skills.Length; i++) + { + pm.Skills[i].Base = m.Skills[i].Base; + pm.Skills[i].SetLockNoRelay(m.Skills[i].Lock); + } + + World.Mobiles[m.Serial] = pm; + } + + if (count > 0) + { + NetState.ProcessDisposedQueue(); + World.Save(); + + Console.WriteLine("{0} players have been converted to PlayerMobile. {1}.", count, + Core.Service ? "The server is now restarting" : "Press any key to restart the server"); + + if (!Core.Service) + Console.ReadKey(true); + + Core.Kill(true); + } + else + { + e.Mobile.SendMessage("Couldn't find any Players to convert."); + } + } + + private static void CopyProps(Mobile to, Mobile from) + { + Type type = typeof(Mobile); + + PropertyInfo[] props = type.GetProperties(BindingFlags.Public | BindingFlags.Instance); + + for (int p = 0; p < props.Length; p++) + { + PropertyInfo prop = props[p]; + + if (prop.CanRead && prop.CanWrite) + try + { + prop.SetValue(to, prop.GetValue(from, null), null); + } + catch + { + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Decorate.cs b/Scripts/Commands/Decorate.cs index eb2ecc242..fe7b937d5 100644 --- a/Scripts/Commands/Decorate.cs +++ b/Scripts/Commands/Decorate.cs @@ -1,1140 +1,1098 @@ using System; -using System.IO; using System.Collections; using System.Collections.Generic; -using Server.Items; +using System.IO; using Server.Engines.Quests.Haven; using Server.Engines.Quests.Necro; +using Server.Items; using Server.Mobiles; namespace Server.Commands { - public class Decorate - { - public static void Initialize() - { - CommandSystem.Register( "Decorate", AccessLevel.Administrator, Decorate_OnCommand ); - } - - [Usage( "Decorate" )] - [Description( "Generates world decoration." )] - private static void Decorate_OnCommand( CommandEventArgs e ) - { - m_Mobile = e.Mobile; - m_Count = 0; - - m_Mobile.SendMessage( "Generating world decoration, please wait." ); - - Generate( "Data/Decoration/Britannia", Map.Trammel, Map.Felucca ); - Generate( "Data/Decoration/Trammel", Map.Trammel ); - Generate( "Data/Decoration/Felucca", Map.Felucca ); - Generate( "Data/Decoration/Ilshenar", Map.Ilshenar ); - Generate( "Data/Decoration/Malas", Map.Malas ); - Generate( "Data/Decoration/Tokuno", Map.Tokuno ); - - m_Mobile.SendMessage( "World generating complete. {0} items were generated.", m_Count ); - } - - public static void Generate( string folder, params Map[] maps ) - { - if ( !Directory.Exists( folder ) ) - return; - - string[] files = Directory.GetFiles( folder, "*.cfg" ); - - for ( int i = 0; i < files.Length; ++i ) - { - ArrayList list = DecorationList.ReadAll( files[i] ); - - for ( int j = 0; j < list.Count; ++j ) - m_Count += ((DecorationList)list[j]).Generate( maps ); - } - } - - private static Mobile m_Mobile; - private static int m_Count; - } - - public class DecorationList - { - private Type m_Type; - private int m_ItemID; - private string[] m_Params; - private ArrayList m_Entries; - - public DecorationList() - { - } - - private static Type typeofStatic = typeof( Static ); - private static Type typeofLocalizedStatic = typeof( LocalizedStatic ); - private static Type typeofBaseDoor = typeof( BaseDoor ); - private static Type typeofAnkhWest = typeof( AnkhWest ); - private static Type typeofAnkhNorth = typeof( AnkhNorth ); - private static Type typeofBeverage = typeof( BaseBeverage ); - private static Type typeofLocalizedSign = typeof( LocalizedSign ); - private static Type typeofMarkContainer = typeof( MarkContainer ); - private static Type typeofWarningItem = typeof( WarningItem ); - private static Type typeofHintItem = typeof( HintItem ); - private static Type typeofCannon = typeof( Cannon ); - private static Type typeofSerpentPillar = typeof( SerpentPillar ); - - public Item Construct() - { - if ( m_Type == null ) - return null; - - Item item; - - try - { - if ( m_Type == typeofStatic ) - { - item = new Static( m_ItemID ); - } - else if ( m_Type == typeofLocalizedStatic ) - { - int labelNumber = 0; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "LabelNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - labelNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - break; - } - } - } - - item = new LocalizedStatic( m_ItemID, labelNumber ); - } - else if ( m_Type == typeofLocalizedSign ) - { - int labelNumber = 0; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "LabelNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - labelNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - break; - } - } - } - - item = new LocalizedSign( m_ItemID, labelNumber ); - } - else if ( m_Type == typeofAnkhWest || m_Type == typeofAnkhNorth ) - { - bool bloodied = false; - - for ( int i = 0; !bloodied && i < m_Params.Length; ++i ) - bloodied = ( m_Params[i] == "Bloodied" ); - - if ( m_Type == typeofAnkhWest ) - item = new AnkhWest( bloodied ); - else - item = new AnkhNorth( bloodied ); - } - else if ( m_Type == typeofMarkContainer ) - { - bool bone = false; - bool locked = false; - Map map = Map.Malas; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i] == "Bone" ) - { - bone = true; - } - else if ( m_Params[i] == "Locked" ) - { - locked = true; - } - else if ( m_Params[i].StartsWith( "TargetMap" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - map = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - MarkContainer mc = new MarkContainer( bone, locked ); - - mc.TargetMap = map; - mc.Description = "strange location"; - - item = mc; - } - else if ( m_Type == typeofHintItem ) - { - int range = 0; - int messageNumber = 0; - string messageString = null; - int hintNumber = 0; - string hintString = null; - TimeSpan resetDelay = TimeSpan.Zero; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Range" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - range = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "WarningString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "WarningNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "HintString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - hintString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "HintNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - hintNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "ResetDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - resetDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - HintItem hi = new HintItem( m_ItemID, range, messageNumber, hintNumber ); - - hi.WarningString = messageString; - hi.HintString = hintString; - hi.ResetDelay = resetDelay; - - item = hi; - } - else if ( m_Type == typeofWarningItem ) - { - int range = 0; - int messageNumber = 0; - string messageString = null; - TimeSpan resetDelay = TimeSpan.Zero; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Range" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - range = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "WarningString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "WarningNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "ResetDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - resetDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - WarningItem wi = new WarningItem( m_ItemID, range, messageNumber ); - - wi.WarningString = messageString; - wi.ResetDelay = resetDelay; - - item = wi; - } - else if ( m_Type == typeofCannon ) - { - CannonDirection direction = CannonDirection.North; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "CannonDirection" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - direction = (CannonDirection)Enum.Parse( typeof( CannonDirection ), m_Params[i].Substring( ++indexOf ), true ); - } - } - - item = new Cannon( direction ); - } - else if ( m_Type == typeofSerpentPillar ) - { - string word = null; - Rectangle2D destination = new Rectangle2D(); - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Word" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - word = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "DestStart" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - destination.Start = Point2D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEnd" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - destination.End = Point2D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - item = new SerpentPillar( word, destination ); - } - else if ( m_Type.IsSubclassOf( typeofBeverage ) ) - { - BeverageType content = BeverageType.Liquor; - bool fill = false; - - for ( int i = 0; !fill && i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Content" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - content = (BeverageType)Enum.Parse( typeof( BeverageType ), m_Params[i].Substring( ++indexOf ), true ); - fill = true; - } - } - } - - if ( fill ) - item = (Item)Activator.CreateInstance( m_Type, new object[]{ content } ); - else - item = (Item)Activator.CreateInstance( m_Type ); - } - else if ( m_Type.IsSubclassOf( typeofBaseDoor ) ) - { - DoorFacing facing = DoorFacing.WestCW; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Facing" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - facing = (DoorFacing)Enum.Parse( typeof( DoorFacing ), m_Params[i].Substring( ++indexOf ), true ); - break; - } - } - } - - item = (Item)Activator.CreateInstance( m_Type, new object[]{ facing } ); - } - else - { - item = (Item)Activator.CreateInstance( m_Type ); - } - } - catch ( Exception e ) - { - throw new Exception($"Bad type: {m_Type}", e ); - } - - if ( item is BaseAddon addon ) - { - if ( addon is MaabusCoffin coffin ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "SpawnLocation" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - coffin.SpawnLocation = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - } - else if ( m_ItemID > 0 ) - { - List comps = addon.Components; - - for ( int i = 0; i < comps.Count; ++i ) - { - AddonComponent comp = comps[i]; - - if ( comp.Offset == Point3D.Zero ) - comp.ItemID = m_ItemID; - } - } - } - else if ( item is BaseLight light ) - { - bool unlit = false, unprotected = false; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( !unlit && m_Params[i] == "Unlit" ) - unlit = true; - else if ( !unprotected && m_Params[i] == "Unprotected" ) - unprotected = true; - - if ( unlit && unprotected ) - break; - } - - if ( !unlit ) - light.Ignite(); - if ( !unprotected ) - light.Protected = true; - - if ( m_ItemID > 0 ) - light.ItemID = m_ItemID; - } - else if ( item is Spawner sp ) - { - sp.NextSpawn = TimeSpan.Zero; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Spawn" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.AddEntry( m_Params[i].Substring( ++indexOf ), 100, 1 ); - } - else if ( m_Params[i].StartsWith( "MinDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.MinDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MaxDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.MaxDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "NextSpawn" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.NextSpawn = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Count" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - sp.Count = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - for ( int se = 0;se < sp.Entries.Count; se++ ) - sp.Entries[se].SpawnedMaxCount = sp.Count; - } - } - else if ( m_Params[i].StartsWith( "Team" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.Team = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "HomeRange" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.HomeRange = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Running" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.Running = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Group" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.Group = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - } - } - else if ( item is RecallRune rune ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Description" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.Description = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "Marked" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.Marked = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "TargetMap" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.TargetMap = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Target" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.Target = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - } - else if ( item is SkillTeleporter st ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Skill" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Skill = (SkillName)Enum.Parse( typeof( SkillName ), m_Params[i].Substring( ++indexOf ), true ); - } - else if ( m_Params[i].StartsWith( "RequiredFixedPoint" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Required = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ) * 0.1; - } - else if ( m_Params[i].StartsWith( "Required" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Required = Utility.ToDouble( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MessageString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.MessageString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "MessageNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.MessageNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "PointDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.PointDest = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MapDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.MapDest = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Creatures" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Creatures = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SourceEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.SourceEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.DestEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SoundID" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.SoundID = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Delay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Delay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - if ( m_ItemID > 0 ) - st.ItemID = m_ItemID; - } - else if ( item is KeywordTeleporter kt ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Substring" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Substring = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "Keyword" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Keyword = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Range" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Range = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "PointDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.PointDest = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MapDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.MapDest = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Creatures" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Creatures = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SourceEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.SourceEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.DestEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SoundID" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.SoundID = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Delay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Delay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - if ( m_ItemID > 0 ) - kt.ItemID = m_ItemID; - } - else if ( item is Teleporter tp ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "PointDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.PointDest = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MapDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.MapDest = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Creatures" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.Creatures = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SourceEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.SourceEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.DestEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SoundID" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.SoundID = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Delay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.Delay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - if ( m_ItemID > 0 ) - tp.ItemID = m_ItemID; - } - else if ( item is FillableContainer cont ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "ContentType" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - cont.ContentType = (FillableContentType)Enum.Parse( typeof( FillableContentType ), m_Params[i].Substring( ++indexOf ), true ); - } - } - - if ( m_ItemID > 0 ) - cont.ItemID = m_ItemID; - } - else if ( m_ItemID > 0 ) - { - item.ItemID = m_ItemID; - } - - item.Movable = false; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Light" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - item.Light = (LightType)Enum.Parse( typeof( LightType ), m_Params[i].Substring( ++indexOf ), true ); - } - else if ( m_Params[i].StartsWith( "Hue" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - int hue = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - - if ( item is DyeTub tub ) - tub.DyedHue = hue; - else - item.Hue = hue; - } - } - else if ( m_Params[i].StartsWith( "Name" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - item.Name = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "Amount" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - // Must supress stackable warnings - - bool wasStackable = item.Stackable; - - item.Stackable = true; - item.Amount = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - item.Stackable = wasStackable; - } - } - } - - return item; - } - - private static Queue m_DeleteQueue = new Queue(); - - private static bool FindItem( int x, int y, int z, Map map, Item srcItem ) - { - int itemID = srcItem.ItemID; - - bool res = false; - - IPooledEnumerable eable; - - if ( srcItem is BaseDoor ) - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 1 ); - - foreach ( Item item in eable ) - { - if ( !(item is BaseDoor) ) - continue; - - BaseDoor bd = (BaseDoor)item; - Point3D p; - int bdItemID; - - if ( bd.Open ) - { - p = new Point3D( bd.X - bd.Offset.X, bd.Y - bd.Offset.Y, bd.Z - bd.Offset.Z ); - bdItemID = bd.ClosedID; - } - else - { - p = bd.Location; - bdItemID = bd.ItemID; - } - - if ( p.X != x || p.Y != y ) - continue; - - if ( item.Z == z && bdItemID == itemID ) - res = true; - else if ( Math.Abs( item.Z - z ) < 8 ) - m_DeleteQueue.Enqueue( item ); - } - } - else if ( (TileData.ItemTable[itemID & TileData.MaxItemValue].Flags & TileFlag.LightSource) != 0 ) - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - - LightType lt = srcItem.Light; - string srcName = srcItem.ItemData.Name; - - foreach ( Item item in eable ) - { - if ( item.Z == z ) - { - if ( item.ItemID == itemID ) - { - if ( item.Light != lt ) - m_DeleteQueue.Enqueue( item ); - else - res = true; - } - else if ( (item.ItemData.Flags & TileFlag.LightSource) != 0 && item.ItemData.Name == srcName ) - { - m_DeleteQueue.Enqueue( item ); - } - } - } - } - else if ( srcItem is Teleporter || srcItem is FillableContainer || srcItem is BaseBook ) - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - - Type type = srcItem.GetType(); - - foreach ( Item item in eable ) - { - if ( item.Z == z && item.ItemID == itemID ) - { - if ( item.GetType() != type ) - m_DeleteQueue.Enqueue( item ); - else - res = true; - } - } - } - else - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - - foreach ( Item item in eable ) - { - if ( item.Z == z && item.ItemID == itemID ) - { - eable.Free(); - return true; - } - } - } - - eable.Free(); - - while ( m_DeleteQueue.Count > 0 ) - ((Item)m_DeleteQueue.Dequeue()).Delete(); - - return res; - } - - public int Generate( Map[] maps ) - { - int count = 0; - - Item item = null; - - for ( int i = 0; i < m_Entries.Count; ++i ) - { - DecorationEntry entry = (DecorationEntry)m_Entries[i]; - Point3D loc = entry.Location; - string extra = entry.Extra; - - for ( int j = 0; j < maps.Length; ++j ) - { - if ( item == null ) - item = Construct(); - - if ( item == null ) - continue; - - if ( FindItem( loc.X, loc.Y, loc.Z, maps[j], item ) ) - { - } - else - { - item.MoveToWorld( loc, maps[j] ); - ++count; - - if ( item is BaseDoor door ) - { - IPooledEnumerable eable = maps[j].GetItemsInRange( loc, 1 ); - - Type itemType = door.GetType(); - - foreach ( BaseDoor link in eable ) - { - if ( link != item && link.Z == door.Z && link.GetType() == itemType ) - { - door.Link = link; - link.Link = door; - break; - } - } - - eable.Free(); - } - else if ( item is MarkContainer markCont ) - { - try - { - markCont.Target = Point3D.Parse( extra ); - } - catch{} - } - - item = null; - } - } - } - - item?.Delete(); - - return count; - } - - public static ArrayList ReadAll( string path ) - { - using ( StreamReader ip = new StreamReader( path ) ) - { - ArrayList list = new ArrayList(); - - for ( DecorationList v = Read( ip ); v != null; v = Read( ip ) ) - list.Add( v ); - - return list; - } - } - - private static string[] m_EmptyParams = new string[0]; - - public static DecorationList Read( StreamReader ip ) - { - string line; - - while ( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); - - if ( line.Length > 0 && !line.StartsWith( "#" ) ) - break; - } - - if ( string.IsNullOrEmpty( line ) ) - return null; - - DecorationList list = new DecorationList(); - - int indexOf = line.IndexOf( ' ' ); - - list.m_Type = ScriptCompiler.FindTypeByName( line.Substring( 0, indexOf++ ), true ); - - if ( list.m_Type == null ) - throw new ArgumentException($"Type not found for header: '{line}'"); - - line = line.Substring( indexOf ); - indexOf = line.IndexOf( '(' ); - if ( indexOf >= 0 ) - { - list.m_ItemID = Utility.ToInt32( line.Substring( 0, indexOf - 1 ) ); - - string parms = line.Substring( ++indexOf ); - - if ( line.EndsWith( ")" ) ) - parms = parms.Substring( 0, parms.Length - 1 ); - - list.m_Params = parms.Split( ';' ); - - for ( int i = 0; i < list.m_Params.Length; ++i ) - list.m_Params[i] = list.m_Params[i].Trim(); - } - else - { - list.m_ItemID = Utility.ToInt32( line ); - list.m_Params = m_EmptyParams; - } - - list.m_Entries = new ArrayList(); - - while ( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); - - if ( line.Length == 0 ) - break; - - if ( line.StartsWith( "#" ) ) - continue; - - list.m_Entries.Add( new DecorationEntry( line ) ); - } - - return list; - } - } - - public class DecorationEntry - { - public Point3D Location { get; } + public class Decorate + { + private static Mobile m_Mobile; + private static int m_Count; + + public static void Initialize() + { + CommandSystem.Register("Decorate", AccessLevel.Administrator, Decorate_OnCommand); + } + + [Usage("Decorate")] + [Description("Generates world decoration.")] + private static void Decorate_OnCommand(CommandEventArgs e) + { + m_Mobile = e.Mobile; + m_Count = 0; + + m_Mobile.SendMessage("Generating world decoration, please wait."); + + Generate("Data/Decoration/Britannia", Map.Trammel, Map.Felucca); + Generate("Data/Decoration/Trammel", Map.Trammel); + Generate("Data/Decoration/Felucca", Map.Felucca); + Generate("Data/Decoration/Ilshenar", Map.Ilshenar); + Generate("Data/Decoration/Malas", Map.Malas); + Generate("Data/Decoration/Tokuno", Map.Tokuno); + + m_Mobile.SendMessage("World generating complete. {0} items were generated.", m_Count); + } + + public static void Generate(string folder, params Map[] maps) + { + if (!Directory.Exists(folder)) + return; + + string[] files = Directory.GetFiles(folder, "*.cfg"); + + for (int i = 0; i < files.Length; ++i) + { + ArrayList list = DecorationList.ReadAll(files[i]); + + for (int j = 0; j < list.Count; ++j) + m_Count += ((DecorationList)list[j]).Generate(maps); + } + } + } + + public class DecorationList + { + private static Type typeofStatic = typeof(Static); + private static Type typeofLocalizedStatic = typeof(LocalizedStatic); + private static Type typeofBaseDoor = typeof(BaseDoor); + private static Type typeofAnkhWest = typeof(AnkhWest); + private static Type typeofAnkhNorth = typeof(AnkhNorth); + private static Type typeofBeverage = typeof(BaseBeverage); + private static Type typeofLocalizedSign = typeof(LocalizedSign); + private static Type typeofMarkContainer = typeof(MarkContainer); + private static Type typeofWarningItem = typeof(WarningItem); + private static Type typeofHintItem = typeof(HintItem); + private static Type typeofCannon = typeof(Cannon); + private static Type typeofSerpentPillar = typeof(SerpentPillar); + + private static Queue m_DeleteQueue = new Queue(); + + private static string[] m_EmptyParams = new string[0]; + private ArrayList m_Entries; + private int m_ItemID; + private string[] m_Params; + private Type m_Type; + + public Item Construct() + { + if (m_Type == null) + return null; + + Item item; + + try + { + if (m_Type == typeofStatic) + { + item = new Static(m_ItemID); + } + else if (m_Type == typeofLocalizedStatic) + { + int labelNumber = 0; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("LabelNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + labelNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + break; + } + } + + item = new LocalizedStatic(m_ItemID, labelNumber); + } + else if (m_Type == typeofLocalizedSign) + { + int labelNumber = 0; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("LabelNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + labelNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + break; + } + } + + item = new LocalizedSign(m_ItemID, labelNumber); + } + else if (m_Type == typeofAnkhWest || m_Type == typeofAnkhNorth) + { + bool bloodied = false; + + for (int i = 0; !bloodied && i < m_Params.Length; ++i) + bloodied = m_Params[i] == "Bloodied"; + + if (m_Type == typeofAnkhWest) + item = new AnkhWest(bloodied); + else + item = new AnkhNorth(bloodied); + } + else if (m_Type == typeofMarkContainer) + { + bool bone = false; + bool locked = false; + Map map = Map.Malas; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i] == "Bone") + { + bone = true; + } + else if (m_Params[i] == "Locked") + { + locked = true; + } + else if (m_Params[i].StartsWith("TargetMap")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + map = Map.Parse(m_Params[i].Substring(++indexOf)); + } + + MarkContainer mc = new MarkContainer(bone, locked); + + mc.TargetMap = map; + mc.Description = "strange location"; + + item = mc; + } + else if (m_Type == typeofHintItem) + { + int range = 0; + int messageNumber = 0; + string messageString = null; + int hintNumber = 0; + string hintString = null; + TimeSpan resetDelay = TimeSpan.Zero; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Range")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + range = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("WarningString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("WarningNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("HintString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + hintString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("HintNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + hintNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("ResetDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + resetDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + HintItem hi = new HintItem(m_ItemID, range, messageNumber, hintNumber); + + hi.WarningString = messageString; + hi.HintString = hintString; + hi.ResetDelay = resetDelay; + + item = hi; + } + else if (m_Type == typeofWarningItem) + { + int range = 0; + int messageNumber = 0; + string messageString = null; + TimeSpan resetDelay = TimeSpan.Zero; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Range")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + range = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("WarningString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("WarningNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("ResetDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + resetDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + WarningItem wi = new WarningItem(m_ItemID, range, messageNumber); + + wi.WarningString = messageString; + wi.ResetDelay = resetDelay; + + item = wi; + } + else if (m_Type == typeofCannon) + { + CannonDirection direction = CannonDirection.North; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("CannonDirection")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + direction = (CannonDirection)Enum.Parse(typeof(CannonDirection), + m_Params[i].Substring(++indexOf), true); + } + + item = new Cannon(direction); + } + else if (m_Type == typeofSerpentPillar) + { + string word = null; + Rectangle2D destination = new Rectangle2D(); + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Word")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + word = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("DestStart")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + destination.Start = Point2D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEnd")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + destination.End = Point2D.Parse(m_Params[i].Substring(++indexOf)); + } + + item = new SerpentPillar(word, destination); + } + else if (m_Type.IsSubclassOf(typeofBeverage)) + { + BeverageType content = BeverageType.Liquor; + bool fill = false; + + for (int i = 0; !fill && i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Content")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + content = (BeverageType)Enum.Parse(typeof(BeverageType), m_Params[i].Substring(++indexOf), + true); + fill = true; + } + } + + if (fill) + item = (Item)Activator.CreateInstance(m_Type, content); + else + item = (Item)Activator.CreateInstance(m_Type); + } + else if (m_Type.IsSubclassOf(typeofBaseDoor)) + { + DoorFacing facing = DoorFacing.WestCW; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Facing")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + facing = (DoorFacing)Enum.Parse(typeof(DoorFacing), m_Params[i].Substring(++indexOf), true); + break; + } + } + + item = (Item)Activator.CreateInstance(m_Type, facing); + } + else + { + item = (Item)Activator.CreateInstance(m_Type); + } + } + catch (Exception e) + { + throw new Exception($"Bad type: {m_Type}", e); + } + + if (item is BaseAddon addon) + { + if (addon is MaabusCoffin coffin) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("SpawnLocation")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + coffin.SpawnLocation = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + } + else if (m_ItemID > 0) + { + List comps = addon.Components; + + for (int i = 0; i < comps.Count; ++i) + { + AddonComponent comp = comps[i]; + + if (comp.Offset == Point3D.Zero) + comp.ItemID = m_ItemID; + } + } + } + else if (item is BaseLight light) + { + bool unlit = false, unprotected = false; + + for (int i = 0; i < m_Params.Length; ++i) + { + if (!unlit && m_Params[i] == "Unlit") + unlit = true; + else if (!unprotected && m_Params[i] == "Unprotected") + unprotected = true; + + if (unlit && unprotected) + break; + } + + if (!unlit) + light.Ignite(); + if (!unprotected) + light.Protected = true; + + if (m_ItemID > 0) + light.ItemID = m_ItemID; + } + else if (item is Spawner sp) + { + sp.NextSpawn = TimeSpan.Zero; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Spawn")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.AddEntry(m_Params[i].Substring(++indexOf), 100, 1); + } + else if (m_Params[i].StartsWith("MinDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.MinDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MaxDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.MaxDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("NextSpawn")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.NextSpawn = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Count")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + sp.Count = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + for (int se = 0; se < sp.Entries.Count; se++) + sp.Entries[se].SpawnedMaxCount = sp.Count; + } + } + else if (m_Params[i].StartsWith("Team")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.Team = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("HomeRange")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.HomeRange = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Running")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.Running = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Group")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.Group = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + } + else if (item is RecallRune rune) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Description")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.Description = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("Marked")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.Marked = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("TargetMap")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.TargetMap = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Target")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.Target = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + } + else if (item is SkillTeleporter st) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Skill")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Skill = (SkillName)Enum.Parse(typeof(SkillName), m_Params[i].Substring(++indexOf), true); + } + else if (m_Params[i].StartsWith("RequiredFixedPoint")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Required = Utility.ToInt32(m_Params[i].Substring(++indexOf)) * 0.1; + } + else if (m_Params[i].StartsWith("Required")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Required = Utility.ToDouble(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MessageString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.MessageString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("MessageNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.MessageNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("PointDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.PointDest = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MapDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.MapDest = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Creatures")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Creatures = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SourceEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.SourceEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.DestEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SoundID")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.SoundID = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Delay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Delay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + if (m_ItemID > 0) + st.ItemID = m_ItemID; + } + else if (item is KeywordTeleporter kt) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Substring")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Substring = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("Keyword")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Keyword = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Range")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Range = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("PointDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.PointDest = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MapDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.MapDest = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Creatures")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Creatures = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SourceEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.SourceEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.DestEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SoundID")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.SoundID = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Delay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Delay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + if (m_ItemID > 0) + kt.ItemID = m_ItemID; + } + else if (item is Teleporter tp) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("PointDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.PointDest = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MapDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.MapDest = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Creatures")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.Creatures = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SourceEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.SourceEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.DestEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SoundID")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.SoundID = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Delay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.Delay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + if (m_ItemID > 0) + tp.ItemID = m_ItemID; + } + else if (item is FillableContainer cont) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("ContentType")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + cont.ContentType = (FillableContentType)Enum.Parse(typeof(FillableContentType), + m_Params[i].Substring(++indexOf), true); + } + + if (m_ItemID > 0) + cont.ItemID = m_ItemID; + } + else if (m_ItemID > 0) + { + item.ItemID = m_ItemID; + } + + item.Movable = false; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Light")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + item.Light = (LightType)Enum.Parse(typeof(LightType), m_Params[i].Substring(++indexOf), true); + } + else if (m_Params[i].StartsWith("Hue")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + int hue = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + + if (item is DyeTub tub) + tub.DyedHue = hue; + else + item.Hue = hue; + } + } + else if (m_Params[i].StartsWith("Name")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + item.Name = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("Amount")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + // Must supress stackable warnings + + bool wasStackable = item.Stackable; + + item.Stackable = true; + item.Amount = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + item.Stackable = wasStackable; + } + } + + return item; + } + + private static bool FindItem(int x, int y, int z, Map map, Item srcItem) + { + int itemID = srcItem.ItemID; + + bool res = false; + + IPooledEnumerable eable; + + if (srcItem is BaseDoor) + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 1); + + foreach (Item item in eable) + { + if (!(item is BaseDoor)) + continue; + + BaseDoor bd = (BaseDoor)item; + Point3D p; + int bdItemID; + + if (bd.Open) + { + p = new Point3D(bd.X - bd.Offset.X, bd.Y - bd.Offset.Y, bd.Z - bd.Offset.Z); + bdItemID = bd.ClosedID; + } + else + { + p = bd.Location; + bdItemID = bd.ItemID; + } + + if (p.X != x || p.Y != y) + continue; + + if (item.Z == z && bdItemID == itemID) + res = true; + else if (Math.Abs(item.Z - z) < 8) + m_DeleteQueue.Enqueue(item); + } + } + else if ((TileData.ItemTable[itemID & TileData.MaxItemValue].Flags & TileFlag.LightSource) != 0) + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + + LightType lt = srcItem.Light; + string srcName = srcItem.ItemData.Name; + + foreach (Item item in eable) + if (item.Z == z) + { + if (item.ItemID == itemID) + { + if (item.Light != lt) + m_DeleteQueue.Enqueue(item); + else + res = true; + } + else if ((item.ItemData.Flags & TileFlag.LightSource) != 0 && item.ItemData.Name == srcName) + { + m_DeleteQueue.Enqueue(item); + } + } + } + else if (srcItem is Teleporter || srcItem is FillableContainer || srcItem is BaseBook) + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + + Type type = srcItem.GetType(); + + foreach (Item item in eable) + if (item.Z == z && item.ItemID == itemID) + { + if (item.GetType() != type) + m_DeleteQueue.Enqueue(item); + else + res = true; + } + } + else + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + + foreach (Item item in eable) + if (item.Z == z && item.ItemID == itemID) + { + eable.Free(); + return true; + } + } + + eable.Free(); + + while (m_DeleteQueue.Count > 0) + ((Item)m_DeleteQueue.Dequeue()).Delete(); + + return res; + } + + public int Generate(Map[] maps) + { + int count = 0; + + Item item = null; + + for (int i = 0; i < m_Entries.Count; ++i) + { + DecorationEntry entry = (DecorationEntry)m_Entries[i]; + Point3D loc = entry.Location; + string extra = entry.Extra; + + for (int j = 0; j < maps.Length; ++j) + { + if (item == null) + item = Construct(); + + if (item == null) + continue; + + if (FindItem(loc.X, loc.Y, loc.Z, maps[j], item)) + { + } + else + { + item.MoveToWorld(loc, maps[j]); + ++count; + + if (item is BaseDoor door) + { + IPooledEnumerable eable = maps[j].GetItemsInRange(loc, 1); + + Type itemType = door.GetType(); + + foreach (BaseDoor link in eable) + if (link != item && link.Z == door.Z && link.GetType() == itemType) + { + door.Link = link; + link.Link = door; + break; + } + + eable.Free(); + } + else if (item is MarkContainer markCont) + { + try + { + markCont.Target = Point3D.Parse(extra); + } + catch + { + } + } + + item = null; + } + } + } + + item?.Delete(); + + return count; + } + + public static ArrayList ReadAll(string path) + { + using (StreamReader ip = new StreamReader(path)) + { + ArrayList list = new ArrayList(); + + for (DecorationList v = Read(ip); v != null; v = Read(ip)) + list.Add(v); + + return list; + } + } + + public static DecorationList Read(StreamReader ip) + { + string line; + + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); + + if (line.Length > 0 && !line.StartsWith("#")) + break; + } + + if (string.IsNullOrEmpty(line)) + return null; + + DecorationList list = new DecorationList(); + + int indexOf = line.IndexOf(' '); + + list.m_Type = ScriptCompiler.FindTypeByName(line.Substring(0, indexOf++), true); + + if (list.m_Type == null) + throw new ArgumentException($"Type not found for header: '{line}'"); + + line = line.Substring(indexOf); + indexOf = line.IndexOf('('); + if (indexOf >= 0) + { + list.m_ItemID = Utility.ToInt32(line.Substring(0, indexOf - 1)); + + string parms = line.Substring(++indexOf); + + if (line.EndsWith(")")) + parms = parms.Substring(0, parms.Length - 1); + + list.m_Params = parms.Split(';'); + + for (int i = 0; i < list.m_Params.Length; ++i) + list.m_Params[i] = list.m_Params[i].Trim(); + } + else + { + list.m_ItemID = Utility.ToInt32(line); + list.m_Params = m_EmptyParams; + } + + list.m_Entries = new ArrayList(); + + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); + + if (line.Length == 0) + break; + + if (line.StartsWith("#")) + continue; + + list.m_Entries.Add(new DecorationEntry(line)); + } + + return list; + } + } + + public class DecorationEntry + { + public DecorationEntry(string line) + { + string x, y, z; - public string Extra { get; } + Pop(out x, ref line); + Pop(out y, ref line); + Pop(out z, ref line); - public DecorationEntry( string line ) - { - string x, y, z; + Location = new Point3D(Utility.ToInt32(x), Utility.ToInt32(y), Utility.ToInt32(z)); + Extra = line; + } - Pop( out x, ref line ); - Pop( out y, ref line ); - Pop( out z, ref line ); + public Point3D Location{ get; } - Location = new Point3D( Utility.ToInt32( x ), Utility.ToInt32( y ), Utility.ToInt32( z ) ); - Extra = line; - } + public string Extra{ get; } - public void Pop( out string v, ref string line ) - { - int space = line.IndexOf( ' ' ); + public void Pop(out string v, ref string line) + { + int space = line.IndexOf(' '); - if ( space >= 0 ) - { - v = line.Substring( 0, space++ ); - line = line.Substring( space ); - } - else - { - v = line; - line = ""; - } - } - } -} + if (space >= 0) + { + v = line.Substring(0, space++); + line = line.Substring(space); + } + else + { + v = line; + line = ""; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/DecorateMag.cs b/Scripts/Commands/DecorateMag.cs index 8a972021b..1695cafe4 100644 --- a/Scripts/Commands/DecorateMag.cs +++ b/Scripts/Commands/DecorateMag.cs @@ -1,1137 +1,1095 @@ using System; -using System.IO; using System.Collections; using System.Collections.Generic; -using Server.Items; +using System.IO; using Server.Engines.Quests.Haven; using Server.Engines.Quests.Necro; +using Server.Items; using Server.Mobiles; namespace Server.Commands { - public class DecorateMag - { - public static void Initialize() - { - CommandSystem.Register( "DecorateMag", AccessLevel.Administrator, DecorateMag_OnCommand ); - } - - [Usage( "DecorateMag" )] - [Description( "Generates world decoration." )] - private static void DecorateMag_OnCommand( CommandEventArgs e ) - { - m_Mobile = e.Mobile; - m_Count = 0; - - m_Mobile.SendMessage( "Generating world decoration, please wait." ); - - Generate( "Data/Decoration/RuinedMaginciaTram", Map.Trammel ); - Generate( "Data/Decoration/RuinedMaginciaFel", Map.Felucca ); - - - m_Mobile.SendMessage( "World generating complete. {0} items were generated.", m_Count ); - } - - public static void Generate( string folder, params Map[] maps ) - { - if ( !Directory.Exists( folder ) ) - return; - - string[] files = Directory.GetFiles( folder, "*.cfg" ); - - for ( int i = 0; i < files.Length; ++i ) - { - ArrayList list = DecorationListMag.ReadAll( files[i] ); - - for ( int j = 0; j < list.Count; ++j ) - m_Count += ((DecorationListMag)list[j]).Generate( maps ); - } - } - - private static Mobile m_Mobile; - private static int m_Count; - } - - public class DecorationListMag - { - private Type m_Type; - private int m_ItemID; - private string[] m_Params; - private ArrayList m_Entries; - - public DecorationListMag() - { - } - - private static Type typeofStatic = typeof( Static ); - private static Type typeofLocalizedStatic = typeof( LocalizedStatic ); - private static Type typeofBaseDoor = typeof( BaseDoor ); - private static Type typeofAnkhWest = typeof( AnkhWest ); - private static Type typeofAnkhNorth = typeof( AnkhNorth ); - private static Type typeofBeverage = typeof( BaseBeverage ); - private static Type typeofLocalizedSign = typeof( LocalizedSign ); - private static Type typeofMarkContainer = typeof( MarkContainer ); - private static Type typeofWarningItem = typeof( WarningItem ); - private static Type typeofHintItem = typeof( HintItem ); - private static Type typeofCannon = typeof( Cannon ); - private static Type typeofSerpentPillar = typeof( SerpentPillar ); - - public Item Construct() - { - if ( m_Type == null ) - return null; - - Item item; - - try - { - if ( m_Type == typeofStatic ) - { - item = new Static( m_ItemID ); - } - else if ( m_Type == typeofLocalizedStatic ) - { - int labelNumber = 0; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "LabelNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - labelNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - break; - } - } - } - - item = new LocalizedStatic( m_ItemID, labelNumber ); - } - else if ( m_Type == typeofLocalizedSign ) - { - int labelNumber = 0; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "LabelNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - labelNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - break; - } - } - } - - item = new LocalizedSign( m_ItemID, labelNumber ); - } - else if ( m_Type == typeofAnkhWest || m_Type == typeofAnkhNorth ) - { - bool bloodied = false; - - for ( int i = 0; !bloodied && i < m_Params.Length; ++i ) - bloodied = ( m_Params[i] == "Bloodied" ); - - if ( m_Type == typeofAnkhWest ) - item = new AnkhWest( bloodied ); - else - item = new AnkhNorth( bloodied ); - } - else if ( m_Type == typeofMarkContainer ) - { - bool bone = false; - bool locked = false; - Map map = Map.Malas; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i] == "Bone" ) - { - bone = true; - } - else if ( m_Params[i] == "Locked" ) - { - locked = true; - } - else if ( m_Params[i].StartsWith( "TargetMap" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - map = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - MarkContainer mc = new MarkContainer( bone, locked ); - - mc.TargetMap = map; - mc.Description = "strange location"; - - item = mc; - } - else if ( m_Type == typeofHintItem ) - { - int range = 0; - int messageNumber = 0; - string messageString = null; - int hintNumber = 0; - string hintString = null; - TimeSpan resetDelay = TimeSpan.Zero; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Range" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - range = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "WarningString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "WarningNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "HintString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - hintString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "HintNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - hintNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "ResetDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - resetDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - HintItem hi = new HintItem( m_ItemID, range, messageNumber, hintNumber ); - - hi.WarningString = messageString; - hi.HintString = hintString; - hi.ResetDelay = resetDelay; - - item = hi; - } - else if ( m_Type == typeofWarningItem ) - { - int range = 0; - int messageNumber = 0; - string messageString = null; - TimeSpan resetDelay = TimeSpan.Zero; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Range" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - range = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "WarningString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "WarningNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - messageNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "ResetDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - resetDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - WarningItem wi = new WarningItem( m_ItemID, range, messageNumber ); - - wi.WarningString = messageString; - wi.ResetDelay = resetDelay; - - item = wi; - } - else if ( m_Type == typeofCannon ) - { - CannonDirection direction = CannonDirection.North; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "CannonDirection" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - direction = (CannonDirection)Enum.Parse( typeof( CannonDirection ), m_Params[i].Substring( ++indexOf ), true ); - } - } - - item = new Cannon( direction ); - } - else if ( m_Type == typeofSerpentPillar ) - { - string word = null; - Rectangle2D destination = new Rectangle2D(); - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Word" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - word = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "DestStart" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - destination.Start = Point2D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEnd" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - destination.End = Point2D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - item = new SerpentPillar( word, destination ); - } - else if ( m_Type.IsSubclassOf( typeofBeverage ) ) - { - BeverageType content = BeverageType.Liquor; - bool fill = false; - - for ( int i = 0; !fill && i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Content" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - content = (BeverageType)Enum.Parse( typeof( BeverageType ), m_Params[i].Substring( ++indexOf ), true ); - fill = true; - } - } - } - - if ( fill ) - item = (Item)Activator.CreateInstance( m_Type, new object[]{ content } ); - else - item = (Item)Activator.CreateInstance( m_Type ); - } - else if ( m_Type.IsSubclassOf( typeofBaseDoor ) ) - { - DoorFacing facing = DoorFacing.WestCW; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Facing" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - facing = (DoorFacing)Enum.Parse( typeof( DoorFacing ), m_Params[i].Substring( ++indexOf ), true ); - break; - } - } - } - - item = (Item)Activator.CreateInstance( m_Type, new object[]{ facing } ); - } - else - { - item = (Item)Activator.CreateInstance( m_Type ); - } - } - catch ( Exception e ) - { - throw new Exception($"Bad type: {m_Type}", e ); - } - - if ( item is BaseAddon addon ) - { - if ( addon is MaabusCoffin coffin ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "SpawnLocation" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - coffin.SpawnLocation = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - } - else if ( m_ItemID > 0 ) - { - List comps = addon.Components; - - for ( int i = 0; i < comps.Count; ++i ) - { - AddonComponent comp = (AddonComponent)comps[i]; - - if ( comp.Offset == Point3D.Zero ) - comp.ItemID = m_ItemID; - } - } - } - else if ( item is BaseLight light ) - { - bool unlit = false, unprotected = false; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( !unlit && m_Params[i] == "Unlit" ) - unlit = true; - else if ( !unprotected && m_Params[i] == "Unprotected" ) - unprotected = true; - - if ( unlit && unprotected ) - break; - } - - if ( !unlit ) - light.Ignite(); - if ( !unprotected ) - light.Protected = true; - - if ( m_ItemID > 0 ) - light.ItemID = m_ItemID; - } - else if ( item is Spawner sp ) - { - sp.NextSpawn = TimeSpan.Zero; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Spawn" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.AddEntry( m_Params[i].Substring( ++indexOf ), 100, 1 ); - } - else if ( m_Params[i].StartsWith( "MinDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.MinDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MaxDelay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.MaxDelay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "NextSpawn" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.NextSpawn = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Count" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - sp.Count = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - for ( int se = 0;se < sp.Entries.Count; se++ ) - sp.Entries[se].SpawnedMaxCount = sp.Count; - } - } - else if ( m_Params[i].StartsWith( "Team" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.Team = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "HomeRange" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.HomeRange = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Running" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.Running = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Group" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - sp.Group = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - } - } - else if ( item is RecallRune rune ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Description" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.Description = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "Marked" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.Marked = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "TargetMap" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.TargetMap = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Target" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - rune.Target = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - } - else if ( item is SkillTeleporter st ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Skill" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Skill = (SkillName)Enum.Parse( typeof( SkillName ), m_Params[i].Substring( ++indexOf ), true ); - } - else if ( m_Params[i].StartsWith( "RequiredFixedPoint" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Required = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ) * 0.1; - } - else if ( m_Params[i].StartsWith( "Required" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Required = Utility.ToDouble( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MessageString" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.MessageString = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "MessageNumber" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.MessageNumber = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "PointDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.PointDest = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MapDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.MapDest = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Creatures" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Creatures = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SourceEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.SourceEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.DestEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SoundID" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.SoundID = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Delay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - st.Delay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - if ( m_ItemID > 0 ) - st.ItemID = m_ItemID; - } - else if ( item is KeywordTeleporter kt ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Substring" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Substring = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "Keyword" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Keyword = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Range" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Range = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "PointDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.PointDest = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MapDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.MapDest = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Creatures" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Creatures = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SourceEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.SourceEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.DestEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SoundID" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.SoundID = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Delay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - kt.Delay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - if ( m_ItemID > 0 ) - kt.ItemID = m_ItemID; - } - else if ( item is Teleporter tp ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "PointDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.PointDest = Point3D.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "MapDest" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.MapDest = Map.Parse( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Creatures" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.Creatures = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SourceEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.SourceEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "DestEffect" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.DestEffect = Utility.ToBoolean( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "SoundID" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.SoundID = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - } - else if ( m_Params[i].StartsWith( "Delay" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - tp.Delay = TimeSpan.Parse( m_Params[i].Substring( ++indexOf ) ); - } - } - - if ( m_ItemID > 0 ) - tp.ItemID = m_ItemID; - } - else if ( item is FillableContainer cont ) - { - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "ContentType" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - cont.ContentType = (FillableContentType)Enum.Parse( typeof( FillableContentType ), m_Params[i].Substring( ++indexOf ), true ); - } - } - - if ( m_ItemID > 0 ) - cont.ItemID = m_ItemID; - } - else if ( m_ItemID > 0 ) - { - item.ItemID = m_ItemID; - } - - item.Movable = false; - - for ( int i = 0; i < m_Params.Length; ++i ) - { - if ( m_Params[i].StartsWith( "Light" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - item.Light = (LightType)Enum.Parse( typeof( LightType ), m_Params[i].Substring( ++indexOf ), true ); - } - else if ( m_Params[i].StartsWith( "Hue" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - int hue = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - - if ( item is DyeTub tub ) - tub.DyedHue = hue; - else - item.Hue = hue; - } - } - else if ( m_Params[i].StartsWith( "Name" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - item.Name = m_Params[i].Substring( ++indexOf ); - } - else if ( m_Params[i].StartsWith( "Amount" ) ) - { - int indexOf = m_Params[i].IndexOf( '=' ); - - if ( indexOf >= 0 ) - { - // Must supress stackable warnings - - bool wasStackable = item.Stackable; - - item.Stackable = true; - item.Amount = Utility.ToInt32( m_Params[i].Substring( ++indexOf ) ); - item.Stackable = wasStackable; - } - } - } - - return item; - } - - private static Queue m_DeleteQueue = new Queue(); - - private static bool FindItem( int x, int y, int z, Map map, Item srcItem ) - { - int itemID = srcItem.ItemID; - - bool res = false; - - IPooledEnumerable eable; - - if ( srcItem is BaseDoor ) - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 1 ); - - foreach ( Item item in eable ) - { - if ( !(item is BaseDoor) ) - continue; - - BaseDoor bd = (BaseDoor)item; - Point3D p; - int bdItemID; - - if ( bd.Open ) - { - p = new Point3D( bd.X - bd.Offset.X, bd.Y - bd.Offset.Y, bd.Z - bd.Offset.Z ); - bdItemID = bd.ClosedID; - } - else - { - p = bd.Location; - bdItemID = bd.ItemID; - } - - if ( p.X != x || p.Y != y ) - continue; - - if ( item.Z == z && bdItemID == itemID ) - res = true; - else if ( Math.Abs( item.Z - z ) < 8 ) - m_DeleteQueue.Enqueue( item ); - } - } - else if ( (TileData.ItemTable[itemID & TileData.MaxItemValue].Flags & TileFlag.LightSource) != 0 ) - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - - LightType lt = srcItem.Light; - string srcName = srcItem.ItemData.Name; - - foreach ( Item item in eable ) - { - if ( item.Z == z ) - { - if ( item.ItemID == itemID ) - { - if ( item.Light != lt ) - m_DeleteQueue.Enqueue( item ); - else - res = true; - } - else if ( (item.ItemData.Flags & TileFlag.LightSource) != 0 && item.ItemData.Name == srcName ) - { - m_DeleteQueue.Enqueue( item ); - } - } - } - } - else if ( srcItem is Teleporter || srcItem is FillableContainer || srcItem is BaseBook ) - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - - Type type = srcItem.GetType(); - - foreach ( Item item in eable ) - { - if ( item.Z == z && item.ItemID == itemID ) - { - if ( item.GetType() != type ) - m_DeleteQueue.Enqueue( item ); - else - res = true; - } - } - } - else - { - eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - - foreach ( Item item in eable ) - { - if ( item.Z == z && item.ItemID == itemID ) - { - eable.Free(); - return true; - } - } - } - - eable.Free(); - - while ( m_DeleteQueue.Count > 0 ) - ((Item)m_DeleteQueue.Dequeue()).Delete(); - - return res; - } - - public int Generate( Map[] maps ) - { - int count = 0; - - Item item = null; - - for ( int i = 0; i < m_Entries.Count; ++i ) - { - DecorationEntryMag entry = (DecorationEntryMag)m_Entries[i]; - Point3D loc = entry.Location; - string extra = entry.Extra; - - for ( int j = 0; j < maps.Length; ++j ) - { - if ( item == null ) - item = Construct(); - - if ( item == null ) - continue; - - if ( FindItem( loc.X, loc.Y, loc.Z, maps[j], item ) ) - { - } - else - { - item.MoveToWorld( loc, maps[j] ); - ++count; - - if ( item is BaseDoor door ) - { - IPooledEnumerable eable = maps[j].GetItemsInRange( loc, 1 ); - - Type itemType = door.GetType(); - - foreach ( BaseDoor link in eable ) - { - if ( link != item && link.Z == door.Z && link.GetType() == itemType ) - { - door.Link = link; - link.Link = door; - break; - } - } - - eable.Free(); - } - else if ( item is MarkContainer markCont ) - { - try - { - markCont.Target = Point3D.Parse( extra ); - } - catch{} - } - - item = null; - } - } - } - - item?.Delete(); - - return count; - } - - public static ArrayList ReadAll( string path ) - { - using ( StreamReader ip = new StreamReader( path ) ) - { - ArrayList list = new ArrayList(); - - for ( DecorationListMag v = Read( ip ); v != null; v = Read( ip ) ) - list.Add( v ); - - return list; - } - } - - private static string[] m_EmptyParams = new string[0]; - - public static DecorationListMag Read( StreamReader ip ) - { - string line; - - while ( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); - - if ( line.Length > 0 && !line.StartsWith( "#" ) ) - break; - } - - if ( string.IsNullOrEmpty( line ) ) - return null; - - DecorationListMag list = new DecorationListMag(); - - int indexOf = line.IndexOf( ' ' ); - - list.m_Type = ScriptCompiler.FindTypeByName( line.Substring( 0, indexOf++ ), true ); - - if ( list.m_Type == null ) - throw new ArgumentException($"Type not found for header: '{line}'"); - - line = line.Substring( indexOf ); - indexOf = line.IndexOf( '(' ); - if ( indexOf >= 0 ) - { - list.m_ItemID = Utility.ToInt32( line.Substring( 0, indexOf - 1 ) ); - - string parms = line.Substring( ++indexOf ); - - if ( line.EndsWith( ")" ) ) - parms = parms.Substring( 0, parms.Length - 1 ); - - list.m_Params = parms.Split( ';' ); - - for ( int i = 0; i < list.m_Params.Length; ++i ) - list.m_Params[i] = list.m_Params[i].Trim(); - } - else - { - list.m_ItemID = Utility.ToInt32( line ); - list.m_Params = m_EmptyParams; - } - - list.m_Entries = new ArrayList(); - - while ( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); - - if ( line.Length == 0 ) - break; - - if ( line.StartsWith( "#" ) ) - continue; - - list.m_Entries.Add( new DecorationEntryMag( line ) ); - } - - return list; - } - } - - public class DecorationEntryMag - { - public Point3D Location { get; } + public class DecorateMag + { + private static Mobile m_Mobile; + private static int m_Count; + + public static void Initialize() + { + CommandSystem.Register("DecorateMag", AccessLevel.Administrator, DecorateMag_OnCommand); + } + + [Usage("DecorateMag")] + [Description("Generates world decoration.")] + private static void DecorateMag_OnCommand(CommandEventArgs e) + { + m_Mobile = e.Mobile; + m_Count = 0; + + m_Mobile.SendMessage("Generating world decoration, please wait."); + + Generate("Data/Decoration/RuinedMaginciaTram", Map.Trammel); + Generate("Data/Decoration/RuinedMaginciaFel", Map.Felucca); + + + m_Mobile.SendMessage("World generating complete. {0} items were generated.", m_Count); + } + + public static void Generate(string folder, params Map[] maps) + { + if (!Directory.Exists(folder)) + return; + + string[] files = Directory.GetFiles(folder, "*.cfg"); + + for (int i = 0; i < files.Length; ++i) + { + ArrayList list = DecorationListMag.ReadAll(files[i]); + + for (int j = 0; j < list.Count; ++j) + m_Count += ((DecorationListMag)list[j]).Generate(maps); + } + } + } + + public class DecorationListMag + { + private static Type typeofStatic = typeof(Static); + private static Type typeofLocalizedStatic = typeof(LocalizedStatic); + private static Type typeofBaseDoor = typeof(BaseDoor); + private static Type typeofAnkhWest = typeof(AnkhWest); + private static Type typeofAnkhNorth = typeof(AnkhNorth); + private static Type typeofBeverage = typeof(BaseBeverage); + private static Type typeofLocalizedSign = typeof(LocalizedSign); + private static Type typeofMarkContainer = typeof(MarkContainer); + private static Type typeofWarningItem = typeof(WarningItem); + private static Type typeofHintItem = typeof(HintItem); + private static Type typeofCannon = typeof(Cannon); + private static Type typeofSerpentPillar = typeof(SerpentPillar); + + private static Queue m_DeleteQueue = new Queue(); + + private static string[] m_EmptyParams = new string[0]; + private ArrayList m_Entries; + private int m_ItemID; + private string[] m_Params; + private Type m_Type; + + public Item Construct() + { + if (m_Type == null) + return null; + + Item item; + + try + { + if (m_Type == typeofStatic) + { + item = new Static(m_ItemID); + } + else if (m_Type == typeofLocalizedStatic) + { + int labelNumber = 0; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("LabelNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + labelNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + break; + } + } + + item = new LocalizedStatic(m_ItemID, labelNumber); + } + else if (m_Type == typeofLocalizedSign) + { + int labelNumber = 0; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("LabelNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + labelNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + break; + } + } + + item = new LocalizedSign(m_ItemID, labelNumber); + } + else if (m_Type == typeofAnkhWest || m_Type == typeofAnkhNorth) + { + bool bloodied = false; + + for (int i = 0; !bloodied && i < m_Params.Length; ++i) + bloodied = m_Params[i] == "Bloodied"; + + if (m_Type == typeofAnkhWest) + item = new AnkhWest(bloodied); + else + item = new AnkhNorth(bloodied); + } + else if (m_Type == typeofMarkContainer) + { + bool bone = false; + bool locked = false; + Map map = Map.Malas; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i] == "Bone") + { + bone = true; + } + else if (m_Params[i] == "Locked") + { + locked = true; + } + else if (m_Params[i].StartsWith("TargetMap")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + map = Map.Parse(m_Params[i].Substring(++indexOf)); + } + + MarkContainer mc = new MarkContainer(bone, locked); + + mc.TargetMap = map; + mc.Description = "strange location"; + + item = mc; + } + else if (m_Type == typeofHintItem) + { + int range = 0; + int messageNumber = 0; + string messageString = null; + int hintNumber = 0; + string hintString = null; + TimeSpan resetDelay = TimeSpan.Zero; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Range")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + range = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("WarningString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("WarningNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("HintString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + hintString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("HintNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + hintNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("ResetDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + resetDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + HintItem hi = new HintItem(m_ItemID, range, messageNumber, hintNumber); + + hi.WarningString = messageString; + hi.HintString = hintString; + hi.ResetDelay = resetDelay; + + item = hi; + } + else if (m_Type == typeofWarningItem) + { + int range = 0; + int messageNumber = 0; + string messageString = null; + TimeSpan resetDelay = TimeSpan.Zero; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Range")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + range = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("WarningString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("WarningNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + messageNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("ResetDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + resetDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + WarningItem wi = new WarningItem(m_ItemID, range, messageNumber); + + wi.WarningString = messageString; + wi.ResetDelay = resetDelay; + + item = wi; + } + else if (m_Type == typeofCannon) + { + CannonDirection direction = CannonDirection.North; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("CannonDirection")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + direction = (CannonDirection)Enum.Parse(typeof(CannonDirection), + m_Params[i].Substring(++indexOf), true); + } + + item = new Cannon(direction); + } + else if (m_Type == typeofSerpentPillar) + { + string word = null; + Rectangle2D destination = new Rectangle2D(); + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Word")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + word = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("DestStart")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + destination.Start = Point2D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEnd")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + destination.End = Point2D.Parse(m_Params[i].Substring(++indexOf)); + } + + item = new SerpentPillar(word, destination); + } + else if (m_Type.IsSubclassOf(typeofBeverage)) + { + BeverageType content = BeverageType.Liquor; + bool fill = false; + + for (int i = 0; !fill && i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Content")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + content = (BeverageType)Enum.Parse(typeof(BeverageType), m_Params[i].Substring(++indexOf), + true); + fill = true; + } + } + + if (fill) + item = (Item)Activator.CreateInstance(m_Type, content); + else + item = (Item)Activator.CreateInstance(m_Type); + } + else if (m_Type.IsSubclassOf(typeofBaseDoor)) + { + DoorFacing facing = DoorFacing.WestCW; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Facing")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + facing = (DoorFacing)Enum.Parse(typeof(DoorFacing), m_Params[i].Substring(++indexOf), true); + break; + } + } + + item = (Item)Activator.CreateInstance(m_Type, facing); + } + else + { + item = (Item)Activator.CreateInstance(m_Type); + } + } + catch (Exception e) + { + throw new Exception($"Bad type: {m_Type}", e); + } + + if (item is BaseAddon addon) + { + if (addon is MaabusCoffin coffin) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("SpawnLocation")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + coffin.SpawnLocation = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + } + else if (m_ItemID > 0) + { + List comps = addon.Components; + + for (int i = 0; i < comps.Count; ++i) + { + AddonComponent comp = comps[i]; + + if (comp.Offset == Point3D.Zero) + comp.ItemID = m_ItemID; + } + } + } + else if (item is BaseLight light) + { + bool unlit = false, unprotected = false; + + for (int i = 0; i < m_Params.Length; ++i) + { + if (!unlit && m_Params[i] == "Unlit") + unlit = true; + else if (!unprotected && m_Params[i] == "Unprotected") + unprotected = true; + + if (unlit && unprotected) + break; + } + + if (!unlit) + light.Ignite(); + if (!unprotected) + light.Protected = true; + + if (m_ItemID > 0) + light.ItemID = m_ItemID; + } + else if (item is Spawner sp) + { + sp.NextSpawn = TimeSpan.Zero; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Spawn")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.AddEntry(m_Params[i].Substring(++indexOf), 100, 1); + } + else if (m_Params[i].StartsWith("MinDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.MinDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MaxDelay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.MaxDelay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("NextSpawn")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.NextSpawn = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Count")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + sp.Count = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + for (int se = 0; se < sp.Entries.Count; se++) + sp.Entries[se].SpawnedMaxCount = sp.Count; + } + } + else if (m_Params[i].StartsWith("Team")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.Team = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("HomeRange")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.HomeRange = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Running")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.Running = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Group")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + sp.Group = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + } + else if (item is RecallRune rune) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Description")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.Description = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("Marked")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.Marked = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("TargetMap")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.TargetMap = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Target")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + rune.Target = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + } + else if (item is SkillTeleporter st) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Skill")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Skill = (SkillName)Enum.Parse(typeof(SkillName), m_Params[i].Substring(++indexOf), true); + } + else if (m_Params[i].StartsWith("RequiredFixedPoint")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Required = Utility.ToInt32(m_Params[i].Substring(++indexOf)) * 0.1; + } + else if (m_Params[i].StartsWith("Required")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Required = Utility.ToDouble(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MessageString")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.MessageString = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("MessageNumber")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.MessageNumber = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("PointDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.PointDest = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MapDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.MapDest = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Creatures")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Creatures = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SourceEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.SourceEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.DestEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SoundID")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.SoundID = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Delay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + st.Delay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + if (m_ItemID > 0) + st.ItemID = m_ItemID; + } + else if (item is KeywordTeleporter kt) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Substring")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Substring = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("Keyword")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Keyword = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Range")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Range = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("PointDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.PointDest = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MapDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.MapDest = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Creatures")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Creatures = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SourceEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.SourceEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.DestEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SoundID")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.SoundID = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Delay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + kt.Delay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + if (m_ItemID > 0) + kt.ItemID = m_ItemID; + } + else if (item is Teleporter tp) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("PointDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.PointDest = Point3D.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("MapDest")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.MapDest = Map.Parse(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Creatures")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.Creatures = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SourceEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.SourceEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("DestEffect")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.DestEffect = Utility.ToBoolean(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("SoundID")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.SoundID = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + } + else if (m_Params[i].StartsWith("Delay")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + tp.Delay = TimeSpan.Parse(m_Params[i].Substring(++indexOf)); + } + + if (m_ItemID > 0) + tp.ItemID = m_ItemID; + } + else if (item is FillableContainer cont) + { + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("ContentType")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + cont.ContentType = (FillableContentType)Enum.Parse(typeof(FillableContentType), + m_Params[i].Substring(++indexOf), true); + } + + if (m_ItemID > 0) + cont.ItemID = m_ItemID; + } + else if (m_ItemID > 0) + { + item.ItemID = m_ItemID; + } + + item.Movable = false; + + for (int i = 0; i < m_Params.Length; ++i) + if (m_Params[i].StartsWith("Light")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + item.Light = (LightType)Enum.Parse(typeof(LightType), m_Params[i].Substring(++indexOf), true); + } + else if (m_Params[i].StartsWith("Hue")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + int hue = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + + if (item is DyeTub tub) + tub.DyedHue = hue; + else + item.Hue = hue; + } + } + else if (m_Params[i].StartsWith("Name")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + item.Name = m_Params[i].Substring(++indexOf); + } + else if (m_Params[i].StartsWith("Amount")) + { + int indexOf = m_Params[i].IndexOf('='); + + if (indexOf >= 0) + { + // Must supress stackable warnings + + bool wasStackable = item.Stackable; + + item.Stackable = true; + item.Amount = Utility.ToInt32(m_Params[i].Substring(++indexOf)); + item.Stackable = wasStackable; + } + } + + return item; + } + + private static bool FindItem(int x, int y, int z, Map map, Item srcItem) + { + int itemID = srcItem.ItemID; + + bool res = false; + + IPooledEnumerable eable; + + if (srcItem is BaseDoor) + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 1); + + foreach (Item item in eable) + { + if (!(item is BaseDoor)) + continue; + + BaseDoor bd = (BaseDoor)item; + Point3D p; + int bdItemID; + + if (bd.Open) + { + p = new Point3D(bd.X - bd.Offset.X, bd.Y - bd.Offset.Y, bd.Z - bd.Offset.Z); + bdItemID = bd.ClosedID; + } + else + { + p = bd.Location; + bdItemID = bd.ItemID; + } + + if (p.X != x || p.Y != y) + continue; + + if (item.Z == z && bdItemID == itemID) + res = true; + else if (Math.Abs(item.Z - z) < 8) + m_DeleteQueue.Enqueue(item); + } + } + else if ((TileData.ItemTable[itemID & TileData.MaxItemValue].Flags & TileFlag.LightSource) != 0) + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + + LightType lt = srcItem.Light; + string srcName = srcItem.ItemData.Name; + + foreach (Item item in eable) + if (item.Z == z) + { + if (item.ItemID == itemID) + { + if (item.Light != lt) + m_DeleteQueue.Enqueue(item); + else + res = true; + } + else if ((item.ItemData.Flags & TileFlag.LightSource) != 0 && item.ItemData.Name == srcName) + { + m_DeleteQueue.Enqueue(item); + } + } + } + else if (srcItem is Teleporter || srcItem is FillableContainer || srcItem is BaseBook) + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + + Type type = srcItem.GetType(); + + foreach (Item item in eable) + if (item.Z == z && item.ItemID == itemID) + { + if (item.GetType() != type) + m_DeleteQueue.Enqueue(item); + else + res = true; + } + } + else + { + eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + + foreach (Item item in eable) + if (item.Z == z && item.ItemID == itemID) + { + eable.Free(); + return true; + } + } + + eable.Free(); + + while (m_DeleteQueue.Count > 0) + ((Item)m_DeleteQueue.Dequeue()).Delete(); + + return res; + } + + public int Generate(Map[] maps) + { + int count = 0; + + Item item = null; + + for (int i = 0; i < m_Entries.Count; ++i) + { + DecorationEntryMag entry = (DecorationEntryMag)m_Entries[i]; + Point3D loc = entry.Location; + string extra = entry.Extra; + + for (int j = 0; j < maps.Length; ++j) + { + if (item == null) + item = Construct(); + + if (item == null) + continue; + + if (FindItem(loc.X, loc.Y, loc.Z, maps[j], item)) + { + } + else + { + item.MoveToWorld(loc, maps[j]); + ++count; + + if (item is BaseDoor door) + { + IPooledEnumerable eable = maps[j].GetItemsInRange(loc, 1); + + Type itemType = door.GetType(); + + foreach (BaseDoor link in eable) + if (link != item && link.Z == door.Z && link.GetType() == itemType) + { + door.Link = link; + link.Link = door; + break; + } + + eable.Free(); + } + else if (item is MarkContainer markCont) + { + try + { + markCont.Target = Point3D.Parse(extra); + } + catch + { + } + } + + item = null; + } + } + } + + item?.Delete(); + + return count; + } + + public static ArrayList ReadAll(string path) + { + using (StreamReader ip = new StreamReader(path)) + { + ArrayList list = new ArrayList(); + + for (DecorationListMag v = Read(ip); v != null; v = Read(ip)) + list.Add(v); + + return list; + } + } + + public static DecorationListMag Read(StreamReader ip) + { + string line; + + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); + + if (line.Length > 0 && !line.StartsWith("#")) + break; + } + + if (string.IsNullOrEmpty(line)) + return null; + + DecorationListMag list = new DecorationListMag(); + + int indexOf = line.IndexOf(' '); + + list.m_Type = ScriptCompiler.FindTypeByName(line.Substring(0, indexOf++), true); + + if (list.m_Type == null) + throw new ArgumentException($"Type not found for header: '{line}'"); + + line = line.Substring(indexOf); + indexOf = line.IndexOf('('); + if (indexOf >= 0) + { + list.m_ItemID = Utility.ToInt32(line.Substring(0, indexOf - 1)); + + string parms = line.Substring(++indexOf); + + if (line.EndsWith(")")) + parms = parms.Substring(0, parms.Length - 1); + + list.m_Params = parms.Split(';'); + + for (int i = 0; i < list.m_Params.Length; ++i) + list.m_Params[i] = list.m_Params[i].Trim(); + } + else + { + list.m_ItemID = Utility.ToInt32(line); + list.m_Params = m_EmptyParams; + } + + list.m_Entries = new ArrayList(); + + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); + + if (line.Length == 0) + break; + + if (line.StartsWith("#")) + continue; + + list.m_Entries.Add(new DecorationEntryMag(line)); + } + + return list; + } + } + + public class DecorationEntryMag + { + public DecorationEntryMag(string line) + { + string x, y, z; - public string Extra { get; } + Pop(out x, ref line); + Pop(out y, ref line); + Pop(out z, ref line); - public DecorationEntryMag( string line ) - { - string x, y, z; + Location = new Point3D(Utility.ToInt32(x), Utility.ToInt32(y), Utility.ToInt32(z)); + Extra = line; + } - Pop( out x, ref line ); - Pop( out y, ref line ); - Pop( out z, ref line ); + public Point3D Location{ get; } - Location = new Point3D( Utility.ToInt32( x ), Utility.ToInt32( y ), Utility.ToInt32( z ) ); - Extra = line; - } + public string Extra{ get; } - public void Pop( out string v, ref string line ) - { - int space = line.IndexOf( ' ' ); + public void Pop(out string v, ref string line) + { + int space = line.IndexOf(' '); - if ( space >= 0 ) - { - v = line.Substring( 0, space++ ); - line = line.Substring( space ); - } - else - { - v = line; - line = ""; - } - } - } -} + if (space >= 0) + { + v = line.Substring(0, space++); + line = line.Substring(space); + } + else + { + v = line; + line = ""; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Docs.cs b/Scripts/Commands/Docs.cs index 4a6c7a788..0b4b355a2 100644 --- a/Scripts/Commands/Docs.cs +++ b/Scripts/Commands/Docs.cs @@ -1,2571 +1,2756 @@ using System; -using System.IO; -using System.Text; -using System.Reflection; using System.Collections; -using Server.Items; -using Server.Engines.BulkOrders; -using Server.Commands.Generic; using System.Collections.Generic; +using System.IO; +using System.Reflection; +using System.Text; +using Server.Commands.Generic; +using Server.Engines.BulkOrders; +using Server.Items; +using Server.Network; namespace Server.Commands { - public class Docs - { - public static void Initialize() - { - CommandSystem.Register( "DocGen", AccessLevel.Administrator, DocGen_OnCommand ); - } - - [Usage( "DocGen" )] - [Description( "Generates RunUO documentation." )] - private static void DocGen_OnCommand( CommandEventArgs e ) - { - World.Broadcast( 0x35, true, "Documentation is being generated, please wait." ); - Console.WriteLine( "Documentation is being generated, please wait." ); - - Network.NetState.FlushAll(); - Network.NetState.Pause(); - - DateTime startTime = DateTime.UtcNow; - - bool generated = Document(); - - DateTime endTime = DateTime.UtcNow; - - Network.NetState.Resume(); - - if ( generated ) - { - World.Broadcast( 0x35, true, "Documentation has been completed. The entire process took {0:F1} seconds.", (endTime - startTime).TotalSeconds ); - Console.WriteLine( "Documentation complete." ); - } - else - { - World.Broadcast( 0x35, true, "Docmentation failed: Documentation directories are locked and in use. Please close all open files and directories and try again." ); - Console.WriteLine( "Documentation failed." ); - } - } - - private class MemberComparer : IComparer - { - public int Compare( object x, object y ) - { - if ( x == y ) - return 0; - - ConstructorInfo aCtor = x as ConstructorInfo; - ConstructorInfo bCtor = y as ConstructorInfo; - - PropertyInfo aProp = x as PropertyInfo; - PropertyInfo bProp = y as PropertyInfo; - - MethodInfo aMethod = x as MethodInfo; - MethodInfo bMethod = y as MethodInfo; - - bool aStatic = GetStaticFor( aCtor, aProp, aMethod ); - bool bStatic = GetStaticFor( bCtor, bProp, bMethod ); - - if ( aStatic && !bStatic ) - return -1; - if ( !aStatic && bStatic ) - return 1; - - int v = 0; - - if ( aCtor != null ) - { - if ( bCtor == null ) - v = -1; - } - else if ( bCtor != null ) - { - if ( aCtor == null ) - v = 1; - } - else if ( aProp != null ) - { - if ( bProp == null ) - v = -1; - } - else if ( bProp != null ) - { - if ( aProp == null ) - v = 1; - } - - if ( v == 0 ) - { - v = GetNameFrom( aCtor, aProp, aMethod ).CompareTo( GetNameFrom( bCtor, bProp, bMethod ) ); - } - - if ( v == 0 && aCtor != null && bCtor != null ) - { - v = aCtor.GetParameters().Length.CompareTo( bCtor.GetParameters().Length ); - } - else if ( v == 0 && aMethod != null && bMethod != null ) - { - v = aMethod.GetParameters().Length.CompareTo( bMethod.GetParameters().Length ); - } - - return v; - } - - private bool GetStaticFor( ConstructorInfo ctor, PropertyInfo prop, MethodInfo method ) - { - if ( ctor != null ) - return ctor.IsStatic; - if ( method != null ) - return method.IsStatic; - - if ( prop != null ) - { - MethodInfo getMethod = prop.GetGetMethod(); - MethodInfo setMethod = prop.GetGetMethod(); - - return (getMethod != null && getMethod.IsStatic) || (setMethod != null && setMethod.IsStatic); - } - - return false; - } - - private string GetNameFrom( ConstructorInfo ctor, PropertyInfo prop, MethodInfo method ) - { - if ( ctor != null ) - return ctor.DeclaringType.Name; - if ( prop != null ) - return prop.Name; - if ( method != null ) - return method.Name; - return ""; - } - } - - private class TypeComparer : IComparer - { - public int Compare( TypeInfo x, TypeInfo y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; - - return x.TypeName.CompareTo( y.TypeName ); - } - } - - private class TypeInfo - { - public Type m_Type, m_BaseType, m_Declaring; - public List m_Derived, m_Nested; - public Type[] m_Interfaces; - private string m_FileName, m_TypeName, m_LinkName; - - public TypeInfo( Type type ) - { - m_Type = type; - - m_BaseType = type.BaseType; - m_Declaring = type.DeclaringType; - m_Interfaces = type.GetInterfaces(); - - FormatGeneric( m_Type, ref m_TypeName, ref m_FileName, ref m_LinkName ); - - // Console.WriteLine( ">> inline typeinfo: "+m_TypeName ); - // m_TypeName = GetGenericTypeName( m_Type ); - // m_FileName = Docs.GetFileName( "docs/types/", GetGenericTypeName( m_Type, "-", "-" ), ".html" ); - // m_Writer = Docs.GetWriter( "docs/types/", m_FileName ); - } - - public string FileName => m_FileName; - public string TypeName => m_TypeName; - - public string LinkName( string dirRoot ) - { - return m_LinkName.Replace( "@directory@", dirRoot ); - } - } - - #region FileSystem - private static readonly char[] ReplaceChars = "<>".ToCharArray(); - - public static string GetFileName( string root, string name, string ext ) - { - if ( name.IndexOfAny( ReplaceChars ) >= 0 ) - { - StringBuilder sb = new StringBuilder( name ); - - for( int i = 0; i < ReplaceChars.Length; ++i ) - { - sb.Replace( ReplaceChars[i], '-' ); - } - - name = sb.ToString(); - } - - int index = 0; - string file = string.Concat( name, ext ); - - while( File.Exists( Path.Combine( root, file ) ) ) - { - file = string.Concat( name, ++index, ext ); - } - - return file; - } - - private static string m_RootDirectory = Path.GetDirectoryName( Environment.GetCommandLineArgs()[0] ); - - private static void EnsureDirectory( string path ) - { - path = Path.Combine( m_RootDirectory, path ); - - if ( !Directory.Exists( path ) ) - Directory.CreateDirectory( path ); - } - - private static void DeleteDirectory( string path ) - { - path = Path.Combine( m_RootDirectory, path ); - - if ( Directory.Exists( path ) ) - Directory.Delete( path, true ); - } - - private static StreamWriter GetWriter( string root, string name ) - { - return new StreamWriter( Path.Combine( Path.Combine( m_RootDirectory, root ), name ) ); - } - - private static StreamWriter GetWriter( string path ) - { - return new StreamWriter( Path.Combine( m_RootDirectory, path ) ); - } - #endregion - - #region GetPair - - private static string[,] m_Aliases = { - { "System.Object", "object" }, - { "System.String", "string" }, - { "System.Boolean", "bool" }, - { "System.Byte", "byte" }, - { "System.SByte", "sbyte" }, - { "System.Int16", "short" }, - { "System.UInt16", "ushort" }, - { "System.Int32", "int" }, - { "System.UInt32", "uint" }, - { "System.Int64", "long" }, - { "System.UInt64", "ulong" }, - { "System.Single", "float" }, - { "System.Double", "double" }, - { "System.Decimal", "decimal" }, - { "System.Char", "char" }, - { "System.Void", "void" }, - }; - - private static int m_AliasLength = m_Aliases.GetLength( 0 ); - - public static string GetPair( Type varType, string name, bool ignoreRef ) - { - string prepend = ""; - StringBuilder append = new StringBuilder(); - - Type realType = varType; - - if ( varType.IsByRef ) - { - if ( !ignoreRef ) - prepend = RefString; - - realType = varType.GetElementType(); - } - - if ( realType.IsPointer ) - { - if ( realType.IsArray ) - { - append.Append( '*' ); - - do - { - append.Append( '[' ); - - for( int i = 1; i < realType.GetArrayRank(); ++i ) - append.Append( ',' ); - - append.Append( ']' ); - - realType = realType.GetElementType(); - } while( realType.IsArray ); - - append.Append( ' ' ); - } - else - { - realType = realType.GetElementType(); - append.Append( " *" ); - } - } - else if ( realType.IsArray ) - { - do - { - append.Append( '[' ); - - for( int i = 1; i < realType.GetArrayRank(); ++i ) - append.Append( ',' ); - - append.Append( ']' ); - - realType = realType.GetElementType(); - } while( realType.IsArray ); - - append.Append( ' ' ); - } - else - { - append.Append( ' ' ); - } - - string fullName = realType.FullName; - string aliased = null;// = realType.Name; - - m_Types.TryGetValue( realType, out TypeInfo info ); - - if ( info != null ) - { - aliased = ""+info.LinkName( null ); - //aliased = String.Format( "{1}", info.m_FileName, info.m_TypeName ); - } - else - { - //FormatGeneric( ); - if ( realType.IsGenericType ) - { - string typeName = ""; - string fileName = ""; - string linkName = ""; - - FormatGeneric( realType, ref typeName, ref fileName, ref linkName ); - linkName = linkName.Replace( "@directory@", null ); - aliased = linkName; - } - else - { - for( int i = 0; i < m_AliasLength; ++i ) - { - if ( m_Aliases[i, 0] == fullName ) - { - aliased = m_Aliases[i, 1]; - break; - } - } - } - - if ( aliased == null ) - aliased = realType.Name; - } - - string retval = string.Concat( prepend, aliased, append, name ); - //Console.WriteLine(">> getpair: "+retval); - return retval; - } - - #endregion - - private static Dictionary m_Types; - private static Dictionary> m_Namespaces; - - #region Root documentation - - private static bool Document() - { - try { DeleteDirectory( "docs/" ); } - catch { return false; } - - EnsureDirectory( "docs/" ); - EnsureDirectory( "docs/namespaces/" ); - EnsureDirectory( "docs/types/" ); - EnsureDirectory( "docs/bods/" ); - - GenerateStyles(); - GenerateIndex(); - - DocumentCommands(); - DocumentKeywords(); - DocumentBodies(); - - DocumentBulkOrders(); - - m_Types = new Dictionary(); - m_Namespaces = new Dictionary>(); - - List assemblies = new List(); - - assemblies.Add( Core.Assembly ); - - foreach( Assembly asm in ScriptCompiler.Assemblies ) - assemblies.Add( asm ); - - Assembly[] asms = assemblies.ToArray(); - - for( int i = 0; i < asms.Length; ++i ) - LoadTypes( asms[i], asms ); - - DocumentLoadedTypes(); - DocumentConstructibleObjects(); - - return true; - } - - private static void AddIndexLink( StreamWriter html, string filePath, string label, string desc ) - { - html.WriteLine( "

{2}

", filePath, desc, label ); - } - - private static void GenerateStyles() - { - using( StreamWriter css = GetWriter( "docs/", "styles.css" ) ) - { - css.WriteLine( "body { background-color: #FFFFFF; font-family: verdana, arial; font-size: 11px; }" ); - css.WriteLine( "a { color: #28435E; }" ); - css.WriteLine( "a:hover { color: #4878A9; }" ); - css.WriteLine( "td.header { background-color: #9696AA; font-weight: bold; font-size: 12px; }" ); - css.WriteLine( "td.lentry { background-color: #D7D7EB; width: 10%; }" ); - css.WriteLine( "td.rentry { background-color: #FFFFFF; width: 90%; }" ); - css.WriteLine( "td.entry { background-color: #FFFFFF; }" ); - css.WriteLine( "td { font-size: 11px; }" ); - css.WriteLine( ".tbl-border { background-color: #46465A; }" ); - - css.WriteLine( "td.ir {{ background-color: #{0:X6}; }}", Iron ); - css.WriteLine( "td.du {{ background-color: #{0:X6}; }}", DullCopper ); - css.WriteLine( "td.sh {{ background-color: #{0:X6}; }}", ShadowIron ); - css.WriteLine( "td.co {{ background-color: #{0:X6}; }}", Copper ); - css.WriteLine( "td.br {{ background-color: #{0:X6}; }}", Bronze ); - css.WriteLine( "td.go {{ background-color: #{0:X6}; }}", Gold ); - css.WriteLine( "td.ag {{ background-color: #{0:X6}; }}", Agapite ); - css.WriteLine( "td.ve {{ background-color: #{0:X6}; }}", Verite ); - css.WriteLine( "td.va {{ background-color: #{0:X6}; }}", Valorite ); - - css.WriteLine( "td.cl {{ background-color: #{0:X6}; }}", Cloth ); - css.WriteLine( "td.pl {{ background-color: #{0:X6}; }}", Plain ); - css.WriteLine( "td.sp {{ background-color: #{0:X6}; }}", Core.AOS ? SpinedAOS : SpinedLBR ); - css.WriteLine( "td.ho {{ background-color: #{0:X6}; }}", Core.AOS ? HornedAOS : HornedLBR ); - css.WriteLine( "td.ba {{ background-color: #{0:X6}; }}", Core.AOS ? BarbedAOS : BarbedLBR ); - } - } - - private static void GenerateIndex() - { - using( StreamWriter html = GetWriter( "docs/", "index.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Index" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - - AddIndexLink( html, "commands.html", "Commands", "Every available command. This contains command name, usage, aliases, and description." ); - AddIndexLink( html, "objects.html", "Constructible Objects", "Every constructable item or npc. This contains object name and usage. Hover mouse over parameters to see type description." ); - AddIndexLink( html, "keywords.html", "Speech Keywords", "Lists speech keyword numbers and associated match patterns. These are used in some scripts for multi-language matching of client speech." ); - AddIndexLink( html, "bodies.html", "Body List", "Every usable body number and name. Table is generated from a UO:3D client datafile. If you do not have UO:3D installed, this may be blank." ); - AddIndexLink( html, "overview.html", "Class Overview", "Scripting reference. Contains every class type and contained methods in the core and scripts." ); - AddIndexLink( html, "bods/bod_smith_rewards.html", "Bulk Order Rewards: Smithing", "Reference table for large and small smithing bulk order deed rewards." ); - AddIndexLink( html, "bods/bod_tailor_rewards.html", "Bulk Order Rewards: Tailoring", "Reference table for large and small tailoring bulk order deed rewards." ); - - html.WriteLine( " " ); - html.WriteLine( "" ); - } - } - - #endregion - - #region BODs - - private const int Iron = 0xCCCCDD; - private const int DullCopper = 0xAAAAAA; - private const int ShadowIron = 0x777799; - private const int Copper = 0xDDCC99; - private const int Bronze = 0xAA8866; - private const int Gold = 0xDDCC55; - private const int Agapite = 0xDDAAAA; - private const int Verite = 0x99CC77; - private const int Valorite = 0x88AABB; - - private const int Cloth = 0xDDDDDD; - private const int Plain = 0xCCAA88; - private const int SpinedAOS = 0x99BBBB; - private const int HornedAOS = 0xCC8888; - private const int BarbedAOS = 0xAABBAA; - private const int SpinedLBR = 0xAA8833; - private const int HornedLBR = 0xBBBBAA; - private const int BarbedLBR = 0xCCAA88; - - private static void DocumentBulkOrders() - { - using( StreamWriter html = GetWriter( "docs/bods/", "bod_smith_rewards.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Bulk Orders - Smith Rewards" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - - SmallBOD sbod = new SmallSmithBOD(); - - sbod.Type = typeof( Katana ); - sbod.Material = BulkMaterialType.None; - sbod.AmountMax = 10; - - WriteSmithBODHeader( html, "(Small) Weapons" ); - sbod.RequireExceptional = false; - DocumentSmithBOD( html, sbod.ComputeRewards( true ), "10, 15, 20: Normal", sbod.Material ); - sbod.RequireExceptional = true; - DocumentSmithBOD( html, sbod.ComputeRewards( true ), "10, 15, 20: Exceptional", sbod.Material ); - WriteSmithBODFooter( html ); - - html.WriteLine( "

" ); - html.WriteLine( "

" ); - - - sbod.Type = typeof( PlateArms ); - - WriteSmithBODHeader( html, "(Small) Armor: Normal" ); - - sbod.RequireExceptional = false; - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat ) - { - sbod.Material = mat; - sbod.AmountMax = 10; - DocumentSmithBOD( html, sbod.ComputeRewards( true ), "10, 15, 20", sbod.Material ); - } - - WriteSmithBODFooter( html ); - - html.WriteLine( "

" ); - - WriteSmithBODHeader( html, "(Small) Armor: Exceptional" ); - - sbod.RequireExceptional = true; - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat ) - { - sbod.Material = mat; - - for( int amt = 15; amt <= 20; amt += 5 ) - { - sbod.AmountMax = amt; - DocumentSmithBOD( html, sbod.ComputeRewards( true ), amt == 20 ? "20" : "10, 15", sbod.Material ); - } - } - - WriteSmithBODFooter( html ); - - html.WriteLine( "

" ); - html.WriteLine( "

" ); - - sbod.Delete(); - - WriteSmithLBOD( html, "Ringmail", LargeBulkEntry.LargeRing ); - WriteSmithLBOD( html, "Chainmail", LargeBulkEntry.LargeChain ); - WriteSmithLBOD( html, "Platemail", LargeBulkEntry.LargePlate ); - - html.WriteLine( " " ); - html.WriteLine( "" ); - } - - using( StreamWriter html = GetWriter( "docs/bods/", "bod_tailor_rewards.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Bulk Orders - Tailor Rewards" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - - SmallBOD sbod = new SmallTailorBOD(); - - WriteTailorBODHeader( html, "Small Bulk Order" ); - - html.WriteLine( " " ); - html.WriteLine( " Regular: 10, 15" ); - html.WriteLine( " " ); - - sbod.AmountMax = 10; - sbod.RequireExceptional = false; + public class Docs + { + private static Dictionary m_Types; + private static Dictionary> m_Namespaces; - sbod.Type = typeof( SkullCap ); - sbod.Material = BulkMaterialType.None; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "10, 15", sbod.Material, sbod.Type ); + public static void Initialize() + { + CommandSystem.Register("DocGen", AccessLevel.Administrator, DocGen_OnCommand); + } - sbod.Type = typeof( LeatherCap ); - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat ) - { - if ( mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite ) - continue; + [Usage("DocGen")] + [Description("Generates RunUO documentation.")] + private static void DocGen_OnCommand(CommandEventArgs e) + { + World.Broadcast(0x35, true, "Documentation is being generated, please wait."); + Console.WriteLine("Documentation is being generated, please wait."); - sbod.Material = mat; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "10, 15", sbod.Material, sbod.Type ); - } + NetState.FlushAll(); + NetState.Pause(); - html.WriteLine( " " ); - html.WriteLine( " Regular: 20" ); - html.WriteLine( " " ); + DateTime startTime = DateTime.UtcNow; - sbod.AmountMax = 20; - sbod.RequireExceptional = false; + bool generated = Document(); - sbod.Type = typeof( SkullCap ); - sbod.Material = BulkMaterialType.None; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "20", sbod.Material, sbod.Type ); + DateTime endTime = DateTime.UtcNow; - sbod.Type = typeof( LeatherCap ); - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat ) - { - if ( mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite ) - continue; + NetState.Resume(); - sbod.Material = mat; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "20", sbod.Material, sbod.Type ); - } + if (generated) + { + World.Broadcast(0x35, true, "Documentation has been completed. The entire process took {0:F1} seconds.", + (endTime - startTime).TotalSeconds); + Console.WriteLine("Documentation complete."); + } + else + { + World.Broadcast(0x35, true, + "Docmentation failed: Documentation directories are locked and in use. Please close all open files and directories and try again."); + Console.WriteLine("Documentation failed."); + } + } - html.WriteLine( " " ); - html.WriteLine( " Exceptional: 10, 15" ); - html.WriteLine( " " ); + private static void LoadTypes(Assembly a, Assembly[] asms) + { + Type[] types = a.GetTypes(); - sbod.AmountMax = 10; - sbod.RequireExceptional = true; - - sbod.Type = typeof( SkullCap ); - sbod.Material = BulkMaterialType.None; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "10, 15", sbod.Material, sbod.Type ); + for (int i = 0; i < types.Length; ++i) + { + Type type = types[i]; - sbod.Type = typeof( LeatherCap ); - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat ) - { - if ( mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite ) - continue; - - sbod.Material = mat; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "10, 15", sbod.Material, sbod.Type ); - } - - html.WriteLine( " " ); - html.WriteLine( " Exceptional: 20" ); - html.WriteLine( " " ); - - sbod.AmountMax = 20; - sbod.RequireExceptional = true; - - sbod.Type = typeof( SkullCap ); - sbod.Material = BulkMaterialType.None; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "20", sbod.Material, sbod.Type ); - - sbod.Type = typeof( LeatherCap ); - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat ) - { - if ( mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite ) - continue; - - sbod.Material = mat; - DocumentTailorBOD( html, sbod.ComputeRewards( true ), "20", sbod.Material, sbod.Type ); - } - - WriteTailorBODFooter( html ); - - html.WriteLine( "

" ); - html.WriteLine( "

" ); - - sbod.Delete(); - - WriteTailorLBOD( html, "Large Bulk Order: 4-part", LargeBulkEntry.Gypsy, true, true ); - WriteTailorLBOD( html, "Large Bulk Order: 5-part", LargeBulkEntry.TownCrier, true, true ); - WriteTailorLBOD( html, "Large Bulk Order: 6-part", LargeBulkEntry.MaleLeatherSet, false, true ); - - html.WriteLine( " " ); - html.WriteLine( "" ); - } - } - - #region Tailor Bods - private static void WriteTailorLBOD( StreamWriter html, string name, SmallBulkEntry[] entries, bool expandCloth, bool expandPlain ) - { - WriteTailorBODHeader( html, name ); - - LargeBOD lbod = new LargeTailorBOD(); - - lbod.Entries = LargeBulkEntry.ConvertEntries( lbod, entries ); - - Type type = entries[0].Type; - - bool showCloth = !(type.IsSubclassOf( typeof( BaseArmor ) ) || type.IsSubclassOf( typeof( BaseShoes ) )); - - html.WriteLine( " " ); - html.WriteLine( " Regular" ); - html.WriteLine( " " ); - - lbod.RequireExceptional = false; - lbod.AmountMax = 10; - - if ( showCloth ) - { - lbod.Material = BulkMaterialType.None; - - if ( expandCloth ) - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15", lbod.Material, type ); - lbod.AmountMax = 20; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "20", lbod.Material, type ); - } - else - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material, type ); - } - } - - lbod.Material = BulkMaterialType.None; - - if ( expandPlain ) - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material, typeof( LeatherCap ) ); - lbod.AmountMax = 20; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "20", lbod.Material, typeof( LeatherCap ) ); - } - else - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material, typeof( LeatherCap ) ); - } - - for( BulkMaterialType mat = BulkMaterialType.Spined; mat <= BulkMaterialType.Barbed; ++mat ) - { - lbod.Material = mat; - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15", lbod.Material, type ); - lbod.AmountMax = 20; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "20", lbod.Material, type ); - } - - html.WriteLine( " " ); - html.WriteLine( " Exceptional" ); - html.WriteLine( " " ); - - lbod.RequireExceptional = true; - lbod.AmountMax = 10; - - if ( showCloth ) - { - lbod.Material = BulkMaterialType.None; - - if ( expandCloth ) - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15", lbod.Material, type ); - lbod.AmountMax = 20; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "20", lbod.Material, type ); - } - else - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material, type ); - } - } - - lbod.Material = BulkMaterialType.None; - - if ( expandPlain ) - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material, typeof( LeatherCap ) ); - lbod.AmountMax = 20; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "20", lbod.Material, typeof( LeatherCap ) ); - } - else - { - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material, typeof( LeatherCap ) ); - } - - for( BulkMaterialType mat = BulkMaterialType.Spined; mat <= BulkMaterialType.Barbed; ++mat ) - { - lbod.Material = mat; - lbod.AmountMax = 10; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "10, 15", lbod.Material, type ); - lbod.AmountMax = 20; - DocumentTailorBOD( html, lbod.ComputeRewards( true ), "20", lbod.Material, type ); - } - - WriteTailorBODFooter( html ); - - html.WriteLine( "

" ); - html.WriteLine( "

" ); - } - - private static void WriteTailorBODHeader( StreamWriter html, string title ) - { - html.WriteLine( " " ); - html.WriteLine( "
" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " ", title ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - } - - private static void WriteTailorBODFooter( StreamWriter html ) - { - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "
{0}
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
Power Scrolls
\"Small
\"Medium
\"Light
\"Dark
\"Brown
\"Polar
\"Clothing
Runic Kits
+5
+10
+15
+20
\"Runic
\"Runic
\"Runic
 
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
+5
+10
+15
+20
\"Small
\"Medium
\"Light
\"Dark
\"Brown
\"Polar
\"Clothing
\"Runic
\"Runic
\"Runic
Power Scrolls
Runic Kits
" ); - } - - private static void DocumentTailorBOD( StreamWriter html, List items, string amt, BulkMaterialType material, Type type ) - { - bool[] rewards = new bool[20]; - - for( int i = 0; i < items.Count; ++i ) - { - Item item = (Item)items[i]; - - if ( item is Sandals ) - rewards[5] = true; - else if ( item is SmallStretchedHideEastDeed || item is SmallStretchedHideSouthDeed ) - rewards[10] = rewards[11] = true; - else if ( item is MediumStretchedHideEastDeed || item is MediumStretchedHideSouthDeed ) - rewards[10] = rewards[11] = true; - else if ( item is LightFlowerTapestryEastDeed || item is LightFlowerTapestrySouthDeed ) - rewards[12] = rewards[13] = true; - else if ( item is DarkFlowerTapestryEastDeed || item is DarkFlowerTapestrySouthDeed ) - rewards[12] = rewards[13] = true; - else if ( item is BrownBearRugEastDeed || item is BrownBearRugSouthDeed ) - rewards[14] = rewards[15] = true; - else if ( item is PolarBearRugEastDeed || item is PolarBearRugSouthDeed ) - rewards[14] = rewards[15] = true; - else if ( item is ClothingBlessDeed ) - rewards[16] = true; - else if ( item is PowerScroll ps ) - { - if ( ps.Value == 105.0 ) - rewards[6] = true; - else if ( ps.Value == 110.0 ) - rewards[7] = true; - else if ( ps.Value == 115.0 ) - rewards[8] = true; - else if ( ps.Value == 120.0 ) - rewards[9] = true; - } - else if ( item is UncutCloth ) - { - if ( item.Hue == 0x483 || item.Hue == 0x48C || item.Hue == 0x488 || item.Hue == 0x48A ) - rewards[0] = true; - else if ( item.Hue == 0x495 || item.Hue == 0x48B || item.Hue == 0x486 || item.Hue == 0x485 ) - rewards[1] = true; - else if ( item.Hue == 0x48D || item.Hue == 0x490 || item.Hue == 0x48E || item.Hue == 0x491 ) - rewards[2] = true; - else if ( item.Hue == 0x48F || item.Hue == 0x494 || item.Hue == 0x484 || item.Hue == 0x497 ) - rewards[3] = true; - else - rewards[4] = true; - } - else if ( item is RunicSewingKit rkit ) - { - rewards[16 + CraftResources.GetIndex( rkit.Resource )] = true; - } - - item.Delete(); - } - - string style = null; - string name = null; - - switch( material ) - { - case BulkMaterialType.None: - { - if ( type.IsSubclassOf( typeof( BaseArmor ) ) || type.IsSubclassOf( typeof( BaseShoes ) ) ) - { - style = "pl"; - name = "Plain"; - } - else - { - style = "cl"; - name = "Cloth"; - } - - break; - } - case BulkMaterialType.Spined: style = "sp"; name = "Spined"; break; - case BulkMaterialType.Horned: style = "ho"; name = "Horned"; break; - case BulkMaterialType.Barbed: style = "ba"; name = "Barbed"; break; - } - - html.WriteLine( " " ); - html.WriteLine( "  - {0} {1}", name, amt ); - - int index = 0; - - while( index < 20 ) - { - if ( rewards[index] ) - { - html.WriteLine( "
X
", style ); - ++index; - } - else - { - int count = 0; - - while( index < 20 && !rewards[index] ) - { - ++count; - ++index; - - if ( index == 5 || index == 6 || index == 10 || index == 17 ) - break; - } - - html.WriteLine( "  ", count*25, count==1?"": $" colspan=\"{count}\""); - } - } - - html.WriteLine( " " ); - } - - #endregion - - #region Smith Bods - private static void WriteSmithLBOD( StreamWriter html, string name, SmallBulkEntry[] entries ) - { - LargeBOD lbod = new LargeSmithBOD(); - - lbod.Entries = LargeBulkEntry.ConvertEntries( lbod, entries ); - - WriteSmithBODHeader( html, $"(Large) {name}: Normal"); - - lbod.RequireExceptional = false; - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat ) - { - lbod.Material = mat; - lbod.AmountMax = 10; - DocumentSmithBOD( html, lbod.ComputeRewards( true ), "10, 15, 20", lbod.Material ); - } - - WriteSmithBODFooter( html ); - - html.WriteLine( "

" ); - - WriteSmithBODHeader( html, $"(Large) {name}: Exceptional"); - - lbod.RequireExceptional = true; - for( BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat ) - { - lbod.Material = mat; - - for( int amt = 15; amt <= 20; amt += 5 ) - { - lbod.AmountMax = amt; - DocumentSmithBOD( html, lbod.ComputeRewards( true ), amt == 20 ? "20" : "10, 15", lbod.Material ); - } - } - - WriteSmithBODFooter( html ); - - html.WriteLine( "

" ); - html.WriteLine( "

" ); - } - - private static void WriteSmithBODHeader( StreamWriter html, string title ) - { - html.WriteLine( " " ); - html.WriteLine( "
" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " ", title ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - } - - private static void WriteSmithBODFooter( StreamWriter html ) - { - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "
{0}
\"Sturdy
Gloves
\"Gargoyles
\"Prospectors
\"Powder
\"Colored
Power Scrolls
Runic Hammers
Ancient Hammers
+1
+3
+5
+5
+10
+15
+20
Du
Sh
Co
Br
Go
Ag
Ve
Va
+10
+15
+30
+60
 
\"Sturdy
+1
 
+3
 
+5
 
\"Gargoyles
\"Prospectors
\"Powder
\"Colored
+5
+10
+15
+20
Du
Sh
Co
Br
Go
Ag
Ve
Va
+10
+15
+30
+60
Gloves
Power Scrolls
Runic Hammers
Ancient Hammers
" ); - } - - private static void DocumentSmithBOD( StreamWriter html, List items, string amt, BulkMaterialType material ) - { - bool[] rewards = new bool[24]; - - for( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( item is SturdyPickaxe || item is SturdyShovel ) - rewards[0] = true; - else if ( item is LeatherGlovesOfMining ) - rewards[1] = true; - else if ( item is StuddedGlovesOfMining ) - rewards[2] = true; - else if ( item is RingmailGlovesOfMining ) - rewards[3] = true; - else if ( item is GargoylesPickaxe ) - rewards[4] = true; - else if ( item is ProspectorsTool ) - rewards[5] = true; - else if ( item is PowderOfTemperament ) - rewards[6] = true; - else if ( item is ColoredAnvil ) - rewards[7] = true; - else if ( item is PowerScroll ps ) - { - if ( ps.Value == 105.0 ) - rewards[8] = true; - else if ( ps.Value == 110.0 ) - rewards[9] = true; - else if ( ps.Value == 115.0 ) - rewards[10] = true; - else if ( ps.Value == 120.0 ) - rewards[11] = true; - } - else if ( item is RunicHammer rh ) - { - rewards[11 + CraftResources.GetIndex( rh.Resource )] = true; - } - else if ( item is AncientSmithyHammer ash ) - { - if ( ash.Bonus == 10 ) - rewards[20] = true; - else if ( ash.Bonus == 15 ) - rewards[21] = true; - else if ( ash.Bonus == 30 ) - rewards[22] = true; - else if ( ash.Bonus == 60 ) - rewards[23] = true; - } - - item.Delete(); - } - - string style = null; - string name = null; - - switch( material ) - { - case BulkMaterialType.None: style = "ir"; name = "Iron"; break; - case BulkMaterialType.DullCopper: style = "du"; name = "Dull Copper"; break; - case BulkMaterialType.ShadowIron: style = "sh"; name = "Shadow Iron"; break; - case BulkMaterialType.Copper: style = "co"; name = "Copper"; break; - case BulkMaterialType.Bronze: style = "br"; name = "Bronze"; break; - case BulkMaterialType.Gold: style = "go"; name = "Gold"; break; - case BulkMaterialType.Agapite: style = "ag"; name = "Agapite"; break; - case BulkMaterialType.Verite: style = "ve"; name = "Verite"; break; - case BulkMaterialType.Valorite: style = "va"; name = "Valorite"; break; - } - - html.WriteLine( " " ); - html.WriteLine( " {0} {1}", name, amt ); - - int index = 0; - - while( index < 24 ) - { - if ( rewards[index] ) - { - html.WriteLine( "
X
", style ); - ++index; - } - else - { - int count = 0; - - while( index < 24 && !rewards[index] ) - { - ++count; - ++index; - - if ( index == 4 || index == 8 || index == 12 || index == 20 ) - break; - } - - html.WriteLine( "  ", count*25, count==1?"": $" colspan=\"{count}\""); - } - } - - html.WriteLine( " " ); - } - - #endregion - - #endregion - - #region Bodies - public static List LoadBodies() - { - List list = new List(); - - string path = Core.FindDataFile( "models/models.txt" ); - - if ( File.Exists( path ) ) - { - using( StreamReader ip = new StreamReader( path ) ) - { - string line; - - while( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); - - if ( line.Length == 0 || line.StartsWith( "#" ) ) - continue; - - string[] split = line.Split( '\t' ); - - if ( split.Length >= 9 ) - { - Body body = Utility.ToInt32( split[0] ); - ModelBodyType type = (ModelBodyType)Utility.ToInt32( split[1] ); - string name = split[8]; - - BodyEntry entry = new BodyEntry( body, type, name ); - - if ( !list.Contains( entry ) ) - list.Add( entry ); - } - } - } - } - - return list; - } - - private static void DocumentBodies() - { - List list = LoadBodies(); - - using( StreamWriter html = GetWriter( "docs/", "bodies.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Body List" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "

Back to the index

" ); - - if ( list.Count > 0 ) - { - html.WriteLine( "

Body List

" ); - - list.Sort( new BodyEntrySorter() ); - - ModelBodyType lastType = ModelBodyType.Invalid; - - for( int i = 0; i < list.Count; ++i ) - { - BodyEntry entry = list[i]; - ModelBodyType type = entry.BodyType; - - if ( type != lastType ) - { - if ( lastType != ModelBodyType.Invalid ) - html.WriteLine( "
" ); - - lastType = type; - - html.WriteLine( " ", type ); - - switch( type ) - { - case ModelBodyType.Monsters: html.WriteLine( " Monsters | Sea | Animals | Human | Equipment

" ); break; - case ModelBodyType.Sea: html.WriteLine( " Monsters | Sea | Animals | Human | Equipment

" ); break; - case ModelBodyType.Animals: html.WriteLine( " Monsters | Sea | Animals | Human | Equipment

" ); break; - case ModelBodyType.Human: html.WriteLine( " Monsters | Sea | Animals | Human | Equipment

" ); break; - case ModelBodyType.Equipment: html.WriteLine( " Monsters | Sea | Animals | Human | Equipment

" ); break; - } - - html.WriteLine( " " ); - html.WriteLine( " "); + html.WriteLine(" "); + html.WriteLine(" "); - if ( usage == null || !(attrs[0] is DescriptionAttribute desc) ) - continue; + sbod.AmountMax = 10; + sbod.RequireExceptional = false; + + sbod.Type = typeof(SkullCap); + sbod.Material = BulkMaterialType.None; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "10, 15", sbod.Material, sbod.Type); - attrs = mi.GetCustomAttributes( typeof( AliasesAttribute ), false ); + sbod.Type = typeof(LeatherCap); + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat) + { + if (mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite) + continue; - AliasesAttribute aliases = (attrs.Length == 0 ? null : attrs[0] as AliasesAttribute); + sbod.Material = mat; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "10, 15", sbod.Material, sbod.Type); + } - string descString = desc.Description.Replace( "<", "<" ).Replace( ">", ">" ); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); - if ( aliases == null ) - list.Add( new DocCommandEntry( e.AccessLevel, e.Command, null, usage.Usage, descString ) ); - else - list.Add( new DocCommandEntry( e.AccessLevel, e.Command, aliases.Aliases, usage.Usage, descString ) ); - } + sbod.AmountMax = 20; + sbod.RequireExceptional = false; - for( int i = 0; i < TargetCommands.AllCommands.Count; ++i ) - { - BaseCommand command = TargetCommands.AllCommands[i]; + sbod.Type = typeof(SkullCap); + sbod.Material = BulkMaterialType.None; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "20", sbod.Material, sbod.Type); - string usage = command.Usage; - string desc = command.Description; + sbod.Type = typeof(LeatherCap); + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat) + { + if (mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite) + continue; - if ( usage == null || desc == null ) - continue; + sbod.Material = mat; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "20", sbod.Material, sbod.Type); + } - string[] cmds = command.Commands; - string cmd = cmds[0]; - string[] aliases = new string[cmds.Length - 1]; + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine(" "); - for( int j = 0; j < aliases.Length; ++j ) - aliases[j] = cmds[j + 1]; + sbod.AmountMax = 10; + sbod.RequireExceptional = true; - desc = desc.Replace( "<", "<" ).Replace( ">", ">" ); + sbod.Type = typeof(SkullCap); + sbod.Material = BulkMaterialType.None; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "10, 15", sbod.Material, sbod.Type); - if ( command.Supports != CommandSupport.Single ) - { - StringBuilder sb = new StringBuilder( 50 + desc.Length ); + sbod.Type = typeof(LeatherCap); + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat) + { + if (mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite) + continue; + + sbod.Material = mat; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "10, 15", sbod.Material, sbod.Type); + } + + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + + sbod.AmountMax = 20; + sbod.RequireExceptional = true; + + sbod.Type = typeof(SkullCap); + sbod.Material = BulkMaterialType.None; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "20", sbod.Material, sbod.Type); + + sbod.Type = typeof(LeatherCap); + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Barbed; ++mat) + { + if (mat >= BulkMaterialType.DullCopper && mat <= BulkMaterialType.Valorite) + continue; + + sbod.Material = mat; + DocumentTailorBOD(html, sbod.ComputeRewards(true), "20", sbod.Material, sbod.Type); + } + + WriteTailorBODFooter(html); + + html.WriteLine("

"); + html.WriteLine("

"); + + sbod.Delete(); + + WriteTailorLBOD(html, "Large Bulk Order: 4-part", LargeBulkEntry.Gypsy, true, true); + WriteTailorLBOD(html, "Large Bulk Order: 5-part", LargeBulkEntry.TownCrier, true, true); + WriteTailorLBOD(html, "Large Bulk Order: 6-part", LargeBulkEntry.MaleLeatherSet, false, true); + + html.WriteLine(" "); + html.WriteLine(""); + } + } + + #region Tailor Bods + + private static void WriteTailorLBOD(StreamWriter html, string name, SmallBulkEntry[] entries, bool expandCloth, + bool expandPlain) + { + WriteTailorBODHeader(html, name); + + LargeBOD lbod = new LargeTailorBOD(); + + lbod.Entries = LargeBulkEntry.ConvertEntries(lbod, entries); + + Type type = entries[0].Type; + + bool showCloth = !(type.IsSubclassOf(typeof(BaseArmor)) || type.IsSubclassOf(typeof(BaseShoes))); + + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + + lbod.RequireExceptional = false; + lbod.AmountMax = 10; + + if (showCloth) + { + lbod.Material = BulkMaterialType.None; + + if (expandCloth) + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15", lbod.Material, type); + lbod.AmountMax = 20; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "20", lbod.Material, type); + } + else + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material, type); + } + } + + lbod.Material = BulkMaterialType.None; + + if (expandPlain) + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material, typeof(LeatherCap)); + lbod.AmountMax = 20; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "20", lbod.Material, typeof(LeatherCap)); + } + else + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material, typeof(LeatherCap)); + } + + for (BulkMaterialType mat = BulkMaterialType.Spined; mat <= BulkMaterialType.Barbed; ++mat) + { + lbod.Material = mat; + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15", lbod.Material, type); + lbod.AmountMax = 20; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "20", lbod.Material, type); + } + + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + + lbod.RequireExceptional = true; + lbod.AmountMax = 10; + + if (showCloth) + { + lbod.Material = BulkMaterialType.None; + + if (expandCloth) + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15", lbod.Material, type); + lbod.AmountMax = 20; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "20", lbod.Material, type); + } + else + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material, type); + } + } + + lbod.Material = BulkMaterialType.None; + + if (expandPlain) + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material, typeof(LeatherCap)); + lbod.AmountMax = 20; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "20", lbod.Material, typeof(LeatherCap)); + } + else + { + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material, typeof(LeatherCap)); + } + + for (BulkMaterialType mat = BulkMaterialType.Spined; mat <= BulkMaterialType.Barbed; ++mat) + { + lbod.Material = mat; + lbod.AmountMax = 10; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "10, 15", lbod.Material, type); + lbod.AmountMax = 20; + DocumentTailorBOD(html, lbod.ComputeRewards(true), "20", lbod.Material, type); + } + + WriteTailorBODFooter(html); + + html.WriteLine("

"); + html.WriteLine("

"); + } + + private static void WriteTailorBODHeader(StreamWriter html, string title) + { + html.WriteLine("
" ); - html.WriteLine( " " ); - html.WriteLine( " ", type ); - } - - html.WriteLine( " ", entry.Body.BodyID, entry.Name ); - } - - html.WriteLine( "
{0}
{0}{1}
" ); - } - else - { - html.WriteLine( " This feature requires a UO:3D installation." ); - } - - html.WriteLine( " " ); - html.WriteLine( "" ); - } - } - #endregion - - #region Speech - private static void DocumentKeywords() - { - List> tables = LoadSpeechFile(); - - using( StreamWriter html = GetWriter( "docs/", "keywords.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Speech Keywords" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "

Back to the index

" ); - html.WriteLine( "

Speech Keywords

" ); - - for( int p = 0; p < 1 && p < tables.Count; ++p ) - { - Dictionary table = tables[p]; - - if ( p > 0 ) - html.WriteLine( "
" ); - - html.WriteLine( " " ); - html.WriteLine( "
" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - - List list = new List( table.Values ); - list.Sort( new SpeechEntrySorter() ); - - for( int i = 0; i < list.Count; ++i ) - { - SpeechEntry entry = list[i]; - - html.Write( " " ); - } - - html.WriteLine( "
NumberText
0x{0:X4}", entry.Index ); - - entry.Strings.Sort();//( new EnglishPrioStringSorter() ); - - for( int j = 0; j < entry.Strings.Count; ++j ) - { - if ( j > 0 ) - html.Write( "
" ); - - string v = entry.Strings[j]; - - for( int k = 0; k < v.Length; ++k ) - { - char c = v[k]; - - if ( c == '<' ) - html.Write( "<" ); - else if ( c == '>' ) - html.Write( ">" ); - else if ( c == '&' ) - html.Write( "&" ); - else if ( c == '"' ) - html.Write( """ ); - else if ( c == '\'' ) - html.Write( "'" ); - else if ( c >= 0x20 && c < 0x7F ) - html.Write( c ); - else - html.Write( "&#{0};", (int)c ); - } - } - - html.WriteLine( "
" ); - } - - html.WriteLine( " " ); - html.WriteLine( "" ); - } - } - - private class SpeechEntry - { - public int Index { get; } - - public List Strings { get; } - - public SpeechEntry( int index ) - { - Index = index; - Strings = new List(); - } - } - - private class SpeechEntrySorter : IComparer - { - public int Compare( SpeechEntry x, SpeechEntry y ) - { - return x.Index.CompareTo( y.Index ); - } - } - - private static List> LoadSpeechFile() - { - List> tables = new List>(); - int lastIndex = -1; - - Dictionary table = null; - - string path = Core.FindDataFile( "speech.mul" ); - - if ( File.Exists( path ) ) - { - using( FileStream ip = new FileStream( path, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - BinaryReader bin = new BinaryReader( ip ); - - while( bin.PeekChar() >= 0 ) - { - int index = (bin.ReadByte() << 8) | bin.ReadByte(); - int length = (bin.ReadByte() << 8) | bin.ReadByte(); - string text = Encoding.UTF8.GetString( bin.ReadBytes( length ) ).Trim(); - - if ( text.Length == 0 ) - continue; - - if ( table == null || lastIndex > index ) - { - if ( index == 0 && text == "*withdraw*" ) - tables.Insert( 0, table = new Dictionary() ); - else - tables.Add( table = new Dictionary() ); - } + string nspace = type.Namespace; - lastIndex = index; + if (nspace == null || type.IsSpecialName) + continue; - table.TryGetValue( index, out SpeechEntry entry ); + TypeInfo info = new TypeInfo(type); + m_Types[type] = info; - if ( entry == null ) - table[index] = entry = new SpeechEntry( index ); - - entry.Strings.Add( text ); - } - } - } - - return tables; - } - #endregion - - #region Commands - - public class DocCommandEntry - { - public AccessLevel AccessLevel { get; } - - public string Name { get; } + m_Namespaces.TryGetValue(nspace, out List nspaces); - public string[] Aliases { get; } + if (nspaces == null) + m_Namespaces[nspace] = nspaces = new List(); - public string Usage { get; } + nspaces.Add(info); - public string Description { get; } + Type baseType = info.m_BaseType; - public DocCommandEntry( AccessLevel accessLevel, string name, string[] aliases, string usage, string description ) - { - AccessLevel = accessLevel; - Name = name; - Aliases = aliases; - Usage = usage; - Description = description; - } - } + if (baseType != null && InAssemblies(baseType, asms)) + { + m_Types.TryGetValue(baseType, out TypeInfo baseInfo); - public class CommandEntrySorter : IComparer - { - public int Compare( DocCommandEntry a, DocCommandEntry b ) - { - int v = b.AccessLevel.CompareTo( a.AccessLevel ); + if (baseInfo == null) + m_Types[baseType] = baseInfo = new TypeInfo(baseType); - if ( v == 0 ) - v = a.Name.CompareTo( b.Name ); + if (baseInfo.m_Derived == null) + baseInfo.m_Derived = new List(); - return v; - } - } + baseInfo.m_Derived.Add(info); + } - private static void DocumentCommands() - { - using( StreamWriter html = GetWriter( "docs/", "commands.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Commands" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "

Back to the index

" ); - html.WriteLine( "

Commands

" ); + Type decType = info.m_Declaring; - List commands = new List( CommandSystem.Entries.Values ); - List list = new List(); + if (decType != null) + { + m_Types.TryGetValue(decType, out TypeInfo decInfo); - commands.Sort(); - commands.Reverse(); - Clean( commands ); + if (decInfo == null) + m_Types[decType] = decInfo = new TypeInfo(decType); - for( int i = 0; i < commands.Count; ++i ) - { - CommandEntry e = commands[i]; + if (decInfo.m_Nested == null) + decInfo.m_Nested = new List(); + + decInfo.m_Nested.Add(info); + } - MethodInfo mi = e.Handler.Method; + for (int j = 0; j < info.m_Interfaces.Length; ++j) + { + Type iface = info.m_Interfaces[j]; - object[] attrs = mi.GetCustomAttributes( typeof( UsageAttribute ), false ); + if (!InAssemblies(iface, asms)) + continue; + + m_Types.TryGetValue(iface, out TypeInfo ifaceInfo); - if ( attrs.Length == 0 ) - continue; + if (ifaceInfo == null) + m_Types[iface] = ifaceInfo = new TypeInfo(iface); + + if (ifaceInfo.m_Derived == null) + ifaceInfo.m_Derived = new List(); - UsageAttribute usage = attrs[0] as UsageAttribute; + ifaceInfo.m_Derived.Add(info); + } + } + } - attrs = mi.GetCustomAttributes( typeof( DescriptionAttribute ), false ); + private static bool InAssemblies(Type t, Assembly[] asms) + { + Assembly a = t.Assembly; - if ( attrs.Length == 0 ) - continue; + for (int i = 0; i < asms.Length; ++i) + if (a == asms[i]) + return true; + + return false; + } + + private static void DocumentLoadedTypes() + { + using (StreamWriter indexHtml = GetWriter("docs/", "overview.html")) + { + indexHtml.WriteLine(""); + indexHtml.WriteLine(" "); + indexHtml.WriteLine(" RunUO Documentation - Class Overview"); + indexHtml.WriteLine(" "); + indexHtml.WriteLine( + " "); + indexHtml.WriteLine("

Back to the index

"); + indexHtml.WriteLine("

Namespaces

"); + + SortedList> nspaces = new SortedList>(m_Namespaces); + + foreach (KeyValuePair> kvp in nspaces) + { + kvp.Value.Sort(new TypeComparer()); + + SaveNamespace(kvp.Key, kvp.Value, indexHtml); + } + + indexHtml.WriteLine(" "); + indexHtml.WriteLine(""); + } + } + + private static void SaveNamespace(string name, List types, StreamWriter indexHtml) + { + string fileName = GetFileName("docs/namespaces/", name, ".html"); + + indexHtml.WriteLine(" {1}
", fileName, name); + + using (StreamWriter nsHtml = GetWriter("docs/namespaces/", fileName)) + { + nsHtml.WriteLine(""); + nsHtml.WriteLine(" "); + nsHtml.WriteLine(" RunUO Documentation - Class Overview - {0}", name); + nsHtml.WriteLine(" "); + nsHtml.WriteLine( + " "); + nsHtml.WriteLine("

Back to the namespace index

"); + nsHtml.WriteLine("

{0}

", name); + + for (int i = 0; i < types.Count; ++i) + SaveType(types[i], nsHtml, fileName, name); + + nsHtml.WriteLine(" "); + nsHtml.WriteLine(""); + } + } + + private static void SaveType(TypeInfo info, StreamWriter nsHtml, string nsFileName, string nsName) + { + if (info.m_Declaring == null) + nsHtml.WriteLine(" " + info.LinkName("../types/") + "
"); + + using (StreamWriter typeHtml = GetWriter(info.FileName)) + { + typeHtml.WriteLine(""); + typeHtml.WriteLine(" "); + typeHtml.WriteLine(" RunUO Documentation - Class Overview - {0}", info.TypeName); + typeHtml.WriteLine(" "); + typeHtml.WriteLine( + " "); + typeHtml.WriteLine("

Back to {1}

", nsFileName, nsName); + + if (info.m_Type.IsEnum) + WriteEnum(info, typeHtml); + else + WriteType(info, typeHtml); + + typeHtml.WriteLine(" "); + typeHtml.WriteLine(""); + } + } + + public static void FormatGeneric(Type type, ref string typeName, ref string fileName, ref string linkName) + { + string name = null; + string fnam = null; + string link = null; + + if (type.IsGenericType) + { + int index = type.Name.IndexOf('`'); + + if (index > 0) + { + string rootType = type.Name.Substring(0, index); + + StringBuilder nameBuilder = new StringBuilder(rootType); + StringBuilder fnamBuilder = new StringBuilder("docs/types/" + SanitizeType(rootType)); + StringBuilder linkBuilder; + if (DontLink(type)) //if ( DontLink( rootType ) ) + linkBuilder = new StringBuilder("" + rootType + ""); + else + linkBuilder = + new StringBuilder("" + rootType + ""); + + nameBuilder.Append("<"); + fnamBuilder.Append("-"); + linkBuilder.Append("<"); + + Type[] typeArguments = type.GetGenericArguments(); + + for (int i = 0; i < typeArguments.Length; i++) + { + if (i != 0) + { + nameBuilder.Append(','); + fnamBuilder.Append(','); + linkBuilder.Append(','); + } + + string sanitizedName = SanitizeType(typeArguments[i].Name); + string aliasedName = AliasForName(sanitizedName); + + nameBuilder.Append(sanitizedName); + fnamBuilder.Append("T"); + if (DontLink(typeArguments[i])) //if ( DontLink( typeArguments[i].Name ) ) + linkBuilder.Append("" + aliasedName + ""); + else + linkBuilder.Append( + "" + aliasedName + ""); + } + + nameBuilder.Append(">"); + fnamBuilder.Append("-"); + linkBuilder.Append(">"); + + name = nameBuilder.ToString(); + fnam = fnamBuilder.ToString(); + link = linkBuilder.ToString(); + } + } + + if (name == null) typeName = type.Name; + else typeName = name; + + if (fnam == null) fileName = "docs/types/" + SanitizeType(type.Name) + ".html"; + else fileName = fnam + ".html"; + + if (link == null) + { + if (DontLink(type)) //if ( DontLink( type.Name ) ) + linkName = "" + SanitizeType(type.Name) + ""; + else + linkName = "" + + SanitizeType(type.Name) + ""; + } + else + { + linkName = link; + } + + //Console.WriteLine( typeName+":"+fileName+":"+linkName ); + } + + public static string SanitizeType(string name) + { + bool anonymousType = name.Contains("<"); + StringBuilder sb = new StringBuilder(name); + for (int i = 0; i < ReplaceChars.Length; ++i) sb.Replace(ReplaceChars[i], '-'); + + if (anonymousType) return "(Anonymous-Type)" + sb; + return sb.ToString(); + } + + public static string AliasForName(string name) + { + for (int i = 0; i < m_AliasLength; ++i) + if (m_Aliases[i, 0] == name) + return m_Aliases[i, 1]; + return name; + } + + /* + // For stuff we don't want to links to + private static string[] m_DontLink = new string[] + { + "List", + "Stack", + "Queue", + "Dictionary", + "LinkedList", + "SortedList", + "SortedDictionary", + "IComparable", + "IComparer", + "ICloneable", + "Type" + }; + + public static bool DontLink( string name ) + { + foreach( string dontLink in m_DontLink ) + if ( dontLink == name ) return true; + return false; + } + */ + public static bool DontLink(Type type) + { + // MONO: type.Namespace is null/empty for generic arguments + + if (type.Name == "T" || string.IsNullOrEmpty(type.Namespace) || m_Namespaces == null) + return true; + + if (type.Namespace.StartsWith("Server")) + return false; + + return !m_Namespaces.ContainsKey(type.Namespace); + } + + private class MemberComparer : IComparer + { + public int Compare(object x, object y) + { + if (x == y) + return 0; + + ConstructorInfo aCtor = x as ConstructorInfo; + ConstructorInfo bCtor = y as ConstructorInfo; + + PropertyInfo aProp = x as PropertyInfo; + PropertyInfo bProp = y as PropertyInfo; + + MethodInfo aMethod = x as MethodInfo; + MethodInfo bMethod = y as MethodInfo; + + bool aStatic = GetStaticFor(aCtor, aProp, aMethod); + bool bStatic = GetStaticFor(bCtor, bProp, bMethod); + + if (aStatic && !bStatic) + return -1; + if (!aStatic && bStatic) + return 1; + + int v = 0; + + if (aCtor != null) + { + if (bCtor == null) + v = -1; + } + else if (bCtor != null) + { + v = 1; + } + else if (aProp != null) + { + if (bProp == null) + v = -1; + } + else if (bProp != null) + { + v = 1; + } + + if (v == 0) v = GetNameFrom(aCtor, aProp, aMethod).CompareTo(GetNameFrom(bCtor, bProp, bMethod)); + + if (v == 0 && aCtor != null && bCtor != null) + v = aCtor.GetParameters().Length.CompareTo(bCtor.GetParameters().Length); + else if (v == 0 && aMethod != null && bMethod != null) + v = aMethod.GetParameters().Length.CompareTo(bMethod.GetParameters().Length); + + return v; + } + + private bool GetStaticFor(ConstructorInfo ctor, PropertyInfo prop, MethodInfo method) + { + if (ctor != null) + return ctor.IsStatic; + if (method != null) + return method.IsStatic; + + if (prop != null) + { + MethodInfo getMethod = prop.GetGetMethod(); + MethodInfo setMethod = prop.GetGetMethod(); + + return getMethod != null && getMethod.IsStatic || setMethod != null && setMethod.IsStatic; + } + + return false; + } + + private string GetNameFrom(ConstructorInfo ctor, PropertyInfo prop, MethodInfo method) + { + if (ctor != null) + return ctor.DeclaringType?.Name ?? ""; + if (prop != null) + return prop.Name; + if (method != null) + return method.Name; + return ""; + } + } + + private class TypeComparer : IComparer + { + public int Compare(TypeInfo x, TypeInfo y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + return x.TypeName.CompareTo(y.TypeName); + } + } + + private class TypeInfo + { + public List m_Derived, m_Nested; + private string m_FileName, m_TypeName, m_LinkName; + public Type[] m_Interfaces; + public Type m_Type, m_BaseType, m_Declaring; + + public TypeInfo(Type type) + { + m_Type = type; + + m_BaseType = type.BaseType; + m_Declaring = type.DeclaringType; + m_Interfaces = type.GetInterfaces(); + + FormatGeneric(m_Type, ref m_TypeName, ref m_FileName, ref m_LinkName); + + // Console.WriteLine( ">> inline typeinfo: "+m_TypeName ); + // m_TypeName = GetGenericTypeName( m_Type ); + // m_FileName = Docs.GetFileName( "docs/types/", GetGenericTypeName( m_Type, "-", "-" ), ".html" ); + // m_Writer = Docs.GetWriter( "docs/types/", m_FileName ); + } + + public string FileName => m_FileName; + public string TypeName => m_TypeName; + + public string LinkName(string dirRoot) + { + return m_LinkName.Replace("@directory@", dirRoot); + } + } + + #region FileSystem + + private static readonly char[] ReplaceChars = "<>".ToCharArray(); + + public static string GetFileName(string root, string name, string ext) + { + if (name.IndexOfAny(ReplaceChars) >= 0) + { + StringBuilder sb = new StringBuilder(name); + + for (int i = 0; i < ReplaceChars.Length; ++i) sb.Replace(ReplaceChars[i], '-'); + + name = sb.ToString(); + } + + int index = 0; + string file = string.Concat(name, ext); + + while (File.Exists(Path.Combine(root, file))) file = string.Concat(name, ++index, ext); + + return file; + } + + private static string m_RootDirectory = Path.GetDirectoryName(Environment.GetCommandLineArgs()[0]); + + private static void EnsureDirectory(string path) + { + path = Path.Combine(m_RootDirectory, path); + + if (!Directory.Exists(path)) + Directory.CreateDirectory(path); + } + + private static void DeleteDirectory(string path) + { + path = Path.Combine(m_RootDirectory, path); + + if (Directory.Exists(path)) + Directory.Delete(path, true); + } + + private static StreamWriter GetWriter(string root, string name) + { + return new StreamWriter(Path.Combine(Path.Combine(m_RootDirectory, root), name)); + } + + private static StreamWriter GetWriter(string path) + { + return new StreamWriter(Path.Combine(m_RootDirectory, path)); + } + + #endregion + + #region GetPair + + private static string[,] m_Aliases = + { + { "System.Object", "object" }, + { "System.String", "string" }, + { "System.Boolean", "bool" }, + { "System.Byte", "byte" }, + { "System.SByte", "sbyte" }, + { "System.Int16", "short" }, + { "System.UInt16", "ushort" }, + { "System.Int32", "int" }, + { "System.UInt32", "uint" }, + { "System.Int64", "long" }, + { "System.UInt64", "ulong" }, + { "System.Single", "float" }, + { "System.Double", "double" }, + { "System.Decimal", "decimal" }, + { "System.Char", "char" }, + { "System.Void", "void" } + }; + + private static int m_AliasLength = m_Aliases.GetLength(0); + + public static string GetPair(Type varType, string name, bool ignoreRef) + { + string prepend = ""; + StringBuilder append = new StringBuilder(); + + Type realType = varType; + + if (varType.IsByRef) + { + if (!ignoreRef) + prepend = RefString; + + realType = varType.GetElementType(); + } + + if (realType?.IsPointer == true) + { + if (realType.IsArray) + { + append.Append('*'); + + do + { + append.Append('['); + + for (int i = 1; i < realType.GetArrayRank(); ++i) + append.Append(','); + + append.Append(']'); + + realType = realType.GetElementType(); + } while (realType?.IsArray == true); + + append.Append(' '); + } + else + { + realType = realType.GetElementType(); + append.Append(" *"); + } + } + else if (realType.IsArray) + { + do + { + append.Append('['); + + for (int i = 1; i < realType.GetArrayRank(); ++i) + append.Append(','); + + append.Append(']'); + + realType = realType.GetElementType(); + } while (realType?.IsArray == true); + + append.Append(' '); + } + else + { + append.Append(' '); + } + + string fullName = realType?.FullName ?? "(-null-)"; + string aliased = null; // = realType.Name; + + TypeInfo info = null; + + if (realType != null) + { + m_Types.TryGetValue(realType, out info); + } + + if (info != null) + { + aliased = "" + info.LinkName(null); + //aliased = String.Format( "{1}", info.m_FileName, info.m_TypeName ); + } + else + { + //FormatGeneric( ); + if (realType?.IsGenericType == true) + { + string typeName = ""; + string fileName = ""; + string linkName = ""; + + FormatGeneric(realType, ref typeName, ref fileName, ref linkName); + linkName = linkName.Replace("@directory@", null); + aliased = linkName; + } + else + { + for (int i = 0; i < m_AliasLength; ++i) + if (m_Aliases[i, 0] == fullName) + { + aliased = m_Aliases[i, 1]; + break; + } + } + + if (aliased == null) + aliased = realType?.Name ?? ""; + } + + return string.Concat(prepend, aliased, append, name); + } + + #endregion + + #region Root documentation + + private static bool Document() + { + try + { + DeleteDirectory("docs/"); + } + catch + { + return false; + } + + EnsureDirectory("docs/"); + EnsureDirectory("docs/namespaces/"); + EnsureDirectory("docs/types/"); + EnsureDirectory("docs/bods/"); + + GenerateStyles(); + GenerateIndex(); + + DocumentCommands(); + DocumentKeywords(); + DocumentBodies(); + + DocumentBulkOrders(); + + m_Types = new Dictionary(); + m_Namespaces = new Dictionary>(); + + List assemblies = new List(); + + assemblies.Add(Core.Assembly); + + foreach (Assembly asm in ScriptCompiler.Assemblies) + assemblies.Add(asm); + + Assembly[] asms = assemblies.ToArray(); + + for (int i = 0; i < asms.Length; ++i) + LoadTypes(asms[i], asms); + + DocumentLoadedTypes(); + DocumentConstructibleObjects(); + + return true; + } + + private static void AddIndexLink(StreamWriter html, string filePath, string label, string desc) + { + html.WriteLine("

{2}

", filePath, desc, label); + } + + private static void GenerateStyles() + { + using (StreamWriter css = GetWriter("docs/", "styles.css")) + { + css.WriteLine("body { background-color: #FFFFFF; font-family: verdana, arial; font-size: 11px; }"); + css.WriteLine("a { color: #28435E; }"); + css.WriteLine("a:hover { color: #4878A9; }"); + css.WriteLine("td.header { background-color: #9696AA; font-weight: bold; font-size: 12px; }"); + css.WriteLine("td.lentry { background-color: #D7D7EB; width: 10%; }"); + css.WriteLine("td.rentry { background-color: #FFFFFF; width: 90%; }"); + css.WriteLine("td.entry { background-color: #FFFFFF; }"); + css.WriteLine("td { font-size: 11px; }"); + css.WriteLine(".tbl-border { background-color: #46465A; }"); + + css.WriteLine("td.ir {{ background-color: #{0:X6}; }}", Iron); + css.WriteLine("td.du {{ background-color: #{0:X6}; }}", DullCopper); + css.WriteLine("td.sh {{ background-color: #{0:X6}; }}", ShadowIron); + css.WriteLine("td.co {{ background-color: #{0:X6}; }}", Copper); + css.WriteLine("td.br {{ background-color: #{0:X6}; }}", Bronze); + css.WriteLine("td.go {{ background-color: #{0:X6}; }}", Gold); + css.WriteLine("td.ag {{ background-color: #{0:X6}; }}", Agapite); + css.WriteLine("td.ve {{ background-color: #{0:X6}; }}", Verite); + css.WriteLine("td.va {{ background-color: #{0:X6}; }}", Valorite); + + css.WriteLine("td.cl {{ background-color: #{0:X6}; }}", Cloth); + css.WriteLine("td.pl {{ background-color: #{0:X6}; }}", Plain); + css.WriteLine("td.sp {{ background-color: #{0:X6}; }}", Core.AOS ? SpinedAOS : SpinedLBR); + css.WriteLine("td.ho {{ background-color: #{0:X6}; }}", Core.AOS ? HornedAOS : HornedLBR); + css.WriteLine("td.ba {{ background-color: #{0:X6}; }}", Core.AOS ? BarbedAOS : BarbedLBR); + } + } + + private static void GenerateIndex() + { + using (StreamWriter html = GetWriter("docs/", "index.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Index"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + + AddIndexLink(html, "commands.html", "Commands", + "Every available command. This contains command name, usage, aliases, and description."); + AddIndexLink(html, "objects.html", "Constructible Objects", + "Every constructable item or npc. This contains object name and usage. Hover mouse over parameters to see type description."); + AddIndexLink(html, "keywords.html", "Speech Keywords", + "Lists speech keyword numbers and associated match patterns. These are used in some scripts for multi-language matching of client speech."); + AddIndexLink(html, "bodies.html", "Body List", + "Every usable body number and name. Table is generated from a UO:3D client datafile. If you do not have UO:3D installed, this may be blank."); + AddIndexLink(html, "overview.html", "Class Overview", + "Scripting reference. Contains every class type and contained methods in the core and scripts."); + AddIndexLink(html, "bods/bod_smith_rewards.html", "Bulk Order Rewards: Smithing", + "Reference table for large and small smithing bulk order deed rewards."); + AddIndexLink(html, "bods/bod_tailor_rewards.html", "Bulk Order Rewards: Tailoring", + "Reference table for large and small tailoring bulk order deed rewards."); + + html.WriteLine(" "); + html.WriteLine(""); + } + } + + #endregion + + #region BODs + + private const int Iron = 0xCCCCDD; + private const int DullCopper = 0xAAAAAA; + private const int ShadowIron = 0x777799; + private const int Copper = 0xDDCC99; + private const int Bronze = 0xAA8866; + private const int Gold = 0xDDCC55; + private const int Agapite = 0xDDAAAA; + private const int Verite = 0x99CC77; + private const int Valorite = 0x88AABB; + + private const int Cloth = 0xDDDDDD; + private const int Plain = 0xCCAA88; + private const int SpinedAOS = 0x99BBBB; + private const int HornedAOS = 0xCC8888; + private const int BarbedAOS = 0xAABBAA; + private const int SpinedLBR = 0xAA8833; + private const int HornedLBR = 0xBBBBAA; + private const int BarbedLBR = 0xCCAA88; + + private static void DocumentBulkOrders() + { + using (StreamWriter html = GetWriter("docs/bods/", "bod_smith_rewards.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Bulk Orders - Smith Rewards"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + + SmallBOD sbod = new SmallSmithBOD(); + + sbod.Type = typeof(Katana); + sbod.Material = BulkMaterialType.None; + sbod.AmountMax = 10; + + WriteSmithBODHeader(html, "(Small) Weapons"); + sbod.RequireExceptional = false; + DocumentSmithBOD(html, sbod.ComputeRewards(true), "10, 15, 20: Normal", sbod.Material); + sbod.RequireExceptional = true; + DocumentSmithBOD(html, sbod.ComputeRewards(true), "10, 15, 20: Exceptional", sbod.Material); + WriteSmithBODFooter(html); + + html.WriteLine("

"); + html.WriteLine("

"); + + + sbod.Type = typeof(PlateArms); + + WriteSmithBODHeader(html, "(Small) Armor: Normal"); + + sbod.RequireExceptional = false; + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat) + { + sbod.Material = mat; + sbod.AmountMax = 10; + DocumentSmithBOD(html, sbod.ComputeRewards(true), "10, 15, 20", sbod.Material); + } + + WriteSmithBODFooter(html); + + html.WriteLine("

"); + + WriteSmithBODHeader(html, "(Small) Armor: Exceptional"); + + sbod.RequireExceptional = true; + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat) + { + sbod.Material = mat; + + for (int amt = 15; amt <= 20; amt += 5) + { + sbod.AmountMax = amt; + DocumentSmithBOD(html, sbod.ComputeRewards(true), amt == 20 ? "20" : "10, 15", sbod.Material); + } + } + + WriteSmithBODFooter(html); + + html.WriteLine("

"); + html.WriteLine("

"); + + sbod.Delete(); + + WriteSmithLBOD(html, "Ringmail", LargeBulkEntry.LargeRing); + WriteSmithLBOD(html, "Chainmail", LargeBulkEntry.LargeChain); + WriteSmithLBOD(html, "Platemail", LargeBulkEntry.LargePlate); + + html.WriteLine(" "); + html.WriteLine(""); + } + + using (StreamWriter html = GetWriter("docs/bods/", "bod_tailor_rewards.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Bulk Orders - Tailor Rewards"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + + SmallBOD sbod = new SmallTailorBOD(); + + WriteTailorBODHeader(html, "Small Bulk Order"); + + html.WriteLine("
Regular: 10, 15
Regular: 20
Exceptional: 10, 15
Exceptional: 20
Regular
Exceptional
"); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" ", title); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + } + + private static void WriteTailorBODFooter(StreamWriter html) + { + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine("
{0}
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
Power Scrolls
\"Small
\"Medium
\"Light
\"Dark
\"Brown
\"Polar
\"Clothing
Runic Kits
+5
+10
+15
+20
\"Runic
\"Runic
\"Runic
 
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
\"Colored
+5
+10
+15
+20
\"Small
\"Medium
\"Light
\"Dark
\"Brown
\"Polar
\"Clothing
\"Runic
\"Runic
\"Runic
Power Scrolls
Runic Kits
"); + } + + private static void DocumentTailorBOD(StreamWriter html, List items, string amt, BulkMaterialType material, + Type type) + { + bool[] rewards = new bool[20]; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (item is Sandals) + { + rewards[5] = true; + } + else if (item is SmallStretchedHideEastDeed || item is SmallStretchedHideSouthDeed) + { + rewards[10] = rewards[11] = true; + } + else if (item is MediumStretchedHideEastDeed || item is MediumStretchedHideSouthDeed) + { + rewards[10] = rewards[11] = true; + } + else if (item is LightFlowerTapestryEastDeed || item is LightFlowerTapestrySouthDeed) + { + rewards[12] = rewards[13] = true; + } + else if (item is DarkFlowerTapestryEastDeed || item is DarkFlowerTapestrySouthDeed) + { + rewards[12] = rewards[13] = true; + } + else if (item is BrownBearRugEastDeed || item is BrownBearRugSouthDeed) + { + rewards[14] = rewards[15] = true; + } + else if (item is PolarBearRugEastDeed || item is PolarBearRugSouthDeed) + { + rewards[14] = rewards[15] = true; + } + else if (item is ClothingBlessDeed) + { + rewards[16] = true; + } + else if (item is PowerScroll ps) + { + if (ps.Value == 105.0) + rewards[6] = true; + else if (ps.Value == 110.0) + rewards[7] = true; + else if (ps.Value == 115.0) + rewards[8] = true; + else if (ps.Value == 120.0) + rewards[9] = true; + } + else if (item is UncutCloth) + { + if (item.Hue == 0x483 || item.Hue == 0x48C || item.Hue == 0x488 || item.Hue == 0x48A) + rewards[0] = true; + else if (item.Hue == 0x495 || item.Hue == 0x48B || item.Hue == 0x486 || item.Hue == 0x485) + rewards[1] = true; + else if (item.Hue == 0x48D || item.Hue == 0x490 || item.Hue == 0x48E || item.Hue == 0x491) + rewards[2] = true; + else if (item.Hue == 0x48F || item.Hue == 0x494 || item.Hue == 0x484 || item.Hue == 0x497) + rewards[3] = true; + else + rewards[4] = true; + } + else if (item is RunicSewingKit rkit) + { + rewards[16 + CraftResources.GetIndex(rkit.Resource)] = true; + } + + item.Delete(); + } + + string style = null; + string name = null; + + switch (material) + { + case BulkMaterialType.None: + { + if (type.IsSubclassOf(typeof(BaseArmor)) || type.IsSubclassOf(typeof(BaseShoes))) + { + style = "pl"; + name = "Plain"; + } + else + { + style = "cl"; + name = "Cloth"; + } + + break; + } + case BulkMaterialType.Spined: + style = "sp"; + name = "Spined"; + break; + case BulkMaterialType.Horned: + style = "ho"; + name = "Horned"; + break; + case BulkMaterialType.Barbed: + style = "ba"; + name = "Barbed"; + break; + } + + html.WriteLine(" "); + html.WriteLine("  - {0} {1}", + name, amt); + + int index = 0; + + while (index < 20) + if (rewards[index]) + { + html.WriteLine("
X
", style); + ++index; + } + else + { + int count = 0; + + while (index < 20 && !rewards[index]) + { + ++count; + ++index; + + if (index == 5 || index == 6 || index == 10 || index == 17) + break; + } + + html.WriteLine("  ", count * 25, + count == 1 ? "" : $" colspan=\"{count}\""); + } + + html.WriteLine(" "); + } + + #endregion + + #region Smith Bods + + private static void WriteSmithLBOD(StreamWriter html, string name, SmallBulkEntry[] entries) + { + LargeBOD lbod = new LargeSmithBOD(); + + lbod.Entries = LargeBulkEntry.ConvertEntries(lbod, entries); + + WriteSmithBODHeader(html, $"(Large) {name}: Normal"); + + lbod.RequireExceptional = false; + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat) + { + lbod.Material = mat; + lbod.AmountMax = 10; + DocumentSmithBOD(html, lbod.ComputeRewards(true), "10, 15, 20", lbod.Material); + } + + WriteSmithBODFooter(html); + + html.WriteLine("

"); + + WriteSmithBODHeader(html, $"(Large) {name}: Exceptional"); + + lbod.RequireExceptional = true; + for (BulkMaterialType mat = BulkMaterialType.None; mat <= BulkMaterialType.Valorite; ++mat) + { + lbod.Material = mat; + + for (int amt = 15; amt <= 20; amt += 5) + { + lbod.AmountMax = amt; + DocumentSmithBOD(html, lbod.ComputeRewards(true), amt == 20 ? "20" : "10, 15", lbod.Material); + } + } + + WriteSmithBODFooter(html); + + html.WriteLine("

"); + html.WriteLine("

"); + } + + private static void WriteSmithBODHeader(StreamWriter html, string title) + { + html.WriteLine(" "); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" ", title); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + } + + private static void WriteSmithBODFooter(StreamWriter html) + { + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine( + " "); + html.WriteLine(" "); + html.WriteLine("
{0}
\"Sturdy
Gloves
\"Gargoyles
\"Prospectors
\"Powder
\"Colored
Power Scrolls
Runic Hammers
Ancient Hammers
+1
+3
+5
+5
+10
+15
+20
Du
Sh
Co
Br
Go
Ag
Ve
Va
+10
+15
+30
+60
 
\"Sturdy
+1
 
+3
 
+5
 
\"Gargoyles
\"Prospectors
\"Powder
\"Colored
+5
+10
+15
+20
Du
Sh
Co
Br
Go
Ag
Ve
Va
+10
+15
+30
+60
Gloves
Power Scrolls
Runic Hammers
Ancient Hammers
"); + } + + private static void DocumentSmithBOD(StreamWriter html, List items, string amt, BulkMaterialType material) + { + bool[] rewards = new bool[24]; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (item is SturdyPickaxe || item is SturdyShovel) + { + rewards[0] = true; + } + else if (item is LeatherGlovesOfMining) + { + rewards[1] = true; + } + else if (item is StuddedGlovesOfMining) + { + rewards[2] = true; + } + else if (item is RingmailGlovesOfMining) + { + rewards[3] = true; + } + else if (item is GargoylesPickaxe) + { + rewards[4] = true; + } + else if (item is ProspectorsTool) + { + rewards[5] = true; + } + else if (item is PowderOfTemperament) + { + rewards[6] = true; + } + else if (item is ColoredAnvil) + { + rewards[7] = true; + } + else if (item is PowerScroll ps) + { + if (ps.Value == 105.0) + rewards[8] = true; + else if (ps.Value == 110.0) + rewards[9] = true; + else if (ps.Value == 115.0) + rewards[10] = true; + else if (ps.Value == 120.0) + rewards[11] = true; + } + else if (item is RunicHammer rh) + { + rewards[11 + CraftResources.GetIndex(rh.Resource)] = true; + } + else if (item is AncientSmithyHammer ash) + { + if (ash.Bonus == 10) + rewards[20] = true; + else if (ash.Bonus == 15) + rewards[21] = true; + else if (ash.Bonus == 30) + rewards[22] = true; + else if (ash.Bonus == 60) + rewards[23] = true; + } + + item.Delete(); + } + + string style = null; + string name = null; + + switch (material) + { + case BulkMaterialType.None: + style = "ir"; + name = "Iron"; + break; + case BulkMaterialType.DullCopper: + style = "du"; + name = "Dull Copper"; + break; + case BulkMaterialType.ShadowIron: + style = "sh"; + name = "Shadow Iron"; + break; + case BulkMaterialType.Copper: + style = "co"; + name = "Copper"; + break; + case BulkMaterialType.Bronze: + style = "br"; + name = "Bronze"; + break; + case BulkMaterialType.Gold: + style = "go"; + name = "Gold"; + break; + case BulkMaterialType.Agapite: + style = "ag"; + name = "Agapite"; + break; + case BulkMaterialType.Verite: + style = "ve"; + name = "Verite"; + break; + case BulkMaterialType.Valorite: + style = "va"; + name = "Valorite"; + break; + } + + html.WriteLine(" "); + html.WriteLine(" {0} {1}", name, + amt); + + int index = 0; + + while (index < 24) + if (rewards[index]) + { + html.WriteLine("
X
", style); + ++index; + } + else + { + int count = 0; + + while (index < 24 && !rewards[index]) + { + ++count; + ++index; + + if (index == 4 || index == 8 || index == 12 || index == 20) + break; + } + + html.WriteLine("  ", count * 25, + count == 1 ? "" : $" colspan=\"{count}\""); + } + + html.WriteLine(" "); + } + + #endregion + + #endregion + + #region Bodies + + public static List LoadBodies() + { + List list = new List(); + + string path = Core.FindDataFile("models/models.txt"); + + if (File.Exists(path)) + using (StreamReader ip = new StreamReader(path)) + { + string line; + + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); + + if (line.Length == 0 || line.StartsWith("#")) + continue; + + string[] split = line.Split('\t'); + + if (split.Length >= 9) + { + Body body = Utility.ToInt32(split[0]); + ModelBodyType type = (ModelBodyType)Utility.ToInt32(split[1]); + string name = split[8]; + + BodyEntry entry = new BodyEntry(body, type, name); + + if (!list.Contains(entry)) + list.Add(entry); + } + } + } + + return list; + } + + private static void DocumentBodies() + { + List list = LoadBodies(); + + using (StreamWriter html = GetWriter("docs/", "bodies.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Body List"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine("

Back to the index

"); + + if (list.Count > 0) + { + html.WriteLine("

Body List

"); + + list.Sort(new BodyEntrySorter()); + + ModelBodyType lastType = ModelBodyType.Invalid; + + for (int i = 0; i < list.Count; ++i) + { + BodyEntry entry = list[i]; + ModelBodyType type = entry.BodyType; + + if (type != lastType) + { + if (lastType != ModelBodyType.Invalid) + html.WriteLine("
"); + + lastType = type; + + html.WriteLine(" ", type); + + switch (type) + { + case ModelBodyType.Monsters: + html.WriteLine( + " Monsters | Sea | Animals | Human | Equipment

"); + break; + case ModelBodyType.Sea: + html.WriteLine( + " Monsters | Sea | Animals | Human | Equipment

"); + break; + case ModelBodyType.Animals: + html.WriteLine( + " Monsters | Sea | Animals | Human | Equipment

"); + break; + case ModelBodyType.Human: + html.WriteLine( + " Monsters | Sea | Animals | Human | Equipment

"); + break; + case ModelBodyType.Equipment: + html.WriteLine( + " Monsters | Sea | Animals | Human | Equipment

"); + break; + } + + html.WriteLine(" "); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" ", + type); + } + + html.WriteLine(" ", + entry.Body.BodyID, entry.Name); + } + + html.WriteLine("
{0}
{0}{1}
"); + } + else + { + html.WriteLine(" This feature requires a UO:3D installation."); + } + + html.WriteLine(" "); + html.WriteLine(""); + } + } + + #endregion + + #region Speech + + private static void DocumentKeywords() + { + List> tables = LoadSpeechFile(); + + using (StreamWriter html = GetWriter("docs/", "keywords.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Speech Keywords"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine("

Back to the index

"); + html.WriteLine("

Speech Keywords

"); + + for (int p = 0; p < 1 && p < tables.Count; ++p) + { + Dictionary table = tables[p]; + + if (p > 0) + html.WriteLine("
"); + + html.WriteLine(" "); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" "); + + List list = new List(table.Values); + list.Sort(new SpeechEntrySorter()); + + for (int i = 0; i < list.Count; ++i) + { + SpeechEntry entry = list[i]; + + html.Write(" "); + } + + html.WriteLine("
NumberText
0x{0:X4}", entry.Index); + + entry.Strings.Sort(); //( new EnglishPrioStringSorter() ); + + for (int j = 0; j < entry.Strings.Count; ++j) + { + if (j > 0) + html.Write("
"); + + string v = entry.Strings[j]; + + for (int k = 0; k < v.Length; ++k) + { + char c = v[k]; + + if (c == '<') + html.Write("<"); + else if (c == '>') + html.Write(">"); + else if (c == '&') + html.Write("&"); + else if (c == '"') + html.Write("""); + else if (c == '\'') + html.Write("'"); + else if (c >= 0x20 && c < 0x7F) + html.Write(c); + else + html.Write("&#{0};", (int)c); + } + } + + html.WriteLine("
"); + } + + html.WriteLine(" "); + html.WriteLine(""); + } + } + + private class SpeechEntry + { + public SpeechEntry(int index) + { + Index = index; + Strings = new List(); + } + + public int Index{ get; } + + public List Strings{ get; } + } + + private class SpeechEntrySorter : IComparer + { + public int Compare(SpeechEntry x, SpeechEntry y) + { + return x.Index.CompareTo(y.Index); + } + } + + private static List> LoadSpeechFile() + { + List> tables = new List>(); + int lastIndex = -1; + + Dictionary table = null; + + string path = Core.FindDataFile("speech.mul"); + + if (File.Exists(path)) + using (FileStream ip = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader bin = new BinaryReader(ip); + + while (bin.PeekChar() >= 0) + { + int index = (bin.ReadByte() << 8) | bin.ReadByte(); + int length = (bin.ReadByte() << 8) | bin.ReadByte(); + string text = Encoding.UTF8.GetString(bin.ReadBytes(length)).Trim(); - sb.Append( "Modifiers: " ); + if (text.Length == 0) + continue; - if ( (command.Supports & CommandSupport.Global) != 0 ) - sb.Append( "Global, " ); + if (table == null || lastIndex > index) + { + if (index == 0 && text == "*withdraw*") + tables.Insert(0, table = new Dictionary()); + else + tables.Add(table = new Dictionary()); + } - if ( (command.Supports & CommandSupport.Online) != 0 ) - sb.Append( "Online, " ); + lastIndex = index; - if ( (command.Supports & CommandSupport.Region) != 0 ) - sb.Append( "Region, " ); + table.TryGetValue(index, out SpeechEntry entry); - if ( (command.Supports & CommandSupport.Contained) != 0 ) - sb.Append( "Contained, " ); + if (entry == null) + table[index] = entry = new SpeechEntry(index); - if ( (command.Supports & CommandSupport.Multi) != 0 ) - sb.Append( "Multi, " ); + entry.Strings.Add(text); + } + } - if ( (command.Supports & CommandSupport.Area) != 0 ) - sb.Append( "Area, " ); + return tables; + } - if ( (command.Supports & CommandSupport.Self) != 0 ) - sb.Append( "Self, " ); + #endregion - sb.Remove( sb.Length - 2, 2 ); - sb.Append( "
" ); - sb.Append( desc ); + #region Commands - desc = sb.ToString(); - } + public class DocCommandEntry + { + public DocCommandEntry(AccessLevel accessLevel, string name, string[] aliases, string usage, string description) + { + AccessLevel = accessLevel; + Name = name; + Aliases = aliases; + Usage = usage; + Description = description; + } - list.Add( new DocCommandEntry( command.AccessLevel, cmd, aliases, usage, desc ) ); - } + public AccessLevel AccessLevel{ get; } - List commandImpls = BaseCommandImplementor.Implementors; + public string Name{ get; } - for( int i = 0; i < commandImpls.Count; ++i ) - { - BaseCommandImplementor command = commandImpls[i]; + public string[] Aliases{ get; } - string usage = command.Usage; - string desc = command.Description; + public string Usage{ get; } - if ( usage == null || desc == null ) - continue; + public string Description{ get; } + } - string[] cmds = command.Accessors; - string cmd = cmds[0]; - string[] aliases = new string[cmds.Length - 1]; + public class CommandEntrySorter : IComparer + { + public int Compare(DocCommandEntry a, DocCommandEntry b) + { + int v = b.AccessLevel.CompareTo(a.AccessLevel); - for( int j = 0; j < aliases.Length; ++j ) - aliases[j] = cmds[j + 1]; + if (v == 0) + v = a.Name.CompareTo(b.Name); - desc = desc.Replace( "<", "<" ).Replace( ">", ">" ); + return v; + } + } - list.Add( new DocCommandEntry( command.AccessLevel, cmd, aliases, usage, desc ) ); - } + private static void DocumentCommands() + { + using (StreamWriter html = GetWriter("docs/", "commands.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Commands"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine("

Back to the index

"); + html.WriteLine("

Commands

"); - list.Sort( new CommandEntrySorter() ); + List commands = new List(CommandSystem.Entries.Values); + List list = new List(); - AccessLevel last = AccessLevel.Player; + commands.Sort(); + commands.Reverse(); + Clean(commands); - foreach( DocCommandEntry e in list ) - { - if ( e.AccessLevel != last ) - { - if ( last != AccessLevel.Player ) - html.WriteLine( "

" ); + for (int i = 0; i < commands.Count; ++i) + { + CommandEntry e = commands[i]; - last = e.AccessLevel; + MethodInfo mi = e.Handler.Method; - html.WriteLine( " ", last ); + object[] attrs = mi.GetCustomAttributes(typeof(UsageAttribute), false); - switch( last ) - { - case AccessLevel.Administrator: html.WriteLine( " Administrator | Game Master | Counselor | Player

" ); break; - case AccessLevel.GameMaster: html.WriteLine( " Administrator | Game Master | Counselor | Player

" ); break; - case AccessLevel.Seer: html.WriteLine( " Administrator | Game Master | Counselor | Player

" ); break; - case AccessLevel.Counselor: html.WriteLine( " Administrator | Game Master | Counselor | Player

" ); break; - case AccessLevel.Player: html.WriteLine( " Administrator | Game Master | Counselor | Player

" ); break; - } + if (attrs.Length == 0) + continue; - html.WriteLine( " " ); - html.WriteLine( "
" ); - html.WriteLine( " " ); - html.WriteLine( " ", last == AccessLevel.GameMaster ? "Game Master" : last.ToString() ); - } + UsageAttribute usage = attrs[0] as UsageAttribute; - DocumentCommand( html, e ); - } + attrs = mi.GetCustomAttributes(typeof(DescriptionAttribute), false); - html.WriteLine( "
{0}
" ); - html.WriteLine( " " ); - html.WriteLine( "" ); - } - } + if (attrs.Length == 0) + continue; - public static void Clean( List list ) - { - for( int i = 0; i < list.Count; ++i ) - { - CommandEntry e = list[i]; + if (usage == null || !(attrs[0] is DescriptionAttribute desc)) + continue; - for( int j = i + 1; j < list.Count; ++j ) - { - CommandEntry c = list[j]; + attrs = mi.GetCustomAttributes(typeof(AliasesAttribute), false); - if ( e.Handler.Method == c.Handler.Method ) - { - list.RemoveAt( j ); - --j; - } - } - } - } + AliasesAttribute aliases = attrs.Length == 0 ? null : attrs[0] as AliasesAttribute; - private static void DocumentCommand( StreamWriter html, DocCommandEntry e ) - { - string usage = e.Usage; - string desc = e.Description; - string[] aliases = e.Aliases; + string descString = desc.Description.Replace("<", "<").Replace(">", ">"); - html.Write( " {0}", e.Name ); + if (aliases == null) + list.Add(new DocCommandEntry(e.AccessLevel, e.Command, null, usage.Usage, descString)); + else + list.Add(new DocCommandEntry(e.AccessLevel, e.Command, aliases.Aliases, usage.Usage, descString)); + } - if ( aliases == null || aliases.Length == 0 ) - { - html.Write( "Usage: {0}
{1}", usage.Replace( "<", "<" ).Replace( ">", ">" ), desc ); - } - else - { - html.Write( "Usage: {0}
Alias{1}: ", usage.Replace( "<", "<" ).Replace( ">", ">" ), aliases.Length == 1 ? "" : "es" ); + for (int i = 0; i < TargetCommands.AllCommands.Count; ++i) + { + BaseCommand command = TargetCommands.AllCommands[i]; - for( int i = 0; i < aliases.Length; ++i ) - { - if ( i != 0 ) - html.Write( ", " ); + string usage = command.Usage; + string desc = command.Description; - html.Write( aliases[i] ); - } + if (usage == null || desc == null) + continue; - html.Write( "
{0}", desc ); - } + string[] cmds = command.Commands; + string cmd = cmds[0]; + string[] aliases = new string[cmds.Length - 1]; - html.WriteLine( "" ); - } + for (int j = 0; j < aliases.Length; ++j) + aliases[j] = cmds[j + 1]; - #endregion + desc = desc.Replace("<", "<").Replace(">", ">"); - private static void LoadTypes( Assembly a, Assembly[] asms ) - { - Type[] types = a.GetTypes(); + if (command.Supports != CommandSupport.Single) + { + StringBuilder sb = new StringBuilder(50 + desc.Length); - for( int i = 0; i < types.Length; ++i ) - { - Type type = types[i]; + sb.Append("Modifiers: "); - string nspace = type.Namespace; + if ((command.Supports & CommandSupport.Global) != 0) + sb.Append("
Global, "); - if ( nspace == null || type.IsSpecialName ) - continue; + if ((command.Supports & CommandSupport.Online) != 0) + sb.Append("Online, "); - TypeInfo info = new TypeInfo( type ); - m_Types[type] = info; + if ((command.Supports & CommandSupport.Region) != 0) + sb.Append("Region, "); - m_Namespaces.TryGetValue( nspace, out List nspaces ); + if ((command.Supports & CommandSupport.Contained) != 0) + sb.Append("Contained, "); - if ( nspaces == null ) - m_Namespaces[nspace] = nspaces = new List(); + if ((command.Supports & CommandSupport.Multi) != 0) + sb.Append("Multi, "); - nspaces.Add( info ); + if ((command.Supports & CommandSupport.Area) != 0) + sb.Append("Area, "); - Type baseType = info.m_BaseType; + if ((command.Supports & CommandSupport.Self) != 0) + sb.Append("Self, "); - if ( baseType != null && InAssemblies( baseType, asms ) ) - { - m_Types.TryGetValue( baseType, out TypeInfo baseInfo ); + sb.Remove(sb.Length - 2, 2); + sb.Append("
"); + sb.Append(desc); - if ( baseInfo == null ) - m_Types[baseType] = baseInfo = new TypeInfo( baseType ); + desc = sb.ToString(); + } - if ( baseInfo.m_Derived == null ) - baseInfo.m_Derived = new List(); + list.Add(new DocCommandEntry(command.AccessLevel, cmd, aliases, usage, desc)); + } - baseInfo.m_Derived.Add( info ); - } + List commandImpls = BaseCommandImplementor.Implementors; - Type decType = info.m_Declaring; + for (int i = 0; i < commandImpls.Count; ++i) + { + BaseCommandImplementor command = commandImpls[i]; - if ( decType != null ) - { - m_Types.TryGetValue( decType, out TypeInfo decInfo ); + string usage = command.Usage; + string desc = command.Description; - if ( decInfo == null ) - m_Types[decType] = decInfo = new TypeInfo( decType ); + if (usage == null || desc == null) + continue; - if ( decInfo.m_Nested == null ) - decInfo.m_Nested = new List(); + string[] cmds = command.Accessors; + string cmd = cmds[0]; + string[] aliases = new string[cmds.Length - 1]; - decInfo.m_Nested.Add( info ); - } + for (int j = 0; j < aliases.Length; ++j) + aliases[j] = cmds[j + 1]; - for( int j = 0; j < info.m_Interfaces.Length; ++j ) - { - Type iface = info.m_Interfaces[j]; + desc = desc.Replace("<", "<").Replace(">", ">"); - if ( !InAssemblies( iface, asms ) ) - continue; + list.Add(new DocCommandEntry(command.AccessLevel, cmd, aliases, usage, desc)); + } - m_Types.TryGetValue( iface, out TypeInfo ifaceInfo ); + list.Sort(new CommandEntrySorter()); - if ( ifaceInfo == null ) - m_Types[iface] = ifaceInfo = new TypeInfo( iface ); + AccessLevel last = AccessLevel.Player; - if ( ifaceInfo.m_Derived == null ) - ifaceInfo.m_Derived = new List(); + foreach (DocCommandEntry e in list) + { + if (e.AccessLevel != last) + { + if (last != AccessLevel.Player) + html.WriteLine("
"); - ifaceInfo.m_Derived.Add( info ); - } - } - } + last = e.AccessLevel; - private static bool InAssemblies( Type t, Assembly[] asms ) - { - Assembly a = t.Assembly; + html.WriteLine(" ", last); + + switch (last) + { + case AccessLevel.Administrator: + html.WriteLine( + " Administrator | Game Master | Counselor | Player

"); + break; + case AccessLevel.GameMaster: + html.WriteLine( + " Administrator | Game Master | Counselor | Player

"); + break; + case AccessLevel.Seer: + html.WriteLine( + " Administrator | Game Master | Counselor | Player

"); + break; + case AccessLevel.Counselor: + html.WriteLine( + " Administrator | Game Master | Counselor | Player

"); + break; + case AccessLevel.Player: + html.WriteLine( + " Administrator | Game Master | Counselor | Player

"); + break; + } + + html.WriteLine(" "); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" ", + last == AccessLevel.GameMaster ? "Game Master" : last.ToString()); + } + + DocumentCommand(html, e); + } + + html.WriteLine("
{0}
"); + html.WriteLine(" "); + html.WriteLine(""); + } + } + + public static void Clean(List list) + { + for (int i = 0; i < list.Count; ++i) + { + CommandEntry e = list[i]; + + for (int j = i + 1; j < list.Count; ++j) + { + CommandEntry c = list[j]; + + if (e.Handler.Method == c.Handler.Method) + { + list.RemoveAt(j); + --j; + } + } + } + } + + private static void DocumentCommand(StreamWriter html, DocCommandEntry e) + { + string usage = e.Usage; + string desc = e.Description; + string[] aliases = e.Aliases; + + html.Write(" {0}", e.Name); + + if (aliases == null || aliases.Length == 0) + { + html.Write("Usage: {0}
{1}", + usage.Replace("<", "<").Replace(">", ">"), desc); + } + else + { + html.Write("Usage: {0}
Alias{1}: ", + usage.Replace("<", "<").Replace(">", ">"), aliases.Length == 1 ? "" : "es"); + + for (int i = 0; i < aliases.Length; ++i) + { + if (i != 0) + html.Write(", "); + + html.Write(aliases[i]); + } + + html.Write("
{0}", desc); + } + + html.WriteLine(""); + } + + #endregion + + #region Constructible Objects + + private static Type typeofItem = typeof(Item), typeofMobile = typeof(Mobile), typeofMap = typeof(Map); + private static Type typeofCustomEnum = typeof(CustomEnumAttribute); + + private static bool IsConstructible(Type t, out bool isItem) + { + if (isItem = typeofItem.IsAssignableFrom(t)) + return true; + + return typeofMobile.IsAssignableFrom(t); + } + + private static bool IsConstructible(ConstructorInfo ctor) + { + return ctor.IsDefined(typeof(ConstructibleAttribute), false); + } + + private static void DocumentConstructibleObjects() + { + List types = new List(m_Types.Values); + types.Sort(new TypeComparer()); + + ArrayList items = new ArrayList(), mobiles = new ArrayList(); + + for (int i = 0; i < types.Count; ++i) + { + Type t = types[i].m_Type; + bool isItem; - for( int i = 0; i < asms.Length; ++i ) - if ( a == asms[i] ) - return true; + if (t.IsAbstract || !IsConstructible(t, out isItem)) + continue; - return false; - } + ConstructorInfo[] ctors = t.GetConstructors(); + bool anyConstructible = false; - #region Constructible Objects - private static Type typeofItem = typeof( Item ), typeofMobile = typeof( Mobile ), typeofMap = typeof( Map ); - private static Type typeofCustomEnum = typeof( CustomEnumAttribute ); + for (int j = 0; !anyConstructible && j < ctors.Length; ++j) + anyConstructible = IsConstructible(ctors[j]); + + if (anyConstructible) + { + (isItem ? items : mobiles).Add(t); + (isItem ? items : mobiles).Add(ctors); + } + } + + using (StreamWriter html = GetWriter("docs/", "objects.html")) + { + html.WriteLine(""); + html.WriteLine(" "); + html.WriteLine(" RunUO Documentation - Constructible Objects"); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine("

Back to the index

"); + html.WriteLine( + "

Constructible Items and Mobiles

"); + + html.WriteLine(" "); + html.WriteLine(" "); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" "); + + for (int i = 0; i < items.Count; i += 2) + DocumentConstructibleObject(html, (Type)items[i], (ConstructorInfo[])items[i + 1]); + + html.WriteLine("
Item NameUsage


"); + + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine("
"); + html.WriteLine(" "); + html.WriteLine(" "); + + for (int i = 0; i < mobiles.Count; i += 2) + DocumentConstructibleObject(html, (Type)mobiles[i], (ConstructorInfo[])mobiles[i + 1]); - private static bool IsConstructible( Type t, out bool isItem ) - { - if ( isItem = typeofItem.IsAssignableFrom( t ) ) - return true; + html.WriteLine("
Mobile NameUsage
"); - return typeofMobile.IsAssignableFrom( t ); - } + html.WriteLine(" "); + html.WriteLine(""); + } + } - private static bool IsConstructible( ConstructorInfo ctor ) - { - return ctor.IsDefined( typeof( ConstructibleAttribute ), false ); - } + private static void DocumentConstructibleObject(StreamWriter html, Type t, ConstructorInfo[] ctors) + { + html.Write(" {0}", t.Name); - private static void DocumentConstructibleObjects() - { - List types = new List( m_Types.Values ); - types.Sort( new TypeComparer() ); + bool first = true; - ArrayList items = new ArrayList(), mobiles = new ArrayList(); + for (int i = 0; i < ctors.Length; ++i) + { + ConstructorInfo ctor = ctors[i]; - for( int i = 0; i < types.Count; ++i ) - { - Type t = types[i].m_Type; - bool isItem; + if (!IsConstructible(ctor)) + continue; - if ( t.IsAbstract || !IsConstructible( t, out isItem ) ) - continue; + if (!first) + html.Write("
"); - ConstructorInfo[] ctors = t.GetConstructors(); - bool anyConstructible = false; + first = false; - for( int j = 0; !anyConstructible && j < ctors.Length; ++j ) - anyConstructible = IsConstructible( ctors[j] ); + html.Write("{0}Add {1}", CommandSystem.Prefix, t.Name); - if ( anyConstructible ) - { - (isItem ? items : mobiles).Add( t ); - (isItem ? items : mobiles).Add( ctors ); - } - } + ParameterInfo[] parms = ctor.GetParameters(); - using( StreamWriter html = GetWriter( "docs/", "objects.html" ) ) - { - html.WriteLine( "" ); - html.WriteLine( " " ); - html.WriteLine( " RunUO Documentation - Constructible Objects" ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "

Back to the index

" ); - html.WriteLine( "

Constructible Items and Mobiles

" ); + for (int j = 0; j < parms.Length; ++j) + { + html.Write(" " ); - html.WriteLine( " " ); - html.WriteLine( "
" ); - html.WriteLine( " " ); - html.WriteLine( " " ); + m_Types.TryGetValue(parms[j].ParameterType, out TypeInfo typeInfo); - for( int i = 0; i < items.Count; i += 2 ) - DocumentConstructibleObject( html, (Type)items[i], (ConstructorInfo[])items[i + 1] ); + if (typeInfo != null) + html.Write("href=\"types/{0}\" ", typeInfo.FileName); - html.WriteLine( "
Item NameUsage


" ); + html.Write("title=\"{0}\">{1}
", GetTooltipFor(parms[j]), parms[j].Name); + } + } - html.WriteLine( " " ); - html.WriteLine( " " ); - html.WriteLine( "
" ); - html.WriteLine( " " ); - html.WriteLine( " " ); + html.WriteLine(""); + } - for( int i = 0; i < mobiles.Count; i += 2 ) - DocumentConstructibleObject( html, (Type)mobiles[i], (ConstructorInfo[])mobiles[i + 1] ); + #endregion - html.WriteLine( "
Mobile NameUsage
" ); + #region Tooltips - html.WriteLine( " " ); - html.WriteLine( "" ); - } - } + private const string HtmlNewLine = " "; - private static void DocumentConstructibleObject( StreamWriter html, Type t, ConstructorInfo[] ctors ) - { - html.Write( " {0}", t.Name ); + private static object[,] m_Tooltips = + { + { typeof(byte), "Numeric value in the range from 0 to 255, inclusive." }, + { typeof(sbyte), "Numeric value in the range from negative 128 to positive 127, inclusive." }, + { typeof(ushort), "Numeric value in the range from 0 to 65,535, inclusive." }, + { typeof(short), "Numeric value in the range from negative 32,768 to positive 32,767, inclusive." }, + { typeof(uint), "Numeric value in the range from 0 to 4,294,967,295, inclusive." }, + { typeof(int), "Numeric value in the range from negative 2,147,483,648 to positive 2,147,483,647, inclusive." }, + { typeof(ulong), "Numeric value in the range from 0 through about 10^20." }, + { typeof(long), "Numeric value in the approximate range from negative 10^19 through 10^19." }, + { + typeof(string), + "Text value. To specify a value containing spaces, encapsulate the value in quote characters:{0}{0}"Spaced text example"" + }, + { typeof(bool), "Boolean value which can be either True or False." }, + { typeof(Map), "Map or facet name. Possible values include:{0}{0}- Felucca{0}- Trammel{0}- Ilshenar{0}- Malas" }, + { + typeof(Poison), + "Poison name or level. Possible values include:{0}{0}- Lesser{0}- Regular{0}- Greater{0}- Deadly{0}- Lethal" + }, + { + typeof(Point3D), + "Three-dimensional coordinate value. Format as follows:{0}{0}"(, , )"" + } + }; - bool first = true; + private static string GetTooltipFor(ParameterInfo param) + { + Type paramType = param.ParameterType; - for( int i = 0; i < ctors.Length; ++i ) - { - ConstructorInfo ctor = ctors[i]; + for (int i = 0; i < m_Tooltips.GetLength(0); ++i) + { + Type checkType = (Type)m_Tooltips[i, 0]; - if ( !IsConstructible( ctor ) ) - continue; + if (paramType == checkType) + return string.Format((string)m_Tooltips[i, 1], HtmlNewLine); + } - if ( !first ) - html.Write( "
" ); + if (paramType.IsEnum) + { + StringBuilder sb = new StringBuilder(); - first = false; + sb.AppendFormat("Enumeration value or name. Possible named values include:{0}", HtmlNewLine); - html.Write( "{0}Add {1}", CommandSystem.Prefix, t.Name ); + string[] names = Enum.GetNames(paramType); - ParameterInfo[] parms = ctor.GetParameters(); + for (int i = 0; i < names.Length; ++i) + sb.AppendFormat("{0}- {1}", HtmlNewLine, names[i]); - for( int j = 0; j < parms.Length; ++j ) - { - html.Write( "
0 && attributes[0] is CustomEnumAttribute attr) + { + StringBuilder sb = new StringBuilder(); - html.Write( "title=\"{0}\">{1}", GetTooltipFor( parms[j] ), parms[j].Name ); - } - } + sb.AppendFormat("Enumeration value or name. Possible named values include:{0}", HtmlNewLine); - html.WriteLine( "" ); - } + string[] names = attr.Names; - #endregion + for (int i = 0; i < names.Length; ++i) + sb.AppendFormat("{0}- {1}", HtmlNewLine, names[i]); - #region Tooltips + return sb.ToString(); + } + } + else if (paramType == typeofMap) + { + StringBuilder sb = new StringBuilder(); - private const string HtmlNewLine = " "; + sb.AppendFormat("Enumeration value or name. Possible named values include:{0}", HtmlNewLine); - private static object[,] m_Tooltips = { - { typeof( byte ), "Numeric value in the range from 0 to 255, inclusive." }, - { typeof( sbyte ), "Numeric value in the range from negative 128 to positive 127, inclusive." }, - { typeof( ushort ), "Numeric value in the range from 0 to 65,535, inclusive." }, - { typeof( short ), "Numeric value in the range from negative 32,768 to positive 32,767, inclusive." }, - { typeof( uint ), "Numeric value in the range from 0 to 4,294,967,295, inclusive." }, - { typeof( int ), "Numeric value in the range from negative 2,147,483,648 to positive 2,147,483,647, inclusive." }, - { typeof( ulong ), "Numeric value in the range from 0 through about 10^20." }, - { typeof( long ), "Numeric value in the approximate range from negative 10^19 through 10^19." }, - { typeof( string ), "Text value. To specify a value containing spaces, encapsulate the value in quote characters:{0}{0}"Spaced text example"" }, - { typeof( bool ), "Boolean value which can be either True or False." }, - { typeof( Map ), "Map or facet name. Possible values include:{0}{0}- Felucca{0}- Trammel{0}- Ilshenar{0}- Malas" }, - { typeof( Poison ), "Poison name or level. Possible values include:{0}{0}- Lesser{0}- Regular{0}- Greater{0}- Deadly{0}- Lethal" }, - { typeof( Point3D ), "Three-dimensional coordinate value. Format as follows:{0}{0}"(, , )"" } - }; + string[] names = Map.GetMapNames(); - private static string GetTooltipFor( ParameterInfo param ) - { - Type paramType = param.ParameterType; + for (int i = 0; i < names.Length; ++i) + sb.AppendFormat("{0}- {1}", HtmlNewLine, names[i]); - for( int i = 0; i < m_Tooltips.GetLength( 0 ); ++i ) - { - Type checkType = (Type)m_Tooltips[i, 0]; + return sb.ToString(); + } - if ( paramType == checkType ) - return string.Format( (string)m_Tooltips[i, 1], HtmlNewLine ); - } + return ""; + } - if ( paramType.IsEnum ) - { - StringBuilder sb = new StringBuilder(); + #endregion - sb.AppendFormat( "Enumeration value or name. Possible named values include:{0}", HtmlNewLine ); + #region Const Strings - string[] names = Enum.GetNames( paramType ); + private const string RefString = "ref "; + private const string GetString = " get;"; + private const string SetString = " set;"; - for( int i = 0; i < names.Length; ++i ) - sb.AppendFormat( "{0}- {1}", HtmlNewLine, names[i] ); + private const string InString = "in "; + private const string OutString = "out "; - return sb.ToString(); - } - if ( paramType.IsDefined( typeofCustomEnum, false ) ) - { - object[] attributes = paramType.GetCustomAttributes( typeofCustomEnum, false ); + private const string VirtString = "virtual "; + private const string CtorString = "(ctor) "; + private const string StaticString = "(static) "; - if ( attributes.Length > 0 && attributes[0] is CustomEnumAttribute attr ) - { - StringBuilder sb = new StringBuilder(); + #endregion - sb.AppendFormat( "Enumeration value or name. Possible named values include:{0}", HtmlNewLine ); + #region Write[...] - string[] names = attr.Names; + private static void WriteEnum(TypeInfo info, StreamWriter typeHtml) + { + Type type = info.m_Type; - for( int i = 0; i < names.Length; ++i ) - sb.AppendFormat( "{0}- {1}", HtmlNewLine, names[i] ); + typeHtml.WriteLine("

{0} (Enum)

", info.TypeName); - return sb.ToString(); - } - } - else if ( paramType == typeofMap ) - { - StringBuilder sb = new StringBuilder(); + string[] names = Enum.GetNames(type); - sb.AppendFormat( "Enumeration value or name. Possible named values include:{0}", HtmlNewLine ); + bool flags = type.IsDefined(typeof(FlagsAttribute), false); + string format; - string[] names = Map.GetMapNames(); + if (flags) + format = " {0:G} = 0x{1:X}{2}
"; + else + format = " {0:G} = {1:D}{2}
"; - for( int i = 0; i < names.Length; ++i ) - sb.AppendFormat( "{0}- {1}", HtmlNewLine, names[i] ); + for (int i = 0; i < names.Length; ++i) + { + object value = Enum.Parse(type, names[i]); - return sb.ToString(); - } + typeHtml.WriteLine(format, names[i], value, i < names.Length - 1 ? "," : ""); + } + } - return ""; - } + private static void WriteType(TypeInfo info, StreamWriter typeHtml) + { + Type type = info.m_Type; - #endregion + typeHtml.Write("

"); - #region Const Strings + Type decType = info.m_Declaring; - private const string RefString = "ref "; - private const string GetString = " get;"; - private const string SetString = " set;"; + if (decType != null) + { + // We are a nested type - private const string InString = "in "; - private const string OutString = "out "; + typeHtml.Write('('); - private const string VirtString = "virtual "; - private const string CtorString ="(ctor) "; - private const string StaticString = "(static) "; - #endregion - - private static void DocumentLoadedTypes() - { - using( StreamWriter indexHtml = GetWriter( "docs/", "overview.html" ) ) - { - indexHtml.WriteLine( "" ); - indexHtml.WriteLine( " " ); - indexHtml.WriteLine( " RunUO Documentation - Class Overview" ); - indexHtml.WriteLine( " " ); - indexHtml.WriteLine( " " ); - indexHtml.WriteLine( "

Back to the index

" ); - indexHtml.WriteLine( "

Namespaces

" ); - - SortedList> nspaces = new SortedList>( m_Namespaces ); + m_Types.TryGetValue(decType, out TypeInfo decInfo); - foreach( KeyValuePair> kvp in nspaces ) - { - kvp.Value.Sort( new TypeComparer() ); + if (decInfo == null) + typeHtml.Write(decType.Name); + else + //typeHtml.Write( "{1}", decInfo.m_FileName, decInfo.m_TypeName ); + typeHtml.Write(decInfo.LinkName(null)); - SaveNamespace( kvp.Key, kvp.Value, indexHtml ); - } + typeHtml.Write(") - "); + } - indexHtml.WriteLine( " " ); - indexHtml.WriteLine( "" ); - } - } + typeHtml.Write(info.TypeName); - private static void SaveNamespace( string name, List types, StreamWriter indexHtml ) - { - string fileName = GetFileName( "docs/namespaces/", name, ".html" ); + Type[] ifaces = info.m_Interfaces; + Type baseType = info.m_BaseType; - indexHtml.WriteLine( " {1}
", fileName, name ); + int extendCount = 0; - using( StreamWriter nsHtml = GetWriter( "docs/namespaces/", fileName ) ) - { - nsHtml.WriteLine( "" ); - nsHtml.WriteLine( " " ); - nsHtml.WriteLine( " RunUO Documentation - Class Overview - {0}", name ); - nsHtml.WriteLine( " " ); - nsHtml.WriteLine( " " ); - nsHtml.WriteLine( "

Back to the namespace index

" ); - nsHtml.WriteLine( "

{0}

", name ); + if (baseType != null && baseType != typeof(object) && baseType != typeof(ValueType) && !baseType.IsPrimitive) + { + typeHtml.Write(" : "); - for( int i = 0; i < types.Count; ++i ) - SaveType( types[i], nsHtml, fileName, name ); + m_Types.TryGetValue(baseType, out TypeInfo baseInfo); - nsHtml.WriteLine( " " ); - nsHtml.WriteLine( "" ); - } - } + if (baseInfo == null) + typeHtml.Write(baseType.Name); + else + typeHtml.Write("" + baseInfo.LinkName(null)); - private static void SaveType( TypeInfo info, StreamWriter nsHtml, string nsFileName, string nsName ) - { - if ( info.m_Declaring == null ) - nsHtml.WriteLine( " "+info.LinkName( "../types/" ) + "
" ); + ++extendCount; + } - using( StreamWriter typeHtml = GetWriter( info.FileName ) ) - { - typeHtml.WriteLine( "" ); - typeHtml.WriteLine( " " ); - typeHtml.WriteLine( " RunUO Documentation - Class Overview - {0}", info.TypeName ); - typeHtml.WriteLine( " " ); - typeHtml.WriteLine( " " ); - typeHtml.WriteLine( "

Back to {1}

", nsFileName, nsName ); + if (ifaces.Length > 0) + { + if (extendCount == 0) + typeHtml.Write(" : "); - if ( info.m_Type.IsEnum ) - WriteEnum( info, typeHtml ); - else - WriteType( info, typeHtml ); + for (int i = 0; i < ifaces.Length; ++i) + { + Type iface = ifaces[i]; + m_Types.TryGetValue(iface, out TypeInfo ifaceInfo); - typeHtml.WriteLine( " " ); - typeHtml.WriteLine( "" ); - } - } - - #region Write[...] - private static void WriteEnum( TypeInfo info, StreamWriter typeHtml ) - { - Type type = info.m_Type; - - typeHtml.WriteLine( "

{0} (Enum)

", info.TypeName ); - - string[] names = Enum.GetNames( type ); - - bool flags = type.IsDefined( typeof( FlagsAttribute ), false ); - string format; - - if ( flags ) - format = " {0:G} = 0x{1:X}{2}
"; - else - format = " {0:G} = {1:D}{2}
"; - - for( int i = 0; i < names.Length; ++i ) - { - object value = Enum.Parse( type, names[i] ); - - typeHtml.WriteLine( format, names[i], value, i < (names.Length - 1) ? "," : "" ); - } - } - - private static void WriteType( TypeInfo info, StreamWriter typeHtml ) - { - Type type = info.m_Type; - - typeHtml.Write( "

" ); + if (extendCount != 0) + typeHtml.Write(", "); - Type decType = info.m_Declaring; + ++extendCount; - if ( decType != null ) - { - // We are a nested type + if (ifaceInfo == null) + { + string typeName = ""; + string fileName = ""; + string linkName = ""; + FormatGeneric(iface, ref typeName, ref fileName, ref linkName); + linkName = linkName.Replace("@directory@", null); + typeHtml.Write("" + linkName); + } + else + { + typeHtml.Write("" + ifaceInfo.LinkName(null)); + } + } + } - typeHtml.Write( '(' ); + typeHtml.WriteLine("

"); - m_Types.TryGetValue( decType, out TypeInfo decInfo ); + List derived = info.m_Derived; - if ( decInfo == null ) - typeHtml.Write( decType.Name ); - else - //typeHtml.Write( "{1}", decInfo.m_FileName, decInfo.m_TypeName ); - typeHtml.Write( decInfo.LinkName( null ) ); + if (derived != null) + { + typeHtml.Write("

Derived Types: "); - typeHtml.Write( ") - " ); - } + derived.Sort(new TypeComparer()); - typeHtml.Write( info.TypeName ); + for (int i = 0; i < derived.Count; ++i) + { + TypeInfo derivedInfo = derived[i]; - Type[] ifaces = info.m_Interfaces; - Type baseType = info.m_BaseType; + if (i != 0) + typeHtml.Write(", "); - int extendCount = 0; + //typeHtml.Write( "{1}", derivedInfo.m_FileName, derivedInfo.m_TypeName ); + typeHtml.Write("" + derivedInfo.LinkName(null)); + } - if ( baseType != null && baseType != typeof( object ) && baseType != typeof( ValueType ) && !baseType.IsPrimitive ) - { - typeHtml.Write( " : " ); + typeHtml.WriteLine("

"); + } - m_Types.TryGetValue( baseType, out TypeInfo baseInfo ); + List nested = info.m_Nested; - if ( baseInfo == null ) - typeHtml.Write( baseType.Name ); - else - { - typeHtml.Write( ""+baseInfo.LinkName( null ) ); - } + if (nested != null) + { + typeHtml.Write("

Nested Types: "); - ++extendCount; - } + nested.Sort(new TypeComparer()); - if ( ifaces.Length > 0 ) - { - if ( extendCount == 0 ) - typeHtml.Write( " : " ); + for (int i = 0; i < nested.Count; ++i) + { + TypeInfo nestedInfo = nested[i]; - for( int i = 0; i < ifaces.Length; ++i ) - { - Type iface = ifaces[i]; - m_Types.TryGetValue( iface, out TypeInfo ifaceInfo ); + if (i != 0) + typeHtml.Write(", "); - if ( extendCount != 0 ) - typeHtml.Write( ", " ); + //typeHtml.Write( "{1}", nestedInfo.m_FileName, nestedInfo.m_TypeName ); + typeHtml.Write("" + nestedInfo.LinkName(null)); + } - ++extendCount; + typeHtml.WriteLine("

"); + } - if ( ifaceInfo == null ) - { - string typeName = ""; - string fileName = ""; - string linkName = ""; - FormatGeneric( iface, ref typeName, ref fileName, ref linkName ); - linkName = linkName.Replace( "@directory@", null ); - typeHtml.Write( ""+linkName ); - } - else - { - typeHtml.Write( ""+ifaceInfo.LinkName( null ) ); - } - } - } + MemberInfo[] membs = type.GetMembers(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | + BindingFlags.Instance | BindingFlags.DeclaredOnly); - typeHtml.WriteLine( "" ); + Array.Sort(membs, new MemberComparer()); - List derived = info.m_Derived; + for (int i = 0; i < membs.Length; ++i) + { + MemberInfo mi = membs[i]; - if ( derived != null ) - { - typeHtml.Write( "

Derived Types: " ); + if (mi is PropertyInfo propertyInfo) + WriteProperty(propertyInfo, typeHtml); + else if (mi is ConstructorInfo constructorInfo) + WriteCtor(info.TypeName, constructorInfo, typeHtml); + else if (mi is MethodInfo methodInfo) + WriteMethod(methodInfo, typeHtml); + } + } - derived.Sort( new TypeComparer() ); + private static void WriteProperty(PropertyInfo pi, StreamWriter html) + { + html.Write(" "); - for( int i = 0; i < derived.Count; ++i ) - { - TypeInfo derivedInfo = derived[i]; + MethodInfo getMethod = pi.GetGetMethod(); + MethodInfo setMethod = pi.GetSetMethod(); - if ( i != 0 ) - typeHtml.Write( ", " ); + if (getMethod != null && getMethod.IsStatic || setMethod != null && setMethod.IsStatic) + html.Write(StaticString); - //typeHtml.Write( "{1}", derivedInfo.m_FileName, derivedInfo.m_TypeName ); - typeHtml.Write( ""+derivedInfo.LinkName( null ) ); - } + html.Write(GetPair(pi.PropertyType, pi.Name, false)); + html.Write('('); - typeHtml.WriteLine( "

" ); - } + if (pi.CanRead) + html.Write(GetString); - List nested = info.m_Nested; + if (pi.CanWrite) + html.Write(SetString); - if ( nested != null ) - { - typeHtml.Write( "

Nested Types: " ); + html.WriteLine(" )
"); + } - nested.Sort( new TypeComparer() ); + private static void WriteCtor(string name, ConstructorInfo ctor, StreamWriter html) + { + if (ctor.IsStatic) + return; - for( int i = 0; i < nested.Count; ++i ) - { - TypeInfo nestedInfo = nested[i]; + html.Write(" "); + html.Write(CtorString); + html.Write(name); + html.Write('('); - if ( i != 0 ) - typeHtml.Write( ", " ); + ParameterInfo[] parms = ctor.GetParameters(); - //typeHtml.Write( "{1}", nestedInfo.m_FileName, nestedInfo.m_TypeName ); - typeHtml.Write( ""+nestedInfo.LinkName( null ) ); - } + if (parms.Length > 0) + { + html.Write(' '); - typeHtml.WriteLine( "

" ); - } + for (int i = 0; i < parms.Length; ++i) + { + ParameterInfo pi = parms[i]; - MemberInfo[] membs = type.GetMembers( BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.Instance | BindingFlags.DeclaredOnly ); + if (i != 0) + html.Write(", "); - Array.Sort( membs, new MemberComparer() ); + if (pi.IsIn) + html.Write(InString); + else if (pi.IsOut) + html.Write(OutString); - for( int i = 0; i < membs.Length; ++i ) - { - MemberInfo mi = membs[i]; + html.Write(GetPair(pi.ParameterType, pi.Name, pi.IsOut)); + } - if ( mi is PropertyInfo propertyInfo ) - WriteProperty( propertyInfo, typeHtml ); - else if ( mi is ConstructorInfo constructorInfo ) - WriteCtor( info.TypeName, constructorInfo, typeHtml ); - else if ( mi is MethodInfo methodInfo ) - WriteMethod( methodInfo, typeHtml ); - } - } + html.Write(' '); + } - private static void WriteProperty( PropertyInfo pi, StreamWriter html ) - { - html.Write( " " ); + html.WriteLine(")
"); + } - MethodInfo getMethod = pi.GetGetMethod(); - MethodInfo setMethod = pi.GetSetMethod(); + private static void WriteMethod(MethodInfo mi, StreamWriter html) + { + if (mi.IsSpecialName) + return; - if ( (getMethod != null && getMethod.IsStatic) || (setMethod != null && setMethod.IsStatic) ) - html.Write( StaticString ); + html.Write(" "); - html.Write( GetPair( pi.PropertyType, pi.Name, false ) ); - html.Write( '(' ); + if (mi.IsStatic) + html.Write(StaticString); - if ( pi.CanRead ) - html.Write( GetString ); + if (mi.IsVirtual) + html.Write(VirtString); - if ( pi.CanWrite ) - html.Write( SetString ); + html.Write(GetPair(mi.ReturnType, mi.Name, false)); + html.Write('('); - html.WriteLine( " )
" ); - } + ParameterInfo[] parms = mi.GetParameters(); - private static void WriteCtor( string name, ConstructorInfo ctor, StreamWriter html ) - { - if ( ctor.IsStatic ) - return; + if (parms.Length > 0) + { + html.Write(' '); - html.Write( " " ); - html.Write( CtorString ); - html.Write( name ); - html.Write( '(' ); + for (int i = 0; i < parms.Length; ++i) + { + ParameterInfo pi = parms[i]; - ParameterInfo[] parms = ctor.GetParameters(); + if (i != 0) + html.Write(", "); - if ( parms.Length > 0 ) - { - html.Write( ' ' ); + if (pi.IsIn) + html.Write(InString); + else if (pi.IsOut) + html.Write(OutString); - for( int i = 0; i < parms.Length; ++i ) - { - ParameterInfo pi = parms[i]; + html.Write(GetPair(pi.ParameterType, pi.Name, pi.IsOut)); + } - if ( i != 0 ) - html.Write( ", " ); + html.Write(' '); + } - if ( pi.IsIn ) - html.Write( InString ); - else if ( pi.IsOut ) - html.Write( OutString ); + html.WriteLine(")
"); + } - html.Write( GetPair( pi.ParameterType, pi.Name, pi.IsOut ) ); - } + #endregion + } - html.Write( ' ' ); - } + #region BodyEntry & BodyType - html.WriteLine( ")
" ); - } + public enum ModelBodyType + { + Invalid = -1, + Monsters, + Sea, + Animals, + Human, + Equipment + } - private static void WriteMethod( MethodInfo mi, StreamWriter html ) - { - if ( mi.IsSpecialName ) - return; + public class BodyEntry + { + public BodyEntry(Body body, ModelBodyType bodyType, string name) + { + Body = body; + BodyType = bodyType; + Name = name; + } - html.Write( " " ); + public Body Body{ get; } - if ( mi.IsStatic ) - html.Write( StaticString ); + public ModelBodyType BodyType{ get; } - if ( mi.IsVirtual ) - html.Write( VirtString ); + public string Name{ get; } - html.Write( GetPair( mi.ReturnType, mi.Name, false ) ); - html.Write( '(' ); + public override bool Equals(object obj) + { + BodyEntry e = (BodyEntry)obj; - ParameterInfo[] parms = mi.GetParameters(); - - if ( parms.Length > 0 ) - { - html.Write( ' ' ); - - for( int i = 0; i < parms.Length; ++i ) - { - ParameterInfo pi = parms[i]; - - if ( i != 0 ) - html.Write( ", " ); - - if ( pi.IsIn ) - html.Write( InString ); - else if ( pi.IsOut ) - html.Write( OutString ); - - html.Write( GetPair( pi.ParameterType, pi.Name, pi.IsOut ) ); - } - - html.Write( ' ' ); - } - - html.WriteLine( ")
" ); - } - #endregion - - public static void FormatGeneric( Type type, ref string typeName, ref string fileName, ref string linkName ) - { - string name = null; - string fnam = null; - string link = null; - - if ( type.IsGenericType ) - { - int index = type.Name.IndexOf( '`' ); - - if ( index > 0 ) - { - string rootType = type.Name.Substring( 0, index ); - - StringBuilder nameBuilder = new StringBuilder( rootType ); - StringBuilder fnamBuilder = new StringBuilder( "docs/types/" + SanitizeType( rootType ) ); - StringBuilder linkBuilder; - if ( DontLink( type ) )//if ( DontLink( rootType ) ) - linkBuilder = new StringBuilder( "" + rootType + "" ); - else - linkBuilder = new StringBuilder( "" + rootType + "" ); - - nameBuilder.Append( "<" ); - fnamBuilder.Append( "-" ); - linkBuilder.Append( "<" ); - - Type[] typeArguments = type.GetGenericArguments(); - - for( int i = 0; i < typeArguments.Length; i++ ) - { - if ( i != 0 ) - { - nameBuilder.Append( ',' ); - fnamBuilder.Append( ',' ); - linkBuilder.Append( ',' ); - } - - string sanitizedName = SanitizeType( typeArguments[i].Name ); - string aliasedName = AliasForName( sanitizedName ); - - nameBuilder.Append( sanitizedName ); - fnamBuilder.Append( "T" ); - if ( DontLink( typeArguments[i] ) )//if ( DontLink( typeArguments[i].Name ) ) - linkBuilder.Append( "" + aliasedName + "" ); - else - linkBuilder.Append( "" + aliasedName + "" ); - } - - nameBuilder.Append( ">" ); - fnamBuilder.Append( "-" ); - linkBuilder.Append( ">" ); - - name = nameBuilder.ToString(); - fnam = fnamBuilder.ToString(); - link = linkBuilder.ToString(); - } - } - if ( name == null ) typeName = type.Name; - else typeName = name; - - if ( fnam == null ) fileName = "docs/types/" + SanitizeType( type.Name ) + ".html"; - else fileName = fnam + ".html"; - - if ( link == null ) - { - if ( DontLink( type ) ) //if ( DontLink( type.Name ) ) - linkName = "" + SanitizeType( type.Name ) + ""; - else - linkName = "" + SanitizeType( type.Name ) + ""; - } - else linkName = link; - - //Console.WriteLine( typeName+":"+fileName+":"+linkName ); - } - - public static string SanitizeType( string name ) - { - bool anonymousType = false; - if ( name.Contains( "<" ) ) anonymousType = true; - StringBuilder sb = new StringBuilder( name ); - for( int i = 0; i < ReplaceChars.Length; ++i ) { sb.Replace( ReplaceChars[i], '-' ); } - - if ( anonymousType ) return "(Anonymous-Type)"+sb.ToString(); - return sb.ToString(); - } - - public static string AliasForName( string name ) - { - for( int i = 0; i < m_AliasLength; ++i ) - { - if ( m_Aliases[i, 0] == name ) - { - return m_Aliases[i, 1]; - } - } - return name; - } - - /* - // For stuff we don't want to links to - private static string[] m_DontLink = new string[] - { - "List", - "Stack", - "Queue", - "Dictionary", - "LinkedList", - "SortedList", - "SortedDictionary", - "IComparable", - "IComparer", - "ICloneable", - "Type" - }; - - public static bool DontLink( string name ) - { - foreach( string dontLink in m_DontLink ) - if ( dontLink == name ) return true; - return false; - } - */ - public static bool DontLink( Type type ) - { - // MONO: type.Namespace is null/empty for generic arguments - - if ( type.Name == "T" || string.IsNullOrEmpty( type.Namespace ) || m_Namespaces == null ) - return true; - - if ( type.Namespace.StartsWith( "Server" ) ) - return false; - - return !m_Namespaces.ContainsKey( type.Namespace ); - } - } - - #region BodyEntry & BodyType - public enum ModelBodyType - { - Invalid=-1, - Monsters, - Sea, - Animals, - Human, - Equipment - } - - public class BodyEntry - { - public Body Body { get; } - - public ModelBodyType BodyType { get; } - - public string Name { get; } - - public BodyEntry( Body body, ModelBodyType bodyType, string name ) - { - Body = body; - BodyType = bodyType; - Name = name; - } - - public override bool Equals( object obj ) - { - BodyEntry e = (BodyEntry)obj; - - return (Body == e.Body && BodyType == e.BodyType && Name == e.Name); - } - - public override int GetHashCode() - { - return Body.BodyID ^ (int)BodyType ^ Name.GetHashCode(); - } - } - - public class BodyEntrySorter : IComparer - { - public int Compare( BodyEntry a, BodyEntry b ) - { - int v = a.BodyType.CompareTo( b.BodyType ); - - if ( v == 0 ) - v = a.Body.BodyID.CompareTo( b.Body.BodyID ); - - if ( v == 0 ) - v = a.Name.CompareTo( b.Name ); - - return v; - } - } - #endregion -} + return Body == e.Body && BodyType == e.BodyType && Name == e.Name; + } + + public override int GetHashCode() + { + return Body.BodyID ^ (int)BodyType ^ Name.GetHashCode(); + } + } + + public class BodyEntrySorter : IComparer + { + public int Compare(BodyEntry a, BodyEntry b) + { + int v = a.BodyType.CompareTo(b.BodyType); + + if (v == 0) + v = a.Body.BodyID.CompareTo(b.Body.BodyID); + + if (v == 0) + v = a.Name.CompareTo(b.Name); + + return v; + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Commands/DragEffects.cs b/Scripts/Commands/DragEffects.cs index 7b2ed9ab2..fbe967a21 100644 --- a/Scripts/Commands/DragEffects.cs +++ b/Scripts/Commands/DragEffects.cs @@ -1,26 +1,26 @@ namespace Server.Commands { - public static class DragEffects - { - public static void Initialize() - { - CommandSystem.Register( "DragEffects", AccessLevel.Developer, DragEffects_OnCommand ); - } + public static class DragEffects + { + public static void Initialize() + { + CommandSystem.Register("DragEffects", AccessLevel.Developer, DragEffects_OnCommand); + } - [Usage( "DragEffects [enable=false]" )] - [Description( "Enables or disables the item drag and drop effects." )] - public static void DragEffects_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 0 ) - { - e.Mobile.SendMessage( "Drag effects are currently {0}.", Mobile.DragEffects ? "enabled" : "disabled" ); - } - else - { - Mobile.DragEffects = e.GetBoolean( 0 ); + [Usage("DragEffects [enable=false]")] + [Description("Enables or disables the item drag and drop effects.")] + public static void DragEffects_OnCommand(CommandEventArgs e) + { + if (e.Length == 0) + { + e.Mobile.SendMessage("Drag effects are currently {0}.", Mobile.DragEffects ? "enabled" : "disabled"); + } + else + { + Mobile.DragEffects = e.GetBoolean(0); - e.Mobile.SendMessage( "Drag effects have been {0}.", Mobile.DragEffects ? "enabled" : "disabled" ); - } - } - } -} + e.Mobile.SendMessage("Drag effects have been {0}.", Mobile.DragEffects ? "enabled" : "disabled"); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Dupe.cs b/Scripts/Commands/Dupe.cs index 269e1b41e..7ed32436a 100644 --- a/Scripts/Commands/Dupe.cs +++ b/Scripts/Commands/Dupe.cs @@ -5,138 +5,131 @@ using Server.Targeting; namespace Server.Commands { - public class Dupe - { - public static void Initialize() - { - CommandSystem.Register( "Dupe", AccessLevel.GameMaster, Dupe_OnCommand ); - CommandSystem.Register( "DupeInBag", AccessLevel.GameMaster, DupeInBag_OnCommand ); - } + public class Dupe + { + public static void Initialize() + { + CommandSystem.Register("Dupe", AccessLevel.GameMaster, Dupe_OnCommand); + CommandSystem.Register("DupeInBag", AccessLevel.GameMaster, DupeInBag_OnCommand); + } - [Usage( "Dupe [amount]" )] - [Description( "Dupes a targeted item." )] - private static void Dupe_OnCommand( CommandEventArgs e ) - { - int amount = 1; - if ( e.Length >= 1 ) - amount = e.GetInt32( 0 ); - e.Mobile.Target = new DupeTarget( false, amount > 0 ? amount : 1 ); - e.Mobile.SendMessage( "What do you wish to dupe?" ); - } + [Usage("Dupe [amount]")] + [Description("Dupes a targeted item.")] + private static void Dupe_OnCommand(CommandEventArgs e) + { + int amount = 1; + if (e.Length >= 1) + amount = e.GetInt32(0); + e.Mobile.Target = new DupeTarget(false, amount > 0 ? amount : 1); + e.Mobile.SendMessage("What do you wish to dupe?"); + } - [Usage( "DupeInBag " )] - [Description( "Dupes an item at it's current location (count) number of times." )] - private static void DupeInBag_OnCommand( CommandEventArgs e ) - { - int amount = 1; - if ( e.Length >= 1 ) - amount = e.GetInt32( 0 ); + [Usage("DupeInBag ")] + [Description("Dupes an item at it's current location (count) number of times.")] + private static void DupeInBag_OnCommand(CommandEventArgs e) + { + int amount = 1; + if (e.Length >= 1) + amount = e.GetInt32(0); - e.Mobile.Target = new DupeTarget( true, amount > 0 ? amount : 1 ); - e.Mobile.SendMessage( "What do you wish to dupe?" ); - } + e.Mobile.Target = new DupeTarget(true, amount > 0 ? amount : 1); + e.Mobile.SendMessage("What do you wish to dupe?"); + } - private class DupeTarget : Target - { - private bool m_InBag; - private int m_Amount; + public static void CopyProperties(Item dest, Item src) + { + PropertyInfo[] props = src.GetType().GetProperties(); - public DupeTarget( bool inbag, int amount ) - : base( 15, false, TargetFlags.None ) - { - m_InBag = inbag; - m_Amount = amount; - } + for (int i = 0; i < props.Length; i++) + try + { + if (props[i].CanRead && props[i].CanWrite) props[i].SetValue(dest, props[i].GetValue(src, null), null); + } + catch + { + //Console.WriteLine( "Denied" ); + } + } - protected override void OnTarget( Mobile from, object targ ) - { - bool done = false; - if ( !( targ is Item ) ) - { - from.SendMessage( "You can only dupe items." ); - return; - } + private class DupeTarget : Target + { + private int m_Amount; + private bool m_InBag; - CommandLogging.WriteLine( from, "{0} {1} duping {2} (inBag={3}; amount={4})", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( targ ), m_InBag, m_Amount ); + public DupeTarget(bool inbag, int amount) + : base(15, false, TargetFlags.None) + { + m_InBag = inbag; + m_Amount = amount; + } - Item copy = (Item)targ; - Container pack = null; + protected override void OnTarget(Mobile from, object targ) + { + bool done = false; + if (!(targ is Item)) + { + from.SendMessage("You can only dupe items."); + return; + } - if ( m_InBag ) - { - if ( copy.Parent is Container cont ) - pack = cont; - else if ( copy.Parent is Mobile m ) - pack = m.Backpack; - } - else - pack = from.Backpack; + CommandLogging.WriteLine(from, "{0} {1} duping {2} (inBag={3}; amount={4})", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(targ), m_InBag, m_Amount); - Type t = copy.GetType(); + Item copy = (Item)targ; + Container pack = null; - //ConstructorInfo[] info = t.GetConstructors(); + if (m_InBag) + { + if (copy.Parent is Container cont) + pack = cont; + else if (copy.Parent is Mobile m) + pack = m.Backpack; + } + else + { + pack = from.Backpack; + } - ConstructorInfo c = t.GetConstructor( Type.EmptyTypes ); + Type t = copy.GetType(); - if ( c != null ) - { - try - { - from.SendMessage( "Duping {0}...", m_Amount ); - for ( int i = 0; i < m_Amount; i++ ) - { - if ( c.Invoke( null ) is Item newItem ) - { - CopyProperties( newItem, copy );//copy.Dupe( item, copy.Amount ); - copy.OnAfterDuped( newItem ); - newItem.Parent = null; + //ConstructorInfo[] info = t.GetConstructors(); - if ( pack != null ) - pack.DropItem( newItem ); - else - newItem.MoveToWorld( from.Location, from.Map ); + ConstructorInfo c = t.GetConstructor(Type.EmptyTypes); - newItem.InvalidateProperties(); + if (c != null) + try + { + from.SendMessage("Duping {0}...", m_Amount); + for (int i = 0; i < m_Amount; i++) + if (c.Invoke(null) is Item newItem) + { + CopyProperties(newItem, copy); //copy.Dupe( item, copy.Amount ); + copy.OnAfterDuped(newItem); + newItem.Parent = null; - CommandLogging.WriteLine( from, "{0} {1} duped {2} creating {3}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( targ ), CommandLogging.Format( newItem ) ); - } - } - from.SendMessage( "Done" ); - done = true; - } - catch - { - from.SendMessage( "Error!" ); - return; - } - } + if (pack != null) + pack.DropItem(newItem); + else + newItem.MoveToWorld(from.Location, from.Map); - if ( !done ) - { - from.SendMessage( "Unable to dupe. Item must have a 0 parameter constructor." ); - } - } - } + newItem.InvalidateProperties(); - public static void CopyProperties( Item dest, Item src ) - { - PropertyInfo[] props = src.GetType().GetProperties(); + CommandLogging.WriteLine(from, "{0} {1} duped {2} creating {3}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(targ), + CommandLogging.Format(newItem)); + } - for ( int i = 0; i < props.Length; i++ ) - { - try - { - if ( props[i].CanRead && props[i].CanWrite ) - { - //Console.WriteLine( "Setting {0} = {1}", props[i].Name, props[i].GetValue( src, null ) ); - props[i].SetValue( dest, props[i].GetValue( src, null ), null ); - } - } - catch - { - //Console.WriteLine( "Denied" ); - } - } - } - } -} + from.SendMessage("Done"); + done = true; + } + catch + { + from.SendMessage("Error!"); + return; + } + + if (!done) from.SendMessage("Unable to dupe. Item must have a 0 parameter constructor."); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/ExportWSC.cs b/Scripts/Commands/ExportWSC.cs index 1c91a2aa9..0f743d4a2 100644 --- a/Scripts/Commands/ExportWSC.cs +++ b/Scripts/Commands/ExportWSC.cs @@ -4,63 +4,61 @@ using Server.Items; namespace Server.Commands { - public class ExportCommand - { - private const string ExportFile = @"C:\Uo\WorldForge\items.wsc"; + public class ExportCommand + { + private const string ExportFile = @"C:\Uo\WorldForge\items.wsc"; - public static void Initialize() - { - CommandSystem.Register( "ExportWSC", AccessLevel.Administrator, Export_OnCommand ); - } + public static void Initialize() + { + CommandSystem.Register("ExportWSC", AccessLevel.Administrator, Export_OnCommand); + } - public static void Export_OnCommand( CommandEventArgs e ) - { - StreamWriter w = new StreamWriter( ExportFile ); - ArrayList remove = new ArrayList(); - int count = 0; + public static void Export_OnCommand(CommandEventArgs e) + { + StreamWriter w = new StreamWriter(ExportFile); + ArrayList remove = new ArrayList(); + int count = 0; - e.Mobile.SendMessage( "Exporting all static items to \"{0}\"...", ExportFile ); - e.Mobile.SendMessage( "This will delete all static items in the world. Please make a backup." ); + e.Mobile.SendMessage("Exporting all static items to \"{0}\"...", ExportFile); + e.Mobile.SendMessage("This will delete all static items in the world. Please make a backup."); - foreach ( Item item in World.Items.Values ) - { - if ( ( item is Static || item is BaseFloor || item is BaseWall ) - && item.RootParent == null ) - { - w.WriteLine( "SECTION WORLDITEM {0}", count ); - w.WriteLine( "{" ); - w.WriteLine( "SERIAL {0}", item.Serial ); - w.WriteLine( "NAME #" ); - w.WriteLine( "NAME2 #" ); - w.WriteLine( "ID {0}", item.ItemID ); - w.WriteLine( "X {0}", item.X ); - w.WriteLine( "Y {0}", item.Y ); - w.WriteLine( "Z {0}", item.Z ); - w.WriteLine( "COLOR {0}", item.Hue ); - w.WriteLine( "CONT -1" ); - w.WriteLine( "TYPE 0" ); - w.WriteLine( "AMOUNT 1" ); - w.WriteLine( "WEIGHT 255" ); - w.WriteLine( "OWNER -1" ); - w.WriteLine( "SPAWN -1" ); - w.WriteLine( "VALUE 1" ); - w.WriteLine( "}" ); - w.WriteLine( "" ); + foreach (Item item in World.Items.Values) + if ((item is Static || item is BaseFloor || item is BaseWall) + && item.RootParent == null) + { + w.WriteLine("SECTION WORLDITEM {0}", count); + w.WriteLine("{"); + w.WriteLine("SERIAL {0}", item.Serial); + w.WriteLine("NAME #"); + w.WriteLine("NAME2 #"); + w.WriteLine("ID {0}", item.ItemID); + w.WriteLine("X {0}", item.X); + w.WriteLine("Y {0}", item.Y); + w.WriteLine("Z {0}", item.Z); + w.WriteLine("COLOR {0}", item.Hue); + w.WriteLine("CONT -1"); + w.WriteLine("TYPE 0"); + w.WriteLine("AMOUNT 1"); + w.WriteLine("WEIGHT 255"); + w.WriteLine("OWNER -1"); + w.WriteLine("SPAWN -1"); + w.WriteLine("VALUE 1"); + w.WriteLine("}"); + w.WriteLine(""); - count++; - remove.Add( item ); - w.Flush(); - } - } + count++; + remove.Add(item); + w.Flush(); + } - w.Close(); + w.Close(); - foreach( Item item in remove ) - item.Delete(); + foreach (Item item in remove) + item.Delete(); - e.Mobile.SendMessage( "Export complete. Exported {0} statics.", count ); - } - } + e.Mobile.SendMessage("Export complete. Exported {0} statics.", count); + } + } } /*SECTION WORLDITEM 1 { @@ -78,4 +76,4 @@ WEIGHT 25500 OWNER -1 SPAWN -1 VALUE 1 -}*/ +}*/ \ No newline at end of file diff --git a/Scripts/Commands/GenCategorization.cs b/Scripts/Commands/GenCategorization.cs index e9f4d3cb0..cc94c8d78 100644 --- a/Scripts/Commands/GenCategorization.cs +++ b/Scripts/Commands/GenCategorization.cs @@ -1,413 +1,410 @@ using System; -using System.IO; -using System.Xml; using System.Collections; +using System.IO; using System.Reflection; +using System.Text; +using System.Xml; using Server.Items; namespace Server.Commands { - public class Categorization - { - private static CategoryEntry m_RootItems, m_RootMobiles; + public class Categorization + { + private static CategoryEntry m_RootItems, m_RootMobiles; - public static CategoryEntry Items - { - get - { - if ( m_RootItems == null ) - Load(); + private static Type typeofItem = typeof(Item); + private static Type typeofMobile = typeof(Mobile); + private static Type typeofConstructible = typeof(ConstructibleAttribute); - return m_RootItems; - } - } + public static CategoryEntry Items + { + get + { + if (m_RootItems == null) + Load(); - public static CategoryEntry Mobiles - { - get - { - if ( m_RootMobiles == null ) - Load(); + return m_RootItems; + } + } - return m_RootMobiles; - } - } + public static CategoryEntry Mobiles + { + get + { + if (m_RootMobiles == null) + Load(); - public static void Initialize() - { - CommandSystem.Register( "RebuildCategorization", AccessLevel.Administrator, RebuildCategorization_OnCommand ); - } + return m_RootMobiles; + } + } - [Usage( "RebuildCategorization" )] - [Description( "Rebuilds the categorization data file used by the Add command." )] - public static void RebuildCategorization_OnCommand( CommandEventArgs e ) - { - CategoryEntry root = new CategoryEntry( null, "Add Menu", new[]{ Items, Mobiles } ); + public static void Initialize() + { + CommandSystem.Register("RebuildCategorization", AccessLevel.Administrator, RebuildCategorization_OnCommand); + } - Export( root, "Data/objects.xml", "Objects" ); + [Usage("RebuildCategorization")] + [Description("Rebuilds the categorization data file used by the Add command.")] + public static void RebuildCategorization_OnCommand(CommandEventArgs e) + { + CategoryEntry root = new CategoryEntry(null, "Add Menu", new[] { Items, Mobiles }); - e.Mobile.SendMessage( "Categorization menu rebuilt." ); - } + Export(root, "Data/objects.xml", "Objects"); - public static void RecurseFindCategories( CategoryEntry ce, ArrayList list ) - { - list.Add( ce ); + e.Mobile.SendMessage("Categorization menu rebuilt."); + } - for ( int i = 0; i < ce.SubCategories.Length; ++i ) - RecurseFindCategories( ce.SubCategories[i], list ); - } + public static void RecurseFindCategories(CategoryEntry ce, ArrayList list) + { + list.Add(ce); - public static void Export( CategoryEntry ce, string fileName, string title ) - { - XmlTextWriter xml = new XmlTextWriter( fileName, System.Text.Encoding.UTF8 ); + for (int i = 0; i < ce.SubCategories.Length; ++i) + RecurseFindCategories(ce.SubCategories[i], list); + } - xml.Indentation = 1; - xml.IndentChar = '\t'; - xml.Formatting = Formatting.Indented; + public static void Export(CategoryEntry ce, string fileName, string title) + { + XmlTextWriter xml = new XmlTextWriter(fileName, Encoding.UTF8); - xml.WriteStartDocument( true ); + xml.Indentation = 1; + xml.IndentChar = '\t'; + xml.Formatting = Formatting.Indented; - RecurseExport( xml, ce ); + xml.WriteStartDocument(true); - xml.Flush(); - xml.Close(); - } + RecurseExport(xml, ce); - public static void RecurseExport( XmlTextWriter xml, CategoryEntry ce ) - { - xml.WriteStartElement( "category" ); + xml.Flush(); + xml.Close(); + } - xml.WriteAttributeString( "title", ce.Title ); + public static void RecurseExport(XmlTextWriter xml, CategoryEntry ce) + { + xml.WriteStartElement("category"); - ArrayList subCats = new ArrayList( ce.SubCategories ); + xml.WriteAttributeString("title", ce.Title); - subCats.Sort( new CategorySorter() ); + ArrayList subCats = new ArrayList(ce.SubCategories); - for ( int i = 0; i < subCats.Count; ++i ) - RecurseExport( xml, (CategoryEntry)subCats[i] ); + subCats.Sort(new CategorySorter()); - ce.Matched.Sort( new CategorySorter() ); + for (int i = 0; i < subCats.Count; ++i) + RecurseExport(xml, (CategoryEntry)subCats[i]); - for ( int i = 0; i < ce.Matched.Count; ++i ) - { - CategoryTypeEntry cte = (CategoryTypeEntry)ce.Matched[i]; + ce.Matched.Sort(new CategorySorter()); - xml.WriteStartElement( "object" ); + for (int i = 0; i < ce.Matched.Count; ++i) + { + CategoryTypeEntry cte = (CategoryTypeEntry)ce.Matched[i]; - xml.WriteAttributeString( "type", cte.Type.ToString() ); + xml.WriteStartElement("object"); - if ( cte.Object is Item item ) - { - int itemID = item.ItemID; + xml.WriteAttributeString("type", cte.Type.ToString()); - if ( item is BaseAddon addon && addon.Components.Count == 1 ) - itemID = addon.Components[0].ItemID; + if (cte.Object is Item item) + { + int itemID = item.ItemID; - if ( itemID > TileData.MaxItemValue ) - itemID = 1; + if (item is BaseAddon addon && addon.Components.Count == 1) + itemID = addon.Components[0].ItemID; - xml.WriteAttributeString( "gfx", XmlConvert.ToString( itemID ) ); + if (itemID > TileData.MaxItemValue) + itemID = 1; - int hue = item.Hue & 0x7FFF; + xml.WriteAttributeString("gfx", XmlConvert.ToString(itemID)); - if ( (hue & 0x4000) != 0 ) - hue = 0; + int hue = item.Hue & 0x7FFF; - if ( hue != 0 ) - xml.WriteAttributeString( "hue", XmlConvert.ToString( hue ) ); + if ((hue & 0x4000) != 0) + hue = 0; - item.Delete(); - } - else if ( cte.Object is Mobile mob ) - { - int itemID = ShrinkTable.Lookup( mob, 1 ); + if (hue != 0) + xml.WriteAttributeString("hue", XmlConvert.ToString(hue)); - xml.WriteAttributeString( "gfx", XmlConvert.ToString( itemID ) ); + item.Delete(); + } + else if (cte.Object is Mobile mob) + { + int itemID = ShrinkTable.Lookup(mob, 1); - int hue = mob.Hue & 0x7FFF; + xml.WriteAttributeString("gfx", XmlConvert.ToString(itemID)); - if ( (hue & 0x4000) != 0 ) - hue = 0; + int hue = mob.Hue & 0x7FFF; - if ( hue != 0 ) - xml.WriteAttributeString( "hue", XmlConvert.ToString( hue ) ); + if ((hue & 0x4000) != 0) + hue = 0; - mob.Delete(); - } + if (hue != 0) + xml.WriteAttributeString("hue", XmlConvert.ToString(hue)); - xml.WriteEndElement(); - } + mob.Delete(); + } - xml.WriteEndElement(); - } + xml.WriteEndElement(); + } - public static void Load() - { - ArrayList types = new ArrayList(); + xml.WriteEndElement(); + } - AddTypes( Core.Assembly, types ); + public static void Load() + { + ArrayList types = new ArrayList(); - for ( int i = 0; i < ScriptCompiler.Assemblies.Length; ++i ) - AddTypes( ScriptCompiler.Assemblies[i], types ); + AddTypes(Core.Assembly, types); - m_RootItems = Load( types, "Data/items.cfg" ); - m_RootMobiles = Load( types, "Data/mobiles.cfg" ); - } + for (int i = 0; i < ScriptCompiler.Assemblies.Length; ++i) + AddTypes(ScriptCompiler.Assemblies[i], types); - private static CategoryEntry Load( ArrayList types, string config ) - { - CategoryLine[] lines = CategoryLine.Load( config ); + m_RootItems = Load(types, "Data/items.cfg"); + m_RootMobiles = Load(types, "Data/mobiles.cfg"); + } - if ( lines.Length > 0 ) - { - int index = 0; - CategoryEntry root = new CategoryEntry( null, lines, ref index ); + private static CategoryEntry Load(ArrayList types, string config) + { + CategoryLine[] lines = CategoryLine.Load(config); - Fill( root, types ); + if (lines.Length > 0) + { + int index = 0; + CategoryEntry root = new CategoryEntry(null, lines, ref index); - return root; - } + Fill(root, types); - return new CategoryEntry(); - } + return root; + } - private static Type typeofItem = typeof( Item ); - private static Type typeofMobile = typeof( Mobile ); - private static Type typeofConstructible = typeof( ConstructibleAttribute ); + return new CategoryEntry(); + } - private static bool IsConstructible( Type type ) - { - if ( !type.IsSubclassOf( typeofItem ) && !type.IsSubclassOf( typeofMobile ) ) - return false; + private static bool IsConstructible(Type type) + { + if (!type.IsSubclassOf(typeofItem) && !type.IsSubclassOf(typeofMobile)) + return false; - ConstructorInfo ctor = type.GetConstructor( Type.EmptyTypes ); + ConstructorInfo ctor = type.GetConstructor(Type.EmptyTypes); - return ( ctor != null && ctor.IsDefined( typeofConstructible, false ) ); - } + return ctor != null && ctor.IsDefined(typeofConstructible, false); + } - private static void AddTypes( Assembly asm, ArrayList types ) - { - Type[] allTypes = asm.GetTypes(); + private static void AddTypes(Assembly asm, ArrayList types) + { + Type[] allTypes = asm.GetTypes(); - for ( int i = 0; i < allTypes.Length; ++i ) - { - Type type = allTypes[i]; + for (int i = 0; i < allTypes.Length; ++i) + { + Type type = allTypes[i]; - if ( type.IsAbstract ) - continue; + if (type.IsAbstract) + continue; - if ( IsConstructible( type ) ) - types.Add( type ); - } - } + if (IsConstructible(type)) + types.Add(type); + } + } - private static void Fill( CategoryEntry root, ArrayList list ) - { - for ( int i = 0; i < list.Count; ++i ) - { - Type type = (Type)list[i]; - CategoryEntry match = GetDeepestMatch( root, type ); + private static void Fill(CategoryEntry root, ArrayList list) + { + for (int i = 0; i < list.Count; ++i) + { + Type type = (Type)list[i]; + CategoryEntry match = GetDeepestMatch(root, type); - if ( match == null ) - continue; + if (match == null) + continue; - try - { - match.Matched.Add( new CategoryTypeEntry( type ) ); - } - catch - { - } - } - } + try + { + match.Matched.Add(new CategoryTypeEntry(type)); + } + catch + { + } + } + } - private static CategoryEntry GetDeepestMatch( CategoryEntry root, Type type ) - { - if ( !root.IsMatch( type ) ) - return null; + private static CategoryEntry GetDeepestMatch(CategoryEntry root, Type type) + { + if (!root.IsMatch(type)) + return null; - for ( int i = 0; i < root.SubCategories.Length; ++i ) - { - CategoryEntry check = GetDeepestMatch( root.SubCategories[i], type ); + for (int i = 0; i < root.SubCategories.Length; ++i) + { + CategoryEntry check = GetDeepestMatch(root.SubCategories[i], type); - if ( check != null ) - return check; - } + if (check != null) + return check; + } - return root; - } - } + return root; + } + } - public class CategorySorter : IComparer - { - public int Compare( object x, object y ) - { - string a = null, b = null; + public class CategorySorter : IComparer + { + public int Compare(object x, object y) + { + string a = null, b = null; - if ( x is CategoryEntry entry ) - a = entry.Title; - else if ( x is CategoryTypeEntry xTypeEntry ) - a = xTypeEntry.Type.Name; + if (x is CategoryEntry entry) + a = entry.Title; + else if (x is CategoryTypeEntry xTypeEntry) + a = xTypeEntry.Type.Name; - if ( y is CategoryEntry categoryEntry ) - b = categoryEntry.Title; - else if ( y is CategoryTypeEntry yTypeEntry ) - b = yTypeEntry.Type.Name; + if (y is CategoryEntry categoryEntry) + b = categoryEntry.Title; + else if (y is CategoryTypeEntry yTypeEntry) + b = yTypeEntry.Type.Name; - if ( a == null && b == null ) - return 0; + if (a == null && b == null) + return 0; - if ( a == null ) - return 1; + if (a == null) + return 1; - if ( b == null ) - return -1; + if (b == null) + return -1; - return a.CompareTo( b ); - } - } + return a.CompareTo(b); + } + } - public class CategoryTypeEntry - { - public Type Type { get; } + public class CategoryTypeEntry + { + public CategoryTypeEntry(Type type) + { + Type = type; + Object = Activator.CreateInstance(type); + } - public object Object { get; } + public Type Type{ get; } - public CategoryTypeEntry( Type type ) - { - Type = type; - Object = Activator.CreateInstance( type ); - } - } + public object Object{ get; } + } - public class CategoryEntry - { - public string Title { get; } + public class CategoryEntry + { + public CategoryEntry() + { + Title = "(empty)"; + Matches = new Type[0]; + SubCategories = new CategoryEntry[0]; + Matched = new ArrayList(); + } - public Type[] Matches { get; } + public CategoryEntry(CategoryEntry parent, string title, CategoryEntry[] subCats) + { + Parent = parent; + Title = title; + SubCategories = subCats; + Matches = new Type[0]; + Matched = new ArrayList(); + } - public CategoryEntry Parent { get; } + public CategoryEntry(CategoryEntry parent, CategoryLine[] lines, ref int index) + { + Parent = parent; - public CategoryEntry[] SubCategories { get; } + string text = lines[index].Text; - public ArrayList Matched { get; } + int start = text.IndexOf('('); - public CategoryEntry() - { - Title = "(empty)"; - Matches = new Type[0]; - SubCategories = new CategoryEntry[0]; - Matched = new ArrayList(); - } + if (start < 0) + throw new FormatException($"Input string not correctly formatted ('{text}')"); - public CategoryEntry( CategoryEntry parent, string title, CategoryEntry[] subCats ) - { - Parent = parent; - Title = title; - SubCategories = subCats; - Matches = new Type[0]; - Matched = new ArrayList(); - } + Title = text.Substring(0, start).Trim(); - public bool IsMatch( Type type ) - { - bool isMatch = false; + int end = text.IndexOf(')', ++start); - for ( int i = 0; !isMatch && i < Matches.Length; ++i ) - isMatch = ( type == Matches[i] || type.IsSubclassOf( Matches[i] ) ); + if (end < start) + throw new FormatException($"Input string not correctly formatted ('{text}')"); - return isMatch; - } + text = text.Substring(start, end - start); + string[] split = text.Split(';'); - public CategoryEntry( CategoryEntry parent, CategoryLine[] lines, ref int index ) - { - Parent = parent; + ArrayList list = new ArrayList(); - string text = lines[index].Text; + for (int i = 0; i < split.Length; ++i) + { + Type type = ScriptCompiler.FindTypeByName(split[i].Trim()); - int start = text.IndexOf( '(' ); + if (type == null) + Console.WriteLine("Match type not found ('{0}')", split[i].Trim()); + else + list.Add(type); + } - if ( start < 0 ) - throw new FormatException($"Input string not correctly formatted ('{text}')"); + Matches = (Type[])list.ToArray(typeof(Type)); + list.Clear(); - Title = text.Substring( 0, start ).Trim(); + int ourIndentation = lines[index].Indentation; - int end = text.IndexOf( ')', ++start ); + ++index; - if ( end < start ) - throw new FormatException($"Input string not correctly formatted ('{text}')"); + while (index < lines.Length && lines[index].Indentation > ourIndentation) + list.Add(new CategoryEntry(this, lines, ref index)); - text = text.Substring( start, end-start ); - string[] split = text.Split( ';' ); + SubCategories = (CategoryEntry[])list.ToArray(typeof(CategoryEntry)); + list.Clear(); - ArrayList list = new ArrayList(); + Matched = list; + } - for ( int i = 0; i < split.Length; ++i ) - { - Type type = ScriptCompiler.FindTypeByName( split[i].Trim() ); + public string Title{ get; } - if ( type == null ) - Console.WriteLine( "Match type not found ('{0}')", split[i].Trim() ); - else - list.Add( type ); - } + public Type[] Matches{ get; } - Matches = (Type[])list.ToArray( typeof( Type ) ); - list.Clear(); + public CategoryEntry Parent{ get; } - int ourIndentation = lines[index].Indentation; + public CategoryEntry[] SubCategories{ get; } - ++index; + public ArrayList Matched{ get; } - while ( index < lines.Length && lines[index].Indentation > ourIndentation ) - list.Add( new CategoryEntry( this, lines, ref index ) ); + public bool IsMatch(Type type) + { + bool isMatch = false; - SubCategories = (CategoryEntry[])list.ToArray( typeof( CategoryEntry ) ); - list.Clear(); + for (int i = 0; !isMatch && i < Matches.Length; ++i) + isMatch = type == Matches[i] || type.IsSubclassOf(Matches[i]); - Matched = list; - } - } + return isMatch; + } + } - public class CategoryLine - { - public int Indentation { get; } + public class CategoryLine + { + public CategoryLine(string input) + { + int index; - public string Text { get; } + for (index = 0; index < input.Length; ++index) + if (char.IsLetter(input, index)) + break; - public CategoryLine( string input ) - { - int index; + if (index >= input.Length) + throw new FormatException($"Input string not correctly formatted ('{input}')"); - for ( index = 0; index < input.Length; ++index ) - { - if ( char.IsLetter( input, index ) ) - break; - } + Indentation = index; + Text = input.Substring(index); + } - if ( index >= input.Length ) - throw new FormatException($"Input string not correctly formatted ('{input}')"); + public int Indentation{ get; } - Indentation = index; - Text = input.Substring( index ); - } + public string Text{ get; } - public static CategoryLine[] Load( string path ) - { - ArrayList list = new ArrayList(); + public static CategoryLine[] Load(string path) + { + ArrayList list = new ArrayList(); - if ( File.Exists( path ) ) - { - using ( StreamReader ip = new StreamReader( path ) ) - { - string line; + if (File.Exists(path)) + using (StreamReader ip = new StreamReader(path)) + { + string line; - while ( (line = ip.ReadLine()) != null ) - list.Add( new CategoryLine( line ) ); - } - } + while ((line = ip.ReadLine()) != null) + list.Add(new CategoryLine(line)); + } - return (CategoryLine[])list.ToArray( typeof( CategoryLine ) ); - } - } -} + return (CategoryLine[])list.ToArray(typeof(CategoryLine)); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/GenTeleporter.cs b/Scripts/Commands/GenTeleporter.cs index ef122dde2..1c42392d7 100644 --- a/Scripts/Commands/GenTeleporter.cs +++ b/Scripts/Commands/GenTeleporter.cs @@ -3,1049 +3,1041 @@ using Server.Items; namespace Server.Commands { - public class GenTeleporter - { - public GenTeleporter() - { - } - - public static void Initialize() - { - CommandSystem.Register( "TelGen", AccessLevel.Administrator, GenTeleporter_OnCommand ); - } - - [Usage( "TelGen" )] - [Description( "Generates world/dungeon teleporters for all facets." )] - public static void GenTeleporter_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( "Generating teleporters, please wait." ); - - int count = new TeleportersCreator().CreateTeleporters(); - - count += new SHTeleporter.SHTeleporterCreator().CreateSHTeleporters(); - - e.Mobile.SendMessage( "Teleporter generating complete. {0} teleporters were generated.", count ); - } - - public class TeleportersCreator - { - private int m_Count; - - public TeleportersCreator() - { - } - - private static Queue m_Queue = new Queue(); - - public static bool FindTeleporter( Map map, Point3D p ) - { - IPooledEnumerable eable = map.GetItemsInRange( p, 0 ); - - foreach ( Item item in eable ) - { - if ( item is Teleporter && !(item is KeywordTeleporter) && !(item is SkillTeleporter) ) - { - int delta = item.Z - p.Z; - - if ( delta >= -12 && delta <= 12 ) - m_Queue.Enqueue( item ); - } - } - - eable.Free(); - - while ( m_Queue.Count > 0 ) - m_Queue.Dequeue().Delete(); - - return false; - } - - public void CreateTeleporter( Point3D pointLocation, Point3D pointDestination, Map mapLocation, Map mapDestination, bool back ) - { - if ( !FindTeleporter( mapLocation, pointLocation ) ) - { - m_Count++; - - Teleporter tel = new Teleporter( pointDestination, mapDestination ); - - tel.MoveToWorld( pointLocation, mapLocation ); - } - - if ( back && !FindTeleporter( mapDestination, pointDestination ) ) - { - m_Count++; - - Teleporter telBack = new Teleporter( pointLocation, mapLocation ); - - telBack.MoveToWorld( pointDestination, mapDestination ); - } - } - - public void CreateTeleporter( int xLoc, int yLoc, int zLoc, int xDest, int yDest, int zDest, Map map, bool back ) - { - CreateTeleporter( new Point3D( xLoc, yLoc, zLoc ), new Point3D( xDest, yDest, zDest ), map, map, back); - } - - public void CreateTeleporter( int xLoc, int yLoc, int zLoc, int xDest, int yDest, int zDest, Map mapLocation, Map mapDestination, bool back ) - { - CreateTeleporter( new Point3D( xLoc, yLoc, zLoc ), new Point3D( xDest, yDest, zDest ), mapLocation, mapDestination, back); - } - - public void DestroyTeleporter( int x, int y, int z, Map map ) - { - Point3D p = new Point3D( x, y, z ); - IPooledEnumerable eable = map.GetItemsInRange( p, 0 ); - - foreach ( Item item in eable ) - { - if ( item is Teleporter && !(item is KeywordTeleporter) && !(item is SkillTeleporter) && item.Z == p.Z ) - m_Queue.Enqueue( item ); - } - - eable.Free(); - - while ( m_Queue.Count > 0 ) - m_Queue.Dequeue().Delete(); - } - - public void CreateTeleportersMap( Map map ) - { - // Shame - CreateTeleporter( 512, 1559, 0, 5394, 127, 0, map, true ); - CreateTeleporter( 513, 1559, 0, 5395, 127, 0, map, true ); - CreateTeleporter( 514, 1559, 0, 5396, 127, 0, map, true ); - CreateTeleporter( 5490, 19, -25, 5514, 10, 5, map, true ); - CreateTeleporter( 5875, 19, -5, 5507, 162, 5, map, true ); - CreateTeleporter( 5604, 102, 5, 5514, 147, 25, map, true ); - - CreateTeleporter( 5513, 176, 5, 5540, 187, 0, map, false ); - CreateTeleporter( 5538, 170, 5, 5517, 176, 0, map, false ); - - // Hythloth - CreateTeleporter( 4721, 3813, 0, 5904, 16, 64, map, true ); - CreateTeleporter( 4722, 3813, 0, 5905, 16, 64, map, true ); - CreateTeleporter( 4723, 3813, 0, 5906, 16, 64, map, true ); - CreateTeleporter( 6040, 192, 12, 6059, 88, 24, map, true ); - CreateTeleporter( 6040, 193, 12, 6059, 89, 24, map, true ); - CreateTeleporter( 6040, 194, 12, 6059, 90, 24, map, true ); - - DestroyTeleporter( 5920, 168, 16, map ); - DestroyTeleporter( 5920, 169, 17, map ); - DestroyTeleporter( 5920, 170, 16, map ); - - CreateTeleporter( 5920, 168, 16, 6083, 144, -20, map, false ); - CreateTeleporter( 5920, 169, 16, 6083, 145, -20, map, false ); - CreateTeleporter( 5920, 170, 16, 6083, 146, -20, map, false ); - - CreateTeleporter( 6083, 144, -20, 5920, 168, 22, map, false ); - CreateTeleporter( 6083, 145, -20, 5920, 169, 22, map, false ); - CreateTeleporter( 6083, 146, -20, 5920, 170, 22, map, false ); - - DestroyTeleporter( 5906, 96, 0, map ); - - CreateTeleporter( 5972, 168, 0, 5905, 100, 0, map, false ); - CreateTeleporter( 5906, 96, 0, 5977, 169, 0, map, false ); - - // Covetous - CreateTeleporter( 2498, 916, 0, 5455, 1864, 0, map, true ); - CreateTeleporter( 2499, 916, 0, 5456, 1864, 0, map, true ); - CreateTeleporter( 2500, 916, 0, 5457, 1864, 0, map, true ); - CreateTeleporter( 2384, 836, 0, 5615, 1996, 0, map, true ); - CreateTeleporter( 2384, 837, 0, 5615, 1997, 0, map, true ); - CreateTeleporter( 2384, 838, 0, 5615, 1998, 0, map, true ); - CreateTeleporter( 2420, 883, 0, 5392, 1959, 0, map, true ); - CreateTeleporter( 2421, 883, 0, 5393, 1959, 0, map, true ); - CreateTeleporter( 2422, 883, 0, 5394, 1959, 0, map, true ); - CreateTeleporter( 2455, 858, 0, 5388, 2027, 0, map, true ); - CreateTeleporter( 2456, 858, 0, 5389, 2027, 0, map, true ); - CreateTeleporter( 2457, 858, 0, 5390, 2027, 0, map, true ); - CreateTeleporter( 2544, 850, 0, 5578, 1927, 0, map, true ); - CreateTeleporter( 2545, 850, 0, 5579, 1927, 0, map, true ); - CreateTeleporter( 2546, 850, 0, 5580, 1927, 0, map, true ); - - CreateTeleporter( 5551, 1805, 12, 5556, 1825, -3, map, false ); - CreateTeleporter( 5552, 1805, 12, 5557, 1825, -3, map, false ); - CreateTeleporter( 5553, 1805, 12, 5557, 1825, -3, map, false ); - - DestroyTeleporter( 5551, 1807, 0, map ); - DestroyTeleporter( 5552, 1807, 0, map ); - DestroyTeleporter( 5553, 1807, 0, map ); - - CreateTeleporter( 5556, 1826, -10, 5551, 1806, 7, map, false ); - CreateTeleporter( 5557, 1826, -10, 5552, 1806, 7, map, false ); - - DestroyTeleporter( 5556, 1825, -7, map ); - DestroyTeleporter( 5556, 1827, -13, map ); - DestroyTeleporter( 5557, 1825, -7, map ); - DestroyTeleporter( 5557, 1827, -13, map ); - DestroyTeleporter( 5558, 1825, -7, map ); - - DestroyTeleporter( 5468, 1804, 0, map ); - DestroyTeleporter( 5468, 1805, 0, map ); - DestroyTeleporter( 5468, 1806, 0, map ); - - CreateTeleporter( 5466, 1804, 12, 5593, 1840, -3, map, false ); - CreateTeleporter( 5466, 1805, 12, 5593, 1841, -3, map, false ); - CreateTeleporter( 5466, 1806, 12, 5593, 1842, -3, map, false ); - - DestroyTeleporter( 5595, 1840, -14, map ); - DestroyTeleporter( 5595, 1840, -14, map ); - - CreateTeleporter( 5594, 1840, -8, 5467, 1804, 7, map, false ); - CreateTeleporter( 5594, 1841, -8, 5467, 1805, 7, map, false ); - - // Wrong - CreateTeleporter( 5824, 631, 5, 2041, 215, 14, map, true ); - CreateTeleporter( 5825, 631, 5, 2042, 215, 14, map, true ); - CreateTeleporter( 5825, 631, 5, 2043, 215, 14, map, true ); - CreateTeleporter( 5698, 662, 0, 5793, 527, 10, map, false ); - - DestroyTeleporter( 5863, 525, 15, map ); - DestroyTeleporter( 5863, 526, 15, map ); - DestroyTeleporter( 5863, 527, 15, map ); - DestroyTeleporter( 5868, 537, 15, map ); - DestroyTeleporter( 5868, 538, 15, map ); - DestroyTeleporter( 5869, 538, 15, map ); - DestroyTeleporter( 5733, 554, 20, map ); - DestroyTeleporter( 5862, 527, 15, map ); - - // Deceit - CreateTeleporter( 4110, 430, 5, 5187, 639, 0, map, false ); - CreateTeleporter( 4111, 430, 5, 5188, 639, 0, map, false ); - CreateTeleporter( 4112, 430, 5, 5189, 639, 0, map, false ); - CreateTeleporter( 5187, 639, 0, 4110, 430, 5, map, false ); - CreateTeleporter( 5188, 639, 0, 4111, 430, 5, map, false ); - CreateTeleporter( 5189, 639, 0, 4112, 430, 5, map, false ); - CreateTeleporter( 5216, 586, -13, 5304, 533, 2, map, false ); - CreateTeleporter( 5217, 586, -13, 5305, 533, 2, map, false ); - CreateTeleporter( 5218, 586, -13, 5306, 533, 2, map, false ); - CreateTeleporter( 5304, 532, 7, 5216, 585, -8, map, false ); - CreateTeleporter( 5305, 532, 7, 5217, 585, -8, map, false ); - CreateTeleporter( 5306, 532, 7, 5218, 585, -8, map, false ); - CreateTeleporter( 5218, 761, -28, 5305, 651, 7, map, false ); - CreateTeleporter( 5219, 761, -28, 5306, 651, 7, map, false ); - CreateTeleporter( 5305, 650, 12, 5218, 760, -23, map, false ); - CreateTeleporter( 5306, 650, 12, 5219, 760, -23, map, false ); - CreateTeleporter( 5346, 578, 5, 5137, 649, 5, map, true ); - - CreateTeleporter( 5186, 639, 0, 4110, 430, 5, map, false ); - - // Despise - CreateTeleporter( 5504, 569, 46, 5574, 628, 37, map, false ); - CreateTeleporter( 5504, 570, 46, 5574, 629, 37, map, false ); - CreateTeleporter( 5504, 571, 46, 5574, 630, 37, map, false ); - CreateTeleporter( 5572, 632, 17, 5521, 672, 27, map, false ); - CreateTeleporter( 5572, 633, 17, 5521, 673, 27, map, false ); - CreateTeleporter( 5572, 634, 17, 5521, 674, 27, map, false ); - CreateTeleporter( 5573, 628, 42, 5503, 569, 51, map, false ); - CreateTeleporter( 5573, 629, 42, 5503, 570, 51, map, false ); - CreateTeleporter( 5573, 630, 42, 5503, 571, 51, map, false ); - CreateTeleporter( 5588, 632, 30, 1296, 1082, 0, map, true ); - CreateTeleporter( 5588, 630, 30, 1296, 1080, 0, map, true ); - CreateTeleporter( 5588, 631, 30, 1296, 1081, 0, map, true ); - CreateTeleporter( 5522, 672, 32, 5573, 632, 22, map, false ); - CreateTeleporter( 5522, 673, 32, 5573, 633, 22, map, false ); - CreateTeleporter( 5522, 674, 32, 5573, 634, 22, map, false ); - CreateTeleporter( 5386, 756, -8, 5408, 859, 47, map, false ); - CreateTeleporter( 5386, 757, -8, 5408, 860, 47, map, false ); - CreateTeleporter( 5386, 755, -8, 5408, 858, 47, map, false ); - CreateTeleporter( 5409, 860, 52, 5387, 757, -3, map, false ); - CreateTeleporter( 5409, 858, 52, 5387, 755, -3, map, false ); - CreateTeleporter( 5409, 859, 52, 5387, 756, -3, map, false ); - - // Destard - CreateTeleporter( 5242, 1007, 0, 1175, 2635, 0, map, true ); - CreateTeleporter( 5243, 1007, 0, 1176, 2635, 0, map, true ); - CreateTeleporter( 5244, 1007, 0, 1177, 2635, 0, map, true ); - CreateTeleporter( 5142, 797, 22, 5129, 908, -23, map, false ); - CreateTeleporter( 5143, 797, 22, 5130, 908, -23, map, false ); - CreateTeleporter( 5144, 797, 22, 5131, 908, -23, map, false ); - CreateTeleporter( 5145, 797, 22, 5132, 908, -23, map, false ); - CreateTeleporter( 5153, 808, -25, 5134, 984, 17, map, false ); - CreateTeleporter( 5153, 809, -25, 5134, 985, 17, map, false ); - CreateTeleporter( 5153, 810, -25, 5134, 986, 17, map, false ); - CreateTeleporter( 5153, 811, -25, 5134, 987, 17, map, false ); - CreateTeleporter( 5129, 909, -28, 5142, 798, 17, map, false ); - CreateTeleporter( 5130, 909, -28, 5143, 798, 17, map, false ); - CreateTeleporter( 5131, 909, -28, 5144, 798, 17, map, false ); - CreateTeleporter( 5132, 909, -28, 5145, 798, 17, map, false ); - CreateTeleporter( 5133, 984, 22, 5152, 808, -19, map, false ); - CreateTeleporter( 5133, 985, 22, 5152, 809, -19, map, false ); - CreateTeleporter( 5133, 986, 22, 5152, 810, -19, map, false ); - CreateTeleporter( 5133, 987, 22, 5152, 811, -19, map, false ); - - // Buccaneer's Den underground tunnels - - DestroyTeleporter( 2666, 2073, 5, map ); - DestroyTeleporter( 2669, 2072, -20, map ); - DestroyTeleporter( 2669, 2073, -20, map ); - DestroyTeleporter( 2649, 2194, 4, map ); - DestroyTeleporter( 2649, 2195, -14, map ); - - CreateTeleporter( 2603, 2121, -20, 2605, 2130, 8, map, false ); - CreateTeleporter( 2603, 2120, -20, 2605, 2130, 8, map, false ); - CreateTeleporter( 2669, 2071, -20, 2666, 2099, 3, map, false ); - CreateTeleporter( 2669, 2072, -20, 2666, 2099, 3, map, false ); - CreateTeleporter( 2669, 2073, -20, 2666, 2099, 3, map, false ); - CreateTeleporter( 2676, 2241, -18, 2691, 2234, 2, map, false ); - CreateTeleporter( 2676, 2242, -18, 2691, 2234, 2, map, false ); - CreateTeleporter( 2758, 2092, -20, 2756, 2097, 38, map, false ); - CreateTeleporter( 2759, 2092, -20, 2756, 2097, 38, map, false ); - CreateTeleporter( 2685, 2063, 39, 2685, 2063, -20, map, false ); // that should not be a teleporter: on OSI you simply fall under the ground - - // Misc - CreateTeleporter( 5217, 18, 15, 5204, 74, 17, map, false ); - CreateTeleporter( 5200, 71, 17, 5211, 22, 15, map, false ); - CreateTeleporter( 1997, 81, 7, 5881, 242, 0, map, false ); - CreateTeleporter( 5704, 146, -45, 5705, 305, 7, map, false ); - CreateTeleporter( 5704, 147, -45, 5705, 306, 7, map, false ); - CreateTeleporter( 5874, 146, 27, 5208, 2323, 31, map, false ); - CreateTeleporter( 5875, 146, 27, 5208, 2322, 32, map, false ); - CreateTeleporter( 5876, 146, 27, 5208, 2322, 32, map, false ); - CreateTeleporter( 5877, 146, 27, 5208, 2322, 32, map, false ); - CreateTeleporter( 5923, 169, 1, 5925, 171, 22, map, false ); - CreateTeleporter( 2399, 198, 0, 5753, 436, 79, map, false ); - CreateTeleporter( 2400, 198, 0, 5754, 436, 80, map, false ); - DestroyTeleporter( 5166, 245, 15, map ); - DestroyTeleporter( 1361, 883, 0, map ); - CreateTeleporter( 5191, 152, 0, 1367, 891, 0, map, false ); - CreateTeleporter( 5849, 239, -25, 5831, 324, 27, map, false ); - CreateTeleporter( 5850, 239, -25, 5832, 324, 26, map, false ); - CreateTeleporter( 5851, 239, -25, 5833, 324, 28, map, false ); - CreateTeleporter( 5852, 239, -25, 5834, 324, 27, map, false ); - CreateTeleporter( 5853, 239, -23, 5835, 324, 27, map, false ); - CreateTeleporter( 5882, 241, 0, 1998, 81, 5, map, false ); - CreateTeleporter( 5882, 242, 0, 1998, 81, 5, map, false ); - CreateTeleporter( 5882, 243, 0, 1998, 81, 5, map, false ); - CreateTeleporter( 5706, 305, 12, 5705, 146, -45, map, false ); - CreateTeleporter( 5706, 306, 12, 5705, 147, -45, map, false ); - CreateTeleporter( 5748, 362, 2, 313, 786, -24, map, false ); - CreateTeleporter( 5749, 362, 0, 313, 786, -24, map, false ); - CreateTeleporter( 5750, 362, 3, 314, 786, -24, map, false ); - CreateTeleporter( 5753, 324, 21, 5670, 2391, 40, map, false ); - CreateTeleporter( 5831, 323, 34, 5849, 238, -25, map, false ); - CreateTeleporter( 5832, 323, 34, 5850, 238, -25, map, false ); - CreateTeleporter( 5833, 323, 33, 5851, 238, -25, map, false ); - CreateTeleporter( 5834, 323, 33, 5852, 238, -25, map, false ); - CreateTeleporter( 5835, 323, 33, 5853, 238, -23, map, false ); - CreateTeleporter( 5658, 423, 8, 5697, 3659, 2, map, false ); - CreateTeleporter( 5686, 385, 2, 2777, 894, -23, map, false ); - CreateTeleporter( 5686, 386, 2, 2777, 894, -23, map, false ); - CreateTeleporter( 5686, 387, 2, 2777, 895, -23, map, false ); - CreateTeleporter( 5731, 445, -18, 6087, 3676, 18, map, false ); - CreateTeleporter( 5753, 437, 78, 2400, 199, 0, map, false ); - CreateTeleporter( 5850, 432, 0, 5127, 3143, 97, map, false ); - CreateTeleporter( 5850, 433, -2, 5127, 3143, 97, map, false ); - CreateTeleporter( 5850, 434, -1, 5127, 3143, 97, map, false ); - CreateTeleporter( 5850, 431, 2, 5127, 3143, 97, map, false ); - CreateTeleporter( 5826, 465, -1, 1987, 2063, -40, map, false ); - CreateTeleporter( 5827, 465, -1, 1988, 2063, -40, map, false ); - CreateTeleporter( 5828, 465, 0, 1989, 2063, -40, map, false ); - CreateTeleporter( 313, 786, -24, 5748, 361, 2, map, false ); - CreateTeleporter( 314, 786, -24, 5749, 361, 2, map, false ); - CreateTeleporter( 2776, 895, -23, 5685, 387, 2, map, false ); - //CreateTeleporter( 4545, 851, 30, 5736, 3196, 8, map, false ); - DestroyTeleporter( 4545, 851, 30, map ); - CreateTeleporter( 4540, 898, 32, 4442, 1122, 5, map, false ); - CreateTeleporter( 4300, 968, 5, 4442, 1122, 5, map, false ); - CreateTeleporter( 4436, 1107, 5, 4300, 992, 5, map, false ); - CreateTeleporter( 4443, 1137, 5, 4487, 1475, 5, map, false ); - CreateTeleporter( 4449, 1107, 5, 4539, 890, 28, map, false ); - CreateTeleporter( 4449, 1115, 5, 4671, 1135, 10, map, false ); - CreateTeleporter( 4663, 1134, 13, 4442, 1122, 5, map, false ); - CreateTeleporter( 5701, 1320, 16, 5786, 1336, -8, map, false ); - CreateTeleporter( 5702, 1320, 16, 5787, 1336, -8, map, false ); - CreateTeleporter( 5703, 1320, 16, 5788, 1336, -8, map, false ); - CreateTeleporter( 5786, 1335, -13, 5701, 1319, 13, map, false ); - CreateTeleporter( 5787, 1335, -13, 5702, 1319, 13, map, false ); - CreateTeleporter( 5788, 1335, -13, 5703, 1319, 13, map, false ); - CreateTeleporter( 6005, 1380, 1, 5151, 4063, 37, map, false ); - CreateTeleporter( 6005, 1378, 0, 5151, 4062, 37, map, false ); - CreateTeleporter( 6005, 1379, 2, 5151, 4062, 37, map, false ); - CreateTeleporter( 6025, 1344, -26, 5137, 3664, 27, map, false ); - CreateTeleporter( 6025, 1345, -26, 5137, 3664, 27, map, false ); - CreateTeleporter( 6025, 1346, -26, 5137, 3665, 31, map, false ); - CreateTeleporter( 5687, 1424, 38, 2923, 3406, 8, map, false ); - CreateTeleporter( 5792, 1416, 41, 5758, 2908, 15, map, false ); - CreateTeleporter( 5792, 1417, 41, 5758, 2909, 15, map, false ); - CreateTeleporter( 5792, 1415, 41, 5758, 2907, 15, map, false ); - CreateTeleporter( 5899, 1411, 43, 1630, 3320, 0, map, false ); - CreateTeleporter( 5900, 1411, 42, 1630, 3320, 0, map, false ); - CreateTeleporter( 5918, 1412, -29, 5961, 1409, 59, map, false ); - CreateTeleporter( 5918, 1410, -29, 5961, 1408, 59, map, false ); - CreateTeleporter( 5918, 1411, -29, 5961, 1408, 59, map, false ); - CreateTeleporter( 5961, 1408, 59, 5918, 1411, -29, map, false ); - CreateTeleporter( 5961, 1409, 59, 5918, 1412, -29, map, false ); - CreateTeleporter( 6125, 1411, 15, 6075, 3332, 4, map, false ); - CreateTeleporter( 6126, 1411, 15, 6075, 3332, 4, map, false ); - CreateTeleporter( 6127, 1411, 15, 6075, 3332, 4, map, false ); - CreateTeleporter( 6137, 1409, 2, 6140, 1432, 4, map, false ); - CreateTeleporter( 6138, 1409, 2, 6140, 1432, 4, map, false ); - CreateTeleporter( 6140, 1431, 4, 6137, 1408, 2, map, false ); - CreateTeleporter( 4496, 1475, 15, 4442, 1122, 5, map, false ); - CreateTeleporter( 6031, 1501, 42, 1491, 1642, 24, map, false ); - CreateTeleporter( 6031, 1499, 42, 1491, 1640, 24, map, false ); - CreateTeleporter( 1491, 1640, 24, 6032, 1499, 31, map, false ); - CreateTeleporter( 1491, 1642, 24, 6032, 1501, 31, map, false ); - DestroyTeleporter( 5341, 1602, 0, map ); - CreateTeleporter( 5340, 1599, 40, 5426, 3122, -74, map, false ); - CreateTeleporter( 5341, 1599, 40, 5426, 3122, -74, map, false ); - CreateTeleporter( 1987, 2062, -40, 5826, 464, 0, map, false ); - CreateTeleporter( 1988, 2062, -40, 5827, 464, -1, map, false ); - CreateTeleporter( 1989, 2062, -40, 5828, 464, -1, map, false ); - CreateTeleporter( 5203, 2327, 27, 5876, 147, 25, map, false ); - CreateTeleporter( 5207, 2322, 27, 5877, 147, 25, map, false ); - CreateTeleporter( 5207, 2323, 26, 5876, 147, 25, map, false ); - CreateTeleporter( 5670, 2391, 40, 5753, 325, 10, map, false ); - CreateTeleporter( 5974, 2697, 35, 2985, 2890, 35, map, false ); - CreateTeleporter( 5267, 2757, 35, 424, 3283, 35, map, false ); - CreateTeleporter( 5757, 2908, 14, 5791, 1416, 38, map, false ); - CreateTeleporter( 5757, 2909, 15, 5791, 1417, 40, map, false ); - CreateTeleporter( 5757, 2907, 15, 5791, 1415, 38, map, false ); - CreateTeleporter( 1653, 2963, 0, 1677, 2987, 0, map, false ); - CreateTeleporter( 1677, 2987, 0, 1675, 2987, 20, map, false ); - CreateTeleporter( 5426, 3123, -80, 5341, 1602, 0, map, false ); - CreateTeleporter( 5126, 3143, 99, 5849, 432, 1, map, false ); - //CreateTeleporter( 5736, 3196, 8, 4545, 851, 30, map, false ); - DestroyTeleporter( 5736, 3196, 8, map ); - CreateTeleporter( 424, 3283, 35, 5267, 2757, 35, map, false ); - CreateTeleporter( 1629, 3320, 0, 5899, 1411, 43, map, false ); - CreateTeleporter( 6075, 3332, 4, 6126, 1410, 15, map, false ); - CreateTeleporter( 2923, 3405, 6, 5687, 1423, 39, map, false ); - CreateTeleporter( 1142, 3621, 5, 1414, 3828, 5, map, false ); - CreateTeleporter( 5137, 3664, 27, 6025, 1344, -26, map, false ); - CreateTeleporter( 5137, 3665, 31, 6025, 1345, -26, map, false ); - CreateTeleporter( 5697, 3660, -5, 5658, 424, 0, map, false ); - CreateTeleporter( 6086, 3676, 16, 5731, 446, -16, map, false ); - CreateTeleporter( 1409, 3824, 5, 1124, 3623, 5, map, false ); - CreateTeleporter( 1419, 3832, 5, 1466, 4015, 5, map, false ); - CreateTeleporter( 1406, 3996, 5, 1414, 3828, 5, map, false ); - CreateTeleporter( 5150, 4062, 38, 6005, 1378, 0, map, false ); - CreateTeleporter( 5150, 4063, 38, 6005, 1380, 1, map, false ); - CreateTeleporter( 5906, 4069, 26, 2494, 3576, 5, map, true ); - CreateTeleporter( 2985, 2890, 35, 5974, 2697, 35, map, false ); - - // Mondain's Legacy dungeons - - // Sanctuary - CreateTeleporter( 6172, 21, 0, 765, 1645, 0, map, false ); // Entrance gate - CreateTeleporter( 6172, 22, 0, 765, 1646, 0, map, false ); - CreateTeleporter( 6172, 23, 0, 765, 1647, 0, map, false ); - CreateTeleporter( 766, 1645, 0, 6174, 21, 0, map, false ); - CreateTeleporter( 766, 1646, 0, 6174, 22, 0, map, false ); - CreateTeleporter( 766, 1647, 0, 6174, 23, 0, map, false ); - - CreateTeleporter( 6173, 176, -10, 6233, 15, -10, map, false ); // Zone change - CreateTeleporter( 6174, 176, -10, 6234, 15, -10, map, false ); - CreateTeleporter( 6175, 176, -10, 6235, 15, -10, map, false ); - CreateTeleporter( 6176, 176, -10, 6236, 15, -10, map, false ); - CreateTeleporter( 6177, 176, -10, 6237, 15, -10, map, false ); - CreateTeleporter( 6178, 176, -10, 6238, 15, -10, map, false ); - CreateTeleporter( 6179, 176, -10, 6239, 15, -10, map, false ); - CreateTeleporter( 6233, 14, -10, 6172, 174, -10, map, false ); - CreateTeleporter( 6234, 14, -10, 6173, 174, -10, map, false ); - CreateTeleporter( 6235, 14, -10, 6174, 174, -10, map, false ); - CreateTeleporter( 6236, 14, -10, 6175, 174, -10, map, false ); - CreateTeleporter( 6237, 14, -10, 6176, 174, -10, map, false ); - CreateTeleporter( 6238, 14, -10, 6177, 174, -10, map, false ); - CreateTeleporter( 6239, 14, -10, 6177, 174, -10, map, false ); - CreateTeleporter( 6240, 14, -10, 6178, 174, -10, map, false ); - - CreateTeleporter( 6256, 97, -4, 6257, 95, -10, map, false ); // Ladders - CreateTeleporter( 6260, 97, -4, 6260, 95, -10, map, false ); - CreateTeleporter( 6263, 97, -4, 6262, 95, -10, map, false ); - CreateTeleporter( 6269, 97, -4, 6269, 95, -10, map, false ); - CreateTeleporter( 6273, 97, -4, 6272, 95, -10, map, false ); - CreateTeleporter( 6262, 95, -10, 6262, 99, -10, map, false ); - - CreateTeleporter( 6159, 130, 0, 6317, 63, -20, map, false ); // Holes - CreateTeleporter( 6164, 73, 0, 6320, 22, -20, map, false ); - CreateTeleporter( 6161, 163, -10, 6321, 106, -20, map, false ); - CreateTeleporter( 6276, 40, -10, 6374, 124, -20, map, false ); - CreateTeleporter( 6211, 106, 0, 6355, 34, -20, map, false ); - - CreateTeleporter( 6316, 62, -5, 6160, 131, 0, map, false ); // Cave ladders - CreateTeleporter( 6319, 19, -20, 6165, 74, 0, map, false ); // This actually goes to (6165, 75) inside the wall... - CreateTeleporter( 6356, 32, -9, 6210, 105, 0, map, false ); - CreateTeleporter( 6374, 125, -20, 6277, 41, -10, map, false ); - - CreateTeleporter( 6373, 49, -20, 801, 1682, 0, map, false ); - CreateTeleporter( 6374, 49, -20, 801, 1682, 0, map, false ); - CreateTeleporter( 6375, 49, -20, 801, 1682, 0, map, false ); - CreateTeleporter( 6376, 49, -20, 801, 1682, 0, map, false ); - CreateTeleporter( 6377, 49, -20, 801, 1682, 0, map, false ); - - // Painted Caves - CreateTeleporter( 1714, 2996, 0, 6308, 892, 0, map, false ); // Entrance - CreateTeleporter( 1714, 2997, 0, 6308, 892, 0, map, false ); - CreateTeleporter( 6310, 890, 0, 1716, 2997, 0, map, false ); - CreateTeleporter( 6310, 891, 0, 1716, 2997, 0, map, false ); - CreateTeleporter( 6310, 892, 0, 1716, 2997, 0, map, false ); - CreateTeleporter( 6310, 893, 0, 1716, 2997, 0, map, false ); - } - - public void CreateTeleportersMap2( Map map ) - { - // Dungeon of rock - CreateTeleporter( 2186, 294, -27, 2186, 33, -27, map, true ); - CreateTeleporter( 2187, 294, -27, 2187, 33, -27, map, true ); - CreateTeleporter( 2188, 294, -27, 2188, 33, -27, map, true ); - CreateTeleporter( 2189, 294, -27, 2189, 33, -27, map, true ); - CreateTeleporter( 2189, 320, -7, 1788, 569, 74, map, true ); - CreateTeleporter( 2188, 320, -7, 1787, 569, 74, map, true ); - CreateTeleporter( 2187, 320, -7, 1787, 569, 74, map, false ); - - // Spider Cave - DestroyTeleporter( 1783, 993, -28, map ); - DestroyTeleporter( 1784, 993, -28, map ); - DestroyTeleporter( 1785, 993, -28, map ); - DestroyTeleporter( 1786, 993, -28, map ); - DestroyTeleporter( 1787, 993, -28, map ); - DestroyTeleporter( 1788, 993, -28, map ); - - DestroyTeleporter( 1419, 910, -10, map ); - DestroyTeleporter( 1420, 910, -10, map ); - DestroyTeleporter( 1421, 910, -10, map ); - DestroyTeleporter( 1422, 910, -10, map ); - - CreateTeleporter( 1419, 909, -10, 1784, 994, -28, map, true ); - CreateTeleporter( 1420, 909, -10, 1785, 994, -28, map, true ); - CreateTeleporter( 1421, 909, -10, 1786, 994, -28, map, true ); - CreateTeleporter( 1787, 994, -28, 1421, 909, -10, map, false ); - CreateTeleporter( 1788, 994, -28, 1421, 909, -10, map, false ); - CreateTeleporter( 1783, 994, -28, 1419, 909, -10, map, false ); - - CreateTeleporter( 1861, 980, -28, 1490, 877, 10, map, true ); - CreateTeleporter( 1861, 981, -28, 1490, 878, 10, map, true ); - CreateTeleporter( 1861, 982, -28, 1490, 879, 10, map, true ); - CreateTeleporter( 1861, 983, -28, 1490, 880, 10, map, true ); - CreateTeleporter( 1861, 984, -28, 1490, 880, 10, map, false ); - CreateTeleporter( 1516, 879, 10, 1363, 1105, -26, map, true ); - - // Spectre Dungeon - CreateTeleporter( 1362, 1031, -13, 1981, 1107, -16, map, true ); - CreateTeleporter( 1363, 1031, -13, 1982, 1107, -16, map, true ); - CreateTeleporter( 1364, 1031, -13, 1983, 1107, -16, map, true ); - CreateTeleporter( 1980, 1107, -16, 1362, 1031, -13, map, false ); - CreateTeleporter( 1984, 1107, -16, 1364, 1031, -13, map, false ); - - // BLOOD DUNGEON - CreateTeleporter( 1745, 1236, -30, 2112, 829, -11, map, true ); - CreateTeleporter( 1746, 1236, -30, 2113, 829, -11, map, true ); - CreateTeleporter( 1747, 1236, -30, 2114, 829, -11, map, true ); - CreateTeleporter( 1748, 1236, -30, 2115, 829, -11, map, true ); - CreateTeleporter( 2116, 829, -11, 1748, 1236, -30, map, false ); - - // Mushroom Cave - CreateTeleporter( 1456, 1328, -27, 1479, 1494, -28, map, true ); - CreateTeleporter( 1456, 1329, -27, 1479, 1495, -28, map, true ); - CreateTeleporter( 1456, 1330, -27, 1479, 1496, -28, map, true ); - CreateTeleporter( 1479, 1493, -28, 1456, 1328, -27, map, false ); - CreateTeleporter( 1479, 1497, -28, 1456, 1330, -27, map, false ); - - // RATMAN CAVE - CreateTeleporter( 1029, 1155, -24, 1349, 1512, -3, map, true ); - CreateTeleporter( 1029, 1154, -24, 1349, 1511, -3, map, true ); - CreateTeleporter( 1029, 1153, -24, 1349, 1510, -3, map, true ); - CreateTeleporter( 1349, 1509, -3, 1030, 1153, -24, map, false ); - CreateTeleporter( 1268, 1508, -28, 1250, 1508, -28, map, true ); - CreateTeleporter( 1268, 1509, -28, 1250, 1509, -28, map, true ); - CreateTeleporter( 1268, 1510, -28, 1250, 1510, -28, map, true ); - CreateTeleporter( 1250, 1511, -28, 1268, 1510, -28, map, false ); - CreateTeleporter( 1250, 1512, -28, 1268, 1510, -28, map, false ); - - // Serpentine Passage - DestroyTeleporter( 532, 1532, -7, map ); - DestroyTeleporter( 533, 1532, -7, map ); - DestroyTeleporter( 534, 1532, -7, map ); - - CreateTeleporter( 810, 874, -39, 532, 1532, -7, map, false ); - CreateTeleporter( 811, 874, -39, 533, 1532, -7, map, false ); - CreateTeleporter( 812, 874, -39, 534, 1532, -7, map, false ); - CreateTeleporter( 531, 1533, -4, 810, 875, -40, map, false ); - CreateTeleporter( 532, 1533, -4, 811, 875, -39, map, false ); - CreateTeleporter( 533, 1533, -4, 812, 875, -39, map, false ); - CreateTeleporter( 534, 1533, -4, 813, 875, -40, map, false ); - - CreateTeleporter( 393, 1587, -13, 78, 1366, -36, map, false ); - CreateTeleporter( 394, 1587, -13, 79, 1366, -36, map, false ); - CreateTeleporter( 395, 1587, -13, 80, 1366, -36, map, false ); - CreateTeleporter( 396, 1587, -13, 81, 1366, -36, map, false ); - CreateTeleporter( 78, 1365, -41, 393, 1586, -16, map, false ); - CreateTeleporter( 79, 1365, -41, 394, 1586, -16, map, false ); - CreateTeleporter( 80, 1365, -41, 395, 1586, -16, map, false ); - CreateTeleporter( 81, 1365, -41, 396, 1586, -16, map, false ); - DestroyTeleporter( 82, 1365, -38, map ); - - // ANKH DUNGEON - DestroyTeleporter( 4, 1267, -11, map ); - DestroyTeleporter( 4, 1268, -11, map ); - DestroyTeleporter( 4, 1269, -11, map ); - CreateTeleporter( 668, 928, -84, 3, 1267, -8, map, true ); - CreateTeleporter( 668, 929, -84, 3, 1268, -8, map, true ); - CreateTeleporter( 668, 930, -82, 3, 1269, -8, map, true ); - - DestroyTeleporter( 154, 1473, -8, map ); - DestroyTeleporter( 155, 1473, -8, map ); - DestroyTeleporter( 156, 1473, -8, map ); - CreateTeleporter( 575, 1156, -121, 154, 1473, -8, map, false ); - CreateTeleporter( 576, 1156, -121, 155, 1473, -8, map, false ); - CreateTeleporter( 577, 1156, -121, 156, 1473, -8, map, false ); - CreateTeleporter( 154, 1472, -8, 575, 1155, -121, map, false ); - CreateTeleporter( 155, 1472, -8, 576, 1155, -120, map, false ); - CreateTeleporter( 156, 1472, -8, 577, 1155, -120, map, false ); - - DestroyTeleporter( 10, 1518, -28, map ); - DestroyTeleporter( 10, 1518, -27, map ); - DestroyTeleporter( 10, 1518, -27, map ); - CreateTeleporter( 10, 872, -28, 10, 1518, -27, map, false ); - CreateTeleporter( 11, 872, -28, 11, 1518, -28, map, false ); - CreateTeleporter( 12, 872, -27, 12, 1518, -28, map, false ); - CreateTeleporter( 10, 1519, -28, 10, 873, -28, map, false ); - CreateTeleporter( 11, 1519, -27, 11, 873, -28, map, false ); - CreateTeleporter( 12, 1519, -27, 12, 873, -27, map, false ); - - // Ratman Lair - CreateTeleporter( 636, 813, -62, 164, 743, -28, map, false ); - CreateTeleporter( 164, 746, -16, 636, 815, -52, map, false ); - - // WISP DUNGEON - CreateTeleporter( 348, 1427, 15, 18, 1198, -5, map, true ); - CreateTeleporter( 349, 1427, 15, 19, 1198, -5, map, true ); - CreateTeleporter( 350, 1427, 15, 20, 1198, -5, map, true ); - CreateTeleporter( 351, 1427, 15, 21, 1198, -5, map, true ); - CreateTeleporter( 712, 1490, -3, 686, 1490, -28, map, false ); - CreateTeleporter( 712, 1491, -3, 686, 1491, -28, map, false ); - CreateTeleporter( 712, 1492, -3, 686, 1492, -28, map, false ); - CreateTeleporter( 712, 1493, -3, 686, 1493, -28, map, false ); - CreateTeleporter( 694, 1490, -53, 719, 1490, -28, map, false ); - CreateTeleporter( 694, 1491, -53, 719, 1491, -28, map, false ); - CreateTeleporter( 694, 1492, -53, 719, 1492, -28, map, false ); - CreateTeleporter( 694, 1493, -53, 719, 1493, -28, map, false ); - CreateTeleporter( 775, 1467, -28, 658, 1498, -28, map, false ); - DestroyTeleporter( 658, 1498, -28, map ); - CreateTeleporter( 838, 1550, -6, 728, 1505, -28, map, false ); - CreateTeleporter( 838, 1551, -6, 728, 1506, -28, map, false ); - CreateTeleporter( 838, 1552, -6, 728, 1507, -28, map, false ); - CreateTeleporter( 838, 1553, -6, 728, 1508, -28, map, false ); - CreateTeleporter( 722, 1505, -53, 833, 1550, -28, map, false ); - CreateTeleporter( 722, 1506, -53, 833, 1551, -28, map, false ); - CreateTeleporter( 722, 1507, -53, 833, 1552, -28, map, false ); - CreateTeleporter( 722, 1508, -53, 833, 1553, -28, map, false ); - CreateTeleporter( 954, 1425, -53, 874, 1490, 2, map, false ); - CreateTeleporter( 954, 1426, -53, 874, 1491, 2, map, false ); - CreateTeleporter( 954, 1427, -53, 874, 1492, 2, map, false ); - CreateTeleporter( 954, 1428, -53, 874, 1493, 2, map, false ); - CreateTeleporter( 954, 1429, -53, 874, 1493, 2, map, false ); - CreateTeleporter( 879, 1490, 24, 960, 1425, -28, map, false ); - CreateTeleporter( 879, 1491, 24, 960, 1426, -28, map, false ); - CreateTeleporter( 879, 1492, 24, 960, 1427, -28, map, false ); - CreateTeleporter( 879, 1493, 24, 960, 1428, -28, map, false ); - CreateTeleporter( 948, 1464, -56, 951, 1442, -6, map, true ); - CreateTeleporter( 948, 1465, -56, 951, 1443, -6, map, true ); - CreateTeleporter( 948, 1466, -56, 951, 1444, -6, map, true ); - CreateTeleporter( 948, 1467, -56, 951, 1445, -6, map, true ); - CreateTeleporter( 871, 1433, -6, 897, 1449, -28, map, false ); - CreateTeleporter( 871, 1434, -6, 897, 1450, -28, map, false ); - CreateTeleporter( 871, 1435, -6, 897, 1451, -28, map, false ); - CreateTeleporter( 871, 1436, -6, 897, 1452, -28, map, false ); - CreateTeleporter( 871, 1437, -6, 897, 1453, -28, map, false ); - CreateTeleporter( 892, 1449, -51, 866, 1433, -28, map, false ); - CreateTeleporter( 892, 1450, -51, 866, 1434, -28, map, false ); - CreateTeleporter( 892, 1451, -51, 866, 1435, -28, map, false ); - CreateTeleporter( 892, 1452, -51, 866, 1436, -28, map, false ); - CreateTeleporter( 892, 1453, -51, 866, 1437, -28, map, false ); - CreateTeleporter( 812, 1546, -6, 848, 1434, -28, map, false ); - CreateTeleporter( 812, 1547, -6, 848, 1435, -28, map, false ); - CreateTeleporter( 812, 1548, -6, 848, 1436, -28, map, false ); - CreateTeleporter( 812, 1549, -6, 848, 1437, -28, map, false ); - CreateTeleporter( 843, 1434, -51, 807, 1546, -28, map, false ); - CreateTeleporter( 843, 1435, -51, 807, 1547, -28, map, false ); - CreateTeleporter( 843, 1436, -51, 807, 1548, -28, map, false ); - CreateTeleporter( 843, 1437, -51, 807, 1549, -28, map, false ); - CreateTeleporter( 751, 1473, -28, 763, 1479, -28, map, false ); - DestroyTeleporter( 763, 1479, -28, map ); - CreateTeleporter( 751, 1479, -28, 763, 1555, -28, map, false ); - DestroyTeleporter( 763, 1555, -28, map ); - CreateTeleporter( 752, 1549, -28, 751, 1484, -28, map, false ); - DestroyTeleporter( 751, 1484, -28, map ); - CreateTeleporter( 775, 1492, -28, 827, 1515, -28, map, false ); - DestroyTeleporter( 827, 1515, -28, map ); - DestroyTeleporter( 1013, 1506, 0, map ); - DestroyTeleporter( 1013, 1507, 0, map ); - DestroyTeleporter( 1013, 1508, 0, map ); - DestroyTeleporter( 1013, 1509, 0, map ); - CreateTeleporter( 904, 1360, -21, 1014, 1506, 0, map, true ); - CreateTeleporter( 904, 1361, -21, 1014, 1507, 0, map, true ); - CreateTeleporter( 904, 1362, -21, 1014, 1508, 0, map, true ); - CreateTeleporter( 904, 1363, -21, 1014, 1509, 0, map, true ); - - /*CreateTeleporter( 650, 1297, -58, 626, 1526, -28, map, true ); - CreateTeleporter( 651, 1297, -58, 627, 1526, -28, map, true ); - CreateTeleporter( 652, 1297, -58, 628, 1526, -28, map, true ); - CreateTeleporter( 653, 1297, -58, 629, 1526, -28, map, true );*/ - - // Update: remove old teleporters - DestroyTeleporter( 650, 1297, -58, map ); - DestroyTeleporter( 651, 1297, -58, map ); - DestroyTeleporter( 652, 1297, -58, map ); - DestroyTeleporter( 653, 1297, -58, map ); - DestroyTeleporter( 626, 1526, -28, map ); - DestroyTeleporter( 627, 1526, -28, map ); - DestroyTeleporter( 628, 1526, -28, map ); - DestroyTeleporter( 629, 1526, -28, map ); - - // Update: add new ones - for ( int i = 0; i < 4; ++i ) - { - CreateTeleporter( 650 + i, 1297, -58, 626 + i, 1526, -28, map, false ); - CreateTeleporter( 626 + i, 1527, -28, 650 + i, 1298, i == 1 ? -59 : -58, map, false ); - } - - // WISP DUNGEON MAZE - CreateTeleporter( 747, 1539, -28, 785, 1514, -28, map, false ); - CreateTeleporter( 785, 1524, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 747, 1555, -28, 785, 1570, -28, map, false ); - CreateTeleporter( 784, 1580, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 791, 1548, -28, 781, 1547, -28, map, false ); - CreateTeleporter( 782, 1550, -28, 783, 1538, -28, map, false ); - CreateTeleporter( 783, 1539, -28, 787, 1542, -28, map, false ); - CreateTeleporter( 787, 1543, -28, 781, 1554, -28, map, false ); - CreateTeleporter( 781, 1555, -28, 789, 1556, -28, map, false ); - CreateTeleporter( 789, 1557, -28, 785, 1550, -28, map, false ); - CreateTeleporter( 784, 1550, -28, 777, 1554, -28, map, false ); - CreateTeleporter( 778, 1554, -28, 787, 1538, -28, map, false ); - CreateTeleporter( 787, 1537, -28, 781, 1546, -28, map, false ); - CreateTeleporter( 781, 1545, -28, 789, 1552, -28, map, false ); - CreateTeleporter( 789, 1553, -28, 789, 1546, -28, map, false ); - CreateTeleporter( 789, 1545, -28, 779, 1541, -28, map, false ); - CreateTeleporter( 780, 1541, -28, 785, 1554, -28, map, false ); - CreateTeleporter( 785, 1555, -28, 783, 1542, -28, map, false ); - CreateTeleporter( 782, 1542, -28, 785, 1546, -28, map, false ); - CreateTeleporter( 784, 1546, -28, 776, 1548, -28, map, false ); - CreateTeleporter( 777, 1555, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 777, 1553, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 776, 1549, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 777, 1548, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 777, 1547, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 776, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 778, 1541, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 779, 1540, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 779, 1542, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 780, 1554, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 781, 1553, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 782, 1554, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 780, 1550, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 781, 1549, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 781, 1551, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 780, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 781, 1547, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 782, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 783, 1543, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 784, 1542, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 783, 1541, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 782, 1538, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 783, 1537, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 784, 1538, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 786, 1538, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 787, 1539, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 788, 1538, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 788, 1542, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 787, 1541, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 786, 1542, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 785, 1545, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 786, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 785, 1547, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 785, 1549, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 785, 1551, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 786, 1550, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 784, 1554, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 785, 1553, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 786, 1554, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 788, 1556, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 789, 1555, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 790, 1556, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 788, 1552, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 789, 1551, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 790, 1552, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 790, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 788, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 789, 1547, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 791, 1545, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 791, 1546, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 791, 1547, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 791, 1549, -28, 798, 1547, -28, map, false ); - CreateTeleporter( 791, 1550, -28, 798, 1547, -28, map, false ); - - // Sorcerer`s Dungeon - CreateTeleporter( 546, 455, -40, 426, 113, -28, map, true ); - CreateTeleporter( 547, 455, -40, 427, 113, -28, map, true ); - CreateTeleporter( 548, 455, -40, 428, 113, -28, map, true ); - CreateTeleporter( 429, 113, -28, 548, 455, -40, map, false ); - - CreateTeleporter( 242, 27, -16, 372, 31, -31, map, false ); // stairs - 0x754 - CreateTeleporter( 242, 26, -16, 372, 30, -31, map, false ); // stairs - 0x754 - CreateTeleporter( 242, 25, -16, 372, 29, -31, map, false ); // stairs - 0x754 - CreateTeleporter( 371, 31, -36, 241, 27, -18, map, false ); // stairs - 0x754 - CreateTeleporter( 371, 30, -36, 241, 26, -18, map, false ); // stairs - 0x754 - - DestroyTeleporter( 371, 29, -36, map ); //To remove old erroneous teleporter - - CreateTeleporter( 371, 29, -36, 241, 25, -18, map, false ); // stairs - 0x754 - - CreateTeleporter( 272, 141, -16, 555, 427, -1, map, false ); // stairs - 1st 0x753 - CreateTeleporter( 273, 141, -16, 556, 427, -1, map, false ); // stairs - 1st 0x753 - CreateTeleporter( 274, 141, -16, 557, 427, -1, map, false ); // stairs - 1st 0x753 - CreateTeleporter( 555, 426, -6, 272, 140, -21, map, false ); // stairs - 1st 0x753 - CreateTeleporter( 556, 426, -6, 273, 140, -21, map, false ); // stairs - 1st 0x753 - CreateTeleporter( 557, 426, -6, 274, 140, -21, map, false ); // stairs - 1st 0x753 - - CreateTeleporter( 265, 130, -31, 284, 72, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 266, 130, -31, 285, 72, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 267, 130, -31, 286, 72, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 268, 130, -31, 287, 72, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 284, 73, -16, 265, 131, -28, map, false ); // stairs - 0x753 - CreateTeleporter( 285, 73, -16, 266, 131, -28, map, false ); // stairs - 0x753 - CreateTeleporter( 286, 73, -16, 267, 131, -28, map, false ); // stairs - 0x753 - CreateTeleporter( 287, 73, -16, 268, 131, -28, map, false ); // stairs - 0x753 - - CreateTeleporter( 284, 67, -30, 131, 128, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 285, 67, -30, 132, 128, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 286, 67, -30, 133, 128, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 287, 67, -30, 134, 128, -21, map, false ); // stairs - 0x753 - CreateTeleporter( 131, 129, -16, 284, 68, -28, map, false ); // stairs - 0x753 - CreateTeleporter( 132, 129, -16, 285, 68, -28, map, false ); // stairs - 0x753 - CreateTeleporter( 133, 129, -16, 286, 68, -28, map, false ); // stairs - 0x753 - CreateTeleporter( 134, 129, -16, 287, 68, -28, map, false ); // stairs - 0x753 - - CreateTeleporter( 358, 40, -36, 156, 88, -18, map, false ); // stairs - 0x73A - CreateTeleporter( 358, 41, -36, 156, 89, -18, map, false ); // stairs - 0x73A - CreateTeleporter( 358, 42, -36, 156, 90, -18, map, false ); // stairs - 0x73A - CreateTeleporter( 155, 88, -16, 357, 40, -31, map, false ); // stairs - 0x73A - CreateTeleporter( 155, 89, -16, 357, 41, -31, map, false ); // stairs - 0x73A - CreateTeleporter( 155, 90, -16, 357, 42, -31, map, false ); // stairs - 0x73A - - CreateTeleporter( 259, 90, -28, 236, 113, -28, map, true ); - - // Ancient Lair - - DestroyTeleporter( 83, 747, -28, map ); - DestroyTeleporter( 84, 747, -28, map ); - DestroyTeleporter( 85, 747, -28, map ); - DestroyTeleporter( 86, 747, -28, map ); - CreateTeleporter( 938, 494, -40, 83, 749, -23, map, true ); - CreateTeleporter( 939, 494, -40, 84, 749, -23, map, true ); - CreateTeleporter( 940, 494, -40, 85, 749, -23, map, true ); - CreateTeleporter( 941, 494, -40, 86, 749, -23, map, true ); - - // Lizard Passage - - DestroyTeleporter( 313, 1330, -39, map ); - DestroyTeleporter( 314, 1330, -37, map ); - DestroyTeleporter( 315, 1330, -35, map ); - CreateTeleporter( 313, 1329, -40, 327, 1593, -13, map, true ); - CreateTeleporter( 314, 1329, -38, 328, 1593, -13, map, true ); - CreateTeleporter( 315, 1329, -36, 329, 1593, -13, map, true ); - CreateTeleporter( 330, 1593, -13, 315, 1329, -35, map, false ); - - DestroyTeleporter( 225, 1335, -20, map ); - DestroyTeleporter( 226, 1335, -20, map ); - DestroyTeleporter( 227, 1335, -19, map ); - CreateTeleporter( 265, 1587, -28, 225, 1334, -20, map, true ); - CreateTeleporter( 266, 1587, -28, 226, 1334, -20, map, true ); - CreateTeleporter( 267, 1587, -28, 227, 1334, -20, map, true ); - - // Central Ilshenar - /*CreateTeleporter( 1139, 593, -80, 1237, 582, -19, map, true ); - CreateTeleporter( 1140, 593, -80, 1237, 583, -19, map, true ); - CreateTeleporter( 1141, 593, -80, 1237, 584, -19, map, true ); - CreateTeleporter( 1142, 593, -80, 1237, 585, -19, map, true ); - CreateTeleporter( 912, 451, -80, 708, 667, -39, map, true ); - CreateTeleporter( 912, 452, -80, 709, 667, -39, map, true ); - CreateTeleporter( 912, 453, -80, 710, 667, -39, map, true ); - CreateTeleporter( 711, 667, -39, 912, 453, -80, map, false );*/ - - // Update: remove old teleporters.. - DestroyTeleporter( 1139, 593, -80, map ); - DestroyTeleporter( 1140, 593, -80, map ); - DestroyTeleporter( 1141, 593, -80, map ); - DestroyTeleporter( 1142, 593, -80, map ); - DestroyTeleporter( 1237, 582, -19, map ); - DestroyTeleporter( 1237, 583, -19, map ); - DestroyTeleporter( 1237, 584, -19, map ); - DestroyTeleporter( 1237, 585, -19, map ); - - DestroyTeleporter( 912, 451, -80, map ); - DestroyTeleporter( 912, 452, -80, map ); - DestroyTeleporter( 912, 453, -80, map ); - DestroyTeleporter( 708, 667, -39, map ); - DestroyTeleporter( 709, 667, -39, map ); - DestroyTeleporter( 710, 667, -39, map ); - DestroyTeleporter( 711, 667, -39, map ); - - // Update: add new ones... - CreateTeleporter( 1139, 592, -80, 1238, 583, -19, map, false ); - CreateTeleporter( 1140, 592, -80, 1238, 584, -19, map, false ); - CreateTeleporter( 1141, 592, -80, 1238, 585, -19, map, false ); - CreateTeleporter( 1142, 592, -80, 1238, 585, -19, map, false ); - CreateTeleporter( 1237, 583, -19, 1139, 593, -80, map, false ); - CreateTeleporter( 1237, 584, -19, 1140, 593, -80, map, false ); - CreateTeleporter( 1237, 585, -19, 1141, 593, -80, map, false ); - - CreateTeleporter( 709, 667, -39, 912, 451, -80, map, false ); - CreateTeleporter( 710, 667, -39, 912, 452, -80, map, false ); - CreateTeleporter( 711, 667, -39, 912, 453, -80, map, false ); - - CreateTeleporter( 911, 451, -80, 709, 668, -39, map, false ); - CreateTeleporter( 911, 452, -80, 710, 668, -39, map, false ); - CreateTeleporter( 911, 453, -80, 711, 668, -38, map, false ); - - // Exodus Dungeon - CreateTeleporter( 827, 777, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 827, 778, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 827, 779, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 828, 777, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 828, 778, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 828, 779, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 829, 777, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 829, 778, -80, 1975, 114, -28, map, false ); - CreateTeleporter( 829, 779, -80, 1975, 114, -28, map, false ); - - CreateTeleporter( 1978, 114, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1978, 115, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1978, 116, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1978, 117, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1979, 114, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1979, 115, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1979, 116, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1979, 117, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1980, 114, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1980, 115, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1980, 116, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1980, 117, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1981, 114, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1981, 115, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1981, 116, -28, 835, 778, -80, map, false ); - CreateTeleporter( 1981, 117, -28, 835, 778, -80, map, false ); - } - - public void CreateTeleportersMap3( Map map ) - { - // CreateTeleporter( 408, 254, 2, 428, 319, 2, map, false ); // for doom quest; use blockers to avoid players teleporting into the ship! - // CreateTeleporter( 428, 321, 2, 422, 328, -1, map, false ); // for doom quest; use blockers to avoid players teleporting into the ship! - - // Doom Dungeon - CreateTeleporter( 2317, 1269, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2317, 1268, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2317, 1267, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2317, 1266, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2316, 1269, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2315, 1269, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2315, 1268, -110, 381, 132, 33, map, false ); - CreateTeleporter( 2315, 1267, -109, 381, 132, 33, map, false ); - CreateTeleporter( 2316, 1267, -110, 381, 132, 33, map, false ); - CreateTeleporter( 496, 49, 6, 2350, 1270, -85, map, false ); - DestroyTeleporter( 433, 326, 4, map ); - DestroyTeleporter( 365, 15, -1, map ); - - //Yomotsu Mines Exit - CreateTeleporter( 3, 128, -1, 259, 785, 64, map, Map.Tokuno, false ); - CreateTeleporter( 4, 128, -1, 259, 785, 64, map, Map.Tokuno, false ); - CreateTeleporter( 5, 128, -1, 259, 785, 64, map, Map.Tokuno, false ); - CreateTeleporter( 6, 128, -1, 259, 785, 64, map, Map.Tokuno, false ); - CreateTeleporter( 7, 128, -1, 259, 785, 64, map, Map.Tokuno, false ); - CreateTeleporter( 8, 128, -1, 259, 785, 64, map, Map.Tokuno, false ); - - //Fan Dancer Exit - CreateTeleporter( 64, 336, 11, 983, 195, 24, map, Map.Tokuno, false ); - CreateTeleporter( 64, 337, 11, 983, 195, 24, map, Map.Tokuno, false ); - CreateTeleporter( 64, 338, 11, 983, 195, 24, map, Map.Tokuno, false ); - CreateTeleporter( 64, 339, 11, 983, 195, 24, map, Map.Tokuno, false ); - - //Fan Dancer Levels - CreateTeleporter( 66, 351, -7, 63, 524, -1, map, false ); - CreateTeleporter( 66, 352, -7, 63, 524, -1, map, false ); - CreateTeleporter( 66, 353, -7, 63, 524, -1, map, false ); - CreateTeleporter( 66, 354, -7, 63, 524, -1, map, false ); - - CreateTeleporter( 61, 523, 6, 63, 352, -3, map, false ); - CreateTeleporter( 61, 524, 6, 63, 352, -3, map, false ); - CreateTeleporter( 61, 525, 6, 63, 352, -3, map, false ); - CreateTeleporter( 61, 526, 6, 63, 352, -3, map, false ); - - CreateTeleporter( 103, 555, -6, 76, 691, -1, map, false ); - CreateTeleporter( 103, 556, -6, 76, 691, -1, map, false ); - CreateTeleporter( 103, 557, -6, 76, 691, -1, map, false ); - CreateTeleporter( 103, 558, -6, 76, 691, -1, map, false ); - - CreateTeleporter( 73, 688, 6, 100, 556, -2, map, false ); - CreateTeleporter( 73, 689, 6, 100, 556, -2, map, false ); - CreateTeleporter( 73, 690, 6, 100, 556, -2, map, false ); - CreateTeleporter( 73, 691, 6, 100, 556, -2, map, false ); - CreateTeleporter( 73, 692, 6, 100, 556, -2, map, false ); - CreateTeleporter( 73, 693, 6, 100, 556, -2, map, false ); - CreateTeleporter( 73, 694, 6, 100, 556, -2, map, false ); - - //Ninja cave - CreateTeleporter( 384, 810, -1, 403, 1167, 0, map, false ); - - CreateTeleporter( 403, 1169, 0, 385, 811, -1, map, false ); - CreateTeleporter( 404, 1169, 0, 385, 808, -1, map, false ); - CreateTeleporter( 405, 1169, 0, 385, 808, -1, map, false ); - - // Dungeon Labyrinth - CreateTeleporter( 328, 1972, 5, 1731, 978, -80, map, false ); // Door exit - CreateTeleporter( 328, 1973, 5, 1731, 978, -80, map, false ); - CreateTeleporter( 328, 1974, 5, 1731, 978, -80, map, false ); - CreateTeleporter( 328, 1975, 5, 1731, 978, -80, map, false ); - - // Dungeon Bedlam - CreateTeleporter( 119, 1684, 0, 2068, 1372, -75, map, false ); - CreateTeleporter( 120, 1684, 0, 2068, 1372, -75, map, false ); - CreateTeleporter( 121, 1684, 0, 2068, 1372, -75, map, false ); - CreateTeleporter( 84, 1673, -2, 156, 1613, 0, map, false ); - CreateTeleporter( 156, 1609, 17, 87, 1673, 0, map, false ); - CreateTeleporter( 157, 1609, 17, 87, 1673, 0, map, false ); - } - - public void CreateTeleportersMap4( Map map ) - { - //Yomotso Mines Entrance - CreateTeleporter( 257, 783, 63, 5, 128, -1, map, Map.Malas, false ); - CreateTeleporter( 258, 783, 63, 5, 128, -1, map, Map.Malas, false ); - CreateTeleporter( 259, 783, 63, 5, 128, -1, map, Map.Malas, false ); - CreateTeleporter( 260, 783, 63, 5, 128, -1, map, Map.Malas, false ); - - //Fan dancer Entrance - CreateTeleporter( 988, 194, 15, 67, 337, -1, map, Map.Malas, false ); - CreateTeleporter( 988, 195, 15, 67, 337, -1, map, Map.Malas, false ); - CreateTeleporter( 987, 196, 15, 67, 337, -1, map, Map.Malas, false ); - CreateTeleporter( 988, 197, 18, 67, 337, -1, map, Map.Malas, false ); - - } - public void CreateTeleportersTrammel( Map map ) - { - // Haven - CreateTeleporter( 3632, 2566, 0, 3632, 2566, 20, map, true ); - } - - public void CreateTeleportersFelucca( Map map ) - { - // Star room - CreateTeleporter( 5140, 1773, 0, 5171, 1586, 0, map, false ); - } - - public int CreateTeleporters() - { - CreateTeleportersMap( Map.Felucca ); - CreateTeleportersMap( Map.Trammel ); - CreateTeleportersTrammel( Map.Trammel ); - CreateTeleportersFelucca( Map.Felucca ); - CreateTeleportersMap2( Map.Ilshenar ); - CreateTeleportersMap3( Map.Malas ); - CreateTeleportersMap4( Map.Tokuno ); - return m_Count; - } - } - } -} + public class GenTeleporter + { + public static void Initialize() + { + CommandSystem.Register("TelGen", AccessLevel.Administrator, GenTeleporter_OnCommand); + } + + [Usage("TelGen")] + [Description("Generates world/dungeon teleporters for all facets.")] + public static void GenTeleporter_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage("Generating teleporters, please wait."); + + int count = new TeleportersCreator().CreateTeleporters(); + + count += new SHTeleporter.SHTeleporterCreator().CreateSHTeleporters(); + + e.Mobile.SendMessage("Teleporter generating complete. {0} teleporters were generated.", count); + } + + public class TeleportersCreator + { + private static Queue m_Queue = new Queue(); + private int m_Count; + + public static bool FindTeleporter(Map map, Point3D p) + { + IPooledEnumerable eable = map.GetItemsInRange(p, 0); + + foreach (Item item in eable) + if (item is Teleporter && !(item is KeywordTeleporter) && !(item is SkillTeleporter)) + { + int delta = item.Z - p.Z; + + if (delta >= -12 && delta <= 12) + m_Queue.Enqueue(item); + } + + eable.Free(); + + while (m_Queue.Count > 0) + m_Queue.Dequeue().Delete(); + + return false; + } + + public void CreateTeleporter(Point3D pointLocation, Point3D pointDestination, Map mapLocation, + Map mapDestination, bool back) + { + if (!FindTeleporter(mapLocation, pointLocation)) + { + m_Count++; + + Teleporter tel = new Teleporter(pointDestination, mapDestination); + + tel.MoveToWorld(pointLocation, mapLocation); + } + + if (back && !FindTeleporter(mapDestination, pointDestination)) + { + m_Count++; + + Teleporter telBack = new Teleporter(pointLocation, mapLocation); + + telBack.MoveToWorld(pointDestination, mapDestination); + } + } + + public void CreateTeleporter(int xLoc, int yLoc, int zLoc, int xDest, int yDest, int zDest, Map map, bool back) + { + CreateTeleporter(new Point3D(xLoc, yLoc, zLoc), new Point3D(xDest, yDest, zDest), map, map, back); + } + + public void CreateTeleporter(int xLoc, int yLoc, int zLoc, int xDest, int yDest, int zDest, Map mapLocation, + Map mapDestination, bool back) + { + CreateTeleporter(new Point3D(xLoc, yLoc, zLoc), new Point3D(xDest, yDest, zDest), mapLocation, + mapDestination, back); + } + + public void DestroyTeleporter(int x, int y, int z, Map map) + { + Point3D p = new Point3D(x, y, z); + IPooledEnumerable eable = map.GetItemsInRange(p, 0); + + foreach (Item item in eable) + if (item is Teleporter && !(item is KeywordTeleporter) && !(item is SkillTeleporter) && item.Z == p.Z) + m_Queue.Enqueue(item); + + eable.Free(); + + while (m_Queue.Count > 0) + m_Queue.Dequeue().Delete(); + } + + public void CreateTeleportersMap(Map map) + { + // Shame + CreateTeleporter(512, 1559, 0, 5394, 127, 0, map, true); + CreateTeleporter(513, 1559, 0, 5395, 127, 0, map, true); + CreateTeleporter(514, 1559, 0, 5396, 127, 0, map, true); + CreateTeleporter(5490, 19, -25, 5514, 10, 5, map, true); + CreateTeleporter(5875, 19, -5, 5507, 162, 5, map, true); + CreateTeleporter(5604, 102, 5, 5514, 147, 25, map, true); + + CreateTeleporter(5513, 176, 5, 5540, 187, 0, map, false); + CreateTeleporter(5538, 170, 5, 5517, 176, 0, map, false); + + // Hythloth + CreateTeleporter(4721, 3813, 0, 5904, 16, 64, map, true); + CreateTeleporter(4722, 3813, 0, 5905, 16, 64, map, true); + CreateTeleporter(4723, 3813, 0, 5906, 16, 64, map, true); + CreateTeleporter(6040, 192, 12, 6059, 88, 24, map, true); + CreateTeleporter(6040, 193, 12, 6059, 89, 24, map, true); + CreateTeleporter(6040, 194, 12, 6059, 90, 24, map, true); + + DestroyTeleporter(5920, 168, 16, map); + DestroyTeleporter(5920, 169, 17, map); + DestroyTeleporter(5920, 170, 16, map); + + CreateTeleporter(5920, 168, 16, 6083, 144, -20, map, false); + CreateTeleporter(5920, 169, 16, 6083, 145, -20, map, false); + CreateTeleporter(5920, 170, 16, 6083, 146, -20, map, false); + + CreateTeleporter(6083, 144, -20, 5920, 168, 22, map, false); + CreateTeleporter(6083, 145, -20, 5920, 169, 22, map, false); + CreateTeleporter(6083, 146, -20, 5920, 170, 22, map, false); + + DestroyTeleporter(5906, 96, 0, map); + + CreateTeleporter(5972, 168, 0, 5905, 100, 0, map, false); + CreateTeleporter(5906, 96, 0, 5977, 169, 0, map, false); + + // Covetous + CreateTeleporter(2498, 916, 0, 5455, 1864, 0, map, true); + CreateTeleporter(2499, 916, 0, 5456, 1864, 0, map, true); + CreateTeleporter(2500, 916, 0, 5457, 1864, 0, map, true); + CreateTeleporter(2384, 836, 0, 5615, 1996, 0, map, true); + CreateTeleporter(2384, 837, 0, 5615, 1997, 0, map, true); + CreateTeleporter(2384, 838, 0, 5615, 1998, 0, map, true); + CreateTeleporter(2420, 883, 0, 5392, 1959, 0, map, true); + CreateTeleporter(2421, 883, 0, 5393, 1959, 0, map, true); + CreateTeleporter(2422, 883, 0, 5394, 1959, 0, map, true); + CreateTeleporter(2455, 858, 0, 5388, 2027, 0, map, true); + CreateTeleporter(2456, 858, 0, 5389, 2027, 0, map, true); + CreateTeleporter(2457, 858, 0, 5390, 2027, 0, map, true); + CreateTeleporter(2544, 850, 0, 5578, 1927, 0, map, true); + CreateTeleporter(2545, 850, 0, 5579, 1927, 0, map, true); + CreateTeleporter(2546, 850, 0, 5580, 1927, 0, map, true); + + CreateTeleporter(5551, 1805, 12, 5556, 1825, -3, map, false); + CreateTeleporter(5552, 1805, 12, 5557, 1825, -3, map, false); + CreateTeleporter(5553, 1805, 12, 5557, 1825, -3, map, false); + + DestroyTeleporter(5551, 1807, 0, map); + DestroyTeleporter(5552, 1807, 0, map); + DestroyTeleporter(5553, 1807, 0, map); + + CreateTeleporter(5556, 1826, -10, 5551, 1806, 7, map, false); + CreateTeleporter(5557, 1826, -10, 5552, 1806, 7, map, false); + + DestroyTeleporter(5556, 1825, -7, map); + DestroyTeleporter(5556, 1827, -13, map); + DestroyTeleporter(5557, 1825, -7, map); + DestroyTeleporter(5557, 1827, -13, map); + DestroyTeleporter(5558, 1825, -7, map); + + DestroyTeleporter(5468, 1804, 0, map); + DestroyTeleporter(5468, 1805, 0, map); + DestroyTeleporter(5468, 1806, 0, map); + + CreateTeleporter(5466, 1804, 12, 5593, 1840, -3, map, false); + CreateTeleporter(5466, 1805, 12, 5593, 1841, -3, map, false); + CreateTeleporter(5466, 1806, 12, 5593, 1842, -3, map, false); + + DestroyTeleporter(5595, 1840, -14, map); + DestroyTeleporter(5595, 1840, -14, map); + + CreateTeleporter(5594, 1840, -8, 5467, 1804, 7, map, false); + CreateTeleporter(5594, 1841, -8, 5467, 1805, 7, map, false); + + // Wrong + CreateTeleporter(5824, 631, 5, 2041, 215, 14, map, true); + CreateTeleporter(5825, 631, 5, 2042, 215, 14, map, true); + CreateTeleporter(5825, 631, 5, 2043, 215, 14, map, true); + CreateTeleporter(5698, 662, 0, 5793, 527, 10, map, false); + + DestroyTeleporter(5863, 525, 15, map); + DestroyTeleporter(5863, 526, 15, map); + DestroyTeleporter(5863, 527, 15, map); + DestroyTeleporter(5868, 537, 15, map); + DestroyTeleporter(5868, 538, 15, map); + DestroyTeleporter(5869, 538, 15, map); + DestroyTeleporter(5733, 554, 20, map); + DestroyTeleporter(5862, 527, 15, map); + + // Deceit + CreateTeleporter(4110, 430, 5, 5187, 639, 0, map, false); + CreateTeleporter(4111, 430, 5, 5188, 639, 0, map, false); + CreateTeleporter(4112, 430, 5, 5189, 639, 0, map, false); + CreateTeleporter(5187, 639, 0, 4110, 430, 5, map, false); + CreateTeleporter(5188, 639, 0, 4111, 430, 5, map, false); + CreateTeleporter(5189, 639, 0, 4112, 430, 5, map, false); + CreateTeleporter(5216, 586, -13, 5304, 533, 2, map, false); + CreateTeleporter(5217, 586, -13, 5305, 533, 2, map, false); + CreateTeleporter(5218, 586, -13, 5306, 533, 2, map, false); + CreateTeleporter(5304, 532, 7, 5216, 585, -8, map, false); + CreateTeleporter(5305, 532, 7, 5217, 585, -8, map, false); + CreateTeleporter(5306, 532, 7, 5218, 585, -8, map, false); + CreateTeleporter(5218, 761, -28, 5305, 651, 7, map, false); + CreateTeleporter(5219, 761, -28, 5306, 651, 7, map, false); + CreateTeleporter(5305, 650, 12, 5218, 760, -23, map, false); + CreateTeleporter(5306, 650, 12, 5219, 760, -23, map, false); + CreateTeleporter(5346, 578, 5, 5137, 649, 5, map, true); + + CreateTeleporter(5186, 639, 0, 4110, 430, 5, map, false); + + // Despise + CreateTeleporter(5504, 569, 46, 5574, 628, 37, map, false); + CreateTeleporter(5504, 570, 46, 5574, 629, 37, map, false); + CreateTeleporter(5504, 571, 46, 5574, 630, 37, map, false); + CreateTeleporter(5572, 632, 17, 5521, 672, 27, map, false); + CreateTeleporter(5572, 633, 17, 5521, 673, 27, map, false); + CreateTeleporter(5572, 634, 17, 5521, 674, 27, map, false); + CreateTeleporter(5573, 628, 42, 5503, 569, 51, map, false); + CreateTeleporter(5573, 629, 42, 5503, 570, 51, map, false); + CreateTeleporter(5573, 630, 42, 5503, 571, 51, map, false); + CreateTeleporter(5588, 632, 30, 1296, 1082, 0, map, true); + CreateTeleporter(5588, 630, 30, 1296, 1080, 0, map, true); + CreateTeleporter(5588, 631, 30, 1296, 1081, 0, map, true); + CreateTeleporter(5522, 672, 32, 5573, 632, 22, map, false); + CreateTeleporter(5522, 673, 32, 5573, 633, 22, map, false); + CreateTeleporter(5522, 674, 32, 5573, 634, 22, map, false); + CreateTeleporter(5386, 756, -8, 5408, 859, 47, map, false); + CreateTeleporter(5386, 757, -8, 5408, 860, 47, map, false); + CreateTeleporter(5386, 755, -8, 5408, 858, 47, map, false); + CreateTeleporter(5409, 860, 52, 5387, 757, -3, map, false); + CreateTeleporter(5409, 858, 52, 5387, 755, -3, map, false); + CreateTeleporter(5409, 859, 52, 5387, 756, -3, map, false); + + // Destard + CreateTeleporter(5242, 1007, 0, 1175, 2635, 0, map, true); + CreateTeleporter(5243, 1007, 0, 1176, 2635, 0, map, true); + CreateTeleporter(5244, 1007, 0, 1177, 2635, 0, map, true); + CreateTeleporter(5142, 797, 22, 5129, 908, -23, map, false); + CreateTeleporter(5143, 797, 22, 5130, 908, -23, map, false); + CreateTeleporter(5144, 797, 22, 5131, 908, -23, map, false); + CreateTeleporter(5145, 797, 22, 5132, 908, -23, map, false); + CreateTeleporter(5153, 808, -25, 5134, 984, 17, map, false); + CreateTeleporter(5153, 809, -25, 5134, 985, 17, map, false); + CreateTeleporter(5153, 810, -25, 5134, 986, 17, map, false); + CreateTeleporter(5153, 811, -25, 5134, 987, 17, map, false); + CreateTeleporter(5129, 909, -28, 5142, 798, 17, map, false); + CreateTeleporter(5130, 909, -28, 5143, 798, 17, map, false); + CreateTeleporter(5131, 909, -28, 5144, 798, 17, map, false); + CreateTeleporter(5132, 909, -28, 5145, 798, 17, map, false); + CreateTeleporter(5133, 984, 22, 5152, 808, -19, map, false); + CreateTeleporter(5133, 985, 22, 5152, 809, -19, map, false); + CreateTeleporter(5133, 986, 22, 5152, 810, -19, map, false); + CreateTeleporter(5133, 987, 22, 5152, 811, -19, map, false); + + // Buccaneer's Den underground tunnels + + DestroyTeleporter(2666, 2073, 5, map); + DestroyTeleporter(2669, 2072, -20, map); + DestroyTeleporter(2669, 2073, -20, map); + DestroyTeleporter(2649, 2194, 4, map); + DestroyTeleporter(2649, 2195, -14, map); + + CreateTeleporter(2603, 2121, -20, 2605, 2130, 8, map, false); + CreateTeleporter(2603, 2120, -20, 2605, 2130, 8, map, false); + CreateTeleporter(2669, 2071, -20, 2666, 2099, 3, map, false); + CreateTeleporter(2669, 2072, -20, 2666, 2099, 3, map, false); + CreateTeleporter(2669, 2073, -20, 2666, 2099, 3, map, false); + CreateTeleporter(2676, 2241, -18, 2691, 2234, 2, map, false); + CreateTeleporter(2676, 2242, -18, 2691, 2234, 2, map, false); + CreateTeleporter(2758, 2092, -20, 2756, 2097, 38, map, false); + CreateTeleporter(2759, 2092, -20, 2756, 2097, 38, map, false); + CreateTeleporter(2685, 2063, 39, 2685, 2063, -20, map, + false); // that should not be a teleporter: on OSI you simply fall under the ground + + // Misc + CreateTeleporter(5217, 18, 15, 5204, 74, 17, map, false); + CreateTeleporter(5200, 71, 17, 5211, 22, 15, map, false); + CreateTeleporter(1997, 81, 7, 5881, 242, 0, map, false); + CreateTeleporter(5704, 146, -45, 5705, 305, 7, map, false); + CreateTeleporter(5704, 147, -45, 5705, 306, 7, map, false); + CreateTeleporter(5874, 146, 27, 5208, 2323, 31, map, false); + CreateTeleporter(5875, 146, 27, 5208, 2322, 32, map, false); + CreateTeleporter(5876, 146, 27, 5208, 2322, 32, map, false); + CreateTeleporter(5877, 146, 27, 5208, 2322, 32, map, false); + CreateTeleporter(5923, 169, 1, 5925, 171, 22, map, false); + CreateTeleporter(2399, 198, 0, 5753, 436, 79, map, false); + CreateTeleporter(2400, 198, 0, 5754, 436, 80, map, false); + DestroyTeleporter(5166, 245, 15, map); + DestroyTeleporter(1361, 883, 0, map); + CreateTeleporter(5191, 152, 0, 1367, 891, 0, map, false); + CreateTeleporter(5849, 239, -25, 5831, 324, 27, map, false); + CreateTeleporter(5850, 239, -25, 5832, 324, 26, map, false); + CreateTeleporter(5851, 239, -25, 5833, 324, 28, map, false); + CreateTeleporter(5852, 239, -25, 5834, 324, 27, map, false); + CreateTeleporter(5853, 239, -23, 5835, 324, 27, map, false); + CreateTeleporter(5882, 241, 0, 1998, 81, 5, map, false); + CreateTeleporter(5882, 242, 0, 1998, 81, 5, map, false); + CreateTeleporter(5882, 243, 0, 1998, 81, 5, map, false); + CreateTeleporter(5706, 305, 12, 5705, 146, -45, map, false); + CreateTeleporter(5706, 306, 12, 5705, 147, -45, map, false); + CreateTeleporter(5748, 362, 2, 313, 786, -24, map, false); + CreateTeleporter(5749, 362, 0, 313, 786, -24, map, false); + CreateTeleporter(5750, 362, 3, 314, 786, -24, map, false); + CreateTeleporter(5753, 324, 21, 5670, 2391, 40, map, false); + CreateTeleporter(5831, 323, 34, 5849, 238, -25, map, false); + CreateTeleporter(5832, 323, 34, 5850, 238, -25, map, false); + CreateTeleporter(5833, 323, 33, 5851, 238, -25, map, false); + CreateTeleporter(5834, 323, 33, 5852, 238, -25, map, false); + CreateTeleporter(5835, 323, 33, 5853, 238, -23, map, false); + CreateTeleporter(5658, 423, 8, 5697, 3659, 2, map, false); + CreateTeleporter(5686, 385, 2, 2777, 894, -23, map, false); + CreateTeleporter(5686, 386, 2, 2777, 894, -23, map, false); + CreateTeleporter(5686, 387, 2, 2777, 895, -23, map, false); + CreateTeleporter(5731, 445, -18, 6087, 3676, 18, map, false); + CreateTeleporter(5753, 437, 78, 2400, 199, 0, map, false); + CreateTeleporter(5850, 432, 0, 5127, 3143, 97, map, false); + CreateTeleporter(5850, 433, -2, 5127, 3143, 97, map, false); + CreateTeleporter(5850, 434, -1, 5127, 3143, 97, map, false); + CreateTeleporter(5850, 431, 2, 5127, 3143, 97, map, false); + CreateTeleporter(5826, 465, -1, 1987, 2063, -40, map, false); + CreateTeleporter(5827, 465, -1, 1988, 2063, -40, map, false); + CreateTeleporter(5828, 465, 0, 1989, 2063, -40, map, false); + CreateTeleporter(313, 786, -24, 5748, 361, 2, map, false); + CreateTeleporter(314, 786, -24, 5749, 361, 2, map, false); + CreateTeleporter(2776, 895, -23, 5685, 387, 2, map, false); + //CreateTeleporter( 4545, 851, 30, 5736, 3196, 8, map, false ); + DestroyTeleporter(4545, 851, 30, map); + CreateTeleporter(4540, 898, 32, 4442, 1122, 5, map, false); + CreateTeleporter(4300, 968, 5, 4442, 1122, 5, map, false); + CreateTeleporter(4436, 1107, 5, 4300, 992, 5, map, false); + CreateTeleporter(4443, 1137, 5, 4487, 1475, 5, map, false); + CreateTeleporter(4449, 1107, 5, 4539, 890, 28, map, false); + CreateTeleporter(4449, 1115, 5, 4671, 1135, 10, map, false); + CreateTeleporter(4663, 1134, 13, 4442, 1122, 5, map, false); + CreateTeleporter(5701, 1320, 16, 5786, 1336, -8, map, false); + CreateTeleporter(5702, 1320, 16, 5787, 1336, -8, map, false); + CreateTeleporter(5703, 1320, 16, 5788, 1336, -8, map, false); + CreateTeleporter(5786, 1335, -13, 5701, 1319, 13, map, false); + CreateTeleporter(5787, 1335, -13, 5702, 1319, 13, map, false); + CreateTeleporter(5788, 1335, -13, 5703, 1319, 13, map, false); + CreateTeleporter(6005, 1380, 1, 5151, 4063, 37, map, false); + CreateTeleporter(6005, 1378, 0, 5151, 4062, 37, map, false); + CreateTeleporter(6005, 1379, 2, 5151, 4062, 37, map, false); + CreateTeleporter(6025, 1344, -26, 5137, 3664, 27, map, false); + CreateTeleporter(6025, 1345, -26, 5137, 3664, 27, map, false); + CreateTeleporter(6025, 1346, -26, 5137, 3665, 31, map, false); + CreateTeleporter(5687, 1424, 38, 2923, 3406, 8, map, false); + CreateTeleporter(5792, 1416, 41, 5758, 2908, 15, map, false); + CreateTeleporter(5792, 1417, 41, 5758, 2909, 15, map, false); + CreateTeleporter(5792, 1415, 41, 5758, 2907, 15, map, false); + CreateTeleporter(5899, 1411, 43, 1630, 3320, 0, map, false); + CreateTeleporter(5900, 1411, 42, 1630, 3320, 0, map, false); + CreateTeleporter(5918, 1412, -29, 5961, 1409, 59, map, false); + CreateTeleporter(5918, 1410, -29, 5961, 1408, 59, map, false); + CreateTeleporter(5918, 1411, -29, 5961, 1408, 59, map, false); + CreateTeleporter(5961, 1408, 59, 5918, 1411, -29, map, false); + CreateTeleporter(5961, 1409, 59, 5918, 1412, -29, map, false); + CreateTeleporter(6125, 1411, 15, 6075, 3332, 4, map, false); + CreateTeleporter(6126, 1411, 15, 6075, 3332, 4, map, false); + CreateTeleporter(6127, 1411, 15, 6075, 3332, 4, map, false); + CreateTeleporter(6137, 1409, 2, 6140, 1432, 4, map, false); + CreateTeleporter(6138, 1409, 2, 6140, 1432, 4, map, false); + CreateTeleporter(6140, 1431, 4, 6137, 1408, 2, map, false); + CreateTeleporter(4496, 1475, 15, 4442, 1122, 5, map, false); + CreateTeleporter(6031, 1501, 42, 1491, 1642, 24, map, false); + CreateTeleporter(6031, 1499, 42, 1491, 1640, 24, map, false); + CreateTeleporter(1491, 1640, 24, 6032, 1499, 31, map, false); + CreateTeleporter(1491, 1642, 24, 6032, 1501, 31, map, false); + DestroyTeleporter(5341, 1602, 0, map); + CreateTeleporter(5340, 1599, 40, 5426, 3122, -74, map, false); + CreateTeleporter(5341, 1599, 40, 5426, 3122, -74, map, false); + CreateTeleporter(1987, 2062, -40, 5826, 464, 0, map, false); + CreateTeleporter(1988, 2062, -40, 5827, 464, -1, map, false); + CreateTeleporter(1989, 2062, -40, 5828, 464, -1, map, false); + CreateTeleporter(5203, 2327, 27, 5876, 147, 25, map, false); + CreateTeleporter(5207, 2322, 27, 5877, 147, 25, map, false); + CreateTeleporter(5207, 2323, 26, 5876, 147, 25, map, false); + CreateTeleporter(5670, 2391, 40, 5753, 325, 10, map, false); + CreateTeleporter(5974, 2697, 35, 2985, 2890, 35, map, false); + CreateTeleporter(5267, 2757, 35, 424, 3283, 35, map, false); + CreateTeleporter(5757, 2908, 14, 5791, 1416, 38, map, false); + CreateTeleporter(5757, 2909, 15, 5791, 1417, 40, map, false); + CreateTeleporter(5757, 2907, 15, 5791, 1415, 38, map, false); + CreateTeleporter(1653, 2963, 0, 1677, 2987, 0, map, false); + CreateTeleporter(1677, 2987, 0, 1675, 2987, 20, map, false); + CreateTeleporter(5426, 3123, -80, 5341, 1602, 0, map, false); + CreateTeleporter(5126, 3143, 99, 5849, 432, 1, map, false); + //CreateTeleporter( 5736, 3196, 8, 4545, 851, 30, map, false ); + DestroyTeleporter(5736, 3196, 8, map); + CreateTeleporter(424, 3283, 35, 5267, 2757, 35, map, false); + CreateTeleporter(1629, 3320, 0, 5899, 1411, 43, map, false); + CreateTeleporter(6075, 3332, 4, 6126, 1410, 15, map, false); + CreateTeleporter(2923, 3405, 6, 5687, 1423, 39, map, false); + CreateTeleporter(1142, 3621, 5, 1414, 3828, 5, map, false); + CreateTeleporter(5137, 3664, 27, 6025, 1344, -26, map, false); + CreateTeleporter(5137, 3665, 31, 6025, 1345, -26, map, false); + CreateTeleporter(5697, 3660, -5, 5658, 424, 0, map, false); + CreateTeleporter(6086, 3676, 16, 5731, 446, -16, map, false); + CreateTeleporter(1409, 3824, 5, 1124, 3623, 5, map, false); + CreateTeleporter(1419, 3832, 5, 1466, 4015, 5, map, false); + CreateTeleporter(1406, 3996, 5, 1414, 3828, 5, map, false); + CreateTeleporter(5150, 4062, 38, 6005, 1378, 0, map, false); + CreateTeleporter(5150, 4063, 38, 6005, 1380, 1, map, false); + CreateTeleporter(5906, 4069, 26, 2494, 3576, 5, map, true); + CreateTeleporter(2985, 2890, 35, 5974, 2697, 35, map, false); + + // Mondain's Legacy dungeons + + // Sanctuary + CreateTeleporter(6172, 21, 0, 765, 1645, 0, map, false); // Entrance gate + CreateTeleporter(6172, 22, 0, 765, 1646, 0, map, false); + CreateTeleporter(6172, 23, 0, 765, 1647, 0, map, false); + CreateTeleporter(766, 1645, 0, 6174, 21, 0, map, false); + CreateTeleporter(766, 1646, 0, 6174, 22, 0, map, false); + CreateTeleporter(766, 1647, 0, 6174, 23, 0, map, false); + + CreateTeleporter(6173, 176, -10, 6233, 15, -10, map, false); // Zone change + CreateTeleporter(6174, 176, -10, 6234, 15, -10, map, false); + CreateTeleporter(6175, 176, -10, 6235, 15, -10, map, false); + CreateTeleporter(6176, 176, -10, 6236, 15, -10, map, false); + CreateTeleporter(6177, 176, -10, 6237, 15, -10, map, false); + CreateTeleporter(6178, 176, -10, 6238, 15, -10, map, false); + CreateTeleporter(6179, 176, -10, 6239, 15, -10, map, false); + CreateTeleporter(6233, 14, -10, 6172, 174, -10, map, false); + CreateTeleporter(6234, 14, -10, 6173, 174, -10, map, false); + CreateTeleporter(6235, 14, -10, 6174, 174, -10, map, false); + CreateTeleporter(6236, 14, -10, 6175, 174, -10, map, false); + CreateTeleporter(6237, 14, -10, 6176, 174, -10, map, false); + CreateTeleporter(6238, 14, -10, 6177, 174, -10, map, false); + CreateTeleporter(6239, 14, -10, 6177, 174, -10, map, false); + CreateTeleporter(6240, 14, -10, 6178, 174, -10, map, false); + + CreateTeleporter(6256, 97, -4, 6257, 95, -10, map, false); // Ladders + CreateTeleporter(6260, 97, -4, 6260, 95, -10, map, false); + CreateTeleporter(6263, 97, -4, 6262, 95, -10, map, false); + CreateTeleporter(6269, 97, -4, 6269, 95, -10, map, false); + CreateTeleporter(6273, 97, -4, 6272, 95, -10, map, false); + CreateTeleporter(6262, 95, -10, 6262, 99, -10, map, false); + + CreateTeleporter(6159, 130, 0, 6317, 63, -20, map, false); // Holes + CreateTeleporter(6164, 73, 0, 6320, 22, -20, map, false); + CreateTeleporter(6161, 163, -10, 6321, 106, -20, map, false); + CreateTeleporter(6276, 40, -10, 6374, 124, -20, map, false); + CreateTeleporter(6211, 106, 0, 6355, 34, -20, map, false); + + CreateTeleporter(6316, 62, -5, 6160, 131, 0, map, false); // Cave ladders + CreateTeleporter(6319, 19, -20, 6165, 74, 0, map, + false); // This actually goes to (6165, 75) inside the wall... + CreateTeleporter(6356, 32, -9, 6210, 105, 0, map, false); + CreateTeleporter(6374, 125, -20, 6277, 41, -10, map, false); + + CreateTeleporter(6373, 49, -20, 801, 1682, 0, map, false); + CreateTeleporter(6374, 49, -20, 801, 1682, 0, map, false); + CreateTeleporter(6375, 49, -20, 801, 1682, 0, map, false); + CreateTeleporter(6376, 49, -20, 801, 1682, 0, map, false); + CreateTeleporter(6377, 49, -20, 801, 1682, 0, map, false); + + // Painted Caves + CreateTeleporter(1714, 2996, 0, 6308, 892, 0, map, false); // Entrance + CreateTeleporter(1714, 2997, 0, 6308, 892, 0, map, false); + CreateTeleporter(6310, 890, 0, 1716, 2997, 0, map, false); + CreateTeleporter(6310, 891, 0, 1716, 2997, 0, map, false); + CreateTeleporter(6310, 892, 0, 1716, 2997, 0, map, false); + CreateTeleporter(6310, 893, 0, 1716, 2997, 0, map, false); + } + + public void CreateTeleportersMap2(Map map) + { + // Dungeon of rock + CreateTeleporter(2186, 294, -27, 2186, 33, -27, map, true); + CreateTeleporter(2187, 294, -27, 2187, 33, -27, map, true); + CreateTeleporter(2188, 294, -27, 2188, 33, -27, map, true); + CreateTeleporter(2189, 294, -27, 2189, 33, -27, map, true); + CreateTeleporter(2189, 320, -7, 1788, 569, 74, map, true); + CreateTeleporter(2188, 320, -7, 1787, 569, 74, map, true); + CreateTeleporter(2187, 320, -7, 1787, 569, 74, map, false); + + // Spider Cave + DestroyTeleporter(1783, 993, -28, map); + DestroyTeleporter(1784, 993, -28, map); + DestroyTeleporter(1785, 993, -28, map); + DestroyTeleporter(1786, 993, -28, map); + DestroyTeleporter(1787, 993, -28, map); + DestroyTeleporter(1788, 993, -28, map); + + DestroyTeleporter(1419, 910, -10, map); + DestroyTeleporter(1420, 910, -10, map); + DestroyTeleporter(1421, 910, -10, map); + DestroyTeleporter(1422, 910, -10, map); + + CreateTeleporter(1419, 909, -10, 1784, 994, -28, map, true); + CreateTeleporter(1420, 909, -10, 1785, 994, -28, map, true); + CreateTeleporter(1421, 909, -10, 1786, 994, -28, map, true); + CreateTeleporter(1787, 994, -28, 1421, 909, -10, map, false); + CreateTeleporter(1788, 994, -28, 1421, 909, -10, map, false); + CreateTeleporter(1783, 994, -28, 1419, 909, -10, map, false); + + CreateTeleporter(1861, 980, -28, 1490, 877, 10, map, true); + CreateTeleporter(1861, 981, -28, 1490, 878, 10, map, true); + CreateTeleporter(1861, 982, -28, 1490, 879, 10, map, true); + CreateTeleporter(1861, 983, -28, 1490, 880, 10, map, true); + CreateTeleporter(1861, 984, -28, 1490, 880, 10, map, false); + CreateTeleporter(1516, 879, 10, 1363, 1105, -26, map, true); + + // Spectre Dungeon + CreateTeleporter(1362, 1031, -13, 1981, 1107, -16, map, true); + CreateTeleporter(1363, 1031, -13, 1982, 1107, -16, map, true); + CreateTeleporter(1364, 1031, -13, 1983, 1107, -16, map, true); + CreateTeleporter(1980, 1107, -16, 1362, 1031, -13, map, false); + CreateTeleporter(1984, 1107, -16, 1364, 1031, -13, map, false); + + // BLOOD DUNGEON + CreateTeleporter(1745, 1236, -30, 2112, 829, -11, map, true); + CreateTeleporter(1746, 1236, -30, 2113, 829, -11, map, true); + CreateTeleporter(1747, 1236, -30, 2114, 829, -11, map, true); + CreateTeleporter(1748, 1236, -30, 2115, 829, -11, map, true); + CreateTeleporter(2116, 829, -11, 1748, 1236, -30, map, false); + + // Mushroom Cave + CreateTeleporter(1456, 1328, -27, 1479, 1494, -28, map, true); + CreateTeleporter(1456, 1329, -27, 1479, 1495, -28, map, true); + CreateTeleporter(1456, 1330, -27, 1479, 1496, -28, map, true); + CreateTeleporter(1479, 1493, -28, 1456, 1328, -27, map, false); + CreateTeleporter(1479, 1497, -28, 1456, 1330, -27, map, false); + + // RATMAN CAVE + CreateTeleporter(1029, 1155, -24, 1349, 1512, -3, map, true); + CreateTeleporter(1029, 1154, -24, 1349, 1511, -3, map, true); + CreateTeleporter(1029, 1153, -24, 1349, 1510, -3, map, true); + CreateTeleporter(1349, 1509, -3, 1030, 1153, -24, map, false); + CreateTeleporter(1268, 1508, -28, 1250, 1508, -28, map, true); + CreateTeleporter(1268, 1509, -28, 1250, 1509, -28, map, true); + CreateTeleporter(1268, 1510, -28, 1250, 1510, -28, map, true); + CreateTeleporter(1250, 1511, -28, 1268, 1510, -28, map, false); + CreateTeleporter(1250, 1512, -28, 1268, 1510, -28, map, false); + + // Serpentine Passage + DestroyTeleporter(532, 1532, -7, map); + DestroyTeleporter(533, 1532, -7, map); + DestroyTeleporter(534, 1532, -7, map); + + CreateTeleporter(810, 874, -39, 532, 1532, -7, map, false); + CreateTeleporter(811, 874, -39, 533, 1532, -7, map, false); + CreateTeleporter(812, 874, -39, 534, 1532, -7, map, false); + CreateTeleporter(531, 1533, -4, 810, 875, -40, map, false); + CreateTeleporter(532, 1533, -4, 811, 875, -39, map, false); + CreateTeleporter(533, 1533, -4, 812, 875, -39, map, false); + CreateTeleporter(534, 1533, -4, 813, 875, -40, map, false); + + CreateTeleporter(393, 1587, -13, 78, 1366, -36, map, false); + CreateTeleporter(394, 1587, -13, 79, 1366, -36, map, false); + CreateTeleporter(395, 1587, -13, 80, 1366, -36, map, false); + CreateTeleporter(396, 1587, -13, 81, 1366, -36, map, false); + CreateTeleporter(78, 1365, -41, 393, 1586, -16, map, false); + CreateTeleporter(79, 1365, -41, 394, 1586, -16, map, false); + CreateTeleporter(80, 1365, -41, 395, 1586, -16, map, false); + CreateTeleporter(81, 1365, -41, 396, 1586, -16, map, false); + DestroyTeleporter(82, 1365, -38, map); + + // ANKH DUNGEON + DestroyTeleporter(4, 1267, -11, map); + DestroyTeleporter(4, 1268, -11, map); + DestroyTeleporter(4, 1269, -11, map); + CreateTeleporter(668, 928, -84, 3, 1267, -8, map, true); + CreateTeleporter(668, 929, -84, 3, 1268, -8, map, true); + CreateTeleporter(668, 930, -82, 3, 1269, -8, map, true); + + DestroyTeleporter(154, 1473, -8, map); + DestroyTeleporter(155, 1473, -8, map); + DestroyTeleporter(156, 1473, -8, map); + CreateTeleporter(575, 1156, -121, 154, 1473, -8, map, false); + CreateTeleporter(576, 1156, -121, 155, 1473, -8, map, false); + CreateTeleporter(577, 1156, -121, 156, 1473, -8, map, false); + CreateTeleporter(154, 1472, -8, 575, 1155, -121, map, false); + CreateTeleporter(155, 1472, -8, 576, 1155, -120, map, false); + CreateTeleporter(156, 1472, -8, 577, 1155, -120, map, false); + + DestroyTeleporter(10, 1518, -28, map); + DestroyTeleporter(10, 1518, -27, map); + DestroyTeleporter(10, 1518, -27, map); + CreateTeleporter(10, 872, -28, 10, 1518, -27, map, false); + CreateTeleporter(11, 872, -28, 11, 1518, -28, map, false); + CreateTeleporter(12, 872, -27, 12, 1518, -28, map, false); + CreateTeleporter(10, 1519, -28, 10, 873, -28, map, false); + CreateTeleporter(11, 1519, -27, 11, 873, -28, map, false); + CreateTeleporter(12, 1519, -27, 12, 873, -27, map, false); + + // Ratman Lair + CreateTeleporter(636, 813, -62, 164, 743, -28, map, false); + CreateTeleporter(164, 746, -16, 636, 815, -52, map, false); + + // WISP DUNGEON + CreateTeleporter(348, 1427, 15, 18, 1198, -5, map, true); + CreateTeleporter(349, 1427, 15, 19, 1198, -5, map, true); + CreateTeleporter(350, 1427, 15, 20, 1198, -5, map, true); + CreateTeleporter(351, 1427, 15, 21, 1198, -5, map, true); + CreateTeleporter(712, 1490, -3, 686, 1490, -28, map, false); + CreateTeleporter(712, 1491, -3, 686, 1491, -28, map, false); + CreateTeleporter(712, 1492, -3, 686, 1492, -28, map, false); + CreateTeleporter(712, 1493, -3, 686, 1493, -28, map, false); + CreateTeleporter(694, 1490, -53, 719, 1490, -28, map, false); + CreateTeleporter(694, 1491, -53, 719, 1491, -28, map, false); + CreateTeleporter(694, 1492, -53, 719, 1492, -28, map, false); + CreateTeleporter(694, 1493, -53, 719, 1493, -28, map, false); + CreateTeleporter(775, 1467, -28, 658, 1498, -28, map, false); + DestroyTeleporter(658, 1498, -28, map); + CreateTeleporter(838, 1550, -6, 728, 1505, -28, map, false); + CreateTeleporter(838, 1551, -6, 728, 1506, -28, map, false); + CreateTeleporter(838, 1552, -6, 728, 1507, -28, map, false); + CreateTeleporter(838, 1553, -6, 728, 1508, -28, map, false); + CreateTeleporter(722, 1505, -53, 833, 1550, -28, map, false); + CreateTeleporter(722, 1506, -53, 833, 1551, -28, map, false); + CreateTeleporter(722, 1507, -53, 833, 1552, -28, map, false); + CreateTeleporter(722, 1508, -53, 833, 1553, -28, map, false); + CreateTeleporter(954, 1425, -53, 874, 1490, 2, map, false); + CreateTeleporter(954, 1426, -53, 874, 1491, 2, map, false); + CreateTeleporter(954, 1427, -53, 874, 1492, 2, map, false); + CreateTeleporter(954, 1428, -53, 874, 1493, 2, map, false); + CreateTeleporter(954, 1429, -53, 874, 1493, 2, map, false); + CreateTeleporter(879, 1490, 24, 960, 1425, -28, map, false); + CreateTeleporter(879, 1491, 24, 960, 1426, -28, map, false); + CreateTeleporter(879, 1492, 24, 960, 1427, -28, map, false); + CreateTeleporter(879, 1493, 24, 960, 1428, -28, map, false); + CreateTeleporter(948, 1464, -56, 951, 1442, -6, map, true); + CreateTeleporter(948, 1465, -56, 951, 1443, -6, map, true); + CreateTeleporter(948, 1466, -56, 951, 1444, -6, map, true); + CreateTeleporter(948, 1467, -56, 951, 1445, -6, map, true); + CreateTeleporter(871, 1433, -6, 897, 1449, -28, map, false); + CreateTeleporter(871, 1434, -6, 897, 1450, -28, map, false); + CreateTeleporter(871, 1435, -6, 897, 1451, -28, map, false); + CreateTeleporter(871, 1436, -6, 897, 1452, -28, map, false); + CreateTeleporter(871, 1437, -6, 897, 1453, -28, map, false); + CreateTeleporter(892, 1449, -51, 866, 1433, -28, map, false); + CreateTeleporter(892, 1450, -51, 866, 1434, -28, map, false); + CreateTeleporter(892, 1451, -51, 866, 1435, -28, map, false); + CreateTeleporter(892, 1452, -51, 866, 1436, -28, map, false); + CreateTeleporter(892, 1453, -51, 866, 1437, -28, map, false); + CreateTeleporter(812, 1546, -6, 848, 1434, -28, map, false); + CreateTeleporter(812, 1547, -6, 848, 1435, -28, map, false); + CreateTeleporter(812, 1548, -6, 848, 1436, -28, map, false); + CreateTeleporter(812, 1549, -6, 848, 1437, -28, map, false); + CreateTeleporter(843, 1434, -51, 807, 1546, -28, map, false); + CreateTeleporter(843, 1435, -51, 807, 1547, -28, map, false); + CreateTeleporter(843, 1436, -51, 807, 1548, -28, map, false); + CreateTeleporter(843, 1437, -51, 807, 1549, -28, map, false); + CreateTeleporter(751, 1473, -28, 763, 1479, -28, map, false); + DestroyTeleporter(763, 1479, -28, map); + CreateTeleporter(751, 1479, -28, 763, 1555, -28, map, false); + DestroyTeleporter(763, 1555, -28, map); + CreateTeleporter(752, 1549, -28, 751, 1484, -28, map, false); + DestroyTeleporter(751, 1484, -28, map); + CreateTeleporter(775, 1492, -28, 827, 1515, -28, map, false); + DestroyTeleporter(827, 1515, -28, map); + DestroyTeleporter(1013, 1506, 0, map); + DestroyTeleporter(1013, 1507, 0, map); + DestroyTeleporter(1013, 1508, 0, map); + DestroyTeleporter(1013, 1509, 0, map); + CreateTeleporter(904, 1360, -21, 1014, 1506, 0, map, true); + CreateTeleporter(904, 1361, -21, 1014, 1507, 0, map, true); + CreateTeleporter(904, 1362, -21, 1014, 1508, 0, map, true); + CreateTeleporter(904, 1363, -21, 1014, 1509, 0, map, true); + + /*CreateTeleporter( 650, 1297, -58, 626, 1526, -28, map, true ); + CreateTeleporter( 651, 1297, -58, 627, 1526, -28, map, true ); + CreateTeleporter( 652, 1297, -58, 628, 1526, -28, map, true ); + CreateTeleporter( 653, 1297, -58, 629, 1526, -28, map, true );*/ + + // Update: remove old teleporters + DestroyTeleporter(650, 1297, -58, map); + DestroyTeleporter(651, 1297, -58, map); + DestroyTeleporter(652, 1297, -58, map); + DestroyTeleporter(653, 1297, -58, map); + DestroyTeleporter(626, 1526, -28, map); + DestroyTeleporter(627, 1526, -28, map); + DestroyTeleporter(628, 1526, -28, map); + DestroyTeleporter(629, 1526, -28, map); + + // Update: add new ones + for (int i = 0; i < 4; ++i) + { + CreateTeleporter(650 + i, 1297, -58, 626 + i, 1526, -28, map, false); + CreateTeleporter(626 + i, 1527, -28, 650 + i, 1298, i == 1 ? -59 : -58, map, false); + } + + // WISP DUNGEON MAZE + CreateTeleporter(747, 1539, -28, 785, 1514, -28, map, false); + CreateTeleporter(785, 1524, -28, 798, 1547, -28, map, false); + CreateTeleporter(747, 1555, -28, 785, 1570, -28, map, false); + CreateTeleporter(784, 1580, -28, 798, 1547, -28, map, false); + CreateTeleporter(791, 1548, -28, 781, 1547, -28, map, false); + CreateTeleporter(782, 1550, -28, 783, 1538, -28, map, false); + CreateTeleporter(783, 1539, -28, 787, 1542, -28, map, false); + CreateTeleporter(787, 1543, -28, 781, 1554, -28, map, false); + CreateTeleporter(781, 1555, -28, 789, 1556, -28, map, false); + CreateTeleporter(789, 1557, -28, 785, 1550, -28, map, false); + CreateTeleporter(784, 1550, -28, 777, 1554, -28, map, false); + CreateTeleporter(778, 1554, -28, 787, 1538, -28, map, false); + CreateTeleporter(787, 1537, -28, 781, 1546, -28, map, false); + CreateTeleporter(781, 1545, -28, 789, 1552, -28, map, false); + CreateTeleporter(789, 1553, -28, 789, 1546, -28, map, false); + CreateTeleporter(789, 1545, -28, 779, 1541, -28, map, false); + CreateTeleporter(780, 1541, -28, 785, 1554, -28, map, false); + CreateTeleporter(785, 1555, -28, 783, 1542, -28, map, false); + CreateTeleporter(782, 1542, -28, 785, 1546, -28, map, false); + CreateTeleporter(784, 1546, -28, 776, 1548, -28, map, false); + CreateTeleporter(777, 1555, -28, 798, 1547, -28, map, false); + CreateTeleporter(777, 1553, -28, 798, 1547, -28, map, false); + CreateTeleporter(776, 1549, -28, 798, 1547, -28, map, false); + CreateTeleporter(777, 1548, -28, 798, 1547, -28, map, false); + CreateTeleporter(777, 1547, -28, 798, 1547, -28, map, false); + CreateTeleporter(776, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(778, 1541, -28, 798, 1547, -28, map, false); + CreateTeleporter(779, 1540, -28, 798, 1547, -28, map, false); + CreateTeleporter(779, 1542, -28, 798, 1547, -28, map, false); + CreateTeleporter(780, 1554, -28, 798, 1547, -28, map, false); + CreateTeleporter(781, 1553, -28, 798, 1547, -28, map, false); + CreateTeleporter(782, 1554, -28, 798, 1547, -28, map, false); + CreateTeleporter(780, 1550, -28, 798, 1547, -28, map, false); + CreateTeleporter(781, 1549, -28, 798, 1547, -28, map, false); + CreateTeleporter(781, 1551, -28, 798, 1547, -28, map, false); + CreateTeleporter(780, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(781, 1547, -28, 798, 1547, -28, map, false); + CreateTeleporter(782, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(783, 1543, -28, 798, 1547, -28, map, false); + CreateTeleporter(784, 1542, -28, 798, 1547, -28, map, false); + CreateTeleporter(783, 1541, -28, 798, 1547, -28, map, false); + CreateTeleporter(782, 1538, -28, 798, 1547, -28, map, false); + CreateTeleporter(783, 1537, -28, 798, 1547, -28, map, false); + CreateTeleporter(784, 1538, -28, 798, 1547, -28, map, false); + CreateTeleporter(786, 1538, -28, 798, 1547, -28, map, false); + CreateTeleporter(787, 1539, -28, 798, 1547, -28, map, false); + CreateTeleporter(788, 1538, -28, 798, 1547, -28, map, false); + CreateTeleporter(788, 1542, -28, 798, 1547, -28, map, false); + CreateTeleporter(787, 1541, -28, 798, 1547, -28, map, false); + CreateTeleporter(786, 1542, -28, 798, 1547, -28, map, false); + CreateTeleporter(785, 1545, -28, 798, 1547, -28, map, false); + CreateTeleporter(786, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(785, 1547, -28, 798, 1547, -28, map, false); + CreateTeleporter(785, 1549, -28, 798, 1547, -28, map, false); + CreateTeleporter(785, 1551, -28, 798, 1547, -28, map, false); + CreateTeleporter(786, 1550, -28, 798, 1547, -28, map, false); + CreateTeleporter(784, 1554, -28, 798, 1547, -28, map, false); + CreateTeleporter(785, 1553, -28, 798, 1547, -28, map, false); + CreateTeleporter(786, 1554, -28, 798, 1547, -28, map, false); + CreateTeleporter(788, 1556, -28, 798, 1547, -28, map, false); + CreateTeleporter(789, 1555, -28, 798, 1547, -28, map, false); + CreateTeleporter(790, 1556, -28, 798, 1547, -28, map, false); + CreateTeleporter(788, 1552, -28, 798, 1547, -28, map, false); + CreateTeleporter(789, 1551, -28, 798, 1547, -28, map, false); + CreateTeleporter(790, 1552, -28, 798, 1547, -28, map, false); + CreateTeleporter(790, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(788, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(789, 1547, -28, 798, 1547, -28, map, false); + CreateTeleporter(791, 1545, -28, 798, 1547, -28, map, false); + CreateTeleporter(791, 1546, -28, 798, 1547, -28, map, false); + CreateTeleporter(791, 1547, -28, 798, 1547, -28, map, false); + CreateTeleporter(791, 1549, -28, 798, 1547, -28, map, false); + CreateTeleporter(791, 1550, -28, 798, 1547, -28, map, false); + + // Sorcerer`s Dungeon + CreateTeleporter(546, 455, -40, 426, 113, -28, map, true); + CreateTeleporter(547, 455, -40, 427, 113, -28, map, true); + CreateTeleporter(548, 455, -40, 428, 113, -28, map, true); + CreateTeleporter(429, 113, -28, 548, 455, -40, map, false); + + CreateTeleporter(242, 27, -16, 372, 31, -31, map, false); // stairs - 0x754 + CreateTeleporter(242, 26, -16, 372, 30, -31, map, false); // stairs - 0x754 + CreateTeleporter(242, 25, -16, 372, 29, -31, map, false); // stairs - 0x754 + CreateTeleporter(371, 31, -36, 241, 27, -18, map, false); // stairs - 0x754 + CreateTeleporter(371, 30, -36, 241, 26, -18, map, false); // stairs - 0x754 + + DestroyTeleporter(371, 29, -36, map); //To remove old erroneous teleporter + + CreateTeleporter(371, 29, -36, 241, 25, -18, map, false); // stairs - 0x754 + + CreateTeleporter(272, 141, -16, 555, 427, -1, map, false); // stairs - 1st 0x753 + CreateTeleporter(273, 141, -16, 556, 427, -1, map, false); // stairs - 1st 0x753 + CreateTeleporter(274, 141, -16, 557, 427, -1, map, false); // stairs - 1st 0x753 + CreateTeleporter(555, 426, -6, 272, 140, -21, map, false); // stairs - 1st 0x753 + CreateTeleporter(556, 426, -6, 273, 140, -21, map, false); // stairs - 1st 0x753 + CreateTeleporter(557, 426, -6, 274, 140, -21, map, false); // stairs - 1st 0x753 + + CreateTeleporter(265, 130, -31, 284, 72, -21, map, false); // stairs - 0x753 + CreateTeleporter(266, 130, -31, 285, 72, -21, map, false); // stairs - 0x753 + CreateTeleporter(267, 130, -31, 286, 72, -21, map, false); // stairs - 0x753 + CreateTeleporter(268, 130, -31, 287, 72, -21, map, false); // stairs - 0x753 + CreateTeleporter(284, 73, -16, 265, 131, -28, map, false); // stairs - 0x753 + CreateTeleporter(285, 73, -16, 266, 131, -28, map, false); // stairs - 0x753 + CreateTeleporter(286, 73, -16, 267, 131, -28, map, false); // stairs - 0x753 + CreateTeleporter(287, 73, -16, 268, 131, -28, map, false); // stairs - 0x753 + + CreateTeleporter(284, 67, -30, 131, 128, -21, map, false); // stairs - 0x753 + CreateTeleporter(285, 67, -30, 132, 128, -21, map, false); // stairs - 0x753 + CreateTeleporter(286, 67, -30, 133, 128, -21, map, false); // stairs - 0x753 + CreateTeleporter(287, 67, -30, 134, 128, -21, map, false); // stairs - 0x753 + CreateTeleporter(131, 129, -16, 284, 68, -28, map, false); // stairs - 0x753 + CreateTeleporter(132, 129, -16, 285, 68, -28, map, false); // stairs - 0x753 + CreateTeleporter(133, 129, -16, 286, 68, -28, map, false); // stairs - 0x753 + CreateTeleporter(134, 129, -16, 287, 68, -28, map, false); // stairs - 0x753 + + CreateTeleporter(358, 40, -36, 156, 88, -18, map, false); // stairs - 0x73A + CreateTeleporter(358, 41, -36, 156, 89, -18, map, false); // stairs - 0x73A + CreateTeleporter(358, 42, -36, 156, 90, -18, map, false); // stairs - 0x73A + CreateTeleporter(155, 88, -16, 357, 40, -31, map, false); // stairs - 0x73A + CreateTeleporter(155, 89, -16, 357, 41, -31, map, false); // stairs - 0x73A + CreateTeleporter(155, 90, -16, 357, 42, -31, map, false); // stairs - 0x73A + + CreateTeleporter(259, 90, -28, 236, 113, -28, map, true); + + // Ancient Lair + + DestroyTeleporter(83, 747, -28, map); + DestroyTeleporter(84, 747, -28, map); + DestroyTeleporter(85, 747, -28, map); + DestroyTeleporter(86, 747, -28, map); + CreateTeleporter(938, 494, -40, 83, 749, -23, map, true); + CreateTeleporter(939, 494, -40, 84, 749, -23, map, true); + CreateTeleporter(940, 494, -40, 85, 749, -23, map, true); + CreateTeleporter(941, 494, -40, 86, 749, -23, map, true); + + // Lizard Passage + + DestroyTeleporter(313, 1330, -39, map); + DestroyTeleporter(314, 1330, -37, map); + DestroyTeleporter(315, 1330, -35, map); + CreateTeleporter(313, 1329, -40, 327, 1593, -13, map, true); + CreateTeleporter(314, 1329, -38, 328, 1593, -13, map, true); + CreateTeleporter(315, 1329, -36, 329, 1593, -13, map, true); + CreateTeleporter(330, 1593, -13, 315, 1329, -35, map, false); + + DestroyTeleporter(225, 1335, -20, map); + DestroyTeleporter(226, 1335, -20, map); + DestroyTeleporter(227, 1335, -19, map); + CreateTeleporter(265, 1587, -28, 225, 1334, -20, map, true); + CreateTeleporter(266, 1587, -28, 226, 1334, -20, map, true); + CreateTeleporter(267, 1587, -28, 227, 1334, -20, map, true); + + // Central Ilshenar + /*CreateTeleporter( 1139, 593, -80, 1237, 582, -19, map, true ); + CreateTeleporter( 1140, 593, -80, 1237, 583, -19, map, true ); + CreateTeleporter( 1141, 593, -80, 1237, 584, -19, map, true ); + CreateTeleporter( 1142, 593, -80, 1237, 585, -19, map, true ); + CreateTeleporter( 912, 451, -80, 708, 667, -39, map, true ); + CreateTeleporter( 912, 452, -80, 709, 667, -39, map, true ); + CreateTeleporter( 912, 453, -80, 710, 667, -39, map, true ); + CreateTeleporter( 711, 667, -39, 912, 453, -80, map, false );*/ + + // Update: remove old teleporters.. + DestroyTeleporter(1139, 593, -80, map); + DestroyTeleporter(1140, 593, -80, map); + DestroyTeleporter(1141, 593, -80, map); + DestroyTeleporter(1142, 593, -80, map); + DestroyTeleporter(1237, 582, -19, map); + DestroyTeleporter(1237, 583, -19, map); + DestroyTeleporter(1237, 584, -19, map); + DestroyTeleporter(1237, 585, -19, map); + + DestroyTeleporter(912, 451, -80, map); + DestroyTeleporter(912, 452, -80, map); + DestroyTeleporter(912, 453, -80, map); + DestroyTeleporter(708, 667, -39, map); + DestroyTeleporter(709, 667, -39, map); + DestroyTeleporter(710, 667, -39, map); + DestroyTeleporter(711, 667, -39, map); + + // Update: add new ones... + CreateTeleporter(1139, 592, -80, 1238, 583, -19, map, false); + CreateTeleporter(1140, 592, -80, 1238, 584, -19, map, false); + CreateTeleporter(1141, 592, -80, 1238, 585, -19, map, false); + CreateTeleporter(1142, 592, -80, 1238, 585, -19, map, false); + CreateTeleporter(1237, 583, -19, 1139, 593, -80, map, false); + CreateTeleporter(1237, 584, -19, 1140, 593, -80, map, false); + CreateTeleporter(1237, 585, -19, 1141, 593, -80, map, false); + + CreateTeleporter(709, 667, -39, 912, 451, -80, map, false); + CreateTeleporter(710, 667, -39, 912, 452, -80, map, false); + CreateTeleporter(711, 667, -39, 912, 453, -80, map, false); + + CreateTeleporter(911, 451, -80, 709, 668, -39, map, false); + CreateTeleporter(911, 452, -80, 710, 668, -39, map, false); + CreateTeleporter(911, 453, -80, 711, 668, -38, map, false); + + // Exodus Dungeon + CreateTeleporter(827, 777, -80, 1975, 114, -28, map, false); + CreateTeleporter(827, 778, -80, 1975, 114, -28, map, false); + CreateTeleporter(827, 779, -80, 1975, 114, -28, map, false); + CreateTeleporter(828, 777, -80, 1975, 114, -28, map, false); + CreateTeleporter(828, 778, -80, 1975, 114, -28, map, false); + CreateTeleporter(828, 779, -80, 1975, 114, -28, map, false); + CreateTeleporter(829, 777, -80, 1975, 114, -28, map, false); + CreateTeleporter(829, 778, -80, 1975, 114, -28, map, false); + CreateTeleporter(829, 779, -80, 1975, 114, -28, map, false); + + CreateTeleporter(1978, 114, -28, 835, 778, -80, map, false); + CreateTeleporter(1978, 115, -28, 835, 778, -80, map, false); + CreateTeleporter(1978, 116, -28, 835, 778, -80, map, false); + CreateTeleporter(1978, 117, -28, 835, 778, -80, map, false); + CreateTeleporter(1979, 114, -28, 835, 778, -80, map, false); + CreateTeleporter(1979, 115, -28, 835, 778, -80, map, false); + CreateTeleporter(1979, 116, -28, 835, 778, -80, map, false); + CreateTeleporter(1979, 117, -28, 835, 778, -80, map, false); + CreateTeleporter(1980, 114, -28, 835, 778, -80, map, false); + CreateTeleporter(1980, 115, -28, 835, 778, -80, map, false); + CreateTeleporter(1980, 116, -28, 835, 778, -80, map, false); + CreateTeleporter(1980, 117, -28, 835, 778, -80, map, false); + CreateTeleporter(1981, 114, -28, 835, 778, -80, map, false); + CreateTeleporter(1981, 115, -28, 835, 778, -80, map, false); + CreateTeleporter(1981, 116, -28, 835, 778, -80, map, false); + CreateTeleporter(1981, 117, -28, 835, 778, -80, map, false); + } + + public void CreateTeleportersMap3(Map map) + { + // CreateTeleporter( 408, 254, 2, 428, 319, 2, map, false ); // for doom quest; use blockers to avoid players teleporting into the ship! + // CreateTeleporter( 428, 321, 2, 422, 328, -1, map, false ); // for doom quest; use blockers to avoid players teleporting into the ship! + + // Doom Dungeon + CreateTeleporter(2317, 1269, -110, 381, 132, 33, map, false); + CreateTeleporter(2317, 1268, -110, 381, 132, 33, map, false); + CreateTeleporter(2317, 1267, -110, 381, 132, 33, map, false); + CreateTeleporter(2317, 1266, -110, 381, 132, 33, map, false); + CreateTeleporter(2316, 1269, -110, 381, 132, 33, map, false); + CreateTeleporter(2315, 1269, -110, 381, 132, 33, map, false); + CreateTeleporter(2315, 1268, -110, 381, 132, 33, map, false); + CreateTeleporter(2315, 1267, -109, 381, 132, 33, map, false); + CreateTeleporter(2316, 1267, -110, 381, 132, 33, map, false); + CreateTeleporter(496, 49, 6, 2350, 1270, -85, map, false); + DestroyTeleporter(433, 326, 4, map); + DestroyTeleporter(365, 15, -1, map); + + //Yomotsu Mines Exit + CreateTeleporter(3, 128, -1, 259, 785, 64, map, Map.Tokuno, false); + CreateTeleporter(4, 128, -1, 259, 785, 64, map, Map.Tokuno, false); + CreateTeleporter(5, 128, -1, 259, 785, 64, map, Map.Tokuno, false); + CreateTeleporter(6, 128, -1, 259, 785, 64, map, Map.Tokuno, false); + CreateTeleporter(7, 128, -1, 259, 785, 64, map, Map.Tokuno, false); + CreateTeleporter(8, 128, -1, 259, 785, 64, map, Map.Tokuno, false); + + //Fan Dancer Exit + CreateTeleporter(64, 336, 11, 983, 195, 24, map, Map.Tokuno, false); + CreateTeleporter(64, 337, 11, 983, 195, 24, map, Map.Tokuno, false); + CreateTeleporter(64, 338, 11, 983, 195, 24, map, Map.Tokuno, false); + CreateTeleporter(64, 339, 11, 983, 195, 24, map, Map.Tokuno, false); + + //Fan Dancer Levels + CreateTeleporter(66, 351, -7, 63, 524, -1, map, false); + CreateTeleporter(66, 352, -7, 63, 524, -1, map, false); + CreateTeleporter(66, 353, -7, 63, 524, -1, map, false); + CreateTeleporter(66, 354, -7, 63, 524, -1, map, false); + + CreateTeleporter(61, 523, 6, 63, 352, -3, map, false); + CreateTeleporter(61, 524, 6, 63, 352, -3, map, false); + CreateTeleporter(61, 525, 6, 63, 352, -3, map, false); + CreateTeleporter(61, 526, 6, 63, 352, -3, map, false); + + CreateTeleporter(103, 555, -6, 76, 691, -1, map, false); + CreateTeleporter(103, 556, -6, 76, 691, -1, map, false); + CreateTeleporter(103, 557, -6, 76, 691, -1, map, false); + CreateTeleporter(103, 558, -6, 76, 691, -1, map, false); + + CreateTeleporter(73, 688, 6, 100, 556, -2, map, false); + CreateTeleporter(73, 689, 6, 100, 556, -2, map, false); + CreateTeleporter(73, 690, 6, 100, 556, -2, map, false); + CreateTeleporter(73, 691, 6, 100, 556, -2, map, false); + CreateTeleporter(73, 692, 6, 100, 556, -2, map, false); + CreateTeleporter(73, 693, 6, 100, 556, -2, map, false); + CreateTeleporter(73, 694, 6, 100, 556, -2, map, false); + + //Ninja cave + CreateTeleporter(384, 810, -1, 403, 1167, 0, map, false); + + CreateTeleporter(403, 1169, 0, 385, 811, -1, map, false); + CreateTeleporter(404, 1169, 0, 385, 808, -1, map, false); + CreateTeleporter(405, 1169, 0, 385, 808, -1, map, false); + + // Dungeon Labyrinth + CreateTeleporter(328, 1972, 5, 1731, 978, -80, map, false); // Door exit + CreateTeleporter(328, 1973, 5, 1731, 978, -80, map, false); + CreateTeleporter(328, 1974, 5, 1731, 978, -80, map, false); + CreateTeleporter(328, 1975, 5, 1731, 978, -80, map, false); + + // Dungeon Bedlam + CreateTeleporter(119, 1684, 0, 2068, 1372, -75, map, false); + CreateTeleporter(120, 1684, 0, 2068, 1372, -75, map, false); + CreateTeleporter(121, 1684, 0, 2068, 1372, -75, map, false); + CreateTeleporter(84, 1673, -2, 156, 1613, 0, map, false); + CreateTeleporter(156, 1609, 17, 87, 1673, 0, map, false); + CreateTeleporter(157, 1609, 17, 87, 1673, 0, map, false); + } + + public void CreateTeleportersMap4(Map map) + { + //Yomotso Mines Entrance + CreateTeleporter(257, 783, 63, 5, 128, -1, map, Map.Malas, false); + CreateTeleporter(258, 783, 63, 5, 128, -1, map, Map.Malas, false); + CreateTeleporter(259, 783, 63, 5, 128, -1, map, Map.Malas, false); + CreateTeleporter(260, 783, 63, 5, 128, -1, map, Map.Malas, false); + + //Fan dancer Entrance + CreateTeleporter(988, 194, 15, 67, 337, -1, map, Map.Malas, false); + CreateTeleporter(988, 195, 15, 67, 337, -1, map, Map.Malas, false); + CreateTeleporter(987, 196, 15, 67, 337, -1, map, Map.Malas, false); + CreateTeleporter(988, 197, 18, 67, 337, -1, map, Map.Malas, false); + } + + public void CreateTeleportersTrammel(Map map) + { + // Haven + CreateTeleporter(3632, 2566, 0, 3632, 2566, 20, map, true); + } + + public void CreateTeleportersFelucca(Map map) + { + // Star room + CreateTeleporter(5140, 1773, 0, 5171, 1586, 0, map, false); + } + + public int CreateTeleporters() + { + CreateTeleportersMap(Map.Felucca); + CreateTeleportersMap(Map.Trammel); + CreateTeleportersTrammel(Map.Trammel); + CreateTeleportersFelucca(Map.Felucca); + CreateTeleportersMap2(Map.Ilshenar); + CreateTeleportersMap3(Map.Malas); + CreateTeleportersMap4(Map.Tokuno); + return m_Count; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Commands/BaseCommand.cs b/Scripts/Commands/Generic/Commands/BaseCommand.cs index a3c7a35ae..b8808f782 100644 --- a/Scripts/Commands/Generic/Commands/BaseCommand.cs +++ b/Scripts/Commands/Generic/Commands/BaseCommand.cs @@ -1,163 +1,158 @@ -using System; using System.Collections; using Server.Gumps; namespace Server.Commands.Generic { - public enum ObjectTypes - { - Both, - Items, - Mobiles, - All - } + public enum ObjectTypes + { + Both, + Items, + Mobiles, + All + } - public abstract class BaseCommand - { - public bool ListOptimized { get; set; } + public abstract class BaseCommand + { + private ArrayList m_Responses, m_Failures; - public string[] Commands { get; set; } + public BaseCommand() + { + m_Responses = new ArrayList(); + m_Failures = new ArrayList(); + } - public string Usage { get; set; } + public bool ListOptimized{ get; set; } - public string Description { get; set; } + public string[] Commands{ get; set; } - public AccessLevel AccessLevel { get; set; } + public string Usage{ get; set; } - public ObjectTypes ObjectTypes { get; set; } + public string Description{ get; set; } - public CommandSupport Supports { get; set; } + public AccessLevel AccessLevel{ get; set; } - public BaseCommand() - { - m_Responses = new ArrayList(); - m_Failures = new ArrayList(); - } + public ObjectTypes ObjectTypes{ get; set; } - public static bool IsAccessible( Mobile from, object obj ) - { - if ( from.AccessLevel >= AccessLevel.Administrator || obj == null ) - return true; + public CommandSupport Supports{ get; set; } - Mobile mob = null; + public static bool IsAccessible(Mobile from, object obj) + { + if (from.AccessLevel >= AccessLevel.Administrator || obj == null) + return true; - if ( obj is Mobile m ) - mob = m; - else if ( obj is Item item ) - mob = item.RootParent as Mobile; + Mobile mob = null; - return mob == null || mob == from || from.AccessLevel > mob.AccessLevel; - } + if (obj is Mobile m) + mob = m; + else if (obj is Item item) + mob = item.RootParent as Mobile; - public virtual void ExecuteList( CommandEventArgs e, ArrayList list ) - { - for ( int i = 0; i < list.Count; ++i ) - Execute( e, list[i] ); - } + return mob == null || mob == from || from.AccessLevel > mob.AccessLevel; + } - public virtual void Execute( CommandEventArgs e, object obj ) - { - } + public virtual void ExecuteList(CommandEventArgs e, ArrayList list) + { + for (int i = 0; i < list.Count; ++i) + Execute(e, list[i]); + } - public virtual bool ValidateArgs( BaseCommandImplementor impl, CommandEventArgs e ) - { - return true; - } + public virtual void Execute(CommandEventArgs e, object obj) + { + } - private ArrayList m_Responses, m_Failures; + public virtual bool ValidateArgs(BaseCommandImplementor impl, CommandEventArgs e) + { + return true; + } - private class MessageEntry - { - public string m_Message; - public int m_Count; + public void AddResponse(string message) + { + for (int i = 0; i < m_Responses.Count; ++i) + { + MessageEntry entry = (MessageEntry)m_Responses[i]; - public MessageEntry( string message ) - { - m_Message = message; - m_Count = 1; - } + if (entry.m_Message == message) + { + ++entry.m_Count; + return; + } + } - public override string ToString() - { - if ( m_Count > 1 ) - return $"{m_Message} ({m_Count})"; + if (m_Responses.Count == 10) + return; - return m_Message; - } - } + m_Responses.Add(new MessageEntry(message)); + } - public void AddResponse( string message ) - { - for ( int i = 0; i < m_Responses.Count; ++i ) - { - MessageEntry entry = (MessageEntry)m_Responses[i]; + public void AddResponse(Gump gump) + { + m_Responses.Add(gump); + } - if ( entry.m_Message == message ) - { - ++entry.m_Count; - return; - } - } + public void LogFailure(string message) + { + for (int i = 0; i < m_Failures.Count; ++i) + { + MessageEntry entry = (MessageEntry)m_Failures[i]; - if ( m_Responses.Count == 10 ) - return; + if (entry.m_Message == message) + { + ++entry.m_Count; + return; + } + } - m_Responses.Add( new MessageEntry( message ) ); - } + if (m_Failures.Count == 10) + return; - public void AddResponse( Gump gump ) - { - m_Responses.Add( gump ); - } + m_Failures.Add(new MessageEntry(message)); + } - public void LogFailure( string message ) - { - for ( int i = 0; i < m_Failures.Count; ++i ) - { - MessageEntry entry = (MessageEntry)m_Failures[i]; + public void Flush(Mobile from, bool flushToLog) + { + if (m_Responses.Count > 0) + for (int i = 0; i < m_Responses.Count; ++i) + { + object obj = m_Responses[i]; - if ( entry.m_Message == message ) - { - ++entry.m_Count; - return; - } - } + if (obj is MessageEntry entry) + { + from.SendMessage(entry.ToString()); - if ( m_Failures.Count == 10 ) - return; + if (flushToLog) + CommandLogging.WriteLine(from, entry.ToString()); + } + else if (obj is Gump gump) + { + from.SendGump(gump); + } + } + else + for (int i = 0; i < m_Failures.Count; ++i) + from.SendMessage(((MessageEntry)m_Failures[i]).ToString()); - m_Failures.Add( new MessageEntry( message ) ); - } + m_Responses.Clear(); + m_Failures.Clear(); + } - public void Flush( Mobile from, bool flushToLog ) - { - if ( m_Responses.Count > 0 ) - { - for ( int i = 0; i < m_Responses.Count; ++i ) - { - object obj = m_Responses[i]; + private class MessageEntry + { + public int m_Count; + public string m_Message; - if ( obj is MessageEntry entry ) - { - from.SendMessage( entry.ToString() ); + public MessageEntry(string message) + { + m_Message = message; + m_Count = 1; + } - if ( flushToLog ) - CommandLogging.WriteLine( from, entry.ToString() ); - } - else if ( obj is Gump gump ) - { - from.SendGump( gump ); - } - } - } - else - { - for ( int i = 0; i < m_Failures.Count; ++i ) - from.SendMessage( ((MessageEntry)m_Failures[i]).ToString() ); - } + public override string ToString() + { + if (m_Count > 1) + return $"{m_Message} ({m_Count})"; - m_Responses.Clear(); - m_Failures.Clear(); - } - } -} + return m_Message; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Commands/Commands.cs b/Scripts/Commands/Generic/Commands/Commands.cs index 36dc5f4d4..cef65354f 100644 --- a/Scripts/Commands/Generic/Commands/Commands.cs +++ b/Scripts/Commands/Generic/Commands/Commands.cs @@ -3,8 +3,9 @@ using System.Collections; using System.Collections.Generic; using Server.Accounting; using Server.Engines.Help; -using Server.Items; +using Server.Factions; using Server.Gumps; +using Server.Items; using Server.Mobiles; using Server.Multis; using Server.Network; @@ -12,1094 +13,1108 @@ using Server.Spells; namespace Server.Commands.Generic { - public class TargetCommands - { - public static void Initialize() - { - Register( new KillCommand( true ) ); - Register( new KillCommand( false ) ); - Register( new HideCommand( true ) ); - Register( new HideCommand( false ) ); - Register( new KickCommand( true ) ); - Register( new KickCommand( false ) ); - Register( new FirewallCommand() ); - Register( new TeleCommand() ); - Register( new SetCommand() ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "Immortal", "blessed", "true", ObjectTypes.Mobiles ) ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "Invul", "blessed", "true", ObjectTypes.Mobiles ) ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "Mortal", "blessed", "false", ObjectTypes.Mobiles ) ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "NoInvul", "blessed", "false", ObjectTypes.Mobiles ) ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "Squelch", "squelched", "true", ObjectTypes.Mobiles ) ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "Unsquelch", "squelched", "false", ObjectTypes.Mobiles ) ); - - Register( new AliasedSetCommand( AccessLevel.GameMaster, "ShaveHair", "HairItemID", "0", ObjectTypes.Mobiles ) ); - Register( new AliasedSetCommand( AccessLevel.GameMaster, "ShaveBeard", "FacialHairItemID", "0", ObjectTypes.Mobiles ) ); - - Register( new GetCommand() ); - Register( new GetTypeCommand() ); - Register( new DeleteCommand() ); - Register( new RestockCommand() ); - Register( new DismountCommand() ); - Register( new AddCommand() ); - Register( new AddToPackCommand() ); - Register( new TellCommand( true ) ); - Register( new TellCommand( false ) ); - Register( new PrivSoundCommand() ); - Register( new IncreaseCommand() ); - Register( new OpenBrowserCommand() ); - Register( new CountCommand() ); - Register( new InterfaceCommand() ); - Register( new RefreshHouseCommand() ); - Register( new ConditionCommand() ); - Register( new Factions.FactionKickCommand( Factions.FactionKickType.Kick ) ); - Register( new Factions.FactionKickCommand( Factions.FactionKickType.Ban ) ); - Register( new Factions.FactionKickCommand( Factions.FactionKickType.Unban ) ); - Register( new BringToPackCommand() ); - Register( new TraceLockdownCommand() ); - } - - public static List AllCommands { get; } = new List(); - - public static void Register( BaseCommand command ) - { - AllCommands.Add( command ); - - List impls = BaseCommandImplementor.Implementors; - - for ( int i = 0; i < impls.Count; ++i ) - { - BaseCommandImplementor impl = impls[i]; - - if ( (command.Supports & impl.SupportRequirement) != 0 ) - impl.Register( command ); - } - } - } - - public class ConditionCommand : BaseCommand - { - public ConditionCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Simple | CommandSupport.Complex | CommandSupport.Self; - Commands = new[]{ "Condition" }; - ObjectTypes = ObjectTypes.All; - Usage = "Condition "; - Description = "Checks that the given condition matches a targeted object."; - ListOptimized = true; - } - - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - try - { - string[] args = e.Arguments; - ObjectConditional condition = ObjectConditional.Parse( e.Mobile, ref args ); - - for ( int i = 0; i < list.Count; ++i ) - { - if ( condition.CheckCondition( list[i] ) ) - AddResponse( "True - that object matches the condition." ); - else - AddResponse( "False - that object does not match the condition." ); - } - } - catch ( Exception ex ) - { - e.Mobile.SendMessage( ex.Message ); - } - } - } - - public class BringToPackCommand : BaseCommand - { - public BringToPackCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllItems; - Commands = new[]{ "BringToPack" }; - ObjectTypes = ObjectTypes.Items; - Usage = "BringToPack"; - Description = "Brings a targeted item to your backpack."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj is Item item ) - { - if ( e.Mobile.PlaceInBackpack( item ) ) - AddResponse( "The item has been placed in your backpack." ); - else - AddResponse( "Your backpack could not hold the item." ); - } - } - } - - public class RefreshHouseCommand : BaseCommand - { - public RefreshHouseCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Simple; - Commands = new[]{ "RefreshHouse" }; - ObjectTypes = ObjectTypes.Items; - Usage = "RefreshHouse"; - Description = "Refreshes a targeted house sign."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj is HouseSign sign ) - { - BaseHouse house = sign.Owner; - - if ( house == null ) - { - LogFailure( "That sign has no house attached." ); - } - else - { - house.RefreshDecay(); - AddResponse( "The house has been refreshed." ); - } - } - else - { - LogFailure( "That is not a house sign." ); - } - } - } - - public class CountCommand : BaseCommand - { - public CountCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Complex; - Commands = new[]{ "Count" }; - ObjectTypes = ObjectTypes.All; - Usage = "Count"; - Description = "Counts the number of objects that a command modifier would use. Generally used with condition arguments."; - ListOptimized = true; - } - - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - if ( list.Count == 1 ) - AddResponse( "There is one matching object." ); - else - AddResponse($"There are {list.Count} matching objects."); - } - } - - public class OpenBrowserCommand : BaseCommand - { - public OpenBrowserCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllMobiles; - Commands = new[]{ "OpenBrowser", "OB" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "OpenBrowser "; - Description = "Opens the web browser of a targeted player to a specified url."; - } - - public static void OpenBrowser_Callback( Mobile from, bool okay, object state ) - { - object[] states = (object[])state; - Mobile gm = (Mobile)states[0]; - string url = (string)states[1]; - bool echo = (bool)states[2]; - - if ( okay ) - { - if ( echo ) - gm.SendMessage( "{0} : has opened their web browser to : {1}", from.Name, url ); - - from.LaunchBrowser( url ); - } - else - { - if ( echo ) - gm.SendMessage( "{0} : has chosen not to open their web browser to : {1}", from.Name, url ); - - from.SendMessage( "You have chosen not to open your web browser." ); - } - } - - public void Execute( CommandEventArgs e, object obj, bool echo ) - { - if ( e.Length == 1 ) - { - Mobile mob = (Mobile)obj; - Mobile from = e.Mobile; - - if ( mob.Player ) - { - NetState ns = mob.NetState; - - if ( ns == null ) - { - LogFailure( "That player is not online." ); - } - else - { - string url = e.GetString( 0 ); - - CommandLogging.WriteLine( from, "{0} {1} requesting to open web browser of {2} to {3}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( mob ), url ); - - if ( echo ) - AddResponse( "Awaiting user confirmation..." ); - else - AddResponse( "Open web browser request sent." ); - - mob.SendGump( new WarningGump( 1060637, 30720, - $"A game master is requesting to open your web browser to the following URL:
{url}", 0xFFC000, 320, 240, OpenBrowser_Callback, new object[]{ from, url, echo } ) ); - } - } - else - { - LogFailure( "That is not a player." ); - } - } - else - { - LogFailure( "Format: OpenBrowser " ); - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Execute( e, obj, true ); - } - - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - for ( int i = 0; i < list.Count; ++i ) - Execute( e, list[i], false ); - } - } - - public class IncreaseCommand : BaseCommand - { - public IncreaseCommand() - { - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.All; - Commands = new[]{ "Increase", "Inc" }; - ObjectTypes = ObjectTypes.Both; - Usage = "Increase { ...}"; - Description = "Increases the value of a specified property by the specified offset."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj is BaseMulti ) - { - LogFailure( "This command does not work on multis." ); - } - else if ( e.Length >= 2 ) - { - string result = Properties.IncreaseValue( e.Mobile, obj, e.Arguments ); - - if ( result == "The property has been increased." || result == "The properties have been increased." || result == "The property has been decreased." || result == "The properties have been decreased." || result == "The properties have been changed." ) - AddResponse( result ); - else - LogFailure( result ); - } - else - { - LogFailure( "Format: Increase { ...}" ); - } - } - } - - public class PrivSoundCommand : BaseCommand - { - public PrivSoundCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllMobiles; - Commands = new[]{ "PrivSound" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "PrivSound "; - Description = "Plays a sound to a given target."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile from = e.Mobile; - - if ( e.Length == 1 ) - { - int index = e.GetInt32( 0 ); - Mobile mob = (Mobile)obj; - - CommandLogging.WriteLine( from, "{0} {1} playing sound {2} for {3}", from.AccessLevel, CommandLogging.Format( from ), index, CommandLogging.Format( mob ) ); - mob.Send( new PlaySound( index, mob.Location ) ); - } - else - { - from.SendMessage( "Format: PrivSound " ); - } - } - } - - public class TellCommand : BaseCommand - { - private bool m_InGump; - - public TellCommand( bool inGump ) - { - m_InGump = inGump; - - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.AllMobiles; - ObjectTypes = ObjectTypes.Mobiles; - - if ( inGump ) - { - Commands = new[]{ "Message", "Msg" }; - Usage = "Message \"text\""; - Description = "Sends a message to a targeted player."; - } - else - { - Commands = new[]{ "Tell" }; - Usage = "Tell \"text\""; - Description = "Sends a system message to a targeted player."; - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile mob = (Mobile)obj; - Mobile from = e.Mobile; - - CommandLogging.WriteLine( from, "{0} {1} {2} {3} \"{4}\"", from.AccessLevel, CommandLogging.Format( from ), m_InGump ? "messaging" : "telling", CommandLogging.Format( mob ), e.ArgString ); - - if ( m_InGump ) - mob.SendGump( new MessageSentGump( mob, from.Name, e.ArgString ) ); - else - mob.SendMessage( e.ArgString ); - } - } - - public class AddToPackCommand : BaseCommand - { - public AddToPackCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.All; - Commands = new[]{ "AddToPack", "AddToCont" }; - ObjectTypes = ObjectTypes.Both; - ListOptimized = true; - Usage = "AddToPack [params] [set { ...}]"; - Description = "Adds an item by name to the backpack of a targeted player or npc, or a targeted container. Optional constructor parameters. Optional set property list."; - } - - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - if ( e.Arguments.Length == 0 ) - return; - - List packs = new List( list.Count ); - - for ( int i = 0; i < list.Count; ++i ) - { - object obj = list[i]; - Container cont = null; - - if ( obj is Mobile mobile ) - cont = mobile.Backpack; - else if ( obj is Container container ) - cont = container; - - if ( cont != null ) - packs.Add( cont ); - else - LogFailure( "That is not a container." ); - } - - Add.Invoke( e.Mobile, e.Mobile.Location, e.Mobile.Location, e.Arguments, packs ); - } - } - - public class AddCommand : BaseCommand - { - public AddCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Simple | CommandSupport.Self; - Commands = new[]{ "Add" }; - ObjectTypes = ObjectTypes.All; - Usage = "Add [ [params] [set { ...}]]"; - Description = "Adds an item or npc by name to a targeted location. Optional constructor parameters. Optional set property list. If no arguments are specified, this brings up a categorized add menu."; - } - - public override bool ValidateArgs( BaseCommandImplementor impl, CommandEventArgs e ) - { - if ( e.Length >= 1 ) - { - Type t = ScriptCompiler.FindTypeByName( e.GetString( 0 ) ); - - if ( t == null ) - { - e.Mobile.SendMessage( "No type with that name was found." ); - - string match = e.GetString( 0 ).Trim(); - - if ( match.Length < 3 ) - { - e.Mobile.SendMessage( "Invalid search string." ); - e.Mobile.SendGump( new AddGump( e.Mobile, match, 0, Type.EmptyTypes, false ) ); - } - else - { - e.Mobile.SendGump( new AddGump( e.Mobile, match, 0, AddGump.Match( match ).ToArray(), true ) ); - } - } - else - { - return true; - } - } - else - { - e.Mobile.SendGump( new CategorizedAddGump( e.Mobile ) ); - } - - return false; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( !(obj is IPoint3D p) ) - return; - - if ( p is Item item ) - p = item.GetWorldTop(); - else if ( p is Mobile m ) - p = m.Location; - - Add.Invoke( e.Mobile, new Point3D( p ), new Point3D( p ), e.Arguments ); - } - } - - public class TeleCommand : BaseCommand - { - public TeleCommand() - { - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.Simple; - Commands = new[]{ "Teleport", "Tele" }; - ObjectTypes = ObjectTypes.All; - Usage = "Teleport"; - Description = "Teleports your character to a targeted location."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( !(obj is IPoint3D p) ) - return; - - Mobile from = e.Mobile; - - SpellHelper.GetSurfaceTop( ref p ); - - //CommandLogging.WriteLine( from, "{0} {1} teleporting to {2}", from.AccessLevel, CommandLogging.Format( from ), new Point3D( p ) ); - - Point3D fromLoc = from.Location; - Point3D toLoc = new Point3D( p ); - - from.Location = toLoc; - from.ProcessDelta(); - - if ( !from.Hidden ) - { - Effects.SendLocationParticles( EffectItem.Create( fromLoc, from.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( toLoc, from.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); - - from.PlaySound( 0x1FE ); - } - } - } - - public class DismountCommand : BaseCommand - { - public DismountCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllMobiles; - Commands = new[]{ "Dismount" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "Dismount"; - Description = "Forcefully dismounts a given target."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile from = e.Mobile; - Mobile mob = (Mobile)obj; - - CommandLogging.WriteLine( from, "{0} {1} dismounting {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( mob ) ); - - bool takenAction = false; - - for ( int i = 0; i < mob.Items.Count; ++i ) - { - Item item = mob.Items[i]; - - if ( item is IMountItem mountItem ) - { - IMount mount = mountItem.Mount; - - if ( mount != null ) - { - mount.Rider = null; - takenAction = true; - } - - if ( mob.Items.IndexOf( item ) == -1 ) - --i; - } - } - - for ( int i = 0; i < mob.Items.Count; ++i ) - { - Item item = mob.Items[i]; - - if ( item.Layer == Layer.Mount ) - { - takenAction = true; - item.Delete(); - --i; - } - } - - if ( takenAction ) - AddResponse( "They have been dismounted." ); - else - LogFailure( "They were not mounted." ); - } - } - - public class RestockCommand : BaseCommand - { - public RestockCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllNPCs; - Commands = new[]{ "Restock" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "Restock"; - Description = "Manually restocks a targeted vendor, refreshing the quantity of every item the vendor sells to the maximum. This also invokes the maximum quantity adjustment algorithms."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj is BaseVendor vendor ) - { - CommandLogging.WriteLine( e.Mobile, "{0} {1} restocking {2}", e.Mobile.AccessLevel, CommandLogging.Format( e.Mobile ), CommandLogging.Format( vendor ) ); - - vendor.Restock(); - AddResponse( "The vendor has been restocked." ); - } - else - { - AddResponse( "That is not a vendor." ); - } - } - } - - public class GetTypeCommand : BaseCommand - { - public GetTypeCommand() - { - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.All; - Commands = new[]{ "GetType" }; - ObjectTypes = ObjectTypes.All; - Usage = "GetType"; - Description = "Gets the type name of a targeted object."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj == null ) - { - AddResponse( "The object is null." ); - } - else - { - Type type = obj.GetType(); - - if ( type.DeclaringType == null ) - AddResponse($"The type of that object is {type.Name}."); - else - AddResponse($"The type of that object is {type.FullName}."); - } - } - } - - public class GetCommand : BaseCommand - { - public GetCommand() - { - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.All; - Commands = new[]{ "Get" }; - ObjectTypes = ObjectTypes.All; - Usage = "Get "; - Description = "Gets one or more property values by name of a targeted object."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( e.Length >= 1 ) - { - for ( int i = 0; i < e.Length; ++i ) - { - string result = Properties.GetValue( e.Mobile, obj, e.GetString( i ) ); - - if ( result == "Property not found." || result == "Property is write only." || result.StartsWith( "Getting this property" ) ) - LogFailure( result ); - else - AddResponse( result ); - } - } - else - { - LogFailure( "Format: Get " ); - } - } - } - - public class AliasedSetCommand : BaseCommand - { - private string m_Name; - private string m_Value; - - public AliasedSetCommand( AccessLevel level, string command, string name, string value, ObjectTypes objects ) - { - m_Name = name; - m_Value = value; - - AccessLevel = level; - - if ( objects == ObjectTypes.Items ) - Supports = CommandSupport.AllItems; - else if ( objects == ObjectTypes.Mobiles ) - Supports = CommandSupport.AllMobiles; - else - Supports = CommandSupport.All; - - Commands = new[]{ command }; - ObjectTypes = objects; - Usage = command; - Description = $"Sets the {name} property to {value}."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - string result = Properties.SetValue( e.Mobile, obj, m_Name, m_Value ); - - if ( result == "Property has been set." ) - AddResponse( result ); - else - LogFailure( result ); - } - } - - public class SetCommand : BaseCommand - { - public SetCommand() - { - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.All; - Commands = new[]{ "Set" }; - ObjectTypes = ObjectTypes.Both; - Usage = "Set [...]"; - Description = "Sets one or more property values by name of a targeted object."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( e.Length >= 2 ) - { - for ( int i = 0; (i+1) < e.Length; i += 2 ) - { - string result = Properties.SetValue( e.Mobile, obj, e.GetString( i ), e.GetString( i+1 ) ); - - if ( result == "Property has been set." ) - AddResponse( result ); - else - LogFailure( result ); - } - } - else - { - LogFailure( "Format: Set " ); - } - } - } - - public class DeleteCommand : BaseCommand - { - public DeleteCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllNPCs | CommandSupport.AllItems; - Commands = new[]{ "Delete", "Remove" }; - ObjectTypes = ObjectTypes.Both; - Usage = "Delete"; - Description = "Deletes a targeted item or mobile. Does not delete players."; - } - - private void OnConfirmCallback( Mobile from, bool okay, object state ) - { - object[] states = (object[])state; - CommandEventArgs e = (CommandEventArgs)states[0]; - ArrayList list = (ArrayList)states[1]; - - bool flushToLog = false; - - if ( okay ) - { - AddResponse( "Delete command confirmed." ); - - if ( list.Count > 20 ) - { - CommandLogging.Enabled = false; - NetState.Pause(); - } - - base.ExecuteList( e, list ); - - if ( list.Count > 20 ) - { - NetState.Resume(); - flushToLog = true; - CommandLogging.Enabled = true; - } - } - else - { - AddResponse( "Delete command aborted." ); - } - - Flush( from, flushToLog ); - } - - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - if ( list.Count > 1 ) - { - e.Mobile.SendGump( new WarningGump( 1060637, 30720, - $"You are about to delete {list.Count} objects. This cannot be undone without a full server revert.

Continue?", 0xFFC000, 420, 280, OnConfirmCallback, new object[]{ e, list } ) ); - AddResponse( "Awaiting confirmation..." ); - } - else - { - base.ExecuteList( e, list ); - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj is Item item ) - { - CommandLogging.WriteLine( e.Mobile, "{0} {1} deleting {2}", e.Mobile.AccessLevel, CommandLogging.Format( e.Mobile ), CommandLogging.Format( item ) ); - item.Delete(); - AddResponse( "The item has been deleted." ); - } - else if ( obj is Mobile mobile && !mobile.Player ) - { - CommandLogging.WriteLine( e.Mobile, "{0} {1} deleting {2}", e.Mobile.AccessLevel, CommandLogging.Format( e.Mobile ), CommandLogging.Format( mobile ) ); - mobile.Delete(); - AddResponse( "The mobile has been deleted." ); - } - else - { - LogFailure( "That cannot be deleted." ); - } - } - } - - public class KillCommand : BaseCommand - { - private bool m_Value; - - public KillCommand( bool value ) - { - m_Value = value; - - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllMobiles; - Commands = value ? new[]{ "Kill" } : new[]{ "Resurrect", "Res" }; - ObjectTypes = ObjectTypes.Mobiles; - - if ( value ) - { - Usage = "Kill"; - Description = "Kills a targeted player or npc."; - } - else - { - Usage = "Resurrect"; - Description = "Resurrects a targeted ghost."; - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile mob = (Mobile)obj; - Mobile from = e.Mobile; - - if ( m_Value ) - { - if ( !mob.Alive ) - { - LogFailure( "They are already dead." ); - } - else if ( !mob.CanBeDamaged() ) - { - LogFailure( "They cannot be harmed." ); - } - else - { - CommandLogging.WriteLine( from, "{0} {1} killing {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( mob ) ); - mob.Kill(); - - AddResponse( "They have been killed." ); - } - } - else - { - if ( mob.IsDeadBondedPet ) - { - if ( mob is BaseCreature bc ) - { - CommandLogging.WriteLine( from, "{0} {1} resurrecting {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( mob ) ); - - bc.PlaySound( 0x214 ); - bc.FixedEffect( 0x376A, 10, 16 ); - - bc.ResurrectPet(); - - AddResponse( "It has been resurrected." ); - } - } - else if ( !mob.Alive ) - { - CommandLogging.WriteLine( from, "{0} {1} resurrecting {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( mob ) ); - - mob.PlaySound( 0x214 ); - mob.FixedEffect( 0x376A, 10, 16 ); - - mob.Resurrect(); - - AddResponse( "They have been resurrected." ); - } - else - { - LogFailure( "They are not dead." ); - } - } - } - } - - public class HideCommand : BaseCommand - { - private bool m_Value; - - public HideCommand( bool value ) - { - m_Value = value; - - AccessLevel = AccessLevel.Counselor; - Supports = CommandSupport.AllMobiles; - Commands = new[]{ value ? "Hide" : "Unhide" }; - ObjectTypes = ObjectTypes.Mobiles; - - if ( value ) - { - Usage = "Hide"; - Description = "Makes a targeted mobile disappear in a puff of smoke."; - } - else - { - Usage = "Unhide"; - Description = "Makes a targeted mobile appear in a puff of smoke."; - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile m = (Mobile)obj; - - CommandLogging.WriteLine( e.Mobile, "{0} {1} {2} {3}", e.Mobile.AccessLevel, CommandLogging.Format( e.Mobile ), m_Value ? "hiding" : "unhiding", CommandLogging.Format( m ) ); - - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y, m.Z + 4 ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y, m.Z ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y, m.Z - 4 ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X, m.Y + 1, m.Z + 4 ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X, m.Y + 1, m.Z ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X, m.Y + 1, m.Z - 4 ), m.Map, 0x3728, 13 ); - - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y + 1, m.Z + 11 ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y + 1, m.Z + 7 ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y + 1, m.Z + 3 ), m.Map, 0x3728, 13 ); - Effects.SendLocationEffect( new Point3D( m.X + 1, m.Y + 1, m.Z - 1 ), m.Map, 0x3728, 13 ); - - m.PlaySound( 0x228 ); - m.Hidden = m_Value; - - if ( m_Value ) - AddResponse( "They have been hidden." ); - else - AddResponse( "They have been revealed." ); - } - } - - public class FirewallCommand : BaseCommand - { - public FirewallCommand() - { - AccessLevel = AccessLevel.Administrator; - Supports = CommandSupport.AllMobiles; - Commands = new[]{ "Firewall" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "Firewall"; - Description = "Adds a targeted player to the firewall (list of blocked IP addresses). This command does not ban or kick."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile from = e.Mobile; - Mobile targ = (Mobile)obj; - NetState state = targ.NetState; - - if ( state != null ) - { - CommandLogging.WriteLine( from, "{0} {1} firewalling {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( targ ) ); - - try - { - Firewall.Add( state.Address ); - AddResponse( "They have been firewalled." ); - } - catch ( Exception ex ) - { - LogFailure( ex.Message ); - } - } - else - { - LogFailure( "They are not online." ); - } - } - } - - public class KickCommand : BaseCommand - { - private bool m_Ban; - - public KickCommand( bool ban ) - { - m_Ban = ban; - - AccessLevel = ( ban ? AccessLevel.Administrator : AccessLevel.GameMaster ); - Supports = CommandSupport.AllMobiles; - Commands = new[]{ ban ? "Ban" : "Kick" }; - ObjectTypes = ObjectTypes.Mobiles; - - if ( ban ) - { - Usage = "Ban"; - Description = "Bans the account of a targeted player."; - } - else - { - Usage = "Kick"; - Description = "Disconnects a targeted player."; - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile from = e.Mobile; - Mobile targ = (Mobile)obj; - - if ( from.AccessLevel > targ.AccessLevel ) - { - NetState fromState = from.NetState, targState = targ.NetState; - - if ( fromState != null && targState != null ) - { - if ( fromState.Account is Account && targState.Account is Account targAccount ) - { - CommandLogging.WriteLine( from, "{0} {1} {2} {3}", from.AccessLevel, CommandLogging.Format( from ), m_Ban ? "banning" : "kicking", CommandLogging.Format( targ ) ); - - targ.Say( "I've been {0}!", m_Ban ? "banned" : "kicked" ); - - AddResponse($"They have been {(m_Ban ? "banned" : "kicked")}."); - - targState.Dispose(); - - if ( m_Ban ) - { - targAccount.Banned = true; - targAccount.SetUnspecifiedBan( from ); - from.SendGump( new BanDurationGump( targAccount ) ); - } - } - } - else if ( targState == null ) - { - LogFailure( "They are not online." ); - } - } - else - { - LogFailure( "You do not have the required access level to do this." ); - } - } - } - - public class TraceLockdownCommand : BaseCommand - { - public TraceLockdownCommand() - { - AccessLevel = AccessLevel.Administrator; - Supports = CommandSupport.Simple; - Commands = new[] { "TraceLockdown" }; - ObjectTypes = ObjectTypes.Items; - Usage = "TraceLockdown"; - Description = "Finds the BaseHouse for which a targeted item is locked down or secured."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( !(obj is Item item) ) - return; - - if ( !item.IsLockedDown && !item.IsSecure ) - { - LogFailure( "That is not locked down." ); - return; - } - - foreach ( BaseHouse house in BaseHouse.AllHouses ) - { - if ( house.IsSecure( item ) || house.IsLockedDown( item ) ) - { - e.Mobile.SendGump( new PropertiesGump( e.Mobile, house ) ); - return; - } - } - - LogFailure( "No house was found." ); - } - } -} + public class TargetCommands + { + public static List AllCommands{ get; } = new List(); + + public static void Initialize() + { + Register(new KillCommand(true)); + Register(new KillCommand(false)); + Register(new HideCommand(true)); + Register(new HideCommand(false)); + Register(new KickCommand(true)); + Register(new KickCommand(false)); + Register(new FirewallCommand()); + Register(new TeleCommand()); + Register(new SetCommand()); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "Immortal", "blessed", "true", ObjectTypes.Mobiles)); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "Invul", "blessed", "true", ObjectTypes.Mobiles)); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "Mortal", "blessed", "false", ObjectTypes.Mobiles)); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "NoInvul", "blessed", "false", ObjectTypes.Mobiles)); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "Squelch", "squelched", "true", ObjectTypes.Mobiles)); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "Unsquelch", "squelched", "false", ObjectTypes.Mobiles)); + + Register(new AliasedSetCommand(AccessLevel.GameMaster, "ShaveHair", "HairItemID", "0", ObjectTypes.Mobiles)); + Register(new AliasedSetCommand(AccessLevel.GameMaster, "ShaveBeard", "FacialHairItemID", "0", + ObjectTypes.Mobiles)); + + Register(new GetCommand()); + Register(new GetTypeCommand()); + Register(new DeleteCommand()); + Register(new RestockCommand()); + Register(new DismountCommand()); + Register(new AddCommand()); + Register(new AddToPackCommand()); + Register(new TellCommand(true)); + Register(new TellCommand(false)); + Register(new PrivSoundCommand()); + Register(new IncreaseCommand()); + Register(new OpenBrowserCommand()); + Register(new CountCommand()); + Register(new InterfaceCommand()); + Register(new RefreshHouseCommand()); + Register(new ConditionCommand()); + Register(new FactionKickCommand(FactionKickType.Kick)); + Register(new FactionKickCommand(FactionKickType.Ban)); + Register(new FactionKickCommand(FactionKickType.Unban)); + Register(new BringToPackCommand()); + Register(new TraceLockdownCommand()); + } + + public static void Register(BaseCommand command) + { + AllCommands.Add(command); + + List impls = BaseCommandImplementor.Implementors; + + for (int i = 0; i < impls.Count; ++i) + { + BaseCommandImplementor impl = impls[i]; + + if ((command.Supports & impl.SupportRequirement) != 0) + impl.Register(command); + } + } + } + + public class ConditionCommand : BaseCommand + { + public ConditionCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Simple | CommandSupport.Complex | CommandSupport.Self; + Commands = new[] { "Condition" }; + ObjectTypes = ObjectTypes.All; + Usage = "Condition "; + Description = "Checks that the given condition matches a targeted object."; + ListOptimized = true; + } + + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + try + { + string[] args = e.Arguments; + ObjectConditional condition = ObjectConditional.Parse(e.Mobile, ref args); + + for (int i = 0; i < list.Count; ++i) + if (condition.CheckCondition(list[i])) + AddResponse("True - that object matches the condition."); + else + AddResponse("False - that object does not match the condition."); + } + catch (Exception ex) + { + e.Mobile.SendMessage(ex.Message); + } + } + } + + public class BringToPackCommand : BaseCommand + { + public BringToPackCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllItems; + Commands = new[] { "BringToPack" }; + ObjectTypes = ObjectTypes.Items; + Usage = "BringToPack"; + Description = "Brings a targeted item to your backpack."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (obj is Item item) + { + if (e.Mobile.PlaceInBackpack(item)) + AddResponse("The item has been placed in your backpack."); + else + AddResponse("Your backpack could not hold the item."); + } + } + } + + public class RefreshHouseCommand : BaseCommand + { + public RefreshHouseCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Simple; + Commands = new[] { "RefreshHouse" }; + ObjectTypes = ObjectTypes.Items; + Usage = "RefreshHouse"; + Description = "Refreshes a targeted house sign."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (obj is HouseSign sign) + { + BaseHouse house = sign.Owner; + + if (house == null) + { + LogFailure("That sign has no house attached."); + } + else + { + house.RefreshDecay(); + AddResponse("The house has been refreshed."); + } + } + else + { + LogFailure("That is not a house sign."); + } + } + } + + public class CountCommand : BaseCommand + { + public CountCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Complex; + Commands = new[] { "Count" }; + ObjectTypes = ObjectTypes.All; + Usage = "Count"; + Description = + "Counts the number of objects that a command modifier would use. Generally used with condition arguments."; + ListOptimized = true; + } + + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + if (list.Count == 1) + AddResponse("There is one matching object."); + else + AddResponse($"There are {list.Count} matching objects."); + } + } + + public class OpenBrowserCommand : BaseCommand + { + public OpenBrowserCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllMobiles; + Commands = new[] { "OpenBrowser", "OB" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "OpenBrowser "; + Description = "Opens the web browser of a targeted player to a specified url."; + } + + public static void OpenBrowser_Callback(Mobile from, bool okay, object state) + { + object[] states = (object[])state; + Mobile gm = (Mobile)states[0]; + string url = (string)states[1]; + bool echo = (bool)states[2]; + + if (okay) + { + if (echo) + gm.SendMessage("{0} : has opened their web browser to : {1}", from.Name, url); + + from.LaunchBrowser(url); + } + else + { + if (echo) + gm.SendMessage("{0} : has chosen not to open their web browser to : {1}", from.Name, url); + + from.SendMessage("You have chosen not to open your web browser."); + } + } + + public void Execute(CommandEventArgs e, object obj, bool echo) + { + if (e.Length == 1) + { + Mobile mob = (Mobile)obj; + Mobile from = e.Mobile; + + if (mob.Player) + { + NetState ns = mob.NetState; + + if (ns == null) + { + LogFailure("That player is not online."); + } + else + { + string url = e.GetString(0); + + CommandLogging.WriteLine(from, "{0} {1} requesting to open web browser of {2} to {3}", + from.AccessLevel, CommandLogging.Format(from), CommandLogging.Format(mob), url); + + if (echo) + AddResponse("Awaiting user confirmation..."); + else + AddResponse("Open web browser request sent."); + + mob.SendGump(new WarningGump(1060637, 30720, + $"A game master is requesting to open your web browser to the following URL:
{url}", 0xFFC000, + 320, 240, OpenBrowser_Callback, new object[] { from, url, echo })); + } + } + else + { + LogFailure("That is not a player."); + } + } + else + { + LogFailure("Format: OpenBrowser "); + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + Execute(e, obj, true); + } + + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + for (int i = 0; i < list.Count; ++i) + Execute(e, list[i], false); + } + } + + public class IncreaseCommand : BaseCommand + { + public IncreaseCommand() + { + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.All; + Commands = new[] { "Increase", "Inc" }; + ObjectTypes = ObjectTypes.Both; + Usage = "Increase { ...}"; + Description = "Increases the value of a specified property by the specified offset."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (obj is BaseMulti) + { + LogFailure("This command does not work on multis."); + } + else if (e.Length >= 2) + { + string result = Properties.IncreaseValue(e.Mobile, obj, e.Arguments); + + if (result == "The property has been increased." || result == "The properties have been increased." || + result == "The property has been decreased." || result == "The properties have been decreased." || + result == "The properties have been changed.") + AddResponse(result); + else + LogFailure(result); + } + else + { + LogFailure("Format: Increase { ...}"); + } + } + } + + public class PrivSoundCommand : BaseCommand + { + public PrivSoundCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllMobiles; + Commands = new[] { "PrivSound" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "PrivSound "; + Description = "Plays a sound to a given target."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile from = e.Mobile; + + if (e.Length == 1) + { + int index = e.GetInt32(0); + Mobile mob = (Mobile)obj; + + CommandLogging.WriteLine(from, "{0} {1} playing sound {2} for {3}", from.AccessLevel, + CommandLogging.Format(from), index, CommandLogging.Format(mob)); + mob.Send(new PlaySound(index, mob.Location)); + } + else + { + from.SendMessage("Format: PrivSound "); + } + } + } + + public class TellCommand : BaseCommand + { + private bool m_InGump; + + public TellCommand(bool inGump) + { + m_InGump = inGump; + + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.AllMobiles; + ObjectTypes = ObjectTypes.Mobiles; + + if (inGump) + { + Commands = new[] { "Message", "Msg" }; + Usage = "Message \"text\""; + Description = "Sends a message to a targeted player."; + } + else + { + Commands = new[] { "Tell" }; + Usage = "Tell \"text\""; + Description = "Sends a system message to a targeted player."; + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile mob = (Mobile)obj; + Mobile from = e.Mobile; + + CommandLogging.WriteLine(from, "{0} {1} {2} {3} \"{4}\"", from.AccessLevel, CommandLogging.Format(from), + m_InGump ? "messaging" : "telling", CommandLogging.Format(mob), e.ArgString); + + if (m_InGump) + mob.SendGump(new MessageSentGump(mob, from.Name, e.ArgString)); + else + mob.SendMessage(e.ArgString); + } + } + + public class AddToPackCommand : BaseCommand + { + public AddToPackCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.All; + Commands = new[] { "AddToPack", "AddToCont" }; + ObjectTypes = ObjectTypes.Both; + ListOptimized = true; + Usage = "AddToPack [params] [set { ...}]"; + Description = + "Adds an item by name to the backpack of a targeted player or npc, or a targeted container. Optional constructor parameters. Optional set property list."; + } + + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + if (e.Arguments.Length == 0) + return; + + List packs = new List(list.Count); + + for (int i = 0; i < list.Count; ++i) + { + object obj = list[i]; + Container cont = null; + + if (obj is Mobile mobile) + cont = mobile.Backpack; + else if (obj is Container container) + cont = container; + + if (cont != null) + packs.Add(cont); + else + LogFailure("That is not a container."); + } + + Add.Invoke(e.Mobile, e.Mobile.Location, e.Mobile.Location, e.Arguments, packs); + } + } + + public class AddCommand : BaseCommand + { + public AddCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Simple | CommandSupport.Self; + Commands = new[] { "Add" }; + ObjectTypes = ObjectTypes.All; + Usage = "Add [ [params] [set { ...}]]"; + Description = + "Adds an item or npc by name to a targeted location. Optional constructor parameters. Optional set property list. If no arguments are specified, this brings up a categorized add menu."; + } + + public override bool ValidateArgs(BaseCommandImplementor impl, CommandEventArgs e) + { + if (e.Length >= 1) + { + Type t = ScriptCompiler.FindTypeByName(e.GetString(0)); + + if (t == null) + { + e.Mobile.SendMessage("No type with that name was found."); + + string match = e.GetString(0).Trim(); + + if (match.Length < 3) + { + e.Mobile.SendMessage("Invalid search string."); + e.Mobile.SendGump(new AddGump(e.Mobile, match, 0, Type.EmptyTypes, false)); + } + else + { + e.Mobile.SendGump(new AddGump(e.Mobile, match, 0, AddGump.Match(match).ToArray(), true)); + } + } + else + { + return true; + } + } + else + { + e.Mobile.SendGump(new CategorizedAddGump(e.Mobile)); + } + + return false; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (!(obj is IPoint3D p)) + return; + + if (p is Item item) + p = item.GetWorldTop(); + else if (p is Mobile m) + p = m.Location; + + Add.Invoke(e.Mobile, new Point3D(p), new Point3D(p), e.Arguments); + } + } + + public class TeleCommand : BaseCommand + { + public TeleCommand() + { + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.Simple; + Commands = new[] { "Teleport", "Tele" }; + ObjectTypes = ObjectTypes.All; + Usage = "Teleport"; + Description = "Teleports your character to a targeted location."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (!(obj is IPoint3D p)) + return; + + Mobile from = e.Mobile; + + SpellHelper.GetSurfaceTop(ref p); + + //CommandLogging.WriteLine( from, "{0} {1} teleporting to {2}", from.AccessLevel, CommandLogging.Format( from ), new Point3D( p ) ); + + Point3D fromLoc = from.Location; + Point3D toLoc = new Point3D(p); + + from.Location = toLoc; + from.ProcessDelta(); + + if (!from.Hidden) + { + Effects.SendLocationParticles(EffectItem.Create(fromLoc, from.Map, EffectItem.DefaultDuration), 0x3728, 10, + 10, 2023); + Effects.SendLocationParticles(EffectItem.Create(toLoc, from.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); + + from.PlaySound(0x1FE); + } + } + } + + public class DismountCommand : BaseCommand + { + public DismountCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllMobiles; + Commands = new[] { "Dismount" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "Dismount"; + Description = "Forcefully dismounts a given target."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile from = e.Mobile; + Mobile mob = (Mobile)obj; + + CommandLogging.WriteLine(from, "{0} {1} dismounting {2}", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(mob)); + + bool takenAction = false; + + for (int i = 0; i < mob.Items.Count; ++i) + { + Item item = mob.Items[i]; + + if (item is IMountItem mountItem) + { + IMount mount = mountItem.Mount; + + if (mount != null) + { + mount.Rider = null; + takenAction = true; + } + + if (mob.Items.IndexOf(item) == -1) + --i; + } + } + + for (int i = 0; i < mob.Items.Count; ++i) + { + Item item = mob.Items[i]; + + if (item.Layer == Layer.Mount) + { + takenAction = true; + item.Delete(); + --i; + } + } + + if (takenAction) + AddResponse("They have been dismounted."); + else + LogFailure("They were not mounted."); + } + } + + public class RestockCommand : BaseCommand + { + public RestockCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllNPCs; + Commands = new[] { "Restock" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "Restock"; + Description = + "Manually restocks a targeted vendor, refreshing the quantity of every item the vendor sells to the maximum. This also invokes the maximum quantity adjustment algorithms."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (obj is BaseVendor vendor) + { + CommandLogging.WriteLine(e.Mobile, "{0} {1} restocking {2}", e.Mobile.AccessLevel, + CommandLogging.Format(e.Mobile), CommandLogging.Format(vendor)); + + vendor.Restock(); + AddResponse("The vendor has been restocked."); + } + else + { + AddResponse("That is not a vendor."); + } + } + } + + public class GetTypeCommand : BaseCommand + { + public GetTypeCommand() + { + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.All; + Commands = new[] { "GetType" }; + ObjectTypes = ObjectTypes.All; + Usage = "GetType"; + Description = "Gets the type name of a targeted object."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (obj == null) + { + AddResponse("The object is null."); + } + else + { + Type type = obj.GetType(); + + if (type.DeclaringType == null) + AddResponse($"The type of that object is {type.Name}."); + else + AddResponse($"The type of that object is {type.FullName}."); + } + } + } + + public class GetCommand : BaseCommand + { + public GetCommand() + { + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.All; + Commands = new[] { "Get" }; + ObjectTypes = ObjectTypes.All; + Usage = "Get "; + Description = "Gets one or more property values by name of a targeted object."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (e.Length >= 1) + for (int i = 0; i < e.Length; ++i) + { + string result = Properties.GetValue(e.Mobile, obj, e.GetString(i)); + + if (result == "Property not found." || result == "Property is write only." || + result.StartsWith("Getting this property")) + LogFailure(result); + else + AddResponse(result); + } + else + LogFailure("Format: Get "); + } + } + + public class AliasedSetCommand : BaseCommand + { + private string m_Name; + private string m_Value; + + public AliasedSetCommand(AccessLevel level, string command, string name, string value, ObjectTypes objects) + { + m_Name = name; + m_Value = value; + + AccessLevel = level; + + if (objects == ObjectTypes.Items) + Supports = CommandSupport.AllItems; + else if (objects == ObjectTypes.Mobiles) + Supports = CommandSupport.AllMobiles; + else + Supports = CommandSupport.All; + + Commands = new[] { command }; + ObjectTypes = objects; + Usage = command; + Description = $"Sets the {name} property to {value}."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + string result = Properties.SetValue(e.Mobile, obj, m_Name, m_Value); + + if (result == "Property has been set.") + AddResponse(result); + else + LogFailure(result); + } + } + + public class SetCommand : BaseCommand + { + public SetCommand() + { + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.All; + Commands = new[] { "Set" }; + ObjectTypes = ObjectTypes.Both; + Usage = "Set [...]"; + Description = "Sets one or more property values by name of a targeted object."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (e.Length >= 2) + for (int i = 0; i + 1 < e.Length; i += 2) + { + string result = Properties.SetValue(e.Mobile, obj, e.GetString(i), e.GetString(i + 1)); + + if (result == "Property has been set.") + AddResponse(result); + else + LogFailure(result); + } + else + LogFailure("Format: Set "); + } + } + + public class DeleteCommand : BaseCommand + { + public DeleteCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllNPCs | CommandSupport.AllItems; + Commands = new[] { "Delete", "Remove" }; + ObjectTypes = ObjectTypes.Both; + Usage = "Delete"; + Description = "Deletes a targeted item or mobile. Does not delete players."; + } + + private void OnConfirmCallback(Mobile from, bool okay, object state) + { + object[] states = (object[])state; + CommandEventArgs e = (CommandEventArgs)states[0]; + ArrayList list = (ArrayList)states[1]; + + bool flushToLog = false; + + if (okay) + { + AddResponse("Delete command confirmed."); + + if (list.Count > 20) + { + CommandLogging.Enabled = false; + NetState.Pause(); + } + + base.ExecuteList(e, list); + + if (list.Count > 20) + { + NetState.Resume(); + flushToLog = true; + CommandLogging.Enabled = true; + } + } + else + { + AddResponse("Delete command aborted."); + } + + Flush(from, flushToLog); + } + + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + if (list.Count > 1) + { + e.Mobile.SendGump(new WarningGump(1060637, 30720, + $"You are about to delete {list.Count} objects. This cannot be undone without a full server revert.

Continue?", + 0xFFC000, 420, 280, OnConfirmCallback, new object[] { e, list })); + AddResponse("Awaiting confirmation..."); + } + else + { + base.ExecuteList(e, list); + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (obj is Item item) + { + CommandLogging.WriteLine(e.Mobile, "{0} {1} deleting {2}", e.Mobile.AccessLevel, + CommandLogging.Format(e.Mobile), CommandLogging.Format(item)); + item.Delete(); + AddResponse("The item has been deleted."); + } + else if (obj is Mobile mobile && !mobile.Player) + { + CommandLogging.WriteLine(e.Mobile, "{0} {1} deleting {2}", e.Mobile.AccessLevel, + CommandLogging.Format(e.Mobile), CommandLogging.Format(mobile)); + mobile.Delete(); + AddResponse("The mobile has been deleted."); + } + else + { + LogFailure("That cannot be deleted."); + } + } + } + + public class KillCommand : BaseCommand + { + private bool m_Value; + + public KillCommand(bool value) + { + m_Value = value; + + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllMobiles; + Commands = value ? new[] { "Kill" } : new[] { "Resurrect", "Res" }; + ObjectTypes = ObjectTypes.Mobiles; + + if (value) + { + Usage = "Kill"; + Description = "Kills a targeted player or npc."; + } + else + { + Usage = "Resurrect"; + Description = "Resurrects a targeted ghost."; + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile mob = (Mobile)obj; + Mobile from = e.Mobile; + + if (m_Value) + { + if (!mob.Alive) + { + LogFailure("They are already dead."); + } + else if (!mob.CanBeDamaged()) + { + LogFailure("They cannot be harmed."); + } + else + { + CommandLogging.WriteLine(from, "{0} {1} killing {2}", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(mob)); + mob.Kill(); + + AddResponse("They have been killed."); + } + } + else + { + if (mob.IsDeadBondedPet) + { + if (mob is BaseCreature bc) + { + CommandLogging.WriteLine(from, "{0} {1} resurrecting {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(mob)); + + bc.PlaySound(0x214); + bc.FixedEffect(0x376A, 10, 16); + + bc.ResurrectPet(); + + AddResponse("It has been resurrected."); + } + } + else if (!mob.Alive) + { + CommandLogging.WriteLine(from, "{0} {1} resurrecting {2}", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(mob)); + + mob.PlaySound(0x214); + mob.FixedEffect(0x376A, 10, 16); + + mob.Resurrect(); + + AddResponse("They have been resurrected."); + } + else + { + LogFailure("They are not dead."); + } + } + } + } + + public class HideCommand : BaseCommand + { + private bool m_Value; + + public HideCommand(bool value) + { + m_Value = value; + + AccessLevel = AccessLevel.Counselor; + Supports = CommandSupport.AllMobiles; + Commands = new[] { value ? "Hide" : "Unhide" }; + ObjectTypes = ObjectTypes.Mobiles; + + if (value) + { + Usage = "Hide"; + Description = "Makes a targeted mobile disappear in a puff of smoke."; + } + else + { + Usage = "Unhide"; + Description = "Makes a targeted mobile appear in a puff of smoke."; + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile m = (Mobile)obj; + + CommandLogging.WriteLine(e.Mobile, "{0} {1} {2} {3}", e.Mobile.AccessLevel, CommandLogging.Format(e.Mobile), + m_Value ? "hiding" : "unhiding", CommandLogging.Format(m)); + + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y, m.Z + 4), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y, m.Z), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y, m.Z - 4), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X, m.Y + 1, m.Z + 4), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X, m.Y + 1, m.Z), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X, m.Y + 1, m.Z - 4), m.Map, 0x3728, 13); + + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y + 1, m.Z + 11), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y + 1, m.Z + 7), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y + 1, m.Z + 3), m.Map, 0x3728, 13); + Effects.SendLocationEffect(new Point3D(m.X + 1, m.Y + 1, m.Z - 1), m.Map, 0x3728, 13); + + m.PlaySound(0x228); + m.Hidden = m_Value; + + if (m_Value) + AddResponse("They have been hidden."); + else + AddResponse("They have been revealed."); + } + } + + public class FirewallCommand : BaseCommand + { + public FirewallCommand() + { + AccessLevel = AccessLevel.Administrator; + Supports = CommandSupport.AllMobiles; + Commands = new[] { "Firewall" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "Firewall"; + Description = + "Adds a targeted player to the firewall (list of blocked IP addresses). This command does not ban or kick."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile from = e.Mobile; + Mobile targ = (Mobile)obj; + NetState state = targ.NetState; + + if (state != null) + { + CommandLogging.WriteLine(from, "{0} {1} firewalling {2}", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(targ)); + + try + { + Firewall.Add(state.Address); + AddResponse("They have been firewalled."); + } + catch (Exception ex) + { + LogFailure(ex.Message); + } + } + else + { + LogFailure("They are not online."); + } + } + } + + public class KickCommand : BaseCommand + { + private bool m_Ban; + + public KickCommand(bool ban) + { + m_Ban = ban; + + AccessLevel = ban ? AccessLevel.Administrator : AccessLevel.GameMaster; + Supports = CommandSupport.AllMobiles; + Commands = new[] { ban ? "Ban" : "Kick" }; + ObjectTypes = ObjectTypes.Mobiles; + + if (ban) + { + Usage = "Ban"; + Description = "Bans the account of a targeted player."; + } + else + { + Usage = "Kick"; + Description = "Disconnects a targeted player."; + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile from = e.Mobile; + Mobile targ = (Mobile)obj; + + if (from.AccessLevel > targ.AccessLevel) + { + NetState fromState = from.NetState, targState = targ.NetState; + + if (fromState != null && targState != null) + { + if (fromState.Account is Account && targState.Account is Account targAccount) + { + CommandLogging.WriteLine(from, "{0} {1} {2} {3}", from.AccessLevel, CommandLogging.Format(from), + m_Ban ? "banning" : "kicking", CommandLogging.Format(targ)); + + targ.Say("I've been {0}!", m_Ban ? "banned" : "kicked"); + + AddResponse($"They have been {(m_Ban ? "banned" : "kicked")}."); + + targState.Dispose(); + + if (m_Ban) + { + targAccount.Banned = true; + targAccount.SetUnspecifiedBan(from); + from.SendGump(new BanDurationGump(targAccount)); + } + } + } + else if (targState == null) + { + LogFailure("They are not online."); + } + } + else + { + LogFailure("You do not have the required access level to do this."); + } + } + } + + public class TraceLockdownCommand : BaseCommand + { + public TraceLockdownCommand() + { + AccessLevel = AccessLevel.Administrator; + Supports = CommandSupport.Simple; + Commands = new[] { "TraceLockdown" }; + ObjectTypes = ObjectTypes.Items; + Usage = "TraceLockdown"; + Description = "Finds the BaseHouse for which a targeted item is locked down or secured."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (!(obj is Item item)) + return; + + if (!item.IsLockedDown && !item.IsSecure) + { + LogFailure("That is not locked down."); + return; + } + + foreach (BaseHouse house in BaseHouse.AllHouses) + if (house.IsSecure(item) || house.IsLockedDown(item)) + { + e.Mobile.SendGump(new PropertiesGump(e.Mobile, house)); + return; + } + + LogFailure("No house was found."); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Commands/DesignInsert.cs b/Scripts/Commands/Generic/Commands/DesignInsert.cs index e0df0e7f2..3111fd727 100644 --- a/Scripts/Commands/Generic/Commands/DesignInsert.cs +++ b/Scripts/Commands/Generic/Commands/DesignInsert.cs @@ -1,4 +1,3 @@ -using System; using System.Collections; using System.Collections.Generic; using Server.Gumps; @@ -8,198 +7,204 @@ using Server.Targeting; namespace Server.Commands.Generic { - public class DesignInsertCommand : BaseCommand - { - public static void Initialize() - { - TargetCommands.Register( new DesignInsertCommand() ); - } + public class DesignInsertCommand : BaseCommand + { + public enum DesignInsertResult + { + Valid, + InvalidItem, + NotInHouse, + OutsideHouseBounds + } - public DesignInsertCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Single | CommandSupport.Area; - Commands = new[] { "DesignInsert" }; - ObjectTypes = ObjectTypes.Items; - Usage = "DesignInsert [allItems=false]"; - Description = "Inserts multiple targeted items into a customizable house's design."; - } + public DesignInsertCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Single | CommandSupport.Area; + Commands = new[] { "DesignInsert" }; + ObjectTypes = ObjectTypes.Items; + Usage = "DesignInsert [allItems=false]"; + Description = "Inserts multiple targeted items into a customizable house's design."; + } - #region Single targeting mode - public override void Execute( CommandEventArgs e, object obj ) - { - Target t = new DesignInsertTarget( new List(), ( e.Length < 1 || !e.GetBoolean( 0 ) ) ); - t.Invoke( e.Mobile, obj ); - } + public static void Initialize() + { + TargetCommands.Register(new DesignInsertCommand()); + } - private class DesignInsertTarget : Target - { - private List m_Foundations; - private bool m_StaticsOnly; + public static DesignInsertResult ProcessInsert(Item item, bool staticsOnly, out HouseFoundation house) + { + house = null; - public DesignInsertTarget( List foundations, bool staticsOnly ) - : base( -1, false, TargetFlags.None ) - { - m_Foundations = foundations; - m_StaticsOnly = staticsOnly; - } + if (item == null || item is BaseMulti || item is HouseSign || staticsOnly && !(item is Static)) + return DesignInsertResult.InvalidItem; - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - if ( m_Foundations.Count != 0 ) - { - from.SendMessage( "Your changes have been committed. Updating..." ); + house = BaseHouse.FindHouseAt(item) as HouseFoundation; - foreach ( HouseFoundation house in m_Foundations ) - house.Delta( ItemDelta.Update ); - } - } + if (house == null) + return DesignInsertResult.NotInHouse; - protected override void OnTarget( Mobile from, object obj ) - { - HouseFoundation house; - DesignInsertResult result = ProcessInsert( obj as Item, m_StaticsOnly, out house ); + int x = item.X - house.X; + int y = item.Y - house.Y; + int z = item.Z - house.Z; - switch ( result ) - { - case DesignInsertResult.Valid: - { - if ( m_Foundations.Count == 0 ) - from.SendMessage( "The item has been inserted into the house design. Press ESC when you are finished." ); - else - from.SendMessage( "The item has been inserted into the house design." ); + if (!TryInsertIntoState(house.CurrentState, item.ItemID, x, y, z)) + return DesignInsertResult.OutsideHouseBounds; - if ( !m_Foundations.Contains( house ) ) - m_Foundations.Add( house ); + TryInsertIntoState(house.DesignState, item.ItemID, x, y, z); + item.Delete(); - break; - } - case DesignInsertResult.InvalidItem: - { - from.SendMessage( "That cannot be inserted. Try again." ); - break; - } - case DesignInsertResult.NotInHouse: - case DesignInsertResult.OutsideHouseBounds: - { - from.SendMessage( "That item is not inside a customizable house. Try again." ); - break; - } - } + return DesignInsertResult.Valid; + } - from.Target = new DesignInsertTarget( m_Foundations, m_StaticsOnly ); - } - } - #endregion + private static bool TryInsertIntoState(DesignState state, int itemID, int x, int y, int z) + { + MultiComponentList mcl = state.Components; - #region Area targeting mode - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - e.Mobile.SendGump( new WarningGump( 1060637, 30720, - $"You are about to insert {list.Count} objects. This cannot be undone without a full server revert.

Continue?", 0xFFC000, 420, 280, OnConfirmCallback, new object[] { e, list, ( e.Length < 1 || !e.GetBoolean( 0 ) ) } ) ); - AddResponse( "Awaiting confirmation..." ); - } + if (x < mcl.Min.X || y < mcl.Min.Y || x > mcl.Max.X || y > mcl.Max.Y) + return false; - private void OnConfirmCallback( Mobile from, bool okay, object state ) - { - object[] states = (object[])state; - CommandEventArgs e = (CommandEventArgs)states[0]; - ArrayList list = (ArrayList)states[1]; - bool staticsOnly = (bool)states[2]; + mcl.Add(itemID, x, y, z); + state.OnRevised(); - bool flushToLog = false; + return true; + } - if ( okay ) - { - List foundations = new List(); - flushToLog = ( list.Count > 20 ); + #region Single targeting mode - for ( int i = 0; i < list.Count; ++i ) - { - HouseFoundation house; - DesignInsertResult result = ProcessInsert( list[i] as Item, staticsOnly, out house ); + public override void Execute(CommandEventArgs e, object obj) + { + Target t = new DesignInsertTarget(new List(), e.Length < 1 || !e.GetBoolean(0)); + t.Invoke(e.Mobile, obj); + } - switch ( result ) - { - case DesignInsertResult.Valid: - { - AddResponse( "The item has been inserted into the house design." ); + private class DesignInsertTarget : Target + { + private List m_Foundations; + private bool m_StaticsOnly; - if ( !foundations.Contains( house ) ) - foundations.Add( house ); + public DesignInsertTarget(List foundations, bool staticsOnly) + : base(-1, false, TargetFlags.None) + { + m_Foundations = foundations; + m_StaticsOnly = staticsOnly; + } - break; - } - case DesignInsertResult.InvalidItem: - { - LogFailure( "That cannot be inserted." ); - break; - } - case DesignInsertResult.NotInHouse: - case DesignInsertResult.OutsideHouseBounds: - { - LogFailure( "That item is not inside a customizable house." ); - break; - } - } - } + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + if (m_Foundations.Count != 0) + { + from.SendMessage("Your changes have been committed. Updating..."); - foreach ( HouseFoundation house in foundations ) - house.Delta( ItemDelta.Update ); - } - else - { - AddResponse( "Command aborted." ); - } + foreach (HouseFoundation house in m_Foundations) + house.Delta(ItemDelta.Update); + } + } - Flush( from, flushToLog ); - } - #endregion + protected override void OnTarget(Mobile from, object obj) + { + HouseFoundation house; + DesignInsertResult result = ProcessInsert(obj as Item, m_StaticsOnly, out house); - public enum DesignInsertResult - { - Valid, - InvalidItem, - NotInHouse, - OutsideHouseBounds - } + switch (result) + { + case DesignInsertResult.Valid: + { + if (m_Foundations.Count == 0) + from.SendMessage( + "The item has been inserted into the house design. Press ESC when you are finished."); + else + from.SendMessage("The item has been inserted into the house design."); - public static DesignInsertResult ProcessInsert( Item item, bool staticsOnly, out HouseFoundation house ) - { - house = null; + if (!m_Foundations.Contains(house)) + m_Foundations.Add(house); - if ( item == null || item is BaseMulti || item is HouseSign || ( staticsOnly && !( item is Static ) ) ) - return DesignInsertResult.InvalidItem; + break; + } + case DesignInsertResult.InvalidItem: + { + from.SendMessage("That cannot be inserted. Try again."); + break; + } + case DesignInsertResult.NotInHouse: + case DesignInsertResult.OutsideHouseBounds: + { + from.SendMessage("That item is not inside a customizable house. Try again."); + break; + } + } - house = BaseHouse.FindHouseAt( item ) as HouseFoundation; + from.Target = new DesignInsertTarget(m_Foundations, m_StaticsOnly); + } + } - if ( house == null ) - return DesignInsertResult.NotInHouse; + #endregion - int x = item.X - house.X; - int y = item.Y - house.Y; - int z = item.Z - house.Z; + #region Area targeting mode - if ( !TryInsertIntoState( house.CurrentState, item.ItemID, x, y, z ) ) - return DesignInsertResult.OutsideHouseBounds; + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + e.Mobile.SendGump(new WarningGump(1060637, 30720, + $"You are about to insert {list.Count} objects. This cannot be undone without a full server revert.

Continue?", + 0xFFC000, 420, 280, OnConfirmCallback, new object[] { e, list, e.Length < 1 || !e.GetBoolean(0) })); + AddResponse("Awaiting confirmation..."); + } - TryInsertIntoState( house.DesignState, item.ItemID, x, y, z ); - item.Delete(); + private void OnConfirmCallback(Mobile from, bool okay, object state) + { + object[] states = (object[])state; + CommandEventArgs e = (CommandEventArgs)states[0]; + ArrayList list = (ArrayList)states[1]; + bool staticsOnly = (bool)states[2]; - return DesignInsertResult.Valid; - } + bool flushToLog = false; - private static bool TryInsertIntoState( DesignState state, int itemID, int x, int y, int z ) - { - MultiComponentList mcl = state.Components; + if (okay) + { + List foundations = new List(); + flushToLog = list.Count > 20; - if ( x < mcl.Min.X || y < mcl.Min.Y || x > mcl.Max.X || y > mcl.Max.Y ) - return false; + for (int i = 0; i < list.Count; ++i) + { + HouseFoundation house; + DesignInsertResult result = ProcessInsert(list[i] as Item, staticsOnly, out house); - mcl.Add( itemID, x, y, z ); - state.OnRevised(); + switch (result) + { + case DesignInsertResult.Valid: + { + AddResponse("The item has been inserted into the house design."); - return true; - } - } -} + if (!foundations.Contains(house)) + foundations.Add(house); + + break; + } + case DesignInsertResult.InvalidItem: + { + LogFailure("That cannot be inserted."); + break; + } + case DesignInsertResult.NotInHouse: + case DesignInsertResult.OutsideHouseBounds: + { + LogFailure("That item is not inside a customizable house."); + break; + } + } + } + + foreach (HouseFoundation house in foundations) + house.Delta(ItemDelta.Update); + } + else + { + AddResponse("Command aborted."); + } + + Flush(from, flushToLog); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Commands/Interface.cs b/Scripts/Commands/Generic/Commands/Interface.cs index acf0c57b8..0969d3301 100644 --- a/Scripts/Commands/Generic/Commands/Interface.cs +++ b/Scripts/Commands/Generic/Commands/Interface.cs @@ -1,4 +1,3 @@ -using System; using System.Collections; using System.Collections.Generic; using System.Reflection; @@ -8,560 +7,564 @@ using Server.Targets; namespace Server.Commands.Generic { - public class InterfaceCommand : BaseCommand - { - public InterfaceCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Complex | CommandSupport.Simple; - Commands = new[]{ "Interface" }; - ObjectTypes = ObjectTypes.Both; - Usage = "Interface [view ]"; - Description = "Opens an interface to interact with matched objects. Generally used with condition arguments."; - ListOptimized = true; - } - - public override void ExecuteList( CommandEventArgs e, ArrayList list ) - { - if ( list.Count > 0 ) - { - List columns = new List(); - - columns.Add( "Object" ); - - if ( e.Length > 0 ) - { - int offset = 0; - - if ( Insensitive.Equals( e.GetString( 0 ), "view" ) ) - ++offset; - - while ( offset < e.Length ) - columns.Add( e.GetString( offset++ ) ); - } - - e.Mobile.SendGump( new InterfaceGump( e.Mobile, columns.ToArray(), list, 0, null ) ); - } - else - { - AddResponse( "No matching objects found." ); - } - } - } - - public class InterfaceGump : BaseGridGump - { - private Mobile m_From; - - private string[] m_Columns; - - private ArrayList m_List; - private int m_Page; - - private object m_Select; - - private const int EntriesPerPage = 15; - - public InterfaceGump( Mobile from, string[] columns, ArrayList list, int page, object select ) : base( 30, 30 ) - { - m_From = from; - - m_Columns = columns; - - m_List = list; - m_Page = page; - - m_Select = select; - - Render(); - } - - public void Render() - { - AddNewPage(); - - if ( m_Page > 0 ) - AddEntryButton( 20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight ); - else - AddEntryHeader( 20 ); - - AddEntryHtml( 40 + ( m_Columns.Length * 130 ) - 20 + ( ( m_Columns.Length - 2 ) * OffsetSize ), Center( - $"Page {m_Page + 1} of {(m_List.Count + EntriesPerPage - 1) / EntriesPerPage}") ); - - if ( (m_Page + 1) * EntriesPerPage < m_List.Count ) - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight ); - else - AddEntryHeader( 20 ); - - if ( m_Columns.Length > 1 ) - { - AddNewLine(); - - for ( int i = 0; i < m_Columns.Length; ++i ) - { - if ( i > 0 && m_List.Count > 0 ) - { - object obj = m_List[0]; - - if ( obj != null ) - { - string failReason = null; - PropertyInfo[] chain = Properties.GetPropertyInfoChain( m_From, obj.GetType(), m_Columns[i], PropertyAccess.Read, ref failReason ); - - if ( chain != null && chain.Length > 0 ) - { - m_Columns[i] = ""; - - for ( int j = 0; j < chain.Length; ++j ) - { - if ( j > 0 ) - m_Columns[i] += '.'; - - m_Columns[i] += chain[j].Name; - } - } - } - } - - AddEntryHtml( 130 + ( i == 0 ? 40 : 0 ), m_Columns[i] ); - } - - AddEntryHeader( 20 ); - } - - for ( int i = m_Page * EntriesPerPage, line = 0; line < EntriesPerPage && i < m_List.Count; ++i, ++line ) - { - AddNewLine(); - - object obj = m_List[i]; - bool isDeleted = false; - - if ( obj is Item item ) - { - if ( !(isDeleted = item.Deleted) ) - AddEntryHtml( 40 + 130, item.GetType().Name ); - } - else if ( obj is Mobile mob ) - { - if ( !(isDeleted = mob.Deleted) ) - AddEntryHtml( 40 + 130, mob.Name ); - } - - if ( isDeleted ) - { - AddEntryHtml( 40 + 130, "(deleted)" ); - - for ( int j = 1; j < m_Columns.Length; ++j ) - AddEntryHtml( 130, "---" ); - - AddEntryHeader( 20 ); - } - else - { - for ( int j = 1; j < m_Columns.Length; ++j ) - { - object src = obj; - - string value; - string failReason = ""; - - PropertyInfo[] chain = Properties.GetPropertyInfoChain( m_From, src.GetType(), m_Columns[j], PropertyAccess.Read, ref failReason ); - - if ( chain == null || chain.Length == 0 ) - { - value = "---"; - } - else - { - PropertyInfo p = Properties.GetPropertyInfo( ref src, chain, ref failReason ); - - if ( p == null ) - value = "---"; - else - value = PropertiesGump.ValueToString( src, p ); - } - - AddEntryHtml( 130, value ); - } - - bool isSelected = ( m_Select != null && obj == m_Select ); - - AddEntryButton( 20, ( isSelected ? 9762 : ArrowRightID1 ), ( isSelected ? 9763 : ArrowRightID2 ), 3 + i, ArrowRightWidth, ArrowRightHeight ); - } - } - - FinishPage(); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 1: - { - if ( m_Page > 0 ) - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page - 1, m_Select ) ); - - break; - } - case 2: - { - if ( (m_Page + 1) * EntriesPerPage < m_List.Count ) - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page + 1, m_Select ) ); - - break; - } - default: - { - int v = info.ButtonID - 3; - - if ( v >= 0 && v < m_List.Count ) - { - object obj = m_List[v]; - - if ( !BaseCommand.IsAccessible( m_From, obj ) ) - { - m_From.SendMessage( "That is not accessible." ); - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Select ) ); - break; - } - - if ( obj is Item item && !item.Deleted ) - m_From.SendGump( new InterfaceItemGump( m_From, m_Columns, m_List, m_Page, item ) ); - else if ( obj is Mobile mobile && !mobile.Deleted ) - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, mobile ) ); - else - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Select ) ); - } - - break; - } - } - } - } - - public class InterfaceItemGump : BaseGridGump - { - private Mobile m_From; - - private string[] m_Columns; - - private ArrayList m_List; - private int m_Page; - - private Item m_Item; - - public InterfaceItemGump( Mobile from, string[] columns, ArrayList list, int page, Item item ) : base( 30, 30 ) - { - m_From = from; - - m_Columns = columns; - - m_List = list; - m_Page = page; - - m_Item = item; - - Render(); - } - - public void Render() - { - AddNewPage(); - - AddEntryButton( 20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight ); - AddEntryHtml( 160, m_Item.GetType().Name ); - AddEntryHeader( 20 ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Properties" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Delete" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 3, ArrowRightWidth, ArrowRightHeight ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Go there" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 4, ArrowRightWidth, ArrowRightHeight ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Move to target" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 5, ArrowRightWidth, ArrowRightHeight ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Bring to pack" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 6, ArrowRightWidth, ArrowRightHeight ); - - FinishPage(); - } - - private void InvokeCommand( string ip ) - { - CommandSystem.Handle( m_From, $"{CommandSystem.Prefix}{ip}"); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Item.Deleted ) - { - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - return; - } - - if ( !BaseCommand.IsAccessible( m_From, m_Item ) ) - { - m_From.SendMessage( "That is no longer accessible." ); - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - return; - } - - switch ( info.ButtonID ) - { - case 0: - case 1: - { - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - break; - } - case 2: // Properties - { - m_From.SendGump( new InterfaceItemGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - m_From.SendGump( new PropertiesGump( m_From, m_Item ) ); - break; - } - case 3: // Delete - { - CommandLogging.WriteLine( m_From, "{0} {1} deleting {2}", m_From.AccessLevel, CommandLogging.Format( m_From ), CommandLogging.Format( m_Item ) ); - m_Item.Delete(); - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - break; - } - case 4: // Go there - { - m_From.SendGump( new InterfaceItemGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - InvokeCommand($"Go {m_Item.Serial.Value}"); - break; - } - case 5: // Move to target - { - m_From.SendGump( new InterfaceItemGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - m_From.Target = new MoveTarget( m_Item ); - break; - } - case 6: // Bring to pack - { - Mobile owner = m_Item.RootParent as Mobile; - - if ( owner?.Map != null && owner.Map != Map.Internal && !BaseCommand.IsAccessible( m_From, owner ) /* !m_From.CanSee( owner )*/ ) - { - m_From.SendMessage( "You can not get what you can not see." ); - } - else if ( owner != null && (owner.Map == null || owner.Map == Map.Internal) && owner.Hidden && owner.AccessLevel >= m_From.AccessLevel ) - { - m_From.SendMessage( "You can not get what you can not see." ); - } - else - { - m_From.SendGump( new InterfaceItemGump( m_From, m_Columns, m_List, m_Page, m_Item ) ); - m_From.AddToBackpack( m_Item ); - } - - break; - } - } - } - } - - public class InterfaceMobileGump : BaseGridGump - { - private Mobile m_From; - - private string[] m_Columns; - - private ArrayList m_List; - private int m_Page; - - private Mobile m_Mobile; - - public InterfaceMobileGump( Mobile from, string[] columns, ArrayList list, int page, Mobile mob ) - : base( 30, 30 ) - { - m_From = from; - - m_Columns = columns; - - m_List = list; - m_Page = page; - - m_Mobile = mob; - - Render(); - } - - public void Render() - { - AddNewPage(); - - AddEntryButton( 20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight ); - AddEntryHtml( 160, m_Mobile.Name ); - AddEntryHeader( 20 ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Properties" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight ); - - if ( !m_Mobile.Player ) - { - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Delete" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 3, ArrowRightWidth, ArrowRightHeight ); - } - - if ( m_Mobile != m_From ) - { - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Go to there" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 4, ArrowRightWidth, ArrowRightHeight ); - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Bring them here" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 5, ArrowRightWidth, ArrowRightHeight ); - } - - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Move to target" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 6, ArrowRightWidth, ArrowRightHeight ); - - if ( m_From == m_Mobile || m_From.AccessLevel > m_Mobile.AccessLevel ) - { - AddNewLine(); - if ( m_Mobile.Alive ) - { - AddEntryHtml( 20 + OffsetSize + 160, "Kill" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 7, ArrowRightWidth, ArrowRightHeight ); - } - else - { - AddEntryHtml( 20 + OffsetSize + 160, "Resurrect" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 8, ArrowRightWidth, ArrowRightHeight ); - } - } - - if ( m_Mobile.NetState != null ) - { - AddNewLine(); - AddEntryHtml( 20 + OffsetSize + 160, "Client" ); - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 9, ArrowRightWidth, ArrowRightHeight ); - } - - FinishPage(); - } - - private void InvokeCommand( string ip ) - { - CommandSystem.Handle( m_From, $"{CommandSystem.Prefix}{ip}"); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Mobile.Deleted ) - { - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - return; - } - - if ( !BaseCommand.IsAccessible( m_From, m_Mobile ) ) - { - m_From.SendMessage( "That is no longer accessible." ); - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - return; - } - - switch ( info.ButtonID ) - { - case 0: - case 1: - { - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - break; - } - case 2: // Properties - { - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - m_From.SendGump( new PropertiesGump( m_From, m_Mobile ) ); - break; - } - case 3: // Delete - { - if ( !m_Mobile.Player ) - { - CommandLogging.WriteLine( m_From, "{0} {1} deleting {2}", m_From.AccessLevel, CommandLogging.Format( m_From ), CommandLogging.Format( m_Mobile ) ); - m_Mobile.Delete(); - m_From.SendGump( new InterfaceGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - } - - break; - } - case 4: // Go there - { - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - InvokeCommand($"Go {m_Mobile.Serial.Value}"); - break; - } - case 5: // Bring them here - { - if ( m_From.Map == null || m_From.Map == Map.Internal ) - { - m_From.SendMessage( "You cannot bring that person here." ); - } - else - { - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - m_Mobile.MoveToWorld( m_From.Location, m_From.Map ); - } - - break; - } - case 6: // Move to target - { - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - m_From.Target = new MoveTarget( m_Mobile ); - break; - } - case 7: // Kill - { - if ( m_From == m_Mobile || m_From.AccessLevel > m_Mobile.AccessLevel ) - m_Mobile.Kill(); - - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - - break; - } - case 8: // Res - { - if ( m_From == m_Mobile || m_From.AccessLevel > m_Mobile.AccessLevel ) - { - m_Mobile.PlaySound( 0x214 ); - m_Mobile.FixedEffect( 0x376A, 10, 16 ); - - m_Mobile.Resurrect(); - } - - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - - break; - } - case 9: // Client - { - m_From.SendGump( new InterfaceMobileGump( m_From, m_Columns, m_List, m_Page, m_Mobile ) ); - - if ( m_Mobile.NetState != null ) - m_From.SendGump( new ClientGump( m_From, m_Mobile.NetState ) ); - - break; - } - } - } - } -} + public class InterfaceCommand : BaseCommand + { + public InterfaceCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Complex | CommandSupport.Simple; + Commands = new[] { "Interface" }; + ObjectTypes = ObjectTypes.Both; + Usage = "Interface [view ]"; + Description = "Opens an interface to interact with matched objects. Generally used with condition arguments."; + ListOptimized = true; + } + + public override void ExecuteList(CommandEventArgs e, ArrayList list) + { + if (list.Count > 0) + { + List columns = new List(); + + columns.Add("Object"); + + if (e.Length > 0) + { + int offset = 0; + + if (Insensitive.Equals(e.GetString(0), "view")) + ++offset; + + while (offset < e.Length) + columns.Add(e.GetString(offset++)); + } + + e.Mobile.SendGump(new InterfaceGump(e.Mobile, columns.ToArray(), list, 0, null)); + } + else + { + AddResponse("No matching objects found."); + } + } + } + + public class InterfaceGump : BaseGridGump + { + private const int EntriesPerPage = 15; + + private string[] m_Columns; + private Mobile m_From; + + private ArrayList m_List; + private int m_Page; + + private object m_Select; + + public InterfaceGump(Mobile from, string[] columns, ArrayList list, int page, object select) : base(30, 30) + { + m_From = from; + + m_Columns = columns; + + m_List = list; + m_Page = page; + + m_Select = select; + + Render(); + } + + public void Render() + { + AddNewPage(); + + if (m_Page > 0) + AddEntryButton(20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight); + else + AddEntryHeader(20); + + AddEntryHtml(40 + m_Columns.Length * 130 - 20 + (m_Columns.Length - 2) * OffsetSize, Center( + $"Page {m_Page + 1} of {(m_List.Count + EntriesPerPage - 1) / EntriesPerPage}")); + + if ((m_Page + 1) * EntriesPerPage < m_List.Count) + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight); + else + AddEntryHeader(20); + + if (m_Columns.Length > 1) + { + AddNewLine(); + + for (int i = 0; i < m_Columns.Length; ++i) + { + if (i > 0 && m_List.Count > 0) + { + object obj = m_List[0]; + + if (obj != null) + { + string failReason = null; + PropertyInfo[] chain = Properties.GetPropertyInfoChain(m_From, obj.GetType(), m_Columns[i], + PropertyAccess.Read, ref failReason); + + if (chain != null && chain.Length > 0) + { + m_Columns[i] = ""; + + for (int j = 0; j < chain.Length; ++j) + { + if (j > 0) + m_Columns[i] += '.'; + + m_Columns[i] += chain[j].Name; + } + } + } + } + + AddEntryHtml(130 + (i == 0 ? 40 : 0), m_Columns[i]); + } + + AddEntryHeader(20); + } + + for (int i = m_Page * EntriesPerPage, line = 0; line < EntriesPerPage && i < m_List.Count; ++i, ++line) + { + AddNewLine(); + + object obj = m_List[i]; + bool isDeleted = false; + + if (obj is Item item) + { + if (!(isDeleted = item.Deleted)) + AddEntryHtml(40 + 130, item.GetType().Name); + } + else if (obj is Mobile mob) + { + if (!(isDeleted = mob.Deleted)) + AddEntryHtml(40 + 130, mob.Name); + } + + if (isDeleted) + { + AddEntryHtml(40 + 130, "(deleted)"); + + for (int j = 1; j < m_Columns.Length; ++j) + AddEntryHtml(130, "---"); + + AddEntryHeader(20); + } + else + { + for (int j = 1; j < m_Columns.Length; ++j) + { + object src = obj; + + string value; + string failReason = ""; + + PropertyInfo[] chain = Properties.GetPropertyInfoChain(m_From, src.GetType(), m_Columns[j], + PropertyAccess.Read, ref failReason); + + if (chain == null || chain.Length == 0) + { + value = "---"; + } + else + { + PropertyInfo p = Properties.GetPropertyInfo(ref src, chain, ref failReason); + + if (p == null) + value = "---"; + else + value = PropertiesGump.ValueToString(src, p); + } + + AddEntryHtml(130, value); + } + + bool isSelected = m_Select != null && obj == m_Select; + + AddEntryButton(20, isSelected ? 9762 : ArrowRightID1, isSelected ? 9763 : ArrowRightID2, 3 + i, + ArrowRightWidth, ArrowRightHeight); + } + } + + FinishPage(); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: + { + if (m_Page > 0) + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page - 1, m_Select)); + + break; + } + case 2: + { + if ((m_Page + 1) * EntriesPerPage < m_List.Count) + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page + 1, m_Select)); + + break; + } + default: + { + int v = info.ButtonID - 3; + + if (v >= 0 && v < m_List.Count) + { + object obj = m_List[v]; + + if (!BaseCommand.IsAccessible(m_From, obj)) + { + m_From.SendMessage("That is not accessible."); + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Select)); + break; + } + + if (obj is Item item && !item.Deleted) + m_From.SendGump(new InterfaceItemGump(m_From, m_Columns, m_List, m_Page, item)); + else if (obj is Mobile mobile && !mobile.Deleted) + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, mobile)); + else + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Select)); + } + + break; + } + } + } + } + + public class InterfaceItemGump : BaseGridGump + { + private string[] m_Columns; + private Mobile m_From; + + private Item m_Item; + + private ArrayList m_List; + private int m_Page; + + public InterfaceItemGump(Mobile from, string[] columns, ArrayList list, int page, Item item) : base(30, 30) + { + m_From = from; + + m_Columns = columns; + + m_List = list; + m_Page = page; + + m_Item = item; + + Render(); + } + + public void Render() + { + AddNewPage(); + + AddEntryButton(20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight); + AddEntryHtml(160, m_Item.GetType().Name); + AddEntryHeader(20); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Properties"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Delete"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 3, ArrowRightWidth, ArrowRightHeight); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Go there"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 4, ArrowRightWidth, ArrowRightHeight); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Move to target"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 5, ArrowRightWidth, ArrowRightHeight); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Bring to pack"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 6, ArrowRightWidth, ArrowRightHeight); + + FinishPage(); + } + + private void InvokeCommand(string ip) + { + CommandSystem.Handle(m_From, $"{CommandSystem.Prefix}{ip}"); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Item.Deleted) + { + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Item)); + return; + } + + if (!BaseCommand.IsAccessible(m_From, m_Item)) + { + m_From.SendMessage("That is no longer accessible."); + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Item)); + return; + } + + switch (info.ButtonID) + { + case 0: + case 1: + { + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Item)); + break; + } + case 2: // Properties + { + m_From.SendGump(new InterfaceItemGump(m_From, m_Columns, m_List, m_Page, m_Item)); + m_From.SendGump(new PropertiesGump(m_From, m_Item)); + break; + } + case 3: // Delete + { + CommandLogging.WriteLine(m_From, "{0} {1} deleting {2}", m_From.AccessLevel, + CommandLogging.Format(m_From), CommandLogging.Format(m_Item)); + m_Item.Delete(); + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Item)); + break; + } + case 4: // Go there + { + m_From.SendGump(new InterfaceItemGump(m_From, m_Columns, m_List, m_Page, m_Item)); + InvokeCommand($"Go {m_Item.Serial.Value}"); + break; + } + case 5: // Move to target + { + m_From.SendGump(new InterfaceItemGump(m_From, m_Columns, m_List, m_Page, m_Item)); + m_From.Target = new MoveTarget(m_Item); + break; + } + case 6: // Bring to pack + { + Mobile owner = m_Item.RootParent as Mobile; + + if (owner?.Map != null && owner.Map != Map.Internal && + !BaseCommand.IsAccessible(m_From, owner) /* !m_From.CanSee( owner )*/) + { + m_From.SendMessage("You can not get what you can not see."); + } + else if (owner != null && (owner.Map == null || owner.Map == Map.Internal) && owner.Hidden && + owner.AccessLevel >= m_From.AccessLevel) + { + m_From.SendMessage("You can not get what you can not see."); + } + else + { + m_From.SendGump(new InterfaceItemGump(m_From, m_Columns, m_List, m_Page, m_Item)); + m_From.AddToBackpack(m_Item); + } + + break; + } + } + } + } + + public class InterfaceMobileGump : BaseGridGump + { + private string[] m_Columns; + private Mobile m_From; + + private ArrayList m_List; + + private Mobile m_Mobile; + private int m_Page; + + public InterfaceMobileGump(Mobile from, string[] columns, ArrayList list, int page, Mobile mob) + : base(30, 30) + { + m_From = from; + + m_Columns = columns; + + m_List = list; + m_Page = page; + + m_Mobile = mob; + + Render(); + } + + public void Render() + { + AddNewPage(); + + AddEntryButton(20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight); + AddEntryHtml(160, m_Mobile.Name); + AddEntryHeader(20); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Properties"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight); + + if (!m_Mobile.Player) + { + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Delete"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 3, ArrowRightWidth, ArrowRightHeight); + } + + if (m_Mobile != m_From) + { + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Go to there"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 4, ArrowRightWidth, ArrowRightHeight); + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Bring them here"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 5, ArrowRightWidth, ArrowRightHeight); + } + + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Move to target"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 6, ArrowRightWidth, ArrowRightHeight); + + if (m_From == m_Mobile || m_From.AccessLevel > m_Mobile.AccessLevel) + { + AddNewLine(); + if (m_Mobile.Alive) + { + AddEntryHtml(20 + OffsetSize + 160, "Kill"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 7, ArrowRightWidth, ArrowRightHeight); + } + else + { + AddEntryHtml(20 + OffsetSize + 160, "Resurrect"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 8, ArrowRightWidth, ArrowRightHeight); + } + } + + if (m_Mobile.NetState != null) + { + AddNewLine(); + AddEntryHtml(20 + OffsetSize + 160, "Client"); + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 9, ArrowRightWidth, ArrowRightHeight); + } + + FinishPage(); + } + + private void InvokeCommand(string ip) + { + CommandSystem.Handle(m_From, $"{CommandSystem.Prefix}{ip}"); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Mobile.Deleted) + { + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + return; + } + + if (!BaseCommand.IsAccessible(m_From, m_Mobile)) + { + m_From.SendMessage("That is no longer accessible."); + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + return; + } + + switch (info.ButtonID) + { + case 0: + case 1: + { + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + break; + } + case 2: // Properties + { + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + m_From.SendGump(new PropertiesGump(m_From, m_Mobile)); + break; + } + case 3: // Delete + { + if (!m_Mobile.Player) + { + CommandLogging.WriteLine(m_From, "{0} {1} deleting {2}", m_From.AccessLevel, + CommandLogging.Format(m_From), CommandLogging.Format(m_Mobile)); + m_Mobile.Delete(); + m_From.SendGump(new InterfaceGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + } + + break; + } + case 4: // Go there + { + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + InvokeCommand($"Go {m_Mobile.Serial.Value}"); + break; + } + case 5: // Bring them here + { + if (m_From.Map == null || m_From.Map == Map.Internal) + { + m_From.SendMessage("You cannot bring that person here."); + } + else + { + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + m_Mobile.MoveToWorld(m_From.Location, m_From.Map); + } + + break; + } + case 6: // Move to target + { + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + m_From.Target = new MoveTarget(m_Mobile); + break; + } + case 7: // Kill + { + if (m_From == m_Mobile || m_From.AccessLevel > m_Mobile.AccessLevel) + m_Mobile.Kill(); + + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + + break; + } + case 8: // Res + { + if (m_From == m_Mobile || m_From.AccessLevel > m_Mobile.AccessLevel) + { + m_Mobile.PlaySound(0x214); + m_Mobile.FixedEffect(0x376A, 10, 16); + + m_Mobile.Resurrect(); + } + + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + + break; + } + case 9: // Client + { + m_From.SendGump(new InterfaceMobileGump(m_From, m_Columns, m_List, m_Page, m_Mobile)); + + if (m_Mobile.NetState != null) + m_From.SendGump(new ClientGump(m_From, m_Mobile.NetState)); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/BaseExtension.cs b/Scripts/Commands/Generic/Extensions/BaseExtension.cs index 977e28beb..e481b2560 100644 --- a/Scripts/Commands/Generic/Extensions/BaseExtension.cs +++ b/Scripts/Commands/Generic/Extensions/BaseExtension.cs @@ -4,139 +4,131 @@ using System.Collections.Generic; namespace Server.Commands.Generic { - public delegate BaseExtension ExtensionConstructor(); + public delegate BaseExtension ExtensionConstructor(); - public sealed class ExtensionInfo - { - public static Dictionary Table { get; } = new Dictionary( StringComparer.InvariantCultureIgnoreCase ); + public sealed class ExtensionInfo + { + public ExtensionInfo(int order, string name, int size, ExtensionConstructor constructor) + { + Name = name; + Size = size; - public static void Register( ExtensionInfo ext ) - { - Table[ext.Name] = ext; - } + Order = order; - public int Order { get; } + Constructor = constructor; + } - public string Name { get; } + public static Dictionary Table{ get; } = + new Dictionary(StringComparer.InvariantCultureIgnoreCase); - public int Size { get; } + public int Order{ get; } - public bool IsFixedSize => ( Size >= 0 ); + public string Name{ get; } - public ExtensionConstructor Constructor { get; } + public int Size{ get; } - public ExtensionInfo( int order, string name, int size, ExtensionConstructor constructor ) - { - Name = name; - Size = size; + public bool IsFixedSize => Size >= 0; - Order = order; + public ExtensionConstructor Constructor{ get; } - Constructor = constructor; - } - } + public static void Register(ExtensionInfo ext) + { + Table[ext.Name] = ext; + } + } - public sealed class Extensions : List - { - public Extensions() - { - } + public sealed class Extensions : List + { + public bool IsValid(object obj) + { + for (int i = 0; i < Count; ++i) + if (!this[i].IsValid(obj)) + return false; - public bool IsValid( object obj ) - { - for ( int i = 0; i < Count; ++i ) - { - if ( !this[i].IsValid( obj ) ) - return false; - } + return true; + } - return true; - } + public void Filter(ArrayList list) + { + for (int i = 0; i < Count; ++i) + this[i].Filter(list); + } - public void Filter( ArrayList list ) - { - for ( int i = 0; i < Count; ++i ) - this[i].Filter( list ); - } + public static Extensions Parse(Mobile from, ref string[] args) + { + Extensions parsed = new Extensions(); - public static Extensions Parse( Mobile from, ref string[] args ) - { - Extensions parsed = new Extensions(); + int size = args.Length; - int size = args.Length; + Type baseType = null; - Type baseType = null; + for (int i = args.Length - 1; i >= 0; --i) + { + if (!ExtensionInfo.Table.TryGetValue(args[i], out ExtensionInfo extInfo)) + continue; - for ( int i = args.Length - 1; i >= 0; --i ) - { - if ( !ExtensionInfo.Table.TryGetValue( args[i], out ExtensionInfo extInfo ) ) - continue; + if (extInfo.IsFixedSize && i != size - extInfo.Size - 1) + throw new Exception("Invalid extended argument count."); - if ( extInfo.IsFixedSize && i != ( size - extInfo.Size - 1 ) ) - throw new Exception( "Invalid extended argument count." ); + BaseExtension ext = extInfo.Constructor(); - BaseExtension ext = extInfo.Constructor(); + ext.Parse(from, args, i + 1, size - i - 1); - ext.Parse( from, args, i + 1, size - i - 1 ); + if (ext is WhereExtension extension) + baseType = extension.Conditional.Type; - if ( ext is WhereExtension extension ) - baseType = extension.Conditional.Type; + parsed.Add(ext); - parsed.Add( ext ); + size = i; + } - size = i; - } + parsed.Sort(delegate(BaseExtension a, BaseExtension b) { return a.Order - b.Order; }); - parsed.Sort( delegate( BaseExtension a, BaseExtension b ) - { - return ( a.Order - b.Order ); - } ); + AssemblyEmitter emitter = null; - AssemblyEmitter emitter = null; + foreach (BaseExtension update in parsed) + update.Optimize(from, baseType, ref emitter); - foreach ( BaseExtension update in parsed ) - update.Optimize( from, baseType, ref emitter ); + if (size != args.Length) + { + string[] old = args; + args = new string[size]; - if ( size != args.Length ) - { - string[] old = args; - args = new string[size]; + for (int i = 0; i < args.Length; ++i) + args[i] = old[i]; + } - for ( int i = 0; i < args.Length; ++i ) - args[i] = old[i]; - } + return parsed; + } + } - return parsed; - } - } + public abstract class BaseExtension + { + public abstract ExtensionInfo Info{ get; } - public abstract class BaseExtension - { - public abstract ExtensionInfo Info { get; } + public string Name => Info.Name; - public string Name => Info.Name; + public int Size => Info.Size; - public int Size => Info.Size; + public bool IsFixedSize => Info.IsFixedSize; - public bool IsFixedSize => Info.IsFixedSize; + public int Order => Info.Order; - public int Order => Info.Order; + public virtual void Optimize(Mobile from, Type baseType, ref AssemblyEmitter assembly) + { + } - public virtual void Optimize( Mobile from, Type baseType, ref AssemblyEmitter assembly ) - { - } + public virtual void Parse(Mobile from, string[] arguments, int offset, int size) + { + } - public virtual void Parse( Mobile from, string[] arguments, int offset, int size ) - { - } + public virtual bool IsValid(object obj) + { + return true; + } - public virtual bool IsValid( object obj ) - { - return true; - } - - public virtual void Filter( ArrayList list ) - { - } - } -} + public virtual void Filter(ArrayList list) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/Compilers/ConditionalCompiler.cs b/Scripts/Commands/Generic/Extensions/Compilers/ConditionalCompiler.cs index 415869ef4..d3fffe364 100644 --- a/Scripts/Commands/Generic/Extensions/Compilers/ConditionalCompiler.cs +++ b/Scripts/Commands/Generic/Extensions/Compilers/ConditionalCompiler.cs @@ -5,539 +5,541 @@ using System.Reflection.Emit; namespace Server.Commands.Generic { - public interface IConditional - { - bool Verify( object obj ); - } - - public interface ICondition - { - // Invoked during the constructor - void Construct( TypeBuilder typeBuilder, ILGenerator il, int index ); - - // Target object will be loaded on the stack - void Compile( MethodEmitter emitter ); - } - - public sealed class TypeCondition : ICondition - { - public static TypeCondition Default = new TypeCondition(); - - void ICondition.Construct( TypeBuilder typeBuilder, ILGenerator il, int index ) - { - } - - void ICondition.Compile( MethodEmitter emitter ) - { - // The object was safely cast to be the conditionals type - // If it's null, then the type cast didn't work... - - emitter.LoadNull(); - emitter.Compare( OpCodes.Ceq ); - emitter.LogicalNot(); - } - } - - public sealed class PropertyValue - { - public Type Type { get; } - - public object Value { get; private set; } - - public FieldInfo Field { get; private set; } - - public bool HasField => ( Field != null ); - - public PropertyValue( Type type, object value ) - { - Type = type; - Value = value; - } - - public void Load( MethodEmitter method ) - { - if ( Field != null ) - { - method.LoadArgument( 0 ); - method.LoadField( Field ); - } - else if ( Value == null ) - { - method.LoadNull( Type ); - } - else - { - if ( Value is int i ) - method.Load( i ); - else if ( Value is long l ) - method.Load( l ); - else if ( Value is float f ) - method.Load( f ); - else if ( Value is double d ) - method.Load( d ); - else if ( Value is char c ) - method.Load( c ); - else if ( Value is bool b ) - method.Load( b ); - else if ( Value is string s ) - method.Load( s ); - else if ( Value is Enum e ) - method.Load( e ); - else - throw new InvalidOperationException( "Unrecognized comparison value." ); - } - } - - public void Acquire( TypeBuilder typeBuilder, ILGenerator il, string fieldName ) - { - if ( Value is string toParse ) - { - if ( !Type.IsValueType && toParse == "null" ) - { - Value = null; - } - else if ( Type == typeof( string ) ) - { - if ( toParse == @"@""null""" ) - toParse = "null"; - - Value = toParse; - } - else if ( Type.IsEnum ) - { - Value = Enum.Parse( Type, toParse, true ); - } - else - { - MethodInfo parseMethod = null; - object[] parseArgs = null; - - MethodInfo parseNumber = Type.GetMethod( - "Parse", - BindingFlags.Public | BindingFlags.Static, - null, - new[] { typeof( string ), typeof( NumberStyles ) }, - null - ); - - if ( parseNumber != null ) - { - NumberStyles style = NumberStyles.Integer; - - if ( Insensitive.StartsWith( toParse, "0x" ) ) - { - style = NumberStyles.HexNumber; - toParse = toParse.Substring( 2 ); - } - - parseMethod = parseNumber; - parseArgs = new object[] { toParse, style }; - } - else - { - MethodInfo parseGeneral = Type.GetMethod( - "Parse", - BindingFlags.Public | BindingFlags.Static, - null, - new[] { typeof( string ) }, - null - ); - - parseMethod = parseGeneral; - parseArgs = new object[] { toParse }; - } - - if ( parseMethod != null ) - { - Value = parseMethod.Invoke( null, parseArgs ); - - if ( !Type.IsPrimitive ) - { - Field = typeBuilder.DefineField( - fieldName, - Type, - FieldAttributes.Private | FieldAttributes.InitOnly - ); - - il.Emit( OpCodes.Ldarg_0 ); - - il.Emit( OpCodes.Ldstr, toParse ); - - if ( parseArgs.Length == 2 ) // dirty evil hack :-( - il.Emit( OpCodes.Ldc_I4, (int) parseArgs[1] ); - - il.Emit( OpCodes.Call, parseMethod ); - il.Emit( OpCodes.Stfld, Field ); - } - } - else - { - throw new InvalidOperationException( - $"Unable to convert string \"{Value}\" into type '{Type}'." - ); - } - } - } - } - } - - public abstract class PropertyCondition : ICondition - { - protected Property m_Property; - protected bool m_Not; - - public PropertyCondition( Property property, bool not ) - { - m_Property = property; - m_Not = not; - } - - public abstract void Construct( TypeBuilder typeBuilder, ILGenerator il, int index ); - - public abstract void Compile( MethodEmitter emitter ); - } - - public enum StringOperator - { - Equal, - NotEqual, - - Contains, - - StartsWith, - EndsWith - } - - public sealed class StringCondition : PropertyCondition - { - private StringOperator m_Operator; - private PropertyValue m_Value; - - private bool m_IgnoreCase; - - public StringCondition( Property property, bool not, StringOperator op, object value, bool ignoreCase ) - : base( property, not ) - { - m_Operator = op; - m_Value = new PropertyValue( property.Type, value ); - - m_IgnoreCase = ignoreCase; - } - - public override void Construct( TypeBuilder typeBuilder, ILGenerator il, int index ) - { - m_Value.Acquire( typeBuilder, il, "v" + index ); - } - - public override void Compile( MethodEmitter emitter ) - { - bool inverse = false; - - string methodName; - - switch ( m_Operator ) - { - case StringOperator.Equal: - methodName = "Equals"; - break; - - case StringOperator.NotEqual: - methodName = "Equals"; - inverse = true; - break; - - case StringOperator.Contains: - methodName = "Contains"; - break; - - case StringOperator.StartsWith: - methodName = "StartsWith"; - break; - - case StringOperator.EndsWith: - methodName = "EndsWith"; - break; - - default: - throw new InvalidOperationException( "Invalid string comparison operator." ); - } - - if ( m_IgnoreCase || methodName == "Equals" ) - { - Type type = ( m_IgnoreCase ? typeof( Insensitive ) : typeof( string ) ); - - emitter.BeginCall( - type.GetMethod( - methodName, - BindingFlags.Public | BindingFlags.Static, - null, - new[] - { - typeof( string ), - typeof( string ) - }, - null - ) - ); - - emitter.Chain( m_Property ); - m_Value.Load( emitter ); - - emitter.FinishCall(); - } - else - { - Label notNull = emitter.CreateLabel(); - Label moveOn = emitter.CreateLabel(); - - LocalBuilder temp = emitter.AcquireTemp( m_Property.Type ); - - emitter.Chain( m_Property ); - - emitter.StoreLocal( temp ); - emitter.LoadLocal( temp ); - - emitter.BranchIfTrue( notNull ); - - emitter.Load( false ); - emitter.Pop(); - emitter.Branch( moveOn ); - - emitter.MarkLabel( notNull ); - emitter.LoadLocal( temp ); - - emitter.BeginCall( - typeof( string ).GetMethod( - methodName, - BindingFlags.Public | BindingFlags.Instance, - null, - new[] - { - typeof( string ) - }, - null - ) - ); - - m_Value.Load( emitter ); - - emitter.FinishCall(); - - emitter.MarkLabel( moveOn ); - } - - if ( m_Not != inverse ) - emitter.LogicalNot(); - } - } - - public enum ComparisonOperator - { - Equal, - NotEqual, - Greater, - GreaterEqual, - Lesser, - LesserEqual - } - - public sealed class ComparisonCondition : PropertyCondition - { - private ComparisonOperator m_Operator; - private PropertyValue m_Value; - - public ComparisonCondition( Property property, bool not, ComparisonOperator op, object value ) - : base( property, not ) - { - m_Operator = op; - m_Value = new PropertyValue( property.Type, value ); - } - - public override void Construct( TypeBuilder typeBuilder, ILGenerator il, int index ) - { - m_Value.Acquire( typeBuilder, il, "v" + index ); - } - - public override void Compile( MethodEmitter emitter ) - { - emitter.Chain( m_Property ); - - bool inverse = false; - - bool couldCompare = - emitter.CompareTo( 1, delegate - { - m_Value.Load( emitter ); - } ); - - if ( couldCompare ) - { - emitter.Load( 0 ); - - switch ( m_Operator ) - { - case ComparisonOperator.Equal: - emitter.Compare( OpCodes.Ceq ); - break; - - case ComparisonOperator.NotEqual: - emitter.Compare( OpCodes.Ceq ); - inverse = true; - break; - - case ComparisonOperator.Greater: - emitter.Compare( OpCodes.Cgt ); - break; - - case ComparisonOperator.GreaterEqual: - emitter.Compare( OpCodes.Clt ); - inverse = true; - break; - - case ComparisonOperator.Lesser: - emitter.Compare( OpCodes.Clt ); - break; - - case ComparisonOperator.LesserEqual: - emitter.Compare( OpCodes.Cgt ); - inverse = true; - break; - - default: - throw new InvalidOperationException( "Invalid comparison operator." ); - } - } - else - { - // This type is -not- comparable - // We can only support == and != operations - - m_Value.Load( emitter ); - - switch ( m_Operator ) - { - case ComparisonOperator.Equal: - emitter.Compare( OpCodes.Ceq ); - break; - - case ComparisonOperator.NotEqual: - emitter.Compare( OpCodes.Ceq ); - inverse = true; - break; - - case ComparisonOperator.Greater: - case ComparisonOperator.GreaterEqual: - case ComparisonOperator.Lesser: - case ComparisonOperator.LesserEqual: - throw new InvalidOperationException( "Property does not support relational comparisons." ); - - default: - throw new InvalidOperationException( "Invalid operator." ); - } - } - - if ( m_Not != inverse ) - emitter.LogicalNot(); - } - } - - public static class ConditionalCompiler - { - public static IConditional Compile( AssemblyEmitter assembly, Type objectType, ICondition[] conditions, int index ) - { - TypeBuilder typeBuilder = assembly.DefineType( - "__conditional" + index, - TypeAttributes.Public, - typeof( object ) - ); - - #region Constructor - { - ConstructorBuilder ctor = typeBuilder.DefineConstructor( - MethodAttributes.Public, - CallingConventions.Standard, - Type.EmptyTypes - ); - - ILGenerator il = ctor.GetILGenerator(); - - // : base() - il.Emit( OpCodes.Ldarg_0 ); - il.Emit( OpCodes.Call, typeof( object ).GetConstructor( Type.EmptyTypes ) ); - - for ( int i = 0; i < conditions.Length; ++i ) - conditions[i].Construct( typeBuilder, il, i ); - - // return; - il.Emit( OpCodes.Ret ); - } - #endregion - - #region IComparer - typeBuilder.AddInterfaceImplementation( typeof( IConditional ) ); - - MethodBuilder compareMethod; - - #region Compare - { - MethodEmitter emitter = new MethodEmitter( typeBuilder ); - - emitter.Define( - /* name */ "Verify", - /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, - /* return */ typeof( bool ), - /* params */ new[] { typeof( object ) } ); - - LocalBuilder obj = emitter.CreateLocal( objectType ); - LocalBuilder eq = emitter.CreateLocal( typeof( bool ) ); - - emitter.LoadArgument( 1 ); - emitter.CastAs( objectType ); - emitter.StoreLocal( obj ); - - Label done = emitter.CreateLabel(); - - for ( int i = 0; i < conditions.Length; ++i ) - { - if ( i > 0 ) - { - emitter.LoadLocal( eq ); - - emitter.BranchIfFalse( done ); - } - - emitter.LoadLocal( obj ); - - conditions[i].Compile( emitter ); - - emitter.StoreLocal( eq ); - } - - emitter.MarkLabel( done ); - - emitter.LoadLocal( eq ); - - emitter.Return(); - - typeBuilder.DefineMethodOverride( - emitter.Method, - typeof( IConditional ).GetMethod( - "Verify", - new[] - { - typeof( object ) - } - ) - ); - - compareMethod = emitter.Method; - } - #endregion - #endregion + public interface IConditional + { + bool Verify(object obj); + } + + public interface ICondition + { + // Invoked during the constructor + void Construct(TypeBuilder typeBuilder, ILGenerator il, int index); + + // Target object will be loaded on the stack + void Compile(MethodEmitter emitter); + } + + public sealed class TypeCondition : ICondition + { + public static TypeCondition Default = new TypeCondition(); + + void ICondition.Construct(TypeBuilder typeBuilder, ILGenerator il, int index) + { + } + + void ICondition.Compile(MethodEmitter emitter) + { + // The object was safely cast to be the conditionals type + // If it's null, then the type cast didn't work... + + emitter.LoadNull(); + emitter.Compare(OpCodes.Ceq); + emitter.LogicalNot(); + } + } + + public sealed class PropertyValue + { + public PropertyValue(Type type, object value) + { + Type = type; + Value = value; + } + + public Type Type{ get; } + + public object Value{ get; private set; } + + public FieldInfo Field{ get; private set; } + + public bool HasField => Field != null; + + public void Load(MethodEmitter method) + { + if (Field != null) + { + method.LoadArgument(0); + method.LoadField(Field); + } + else if (Value == null) + { + method.LoadNull(Type); + } + else + { + if (Value is int i) + method.Load(i); + else if (Value is long l) + method.Load(l); + else if (Value is float f) + method.Load(f); + else if (Value is double d) + method.Load(d); + else if (Value is char c) + method.Load(c); + else if (Value is bool b) + method.Load(b); + else if (Value is string s) + method.Load(s); + else if (Value is Enum e) + method.Load(e); + else + throw new InvalidOperationException("Unrecognized comparison value."); + } + } + + public void Acquire(TypeBuilder typeBuilder, ILGenerator il, string fieldName) + { + if (Value is string toParse) + { + if (!Type.IsValueType && toParse == "null") + { + Value = null; + } + else if (Type == typeof(string)) + { + if (toParse == @"@""null""") + toParse = "null"; + + Value = toParse; + } + else if (Type.IsEnum) + { + Value = Enum.Parse(Type, toParse, true); + } + else + { + MethodInfo parseMethod = null; + object[] parseArgs = null; + + MethodInfo parseNumber = Type.GetMethod( + "Parse", + BindingFlags.Public | BindingFlags.Static, + null, + new[] { typeof(string), typeof(NumberStyles) }, + null + ); + + if (parseNumber != null) + { + NumberStyles style = NumberStyles.Integer; + + if (Insensitive.StartsWith(toParse, "0x")) + { + style = NumberStyles.HexNumber; + toParse = toParse.Substring(2); + } + + parseMethod = parseNumber; + parseArgs = new object[] { toParse, style }; + } + else + { + MethodInfo parseGeneral = Type.GetMethod( + "Parse", + BindingFlags.Public | BindingFlags.Static, + null, + new[] { typeof(string) }, + null + ); + + parseMethod = parseGeneral; + parseArgs = new object[] { toParse }; + } + + if (parseMethod != null) + { + Value = parseMethod.Invoke(null, parseArgs); + + if (!Type.IsPrimitive) + { + Field = typeBuilder.DefineField( + fieldName, + Type, + FieldAttributes.Private | FieldAttributes.InitOnly + ); + + il.Emit(OpCodes.Ldarg_0); + + il.Emit(OpCodes.Ldstr, toParse); + + if (parseArgs.Length == 2) // dirty evil hack :-( + il.Emit(OpCodes.Ldc_I4, (int)parseArgs[1]); + + il.Emit(OpCodes.Call, parseMethod); + il.Emit(OpCodes.Stfld, Field); + } + } + else + { + throw new InvalidOperationException( + $"Unable to convert string \"{Value}\" into type '{Type}'." + ); + } + } + } + } + } + + public abstract class PropertyCondition : ICondition + { + protected bool m_Not; + protected Property m_Property; + + public PropertyCondition(Property property, bool not) + { + m_Property = property; + m_Not = not; + } + + public abstract void Construct(TypeBuilder typeBuilder, ILGenerator il, int index); + + public abstract void Compile(MethodEmitter emitter); + } + + public enum StringOperator + { + Equal, + NotEqual, + + Contains, + + StartsWith, + EndsWith + } + + public sealed class StringCondition : PropertyCondition + { + private bool m_IgnoreCase; + private StringOperator m_Operator; + private PropertyValue m_Value; + + public StringCondition(Property property, bool not, StringOperator op, object value, bool ignoreCase) + : base(property, not) + { + m_Operator = op; + m_Value = new PropertyValue(property.Type, value); + + m_IgnoreCase = ignoreCase; + } + + public override void Construct(TypeBuilder typeBuilder, ILGenerator il, int index) + { + m_Value.Acquire(typeBuilder, il, "v" + index); + } + + public override void Compile(MethodEmitter emitter) + { + bool inverse = false; + + string methodName; + + switch (m_Operator) + { + case StringOperator.Equal: + methodName = "Equals"; + break; + + case StringOperator.NotEqual: + methodName = "Equals"; + inverse = true; + break; + + case StringOperator.Contains: + methodName = "Contains"; + break; + + case StringOperator.StartsWith: + methodName = "StartsWith"; + break; + + case StringOperator.EndsWith: + methodName = "EndsWith"; + break; + + default: + throw new InvalidOperationException("Invalid string comparison operator."); + } + + if (m_IgnoreCase || methodName == "Equals") + { + Type type = m_IgnoreCase ? typeof(Insensitive) : typeof(string); + + emitter.BeginCall( + type.GetMethod( + methodName, + BindingFlags.Public | BindingFlags.Static, + null, + new[] + { + typeof(string), + typeof(string) + }, + null + ) + ); + + emitter.Chain(m_Property); + m_Value.Load(emitter); + + emitter.FinishCall(); + } + else + { + Label notNull = emitter.CreateLabel(); + Label moveOn = emitter.CreateLabel(); + + LocalBuilder temp = emitter.AcquireTemp(m_Property.Type); + + emitter.Chain(m_Property); + + emitter.StoreLocal(temp); + emitter.LoadLocal(temp); + + emitter.BranchIfTrue(notNull); + + emitter.Load(false); + emitter.Pop(); + emitter.Branch(moveOn); + + emitter.MarkLabel(notNull); + emitter.LoadLocal(temp); + + emitter.BeginCall( + typeof(string).GetMethod( + methodName, + BindingFlags.Public | BindingFlags.Instance, + null, + new[] + { + typeof(string) + }, + null + ) + ); + + m_Value.Load(emitter); + + emitter.FinishCall(); + + emitter.MarkLabel(moveOn); + } + + if (m_Not != inverse) + emitter.LogicalNot(); + } + } + + public enum ComparisonOperator + { + Equal, + NotEqual, + Greater, + GreaterEqual, + Lesser, + LesserEqual + } + + public sealed class ComparisonCondition : PropertyCondition + { + private ComparisonOperator m_Operator; + private PropertyValue m_Value; + + public ComparisonCondition(Property property, bool not, ComparisonOperator op, object value) + : base(property, not) + { + m_Operator = op; + m_Value = new PropertyValue(property.Type, value); + } + + public override void Construct(TypeBuilder typeBuilder, ILGenerator il, int index) + { + m_Value.Acquire(typeBuilder, il, "v" + index); + } + + public override void Compile(MethodEmitter emitter) + { + emitter.Chain(m_Property); + + bool inverse = false; + + bool couldCompare = + emitter.CompareTo(1, delegate { m_Value.Load(emitter); }); + + if (couldCompare) + { + emitter.Load(0); + + switch (m_Operator) + { + case ComparisonOperator.Equal: + emitter.Compare(OpCodes.Ceq); + break; + + case ComparisonOperator.NotEqual: + emitter.Compare(OpCodes.Ceq); + inverse = true; + break; + + case ComparisonOperator.Greater: + emitter.Compare(OpCodes.Cgt); + break; + + case ComparisonOperator.GreaterEqual: + emitter.Compare(OpCodes.Clt); + inverse = true; + break; + + case ComparisonOperator.Lesser: + emitter.Compare(OpCodes.Clt); + break; + + case ComparisonOperator.LesserEqual: + emitter.Compare(OpCodes.Cgt); + inverse = true; + break; + + default: + throw new InvalidOperationException("Invalid comparison operator."); + } + } + else + { + // This type is -not- comparable + // We can only support == and != operations + + m_Value.Load(emitter); + + switch (m_Operator) + { + case ComparisonOperator.Equal: + emitter.Compare(OpCodes.Ceq); + break; + + case ComparisonOperator.NotEqual: + emitter.Compare(OpCodes.Ceq); + inverse = true; + break; + + case ComparisonOperator.Greater: + case ComparisonOperator.GreaterEqual: + case ComparisonOperator.Lesser: + case ComparisonOperator.LesserEqual: + throw new InvalidOperationException("Property does not support relational comparisons."); + + default: + throw new InvalidOperationException("Invalid operator."); + } + } + + if (m_Not != inverse) + emitter.LogicalNot(); + } + } - Type conditionalType = typeBuilder.CreateType(); - - return (IConditional) Activator.CreateInstance( conditionalType ); - } - } -} + public static class ConditionalCompiler + { + public static IConditional Compile(AssemblyEmitter assembly, Type objectType, ICondition[] conditions, int index) + { + TypeBuilder typeBuilder = assembly.DefineType( + "__conditional" + index, + TypeAttributes.Public, + typeof(object) + ); + + #region Constructor + + { + ConstructorBuilder ctor = typeBuilder.DefineConstructor( + MethodAttributes.Public, + CallingConventions.Standard, + Type.EmptyTypes + ); + + ILGenerator il = ctor.GetILGenerator(); + + // : base() + il.Emit(OpCodes.Ldarg_0); + il.Emit(OpCodes.Call, typeof(object).GetConstructor(Type.EmptyTypes)); + + for (int i = 0; i < conditions.Length; ++i) + conditions[i].Construct(typeBuilder, il, i); + + // return; + il.Emit(OpCodes.Ret); + } + + #endregion + + #region IComparer + + typeBuilder.AddInterfaceImplementation(typeof(IConditional)); + + MethodBuilder compareMethod; + + #region Compare + + { + MethodEmitter emitter = new MethodEmitter(typeBuilder); + + emitter.Define( + /* name */ "Verify", + /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, + /* return */ typeof(bool), + /* params */ new[] { typeof(object) }); + + LocalBuilder obj = emitter.CreateLocal(objectType); + LocalBuilder eq = emitter.CreateLocal(typeof(bool)); + + emitter.LoadArgument(1); + emitter.CastAs(objectType); + emitter.StoreLocal(obj); + + Label done = emitter.CreateLabel(); + + for (int i = 0; i < conditions.Length; ++i) + { + if (i > 0) + { + emitter.LoadLocal(eq); + + emitter.BranchIfFalse(done); + } + + emitter.LoadLocal(obj); + + conditions[i].Compile(emitter); + + emitter.StoreLocal(eq); + } + + emitter.MarkLabel(done); + + emitter.LoadLocal(eq); + + emitter.Return(); + + typeBuilder.DefineMethodOverride( + emitter.Method, + typeof(IConditional).GetMethod( + "Verify", + new[] + { + typeof(object) + } + ) + ); + + compareMethod = emitter.Method; + } + + #endregion + + #endregion + + Type conditionalType = typeBuilder.CreateType(); + + return (IConditional)Activator.CreateInstance(conditionalType); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/Compilers/DistinctCompiler.cs b/Scripts/Commands/Generic/Extensions/Compilers/DistinctCompiler.cs index 225955580..4c312e58a 100644 --- a/Scripts/Commands/Generic/Extensions/Compilers/DistinctCompiler.cs +++ b/Scripts/Commands/Generic/Extensions/Compilers/DistinctCompiler.cs @@ -6,242 +6,254 @@ using System.Reflection.Emit; namespace Server.Commands.Generic { - public static class DistinctCompiler - { - public static IComparer Compile( AssemblyEmitter assembly, Type objectType, Property[] props ) - { - TypeBuilder typeBuilder = assembly.DefineType( - "__distinct", - TypeAttributes.Public, - typeof( object ) - ); + public static class DistinctCompiler + { + public static IComparer Compile(AssemblyEmitter assembly, Type objectType, Property[] props) + { + TypeBuilder typeBuilder = assembly.DefineType( + "__distinct", + TypeAttributes.Public, + typeof(object) + ); - #region Constructor - { - ConstructorBuilder ctor = typeBuilder.DefineConstructor( - MethodAttributes.Public, - CallingConventions.Standard, - Type.EmptyTypes - ); + #region Constructor - ILGenerator il = ctor.GetILGenerator(); + { + ConstructorBuilder ctor = typeBuilder.DefineConstructor( + MethodAttributes.Public, + CallingConventions.Standard, + Type.EmptyTypes + ); - // : base() - il.Emit( OpCodes.Ldarg_0 ); - il.Emit( OpCodes.Call, typeof( object ).GetConstructor( Type.EmptyTypes ) ); + ILGenerator il = ctor.GetILGenerator(); - // return; - il.Emit( OpCodes.Ret ); - } - #endregion + // : base() + il.Emit(OpCodes.Ldarg_0); + il.Emit(OpCodes.Call, typeof(object).GetConstructor(Type.EmptyTypes)); - #region IComparer - typeBuilder.AddInterfaceImplementation( typeof( IComparer ) ); + // return; + il.Emit(OpCodes.Ret); + } - MethodBuilder compareMethod; + #endregion - #region Compare - { - MethodEmitter emitter = new MethodEmitter( typeBuilder ); + #region IComparer - emitter.Define( - /* name */ "Compare", - /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, - /* return */ typeof( int ), - /* params */ new[] { typeof( object ), typeof( object ) } ); + typeBuilder.AddInterfaceImplementation(typeof(IComparer)); - LocalBuilder a = emitter.CreateLocal( objectType ); - LocalBuilder b = emitter.CreateLocal( objectType ); + MethodBuilder compareMethod; - LocalBuilder v = emitter.CreateLocal( typeof( int ) ); + #region Compare - emitter.LoadArgument( 1 ); - emitter.CastAs( objectType ); - emitter.StoreLocal( a ); + { + MethodEmitter emitter = new MethodEmitter(typeBuilder); - emitter.LoadArgument( 2 ); - emitter.CastAs( objectType ); - emitter.StoreLocal( b ); + emitter.Define( + /* name */ "Compare", + /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, + /* return */ typeof(int), + /* params */ new[] { typeof(object), typeof(object) }); - emitter.Load( 0 ); - emitter.StoreLocal( v ); + LocalBuilder a = emitter.CreateLocal(objectType); + LocalBuilder b = emitter.CreateLocal(objectType); - Label end = emitter.CreateLabel(); + LocalBuilder v = emitter.CreateLocal(typeof(int)); - for ( int i = 0; i < props.Length; ++i ) - { - if ( i > 0 ) - { - emitter.LoadLocal( v ); - emitter.BranchIfTrue( end ); // if ( v != 0 ) return v; - } + emitter.LoadArgument(1); + emitter.CastAs(objectType); + emitter.StoreLocal(a); - Property prop = props[i]; + emitter.LoadArgument(2); + emitter.CastAs(objectType); + emitter.StoreLocal(b); - emitter.LoadLocal( a ); - emitter.Chain( prop ); + emitter.Load(0); + emitter.StoreLocal(v); - bool couldCompare = - emitter.CompareTo( 1, delegate - { - emitter.LoadLocal( b ); - emitter.Chain( prop ); - } ); + Label end = emitter.CreateLabel(); - if ( !couldCompare ) - throw new InvalidOperationException( "Property is not comparable." ); + for (int i = 0; i < props.Length; ++i) + { + if (i > 0) + { + emitter.LoadLocal(v); + emitter.BranchIfTrue(end); // if ( v != 0 ) return v; + } - emitter.StoreLocal( v ); - } + Property prop = props[i]; - emitter.MarkLabel( end ); + emitter.LoadLocal(a); + emitter.Chain(prop); - emitter.LoadLocal( v ); - emitter.Return(); + bool couldCompare = + emitter.CompareTo(1, delegate + { + emitter.LoadLocal(b); + emitter.Chain(prop); + }); - typeBuilder.DefineMethodOverride( - emitter.Method, - typeof( IComparer ).GetMethod( - "Compare", - new[] - { - typeof( object ), - typeof( object ) - } - ) - ); + if (!couldCompare) + throw new InvalidOperationException("Property is not comparable."); - compareMethod = emitter.Method; - } - #endregion - #endregion + emitter.StoreLocal(v); + } - #region IEqualityComparer - typeBuilder.AddInterfaceImplementation( typeof( IEqualityComparer ) ); + emitter.MarkLabel(end); - #region Equals - { - MethodEmitter emitter = new MethodEmitter( typeBuilder ); + emitter.LoadLocal(v); + emitter.Return(); - emitter.Define( - /* name */ "Equals", - /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, - /* return */ typeof( bool ), - /* params */ new[] { typeof( object ), typeof( object ) } ); + typeBuilder.DefineMethodOverride( + emitter.Method, + typeof(IComparer).GetMethod( + "Compare", + new[] + { + typeof(object), + typeof(object) + } + ) + ); - emitter.Generator.Emit( OpCodes.Ldarg_0 ); - emitter.Generator.Emit( OpCodes.Ldarg_1 ); - emitter.Generator.Emit( OpCodes.Ldarg_2 ); + compareMethod = emitter.Method; + } - emitter.Generator.Emit( OpCodes.Call, compareMethod ); + #endregion - emitter.Generator.Emit( OpCodes.Ldc_I4_0 ); + #endregion - emitter.Generator.Emit( OpCodes.Ceq ); + #region IEqualityComparer - emitter.Generator.Emit( OpCodes.Ret ); + typeBuilder.AddInterfaceImplementation(typeof(IEqualityComparer)); - typeBuilder.DefineMethodOverride( - emitter.Method, - typeof( IEqualityComparer ).GetMethod( - "Equals", - new[] - { - typeof( object ), - typeof( object ) - } - ) - ); - } - #endregion + #region Equals - #region GetHashCode - { - MethodEmitter emitter = new MethodEmitter( typeBuilder ); + { + MethodEmitter emitter = new MethodEmitter(typeBuilder); - emitter.Define( - /* name */ "GetHashCode", - /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, - /* return */ typeof( int ), - /* params */ new[] { typeof( object ) } ); + emitter.Define( + /* name */ "Equals", + /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, + /* return */ typeof(bool), + /* params */ new[] { typeof(object), typeof(object) }); - LocalBuilder obj = emitter.CreateLocal( objectType ); + emitter.Generator.Emit(OpCodes.Ldarg_0); + emitter.Generator.Emit(OpCodes.Ldarg_1); + emitter.Generator.Emit(OpCodes.Ldarg_2); - emitter.LoadArgument( 1 ); - emitter.CastAs( objectType ); - emitter.StoreLocal( obj ); + emitter.Generator.Emit(OpCodes.Call, compareMethod); - for ( int i = 0; i < props.Length; ++i ) - { - Property prop = props[i]; + emitter.Generator.Emit(OpCodes.Ldc_I4_0); - emitter.LoadLocal( obj ); - emitter.Chain( prop ); + emitter.Generator.Emit(OpCodes.Ceq); - Type active = emitter.Active; + emitter.Generator.Emit(OpCodes.Ret); - MethodInfo getHashCode = active.GetMethod( "GetHashCode", Type.EmptyTypes ); + typeBuilder.DefineMethodOverride( + emitter.Method, + typeof(IEqualityComparer).GetMethod( + "Equals", + new[] + { + typeof(object), + typeof(object) + } + ) + ); + } - if ( getHashCode == null ) - getHashCode = typeof( object ).GetMethod( "GetHashCode", Type.EmptyTypes ); + #endregion - if ( active != typeof( int ) ) - { - if ( !active.IsValueType ) - { - LocalBuilder value = emitter.AcquireTemp( active ); + #region GetHashCode - Label valueNotNull = emitter.CreateLabel(); - Label done = emitter.CreateLabel(); + { + MethodEmitter emitter = new MethodEmitter(typeBuilder); - emitter.StoreLocal( value ); - emitter.LoadLocal( value ); + emitter.Define( + /* name */ "GetHashCode", + /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, + /* return */ typeof(int), + /* params */ new[] { typeof(object) }); - emitter.BranchIfTrue( valueNotNull ); + LocalBuilder obj = emitter.CreateLocal(objectType); - emitter.Load( 0 ); - emitter.Pop( typeof( int ) ); + emitter.LoadArgument(1); + emitter.CastAs(objectType); + emitter.StoreLocal(obj); - emitter.Branch( done ); + for (int i = 0; i < props.Length; ++i) + { + Property prop = props[i]; - emitter.MarkLabel( valueNotNull ); + emitter.LoadLocal(obj); + emitter.Chain(prop); - emitter.LoadLocal( value ); - emitter.Call( getHashCode ); + Type active = emitter.Active; - emitter.ReleaseTemp( value ); + MethodInfo getHashCode = active.GetMethod("GetHashCode", Type.EmptyTypes); - emitter.MarkLabel( done ); - } - else - { - emitter.Call( getHashCode ); - } - } + if (getHashCode == null) + getHashCode = typeof(object).GetMethod("GetHashCode", Type.EmptyTypes); - if ( i > 0 ) - emitter.Xor(); - } + if (active != typeof(int)) + { + if (!active.IsValueType) + { + LocalBuilder value = emitter.AcquireTemp(active); - emitter.Return(); + Label valueNotNull = emitter.CreateLabel(); + Label done = emitter.CreateLabel(); - typeBuilder.DefineMethodOverride( - emitter.Method, - typeof( IEqualityComparer ).GetMethod( - "GetHashCode", - new[] - { - typeof( object ) - } - ) - ); - } - #endregion - #endregion + emitter.StoreLocal(value); + emitter.LoadLocal(value); - Type comparerType = typeBuilder.CreateType(); + emitter.BranchIfTrue(valueNotNull); - return (IComparer) Activator.CreateInstance( comparerType ); - } - } -} + emitter.Load(0); + emitter.Pop(typeof(int)); + + emitter.Branch(done); + + emitter.MarkLabel(valueNotNull); + + emitter.LoadLocal(value); + emitter.Call(getHashCode); + + emitter.ReleaseTemp(value); + + emitter.MarkLabel(done); + } + else + { + emitter.Call(getHashCode); + } + } + + if (i > 0) + emitter.Xor(); + } + + emitter.Return(); + + typeBuilder.DefineMethodOverride( + emitter.Method, + typeof(IEqualityComparer).GetMethod( + "GetHashCode", + new[] + { + typeof(object) + } + ) + ); + } + + #endregion + + #endregion + + Type comparerType = typeBuilder.CreateType(); + + return (IComparer)Activator.CreateInstance(comparerType); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/Compilers/SortCompiler.cs b/Scripts/Commands/Generic/Extensions/Compilers/SortCompiler.cs index c23f4392b..a21c055b5 100644 --- a/Scripts/Commands/Generic/Extensions/Compilers/SortCompiler.cs +++ b/Scripts/Commands/Generic/Extensions/Compilers/SortCompiler.cs @@ -5,160 +5,166 @@ using System.Reflection.Emit; namespace Server.Commands.Generic { - public sealed class OrderInfo - { - private int m_Order; + public sealed class OrderInfo + { + private int m_Order; - public Property Property { get; set; } + public OrderInfo(Property property, bool isAscending) + { + Property = property; - public bool IsAscending - { - get => ( m_Order > 0 ); - set => m_Order = ( value ? +1 : -1 ); - } + IsAscending = isAscending; + } - public bool IsDescending - { - get => ( m_Order < 0 ); - set => m_Order = ( value ? -1 : +1 ); - } + public Property Property{ get; set; } - public int Sign - { - get => Math.Sign( m_Order ); - set - { - m_Order = Math.Sign( value ); + public bool IsAscending + { + get => m_Order > 0; + set => m_Order = value ? +1 : -1; + } - if ( m_Order == 0 ) - throw new InvalidOperationException( "Sign cannot be zero." ); - } - } + public bool IsDescending + { + get => m_Order < 0; + set => m_Order = value ? -1 : +1; + } - public OrderInfo( Property property, bool isAscending ) - { - Property = property; + public int Sign + { + get => Math.Sign(m_Order); + set + { + m_Order = Math.Sign(value); - IsAscending = isAscending; - } - } + if (m_Order == 0) + throw new InvalidOperationException("Sign cannot be zero."); + } + } + } - public static class SortCompiler - { - public static IComparer Compile( AssemblyEmitter assembly, Type objectType, OrderInfo[] orders ) - { - TypeBuilder typeBuilder = assembly.DefineType( - "__sort", - TypeAttributes.Public, - typeof( object ) - ); + public static class SortCompiler + { + public static IComparer Compile(AssemblyEmitter assembly, Type objectType, OrderInfo[] orders) + { + TypeBuilder typeBuilder = assembly.DefineType( + "__sort", + TypeAttributes.Public, + typeof(object) + ); - #region Constructor - { - ConstructorBuilder ctor = typeBuilder.DefineConstructor( - MethodAttributes.Public, - CallingConventions.Standard, - Type.EmptyTypes - ); + #region Constructor - ILGenerator il = ctor.GetILGenerator(); + { + ConstructorBuilder ctor = typeBuilder.DefineConstructor( + MethodAttributes.Public, + CallingConventions.Standard, + Type.EmptyTypes + ); - // : base() - il.Emit( OpCodes.Ldarg_0 ); - il.Emit( OpCodes.Call, typeof( object ).GetConstructor( Type.EmptyTypes ) ); + ILGenerator il = ctor.GetILGenerator(); - // return; - il.Emit( OpCodes.Ret ); - } - #endregion + // : base() + il.Emit(OpCodes.Ldarg_0); + il.Emit(OpCodes.Call, typeof(object).GetConstructor(Type.EmptyTypes)); - #region IComparer - typeBuilder.AddInterfaceImplementation( typeof( IComparer ) ); + // return; + il.Emit(OpCodes.Ret); + } - MethodBuilder compareMethod; + #endregion - #region Compare - { - MethodEmitter emitter = new MethodEmitter( typeBuilder ); + #region IComparer - emitter.Define( - /* name */ "Compare", - /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, - /* return */ typeof( int ), - /* params */ new[] { typeof( object ), typeof( object ) } ); + typeBuilder.AddInterfaceImplementation(typeof(IComparer)); - LocalBuilder a = emitter.CreateLocal( objectType ); - LocalBuilder b = emitter.CreateLocal( objectType ); + MethodBuilder compareMethod; - LocalBuilder v = emitter.CreateLocal( typeof( int ) ); + #region Compare - emitter.LoadArgument( 1 ); - emitter.CastAs( objectType ); - emitter.StoreLocal( a ); + { + MethodEmitter emitter = new MethodEmitter(typeBuilder); - emitter.LoadArgument( 2 ); - emitter.CastAs( objectType ); - emitter.StoreLocal( b ); + emitter.Define( + /* name */ "Compare", + /* attr */ MethodAttributes.Public | MethodAttributes.Virtual, + /* return */ typeof(int), + /* params */ new[] { typeof(object), typeof(object) }); - emitter.Load( 0 ); - emitter.StoreLocal( v ); + LocalBuilder a = emitter.CreateLocal(objectType); + LocalBuilder b = emitter.CreateLocal(objectType); - Label end = emitter.CreateLabel(); + LocalBuilder v = emitter.CreateLocal(typeof(int)); - for ( int i = 0; i < orders.Length; ++i ) - { - if ( i > 0 ) - { - emitter.LoadLocal( v ); - emitter.BranchIfTrue( end ); // if ( v != 0 ) return v; - } + emitter.LoadArgument(1); + emitter.CastAs(objectType); + emitter.StoreLocal(a); - OrderInfo orderInfo = orders[i]; + emitter.LoadArgument(2); + emitter.CastAs(objectType); + emitter.StoreLocal(b); - Property prop = orderInfo.Property; - int sign = orderInfo.Sign; + emitter.Load(0); + emitter.StoreLocal(v); - emitter.LoadLocal( a ); - emitter.Chain( prop ); + Label end = emitter.CreateLabel(); - bool couldCompare = - emitter.CompareTo( sign, delegate - { - emitter.LoadLocal( b ); - emitter.Chain( prop ); - } ); + for (int i = 0; i < orders.Length; ++i) + { + if (i > 0) + { + emitter.LoadLocal(v); + emitter.BranchIfTrue(end); // if ( v != 0 ) return v; + } - if ( !couldCompare ) - throw new InvalidOperationException( "Property is not comparable." ); + OrderInfo orderInfo = orders[i]; - emitter.StoreLocal( v ); - } + Property prop = orderInfo.Property; + int sign = orderInfo.Sign; - emitter.MarkLabel( end ); + emitter.LoadLocal(a); + emitter.Chain(prop); - emitter.LoadLocal( v ); - emitter.Return(); + bool couldCompare = + emitter.CompareTo(sign, delegate + { + emitter.LoadLocal(b); + emitter.Chain(prop); + }); - typeBuilder.DefineMethodOverride( - emitter.Method, - typeof( IComparer ).GetMethod( - "Compare", - new[] - { - typeof( object ), - typeof( object ) - } - ) - ); + if (!couldCompare) + throw new InvalidOperationException("Property is not comparable."); - compareMethod = emitter.Method; - } - #endregion - #endregion + emitter.StoreLocal(v); + } - Type comparerType = typeBuilder.CreateType(); + emitter.MarkLabel(end); - return (IComparer) Activator.CreateInstance( comparerType ); - } - } -} + emitter.LoadLocal(v); + emitter.Return(); + + typeBuilder.DefineMethodOverride( + emitter.Method, + typeof(IComparer).GetMethod( + "Compare", + new[] + { + typeof(object), + typeof(object) + } + ) + ); + + compareMethod = emitter.Method; + } + + #endregion + + #endregion + + Type comparerType = typeBuilder.CreateType(); + + return (IComparer)Activator.CreateInstance(comparerType); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/DistinctExtension.cs b/Scripts/Commands/Generic/Extensions/DistinctExtension.cs index 925863dd0..263cc96b2 100644 --- a/Scripts/Commands/Generic/Extensions/DistinctExtension.cs +++ b/Scripts/Commands/Generic/Extensions/DistinctExtension.cs @@ -4,81 +4,82 @@ using System.Collections.Generic; namespace Server.Commands.Generic { - public sealed class DistinctExtension : BaseExtension - { - public static ExtensionInfo ExtInfo = new ExtensionInfo( 30, "Distinct", -1, delegate { return new DistinctExtension(); } ); + public sealed class DistinctExtension : BaseExtension + { + public static ExtensionInfo ExtInfo = + new ExtensionInfo(30, "Distinct", -1, delegate { return new DistinctExtension(); }); - public static void Initialize() - { - ExtensionInfo.Register( ExtInfo ); - } + private IComparer m_Comparer; - public override ExtensionInfo Info => ExtInfo; + private List m_Properties; - private List m_Properties; + public DistinctExtension() + { + m_Properties = new List(); + } - private IComparer m_Comparer; + public override ExtensionInfo Info => ExtInfo; - public DistinctExtension() - { - m_Properties = new List(); - } + public static void Initialize() + { + ExtensionInfo.Register(ExtInfo); + } - public override void Optimize( Mobile from, Type baseType, ref AssemblyEmitter assembly ) - { - if ( baseType == null ) - throw new Exception( "Distinct extension may only be used in combination with an object conditional." ); + public override void Optimize(Mobile from, Type baseType, ref AssemblyEmitter assembly) + { + if (baseType == null) + throw new Exception("Distinct extension may only be used in combination with an object conditional."); - foreach ( Property prop in m_Properties ) - { - prop.BindTo( baseType, PropertyAccess.Read ); - prop.CheckAccess( from ); - } + foreach (Property prop in m_Properties) + { + prop.BindTo(baseType, PropertyAccess.Read); + prop.CheckAccess(from); + } - if ( assembly == null ) - assembly = new AssemblyEmitter( "__dynamic", false ); + if (assembly == null) + assembly = new AssemblyEmitter("__dynamic", false); - m_Comparer = DistinctCompiler.Compile( assembly, baseType, m_Properties.ToArray() ); - } + m_Comparer = DistinctCompiler.Compile(assembly, baseType, m_Properties.ToArray()); + } - public override void Parse( Mobile from, string[] arguments, int offset, int size ) - { - if ( size < 1 ) - throw new Exception( "Invalid distinction syntax." ); + public override void Parse(Mobile from, string[] arguments, int offset, int size) + { + if (size < 1) + throw new Exception("Invalid distinction syntax."); - int end = offset + size; + int end = offset + size; - while ( offset < end ) - { - string binding = arguments[offset++]; + while (offset < end) + { + string binding = arguments[offset++]; - m_Properties.Add( new Property( binding ) ); - } - } + m_Properties.Add(new Property(binding)); + } + } - public override void Filter( ArrayList list ) - { - if ( m_Comparer == null ) - throw new InvalidOperationException( "The extension must first be optimized." ); + public override void Filter(ArrayList list) + { + if (m_Comparer == null) + throw new InvalidOperationException("The extension must first be optimized."); - ArrayList copy = new ArrayList( list ); + ArrayList copy = new ArrayList(list); - copy.Sort( m_Comparer ); + copy.Sort(m_Comparer); - list.Clear(); + list.Clear(); - object last = null; + object last = null; - for ( int i = 0; i < copy.Count; ++i ) - { - object obj = copy[i]; + for (int i = 0; i < copy.Count; ++i) + { + object obj = copy[i]; - if ( last == null || m_Comparer.Compare( obj, last ) != 0 ) - { - list.Add( obj ); - last = obj; - } - } - } - } -} + if (last == null || m_Comparer.Compare(obj, last) != 0) + { + list.Add(obj); + last = obj; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/LimitExtension.cs b/Scripts/Commands/Generic/Extensions/LimitExtension.cs index 9ee3f37ff..9aa8eed91 100644 --- a/Scripts/Commands/Generic/Extensions/LimitExtension.cs +++ b/Scripts/Commands/Generic/Extensions/LimitExtension.cs @@ -3,35 +3,31 @@ using System.Collections; namespace Server.Commands.Generic { - public sealed class LimitExtension : BaseExtension - { - public static ExtensionInfo ExtInfo = new ExtensionInfo( 80, "Limit", 1, delegate { return new LimitExtension(); } ); + public sealed class LimitExtension : BaseExtension + { + public static ExtensionInfo ExtInfo = new ExtensionInfo(80, "Limit", 1, delegate { return new LimitExtension(); }); - public static void Initialize() - { - ExtensionInfo.Register( ExtInfo ); - } + public override ExtensionInfo Info => ExtInfo; - public override ExtensionInfo Info => ExtInfo; + public int Limit{ get; private set; } - public int Limit { get; private set; } + public static void Initialize() + { + ExtensionInfo.Register(ExtInfo); + } - public LimitExtension() - { - } + public override void Parse(Mobile from, string[] arguments, int offset, int size) + { + Limit = Utility.ToInt32(arguments[offset]); - public override void Parse( Mobile from, string[] arguments, int offset, int size ) - { - Limit = Utility.ToInt32( arguments[offset] ); + if (Limit < 0) + throw new Exception("Limit cannot be less than zero."); + } - if ( Limit < 0 ) - throw new Exception( "Limit cannot be less than zero." ); - } - - public override void Filter( ArrayList list ) - { - if ( list.Count > Limit ) - list.RemoveRange( Limit, list.Count - Limit ); - } - } -} + public override void Filter(ArrayList list) + { + if (list.Count > Limit) + list.RemoveRange(Limit, list.Count - Limit); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/SortExtension.cs b/Scripts/Commands/Generic/Extensions/SortExtension.cs index 2c8231cf6..d6fb3e604 100644 --- a/Scripts/Commands/Generic/Extensions/SortExtension.cs +++ b/Scripts/Commands/Generic/Extensions/SortExtension.cs @@ -4,101 +4,101 @@ using System.Collections.Generic; namespace Server.Commands.Generic { - public sealed class SortExtension : BaseExtension - { - public static ExtensionInfo ExtInfo = new ExtensionInfo( 40, "Order", -1, delegate { return new SortExtension(); } ); + public sealed class SortExtension : BaseExtension + { + public static ExtensionInfo ExtInfo = new ExtensionInfo(40, "Order", -1, delegate { return new SortExtension(); }); - public static void Initialize() - { - ExtensionInfo.Register( ExtInfo ); - } + private IComparer m_Comparer; - public override ExtensionInfo Info => ExtInfo; + private List m_Orders; - private List m_Orders; + public SortExtension() + { + m_Orders = new List(); + } - private IComparer m_Comparer; + public override ExtensionInfo Info => ExtInfo; - public SortExtension() - { - m_Orders = new List(); - } + public static void Initialize() + { + ExtensionInfo.Register(ExtInfo); + } - public override void Optimize( Mobile from, Type baseType, ref AssemblyEmitter assembly ) - { - if ( baseType == null ) - throw new Exception( "The ordering extension may only be used in combination with an object conditional." ); + public override void Optimize(Mobile from, Type baseType, ref AssemblyEmitter assembly) + { + if (baseType == null) + throw new Exception("The ordering extension may only be used in combination with an object conditional."); - foreach ( OrderInfo order in m_Orders ) - { - order.Property.BindTo( baseType, PropertyAccess.Read ); - order.Property.CheckAccess( from ); - } + foreach (OrderInfo order in m_Orders) + { + order.Property.BindTo(baseType, PropertyAccess.Read); + order.Property.CheckAccess(from); + } - if ( assembly == null ) - assembly = new AssemblyEmitter( "__dynamic", false ); + if (assembly == null) + assembly = new AssemblyEmitter("__dynamic", false); - m_Comparer = SortCompiler.Compile( assembly, baseType, m_Orders.ToArray() ); - } + m_Comparer = SortCompiler.Compile(assembly, baseType, m_Orders.ToArray()); + } - public override void Parse( Mobile from, string[] arguments, int offset, int size ) - { - if ( size < 1 ) - throw new Exception( "Invalid ordering syntax." ); + public override void Parse(Mobile from, string[] arguments, int offset, int size) + { + if (size < 1) + throw new Exception("Invalid ordering syntax."); - if ( Insensitive.Equals( arguments[offset], "by" ) ) - { - ++offset; - --size; + if (Insensitive.Equals(arguments[offset], "by")) + { + ++offset; + --size; - if ( size < 1 ) - throw new Exception( "Invalid ordering syntax." ); - } + if (size < 1) + throw new Exception("Invalid ordering syntax."); + } - int end = offset + size; + int end = offset + size; - while ( offset < end ) - { - string binding = arguments[offset++]; + while (offset < end) + { + string binding = arguments[offset++]; - bool isAscending = true; + bool isAscending = true; - if ( offset < end ) - { - string next = arguments[offset]; + if (offset < end) + { + string next = arguments[offset]; - switch ( next.ToLower() ) - { - case "+": - case "up": - case "asc": - case "ascending": - isAscending = true; - ++offset; - break; + switch (next.ToLower()) + { + case "+": + case "up": + case "asc": + case "ascending": + isAscending = true; + ++offset; + break; - case "-": - case "down": - case "desc": - case "descending": - isAscending = false; - ++offset; - break; - } - } + case "-": + case "down": + case "desc": + case "descending": + isAscending = false; + ++offset; + break; + } + } - Property property = new Property( binding ); + Property property = new Property(binding); - m_Orders.Add( new OrderInfo( property, isAscending ) ); - } - } + m_Orders.Add(new OrderInfo(property, isAscending)); + } + } - public override void Filter( ArrayList list ) - { - if ( m_Comparer == null ) - throw new InvalidOperationException( "The extension must first be optimized." ); + public override void Filter(ArrayList list) + { + if (m_Comparer == null) + throw new InvalidOperationException("The extension must first be optimized."); - list.Sort( m_Comparer ); - } - } -} + list.Sort(m_Comparer); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Extensions/WhereExtension.cs b/Scripts/Commands/Generic/Extensions/WhereExtension.cs index 90c997399..f72b31236 100644 --- a/Scripts/Commands/Generic/Extensions/WhereExtension.cs +++ b/Scripts/Commands/Generic/Extensions/WhereExtension.cs @@ -2,42 +2,38 @@ using System; namespace Server.Commands.Generic { - public sealed class WhereExtension : BaseExtension - { - public static ExtensionInfo ExtInfo = new ExtensionInfo( 20, "Where", -1, delegate { return new WhereExtension(); } ); + public sealed class WhereExtension : BaseExtension + { + public static ExtensionInfo ExtInfo = new ExtensionInfo(20, "Where", -1, delegate { return new WhereExtension(); }); - public static void Initialize() - { - ExtensionInfo.Register( ExtInfo ); - } + public override ExtensionInfo Info => ExtInfo; - public override ExtensionInfo Info => ExtInfo; + public ObjectConditional Conditional{ get; private set; } - public ObjectConditional Conditional { get; private set; } + public static void Initialize() + { + ExtensionInfo.Register(ExtInfo); + } - public WhereExtension() - { - } + public override void Optimize(Mobile from, Type baseType, ref AssemblyEmitter assembly) + { + if (baseType == null) + throw new InvalidOperationException("Insanity."); - public override void Optimize( Mobile from, Type baseType, ref AssemblyEmitter assembly ) - { - if ( baseType == null ) - throw new InvalidOperationException( "Insanity." ); + Conditional.Compile(ref assembly); + } - Conditional.Compile( ref assembly ); - } + public override void Parse(Mobile from, string[] arguments, int offset, int size) + { + if (size < 1) + throw new Exception("Invalid condition syntax."); - public override void Parse( Mobile from, string[] arguments, int offset, int size ) - { - if ( size < 1 ) - throw new Exception( "Invalid condition syntax." ); + Conditional = ObjectConditional.ParseDirect(from, arguments, offset, size); + } - Conditional = ObjectConditional.ParseDirect( from, arguments, offset, size ); - } - - public override bool IsValid( object obj ) - { - return Conditional.CheckCondition( obj ); - } - } -} + public override bool IsValid(object obj) + { + return Conditional.CheckCondition(obj); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/AreaCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/AreaCommandImplementor.cs index 2d56a2599..850301e26 100644 --- a/Scripts/Commands/Generic/Implementors/AreaCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/AreaCommandImplementor.cs @@ -3,72 +3,73 @@ using System.Collections; namespace Server.Commands.Generic { - public class AreaCommandImplementor : BaseCommandImplementor - { - public static AreaCommandImplementor Instance { get; private set; } + public class AreaCommandImplementor : BaseCommandImplementor + { + public AreaCommandImplementor() + { + Accessors = new[] { "Area", "Group" }; + SupportRequirement = CommandSupport.Area; + SupportsConditionals = true; + AccessLevel = AccessLevel.GameMaster; + Usage = "Area [condition]"; + Description = + "Invokes the command on all appropriate objects in a targeted area. Optional condition arguments can further restrict the set of objects."; - public AreaCommandImplementor() - { - Accessors = new[]{ "Area", "Group" }; - SupportRequirement = CommandSupport.Area; - SupportsConditionals = true; - AccessLevel = AccessLevel.GameMaster; - Usage = "Area [condition]"; - Description = "Invokes the command on all appropriate objects in a targeted area. Optional condition arguments can further restrict the set of objects."; + Instance = this; + } - Instance = this; - } + public static AreaCommandImplementor Instance{ get; private set; } - public override void Process( Mobile from, BaseCommand command, string[] args ) - { - BoundingBoxPicker.Begin( from, OnTarget, new object[]{ command, args } ); - } + public override void Process(Mobile from, BaseCommand command, string[] args) + { + BoundingBoxPicker.Begin(from, OnTarget, new object[] { command, args }); + } - public void OnTarget( Mobile from, Map map, Point3D start, Point3D end, object state ) - { - try - { - object[] states = (object[])state; - BaseCommand command = (BaseCommand)states[0]; - string[] args = (string[])states[1]; + public void OnTarget(Mobile from, Map map, Point3D start, Point3D end, object state) + { + try + { + object[] states = (object[])state; + BaseCommand command = (BaseCommand)states[0]; + string[] args = (string[])states[1]; - Rectangle2D rect = new Rectangle2D( start.X, start.Y, end.X - start.X + 1, end.Y - start.Y + 1 ); + Rectangle2D rect = new Rectangle2D(start.X, start.Y, end.X - start.X + 1, end.Y - start.Y + 1); - Extensions ext = Extensions.Parse( from, ref args ); + Extensions ext = Extensions.Parse(from, ref args); - bool items, mobiles; + bool items, mobiles; - if ( !CheckObjectTypes( from, command, ext, out items, out mobiles ) ) - return; + if (!CheckObjectTypes(from, command, ext, out items, out mobiles)) + return; - IPooledEnumerable eable; + IPooledEnumerable eable; - if (items || mobiles) - eable = map.GetObjectsInBounds(rect, items, mobiles); - else - return; + if (items || mobiles) + eable = map.GetObjectsInBounds(rect, items, mobiles); + else + return; - ArrayList objs = new ArrayList(); + ArrayList objs = new ArrayList(); - foreach ( IEntity obj in eable ) - { - if ( mobiles && obj is Mobile && !BaseCommand.IsAccessible( from, obj ) ) - continue; + foreach (IEntity obj in eable) + { + if (mobiles && obj is Mobile && !BaseCommand.IsAccessible(from, obj)) + continue; - if ( ext.IsValid( obj ) ) - objs.Add( obj ); - } + if (ext.IsValid(obj)) + objs.Add(obj); + } - eable.Free(); + eable.Free(); - ext.Filter( objs ); + ext.Filter(objs); - RunCommand( from, objs, command, args ); - } - catch ( Exception ex ) - { - from.SendMessage( ex.Message ); - } - } - } -} + RunCommand(from, objs, command, args); + } + catch (Exception ex) + { + from.SendMessage(ex.Message); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/BaseCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/BaseCommandImplementor.cs index 240ec45e4..f7a68e580 100644 --- a/Scripts/Commands/Generic/Implementors/BaseCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/BaseCommandImplementor.cs @@ -5,299 +5,294 @@ using System.Text; namespace Server.Commands.Generic { - [Flags] - public enum CommandSupport - { - Single = 0x0001, - Global = 0x0002, - Online = 0x0004, - Multi = 0x0008, - Area = 0x0010, - Self = 0x0020, - Region = 0x0040, - Contained = 0x0080, - IPAddress = 0x0100, + [Flags] + public enum CommandSupport + { + Single = 0x0001, + Global = 0x0002, + Online = 0x0004, + Multi = 0x0008, + Area = 0x0010, + Self = 0x0020, + Region = 0x0040, + Contained = 0x0080, + IPAddress = 0x0100, - All = Single | Global | Online | Multi | Area | Self | Region | Contained | IPAddress, - AllMobiles = All & ~Contained, - AllNPCs = All & ~(IPAddress | Online | Self | Contained), - AllItems = All & ~(IPAddress | Online | Self | Region), + All = Single | Global | Online | Multi | Area | Self | Region | Contained | IPAddress, + AllMobiles = All & ~Contained, + AllNPCs = All & ~(IPAddress | Online | Self | Contained), + AllItems = All & ~(IPAddress | Online | Self | Region), - Simple = Single | Multi, - Complex = Global | Online | Area | Region | Contained | IPAddress - } + Simple = Single | Multi, + Complex = Global | Online | Area | Region | Contained | IPAddress + } - public abstract class BaseCommandImplementor - { - public static void RegisterImplementors() - { - Register( new RegionCommandImplementor() ); - Register( new GlobalCommandImplementor() ); - Register( new OnlineCommandImplementor() ); - Register( new SingleCommandImplementor() ); - Register( new SerialCommandImplementor() ); - Register( new MultiCommandImplementor() ); - Register( new AreaCommandImplementor() ); - Register( new SelfCommandImplementor() ); - Register( new ContainedCommandImplementor() ); - Register( new IPAddressCommandImplementor() ); + public abstract class BaseCommandImplementor + { + private static List m_Implementors; - Register( new RangeCommandImplementor() ); - Register( new ScreenCommandImplementor() ); - Register( new FacetCommandImplementor() ); - } + public BaseCommandImplementor() + { + Commands = new Dictionary(StringComparer.OrdinalIgnoreCase); + } - public bool SupportsConditionals { get; set; } + public bool SupportsConditionals{ get; set; } - public string[] Accessors { get; set; } + public string[] Accessors{ get; set; } - public string Usage { get; set; } + public string Usage{ get; set; } - public string Description { get; set; } + public string Description{ get; set; } - public AccessLevel AccessLevel { get; set; } + public AccessLevel AccessLevel{ get; set; } - public CommandSupport SupportRequirement { get; set; } + public CommandSupport SupportRequirement{ get; set; } - public Dictionary Commands { get; } + public Dictionary Commands{ get; } - public BaseCommandImplementor() - { - Commands = new Dictionary( StringComparer.OrdinalIgnoreCase ); - } + public static List Implementors + { + get + { + if (m_Implementors == null) + { + m_Implementors = new List(); + RegisterImplementors(); + } - public virtual void Compile( Mobile from, BaseCommand command, ref string[] args, ref object obj ) - { - obj = null; - } + return m_Implementors; + } + } - public virtual void Register( BaseCommand command ) - { - for ( int i = 0; i < command.Commands.Length; ++i ) - Commands[command.Commands[i]] = command; - } + public static void RegisterImplementors() + { + Register(new RegionCommandImplementor()); + Register(new GlobalCommandImplementor()); + Register(new OnlineCommandImplementor()); + Register(new SingleCommandImplementor()); + Register(new SerialCommandImplementor()); + Register(new MultiCommandImplementor()); + Register(new AreaCommandImplementor()); + Register(new SelfCommandImplementor()); + Register(new ContainedCommandImplementor()); + Register(new IPAddressCommandImplementor()); - public bool CheckObjectTypes( Mobile from, BaseCommand command, Extensions ext, out bool items, out bool mobiles ) - { - items = mobiles = false; + Register(new RangeCommandImplementor()); + Register(new ScreenCommandImplementor()); + Register(new FacetCommandImplementor()); + } - ObjectConditional cond = ObjectConditional.Empty; + public virtual void Compile(Mobile from, BaseCommand command, ref string[] args, ref object obj) + { + obj = null; + } - foreach ( BaseExtension check in ext ) - { - if ( check is WhereExtension extension ) - { - cond = extension.Conditional; + public virtual void Register(BaseCommand command) + { + for (int i = 0; i < command.Commands.Length; ++i) + Commands[command.Commands[i]] = command; + } - break; - } - } + public bool CheckObjectTypes(Mobile from, BaseCommand command, Extensions ext, out bool items, out bool mobiles) + { + items = mobiles = false; - bool condIsItem = cond.IsItem; - bool condIsMobile = cond.IsMobile; + ObjectConditional cond = ObjectConditional.Empty; - switch ( command.ObjectTypes ) - { - case ObjectTypes.All: - case ObjectTypes.Both: - { - if ( condIsItem ) - items = true; + foreach (BaseExtension check in ext) + if (check is WhereExtension extension) + { + cond = extension.Conditional; - if ( condIsMobile ) - mobiles = true; + break; + } - break; - } - case ObjectTypes.Items: - { - if ( condIsItem ) - { - items = true; - } - else if ( condIsMobile ) - { - from.SendMessage( "You may not use a mobile type condition for this command." ); - return false; - } + bool condIsItem = cond.IsItem; + bool condIsMobile = cond.IsMobile; - break; - } - case ObjectTypes.Mobiles: - { - if ( condIsMobile ) - { - mobiles = true; - } - else if ( condIsItem ) - { - from.SendMessage( "You may not use an item type condition for this command." ); - return false; - } + switch (command.ObjectTypes) + { + case ObjectTypes.All: + case ObjectTypes.Both: + { + if (condIsItem) + items = true; - break; - } - } + if (condIsMobile) + mobiles = true; - return true; - } + break; + } + case ObjectTypes.Items: + { + if (condIsItem) + { + items = true; + } + else if (condIsMobile) + { + from.SendMessage("You may not use a mobile type condition for this command."); + return false; + } - public void RunCommand( Mobile from, BaseCommand command, string[] args ) - { - try - { - object obj = null; + break; + } + case ObjectTypes.Mobiles: + { + if (condIsMobile) + { + mobiles = true; + } + else if (condIsItem) + { + from.SendMessage("You may not use an item type condition for this command."); + return false; + } - Compile( from, command, ref args, ref obj ); + break; + } + } - RunCommand( from, obj, command, args ); - } - catch ( Exception ex ) - { - from.SendMessage( ex.Message ); - } - } + return true; + } - public string GenerateArgString( string[] args ) - { - if ( args.Length == 0 ) - return ""; + public void RunCommand(Mobile from, BaseCommand command, string[] args) + { + try + { + object obj = null; - // NOTE: this does not preserve the case where quotation marks are used on a single word + Compile(from, command, ref args, ref obj); - StringBuilder sb = new StringBuilder(); + RunCommand(from, obj, command, args); + } + catch (Exception ex) + { + from.SendMessage(ex.Message); + } + } - for ( int i = 0; i < args.Length; ++i ) - { - if ( i > 0 ) - sb.Append( ' ' ); + public string GenerateArgString(string[] args) + { + if (args.Length == 0) + return ""; - if ( args[i].IndexOf( ' ' ) >= 0 ) - { - sb.Append( '"' ); - sb.Append( args[i] ); - sb.Append( '"' ); - } - else - { - sb.Append( args[i] ); - } - } + // NOTE: this does not preserve the case where quotation marks are used on a single word - return sb.ToString(); - } + StringBuilder sb = new StringBuilder(); - public void RunCommand( Mobile from, object obj, BaseCommand command, string[] args ) - { - // try - // { - CommandEventArgs e = new CommandEventArgs( from, command.Commands[0], GenerateArgString( args ), args ); + for (int i = 0; i < args.Length; ++i) + { + if (i > 0) + sb.Append(' '); - if ( !command.ValidateArgs( this, e ) ) - return; + if (args[i].IndexOf(' ') >= 0) + { + sb.Append('"'); + sb.Append(args[i]); + sb.Append('"'); + } + else + { + sb.Append(args[i]); + } + } - bool flushToLog = false; + return sb.ToString(); + } - if ( obj is ArrayList list ) - { - if ( list.Count > 20 ) - CommandLogging.Enabled = false; - else if ( list.Count == 0 ) - command.LogFailure( "Nothing was found to use this command on." ); + public void RunCommand(Mobile from, object obj, BaseCommand command, string[] args) + { + // try + // { + CommandEventArgs e = new CommandEventArgs(from, command.Commands[0], GenerateArgString(args), args); - command.ExecuteList( e, list ); + if (!command.ValidateArgs(this, e)) + return; - if ( list.Count > 20 ) - { - flushToLog = true; - CommandLogging.Enabled = true; - } - } - else if ( obj != null ) - { - if ( command.ListOptimized ) - { - command.ExecuteList( e, new ArrayList{ obj } ); - } - else - { - command.Execute( e, obj ); - } - } + bool flushToLog = false; - command.Flush( from, flushToLog ); - // } - // catch ( Exception ex ) - // { - // from.SendMessage( ex.Message ); - // } - } + if (obj is ArrayList list) + { + if (list.Count > 20) + CommandLogging.Enabled = false; + else if (list.Count == 0) + command.LogFailure("Nothing was found to use this command on."); - public virtual void Process( Mobile from, BaseCommand command, string[] args ) - { - RunCommand( from, command, args ); - } + command.ExecuteList(e, list); - public virtual void Execute( CommandEventArgs e ) - { - if ( e.Length >= 1 ) - { - Commands.TryGetValue( e.GetString( 0 ), out BaseCommand command ); + if (list.Count > 20) + { + flushToLog = true; + CommandLogging.Enabled = true; + } + } + else if (obj != null) + { + if (command.ListOptimized) + command.ExecuteList(e, new ArrayList { obj }); + else + command.Execute(e, obj); + } - if ( command == null ) - { - e.Mobile.SendMessage( "That is either an invalid command name or one that does not support this modifier." ); - } - else if ( e.Mobile.AccessLevel < command.AccessLevel ) - { - e.Mobile.SendMessage( "You do not have access to that command." ); - } - else - { - string[] oldArgs = e.Arguments; - string[] args = new string[oldArgs.Length - 1]; + command.Flush(from, flushToLog); + // } + // catch ( Exception ex ) + // { + // from.SendMessage( ex.Message ); + // } + } - for ( int i = 0; i < args.Length; ++i ) - args[i] = oldArgs[i + 1]; + public virtual void Process(Mobile from, BaseCommand command, string[] args) + { + RunCommand(from, command, args); + } - Process( e.Mobile, command, args ); - } - } - else - { - e.Mobile.SendMessage( "You must supply a command name." ); - } - } + public virtual void Execute(CommandEventArgs e) + { + if (e.Length >= 1) + { + Commands.TryGetValue(e.GetString(0), out BaseCommand command); - public void Register() - { - if ( Accessors == null ) - return; + if (command == null) + { + e.Mobile.SendMessage( + "That is either an invalid command name or one that does not support this modifier."); + } + else if (e.Mobile.AccessLevel < command.AccessLevel) + { + e.Mobile.SendMessage("You do not have access to that command."); + } + else + { + string[] oldArgs = e.Arguments; + string[] args = new string[oldArgs.Length - 1]; - for ( int i = 0; i < Accessors.Length; ++i ) - CommandSystem.Register( Accessors[i], AccessLevel, Execute ); - } + for (int i = 0; i < args.Length; ++i) + args[i] = oldArgs[i + 1]; - public static void Register( BaseCommandImplementor impl ) - { - m_Implementors.Add( impl ); - impl.Register(); - } + Process(e.Mobile, command, args); + } + } + else + { + e.Mobile.SendMessage("You must supply a command name."); + } + } - private static List m_Implementors; + public void Register() + { + if (Accessors == null) + return; - public static List Implementors - { - get - { - if ( m_Implementors == null ) - { - m_Implementors = new List(); - RegisterImplementors(); - } + for (int i = 0; i < Accessors.Length; ++i) + CommandSystem.Register(Accessors[i], AccessLevel, Execute); + } - return m_Implementors; - } - } - } -} + public static void Register(BaseCommandImplementor impl) + { + m_Implementors.Add(impl); + impl.Register(); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/ContainedCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/ContainedCommandImplementor.cs index fef2b3fd3..82a294cc2 100644 --- a/Scripts/Commands/Generic/Implementors/ContainedCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/ContainedCommandImplementor.cs @@ -5,80 +5,76 @@ using Server.Targeting; namespace Server.Commands.Generic { - public class ContainedCommandImplementor : BaseCommandImplementor - { - public ContainedCommandImplementor() - { - Accessors = new[]{ "Contained" }; - SupportRequirement = CommandSupport.Contained; - AccessLevel = AccessLevel.GameMaster; - Usage = "Contained [condition]"; - Description = "Invokes the command on all child items in a targeted container. Optional condition arguments can further restrict the set of objects."; - } + public class ContainedCommandImplementor : BaseCommandImplementor + { + public ContainedCommandImplementor() + { + Accessors = new[] { "Contained" }; + SupportRequirement = CommandSupport.Contained; + AccessLevel = AccessLevel.GameMaster; + Usage = "Contained [condition]"; + Description = + "Invokes the command on all child items in a targeted container. Optional condition arguments can further restrict the set of objects."; + } - public override void Process( Mobile from, BaseCommand command, string[] args ) - { - if ( command.ValidateArgs( this, new CommandEventArgs( from, command.Commands[0], GenerateArgString( args ), args ) ) ) - from.BeginTarget( -1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, new TargetStateCallback( OnTarget ), new object[]{ command, args } ); - } + public override void Process(Mobile from, BaseCommand command, string[] args) + { + if (command.ValidateArgs(this, new CommandEventArgs(from, command.Commands[0], GenerateArgString(args), args))) + from.BeginTarget(-1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, + new TargetStateCallback(OnTarget), new object[] { command, args }); + } - public void OnTarget( Mobile from, object targeted, object state ) - { - if ( !BaseCommand.IsAccessible( from, targeted ) ) - { - from.SendMessage( "That is not accessible." ); - return; - } + public void OnTarget(Mobile from, object targeted, object state) + { + if (!BaseCommand.IsAccessible(from, targeted)) + { + from.SendMessage("That is not accessible."); + return; + } - object[] states = (object[])state; - BaseCommand command = (BaseCommand)states[0]; - string[] args = (string[])states[1]; + object[] states = (object[])state; + BaseCommand command = (BaseCommand)states[0]; + string[] args = (string[])states[1]; - if ( command.ObjectTypes == ObjectTypes.Mobiles ) - return; // sanity check + if (command.ObjectTypes == ObjectTypes.Mobiles) + return; // sanity check - if ( !(targeted is Container) ) - { - from.SendMessage( "That is not a container." ); - } - else - { - try - { - Extensions ext = Extensions.Parse( from, ref args ); + if (!(targeted is Container)) + from.SendMessage("That is not a container."); + else + try + { + Extensions ext = Extensions.Parse(from, ref args); - bool items, mobiles; + bool items, mobiles; - if ( !CheckObjectTypes( from, command, ext, out items, out mobiles ) ) - return; + if (!CheckObjectTypes(from, command, ext, out items, out mobiles)) + return; - if ( !items ) - { - from.SendMessage( "This command only works on items." ); - return; - } + if (!items) + { + from.SendMessage("This command only works on items."); + return; + } - Container cont = (Container)targeted; + Container cont = (Container)targeted; - Item[] found = cont.FindItemsByType( typeof( Item ), true ); + Item[] found = cont.FindItemsByType(typeof(Item), true); - ArrayList list = new ArrayList(); + ArrayList list = new ArrayList(); - for ( int i = 0; i < found.Length; ++i ) - { - if ( ext.IsValid( found[i] ) ) - list.Add( found[i] ); - } + for (int i = 0; i < found.Length; ++i) + if (ext.IsValid(found[i])) + list.Add(found[i]); - ext.Filter( list ); + ext.Filter(list); - RunCommand( from, list, command, args ); - } - catch ( Exception e ) - { - from.SendMessage( e.Message ); - } - } - } - } + RunCommand(from, list, command, args); + } + catch (Exception e) + { + from.SendMessage(e.Message); + } + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/FacetCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/FacetCommandImplementor.cs index cfa3aa878..fca6cef90 100644 --- a/Scripts/Commands/Generic/Implementors/FacetCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/FacetCommandImplementor.cs @@ -1,30 +1,32 @@ namespace Server.Commands.Generic { - public class FacetCommandImplementor : BaseCommandImplementor - { - public FacetCommandImplementor() - { - Accessors = new[]{ "Facet" }; - SupportRequirement = CommandSupport.Area; - SupportsConditionals = true; - AccessLevel = AccessLevel.GameMaster; - Usage = "Facet [condition]"; - Description = "Invokes the command on all appropriate objects within your facet's map bounds. Optional condition arguments can further restrict the set of objects."; - } + public class FacetCommandImplementor : BaseCommandImplementor + { + public FacetCommandImplementor() + { + Accessors = new[] { "Facet" }; + SupportRequirement = CommandSupport.Area; + SupportsConditionals = true; + AccessLevel = AccessLevel.GameMaster; + Usage = "Facet [condition]"; + Description = + "Invokes the command on all appropriate objects within your facet's map bounds. Optional condition arguments can further restrict the set of objects."; + } - public override void Process( Mobile from, BaseCommand command, string[] args ) - { - AreaCommandImplementor impl = AreaCommandImplementor.Instance; + public override void Process(Mobile from, BaseCommand command, string[] args) + { + AreaCommandImplementor impl = AreaCommandImplementor.Instance; - if ( impl == null ) - return; + if (impl == null) + return; - Map map = from.Map; + Map map = from.Map; - if ( map == null || map == Map.Internal ) - return; + if (map == null || map == Map.Internal) + return; - impl.OnTarget( from, map, Point3D.Zero, new Point3D( map.Width - 1, map.Height - 1, 0 ), new object[] { command, args } ); - } - } -} + impl.OnTarget(from, map, Point3D.Zero, new Point3D(map.Width - 1, map.Height - 1, 0), + new object[] { command, args }); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/GlobalCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/GlobalCommandImplementor.cs index d33a19bd4..813b132cf 100644 --- a/Scripts/Commands/Generic/Implementors/GlobalCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/GlobalCommandImplementor.cs @@ -3,57 +3,50 @@ using System.Collections; namespace Server.Commands.Generic { - public class GlobalCommandImplementor : BaseCommandImplementor - { - public GlobalCommandImplementor() - { - Accessors = new[]{ "Global" }; - SupportRequirement = CommandSupport.Global; - SupportsConditionals = true; - AccessLevel = AccessLevel.Administrator; - Usage = "Global [condition]"; - Description = "Invokes the command on all appropriate objects in the world. Optional condition arguments can further restrict the set of objects."; - } + public class GlobalCommandImplementor : BaseCommandImplementor + { + public GlobalCommandImplementor() + { + Accessors = new[] { "Global" }; + SupportRequirement = CommandSupport.Global; + SupportsConditionals = true; + AccessLevel = AccessLevel.Administrator; + Usage = "Global [condition]"; + Description = + "Invokes the command on all appropriate objects in the world. Optional condition arguments can further restrict the set of objects."; + } - public override void Compile( Mobile from, BaseCommand command, ref string[] args, ref object obj ) - { - try - { - Extensions ext = Extensions.Parse( from, ref args ); + public override void Compile(Mobile from, BaseCommand command, ref string[] args, ref object obj) + { + try + { + Extensions ext = Extensions.Parse(from, ref args); - bool items, mobiles; + bool items, mobiles; - if ( !CheckObjectTypes( from, command, ext, out items, out mobiles ) ) - return; + if (!CheckObjectTypes(from, command, ext, out items, out mobiles)) + return; - ArrayList list = new ArrayList(); + ArrayList list = new ArrayList(); - if ( items ) - { - foreach ( Item item in World.Items.Values ) - { - if ( ext.IsValid( item ) ) - list.Add( item ); - } - } + if (items) + foreach (Item item in World.Items.Values) + if (ext.IsValid(item)) + list.Add(item); - if ( mobiles ) - { - foreach ( Mobile mob in World.Mobiles.Values ) - { - if ( ext.IsValid( mob ) ) - list.Add( mob ); - } - } + if (mobiles) + foreach (Mobile mob in World.Mobiles.Values) + if (ext.IsValid(mob)) + list.Add(mob); - ext.Filter( list ); + ext.Filter(list); - obj = list; - } - catch ( Exception ex ) - { - from.SendMessage( ex.Message ); - } - } - } + obj = list; + } + catch (Exception ex) + { + from.SendMessage(ex.Message); + } + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/IPAddressCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/IPAddressCommandImplementor.cs index b32a1d8a6..119f56450 100644 --- a/Scripts/Commands/Generic/Implementors/IPAddressCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/IPAddressCommandImplementor.cs @@ -1,63 +1,65 @@ using System; using System.Collections; +using System.Collections.Generic; using Server.Network; namespace Server.Commands.Generic { - public class IPAddressCommandImplementor : BaseCommandImplementor - { - public IPAddressCommandImplementor() - { - Accessors = new[]{ "IPAddress" }; - SupportRequirement = CommandSupport.IPAddress; - SupportsConditionals = true; - AccessLevel = AccessLevel.Administrator; - Usage = "IPAddress [condition]"; - Description = "Invokes the command on one mobile from each IP address that is logged in. Optional condition arguments can further restrict the set of objects."; - } + public class IPAddressCommandImplementor : BaseCommandImplementor + { + public IPAddressCommandImplementor() + { + Accessors = new[] { "IPAddress" }; + SupportRequirement = CommandSupport.IPAddress; + SupportsConditionals = true; + AccessLevel = AccessLevel.Administrator; + Usage = "IPAddress [condition]"; + Description = + "Invokes the command on one mobile from each IP address that is logged in. Optional condition arguments can further restrict the set of objects."; + } - public override void Compile( Mobile from, BaseCommand command, ref string[] args, ref object obj ) - { - try - { - Extensions ext = Extensions.Parse( from, ref args ); + public override void Compile(Mobile from, BaseCommand command, ref string[] args, ref object obj) + { + try + { + Extensions ext = Extensions.Parse(from, ref args); - bool items, mobiles; + bool items, mobiles; - if ( !CheckObjectTypes( from, command, ext, out items, out mobiles ) ) - return; + if (!CheckObjectTypes(from, command, ext, out items, out mobiles)) + return; - if ( !mobiles ) // sanity check - { - command.LogFailure( "This command does not support items." ); - return; - } + if (!mobiles) // sanity check + { + command.LogFailure("This command does not support items."); + return; + } - ArrayList list = new ArrayList(); - ArrayList addresses = new ArrayList(); + ArrayList list = new ArrayList(); + ArrayList addresses = new ArrayList(); - System.Collections.Generic.List states = NetState.Instances; + List states = NetState.Instances; - for ( int i = 0; i < states.Count; ++i ) - { - NetState ns = (NetState)states[i]; - Mobile mob = ns.Mobile; + for (int i = 0; i < states.Count; ++i) + { + NetState ns = states[i]; + Mobile mob = ns.Mobile; - if ( mob != null && !addresses.Contains( ns.Address ) && ext.IsValid( mob ) ) - { - list.Add( mob ); - addresses.Add( ns.Address ); - } - } + if (mob != null && !addresses.Contains(ns.Address) && ext.IsValid(mob)) + { + list.Add(mob); + addresses.Add(ns.Address); + } + } - ext.Filter( list ); + ext.Filter(list); - obj = list; - } - catch ( Exception ex ) - { - from.SendMessage( ex.Message ); - } - } - } + obj = list; + } + catch (Exception ex) + { + from.SendMessage(ex.Message); + } + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/MultiCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/MultiCommandImplementor.cs index f34923456..8e40ecd6e 100644 --- a/Scripts/Commands/Generic/Implementors/MultiCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/MultiCommandImplementor.cs @@ -2,73 +2,76 @@ using Server.Targeting; namespace Server.Commands.Generic { - public class MultiCommandImplementor : BaseCommandImplementor - { - public MultiCommandImplementor() - { - Accessors = new[]{ "Multi", "m" }; - SupportRequirement = CommandSupport.Multi; - AccessLevel = AccessLevel.Counselor; - Usage = "Multi "; - Description = "Invokes the command on multiple targeted objects."; - } + public class MultiCommandImplementor : BaseCommandImplementor + { + public MultiCommandImplementor() + { + Accessors = new[] { "Multi", "m" }; + SupportRequirement = CommandSupport.Multi; + AccessLevel = AccessLevel.Counselor; + Usage = "Multi "; + Description = "Invokes the command on multiple targeted objects."; + } - public override void Process( Mobile from, BaseCommand command, string[] args ) - { - if ( command.ValidateArgs( this, new CommandEventArgs( from, command.Commands[0], GenerateArgString( args ), args ) ) ) - from.BeginTarget( -1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, new TargetStateCallback( OnTarget ), new object[]{ command, args } ); - } + public override void Process(Mobile from, BaseCommand command, string[] args) + { + if (command.ValidateArgs(this, new CommandEventArgs(from, command.Commands[0], GenerateArgString(args), args))) + from.BeginTarget(-1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, + new TargetStateCallback(OnTarget), new object[] { command, args }); + } - public void OnTarget( Mobile from, object targeted, object state ) - { - object[] states = (object[])state; - BaseCommand command = (BaseCommand)states[0]; - string[] args = (string[])states[1]; + public void OnTarget(Mobile from, object targeted, object state) + { + object[] states = (object[])state; + BaseCommand command = (BaseCommand)states[0]; + string[] args = (string[])states[1]; - if ( !BaseCommand.IsAccessible( from, targeted ) ) - { - from.SendMessage( "That is not accessible." ); - from.BeginTarget( -1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, new TargetStateCallback( OnTarget ), new object[]{ command, args } ); - return; - } + if (!BaseCommand.IsAccessible(from, targeted)) + { + from.SendMessage("That is not accessible."); + from.BeginTarget(-1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, + new TargetStateCallback(OnTarget), new object[] { command, args }); + return; + } - switch ( command.ObjectTypes ) - { - case ObjectTypes.Both: - { - if ( !(targeted is Item) && !(targeted is Mobile) ) - { - from.SendMessage( "This command does not work on that." ); - return; - } + switch (command.ObjectTypes) + { + case ObjectTypes.Both: + { + if (!(targeted is Item) && !(targeted is Mobile)) + { + from.SendMessage("This command does not work on that."); + return; + } - break; - } - case ObjectTypes.Items: - { - if ( !(targeted is Item) ) - { - from.SendMessage( "This command only works on items." ); - return; - } + break; + } + case ObjectTypes.Items: + { + if (!(targeted is Item)) + { + from.SendMessage("This command only works on items."); + return; + } - break; - } - case ObjectTypes.Mobiles: - { - if ( !(targeted is Mobile) ) - { - from.SendMessage( "This command only works on mobiles." ); - return; - } + break; + } + case ObjectTypes.Mobiles: + { + if (!(targeted is Mobile)) + { + from.SendMessage("This command only works on mobiles."); + return; + } - break; - } - } + break; + } + } - RunCommand( from, targeted, command, args ); + RunCommand(from, targeted, command, args); - from.BeginTarget( -1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, new TargetStateCallback( OnTarget ), new object[]{ command, args } ); - } - } + from.BeginTarget(-1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, new TargetStateCallback(OnTarget), + new object[] { command, args }); + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/ObjectConditional.cs b/Scripts/Commands/Generic/Implementors/ObjectConditional.cs index 158b60420..1f587b8d9 100644 --- a/Scripts/Commands/Generic/Implementors/ObjectConditional.cs +++ b/Scripts/Commands/Generic/Implementors/ObjectConditional.cs @@ -4,245 +4,247 @@ using CPA = Server.CommandPropertyAttribute; namespace Server.Commands.Generic { - public sealed class ObjectConditional - { - private static readonly Type typeofItem = typeof( Item ); - private static readonly Type typeofMobile = typeof( Mobile ); + public sealed class ObjectConditional + { + private static readonly Type typeofItem = typeof(Item); + private static readonly Type typeofMobile = typeof(Mobile); - private ICondition[][] m_Conditions; + public static readonly ObjectConditional Empty = new ObjectConditional(null, null); - private IConditional[] m_Conditionals; + private IConditional[] m_Conditionals; - public Type Type { get; } + private ICondition[][] m_Conditions; - public bool IsItem => ( Type == null || Type == typeofItem || Type.IsSubclassOf( typeofItem ) ); + public ObjectConditional(Type objectType, ICondition[][] conditions) + { + Type = objectType; + m_Conditions = conditions; + } - public bool IsMobile => ( Type == null || Type == typeofMobile || Type.IsSubclassOf( typeofMobile ) ); + public Type Type{ get; } - public static readonly ObjectConditional Empty = new ObjectConditional( null, null ); + public bool IsItem => Type == null || Type == typeofItem || Type.IsSubclassOf(typeofItem); - public bool HasCompiled => ( m_Conditionals != null ); + public bool IsMobile => Type == null || Type == typeofMobile || Type.IsSubclassOf(typeofMobile); - public void Compile( ref AssemblyEmitter emitter ) - { - if ( emitter == null ) - emitter = new AssemblyEmitter( "__dynamic", false ); + public bool HasCompiled => m_Conditionals != null; - m_Conditionals = new IConditional[m_Conditions.Length]; + public void Compile(ref AssemblyEmitter emitter) + { + if (emitter == null) + emitter = new AssemblyEmitter("__dynamic", false); - for ( int i = 0; i < m_Conditionals.Length; ++i ) - m_Conditionals[i] = ConditionalCompiler.Compile( emitter, Type, m_Conditions[i], i ); - } + m_Conditionals = new IConditional[m_Conditions.Length]; - public bool CheckCondition( object obj ) - { - if ( Type == null ) - return true; // null type means no condition + for (int i = 0; i < m_Conditionals.Length; ++i) + m_Conditionals[i] = ConditionalCompiler.Compile(emitter, Type, m_Conditions[i], i); + } - if ( !HasCompiled ) - { - AssemblyEmitter emitter = null; + public bool CheckCondition(object obj) + { + if (Type == null) + return true; // null type means no condition - Compile( ref emitter ); - } + if (!HasCompiled) + { + AssemblyEmitter emitter = null; - for ( int i = 0; i < m_Conditionals.Length; ++i ) - { - if ( m_Conditionals[i].Verify( obj ) ) - return true; - } + Compile(ref emitter); + } - return false; // all conditions false - } + for (int i = 0; i < m_Conditionals.Length; ++i) + if (m_Conditionals[i].Verify(obj)) + return true; - public static ObjectConditional Parse( Mobile from, ref string[] args ) - { - string[] conditionArgs = null; + return false; // all conditions false + } - for ( int i = 0; i < args.Length; ++i ) - { - if ( Insensitive.Equals( args[i], "where" ) ) - { - string[] origArgs = args; + public static ObjectConditional Parse(Mobile from, ref string[] args) + { + string[] conditionArgs = null; - args = new string[i]; + for (int i = 0; i < args.Length; ++i) + if (Insensitive.Equals(args[i], "where")) + { + string[] origArgs = args; - for ( int j = 0; j < args.Length; ++j ) - args[j] = origArgs[j]; + args = new string[i]; - conditionArgs = new string[origArgs.Length - i - 1]; + for (int j = 0; j < args.Length; ++j) + args[j] = origArgs[j]; - for ( int j = 0; j < conditionArgs.Length; ++j ) - conditionArgs[j] = origArgs[i + j + 1]; + conditionArgs = new string[origArgs.Length - i - 1]; - break; - } - } + for (int j = 0; j < conditionArgs.Length; ++j) + conditionArgs[j] = origArgs[i + j + 1]; - return ParseDirect( from, conditionArgs, 0, conditionArgs.Length ); - } + break; + } - public static ObjectConditional ParseDirect( Mobile from, string[] args, int offset, int size ) - { - if ( args == null || size == 0 ) - return Empty; + return ParseDirect(from, conditionArgs, 0, conditionArgs.Length); + } - int index = 0; + public static ObjectConditional ParseDirect(Mobile from, string[] args, int offset, int size) + { + if (args == null || size == 0) + return Empty; - Type objectType = ScriptCompiler.FindTypeByName( args[offset + index], true ); + int index = 0; - if ( objectType == null ) - throw new Exception($"No type with that name ({args[offset + index]}) was found."); + Type objectType = ScriptCompiler.FindTypeByName(args[offset + index], true); - ++index; + if (objectType == null) + throw new Exception($"No type with that name ({args[offset + index]}) was found."); - List conditions = new List(); - List current = new List(); + ++index; - current.Add( TypeCondition.Default ); + List conditions = new List(); + List current = new List(); - while ( index < size ) - { - string cur = args[offset + index]; + current.Add(TypeCondition.Default); - bool inverse = false; + while (index < size) + { + string cur = args[offset + index]; - if ( Insensitive.Equals( cur, "not" ) || cur == "!" ) - { - inverse = true; - ++index; + bool inverse = false; - if ( index >= size ) - throw new Exception( "Improperly formatted object conditional." ); - } - else if ( Insensitive.Equals( cur, "or" ) || cur == "||" ) - { - if ( current.Count > 1 ) - { - conditions.Add( current.ToArray() ); + if (Insensitive.Equals(cur, "not") || cur == "!") + { + inverse = true; + ++index; - current.Clear(); - current.Add( TypeCondition.Default ); - } + if (index >= size) + throw new Exception("Improperly formatted object conditional."); + } + else if (Insensitive.Equals(cur, "or") || cur == "||") + { + if (current.Count > 1) + { + conditions.Add(current.ToArray()); - ++index; + current.Clear(); + current.Add(TypeCondition.Default); + } - continue; - } + ++index; - string binding = args[offset + index]; - index++; + continue; + } - if ( index >= size ) - throw new Exception( "Improperly formatted object conditional." ); + string binding = args[offset + index]; + index++; - string oper = args[offset + index]; - index++; + if (index >= size) + throw new Exception("Improperly formatted object conditional."); - if ( index >= size ) - throw new Exception( "Improperly formatted object conditional." ); + string oper = args[offset + index]; + index++; - string val = args[offset + index]; - index++; + if (index >= size) + throw new Exception("Improperly formatted object conditional."); - Property prop = new Property( binding ); + string val = args[offset + index]; + index++; - prop.BindTo( objectType, PropertyAccess.Read ); - prop.CheckAccess( from ); + Property prop = new Property(binding); - ICondition condition = null; + prop.BindTo(objectType, PropertyAccess.Read); + prop.CheckAccess(from); - switch ( oper ) - { - #region Equality - case "=": - case "==": - case "is": - condition = new ComparisonCondition( prop, inverse, ComparisonOperator.Equal, val ); - break; + ICondition condition = null; - case "!=": - condition = new ComparisonCondition( prop, inverse, ComparisonOperator.NotEqual, val ); - break; - #endregion + switch (oper) + { + #region Equality - #region Relational - case ">": - condition = new ComparisonCondition( prop, inverse, ComparisonOperator.Greater, val ); - break; + case "=": + case "==": + case "is": + condition = new ComparisonCondition(prop, inverse, ComparisonOperator.Equal, val); + break; - case "<": - condition = new ComparisonCondition( prop, inverse, ComparisonOperator.Lesser, val ); - break; + case "!=": + condition = new ComparisonCondition(prop, inverse, ComparisonOperator.NotEqual, val); + break; - case ">=": - condition = new ComparisonCondition( prop, inverse, ComparisonOperator.GreaterEqual, val ); - break; + #endregion - case "<=": - condition = new ComparisonCondition( prop, inverse, ComparisonOperator.LesserEqual, val ); - break; - #endregion + #region Relational - #region Strings - case "==~": - case "~==": - case "=~": - case "~=": - case "is~": - case "~is": - condition = new StringCondition( prop, inverse, StringOperator.Equal, val, true ); - break; + case ">": + condition = new ComparisonCondition(prop, inverse, ComparisonOperator.Greater, val); + break; - case "!=~": - case "~!=": - condition = new StringCondition( prop, inverse, StringOperator.NotEqual, val, true ); - break; + case "<": + condition = new ComparisonCondition(prop, inverse, ComparisonOperator.Lesser, val); + break; - case "starts": - condition = new StringCondition( prop, inverse, StringOperator.StartsWith, val, false ); - break; + case ">=": + condition = new ComparisonCondition(prop, inverse, ComparisonOperator.GreaterEqual, val); + break; - case "starts~": - case "~starts": - condition = new StringCondition( prop, inverse, StringOperator.StartsWith, val, true ); - break; + case "<=": + condition = new ComparisonCondition(prop, inverse, ComparisonOperator.LesserEqual, val); + break; - case "ends": - condition = new StringCondition( prop, inverse, StringOperator.EndsWith, val, false ); - break; + #endregion - case "ends~": - case "~ends": - condition = new StringCondition( prop, inverse, StringOperator.EndsWith, val, true ); - break; + #region Strings - case "contains": - condition = new StringCondition( prop, inverse, StringOperator.Contains, val, false ); - break; + case "==~": + case "~==": + case "=~": + case "~=": + case "is~": + case "~is": + condition = new StringCondition(prop, inverse, StringOperator.Equal, val, true); + break; - case "contains~": - case "~contains": - condition = new StringCondition( prop, inverse, StringOperator.Contains, val, true ); - break; - #endregion - } + case "!=~": + case "~!=": + condition = new StringCondition(prop, inverse, StringOperator.NotEqual, val, true); + break; - if ( condition == null ) - throw new InvalidOperationException($"Unrecognized operator (\"{oper}\")."); + case "starts": + condition = new StringCondition(prop, inverse, StringOperator.StartsWith, val, false); + break; - current.Add( condition ); - } + case "starts~": + case "~starts": + condition = new StringCondition(prop, inverse, StringOperator.StartsWith, val, true); + break; - conditions.Add( current.ToArray() ); + case "ends": + condition = new StringCondition(prop, inverse, StringOperator.EndsWith, val, false); + break; - return new ObjectConditional( objectType, conditions.ToArray() ); - } + case "ends~": + case "~ends": + condition = new StringCondition(prop, inverse, StringOperator.EndsWith, val, true); + break; - public ObjectConditional( Type objectType, ICondition[][] conditions ) - { - Type = objectType; - m_Conditions = conditions; - } - } + case "contains": + condition = new StringCondition(prop, inverse, StringOperator.Contains, val, false); + break; + + case "contains~": + case "~contains": + condition = new StringCondition(prop, inverse, StringOperator.Contains, val, true); + break; + + #endregion + } + + if (condition == null) + throw new InvalidOperationException($"Unrecognized operator (\"{oper}\")."); + + current.Add(condition); + } + + conditions.Add(current.ToArray()); + + return new ObjectConditional(objectType, conditions.ToArray()); + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/OnlineCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/OnlineCommandImplementor.cs index 288783059..f07cf8dba 100644 --- a/Scripts/Commands/Generic/Implementors/OnlineCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/OnlineCommandImplementor.cs @@ -5,62 +5,63 @@ using Server.Network; namespace Server.Commands.Generic { - public class OnlineCommandImplementor : BaseCommandImplementor - { - public OnlineCommandImplementor() - { - Accessors = new[]{ "Online" }; - SupportRequirement = CommandSupport.Online; - SupportsConditionals = true; - AccessLevel = AccessLevel.GameMaster; - Usage = "Online [condition]"; - Description = "Invokes the command on all mobiles that are currently logged in. Optional condition arguments can further restrict the set of objects."; - } + public class OnlineCommandImplementor : BaseCommandImplementor + { + public OnlineCommandImplementor() + { + Accessors = new[] { "Online" }; + SupportRequirement = CommandSupport.Online; + SupportsConditionals = true; + AccessLevel = AccessLevel.GameMaster; + Usage = "Online [condition]"; + Description = + "Invokes the command on all mobiles that are currently logged in. Optional condition arguments can further restrict the set of objects."; + } - public override void Compile( Mobile from, BaseCommand command, ref string[] args, ref object obj ) - { - try - { - Extensions ext = Extensions.Parse( from, ref args ); + public override void Compile(Mobile from, BaseCommand command, ref string[] args, ref object obj) + { + try + { + Extensions ext = Extensions.Parse(from, ref args); - bool items, mobiles; + bool items, mobiles; - if ( !CheckObjectTypes( from, command, ext, out items, out mobiles ) ) - return; + if (!CheckObjectTypes(from, command, ext, out items, out mobiles)) + return; - if ( !mobiles ) // sanity check - { - command.LogFailure( "This command does not support items." ); - return; - } + if (!mobiles) // sanity check + { + command.LogFailure("This command does not support items."); + return; + } - ArrayList list = new ArrayList(); + ArrayList list = new ArrayList(); - List states = NetState.Instances; + List states = NetState.Instances; - for ( int i = 0; i < states.Count; ++i ) - { - NetState ns = states[i]; - Mobile mob = ns.Mobile; + for (int i = 0; i < states.Count; ++i) + { + NetState ns = states[i]; + Mobile mob = ns.Mobile; - if ( mob == null ) - continue; + if (mob == null) + continue; - if ( !BaseCommand.IsAccessible( from, mob ) ) - continue; + if (!BaseCommand.IsAccessible(from, mob)) + continue; - if ( ext.IsValid( mob ) ) - list.Add( mob ); - } + if (ext.IsValid(mob)) + list.Add(mob); + } - ext.Filter( list ); + ext.Filter(list); - obj = list; - } - catch ( Exception ex ) - { - from.SendMessage( ex.Message ); - } - } - } -} + obj = list; + } + catch (Exception ex) + { + from.SendMessage(ex.Message); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/RangeCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/RangeCommandImplementor.cs index 30aaccef8..1e7257817 100644 --- a/Scripts/Commands/Generic/Implementors/RangeCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/RangeCommandImplementor.cs @@ -1,77 +1,79 @@ namespace Server.Commands.Generic { - public class RangeCommandImplementor : BaseCommandImplementor - { - public static RangeCommandImplementor Instance { get; private set; } + public class RangeCommandImplementor : BaseCommandImplementor + { + public RangeCommandImplementor() + { + Accessors = new[] { "Range" }; + SupportRequirement = CommandSupport.Area; + SupportsConditionals = true; + AccessLevel = AccessLevel.GameMaster; + Usage = "Range [condition]"; + Description = + "Invokes the command on all appropriate objects within a specified range of you. Optional condition arguments can further restrict the set of objects."; - public RangeCommandImplementor() - { - Accessors = new[]{ "Range" }; - SupportRequirement = CommandSupport.Area; - SupportsConditionals = true; - AccessLevel = AccessLevel.GameMaster; - Usage = "Range [condition]"; - Description = "Invokes the command on all appropriate objects within a specified range of you. Optional condition arguments can further restrict the set of objects."; + Instance = this; + } - Instance = this; - } + public static RangeCommandImplementor Instance{ get; private set; } - public override void Execute( CommandEventArgs e ) - { - if ( e.Length >= 2 ) - { - int range = e.GetInt32( 0 ); + public override void Execute(CommandEventArgs e) + { + if (e.Length >= 2) + { + int range = e.GetInt32(0); - if ( range < 0 ) - { - e.Mobile.SendMessage( "The range must not be negative." ); - } - else - { - Commands.TryGetValue( e.GetString( 1 ), out BaseCommand command ); + if (range < 0) + { + e.Mobile.SendMessage("The range must not be negative."); + } + else + { + Commands.TryGetValue(e.GetString(1), out BaseCommand command); - if ( command == null ) - { - e.Mobile.SendMessage( "That is either an invalid command name or one that does not support this modifier." ); - } - else if ( e.Mobile.AccessLevel < command.AccessLevel ) - { - e.Mobile.SendMessage( "You do not have access to that command." ); - } - else - { - string[] oldArgs = e.Arguments; - string[] args = new string[oldArgs.Length - 2]; + if (command == null) + { + e.Mobile.SendMessage( + "That is either an invalid command name or one that does not support this modifier."); + } + else if (e.Mobile.AccessLevel < command.AccessLevel) + { + e.Mobile.SendMessage("You do not have access to that command."); + } + else + { + string[] oldArgs = e.Arguments; + string[] args = new string[oldArgs.Length - 2]; - for ( int i = 0; i < args.Length; ++i ) - args[i] = oldArgs[i + 2]; + for (int i = 0; i < args.Length; ++i) + args[i] = oldArgs[i + 2]; - Process( range, e.Mobile, command, args ); - } - } - } - else - { - e.Mobile.SendMessage( "You must supply a range and a command name." ); - } - } + Process(range, e.Mobile, command, args); + } + } + } + else + { + e.Mobile.SendMessage("You must supply a range and a command name."); + } + } - public void Process( int range, Mobile from, BaseCommand command, string[] args ) - { - AreaCommandImplementor impl = AreaCommandImplementor.Instance; + public void Process(int range, Mobile from, BaseCommand command, string[] args) + { + AreaCommandImplementor impl = AreaCommandImplementor.Instance; - if ( impl == null ) - return; + if (impl == null) + return; - Map map = from.Map; + Map map = from.Map; - if ( map == null || map == Map.Internal ) - return; + if (map == null || map == Map.Internal) + return; - Point3D start = new Point3D( from.X - range, from.Y - range, from.Z ); - Point3D end = new Point3D( from.X + range, from.Y + range, from.Z ); + Point3D start = new Point3D(from.X - range, from.Y - range, from.Z); + Point3D end = new Point3D(from.X + range, from.Y + range, from.Z); - impl.OnTarget( from, map, start, end, new object[] { command, args } ); - } - } -} + impl.OnTarget(from, map, start, end, new object[] { command, args }); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/RegionCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/RegionCommandImplementor.cs index 4ea40bc9c..657072758 100644 --- a/Scripts/Commands/Generic/Implementors/RegionCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/RegionCommandImplementor.cs @@ -3,58 +3,59 @@ using System.Collections; namespace Server.Commands.Generic { - public class RegionCommandImplementor : BaseCommandImplementor - { - public RegionCommandImplementor() - { - Accessors = new[]{ "Region" }; - SupportRequirement = CommandSupport.Region; - SupportsConditionals = true; - AccessLevel = AccessLevel.GameMaster; - Usage = "Region [condition]"; - Description = "Invokes the command on all appropriate mobiles in your current region. Optional condition arguments can further restrict the set of objects."; - } + public class RegionCommandImplementor : BaseCommandImplementor + { + public RegionCommandImplementor() + { + Accessors = new[] { "Region" }; + SupportRequirement = CommandSupport.Region; + SupportsConditionals = true; + AccessLevel = AccessLevel.GameMaster; + Usage = "Region [condition]"; + Description = + "Invokes the command on all appropriate mobiles in your current region. Optional condition arguments can further restrict the set of objects."; + } - public override void Compile( Mobile from, BaseCommand command, ref string[] args, ref object obj ) - { - try - { - Extensions ext = Extensions.Parse( from, ref args ); + public override void Compile(Mobile from, BaseCommand command, ref string[] args, ref object obj) + { + try + { + Extensions ext = Extensions.Parse(from, ref args); - bool items, mobiles; + bool items, mobiles; - if ( !CheckObjectTypes( from, command, ext, out items, out mobiles ) ) - return; + if (!CheckObjectTypes(from, command, ext, out items, out mobiles)) + return; - Region reg = from.Region; + Region reg = from.Region; - ArrayList list = new ArrayList(); + ArrayList list = new ArrayList(); - if ( mobiles ) - { - foreach ( Mobile mob in reg.GetMobiles() ) - { - if ( !BaseCommand.IsAccessible( from, mob ) ) - continue; + if (mobiles) + { + foreach (Mobile mob in reg.GetMobiles()) + { + if (!BaseCommand.IsAccessible(from, mob)) + continue; - if ( ext.IsValid( mob ) ) - list.Add( mob ); - } - } - else - { - command.LogFailure( "This command does not support items." ); - return; - } + if (ext.IsValid(mob)) + list.Add(mob); + } + } + else + { + command.LogFailure("This command does not support items."); + return; + } - ext.Filter( list ); + ext.Filter(list); - obj = list; - } - catch ( Exception ex ) - { - from.SendMessage( ex.Message ); - } - } - } -} + obj = list; + } + catch (Exception ex) + { + from.SendMessage(ex.Message); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/ScreenCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/ScreenCommandImplementor.cs index 4ad640c52..134a4922b 100644 --- a/Scripts/Commands/Generic/Implementors/ScreenCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/ScreenCommandImplementor.cs @@ -1,22 +1,23 @@ namespace Server.Commands.Generic { - public class ScreenCommandImplementor : BaseCommandImplementor - { - public ScreenCommandImplementor() - { - Accessors = new[]{ "Screen" }; - SupportRequirement = CommandSupport.Area; - SupportsConditionals = true; - AccessLevel = AccessLevel.GameMaster; - Usage = "Screen [condition]"; - Description = "Invokes the command on all appropriate objects in your screen. Optional condition arguments can further restrict the set of objects."; - } + public class ScreenCommandImplementor : BaseCommandImplementor + { + public ScreenCommandImplementor() + { + Accessors = new[] { "Screen" }; + SupportRequirement = CommandSupport.Area; + SupportsConditionals = true; + AccessLevel = AccessLevel.GameMaster; + Usage = "Screen [condition]"; + Description = + "Invokes the command on all appropriate objects in your screen. Optional condition arguments can further restrict the set of objects."; + } - public override void Process( Mobile from, BaseCommand command, string[] args ) - { - RangeCommandImplementor impl = RangeCommandImplementor.Instance; + public override void Process(Mobile from, BaseCommand command, string[] args) + { + RangeCommandImplementor impl = RangeCommandImplementor.Instance; - impl?.Process( 18, from, command, args ); - } - } -} + impl?.Process(18, from, command, args); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/SelfCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/SelfCommandImplementor.cs index 6d38795ae..a3c2deafb 100644 --- a/Scripts/Commands/Generic/Implementors/SelfCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/SelfCommandImplementor.cs @@ -1,22 +1,22 @@ namespace Server.Commands.Generic { - public class SelfCommandImplementor : BaseCommandImplementor - { - public SelfCommandImplementor() - { - Accessors = new[]{ "Self" }; - SupportRequirement = CommandSupport.Self; - AccessLevel = AccessLevel.Counselor; - Usage = "Self "; - Description = "Invokes the command on the commanding player."; - } + public class SelfCommandImplementor : BaseCommandImplementor + { + public SelfCommandImplementor() + { + Accessors = new[] { "Self" }; + SupportRequirement = CommandSupport.Self; + AccessLevel = AccessLevel.Counselor; + Usage = "Self "; + Description = "Invokes the command on the commanding player."; + } - public override void Compile( Mobile from, BaseCommand command, ref string[] args, ref object obj ) - { - if ( command.ObjectTypes == ObjectTypes.Items ) - return; // sanity check + public override void Compile(Mobile from, BaseCommand command, ref string[] args, ref object obj) + { + if (command.ObjectTypes == ObjectTypes.Items) + return; // sanity check - obj = from; - } - } + obj = from; + } + } } \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/SerialCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/SerialCommandImplementor.cs index 468ea306a..b300dd679 100644 --- a/Scripts/Commands/Generic/Implementors/SerialCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/SerialCommandImplementor.cs @@ -1,95 +1,96 @@ namespace Server.Commands.Generic { - public class SerialCommandImplementor : BaseCommandImplementor - { - public SerialCommandImplementor() - { - Accessors = new[]{ "Serial" }; - SupportRequirement = CommandSupport.Single; - AccessLevel = AccessLevel.Counselor; - Usage = "Serial "; - Description = "Invokes the command on a single object by serial."; - } + public class SerialCommandImplementor : BaseCommandImplementor + { + public SerialCommandImplementor() + { + Accessors = new[] { "Serial" }; + SupportRequirement = CommandSupport.Single; + AccessLevel = AccessLevel.Counselor; + Usage = "Serial "; + Description = "Invokes the command on a single object by serial."; + } - public override void Execute( CommandEventArgs e ) - { - if ( e.Length >= 2 ) - { - Serial serial = e.GetInt32( 0 ); + public override void Execute(CommandEventArgs e) + { + if (e.Length >= 2) + { + Serial serial = e.GetInt32(0); - object obj = null; + object obj = null; - if ( serial.IsItem ) - obj = World.FindItem( serial ); - else if ( serial.IsMobile ) - obj = World.FindMobile( serial ); + if (serial.IsItem) + obj = World.FindItem(serial); + else if (serial.IsMobile) + obj = World.FindMobile(serial); - if ( obj == null ) - { - e.Mobile.SendMessage( "That is not a valid serial." ); - } - else - { - Commands.TryGetValue( e.GetString( 1 ), out BaseCommand command ); + if (obj == null) + { + e.Mobile.SendMessage("That is not a valid serial."); + } + else + { + Commands.TryGetValue(e.GetString(1), out BaseCommand command); - if ( command == null ) - { - e.Mobile.SendMessage( "That is either an invalid command name or one that does not support this modifier." ); - } - else if ( e.Mobile.AccessLevel < command.AccessLevel ) - { - e.Mobile.SendMessage( "You do not have access to that command." ); - } - else - { - switch ( command.ObjectTypes ) - { - case ObjectTypes.Both: - { - if ( !(obj is Item) && !(obj is Mobile) ) - { - e.Mobile.SendMessage( "This command does not work on that." ); - return; - } + if (command == null) + { + e.Mobile.SendMessage( + "That is either an invalid command name or one that does not support this modifier."); + } + else if (e.Mobile.AccessLevel < command.AccessLevel) + { + e.Mobile.SendMessage("You do not have access to that command."); + } + else + { + switch (command.ObjectTypes) + { +// case ObjectTypes.Both: +// { +// if (!(obj is Item) && !(obj is Mobile)) +// { +// e.Mobile.SendMessage("This command does not work on that."); +// return; +// } +// +// break; +// } + case ObjectTypes.Items: + { + if (!(obj is Item)) + { + e.Mobile.SendMessage("This command only works on items."); + return; + } - break; - } - case ObjectTypes.Items: - { - if ( !(obj is Item) ) - { - e.Mobile.SendMessage( "This command only works on items." ); - return; - } + break; + } + case ObjectTypes.Mobiles: + { + if (!(obj is Mobile)) + { + e.Mobile.SendMessage("This command only works on mobiles."); + return; + } - break; - } - case ObjectTypes.Mobiles: - { - if ( !(obj is Mobile) ) - { - e.Mobile.SendMessage( "This command only works on mobiles." ); - return; - } + break; + } + } - break; - } - } + string[] oldArgs = e.Arguments; + string[] args = new string[oldArgs.Length - 2]; - string[] oldArgs = e.Arguments; - string[] args = new string[oldArgs.Length - 2]; + for (int i = 0; i < args.Length; ++i) + args[i] = oldArgs[i + 2]; - for ( int i = 0; i < args.Length; ++i ) - args[i] = oldArgs[i + 2]; - - RunCommand( e.Mobile, obj, command, args ); - } - } - } - else - { - e.Mobile.SendMessage( "You must supply an object serial and a command name." ); - } - } - } -} + RunCommand(e.Mobile, obj, command, args); + } + } + } + else + { + e.Mobile.SendMessage("You must supply an object serial and a command name."); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Generic/Implementors/SingleCommandImplementor.cs b/Scripts/Commands/Generic/Implementors/SingleCommandImplementor.cs index c94b01b06..20342ca9a 100644 --- a/Scripts/Commands/Generic/Implementors/SingleCommandImplementor.cs +++ b/Scripts/Commands/Generic/Implementors/SingleCommandImplementor.cs @@ -2,90 +2,92 @@ using Server.Targeting; namespace Server.Commands.Generic { - public class SingleCommandImplementor : BaseCommandImplementor - { - public SingleCommandImplementor() - { - Accessors = new[]{ "Single" }; - SupportRequirement = CommandSupport.Single; - AccessLevel = AccessLevel.Counselor; - Usage = "Single "; - Description = "Invokes the command on a single targeted object. This is the same as just invoking the command directly."; - } + public class SingleCommandImplementor : BaseCommandImplementor + { + public SingleCommandImplementor() + { + Accessors = new[] { "Single" }; + SupportRequirement = CommandSupport.Single; + AccessLevel = AccessLevel.Counselor; + Usage = "Single "; + Description = + "Invokes the command on a single targeted object. This is the same as just invoking the command directly."; + } - public override void Register( BaseCommand command ) - { - base.Register( command ); + public override void Register(BaseCommand command) + { + base.Register(command); - for ( int i = 0; i < command.Commands.Length; ++i ) - CommandSystem.Register( command.Commands[i], command.AccessLevel, Redirect ); - } + for (int i = 0; i < command.Commands.Length; ++i) + CommandSystem.Register(command.Commands[i], command.AccessLevel, Redirect); + } - public void Redirect( CommandEventArgs e ) - { - Commands.TryGetValue( e.Command, out BaseCommand command ); + public void Redirect(CommandEventArgs e) + { + Commands.TryGetValue(e.Command, out BaseCommand command); - if ( command == null ) - e.Mobile.SendMessage( "That is either an invalid command name or one that does not support this modifier." ); - else if ( e.Mobile.AccessLevel < command.AccessLevel ) - e.Mobile.SendMessage( "You do not have access to that command." ); - else if ( command.ValidateArgs( this, e ) ) - Process( e.Mobile, command, e.Arguments ); - } + if (command == null) + e.Mobile.SendMessage("That is either an invalid command name or one that does not support this modifier."); + else if (e.Mobile.AccessLevel < command.AccessLevel) + e.Mobile.SendMessage("You do not have access to that command."); + else if (command.ValidateArgs(this, e)) + Process(e.Mobile, command, e.Arguments); + } - public override void Process( Mobile from, BaseCommand command, string[] args ) - { - if ( command.ValidateArgs( this, new CommandEventArgs( from, command.Commands[0], GenerateArgString( args ), args ) ) ) - from.BeginTarget( -1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, new TargetStateCallback( OnTarget ), new object[]{ command, args } ); - } + public override void Process(Mobile from, BaseCommand command, string[] args) + { + if (command.ValidateArgs(this, new CommandEventArgs(from, command.Commands[0], GenerateArgString(args), args))) + from.BeginTarget(-1, command.ObjectTypes == ObjectTypes.All, TargetFlags.None, + new TargetStateCallback(OnTarget), new object[] { command, args }); + } - public void OnTarget( Mobile from, object targeted, object state ) - { - if ( !BaseCommand.IsAccessible( from, targeted ) ) - { - from.SendMessage( "That is not accessible." ); - return; - } + public void OnTarget(Mobile from, object targeted, object state) + { + if (!BaseCommand.IsAccessible(from, targeted)) + { + from.SendMessage("That is not accessible."); + return; + } - object[] states = (object[])state; - BaseCommand command = (BaseCommand)states[0]; - string[] args = (string[])states[1]; + object[] states = (object[])state; + BaseCommand command = (BaseCommand)states[0]; + string[] args = (string[])states[1]; - switch ( command.ObjectTypes ) - { - case ObjectTypes.Both: - { - if ( !(targeted is Item) && !(targeted is Mobile) ) - { - from.SendMessage( "This command does not work on that." ); - return; - } + switch (command.ObjectTypes) + { + case ObjectTypes.Both: + { + if (!(targeted is Item) && !(targeted is Mobile)) + { + from.SendMessage("This command does not work on that."); + return; + } - break; - } - case ObjectTypes.Items: - { - if ( !(targeted is Item) ) - { - from.SendMessage( "This command only works on items." ); - return; - } + break; + } + case ObjectTypes.Items: + { + if (!(targeted is Item)) + { + from.SendMessage("This command only works on items."); + return; + } - break; - } - case ObjectTypes.Mobiles: - { - if ( !(targeted is Mobile) ) - { - from.SendMessage( "This command only works on mobiles." ); - return; - } + break; + } + case ObjectTypes.Mobiles: + { + if (!(targeted is Mobile)) + { + from.SendMessage("This command only works on mobiles."); + return; + } - break; - } - } + break; + } + } - RunCommand( from, targeted, command, args ); - } - } -} + RunCommand(from, targeted, command, args); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Handlers.cs b/Scripts/Commands/Handlers.cs index b7ac61a19..9753f70d0 100644 --- a/Scripts/Commands/Handlers.cs +++ b/Scripts/Commands/Handlers.cs @@ -1,942 +1,961 @@ -using System; -using System.Text; using System.Collections; using System.Collections.Generic; -using Server.Mobiles; +using System.Text; +using Server.Commands.Generic; +using Server.Engines.Help; +using Server.Gumps; using Server.Items; -using Server.Menus.Questions; using Server.Menus.ItemLists; +using Server.Menus.Questions; +using Server.Misc; +using Server.Mobiles; +using Server.Multis; using Server.Network; using Server.Spells; using Server.Targeting; using Server.Targets; -using Server.Gumps; -using Server.Commands.Generic; namespace Server.Commands { - public class CommandHandlers - { - public static void Initialize() - { - CommandSystem.Prefix = "["; + public class CommandHandlers + { + public static void Initialize() + { + CommandSystem.Prefix = "["; - Register( "Go", AccessLevel.Counselor, Go_OnCommand ); + Register("Go", AccessLevel.Counselor, Go_OnCommand); - Register( "DropHolding", AccessLevel.Counselor, DropHolding_OnCommand ); + Register("DropHolding", AccessLevel.Counselor, DropHolding_OnCommand); - Register( "GetFollowers", AccessLevel.GameMaster, GetFollowers_OnCommand ); + Register("GetFollowers", AccessLevel.GameMaster, GetFollowers_OnCommand); - Register( "ClearFacet", AccessLevel.Administrator, ClearFacet_OnCommand ); + Register("ClearFacet", AccessLevel.Administrator, ClearFacet_OnCommand); - Register( "Where", AccessLevel.Counselor, Where_OnCommand ); + Register("Where", AccessLevel.Counselor, Where_OnCommand); - Register( "AutoPageNotify", AccessLevel.Counselor, APN_OnCommand ); - Register( "APN", AccessLevel.Counselor, APN_OnCommand ); + Register("AutoPageNotify", AccessLevel.Counselor, APN_OnCommand); + Register("APN", AccessLevel.Counselor, APN_OnCommand); - Register( "Animate", AccessLevel.GameMaster, Animate_OnCommand ); + Register("Animate", AccessLevel.GameMaster, Animate_OnCommand); - Register( "Cast", AccessLevel.Counselor, Cast_OnCommand ); + Register("Cast", AccessLevel.Counselor, Cast_OnCommand); - Register( "Stuck", AccessLevel.Counselor, Stuck_OnCommand ); + Register("Stuck", AccessLevel.Counselor, Stuck_OnCommand); - Register( "Help", AccessLevel.Player, Help_OnCommand ); + Register("Help", AccessLevel.Player, Help_OnCommand); - Register( "Save", AccessLevel.Administrator, Save_OnCommand ); - Register( "BackgroundSave", AccessLevel.Administrator, BackgroundSave_OnCommand ); - Register( "BGSave", AccessLevel.Administrator, BackgroundSave_OnCommand ); - Register( "SaveBG", AccessLevel.Administrator, BackgroundSave_OnCommand ); + Register("Save", AccessLevel.Administrator, Save_OnCommand); + Register("BackgroundSave", AccessLevel.Administrator, BackgroundSave_OnCommand); + Register("BGSave", AccessLevel.Administrator, BackgroundSave_OnCommand); + Register("SaveBG", AccessLevel.Administrator, BackgroundSave_OnCommand); + + Register("Move", AccessLevel.GameMaster, Move_OnCommand); + Register("Client", AccessLevel.Counselor, Client_OnCommand); - Register( "Move", AccessLevel.GameMaster, Move_OnCommand ); - Register( "Client", AccessLevel.Counselor, Client_OnCommand ); - - Register( "SMsg", AccessLevel.Counselor, StaffMessage_OnCommand ); - Register( "SM", AccessLevel.Counselor, StaffMessage_OnCommand ); - Register( "S", AccessLevel.Counselor, StaffMessage_OnCommand ); - - Register( "BCast", AccessLevel.GameMaster, BroadcastMessage_OnCommand ); - Register( "BC", AccessLevel.GameMaster, BroadcastMessage_OnCommand ); - Register( "B", AccessLevel.GameMaster, BroadcastMessage_OnCommand ); - - Register( "Bank", AccessLevel.GameMaster, Bank_OnCommand ); - - Register( "Echo", AccessLevel.Counselor, Echo_OnCommand ); - - Register( "Sound", AccessLevel.GameMaster, Sound_OnCommand ); - - Register( "ViewEquip", AccessLevel.GameMaster, ViewEquip_OnCommand ); - - Register( "Light", AccessLevel.Counselor, Light_OnCommand ); - Register( "Stats", AccessLevel.Counselor, Stats_OnCommand ); - - Register( "SpeedBoost", AccessLevel.Counselor, SpeedBoost_OnCommand ); - } - - public static void Register( string command, AccessLevel access, CommandEventHandler handler ) - { - CommandSystem.Register( command, access, handler ); - } - - [Usage( "SpeedBoost [true|false]" )] - [Description( "Enables a speed boost for the invoker. Disable with paramaters." )] - private static void SpeedBoost_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; - - if ( e.Length <= 1 ) - { - if ( e.Length == 1 && !e.GetBoolean( 0 ) ) - { - from.Send( SpeedControl.Disable ); - from.SendMessage( "Speed boost has been disabled." ); - } - else - { - from.Send( SpeedControl.MountSpeed ); - from.SendMessage( "Speed boost has been enabled." ); - } - } - else - { - from.SendMessage( "Format: SpeedBoost [true|false]" ); - } - } - - [Usage( "Where" )] - [Description( "Tells the commanding player his coordinates, region, and facet." )] - public static void Where_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; - Map map = from.Map; - - from.SendMessage( "You are at {0} {1} {2} in {3}.", from.X, from.Y, from.Z, map ); - - if ( map != null ) - { - Region reg = from.Region; - - if ( !reg.IsDefault ) - { - StringBuilder builder = new StringBuilder(); - - builder.Append( reg.ToString() ); - reg = reg.Parent; - - while ( reg != null ) - { - builder.Append( " <- " + reg.ToString() ); - reg = reg.Parent; - } - - from.SendMessage( "Your region is {0}.", builder.ToString() ); - } - } - } - - [Usage( "DropHolding" )] - [Description( "Drops the item, if any, that a targeted player is holding. The item is placed into their backpack, or if that's full, at their feet." )] - public static void DropHolding_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, DropHolding_OnTarget ); - e.Mobile.SendMessage( "Target the player to drop what they are holding." ); - } - - public static void DropHolding_OnTarget( Mobile from, object obj ) - { - if ( obj is Mobile targ && targ.Player ) - { - Item held = targ.Holding; - - if ( held == null ) - { - from.SendMessage( "They are not holding anything." ); - } - else - { - if ( from.AccessLevel == AccessLevel.Counselor ) - { - Engines.Help.PageEntry pe = Engines.Help.PageQueue.GetEntry( targ ); - - if ( pe?.Handler == from ) - from.SendMessage( "You may only use this command if you are handling their help page." ); - else - from.SendMessage( "You may only use this command on someone who has paged you." ); - - return; - } - - if ( targ.AddToBackpack( held ) ) - from.SendMessage( "The item they were holding has been placed into their backpack." ); - else - from.SendMessage( "The item they were holding has been placed at their feet." ); - - held.ClearBounce(); - - targ.Holding = null; - } - } - else - { - from.BeginTarget( -1, false, TargetFlags.None, DropHolding_OnTarget ); - from.SendMessage( "That is not a player. Try again." ); - } - } - - public static void DeleteList_Callback( Mobile from, bool okay, object state ) - { - if ( okay ) - { - List list = (List)state; - - CommandLogging.WriteLine( from, "{0} {1} deleting {2} object{3}", from.AccessLevel, CommandLogging.Format( from ), list.Count, list.Count == 1 ? "" : "s" ); - - NetState.Pause(); - - for ( int i = 0; i < list.Count; ++i ) - list[i].Delete(); - - NetState.Resume(); - - from.SendMessage( "You have deleted {0} object{1}.", list.Count, list.Count == 1 ? "" : "s" ); - } - else - { - from.SendMessage( "You have chosen not to delete those objects." ); - } - } - - [Usage( "ClearFacet" )] - [Description( "Deletes all items and mobiles in your facet. Players and their inventory will not be deleted." )] - public static void ClearFacet_OnCommand( CommandEventArgs e ) - { - Map map = e.Mobile.Map; - - if ( map == null || map == Map.Internal ) - { - e.Mobile.SendMessage( "You may not run that command here." ); - return; - } - - List list = new List(); - - foreach ( Item item in World.Items.Values ) - if ( item.Map == map && item.Parent == null ) - list.Add( item ); - - foreach ( Mobile m in World.Mobiles.Values ) - if ( m.Map == map && !m.Player ) - list.Add( m ); - - if ( list.Count > 0 ) - { - CommandLogging.WriteLine( e.Mobile, "{0} {1} starting facet clear of {2} ({3} object{4})", e.Mobile.AccessLevel, CommandLogging.Format( e.Mobile ), map, list.Count, list.Count == 1 ? "" : "s" ); - - e.Mobile.SendGump( - new WarningGump( 1060635, 30720, - $"You are about to delete {list.Count} object{(list.Count == 1 ? "" : "s")} from this facet. Do you really wish to continue?", - 0xFFC000, 360, 260, DeleteList_Callback, list ) ); - } - else - { - e.Mobile.SendMessage( "There were no objects found to delete." ); - } - } - - [Usage( "GetFollowers" )] - [Description( "Teleports all pets of a targeted player to your location." )] - public static void GetFollowers_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, GetFollowers_OnTarget ); - e.Mobile.SendMessage( "Target a player to get their pets." ); - } - - public static void GetFollowers_OnTarget( Mobile from, object obj ) - { - if ( obj is PlayerMobile pm ) - { - List pets = pm.AllFollowers; - - if ( pets.Count > 0 ) - { - CommandLogging.WriteLine( from, "{0} {1} getting all followers of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( pm ) ); - - from.SendMessage( "That player has {0} pet{1}.", pets.Count, pets.Count != 1 ? "s" : "" ); - - for ( int i = 0; i < pets.Count; ++i ) - { - Mobile pet = pets[i]; - - if ( pet is IMount mount ) - mount.Rider = null; // make sure it's dismounted - - pet.MoveToWorld( from.Location, from.Map ); - } - } - else - { - from.SendMessage( "There were no pets found for that player." ); - } - } - else if ( obj is Mobile master && master.Player ) - { - ArrayList pets = new ArrayList(); - - foreach ( Mobile m in World.Mobiles.Values ) - { - if ( m is BaseCreature bc ) - { - if ( (bc.Controlled && bc.ControlMaster == master) || (bc.Summoned && bc.SummonMaster == master) ) - pets.Add( bc ); - } - } - - if ( pets.Count > 0 ) - { - CommandLogging.WriteLine( from, "{0} {1} getting all followers of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( master ) ); - - from.SendMessage( "That player has {0} pet{1}.", pets.Count, pets.Count != 1 ? "s" : "" ); - - for ( int i = 0; i < pets.Count; ++i ) - { - Mobile pet = (Mobile)pets[i]; - - if ( pet is IMount mount ) - mount.Rider = null; // make sure it's dismounted - - pet.MoveToWorld( from.Location, from.Map ); - } - } - else - { - from.SendMessage( "There were no pets found for that player." ); - } - } - else - { - from.BeginTarget( -1, false, TargetFlags.None, GetFollowers_OnTarget ); - from.SendMessage( "That is not a player. Try again." ); - } - } - - private class ViewEqTarget : Target - { - public ViewEqTarget() : base( -1, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !BaseCommand.IsAccessible( from, targeted ) ) - { - from.SendMessage( "That is not accessible." ); - return; - } - - if ( targeted is Mobile mobile ) - from.SendMenu( new EquipMenu( from, mobile, GetEquip( mobile ) ) ); - } - - private static ItemListEntry[] GetEquip( Mobile m ) - { - ItemListEntry[] entries = new ItemListEntry[m.Items.Count]; - - for ( int i = 0; i < m.Items.Count; ++i ) - { - Item item = m.Items[i]; - - entries[i] = new ItemListEntry($"{item.Layer}: {item.GetType().Name}", item.ItemID, item.Hue ); - } - - return entries; - } - - private class EquipMenu : ItemListMenu - { - private Mobile m_Mobile; - - public EquipMenu( Mobile from, Mobile m, ItemListEntry[] entries ) : base( "Equipment", entries ) - { - m_Mobile = m; - - CommandLogging.WriteLine( from, "{0} {1} viewing equipment of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( m ) ); - } - - public override void OnResponse( NetState state, int index ) - { - if ( index >= 0 && index < m_Mobile.Items.Count ) - { - Item item = m_Mobile.Items[index]; - - state.Mobile.SendMenu( new EquipDetailsMenu( m_Mobile, item ) ); - } - } - - private class EquipDetailsMenu : QuestionMenu - { - private Mobile m_Mobile; - private Item m_Item; - - public EquipDetailsMenu( Mobile m, Item item ) : base($"{item.Layer}: {item.GetType().Name}", new[]{"Move","Delete","Props"}) - { - m_Mobile = m; - m_Item = item; - } - - public override void OnCancel( NetState state ) - { - state.Mobile.SendMenu( new EquipMenu( state.Mobile, m_Mobile, GetEquip( m_Mobile ) ) ); - } - - public override void OnResponse( NetState state, int index ) - { - if ( index == 0 ) - { - CommandLogging.WriteLine( state.Mobile, "{0} {1} moving equipment item {2} of {3}", state.Mobile.AccessLevel, CommandLogging.Format( state.Mobile ), CommandLogging.Format( m_Item ), CommandLogging.Format( m_Mobile ) ); - state.Mobile.Target = new MoveTarget( m_Item ); - } - else if ( index == 1 ) - { - CommandLogging.WriteLine( state.Mobile, "{0} {1} deleting equipment item {2} of {3}", state.Mobile.AccessLevel, CommandLogging.Format( state.Mobile ), CommandLogging.Format( m_Item ), CommandLogging.Format( m_Mobile ) ); - m_Item.Delete(); - } - else if ( index == 2 ) - { - CommandLogging.WriteLine( state.Mobile, "{0} {1} opening properties for equipment item {2} of {3}", state.Mobile.AccessLevel, CommandLogging.Format( state.Mobile ), CommandLogging.Format( m_Item ), CommandLogging.Format( m_Mobile ) ); - state.Mobile.SendGump( new PropertiesGump( state.Mobile, m_Item ) ); - } - } - } - } - } - - [Usage( "ViewEquip" )] - [Description( "Lists equipment of a targeted mobile. From the list you can move, delete, or open props." )] - public static void ViewEquip_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new ViewEqTarget(); - } - - [Usage( "Sound [toAll=true]" )] - [Description( "Plays a sound to players within 12 tiles of you. The (toAll) argument specifies to everyone, or just those who can see you." )] - public static void Sound_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 1 ) - PlaySound( e.Mobile, e.GetInt32( 0 ), true ); - else if ( e.Length == 2 ) - PlaySound( e.Mobile, e.GetInt32( 0 ), e.GetBoolean( 1 ) ); - else - e.Mobile.SendMessage( "Format: Sound [toAll]" ); - } - - private static void PlaySound( Mobile m, int index, bool toAll ) - { - Map map = m.Map; - - if ( map == null ) - return; - - CommandLogging.WriteLine( m, "{0} {1} playing sound {2} (toAll={3})", m.AccessLevel, CommandLogging.Format( m ), index, toAll ); - - Packet p = new PlaySound( index, m.Location ); - - p.Acquire(); - - foreach ( NetState state in m.GetClientsInRange( 12 ) ) - { - if ( toAll || state.Mobile.CanSee( m ) ) - state.Send( p ); - } - - p.Release(); - } - - private class BankTarget : Target - { - public BankTarget() : base( -1, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile m ) - { - BankBox box = ( m.Player ? m.BankBox : m.FindBankNoCreate() ); - - if ( box != null ) - { - CommandLogging.WriteLine( from, "{0} {1} opening bank box of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( m ) ); - - if ( from == m ) - box.Open(); - else - box.DisplayTo( from ); - } - else - { - from.SendMessage( "They have no bank box." ); - } - } - } - } - - [Usage( "Echo " )] - [Description( "Relays (text) as a system message." )] - public static void Echo_OnCommand( CommandEventArgs e ) - { - string toEcho = e.ArgString.Trim(); - - if ( toEcho.Length > 0 ) - e.Mobile.SendMessage( toEcho ); - else - e.Mobile.SendMessage( "Format: Echo \"\"" ); - } - - [Usage( "Bank" )] - [Description( "Opens the bank box of a given target." )] - public static void Bank_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new BankTarget(); - } - - private class DismountTarget : Target - { - public DismountTarget() : base( -1, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile targ ) - { - CommandLogging.WriteLine( from, "{0} {1} dismounting {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( targ ) ); - - for ( int i = 0; i < targ.Items.Count; ++i ) - { - Item item = targ.Items[i]; - - if ( item is IMountItem mountItem ) - { - IMount mount = mountItem.Mount; - - if ( mount != null ) - mount.Rider = null; - - if ( targ.Items.IndexOf( item ) == -1 ) - --i; - } - } - - for ( int i = 0; i < targ.Items.Count; ++i ) - { - Item item = targ.Items[i]; - - if ( item.Layer == Layer.Mount ) - { - item.Delete(); - --i; - } - } - } - } - } - - private class ClientTarget : Target - { - public ClientTarget() : base( -1, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile targ && targ.NetState != null ) - { - CommandLogging.WriteLine( from, "{0} {1} opening client menu of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( targ ) ); - from.SendGump( new ClientGump( from, targ.NetState ) ); - } - } - } - - [Usage( "Client" )] - [Description( "Opens the client gump menu for a given player." )] - private static void Client_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new ClientTarget(); - } - - [Usage( "Move" )] - [Description( "Repositions a targeted item or mobile." )] - private static void Move_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new PickMoveTarget(); - } - - [Usage( "Save" )] - [Description( "Saves the world." )] - private static void Save_OnCommand( CommandEventArgs e ) - { - Misc.AutoSave.Save(); - } - - [Usage("BackgroundSave")] - [Aliases("BGSave", "SaveBG")] - [Description("Saves the world, writing to the disk in the background")] - private static void BackgroundSave_OnCommand(CommandEventArgs e) - { - Misc.AutoSave.Save( true ); - } - - private static bool FixMap( ref Map map, ref Point3D loc, Item item ) - { - return map == null || map == Map.Internal && item.RootParent is Mobile m && FixMap( ref map, ref loc, m ); - } - - private static bool FixMap( ref Map map, ref Point3D loc, Mobile m ) - { - if ( map == null || map == Map.Internal ) - { - map = m.LogoutMap; - loc = m.LogoutLocation; - } - - return ( map != null && map != Map.Internal ); - } - - [Usage( "Go [name | serial | (x y [z]) | (deg min (N | S) deg min (E | W))]" )] - [Description( "With no arguments, this command brings up the go menu. With one argument, (name), you are moved to that regions \"go location.\" Or, if a numerical value is specified for one argument, (serial), you are moved to that object. Two or three arguments, (x y [z]), will move your character to that location. When six arguments are specified, (deg min (N | S) deg min (E | W)), your character will go to an approximate of those sextant coordinates." )] - private static void Go_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; - - if ( e.Length == 0 ) - { - GoGump.DisplayTo( from ); - return; - } - - if ( e.Length == 1 ) - { - try - { - int ser = e.GetInt32( 0 ); - - IEntity ent = World.FindEntity( ser ); - - if ( ent is Item item ) - { - Map map = item.Map; - Point3D loc = item.GetWorldLocation(); - - Mobile owner = item.RootParent as Mobile; - - if ( owner?.Map != null && owner.Map != Map.Internal && !BaseCommand.IsAccessible( from, owner ) /* !from.CanSee( owner )*/ ) - { - from.SendMessage( "You can not go to what you can not see." ); - return; - } - if ( owner != null && (owner.Map == null || owner.Map == Map.Internal) && owner.Hidden && owner.AccessLevel >= from.AccessLevel ) - { - from.SendMessage( "You can not go to what you can not see." ); - return; - } - if ( !FixMap( ref map, ref loc, item ) ) - { - from.SendMessage( "That is an internal item and you cannot go to it." ); - return; - } - - from.MoveToWorld( loc, map ); - - return; - } - if ( ent is Mobile m ) - { - Map map = m.Map; - Point3D loc = m.Location; - - Mobile owner = m; - - if ( (owner.Map != null && owner.Map != Map.Internal) && !BaseCommand.IsAccessible( from, owner ) /* !from.CanSee( owner )*/ ) - { - from.SendMessage( "You can not go to what you can not see." ); - return; - } - if ( (owner.Map == null || owner.Map == Map.Internal) && owner.Hidden && owner.AccessLevel >= from.AccessLevel ) - { - from.SendMessage( "You can not go to what you can not see." ); - return; - } - if ( !FixMap( ref map, ref loc, m ) ) - { - from.SendMessage( "That is an internal mobile and you cannot go to it." ); - return; - } - - from.MoveToWorld( loc, map ); - - return; - } - else - { - string name = e.GetString( 0 ); - Map map; - - for ( int i = 0; i < Map.AllMaps.Count; ++i ) - { - map = Map.AllMaps[i]; - - if ( map.MapIndex == 0x7F || map.MapIndex == 0xFF ) - continue; - - if ( Insensitive.Equals( name, map.Name ) ) - { - from.Map = map; - return; - } - } - - Dictionary list = from.Map.Regions; - - foreach( KeyValuePair kvp in list ) - { - Region r = kvp.Value; - - if ( Insensitive.Equals( r.Name, name ) ) - { - from.Location = new Point3D( r.GoLocation ); - return; - } - } - - for( int i = 0; i < Map.AllMaps.Count; ++i ) - { - map = Map.AllMaps[i]; - - if ( map.MapIndex == 0x7F || map.MapIndex == 0xFF || from.Map == map ) - continue; - - foreach( Region r in map.Regions.Values ) - { - if ( Insensitive.Equals( r.Name, name ) ) - { - from.MoveToWorld( r.GoLocation, map ); - return; - } - } - } - - if ( ser != 0 ) - from.SendMessage( "No object with that serial was found." ); - else - from.SendMessage( "No region with that name was found." ); - - return; - } - } - catch - { - } - - from.SendMessage( "Region name not found" ); - } - else if ( e.Length == 2 || e.Length == 3 ) - { - Map map = from.Map; - - if ( map != null ) - { - try - { - /* - * This to avoid being teleported to (0,0) if trying to teleport - * to a region with spaces in its name. - */ - int x = int.Parse( e.GetString( 0 ) ); - int y = int.Parse( e.GetString( 1 ) ); - int z = (e.Length == 3 ) ? int.Parse( e.GetString( 2 ) ) : map.GetAverageZ( x, y ); - - from.Location = new Point3D( x, y, z ); - } - catch - { - from.SendMessage( "Region name not found." ); - } - } - } - else if ( e.Length == 6 ) - { - Map map = from.Map; - - if ( map != null ) - { - Point3D p = Sextant.ReverseLookup( map, e.GetInt32( 3 ), e.GetInt32( 0 ), e.GetInt32( 4 ), e.GetInt32( 1 ), Insensitive.Equals( e.GetString( 5 ), "E" ), Insensitive.Equals( e.GetString( 2 ), "S" ) ); - - if ( p != Point3D.Zero ) - from.Location = p; - else - from.SendMessage( "Sextant reverse lookup failed." ); - } - } - else - { - from.SendMessage( "Format: Go [name | serial | (x y [z]) | (deg min (N | S) deg min (E | W)]" ); - } - } - - [Usage( "Help" )] - [Description( "Lists all available commands." )] - public static void Help_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - - List list = new List(); - - foreach ( CommandEntry entry in CommandSystem.Entries.Values ) - if ( m.AccessLevel >= entry.AccessLevel ) - list.Add( entry ); - - list.Sort(); - - StringBuilder sb = new StringBuilder(); - - if ( list.Count > 0 ) - sb.Append( list[0].Command ); - - for ( int i = 1; i < list.Count; ++i ) - { - string v = list[i].Command; - - if ( (sb.Length + 1 + v.Length) >= 256 ) - { - m.SendAsciiMessage( 0x482, sb.ToString() ); - sb = new StringBuilder(); - sb.Append( v ); - } - else - { - sb.Append( ' ' ); - sb.Append( v ); - } - } - - if ( sb.Length > 0 ) - m.SendAsciiMessage( 0x482, sb.ToString() ); - } - - [Usage( "SMsg " )] - [Aliases( "S", "SM" )] - [Description( "Broadcasts a message to all online staff." )] - public static void StaffMessage_OnCommand( CommandEventArgs e ) - { - BroadcastMessage( AccessLevel.Counselor, e.Mobile.SpeechHue, $"[{e.Mobile.Name}] {e.ArgString}"); - } - - [Usage( "BCast " )] - [Aliases( "B", "BC" )] - [Description( "Broadcasts a message to everyone online." )] - public static void BroadcastMessage_OnCommand( CommandEventArgs e ) - { - BroadcastMessage( AccessLevel.Player, 0x482, $"Staff message from {e.Mobile.Name}:"); - BroadcastMessage( AccessLevel.Player, 0x482, e.ArgString ); - } - - public static void BroadcastMessage ( AccessLevel ac, int hue, string message ) - { - foreach ( NetState state in NetState.Instances ) - { - Mobile m = state.Mobile; - - if ( m != null && m.AccessLevel >= ac ) - m.SendMessage( hue, message ); - } - } - - [Usage( "AutoPageNotify" )] - [Aliases( "APN" )] - [Description( "Toggles your auto-page-notify status." )] - public static void APN_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - - m.AutoPageNotify = !m.AutoPageNotify; - - m.SendMessage( "Your auto-page-notify has been turned {0}.", m.AutoPageNotify ? "on" : "off" ); - } - - [Usage( "Animate " )] - [Description( "Makes your character do a specified animation." )] - public static void Animate_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 6 ) - { - e.Mobile.Animate( e.GetInt32( 0 ), e.GetInt32( 1 ), e.GetInt32( 2 ), e.GetBoolean( 3 ), e.GetBoolean( 4 ), e.GetInt32( 5 ) ); - } - else - { - e.Mobile.SendMessage( "Format: Animate " ); - } - } - - [Usage( "Cast " )] - [Description( "Casts a spell by name." )] - public static void Cast_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 1 ) - { - if ( !Multis.DesignContext.Check( e.Mobile ) ) - return; // They are customizing - - Spell spell = SpellRegistry.NewSpell( e.GetString( 0 ), e.Mobile, null ); - - if ( spell != null ) - spell.Cast(); - else - e.Mobile.SendMessage( "That spell was not found." ); - } - else - { - e.Mobile.SendMessage( "Format: Cast " ); - } - } - - private class StuckMenuTarget : Target - { - public StuckMenuTarget() : base( -1, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile mobile ) - { - if ( mobile.AccessLevel >= from.AccessLevel && mobile != from ) - from.SendMessage( "You can't do that to someone with higher Accesslevel than you!" ); - else - from.SendGump( new StuckMenu( from, mobile, false ) ); - } - } - } - - [Usage( "Stuck" )] - [Description( "Opens a menu of towns, used for teleporting stuck mobiles." )] - public static void Stuck_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new StuckMenuTarget(); - } - - [Usage( "Light ")] - [Description( "Set your local lightlevel." )] - public static void Light_OnCommand( CommandEventArgs e ) - { - e.Mobile.LightLevel = e.GetInt32( 0 ); - } - - [Usage( "Stats")] - [Description( "View some stats about the server." )] - public static void Stats_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( "Open Connections: {0}", NetState.Instances.Count ); - e.Mobile.SendMessage( "Mobiles: {0}", World.Mobiles.Count ); - e.Mobile.SendMessage( "Items: {0}", World.Items.Count ); - } - } -} + Register("SMsg", AccessLevel.Counselor, StaffMessage_OnCommand); + Register("SM", AccessLevel.Counselor, StaffMessage_OnCommand); + Register("S", AccessLevel.Counselor, StaffMessage_OnCommand); + + Register("BCast", AccessLevel.GameMaster, BroadcastMessage_OnCommand); + Register("BC", AccessLevel.GameMaster, BroadcastMessage_OnCommand); + Register("B", AccessLevel.GameMaster, BroadcastMessage_OnCommand); + + Register("Bank", AccessLevel.GameMaster, Bank_OnCommand); + + Register("Echo", AccessLevel.Counselor, Echo_OnCommand); + + Register("Sound", AccessLevel.GameMaster, Sound_OnCommand); + + Register("ViewEquip", AccessLevel.GameMaster, ViewEquip_OnCommand); + + Register("Light", AccessLevel.Counselor, Light_OnCommand); + Register("Stats", AccessLevel.Counselor, Stats_OnCommand); + + Register("SpeedBoost", AccessLevel.Counselor, SpeedBoost_OnCommand); + } + + public static void Register(string command, AccessLevel access, CommandEventHandler handler) + { + CommandSystem.Register(command, access, handler); + } + + [Usage("SpeedBoost [true|false]")] + [Description("Enables a speed boost for the invoker. Disable with paramaters.")] + private static void SpeedBoost_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; + + if (e.Length <= 1) + { + if (e.Length == 1 && !e.GetBoolean(0)) + { + from.Send(SpeedControl.Disable); + from.SendMessage("Speed boost has been disabled."); + } + else + { + from.Send(SpeedControl.MountSpeed); + from.SendMessage("Speed boost has been enabled."); + } + } + else + { + from.SendMessage("Format: SpeedBoost [true|false]"); + } + } + + [Usage("Where")] + [Description("Tells the commanding player his coordinates, region, and facet.")] + public static void Where_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; + Map map = from.Map; + + from.SendMessage("You are at {0} {1} {2} in {3}.", from.X, from.Y, from.Z, map); + + if (map != null) + { + Region reg = from.Region; + + if (!reg.IsDefault) + { + StringBuilder builder = new StringBuilder(); + + builder.Append(reg); + reg = reg.Parent; + + while (reg != null) + { + builder.Append(" <- " + reg); + reg = reg.Parent; + } + + from.SendMessage("Your region is {0}.", builder.ToString()); + } + } + } + + [Usage("DropHolding")] + [Description( + "Drops the item, if any, that a targeted player is holding. The item is placed into their backpack, or if that's full, at their feet.")] + public static void DropHolding_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, DropHolding_OnTarget); + e.Mobile.SendMessage("Target the player to drop what they are holding."); + } + + public static void DropHolding_OnTarget(Mobile from, object obj) + { + if (obj is Mobile targ && targ.Player) + { + Item held = targ.Holding; + + if (held == null) + { + from.SendMessage("They are not holding anything."); + } + else + { + if (from.AccessLevel == AccessLevel.Counselor) + { + PageEntry pe = PageQueue.GetEntry(targ); + + if (pe?.Handler == from) + from.SendMessage("You may only use this command if you are handling their help page."); + else + from.SendMessage("You may only use this command on someone who has paged you."); + + return; + } + + if (targ.AddToBackpack(held)) + from.SendMessage("The item they were holding has been placed into their backpack."); + else + from.SendMessage("The item they were holding has been placed at their feet."); + + held.ClearBounce(); + + targ.Holding = null; + } + } + else + { + from.BeginTarget(-1, false, TargetFlags.None, DropHolding_OnTarget); + from.SendMessage("That is not a player. Try again."); + } + } + + public static void DeleteList_Callback(Mobile from, bool okay, object state) + { + if (okay) + { + List list = (List)state; + + CommandLogging.WriteLine(from, "{0} {1} deleting {2} object{3}", from.AccessLevel, + CommandLogging.Format(from), list.Count, list.Count == 1 ? "" : "s"); + + NetState.Pause(); + + for (int i = 0; i < list.Count; ++i) + list[i].Delete(); + + NetState.Resume(); + + from.SendMessage("You have deleted {0} object{1}.", list.Count, list.Count == 1 ? "" : "s"); + } + else + { + from.SendMessage("You have chosen not to delete those objects."); + } + } + + [Usage("ClearFacet")] + [Description("Deletes all items and mobiles in your facet. Players and their inventory will not be deleted.")] + public static void ClearFacet_OnCommand(CommandEventArgs e) + { + Map map = e.Mobile.Map; + + if (map == null || map == Map.Internal) + { + e.Mobile.SendMessage("You may not run that command here."); + return; + } + + List list = new List(); + + foreach (Item item in World.Items.Values) + if (item.Map == map && item.Parent == null) + list.Add(item); + + foreach (Mobile m in World.Mobiles.Values) + if (m.Map == map && !m.Player) + list.Add(m); + + if (list.Count > 0) + { + CommandLogging.WriteLine(e.Mobile, "{0} {1} starting facet clear of {2} ({3} object{4})", + e.Mobile.AccessLevel, CommandLogging.Format(e.Mobile), map, list.Count, list.Count == 1 ? "" : "s"); + + e.Mobile.SendGump( + new WarningGump(1060635, 30720, + $"You are about to delete {list.Count} object{(list.Count == 1 ? "" : "s")} from this facet. Do you really wish to continue?", + 0xFFC000, 360, 260, DeleteList_Callback, list)); + } + else + { + e.Mobile.SendMessage("There were no objects found to delete."); + } + } + + [Usage("GetFollowers")] + [Description("Teleports all pets of a targeted player to your location.")] + public static void GetFollowers_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, GetFollowers_OnTarget); + e.Mobile.SendMessage("Target a player to get their pets."); + } + + public static void GetFollowers_OnTarget(Mobile from, object obj) + { + if (obj is PlayerMobile pm) + { + List pets = pm.AllFollowers; + + if (pets.Count > 0) + { + CommandLogging.WriteLine(from, "{0} {1} getting all followers of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(pm)); + + from.SendMessage("That player has {0} pet{1}.", pets.Count, pets.Count != 1 ? "s" : ""); + + for (int i = 0; i < pets.Count; ++i) + { + Mobile pet = pets[i]; + + if (pet is IMount mount) + mount.Rider = null; // make sure it's dismounted + + pet.MoveToWorld(from.Location, from.Map); + } + } + else + { + from.SendMessage("There were no pets found for that player."); + } + } + else if (obj is Mobile master && master.Player) + { + ArrayList pets = new ArrayList(); + + foreach (Mobile m in World.Mobiles.Values) + if (m is BaseCreature bc) + if (bc.Controlled && bc.ControlMaster == master || bc.Summoned && bc.SummonMaster == master) + pets.Add(bc); + + if (pets.Count > 0) + { + CommandLogging.WriteLine(from, "{0} {1} getting all followers of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(master)); + + from.SendMessage("That player has {0} pet{1}.", pets.Count, pets.Count != 1 ? "s" : ""); + + for (int i = 0; i < pets.Count; ++i) + { + Mobile pet = (Mobile)pets[i]; + + if (pet is IMount mount) + mount.Rider = null; // make sure it's dismounted + + pet.MoveToWorld(from.Location, from.Map); + } + } + else + { + from.SendMessage("There were no pets found for that player."); + } + } + else + { + from.BeginTarget(-1, false, TargetFlags.None, GetFollowers_OnTarget); + from.SendMessage("That is not a player. Try again."); + } + } + + [Usage("ViewEquip")] + [Description("Lists equipment of a targeted mobile. From the list you can move, delete, or open props.")] + public static void ViewEquip_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new ViewEqTarget(); + } + + [Usage("Sound [toAll=true]")] + [Description( + "Plays a sound to players within 12 tiles of you. The (toAll) argument specifies to everyone, or just those who can see you.")] + public static void Sound_OnCommand(CommandEventArgs e) + { + if (e.Length == 1) + PlaySound(e.Mobile, e.GetInt32(0), true); + else if (e.Length == 2) + PlaySound(e.Mobile, e.GetInt32(0), e.GetBoolean(1)); + else + e.Mobile.SendMessage("Format: Sound [toAll]"); + } + + private static void PlaySound(Mobile m, int index, bool toAll) + { + Map map = m.Map; + + if (map == null) + return; + + CommandLogging.WriteLine(m, "{0} {1} playing sound {2} (toAll={3})", m.AccessLevel, CommandLogging.Format(m), + index, toAll); + + Packet p = new PlaySound(index, m.Location); + + p.Acquire(); + + foreach (NetState state in m.GetClientsInRange(12)) + if (toAll || state.Mobile.CanSee(m)) + state.Send(p); + + p.Release(); + } + + [Usage("Echo ")] + [Description("Relays (text) as a system message.")] + public static void Echo_OnCommand(CommandEventArgs e) + { + string toEcho = e.ArgString.Trim(); + + if (toEcho.Length > 0) + e.Mobile.SendMessage(toEcho); + else + e.Mobile.SendMessage("Format: Echo \"\""); + } + + [Usage("Bank")] + [Description("Opens the bank box of a given target.")] + public static void Bank_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new BankTarget(); + } + + [Usage("Client")] + [Description("Opens the client gump menu for a given player.")] + private static void Client_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new ClientTarget(); + } + + [Usage("Move")] + [Description("Repositions a targeted item or mobile.")] + private static void Move_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new PickMoveTarget(); + } + + [Usage("Save")] + [Description("Saves the world.")] + private static void Save_OnCommand(CommandEventArgs e) + { + AutoSave.Save(); + } + + [Usage("BackgroundSave")] + [Aliases("BGSave", "SaveBG")] + [Description("Saves the world, writing to the disk in the background")] + private static void BackgroundSave_OnCommand(CommandEventArgs e) + { + AutoSave.Save(true); + } + + private static bool FixMap(ref Map map, ref Point3D loc, Item item) + { + return map == null || map == Map.Internal && item.RootParent is Mobile m && FixMap(ref map, ref loc, m); + } + + private static bool FixMap(ref Map map, ref Point3D loc, Mobile m) + { + if (map == null || map == Map.Internal) + { + map = m.LogoutMap; + loc = m.LogoutLocation; + } + + return map != null && map != Map.Internal; + } + + [Usage("Go [name | serial | (x y [z]) | (deg min (N | S) deg min (E | W))]")] + [Description( + "With no arguments, this command brings up the go menu. With one argument, (name), you are moved to that regions \"go location.\" Or, if a numerical value is specified for one argument, (serial), you are moved to that object. Two or three arguments, (x y [z]), will move your character to that location. When six arguments are specified, (deg min (N | S) deg min (E | W)), your character will go to an approximate of those sextant coordinates.")] + private static void Go_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; + + if (e.Length == 0) + { + GoGump.DisplayTo(from); + return; + } + + if (e.Length == 1) + { + try + { + int ser = e.GetInt32(0); + + IEntity ent = World.FindEntity(ser); + + if (ent is Item item) + { + Map map = item.Map; + Point3D loc = item.GetWorldLocation(); + + Mobile owner = item.RootParent as Mobile; + + if (owner?.Map != null && owner.Map != Map.Internal && + !BaseCommand.IsAccessible(from, owner) /* !from.CanSee( owner )*/) + { + from.SendMessage("You can not go to what you can not see."); + return; + } + + if (owner != null && (owner.Map == null || owner.Map == Map.Internal) && owner.Hidden && + owner.AccessLevel >= from.AccessLevel) + { + from.SendMessage("You can not go to what you can not see."); + return; + } + + if (!FixMap(ref map, ref loc, item)) + { + from.SendMessage("That is an internal item and you cannot go to it."); + return; + } + + from.MoveToWorld(loc, map); + + return; + } + + if (ent is Mobile m) + { + Map map = m.Map; + Point3D loc = m.Location; + + Mobile owner = m; + + if (owner.Map != null && owner.Map != Map.Internal && + !BaseCommand.IsAccessible(from, owner) /* !from.CanSee( owner )*/) + { + from.SendMessage("You can not go to what you can not see."); + return; + } + + if ((owner.Map == null || owner.Map == Map.Internal) && owner.Hidden && + owner.AccessLevel >= from.AccessLevel) + { + from.SendMessage("You can not go to what you can not see."); + return; + } + + if (!FixMap(ref map, ref loc, m)) + { + from.SendMessage("That is an internal mobile and you cannot go to it."); + return; + } + + from.MoveToWorld(loc, map); + + return; + } + else + { + string name = e.GetString(0); + Map map; + + for (int i = 0; i < Map.AllMaps.Count; ++i) + { + map = Map.AllMaps[i]; + + if (map.MapIndex == 0x7F || map.MapIndex == 0xFF) + continue; + + if (Insensitive.Equals(name, map.Name)) + { + from.Map = map; + return; + } + } + + Dictionary list = from.Map.Regions; + + foreach (KeyValuePair kvp in list) + { + Region r = kvp.Value; + + if (Insensitive.Equals(r.Name, name)) + { + from.Location = new Point3D(r.GoLocation); + return; + } + } + + for (int i = 0; i < Map.AllMaps.Count; ++i) + { + map = Map.AllMaps[i]; + + if (map.MapIndex == 0x7F || map.MapIndex == 0xFF || from.Map == map) + continue; + + foreach (Region r in map.Regions.Values) + if (Insensitive.Equals(r.Name, name)) + { + from.MoveToWorld(r.GoLocation, map); + return; + } + } + + if (ser != 0) + from.SendMessage("No object with that serial was found."); + else + from.SendMessage("No region with that name was found."); + + return; + } + } + catch + { + } + + from.SendMessage("Region name not found"); + } + else if (e.Length == 2 || e.Length == 3) + { + Map map = from.Map; + + if (map != null) + try + { + /* + * This to avoid being teleported to (0,0) if trying to teleport + * to a region with spaces in its name. + */ + int x = int.Parse(e.GetString(0)); + int y = int.Parse(e.GetString(1)); + int z = e.Length == 3 ? int.Parse(e.GetString(2)) : map.GetAverageZ(x, y); + + from.Location = new Point3D(x, y, z); + } + catch + { + from.SendMessage("Region name not found."); + } + } + else if (e.Length == 6) + { + Map map = from.Map; + + if (map != null) + { + Point3D p = Sextant.ReverseLookup(map, e.GetInt32(3), e.GetInt32(0), e.GetInt32(4), e.GetInt32(1), + Insensitive.Equals(e.GetString(5), "E"), Insensitive.Equals(e.GetString(2), "S")); + + if (p != Point3D.Zero) + from.Location = p; + else + from.SendMessage("Sextant reverse lookup failed."); + } + } + else + { + from.SendMessage("Format: Go [name | serial | (x y [z]) | (deg min (N | S) deg min (E | W)]"); + } + } + + [Usage("Help")] + [Description("Lists all available commands.")] + public static void Help_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + + List list = new List(); + + foreach (CommandEntry entry in CommandSystem.Entries.Values) + if (m.AccessLevel >= entry.AccessLevel) + list.Add(entry); + + list.Sort(); + + StringBuilder sb = new StringBuilder(); + + if (list.Count > 0) + sb.Append(list[0].Command); + + for (int i = 1; i < list.Count; ++i) + { + string v = list[i].Command; + + if (sb.Length + 1 + v.Length >= 256) + { + m.SendAsciiMessage(0x482, sb.ToString()); + sb = new StringBuilder(); + sb.Append(v); + } + else + { + sb.Append(' '); + sb.Append(v); + } + } + + if (sb.Length > 0) + m.SendAsciiMessage(0x482, sb.ToString()); + } + + [Usage("SMsg ")] + [Aliases("S", "SM")] + [Description("Broadcasts a message to all online staff.")] + public static void StaffMessage_OnCommand(CommandEventArgs e) + { + BroadcastMessage(AccessLevel.Counselor, e.Mobile.SpeechHue, $"[{e.Mobile.Name}] {e.ArgString}"); + } + + [Usage("BCast ")] + [Aliases("B", "BC")] + [Description("Broadcasts a message to everyone online.")] + public static void BroadcastMessage_OnCommand(CommandEventArgs e) + { + BroadcastMessage(AccessLevel.Player, 0x482, $"Staff message from {e.Mobile.Name}:"); + BroadcastMessage(AccessLevel.Player, 0x482, e.ArgString); + } + + public static void BroadcastMessage(AccessLevel ac, int hue, string message) + { + foreach (NetState state in NetState.Instances) + { + Mobile m = state.Mobile; + + if (m != null && m.AccessLevel >= ac) + m.SendMessage(hue, message); + } + } + + [Usage("AutoPageNotify")] + [Aliases("APN")] + [Description("Toggles your auto-page-notify status.")] + public static void APN_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + + m.AutoPageNotify = !m.AutoPageNotify; + + m.SendMessage("Your auto-page-notify has been turned {0}.", m.AutoPageNotify ? "on" : "off"); + } + + [Usage("Animate ")] + [Description("Makes your character do a specified animation.")] + public static void Animate_OnCommand(CommandEventArgs e) + { + if (e.Length == 6) + e.Mobile.Animate(e.GetInt32(0), e.GetInt32(1), e.GetInt32(2), e.GetBoolean(3), e.GetBoolean(4), + e.GetInt32(5)); + else + e.Mobile.SendMessage("Format: Animate "); + } + + [Usage("Cast ")] + [Description("Casts a spell by name.")] + public static void Cast_OnCommand(CommandEventArgs e) + { + if (e.Length == 1) + { + if (!DesignContext.Check(e.Mobile)) + return; // They are customizing + + Spell spell = SpellRegistry.NewSpell(e.GetString(0), e.Mobile, null); + + if (spell != null) + spell.Cast(); + else + e.Mobile.SendMessage("That spell was not found."); + } + else + { + e.Mobile.SendMessage("Format: Cast "); + } + } + + [Usage("Stuck")] + [Description("Opens a menu of towns, used for teleporting stuck mobiles.")] + public static void Stuck_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new StuckMenuTarget(); + } + + [Usage("Light ")] + [Description("Set your local lightlevel.")] + public static void Light_OnCommand(CommandEventArgs e) + { + e.Mobile.LightLevel = e.GetInt32(0); + } + + [Usage("Stats")] + [Description("View some stats about the server.")] + public static void Stats_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage("Open Connections: {0}", NetState.Instances.Count); + e.Mobile.SendMessage("Mobiles: {0}", World.Mobiles.Count); + e.Mobile.SendMessage("Items: {0}", World.Items.Count); + } + + private class ViewEqTarget : Target + { + public ViewEqTarget() : base(-1, false, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!BaseCommand.IsAccessible(from, targeted)) + { + from.SendMessage("That is not accessible."); + return; + } + + if (targeted is Mobile mobile) + from.SendMenu(new EquipMenu(from, mobile, GetEquip(mobile))); + } + + private static ItemListEntry[] GetEquip(Mobile m) + { + ItemListEntry[] entries = new ItemListEntry[m.Items.Count]; + + for (int i = 0; i < m.Items.Count; ++i) + { + Item item = m.Items[i]; + + entries[i] = new ItemListEntry($"{item.Layer}: {item.GetType().Name}", item.ItemID, item.Hue); + } + + return entries; + } + + private class EquipMenu : ItemListMenu + { + private Mobile m_Mobile; + + public EquipMenu(Mobile from, Mobile m, ItemListEntry[] entries) : base("Equipment", entries) + { + m_Mobile = m; + + CommandLogging.WriteLine(from, "{0} {1} viewing equipment of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(m)); + } + + public override void OnResponse(NetState state, int index) + { + if (index >= 0 && index < m_Mobile.Items.Count) + { + Item item = m_Mobile.Items[index]; + + state.Mobile.SendMenu(new EquipDetailsMenu(m_Mobile, item)); + } + } + + private class EquipDetailsMenu : QuestionMenu + { + private Item m_Item; + private Mobile m_Mobile; + + public EquipDetailsMenu(Mobile m, Item item) : base($"{item.Layer}: {item.GetType().Name}", + new[] { "Move", "Delete", "Props" }) + { + m_Mobile = m; + m_Item = item; + } + + public override void OnCancel(NetState state) + { + state.Mobile.SendMenu(new EquipMenu(state.Mobile, m_Mobile, GetEquip(m_Mobile))); + } + + public override void OnResponse(NetState state, int index) + { + if (index == 0) + { + CommandLogging.WriteLine(state.Mobile, "{0} {1} moving equipment item {2} of {3}", + state.Mobile.AccessLevel, CommandLogging.Format(state.Mobile), CommandLogging.Format(m_Item), + CommandLogging.Format(m_Mobile)); + state.Mobile.Target = new MoveTarget(m_Item); + } + else if (index == 1) + { + CommandLogging.WriteLine(state.Mobile, "{0} {1} deleting equipment item {2} of {3}", + state.Mobile.AccessLevel, CommandLogging.Format(state.Mobile), CommandLogging.Format(m_Item), + CommandLogging.Format(m_Mobile)); + m_Item.Delete(); + } + else if (index == 2) + { + CommandLogging.WriteLine(state.Mobile, + "{0} {1} opening properties for equipment item {2} of {3}", state.Mobile.AccessLevel, + CommandLogging.Format(state.Mobile), CommandLogging.Format(m_Item), + CommandLogging.Format(m_Mobile)); + state.Mobile.SendGump(new PropertiesGump(state.Mobile, m_Item)); + } + } + } + } + } + + private class BankTarget : Target + { + public BankTarget() : base(-1, false, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile m) + { + BankBox box = m.Player ? m.BankBox : m.FindBankNoCreate(); + + if (box != null) + { + CommandLogging.WriteLine(from, "{0} {1} opening bank box of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(m)); + + if (from == m) + box.Open(); + else + box.DisplayTo(from); + } + else + { + from.SendMessage("They have no bank box."); + } + } + } + } + + private class DismountTarget : Target + { + public DismountTarget() : base(-1, false, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile targ) + { + CommandLogging.WriteLine(from, "{0} {1} dismounting {2}", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(targ)); + + for (int i = 0; i < targ.Items.Count; ++i) + { + Item item = targ.Items[i]; + + if (item is IMountItem mountItem) + { + IMount mount = mountItem.Mount; + + if (mount != null) + mount.Rider = null; + + if (targ.Items.IndexOf(item) == -1) + --i; + } + } + + for (int i = 0; i < targ.Items.Count; ++i) + { + Item item = targ.Items[i]; + + if (item.Layer == Layer.Mount) + { + item.Delete(); + --i; + } + } + } + } + } + + private class ClientTarget : Target + { + public ClientTarget() : base(-1, false, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile targ && targ.NetState != null) + { + CommandLogging.WriteLine(from, "{0} {1} opening client menu of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(targ)); + from.SendGump(new ClientGump(from, targ.NetState)); + } + } + } + + private class StuckMenuTarget : Target + { + public StuckMenuTarget() : base(-1, false, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile mobile) + { + if (mobile.AccessLevel >= from.AccessLevel && mobile != from) + from.SendMessage("You can't do that to someone with higher Accesslevel than you!"); + else + from.SendGump(new StuckMenu(from, mobile, false)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/HelpInfo.cs b/Scripts/Commands/HelpInfo.cs index 784a192fe..a450f80a1 100644 --- a/Scripts/Commands/HelpInfo.cs +++ b/Scripts/Commands/HelpInfo.cs @@ -1,413 +1,411 @@ -using System; using System.Collections.Generic; -using System.Text; using System.Reflection; +using System.Text; +using Server.Commands.Generic; using Server.Gumps; using Server.Network; -using Server.Commands.Generic; -using CommandInfo=Server.Commands.Docs.DocCommandEntry; -using CommandInfoSorter=Server.Commands.Docs.CommandEntrySorter; +using CommandInfo = Server.Commands.Docs.DocCommandEntry; +using CommandInfoSorter = Server.Commands.Docs.CommandEntrySorter; namespace Server.Commands { - public class HelpInfo - { - public static Dictionary HelpInfos { get; } = new Dictionary(); + public class HelpInfo + { + public static Dictionary HelpInfos{ get; } = new Dictionary(); - public static List SortedHelpInfo { get; private set; } = new List(); + public static List SortedHelpInfo{ get; private set; } = new List(); - [CallPriority( 100 )] - public static void Initialize() - { - CommandSystem.Register( "HelpInfo", AccessLevel.Player, HelpInfo_OnCommand ); + [CallPriority(100)] + public static void Initialize() + { + CommandSystem.Register("HelpInfo", AccessLevel.Player, HelpInfo_OnCommand); - FillTable(); - } + FillTable(); + } - [Usage( "HelpInfo []" )] - [Description( "Gives information on a specified command, or when no argument specified, displays a gump containing all commands" )] - private static void HelpInfo_OnCommand( CommandEventArgs e ) - { - if ( e.Length > 0 ) - { - string arg = e.GetString( 0 ).ToLower(); - if (HelpInfos.TryGetValue( arg, out CommandInfo c )) - { - Mobile m = e.Mobile; + [Usage("HelpInfo []")] + [Description( + "Gives information on a specified command, or when no argument specified, displays a gump containing all commands")] + private static void HelpInfo_OnCommand(CommandEventArgs e) + { + if (e.Length > 0) + { + string arg = e.GetString(0).ToLower(); + if (HelpInfos.TryGetValue(arg, out CommandInfo c)) + { + Mobile m = e.Mobile; - if ( m.AccessLevel >= c.AccessLevel ) - m.SendGump( new CommandInfoGump( c ) ); - else - m.SendMessage( "You don't have access to that command." ); + if (m.AccessLevel >= c.AccessLevel) + m.SendGump(new CommandInfoGump(c)); + else + m.SendMessage("You don't have access to that command."); - return; - } + return; + } - e.Mobile.SendMessage($"Command '{arg}' not found!"); - } + e.Mobile.SendMessage($"Command '{arg}' not found!"); + } - e.Mobile.SendGump( new CommandListGump( 0, e.Mobile, null ) ); + e.Mobile.SendGump(new CommandListGump(0, e.Mobile, null)); + } - } + public static void FillTable() + { + List commands = new List(CommandSystem.Entries.Values); + List list = new List(); - public static void FillTable() - { - List commands = new List( CommandSystem.Entries.Values ); - List list = new List(); + commands.Sort(); + commands.Reverse(); + Docs.Clean(commands); - commands.Sort(); - commands.Reverse(); - Docs.Clean( commands ); + for (int i = 0; i < commands.Count; ++i) + { + CommandEntry e = commands[i]; - for( int i = 0; i < commands.Count; ++i ) - { - CommandEntry e =commands[i]; + MethodInfo mi = e.Handler.Method; - MethodInfo mi = e.Handler.Method; + object[] attrs = mi.GetCustomAttributes(typeof(UsageAttribute), false); - object[] attrs = mi.GetCustomAttributes( typeof( UsageAttribute ), false ); + if (attrs.Length == 0) + continue; - if ( attrs.Length == 0 ) - continue; + UsageAttribute usage = attrs[0] as UsageAttribute; - UsageAttribute usage = attrs[0] as UsageAttribute; + attrs = mi.GetCustomAttributes(typeof(DescriptionAttribute), false); - attrs = mi.GetCustomAttributes( typeof( DescriptionAttribute ), false ); + if (attrs.Length == 0) + continue; - if ( attrs.Length == 0 ) - continue; + if (usage == null || !(attrs[0] is DescriptionAttribute desc)) + continue; - if ( usage == null || !(attrs[0] is DescriptionAttribute desc) ) - continue; + attrs = mi.GetCustomAttributes(typeof(AliasesAttribute), false); - attrs = mi.GetCustomAttributes( typeof( AliasesAttribute ), false ); + AliasesAttribute aliases = attrs.Length == 0 ? null : attrs[0] as AliasesAttribute; - AliasesAttribute aliases = (attrs.Length == 0 ? null : attrs[0] as AliasesAttribute); + string descString = desc.Description.Replace("<", "(").Replace(">", ")"); - string descString = desc.Description.Replace( "<", "(" ).Replace( ">", ")" ); + if (aliases == null) + { + list.Add(new CommandInfo(e.AccessLevel, e.Command, null, usage.Usage, descString)); + } + else + { + list.Add(new CommandInfo(e.AccessLevel, e.Command, aliases.Aliases, usage.Usage, descString)); - if ( aliases == null ) - list.Add( new CommandInfo( e.AccessLevel, e.Command, null, usage.Usage, descString ) ); - else - { - list.Add( new CommandInfo( e.AccessLevel, e.Command, aliases.Aliases, usage.Usage, descString ) ); + for (int j = 0; j < aliases.Aliases.Length; j++) + { + string[] newAliases = new string[aliases.Aliases.Length]; - for( int j = 0; j < aliases.Aliases.Length; j++ ) - { - string[] newAliases = new string[aliases.Aliases.Length]; + aliases.Aliases.CopyTo(newAliases, 0); - aliases.Aliases.CopyTo( newAliases, 0 ); + newAliases[j] = e.Command; - newAliases[j] = e.Command; + list.Add(new CommandInfo(e.AccessLevel, aliases.Aliases[j], newAliases, usage.Usage, descString)); + } + } + } - list.Add( new CommandInfo( e.AccessLevel, aliases.Aliases[j], newAliases, usage.Usage, descString ) ); - } - } - } + for (int i = 0; i < TargetCommands.AllCommands.Count; ++i) + { + BaseCommand command = TargetCommands.AllCommands[i]; - for( int i = 0; i < TargetCommands.AllCommands.Count; ++i ) - { - BaseCommand command = TargetCommands.AllCommands[i]; + string usage = command.Usage; + string desc = command.Description; - string usage = command.Usage; - string desc = command.Description; + if (usage == null || desc == null) + continue; - if ( usage == null || desc == null ) - continue; + string[] cmds = command.Commands; + string cmd = cmds[0]; + string[] aliases = new string[cmds.Length - 1]; - string[] cmds = command.Commands; - string cmd = cmds[0]; - string[] aliases = new string[cmds.Length - 1]; + for (int j = 0; j < aliases.Length; ++j) + aliases[j] = cmds[j + 1]; - for( int j = 0; j < aliases.Length; ++j ) - aliases[j] = cmds[j + 1]; + desc = desc.Replace("<", "(").Replace(">", ")"); - desc = desc.Replace( "<", "(" ).Replace( ">", ")" ); + if (command.Supports != CommandSupport.Single) + { + StringBuilder sb = new StringBuilder(50 + desc.Length); - if ( command.Supports != CommandSupport.Single ) - { - StringBuilder sb = new StringBuilder( 50 + desc.Length ); + sb.Append("Modifiers: "); - sb.Append( "Modifiers: " ); + if ((command.Supports & CommandSupport.Global) != 0) + sb.Append("Global, "); - if ( (command.Supports & CommandSupport.Global) != 0 ) - sb.Append( "Global, " ); + if ((command.Supports & CommandSupport.Online) != 0) + sb.Append("Online, "); - if ( (command.Supports & CommandSupport.Online) != 0 ) - sb.Append( "Online, " ); + if ((command.Supports & CommandSupport.Region) != 0) + sb.Append("Region, "); - if ( (command.Supports & CommandSupport.Region) != 0 ) - sb.Append( "Region, " ); + if ((command.Supports & CommandSupport.Contained) != 0) + sb.Append("Contained, "); - if ( (command.Supports & CommandSupport.Contained) != 0 ) - sb.Append( "Contained, " ); + if ((command.Supports & CommandSupport.Multi) != 0) + sb.Append("Multi, "); - if ( (command.Supports & CommandSupport.Multi) != 0 ) - sb.Append( "Multi, " ); + if ((command.Supports & CommandSupport.Area) != 0) + sb.Append("Area, "); - if ( (command.Supports & CommandSupport.Area) != 0 ) - sb.Append( "Area, " ); + if ((command.Supports & CommandSupport.Self) != 0) + sb.Append("Self, "); - if ( (command.Supports & CommandSupport.Self) != 0 ) - sb.Append( "Self, " ); + sb.Remove(sb.Length - 2, 2); + sb.Append("
"); + sb.Append(desc); - sb.Remove( sb.Length - 2, 2 ); - sb.Append( "
" ); - sb.Append( desc ); + desc = sb.ToString(); + } - desc = sb.ToString(); - } + list.Add(new CommandInfo(command.AccessLevel, cmd, aliases, usage, desc)); - list.Add( new CommandInfo( command.AccessLevel, cmd, aliases, usage, desc ) ); + for (int j = 0; j < aliases.Length; j++) + { + string[] newAliases = new string[aliases.Length]; - for( int j = 0; j < aliases.Length; j++ ) - { - string[] newAliases = new string[aliases.Length]; + aliases.CopyTo(newAliases, 0); - aliases.CopyTo( newAliases, 0 ); + newAliases[j] = cmd; - newAliases[j] = cmd; + list.Add(new CommandInfo(command.AccessLevel, aliases[j], newAliases, usage, desc)); + } + } - list.Add( new CommandInfo( command.AccessLevel, aliases[j], newAliases, usage, desc ) ); - } - } + List commandImpls = BaseCommandImplementor.Implementors; - List commandImpls = BaseCommandImplementor.Implementors; + for (int i = 0; i < commandImpls.Count; ++i) + { + BaseCommandImplementor command = commandImpls[i]; - for( int i = 0; i < commandImpls.Count; ++i ) - { - BaseCommandImplementor command = commandImpls[i]; + string usage = command.Usage; + string desc = command.Description; - string usage = command.Usage; - string desc = command.Description; + if (usage == null || desc == null) + continue; - if ( usage == null || desc == null ) - continue; + string[] cmds = command.Accessors; + string cmd = cmds[0]; + string[] aliases = new string[cmds.Length - 1]; - string[] cmds = command.Accessors; - string cmd = cmds[0]; - string[] aliases = new string[cmds.Length - 1]; + for (int j = 0; j < aliases.Length; ++j) + aliases[j] = cmds[j + 1]; - for( int j = 0; j < aliases.Length; ++j ) - aliases[j] = cmds[j + 1]; + desc = desc.Replace("<", ")").Replace(">", ")"); - desc = desc.Replace( "<", ")" ).Replace( ">", ")" ); + list.Add(new CommandInfo(command.AccessLevel, cmd, aliases, usage, desc)); - list.Add( new CommandInfo( command.AccessLevel, cmd, aliases, usage, desc ) ); + for (int j = 0; j < aliases.Length; j++) + { + string[] newAliases = new string[aliases.Length]; - for( int j = 0; j < aliases.Length; j++ ) - { - string[] newAliases = new string[aliases.Length]; + aliases.CopyTo(newAliases, 0); - aliases.CopyTo( newAliases, 0 ); + newAliases[j] = cmd; - newAliases[j] = cmd; + list.Add(new CommandInfo(command.AccessLevel, aliases[j], newAliases, usage, desc)); + } + } - list.Add( new CommandInfo( command.AccessLevel, aliases[j], newAliases, usage, desc ) ); - } - } + list.Sort(new CommandInfoSorter()); - list.Sort( new CommandInfoSorter() ); + SortedHelpInfo = list; - SortedHelpInfo = list; + foreach (CommandInfo c in SortedHelpInfo) + if (!HelpInfos.ContainsKey(c.Name.ToLower())) + HelpInfos.Add(c.Name.ToLower(), c); + } - foreach( CommandInfo c in SortedHelpInfo ) - { - if ( !HelpInfos.ContainsKey( c.Name.ToLower() ) ) - HelpInfos.Add( c.Name.ToLower(), c ); - } - } + public class CommandListGump : BaseGridGump + { + private const int EntriesPerPage = 15; + private List m_List; - public class CommandListGump : BaseGridGump - { - private const int EntriesPerPage = 15; + private int m_Page; - int m_Page; - List m_List; + public CommandListGump(int page, Mobile from, List list) + : base(30, 30) + { + m_Page = page; - public CommandListGump( int page, Mobile from, List list ) - : base( 30, 30 ) - { - m_Page = page; + if (list == null) + { + m_List = new List(); - if ( list == null ) - { - m_List = new List(); + foreach (CommandInfo c in SortedHelpInfo) + if (from.AccessLevel >= c.AccessLevel) + m_List.Add(c); + } + else + { + m_List = list; + } - foreach( CommandInfo c in SortedHelpInfo ) - { - if ( from.AccessLevel >= c.AccessLevel ) - m_List.Add( c ); - } - } - else - m_List = list; + AddNewPage(); - AddNewPage(); + if (m_Page > 0) + AddEntryButton(20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight); + else + AddEntryHeader(20); - if ( m_Page > 0 ) - AddEntryButton( 20, ArrowLeftID1, ArrowLeftID2, 1, ArrowLeftWidth, ArrowLeftHeight ); - else - AddEntryHeader( 20 ); + AddEntryHtml(160, Center( + $"Page {m_Page + 1} of {(m_List.Count + EntriesPerPage - 1) / EntriesPerPage}")); - AddEntryHtml( 160, Center( - $"Page {m_Page + 1} of {(m_List.Count + EntriesPerPage - 1) / EntriesPerPage}") ); - - if ( (m_Page + 1) * EntriesPerPage < m_List.Count ) - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight ); - else - AddEntryHeader( 20 ); - - int last = (int)AccessLevel.Player - 1; - - for( int i = m_Page * EntriesPerPage, line = 0; line < EntriesPerPage && i < m_List.Count; ++i, ++line ) - { - CommandInfo c = m_List[i]; - if ( from.AccessLevel >= c.AccessLevel ) - { - if ( (int)c.AccessLevel != last ) - { - AddNewLine(); - - AddEntryHtml( 20 + OffsetSize + 160, Color( c.AccessLevel.ToString(), 0xFF0000 ) ); - AddEntryHeader( 20 ); - line++; - } - - last = (int)c.AccessLevel; - - AddNewLine(); - - AddEntryHtml( 20 + OffsetSize + 160, c.Name ); - - AddEntryButton( 20, ArrowRightID1, ArrowRightID2, 3 + i, ArrowRightWidth, ArrowRightHeight ); - } - } - - FinishPage(); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile m = sender.Mobile; - switch( info.ButtonID ) - { - case 0: - { - m.CloseGump( typeof( CommandInfoGump ) ); - break; - } - case 1: - { - if ( m_Page > 0 ) - m.SendGump( new CommandListGump( m_Page - 1, m, m_List ) ); - - break; - } - case 2: - { - if ( (m_Page + 1) * EntriesPerPage < SortedHelpInfo.Count ) - m.SendGump( new CommandListGump( m_Page + 1, m, m_List ) ); - - break; - } - default: - { - - int v = info.ButtonID - 3; - - if ( v >= 0 && v < m_List.Count ) - { - CommandInfo c = m_List[v]; - - if ( m.AccessLevel >= c.AccessLevel ) - { - m.SendGump( new CommandInfoGump( c ) ); - m.SendGump( new CommandListGump( m_Page, m, m_List ) ); - } - else - { - m.SendMessage( "You no longer have access to that command." ); - m.SendGump( new CommandListGump( m_Page, m, null ) ); - } - } - break; - } - } - } - } - - - public class CommandInfoGump : Gump - { - public string Color( string text, int color ) - { - return $"{text}"; - } - - public string Center( string text ) - { - return $"
{text}
"; - } - - public CommandInfoGump( CommandInfo info ) - : this( info, 320, 200 ) - { - } - - public CommandInfoGump( CommandInfo info, int width, int height ) - : base( 300, 50 ) - { - AddPage( 0 ); - - AddBackground( 0, 0, width, height, 5054 ); - - //AddImageTiled( 10, 10, width - 20, 20, 2624 ); - //AddAlphaRegion( 10, 10, width - 20, 20 ); - //AddHtmlLocalized( 10, 10, width - 20, 20, header, headerColor, false, false ); - AddHtml( 10, 10, width - 20, 20, Color( Center( info.Name ), 0xFF0000 ), false, false ); - - //AddImageTiled( 10, 40, width - 20, height - 80, 2624 ); - //AddAlphaRegion( 10, 40, width - 20, height - 80 ); - - StringBuilder sb = new StringBuilder(); - - sb.Append( "Usage: " ); - sb.Append( info.Usage.Replace( "<", "(" ).Replace( ">", ")" ) ); - sb.Append( "
" ); - - string[] aliases = info.Aliases; - - if ( aliases != null && aliases.Length != 0 ) - { - sb.Append($"Alias{(aliases.Length == 1 ? "" : "es")}: "); - - for( int i = 0; i < aliases.Length; ++i ) - { - if ( i != 0 ) - sb.Append( ", " ); - - sb.Append( aliases[i] ); - } - - sb.Append( "
" ); - } - - sb.Append( "AccessLevel: " ); - sb.Append( info.AccessLevel.ToString() ); - sb.Append( "
" ); - sb.Append( "
" ); - - sb.Append( info.Description ); - - AddHtml( 10, 40, width - 20, height - 80, sb.ToString(), false, true ); - - //AddImageTiled( 10, height - 30, width - 20, 20, 2624 ); - //AddAlphaRegion( 10, height - 30, width - 20, 20 ); - - } - } - } -} + if ((m_Page + 1) * EntriesPerPage < m_List.Count) + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 2, ArrowRightWidth, ArrowRightHeight); + else + AddEntryHeader(20); + + int last = (int)AccessLevel.Player - 1; + + for (int i = m_Page * EntriesPerPage, line = 0; line < EntriesPerPage && i < m_List.Count; ++i, ++line) + { + CommandInfo c = m_List[i]; + if (from.AccessLevel >= c.AccessLevel) + { + if ((int)c.AccessLevel != last) + { + AddNewLine(); + + AddEntryHtml(20 + OffsetSize + 160, Color(c.AccessLevel.ToString(), 0xFF0000)); + AddEntryHeader(20); + line++; + } + + last = (int)c.AccessLevel; + + AddNewLine(); + + AddEntryHtml(20 + OffsetSize + 160, c.Name); + + AddEntryButton(20, ArrowRightID1, ArrowRightID2, 3 + i, ArrowRightWidth, ArrowRightHeight); + } + } + + FinishPage(); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile m = sender.Mobile; + switch (info.ButtonID) + { + case 0: + { + m.CloseGump(typeof(CommandInfoGump)); + break; + } + case 1: + { + if (m_Page > 0) + m.SendGump(new CommandListGump(m_Page - 1, m, m_List)); + + break; + } + case 2: + { + if ((m_Page + 1) * EntriesPerPage < SortedHelpInfo.Count) + m.SendGump(new CommandListGump(m_Page + 1, m, m_List)); + + break; + } + default: + { + int v = info.ButtonID - 3; + + if (v >= 0 && v < m_List.Count) + { + CommandInfo c = m_List[v]; + + if (m.AccessLevel >= c.AccessLevel) + { + m.SendGump(new CommandInfoGump(c)); + m.SendGump(new CommandListGump(m_Page, m, m_List)); + } + else + { + m.SendMessage("You no longer have access to that command."); + m.SendGump(new CommandListGump(m_Page, m, null)); + } + } + + break; + } + } + } + } + + + public class CommandInfoGump : Gump + { + public CommandInfoGump(CommandInfo info) + : this(info, 320, 200) + { + } + + public CommandInfoGump(CommandInfo info, int width, int height) + : base(300, 50) + { + AddPage(0); + + AddBackground(0, 0, width, height, 5054); + + //AddImageTiled( 10, 10, width - 20, 20, 2624 ); + //AddAlphaRegion( 10, 10, width - 20, 20 ); + //AddHtmlLocalized( 10, 10, width - 20, 20, header, headerColor, false, false ); + AddHtml(10, 10, width - 20, 20, Color(Center(info.Name), 0xFF0000), false, false); + + //AddImageTiled( 10, 40, width - 20, height - 80, 2624 ); + //AddAlphaRegion( 10, 40, width - 20, height - 80 ); + + StringBuilder sb = new StringBuilder(); + + sb.Append("Usage: "); + sb.Append(info.Usage.Replace("<", "(").Replace(">", ")")); + sb.Append("
"); + + string[] aliases = info.Aliases; + + if (aliases != null && aliases.Length != 0) + { + sb.Append($"Alias{(aliases.Length == 1 ? "" : "es")}: "); + + for (int i = 0; i < aliases.Length; ++i) + { + if (i != 0) + sb.Append(", "); + + sb.Append(aliases[i]); + } + + sb.Append("
"); + } + + sb.Append("AccessLevel: "); + sb.Append(info.AccessLevel.ToString()); + sb.Append("
"); + sb.Append("
"); + + sb.Append(info.Description); + + AddHtml(10, 40, width - 20, height - 80, sb.ToString(), false, true); + + //AddImageTiled( 10, height - 30, width - 20, 20, 2624 ); + //AddAlphaRegion( 10, height - 30, width - 20, 20 ); + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + public string Center(string text) + { + return $"
{text}
"; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Logging.cs b/Scripts/Commands/Logging.cs index d81a574b2..55b69d97f 100644 --- a/Scripts/Commands/Logging.cs +++ b/Scripts/Commands/Logging.cs @@ -1,137 +1,139 @@ using System; using System.IO; +using System.Text; using Server.Accounting; namespace Server.Commands { - public class CommandLogging - { - public static bool Enabled { get; set; } = true; + public class CommandLogging + { + private static char[] m_NotSafe = { '\\', '/', ':', '*', '?', '"', '<', '>', '|' }; + public static bool Enabled{ get; set; } = true; - public static StreamWriter Output { get; private set; } + public static StreamWriter Output{ get; private set; } - public static void Initialize() - { - EventSink.Command += EventSink_Command; + public static void Initialize() + { + EventSink.Command += EventSink_Command; - if ( !Directory.Exists( "Logs" ) ) - Directory.CreateDirectory( "Logs" ); + if (!Directory.Exists("Logs")) + Directory.CreateDirectory("Logs"); - string directory = "Logs/Commands"; + string directory = "Logs/Commands"; - if ( !Directory.Exists( directory ) ) - Directory.CreateDirectory( directory ); + if (!Directory.Exists(directory)) + Directory.CreateDirectory(directory); - try - { - Output = new StreamWriter( Path.Combine( directory, $"{DateTime.UtcNow.ToLongDateString()}.log"), true ); + try + { + Output = new StreamWriter(Path.Combine(directory, $"{DateTime.UtcNow.ToLongDateString()}.log"), true); - Output.AutoFlush = true; + Output.AutoFlush = true; - Output.WriteLine( "##############################" ); - Output.WriteLine( "Log started on {0}", DateTime.UtcNow ); - Output.WriteLine(); - } - catch - { - } - } + Output.WriteLine("##############################"); + Output.WriteLine("Log started on {0}", DateTime.UtcNow); + Output.WriteLine(); + } + catch + { + } + } - public static object Format( object o ) - { - if ( o is Mobile m ) - { - if ( m.Account == null ) - return $"{m} (no account)"; + public static object Format(object o) + { + if (o is Mobile m) + { + if (m.Account == null) + return $"{m} (no account)"; - return $"{m} ('{m.Account.Username}')"; - } - if ( o is Item item ) - { - return $"0x{item.Serial.Value:X} ({item.GetType().Name})"; - } + return $"{m} ('{m.Account.Username}')"; + } - return o; - } + if (o is Item item) return $"0x{item.Serial.Value:X} ({item.GetType().Name})"; - public static void WriteLine( Mobile from, string format, params object[] args ) - { - if ( !Enabled ) - return; + return o; + } - WriteLine( from, string.Format( format, args ) ); - } + public static void WriteLine(Mobile from, string format, params object[] args) + { + if (!Enabled) + return; - public static void WriteLine( Mobile from, string text ) - { - if ( !Enabled ) - return; + WriteLine(from, string.Format(format, args)); + } - try - { - Output.WriteLine( "{0}: {1}: {2}", DateTime.UtcNow, from.NetState, text ); + public static void WriteLine(Mobile from, string text) + { + if (!Enabled) + return; - string path = Core.BaseDirectory; + try + { + Output.WriteLine("{0}: {1}: {2}", DateTime.UtcNow, from.NetState, text); - string name = ( !(from.Account is Account acct) ? from.Name : acct.Username ); + string path = Core.BaseDirectory; - AppendPath( ref path, "Logs" ); - AppendPath( ref path, "Commands" ); - AppendPath( ref path, from.AccessLevel.ToString() ); - path = Path.Combine( path, $"{name}.log"); + string name = !(from.Account is Account acct) ? from.Name : acct.Username; - using ( StreamWriter sw = new StreamWriter( path, true ) ) - sw.WriteLine( "{0}: {1}: {2}", DateTime.UtcNow, from.NetState, text ); - } - catch - { - } - } + AppendPath(ref path, "Logs"); + AppendPath(ref path, "Commands"); + AppendPath(ref path, from.AccessLevel.ToString()); + path = Path.Combine(path, $"{name}.log"); - private static char[] m_NotSafe = { '\\', '/', ':', '*', '?', '"', '<', '>', '|' }; + using (StreamWriter sw = new StreamWriter(path, true)) + { + sw.WriteLine("{0}: {1}: {2}", DateTime.UtcNow, from.NetState, text); + } + } + catch + { + } + } - public static void AppendPath( ref string path, string toAppend ) - { - path = Path.Combine( path, toAppend ); + public static void AppendPath(ref string path, string toAppend) + { + path = Path.Combine(path, toAppend); - if ( !Directory.Exists( path ) ) - Directory.CreateDirectory( path ); - } + if (!Directory.Exists(path)) + Directory.CreateDirectory(path); + } - public static string Safe( string ip ) - { - if ( ip == null ) - return "null"; + public static string Safe(string ip) + { + if (ip == null) + return "null"; - ip = ip.Trim(); + ip = ip.Trim(); - if ( ip.Length == 0 ) - return "empty"; + if (ip.Length == 0) + return "empty"; - bool isSafe = true; + bool isSafe = true; - for ( int i = 0; isSafe && i < m_NotSafe.Length; ++i ) - isSafe = ( ip.IndexOf( m_NotSafe[i] ) == -1 ); + for (int i = 0; isSafe && i < m_NotSafe.Length; ++i) + isSafe = ip.IndexOf(m_NotSafe[i]) == -1; - if ( isSafe ) - return ip; + if (isSafe) + return ip; - System.Text.StringBuilder sb = new System.Text.StringBuilder( ip ); + StringBuilder sb = new StringBuilder(ip); - for ( int i = 0; i < m_NotSafe.Length; ++i ) - sb.Replace( m_NotSafe[i], '_' ); + for (int i = 0; i < m_NotSafe.Length; ++i) + sb.Replace(m_NotSafe[i], '_'); - return sb.ToString(); - } + return sb.ToString(); + } - public static void EventSink_Command( CommandEventArgs e ) - { - WriteLine( e.Mobile, "{0} {1} used command '{2} {3}'", e.Mobile.AccessLevel, Format( e.Mobile ), e.Command, e.ArgString ); - } + public static void EventSink_Command(CommandEventArgs e) + { + WriteLine(e.Mobile, "{0} {1} used command '{2} {3}'", e.Mobile.AccessLevel, Format(e.Mobile), e.Command, + e.ArgString); + } - public static void LogChangeProperty( Mobile from, object o, string name, string value ) - { - WriteLine( from, "{0} {1} set property '{2}' of {3} to '{4}'", from.AccessLevel, Format( from ), name, Format( o ), value ); - } - } -} + public static void LogChangeProperty(Mobile from, object o, string name, string value) + { + WriteLine(from, "{0} {1} set property '{2}' of {3} to '{4}'", from.AccessLevel, Format(from), name, Format(o), + value); + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Profiling.cs b/Scripts/Commands/Profiling.cs index 4e1843b1c..022a6e47f 100644 --- a/Scripts/Commands/Profiling.cs +++ b/Scripts/Commands/Profiling.cs @@ -1,396 +1,399 @@ using System; -using System.IO; using System.Collections; +using System.IO; using Server.Diagnostics; namespace Server.Commands { - public class Profiling - { - public static void Initialize() - { - CommandSystem.Register( "DumpTimers", AccessLevel.Administrator, DumpTimers_OnCommand ); - CommandSystem.Register( "CountObjects", AccessLevel.Administrator, CountObjects_OnCommand ); - CommandSystem.Register( "ProfileWorld", AccessLevel.Administrator, ProfileWorld_OnCommand ); - CommandSystem.Register( "TraceInternal", AccessLevel.Administrator, TraceInternal_OnCommand ); - CommandSystem.Register( "TraceExpanded", AccessLevel.Administrator, TraceExpanded_OnCommand ); - CommandSystem.Register( "WriteProfiles", AccessLevel.Administrator, WriteProfiles_OnCommand ); - CommandSystem.Register( "SetProfiles", AccessLevel.Administrator, SetProfiles_OnCommand ); - } - - [Usage( "WriteProfiles" )] - [Description( "Generates a log files containing performance diagnostic information." )] - public static void WriteProfiles_OnCommand( CommandEventArgs e ) - { - try - { - using ( StreamWriter sw = new StreamWriter( "profiles.log", true ) ) - { - sw.WriteLine( "# Dump on {0:f}", DateTime.UtcNow ); - sw.WriteLine( "# Core profiling for " + Core.ProfileTime ); - - sw.WriteLine( "# Packet send" ); - BaseProfile.WriteAll( sw, PacketSendProfile.Profiles ); - sw.WriteLine(); - - sw.WriteLine( "# Packet receive" ); - BaseProfile.WriteAll( sw, PacketReceiveProfile.Profiles ); - sw.WriteLine(); - - sw.WriteLine( "# Timer" ); - BaseProfile.WriteAll( sw, TimerProfile.Profiles ); - sw.WriteLine(); - - sw.WriteLine( "# Gump response" ); - BaseProfile.WriteAll( sw, GumpProfile.Profiles ); - sw.WriteLine(); - - sw.WriteLine( "# Target response" ); - BaseProfile.WriteAll( sw, TargetProfile.Profiles ); - sw.WriteLine(); - } - } - catch - { - } - } - - [Usage( "SetProfiles [true | false]" )] - [Description( "Enables, disables, or toggles the state of core packet and timer profiling." )] - public static void SetProfiles_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 1 ) - Core.Profiling = e.GetBoolean( 0 ); - else - Core.Profiling = !Core.Profiling; - - e.Mobile.SendMessage( "Profiling has been {0}.", Core.Profiling ? "enabled" : "disabled" ); - } - - [Usage( "DumpTimers" )] - [Description( "Generates a log file of all currently executing timers. Used for tracing timer leaks." )] - public static void DumpTimers_OnCommand( CommandEventArgs e ) - { - try - { - using ( StreamWriter sw = new StreamWriter( "timerdump.log", true ) ) - Timer.DumpInfo( sw ); - } - catch - { - } - } - - private class CountSorter : IComparer - { - public int Compare( object x, object y ) - { - DictionaryEntry a = (DictionaryEntry)x; - DictionaryEntry b = (DictionaryEntry)y; - - int aCount = GetCount( a.Value ); - int bCount = GetCount( b.Value ); - - int v = -aCount.CompareTo( bCount ); - - if ( v == 0 ) - { - Type aType = (Type)a.Key; - Type bType = (Type)b.Key; - - v = aType.FullName.CompareTo( bType.FullName ); - } - - return v; - } - - private int GetCount( object obj ) - { - if ( obj is int intObj ) - return intObj; - - if ( obj is int[] list ) - { - int total = 0; - - for ( int i = 0; i < list.Length; ++i ) - total += list[i]; - - return total; - } - - return 0; - } - } - - [Usage( "CountObjects" )] - [Description( "Generates a log file detailing all item and mobile types in the world." )] - public static void CountObjects_OnCommand( CommandEventArgs e ) - { - using ( StreamWriter op = new StreamWriter( "objects.log" ) ) - { - Hashtable table = new Hashtable(); + public class Profiling + { + public static void Initialize() + { + CommandSystem.Register("DumpTimers", AccessLevel.Administrator, DumpTimers_OnCommand); + CommandSystem.Register("CountObjects", AccessLevel.Administrator, CountObjects_OnCommand); + CommandSystem.Register("ProfileWorld", AccessLevel.Administrator, ProfileWorld_OnCommand); + CommandSystem.Register("TraceInternal", AccessLevel.Administrator, TraceInternal_OnCommand); + CommandSystem.Register("TraceExpanded", AccessLevel.Administrator, TraceExpanded_OnCommand); + CommandSystem.Register("WriteProfiles", AccessLevel.Administrator, WriteProfiles_OnCommand); + CommandSystem.Register("SetProfiles", AccessLevel.Administrator, SetProfiles_OnCommand); + } + + [Usage("WriteProfiles")] + [Description("Generates a log files containing performance diagnostic information.")] + public static void WriteProfiles_OnCommand(CommandEventArgs e) + { + try + { + using (StreamWriter sw = new StreamWriter("profiles.log", true)) + { + sw.WriteLine("# Dump on {0:f}", DateTime.UtcNow); + sw.WriteLine("# Core profiling for " + Core.ProfileTime); + + sw.WriteLine("# Packet send"); + BaseProfile.WriteAll(sw, PacketSendProfile.Profiles); + sw.WriteLine(); + + sw.WriteLine("# Packet receive"); + BaseProfile.WriteAll(sw, PacketReceiveProfile.Profiles); + sw.WriteLine(); + + sw.WriteLine("# Timer"); + BaseProfile.WriteAll(sw, TimerProfile.Profiles); + sw.WriteLine(); + + sw.WriteLine("# Gump response"); + BaseProfile.WriteAll(sw, GumpProfile.Profiles); + sw.WriteLine(); + + sw.WriteLine("# Target response"); + BaseProfile.WriteAll(sw, TargetProfile.Profiles); + sw.WriteLine(); + } + } + catch + { + } + } + + [Usage("SetProfiles [true | false]")] + [Description("Enables, disables, or toggles the state of core packet and timer profiling.")] + public static void SetProfiles_OnCommand(CommandEventArgs e) + { + if (e.Length == 1) + Core.Profiling = e.GetBoolean(0); + else + Core.Profiling = !Core.Profiling; + + e.Mobile.SendMessage("Profiling has been {0}.", Core.Profiling ? "enabled" : "disabled"); + } + + [Usage("DumpTimers")] + [Description("Generates a log file of all currently executing timers. Used for tracing timer leaks.")] + public static void DumpTimers_OnCommand(CommandEventArgs e) + { + try + { + using (StreamWriter sw = new StreamWriter("timerdump.log", true)) + { + Timer.DumpInfo(sw); + } + } + catch + { + } + } + + [Usage("CountObjects")] + [Description("Generates a log file detailing all item and mobile types in the world.")] + public static void CountObjects_OnCommand(CommandEventArgs e) + { + using (StreamWriter op = new StreamWriter("objects.log")) + { + Hashtable table = new Hashtable(); + + foreach (Item item in World.Items.Values) + { + Type type = item.GetType(); + + object o = table[type]; + + if (o == null) + table[type] = 1; + else + table[type] = 1 + (int)o; + } + + ArrayList items = new ArrayList(table); + + table.Clear(); + + foreach (Mobile m in World.Mobiles.Values) + { + Type type = m.GetType(); + + object o = table[type]; + + if (o == null) + table[type] = 1; + else + table[type] = 1 + (int)o; + } + + ArrayList mobiles = new ArrayList(table); + + items.Sort(new CountSorter()); + mobiles.Sort(new CountSorter()); + + op.WriteLine("# Object count table generated on {0}", DateTime.UtcNow); + op.WriteLine(); + op.WriteLine(); + + op.WriteLine("# Items:"); + + foreach (DictionaryEntry de in items) + op.WriteLine("{0}\t{1:F2}%\t{2}", de.Value, 100 * (int)de.Value / (double)World.Items.Count, de.Key); + + op.WriteLine(); + op.WriteLine(); + + op.WriteLine("#Mobiles:"); + + foreach (DictionaryEntry de in mobiles) + op.WriteLine("{0}\t{1:F2}%\t{2}", de.Value, 100 * (int)de.Value / (double)World.Mobiles.Count, de.Key); + } + + e.Mobile.SendMessage("Object table has been generated. See the file : /objects.log"); + } + + [Usage("TraceExpanded")] + [Description("Generates a log file describing all items using expanded memory.")] + public static void TraceExpanded_OnCommand(CommandEventArgs e) + { + Hashtable typeTable = new Hashtable(); + + foreach (Item item in World.Items.Values) + { + ExpandFlag flags = item.GetExpandFlags(); + + if ((flags & ~(ExpandFlag.TempFlag | ExpandFlag.SaveFlag)) == 0) + continue; + + Type itemType = item.GetType(); + + do + { + if (!(typeTable[itemType] is int[] countTable)) + typeTable[itemType] = countTable = new int[9]; + + if ((flags & ExpandFlag.Name) != 0) + ++countTable[0]; + + if ((flags & ExpandFlag.Items) != 0) + ++countTable[1]; + + if ((flags & ExpandFlag.Bounce) != 0) + ++countTable[2]; + + if ((flags & ExpandFlag.Holder) != 0) + ++countTable[3]; + + if ((flags & ExpandFlag.Blessed) != 0) + ++countTable[4]; - foreach ( Item item in World.Items.Values ) - { - Type type = item.GetType(); + /*if ( ( flags & ExpandFlag.TempFlag ) != 0 ) + ++countTable[5]; - object o = (object)table[type]; + if ( ( flags & ExpandFlag.SaveFlag ) != 0 ) + ++countTable[6];*/ + + if ((flags & ExpandFlag.Weight) != 0) + ++countTable[7]; - if ( o == null ) - table[type] = 1; - else - table[type] = 1 + (int)o; - } - - ArrayList items = new ArrayList( table ); - - table.Clear(); - - foreach ( Mobile m in World.Mobiles.Values ) - { - Type type = m.GetType(); - - object o = (object)table[type]; - - if ( o == null ) - table[type] = 1; - else - table[type] = 1 + (int)o; - } - - ArrayList mobiles = new ArrayList( table ); - - items.Sort( new CountSorter() ); - mobiles.Sort( new CountSorter() ); - - op.WriteLine( "# Object count table generated on {0}", DateTime.UtcNow ); - op.WriteLine(); - op.WriteLine(); - - op.WriteLine( "# Items:" ); - - foreach ( DictionaryEntry de in items ) - op.WriteLine( "{0}\t{1:F2}%\t{2}", de.Value, (100 * (int)de.Value) / (double)World.Items.Count, de.Key ); - - op.WriteLine(); - op.WriteLine(); - - op.WriteLine( "#Mobiles:" ); - - foreach ( DictionaryEntry de in mobiles ) - op.WriteLine( "{0}\t{1:F2}%\t{2}", de.Value, (100 * (int)de.Value) / (double)World.Mobiles.Count, de.Key ); - } - - e.Mobile.SendMessage( "Object table has been generated. See the file : /objects.log" ); - } - - [Usage( "TraceExpanded" )] - [Description( "Generates a log file describing all items using expanded memory." )] - public static void TraceExpanded_OnCommand( CommandEventArgs e ) - { - Hashtable typeTable = new Hashtable(); - - foreach ( Item item in World.Items.Values ) - { - ExpandFlag flags = item.GetExpandFlags(); - - if ( ( flags & ~(ExpandFlag.TempFlag | ExpandFlag.SaveFlag) ) == 0 ) - continue; - - Type itemType = item.GetType(); - - do - { - if ( !(typeTable[itemType] is int[] countTable) ) - typeTable[itemType] = countTable = new int[9]; - - if ( ( flags & ExpandFlag.Name ) != 0 ) - ++countTable[0]; - - if ( ( flags & ExpandFlag.Items ) != 0 ) - ++countTable[1]; - - if ( ( flags & ExpandFlag.Bounce ) != 0 ) - ++countTable[2]; - - if ( ( flags & ExpandFlag.Holder ) != 0 ) - ++countTable[3]; - - if ( ( flags & ExpandFlag.Blessed ) != 0 ) - ++countTable[4]; - - /*if ( ( flags & ExpandFlag.TempFlag ) != 0 ) - ++countTable[5]; - - if ( ( flags & ExpandFlag.SaveFlag ) != 0 ) - ++countTable[6];*/ - - if ( ( flags & ExpandFlag.Weight ) != 0 ) - ++countTable[7]; - - if ((flags & ExpandFlag.Spawner) != 0) - ++countTable[8]; - - itemType = itemType.BaseType; - } while ( itemType != typeof( object ) ); - } - - try - { - using ( StreamWriter op = new StreamWriter( "expandedItems.log", true ) ) - { - string[] names = { - "Name", - "Items", - "Bounce", - "Holder", - "Blessed", - "TempFlag", - "SaveFlag", - "Weight", - "Spawner" - }; - - ArrayList list = new ArrayList( typeTable ); - - list.Sort( new CountSorter() ); - - foreach ( DictionaryEntry de in list ) - { - Type itemType = de.Key as Type; - int[] countTable = de.Value as int[]; - - op.WriteLine( "# {0}", itemType.FullName ); - - for ( int i = 0; i < countTable.Length; ++i ) - { - if ( countTable[i] > 0 ) - op.WriteLine( "{0}\t{1:N0}", names[i], countTable[i] ); - } - - op.WriteLine(); - } - } - } - catch - { - } - } - - [Usage( "TraceInternal" )] - [Description( "Generates a log file describing all items in the 'internal' map." )] - public static void TraceInternal_OnCommand( CommandEventArgs e ) - { - int totalCount = 0; - Hashtable table = new Hashtable(); - - foreach ( Item item in World.Items.Values ) - { - if ( item.Parent != null || item.Map != Map.Internal ) - continue; - - ++totalCount; - - Type type = item.GetType(); - int[] parms = (int[])table[type]; - - if ( parms == null ) - table[type] = parms = new[]{ 0, 0 }; - - parms[0]++; - parms[1] += item.Amount; - } - - using ( StreamWriter op = new StreamWriter( "internal.log" ) ) - { - op.WriteLine( "# {0} items found", totalCount ); - op.WriteLine( "# {0} different types", table.Count ); - op.WriteLine(); - op.WriteLine(); - op.WriteLine( "Type\t\tCount\t\tAmount\t\tAvg. Amount" ); - - foreach ( DictionaryEntry de in table ) - { - Type type = (Type)de.Key; - int[] parms = (int[])de.Value; - - op.WriteLine( "{0}\t\t{1}\t\t{2}\t\t{3:F2}", type.Name, parms[0], parms[1], (double)parms[1] / parms[0] ); - } - } - } - - [Usage( "ProfileWorld" )] - [Description( "Prints the amount of data serialized for every object type in your world file." )] - public static void ProfileWorld_OnCommand( CommandEventArgs e ) - { - ProfileWorld( "items", "worldprofile_items.log" ); - ProfileWorld( "mobiles", "worldprofile_mobiles.log" ); - } - - public static void ProfileWorld( string type, string opFile ) - { - try - { - ArrayList types = new ArrayList(); - - using ( BinaryReader bin = new BinaryReader( new FileStream( string.Format( "Saves/{0}/{0}.tdb", type ), FileMode.Open, FileAccess.Read, FileShare.Read ) ) ) - { - int count = bin.ReadInt32(); - - for ( int i = 0; i < count; ++i ) - types.Add( ScriptCompiler.FindTypeByFullName( bin.ReadString() ) ); - } - - long total = 0; - - Hashtable table = new Hashtable(); - - using ( BinaryReader bin = new BinaryReader( new FileStream( string.Format( "Saves/{0}/{0}.idx", type ), FileMode.Open, FileAccess.Read, FileShare.Read ) ) ) - { - int count = bin.ReadInt32(); - - for ( int i = 0; i < count; ++i ) - { - int typeID = bin.ReadInt32(); - int serial = bin.ReadInt32(); - long pos = bin.ReadInt64(); - int length = bin.ReadInt32(); - Type objType = (Type)types[typeID]; - - while ( objType != null && objType != typeof( object ) ) - { - object obj = table[objType]; - - if ( obj == null ) - table[objType] = length; - else - table[objType] = length + (int)obj; - - objType = objType.BaseType; - total += length; - } - } - } - - ArrayList list = new ArrayList( table ); - - list.Sort( new CountSorter() ); - - using ( StreamWriter op = new StreamWriter( opFile ) ) - { - op.WriteLine( "# Profile of world {0}", type ); - op.WriteLine( "# Generated on {0}", DateTime.UtcNow ); - op.WriteLine(); - op.WriteLine(); - - foreach ( DictionaryEntry de in list ) - op.WriteLine( "{0}\t{1:F2}%\t{2}", de.Value, (100 * (int)de.Value) / (double)total, de.Key ); - } - } - catch - { - } - } - } -} + if ((flags & ExpandFlag.Spawner) != 0) + ++countTable[8]; + + itemType = itemType.BaseType; + } while (itemType != typeof(object)); + } + + try + { + using (StreamWriter op = new StreamWriter("expandedItems.log", true)) + { + string[] names = + { + "Name", + "Items", + "Bounce", + "Holder", + "Blessed", + "TempFlag", + "SaveFlag", + "Weight", + "Spawner" + }; + + ArrayList list = new ArrayList(typeTable); + + list.Sort(new CountSorter()); + + foreach (DictionaryEntry de in list) + { + Type itemType = de.Key as Type; + int[] countTable = de.Value as int[]; + + op.WriteLine("# {0}", itemType.FullName); + + for (int i = 0; i < countTable.Length; ++i) + if (countTable[i] > 0) + op.WriteLine("{0}\t{1:N0}", names[i], countTable[i]); + + op.WriteLine(); + } + } + } + catch + { + } + } + + [Usage("TraceInternal")] + [Description("Generates a log file describing all items in the 'internal' map.")] + public static void TraceInternal_OnCommand(CommandEventArgs e) + { + int totalCount = 0; + Hashtable table = new Hashtable(); + + foreach (Item item in World.Items.Values) + { + if (item.Parent != null || item.Map != Map.Internal) + continue; + + ++totalCount; + + Type type = item.GetType(); + int[] parms = (int[])table[type]; + + if (parms == null) + table[type] = parms = new[] { 0, 0 }; + + parms[0]++; + parms[1] += item.Amount; + } + + using (StreamWriter op = new StreamWriter("internal.log")) + { + op.WriteLine("# {0} items found", totalCount); + op.WriteLine("# {0} different types", table.Count); + op.WriteLine(); + op.WriteLine(); + op.WriteLine("Type\t\tCount\t\tAmount\t\tAvg. Amount"); + + foreach (DictionaryEntry de in table) + { + Type type = (Type)de.Key; + int[] parms = (int[])de.Value; + + op.WriteLine("{0}\t\t{1}\t\t{2}\t\t{3:F2}", type.Name, parms[0], parms[1], (double)parms[1] / parms[0]); + } + } + } + + [Usage("ProfileWorld")] + [Description("Prints the amount of data serialized for every object type in your world file.")] + public static void ProfileWorld_OnCommand(CommandEventArgs e) + { + ProfileWorld("items", "worldprofile_items.log"); + ProfileWorld("mobiles", "worldprofile_mobiles.log"); + } + + public static void ProfileWorld(string type, string opFile) + { + try + { + ArrayList types = new ArrayList(); + + using (BinaryReader bin = new BinaryReader(new FileStream(string.Format("Saves/{0}/{0}.tdb", type), + FileMode.Open, FileAccess.Read, FileShare.Read))) + { + int count = bin.ReadInt32(); + + for (int i = 0; i < count; ++i) + types.Add(ScriptCompiler.FindTypeByFullName(bin.ReadString())); + } + + long total = 0; + + Hashtable table = new Hashtable(); + + using (BinaryReader bin = new BinaryReader(new FileStream(string.Format("Saves/{0}/{0}.idx", type), + FileMode.Open, FileAccess.Read, FileShare.Read))) + { + int count = bin.ReadInt32(); + + for (int i = 0; i < count; ++i) + { + int typeID = bin.ReadInt32(); + int serial = bin.ReadInt32(); + long pos = bin.ReadInt64(); + int length = bin.ReadInt32(); + Type objType = (Type)types[typeID]; + + while (objType != null && objType != typeof(object)) + { + object obj = table[objType]; + + if (obj == null) + table[objType] = length; + else + table[objType] = length + (int)obj; + + objType = objType.BaseType; + total += length; + } + } + } + + ArrayList list = new ArrayList(table); + + list.Sort(new CountSorter()); + + using (StreamWriter op = new StreamWriter(opFile)) + { + op.WriteLine("# Profile of world {0}", type); + op.WriteLine("# Generated on {0}", DateTime.UtcNow); + op.WriteLine(); + op.WriteLine(); + + foreach (DictionaryEntry de in list) + op.WriteLine("{0}\t{1:F2}%\t{2}", de.Value, 100 * (int)de.Value / (double)total, de.Key); + } + } + catch + { + } + } + + private class CountSorter : IComparer + { + public int Compare(object x, object y) + { + DictionaryEntry a = (DictionaryEntry)x; + DictionaryEntry b = (DictionaryEntry)y; + + int aCount = GetCount(a.Value); + int bCount = GetCount(b.Value); + + int v = -aCount.CompareTo(bCount); + + if (v == 0) + { + Type aType = (Type)a.Key; + Type bType = (Type)b.Key; + + v = aType.FullName.CompareTo(bType.FullName); + } + + return v; + } + + private int GetCount(object obj) + { + if (obj is int intObj) + return intObj; + + if (obj is int[] list) + { + int total = 0; + + for (int i = 0; i < list.Length; ++i) + total += list[i]; + + return total; + } + + return 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Properties.cs b/Scripts/Commands/Properties.cs index 3ac0e1315..f8580acef 100644 --- a/Scripts/Commands/Properties.cs +++ b/Scripts/Commands/Properties.cs @@ -1,818 +1,808 @@ using System; using System.Reflection; -using Server.Targeting; -using Server.Gumps; -using CPA = Server.CommandPropertyAttribute; using Server.Commands; using Server.Commands.Generic; +using Server.Gumps; +using Server.Targeting; +using CPA = Server.CommandPropertyAttribute; namespace Server.Commands { - public enum PropertyAccess - { - Read = 0x01, - Write = 0x02, - ReadWrite = Read | Write - } - - public class Properties - { - public static void Initialize() - { - CommandSystem.Register( "Props", AccessLevel.Counselor, Props_OnCommand ); - } - - private class PropsTarget : Target - { - public PropsTarget() : base( -1, true, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object o ) - { - if ( !BaseCommand.IsAccessible( from, o ) ) - from.SendMessage( "That is not accessible." ); - else - from.SendGump( new PropertiesGump( from, o ) ); - } - } - - [Usage( "Props [serial]" )] - [Description( "Opens a menu where you can view and edit all properties of a targeted (or specified) object." )] - private static void Props_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 1 ) - { - IEntity ent = World.FindEntity( e.GetInt32( 0 ) ); - - if ( ent == null ) - e.Mobile.SendMessage( "No object with that serial was found." ); - else if ( !BaseCommand.IsAccessible( e.Mobile, ent ) ) - e.Mobile.SendMessage( "That is not accessible." ); - else - e.Mobile.SendGump( new PropertiesGump( e.Mobile, ent ) ); - } - else - { - e.Mobile.Target = new PropsTarget(); - } - } - - private static bool CIEqual( string l, string r ) - { - return Insensitive.Equals( l, r ); - } - - private static Type typeofCPA = typeof( CPA ); - - public static CPA GetCPA( PropertyInfo p ) - { - object[] attrs = p.GetCustomAttributes( typeofCPA, false ); - - if ( attrs.Length == 0 ) - return null; - - return attrs[0] as CPA; - } - - public static PropertyInfo[] GetPropertyInfoChain( Mobile from, Type type, string propertyString, PropertyAccess endAccess, ref string failReason ) - { - string[] split = propertyString.Split( '.' ); - - if ( split.Length == 0 ) - return null; - - PropertyInfo[] info = new PropertyInfo[split.Length]; - - for ( int i = 0; i < info.Length; ++i ) - { - string propertyName = split[i]; - - if ( CIEqual( propertyName, "current" ) ) - continue; - - PropertyInfo[] props = type.GetProperties( BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public ); - - bool isFinal = ( i == (info.Length - 1) ); - - PropertyAccess access = endAccess; - - if ( !isFinal ) - access |= PropertyAccess.Read; - - for ( int j = 0; j < props.Length; ++j ) - { - PropertyInfo p = props[j]; - - if ( CIEqual( p.Name, propertyName ) ) - { - CPA attr = GetCPA( p ); - - if ( attr == null ) - { - failReason = $"Property '{propertyName}' not found."; - return null; - } - - if ( (access & PropertyAccess.Read) != 0 && from.AccessLevel < attr.ReadLevel ) - { - failReason = - $"You must be at least {Mobile.GetAccessLevelName(attr.ReadLevel)} to get the property '{propertyName}'."; - - return null; - } - if ( (access & PropertyAccess.Write) != 0 && from.AccessLevel < attr.WriteLevel ) - { - failReason = - $"You must be at least {Mobile.GetAccessLevelName(attr.WriteLevel)} to set the property '{propertyName}'."; - - return null; - } - if ( (access & PropertyAccess.Read) != 0 && !p.CanRead ) - { - failReason = $"Property '{propertyName}' is write only."; - return null; - } - if ( (access & PropertyAccess.Write) != 0 && (!p.CanWrite || attr.ReadOnly) && isFinal ) - { - failReason = $"Property '{propertyName}' is read only."; - return null; - } - - info[i] = p; - type = p.PropertyType; - break; - } - } - - if ( info[i] == null ) - { - failReason = $"Property '{propertyName}' not found."; - return null; - } - } - - return info; - } - - public static PropertyInfo GetPropertyInfo( Mobile from, ref object obj, string propertyName, PropertyAccess access, ref string failReason ) - { - PropertyInfo[] chain = GetPropertyInfoChain( from, obj.GetType(), propertyName, access, ref failReason ); - - if ( chain == null ) - return null; - - return GetPropertyInfo( ref obj, chain, ref failReason ); - } - - public static PropertyInfo GetPropertyInfo( ref object obj, PropertyInfo[] chain, ref string failReason ) - { - if ( chain == null || chain.Length == 0 ) - { - failReason = "Property chain is empty."; - return null; - } - - for ( int i = 0; i < chain.Length - 1; ++i ) - { - if ( chain[i] == null ) - continue; - - obj = chain[i].GetValue( obj, null ); - - if ( obj == null ) - { - failReason = $"Property '{chain[i]}' is null."; - return null; - } - } - - return chain[chain.Length-1]; - } - - public static string GetValue( Mobile from, object o, string name ) - { - string failReason = ""; - - PropertyInfo[] chain = GetPropertyInfoChain( from, o.GetType(), name, PropertyAccess.Read, ref failReason ); - - if ( chain == null || chain.Length == 0 ) - return failReason; - - PropertyInfo p = GetPropertyInfo( ref o, chain, ref failReason ); - - if ( p == null ) - return failReason; - - return InternalGetValue( o, p, chain ); - } - - public static string IncreaseValue( Mobile from, object o, string[] args ) - { - Type type = o.GetType(); - - object[] realObjs = new object[args.Length/2]; - PropertyInfo[] realProps = new PropertyInfo[args.Length/2]; - int[] realValues = new int[args.Length/2]; - - bool positive = false, negative = false; - - for ( int i = 0; i < realProps.Length; ++i ) - { - string name = args[i*2]; - - try - { - string valueString = args[1 + (i*2)]; - - if ( valueString.StartsWith( "0x" ) ) - { - realValues[i] = Convert.ToInt32( valueString.Substring( 2 ), 16 ); - } - else - { - realValues[i] = Convert.ToInt32( valueString ); - } - } - catch - { - return "Offset value could not be parsed."; - } - - if ( realValues[i] > 0 ) - positive = true; - else if ( realValues[i] < 0 ) - negative = true; - else - return "Zero is not a valid value to offset."; - - string failReason = null; - realObjs[i] = o; - realProps[i] = GetPropertyInfo( from, ref realObjs[i], name, PropertyAccess.ReadWrite, ref failReason ); - - if ( failReason != null ) - return failReason; - - if ( realProps[i] == null ) - return "Property not found."; - } - - for ( int i = 0; i < realProps.Length; ++i ) - { - object obj = realProps[i].GetValue( realObjs[i], null ); - - if ( !( obj is IConvertible ) ) - return "Property is not IConvertable."; - - try - { - - long v = (long)Convert.ChangeType( obj, TypeCode.Int64 ); - v += realValues[i]; + public enum PropertyAccess + { + Read = 0x01, + Write = 0x02, + ReadWrite = Read | Write + } - realProps[i].SetValue( realObjs[i], Convert.ChangeType( v, realProps[i].PropertyType ), null ); - } - catch - { - return "Value could not be converted"; - } - } + public class Properties + { + private static Type typeofCPA = typeof(CPA); - if ( realProps.Length == 1 ) - { - if ( positive ) - return "The property has been increased."; + private static Type typeofSerial = typeof(Serial); - return "The property has been decreased."; - } + private static Type typeofType = typeof(Type); - if ( positive && negative ) - return "The properties have been changed."; + private static Type typeofChar = typeof(char); - if ( positive ) - return "The properties have been increased."; + private static Type typeofString = typeof(string); - return "The properties have been decreased."; - } + private static Type typeofText = typeof(TextDefinition); - private static string InternalGetValue( object o, PropertyInfo p ) - { - return InternalGetValue( o, p, null ); - } + private static Type typeofTimeSpan = typeof(TimeSpan); + private static Type typeofParsable = typeof(ParsableAttribute); - private static string InternalGetValue( object o, PropertyInfo p, PropertyInfo[] chain ) - { - Type type = p.PropertyType; + private static Type[] m_ParseTypes = { typeof(string) }; + private static object[] m_ParseParams = new object[1]; - object value = p.GetValue( o, null ); - string toString; + private static Type[] m_NumericTypes = + { + typeof(byte), typeof(sbyte), + typeof(short), typeof(ushort), + typeof(int), typeof(uint), + typeof(long), typeof(ulong) + }; - if ( value == null ) - toString = "null"; - else if ( IsNumeric( type ) ) - toString = string.Format( "{0} (0x{0:X})", value ); - else if ( IsChar( type ) ) - toString = string.Format( "'{0}' ({1} [0x{1:X}])", value, (int) value ); - else if ( IsString( type ) ) - toString = ( (string) value == "null" ? @"@""null""" : $"\"{value}\""); - else if ( IsText( type ) ) - toString = ( (TextDefinition) value ).Format( false ); - else - toString = value.ToString(); - - if ( chain == null ) - return $"{p.Name} = {toString}"; - - string[] concat = new string[chain.Length*2+1]; - - for ( int i = 0; i < chain.Length; ++i ) - { - concat[(i*2)+0] = chain[i].Name; - concat[(i*2)+1] = ( i < (chain.Length - 1) ) ? "." : " = "; - } - - concat[concat.Length-1] = toString; + public static void Initialize() + { + CommandSystem.Register("Props", AccessLevel.Counselor, Props_OnCommand); + } + + [Usage("Props [serial]")] + [Description("Opens a menu where you can view and edit all properties of a targeted (or specified) object.")] + private static void Props_OnCommand(CommandEventArgs e) + { + if (e.Length == 1) + { + IEntity ent = World.FindEntity(e.GetInt32(0)); + + if (ent == null) + e.Mobile.SendMessage("No object with that serial was found."); + else if (!BaseCommand.IsAccessible(e.Mobile, ent)) + e.Mobile.SendMessage("That is not accessible."); + else + e.Mobile.SendGump(new PropertiesGump(e.Mobile, ent)); + } + else + { + e.Mobile.Target = new PropsTarget(); + } + } + + private static bool CIEqual(string l, string r) + { + return Insensitive.Equals(l, r); + } + + public static CPA GetCPA(PropertyInfo p) + { + object[] attrs = p.GetCustomAttributes(typeofCPA, false); + + if (attrs.Length == 0) + return null; + + return attrs[0] as CPA; + } + + public static PropertyInfo[] GetPropertyInfoChain(Mobile from, Type type, string propertyString, + PropertyAccess endAccess, ref string failReason) + { + string[] split = propertyString.Split('.'); + + if (split.Length == 0) + return null; + + PropertyInfo[] info = new PropertyInfo[split.Length]; + + for (int i = 0; i < info.Length; ++i) + { + string propertyName = split[i]; + + if (CIEqual(propertyName, "current")) + continue; + + PropertyInfo[] props = type.GetProperties(BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public); + + bool isFinal = i == info.Length - 1; + + PropertyAccess access = endAccess; + + if (!isFinal) + access |= PropertyAccess.Read; + + for (int j = 0; j < props.Length; ++j) + { + PropertyInfo p = props[j]; + + if (CIEqual(p.Name, propertyName)) + { + CPA attr = GetCPA(p); - return string.Concat( concat ); - } + if (attr == null) + { + failReason = $"Property '{propertyName}' not found."; + return null; + } + + if ((access & PropertyAccess.Read) != 0 && from.AccessLevel < attr.ReadLevel) + { + failReason = + $"You must be at least {Mobile.GetAccessLevelName(attr.ReadLevel)} to get the property '{propertyName}'."; + + return null; + } + + if ((access & PropertyAccess.Write) != 0 && from.AccessLevel < attr.WriteLevel) + { + failReason = + $"You must be at least {Mobile.GetAccessLevelName(attr.WriteLevel)} to set the property '{propertyName}'."; + + return null; + } + + if ((access & PropertyAccess.Read) != 0 && !p.CanRead) + { + failReason = $"Property '{propertyName}' is write only."; + return null; + } + + if ((access & PropertyAccess.Write) != 0 && (!p.CanWrite || attr.ReadOnly) && isFinal) + { + failReason = $"Property '{propertyName}' is read only."; + return null; + } + + info[i] = p; + type = p.PropertyType; + break; + } + } + + if (info[i] == null) + { + failReason = $"Property '{propertyName}' not found."; + return null; + } + } + + return info; + } - public static string SetValue( Mobile from, object o, string name, string value ) - { - object logObject = o; - - string failReason = ""; - PropertyInfo p = GetPropertyInfo( from, ref o, name, PropertyAccess.Write, ref failReason ); - - if ( p == null ) - return failReason; - - return InternalSetValue( from, logObject, o, p, name, value, true ); - } - - private static Type typeofSerial = typeof( Serial ); - - private static bool IsSerial( Type t ) - { - return ( t == typeofSerial ); - } - - private static Type typeofType = typeof( Type ); - - private static bool IsType( Type t ) - { - return ( t == typeofType ); - } - - private static Type typeofChar = typeof( char ); - - private static bool IsChar( Type t ) - { - return ( t == typeofChar ); - } - - private static Type typeofString = typeof( string ); - - private static bool IsString( Type t ) - { - return ( t == typeofString ); - } - - private static Type typeofText = typeof( TextDefinition ); - - private static bool IsText( Type t ) - { - return ( t == typeofText ); - } - - private static bool IsEnum( Type t ) - { - return t.IsEnum; - } - - private static Type typeofTimeSpan = typeof( TimeSpan ); - private static Type typeofParsable = typeof( ParsableAttribute ); - - private static bool IsParsable( Type t ) - { - return ( t == typeofTimeSpan || t.IsDefined( typeofParsable, false ) ); - } - - private static Type[] m_ParseTypes = { typeof( string ) }; - private static object[] m_ParseParams = new object[1]; - - private static object Parse( object o, Type t, string value ) - { - MethodInfo method = t.GetMethod( "Parse", m_ParseTypes ); - - m_ParseParams[0] = value; - - return method.Invoke( o, m_ParseParams ); - } - - private static Type[] m_NumericTypes = { - typeof( byte ), typeof( sbyte ), - typeof( short ), typeof( ushort ), - typeof( int ), typeof( uint ), - typeof( long ), typeof( ulong ) - }; - - private static bool IsNumeric( Type t ) - { - return ( Array.IndexOf( m_NumericTypes, t ) >= 0 ); - } - - public static string ConstructFromString( Type type, object obj, string value, ref object constructed ) - { - object toSet; - bool isSerial = IsSerial( type ); - - if ( isSerial ) // mutate into int32 - type = m_NumericTypes[4]; - - if ( value == "(-null-)" && !type.IsValueType ) - value = null; - - if ( IsEnum( type ) ) - { - try - { - toSet = Enum.Parse( type, value, true ); - } - catch - { - return "That is not a valid enumeration member."; - } - } - else if ( IsType( type ) ) - { - try - { - toSet = ScriptCompiler.FindTypeByName( value ); - - if ( toSet == null ) - return "No type with that name was found."; - } - catch - { - return "No type with that name was found."; - } - } - else if ( IsParsable( type ) ) - { - try - { - toSet = Parse( obj, type, value ); - } - catch - { - return "That is not properly formatted."; - } - } - else if ( value == null ) - { - toSet = null; - } - else if ( value.StartsWith( "0x" ) && IsNumeric( type ) ) - { - try - { - toSet = Convert.ChangeType( Convert.ToUInt64( value.Substring( 2 ), 16 ), type ); - } - catch - { - return "That is not properly formatted."; - } - } - else - { - try - { - toSet = Convert.ChangeType( value, type ); - } - catch - { - return "That is not properly formatted."; - } - } - - if ( isSerial ) // mutate back - toSet = (Serial)((int)toSet); - - constructed = toSet; - return null; - } - - public static string SetDirect( Mobile from, object logObject, object obj, PropertyInfo prop, string givenName, object toSet, bool shouldLog ) - { - try - { - if ( toSet is AccessLevel newLevel ) - { - AccessLevel reqLevel = AccessLevel.Administrator; - - if ( newLevel == AccessLevel.Administrator ) - reqLevel = AccessLevel.Developer; - else if ( newLevel >= AccessLevel.Developer ) - reqLevel = AccessLevel.Owner; - - if ( from.AccessLevel < reqLevel ) - return "You do not have access to that level."; - } - - if ( shouldLog ) - CommandLogging.LogChangeProperty( from, logObject, givenName, toSet == null ? "(-null-)" : toSet.ToString() ); - - prop.SetValue( obj, toSet, null ); - return "Property has been set."; - } - catch - { - return "An exception was caught, the property may not be set."; - } - } - - public static string SetDirect( object obj, PropertyInfo prop, object toSet ) - { - try - { - if ( toSet is AccessLevel ) - { - return "You do not have access to that level."; - } - - prop.SetValue( obj, toSet, null ); - return "Property has been set."; - } - catch - { - return "An exception was caught, the property may not be set."; - } - } - - public static string InternalSetValue( Mobile from, object logobj, object o, PropertyInfo p, string pname, string value, bool shouldLog ) - { - object toSet = null; - string result = ConstructFromString( p.PropertyType, o, value, ref toSet ); - - if ( result != null ) - return result; - - return SetDirect( from, logobj, o, p, pname, toSet, shouldLog ); - } - - public static string InternalSetValue( object o, PropertyInfo p, string value ) - { - object toSet = null; - string result = ConstructFromString( p.PropertyType, o, value, ref toSet ); - - if ( result != null ) - return result; - - return SetDirect( o, p, toSet ); - } - } + public static PropertyInfo GetPropertyInfo(Mobile from, ref object obj, string propertyName, PropertyAccess access, + ref string failReason) + { + PropertyInfo[] chain = GetPropertyInfoChain(from, obj.GetType(), propertyName, access, ref failReason); + + if (chain == null) + return null; + + return GetPropertyInfo(ref obj, chain, ref failReason); + } + + public static PropertyInfo GetPropertyInfo(ref object obj, PropertyInfo[] chain, ref string failReason) + { + if (chain == null || chain.Length == 0) + { + failReason = "Property chain is empty."; + return null; + } + + for (int i = 0; i < chain.Length - 1; ++i) + { + if (chain[i] == null) + continue; + + obj = chain[i].GetValue(obj, null); + + if (obj == null) + { + failReason = $"Property '{chain[i]}' is null."; + return null; + } + } + + return chain[chain.Length - 1]; + } + + public static string GetValue(Mobile from, object o, string name) + { + string failReason = ""; + + PropertyInfo[] chain = GetPropertyInfoChain(from, o.GetType(), name, PropertyAccess.Read, ref failReason); + + if (chain == null || chain.Length == 0) + return failReason; + + PropertyInfo p = GetPropertyInfo(ref o, chain, ref failReason); + + if (p == null) + return failReason; + + return InternalGetValue(o, p, chain); + } + + public static string IncreaseValue(Mobile from, object o, string[] args) + { + Type type = o.GetType(); + + object[] realObjs = new object[args.Length / 2]; + PropertyInfo[] realProps = new PropertyInfo[args.Length / 2]; + int[] realValues = new int[args.Length / 2]; + + bool positive = false, negative = false; + + for (int i = 0; i < realProps.Length; ++i) + { + string name = args[i * 2]; + + try + { + string valueString = args[1 + i * 2]; + + if (valueString.StartsWith("0x")) + realValues[i] = Convert.ToInt32(valueString.Substring(2), 16); + else + realValues[i] = Convert.ToInt32(valueString); + } + catch + { + return "Offset value could not be parsed."; + } + + if (realValues[i] > 0) + positive = true; + else if (realValues[i] < 0) + negative = true; + else + return "Zero is not a valid value to offset."; + + string failReason = null; + realObjs[i] = o; + realProps[i] = GetPropertyInfo(from, ref realObjs[i], name, PropertyAccess.ReadWrite, ref failReason); + + if (failReason != null) + return failReason; + + if (realProps[i] == null) + return "Property not found."; + } + + for (int i = 0; i < realProps.Length; ++i) + { + object obj = realProps[i].GetValue(realObjs[i], null); + + if (!(obj is IConvertible)) + return "Property is not IConvertable."; + + try + { + long v = (long)Convert.ChangeType(obj, TypeCode.Int64); + v += realValues[i]; + + realProps[i].SetValue(realObjs[i], Convert.ChangeType(v, realProps[i].PropertyType), null); + } + catch + { + return "Value could not be converted"; + } + } + + if (realProps.Length == 1) + { + if (positive) + return "The property has been increased."; + + return "The property has been decreased."; + } + + if (positive && negative) + return "The properties have been changed."; + + if (positive) + return "The properties have been increased."; + + return "The properties have been decreased."; + } + + private static string InternalGetValue(object o, PropertyInfo p) + { + return InternalGetValue(o, p, null); + } + + private static string InternalGetValue(object o, PropertyInfo p, PropertyInfo[] chain) + { + Type type = p.PropertyType; + + object value = p.GetValue(o, null); + string toString; + + if (value == null) + toString = "null"; + else if (IsNumeric(type)) + toString = string.Format("{0} (0x{0:X})", value); + else if (IsChar(type)) + toString = string.Format("'{0}' ({1} [0x{1:X}])", value, (int)value); + else if (IsString(type)) + toString = (string)value == "null" ? @"@""null""" : $"\"{value}\""; + else if (IsText(type)) + toString = ((TextDefinition)value).Format(false); + else + toString = value.ToString(); + + if (chain == null) + return $"{p.Name} = {toString}"; + + string[] concat = new string[chain.Length * 2 + 1]; + + for (int i = 0; i < chain.Length; ++i) + { + concat[i * 2 + 0] = chain[i].Name; + concat[i * 2 + 1] = i < chain.Length - 1 ? "." : " = "; + } + + concat[concat.Length - 1] = toString; + + return string.Concat(concat); + } + + public static string SetValue(Mobile from, object o, string name, string value) + { + object logObject = o; + + string failReason = ""; + PropertyInfo p = GetPropertyInfo(from, ref o, name, PropertyAccess.Write, ref failReason); + + if (p == null) + return failReason; + + return InternalSetValue(from, logObject, o, p, name, value, true); + } + + private static bool IsSerial(Type t) + { + return t == typeofSerial; + } + + private static bool IsType(Type t) + { + return t == typeofType; + } + + private static bool IsChar(Type t) + { + return t == typeofChar; + } + + private static bool IsString(Type t) + { + return t == typeofString; + } + + private static bool IsText(Type t) + { + return t == typeofText; + } + + private static bool IsEnum(Type t) + { + return t.IsEnum; + } + + private static bool IsParsable(Type t) + { + return t == typeofTimeSpan || t.IsDefined(typeofParsable, false); + } + + private static object Parse(object o, Type t, string value) + { + MethodInfo method = t.GetMethod("Parse", m_ParseTypes); + + m_ParseParams[0] = value; + + return method.Invoke(o, m_ParseParams); + } + + private static bool IsNumeric(Type t) + { + return Array.IndexOf(m_NumericTypes, t) >= 0; + } + + public static string ConstructFromString(Type type, object obj, string value, ref object constructed) + { + object toSet; + bool isSerial = IsSerial(type); + + if (isSerial) // mutate into int32 + type = m_NumericTypes[4]; + + if (value == "(-null-)" && !type.IsValueType) + value = null; + + if (IsEnum(type)) + try + { + toSet = Enum.Parse(type, value, true); + } + catch + { + return "That is not a valid enumeration member."; + } + else if (IsType(type)) + try + { + toSet = ScriptCompiler.FindTypeByName(value); + + if (toSet == null) + return "No type with that name was found."; + } + catch + { + return "No type with that name was found."; + } + else if (IsParsable(type)) + try + { + toSet = Parse(obj, type, value); + } + catch + { + return "That is not properly formatted."; + } + else if (value == null) + toSet = null; + else if (value.StartsWith("0x") && IsNumeric(type)) + try + { + toSet = Convert.ChangeType(Convert.ToUInt64(value.Substring(2), 16), type); + } + catch + { + return "That is not properly formatted."; + } + else + try + { + toSet = Convert.ChangeType(value, type); + } + catch + { + return "That is not properly formatted."; + } + + if (isSerial) // mutate back + toSet = (Serial)(int)toSet; + + constructed = toSet; + return null; + } + + public static string SetDirect(Mobile from, object logObject, object obj, PropertyInfo prop, string givenName, + object toSet, bool shouldLog) + { + try + { + if (toSet is AccessLevel newLevel) + { + AccessLevel reqLevel = AccessLevel.Administrator; + + if (newLevel == AccessLevel.Administrator) + reqLevel = AccessLevel.Developer; + else if (newLevel >= AccessLevel.Developer) + reqLevel = AccessLevel.Owner; + + if (from.AccessLevel < reqLevel) + return "You do not have access to that level."; + } + + if (shouldLog) + CommandLogging.LogChangeProperty(from, logObject, givenName, + toSet == null ? "(-null-)" : toSet.ToString()); + + prop.SetValue(obj, toSet, null); + return "Property has been set."; + } + catch + { + return "An exception was caught, the property may not be set."; + } + } + + public static string SetDirect(object obj, PropertyInfo prop, object toSet) + { + try + { + if (toSet is AccessLevel) return "You do not have access to that level."; + + prop.SetValue(obj, toSet, null); + return "Property has been set."; + } + catch + { + return "An exception was caught, the property may not be set."; + } + } + + public static string InternalSetValue(Mobile from, object logobj, object o, PropertyInfo p, string pname, + string value, bool shouldLog) + { + object toSet = null; + string result = ConstructFromString(p.PropertyType, o, value, ref toSet); + + if (result != null) + return result; + + return SetDirect(from, logobj, o, p, pname, toSet, shouldLog); + } + + public static string InternalSetValue(object o, PropertyInfo p, string value) + { + object toSet = null; + string result = ConstructFromString(p.PropertyType, o, value, ref toSet); + + if (result != null) + return result; + + return SetDirect(o, p, toSet); + } + + private class PropsTarget : Target + { + public PropsTarget() : base(-1, true, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object o) + { + if (!BaseCommand.IsAccessible(from, o)) + from.SendMessage("That is not accessible."); + else + from.SendGump(new PropertiesGump(from, o)); + } + } + } } namespace Server { - public abstract class PropertyException : ApplicationException - { - protected Property m_Property; + public abstract class PropertyException : ApplicationException + { + protected Property m_Property; - public Property Property => m_Property; + public PropertyException(Property property, string message) + : base(message) + { + m_Property = property; + } - public PropertyException( Property property, string message ) - : base( message ) - { - m_Property = property; - } - } + public Property Property => m_Property; + } - public abstract class BindingException : PropertyException - { - public BindingException( Property property, string message ) - : base( property, message ) - { - } - } + public abstract class BindingException : PropertyException + { + public BindingException(Property property, string message) + : base(property, message) + { + } + } - public sealed class NotYetBoundException : BindingException - { - public NotYetBoundException( Property property ) - : base( property, string.Format( "Property has not yet been bound." ) ) - { - } - } + public sealed class NotYetBoundException : BindingException + { + public NotYetBoundException(Property property) + : base(property, "Property has not yet been bound.") + { + } + } - public sealed class AlreadyBoundException : BindingException - { - public AlreadyBoundException( Property property ) - : base( property, string.Format( "Property has already been bound." ) ) - { - } - } + public sealed class AlreadyBoundException : BindingException + { + public AlreadyBoundException(Property property) + : base(property, "Property has already been bound.") + { + } + } - public sealed class UnknownPropertyException : BindingException - { - public UnknownPropertyException( Property property, string current ) - : base( property, $"Property '{current}' not found.") - { - } - } + public sealed class UnknownPropertyException : BindingException + { + public UnknownPropertyException(Property property, string current) + : base(property, $"Property '{current}' not found.") + { + } + } - public sealed class ReadOnlyException : BindingException - { - public ReadOnlyException( Property property ) - : base( property, "Property is read-only." ) - { - } - } + public sealed class ReadOnlyException : BindingException + { + public ReadOnlyException(Property property) + : base(property, "Property is read-only.") + { + } + } - public sealed class WriteOnlyException : BindingException - { - public WriteOnlyException( Property property ) - : base( property, "Property is write-only." ) - { - } - } + public sealed class WriteOnlyException : BindingException + { + public WriteOnlyException(Property property) + : base(property, "Property is write-only.") + { + } + } - public abstract class AccessException : PropertyException - { - public AccessException( Property property, string message ) - : base( property, message ) - { - } - } + public abstract class AccessException : PropertyException + { + public AccessException(Property property, string message) + : base(property, message) + { + } + } - public sealed class InternalAccessException : AccessException - { - public InternalAccessException( Property property ) - : base( property, "Property is internal." ) - { - } - } + public sealed class InternalAccessException : AccessException + { + public InternalAccessException(Property property) + : base(property, "Property is internal.") + { + } + } - public abstract class ClearanceException : AccessException - { - protected AccessLevel m_PlayerAccess; - protected AccessLevel m_NeededAccess; + public abstract class ClearanceException : AccessException + { + protected AccessLevel m_NeededAccess; + protected AccessLevel m_PlayerAccess; - public AccessLevel PlayerAccess => m_PlayerAccess; + public ClearanceException(Property property, AccessLevel playerAccess, AccessLevel neededAccess, string accessType) + : base(property, + $"You must be at least {Mobile.GetAccessLevelName(neededAccess)} to {accessType} this property.") + { + } - public AccessLevel NeededAccess => m_NeededAccess; + public AccessLevel PlayerAccess => m_PlayerAccess; - public ClearanceException( Property property, AccessLevel playerAccess, AccessLevel neededAccess, string accessType ) - : base( property, - $"You must be at least {Mobile.GetAccessLevelName(neededAccess)} to {accessType} this property.") - { - } - } + public AccessLevel NeededAccess => m_NeededAccess; + } - public sealed class ReadAccessException : ClearanceException - { - public ReadAccessException( Property property, AccessLevel playerAccess, AccessLevel neededAccess ) - : base( property, playerAccess, neededAccess, "read" ) - { - } - } + public sealed class ReadAccessException : ClearanceException + { + public ReadAccessException(Property property, AccessLevel playerAccess, AccessLevel neededAccess) + : base(property, playerAccess, neededAccess, "read") + { + } + } - public sealed class WriteAccessException : ClearanceException - { - public WriteAccessException( Property property, AccessLevel playerAccess, AccessLevel neededAccess ) - : base( property, playerAccess, neededAccess, "write" ) - { - } - } + public sealed class WriteAccessException : ClearanceException + { + public WriteAccessException(Property property, AccessLevel playerAccess, AccessLevel neededAccess) + : base(property, playerAccess, neededAccess, "write") + { + } + } - public sealed class Property - { - private PropertyInfo[] m_Chain; + public sealed class Property + { + private PropertyInfo[] m_Chain; - public string Binding { get; } + public Property(string binding) + { + Binding = binding; + } - public bool IsBound => ( m_Chain != null ); + public Property(PropertyInfo[] chain) + { + m_Chain = chain; + } - public PropertyAccess Access { get; private set; } + public string Binding{ get; } - public PropertyInfo[] Chain - { - get - { - if ( !IsBound ) - throw new NotYetBoundException( this ); + public bool IsBound => m_Chain != null; - return m_Chain; - } - } + public PropertyAccess Access{ get; private set; } - public Type Type - { - get - { - if ( !IsBound ) - throw new NotYetBoundException( this ); + public PropertyInfo[] Chain + { + get + { + if (!IsBound) + throw new NotYetBoundException(this); - return m_Chain[m_Chain.Length - 1].PropertyType; - } - } + return m_Chain; + } + } - public bool CheckAccess( Mobile from ) - { - if ( !IsBound ) - throw new NotYetBoundException( this ); + public Type Type + { + get + { + if (!IsBound) + throw new NotYetBoundException(this); - for ( int i = 0; i < m_Chain.Length; ++i ) - { - PropertyInfo prop = m_Chain[i]; + return m_Chain[m_Chain.Length - 1].PropertyType; + } + } - bool isFinal = ( i == ( m_Chain.Length - 1 ) ); + public bool CheckAccess(Mobile from) + { + if (!IsBound) + throw new NotYetBoundException(this); - PropertyAccess access = Access; + for (int i = 0; i < m_Chain.Length; ++i) + { + PropertyInfo prop = m_Chain[i]; - if ( !isFinal ) - access |= PropertyAccess.Read; + bool isFinal = i == m_Chain.Length - 1; - CPA security = Properties.GetCPA( prop ); + PropertyAccess access = Access; - if ( security == null ) - throw new InternalAccessException( this ); + if (!isFinal) + access |= PropertyAccess.Read; - if ( ( access & PropertyAccess.Read ) != 0 && from.AccessLevel < security.ReadLevel ) - throw new ReadAccessException( this, from.AccessLevel, security.ReadLevel ); + CPA security = Properties.GetCPA(prop); - if ( ( access & PropertyAccess.Write ) != 0 && (from.AccessLevel < security.WriteLevel || security.ReadOnly) ) - throw new WriteAccessException( this, from.AccessLevel, security.ReadLevel ); - } + if (security == null) + throw new InternalAccessException(this); - return true; - } + if ((access & PropertyAccess.Read) != 0 && from.AccessLevel < security.ReadLevel) + throw new ReadAccessException(this, from.AccessLevel, security.ReadLevel); - public void BindTo( Type objectType, PropertyAccess desiredAccess ) - { - if ( IsBound ) - throw new AlreadyBoundException( this ); + if ((access & PropertyAccess.Write) != 0 && (from.AccessLevel < security.WriteLevel || security.ReadOnly)) + throw new WriteAccessException(this, from.AccessLevel, security.ReadLevel); + } - string[] split = Binding.Split( '.' ); + return true; + } - PropertyInfo[] chain = new PropertyInfo[split.Length]; + public void BindTo(Type objectType, PropertyAccess desiredAccess) + { + if (IsBound) + throw new AlreadyBoundException(this); - for ( int i = 0; i < split.Length; ++i ) - { - bool isFinal = ( i == ( chain.Length - 1 ) ); + string[] split = Binding.Split('.'); - chain[i] = objectType.GetProperty( split[i], BindingFlags.Instance | BindingFlags.Public | BindingFlags.IgnoreCase ); + PropertyInfo[] chain = new PropertyInfo[split.Length]; - if ( chain[i] == null ) - throw new UnknownPropertyException( this, split[i] ); + for (int i = 0; i < split.Length; ++i) + { + bool isFinal = i == chain.Length - 1; - objectType = chain[i].PropertyType; + chain[i] = objectType.GetProperty(split[i], + BindingFlags.Instance | BindingFlags.Public | BindingFlags.IgnoreCase); - PropertyAccess access = desiredAccess; + if (chain[i] == null) + throw new UnknownPropertyException(this, split[i]); - if ( !isFinal ) - access |= PropertyAccess.Read; + objectType = chain[i].PropertyType; - if ( ( access & PropertyAccess.Read ) != 0 && !chain[i].CanRead ) - throw new WriteOnlyException( this ); + PropertyAccess access = desiredAccess; - if ( ( access & PropertyAccess.Write ) != 0 && !chain[i].CanWrite ) - throw new ReadOnlyException( this ); - } + if (!isFinal) + access |= PropertyAccess.Read; - Access = desiredAccess; - m_Chain = chain; - } + if ((access & PropertyAccess.Read) != 0 && !chain[i].CanRead) + throw new WriteOnlyException(this); - public Property( string binding ) - { - Binding = binding; - } + if ((access & PropertyAccess.Write) != 0 && !chain[i].CanWrite) + throw new ReadOnlyException(this); + } - public Property( PropertyInfo[] chain ) - { - m_Chain = chain; - } + Access = desiredAccess; + m_Chain = chain; + } - public override string ToString() - { - if ( !IsBound ) - return Binding; + public override string ToString() + { + if (!IsBound) + return Binding; - string[] toJoin = new string[m_Chain.Length]; + string[] toJoin = new string[m_Chain.Length]; - for ( int i = 0; i < toJoin.Length; ++i ) - toJoin[i] = m_Chain[i].Name; + for (int i = 0; i < toJoin.Length; ++i) + toJoin[i] = m_Chain[i].Name; - return string.Join( ".", toJoin ); - } + return string.Join(".", toJoin); + } - public static Property Parse( Type type, string binding, PropertyAccess access ) - { - Property prop = new Property( binding ); + public static Property Parse(Type type, string binding, PropertyAccess access) + { + Property prop = new Property(binding); - prop.BindTo( type, access ); + prop.BindTo(type, access); - return prop; - } - } -} + return prop; + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/ShardTime.cs b/Scripts/Commands/ShardTime.cs index 97d3f3294..af91bba37 100644 --- a/Scripts/Commands/ShardTime.cs +++ b/Scripts/Commands/ShardTime.cs @@ -2,18 +2,18 @@ namespace Server.Commands { - public class ShardTime - { - public static void Initialize() - { - CommandSystem.Register( "Time", AccessLevel.Player, Time_OnCommand ); - } + public class ShardTime + { + public static void Initialize() + { + CommandSystem.Register("Time", AccessLevel.Player, Time_OnCommand); + } - [Usage( "Time" )] - [Description( "Returns the server's local time." )] - private static void Time_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( DateTime.UtcNow.ToString() ); - } - } + [Usage("Time")] + [Description("Returns the server's local time.")] + private static void Time_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage(DateTime.UtcNow.ToString()); + } + } } \ No newline at end of file diff --git a/Scripts/Commands/SignParser.cs b/Scripts/Commands/SignParser.cs index 8e08eed2b..b5aa215ca 100644 --- a/Scripts/Commands/SignParser.cs +++ b/Scripts/Commands/SignParser.cs @@ -4,134 +4,145 @@ using Server.Items; namespace Server.Commands { - public class SignParser - { - private class SignEntry - { - public string m_Text; - public Point3D m_Location; - public int m_ItemID; - public int m_Map; + public class SignParser + { + private static Queue m_ToDelete = new Queue(); - public SignEntry( string text, Point3D pt, int itemID, int mapLoc ) - { - m_Text = text; - m_Location = pt; - m_ItemID = itemID; - m_Map = mapLoc; - } - } + public static void Initialize() + { + CommandSystem.Register("SignGen", AccessLevel.Administrator, SignGen_OnCommand); + } - public static void Initialize() - { - CommandSystem.Register( "SignGen", AccessLevel.Administrator, SignGen_OnCommand ); - } + [Usage("SignGen")] + [Description("Generates world/shop signs on all facets.")] + public static void SignGen_OnCommand(CommandEventArgs c) + { + Parse(c.Mobile); + } - [Usage( "SignGen" )] - [Description( "Generates world/shop signs on all facets." )] - public static void SignGen_OnCommand( CommandEventArgs c ) - { - Parse( c.Mobile ); - } + public static void Parse(Mobile from) + { + string cfg = Path.Combine(Core.BaseDirectory, "Data/signs.cfg"); - public static void Parse( Mobile from ) - { - string cfg = Path.Combine( Core.BaseDirectory, "Data/signs.cfg" ); + if (File.Exists(cfg)) + { + List list = new List(); + from.SendMessage("Generating signs, please wait."); - if ( File.Exists( cfg ) ) - { - List list = new List(); - from.SendMessage( "Generating signs, please wait." ); + using (StreamReader ip = new StreamReader(cfg)) + { + string line; - using ( StreamReader ip = new StreamReader( cfg ) ) - { - string line; + while ((line = ip.ReadLine()) != null) + { + string[] split = line.Split(' '); - while ( (line = ip.ReadLine()) != null ) - { - string[] split = line.Split( ' ' ); + SignEntry e = new SignEntry( + line.Substring(split[0].Length + 1 + split[1].Length + 1 + split[2].Length + 1 + + split[3].Length + 1 + split[4].Length + 1), + new Point3D(Utility.ToInt32(split[2]), Utility.ToInt32(split[3]), Utility.ToInt32(split[4])), + Utility.ToInt32(split[1]), Utility.ToInt32(split[0])); - SignEntry e = new SignEntry( - line.Substring( split[0].Length + 1 + split[1].Length + 1 + split[2].Length + 1 + split[3].Length + 1 + split[4].Length + 1 ), - new Point3D( Utility.ToInt32( split[2] ), Utility.ToInt32( split[3] ), Utility.ToInt32( split[4] ) ), - Utility.ToInt32( split[1] ), Utility.ToInt32( split[0] ) ); + list.Add(e); + } + } - list.Add( e ); - } - } + Map[] brit = { Map.Felucca, Map.Trammel }; + Map[] fel = { Map.Felucca }; + Map[] tram = { Map.Trammel }; + Map[] ilsh = { Map.Ilshenar }; + Map[] malas = { Map.Malas }; + Map[] tokuno = { Map.Tokuno }; - Map[] brit = { Map.Felucca, Map.Trammel }; - Map[] fel = { Map.Felucca }; - Map[] tram = { Map.Trammel }; - Map[] ilsh = { Map.Ilshenar }; - Map[] malas = { Map.Malas }; - Map[] tokuno = { Map.Tokuno }; + for (int i = 0; i < list.Count; ++i) + { + SignEntry e = list[i]; + Map[] maps = null; - for ( int i = 0; i < list.Count; ++i ) - { - SignEntry e = list[i]; - Map[] maps = null; + switch (e.m_Map) + { + case 0: + maps = brit; + break; // Trammel and Felucca + case 1: + maps = fel; + break; // Felucca + case 2: + maps = tram; + break; // Trammel + case 3: + maps = ilsh; + break; // Ilshenar + case 4: + maps = malas; + break; // Malas + case 5: + maps = tokuno; + break; // Tokuno Islands + } - switch ( e.m_Map ) - { - case 0: maps = brit; break; // Trammel and Felucca - case 1: maps = fel; break; // Felucca - case 2: maps = tram; break; // Trammel - case 3: maps = ilsh; break; // Ilshenar - case 4: maps = malas; break; // Malas - case 5: maps = tokuno; break; // Tokuno Islands - } + for (int j = 0; maps != null && j < maps.Length; ++j) + Add_Static(e.m_ItemID, e.m_Location, maps[j], e.m_Text); + } - for ( int j = 0; maps != null && j < maps.Length; ++j ) - Add_Static( e.m_ItemID, e.m_Location, maps[j], e.m_Text ); - } + from.SendMessage("Sign generating complete."); + } + else + { + from.SendMessage("{0} not found!", cfg); + } + } - from.SendMessage( "Sign generating complete." ); - } - else - { - from.SendMessage( "{0} not found!", cfg ); - } - } + public static void Add_Static(int itemID, Point3D location, Map map, string name) + { + IPooledEnumerable eable = map.GetItemsInRange(location, 0); - private static Queue m_ToDelete = new Queue(); + foreach (Item item in eable) + if (item is Sign && item.Z == location.Z && item.ItemID == itemID) + m_ToDelete.Enqueue(item); - public static void Add_Static( int itemID, Point3D location, Map map, string name ) - { - IPooledEnumerable eable = map.GetItemsInRange( location, 0 ); + eable.Free(); - foreach ( Item item in eable ) - { - if ( item is Sign && item.Z == location.Z && item.ItemID == itemID ) - m_ToDelete.Enqueue( item ); - } + while (m_ToDelete.Count > 0) + m_ToDelete.Dequeue().Delete(); - eable.Free(); + Item sign; - while ( m_ToDelete.Count > 0 ) - m_ToDelete.Dequeue().Delete(); + if (name.StartsWith("#")) + { + sign = new LocalizedSign(itemID, Utility.ToInt32(name.Substring(1))); + } + else + { + sign = new Sign(itemID); + sign.Name = name; + } - Item sign; + if (map == Map.Malas) + { + if (location.X >= 965 && location.Y >= 502 && location.X <= 1012 && location.Y <= 537) + sign.Hue = 0x47E; + else if (location.X >= 1960 && location.Y >= 1278 && location.X < 2106 && location.Y < 1413) + sign.Hue = 0x44E; + } - if ( name.StartsWith( "#" ) ) - { - sign = new LocalizedSign( itemID, Utility.ToInt32( name.Substring( 1 ) ) ); - } - else - { - sign = new Sign( itemID ); - sign.Name = name; - } + sign.MoveToWorld(location, map); + } - if ( map == Map.Malas ) - { - if ( location.X >= 965 && location.Y >= 502 && location.X <= 1012 && location.Y <= 537 ) - sign.Hue = 0x47E; - else if ( location.X >= 1960 && location.Y >= 1278 && location.X < 2106 && location.Y < 1413 ) - sign.Hue = 0x44E; - } + private class SignEntry + { + public int m_ItemID; + public Point3D m_Location; + public int m_Map; + public string m_Text; - sign.MoveToWorld( location, map ); - } - } -} + public SignEntry(string text, Point3D pt, int itemID, int mapLoc) + { + m_Text = text; + m_Location = pt; + m_ItemID = itemID; + m_Map = mapLoc; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Skills.cs b/Scripts/Commands/Skills.cs index b9dbe64bf..c79056727 100644 --- a/Scripts/Commands/Skills.cs +++ b/Scripts/Commands/Skills.cs @@ -3,141 +3,129 @@ using Server.Targeting; namespace Server.Commands { - public class SkillsCommand - { - public static void Initialize() - { - CommandSystem.Register( "SetSkill", AccessLevel.GameMaster, SetSkill_OnCommand ); - CommandSystem.Register( "GetSkill", AccessLevel.GameMaster, GetSkill_OnCommand ); - CommandSystem.Register( "SetAllSkills", AccessLevel.GameMaster, SetAllSkills_OnCommand ); - } + public class SkillsCommand + { + public static void Initialize() + { + CommandSystem.Register("SetSkill", AccessLevel.GameMaster, SetSkill_OnCommand); + CommandSystem.Register("GetSkill", AccessLevel.GameMaster, GetSkill_OnCommand); + CommandSystem.Register("SetAllSkills", AccessLevel.GameMaster, SetAllSkills_OnCommand); + } - [Usage( "SetSkill " )] - [Description( "Sets a skill value by name of a targeted mobile." )] - public static void SetSkill_OnCommand( CommandEventArgs arg ) - { - if ( arg.Length != 2 ) - { - arg.Mobile.SendMessage( "SetSkill " ); - } - else - { - SkillName skill; - if ( Enum.TryParse( arg.GetString( 0 ), true, out skill ) ) - { - arg.Mobile.Target = new SkillTarget( skill, arg.GetDouble( 1 ) ); - } - else - { - arg.Mobile.SendLocalizedMessage( 1005631 ); // You have specified an invalid skill to set. - } - } - } + [Usage("SetSkill ")] + [Description("Sets a skill value by name of a targeted mobile.")] + public static void SetSkill_OnCommand(CommandEventArgs arg) + { + if (arg.Length != 2) + { + arg.Mobile.SendMessage("SetSkill "); + } + else + { + SkillName skill; + if (Enum.TryParse(arg.GetString(0), true, out skill)) + arg.Mobile.Target = new SkillTarget(skill, arg.GetDouble(1)); + else + arg.Mobile.SendLocalizedMessage(1005631); // You have specified an invalid skill to set. + } + } - [Usage( "SetAllSkills " )] - [Description( "Sets all skill values of a targeted mobile." )] - public static void SetAllSkills_OnCommand( CommandEventArgs arg ) - { - if ( arg.Length != 1 ) - { - arg.Mobile.SendMessage( "SetAllSkills " ); - } - else - { - arg.Mobile.Target = new AllSkillsTarget( arg.GetDouble( 0 ) ); - } - } + [Usage("SetAllSkills ")] + [Description("Sets all skill values of a targeted mobile.")] + public static void SetAllSkills_OnCommand(CommandEventArgs arg) + { + if (arg.Length != 1) + arg.Mobile.SendMessage("SetAllSkills "); + else + arg.Mobile.Target = new AllSkillsTarget(arg.GetDouble(0)); + } - [Usage( "GetSkill " )] - [Description( "Gets a skill value by name of a targeted mobile." )] - public static void GetSkill_OnCommand( CommandEventArgs arg ) - { - if ( arg.Length != 1 ) - { - arg.Mobile.SendMessage( "GetSkill " ); - } - else - { - SkillName skill; - if ( Enum.TryParse( arg.GetString( 0 ), true, out skill ) ) - { - arg.Mobile.Target = new SkillTarget( skill ); - } - else - { - arg.Mobile.SendMessage( "You have specified an invalid skill to get." ); - } - } - } + [Usage("GetSkill ")] + [Description("Gets a skill value by name of a targeted mobile.")] + public static void GetSkill_OnCommand(CommandEventArgs arg) + { + if (arg.Length != 1) + { + arg.Mobile.SendMessage("GetSkill "); + } + else + { + SkillName skill; + if (Enum.TryParse(arg.GetString(0), true, out skill)) + arg.Mobile.Target = new SkillTarget(skill); + else + arg.Mobile.SendMessage("You have specified an invalid skill to get."); + } + } - public class AllSkillsTarget : Target - { - private double m_Value; + public class AllSkillsTarget : Target + { + private double m_Value; - public AllSkillsTarget( double value ) : base( -1, false, TargetFlags.None ) - { - m_Value = value; - } + public AllSkillsTarget(double value) : base(-1, false, TargetFlags.None) + { + m_Value = value; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile targ ) - { - Server.Skills skills = targ.Skills; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile targ) + { + Server.Skills skills = targ.Skills; - for ( int i = 0; i < skills.Length; ++i ) - skills[i].Base = m_Value; + for (int i = 0; i < skills.Length; ++i) + skills[i].Base = m_Value; - CommandLogging.LogChangeProperty( from, targ, "EverySkill.Base", m_Value.ToString() ); - } - else - { - from.SendMessage( "That does not have skills!" ); - } - } - } + CommandLogging.LogChangeProperty(from, targ, "EverySkill.Base", m_Value.ToString()); + } + else + { + from.SendMessage("That does not have skills!"); + } + } + } - public class SkillTarget : Target - { - private bool m_Set; - private SkillName m_Skill; - private double m_Value; + public class SkillTarget : Target + { + private bool m_Set; + private SkillName m_Skill; + private double m_Value; - public SkillTarget( SkillName skill, double value ) : base( -1, false, TargetFlags.None ) - { - m_Set = true; - m_Skill = skill; - m_Value = value; - } + public SkillTarget(SkillName skill, double value) : base(-1, false, TargetFlags.None) + { + m_Set = true; + m_Skill = skill; + m_Value = value; + } - public SkillTarget( SkillName skill ) : base( -1, false, TargetFlags.None ) - { - m_Set = false; - m_Skill = skill; - } + public SkillTarget(SkillName skill) : base(-1, false, TargetFlags.None) + { + m_Set = false; + m_Skill = skill; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile targ ) - { - Skill skill = targ.Skills[m_Skill]; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile targ) + { + Skill skill = targ.Skills[m_Skill]; - if ( skill == null ) - return; + if (skill == null) + return; - if ( m_Set ) - { - skill.Base = m_Value; - CommandLogging.LogChangeProperty( from, targ, $"{m_Skill}.Base", m_Value.ToString() ); - } + if (m_Set) + { + skill.Base = m_Value; + CommandLogging.LogChangeProperty(from, targ, $"{m_Skill}.Base", m_Value.ToString()); + } - from.SendMessage( "{0} : {1} (Base: {2})", m_Skill, skill.Value, skill.Base ); - } - else - { - from.SendMessage( "That does not have skills!" ); - } - } - } - } -} + from.SendMessage("{0} : {1} (Base: {2})", m_Skill, skill.Value, skill.Base); + } + else + { + from.SendMessage("That does not have skills!"); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/SkillsMenu.cs b/Scripts/Commands/SkillsMenu.cs index 3b1f8084e..6b4e617ab 100644 --- a/Scripts/Commands/SkillsMenu.cs +++ b/Scripts/Commands/SkillsMenu.cs @@ -1,38 +1,38 @@ -using Server.Targeting; using Server.Gumps; +using Server.Targeting; namespace Server.Commands { - public class Skills - { - public static void Initialize() - { - Register(); - } + public class Skills + { + public static void Initialize() + { + Register(); + } - public static void Register() - { - CommandSystem.Register( "Skills", AccessLevel.Counselor, Skills_OnCommand ); - } + public static void Register() + { + CommandSystem.Register("Skills", AccessLevel.Counselor, Skills_OnCommand); + } - private class SkillsTarget : Target - { - public SkillsTarget( ) : base( -1, true, TargetFlags.None ) - { - } + [Usage("Skills")] + [Description("Opens a menu where you can view or edit skills of a targeted mobile.")] + private static void Skills_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new SkillsTarget(); + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile mobile ) - from.SendGump( new SkillsGump( from, mobile ) ); - } - } + private class SkillsTarget : Target + { + public SkillsTarget() : base(-1, true, TargetFlags.None) + { + } - [Usage( "Skills" )] - [Description( "Opens a menu where you can view or edit skills of a targeted mobile." )] - private static void Skills_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new SkillsTarget(); - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile mobile) + from.SendGump(new SkillsGump(from, mobile)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Statics.cs b/Scripts/Commands/Statics.cs index e6bf2fa7c..f2ae92ddb 100644 --- a/Scripts/Commands/Statics.cs +++ b/Scripts/Commands/Statics.cs @@ -1,570 +1,596 @@ -using System; -using System.IO; using System.Collections; +using System.Collections.Generic; +using System.IO; +using Server.Commands; using Server.Gumps; using Server.Items; -using Server.Commands; -using System.Collections.Generic; namespace Server { - public class Statics - { - public static void Initialize() - { - CommandSystem.Register( "Freeze", AccessLevel.Administrator, Freeze_OnCommand ); - CommandSystem.Register( "FreezeMap", AccessLevel.Administrator, FreezeMap_OnCommand ); - CommandSystem.Register( "FreezeWorld", AccessLevel.Administrator, FreezeWorld_OnCommand ); - - CommandSystem.Register( "Unfreeze", AccessLevel.Administrator, Unfreeze_OnCommand ); - CommandSystem.Register( "UnfreezeMap", AccessLevel.Administrator, UnfreezeMap_OnCommand ); - CommandSystem.Register( "UnfreezeWorld", AccessLevel.Administrator, UnfreezeWorld_OnCommand ); - } - - private static Point3D NullP3D = new Point3D( int.MinValue, int.MinValue, int.MinValue ); - - [Usage( "Freeze" )] - [Description( "Makes a targeted area of dynamic items static." )] - public static void Freeze_OnCommand( CommandEventArgs e ) - { - BoundingBoxPicker.Begin( e.Mobile, FreezeBox_Callback, null ); - } - - [Usage( "FreezeMap" )] - [Description( "Makes every dynamic item in your map static." )] - public static void FreezeMap_OnCommand( CommandEventArgs e ) - { - Map map = e.Mobile.Map; - - if ( map != null && map != Map.Internal ) - SendWarning( e.Mobile, "You are about to freeze all items in {0}.", BaseFreezeWarning, map, NullP3D, NullP3D, FreezeWarning_Callback ); - } - - [Usage( "FreezeWorld" )] - [Description( "Makes every dynamic item on all maps static." )] - public static void FreezeWorld_OnCommand( CommandEventArgs e ) - { - SendWarning( e.Mobile, "You are about to freeze every item on every map.", BaseFreezeWarning, null, NullP3D, NullP3D, FreezeWarning_Callback ); - } - - public static void SendWarning( Mobile m, string header, string baseWarning, Map map, Point3D start, Point3D end, WarningGumpCallback callback ) - { - m.SendGump( new WarningGump( 1060635, 30720, string.Format( baseWarning, string.Format( header, map ) ), 0xFFC000, 420, 400, callback, new StateInfo( map, start, end ) ) ); - } - - private const string BaseFreezeWarning = "{0} " + - "Those items will be removed from the world and placed into the server data files. " + - "Other players will not see the changes unless you distribute your data files to them.

" + - "This operation may not complete unless the server and client are using different data files. " + - "If you receive a message stating 'output data files could not be opened,' then you are probably sharing data files. " + - "Create a new directory for the world data files (statics*.mul and staidx*.mul) and add that to Scritps/Misc/DataPath.cs.

" + - "The change will be in effect immediately on the server, however, you must restart your client and update it's data files for the changes to become visible. " + - "It is strongly recommended that you make backup of the data files mentioned above. " + - "Do you wish to proceed?"; - - private static void FreezeBox_Callback( Mobile from, Map map, Point3D start, Point3D end, object state ) - { - SendWarning( from, "You are about to freeze a section of items.", BaseFreezeWarning, map, start, end, FreezeWarning_Callback ); - } + public class Statics + { + private const string BaseFreezeWarning = "{0} " + + "Those items will be removed from the world and placed into the server data files. " + + "Other players will not see the changes unless you distribute your data files to them.

" + + "This operation may not complete unless the server and client are using different data files. " + + "If you receive a message stating 'output data files could not be opened,' then you are probably sharing data files. " + + "Create a new directory for the world data files (statics*.mul and staidx*.mul) and add that to Scritps/Misc/DataPath.cs.

" + + "The change will be in effect immediately on the server, however, you must restart your client and update it's data files for the changes to become visible. " + + "It is strongly recommended that you make backup of the data files mentioned above. " + + "Do you wish to proceed?"; + + private const string BaseUnfreezeWarning = "{0} " + + "Those items will be removed from the static files and exchanged with unmovable dynamic items. " + + "Other players will not see the changes unless you distribute your data files to them.

" + + "This operation may not complete unless the server and client are using different data files. " + + "If you receive a message stating 'output data files could not be opened,' then you are probably sharing data files. " + + "Create a new directory for the world data files (statics*.mul and staidx*.mul) and add that to Scritps/Misc/DataPath.cs.

" + + "The change will be in effect immediately on the server, however, you must restart your client and update it's data files for the changes to become visible. " + + "It is strongly recommended that you make backup of the data files mentioned above. " + + "Do you wish to proceed?"; + + private static Point3D NullP3D = new Point3D(int.MinValue, int.MinValue, int.MinValue); + + private static byte[] m_Buffer; + + private static StaticTile[] m_TileBuffer = new StaticTile[128]; + + public static void Initialize() + { + CommandSystem.Register("Freeze", AccessLevel.Administrator, Freeze_OnCommand); + CommandSystem.Register("FreezeMap", AccessLevel.Administrator, FreezeMap_OnCommand); + CommandSystem.Register("FreezeWorld", AccessLevel.Administrator, FreezeWorld_OnCommand); + + CommandSystem.Register("Unfreeze", AccessLevel.Administrator, Unfreeze_OnCommand); + CommandSystem.Register("UnfreezeMap", AccessLevel.Administrator, UnfreezeMap_OnCommand); + CommandSystem.Register("UnfreezeWorld", AccessLevel.Administrator, UnfreezeWorld_OnCommand); + } + + [Usage("Freeze")] + [Description("Makes a targeted area of dynamic items static.")] + public static void Freeze_OnCommand(CommandEventArgs e) + { + BoundingBoxPicker.Begin(e.Mobile, FreezeBox_Callback, null); + } + + [Usage("FreezeMap")] + [Description("Makes every dynamic item in your map static.")] + public static void FreezeMap_OnCommand(CommandEventArgs e) + { + Map map = e.Mobile.Map; + + if (map != null && map != Map.Internal) + SendWarning(e.Mobile, "You are about to freeze all items in {0}.", BaseFreezeWarning, map, NullP3D, + NullP3D, FreezeWarning_Callback); + } + + [Usage("FreezeWorld")] + [Description("Makes every dynamic item on all maps static.")] + public static void FreezeWorld_OnCommand(CommandEventArgs e) + { + SendWarning(e.Mobile, "You are about to freeze every item on every map.", BaseFreezeWarning, null, + NullP3D, NullP3D, FreezeWarning_Callback); + } + + public static void SendWarning(Mobile m, string header, string baseWarning, Map map, Point3D start, Point3D end, + WarningGumpCallback callback) + { + m.SendGump(new WarningGump(1060635, 30720, string.Format(baseWarning, string.Format(header, map)), 0xFFC000, 420, + 400, callback, new StateInfo(map, start, end))); + } + + private static void FreezeBox_Callback(Mobile from, Map map, Point3D start, Point3D end, object state) + { + SendWarning(from, "You are about to freeze a section of items.", BaseFreezeWarning, map, start, end, + FreezeWarning_Callback); + } + + private static void FreezeWarning_Callback(Mobile from, bool okay, object state) + { + if (!okay) + return; + + StateInfo si = (StateInfo)state; + + Freeze(from, si.m_Map, si.m_Start, si.m_End); + } + + public static void Freeze(Mobile from, Map targetMap, Point3D start3d, Point3D end3d) + { + Hashtable mapTable = new Hashtable(); + + if (start3d == NullP3D && end3d == NullP3D) + { + if (targetMap == null) + CommandLogging.WriteLine(from, "{0} {1} invoking freeze for every item in every map", from.AccessLevel, + CommandLogging.Format(from)); + else + CommandLogging.WriteLine(from, "{0} {1} invoking freeze for every item in {0}", from.AccessLevel, + CommandLogging.Format(from), targetMap); + + foreach (Item item in World.Items.Values) + { + if (targetMap != null && item.Map != targetMap) + continue; + + if (item.Parent != null) + continue; + + if (item is Static || item is BaseFloor || item is BaseWall) + { + Map itemMap = item.Map; + + if (itemMap == null || itemMap == Map.Internal) + continue; + + Hashtable table = (Hashtable)mapTable[itemMap]; - private static void FreezeWarning_Callback( Mobile from, bool okay, object state ) - { - if ( !okay ) - return; + if (table == null) + mapTable[itemMap] = table = new Hashtable(); - StateInfo si = (StateInfo)state; + Point2D p = new Point2D(item.X >> 3, item.Y >> 3); - Freeze( from, si.m_Map, si.m_Start, si.m_End ); - } - - public static void Freeze( Mobile from, Map targetMap, Point3D start3d, Point3D end3d ) - { - Hashtable mapTable = new Hashtable(); - - if ( start3d == NullP3D && end3d == NullP3D ) - { - if ( targetMap == null ) - CommandLogging.WriteLine( from, "{0} {1} invoking freeze for every item in every map", from.AccessLevel, CommandLogging.Format( from ) ); - else - CommandLogging.WriteLine( from, "{0} {1} invoking freeze for every item in {0}", from.AccessLevel, CommandLogging.Format( from ), targetMap ); - - foreach ( Item item in World.Items.Values ) - { - if ( targetMap != null && item.Map != targetMap ) - continue; - - if ( item.Parent != null ) - continue; - - if ( item is Static || item is BaseFloor || item is BaseWall ) - { - Map itemMap = item.Map; - - if ( itemMap == null || itemMap == Map.Internal ) - continue; + DeltaState state = (DeltaState)table[p]; - Hashtable table = (Hashtable)mapTable[itemMap]; + if (state == null) + table[p] = state = new DeltaState(p); - if ( table == null ) - mapTable[itemMap] = table = new Hashtable(); + state.m_List.Add(item); + } + } + } + else if (targetMap != null) + { + Point2D start = targetMap.Bound(new Point2D(start3d)), end = targetMap.Bound(new Point2D(end3d)); - Point2D p = new Point2D( item.X >> 3, item.Y >> 3 ); + CommandLogging.WriteLine(from, "{0} {1} invoking freeze from {2} to {3} in {4}", from.AccessLevel, + CommandLogging.Format(from), start, end, targetMap); - DeltaState state = (DeltaState)table[p]; + IPooledEnumerable eable = + targetMap.GetItemsInBounds(new Rectangle2D(start.X, start.Y, end.X - start.X + 1, end.Y - start.Y + 1)); - if ( state == null ) - table[p] = state = new DeltaState( p ); + foreach (Item item in eable) + if (item is Static || item is BaseFloor || item is BaseWall) + { + Map itemMap = item.Map; - state.m_List.Add( item ); - } - } - } - else if ( targetMap != null ) - { - Point2D start = targetMap.Bound( new Point2D( start3d ) ), end = targetMap.Bound( new Point2D( end3d ) ); + if (itemMap == null || itemMap == Map.Internal) + continue; - CommandLogging.WriteLine( from, "{0} {1} invoking freeze from {2} to {3} in {4}", from.AccessLevel, CommandLogging.Format( from ), start, end, targetMap ); + Hashtable table = (Hashtable)mapTable[itemMap]; - IPooledEnumerable eable = targetMap.GetItemsInBounds( new Rectangle2D( start.X, start.Y, end.X - start.X + 1, end.Y - start.Y + 1 ) ); + if (table == null) + mapTable[itemMap] = table = new Hashtable(); - foreach ( Item item in eable ) - { - if ( item is Static || item is BaseFloor || item is BaseWall ) - { - Map itemMap = item.Map; + Point2D p = new Point2D(item.X >> 3, item.Y >> 3); - if ( itemMap == null || itemMap == Map.Internal ) - continue; + DeltaState state = (DeltaState)table[p]; - Hashtable table = (Hashtable)mapTable[itemMap]; + if (state == null) + table[p] = state = new DeltaState(p); - if ( table == null ) - mapTable[itemMap] = table = new Hashtable(); + state.m_List.Add(item); + } - Point2D p = new Point2D( item.X >> 3, item.Y >> 3 ); + eable.Free(); + } - DeltaState state = (DeltaState)table[p]; + if (mapTable.Count == 0) + { + from.SendGump(new NoticeGump(1060637, 30720, + "No freezable items were found. Only the following item types are frozen:
- Static
- BaseFloor
- BaseWall", + 0xFFC000, 320, 240, null, null)); + return; + } - if ( state == null ) - table[p] = state = new DeltaState( p ); + bool badDataFile = false; - state.m_List.Add( item ); - } - } + int totalFrozen = 0; - eable.Free(); - } + foreach (DictionaryEntry de in mapTable) + { + Map map = (Map)de.Key; + Hashtable table = (Hashtable)de.Value; - if ( mapTable.Count == 0 ) - { - from.SendGump( new NoticeGump( 1060637, 30720, "No freezable items were found. Only the following item types are frozen:
- Static
- BaseFloor
- BaseWall", 0xFFC000, 320, 240, null, null ) ); - return; - } + TileMatrix matrix = map.Tiles; - bool badDataFile = false; + using (FileStream idxStream = OpenWrite(matrix.IndexStream)) + { + using (FileStream mulStream = OpenWrite(matrix.DataStream)) + { + if (idxStream == null || mulStream == null) + { + badDataFile = true; + continue; + } - int totalFrozen = 0; + BinaryReader idxReader = new BinaryReader(idxStream); - foreach ( DictionaryEntry de in mapTable ) - { - Map map = (Map)de.Key; - Hashtable table = (Hashtable)de.Value; + BinaryWriter idxWriter = new BinaryWriter(idxStream); + BinaryWriter mulWriter = new BinaryWriter(mulStream); - TileMatrix matrix = map.Tiles; + foreach (DeltaState state in table.Values) + { + int oldTileCount; + StaticTile[] oldTiles = ReadStaticBlock(idxReader, mulStream, state.m_X, state.m_Y, + matrix.BlockWidth, matrix.BlockHeight, out oldTileCount); - using ( FileStream idxStream = OpenWrite( matrix.IndexStream ) ) - { - using ( FileStream mulStream = OpenWrite( matrix.DataStream ) ) - { - if ( idxStream == null || mulStream == null ) - { - badDataFile = true; - continue; - } + if (oldTileCount < 0) + continue; - BinaryReader idxReader = new BinaryReader( idxStream ); + int newTileCount = 0; + StaticTile[] newTiles = new StaticTile[state.m_List.Count]; - BinaryWriter idxWriter = new BinaryWriter( idxStream ); - BinaryWriter mulWriter = new BinaryWriter( mulStream ); + for (int i = 0; i < state.m_List.Count; ++i) + { + Item item = state.m_List[i]; - foreach ( DeltaState state in table.Values ) - { - int oldTileCount; - StaticTile[] oldTiles = ReadStaticBlock( idxReader, mulStream, state.m_X, state.m_Y, matrix.BlockWidth, matrix.BlockHeight, out oldTileCount ); + int xOffset = item.X - state.m_X * 8; + int yOffset = item.Y - state.m_Y * 8; - if ( oldTileCount < 0 ) - continue; + if (xOffset < 0 || xOffset >= 8 || yOffset < 0 || yOffset >= 8) + continue; + + StaticTile newTile = new StaticTile((ushort)item.ItemID, (byte)xOffset, (byte)yOffset, + (sbyte)item.Z, (short)item.Hue); + + newTiles[newTileCount++] = newTile; + + item.Delete(); + + ++totalFrozen; + } + + int mulPos = -1; + int length = -1; + int extra = 0; - int newTileCount = 0; - StaticTile[] newTiles = new StaticTile[state.m_List.Count]; - - for ( int i = 0; i < state.m_List.Count; ++i ) - { - Item item = state.m_List[i]; - - int xOffset = item.X - (state.m_X * 8); - int yOffset = item.Y - (state.m_Y * 8); - - if ( xOffset < 0 || xOffset >= 8 || yOffset < 0 || yOffset >= 8 ) - continue; - - StaticTile newTile = new StaticTile( (ushort)item.ItemID, (byte)xOffset, (byte)yOffset, (sbyte)item.Z, (short)item.Hue ); - - newTiles[newTileCount++] = newTile; - - item.Delete(); - - ++totalFrozen; - } - - int mulPos = -1; - int length = -1; - int extra = 0; - - if ( (oldTileCount + newTileCount) > 0 ) - { - mulWriter.Seek( 0, SeekOrigin.End ); - - mulPos = (int)mulWriter.BaseStream.Position; - length = (oldTileCount + newTileCount) * 7; - extra = 1; - - for ( int i = 0; i < oldTileCount; ++i ) - { - StaticTile toWrite = oldTiles[i]; - - mulWriter.Write( (ushort) toWrite.ID ); - mulWriter.Write( (byte) toWrite.X ); - mulWriter.Write( (byte) toWrite.Y ); - mulWriter.Write( (sbyte) toWrite.Z ); - mulWriter.Write( (short) toWrite.Hue ); - } - - for ( int i = 0; i < newTileCount; ++i ) - { - StaticTile toWrite = newTiles[i]; - - mulWriter.Write( (ushort) toWrite.ID ); - mulWriter.Write( (byte) toWrite.X ); - mulWriter.Write( (byte) toWrite.Y ); - mulWriter.Write( (sbyte) toWrite.Z ); - mulWriter.Write( (short) toWrite.Hue ); - } - - mulWriter.Flush(); - } - - int idxPos = ((state.m_X * matrix.BlockHeight) + state.m_Y) * 12; - - idxWriter.Seek( idxPos, SeekOrigin.Begin ); - idxWriter.Write( mulPos ); - idxWriter.Write( length ); - idxWriter.Write( extra ); - - idxWriter.Flush(); - - matrix.SetStaticBlock( state.m_X, state.m_Y, null ); - } - } - } - } - - if ( totalFrozen == 0 && badDataFile ) - from.SendGump( new NoticeGump( 1060637, 30720, "Output data files could not be opened and the freeze operation has been aborted.

This probably means your server and client are using the same data files. Instructions on how to resolve this can be found in the first warning window.", 0xFFC000, 320, 240, null, null ) ); - else - from.SendGump( new NoticeGump( 1060637, 30720, - $"Freeze operation completed successfully.

{totalFrozen} item{(totalFrozen != 1 ? "s were" : " was")} frozen.

You must restart your client and update it's data files to see the changes.", 0xFFC000, 320, 240, null, null ) ); - } - - private const string BaseUnfreezeWarning = "{0} " + - "Those items will be removed from the static files and exchanged with unmovable dynamic items. " + - "Other players will not see the changes unless you distribute your data files to them.

" + - "This operation may not complete unless the server and client are using different data files. " + - "If you receive a message stating 'output data files could not be opened,' then you are probably sharing data files. " + - "Create a new directory for the world data files (statics*.mul and staidx*.mul) and add that to Scritps/Misc/DataPath.cs.

" + - "The change will be in effect immediately on the server, however, you must restart your client and update it's data files for the changes to become visible. " + - "It is strongly recommended that you make backup of the data files mentioned above. " + - "Do you wish to proceed?"; - - [Usage( "Unfreeze" )] - [Description( "Makes a targeted area of static items dynamic." )] - public static void Unfreeze_OnCommand( CommandEventArgs e ) - { - BoundingBoxPicker.Begin( e.Mobile, UnfreezeBox_Callback, null ); - } - - [Usage( "UnfreezeMap" )] - [Description( "Makes every static item in your map dynamic." )] - public static void UnfreezeMap_OnCommand( CommandEventArgs e ) - { - Map map = e.Mobile.Map; - - if ( map != null && map != Map.Internal ) - SendWarning( e.Mobile, "You are about to unfreeze all items in {0}.", BaseUnfreezeWarning, map, NullP3D, NullP3D, UnfreezeWarning_Callback ); - } - - [Usage( "UnfreezeWorld" )] - [Description( "Makes every static item on all maps dynamic." )] - public static void UnfreezeWorld_OnCommand( CommandEventArgs e ) - { - SendWarning( e.Mobile, "You are about to unfreeze every item on every map.", BaseUnfreezeWarning, null, NullP3D, NullP3D, UnfreezeWarning_Callback ); - } - - private static void UnfreezeBox_Callback( Mobile from, Map map, Point3D start, Point3D end, object state ) - { - SendWarning( from, "You are about to unfreeze a section of items.", BaseUnfreezeWarning, map, start, end, UnfreezeWarning_Callback ); - } - - private static void UnfreezeWarning_Callback( Mobile from, bool okay, object state ) - { - if ( !okay ) - return; - - StateInfo si = (StateInfo)state; - - Unfreeze( from, si.m_Map, si.m_Start, si.m_End ); - } - - private static void DoUnfreeze( Map map, Point2D start, Point2D end, ref bool badDataFile, ref int totalUnfrozen ) - { - start = map.Bound( start ); - end = map.Bound( end ); - - int xStartBlock = start.X >> 3; - int yStartBlock = start.Y >> 3; - int xEndBlock = end.X >> 3; - int yEndBlock = end.Y >> 3; - - int xTileStart = start.X, yTileStart = start.Y; - int xTileWidth = end.X - start.X + 1, yTileHeight = end.Y - start.Y + 1; - - TileMatrix matrix = map.Tiles; - - using ( FileStream idxStream = OpenWrite( matrix.IndexStream ) ) - { - using ( FileStream mulStream = OpenWrite( matrix.DataStream ) ) - { - if ( idxStream == null || mulStream == null ) - { - badDataFile = true; - return; - } - - BinaryReader idxReader = new BinaryReader( idxStream ); - - BinaryWriter idxWriter = new BinaryWriter( idxStream ); - BinaryWriter mulWriter = new BinaryWriter( mulStream ); - - for ( int x = xStartBlock; x <= xEndBlock; ++x ) - { - for ( int y = yStartBlock; y <= yEndBlock; ++y ) - { - int oldTileCount; - StaticTile[] oldTiles = ReadStaticBlock( idxReader, mulStream, x, y, matrix.BlockWidth, matrix.BlockHeight, out oldTileCount ); - - if ( oldTileCount < 0 ) - continue; - - int newTileCount = 0; - StaticTile[] newTiles = new StaticTile[oldTileCount]; - - int baseX = (x << 3) - xTileStart, baseY = (y << 3) - yTileStart; - - for ( int i = 0; i < oldTileCount; ++i ) - { - StaticTile oldTile = oldTiles[i]; - - int px = baseX + oldTile.X; - int py = baseY + oldTile.Y; - - if ( px < 0 || px >= xTileWidth || py < 0 || py >= yTileHeight ) - { - newTiles[newTileCount++] = oldTile; - } - else - { - ++totalUnfrozen; - - Item item = new Static( oldTile.ID ); - - item.Hue = oldTile.Hue; - - item.MoveToWorld( new Point3D( px + xTileStart, py + yTileStart, oldTile.Z ), map ); - } - } - - int mulPos = -1; - int length = -1; - int extra = 0; - - if ( newTileCount > 0 ) - { - mulWriter.Seek( 0, SeekOrigin.End ); - - mulPos = (int)mulWriter.BaseStream.Position; - length = newTileCount * 7; - extra = 1; - - for ( int i = 0; i < newTileCount; ++i ) - { - StaticTile toWrite = newTiles[i]; - - mulWriter.Write( (ushort) toWrite.ID ); - mulWriter.Write( (byte) toWrite.X ); - mulWriter.Write( (byte) toWrite.Y ); - mulWriter.Write( (sbyte) toWrite.Z ); - mulWriter.Write( (short) toWrite.Hue ); - } - - mulWriter.Flush(); - } - - int idxPos = ((x * matrix.BlockHeight) + y) * 12; - - idxWriter.Seek( idxPos, SeekOrigin.Begin ); - idxWriter.Write( mulPos ); - idxWriter.Write( length ); - idxWriter.Write( extra ); - - idxWriter.Flush(); - - matrix.SetStaticBlock( x, y, null ); - } - } - } - } - } - - public static void DoUnfreeze( Map map, ref bool badDataFile, ref int totalUnfrozen ) - { - DoUnfreeze( map, Point2D.Zero, new Point2D( map.Width - 1, map.Height - 1 ), ref badDataFile, ref totalUnfrozen ); - } - - public static void Unfreeze( Mobile from, Map map, Point3D start, Point3D end ) - { - int totalUnfrozen = 0; - bool badDataFile = false; - - if ( map == null ) - { - CommandLogging.WriteLine( from, "{0} {1} invoking unfreeze for every item in every map", from.AccessLevel, CommandLogging.Format( from ) ); - - DoUnfreeze( Map.Felucca, ref badDataFile, ref totalUnfrozen ); - DoUnfreeze( Map.Trammel, ref badDataFile, ref totalUnfrozen ); - DoUnfreeze( Map.Ilshenar, ref badDataFile, ref totalUnfrozen ); - DoUnfreeze( Map.Malas, ref badDataFile, ref totalUnfrozen ); - DoUnfreeze( Map.Tokuno, ref badDataFile, ref totalUnfrozen ); - } - else if ( start == NullP3D && end == NullP3D ) - { - CommandLogging.WriteLine( from, "{0} {1} invoking unfreeze for every item in {2}", from.AccessLevel, CommandLogging.Format( from ), map ); - - DoUnfreeze( map, ref badDataFile, ref totalUnfrozen ); - } - else - { - CommandLogging.WriteLine( from, "{0} {1} invoking unfreeze from {2} to {3} in {4}", from.AccessLevel, CommandLogging.Format( from ), new Point2D( start ), new Point2D( end ), map ); - - DoUnfreeze( map, new Point2D( start ), new Point2D( end ), ref badDataFile, ref totalUnfrozen ); - } - - if ( totalUnfrozen == 0 && badDataFile ) - from.SendGump( new NoticeGump( 1060637, 30720, "Output data files could not be opened and the unfreeze operation has been aborted.

This probably means your server and client are using the same data files. Instructions on how to resolve this can be found in the first warning window.", 0xFFC000, 320, 240, null, null ) ); - else - from.SendGump( new NoticeGump( 1060637, 30720, - $"Unfreeze operation completed successfully.

{totalUnfrozen} item{(totalUnfrozen != 1 ? "s were" : " was")} unfrozen.

You must restart your client and update it's data files to see the changes.", 0xFFC000, 320, 240, null, null ) ); - } - - private static FileStream OpenWrite( FileStream orig ) - { - if ( orig == null ) - return null; - - try{ return new FileStream( orig.Name, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite ); } - catch{ return null; } - } - - private static byte[] m_Buffer; - - private static StaticTile[] m_TileBuffer = new StaticTile[128]; - - private static StaticTile[] ReadStaticBlock( BinaryReader idxReader, FileStream mulStream, int x, int y, int width, int height, out int count ) - { - try - { - if ( x < 0 || x >= width || y < 0 || y >= height ) - { - count = -1; - return m_TileBuffer; - } - - idxReader.BaseStream.Seek( ((x * height) + y) * 12, SeekOrigin.Begin ); - - int lookup = idxReader.ReadInt32(); - int length = idxReader.ReadInt32(); - - if ( lookup < 0 || length <= 0 ) - { - count = 0; - } - else - { - count = length / 7; - - mulStream.Seek( lookup, SeekOrigin.Begin ); - - if ( m_TileBuffer.Length < count ) - m_TileBuffer = new StaticTile[count]; - - StaticTile[] staTiles = m_TileBuffer; - - if ( m_Buffer == null || length > m_Buffer.Length ) - m_Buffer = new byte[length]; - - mulStream.Read( m_Buffer, 0, length ); - - int index = 0; - - for ( int i = 0; i < count; ++i ) - { - staTiles[i].Set((ushort)(m_Buffer[index++] | (m_Buffer[index++] << 8)), - (byte)m_Buffer[index++], (byte)m_Buffer[index++], (sbyte)m_Buffer[index++], - (short)(m_Buffer[index++] | (m_Buffer[index++] << 8))); - } - } - } - catch - { - count = -1; - } - - return m_TileBuffer; - } - - private class DeltaState - { - public int m_X, m_Y; - public List m_List; - - public DeltaState( Point2D p ) - { - m_X = p.X; - m_Y = p.Y; - m_List = new List(); - } - } - - private class StateInfo - { - public Map m_Map; - public Point3D m_Start, m_End; - - public StateInfo( Map map, Point3D start, Point3D end ) - { - m_Map = map; - m_Start = start; - m_End = end; - } - } - } -} + if (oldTileCount + newTileCount > 0) + { + mulWriter.Seek(0, SeekOrigin.End); + + mulPos = (int)mulWriter.BaseStream.Position; + length = (oldTileCount + newTileCount) * 7; + extra = 1; + + for (int i = 0; i < oldTileCount; ++i) + { + StaticTile toWrite = oldTiles[i]; + + mulWriter.Write((ushort)toWrite.ID); + mulWriter.Write((byte)toWrite.X); + mulWriter.Write((byte)toWrite.Y); + mulWriter.Write((sbyte)toWrite.Z); + mulWriter.Write((short)toWrite.Hue); + } + + for (int i = 0; i < newTileCount; ++i) + { + StaticTile toWrite = newTiles[i]; + + mulWriter.Write((ushort)toWrite.ID); + mulWriter.Write((byte)toWrite.X); + mulWriter.Write((byte)toWrite.Y); + mulWriter.Write((sbyte)toWrite.Z); + mulWriter.Write((short)toWrite.Hue); + } + + mulWriter.Flush(); + } + + int idxPos = (state.m_X * matrix.BlockHeight + state.m_Y) * 12; + + idxWriter.Seek(idxPos, SeekOrigin.Begin); + idxWriter.Write(mulPos); + idxWriter.Write(length); + idxWriter.Write(extra); + + idxWriter.Flush(); + + matrix.SetStaticBlock(state.m_X, state.m_Y, null); + } + } + } + } + + if (totalFrozen == 0 && badDataFile) + from.SendGump(new NoticeGump(1060637, 30720, + "Output data files could not be opened and the freeze operation has been aborted.

This probably means your server and client are using the same data files. Instructions on how to resolve this can be found in the first warning window.", + 0xFFC000, 320, 240, null, null)); + else + from.SendGump(new NoticeGump(1060637, 30720, + $"Freeze operation completed successfully.

{totalFrozen} item{(totalFrozen != 1 ? "s were" : " was")} frozen.

You must restart your client and update it's data files to see the changes.", + 0xFFC000, 320, 240, null, null)); + } + + [Usage("Unfreeze")] + [Description("Makes a targeted area of static items dynamic.")] + public static void Unfreeze_OnCommand(CommandEventArgs e) + { + BoundingBoxPicker.Begin(e.Mobile, UnfreezeBox_Callback, null); + } + + [Usage("UnfreezeMap")] + [Description("Makes every static item in your map dynamic.")] + public static void UnfreezeMap_OnCommand(CommandEventArgs e) + { + Map map = e.Mobile.Map; + + if (map != null && map != Map.Internal) + SendWarning(e.Mobile, "You are about to unfreeze all items in {0}.", BaseUnfreezeWarning, map, + NullP3D, NullP3D, UnfreezeWarning_Callback); + } + + [Usage("UnfreezeWorld")] + [Description("Makes every static item on all maps dynamic.")] + public static void UnfreezeWorld_OnCommand(CommandEventArgs e) + { + SendWarning(e.Mobile, "You are about to unfreeze every item on every map.", BaseUnfreezeWarning, null, + NullP3D, NullP3D, UnfreezeWarning_Callback); + } + + private static void UnfreezeBox_Callback(Mobile from, Map map, Point3D start, Point3D end, object state) + { + SendWarning(from, "You are about to unfreeze a section of items.", BaseUnfreezeWarning, map, start, end, + UnfreezeWarning_Callback); + } + + private static void UnfreezeWarning_Callback(Mobile from, bool okay, object state) + { + if (!okay) + return; + + StateInfo si = (StateInfo)state; + + Unfreeze(from, si.m_Map, si.m_Start, si.m_End); + } + + private static void DoUnfreeze(Map map, Point2D start, Point2D end, ref bool badDataFile, ref int totalUnfrozen) + { + start = map.Bound(start); + end = map.Bound(end); + + int xStartBlock = start.X >> 3; + int yStartBlock = start.Y >> 3; + int xEndBlock = end.X >> 3; + int yEndBlock = end.Y >> 3; + + int xTileStart = start.X, yTileStart = start.Y; + int xTileWidth = end.X - start.X + 1, yTileHeight = end.Y - start.Y + 1; + + TileMatrix matrix = map.Tiles; + + using (FileStream idxStream = OpenWrite(matrix.IndexStream)) + { + using (FileStream mulStream = OpenWrite(matrix.DataStream)) + { + if (idxStream == null || mulStream == null) + { + badDataFile = true; + return; + } + + BinaryReader idxReader = new BinaryReader(idxStream); + + BinaryWriter idxWriter = new BinaryWriter(idxStream); + BinaryWriter mulWriter = new BinaryWriter(mulStream); + + for (int x = xStartBlock; x <= xEndBlock; ++x) + for (int y = yStartBlock; y <= yEndBlock; ++y) + { + int oldTileCount; + StaticTile[] oldTiles = ReadStaticBlock(idxReader, mulStream, x, y, matrix.BlockWidth, + matrix.BlockHeight, out oldTileCount); + + if (oldTileCount < 0) + continue; + + int newTileCount = 0; + StaticTile[] newTiles = new StaticTile[oldTileCount]; + + int baseX = (x << 3) - xTileStart, baseY = (y << 3) - yTileStart; + + for (int i = 0; i < oldTileCount; ++i) + { + StaticTile oldTile = oldTiles[i]; + + int px = baseX + oldTile.X; + int py = baseY + oldTile.Y; + + if (px < 0 || px >= xTileWidth || py < 0 || py >= yTileHeight) + { + newTiles[newTileCount++] = oldTile; + } + else + { + ++totalUnfrozen; + + Item item = new Static(oldTile.ID); + + item.Hue = oldTile.Hue; + + item.MoveToWorld(new Point3D(px + xTileStart, py + yTileStart, oldTile.Z), map); + } + } + + int mulPos = -1; + int length = -1; + int extra = 0; + + if (newTileCount > 0) + { + mulWriter.Seek(0, SeekOrigin.End); + + mulPos = (int)mulWriter.BaseStream.Position; + length = newTileCount * 7; + extra = 1; + + for (int i = 0; i < newTileCount; ++i) + { + StaticTile toWrite = newTiles[i]; + + mulWriter.Write((ushort)toWrite.ID); + mulWriter.Write((byte)toWrite.X); + mulWriter.Write((byte)toWrite.Y); + mulWriter.Write((sbyte)toWrite.Z); + mulWriter.Write((short)toWrite.Hue); + } + + mulWriter.Flush(); + } + + int idxPos = (x * matrix.BlockHeight + y) * 12; + + idxWriter.Seek(idxPos, SeekOrigin.Begin); + idxWriter.Write(mulPos); + idxWriter.Write(length); + idxWriter.Write(extra); + + idxWriter.Flush(); + + matrix.SetStaticBlock(x, y, null); + } + } + } + } + + public static void DoUnfreeze(Map map, ref bool badDataFile, ref int totalUnfrozen) + { + DoUnfreeze(map, Point2D.Zero, new Point2D(map.Width - 1, map.Height - 1), ref badDataFile, ref totalUnfrozen); + } + + public static void Unfreeze(Mobile from, Map map, Point3D start, Point3D end) + { + int totalUnfrozen = 0; + bool badDataFile = false; + + if (map == null) + { + CommandLogging.WriteLine(from, "{0} {1} invoking unfreeze for every item in every map", from.AccessLevel, + CommandLogging.Format(from)); + + DoUnfreeze(Map.Felucca, ref badDataFile, ref totalUnfrozen); + DoUnfreeze(Map.Trammel, ref badDataFile, ref totalUnfrozen); + DoUnfreeze(Map.Ilshenar, ref badDataFile, ref totalUnfrozen); + DoUnfreeze(Map.Malas, ref badDataFile, ref totalUnfrozen); + DoUnfreeze(Map.Tokuno, ref badDataFile, ref totalUnfrozen); + } + else if (start == NullP3D && end == NullP3D) + { + CommandLogging.WriteLine(from, "{0} {1} invoking unfreeze for every item in {2}", from.AccessLevel, + CommandLogging.Format(from), map); + + DoUnfreeze(map, ref badDataFile, ref totalUnfrozen); + } + else + { + CommandLogging.WriteLine(from, "{0} {1} invoking unfreeze from {2} to {3} in {4}", from.AccessLevel, + CommandLogging.Format(from), new Point2D(start), new Point2D(end), map); + + DoUnfreeze(map, new Point2D(start), new Point2D(end), ref badDataFile, ref totalUnfrozen); + } + + if (totalUnfrozen == 0 && badDataFile) + from.SendGump(new NoticeGump(1060637, 30720, + "Output data files could not be opened and the unfreeze operation has been aborted.

This probably means your server and client are using the same data files. Instructions on how to resolve this can be found in the first warning window.", + 0xFFC000, 320, 240, null, null)); + else + from.SendGump(new NoticeGump(1060637, 30720, + $"Unfreeze operation completed successfully.

{totalUnfrozen} item{(totalUnfrozen != 1 ? "s were" : " was")} unfrozen.

You must restart your client and update it's data files to see the changes.", + 0xFFC000, 320, 240, null, null)); + } + + private static FileStream OpenWrite(FileStream orig) + { + if (orig == null) + return null; + + try + { + return new FileStream(orig.Name, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite); + } + catch + { + return null; + } + } + + private static StaticTile[] ReadStaticBlock(BinaryReader idxReader, FileStream mulStream, int x, int y, int width, + int height, out int count) + { + try + { + if (x < 0 || x >= width || y < 0 || y >= height) + { + count = -1; + return m_TileBuffer; + } + + idxReader.BaseStream.Seek((x * height + y) * 12, SeekOrigin.Begin); + + int lookup = idxReader.ReadInt32(); + int length = idxReader.ReadInt32(); + + if (lookup < 0 || length <= 0) + { + count = 0; + } + else + { + count = length / 7; + + mulStream.Seek(lookup, SeekOrigin.Begin); + + if (m_TileBuffer.Length < count) + m_TileBuffer = new StaticTile[count]; + + StaticTile[] staTiles = m_TileBuffer; + + if (m_Buffer == null || length > m_Buffer.Length) + m_Buffer = new byte[length]; + + mulStream.Read(m_Buffer, 0, length); + + int index = 0; + + for (int i = 0; i < count; ++i) + staTiles[i].Set((ushort)(m_Buffer[index++] | (m_Buffer[index++] << 8)), + m_Buffer[index++], m_Buffer[index++], (sbyte)m_Buffer[index++], + (short)(m_Buffer[index++] | (m_Buffer[index++] << 8))); + } + } + catch + { + count = -1; + } + + return m_TileBuffer; + } + + private class DeltaState + { + public List m_List; + public int m_X, m_Y; + + public DeltaState(Point2D p) + { + m_X = p.X; + m_Y = p.Y; + m_List = new List(); + } + } + + private class StateInfo + { + public Map m_Map; + public Point3D m_Start, m_End; + + public StateInfo(Map map, Point3D start, Point3D end) + { + m_Map = map; + m_Start = start; + m_End = end; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/VisibilityList.cs b/Scripts/Commands/VisibilityList.cs index 93f3172b3..6e7afd9ec 100644 --- a/Scripts/Commands/VisibilityList.cs +++ b/Scripts/Commands/VisibilityList.cs @@ -1,142 +1,141 @@ -using Server.Mobiles; -using Server.Targeting; -using Server.Network; using System.Collections.Generic; +using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Commands { - public class VisibilityList - { - public static void Initialize() - { - EventSink.Login += OnLogin; + public class VisibilityList + { + public static void Initialize() + { + EventSink.Login += OnLogin; - CommandSystem.Register( "Vis", AccessLevel.Counselor, Vis_OnCommand ); - CommandSystem.Register( "VisList", AccessLevel.Counselor, VisList_OnCommand ); - CommandSystem.Register( "VisClear", AccessLevel.Counselor, VisClear_OnCommand ); - } + CommandSystem.Register("Vis", AccessLevel.Counselor, Vis_OnCommand); + CommandSystem.Register("VisList", AccessLevel.Counselor, VisList_OnCommand); + CommandSystem.Register("VisClear", AccessLevel.Counselor, VisClear_OnCommand); + } - public static void OnLogin( LoginEventArgs e ) - { - if ( e.Mobile is PlayerMobile pm ) - { - pm.VisibilityList.Clear(); - } - } + public static void OnLogin(LoginEventArgs e) + { + if (e.Mobile is PlayerMobile pm) pm.VisibilityList.Clear(); + } - [Usage( "Vis" )] - [Description( "Adds or removes a targeted player from your visibility list. Anyone on your visibility list will be able to see you at all times, even when you're hidden." )] - public static void Vis_OnCommand( CommandEventArgs e ) - { - if ( e.Mobile is PlayerMobile ) - { - e.Mobile.Target = new VisTarget(); - e.Mobile.SendMessage( "Select person to add or remove from your visibility list." ); - } - } + [Usage("Vis")] + [Description( + "Adds or removes a targeted player from your visibility list. Anyone on your visibility list will be able to see you at all times, even when you're hidden.")] + public static void Vis_OnCommand(CommandEventArgs e) + { + if (e.Mobile is PlayerMobile) + { + e.Mobile.Target = new VisTarget(); + e.Mobile.SendMessage("Select person to add or remove from your visibility list."); + } + } - [Usage( "VisList" )] - [Description( "Shows the names of everyone in your visibility list." )] - public static void VisList_OnCommand( CommandEventArgs e ) - { - if ( e.Mobile is PlayerMobile pm ) - { - List list = pm.VisibilityList; + [Usage("VisList")] + [Description("Shows the names of everyone in your visibility list.")] + public static void VisList_OnCommand(CommandEventArgs e) + { + if (e.Mobile is PlayerMobile pm) + { + List list = pm.VisibilityList; - if ( list.Count > 0 ) - { - pm.SendMessage( "You are visible to {0} mobile{1}:", list.Count, list.Count == 1 ? "" : "s" ); + if (list.Count > 0) + { + pm.SendMessage("You are visible to {0} mobile{1}:", list.Count, list.Count == 1 ? "" : "s"); - for ( int i = 0; i < list.Count; ++i ) - pm.SendMessage( "#{0}: {1}", i+1, list[i].Name ); - } - else - { - pm.SendMessage( "Your visibility list is empty." ); - } - } - } + for (int i = 0; i < list.Count; ++i) + pm.SendMessage("#{0}: {1}", i + 1, list[i].Name); + } + else + { + pm.SendMessage("Your visibility list is empty."); + } + } + } - [Usage( "VisClear" )] - [Description( "Removes everyone from your visibility list." )] - public static void VisClear_OnCommand( CommandEventArgs e ) - { - if ( e.Mobile is PlayerMobile pm ) - { - List list = new List( pm.VisibilityList ); + [Usage("VisClear")] + [Description("Removes everyone from your visibility list.")] + public static void VisClear_OnCommand(CommandEventArgs e) + { + if (e.Mobile is PlayerMobile pm) + { + List list = new List(pm.VisibilityList); - pm.VisibilityList.Clear(); - pm.SendMessage( "Your visibility list has been cleared." ); + pm.VisibilityList.Clear(); + pm.SendMessage("Your visibility list has been cleared."); - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = list[i]; + for (int i = 0; i < list.Count; ++i) + { + Mobile m = list[i]; - if ( !m.CanSee( pm ) && Utility.InUpdateRange( m, pm ) ) - m.Send( pm.RemovePacket ); - } - } - } + if (!m.CanSee(pm) && Utility.InUpdateRange(m, pm)) + m.Send(pm.RemovePacket); + } + } + } - private class VisTarget : Target - { - public VisTarget() : base( -1, false, TargetFlags.None ) - { - } + private class VisTarget : Target + { + public VisTarget() : base(-1, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( from is PlayerMobile pm && targeted is Mobile targ ) - { - if ( targ.AccessLevel <= pm.AccessLevel ) - { - List list = pm.VisibilityList; + protected override void OnTarget(Mobile from, object targeted) + { + if (from is PlayerMobile pm && targeted is Mobile targ) + { + if (targ.AccessLevel <= pm.AccessLevel) + { + List list = pm.VisibilityList; - if ( list.Contains( targ ) ) - { - list.Remove( targ ); - pm.SendMessage( "{0} has been removed from your visibility list.", targ.Name ); - } - else - { - list.Add( targ ); - pm.SendMessage( "{0} has been added to your visibility list.", targ.Name ); - } + if (list.Contains(targ)) + { + list.Remove(targ); + pm.SendMessage("{0} has been removed from your visibility list.", targ.Name); + } + else + { + list.Add(targ); + pm.SendMessage("{0} has been added to your visibility list.", targ.Name); + } - if ( Utility.InUpdateRange( targ, from ) ) - { - NetState ns = targ.NetState; + if (Utility.InUpdateRange(targ, from)) + { + NetState ns = targ.NetState; - if ( ns != null ) { - if ( targ.CanSee( pm ) ) - { - ns.Send(MobileIncoming.Create(ns, targ, pm)); + if (ns != null) + { + if (targ.CanSee(pm)) + { + ns.Send(MobileIncoming.Create(ns, targ, pm)); - if ( ObjectPropertyList.Enabled ) - { - ns.Send( pm.OPLPacket ); + if (ObjectPropertyList.Enabled) + { + ns.Send(pm.OPLPacket); - foreach ( Item item in pm.Items ) - ns.Send( item.OPLPacket ); - } - } - else - { - ns.Send( pm.RemovePacket ); - } - } - } - } - else - { - pm.SendMessage( "They can already see you!" ); - } - } - else - { - from.SendMessage( "Add only mobiles to your visibility list." ); - } - } - } - } -} + foreach (Item item in pm.Items) + ns.Send(item.OPLPacket); + } + } + else + { + ns.Send(pm.RemovePacket); + } + } + } + } + else + { + pm.SendMessage("They can already see you!"); + } + } + else + { + from.SendMessage("Add only mobiles to your visibility list."); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Commands/Wipe.cs b/Scripts/Commands/Wipe.cs index e8c9dd8bb..a5fb11cca 100644 --- a/Scripts/Commands/Wipe.cs +++ b/Scripts/Commands/Wipe.cs @@ -5,96 +5,95 @@ using Server.Multis; namespace Server.Commands { - public class Wipe - { - [Flags] - public enum WipeType - { - Items = 0x01, - Mobiles = 0x02, - Multis = 0x04, - All = Items | Mobiles | Multis - } + public class Wipe + { + [Flags] + public enum WipeType + { + Items = 0x01, + Mobiles = 0x02, + Multis = 0x04, + All = Items | Mobiles | Multis + } - public static void Initialize() - { - CommandSystem.Register( "Wipe", AccessLevel.GameMaster, WipeAll_OnCommand ); - CommandSystem.Register( "WipeItems", AccessLevel.GameMaster, WipeItems_OnCommand ); - CommandSystem.Register( "WipeNPCs", AccessLevel.GameMaster, WipeNPCs_OnCommand ); - CommandSystem.Register( "WipeMultis", AccessLevel.GameMaster, WipeMultis_OnCommand ); - } + public static void Initialize() + { + CommandSystem.Register("Wipe", AccessLevel.GameMaster, WipeAll_OnCommand); + CommandSystem.Register("WipeItems", AccessLevel.GameMaster, WipeItems_OnCommand); + CommandSystem.Register("WipeNPCs", AccessLevel.GameMaster, WipeNPCs_OnCommand); + CommandSystem.Register("WipeMultis", AccessLevel.GameMaster, WipeMultis_OnCommand); + } - [Usage( "Wipe" )] - [Description( "Wipes all items and npcs in a targeted bounding box." )] - private static void WipeAll_OnCommand( CommandEventArgs e ) - { - BeginWipe( e.Mobile, WipeType.Items | WipeType.Mobiles ); - } + [Usage("Wipe")] + [Description("Wipes all items and npcs in a targeted bounding box.")] + private static void WipeAll_OnCommand(CommandEventArgs e) + { + BeginWipe(e.Mobile, WipeType.Items | WipeType.Mobiles); + } - [Usage( "WipeItems" )] - [Description( "Wipes all items in a targeted bounding box." )] - private static void WipeItems_OnCommand( CommandEventArgs e ) - { - BeginWipe( e.Mobile, WipeType.Items ); - } + [Usage("WipeItems")] + [Description("Wipes all items in a targeted bounding box.")] + private static void WipeItems_OnCommand(CommandEventArgs e) + { + BeginWipe(e.Mobile, WipeType.Items); + } - [Usage( "WipeNPCs" )] - [Description( "Wipes all npcs in a targeted bounding box." )] - private static void WipeNPCs_OnCommand( CommandEventArgs e ) - { - BeginWipe( e.Mobile, WipeType.Mobiles ); - } + [Usage("WipeNPCs")] + [Description("Wipes all npcs in a targeted bounding box.")] + private static void WipeNPCs_OnCommand(CommandEventArgs e) + { + BeginWipe(e.Mobile, WipeType.Mobiles); + } - [Usage( "WipeMultis" )] - [Description( "Wipes all multis in a targeted bounding box." )] - private static void WipeMultis_OnCommand( CommandEventArgs e ) - { - BeginWipe( e.Mobile, WipeType.Multis ); - } + [Usage("WipeMultis")] + [Description("Wipes all multis in a targeted bounding box.")] + private static void WipeMultis_OnCommand(CommandEventArgs e) + { + BeginWipe(e.Mobile, WipeType.Multis); + } - public static void BeginWipe( Mobile from, WipeType type ) - { - BoundingBoxPicker.Begin( from, WipeBox_Callback, type ); - } + public static void BeginWipe(Mobile from, WipeType type) + { + BoundingBoxPicker.Begin(from, WipeBox_Callback, type); + } - private static void WipeBox_Callback( Mobile from, Map map, Point3D start, Point3D end, object state ) - { - DoWipe( from, map, start, end, (WipeType)state ); - } + private static void WipeBox_Callback(Mobile from, Map map, Point3D start, Point3D end, object state) + { + DoWipe(from, map, start, end, (WipeType)state); + } - public static void DoWipe( Mobile from, Map map, Point3D start, Point3D end, WipeType type ) - { - CommandLogging.WriteLine( from, "{0} {1} wiping from {2} to {3} in {5} ({4})", from.AccessLevel, CommandLogging.Format( from ), start, end, type, map ); + public static void DoWipe(Mobile from, Map map, Point3D start, Point3D end, WipeType type) + { + CommandLogging.WriteLine(from, "{0} {1} wiping from {2} to {3} in {5} ({4})", from.AccessLevel, + CommandLogging.Format(from), start, end, type, map); - bool mobiles = ( (type & WipeType.Mobiles) != 0 ); - bool multis = ( (type & WipeType.Multis) != 0 ); - bool items = ( (type & WipeType.Items) != 0 ); + bool mobiles = (type & WipeType.Mobiles) != 0; + bool multis = (type & WipeType.Multis) != 0; + bool items = (type & WipeType.Items) != 0; - List toDelete = new List(); + List toDelete = new List(); - Rectangle2D rect = new Rectangle2D( start.X, start.Y, end.X - start.X + 1, end.Y - start.Y + 1 ); + Rectangle2D rect = new Rectangle2D(start.X, start.Y, end.X - start.X + 1, end.Y - start.Y + 1); - IPooledEnumerable eable; + IPooledEnumerable eable; - if ( (items || multis) && mobiles ) - eable = map.GetObjectsInBounds( rect, items || multis, mobiles ); - else - return; + if ((items || multis) && mobiles) + eable = map.GetObjectsInBounds(rect, items || multis, mobiles); + else + return; - foreach ( IEntity obj in eable ) - { - if ( items && (obj is Item) && !((obj is BaseMulti) || (obj is HouseSign)) ) - toDelete.Add( obj ); - else if ( multis && (obj is BaseMulti) ) - toDelete.Add( obj ); - else if ( mobiles && (obj is Mobile mobile) && !mobile.Player ) - toDelete.Add( mobile ); - } + foreach (IEntity obj in eable) + if (items && obj is Item && !(obj is BaseMulti || obj is HouseSign)) + toDelete.Add(obj); + else if (multis && obj is BaseMulti) + toDelete.Add(obj); + else if (mobiles && obj is Mobile mobile && !mobile.Player) + toDelete.Add(mobile); - eable.Free(); + eable.Free(); - for ( int i = 0; i < toDelete.Count; ++i ) - toDelete[i].Delete(); - } - } -} + for (int i = 0; i < toDelete.Count; ++i) + toDelete[i].Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Context Menus/AddToParty.cs b/Scripts/Context Menus/AddToParty.cs index ac839ab09..c35817acc 100644 --- a/Scripts/Context Menus/AddToParty.cs +++ b/Scripts/Context Menus/AddToParty.cs @@ -2,36 +2,36 @@ using Server.Engines.PartySystem; namespace Server.ContextMenus { - public class AddToPartyEntry : ContextMenuEntry - { - private Mobile m_From; - private Mobile m_Target; - - public AddToPartyEntry( Mobile from, Mobile target ) : base( 0197, 12 ) - { - m_From = from; - m_Target = target; - } + public class AddToPartyEntry : ContextMenuEntry + { + private Mobile m_From; + private Mobile m_Target; - public override void OnClick() - { - Party p = Party.Get( m_From ); - Party mp = Party.Get( m_Target ); + public AddToPartyEntry(Mobile from, Mobile target) : base(0197, 12) + { + m_From = from; + m_Target = target; + } - if ( m_From == m_Target ) - m_From.SendLocalizedMessage( 1005439 ); // You cannot add yourself to a party. - else if ( p != null && p.Leader != m_From ) - m_From.SendLocalizedMessage( 1005453 ); // You may only add members to the party if you are the leader. - else if ( p != null && (p.Members.Count + p.Candidates.Count) >= Party.Capacity ) - m_From.SendLocalizedMessage( 1008095 ); // You may only have 10 in your party (this includes candidates). - else if ( !m_Target.Player ) - m_From.SendLocalizedMessage( 1005444 ); // The creature ignores your offer. - else if ( mp != null && mp == p ) - m_From.SendLocalizedMessage( 1005440 ); // This person is already in your party! - else if ( mp != null ) - m_From.SendLocalizedMessage( 1005441 ); // This person is already in a party! - else - Party.Invite( m_From, m_Target ); - } - } -} + public override void OnClick() + { + Party p = Party.Get(m_From); + Party mp = Party.Get(m_Target); + + if (m_From == m_Target) + m_From.SendLocalizedMessage(1005439); // You cannot add yourself to a party. + else if (p != null && p.Leader != m_From) + m_From.SendLocalizedMessage(1005453); // You may only add members to the party if you are the leader. + else if (p != null && p.Members.Count + p.Candidates.Count >= Party.Capacity) + m_From.SendLocalizedMessage(1008095); // You may only have 10 in your party (this includes candidates). + else if (!m_Target.Player) + m_From.SendLocalizedMessage(1005444); // The creature ignores your offer. + else if (mp != null && mp == p) + m_From.SendLocalizedMessage(1005440); // This person is already in your party! + else if (mp != null) + m_From.SendLocalizedMessage(1005441); // This person is already in a party! + else + Party.Invite(m_From, m_Target); + } + } +} \ No newline at end of file diff --git a/Scripts/Context Menus/AddToSpellbookEntry.cs b/Scripts/Context Menus/AddToSpellbookEntry.cs index 632679c52..434f7186a 100644 --- a/Scripts/Context Menus/AddToSpellbookEntry.cs +++ b/Scripts/Context Menus/AddToSpellbookEntry.cs @@ -1,60 +1,60 @@ using Server.Items; +using Server.Network; using Server.Targeting; namespace Server.ContextMenus { - public class AddToSpellbookEntry : ContextMenuEntry - { - public AddToSpellbookEntry() : base( 6144, 3 ) - { - } + public class AddToSpellbookEntry : ContextMenuEntry + { + public AddToSpellbookEntry() : base(6144, 3) + { + } - public override void OnClick() - { - if ( Owner.From.CheckAlive() && Owner.Target is SpellScroll scroll ) - Owner.From.Target = new InternalTarget( scroll ); - } + public override void OnClick() + { + if (Owner.From.CheckAlive() && Owner.Target is SpellScroll scroll) + Owner.From.Target = new InternalTarget(scroll); + } - private class InternalTarget : Target - { - private SpellScroll m_Scroll; + private class InternalTarget : Target + { + private SpellScroll m_Scroll; - public InternalTarget( SpellScroll scroll ) : base( 3, false, TargetFlags.None ) - { - m_Scroll = scroll; - } + public InternalTarget(SpellScroll scroll) : base(3, false, TargetFlags.None) + { + m_Scroll = scroll; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Spellbook book ) - { - if ( from.CheckAlive() && !m_Scroll.Deleted && m_Scroll.Movable && m_Scroll.Amount >= 1 && m_Scroll.CheckItemUse( from ) ) - { - SpellbookType type = Spellbook.GetTypeForSpell( m_Scroll.SpellID ); + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Spellbook book) + if (from.CheckAlive() && !m_Scroll.Deleted && m_Scroll.Movable && m_Scroll.Amount >= 1 && + m_Scroll.CheckItemUse(from)) + { + SpellbookType type = Spellbook.GetTypeForSpell(m_Scroll.SpellID); - if ( type != book.SpellbookType ) - { - } - else if ( book.HasSpell( m_Scroll.SpellID ) ) - { - from.SendLocalizedMessage( 500179 ); // That spell is already present in that spellbook. - } - else - { - int val = m_Scroll.SpellID - book.BookOffset; + if (type != book.SpellbookType) + { + } + else if (book.HasSpell(m_Scroll.SpellID)) + { + from.SendLocalizedMessage(500179); // That spell is already present in that spellbook. + } + else + { + int val = m_Scroll.SpellID - book.BookOffset; - if ( val >= 0 && val < book.BookCount ) - { - book.Content |= (ulong)1 << val; + if (val >= 0 && val < book.BookCount) + { + book.Content |= (ulong)1 << val; - m_Scroll.Consume(); + m_Scroll.Consume(); - from.Send( new Network.PlaySound( 0x249, book.GetWorldLocation() ) ); - } - } - } - } - } - } - } -} + from.Send(new PlaySound(0x249, book.GetWorldLocation())); + } + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Context Menus/EatEntry.cs b/Scripts/Context Menus/EatEntry.cs index 62d3aab57..3aebaa29a 100644 --- a/Scripts/Context Menus/EatEntry.cs +++ b/Scripts/Context Menus/EatEntry.cs @@ -2,23 +2,23 @@ using Server.Items; namespace Server.ContextMenus { - public class EatEntry : ContextMenuEntry - { - private Mobile m_From; - private Food m_Food; + public class EatEntry : ContextMenuEntry + { + private Food m_Food; + private Mobile m_From; - public EatEntry( Mobile from, Food food ) : base( 6135, 1 ) - { - m_From = from; - m_Food = food; - } + public EatEntry(Mobile from, Food food) : base(6135, 1) + { + m_From = from; + m_Food = food; + } - public override void OnClick() - { - if ( m_Food.Deleted || !m_Food.Movable || !m_From.CheckAlive() || !m_Food.CheckItemUse( m_From ) ) - return; + public override void OnClick() + { + if (m_Food.Deleted || !m_Food.Movable || !m_From.CheckAlive() || !m_Food.CheckItemUse(m_From)) + return; - m_Food.Eat( m_From ); - } - } + m_Food.Eat(m_From); + } + } } \ No newline at end of file diff --git a/Scripts/Context Menus/EjectPlayer.cs b/Scripts/Context Menus/EjectPlayer.cs index 017ccb4c6..dff14d980 100644 --- a/Scripts/Context Menus/EjectPlayer.cs +++ b/Scripts/Context Menus/EjectPlayer.cs @@ -2,26 +2,26 @@ using Server.Multis; namespace Server.ContextMenus { - public class EjectPlayerEntry : ContextMenuEntry - { - private Mobile m_From; - private Mobile m_Target; - private BaseHouse m_TargetHouse; + public class EjectPlayerEntry : ContextMenuEntry + { + private Mobile m_From; + private Mobile m_Target; + private BaseHouse m_TargetHouse; - public EjectPlayerEntry( Mobile from, Mobile target ) : base( 6206, 12 ) - { - m_From = from; - m_Target = target; - m_TargetHouse = BaseHouse.FindHouseAt( m_Target ); - } + public EjectPlayerEntry(Mobile from, Mobile target) : base(6206, 12) + { + m_From = from; + m_Target = target; + m_TargetHouse = BaseHouse.FindHouseAt(m_Target); + } - public override void OnClick() - { - if ( !m_From.Alive || m_TargetHouse.Deleted || !m_TargetHouse.IsFriend( m_From ) ) - return; + public override void OnClick() + { + if (!m_From.Alive || m_TargetHouse.Deleted || !m_TargetHouse.IsFriend(m_From)) + return; - if ( m_Target is Mobile mobile ) - m_TargetHouse.Kick( m_From, mobile ); - } - } -} + if (m_Target is Mobile mobile) + m_TargetHouse.Kick(m_From, mobile); + } + } +} \ No newline at end of file diff --git a/Scripts/Context Menus/OpenBankEntry.cs b/Scripts/Context Menus/OpenBankEntry.cs index a3781749b..35b1a4dad 100644 --- a/Scripts/Context Menus/OpenBankEntry.cs +++ b/Scripts/Context Menus/OpenBankEntry.cs @@ -1,27 +1,23 @@ namespace Server.ContextMenus { - public class OpenBankEntry : ContextMenuEntry - { - private Mobile m_Banker; + public class OpenBankEntry : ContextMenuEntry + { + private Mobile m_Banker; - public OpenBankEntry( Mobile from, Mobile banker ) : base( 6105, 12 ) - { - m_Banker = banker; - } + public OpenBankEntry(Mobile from, Mobile banker) : base(6105, 12) + { + m_Banker = banker; + } - public override void OnClick() - { - if ( !Owner.From.CheckAlive() ) - return; + public override void OnClick() + { + if (!Owner.From.CheckAlive()) + return; - if ( Owner.From.Criminal ) - { - m_Banker.Say( 500378 ); // Thou art a criminal and cannot access thy bank box. - } - else - { - Owner.From.BankBox.Open(); - } - } - } + if (Owner.From.Criminal) + m_Banker.Say(500378); // Thou art a criminal and cannot access thy bank box. + else + Owner.From.BankBox.Open(); + } + } } \ No newline at end of file diff --git a/Scripts/Context Menus/TeachEntry.cs b/Scripts/Context Menus/TeachEntry.cs index 1aea4cf08..03f0f5325 100644 --- a/Scripts/Context Menus/TeachEntry.cs +++ b/Scripts/Context Menus/TeachEntry.cs @@ -1,29 +1,30 @@ using Server.Mobiles; +using Server.Network; namespace Server.ContextMenus { - public class TeachEntry : ContextMenuEntry - { - private SkillName m_Skill; - private BaseCreature m_Mobile; - private Mobile m_From; + public class TeachEntry : ContextMenuEntry + { + private Mobile m_From; + private BaseCreature m_Mobile; + private SkillName m_Skill; - public TeachEntry( SkillName skill, BaseCreature m, Mobile from, bool enabled ) : base( 6000 + (int)skill ) - { - m_Skill = skill; - m_Mobile = m; - m_From = from; + public TeachEntry(SkillName skill, BaseCreature m, Mobile from, bool enabled) : base(6000 + (int)skill) + { + m_Skill = skill; + m_Mobile = m; + m_From = from; - if ( !enabled ) - Flags |= Network.CMEFlags.Disabled; - } + if (!enabled) + Flags |= CMEFlags.Disabled; + } - public override void OnClick() - { - if ( !m_From.CheckAlive() ) - return; + public override void OnClick() + { + if (!m_From.CheckAlive()) + return; - m_Mobile.Teach( m_Skill, m_From, 0, false ); - } - } + m_Mobile.Teach(m_Skill, m_From, 0, false); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BOBFilter.cs b/Scripts/Engines/BulkOrders/Books/BOBFilter.cs index fc827cea7..638c26108 100644 --- a/Scripts/Engines/BulkOrders/Books/BOBFilter.cs +++ b/Scripts/Engines/BulkOrders/Books/BOBFilter.cs @@ -1,62 +1,62 @@ namespace Server.Engines.BulkOrders { - public class BOBFilter - { - public bool IsDefault => ( Type == 0 && Quality == 0 && Material == 0 && Quantity == 0 ); + public class BOBFilter + { + public BOBFilter() + { + } - public void Clear() - { - Type = 0; - Quality = 0; - Material = 0; - Quantity = 0; - } + public BOBFilter(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public int Type { get; set; } + switch (version) + { + case 1: + { + Type = reader.ReadEncodedInt(); + Quality = reader.ReadEncodedInt(); + Material = reader.ReadEncodedInt(); + Quantity = reader.ReadEncodedInt(); - public int Quality { get; set; } + break; + } + } + } - public int Material { get; set; } + public bool IsDefault => Type == 0 && Quality == 0 && Material == 0 && Quantity == 0; - public int Quantity { get; set; } + public int Type{ get; set; } - public BOBFilter() - { - } + public int Quality{ get; set; } - public BOBFilter( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public int Material{ get; set; } - switch ( version ) - { - case 1: - { - Type = reader.ReadEncodedInt(); - Quality = reader.ReadEncodedInt(); - Material = reader.ReadEncodedInt(); - Quantity = reader.ReadEncodedInt(); + public int Quantity{ get; set; } - break; - } - } - } + public void Clear() + { + Type = 0; + Quality = 0; + Material = 0; + Quantity = 0; + } - public void Serialize( GenericWriter writer ) - { - if ( IsDefault ) - { - writer.WriteEncodedInt( 0 ); // version - } - else - { - writer.WriteEncodedInt( 1 ); // version + public void Serialize(GenericWriter writer) + { + if (IsDefault) + { + writer.WriteEncodedInt(0); // version + } + else + { + writer.WriteEncodedInt(1); // version - writer.WriteEncodedInt( Type ); - writer.WriteEncodedInt( Quality ); - writer.WriteEncodedInt( Material ); - writer.WriteEncodedInt( Quantity ); - } - } - } + writer.WriteEncodedInt(Type); + writer.WriteEncodedInt(Quality); + writer.WriteEncodedInt(Material); + writer.WriteEncodedInt(Quantity); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BOBFilterGump.cs b/Scripts/Engines/BulkOrders/Books/BOBFilterGump.cs index c95a2daa1..aac526108 100644 --- a/Scripts/Engines/BulkOrders/Books/BOBFilterGump.cs +++ b/Scripts/Engines/BulkOrders/Books/BOBFilterGump.cs @@ -1,206 +1,224 @@ using Server.Gumps; using Server.Mobiles; +using Server.Network; namespace Server.Engines.BulkOrders { - public class BOBFilterGump : Gump - { - private PlayerMobile m_From; - private BulkOrderBook m_Book; + public class BOBFilterGump : Gump + { + private const int LabelColor = 0x7FFF; - private const int LabelColor = 0x7FFF; + private static int[,] m_MaterialFilters = + { + { 1044067, 1 }, // Blacksmithy + { 1062226, 3 }, // Iron + { 1018332, 4 }, // Dull Copper + { 1018333, 5 }, // Shadow Iron + { 1018334, 6 }, // Copper + { 1018335, 7 }, // Bronze - private static int[,] m_MaterialFilters = { - { 1044067, 1 }, // Blacksmithy - { 1062226, 3 }, // Iron - { 1018332, 4 }, // Dull Copper - { 1018333, 5 }, // Shadow Iron - { 1018334, 6 }, // Copper - { 1018335, 7 }, // Bronze + { 0, 0 }, // --Blank-- + { 1018336, 8 }, // Golden + { 1018337, 9 }, // Agapite + { 1018338, 10 }, // Verite + { 1018339, 11 }, // Valorite + { 0, 0 }, // --Blank-- - { 0, 0 }, // --Blank-- - { 1018336, 8 }, // Golden - { 1018337, 9 }, // Agapite - { 1018338, 10 }, // Verite - { 1018339, 11 }, // Valorite - { 0, 0 }, // --Blank-- + { 1044094, 2 }, // Tailoring + { 1044286, 12 }, // Cloth + { 1062235, 13 }, // Leather + { 1062236, 14 }, // Spined + { 1062237, 15 }, // Horned + { 1062238, 16 } // Barbed + }; - { 1044094, 2 }, // Tailoring - { 1044286, 12 }, // Cloth - { 1062235, 13 }, // Leather - { 1062236, 14 }, // Spined - { 1062237, 15 }, // Horned - { 1062238, 16 } // Barbed - }; + private static int[,] m_TypeFilters = + { + { 1062229, 0 }, // All + { 1062224, 1 }, // Small + { 1062225, 2 } // Large + }; - private static int[,] m_TypeFilters = { - { 1062229, 0 }, // All - { 1062224, 1 }, // Small - { 1062225, 2 } // Large - }; + private static int[,] m_QualityFilters = + { + { 1062229, 0 }, // All + { 1011542, 1 }, // Normal + { 1060636, 2 } // Exceptional + }; - private static int[,] m_QualityFilters = { - { 1062229, 0 }, // All - { 1011542, 1 }, // Normal - { 1060636, 2 } // Exceptional - }; + private static int[,] m_AmountFilters = + { + { 1062229, 0 }, // All + { 1049706, 1 }, // 10 + { 1016007, 2 }, // 15 + { 1062239, 3 } // 20 + }; - private static int[,] m_AmountFilters = { - { 1062229, 0 }, // All - { 1049706, 1 }, // 10 - { 1016007, 2 }, // 15 - { 1062239, 3 } // 20 - }; + private static int[][,] m_Filters = + { + m_TypeFilters, + m_QualityFilters, + m_MaterialFilters, + m_AmountFilters + }; - private static int[][,] m_Filters = { - m_TypeFilters, - m_QualityFilters, - m_MaterialFilters, - m_AmountFilters - }; + private static int[] m_XOffsets_Type = { 0, 75, 170 }; + private static int[] m_XOffsets_Quality = { 0, 75, 170 }; + private static int[] m_XOffsets_Amount = { 0, 75, 180, 275 }; + private static int[] m_XOffsets_Material = { 0, 105, 210, 305, 390, 485 }; - private static int[] m_XOffsets_Type = { 0, 75, 170 }; - private static int[] m_XOffsets_Quality = { 0, 75, 170 }; - private static int[] m_XOffsets_Amount = { 0, 75, 180, 275 }; - private static int[] m_XOffsets_Material = { 0, 105, 210, 305, 390, 485 }; + private static int[] m_XWidths_Small = { 50, 50, 70, 50 }; + private static int[] m_XWidths_Large = { 80, 50, 50, 50, 50, 50 }; + private BulkOrderBook m_Book; + private PlayerMobile m_From; - private static int[] m_XWidths_Small = { 50, 50, 70, 50 }; - private static int[] m_XWidths_Large = { 80, 50, 50, 50, 50, 50 }; + public BOBFilterGump(PlayerMobile from, BulkOrderBook book) : base(12, 24) + { + from.CloseGump(typeof(BOBGump)); + from.CloseGump(typeof(BOBFilterGump)); - private void AddFilterList( int x, int y, int[] xOffsets, int yOffset, int[,] filters, int[] xWidths, int filterValue, int filterIndex ) - { - for ( int i = 0; i < filters.GetLength( 0 ); ++i ) - { - int number = filters[i, 0]; + m_From = from; + m_Book = book; - if ( number == 0 ) - continue; + BOBFilter f = from.UseOwnFilter ? from.BOBFilter : book.Filter; - bool isSelected = ( filters[i, 1] == filterValue ); + AddPage(0); - if ( !isSelected && (i % xOffsets.Length) == 0 ) - isSelected = ( filterValue == 0 ); + AddBackground(10, 10, 600, 439, 5054); - AddHtmlLocalized( x + 35 + xOffsets[i % xOffsets.Length], y + ((i / xOffsets.Length) * yOffset), xWidths[i % xOffsets.Length], 32, number, isSelected ? 16927 : LabelColor, false, false ); - AddButton( x + xOffsets[i % xOffsets.Length], y + ((i / xOffsets.Length) * yOffset), 4005, 4007, 4 + filterIndex + (i * 4), GumpButtonType.Reply, 0 ); - } - } + AddImageTiled(18, 20, 583, 420, 2624); + AddAlphaRegion(18, 20, 583, 420); - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - BOBFilter f = ( m_From.UseOwnFilter ? m_From.BOBFilter : m_Book.Filter ); + AddImage(5, 5, 10460); + AddImage(585, 5, 10460); + AddImage(5, 424, 10460); + AddImage(585, 424, 10460); - int index = info.ButtonID; + AddHtmlLocalized(270, 32, 200, 32, 1062223, LabelColor, false, false); // Filter Preference - switch ( index ) - { - case 0: // Apply - { - m_From.SendGump( new BOBGump( m_From, m_Book ) ); + AddHtmlLocalized(26, 64, 120, 32, 1062228, LabelColor, false, false); // Bulk Order Type + AddFilterList(25, 96, m_XOffsets_Type, 40, m_TypeFilters, m_XWidths_Small, f.Type, 0); - break; - } - case 1: // Set Book Filter - { - m_From.UseOwnFilter = false; - m_From.SendGump( new BOBFilterGump( m_From, m_Book ) ); + AddHtmlLocalized(320, 64, 50, 32, 1062215, LabelColor, false, false); // Quality + AddFilterList(320, 96, m_XOffsets_Quality, 40, m_QualityFilters, m_XWidths_Small, f.Quality, 1); - break; - } - case 2: // Set Your Filter - { - m_From.UseOwnFilter = true; - m_From.SendGump( new BOBFilterGump( m_From, m_Book ) ); + AddHtmlLocalized(26, 160, 120, 32, 1062232, LabelColor, false, false); // Material Type + AddFilterList(25, 192, m_XOffsets_Material, 40, m_MaterialFilters, m_XWidths_Large, f.Material, 2); - break; - } - case 3: // Clear Filter - { - f.Clear(); - m_From.SendGump( new BOBFilterGump( m_From, m_Book ) ); + AddHtmlLocalized(26, 320, 120, 32, 1062217, LabelColor, false, false); // Amount + AddFilterList(25, 352, m_XOffsets_Amount, 40, m_AmountFilters, m_XWidths_Small, f.Quantity, 3); - break; - } - default: - { - index -= 4; + AddHtmlLocalized(75, 416, 120, 32, 1062477, from.UseOwnFilter ? LabelColor : 16927, false, + false); // Set Book Filter + AddButton(40, 416, 4005, 4007, 1, GumpButtonType.Reply, 0); - int type = index % 4; - index /= 4; + AddHtmlLocalized(235, 416, 120, 32, 1062478, from.UseOwnFilter ? 16927 : LabelColor, false, + false); // Set Your Filter + AddButton(200, 416, 4005, 4007, 2, GumpButtonType.Reply, 0); - if ( type >= 0 && type < m_Filters.Length ) - { - int[,] filters = m_Filters[type]; + AddHtmlLocalized(405, 416, 120, 32, 1062231, LabelColor, false, false); // Clear Filter + AddButton(370, 416, 4005, 4007, 3, GumpButtonType.Reply, 0); - if ( index >= 0 && index < filters.GetLength( 0 ) ) - { - if ( filters[index, 0] == 0 ) - break; + AddHtmlLocalized(540, 416, 50, 32, 1011046, LabelColor, false, false); // APPLY + AddButton(505, 416, 4017, 4018, 0, GumpButtonType.Reply, 0); + } - switch ( type ) - { - case 0: f.Type = filters[index, 1]; break; - case 1: f.Quality = filters[index, 1]; break; - case 2: f.Material = filters[index, 1]; break; - case 3: f.Quantity = filters[index, 1]; break; - } + private void AddFilterList(int x, int y, int[] xOffsets, int yOffset, int[,] filters, int[] xWidths, int filterValue, + int filterIndex) + { + for (int i = 0; i < filters.GetLength(0); ++i) + { + int number = filters[i, 0]; - m_From.SendGump( new BOBFilterGump( m_From, m_Book ) ); - } - } + if (number == 0) + continue; - break; - } - } - } + bool isSelected = filters[i, 1] == filterValue; - public BOBFilterGump( PlayerMobile from, BulkOrderBook book ) : base( 12, 24 ) - { - from.CloseGump( typeof( BOBGump ) ); - from.CloseGump( typeof( BOBFilterGump ) ); + if (!isSelected && i % xOffsets.Length == 0) + isSelected = filterValue == 0; - m_From = from; - m_Book = book; + AddHtmlLocalized(x + 35 + xOffsets[i % xOffsets.Length], y + i / xOffsets.Length * yOffset, + xWidths[i % xOffsets.Length], 32, number, isSelected ? 16927 : LabelColor, false, false); + AddButton(x + xOffsets[i % xOffsets.Length], y + i / xOffsets.Length * yOffset, 4005, 4007, + 4 + filterIndex + i * 4, GumpButtonType.Reply, 0); + } + } - BOBFilter f = ( from.UseOwnFilter ? from.BOBFilter : book.Filter ); + public override void OnResponse(NetState sender, RelayInfo info) + { + BOBFilter f = m_From.UseOwnFilter ? m_From.BOBFilter : m_Book.Filter; - AddPage( 0 ); + int index = info.ButtonID; - AddBackground( 10, 10, 600, 439, 5054 ); + switch (index) + { + case 0: // Apply + { + m_From.SendGump(new BOBGump(m_From, m_Book)); - AddImageTiled( 18, 20, 583, 420, 2624 ); - AddAlphaRegion( 18, 20, 583, 420 ); + break; + } + case 1: // Set Book Filter + { + m_From.UseOwnFilter = false; + m_From.SendGump(new BOBFilterGump(m_From, m_Book)); - AddImage( 5, 5, 10460 ); - AddImage( 585, 5, 10460 ); - AddImage( 5, 424, 10460 ); - AddImage( 585, 424, 10460 ); + break; + } + case 2: // Set Your Filter + { + m_From.UseOwnFilter = true; + m_From.SendGump(new BOBFilterGump(m_From, m_Book)); - AddHtmlLocalized( 270, 32, 200, 32, 1062223, LabelColor, false, false ); // Filter Preference + break; + } + case 3: // Clear Filter + { + f.Clear(); + m_From.SendGump(new BOBFilterGump(m_From, m_Book)); - AddHtmlLocalized( 26, 64, 120, 32, 1062228, LabelColor, false, false ); // Bulk Order Type - AddFilterList( 25, 96, m_XOffsets_Type, 40, m_TypeFilters, m_XWidths_Small, f.Type, 0 ); + break; + } + default: + { + index -= 4; - AddHtmlLocalized( 320, 64, 50, 32, 1062215, LabelColor, false, false ); // Quality - AddFilterList( 320, 96, m_XOffsets_Quality, 40, m_QualityFilters, m_XWidths_Small, f.Quality, 1 ); + int type = index % 4; + index /= 4; - AddHtmlLocalized( 26, 160, 120, 32, 1062232, LabelColor, false, false ); // Material Type - AddFilterList( 25, 192, m_XOffsets_Material, 40, m_MaterialFilters, m_XWidths_Large, f.Material, 2 ); + if (type >= 0 && type < m_Filters.Length) + { + int[,] filters = m_Filters[type]; - AddHtmlLocalized( 26, 320, 120, 32, 1062217, LabelColor, false, false ); // Amount - AddFilterList( 25, 352, m_XOffsets_Amount, 40, m_AmountFilters, m_XWidths_Small, f.Quantity, 3 ); + if (index >= 0 && index < filters.GetLength(0)) + { + if (filters[index, 0] == 0) + break; - AddHtmlLocalized( 75, 416, 120, 32, 1062477, ( from.UseOwnFilter ? LabelColor : 16927 ), false, false ); // Set Book Filter - AddButton( 40, 416, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + switch (type) + { + case 0: + f.Type = filters[index, 1]; + break; + case 1: + f.Quality = filters[index, 1]; + break; + case 2: + f.Material = filters[index, 1]; + break; + case 3: + f.Quantity = filters[index, 1]; + break; + } - AddHtmlLocalized( 235, 416, 120, 32, 1062478, ( from.UseOwnFilter ? 16927 : LabelColor ), false, false ); // Set Your Filter - AddButton( 200, 416, 4005, 4007, 2, GumpButtonType.Reply, 0 ); + m_From.SendGump(new BOBFilterGump(m_From, m_Book)); + } + } - AddHtmlLocalized( 405, 416, 120, 32, 1062231, LabelColor, false, false ); // Clear Filter - AddButton( 370, 416, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - - AddHtmlLocalized( 540, 416, 50, 32, 1011046, LabelColor, false, false ); // APPLY - AddButton( 505, 416, 4017, 4018, 0, GumpButtonType.Reply, 0 ); - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BOBGump.cs b/Scripts/Engines/BulkOrders/Books/BOBGump.cs index 33563a0bc..0ac06410f 100644 --- a/Scripts/Engines/BulkOrders/Books/BOBGump.cs +++ b/Scripts/Engines/BulkOrders/Books/BOBGump.cs @@ -3,698 +3,717 @@ using System.Collections; using Server.Gumps; using Server.Items; using Server.Mobiles; +using Server.Network; using Server.Prompts; namespace Server.Engines.BulkOrders { - public class BOBGump : Gump - { - private PlayerMobile m_From; - private BulkOrderBook m_Book; - private ArrayList m_List; - - private int m_Page; - - private const int LabelColor = 0x7FFF; - - public Item Reconstruct( object obj ) - { - Item item = null; - - if ( obj is BOBLargeEntry entry ) - item = entry.Reconstruct(); - else - item = ((BOBSmallEntry)obj).Reconstruct(); - - return item; - } - - public bool CheckFilter( object obj ) - { - if ( obj is BOBLargeEntry entry ) - { - return CheckFilter( entry.Material, entry.AmountMax, true, entry.RequireExceptional, entry.DeedType, ( entry.Entries.Length > 0 ? entry.Entries[0].ItemType : null ) ); - } - if ( obj is BOBSmallEntry smallEntry ) - { - return CheckFilter( smallEntry.Material, smallEntry.AmountMax, false, smallEntry.RequireExceptional, smallEntry.DeedType, smallEntry.ItemType ); - } - - return false; - } - - public bool CheckFilter( BulkMaterialType mat, int amountMax, bool isLarge, bool reqExc, BODType deedType, Type itemType ) - { - BOBFilter f = ( m_From.UseOwnFilter ? m_From.BOBFilter : m_Book.Filter ); - - if ( f.IsDefault ) - return true; - - if ( f.Quality == 1 && reqExc ) - return false; - if ( f.Quality == 2 && !reqExc ) - return false; - - if ( f.Quantity == 1 && amountMax != 10 ) - return false; - if ( f.Quantity == 2 && amountMax != 15 ) - return false; - if ( f.Quantity == 3 && amountMax != 20 ) - return false; - - if ( f.Type == 1 && isLarge ) - return false; - if ( f.Type == 2 && !isLarge ) - return false; - - switch ( f.Material ) - { - default: - return true; - case 1: return ( deedType == BODType.Smith ); - case 2: return ( deedType == BODType.Tailor ); - - case 3: return ( mat == BulkMaterialType.None && BGTClassifier.Classify( deedType, itemType ) == BulkGenericType.Iron ); - case 4: return ( mat == BulkMaterialType.DullCopper ); - case 5: return ( mat == BulkMaterialType.ShadowIron ); - case 6: return ( mat == BulkMaterialType.Copper ); - case 7: return ( mat == BulkMaterialType.Bronze ); - case 8: return ( mat == BulkMaterialType.Gold ); - case 9: return ( mat == BulkMaterialType.Agapite ); - case 10: return ( mat == BulkMaterialType.Verite ); - case 11: return ( mat == BulkMaterialType.Valorite ); - - case 12: return ( mat == BulkMaterialType.None && BGTClassifier.Classify( deedType, itemType ) == BulkGenericType.Cloth ); - case 13: return ( mat == BulkMaterialType.None && BGTClassifier.Classify( deedType, itemType ) == BulkGenericType.Leather ); - case 14: return ( mat == BulkMaterialType.Spined ); - case 15: return ( mat == BulkMaterialType.Horned ); - case 16: return ( mat == BulkMaterialType.Barbed ); - } - } - - public int GetIndexForPage( int page ) - { - int index = 0; - - while ( page-- > 0 ) - index += GetCountForIndex( index ); - - return index; - } - - public int GetCountForIndex( int index ) - { - int slots = 0; - int count = 0; - - ArrayList list = m_List; - - for ( int i = index; i >= 0 && i < list.Count; ++i ) - { - object obj = list[i]; - - if ( CheckFilter( obj ) ) - { - int add; - - if ( obj is BOBLargeEntry entry ) - add = entry.Entries.Length; - else - add = 1; - - if ( (slots + add) > 10 ) - break; - - slots += add; - } - - ++count; - } - - return count; - } - - public int GetPageForIndex(int index, int sizeDropped) - { - if (index <= 0) - return 0; - - int count = 0; - int add = 0; - int page = 0; - ArrayList list = m_List; - int i; - object obj; - - for (i=0; (i < index) && (i < list.Count); i++) - { - obj = list[i]; - if (CheckFilter(obj)) - { - if (obj is BOBLargeEntry entry) - add = entry.Entries.Length; - else - add = 1; - count += add; - if (count > 10) - { - page++; - count = add; - } - } - } - /* now we are on the page of the bod preceeding the dropped one. - * next step: checking whether we have to remain where we are. - * The counter i needs to be incremented as the bod to this very moment - * has not yet been removed from m_List */ - i++; - - /* if, for instance, a big bod of size 6 has been removed, smaller bods - * might fall back into this page. Depending on their sizes, the page eeds - * to be adjusted accordingly. This is done now. - */ - if (count + sizeDropped > 10) - { - while ((i < list.Count) && (count <= 10)) - { - obj = list[i]; - if (CheckFilter(obj)) - { - if (obj is BOBLargeEntry entry) - count += entry.Entries.Length; - else - count += 1; - } - i++; - } - if (count > 10) - page++; - } - return page; - } - - - public object GetMaterialName( BulkMaterialType mat, BODType type, Type itemType ) - { - switch ( type ) - { - case BODType.Smith: - { - switch ( mat ) - { - case BulkMaterialType.None: return 1062226; - case BulkMaterialType.DullCopper: return 1018332; - case BulkMaterialType.ShadowIron: return 1018333; - case BulkMaterialType.Copper: return 1018334; - case BulkMaterialType.Bronze: return 1018335; - case BulkMaterialType.Gold: return 1018336; - case BulkMaterialType.Agapite: return 1018337; - case BulkMaterialType.Verite: return 1018338; - case BulkMaterialType.Valorite: return 1018339; - } - - break; - } - case BODType.Tailor: - { - switch ( mat ) - { - case BulkMaterialType.None: - { - if ( itemType.IsSubclassOf( typeof( BaseArmor ) ) || itemType.IsSubclassOf( typeof( BaseShoes ) ) ) - return 1062235; - - return 1044286; - } - case BulkMaterialType.Spined: return 1062236; - case BulkMaterialType.Horned: return 1062237; - case BulkMaterialType.Barbed: return 1062238; - } - - break; - } - } - - return "Invalid"; - } - - public BOBGump( PlayerMobile from, BulkOrderBook book ) : this( from, book, 0, null ) - { - } - - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - int index = info.ButtonID; - - switch ( index ) - { - case 0: // EXIT - { - break; - } - case 1: // Set Filter - { - m_From.SendGump( new BOBFilterGump( m_From, m_Book ) ); - - break; - } - case 2: // Previous page - { - if ( m_Page > 0 ) - m_From.SendGump( new BOBGump( m_From, m_Book, m_Page - 1, m_List ) ); - - return; - } - case 3: // Next page - { - if ( GetIndexForPage( m_Page + 1 ) < m_List.Count ) - m_From.SendGump( new BOBGump( m_From, m_Book, m_Page + 1, m_List ) ); - - break; - } - case 4: // Price all - { - if ( m_Book.IsChildOf( m_From.Backpack ) ) - { - m_From.Prompt = new SetPricePrompt( m_Book, null, m_Page, m_List ); - m_From.SendMessage( "Type in a price for all deeds in the book:" ); - } - - break; - } - default: - { - bool canDrop = m_Book.IsChildOf( m_From.Backpack ); - bool canPrice = canDrop || (m_Book.RootParent is PlayerVendor); - - index -= 5; - - int type = index % 2; - index /= 2; - - if ( index < 0 || index >= m_List.Count ) - break; - - object obj = m_List[index]; - - if ( !m_Book.Entries.Contains( obj ) ) - { - m_From.SendLocalizedMessage( 1062382 ); // The deed selected is not available. - break; - } - - if ( type == 0 ) // Drop - { - if ( m_Book.IsChildOf( m_From.Backpack ) ) - { - Item item = Reconstruct( obj ); - - if ( item != null ) - { - Container pack = m_From.Backpack; - if ((pack == null) || ((pack != null) && (!pack.CheckHold(m_From, item, true, true, 0, item.PileWeight + item.TotalWeight)))) - { - m_From.SendLocalizedMessage(503204); // You do not have room in your backpack for this - m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); - } - else - { - if (m_Book.IsChildOf(m_From.Backpack)) - { - int sizeOfDroppedBod; - if (obj is BOBLargeEntry entry) - sizeOfDroppedBod = entry.Entries.Length; - else - sizeOfDroppedBod = 1; - - m_From.AddToBackpack(item); - m_From.SendLocalizedMessage(1045152); // The bulk order deed has been placed in your backpack. - m_Book.Entries.Remove(obj); - m_Book.InvalidateProperties(); - - if ( m_Book.Entries.Count / 5 < m_Book.ItemCount ) - { - m_Book.ItemCount--; - m_Book.InvalidateItems(); - } - - if (m_Book.Entries.Count > 0) - { - m_Page = GetPageForIndex(index, sizeOfDroppedBod); - m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); - } - else - m_From.SendLocalizedMessage(1062381); // The book is empty. - } - } - } - else - { - m_From.SendMessage( "Internal error. The bulk order deed could not be reconstructed." ); - } - } - } - else // Set Price | Buy - { - if ( m_Book.IsChildOf( m_From.Backpack ) ) - { - m_From.Prompt = new SetPricePrompt( m_Book, obj, m_Page, m_List ); - m_From.SendLocalizedMessage( 1062383 ); // Type in a price for the deed: - } - else if ( m_Book.RootParent is PlayerVendor pv ) - { - VendorItem vi = pv.GetVendorItem( m_Book ); - - if (vi != null && !vi.IsForSale) - { - int sizeOfDroppedBod; - int price = 0; - if (obj is BOBLargeEntry entry) - { - price = entry.Price; - sizeOfDroppedBod = entry.Entries.Length; - } - else - { - price = ((BOBSmallEntry)obj).Price; - sizeOfDroppedBod = 1; - } - if (price == 0) - m_From.SendLocalizedMessage(1062382); // The deed selected is not available. - else - { - if (m_Book.Entries.Count > 0) - { - m_Page = GetPageForIndex(index, sizeOfDroppedBod); - m_From.SendGump(new BODBuyGump(m_From, m_Book, obj, m_Page, price)); - } - else - m_From.SendLocalizedMessage(1062381); // The book is emptz - } - } - } - } - break; - } - } - } - - private class SetPricePrompt : Prompt - { - private BulkOrderBook m_Book; - private object m_Object; - private int m_Page; - private ArrayList m_List; - - public SetPricePrompt( BulkOrderBook book, object obj, int page, ArrayList list ) - { - m_Book = book; - m_Object = obj; - m_Page = page; - m_List = list; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Object != null && !m_Book.Entries.Contains( m_Object ) ) - { - from.SendLocalizedMessage( 1062382 ); // The deed selected is not available. - return; - } - - int price = Utility.ToInt32( text ); - - if ( price < 0 || price > 250000000 ) - { - from.SendLocalizedMessage( 1062390 ); // The price you requested is outrageous! - } - else if ( m_Object == null ) - { - for ( int i = 0; i < m_List.Count; ++i ) - { - object obj = m_List[i]; - - if ( !m_Book.Entries.Contains( obj ) ) - continue; - - if ( obj is BOBLargeEntry entry ) - entry.Price = price; - else - ((BOBSmallEntry)obj).Price = price; - } - - from.SendMessage( "Deed prices set." ); - - if ( from is PlayerMobile mobile ) - mobile.SendGump( new BOBGump( mobile, m_Book, m_Page, m_List ) ); - } - else if ( m_Object is BOBLargeEntry entry ) - { - entry.Price = price; - - from.SendLocalizedMessage( 1062384 ); // Deed price set. - - if ( from is PlayerMobile mobile ) - mobile.SendGump( new BOBGump( mobile, m_Book, m_Page, m_List ) ); - } - else - { - ((BOBSmallEntry)m_Object).Price = price; - - from.SendLocalizedMessage( 1062384 ); // Deed price set. - - if ( from is PlayerMobile mobile ) - mobile.SendGump( new BOBGump( mobile, m_Book, m_Page, m_List ) ); - } - } - } - - public BOBGump( PlayerMobile from, BulkOrderBook book, int page, ArrayList list ) : base( 12, 24 ) - { - from.CloseGump( typeof( BOBGump ) ); - from.CloseGump( typeof( BOBFilterGump ) ); - - m_From = from; - m_Book = book; - m_Page = page; - - if ( list == null ) - { - list = new ArrayList( book.Entries.Count ); - - for ( int i = 0; i < book.Entries.Count; ++i ) - { - object obj = book.Entries[i]; - - if ( CheckFilter( obj ) ) - list.Add( obj ); - } - } - - m_List = list; - - int index = GetIndexForPage( page ); - int count = GetCountForIndex( index ); - - int tableIndex = 0; - - PlayerVendor pv = book.RootParent as PlayerVendor; - - bool canDrop = book.IsChildOf( from.Backpack ); - bool canBuy = ( pv != null ); - bool canPrice = ( canDrop || canBuy ); - - if ( canBuy ) - { - VendorItem vi = pv.GetVendorItem( book ); - - canBuy = ( vi != null && !vi.IsForSale ); - } - - int width = 600; - - if ( !canPrice ) - width = 516; - - X = (624 - width) / 2; - - AddPage( 0 ); - - AddBackground( 10, 10, width, 439, 5054 ); - AddImageTiled( 18, 20, width - 17, 420, 2624 ); - - if ( canPrice ) - { - AddImageTiled( 573, 64, 24, 352, 200 ); - AddImageTiled( 493, 64, 78, 352, 1416 ); - } + public class BOBGump : Gump + { + private const int LabelColor = 0x7FFF; + private BulkOrderBook m_Book; + private PlayerMobile m_From; + private ArrayList m_List; - if ( canDrop ) - AddImageTiled( 24, 64, 32, 352, 1416 ); + private int m_Page; - AddImageTiled( 58, 64, 36, 352, 200 ); - AddImageTiled( 96, 64, 133, 352, 1416 ); - AddImageTiled( 231, 64, 80, 352, 200 ); - AddImageTiled( 313, 64, 100, 352, 1416 ); - AddImageTiled( 415, 64, 76, 352, 200 ); + public BOBGump(PlayerMobile from, BulkOrderBook book) : this(from, book, 0, null) + { + } - for ( int i = index; i < (index + count) && i >= 0 && i < list.Count; ++i ) - { - object obj = list[i]; + public BOBGump(PlayerMobile from, BulkOrderBook book, int page, ArrayList list) : base(12, 24) + { + from.CloseGump(typeof(BOBGump)); + from.CloseGump(typeof(BOBFilterGump)); - if ( !CheckFilter( obj ) ) - continue; + m_From = from; + m_Book = book; + m_Page = page; - AddImageTiled( 24, 94 + (tableIndex * 32), canPrice ? 573 : 489, 2, 2624 ); + if (list == null) + { + list = new ArrayList(book.Entries.Count); - if ( obj is BOBLargeEntry entry ) - tableIndex += entry.Entries.Length; - else - ++tableIndex; - } + for (int i = 0; i < book.Entries.Count; ++i) + { + object obj = book.Entries[i]; - AddAlphaRegion( 18, 20, width - 17, 420 ); - AddImage( 5, 5, 10460 ); - AddImage( width - 15, 5, 10460 ); - AddImage( 5, 424, 10460 ); - AddImage( width - 15, 424, 10460 ); + if (CheckFilter(obj)) + list.Add(obj); + } + } - AddHtmlLocalized( canPrice ? 266 : 224, 32, 200, 32, 1062220, LabelColor, false, false ); // Bulk Order Book - AddHtmlLocalized( 63, 64, 200, 32, 1062213, LabelColor, false, false ); // Type - AddHtmlLocalized( 147, 64, 200, 32, 1062214, LabelColor, false, false ); // Item - AddHtmlLocalized( 246, 64, 200, 32, 1062215, LabelColor, false, false ); // Quality - AddHtmlLocalized( 336, 64, 200, 32, 1062216, LabelColor, false, false ); // Material - AddHtmlLocalized( 429, 64, 200, 32, 1062217, LabelColor, false, false ); // Amount + m_List = list; - AddButton( 35, 32, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 70, 32, 200, 32, 1062476, LabelColor, false, false ); // Set Filter + int index = GetIndexForPage(page); + int count = GetCountForIndex(index); - BOBFilter f = ( from.UseOwnFilter ? from.BOBFilter : book.Filter ); + int tableIndex = 0; - if ( f.IsDefault ) - AddHtmlLocalized( canPrice ? 470 : 386, 32, 120, 32, 1062475, 16927, false, false ); // Using No Filter - else if ( from.UseOwnFilter ) - AddHtmlLocalized( canPrice ? 470 : 386, 32, 120, 32, 1062451, 16927, false, false ); // Using Your Filter - else - AddHtmlLocalized( canPrice ? 470 : 386, 32, 120, 32, 1062230, 16927, false, false ); // Using Book Filter + PlayerVendor pv = book.RootParent as PlayerVendor; - AddButton( 375, 416, 4017, 4018, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 410, 416, 120, 20, 1011441, LabelColor, false, false ); // EXIT + bool canDrop = book.IsChildOf(from.Backpack); + bool canBuy = pv != null; + bool canPrice = canDrop || canBuy; - if ( canDrop ) - AddHtmlLocalized( 26, 64, 50, 32, 1062212, LabelColor, false, false ); // Drop + if (canBuy) + { + VendorItem vi = pv.GetVendorItem(book); - if ( canPrice ) - { - AddHtmlLocalized( 516, 64, 200, 32, 1062218, LabelColor, false, false ); // Price + canBuy = vi != null && !vi.IsForSale; + } - if ( canBuy ) - { - AddHtmlLocalized( 576, 64, 200, 32, 1062219, LabelColor, false, false ); // Buy - } - else - { - AddHtmlLocalized( 576, 64, 200, 32, 1062227, LabelColor, false, false ); // Set + int width = 600; - AddButton( 450, 416, 4005, 4007, 4, GumpButtonType.Reply, 0 ); - AddHtml( 485, 416, 120, 20, "Price all", false, false ); - } - } + if (!canPrice) + width = 516; - tableIndex = 0; + X = (624 - width) / 2; - if ( page > 0 ) - { - AddButton( 75, 416, 4014, 4016, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 110, 416, 150, 20, 1011067, LabelColor, false, false ); // Previous page - } + AddPage(0); - if ( GetIndexForPage( page + 1 ) < list.Count ) - { - AddButton( 225, 416, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 260, 416, 150, 20, 1011066, LabelColor, false, false ); // Next page - } - - for ( int i = index; i < (index + count) && i >= 0 && i < list.Count; ++i ) - { - object obj = list[i]; - - if ( !CheckFilter( obj ) ) - continue; - - if ( obj is BOBLargeEntry entry ) - { - int y = 96 + (tableIndex * 32); - - if ( canDrop ) - AddButton( 35, y + 2, 5602, 5606, 5 + (i * 2), GumpButtonType.Reply, 0 ); - - if ( canDrop || (canBuy && entry.Price > 0) ) - { - AddButton( 579, y + 2, 2117, 2118, 6 + (i * 2), GumpButtonType.Reply, 0 ); - AddLabel( 495, y, 1152, entry.Price.ToString() ); - } - - AddHtmlLocalized( 61, y, 50, 32, 1062225, LabelColor, false, false ); // Large - - for ( int j = 0; j < entry.Entries.Length; ++j ) - { - BOBLargeSubEntry sub = entry.Entries[j]; - - AddHtmlLocalized( 103, y, 130, 32, sub.Number, LabelColor, false, false ); - - if ( entry.RequireExceptional ) - AddHtmlLocalized( 235, y, 80, 20, 1060636, LabelColor, false, false ); // exceptional - else - AddHtmlLocalized( 235, y, 80, 20, 1011542, LabelColor, false, false ); // normal - - object name = GetMaterialName( entry.Material, entry.DeedType, sub.ItemType ); - - if ( name is int intName ) - AddHtmlLocalized( 316, y, 100, 20, intName, LabelColor, false, false ); - else - AddLabel( 316, y, 1152, name.ToString() ); - - AddLabel( 421, y, 1152, $"{sub.AmountCur} / {entry.AmountMax}"); - - ++tableIndex; - y += 32; - } - } - else - { - BOBSmallEntry smallEntry = (BOBSmallEntry)obj; + AddBackground(10, 10, width, 439, 5054); + AddImageTiled(18, 20, width - 17, 420, 2624); - int y = 96 + (tableIndex++ * 32); - - if ( canDrop ) - AddButton( 35, y + 2, 5602, 5606, 5 + (i * 2), GumpButtonType.Reply, 0 ); - - if ( canDrop || (canBuy && smallEntry.Price > 0) ) - { - AddButton( 579, y + 2, 2117, 2118, 6 + (i * 2), GumpButtonType.Reply, 0 ); - AddLabel( 495, y, 1152, smallEntry.Price.ToString() ); - } + if (canPrice) + { + AddImageTiled(573, 64, 24, 352, 200); + AddImageTiled(493, 64, 78, 352, 1416); + } - AddHtmlLocalized( 61, y, 50, 32, 1062224, LabelColor, false, false ); // Small + if (canDrop) + AddImageTiled(24, 64, 32, 352, 1416); - AddHtmlLocalized( 103, y, 130, 32, smallEntry.Number, LabelColor, false, false ); + AddImageTiled(58, 64, 36, 352, 200); + AddImageTiled(96, 64, 133, 352, 1416); + AddImageTiled(231, 64, 80, 352, 200); + AddImageTiled(313, 64, 100, 352, 1416); + AddImageTiled(415, 64, 76, 352, 200); - if ( smallEntry.RequireExceptional ) - AddHtmlLocalized( 235, y, 80, 20, 1060636, LabelColor, false, false ); // exceptional - else - AddHtmlLocalized( 235, y, 80, 20, 1011542, LabelColor, false, false ); // normal - - object name = GetMaterialName( smallEntry.Material, smallEntry.DeedType, smallEntry.ItemType ); - - if ( name is int intName ) - AddHtmlLocalized( 316, y, 100, 20, intName, LabelColor, false, false ); - else - AddLabel( 316, y, 1152, name.ToString() ); + for (int i = index; i < index + count && i >= 0 && i < list.Count; ++i) + { + object obj = list[i]; - AddLabel( 421, y, 1152, $"{smallEntry.AmountCur} / {smallEntry.AmountMax}"); - } - } - } - } -} + if (!CheckFilter(obj)) + continue; + + AddImageTiled(24, 94 + tableIndex * 32, canPrice ? 573 : 489, 2, 2624); + + if (obj is BOBLargeEntry entry) + tableIndex += entry.Entries.Length; + else + ++tableIndex; + } + + AddAlphaRegion(18, 20, width - 17, 420); + AddImage(5, 5, 10460); + AddImage(width - 15, 5, 10460); + AddImage(5, 424, 10460); + AddImage(width - 15, 424, 10460); + + AddHtmlLocalized(canPrice ? 266 : 224, 32, 200, 32, 1062220, LabelColor, false, false); // Bulk Order Book + AddHtmlLocalized(63, 64, 200, 32, 1062213, LabelColor, false, false); // Type + AddHtmlLocalized(147, 64, 200, 32, 1062214, LabelColor, false, false); // Item + AddHtmlLocalized(246, 64, 200, 32, 1062215, LabelColor, false, false); // Quality + AddHtmlLocalized(336, 64, 200, 32, 1062216, LabelColor, false, false); // Material + AddHtmlLocalized(429, 64, 200, 32, 1062217, LabelColor, false, false); // Amount + + AddButton(35, 32, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(70, 32, 200, 32, 1062476, LabelColor, false, false); // Set Filter + + BOBFilter f = from.UseOwnFilter ? from.BOBFilter : book.Filter; + + if (f.IsDefault) + AddHtmlLocalized(canPrice ? 470 : 386, 32, 120, 32, 1062475, 16927, false, false); // Using No Filter + else if (from.UseOwnFilter) + AddHtmlLocalized(canPrice ? 470 : 386, 32, 120, 32, 1062451, 16927, false, false); // Using Your Filter + else + AddHtmlLocalized(canPrice ? 470 : 386, 32, 120, 32, 1062230, 16927, false, false); // Using Book Filter + + AddButton(375, 416, 4017, 4018, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(410, 416, 120, 20, 1011441, LabelColor, false, false); // EXIT + + if (canDrop) + AddHtmlLocalized(26, 64, 50, 32, 1062212, LabelColor, false, false); // Drop + + if (canPrice) + { + AddHtmlLocalized(516, 64, 200, 32, 1062218, LabelColor, false, false); // Price + + if (canBuy) + { + AddHtmlLocalized(576, 64, 200, 32, 1062219, LabelColor, false, false); // Buy + } + else + { + AddHtmlLocalized(576, 64, 200, 32, 1062227, LabelColor, false, false); // Set + + AddButton(450, 416, 4005, 4007, 4, GumpButtonType.Reply, 0); + AddHtml(485, 416, 120, 20, "Price all", false, false); + } + } + + tableIndex = 0; + + if (page > 0) + { + AddButton(75, 416, 4014, 4016, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(110, 416, 150, 20, 1011067, LabelColor, false, false); // Previous page + } + + if (GetIndexForPage(page + 1) < list.Count) + { + AddButton(225, 416, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(260, 416, 150, 20, 1011066, LabelColor, false, false); // Next page + } + + for (int i = index; i < index + count && i >= 0 && i < list.Count; ++i) + { + object obj = list[i]; + + if (!CheckFilter(obj)) + continue; + + if (obj is BOBLargeEntry entry) + { + int y = 96 + tableIndex * 32; + + if (canDrop) + AddButton(35, y + 2, 5602, 5606, 5 + i * 2, GumpButtonType.Reply, 0); + + if (canDrop || canBuy && entry.Price > 0) + { + AddButton(579, y + 2, 2117, 2118, 6 + i * 2, GumpButtonType.Reply, 0); + AddLabel(495, y, 1152, entry.Price.ToString()); + } + + AddHtmlLocalized(61, y, 50, 32, 1062225, LabelColor, false, false); // Large + + for (int j = 0; j < entry.Entries.Length; ++j) + { + BOBLargeSubEntry sub = entry.Entries[j]; + + AddHtmlLocalized(103, y, 130, 32, sub.Number, LabelColor, false, false); + + if (entry.RequireExceptional) + AddHtmlLocalized(235, y, 80, 20, 1060636, LabelColor, false, false); // exceptional + else + AddHtmlLocalized(235, y, 80, 20, 1011542, LabelColor, false, false); // normal + + object name = GetMaterialName(entry.Material, entry.DeedType, sub.ItemType); + + if (name is int intName) + AddHtmlLocalized(316, y, 100, 20, intName, LabelColor, false, false); + else + AddLabel(316, y, 1152, name.ToString()); + + AddLabel(421, y, 1152, $"{sub.AmountCur} / {entry.AmountMax}"); + + ++tableIndex; + y += 32; + } + } + else + { + BOBSmallEntry smallEntry = (BOBSmallEntry)obj; + + int y = 96 + tableIndex++ * 32; + + if (canDrop) + AddButton(35, y + 2, 5602, 5606, 5 + i * 2, GumpButtonType.Reply, 0); + + if (canDrop || canBuy && smallEntry.Price > 0) + { + AddButton(579, y + 2, 2117, 2118, 6 + i * 2, GumpButtonType.Reply, 0); + AddLabel(495, y, 1152, smallEntry.Price.ToString()); + } + + AddHtmlLocalized(61, y, 50, 32, 1062224, LabelColor, false, false); // Small + + AddHtmlLocalized(103, y, 130, 32, smallEntry.Number, LabelColor, false, false); + + if (smallEntry.RequireExceptional) + AddHtmlLocalized(235, y, 80, 20, 1060636, LabelColor, false, false); // exceptional + else + AddHtmlLocalized(235, y, 80, 20, 1011542, LabelColor, false, false); // normal + + object name = GetMaterialName(smallEntry.Material, smallEntry.DeedType, smallEntry.ItemType); + + if (name is int intName) + AddHtmlLocalized(316, y, 100, 20, intName, LabelColor, false, false); + else + AddLabel(316, y, 1152, name.ToString()); + + AddLabel(421, y, 1152, $"{smallEntry.AmountCur} / {smallEntry.AmountMax}"); + } + } + } + + public Item Reconstruct(object obj) + { + Item item = null; + + if (obj is BOBLargeEntry entry) + item = entry.Reconstruct(); + else + item = ((BOBSmallEntry)obj).Reconstruct(); + + return item; + } + + public bool CheckFilter(object obj) + { + if (obj is BOBLargeEntry entry) + return CheckFilter(entry.Material, entry.AmountMax, true, entry.RequireExceptional, entry.DeedType, + entry.Entries.Length > 0 ? entry.Entries[0].ItemType : null); + if (obj is BOBSmallEntry smallEntry) + return CheckFilter(smallEntry.Material, smallEntry.AmountMax, false, smallEntry.RequireExceptional, + smallEntry.DeedType, smallEntry.ItemType); + + return false; + } + + public bool CheckFilter(BulkMaterialType mat, int amountMax, bool isLarge, bool reqExc, BODType deedType, + Type itemType) + { + BOBFilter f = m_From.UseOwnFilter ? m_From.BOBFilter : m_Book.Filter; + + if (f.IsDefault) + return true; + + if (f.Quality == 1 && reqExc) + return false; + if (f.Quality == 2 && !reqExc) + return false; + + if (f.Quantity == 1 && amountMax != 10) + return false; + if (f.Quantity == 2 && amountMax != 15) + return false; + if (f.Quantity == 3 && amountMax != 20) + return false; + + if (f.Type == 1 && isLarge) + return false; + if (f.Type == 2 && !isLarge) + return false; + + switch (f.Material) + { + default: + return true; + case 1: return deedType == BODType.Smith; + case 2: return deedType == BODType.Tailor; + + case 3: + return mat == BulkMaterialType.None && + BGTClassifier.Classify(deedType, itemType) == BulkGenericType.Iron; + case 4: return mat == BulkMaterialType.DullCopper; + case 5: return mat == BulkMaterialType.ShadowIron; + case 6: return mat == BulkMaterialType.Copper; + case 7: return mat == BulkMaterialType.Bronze; + case 8: return mat == BulkMaterialType.Gold; + case 9: return mat == BulkMaterialType.Agapite; + case 10: return mat == BulkMaterialType.Verite; + case 11: return mat == BulkMaterialType.Valorite; + + case 12: + return mat == BulkMaterialType.None && + BGTClassifier.Classify(deedType, itemType) == BulkGenericType.Cloth; + case 13: + return mat == BulkMaterialType.None && + BGTClassifier.Classify(deedType, itemType) == BulkGenericType.Leather; + case 14: return mat == BulkMaterialType.Spined; + case 15: return mat == BulkMaterialType.Horned; + case 16: return mat == BulkMaterialType.Barbed; + } + } + + public int GetIndexForPage(int page) + { + int index = 0; + + while (page-- > 0) + index += GetCountForIndex(index); + + return index; + } + + public int GetCountForIndex(int index) + { + int slots = 0; + int count = 0; + + ArrayList list = m_List; + + for (int i = index; i >= 0 && i < list.Count; ++i) + { + object obj = list[i]; + + if (CheckFilter(obj)) + { + int add; + + if (obj is BOBLargeEntry entry) + add = entry.Entries.Length; + else + add = 1; + + if (slots + add > 10) + break; + + slots += add; + } + + ++count; + } + + return count; + } + + public int GetPageForIndex(int index, int sizeDropped) + { + if (index <= 0) + return 0; + + int count = 0; + int add = 0; + int page = 0; + ArrayList list = m_List; + int i; + object obj; + + for (i = 0; i < index && i < list.Count; i++) + { + obj = list[i]; + if (CheckFilter(obj)) + { + if (obj is BOBLargeEntry entry) + add = entry.Entries.Length; + else + add = 1; + count += add; + if (count > 10) + { + page++; + count = add; + } + } + } + + /* now we are on the page of the bod preceeding the dropped one. + * next step: checking whether we have to remain where we are. + * The counter i needs to be incremented as the bod to this very moment + * has not yet been removed from m_List */ + i++; + + /* if, for instance, a big bod of size 6 has been removed, smaller bods + * might fall back into this page. Depending on their sizes, the page eeds + * to be adjusted accordingly. This is done now. + */ + if (count + sizeDropped > 10) + { + while (i < list.Count && count <= 10) + { + obj = list[i]; + if (CheckFilter(obj)) + { + if (obj is BOBLargeEntry entry) + count += entry.Entries.Length; + else + count += 1; + } + + i++; + } + + if (count > 10) + page++; + } + + return page; + } + + + public object GetMaterialName(BulkMaterialType mat, BODType type, Type itemType) + { + switch (type) + { + case BODType.Smith: + { + switch (mat) + { + case BulkMaterialType.None: return 1062226; + case BulkMaterialType.DullCopper: return 1018332; + case BulkMaterialType.ShadowIron: return 1018333; + case BulkMaterialType.Copper: return 1018334; + case BulkMaterialType.Bronze: return 1018335; + case BulkMaterialType.Gold: return 1018336; + case BulkMaterialType.Agapite: return 1018337; + case BulkMaterialType.Verite: return 1018338; + case BulkMaterialType.Valorite: return 1018339; + } + + break; + } + case BODType.Tailor: + { + switch (mat) + { + case BulkMaterialType.None: + { + if (itemType.IsSubclassOf(typeof(BaseArmor)) || itemType.IsSubclassOf(typeof(BaseShoes))) + return 1062235; + + return 1044286; + } + case BulkMaterialType.Spined: return 1062236; + case BulkMaterialType.Horned: return 1062237; + case BulkMaterialType.Barbed: return 1062238; + } + + break; + } + } + + return "Invalid"; + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int index = info.ButtonID; + + switch (index) + { + case 0: // EXIT + { + break; + } + case 1: // Set Filter + { + m_From.SendGump(new BOBFilterGump(m_From, m_Book)); + + break; + } + case 2: // Previous page + { + if (m_Page > 0) + m_From.SendGump(new BOBGump(m_From, m_Book, m_Page - 1, m_List)); + + return; + } + case 3: // Next page + { + if (GetIndexForPage(m_Page + 1) < m_List.Count) + m_From.SendGump(new BOBGump(m_From, m_Book, m_Page + 1, m_List)); + + break; + } + case 4: // Price all + { + if (m_Book.IsChildOf(m_From.Backpack)) + { + m_From.Prompt = new SetPricePrompt(m_Book, null, m_Page, m_List); + m_From.SendMessage("Type in a price for all deeds in the book:"); + } + + break; + } + default: + { + bool canDrop = m_Book.IsChildOf(m_From.Backpack); + bool canPrice = canDrop || m_Book.RootParent is PlayerVendor; + + index -= 5; + + int type = index % 2; + index /= 2; + + if (index < 0 || index >= m_List.Count) + break; + + object obj = m_List[index]; + + if (!m_Book.Entries.Contains(obj)) + { + m_From.SendLocalizedMessage(1062382); // The deed selected is not available. + break; + } + + if (type == 0) // Drop + { + if (m_Book.IsChildOf(m_From.Backpack)) + { + Item item = Reconstruct(obj); + + if (item != null) + { + Container pack = m_From.Backpack; + if (pack == null || pack != null && !pack.CheckHold(m_From, item, true, true, 0, + item.PileWeight + item.TotalWeight)) + { + m_From.SendLocalizedMessage(503204); // You do not have room in your backpack for this + m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); + } + else + { + if (m_Book.IsChildOf(m_From.Backpack)) + { + int sizeOfDroppedBod; + if (obj is BOBLargeEntry entry) + sizeOfDroppedBod = entry.Entries.Length; + else + sizeOfDroppedBod = 1; + + m_From.AddToBackpack(item); + m_From.SendLocalizedMessage( + 1045152); // The bulk order deed has been placed in your backpack. + m_Book.Entries.Remove(obj); + m_Book.InvalidateProperties(); + + if (m_Book.Entries.Count / 5 < m_Book.ItemCount) + { + m_Book.ItemCount--; + m_Book.InvalidateItems(); + } + + if (m_Book.Entries.Count > 0) + { + m_Page = GetPageForIndex(index, sizeOfDroppedBod); + m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); + } + else + { + m_From.SendLocalizedMessage(1062381); // The book is empty. + } + } + } + } + else + { + m_From.SendMessage("Internal error. The bulk order deed could not be reconstructed."); + } + } + } + else // Set Price | Buy + { + if (m_Book.IsChildOf(m_From.Backpack)) + { + m_From.Prompt = new SetPricePrompt(m_Book, obj, m_Page, m_List); + m_From.SendLocalizedMessage(1062383); // Type in a price for the deed: + } + else if (m_Book.RootParent is PlayerVendor pv) + { + VendorItem vi = pv.GetVendorItem(m_Book); + + if (vi != null && !vi.IsForSale) + { + int sizeOfDroppedBod; + int price = 0; + if (obj is BOBLargeEntry entry) + { + price = entry.Price; + sizeOfDroppedBod = entry.Entries.Length; + } + else + { + price = ((BOBSmallEntry)obj).Price; + sizeOfDroppedBod = 1; + } + + if (price == 0) + { + m_From.SendLocalizedMessage(1062382); // The deed selected is not available. + } + else + { + if (m_Book.Entries.Count > 0) + { + m_Page = GetPageForIndex(index, sizeOfDroppedBod); + m_From.SendGump(new BODBuyGump(m_From, m_Book, obj, m_Page, price)); + } + else + { + m_From.SendLocalizedMessage(1062381); // The book is emptz + } + } + } + } + } + + break; + } + } + } + + private class SetPricePrompt : Prompt + { + private BulkOrderBook m_Book; + private ArrayList m_List; + private object m_Object; + private int m_Page; + + public SetPricePrompt(BulkOrderBook book, object obj, int page, ArrayList list) + { + m_Book = book; + m_Object = obj; + m_Page = page; + m_List = list; + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Object != null && !m_Book.Entries.Contains(m_Object)) + { + from.SendLocalizedMessage(1062382); // The deed selected is not available. + return; + } + + int price = Utility.ToInt32(text); + + if (price < 0 || price > 250000000) + { + from.SendLocalizedMessage(1062390); // The price you requested is outrageous! + } + else if (m_Object == null) + { + for (int i = 0; i < m_List.Count; ++i) + { + object obj = m_List[i]; + + if (!m_Book.Entries.Contains(obj)) + continue; + + if (obj is BOBLargeEntry entry) + entry.Price = price; + else + ((BOBSmallEntry)obj).Price = price; + } + + from.SendMessage("Deed prices set."); + + if (from is PlayerMobile mobile) + mobile.SendGump(new BOBGump(mobile, m_Book, m_Page, m_List)); + } + else if (m_Object is BOBLargeEntry entry) + { + entry.Price = price; + + from.SendLocalizedMessage(1062384); // Deed price set. + + if (from is PlayerMobile mobile) + mobile.SendGump(new BOBGump(mobile, m_Book, m_Page, m_List)); + } + else + { + ((BOBSmallEntry)m_Object).Price = price; + + from.SendLocalizedMessage(1062384); // Deed price set. + + if (from is PlayerMobile mobile) + mobile.SendGump(new BOBGump(mobile, m_Book, m_Page, m_List)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BOBLargeEntry.cs b/Scripts/Engines/BulkOrders/Books/BOBLargeEntry.cs index ace3b2f99..6c4497545 100644 --- a/Scripts/Engines/BulkOrders/Books/BOBLargeEntry.cs +++ b/Scripts/Engines/BulkOrders/Books/BOBLargeEntry.cs @@ -1,106 +1,107 @@ namespace Server.Engines.BulkOrders { - public class BOBLargeEntry - { - public bool RequireExceptional { get; } + public class BOBLargeEntry + { + public BOBLargeEntry(LargeBOD bod) + { + RequireExceptional = bod.RequireExceptional; - public BODType DeedType { get; } + if (bod is LargeTailorBOD) + DeedType = BODType.Tailor; + else if (bod is LargeSmithBOD) + DeedType = BODType.Smith; - public BulkMaterialType Material { get; } + Material = bod.Material; + AmountMax = bod.AmountMax; - public int AmountMax { get; } + Entries = new BOBLargeSubEntry[bod.Entries.Length]; - public int Price { get; set; } + for (int i = 0; i < Entries.Length; ++i) + Entries[i] = new BOBLargeSubEntry(bod.Entries[i]); + } - public BOBLargeSubEntry[] Entries { get; } + public BOBLargeEntry(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public Item Reconstruct() - { - LargeBOD bod = null; + switch (version) + { + case 0: + { + RequireExceptional = reader.ReadBool(); - if ( DeedType == BODType.Smith ) - bod = new LargeSmithBOD( AmountMax, RequireExceptional, Material, ReconstructEntries() ); - else if ( DeedType == BODType.Tailor ) - bod = new LargeTailorBOD( AmountMax, RequireExceptional, Material, ReconstructEntries() ); + DeedType = (BODType)reader.ReadEncodedInt(); - for ( int i = 0; bod != null && i < bod.Entries.Length; ++i ) - bod.Entries[i].Owner = bod; + Material = (BulkMaterialType)reader.ReadEncodedInt(); + AmountMax = reader.ReadEncodedInt(); + Price = reader.ReadEncodedInt(); - return bod; - } + Entries = new BOBLargeSubEntry[reader.ReadEncodedInt()]; - private LargeBulkEntry[] ReconstructEntries() - { - LargeBulkEntry[] entries = new LargeBulkEntry[Entries.Length]; + for (int i = 0; i < Entries.Length; ++i) + Entries[i] = new BOBLargeSubEntry(reader); - for ( int i = 0; i < Entries.Length; ++i ) - { - entries[i] = new LargeBulkEntry( null, new SmallBulkEntry( Entries[i].ItemType, Entries[i].Number, Entries[i].Graphic ) ); - entries[i].Amount = Entries[i].AmountCur; - } + break; + } + } + } - return entries; - } + public bool RequireExceptional{ get; } - public BOBLargeEntry( LargeBOD bod ) - { - RequireExceptional = bod.RequireExceptional; + public BODType DeedType{ get; } - if ( bod is LargeTailorBOD ) - DeedType = BODType.Tailor; - else if ( bod is LargeSmithBOD ) - DeedType = BODType.Smith; + public BulkMaterialType Material{ get; } - Material = bod.Material; - AmountMax = bod.AmountMax; + public int AmountMax{ get; } - Entries = new BOBLargeSubEntry[bod.Entries.Length]; + public int Price{ get; set; } - for ( int i = 0; i < Entries.Length; ++i ) - Entries[i] = new BOBLargeSubEntry( bod.Entries[i] ); - } + public BOBLargeSubEntry[] Entries{ get; } - public BOBLargeEntry( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public Item Reconstruct() + { + LargeBOD bod = null; - switch ( version ) - { - case 0: - { - RequireExceptional = reader.ReadBool(); + if (DeedType == BODType.Smith) + bod = new LargeSmithBOD(AmountMax, RequireExceptional, Material, ReconstructEntries()); + else if (DeedType == BODType.Tailor) + bod = new LargeTailorBOD(AmountMax, RequireExceptional, Material, ReconstructEntries()); - DeedType = (BODType)reader.ReadEncodedInt(); + for (int i = 0; bod != null && i < bod.Entries.Length; ++i) + bod.Entries[i].Owner = bod; - Material = (BulkMaterialType)reader.ReadEncodedInt(); - AmountMax = reader.ReadEncodedInt(); - Price = reader.ReadEncodedInt(); + return bod; + } - Entries = new BOBLargeSubEntry[reader.ReadEncodedInt()]; + private LargeBulkEntry[] ReconstructEntries() + { + LargeBulkEntry[] entries = new LargeBulkEntry[Entries.Length]; - for ( int i = 0; i < Entries.Length; ++i ) - Entries[i] = new BOBLargeSubEntry( reader ); + for (int i = 0; i < Entries.Length; ++i) + { + entries[i] = new LargeBulkEntry(null, + new SmallBulkEntry(Entries[i].ItemType, Entries[i].Number, Entries[i].Graphic)); + entries[i].Amount = Entries[i].AmountCur; + } - break; - } - } - } + return entries; + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) RequireExceptional ); + writer.Write(RequireExceptional); - writer.WriteEncodedInt( (int) DeedType ); - writer.WriteEncodedInt( (int) Material ); - writer.WriteEncodedInt( (int) AmountMax ); - writer.WriteEncodedInt( (int) Price ); + writer.WriteEncodedInt((int)DeedType); + writer.WriteEncodedInt((int)Material); + writer.WriteEncodedInt(AmountMax); + writer.WriteEncodedInt(Price); - writer.WriteEncodedInt( (int) Entries.Length ); + writer.WriteEncodedInt(Entries.Length); - for ( int i = 0; i < Entries.Length; ++i ) - Entries[i].Serialize( writer ); - } - } + for (int i = 0; i < Entries.Length; ++i) + Entries[i].Serialize(writer); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BOBLargeSubEntry.cs b/Scripts/Engines/BulkOrders/Books/BOBLargeSubEntry.cs index b3e2bcf69..fdd0430a0 100644 --- a/Scripts/Engines/BulkOrders/Books/BOBLargeSubEntry.cs +++ b/Scripts/Engines/BulkOrders/Books/BOBLargeSubEntry.cs @@ -2,55 +2,55 @@ using System; namespace Server.Engines.BulkOrders { - public class BOBLargeSubEntry - { - public Type ItemType { get; } + public class BOBLargeSubEntry + { + public BOBLargeSubEntry(LargeBulkEntry lbe) + { + ItemType = lbe.Details.Type; + AmountCur = lbe.Amount; + Number = lbe.Details.Number; + Graphic = lbe.Details.Graphic; + } - public int AmountCur { get; } + public BOBLargeSubEntry(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public int Number { get; } + switch (version) + { + case 0: + { + string type = reader.ReadString(); - public int Graphic { get; } + if (type != null) + ItemType = ScriptCompiler.FindTypeByFullName(type); - public BOBLargeSubEntry( LargeBulkEntry lbe ) - { - ItemType = lbe.Details.Type; - AmountCur = lbe.Amount; - Number = lbe.Details.Number; - Graphic = lbe.Details.Graphic; - } + AmountCur = reader.ReadEncodedInt(); + Number = reader.ReadEncodedInt(); + Graphic = reader.ReadEncodedInt(); - public BOBLargeSubEntry( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + break; + } + } + } - switch ( version ) - { - case 0: - { - string type = reader.ReadString(); + public Type ItemType{ get; } - if ( type != null ) - ItemType = ScriptCompiler.FindTypeByFullName( type ); + public int AmountCur{ get; } - AmountCur = reader.ReadEncodedInt(); - Number = reader.ReadEncodedInt(); - Graphic = reader.ReadEncodedInt(); + public int Number{ get; } - break; - } - } - } + public int Graphic{ get; } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( ItemType == null ? null : ItemType.FullName ); + writer.Write(ItemType == null ? null : ItemType.FullName); - writer.WriteEncodedInt( (int) AmountCur ); - writer.WriteEncodedInt( (int) Number ); - writer.WriteEncodedInt( (int) Graphic ); - } - } + writer.WriteEncodedInt(AmountCur); + writer.WriteEncodedInt(Number); + writer.WriteEncodedInt(Graphic); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BOBSmallEntry.cs b/Scripts/Engines/BulkOrders/Books/BOBSmallEntry.cs index 67af7315a..3a4f9f149 100644 --- a/Scripts/Engines/BulkOrders/Books/BOBSmallEntry.cs +++ b/Scripts/Engines/BulkOrders/Books/BOBSmallEntry.cs @@ -2,99 +2,99 @@ using System; namespace Server.Engines.BulkOrders { - public class BOBSmallEntry - { - public Type ItemType { get; } + public class BOBSmallEntry + { + public BOBSmallEntry(SmallBOD bod) + { + ItemType = bod.Type; + RequireExceptional = bod.RequireExceptional; - public bool RequireExceptional { get; } + if (bod is SmallTailorBOD) + DeedType = BODType.Tailor; + else if (bod is SmallSmithBOD) + DeedType = BODType.Smith; - public BODType DeedType { get; } + Material = bod.Material; + AmountCur = bod.AmountCur; + AmountMax = bod.AmountMax; + Number = bod.Number; + Graphic = bod.Graphic; + } - public BulkMaterialType Material { get; } + public BOBSmallEntry(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public int AmountCur { get; } + switch (version) + { + case 0: + { + string type = reader.ReadString(); - public int AmountMax { get; } + if (type != null) + ItemType = ScriptCompiler.FindTypeByFullName(type); - public int Number { get; } + RequireExceptional = reader.ReadBool(); - public int Graphic { get; } + DeedType = (BODType)reader.ReadEncodedInt(); - public int Price { get; set; } + Material = (BulkMaterialType)reader.ReadEncodedInt(); + AmountCur = reader.ReadEncodedInt(); + AmountMax = reader.ReadEncodedInt(); + Number = reader.ReadEncodedInt(); + Graphic = reader.ReadEncodedInt(); + Price = reader.ReadEncodedInt(); - public Item Reconstruct() - { - SmallBOD bod = null; + break; + } + } + } - if ( DeedType == BODType.Smith ) - bod = new SmallSmithBOD( AmountCur, AmountMax, ItemType, Number, Graphic, RequireExceptional, Material ); - else if ( DeedType == BODType.Tailor ) - bod = new SmallTailorBOD( AmountCur, AmountMax, ItemType, Number, Graphic, RequireExceptional, Material ); + public Type ItemType{ get; } - return bod; - } + public bool RequireExceptional{ get; } - public BOBSmallEntry( SmallBOD bod ) - { - ItemType = bod.Type; - RequireExceptional = bod.RequireExceptional; + public BODType DeedType{ get; } - if ( bod is SmallTailorBOD ) - DeedType = BODType.Tailor; - else if ( bod is SmallSmithBOD ) - DeedType = BODType.Smith; + public BulkMaterialType Material{ get; } - Material = bod.Material; - AmountCur = bod.AmountCur; - AmountMax = bod.AmountMax; - Number = bod.Number; - Graphic = bod.Graphic; - } + public int AmountCur{ get; } - public BOBSmallEntry( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public int AmountMax{ get; } - switch ( version ) - { - case 0: - { - string type = reader.ReadString(); + public int Number{ get; } - if ( type != null ) - ItemType = ScriptCompiler.FindTypeByFullName( type ); + public int Graphic{ get; } - RequireExceptional = reader.ReadBool(); + public int Price{ get; set; } - DeedType = (BODType)reader.ReadEncodedInt(); + public Item Reconstruct() + { + SmallBOD bod = null; - Material = (BulkMaterialType)reader.ReadEncodedInt(); - AmountCur = reader.ReadEncodedInt(); - AmountMax = reader.ReadEncodedInt(); - Number = reader.ReadEncodedInt(); - Graphic = reader.ReadEncodedInt(); - Price = reader.ReadEncodedInt(); + if (DeedType == BODType.Smith) + bod = new SmallSmithBOD(AmountCur, AmountMax, ItemType, Number, Graphic, RequireExceptional, Material); + else if (DeedType == BODType.Tailor) + bod = new SmallTailorBOD(AmountCur, AmountMax, ItemType, Number, Graphic, RequireExceptional, Material); - break; - } - } - } + return bod; + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( ItemType == null ? null : ItemType.FullName ); + writer.Write(ItemType == null ? null : ItemType.FullName); - writer.Write( (bool) RequireExceptional ); + writer.Write(RequireExceptional); - writer.WriteEncodedInt( (int) DeedType ); - writer.WriteEncodedInt( (int) Material ); - writer.WriteEncodedInt( (int) AmountCur ); - writer.WriteEncodedInt( (int) AmountMax ); - writer.WriteEncodedInt( (int) Number ); - writer.WriteEncodedInt( (int) Graphic ); - writer.WriteEncodedInt( (int) Price ); - } - } + writer.WriteEncodedInt((int)DeedType); + writer.WriteEncodedInt((int)Material); + writer.WriteEncodedInt(AmountCur); + writer.WriteEncodedInt(AmountMax); + writer.WriteEncodedInt(Number); + writer.WriteEncodedInt(Graphic); + writer.WriteEncodedInt(Price); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BODBuyGump.cs b/Scripts/Engines/BulkOrders/Books/BODBuyGump.cs index e8d2040db..dc4acf393 100644 --- a/Scripts/Engines/BulkOrders/Books/BODBuyGump.cs +++ b/Scripts/Engines/BulkOrders/Books/BODBuyGump.cs @@ -1,136 +1,140 @@ -using Server.Items; using Server.Gumps; +using Server.Items; using Server.Mobiles; +using Server.Network; namespace Server.Engines.BulkOrders { - public class BODBuyGump : Gump - { - private PlayerMobile m_From; - private BulkOrderBook m_Book; - private object m_Object; - private int m_Price; - private int m_Page; + public class BODBuyGump : Gump + { + private BulkOrderBook m_Book; + private PlayerMobile m_From; + private object m_Object; + private int m_Page; + private int m_Price; - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 2 ) - { - PlayerVendor pv = m_Book.RootParent as PlayerVendor; + public BODBuyGump(PlayerMobile from, BulkOrderBook book, object obj, int page, int price) : base(100, 200) + { + m_From = from; + m_Book = book; + m_Object = obj; + m_Price = price; + m_Page = page; - if ( m_Book.Entries.Contains( m_Object ) && pv != null ) - { - int price = 0; + AddPage(0); - VendorItem vi = pv.GetVendorItem( m_Book ); + AddBackground(100, 10, 300, 150, 5054); - if ( vi != null && !vi.IsForSale ) - { - if ( m_Object is BOBLargeEntry entry ) - price = entry.Price; - else - price = ((BOBSmallEntry)m_Object).Price; - } + AddHtmlLocalized(125, 20, 250, 24, 1019070, false, false); // You have agreed to purchase: + AddHtmlLocalized(125, 45, 250, 24, 1045151, false, false); // a bulk order deed - if ( price != m_Price ) - { - pv.SayTo( m_From, "The price has been been changed. If you like, you may offer to purchase the item again." ); - } - else if ( price == 0 ) - { - pv.SayTo( m_From, 1062382 ); // The deed selected is not available. - } - else - { - Item item = null; + AddHtmlLocalized(125, 70, 250, 24, 1019071, false, false); // for the amount of: + AddLabel(125, 95, 0, price.ToString()); - if ( m_Object is BOBLargeEntry entry ) - item = entry.Reconstruct(); - else - item = ((BOBSmallEntry)m_Object).Reconstruct(); + AddButton(250, 130, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(282, 130, 100, 24, 1011012, false, false); // CANCEL - if ( item == null ) - { - m_From.SendMessage( "Internal error. The bulk order deed could not be reconstructed." ); - } - else - { - pv.Say( m_From.Name ); + AddButton(120, 130, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(152, 130, 100, 24, 1011036, false, false); // OKAY + } - Container pack = m_From.Backpack; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 2) + { + PlayerVendor pv = m_Book.RootParent as PlayerVendor; - if ( (pack == null) || ((pack != null) && (!pack.CheckHold(m_From, item, true, true, 0, item.PileWeight + item.TotalWeight)) ) ) - { - pv.SayTo(m_From, 503204); // You do not have room in your backpack for this - m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); - } - else - { - if ((pack != null && pack.ConsumeTotal( typeof( Gold ), price )) || Banker.Withdraw( m_From, price ) ) - { - m_Book.Entries.Remove( m_Object ); - m_Book.InvalidateProperties(); - pv.HoldGold += price; - m_From.AddToBackpack( item ); - m_From.SendLocalizedMessage( 1045152 ); // The bulk order deed has been placed in your backpack. + if (m_Book.Entries.Contains(m_Object) && pv != null) + { + int price = 0; - if ( m_Book.Entries.Count / 5 < m_Book.ItemCount ) - { - m_Book.ItemCount--; - m_Book.InvalidateItems(); - } + VendorItem vi = pv.GetVendorItem(m_Book); - if ( m_Book.Entries.Count > 0 ) - m_From.SendGump( new BOBGump( m_From, m_Book, m_Page, null ) ); - else - m_From.SendLocalizedMessage( 1062381 ); // The book is empty. - } - else - { - pv.SayTo( m_From, 503205 ); // You cannot afford this item. - item.Delete(); - } - } - } - } - } - else - { - if ( pv == null ) - m_From.SendLocalizedMessage( 1062382 ); // The deed selected is not available. - else - pv.SayTo( m_From, 1062382 ); // The deed selected is not available. - } - } - else - { - m_From.SendLocalizedMessage( 503207 ); // Cancelled purchase. - } - } + if (vi != null && !vi.IsForSale) + { + if (m_Object is BOBLargeEntry entry) + price = entry.Price; + else + price = ((BOBSmallEntry)m_Object).Price; + } - public BODBuyGump( PlayerMobile from, BulkOrderBook book, object obj, int page, int price ) : base( 100, 200 ) - { - m_From = from; - m_Book = book; - m_Object = obj; - m_Price = price; - m_Page = page; + if (price != m_Price) + { + pv.SayTo(m_From, + "The price has been been changed. If you like, you may offer to purchase the item again."); + } + else if (price == 0) + { + pv.SayTo(m_From, 1062382); // The deed selected is not available. + } + else + { + Item item = null; - AddPage( 0 ); + if (m_Object is BOBLargeEntry entry) + item = entry.Reconstruct(); + else + item = ((BOBSmallEntry)m_Object).Reconstruct(); - AddBackground( 100, 10, 300, 150, 5054 ); + if (item == null) + { + m_From.SendMessage("Internal error. The bulk order deed could not be reconstructed."); + } + else + { + pv.Say(m_From.Name); - AddHtmlLocalized( 125, 20, 250, 24, 1019070, false, false ); // You have agreed to purchase: - AddHtmlLocalized( 125, 45, 250, 24, 1045151, false, false ); // a bulk order deed + Container pack = m_From.Backpack; - AddHtmlLocalized( 125, 70, 250, 24, 1019071, false, false ); // for the amount of: - AddLabel( 125, 95, 0, price.ToString() ); + if (pack == null || pack != null && !pack.CheckHold(m_From, item, true, true, 0, + item.PileWeight + item.TotalWeight)) + { + pv.SayTo(m_From, 503204); // You do not have room in your backpack for this + m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); + } + else + { + if (pack != null && pack.ConsumeTotal(typeof(Gold), price) || Banker.Withdraw(m_From, price)) + { + m_Book.Entries.Remove(m_Object); + m_Book.InvalidateProperties(); + pv.HoldGold += price; + m_From.AddToBackpack(item); + m_From.SendLocalizedMessage( + 1045152); // The bulk order deed has been placed in your backpack. - AddButton( 250, 130, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 282, 130, 100, 24, 1011012, false, false ); // CANCEL + if (m_Book.Entries.Count / 5 < m_Book.ItemCount) + { + m_Book.ItemCount--; + m_Book.InvalidateItems(); + } - AddButton( 120, 130, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 152, 130, 100, 24, 1011036, false, false ); // OKAY - } - } -} + if (m_Book.Entries.Count > 0) + m_From.SendGump(new BOBGump(m_From, m_Book, m_Page, null)); + else + m_From.SendLocalizedMessage(1062381); // The book is empty. + } + else + { + pv.SayTo(m_From, 503205); // You cannot afford this item. + item.Delete(); + } + } + } + } + } + else + { + if (pv == null) + m_From.SendLocalizedMessage(1062382); // The deed selected is not available. + else + pv.SayTo(m_From, 1062382); // The deed selected is not available. + } + } + else + { + m_From.SendLocalizedMessage(503207); // Cancelled purchase. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Books/BODType.cs b/Scripts/Engines/BulkOrders/Books/BODType.cs index b29649e78..fbeb7cb5a 100644 --- a/Scripts/Engines/BulkOrders/Books/BODType.cs +++ b/Scripts/Engines/BulkOrders/Books/BODType.cs @@ -1,8 +1,8 @@ namespace Server.Engines.BulkOrders { - public enum BODType - { - Smith, - Tailor - } + public enum BODType + { + Smith, + Tailor + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/BulkMaterialType.cs b/Scripts/Engines/BulkOrders/BulkMaterialType.cs index 06869e0cc..82085ca4d 100644 --- a/Scripts/Engines/BulkOrders/BulkMaterialType.cs +++ b/Scripts/Engines/BulkOrders/BulkMaterialType.cs @@ -3,42 +3,42 @@ using Server.Items; namespace Server.Engines.BulkOrders { - public enum BulkMaterialType - { - None, - DullCopper, - ShadowIron, - Copper, - Bronze, - Gold, - Agapite, - Verite, - Valorite, - Spined, - Horned, - Barbed - } + public enum BulkMaterialType + { + None, + DullCopper, + ShadowIron, + Copper, + Bronze, + Gold, + Agapite, + Verite, + Valorite, + Spined, + Horned, + Barbed + } - public enum BulkGenericType - { - Iron, - Cloth, - Leather - } + public enum BulkGenericType + { + Iron, + Cloth, + Leather + } - public class BGTClassifier - { - public static BulkGenericType Classify( BODType deedType, Type itemType ) - { - if ( deedType == BODType.Tailor ) - { - if ( itemType == null || itemType.IsSubclassOf( typeof( BaseArmor ) ) || itemType.IsSubclassOf( typeof( BaseShoes ) ) ) - return BulkGenericType.Leather; + public class BGTClassifier + { + public static BulkGenericType Classify(BODType deedType, Type itemType) + { + if (deedType == BODType.Tailor) + { + if (itemType == null || itemType.IsSubclassOf(typeof(BaseArmor)) || itemType.IsSubclassOf(typeof(BaseShoes))) + return BulkGenericType.Leather; - return BulkGenericType.Cloth; - } + return BulkGenericType.Cloth; + } - return BulkGenericType.Iron; - } - } + return BulkGenericType.Iron; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/LargeBODAcceptGump.cs b/Scripts/Engines/BulkOrders/LargeBODAcceptGump.cs index a4cf6f421..e5619b07a 100644 --- a/Scripts/Engines/BulkOrders/LargeBODAcceptGump.cs +++ b/Scripts/Engines/BulkOrders/LargeBODAcceptGump.cs @@ -3,102 +3,105 @@ using Server.Network; namespace Server.Engines.BulkOrders { - public class LargeBODAcceptGump : Gump - { - private LargeBOD m_Deed; - private Mobile m_From; + public class LargeBODAcceptGump : Gump + { + private LargeBOD m_Deed; + private Mobile m_From; - public LargeBODAcceptGump( Mobile from, LargeBOD deed ) : base( 50, 50 ) - { - m_From = from; - m_Deed = deed; + public LargeBODAcceptGump(Mobile from, LargeBOD deed) : base(50, 50) + { + m_From = from; + m_Deed = deed; - m_From.CloseGump( typeof( LargeBODAcceptGump ) ); - m_From.CloseGump( typeof( SmallBODAcceptGump ) ); + m_From.CloseGump(typeof(LargeBODAcceptGump)); + m_From.CloseGump(typeof(SmallBODAcceptGump)); - LargeBulkEntry[] entries = deed.Entries; + LargeBulkEntry[] entries = deed.Entries; - AddPage( 0 ); + AddPage(0); - AddBackground( 25, 10, 430, 240 + (entries.Length * 24), 5054 ); + AddBackground(25, 10, 430, 240 + entries.Length * 24, 5054); - AddImageTiled( 33, 20, 413, 221 + (entries.Length * 24), 2624 ); - AddAlphaRegion( 33, 20, 413, 221 + (entries.Length * 24) ); + AddImageTiled(33, 20, 413, 221 + entries.Length * 24, 2624); + AddAlphaRegion(33, 20, 413, 221 + entries.Length * 24); - AddImage( 20, 5, 10460 ); - AddImage( 430, 5, 10460 ); - AddImage( 20, 225 + (entries.Length * 24), 10460 ); - AddImage( 430, 225 + (entries.Length * 24), 10460 ); + AddImage(20, 5, 10460); + AddImage(430, 5, 10460); + AddImage(20, 225 + entries.Length * 24, 10460); + AddImage(430, 225 + entries.Length * 24, 10460); - AddHtmlLocalized( 180, 25, 120, 20, 1045134, 0x7FFF, false, false ); // A large bulk order + AddHtmlLocalized(180, 25, 120, 20, 1045134, 0x7FFF, false, false); // A large bulk order - AddHtmlLocalized( 40, 48, 350, 20, 1045135, 0x7FFF, false, false ); // Ah! Thanks for the goods! Would you help me out? + AddHtmlLocalized(40, 48, 350, 20, 1045135, 0x7FFF, false, + false); // Ah! Thanks for the goods! Would you help me out? - AddHtmlLocalized( 40, 72, 210, 20, 1045138, 0x7FFF, false, false ); // Amount to make: - AddLabel( 250, 72, 1152, deed.AmountMax.ToString() ); + AddHtmlLocalized(40, 72, 210, 20, 1045138, 0x7FFF, false, false); // Amount to make: + AddLabel(250, 72, 1152, deed.AmountMax.ToString()); - AddHtmlLocalized( 40, 96, 120, 20, 1045137, 0x7FFF, false, false ); // Items requested: + AddHtmlLocalized(40, 96, 120, 20, 1045137, 0x7FFF, false, false); // Items requested: - int y = 120; + int y = 120; - for ( int i = 0; i < entries.Length; ++i, y += 24 ) - AddHtmlLocalized( 40, y, 210, 20, entries[i].Details.Number, 0x7FFF, false, false ); + for (int i = 0; i < entries.Length; ++i, y += 24) + AddHtmlLocalized(40, y, 210, 20, entries[i].Details.Number, 0x7FFF, false, false); - if ( deed.RequireExceptional || deed.Material != BulkMaterialType.None ) - { - AddHtmlLocalized( 40, y, 210, 20, 1045140, 0x7FFF, false, false ); // Special requirements to meet: - y += 24; + if (deed.RequireExceptional || deed.Material != BulkMaterialType.None) + { + AddHtmlLocalized(40, y, 210, 20, 1045140, 0x7FFF, false, false); // Special requirements to meet: + y += 24; - if ( deed.RequireExceptional ) - { - AddHtmlLocalized( 40, y, 350, 20, 1045141, 0x7FFF, false, false ); // All items must be exceptional. - y += 24; - } + if (deed.RequireExceptional) + { + AddHtmlLocalized(40, y, 350, 20, 1045141, 0x7FFF, false, false); // All items must be exceptional. + y += 24; + } - if ( deed.Material != BulkMaterialType.None ) - { - AddHtmlLocalized( 40, y, 350, 20, GetMaterialNumberFor( deed.Material ), 0x7FFF, false, false ); // All items must be made with x material. - y += 24; - } - } + if (deed.Material != BulkMaterialType.None) + { + AddHtmlLocalized(40, y, 350, 20, GetMaterialNumberFor(deed.Material), 0x7FFF, false, + false); // All items must be made with x material. + y += 24; + } + } - AddHtmlLocalized( 40, 192 + (entries.Length * 24), 350, 20, 1045139, 0x7FFF, false, false ); // Do you want to accept this order? + AddHtmlLocalized(40, 192 + entries.Length * 24, 350, 20, 1045139, 0x7FFF, false, + false); // Do you want to accept this order? - AddButton( 100, 216 + (entries.Length * 24), 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 135, 216 + (entries.Length * 24), 120, 20, 1006044, 0x7FFF, false, false ); // Ok + AddButton(100, 216 + entries.Length * 24, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(135, 216 + entries.Length * 24, 120, 20, 1006044, 0x7FFF, false, false); // Ok - AddButton( 275, 216 + (entries.Length * 24), 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 310, 216 + (entries.Length * 24), 120, 20, 1011012, 0x7FFF, false, false ); // CANCEL - } + AddButton(275, 216 + entries.Length * 24, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(310, 216 + entries.Length * 24, 120, 20, 1011012, 0x7FFF, false, false); // CANCEL + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) // Ok - { - if ( m_From.PlaceInBackpack( m_Deed ) ) - { - m_From.SendLocalizedMessage( 1045152 ); // The bulk order deed has been placed in your backpack. - } - else - { - m_From.SendLocalizedMessage( 1045150 ); // There is not enough room in your backpack for the deed. - m_Deed.Delete(); - } - } - else - { - m_Deed.Delete(); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) // Ok + { + if (m_From.PlaceInBackpack(m_Deed)) + { + m_From.SendLocalizedMessage(1045152); // The bulk order deed has been placed in your backpack. + } + else + { + m_From.SendLocalizedMessage(1045150); // There is not enough room in your backpack for the deed. + m_Deed.Delete(); + } + } + else + { + m_Deed.Delete(); + } + } - public static int GetMaterialNumberFor( BulkMaterialType material ) - { - if ( material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite ) - return 1045142 + (int)(material - BulkMaterialType.DullCopper); - if ( material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed ) - return 1049348 + (int)(material - BulkMaterialType.Spined); + public static int GetMaterialNumberFor(BulkMaterialType material) + { + if (material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite) + return 1045142 + (material - BulkMaterialType.DullCopper); + if (material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed) + return 1049348 + (material - BulkMaterialType.Spined); - return 0; - } - } + return 0; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/LargeBODGump.cs b/Scripts/Engines/BulkOrders/LargeBODGump.cs index 36b810004..e7d992fb0 100644 --- a/Scripts/Engines/BulkOrders/LargeBODGump.cs +++ b/Scripts/Engines/BulkOrders/LargeBODGump.cs @@ -3,96 +3,98 @@ using Server.Network; namespace Server.Engines.BulkOrders { - public class LargeBODGump : Gump - { - private LargeBOD m_Deed; - private Mobile m_From; + public class LargeBODGump : Gump + { + private LargeBOD m_Deed; + private Mobile m_From; - public LargeBODGump( Mobile from, LargeBOD deed ) : base( 25, 25 ) - { - m_From = from; - m_Deed = deed; + public LargeBODGump(Mobile from, LargeBOD deed) : base(25, 25) + { + m_From = from; + m_Deed = deed; - m_From.CloseGump( typeof( LargeBODGump ) ); - m_From.CloseGump( typeof( SmallBODGump ) ); + m_From.CloseGump(typeof(LargeBODGump)); + m_From.CloseGump(typeof(SmallBODGump)); - LargeBulkEntry[] entries = deed.Entries; + LargeBulkEntry[] entries = deed.Entries; - AddPage( 0 ); + AddPage(0); - AddBackground( 50, 10, 455, 236 + (entries.Length * 24), 5054 ); + AddBackground(50, 10, 455, 236 + entries.Length * 24, 5054); - AddImageTiled( 58, 20, 438, 217 + (entries.Length * 24), 2624 ); - AddAlphaRegion( 58, 20, 438, 217 + (entries.Length * 24) ); + AddImageTiled(58, 20, 438, 217 + entries.Length * 24, 2624); + AddAlphaRegion(58, 20, 438, 217 + entries.Length * 24); - AddImage( 45, 5, 10460 ); - AddImage( 480, 5, 10460 ); - AddImage( 45, 221 + (entries.Length * 24), 10460 ); - AddImage( 480, 221 + (entries.Length * 24), 10460 ); + AddImage(45, 5, 10460); + AddImage(480, 5, 10460); + AddImage(45, 221 + entries.Length * 24, 10460); + AddImage(480, 221 + entries.Length * 24, 10460); - AddHtmlLocalized( 225, 25, 120, 20, 1045134, 0x7FFF, false, false ); // A large bulk order + AddHtmlLocalized(225, 25, 120, 20, 1045134, 0x7FFF, false, false); // A large bulk order - AddHtmlLocalized( 75, 48, 250, 20, 1045138, 0x7FFF, false, false ); // Amount to make: - AddLabel( 275, 48, 1152, deed.AmountMax.ToString() ); + AddHtmlLocalized(75, 48, 250, 20, 1045138, 0x7FFF, false, false); // Amount to make: + AddLabel(275, 48, 1152, deed.AmountMax.ToString()); - AddHtmlLocalized( 75, 72, 120, 20, 1045137, 0x7FFF, false, false ); // Items requested: - AddHtmlLocalized( 275, 76, 200, 20, 1045153, 0x7FFF, false, false ); // Amount finished: + AddHtmlLocalized(75, 72, 120, 20, 1045137, 0x7FFF, false, false); // Items requested: + AddHtmlLocalized(275, 76, 200, 20, 1045153, 0x7FFF, false, false); // Amount finished: - int y = 96; + int y = 96; - for ( int i = 0; i < entries.Length; ++i ) - { - LargeBulkEntry entry = entries[i]; - SmallBulkEntry details = entry.Details; + for (int i = 0; i < entries.Length; ++i) + { + LargeBulkEntry entry = entries[i]; + SmallBulkEntry details = entry.Details; - AddHtmlLocalized( 75, y, 210, 20, details.Number, 0x7FFF, false, false ); - AddLabel( 275, y, 0x480, entry.Amount.ToString() ); + AddHtmlLocalized(75, y, 210, 20, details.Number, 0x7FFF, false, false); + AddLabel(275, y, 0x480, entry.Amount.ToString()); - y += 24; - } + y += 24; + } - if ( deed.RequireExceptional || deed.Material != BulkMaterialType.None ) - { - AddHtmlLocalized( 75, y, 200, 20, 1045140, 0x7FFF, false, false ); // Special requirements to meet: - y += 24; - } + if (deed.RequireExceptional || deed.Material != BulkMaterialType.None) + { + AddHtmlLocalized(75, y, 200, 20, 1045140, 0x7FFF, false, false); // Special requirements to meet: + y += 24; + } - if ( deed.RequireExceptional ) - { - AddHtmlLocalized( 75, y, 300, 20, 1045141, 0x7FFF, false, false ); // All items must be exceptional. - y += 24; - } + if (deed.RequireExceptional) + { + AddHtmlLocalized(75, y, 300, 20, 1045141, 0x7FFF, false, false); // All items must be exceptional. + y += 24; + } - if ( deed.Material != BulkMaterialType.None ) - AddHtmlLocalized( 75, y, 300, 20, GetMaterialNumberFor( deed.Material ), 0x7FFF, false, false ); // All items must be made with x material. + if (deed.Material != BulkMaterialType.None) + AddHtmlLocalized(75, y, 300, 20, GetMaterialNumberFor(deed.Material), 0x7FFF, false, + false); // All items must be made with x material. - AddButton( 125, 168 + (entries.Length * 24), 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 160, 168 + (entries.Length * 24), 300, 20, 1045155, 0x7FFF, false, false ); // Combine this deed with another deed. + AddButton(125, 168 + entries.Length * 24, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(160, 168 + entries.Length * 24, 300, 20, 1045155, 0x7FFF, false, + false); // Combine this deed with another deed. - AddButton( 125, 192 + (entries.Length * 24), 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 160, 192 + (entries.Length * 24), 120, 20, 1011441, 0x7FFF, false, false ); // EXIT - } + AddButton(125, 192 + entries.Length * 24, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(160, 192 + entries.Length * 24, 120, 20, 1011441, 0x7FFF, false, false); // EXIT + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed.Deleted || !m_Deed.IsChildOf( m_From.Backpack ) ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed.Deleted || !m_Deed.IsChildOf(m_From.Backpack)) + return; - if ( info.ButtonID == 2 ) // Combine - { - m_From.SendGump( new LargeBODGump( m_From, m_Deed ) ); - m_Deed.BeginCombine( m_From ); - } - } + if (info.ButtonID == 2) // Combine + { + m_From.SendGump(new LargeBODGump(m_From, m_Deed)); + m_Deed.BeginCombine(m_From); + } + } - public static int GetMaterialNumberFor( BulkMaterialType material ) - { - if ( material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite ) - return 1045142 + (int)(material - BulkMaterialType.DullCopper); - if ( material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed ) - return 1049348 + (int)(material - BulkMaterialType.Spined); + public static int GetMaterialNumberFor(BulkMaterialType material) + { + if (material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite) + return 1045142 + (material - BulkMaterialType.DullCopper); + if (material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed) + return 1049348 + (material - BulkMaterialType.Spined); - return 0; - } - } + return 0; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/LargeBODTarget.cs b/Scripts/Engines/BulkOrders/LargeBODTarget.cs index b7954597e..be8ec11ef 100644 --- a/Scripts/Engines/BulkOrders/LargeBODTarget.cs +++ b/Scripts/Engines/BulkOrders/LargeBODTarget.cs @@ -2,21 +2,21 @@ using Server.Targeting; namespace Server.Engines.BulkOrders { - public class LargeBODTarget : Target - { - private LargeBOD m_Deed; + public class LargeBODTarget : Target + { + private LargeBOD m_Deed; - public LargeBODTarget( LargeBOD deed ) : base( 18, false, TargetFlags.None ) - { - m_Deed = deed; - } + public LargeBODTarget(LargeBOD deed) : base(18, false, TargetFlags.None) + { + m_Deed = deed; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Deed.Deleted || !m_Deed.IsChildOf( from.Backpack ) ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Deed.Deleted || !m_Deed.IsChildOf(from.Backpack)) + return; - m_Deed.EndCombine( from, targeted ); - } - } + m_Deed.EndCombine(from, targeted); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/LargeSmithBOD.cs b/Scripts/Engines/BulkOrders/LargeSmithBOD.cs index 24fd8a6cc..52827f459 100644 --- a/Scripts/Engines/BulkOrders/LargeSmithBOD.cs +++ b/Scripts/Engines/BulkOrders/LargeSmithBOD.cs @@ -1,132 +1,150 @@ -using Mat = Server.Engines.BulkOrders.BulkMaterialType; using System.Collections.Generic; +using Mat = Server.Engines.BulkOrders.BulkMaterialType; namespace Server.Engines.BulkOrders { - [TypeAlias( "Scripts.Engines.BulkOrders.LargeSmithBOD" )] - public class LargeSmithBOD : LargeBOD - { - public static double[] m_BlacksmithMaterialChances = { - 0.501953125, // None - 0.250000000, // Dull Copper - 0.125000000, // Shadow Iron - 0.062500000, // Copper - 0.031250000, // Bronze - 0.015625000, // Gold - 0.007812500, // Agapite - 0.003906250, // Verite - 0.001953125 // Valorite - }; + [TypeAlias("Scripts.Engines.BulkOrders.LargeSmithBOD")] + public class LargeSmithBOD : LargeBOD + { + public static double[] m_BlacksmithMaterialChances = + { + 0.501953125, // None + 0.250000000, // Dull Copper + 0.125000000, // Shadow Iron + 0.062500000, // Copper + 0.031250000, // Bronze + 0.015625000, // Gold + 0.007812500, // Agapite + 0.003906250, // Verite + 0.001953125 // Valorite + }; - public override int ComputeFame() - { - return SmithRewardCalculator.Instance.ComputeFame( this ); - } + [Constructible] + public LargeSmithBOD() + { + LargeBulkEntry[] entries; + bool useMaterials = true; - public override int ComputeGold() - { - return SmithRewardCalculator.Instance.ComputeGold( this ); - } + int rand = Utility.Random(8); - [Constructible] - public LargeSmithBOD() - { - LargeBulkEntry[] entries; - bool useMaterials = true; + switch (rand) + { + default: + case 0: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargeRing); + break; + case 1: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargePlate); + break; + case 2: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargeChain); + break; + case 3: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargeAxes); + break; + case 4: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargeFencing); + break; + case 5: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargeMaces); + break; + case 6: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargePolearms); + break; + case 7: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.LargeSwords); + break; + } - int rand = Utility.Random( 8 ); + if (rand > 2 && rand < 8) + useMaterials = false; - switch ( rand ) - { - default: - case 0: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargeRing ); break; - case 1: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargePlate ); break; - case 2: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargeChain ); break; - case 3: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargeAxes ); break; - case 4: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargeFencing ); break; - case 5: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargeMaces ); break; - case 6: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargePolearms ); break; - case 7: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.LargeSwords ); break; - } + int hue = 0x44E; + int amountMax = Utility.RandomList(10, 15, 20, 20); + bool reqExceptional = 0.825 > Utility.RandomDouble(); - if ( rand > 2 && rand < 8 ) - useMaterials = false; + BulkMaterialType material; - int hue = 0x44E; - int amountMax = Utility.RandomList( 10, 15, 20, 20 ); - bool reqExceptional = ( 0.825 > Utility.RandomDouble() ); + if (useMaterials) + material = GetRandomMaterial(BulkMaterialType.DullCopper, m_BlacksmithMaterialChances); + else + material = BulkMaterialType.None; - BulkMaterialType material; + Hue = hue; + AmountMax = amountMax; + Entries = entries; + RequireExceptional = reqExceptional; + Material = material; + } - if ( useMaterials ) - material = GetRandomMaterial( BulkMaterialType.DullCopper, m_BlacksmithMaterialChances ); - else - material = BulkMaterialType.None; + public LargeSmithBOD(int amountMax, bool reqExceptional, BulkMaterialType mat, LargeBulkEntry[] entries) + { + Hue = 0x44E; + AmountMax = amountMax; + Entries = entries; + RequireExceptional = reqExceptional; + Material = mat; + } - Hue = hue; - AmountMax = amountMax; - Entries = entries; - RequireExceptional = reqExceptional; - Material = material; - } + public LargeSmithBOD(Serial serial) : base(serial) + { + } - public LargeSmithBOD( int amountMax, bool reqExceptional, BulkMaterialType mat, LargeBulkEntry[] entries ) - { - Hue = 0x44E; - AmountMax = amountMax; - Entries = entries; - RequireExceptional = reqExceptional; - Material = mat; - } + public override int ComputeFame() + { + return SmithRewardCalculator.Instance.ComputeFame(this); + } - public override List ComputeRewards( bool full ) - { - List list = new List(); + public override int ComputeGold() + { + return SmithRewardCalculator.Instance.ComputeGold(this); + } - RewardGroup rewardGroup = SmithRewardCalculator.Instance.LookupRewards( SmithRewardCalculator.Instance.ComputePoints( this ) ); + public override List ComputeRewards(bool full) + { + List list = new List(); - if ( rewardGroup != null ) - { - if ( full ) - { - for ( int i = 0; i < rewardGroup.Items.Length; ++i ) - { - Item item = rewardGroup.Items[i].Construct(); + RewardGroup rewardGroup = + SmithRewardCalculator.Instance.LookupRewards(SmithRewardCalculator.Instance.ComputePoints(this)); - if ( item != null ) - list.Add( item ); - } - } - else - { - RewardItem rewardItem = rewardGroup.AcquireItem(); + if (rewardGroup != null) + { + if (full) + { + for (int i = 0; i < rewardGroup.Items.Length; ++i) + { + Item item = rewardGroup.Items[i].Construct(); - Item item = rewardItem?.Construct(); + if (item != null) + list.Add(item); + } + } + else + { + RewardItem rewardItem = rewardGroup.AcquireItem(); - if ( item != null ) - list.Add( item ); - } - } + Item item = rewardItem?.Construct(); - return list; - } + if (item != null) + list.Add(item); + } + } - public LargeSmithBOD( Serial serial ) : base( serial ) - { - } + return list; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/LargeTailorBOD.cs b/Scripts/Engines/BulkOrders/LargeTailorBOD.cs index 890514a7f..d2d3218fb 100644 --- a/Scripts/Engines/BulkOrders/LargeTailorBOD.cs +++ b/Scripts/Engines/BulkOrders/LargeTailorBOD.cs @@ -1,127 +1,162 @@ -using Mat = Server.Engines.BulkOrders.BulkMaterialType; using System.Collections.Generic; +using Mat = Server.Engines.BulkOrders.BulkMaterialType; namespace Server.Engines.BulkOrders { - public class LargeTailorBOD : LargeBOD - { - public static double[] m_TailoringMaterialChances = { - 0.857421875, // None - 0.125000000, // Spined - 0.015625000, // Horned - 0.001953125 // Barbed - }; + public class LargeTailorBOD : LargeBOD + { + public static double[] m_TailoringMaterialChances = + { + 0.857421875, // None + 0.125000000, // Spined + 0.015625000, // Horned + 0.001953125 // Barbed + }; - public override int ComputeFame() - { - return TailorRewardCalculator.Instance.ComputeFame( this ); - } + [Constructible] + public LargeTailorBOD() + { + LargeBulkEntry[] entries; + bool useMaterials = false; - public override int ComputeGold() - { - return TailorRewardCalculator.Instance.ComputeGold( this ); - } + switch (Utility.Random(14)) + { + default: + case 0: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.Farmer); + break; + case 1: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.FemaleLeatherSet); + useMaterials = true; + break; + case 2: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.FisherGirl); + break; + case 3: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.Gypsy); + break; + case 4: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.HatSet); + break; + case 5: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.Jester); + break; + case 6: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.Lady); + break; + case 7: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.MaleLeatherSet); + useMaterials = true; + break; + case 8: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.Pirate); + break; + case 9: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.ShoeSet); + useMaterials = Core.ML; + break; + case 10: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.StuddedSet); + useMaterials = true; + break; + case 11: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.TownCrier); + break; + case 12: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.Wizard); + break; + case 13: + entries = LargeBulkEntry.ConvertEntries(this, LargeBulkEntry.BoneSet); + useMaterials = true; + break; + } - [Constructible] - public LargeTailorBOD() - { - LargeBulkEntry[] entries; - bool useMaterials = false; + int hue = 0x483; + int amountMax = Utility.RandomList(10, 15, 20, 20); + bool reqExceptional = 0.825 > Utility.RandomDouble(); - switch ( Utility.Random( 14 ) ) - { - default: - case 0: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.Farmer ); break; - case 1: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.FemaleLeatherSet ); useMaterials = true; break; - case 2: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.FisherGirl ); break; - case 3: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.Gypsy ); break; - case 4: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.HatSet ); break; - case 5: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.Jester ); break; - case 6: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.Lady ); break; - case 7: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.MaleLeatherSet ); useMaterials = true; break; - case 8: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.Pirate ); break; - case 9: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.ShoeSet ); useMaterials = Core.ML; break; - case 10: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.StuddedSet ); useMaterials = true; break; - case 11: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.TownCrier ); break; - case 12: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.Wizard ); break; - case 13: entries = LargeBulkEntry.ConvertEntries( this, LargeBulkEntry.BoneSet ); useMaterials = true; break; - } + BulkMaterialType material; - int hue = 0x483; - int amountMax = Utility.RandomList( 10, 15, 20, 20 ); - bool reqExceptional = ( 0.825 > Utility.RandomDouble() ); + if (useMaterials) + material = GetRandomMaterial(BulkMaterialType.Spined, m_TailoringMaterialChances); + else + material = BulkMaterialType.None; - BulkMaterialType material; + Hue = hue; + AmountMax = amountMax; + Entries = entries; + RequireExceptional = reqExceptional; + Material = material; + } - if ( useMaterials ) - material = GetRandomMaterial( BulkMaterialType.Spined, m_TailoringMaterialChances ); - else - material = BulkMaterialType.None; + public LargeTailorBOD(int amountMax, bool reqExceptional, BulkMaterialType mat, LargeBulkEntry[] entries) + { + Hue = 0x483; + AmountMax = amountMax; + Entries = entries; + RequireExceptional = reqExceptional; + Material = mat; + } - Hue = hue; - AmountMax = amountMax; - Entries = entries; - RequireExceptional = reqExceptional; - Material = material; - } + public LargeTailorBOD(Serial serial) : base(serial) + { + } - public LargeTailorBOD( int amountMax, bool reqExceptional, BulkMaterialType mat, LargeBulkEntry[] entries ) - { - Hue = 0x483; - AmountMax = amountMax; - Entries = entries; - RequireExceptional = reqExceptional; - Material = mat; - } + public override int ComputeFame() + { + return TailorRewardCalculator.Instance.ComputeFame(this); + } - public override List ComputeRewards( bool full ) - { - List list = new List(); + public override int ComputeGold() + { + return TailorRewardCalculator.Instance.ComputeGold(this); + } - RewardGroup rewardGroup = TailorRewardCalculator.Instance.LookupRewards( TailorRewardCalculator.Instance.ComputePoints( this ) ); + public override List ComputeRewards(bool full) + { + List list = new List(); - if ( rewardGroup != null ) - { - if ( full ) - { - for ( int i = 0; i < rewardGroup.Items.Length; ++i ) - { - Item item = rewardGroup.Items[i].Construct(); + RewardGroup rewardGroup = + TailorRewardCalculator.Instance.LookupRewards(TailorRewardCalculator.Instance.ComputePoints(this)); - if ( item != null ) - list.Add( item ); - } - } - else - { - RewardItem rewardItem = rewardGroup.AcquireItem(); + if (rewardGroup != null) + { + if (full) + { + for (int i = 0; i < rewardGroup.Items.Length; ++i) + { + Item item = rewardGroup.Items[i].Construct(); - Item item = rewardItem?.Construct(); + if (item != null) + list.Add(item); + } + } + else + { + RewardItem rewardItem = rewardGroup.AcquireItem(); - if ( item != null ) - list.Add( item ); - } - } + Item item = rewardItem?.Construct(); - return list; - } + if (item != null) + list.Add(item); + } + } - public LargeTailorBOD( Serial serial ) : base( serial ) - { - } + return list; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/Rewards.cs b/Scripts/Engines/BulkOrders/Rewards.cs index 2ee3bb7e4..11977639c 100644 --- a/Scripts/Engines/BulkOrders/Rewards.cs +++ b/Scripts/Engines/BulkOrders/Rewards.cs @@ -3,722 +3,746 @@ using Server.Items; namespace Server.Engines.BulkOrders { - public delegate Item ConstructCallback( int type ); + public delegate Item ConstructCallback(int type); + + public sealed class RewardType + { + public RewardType(int points, params Type[] types) + { + Points = points; + Types = types; + } - public sealed class RewardType - { - public int Points { get; } + public int Points{ get; } - public Type[] Types { get; } + public Type[] Types{ get; } - public RewardType( int points, params Type[] types ) - { - Points = points; - Types = types; - } + public bool Contains(Type type) + { + for (int i = 0; i < Types.Length; ++i) + if (Types[i] == type) + return true; - public bool Contains( Type type ) - { - for ( int i = 0; i < Types.Length; ++i ) - { - if ( Types[i] == type ) - return true; - } + return false; + } + } - return false; - } - } + public sealed class RewardItem + { + public RewardItem(int weight, ConstructCallback constructor) : this(weight, constructor, 0) + { + } - public sealed class RewardItem - { - public int Weight { get; } - - public ConstructCallback Constructor { get; } - - public int Type { get; } - - public RewardItem( int weight, ConstructCallback constructor ) : this( weight, constructor, 0 ) - { - } - - public RewardItem( int weight, ConstructCallback constructor, int type ) - { - Weight = weight; - Constructor = constructor; - Type = type; - } - - public Item Construct() - { - try{ return Constructor( Type ); } - catch{ return null; } - } - } - - public sealed class RewardGroup - { - public int Points { get; } - - public RewardItem[] Items { get; } - - public RewardGroup( int points, params RewardItem[] items ) - { - Points = points; - Items = items; - } - - public RewardItem AcquireItem() - { - if ( Items.Length == 0 ) - return null; - if ( Items.Length == 1 ) - return Items[0]; - - int totalWeight = 0; - - for ( int i = 0; i < Items.Length; ++i ) - totalWeight += Items[i].Weight; - - int randomWeight = Utility.Random( totalWeight ); - - for ( int i = 0; i < Items.Length; ++i ) - { - RewardItem item = Items[i]; - - if ( randomWeight < item.Weight ) - return item; - - randomWeight -= item.Weight; - } - - return null; - } - } - - public abstract class RewardCalculator - { - public RewardGroup[] Groups { get; set; } - - public abstract int ComputePoints( int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type ); - public abstract int ComputeGold( int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type ); - - public virtual int ComputeFame( SmallBOD bod ) - { - int points = ComputePoints( bod ) / 50; - - return points * points; - } - - public virtual int ComputeFame( LargeBOD bod ) - { - int points = ComputePoints( bod ) / 50; - - return points * points; - } - - public virtual int ComputePoints( SmallBOD bod ) - { - return ComputePoints( bod.AmountMax, bod.RequireExceptional, bod.Material, 1, bod.Type ); - } - - public virtual int ComputePoints( LargeBOD bod ) - { - return ComputePoints( bod.AmountMax, bod.RequireExceptional, bod.Material, bod.Entries.Length, bod.Entries[0].Details.Type ); - } - - public virtual int ComputeGold( SmallBOD bod ) - { - return ComputeGold( bod.AmountMax, bod.RequireExceptional, bod.Material, 1, bod.Type ); - } - - public virtual int ComputeGold( LargeBOD bod ) - { - return ComputeGold( bod.AmountMax, bod.RequireExceptional, bod.Material, bod.Entries.Length, bod.Entries[0].Details.Type ); - } - - public virtual RewardGroup LookupRewards( int points ) - { - for ( int i = Groups.Length - 1; i >= 1; --i ) - { - RewardGroup group = Groups[i]; - - if ( points >= group.Points ) - return group; - } - - return Groups[0]; - } - - public virtual int LookupTypePoints( RewardType[] types, Type type ) - { - for ( int i = 0; i < types.Length; ++i ) - { - if ( types[i].Contains( type ) ) - return types[i].Points; - } - - return 0; - } - - public RewardCalculator() - { - } - } - - public sealed class SmithRewardCalculator : RewardCalculator - { - #region Constructors - private static readonly ConstructCallback SturdyShovel = CreateSturdyShovel; - private static readonly ConstructCallback SturdyPickaxe = CreateSturdyPickaxe; - private static readonly ConstructCallback MiningGloves = CreateMiningGloves; - private static readonly ConstructCallback GargoylesPickaxe = CreateGargoylesPickaxe; - private static readonly ConstructCallback ProspectorsTool = CreateProspectorsTool; - private static readonly ConstructCallback PowderOfTemperament = CreatePowderOfTemperament; - private static readonly ConstructCallback RunicHammer = CreateRunicHammer; - private static readonly ConstructCallback PowerScroll = CreatePowerScroll; - private static readonly ConstructCallback ColoredAnvil = CreateColoredAnvil; - private static readonly ConstructCallback AncientHammer = CreateAncientHammer; - - private static Item CreateSturdyShovel( int type ) - { - return new SturdyShovel(); - } - - private static Item CreateSturdyPickaxe( int type ) - { - return new SturdyPickaxe(); - } - - private static Item CreateMiningGloves( int type ) - { - if ( type == 1 ) - return new LeatherGlovesOfMining( 1 ); - if ( type == 3 ) - return new StuddedGlovesOfMining( 3 ); - if ( type == 5 ) - return new RingmailGlovesOfMining( 5 ); - - throw new InvalidOperationException(); - } - - private static Item CreateGargoylesPickaxe( int type ) - { - return new GargoylesPickaxe(); - } - - private static Item CreateProspectorsTool( int type ) - { - return new ProspectorsTool(); - } - - private static Item CreatePowderOfTemperament( int type ) - { - return new PowderOfTemperament(); - } - - private static Item CreateRunicHammer( int type ) - { - if ( type >= 1 && type <= 8 ) - return new RunicHammer( CraftResource.Iron + type, Core.AOS ? ( 55 - (type*5) ) : 50 ); - - throw new InvalidOperationException(); - } - - private static Item CreatePowerScroll( int type ) - { - if ( type == 5 || type == 10 || type == 15 || type == 20 ) - return new PowerScroll( SkillName.Blacksmith, 100 + type ); - - throw new InvalidOperationException(); - } - - private static Item CreateColoredAnvil( int type ) - { - // Generate an anvil deed, not an actual anvil. - //return new ColoredAnvilDeed(); - - return new ColoredAnvil(); - } - - private static Item CreateAncientHammer( int type ) - { - if ( type == 10 || type == 15 || type == 30 || type == 60 ) - return new AncientSmithyHammer( type ); - - throw new InvalidOperationException(); - } - #endregion - - public static readonly SmithRewardCalculator Instance = new SmithRewardCalculator(); - - private RewardType[] m_Types = { - // Armors - new RewardType( 200, typeof( RingmailGloves ), typeof( RingmailChest ), typeof( RingmailArms ), typeof( RingmailLegs ) ), - new RewardType( 300, typeof( ChainCoif ), typeof( ChainLegs ), typeof( ChainChest ) ), - new RewardType( 400, typeof( PlateArms ), typeof( PlateLegs ), typeof( PlateHelm ), typeof( PlateGorget ), typeof( PlateGloves ), typeof( PlateChest ) ), - - // Weapons - new RewardType( 200, typeof( Bardiche ), typeof( Halberd ) ), - new RewardType( 300, typeof( Dagger ), typeof( ShortSpear ), typeof( Spear ), typeof( WarFork ), typeof( Kryss ) ), //OSI put the dagger in there. Odd, ain't it. - new RewardType( 350, typeof( Axe ), typeof( BattleAxe ), typeof( DoubleAxe ), typeof( ExecutionersAxe ), typeof( LargeBattleAxe ), typeof( TwoHandedAxe ) ), - new RewardType( 350, typeof( Broadsword ), typeof( Cutlass ), typeof( Katana ), typeof( Longsword ), typeof( Scimitar ), /*typeof( ThinLongsword ),*/ typeof( VikingSword ) ), - new RewardType( 350, typeof( WarAxe ), typeof( HammerPick ), typeof( Mace ), typeof( Maul ), typeof( WarHammer ), typeof( WarMace ) ) - }; - - public override int ComputePoints( int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type ) - { - int points = 0; - - if ( quantity == 10 ) - points += 10; - else if ( quantity == 15 ) - points += 25; - else if ( quantity == 20 ) - points += 50; - - if ( exceptional ) - points += 200; - - if ( itemCount > 1 ) - points += LookupTypePoints( m_Types, type ); - - if ( material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite ) - points += 200 + (50 * (material - BulkMaterialType.DullCopper)); - - return points; - } - - private static int[][][] m_GoldTable = { - new[] // 1-part (regular) - { - new[]{ 150, 250, 250, 400, 400, 750, 750, 1200, 1200 }, - new[]{ 225, 375, 375, 600, 600, 1125, 1125, 1800, 1800 }, - new[]{ 300, 500, 750, 800, 1050, 1500, 2250, 2400, 4000 } - }, - new[] // 1-part (exceptional) - { - new[]{ 250, 400, 400, 750, 750, 1500, 1500, 3000, 3000 }, - new[]{ 375, 600, 600, 1125, 1125, 2250, 2250, 4500, 4500 }, - new[]{ 500, 800, 1200, 1500, 2500, 3000, 6000, 6000, 12000 } - }, - new[] // Ringmail (regular) - { - new[]{ 3000, 5000, 5000, 7500, 7500, 10000, 10000, 15000, 15000 }, - new[]{ 4500, 7500, 7500, 11250, 11500, 15000, 15000, 22500, 22500 }, - new[]{ 6000, 10000, 15000, 15000, 20000, 20000, 30000, 30000, 50000 } - }, - new[] // Ringmail (exceptional) - { - new[]{ 5000, 10000, 10000, 15000, 15000, 25000, 25000, 50000, 50000 }, - new[]{ 7500, 15000, 15000, 22500, 22500, 37500, 37500, 75000, 75000 }, - new[]{ 10000, 20000, 30000, 30000, 50000, 50000, 100000, 100000, 200000 } - }, - new[] // Chainmail (regular) - { - new[]{ 4000, 7500, 7500, 10000, 10000, 15000, 15000, 25000, 25000 }, - new[]{ 6000, 11250, 11250, 15000, 15000, 22500, 22500, 37500, 37500 }, - new[]{ 8000, 15000, 20000, 20000, 30000, 30000, 50000, 50000, 100000 } - }, - new[] // Chainmail (exceptional) - { - new[]{ 7500, 15000, 15000, 25000, 25000, 50000, 50000, 100000, 100000 }, - new[]{ 11250, 22500, 22500, 37500, 37500, 75000, 75000, 150000, 150000 }, - new[]{ 15000, 30000, 50000, 50000, 100000, 100000, 200000, 200000, 200000 } - }, - new[] // Platemail (regular) - { - new[]{ 5000, 10000, 10000, 15000, 15000, 25000, 25000, 50000, 50000 }, - new[]{ 7500, 15000, 15000, 22500, 22500, 37500, 37500, 75000, 75000 }, - new[]{ 10000, 20000, 30000, 30000, 50000, 50000, 100000, 100000, 200000 } - }, - new[] // Platemail (exceptional) - { - new[]{ 10000, 25000, 25000, 50000, 50000, 100000, 100000, 100000, 100000 }, - new[]{ 15000, 37500, 37500, 75000, 75000, 150000, 150000, 150000, 150000 }, - new[]{ 20000, 50000, 100000, 100000, 200000, 200000, 200000, 200000, 200000 } - }, - new[] // 2-part weapons (regular) - { - new[]{ 3000, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 4500, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 6000, 0, 0, 0, 0, 0, 0, 0, 0 } - }, - new[] // 2-part weapons (exceptional) - { - new[]{ 5000, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 7500, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 10000, 0, 0, 0, 0, 0, 0, 0, 0 } - }, - new[] // 5-part weapons (regular) - { - new[]{ 4000, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 6000, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 8000, 0, 0, 0, 0, 0, 0, 0, 0 } - }, - new[] // 5-part weapons (exceptional) - { - new[]{ 7500, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 11250, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 15000, 0, 0, 0, 0, 0, 0, 0, 0 } - }, - new[] // 6-part weapons (regular) - { - new[]{ 4000, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 6000, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 10000, 0, 0, 0, 0, 0, 0, 0, 0 } - }, - new[] // 6-part weapons (exceptional) - { - new[]{ 7500, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 11250, 0, 0, 0, 0, 0, 0, 0, 0 }, - new[]{ 15000, 0, 0, 0, 0, 0, 0, 0, 0 } - } - }; - - private int ComputeType( Type type, int itemCount ) - { - // Item count of 1 means it's a small BOD. - if ( itemCount == 1 ) - return 0; - - int typeIdx; - - // Loop through the RewardTypes defined earlier and find the correct one. - for ( typeIdx = 0; typeIdx < 7; ++typeIdx ) - { - if ( m_Types[typeIdx].Contains( type ) ) - break; - } - - // Types 5, 6 and 7 are Large Weapon BODs with the same rewards. - if ( typeIdx > 5 ) - typeIdx = 5; - - return ( typeIdx + 1 ) * 2; - } - - public override int ComputeGold( int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type ) - { - int[][][] goldTable = m_GoldTable; - - int typeIndex = ComputeType( type, itemCount ); - int quanIndex = ( quantity == 20 ? 2 : quantity == 15 ? 1 : 0 ); - int mtrlIndex = ( material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite ) ? 1 + (int)(material - BulkMaterialType.DullCopper) : 0; - - if ( exceptional ) - typeIndex++; - - int gold = goldTable[typeIndex][quanIndex][mtrlIndex]; - - int min = (gold * 9) / 10; - int max = (gold * 10) / 9; - - return Utility.RandomMinMax( min, max ); - } - - public SmithRewardCalculator() - { - Groups = new[] - { - new RewardGroup( 0, new RewardItem( 1, SturdyShovel ) ), - new RewardGroup( 25, new RewardItem( 1, SturdyPickaxe ) ), - new RewardGroup( 50, new RewardItem( 45, SturdyShovel ), new RewardItem( 45, SturdyPickaxe ), new RewardItem( 10, MiningGloves, 1 ) ), - new RewardGroup( 200, new RewardItem( 45, GargoylesPickaxe ), new RewardItem( 45, ProspectorsTool ), new RewardItem( 10, MiningGloves, 3 ) ), - new RewardGroup( 400, new RewardItem( 2, GargoylesPickaxe ), new RewardItem( 2, ProspectorsTool ), new RewardItem( 1, PowderOfTemperament ) ), - new RewardGroup( 450, new RewardItem( 9, PowderOfTemperament ), new RewardItem( 1, MiningGloves, 5 ) ), - new RewardGroup( 500, new RewardItem( 1, RunicHammer, 1 ) ), - new RewardGroup( 550, new RewardItem( 3, RunicHammer, 1 ), new RewardItem( 2, RunicHammer, 2 ) ), - new RewardGroup( 600, new RewardItem( 1, RunicHammer, 2 ) ), - new RewardGroup( 625, new RewardItem( 3, RunicHammer, 2 ), new RewardItem( 6, PowerScroll, 5 ), new RewardItem( 1, ColoredAnvil ) ), - new RewardGroup( 650, new RewardItem( 1, RunicHammer, 3 ) ), - new RewardGroup( 675, new RewardItem( 1, ColoredAnvil ), new RewardItem( 6, PowerScroll, 10 ), new RewardItem( 3, RunicHammer, 3 ) ), - new RewardGroup( 700, new RewardItem( 1, RunicHammer, 4 ) ), - new RewardGroup( 750, new RewardItem( 1, AncientHammer, 10 ) ), - new RewardGroup( 800, new RewardItem( 1, PowerScroll, 15 ) ), - new RewardGroup( 850, new RewardItem( 1, AncientHammer, 15 ) ), - new RewardGroup( 900, new RewardItem( 1, PowerScroll, 20 ) ), - new RewardGroup( 950, new RewardItem( 1, RunicHammer, 5 ) ), - new RewardGroup( 1000, new RewardItem( 1, AncientHammer, 30 ) ), - new RewardGroup( 1050, new RewardItem( 1, RunicHammer, 6 ) ), - new RewardGroup( 1100, new RewardItem( 1, AncientHammer, 60 ) ), - new RewardGroup( 1150, new RewardItem( 1, RunicHammer, 7 ) ), - new RewardGroup( 1200, new RewardItem( 1, RunicHammer, 8 ) ) - }; - } - } - - public sealed class TailorRewardCalculator : RewardCalculator - { - #region Constructors - private static readonly ConstructCallback Cloth = CreateCloth; - private static readonly ConstructCallback Sandals = CreateSandals; - private static readonly ConstructCallback StretchedHide = CreateStretchedHide; - private static readonly ConstructCallback RunicKit = CreateRunicKit; - private static readonly ConstructCallback Tapestry = CreateTapestry; - private static readonly ConstructCallback PowerScroll = CreatePowerScroll; - private static readonly ConstructCallback BearRug = CreateBearRug; - private static readonly ConstructCallback ClothingBlessDeed = CreateCBD; - - private static int[][] m_ClothHues = { - new[]{ 0x483, 0x48C, 0x488, 0x48A }, - new[]{ 0x495, 0x48B, 0x486, 0x485 }, - new[]{ 0x48D, 0x490, 0x48E, 0x491 }, - new[]{ 0x48F, 0x494, 0x484, 0x497 }, - new[]{ 0x489, 0x47F, 0x482, 0x47E } - }; - - private static Item CreateCloth( int type ) - { - if ( type >= 0 && type < m_ClothHues.Length ) - { - UncutCloth cloth = new UncutCloth( 100 ); - cloth.Hue = m_ClothHues[type][Utility.Random( m_ClothHues[type].Length )]; - return cloth; - } - - throw new InvalidOperationException(); - } - - private static int[] m_SandalHues = { - 0x489, 0x47F, 0x482, - 0x47E, 0x48F, 0x494, - 0x484, 0x497 - }; - - private static Item CreateSandals( int type ) - { - return new Sandals( m_SandalHues[Utility.Random( m_SandalHues.Length )] ); - } - - private static Item CreateStretchedHide( int type ) - { - switch ( Utility.Random( 4 ) ) - { - default: - case 0: return new SmallStretchedHideEastDeed(); - case 1: return new SmallStretchedHideSouthDeed(); - case 2: return new MediumStretchedHideEastDeed(); - case 3: return new MediumStretchedHideSouthDeed(); - } - } - - private static Item CreateTapestry( int type ) - { - switch ( Utility.Random( 4 ) ) - { - default: - case 0: return new LightFlowerTapestryEastDeed(); - case 1: return new LightFlowerTapestrySouthDeed(); - case 2: return new DarkFlowerTapestryEastDeed(); - case 3: return new DarkFlowerTapestrySouthDeed(); - } - } - - private static Item CreateBearRug( int type ) - { - switch ( Utility.Random( 4 ) ) - { - default: - case 0: return new BrownBearRugEastDeed(); - case 1: return new BrownBearRugSouthDeed(); - case 2: return new PolarBearRugEastDeed(); - case 3: return new PolarBearRugSouthDeed(); - } - } - - private static Item CreateRunicKit( int type ) - { - if ( type >= 1 && type <= 3 ) - return new RunicSewingKit( CraftResource.RegularLeather + type, 60 - (type*15) ); - - throw new InvalidOperationException(); - } - - private static Item CreatePowerScroll( int type ) - { - if ( type == 5 || type == 10 || type == 15 || type == 20 ) - return new PowerScroll( SkillName.Tailoring, 100 + type ); - - throw new InvalidOperationException(); - } - - private static Item CreateCBD( int type ) - { - return new ClothingBlessDeed(); - } - #endregion - - public static readonly TailorRewardCalculator Instance = new TailorRewardCalculator(); - - public override int ComputePoints( int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type ) - { - int points = 0; - - if ( quantity == 10 ) - points += 10; - else if ( quantity == 15 ) - points += 25; - else if ( quantity == 20 ) - points += 50; - - if ( exceptional ) - points += 100; - - if ( itemCount == 4 ) - points += 300; - else if ( itemCount == 5 ) - points += 400; - else if ( itemCount == 6 ) - points += 500; - - if ( material == BulkMaterialType.Spined ) - points += 50; - else if ( material == BulkMaterialType.Horned ) - points += 100; - else if ( material == BulkMaterialType.Barbed ) - points += 150; - - return points; - } - - private static int[][][] m_AosGoldTable = { - new[] // 1-part (regular) - { - new[]{ 150, 150, 300, 300 }, - new[]{ 225, 225, 450, 450 }, - new[]{ 300, 400, 600, 750 } - }, - new[] // 1-part (exceptional) - { - new[]{ 300, 300, 600, 600 }, - new[]{ 450, 450, 900, 900 }, - new[]{ 600, 750, 1200, 1800 } - }, - new[] // 4-part (regular) - { - new[]{ 4000, 4000, 5000, 5000 }, - new[]{ 6000, 6000, 7500, 7500 }, - new[]{ 8000, 10000, 10000, 15000 } - }, - new[] // 4-part (exceptional) - { - new[]{ 5000, 5000, 7500, 7500 }, - new[]{ 7500, 7500, 11250, 11250 }, - new[]{ 10000, 15000, 15000, 20000 } - }, - new[] // 5-part (regular) - { - new[]{ 5000, 5000, 7500, 7500 }, - new[]{ 7500, 7500, 11250, 11250 }, - new[]{ 10000, 15000, 15000, 20000 } - }, - new[] // 5-part (exceptional) - { - new[]{ 7500, 7500, 10000, 10000 }, - new[]{ 11250, 11250, 15000, 15000 }, - new[]{ 15000, 20000, 20000, 30000 } - }, - new[] // 6-part (regular) - { - new[]{ 7500, 7500, 10000, 10000 }, - new[]{ 11250, 11250, 15000, 15000 }, - new[]{ 15000, 20000, 20000, 30000 } - }, - new[] // 6-part (exceptional) - { - new[]{ 10000, 10000, 15000, 15000 }, - new[]{ 15000, 15000, 22500, 22500 }, - new[]{ 20000, 30000, 30000, 50000 } - } - }; - - private static int[][][] m_OldGoldTable = { - new[] // 1-part (regular) - { - new[]{ 150, 150, 300, 300 }, - new[]{ 225, 225, 450, 450 }, - new[]{ 300, 400, 600, 750 } - }, - new[] // 1-part (exceptional) - { - new[]{ 300, 300, 600, 600 }, - new[]{ 450, 450, 900, 900 }, - new[]{ 600, 750, 1200, 1800 } - }, - new[] // 4-part (regular) - { - new[]{ 3000, 3000, 4000, 4000 }, - new[]{ 4500, 4500, 6000, 6000 }, - new[]{ 6000, 8000, 8000, 10000 } - }, - new[] // 4-part (exceptional) - { - new[]{ 4000, 4000, 5000, 5000 }, - new[]{ 6000, 6000, 7500, 7500 }, - new[]{ 8000, 10000, 10000, 15000 } - }, - new[] // 5-part (regular) - { - new[]{ 4000, 4000, 5000, 5000 }, - new[]{ 6000, 6000, 7500, 7500 }, - new[]{ 8000, 10000, 10000, 15000 } - }, - new[] // 5-part (exceptional) - { - new[]{ 5000, 5000, 7500, 7500 }, - new[]{ 7500, 7500, 11250, 11250 }, - new[]{ 10000, 15000, 15000, 20000 } - }, - new[] // 6-part (regular) - { - new[]{ 5000, 5000, 7500, 7500 }, - new[]{ 7500, 7500, 11250, 11250 }, - new[]{ 10000, 15000, 15000, 20000 } - }, - new[] // 6-part (exceptional) - { - new[]{ 7500, 7500, 10000, 10000 }, - new[]{ 11250, 11250, 15000, 15000 }, - new[]{ 15000, 20000, 20000, 30000 } - } - }; - - public override int ComputeGold( int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type ) - { - int[][][] goldTable = ( Core.AOS ? m_AosGoldTable : m_OldGoldTable ); - - int typeIndex = (( itemCount == 6 ? 3 : itemCount == 5 ? 2 : itemCount == 4 ? 1 : 0 ) * 2) + (exceptional ? 1 : 0); - int quanIndex = ( quantity == 20 ? 2 : quantity == 15 ? 1 : 0 ); - int mtrlIndex = ( material == BulkMaterialType.Barbed ? 3 : material == BulkMaterialType.Horned ? 2 : material == BulkMaterialType.Spined ? 1 : 0 ); - - int gold = goldTable[typeIndex][quanIndex][mtrlIndex]; - - int min = (gold * 9) / 10; - int max = (gold * 10) / 9; - - return Utility.RandomMinMax( min, max ); - } - - public TailorRewardCalculator() - { - Groups = new[] - { - new RewardGroup( 0, new RewardItem( 1, Cloth, 0 ) ), - new RewardGroup( 50, new RewardItem( 1, Cloth, 1 ) ), - new RewardGroup( 100, new RewardItem( 1, Cloth, 2 ) ), - new RewardGroup( 150, new RewardItem( 9, Cloth, 3 ), new RewardItem( 1, Sandals ) ), - new RewardGroup( 200, new RewardItem( 4, Cloth, 4 ), new RewardItem( 1, Sandals ) ), - new RewardGroup( 300, new RewardItem( 1, StretchedHide ) ), - new RewardGroup( 350, new RewardItem( 1, RunicKit, 1 ) ), - new RewardGroup( 400, new RewardItem( 2, PowerScroll, 5 ), new RewardItem( 3, Tapestry ) ), - new RewardGroup( 450, new RewardItem( 1, BearRug ) ), - new RewardGroup( 500, new RewardItem( 1, PowerScroll, 10 ) ), - new RewardGroup( 550, new RewardItem( 1, ClothingBlessDeed ) ), - new RewardGroup( 575, new RewardItem( 1, PowerScroll, 15 ) ), - new RewardGroup( 600, new RewardItem( 1, RunicKit, 2 ) ), - new RewardGroup( 650, new RewardItem( 1, PowerScroll, 20 ) ), - new RewardGroup( 700, new RewardItem( 1, RunicKit, 3 ) ) - }; - } - } + public RewardItem(int weight, ConstructCallback constructor, int type) + { + Weight = weight; + Constructor = constructor; + Type = type; + } + + public int Weight{ get; } + + public ConstructCallback Constructor{ get; } + + public int Type{ get; } + + public Item Construct() + { + try + { + return Constructor(Type); + } + catch + { + return null; + } + } + } + + public sealed class RewardGroup + { + public RewardGroup(int points, params RewardItem[] items) + { + Points = points; + Items = items; + } + + public int Points{ get; } + + public RewardItem[] Items{ get; } + + public RewardItem AcquireItem() + { + if (Items.Length == 0) + return null; + if (Items.Length == 1) + return Items[0]; + + int totalWeight = 0; + + for (int i = 0; i < Items.Length; ++i) + totalWeight += Items[i].Weight; + + int randomWeight = Utility.Random(totalWeight); + + for (int i = 0; i < Items.Length; ++i) + { + RewardItem item = Items[i]; + + if (randomWeight < item.Weight) + return item; + + randomWeight -= item.Weight; + } + + return null; + } + } + + public abstract class RewardCalculator + { + public RewardGroup[] Groups{ get; set; } + + public abstract int ComputePoints(int quantity, bool exceptional, BulkMaterialType material, int itemCount, + Type type); + + public abstract int ComputeGold(int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type); + + public virtual int ComputeFame(SmallBOD bod) + { + int points = ComputePoints(bod) / 50; + + return points * points; + } + + public virtual int ComputeFame(LargeBOD bod) + { + int points = ComputePoints(bod) / 50; + + return points * points; + } + + public virtual int ComputePoints(SmallBOD bod) + { + return ComputePoints(bod.AmountMax, bod.RequireExceptional, bod.Material, 1, bod.Type); + } + + public virtual int ComputePoints(LargeBOD bod) + { + return ComputePoints(bod.AmountMax, bod.RequireExceptional, bod.Material, bod.Entries.Length, + bod.Entries[0].Details.Type); + } + + public virtual int ComputeGold(SmallBOD bod) + { + return ComputeGold(bod.AmountMax, bod.RequireExceptional, bod.Material, 1, bod.Type); + } + + public virtual int ComputeGold(LargeBOD bod) + { + return ComputeGold(bod.AmountMax, bod.RequireExceptional, bod.Material, bod.Entries.Length, + bod.Entries[0].Details.Type); + } + + public virtual RewardGroup LookupRewards(int points) + { + for (int i = Groups.Length - 1; i >= 1; --i) + { + RewardGroup group = Groups[i]; + + if (points >= group.Points) + return group; + } + + return Groups[0]; + } + + public virtual int LookupTypePoints(RewardType[] types, Type type) + { + for (int i = 0; i < types.Length; ++i) + if (types[i].Contains(type)) + return types[i].Points; + + return 0; + } + } + + public sealed class SmithRewardCalculator : RewardCalculator + { + private static readonly ConstructCallback SturdyShovel = CreateSturdyShovel; + private static readonly ConstructCallback SturdyPickaxe = CreateSturdyPickaxe; + private static readonly ConstructCallback MiningGloves = CreateMiningGloves; + private static readonly ConstructCallback GargoylesPickaxe = CreateGargoylesPickaxe; + private static readonly ConstructCallback ProspectorsTool = CreateProspectorsTool; + private static readonly ConstructCallback PowderOfTemperament = CreatePowderOfTemperament; + private static readonly ConstructCallback RunicHammer = CreateRunicHammer; + private static readonly ConstructCallback PowerScroll = CreatePowerScroll; + private static readonly ConstructCallback ColoredAnvil = CreateColoredAnvil; + private static readonly ConstructCallback AncientHammer = CreateAncientHammer; + public static readonly SmithRewardCalculator Instance = new SmithRewardCalculator(); + + private static int[][][] m_GoldTable = + { + new[] // 1-part (regular) + { + new[] { 150, 250, 250, 400, 400, 750, 750, 1200, 1200 }, + new[] { 225, 375, 375, 600, 600, 1125, 1125, 1800, 1800 }, + new[] { 300, 500, 750, 800, 1050, 1500, 2250, 2400, 4000 } + }, + new[] // 1-part (exceptional) + { + new[] { 250, 400, 400, 750, 750, 1500, 1500, 3000, 3000 }, + new[] { 375, 600, 600, 1125, 1125, 2250, 2250, 4500, 4500 }, + new[] { 500, 800, 1200, 1500, 2500, 3000, 6000, 6000, 12000 } + }, + new[] // Ringmail (regular) + { + new[] { 3000, 5000, 5000, 7500, 7500, 10000, 10000, 15000, 15000 }, + new[] { 4500, 7500, 7500, 11250, 11500, 15000, 15000, 22500, 22500 }, + new[] { 6000, 10000, 15000, 15000, 20000, 20000, 30000, 30000, 50000 } + }, + new[] // Ringmail (exceptional) + { + new[] { 5000, 10000, 10000, 15000, 15000, 25000, 25000, 50000, 50000 }, + new[] { 7500, 15000, 15000, 22500, 22500, 37500, 37500, 75000, 75000 }, + new[] { 10000, 20000, 30000, 30000, 50000, 50000, 100000, 100000, 200000 } + }, + new[] // Chainmail (regular) + { + new[] { 4000, 7500, 7500, 10000, 10000, 15000, 15000, 25000, 25000 }, + new[] { 6000, 11250, 11250, 15000, 15000, 22500, 22500, 37500, 37500 }, + new[] { 8000, 15000, 20000, 20000, 30000, 30000, 50000, 50000, 100000 } + }, + new[] // Chainmail (exceptional) + { + new[] { 7500, 15000, 15000, 25000, 25000, 50000, 50000, 100000, 100000 }, + new[] { 11250, 22500, 22500, 37500, 37500, 75000, 75000, 150000, 150000 }, + new[] { 15000, 30000, 50000, 50000, 100000, 100000, 200000, 200000, 200000 } + }, + new[] // Platemail (regular) + { + new[] { 5000, 10000, 10000, 15000, 15000, 25000, 25000, 50000, 50000 }, + new[] { 7500, 15000, 15000, 22500, 22500, 37500, 37500, 75000, 75000 }, + new[] { 10000, 20000, 30000, 30000, 50000, 50000, 100000, 100000, 200000 } + }, + new[] // Platemail (exceptional) + { + new[] { 10000, 25000, 25000, 50000, 50000, 100000, 100000, 100000, 100000 }, + new[] { 15000, 37500, 37500, 75000, 75000, 150000, 150000, 150000, 150000 }, + new[] { 20000, 50000, 100000, 100000, 200000, 200000, 200000, 200000, 200000 } + }, + new[] // 2-part weapons (regular) + { + new[] { 3000, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 4500, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 6000, 0, 0, 0, 0, 0, 0, 0, 0 } + }, + new[] // 2-part weapons (exceptional) + { + new[] { 5000, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 7500, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 10000, 0, 0, 0, 0, 0, 0, 0, 0 } + }, + new[] // 5-part weapons (regular) + { + new[] { 4000, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 6000, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 8000, 0, 0, 0, 0, 0, 0, 0, 0 } + }, + new[] // 5-part weapons (exceptional) + { + new[] { 7500, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 11250, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 15000, 0, 0, 0, 0, 0, 0, 0, 0 } + }, + new[] // 6-part weapons (regular) + { + new[] { 4000, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 6000, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 10000, 0, 0, 0, 0, 0, 0, 0, 0 } + }, + new[] // 6-part weapons (exceptional) + { + new[] { 7500, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 11250, 0, 0, 0, 0, 0, 0, 0, 0 }, + new[] { 15000, 0, 0, 0, 0, 0, 0, 0, 0 } + } + }; + + private RewardType[] m_Types = + { + // Armors + new RewardType(200, typeof(RingmailGloves), typeof(RingmailChest), typeof(RingmailArms), typeof(RingmailLegs)), + new RewardType(300, typeof(ChainCoif), typeof(ChainLegs), typeof(ChainChest)), + new RewardType(400, typeof(PlateArms), typeof(PlateLegs), typeof(PlateHelm), typeof(PlateGorget), + typeof(PlateGloves), typeof(PlateChest)), + + // Weapons + new RewardType(200, typeof(Bardiche), typeof(Halberd)), + new RewardType(300, typeof(Dagger), typeof(ShortSpear), typeof(Spear), typeof(WarFork), + typeof(Kryss)), //OSI put the dagger in there. Odd, ain't it. + new RewardType(350, typeof(Axe), typeof(BattleAxe), typeof(DoubleAxe), typeof(ExecutionersAxe), + typeof(LargeBattleAxe), typeof(TwoHandedAxe)), + new RewardType(350, typeof(Broadsword), typeof(Cutlass), typeof(Katana), typeof(Longsword), + typeof(Scimitar), /*typeof( ThinLongsword ),*/ typeof(VikingSword)), + new RewardType(350, typeof(WarAxe), typeof(HammerPick), typeof(Mace), typeof(Maul), typeof(WarHammer), + typeof(WarMace)) + }; + + public SmithRewardCalculator() + { + Groups = new[] + { + new RewardGroup(0, new RewardItem(1, SturdyShovel)), + new RewardGroup(25, new RewardItem(1, SturdyPickaxe)), + new RewardGroup(50, new RewardItem(45, SturdyShovel), new RewardItem(45, SturdyPickaxe), + new RewardItem(10, MiningGloves, 1)), + new RewardGroup(200, new RewardItem(45, GargoylesPickaxe), new RewardItem(45, ProspectorsTool), + new RewardItem(10, MiningGloves, 3)), + new RewardGroup(400, new RewardItem(2, GargoylesPickaxe), new RewardItem(2, ProspectorsTool), + new RewardItem(1, PowderOfTemperament)), + new RewardGroup(450, new RewardItem(9, PowderOfTemperament), new RewardItem(1, MiningGloves, 5)), + new RewardGroup(500, new RewardItem(1, RunicHammer, 1)), + new RewardGroup(550, new RewardItem(3, RunicHammer, 1), new RewardItem(2, RunicHammer, 2)), + new RewardGroup(600, new RewardItem(1, RunicHammer, 2)), + new RewardGroup(625, new RewardItem(3, RunicHammer, 2), new RewardItem(6, PowerScroll, 5), + new RewardItem(1, ColoredAnvil)), + new RewardGroup(650, new RewardItem(1, RunicHammer, 3)), + new RewardGroup(675, new RewardItem(1, ColoredAnvil), new RewardItem(6, PowerScroll, 10), + new RewardItem(3, RunicHammer, 3)), + new RewardGroup(700, new RewardItem(1, RunicHammer, 4)), + new RewardGroup(750, new RewardItem(1, AncientHammer, 10)), + new RewardGroup(800, new RewardItem(1, PowerScroll, 15)), + new RewardGroup(850, new RewardItem(1, AncientHammer, 15)), + new RewardGroup(900, new RewardItem(1, PowerScroll, 20)), + new RewardGroup(950, new RewardItem(1, RunicHammer, 5)), + new RewardGroup(1000, new RewardItem(1, AncientHammer, 30)), + new RewardGroup(1050, new RewardItem(1, RunicHammer, 6)), + new RewardGroup(1100, new RewardItem(1, AncientHammer, 60)), + new RewardGroup(1150, new RewardItem(1, RunicHammer, 7)), + new RewardGroup(1200, new RewardItem(1, RunicHammer, 8)) + }; + } + + public override int ComputePoints(int quantity, bool exceptional, BulkMaterialType material, int itemCount, + Type type) + { + int points = 0; + + if (quantity == 10) + points += 10; + else if (quantity == 15) + points += 25; + else if (quantity == 20) + points += 50; + + if (exceptional) + points += 200; + + if (itemCount > 1) + points += LookupTypePoints(m_Types, type); + + if (material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite) + points += 200 + 50 * (material - BulkMaterialType.DullCopper); + + return points; + } + + private int ComputeType(Type type, int itemCount) + { + // Item count of 1 means it's a small BOD. + if (itemCount == 1) + return 0; + + int typeIdx; + + // Loop through the RewardTypes defined earlier and find the correct one. + for (typeIdx = 0; typeIdx < 7; ++typeIdx) + if (m_Types[typeIdx].Contains(type)) + break; + + // Types 5, 6 and 7 are Large Weapon BODs with the same rewards. + if (typeIdx > 5) + typeIdx = 5; + + return (typeIdx + 1) * 2; + } + + public override int ComputeGold(int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type) + { + int[][][] goldTable = m_GoldTable; + + int typeIndex = ComputeType(type, itemCount); + int quanIndex = quantity == 20 ? 2 : quantity == 15 ? 1 : 0; + int mtrlIndex = material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite + ? 1 + (material - BulkMaterialType.DullCopper) + : 0; + + if (exceptional) + typeIndex++; + + int gold = goldTable[typeIndex][quanIndex][mtrlIndex]; + + int min = gold * 9 / 10; + int max = gold * 10 / 9; + + return Utility.RandomMinMax(min, max); + } + + #region Constructors + + private static Item CreateSturdyShovel(int type) + { + return new SturdyShovel(); + } + + private static Item CreateSturdyPickaxe(int type) + { + return new SturdyPickaxe(); + } + + private static Item CreateMiningGloves(int type) + { + if (type == 1) + return new LeatherGlovesOfMining(1); + if (type == 3) + return new StuddedGlovesOfMining(3); + if (type == 5) + return new RingmailGlovesOfMining(5); + + throw new InvalidOperationException(); + } + + private static Item CreateGargoylesPickaxe(int type) + { + return new GargoylesPickaxe(); + } + + private static Item CreateProspectorsTool(int type) + { + return new ProspectorsTool(); + } + + private static Item CreatePowderOfTemperament(int type) + { + return new PowderOfTemperament(); + } + + private static Item CreateRunicHammer(int type) + { + if (type >= 1 && type <= 8) + return new RunicHammer(CraftResource.Iron + type, Core.AOS ? 55 - type * 5 : 50); + + throw new InvalidOperationException(); + } + + private static Item CreatePowerScroll(int type) + { + if (type == 5 || type == 10 || type == 15 || type == 20) + return new PowerScroll(SkillName.Blacksmith, 100 + type); + + throw new InvalidOperationException(); + } + + private static Item CreateColoredAnvil(int type) + { + // Generate an anvil deed, not an actual anvil. + //return new ColoredAnvilDeed(); + + return new ColoredAnvil(); + } + + private static Item CreateAncientHammer(int type) + { + if (type == 10 || type == 15 || type == 30 || type == 60) + return new AncientSmithyHammer(type); + + throw new InvalidOperationException(); + } + + #endregion + } + + public sealed class TailorRewardCalculator : RewardCalculator + { + private static readonly ConstructCallback Cloth = CreateCloth; + private static readonly ConstructCallback Sandals = CreateSandals; + private static readonly ConstructCallback StretchedHide = CreateStretchedHide; + private static readonly ConstructCallback RunicKit = CreateRunicKit; + private static readonly ConstructCallback Tapestry = CreateTapestry; + private static readonly ConstructCallback PowerScroll = CreatePowerScroll; + private static readonly ConstructCallback BearRug = CreateBearRug; + private static readonly ConstructCallback ClothingBlessDeed = CreateCBD; + public static readonly TailorRewardCalculator Instance = new TailorRewardCalculator(); + + private static int[][][] m_AosGoldTable = + { + new[] // 1-part (regular) + { + new[] { 150, 150, 300, 300 }, + new[] { 225, 225, 450, 450 }, + new[] { 300, 400, 600, 750 } + }, + new[] // 1-part (exceptional) + { + new[] { 300, 300, 600, 600 }, + new[] { 450, 450, 900, 900 }, + new[] { 600, 750, 1200, 1800 } + }, + new[] // 4-part (regular) + { + new[] { 4000, 4000, 5000, 5000 }, + new[] { 6000, 6000, 7500, 7500 }, + new[] { 8000, 10000, 10000, 15000 } + }, + new[] // 4-part (exceptional) + { + new[] { 5000, 5000, 7500, 7500 }, + new[] { 7500, 7500, 11250, 11250 }, + new[] { 10000, 15000, 15000, 20000 } + }, + new[] // 5-part (regular) + { + new[] { 5000, 5000, 7500, 7500 }, + new[] { 7500, 7500, 11250, 11250 }, + new[] { 10000, 15000, 15000, 20000 } + }, + new[] // 5-part (exceptional) + { + new[] { 7500, 7500, 10000, 10000 }, + new[] { 11250, 11250, 15000, 15000 }, + new[] { 15000, 20000, 20000, 30000 } + }, + new[] // 6-part (regular) + { + new[] { 7500, 7500, 10000, 10000 }, + new[] { 11250, 11250, 15000, 15000 }, + new[] { 15000, 20000, 20000, 30000 } + }, + new[] // 6-part (exceptional) + { + new[] { 10000, 10000, 15000, 15000 }, + new[] { 15000, 15000, 22500, 22500 }, + new[] { 20000, 30000, 30000, 50000 } + } + }; + + private static int[][][] m_OldGoldTable = + { + new[] // 1-part (regular) + { + new[] { 150, 150, 300, 300 }, + new[] { 225, 225, 450, 450 }, + new[] { 300, 400, 600, 750 } + }, + new[] // 1-part (exceptional) + { + new[] { 300, 300, 600, 600 }, + new[] { 450, 450, 900, 900 }, + new[] { 600, 750, 1200, 1800 } + }, + new[] // 4-part (regular) + { + new[] { 3000, 3000, 4000, 4000 }, + new[] { 4500, 4500, 6000, 6000 }, + new[] { 6000, 8000, 8000, 10000 } + }, + new[] // 4-part (exceptional) + { + new[] { 4000, 4000, 5000, 5000 }, + new[] { 6000, 6000, 7500, 7500 }, + new[] { 8000, 10000, 10000, 15000 } + }, + new[] // 5-part (regular) + { + new[] { 4000, 4000, 5000, 5000 }, + new[] { 6000, 6000, 7500, 7500 }, + new[] { 8000, 10000, 10000, 15000 } + }, + new[] // 5-part (exceptional) + { + new[] { 5000, 5000, 7500, 7500 }, + new[] { 7500, 7500, 11250, 11250 }, + new[] { 10000, 15000, 15000, 20000 } + }, + new[] // 6-part (regular) + { + new[] { 5000, 5000, 7500, 7500 }, + new[] { 7500, 7500, 11250, 11250 }, + new[] { 10000, 15000, 15000, 20000 } + }, + new[] // 6-part (exceptional) + { + new[] { 7500, 7500, 10000, 10000 }, + new[] { 11250, 11250, 15000, 15000 }, + new[] { 15000, 20000, 20000, 30000 } + } + }; + + public TailorRewardCalculator() + { + Groups = new[] + { + new RewardGroup(0, new RewardItem(1, Cloth, 0)), + new RewardGroup(50, new RewardItem(1, Cloth, 1)), + new RewardGroup(100, new RewardItem(1, Cloth, 2)), + new RewardGroup(150, new RewardItem(9, Cloth, 3), new RewardItem(1, Sandals)), + new RewardGroup(200, new RewardItem(4, Cloth, 4), new RewardItem(1, Sandals)), + new RewardGroup(300, new RewardItem(1, StretchedHide)), + new RewardGroup(350, new RewardItem(1, RunicKit, 1)), + new RewardGroup(400, new RewardItem(2, PowerScroll, 5), new RewardItem(3, Tapestry)), + new RewardGroup(450, new RewardItem(1, BearRug)), + new RewardGroup(500, new RewardItem(1, PowerScroll, 10)), + new RewardGroup(550, new RewardItem(1, ClothingBlessDeed)), + new RewardGroup(575, new RewardItem(1, PowerScroll, 15)), + new RewardGroup(600, new RewardItem(1, RunicKit, 2)), + new RewardGroup(650, new RewardItem(1, PowerScroll, 20)), + new RewardGroup(700, new RewardItem(1, RunicKit, 3)) + }; + } + + public override int ComputePoints(int quantity, bool exceptional, BulkMaterialType material, int itemCount, + Type type) + { + int points = 0; + + if (quantity == 10) + points += 10; + else if (quantity == 15) + points += 25; + else if (quantity == 20) + points += 50; + + if (exceptional) + points += 100; + + if (itemCount == 4) + points += 300; + else if (itemCount == 5) + points += 400; + else if (itemCount == 6) + points += 500; + + if (material == BulkMaterialType.Spined) + points += 50; + else if (material == BulkMaterialType.Horned) + points += 100; + else if (material == BulkMaterialType.Barbed) + points += 150; + + return points; + } + + public override int ComputeGold(int quantity, bool exceptional, BulkMaterialType material, int itemCount, Type type) + { + int[][][] goldTable = Core.AOS ? m_AosGoldTable : m_OldGoldTable; + + int typeIndex = (itemCount == 6 ? 3 : itemCount == 5 ? 2 : itemCount == 4 ? 1 : 0) * 2 + (exceptional ? 1 : 0); + int quanIndex = quantity == 20 ? 2 : quantity == 15 ? 1 : 0; + int mtrlIndex = material == BulkMaterialType.Barbed ? 3 : + material == BulkMaterialType.Horned ? 2 : + material == BulkMaterialType.Spined ? 1 : 0; + + int gold = goldTable[typeIndex][quanIndex][mtrlIndex]; + + int min = gold * 9 / 10; + int max = gold * 10 / 9; + + return Utility.RandomMinMax(min, max); + } + + #region Constructors + + private static int[][] m_ClothHues = + { + new[] { 0x483, 0x48C, 0x488, 0x48A }, + new[] { 0x495, 0x48B, 0x486, 0x485 }, + new[] { 0x48D, 0x490, 0x48E, 0x491 }, + new[] { 0x48F, 0x494, 0x484, 0x497 }, + new[] { 0x489, 0x47F, 0x482, 0x47E } + }; + + private static Item CreateCloth(int type) + { + if (type >= 0 && type < m_ClothHues.Length) + { + UncutCloth cloth = new UncutCloth(100); + cloth.Hue = m_ClothHues[type][Utility.Random(m_ClothHues[type].Length)]; + return cloth; + } + + throw new InvalidOperationException(); + } + + private static int[] m_SandalHues = + { + 0x489, 0x47F, 0x482, + 0x47E, 0x48F, 0x494, + 0x484, 0x497 + }; + + private static Item CreateSandals(int type) + { + return new Sandals(m_SandalHues[Utility.Random(m_SandalHues.Length)]); + } + + private static Item CreateStretchedHide(int type) + { + switch (Utility.Random(4)) + { + default: + case 0: return new SmallStretchedHideEastDeed(); + case 1: return new SmallStretchedHideSouthDeed(); + case 2: return new MediumStretchedHideEastDeed(); + case 3: return new MediumStretchedHideSouthDeed(); + } + } + + private static Item CreateTapestry(int type) + { + switch (Utility.Random(4)) + { + default: + case 0: return new LightFlowerTapestryEastDeed(); + case 1: return new LightFlowerTapestrySouthDeed(); + case 2: return new DarkFlowerTapestryEastDeed(); + case 3: return new DarkFlowerTapestrySouthDeed(); + } + } + + private static Item CreateBearRug(int type) + { + switch (Utility.Random(4)) + { + default: + case 0: return new BrownBearRugEastDeed(); + case 1: return new BrownBearRugSouthDeed(); + case 2: return new PolarBearRugEastDeed(); + case 3: return new PolarBearRugSouthDeed(); + } + } + + private static Item CreateRunicKit(int type) + { + if (type >= 1 && type <= 3) + return new RunicSewingKit(CraftResource.RegularLeather + type, 60 - type * 15); + + throw new InvalidOperationException(); + } + + private static Item CreatePowerScroll(int type) + { + if (type == 5 || type == 10 || type == 15 || type == 20) + return new PowerScroll(SkillName.Tailoring, 100 + type); + + throw new InvalidOperationException(); + } + + private static Item CreateCBD(int type) + { + return new ClothingBlessDeed(); + } + + #endregion + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/SmallBOD.cs b/Scripts/Engines/BulkOrders/SmallBOD.cs index 550d84dcb..85a108fb1 100644 --- a/Scripts/Engines/BulkOrders/SmallBOD.cs +++ b/Scripts/Engines/BulkOrders/SmallBOD.cs @@ -1,290 +1,329 @@ using System; -using Server.Items; using System.Collections.Generic; +using Server.Items; using Server.Mobiles; namespace Server.Engines.BulkOrders { - [TypeAlias( "Scripts.Engines.BulkOrders.SmallBOD" )] - public abstract class SmallBOD : Item - { - private int m_AmountCur, m_AmountMax; - private int m_Number; - private bool m_RequireExceptional; - private BulkMaterialType m_Material; + [TypeAlias("Scripts.Engines.BulkOrders.SmallBOD")] + public abstract class SmallBOD : Item + { + private int m_AmountCur, m_AmountMax; + private BulkMaterialType m_Material; + private int m_Number; + private bool m_RequireExceptional; - [CommandProperty( AccessLevel.GameMaster )] - public int AmountCur{ get => m_AmountCur; - set{ m_AmountCur = value; InvalidateProperties(); } } + [Constructible] + public SmallBOD(int hue, int amountMax, Type type, int number, int graphic, bool requireExeptional, + BulkMaterialType material) : base(Core.AOS ? 0x2258 : 0x14EF) + { + Weight = 1.0; + Hue = hue; // Blacksmith: 0x44E; Tailoring: 0x483 + LootType = LootType.Blessed; - [CommandProperty( AccessLevel.GameMaster )] - public int AmountMax{ get => m_AmountMax; - set{ m_AmountMax = value; InvalidateProperties(); } } + m_AmountMax = amountMax; + Type = type; + m_Number = number; + Graphic = graphic; + m_RequireExceptional = requireExeptional; + m_Material = material; + } - [CommandProperty( AccessLevel.GameMaster )] - public Type Type { get; set; } + public SmallBOD() : base(Core.AOS ? 0x2258 : 0x14EF) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public int Number{ get => m_Number; - set{ m_Number = value; InvalidateProperties(); } } + public SmallBOD(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Graphic { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int AmountCur + { + get => m_AmountCur; + set + { + m_AmountCur = value; + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool RequireExceptional{ get => m_RequireExceptional; - set{ m_RequireExceptional = value; InvalidateProperties(); } } + [CommandProperty(AccessLevel.GameMaster)] + public int AmountMax + { + get => m_AmountMax; + set + { + m_AmountMax = value; + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public BulkMaterialType Material{ get => m_Material; - set{ m_Material = value; InvalidateProperties(); } } + [CommandProperty(AccessLevel.GameMaster)] + public Type Type{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public bool Complete => ( m_AmountCur == m_AmountMax ); + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_Number; + set + { + m_Number = value; + InvalidateProperties(); + } + } - public override int LabelNumber => 1045151; // a bulk order deed + [CommandProperty(AccessLevel.GameMaster)] + public int Graphic{ get; set; } - [Constructible] - public SmallBOD( int hue, int amountMax, Type type, int number, int graphic, bool requireExeptional, BulkMaterialType material ) : base( Core.AOS ? 0x2258 : 0x14EF ) - { - Weight = 1.0; - Hue = hue; // Blacksmith: 0x44E; Tailoring: 0x483 - LootType = LootType.Blessed; + [CommandProperty(AccessLevel.GameMaster)] + public bool RequireExceptional + { + get => m_RequireExceptional; + set + { + m_RequireExceptional = value; + InvalidateProperties(); + } + } - m_AmountMax = amountMax; - Type = type; - m_Number = number; - Graphic = graphic; - m_RequireExceptional = requireExeptional; - m_Material = material; - } + [CommandProperty(AccessLevel.GameMaster)] + public BulkMaterialType Material + { + get => m_Material; + set + { + m_Material = value; + InvalidateProperties(); + } + } - public SmallBOD() : base( Core.AOS ? 0x2258 : 0x14EF ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Complete => m_AmountCur == m_AmountMax; - public static BulkMaterialType GetRandomMaterial( BulkMaterialType start, double[] chances ) - { - double random = Utility.RandomDouble(); + public override int LabelNumber => 1045151; // a bulk order deed - for ( int i = 0; i < chances.Length; ++i ) - { - if ( random < chances[i] ) - return ( i == 0 ? BulkMaterialType.None : start + (i - 1) ); + public static BulkMaterialType GetRandomMaterial(BulkMaterialType start, double[] chances) + { + double random = Utility.RandomDouble(); - random -= chances[i]; - } + for (int i = 0; i < chances.Length; ++i) + { + if (random < chances[i]) + return i == 0 ? BulkMaterialType.None : start + (i - 1); - return BulkMaterialType.None; - } + random -= chances[i]; + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + return BulkMaterialType.None; + } - list.Add( 1060654 ); // small bulk order + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_RequireExceptional ) - list.Add( 1045141 ); // All items must be exceptional. + list.Add(1060654); // small bulk order - if ( m_Material != BulkMaterialType.None ) - list.Add( SmallBODGump.GetMaterialNumberFor( m_Material ) ); // All items must be made with x material. + if (m_RequireExceptional) + list.Add(1045141); // All items must be exceptional. - list.Add( 1060656, m_AmountMax.ToString() ); // amount to make: ~1_val~ - list.Add( 1060658, "#{0}\t{1}", m_Number, m_AmountCur ); // ~1_val~: ~2_val~ - } + if (m_Material != BulkMaterialType.None) + list.Add(SmallBODGump.GetMaterialNumberFor(m_Material)); // All items must be made with x material. - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) || InSecureTrade || RootParent is PlayerVendor ) - from.SendGump( new SmallBODGump( from, this ) ); - else - from.SendLocalizedMessage( 1045156 ); // You must have the deed in your backpack to use it. - } + list.Add(1060656, m_AmountMax.ToString()); // amount to make: ~1_val~ + list.Add(1060658, "#{0}\t{1}", m_Number, m_AmountCur); // ~1_val~: ~2_val~ + } - public override void OnDoubleClickNotAccessible( Mobile from ) - { - OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack) || InSecureTrade || RootParent is PlayerVendor) + from.SendGump(new SmallBODGump(from, this)); + else + from.SendLocalizedMessage(1045156); // You must have the deed in your backpack to use it. + } - public override void OnDoubleClickSecureTrade( Mobile from ) - { - OnDoubleClick( from ); - } + public override void OnDoubleClickNotAccessible(Mobile from) + { + OnDoubleClick(from); + } - public void BeginCombine( Mobile from ) - { - if ( m_AmountCur < m_AmountMax ) - from.Target = new SmallBODTarget( this ); - else - from.SendLocalizedMessage( 1045166 ); // The maximum amount of requested items have already been combined to this deed. - } + public override void OnDoubleClickSecureTrade(Mobile from) + { + OnDoubleClick(from); + } - public abstract List ComputeRewards( bool full ); - public abstract int ComputeGold(); - public abstract int ComputeFame(); + public void BeginCombine(Mobile from) + { + if (m_AmountCur < m_AmountMax) + from.Target = new SmallBODTarget(this); + else + from.SendLocalizedMessage( + 1045166); // The maximum amount of requested items have already been combined to this deed. + } - public virtual void GetRewards( out Item reward, out int gold, out int fame ) - { - reward = null; - gold = ComputeGold(); - fame = ComputeFame(); + public abstract List ComputeRewards(bool full); + public abstract int ComputeGold(); + public abstract int ComputeFame(); - List rewards = ComputeRewards( false ); + public virtual void GetRewards(out Item reward, out int gold, out int fame) + { + reward = null; + gold = ComputeGold(); + fame = ComputeFame(); - if ( rewards.Count > 0 ) - { - reward = rewards[Utility.Random( rewards.Count )]; + List rewards = ComputeRewards(false); - for ( int i = 0; i < rewards.Count; ++i ) - { - if ( rewards[i] != reward ) - rewards[i].Delete(); - } - } - } + if (rewards.Count > 0) + { + reward = rewards[Utility.Random(rewards.Count)]; - public static BulkMaterialType GetMaterial( CraftResource resource ) - { - switch ( resource ) - { - case CraftResource.DullCopper: return BulkMaterialType.DullCopper; - case CraftResource.ShadowIron: return BulkMaterialType.ShadowIron; - case CraftResource.Copper: return BulkMaterialType.Copper; - case CraftResource.Bronze: return BulkMaterialType.Bronze; - case CraftResource.Gold: return BulkMaterialType.Gold; - case CraftResource.Agapite: return BulkMaterialType.Agapite; - case CraftResource.Verite: return BulkMaterialType.Verite; - case CraftResource.Valorite: return BulkMaterialType.Valorite; - case CraftResource.SpinedLeather: return BulkMaterialType.Spined; - case CraftResource.HornedLeather: return BulkMaterialType.Horned; - case CraftResource.BarbedLeather: return BulkMaterialType.Barbed; - } + for (int i = 0; i < rewards.Count; ++i) + if (rewards[i] != reward) + rewards[i].Delete(); + } + } - return BulkMaterialType.None; - } + public static BulkMaterialType GetMaterial(CraftResource resource) + { + switch (resource) + { + case CraftResource.DullCopper: return BulkMaterialType.DullCopper; + case CraftResource.ShadowIron: return BulkMaterialType.ShadowIron; + case CraftResource.Copper: return BulkMaterialType.Copper; + case CraftResource.Bronze: return BulkMaterialType.Bronze; + case CraftResource.Gold: return BulkMaterialType.Gold; + case CraftResource.Agapite: return BulkMaterialType.Agapite; + case CraftResource.Verite: return BulkMaterialType.Verite; + case CraftResource.Valorite: return BulkMaterialType.Valorite; + case CraftResource.SpinedLeather: return BulkMaterialType.Spined; + case CraftResource.HornedLeather: return BulkMaterialType.Horned; + case CraftResource.BarbedLeather: return BulkMaterialType.Barbed; + } - public void EndCombine( Mobile from, object o ) - { - if ( o is Item item && item.IsChildOf( from.Backpack ) ) - { - Type objectType = item.GetType(); + return BulkMaterialType.None; + } - if ( m_AmountCur >= m_AmountMax ) - { - from.SendLocalizedMessage( 1045166 ); // The maximum amount of requested items have already been combined to this deed. - } - else if ( Type == null || (objectType != Type && !objectType.IsSubclassOf( Type )) || (!(item is BaseWeapon) && !(item is BaseArmor) && !(item is BaseClothing)) ) - { - from.SendLocalizedMessage( 1045169 ); // The item is not in the request. - } - else - { - BaseArmor armor = item as BaseArmor; - BaseClothing clothing = item as BaseClothing; + public void EndCombine(Mobile from, object o) + { + if (o is Item item && item.IsChildOf(from.Backpack)) + { + Type objectType = item.GetType(); - BulkMaterialType material = GetMaterial( armor?.Resource ?? clothing?.Resource ?? CraftResource.None ); + if (m_AmountCur >= m_AmountMax) + { + from.SendLocalizedMessage( + 1045166); // The maximum amount of requested items have already been combined to this deed. + } + else if (Type == null || objectType != Type && !objectType.IsSubclassOf(Type) || + !(item is BaseWeapon) && !(item is BaseArmor) && !(item is BaseClothing)) + { + from.SendLocalizedMessage(1045169); // The item is not in the request. + } + else + { + BaseArmor armor = item as BaseArmor; + BaseClothing clothing = item as BaseClothing; - if ( m_Material >= BulkMaterialType.DullCopper && m_Material <= BulkMaterialType.Valorite && material != m_Material ) - { - from.SendLocalizedMessage( 1045168 ); // The item is not made from the requested ore. - } - else if ( m_Material >= BulkMaterialType.Spined && m_Material <= BulkMaterialType.Barbed && material != m_Material ) - { - from.SendLocalizedMessage( 1049352 ); // The item is not made from the requested leather type. - } - else - { - bool isExceptional; + BulkMaterialType material = GetMaterial(armor?.Resource ?? clothing?.Resource ?? CraftResource.None); - if ( item is BaseWeapon weapon ) - isExceptional = weapon.Quality == WeaponQuality.Exceptional; - else if ( armor != null ) - isExceptional = armor.Quality == ArmorQuality.Exceptional; - else - isExceptional = clothing.Quality == ClothingQuality.Exceptional; + if (m_Material >= BulkMaterialType.DullCopper && m_Material <= BulkMaterialType.Valorite && + material != m_Material) + { + from.SendLocalizedMessage(1045168); // The item is not made from the requested ore. + } + else if (m_Material >= BulkMaterialType.Spined && m_Material <= BulkMaterialType.Barbed && + material != m_Material) + { + from.SendLocalizedMessage(1049352); // The item is not made from the requested leather type. + } + else + { + bool isExceptional; - if ( m_RequireExceptional && !isExceptional ) - { - from.SendLocalizedMessage( 1045167 ); // The item must be exceptional. - } - else - { - item.Delete(); - ++AmountCur; + if (item is BaseWeapon weapon) + isExceptional = weapon.Quality == WeaponQuality.Exceptional; + else if (armor != null) + isExceptional = armor.Quality == ArmorQuality.Exceptional; + else + isExceptional = clothing.Quality == ClothingQuality.Exceptional; - from.SendLocalizedMessage( 1045170 ); // The item has been combined with the deed. + if (m_RequireExceptional && !isExceptional) + { + from.SendLocalizedMessage(1045167); // The item must be exceptional. + } + else + { + item.Delete(); + ++AmountCur; - from.SendGump( new SmallBODGump( from, this ) ); + from.SendLocalizedMessage(1045170); // The item has been combined with the deed. - if ( m_AmountCur < m_AmountMax ) - BeginCombine( from ); - } - } - } - } - else - { - from.SendLocalizedMessage( 1045158 ); // You must have the item in your backpack to target it. - } - } + from.SendGump(new SmallBODGump(from, this)); - public SmallBOD( Serial serial ) : base( serial ) - { - } + if (m_AmountCur < m_AmountMax) + BeginCombine(from); + } + } + } + } + else + { + from.SendLocalizedMessage(1045158); // You must have the item in your backpack to target it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_AmountCur ); - writer.Write( m_AmountMax ); - writer.Write( Type == null ? null : Type.FullName ); - writer.Write( m_Number ); - writer.Write( Graphic ); - writer.Write( m_RequireExceptional ); - writer.Write( (int) m_Material ); - } + writer.Write(m_AmountCur); + writer.Write(m_AmountMax); + writer.Write(Type == null ? null : Type.FullName); + writer.Write(m_Number); + writer.Write(Graphic); + writer.Write(m_RequireExceptional); + writer.Write((int)m_Material); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_AmountCur = reader.ReadInt(); - m_AmountMax = reader.ReadInt(); + switch (version) + { + case 0: + { + m_AmountCur = reader.ReadInt(); + m_AmountMax = reader.ReadInt(); - string type = reader.ReadString(); + string type = reader.ReadString(); - if ( type != null ) - Type = ScriptCompiler.FindTypeByFullName( type ); + if (type != null) + Type = ScriptCompiler.FindTypeByFullName(type); - m_Number = reader.ReadInt(); - Graphic = reader.ReadInt(); - m_RequireExceptional = reader.ReadBool(); - m_Material = (BulkMaterialType)reader.ReadInt(); + m_Number = reader.ReadInt(); + Graphic = reader.ReadInt(); + m_RequireExceptional = reader.ReadBool(); + m_Material = (BulkMaterialType)reader.ReadInt(); - break; - } - } + break; + } + } - if ( Weight == 0.0 ) - Weight = 1.0; + if (Weight == 0.0) + Weight = 1.0; - if ( Core.AOS && ItemID == 0x14EF ) - ItemID = 0x2258; + if (Core.AOS && ItemID == 0x14EF) + ItemID = 0x2258; - if ( Parent == null && Map == Map.Internal && Location == Point3D.Zero ) - Delete(); - } - } -} + if (Parent == null && Map == Map.Internal && Location == Point3D.Zero) + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/SmallBODAcceptGump.cs b/Scripts/Engines/BulkOrders/SmallBODAcceptGump.cs index 471472a8c..93aff2b86 100644 --- a/Scripts/Engines/BulkOrders/SmallBODAcceptGump.cs +++ b/Scripts/Engines/BulkOrders/SmallBODAcceptGump.cs @@ -3,89 +3,91 @@ using Server.Network; namespace Server.Engines.BulkOrders { - public class SmallBODAcceptGump : Gump - { - private SmallBOD m_Deed; - private Mobile m_From; + public class SmallBODAcceptGump : Gump + { + private SmallBOD m_Deed; + private Mobile m_From; - public SmallBODAcceptGump( Mobile from, SmallBOD deed ) : base( 50, 50 ) - { - m_From = from; - m_Deed = deed; + public SmallBODAcceptGump(Mobile from, SmallBOD deed) : base(50, 50) + { + m_From = from; + m_Deed = deed; - m_From.CloseGump( typeof( LargeBODAcceptGump ) ); - m_From.CloseGump( typeof( SmallBODAcceptGump ) ); + m_From.CloseGump(typeof(LargeBODAcceptGump)); + m_From.CloseGump(typeof(SmallBODAcceptGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 25, 10, 430, 264, 5054 ); + AddBackground(25, 10, 430, 264, 5054); - AddImageTiled( 33, 20, 413, 245, 2624 ); - AddAlphaRegion( 33, 20, 413, 245 ); + AddImageTiled(33, 20, 413, 245, 2624); + AddAlphaRegion(33, 20, 413, 245); - AddImage( 20, 5, 10460 ); - AddImage( 430, 5, 10460 ); - AddImage( 20, 249, 10460 ); - AddImage( 430, 249, 10460 ); + AddImage(20, 5, 10460); + AddImage(430, 5, 10460); + AddImage(20, 249, 10460); + AddImage(430, 249, 10460); - AddHtmlLocalized( 190, 25, 120, 20, 1045133, 0x7FFF, false, false ); // A bulk order - AddHtmlLocalized( 40, 48, 350, 20, 1045135, 0x7FFF, false, false ); // Ah! Thanks for the goods! Would you help me out? + AddHtmlLocalized(190, 25, 120, 20, 1045133, 0x7FFF, false, false); // A bulk order + AddHtmlLocalized(40, 48, 350, 20, 1045135, 0x7FFF, false, + false); // Ah! Thanks for the goods! Would you help me out? - AddHtmlLocalized( 40, 72, 210, 20, 1045138, 0x7FFF, false, false ); // Amount to make: - AddLabel( 250, 72, 1152, deed.AmountMax.ToString() ); + AddHtmlLocalized(40, 72, 210, 20, 1045138, 0x7FFF, false, false); // Amount to make: + AddLabel(250, 72, 1152, deed.AmountMax.ToString()); - AddHtmlLocalized( 40, 96, 120, 20, 1045136, 0x7FFF, false, false ); // Item requested: - AddItem( 385, 96, deed.Graphic ); - AddHtmlLocalized( 40, 120, 210, 20, deed.Number, 0xFFFFFF, false, false ); + AddHtmlLocalized(40, 96, 120, 20, 1045136, 0x7FFF, false, false); // Item requested: + AddItem(385, 96, deed.Graphic); + AddHtmlLocalized(40, 120, 210, 20, deed.Number, 0xFFFFFF, false, false); - if ( deed.RequireExceptional || deed.Material != BulkMaterialType.None ) - { - AddHtmlLocalized( 40, 144, 210, 20, 1045140, 0x7FFF, false, false ); // Special requirements to meet: + if (deed.RequireExceptional || deed.Material != BulkMaterialType.None) + { + AddHtmlLocalized(40, 144, 210, 20, 1045140, 0x7FFF, false, false); // Special requirements to meet: - if ( deed.RequireExceptional ) - AddHtmlLocalized( 40, 168, 350, 20, 1045141, 0x7FFF, false, false ); // All items must be exceptional. + if (deed.RequireExceptional) + AddHtmlLocalized(40, 168, 350, 20, 1045141, 0x7FFF, false, false); // All items must be exceptional. - if ( deed.Material != BulkMaterialType.None ) - AddHtmlLocalized( 40, deed.RequireExceptional ? 192 : 168, 350, 20, GetMaterialNumberFor( deed.Material ), 0x7FFF, false, false ); // All items must be made with x material. - } + if (deed.Material != BulkMaterialType.None) + AddHtmlLocalized(40, deed.RequireExceptional ? 192 : 168, 350, 20, GetMaterialNumberFor(deed.Material), + 0x7FFF, false, false); // All items must be made with x material. + } - AddHtmlLocalized( 40, 216, 350, 20, 1045139, 0x7FFF, false, false ); // Do you want to accept this order? + AddHtmlLocalized(40, 216, 350, 20, 1045139, 0x7FFF, false, false); // Do you want to accept this order? - AddButton( 100, 240, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 135, 240, 120, 20, 1006044, 0x7FFF, false, false ); // Ok + AddButton(100, 240, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(135, 240, 120, 20, 1006044, 0x7FFF, false, false); // Ok - AddButton( 275, 240, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 310, 240, 120, 20, 1011012, 0x7FFF, false, false ); // CANCEL - } + AddButton(275, 240, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(310, 240, 120, 20, 1011012, 0x7FFF, false, false); // CANCEL + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) // Ok - { - if ( m_From.PlaceInBackpack( m_Deed ) ) - { - m_From.SendLocalizedMessage( 1045152 ); // The bulk order deed has been placed in your backpack. - } - else - { - m_From.SendLocalizedMessage( 1045150 ); // There is not enough room in your backpack for the deed. - m_Deed.Delete(); - } - } - else - { - m_Deed.Delete(); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) // Ok + { + if (m_From.PlaceInBackpack(m_Deed)) + { + m_From.SendLocalizedMessage(1045152); // The bulk order deed has been placed in your backpack. + } + else + { + m_From.SendLocalizedMessage(1045150); // There is not enough room in your backpack for the deed. + m_Deed.Delete(); + } + } + else + { + m_Deed.Delete(); + } + } - public static int GetMaterialNumberFor( BulkMaterialType material ) - { - if ( material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite ) - return 1045142 + (int)(material - BulkMaterialType.DullCopper); - if ( material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed ) - return 1049348 + (int)(material - BulkMaterialType.Spined); + public static int GetMaterialNumberFor(BulkMaterialType material) + { + if (material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite) + return 1045142 + (material - BulkMaterialType.DullCopper); + if (material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed) + return 1049348 + (material - BulkMaterialType.Spined); - return 0; - } - } + return 0; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/SmallBODGump.cs b/Scripts/Engines/BulkOrders/SmallBODGump.cs index 3e180caec..d9cc254c2 100644 --- a/Scripts/Engines/BulkOrders/SmallBODGump.cs +++ b/Scripts/Engines/BulkOrders/SmallBODGump.cs @@ -3,79 +3,80 @@ using Server.Network; namespace Server.Engines.BulkOrders { - public class SmallBODGump : Gump - { - private SmallBOD m_Deed; - private Mobile m_From; + public class SmallBODGump : Gump + { + private SmallBOD m_Deed; + private Mobile m_From; - public SmallBODGump( Mobile from, SmallBOD deed ) : base( 25, 25 ) - { - m_From = from; - m_Deed = deed; + public SmallBODGump(Mobile from, SmallBOD deed) : base(25, 25) + { + m_From = from; + m_Deed = deed; - m_From.CloseGump( typeof( LargeBODGump ) ); - m_From.CloseGump( typeof( SmallBODGump ) ); + m_From.CloseGump(typeof(LargeBODGump)); + m_From.CloseGump(typeof(SmallBODGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 50, 10, 455, 260, 5054 ); - AddImageTiled( 58, 20, 438, 241, 2624 ); - AddAlphaRegion( 58, 20, 438, 241 ); + AddBackground(50, 10, 455, 260, 5054); + AddImageTiled(58, 20, 438, 241, 2624); + AddAlphaRegion(58, 20, 438, 241); - AddImage( 45, 5, 10460 ); - AddImage( 480, 5, 10460 ); - AddImage( 45, 245, 10460 ); - AddImage( 480, 245, 10460 ); + AddImage(45, 5, 10460); + AddImage(480, 5, 10460); + AddImage(45, 245, 10460); + AddImage(480, 245, 10460); - AddHtmlLocalized( 225, 25, 120, 20, 1045133, 0x7FFF, false, false ); // A bulk order + AddHtmlLocalized(225, 25, 120, 20, 1045133, 0x7FFF, false, false); // A bulk order - AddHtmlLocalized( 75, 48, 250, 20, 1045138, 0x7FFF, false, false ); // Amount to make: - AddLabel( 275, 48, 1152, deed.AmountMax.ToString() ); + AddHtmlLocalized(75, 48, 250, 20, 1045138, 0x7FFF, false, false); // Amount to make: + AddLabel(275, 48, 1152, deed.AmountMax.ToString()); - AddHtmlLocalized( 275, 76, 200, 20, 1045153, 0x7FFF, false, false ); // Amount finished: - AddHtmlLocalized( 75, 72, 120, 20, 1045136, 0x7FFF, false, false ); // Item requested: + AddHtmlLocalized(275, 76, 200, 20, 1045153, 0x7FFF, false, false); // Amount finished: + AddHtmlLocalized(75, 72, 120, 20, 1045136, 0x7FFF, false, false); // Item requested: - AddItem( 410, 72, deed.Graphic ); + AddItem(410, 72, deed.Graphic); - AddHtmlLocalized( 75, 96, 210, 20, deed.Number, 0x7FFF, false, false ); - AddLabel( 275, 96, 0x480, deed.AmountCur.ToString() ); + AddHtmlLocalized(75, 96, 210, 20, deed.Number, 0x7FFF, false, false); + AddLabel(275, 96, 0x480, deed.AmountCur.ToString()); - if ( deed.RequireExceptional || deed.Material != BulkMaterialType.None ) - AddHtmlLocalized( 75, 120, 200, 20, 1045140, 0x7FFF, false, false ); // Special requirements to meet: + if (deed.RequireExceptional || deed.Material != BulkMaterialType.None) + AddHtmlLocalized(75, 120, 200, 20, 1045140, 0x7FFF, false, false); // Special requirements to meet: - if ( deed.RequireExceptional ) - AddHtmlLocalized( 75, 144, 300, 20, 1045141, 0x7FFF, false, false ); // All items must be exceptional. + if (deed.RequireExceptional) + AddHtmlLocalized(75, 144, 300, 20, 1045141, 0x7FFF, false, false); // All items must be exceptional. - if ( deed.Material != BulkMaterialType.None ) - AddHtmlLocalized( 75, deed.RequireExceptional ? 168 : 144, 300, 20, GetMaterialNumberFor( deed.Material ), 0x7FFF, false, false ); // All items must be made with x material. + if (deed.Material != BulkMaterialType.None) + AddHtmlLocalized(75, deed.RequireExceptional ? 168 : 144, 300, 20, GetMaterialNumberFor(deed.Material), + 0x7FFF, false, false); // All items must be made with x material. - AddButton( 125, 192, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 160, 192, 300, 20, 1045154, 0x7FFF, false, false ); // Combine this deed with the item requested. + AddButton(125, 192, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(160, 192, 300, 20, 1045154, 0x7FFF, false, false); // Combine this deed with the item requested. - AddButton( 125, 216, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 160, 216, 120, 20, 1011441, 0x7FFF, false, false ); // EXIT - } + AddButton(125, 216, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(160, 216, 120, 20, 1011441, 0x7FFF, false, false); // EXIT + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed.Deleted || !m_Deed.IsChildOf( m_From.Backpack ) ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed.Deleted || !m_Deed.IsChildOf(m_From.Backpack)) + return; - if ( info.ButtonID == 2 ) // Combine - { - m_From.SendGump( new SmallBODGump( m_From, m_Deed ) ); - m_Deed.BeginCombine( m_From ); - } - } + if (info.ButtonID == 2) // Combine + { + m_From.SendGump(new SmallBODGump(m_From, m_Deed)); + m_Deed.BeginCombine(m_From); + } + } - public static int GetMaterialNumberFor( BulkMaterialType material ) - { - if ( material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite ) - return 1045142 + (int)(material - BulkMaterialType.DullCopper); - if ( material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed ) - return 1049348 + (int)(material - BulkMaterialType.Spined); + public static int GetMaterialNumberFor(BulkMaterialType material) + { + if (material >= BulkMaterialType.DullCopper && material <= BulkMaterialType.Valorite) + return 1045142 + (material - BulkMaterialType.DullCopper); + if (material >= BulkMaterialType.Spined && material <= BulkMaterialType.Barbed) + return 1049348 + (material - BulkMaterialType.Spined); - return 0; - } - } + return 0; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/SmallBODTarget.cs b/Scripts/Engines/BulkOrders/SmallBODTarget.cs index 1fa368b12..2b412d0b2 100644 --- a/Scripts/Engines/BulkOrders/SmallBODTarget.cs +++ b/Scripts/Engines/BulkOrders/SmallBODTarget.cs @@ -2,21 +2,21 @@ using Server.Targeting; namespace Server.Engines.BulkOrders { - public class SmallBODTarget : Target - { - private SmallBOD m_Deed; + public class SmallBODTarget : Target + { + private SmallBOD m_Deed; - public SmallBODTarget( SmallBOD deed ) : base( 18, false, TargetFlags.None ) - { - m_Deed = deed; - } + public SmallBODTarget(SmallBOD deed) : base(18, false, TargetFlags.None) + { + m_Deed = deed; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Deed.Deleted || !m_Deed.IsChildOf( from.Backpack ) ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Deed.Deleted || !m_Deed.IsChildOf(from.Backpack)) + return; - m_Deed.EndCombine( from, targeted ); - } - } + m_Deed.EndCombine(from, targeted); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/SmallSmithBOD.cs b/Scripts/Engines/BulkOrders/SmallSmithBOD.cs index ca3299a05..06ace1322 100644 --- a/Scripts/Engines/BulkOrders/SmallSmithBOD.cs +++ b/Scripts/Engines/BulkOrders/SmallSmithBOD.cs @@ -5,234 +5,257 @@ using Mat = Server.Engines.BulkOrders.BulkMaterialType; namespace Server.Engines.BulkOrders { - [TypeAlias( "Scripts.Engines.BulkOrders.SmallSmithBOD" )] - public class SmallSmithBOD : SmallBOD - { - public static double[] m_BlacksmithMaterialChances = { - 0.501953125, // None - 0.250000000, // Dull Copper - 0.125000000, // Shadow Iron - 0.062500000, // Copper - 0.031250000, // Bronze - 0.015625000, // Gold - 0.007812500, // Agapite - 0.003906250, // Verite - 0.001953125 // Valorite - }; + [TypeAlias("Scripts.Engines.BulkOrders.SmallSmithBOD")] + public class SmallSmithBOD : SmallBOD + { + public static double[] m_BlacksmithMaterialChances = + { + 0.501953125, // None + 0.250000000, // Dull Copper + 0.125000000, // Shadow Iron + 0.062500000, // Copper + 0.031250000, // Bronze + 0.015625000, // Gold + 0.007812500, // Agapite + 0.003906250, // Verite + 0.001953125 // Valorite + }; - public override int ComputeFame() - { - return SmithRewardCalculator.Instance.ComputeFame( this ); - } + private SmallSmithBOD(SmallBulkEntry entry, BulkMaterialType material, int amountMax, bool reqExceptional) + { + Hue = 0x44E; + AmountMax = amountMax; + Type = entry.Type; + Number = entry.Number; + Graphic = entry.Graphic; + RequireExceptional = reqExceptional; + Material = material; + } - public override int ComputeGold() - { - return SmithRewardCalculator.Instance.ComputeGold( this ); - } + [Constructible] + public SmallSmithBOD() + { + SmallBulkEntry[] entries; + bool useMaterials; - public override List ComputeRewards( bool full ) - { - List list = new List(); + if (useMaterials = Utility.RandomBool()) + entries = SmallBulkEntry.BlacksmithArmor; + else + entries = SmallBulkEntry.BlacksmithWeapons; - RewardGroup rewardGroup = SmithRewardCalculator.Instance.LookupRewards( SmithRewardCalculator.Instance.ComputePoints( this ) ); + if (entries.Length > 0) + { + int hue = 0x44E; + int amountMax = Utility.RandomList(10, 15, 20); - if ( rewardGroup != null ) - { - if ( full ) - { - for ( int i = 0; i < rewardGroup.Items.Length; ++i ) - { - Item item = rewardGroup.Items[i].Construct(); + BulkMaterialType material; - if ( item != null ) - list.Add( item ); - } - } - else - { - RewardItem rewardItem = rewardGroup.AcquireItem(); + if (useMaterials) + material = GetRandomMaterial(BulkMaterialType.DullCopper, m_BlacksmithMaterialChances); + else + material = BulkMaterialType.None; - Item item = rewardItem?.Construct(); + bool reqExceptional = Utility.RandomBool() || material == BulkMaterialType.None; - if ( item != null ) - list.Add( item ); - } - } + SmallBulkEntry entry = entries[Utility.Random(entries.Length)]; - return list; - } + Hue = hue; + AmountMax = amountMax; + Type = entry.Type; + Number = entry.Number; + Graphic = entry.Graphic; + RequireExceptional = reqExceptional; + Material = material; + } + } - public static SmallSmithBOD CreateRandomFor( Mobile m ) - { - SmallBulkEntry[] entries; - bool useMaterials; + public SmallSmithBOD(int amountCur, int amountMax, Type type, int number, int graphic, bool reqExceptional, + BulkMaterialType mat) + { + Hue = 0x44E; + AmountMax = amountMax; + AmountCur = amountCur; + Type = type; + Number = number; + Graphic = graphic; + RequireExceptional = reqExceptional; + Material = mat; + } - if ( useMaterials = Utility.RandomBool() ) - entries = SmallBulkEntry.BlacksmithArmor; - else - entries = SmallBulkEntry.BlacksmithWeapons; + public SmallSmithBOD(Serial serial) : base(serial) + { + } - if ( entries.Length > 0 ) - { - double theirSkill = m.Skills[SkillName.Blacksmith].Base; - int amountMax; + public override int ComputeFame() + { + return SmithRewardCalculator.Instance.ComputeFame(this); + } - if ( theirSkill >= 70.1 ) - amountMax = Utility.RandomList( 10, 15, 20, 20 ); - else if ( theirSkill >= 50.1 ) - amountMax = Utility.RandomList( 10, 15, 15, 20 ); - else - amountMax = Utility.RandomList( 10, 10, 15, 20 ); + public override int ComputeGold() + { + return SmithRewardCalculator.Instance.ComputeGold(this); + } - BulkMaterialType material = BulkMaterialType.None; + public override List ComputeRewards(bool full) + { + List list = new List(); - if ( useMaterials && theirSkill >= 70.1 ) - { - for ( int i = 0; i < 20; ++i ) - { - BulkMaterialType check = GetRandomMaterial( BulkMaterialType.DullCopper, m_BlacksmithMaterialChances ); - double skillReq = 0.0; + RewardGroup rewardGroup = + SmithRewardCalculator.Instance.LookupRewards(SmithRewardCalculator.Instance.ComputePoints(this)); - switch ( check ) - { - case BulkMaterialType.DullCopper: skillReq = 65.0; break; - case BulkMaterialType.ShadowIron: skillReq = 70.0; break; - case BulkMaterialType.Copper: skillReq = 75.0; break; - case BulkMaterialType.Bronze: skillReq = 80.0; break; - case BulkMaterialType.Gold: skillReq = 85.0; break; - case BulkMaterialType.Agapite: skillReq = 90.0; break; - case BulkMaterialType.Verite: skillReq = 95.0; break; - case BulkMaterialType.Valorite: skillReq = 100.0; break; - case BulkMaterialType.Spined: skillReq = 65.0; break; - case BulkMaterialType.Horned: skillReq = 80.0; break; - case BulkMaterialType.Barbed: skillReq = 99.0; break; - } + if (rewardGroup != null) + { + if (full) + { + for (int i = 0; i < rewardGroup.Items.Length; ++i) + { + Item item = rewardGroup.Items[i].Construct(); - if ( theirSkill >= skillReq ) - { - material = check; - break; - } - } - } + if (item != null) + list.Add(item); + } + } + else + { + RewardItem rewardItem = rewardGroup.AcquireItem(); - double excChance = 0.0; + Item item = rewardItem?.Construct(); - if ( theirSkill >= 70.1 ) - excChance = (theirSkill + 80.0) / 200.0; + if (item != null) + list.Add(item); + } + } - bool reqExceptional = ( excChance > Utility.RandomDouble() ); + return list; + } - CraftSystem system = DefBlacksmithy.CraftSystem; + public static SmallSmithBOD CreateRandomFor(Mobile m) + { + SmallBulkEntry[] entries; + bool useMaterials; - List validEntries = new List(); + if (useMaterials = Utility.RandomBool()) + entries = SmallBulkEntry.BlacksmithArmor; + else + entries = SmallBulkEntry.BlacksmithWeapons; - for ( int i = 0; i < entries.Length; ++i ) - { - CraftItem item = system.CraftItems.SearchFor( entries[i].Type ); + if (entries.Length > 0) + { + double theirSkill = m.Skills[SkillName.Blacksmith].Base; + int amountMax; - if ( item != null ) - { - bool allRequiredSkills = true; - double chance = item.GetSuccessChance( m, null, system, false, ref allRequiredSkills ); + if (theirSkill >= 70.1) + amountMax = Utility.RandomList(10, 15, 20, 20); + else if (theirSkill >= 50.1) + amountMax = Utility.RandomList(10, 15, 15, 20); + else + amountMax = Utility.RandomList(10, 10, 15, 20); - if ( allRequiredSkills && chance >= 0.0 ) - { - if ( reqExceptional ) - chance = item.GetExceptionalChance( system, chance, m ); + BulkMaterialType material = BulkMaterialType.None; - if ( chance > 0.0 ) - validEntries.Add( entries[i] ); - } - } - } + if (useMaterials && theirSkill >= 70.1) + for (int i = 0; i < 20; ++i) + { + BulkMaterialType check = GetRandomMaterial(BulkMaterialType.DullCopper, m_BlacksmithMaterialChances); + double skillReq = 0.0; - if ( validEntries.Count > 0 ) - { - SmallBulkEntry entry = validEntries[Utility.Random( validEntries.Count )]; - return new SmallSmithBOD( entry, material, amountMax, reqExceptional ); - } - } + switch (check) + { + case BulkMaterialType.DullCopper: + skillReq = 65.0; + break; + case BulkMaterialType.ShadowIron: + skillReq = 70.0; + break; + case BulkMaterialType.Copper: + skillReq = 75.0; + break; + case BulkMaterialType.Bronze: + skillReq = 80.0; + break; + case BulkMaterialType.Gold: + skillReq = 85.0; + break; + case BulkMaterialType.Agapite: + skillReq = 90.0; + break; + case BulkMaterialType.Verite: + skillReq = 95.0; + break; + case BulkMaterialType.Valorite: + skillReq = 100.0; + break; + case BulkMaterialType.Spined: + skillReq = 65.0; + break; + case BulkMaterialType.Horned: + skillReq = 80.0; + break; + case BulkMaterialType.Barbed: + skillReq = 99.0; + break; + } - return null; - } + if (theirSkill >= skillReq) + { + material = check; + break; + } + } - private SmallSmithBOD( SmallBulkEntry entry, BulkMaterialType material, int amountMax, bool reqExceptional ) - { - Hue = 0x44E; - AmountMax = amountMax; - Type = entry.Type; - Number = entry.Number; - Graphic = entry.Graphic; - RequireExceptional = reqExceptional; - Material = material; - } + double excChance = 0.0; - [Constructible] - public SmallSmithBOD() - { - SmallBulkEntry[] entries; - bool useMaterials; + if (theirSkill >= 70.1) + excChance = (theirSkill + 80.0) / 200.0; - if ( useMaterials = Utility.RandomBool() ) - entries = SmallBulkEntry.BlacksmithArmor; - else - entries = SmallBulkEntry.BlacksmithWeapons; + bool reqExceptional = excChance > Utility.RandomDouble(); - if ( entries.Length > 0 ) - { - int hue = 0x44E; - int amountMax = Utility.RandomList( 10, 15, 20 ); + CraftSystem system = DefBlacksmithy.CraftSystem; - BulkMaterialType material; + List validEntries = new List(); - if ( useMaterials ) - material = GetRandomMaterial( BulkMaterialType.DullCopper, m_BlacksmithMaterialChances ); - else - material = BulkMaterialType.None; + for (int i = 0; i < entries.Length; ++i) + { + CraftItem item = system.CraftItems.SearchFor(entries[i].Type); - bool reqExceptional = Utility.RandomBool() || (material == BulkMaterialType.None); + if (item != null) + { + bool allRequiredSkills = true; + double chance = item.GetSuccessChance(m, null, system, false, ref allRequiredSkills); - SmallBulkEntry entry = entries[Utility.Random( entries.Length )]; + if (allRequiredSkills && chance >= 0.0) + { + if (reqExceptional) + chance = item.GetExceptionalChance(system, chance, m); - Hue = hue; - AmountMax = amountMax; - Type = entry.Type; - Number = entry.Number; - Graphic = entry.Graphic; - RequireExceptional = reqExceptional; - Material = material; - } - } + if (chance > 0.0) + validEntries.Add(entries[i]); + } + } + } - public SmallSmithBOD( int amountCur, int amountMax, Type type, int number, int graphic, bool reqExceptional, BulkMaterialType mat ) - { - Hue = 0x44E; - AmountMax = amountMax; - AmountCur = amountCur; - Type = type; - Number = number; - Graphic = graphic; - RequireExceptional = reqExceptional; - Material = mat; - } + if (validEntries.Count > 0) + { + SmallBulkEntry entry = validEntries[Utility.Random(validEntries.Count)]; + return new SmallSmithBOD(entry, material, amountMax, reqExceptional); + } + } - public SmallSmithBOD( Serial serial ) : base( serial ) - { - } + return null; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/BulkOrders/SmallTailorBOD.cs b/Scripts/Engines/BulkOrders/SmallTailorBOD.cs index 3b8b8d43c..7d5ddf3bf 100644 --- a/Scripts/Engines/BulkOrders/SmallTailorBOD.cs +++ b/Scripts/Engines/BulkOrders/SmallTailorBOD.cs @@ -4,227 +4,247 @@ using Server.Engines.Craft; namespace Server.Engines.BulkOrders { - public class SmallTailorBOD : SmallBOD - { - public static double[] m_TailoringMaterialChances = { - 0.857421875, // None - 0.125000000, // Spined - 0.015625000, // Horned - 0.001953125 // Barbed - }; + public class SmallTailorBOD : SmallBOD + { + public static double[] m_TailoringMaterialChances = + { + 0.857421875, // None + 0.125000000, // Spined + 0.015625000, // Horned + 0.001953125 // Barbed + }; - public override int ComputeFame() - { - return TailorRewardCalculator.Instance.ComputeFame( this ); - } + private SmallTailorBOD(SmallBulkEntry entry, BulkMaterialType material, int amountMax, bool reqExceptional) + { + Hue = 0x483; + AmountMax = amountMax; + Type = entry.Type; + Number = entry.Number; + Graphic = entry.Graphic; + RequireExceptional = reqExceptional; + Material = material; + } - public override int ComputeGold() - { - return TailorRewardCalculator.Instance.ComputeGold( this ); - } + [Constructible] + public SmallTailorBOD() + { + SmallBulkEntry[] entries; + bool useMaterials; - public override List ComputeRewards( bool full ) - { - List list = new List(); + if (useMaterials = Utility.RandomBool()) + entries = SmallBulkEntry.TailorLeather; + else + entries = SmallBulkEntry.TailorCloth; - RewardGroup rewardGroup = TailorRewardCalculator.Instance.LookupRewards( TailorRewardCalculator.Instance.ComputePoints( this ) ); + if (entries.Length > 0) + { + int hue = 0x483; + int amountMax = Utility.RandomList(10, 15, 20); - if ( rewardGroup != null ) - { - if ( full ) - { - for ( int i = 0; i < rewardGroup.Items.Length; ++i ) - { - Item item = rewardGroup.Items[i].Construct(); + BulkMaterialType material; - if ( item != null ) - list.Add( item ); - } - } - else - { - RewardItem rewardItem = rewardGroup.AcquireItem(); + if (useMaterials) + material = GetRandomMaterial(BulkMaterialType.Spined, m_TailoringMaterialChances); + else + material = BulkMaterialType.None; - Item item = rewardItem?.Construct(); + bool reqExceptional = Utility.RandomBool() || material == BulkMaterialType.None; - if ( item != null ) - list.Add( item ); - } - } + SmallBulkEntry entry = entries[Utility.Random(entries.Length)]; - return list; - } + Hue = hue; + AmountMax = amountMax; + Type = entry.Type; + Number = entry.Number; + Graphic = entry.Graphic; + RequireExceptional = reqExceptional; + Material = material; + } + } - public static SmallTailorBOD CreateRandomFor( Mobile m ) - { - SmallBulkEntry[] entries; - bool useMaterials = Utility.RandomBool(); + public SmallTailorBOD(int amountCur, int amountMax, Type type, int number, int graphic, bool reqExceptional, + BulkMaterialType mat) + { + Hue = 0x483; + AmountMax = amountMax; + AmountCur = amountCur; + Type = type; + Number = number; + Graphic = graphic; + RequireExceptional = reqExceptional; + Material = mat; + } - double theirSkill = m.Skills[SkillName.Tailoring].Base; - if ( useMaterials && theirSkill >= 6.2 ) // Ugly, but the easiest leather BOD is Leather Cap which requires at least 6.2 skill. - entries = SmallBulkEntry.TailorLeather; - else - entries = SmallBulkEntry.TailorCloth; + public SmallTailorBOD(Serial serial) : base(serial) + { + } - if ( entries.Length > 0 ) - { - int amountMax; + public override int ComputeFame() + { + return TailorRewardCalculator.Instance.ComputeFame(this); + } - if ( theirSkill >= 70.1 ) - amountMax = Utility.RandomList( 10, 15, 20, 20 ); - else if ( theirSkill >= 50.1 ) - amountMax = Utility.RandomList( 10, 15, 15, 20 ); - else - amountMax = Utility.RandomList( 10, 10, 15, 20 ); + public override int ComputeGold() + { + return TailorRewardCalculator.Instance.ComputeGold(this); + } - BulkMaterialType material = BulkMaterialType.None; + public override List ComputeRewards(bool full) + { + List list = new List(); - if ( useMaterials && theirSkill >= 70.1 ) - { - for ( int i = 0; i < 20; ++i ) - { - BulkMaterialType check = GetRandomMaterial( BulkMaterialType.Spined, m_TailoringMaterialChances ); - double skillReq = 0.0; + RewardGroup rewardGroup = + TailorRewardCalculator.Instance.LookupRewards(TailorRewardCalculator.Instance.ComputePoints(this)); - switch ( check ) - { - case BulkMaterialType.DullCopper: skillReq = 65.0; break; - case BulkMaterialType.Bronze: skillReq = 80.0; break; - case BulkMaterialType.Gold: skillReq = 85.0; break; - case BulkMaterialType.Agapite: skillReq = 90.0; break; - case BulkMaterialType.Verite: skillReq = 95.0; break; - case BulkMaterialType.Valorite: skillReq = 100.0; break; - case BulkMaterialType.Spined: skillReq = 65.0; break; - case BulkMaterialType.Horned: skillReq = 80.0; break; - case BulkMaterialType.Barbed: skillReq = 99.0; break; - } + if (rewardGroup != null) + { + if (full) + { + for (int i = 0; i < rewardGroup.Items.Length; ++i) + { + Item item = rewardGroup.Items[i].Construct(); - if ( theirSkill >= skillReq ) - { - material = check; - break; - } - } - } + if (item != null) + list.Add(item); + } + } + else + { + RewardItem rewardItem = rewardGroup.AcquireItem(); - double excChance = 0.0; + Item item = rewardItem?.Construct(); - if ( theirSkill >= 70.1 ) - excChance = (theirSkill + 80.0) / 200.0; + if (item != null) + list.Add(item); + } + } - bool reqExceptional = ( excChance > Utility.RandomDouble() ); + return list; + } + + public static SmallTailorBOD CreateRandomFor(Mobile m) + { + SmallBulkEntry[] entries; + bool useMaterials = Utility.RandomBool(); + + double theirSkill = m.Skills[SkillName.Tailoring].Base; + if (useMaterials && theirSkill >= 6.2 + ) // Ugly, but the easiest leather BOD is Leather Cap which requires at least 6.2 skill. + entries = SmallBulkEntry.TailorLeather; + else + entries = SmallBulkEntry.TailorCloth; + + if (entries.Length > 0) + { + int amountMax; + + if (theirSkill >= 70.1) + amountMax = Utility.RandomList(10, 15, 20, 20); + else if (theirSkill >= 50.1) + amountMax = Utility.RandomList(10, 15, 15, 20); + else + amountMax = Utility.RandomList(10, 10, 15, 20); + + BulkMaterialType material = BulkMaterialType.None; + + if (useMaterials && theirSkill >= 70.1) + for (int i = 0; i < 20; ++i) + { + BulkMaterialType check = GetRandomMaterial(BulkMaterialType.Spined, m_TailoringMaterialChances); + double skillReq = 0.0; + + switch (check) + { + case BulkMaterialType.DullCopper: + skillReq = 65.0; + break; + case BulkMaterialType.Bronze: + skillReq = 80.0; + break; + case BulkMaterialType.Gold: + skillReq = 85.0; + break; + case BulkMaterialType.Agapite: + skillReq = 90.0; + break; + case BulkMaterialType.Verite: + skillReq = 95.0; + break; + case BulkMaterialType.Valorite: + skillReq = 100.0; + break; + case BulkMaterialType.Spined: + skillReq = 65.0; + break; + case BulkMaterialType.Horned: + skillReq = 80.0; + break; + case BulkMaterialType.Barbed: + skillReq = 99.0; + break; + } + + if (theirSkill >= skillReq) + { + material = check; + break; + } + } + + double excChance = 0.0; + + if (theirSkill >= 70.1) + excChance = (theirSkill + 80.0) / 200.0; + + bool reqExceptional = excChance > Utility.RandomDouble(); - CraftSystem system = DefTailoring.CraftSystem; + CraftSystem system = DefTailoring.CraftSystem; - List validEntries = new List(); + List validEntries = new List(); - for ( int i = 0; i < entries.Length; ++i ) - { - CraftItem item = system.CraftItems.SearchFor( entries[i].Type ); + for (int i = 0; i < entries.Length; ++i) + { + CraftItem item = system.CraftItems.SearchFor(entries[i].Type); - if ( item != null ) - { - bool allRequiredSkills = true; - double chance = item.GetSuccessChance( m, null, system, false, ref allRequiredSkills ); + if (item != null) + { + bool allRequiredSkills = true; + double chance = item.GetSuccessChance(m, null, system, false, ref allRequiredSkills); - if ( allRequiredSkills && chance >= 0.0 ) - { - if ( reqExceptional ) - chance = item.GetExceptionalChance( system, chance, m ); + if (allRequiredSkills && chance >= 0.0) + { + if (reqExceptional) + chance = item.GetExceptionalChance(system, chance, m); - if ( chance > 0.0 ) - validEntries.Add( entries[i] ); - } - } - } + if (chance > 0.0) + validEntries.Add(entries[i]); + } + } + } - if ( validEntries.Count > 0 ) - { - SmallBulkEntry entry = validEntries[Utility.Random( validEntries.Count )]; - return new SmallTailorBOD( entry, material, amountMax, reqExceptional ); - } - } + if (validEntries.Count > 0) + { + SmallBulkEntry entry = validEntries[Utility.Random(validEntries.Count)]; + return new SmallTailorBOD(entry, material, amountMax, reqExceptional); + } + } - return null; - } + return null; + } - private SmallTailorBOD( SmallBulkEntry entry, BulkMaterialType material, int amountMax, bool reqExceptional ) - { - Hue = 0x483; - AmountMax = amountMax; - Type = entry.Type; - Number = entry.Number; - Graphic = entry.Graphic; - RequireExceptional = reqExceptional; - Material = material; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Constructible] - public SmallTailorBOD() - { - SmallBulkEntry[] entries; - bool useMaterials; + writer.Write(0); // version + } - if ( useMaterials = Utility.RandomBool() ) - entries = SmallBulkEntry.TailorLeather; - else - entries = SmallBulkEntry.TailorCloth; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( entries.Length > 0 ) - { - int hue = 0x483; - int amountMax = Utility.RandomList( 10, 15, 20 ); - - BulkMaterialType material; - - if ( useMaterials ) - material = GetRandomMaterial( BulkMaterialType.Spined, m_TailoringMaterialChances ); - else - material = BulkMaterialType.None; - - bool reqExceptional = Utility.RandomBool() || (material == BulkMaterialType.None); - - SmallBulkEntry entry = entries[Utility.Random( entries.Length )]; - - Hue = hue; - AmountMax = amountMax; - Type = entry.Type; - Number = entry.Number; - Graphic = entry.Graphic; - RequireExceptional = reqExceptional; - Material = material; - } - } - - public SmallTailorBOD( int amountCur, int amountMax, Type type, int number, int graphic, bool reqExceptional, BulkMaterialType mat ) - { - Hue = 0x483; - AmountMax = amountMax; - AmountCur = amountCur; - Type = type; - Number = number; - Graphic = graphic; - RequireExceptional = reqExceptional; - Material = mat; - } - - public SmallTailorBOD( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionAltar.cs b/Scripts/Engines/CannedEvil/ChampionAltar.cs index 20d58b39e..0a8d89c0f 100644 --- a/Scripts/Engines/CannedEvil/ChampionAltar.cs +++ b/Scripts/Engines/CannedEvil/ChampionAltar.cs @@ -2,53 +2,53 @@ using Server.Items; namespace Server.Engines.CannedEvil { - public class ChampionAltar : PentagramAddon - { - private ChampionSpawn m_Spawn; + public class ChampionAltar : PentagramAddon + { + private ChampionSpawn m_Spawn; - public ChampionAltar( ChampionSpawn spawn ) - { - m_Spawn = spawn; - } + public ChampionAltar(ChampionSpawn spawn) + { + m_Spawn = spawn; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public ChampionAltar(Serial serial) : base(serial) + { + } - m_Spawn?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public ChampionAltar( Serial serial ) : base( serial ) - { - } + m_Spawn?.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Spawn ); - } + writer.Write(m_Spawn); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Spawn = reader.ReadItem() as ChampionSpawn; + switch (version) + { + case 0: + { + m_Spawn = reader.ReadItem() as ChampionSpawn; - if ( m_Spawn == null ) - Delete(); + if (m_Spawn == null) + Delete(); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionPlatform.cs b/Scripts/Engines/CannedEvil/ChampionPlatform.cs index 87172e6b2..2255d8eaa 100644 --- a/Scripts/Engines/CannedEvil/ChampionPlatform.cs +++ b/Scripts/Engines/CannedEvil/ChampionPlatform.cs @@ -2,84 +2,84 @@ using Server.Items; namespace Server.Engines.CannedEvil { - public class ChampionPlatform : BaseAddon - { - private ChampionSpawn m_Spawn; + public class ChampionPlatform : BaseAddon + { + private ChampionSpawn m_Spawn; - public ChampionPlatform( ChampionSpawn spawn ) - { - m_Spawn = spawn; + public ChampionPlatform(ChampionSpawn spawn) + { + m_Spawn = spawn; - for ( int x = -2; x <= 2; ++x ) - for ( int y = -2; y <= 2; ++y ) - AddComponent( 0x750, x, y, -5 ); + for (int x = -2; x <= 2; ++x) + for (int y = -2; y <= 2; ++y) + AddComponent(0x750, x, y, -5); - for ( int x = -1; x <= 1; ++x ) - for ( int y = -1; y <= 1; ++y ) - AddComponent( 0x750, x, y, 0 ); + for (int x = -1; x <= 1; ++x) + for (int y = -1; y <= 1; ++y) + AddComponent(0x750, x, y, 0); - for ( int i = -1; i <= 1; ++i ) - { - AddComponent( 0x751, i, 2, 0 ); - AddComponent( 0x752, 2, i, 0 ); + for (int i = -1; i <= 1; ++i) + { + AddComponent(0x751, i, 2, 0); + AddComponent(0x752, 2, i, 0); - AddComponent( 0x753, i, -2, 0 ); - AddComponent( 0x754, -2, i, 0 ); - } + AddComponent(0x753, i, -2, 0); + AddComponent(0x754, -2, i, 0); + } - AddComponent( 0x759, -2, -2, 0 ); - AddComponent( 0x75A, 2, 2, 0 ); - AddComponent( 0x75B, -2, 2, 0 ); - AddComponent( 0x75C, 2, -2, 0 ); - } + AddComponent(0x759, -2, -2, 0); + AddComponent(0x75A, 2, 2, 0); + AddComponent(0x75B, -2, 2, 0); + AddComponent(0x75C, 2, -2, 0); + } - public void AddComponent( int id, int x, int y, int z ) - { - AddonComponent ac = new AddonComponent( id ); + public ChampionPlatform(Serial serial) : base(serial) + { + } - ac.Hue = 0x497; + public void AddComponent(int id, int x, int y, int z) + { + AddonComponent ac = new AddonComponent(id); - AddComponent( ac, x, y, z ); - } + ac.Hue = 0x497; - public override void OnAfterDelete() - { - base.OnAfterDelete(); + AddComponent(ac, x, y, z); + } - m_Spawn?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public ChampionPlatform( Serial serial ) : base( serial ) - { - } + m_Spawn?.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Spawn ); - } + writer.Write(m_Spawn); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Spawn = reader.ReadItem() as ChampionSpawn; + switch (version) + { + case 0: + { + m_Spawn = reader.ReadItem() as ChampionSpawn; - if ( m_Spawn == null ) - Delete(); + if (m_Spawn == null) + Delete(); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionSkull.cs b/Scripts/Engines/CannedEvil/ChampionSkull.cs index 0c75fceb2..564071f04 100644 --- a/Scripts/Engines/CannedEvil/ChampionSkull.cs +++ b/Scripts/Engines/CannedEvil/ChampionSkull.cs @@ -2,71 +2,88 @@ using Server.Engines.CannedEvil; namespace Server.Items { - public class ChampionSkull : Item - { - private ChampionSkullType m_Type; + public class ChampionSkull : Item + { + private ChampionSkullType m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public ChampionSkullType Type{ get => m_Type; - set{ m_Type = value; InvalidateProperties(); } } + [Constructible] + public ChampionSkull(ChampionSkullType type) : base(0x1AE1) + { + m_Type = type; + LootType = LootType.Cursed; - public override int LabelNumber => 1049479 + (int)m_Type; + // TODO: All hue values + switch (type) + { + case ChampionSkullType.Power: + Hue = 0x159; + break; + case ChampionSkullType.Venom: + Hue = 0x172; + break; + case ChampionSkullType.Greed: + Hue = 0x1EE; + break; + case ChampionSkullType.Death: + Hue = 0x025; + break; + case ChampionSkullType.Pain: + Hue = 0x035; + break; + } + } - [Constructible] - public ChampionSkull( ChampionSkullType type ) : base( 0x1AE1 ) - { - m_Type = type; - LootType = LootType.Cursed; + public ChampionSkull(Serial serial) : base(serial) + { + } - // TODO: All hue values - switch ( type ) - { - case ChampionSkullType.Power: Hue = 0x159; break; - case ChampionSkullType.Venom: Hue = 0x172; break; - case ChampionSkullType.Greed: Hue = 0x1EE; break; - case ChampionSkullType.Death: Hue = 0x025; break; - case ChampionSkullType.Pain: Hue = 0x035; break; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public ChampionSkullType Type + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - public ChampionSkull( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1049479 + (int)m_Type; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) m_Type ); - } + writer.Write((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - case 0: - { - m_Type = (ChampionSkullType)reader.ReadInt(); + switch (version) + { + case 1: + case 0: + { + m_Type = (ChampionSkullType)reader.ReadInt(); - break; - } - } + break; + } + } - if ( version == 0 ) - { - if ( LootType != LootType.Cursed ) - LootType = LootType.Cursed; + if (version == 0) + { + if (LootType != LootType.Cursed) + LootType = LootType.Cursed; - if ( Insured ) - Insured = false; - } - } - } -} + if (Insured) + Insured = false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionSkullBrazier.cs b/Scripts/Engines/CannedEvil/ChampionSkullBrazier.cs index 2a98690c5..22440bee1 100644 --- a/Scripts/Engines/CannedEvil/ChampionSkullBrazier.cs +++ b/Scripts/Engines/CannedEvil/ChampionSkullBrazier.cs @@ -1,172 +1,184 @@ using Server.Items; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Engines.CannedEvil { - public class ChampionSkullBrazier : AddonComponent - { - private ChampionSkullType m_Type; - private Item m_Skull; + public class ChampionSkullBrazier : AddonComponent + { + private Item m_Skull; + private ChampionSkullType m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public ChampionSkullPlatform Platform { get; private set; } + public ChampionSkullBrazier(ChampionSkullPlatform platform, ChampionSkullType type) : base(0x19BB) + { + Hue = 0x455; + Light = LightType.Circle300; - [CommandProperty( AccessLevel.GameMaster )] - public ChampionSkullType Type{ get => m_Type; - set{ m_Type = value; InvalidateProperties(); } } + Platform = platform; + m_Type = type; + } - [CommandProperty( AccessLevel.GameMaster )] - public Item Skull{ get => m_Skull; - set{ m_Skull = value; - Platform?.Validate(); - } } + public ChampionSkullBrazier(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1049489 + (int)m_Type; + [CommandProperty(AccessLevel.GameMaster)] + public ChampionSkullPlatform Platform{ get; private set; } - public ChampionSkullBrazier( ChampionSkullPlatform platform, ChampionSkullType type ) : base( 0x19BB ) - { - Hue = 0x455; - Light = LightType.Circle300; + [CommandProperty(AccessLevel.GameMaster)] + public ChampionSkullType Type + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - Platform = platform; - m_Type = type; - } + [CommandProperty(AccessLevel.GameMaster)] + public Item Skull + { + get => m_Skull; + set + { + m_Skull = value; + Platform?.Validate(); + } + } - public ChampionSkullBrazier( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1049489 + (int)m_Type; - public override void OnDoubleClick( Mobile from ) - { - Platform?.Validate(); + public override void OnDoubleClick(Mobile from) + { + Platform?.Validate(); - BeginSacrifice( from ); - } + BeginSacrifice(from); + } - public void BeginSacrifice( Mobile from ) - { - if ( Deleted ) - return; + public void BeginSacrifice(Mobile from) + { + if (Deleted) + return; - if ( m_Skull != null && m_Skull.Deleted ) - Skull = null; + if (m_Skull != null && m_Skull.Deleted) + Skull = null; - if ( from.Map != Map || !from.InRange( GetWorldLocation(), 3 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( !Harrower.CanSpawn ) - { - from.SendMessage( "The harrower has already been spawned." ); - } - else if ( m_Skull == null ) - { - from.SendLocalizedMessage( 1049485 ); // What would you like to sacrifice? - from.Target = new SacrificeTarget( this ); - } - else - { - SendLocalizedMessageTo( from, 1049487, "" ); // I already have my champions awakening skull! - } - } + if (from.Map != Map || !from.InRange(GetWorldLocation(), 3)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (!Harrower.CanSpawn) + { + from.SendMessage("The harrower has already been spawned."); + } + else if (m_Skull == null) + { + from.SendLocalizedMessage(1049485); // What would you like to sacrifice? + from.Target = new SacrificeTarget(this); + } + else + { + SendLocalizedMessageTo(from, 1049487, ""); // I already have my champions awakening skull! + } + } - public void EndSacrifice( Mobile from, ChampionSkull skull ) - { - if ( Deleted ) - return; + public void EndSacrifice(Mobile from, ChampionSkull skull) + { + if (Deleted) + return; - if ( m_Skull != null && m_Skull.Deleted ) - Skull = null; + if (m_Skull != null && m_Skull.Deleted) + Skull = null; - if ( from.Map != Map || !from.InRange( GetWorldLocation(), 3 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( !Harrower.CanSpawn ) - { - from.SendMessage( "The harrower has already been spawned." ); - } - else if ( skull == null ) - { - SendLocalizedMessageTo( from, 1049488, "" ); // That is not my champions awakening skull! - } - else if ( m_Skull != null ) - { - SendLocalizedMessageTo( from, 1049487, "" ); // I already have my champions awakening skull! - } - else if ( !skull.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1049486 ); // You can only sacrifice items that are in your backpack! - } - else - { - if ( skull.Type == Type ) - { - skull.Movable = false; - skull.MoveToWorld( GetWorldTop(), Map ); + if (from.Map != Map || !from.InRange(GetWorldLocation(), 3)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (!Harrower.CanSpawn) + { + from.SendMessage("The harrower has already been spawned."); + } + else if (skull == null) + { + SendLocalizedMessageTo(from, 1049488, ""); // That is not my champions awakening skull! + } + else if (m_Skull != null) + { + SendLocalizedMessageTo(from, 1049487, ""); // I already have my champions awakening skull! + } + else if (!skull.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1049486); // You can only sacrifice items that are in your backpack! + } + else + { + if (skull.Type == Type) + { + skull.Movable = false; + skull.MoveToWorld(GetWorldTop(), Map); - Skull = skull; - } - else - { - SendLocalizedMessageTo( from, 1049488, "" ); // That is not my champions awakening skull! - } - } - } + Skull = skull; + } + else + { + SendLocalizedMessageTo(from, 1049488, ""); // That is not my champions awakening skull! + } + } + } - private class SacrificeTarget : Target - { - private ChampionSkullBrazier m_Brazier; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public SacrificeTarget( ChampionSkullBrazier brazier ) : base( 12, false, TargetFlags.None ) - { - m_Brazier = brazier; - } + writer.Write(0); // version - protected override void OnTarget( Mobile from, object targeted ) - { - m_Brazier.EndSacrifice( from, targeted as ChampionSkull ); - } - } + writer.Write((int)m_Type); + writer.Write(Platform); + writer.Write(m_Skull); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version + int version = reader.ReadInt(); - writer.Write( (int) m_Type ); - writer.Write( Platform ); - writer.Write( m_Skull ); - } + switch (version) + { + case 0: + { + m_Type = (ChampionSkullType)reader.ReadInt(); + Platform = reader.ReadItem() as ChampionSkullPlatform; + m_Skull = reader.ReadItem(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (Platform == null) + Delete(); - int version = reader.ReadInt(); + break; + } + } - switch ( version ) - { - case 0: - { - m_Type = (ChampionSkullType)reader.ReadInt(); - Platform = reader.ReadItem() as ChampionSkullPlatform; - m_Skull = reader.ReadItem(); + if (Hue == 0x497) + Hue = 0x455; - if ( Platform == null ) - Delete(); + if (Light != LightType.Circle300) + Light = LightType.Circle300; + } - break; - } - } + private class SacrificeTarget : Target + { + private ChampionSkullBrazier m_Brazier; - if ( Hue == 0x497 ) - Hue = 0x455; + public SacrificeTarget(ChampionSkullBrazier brazier) : base(12, false, TargetFlags.None) + { + m_Brazier = brazier; + } - if ( Light != LightType.Circle300 ) - Light = LightType.Circle300; - } - } -} + protected override void OnTarget(Mobile from, object targeted) + { + m_Brazier.EndSacrifice(from, targeted as ChampionSkull); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionSkullPlatform.cs b/Scripts/Engines/CannedEvil/ChampionSkullPlatform.cs index b9a7096da..6b3872606 100644 --- a/Scripts/Engines/CannedEvil/ChampionSkullPlatform.cs +++ b/Scripts/Engines/CannedEvil/ChampionSkullPlatform.cs @@ -3,125 +3,126 @@ using Server.Mobiles; namespace Server.Engines.CannedEvil { - public class ChampionSkullPlatform : BaseAddon - { - private ChampionSkullBrazier m_Power, m_Enlightenment, m_Venom, m_Pain, m_Greed, m_Death; + public class ChampionSkullPlatform : BaseAddon + { + private ChampionSkullBrazier m_Power, m_Enlightenment, m_Venom, m_Pain, m_Greed, m_Death; - [Constructible] - public ChampionSkullPlatform() - { - AddComponent( new AddonComponent( 0x71A ), -1, -1, -1 ); - AddComponent( new AddonComponent( 0x709 ), 0, -1, -1 ); - AddComponent( new AddonComponent( 0x709 ), 1, -1, -1 ); - AddComponent( new AddonComponent( 0x709 ), -1, 0, -1 ); - AddComponent( new AddonComponent( 0x709 ), 0, 0, -1 ); - AddComponent( new AddonComponent( 0x709 ), 1, 0, -1 ); - AddComponent( new AddonComponent( 0x709 ), -1, 1, -1 ); - AddComponent( new AddonComponent( 0x709 ), 0, 1, -1 ); - AddComponent( new AddonComponent( 0x71B ), 1, 1, -1 ); + [Constructible] + public ChampionSkullPlatform() + { + AddComponent(new AddonComponent(0x71A), -1, -1, -1); + AddComponent(new AddonComponent(0x709), 0, -1, -1); + AddComponent(new AddonComponent(0x709), 1, -1, -1); + AddComponent(new AddonComponent(0x709), -1, 0, -1); + AddComponent(new AddonComponent(0x709), 0, 0, -1); + AddComponent(new AddonComponent(0x709), 1, 0, -1); + AddComponent(new AddonComponent(0x709), -1, 1, -1); + AddComponent(new AddonComponent(0x709), 0, 1, -1); + AddComponent(new AddonComponent(0x71B), 1, 1, -1); - AddComponent( new AddonComponent( 0x50F ), 0, -1, 4 ); - AddComponent( m_Power = new ChampionSkullBrazier( this, ChampionSkullType.Power ), 0, -1, 5 ); + AddComponent(new AddonComponent(0x50F), 0, -1, 4); + AddComponent(m_Power = new ChampionSkullBrazier(this, ChampionSkullType.Power), 0, -1, 5); - AddComponent( new AddonComponent( 0x50F ), 1, -1, 4 ); - AddComponent( m_Enlightenment = new ChampionSkullBrazier( this, ChampionSkullType.Enlightenment ), 1, -1, 5 ); + AddComponent(new AddonComponent(0x50F), 1, -1, 4); + AddComponent(m_Enlightenment = new ChampionSkullBrazier(this, ChampionSkullType.Enlightenment), 1, -1, 5); - AddComponent( new AddonComponent( 0x50F ), -1, 0, 4 ); - AddComponent( m_Venom = new ChampionSkullBrazier( this, ChampionSkullType.Venom ), -1, 0, 5 ); + AddComponent(new AddonComponent(0x50F), -1, 0, 4); + AddComponent(m_Venom = new ChampionSkullBrazier(this, ChampionSkullType.Venom), -1, 0, 5); - AddComponent( new AddonComponent( 0x50F ), 1, 0, 4 ); - AddComponent( m_Pain = new ChampionSkullBrazier( this, ChampionSkullType.Pain ), 1, 0, 5 ); + AddComponent(new AddonComponent(0x50F), 1, 0, 4); + AddComponent(m_Pain = new ChampionSkullBrazier(this, ChampionSkullType.Pain), 1, 0, 5); - AddComponent( new AddonComponent( 0x50F ), -1, 1, 4 ); - AddComponent( m_Greed = new ChampionSkullBrazier( this, ChampionSkullType.Greed ), -1, 1, 5 ); + AddComponent(new AddonComponent(0x50F), -1, 1, 4); + AddComponent(m_Greed = new ChampionSkullBrazier(this, ChampionSkullType.Greed), -1, 1, 5); - AddComponent( new AddonComponent( 0x50F ), 0, 1, 4 ); - AddComponent( m_Death = new ChampionSkullBrazier( this, ChampionSkullType.Death ), 0, 1, 5 ); + AddComponent(new AddonComponent(0x50F), 0, 1, 4); + AddComponent(m_Death = new ChampionSkullBrazier(this, ChampionSkullType.Death), 0, 1, 5); - AddonComponent comp = new LocalizedAddonComponent( 0x20D2, 1049495 ); - comp.Hue = 0x482; - AddComponent( comp, 0, 0, 5 ); + AddonComponent comp = new LocalizedAddonComponent(0x20D2, 1049495); + comp.Hue = 0x482; + AddComponent(comp, 0, 0, 5); - comp = new LocalizedAddonComponent( 0x0BCF, 1049496 ); - comp.Hue = 0x482; - AddComponent( comp, 0, 2, -7 ); + comp = new LocalizedAddonComponent(0x0BCF, 1049496); + comp.Hue = 0x482; + AddComponent(comp, 0, 2, -7); - comp = new LocalizedAddonComponent( 0x0BD0, 1049497 ); - comp.Hue = 0x482; - AddComponent( comp, 2, 0, -7 ); - } + comp = new LocalizedAddonComponent(0x0BD0, 1049497); + comp.Hue = 0x482; + AddComponent(comp, 2, 0, -7); + } - public void Validate() - { - if ( Validate( m_Power ) && Validate( m_Enlightenment ) && Validate( m_Venom ) && Validate( m_Pain ) && Validate( m_Greed ) && Validate( m_Death ) ) - { - Mobile harrower = Harrower.Spawn( new Point3D( X, Y, Z + 6 ), Map ); + public ChampionSkullPlatform(Serial serial) : base(serial) + { + } - if ( harrower == null ) - return; + public void Validate() + { + if (Validate(m_Power) && Validate(m_Enlightenment) && Validate(m_Venom) && Validate(m_Pain) && + Validate(m_Greed) && Validate(m_Death)) + { + Mobile harrower = Harrower.Spawn(new Point3D(X, Y, Z + 6), Map); - Clear( m_Power ); - Clear( m_Enlightenment ); - Clear( m_Venom ); - Clear( m_Pain ); - Clear( m_Greed ); - Clear( m_Death ); - } - } + if (harrower == null) + return; - public void Clear( ChampionSkullBrazier brazier ) - { - if ( brazier != null ) - { - Effects.SendBoltEffect( brazier ); + Clear(m_Power); + Clear(m_Enlightenment); + Clear(m_Venom); + Clear(m_Pain); + Clear(m_Greed); + Clear(m_Death); + } + } - brazier.Skull?.Delete(); - } - } + public void Clear(ChampionSkullBrazier brazier) + { + if (brazier != null) + { + Effects.SendBoltEffect(brazier); - public bool Validate( ChampionSkullBrazier brazier ) - { - return ( brazier?.Skull != null && !brazier.Skull.Deleted ); - } + brazier.Skull?.Delete(); + } + } - public ChampionSkullPlatform( Serial serial ) : base( serial ) - { - } + public bool Validate(ChampionSkullBrazier brazier) + { + return brazier?.Skull != null && !brazier.Skull.Deleted; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Power ); - writer.Write( m_Enlightenment ); - writer.Write( m_Venom ); - writer.Write( m_Pain ); - writer.Write( m_Greed ); - writer.Write( m_Death ); - } + writer.Write(m_Power); + writer.Write(m_Enlightenment); + writer.Write(m_Venom); + writer.Write(m_Pain); + writer.Write(m_Greed); + writer.Write(m_Death); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Power = reader.ReadItem() as ChampionSkullBrazier; - m_Enlightenment = reader.ReadItem() as ChampionSkullBrazier; - m_Venom = reader.ReadItem() as ChampionSkullBrazier; - m_Pain = reader.ReadItem() as ChampionSkullBrazier; - m_Greed = reader.ReadItem() as ChampionSkullBrazier; - m_Death = reader.ReadItem() as ChampionSkullBrazier; + switch (version) + { + case 0: + { + m_Power = reader.ReadItem() as ChampionSkullBrazier; + m_Enlightenment = reader.ReadItem() as ChampionSkullBrazier; + m_Venom = reader.ReadItem() as ChampionSkullBrazier; + m_Pain = reader.ReadItem() as ChampionSkullBrazier; + m_Greed = reader.ReadItem() as ChampionSkullBrazier; + m_Death = reader.ReadItem() as ChampionSkullBrazier; - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionSkullType.cs b/Scripts/Engines/CannedEvil/ChampionSkullType.cs index 8874cf5d0..797b368cb 100644 --- a/Scripts/Engines/CannedEvil/ChampionSkullType.cs +++ b/Scripts/Engines/CannedEvil/ChampionSkullType.cs @@ -1,12 +1,12 @@ namespace Server.Engines.CannedEvil { - public enum ChampionSkullType - { - Power, - Enlightenment, - Venom, - Pain, - Greed, - Death - } + public enum ChampionSkullType + { + Power, + Enlightenment, + Venom, + Pain, + Greed, + Death + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionSpawn.cs b/Scripts/Engines/CannedEvil/ChampionSpawn.cs index 1bace0251..1fb2ecfab 100644 --- a/Scripts/Engines/CannedEvil/ChampionSpawn.cs +++ b/Scripts/Engines/CannedEvil/ChampionSpawn.cs @@ -1,1223 +1,1246 @@ using System; +using System.Collections.Generic; using Server.Gumps; using Server.Items; using Server.Mobiles; using Server.Regions; -using System.Collections.Generic; namespace Server.Engines.CannedEvil { - public class ChampionSpawn : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public int SpawnSzMod - { - get => ( m_SPawnSzMod < 1 || m_SPawnSzMod > 12 ) ? 12 : m_SPawnSzMod; - set => m_SPawnSzMod = ( value < 1 || value > 12 ) ? 12 : value; - } - private int m_SPawnSzMod; - - private bool m_Active; - private ChampionSpawnType m_Type; - private List m_Creatures; - private List m_RedSkulls; - private List m_WhiteSkulls; - private ChampionPlatform m_Platform; - private ChampionAltar m_Altar; - private int m_Kills; - - //private int m_SpawnRange; - private Rectangle2D m_SpawnArea; - private ChampionSpawnRegion m_Region; - - private Timer m_Timer, m_RestartTimer; - - private IdolOfTheChampion m_Idol; - - private Dictionary m_DamageEntries; - - [CommandProperty( AccessLevel.GameMaster )] - public bool ConfinedRoaming { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool HasBeenAdvanced { get; set; } - - [Constructible] - public ChampionSpawn() : base( 0xBD2 ) - { - Movable = false; - Visible = false; - - m_Creatures = new List(); - m_RedSkulls = new List(); - m_WhiteSkulls = new List(); - - m_Platform = new ChampionPlatform( this ); - m_Altar = new ChampionAltar( this ); - m_Idol = new IdolOfTheChampion( this ); - - ExpireDelay = TimeSpan.FromMinutes( 10.0 ); - RestartDelay = TimeSpan.FromMinutes( 10.0 ); - - m_DamageEntries = new Dictionary(); - - Timer.DelayCall( TimeSpan.Zero, SetInitialSpawnArea ); - } - - public void SetInitialSpawnArea() - { - //Previous default used to be 24; - SpawnArea = new Rectangle2D( new Point2D( X - 24, Y - 24 ), new Point2D( X + 24, Y + 24 ) ); - } - - public void UpdateRegion() - { - m_Region?.Unregister(); - - if ( !Deleted && Map != Map.Internal ) - { - m_Region = new ChampionSpawnRegion( this ); - m_Region.Register(); - } - - /* - if ( m_Region == null ) - { - m_Region = new ChampionSpawnRegion( this ); - } - else - { - m_Region.Unregister(); - //Why doesn't Region allow me to set it's map/Area myself? >< - m_Region = new ChampionSpawnRegion( this ); - } - */ - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool RandomizeType { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Kills - { - get => m_Kills; - set - { - m_Kills = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Rectangle2D SpawnArea - { - get => m_SpawnArea; - set - { - m_SpawnArea = value; - InvalidateProperties(); - UpdateRegion(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan RestartDelay { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime RestartTime { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan ExpireDelay { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime ExpireTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public ChampionSpawnType Type - { - get => m_Type; - set - { - m_Type = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Active - { - get => m_Active; - set - { - if ( value ) - Start(); - else - Stop(); - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Champion { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Level - { - get => m_RedSkulls.Count; - set - { - for( int i = m_RedSkulls.Count - 1; i >= value; --i ) - { - m_RedSkulls[i].Delete(); - m_RedSkulls.RemoveAt( i ); - } - - for( int i = m_RedSkulls.Count; i < value; ++i ) - { - Item skull = new Item( 0x1854 ); - - skull.Hue = 0x26; - skull.Movable = false; - skull.Light = LightType.Circle150; - - skull.MoveToWorld( GetRedSkullLocation( i ), Map ); - - m_RedSkulls.Add( skull ); - } - - InvalidateProperties(); - } - } - - public int MaxKills => ( m_SPawnSzMod * ( 250 / 12 ) ) - ( Level * m_SPawnSzMod ); - - public bool IsChampionSpawn( Mobile m ) - { - return m_Creatures.Contains( m ); - } - - public void SetWhiteSkullCount( int val ) - { - for( int i = m_WhiteSkulls.Count - 1; i >= val; --i ) - { - m_WhiteSkulls[i].Delete(); - m_WhiteSkulls.RemoveAt( i ); - } - - for( int i = m_WhiteSkulls.Count; i < val; ++i ) - { - Item skull = new Item( 0x1854 ); - - skull.Movable = false; - skull.Light = LightType.Circle150; - - skull.MoveToWorld( GetWhiteSkullLocation( i ), Map ); - - m_WhiteSkulls.Add( skull ); - - Effects.PlaySound( skull.Location, skull.Map, 0x29 ); - Effects.SendLocationEffect( new Point3D( skull.X + 1, skull.Y + 1, skull.Z ), skull.Map, 0x3728, 10 ); - } - } - - public void Start() - { - if ( m_Active || Deleted ) - return; - - m_Active = true; - HasBeenAdvanced = false; - - m_Timer?.Stop(); - - m_Timer = new SliceTimer( this ); - m_Timer.Start(); - - m_RestartTimer?.Stop(); - - m_RestartTimer = null; - - if ( m_Altar != null ) - { - if ( Champion != null ) - m_Altar.Hue = 0x26; - else - m_Altar.Hue = 0; - } - - if ( m_Platform != null ) - m_Platform.Hue = 0x452; - } - - public void Stop() - { - if ( !m_Active || Deleted ) - return; - - m_Active = false; - HasBeenAdvanced = false; - - m_Timer?.Stop(); - - m_Timer = null; - - m_RestartTimer?.Stop(); - - m_RestartTimer = null; - - if ( m_Altar != null ) - m_Altar.Hue = 0; - - if ( m_Platform != null ) - m_Platform.Hue = 0x497; - } - - public void BeginRestart( TimeSpan ts ) - { - m_RestartTimer?.Stop(); - - RestartTime = DateTime.UtcNow + ts; - - m_RestartTimer = new RestartTimer( this, ts ); - m_RestartTimer.Start(); - } - - public void EndRestart() - { - if ( RandomizeType ) - { - switch( Utility.Random( 5 ) ) - { - case 0: Type = ChampionSpawnType.VerminHorde; break; - case 1: Type = ChampionSpawnType.UnholyTerror; break; - case 2: Type = ChampionSpawnType.ColdBlood; break; - case 3: Type = ChampionSpawnType.Abyss; break; - case 4: Type = ChampionSpawnType.Arachnid; break; - } - } - - HasBeenAdvanced = false; - - Start(); - } - - #region Scroll of Transcendence - private ScrollofTranscendence CreateRandomSoT( bool felucca ) - { - int level = Utility.RandomMinMax( 1, 5 ); - - if ( felucca ) - level += 5; - - return ScrollofTranscendence.CreateRandom(level, level); - } - #endregion - - public static void GiveScrollTo( Mobile killer, SpecialScroll scroll ) - { - if ( scroll == null || killer == null ) //sanity - return; - - if ( scroll is ScrollofTranscendence ) - killer.SendLocalizedMessage( 1094936 ); // You have received a Scroll of Transcendence! - else - killer.SendLocalizedMessage( 1049524 ); // You have received a scroll of power! - - if ( killer.Alive ) - killer.AddToBackpack( scroll ); - else - { - if ( killer.Corpse != null && !killer.Corpse.Deleted ) - killer.Corpse.DropItem( scroll ); - else - killer.AddToBackpack( scroll ); - } - - // Justice reward - PlayerMobile pm = (PlayerMobile)killer; - for (int j = 0; j < pm.JusticeProtectors.Count; ++j) - { - Mobile prot = (Mobile)pm.JusticeProtectors[j]; - - if ( prot.Map != killer.Map || prot.Kills >= 5 || prot.Criminal || !JusticeVirtue.CheckMapRegion( killer, prot ) ) - continue; - - int chance = 0; - - switch ( VirtueHelper.GetLevel( prot, VirtueName.Justice ) ) - { - case VirtueLevel.Seeker: chance = 60; break; - case VirtueLevel.Follower: chance = 80; break; - case VirtueLevel.Knight: chance = 100; break; - } - - if ( chance > Utility.Random( 100 ) ) - { - try - { - prot.SendLocalizedMessage( 1049368 ); // You have been rewarded for your dedication to Justice! - - if ( Activator.CreateInstance( scroll.GetType() ) is SpecialScroll scrollDupe ) - { - scrollDupe.Skill = scroll.Skill; - scrollDupe.Value = scroll.Value; - prot.AddToBackpack( scrollDupe ); - } - } - catch{} - } - } - } - - public void OnSlice() - { - if ( !m_Active || Deleted ) - return; - - if ( Champion != null ) - { - if ( Champion.Deleted ) - { - RegisterDamageTo( Champion ); - - if ( Champion is BaseChampion champion ) - AwardArtifact( champion.GetArtifact() ); - - m_DamageEntries.Clear(); - - if ( m_Platform != null ) - m_Platform.Hue = 0x497; - - if ( m_Altar != null ) - { - m_Altar.Hue = 0; - - if ( !Core.ML || Map == Map.Felucca ) - { - new StarRoomGate( true, m_Altar.Location, m_Altar.Map ); - } - } - - Champion = null; - Stop(); - - BeginRestart( RestartDelay ); - } - } - else - { - int kills = m_Kills; - - for ( int i = 0; i < m_Creatures.Count; ++i ) - { - Mobile m = m_Creatures[i]; - - if ( m.Deleted ) - { - if ( m.Corpse != null && !m.Corpse.Deleted ) - { - ((Corpse)m.Corpse).BeginDecay( TimeSpan.FromMinutes( 1 )); - } - m_Creatures.RemoveAt( i ); - --i; - ++m_Kills; - - Mobile killer = m.FindMostRecentDamager( false ); - - RegisterDamageTo( m ); - - if ( killer is BaseCreature bc ) - killer = bc.GetMaster(); - - if ( killer is PlayerMobile pm ) - { - #region Scroll of Transcendence - if ( Core.ML ) - { - if ( Map == Map.Felucca ) - { - if ( Utility.RandomDouble() < 0.001 ) - { - double random = Utility.Random ( 49 ); - - if ( random <= 24 ) - { - ScrollofTranscendence SoTF = CreateRandomSoT( true ); - GiveScrollTo( pm, (SpecialScroll)SoTF ); - } - else - { - PowerScroll PS = PowerScroll.CreateRandomNoCraft(5, 5); - GiveScrollTo( pm, (SpecialScroll)PS ); - } - } - } - - if ( Map == Map.Ilshenar || Map == Map.Tokuno || Map == Map.Malas ) - { - if ( Utility.RandomDouble() < 0.0015 ) - { - pm.SendLocalizedMessage( 1094936 ); // You have received a Scroll of Transcendence! - ScrollofTranscendence SoTT = CreateRandomSoT( false ); - pm.AddToBackpack( SoTT ); - } - } - } - #endregion - - int mobSubLevel = GetSubLevelFor( m ) + 1; - - if ( mobSubLevel >= 0 ) - { - bool gainedPath = false; - - int pointsToGain = mobSubLevel * 40; - - if ( VirtueHelper.Award( pm, VirtueName.Valor, pointsToGain, ref gainedPath ) ) - { - if ( gainedPath ) - m.SendLocalizedMessage( 1054032 ); // You have gained a path in Valor! - else - m.SendLocalizedMessage( 1054030 ); // You have gained in Valor! - - //No delay on Valor gains - } - - PlayerMobile.ChampionTitleInfo info = pm.ChampionTitles; - - info.Award( m_Type, mobSubLevel ); - } - } - } - } - - // Only really needed once. - if ( m_Kills > kills ) - InvalidateProperties(); - - double n = m_Kills / (double)MaxKills; - int p = (int)(n * 100); - - if ( p >= 90 ) - AdvanceLevel(); - else if ( p > 0 ) - SetWhiteSkullCount( p / 20 ); - - if ( DateTime.UtcNow >= ExpireTime ) - Expire(); - - Respawn(); - } - } - - public void AdvanceLevel() - { - ExpireTime = DateTime.UtcNow + ExpireDelay; - - if ( Level < 16 ) - { - m_Kills = 0; - ++Level; - InvalidateProperties(); - SetWhiteSkullCount( 0 ); - - if ( m_Altar != null ) - { - Effects.PlaySound( m_Altar.Location, m_Altar.Map, 0x29 ); - Effects.SendLocationEffect( new Point3D( m_Altar.X + 1, m_Altar.Y + 1, m_Altar.Z ), m_Altar.Map, 0x3728, 10 ); - } - } - else - { - SpawnChampion(); - } - } - - public void SpawnChampion() - { - if ( m_Altar != null ) - m_Altar.Hue = 0x26; - - if ( m_Platform != null ) - m_Platform.Hue = 0x452; - - m_Kills = 0; - Level = 0; - InvalidateProperties(); - SetWhiteSkullCount( 0 ); - - try - { - Champion = Activator.CreateInstance( ChampionSpawnInfo.GetInfo( m_Type ).Champion ) as Mobile; - } - catch { } - - Champion?.MoveToWorld( new Point3D( X, Y, Z - 15 ), Map ); - } - - public void Respawn() - { - if ( !m_Active || Deleted || Champion != null ) - return; - - while( m_Creatures.Count < ( ( m_SPawnSzMod * ( 200 / 12 ) ) ) - ( GetSubLevel() * ( m_SPawnSzMod * ( 40 / 12 ) ) ) ) - { - Mobile m = Spawn(); - - if ( m == null ) - return; - - Point3D loc = GetSpawnLocation(); - - // Allow creatures to turn into Paragons at Ilshenar champions. - m.OnBeforeSpawn( loc, Map ); - - m_Creatures.Add( m ); - m.MoveToWorld( loc, Map ); - - if ( m is BaseCreature bc ) - { - bc.Tamable = false; - - if ( !ConfinedRoaming ) - { - bc.Home = Location; - bc.RangeHome = (int)(Math.Sqrt( m_SpawnArea.Width * m_SpawnArea.Width + m_SpawnArea.Height * m_SpawnArea.Height )/2); - } - else - { - bc.Home = bc.Location; - - Point2D xWall1 = new Point2D( m_SpawnArea.X, bc.Y ); - Point2D xWall2 = new Point2D( m_SpawnArea.X + m_SpawnArea.Width, bc.Y ); - Point2D yWall1 = new Point2D( bc.X, m_SpawnArea.Y ); - Point2D yWall2 = new Point2D( bc.X, m_SpawnArea.Y + m_SpawnArea.Height ); - - double minXDist = Math.Min( bc.GetDistanceToSqrt( xWall1 ), bc.GetDistanceToSqrt( xWall2 ) ); - double minYDist = Math.Min( bc.GetDistanceToSqrt( yWall1 ), bc.GetDistanceToSqrt( yWall2 ) ); - - bc.RangeHome = (int)Math.Min( minXDist, minYDist ); - } - } - } - } - - public Point3D GetSpawnLocation() - { - Map map = Map; - - if ( map == null ) - return Location; - - // Try 20 times to find a spawnable location. - for( int i = 0; i < 20; i++ ) - { - /* - int x = Location.X + (Utility.Random( (m_SpawnRange * 2) + 1 ) - m_SpawnRange); - int y = Location.Y + (Utility.Random( (m_SpawnRange * 2) + 1 ) - m_SpawnRange); - */ - - int x = Utility.Random( m_SpawnArea.X, m_SpawnArea.Width ); - int y = Utility.Random( m_SpawnArea.Y, m_SpawnArea.Height ); - - int z = Map.GetAverageZ( x, y ); - - if ( Map.CanSpawnMobile( new Point2D( x, y ), z ) ) - return new Point3D( x, y, z ); - - /* try @ platform Z if map z fails */ - if ( Map.CanSpawnMobile( new Point2D( x, y ), m_Platform.Location.Z ) ) - return new Point3D( x, y, m_Platform.Location.Z ); - } - - return Location; - } - - private const int Level1 = 4; // First spawn level from 0-4 red skulls - private const int Level2 = 8; // Second spawn level from 5-8 red skulls - private const int Level3 = 12; // Third spawn level from 9-12 red skulls - - public int GetSubLevel() - { - int level = Level; - - if ( level <= Level1 ) - return 0; - if ( level <= Level2 ) - return 1; - if ( level <= Level3 ) - return 2; - - return 3; - } - - public int GetSubLevelFor( Mobile m ) - { - Type[][] types = ChampionSpawnInfo.GetInfo( m_Type ).SpawnTypes; - Type t = m.GetType(); - - for( int i = 0; i < types.GetLength( 0 ); i++ ) - { - Type[] individualTypes = types[i]; - - for( int j = 0; j < individualTypes.Length; j++ ) - { - if ( t == individualTypes[j] ) - return i; - } - } - - return -1; - } - - public Mobile Spawn() - { - Type[][] types = ChampionSpawnInfo.GetInfo( m_Type ).SpawnTypes; - - int v = GetSubLevel(); - - if ( v >= 0 && v < types.Length ) - return Spawn( types[v] ); - - return null; - } - - public Mobile Spawn( params Type[] types ) - { - try - { - return Activator.CreateInstance( types[Utility.Random( types.Length )] ) as Mobile; - } - catch - { - return null; - } - } - - public void Expire() - { - m_Kills = 0; - - if ( m_WhiteSkulls.Count == 0 ) - { - // They didn't even get 20%, go back a level - - if ( Level > 0 ) - --Level; - - InvalidateProperties(); - } - else - { - SetWhiteSkullCount( 0 ); - } - - ExpireTime = DateTime.UtcNow + ExpireDelay; - } - - public Point3D GetRedSkullLocation( int index ) - { - int x, y; - - if ( index < 5 ) - { - x = index - 2; - y = -2; - } - else if ( index < 9 ) - { - x = 2; - y = index - 6; - } - else if ( index < 13 ) - { - x = 10 - index; - y = 2; - } - else - { - x = -2; - y = 14 - index; - } - - return new Point3D( X + x, Y + y, Z - 15 ); - } - - public Point3D GetWhiteSkullLocation( int index ) - { - int x, y; - - switch( index ) - { - default: - case 0: x = -1; y = -1; break; - case 1: x = 1; y = -1; break; - case 2: x = 1; y = 1; break; - case 3: x = -1; y = 1; break; - } - - return new Point3D( X + x, Y + y, Z - 15 ); - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( "champion spawn" ); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_Active ) - { - list.Add( 1060742 ); // active - list.Add( 1060658, "Type\t{0}", m_Type ); // ~1_val~: ~2_val~ - list.Add( 1060659, "Level\t{0}", Level ); // ~1_val~: ~2_val~ - list.Add( 1060660, "Kills\t{0} of {1} ({2:F1}%)", m_Kills, MaxKills, 100.0 * ((double)m_Kills / MaxKills) ); // ~1_val~: ~2_val~ - //list.Add( 1060661, "Spawn Range\t{0}", m_SpawnRange ); // ~1_val~: ~2_val~ - } - else - { - list.Add( 1060743 ); // inactive - } - } - - public override void OnSingleClick( Mobile from ) - { - if ( m_Active ) - LabelTo( from, "{0} (Active; Level: {1}; Kills: {2}/{3})", m_Type, Level, m_Kills, MaxKills ); - else - LabelTo( from, "{0} (Inactive)", m_Type ); - } - - public override void OnDoubleClick( Mobile from ) - { - from.SendGump( new PropertiesGump( from, this ) ); - } - - public override void OnLocationChange( Point3D oldLoc ) - { - if ( Deleted ) - return; - - if ( m_Platform != null ) - m_Platform.Location = new Point3D( X, Y, Z - 20 ); - - if ( m_Altar != null ) - m_Altar.Location = new Point3D( X, Y, Z - 15 ); - - if ( m_Idol != null ) - m_Idol.Location = new Point3D( X, Y, Z - 15 ); - - if ( m_RedSkulls != null ) - { - for( int i = 0; i < m_RedSkulls.Count; ++i ) - m_RedSkulls[i].Location = GetRedSkullLocation( i ); - } - - if ( m_WhiteSkulls != null ) - { - for( int i = 0; i < m_WhiteSkulls.Count; ++i ) - m_WhiteSkulls[i].Location = GetWhiteSkullLocation( i ); - } - - m_SpawnArea.X += Location.X - oldLoc.X; - m_SpawnArea.Y += Location.Y - oldLoc.Y; - - UpdateRegion(); - } - - public override void OnMapChange() - { - if ( Deleted ) - return; - - if ( m_Platform != null ) - m_Platform.Map = Map; - - if ( m_Altar != null ) - m_Altar.Map = Map; - - if ( m_Idol != null ) - m_Idol.Map = Map; - - if ( m_RedSkulls != null ) - { - for( int i = 0; i < m_RedSkulls.Count; ++i ) - m_RedSkulls[i].Map = Map; - } - - if ( m_WhiteSkulls != null ) - { - for( int i = 0; i < m_WhiteSkulls.Count; ++i ) - m_WhiteSkulls[i].Map = Map; - } - - UpdateRegion(); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Platform?.Delete(); - - m_Altar?.Delete(); - - m_Idol?.Delete(); - - if ( m_RedSkulls != null ) - { - for( int i = 0; i < m_RedSkulls.Count; ++i ) - m_RedSkulls[i].Delete(); - - m_RedSkulls.Clear(); - } - - if ( m_WhiteSkulls != null ) - { - for( int i = 0; i < m_WhiteSkulls.Count; ++i ) - m_WhiteSkulls[i].Delete(); + public class ChampionSpawn : Item + { + private const int Level1 = 4; // First spawn level from 0-4 red skulls + private const int Level2 = 8; // Second spawn level from 5-8 red skulls + private const int Level3 = 12; // Third spawn level from 9-12 red skulls + + private bool m_Active; + private ChampionAltar m_Altar; + private List m_Creatures; + + private Dictionary m_DamageEntries; + + private IdolOfTheChampion m_Idol; + private int m_Kills; + private ChampionPlatform m_Platform; + private List m_RedSkulls; + private ChampionSpawnRegion m_Region; + + //private int m_SpawnRange; + private Rectangle2D m_SpawnArea; + private int m_SPawnSzMod; + + private Timer m_Timer, m_RestartTimer; + private ChampionSpawnType m_Type; + private List m_WhiteSkulls; + + [Constructible] + public ChampionSpawn() : base(0xBD2) + { + Movable = false; + Visible = false; + + m_Creatures = new List(); + m_RedSkulls = new List(); + m_WhiteSkulls = new List(); + + m_Platform = new ChampionPlatform(this); + m_Altar = new ChampionAltar(this); + m_Idol = new IdolOfTheChampion(this); + + ExpireDelay = TimeSpan.FromMinutes(10.0); + RestartDelay = TimeSpan.FromMinutes(10.0); + + m_DamageEntries = new Dictionary(); + + Timer.DelayCall(TimeSpan.Zero, SetInitialSpawnArea); + } + + public ChampionSpawn(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SpawnSzMod + { + get => m_SPawnSzMod < 1 || m_SPawnSzMod > 12 ? 12 : m_SPawnSzMod; + set => m_SPawnSzMod = value < 1 || value > 12 ? 12 : value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool ConfinedRoaming{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool HasBeenAdvanced{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool RandomizeType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Kills + { + get => m_Kills; + set + { + m_Kills = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Rectangle2D SpawnArea + { + get => m_SpawnArea; + set + { + m_SpawnArea = value; + InvalidateProperties(); + UpdateRegion(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan RestartDelay{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime RestartTime{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan ExpireDelay{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime ExpireTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public ChampionSpawnType Type + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Active + { + get => m_Active; + set + { + if (value) + Start(); + else + Stop(); + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Champion{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Level + { + get => m_RedSkulls.Count; + set + { + for (int i = m_RedSkulls.Count - 1; i >= value; --i) + { + m_RedSkulls[i].Delete(); + m_RedSkulls.RemoveAt(i); + } + + for (int i = m_RedSkulls.Count; i < value; ++i) + { + Item skull = new Item(0x1854); + + skull.Hue = 0x26; + skull.Movable = false; + skull.Light = LightType.Circle150; + + skull.MoveToWorld(GetRedSkullLocation(i), Map); + + m_RedSkulls.Add(skull); + } + + InvalidateProperties(); + } + } + + public int MaxKills => m_SPawnSzMod * (250 / 12) - Level * m_SPawnSzMod; + + public void SetInitialSpawnArea() + { + //Previous default used to be 24; + SpawnArea = new Rectangle2D(new Point2D(X - 24, Y - 24), new Point2D(X + 24, Y + 24)); + } + + public void UpdateRegion() + { + m_Region?.Unregister(); + + if (!Deleted && Map != Map.Internal) + { + m_Region = new ChampionSpawnRegion(this); + m_Region.Register(); + } + + /* + if ( m_Region == null ) + { + m_Region = new ChampionSpawnRegion( this ); + } + else + { + m_Region.Unregister(); + //Why doesn't Region allow me to set it's map/Area myself? >< + m_Region = new ChampionSpawnRegion( this ); + } + */ + } + + public bool IsChampionSpawn(Mobile m) + { + return m_Creatures.Contains(m); + } + + public void SetWhiteSkullCount(int val) + { + for (int i = m_WhiteSkulls.Count - 1; i >= val; --i) + { + m_WhiteSkulls[i].Delete(); + m_WhiteSkulls.RemoveAt(i); + } + + for (int i = m_WhiteSkulls.Count; i < val; ++i) + { + Item skull = new Item(0x1854); + + skull.Movable = false; + skull.Light = LightType.Circle150; + + skull.MoveToWorld(GetWhiteSkullLocation(i), Map); + + m_WhiteSkulls.Add(skull); + + Effects.PlaySound(skull.Location, skull.Map, 0x29); + Effects.SendLocationEffect(new Point3D(skull.X + 1, skull.Y + 1, skull.Z), skull.Map, 0x3728, 10); + } + } + + public void Start() + { + if (m_Active || Deleted) + return; + + m_Active = true; + HasBeenAdvanced = false; + + m_Timer?.Stop(); + + m_Timer = new SliceTimer(this); + m_Timer.Start(); + + m_RestartTimer?.Stop(); + + m_RestartTimer = null; + + if (m_Altar != null) + { + if (Champion != null) + m_Altar.Hue = 0x26; + else + m_Altar.Hue = 0; + } + + if (m_Platform != null) + m_Platform.Hue = 0x452; + } + + public void Stop() + { + if (!m_Active || Deleted) + return; + + m_Active = false; + HasBeenAdvanced = false; + + m_Timer?.Stop(); + + m_Timer = null; + + m_RestartTimer?.Stop(); + + m_RestartTimer = null; + + if (m_Altar != null) + m_Altar.Hue = 0; + + if (m_Platform != null) + m_Platform.Hue = 0x497; + } + + public void BeginRestart(TimeSpan ts) + { + m_RestartTimer?.Stop(); + + RestartTime = DateTime.UtcNow + ts; + + m_RestartTimer = new RestartTimer(this, ts); + m_RestartTimer.Start(); + } + + public void EndRestart() + { + if (RandomizeType) + switch (Utility.Random(5)) + { + case 0: + Type = ChampionSpawnType.VerminHorde; + break; + case 1: + Type = ChampionSpawnType.UnholyTerror; + break; + case 2: + Type = ChampionSpawnType.ColdBlood; + break; + case 3: + Type = ChampionSpawnType.Abyss; + break; + case 4: + Type = ChampionSpawnType.Arachnid; + break; + } + + HasBeenAdvanced = false; + + Start(); + } + + #region Scroll of Transcendence + + private ScrollofTranscendence CreateRandomSoT(bool felucca) + { + int level = Utility.RandomMinMax(1, 5); + + if (felucca) + level += 5; + + return ScrollofTranscendence.CreateRandom(level, level); + } + + #endregion + + public static void GiveScrollTo(Mobile killer, SpecialScroll scroll) + { + if (scroll == null || killer == null) //sanity + return; + + if (scroll is ScrollofTranscendence) + killer.SendLocalizedMessage(1094936); // You have received a Scroll of Transcendence! + else + killer.SendLocalizedMessage(1049524); // You have received a scroll of power! + + if (killer.Alive) + { + killer.AddToBackpack(scroll); + } + else + { + if (killer.Corpse != null && !killer.Corpse.Deleted) + killer.Corpse.DropItem(scroll); + else + killer.AddToBackpack(scroll); + } + + // Justice reward + PlayerMobile pm = (PlayerMobile)killer; + for (int j = 0; j < pm.JusticeProtectors.Count; ++j) + { + Mobile prot = pm.JusticeProtectors[j]; + + if (prot.Map != killer.Map || prot.Kills >= 5 || prot.Criminal || + !JusticeVirtue.CheckMapRegion(killer, prot)) + continue; + + int chance = 0; + + switch (VirtueHelper.GetLevel(prot, VirtueName.Justice)) + { + case VirtueLevel.Seeker: + chance = 60; + break; + case VirtueLevel.Follower: + chance = 80; + break; + case VirtueLevel.Knight: + chance = 100; + break; + } + + if (chance > Utility.Random(100)) + try + { + prot.SendLocalizedMessage(1049368); // You have been rewarded for your dedication to Justice! + + if (Activator.CreateInstance(scroll.GetType()) is SpecialScroll scrollDupe) + { + scrollDupe.Skill = scroll.Skill; + scrollDupe.Value = scroll.Value; + prot.AddToBackpack(scrollDupe); + } + } + catch + { + } + } + } + + public void OnSlice() + { + if (!m_Active || Deleted) + return; + + if (Champion != null) + { + if (Champion.Deleted) + { + RegisterDamageTo(Champion); + + if (Champion is BaseChampion champion) + AwardArtifact(champion.GetArtifact()); + + m_DamageEntries.Clear(); + + if (m_Platform != null) + m_Platform.Hue = 0x497; + + if (m_Altar != null) + { + m_Altar.Hue = 0; + + if (!Core.ML || Map == Map.Felucca) new StarRoomGate(true, m_Altar.Location, m_Altar.Map); + } + + Champion = null; + Stop(); + + BeginRestart(RestartDelay); + } + } + else + { + int kills = m_Kills; + + for (int i = 0; i < m_Creatures.Count; ++i) + { + Mobile m = m_Creatures[i]; + + if (m.Deleted) + { + if (m.Corpse != null && !m.Corpse.Deleted) ((Corpse)m.Corpse).BeginDecay(TimeSpan.FromMinutes(1)); + m_Creatures.RemoveAt(i); + --i; + ++m_Kills; + + Mobile killer = m.FindMostRecentDamager(false); + + RegisterDamageTo(m); + + if (killer is BaseCreature bc) + killer = bc.GetMaster(); + + if (killer is PlayerMobile pm) + { + #region Scroll of Transcendence + + if (Core.ML) + { + if (Map == Map.Felucca) + if (Utility.RandomDouble() < 0.001) + { + double random = Utility.Random(49); + + if (random <= 24) + { + ScrollofTranscendence SoTF = CreateRandomSoT(true); + GiveScrollTo(pm, SoTF); + } + else + { + PowerScroll PS = PowerScroll.CreateRandomNoCraft(5, 5); + GiveScrollTo(pm, PS); + } + } + + if (Map == Map.Ilshenar || Map == Map.Tokuno || Map == Map.Malas) + if (Utility.RandomDouble() < 0.0015) + { + pm.SendLocalizedMessage(1094936); // You have received a Scroll of Transcendence! + ScrollofTranscendence SoTT = CreateRandomSoT(false); + pm.AddToBackpack(SoTT); + } + } + + #endregion + + int mobSubLevel = GetSubLevelFor(m) + 1; + + if (mobSubLevel >= 0) + { + bool gainedPath = false; + + int pointsToGain = mobSubLevel * 40; + + if (VirtueHelper.Award(pm, VirtueName.Valor, pointsToGain, ref gainedPath)) + { + if (gainedPath) + m.SendLocalizedMessage(1054032); // You have gained a path in Valor! + else + m.SendLocalizedMessage(1054030); // You have gained in Valor! + + //No delay on Valor gains + } + + PlayerMobile.ChampionTitleInfo info = pm.ChampionTitles; + + info.Award(m_Type, mobSubLevel); + } + } + } + } + + // Only really needed once. + if (m_Kills > kills) + InvalidateProperties(); + + double n = m_Kills / (double)MaxKills; + int p = (int)(n * 100); + + if (p >= 90) + AdvanceLevel(); + else if (p > 0) + SetWhiteSkullCount(p / 20); + + if (DateTime.UtcNow >= ExpireTime) + Expire(); + + Respawn(); + } + } + + public void AdvanceLevel() + { + ExpireTime = DateTime.UtcNow + ExpireDelay; + + if (Level < 16) + { + m_Kills = 0; + ++Level; + InvalidateProperties(); + SetWhiteSkullCount(0); + + if (m_Altar != null) + { + Effects.PlaySound(m_Altar.Location, m_Altar.Map, 0x29); + Effects.SendLocationEffect(new Point3D(m_Altar.X + 1, m_Altar.Y + 1, m_Altar.Z), m_Altar.Map, 0x3728, + 10); + } + } + else + { + SpawnChampion(); + } + } + + public void SpawnChampion() + { + if (m_Altar != null) + m_Altar.Hue = 0x26; + + if (m_Platform != null) + m_Platform.Hue = 0x452; + + m_Kills = 0; + Level = 0; + InvalidateProperties(); + SetWhiteSkullCount(0); + + try + { + Champion = Activator.CreateInstance(ChampionSpawnInfo.GetInfo(m_Type).Champion) as Mobile; + } + catch + { + } + + Champion?.MoveToWorld(new Point3D(X, Y, Z - 15), Map); + } + + public void Respawn() + { + if (!m_Active || Deleted || Champion != null) + return; + + while (m_Creatures.Count < m_SPawnSzMod * (200 / 12) - GetSubLevel() * m_SPawnSzMod * (40 / 12)) + { + Mobile m = Spawn(); + + if (m == null) + return; + + Point3D loc = GetSpawnLocation(); + + // Allow creatures to turn into Paragons at Ilshenar champions. + m.OnBeforeSpawn(loc, Map); + + m_Creatures.Add(m); + m.MoveToWorld(loc, Map); + + if (m is BaseCreature bc) + { + bc.Tamable = false; + + if (!ConfinedRoaming) + { + bc.Home = Location; + bc.RangeHome = + (int)(Math.Sqrt(m_SpawnArea.Width * m_SpawnArea.Width + + m_SpawnArea.Height * m_SpawnArea.Height) / 2); + } + else + { + bc.Home = bc.Location; + + Point2D xWall1 = new Point2D(m_SpawnArea.X, bc.Y); + Point2D xWall2 = new Point2D(m_SpawnArea.X + m_SpawnArea.Width, bc.Y); + Point2D yWall1 = new Point2D(bc.X, m_SpawnArea.Y); + Point2D yWall2 = new Point2D(bc.X, m_SpawnArea.Y + m_SpawnArea.Height); + + double minXDist = Math.Min(bc.GetDistanceToSqrt(xWall1), bc.GetDistanceToSqrt(xWall2)); + double minYDist = Math.Min(bc.GetDistanceToSqrt(yWall1), bc.GetDistanceToSqrt(yWall2)); + + bc.RangeHome = (int)Math.Min(minXDist, minYDist); + } + } + } + } + + public Point3D GetSpawnLocation() + { + Map map = Map; + + if (map == null) + return Location; + + // Try 20 times to find a spawnable location. + for (int i = 0; i < 20; i++) + { + /* + int x = Location.X + (Utility.Random( (m_SpawnRange * 2) + 1 ) - m_SpawnRange); + int y = Location.Y + (Utility.Random( (m_SpawnRange * 2) + 1 ) - m_SpawnRange); + */ + + int x = Utility.Random(m_SpawnArea.X, m_SpawnArea.Width); + int y = Utility.Random(m_SpawnArea.Y, m_SpawnArea.Height); + + int z = Map.GetAverageZ(x, y); + + if (Map.CanSpawnMobile(new Point2D(x, y), z)) + return new Point3D(x, y, z); + + /* try @ platform Z if map z fails */ + if (Map.CanSpawnMobile(new Point2D(x, y), m_Platform.Location.Z)) + return new Point3D(x, y, m_Platform.Location.Z); + } + + return Location; + } + + public int GetSubLevel() + { + int level = Level; + + if (level <= Level1) + return 0; + if (level <= Level2) + return 1; + if (level <= Level3) + return 2; + + return 3; + } + + public int GetSubLevelFor(Mobile m) + { + Type[][] types = ChampionSpawnInfo.GetInfo(m_Type).SpawnTypes; + Type t = m.GetType(); + + for (int i = 0; i < types.GetLength(0); i++) + { + Type[] individualTypes = types[i]; + + for (int j = 0; j < individualTypes.Length; j++) + if (t == individualTypes[j]) + return i; + } + + return -1; + } + + public Mobile Spawn() + { + Type[][] types = ChampionSpawnInfo.GetInfo(m_Type).SpawnTypes; + + int v = GetSubLevel(); + + if (v >= 0 && v < types.Length) + return Spawn(types[v]); + + return null; + } + + public Mobile Spawn(params Type[] types) + { + try + { + return Activator.CreateInstance(types[Utility.Random(types.Length)]) as Mobile; + } + catch + { + return null; + } + } + + public void Expire() + { + m_Kills = 0; + + if (m_WhiteSkulls.Count == 0) + { + // They didn't even get 20%, go back a level + + if (Level > 0) + --Level; + + InvalidateProperties(); + } + else + { + SetWhiteSkullCount(0); + } + + ExpireTime = DateTime.UtcNow + ExpireDelay; + } + + public Point3D GetRedSkullLocation(int index) + { + int x, y; + + if (index < 5) + { + x = index - 2; + y = -2; + } + else if (index < 9) + { + x = 2; + y = index - 6; + } + else if (index < 13) + { + x = 10 - index; + y = 2; + } + else + { + x = -2; + y = 14 - index; + } + + return new Point3D(X + x, Y + y, Z - 15); + } + + public Point3D GetWhiteSkullLocation(int index) + { + int x, y; + + switch (index) + { + default: + case 0: + x = -1; + y = -1; + break; + case 1: + x = 1; + y = -1; + break; + case 2: + x = 1; + y = 1; + break; + case 3: + x = -1; + y = 1; + break; + } + + return new Point3D(X + x, Y + y, Z - 15); + } + + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add("champion spawn"); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Active) + { + list.Add(1060742); // active + list.Add(1060658, "Type\t{0}", m_Type); // ~1_val~: ~2_val~ + list.Add(1060659, "Level\t{0}", Level); // ~1_val~: ~2_val~ + list.Add(1060660, "Kills\t{0} of {1} ({2:F1}%)", m_Kills, MaxKills, + 100.0 * ((double)m_Kills / MaxKills)); // ~1_val~: ~2_val~ + //list.Add( 1060661, "Spawn Range\t{0}", m_SpawnRange ); // ~1_val~: ~2_val~ + } + else + { + list.Add(1060743); // inactive + } + } + + public override void OnSingleClick(Mobile from) + { + if (m_Active) + LabelTo(from, "{0} (Active; Level: {1}; Kills: {2}/{3})", m_Type, Level, m_Kills, MaxKills); + else + LabelTo(from, "{0} (Inactive)", m_Type); + } + + public override void OnDoubleClick(Mobile from) + { + from.SendGump(new PropertiesGump(from, this)); + } + + public override void OnLocationChange(Point3D oldLoc) + { + if (Deleted) + return; + + if (m_Platform != null) + m_Platform.Location = new Point3D(X, Y, Z - 20); + + if (m_Altar != null) + m_Altar.Location = new Point3D(X, Y, Z - 15); + + if (m_Idol != null) + m_Idol.Location = new Point3D(X, Y, Z - 15); + + if (m_RedSkulls != null) + for (int i = 0; i < m_RedSkulls.Count; ++i) + m_RedSkulls[i].Location = GetRedSkullLocation(i); + + if (m_WhiteSkulls != null) + for (int i = 0; i < m_WhiteSkulls.Count; ++i) + m_WhiteSkulls[i].Location = GetWhiteSkullLocation(i); + + m_SpawnArea.X += Location.X - oldLoc.X; + m_SpawnArea.Y += Location.Y - oldLoc.Y; + + UpdateRegion(); + } + + public override void OnMapChange() + { + if (Deleted) + return; + + if (m_Platform != null) + m_Platform.Map = Map; + + if (m_Altar != null) + m_Altar.Map = Map; + + if (m_Idol != null) + m_Idol.Map = Map; + + if (m_RedSkulls != null) + for (int i = 0; i < m_RedSkulls.Count; ++i) + m_RedSkulls[i].Map = Map; + + if (m_WhiteSkulls != null) + for (int i = 0; i < m_WhiteSkulls.Count; ++i) + m_WhiteSkulls[i].Map = Map; + + UpdateRegion(); + } - m_WhiteSkulls.Clear(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - if ( m_Creatures != null ) - { - for( int i = 0; i < m_Creatures.Count; ++i ) - { - Mobile mob = m_Creatures[i]; + m_Platform?.Delete(); - if ( !mob.Player ) - mob.Delete(); - } + m_Altar?.Delete(); - m_Creatures.Clear(); - } + m_Idol?.Delete(); - if ( Champion != null && !Champion.Player ) - Champion.Delete(); + if (m_RedSkulls != null) + { + for (int i = 0; i < m_RedSkulls.Count; ++i) + m_RedSkulls[i].Delete(); - Stop(); + m_RedSkulls.Clear(); + } - UpdateRegion(); - } + if (m_WhiteSkulls != null) + { + for (int i = 0; i < m_WhiteSkulls.Count; ++i) + m_WhiteSkulls[i].Delete(); - public ChampionSpawn( Serial serial ) : base( serial ) - { - } + m_WhiteSkulls.Clear(); + } - public virtual void RegisterDamageTo( Mobile m ) - { - if ( m == null ) - return; + if (m_Creatures != null) + { + for (int i = 0; i < m_Creatures.Count; ++i) + { + Mobile mob = m_Creatures[i]; - foreach( DamageEntry de in m.DamageEntries ) - { - if ( de.HasExpired ) - continue; + if (!mob.Player) + mob.Delete(); + } - Mobile damager = de.Damager; + m_Creatures.Clear(); + } - Mobile master = damager.GetDamageMaster( m ); + if (Champion != null && !Champion.Player) + Champion.Delete(); - if ( master != null ) - damager = master; + Stop(); - RegisterDamage( damager, de.DamageGiven ); - } - } - - public void RegisterDamage( Mobile from, int amount ) - { - if ( from == null || !from.Player ) - return; + UpdateRegion(); + } - if ( m_DamageEntries.ContainsKey( from ) ) - m_DamageEntries[from] += amount; - else - m_DamageEntries.Add( from, amount ); - } + public virtual void RegisterDamageTo(Mobile m) + { + if (m == null) + return; - public void AwardArtifact( Item artifact ) - { - if (artifact == null ) - return; + foreach (DamageEntry de in m.DamageEntries) + { + if (de.HasExpired) + continue; - int totalDamage = 0; + Mobile damager = de.Damager; - Dictionary validEntries = new Dictionary(); + Mobile master = damager.GetDamageMaster(m); - foreach (KeyValuePair kvp in m_DamageEntries) - { - if ( IsEligible( kvp.Key, artifact ) ) - { - validEntries.Add( kvp.Key, kvp.Value ); - totalDamage += kvp.Value; - } - } - - int randomDamage = Utility.RandomMinMax( 1, totalDamage ); - - totalDamage = 0; - - foreach (KeyValuePair kvp in validEntries) - { - totalDamage += kvp.Value; - - if ( totalDamage >= randomDamage ) - { - GiveArtifact( kvp.Key, artifact ); - return; - } - } - - artifact.Delete(); - } - - public void GiveArtifact( Mobile to, Item artifact ) - { - if ( to == null || artifact == null ) - return; - - Container pack = to.Backpack; - - if ( pack == null || !pack.TryDropItem( to, artifact, false ) ) - artifact.Delete(); - else - to.SendLocalizedMessage( 1062317 ); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. - } - - public bool IsEligible( Mobile m, Item Artifact ) - { - return m.Player && m.Alive && m.Region != null && m.Region == m_Region && m.Backpack != null && m.Backpack.CheckHold( m, Artifact, false ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)6 ); // version - - writer.Write( ( int ) m_SPawnSzMod ); - writer.Write( m_DamageEntries.Count ); - foreach (KeyValuePair kvp in m_DamageEntries) - { - writer.Write( kvp.Key ); - writer.Write( kvp.Value ); - } - - writer.Write( ConfinedRoaming ); - writer.WriteItem( m_Idol ); - writer.Write( HasBeenAdvanced ); - writer.Write( m_SpawnArea ); - - writer.Write( RandomizeType ); - - // writer.Write( m_SpawnRange ); - writer.Write( m_Kills ); - - writer.Write( (bool)m_Active ); - writer.Write( (int)m_Type ); - writer.Write( m_Creatures, true ); - writer.Write( m_RedSkulls, true ); - writer.Write( m_WhiteSkulls, true ); - writer.WriteItem( m_Platform ); - writer.WriteItem( m_Altar ); - writer.Write( ExpireDelay ); - writer.WriteDeltaTime( ExpireTime ); - writer.Write( Champion ); - writer.Write( RestartDelay ); - - writer.Write( m_RestartTimer != null ); - - if ( m_RestartTimer != null ) - writer.WriteDeltaTime( RestartTime ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - m_DamageEntries = new Dictionary(); - - int version = reader.ReadInt(); - - switch( version ) - { - case 6: - { - m_SPawnSzMod = reader.ReadInt(); - goto case 5; - } - case 5: - { - int entries = reader.ReadInt(); - Mobile m; - int damage; - for( int i = 0; i < entries; ++i ) - { - m = reader.ReadMobile(); - damage = reader.ReadInt(); - - if ( m == null ) - continue; - - m_DamageEntries.Add( m, damage ); - } - - goto case 4; - } - case 4: - { - ConfinedRoaming = reader.ReadBool(); - m_Idol = reader.ReadItem(); - HasBeenAdvanced = reader.ReadBool(); - - goto case 3; - } - case 3: - { - m_SpawnArea = reader.ReadRect2D(); - - goto case 2; - } - case 2: - { - RandomizeType = reader.ReadBool(); - - goto case 1; - } - case 1: - { - if ( version < 3 ) - { - int oldRange = reader.ReadInt(); - - m_SpawnArea = new Rectangle2D( new Point2D( X - oldRange, Y - oldRange ), new Point2D( X + oldRange, Y + oldRange ) ); - } - - m_Kills = reader.ReadInt(); - - goto case 0; - } - case 0: - { - if ( version < 1 ) - m_SpawnArea = new Rectangle2D( new Point2D( X - 24, Y - 24 ), new Point2D( X + 24, Y + 24 ) ); //Default was 24 - - bool active = reader.ReadBool(); - m_Type = (ChampionSpawnType)reader.ReadInt(); - m_Creatures = reader.ReadStrongMobileList(); - m_RedSkulls = reader.ReadStrongItemList(); - m_WhiteSkulls = reader.ReadStrongItemList(); - m_Platform = reader.ReadItem(); - m_Altar = reader.ReadItem(); - ExpireDelay = reader.ReadTimeSpan(); - ExpireTime = reader.ReadDeltaTime(); - Champion = reader.ReadMobile(); - RestartDelay = reader.ReadTimeSpan(); - - if ( reader.ReadBool() ) - { - RestartTime = reader.ReadDeltaTime(); - BeginRestart( RestartTime - DateTime.UtcNow ); - } - - if ( version < 4 ) - { - m_Idol = new IdolOfTheChampion( this ); - m_Idol.MoveToWorld( new Point3D( X, Y, Z - 15 ), Map ); - } - - if ( m_Platform == null || m_Altar == null || m_Idol == null ) - Delete(); - else if ( active ) - Start(); - - break; - } - } - - Timer.DelayCall( TimeSpan.Zero, UpdateRegion ); - } - } - - public class ChampionSpawnRegion : BaseRegion - { - public override bool YoungProtected => false; - - public ChampionSpawn ChampionSpawn { get; } - - public ChampionSpawnRegion( ChampionSpawn spawn ) : base( null, spawn.Map, Find( spawn.Location, spawn.Map ), spawn.SpawnArea ) - { - ChampionSpawn = spawn; - } - - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } - - public override void AlterLightLevel( Mobile m, ref int global, ref int personal ) - { - base.AlterLightLevel( m, ref global, ref personal ); - global = Math.Max( global, 1 + ChampionSpawn.Level ); //This is a guesstimate. TODO: Verify & get exact values // OSI testing: at 2 red skulls, light = 0x3 ; 1 red = 0x3.; 3 = 8; 9 = 0xD 8 = 0xD 12 = 0x12 10 = 0xD - } - } - - public class IdolOfTheChampion : Item - { - public ChampionSpawn Spawn { get; private set; } - - public override string DefaultName => "Idol of the Champion"; - - - public IdolOfTheChampion( ChampionSpawn spawn ): base( 0x1F18 ) - { - Spawn = spawn; - Movable = false; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - Spawn?.Delete(); - } - - public IdolOfTheChampion( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( Spawn ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Spawn = reader.ReadItem() as ChampionSpawn; - - if ( Spawn == null ) - Delete(); - - break; - } - } - } - } -} + if (master != null) + damager = master; + + RegisterDamage(damager, de.DamageGiven); + } + } + + public void RegisterDamage(Mobile from, int amount) + { + if (from == null || !from.Player) + return; + + if (m_DamageEntries.ContainsKey(from)) + m_DamageEntries[from] += amount; + else + m_DamageEntries.Add(from, amount); + } + + public void AwardArtifact(Item artifact) + { + if (artifact == null) + return; + + int totalDamage = 0; + + Dictionary validEntries = new Dictionary(); + + foreach (KeyValuePair kvp in m_DamageEntries) + if (IsEligible(kvp.Key, artifact)) + { + validEntries.Add(kvp.Key, kvp.Value); + totalDamage += kvp.Value; + } + + int randomDamage = Utility.RandomMinMax(1, totalDamage); + + totalDamage = 0; + + foreach (KeyValuePair kvp in validEntries) + { + totalDamage += kvp.Value; + + if (totalDamage >= randomDamage) + { + GiveArtifact(kvp.Key, artifact); + return; + } + } + + artifact.Delete(); + } + + public void GiveArtifact(Mobile to, Item artifact) + { + if (to == null || artifact == null) + return; + + Container pack = to.Backpack; + + if (pack == null || !pack.TryDropItem(to, artifact, false)) + artifact.Delete(); + else + to.SendLocalizedMessage( + 1062317); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. + } + + public bool IsEligible(Mobile m, Item Artifact) + { + return m.Player && m.Alive && m.Region != null && m.Region == m_Region && m.Backpack != null && + m.Backpack.CheckHold(m, Artifact, false); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(6); // version + + writer.Write(m_SPawnSzMod); + writer.Write(m_DamageEntries.Count); + foreach (KeyValuePair kvp in m_DamageEntries) + { + writer.Write(kvp.Key); + writer.Write(kvp.Value); + } + + writer.Write(ConfinedRoaming); + writer.WriteItem(m_Idol); + writer.Write(HasBeenAdvanced); + writer.Write(m_SpawnArea); + + writer.Write(RandomizeType); + + // writer.Write( m_SpawnRange ); + writer.Write(m_Kills); + + writer.Write(m_Active); + writer.Write((int)m_Type); + writer.Write(m_Creatures, true); + writer.Write(m_RedSkulls, true); + writer.Write(m_WhiteSkulls, true); + writer.WriteItem(m_Platform); + writer.WriteItem(m_Altar); + writer.Write(ExpireDelay); + writer.WriteDeltaTime(ExpireTime); + writer.Write(Champion); + writer.Write(RestartDelay); + + writer.Write(m_RestartTimer != null); + + if (m_RestartTimer != null) + writer.WriteDeltaTime(RestartTime); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + m_DamageEntries = new Dictionary(); + + int version = reader.ReadInt(); + + switch (version) + { + case 6: + { + m_SPawnSzMod = reader.ReadInt(); + goto case 5; + } + case 5: + { + int entries = reader.ReadInt(); + Mobile m; + int damage; + for (int i = 0; i < entries; ++i) + { + m = reader.ReadMobile(); + damage = reader.ReadInt(); + + if (m == null) + continue; + + m_DamageEntries.Add(m, damage); + } + + goto case 4; + } + case 4: + { + ConfinedRoaming = reader.ReadBool(); + m_Idol = reader.ReadItem(); + HasBeenAdvanced = reader.ReadBool(); + + goto case 3; + } + case 3: + { + m_SpawnArea = reader.ReadRect2D(); + + goto case 2; + } + case 2: + { + RandomizeType = reader.ReadBool(); + + goto case 1; + } + case 1: + { + if (version < 3) + { + int oldRange = reader.ReadInt(); + + m_SpawnArea = new Rectangle2D(new Point2D(X - oldRange, Y - oldRange), + new Point2D(X + oldRange, Y + oldRange)); + } + + m_Kills = reader.ReadInt(); + + goto case 0; + } + case 0: + { + if (version < 1) + m_SpawnArea = + new Rectangle2D(new Point2D(X - 24, Y - 24), new Point2D(X + 24, Y + 24)); //Default was 24 + + bool active = reader.ReadBool(); + m_Type = (ChampionSpawnType)reader.ReadInt(); + m_Creatures = reader.ReadStrongMobileList(); + m_RedSkulls = reader.ReadStrongItemList(); + m_WhiteSkulls = reader.ReadStrongItemList(); + m_Platform = reader.ReadItem(); + m_Altar = reader.ReadItem(); + ExpireDelay = reader.ReadTimeSpan(); + ExpireTime = reader.ReadDeltaTime(); + Champion = reader.ReadMobile(); + RestartDelay = reader.ReadTimeSpan(); + + if (reader.ReadBool()) + { + RestartTime = reader.ReadDeltaTime(); + BeginRestart(RestartTime - DateTime.UtcNow); + } + + if (version < 4) + { + m_Idol = new IdolOfTheChampion(this); + m_Idol.MoveToWorld(new Point3D(X, Y, Z - 15), Map); + } + + if (m_Platform == null || m_Altar == null || m_Idol == null) + Delete(); + else if (active) + Start(); + + break; + } + } + + Timer.DelayCall(TimeSpan.Zero, UpdateRegion); + } + } + + public class ChampionSpawnRegion : BaseRegion + { + public ChampionSpawnRegion(ChampionSpawn spawn) : base(null, spawn.Map, Find(spawn.Location, spawn.Map), + spawn.SpawnArea) + { + ChampionSpawn = spawn; + } + + public override bool YoungProtected => false; + + public ChampionSpawn ChampionSpawn{ get; } + + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } + + public override void AlterLightLevel(Mobile m, ref int global, ref int personal) + { + base.AlterLightLevel(m, ref global, ref personal); + global = Math.Max(global, + 1 + ChampionSpawn + .Level); //This is a guesstimate. TODO: Verify & get exact values // OSI testing: at 2 red skulls, light = 0x3 ; 1 red = 0x3.; 3 = 8; 9 = 0xD 8 = 0xD 12 = 0x12 10 = 0xD + } + } + + public class IdolOfTheChampion : Item + { + public IdolOfTheChampion(ChampionSpawn spawn) : base(0x1F18) + { + Spawn = spawn; + Movable = false; + } + + public IdolOfTheChampion(Serial serial) : base(serial) + { + } + + public ChampionSpawn Spawn{ get; private set; } + + public override string DefaultName => "Idol of the Champion"; + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + Spawn?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(Spawn); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Spawn = reader.ReadItem() as ChampionSpawn; + + if (Spawn == null) + Delete(); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/ChampionSpawnType.cs b/Scripts/Engines/CannedEvil/ChampionSpawnType.cs index 51206039d..43bd221f7 100644 --- a/Scripts/Engines/CannedEvil/ChampionSpawnType.cs +++ b/Scripts/Engines/CannedEvil/ChampionSpawnType.cs @@ -3,115 +3,131 @@ using Server.Mobiles; namespace Server.Engines.CannedEvil { - public enum ChampionSpawnType - { - Abyss, - Arachnid, - ColdBlood, - ForestLord, - VerminHorde, - UnholyTerror, - SleepingDragon, - Glade, - Pestilence - } + public enum ChampionSpawnType + { + Abyss, + Arachnid, + ColdBlood, + ForestLord, + VerminHorde, + UnholyTerror, + SleepingDragon, + Glade, + Pestilence + } - public class ChampionSpawnInfo - { - public string Name { get; } + public class ChampionSpawnInfo + { + public ChampionSpawnInfo(string name, Type champion, string[] levelNames, Type[][] spawnTypes) + { + Name = name; + Champion = champion; + LevelNames = levelNames; + SpawnTypes = spawnTypes; + } - public Type Champion { get; } + public string Name{ get; } - public Type[][] SpawnTypes { get; } + public Type Champion{ get; } - public string[] LevelNames { get; } + public Type[][] SpawnTypes{ get; } - public ChampionSpawnInfo( string name, Type champion, string[] levelNames, Type[][] spawnTypes ) - { - Name = name; - Champion = champion; - LevelNames = levelNames; - SpawnTypes = spawnTypes; - } + public string[] LevelNames{ get; } - public static ChampionSpawnInfo[] Table { get; } = - { - new ChampionSpawnInfo( "Abyss", typeof( Semidar ), new[]{ "Foe", "Assassin", "Conqueror" }, new[] // Abyss - { // Abyss - new[]{ typeof( GreaterMongbat ), typeof( Imp ) }, // Level 1 - new[]{ typeof( Gargoyle ), typeof( Harpy ) }, // Level 2 - new[]{ typeof( FireGargoyle ), typeof( StoneGargoyle ) }, // Level 3 - new[]{ typeof( Daemon ), typeof( Succubus ) } // Level 4 - } ), - new ChampionSpawnInfo( "Arachnid", typeof( Mephitis ), new[]{ "Bane", "Killer", "Vanquisher" }, new[] // Arachnid - { // Arachnid - new[]{ typeof( Scorpion ), typeof( GiantSpider ) }, // Level 1 - new[]{ typeof( TerathanDrone ), typeof( TerathanWarrior ) }, // Level 2 - new[]{ typeof( DreadSpider ), typeof( TerathanMatriarch ) }, // Level 3 - new[]{ typeof( PoisonElemental ), typeof( TerathanAvenger ) } // Level 4 - } ), - new ChampionSpawnInfo( "Cold Blood", typeof( Rikktor ), new[]{ "Blight", "Slayer", "Destroyer" }, new[] // Cold Blood - { // Cold Blood - new[]{ typeof( Lizardman ), typeof( Snake ) }, // Level 1 - new[]{ typeof( LavaLizard ), typeof( OphidianWarrior ) }, // Level 2 - new[]{ typeof( Drake ), typeof( OphidianArchmage ) }, // Level 3 - new[]{ typeof( Dragon ), typeof( OphidianKnight ) } // Level 4 - } ), - new ChampionSpawnInfo( "Forest Lord", typeof( LordOaks ), new[]{ "Enemy", "Curse", "Slaughterer" }, new[] // Forest Lord - { // Forest Lord - new[]{ typeof( Pixie ), typeof( ShadowWisp ) }, // Level 1 - new[]{ typeof( Kirin ), typeof( Wisp ) }, // Level 2 - new[]{ typeof( Centaur ), typeof( Unicorn ) }, // Level 3 - new[]{ typeof( EtherealWarrior ), typeof( SerpentineDragon ) } // Level 4 - } ), - new ChampionSpawnInfo( "Vermin Horde", typeof( Barracoon ), new[]{ "Adversary", "Subjugator", "Eradicator" }, new[] // Vermin Horde - { // Vermin Horde - new[]{ typeof( GiantRat ), typeof( Slime ) }, // Level 1 - new[]{ typeof( DireWolf ), typeof( Ratman ) }, // Level 2 - new[]{ typeof( HellHound ), typeof( RatmanMage ) }, // Level 3 - new[]{ typeof( RatmanArcher ), typeof( SilverSerpent ) } // Level 4 - } ), - new ChampionSpawnInfo( "Unholy Terror", typeof( Neira ), new[]{ "Scourge", "Punisher", "Nemesis" }, new[] // Unholy Terror - { // Unholy Terror - (Core.AOS ? - new[]{ typeof( Bogle ), typeof( Ghoul ), typeof( Shade ), typeof( Spectre ), typeof( Wraith ) } // Level 1 (Pre-AoS) - : new[]{ typeof( Ghoul ), typeof( Shade ), typeof( Spectre ), typeof( Wraith ) } ), // Level 1 + public static ChampionSpawnInfo[] Table{ get; } = + { + new ChampionSpawnInfo("Abyss", typeof(Semidar), new[] { "Foe", "Assassin", "Conqueror" }, new[] // Abyss + { + // Abyss + new[] { typeof(GreaterMongbat), typeof(Imp) }, // Level 1 + new[] { typeof(Gargoyle), typeof(Harpy) }, // Level 2 + new[] { typeof(FireGargoyle), typeof(StoneGargoyle) }, // Level 3 + new[] { typeof(Daemon), typeof(Succubus) } // Level 4 + }), + new ChampionSpawnInfo("Arachnid", typeof(Mephitis), new[] { "Bane", "Killer", "Vanquisher" }, new[] // Arachnid + { + // Arachnid + new[] { typeof(Scorpion), typeof(GiantSpider) }, // Level 1 + new[] { typeof(TerathanDrone), typeof(TerathanWarrior) }, // Level 2 + new[] { typeof(DreadSpider), typeof(TerathanMatriarch) }, // Level 3 + new[] { typeof(PoisonElemental), typeof(TerathanAvenger) } // Level 4 + }), + new ChampionSpawnInfo("Cold Blood", typeof(Rikktor), new[] { "Blight", "Slayer", "Destroyer" }, + new[] // Cold Blood + { + // Cold Blood + new[] { typeof(Lizardman), typeof(Snake) }, // Level 1 + new[] { typeof(LavaLizard), typeof(OphidianWarrior) }, // Level 2 + new[] { typeof(Drake), typeof(OphidianArchmage) }, // Level 3 + new[] { typeof(Dragon), typeof(OphidianKnight) } // Level 4 + }), + new ChampionSpawnInfo("Forest Lord", typeof(LordOaks), new[] { "Enemy", "Curse", "Slaughterer" }, + new[] // Forest Lord + { + // Forest Lord + new[] { typeof(Pixie), typeof(ShadowWisp) }, // Level 1 + new[] { typeof(Kirin), typeof(Wisp) }, // Level 2 + new[] { typeof(Centaur), typeof(Unicorn) }, // Level 3 + new[] { typeof(EtherealWarrior), typeof(SerpentineDragon) } // Level 4 + }), + new ChampionSpawnInfo("Vermin Horde", typeof(Barracoon), new[] { "Adversary", "Subjugator", "Eradicator" }, + new[] // Vermin Horde + { + // Vermin Horde + new[] { typeof(GiantRat), typeof(Slime) }, // Level 1 + new[] { typeof(DireWolf), typeof(Ratman) }, // Level 2 + new[] { typeof(HellHound), typeof(RatmanMage) }, // Level 3 + new[] { typeof(RatmanArcher), typeof(SilverSerpent) } // Level 4 + }), + new ChampionSpawnInfo("Unholy Terror", typeof(Neira), new[] { "Scourge", "Punisher", "Nemesis" }, + new[] // Unholy Terror + { + // Unholy Terror + Core.AOS + ? new[] + { + typeof(Bogle), typeof(Ghoul), typeof(Shade), typeof(Spectre), typeof(Wraith) + } // Level 1 (Pre-AoS) + : new[] { typeof(Ghoul), typeof(Shade), typeof(Spectre), typeof(Wraith) }, // Level 1 - new[]{ typeof( BoneMagi ), typeof( Mummy ), typeof( SkeletalMage ) }, // Level 2 - new[]{ typeof( BoneKnight ), typeof( Lich ), typeof( SkeletalKnight ) }, // Level 3 - new[]{ typeof( LichLord ), typeof( RottingCorpse ) } // Level 4 - } ), - new ChampionSpawnInfo( "Sleeping Dragon", typeof( Serado ), new[]{ "Rival", "Challenger", "Antagonist" } , new[] - { // Unholy Terror - new[]{ typeof( DeathwatchBeetleHatchling ), typeof( Lizardman ) }, - new[]{ typeof( DeathwatchBeetle ), typeof( Kappa ) }, - new[]{ typeof( LesserHiryu ), typeof( RevenantLion ) }, - new[]{ typeof( Hiryu ), typeof( Oni ) } - } ), - new ChampionSpawnInfo( "Glade", typeof( Twaulo ), new[]{ "Banisher", "Enforcer", "Eradicator" } , new[] - { // Glade - new[]{ typeof( Pixie ), typeof( ShadowWisp ) }, - new[]{ typeof( Centaur ), typeof( MLDryad ) }, - new[]{ typeof( Satyr ), typeof( CuSidhe ) }, - new[]{ typeof( FeralTreefellow ), typeof( RagingGrizzlyBear ) } - } ), - new ChampionSpawnInfo( "The Corrupt", typeof( Ilhenir ), new[]{ "Cleanser", "Expunger", "Depurator" } , new[] - { // Unholy Terror - new[]{ typeof( PlagueSpawn ), typeof( Bogling ) }, - new[]{ typeof( PlagueBeast ), typeof( BogThing ) }, - new[]{ typeof( PlagueBeastLord ), typeof( InterredGrizzle ) }, - new[]{ typeof( FetidEssence ), typeof( PestilentBandage ) } - } ) - }; + new[] { typeof(BoneMagi), typeof(Mummy), typeof(SkeletalMage) }, // Level 2 + new[] { typeof(BoneKnight), typeof(Lich), typeof(SkeletalKnight) }, // Level 3 + new[] { typeof(LichLord), typeof(RottingCorpse) } // Level 4 + }), + new ChampionSpawnInfo("Sleeping Dragon", typeof(Serado), new[] { "Rival", "Challenger", "Antagonist" }, new[] + { + // Unholy Terror + new[] { typeof(DeathwatchBeetleHatchling), typeof(Lizardman) }, + new[] { typeof(DeathwatchBeetle), typeof(Kappa) }, + new[] { typeof(LesserHiryu), typeof(RevenantLion) }, + new[] { typeof(Hiryu), typeof(Oni) } + }), + new ChampionSpawnInfo("Glade", typeof(Twaulo), new[] { "Banisher", "Enforcer", "Eradicator" }, new[] + { + // Glade + new[] { typeof(Pixie), typeof(ShadowWisp) }, + new[] { typeof(Centaur), typeof(MLDryad) }, + new[] { typeof(Satyr), typeof(CuSidhe) }, + new[] { typeof(FeralTreefellow), typeof(RagingGrizzlyBear) } + }), + new ChampionSpawnInfo("The Corrupt", typeof(Ilhenir), new[] { "Cleanser", "Expunger", "Depurator" }, new[] + { + // Unholy Terror + new[] { typeof(PlagueSpawn), typeof(Bogling) }, + new[] { typeof(PlagueBeast), typeof(BogThing) }, + new[] { typeof(PlagueBeastLord), typeof(InterredGrizzle) }, + new[] { typeof(FetidEssence), typeof(PestilentBandage) } + }) + }; - public static ChampionSpawnInfo GetInfo( ChampionSpawnType type ) - { - int v = (int)type; + public static ChampionSpawnInfo GetInfo(ChampionSpawnType type) + { + int v = (int)type; - if ( v < 0 || v >= Table.Length ) - v = 0; + if (v < 0 || v >= Table.Length) + v = 0; - return Table[v]; - } - } -} + return Table[v]; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/HarrowerGate.cs b/Scripts/Engines/CannedEvil/HarrowerGate.cs index f8d1ea959..454a8da75 100644 --- a/Scripts/Engines/CannedEvil/HarrowerGate.cs +++ b/Scripts/Engines/CannedEvil/HarrowerGate.cs @@ -1,56 +1,56 @@ namespace Server.Items { - public class HarrowerGate : Moongate - { - private Mobile m_Harrower; + public class HarrowerGate : Moongate + { + private Mobile m_Harrower; - public override int LabelNumber => 1049498; // dark moongate + public HarrowerGate(Mobile harrower, Point3D loc, Map map, Point3D targLoc, Map targMap) : base(targLoc, targMap) + { + m_Harrower = harrower; - public HarrowerGate( Mobile harrower, Point3D loc, Map map, Point3D targLoc, Map targMap ) : base( targLoc, targMap ) - { - m_Harrower = harrower; + Dispellable = false; + ItemID = 0x1FD4; + Light = LightType.Circle300; - Dispellable = false; - ItemID = 0x1FD4; - Light = LightType.Circle300; + MoveToWorld(loc, map); + } - MoveToWorld( loc, map ); - } + public HarrowerGate(Serial serial) : base(serial) + { + } - public HarrowerGate( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1049498; // dark moongate - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Harrower ); - } + writer.Write(m_Harrower); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Harrower = reader.ReadMobile(); + switch (version) + { + case 0: + { + m_Harrower = reader.ReadMobile(); - if ( m_Harrower == null ) - Delete(); + if (m_Harrower == null) + Delete(); - break; - } - } + break; + } + } - if ( Light != LightType.Circle300 ) - Light = LightType.Circle300; - } - } -} + if (Light != LightType.Circle300) + Light = LightType.Circle300; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/RestartTimer.cs b/Scripts/Engines/CannedEvil/RestartTimer.cs index 0c0705bb6..692d89fde 100644 --- a/Scripts/Engines/CannedEvil/RestartTimer.cs +++ b/Scripts/Engines/CannedEvil/RestartTimer.cs @@ -2,19 +2,19 @@ using System; namespace Server.Engines.CannedEvil { - public class RestartTimer : Timer - { - private ChampionSpawn m_Spawn; + public class RestartTimer : Timer + { + private ChampionSpawn m_Spawn; - public RestartTimer( ChampionSpawn spawn, TimeSpan delay ) : base( delay ) - { - m_Spawn = spawn; - Priority = TimerPriority.FiveSeconds; - } + public RestartTimer(ChampionSpawn spawn, TimeSpan delay) : base(delay) + { + m_Spawn = spawn; + Priority = TimerPriority.FiveSeconds; + } - protected override void OnTick() - { - m_Spawn.EndRestart(); - } - } + protected override void OnTick() + { + m_Spawn.EndRestart(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/SliceTimer.cs b/Scripts/Engines/CannedEvil/SliceTimer.cs index e06df4268..b28e52af1 100644 --- a/Scripts/Engines/CannedEvil/SliceTimer.cs +++ b/Scripts/Engines/CannedEvil/SliceTimer.cs @@ -2,19 +2,19 @@ using System; namespace Server.Engines.CannedEvil { - public class SliceTimer : Timer - { - private ChampionSpawn m_Spawn; + public class SliceTimer : Timer + { + private ChampionSpawn m_Spawn; - public SliceTimer( ChampionSpawn spawn ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Spawn = spawn; - Priority = TimerPriority.OneSecond; - } + public SliceTimer(ChampionSpawn spawn) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Spawn = spawn; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - m_Spawn.OnSlice(); - } - } + protected override void OnTick() + { + m_Spawn.OnSlice(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/CannedEvil/StarRoomGate.cs b/Scripts/Engines/CannedEvil/StarRoomGate.cs index 99ae352fd..6bd092caa 100644 --- a/Scripts/Engines/CannedEvil/StarRoomGate.cs +++ b/Scripts/Engines/CannedEvil/StarRoomGate.cs @@ -2,103 +2,103 @@ using System; namespace Server.Items { - public class StarRoomGate : Moongate - { - private bool m_Decays; - private DateTime m_DecayTime; - private Timer m_Timer; + public class StarRoomGate : Moongate + { + private bool m_Decays; + private DateTime m_DecayTime; + private Timer m_Timer; - public override int LabelNumber => 1049498; // dark moongate + [Constructible] + public StarRoomGate() : this(false) + { + } - [Constructible] - public StarRoomGate() : this( false ) - { - } + [Constructible] + public StarRoomGate(bool decays, Point3D loc, Map map) : this(decays) + { + MoveToWorld(loc, map); + Effects.PlaySound(loc, map, 0x20E); + } - [Constructible] - public StarRoomGate( bool decays, Point3D loc, Map map ) : this( decays ) - { - MoveToWorld( loc, map ); - Effects.PlaySound( loc, map, 0x20E ); - } + [Constructible] + public StarRoomGate(bool decays) : base(new Point3D(5143, 1774, 0), Map.Felucca) + { + Dispellable = false; + ItemID = 0x1FD4; - [Constructible] - public StarRoomGate( bool decays ) : base( new Point3D( 5143, 1774, 0 ), Map.Felucca ) - { - Dispellable = false; - ItemID = 0x1FD4; + if (decays) + { + m_Decays = true; + m_DecayTime = DateTime.UtcNow + TimeSpan.FromMinutes(2.0); - if ( decays ) - { - m_Decays = true; - m_DecayTime = DateTime.UtcNow + TimeSpan.FromMinutes( 2.0 ); + m_Timer = new InternalTimer(this, m_DecayTime); + m_Timer.Start(); + } + } - m_Timer = new InternalTimer( this, m_DecayTime ); - m_Timer.Start(); - } - } + public StarRoomGate(Serial serial) : base(serial) + { + } - public StarRoomGate( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1049498; // dark moongate - public override void OnAfterDelete() - { - m_Timer?.Stop(); + public override void OnAfterDelete() + { + m_Timer?.Stop(); - base.OnAfterDelete(); - } + base.OnAfterDelete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Decays ); + writer.Write(m_Decays); - if ( m_Decays ) - writer.WriteDeltaTime( m_DecayTime ); - } + if (m_Decays) + writer.WriteDeltaTime(m_DecayTime); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Decays = reader.ReadBool(); + switch (version) + { + case 0: + { + m_Decays = reader.ReadBool(); - if ( m_Decays ) - { - m_DecayTime = reader.ReadDeltaTime(); + if (m_Decays) + { + m_DecayTime = reader.ReadDeltaTime(); - m_Timer = new InternalTimer( this, m_DecayTime ); - m_Timer.Start(); - } + m_Timer = new InternalTimer(this, m_DecayTime); + m_Timer.Start(); + } - break; - } - } - } + break; + } + } + } - private class InternalTimer : Timer - { - private Item m_Item; + private class InternalTimer : Timer + { + private Item m_Item; - public InternalTimer( Item item, DateTime end ) : base( end - DateTime.UtcNow ) - { - m_Item = item; - } + public InternalTimer(Item item, DateTime end) : base(end - DateTime.UtcNow) + { + m_Item = item; + } - protected override void OnTick() - { - m_Item.Delete(); - } - } - } -} + protected override void OnTick() + { + m_Item.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Chat/Channel.cs b/Scripts/Engines/Chat/Channel.cs index 874bd3fdd..d50d7ee3e 100644 --- a/Scripts/Engines/Chat/Channel.cs +++ b/Scripts/Engines/Chat/Channel.cs @@ -1,516 +1,524 @@ -using System; using System.Collections.Generic; namespace Server.Engines.Chat { - public class Channel - { - private string m_Name; - private string m_Password; - private List m_Users, m_Banned, m_Moderators, m_Voices; - private bool m_VoiceRestricted; - - public Channel( string name ) - { - m_Name = name; - - m_Users = new List(); - m_Banned = new List(); - m_Moderators = new List(); - m_Voices = new List(); - } - - public Channel( string name, string password ) : this( name ) - { - m_Password = password; - } - - public string Name - { - get => m_Name; - set - { - SendCommand( ChatCommand.RemoveChannel, m_Name ); - m_Name = value; - SendCommand( ChatCommand.AddChannel, m_Name ); - SendCommand( ChatCommand.JoinedChannel, m_Name ); - } - } - - public string Password - { - get => m_Password; - set - { - string newValue = null; - - if ( value != null ) - { - newValue = value.Trim(); - - if ( string.IsNullOrEmpty( newValue ) ) - newValue = null; - } - - m_Password = newValue; - } - } - - public bool Contains( ChatUser user ) - { - return m_Users.Contains( user ); - } - - public bool IsBanned( ChatUser user ) - { - return m_Banned.Contains( user ); - } - - public bool CanTalk( ChatUser user ) - { - return ( !m_VoiceRestricted || m_Voices.Contains( user ) || m_Moderators.Contains( user ) ); - } - - public bool IsModerator( ChatUser user ) - { - return m_Moderators.Contains( user ); - } - - public bool IsVoiced( ChatUser user ) - { - return m_Voices.Contains( user ); - } - - public bool ValidatePassword( string password ) - { - return ( m_Password == null || Insensitive.Equals( m_Password, password ) ); - } - - public bool ValidateModerator( ChatUser user ) - { - if ( user != null && !IsModerator( user ) ) - { - user.SendMessage( 29 ); // You must have operator status to do this. - return false; - } - - return true; - } - - public bool ValidateAccess( ChatUser from, ChatUser target ) - { - if ( from != null && target != null && from.Mobile.AccessLevel < target.Mobile.AccessLevel ) - { - from.Mobile.SendMessage( "Your access level is too low to do this." ); - return false; - } - - return true; - } - - public bool AddUser( ChatUser user ) - { - return AddUser( user, null ); - } - - public bool AddUser( ChatUser user, string password ) - { - if ( Contains( user ) ) - { - user.SendMessage( 46, m_Name ); // You are already in the conference '%1'. - return true; - } - - if ( IsBanned( user ) ) - { - user.SendMessage( 64 ); // You have been banned from this conference. - return false; - } - if ( !ValidatePassword( password ) ) - { - user.SendMessage( 34 ); // That is not the correct password. - return false; - } - user.CurrentChannel?.RemoveUser( user ); // Remove them from their current channel first - - ChatSystem.SendCommandTo( user.Mobile, ChatCommand.JoinedChannel, m_Name ); - - SendCommand( ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); - - m_Users.Add( user ); - user.CurrentChannel = this; - - if ( user.Mobile.AccessLevel >= AccessLevel.GameMaster || (!AlwaysAvailable && m_Users.Count == 1) ) - AddModerator( user ); - - SendUsersTo( user ); - - return true; - } - - public void RemoveUser( ChatUser user ) - { - if ( Contains( user ) ) - { - m_Users.Remove( user ); - user.CurrentChannel = null; - - if ( m_Moderators.Contains( user ) ) - m_Moderators.Remove( user ); - - if ( m_Voices.Contains( user ) ) - m_Voices.Remove( user ); - - SendCommand( ChatCommand.RemoveUserFromChannel, user, user.Username ); - ChatSystem.SendCommandTo( user.Mobile, ChatCommand.LeaveChannel ); - - if ( m_Users.Count == 0 && !AlwaysAvailable ) - RemoveChannel( this ); - } - } - - public void AdBan( ChatUser user ) - { - AddBan( user, null ); - } - - public void AddBan( ChatUser user, ChatUser moderator ) - { - if ( !ValidateModerator( moderator ) || !ValidateAccess( moderator, user ) ) - return; - - if ( !m_Banned.Contains( user ) ) - m_Banned.Add( user ); - - Kick( user, moderator, true ); - } - - public void RemoveBan( ChatUser user ) - { - if ( m_Banned.Contains( user ) ) - m_Banned.Remove( user ); - } - - public void Kick( ChatUser user ) - { - Kick( user, null ); - } - - public void Kick( ChatUser user, ChatUser moderator ) - { - Kick( user, moderator, false ); - } - - public void Kick( ChatUser user, ChatUser moderator, bool wasBanned ) - { - if ( !ValidateModerator( moderator ) || !ValidateAccess( moderator, user ) ) - return; - - if ( Contains( user ) ) - { - if ( moderator != null ) - { - if ( wasBanned ) - user.SendMessage( 63, moderator.Username ); // %1, a conference moderator, has banned you from the conference. - else - user.SendMessage( 45, moderator.Username ); // %1, a conference moderator, has kicked you out of the conference. - } - - RemoveUser( user ); - ChatSystem.SendCommandTo( user.Mobile, ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); - - SendMessage( 44, user.Username ) ; // %1 has been kicked out of the conference. - } - - if ( wasBanned ) - moderator?.SendMessage( 62, user.Username ); // You are banning %1 from this conference. - } - - public bool VoiceRestricted - { - get => m_VoiceRestricted; - set - { - m_VoiceRestricted = value; - - if ( value ) - SendMessage( 56 ); // From now on, only moderators will have speaking privileges in this conference by default. - else - SendMessage( 55 ); // From now on, everyone in the conference will have speaking privileges by default. - } - } - - public bool AlwaysAvailable { get; set; } - - public void AddVoiced( ChatUser user ) - { - AddVoiced( user, null ); - } - - public void AddVoiced( ChatUser user, ChatUser moderator ) - { - if ( !ValidateModerator( moderator ) ) - return; - - if ( !IsBanned( user ) && !IsModerator( user ) && !IsVoiced( user ) ) - { - m_Voices.Add( user ); - - if ( moderator != null ) - user.SendMessage( 54, moderator.Username ); // %1, a conference moderator, has granted you speaking privileges in this conference. - - SendMessage( 52, user, user.Username ); // %1 now has speaking privileges in this conference. - SendCommand( ChatCommand.AddUserToChannel, user, user.GetColorCharacter() + user.Username ); - } - } - - public void RemoveVoiced( ChatUser user, ChatUser moderator ) - { - if ( !ValidateModerator( moderator ) || !ValidateAccess( moderator, user ) ) - return; - - if ( !IsModerator( user ) && IsVoiced( user ) ) - { - m_Voices.Remove( user ); - - if ( moderator != null ) - user.SendMessage( 53, moderator.Username ); // %1, a conference moderator, has removed your speaking privileges for this conference. - - SendMessage( 51, user, user.Username ); // %1 no longer has speaking privileges in this conference. - SendCommand( ChatCommand.AddUserToChannel, user, user.GetColorCharacter() + user.Username ); - } - } - - public void AddModerator( ChatUser user ) - { - AddModerator( user, null ); - } - - public void AddModerator( ChatUser user, ChatUser moderator ) - { - if ( !ValidateModerator( moderator ) ) - return; - - if ( IsBanned( user ) || IsModerator( user ) ) - return; - - if ( IsVoiced( user ) ) - m_Voices.Remove( user ); - - m_Moderators.Add( user ); - - if ( moderator != null ) - user.SendMessage( 50, moderator.Username ); // %1 has made you a conference moderator. - - SendMessage( 48, user, user.Username ); // %1 is now a conference moderator. - SendCommand( ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); - } - - public void RemoveModerator( ChatUser user ) - { - RemoveModerator( user, null ); - } - - public void RemoveModerator( ChatUser user, ChatUser moderator ) - { - if ( !ValidateModerator( moderator ) || !ValidateAccess( moderator, user ) ) - return; - - if ( IsModerator( user ) ) - { - m_Moderators.Remove( user ); - - if ( moderator != null ) - user.SendMessage( 49, moderator.Username ); // %1 has removed you from the list of conference moderators. - - SendMessage( 47, user, user.Username ); // %1 is no longer a conference moderator. - SendCommand( ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); - } - } - - public void SendMessage( int number ) - { - SendMessage( number, null, null, null ); - } - - public void SendMessage( int number, string param1 ) - { - SendMessage( number, null, param1, null ); - } - - public void SendMessage( int number, string param1, string param2 ) - { - SendMessage( number, null, param1, param2 ); - } - - public void SendMessage( int number, ChatUser initiator ) - { - SendMessage( number, initiator, null, null ); - } - - public void SendMessage( int number, ChatUser initiator, string param1 ) - { - SendMessage( number, initiator, param1, null ); - } - - public void SendMessage( int number, ChatUser initiator, string param1, string param2 ) - { - for ( int i = 0; i < m_Users.Count; ++i ) - { - ChatUser user = m_Users[i]; - - if ( user == initiator ) - continue; - - if ( user.CheckOnline() ) - user.SendMessage( number, param1, param2 ); - else if ( !Contains( user ) ) - --i; - } - } - - public void SendIgnorableMessage( int number, ChatUser from, string param1, string param2 ) - { - for ( int i = 0; i < m_Users.Count; ++i ) - { - ChatUser user = m_Users[i]; - - if ( user.IsIgnored( from ) ) - continue; - - if ( user.CheckOnline() ) - user.SendMessage( number, from.Mobile, param1, param2 ); - else if ( !Contains( user ) ) - --i; - } - } - - public void SendCommand( ChatCommand command ) - { - SendCommand( command, null, null, null ); - } - - public void SendCommand( ChatCommand command, string param1 ) - { - SendCommand( command, null, param1, null ); - } - - public void SendCommand( ChatCommand command, string param1, string param2 ) - { - SendCommand( command, null, param1, param2 ); - } - - public void SendCommand( ChatCommand command, ChatUser initiator ) - { - SendCommand( command, initiator, null, null ); - } - - public void SendCommand( ChatCommand command, ChatUser initiator, string param1 ) - { - SendCommand( command, initiator, param1, null ); - } - - public void SendCommand( ChatCommand command, ChatUser initiator, string param1, string param2 ) - { - for ( int i = 0; i < m_Users.Count; ++i ) - { - ChatUser user = m_Users[i]; - - if ( user == initiator ) - continue; - - if ( user.CheckOnline() ) - ChatSystem.SendCommandTo( user.Mobile, command, param1, param2 ); - else if ( !Contains( user ) ) - --i; - } - } - - public void SendUsersTo( ChatUser to ) - { - for ( int i = 0; i < m_Users.Count; ++i ) - { - ChatUser user = m_Users[i]; - - ChatSystem.SendCommandTo( to.Mobile, ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); - } - } - - public static List Channels { get; } = new List(); - - public static void SendChannelsTo( ChatUser user ) - { - for ( int i = 0; i < Channels.Count; ++i ) - { - Channel channel = Channels[i]; - - if ( !channel.IsBanned( user ) ) - ChatSystem.SendCommandTo( user.Mobile, ChatCommand.AddChannel, channel.Name, "0" ); - } - } - - public static Channel AddChannel( string name ) - { - return AddChannel( name, null ); - } - - public static Channel AddChannel( string name, string password ) - { - Channel channel = FindChannelByName( name ); - - if ( channel == null ) - { - channel = new Channel( name, password ); - Channels.Add( channel ); - } - - ChatUser.GlobalSendCommand( ChatCommand.AddChannel, name, "0" ) ; - - return channel; - } - - public static void RemoveChannel( string name ) - { - RemoveChannel( FindChannelByName( name ) ); - } - - public static void RemoveChannel( Channel channel ) - { - if ( channel == null ) - return; - - if ( Channels.Contains( channel ) && channel.m_Users.Count == 0 ) - { - ChatUser.GlobalSendCommand( ChatCommand.RemoveChannel, channel.Name ) ; - - channel.m_Moderators.Clear(); - channel.m_Voices.Clear(); - - Channels.Remove( channel ); - } - } - - public static Channel FindChannelByName( string name ) - { - for ( int i = 0; i < Channels.Count; ++i ) - { - Channel channel = Channels[i]; - - if ( channel.m_Name == name ) - return channel; - } - - return null; - } - - public static void Initialize() - { - AddStaticChannel( "Newbie Help" ); - } - - public static void AddStaticChannel( string name ) - { - AddChannel( name ).AlwaysAvailable = true; - } - } -} + public class Channel + { + private string m_Name; + private string m_Password; + private List m_Users, m_Banned, m_Moderators, m_Voices; + private bool m_VoiceRestricted; + + public Channel(string name) + { + m_Name = name; + + m_Users = new List(); + m_Banned = new List(); + m_Moderators = new List(); + m_Voices = new List(); + } + + public Channel(string name, string password) : this(name) + { + m_Password = password; + } + + public string Name + { + get => m_Name; + set + { + SendCommand(ChatCommand.RemoveChannel, m_Name); + m_Name = value; + SendCommand(ChatCommand.AddChannel, m_Name); + SendCommand(ChatCommand.JoinedChannel, m_Name); + } + } + + public string Password + { + get => m_Password; + set + { + string newValue = null; + + if (value != null) + { + newValue = value.Trim(); + + if (string.IsNullOrEmpty(newValue)) + newValue = null; + } + + m_Password = newValue; + } + } + + public bool VoiceRestricted + { + get => m_VoiceRestricted; + set + { + m_VoiceRestricted = value; + + if (value) + SendMessage(56); // From now on, only moderators will have speaking privileges in this conference by default. + else + SendMessage(55); // From now on, everyone in the conference will have speaking privileges by default. + } + } + + public bool AlwaysAvailable{ get; set; } + + public static List Channels{ get; } = new List(); + + public bool Contains(ChatUser user) + { + return m_Users.Contains(user); + } + + public bool IsBanned(ChatUser user) + { + return m_Banned.Contains(user); + } + + public bool CanTalk(ChatUser user) + { + return !m_VoiceRestricted || m_Voices.Contains(user) || m_Moderators.Contains(user); + } + + public bool IsModerator(ChatUser user) + { + return m_Moderators.Contains(user); + } + + public bool IsVoiced(ChatUser user) + { + return m_Voices.Contains(user); + } + + public bool ValidatePassword(string password) + { + return m_Password == null || Insensitive.Equals(m_Password, password); + } + + public bool ValidateModerator(ChatUser user) + { + if (user != null && !IsModerator(user)) + { + user.SendMessage(29); // You must have operator status to do this. + return false; + } + + return true; + } + + public bool ValidateAccess(ChatUser from, ChatUser target) + { + if (from != null && target != null && from.Mobile.AccessLevel < target.Mobile.AccessLevel) + { + from.Mobile.SendMessage("Your access level is too low to do this."); + return false; + } + + return true; + } + + public bool AddUser(ChatUser user) + { + return AddUser(user, null); + } + + public bool AddUser(ChatUser user, string password) + { + if (Contains(user)) + { + user.SendMessage(46, m_Name); // You are already in the conference '%1'. + return true; + } + + if (IsBanned(user)) + { + user.SendMessage(64); // You have been banned from this conference. + return false; + } + + if (!ValidatePassword(password)) + { + user.SendMessage(34); // That is not the correct password. + return false; + } + + user.CurrentChannel?.RemoveUser(user); // Remove them from their current channel first + + ChatSystem.SendCommandTo(user.Mobile, ChatCommand.JoinedChannel, m_Name); + + SendCommand(ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username); + + m_Users.Add(user); + user.CurrentChannel = this; + + if (user.Mobile.AccessLevel >= AccessLevel.GameMaster || !AlwaysAvailable && m_Users.Count == 1) + AddModerator(user); + + SendUsersTo(user); + + return true; + } + + public void RemoveUser(ChatUser user) + { + if (Contains(user)) + { + m_Users.Remove(user); + user.CurrentChannel = null; + + if (m_Moderators.Contains(user)) + m_Moderators.Remove(user); + + if (m_Voices.Contains(user)) + m_Voices.Remove(user); + + SendCommand(ChatCommand.RemoveUserFromChannel, user, user.Username); + ChatSystem.SendCommandTo(user.Mobile, ChatCommand.LeaveChannel); + + if (m_Users.Count == 0 && !AlwaysAvailable) + RemoveChannel(this); + } + } + + public void AdBan(ChatUser user) + { + AddBan(user, null); + } + + public void AddBan(ChatUser user, ChatUser moderator) + { + if (!ValidateModerator(moderator) || !ValidateAccess(moderator, user)) + return; + + if (!m_Banned.Contains(user)) + m_Banned.Add(user); + + Kick(user, moderator, true); + } + + public void RemoveBan(ChatUser user) + { + if (m_Banned.Contains(user)) + m_Banned.Remove(user); + } + + public void Kick(ChatUser user) + { + Kick(user, null); + } + + public void Kick(ChatUser user, ChatUser moderator) + { + Kick(user, moderator, false); + } + + public void Kick(ChatUser user, ChatUser moderator, bool wasBanned) + { + if (!ValidateModerator(moderator) || !ValidateAccess(moderator, user)) + return; + + if (Contains(user)) + { + if (moderator != null) + { + if (wasBanned) + user.SendMessage(63, + moderator.Username); // %1, a conference moderator, has banned you from the conference. + else + user.SendMessage(45, + moderator.Username); // %1, a conference moderator, has kicked you out of the conference. + } + + RemoveUser(user); + ChatSystem.SendCommandTo(user.Mobile, ChatCommand.AddUserToChannel, + user.GetColorCharacter() + user.Username); + + SendMessage(44, user.Username); // %1 has been kicked out of the conference. + } + + if (wasBanned) + moderator?.SendMessage(62, user.Username); // You are banning %1 from this conference. + } + + public void AddVoiced(ChatUser user) + { + AddVoiced(user, null); + } + + public void AddVoiced(ChatUser user, ChatUser moderator) + { + if (!ValidateModerator(moderator)) + return; + + if (!IsBanned(user) && !IsModerator(user) && !IsVoiced(user)) + { + m_Voices.Add(user); + + if (moderator != null) + user.SendMessage(54, + moderator + .Username); // %1, a conference moderator, has granted you speaking privileges in this conference. + + SendMessage(52, user, user.Username); // %1 now has speaking privileges in this conference. + SendCommand(ChatCommand.AddUserToChannel, user, user.GetColorCharacter() + user.Username); + } + } + + public void RemoveVoiced(ChatUser user, ChatUser moderator) + { + if (!ValidateModerator(moderator) || !ValidateAccess(moderator, user)) + return; + + if (!IsModerator(user) && IsVoiced(user)) + { + m_Voices.Remove(user); + + if (moderator != null) + user.SendMessage(53, + moderator + .Username); // %1, a conference moderator, has removed your speaking privileges for this conference. + + SendMessage(51, user, user.Username); // %1 no longer has speaking privileges in this conference. + SendCommand(ChatCommand.AddUserToChannel, user, user.GetColorCharacter() + user.Username); + } + } + + public void AddModerator(ChatUser user) + { + AddModerator(user, null); + } + + public void AddModerator(ChatUser user, ChatUser moderator) + { + if (!ValidateModerator(moderator)) + return; + + if (IsBanned(user) || IsModerator(user)) + return; + + if (IsVoiced(user)) + m_Voices.Remove(user); + + m_Moderators.Add(user); + + if (moderator != null) + user.SendMessage(50, moderator.Username); // %1 has made you a conference moderator. + + SendMessage(48, user, user.Username); // %1 is now a conference moderator. + SendCommand(ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username); + } + + public void RemoveModerator(ChatUser user) + { + RemoveModerator(user, null); + } + + public void RemoveModerator(ChatUser user, ChatUser moderator) + { + if (!ValidateModerator(moderator) || !ValidateAccess(moderator, user)) + return; + + if (IsModerator(user)) + { + m_Moderators.Remove(user); + + if (moderator != null) + user.SendMessage(49, moderator.Username); // %1 has removed you from the list of conference moderators. + + SendMessage(47, user, user.Username); // %1 is no longer a conference moderator. + SendCommand(ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username); + } + } + + public void SendMessage(int number) + { + SendMessage(number, null, null, null); + } + + public void SendMessage(int number, string param1) + { + SendMessage(number, null, param1, null); + } + + public void SendMessage(int number, string param1, string param2) + { + SendMessage(number, null, param1, param2); + } + + public void SendMessage(int number, ChatUser initiator) + { + SendMessage(number, initiator, null, null); + } + + public void SendMessage(int number, ChatUser initiator, string param1) + { + SendMessage(number, initiator, param1, null); + } + + public void SendMessage(int number, ChatUser initiator, string param1, string param2) + { + for (int i = 0; i < m_Users.Count; ++i) + { + ChatUser user = m_Users[i]; + + if (user == initiator) + continue; + + if (user.CheckOnline()) + user.SendMessage(number, param1, param2); + else if (!Contains(user)) + --i; + } + } + + public void SendIgnorableMessage(int number, ChatUser from, string param1, string param2) + { + for (int i = 0; i < m_Users.Count; ++i) + { + ChatUser user = m_Users[i]; + + if (user.IsIgnored(from)) + continue; + + if (user.CheckOnline()) + user.SendMessage(number, from.Mobile, param1, param2); + else if (!Contains(user)) + --i; + } + } + + public void SendCommand(ChatCommand command) + { + SendCommand(command, null, null, null); + } + + public void SendCommand(ChatCommand command, string param1) + { + SendCommand(command, null, param1, null); + } + + public void SendCommand(ChatCommand command, string param1, string param2) + { + SendCommand(command, null, param1, param2); + } + + public void SendCommand(ChatCommand command, ChatUser initiator) + { + SendCommand(command, initiator, null, null); + } + + public void SendCommand(ChatCommand command, ChatUser initiator, string param1) + { + SendCommand(command, initiator, param1, null); + } + + public void SendCommand(ChatCommand command, ChatUser initiator, string param1, string param2) + { + for (int i = 0; i < m_Users.Count; ++i) + { + ChatUser user = m_Users[i]; + + if (user == initiator) + continue; + + if (user.CheckOnline()) + ChatSystem.SendCommandTo(user.Mobile, command, param1, param2); + else if (!Contains(user)) + --i; + } + } + + public void SendUsersTo(ChatUser to) + { + for (int i = 0; i < m_Users.Count; ++i) + { + ChatUser user = m_Users[i]; + + ChatSystem.SendCommandTo(to.Mobile, ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username); + } + } + + public static void SendChannelsTo(ChatUser user) + { + for (int i = 0; i < Channels.Count; ++i) + { + Channel channel = Channels[i]; + + if (!channel.IsBanned(user)) + ChatSystem.SendCommandTo(user.Mobile, ChatCommand.AddChannel, channel.Name, "0"); + } + } + + public static Channel AddChannel(string name) + { + return AddChannel(name, null); + } + + public static Channel AddChannel(string name, string password) + { + Channel channel = FindChannelByName(name); + + if (channel == null) + { + channel = new Channel(name, password); + Channels.Add(channel); + } + + ChatUser.GlobalSendCommand(ChatCommand.AddChannel, name, "0"); + + return channel; + } + + public static void RemoveChannel(string name) + { + RemoveChannel(FindChannelByName(name)); + } + + public static void RemoveChannel(Channel channel) + { + if (channel == null) + return; + + if (Channels.Contains(channel) && channel.m_Users.Count == 0) + { + ChatUser.GlobalSendCommand(ChatCommand.RemoveChannel, channel.Name); + + channel.m_Moderators.Clear(); + channel.m_Voices.Clear(); + + Channels.Remove(channel); + } + } + + public static Channel FindChannelByName(string name) + { + for (int i = 0; i < Channels.Count; ++i) + { + Channel channel = Channels[i]; + + if (channel.m_Name == name) + return channel; + } + + return null; + } + + public static void Initialize() + { + AddStaticChannel("Newbie Help"); + } + + public static void AddStaticChannel(string name) + { + AddChannel(name).AlwaysAvailable = true; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Chat/Chat.cs b/Scripts/Engines/Chat/Chat.cs index ad3e5ad49..6bb570bc6 100644 --- a/Scripts/Engines/Chat/Chat.cs +++ b/Scripts/Engines/Chat/Chat.cs @@ -1,164 +1,160 @@ using System; +using System.IO; +using Server.Accounting; using Server.Misc; using Server.Network; -using Server.Accounting; namespace Server.Engines.Chat { - public class ChatSystem - { - public static bool Enabled { get; set; } = true; + public class ChatSystem + { + public static bool Enabled{ get; set; } = true; - public static void Initialize() - { - PacketHandlers.Register( 0xB5, 0x40, true, OpenChatWindowRequest ); - PacketHandlers.Register( 0xB3, 0, true, ChatAction ); - } + public static void Initialize() + { + PacketHandlers.Register(0xB5, 0x40, true, OpenChatWindowRequest); + PacketHandlers.Register(0xB3, 0, true, ChatAction); + } - public static void SendCommandTo( Mobile to, ChatCommand type ) - { - SendCommandTo( to, type, null, null ); - } + public static void SendCommandTo(Mobile to, ChatCommand type) + { + SendCommandTo(to, type, null, null); + } - public static void SendCommandTo( Mobile to, ChatCommand type, string param1 ) - { - SendCommandTo( to, type, param1, null ); - } + public static void SendCommandTo(Mobile to, ChatCommand type, string param1) + { + SendCommandTo(to, type, param1, null); + } - public static void SendCommandTo( Mobile to, ChatCommand type, string param1, string param2 ) - { - to?.Send( new ChatMessagePacket( null, (int)type + 20, param1, param2 ) ); - } + public static void SendCommandTo(Mobile to, ChatCommand type, string param1, string param2) + { + to?.Send(new ChatMessagePacket(null, (int)type + 20, param1, param2)); + } - public static void OpenChatWindowRequest( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; + public static void OpenChatWindowRequest(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; - if ( !Enabled ) - { - from.SendMessage( "The chat system has been disabled." ); - return; - } + if (!Enabled) + { + from.SendMessage("The chat system has been disabled."); + return; + } - pvSrc.Seek( 2, System.IO.SeekOrigin.Begin ); - string chatName = pvSrc.ReadUnicodeStringSafe( ( 0x40 - 2 ) >> 1 ).Trim(); + pvSrc.Seek(2, SeekOrigin.Begin); + string chatName = pvSrc.ReadUnicodeStringSafe((0x40 - 2) >> 1).Trim(); - Account acct = state.Account as Account; + Account acct = state.Account as Account; - string accountChatName = null; + string accountChatName = null; - if ( acct != null ) - accountChatName = acct.GetTag( "ChatName" ); + if (acct != null) + accountChatName = acct.GetTag("ChatName"); - accountChatName = accountChatName?.Trim(); + accountChatName = accountChatName?.Trim(); - if ( accountChatName != null && accountChatName.Length > 0 ) - { - if ( chatName.Length > 0 && chatName != accountChatName ) - from.SendMessage( "You cannot change chat nickname once it has been set." ); - } - else - { - if ( chatName == null || chatName.Length == 0 ) - { - SendCommandTo( from, ChatCommand.AskNewNickname ); - return; - } + if (accountChatName != null && accountChatName.Length > 0) + { + if (chatName.Length > 0 && chatName != accountChatName) + from.SendMessage("You cannot change chat nickname once it has been set."); + } + else + { + if (chatName == null || chatName.Length == 0) + { + SendCommandTo(from, ChatCommand.AskNewNickname); + return; + } - if ( NameVerification.Validate( chatName, 2, 31, true, true, true, 0, NameVerification.SpaceDashPeriodQuote ) && chatName.ToLower().IndexOf( "system" ) == -1 ) - { - // TODO: Optimize this search + if (NameVerification.Validate(chatName, 2, 31, true, true, true, 0, NameVerification.SpaceDashPeriodQuote) && + chatName.ToLower().IndexOf("system") == -1) + { + // TODO: Optimize this search - foreach ( Account checkAccount in Accounts.GetAccounts() ) - { - string existingName = checkAccount.GetTag( "ChatName" ); + foreach (Account checkAccount in Accounts.GetAccounts()) + { + string existingName = checkAccount.GetTag("ChatName"); - if ( existingName != null ) - { - existingName = existingName.Trim(); + if (existingName != null) + { + existingName = existingName.Trim(); - if ( Insensitive.Equals( existingName, chatName ) ) - { - from.SendMessage( "Nickname already in use." ); - SendCommandTo( from, ChatCommand.AskNewNickname ); - return; - } - } - } + if (Insensitive.Equals(existingName, chatName)) + { + from.SendMessage("Nickname already in use."); + SendCommandTo(from, ChatCommand.AskNewNickname); + return; + } + } + } - accountChatName = chatName; + accountChatName = chatName; - acct?.AddTag( "ChatName", chatName ); - } - else - { - from.SendLocalizedMessage( 501173 ); // That name is disallowed. - SendCommandTo( from, ChatCommand.AskNewNickname ); - return; - } - } + acct?.AddTag("ChatName", chatName); + } + else + { + from.SendLocalizedMessage(501173); // That name is disallowed. + SendCommandTo(from, ChatCommand.AskNewNickname); + return; + } + } - SendCommandTo( from, ChatCommand.OpenChatWindow, accountChatName ); - ChatUser.AddChatUser( from ); - } + SendCommandTo(from, ChatCommand.OpenChatWindow, accountChatName); + ChatUser.AddChatUser(from); + } - public static ChatUser SearchForUser( ChatUser from, string name ) - { - ChatUser user = ChatUser.GetChatUser( name ); + public static ChatUser SearchForUser(ChatUser from, string name) + { + ChatUser user = ChatUser.GetChatUser(name); - if ( user == null ) - from.SendMessage( 32, name ); // There is no player named '%1'. + if (user == null) + from.SendMessage(32, name); // There is no player named '%1'. - return user; - } + return user; + } - public static void ChatAction( NetState state, PacketReader pvSrc ) - { - if ( !Enabled ) - return; + public static void ChatAction(NetState state, PacketReader pvSrc) + { + if (!Enabled) + return; - try - { - Mobile from = state.Mobile; - ChatUser user = ChatUser.GetChatUser( from ); + try + { + Mobile from = state.Mobile; + ChatUser user = ChatUser.GetChatUser(from); - if ( user == null ) - return; + if (user == null) + return; - string lang = pvSrc.ReadStringSafe( 4 ); - int actionID = pvSrc.ReadInt16(); - string param = pvSrc.ReadUnicodeString(); + string lang = pvSrc.ReadStringSafe(4); + int actionID = pvSrc.ReadInt16(); + string param = pvSrc.ReadUnicodeString(); - ChatActionHandler handler = ChatActionHandlers.GetHandler( actionID ); + ChatActionHandler handler = ChatActionHandlers.GetHandler(actionID); - if ( handler != null ) - { - Channel channel = user.CurrentChannel; + if (handler != null) + { + Channel channel = user.CurrentChannel; - if ( handler.RequireConference && channel == null ) - { - user.SendMessage( 31 ); /* You must be in a conference to do this. + if (handler.RequireConference && channel == null) + user.SendMessage(31); /* You must be in a conference to do this. * To join a conference, select one from the Conference menu. */ - } - else if ( handler.RequireModerator && !user.IsModerator ) - { - user.SendMessage( 29 ); // You must have operator status to do this. - } - else - { - handler.Callback( user, channel, param ); - } - } - else - { - Console.WriteLine( "Client: {0}: Unknown chat action 0x{1:X}: {2}", state, actionID, param ); - } - } - catch ( Exception e ) - { - Console.WriteLine( e ); - } - } - } + else if (handler.RequireModerator && !user.IsModerator) + user.SendMessage(29); // You must have operator status to do this. + else + handler.Callback(user, channel, param); + } + else + { + Console.WriteLine("Client: {0}: Unknown chat action 0x{1:X}: {2}", state, actionID, param); + } + } + catch (Exception e) + { + Console.WriteLine(e); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Chat/ChatActionHandler.cs b/Scripts/Engines/Chat/ChatActionHandler.cs index 7115cd5d0..5130d31b4 100644 --- a/Scripts/Engines/Chat/ChatActionHandler.cs +++ b/Scripts/Engines/Chat/ChatActionHandler.cs @@ -1,20 +1,20 @@ namespace Server.Engines.Chat { - public delegate void OnChatAction( ChatUser from, Channel channel, string param ); + public delegate void OnChatAction(ChatUser from, Channel channel, string param); - public class ChatActionHandler - { - public bool RequireModerator { get; } + public class ChatActionHandler + { + public ChatActionHandler(bool requireModerator, bool requireConference, OnChatAction callback) + { + RequireModerator = requireModerator; + RequireConference = requireConference; + Callback = callback; + } - public bool RequireConference { get; } + public bool RequireModerator{ get; } - public OnChatAction Callback { get; } + public bool RequireConference{ get; } - public ChatActionHandler( bool requireModerator, bool requireConference, OnChatAction callback ) - { - RequireModerator = requireModerator; - RequireConference = requireConference; - Callback = callback; - } - } + public OnChatAction Callback{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Chat/ChatActionHandlers.cs b/Scripts/Engines/Chat/ChatActionHandlers.cs index 81851b3bf..8175aa3da 100644 --- a/Scripts/Engines/Chat/ChatActionHandlers.cs +++ b/Scripts/Engines/Chat/ChatActionHandlers.cs @@ -1,355 +1,358 @@ namespace Server.Engines.Chat { - public class ChatActionHandlers - { - private static ChatActionHandler[] m_Handlers; + public class ChatActionHandlers + { + private static ChatActionHandler[] m_Handlers; - static ChatActionHandlers() - { - m_Handlers = new ChatActionHandler[0x100]; + static ChatActionHandlers() + { + m_Handlers = new ChatActionHandler[0x100]; - Register( 0x41, true, true, ChangeChannelPassword ); + Register(0x41, true, true, ChangeChannelPassword); - Register( 0x58, false, false, LeaveChat ); + Register(0x58, false, false, LeaveChat); - Register( 0x61, false, true, ChannelMessage ); - Register( 0x62, false, false, JoinChannel ); - Register( 0x63, false, false, JoinNewChannel ); - Register( 0x64, true, true, RenameChannel ); - Register( 0x65, false, false, PrivateMessage ); - Register( 0x66, false, false, AddIgnore ); - Register( 0x67, false, false, RemoveIgnore ); - Register( 0x68, false, false, ToggleIgnore ); - Register( 0x69, true, true, AddVoice ); - Register( 0x6A, true, true, RemoveVoice ); - Register( 0x6B, true, true, ToggleVoice ); - Register( 0x6C, true, true, AddModerator ); - Register( 0x6D, true, true, RemoveModerator ); - Register( 0x6E, true, true, ToggleModerator ); - Register( 0x6F, false, false, AllowPrivateMessages ); - Register( 0x70, false, false, DisallowPrivateMessages ); - Register( 0x71, false, false, TogglePrivateMessages ); - Register( 0x72, false, false, ShowCharacterName ); - Register( 0x73, false, false, HideCharacterName ); - Register( 0x74, false, false, ToggleCharacterName ); - Register( 0x75, false, false, QueryWhoIs ); - Register( 0x76, true, true, Kick ); - Register( 0x77, true, true, EnableDefaultVoice ); - Register( 0x78, true, true, DisableDefaultVoice ); - Register( 0x79, true, true, ToggleDefaultVoice ); - Register( 0x7A, false, true, EmoteMessage ); - } + Register(0x61, false, true, ChannelMessage); + Register(0x62, false, false, JoinChannel); + Register(0x63, false, false, JoinNewChannel); + Register(0x64, true, true, RenameChannel); + Register(0x65, false, false, PrivateMessage); + Register(0x66, false, false, AddIgnore); + Register(0x67, false, false, RemoveIgnore); + Register(0x68, false, false, ToggleIgnore); + Register(0x69, true, true, AddVoice); + Register(0x6A, true, true, RemoveVoice); + Register(0x6B, true, true, ToggleVoice); + Register(0x6C, true, true, AddModerator); + Register(0x6D, true, true, RemoveModerator); + Register(0x6E, true, true, ToggleModerator); + Register(0x6F, false, false, AllowPrivateMessages); + Register(0x70, false, false, DisallowPrivateMessages); + Register(0x71, false, false, TogglePrivateMessages); + Register(0x72, false, false, ShowCharacterName); + Register(0x73, false, false, HideCharacterName); + Register(0x74, false, false, ToggleCharacterName); + Register(0x75, false, false, QueryWhoIs); + Register(0x76, true, true, Kick); + Register(0x77, true, true, EnableDefaultVoice); + Register(0x78, true, true, DisableDefaultVoice); + Register(0x79, true, true, ToggleDefaultVoice); + Register(0x7A, false, true, EmoteMessage); + } - public static void Register( int actionID, bool requireModerator, bool requireConference, OnChatAction callback ) - { - if ( actionID >= 0 && actionID < m_Handlers.Length ) - m_Handlers[actionID] = new ChatActionHandler( requireModerator, requireConference, callback ); - } + public static void Register(int actionID, bool requireModerator, bool requireConference, OnChatAction callback) + { + if (actionID >= 0 && actionID < m_Handlers.Length) + m_Handlers[actionID] = new ChatActionHandler(requireModerator, requireConference, callback); + } - public static ChatActionHandler GetHandler( int actionID ) - { - if ( actionID >= 0 && actionID < m_Handlers.Length ) - return m_Handlers[actionID]; + public static ChatActionHandler GetHandler(int actionID) + { + if (actionID >= 0 && actionID < m_Handlers.Length) + return m_Handlers[actionID]; - return null; - } + return null; + } - public static void ChannelMessage( ChatUser from, Channel channel, string param ) - { - if ( channel.CanTalk( from ) ) - channel.SendIgnorableMessage( 57, from, from.GetColorCharacter() + from.Username, param ); // %1: %2 - else - from.SendMessage( 36 ); // The moderator of this conference has not given you speaking privileges. - } + public static void ChannelMessage(ChatUser from, Channel channel, string param) + { + if (channel.CanTalk(from)) + channel.SendIgnorableMessage(57, from, from.GetColorCharacter() + from.Username, param); // %1: %2 + else + from.SendMessage(36); // The moderator of this conference has not given you speaking privileges. + } - public static void EmoteMessage( ChatUser from, Channel channel, string param ) - { - if ( channel.CanTalk( from ) ) - channel.SendIgnorableMessage( 58, from, from.GetColorCharacter() + from.Username, param ); // %1 %2 - else - from.SendMessage( 36 ); // The moderator of this conference has not given you speaking privileges. - } + public static void EmoteMessage(ChatUser from, Channel channel, string param) + { + if (channel.CanTalk(from)) + channel.SendIgnorableMessage(58, from, from.GetColorCharacter() + from.Username, param); // %1 %2 + else + from.SendMessage(36); // The moderator of this conference has not given you speaking privileges. + } - public static void PrivateMessage( ChatUser from, Channel channel, string param ) - { - int indexOf = param.IndexOf( ' ' ); + public static void PrivateMessage(ChatUser from, Channel channel, string param) + { + int indexOf = param.IndexOf(' '); - string name = param.Substring( 0, indexOf ); - string text = param.Substring( indexOf + 1 ); + string name = param.Substring(0, indexOf); + string text = param.Substring(indexOf + 1); - ChatUser target = ChatSystem.SearchForUser( from, name ); + ChatUser target = ChatSystem.SearchForUser(from, name); - if ( target == null ) - return; + if (target == null) + return; - if ( target.IsIgnored( from ) ) - from.SendMessage( 35, target.Username ); // %1 has chosen to ignore you. None of your messages to them will get through. - else if ( target.IgnorePrivateMessage ) - from.SendMessage( 42, target.Username ); // %1 has chosen to not receive private messages at the moment. - else - target.SendMessage( 59, from.Mobile, from.GetColorCharacter() + from.Username, text ); // [%1]: %2 - } + if (target.IsIgnored(from)) + from.SendMessage(35, + target.Username); // %1 has chosen to ignore you. None of your messages to them will get through. + else if (target.IgnorePrivateMessage) + from.SendMessage(42, target.Username); // %1 has chosen to not receive private messages at the moment. + else + target.SendMessage(59, from.Mobile, from.GetColorCharacter() + from.Username, text); // [%1]: %2 + } - public static void LeaveChat( ChatUser from, Channel channel, string param ) - { - ChatUser.RemoveChatUser( from ); - } + public static void LeaveChat(ChatUser from, Channel channel, string param) + { + ChatUser.RemoveChatUser(from); + } - public static void ChangeChannelPassword( ChatUser from, Channel channel, string param ) - { - channel.Password = param; - from.SendMessage( 60 ); // The password to the conference has been changed. - } + public static void ChangeChannelPassword(ChatUser from, Channel channel, string param) + { + channel.Password = param; + from.SendMessage(60); // The password to the conference has been changed. + } - public static void AllowPrivateMessages( ChatUser from, Channel channel, string param ) - { - from.IgnorePrivateMessage = false; - from.SendMessage( 37 ); // You can now receive private messages. - } + public static void AllowPrivateMessages(ChatUser from, Channel channel, string param) + { + from.IgnorePrivateMessage = false; + from.SendMessage(37); // You can now receive private messages. + } - public static void DisallowPrivateMessages( ChatUser from, Channel channel, string param ) - { - from.IgnorePrivateMessage = true; - from.SendMessage( 38 ); /* You will no longer receive private messages. + public static void DisallowPrivateMessages(ChatUser from, Channel channel, string param) + { + from.IgnorePrivateMessage = true; + from.SendMessage(38); /* You will no longer receive private messages. * Those who send you a message will be notified that you are blocking incoming messages. */ - } + } - public static void TogglePrivateMessages( ChatUser from, Channel channel, string param ) - { - from.IgnorePrivateMessage = !from.IgnorePrivateMessage; - from.SendMessage( from.IgnorePrivateMessage ? 38 : 37 ); // See above for messages - } + public static void TogglePrivateMessages(ChatUser from, Channel channel, string param) + { + from.IgnorePrivateMessage = !from.IgnorePrivateMessage; + from.SendMessage(from.IgnorePrivateMessage ? 38 : 37); // See above for messages + } - public static void ShowCharacterName( ChatUser from, Channel channel, string param ) - { - from.Anonymous = false; - from.SendMessage( 39 ); // You are now showing your character name to any players who inquire with the whois command. - } + public static void ShowCharacterName(ChatUser from, Channel channel, string param) + { + from.Anonymous = false; + from.SendMessage( + 39); // You are now showing your character name to any players who inquire with the whois command. + } - public static void HideCharacterName( ChatUser from, Channel channel, string param ) - { - from.Anonymous = true; - from.SendMessage( 40 ); // You are no longer showing your character name to any players who inquire with the whois command. - } + public static void HideCharacterName(ChatUser from, Channel channel, string param) + { + from.Anonymous = true; + from.SendMessage( + 40); // You are no longer showing your character name to any players who inquire with the whois command. + } - public static void ToggleCharacterName( ChatUser from, Channel channel, string param ) - { - from.Anonymous = !from.Anonymous; - from.SendMessage( from.Anonymous ? 40 : 39 ); // See above for messages - } + public static void ToggleCharacterName(ChatUser from, Channel channel, string param) + { + from.Anonymous = !from.Anonymous; + from.SendMessage(from.Anonymous ? 40 : 39); // See above for messages + } - public static void JoinChannel( ChatUser from, Channel channel, string param ) - { - string name; - string password = null; + public static void JoinChannel(ChatUser from, Channel channel, string param) + { + string name; + string password = null; - int start = param.IndexOf( '\"' ); + int start = param.IndexOf('\"'); - if ( start >= 0 ) - { - int end = param.IndexOf( '\"', ++start ); + if (start >= 0) + { + int end = param.IndexOf('\"', ++start); - if ( end >= 0 ) - { - name = param.Substring( start, end - start ); - password = param.Substring( ++end ); - } - else - { - name = param.Substring( start ); - } - } - else - { - int indexOf = param.IndexOf( ' ' ); + if (end >= 0) + { + name = param.Substring(start, end - start); + password = param.Substring(++end); + } + else + { + name = param.Substring(start); + } + } + else + { + int indexOf = param.IndexOf(' '); - if ( indexOf >= 0 ) - { - name = param.Substring( 0, indexOf++ ); - password = param.Substring( indexOf ); - } - else - { - name = param; - } - } + if (indexOf >= 0) + { + name = param.Substring(0, indexOf++); + password = param.Substring(indexOf); + } + else + { + name = param; + } + } - password = password?.Trim(); + password = password?.Trim(); - if ( password != null && password.Length == 0 ) - password = null; + if (password != null && password.Length == 0) + password = null; - Channel joined = Channel.FindChannelByName( name ); + Channel joined = Channel.FindChannelByName(name); - if ( joined == null ) - from.SendMessage( 33, name ); // There is no conference named '%1'. - else - joined.AddUser( from, password ); - } + if (joined == null) + from.SendMessage(33, name); // There is no conference named '%1'. + else + joined.AddUser(from, password); + } - public static void JoinNewChannel( ChatUser from, Channel channel, string param ) - { - if ( (param = param.Trim()).Length == 0 ) - return; + public static void JoinNewChannel(ChatUser from, Channel channel, string param) + { + if ((param = param.Trim()).Length == 0) + return; - string name; - string password = null; + string name; + string password = null; - int start = param.IndexOf( '{' ); + int start = param.IndexOf('{'); - if ( start >= 0 ) - { - name = param.Substring( 0, start++ ); + if (start >= 0) + { + name = param.Substring(0, start++); - int end = param.IndexOf( '}', start ); + int end = param.IndexOf('}', start); - if ( end >= start ) - password = param.Substring( start, end - start ); - } - else - { - name = param; - } + if (end >= start) + password = param.Substring(start, end - start); + } + else + { + name = param; + } - password = password?.Trim(); + password = password?.Trim(); - if ( password != null && password.Length == 0 ) - password = null; + if (password != null && password.Length == 0) + password = null; - Channel.AddChannel( name, password ).AddUser( from, password ); - } + Channel.AddChannel(name, password).AddUser(from, password); + } - public static void AddIgnore( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void AddIgnore(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target == null ) - return; + if (target == null) + return; - from.AddIgnored( target ); - } + from.AddIgnored(target); + } - public static void RemoveIgnore( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void RemoveIgnore(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target == null ) - return; + if (target == null) + return; - from.RemoveIgnored( target ); - } + from.RemoveIgnored(target); + } - public static void ToggleIgnore( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void ToggleIgnore(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target == null ) - return; + if (target == null) + return; - if ( from.IsIgnored( target ) ) - from.RemoveIgnored( target ); - else - from.AddIgnored( target ); - } + if (from.IsIgnored(target)) + from.RemoveIgnored(target); + else + from.AddIgnored(target); + } - public static void AddVoice( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void AddVoice(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target != null ) - channel.AddVoiced( target, from ); - } + if (target != null) + channel.AddVoiced(target, from); + } - public static void RemoveVoice( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void RemoveVoice(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target != null ) - channel.RemoveVoiced( target, from ); - } + if (target != null) + channel.RemoveVoiced(target, from); + } - public static void ToggleVoice( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void ToggleVoice(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target == null ) - return; + if (target == null) + return; - if ( channel.IsVoiced( target ) ) - channel.RemoveVoiced( target, from ); - else - channel.AddVoiced( target, from ); - } + if (channel.IsVoiced(target)) + channel.RemoveVoiced(target, from); + else + channel.AddVoiced(target, from); + } - public static void AddModerator( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void AddModerator(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target != null ) - channel.AddModerator( target, from ); - } + if (target != null) + channel.AddModerator(target, from); + } - public static void RemoveModerator( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void RemoveModerator(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target != null ) - channel.RemoveModerator( target, from ); - } + if (target != null) + channel.RemoveModerator(target, from); + } - public static void ToggleModerator( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void ToggleModerator(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target == null ) - return; + if (target == null) + return; - if ( channel.IsModerator( target ) ) - channel.RemoveModerator( target, from ); - else - channel.AddModerator( target, from ); - } + if (channel.IsModerator(target)) + channel.RemoveModerator(target, from); + else + channel.AddModerator(target, from); + } - public static void RenameChannel( ChatUser from, Channel channel, string param ) - { - channel.Name = param; - } + public static void RenameChannel(ChatUser from, Channel channel, string param) + { + channel.Name = param; + } - public static void QueryWhoIs( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void QueryWhoIs(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target == null ) - return; + if (target == null) + return; - if ( target.Anonymous ) - from.SendMessage( 41, target.Username ); // %1 is remaining anonymous. - else - from.SendMessage( 43, target.Username, target.Mobile.Name ); // %2 is known in the lands of Britannia as %2. - } + if (target.Anonymous) + from.SendMessage(41, target.Username); // %1 is remaining anonymous. + else + from.SendMessage(43, target.Username, target.Mobile.Name); // %2 is known in the lands of Britannia as %2. + } - public static void Kick( ChatUser from, Channel channel, string param ) - { - ChatUser target = ChatSystem.SearchForUser( from, param ); + public static void Kick(ChatUser from, Channel channel, string param) + { + ChatUser target = ChatSystem.SearchForUser(from, param); - if ( target != null ) - channel.Kick( target, from ); - } + if (target != null) + channel.Kick(target, from); + } - public static void EnableDefaultVoice( ChatUser from, Channel channel, string param ) - { - channel.VoiceRestricted = false; - } + public static void EnableDefaultVoice(ChatUser from, Channel channel, string param) + { + channel.VoiceRestricted = false; + } - public static void DisableDefaultVoice( ChatUser from, Channel channel, string param ) - { - channel.VoiceRestricted = true; - } + public static void DisableDefaultVoice(ChatUser from, Channel channel, string param) + { + channel.VoiceRestricted = true; + } - public static void ToggleDefaultVoice( ChatUser from, Channel channel, string param ) - { - channel.VoiceRestricted = !channel.VoiceRestricted; - } - } -} + public static void ToggleDefaultVoice(ChatUser from, Channel channel, string param) + { + channel.VoiceRestricted = !channel.VoiceRestricted; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Chat/ChatCommand.cs b/Scripts/Engines/Chat/ChatCommand.cs index 2c78bb201..bd7b81e4e 100644 --- a/Scripts/Engines/Chat/ChatCommand.cs +++ b/Scripts/Engines/Chat/ChatCommand.cs @@ -1,42 +1,50 @@ namespace Server.Engines.Chat { - public enum ChatCommand - { - /// - /// Add a channel to top list. - /// - AddChannel = 0x3E8, - /// - /// Remove channel from top list. - /// - RemoveChannel = 0x3E9, - /// - /// Queries for a new chat nickname. - /// - AskNewNickname = 0x3EB, - /// - /// Closes the chat window. - /// - CloseChatWindow = 0x3EC, - /// - /// Opens the chat window. - /// - OpenChatWindow = 0x3ED, - /// - /// Add a user to current channel. - /// - AddUserToChannel = 0x3EE, - /// - /// Remove a user from current channel. - /// - RemoveUserFromChannel = 0x3EF, - /// - /// Send a message putting generic conference name at top when player leaves a channel. - /// - LeaveChannel = 0x3F0, - /// - /// Send a message putting Channel name at top and telling player he joined the channel. - /// - JoinedChannel = 0x3F1 - } + public enum ChatCommand + { + /// + /// Add a channel to top list. + /// + AddChannel = 0x3E8, + + /// + /// Remove channel from top list. + /// + RemoveChannel = 0x3E9, + + /// + /// Queries for a new chat nickname. + /// + AskNewNickname = 0x3EB, + + /// + /// Closes the chat window. + /// + CloseChatWindow = 0x3EC, + + /// + /// Opens the chat window. + /// + OpenChatWindow = 0x3ED, + + /// + /// Add a user to current channel. + /// + AddUserToChannel = 0x3EE, + + /// + /// Remove a user from current channel. + /// + RemoveUserFromChannel = 0x3EF, + + /// + /// Send a message putting generic conference name at top when player leaves a channel. + /// + LeaveChannel = 0x3F0, + + /// + /// Send a message putting Channel name at top and telling player he joined the channel. + /// + JoinedChannel = 0x3F1 + } } \ No newline at end of file diff --git a/Scripts/Engines/Chat/ChatUser.cs b/Scripts/Engines/Chat/ChatUser.cs index 874129b1e..fd5bc596c 100644 --- a/Scripts/Engines/Chat/ChatUser.cs +++ b/Scripts/Engines/Chat/ChatUser.cs @@ -3,245 +3,245 @@ using Server.Accounting; namespace Server.Engines.Chat { - public class ChatUser - { - public ChatUser( Mobile m ) - { - Mobile = m; - Ignored = new List(); - Ignoring = new List(); - } + public class ChatUser + { + public const char NormalColorCharacter = '0'; + public const char ModeratorColorCharacter = '1'; + public const char VoicedColorCharacter = '2'; - public Mobile Mobile { get; } + private static List m_Users = new List(); + private static Dictionary m_Table = new Dictionary(); - public List Ignored { get; } + public ChatUser(Mobile m) + { + Mobile = m; + Ignored = new List(); + Ignoring = new List(); + } - public List Ignoring { get; } + public Mobile Mobile{ get; } - public string Username - { - get - { - if ( Mobile.Account is Account acct ) - return acct.GetTag( "ChatName" ); + public List Ignored{ get; } - return null; - } - set - { - if ( Mobile.Account is Account acct ) - acct.SetTag( "ChatName", value ); - } - } + public List Ignoring{ get; } - public Channel CurrentChannel { get; set; } + public string Username + { + get + { + if (Mobile.Account is Account acct) + return acct.GetTag("ChatName"); - public bool IsOnline => ( Mobile.NetState != null ); + return null; + } + set + { + if (Mobile.Account is Account acct) + acct.SetTag("ChatName", value); + } + } - public bool Anonymous { get; set; } + public Channel CurrentChannel{ get; set; } - public bool IgnorePrivateMessage { get; set; } + public bool IsOnline => Mobile.NetState != null; - public const char NormalColorCharacter = '0'; - public const char ModeratorColorCharacter = '1'; - public const char VoicedColorCharacter = '2'; + public bool Anonymous{ get; set; } - public char GetColorCharacter() - { - if ( CurrentChannel != null && CurrentChannel.IsModerator( this ) ) - return ModeratorColorCharacter; + public bool IgnorePrivateMessage{ get; set; } - if ( CurrentChannel != null && CurrentChannel.IsVoiced( this ) ) - return VoicedColorCharacter; + public bool IsModerator => CurrentChannel != null && CurrentChannel.IsModerator(this); - return NormalColorCharacter; - } + public char GetColorCharacter() + { + if (CurrentChannel != null && CurrentChannel.IsModerator(this)) + return ModeratorColorCharacter; - public bool CheckOnline() - { - if ( IsOnline ) - return true; + if (CurrentChannel != null && CurrentChannel.IsVoiced(this)) + return VoicedColorCharacter; - RemoveChatUser( this ); - return false; - } + return NormalColorCharacter; + } - public void SendMessage( int number ) - { - SendMessage( number, null, null ); - } + public bool CheckOnline() + { + if (IsOnline) + return true; - public void SendMessage( int number, string param1 ) - { - SendMessage( number, param1, null ); - } + RemoveChatUser(this); + return false; + } - public void SendMessage( int number, string param1, string param2 ) - { - if ( Mobile.NetState != null ) - Mobile.Send( new ChatMessagePacket( Mobile, number, param1, param2 ) ); - } + public void SendMessage(int number) + { + SendMessage(number, null, null); + } - public void SendMessage( int number, Mobile from, string param1, string param2 ) - { - if ( Mobile.NetState != null ) - Mobile.Send( new ChatMessagePacket( from, number, param1, param2 ) ); - } + public void SendMessage(int number, string param1) + { + SendMessage(number, param1, null); + } - public bool IsIgnored( ChatUser check ) - { - return Ignored.Contains( check ); - } + public void SendMessage(int number, string param1, string param2) + { + if (Mobile.NetState != null) + Mobile.Send(new ChatMessagePacket(Mobile, number, param1, param2)); + } - public bool IsModerator => ( CurrentChannel != null && CurrentChannel.IsModerator( this ) ); + public void SendMessage(int number, Mobile from, string param1, string param2) + { + if (Mobile.NetState != null) + Mobile.Send(new ChatMessagePacket(from, number, param1, param2)); + } - public void AddIgnored( ChatUser user ) - { - if ( IsIgnored( user ) ) - { - SendMessage( 22, user.Username ); // You are already ignoring %1. - } - else - { - Ignored.Add( user ); - user.Ignoring.Add( this ); + public bool IsIgnored(ChatUser check) + { + return Ignored.Contains(check); + } - SendMessage( 23, user.Username ); // You are now ignoring %1. - } - } + public void AddIgnored(ChatUser user) + { + if (IsIgnored(user)) + { + SendMessage(22, user.Username); // You are already ignoring %1. + } + else + { + Ignored.Add(user); + user.Ignoring.Add(this); - public void RemoveIgnored( ChatUser user ) - { - if ( IsIgnored( user ) ) - { - Ignored.Remove( user ); - user.Ignoring.Remove( this ); + SendMessage(23, user.Username); // You are now ignoring %1. + } + } - SendMessage( 24, user.Username ); // You are no longer ignoring %1. + public void RemoveIgnored(ChatUser user) + { + if (IsIgnored(user)) + { + Ignored.Remove(user); + user.Ignoring.Remove(this); - if ( Ignored.Count == 0 ) - SendMessage( 26 ); // You are no longer ignoring anyone. - } - else - { - SendMessage( 25, user.Username ); // You are not ignoring %1. - } - } + SendMessage(24, user.Username); // You are no longer ignoring %1. - private static List m_Users = new List(); - private static Dictionary m_Table = new Dictionary(); + if (Ignored.Count == 0) + SendMessage(26); // You are no longer ignoring anyone. + } + else + { + SendMessage(25, user.Username); // You are not ignoring %1. + } + } - public static ChatUser AddChatUser( Mobile from ) - { - ChatUser user = GetChatUser( from ); + public static ChatUser AddChatUser(Mobile from) + { + ChatUser user = GetChatUser(from); - if ( user == null ) - { - user = new ChatUser( from ); + if (user == null) + { + user = new ChatUser(from); - m_Users.Add( user ); - m_Table[from] = user; + m_Users.Add(user); + m_Table[from] = user; - Channel.SendChannelsTo( user ); + Channel.SendChannelsTo(user); - List list = Channel.Channels; + List list = Channel.Channels; - for ( int i = 0; i < list.Count; ++i ) - { - Channel c = list[i]; + for (int i = 0; i < list.Count; ++i) + { + Channel c = list[i]; - if ( c.AddUser( user ) ) - break; - } + if (c.AddUser(user)) + break; + } - //ChatSystem.SendCommandTo( user.m_Mobile, ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); - } + //ChatSystem.SendCommandTo( user.m_Mobile, ChatCommand.AddUserToChannel, user.GetColorCharacter() + user.Username ); + } - return user; - } + return user; + } - public static void RemoveChatUser( ChatUser user ) - { - if ( user == null ) - return; + public static void RemoveChatUser(ChatUser user) + { + if (user == null) + return; - for ( int i = 0; i < user.Ignoring.Count; ++i ) - user.Ignoring[i].RemoveIgnored( user ); + for (int i = 0; i < user.Ignoring.Count; ++i) + user.Ignoring[i].RemoveIgnored(user); - if ( m_Users.Contains( user ) ) - { - ChatSystem.SendCommandTo( user.Mobile, ChatCommand.CloseChatWindow ); + if (m_Users.Contains(user)) + { + ChatSystem.SendCommandTo(user.Mobile, ChatCommand.CloseChatWindow); - user.CurrentChannel?.RemoveUser( user ); + user.CurrentChannel?.RemoveUser(user); - m_Users.Remove( user ); - m_Table.Remove( user.Mobile ); - } - } + m_Users.Remove(user); + m_Table.Remove(user.Mobile); + } + } - public static void RemoveChatUser( Mobile from ) - { - ChatUser user = GetChatUser( from ); + public static void RemoveChatUser(Mobile from) + { + ChatUser user = GetChatUser(from); - RemoveChatUser( user ); - } + RemoveChatUser(user); + } - public static ChatUser GetChatUser( Mobile from ) - { - m_Table.TryGetValue( from, out ChatUser c ); - return c; - } + public static ChatUser GetChatUser(Mobile from) + { + m_Table.TryGetValue(from, out ChatUser c); + return c; + } - public static ChatUser GetChatUser( string username ) - { - for ( int i = 0; i < m_Users.Count; ++i ) - { - ChatUser user = m_Users[i]; + public static ChatUser GetChatUser(string username) + { + for (int i = 0; i < m_Users.Count; ++i) + { + ChatUser user = m_Users[i]; - if ( user.Username == username ) - return user; - } + if (user.Username == username) + return user; + } - return null; - } + return null; + } - public static void GlobalSendCommand( ChatCommand command ) - { - GlobalSendCommand( command, null, null, null ); - } + public static void GlobalSendCommand(ChatCommand command) + { + GlobalSendCommand(command, null, null, null); + } - public static void GlobalSendCommand( ChatCommand command, string param1 ) - { - GlobalSendCommand( command, null, param1, null ); - } + public static void GlobalSendCommand(ChatCommand command, string param1) + { + GlobalSendCommand(command, null, param1, null); + } - public static void GlobalSendCommand( ChatCommand command, string param1, string param2 ) - { - GlobalSendCommand( command, null, param1, param2 ); - } + public static void GlobalSendCommand(ChatCommand command, string param1, string param2) + { + GlobalSendCommand(command, null, param1, param2); + } - public static void GlobalSendCommand( ChatCommand command, ChatUser initiator ) - { - GlobalSendCommand( command, initiator, null, null ); - } + public static void GlobalSendCommand(ChatCommand command, ChatUser initiator) + { + GlobalSendCommand(command, initiator, null, null); + } - public static void GlobalSendCommand( ChatCommand command, ChatUser initiator, string param1 ) - { - GlobalSendCommand( command, initiator, param1, null ); - } + public static void GlobalSendCommand(ChatCommand command, ChatUser initiator, string param1) + { + GlobalSendCommand(command, initiator, param1, null); + } - public static void GlobalSendCommand( ChatCommand command, ChatUser initiator, string param1, string param2 ) - { - for ( int i = 0; i < m_Users.Count; ++i ) - { - ChatUser user = m_Users[i]; + public static void GlobalSendCommand(ChatCommand command, ChatUser initiator, string param1, string param2) + { + for (int i = 0; i < m_Users.Count; ++i) + { + ChatUser user = m_Users[i]; - if ( user == initiator ) - continue; + if (user == initiator) + continue; - if ( user.CheckOnline() ) - ChatSystem.SendCommandTo( user.Mobile, command, param1, param2 ); - } - } - } -} + if (user.CheckOnline()) + ChatSystem.SendCommandTo(user.Mobile, command, param1, param2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Chat/Chatold.cs b/Scripts/Engines/Chat/Chatold.cs index 34f3dac9d..0f3626116 100644 --- a/Scripts/Engines/Chat/Chatold.cs +++ b/Scripts/Engines/Chat/Chatold.cs @@ -1,15 +1,15 @@ namespace Server.Chat { - public class ChatSystem - { - public static void Initialize() - { - EventSink.ChatRequest += EventSink_ChatRequest; - } + public class ChatSystem + { + public static void Initialize() + { + EventSink.ChatRequest += EventSink_ChatRequest; + } - private static void EventSink_ChatRequest( ChatRequestEventArgs e ) - { - e.Mobile.SendMessage( "Chat is not currently supported." ); - } - } + private static void EventSink_ChatRequest(ChatRequestEventArgs e) + { + e.Mobile.SendMessage("Chat is not currently supported."); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Chat/Packets.cs b/Scripts/Engines/Chat/Packets.cs index 810708b90..3d8bfd563 100644 --- a/Scripts/Engines/Chat/Packets.cs +++ b/Scripts/Engines/Chat/Packets.cs @@ -1,29 +1,28 @@ -using System; using Server.Network; namespace Server.Engines.Chat { - public sealed class ChatMessagePacket : Packet - { - public ChatMessagePacket( Mobile who, int number, string param1, string param2 ) : base( 0xB2 ) - { - if ( param1 == null ) - param1 = string.Empty; + public sealed class ChatMessagePacket : Packet + { + public ChatMessagePacket(Mobile who, int number, string param1, string param2) : base(0xB2) + { + if (param1 == null) + param1 = string.Empty; - if ( param2 == null ) - param2 = string.Empty; + if (param2 == null) + param2 = string.Empty; - EnsureCapacity( 13 + ((param1.Length + param2.Length) * 2) ); + EnsureCapacity(13 + (param1.Length + param2.Length) * 2); - m_Stream.Write( (ushort) (number - 20) ); + m_Stream.Write((ushort)(number - 20)); - if ( who != null ) - m_Stream.WriteAsciiFixed( who.Language, 4 ); - else - m_Stream.Write( (int) 0 ); + if (who != null) + m_Stream.WriteAsciiFixed(who.Language, 4); + else + m_Stream.Write(0); - m_Stream.WriteBigUniNull( param1 ); - m_Stream.WriteBigUniNull( param2 ); - } - } + m_Stream.WriteBigUniNull(param1); + m_Stream.WriteBigUniNull(param2); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/AcceptDuelGump.cs b/Scripts/Engines/ConPVP/AcceptDuelGump.cs index 75afb1297..1bd265942 100644 --- a/Scripts/Engines/ConPVP/AcceptDuelGump.cs +++ b/Scripts/Engines/ConPVP/AcceptDuelGump.cs @@ -1,283 +1,282 @@ using System; using System.Collections; using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Engines.ConPVP { - public class AcceptDuelGump : Gump - { - private Mobile m_Challenger, m_Challenged; - private DuelContext m_Context; - private Participant m_Participant; - private int m_Slot; + public class AcceptDuelGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int BlackColor32 = 0x000008; - public string Center( string text ) - { - return $"
{text}
"; - } + private static Hashtable m_IgnoreLists = new Hashtable(); - public string Color( string text, int color ) - { - return $"{text}"; - } + private bool m_Active = true; + private Mobile m_Challenger, m_Challenged; + private DuelContext m_Context; + private Participant m_Participant; + private int m_Slot; - private const int LabelColor32 = 0xFFFFFF; - private const int BlackColor32 = 0x000008; + public AcceptDuelGump(Mobile challenger, Mobile challenged, DuelContext context, Participant p, int slot) : base(50, + 50) + { + m_Challenger = challenger; + m_Challenged = challenged; + m_Context = context; + m_Participant = p; + m_Slot = slot; - private bool m_Active = true; + challenged.CloseGump(typeof(AcceptDuelGump)); - public AcceptDuelGump( Mobile challenger, Mobile challenged, DuelContext context, Participant p, int slot ) : base( 50, 50 ) - { - m_Challenger = challenger; - m_Challenged = challenged; - m_Context = context; - m_Participant = p; - m_Slot = slot; + Closable = false; - challenged.CloseGump( typeof( AcceptDuelGump ) ); + AddPage(0); - Closable = false; + //AddBackground( 0, 0, 400, 220, 9150 ); + AddBackground(1, 1, 398, 218, 3600); + //AddBackground( 16, 15, 369, 189, 9100 ); - AddPage( 0 ); + AddImageTiled(16, 15, 369, 189, 3604); + AddAlphaRegion(16, 15, 369, 189); - //AddBackground( 0, 0, 400, 220, 9150 ); - AddBackground( 1, 1, 398, 218, 3600 ); - //AddBackground( 16, 15, 369, 189, 9100 ); + AddImage(215, -43, 0xEE40); + //AddImage( 330, 141, 0x8BA ); - AddImageTiled( 16, 15, 369, 189, 3604 ); - AddAlphaRegion( 16, 15, 369, 189 ); + AddHtml(22 - 1, 22, 294, 20, Color(Center("Duel Challenge"), BlackColor32), false, false); + AddHtml(22 + 1, 22, 294, 20, Color(Center("Duel Challenge"), BlackColor32), false, false); + AddHtml(22, 22 - 1, 294, 20, Color(Center("Duel Challenge"), BlackColor32), false, false); + AddHtml(22, 22 + 1, 294, 20, Color(Center("Duel Challenge"), BlackColor32), false, false); + AddHtml(22, 22, 294, 20, Color(Center("Duel Challenge"), LabelColor32), false, false); - AddImage( 215, -43, 0xEE40 ); - //AddImage( 330, 141, 0x8BA ); + string fmt; - AddHtml( 22-1, 22, 294, 20, Color( Center( "Duel Challenge" ), BlackColor32 ), false, false ); - AddHtml( 22+1, 22, 294, 20, Color( Center( "Duel Challenge" ), BlackColor32 ), false, false ); - AddHtml( 22, 22-1, 294, 20, Color( Center( "Duel Challenge" ), BlackColor32 ), false, false ); - AddHtml( 22, 22+1, 294, 20, Color( Center( "Duel Challenge" ), BlackColor32 ), false, false ); - AddHtml( 22, 22, 294, 20, Color( Center( "Duel Challenge" ), LabelColor32 ), false, false ); + if (p.Contains(challenger)) + fmt = "You have been asked to join sides with {0} in a duel. Do you accept?"; + else + fmt = "You have been challenged to a duel from {0}. Do you accept?"; - string fmt; + AddHtml(22 - 1, 50, 294, 40, Color(string.Format(fmt, challenger.Name), BlackColor32), false, false); + AddHtml(22 + 1, 50, 294, 40, Color(string.Format(fmt, challenger.Name), BlackColor32), false, false); + AddHtml(22, 50 - 1, 294, 40, Color(string.Format(fmt, challenger.Name), BlackColor32), false, false); + AddHtml(22, 50 + 1, 294, 40, Color(string.Format(fmt, challenger.Name), BlackColor32), false, false); + AddHtml(22, 50, 294, 40, Color(string.Format(fmt, challenger.Name), 0xB0C868), false, false); - if ( p.Contains( challenger ) ) - fmt = "You have been asked to join sides with {0} in a duel. Do you accept?"; - else - fmt = "You have been challenged to a duel from {0}. Do you accept?"; + AddImageTiled(32, 88, 264, 1, 9107); + AddImageTiled(42, 90, 264, 1, 9157); - AddHtml( 22-1, 50, 294, 40, Color( string.Format( fmt, challenger.Name ), BlackColor32 ), false, false ); - AddHtml( 22+1, 50, 294, 40, Color( string.Format( fmt, challenger.Name ), BlackColor32 ), false, false ); - AddHtml( 22, 50-1, 294, 40, Color( string.Format( fmt, challenger.Name ), BlackColor32 ), false, false ); - AddHtml( 22, 50+1, 294, 40, Color( string.Format( fmt, challenger.Name ), BlackColor32 ), false, false ); - AddHtml( 22, 50, 294, 40, Color( string.Format( fmt, challenger.Name ), 0xB0C868 ), false, false ); + AddRadio(24, 100, 9727, 9730, true, 1); + AddHtml(60 - 1, 105, 250, 20, Color("Yes, I will fight this duel.", BlackColor32), false, false); + AddHtml(60 + 1, 105, 250, 20, Color("Yes, I will fight this duel.", BlackColor32), false, false); + AddHtml(60, 105 - 1, 250, 20, Color("Yes, I will fight this duel.", BlackColor32), false, false); + AddHtml(60, 105 + 1, 250, 20, Color("Yes, I will fight this duel.", BlackColor32), false, false); + AddHtml(60, 105, 250, 20, Color("Yes, I will fight this duel.", LabelColor32), false, false); - AddImageTiled( 32, 88, 264, 1, 9107 ); - AddImageTiled( 42, 90, 264, 1, 9157 ); + AddRadio(24, 135, 9727, 9730, false, 2); + AddHtml(60 - 1, 140, 250, 20, Color("No, I do not wish to fight.", BlackColor32), false, false); + AddHtml(60 + 1, 140, 250, 20, Color("No, I do not wish to fight.", BlackColor32), false, false); + AddHtml(60, 140 - 1, 250, 20, Color("No, I do not wish to fight.", BlackColor32), false, false); + AddHtml(60, 140 + 1, 250, 20, Color("No, I do not wish to fight.", BlackColor32), false, false); + AddHtml(60, 140, 250, 20, Color("No, I do not wish to fight.", LabelColor32), false, false); - AddRadio( 24, 100, 9727, 9730, true, 1 ); - AddHtml( 60-1, 105, 250, 20, Color( "Yes, I will fight this duel.", BlackColor32 ), false, false ); - AddHtml( 60+1, 105, 250, 20, Color( "Yes, I will fight this duel.", BlackColor32 ), false, false ); - AddHtml( 60, 105-1, 250, 20, Color( "Yes, I will fight this duel.", BlackColor32 ), false, false ); - AddHtml( 60, 105+1, 250, 20, Color( "Yes, I will fight this duel.", BlackColor32 ), false, false ); - AddHtml( 60, 105, 250, 20, Color( "Yes, I will fight this duel.", LabelColor32 ), false, false ); + AddRadio(24, 170, 9727, 9730, false, 3); + AddHtml(60 - 1, 175, 250, 20, Color("No, knave. Do not ask again.", BlackColor32), false, false); + AddHtml(60 + 1, 175, 250, 20, Color("No, knave. Do not ask again.", BlackColor32), false, false); + AddHtml(60, 175 - 1, 250, 20, Color("No, knave. Do not ask again.", BlackColor32), false, false); + AddHtml(60, 175 + 1, 250, 20, Color("No, knave. Do not ask again.", BlackColor32), false, false); + AddHtml(60, 175, 250, 20, Color("No, knave. Do not ask again.", LabelColor32), false, false); - AddRadio( 24, 135, 9727, 9730, false, 2 ); - AddHtml( 60-1, 140, 250, 20, Color( "No, I do not wish to fight.", BlackColor32 ), false, false ); - AddHtml( 60+1, 140, 250, 20, Color( "No, I do not wish to fight.", BlackColor32 ), false, false ); - AddHtml( 60, 140-1, 250, 20, Color( "No, I do not wish to fight.", BlackColor32 ), false, false ); - AddHtml( 60, 140+1, 250, 20, Color( "No, I do not wish to fight.", BlackColor32 ), false, false ); - AddHtml( 60, 140, 250, 20, Color( "No, I do not wish to fight.", LabelColor32 ), false, false ); + AddButton(314, 173, 247, 248, 1, GumpButtonType.Reply, 0); - AddRadio( 24, 170, 9727, 9730, false, 3 ); - AddHtml( 60-1, 175, 250, 20, Color( "No, knave. Do not ask again.", BlackColor32 ), false, false ); - AddHtml( 60+1, 175, 250, 20, Color( "No, knave. Do not ask again.", BlackColor32 ), false, false ); - AddHtml( 60, 175-1, 250, 20, Color( "No, knave. Do not ask again.", BlackColor32 ), false, false ); - AddHtml( 60, 175+1, 250, 20, Color( "No, knave. Do not ask again.", BlackColor32 ), false, false ); - AddHtml( 60, 175, 250, 20, Color( "No, knave. Do not ask again.", LabelColor32 ), false, false ); + Timer.DelayCall(TimeSpan.FromSeconds(15.0), AutoReject); + } - AddButton( 314, 173, 247, 248, 1, GumpButtonType.Reply, 0 ); + public string Center(string text) + { + return $"
{text}
"; + } - Timer.DelayCall( TimeSpan.FromSeconds( 15.0 ), AutoReject ); - } + public string Color(string text, int color) + { + return $"{text}"; + } - public void AutoReject() - { - if ( !m_Active ) - return; + public void AutoReject() + { + if (!m_Active) + return; - m_Active = false; + m_Active = false; - m_Challenged.CloseGump( typeof( AcceptDuelGump ) ); + m_Challenged.CloseGump(typeof(AcceptDuelGump)); - m_Challenger.SendMessage( "{0} seems unresponsive.", m_Challenged.Name ); - m_Challenged.SendMessage( "You decline the challenge." ); - } + m_Challenger.SendMessage("{0} seems unresponsive.", m_Challenged.Name); + m_Challenged.SendMessage("You decline the challenge."); + } - private static Hashtable m_IgnoreLists = new Hashtable(); + public static void BeginIgnore(Mobile source, Mobile toIgnore) + { + ArrayList list = (ArrayList)m_IgnoreLists[source]; - private class IgnoreEntry - { - public Mobile m_Ignored; - public DateTime m_Expire; + if (list == null) + m_IgnoreLists[source] = list = new ArrayList(); - public Mobile Ignored => m_Ignored; - public bool Expired => ( DateTime.UtcNow >= m_Expire ); + for (int i = 0; i < list.Count; ++i) + { + IgnoreEntry ie = (IgnoreEntry)list[i]; - private static TimeSpan ExpireDelay = TimeSpan.FromMinutes( 15.0 ); + if (ie.Ignored == toIgnore) + { + ie.Refresh(); + return; + } - public void Refresh() - { - m_Expire = DateTime.UtcNow + ExpireDelay; - } + if (ie.Expired) list.RemoveAt(i--); + } - public IgnoreEntry( Mobile ignored ) - { - m_Ignored = ignored; - Refresh(); - } - } + list.Add(new IgnoreEntry(toIgnore)); + } - public static void BeginIgnore( Mobile source, Mobile toIgnore ) - { - ArrayList list = (ArrayList)m_IgnoreLists[source]; + public static bool IsIgnored(Mobile source, Mobile check) + { + ArrayList list = (ArrayList)m_IgnoreLists[source]; - if ( list == null ) - m_IgnoreLists[source] = list = new ArrayList(); + if (list == null) + return false; - for ( int i = 0; i < list.Count; ++i ) - { - IgnoreEntry ie = (IgnoreEntry)list[i]; + for (int i = 0; i < list.Count; ++i) + { + IgnoreEntry ie = (IgnoreEntry)list[i]; - if ( ie.Ignored == toIgnore ) - { - ie.Refresh(); - return; - } + if (ie.Expired) + list.RemoveAt(i--); + else if (ie.Ignored == check) + return true; + } - if ( ie.Expired ) - { - list.RemoveAt( i-- ); - } - } + return false; + } - list.Add( new IgnoreEntry( toIgnore ) ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID != 1 || !m_Active || !m_Context.Registered) + return; - public static bool IsIgnored( Mobile source, Mobile check ) - { - ArrayList list = (ArrayList)m_IgnoreLists[source]; + m_Active = false; - if ( list == null ) - return false; + if (!m_Context.Participants.Contains(m_Participant)) + return; - for ( int i = 0; i < list.Count; ++i ) - { - IgnoreEntry ie = (IgnoreEntry)list[i]; + if (info.IsSwitched(1)) + { + if (!(m_Challenged is PlayerMobile pm)) + return; - if ( ie.Expired ) - list.RemoveAt( i-- ); - else if ( ie.Ignored == check ) - return true; - } + if (pm.DuelContext != null) + { + if (pm.DuelContext.Initiator == pm) + pm.SendMessage(0x22, "You have already started a duel."); + else + pm.SendMessage(0x22, "You have already been challenged in a duel."); - return false; - } + m_Challenger.SendMessage("{0} cannot fight because they are already assigned to another duel.", pm.Name); + } + else if (DuelContext.CheckCombat(pm)) + { + pm.SendMessage(0x22, + "You have recently been in combat with another player and must wait before starting a duel."); + m_Challenger.SendMessage( + "{0} cannot fight because they have recently been in combat with another player.", pm.Name); + } + else if (TournamentController.IsActive) + { + pm.SendMessage(0x22, "A tournament is currently active and you may not duel."); + m_Challenger.SendMessage(0x22, "A tournament is currently active and you may not duel."); + } + else + { + bool added = false; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID != 1 || !m_Active || !m_Context.Registered ) - return; + if (m_Slot >= 0 && m_Slot < m_Participant.Players.Length && m_Participant.Players[m_Slot] == null) + { + added = true; + m_Participant.Players[m_Slot] = new DuelPlayer(m_Challenged, m_Participant); + } + else + { + for (int i = 0; i < m_Participant.Players.Length; ++i) + if (m_Participant.Players[i] == null) + { + added = true; + m_Participant.Players[i] = new DuelPlayer(m_Challenged, m_Participant); + break; + } + } - m_Active = false; + if (added) + { + m_Challenger.SendMessage("{0} has accepted the request.", m_Challenged.Name); + m_Challenged.SendMessage("You have accepted the request from {0}.", m_Challenger.Name); - if ( !m_Context.Participants.Contains( m_Participant ) ) - return; + NetState ns = m_Challenger.NetState; - if ( info.IsSwitched( 1 ) ) - { - if ( !(m_Challenged is PlayerMobile pm) ) - return; + if (ns != null) + foreach (Gump g in ns.Gumps) + { + if (g is ParticipantGump pg && pg.Participant == m_Participant) + { + m_Challenger.SendGump(new ParticipantGump(m_Challenger, m_Context, m_Participant)); + break; + } - if ( pm.DuelContext != null ) - { - if ( pm.DuelContext.Initiator == pm ) - pm.SendMessage( 0x22, "You have already started a duel." ); - else - pm.SendMessage( 0x22, "You have already been challenged in a duel." ); + if (g is DuelContextGump dcg && dcg.Context == m_Context) + { + m_Challenger.SendGump(new DuelContextGump(m_Challenger, m_Context)); + break; + } + } + } + else + { + m_Challenger.SendMessage("The participant list was full and so {0} could not join.", + m_Challenged.Name); + m_Challenged.SendMessage( + "The participant list was full and so you could not join the fight {1} {0}.", m_Challenger.Name, + m_Participant.Contains(m_Challenger) ? "with" : "against"); + } + } + } + else + { + if (info.IsSwitched(3)) + BeginIgnore(m_Challenged, m_Challenger); - m_Challenger.SendMessage( "{0} cannot fight because they are already assigned to another duel.", pm.Name ); - } - else if ( DuelContext.CheckCombat( pm ) ) - { - pm.SendMessage( 0x22, "You have recently been in combat with another player and must wait before starting a duel." ); - m_Challenger.SendMessage( "{0} cannot fight because they have recently been in combat with another player.", pm.Name ); - } - else if ( TournamentController.IsActive ) - { - pm.SendMessage( 0x22, "A tournament is currently active and you may not duel." ); - m_Challenger.SendMessage( 0x22, "A tournament is currently active and you may not duel." ); - } - else - { - bool added = false; + m_Challenger.SendMessage("{0} does not wish to fight.", m_Challenged.Name); + m_Challenged.SendMessage("You chose not to fight {1} {0}.", m_Challenger.Name, + m_Participant.Contains(m_Challenger) ? "with" : "against"); + } + } - if ( m_Slot >= 0 && m_Slot < m_Participant.Players.Length && m_Participant.Players[m_Slot] == null ) - { - added = true; - m_Participant.Players[m_Slot] = new DuelPlayer( m_Challenged, m_Participant ); - } - else - { - for ( int i = 0; i < m_Participant.Players.Length; ++i ) - { - if ( m_Participant.Players[i] == null ) - { - added = true; - m_Participant.Players[i] = new DuelPlayer( m_Challenged, m_Participant ); - break; - } - } - } + private class IgnoreEntry + { + private static TimeSpan ExpireDelay = TimeSpan.FromMinutes(15.0); + public DateTime m_Expire; + public Mobile m_Ignored; - if ( added ) - { - m_Challenger.SendMessage( "{0} has accepted the request.", m_Challenged.Name ); - m_Challenged.SendMessage( "You have accepted the request from {0}.", m_Challenger.Name ); + public IgnoreEntry(Mobile ignored) + { + m_Ignored = ignored; + Refresh(); + } - NetState ns = m_Challenger.NetState; + public Mobile Ignored => m_Ignored; + public bool Expired => DateTime.UtcNow >= m_Expire; - if ( ns != null ) - { - foreach ( Gump g in ns.Gumps ) - { - if ( g is ParticipantGump pg && pg.Participant == m_Participant ) - { - m_Challenger.SendGump( new ParticipantGump( m_Challenger, m_Context, m_Participant ) ); - break; - } - if ( g is DuelContextGump dcg && dcg.Context == m_Context ) - { - m_Challenger.SendGump( new DuelContextGump( m_Challenger, m_Context ) ); - break; - } - } - } - } - else - { - m_Challenger.SendMessage( "The participant list was full and so {0} could not join.", m_Challenged.Name ); - m_Challenged.SendMessage( "The participant list was full and so you could not join the fight {1} {0}.", m_Challenger.Name, m_Participant.Contains( m_Challenger ) ? "with" : "against" ); - } - } - } - else - { - if ( info.IsSwitched( 3 ) ) - BeginIgnore( m_Challenged, m_Challenger ); - - m_Challenger.SendMessage( "{0} does not wish to fight.", m_Challenged.Name ); - m_Challenged.SendMessage( "You chose not to fight {1} {0}.", m_Challenger.Name, m_Participant.Contains( m_Challenger ) ? "with" : "against" ); - } - } - } -} + public void Refresh() + { + m_Expire = DateTime.UtcNow + ExpireDelay; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Arena.cs b/Scripts/Engines/ConPVP/Arena.cs index a0dedecf6..f2ec33fff 100644 --- a/Scripts/Engines/ConPVP/Arena.cs +++ b/Scripts/Engines/ConPVP/Arena.cs @@ -1,795 +1,846 @@ using System; using System.Collections.Generic; +using Server.Gumps; using Server.Mobiles; +using Server.Multis; namespace Server.Engines.ConPVP { - public class ArenaController : Item - { - private Arena m_Arena; - - [CommandProperty( AccessLevel.GameMaster )] - public Arena Arena{ get => m_Arena; - set{} } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsPrivate { get; set; } + public class ArenaController : Item + { + private Arena m_Arena; + + [Constructible] + public ArenaController() : base(0x1B7A) + { + Visible = false; + Movable = false; + + m_Arena = new Arena(); + + Instances.Add(this); + } + + public ArenaController(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Arena Arena + { + get => m_Arena; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsPrivate{ get; set; } + + public override string DefaultName => "arena controller"; + + public static List Instances{ get; set; } = new List(); + + public override void OnDelete() + { + base.OnDelete(); + + Instances.Remove(this); + m_Arena.Delete(); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + from.SendGump(new PropertiesGump(from, m_Arena)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + + writer.Write(IsPrivate); + + m_Arena.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + IsPrivate = reader.ReadBool(); + + goto case 0; + } + case 0: + { + m_Arena = new Arena(reader); + break; + } + } + + Instances.Add(this); + } + } + + [PropertyObject] + public class ArenaStartPoints + { + public ArenaStartPoints() : this(new Point3D[8]) + { + } + + public ArenaStartPoints(Point3D[] points) + { + Points = points; + } + + public ArenaStartPoints(GenericReader reader) + { + Points = new Point3D[reader.ReadEncodedInt()]; + + for (int i = 0; i < Points.Length; ++i) + Points[i] = reader.ReadPoint3D(); + } + + public Point3D[] Points{ get; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D EdgeWest + { + get => Points[0]; + set => Points[0] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D EdgeEast + { + get => Points[1]; + set => Points[1] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D EdgeNorth + { + get => Points[2]; + set => Points[2] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D EdgeSouth + { + get => Points[3]; + set => Points[3] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D CornerNW + { + get => Points[4]; + set => Points[4] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D CornerSE + { + get => Points[5]; + set => Points[5] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D CornerSW + { + get => Points[6]; + set => Points[6] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D CornerNE + { + get => Points[7]; + set => Points[7] = value; + } + + public override string ToString() + { + return "..."; + } + + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(Points.Length); + + for (int i = 0; i < Points.Length; ++i) + writer.Write(Points[i]); + } + } + + [PropertyObject] + public class Arena : IComparable + { + private bool m_Active; + private Rectangle2D m_Bounds; + private Map m_Facet; + private Point3D m_GateOut; + + private bool m_IsGuarded; + private string m_Name; + private ArenaStartPoints m_Points; + + private SafeZone m_Region; + + private TournamentController m_Tournament; + private Rectangle2D m_Zone; + + public Arena() + { + m_Points = new ArenaStartPoints(); + Players = new List(); + } + + public Arena(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 7: + { + m_IsGuarded = reader.ReadBool(); + + goto case 6; + } + case 6: + { + Ladder = reader.ReadItem() as LadderController; + + goto case 5; + } + case 5: + { + m_Tournament = reader.ReadItem() as TournamentController; + Announcer = reader.ReadMobile(); + + goto case 4; + } + case 4: + { + m_Name = reader.ReadString(); + + goto case 3; + } + case 3: + { + m_Zone = reader.ReadRect2D(); + + goto case 2; + } + case 2: + { + GateIn = reader.ReadPoint3D(); + m_GateOut = reader.ReadPoint3D(); + Teleporter = reader.ReadItem(); + + goto case 1; + } + case 1: + { + Players = reader.ReadStrongMobileList(); + + goto case 0; + } + case 0: + { + m_Facet = reader.ReadMap(); + m_Bounds = reader.ReadRect2D(); + Outside = reader.ReadPoint3D(); + Wall = reader.ReadPoint3D(); + + if (version == 0) + { + reader.ReadBool(); + Players = new List(); + } + + m_Active = reader.ReadBool(); + m_Points = new ArenaStartPoints(reader); + + if (m_Active) + { + Arenas.Add(this); + Arenas.Sort(); + } + + break; + } + } + + if (m_Zone.Start != Point2D.Zero && m_Zone.End != Point2D.Zero && m_Facet != null) + m_Region = new SafeZone(m_Zone, Outside, m_Facet, m_IsGuarded); + + if (IsOccupied) + Timer.DelayCall(TimeSpan.FromSeconds(2.0), Evict); + + if (m_Tournament != null) + Timer.DelayCall(TimeSpan.Zero, AttachToTournament_Sandbox); + } + + [CommandProperty(AccessLevel.GameMaster)] + public LadderController Ladder{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsGuarded + { + get => m_IsGuarded; + set + { + m_IsGuarded = value; + + if (m_Region != null) + m_Region.Disabled = !m_IsGuarded; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TournamentController Tournament + { + get => m_Tournament; + set + { + m_Tournament?.Tournament.Arenas.Remove(this); + + m_Tournament = value; + + m_Tournament?.Tournament.Arenas.Add(this); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Announcer{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string Name + { + get => m_Name; + set + { + m_Name = value; + if (m_Active) Arenas.Sort(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Map Facet + { + get => m_Facet; + set + { + m_Facet = value; + + if (Teleporter != null) + Teleporter.Map = value; + + m_Region?.Unregister(); + + if (m_Zone.Start != Point2D.Zero && m_Zone.End != Point2D.Zero && m_Facet != null) + m_Region = new SafeZone(m_Zone, Outside, m_Facet, m_IsGuarded); + else + m_Region = null; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Rectangle2D Bounds + { + get => m_Bounds; + set => m_Bounds = value; + } + + public int Spectators + { + get + { + if (m_Region == null) + return 0; + + int specs = m_Region.GetPlayerCount() - Players.Count; + + if (specs < 0) + specs = 0; + + return specs; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Rectangle2D Zone + { + get => m_Zone; + set + { + m_Zone = value; + + if (m_Zone.Start != Point2D.Zero && m_Zone.End != Point2D.Zero && m_Facet != null) + { + m_Region?.Unregister(); + + m_Region = new SafeZone(m_Zone, Outside, m_Facet, m_IsGuarded); + } + else + { + m_Region?.Unregister(); + + m_Region = null; + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Outside{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D GateIn{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D GateOut + { + get => m_GateOut; + set + { + m_GateOut = value; + if (Teleporter != null) Teleporter.Location = m_GateOut; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Wall{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsOccupied => Players.Count > 0; + + [CommandProperty(AccessLevel.GameMaster)] + public ArenaStartPoints Points + { + get => m_Points; + set { } + } + + public Item Teleporter{ get; set; } + + public List Players{ get; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Active + { + get => m_Active; + set + { + if (m_Active == value) + return; + + m_Active = value; + + if (m_Active) + { + Arenas.Add(this); + Arenas.Sort(); + } + else + { + Arenas.Remove(this); + } + } + } + + [CommandProperty(AccessLevel.Administrator, AccessLevel.Administrator)] + public bool ForceEvict + { + get => false; + set + { + if (value) Evict(); + } + } + + public static List Arenas{ get; } = new List(); + + public int CompareTo(object obj) + { + Arena c = (Arena)obj; + + string a = m_Name; + string b = c.m_Name; + + if (a == null && b == null) + return 0; + if (a == null) + return -1; + if (b == null) + return +1; + + return a.CompareTo(b); + } + + public Ladder AcquireLadder() + { + if (Ladder != null) + return Ladder.Ladder; + + return ConPVP.Ladder.Instance; + } + + public void Delete() + { + Active = false; + + m_Region?.Unregister(); + + m_Region = null; + } + + public override string ToString() + { + return "..."; + } + + public Point3D GetBaseStartPoint(int index) + { + if (index < 0) + index = 0; + + return m_Points.Points[index % m_Points.Points.Length]; + } + + public void MoveInside(DuelPlayer[] players, int index) + { + if (index < 0) + index = 0; + else + index %= m_Points.Points.Length; + + Point3D start = GetBaseStartPoint(index); + + int offset = 0; + + Point2D[] offsets = index < 4 ? m_EdgeOffsets : m_CornerOffsets; + int[,] matrix = m_Rotate[index]; + + for (int i = 0; i < players.Length; ++i) + { + DuelPlayer pl = players[i]; + + if (pl == null) + continue; + + Mobile mob = pl.Mobile; + + Point2D p; + + if (offset < offsets.Length) + p = offsets[offset++]; + else + p = offsets[offsets.Length - 1]; + + p.X = p.X * matrix[0, 0] + p.Y * matrix[0, 1]; + p.Y = p.X * matrix[1, 0] + p.Y * matrix[1, 1]; + + mob.MoveToWorld(new Point3D(start.X + p.X, start.Y + p.Y, start.Z), m_Facet); + mob.Direction = mob.GetDirectionTo(Wall); + + Players.Add(mob); + } + } - public override string DefaultName => "arena controller"; - - [Constructible] - public ArenaController() : base( 0x1B7A ) - { - Visible = false; - Movable = false; - - m_Arena = new Arena(); - - Instances.Add( this ); - } - - public override void OnDelete() - { - base.OnDelete(); - - Instances.Remove( this ); - m_Arena.Delete(); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - from.SendGump( new Gumps.PropertiesGump( from, m_Arena ) ); - } - - public ArenaController( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); - - writer.Write( (bool) IsPrivate ); - - m_Arena.Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - IsPrivate = reader.ReadBool(); - - goto case 0; - } - case 0: - { - m_Arena = new Arena( reader ); - break; - } - } - - Instances.Add( this ); - } - - public static List Instances { get; set; } = new List(); - } - - [PropertyObject] - public class ArenaStartPoints - { - public Point3D[] Points { get; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D EdgeWest{ get => Points[0]; - set => Points[0] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D EdgeEast{ get => Points[1]; - set => Points[1] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D EdgeNorth{ get => Points[2]; - set => Points[2] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D EdgeSouth{ get => Points[3]; - set => Points[3] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D CornerNW{ get => Points[4]; - set => Points[4] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D CornerSE{ get => Points[5]; - set => Points[5] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D CornerSW{ get => Points[6]; - set => Points[6] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D CornerNE{ get => Points[7]; - set => Points[7] = value; - } - - public override string ToString() - { - return "..."; - } - - public ArenaStartPoints() : this( new Point3D[8] ) - { - } - - public ArenaStartPoints( Point3D[] points ) - { - Points = points; - } - - public ArenaStartPoints( GenericReader reader ) - { - Points = new Point3D[reader.ReadEncodedInt()]; - - for ( int i = 0; i < Points.Length; ++i ) - Points[i] = reader.ReadPoint3D(); - } - - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) Points.Length ); - - for ( int i = 0; i < Points.Length; ++i ) - writer.Write( (Point3D) Points[i] ); - } - } - - [PropertyObject] - public class Arena : IComparable - { - private Map m_Facet; - private Rectangle2D m_Bounds; - private Rectangle2D m_Zone; - private Point3D m_GateOut; - private ArenaStartPoints m_Points; - private bool m_Active; - private string m_Name; - - private bool m_IsGuarded; - - private TournamentController m_Tournament; - - [CommandProperty( AccessLevel.GameMaster )] - public LadderController Ladder { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsGuarded - { - get => m_IsGuarded; - set - { - m_IsGuarded = value; - - if ( m_Region != null ) - m_Region.Disabled = !m_IsGuarded; - } - } - - public Ladder AcquireLadder() - { - if ( Ladder != null ) - return Ladder.Ladder; - - return Server.Engines.ConPVP.Ladder.Instance; - } - - [CommandProperty( AccessLevel.GameMaster )] - public TournamentController Tournament - { - get => m_Tournament; - set - { - m_Tournament?.Tournament.Arenas.Remove( this ); - - m_Tournament = value; - - m_Tournament?.Tournament.Arenas.Add( this ); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Announcer { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string Name - { - get => m_Name; - set{ m_Name = value; if ( m_Active ) Arenas.Sort(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Map Facet - { - get => m_Facet; - set - { - m_Facet = value; - - if ( Teleporter != null ) - Teleporter.Map = value; - - m_Region?.Unregister(); - - if ( m_Zone.Start != Point2D.Zero && m_Zone.End != Point2D.Zero && m_Facet != null ) - m_Region = new SafeZone( m_Zone, Outside, m_Facet, m_IsGuarded ); - else - m_Region = null; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Rectangle2D Bounds{ get => m_Bounds; - set => m_Bounds = value; - } - - private SafeZone m_Region; - - public int Spectators - { - get - { - if ( m_Region == null ) - return 0; - - int specs = m_Region.GetPlayerCount() - Players.Count; - - if ( specs < 0 ) - specs = 0; - - return specs; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Rectangle2D Zone - { - get => m_Zone; - set - { - m_Zone = value; - - if ( m_Zone.Start != Point2D.Zero && m_Zone.End != Point2D.Zero && m_Facet != null ) - { - m_Region?.Unregister(); - - m_Region = new SafeZone( m_Zone, Outside, m_Facet, m_IsGuarded ); - } - else - { - m_Region?.Unregister(); - - m_Region = null; - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Outside { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D GateIn { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D GateOut{ get => m_GateOut; - set{ m_GateOut = value; if ( Teleporter != null ) Teleporter.Location = m_GateOut; } } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Wall { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsOccupied => ( Players.Count > 0 ); - - [CommandProperty( AccessLevel.GameMaster )] - public ArenaStartPoints Points{ get => m_Points; - set{} } - - public Item Teleporter { get; set; } - - public List Players { get; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Active - { - get => m_Active; - set - { - if ( m_Active == value ) - return; - - m_Active = value; - - if ( m_Active ) - { - Arenas.Add( this ); - Arenas.Sort(); - } - else - { - Arenas.Remove( this ); - } - } - } - - public void Delete() - { - Active = false; - - m_Region?.Unregister(); - - m_Region = null; - } - - public override string ToString() - { - return "..."; - } - - public Point3D GetBaseStartPoint( int index ) - { - if ( index < 0 ) - index = 0; - - return m_Points.Points[index % m_Points.Points.Length]; - } - - #region Offsets & Rotation - private static Point2D[] m_EdgeOffsets = { - /* - * /\ - * /\/\ - * /\/\/\ - * \/\/\/ - * \/\/\ - * \/\/ - */ - new Point2D( 0, 0 ), - new Point2D( 0, -1 ), - new Point2D( 0, +1 ), - new Point2D( 1, 0 ), - new Point2D( 1, -1 ), - new Point2D( 1, +1 ), - new Point2D( 2, 0 ), - new Point2D( 2, -1 ), - new Point2D( 2, +1 ), - new Point2D( 3, 0 ) - }; - - // nw corner - private static Point2D[] m_CornerOffsets = { - /* - * /\ - * /\/\ - * /\/\/\ - * /\/\/\/\ - * \/\/\/\/ - */ - new Point2D( 0, 0 ), - new Point2D( 0, 1 ), - new Point2D( 1, 0 ), - new Point2D( 1, 1 ), - new Point2D( 0, 2 ), - new Point2D( 2, 0 ), - new Point2D( 2, 1 ), - new Point2D( 1, 2 ), - new Point2D( 0, 3 ), - new Point2D( 3, 0 ) - }; - - private static int[][,] m_Rotate = { - new[,]{ { +1, 0 }, { 0, +1 } }, // west - new[,]{ { -1, 0 }, { 0, -1 } }, // east - new[,]{ { 0, +1 }, { +1, 0 } }, // north - new[,]{ { 0, -1 }, { -1, 0 } }, // south - new[,]{ { +1, 0 }, { 0, +1 } }, // nw - new[,]{ { -1, 0 }, { 0, -1 } }, // se - new[,]{ { 0, +1 }, { +1, 0 } }, // sw - new[,]{ { 0, -1 }, { -1, 0 } }, // ne - }; - #endregion - - public void MoveInside( DuelPlayer[] players, int index ) - { - if ( index < 0 ) - index = 0; - else - index %= m_Points.Points.Length; - - Point3D start = GetBaseStartPoint( index ); - - int offset = 0; - - Point2D[] offsets = ( index < 4 ) ? m_EdgeOffsets : m_CornerOffsets; - int[,] matrix = m_Rotate[index]; - - for ( int i = 0; i < players.Length; ++i ) - { - DuelPlayer pl = players[i]; - - if ( pl == null ) - continue; - - Mobile mob = pl.Mobile; - - Point2D p; - - if ( offset < offsets.Length ) - p = offsets[offset++]; - else - p = offsets[offsets.Length - 1]; - - p.X = (p.X * matrix[0, 0]) + (p.Y * matrix[0, 1]); - p.Y = (p.X * matrix[1, 0]) + (p.Y * matrix[1, 1]); - - mob.MoveToWorld( new Point3D( start.X + p.X, start.Y + p.Y, start.Z ), m_Facet ); - mob.Direction = mob.GetDirectionTo( Wall ); - - Players.Add( mob ); - } - } - - public Arena() - { - m_Points = new ArenaStartPoints(); - Players = new List(); - } - - public Arena( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 7: - { - m_IsGuarded = reader.ReadBool(); - - goto case 6; - } - case 6: - { - Ladder = reader.ReadItem() as LadderController; - - goto case 5; - } - case 5: - { - m_Tournament = reader.ReadItem() as TournamentController; - Announcer = reader.ReadMobile(); - - goto case 4; - } - case 4: - { - m_Name = reader.ReadString(); - - goto case 3; - } - case 3: - { - m_Zone = reader.ReadRect2D(); - - goto case 2; - } - case 2: - { - GateIn = reader.ReadPoint3D(); - m_GateOut = reader.ReadPoint3D(); - Teleporter = reader.ReadItem(); - - goto case 1; - } - case 1: - { - Players = reader.ReadStrongMobileList(); - - goto case 0; - } - case 0: - { - m_Facet = reader.ReadMap(); - m_Bounds = reader.ReadRect2D(); - Outside = reader.ReadPoint3D(); - Wall = reader.ReadPoint3D(); - - if ( version == 0 ) - { - reader.ReadBool(); - Players = new List(); - } - - m_Active = reader.ReadBool(); - m_Points = new ArenaStartPoints( reader ); - - if ( m_Active ) - { - Arenas.Add( this ); - Arenas.Sort(); - } - - break; - } - } - - if ( m_Zone.Start != Point2D.Zero && m_Zone.End != Point2D.Zero && m_Facet != null ) - m_Region = new SafeZone( m_Zone, Outside, m_Facet, m_IsGuarded ); - - if ( IsOccupied ) - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), Evict ); - - if ( m_Tournament != null ) - Timer.DelayCall( TimeSpan.Zero, AttachToTournament_Sandbox ); - } - - private void AttachToTournament_Sandbox() - { - m_Tournament?.Tournament.Arenas.Add( this ); - } - - [CommandProperty( AccessLevel.Administrator, AccessLevel.Administrator )] - public bool ForceEvict{ get => false; - set{ if ( value ) Evict(); } } - - public void Evict() - { - Point3D loc; - Map facet; - - if ( m_Facet == null ) - { - loc = new Point3D( 2715, 2165, 0 ); - facet = Map.Felucca; - } - else - { - loc = Outside; - facet = m_Facet; - } - - bool hasBounds = ( m_Bounds.Start != Point2D.Zero && m_Bounds.End != Point2D.Zero ); - - for ( int i = 0; i < Players.Count; ++i ) - { - Mobile mob = Players[i]; - - if ( mob == null ) - continue; - - if ( mob.Map == Map.Internal ) - { - if ( (m_Facet == null || mob.LogoutMap == m_Facet) && (!hasBounds || m_Bounds.Contains( mob.LogoutLocation )) ) - mob.LogoutLocation = loc; - } - else if ( (m_Facet == null || mob.Map == m_Facet) && (!hasBounds || m_Bounds.Contains( mob.Location )) ) - { - mob.MoveToWorld( loc, facet ); - } - - mob.Combatant = null; - mob.Frozen = false; - DuelContext.Debuff( mob ); - DuelContext.CancelSpell( mob ); - } - - if ( hasBounds ) { - List pets = new List(); - - foreach ( Mobile mob in facet.GetMobilesInBounds( m_Bounds ) ) { - if ( mob is BaseCreature pet && pet.Controlled && pet.ControlMaster != null && Players.Contains( pet.ControlMaster ) ) { - pets.Add( pet ); - } - } - - foreach ( Mobile pet in pets ) { - pet.Combatant = null; - pet.Frozen = false; - - pet.MoveToWorld( loc, facet ); - } - } - - Players.Clear(); - } + private void AttachToTournament_Sandbox() + { + m_Tournament?.Tournament.Arenas.Add(this); + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 7 ); + public void Evict() + { + Point3D loc; + Map facet; - writer.Write( (bool) m_IsGuarded ); + if (m_Facet == null) + { + loc = new Point3D(2715, 2165, 0); + facet = Map.Felucca; + } + else + { + loc = Outside; + facet = m_Facet; + } - writer.Write( (Item) Ladder ); - - writer.Write( (Item) m_Tournament ); - writer.Write( (Mobile) Announcer ); - - writer.Write( (string) m_Name ); + bool hasBounds = m_Bounds.Start != Point2D.Zero && m_Bounds.End != Point2D.Zero; - writer.Write( (Rectangle2D) m_Zone ); + for (int i = 0; i < Players.Count; ++i) + { + Mobile mob = Players[i]; - writer.Write( (Point3D) GateIn ); - writer.Write( (Point3D) m_GateOut ); - writer.Write( (Item) Teleporter ); + if (mob == null) + continue; - writer.Write( Players ); + if (mob.Map == Map.Internal) + { + if ((m_Facet == null || mob.LogoutMap == m_Facet) && + (!hasBounds || m_Bounds.Contains(mob.LogoutLocation))) + mob.LogoutLocation = loc; + } + else if ((m_Facet == null || mob.Map == m_Facet) && (!hasBounds || m_Bounds.Contains(mob.Location))) + { + mob.MoveToWorld(loc, facet); + } - writer.Write( (Map) m_Facet ); - writer.Write( (Rectangle2D) m_Bounds ); - writer.Write( (Point3D) Outside ); - writer.Write( (Point3D) Wall ); - writer.Write( (bool) m_Active ); + mob.Combatant = null; + mob.Frozen = false; + DuelContext.Debuff(mob); + DuelContext.CancelSpell(mob); + } - m_Points.Serialize( writer ); - } + if (hasBounds) + { + List pets = new List(); - public static List Arenas { get; } = new List(); + foreach (Mobile mob in facet.GetMobilesInBounds(m_Bounds)) + if (mob is BaseCreature pet && pet.Controlled && pet.ControlMaster != null && + Players.Contains(pet.ControlMaster)) + pets.Add(pet); - public static Arena FindArena( List players ) - { - Preferences prefs = Preferences.Instance; + foreach (Mobile pet in pets) + { + pet.Combatant = null; + pet.Frozen = false; - if ( prefs == null ) - return FindArena(); + pet.MoveToWorld(loc, facet); + } + } - if ( Arenas.Count == 0 ) - return null; + Players.Clear(); + } - if ( players.Count > 0 ) - { - Mobile first = players[0]; + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(7); - List allControllers = ArenaController.Instances; + writer.Write(m_IsGuarded); - for ( int i = 0; i < allControllers.Count; ++i ) - { - ArenaController controller = allControllers[i]; + writer.Write(Ladder); - if ( controller != null && !controller.Deleted && controller.Arena != null && controller.IsPrivate && controller.Map == first.Map && first.InRange( controller, 24 ) ) - { - Multis.BaseHouse house = Multis.BaseHouse.FindHouseAt( controller ); - bool allNear = true; + writer.Write(m_Tournament); + writer.Write(Announcer); - for ( int j = 0; j < players.Count; ++j ) - { - Mobile check = players[j]; - bool isNear; + writer.Write(m_Name); - if ( house == null ) - isNear = ( controller.Map == check.Map && check.InRange( controller, 24 ) ); - else - isNear = ( Multis.BaseHouse.FindHouseAt( check ) == house ); + writer.Write(m_Zone); - if ( !isNear ) - { - allNear = false; - break; - } - } + writer.Write(GateIn); + writer.Write(m_GateOut); + writer.Write(Teleporter); + + writer.Write(Players); - if ( allNear ) - return controller.Arena; - } - } - } + writer.Write(m_Facet); + writer.Write(m_Bounds); + writer.Write(Outside); + writer.Write(Wall); + writer.Write(m_Active); - List arenas = new List(); + m_Points.Serialize(writer); + } + + public static Arena FindArena(List players) + { + Preferences prefs = Preferences.Instance; - for ( int i = 0; i < Arenas.Count; ++i ) - { - Arena arena = Arenas[i]; + if (prefs == null) + return FindArena(); - if ( !arena.IsOccupied ) - arenas.Add( new ArenaEntry( arena ) ); - } + if (Arenas.Count == 0) + return null; - if ( arenas.Count == 0 ) - return Arenas[0]; + if (players.Count > 0) + { + Mobile first = players[0]; - int tc = 0; + List allControllers = ArenaController.Instances; - for ( int i = 0; i < arenas.Count; ++i ) - { - ArenaEntry ae = arenas[i]; + for (int i = 0; i < allControllers.Count; ++i) + { + ArenaController controller = allControllers[i]; - for ( int j = 0; j < players.Count; ++j ) - { - PreferencesEntry pe = prefs.Find( players[j] ); + if (controller != null && !controller.Deleted && controller.Arena != null && controller.IsPrivate && + controller.Map == first.Map && first.InRange(controller, 24)) + { + BaseHouse house = BaseHouse.FindHouseAt(controller); + bool allNear = true; - if ( pe.Disliked.Contains( ae.m_Arena.Name ) ) - ++ae.m_VotesAgainst; - else - ++ae.m_VotesFor; - } + for (int j = 0; j < players.Count; ++j) + { + Mobile check = players[j]; + bool isNear; - tc += ae.Value; - } + if (house == null) + isNear = controller.Map == check.Map && check.InRange(controller, 24); + else + isNear = BaseHouse.FindHouseAt(check) == house; - int rn = Utility.Random( tc ); + if (!isNear) + { + allNear = false; + break; + } + } - for ( int i = 0; i < arenas.Count; ++i ) - { - ArenaEntry ae = arenas[i]; + if (allNear) + return controller.Arena; + } + } + } - if ( rn < ae.Value ) - return ae.m_Arena; - - rn -= ae.Value; - } - - return arenas[Utility.Random( arenas.Count )].m_Arena; - } - - private class ArenaEntry - { - public Arena m_Arena; - public int m_VotesFor; - public int m_VotesAgainst; - - public int Value => m_VotesFor; - - public ArenaEntry( Arena arena ) - { - m_Arena = arena; - } - } - - public static Arena FindArena() - { - if ( Arenas.Count == 0 ) - return null; - - int offset = Utility.Random( Arenas.Count ); - - for ( int i = 0; i < Arenas.Count; ++i ) - { - Arena arena = Arenas[(i + offset) % Arenas.Count]; - - if ( !arena.IsOccupied ) - return arena; - } - - return Arenas[offset]; - } - - public int CompareTo(object obj) - { - Arena c = (Arena)obj; - - string a = m_Name; - string b = c.m_Name; - - if ( a == null && b == null ) - return 0; - if ( a == null ) - return -1; - if ( b == null ) - return +1; - - return a.CompareTo( b ); - } - } -} + List arenas = new List(); + + for (int i = 0; i < Arenas.Count; ++i) + { + Arena arena = Arenas[i]; + + if (!arena.IsOccupied) + arenas.Add(new ArenaEntry(arena)); + } + + if (arenas.Count == 0) + return Arenas[0]; + + int tc = 0; + + for (int i = 0; i < arenas.Count; ++i) + { + ArenaEntry ae = arenas[i]; + + for (int j = 0; j < players.Count; ++j) + { + PreferencesEntry pe = prefs.Find(players[j]); + + if (pe.Disliked.Contains(ae.m_Arena.Name)) + ++ae.m_VotesAgainst; + else + ++ae.m_VotesFor; + } + + tc += ae.Value; + } + + int rn = Utility.Random(tc); + + for (int i = 0; i < arenas.Count; ++i) + { + ArenaEntry ae = arenas[i]; + + if (rn < ae.Value) + return ae.m_Arena; + + rn -= ae.Value; + } + + return arenas[Utility.Random(arenas.Count)].m_Arena; + } + + public static Arena FindArena() + { + if (Arenas.Count == 0) + return null; + + int offset = Utility.Random(Arenas.Count); + + for (int i = 0; i < Arenas.Count; ++i) + { + Arena arena = Arenas[(i + offset) % Arenas.Count]; + + if (!arena.IsOccupied) + return arena; + } + + return Arenas[offset]; + } + + private class ArenaEntry + { + public Arena m_Arena; + public int m_VotesAgainst; + public int m_VotesFor; + + public ArenaEntry(Arena arena) + { + m_Arena = arena; + } + + public int Value => m_VotesFor; + } + + #region Offsets & Rotation + + private static Point2D[] m_EdgeOffsets = + { + /* + * /\ + * /\/\ + * /\/\/\ + * \/\/\/ + * \/\/\ + * \/\/ + */ + new Point2D(0, 0), + new Point2D(0, -1), + new Point2D(0, +1), + new Point2D(1, 0), + new Point2D(1, -1), + new Point2D(1, +1), + new Point2D(2, 0), + new Point2D(2, -1), + new Point2D(2, +1), + new Point2D(3, 0) + }; + + // nw corner + private static Point2D[] m_CornerOffsets = + { + /* + * /\ + * /\/\ + * /\/\/\ + * /\/\/\/\ + * \/\/\/\/ + */ + new Point2D(0, 0), + new Point2D(0, 1), + new Point2D(1, 0), + new Point2D(1, 1), + new Point2D(0, 2), + new Point2D(2, 0), + new Point2D(2, 1), + new Point2D(1, 2), + new Point2D(0, 3), + new Point2D(3, 0) + }; + + private static int[][,] m_Rotate = + { + new[,] { { +1, 0 }, { 0, +1 } }, // west + new[,] { { -1, 0 }, { 0, -1 } }, // east + new[,] { { 0, +1 }, { +1, 0 } }, // north + new[,] { { 0, -1 }, { -1, 0 } }, // south + new[,] { { +1, 0 }, { 0, +1 } }, // nw + new[,] { { -1, 0 }, { 0, -1 } }, // se + new[,] { { 0, +1 }, { +1, 0 } }, // sw + new[,] { { 0, -1 }, { -1, 0 } } // ne + }; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/ArenaGump.cs b/Scripts/Engines/ConPVP/ArenaGump.cs index 77b6b97e3..d9161a52b 100644 --- a/Scripts/Engines/ConPVP/ArenaGump.cs +++ b/Scripts/Engines/ConPVP/ArenaGump.cs @@ -1,289 +1,290 @@ -using System; -using System.Text; using System.Collections.Generic; +using System.Text; using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Engines.ConPVP { - public class ArenasMoongate : Item - { - public override string DefaultName => "arena moongate"; + public class ArenasMoongate : Item + { + [Constructible] + public ArenasMoongate() : base(0x1FD4) + { + Movable = false; + Light = LightType.Circle300; + } - [Constructible] - public ArenasMoongate() : base( 0x1FD4 ) - { - Movable = false; - Light = LightType.Circle300; - } + public ArenasMoongate(Serial serial) : base(serial) + { + } - public ArenasMoongate( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "arena moongate"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - Light = LightType.Circle300; - } + int version = reader.ReadInt(); + Light = LightType.Circle300; + } - public bool UseGate( Mobile from ) - { - if ( DuelContext.CheckCombat( from ) ) - { - from.SendMessage( 0x22, "You have recently been in combat with another player and cannot use this moongate." ); - return false; - } + public bool UseGate(Mobile from) + { + if (DuelContext.CheckCombat(from)) + { + from.SendMessage(0x22, "You have recently been in combat with another player and cannot use this moongate."); + return false; + } - if ( from.Spell != null ) - { - from.SendLocalizedMessage( 1049616 ); // You are too busy to do that at the moment. - return false; - } - from.CloseGump( typeof( ArenaGump ) ); - from.SendGump( new ArenaGump( from, this ) ); + if (from.Spell != null) + { + from.SendLocalizedMessage(1049616); // You are too busy to do that at the moment. + return false; + } - if ( !from.Hidden || from.AccessLevel == AccessLevel.Player ) - Effects.PlaySound( from.Location, from.Map, 0x20E ); + from.CloseGump(typeof(ArenaGump)); + from.SendGump(new ArenaGump(from, this)); - return true; - } + if (!from.Hidden || from.AccessLevel == AccessLevel.Player) + Effects.PlaySound(from.Location, from.Map, 0x20E); - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - UseGate( from ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that - } + return true; + } - public override bool OnMoveOver( Mobile m ) - { - return ( !m.Player || UseGate( m ) ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 1)) + UseGate(from); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that + } - public class ArenaGump : Gump - { - private Mobile m_From; - private ArenasMoongate m_Gate; - private List m_Arenas; + public override bool OnMoveOver(Mobile m) + { + return !m.Player || UseGate(m); + } + } - private void Append( StringBuilder sb, LadderEntry le ) - { - if ( le == null ) - return; + public class ArenaGump : Gump + { + private List m_Arenas; - if ( sb.Length > 0 ) - sb.Append( ", " ); + private int m_ColumnX = 12; + private Mobile m_From; + private ArenasMoongate m_Gate; - sb.Append( le.Mobile.Name ); - } + public ArenaGump(Mobile from, ArenasMoongate gate) : base(50, 50) + { + m_From = from; + m_Gate = gate; + m_Arenas = Arena.Arenas; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID != 1 ) - return; + AddPage(0); - int[] switches = info.Switches; + int height = 12 + 20 + m_Arenas.Count * 31 + 24 + 12; - if ( switches.Length == 0 ) - return; + AddBackground(0, 0, 499 + 40, height, 0x2436); - int opt = switches[0]; + List list = m_Arenas; - if ( opt < 0 || opt >= m_Arenas.Count ) - return; + for (int i = 1; i < list.Count; i += 2) + AddImageTiled(12, 32 + i * 31, 475 + 40, 30, 0x2430); - Arena arena = m_Arenas[opt]; + AddAlphaRegion(10, 10, 479 + 40, height - 20); - if ( !m_From.InRange( m_Gate.GetWorldLocation(), 1 ) || m_From.Map != m_Gate.Map ) - { - m_From.SendLocalizedMessage( 1019002 ); // You are too far away to use the gate. - } - else if ( DuelContext.CheckCombat( m_From ) ) - { - m_From.SendMessage( 0x22, "You have recently been in combat with another player and cannot use this moongate." ); - } - else if ( m_From.Spell != null ) - { - m_From.SendLocalizedMessage( 1049616 ); // You are too busy to do that at the moment. - } - else if ( m_From.Map == arena.Facet && arena.Zone.Contains( m_From ) ) - { - m_From.SendLocalizedMessage( 1019003 ); // You are already there. - } - else - { - BaseCreature.TeleportPets( m_From, arena.GateIn, arena.Facet ); + AddColumnHeader(35, null); + AddColumnHeader(115, "Arena"); + AddColumnHeader(325, "Participants"); + AddColumnHeader(40, "Obs"); - m_From.Combatant = null; - m_From.Warmode = false; - m_From.Hidden = true; + AddButton(499 + 40 - 12 - 63 - 4 - 63, height - 12 - 24, 247, 248, 1, GumpButtonType.Reply, 0); + AddButton(499 + 40 - 12 - 63, height - 12 - 24, 241, 242, 2, GumpButtonType.Reply, 0); - m_From.MoveToWorld( arena.GateIn, arena.Facet ); + for (int i = 0; i < list.Count; ++i) + { + Arena ar = list[i]; - Effects.PlaySound( arena.GateIn, arena.Facet, 0x1FE ); - } - } + string name = ar.Name; - public ArenaGump( Mobile from, ArenasMoongate gate ) : base( 50, 50 ) - { - m_From = from; - m_Gate = gate; - m_Arenas = Arena.Arenas; + if (name == null) + name = "(no name)"; - AddPage( 0 ); + int x = 12; + int y = 32 + i * 31; - int height = 12 + 20 + (m_Arenas.Count * 31) + 24 + 12; + int color = ar.Players.Count > 0 ? 0xCCFFCC : 0xCCCCCC; - AddBackground( 0, 0, 499+40, height, 0x2436 ); + AddRadio(x + 3, y + 1, 9727, 9730, false, i); + x += 35; - List list = m_Arenas; + AddBorderedText(x + 5, y + 5, 115 - 5, name, color, 0); + x += 115; - for ( int i = 1; i < list.Count; i += 2 ) - AddImageTiled( 12, 32 + (i * 31), 475+40, 30, 0x2430 ); + StringBuilder sb = new StringBuilder(); - AddAlphaRegion( 10, 10, 479+40, height - 20 ); + if (ar.Players.Count > 0) + { + Ladder ladder = Ladder.Instance; - AddColumnHeader( 35, null ); - AddColumnHeader( 115, "Arena" ); - AddColumnHeader( 325, "Participants" ); - AddColumnHeader( 40, "Obs" ); + if (ladder == null) + continue; - AddButton( 499+40 - 12 - 63 - 4 - 63, height - 12 - 24, 247, 248, 1, GumpButtonType.Reply, 0 ); - AddButton( 499+40 - 12 - 63, height - 12 - 24, 241, 242, 2, GumpButtonType.Reply, 0 ); + LadderEntry p1 = null, p2 = null, p3 = null, p4 = null; - for ( int i = 0; i < list.Count; ++i ) - { - Arena ar = list[i]; + for (int j = 0; j < ar.Players.Count; ++j) + { + Mobile mob = ar.Players[j]; + LadderEntry c = ladder.Find(mob); - string name = ar.Name; + if (p1 == null || c.Index < p1.Index) + { + p4 = p3; + p3 = p2; + p2 = p1; + p1 = c; + } + else if (p2 == null || c.Index < p2.Index) + { + p4 = p3; + p3 = p2; + p2 = c; + } + else if (p3 == null || c.Index < p3.Index) + { + p4 = p3; + p3 = c; + } + else if (p4 == null || c.Index < p4.Index) + { + p4 = c; + } + } - if ( name == null ) - name = "(no name)"; + Append(sb, p1); + Append(sb, p2); + Append(sb, p3); + Append(sb, p4); - int x = 12; - int y = 32 + (i * 31); + if (ar.Players.Count > 4) + sb.Append(", ..."); + } + else + { + sb.Append("Empty"); + } - int color = ( ar.Players.Count > 0 ? 0xCCFFCC : 0xCCCCCC ); + AddBorderedText(x + 5, y + 5, 325 - 5, sb.ToString(), color, 0); + x += 325; - AddRadio( x + 3, y + 1, 9727, 9730, false, i ); - x += 35; + AddBorderedText(x, y + 5, 40, Center(ar.Spectators.ToString()), color, 0); + } + } - AddBorderedText( x + 5, y + 5, 115 - 5, name, color, 0 ); - x += 115; + private void Append(StringBuilder sb, LadderEntry le) + { + if (le == null) + return; - StringBuilder sb = new StringBuilder(); + if (sb.Length > 0) + sb.Append(", "); - if ( ar.Players.Count > 0 ) - { - Ladder ladder = Ladder.Instance; + sb.Append(le.Mobile.Name); + } - if ( ladder == null ) - continue; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID != 1) + return; - LadderEntry p1 = null, p2 = null, p3 = null, p4 = null; + int[] switches = info.Switches; - for ( int j = 0; j < ar.Players.Count; ++j ) - { - Mobile mob = (Mobile)ar.Players[j]; - LadderEntry c = ladder.Find( mob ); + if (switches.Length == 0) + return; - if ( p1 == null || c.Index < p1.Index ) - { - p4 = p3; - p3 = p2; - p2 = p1; - p1 = c; - } - else if ( p2 == null || c.Index < p2.Index ) - { - p4 = p3; - p3 = p2; - p2 = c; - } - else if ( p3 == null || c.Index < p3.Index ) - { - p4 = p3; - p3 = c; - } - else if ( p4 == null || c.Index < p4.Index ) - { - p4 = c; - } - } + int opt = switches[0]; - Append( sb, p1 ); - Append( sb, p2 ); - Append( sb, p3 ); - Append( sb, p4 ); + if (opt < 0 || opt >= m_Arenas.Count) + return; - if ( ar.Players.Count > 4 ) - sb.Append( ", ..." ); - } - else - { - sb.Append( "Empty" ); - } + Arena arena = m_Arenas[opt]; - AddBorderedText( x + 5, y + 5, 325 - 5, sb.ToString(), color, 0 ); - x += 325; + if (!m_From.InRange(m_Gate.GetWorldLocation(), 1) || m_From.Map != m_Gate.Map) + { + m_From.SendLocalizedMessage(1019002); // You are too far away to use the gate. + } + else if (DuelContext.CheckCombat(m_From)) + { + m_From.SendMessage(0x22, + "You have recently been in combat with another player and cannot use this moongate."); + } + else if (m_From.Spell != null) + { + m_From.SendLocalizedMessage(1049616); // You are too busy to do that at the moment. + } + else if (m_From.Map == arena.Facet && arena.Zone.Contains(m_From)) + { + m_From.SendLocalizedMessage(1019003); // You are already there. + } + else + { + BaseCreature.TeleportPets(m_From, arena.GateIn, arena.Facet); - AddBorderedText( x, y + 5, 40, Center( ar.Spectators.ToString() ), color, 0 ); - } - } + m_From.Combatant = null; + m_From.Warmode = false; + m_From.Hidden = true; - public string Center( string text ) - { - return $"
{text}
"; - } + m_From.MoveToWorld(arena.GateIn, arena.Facet); - public string Color( string text, int color ) - { - return $"{text}"; - } + Effects.PlaySound(arena.GateIn, arena.Facet, 0x1FE); + } + } - private void AddBorderedText( int x, int y, int width, string text, int color, int borderColor ) - { - /*AddColoredText( x - 1, y, width, text, borderColor ); - AddColoredText( x + 1, y, width, text, borderColor ); - AddColoredText( x, y - 1, width, text, borderColor ); - AddColoredText( x, y + 1, width, text, borderColor );*/ - /*AddColoredText( x - 1, y - 1, width, text, borderColor ); - AddColoredText( x + 1, y + 1, width, text, borderColor );*/ - AddColoredText( x, y, width, text, color ); - } + public string Center(string text) + { + return $"
{text}
"; + } - private void AddColoredText( int x, int y, int width, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, 20, text, false, false ); - else - AddHtml( x, y, width, 20, Color( text, color ), false, false ); - } + public string Color(string text, int color) + { + return $"{text}"; + } - private int m_ColumnX = 12; + private void AddBorderedText(int x, int y, int width, string text, int color, int borderColor) + { + /*AddColoredText( x - 1, y, width, text, borderColor ); + AddColoredText( x + 1, y, width, text, borderColor ); + AddColoredText( x, y - 1, width, text, borderColor ); + AddColoredText( x, y + 1, width, text, borderColor );*/ + /*AddColoredText( x - 1, y - 1, width, text, borderColor ); + AddColoredText( x + 1, y + 1, width, text, borderColor );*/ + AddColoredText(x, y, width, text, color); + } - private void AddColumnHeader( int width, string name ) - { - AddBackground( m_ColumnX, 12, width, 20, 0x242C ); - AddImageTiled( m_ColumnX + 2, 14, width - 4, 16, 0x2430 ); + private void AddColoredText(int x, int y, int width, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, 20, text, false, false); + else + AddHtml(x, y, width, 20, Color(text, color), false, false); + } - if ( name != null ) - AddBorderedText( m_ColumnX, 13, width, Center( name ), 0xFFFFFF, 0 ); + private void AddColumnHeader(int width, string name) + { + AddBackground(m_ColumnX, 12, width, 20, 0x242C); + AddImageTiled(m_ColumnX + 2, 14, width - 4, 16, 0x2430); - m_ColumnX += width; - } - } -} + if (name != null) + AddBorderedText(m_ColumnX, 13, width, Center(name), 0xFFFFFF, 0); + + m_ColumnX += width; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/BeginGump.cs b/Scripts/Engines/ConPVP/BeginGump.cs index 3143afa22..6e02ae089 100644 --- a/Scripts/Engines/ConPVP/BeginGump.cs +++ b/Scripts/Engines/ConPVP/BeginGump.cs @@ -1,58 +1,72 @@ -using System; using Server.Gumps; namespace Server.Engines.ConPVP { - public class BeginGump : Gump - { - public string Center( string text ) - { - return $"
{text}
"; - } + public class BeginGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int BlackColor32 = 0x000008; - public string Color( string text, int color ) - { - return $"{text}"; - } + public BeginGump(int count) : base(50, 50) + { + AddPage(0); - private const int LabelColor32 = 0xFFFFFF; - private const int BlackColor32 = 0x000008; + const int offset = 50; - public BeginGump( int count ) : base( 50, 50 ) - { - AddPage( 0 ); + AddBackground(1, 1, 398, 202 - offset, 3600); - const int offset = 50; + AddImageTiled(16, 15, 369, 173 - offset, 3604); + AddAlphaRegion(16, 15, 369, 173 - offset); - AddBackground( 1, 1, 398, 202-offset, 3600 ); + AddImage(215, -43, 0xEE40); - AddImageTiled( 16, 15, 369, 173-offset, 3604 ); - AddAlphaRegion( 16, 15, 369, 173-offset ); + AddHtml(22 - 1, 22, 294, 20, Color(Center("Duel Countdown"), BlackColor32), false, false); + AddHtml(22 + 1, 22, 294, 20, Color(Center("Duel Countdown"), BlackColor32), false, false); + AddHtml(22, 22 - 1, 294, 20, Color(Center("Duel Countdown"), BlackColor32), false, false); + AddHtml(22, 22 + 1, 294, 20, Color(Center("Duel Countdown"), BlackColor32), false, false); + AddHtml(22, 22, 294, 20, Color(Center("Duel Countdown"), LabelColor32), false, false); - AddImage( 215, -43, 0xEE40 ); + AddHtml(22 - 1, 50, 294, 80, + Color( + "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", + BlackColor32), false, false); + AddHtml(22 + 1, 50, 294, 80, + Color( + "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", + BlackColor32), false, false); + AddHtml(22, 50 - 1, 294, 80, + Color( + "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", + BlackColor32), false, false); + AddHtml(22, 50 + 1, 294, 80, + Color( + "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", + BlackColor32), false, false); + AddHtml(22, 50, 294, 80, + Color( + "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", + 0xFFCC66), false, false); - AddHtml( 22-1, 22, 294, 20, Color( Center( "Duel Countdown" ), BlackColor32 ), false, false ); - AddHtml( 22+1, 22, 294, 20, Color( Center( "Duel Countdown" ), BlackColor32 ), false, false ); - AddHtml( 22, 22-1, 294, 20, Color( Center( "Duel Countdown" ), BlackColor32 ), false, false ); - AddHtml( 22, 22+1, 294, 20, Color( Center( "Duel Countdown" ), BlackColor32 ), false, false ); - AddHtml( 22, 22, 294, 20, Color( Center( "Duel Countdown" ), LabelColor32 ), false, false ); + /*AddImageTiled( 32, 128, 264, 1, 9107 ); + AddImageTiled( 42, 130, 264, 1, 9157 ); - AddHtml( 22-1, 50, 294, 80, Color( "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", BlackColor32 ), false, false ); - AddHtml( 22+1, 50, 294, 80, Color( "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", BlackColor32 ), false, false ); - AddHtml( 22, 50-1, 294, 80, Color( "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", BlackColor32 ), false, false ); - AddHtml( 22, 50+1, 294, 80, Color( "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", BlackColor32 ), false, false ); - AddHtml( 22, 50, 294, 80, Color( "The arranged duel is about to begin. During this countdown period you may not cast spells and you may not move. This message will close automatically when the period ends.", 0xFFCC66 ), false, false ); + AddHtml( 60-1, 140, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); + AddHtml( 60+1, 140, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); + AddHtml( 60, 140-1, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); + AddHtml( 60, 140+1, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); + AddHtml( 60, 140, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", 0x66AACC ), 0x66AACC ), false, false );*/ - /*AddImageTiled( 32, 128, 264, 1, 9107 ); - AddImageTiled( 42, 130, 264, 1, 9157 ); + AddButton(314 - 50, 157 - offset, 247, 248, 1, GumpButtonType.Reply, 0); + } - AddHtml( 60-1, 140, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); - AddHtml( 60+1, 140, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); - AddHtml( 60, 140-1, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); - AddHtml( 60, 140+1, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", BlackColor32 ), BlackColor32 ), false, false ); - AddHtml( 60, 140, 250, 20, Color( String.Format( "Duel will begin in {0} second{1}.", count, count==1?"":"s", 0x66AACC ), 0x66AACC ), false, false );*/ + public string Center(string text) + { + return $"
{text}
"; + } - AddButton( 314-50, 157-offset, 247, 248, 1, GumpButtonType.Reply, 0 ); - } - } + public string Color(string text, int color) + { + return $"{text}"; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/DuelContext.cs b/Scripts/Engines/ConPVP/DuelContext.cs index 152ab0a9d..98dbe000a 100644 --- a/Scripts/Engines/ConPVP/DuelContext.cs +++ b/Scripts/Engines/ConPVP/DuelContext.cs @@ -8,2581 +8,2613 @@ using Server.Gumps; using Server.Items; using Server.Mobiles; using Server.Network; +using Server.Regions; using Server.Spells; using Server.Spells.Bushido; using Server.Spells.Chivalry; +using Server.Spells.Fourth; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; +using Server.Spells.Second; using Server.Spells.Seventh; using Server.Spells.Spellweaving; +using Server.Targeting; namespace Server.Engines.ConPVP { - public delegate void CountdownCallback( int count ); + public delegate void CountdownCallback(int count); - public class DuelContext - { - public bool Rematch { get; private set; } + public class DuelContext + { + private static TimeSpan CombatDelay = TimeSpan.FromSeconds(30.0); + private static TimeSpan AutoTieDelay = TimeSpan.FromMinutes(15.0); - public bool ReadyWait { get; private set; } + private Timer m_AutoTieTimer; - public int ReadyCount { get; private set; } + private Timer m_Countdown; - public bool Registered { get; private set; } = true; + private ArrayList m_Entered = new ArrayList(); + public EventGame m_EventGame; + private Map m_GateFacet; - public bool Finished { get; private set; } + private Point3D m_GatePoint; + public TournyMatch m_Match; - public bool Started { get; private set; } + public Arena m_OverrideArena; - public Mobile Initiator { get; } + private Timer m_SDWarnTimer, m_SDActivateTimer; + public Tournament m_Tournament; - public ArrayList Participants { get; } + private ArrayList m_Walls = new ArrayList(); - public Ruleset Ruleset { get; private set; } + private bool m_Yielding; - public Arena Arena { get; private set; } + public DuelContext(Mobile initiator, RulesetLayout layout) : this(initiator, layout, true) + { + } - private bool CantDoAnything( Mobile mob ) - { - if ( m_EventGame != null ) - return m_EventGame.CantDoAnything( mob ); + public DuelContext(Mobile initiator, RulesetLayout layout, bool addNew) + { + Initiator = initiator; + Participants = new ArrayList(); + Ruleset = new Ruleset(layout); + Ruleset.ApplyDefault(layout.Defaults[0]); - return false; - } + if (addNew) + { + Participants.Add(new Participant(this, 1)); + Participants.Add(new Participant(this, 1)); - public static bool IsFreeConsume( Mobile mob ) - { - if ( !(mob is PlayerMobile pm) || pm.DuelContext?.m_EventGame == null ) - return false; + ((Participant)Participants[0]).Add(initiator); + } + } - return pm.DuelContext.m_EventGame.FreeConsume; - } + public bool Rematch{ get; private set; } - public void DelayBounce( TimeSpan ts, Mobile mob, Container corpse ) - { - Timer.DelayCall( ts, new TimerStateCallback( DelayBounce_Callback ), new object[]{ mob, corpse } ); - } + public bool ReadyWait{ get; private set; } - public static bool AllowSpecialMove( Mobile from, string name, SpecialMove move ) - { - if ( !(from is PlayerMobile pm) ) - return true; + public int ReadyCount{ get; private set; } - DuelContext dc = pm.DuelContext; - - // No DuelContext, or InstaAllowSpecialMove - return dc?.InstAllowSpecialMove( from, name, move ) != false; - } - - public bool InstAllowSpecialMove( Mobile from, string name, SpecialMove move ) - { + public bool Registered{ get; private set; } = true; - if ( !StartedBeginCountdown ) - return true; + public bool Finished{ get; private set; } - DuelPlayer pl = Find( from ); + public bool Started{ get; private set; } - if ( pl == null || pl.Eliminated ) - return true; + public Mobile Initiator{ get; } - if ( CantDoAnything( from ) ) - return false; + public ArrayList Participants{ get; } - string title = null; + public Ruleset Ruleset{ get; private set; } - if ( move is NinjaMove ) - title = "Bushido"; - else if ( move is SamuraiMove ) - title = "Ninjitsu"; + public Arena Arena{ get; private set; } + public bool Tied{ get; private set; } - if ( title == null || name == null || Ruleset.GetOption( title, name ) ) - return true; + public bool IsSuddenDeath{ get; set; } - from.SendMessage( "The dueling ruleset prevents you from using this move." ); - return false; - } + public bool IsOneVsOne + { + get + { + if (Participants.Count != 2) + return false; - public bool AllowSpellCast( Mobile from, Spell spell ) - { - if ( !StartedBeginCountdown ) - return true; + if (((Participant)Participants[0]).Players.Length != 1) + return false; - DuelPlayer pl = Find( from ); + if (((Participant)Participants[1]).Players.Length != 1) + return false; - if ( pl == null || pl.Eliminated ) - return true; + return true; + } + } - if ( CantDoAnything( from ) ) - return false; + public bool StartedBeginCountdown{ get; private set; } - if ( spell is Spells.Fourth.RecallSpell ) - from.SendMessage( "You may not cast this spell." ); + public bool StartedReadyCountdown{ get; private set; } - string title = null, option = null; + public Tournament Tournament => m_Tournament; - if ( spell is ArcanistSpell ) - { - title = "Spellweaving"; - option = spell.Name; - } - else if ( spell is PaladinSpell ) - { - title = "Chivalry"; - option = spell.Name; - } - else if ( spell is NecromancerSpell ) - { - title = "Necromancy"; - option = spell.Name; - } - else if ( spell is NinjaSpell ) - { - title = "Ninjitsu"; - option = spell.Name; - } - else if ( spell is SamuraiSpell ) - { - title = "Bushido"; - option = spell.Name; - } - else if ( spell is MagerySpell magerySpell ) - { - switch( magerySpell.Circle ) - { - case SpellCircle.First: title = "1st Circle"; break; - case SpellCircle.Second: title = "2nd Circle"; break; - case SpellCircle.Third: title = "3rd Circle"; break; - case SpellCircle.Fourth: title = "4th Circle"; break; - case SpellCircle.Fifth: title = "5th Circle"; break; - case SpellCircle.Sixth: title = "6th Circle"; break; - case SpellCircle.Seventh: title = "7th Circle"; break; - case SpellCircle.Eighth: title = "8th Circle"; break; - } - - option = magerySpell.Name; - } - else - { - title = "Other Spell"; - option = spell.Name; - } - - if ( title == null || option == null || Ruleset.GetOption( title, option ) ) - return true; - - from.SendMessage( "The dueling ruleset prevents you from casting this spell." ); - return false; - } - - public bool AllowItemEquip( Mobile from, Item item ) - { - if ( !StartedBeginCountdown ) - return true; - - DuelPlayer pl = Find( from ); - - if ( pl == null || pl.Eliminated ) - return true; - - if ( item is Dagger || CheckItemEquip( from, item ) ) - return true; - - from.SendMessage( "The dueling ruleset prevents you from equiping this item." ); - return false; - } - - public static bool AllowSpecialAbility( Mobile from, string name, bool message ) - { - if ( !(from is PlayerMobile pm) ) - return true; - - DuelContext dc = pm.DuelContext; - - // No DuelContext or InstAllowSpecialAbility - return dc?.InstAllowSpecialAbility( from, name, message ) != false; - } - - public bool InstAllowSpecialAbility( Mobile from, string name, bool message ) - { - if ( !StartedBeginCountdown ) - return true; - - DuelPlayer pl = Find( from ); - - if ( pl?.Eliminated != false ) - return true; - - if ( CantDoAnything( from ) ) - return false; - - if ( Ruleset.GetOption( "Combat Abilities", name ) ) - return true; - - if ( message ) - from.SendMessage( "The dueling ruleset prevents you from using this combat ability." ); - - return false; - } - - public bool CheckItemEquip( Mobile from, Item item ) - { - if ( item is Fists ) - { - if ( !Ruleset.GetOption( "Weapons", "Wrestling" ) ) - return false; - } - else if ( item is BaseArmor armor ) - { - if ( armor.ProtectionLevel > ArmorProtectionLevel.Regular && !Ruleset.GetOption( "Armor", "Magical" ) ) - return false; - - if ( !Core.AOS && armor.Resource != armor.DefaultResource && !Ruleset.GetOption( "Armor", "Colored" ) ) - return false; - - if ( armor is BaseShield && !Ruleset.GetOption( "Armor", "Shields" ) ) - return false; - } - else if ( item is BaseWeapon weapon ) - { - if ( (weapon.DamageLevel > WeaponDamageLevel.Regular || weapon.AccuracyLevel > WeaponAccuracyLevel.Regular) && !Ruleset.GetOption( "Weapons", "Magical" ) ) - return false; - - if ( !Core.AOS && weapon.Resource != CraftResource.Iron && weapon.Resource != CraftResource.None && !Ruleset.GetOption( "Weapons", "Runics" ) ) - return false; - - if ( weapon is BaseRanged && !Ruleset.GetOption( "Weapons", "Ranged" ) ) - return false; - - if ( !(weapon is BaseRanged) && !Ruleset.GetOption( "Weapons", "Melee" ) ) - return false; - - if ( weapon.PoisonCharges > 0 && weapon.Poison != null && !Ruleset.GetOption( "Weapons", "Poisoned" ) ) - return false; - - if ( weapon is BaseWand && !Ruleset.GetOption( "Items", "Wands" ) ) - return false; - } - - return true; - } - - public bool AllowSkillUse( Mobile from, SkillName skill ) - { - if ( !StartedBeginCountdown ) - return true; - - DuelPlayer pl = Find( from ); - - if ( pl == null || pl.Eliminated ) - return true; - - if ( CantDoAnything( from ) ) - return false; - - int id = (int)skill; - - if ( id >= 0 && id < SkillInfo.Table.Length ) - { - if ( Ruleset.GetOption( "Skills", SkillInfo.Table[id].Name ) ) - return true; - } - - from.SendMessage( "The dueling ruleset prevents you from using this skill." ); - return false; - } - - public bool AllowItemUse( Mobile from, Item item ) - { - if ( !StartedBeginCountdown ) - return true; - - DuelPlayer pl = Find( from ); - - if ( pl == null || pl.Eliminated ) - return true; - - if ( !(item is BaseRefreshPotion) ) - { - if ( CantDoAnything( from ) ) - return false; - } - - string title = null, option = null; - - if ( item is BasePotion ) - { - title = "Potions"; - - if ( item is BaseAgilityPotion ) - option = "Agility"; - else if ( item is BaseCurePotion ) - option = "Cure"; - else if ( item is BaseHealPotion ) - option = "Heal"; - else if ( item is NightSightPotion ) - option = "Nightsight"; - else if ( item is BasePoisonPotion ) - option = "Poison"; - else if ( item is BaseStrengthPotion ) - option = "Strength"; - else if ( item is BaseExplosionPotion ) - option = "Explosion"; - else if ( item is BaseRefreshPotion ) - option = "Refresh"; - } - else if ( item is Bandage ) - { - title = "Items"; - option = "Bandages"; - } - else if ( item is TrappableContainer container ) - { - if ( container.TrapType != TrapType.None ) - { - title = "Items"; - option = "Trapped Containers"; - } - } - else if ( item is Bola ) - { - title = "Items"; - option = "Bolas"; - } - else if ( item is OrangePetals ) - { - title = "Items"; - option = "Orange Petals"; - } - else if ( item is EtherealMount || item.Layer == Layer.Mount ) - { - title = "Items"; - option = "Mounts"; - } - else if ( item is LeatherNinjaBelt ) - { - title = "Items"; - option = "Shurikens"; - } - else if ( item is Fukiya ) - { - title = "Items"; - option = "Fukiya Darts"; - } - else if ( item is FireHorn ) - { - title = "Items"; - option = "Fire Horns"; - } - else if ( item is BaseWand ) - { - title = "Items"; - option = "Wands"; - } - - if ( title != null && option != null && StartedBeginCountdown && !Started ) - { - from.SendMessage( "You may not use this item before the duel begins." ); - return false; - } - if ( item is BasePotion && !(item is BaseExplosionPotion) && !(item is BaseRefreshPotion) && IsSuddenDeath ) - { - from.SendMessage( 0x22, "You may not drink potions in sudden death." ); - return false; - } - if ( item is Bandage && IsSuddenDeath ) - { - from.SendMessage( 0x22, "You may not use bandages in sudden death." ); - return false; - } - - if ( title == null || option == null || Ruleset.GetOption( title, option ) ) - return true; - - from.SendMessage( "The dueling ruleset prevents you from using this item." ); - return false; - } - - private void DelayBounce_Callback( object state ) - { - object[] states = (object[])state; - Mobile mob = (Mobile) states[0]; - Container corpse = (Container) states[1]; - - RemoveAggressions( mob ); - SendOutside( mob ); - Refresh( mob, corpse ); - Debuff( mob ); - CancelSpell( mob ); - mob.Frozen = false; - } - - public void OnMapChanged( Mobile mob ) - { - OnLocationChanged( mob ); - } - - public void OnLocationChanged( Mobile mob ) - { - if ( !Registered || !StartedBeginCountdown || Finished ) - return; - - Arena arena = Arena; - - if ( arena == null ) - return; - - if ( mob.Map == arena.Facet && arena.Bounds.Contains( mob.Location ) ) - return; - - DuelPlayer pl = Find( mob ); - - if ( pl == null || pl.Eliminated ) - return; - - if ( mob.Map == Map.Internal ) { - // they've logged out - - if ( mob.LogoutMap == arena.Facet && arena.Bounds.Contains( mob.LogoutLocation ) ) { - // they logged out inside the arena.. set them to eject on login - - mob.LogoutLocation = arena.Outside; - } - } - - pl.Eliminated = true; - - mob.LocalOverheadMessage( MessageType.Regular, 0x22, false, "You have forfeited your position in the duel." ); - mob.NonlocalOverheadMessage( MessageType.Regular, 0x22, false, - $"{mob.Name} has forfeited by leaving the dueling arena."); - - Participant winner = CheckCompletion(); - - if ( winner != null ) - Finish( winner ); - } - - private bool m_Yielding; - - public void OnDeath( Mobile mob, Container corpse ) - { - if ( !Registered || !Started ) - return; - - DuelPlayer pl = Find( mob ); - - if ( pl != null && !pl.Eliminated ) - { - if ( m_EventGame != null && !m_EventGame.OnDeath( mob, corpse ) ) - return; - - pl.Eliminated = true; - - if ( mob.Poison != null ) - mob.Poison = null; - - Requip( mob, corpse ); - DelayBounce( TimeSpan.FromSeconds( 4.0 ), mob, corpse ); - - Participant winner = CheckCompletion(); + private bool CantDoAnything(Mobile mob) + { + if (m_EventGame != null) + return m_EventGame.CantDoAnything(mob); - if ( winner != null ) - { - Finish( winner ); - } - else if ( !m_Yielding ) - { - mob.LocalOverheadMessage( MessageType.Regular, 0x22, false, "You have been defeated." ); - mob.NonlocalOverheadMessage( MessageType.Regular, 0x22, false, $"{mob.Name} has been defeated."); - } - } - } + return false; + } - public bool CheckFull() - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + public static bool IsFreeConsume(Mobile mob) + { + if (!(mob is PlayerMobile pm) || pm.DuelContext?.m_EventGame == null) + return false; - if ( p.HasOpenSlot ) - return false; - } + return pm.DuelContext.m_EventGame.FreeConsume; + } - return true; - } + public void DelayBounce(TimeSpan ts, Mobile mob, Container corpse) + { + Timer.DelayCall(ts, new TimerStateCallback(DelayBounce_Callback), new object[] { mob, corpse }); + } - public void Requip( Mobile from, Container cont ) - { - if ( !(cont is Corpse corpse) ) - return; + public static bool AllowSpecialMove(Mobile from, string name, SpecialMove move) + { + if (!(from is PlayerMobile pm)) + return true; - List items = new List( corpse.Items ); + DuelContext dc = pm.DuelContext; + + // No DuelContext, or InstaAllowSpecialMove + return dc?.InstAllowSpecialMove(from, name, move) != false; + } + + public bool InstAllowSpecialMove(Mobile from, string name, SpecialMove move) + { + if (!StartedBeginCountdown) + return true; + + DuelPlayer pl = Find(from); + + if (pl == null || pl.Eliminated) + return true; + + if (CantDoAnything(from)) + return false; + + string title = null; + + if (move is NinjaMove) + title = "Bushido"; + else if (move is SamuraiMove) + title = "Ninjitsu"; + + + if (title == null || name == null || Ruleset.GetOption(title, name)) + return true; + + from.SendMessage("The dueling ruleset prevents you from using this move."); + return false; + } + + public bool AllowSpellCast(Mobile from, Spell spell) + { + if (!StartedBeginCountdown) + return true; + + DuelPlayer pl = Find(from); + + if (pl == null || pl.Eliminated) + return true; + + if (CantDoAnything(from)) + return false; + + if (spell is RecallSpell) + from.SendMessage("You may not cast this spell."); + + string title = null, option = null; + + if (spell is ArcanistSpell) + { + title = "Spellweaving"; + option = spell.Name; + } + else if (spell is PaladinSpell) + { + title = "Chivalry"; + option = spell.Name; + } + else if (spell is NecromancerSpell) + { + title = "Necromancy"; + option = spell.Name; + } + else if (spell is NinjaSpell) + { + title = "Ninjitsu"; + option = spell.Name; + } + else if (spell is SamuraiSpell) + { + title = "Bushido"; + option = spell.Name; + } + else if (spell is MagerySpell magerySpell) + { + switch (magerySpell.Circle) + { + case SpellCircle.First: + title = "1st Circle"; + break; + case SpellCircle.Second: + title = "2nd Circle"; + break; + case SpellCircle.Third: + title = "3rd Circle"; + break; + case SpellCircle.Fourth: + title = "4th Circle"; + break; + case SpellCircle.Fifth: + title = "5th Circle"; + break; + case SpellCircle.Sixth: + title = "6th Circle"; + break; + case SpellCircle.Seventh: + title = "7th Circle"; + break; + case SpellCircle.Eighth: + title = "8th Circle"; + break; + } + + option = magerySpell.Name; + } + else + { + title = "Other Spell"; + option = spell.Name; + } + + if (title == null || option == null || Ruleset.GetOption(title, option)) + return true; + + from.SendMessage("The dueling ruleset prevents you from casting this spell."); + return false; + } + + public bool AllowItemEquip(Mobile from, Item item) + { + if (!StartedBeginCountdown) + return true; + + DuelPlayer pl = Find(from); + + if (pl == null || pl.Eliminated) + return true; + + if (item is Dagger || CheckItemEquip(from, item)) + return true; + + from.SendMessage("The dueling ruleset prevents you from equipping this item."); + return false; + } + + public static bool AllowSpecialAbility(Mobile from, string name, bool message) + { + if (!(from is PlayerMobile pm)) + return true; + + DuelContext dc = pm.DuelContext; + + // No DuelContext or InstAllowSpecialAbility + return dc?.InstAllowSpecialAbility(from, name, message) != false; + } + + public bool InstAllowSpecialAbility(Mobile from, string name, bool message) + { + if (!StartedBeginCountdown) + return true; + + DuelPlayer pl = Find(from); + + if (pl?.Eliminated != false) + return true; + + if (CantDoAnything(from)) + return false; + + if (Ruleset.GetOption("Combat Abilities", name)) + return true; + + if (message) + from.SendMessage("The dueling ruleset prevents you from using this combat ability."); + + return false; + } + + public bool CheckItemEquip(Mobile from, Item item) + { + if (item is Fists) + { + if (!Ruleset.GetOption("Weapons", "Wrestling")) + return false; + } + else if (item is BaseArmor armor) + { + if (armor.ProtectionLevel > ArmorProtectionLevel.Regular && !Ruleset.GetOption("Armor", "Magical")) + return false; + + if (!Core.AOS && armor.Resource != armor.DefaultResource && !Ruleset.GetOption("Armor", "Colored")) + return false; + + if (armor is BaseShield && !Ruleset.GetOption("Armor", "Shields")) + return false; + } + else if (item is BaseWeapon weapon) + { + if ((weapon.DamageLevel > WeaponDamageLevel.Regular || weapon.AccuracyLevel > WeaponAccuracyLevel.Regular) && + !Ruleset.GetOption("Weapons", "Magical")) + return false; + + if (!Core.AOS && weapon.Resource != CraftResource.Iron && weapon.Resource != CraftResource.None && + !Ruleset.GetOption("Weapons", "Runics")) + return false; + + if (weapon is BaseRanged && !Ruleset.GetOption("Weapons", "Ranged")) + return false; + + if (!(weapon is BaseRanged) && !Ruleset.GetOption("Weapons", "Melee")) + return false; + + if (weapon.PoisonCharges > 0 && weapon.Poison != null && !Ruleset.GetOption("Weapons", "Poisoned")) + return false; + + if (weapon is BaseWand && !Ruleset.GetOption("Items", "Wands")) + return false; + } + + return true; + } + + public bool AllowSkillUse(Mobile from, SkillName skill) + { + if (!StartedBeginCountdown) + return true; + + DuelPlayer pl = Find(from); + + if (pl == null || pl.Eliminated) + return true; + + if (CantDoAnything(from)) + return false; + + int id = (int)skill; + + if (id >= 0 && id < SkillInfo.Table.Length) + if (Ruleset.GetOption("Skills", SkillInfo.Table[id].Name)) + return true; + + from.SendMessage("The dueling ruleset prevents you from using this skill."); + return false; + } + + public bool AllowItemUse(Mobile from, Item item) + { + if (!StartedBeginCountdown) + return true; + + DuelPlayer pl = Find(from); + + if (pl == null || pl.Eliminated) + return true; + + if (!(item is BaseRefreshPotion)) + if (CantDoAnything(from)) + return false; + + string title = null, option = null; + + if (item is BasePotion) + { + title = "Potions"; + + if (item is BaseAgilityPotion) + option = "Agility"; + else if (item is BaseCurePotion) + option = "Cure"; + else if (item is BaseHealPotion) + option = "Heal"; + else if (item is NightSightPotion) + option = "Nightsight"; + else if (item is BasePoisonPotion) + option = "Poison"; + else if (item is BaseStrengthPotion) + option = "Strength"; + else if (item is BaseExplosionPotion) + option = "Explosion"; + else if (item is BaseRefreshPotion) + option = "Refresh"; + } + else if (item is Bandage) + { + title = "Items"; + option = "Bandages"; + } + else if (item is TrappableContainer container) + { + if (container.TrapType != TrapType.None) + { + title = "Items"; + option = "Trapped Containers"; + } + } + else if (item is Bola) + { + title = "Items"; + option = "Bolas"; + } + else if (item is OrangePetals) + { + title = "Items"; + option = "Orange Petals"; + } + else if (item is EtherealMount || item.Layer == Layer.Mount) + { + title = "Items"; + option = "Mounts"; + } + else if (item is LeatherNinjaBelt) + { + title = "Items"; + option = "Shurikens"; + } + else if (item is Fukiya) + { + title = "Items"; + option = "Fukiya Darts"; + } + else if (item is FireHorn) + { + title = "Items"; + option = "Fire Horns"; + } + else if (item is BaseWand) + { + title = "Items"; + option = "Wands"; + } + + if (title != null && option != null && StartedBeginCountdown && !Started) + { + from.SendMessage("You may not use this item before the duel begins."); + return false; + } + + if (item is BasePotion && !(item is BaseExplosionPotion) && !(item is BaseRefreshPotion) && IsSuddenDeath) + { + from.SendMessage(0x22, "You may not drink potions in sudden death."); + return false; + } + + if (item is Bandage && IsSuddenDeath) + { + from.SendMessage(0x22, "You may not use bandages in sudden death."); + return false; + } + + if (title == null || option == null || Ruleset.GetOption(title, option)) + return true; + + from.SendMessage("The dueling ruleset prevents you from using this item."); + return false; + } + + private void DelayBounce_Callback(object state) + { + object[] states = (object[])state; + Mobile mob = (Mobile)states[0]; + Container corpse = (Container)states[1]; + + RemoveAggressions(mob); + SendOutside(mob); + Refresh(mob, corpse); + Debuff(mob); + CancelSpell(mob); + mob.Frozen = false; + } + + public void OnMapChanged(Mobile mob) + { + OnLocationChanged(mob); + } + + public void OnLocationChanged(Mobile mob) + { + if (!Registered || !StartedBeginCountdown || Finished) + return; + + Arena arena = Arena; + + if (arena == null) + return; + + if (mob.Map == arena.Facet && arena.Bounds.Contains(mob.Location)) + return; + + DuelPlayer pl = Find(mob); + + if (pl == null || pl.Eliminated) + return; + + if (mob.Map == Map.Internal) + if (mob.LogoutMap == arena.Facet && arena.Bounds.Contains(mob.LogoutLocation)) + mob.LogoutLocation = arena.Outside; + + pl.Eliminated = true; + + mob.LocalOverheadMessage(MessageType.Regular, 0x22, false, "You have forfeited your position in the duel."); + mob.NonlocalOverheadMessage(MessageType.Regular, 0x22, false, + $"{mob.Name} has forfeited by leaving the dueling arena."); + + Participant winner = CheckCompletion(); + + if (winner != null) + Finish(winner); + } + + public void OnDeath(Mobile mob, Container corpse) + { + if (!Registered || !Started) + return; + + DuelPlayer pl = Find(mob); + + if (pl != null && !pl.Eliminated) + { + if (m_EventGame != null && !m_EventGame.OnDeath(mob, corpse)) + return; + + pl.Eliminated = true; + + if (mob.Poison != null) + mob.Poison = null; + + Requip(mob, corpse); + DelayBounce(TimeSpan.FromSeconds(4.0), mob, corpse); + + Participant winner = CheckCompletion(); - bool didntFit = false; + if (winner != null) + { + Finish(winner); + } + else if (!m_Yielding) + { + mob.LocalOverheadMessage(MessageType.Regular, 0x22, false, "You have been defeated."); + mob.NonlocalOverheadMessage(MessageType.Regular, 0x22, false, $"{mob.Name} has been defeated."); + } + } + } - Container pack = from.Backpack; + public bool CheckFull() + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - for ( int i = 0; !didntFit && i < items.Count; ++i ) - { - Item item = items[i]; + if (p.HasOpenSlot) + return false; + } - if ( (item.Layer == Layer.Hair || item.Layer == Layer.FacialHair) || !item.Movable ) - continue; + return true; + } - if ( pack != null ) - pack.DropItem( item ); - else - didntFit = true; - } + public void Requip(Mobile from, Container cont) + { + if (!(cont is Corpse corpse)) + return; - corpse.Carved = true; + List items = new List(corpse.Items); - if ( corpse.ItemID == 0x2006 ) - { - corpse.ProcessDelta(); - corpse.SendRemovePacket(); - corpse.ItemID = Utility.Random( 0xECA, 9 ); // bone graphic - corpse.Hue = 0; - corpse.ProcessDelta(); + bool didntFit = false; - Mobile killer = from.FindMostRecentDamager( false ); + Container pack = from.Backpack; - if ( killer != null && killer.Player ) - killer.AddToBackpack( new Head( m_Tournament == null ? HeadType.Duel : HeadType.Tournament, from.Name ) ); - } + for (int i = 0; !didntFit && i < items.Count; ++i) + { + Item item = items[i]; - from.PlaySound( 0x3E3 ); + if (item.Layer == Layer.Hair || item.Layer == Layer.FacialHair || !item.Movable) + continue; - if (didntFit) - from.SendLocalizedMessage(1062472); // You gather some of your belongings. The rest remain on the corpse. - else - from.SendLocalizedMessage(1062471); // You quickly gather all of your belongings. + if (pack != null) + pack.DropItem(item); + else + didntFit = true; + } - } - - public void Refresh( Mobile mob, Container cont ) - { - if ( !mob.Alive ) - { - mob.Resurrect(); - - if ( mob.FindItemOnLayer( Layer.OuterTorso ) is DeathRobe robe ) - robe.Delete(); - - if ( cont is Corpse corpse ) - { - for ( int i = 0; i < corpse.EquipItems.Count; ++i ) - { - Item item = corpse.EquipItems[i]; - - if ( item.Movable && item.Layer != Layer.Hair && item.Layer != Layer.FacialHair && item.IsChildOf( mob.Backpack ) ) - mob.EquipItem( item ); - } - } - } - - mob.Hits = mob.HitsMax; - mob.Stam = mob.StamMax; - mob.Mana = mob.ManaMax; - - mob.Poison = null; - } - - public void SendOutside( Mobile mob ) - { - if ( Arena == null ) - return; + corpse.Carved = true; - mob.Combatant = null; - mob.MoveToWorld( Arena.Outside, Arena.Facet ); - } + if (corpse.ItemID == 0x2006) + { + corpse.ProcessDelta(); + corpse.SendRemovePacket(); + corpse.ItemID = Utility.Random(0xECA, 9); // bone graphic + corpse.Hue = 0; + corpse.ProcessDelta(); - private Point3D m_GatePoint; - private Map m_GateFacet; + Mobile killer = from.FindMostRecentDamager(false); + + if (killer != null && killer.Player) + killer.AddToBackpack(new Head(m_Tournament == null ? HeadType.Duel : HeadType.Tournament, from.Name)); + } + + from.PlaySound(0x3E3); + + if (didntFit) + from.SendLocalizedMessage(1062472); // You gather some of your belongings. The rest remain on the corpse. + else + from.SendLocalizedMessage(1062471); // You quickly gather all of your belongings. + } + + public void Refresh(Mobile mob, Container cont) + { + if (!mob.Alive) + { + mob.Resurrect(); + + if (mob.FindItemOnLayer(Layer.OuterTorso) is DeathRobe robe) + robe.Delete(); + + if (cont is Corpse corpse) + for (int i = 0; i < corpse.EquipItems.Count; ++i) + { + Item item = corpse.EquipItems[i]; + + if (item.Movable && item.Layer != Layer.Hair && item.Layer != Layer.FacialHair && + item.IsChildOf(mob.Backpack)) + mob.EquipItem(item); + } + } + + mob.Hits = mob.HitsMax; + mob.Stam = mob.StamMax; + mob.Mana = mob.ManaMax; + + mob.Poison = null; + } + + public void SendOutside(Mobile mob) + { + if (Arena == null) + return; + + mob.Combatant = null; + mob.MoveToWorld(Arena.Outside, Arena.Facet); + } - public void Finish( Participant winner ) - { - if ( Finished ) - return; + public void Finish(Participant winner) + { + if (Finished) + return; - EndAutoTie(); - StopSDTimers(); + EndAutoTie(); + StopSDTimers(); - Finished = true; + Finished = true; - for ( int i = 0; i < winner.Players.Length; ++i ) - { - DuelPlayer pl = winner.Players[i]; + for (int i = 0; i < winner.Players.Length; ++i) + { + DuelPlayer pl = winner.Players[i]; - if ( pl != null && !pl.Eliminated ) - DelayBounce( TimeSpan.FromSeconds( 8.0 ), pl.Mobile, null ); - } + if (pl != null && !pl.Eliminated) + DelayBounce(TimeSpan.FromSeconds(8.0), pl.Mobile, null); + } - winner.Broadcast( 0x59, null, winner.Players.Length == 1 ? "{0} has won the duel." : "{0} and {1} team have won the duel.", winner.Players.Length == 1 ? "You have won the duel." : "Your team has won the duel." ); + winner.Broadcast(0x59, null, + winner.Players.Length == 1 ? "{0} has won the duel." : "{0} and {1} team have won the duel.", + winner.Players.Length == 1 ? "You have won the duel." : "Your team has won the duel."); - if ( m_Tournament != null && winner.TournyPart != null ) - { - m_Match.Winner = winner.TournyPart; - winner.TournyPart.WonMatch( m_Match ); - m_Tournament.HandleWon( Arena, m_Match, winner.TournyPart ); - } + if (m_Tournament != null && winner.TournyPart != null) + { + m_Match.Winner = winner.TournyPart; + winner.TournyPart.WonMatch(m_Match); + m_Tournament.HandleWon(Arena, m_Match, winner.TournyPart); + } - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant loser = (Participant)Participants[i]; + for (int i = 0; i < Participants.Count; ++i) + { + Participant loser = (Participant)Participants[i]; - if ( loser != winner ) - { - loser.Broadcast( 0x22, null, loser.Players.Length == 1 ? "{0} has lost the duel." : "{0} and {1} team have lost the duel.", loser.Players.Length == 1 ? "You have lost the duel." : "Your team has lost the duel." ); + if (loser != winner) + { + loser.Broadcast(0x22, null, + loser.Players.Length == 1 ? "{0} has lost the duel." : "{0} and {1} team have lost the duel.", + loser.Players.Length == 1 ? "You have lost the duel." : "Your team has lost the duel."); - if ( m_Tournament != null ) - loser.TournyPart?.LostMatch( m_Match ); - } + if (m_Tournament != null) + loser.TournyPart?.LostMatch(m_Match); + } - for ( int j = 0; j < loser.Players.Length; ++j ) - { - if ( loser.Players[j] != null ) - { - RemoveAggressions( loser.Players[j].Mobile ); - loser.Players[j].Mobile.Delta( MobileDelta.Noto ); - loser.Players[j].Mobile.CloseGump( typeof( BeginGump ) ); + for (int j = 0; j < loser.Players.Length; ++j) + if (loser.Players[j] != null) + { + RemoveAggressions(loser.Players[j].Mobile); + loser.Players[j].Mobile.Delta(MobileDelta.Noto); + loser.Players[j].Mobile.CloseGump(typeof(BeginGump)); - if ( m_Tournament != null ) - loser.Players[j].Mobile.SendEverything(); - } - } - } + if (m_Tournament != null) + loser.Players[j].Mobile.SendEverything(); + } + } - if ( IsOneVsOne ) - { - DuelPlayer dp1 = ((Participant)Participants[0]).Players[0]; - DuelPlayer dp2 = ((Participant)Participants[1]).Players[0]; + if (IsOneVsOne) + { + DuelPlayer dp1 = ((Participant)Participants[0]).Players[0]; + DuelPlayer dp2 = ((Participant)Participants[1]).Players[0]; - if ( dp1 != null && dp2 != null ) - { - Award( dp1.Mobile, dp2.Mobile, dp1.Participant == winner ); - Award( dp2.Mobile, dp1.Mobile, dp2.Participant == winner ); - } - } + if (dp1 != null && dp2 != null) + { + Award(dp1.Mobile, dp2.Mobile, dp1.Participant == winner); + Award(dp2.Mobile, dp1.Mobile, dp2.Participant == winner); + } + } - m_EventGame?.OnStop(); + m_EventGame?.OnStop(); - Timer.DelayCall( TimeSpan.FromSeconds( 9.0 ), UnregisterRematch ); - } + Timer.DelayCall(TimeSpan.FromSeconds(9.0), UnregisterRematch); + } - public void Award( Mobile us, Mobile them, bool won ) - { - Ladder ladder = ( Arena == null ? Ladder.Instance : Arena.AcquireLadder() ); + public void Award(Mobile us, Mobile them, bool won) + { + Ladder ladder = Arena == null ? Ladder.Instance : Arena.AcquireLadder(); - if ( ladder == null ) - return; + if (ladder == null) + return; - LadderEntry ourEntry = ladder.Find( us ); - LadderEntry theirEntry = ladder.Find( them ); + LadderEntry ourEntry = ladder.Find(us); + LadderEntry theirEntry = ladder.Find(them); - if ( ourEntry == null || theirEntry == null ) - return; + if (ourEntry == null || theirEntry == null) + return; - int xpGain = Ladder.GetExperienceGain( ourEntry, theirEntry, won ); + int xpGain = Ladder.GetExperienceGain(ourEntry, theirEntry, won); - if ( xpGain == 0 ) - return; + if (xpGain == 0) + return; - if ( m_Tournament != null ) - xpGain *= ( xpGain > 0 ? 5 : 2 ); + if (m_Tournament != null) + xpGain *= xpGain > 0 ? 5 : 2; - if ( won ) - ++ourEntry.Wins; - else - ++ourEntry.Losses; + if (won) + ++ourEntry.Wins; + else + ++ourEntry.Losses; - int oldLevel = Ladder.GetLevel( ourEntry.Experience ); + int oldLevel = Ladder.GetLevel(ourEntry.Experience); - ourEntry.Experience += xpGain; + ourEntry.Experience += xpGain; - if ( ourEntry.Experience < 0 ) - ourEntry.Experience = 0; + if (ourEntry.Experience < 0) + ourEntry.Experience = 0; - ladder.UpdateEntry( ourEntry ); + ladder.UpdateEntry(ourEntry); - int newLevel = Ladder.GetLevel( ourEntry.Experience ); + int newLevel = Ladder.GetLevel(ourEntry.Experience); - if ( newLevel > oldLevel ) - us.SendMessage( 0x59, "You have achieved level {0}!", newLevel ); - else if ( newLevel < oldLevel ) - us.SendMessage( 0x22, "You have lost a level. You are now at {0}.", newLevel ); - } + if (newLevel > oldLevel) + us.SendMessage(0x59, "You have achieved level {0}!", newLevel); + else if (newLevel < oldLevel) + us.SendMessage(0x22, "You have lost a level. You are now at {0}.", newLevel); + } - public void UnregisterRematch() - { - Unregister(true); - } + public void UnregisterRematch() + { + Unregister(true); + } - public void Unregister() - { - Unregister(false); - } + public void Unregister() + { + Unregister(false); + } - public void Unregister( bool queryRematch ) - { - DestroyWall(); + public void Unregister(bool queryRematch) + { + DestroyWall(); - if ( !Registered ) - return; + if (!Registered) + return; - Registered = false; + Registered = false; - Arena?.Evict(); + Arena?.Evict(); - StopSDTimers(); + StopSDTimers(); - Type[] types = { typeof( BeginGump ), typeof( DuelContextGump ), typeof( ParticipantGump ), typeof( PickRulesetGump ), typeof( ReadyGump ), typeof( ReadyUpGump ), typeof( RulesetGump ) }; + Type[] types = + { + typeof(BeginGump), typeof(DuelContextGump), typeof(ParticipantGump), typeof(PickRulesetGump), + typeof(ReadyGump), typeof(ReadyUpGump), typeof(RulesetGump) + }; - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - if ( pl == null ) - continue; + if (pl == null) + continue; - if ( pl.Mobile is PlayerMobile mobile ) - mobile.DuelPlayer = null; + if (pl.Mobile is PlayerMobile mobile) + mobile.DuelPlayer = null; - for ( int k = 0; k < types.Length; ++k ) - pl.Mobile.CloseGump( types[k] ); - } - } + for (int k = 0; k < types.Length; ++k) + pl.Mobile.CloseGump(types[k]); + } + } - if ( queryRematch && m_Tournament == null ) - QueryRematch(); - } + if (queryRematch && m_Tournament == null) + QueryRematch(); + } - public void QueryRematch() - { - DuelContext dc = new DuelContext( Initiator, Ruleset.Layout, false ); + public void QueryRematch() + { + DuelContext dc = new DuelContext(Initiator, Ruleset.Layout, false); - dc.Ruleset = Ruleset; - dc.Rematch = true; + dc.Ruleset = Ruleset; + dc.Rematch = true; - dc.Participants.Clear(); + dc.Participants.Clear(); - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant oldPart = (Participant)Participants[i]; - Participant newPart = new Participant( dc, oldPart.Players.Length ); + for (int i = 0; i < Participants.Count; ++i) + { + Participant oldPart = (Participant)Participants[i]; + Participant newPart = new Participant(dc, oldPart.Players.Length); - for ( int j = 0; j < oldPart.Players.Length; ++j ) - { - DuelPlayer oldPlayer = oldPart.Players[j]; + for (int j = 0; j < oldPart.Players.Length; ++j) + { + DuelPlayer oldPlayer = oldPart.Players[j]; - if ( oldPlayer != null ) - newPart.Players[j] = new DuelPlayer( oldPlayer.Mobile, newPart ); - } + if (oldPlayer != null) + newPart.Players[j] = new DuelPlayer(oldPlayer.Mobile, newPart); + } - dc.Participants.Add( newPart ); - } + dc.Participants.Add(newPart); + } - dc.CloseAllGumps(); - dc.SendReadyUpGump(); - } + dc.CloseAllGumps(); + dc.SendReadyUpGump(); + } - public DuelPlayer Find( Mobile mob ) - { - if ( mob is PlayerMobile pm ) - { - if ( pm.DuelContext == this ) - return pm.DuelPlayer; + public DuelPlayer Find(Mobile mob) + { + if (mob is PlayerMobile pm) + { + if (pm.DuelContext == this) + return pm.DuelPlayer; - return null; - } + return null; + } - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - DuelPlayer pl = p.Find( mob ); + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + DuelPlayer pl = p.Find(mob); - if ( pl != null ) - return pl; - } + if (pl != null) + return pl; + } - return null; - } + return null; + } - public bool IsAlly( Mobile m1, Mobile m2 ) - { - DuelPlayer pl1 = Find( m1 ); - DuelPlayer pl2 = Find( m2 ); + public bool IsAlly(Mobile m1, Mobile m2) + { + DuelPlayer pl1 = Find(m1); + DuelPlayer pl2 = Find(m2); - return ( pl1 != null && pl2 != null && pl1.Participant == pl2.Participant ); - } + return pl1 != null && pl2 != null && pl1.Participant == pl2.Participant; + } - public Participant CheckCompletion() - { - Participant winner = null; + public Participant CheckCompletion() + { + Participant winner = null; - bool hasWinner = false; - int eliminated = 0; + bool hasWinner = false; + int eliminated = 0; - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - if ( p.Eliminated ) - { - ++eliminated; + if (p.Eliminated) + { + ++eliminated; - if ( eliminated == (Participants.Count - 1) ) - hasWinner = true; - } - else - { - winner = p; - } - } + if (eliminated == Participants.Count - 1) + hasWinner = true; + } + else + { + winner = p; + } + } - if ( hasWinner ) - return winner ?? (Participant) Participants[0]; + if (hasWinner) + return winner ?? (Participant)Participants[0]; - return null; - } + return null; + } - private Timer m_Countdown; + public void StartCountdown(int count, CountdownCallback cb) + { + cb(count); + m_Countdown = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0), count, + new TimerStateCallback(Countdown_Callback), new object[] { count - 1, cb }); + } - public void StartCountdown( int count, CountdownCallback cb ) - { - cb(count); - m_Countdown=Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ), count, new TimerStateCallback( Countdown_Callback ), new object[]{ count-1, cb } ); - } + public void StopCountdown() + { + m_Countdown?.Stop(); - public void StopCountdown() - { - m_Countdown?.Stop(); + m_Countdown = null; + } - m_Countdown = null; - } + private void Countdown_Callback(object state) + { + object[] states = (object[])state; - private void Countdown_Callback( object state ) - { - object[] states = (object[])state; + int count = (int)states[0]; + CountdownCallback cb = (CountdownCallback)states[1]; - int count = (int)states[0]; - CountdownCallback cb = (CountdownCallback)states[1]; + if (count == 0) + { + m_Countdown?.Stop(); - if ( count==0 ) - { - m_Countdown?.Stop(); + m_Countdown = null; + } - m_Countdown=null; - } + cb(count); - cb( count ); + states[0] = count - 1; + } - states[0] = count - 1; - } + public void StopSDTimers() + { + m_SDWarnTimer?.Stop(); - private Timer m_AutoTieTimer; + m_SDWarnTimer = null; - public bool Tied { get; private set; } + m_SDActivateTimer?.Stop(); - public bool IsSuddenDeath { get; set; } + m_SDActivateTimer = null; + } - private Timer m_SDWarnTimer, m_SDActivateTimer; + public void StartSuddenDeath(TimeSpan timeUntilActive) + { + m_SDWarnTimer?.Stop(); - public void StopSDTimers() - { - m_SDWarnTimer?.Stop(); + m_SDWarnTimer = Timer.DelayCall(TimeSpan.FromMinutes(timeUntilActive.TotalMinutes * 0.9), WarnSuddenDeath); - m_SDWarnTimer = null; + m_SDActivateTimer?.Stop(); - m_SDActivateTimer?.Stop(); + m_SDActivateTimer = Timer.DelayCall(timeUntilActive, ActivateSuddenDeath); + } - m_SDActivateTimer = null; - } + public void WarnSuddenDeath() + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - public void StartSuddenDeath( TimeSpan timeUntilActive ) - { - m_SDWarnTimer?.Stop(); + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - m_SDWarnTimer = Timer.DelayCall( TimeSpan.FromMinutes( timeUntilActive.TotalMinutes * 0.9 ), WarnSuddenDeath ); + if (pl == null || pl.Eliminated) + continue; - m_SDActivateTimer?.Stop(); + pl.Mobile.SendSound(0x1E1); + pl.Mobile.SendMessage(0x22, "Warning! Warning! Warning!"); + pl.Mobile.SendMessage(0x22, "Sudden death will be active soon!"); + } + } - m_SDActivateTimer = Timer.DelayCall( timeUntilActive, ActivateSuddenDeath ); - } + m_Tournament?.Alert(Arena, "Sudden death will be active soon!"); - public void WarnSuddenDeath() - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + m_SDWarnTimer?.Stop(); - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + m_SDWarnTimer = null; + } - if ( pl == null || pl.Eliminated ) - continue; + public static bool CheckSuddenDeath(Mobile mob) + { + return mob is PlayerMobile pm && pm.DuelPlayer?.Eliminated == false && pm.DuelContext?.IsSuddenDeath == true; + } - pl.Mobile.SendSound( 0x1E1 ); - pl.Mobile.SendMessage( 0x22, "Warning! Warning! Warning!" ); - pl.Mobile.SendMessage( 0x22, "Sudden death will be active soon!" ); - } - } + public void ActivateSuddenDeath() + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - m_Tournament?.Alert( Arena, "Sudden death will be active soon!" ); + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - m_SDWarnTimer?.Stop(); + if (pl == null || pl.Eliminated) + continue; - m_SDWarnTimer = null; - } + pl.Mobile.SendSound(0x1E1); + pl.Mobile.SendMessage(0x22, "Warning! Warning! Warning!"); + pl.Mobile.SendMessage(0x22, + "Sudden death has ACTIVATED. You are now unable to perform any beneficial actions."); + } + } - public static bool CheckSuddenDeath( Mobile mob ) - { - return mob is PlayerMobile pm && pm.DuelPlayer?.Eliminated == false && pm.DuelContext?.IsSuddenDeath == true; - } + m_Tournament?.Alert(Arena, "Sudden death has been activated!"); - public void ActivateSuddenDeath() - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + IsSuddenDeath = true; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + m_SDActivateTimer?.Stop(); - if ( pl == null || pl.Eliminated ) - continue; + m_SDActivateTimer = null; + } - pl.Mobile.SendSound( 0x1E1 ); - pl.Mobile.SendMessage( 0x22, "Warning! Warning! Warning!" ); - pl.Mobile.SendMessage( 0x22, "Sudden death has ACTIVATED. You are now unable to perform any beneficial actions." ); - } - } + public void BeginAutoTie() + { + m_AutoTieTimer?.Stop(); - m_Tournament?.Alert( Arena, "Sudden death has been activated!" ); + TimeSpan ts = m_Tournament == null || m_Tournament.TournyType == TournyType.Standard + ? AutoTieDelay + : TimeSpan.FromMinutes(90.0); - IsSuddenDeath = true; + m_AutoTieTimer = Timer.DelayCall(ts, InvokeAutoTie); + } - m_SDActivateTimer?.Stop(); + public void EndAutoTie() + { + m_AutoTieTimer?.Stop(); - m_SDActivateTimer = null; - } + m_AutoTieTimer = null; + } - public void BeginAutoTie() - { - m_AutoTieTimer?.Stop(); + public void InvokeAutoTie() + { + m_AutoTieTimer = null; - TimeSpan ts = ( m_Tournament == null || m_Tournament.TournyType == TournyType.Standard ) - ? AutoTieDelay - : TimeSpan.FromMinutes( 90.0 ); + if (!Started || Finished) + return; - m_AutoTieTimer = Timer.DelayCall( ts, InvokeAutoTie ); - } + Tied = true; + Finished = true; - public void EndAutoTie() - { - m_AutoTieTimer?.Stop(); + StopSDTimers(); - m_AutoTieTimer = null; - } + ArrayList remaining = new ArrayList(); - public void InvokeAutoTie() - { - m_AutoTieTimer = null; + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - if ( !Started || Finished ) - return; + if (p.Eliminated) + { + p.Broadcast(0x22, null, + p.Players.Length == 1 ? "{0} has lost the duel." : "{0} and {1} team have lost the duel.", + p.Players.Length == 1 ? "You have lost the duel." : "Your team has lost the duel."); + } + else + { + p.Broadcast(0x59, null, + p.Players.Length == 1 + ? "{0} has tied the duel due to time expiration." + : "{0} and {1} team have tied the duel due to time expiration.", + p.Players.Length == 1 + ? "You have tied the duel due to time expiration." + : "Your team has tied the duel due to time expiration."); + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + if (pl != null && !pl.Eliminated) + DelayBounce(TimeSpan.FromSeconds(8.0), pl.Mobile, null); + } + + if (p.TournyPart != null) + remaining.Add(p.TournyPart); + } + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + if (pl != null) + { + pl.Mobile.Delta(MobileDelta.Noto); + pl.Mobile.SendEverything(); + } + } + } + + m_Tournament?.HandleTie(Arena, m_Match, remaining); + + Timer.DelayCall(TimeSpan.FromSeconds(10.0), Unregister); + } + + public static void Initialize() + { + EventSink.Speech += EventSink_Speech; + EventSink.Login += EventSink_Login; + + CommandSystem.Register("vli", AccessLevel.GameMaster, vli_oc); + } + + private static void vli_oc(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, vli_ot); + } + + private static void vli_ot(Mobile from, object obj) + { + if (obj is PlayerMobile pm) + { + Ladder ladder = Ladder.Instance; + + if (ladder == null) + return; + + LadderEntry entry = ladder.Find(pm); + + if (entry != null) + from.SendGump(new PropertiesGump(from, entry)); + } + } + + public static bool CheckCombat(Mobile m) + { + for (int i = 0; i < m.Aggressed.Count; ++i) + { + AggressorInfo info = m.Aggressed[i]; + + if (info.Defender.Player && DateTime.UtcNow - info.LastCombatTime < CombatDelay) + return true; + } + + for (int i = 0; i < m.Aggressors.Count; ++i) + { + AggressorInfo info = m.Aggressors[i]; + + if (info.Attacker.Player && DateTime.UtcNow - info.LastCombatTime < CombatDelay) + return true; + } + + return false; + } + + private static void EventSink_Login(LoginEventArgs e) + { + if (!(e.Mobile is PlayerMobile pm)) + return; + + DuelContext dc = pm.DuelContext; + + if (dc == null) + return; + + if (dc.ReadyWait && pm.DuelPlayer.Ready && !dc.Started && !dc.StartedBeginCountdown && !dc.Finished) + { + if (dc.m_Tournament == null) + pm.SendGump(new ReadyGump(pm, dc, dc.ReadyCount)); + } + else if (dc.ReadyWait && !dc.StartedBeginCountdown && !dc.Started && !dc.Finished) + { + if (dc.m_Tournament == null) + pm.SendGump(new ReadyUpGump(pm, dc)); + } + else if (dc.Initiator == pm && !dc.ReadyWait && !dc.StartedBeginCountdown && !dc.Started && !dc.Finished) + { + pm.SendGump(new DuelContextGump(pm, dc)); + } + } + + private static void ViewLadder_OnTarget(Mobile from, object obj, object state) + { + if (obj is PlayerMobile pm) + { + Ladder ladder = (Ladder)state; + + LadderEntry entry = ladder.Find(pm); + + if (entry == null) + return; // sanity + + string text = + $"{{0}} are ranked {LadderGump.Rank(entry.Index + 1)} at level {Ladder.GetLevel(entry.Experience)}."; + + pm.PrivateOverheadMessage(MessageType.Regular, pm.SpeechHue, true, + string.Format(text, from == pm ? "You" : "They"), from.NetState); + } + else if (obj is Mobile mob) + { + if (mob.Body.IsHuman) + mob.PrivateOverheadMessage(MessageType.Regular, mob.SpeechHue, false, + "I'm not a duelist, and quite frankly, I resent the implication.", from.NetState); + else + mob.PrivateOverheadMessage(MessageType.Regular, 0x3B2, true, "It's probably better than you.", + from.NetState); + } + else + { + from.SendMessage("That's not a player."); + } + } + + private static void EventSink_Speech(SpeechEventArgs e) + { + if (e.Handled) + return; + + if (!(e.Mobile is PlayerMobile pm)) + return; + + if (Insensitive.Contains(e.Speech, "i wish to duel")) + { + if (!pm.CheckAlive()) + { + } + else if (pm.Region.IsPartOf(typeof(Jail))) + { + } + else if (CheckCombat(pm)) + { + e.Mobile.SendMessage(0x22, + "You have recently been in combat with another player and must wait before starting a duel."); + } + else if (pm.DuelContext != null) + { + if (pm.DuelContext.Initiator == pm) + e.Mobile.SendMessage(0x22, "You have already started a duel."); + else + e.Mobile.SendMessage(0x22, "You have already been challenged in a duel."); + } + else if (TournamentController.IsActive) + { + e.Mobile.SendMessage(0x22, "You may not start a duel while a tournament is active."); + } + else + { + pm.SendGump(new DuelContextGump(pm, new DuelContext(pm, RulesetLayout.Root))); + e.Handled = true; + } + } + else if (Insensitive.Equals(e.Speech, "change arena preferences")) + { + if (!pm.CheckAlive()) + { + } + else + { + Preferences prefs = Preferences.Instance; + + if (prefs != null) + { + e.Mobile.CloseGump(typeof(PreferencesGump)); + e.Mobile.SendGump(new PreferencesGump(e.Mobile, prefs)); + } + } + } + else if (Insensitive.Equals(e.Speech, "showladder")) + { + e.Blocked = true; + if (!pm.CheckAlive()) + { + } + else + { + Ladder instance = Ladder.Instance; + + if (instance == null) + { + //pm.SendMessage( "Ladder not yet initialized." ); + } + else + { + LadderEntry entry = instance.Find(pm); + + if (entry == null) + return; // sanity + + string text = + $"{{0}} {{1}} ranked {LadderGump.Rank(entry.Index + 1)} at level {Ladder.GetLevel(entry.Experience)}."; + + pm.LocalOverheadMessage(MessageType.Regular, pm.SpeechHue, true, string.Format(text, "You", "are")); + pm.NonlocalOverheadMessage(MessageType.Regular, pm.SpeechHue, true, + string.Format(text, pm.Name, "is")); + + //pm.PublicOverheadMessage( MessageType.Regular, pm.SpeechHue, true, String.Format( "Level {0} with {1} win{2} and {3} loss{4}.", Ladder.GetLevel( entry.Experience ), entry.Wins, entry.Wins==1?"":"s", entry.Losses, entry.Losses==1?"":"es" ) ); + //pm.PublicOverheadMessage( MessageType.Regular, pm.SpeechHue, true, String.Format( "Level {0} with {1} win{2} and {3} loss{4}.", Ladder.GetLevel( entry.Experience ), entry.Wins, entry.Wins==1?"":"s", entry.Losses, entry.Losses==1?"":"es" ) ); + } + } + } + else if (Insensitive.Equals(e.Speech, "viewladder")) + { + e.Blocked = true; + + if (!pm.CheckAlive()) + { + } + else + { + Ladder instance = Ladder.Instance; + + if (instance == null) + { + //pm.SendMessage( "Ladder not yet initialized." ); + } + else + { + pm.SendMessage("Target a player to view their ranking and level."); + pm.BeginTarget(16, false, TargetFlags.None, new TargetStateCallback(ViewLadder_OnTarget), instance); + } + } + } + else if (Insensitive.Contains(e.Speech, "i yield")) + { + if (!pm.CheckAlive()) + { + } + else if (pm.DuelContext == null) + { + } + else if (pm.DuelContext.Finished) + { + e.Mobile.SendMessage(0x22, "The duel is already finished."); + } + else if (!pm.DuelContext.Started) + { + DuelContext dc = pm.DuelContext; + Mobile init = dc.Initiator; + + if (pm.DuelContext.StartedBeginCountdown) + { + e.Mobile.SendMessage(0x22, "The duel has not yet started."); + } + else + { + DuelPlayer pl = pm.DuelContext.Find(pm); + + if (pl == null) + return; + + Participant p = pl.Participant; + + if (!pm.DuelContext.ReadyWait) // still setting stuff up + { + p.Broadcast(0x22, null, "{0} has yielded.", "You have yielded."); + + if (init == pm) + { + dc.Unregister(); + } + else + { + p.Nullify(pl); + pm.DuelPlayer = null; + + NetState ns = init.NetState; + + if (ns != null) + foreach (Gump g in ns.Gumps) + { + if (g is ParticipantGump pg && pg.Participant == p) + { + init.SendGump(new ParticipantGump(init, dc, p)); + break; + } + + if (g is DuelContextGump dcg && dcg.Context == dc) + { + init.SendGump(new DuelContextGump(init, dc)); + break; + } + } + } + } + else if (!pm.DuelContext.StartedReadyCountdown) // at ready stage + { + p.Broadcast(0x22, null, "{0} has yielded.", "You have yielded."); + + dc.m_Yielding = true; + dc.RejectReady(pm, null); + dc.m_Yielding = false; + + if (init == pm) + { + dc.Unregister(); + } + else if (dc.Registered) + { + p.Nullify(pl); + pm.DuelPlayer = null; + + NetState ns = init.NetState; + + if (ns != null) + { + bool send = true; + + foreach (Gump g in ns.Gumps) + { + if (g is ParticipantGump pg && pg.Participant == p) + { + init.SendGump(new ParticipantGump(init, dc, p)); + send = false; + break; + } + + if (g is DuelContextGump dcg && dcg.Context == dc) + { + init.SendGump(new DuelContextGump(init, dc)); + send = false; + break; + } + } + + if (send) + init.SendGump(new DuelContextGump(init, dc)); + } + } + } + else + { + pm.DuelContext.m_Countdown?.Stop(); + pm.DuelContext.m_Countdown = null; + + pm.DuelContext.StartedReadyCountdown = false; + p.Broadcast(0x22, null, "{0} has yielded.", "You have yielded."); + + dc.m_Yielding = true; + dc.RejectReady(pm, null); + dc.m_Yielding = false; + + if (init == pm) + { + dc.Unregister(); + } + else if (dc.Registered) + { + p.Nullify(pl); + pm.DuelPlayer = null; + + NetState ns = init.NetState; + + if (ns != null) + { + bool send = true; + + foreach (Gump g in ns.Gumps) + { + if (g is ParticipantGump pg && pg.Participant == p) + { + init.SendGump(new ParticipantGump(init, dc, p)); + send = false; + break; + } + + if (g is DuelContextGump dcg && dcg.Context == dc) + { + init.SendGump(new DuelContextGump(init, dc)); + send = false; + break; + } + } + + if (send) + init.SendGump(new DuelContextGump(init, dc)); + } + } + } + } + } + else + { + DuelPlayer pl = pm.DuelContext.Find(pm); + + if (pl != null) + { + if (pm.DuelContext.IsOneVsOne) + { + e.Mobile.SendMessage(0x22, "You may not yield a 1 on 1 match."); + } + else if (pl.Eliminated) + { + e.Mobile.SendMessage(0x22, "You have already been eliminated."); + } + else + { + pm.LocalOverheadMessage(MessageType.Regular, 0x22, false, "You have yielded."); + pm.NonlocalOverheadMessage(MessageType.Regular, 0x22, false, $"{pm.Name} has yielded."); + + pm.DuelContext.m_Yielding = true; + pm.Kill(); + pm.DuelContext.m_Yielding = false; + + if (pm.Alive) // invul, ... + { + pl.Eliminated = true; + + pm.DuelContext.RemoveAggressions(pm); + pm.DuelContext.SendOutside(pm); + pm.DuelContext.Refresh(pm, null); + Debuff(pm); + CancelSpell(pm); + pm.Frozen = false; + + Participant winner = pm.DuelContext.CheckCompletion(); + + if (winner != null) + pm.DuelContext.Finish(winner); + } + } + } + else + { + e.Mobile.SendMessage(0x22, "BUG: Unable to find duel context."); + } + } + } + } + + public void CloseAllGumps() + { + Type[] types = { typeof(DuelContextGump), typeof(ParticipantGump), typeof(RulesetGump) }; + int[] defs = { -1, -1, -1 }; + + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + if (pl == null) + continue; + + Mobile mob = pl.Mobile; + + for (int k = 0; k < types.Length; ++k) + mob.CloseGump(types[k]); + //mob.CloseGump( types[k], defs[k] ); + } + } + } + + public void RejectReady(Mobile rejector, string page) + { + if (StartedReadyCountdown) + return; // sanity + + Type[] types = { typeof(DuelContextGump), typeof(ReadyUpGump), typeof(ReadyGump) }; + int[] defs = { -1, -1, -1 }; + + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + if (pl == null) + continue; + + pl.Ready = false; + + Mobile mob = pl.Mobile; + + if (page == null) // yield + { + if (mob != rejector) + mob.SendMessage(0x22, "{0} has yielded.", rejector.Name); + } + else + { + if (mob == rejector) + mob.SendMessage(0x22, "You have rejected the {0}.", Rematch ? "rematch" : page); + else + mob.SendMessage(0x22, "{0} has rejected the {1}.", rejector.Name, Rematch ? "rematch" : page); + } + + for (int k = 0; k < types.Length; ++k) + mob.CloseGump(types[k]); + //mob.CloseGump( types[k], defs[k] ); + } + } + + if (Rematch) + Unregister(); + else if (!m_Yielding) + Initiator.SendGump(new DuelContextGump(Initiator, this)); + + ReadyWait = false; + ReadyCount = 0; + } + + public void SendReadyGump() + { + SendReadyGump(-1); + } + + public static void Debuff(Mobile mob) + { + mob.RemoveStatMod("[Magic] Str Offset"); + mob.RemoveStatMod("[Magic] Dex Offset"); + mob.RemoveStatMod("[Magic] Int Offset"); + mob.RemoveStatMod("Concussion"); + mob.RemoveStatMod("blood-rose"); + mob.RemoveStatMod("clarity-potion"); + + OrangePetals.RemoveContext(mob); + + mob.Paralyzed = false; + mob.Hidden = false; + + if (!Core.AOS) + { + mob.MagicDamageAbsorb = 0; + mob.MeleeDamageAbsorb = 0; + ProtectionSpell.Registry.Remove(mob); + + ArchProtectionSpell.RemoveEntry(mob); + + mob.EndAction(typeof(DefensiveSpell)); + } + + TransformationSpellHelper.RemoveContext(mob, true); + AnimalForm.RemoveContext(mob, true); + + if (DisguiseTimers.IsDisguised(mob)) + DisguiseTimers.StopTimer(mob); + + if (!mob.CanBeginAction(typeof(PolymorphSpell))) + { + mob.BodyMod = 0; + mob.HueMod = -1; + mob.EndAction(typeof(PolymorphSpell)); + } + + BaseArmor.ValidateMobile(mob); + BaseClothing.ValidateMobile(mob); + + mob.Hits = mob.HitsMax; + mob.Stam = mob.StamMax; + mob.Mana = mob.ManaMax; + + mob.Poison = null; + } + + public static void CancelSpell(Mobile mob) + { + if (mob.Spell is Spell spell) + spell.Disturb(DisturbType.Kill); + + Target.Cancel(mob); + } + + public void DestroyWall() + { + for (int i = 0; i < m_Walls.Count; ++i) + ((Item)m_Walls[i]).Delete(); + + m_Walls.Clear(); + } + + public void CreateWall() + { + if (Arena == null) + return; + + Point3D start = Arena.Points.EdgeWest; + Point3D wall = Arena.Wall; + + int dx = start.X - wall.X; + int dy = start.Y - wall.Y; + int rx = dx - dy; + int ry = dx + dy; + + bool eastToWest; + + if (rx >= 0 && ry >= 0) + eastToWest = false; + else if (rx >= 0) + eastToWest = true; + else if (ry >= 0) + eastToWest = true; + else + eastToWest = false; + + Effects.PlaySound(wall, Arena.Facet, 0x1F6); + + for (int i = -1; i <= 1; ++i) + { + Point3D loc = new Point3D(eastToWest ? wall.X + i : wall.X, eastToWest ? wall.Y : wall.Y + i, wall.Z); + + InternalWall created = new InternalWall(); + + created.Appear(loc, Arena.Facet); + + m_Walls.Add(created); + } + } + + public void BuildParties() + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + if (p.Players.Length > 1) + { + ArrayList players = new ArrayList(); + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; + + if (dp == null) + continue; + + players.Add(dp.Mobile); + } + + if (players.Count > 1) + for (int leaderIndex = 0; leaderIndex + 1 < players.Count; leaderIndex += Party.Capacity) + { + Mobile leader = (Mobile)players[leaderIndex]; + Party party = Party.Get(leader); + + if (party == null) + { + leader.Party = party = new Party(leader); + } + else if (party.Leader != leader) + { + party.SendPublicMessage(leader, "I leave this party to fight in a duel."); + party.Remove(leader); + leader.Party = party = new Party(leader); + } + + for (int j = leaderIndex + 1; j < players.Count && j < leaderIndex + Party.Capacity; ++j) + { + Mobile player = (Mobile)players[j]; + Party existing = Party.Get(player); + + if (existing == party) + continue; + + if (party.Members.Count + party.Candidates.Count >= Party.Capacity) + { + player.SendMessage( + "You could not be added to the team party because it is at full capacity."); + leader.SendMessage( + "{0} could not be added to the team party because it is at full capacity."); + } + else + { + if (existing != null) + { + existing.SendPublicMessage(player, "I leave this party to fight in a duel."); + existing.Remove(player); + } + + party.OnAccept(player, true); + } + } + } + } + } + } + + public void ClearIllegalItems() + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + if (pl == null) + continue; + + ClearIllegalItems(pl.Mobile); + } + } + } + + public void ClearIllegalItems(Mobile mob) + { + if (mob.StunReady && !AllowSpecialAbility(mob, "Stun", false)) + mob.StunReady = false; + + if (mob.DisarmReady && !AllowSpecialAbility(mob, "Disarm", false)) + mob.DisarmReady = false; + + Container pack = mob.Backpack; + + if (pack == null) + return; + + for (int i = mob.Items.Count - 1; i >= 0; --i) + { + if (i >= mob.Items.Count) + continue; // sanity + + Item item = mob.Items[i]; + + if (!CheckItemEquip(mob, item)) + { + pack.DropItem(item); + + if (item is BaseWeapon) + mob.SendLocalizedMessage(1062001, + item.Name ?? "#" + item.LabelNumber); // You can no longer wield your ~1_WEAPON~ + else if (item is BaseArmor && !(item is BaseShield)) + mob.SendLocalizedMessage(1062002, + item.Name ?? "#" + item.LabelNumber); // You can no longer wear your ~1_ARMOR~ + else + mob.SendLocalizedMessage(1062003, + item.Name ?? "#" + item.LabelNumber); // You can no longer equip your ~1_SHIELD~ + } + } + + Item inHand = mob.Holding; + + if (inHand != null && !CheckItemEquip(mob, inHand)) + { + mob.Holding = null; + + BounceInfo bi = inHand.GetBounce(); + + if (bi.m_Parent == mob) + pack.DropItem(inHand); + else + inHand.Bounce(mob); + + inHand.ClearBounce(); + } + } + + private void MessageRuleset(Mobile mob) + { + if (Ruleset == null) return; + + Ruleset ruleset = Ruleset; + Ruleset basedef = ruleset.Base; + + mob.SendMessage("Ruleset: {0}", basedef.Title); + + BitArray defs; + + if (ruleset.Flavors.Count > 0) + { + defs = new BitArray(basedef.Options); + + for (int i = 0; i < ruleset.Flavors.Count; ++i) + { + defs.Or(((Ruleset)ruleset.Flavors[i]).Options); + + mob.SendMessage(" + {0}", ((Ruleset)ruleset.Flavors[i]).Title); + } + } + else + { + defs = basedef.Options; + } + + int changes = 0; + + BitArray opts = ruleset.Options; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + { + string name = ruleset.Layout.FindByIndex(i); + + if (name != null) // sanity + { + ++changes; + + if (changes == 1) mob.SendMessage("Modifications:"); + + mob.SendMessage("{0}: {1}", name, opts[i] ? "enabled" : "disabled"); + } + } + } + + public void SendBeginGump(int count) + { + if (!Registered || Finished) + return; + + if (count == 10) + { + CreateWall(); + BuildParties(); + ClearIllegalItems(); + } + else if (count == 0) + { + DestroyWall(); + } + + StartedBeginCountdown = true; + + if (count == 0) + { + Started = true; + BeginAutoTie(); + } + + Type[] types = { typeof(ReadyGump), typeof(ReadyUpGump), typeof(BeginGump) }; + + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + if (pl == null) + continue; + + Mobile mob = pl.Mobile; + + if (count > 0) + { + if (count == 10) + CloseAndSendGump(mob, new BeginGump(count), types); + + mob.Frozen = true; + } + else + { + mob.CloseGump(typeof(BeginGump)); + mob.Frozen = false; + } + } + } + } + + public void RemoveAggressions(Mobile mob) + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; + + if (dp == null || dp.Mobile == mob) + continue; + + mob.RemoveAggressed(dp.Mobile); + mob.RemoveAggressor(dp.Mobile); + dp.Mobile.RemoveAggressed(mob); + dp.Mobile.RemoveAggressor(mob); + } + } + } + + public void SendReadyUpGump() + { + if (!Registered) + return; + + ReadyWait = true; + ReadyCount = -1; + + Type[] types = { typeof(ReadyUpGump) }; + + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; + + Mobile mob = pl?.Mobile; + + if (mob != null) + if (m_Tournament == null) + CloseAndSendGump(mob, new ReadyUpGump(mob, this), types); + } + } + } + + public string ValidateStart() + { + if (m_Tournament == null && TournamentController.IsActive) + return "a tournament is active"; + + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; - Tied = true; - Finished = true; + if (dp == null) + return "a slot is empty"; + + if (dp.Mobile.Region.IsPartOf(typeof(Jail))) + return $"{dp.Mobile.Name} is in jail"; + + if (Sigil.ExistsOn(dp.Mobile)) + return $"{dp.Mobile.Name} is holding a sigil"; + + if (!dp.Mobile.Alive) + { + if (m_Tournament == null) + return $"{dp.Mobile.Name} is dead"; + dp.Mobile.Resurrect(); + } + + if (m_Tournament == null && CheckCombat(dp.Mobile)) + return $"{dp.Mobile.Name} is in combat"; + + if (dp.Mobile.Mounted) + { + IMount mount = dp.Mobile.Mount; + + if (m_Tournament != null && mount != null) + mount.Rider = null; + else + return $"{dp.Mobile.Name} is mounted"; + } + } + } + + return null; + } + + public void SendReadyGump(int count) + { + if (!Registered) + return; + + if (count != -1) + StartedReadyCountdown = true; + + ReadyCount = count; + + if (count == 0) + { + string error = ValidateStart(); - StopSDTimers(); + if (error != null) + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - ArrayList remaining = new ArrayList(); + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + dp?.Mobile.SendMessage("The duel could not be started because {0}.", error); + } + } - if ( p.Eliminated ) - { - p.Broadcast( 0x22, null, p.Players.Length == 1 ? "{0} has lost the duel." : "{0} and {1} team have lost the duel.", p.Players.Length == 1 ? "You have lost the duel." : "Your team has lost the duel." ); - } - else - { - p.Broadcast( 0x59, null, p.Players.Length == 1 ? "{0} has tied the duel due to time expiration." : "{0} and {1} team have tied the duel due to time expiration.", p.Players.Length == 1 ? "You have tied the duel due to time expiration." : "Your team has tied the duel due to time expiration." ); + StartCountdown(10, SendReadyGump); - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + return; + } - if ( pl != null && !pl.Eliminated ) - DelayBounce( TimeSpan.FromSeconds( 8.0 ), pl.Mobile, null ); - } + ReadyWait = false; - if ( p.TournyPart != null ) - remaining.Add( p.TournyPart ); - } + List players = new List(); - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - if ( pl != null ) - { - pl.Mobile.Delta( MobileDelta.Noto ); - pl.Mobile.SendEverything(); - } - } - } - - m_Tournament?.HandleTie( Arena, m_Match, remaining ); - - Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), Unregister ); - } - - public bool IsOneVsOne - { - get - { - if ( Participants.Count != 2 ) - return false; + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; - if ( ((Participant)Participants[0]).Players.Length != 1 ) - return false; + if (dp != null) + players.Add(dp.Mobile); + } + } - if ( ((Participant)Participants[1]).Players.Length != 1 ) - return false; - - return true; - } - } - - public static void Initialize() - { - EventSink.Speech += EventSink_Speech; - EventSink.Login += EventSink_Login; - - CommandSystem.Register( "vli", AccessLevel.GameMaster, vli_oc ); - } - - private static void vli_oc( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, Targeting.TargetFlags.None, vli_ot ); - } - - private static void vli_ot( Mobile from, object obj ) - { - if ( obj is PlayerMobile pm ) - { - Ladder ladder = Ladder.Instance; - - if ( ladder == null ) - return; - - LadderEntry entry = ladder.Find( pm ); - - if ( entry != null ) - from.SendGump( new PropertiesGump( from, entry ) ); - } - } - - private static TimeSpan CombatDelay = TimeSpan.FromSeconds( 30.0 ); - private static TimeSpan AutoTieDelay = TimeSpan.FromMinutes( 15.0 ); - - public static bool CheckCombat( Mobile m ) - { - for ( int i = 0; i < m.Aggressed.Count; ++i ) - { - AggressorInfo info = m.Aggressed[i]; - - if ( info.Defender.Player && (DateTime.UtcNow - info.LastCombatTime) < CombatDelay ) - return true; - } - - for ( int i = 0; i < m.Aggressors.Count; ++i ) - { - AggressorInfo info = m.Aggressors[i]; - - if ( info.Attacker.Player && (DateTime.UtcNow - info.LastCombatTime) < CombatDelay ) - return true; - } - - return false; - } - - private static void EventSink_Login( LoginEventArgs e ) - { - if ( !(e.Mobile is PlayerMobile pm) ) - return; - - DuelContext dc = pm.DuelContext; - - if ( dc == null ) - return; - - if ( dc.ReadyWait && pm.DuelPlayer.Ready && !dc.Started && !dc.StartedBeginCountdown && !dc.Finished ) - { - if ( dc.m_Tournament == null ) - pm.SendGump( new ReadyGump( pm, dc, dc.ReadyCount ) ); - } - else if ( dc.ReadyWait && !dc.StartedBeginCountdown && !dc.Started && !dc.Finished ) - { - if ( dc.m_Tournament == null ) - pm.SendGump( new ReadyUpGump( pm, dc ) ); - } - else if ( dc.Initiator == pm && !dc.ReadyWait && !dc.StartedBeginCountdown && !dc.Started && !dc.Finished ) - pm.SendGump( new DuelContextGump( pm, dc ) ); - } - - private static void ViewLadder_OnTarget( Mobile from, object obj, object state ) - { - if ( obj is PlayerMobile pm ) - { - Ladder ladder = (Ladder)state; - - LadderEntry entry = ladder.Find( pm ); - - if ( entry == null ) - return; // sanity - - string text = - $"{{0}} are ranked {LadderGump.Rank(entry.Index + 1)} at level {Ladder.GetLevel(entry.Experience)}."; - - pm.PrivateOverheadMessage( MessageType.Regular, pm.SpeechHue, true, string.Format( text, from==pm?"You":"They" ), from.NetState ); - } - else if ( obj is Mobile mob ) - { - if ( mob.Body.IsHuman ) - mob.PrivateOverheadMessage( MessageType.Regular, mob.SpeechHue, false, "I'm not a duelist, and quite frankly, I resent the implication.", from.NetState ); - else - mob.PrivateOverheadMessage( MessageType.Regular, 0x3B2, true, "It's probably better than you.", from.NetState ); - } - else - { - from.SendMessage( "That's not a player." ); - } - } - - private static void EventSink_Speech( SpeechEventArgs e ) - { - if ( e.Handled ) - return; - - if ( !(e.Mobile is PlayerMobile pm) ) - return; - - if ( Insensitive.Contains( e.Speech, "i wish to duel" ) ) - { - if ( !pm.CheckAlive() ) - { - } - else if ( pm.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - } - else if ( CheckCombat( pm ) ) - { - e.Mobile.SendMessage( 0x22, "You have recently been in combat with another player and must wait before starting a duel." ); - } - else if ( pm.DuelContext != null ) - { - if ( pm.DuelContext.Initiator == pm ) - e.Mobile.SendMessage( 0x22, "You have already started a duel." ); - else - e.Mobile.SendMessage( 0x22, "You have already been challenged in a duel." ); - } - else if ( TournamentController.IsActive ) - { - e.Mobile.SendMessage( 0x22, "You may not start a duel while a tournament is active." ); - } - else - { - pm.SendGump( new DuelContextGump( pm, new DuelContext( pm, RulesetLayout.Root ) ) ); - e.Handled = true; - } - } - else if ( Insensitive.Equals( e.Speech, "change arena preferences" ) ) - { - if ( !pm.CheckAlive() ) - { - } - else - { - Preferences prefs = Preferences.Instance; - - if ( prefs != null ) - { - e.Mobile.CloseGump( typeof( PreferencesGump ) ); - e.Mobile.SendGump( new PreferencesGump( e.Mobile, prefs ) ); - } - } - } - else if ( Insensitive.Equals( e.Speech, "showladder" ) ) - { - e.Blocked=true; - if ( !pm.CheckAlive() ) - { - } - else - { - Ladder instance = Ladder.Instance; - - if ( instance == null ) - { - //pm.SendMessage( "Ladder not yet initialized." ); - } - else - { - LadderEntry entry = instance.Find( pm ); - - if ( entry == null ) - return; // sanity - - string text = - $"{{0}} {{1}} ranked {LadderGump.Rank(entry.Index + 1)} at level {Ladder.GetLevel(entry.Experience)}."; - - pm.LocalOverheadMessage( MessageType.Regular, pm.SpeechHue, true, string.Format( text, "You", "are" ) ); - pm.NonlocalOverheadMessage( MessageType.Regular, pm.SpeechHue, true, string.Format( text, pm.Name, "is" ) ); - - //pm.PublicOverheadMessage( MessageType.Regular, pm.SpeechHue, true, String.Format( "Level {0} with {1} win{2} and {3} loss{4}.", Ladder.GetLevel( entry.Experience ), entry.Wins, entry.Wins==1?"":"s", entry.Losses, entry.Losses==1?"":"es" ) ); - //pm.PublicOverheadMessage( MessageType.Regular, pm.SpeechHue, true, String.Format( "Level {0} with {1} win{2} and {3} loss{4}.", Ladder.GetLevel( entry.Experience ), entry.Wins, entry.Wins==1?"":"s", entry.Losses, entry.Losses==1?"":"es" ) ); - } - } - } - else if ( Insensitive.Equals( e.Speech, "viewladder" ) ) - { - e.Blocked=true; - - if ( !pm.CheckAlive() ) - { - } - else - { - Ladder instance = Ladder.Instance; - - if ( instance == null ) - { - //pm.SendMessage( "Ladder not yet initialized." ); - } - else - { - pm.SendMessage( "Target a player to view their ranking and level." ); - pm.BeginTarget( 16, false, Targeting.TargetFlags.None, new TargetStateCallback( ViewLadder_OnTarget ), instance ); - } - } - } - else if ( Insensitive.Contains( e.Speech, "i yield" ) ) - { - if ( !pm.CheckAlive() ) - { - } - else if ( pm.DuelContext == null ) - { - } - else if ( pm.DuelContext.Finished ) - { - e.Mobile.SendMessage( 0x22, "The duel is already finished." ); - } - else if ( !pm.DuelContext.Started ) - { - DuelContext dc = pm.DuelContext; - Mobile init = dc.Initiator; - - if ( pm.DuelContext.StartedBeginCountdown ) - { - e.Mobile.SendMessage( 0x22, "The duel has not yet started." ); - } - else - { - DuelPlayer pl = pm.DuelContext.Find( pm ); - - if ( pl == null ) - return; - - Participant p = pl.Participant; - - if ( !pm.DuelContext.ReadyWait ) // still setting stuff up - { - p.Broadcast( 0x22, null, "{0} has yielded.", "You have yielded." ); - - if ( init == pm ) - { - dc.Unregister(); - } - else - { - p.Nullify( pl ); - pm.DuelPlayer=null; - - NetState ns = init.NetState; - - if ( ns != null ) - { - foreach ( Gump g in ns.Gumps ) - { - if (g is ParticipantGump pg && pg.Participant == p) - { - init.SendGump( new ParticipantGump( init, dc, p ) ); - break; - } - if ( g is DuelContextGump dcg && dcg.Context == dc ) - { - init.SendGump( new DuelContextGump( init, dc ) ); - break; - } - } - } - } - } - else if ( !pm.DuelContext.StartedReadyCountdown ) // at ready stage - { - p.Broadcast( 0x22, null, "{0} has yielded.", "You have yielded." ); - - dc.m_Yielding=true; - dc.RejectReady( pm, null ); - dc.m_Yielding=false; - - if ( init == pm ) - { - dc.Unregister(); - } - else if ( dc.Registered ) - { - p.Nullify( pl ); - pm.DuelPlayer=null; - - NetState ns = init.NetState; - - if ( ns != null ) - { - bool send = true; - - foreach ( Gump g in ns.Gumps ) - { - if ( g is ParticipantGump pg && pg.Participant == p ) - { - init.SendGump( new ParticipantGump( init, dc, p ) ); - send=false; - break; - } - - if ( g is DuelContextGump dcg && dcg.Context == dc ) - { - init.SendGump( new DuelContextGump( init, dc ) ); - send=false; - break; - } - } - - if ( send ) - init.SendGump( new DuelContextGump( init, dc ) ); - } - } - } - else - { - pm.DuelContext.m_Countdown?.Stop(); - pm.DuelContext.m_Countdown = null; - - pm.DuelContext.StartedReadyCountdown=false; - p.Broadcast( 0x22, null, "{0} has yielded.", "You have yielded." ); - - dc.m_Yielding=true; - dc.RejectReady( pm, null ); - dc.m_Yielding=false; - - if ( init == pm ) - { - dc.Unregister(); - } - else if ( dc.Registered ) - { - p.Nullify( pl ); - pm.DuelPlayer=null; - - NetState ns = init.NetState; - - if ( ns != null ) - { - bool send = true; - - foreach ( Gump g in ns.Gumps ) - { - if ( g is ParticipantGump pg && pg.Participant == p ) - { - init.SendGump( new ParticipantGump( init, dc, p ) ); - send=false; - break; - } - if ( g is DuelContextGump dcg && dcg.Context == dc ) - { - init.SendGump( new DuelContextGump( init, dc ) ); - send=false; - break; - } - } - - if ( send ) - init.SendGump( new DuelContextGump( init, dc ) ); - } - } - } - } - } - else - { - DuelPlayer pl = pm.DuelContext.Find( pm ); - - if ( pl != null ) - { - if ( pm.DuelContext.IsOneVsOne ) - { - e.Mobile.SendMessage( 0x22, "You may not yield a 1 on 1 match." ); - } - else if ( pl.Eliminated ) - { - e.Mobile.SendMessage( 0x22, "You have already been eliminated." ); - } - else - { - pm.LocalOverheadMessage( MessageType.Regular, 0x22, false, "You have yielded." ); - pm.NonlocalOverheadMessage( MessageType.Regular, 0x22, false, $"{pm.Name} has yielded."); - - pm.DuelContext.m_Yielding=true; - pm.Kill(); - pm.DuelContext.m_Yielding=false; - - if ( pm.Alive ) // invul, ... - { - pl.Eliminated = true; - - pm.DuelContext.RemoveAggressions( pm ); - pm.DuelContext.SendOutside( pm ); - pm.DuelContext.Refresh( pm, null ); - Debuff( pm ); - CancelSpell( pm ); - pm.Frozen = false; - - Participant winner = pm.DuelContext.CheckCompletion(); - - if ( winner != null ) - pm.DuelContext.Finish( winner ); - } - } - } - else - { - e.Mobile.SendMessage( 0x22, "BUG: Unable to find duel context." ); - } - } - } - } - - public DuelContext( Mobile initiator, RulesetLayout layout ) : this( initiator, layout, true ) - { - } - - public DuelContext( Mobile initiator, RulesetLayout layout, bool addNew ) - { - Initiator = initiator; - Participants = new ArrayList(); - Ruleset = new Ruleset( layout ); - Ruleset.ApplyDefault( layout.Defaults[0] ); - - if ( addNew ) - { - Participants.Add( new Participant( this, 1 ) ); - Participants.Add( new Participant( this, 1 ) ); - - ((Participant)Participants[0]).Add( initiator ); - } - } - - public void CloseAllGumps() - { - Type[] types = { typeof( DuelContextGump ), typeof( ParticipantGump ), typeof( RulesetGump ) }; - int[] defs = { -1, -1, -1 }; - - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; - - if ( pl == null ) - continue; - - Mobile mob = pl.Mobile; - - for ( int k = 0; k < types.Length; ++k ) - mob.CloseGump( types[k] ); - //mob.CloseGump( types[k], defs[k] ); - } - } - } - - public void RejectReady( Mobile rejector, string page ) - { - if ( StartedReadyCountdown ) - return; // sanity - - Type[] types = { typeof( DuelContextGump ), typeof( ReadyUpGump ), typeof( ReadyGump ) }; - int[] defs = { -1, -1, -1 }; - - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; - - if ( pl == null ) - continue; - - pl.Ready = false; - - Mobile mob = pl.Mobile; - - if ( page == null ) // yield - { - if ( mob != rejector ) - mob.SendMessage( 0x22, "{0} has yielded.", rejector.Name ); - } - else - { - if ( mob == rejector ) - mob.SendMessage( 0x22, "You have rejected the {0}.", Rematch ? "rematch" : page ); - else - mob.SendMessage( 0x22, "{0} has rejected the {1}.", rejector.Name, Rematch ? "rematch" : page ); - } - - for ( int k = 0; k < types.Length; ++k ) - mob.CloseGump( types[k] ); - //mob.CloseGump( types[k], defs[k] ); - } - } - - if ( Rematch ) - Unregister(); - else if ( !m_Yielding ) - Initiator.SendGump( new DuelContextGump( Initiator, this ) ); - - ReadyWait = false; - ReadyCount = 0; - } - - public void SendReadyGump() - { - SendReadyGump( -1 ); - } - - public static void Debuff( Mobile mob ) - { - mob.RemoveStatMod( "[Magic] Str Offset" ); - mob.RemoveStatMod( "[Magic] Dex Offset" ); - mob.RemoveStatMod( "[Magic] Int Offset" ); - mob.RemoveStatMod( "Concussion" ); - mob.RemoveStatMod( "blood-rose" ); - mob.RemoveStatMod( "clarity-potion" ); - - OrangePetals.RemoveContext( mob ); - - mob.Paralyzed = false; - mob.Hidden = false; + Arena arena = m_OverrideArena; - if ( !Core.AOS ) - { - mob.MagicDamageAbsorb = 0; - mob.MeleeDamageAbsorb = 0; - Spells.Second.ProtectionSpell.Registry.Remove( mob ); + if (arena == null) + arena = Arena.FindArena(players); - Spells.Fourth.ArchProtectionSpell.RemoveEntry( mob ); + if (arena == null) + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - mob.EndAction( typeof( DefensiveSpell ) ); - } - - TransformationSpellHelper.RemoveContext( mob, true ); - AnimalForm.RemoveContext( mob, true ); - - if ( DisguiseTimers.IsDisguised( mob ) ) - DisguiseTimers.StopTimer( mob ); + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; - if ( !mob.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - mob.BodyMod = 0; - mob.HueMod = -1; - mob.EndAction( typeof( PolymorphSpell ) ); - } - - BaseArmor.ValidateMobile( mob ); - BaseClothing.ValidateMobile( mob ); + dp?.Mobile.SendMessage( + "The duel could not be started because there are no arenas. If you want to stop waiting for a free arena, yield the duel."); + } + } - mob.Hits = mob.HitsMax; - mob.Stam = mob.StamMax; - mob.Mana = mob.ManaMax; + StartCountdown(10, SendReadyGump); + return; + } - mob.Poison = null; - } + if (!arena.IsOccupied) + { + Arena = arena; - public static void CancelSpell( Mobile mob ) - { - if ( mob.Spell is Spell spell ) - spell.Disturb( DisturbType.Kill ); + if (Initiator.Map == Map.Internal) + { + m_GatePoint = Initiator.LogoutLocation; + m_GateFacet = Initiator.LogoutMap; + } + else + { + m_GatePoint = Initiator.Location; + m_GateFacet = Initiator.Map; + } - Targeting.Target.Cancel( mob ); - } + if (!(arena.Teleporter is ExitTeleporter tp)) + { + arena.Teleporter = tp = new ExitTeleporter(); + tp.MoveToWorld(arena.GateOut == Point3D.Zero ? arena.Outside : arena.GateOut, arena.Facet); + } - public bool StartedBeginCountdown { get; private set; } + ArenaMoongate mg = new ArenaMoongate(arena.GateIn == Point3D.Zero ? arena.Outside : arena.GateIn, + arena.Facet, tp); - public bool StartedReadyCountdown { get; private set; } + StartedBeginCountdown = true; - private class InternalWall : Item - { - public InternalWall() : base( 0x80 ) - { - Movable = false; - } - - public void Appear( Point3D loc, Map map ) - { - MoveToWorld( loc, map ); - - Effects.SendLocationParticles( this, 0x376A, 9, 10, 5025 ); - } - - public InternalWall( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - int version = reader.ReadInt(); + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - Delete(); - } - } - - private ArrayList m_Walls = new ArrayList(); - - public void DestroyWall() - { - for ( int i = 0; i < m_Walls.Count; ++i ) - ((Item)m_Walls[i]).Delete(); - - m_Walls.Clear(); - } - - public void CreateWall() - { - if ( Arena == null ) - return; - - Point3D start = Arena.Points.EdgeWest; - Point3D wall = Arena.Wall; - - int dx = start.X - wall.X; - int dy = start.Y - wall.Y; - int rx = dx - dy; - int ry = dx + dy; - - bool eastToWest; - - if ( rx >= 0 && ry >= 0 ) - eastToWest = false; - else if ( rx >= 0 ) - eastToWest = true; - else if ( ry >= 0 ) - eastToWest = true; - else - eastToWest = false; - - Effects.PlaySound( wall, Arena.Facet, 0x1F6 ); - - for ( int i = -1; i <= 1; ++i ) - { - Point3D loc = new Point3D( eastToWest ? wall.X + i : wall.X, eastToWest ? wall.Y : wall.Y + i, wall.Z ); - - InternalWall created = new InternalWall(); - - created.Appear( loc, Arena.Facet ); - - m_Walls.Add( created ); - } - } - - public void BuildParties() - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - if ( p.Players.Length > 1 ) - { - ArrayList players = new ArrayList(); - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; - - if ( dp == null ) - continue; - - players.Add( dp.Mobile ); - } - - if ( players.Count > 1 ) - { - for ( int leaderIndex = 0; (leaderIndex+1) < players.Count; leaderIndex += Party.Capacity ) - { - Mobile leader = (Mobile) players[leaderIndex]; - Party party = Party.Get( leader ); - - if ( party == null ) - { - leader.Party = party = new Party( leader ); - } - else if ( party.Leader != leader ) - { - party.SendPublicMessage( leader, "I leave this party to fight in a duel." ); - party.Remove( leader ); - leader.Party = party = new Party( leader ); - } - - for ( int j = leaderIndex+1; j < players.Count && j < leaderIndex+Party.Capacity; ++j ) - { - Mobile player = (Mobile)players[j]; - Party existing = Party.Get( player ); - - if ( existing == party ) - continue; - - if ( (party.Members.Count + party.Candidates.Count) >= Party.Capacity ) - { - player.SendMessage( "You could not be added to the team party because it is at full capacity." ); - leader.SendMessage( "{0} could not be added to the team party because it is at full capacity." ); - } - else - { - if ( existing != null ) - { - existing.SendPublicMessage( player, "I leave this party to fight in a duel." ); - existing.Remove( player ); - } - - party.OnAccept( player, true ); - } - } - } - } - } - } - } - - public void ClearIllegalItems() - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; - - if ( pl == null ) - continue; - - ClearIllegalItems( pl.Mobile ); - } - } - } - - public void ClearIllegalItems( Mobile mob ) - { - if ( mob.StunReady && !AllowSpecialAbility( mob, "Stun", false ) ) - mob.StunReady = false; - - if ( mob.DisarmReady && !AllowSpecialAbility( mob, "Disarm", false ) ) - mob.DisarmReady = false; - - Container pack = mob.Backpack; - - if ( pack == null ) - return; - - for ( int i = mob.Items.Count - 1; i >= 0; --i ) - { - if ( i >= mob.Items.Count ) - continue; // sanity - - Item item = mob.Items[i]; - - if ( !CheckItemEquip( mob, item ) ) - { - pack.DropItem( item ); - - if ( item is BaseWeapon ) - mob.SendLocalizedMessage( 1062001, item.Name ?? "#" + item.LabelNumber.ToString() ); // You can no longer wield your ~1_WEAPON~ - else if ( item is BaseArmor && !(item is BaseShield) ) - mob.SendLocalizedMessage( 1062002, item.Name ?? "#" + item.LabelNumber.ToString() ); // You can no longer wear your ~1_ARMOR~ - else - mob.SendLocalizedMessage( 1062003, item.Name ?? "#" + item.LabelNumber.ToString() ); // You can no longer equip your ~1_SHIELD~ - } - } - - Item inHand = mob.Holding; - - if ( inHand != null && !CheckItemEquip( mob, inHand ) ) - { - mob.Holding = null; - - BounceInfo bi = inHand.GetBounce(); - - if ( bi.m_Parent == mob ) - pack.DropItem( inHand ); - else - inHand.Bounce( mob ); - - inHand.ClearBounce(); - } - } - - private void MessageRuleset( Mobile mob ) { - if ( Ruleset == null ) { - return; - } - - Ruleset ruleset = Ruleset; - Ruleset basedef = ruleset.Base; - - mob.SendMessage( "Ruleset: {0}", basedef.Title ); - - BitArray defs; - - if ( ruleset.Flavors.Count > 0 ) - { - defs = new BitArray( basedef.Options ); - - for ( int i = 0; i < ruleset.Flavors.Count; ++i ) { - defs.Or( ((Ruleset)ruleset.Flavors[i]).Options ); - - mob.SendMessage( " + {0}", ((Ruleset)ruleset.Flavors[i]).Title ); - } - } - else - { - defs = basedef.Options; - } - - int changes = 0; - - BitArray opts = ruleset.Options; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) { - string name = ruleset.Layout.FindByIndex( i ); - - if ( name != null ) // sanity - { - ++changes; - - if ( changes == 1 ) { - mob.SendMessage( "Modifications:" ); - } - - mob.SendMessage( "{0}: {1}", name, opts[i] ? "enabled" : "disabled" ); - } - } - } - } - - public void SendBeginGump( int count ) - { - if ( !Registered || Finished ) - return; - - if ( count == 10 ) - { - CreateWall(); - BuildParties(); - ClearIllegalItems(); - } - else if ( count == 0 ) - { - DestroyWall(); - } - - StartedBeginCountdown = true; - - if ( count == 0 ) - { - Started = true; - BeginAutoTie(); - } - - Type[] types = { typeof( ReadyGump ), typeof( ReadyUpGump ), typeof( BeginGump ) }; - - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; - - if ( pl == null ) - continue; - - Mobile mob = pl.Mobile; - - if ( count > 0 ) - { - if ( count == 10 ) - CloseAndSendGump( mob, new BeginGump( count ), types ); - - mob.Frozen = true; - } - else - { - mob.CloseGump( typeof( BeginGump ) ); - mob.Frozen = false; - } - } - } - } - - private ArrayList m_Entered = new ArrayList(); - - private class ReturnEntry - { - private DateTime m_Expire; - - public Mobile Mobile { get; } - - public Point3D Location { get; private set; } - - public Map Facet { get; private set; } - - public void Return() - { - if ( Facet == Map.Internal || Facet == null ) - return; - - if ( Mobile.Map == Map.Internal ) - { - Mobile.LogoutLocation = Location; - Mobile.LogoutMap = Facet; - } - else - { - Mobile.Location = Location; - Mobile.Map = Facet; - } - } - - public ReturnEntry( Mobile mob ) - { - Mobile = mob; - - Update(); - } - - public ReturnEntry( Mobile mob, Point3D loc, Map facet ) - { - Mobile = mob; - Location = loc; - Facet = facet; - m_Expire = DateTime.UtcNow + TimeSpan.FromMinutes( 30.0 ); - } - - public bool Expired => ( DateTime.UtcNow >= m_Expire ); - - public void Update() - { - m_Expire = DateTime.UtcNow + TimeSpan.FromMinutes( 30.0 ); - - if ( Mobile.Map == Map.Internal ) - { - Facet = Mobile.LogoutMap; - Location = Mobile.LogoutLocation; - } - else - { - Facet = Mobile.Map; - Location = Mobile.Location; - } - } - } - - private class ExitTeleporter : Item - { - private ArrayList m_Entries; - - public override string DefaultName => "return teleporter"; - - public ExitTeleporter() : base( 0x1822 ) - { - m_Entries = new ArrayList(); - - Hue = 0x482; - Movable = false; - } - - public void Register( Mobile mob ) - { - ReturnEntry entry = Find( mob ); - - if ( entry != null ) - { - entry.Update(); - return; - } - - m_Entries.Add( new ReturnEntry( mob ) ); - } - - private ReturnEntry Find( Mobile mob ) - { - for ( int i = 0; i < m_Entries.Count; ++i ) - { - ReturnEntry entry = (ReturnEntry)m_Entries[i]; - - if ( entry.Mobile == mob ) - return entry; - if ( entry.Expired ) - m_Entries.RemoveAt( i-- ); - } - - return null; - } - - public override bool OnMoveOver( Mobile m ) - { - if ( !base.OnMoveOver( m ) ) - return false; - - ReturnEntry entry = Find( m ); - - if ( entry != null ) - { - entry.Return(); - - Effects.PlaySound( GetWorldLocation(), Map, 0x1FE ); - Effects.PlaySound( m.Location, m.Map, 0x1FE ); - - m_Entries.Remove( entry ); - - return false; - } - - m.SendLocalizedMessage( 1049383 ); // The teleporter doesn't seem to work for you. - return true; - } - - public ExitTeleporter( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - writer.WriteEncodedInt( (int) m_Entries.Count ); - - for ( int i = 0; i < m_Entries.Count; ++i ) - { - ReturnEntry entry = (ReturnEntry)m_Entries[i]; - - writer.Write( (Mobile) entry.Mobile ); - writer.Write( (Point3D) entry.Location ); - writer.Write( (Map) entry.Facet ); - - if ( entry.Expired ) - m_Entries.RemoveAt( i-- ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - int count = reader.ReadEncodedInt(); - - m_Entries = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) - { - Mobile mob = reader.ReadMobile(); - Point3D loc = reader.ReadPoint3D(); - Map map = reader.ReadMap(); - - m_Entries.Add( new ReturnEntry( mob, loc, map ) ); - } - - break; - } - } - } - } - - private class ArenaMoongate : ConfirmationMoongate - { - private ExitTeleporter m_Teleporter; - - public override string DefaultName => "spectator moongate"; - - public ArenaMoongate( Point3D target, Map map, ExitTeleporter tp ) : base( target, map ) - { - m_Teleporter = tp; - - ItemID = 0x1FD4; - Dispellable = false; - - GumpWidth = 300; - GumpHeight = 150; - MessageColor = 0xFFC000; - MessageString = "Are you sure you wish to spectate this duel?"; - TitleColor = 0x7800; - TitleNumber = 1062051; // Gate Warning - - Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), Delete ); - } - - public override void CheckGate(Mobile m, int range) - { - if ( CheckCombat( m ) ) - { - m.SendMessage( 0x22, "You have recently been in combat with another player and cannot use this moongate." ); - } - else - { - base.CheckGate( m, range ); - } - } - - public override void UseGate( Mobile m ) - { - if ( CheckCombat( m ) ) - { - m.SendMessage( 0x22, "You have recently been in combat with another player and cannot use this moongate." ); - } - else - { - if ( m_Teleporter != null && !m_Teleporter.Deleted ) - m_Teleporter.Register( m ); - - base.UseGate( m ); - } - } - - public void Appear( Point3D loc, Map map ) - { - Effects.PlaySound( loc, map, 0x20E ); - MoveToWorld( loc, map ); - } - - public ArenaMoongate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Delete(); - } - } - - public void RemoveAggressions( Mobile mob ) - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = (DuelPlayer)p.Players[j]; - - if ( dp == null || dp.Mobile == mob ) - continue; - - mob.RemoveAggressed( dp.Mobile ); - mob.RemoveAggressor( dp.Mobile ); - dp.Mobile.RemoveAggressed( mob ); - dp.Mobile.RemoveAggressor( mob ); - } - } - } - - public void SendReadyUpGump() - { - if ( !Registered ) - return; - - ReadyWait = true; - ReadyCount = -1; - - Type[] types = { typeof( ReadyUpGump ) }; - - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; - - Mobile mob = pl?.Mobile; - - if ( mob != null ) - { - if ( m_Tournament == null ) - CloseAndSendGump( mob, new ReadyUpGump( mob, this ), types ); - } - } - } - } - - public string ValidateStart() - { - if ( m_Tournament == null && TournamentController.IsActive ) - return "a tournament is active"; - - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; - - if ( dp == null ) - return "a slot is empty"; + if (pl == null) + continue; - if ( dp.Mobile.Region.IsPartOf( typeof( Regions.Jail ) ) ) - return $"{dp.Mobile.Name} is in jail"; + tp.Register(pl.Mobile); - if ( Sigil.ExistsOn( dp.Mobile ) ) - return $"{dp.Mobile.Name} is holding a sigil"; + pl.Mobile.Frozen = false; // reset timer just in case + pl.Mobile.Frozen = true; - if ( !dp.Mobile.Alive ) - { - if ( m_Tournament == null ) - return $"{dp.Mobile.Name} is dead"; - dp.Mobile.Resurrect(); - } + Debuff(pl.Mobile); + CancelSpell(pl.Mobile); - if ( m_Tournament == null && CheckCombat( dp.Mobile ) ) - return $"{dp.Mobile.Name} is in combat"; + pl.Mobile.Delta(MobileDelta.Noto); + } - if ( dp.Mobile.Mounted ) - { - IMount mount = dp.Mobile.Mount; + arena.MoveInside(p.Players, i); + } - if ( m_Tournament != null && mount != null ) - mount.Rider = null; - else - return $"{dp.Mobile.Name} is mounted"; - } - } - } - - return null; - } - - public Arena m_OverrideArena; - public Tournament m_Tournament; - public TournyMatch m_Match; - public EventGame m_EventGame; - - public Tournament Tournament => m_Tournament; - - public void SendReadyGump( int count ) - { - if ( !Registered ) - return; - - if ( count != -1 ) - StartedReadyCountdown = true; - - ReadyCount = count; - - if ( count == 0 ) - { - string error = ValidateStart(); + m_EventGame?.OnStart(); - if ( error != null ) - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + StartCountdown(10, SendBeginGump); - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + mg.Appear(m_GatePoint, m_GateFacet); + } + else + { + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - dp?.Mobile.SendMessage( "The duel could not be started because {0}.", error ); - } - } + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; - StartCountdown( 10, SendReadyGump ); + dp?.Mobile.SendMessage( + "The duel could not be started because all arenas are full. If you want to stop waiting for a free arena, yield the duel."); + } + } - return; - } + StartCountdown(10, SendReadyGump); + } - ReadyWait = false; + return; + } - List players = new List(); + ReadyWait = true; - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + bool isAllReady = true; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + Type[] types = { typeof(ReadyGump) }; - if ( dp != null ) - players.Add( dp.Mobile ); - } - } + for (int i = 0; i < Participants.Count; ++i) + { + Participant p = (Participant)Participants[i]; - Arena arena = m_OverrideArena; + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - if ( arena == null ) - arena = Arena.FindArena( players ); + if (pl == null) + continue; - if ( arena == null ) - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + Mobile mob = pl.Mobile; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + if (pl.Ready) + { + if (m_Tournament == null) + CloseAndSendGump(mob, new ReadyGump(mob, this, count), types); + } + else + { + isAllReady = false; + } + } + } - dp?.Mobile.SendMessage( "The duel could not be started because there are no arenas. If you want to stop waiting for a free arena, yield the duel." ); - } - } + if (count == -1 && isAllReady) + StartCountdown(3, SendReadyGump); + } - StartCountdown( 10, SendReadyGump ); - return; - } + public static void CloseAndSendGump(Mobile mob, Gump g, params Type[] types) + { + CloseAndSendGump(mob.NetState, g, types); + } - if ( !arena.IsOccupied ) - { - Arena = arena; + public static void CloseAndSendGump(NetState ns, Gump g, params Type[] types) + { + Mobile mob = ns?.Mobile; - if ( Initiator.Map == Map.Internal ) - { - m_GatePoint = Initiator.LogoutLocation; - m_GateFacet = Initiator.LogoutMap; - } - else - { - m_GatePoint = Initiator.Location; - m_GateFacet = Initiator.Map; - } + if (mob != null) + { + foreach (Type type in types) mob.CloseGump(type); - if ( !(arena.Teleporter is ExitTeleporter tp) ) - { - arena.Teleporter = tp = new ExitTeleporter(); - tp.MoveToWorld( arena.GateOut == Point3D.Zero ? arena.Outside : arena.GateOut, arena.Facet ); - } + mob.SendGump(g); + } - ArenaMoongate mg = new ArenaMoongate( arena.GateIn == Point3D.Zero ? arena.Outside : arena.GateIn, arena.Facet, tp ); + /*if ( ns == null ) + return; - StartedBeginCountdown = true; + for ( int i = 0; i < types.Length; ++i ) + ns.Send( new CloseGump( Gump.GetTypeID( types[i] ), 0 ) ); - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + g.SendTo( ns ); - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + ns.AddGump( g ); - if ( pl == null ) - continue; + Packet[] packets = new Packet[types.Length + 1]; - tp.Register( pl.Mobile ); + for ( int i = 0; i < types.Length; ++i ) + packets[i] = new CloseGump( Gump.GetTypeID( types[i] ), 0 ); - pl.Mobile.Frozen = false; // reset timer just in case - pl.Mobile.Frozen = true; + packets[types.Length] = (Packet) typeof( Gump ).InvokeMember( "Compile", BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.InvokeMethod, null, g, null, null ); - Debuff( pl.Mobile ); - CancelSpell( pl.Mobile ); + bool compress = ns.CompressionEnabled; + ns.CompressionEnabled = false; + ns.Send( BindPackets( compress, packets ) ); + ns.CompressionEnabled = compress;*/ + } - pl.Mobile.Delta( MobileDelta.Noto ); - } + private class InternalWall : Item + { + public InternalWall() : base(0x80) + { + Movable = false; + } + + public InternalWall(Serial serial) : base(serial) + { + } - arena.MoveInside( p.Players, i ); - } + public void Appear(Point3D loc, Map map) + { + MoveToWorld(loc, map); - m_EventGame?.OnStart(); + Effects.SendLocationParticles(this, 0x376A, 9, 10, 5025); + } - StartCountdown( 10, SendBeginGump ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - mg.Appear( m_GatePoint, m_GateFacet ); - } - else - { - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + writer.Write(0); + } - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Delete(); + } + } + + private class ReturnEntry + { + private DateTime m_Expire; + + public ReturnEntry(Mobile mob) + { + Mobile = mob; + + Update(); + } + + public ReturnEntry(Mobile mob, Point3D loc, Map facet) + { + Mobile = mob; + Location = loc; + Facet = facet; + m_Expire = DateTime.UtcNow + TimeSpan.FromMinutes(30.0); + } + + public Mobile Mobile{ get; } - dp?.Mobile.SendMessage( "The duel could not be started because all arenas are full. If you want to stop waiting for a free arena, yield the duel." ); - } - } + public Point3D Location{ get; private set; } - StartCountdown( 10, SendReadyGump ); - } + public Map Facet{ get; private set; } - return; - } + public bool Expired => DateTime.UtcNow >= m_Expire; - ReadyWait = true; + public void Return() + { + if (Facet == Map.Internal || Facet == null) + return; - bool isAllReady = true; + if (Mobile.Map == Map.Internal) + { + Mobile.LogoutLocation = Location; + Mobile.LogoutMap = Facet; + } + else + { + Mobile.Location = Location; + Mobile.Map = Facet; + } + } - Type[] types = { typeof( ReadyGump ) }; + public void Update() + { + m_Expire = DateTime.UtcNow + TimeSpan.FromMinutes(30.0); - for ( int i = 0; i < Participants.Count; ++i ) - { - Participant p = (Participant)Participants[i]; + if (Mobile.Map == Map.Internal) + { + Facet = Mobile.LogoutMap; + Location = Mobile.LogoutLocation; + } + else + { + Facet = Mobile.Map; + Location = Mobile.Location; + } + } + } + + private class ExitTeleporter : Item + { + private ArrayList m_Entries; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + public ExitTeleporter() : base(0x1822) + { + m_Entries = new ArrayList(); + + Hue = 0x482; + Movable = false; + } + + public ExitTeleporter(Serial serial) : base(serial) + { + } + + public override string DefaultName => "return teleporter"; + + public void Register(Mobile mob) + { + ReturnEntry entry = Find(mob); + + if (entry != null) + { + entry.Update(); + return; + } + + m_Entries.Add(new ReturnEntry(mob)); + } + + private ReturnEntry Find(Mobile mob) + { + for (int i = 0; i < m_Entries.Count; ++i) + { + ReturnEntry entry = (ReturnEntry)m_Entries[i]; + + if (entry.Mobile == mob) + return entry; + if (entry.Expired) + m_Entries.RemoveAt(i--); + } + + return null; + } + + public override bool OnMoveOver(Mobile m) + { + if (!base.OnMoveOver(m)) + return false; + + ReturnEntry entry = Find(m); + + if (entry != null) + { + entry.Return(); + + Effects.PlaySound(GetWorldLocation(), Map, 0x1FE); + Effects.PlaySound(m.Location, m.Map, 0x1FE); + + m_Entries.Remove(entry); + + return false; + } + + m.SendLocalizedMessage(1049383); // The teleporter doesn't seem to work for you. + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.WriteEncodedInt(m_Entries.Count); + + for (int i = 0; i < m_Entries.Count; ++i) + { + ReturnEntry entry = (ReturnEntry)m_Entries[i]; + + writer.Write(entry.Mobile); + writer.Write(entry.Location); + writer.Write(entry.Facet); + + if (entry.Expired) + m_Entries.RemoveAt(i--); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + int count = reader.ReadEncodedInt(); + + m_Entries = new ArrayList(count); - if ( pl == null ) - continue; - - Mobile mob = pl.Mobile; - - if ( pl.Ready ) - { - if ( m_Tournament == null ) - CloseAndSendGump( mob, new ReadyGump( mob, this, count ), types ); - } - else - { - isAllReady = false; - } - } - } - - if ( count == -1 && isAllReady ) - StartCountdown( 3, SendReadyGump ); - } - - public static void CloseAndSendGump( Mobile mob, Gump g, params Type[] types ) - { - CloseAndSendGump( mob.NetState, g, types ); - } - - public static void CloseAndSendGump( NetState ns, Gump g, params Type[] types ) - { - Mobile mob = ns?.Mobile; - - if ( mob != null ) { - foreach ( Type type in types ) { - mob.CloseGump( type ); - } - - mob.SendGump( g ); - } - - /*if ( ns == null ) - return; - - for ( int i = 0; i < types.Length; ++i ) - ns.Send( new CloseGump( Gump.GetTypeID( types[i] ), 0 ) ); - - g.SendTo( ns ); - - ns.AddGump( g ); - - Packet[] packets = new Packet[types.Length + 1]; - - for ( int i = 0; i < types.Length; ++i ) - packets[i] = new CloseGump( Gump.GetTypeID( types[i] ), 0 ); - - packets[types.Length] = (Packet) typeof( Gump ).InvokeMember( "Compile", BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.InvokeMethod, null, g, null, null ); - - bool compress = ns.CompressionEnabled; - ns.CompressionEnabled = false; - ns.Send( BindPackets( compress, packets ) ); - ns.CompressionEnabled = compress;*/ - } - - /*public static Packet BindPackets( bool compress, params Packet[] packets ) - { - if ( packets.Length == 0 ) - throw new ArgumentException( "No packets to bind", "packets" ); - - byte[][] compiled = new byte[packets.Length][]; - int[] lengths = new int[packets.Length]; - - int length = 0; - - for ( int i = 0; i < packets.Length; ++i ) - { - compiled[i] = packets[i].Compile( compress, out lengths[i] ); - length += lengths[i]; - } - - return new BoundPackets( length, compiled, lengths ); - } - - private class BoundPackets : Packet - { - public BoundPackets( int length, byte[][] compiled, int[] lengths ) : base( 0, length ) - { - m_Stream.Seek( 0, System.IO.SeekOrigin.Begin ); - - for ( int i = 0; i < compiled.Length; ++i ) - m_Stream.Write( compiled[i], 0, lengths[i] ); - } - }*/ - } -} + for (int i = 0; i < count; ++i) + { + Mobile mob = reader.ReadMobile(); + Point3D loc = reader.ReadPoint3D(); + Map map = reader.ReadMap(); + + m_Entries.Add(new ReturnEntry(mob, loc, map)); + } + + break; + } + } + } + } + + private class ArenaMoongate : ConfirmationMoongate + { + private ExitTeleporter m_Teleporter; + + public ArenaMoongate(Point3D target, Map map, ExitTeleporter tp) : base(target, map) + { + m_Teleporter = tp; + + ItemID = 0x1FD4; + Dispellable = false; + + GumpWidth = 300; + GumpHeight = 150; + MessageColor = 0xFFC000; + MessageString = "Are you sure you wish to spectate this duel?"; + TitleColor = 0x7800; + TitleNumber = 1062051; // Gate Warning + + Timer.DelayCall(TimeSpan.FromSeconds(10.0), Delete); + } + + public ArenaMoongate(Serial serial) : base(serial) + { + } + + public override string DefaultName => "spectator moongate"; + + public override void CheckGate(Mobile m, int range) + { + if (CheckCombat(m)) + m.SendMessage(0x22, + "You have recently been in combat with another player and cannot use this moongate."); + else + base.CheckGate(m, range); + } + + public override void UseGate(Mobile m) + { + if (CheckCombat(m)) + { + m.SendMessage(0x22, + "You have recently been in combat with another player and cannot use this moongate."); + } + else + { + if (m_Teleporter != null && !m_Teleporter.Deleted) + m_Teleporter.Register(m); + + base.UseGate(m); + } + } + + public void Appear(Point3D loc, Map map) + { + Effects.PlaySound(loc, map, 0x20E); + MoveToWorld(loc, map); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Delete(); + } + } + + /*public static Packet BindPackets( bool compress, params Packet[] packets ) + { + if ( packets.Length == 0 ) + throw new ArgumentException( "No packets to bind", "packets" ); + + byte[][] compiled = new byte[packets.Length][]; + int[] lengths = new int[packets.Length]; + + int length = 0; + + for ( int i = 0; i < packets.Length; ++i ) + { + compiled[i] = packets[i].Compile( compress, out lengths[i] ); + length += lengths[i]; + } + + return new BoundPackets( length, compiled, lengths ); + } + + private class BoundPackets : Packet + { + public BoundPackets( int length, byte[][] compiled, int[] lengths ) : base( 0, length ) + { + m_Stream.Seek( 0, System.IO.SeekOrigin.Begin ); + + for ( int i = 0; i < compiled.Length; ++i ) + m_Stream.Write( compiled[i], 0, lengths[i] ); + } + }*/ + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/DuelContextGump.cs b/Scripts/Engines/ConPVP/DuelContextGump.cs index f6cb72431..a6560083c 100644 --- a/Scripts/Engines/ConPVP/DuelContextGump.cs +++ b/Scripts/Engines/ConPVP/DuelContextGump.cs @@ -1,133 +1,139 @@ -using System; using Server.Gumps; using Server.Network; namespace Server.Engines.ConPVP { - public class DuelContextGump : Gump - { - public Mobile From { get; } + public class DuelContextGump : Gump + { + public DuelContextGump(Mobile from, DuelContext context) : base(50, 50) + { + From = from; + Context = context; - public DuelContext Context { get; } + from.CloseGump(typeof(RulesetGump)); + from.CloseGump(typeof(DuelContextGump)); + from.CloseGump(typeof(ParticipantGump)); - public string Center( string text ) - { - return $"
{text}
"; - } + int count = context.Participants.Count; - public void AddGoldenButton( int x, int y, int bid ) - { - AddButton( x , y , 0xD2, 0xD2, bid, GumpButtonType.Reply, 0 ); - AddButton( x+3, y+3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0 ); - } + if (count < 3) + count = 3; - public void AddGoldenButtonLabeled( int x, int y, int bid, string text ) - { - AddGoldenButton( x, y, bid ); - AddHtml( x + 25, y, 200, 20, text, false, false ); - } + int height = 35 + 10 + 22 + 30 + 22 + 22 + 2 + count * 22 + 2 + 30; - public DuelContextGump( Mobile from, DuelContext context ) : base( 50, 50 ) - { - From = from; - Context = context; + AddPage(0); - from.CloseGump( typeof( RulesetGump ) ); - from.CloseGump( typeof( DuelContextGump ) ); - from.CloseGump( typeof( ParticipantGump ) ); + AddBackground(0, 0, 300, height, 9250); + AddBackground(10, 10, 280, height - 20, 0xDAC); - int count = context.Participants.Count; + AddHtml(35, 25, 230, 20, Center("Duel Setup"), false, false); - if ( count < 3 ) - count = 3; + int x = 35; + int y = 47; - int height = 35 + 10 + 22 + 30 + 22 + 22 + 2 + (count * 22) + 2 + 30; + AddGoldenButtonLabeled(x, y, 1, "Rules"); + y += 22; + AddGoldenButtonLabeled(x, y, 2, "Start"); + y += 22; + AddGoldenButtonLabeled(x, y, 3, "Add Participant"); + y += 30; - AddPage( 0 ); + AddHtml(35, y, 230, 20, Center("Participants"), false, false); + y += 22; - AddBackground( 0, 0, 300, height, 9250 ); - AddBackground( 10, 10, 280, height - 20, 0xDAC ); + for (int i = 0; i < context.Participants.Count; ++i) + { + Participant p = (Participant)context.Participants[i]; - AddHtml( 35, 25, 230, 20, Center( "Duel Setup" ), false, false ); + AddGoldenButtonLabeled(x, y, 4 + i, + string.Format(p.Count == 1 ? "Player {0}: {3}" : "Team {0}: {1}/{2}: {3}", 1 + i, p.FilledSlots, p.Count, + p.NameList)); + y += 22; + } + } - int x = 35; - int y = 47; + public Mobile From{ get; } - AddGoldenButtonLabeled( x, y, 1, "Rules" ); y += 22; - AddGoldenButtonLabeled( x, y, 2, "Start" ); y += 22; - AddGoldenButtonLabeled( x, y, 3, "Add Participant" ); y += 30; + public DuelContext Context{ get; } - AddHtml( 35, y, 230, 20, Center( "Participants" ), false, false ); y += 22; + public string Center(string text) + { + return $"
{text}
"; + } - for ( int i = 0; i < context.Participants.Count; ++i ) - { - Participant p = (Participant)context.Participants[i]; + public void AddGoldenButton(int x, int y, int bid) + { + AddButton(x, y, 0xD2, 0xD2, bid, GumpButtonType.Reply, 0); + AddButton(x + 3, y + 3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0); + } - AddGoldenButtonLabeled( x, y, 4 + i, string.Format( p.Count == 1 ? "Player {0}: {3}" : "Team {0}: {1}/{2}: {3}", 1 + i, p.FilledSlots, p.Count, p.NameList ) ); y += 22; - } - } + public void AddGoldenButtonLabeled(int x, int y, int bid, string text) + { + AddGoldenButton(x, y, bid); + AddHtml(x + 25, y, 200, 20, text, false, false); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !Context.Registered ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!Context.Registered) + return; - int index = info.ButtonID; + int index = info.ButtonID; - switch ( index ) - { - case -1: // CloseGump - { - break; - } - case 0: // closed - { - Context.Unregister(); - break; - } - case 1: // Rules - { - //m_From.SendGump( new RulesetGump( m_From, m_Context.Ruleset, m_Context.Ruleset.Layout, m_Context ) ); - From.SendGump( new PickRulesetGump( From, Context, Context.Ruleset ) ); - break; - } - case 2: // Start - { - if ( Context.CheckFull() ) - { - Context.CloseAllGumps(); - Context.SendReadyUpGump(); - //m_Context.SendReadyGump(); - } - else - { - From.SendMessage( "You cannot start the duel before all participating players have been assigned." ); - From.SendGump( new DuelContextGump( From, Context ) ); - } + switch (index) + { + case -1: // CloseGump + { + break; + } + case 0: // closed + { + Context.Unregister(); + break; + } + case 1: // Rules + { + //m_From.SendGump( new RulesetGump( m_From, m_Context.Ruleset, m_Context.Ruleset.Layout, m_Context ) ); + From.SendGump(new PickRulesetGump(From, Context, Context.Ruleset)); + break; + } + case 2: // Start + { + if (Context.CheckFull()) + { + Context.CloseAllGumps(); + Context.SendReadyUpGump(); + //m_Context.SendReadyGump(); + } + else + { + From.SendMessage("You cannot start the duel before all participating players have been assigned."); + From.SendGump(new DuelContextGump(From, Context)); + } - break; - } - case 3: // New Participant - { - if ( Context.Participants.Count < 10 ) - Context.Participants.Add( new Participant( Context, 1 ) ); - else - From.SendMessage( "The number of participating parties may not be increased further." ); + break; + } + case 3: // New Participant + { + if (Context.Participants.Count < 10) + Context.Participants.Add(new Participant(Context, 1)); + else + From.SendMessage("The number of participating parties may not be increased further."); - From.SendGump( new DuelContextGump( From, Context ) ); + From.SendGump(new DuelContextGump(From, Context)); - break; - } - default: // Participant - { - index -= 4; + break; + } + default: // Participant + { + index -= 4; - if ( index >= 0 && index < Context.Participants.Count ) - From.SendGump( new ParticipantGump( From, Context, (Participant)Context.Participants[index] ) ); + if (index >= 0 && index < Context.Participants.Count) + From.SendGump(new ParticipantGump(From, Context, (Participant)Context.Participants[index])); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/DuelTeleporterAddon.cs b/Scripts/Engines/ConPVP/DuelTeleporterAddon.cs index 6375891a1..e1a5dd094 100644 --- a/Scripts/Engines/ConPVP/DuelTeleporterAddon.cs +++ b/Scripts/Engines/ConPVP/DuelTeleporterAddon.cs @@ -2,93 +2,93 @@ using Server.Items; namespace Server.Engines.ConPVP { - public enum DuelTeleporterType - { - Squares = 6095, - Buds = 6104, - Flowers = 6113, - Spikes = 6122, - Arrows = 6140, - Links = 6149 - } + public enum DuelTeleporterType + { + Squares = 6095, + Buds = 6104, + Flowers = 6113, + Spikes = 6122, + Arrows = 6140, + Links = 6149 + } - public class DuelTeleporterAddon : BaseAddon - { - [CommandProperty( AccessLevel.GameMaster )] - public DuelTeleporterType Type - { - get - { - if ( Components.Count > 0 ) - return (DuelTeleporterType)(((Item)Components[0]).ItemID); + public class DuelTeleporterAddon : BaseAddon + { + [Constructible] + public DuelTeleporterAddon() : this(DuelTeleporterType.Squares) + { + } - return DuelTeleporterType.Squares; - } - set - { - for ( int i = 0; i < Components.Count && i < 9; ++i ) - ((Item)Components[i]).ItemID = i + (int)value; - } - } + [Constructible] + public DuelTeleporterAddon(DuelTeleporterType type) + { + int itemID = (int)type; - [Constructible] - public DuelTeleporterAddon() : this( DuelTeleporterType.Squares ) - { - } + AddComponent(new AddonComponent(itemID + 0), -1, -1, 5); + AddComponent(new AddonComponent(itemID + 1), -1, 0, 5); + AddComponent(new AddonComponent(itemID + 2), 0, -1, 5); + AddComponent(new AddonComponent(itemID + 3), -1, +1, 5); + AddComponent(new AddonComponent(itemID + 4), 0, 0, 5); + AddComponent(new AddonComponent(itemID + 5), +1, -1, 5); + AddComponent(new AddonComponent(itemID + 6), 0, +1, 5); + AddComponent(new AddonComponent(itemID + 7), +1, 0, 5); + AddComponent(new AddonComponent(itemID + 8), +1, +1, 5); - [Constructible] - public DuelTeleporterAddon( DuelTeleporterType type ) - { - int itemID = (int)type; + AddComponent(new AddonComponent(0x759), -2, -2, 0); + AddComponent(new AddonComponent(0x75A), +2, +2, 0); + AddComponent(new AddonComponent(0x75B), -2, +2, 0); + AddComponent(new AddonComponent(0x75C), +2, -2, 0); - AddComponent( new AddonComponent( itemID + 0 ), -1, -1, 5 ); - AddComponent( new AddonComponent( itemID + 1 ), -1, 0, 5 ); - AddComponent( new AddonComponent( itemID + 2 ), 0, -1, 5 ); - AddComponent( new AddonComponent( itemID + 3 ), -1, +1, 5 ); - AddComponent( new AddonComponent( itemID + 4 ), 0, 0, 5 ); - AddComponent( new AddonComponent( itemID + 5 ), +1, -1, 5 ); - AddComponent( new AddonComponent( itemID + 6 ), 0, +1, 5 ); - AddComponent( new AddonComponent( itemID + 7 ), +1, 0, 5 ); - AddComponent( new AddonComponent( itemID + 8 ), +1, +1, 5 ); + AddComponent(new AddonComponent(0x751), -1, +2, 0); + AddComponent(new AddonComponent(0x751), 0, +2, 0); + AddComponent(new AddonComponent(0x751), +1, +2, 0); - AddComponent( new AddonComponent( 0x759 ), -2, -2, 0 ); - AddComponent( new AddonComponent( 0x75A ), +2, +2, 0 ); - AddComponent( new AddonComponent( 0x75B ), -2, +2, 0 ); - AddComponent( new AddonComponent( 0x75C ), +2, -2, 0 ); + AddComponent(new AddonComponent(0x752), +2, -1, 0); + AddComponent(new AddonComponent(0x752), +2, 0, 0); + AddComponent(new AddonComponent(0x752), +2, +1, 0); - AddComponent( new AddonComponent( 0x751 ), -1, +2, 0 ); - AddComponent( new AddonComponent( 0x751 ), 0, +2, 0 ); - AddComponent( new AddonComponent( 0x751 ), +1, +2, 0 ); + AddComponent(new AddonComponent(0x753), -1, -2, 0); + AddComponent(new AddonComponent(0x753), 0, -2, 0); + AddComponent(new AddonComponent(0x753), +1, -2, 0); - AddComponent( new AddonComponent( 0x752 ), +2, -1, 0 ); - AddComponent( new AddonComponent( 0x752 ), +2, 0, 0 ); - AddComponent( new AddonComponent( 0x752 ), +2, +1, 0 ); + AddComponent(new AddonComponent(0x754), -2, -1, 0); + AddComponent(new AddonComponent(0x754), -2, 0, 0); + AddComponent(new AddonComponent(0x754), -2, +1, 0); + } - AddComponent( new AddonComponent( 0x753 ), -1, -2, 0 ); - AddComponent( new AddonComponent( 0x753 ), 0, -2, 0 ); - AddComponent( new AddonComponent( 0x753 ), +1, -2, 0 ); + public DuelTeleporterAddon(Serial serial) : base(serial) + { + } - AddComponent( new AddonComponent( 0x754 ), -2, -1, 0 ); - AddComponent( new AddonComponent( 0x754 ), -2, 0, 0 ); - AddComponent( new AddonComponent( 0x754 ), -2, +1, 0 ); - } + [CommandProperty(AccessLevel.GameMaster)] + public DuelTeleporterType Type + { + get + { + if (Components.Count > 0) + return (DuelTeleporterType)Components[0].ItemID; - public DuelTeleporterAddon( Serial serial ) : base( serial ) - { - } + return DuelTeleporterType.Squares; + } + set + { + for (int i = 0; i < Components.Count && i < 9; ++i) + Components[i].ItemID = i + (int)value; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Games/BombingRun.cs b/Scripts/Engines/ConPVP/Games/BombingRun.cs index 7b58342ae..29e3e3a0f 100644 --- a/Scripts/Engines/ConPVP/Games/BombingRun.cs +++ b/Scripts/Engines/ConPVP/Games/BombingRun.cs @@ -1,1868 +1,1859 @@ - using System; using System.Collections; using System.Text; +using Server.Gumps; using Server.Items; using Server.Mobiles; using Server.Network; using Server.Targeting; -using Server.Gumps; namespace Server.Engines.ConPVP { - public class BRBomb : Item - { - public override string DefaultName => "da bomb"; - - private BRGame m_Game; - private EffectTimer m_Timer; - private bool m_Flying; - - private ArrayList m_Helpers; - - private Mobile FindOwner( object parent ) - { - if ( parent is Item item ) - return item.RootParent as Mobile; - - if ( parent is Mobile mobile ) - return mobile; - - return null; - } - - public BRBomb( BRGame game ) : base( 0x103C ) // 0x103C = bread, 0x1042 = pie, 0x1364 = rock, 0x13a8 = pillow, 0x2256 = bagball - { - Movable = false; - Hue = 0x35; - - m_Game = game; - - m_Helpers = new ArrayList(); - - m_Timer = new EffectTimer( this ); - m_Timer.Start(); - } - - private class EffectTimer : Timer - { - private BRBomb m_Bomb; - private int m_Count; - - public EffectTimer( BRBomb bomb ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ) ) - { - m_Bomb = bomb; - m_Count = 0; - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - if ( m_Bomb.Parent == null && m_Bomb.m_Game?.Controller != null ) - { - if ( !m_Bomb.m_Flying && m_Bomb.Map != Map.Internal ) - Effects.SendLocationEffect( m_Bomb.GetWorldLocation(), m_Bomb.Map, 0x377A, 16, 10, m_Bomb.Hue, 0 ); - - if ( m_Bomb.Location != m_Bomb.m_Game.Controller.BombHome ) - { - if ( ++m_Count >= 30 ) - { - m_Bomb.m_Game.ReturnBomb(); - m_Bomb.m_Game.Alert( "The bomb has been returned to it's starting point." ); - - m_Count = 0; - m_Bomb.m_Helpers.Clear(); - } - } - else - { - m_Count = 0; - } - } - else - { - m_Count = 0; - } - } - } - - public BRBomb( Serial serial ) : base( serial ) - { - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize (reader); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - break; - } - } - - Timer.DelayCall( TimeSpan.Zero, Delete ).Start(); // delete this after the world loads - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize (writer); - - writer.Write( (int) 0 ); // version - } - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - Mobile mob = FindOwner( parent ); - - if ( mob != null ) - { - mob.SolidHueOverride = 0x0499; - - //int fighterRank = mob.Skills.Tactics.Value + mob.Skills.Anatomy + mob.Skills.Healing.Value + mob.Skills.Swords.Value + mob.Skills.Macing.Value + mob.Skills.Fencing.Value + mob.Skills.Archery.Value + mob.Skills.Parrying.Value; - //int mageRank = mob.Skills.Magery.Value + mob.Skills.Meditation.Value + mob.Skills.EvalInt.Value + mob.Skills.Inscribe.Value + mob.Skills.Wrestling.Value + mob.Skills.MagicResist; - //int theifRank = mob.Skills.Stealing.Value + mob.Skills.Snooping.Value + mob.Skills.Hiding.Value + mob.Skills.Stealth.Value + mob.Skills.RemoveTrap.Value + mob.Skills.Lockpicking.Value + mob.Skills.ItemID.Value; - - // To Do: Give them a special ability while holding the ball maybe based on skills? - } - } - - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); - - Mobile mob = FindOwner( parent ); - - if ( mob != null && m_Game != null ) - mob.SolidHueOverride = m_Game.GetColor( mob ); - } - - public void DropTo( Mobile mob, Mobile killer ) - { - if ( mob != null && !mob.Deleted ) - MoveToWorld( mob.Location, mob.Map ); - else if ( killer != null && !killer.Deleted ) - MoveToWorld( killer.Location, killer.Map ); - else - { - m_Game?.ReturnBomb(); - } - } - - public override bool OnMoveOver( Mobile m ) - { - if ( m_Flying || !Visible || m_Game == null || m == null || !m.Alive ) - return true; - - BRTeamInfo useTeam = m_Game.GetTeamInfo( m ); - if ( useTeam == null ) - return true; - - return TakeBomb( m, useTeam, "picked up" ); - } - - public override void OnLocationChange(Point3D oldLocation) - { - base.OnLocationChange(oldLocation); - - if ( m_Flying || !Visible || m_Game == null || Parent != null ) - return; - - IPooledEnumerable eable = GetClientsInRange( 0 ); - foreach ( NetState ns in eable ) - { - Mobile m = ns.Mobile; - - if ( m == null || !m.Player || !m.Alive ) - continue; - - BRTeamInfo useTeam = m_Game.GetTeamInfo( m ); - if ( useTeam != null ) - TakeBomb( m, useTeam, "got" ); - } - } - - public override void OnAfterDelete() - { - base.OnAfterDelete (); - - m_Timer?.Stop(); - } - - public override void OnDoubleClick( Mobile m ) - { - if ( m_Game == null || !Visible || m == null || !m.Alive ) - return; - - if ( !m_Flying && IsChildOf( m.Backpack ) ) - { - m.Target = new BombTarget( this, m ); - } - else if ( Parent == null ) - { - if ( m.InRange( Location, 1 ) && m.Location.Z != Z ) - { - BRTeamInfo useTeam = m_Game.GetTeamInfo( m ); - if ( useTeam == null ) - return; - - TakeBomb( m, useTeam, "grabbed" ); - } - } - } - - private class BombTarget : Target - { - private BRBomb m_Bomb; - private Mobile m_Mob; - private bool m_Resend = true; - - public BombTarget( BRBomb bomb, Mobile from ) : base( 10, true, TargetFlags.None ) - { - CheckLOS = false; - - m_Bomb = bomb; - m_Mob = from; - - m_Mob.SendMessage( 0x26, "Where do you want to throw it?" ); - } - - protected override void OnTarget( Mobile from, object targeted ) - { - m_Resend = !m_Bomb.OnBombTarget( from, targeted ); - } - - protected override void OnTargetUntargetable( Mobile from, object targeted ) - { - m_Resend = !m_Bomb.OnBombTarget( from, targeted ); - } - - protected override void OnTargetFinish( Mobile from ) - { - base.OnTargetFinish( from ); - - // has to be delayed in case some other target canceled us... - if ( m_Resend ) - Timer.DelayCall( TimeSpan.Zero, ResendBombTarget ).Start(); - } - - private void ResendBombTarget() - { - // Make sure they still have the bomb, then give them the target back - if ( m_Bomb != null && !m_Bomb.Deleted && m_Mob != null && !m_Mob.Deleted && m_Mob.Alive ) - { - if ( m_Bomb.IsChildOf( m_Mob ) ) - m_Mob.Target = new BombTarget( m_Bomb, m_Mob ); - } - } - } - - private bool OnBombTarget( Mobile from, object obj ) - { - if ( m_Game == null ) - return true; - - if ( !IsChildOf( from.Backpack ) ) - return true; - - // don't let them throw it to themselves - if ( obj == from ) - return false; - - if ( !(obj is IPoint3D) ) - return false; - - Point3D pt = new Point3D( (IPoint3D)obj ); - - if ( obj is Mobile ) - pt.Z += 10; - else if ( obj is Item item ) - pt.Z += item.ItemData.CalcHeight + 1; - - m_Flying = true; - Visible = false; - Thrower = from; - MoveToWorld( GetWorldLocation(), from.Map ); - - BeginFlight( pt ); - return true; - } - - private void HitObject( Point3D ballLoc, int objZ, int objHeight ) - { - DoAnim( GetWorldLocation(), ballLoc, Map ); - MoveToWorld( ballLoc ); - - m_Path.Clear(); - m_PathIdx = 0; - - Timer.DelayCall( TimeSpan.FromSeconds( 0.05 ), ContinueFlight ).Start(); - } - - private bool CheckCatch( Mobile m, Point3D myLoc ) - { - if ( m == null || !m.Alive || !m.Player || m_Game == null ) - return false; - - if ( m_Game.GetTeamInfo( m ) == null ) - return false; - - int zdiff = myLoc.Z - m.Z; - - if ( zdiff < 0 ) - return false; - if ( zdiff < 12 ) - return true; - if ( zdiff < 16 ) - return Utility.RandomBool(); // 50% chance - - return false; - } - - private void DoAnim( Point3D start, Point3D end, Map map ) - { - Effects.SendMovingEffect( new Entity( Serial.Zero, start, map ), new Entity( Serial.Zero, end, map ), - ItemID, 15, 0, false, false, Hue, 0 ); - } - - private void DoCatch( Mobile m ) - { - m_Flying = false; - Visible = true; - - if ( m == null || !m.Alive || !m.Player || m_Game == null ) - return; - - BRTeamInfo useTeam = m_Game.GetTeamInfo( m ); - - if ( useTeam == null ) - return; - - DoAnim( GetWorldLocation(), m.Location, m.Map ); - - string verb = "caught"; - - if ( Thrower != null && m_Game.GetTeamInfo( Thrower ) != useTeam ) - verb = "intercepted"; - - if ( !TakeBomb( m, useTeam, verb ) ) - MoveToWorld( m.Location, m.Map ); - } - - private Point3DList m_Path = new Point3DList(); - private int m_PathIdx; - - private void BeginFlight( Point3D dest ) - { - Point3D org = GetWorldLocation(); - - org.Z += 10; // always add 10 at the start cause we're coming from a mobile's eye level - - /*if ( org.X > dest.X || ( org.X == dest.X && org.Y > dest.Y ) || ( org.X == dest.X && org.Y == dest.Y && org.Z > dest.Z ) ) - { - Point3D swap = org; - org = dest; - dest = swap; - }*/ - - ArrayList list = new ArrayList(); - double rise, run, zslp; - double dist3d, dist2d; - double x, y, z; - int xd, yd, zd; - Point3D p; - - xd = dest.X - org.X; - yd = dest.Y - org.Y; - zd = dest.Z - org.Z; - dist2d = Math.Sqrt( xd * xd + yd * yd ); - if ( zd != 0 ) - dist3d = Math.Sqrt( dist2d * dist2d + zd * zd ); - else - dist3d = dist2d; - - rise = ( (float) yd ) / dist3d; - run = ( (float) xd ) / dist3d; - zslp = ( (float) zd ) / dist3d; - - x = (int) org.X; - y = (int) org.Y; - z = (int) org.Z; - while ( Utility.NumberBetween( x, dest.X, org.X, 0.5 ) && Utility.NumberBetween( y, dest.Y, org.Y, 0.5 ) && Utility.NumberBetween( z, dest.Z, org.Z, 0.5 ) ) - { - int ix = (int) Math.Round( x ); - int iy = (int) Math.Round( y ); - int iz = (int) Math.Round( z ); - - if ( list.Count > 0 ) - { - p = (Point3D)list[list.Count-1]; - - if ( p.X != ix || p.Y != iy || p.Z != iz ) - list.Add( new Point3D( ix, iy, iz ) ); - } - else - { - list.Add( new Point3D( ix, iy, iz ) ); - } - - x += run; - y += rise; - z += zslp; - } - - if ( list.Count > 0 ) - { - if ( ((Point3D)list[list.Count-1]) != dest ) - list.Add( dest ); - } - - /*if ( dist3d > 4 && ( dest.X != org.X || dest.Y != org.Y ) ) - { - int count = list.Count; - int i; - int climb = count / 2; - if ( climb > 3 ) - climb = 3; - - for ( i = 0; i < climb; i++ ) - { - p = ((Point3D)list[i]); - p.Z += (i+1) * 4; - list[i] = p; - } - - for ( ; i < count - climb; i++ ) - { - p = ((Point3D)list[i]); - p.Z += 16; - list[i] = p; - } - - for ( i = climb; i > 0; i-- ) - { - p = ((Point3D)list[i]); - p.Z += i * 4; - list[i] = p; - } - }*/ - - if ( dist2d > 1 ) - { - int count = list.Count; - double height = count * 2 * ( Utility.RandomDouble() * 0.40 + 0.10 ); // 10 - 50% - double coeff = ( -height / ( (count*count)/4.0 ) ); - - for ( int i = 0; i < count; i++ ) - { - p = ((Point3D)list[i]); - - int xp = ( i - (count / 2) ); - - p.Z += (int)Math.Ceiling( coeff * xp * xp + height ); - - list[i] = p; - } - } - - m_Path.Clear(); - for (int i = 0; i < list.Count; i++) - m_Path.Add( (Point3D)list[i] ); - - m_PathIdx = 0; - - ContinueFlight(); - } - - private void ContinueFlight() - { - int height; - bool found = false; - - if ( m_PathIdx < m_Path.Count && Map?.Tiles != null && Map != Map.Internal ) - { - int pathCheckEnd = m_PathIdx + 5; - - if ( m_Path.Count < pathCheckEnd ) - pathCheckEnd = m_Path.Count; - - Visible = false; - - if ( m_PathIdx > 0 ) // move to the next location - MoveToWorld( m_Path[m_PathIdx - 1] ); - - Point3D pTop = new Point3D( GetWorldLocation() ), pBottom = new Point3D( m_Path[pathCheckEnd-1] ); - Utility.FixPoints( ref pTop, ref pBottom ); - - for ( int i = m_PathIdx; i < pathCheckEnd; i++ ) - { - Point3D point = m_Path[i]; - - LandTile landTile = Map.Tiles.GetLandTile( point.X, point.Y ); - int landZ = 0, landAvg = 0, landTop = 0; - Map.GetAverageZ( point.X, point.Y, ref landZ, ref landAvg, ref landTop ); - - if ( landZ <= point.Z && landTop >= point.Z && !landTile.Ignored ) - { - HitObject( point, landTop, 0 ); - return; - } - - StaticTile[] statics = Map.Tiles.GetStaticTiles( point.X, point.Y, true ); - - if ( landTile.ID == 0x244 && statics.Length == 0 ) // 0x244 = invalid land tile - { - bool empty = true; - IPooledEnumerable eable = Map.GetItemsInRange( point, 0 ); - - foreach ( Item item in eable ) - { - if ( item != this ) - { - empty = false; - break; - } - } - - eable.Free(); - - if ( empty ) - { - HitObject( point, landTop, 0 ); - return; - } - } - - for ( int j = 0; j < statics.Length; j++ ) - { - StaticTile t = statics[j]; - - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - height = id.CalcHeight; - - if ( t.Z <= point.Z && t.Z + height >= point.Z && ( id.Flags & ( TileFlag.Impassable | TileFlag.Wall | TileFlag.NoShoot ) ) != 0 ) - { - if ( i > m_PathIdx ) - point = m_Path[i-1]; - else - point = GetWorldLocation(); - HitObject( point, t.Z, height ); - return; - } - } - } - - Rectangle2D rect = new Rectangle2D( pTop.X, pTop.Y, ( pBottom.X - pTop.X ) + 1, ( pBottom.Y - pTop.Y ) + 1 ); - - IPooledEnumerable area = Map.GetItemsInBounds( rect ); - foreach ( Item i in area ) - { - if ( i == this || i.ItemID >= 0x4000 ) - continue; - - if ( i is BRGoal ) - { - height = 17; - } - else if ( i is Blocker ) - { - height = 20; - } - else - { - ItemData id = i.ItemData; - if ( ( id.Flags & (TileFlag.Impassable | TileFlag.Wall | TileFlag.NoShoot)) == 0 ) - continue; - height = id.CalcHeight; - } - - Point3D point = i.Location; - Point3D loc = i.Location; - for ( int j = m_PathIdx; j < pathCheckEnd; j++ ) - { - point = m_Path[j]; - - if ( loc.X == point.X && loc.Y == point.Y && - ( (i is Blocker ) || ( loc.Z <= point.Z && loc.Z + height >= point.Z ) ) ) - { - found = true; - if ( j > m_PathIdx ) - point = m_Path[j-1]; - else - point = GetWorldLocation(); - break; - } - } - - if ( !found ) - continue; - - area.Free(); - if ( i is BRGoal goal ) - { - Point3D oldLoc = new Point3D( GetWorldLocation() ); - if ( CheckScore( goal, Thrower, 3 ) ) - DoAnim( oldLoc, point, Map ); - else - HitObject( point, loc.Z, height ); - } - else - { - HitObject( point, loc.Z, height ); - } - return; - } - - area.Free(); - - IPooledEnumerable clients = Map.GetClientsInBounds( rect ); - foreach ( NetState ns in clients) - { - Mobile m = ns.Mobile; - - if ( m == null || m == Thrower ) - continue; - - Point3D point; - Point3D loc = m.Location; - - for ( int j = m_PathIdx; j < pathCheckEnd && !found; j++ ) - { - point = m_Path[j]; - - if ( loc.X == point.X && loc.Y == point.Y && - loc.Z <= point.Z && loc.Z + 16 >= point.Z ) - { - found = CheckCatch( m, point ); - } - } - - if ( !found ) - continue; - - clients.Free(); - - // TODO: probably need to change this a lot... - DoCatch( m ); - - return; - } - - clients.Free(); - - m_PathIdx = pathCheckEnd; - - if ( m_PathIdx > 0 && m_PathIdx - 1 < m_Path.Count ) - DoAnim( GetWorldLocation(), m_Path[m_PathIdx - 1], Map ); - - Timer.DelayCall( TimeSpan.FromSeconds( 0.1 ), ContinueFlight ).Start(); - } - else - { - if ( m_PathIdx > 0 && m_PathIdx - 1 < m_Path.Count ) - MoveToWorld( m_Path[m_PathIdx - 1] ); - else if ( m_Path.Count > 0 ) - MoveToWorld( m_Path.Last ); - - int myZ = Map.GetAverageZ( X, Y ); - - StaticTile[] statics = Map.Tiles.GetStaticTiles( X, Y, true ); - for ( int j = 0; j < statics.Length; j++ ) - { - StaticTile t = statics[j]; - - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - height = id.CalcHeight; - - if ( t.Z + height > myZ && t.Z + height <= Z ) - myZ = t.Z + height; - } - - IPooledEnumerable eable = GetItemsInRange( 0 ); - foreach ( Item item in eable ) - { - if ( item.Visible && item != this ) - { - height = item.ItemData.CalcHeight; - if ( item.Z + height > myZ && item.Z + height <= Z ) - myZ = item.Z + height; - } - } - eable.Free(); - - Z = myZ; - m_Flying = false; - Visible = true; - - m_Path.Clear(); - m_PathIdx = 0; - } - } - - public Mobile Thrower { get; private set; } - - public bool CheckScore( BRGoal goal, Mobile m, int points ) - { - if ( m_Game == null || m == null || goal == null ) - return false; - - BRTeamInfo team = m_Game.GetTeamInfo( m ); - if ( team == null || goal.Team == null || team == goal.Team ) - return false; - - if ( points > 3 ) - m_Game.Alert( "Touchdown {0} ({1})!", team.Name, m.Name ); - else - m_Game.Alert( "Field goal {0} ({1})!", team.Name, m.Name ); + public class BRBomb : Item + { + private bool m_Flying; - for (int i = m_Helpers.Count - 1; i >= 0; i--) - { - Mobile mob = (Mobile)m_Helpers[i]; - - BRPlayerInfo pi = team[mob]; - if ( pi != null ) - { - if ( mob == m ) - pi.Captures += points; - - pi.Score += points + 1; - - points /= 2; - } - } - - m_Game.ReturnBomb(); - - m_Flying = false; - Visible = true; - m_Path.Clear(); - m_PathIdx = 0; - - Target.Cancel( m ); - - return true; - } - - private bool TakeBomb( Mobile m, BRTeamInfo team, string verb ) - { - if ( !m.Player || !m.Alive || m.NetState == null ) - return false; - - if ( m.PlaceInBackpack( this ) ) - { - m.RevealingAction(); - - m.LocalOverheadMessage( MessageType.Regular, 0x59, false, "You got the bomb!" ); - m_Game.Alert( "{1} ({2}) {0} the bomb!", verb, m.Name, team.Name ); - - m.Target = new BombTarget( this, m ); - - if ( m_Helpers.Contains( m ) ) - m_Helpers.Remove( m ); - - if ( m_Helpers.Count > 0 ) - { - Mobile last = (Mobile)m_Helpers[0]; - - if ( m_Game.GetTeamInfo( last ) != team ) - m_Helpers.Clear(); - } - - m_Helpers.Add( m ); - - return true; - } - - return false; - } - } - - public class BRGoal : BaseAddon - { - private bool m_North; - - [CommandProperty( AccessLevel.GameMaster )] - public bool North { get => m_North; - set { m_North = value; Remake(); } } - - private static AddonComponent SetHue( AddonComponent ac, int hue ) - { - ac.Hue = hue; - return ac; - } - - private void Remake() - { - foreach ( AddonComponent ac in Components ) - { - ac.Addon = null; - ac.Delete(); - } - - Components.Clear(); - - // stairs - AddComponent( new AddonComponent( 0x74D ), -1, +1, -5 ); - AddComponent( new AddonComponent( 0x71F ), 0, +1, -5 ); - AddComponent( new AddonComponent( 0x74B ), +1, +1, -5 ); - AddComponent( new AddonComponent( 0x736 ), +1, 0, -5 ); - AddComponent( new AddonComponent( 0x74C ), +1, -1, -5 ); - AddComponent( new AddonComponent( 0x737 ), 0, -1, -5 ); - AddComponent( new AddonComponent( 0x74A ), -1, -1, -5 ); - AddComponent( new AddonComponent( 0x749 ), -1, 0, -5 ); - - // Center Sparkle - AddComponent( new AddonComponent( 0x375A ), 0, 0, -1 ); - - if ( !m_North ) - { - // Pillars - AddComponent( new AddonComponent( 0x0CE ), 0, +1, -2 ); - AddComponent( new AddonComponent( 0x0CC ), 0, -1, -2 ); - AddComponent( new AddonComponent( 0x0D0 ), 0, 0, -2 ); - - // Yellow parts - AddComponent( SetHue( new AddonComponent( 0x0DF ), 0x499 ), 0, +1, 7 ); - AddComponent( SetHue( new AddonComponent( 0x0DF ), 0x499 ), 0, 0, 16 ); - AddComponent( SetHue( new AddonComponent( 0x0DF ), 0x499 ), 0, -1, 7 ); - - // Blue Sparkles - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), 0, +1, 12 ); - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), 0, +1, -1 ); - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), 0, -1, 12 ); - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), 0, -1, -1 ); - } - else - { - // Pillars - AddComponent( new AddonComponent( 0x0CF ), +1, 0, -2 ); - AddComponent( new AddonComponent( 0x0CC ), -1, 0, -2 ); - AddComponent( new AddonComponent( 0x0D1 ), 0, 0, -2 ); - - // Yellow parts - AddComponent( SetHue( new AddonComponent( 0x0DF ), 0x499 ), +1, 0, 7 ); - AddComponent( SetHue( new AddonComponent( 0x0DF ), 0x499 ), 0, 0, 16 ); - AddComponent( SetHue( new AddonComponent( 0x0DF ), 0x499 ), -1, 0, 7 ); - - // Blue Sparkles - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), +1, 0, 12 ); - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), +1, 0, -1 ); - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), -1, 0, 12 ); - AddComponent( SetHue( new AddonComponent( 0x377A ), 0x84C ), -1, 0, -1 ); - } - } - - public override string DefaultName => "Bombing Run Goal"; - - [Constructible] - public BRGoal() - { - ItemID = 0x51D; - Hue = 0x84C; - Visible = true; - - Remake(); - } - - public BRGoal( Serial serial ) : base( serial ) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize (writer); - - writer.Write( (int)1 ); // version - - writer.Write( m_North ); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize (reader); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_North = reader.ReadBool(); - goto case 0; - } - case 0: - { - break; - } - } - - Hue = 0x84C; - } - - public override bool ShareHue => false; - - public BRTeamInfo Team - { - get => m_Team; - set - { - m_Team = value; - if ( m_Team != null && m_Team.Color != 0 ) - Hue = m_Team.Color; - else - Hue = 0x84C; - } - } - - private BRTeamInfo m_Team; - - public override bool OnMoveOver( Mobile m ) - { - if ( !Visible ) - return true; - - if ( m == null || !m.Player || !m.Alive || m.Backpack == null || m_Team?.Game == null ) - return true; - - if ( !base.OnMoveOver( m ) ) - return false; - - if ( m_Team != null && m_Team.Color != 0 ) - Hue = m_Team.Color; - else - Hue = 0x84C; - - if ( m.Backpack.FindItemByType( typeof( BRBomb ), true ) is BRBomb b ) - b.CheckScore( this, m, 7 ); - - return true; - } - } - - public sealed class BRBoard : Item - { - public override string DefaultName => "Scoreboard"; - - public BRTeamInfo m_TeamInfo; - - [Constructible] - public BRBoard() - : base( 7774 ) - { - Movable = false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_TeamInfo?.Game != null ) - { - from.CloseGump( typeof( BRBoardGump ) ); - from.SendGump( new BRBoardGump( from, m_TeamInfo.Game ) ); - } - } - - public BRBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BRBoardGump : Gump - { - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - private void AddBorderedText( int x, int y, int width, int height, string text, int color, int borderColor ) - { - AddColoredText( x - 1, y - 1, width, height, text, borderColor ); - AddColoredText( x - 1, y + 1, width, height, text, borderColor ); - AddColoredText( x + 1, y - 1, width, height, text, borderColor ); - AddColoredText( x + 1, y + 1, width, height, text, borderColor ); - AddColoredText( x, y, width, height, text, color ); - } - - private void AddColoredText( int x, int y, int width, int height, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, height, text, false, false ); - else - AddHtml( x, y, width, height, Color( text, color ), false, false ); - } - - private const int LabelColor32 = 0xFFFFFF; - private const int BlackColor32 = 0x000000; - - private BRGame m_Game; - - public BRBoardGump( Mobile mob, BRGame game ) - : this( mob, game, null ) - { - } - - public BRBoardGump( Mobile mob, BRGame game, BRTeamInfo section ) - : base( 60, 60 ) - { - m_Game = game; - - BRTeamInfo ourTeam = game.GetTeamInfo( mob ); - - ArrayList entries = new ArrayList(); - - if ( section == null ) - { - for ( int i = 0; i < game.Context.Participants.Count; ++i ) - { - BRTeamInfo teamInfo = game.Controller.TeamInfo[i % game.Controller.TeamInfo.Length]; - - if ( teamInfo == null ) - continue; - - entries.Add( teamInfo ); - } - } - else - { - foreach ( BRPlayerInfo player in section.Players.Values ) - { - if ( player.Score > 0 ) - entries.Add( player ); - } - } - - entries.Sort(); - /* - delegate( IRankedCTF a, IRankedCTF b ) - { - return b.Score - a.Score; - } );*/ + private BRGame m_Game; - int height = 0; + private ArrayList m_Helpers; - if ( section == null ) - height = 73 + ( entries.Count * 75 ) + 28; + private Point3DList m_Path = new Point3DList(); + private int m_PathIdx; + private EffectTimer m_Timer; - Closable = false; + public BRBomb(BRGame game) : + base(0x103C) // 0x103C = bread, 0x1042 = pie, 0x1364 = rock, 0x13a8 = pillow, 0x2256 = bagball + { + Movable = false; + Hue = 0x35; - AddPage( 0 ); + m_Game = game; - AddBackground( 1, 1, 398, height, 3600 ); + m_Helpers = new ArrayList(); - AddImageTiled( 16, 15, 369, height - 29, 3604 ); + m_Timer = new EffectTimer(this); + m_Timer.Start(); + } - for ( int i = 0; i < entries.Count; i += 1 ) - AddImageTiled( 22, 58 + ( i * 75 ), 357, 70, 0x2430 ); + public BRBomb(Serial serial) : base(serial) + { + } - AddAlphaRegion( 16, 15, 369, height - 29 ); + public override string DefaultName => "da bomb"; - AddImage( 215, -45, 0xEE40 ); - //AddImage( 330, 141, 0x8BA ); + public Mobile Thrower{ get; private set; } - AddBorderedText( 22, 22, 294, 20, Center( "BR Scoreboard" ), LabelColor32, BlackColor32 ); + private Mobile FindOwner(object parent) + { + if (parent is Item item) + return item.RootParent as Mobile; - AddImageTiled( 32, 50, 264, 1, 9107 ); - AddImageTiled( 42, 52, 264, 1, 9157 ); + if (parent is Mobile mobile) + return mobile; - if ( section == null ) - { - for ( int i = 0; i < entries.Count; ++i ) - { - BRTeamInfo teamInfo = entries[i] as BRTeamInfo; + return null; + } - AddImage( 30, 70 + ( i * 75 ), 10152 ); - AddImage( 30, 85 + ( i * 75 ), 10151 ); - AddImage( 30, 100 + ( i * 75 ), 10151 ); - AddImage( 30, 106 + ( i * 75 ), 10154 ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - AddImage( 24, 60 + ( i * 75 ), teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1 ); + int version = reader.ReadInt(); - int nameColor = LabelColor32; - int borderColor = BlackColor32; + switch (version) + { + case 0: + { + break; + } + } - switch ( teamInfo.Color ) - { - case 0x47E: - nameColor = 0xFFFFFF; - break; + Timer.DelayCall(TimeSpan.Zero, Delete).Start(); // delete this after the world loads + } - case 0x4F2: - nameColor = 0x3399FF; - break; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - case 0x4F7: - nameColor = 0x33FF33; - break; + writer.Write(0); // version + } - case 0x4FC: - nameColor = 0xFF00FF; - break; - - case 0x021: - nameColor = 0xFF3333; - break; - - case 0x01A: - nameColor = 0xFF66FF; - break; - - case 0x455: - nameColor = 0x333333; - borderColor = 0xFFFFFF; - break; - } - - AddBorderedText( 60, 65 + ( i * 75 ), 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name}", nameColor, borderColor ); - - AddBorderedText( 50 + 10, 85 + ( i * 75 ), 100, 20, "Score:", 0xFFC000, BlackColor32 ); - AddBorderedText( 50 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Score.ToString( "N0" ), 0xFFC000, BlackColor32 ); - - AddBorderedText( 110 + 10, 85 + ( i * 75 ), 100, 20, "Kills:", 0xFFC000, BlackColor32 ); - AddBorderedText( 110 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Kills.ToString( "N0" ), 0xFFC000, BlackColor32 ); - - AddBorderedText( 160 + 10, 85 + ( i * 75 ), 100, 20, "Points:", 0xFFC000, BlackColor32 ); - AddBorderedText( 160 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Captures.ToString( "N0" ), 0xFFC000, BlackColor32 ); - - BRPlayerInfo pl = teamInfo.Leader; - - AddBorderedText( 235 + 10, 85 + ( i * 75 ), 250, 20, "Leader:", 0xFFC000, BlackColor32 ); - - if ( pl != null ) - AddBorderedText( 235 + 15, 105 + ( i * 75 ), 250, 20, pl.Player.Name, 0xFFC000, BlackColor32 ); - } - } + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - AddButton( 314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0 ); - } - } + Mobile mob = FindOwner(parent); - public sealed class BRPlayerInfo : IRankedCTF, IComparable - { - private BRTeamInfo m_TeamInfo; + if (mob != null) mob.SolidHueOverride = 0x0499; + } - private int m_Kills; - private int m_Captures; + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); - private int m_Score; + Mobile mob = FindOwner(parent); - public Mobile Player { get; } + if (mob != null && m_Game != null) + mob.SolidHueOverride = m_Game.GetColor(mob); + } - public int CompareTo( object obj ) - { - BRPlayerInfo pi = (BRPlayerInfo)obj; - int res = pi.Captures.CompareTo( Captures ); - if ( res == 0 ) - { - res = pi.Score.CompareTo( Score ); + public void DropTo(Mobile mob, Mobile killer) + { + if (mob != null && !mob.Deleted) + MoveToWorld(mob.Location, mob.Map); + else if (killer != null && !killer.Deleted) + MoveToWorld(killer.Location, killer.Map); + else + m_Game?.ReturnBomb(); + } - if ( res == 0 ) - res = pi.Kills.CompareTo( Kills ); - } - return res; - } + public override bool OnMoveOver(Mobile m) + { + if (m_Flying || !Visible || m_Game == null || m == null || !m.Alive) + return true; - public string Name => Player.Name; - - public int Kills - { - get => m_Kills; - set - { - m_TeamInfo.Kills += ( value - m_Kills ); - m_Kills = value; - } - } - - public int Captures - { - get => m_Captures; - set - { - m_TeamInfo.Captures += ( value - m_Captures ); - m_Captures = value; - } - } - - public int Score - { - get => m_Score; - set - { - m_TeamInfo.Score += ( value - m_Score ); - m_Score = value; - - if ( m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score ) - m_TeamInfo.Leader = this; - } - } - - public BRPlayerInfo( BRTeamInfo teamInfo, Mobile player ) - { - m_TeamInfo = teamInfo; - Player = player; - } - } - - [PropertyObject] - public sealed class BRTeamInfo : IRankedCTF, IComparable - { - private BRGoal m_Goal; - - public int CompareTo( object obj ) - { - BRTeamInfo ti = (BRTeamInfo)obj; - int res = ti.Captures.CompareTo( Captures ); - if ( res == 0 ) - { - res = ti.Score.CompareTo( Score ); - - if ( res == 0 ) - res = ti.Kills.CompareTo( Kills ); - } - return res; - } - - public string Name => $"{TeamName} Team"; - - public BRGame Game { get; set; } - - public int TeamID { get; } - - public int Kills { get; set; } - - public int Captures { get; set; } - - public int Score { get; set; } - - public BRPlayerInfo Leader { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public BRBoard Board { get; set; } - - public Hashtable Players { get; } - - public BRPlayerInfo this[Mobile mob] - { - get - { - if ( mob == null ) - return null; - - if ( !(Players[mob] is BRPlayerInfo val) ) - Players[mob] = val = new BRPlayerInfo( this, mob ); - - return val; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Color { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string TeamName { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public BRGoal Goal - { - get => m_Goal; - set - { - m_Goal = value; - if ( m_Goal != null ) - m_Goal.Team = this; - } - } - - public BRTeamInfo( int teamID ) - { - TeamID = teamID; - Players = new Hashtable(); - } - - public void Reset() - { - Kills = 0; - Captures = 0; - Score = 0; - - Leader = null; - - Players.Clear(); - - if ( Board != null ) - Board.m_TeamInfo = this; - if ( m_Goal != null ) - m_Goal.Team = this; - } - - public BRTeamInfo( int teamID, GenericReader ip ) - { - TeamID = teamID; - Players = new Hashtable(); + BRTeamInfo useTeam = m_Game.GetTeamInfo(m); + if (useTeam == null) + return true; - int version = ip.ReadEncodedInt(); + return TakeBomb(m, useTeam, "picked up"); + } - switch ( version ) - { - case 0: - { - Board = ip.ReadItem() as BRBoard; - TeamName = ip.ReadString(); - Color = ip.ReadEncodedInt(); - m_Goal = ip.ReadItem() as BRGoal; - break; - } - } - } + public override void OnLocationChange(Point3D oldLocation) + { + base.OnLocationChange(oldLocation); - public void Serialize( GenericWriter op ) - { - op.WriteEncodedInt( 0 ); // version + if (m_Flying || !Visible || m_Game == null || Parent != null) + return; - op.Write( Board ); + IPooledEnumerable eable = GetClientsInRange(0); + foreach (NetState ns in eable) + { + Mobile m = ns.Mobile; - op.Write( TeamName ); + if (m == null || !m.Player || !m.Alive) + continue; - op.WriteEncodedInt( Color ); + BRTeamInfo useTeam = m_Game.GetTeamInfo(m); + if (useTeam != null) + TakeBomb(m, useTeam, "got"); + } + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Timer?.Stop(); + } - op.Write( m_Goal ); - } + public override void OnDoubleClick(Mobile m) + { + if (m_Game == null || !Visible || m == null || !m.Alive) + return; - public override string ToString() - { - if ( TeamName != null ) - return $"({Name}) ..."; - return "..."; - } - } + if (!m_Flying && IsChildOf(m.Backpack)) + m.Target = new BombTarget(this, m); + else if (Parent == null) + if (m.InRange(Location, 1) && m.Location.Z != Z) + { + BRTeamInfo useTeam = m_Game.GetTeamInfo(m); + if (useTeam == null) + return; - public sealed class BRController : EventController - { - public BRTeamInfo[] TeamInfo { get; private set; } + TakeBomb(m, useTeam, "grabbed"); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public BRTeamInfo Team1 { get => TeamInfo[0]; - set { } } + private bool OnBombTarget(Mobile from, object obj) + { + if (m_Game == null) + return true; - [CommandProperty( AccessLevel.GameMaster )] - public BRTeamInfo Team2 { get => TeamInfo[1]; - set { } } + if (!IsChildOf(from.Backpack)) + return true; - [CommandProperty( AccessLevel.GameMaster )] - public BRTeamInfo Team3 { get => TeamInfo[2]; - set { } } + // don't let them throw it to themselves + if (obj == from) + return false; - [CommandProperty( AccessLevel.GameMaster )] - public BRTeamInfo Team4 { get => TeamInfo[3]; - set { } } + if (!(obj is IPoint3D)) + return false; + + Point3D pt = new Point3D((IPoint3D)obj); + + if (obj is Mobile) + pt.Z += 10; + else if (obj is Item item) + pt.Z += item.ItemData.CalcHeight + 1; + + m_Flying = true; + Visible = false; + Thrower = from; + MoveToWorld(GetWorldLocation(), from.Map); + + BeginFlight(pt); + return true; + } + + private void HitObject(Point3D ballLoc, int objZ, int objHeight) + { + DoAnim(GetWorldLocation(), ballLoc, Map); + MoveToWorld(ballLoc); + + m_Path.Clear(); + m_PathIdx = 0; + + Timer.DelayCall(TimeSpan.FromSeconds(0.05), ContinueFlight).Start(); + } + + private bool CheckCatch(Mobile m, Point3D myLoc) + { + if (m == null || !m.Alive || !m.Player || m_Game == null) + return false; + + if (m_Game.GetTeamInfo(m) == null) + return false; + + int zdiff = myLoc.Z - m.Z; + + if (zdiff < 0) + return false; + if (zdiff < 12) + return true; + if (zdiff < 16) + return Utility.RandomBool(); // 50% chance + + return false; + } + + private void DoAnim(Point3D start, Point3D end, Map map) + { + Effects.SendMovingEffect(new Entity(Serial.Zero, start, map), new Entity(Serial.Zero, end, map), + ItemID, 15, 0, false, false, Hue, 0); + } + + private void DoCatch(Mobile m) + { + m_Flying = false; + Visible = true; + + if (m == null || !m.Alive || !m.Player || m_Game == null) + return; + + BRTeamInfo useTeam = m_Game.GetTeamInfo(m); + + if (useTeam == null) + return; + + DoAnim(GetWorldLocation(), m.Location, m.Map); + + string verb = "caught"; + + if (Thrower != null && m_Game.GetTeamInfo(Thrower) != useTeam) + verb = "intercepted"; + + if (!TakeBomb(m, useTeam, verb)) + MoveToWorld(m.Location, m.Map); + } + + private void BeginFlight(Point3D dest) + { + Point3D org = GetWorldLocation(); + + org.Z += 10; // always add 10 at the start cause we're coming from a mobile's eye level + + /*if ( org.X > dest.X || ( org.X == dest.X && org.Y > dest.Y ) || ( org.X == dest.X && org.Y == dest.Y && org.Z > dest.Z ) ) + { + Point3D swap = org; + org = dest; + dest = swap; + }*/ + + ArrayList list = new ArrayList(); + double rise, run, zslp; + double dist3d, dist2d; + double x, y, z; + int xd, yd, zd; + Point3D p; + + xd = dest.X - org.X; + yd = dest.Y - org.Y; + zd = dest.Z - org.Z; + dist2d = Math.Sqrt(xd * xd + yd * yd); + if (zd != 0) + dist3d = Math.Sqrt(dist2d * dist2d + zd * zd); + else + dist3d = dist2d; + + rise = yd / dist3d; + run = xd / dist3d; + zslp = zd / dist3d; + + x = org.X; + y = org.Y; + z = org.Z; + while (Utility.NumberBetween(x, dest.X, org.X, 0.5) && Utility.NumberBetween(y, dest.Y, org.Y, 0.5) && + Utility.NumberBetween(z, dest.Z, org.Z, 0.5)) + { + int ix = (int)Math.Round(x); + int iy = (int)Math.Round(y); + int iz = (int)Math.Round(z); + + if (list.Count > 0) + { + p = (Point3D)list[list.Count - 1]; + + if (p.X != ix || p.Y != iy || p.Z != iz) + list.Add(new Point3D(ix, iy, iz)); + } + else + { + list.Add(new Point3D(ix, iy, iz)); + } + + x += run; + y += rise; + z += zslp; + } + + if (list.Count > 0) + if ((Point3D)list[list.Count - 1] != dest) + list.Add(dest); + + /*if ( dist3d > 4 && ( dest.X != org.X || dest.Y != org.Y ) ) + { + int count = list.Count; + int i; + int climb = count / 2; + if ( climb > 3 ) + climb = 3; + + for ( i = 0; i < climb; i++ ) + { + p = ((Point3D)list[i]); + p.Z += (i+1) * 4; + list[i] = p; + } + + for ( ; i < count - climb; i++ ) + { + p = ((Point3D)list[i]); + p.Z += 16; + list[i] = p; + } + + for ( i = climb; i > 0; i-- ) + { + p = ((Point3D)list[i]); + p.Z += i * 4; + list[i] = p; + } + }*/ + + if (dist2d > 1) + { + int count = list.Count; + double height = count * 2 * (Utility.RandomDouble() * 0.40 + 0.10); // 10 - 50% + double coeff = -height / (count * count / 4.0); + + for (int i = 0; i < count; i++) + { + p = (Point3D)list[i]; + + int xp = i - count / 2; + + p.Z += (int)Math.Ceiling(coeff * xp * xp + height); + + list[i] = p; + } + } + + m_Path.Clear(); + for (int i = 0; i < list.Count; i++) + m_Path.Add((Point3D)list[i]); + + m_PathIdx = 0; + + ContinueFlight(); + } + + private void ContinueFlight() + { + int height; + bool found = false; + + if (m_PathIdx < m_Path.Count && Map?.Tiles != null && Map != Map.Internal) + { + int pathCheckEnd = m_PathIdx + 5; + + if (m_Path.Count < pathCheckEnd) + pathCheckEnd = m_Path.Count; + + Visible = false; + + if (m_PathIdx > 0) // move to the next location + MoveToWorld(m_Path[m_PathIdx - 1]); + + Point3D pTop = new Point3D(GetWorldLocation()), pBottom = new Point3D(m_Path[pathCheckEnd - 1]); + Utility.FixPoints(ref pTop, ref pBottom); + + for (int i = m_PathIdx; i < pathCheckEnd; i++) + { + Point3D point = m_Path[i]; + + LandTile landTile = Map.Tiles.GetLandTile(point.X, point.Y); + int landZ = 0, landAvg = 0, landTop = 0; + Map.GetAverageZ(point.X, point.Y, ref landZ, ref landAvg, ref landTop); + + if (landZ <= point.Z && landTop >= point.Z && !landTile.Ignored) + { + HitObject(point, landTop, 0); + return; + } + + StaticTile[] statics = Map.Tiles.GetStaticTiles(point.X, point.Y, true); + + if (landTile.ID == 0x244 && statics.Length == 0) // 0x244 = invalid land tile + { + bool empty = true; + IPooledEnumerable eable = Map.GetItemsInRange(point, 0); + + foreach (Item item in eable) + if (item != this) + { + empty = false; + break; + } + + eable.Free(); + + if (empty) + { + HitObject(point, landTop, 0); + return; + } + } + + for (int j = 0; j < statics.Length; j++) + { + StaticTile t = statics[j]; + + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + height = id.CalcHeight; + + if (t.Z <= point.Z && t.Z + height >= point.Z && + (id.Flags & (TileFlag.Impassable | TileFlag.Wall | TileFlag.NoShoot)) != 0) + { + if (i > m_PathIdx) + point = m_Path[i - 1]; + else + point = GetWorldLocation(); + HitObject(point, t.Z, height); + return; + } + } + } + + Rectangle2D rect = new Rectangle2D(pTop.X, pTop.Y, pBottom.X - pTop.X + 1, pBottom.Y - pTop.Y + 1); + + IPooledEnumerable area = Map.GetItemsInBounds(rect); + foreach (Item i in area) + { + if (i == this || i.ItemID >= 0x4000) + continue; + + if (i is BRGoal) + { + height = 17; + } + else if (i is Blocker) + { + height = 20; + } + else + { + ItemData id = i.ItemData; + if ((id.Flags & (TileFlag.Impassable | TileFlag.Wall | TileFlag.NoShoot)) == 0) + continue; + height = id.CalcHeight; + } + + Point3D point = i.Location; + Point3D loc = i.Location; + for (int j = m_PathIdx; j < pathCheckEnd; j++) + { + point = m_Path[j]; + + if (loc.X == point.X && loc.Y == point.Y && + (i is Blocker || loc.Z <= point.Z && loc.Z + height >= point.Z)) + { + found = true; + if (j > m_PathIdx) + point = m_Path[j - 1]; + else + point = GetWorldLocation(); + break; + } + } + + if (!found) + continue; + + area.Free(); + if (i is BRGoal goal) + { + Point3D oldLoc = new Point3D(GetWorldLocation()); + if (CheckScore(goal, Thrower, 3)) + DoAnim(oldLoc, point, Map); + else + HitObject(point, loc.Z, height); + } + else + { + HitObject(point, loc.Z, height); + } + + return; + } + + area.Free(); + + IPooledEnumerable clients = Map.GetClientsInBounds(rect); + foreach (NetState ns in clients) + { + Mobile m = ns.Mobile; + + if (m == null || m == Thrower) + continue; + + Point3D point; + Point3D loc = m.Location; + + for (int j = m_PathIdx; j < pathCheckEnd && !found; j++) + { + point = m_Path[j]; + + if (loc.X == point.X && loc.Y == point.Y && + loc.Z <= point.Z && loc.Z + 16 >= point.Z) + found = CheckCatch(m, point); + } + + if (!found) + continue; + + clients.Free(); + + // TODO: probably need to change this a lot... + DoCatch(m); + + return; + } + + clients.Free(); + + m_PathIdx = pathCheckEnd; + + if (m_PathIdx > 0 && m_PathIdx - 1 < m_Path.Count) + DoAnim(GetWorldLocation(), m_Path[m_PathIdx - 1], Map); + + Timer.DelayCall(TimeSpan.FromSeconds(0.1), ContinueFlight).Start(); + } + else + { + if (m_PathIdx > 0 && m_PathIdx - 1 < m_Path.Count) + MoveToWorld(m_Path[m_PathIdx - 1]); + else if (m_Path.Count > 0) + MoveToWorld(m_Path.Last); + + int myZ = Map.GetAverageZ(X, Y); + + StaticTile[] statics = Map.Tiles.GetStaticTiles(X, Y, true); + for (int j = 0; j < statics.Length; j++) + { + StaticTile t = statics[j]; + + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + height = id.CalcHeight; + + if (t.Z + height > myZ && t.Z + height <= Z) + myZ = t.Z + height; + } + + IPooledEnumerable eable = GetItemsInRange(0); + foreach (Item item in eable) + if (item.Visible && item != this) + { + height = item.ItemData.CalcHeight; + if (item.Z + height > myZ && item.Z + height <= Z) + myZ = item.Z + height; + } + + eable.Free(); + + Z = myZ; + m_Flying = false; + Visible = true; - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan Duration { get; set; } + m_Path.Clear(); + m_PathIdx = 0; + } + } + + public bool CheckScore(BRGoal goal, Mobile m, int points) + { + if (m_Game == null || m == null || goal == null) + return false; + + BRTeamInfo team = m_Game.GetTeamInfo(m); + if (team == null || goal.Team == null || team == goal.Team) + return false; + + if (points > 3) + m_Game.Alert("Touchdown {0} ({1})!", team.Name, m.Name); + else + m_Game.Alert("Field goal {0} ({1})!", team.Name, m.Name); + + for (int i = m_Helpers.Count - 1; i >= 0; i--) + { + Mobile mob = (Mobile)m_Helpers[i]; + + BRPlayerInfo pi = team[mob]; + if (pi != null) + { + if (mob == m) + pi.Captures += points; + + pi.Score += points + 1; + + points /= 2; + } + } + + m_Game.ReturnBomb(); + + m_Flying = false; + Visible = true; + m_Path.Clear(); + m_PathIdx = 0; + + Target.Cancel(m); + + return true; + } + + private bool TakeBomb(Mobile m, BRTeamInfo team, string verb) + { + if (!m.Player || !m.Alive || m.NetState == null) + return false; + + if (m.PlaceInBackpack(this)) + { + m.RevealingAction(); + + m.LocalOverheadMessage(MessageType.Regular, 0x59, false, "You got the bomb!"); + m_Game.Alert("{1} ({2}) {0} the bomb!", verb, m.Name, team.Name); + + m.Target = new BombTarget(this, m); + + if (m_Helpers.Contains(m)) + m_Helpers.Remove(m); + + if (m_Helpers.Count > 0) + { + Mobile last = (Mobile)m_Helpers[0]; + + if (m_Game.GetTeamInfo(last) != team) + m_Helpers.Clear(); + } + + m_Helpers.Add(m); + + return true; + } + + return false; + } + + private class EffectTimer : Timer + { + private BRBomb m_Bomb; + private int m_Count; + + public EffectTimer(BRBomb bomb) : base(TimeSpan.Zero, TimeSpan.FromSeconds(1.0)) + { + m_Bomb = bomb; + m_Count = 0; + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + if (m_Bomb.Parent == null && m_Bomb.m_Game?.Controller != null) + { + if (!m_Bomb.m_Flying && m_Bomb.Map != Map.Internal) + Effects.SendLocationEffect(m_Bomb.GetWorldLocation(), m_Bomb.Map, 0x377A, 16, 10, m_Bomb.Hue, 0); + + if (m_Bomb.Location != m_Bomb.m_Game.Controller.BombHome) + { + if (++m_Count >= 30) + { + m_Bomb.m_Game.ReturnBomb(); + m_Bomb.m_Game.Alert("The bomb has been returned to it's starting point."); + + m_Count = 0; + m_Bomb.m_Helpers.Clear(); + } + } + else + { + m_Count = 0; + } + } + else + { + m_Count = 0; + } + } + } + + private class BombTarget : Target + { + private BRBomb m_Bomb; + private Mobile m_Mob; + private bool m_Resend = true; + + public BombTarget(BRBomb bomb, Mobile from) : base(10, true, TargetFlags.None) + { + CheckLOS = false; + + m_Bomb = bomb; + m_Mob = from; + + m_Mob.SendMessage(0x26, "Where do you want to throw it?"); + } + + protected override void OnTarget(Mobile from, object targeted) + { + m_Resend = !m_Bomb.OnBombTarget(from, targeted); + } + + protected override void OnTargetUntargetable(Mobile from, object targeted) + { + m_Resend = !m_Bomb.OnBombTarget(from, targeted); + } + + protected override void OnTargetFinish(Mobile from) + { + base.OnTargetFinish(from); + + // has to be delayed in case some other target canceled us... + if (m_Resend) + Timer.DelayCall(TimeSpan.Zero, ResendBombTarget).Start(); + } + + private void ResendBombTarget() + { + // Make sure they still have the bomb, then give them the target back + if (m_Bomb != null && !m_Bomb.Deleted && m_Mob != null && !m_Mob.Deleted && m_Mob.Alive) + if (m_Bomb.IsChildOf(m_Mob)) + m_Mob.Target = new BombTarget(m_Bomb, m_Mob); + } + } + } + + public class BRGoal : BaseAddon + { + private bool m_North; + + private BRTeamInfo m_Team; + + [Constructible] + public BRGoal() + { + ItemID = 0x51D; + Hue = 0x84C; + Visible = true; + + Remake(); + } + + public BRGoal(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool North + { + get => m_North; + set + { + m_North = value; + Remake(); + } + } + + public override string DefaultName => "Bombing Run Goal"; + + public override bool ShareHue => false; + + public BRTeamInfo Team + { + get => m_Team; + set + { + m_Team = value; + if (m_Team != null && m_Team.Color != 0) + Hue = m_Team.Color; + else + Hue = 0x84C; + } + } + + private static AddonComponent SetHue(AddonComponent ac, int hue) + { + ac.Hue = hue; + return ac; + } + + private void Remake() + { + foreach (AddonComponent ac in Components) + { + ac.Addon = null; + ac.Delete(); + } + + Components.Clear(); + + // stairs + AddComponent(new AddonComponent(0x74D), -1, +1, -5); + AddComponent(new AddonComponent(0x71F), 0, +1, -5); + AddComponent(new AddonComponent(0x74B), +1, +1, -5); + AddComponent(new AddonComponent(0x736), +1, 0, -5); + AddComponent(new AddonComponent(0x74C), +1, -1, -5); + AddComponent(new AddonComponent(0x737), 0, -1, -5); + AddComponent(new AddonComponent(0x74A), -1, -1, -5); + AddComponent(new AddonComponent(0x749), -1, 0, -5); + + // Center Sparkle + AddComponent(new AddonComponent(0x375A), 0, 0, -1); + + if (!m_North) + { + // Pillars + AddComponent(new AddonComponent(0x0CE), 0, +1, -2); + AddComponent(new AddonComponent(0x0CC), 0, -1, -2); + AddComponent(new AddonComponent(0x0D0), 0, 0, -2); + + // Yellow parts + AddComponent(SetHue(new AddonComponent(0x0DF), 0x499), 0, +1, 7); + AddComponent(SetHue(new AddonComponent(0x0DF), 0x499), 0, 0, 16); + AddComponent(SetHue(new AddonComponent(0x0DF), 0x499), 0, -1, 7); + + // Blue Sparkles + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), 0, +1, 12); + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), 0, +1, -1); + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), 0, -1, 12); + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), 0, -1, -1); + } + else + { + // Pillars + AddComponent(new AddonComponent(0x0CF), +1, 0, -2); + AddComponent(new AddonComponent(0x0CC), -1, 0, -2); + AddComponent(new AddonComponent(0x0D1), 0, 0, -2); + + // Yellow parts + AddComponent(SetHue(new AddonComponent(0x0DF), 0x499), +1, 0, 7); + AddComponent(SetHue(new AddonComponent(0x0DF), 0x499), 0, 0, 16); + AddComponent(SetHue(new AddonComponent(0x0DF), 0x499), -1, 0, 7); + + // Blue Sparkles + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), +1, 0, 12); + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), +1, 0, -1); + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), -1, 0, 12); + AddComponent(SetHue(new AddonComponent(0x377A), 0x84C), -1, 0, -1); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(m_North); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_North = reader.ReadBool(); + goto case 0; + } + case 0: + { + break; + } + } + + Hue = 0x84C; + } + + public override bool OnMoveOver(Mobile m) + { + if (!Visible) + return true; + + if (m == null || !m.Player || !m.Alive || m.Backpack == null || m_Team?.Game == null) + return true; + + if (!base.OnMoveOver(m)) + return false; + + if (m_Team != null && m_Team.Color != 0) + Hue = m_Team.Color; + else + Hue = 0x84C; + + if (m.Backpack.FindItemByType(typeof(BRBomb), true) is BRBomb b) + b.CheckScore(this, m, 7); + + return true; + } + } + + public sealed class BRBoard : Item + { + public BRTeamInfo m_TeamInfo; + + [Constructible] + public BRBoard() + : base(7774) + { + Movable = false; + } + + public BRBoard(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Scoreboard"; + + public override void OnDoubleClick(Mobile from) + { + if (m_TeamInfo?.Game != null) + { + from.CloseGump(typeof(BRBoardGump)); + from.SendGump(new BRBoardGump(from, m_TeamInfo.Game)); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public Point3D BombHome { get; set; } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override string Title => "Bombing Run"; - public override string DefaultName => "Bombing Run Controller"; + writer.Write(0); + } - public override string GetTeamName( int teamID ) - { - return TeamInfo[teamID % TeamInfo.Length].Name; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override EventGame Construct( DuelContext context ) - { - return new BRGame( this, context ); - } + int version = reader.ReadInt(); + } + } - [Constructible] - public BRController() - { - Visible = false; - Movable = false; + public class BRBoardGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int BlackColor32 = 0x000000; - Duration = TimeSpan.FromMinutes( 30.0 ); + private BRGame m_Game; - BombHome = Point3D.Zero; + public BRBoardGump(Mobile mob, BRGame game) + : this(mob, game, null) + { + } - TeamInfo = new BRTeamInfo[4]; + public BRBoardGump(Mobile mob, BRGame game, BRTeamInfo section) + : base(60, 60) + { + m_Game = game; - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new BRTeamInfo( i ); - } + BRTeamInfo ourTeam = game.GetTeamInfo(mob); - public BRController( Serial serial ) - : base( serial ) - { - } + ArrayList entries = new ArrayList(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (section == null) + for (int i = 0; i < game.Context.Participants.Count; ++i) + { + BRTeamInfo teamInfo = game.Controller.TeamInfo[i % game.Controller.TeamInfo.Length]; - writer.Write( (int) 0 ); + if (teamInfo == null) + continue; - writer.Write( BombHome ); - - writer.Write( Duration ); + entries.Add(teamInfo); + } + else + foreach (BRPlayerInfo player in section.Players.Values) + if (player.Score > 0) + entries.Add(player); - writer.WriteEncodedInt( TeamInfo.Length ); + entries.Sort(); + /* + delegate( IRankedCTF a, IRankedCTF b ) + { + return b.Score - a.Score; + } );*/ - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i].Serialize( writer ); - } + int height = 0; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (section == null) + height = 73 + entries.Count * 75 + 28; - int version = reader.ReadInt(); + Closable = false; - switch ( version ) - { - case 0: - { - BombHome = reader.ReadPoint3D(); + AddPage(0); - Duration = reader.ReadTimeSpan(); + AddBackground(1, 1, 398, height, 3600); - TeamInfo = new BRTeamInfo[reader.ReadEncodedInt()]; + AddImageTiled(16, 15, 369, height - 29, 3604); - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new BRTeamInfo( i, reader ); + for (int i = 0; i < entries.Count; i += 1) + AddImageTiled(22, 58 + i * 75, 357, 70, 0x2430); - break; - } - } - } - } + AddAlphaRegion(16, 15, 369, height - 29); - public sealed class BRGame : EventGame - { - public override bool CantDoAnything( Mobile mob ) - { - if ( mob?.Backpack == null || GetTeamInfo( mob ) == null ) - return false; + AddImage(215, -45, 0xEE40); + //AddImage( 330, 141, 0x8BA ); - Item bomb = mob.Backpack.FindItemByType( typeof( BRBomb ), true ); + AddBorderedText(22, 22, 294, 20, Center("BR Scoreboard"), LabelColor32, BlackColor32); - if ( bomb != null ) - return true; + AddImageTiled(32, 50, 264, 1, 9107); + AddImageTiled(42, 52, 264, 1, 9157); - return false; - } + if (section == null) + for (int i = 0; i < entries.Count; ++i) + { + BRTeamInfo teamInfo = entries[i] as BRTeamInfo; - private BRBomb m_Bomb; + AddImage(30, 70 + i * 75, 10152); + AddImage(30, 85 + i * 75, 10151); + AddImage(30, 100 + i * 75, 10151); + AddImage(30, 106 + i * 75, 10154); - private TimerCallback m_UnhideCallback; + AddImage(24, 60 + i * 75, teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1); - public void ReturnBomb() - { - if ( m_Bomb != null && Controller != null ) - { - if ( m_UnhideCallback == null ) - m_UnhideCallback = UnhideBomb; - m_Bomb.Visible = false; - m_Bomb.MoveToWorld( Controller.BombHome, Controller.Map ); - Timer.DelayCall( TimeSpan.FromSeconds( Utility.RandomMinMax( 5, 15 ) ), m_UnhideCallback ); - } - } - - private void UnhideBomb() - { - if ( m_Bomb != null ) - { - m_Bomb.Visible = true; - m_Bomb.OnLocationChange( m_Bomb.Location ); - } - } + int nameColor = LabelColor32; + int borderColor = BlackColor32; - public BRController Controller { get; } + switch (teamInfo.Color) + { + case 0x47E: + nameColor = 0xFFFFFF; + break; - public void Alert( string text ) - { - m_Context.m_Tournament?.Alert( text ); + case 0x4F2: + nameColor = 0x3399FF; + break; - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - Participant p = m_Context.Participants[i] as Participant; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - if ( p.Players[j] != null ) - p.Players[j].Mobile.SendMessage( 0x35, text ); - } - } - } + case 0x4F7: + nameColor = 0x33FF33; + break; - public void Alert( string format, params object[] args ) - { - Alert( string.Format( format, args ) ); - } + case 0x4FC: + nameColor = 0xFF00FF; + break; - public BRGame( BRController controller, DuelContext context ) : base( context ) - { - Controller = controller; - } - - public Map Facet - { - get - { - if ( m_Context.Arena != null ) - return m_Context.Arena.Facet; - - return Controller.Map; - } - } - - public BRTeamInfo GetTeamInfo( Mobile mob ) - { - int teamID = GetTeamID( mob ); - - if ( teamID >= 0 ) - return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; - - return null; - } - - public int GetTeamID( Mobile mob ) - { - if ( !(mob is PlayerMobile pm) ) - return mob is BaseCreature creature ? creature.Team - 1 : -1; - - if ( pm.DuelContext == null || pm.DuelContext != m_Context ) - return -1; - - if ( pm.DuelPlayer == null || pm.DuelPlayer.Eliminated ) - return -1; - - return pm.DuelContext.Participants.IndexOf( pm.DuelPlayer.Participant ); - } - - public int GetColor( Mobile mob ) - { - return GetTeamInfo( mob )?.Color ?? -1; - } - - private void ApplyHues( Participant p, int hueOverride ) - { - for ( int i = 0; i < p.Players.Length; ++i ) - { - if ( p.Players[i] != null ) - p.Players[i].Mobile.SolidHueOverride = hueOverride; - } - } - - public void DelayBounce( TimeSpan ts, Mobile mob, Container corpse ) - { - Timer.DelayCall( ts, new TimerStateCallback( DelayBounce_Callback ), new object[] { mob, corpse } ); - } - - private void DelayBounce_Callback( object state ) - { - object[] states = (object[]) state; - Mobile mob = (Mobile) states[0]; - Container corpse = (Container) states[1]; - - DuelPlayer dp = null; + case 0x021: + nameColor = 0xFF3333; + break; - if ( mob is PlayerMobile mobile ) - dp = mobile.DuelPlayer; + case 0x01A: + nameColor = 0xFF66FF; + break; - m_Context.RemoveAggressions( mob ); + case 0x455: + nameColor = 0x333333; + borderColor = 0xFFFFFF; + break; + } - if ( dp != null && !dp.Eliminated ) - mob.MoveToWorld( m_Context.Arena.GetBaseStartPoint( GetTeamID( mob ) ), Facet ); - else - m_Context.SendOutside( mob ); + AddBorderedText(60, 65 + i * 75, 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name}", nameColor, + borderColor); - m_Context.Refresh( mob, corpse ); - DuelContext.Debuff( mob ); - DuelContext.CancelSpell( mob ); - mob.Frozen = false; - } + AddBorderedText(50 + 10, 85 + i * 75, 100, 20, "Score:", 0xFFC000, BlackColor32); + AddBorderedText(50 + 15, 105 + i * 75, 100, 20, teamInfo.Score.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(110 + 10, 85 + i * 75, 100, 20, "Kills:", 0xFFC000, BlackColor32); + AddBorderedText(110 + 15, 105 + i * 75, 100, 20, teamInfo.Kills.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(160 + 10, 85 + i * 75, 100, 20, "Points:", 0xFFC000, BlackColor32); + AddBorderedText(160 + 15, 105 + i * 75, 100, 20, teamInfo.Captures.ToString("N0"), 0xFFC000, + BlackColor32); + + BRPlayerInfo pl = teamInfo.Leader; + + AddBorderedText(235 + 10, 85 + i * 75, 250, 20, "Leader:", 0xFFC000, BlackColor32); + + if (pl != null) + AddBorderedText(235 + 15, 105 + i * 75, 250, 20, pl.Player.Name, 0xFFC000, BlackColor32); + } + + AddButton(314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + } + + public sealed class BRPlayerInfo : IRankedCTF, IComparable + { + private int m_Captures; + + private int m_Kills; + + private int m_Score; + private BRTeamInfo m_TeamInfo; + + public BRPlayerInfo(BRTeamInfo teamInfo, Mobile player) + { + m_TeamInfo = teamInfo; + Player = player; + } + + public Mobile Player{ get; } + + public int CompareTo(object obj) + { + BRPlayerInfo pi = (BRPlayerInfo)obj; + int res = pi.Captures.CompareTo(Captures); + if (res == 0) + { + res = pi.Score.CompareTo(Score); + + if (res == 0) + res = pi.Kills.CompareTo(Kills); + } + + return res; + } + + public string Name => Player.Name; + + public int Kills + { + get => m_Kills; + set + { + m_TeamInfo.Kills += value - m_Kills; + m_Kills = value; + } + } + + public int Captures + { + get => m_Captures; + set + { + m_TeamInfo.Captures += value - m_Captures; + m_Captures = value; + } + } + + public int Score + { + get => m_Score; + set + { + m_TeamInfo.Score += value - m_Score; + m_Score = value; + + if (m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score) + m_TeamInfo.Leader = this; + } + } + } + + [PropertyObject] + public sealed class BRTeamInfo : IRankedCTF, IComparable + { + private BRGoal m_Goal; + + public BRTeamInfo(int teamID) + { + TeamID = teamID; + Players = new Hashtable(); + } + + public BRTeamInfo(int teamID, GenericReader ip) + { + TeamID = teamID; + Players = new Hashtable(); + + int version = ip.ReadEncodedInt(); + + switch (version) + { + case 0: + { + Board = ip.ReadItem() as BRBoard; + TeamName = ip.ReadString(); + Color = ip.ReadEncodedInt(); + m_Goal = ip.ReadItem() as BRGoal; + break; + } + } + } + + public BRGame Game{ get; set; } + + public int TeamID{ get; } + + public BRPlayerInfo Leader{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public BRBoard Board{ get; set; } + + public Hashtable Players{ get; } + + public BRPlayerInfo this[Mobile mob] + { + get + { + if (mob == null) + return null; + + if (!(Players[mob] is BRPlayerInfo val)) + Players[mob] = val = new BRPlayerInfo(this, mob); + + return val; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Color{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string TeamName{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public BRGoal Goal + { + get => m_Goal; + set + { + m_Goal = value; + if (m_Goal != null) + m_Goal.Team = this; + } + } + + public int CompareTo(object obj) + { + BRTeamInfo ti = (BRTeamInfo)obj; + int res = ti.Captures.CompareTo(Captures); + if (res == 0) + { + res = ti.Score.CompareTo(Score); + + if (res == 0) + res = ti.Kills.CompareTo(Kills); + } + + return res; + } + + public string Name => $"{TeamName} Team"; + + public int Kills{ get; set; } + + public int Captures{ get; set; } + + public int Score{ get; set; } + + public void Reset() + { + Kills = 0; + Captures = 0; + Score = 0; + + Leader = null; + + Players.Clear(); + + if (Board != null) + Board.m_TeamInfo = this; + if (m_Goal != null) + m_Goal.Team = this; + } + + public void Serialize(GenericWriter op) + { + op.WriteEncodedInt(0); // version - public override bool OnDeath( Mobile mob, Container corpse ) - { - Mobile killer = mob.FindMostRecentDamager( false ); + op.Write(Board); - bool hadBomb = false; + op.Write(TeamName); - Item[] bombs = corpse.FindItemsByType( typeof( BRBomb ), false ); + op.WriteEncodedInt(Color); - for ( int i = 0; i < bombs.Length; ++i ) - ( bombs[i] as BRBomb ).DropTo( mob, killer ); + op.Write(m_Goal); + } - hadBomb = ( hadBomb || bombs.Length > 0 ); - - if ( mob.Backpack != null ) - { - bombs = mob.Backpack.FindItemsByType( typeof( BRBomb ), false ); - - for ( int i = 0; i < bombs.Length; ++i ) - ( bombs[i] as BRBomb ).DropTo( mob, killer ); - - hadBomb = ( hadBomb || bombs.Length > 0 ); - } - - if ( killer != null && killer.Player ) - { - BRTeamInfo teamInfo = GetTeamInfo( killer ); - BRTeamInfo victInfo = GetTeamInfo( mob ); + public override string ToString() + { + if (TeamName != null) + return $"({Name}) ..."; + return "..."; + } + } - if ( teamInfo != null && teamInfo != victInfo ) - { - BRPlayerInfo playerInfo = teamInfo[killer]; + public sealed class BRController : EventController + { + [Constructible] + public BRController() + { + Visible = false; + Movable = false; - if ( playerInfo != null ) - { - playerInfo.Kills += 1; - playerInfo.Score += 1; // base frag + Duration = TimeSpan.FromMinutes(30.0); - if ( hadBomb ) - playerInfo.Score += 4; // fragged bomb carrier - } - } - } + BombHome = Point3D.Zero; - mob.CloseGump( typeof( BRBoardGump ) ); - mob.SendGump( new BRBoardGump( mob, this ) ); + TeamInfo = new BRTeamInfo[4]; - m_Context.Requip( mob, corpse ); - DelayBounce( TimeSpan.FromSeconds( 30.0 ), mob, corpse ); + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new BRTeamInfo(i); + } - return false; - } + public BRController(Serial serial) + : base(serial) + { + } - private Timer m_FinishTimer; + public BRTeamInfo[] TeamInfo{ get; private set; } - public override void OnStart() - { - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - BRTeamInfo teamInfo = Controller.TeamInfo[i]; + [CommandProperty(AccessLevel.GameMaster)] + public BRTeamInfo Team1 + { + get => TeamInfo[0]; + set { } + } - teamInfo.Game = this; - teamInfo.Reset(); - } + [CommandProperty(AccessLevel.GameMaster)] + public BRTeamInfo Team2 + { + get => TeamInfo[1]; + set { } + } - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - ApplyHues( m_Context.Participants[i] as Participant, Controller.TeamInfo[i % Controller.TeamInfo.Length].Color ); + [CommandProperty(AccessLevel.GameMaster)] + public BRTeamInfo Team3 + { + get => TeamInfo[2]; + set { } + } - m_FinishTimer?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public BRTeamInfo Team4 + { + get => TeamInfo[3]; + set { } + } - m_Bomb = new BRBomb( this ); - ReturnBomb(); + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan Duration{ get; set; } - m_FinishTimer = Timer.DelayCall( Controller.Duration, Finish_Callback ); - } + [CommandProperty(AccessLevel.GameMaster)] + public Point3D BombHome{ get; set; } - private void Finish_Callback() - { - ArrayList teams = new ArrayList(); + public override string Title => "Bombing Run"; + public override string DefaultName => "Bombing Run Controller"; - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - BRTeamInfo teamInfo = Controller.TeamInfo[i % Controller.TeamInfo.Length]; + public override string GetTeamName(int teamID) + { + return TeamInfo[teamID % TeamInfo.Length].Name; + } - if ( teamInfo == null ) - continue; + public override EventGame Construct(DuelContext context) + { + return new BRGame(this, context); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); - teams.Add( teamInfo ); - } + writer.Write(BombHome); + + writer.Write(Duration); - teams.Sort(); + writer.WriteEncodedInt(TeamInfo.Length); + + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i].Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + BombHome = reader.ReadPoint3D(); + + Duration = reader.ReadTimeSpan(); + + TeamInfo = new BRTeamInfo[reader.ReadEncodedInt()]; + + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new BRTeamInfo(i, reader); - Tournament tourny = m_Context.m_Tournament; + break; + } + } + } + } + + public sealed class BRGame : EventGame + { + private BRBomb m_Bomb; + + private Timer m_FinishTimer; + + private TimerCallback m_UnhideCallback; + + public BRGame(BRController controller, DuelContext context) : base(context) + { + Controller = controller; + } + + public BRController Controller{ get; } + + public Map Facet + { + get + { + if (m_Context.Arena != null) + return m_Context.Arena.Facet; + + return Controller.Map; + } + } + + public override bool CantDoAnything(Mobile mob) + { + if (mob?.Backpack == null || GetTeamInfo(mob) == null) + return false; - StringBuilder sb = new StringBuilder(); + Item bomb = mob.Backpack.FindItemByType(typeof(BRBomb), true); - if ( tourny != null && tourny.TournyType == TournyType.FreeForAll ) - { - sb.Append( m_Context.Participants.Count * tourny.PlayersPerParticipant ); - sb.Append( "-man FFA" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.RandomTeam ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-team" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.Faction ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-team Faction" ); - } - else if ( tourny != null ) - { - for ( int i = 0; i < tourny.ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); + if (bomb != null) + return true; - sb.Append( tourny.PlayersPerParticipant ); - } - } + return false; + } - if ( Controller != null ) - sb.Append( ' ' ).Append( Controller.Title ); + public void ReturnBomb() + { + if (m_Bomb != null && Controller != null) + { + if (m_UnhideCallback == null) + m_UnhideCallback = UnhideBomb; + m_Bomb.Visible = false; + m_Bomb.MoveToWorld(Controller.BombHome, Controller.Map); + Timer.DelayCall(TimeSpan.FromSeconds(Utility.RandomMinMax(5, 15)), m_UnhideCallback); + } + } - string title = sb.ToString(); - - BRTeamInfo winner = (BRTeamInfo)( teams.Count > 0 ? teams[0] : null ); + private void UnhideBomb() + { + if (m_Bomb != null) + { + m_Bomb.Visible = true; + m_Bomb.OnLocationChange(m_Bomb.Location); + } + } - for ( int i = 0; i < teams.Count; ++i ) - { - TrophyRank rank = TrophyRank.Bronze; + public void Alert(string text) + { + m_Context.m_Tournament?.Alert(text); - if ( i == 0 ) - rank = TrophyRank.Gold; - else if ( i == 1 ) - rank = TrophyRank.Silver; + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + Participant p = m_Context.Participants[i] as Participant; - BRPlayerInfo leader = ((BRTeamInfo)teams[i]).Leader; + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Mobile.SendMessage(0x35, text); + } + } - foreach ( BRPlayerInfo pl in ((BRTeamInfo)teams[i]).Players.Values ) - { - Mobile mob = pl.Player; + public void Alert(string format, params object[] args) + { + Alert(string.Format(format, args)); + } - if ( mob == null ) - continue; + public BRTeamInfo GetTeamInfo(Mobile mob) + { + int teamID = GetTeamID(mob); + + if (teamID >= 0) + return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; + + return null; + } + + public int GetTeamID(Mobile mob) + { + if (!(mob is PlayerMobile pm)) + return mob is BaseCreature creature ? creature.Team - 1 : -1; + + if (pm.DuelContext == null || pm.DuelContext != m_Context) + return -1; + + if (pm.DuelPlayer == null || pm.DuelPlayer.Eliminated) + return -1; + + return pm.DuelContext.Participants.IndexOf(pm.DuelPlayer.Participant); + } + + public int GetColor(Mobile mob) + { + return GetTeamInfo(mob)?.Color ?? -1; + } + + private void ApplyHues(Participant p, int hueOverride) + { + for (int i = 0; i < p.Players.Length; ++i) + if (p.Players[i] != null) + p.Players[i].Mobile.SolidHueOverride = hueOverride; + } + + public void DelayBounce(TimeSpan ts, Mobile mob, Container corpse) + { + Timer.DelayCall(ts, new TimerStateCallback(DelayBounce_Callback), new object[] { mob, corpse }); + } + + private void DelayBounce_Callback(object state) + { + object[] states = (object[])state; + Mobile mob = (Mobile)states[0]; + Container corpse = (Container)states[1]; - sb = new StringBuilder(); + DuelPlayer dp = null; + + if (mob is PlayerMobile mobile) + dp = mobile.DuelPlayer; - sb.Append( title ); + m_Context.RemoveAggressions(mob); - if ( pl == leader ) - sb.Append( " Leader" ); + if (dp != null && !dp.Eliminated) + mob.MoveToWorld(m_Context.Arena.GetBaseStartPoint(GetTeamID(mob)), Facet); + else + m_Context.SendOutside(mob); - if ( pl.Score > 0 ) - { - sb.Append( ": " ); + m_Context.Refresh(mob, corpse); + DuelContext.Debuff(mob); + DuelContext.CancelSpell(mob); + mob.Frozen = false; + } - //sb.Append( pl.Score.ToString( "N0" ) ); - //sb.Append( pl.Score == 1 ? " point" : " points" ); + public override bool OnDeath(Mobile mob, Container corpse) + { + Mobile killer = mob.FindMostRecentDamager(false); - sb.Append( pl.Kills.ToString( "N0" ) ); - sb.Append( pl.Kills == 1 ? " kill" : " kills" ); + bool hadBomb = false; - if ( pl.Captures > 0 ) - { - sb.Append( ", " ); - sb.Append( pl.Captures.ToString( "N0" ) ); - sb.Append( pl.Captures == 1 ? " point" : " points" ); - } - } - - Item item = new Trophy( sb.ToString(), rank ); - - if ( pl == leader ) - item.ItemID = 4810; - - item.Name = $"{item.Name}, {((BRTeamInfo) teams[i]).Name.ToLower()} team"; - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - int cash = pl.Score * 250; - - if ( cash > 0 ) - { - item = new BankCheck( cash ); - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - mob.SendMessage( "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", rank.ToString().ToLower(), cash ); - } - else - { - mob.SendMessage( "You have been awarded a {0} trophy for your participation in this tournament.", rank.ToString().ToLower() ); - } - } - } - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - if ( !(m_Context.Participants[i] is Participant p) || p.Players == null ) - continue; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + Item[] bombs = corpse.FindItemsByType(typeof(BRBomb), false); + + for (int i = 0; i < bombs.Length; ++i) + (bombs[i] as BRBomb).DropTo(mob, killer); + + hadBomb = hadBomb || bombs.Length > 0; + + if (mob.Backpack != null) + { + bombs = mob.Backpack.FindItemsByType(typeof(BRBomb), false); + + for (int i = 0; i < bombs.Length; ++i) + (bombs[i] as BRBomb).DropTo(mob, killer); + + hadBomb = hadBomb || bombs.Length > 0; + } + + if (killer != null && killer.Player) + { + BRTeamInfo teamInfo = GetTeamInfo(killer); + BRTeamInfo victInfo = GetTeamInfo(mob); + + if (teamInfo != null && teamInfo != victInfo) + { + BRPlayerInfo playerInfo = teamInfo[killer]; - if ( dp?.Mobile != null ) - { - dp.Mobile.CloseGump( typeof( BRBoardGump ) ); - dp.Mobile.SendGump( new BRBoardGump( dp.Mobile, this ) ); - } - } + if (playerInfo != null) + { + playerInfo.Kills += 1; + playerInfo.Score += 1; // base frag - if ( i == winner.TeamID ) - continue; + if (hadBomb) + playerInfo.Score += 4; // fragged bomb carrier + } + } + } - if ( p.Players != null ) - { - for ( int j = 0; j < p.Players.Length; ++j ) - { - if ( p.Players[j] != null ) - p.Players[j].Eliminated = true; - } - } - } + mob.CloseGump(typeof(BRBoardGump)); + mob.SendGump(new BRBoardGump(mob, this)); - m_Context.Finish( m_Context.Participants[winner.TeamID] as Participant ); - } + m_Context.Requip(mob, corpse); + DelayBounce(TimeSpan.FromSeconds(30.0), mob, corpse); - public override void OnStop() - { - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - BRTeamInfo teamInfo = Controller.TeamInfo[i]; + return false; + } - if ( teamInfo.Board != null ) - teamInfo.Board.m_TeamInfo = null; + public override void OnStart() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + BRTeamInfo teamInfo = Controller.TeamInfo[i]; - teamInfo.Game = null; - } + teamInfo.Game = this; + teamInfo.Reset(); + } - ReturnBomb(); + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, + Controller.TeamInfo[i % Controller.TeamInfo.Length].Color); - m_Bomb?.Delete(); + m_FinishTimer?.Stop(); - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - ApplyHues( m_Context.Participants[i] as Participant, -1 ); + m_Bomb = new BRBomb(this); + ReturnBomb(); - m_FinishTimer?.Stop(); - m_FinishTimer = null; - } - } -} + m_FinishTimer = Timer.DelayCall(Controller.Duration, Finish_Callback); + } + + private void Finish_Callback() + { + ArrayList teams = new ArrayList(); + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + BRTeamInfo teamInfo = Controller.TeamInfo[i % Controller.TeamInfo.Length]; + + if (teamInfo == null) + continue; + + teams.Add(teamInfo); + } + + teams.Sort(); + + Tournament tourny = m_Context.m_Tournament; + + StringBuilder sb = new StringBuilder(); + + if (tourny != null && tourny.TournyType == TournyType.FreeForAll) + { + sb.Append(m_Context.Participants.Count * tourny.PlayersPerParticipant); + sb.Append("-man FFA"); + } + else if (tourny != null && tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team"); + } + else if (tourny != null && tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else if (tourny != null && tourny.TournyType == TournyType.Faction) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team Faction"); + } + else if (tourny != null) + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (Controller != null) + sb.Append(' ').Append(Controller.Title); + + string title = sb.ToString(); + + BRTeamInfo winner = (BRTeamInfo)(teams.Count > 0 ? teams[0] : null); + + for (int i = 0; i < teams.Count; ++i) + { + TrophyRank rank = TrophyRank.Bronze; + + if (i == 0) + rank = TrophyRank.Gold; + else if (i == 1) + rank = TrophyRank.Silver; + + BRPlayerInfo leader = ((BRTeamInfo)teams[i]).Leader; + + foreach (BRPlayerInfo pl in ((BRTeamInfo)teams[i]).Players.Values) + { + Mobile mob = pl.Player; + + if (mob == null) + continue; + + sb = new StringBuilder(); + + sb.Append(title); + + if (pl == leader) + sb.Append(" Leader"); + + if (pl.Score > 0) + { + sb.Append(": "); + + //sb.Append( pl.Score.ToString( "N0" ) ); + //sb.Append( pl.Score == 1 ? " point" : " points" ); + + sb.Append(pl.Kills.ToString("N0")); + sb.Append(pl.Kills == 1 ? " kill" : " kills"); + + if (pl.Captures > 0) + { + sb.Append(", "); + sb.Append(pl.Captures.ToString("N0")); + sb.Append(pl.Captures == 1 ? " point" : " points"); + } + } + + Item item = new Trophy(sb.ToString(), rank); + + if (pl == leader) + item.ItemID = 4810; + + item.Name = $"{item.Name}, {((BRTeamInfo)teams[i]).Name.ToLower()} team"; + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + int cash = pl.Score * 250; + + if (cash > 0) + { + item = new BankCheck(cash); + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + mob.SendMessage( + "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", + rank.ToString().ToLower(), cash); + } + else + { + mob.SendMessage("You have been awarded a {0} trophy for your participation in this tournament.", + rank.ToString().ToLower()); + } + } + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + if (!(m_Context.Participants[i] is Participant p) || p.Players == null) + continue; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; + + if (dp?.Mobile != null) + { + dp.Mobile.CloseGump(typeof(BRBoardGump)); + dp.Mobile.SendGump(new BRBoardGump(dp.Mobile, this)); + } + } + + if (i == winner.TeamID) + continue; + + if (p.Players != null) + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Eliminated = true; + } + + m_Context.Finish(m_Context.Participants[winner.TeamID] as Participant); + } + + public override void OnStop() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + BRTeamInfo teamInfo = Controller.TeamInfo[i]; + + if (teamInfo.Board != null) + teamInfo.Board.m_TeamInfo = null; + + teamInfo.Game = null; + } + + ReturnBomb(); + + m_Bomb?.Delete(); + + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, -1); + + m_FinishTimer?.Stop(); + m_FinishTimer = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Games/CTF.cs b/Scripts/Engines/ConPVP/Games/CTF.cs index 46c588925..e32b46da2 100644 --- a/Scripts/Engines/ConPVP/Games/CTF.cs +++ b/Scripts/Engines/ConPVP/Games/CTF.cs @@ -1,1242 +1,1251 @@ using System; using System.Collections.Generic; using System.Text; +using Server.Gumps; using Server.Items; using Server.Mobiles; using Server.Network; using Server.Targeting; -using Server.Gumps; namespace Server.Engines.ConPVP { - public sealed class CTFBoard : Item - { - public CTFTeamInfo m_TeamInfo; - - public override string DefaultName => "scoreboard"; - - [Constructible] - public CTFBoard() - : base( 7774 ) - { - Movable = false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_TeamInfo?.Game != null ) - { - from.CloseGump( typeof( CTFBoardGump ) ); - from.SendGump( new CTFBoardGump( from, m_TeamInfo.Game ) ); - } - } - - public CTFBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CTFBoardGump : Gump - { - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - private void AddBorderedText( int x, int y, int width, int height, string text, int color, int borderColor ) - { - AddColoredText( x - 1, y - 1, width, height, text, borderColor ); - AddColoredText( x - 1, y + 1, width, height, text, borderColor ); - AddColoredText( x + 1, y - 1, width, height, text, borderColor ); - AddColoredText( x + 1, y + 1, width, height, text, borderColor ); - AddColoredText( x, y, width, height, text, color ); - } - - private void AddColoredText( int x, int y, int width, int height, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, height, text, false, false ); - else - AddHtml( x, y, width, height, Color( text, color ), false, false ); - } - - private const int LabelColor32 = 0xFFFFFF; - private const int BlackColor32 = 0x000000; - - private CTFGame m_Game; - - public CTFBoardGump( Mobile mob, CTFGame game ) - : this( mob, game, null ) - { - } - - public CTFBoardGump( Mobile mob, CTFGame game, CTFTeamInfo section ) - : base( 60, 60 ) - { - m_Game = game; - - CTFTeamInfo ourTeam = game.GetTeamInfo( mob ); - - List entries = new List(); - - if ( section == null ) - { - for ( int i = 0; i < game.Context.Participants.Count; ++i ) - { - CTFTeamInfo teamInfo = game.Controller.TeamInfo[i % 8]; - - if ( teamInfo?.Flag == null ) - continue; - - entries.Add( teamInfo ); - } - } - else - { - foreach ( CTFPlayerInfo player in section.Players.Values ) - { - if ( player.Score > 0 ) - entries.Add( player ); - } - } + public sealed class CTFBoard : Item + { + public CTFTeamInfo m_TeamInfo; - entries.Sort( delegate( IRankedCTF a, IRankedCTF b ) - { - return b.Score - a.Score; - } ); + [Constructible] + public CTFBoard() + : base(7774) + { + Movable = false; + } - int height = 0; + public CTFBoard(Serial serial) + : base(serial) + { + } - if ( section == null ) - height = 73 + ( entries.Count * 75 ) + 28; + public override string DefaultName => "scoreboard"; - Closable = false; + public override void OnDoubleClick(Mobile from) + { + if (m_TeamInfo?.Game != null) + { + from.CloseGump(typeof(CTFBoardGump)); + from.SendGump(new CTFBoardGump(from, m_TeamInfo.Game)); + } + } - AddPage( 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - AddBackground( 1, 1, 398, height, 3600 ); + writer.Write(0); + } - AddImageTiled( 16, 15, 369, height - 29, 3604 ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - for ( int i = 0; i < entries.Count; i += 1 ) - AddImageTiled( 22, 58 + ( i * 75 ), 357, 70, 0x2430 ); + int version = reader.ReadInt(); + } + } - AddAlphaRegion( 16, 15, 369, height - 29 ); + public class CTFBoardGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int BlackColor32 = 0x000000; - AddImage( 215, -45, 0xEE40 ); - //AddImage( 330, 141, 0x8BA ); + private CTFGame m_Game; - AddBorderedText( 22, 22, 294, 20, Center( "CTF Scoreboard" ), LabelColor32, BlackColor32 ); + public CTFBoardGump(Mobile mob, CTFGame game) + : this(mob, game, null) + { + } - AddImageTiled( 32, 50, 264, 1, 9107 ); - AddImageTiled( 42, 52, 264, 1, 9157 ); + public CTFBoardGump(Mobile mob, CTFGame game, CTFTeamInfo section) + : base(60, 60) + { + m_Game = game; - if ( section == null ) - { - for ( int i = 0; i < entries.Count; ++i ) - { - CTFTeamInfo teamInfo = entries[i] as CTFTeamInfo; + CTFTeamInfo ourTeam = game.GetTeamInfo(mob); - AddImage( 30, 70 + ( i * 75 ), 10152 ); - AddImage( 30, 85 + ( i * 75 ), 10151 ); - AddImage( 30, 100 + ( i * 75 ), 10151 ); - AddImage( 30, 106 + ( i * 75 ), 10154 ); + List entries = new List(); - AddImage( 24, 60 + ( i * 75 ), teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1 ); + if (section == null) + for (int i = 0; i < game.Context.Participants.Count; ++i) + { + CTFTeamInfo teamInfo = game.Controller.TeamInfo[i % 8]; - int nameColor = LabelColor32; - int borderColor = BlackColor32; + if (teamInfo?.Flag == null) + continue; - switch ( teamInfo.Color ) - { - case 0x47E: - nameColor = 0xFFFFFF; - break; + entries.Add(teamInfo); + } + else + foreach (CTFPlayerInfo player in section.Players.Values) + if (player.Score > 0) + entries.Add(player); - case 0x4F2: - nameColor = 0x3399FF; - break; + entries.Sort(delegate(IRankedCTF a, IRankedCTF b) { return b.Score - a.Score; }); - case 0x4F7: - nameColor = 0x33FF33; - break; + int height = 0; - case 0x4FC: - nameColor = 0xFF00FF; - break; + if (section == null) + height = 73 + entries.Count * 75 + 28; - case 0x021: - nameColor = 0xFF3333; - break; + Closable = false; - case 0x01A: - nameColor = 0xFF66FF; - break; + AddPage(0); - case 0x455: - nameColor = 0x333333; - borderColor = 0xFFFFFF; - break; - } - - AddBorderedText( 60, 65 + ( i * 75 ), 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name} Team", nameColor, borderColor ); - - AddBorderedText( 50 + 10, 85 + ( i * 75 ), 100, 20, "Score:", 0xFFC000, BlackColor32 ); - AddBorderedText( 50 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Score.ToString( "N0" ), 0xFFC000, BlackColor32 ); - - AddBorderedText( 110 + 10, 85 + ( i * 75 ), 100, 20, "Kills:", 0xFFC000, BlackColor32 ); - AddBorderedText( 110 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Kills.ToString( "N0" ), 0xFFC000, BlackColor32 ); - - AddBorderedText( 160 + 10, 85 + ( i * 75 ), 100, 20, "Captures:", 0xFFC000, BlackColor32 ); - AddBorderedText( 160 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Captures.ToString( "N0" ), 0xFFC000, BlackColor32 ); - - CTFPlayerInfo pl = teamInfo.Leader; - - AddBorderedText( 235 + 10, 85 + ( i * 75 ), 250, 20, "Leader:", 0xFFC000, BlackColor32 ); - - if ( pl != null ) - AddBorderedText( 235 + 15, 105 + ( i * 75 ), 250, 20, pl.Player.Name, 0xFFC000, BlackColor32 ); - } - } + AddBackground(1, 1, 398, height, 3600); - AddButton( 314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0 ); - } - } + AddImageTiled(16, 15, 369, height - 29, 3604); - public sealed class CTFFlag : Item - { - public CTFTeamInfo m_TeamInfo; - - public override string DefaultName => "old people cookies"; - - public Mobile m_Fragger; - public DateTime m_FragTime; - - public Mobile m_Returner; - public DateTime m_ReturnTime; - - private int m_ReturnCount; - private Timer m_ReturnTimer; - - [Constructible] - public CTFFlag() - : base( 5643 ) - { - Movable = false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_TeamInfo?.Game != null ) - { - CTFTeamInfo ourTeam = m_TeamInfo; - CTFTeamInfo useTeam = m_TeamInfo.Game.GetTeamInfo( from ); - - if ( ourTeam == null || useTeam == null ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - from.BeginTarget( 1, false, TargetFlags.None, Flag_OnTarget ); - } - else if ( !from.InRange( this, 1 ) || !from.InLOS( this ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x26, 1019045 ); // I can't reach that - } - else if ( ourTeam == useTeam ) - { - if ( Location == m_TeamInfo.Origin && Map == m_TeamInfo.Game.Facet ) - { - from.Send( new UnicodeMessage( Serial, ItemID, MessageType.Regular, 0x3B2, 3, "ENU", Name, "Touch me not for I am chaste." ) ); - } - else - { - CTFPlayerInfo playerInfo = useTeam[from]; - - if ( playerInfo != null ) - playerInfo.Score += 4; // return - - m_Returner = from; - m_ReturnTime = DateTime.UtcNow; - - SendHome(); - - from.LocalOverheadMessage( MessageType.Regular, 0x59, false, "You returned the cookies!" ); - m_TeamInfo.Game.Alert( "The {1} cookies have been returned by {0}.", from.Name, ourTeam.Name ); - } - } - else if ( !from.PlaceInBackpack( this ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x26, false, "I can't hold that." ); - } - else - { - from.RevealingAction(); - - from.LocalOverheadMessage( MessageType.Regular, 0x59, false, "You stole the cookies!" ); - m_TeamInfo.Game.Alert( "The {1} cookies have been stolen by {0} ({2}).", from.Name, ourTeam.Name, useTeam.Name ); - - BeginCountdown( 120 ); - } - } - } - - public override void Delete() - { - if ( Parent != null ) - { - SendHome(); - return; - } - - base.Delete(); - } - - public void DropTo( Mobile mob, Mobile killer ) - { - m_Fragger = killer; - m_FragTime = DateTime.UtcNow; - - if ( mob != null ) - { - MoveToWorld( new Point3D( mob.X, mob.Y, mob.Z + 2 ), mob.Map ); - - m_ReturnCount = Math.Min( m_ReturnCount, 10 ); - } - else - { - SendHome(); - } - } - - private void StopCountdown() - { - m_ReturnTimer?.Stop(); - - m_ReturnTimer = null; - } - - private void BeginCountdown( int returnCount ) - { - StopCountdown(); - - m_ReturnTimer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ), Countdown_OnTick ); - m_ReturnCount = returnCount; - } - - private void Countdown_OnTick() - { - Mobile owner = RootParent as Mobile; - - switch ( m_ReturnCount ) - { - case 60: - case 30: - case 15: - case 10: - case 5: - case 4: - case 3: - case 2: - case 1: - { - owner?.SendMessage( 0x26, "You have {0} {1} to capture the cookies!", m_ReturnCount, m_ReturnCount == 1 ? "second" : "seconds" ); - - break; - } - - case 0: - { - if ( owner != null ) - { - owner.SendMessage( 0x26, "You have taken too long to capture the cookies!" ); - owner.Kill(); - } - - SendHome(); - - m_TeamInfo?.Game?.Alert( "The {0} cookies have been returned.", m_TeamInfo.Name ); - - return; - } - } - - --m_ReturnCount; - } - - private void Flag_OnTarget( Mobile from, object obj ) - { - if ( m_TeamInfo == null ) - return; - - if ( !IsChildOf( from.Backpack ) ) - return; - - CTFTeamInfo ourTeam = m_TeamInfo; - CTFTeamInfo useTeam = m_TeamInfo.Game.GetTeamInfo( from ); - - if ( obj is CTFFlag ) - { - if ( obj == useTeam.Flag ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x59, false, "You captured the cookies!" ); - m_TeamInfo.Game.Alert( "{0} captured the {1} cookies!", from.Name, ourTeam.Name ); - - SendHome(); - - CTFPlayerInfo playerInfo = useTeam[from]; - - if ( playerInfo != null ) - { - playerInfo.Captures += 1; - playerInfo.Score += 50; // capture - - CTFFlag teamFlag = useTeam.Flag; - - if ( teamFlag.m_Fragger != null && DateTime.UtcNow < ( teamFlag.m_FragTime + TimeSpan.FromSeconds( 5.0 ) ) && m_TeamInfo.Game.GetTeamInfo( teamFlag.m_Fragger ) == useTeam ) - { - CTFPlayerInfo assistInfo = useTeam[teamFlag.m_Fragger]; - - if ( assistInfo != null ) - assistInfo.Score += 6; // frag assist - } - - if ( teamFlag.m_Returner != null && DateTime.UtcNow < ( teamFlag.m_ReturnTime + TimeSpan.FromSeconds( 5.0 ) ) ) - { - CTFPlayerInfo assistInfo = useTeam[teamFlag.m_Returner]; - - if ( assistInfo != null ) - assistInfo.Score += 4; // return assist - } - } - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x26, false, "Those are not my cookies." ); - } - } - else if ( obj is Mobile passTo ) - { - CTFTeamInfo passTeam = m_TeamInfo.Game.GetTeamInfo( passTo ); - - if ( passTo == from ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x26, false, "I can't pass to them." ); - } - else if ( passTeam == useTeam && passTo.PlaceInBackpack( this ) ) - { - passTo.LocalOverheadMessage( MessageType.Regular, 0x59, false, - $"{from.Name} has passed you the cookies!"); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x26, false, "I can't pass to them." ); - } - } - } - - public void SendHome() - { - StopCountdown(); - - if ( m_TeamInfo == null ) - return; - - MoveToWorld( m_TeamInfo.Origin, m_TeamInfo.Game.Facet ); - } - - private Mobile FindOwner( object parent ) - { - if ( parent is Item item ) - return item.RootParent as Mobile; - - if ( parent is Mobile mobile ) - return mobile; - - return null; - } - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - Mobile mob = FindOwner( parent ); - - if ( mob != null ) - mob.SolidHueOverride = 0x4001; - } - - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); - - Mobile mob = FindOwner( parent ); - - if ( mob != null ) - mob.SolidHueOverride = m_TeamInfo?.Game.GetColor( mob ) ?? -1; - } - - public CTFFlag( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public interface IRankedCTF - { - int Kills { get; } - int Captures { get; } - int Score { get; } - string Name { get; } - } - - public sealed class CTFPlayerInfo : IRankedCTF - { - private CTFTeamInfo m_TeamInfo; - - private int m_Kills; - private int m_Captures; - - private int m_Score; - - public Mobile Player { get; } - - string IRankedCTF.Name => Player.Name; - - public int Kills - { - get => m_Kills; - set - { - m_TeamInfo.Kills += ( value - m_Kills ); - m_Kills = value; - } - } + for (int i = 0; i < entries.Count; i += 1) + AddImageTiled(22, 58 + i * 75, 357, 70, 0x2430); - public int Captures - { - get => m_Captures; - set - { - m_TeamInfo.Captures += ( value - m_Captures ); - m_Captures = value; - } - } + AddAlphaRegion(16, 15, 369, height - 29); - public int Score - { - get => m_Score; - set - { - m_TeamInfo.Score += ( value - m_Score ); - m_Score = value; + AddImage(215, -45, 0xEE40); + //AddImage( 330, 141, 0x8BA ); - if ( m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score ) - m_TeamInfo.Leader = this; - } - } + AddBorderedText(22, 22, 294, 20, Center("CTF Scoreboard"), LabelColor32, BlackColor32); - public CTFPlayerInfo( CTFTeamInfo teamInfo, Mobile player ) - { - m_TeamInfo = teamInfo; - Player = player; - } - } - - [PropertyObject] - public sealed class CTFTeamInfo : IRankedCTF - { - string IRankedCTF.Name => $"{Name} Team"; - - public CTFGame Game { get; set; } - - public int TeamID { get; } - - public int Kills { get; set; } - - public int Captures { get; set; } - - public int Score { get; set; } - - public CTFPlayerInfo Leader { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public CTFBoard Board { get; set; } - - public Dictionary Players { get; } + AddImageTiled(32, 50, 264, 1, 9107); + AddImageTiled(42, 52, 264, 1, 9157); - public CTFPlayerInfo this[Mobile mob] - { - get - { - if ( mob == null ) - return null; - - if (!Players.TryGetValue( mob, out CTFPlayerInfo val )) - Players[mob] = val = new CTFPlayerInfo( this, mob ); - - return val; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Color { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string Name { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public CTFFlag Flag { get; set; } + if (section == null) + for (int i = 0; i < entries.Count; ++i) + { + CTFTeamInfo teamInfo = entries[i] as CTFTeamInfo; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Origin { get; set; } + AddImage(30, 70 + i * 75, 10152); + AddImage(30, 85 + i * 75, 10151); + AddImage(30, 100 + i * 75, 10151); + AddImage(30, 106 + i * 75, 10154); - public CTFTeamInfo( int teamID ) - { - TeamID = teamID; - Players = new Dictionary(); - } + AddImage(24, 60 + i * 75, teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1); - public void Reset() - { - Kills = 0; - Captures = 0; - - Score = 0; - - Leader = null; - - Players.Clear(); - - if ( Flag != null ) - { - Flag.m_TeamInfo = this; - Flag.Hue = Color; - Flag.SendHome(); - } + int nameColor = LabelColor32; + int borderColor = BlackColor32; - if ( Board != null ) - Board.m_TeamInfo = this; - } + switch (teamInfo.Color) + { + case 0x47E: + nameColor = 0xFFFFFF; + break; - public CTFTeamInfo( int teamID, GenericReader ip ) - { - TeamID = teamID; - Players = new Dictionary(); + case 0x4F2: + nameColor = 0x3399FF; + break; - int version = ip.ReadEncodedInt(); + case 0x4F7: + nameColor = 0x33FF33; + break; - switch ( version ) - { - case 2: - { - Board = ip.ReadItem() as CTFBoard; + case 0x4FC: + nameColor = 0xFF00FF; + break; - goto case 1; - } - case 1: - { - Name = ip.ReadString(); + case 0x021: + nameColor = 0xFF3333; + break; - goto case 0; - } - case 0: - { - Color = ip.ReadEncodedInt(); + case 0x01A: + nameColor = 0xFF66FF; + break; - Flag = ip.ReadItem() as CTFFlag; - Origin = ip.ReadPoint3D(); - break; - } - } - } + case 0x455: + nameColor = 0x333333; + borderColor = 0xFFFFFF; + break; + } - public void Serialize( GenericWriter op ) - { - op.WriteEncodedInt( 2 ); // version + AddBorderedText(60, 65 + i * 75, 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name} Team", nameColor, + borderColor); + + AddBorderedText(50 + 10, 85 + i * 75, 100, 20, "Score:", 0xFFC000, BlackColor32); + AddBorderedText(50 + 15, 105 + i * 75, 100, 20, teamInfo.Score.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(110 + 10, 85 + i * 75, 100, 20, "Kills:", 0xFFC000, BlackColor32); + AddBorderedText(110 + 15, 105 + i * 75, 100, 20, teamInfo.Kills.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(160 + 10, 85 + i * 75, 100, 20, "Captures:", 0xFFC000, BlackColor32); + AddBorderedText(160 + 15, 105 + i * 75, 100, 20, teamInfo.Captures.ToString("N0"), 0xFFC000, + BlackColor32); + + CTFPlayerInfo pl = teamInfo.Leader; - op.Write( Board ); + AddBorderedText(235 + 10, 85 + i * 75, 250, 20, "Leader:", 0xFFC000, BlackColor32); + + if (pl != null) + AddBorderedText(235 + 15, 105 + i * 75, 250, 20, pl.Player.Name, 0xFFC000, BlackColor32); + } + + AddButton(314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + } + + public sealed class CTFFlag : Item + { + public Mobile m_Fragger; + public DateTime m_FragTime; + + private int m_ReturnCount; + + public Mobile m_Returner; + public DateTime m_ReturnTime; + private Timer m_ReturnTimer; + public CTFTeamInfo m_TeamInfo; + + [Constructible] + public CTFFlag() + : base(5643) + { + Movable = false; + } + + public CTFFlag(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "old people cookies"; + + public override void OnDoubleClick(Mobile from) + { + if (m_TeamInfo?.Game != null) + { + CTFTeamInfo ourTeam = m_TeamInfo; + CTFTeamInfo useTeam = m_TeamInfo.Game.GetTeamInfo(from); + + if (ourTeam == null || useTeam == null) + return; + + if (IsChildOf(from.Backpack)) + { + from.BeginTarget(1, false, TargetFlags.None, Flag_OnTarget); + } + else if (!from.InRange(this, 1) || !from.InLOS(this)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x26, 1019045); // I can't reach that + } + else if (ourTeam == useTeam) + { + if (Location == m_TeamInfo.Origin && Map == m_TeamInfo.Game.Facet) + { + from.Send(new UnicodeMessage(Serial, ItemID, MessageType.Regular, 0x3B2, 3, "ENU", Name, + "Touch me not for I am chaste.")); + } + else + { + CTFPlayerInfo playerInfo = useTeam[from]; + + if (playerInfo != null) + playerInfo.Score += 4; // return + + m_Returner = from; + m_ReturnTime = DateTime.UtcNow; + + SendHome(); + + from.LocalOverheadMessage(MessageType.Regular, 0x59, false, "You returned the cookies!"); + m_TeamInfo.Game.Alert("The {1} cookies have been returned by {0}.", from.Name, ourTeam.Name); + } + } + else if (!from.PlaceInBackpack(this)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x26, false, "I can't hold that."); + } + else + { + from.RevealingAction(); + + from.LocalOverheadMessage(MessageType.Regular, 0x59, false, "You stole the cookies!"); + m_TeamInfo.Game.Alert("The {1} cookies have been stolen by {0} ({2}).", from.Name, ourTeam.Name, + useTeam.Name); + + BeginCountdown(120); + } + } + } + + public override void Delete() + { + if (Parent != null) + { + SendHome(); + return; + } + + base.Delete(); + } + + public void DropTo(Mobile mob, Mobile killer) + { + m_Fragger = killer; + m_FragTime = DateTime.UtcNow; + + if (mob != null) + { + MoveToWorld(new Point3D(mob.X, mob.Y, mob.Z + 2), mob.Map); + + m_ReturnCount = Math.Min(m_ReturnCount, 10); + } + else + { + SendHome(); + } + } + + private void StopCountdown() + { + m_ReturnTimer?.Stop(); + + m_ReturnTimer = null; + } + + private void BeginCountdown(int returnCount) + { + StopCountdown(); + + m_ReturnTimer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0), Countdown_OnTick); + m_ReturnCount = returnCount; + } + + private void Countdown_OnTick() + { + Mobile owner = RootParent as Mobile; + + switch (m_ReturnCount) + { + case 60: + case 30: + case 15: + case 10: + case 5: + case 4: + case 3: + case 2: + case 1: + { + owner?.SendMessage(0x26, "You have {0} {1} to capture the cookies!", m_ReturnCount, + m_ReturnCount == 1 ? "second" : "seconds"); + + break; + } + + case 0: + { + if (owner != null) + { + owner.SendMessage(0x26, "You have taken too long to capture the cookies!"); + owner.Kill(); + } + + SendHome(); + + m_TeamInfo?.Game?.Alert("The {0} cookies have been returned.", m_TeamInfo.Name); + + return; + } + } + + --m_ReturnCount; + } + + private void Flag_OnTarget(Mobile from, object obj) + { + if (m_TeamInfo == null) + return; + + if (!IsChildOf(from.Backpack)) + return; + + CTFTeamInfo ourTeam = m_TeamInfo; + CTFTeamInfo useTeam = m_TeamInfo.Game.GetTeamInfo(from); + + if (obj is CTFFlag) + { + if (obj == useTeam.Flag) + { + from.LocalOverheadMessage(MessageType.Regular, 0x59, false, "You captured the cookies!"); + m_TeamInfo.Game.Alert("{0} captured the {1} cookies!", from.Name, ourTeam.Name); + + SendHome(); + + CTFPlayerInfo playerInfo = useTeam[from]; + + if (playerInfo != null) + { + playerInfo.Captures += 1; + playerInfo.Score += 50; // capture + + CTFFlag teamFlag = useTeam.Flag; + + if (teamFlag.m_Fragger != null && + DateTime.UtcNow < teamFlag.m_FragTime + TimeSpan.FromSeconds(5.0) && + m_TeamInfo.Game.GetTeamInfo(teamFlag.m_Fragger) == useTeam) + { + CTFPlayerInfo assistInfo = useTeam[teamFlag.m_Fragger]; + + if (assistInfo != null) + assistInfo.Score += 6; // frag assist + } + + if (teamFlag.m_Returner != null && + DateTime.UtcNow < teamFlag.m_ReturnTime + TimeSpan.FromSeconds(5.0)) + { + CTFPlayerInfo assistInfo = useTeam[teamFlag.m_Returner]; + + if (assistInfo != null) + assistInfo.Score += 4; // return assist + } + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x26, false, "Those are not my cookies."); + } + } + else if (obj is Mobile passTo) + { + CTFTeamInfo passTeam = m_TeamInfo.Game.GetTeamInfo(passTo); + + if (passTo == from) + from.LocalOverheadMessage(MessageType.Regular, 0x26, false, "I can't pass to them."); + else if (passTeam == useTeam && passTo.PlaceInBackpack(this)) + passTo.LocalOverheadMessage(MessageType.Regular, 0x59, false, + $"{from.Name} has passed you the cookies!"); + else + from.LocalOverheadMessage(MessageType.Regular, 0x26, false, "I can't pass to them."); + } + } + + public void SendHome() + { + StopCountdown(); + + if (m_TeamInfo == null) + return; + + MoveToWorld(m_TeamInfo.Origin, m_TeamInfo.Game.Facet); + } + + private Mobile FindOwner(object parent) + { + if (parent is Item item) + return item.RootParent as Mobile; + + if (parent is Mobile mobile) + return mobile; + + return null; + } + + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); + + Mobile mob = FindOwner(parent); + + if (mob != null) + mob.SolidHueOverride = 0x4001; + } + + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); + + Mobile mob = FindOwner(parent); + + if (mob != null) + mob.SolidHueOverride = m_TeamInfo?.Game.GetColor(mob) ?? -1; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public interface IRankedCTF + { + int Kills{ get; } + int Captures{ get; } + int Score{ get; } + string Name{ get; } + } + + public sealed class CTFPlayerInfo : IRankedCTF + { + private int m_Captures; + + private int m_Kills; + + private int m_Score; + private CTFTeamInfo m_TeamInfo; + + public CTFPlayerInfo(CTFTeamInfo teamInfo, Mobile player) + { + m_TeamInfo = teamInfo; + Player = player; + } + + public Mobile Player{ get; } + + string IRankedCTF.Name => Player.Name; + + public int Kills + { + get => m_Kills; + set + { + m_TeamInfo.Kills += value - m_Kills; + m_Kills = value; + } + } + + public int Captures + { + get => m_Captures; + set + { + m_TeamInfo.Captures += value - m_Captures; + m_Captures = value; + } + } - op.Write( Name ); + public int Score + { + get => m_Score; + set + { + m_TeamInfo.Score += value - m_Score; + m_Score = value; + + if (m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score) + m_TeamInfo.Leader = this; + } + } + } - op.WriteEncodedInt( Color ); + [PropertyObject] + public sealed class CTFTeamInfo : IRankedCTF + { + public CTFTeamInfo(int teamID) + { + TeamID = teamID; + Players = new Dictionary(); + } + + public CTFTeamInfo(int teamID, GenericReader ip) + { + TeamID = teamID; + Players = new Dictionary(); - op.Write( Flag ); - op.Write( Origin ); - } + int version = ip.ReadEncodedInt(); - public override string ToString() - { - return "..."; - } - } + switch (version) + { + case 2: + { + Board = ip.ReadItem() as CTFBoard; - public sealed class CTFController : EventController - { - public CTFTeamInfo[] TeamInfo { get; private set; } + goto case 1; + } + case 1: + { + Name = ip.ReadString(); - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team1 { get => TeamInfo[0]; - set { } } + goto case 0; + } + case 0: + { + Color = ip.ReadEncodedInt(); + + Flag = ip.ReadItem() as CTFFlag; + Origin = ip.ReadPoint3D(); + break; + } + } + } + + public CTFGame Game{ get; set; } + + public int TeamID{ get; } - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team2 { get => TeamInfo[1]; - set { } } + public CTFPlayerInfo Leader{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team3 { get => TeamInfo[2]; - set { } } + [CommandProperty(AccessLevel.GameMaster)] + public CTFBoard Board{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team4 { get => TeamInfo[3]; - set { } } + public Dictionary Players{ get; } - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team5 { get => TeamInfo[4]; - set { } } + public CTFPlayerInfo this[Mobile mob] + { + get + { + if (mob == null) + return null; + + if (!Players.TryGetValue(mob, out CTFPlayerInfo val)) + Players[mob] = val = new CTFPlayerInfo(this, mob); + + return val; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Color{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string Name{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public CTFFlag Flag{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Origin{ get; set; } + + string IRankedCTF.Name => $"{Name} Team"; + + public int Kills{ get; set; } + + public int Captures{ get; set; } + + public int Score{ get; set; } + + public void Reset() + { + Kills = 0; + Captures = 0; + + Score = 0; + + Leader = null; + + Players.Clear(); + + if (Flag != null) + { + Flag.m_TeamInfo = this; + Flag.Hue = Color; + Flag.SendHome(); + } + + if (Board != null) + Board.m_TeamInfo = this; + } + + public void Serialize(GenericWriter op) + { + op.WriteEncodedInt(2); // version - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team6 { get => TeamInfo[5]; - set { } } + op.Write(Board); - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team7 { get => TeamInfo[6]; - set { } } + op.Write(Name); + + op.WriteEncodedInt(Color); + + op.Write(Flag); + op.Write(Origin); + } - [CommandProperty( AccessLevel.GameMaster )] - public CTFTeamInfo Team8 { get => TeamInfo[7]; - set { } } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan Duration { get; set; } - - public override string Title => "CTF"; + public override string ToString() + { + return "..."; + } + } - public override string GetTeamName( int teamID ) - { - return TeamInfo[teamID % TeamInfo.Length].Name; - } - - public override EventGame Construct( DuelContext context ) - { - return new CTFGame( this, context ); - } - - [Constructible] - public CTFController() - { - Visible = false; - Movable = false; - - Duration = TimeSpan.FromMinutes( 30.0 ); - - TeamInfo = new CTFTeamInfo[8]; - - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new CTFTeamInfo( i ); - } - - public CTFController( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); - - writer.Write( Duration ); + public sealed class CTFController : EventController + { + [Constructible] + public CTFController() + { + Visible = false; + Movable = false; - writer.WriteEncodedInt( TeamInfo.Length ); + Duration = TimeSpan.FromMinutes(30.0); - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i].Serialize( writer ); - } + TeamInfo = new CTFTeamInfo[8]; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new CTFTeamInfo(i); + } - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - { - Duration = reader.ReadTimeSpan(); - - goto case 1; - } - case 1: - { - TeamInfo = new CTFTeamInfo[reader.ReadEncodedInt()]; + public CTFController(Serial serial) + : base(serial) + { + } - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new CTFTeamInfo( i, reader ); + public CTFTeamInfo[] TeamInfo{ get; private set; } - break; - } - case 0: - { - TeamInfo = new CTFTeamInfo[8]; - - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new CTFTeamInfo( i ); - - break; - } - } - - if ( version < 2 ) - Duration = TimeSpan.FromMinutes( 30.0 ); - } - } - - public sealed class CTFGame : EventGame - { - public static void Initialize() - { - for ( int i = 0x7C9; i <= 0x7D0; ++i ) - TileData.ItemTable[i].Flags |= TileFlag.NoShoot; - } + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team1 + { + get => TeamInfo[0]; + set { } + } - public CTFController Controller { get; } - - public void Alert( string text ) - { - m_Context.m_Tournament?.Alert( text ); - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - Participant p = m_Context.Participants[i] as Participant; - - for ( int j = 0; j < p.Players.Length; ++j ) - { - if ( p.Players[j] != null ) - p.Players[j].Mobile.SendMessage( 0x35, text ); - } - } - } - - public void Alert( string format, params object[] args ) - { - Alert( string.Format( format, args ) ); - } + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team2 + { + get => TeamInfo[1]; + set { } + } - public CTFGame( CTFController controller, DuelContext context ) : base( context ) - { - Controller = controller; - } + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team3 + { + get => TeamInfo[2]; + set { } + } - public Map Facet - { - get - { - if ( m_Context.Arena != null ) - return m_Context.Arena.Facet; + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team4 + { + get => TeamInfo[3]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team5 + { + get => TeamInfo[4]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team6 + { + get => TeamInfo[5]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team7 + { + get => TeamInfo[6]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CTFTeamInfo Team8 + { + get => TeamInfo[7]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan Duration{ get; set; } + + public override string Title => "CTF"; + + public override string GetTeamName(int teamID) + { + return TeamInfo[teamID % TeamInfo.Length].Name; + } + + public override EventGame Construct(DuelContext context) + { + return new CTFGame(this, context); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); + + writer.Write(Duration); + + writer.WriteEncodedInt(TeamInfo.Length); + + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i].Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: + { + Duration = reader.ReadTimeSpan(); + + goto case 1; + } + case 1: + { + TeamInfo = new CTFTeamInfo[reader.ReadEncodedInt()]; + + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new CTFTeamInfo(i, reader); + + break; + } + case 0: + { + TeamInfo = new CTFTeamInfo[8]; + + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new CTFTeamInfo(i); + + break; + } + } + + if (version < 2) + Duration = TimeSpan.FromMinutes(30.0); + } + } + + public sealed class CTFGame : EventGame + { + private Timer m_FinishTimer; + + public CTFGame(CTFController controller, DuelContext context) : base(context) + { + Controller = controller; + } + + public CTFController Controller{ get; } + + public Map Facet + { + get + { + if (m_Context.Arena != null) + return m_Context.Arena.Facet; + + return Controller.Map; + } + } + + public static void Initialize() + { + for (int i = 0x7C9; i <= 0x7D0; ++i) + TileData.ItemTable[i].Flags |= TileFlag.NoShoot; + } - return Controller.Map; - } - } + public void Alert(string text) + { + m_Context.m_Tournament?.Alert(text); - public CTFTeamInfo GetTeamInfo( Mobile mob ) - { - int teamID = GetTeamID( mob ); + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + Participant p = m_Context.Participants[i] as Participant; - if ( teamID >= 0 ) - return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; - - return null; - } - - public int GetTeamID( Mobile mob ) - { - if ( !(mob is PlayerMobile pm) ) - return -1; - - if ( pm.DuelContext == null || pm.DuelContext != m_Context ) - return -1; - - if ( pm.DuelPlayer == null || pm.DuelPlayer.Eliminated ) - return -1; - - return pm.DuelContext.Participants.IndexOf( pm.DuelPlayer.Participant ); - } - - public int GetColor( Mobile mob ) - { - CTFTeamInfo teamInfo = GetTeamInfo( mob ); - - if ( teamInfo != null ) - return teamInfo.Color; - - return -1; - } - - private void ApplyHues( Participant p, int hueOverride ) - { - for ( int i = 0; i < p.Players.Length; ++i ) - { - if ( p.Players[i] != null ) - p.Players[i].Mobile.SolidHueOverride = hueOverride; - } - } - - public void DelayBounce( TimeSpan ts, Mobile mob, Container corpse ) - { - Timer.DelayCall( ts, new TimerStateCallback( DelayBounce_Callback ), new object[] { mob, corpse } ); - } - - private void DelayBounce_Callback( object state ) - { - object[] states = (object[]) state; - Mobile mob = (Mobile) states[0]; - Container corpse = (Container) states[1]; - - DuelPlayer dp = null; + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Mobile.SendMessage(0x35, text); + } + } - if ( mob is PlayerMobile mobile ) - dp = mobile.DuelPlayer; + public void Alert(string format, params object[] args) + { + Alert(string.Format(format, args)); + } - m_Context.RemoveAggressions( mob ); + public CTFTeamInfo GetTeamInfo(Mobile mob) + { + int teamID = GetTeamID(mob); - if ( dp != null && !dp.Eliminated ) - mob.MoveToWorld( m_Context.Arena.GetBaseStartPoint( GetTeamID( mob ) ), Facet ); - else - m_Context.SendOutside( mob ); + if (teamID >= 0) + return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; - m_Context.Refresh( mob, corpse ); - DuelContext.Debuff( mob ); - DuelContext.CancelSpell( mob ); - mob.Frozen = false; - } + return null; + } - public override bool OnDeath( Mobile mob, Container corpse ) - { - Mobile killer = mob.FindMostRecentDamager( false ); + public int GetTeamID(Mobile mob) + { + if (!(mob is PlayerMobile pm)) + return -1; - bool hadFlag = false; + if (pm.DuelContext == null || pm.DuelContext != m_Context) + return -1; - Item[] flags = corpse.FindItemsByType( typeof( CTFFlag ), false ); + if (pm.DuelPlayer == null || pm.DuelPlayer.Eliminated) + return -1; - for ( int i = 0; i < flags.Length; ++i ) - ( flags[i] as CTFFlag ).DropTo( mob, killer ); + return pm.DuelContext.Participants.IndexOf(pm.DuelPlayer.Participant); + } - hadFlag = ( hadFlag || flags.Length > 0 ); + public int GetColor(Mobile mob) + { + CTFTeamInfo teamInfo = GetTeamInfo(mob); - if ( mob.Backpack != null ) - { - flags = mob.Backpack.FindItemsByType( typeof( CTFFlag ), false ); + if (teamInfo != null) + return teamInfo.Color; - for ( int i = 0; i < flags.Length; ++i ) - ( flags[i] as CTFFlag ).DropTo( mob, killer ); + return -1; + } - hadFlag = ( hadFlag || flags.Length > 0 ); - } + private void ApplyHues(Participant p, int hueOverride) + { + for (int i = 0; i < p.Players.Length; ++i) + if (p.Players[i] != null) + p.Players[i].Mobile.SolidHueOverride = hueOverride; + } - if ( killer != null && killer.Player ) - { - CTFTeamInfo teamInfo = GetTeamInfo( killer ); - CTFTeamInfo victInfo = GetTeamInfo( mob ); + public void DelayBounce(TimeSpan ts, Mobile mob, Container corpse) + { + Timer.DelayCall(ts, new TimerStateCallback(DelayBounce_Callback), new object[] { mob, corpse }); + } - if ( teamInfo != null && teamInfo != victInfo ) - { - CTFPlayerInfo playerInfo = teamInfo[killer]; + private void DelayBounce_Callback(object state) + { + object[] states = (object[])state; + Mobile mob = (Mobile)states[0]; + Container corpse = (Container)states[1]; - if ( playerInfo != null ) - { - playerInfo.Kills += 1; - playerInfo.Score += 1; // base frag + DuelPlayer dp = null; - if ( hadFlag ) - playerInfo.Score += 4; // fragged flag carrier + if (mob is PlayerMobile mobile) + dp = mobile.DuelPlayer; - if ( mob.InRange( teamInfo.Origin, 24 ) && mob.Map == Facet ) - playerInfo.Score += 1; // fragged in base -- guarding + m_Context.RemoveAggressions(mob); - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - if ( Controller.TeamInfo[i] == teamInfo ) - continue; - - Mobile ourFlagCarrier = null; - - if ( Controller.TeamInfo[i].Flag != null ) - ourFlagCarrier = Controller.TeamInfo[i].Flag.RootParent as Mobile; - - if ( ourFlagCarrier != null && GetTeamInfo( ourFlagCarrier ) == teamInfo ) - { - for ( int j = 0; j < ourFlagCarrier.Aggressors.Count; ++j ) - { - if ( !(ourFlagCarrier.Aggressors[j] is AggressorInfo aggr) || aggr.Defender != ourFlagCarrier || aggr.Attacker != mob ) - continue; - - playerInfo.Score += 2; // helped defend guy capturing enemy flag - break; - } - - if ( mob.Map == ourFlagCarrier.Map && ourFlagCarrier.InRange( mob, 12 ) ) - playerInfo.Score += 1; // helped defend guy capturing enemy flag - } - } - } - } - } + if (dp != null && !dp.Eliminated) + mob.MoveToWorld(m_Context.Arena.GetBaseStartPoint(GetTeamID(mob)), Facet); + else + m_Context.SendOutside(mob); - mob.CloseGump( typeof( CTFBoardGump ) ); - mob.SendGump( new CTFBoardGump( mob, this ) ); + m_Context.Refresh(mob, corpse); + DuelContext.Debuff(mob); + DuelContext.CancelSpell(mob); + mob.Frozen = false; + } - m_Context.Requip( mob, corpse ); - DelayBounce( TimeSpan.FromSeconds( 30.0 ), mob, corpse ); + public override bool OnDeath(Mobile mob, Container corpse) + { + Mobile killer = mob.FindMostRecentDamager(false); - return false; - } + bool hadFlag = false; - private Timer m_FinishTimer; + Item[] flags = corpse.FindItemsByType(typeof(CTFFlag), false); - public override void OnStart() - { - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - CTFTeamInfo teamInfo = Controller.TeamInfo[i]; + for (int i = 0; i < flags.Length; ++i) + (flags[i] as CTFFlag).DropTo(mob, killer); - teamInfo.Game = this; - teamInfo.Reset(); - } + hadFlag = hadFlag || flags.Length > 0; - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - ApplyHues( m_Context.Participants[i] as Participant, Controller.TeamInfo[i % 8].Color ); + if (mob.Backpack != null) + { + flags = mob.Backpack.FindItemsByType(typeof(CTFFlag), false); - m_FinishTimer?.Stop(); + for (int i = 0; i < flags.Length; ++i) + (flags[i] as CTFFlag).DropTo(mob, killer); - m_FinishTimer = Timer.DelayCall( Controller.Duration, Finish_Callback ); - } + hadFlag = hadFlag || flags.Length > 0; + } - private void Finish_Callback() - { - List teams = new List(); + if (killer != null && killer.Player) + { + CTFTeamInfo teamInfo = GetTeamInfo(killer); + CTFTeamInfo victInfo = GetTeamInfo(mob); - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - CTFTeamInfo teamInfo = Controller.TeamInfo[i % 8]; - - if ( teamInfo?.Flag == null ) - continue; + if (teamInfo != null && teamInfo != victInfo) + { + CTFPlayerInfo playerInfo = teamInfo[killer]; - teams.Add( teamInfo ); - } + if (playerInfo != null) + { + playerInfo.Kills += 1; + playerInfo.Score += 1; // base frag - teams.Sort( delegate( CTFTeamInfo a, CTFTeamInfo b ) - { - return b.Score - a.Score; - } ); + if (hadFlag) + playerInfo.Score += 4; // fragged flag carrier - Tournament tourny = m_Context.m_Tournament; + if (mob.InRange(teamInfo.Origin, 24) && mob.Map == Facet) + playerInfo.Score += 1; // fragged in base -- guarding + + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + if (Controller.TeamInfo[i] == teamInfo) + continue; + + Mobile ourFlagCarrier = null; + + if (Controller.TeamInfo[i].Flag != null) + ourFlagCarrier = Controller.TeamInfo[i].Flag.RootParent as Mobile; + + if (ourFlagCarrier != null && GetTeamInfo(ourFlagCarrier) == teamInfo) + { + for (int j = 0; j < ourFlagCarrier.Aggressors.Count; ++j) + { + if (!(ourFlagCarrier.Aggressors[j] is AggressorInfo aggr) || + aggr.Defender != ourFlagCarrier || aggr.Attacker != mob) + continue; - StringBuilder sb = new StringBuilder(); + playerInfo.Score += 2; // helped defend guy capturing enemy flag + break; + } + + if (mob.Map == ourFlagCarrier.Map && ourFlagCarrier.InRange(mob, 12)) + playerInfo.Score += 1; // helped defend guy capturing enemy flag + } + } + } + } + } - if ( tourny != null && tourny.TournyType == TournyType.FreeForAll ) - { - sb.Append( m_Context.Participants.Count * tourny.PlayersPerParticipant ); - sb.Append( "-man FFA" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.RandomTeam ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-team" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.Faction ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-team Faction" ); - } - else if ( tourny != null ) - { - for ( int i = 0; i < tourny.ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); - - sb.Append( tourny.PlayersPerParticipant ); - } - } - - if ( Controller != null ) - sb.Append( ' ' ).Append( Controller.Title ); - - string title = sb.ToString(); - - CTFTeamInfo winner = ( teams.Count > 0 ? teams[0] : null ); - - for ( int i = 0; i < teams.Count; ++i ) - { - TrophyRank rank = TrophyRank.Bronze; - - if ( i == 0 ) - rank = TrophyRank.Gold; - else if ( i == 1 ) - rank = TrophyRank.Silver; - - CTFPlayerInfo leader = teams[i].Leader; + mob.CloseGump(typeof(CTFBoardGump)); + mob.SendGump(new CTFBoardGump(mob, this)); - foreach ( CTFPlayerInfo pl in teams[i].Players.Values ) - { - Mobile mob = pl.Player; - - if ( mob == null ) - continue; - - //"Red v Blue CTF Champion" - - sb = new StringBuilder(); - - sb.Append( title ); - - if ( pl == leader ) - sb.Append( " Leader" ); - - if ( pl.Score > 0 ) - { - sb.Append( ": " ); - - sb.Append( pl.Score.ToString( "N0" ) ); - sb.Append( pl.Score == 1 ? " point" : " points" ); - - if ( pl.Kills > 0 ) - { - sb.Append( ", " ); - sb.Append( pl.Kills.ToString( "N0" ) ); - sb.Append( pl.Kills == 1 ? " kill" : " kills" ); - } - - if ( pl.Captures > 0 ) - { - sb.Append( ", " ); - sb.Append( pl.Captures.ToString( "N0" ) ); - sb.Append( pl.Captures == 1 ? " capture" : " captures" ); - } - } - - Item item = new Trophy( sb.ToString(), rank ); - - if ( pl == leader ) - item.ItemID = 4810; - - item.Name = $"{item.Name}, {teams[i].Name.ToLower()} team"; - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - int cash = pl.Score * 250; - - if ( cash > 0 ) - { - item = new BankCheck( cash ); - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - mob.SendMessage( "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", rank.ToString().ToLower(), cash ); - } - else - { - mob.SendMessage( "You have been awarded a {0} trophy for your participation in this tournament.", rank.ToString().ToLower() ); - } - } - } - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - Participant p = m_Context.Participants[i] as Participant; + m_Context.Requip(mob, corpse); + DelayBounce(TimeSpan.FromSeconds(30.0), mob, corpse); - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + return false; + } - if ( dp?.Mobile != null ) - { - dp.Mobile.CloseGump( typeof( CTFBoardGump ) ); - dp.Mobile.SendGump( new CTFBoardGump( dp.Mobile, this ) ); - } - } + public override void OnStart() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + CTFTeamInfo teamInfo = Controller.TeamInfo[i]; - if ( i == winner.TeamID ) - continue; + teamInfo.Game = this; + teamInfo.Reset(); + } - for ( int j = 0; j < p.Players.Length; ++j ) - { - if ( p.Players[j] != null ) - p.Players[j].Eliminated = true; - } - } + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, Controller.TeamInfo[i % 8].Color); - m_Context.Finish( m_Context.Participants[winner.TeamID] as Participant ); - } + m_FinishTimer?.Stop(); - public override void OnStop() - { - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - CTFTeamInfo teamInfo = Controller.TeamInfo[i]; + m_FinishTimer = Timer.DelayCall(Controller.Duration, Finish_Callback); + } - if ( teamInfo.Flag != null ) - { - teamInfo.Flag.SendHome(); - teamInfo.Flag.m_TeamInfo = null; - } + private void Finish_Callback() + { + List teams = new List(); - if ( teamInfo.Board != null ) - teamInfo.Board.m_TeamInfo = null; + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + CTFTeamInfo teamInfo = Controller.TeamInfo[i % 8]; - teamInfo.Game = null; - } - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - ApplyHues( m_Context.Participants[i] as Participant, -1 ); - - m_FinishTimer?.Stop(); - - m_FinishTimer = null; - } - } -} + if (teamInfo?.Flag == null) + continue; + + teams.Add(teamInfo); + } + + teams.Sort(delegate(CTFTeamInfo a, CTFTeamInfo b) { return b.Score - a.Score; }); + + Tournament tourny = m_Context.m_Tournament; + + StringBuilder sb = new StringBuilder(); + + if (tourny != null && tourny.TournyType == TournyType.FreeForAll) + { + sb.Append(m_Context.Participants.Count * tourny.PlayersPerParticipant); + sb.Append("-man FFA"); + } + else if (tourny != null && tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team"); + } + else if (tourny != null && tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else if (tourny != null && tourny.TournyType == TournyType.Faction) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team Faction"); + } + else if (tourny != null) + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (Controller != null) + sb.Append(' ').Append(Controller.Title); + + string title = sb.ToString(); + + CTFTeamInfo winner = teams.Count > 0 ? teams[0] : null; + + for (int i = 0; i < teams.Count; ++i) + { + TrophyRank rank = TrophyRank.Bronze; + + if (i == 0) + rank = TrophyRank.Gold; + else if (i == 1) + rank = TrophyRank.Silver; + + CTFPlayerInfo leader = teams[i].Leader; + + foreach (CTFPlayerInfo pl in teams[i].Players.Values) + { + Mobile mob = pl.Player; + + if (mob == null) + continue; + + //"Red v Blue CTF Champion" + + sb = new StringBuilder(); + + sb.Append(title); + + if (pl == leader) + sb.Append(" Leader"); + + if (pl.Score > 0) + { + sb.Append(": "); + + sb.Append(pl.Score.ToString("N0")); + sb.Append(pl.Score == 1 ? " point" : " points"); + + if (pl.Kills > 0) + { + sb.Append(", "); + sb.Append(pl.Kills.ToString("N0")); + sb.Append(pl.Kills == 1 ? " kill" : " kills"); + } + + if (pl.Captures > 0) + { + sb.Append(", "); + sb.Append(pl.Captures.ToString("N0")); + sb.Append(pl.Captures == 1 ? " capture" : " captures"); + } + } + + Item item = new Trophy(sb.ToString(), rank); + + if (pl == leader) + item.ItemID = 4810; + + item.Name = $"{item.Name}, {teams[i].Name.ToLower()} team"; + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + int cash = pl.Score * 250; + + if (cash > 0) + { + item = new BankCheck(cash); + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + mob.SendMessage( + "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", + rank.ToString().ToLower(), cash); + } + else + { + mob.SendMessage("You have been awarded a {0} trophy for your participation in this tournament.", + rank.ToString().ToLower()); + } + } + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + Participant p = m_Context.Participants[i] as Participant; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; + + if (dp?.Mobile != null) + { + dp.Mobile.CloseGump(typeof(CTFBoardGump)); + dp.Mobile.SendGump(new CTFBoardGump(dp.Mobile, this)); + } + } + + if (i == winner.TeamID) + continue; + + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Eliminated = true; + } + + m_Context.Finish(m_Context.Participants[winner.TeamID] as Participant); + } + + public override void OnStop() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + CTFTeamInfo teamInfo = Controller.TeamInfo[i]; + + if (teamInfo.Flag != null) + { + teamInfo.Flag.SendHome(); + teamInfo.Flag.m_TeamInfo = null; + } + + if (teamInfo.Board != null) + teamInfo.Board.m_TeamInfo = null; + + teamInfo.Game = null; + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, -1); + + m_FinishTimer?.Stop(); + + m_FinishTimer = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Games/DoubleDom.cs b/Scripts/Engines/ConPVP/Games/DoubleDom.cs index cac4af78d..54a60c092 100644 --- a/Scripts/Engines/ConPVP/Games/DoubleDom.cs +++ b/Scripts/Engines/ConPVP/Games/DoubleDom.cs @@ -1,1144 +1,1133 @@ using System; +using System.Collections.Generic; using System.Text; +using Server.Gumps; using Server.Items; using Server.Mobiles; -using Server.Gumps; -using System.Collections.Generic; namespace Server.Engines.ConPVP { - public sealed class DDBoard : Item - { - public DDTeamInfo m_TeamInfo; - - public override string DefaultName => "scoreboard"; - - [Constructible] - public DDBoard() - : base( 7774 ) - { - Movable = false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_TeamInfo?.Game != null ) - { - from.CloseGump( typeof( DDBoardGump ) ); - from.SendGump( new DDBoardGump( from, m_TeamInfo.Game ) ); - } - } - - public DDBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DDBoardGump : Gump - { - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - private void AddBorderedText( int x, int y, int width, int height, string text, int color, int borderColor ) - { - AddColoredText( x - 1, y - 1, width, height, text, borderColor ); - AddColoredText( x - 1, y + 1, width, height, text, borderColor ); - AddColoredText( x + 1, y - 1, width, height, text, borderColor ); - AddColoredText( x + 1, y + 1, width, height, text, borderColor ); - AddColoredText( x, y, width, height, text, color ); - } - - private void AddColoredText( int x, int y, int width, int height, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, height, text, false, false ); - else - AddHtml( x, y, width, height, Color( text, color ), false, false ); - } - - private const int LabelColor32 = 0xFFFFFF; - private const int BlackColor32 = 0x000000; - - private DDGame m_Game; - - public DDBoardGump( Mobile mob, DDGame game ) - : this( mob, game, null ) - { - } - - public DDBoardGump( Mobile mob, DDGame game, DDTeamInfo section ) - : base( 60, 60 ) - { - m_Game = game; - - DDTeamInfo ourTeam = game.GetTeamInfo( mob ); - - List entries = new List(); - - if ( section == null ) - { - for ( int i = 0; i < game.Context.Participants.Count; ++i ) - { - DDTeamInfo teamInfo = game.Controller.TeamInfo[i % game.Controller.TeamInfo.Length]; - - if ( teamInfo != null ) - entries.Add( teamInfo ); - } - } - else - { - foreach ( DDPlayerInfo player in section.Players.Values ) - { - if ( player.Score > 0 ) - entries.Add( player ); - } - } - - entries.Sort( delegate( IRankedCTF a, IRankedCTF b ) - { - return b.Score - a.Score; - } ); - - int height = 0; + public sealed class DDBoard : Item + { + public DDTeamInfo m_TeamInfo; - if ( section == null ) - height = 73 + ( entries.Count * 75 ) + 28; + [Constructible] + public DDBoard() + : base(7774) + { + Movable = false; + } - Closable = false; + public DDBoard(Serial serial) + : base(serial) + { + } - AddPage( 0 ); + public override string DefaultName => "scoreboard"; - AddBackground( 1, 1, 398, height, 3600 ); + public override void OnDoubleClick(Mobile from) + { + if (m_TeamInfo?.Game != null) + { + from.CloseGump(typeof(DDBoardGump)); + from.SendGump(new DDBoardGump(from, m_TeamInfo.Game)); + } + } - AddImageTiled( 16, 15, 369, height - 29, 3604 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - for ( int i = 0; i < entries.Count; i += 1 ) - AddImageTiled( 22, 58 + ( i * 75 ), 357, 70, 0x2430 ); + writer.Write(0); + } - AddAlphaRegion( 16, 15, 369, height - 29 ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - AddImage( 215, -45, 0xEE40 ); - //AddImage( 330, 141, 0x8BA ); + int version = reader.ReadInt(); + } + } - AddBorderedText( 22, 22, 294, 20, Center( "DD Scoreboard" ), LabelColor32, BlackColor32 ); + public class DDBoardGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int BlackColor32 = 0x000000; - AddImageTiled( 32, 50, 264, 1, 9107 ); - AddImageTiled( 42, 52, 264, 1, 9157 ); + private DDGame m_Game; - if ( section == null ) - { - for ( int i = 0; i < entries.Count; ++i ) - { - DDTeamInfo teamInfo = entries[i] as DDTeamInfo; + public DDBoardGump(Mobile mob, DDGame game) + : this(mob, game, null) + { + } - AddImage( 30, 70 + ( i * 75 ), 10152 ); - AddImage( 30, 85 + ( i * 75 ), 10151 ); - AddImage( 30, 100 + ( i * 75 ), 10151 ); - AddImage( 30, 106 + ( i * 75 ), 10154 ); - - AddImage( 24, 60 + ( i * 75 ), teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1 ); + public DDBoardGump(Mobile mob, DDGame game, DDTeamInfo section) + : base(60, 60) + { + m_Game = game; - int nameColor = LabelColor32; - int borderColor = BlackColor32; - - switch ( teamInfo.Color ) - { - case 0x47E: - nameColor = 0xFFFFFF; - break; + DDTeamInfo ourTeam = game.GetTeamInfo(mob); - case 0x4F2: - nameColor = 0x3399FF; - break; + List entries = new List(); - case 0x4F7: - nameColor = 0x33FF33; - break; + if (section == null) + for (int i = 0; i < game.Context.Participants.Count; ++i) + { + DDTeamInfo teamInfo = game.Controller.TeamInfo[i % game.Controller.TeamInfo.Length]; - case 0x4FC: - nameColor = 0xFF00FF; - break; + if (teamInfo != null) + entries.Add(teamInfo); + } + else + foreach (DDPlayerInfo player in section.Players.Values) + if (player.Score > 0) + entries.Add(player); - case 0x021: - nameColor = 0xFF3333; - break; + entries.Sort(delegate(IRankedCTF a, IRankedCTF b) { return b.Score - a.Score; }); - case 0x01A: - nameColor = 0xFF66FF; - break; + int height = 0; - case 0x455: - nameColor = 0x333333; - borderColor = 0xFFFFFF; - break; - } + if (section == null) + height = 73 + entries.Count * 75 + 28; - AddBorderedText( 60, 65 + ( i * 75 ), 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name}", nameColor, borderColor ); + Closable = false; - AddBorderedText( 50 + 10, 85 + ( i * 75 ), 100, 20, "Score:", 0xFFC000, BlackColor32 ); - AddBorderedText( 50 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Score.ToString( "N0" ), 0xFFC000, BlackColor32 ); + AddPage(0); - AddBorderedText( 110 + 10, 85 + ( i * 75 ), 100, 20, "Kills:", 0xFFC000, BlackColor32 ); - AddBorderedText( 110 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Kills.ToString( "N0" ), 0xFFC000, BlackColor32 ); + AddBackground(1, 1, 398, height, 3600); - AddBorderedText( 160 + 10, 85 + ( i * 75 ), 100, 20, "Captures:", 0xFFC000, BlackColor32 ); - AddBorderedText( 160 + 15, 105 + ( i * 75 ), 100, 20, teamInfo.Captures.ToString( "N0" ), 0xFFC000, BlackColor32 ); + AddImageTiled(16, 15, 369, height - 29, 3604); - DDPlayerInfo pl = teamInfo.Leader; + for (int i = 0; i < entries.Count; i += 1) + AddImageTiled(22, 58 + i * 75, 357, 70, 0x2430); - AddBorderedText( 235 + 10, 85 + ( i * 75 ), 250, 20, "Leader:", 0xFFC000, BlackColor32 ); + AddAlphaRegion(16, 15, 369, height - 29); - if ( pl != null ) - AddBorderedText( 235 + 15, 105 + ( i * 75 ), 250, 20, pl.Player.Name, 0xFFC000, BlackColor32 ); - } - } + AddImage(215, -45, 0xEE40); + //AddImage( 330, 141, 0x8BA ); - AddButton( 314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0 ); - } - } + AddBorderedText(22, 22, 294, 20, Center("DD Scoreboard"), LabelColor32, BlackColor32); - public sealed class DDPlayerInfo : IRankedCTF - { - private DDTeamInfo m_TeamInfo; + AddImageTiled(32, 50, 264, 1, 9107); + AddImageTiled(42, 52, 264, 1, 9157); - private int m_Kills; - private int m_Captures; + if (section == null) + for (int i = 0; i < entries.Count; ++i) + { + DDTeamInfo teamInfo = entries[i] as DDTeamInfo; - private int m_Score; + AddImage(30, 70 + i * 75, 10152); + AddImage(30, 85 + i * 75, 10151); + AddImage(30, 100 + i * 75, 10151); + AddImage(30, 106 + i * 75, 10154); - public Mobile Player { get; } + AddImage(24, 60 + i * 75, teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1); - public string Name => Player.Name; + int nameColor = LabelColor32; + int borderColor = BlackColor32; - public int Kills - { - get => m_Kills; - set - { - m_TeamInfo.Kills += ( value - m_Kills ); - m_Kills = value; - } - } + switch (teamInfo.Color) + { + case 0x47E: + nameColor = 0xFFFFFF; + break; - public int Captures - { - get => m_Captures; - set - { - m_TeamInfo.Captures += ( value - m_Captures ); - m_Captures = value; - } - } + case 0x4F2: + nameColor = 0x3399FF; + break; - public int Score - { - get => m_Score; - set - { - m_TeamInfo.Score += ( value - m_Score ); - m_Score = value; + case 0x4F7: + nameColor = 0x33FF33; + break; - if ( m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score ) - m_TeamInfo.Leader = this; - } - } + case 0x4FC: + nameColor = 0xFF00FF; + break; - public DDPlayerInfo( DDTeamInfo teamInfo, Mobile player ) - { - m_TeamInfo = teamInfo; - Player = player; - } - } + case 0x021: + nameColor = 0xFF3333; + break; - [PropertyObject] - public sealed class DDTeamInfo : IRankedCTF - { - public string Name => $"{TeamName} Team"; + case 0x01A: + nameColor = 0xFF66FF; + break; - public DDGame Game { get; set; } + case 0x455: + nameColor = 0x333333; + borderColor = 0xFFFFFF; + break; + } - public int TeamID { get; } + AddBorderedText(60, 65 + i * 75, 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name}", nameColor, + borderColor); - public int Kills { get; set; } + AddBorderedText(50 + 10, 85 + i * 75, 100, 20, "Score:", 0xFFC000, BlackColor32); + AddBorderedText(50 + 15, 105 + i * 75, 100, 20, teamInfo.Score.ToString("N0"), 0xFFC000, BlackColor32); - public int Captures { get; set; } + AddBorderedText(110 + 10, 85 + i * 75, 100, 20, "Kills:", 0xFFC000, BlackColor32); + AddBorderedText(110 + 15, 105 + i * 75, 100, 20, teamInfo.Kills.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(160 + 10, 85 + i * 75, 100, 20, "Captures:", 0xFFC000, BlackColor32); + AddBorderedText(160 + 15, 105 + i * 75, 100, 20, teamInfo.Captures.ToString("N0"), 0xFFC000, + BlackColor32); + + DDPlayerInfo pl = teamInfo.Leader; + + AddBorderedText(235 + 10, 85 + i * 75, 250, 20, "Leader:", 0xFFC000, BlackColor32); + + if (pl != null) + AddBorderedText(235 + 15, 105 + i * 75, 250, 20, pl.Player.Name, 0xFFC000, BlackColor32); + } + + AddButton(314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + } + + public sealed class DDPlayerInfo : IRankedCTF + { + private int m_Captures; + + private int m_Kills; + + private int m_Score; + private DDTeamInfo m_TeamInfo; + + public DDPlayerInfo(DDTeamInfo teamInfo, Mobile player) + { + m_TeamInfo = teamInfo; + Player = player; + } + + public Mobile Player{ get; } + + public string Name => Player.Name; + + public int Kills + { + get => m_Kills; + set + { + m_TeamInfo.Kills += value - m_Kills; + m_Kills = value; + } + } + + public int Captures + { + get => m_Captures; + set + { + m_TeamInfo.Captures += value - m_Captures; + m_Captures = value; + } + } + + public int Score + { + get => m_Score; + set + { + m_TeamInfo.Score += value - m_Score; + m_Score = value; + + if (m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score) + m_TeamInfo.Leader = this; + } + } + } + + [PropertyObject] + public sealed class DDTeamInfo : IRankedCTF + { + public DDTeamInfo(int teamID) + { + TeamID = teamID; + Players = new Dictionary(); + } + + public DDTeamInfo(int teamID, GenericReader ip) + { + TeamID = teamID; + Players = new Dictionary(); + + int version = ip.ReadEncodedInt(); + + switch (version) + { + case 0: + { + Board = ip.ReadItem() as DDBoard; + TeamName = ip.ReadString(); + Color = ip.ReadEncodedInt(); + Origin = ip.ReadPoint3D(); + break; + } + } + } + + public DDGame Game{ get; set; } + + public int TeamID{ get; } + + public DDPlayerInfo Leader{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DDBoard Board{ get; set; } + + public Dictionary Players{ get; } + + public DDPlayerInfo this[Mobile mob] + { + get + { + if (mob == null) + return null; + + if (!Players.TryGetValue(mob, out DDPlayerInfo val)) + Players[mob] = val = new DDPlayerInfo(this, mob); + + return val; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Color{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string TeamName{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Origin{ get; set; } + + public string Name => $"{TeamName} Team"; + + public int Kills{ get; set; } + + public int Captures{ get; set; } + + public int Score{ get; set; } + + public void Reset() + { + Kills = 0; + Captures = 0; - public int Score { get; set; } + Score = 0; - public DDPlayerInfo Leader { get; set; } + Leader = null; - [CommandProperty( AccessLevel.GameMaster )] - public DDBoard Board { get; set; } + Players.Clear(); - public Dictionary Players { get; } + if (Board != null) + Board.m_TeamInfo = this; + } - public DDPlayerInfo this[Mobile mob] - { - get - { - if ( mob == null ) - return null; + public void Serialize(GenericWriter op) + { + op.WriteEncodedInt(0); // version - if (!Players.TryGetValue( mob, out DDPlayerInfo val )) - Players[mob] = val = new DDPlayerInfo( this, mob ); + op.Write(Board); + op.Write(TeamName); + op.WriteEncodedInt(Color); + op.Write(Origin); + } - return val; - } - } + public override string ToString() + { + return "..."; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public int Color { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string TeamName { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Origin { get; set; } + public sealed class DDController : EventController + { + [Constructible] + public DDController() + { + Visible = false; + Movable = false; - public DDTeamInfo( int teamID ) - { - TeamID = teamID; - Players = new Dictionary(); - } + Duration = TimeSpan.FromMinutes(30.0); - public void Reset() - { - Kills = 0; - Captures = 0; + TeamInfo = new DDTeamInfo[2]; - Score = 0; - - Leader = null; - - Players.Clear(); - - if ( Board != null ) - Board.m_TeamInfo = this; - } + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new DDTeamInfo(i); + } - public DDTeamInfo( int teamID, GenericReader ip ) - { - TeamID = teamID; - Players = new Dictionary(); + public DDController(Serial serial) + : base(serial) + { + } - int version = ip.ReadEncodedInt(); + public DDTeamInfo[] TeamInfo{ get; private set; } - switch ( version ) - { - case 0: - { - Board = ip.ReadItem() as DDBoard; - TeamName = ip.ReadString(); - Color = ip.ReadEncodedInt(); - Origin = ip.ReadPoint3D(); - break; - } - } - } + [CommandProperty(AccessLevel.GameMaster)] + public DDTeamInfo Team1 + { + get => TeamInfo[0]; + set { } + } - public void Serialize( GenericWriter op ) - { - op.WriteEncodedInt( 0 ); // version + [CommandProperty(AccessLevel.GameMaster)] + public DDTeamInfo Team2 + { + get => TeamInfo[1]; + set { } + } - op.Write( Board ); - op.Write( TeamName ); - op.WriteEncodedInt( Color ); - op.Write( Origin ); - } + [CommandProperty(AccessLevel.GameMaster)] + public DDWayPoint PointA{ get; set; } - public override string ToString() - { - return "..."; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public DDWayPoint PointB{ get; set; } - public sealed class DDController : EventController - { - public DDTeamInfo[] TeamInfo { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan Duration{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public DDTeamInfo Team1 { get => TeamInfo[0]; - set { } } + public override string Title => "DoubleDom"; - [CommandProperty( AccessLevel.GameMaster )] - public DDTeamInfo Team2 { get => TeamInfo[1]; - set { } } + public override string DefaultName => "DD Controller"; - [CommandProperty( AccessLevel.GameMaster )] - public DDWayPoint PointA { get; set; } + public override string GetTeamName(int teamID) + { + return TeamInfo[teamID % TeamInfo.Length].Name; + } - [CommandProperty( AccessLevel.GameMaster )] - public DDWayPoint PointB { get; set; } + public override EventGame Construct(DuelContext context) + { + return new DDGame(this, context); + } - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan Duration { get; set; } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override string Title => "DoubleDom"; + writer.Write(0); - public override string GetTeamName( int teamID ) - { - return TeamInfo[teamID % TeamInfo.Length].Name; - } + writer.Write(Duration); - public override EventGame Construct( DuelContext context ) - { - return new DDGame( this, context ); - } + writer.WriteEncodedInt(TeamInfo.Length); - public override string DefaultName => "DD Controller"; - - [Constructible] - public DDController() - { - Visible = false; - Movable = false; - - Duration = TimeSpan.FromMinutes( 30.0 ); - - TeamInfo = new DDTeamInfo[2]; - - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new DDTeamInfo( i ); - } + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i].Serialize(writer); - public DDController( Serial serial ) - : base( serial ) - { - } + writer.Write(PointA); + writer.Write(PointB); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int)0 ); - - writer.Write( Duration ); - - writer.WriteEncodedInt( TeamInfo.Length ); - - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i].Serialize( writer ); - - writer.Write( PointA ); - writer.Write( PointB ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Duration = reader.ReadTimeSpan(); - TeamInfo = new DDTeamInfo[reader.ReadEncodedInt()]; - - for ( int i = 0; i < TeamInfo.Length; ++i ) - TeamInfo[i] = new DDTeamInfo( i, reader ); - - PointA = reader.ReadItem() as DDWayPoint; - PointB = reader.ReadItem() as DDWayPoint; - - break; - } - } - } - } + int version = reader.ReadInt(); - public sealed class DDGame : EventGame - { - public DDController Controller { get; } + switch (version) + { + case 0: + { + Duration = reader.ReadTimeSpan(); + TeamInfo = new DDTeamInfo[reader.ReadEncodedInt()]; - public void Alert( string text ) - { - m_Context.m_Tournament?.Alert( text ); + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new DDTeamInfo(i, reader); - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - Participant p = m_Context.Participants[i] as Participant; + PointA = reader.ReadItem() as DDWayPoint; + PointB = reader.ReadItem() as DDWayPoint; - for ( int j = 0; j < p.Players.Length; ++j ) - { - if ( p.Players[j] != null ) - p.Players[j].Mobile.SendMessage( 0x35, text ); - } - } - } - - public void Alert( string format, params object[] args ) - { - Alert( string.Format( format, args ) ); - } - - public DDGame( DDController controller, DuelContext context ) : base( context ) - { - Controller = controller; - } - - public Map Facet - { - get - { - if ( m_Context.Arena != null ) - return m_Context.Arena.Facet; - - return Controller.Map; - } - } - - public DDTeamInfo GetTeamInfo( Mobile mob ) - { - int teamID = GetTeamID( mob ); - - if ( teamID >= 0 ) - return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; - - return null; - } - - public int GetTeamID( Mobile mob ) - { - if ( !(mob is PlayerMobile pm) ) - return -1; - - if ( pm.DuelContext == null || pm.DuelContext != m_Context ) - return -1; - - if ( pm.DuelPlayer == null || pm.DuelPlayer.Eliminated ) - return -1; - - return pm.DuelContext.Participants.IndexOf( pm.DuelPlayer.Participant ); - } - - public int GetColor( Mobile mob ) - { - return GetTeamInfo( mob )?.Color ?? -1; - } - - private void ApplyHues( Participant p, int hueOverride ) - { - for ( int i = 0; i < p.Players.Length; ++i ) - { - if ( p.Players[i] != null ) - p.Players[i].Mobile.SolidHueOverride = hueOverride; - } - } - - public void DelayBounce( TimeSpan ts, Mobile mob, Container corpse ) - { - Timer.DelayCall( ts, new TimerStateCallback( DelayBounce_Callback ), new object[] { mob, corpse } ); - } - - private void DelayBounce_Callback( object state ) - { - object[] states = (object[]) state; - Mobile mob = (Mobile) states[0]; - Container corpse = (Container) states[1]; - - DuelPlayer dp = null; - - if ( mob is PlayerMobile mobile ) - dp = mobile.DuelPlayer; - - m_Context.RemoveAggressions( mob ); - - if ( dp != null && !dp.Eliminated ) - mob.MoveToWorld( m_Context.Arena.GetBaseStartPoint( GetTeamID( mob ) ), Facet ); - else - m_Context.SendOutside( mob ); - - m_Context.Refresh( mob, corpse ); - DuelContext.Debuff( mob ); - DuelContext.CancelSpell( mob ); - mob.Frozen = false; - } - - public override bool OnDeath( Mobile mob, Container corpse ) - { - Mobile killer = mob.FindMostRecentDamager( false ); - - if ( killer != null && killer.Player ) - { - DDTeamInfo teamInfo = GetTeamInfo( killer ); - DDTeamInfo victInfo = GetTeamInfo( mob ); - - if ( teamInfo != null && teamInfo != victInfo ) - { - DDPlayerInfo playerInfo = teamInfo[killer]; - - if ( playerInfo != null ) - { - playerInfo.Kills += 1; - playerInfo.Score += 1; // base frag - - // extra points for killing someone on the waypoint - if ( Controller.PointA != null ) - { - if ( mob.InRange( Controller.PointA, 2 ) ) - playerInfo.Score += 1; - } - - if ( Controller.PointB != null ) - { - if ( mob.InRange( Controller.PointB, 2 ) ) - playerInfo.Score += 1; - } - } - - playerInfo = victInfo[mob]; - if ( playerInfo != null ) - playerInfo.Score -= 1; - } - } - - mob.CloseGump( typeof( DDBoardGump ) ); - mob.SendGump( new DDBoardGump( mob, this ) ); - - m_Context.Requip( mob, corpse ); - DelayBounce( TimeSpan.FromSeconds( 30.0 ), mob, corpse ); - - return false; - } - - private Timer m_FinishTimer; - - public override void OnStart() - { - m_Capturable = true; - - if ( m_CaptureTimer != null ) - { - m_CaptureTimer.Stop(); - m_CaptureTimer = null; - } - - if ( m_UncaptureTimer != null ) - { - m_UncaptureTimer.Stop(); - m_UncaptureTimer = null; - } - - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - DDTeamInfo teamInfo = Controller.TeamInfo[i]; - - teamInfo.Game = this; - teamInfo.Reset(); - } - - if ( Controller.PointA != null ) - Controller.PointA.Game = this; - - if ( Controller.PointB != null ) - Controller.PointB.Game = this; - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - ApplyHues( m_Context.Participants[i] as Participant, Controller.TeamInfo[i % Controller.TeamInfo.Length].Color ); - - m_FinishTimer?.Stop(); - m_FinishTimer = Timer.DelayCall( Controller.Duration, Finish_Callback ); - } - - private void Finish_Callback() - { - List teams = new List(); - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - DDTeamInfo teamInfo = Controller.TeamInfo[i % Controller.TeamInfo.Length]; - - if ( teamInfo != null ) - teams.Add( teamInfo ); - } - - teams.Sort((a, b) => b.Score - a.Score); - - Tournament tourny = m_Context.m_Tournament; - - StringBuilder sb = new StringBuilder(); - - if ( tourny != null && tourny.TournyType == TournyType.FreeForAll ) - { - sb.Append( m_Context.Participants.Count * tourny.PlayersPerParticipant ); - sb.Append( "-man FFA" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.RandomTeam ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-team" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else if ( tourny != null && tourny.TournyType == TournyType.Faction ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-team Faction" ); - } - else if ( tourny != null ) - { - for ( int i = 0; i < tourny.ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); - - sb.Append( tourny.PlayersPerParticipant ); - } - } - - if ( Controller != null ) - sb.Append( ' ' ).Append( Controller.Title ); + break; + } + } + } + } - string title = sb.ToString(); - - DDTeamInfo winner = (DDTeamInfo)( teams.Count > 0 ? teams[0] : null ); - - for ( int i = 0; i < teams.Count; ++i ) - { - TrophyRank rank = TrophyRank.Bronze; - - if ( i == 0 ) - rank = TrophyRank.Gold; - else if ( i == 1 ) - rank = TrophyRank.Silver; - - DDPlayerInfo leader = ((DDTeamInfo)teams[i]).Leader; - - foreach ( DDPlayerInfo pl in ((DDTeamInfo)teams[i]).Players.Values ) - { - Mobile mob = pl.Player; - - if ( mob == null ) - continue; - - //"Red v Blue DD Champion" - - sb = new StringBuilder(); - - sb.Append( title ); + public sealed class DDGame : EventGame + { + private int m_CapStage; - if ( pl == leader ) - sb.Append( " Leader" ); + private bool m_Capturable = true; + private Timer m_CaptureTimer; - if ( pl.Score > 0 ) - { - sb.Append( ": " ); + private Timer m_FinishTimer; + private Timer m_UncaptureTimer; - sb.Append( pl.Score.ToString( "N0" ) ); - sb.Append( pl.Score == 1 ? " point" : " points" ); - - if ( pl.Kills > 0 ) - { - sb.Append( ", " ); - sb.Append( pl.Kills.ToString( "N0" ) ); - sb.Append( pl.Kills == 1 ? " kill" : " kills" ); - } - - if ( pl.Captures > 0 ) - { - sb.Append( ", " ); - sb.Append( pl.Captures.ToString( "N0" ) ); - sb.Append( pl.Captures == 1 ? " capture" : " captures" ); - } - } - - Item item = new Trophy( sb.ToString(), rank ); - - if ( pl == leader ) - item.ItemID = 4810; - - item.Name = $"{item.Name}, {((DDTeamInfo) teams[i]).Name.ToLower()} team"; - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - int cash = pl.Score * 250; - - if ( cash > 0 ) - { - item = new BankCheck( cash ); - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - mob.SendMessage( "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", rank.ToString().ToLower(), cash ); - } - else - { - mob.SendMessage( "You have been awarded a {0} trophy for your participation in this tournament.", rank.ToString().ToLower() ); - } - } - } - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - { - Participant p = m_Context.Participants[i] as Participant; + public DDGame(DDController controller, DuelContext context) : base(context) + { + Controller = controller; + } - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer dp = p.Players[j]; + public DDController Controller{ get; } - if ( dp?.Mobile != null ) - { - dp.Mobile.CloseGump( typeof( DDBoardGump ) ); - dp.Mobile.SendGump( new DDBoardGump( dp.Mobile, this ) ); - } - } + public Map Facet + { + get + { + if (m_Context.Arena != null) + return m_Context.Arena.Facet; - if ( i == winner.TeamID ) - continue; + return Controller.Map; + } + } - for ( int j = 0; j < p.Players.Length; ++j ) - { - if ( p.Players[j] != null ) - p.Players[j].Eliminated = true; - } - } - - m_Context.Finish( m_Context.Participants[winner.TeamID] as Participant ); - } - - public override void OnStop() - { - for ( int i = 0; i < Controller.TeamInfo.Length; ++i ) - { - DDTeamInfo teamInfo = Controller.TeamInfo[i]; - - if ( teamInfo.Board != null ) - teamInfo.Board.m_TeamInfo = null; - - teamInfo.Game = null; - } - - if ( Controller.PointA != null ) - Controller.PointA.Game = null; - - if ( Controller.PointB != null ) - Controller.PointB.Game = null; - - m_Capturable = false; - - if ( m_CaptureTimer != null ) - { - m_CaptureTimer.Stop(); - m_CaptureTimer = null; - } - - if ( m_UncaptureTimer != null ) - { - m_UncaptureTimer.Stop(); - m_UncaptureTimer = null; - } - - for ( int i = 0; i < m_Context.Participants.Count; ++i ) - ApplyHues( m_Context.Participants[i] as Participant, -1 ); - - m_FinishTimer?.Stop(); - m_FinishTimer = null; - } - - private bool m_Capturable = true; - private Timer m_CaptureTimer; - private Timer m_UncaptureTimer; - private int m_CapStage; - - public void Dominate( DDWayPoint point, Mobile from, DDTeamInfo team ) - { - if ( point == null || from == null || team == null || !m_Capturable ) - return; - - bool wasDom = ( Controller.PointA != null && Controller.PointB != null && - Controller.PointA.TeamOwner == Controller.PointB.TeamOwner && Controller.PointA.TeamOwner != null ); - - point.TeamOwner = team; - Alert( "{0} has captured {1}!", team.Name, point.Name ); - - bool isDom = ( Controller.PointA != null && Controller.PointB != null && - Controller.PointA.TeamOwner == Controller.PointB.TeamOwner && Controller.PointA.TeamOwner != null ); - - if ( wasDom && !isDom ) - { - Alert( "Domination averted!" ); - - Controller.PointA?.SetNonCaptureHue(); - Controller.PointB?.SetNonCaptureHue(); - m_CaptureTimer?.Stop(); - m_CaptureTimer = null; - } - - if ( !wasDom && isDom ) - { - m_CapStage = 0; - m_CaptureTimer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ), CaptureTick ); - m_CaptureTimer.Start(); - } - } - - private void CaptureTick() - { - DDTeamInfo team = null; - - if ( Controller.PointA?.TeamOwner != null ) - team = Controller.PointA.TeamOwner; - else if ( Controller.PointB?.TeamOwner != null ) - team = Controller.PointB.TeamOwner; - - if ( team == null ) - { - m_Capturable = true; - m_CaptureTimer?.Stop(); - m_CaptureTimer = null; - return; - } - - if ( ++m_CapStage < 10 ) - { - Alert( "{0} is dominating... {1}", team.Name, 10 - m_CapStage ); - - Controller.PointA?.SetCaptureHue( m_CapStage ); - Controller.PointB?.SetCaptureHue( m_CapStage ); - } - else - { - Alert( "{0} has scored!", team.Name ); - - team.Score += 100; - team.Captures += 1; - - m_Capturable = false; - m_CapStage = 0; - m_CaptureTimer.Stop(); - m_CaptureTimer = null; - - if ( Controller.PointA != null ) - { - Controller.PointA.TeamOwner = null; - Controller.PointA.SetUncapturableHue(); - } - - if ( Controller.PointB != null ) - { - Controller.PointB.TeamOwner = null; - Controller.PointB.SetUncapturableHue(); - } - - m_UncaptureTimer = Timer.DelayCall( TimeSpan.FromSeconds( 30.0 ), UncaptureTick ); - m_UncaptureTimer.Start(); - } - } - - private void UncaptureTick() - { - m_Capturable = true; - - if ( m_CaptureTimer != null ) - { - m_CaptureTimer.Stop(); - m_CaptureTimer = null; - } - - if ( m_UncaptureTimer != null ) - { - m_UncaptureTimer.Stop(); - m_UncaptureTimer = null; - } - - if ( Controller.PointA != null ) - { - Controller.PointA.TeamOwner = null; - Controller.PointA.SetNonCaptureHue(); - } - - if ( Controller.PointB != null ) - { - Controller.PointB.TeamOwner = null; - Controller.PointB.SetNonCaptureHue(); - } - } - } - - public class DDWayPoint : BaseAddon - { - private DDTeamInfo m_TeamOwner; - private DDGame m_Game; - - [Constructible] - public DDWayPoint() - { - ItemID = 0x519; - Visible = true; - Name = "SET MY NAME"; - - AddComponent( new DDStep( 0x7A8 ), -1, -1, -5 ); - AddComponent( new DDStep( 0x7A6 ), 0, -1, -5 ); - AddComponent( new DDStep( 0x7AA ), 1, -1, -5 ); - - AddComponent( new DDStep( 0x7A5 ), 1, 0, -5 ); - - AddComponent( new DDStep( 0x7A9 ), 1, 1, -5 ); - AddComponent( new DDStep( 0x7A4 ), 0, 1, -5 ); - AddComponent( new DDStep( 0x7AB ), -1, 1, -5 ); - - AddComponent( new DDStep( 0x7A7 ), -1, 0, -5 ); - - SetUncapturableHue(); - } - - public DDWayPoint( Serial serial ) : base(serial) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - - public override bool ShareHue => false; - - public DDGame Game - { - get => m_Game; - set - { - m_Game = value; - m_TeamOwner = null; - - if ( m_Game != null ) - SetNonCaptureHue(); - else - SetUncapturableHue(); - } - } - - public DDTeamInfo TeamOwner - { - get => m_TeamOwner; - set - { - m_TeamOwner = value; - - SetNonCaptureHue(); - } - } - - public const int UncapturableHue = 0x497; - public const int NonCapturedHue = 0x38A; - - public void SetUncapturableHue() - { - for (int i=0;i= 0) + return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; + + return null; + } + + public int GetTeamID(Mobile mob) + { + if (!(mob is PlayerMobile pm)) + return -1; + + if (pm.DuelContext == null || pm.DuelContext != m_Context) + return -1; + + if (pm.DuelPlayer == null || pm.DuelPlayer.Eliminated) + return -1; + + return pm.DuelContext.Participants.IndexOf(pm.DuelPlayer.Participant); + } + + public int GetColor(Mobile mob) + { + return GetTeamInfo(mob)?.Color ?? -1; + } + + private void ApplyHues(Participant p, int hueOverride) + { + for (int i = 0; i < p.Players.Length; ++i) + if (p.Players[i] != null) + p.Players[i].Mobile.SolidHueOverride = hueOverride; + } + + public void DelayBounce(TimeSpan ts, Mobile mob, Container corpse) + { + Timer.DelayCall(ts, new TimerStateCallback(DelayBounce_Callback), new object[] { mob, corpse }); + } + + private void DelayBounce_Callback(object state) + { + object[] states = (object[])state; + Mobile mob = (Mobile)states[0]; + Container corpse = (Container)states[1]; + + DuelPlayer dp = null; + + if (mob is PlayerMobile mobile) + dp = mobile.DuelPlayer; + + m_Context.RemoveAggressions(mob); + + if (dp != null && !dp.Eliminated) + mob.MoveToWorld(m_Context.Arena.GetBaseStartPoint(GetTeamID(mob)), Facet); + else + m_Context.SendOutside(mob); + + m_Context.Refresh(mob, corpse); + DuelContext.Debuff(mob); + DuelContext.CancelSpell(mob); + mob.Frozen = false; + } + + public override bool OnDeath(Mobile mob, Container corpse) + { + Mobile killer = mob.FindMostRecentDamager(false); + + if (killer != null && killer.Player) + { + DDTeamInfo teamInfo = GetTeamInfo(killer); + DDTeamInfo victInfo = GetTeamInfo(mob); + + if (teamInfo != null && teamInfo != victInfo) + { + DDPlayerInfo playerInfo = teamInfo[killer]; + + if (playerInfo != null) + { + playerInfo.Kills += 1; + playerInfo.Score += 1; // base frag + + // extra points for killing someone on the waypoint + if (Controller.PointA != null) + if (mob.InRange(Controller.PointA, 2)) + playerInfo.Score += 1; + + if (Controller.PointB != null) + if (mob.InRange(Controller.PointB, 2)) + playerInfo.Score += 1; + } + + playerInfo = victInfo[mob]; + if (playerInfo != null) + playerInfo.Score -= 1; + } + } + + mob.CloseGump(typeof(DDBoardGump)); + mob.SendGump(new DDBoardGump(mob, this)); + + m_Context.Requip(mob, corpse); + DelayBounce(TimeSpan.FromSeconds(30.0), mob, corpse); + + return false; + } + + public override void OnStart() + { + m_Capturable = true; + + if (m_CaptureTimer != null) + { + m_CaptureTimer.Stop(); + m_CaptureTimer = null; + } + + if (m_UncaptureTimer != null) + { + m_UncaptureTimer.Stop(); + m_UncaptureTimer = null; + } + + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + DDTeamInfo teamInfo = Controller.TeamInfo[i]; + + teamInfo.Game = this; + teamInfo.Reset(); + } + + if (Controller.PointA != null) + Controller.PointA.Game = this; + + if (Controller.PointB != null) + Controller.PointB.Game = this; + + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, + Controller.TeamInfo[i % Controller.TeamInfo.Length].Color); + + m_FinishTimer?.Stop(); + m_FinishTimer = Timer.DelayCall(Controller.Duration, Finish_Callback); + } + + private void Finish_Callback() + { + List teams = new List(); + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + DDTeamInfo teamInfo = Controller.TeamInfo[i % Controller.TeamInfo.Length]; + + if (teamInfo != null) + teams.Add(teamInfo); + } + + teams.Sort((a, b) => b.Score - a.Score); + + Tournament tourny = m_Context.m_Tournament; + + StringBuilder sb = new StringBuilder(); + + if (tourny != null && tourny.TournyType == TournyType.FreeForAll) + { + sb.Append(m_Context.Participants.Count * tourny.PlayersPerParticipant); + sb.Append("-man FFA"); + } + else if (tourny != null && tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team"); + } + else if (tourny != null && tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else if (tourny != null && tourny.TournyType == TournyType.Faction) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team Faction"); + } + else if (tourny != null) + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (Controller != null) + sb.Append(' ').Append(Controller.Title); + + string title = sb.ToString(); + + DDTeamInfo winner = teams.Count > 0 ? teams[0] : null; + + for (int i = 0; i < teams.Count; ++i) + { + TrophyRank rank = TrophyRank.Bronze; + + if (i == 0) + rank = TrophyRank.Gold; + else if (i == 1) + rank = TrophyRank.Silver; + + DDPlayerInfo leader = teams[i].Leader; + + foreach (DDPlayerInfo pl in teams[i].Players.Values) + { + Mobile mob = pl.Player; + + if (mob == null) + continue; + + //"Red v Blue DD Champion" + + sb = new StringBuilder(); + + sb.Append(title); + + if (pl == leader) + sb.Append(" Leader"); + + if (pl.Score > 0) + { + sb.Append(": "); + + sb.Append(pl.Score.ToString("N0")); + sb.Append(pl.Score == 1 ? " point" : " points"); + + if (pl.Kills > 0) + { + sb.Append(", "); + sb.Append(pl.Kills.ToString("N0")); + sb.Append(pl.Kills == 1 ? " kill" : " kills"); + } + + if (pl.Captures > 0) + { + sb.Append(", "); + sb.Append(pl.Captures.ToString("N0")); + sb.Append(pl.Captures == 1 ? " capture" : " captures"); + } + } + + Item item = new Trophy(sb.ToString(), rank); + + if (pl == leader) + item.ItemID = 4810; + + item.Name = $"{item.Name}, {teams[i].Name.ToLower()} team"; + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + int cash = pl.Score * 250; + + if (cash > 0) + { + item = new BankCheck(cash); + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + mob.SendMessage( + "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", + rank.ToString().ToLower(), cash); + } + else + { + mob.SendMessage("You have been awarded a {0} trophy for your participation in this tournament.", + rank.ToString().ToLower()); + } + } + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + Participant p = m_Context.Participants[i] as Participant; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; + + if (dp?.Mobile != null) + { + dp.Mobile.CloseGump(typeof(DDBoardGump)); + dp.Mobile.SendGump(new DDBoardGump(dp.Mobile, this)); + } + } + + if (i == winner.TeamID) + continue; + + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Eliminated = true; + } + + m_Context.Finish(m_Context.Participants[winner.TeamID] as Participant); + } + + public override void OnStop() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + DDTeamInfo teamInfo = Controller.TeamInfo[i]; + + if (teamInfo.Board != null) + teamInfo.Board.m_TeamInfo = null; + + teamInfo.Game = null; + } + + if (Controller.PointA != null) + Controller.PointA.Game = null; + + if (Controller.PointB != null) + Controller.PointB.Game = null; + + m_Capturable = false; + + if (m_CaptureTimer != null) + { + m_CaptureTimer.Stop(); + m_CaptureTimer = null; + } + + if (m_UncaptureTimer != null) + { + m_UncaptureTimer.Stop(); + m_UncaptureTimer = null; + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, -1); + + m_FinishTimer?.Stop(); + m_FinishTimer = null; + } + + public void Dominate(DDWayPoint point, Mobile from, DDTeamInfo team) + { + if (point == null || from == null || team == null || !m_Capturable) + return; + + bool wasDom = Controller.PointA != null && Controller.PointB != null && + Controller.PointA.TeamOwner == Controller.PointB.TeamOwner && Controller.PointA.TeamOwner != null; + + point.TeamOwner = team; + Alert("{0} has captured {1}!", team.Name, point.Name); + + bool isDom = Controller.PointA != null && Controller.PointB != null && + Controller.PointA.TeamOwner == Controller.PointB.TeamOwner && Controller.PointA.TeamOwner != null; + + if (wasDom && !isDom) + { + Alert("Domination averted!"); + + Controller.PointA?.SetNonCaptureHue(); + Controller.PointB?.SetNonCaptureHue(); + m_CaptureTimer?.Stop(); + m_CaptureTimer = null; + } + + if (!wasDom && isDom) + { + m_CapStage = 0; + m_CaptureTimer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromSeconds(1.0), CaptureTick); + m_CaptureTimer.Start(); + } + } + + private void CaptureTick() + { + DDTeamInfo team = null; + + if (Controller.PointA?.TeamOwner != null) + team = Controller.PointA.TeamOwner; + else if (Controller.PointB?.TeamOwner != null) + team = Controller.PointB.TeamOwner; + + if (team == null) + { + m_Capturable = true; + m_CaptureTimer?.Stop(); + m_CaptureTimer = null; + return; + } + + if (++m_CapStage < 10) + { + Alert("{0} is dominating... {1}", team.Name, 10 - m_CapStage); + + Controller.PointA?.SetCaptureHue(m_CapStage); + Controller.PointB?.SetCaptureHue(m_CapStage); + } + else + { + Alert("{0} has scored!", team.Name); + + team.Score += 100; + team.Captures += 1; + + m_Capturable = false; + m_CapStage = 0; + m_CaptureTimer.Stop(); + m_CaptureTimer = null; + + if (Controller.PointA != null) + { + Controller.PointA.TeamOwner = null; + Controller.PointA.SetUncapturableHue(); + } + + if (Controller.PointB != null) + { + Controller.PointB.TeamOwner = null; + Controller.PointB.SetUncapturableHue(); + } + + m_UncaptureTimer = Timer.DelayCall(TimeSpan.FromSeconds(30.0), UncaptureTick); + m_UncaptureTimer.Start(); + } + } + + private void UncaptureTick() + { + m_Capturable = true; + + if (m_CaptureTimer != null) + { + m_CaptureTimer.Stop(); + m_CaptureTimer = null; + } + + if (m_UncaptureTimer != null) + { + m_UncaptureTimer.Stop(); + m_UncaptureTimer = null; + } + + if (Controller.PointA != null) + { + Controller.PointA.TeamOwner = null; + Controller.PointA.SetNonCaptureHue(); + } + + if (Controller.PointB != null) + { + Controller.PointB.TeamOwner = null; + Controller.PointB.SetNonCaptureHue(); + } + } + } + + public class DDWayPoint : BaseAddon + { + public const int UncapturableHue = 0x497; + public const int NonCapturedHue = 0x38A; + private DDGame m_Game; + private DDTeamInfo m_TeamOwner; + + [Constructible] + public DDWayPoint() + { + ItemID = 0x519; + Visible = true; + Name = "SET MY NAME"; + + AddComponent(new DDStep(0x7A8), -1, -1, -5); + AddComponent(new DDStep(0x7A6), 0, -1, -5); + AddComponent(new DDStep(0x7AA), 1, -1, -5); + + AddComponent(new DDStep(0x7A5), 1, 0, -5); + + AddComponent(new DDStep(0x7A9), 1, 1, -5); + AddComponent(new DDStep(0x7A4), 0, 1, -5); + AddComponent(new DDStep(0x7AB), -1, 1, -5); + + AddComponent(new DDStep(0x7A7), -1, 0, -5); + + SetUncapturableHue(); + } + + public DDWayPoint(Serial serial) : base(serial) + { + } + + public override bool ShareHue => false; + + public DDGame Game + { + get => m_Game; + set + { + m_Game = value; + m_TeamOwner = null; + + if (m_Game != null) + SetNonCaptureHue(); + else + SetUncapturableHue(); + } + } + + public DDTeamInfo TeamOwner + { + get => m_TeamOwner; + set + { + m_TeamOwner = value; + + SetNonCaptureHue(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public void SetUncapturableHue() + { + for (int i = 0; i < Components.Count; i++) + Components[i].Hue = UncapturableHue; + Hue = UncapturableHue; + } + + public void SetNonCaptureHue() + { + for (int i = 0; i < Components.Count; i++) + Components[i].Hue = NonCapturedHue; + + if (m_TeamOwner != null) + Hue = m_TeamOwner.Color; + else + Hue = NonCapturedHue; + } + + public void SetCaptureHue(int stage) + { + if (m_TeamOwner == null) + return; + + Hue = m_TeamOwner.Color; + + for (int i = 0; i < Components.Count; i++) + if (i < stage) + Components[i].Hue = m_TeamOwner.Color; + else + Components[i].Hue = NonCapturedHue; + } + + public override bool OnMoveOver(Mobile from) + { + if (m_Game == null) + { + SetUncapturableHue(); + } + else if (from.Alive) + { + DDTeamInfo team = m_Game.GetTeamInfo(from); + + if (team != null && team != TeamOwner) + m_Game.Dominate(this, from, team); + } + + return true; + } + + public class DDStep : AddonComponent + { + public DDStep(int itemID) : base(itemID) + { + Visible = true; + } + + public DDStep(Serial serial) : base(serial) + { + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); //version + } + + public override bool OnMoveOver(Mobile m) + { + return Addon.OnMoveOver(m); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Games/EventGame.cs b/Scripts/Engines/ConPVP/Games/EventGame.cs index 1e1f7773d..5f49e80d0 100644 --- a/Scripts/Engines/ConPVP/Games/EventGame.cs +++ b/Scripts/Engines/ConPVP/Games/EventGame.cs @@ -1,77 +1,77 @@ +using Server.Gumps; using Server.Items; namespace Server.Engines.ConPVP { - public abstract class EventController : Item - { - public abstract EventGame Construct( DuelContext dc ); + public abstract class EventController : Item + { + public EventController() + : base(0x1B7A) + { + Visible = false; + Movable = false; + } - public abstract string Title { get; } + public EventController(Serial serial) + : base(serial) + { + } - public abstract string GetTeamName( int teamID ); + public abstract string Title{ get; } + public abstract EventGame Construct(DuelContext dc); - public EventController() - : base( 0x1B7A ) - { - Visible = false; - Movable = false; - } + public abstract string GetTeamName(int teamID); - public EventController( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } - int version = reader.ReadInt(); - } + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + from.SendGump(new PropertiesGump(from, this)); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - from.SendGump( new Gumps.PropertiesGump( from, this ) ); - } - } + public abstract class EventGame + { + protected DuelContext m_Context; - public abstract class EventGame - { - protected DuelContext m_Context; + public EventGame(DuelContext context) + { + m_Context = context; + } - public DuelContext Context => m_Context; + public DuelContext Context => m_Context; - public virtual bool FreeConsume => true; + public virtual bool FreeConsume => true; - public EventGame( DuelContext context ) - { - m_Context = context; - } + public virtual bool OnDeath(Mobile mob, Container corpse) + { + return true; + } - public virtual bool OnDeath( Mobile mob, Container corpse ) - { - return true; - } + public virtual bool CantDoAnything(Mobile mob) + { + return false; + } - public virtual bool CantDoAnything( Mobile mob ) - { - return false; - } + public virtual void OnStart() + { + } - public virtual void OnStart() - { - } - - public virtual void OnStop() - { - } - } -} + public virtual void OnStop() + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Games/KingOfTheHill.cs b/Scripts/Engines/ConPVP/Games/KingOfTheHill.cs index 2466769d5..ee171509e 100644 --- a/Scripts/Engines/ConPVP/Games/KingOfTheHill.cs +++ b/Scripts/Engines/ConPVP/Games/KingOfTheHill.cs @@ -1,1239 +1,1259 @@ - using System; using System.Collections; using System.Text; +using Server.Gumps; using Server.Items; using Server.Mobiles; using Server.Network; -using Server.Gumps; namespace Server.Engines.ConPVP { - public class HillOfTheKing : Item + public class HillOfTheKing : Item + { + private KHGame m_Game; + private KingTimer m_KingTimer; + + [Constructible] + public HillOfTheKing() + : base(0x520) { - private KHGame m_Game; - private KingTimer m_KingTimer; + ScoreInterval = 10; + m_Game = null; + King = null; + Movable = false; - [Constructible] - public HillOfTheKing() - : base(0x520) + Name = "the hill"; + } + + public HillOfTheKing(Serial s) + : base(s) + { + } + + public Mobile King{ get; private set; } + + public KHGame Game + { + get => m_Game; + set + { + if (m_Game != value) { - ScoreInterval = 10; - m_Game = null; - King = null; - Movable = false; + m_KingTimer?.Stop(); + m_Game = value; + King = null; + } + } + } - Name = "the hill"; + [CommandProperty(AccessLevel.GameMaster)] + public int ScoreInterval{ get; set; } + + public int CapturesSoFar + { + get + { + if (m_KingTimer != null) + return m_KingTimer.Captures; + return 0; + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + ScoreInterval = reader.ReadEncodedInt(); + break; + } + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.WriteEncodedInt(ScoreInterval); + } + + private bool CanBeKing(Mobile m) + { + // Game running? + if (m_Game == null) + return false; + + // Mobile exists and is alive and is a player? + if (m == null || m.Deleted || !m.Alive || !m.Player) + return false; + + // Not current king (or they are the current king) + if (King != null && King != m) + return false; + + // They are on a team + if (m_Game.GetTeamInfo(m) == null) + return false; + + return true; + } + + public override bool OnMoveOver(Mobile m) + { + if (m_Game == null || m == null || !m.Alive) + return base.OnMoveOver(m); + + if (CanBeKing(m)) + { + if (base.OnMoveOver(m)) + { + ReKingify(m); + return true; + } + } + else + { + // Decrease their stam a little so they don't keep pushing someone out of the way + if (m.AccessLevel == AccessLevel.Player && m.Stam >= m.StamMax) + m.Stam -= 5; + } + + return false; + } + + public override bool OnMoveOff(Mobile m) + { + if (base.OnMoveOff(m)) + { + if (King == m) + DeKingify(); + + return true; + } + + return false; + } + + public virtual void OnKingDied(Mobile king, KHTeamInfo kingTeam, Mobile killer, KHTeamInfo killerTeam) + { + if (m_Game != null && CapturesSoFar > 0 && killer != null && king != null && kingTeam != null && + killerTeam != null) + { + string kingName = king.Name; + if (kingName == null) + kingName = ""; + string killerName = killer.Name; + if (killerName == null) + killerName = ""; + + m_Game.Alert("{0} ({1}) was dethroned by {2} ({3})!", kingName, kingTeam.Name, killerName, killerTeam.Name); + } + + DeKingify(); + } + + private void DeKingify() + { + PublicOverheadMessage(MessageType.Regular, 0x0481, false, "Free!"); + + m_KingTimer?.Stop(); + + King = null; + } + + private void ReKingify(Mobile m) + { + KHTeamInfo ti = null; + if (m_Game == null || m == null) + return; + + ti = m_Game.GetTeamInfo(m); + if (ti == null) + return; + + King = m; + + if (m_KingTimer == null) + m_KingTimer = new KingTimer(this); + m_KingTimer.Stop(); + m_KingTimer.StartHillTicker(); + + if (King.Name != null) + PublicOverheadMessage(MessageType.Regular, 0x0481, false, $"Taken by {King.Name}!"); + } + + private class KingTimer : Timer + { + private int m_Counter; + private HillOfTheKing m_Hill; + + public KingTimer(HillOfTheKing hill) + : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Hill = hill; + Captures = 0; + m_Counter = 0; + + Priority = TimerPriority.FiftyMS; + } + + public int Captures{ get; private set; } + + public void StartHillTicker() + { + Captures = 0; + m_Counter = 0; + + Start(); + } + + protected override void OnTick() + { + KHTeamInfo ti = null; + KHPlayerInfo pi = null; + + if (m_Hill == null || m_Hill.Deleted || m_Hill.Game == null) + { + Stop(); + return; } - public HillOfTheKing(Serial s) - : base(s) + if (m_Hill.King == null || m_Hill.King.Deleted || !m_Hill.King.Alive) { + m_Hill.DeKingify(); + Stop(); + return; } - public override void Deserialize(GenericReader reader) + ti = m_Hill.Game.GetTeamInfo(m_Hill.King); + if (ti != null) + pi = ti[m_Hill.King]; + + if (ti == null || pi == null) { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 0: - { - ScoreInterval = reader.ReadEncodedInt(); - break; - } - } + // error, bail + m_Hill.DeKingify(); + Stop(); + return; } - public override void Serialize(GenericWriter writer) + m_Counter++; + + m_Hill.King.RevealingAction(); + + if (m_Counter >= m_Hill.ScoreInterval) { - base.Serialize(writer); + string hill = m_Hill.Name; + string king = m_Hill.King.Name; + if (king == null) + king = ""; - writer.Write((int)0); // version + if (hill == null || hill == "") + hill = "the hill"; - writer.WriteEncodedInt(ScoreInterval); + m_Hill.Game.Alert("{0} ({1}) is king of {2}!", king, ti.Name, hill); + + m_Hill.PublicOverheadMessage(MessageType.Regular, 0x0481, false, "Capture!"); + + pi.Captures++; + Captures++; + + pi.Score += m_Counter; + + m_Counter = 0; + } + else + { + m_Hill.PublicOverheadMessage(MessageType.Regular, 0x0481, false, + (m_Hill.ScoreInterval - m_Counter).ToString()); + } + } + } + } + + public class KHBoard : Item + { + private KHController m_Controller; + public KHGame m_Game; + + [Constructible] + public KHBoard() + : base(7774) + { + Name = "King of the Hill Scoreboard"; + Movable = false; + } + + public KHBoard(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHController Controller + { + get => m_Controller; + set + { + if (m_Controller != value) + { + m_Controller?.RemoveBoard(this); + m_Controller = value; + m_Controller?.AddBoard(this); + } + } + } + + public override void OnDoubleClick(Mobile from) + { + if (m_Game != null) + { + from.CloseGump(typeof(KHBoardGump)); + from.SendGump(new KHBoardGump(from, m_Game)); + } + else + { + from.SendMessage("There is no King of the Hill game in progress."); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.Write(m_Controller); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Controller = reader.ReadItem() as KHController; + break; + } + } + } + } + + public sealed class KHBoardGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int BlackColor32 = 0x000000; + + private KHGame m_Game; + + public KHBoardGump(Mobile mob, KHGame game) + : base(60, 60) + { + m_Game = game; + + KHTeamInfo ourTeam = game.GetTeamInfo(mob); + + ArrayList entries = new ArrayList(); + + for (int i = 0; i < game.Context.Participants.Count; ++i) + { + KHTeamInfo teamInfo = game.Controller.TeamInfo[i % game.Controller.TeamInfo.Length]; + + if (teamInfo == null) + continue; + + entries.Add(teamInfo); + } + + entries.Sort(); + /* + delegate( IRankedCTF a, IRankedCTF b ) + { + return b.Score - a.Score; + } );*/ + + int height = 73 + entries.Count * 75 + 28; + + Closable = false; + + AddPage(0); + + AddBackground(1, 1, 398, height, 3600); + + AddImageTiled(16, 15, 369, height - 29, 3604); + + for (int i = 0; i < entries.Count; i += 1) + AddImageTiled(22, 58 + i * 75, 357, 70, 0x2430); + + AddAlphaRegion(16, 15, 369, height - 29); + + AddImage(215, -45, 0xEE40); + //AddImage( 330, 141, 0x8BA ); + + AddBorderedText(22, 22, 294, 20, Center("King of the Hill Scoreboard"), LabelColor32, BlackColor32); + + AddImageTiled(32, 50, 264, 1, 9107); + AddImageTiled(42, 52, 264, 1, 9157); + + for (int i = 0; i < entries.Count; ++i) + { + KHTeamInfo teamInfo = entries[i] as KHTeamInfo; + + AddImage(30, 70 + i * 75, 10152); + AddImage(30, 85 + i * 75, 10151); + AddImage(30, 100 + i * 75, 10151); + AddImage(30, 106 + i * 75, 10154); + + AddImage(24, 60 + i * 75, teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1); + + int nameColor = LabelColor32; + int borderColor = BlackColor32; + + switch (teamInfo.Color) + { + case 0x47E: + nameColor = 0xFFFFFF; + break; + + case 0x4F2: + nameColor = 0x3399FF; + break; + + case 0x4F7: + nameColor = 0x33FF33; + break; + + case 0x4FC: + nameColor = 0xFF00FF; + break; + + case 0x021: + nameColor = 0xFF3333; + break; + + case 0x01A: + nameColor = 0xFF66FF; + break; + + case 0x455: + nameColor = 0x333333; + borderColor = 0xFFFFFF; + break; } - public Mobile King { get; private set; } + AddBorderedText(60, 65 + i * 75, 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name}", nameColor, + borderColor); - public KHGame Game + AddBorderedText(50 + 10, 85 + i * 75, 100, 20, "Score:", 0xFFC000, BlackColor32); + AddBorderedText(50 + 15, 105 + i * 75, 100, 20, teamInfo.Score.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(110 + 10, 85 + i * 75, 100, 20, "Kills:", 0xFFC000, BlackColor32); + AddBorderedText(110 + 15, 105 + i * 75, 100, 20, teamInfo.Kills.ToString("N0"), 0xFFC000, BlackColor32); + + AddBorderedText(160 + 10, 85 + i * 75, 100, 20, "Captures:", 0xFFC000, BlackColor32); + AddBorderedText(160 + 15, 105 + i * 75, 100, 20, teamInfo.Captures.ToString("N0"), 0xFFC000, BlackColor32); + + string leader = null; + if (teamInfo.Leader != null) + leader = teamInfo.Leader.Name; + if (leader == null) + leader = "(none)"; + + AddBorderedText(235 + 10, 85 + i * 75, 250, 20, "Leader:", 0xFFC000, BlackColor32); + AddBorderedText(235 + 15, 105 + i * 75, 250, 20, leader, 0xFFC000, BlackColor32); + } + + AddButton(314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + } + + public sealed class KHPlayerInfo : IRankedCTF, IComparable + { + private int m_Captures; + + private int m_Kills; + private int m_Score; + private KHTeamInfo m_TeamInfo; + + public KHPlayerInfo(KHTeamInfo teamInfo, Mobile player) + { + m_TeamInfo = teamInfo; + Player = player; + } + + public Mobile Player{ get; } + + public int CompareTo(object obj) + { + KHPlayerInfo pi = (KHPlayerInfo)obj; + int res = pi.Score.CompareTo(Score); + if (res == 0) + { + res = pi.Captures.CompareTo(Captures); + + if (res == 0) + res = pi.Kills.CompareTo(Kills); + } + + return res; + } + + public string Name + { + get + { + if (Player?.Name == null) + return ""; + return Player.Name; + } + } + + public int Kills + { + get => m_Kills; + set + { + m_TeamInfo.Kills += value - m_Kills; + m_Kills = value; + } + } + + public int Captures + { + get => m_Captures; + set + { + m_TeamInfo.Captures += value - m_Captures; + m_Captures = value; + } + } + + public int Score + { + get => m_Score; + set + { + m_TeamInfo.Score += value - m_Score; + m_Score = value; + + if (m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score) + m_TeamInfo.Leader = this; + } + } + } + + [PropertyObject] + public sealed class KHTeamInfo : IRankedCTF, IComparable + { + public KHTeamInfo(int teamID) + { + TeamID = teamID; + Players = new Hashtable(); + } + + public KHTeamInfo(int teamID, GenericReader ip) + { + TeamID = teamID; + Players = new Hashtable(); + + int version = ip.ReadEncodedInt(); + + switch (version) + { + case 0: { - get => m_Game; - set - { - if (m_Game != value) - { - m_KingTimer?.Stop(); - m_Game = value; - King = null; - } - } + TeamName = ip.ReadString(); + Color = ip.ReadEncodedInt(); + break; } + } + } - [CommandProperty(AccessLevel.GameMaster)] - public int ScoreInterval { get; set; } + public KHGame Game{ get; set; } - public int CapturesSoFar + public int TeamID{ get; } + + public KHPlayerInfo Leader{ get; set; } + + public Hashtable Players{ get; } + + public KHPlayerInfo this[Mobile mob] + { + get + { + if (mob == null) + return null; + + if (!(Players[mob] is KHPlayerInfo val)) + Players[mob] = val = new KHPlayerInfo(this, mob); + + return val; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Color{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string TeamName{ get; set; } + + public int CompareTo(object obj) + { + KHTeamInfo ti = (KHTeamInfo)obj; + int res = ti.Score.CompareTo(Score); + if (res == 0) + { + res = ti.Captures.CompareTo(Captures); + + if (res == 0) + res = ti.Kills.CompareTo(Kills); + } + + return res; + } + + public string Name + { + get + { + if (TeamName == null) + return "(null) Team"; + return $"{TeamName} Team"; + } + } + + public int Kills{ get; set; } + + public int Captures{ get; set; } + + public int Score{ get; set; } + + public void Reset() + { + Kills = 0; + Captures = 0; + Score = 0; + + Leader = null; + + Players.Clear(); + } + + public void Serialize(GenericWriter op) + { + op.WriteEncodedInt(0); // version + + op.Write(TeamName); + op.WriteEncodedInt(Color); + } + + public override string ToString() + { + if (TeamName != null) + return $"({Name}) ..."; + return "..."; + } + } + + public sealed class KHController : EventController + { + private int m_ScoreInterval; + + [Constructible] + public KHController() + { + Visible = false; + Movable = false; + + Name = "King of the Hill Controller"; + + Duration = TimeSpan.FromMinutes(30.0); + Boards = new ArrayList(); + Hills = new HillOfTheKing[4]; + TeamInfo = new KHTeamInfo[8]; + + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new KHTeamInfo(i); + } + + public KHController(Serial serial) + : base(serial) + { + } + + public KHTeamInfo[] TeamInfo{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team1_W + { + get => TeamInfo[0]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team2_E + { + get => TeamInfo[1]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team3_N + { + get => TeamInfo[2]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team4_S + { + get => TeamInfo[3]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team5_NW + { + get => TeamInfo[4]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team6_SE + { + get => TeamInfo[5]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team7_SW + { + get => TeamInfo[6]; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public KHTeamInfo Team8_NE + { + get => TeamInfo[7]; + set { } + } + + public HillOfTheKing[] Hills{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public HillOfTheKing Hill1 + { + get => Hills[0]; + set => Hills[0] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public HillOfTheKing Hill2 + { + get => Hills[1]; + set => Hills[1] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public HillOfTheKing Hill3 + { + get => Hills[2]; + set => Hills[2] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public HillOfTheKing Hill4 + { + get => Hills[3]; + set => Hills[3] = value; + } + + public ArrayList Boards{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan Duration{ get; set; } + + public override string Title => "King of the Hill"; + + public override string GetTeamName(int teamID) + { + return TeamInfo[teamID % TeamInfo.Length].Name; + } + + public override EventGame Construct(DuelContext context) + { + return new KHGame(this, context); + } + + public void RemoveBoard(KHBoard b) + { + if (b != null) + { + Boards.Remove(b); + b.m_Game = null; + } + } + + public void AddBoard(KHBoard b) + { + if (b != null) + Boards.Add(b); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.WriteEncodedInt(m_ScoreInterval); + writer.Write(Duration); + + writer.WriteItemList(Boards, true); + + writer.WriteEncodedInt(Hills.Length); + for (int i = 0; i < Hills.Length; ++i) + writer.Write(Hills[i]); + + writer.WriteEncodedInt(TeamInfo.Length); + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i].Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: { - get - { - if (m_KingTimer != null) - return m_KingTimer.Captures; - return 0; - } + m_ScoreInterval = reader.ReadEncodedInt(); + + Duration = reader.ReadTimeSpan(); + + Boards = reader.ReadItemList(); + + Hills = new HillOfTheKing[reader.ReadEncodedInt()]; + for (int i = 0; i < Hills.Length; ++i) + Hills[i] = reader.ReadItem() as HillOfTheKing; + + TeamInfo = new KHTeamInfo[reader.ReadEncodedInt()]; + for (int i = 0; i < TeamInfo.Length; ++i) + TeamInfo[i] = new KHTeamInfo(i, reader); + + break; } + } + } + } - private bool CanBeKing(Mobile m) - { - // Game running? - if (m_Game == null) - return false; + public sealed class KHGame : EventGame + { + private Timer m_FinishTimer; - // Mobile exists and is alive and is a player? - if (m == null || m.Deleted || !m.Alive || !m.Player) - return false; + public KHGame(KHController controller, DuelContext context) + : base(context) + { + Controller = controller; + } - // Not current king (or they are the current king) - if (King != null && King != m) - return false; + public KHController Controller{ get; } - // They are on a team - if (m_Game.GetTeamInfo(m) == null) - return false; + public Map Facet + { + get + { + if (m_Context?.Arena != null) + return m_Context.Arena.Facet; + return Controller.Map; + } + } + + public override bool CantDoAnything(Mobile mob) + { + if (mob != null && GetTeamInfo(mob) != null && Controller != null) + for (int i = 0; i < Controller.Hills.Length; i++) + if (Controller.Hills[i] != null && Controller.Hills[i].King == mob) return true; - } - public override bool OnMoveOver(Mobile m) - { - if (m_Game == null || m == null || !m.Alive) - return base.OnMoveOver(m); - - if (CanBeKing(m)) - { - if (base.OnMoveOver(m)) - { - ReKingify(m); - return true; - } - } - else - { - // Decrease their stam a little so they don't keep pushing someone out of the way - if (m.AccessLevel == AccessLevel.Player && m.Stam >= m.StamMax) - m.Stam -= 5; - } - - return false; - } - - public override bool OnMoveOff(Mobile m) - { - if (base.OnMoveOff(m)) - { - if (King == m) - DeKingify(); - - return true; - } - - return false; - } - - public virtual void OnKingDied(Mobile king, KHTeamInfo kingTeam, Mobile killer, KHTeamInfo killerTeam) - { - if (m_Game != null && CapturesSoFar > 0 && killer != null && king != null && kingTeam != null && killerTeam != null) - { - string kingName = king.Name; - if (kingName == null) - kingName = ""; - string killerName = killer.Name; - if (killerName == null) - killerName = ""; - - m_Game.Alert("{0} ({1}) was dethroned by {2} ({3})!", kingName, kingTeam.Name, killerName, killerTeam.Name); - } - - DeKingify(); - } - - private void DeKingify() - { - PublicOverheadMessage(MessageType.Regular, 0x0481, false, "Free!"); - - m_KingTimer?.Stop(); - - King = null; - } - - private void ReKingify(Mobile m) - { - KHTeamInfo ti = null; - if (m_Game == null || m == null) - return; - - ti = m_Game.GetTeamInfo(m); - if (ti == null) - return; - - King = m; - - if (m_KingTimer == null) - m_KingTimer = new KingTimer(this); - m_KingTimer.Stop(); - m_KingTimer.StartHillTicker(); - - if (King.Name != null) - PublicOverheadMessage(MessageType.Regular, 0x0481, false, $"Taken by {King.Name}!"); - } - - private class KingTimer : Timer - { - private HillOfTheKing m_Hill; - private int m_Counter; - - public int Captures { get; private set; } - - public KingTimer(HillOfTheKing hill) - : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) - { - m_Hill = hill; - Captures = 0; - m_Counter = 0; - - Priority = TimerPriority.FiftyMS; - } - - public void StartHillTicker() - { - Captures = 0; - m_Counter = 0; - - Start(); - } - - protected override void OnTick() - { - KHTeamInfo ti = null; - KHPlayerInfo pi = null; - - if (m_Hill == null || m_Hill.Deleted || m_Hill.Game == null) - { - Stop(); - return; - } - - if (m_Hill.King == null || m_Hill.King.Deleted || !m_Hill.King.Alive) - { - m_Hill.DeKingify(); - Stop(); - return; - } - - ti = m_Hill.Game.GetTeamInfo(m_Hill.King); - if (ti != null) - pi = ti[m_Hill.King]; - - if (ti == null || pi == null) - { - // error, bail - m_Hill.DeKingify(); - Stop(); - return; - } - - m_Counter++; - - m_Hill.King.RevealingAction(); - - if (m_Counter >= m_Hill.ScoreInterval) - { - string hill = m_Hill.Name; - string king = m_Hill.King.Name; - if (king == null) - king = ""; - - if (hill == null || hill == "") - hill = "the hill"; - - m_Hill.Game.Alert("{0} ({1}) is king of {2}!", king, ti.Name, hill); - - m_Hill.PublicOverheadMessage(MessageType.Regular, 0x0481, false, "Capture!"); - - pi.Captures++; - Captures++; - - pi.Score += m_Counter; - - m_Counter = 0; - } - else - { - m_Hill.PublicOverheadMessage(MessageType.Regular, 0x0481, false, (m_Hill.ScoreInterval - m_Counter).ToString()); - } - } - } + return false; } - public class KHBoard : Item + public void Alert(string text) { - public KHGame m_Game; - private KHController m_Controller; + m_Context.m_Tournament?.Alert(text); - [Constructible] - public KHBoard() - : base(7774) - { - Name = "King of the Hill Scoreboard"; - Movable = false; - } + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + Participant p = m_Context.Participants[i] as Participant; - [CommandProperty(AccessLevel.GameMaster)] - public KHController Controller - { - get => m_Controller; - set - { - if (m_Controller != value) - { - m_Controller?.RemoveBoard(this); - m_Controller = value; - m_Controller?.AddBoard(this); - } - } - } - - public override void OnDoubleClick(Mobile from) - { - if (m_Game != null) - { - from.CloseGump(typeof(KHBoardGump)); - from.SendGump(new KHBoardGump(from, m_Game)); - } - else - { - from.SendMessage("There is no King of the Hill game in progress."); - } - } - - public KHBoard(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); - - writer.Write(m_Controller); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 0: - { - m_Controller = reader.ReadItem() as KHController; - break; - } - } - } + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Mobile.SendMessage(0x35, text); + } } - public sealed class KHBoardGump : Gump + public void Alert(string format, params object[] args) { - public string Center(string text) - { - return $"
{text}
"; - } - - public string Color(string text, int color) - { - return $"{text}"; - } - - private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) - { - AddColoredText(x - 1, y - 1, width, height, text, borderColor); - AddColoredText(x - 1, y + 1, width, height, text, borderColor); - AddColoredText(x + 1, y - 1, width, height, text, borderColor); - AddColoredText(x + 1, y + 1, width, height, text, borderColor); - AddColoredText(x, y, width, height, text, color); - } - - private void AddColoredText(int x, int y, int width, int height, string text, int color) - { - if (color == 0) - AddHtml(x, y, width, height, text, false, false); - else - AddHtml(x, y, width, height, Color(text, color), false, false); - } - - private const int LabelColor32 = 0xFFFFFF; - private const int BlackColor32 = 0x000000; - - private KHGame m_Game; - - public KHBoardGump(Mobile mob, KHGame game) - : base(60, 60) - { - m_Game = game; - - KHTeamInfo ourTeam = game.GetTeamInfo(mob); - - ArrayList entries = new ArrayList(); - - for (int i = 0; i < game.Context.Participants.Count; ++i) - { - KHTeamInfo teamInfo = game.Controller.TeamInfo[i % game.Controller.TeamInfo.Length]; - - if (teamInfo == null) - continue; - - entries.Add(teamInfo); - } - - entries.Sort(); - /* - delegate( IRankedCTF a, IRankedCTF b ) - { - return b.Score - a.Score; - } );*/ - - int height = 73 + (entries.Count * 75) + 28; - - Closable = false; - - AddPage(0); - - AddBackground(1, 1, 398, height, 3600); - - AddImageTiled(16, 15, 369, height - 29, 3604); - - for (int i = 0; i < entries.Count; i += 1) - AddImageTiled(22, 58 + (i * 75), 357, 70, 0x2430); - - AddAlphaRegion(16, 15, 369, height - 29); - - AddImage(215, -45, 0xEE40); - //AddImage( 330, 141, 0x8BA ); - - AddBorderedText(22, 22, 294, 20, Center("King of the Hill Scoreboard"), LabelColor32, BlackColor32); - - AddImageTiled(32, 50, 264, 1, 9107); - AddImageTiled(42, 52, 264, 1, 9157); - - for (int i = 0; i < entries.Count; ++i) - { - KHTeamInfo teamInfo = entries[i] as KHTeamInfo; - - AddImage(30, 70 + (i * 75), 10152); - AddImage(30, 85 + (i * 75), 10151); - AddImage(30, 100 + (i * 75), 10151); - AddImage(30, 106 + (i * 75), 10154); - - AddImage(24, 60 + (i * 75), teamInfo == ourTeam ? 9730 : 9727, teamInfo.Color - 1); - - int nameColor = LabelColor32; - int borderColor = BlackColor32; - - switch (teamInfo.Color) - { - case 0x47E: - nameColor = 0xFFFFFF; - break; - - case 0x4F2: - nameColor = 0x3399FF; - break; - - case 0x4F7: - nameColor = 0x33FF33; - break; - - case 0x4FC: - nameColor = 0xFF00FF; - break; - - case 0x021: - nameColor = 0xFF3333; - break; - - case 0x01A: - nameColor = 0xFF66FF; - break; - - case 0x455: - nameColor = 0x333333; - borderColor = 0xFFFFFF; - break; - } - - AddBorderedText(60, 65 + (i * 75), 250, 20, $"{LadderGump.Rank(1 + i)}: {teamInfo.Name}", nameColor, borderColor); - - AddBorderedText(50 + 10, 85 + (i * 75), 100, 20, "Score:", 0xFFC000, BlackColor32); - AddBorderedText(50 + 15, 105 + (i * 75), 100, 20, teamInfo.Score.ToString("N0"), 0xFFC000, BlackColor32); - - AddBorderedText(110 + 10, 85 + (i * 75), 100, 20, "Kills:", 0xFFC000, BlackColor32); - AddBorderedText(110 + 15, 105 + (i * 75), 100, 20, teamInfo.Kills.ToString("N0"), 0xFFC000, BlackColor32); - - AddBorderedText(160 + 10, 85 + (i * 75), 100, 20, "Captures:", 0xFFC000, BlackColor32); - AddBorderedText(160 + 15, 105 + (i * 75), 100, 20, teamInfo.Captures.ToString("N0"), 0xFFC000, BlackColor32); - - string leader = null; - if (teamInfo.Leader != null) - leader = teamInfo.Leader.Name; - if (leader == null) - leader = "(none)"; - - AddBorderedText(235 + 10, 85 + (i * 75), 250, 20, "Leader:", 0xFFC000, BlackColor32); - AddBorderedText(235 + 15, 105 + (i * 75), 250, 20, leader, 0xFFC000, BlackColor32); - } - - AddButton(314, height - 42, 247, 248, 1, GumpButtonType.Reply, 0); - } + Alert(string.Format(format, args)); } - public sealed class KHPlayerInfo : IRankedCTF, IComparable + public KHTeamInfo GetTeamInfo(Mobile mob) { - private KHTeamInfo m_TeamInfo; + int teamID = GetTeamID(mob); - private int m_Kills; - private int m_Captures; - private int m_Score; + if (teamID >= 0) + return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; - public KHPlayerInfo(KHTeamInfo teamInfo, Mobile player) - { - m_TeamInfo = teamInfo; - Player = player; - } - - public Mobile Player { get; } - - public int CompareTo(object obj) - { - KHPlayerInfo pi = (KHPlayerInfo)obj; - int res = pi.Score.CompareTo(Score); - if (res == 0) - { - res = pi.Captures.CompareTo(Captures); - - if (res == 0) - res = pi.Kills.CompareTo(Kills); - } - return res; - } - - public string Name - { - get - { - if (Player?.Name == null) - return ""; - return Player.Name; - } - } - - public int Kills - { - get => m_Kills; - set - { - m_TeamInfo.Kills += (value - m_Kills); - m_Kills = value; - } - } - - public int Captures - { - get => m_Captures; - set - { - m_TeamInfo.Captures += (value - m_Captures); - m_Captures = value; - } - } - - public int Score - { - get => m_Score; - set - { - m_TeamInfo.Score += (value - m_Score); - m_Score = value; - - if (m_TeamInfo.Leader == null || m_Score > m_TeamInfo.Leader.Score) - m_TeamInfo.Leader = this; - } - } + return null; } - [PropertyObject] - public sealed class KHTeamInfo : IRankedCTF, IComparable + public int GetTeamID(Mobile mob) { - public int CompareTo(object obj) - { - KHTeamInfo ti = (KHTeamInfo)obj; - int res = ti.Score.CompareTo(Score); - if (res == 0) - { - res = ti.Captures.CompareTo(Captures); + if (!(mob is PlayerMobile pm)) + return mob is BaseCreature creature ? creature.Team - 1 : -1; - if (res == 0) - res = ti.Kills.CompareTo(Kills); - } - return res; - } + if (pm.DuelContext == null || pm.DuelContext != m_Context) + return -1; - public string Name - { - get - { - if (TeamName == null) - return "(null) Team"; - return $"{TeamName} Team"; - } - } + if (pm.DuelPlayer == null || pm.DuelPlayer.Eliminated) + return -1; - public KHGame Game { get; set; } - - public int TeamID { get; } - - public int Kills { get; set; } - - public int Captures { get; set; } - - public int Score { get; set; } - - public KHPlayerInfo Leader { get; set; } - - public Hashtable Players { get; } - - public KHPlayerInfo this[Mobile mob] - { - get - { - if (mob == null) - return null; - - if (!(Players[mob] is KHPlayerInfo val)) - Players[mob] = val = new KHPlayerInfo(this, mob); - - return val; - } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int Color { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public string TeamName { get; set; } - - public KHTeamInfo(int teamID) - { - TeamID = teamID; - Players = new Hashtable(); - } - - public void Reset() - { - Kills = 0; - Captures = 0; - Score = 0; - - Leader = null; - - Players.Clear(); - } - - public KHTeamInfo(int teamID, GenericReader ip) - { - TeamID = teamID; - Players = new Hashtable(); - - int version = ip.ReadEncodedInt(); - - switch (version) - { - case 0: - { - TeamName = ip.ReadString(); - Color = ip.ReadEncodedInt(); - break; - } - } - } - - public void Serialize(GenericWriter op) - { - op.WriteEncodedInt(0); // version - - op.Write(TeamName); - op.WriteEncodedInt(Color); - } - - public override string ToString() - { - if (TeamName != null) - return $"({Name}) ..."; - return "..."; - } + return pm.DuelContext.Participants.IndexOf(pm.DuelPlayer.Participant); } - public sealed class KHController : EventController + public int GetColor(Mobile mob) { - private int m_ScoreInterval; - - public KHTeamInfo[] TeamInfo { get; private set; } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team1_W { get => TeamInfo[0]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team2_E { get => TeamInfo[1]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team3_N { get => TeamInfo[2]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team4_S { get => TeamInfo[3]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team5_NW { get => TeamInfo[4]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team6_SE { get => TeamInfo[5]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team7_SW { get => TeamInfo[6]; - set { } } - - [CommandProperty(AccessLevel.GameMaster)] - public KHTeamInfo Team8_NE { get => TeamInfo[7]; - set { } } - - public HillOfTheKing[] Hills { get; private set; } - - [CommandProperty(AccessLevel.GameMaster)] - public HillOfTheKing Hill1 { get => Hills[0]; - set => Hills[0] = value; - } - - [CommandProperty(AccessLevel.GameMaster)] - public HillOfTheKing Hill2 { get => Hills[1]; - set => Hills[1] = value; - } - - [CommandProperty(AccessLevel.GameMaster)] - public HillOfTheKing Hill3 { get => Hills[2]; - set => Hills[2] = value; - } - - [CommandProperty(AccessLevel.GameMaster)] - public HillOfTheKing Hill4 { get => Hills[3]; - set => Hills[3] = value; - } - - public ArrayList Boards { get; private set; } - - [CommandProperty(AccessLevel.GameMaster)] - public TimeSpan Duration { get; set; } - - public override string Title => "King of the Hill"; - - public override string GetTeamName(int teamID) - { - return TeamInfo[teamID % TeamInfo.Length].Name; - } - - public override EventGame Construct(DuelContext context) - { - return new KHGame(this, context); - } - - public void RemoveBoard(KHBoard b) - { - if (b != null) - { - Boards.Remove(b); - b.m_Game = null; - } - } - - public void AddBoard(KHBoard b) - { - if (b != null) - Boards.Add(b); - } - - [Constructible] - public KHController() - { - Visible = false; - Movable = false; - - Name = "King of the Hill Controller"; - - Duration = TimeSpan.FromMinutes(30.0); - Boards = new ArrayList(); - Hills = new HillOfTheKing[4]; - TeamInfo = new KHTeamInfo[8]; - - for (int i = 0; i < TeamInfo.Length; ++i) - TeamInfo[i] = new KHTeamInfo(i); - } - - public KHController(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); - - writer.WriteEncodedInt(m_ScoreInterval); - writer.Write(Duration); - - writer.WriteItemList(Boards, true); - - writer.WriteEncodedInt(Hills.Length); - for (int i = 0; i < Hills.Length; ++i) - writer.Write(Hills[i]); - - writer.WriteEncodedInt(TeamInfo.Length); - for (int i = 0; i < TeamInfo.Length; ++i) - TeamInfo[i].Serialize(writer); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 0: - { - m_ScoreInterval = reader.ReadEncodedInt(); - - Duration = reader.ReadTimeSpan(); - - Boards = reader.ReadItemList(); - - Hills = new HillOfTheKing[reader.ReadEncodedInt()]; - for (int i = 0; i < Hills.Length; ++i) - Hills[i] = reader.ReadItem() as HillOfTheKing; - - TeamInfo = new KHTeamInfo[reader.ReadEncodedInt()]; - for (int i = 0; i < TeamInfo.Length; ++i) - TeamInfo[i] = new KHTeamInfo(i, reader); - - break; - } - } - } + return GetTeamInfo(mob)?.Color ?? -1; } - public sealed class KHGame : EventGame + private void ApplyHues(Participant p, int hueOverride) { - public KHController Controller { get; } - - public override bool CantDoAnything(Mobile mob) - { - if (mob != null && GetTeamInfo(mob) != null && Controller != null) - { - for (int i = 0; i < Controller.Hills.Length; i++) - { - if (Controller.Hills[i] != null && Controller.Hills[i].King == mob) - return true; - } - } - - return false; - } - - public void Alert(string text) - { - m_Context.m_Tournament?.Alert(text); - - for (int i = 0; i < m_Context.Participants.Count; ++i) - { - Participant p = m_Context.Participants[i] as Participant; - - for (int j = 0; j < p.Players.Length; ++j) - { - if (p.Players[j] != null) - p.Players[j].Mobile.SendMessage(0x35, text); - } - } - } - - public void Alert(string format, params object[] args) - { - Alert(string.Format(format, args)); - } - - public KHGame(KHController controller, DuelContext context) - : base(context) - { - Controller = controller; - } - - public Map Facet - { - get - { - if (m_Context?.Arena != null) - return m_Context.Arena.Facet; - - return Controller.Map; - } - } - - public KHTeamInfo GetTeamInfo(Mobile mob) - { - int teamID = GetTeamID(mob); - - if (teamID >= 0) - return Controller.TeamInfo[teamID % Controller.TeamInfo.Length]; - - return null; - } - - public int GetTeamID(Mobile mob) - { - if (!(mob is PlayerMobile pm)) - return mob is BaseCreature creature ? creature.Team - 1 : -1; - - if (pm.DuelContext == null || pm.DuelContext != m_Context) - return -1; - - if (pm.DuelPlayer == null || pm.DuelPlayer.Eliminated) - return -1; - - return pm.DuelContext.Participants.IndexOf(pm.DuelPlayer.Participant); - } - - public int GetColor(Mobile mob) - { - return GetTeamInfo(mob)?.Color ?? -1; - } - - private void ApplyHues(Participant p, int hueOverride) - { - for (int i = 0; i < p.Players.Length; ++i) - { - if (p.Players[i] != null) - p.Players[i].Mobile.SolidHueOverride = hueOverride; - } - } - - public void DelayBounce(TimeSpan ts, Mobile mob, Container corpse) - { - Timer.DelayCall(ts, new TimerStateCallback(DelayBounce_Callback), new object[] { mob, corpse }); - } - - private void DelayBounce_Callback(object state) - { - object[] states = (object[])state; - Mobile mob = (Mobile)states[0]; - Container corpse = (Container)states[1]; - - DuelPlayer dp = null; - - if (mob is PlayerMobile mobile) - dp = mobile.DuelPlayer; - - m_Context.RemoveAggressions(mob); - - if (dp != null && !dp.Eliminated) - mob.MoveToWorld(m_Context.Arena.GetBaseStartPoint(GetTeamID(mob)), Facet); - else - m_Context.SendOutside(mob); - - m_Context.Refresh(mob, corpse); - DuelContext.Debuff(mob); - DuelContext.CancelSpell(mob); - mob.Frozen = false; - - if (corpse != null && !corpse.Deleted) - Timer.DelayCall(TimeSpan.FromSeconds(30), corpse.Delete); - } - - public override bool OnDeath(Mobile mob, Container corpse) - { - Mobile killer = mob.FindMostRecentDamager(false); - KHTeamInfo teamInfo = null; - KHTeamInfo victInfo = GetTeamInfo(mob); - int bonus = 0; - - if (killer != null && killer.Player) - teamInfo = GetTeamInfo(killer); - - for (int i = 0; i < Controller.Hills.Length; i++) - { - if (Controller.Hills[i] == null) - continue; - - if (Controller.Hills[i].King == mob) - { - bonus += Controller.Hills[i].CapturesSoFar; - Controller.Hills[i].OnKingDied(mob, victInfo, killer, teamInfo); - } - - if (Controller.Hills[i].King == killer) - bonus += 2; - } - - if (teamInfo != null && teamInfo != victInfo) - { - KHPlayerInfo playerInfo = teamInfo[killer]; - - if (playerInfo != null) - { - playerInfo.Kills += 1; - playerInfo.Score += 1 + bonus; - } - } - - mob.CloseGump(typeof(KHBoardGump)); - mob.SendGump(new KHBoardGump(mob, this)); - - m_Context.Requip(mob, corpse); - DelayBounce(TimeSpan.FromSeconds(30.0), mob, corpse); - - return false; - } - - private Timer m_FinishTimer; - - public override void OnStart() - { - for (int i = 0; i < Controller.TeamInfo.Length; ++i) - { - KHTeamInfo teamInfo = Controller.TeamInfo[i]; - - teamInfo.Game = this; - teamInfo.Reset(); - } - - for (int i = 0; i < m_Context.Participants.Count; ++i) - ApplyHues(m_Context.Participants[i] as Participant, Controller.TeamInfo[i % Controller.TeamInfo.Length].Color); - - m_FinishTimer?.Stop(); - - for (int i = 0; i < Controller.Hills.Length; i++) - { - if (Controller.Hills[i] != null) - Controller.Hills[i].Game = this; - } - - foreach (KHBoard board in Controller.Boards) - { - if (board != null && !board.Deleted) - board.m_Game = this; - } - - m_FinishTimer = Timer.DelayCall(Controller.Duration, Finish_Callback); - } - - private void Finish_Callback() - { - ArrayList teams = new ArrayList(); - - for (int i = 0; i < m_Context.Participants.Count; ++i) - { - KHTeamInfo teamInfo = Controller.TeamInfo[i % Controller.TeamInfo.Length]; - - if (teamInfo == null) - continue; - - teams.Add(teamInfo); - } - - teams.Sort(); - - Tournament tourny = m_Context.m_Tournament; - - StringBuilder sb = new StringBuilder(); - - if (tourny != null && tourny.TournyType == TournyType.FreeForAll) - { - sb.Append(m_Context.Participants.Count * tourny.PlayersPerParticipant); - sb.Append("-man FFA"); - } - else if (tourny != null && tourny.TournyType == TournyType.RandomTeam) - { - sb.Append(tourny.ParticipantsPerMatch); - sb.Append("-team"); - } - else if (tourny != null && tourny.TournyType == TournyType.RedVsBlue) - { - sb.Append("Red v Blue"); - } - else if (tourny != null) - { - for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) - { - if (sb.Length > 0) - sb.Append('v'); - - sb.Append(tourny.PlayersPerParticipant); - } - } - - if (Controller != null) - sb.Append(' ').Append(Controller.Title); - - string title = sb.ToString(); - - KHTeamInfo winner = (KHTeamInfo)(teams.Count > 0 ? teams[0] : null); - - for (int i = 0; i < teams.Count; ++i) - { - TrophyRank rank = TrophyRank.Bronze; - - if (i == 0) - rank = TrophyRank.Gold; - else if (i == 1) - rank = TrophyRank.Silver; - - KHPlayerInfo leader = ((KHTeamInfo)teams[i]).Leader; - - foreach (KHPlayerInfo pl in ((KHTeamInfo)teams[i]).Players.Values) - { - Mobile mob = pl.Player; - - if (mob == null) - continue; - - sb = new StringBuilder(); - - sb.Append(title); - - if (pl == leader) - sb.Append(" Leader"); - - if (pl.Score > 0) - { - sb.Append(": "); - - sb.Append(pl.Score.ToString("N0")); - sb.Append(pl.Score == 1 ? " point" : " points"); - - sb.Append(", "); - sb.Append(pl.Kills.ToString("N0")); - sb.Append(pl.Kills == 1 ? " kill" : " kills"); - - if (pl.Captures > 0) - { - sb.Append(", "); - sb.Append(pl.Captures.ToString("N0")); - sb.Append(pl.Captures == 1 ? " capture" : " captures"); - } - } - - Item item = new Trophy(sb.ToString(), rank); - - if (pl == leader) - item.ItemID = 4810; - - item.Name = $"{item.Name}, {((KHTeamInfo) teams[i]).Name.ToLower()}"; - - if (!mob.PlaceInBackpack(item)) - mob.BankBox.DropItem(item); - - int cash = pl.Score * 250; - - if (cash > 0) - { - item = new BankCheck(cash); - - if (!mob.PlaceInBackpack(item)) - mob.BankBox.DropItem(item); - - mob.SendMessage("You have been awarded a {0} trophy and {1:N0}gp for your participation in this game.", rank.ToString().ToLower(), cash); - } - else - { - mob.SendMessage("You have been awarded a {0} trophy for your participation in this game.", rank.ToString().ToLower()); - } - } - } - - for (int i = 0; i < m_Context.Participants.Count; ++i) - { - if (!(m_Context.Participants[i] is Participant p) || p.Players == null) - continue; - - for (int j = 0; j < p.Players.Length; ++j) - { - DuelPlayer dp = p.Players[j]; - - if (dp?.Mobile != null) - { - dp.Mobile.CloseGump(typeof(KHBoardGump)); - dp.Mobile.SendGump(new KHBoardGump(dp.Mobile, this)); - } - } - - if (i == winner.TeamID) - continue; - - if (p?.Players != null) - { - for (int j = 0; j < p.Players.Length; ++j) - { - if (p.Players[j] != null) - p.Players[j].Eliminated = true; - } - } - } - - m_Context.Finish(m_Context.Participants[winner.TeamID] as Participant); - } - - public override void OnStop() - { - for (int i = 0; i < Controller.TeamInfo.Length; ++i) - Controller.TeamInfo[i].Game = null; - - for (int i = 0; i < Controller.Hills.Length; ++i) - { - if (Controller.Hills[i] != null) - Controller.Hills[i].Game = null; - } - - foreach (KHBoard board in Controller.Boards) - { - if (board != null) - board.m_Game = null; - } - - for (int i = 0; i < m_Context.Participants.Count; ++i) - ApplyHues(m_Context.Participants[i] as Participant, -1); - - m_FinishTimer?.Stop(); - m_FinishTimer = null; - } + for (int i = 0; i < p.Players.Length; ++i) + if (p.Players[i] != null) + p.Players[i].Mobile.SolidHueOverride = hueOverride; } -} + + public void DelayBounce(TimeSpan ts, Mobile mob, Container corpse) + { + Timer.DelayCall(ts, new TimerStateCallback(DelayBounce_Callback), new object[] { mob, corpse }); + } + + private void DelayBounce_Callback(object state) + { + object[] states = (object[])state; + Mobile mob = (Mobile)states[0]; + Container corpse = (Container)states[1]; + + DuelPlayer dp = null; + + if (mob is PlayerMobile mobile) + dp = mobile.DuelPlayer; + + m_Context.RemoveAggressions(mob); + + if (dp != null && !dp.Eliminated) + mob.MoveToWorld(m_Context.Arena.GetBaseStartPoint(GetTeamID(mob)), Facet); + else + m_Context.SendOutside(mob); + + m_Context.Refresh(mob, corpse); + DuelContext.Debuff(mob); + DuelContext.CancelSpell(mob); + mob.Frozen = false; + + if (corpse != null && !corpse.Deleted) + Timer.DelayCall(TimeSpan.FromSeconds(30), corpse.Delete); + } + + public override bool OnDeath(Mobile mob, Container corpse) + { + Mobile killer = mob.FindMostRecentDamager(false); + KHTeamInfo teamInfo = null; + KHTeamInfo victInfo = GetTeamInfo(mob); + int bonus = 0; + + if (killer != null && killer.Player) + teamInfo = GetTeamInfo(killer); + + for (int i = 0; i < Controller.Hills.Length; i++) + { + if (Controller.Hills[i] == null) + continue; + + if (Controller.Hills[i].King == mob) + { + bonus += Controller.Hills[i].CapturesSoFar; + Controller.Hills[i].OnKingDied(mob, victInfo, killer, teamInfo); + } + + if (Controller.Hills[i].King == killer) + bonus += 2; + } + + if (teamInfo != null && teamInfo != victInfo) + { + KHPlayerInfo playerInfo = teamInfo[killer]; + + if (playerInfo != null) + { + playerInfo.Kills += 1; + playerInfo.Score += 1 + bonus; + } + } + + mob.CloseGump(typeof(KHBoardGump)); + mob.SendGump(new KHBoardGump(mob, this)); + + m_Context.Requip(mob, corpse); + DelayBounce(TimeSpan.FromSeconds(30.0), mob, corpse); + + return false; + } + + public override void OnStart() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + { + KHTeamInfo teamInfo = Controller.TeamInfo[i]; + + teamInfo.Game = this; + teamInfo.Reset(); + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, + Controller.TeamInfo[i % Controller.TeamInfo.Length].Color); + + m_FinishTimer?.Stop(); + + for (int i = 0; i < Controller.Hills.Length; i++) + if (Controller.Hills[i] != null) + Controller.Hills[i].Game = this; + + foreach (KHBoard board in Controller.Boards) + if (board != null && !board.Deleted) + board.m_Game = this; + + m_FinishTimer = Timer.DelayCall(Controller.Duration, Finish_Callback); + } + + private void Finish_Callback() + { + ArrayList teams = new ArrayList(); + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + KHTeamInfo teamInfo = Controller.TeamInfo[i % Controller.TeamInfo.Length]; + + if (teamInfo == null) + continue; + + teams.Add(teamInfo); + } + + teams.Sort(); + + Tournament tourny = m_Context.m_Tournament; + + StringBuilder sb = new StringBuilder(); + + if (tourny != null && tourny.TournyType == TournyType.FreeForAll) + { + sb.Append(m_Context.Participants.Count * tourny.PlayersPerParticipant); + sb.Append("-man FFA"); + } + else if (tourny != null && tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-team"); + } + else if (tourny != null && tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else if (tourny != null) + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (Controller != null) + sb.Append(' ').Append(Controller.Title); + + string title = sb.ToString(); + + KHTeamInfo winner = (KHTeamInfo)(teams.Count > 0 ? teams[0] : null); + + for (int i = 0; i < teams.Count; ++i) + { + TrophyRank rank = TrophyRank.Bronze; + + if (i == 0) + rank = TrophyRank.Gold; + else if (i == 1) + rank = TrophyRank.Silver; + + KHPlayerInfo leader = ((KHTeamInfo)teams[i]).Leader; + + foreach (KHPlayerInfo pl in ((KHTeamInfo)teams[i]).Players.Values) + { + Mobile mob = pl.Player; + + if (mob == null) + continue; + + sb = new StringBuilder(); + + sb.Append(title); + + if (pl == leader) + sb.Append(" Leader"); + + if (pl.Score > 0) + { + sb.Append(": "); + + sb.Append(pl.Score.ToString("N0")); + sb.Append(pl.Score == 1 ? " point" : " points"); + + sb.Append(", "); + sb.Append(pl.Kills.ToString("N0")); + sb.Append(pl.Kills == 1 ? " kill" : " kills"); + + if (pl.Captures > 0) + { + sb.Append(", "); + sb.Append(pl.Captures.ToString("N0")); + sb.Append(pl.Captures == 1 ? " capture" : " captures"); + } + } + + Item item = new Trophy(sb.ToString(), rank); + + if (pl == leader) + item.ItemID = 4810; + + item.Name = $"{item.Name}, {((KHTeamInfo)teams[i]).Name.ToLower()}"; + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + int cash = pl.Score * 250; + + if (cash > 0) + { + item = new BankCheck(cash); + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + mob.SendMessage( + "You have been awarded a {0} trophy and {1:N0}gp for your participation in this game.", + rank.ToString().ToLower(), cash); + } + else + { + mob.SendMessage("You have been awarded a {0} trophy for your participation in this game.", + rank.ToString().ToLower()); + } + } + } + + for (int i = 0; i < m_Context.Participants.Count; ++i) + { + if (!(m_Context.Participants[i] is Participant p) || p.Players == null) + continue; + + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer dp = p.Players[j]; + + if (dp?.Mobile != null) + { + dp.Mobile.CloseGump(typeof(KHBoardGump)); + dp.Mobile.SendGump(new KHBoardGump(dp.Mobile, this)); + } + } + + if (i == winner.TeamID) + continue; + + if (p?.Players != null) + for (int j = 0; j < p.Players.Length; ++j) + if (p.Players[j] != null) + p.Players[j].Eliminated = true; + } + + m_Context.Finish(m_Context.Participants[winner.TeamID] as Participant); + } + + public override void OnStop() + { + for (int i = 0; i < Controller.TeamInfo.Length; ++i) + Controller.TeamInfo[i].Game = null; + + for (int i = 0; i < Controller.Hills.Length; ++i) + if (Controller.Hills[i] != null) + Controller.Hills[i].Game = null; + + foreach (KHBoard board in Controller.Boards) + if (board != null) + board.m_Game = null; + + for (int i = 0; i < m_Context.Participants.Count; ++i) + ApplyHues(m_Context.Participants[i] as Participant, -1); + + m_FinishTimer?.Stop(); + m_FinishTimer = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Ladder.cs b/Scripts/Engines/ConPVP/Ladder.cs index 0ca7e76c0..d298fe710 100644 --- a/Scripts/Engines/ConPVP/Ladder.cs +++ b/Scripts/Engines/ConPVP/Ladder.cs @@ -3,366 +3,381 @@ using System.Collections; namespace Server.Engines.ConPVP { - public class LadderController : Item - { - private Ladder m_Ladder; - - //[CommandProperty( AccessLevel.GameMaster )] - public Ladder Ladder{ get => m_Ladder; - set{} } - - public override string DefaultName => "ladder controller"; - - [Constructible] - public LadderController() : base( 0x1B7A ) - { - Visible = false; - Movable = false; - - m_Ladder = new Ladder(); - - if ( Ladder.Instance == null ) - Ladder.Instance = m_Ladder; - } - - public override void Delete() - { - if ( Ladder.Instance == m_Ladder ) - Ladder.Instance = null; - - base.Delete(); - } - - public LadderController( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); - - m_Ladder.Serialize( writer ); - - writer.Write( (bool) ( Ladder.Instance == m_Ladder ) ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - case 0: - { - m_Ladder = new Ladder( reader ); - - if ( version < 1 || reader.ReadBool() ) - Ladder.Instance = m_Ladder; - - break; - } - } - } - } - - public class Ladder - { - private static int[] m_ShortLevels = { - 1, - 2, - 3, 3, - 4, 4, - 5, 5, 5, - 6, 6, 6, - 7, 7, 7, 7, - 8, 8, 8, 8, - 9, 9, 9, 9, 9 - }; - - public static int GetLevel( int xp ) - { - if ( xp >= 22500 ) - return 50; - if ( xp >= 2500 ) - return (10 + ((xp - 2500) / 500)); - if ( xp < 0 ) - xp = 0; - - return m_ShortLevels[xp / 100]; - } - - private static int[] m_BaseXP = { - 0, 100, 200, 400, 600, 900, 1200, 1600, 2000, 2500 - }; - - public static void GetLevelInfo( int level, out int xpBase, out int xpAdvance ) - { - if ( level >= 10 ) - { - xpBase = 2500 + ((level-10)*500); - xpAdvance = 500; - } - else - { - xpBase = m_BaseXP[level-1]; - xpAdvance = m_BaseXP[level] - xpBase; - } - } - - private static int[] m_LossFactors = { - 10, - 11, 11, - 25, 25, - 43, 43, - 67, 67 - }; - - public static int GetLossFactor( int level ) - { - if ( level >= 10 ) - return 100; - - return m_LossFactors[level - 1]; - } - - private static int[,] m_OffsetScalar = { - /* { win, los } */ - /* -6 */ { 175, 25 }, - /* -5 */ { 165, 35 }, - /* -4 */ { 155, 45 }, - /* -3 */ { 145, 55 }, - /* -2 */ { 130, 70 }, - /* -1 */ { 115, 85 }, - /* 0 */ { 100, 100 }, - /* +1 */ { 90, 110 }, - /* +2 */ { 80, 120 }, - /* +3 */ { 70, 130 }, - /* +4 */ { 60, 140 }, - /* +5 */ { 50, 150 }, - /* +6 */ { 40, 160 } - }; - - public static int GetOffsetScalar( int ourLevel, int theirLevel, bool win ) - { - int x = ourLevel - theirLevel; - - if ( x < -6 || x > +6 ) - return 0; - - int y = win ? 0 : 1; - - return m_OffsetScalar[x+6, y]; - } - - public static int GetExperienceGain( LadderEntry us, LadderEntry them, bool weWon ) - { - if ( us == null || them == null ) - return 0; - - int ourLevel = GetLevel( us.Experience ); - int theirLevel = GetLevel( them.Experience ); - - int scalar = GetOffsetScalar( ourLevel, theirLevel, weWon ); - - if ( scalar == 0 ) - return 0; - - int xp = 25 * scalar; - - if ( !weWon ) - xp = (xp * GetLossFactor( ourLevel )) / 100; - - xp /= 100; - - if ( xp <= 0 ) - xp = 1; - - return xp * (weWon ? 1 : -1); - } - - private Hashtable m_Table; - private ArrayList m_Entries; - - public ArrayList ToArrayList() - { - return m_Entries; - } - - private int Swap( int idx, int newIdx ) - { - object hold = m_Entries[idx]; - - m_Entries[idx] = m_Entries[newIdx]; - m_Entries[newIdx] = hold; - - ((LadderEntry)m_Entries[idx]).Index = idx; - ((LadderEntry)m_Entries[newIdx]).Index = newIdx; - - return newIdx; - } - - public void UpdateEntry( LadderEntry entry ) - { - int index = entry.Index; - - if ( index >= 0 && index < m_Entries.Count ) - { - // sanity - - int c; - - while ( (index - 1) >= 0 && (c = entry.CompareTo( m_Entries[index - 1] )) < 0 ) - index = Swap( index, index - 1 ); + public class LadderController : Item + { + private Ladder m_Ladder; + + [Constructible] + public LadderController() : base(0x1B7A) + { + Visible = false; + Movable = false; + + m_Ladder = new Ladder(); + + if (Ladder.Instance == null) + Ladder.Instance = m_Ladder; + } + + public LadderController(Serial serial) : base(serial) + { + } + + //[CommandProperty( AccessLevel.GameMaster )] + public Ladder Ladder + { + get => m_Ladder; + set { } + } + + public override string DefaultName => "ladder controller"; + + public override void Delete() + { + if (Ladder.Instance == m_Ladder) + Ladder.Instance = null; + + base.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + + m_Ladder.Serialize(writer); + + writer.Write(Ladder.Instance == m_Ladder); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + case 0: + { + m_Ladder = new Ladder(reader); + + if (version < 1 || reader.ReadBool()) + Ladder.Instance = m_Ladder; + + break; + } + } + } + } + + public class Ladder + { + private static int[] m_ShortLevels = + { + 1, + 2, + 3, 3, + 4, 4, + 5, 5, 5, + 6, 6, 6, + 7, 7, 7, 7, + 8, 8, 8, 8, + 9, 9, 9, 9, 9 + }; + + private static int[] m_BaseXP = + { + 0, 100, 200, 400, 600, 900, 1200, 1600, 2000, 2500 + }; + + private static int[] m_LossFactors = + { + 10, + 11, 11, + 25, 25, + 43, 43, + 67, 67 + }; + + private static int[,] m_OffsetScalar = + { + /* { win, los } */ + /* -6 */ { 175, 25 }, + /* -5 */ { 165, 35 }, + /* -4 */ { 155, 45 }, + /* -3 */ { 145, 55 }, + /* -2 */ { 130, 70 }, + /* -1 */ { 115, 85 }, + /* 0 */ { 100, 100 }, + /* +1 */ { 90, 110 }, + /* +2 */ { 80, 120 }, + /* +3 */ { 70, 130 }, + /* +4 */ { 60, 140 }, + /* +5 */ { 50, 150 }, + /* +6 */ { 40, 160 } + }; + + private ArrayList m_Entries; + + private Hashtable m_Table; + + public Ladder() + { + m_Table = new Hashtable(); + m_Entries = new ArrayList(); + } + + public Ladder(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 1: + case 0: + { + int count = reader.ReadEncodedInt(); + + m_Table = new Hashtable(count); + m_Entries = new ArrayList(count); + + for (int i = 0; i < count; ++i) + { + LadderEntry entry = new LadderEntry(reader, this, version); + + if (entry.Mobile != null) + { + m_Table[entry.Mobile] = entry; + entry.Index = m_Entries.Count; + m_Entries.Add(entry); + } + } + + if (version == 0) + { + m_Entries.Sort(); + + for (int i = 0; i < m_Entries.Count; ++i) + { + LadderEntry entry = (LadderEntry)m_Entries[i]; + + entry.Index = i; + } + } + + break; + } + } + } + + public static Ladder Instance{ get; set; } + + public static int GetLevel(int xp) + { + if (xp >= 22500) + return 50; + if (xp >= 2500) + return 10 + (xp - 2500) / 500; + if (xp < 0) + xp = 0; + + return m_ShortLevels[xp / 100]; + } + + public static void GetLevelInfo(int level, out int xpBase, out int xpAdvance) + { + if (level >= 10) + { + xpBase = 2500 + (level - 10) * 500; + xpAdvance = 500; + } + else + { + xpBase = m_BaseXP[level - 1]; + xpAdvance = m_BaseXP[level] - xpBase; + } + } + + public static int GetLossFactor(int level) + { + if (level >= 10) + return 100; + + return m_LossFactors[level - 1]; + } + + public static int GetOffsetScalar(int ourLevel, int theirLevel, bool win) + { + int x = ourLevel - theirLevel; + + if (x < -6 || x > +6) + return 0; + + int y = win ? 0 : 1; - while ( (index + 1) < m_Entries.Count && (c = entry.CompareTo( m_Entries[index + 1] )) > 0 ) - index = Swap( index, index + 1 ); - } - } + return m_OffsetScalar[x + 6, y]; + } + + public static int GetExperienceGain(LadderEntry us, LadderEntry them, bool weWon) + { + if (us == null || them == null) + return 0; + + int ourLevel = GetLevel(us.Experience); + int theirLevel = GetLevel(them.Experience); + + int scalar = GetOffsetScalar(ourLevel, theirLevel, weWon); + + if (scalar == 0) + return 0; + + int xp = 25 * scalar; + + if (!weWon) + xp = xp * GetLossFactor(ourLevel) / 100; + + xp /= 100; + + if (xp <= 0) + xp = 1; + + return xp * (weWon ? 1 : -1); + } + + public ArrayList ToArrayList() + { + return m_Entries; + } + + private int Swap(int idx, int newIdx) + { + object hold = m_Entries[idx]; + + m_Entries[idx] = m_Entries[newIdx]; + m_Entries[newIdx] = hold; + + ((LadderEntry)m_Entries[idx]).Index = idx; + ((LadderEntry)m_Entries[newIdx]).Index = newIdx; + + return newIdx; + } + + public void UpdateEntry(LadderEntry entry) + { + int index = entry.Index; + + if (index >= 0 && index < m_Entries.Count) + { + // sanity + + int c; + + while (index - 1 >= 0 && (c = entry.CompareTo(m_Entries[index - 1])) < 0) + index = Swap(index, index - 1); + + while (index + 1 < m_Entries.Count && (c = entry.CompareTo(m_Entries[index + 1])) > 0) + index = Swap(index, index + 1); + } + } + + public LadderEntry Find(Mobile mob) + { + LadderEntry entry = (LadderEntry)m_Table[mob]; + + if (entry == null) + { + m_Table[mob] = entry = new LadderEntry(mob, this); + entry.Index = m_Entries.Count; + m_Entries.Add(entry); + } + + return entry; + } + + public LadderEntry FindNoCreate(Mobile mob) + { + return m_Table[mob] as LadderEntry; + } - public LadderEntry Find( Mobile mob ) - { - LadderEntry entry = (LadderEntry) m_Table[mob]; + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(1); // version; - if ( entry == null ) - { - m_Table[mob] = entry = new LadderEntry( mob, this ); - entry.Index = m_Entries.Count; - m_Entries.Add( entry ); - } + writer.WriteEncodedInt(m_Entries.Count); - return entry; - } + for (int i = 0; i < m_Entries.Count; ++i) + ((LadderEntry)m_Entries[i]).Serialize(writer); + } + } - public LadderEntry FindNoCreate( Mobile mob ) - { - return m_Table[mob] as LadderEntry; - } + public class LadderEntry : IComparable + { + private int m_Experience; + private Ladder m_Ladder; - public static Ladder Instance { get; set; } - - public Ladder() - { - m_Table = new Hashtable(); - m_Entries = new ArrayList(); - } - - public Ladder( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 1: - case 0: - { - int count = reader.ReadEncodedInt(); - - m_Table = new Hashtable( count ); - m_Entries = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) - { - LadderEntry entry = new LadderEntry( reader, this, version ); - - if ( entry.Mobile != null ) - { - m_Table[entry.Mobile] = entry; - entry.Index = m_Entries.Count; - m_Entries.Add( entry ); - } - } - - if ( version == 0 ) - { - m_Entries.Sort(); - - for ( int i = 0; i < m_Entries.Count; ++i ) - { - LadderEntry entry = (LadderEntry)m_Entries[i]; - - entry.Index = i; - } - } - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 1 ); // version; - - writer.WriteEncodedInt( (int) m_Entries.Count ); - - for ( int i = 0; i < m_Entries.Count; ++i ) - ((LadderEntry)m_Entries[i]).Serialize( writer ); - } - } - - public class LadderEntry : IComparable - { - private int m_Experience; - private Ladder m_Ladder; - - public Mobile Mobile { get; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public int Experience{ get => m_Experience; - set{ m_Experience = value; m_Ladder.UpdateEntry(this); } } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public int Wins { get; set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public int Losses { get; set; } - - public int Index { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Rank => Index; - - public LadderEntry( Mobile mob, Ladder ladder ) - { - m_Ladder = ladder; - Mobile = mob; - } - - public LadderEntry( GenericReader reader, Ladder ladder, int version ) - { - m_Ladder = ladder; - - switch ( version ) - { - case 1: - case 0: - { - Mobile = reader.ReadMobile(); - m_Experience = reader.ReadEncodedInt(); - Wins = reader.ReadEncodedInt(); - Losses = reader.ReadEncodedInt(); - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (Mobile) Mobile ); - writer.WriteEncodedInt( (int) m_Experience ); - writer.WriteEncodedInt( (int) Wins ); - writer.WriteEncodedInt( (int) Losses ); - } - - public int CompareTo( object obj ) - { - return ((LadderEntry)obj).m_Experience - m_Experience; - } - } + public LadderEntry(Mobile mob, Ladder ladder) + { + m_Ladder = ladder; + Mobile = mob; + } + + public LadderEntry(GenericReader reader, Ladder ladder, int version) + { + m_Ladder = ladder; + + switch (version) + { + case 1: + case 0: + { + Mobile = reader.ReadMobile(); + m_Experience = reader.ReadEncodedInt(); + Wins = reader.ReadEncodedInt(); + Losses = reader.ReadEncodedInt(); + + break; + } + } + } + + public Mobile Mobile{ get; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public int Experience + { + get => m_Experience; + set + { + m_Experience = value; + m_Ladder.UpdateEntry(this); + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public int Wins{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public int Losses{ get; set; } + + public int Index{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Rank => Index; + + public int CompareTo(object obj) + { + return ((LadderEntry)obj).m_Experience - m_Experience; + } + + public void Serialize(GenericWriter writer) + { + writer.Write(Mobile); + writer.WriteEncodedInt(m_Experience); + writer.WriteEncodedInt(Wins); + writer.WriteEncodedInt(Losses); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/LadderGump.cs b/Scripts/Engines/ConPVP/LadderGump.cs index 277d858e6..d7ab629a1 100644 --- a/Scripts/Engines/ConPVP/LadderGump.cs +++ b/Scripts/Engines/ConPVP/LadderGump.cs @@ -5,250 +5,253 @@ using Server.Network; namespace Server.Engines.ConPVP { - public class LadderItem : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public LadderController Ladder { get; set; } + public class LadderItem : Item + { + [Constructible] + public LadderItem() : base(0x117F) + { + Movable = false; + } - public override string DefaultName => "1v1 leaderboard"; + public LadderItem(Serial serial) : base(serial) + { + } - [Constructible] - public LadderItem() : base( 0x117F ) - { - Movable = false; - } + [CommandProperty(AccessLevel.GameMaster)] + public LadderController Ladder{ get; set; } - public LadderItem( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "1v1 leaderboard"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); + writer.Write(1); - writer.Write( (Item) Ladder ); - } + writer.Write(Ladder); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Ladder = reader.ReadItem() as LadderController; - break; - } - } - } + switch (version) + { + case 1: + { + Ladder = reader.ReadItem() as LadderController; + break; + } + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - Ladder ladder = Server.Engines.ConPVP.Ladder.Instance; + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + { + Ladder ladder = ConPVP.Ladder.Instance; - if ( Ladder != null ) - ladder = Ladder.Ladder; + if (Ladder != null) + ladder = Ladder.Ladder; - if ( ladder != null ) - { - from.CloseGump( typeof( LadderGump ) ); - from.SendGump( new LadderGump( ladder, 0 ) ); - } - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that - } - } + if (ladder != null) + { + from.CloseGump(typeof(LadderGump)); + from.SendGump(new LadderGump(ladder, 0)); + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that + } + } + } - public class LadderGump : Gump - { - private Ladder m_Ladder; - private int m_Page; + public class LadderGump : Gump + { + private int m_ColumnX = 12; + private Ladder m_Ladder; - public LadderGump( Ladder ladder ) : this( ladder, 0 ) - { - } + private ArrayList m_List; + private int m_Page; - public static string Rank( int num ) - { - string numStr = num.ToString( "N0" ); + public LadderGump(Ladder ladder) : this(ladder, 0) + { + } - if ( (num%100) > 10 && (num%100) < 20 ) - return numStr + "th"; + public LadderGump(Ladder ladder, int page) : base(50, 50) + { + m_Ladder = ladder; + m_Page = page; - switch ( num % 10 ) - { - case 1: return numStr + "st"; - case 2: return numStr + "nd"; - case 3: return numStr + "rd"; - default: return numStr + "th"; - } - } + AddPage(0); - public override void OnResponse(NetState sender, RelayInfo info) - { - Mobile from = sender.Mobile; + ArrayList list = ladder.ToArrayList(); + m_List = list; - if ( info.ButtonID == 1 && m_Page > 0 ) - from.SendGump( new LadderGump( m_Ladder, m_Page - 1 ) ); - else if ( info.ButtonID == 2 && ((m_Page+1)*15) lc) + end = lc; - AddPage( 0 ); + int ct = end - start; - ArrayList list = ladder.ToArrayList(); - m_List = list; + int height = 12 + 20 + ct * 20 + 23 + 12; - int lc = Math.Min( list.Count, 150 ); + AddBackground(0, 0, 499, height, 0x2436); - int start = page * 15; - int end = start+15; + for (int i = start + 1; i < end; i += 2) + AddImageTiled(12, 32 + (i - start) * 20, 475, 20, 0x2430); - if ( end > lc ) - end = lc; + AddAlphaRegion(10, 10, 479, height - 20); - int ct = end-start; + if (page > 0) + AddButton(446, height - 12 - 2 - 16, 0x15E3, 0x15E7, 1, GumpButtonType.Reply, 0); + else + AddImage(446, height - 12 - 2 - 16, 0x2626); - int height = 12 + 20 + (ct*20) + 23 + 12; + if ((page + 1) * 15 < lc) + AddButton(466, height - 12 - 2 - 16, 0x15E1, 0x15E5, 2, GumpButtonType.Reply, 0); + else + AddImage(466, height - 12 - 2 - 16, 0x2622); - AddBackground( 0, 0, 499, height, 0x2436 ); + AddHtml(16, height - 12 - 2 - 18, 400, 20, + Color(string.Format("Top {3} of {0:N0} duelists, page {1} of {2}", list.Count, page + 1, (lc + 14) / 15, lc), + 0xFFC000), false, false); - for ( int i = start + 1; i < end; i += 2 ) - AddImageTiled( 12, 32 + ((i - start) * 20), 475, 20, 0x2430 ); + AddColumnHeader(75, "Rank"); + AddColumnHeader(115, "Level"); + AddColumnHeader(50, "Guild"); + AddColumnHeader(115, "Name"); + AddColumnHeader(60, "Wins"); + AddColumnHeader(60, "Losses"); - AddAlphaRegion( 10, 10, 479, height - 20 ); + for (int i = start; i < end && i < lc; ++i) + { + LadderEntry entry = (LadderEntry)list[i]; - if ( page > 0 ) - AddButton( 446, height-12-2-16, 0x15E3, 0x15E7, 1, GumpButtonType.Reply, 0 ); - else - AddImage( 446, height-12-2-16, 0x2626 ); + int y = 32 + (i - start) * 20; + int x = 12; - if ( ((page+1)*15)= xpAdvance) + width = 109; // level 50 + else + width = (109 * xpOffset + xpAdvance / 2) / (xpAdvance - 1); - int xp = entry.Experience; - int level = Ladder.GetLevel( xp ); + //AddImageTiled( 21, y + 6, width, 8, 0x2617 ); + AddImageTiled(x + 3, y + 4, width, 11, 0x806); + AddBorderedText(x, y, 115, Center(level.ToString()), 0xFFFFFF, 0); + x += 115; - int xpBase, xpAdvance; - Ladder.GetLevelInfo( level, out xpBase, out xpAdvance ); + Mobile mob = entry.Mobile; - int width; + if (mob.Guild != null) + AddBorderedText(x, y, 50, Center(mob.Guild.Abbreviation), 0xFFFFFF, 0); - int xpOffset = xp - xpBase; + x += 50; - if ( xpOffset >= xpAdvance ) - width = 109; // level 50 - else - width = ((109 * xpOffset) + (xpAdvance / 2)) / (xpAdvance - 1); + AddBorderedText(x + 5, y, 115 - 5, mob.Name, 0xFFFFFF, 0); + x += 115; - //AddImageTiled( 21, y + 6, width, 8, 0x2617 ); - AddImageTiled( x + 3, y + 4, width, 11, 0x806 ); - AddBorderedText( x, y, 115, Center( level.ToString() ), 0xFFFFFF, 0 ); - x += 115; + AddBorderedText(x, y, 60, Center(entry.Wins.ToString()), 0xFFFFFF, 0); + x += 60; - Mobile mob = entry.Mobile; + AddBorderedText(x, y, 60, Center(entry.Losses.ToString()), 0xFFFFFF, 0); + x += 60; - if ( mob.Guild != null ) - AddBorderedText( x, y, 50, Center( mob.Guild.Abbreviation ), 0xFFFFFF, 0 ); + //AddBorderedText( 292 + 15, y, 115 - 30, String.Format( "{0}
/
{1}
", entry.Wins, entry.Losses ), 0xFFC000, 0 ); + } + } - x += 50; + public static string Rank(int num) + { + string numStr = num.ToString("N0"); - AddBorderedText( x + 5, y, 115 - 5, ( mob.Name ), 0xFFFFFF, 0 ); - x += 115; + if (num % 100 > 10 && num % 100 < 20) + return numStr + "th"; - AddBorderedText( x, y, 60, Center( entry.Wins.ToString() ), 0xFFFFFF, 0 ); - x += 60; + switch (num % 10) + { + case 1: return numStr + "st"; + case 2: return numStr + "nd"; + case 3: return numStr + "rd"; + default: return numStr + "th"; + } + } - AddBorderedText( x, y, 60, Center( entry.Losses.ToString() ), 0xFFFFFF, 0 ); - x += 60; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - //AddBorderedText( 292 + 15, y, 115 - 30, String.Format( "{0}
/
{1}
", entry.Wins, entry.Losses ), 0xFFC000, 0 ); - } - } + if (info.ButtonID == 1 && m_Page > 0) + from.SendGump(new LadderGump(m_Ladder, m_Page - 1)); + else if (info.ButtonID == 2 && (m_Page + 1) * 15 < Math.Min(m_List.Count, 150)) + from.SendGump(new LadderGump(m_Ladder, m_Page + 1)); + } - public string Center( string text ) - { - return $"
{text}
"; - } + public string Center(string text) + { + return $"
{text}
"; + } - public string Color( string text, int color ) - { - return $"{text}"; - } + public string Color(string text, int color) + { + return $"{text}"; + } - private void AddBorderedText( int x, int y, int width, string text, int color, int borderColor ) - { - /*AddColoredText( x - 1, y, width, text, borderColor ); - AddColoredText( x + 1, y, width, text, borderColor ); - AddColoredText( x, y - 1, width, text, borderColor ); - AddColoredText( x, y + 1, width, text, borderColor );*/ - /*AddColoredText( x - 1, y - 1, width, text, borderColor ); - AddColoredText( x + 1, y + 1, width, text, borderColor );*/ - AddColoredText( x, y, width, text, color ); - } + private void AddBorderedText(int x, int y, int width, string text, int color, int borderColor) + { + /*AddColoredText( x - 1, y, width, text, borderColor ); + AddColoredText( x + 1, y, width, text, borderColor ); + AddColoredText( x, y - 1, width, text, borderColor ); + AddColoredText( x, y + 1, width, text, borderColor );*/ + /*AddColoredText( x - 1, y - 1, width, text, borderColor ); + AddColoredText( x + 1, y + 1, width, text, borderColor );*/ + AddColoredText(x, y, width, text, color); + } - private void AddColoredText( int x, int y, int width, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, 20, text, false, false ); - else - AddHtml( x, y, width, 20, Color( text, color ), false, false ); - } + private void AddColoredText(int x, int y, int width, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, 20, text, false, false); + else + AddHtml(x, y, width, 20, Color(text, color), false, false); + } - private int m_ColumnX = 12; + private void AddColumnHeader(int width, string name) + { + AddBackground(m_ColumnX, 12, width, 20, 0x242C); + AddImageTiled(m_ColumnX + 2, 14, width - 4, 16, 0x2430); + AddBorderedText(m_ColumnX, 13, width, Center(name), 0xFFFFFF, 0); - private void AddColumnHeader( int width, string name ) - { - AddBackground( m_ColumnX, 12, width, 20, 0x242C ); - AddImageTiled( m_ColumnX + 2, 14, width - 4, 16, 0x2430 ); - AddBorderedText( m_ColumnX, 13, width, Center( name ), 0xFFFFFF, 0 ); - - m_ColumnX += width; - } - } + m_ColumnX += width; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Participant.cs b/Scripts/Engines/ConPVP/Participant.cs index a5416510c..0f379aae8 100644 --- a/Scripts/Engines/ConPVP/Participant.cs +++ b/Scripts/Engines/ConPVP/Participant.cs @@ -1,230 +1,231 @@ using System; using System.Text; using Server.Mobiles; +using Server.Network; namespace Server.Engines.ConPVP { - public class Participant - { - public int Count => Players.Length; - public DuelPlayer[] Players { get; private set; } + public class Participant + { + public Participant(DuelContext context, int count) + { + Context = context; + //m_Stakes = new StakesContainer( context, this ); + Resize(count); + } - public DuelContext Context { get; } + public int Count => Players.Length; + public DuelPlayer[] Players{ get; private set; } - public TournyParticipant TournyPart { get; set; } + public DuelContext Context{ get; } - public DuelPlayer Find( Mobile mob ) - { - if ( mob is PlayerMobile pm ) - { - if ( pm.DuelContext == Context && pm.DuelPlayer.Participant == this ) - return pm.DuelPlayer; + public TournyParticipant TournyPart{ get; set; } - return null; - } + public int FilledSlots + { + get + { + int count = 0; - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] != null && Players[i].Mobile == mob ) - return Players[i]; - } + for (int i = 0; i < Players.Length; ++i) + if (Players[i] != null) + ++count; - return null; - } + return count; + } + } - public bool Contains( Mobile mob ) - { - return ( Find( mob ) != null ); - } + public bool HasOpenSlot + { + get + { + for (int i = 0; i < Players.Length; ++i) + if (Players[i] == null) + return true; - public void Broadcast( int hue, string message, string nonLocalOverhead, string localOverhead ) - { - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] != null ) - { - if ( message != null ) - Players[i].Mobile.SendMessage( hue, message ); + return false; + } + } - if ( nonLocalOverhead != null ) - Players[i].Mobile.NonlocalOverheadMessage( Network.MessageType.Regular, hue, false, string.Format( nonLocalOverhead, Players[i].Mobile.Name, Players[i].Mobile.Female ? "her" : "his" ) ); + public bool Eliminated + { + get + { + for (int i = 0; i < Players.Length; ++i) + if (Players[i] != null && !Players[i].Eliminated) + return false; - if ( localOverhead != null ) - Players[i].Mobile.LocalOverheadMessage( Network.MessageType.Regular, hue, false, localOverhead ); - } - } - } + return true; + } + } - public int FilledSlots - { - get - { - int count = 0; + public string NameList + { + get + { + StringBuilder sb = new StringBuilder(); - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] != null ) - ++count; - } + for (int i = 0; i < Players.Length; ++i) + { + if (Players[i] == null) + continue; - return count; - } - } + Mobile mob = Players[i].Mobile; - public bool HasOpenSlot - { - get - { - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] == null ) - return true; - } + if (sb.Length > 0) + sb.Append(", "); - return false; - } - } + sb.Append(mob.Name); + } - public bool Eliminated - { - get - { - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] != null && !Players[i].Eliminated ) - return false; - } + if (sb.Length == 0) + return "Empty"; - return true; - } - } + return sb.ToString(); + } + } - public string NameList - { - get - { - StringBuilder sb = new StringBuilder(); + public DuelPlayer Find(Mobile mob) + { + if (mob is PlayerMobile pm) + { + if (pm.DuelContext == Context && pm.DuelPlayer.Participant == this) + return pm.DuelPlayer; - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] == null ) - continue; + return null; + } - Mobile mob = Players[i].Mobile; + for (int i = 0; i < Players.Length; ++i) + if (Players[i] != null && Players[i].Mobile == mob) + return Players[i]; - if ( sb.Length > 0 ) - sb.Append( ", " ); + return null; + } - sb.Append( mob.Name ); - } + public bool Contains(Mobile mob) + { + return Find(mob) != null; + } - if ( sb.Length == 0 ) - return "Empty"; + public void Broadcast(int hue, string message, string nonLocalOverhead, string localOverhead) + { + for (int i = 0; i < Players.Length; ++i) + if (Players[i] != null) + { + if (message != null) + Players[i].Mobile.SendMessage(hue, message); - return sb.ToString(); - } - } + if (nonLocalOverhead != null) + Players[i].Mobile.NonlocalOverheadMessage(MessageType.Regular, hue, false, + string.Format(nonLocalOverhead, Players[i].Mobile.Name, + Players[i].Mobile.Female ? "her" : "his")); - public void Nullify( DuelPlayer player ) - { - if ( player == null ) - return; + if (localOverhead != null) + Players[i].Mobile.LocalOverheadMessage(MessageType.Regular, hue, false, localOverhead); + } + } - int index = Array.IndexOf( Players, player ); + public void Nullify(DuelPlayer player) + { + if (player == null) + return; - if ( index == -1 ) - return; + int index = Array.IndexOf(Players, player); - Players[index] = null; - } + if (index == -1) + return; - public void Remove( DuelPlayer player ) - { - if ( player == null ) - return; + Players[index] = null; + } - int index = Array.IndexOf( Players, player ); + public void Remove(DuelPlayer player) + { + if (player == null) + return; - if ( index == -1 ) - return; + int index = Array.IndexOf(Players, player); - DuelPlayer[] old = Players; - Players = new DuelPlayer[old.Length - 1]; + if (index == -1) + return; - for ( int i = 0; i < index; ++i ) - Players[i] = old[i]; + DuelPlayer[] old = Players; + Players = new DuelPlayer[old.Length - 1]; - for ( int i = index + 1; i < old.Length; ++i ) - Players[i - 1] = old[i]; - } + for (int i = 0; i < index; ++i) + Players[i] = old[i]; - public void Remove( Mobile player ) - { - Remove( Find( player ) ); - } + for (int i = index + 1; i < old.Length; ++i) + Players[i - 1] = old[i]; + } - public void Add( Mobile player ) - { - if ( Contains( player ) ) - return; + public void Remove(Mobile player) + { + Remove(Find(player)); + } - for ( int i = 0; i < Players.Length; ++i ) - { - if ( Players[i] == null ) - { - Players[i] = new DuelPlayer( player, this ); - return; - } - } + public void Add(Mobile player) + { + if (Contains(player)) + return; - Resize( Players.Length + 1 ); - Players[Players.Length - 1] = new DuelPlayer( player, this ); - } + for (int i = 0; i < Players.Length; ++i) + if (Players[i] == null) + { + Players[i] = new DuelPlayer(player, this); + return; + } - public void Resize( int count ) - { - DuelPlayer[] old = Players; - Players = new DuelPlayer[count]; + Resize(Players.Length + 1); + Players[Players.Length - 1] = new DuelPlayer(player, this); + } - if ( old != null ) - { - int ct = 0; + public void Resize(int count) + { + DuelPlayer[] old = Players; + Players = new DuelPlayer[count]; - for ( int i = 0; i < old.Length; ++i ) - { - if ( old[i] != null && ct < count ) - Players[ct++] = old[i]; - } - } - } + if (old != null) + { + int ct = 0; - public Participant( DuelContext context, int count ) - { - Context = context; - //m_Stakes = new StakesContainer( context, this ); - Resize( count ); - } - } + for (int i = 0; i < old.Length; ++i) + if (old[i] != null && ct < count) + Players[ct++] = old[i]; + } + } + } - public class DuelPlayer - { - private bool m_Eliminated; + public class DuelPlayer + { + private bool m_Eliminated; - public Mobile Mobile { get; } + public DuelPlayer(Mobile mob, Participant p) + { + Mobile = mob; + Participant = p; - public bool Ready { get; set; } + if (mob is PlayerMobile mobile) + mobile.DuelPlayer = this; + } - public bool Eliminated{ get => m_Eliminated; - set{ m_Eliminated = value; if ( Participant.Context.m_Tournament != null && m_Eliminated ){ Participant.Context.m_Tournament.OnEliminated( this ); Mobile.SendEverything(); } } } - public Participant Participant { get; set; } + public Mobile Mobile{ get; } - public DuelPlayer( Mobile mob, Participant p ) - { - Mobile = mob; - Participant = p; + public bool Ready{ get; set; } - if ( mob is PlayerMobile mobile ) - mobile.DuelPlayer = this; - } - } -} + public bool Eliminated + { + get => m_Eliminated; + set + { + m_Eliminated = value; + if (Participant.Context.m_Tournament != null && m_Eliminated) + { + Participant.Context.m_Tournament.OnEliminated(this); + Mobile.SendEverything(); + } + } + } + + public Participant Participant{ get; set; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/ParticipantGump.cs b/Scripts/Engines/ConPVP/ParticipantGump.cs index 401965f03..58d8a8787 100644 --- a/Scripts/Engines/ConPVP/ParticipantGump.cs +++ b/Scripts/Engines/ConPVP/ParticipantGump.cs @@ -1,241 +1,253 @@ -using System; using Server.Gumps; +using Server.Mobiles; using Server.Network; using Server.Targeting; -using Server.Mobiles; namespace Server.Engines.ConPVP { - public class ParticipantGump : Gump - { - public Mobile From { get; } + public class ParticipantGump : Gump + { + public ParticipantGump(Mobile from, DuelContext context, Participant p) : base(50, 50) + { + From = from; + Context = context; + Participant = p; - public DuelContext Context { get; } + from.CloseGump(typeof(RulesetGump)); + from.CloseGump(typeof(DuelContextGump)); + from.CloseGump(typeof(ParticipantGump)); - public Participant Participant { get; } + int count = p.Players.Length; - public string Center( string text ) - { - return $"
{text}
"; - } + if (count < 4) + count = 4; - public void AddGoldenButton( int x, int y, int bid ) - { - AddButton( x , y , 0xD2, 0xD2, bid, GumpButtonType.Reply, 0 ); - AddButton( x+3, y+3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0 ); - } + AddPage(0); - public void AddGoldenButtonLabeled( int x, int y, int bid, string text ) - { - AddGoldenButton( x, y, bid ); - AddHtml( x + 25, y, 200, 20, text, false, false ); - } + int height = 35 + 10 + 22 + 22 + 30 + 22 + 2 + count * 22 + 2 + 30; - public ParticipantGump( Mobile from, DuelContext context, Participant p ) : base( 50, 50 ) - { - From = from; - Context = context; - Participant = p; + AddBackground(0, 0, 300, height, 9250); + AddBackground(10, 10, 280, height - 20, 0xDAC); - from.CloseGump( typeof( RulesetGump ) ); - from.CloseGump( typeof( DuelContextGump ) ); - from.CloseGump( typeof( ParticipantGump ) ); + AddButton(240, 25, 0xFB1, 0xFB3, 3, GumpButtonType.Reply, 0); - int count = p.Players.Length; + //AddButton( 223, 54, 0x265A, 0x265A, 4, GumpButtonType.Reply, 0 ); - if ( count < 4 ) - count = 4; + AddHtml(35, 25, 230, 20, Center("Participant Setup"), false, false); - AddPage( 0 ); + int x = 35; + int y = 47; - int height = 35 + 10 + 22 + 22 + 30 + 22 + 2 + (count * 22) + 2 + 30; + AddHtml(x, y, 200, 20, $"Team Size: {p.Players.Length}", false, false); + y += 22; - AddBackground( 0, 0, 300, height, 9250 ); - AddBackground( 10, 10, 280, height - 20, 0xDAC ); + AddGoldenButtonLabeled(x + 20, y, 1, "Increase"); + y += 22; + AddGoldenButtonLabeled(x + 20, y, 2, "Decrease"); + y += 30; - AddButton( 240, 25, 0xFB1, 0xFB3, 3, GumpButtonType.Reply, 0 ); + AddHtml(35, y, 230, 20, Center("Players"), false, false); + y += 22; - //AddButton( 223, 54, 0x265A, 0x265A, 4, GumpButtonType.Reply, 0 ); + for (int i = 0; i < p.Players.Length; ++i) + { + DuelPlayer pl = p.Players[i]; - AddHtml( 35, 25, 230, 20, Center( "Participant Setup" ), false, false ); + AddGoldenButtonLabeled(x, y, 5 + i, $"{1 + i}: {(pl == null ? "Empty" : pl.Mobile.Name)}"); + y += 22; + } + } - int x = 35; - int y = 47; + public Mobile From{ get; } - AddHtml( x, y, 200, 20, $"Team Size: {p.Players.Length}", false, false ); y += 22; + public DuelContext Context{ get; } - AddGoldenButtonLabeled( x + 20, y, 1, "Increase" ); y += 22; - AddGoldenButtonLabeled( x + 20, y, 2, "Decrease" ); y += 30; + public Participant Participant{ get; } - AddHtml( 35, y, 230, 20, Center( "Players" ), false, false ); y += 22; + public string Center(string text) + { + return $"
{text}
"; + } - for ( int i = 0; i < p.Players.Length; ++i ) - { - DuelPlayer pl = p.Players[i]; + public void AddGoldenButton(int x, int y, int bid) + { + AddButton(x, y, 0xD2, 0xD2, bid, GumpButtonType.Reply, 0); + AddButton(x + 3, y + 3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0); + } - AddGoldenButtonLabeled( x, y, 5 + i, $"{1 + i}: {(pl == null ? "Empty" : pl.Mobile.Name)}"); y += 22; - } - } + public void AddGoldenButtonLabeled(int x, int y, int bid, string text) + { + AddGoldenButton(x, y, bid); + AddHtml(x + 25, y, 200, 20, text, false, false); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !Context.Registered ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!Context.Registered) + return; - int bid = info.ButtonID; + int bid = info.ButtonID; - if ( bid == 0 ) - { - From.SendGump( new DuelContextGump( From, Context ) ); - } - else if ( bid == 1 ) - { - if ( Participant.Count < 8 ) - Participant.Resize( Participant.Count + 1 ); - else - From.SendMessage( "You may not raise the team size any further." ); + if (bid == 0) + { + From.SendGump(new DuelContextGump(From, Context)); + } + else if (bid == 1) + { + if (Participant.Count < 8) + Participant.Resize(Participant.Count + 1); + else + From.SendMessage("You may not raise the team size any further."); - From.SendGump( new ParticipantGump( From, Context, Participant ) ); - } - else if ( bid == 2 ) - { - if ( Participant.Count > 1 && Participant.Count > Participant.FilledSlots ) - Participant.Resize( Participant.Count - 1 ); - else - From.SendMessage( "You may not lower the team size any further." ); + From.SendGump(new ParticipantGump(From, Context, Participant)); + } + else if (bid == 2) + { + if (Participant.Count > 1 && Participant.Count > Participant.FilledSlots) + Participant.Resize(Participant.Count - 1); + else + From.SendMessage("You may not lower the team size any further."); - From.SendGump( new ParticipantGump( From, Context, Participant ) ); - } - else if ( bid == 3 ) - { - if ( Participant.FilledSlots > 0 ) - { - From.SendMessage( "There is at least one currently active player. You must remove them first." ); - From.SendGump( new ParticipantGump( From, Context, Participant ) ); - } - else if ( Context.Participants.Count > 2 ) - { - /*Container cont = m_Participant.Stakes; + From.SendGump(new ParticipantGump(From, Context, Participant)); + } + else if (bid == 3) + { + if (Participant.FilledSlots > 0) + { + From.SendMessage("There is at least one currently active player. You must remove them first."); + From.SendGump(new ParticipantGump(From, Context, Participant)); + } + else if (Context.Participants.Count > 2) + { + /*Container cont = m_Participant.Stakes; - if ( cont != null ) - cont.Delete();*/ + if ( cont != null ) + cont.Delete();*/ - Context.Participants.Remove( Participant ); - From.SendGump( new DuelContextGump( From, Context ) ); - } - else - { - From.SendMessage( "Duels must have at least two participating parties." ); - From.SendGump( new ParticipantGump( From, Context, Participant ) ); - } - } - /*else if ( bid == 4 ) - { - m_From.SendGump( new ParticipantGump( m_From, m_Context, m_Participant ) ); + Context.Participants.Remove(Participant); + From.SendGump(new DuelContextGump(From, Context)); + } + else + { + From.SendMessage("Duels must have at least two participating parties."); + From.SendGump(new ParticipantGump(From, Context, Participant)); + } + } + /*else if ( bid == 4 ) + { + m_From.SendGump( new ParticipantGump( m_From, m_Context, m_Participant ) ); - Container cont = m_Participant.Stakes; + Container cont = m_Participant.Stakes; - if ( cont != null && !cont.Deleted ) - { - cont.DisplayTo( m_From ); + if ( cont != null && !cont.Deleted ) + { + cont.DisplayTo( m_From ); - Item[] checks = cont.FindItemsByType( typeof( BankCheck ) ); + Item[] checks = cont.FindItemsByType( typeof( BankCheck ) ); - int gold = cont.TotalGold; + int gold = cont.TotalGold; - for ( int i = 0; i < checks.Length; ++i ) - gold += ((BankCheck)checks[i]).Worth; + for ( int i = 0; i < checks.Length; ++i ) + gold += ((BankCheck)checks[i]).Worth; - m_From.SendMessage( "This container has {0} item{1} and {2} stone{3}. In gold or check form there is a total of {4:D}gp.", cont.TotalItems, cont.TotalItems==1?"":"s", cont.TotalWeight, cont.TotalWeight==1?"":"s", gold ); - } - }*/ - else - { - bid -= 5; + m_From.SendMessage( "This container has {0} item{1} and {2} stone{3}. In gold or check form there is a total of {4:D}gp.", cont.TotalItems, cont.TotalItems==1?"":"s", cont.TotalWeight, cont.TotalWeight==1?"":"s", gold ); + } + }*/ + else + { + bid -= 5; - if ( bid >= 0 && bid < Participant.Players.Length ) - { - if ( Participant.Players[bid] == null ) - { - From.Target = new ParticipantTarget( Context, Participant, bid ); - From.SendMessage( "Target a player." ); - } - else - { - Participant.Players[bid].Mobile.SendMessage( "You have been removed from the duel." ); + if (bid >= 0 && bid < Participant.Players.Length) + { + if (Participant.Players[bid] == null) + { + From.Target = new ParticipantTarget(Context, Participant, bid); + From.SendMessage("Target a player."); + } + else + { + Participant.Players[bid].Mobile.SendMessage("You have been removed from the duel."); - if ( Participant.Players[bid].Mobile is PlayerMobile ) - ((PlayerMobile)(Participant.Players[bid].Mobile)).DuelPlayer = null; + if (Participant.Players[bid].Mobile is PlayerMobile) + ((PlayerMobile)Participant.Players[bid].Mobile).DuelPlayer = null; - Participant.Players[bid] = null; - From.SendMessage( "They have been removed from the duel." ); - From.SendGump( new ParticipantGump( From, Context, Participant ) ); - } - } - } - } + Participant.Players[bid] = null; + From.SendMessage("They have been removed from the duel."); + From.SendGump(new ParticipantGump(From, Context, Participant)); + } + } + } + } - private class ParticipantTarget : Target - { - private DuelContext m_Context; - private Participant m_Participant; - private int m_Index; + private class ParticipantTarget : Target + { + private DuelContext m_Context; + private int m_Index; + private Participant m_Participant; - public ParticipantTarget( DuelContext context, Participant p, int index ) : base( 12, false, TargetFlags.None ) - { - m_Context = context; - m_Participant = p; - m_Index = index; - } + public ParticipantTarget(DuelContext context, Participant p, int index) : base(12, false, TargetFlags.None) + { + m_Context = context; + m_Participant = p; + m_Index = index; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Context.Registered ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Context.Registered) + return; - int index = m_Index; + int index = m_Index; - if ( index < 0 || index >= m_Participant.Players.Length ) - return; + if (index < 0 || index >= m_Participant.Players.Length) + return; - if ( !(targeted is Mobile mob) ) - { - from.SendMessage( "That is not a player." ); - } - else if ( !mob.Player ) - { - if ( mob.Body.IsHuman ) - mob.SayTo( from, 1005443 ); // Nay, I would rather stay here and watch a nail rust. - else - mob.SayTo( from, 1005444 ); // The creature ignores your offer. - } - else if ( AcceptDuelGump.IsIgnored( mob, from ) || mob.Blessed ) - { - from.SendMessage( "They ignore your offer." ); - } - else - { - if ( !(mob is PlayerMobile pm) ) - return; + if (!(targeted is Mobile mob)) + { + from.SendMessage("That is not a player."); + } + else if (!mob.Player) + { + if (mob.Body.IsHuman) + mob.SayTo(from, 1005443); // Nay, I would rather stay here and watch a nail rust. + else + mob.SayTo(from, 1005444); // The creature ignores your offer. + } + else if (AcceptDuelGump.IsIgnored(mob, from) || mob.Blessed) + { + from.SendMessage("They ignore your offer."); + } + else + { + if (!(mob is PlayerMobile pm)) + return; - if ( pm.DuelContext != null ) - from.SendMessage( "{0} cannot fight because they are already assigned to another duel.", pm.Name ); - else if ( DuelContext.CheckCombat( pm ) ) - from.SendMessage( "{0} cannot fight because they have recently been in combat with another player.", pm.Name ); - else if ( mob.HasGump( typeof( AcceptDuelGump ) ) ) - from.SendMessage( "{0} has already been offered a duel." ); - else - { - from.SendMessage( "You send {0} to {1}.", m_Participant.Find( from ) == null ? "a challenge" : "an invitation", mob.Name ); - mob.SendGump( new AcceptDuelGump( from, mob, m_Context, m_Participant, m_Index ) ); - } - } - } + if (pm.DuelContext != null) + { + from.SendMessage("{0} cannot fight because they are already assigned to another duel.", pm.Name); + } + else if (DuelContext.CheckCombat(pm)) + { + from.SendMessage("{0} cannot fight because they have recently been in combat with another player.", + pm.Name); + } + else if (mob.HasGump(typeof(AcceptDuelGump))) + { + from.SendMessage("{0} has already been offered a duel."); + } + else + { + from.SendMessage("You send {0} to {1}.", + m_Participant.Find(from) == null ? "a challenge" : "an invitation", mob.Name); + mob.SendGump(new AcceptDuelGump(from, mob, m_Context, m_Participant, m_Index)); + } + } + } - protected override void OnTargetFinish( Mobile from ) - { - from.SendGump( new ParticipantGump( from, m_Context, m_Participant ) ); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + from.SendGump(new ParticipantGump(from, m_Context, m_Participant)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/PickRulesetGump.cs b/Scripts/Engines/ConPVP/PickRulesetGump.cs index 0f9def900..cd32ba582 100644 --- a/Scripts/Engines/ConPVP/PickRulesetGump.cs +++ b/Scripts/Engines/ConPVP/PickRulesetGump.cs @@ -1,127 +1,126 @@ -using System; using Server.Gumps; using Server.Network; namespace Server.Engines.ConPVP { - public class PickRulesetGump : Gump - { - private Mobile m_From; - private DuelContext m_Context; - private Ruleset m_Ruleset; - private Ruleset[] m_Defaults; - private Ruleset[] m_Flavors; + public class PickRulesetGump : Gump + { + private DuelContext m_Context; + private Ruleset[] m_Defaults; + private Ruleset[] m_Flavors; + private Mobile m_From; + private Ruleset m_Ruleset; - public string Center( string text ) - { - return $"
{text}
"; - } + public PickRulesetGump(Mobile from, DuelContext context, Ruleset ruleset) : base(50, 50) + { + m_From = from; + m_Context = context; + m_Ruleset = ruleset; + m_Defaults = ruleset.Layout.Defaults; + m_Flavors = ruleset.Layout.Flavors; - public PickRulesetGump( Mobile from, DuelContext context, Ruleset ruleset ) : base( 50, 50 ) - { - m_From = from; - m_Context = context; - m_Ruleset = ruleset; - m_Defaults = ruleset.Layout.Defaults; - m_Flavors = ruleset.Layout.Flavors; + int height = 25 + 20 + (m_Defaults.Length + 1) * 22 + 6 + 20 + m_Flavors.Length * 22 + 25; - int height = 25 + 20 + ((m_Defaults.Length + 1) * 22) + 6 + 20 + (m_Flavors.Length * 22) + 25; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 260, height, 9250); + AddBackground(10, 10, 240, height - 20, 0xDAC); - AddBackground( 0, 0, 260, height, 9250 ); - AddBackground( 10, 10, 240, height - 20, 0xDAC ); + AddHtml(35, 25, 190, 20, Center("Rules"), false, false); - AddHtml( 35, 25, 190, 20, Center( "Rules" ), false, false ); + int y = 25 + 20; - int y = 25 + 20; + for (int i = 0; i < m_Defaults.Length; ++i) + { + Ruleset cur = m_Defaults[i]; - for ( int i = 0; i < m_Defaults.Length; ++i ) - { - Ruleset cur = m_Defaults[i]; + AddHtml(35 + 14, y, 176, 20, cur.Title, false, false); - AddHtml( 35 + 14, y, 176, 20, cur.Title, false, false ); + if (ruleset.Base == cur && !ruleset.Changed) + AddImage(35, y + 4, 0x939); + else if (ruleset.Base == cur) + AddButton(35, y + 4, 0x93A, 0x939, 2 + i, GumpButtonType.Reply, 0); + else + AddButton(35, y + 4, 0x938, 0x939, 2 + i, GumpButtonType.Reply, 0); - if ( ruleset.Base == cur && !ruleset.Changed ) - AddImage( 35, y + 4, 0x939 ); - else if ( ruleset.Base == cur ) - AddButton( 35, y + 4, 0x93A, 0x939, 2 + i, GumpButtonType.Reply, 0 ); - else - AddButton( 35, y + 4, 0x938, 0x939, 2 + i, GumpButtonType.Reply, 0 ); + y += 22; + } - y += 22; - } + AddHtml(35 + 14, y, 176, 20, "Custom", false, false); + AddButton(35, y + 4, ruleset.Changed ? 0x939 : 0x938, 0x939, 1, GumpButtonType.Reply, 0); - AddHtml( 35 + 14, y, 176, 20, "Custom", false, false ); - AddButton( 35, y + 4, ruleset.Changed ? 0x939 : 0x938, 0x939, 1, GumpButtonType.Reply, 0 ); + y += 22; + y += 6; - y += 22; - y += 6; + AddHtml(35, y, 190, 20, Center("Flavors"), false, false); + y += 20; - AddHtml( 35, y, 190, 20, Center( "Flavors" ), false, false ); - y += 20; + for (int i = 0; i < m_Flavors.Length; ++i) + { + Ruleset cur = m_Flavors[i]; - for ( int i = 0; i < m_Flavors.Length; ++i ) - { - Ruleset cur = m_Flavors[i]; + AddHtml(35 + 14, y, 176, 20, cur.Title, false, false); - AddHtml( 35 + 14, y, 176, 20, cur.Title, false, false ); + if (ruleset.Flavors.Contains(cur)) + AddButton(35, y + 4, 0x939, 0x938, 2 + m_Defaults.Length + i, GumpButtonType.Reply, 0); + else + AddButton(35, y + 4, 0x938, 0x939, 2 + m_Defaults.Length + i, GumpButtonType.Reply, 0); - if ( ruleset.Flavors.Contains( cur ) ) - AddButton( 35, y + 4, 0x939, 0x938, 2 + m_Defaults.Length + i, GumpButtonType.Reply, 0 ); - else - AddButton( 35, y + 4, 0x938, 0x939, 2 + m_Defaults.Length + i, GumpButtonType.Reply, 0 ); + y += 22; + } + } - y += 22; - } - } + public string Center(string text) + { + return $"
{text}
"; + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Context != null && !m_Context.Registered ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Context != null && !m_Context.Registered) + return; - switch ( info.ButtonID ) - { - case 0: // closed - { - if ( m_Context != null ) - m_From.SendGump( new DuelContextGump( m_From, m_Context ) ); + switch (info.ButtonID) + { + case 0: // closed + { + if (m_Context != null) + m_From.SendGump(new DuelContextGump(m_From, m_Context)); - break; - } - case 1: // customize - { - m_From.SendGump( new RulesetGump( m_From, m_Ruleset, m_Ruleset.Layout, m_Context ) ); - break; - } - default: - { - int idx = info.ButtonID - 2; + break; + } + case 1: // customize + { + m_From.SendGump(new RulesetGump(m_From, m_Ruleset, m_Ruleset.Layout, m_Context)); + break; + } + default: + { + int idx = info.ButtonID - 2; - if ( idx >= 0 && idx < m_Defaults.Length ) - { - m_Ruleset.ApplyDefault( m_Defaults[idx] ); - m_From.SendGump( new PickRulesetGump( m_From, m_Context, m_Ruleset ) ); - } - else - { - idx -= m_Defaults.Length; + if (idx >= 0 && idx < m_Defaults.Length) + { + m_Ruleset.ApplyDefault(m_Defaults[idx]); + m_From.SendGump(new PickRulesetGump(m_From, m_Context, m_Ruleset)); + } + else + { + idx -= m_Defaults.Length; - if ( idx >= 0 && idx < m_Flavors.Length ) - { - if ( m_Ruleset.Flavors.Contains( m_Flavors[idx] ) ) - m_Ruleset.RemoveFlavor( m_Flavors[idx] ); - else - m_Ruleset.AddFlavor( m_Flavors[idx] ); + if (idx >= 0 && idx < m_Flavors.Length) + { + if (m_Ruleset.Flavors.Contains(m_Flavors[idx])) + m_Ruleset.RemoveFlavor(m_Flavors[idx]); + else + m_Ruleset.AddFlavor(m_Flavors[idx]); - m_From.SendGump( new PickRulesetGump( m_From, m_Context, m_Ruleset ) ); - } - } + m_From.SendGump(new PickRulesetGump(m_From, m_Context, m_Ruleset)); + } + } - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Preferences.cs b/Scripts/Engines/ConPVP/Preferences.cs index 458c95a2a..31bdc45ee 100644 --- a/Scripts/Engines/ConPVP/Preferences.cs +++ b/Scripts/Engines/ConPVP/Preferences.cs @@ -1,4 +1,3 @@ -using System; using System.Collections; using System.Collections.Generic; using Server.Gumps; @@ -6,297 +5,299 @@ using Server.Network; namespace Server.Engines.ConPVP { - public class PreferencesController : Item - { - private Preferences m_Preferences; - - //[CommandProperty( AccessLevel.GameMaster )] - public Preferences Preferences{ get => m_Preferences; - set{} } - - public override string DefaultName => "preferences controller"; - - [Constructible] - public PreferencesController() : base( 0x1B7A ) - { - Visible = false; - Movable = false; - - m_Preferences = new Preferences(); - - if ( Preferences.Instance == null ) - Preferences.Instance = m_Preferences; - else - Delete(); - } - - public override void Delete() - { - if ( Preferences.Instance != m_Preferences ) - base.Delete(); - } - - public PreferencesController( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - m_Preferences.Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Preferences = new Preferences( reader ); - Preferences.Instance = m_Preferences; - break; - } - } - } - } - - public class Preferences - { - private Hashtable m_Table; - - public ArrayList Entries { get; } - - public PreferencesEntry Find( Mobile mob ) - { - PreferencesEntry entry = (PreferencesEntry) m_Table[mob]; + public class PreferencesController : Item + { + private Preferences m_Preferences; + + [Constructible] + public PreferencesController() : base(0x1B7A) + { + Visible = false; + Movable = false; + + m_Preferences = new Preferences(); + + if (Preferences.Instance == null) + Preferences.Instance = m_Preferences; + else + Delete(); + } + + public PreferencesController(Serial serial) : base(serial) + { + } + + //[CommandProperty( AccessLevel.GameMaster )] + public Preferences Preferences + { + get => m_Preferences; + set { } + } + + public override string DefaultName => "preferences controller"; + + public override void Delete() + { + if (Preferences.Instance != m_Preferences) + base.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + m_Preferences.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Preferences = new Preferences(reader); + Preferences.Instance = m_Preferences; + break; + } + } + } + } + + public class Preferences + { + private Hashtable m_Table; + + public Preferences() + { + m_Table = new Hashtable(); + Entries = new ArrayList(); + } + + public Preferences(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 0: + { + int count = reader.ReadEncodedInt(); + + m_Table = new Hashtable(count); + Entries = new ArrayList(count); + + for (int i = 0; i < count; ++i) + { + PreferencesEntry entry = new PreferencesEntry(reader, this, version); + + if (entry.Mobile != null) + { + m_Table[entry.Mobile] = entry; + Entries.Add(entry); + } + } + + break; + } + } + } - if ( entry == null ) - { - m_Table[mob] = entry = new PreferencesEntry( mob, this ); - Entries.Add( entry ); - } - - return entry; - } - - public static Preferences Instance { get; set; } - - public Preferences() - { - m_Table = new Hashtable(); - Entries = new ArrayList(); - } - - public Preferences( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 0: - { - int count = reader.ReadEncodedInt(); + public ArrayList Entries{ get; } - m_Table = new Hashtable( count ); - Entries = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) - { - PreferencesEntry entry = new PreferencesEntry( reader, this, version ); - - if ( entry.Mobile != null ) - { - m_Table[entry.Mobile] = entry; - Entries.Add( entry ); - } - } + public static Preferences Instance{ get; set; } - break; - } - } - } + public PreferencesEntry Find(Mobile mob) + { + PreferencesEntry entry = (PreferencesEntry)m_Table[mob]; - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version; + if (entry == null) + { + m_Table[mob] = entry = new PreferencesEntry(mob, this); + Entries.Add(entry); + } - writer.WriteEncodedInt( (int) Entries.Count ); + return entry; + } - for ( int i = 0; i < Entries.Count; ++i ) - ((PreferencesEntry)Entries[i]).Serialize( writer ); - } - } + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version; - public class PreferencesEntry - { - private Preferences m_Preferences; + writer.WriteEncodedInt(Entries.Count); - public Mobile Mobile { get; } + for (int i = 0; i < Entries.Count; ++i) + ((PreferencesEntry)Entries[i]).Serialize(writer); + } + } - public ArrayList Disliked { get; } + public class PreferencesEntry + { + private Preferences m_Preferences; - public PreferencesEntry( Mobile mob, Preferences prefs ) - { - m_Preferences = prefs; - Mobile = mob; - Disliked = new ArrayList(); - } + public PreferencesEntry(Mobile mob, Preferences prefs) + { + m_Preferences = prefs; + Mobile = mob; + Disliked = new ArrayList(); + } - public PreferencesEntry( GenericReader reader, Preferences prefs, int version ) - { - m_Preferences = prefs; + public PreferencesEntry(GenericReader reader, Preferences prefs, int version) + { + m_Preferences = prefs; - switch ( version ) - { - case 0: - { - Mobile = reader.ReadMobile(); + switch (version) + { + case 0: + { + Mobile = reader.ReadMobile(); - int count = reader.ReadEncodedInt(); + int count = reader.ReadEncodedInt(); - Disliked = new ArrayList( count ); + Disliked = new ArrayList(count); - for ( int i = 0; i < count; ++i ) - Disliked.Add( reader.ReadString() ); + for (int i = 0; i < count; ++i) + Disliked.Add(reader.ReadString()); - break; - } - } - } + break; + } + } + } - public void Serialize( GenericWriter writer ) - { - writer.Write( (Mobile) Mobile ); + public Mobile Mobile{ get; } - writer.WriteEncodedInt( (int) Disliked.Count ); + public ArrayList Disliked{ get; } - for ( int i = 0; i < Disliked.Count; ++i ) - writer.Write( (string) Disliked[i] ); - } - } + public void Serialize(GenericWriter writer) + { + writer.Write(Mobile); - public class PreferencesGump : Gump - { - private Mobile m_From; - private PreferencesEntry m_Entry; + writer.WriteEncodedInt(Disliked.Count); - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Entry == null ) - return; + for (int i = 0; i < Disliked.Count; ++i) + writer.Write((string)Disliked[i]); + } + } - if ( info.ButtonID != 1 ) - return; + public class PreferencesGump : Gump + { + private int m_ColumnX = 12; + private PreferencesEntry m_Entry; + private Mobile m_From; - m_Entry.Disliked.Clear(); + public PreferencesGump(Mobile from, Preferences prefs) : base(50, 50) + { + m_From = from; + m_Entry = prefs.Find(from); - List arenas = Arena.Arenas; + if (m_Entry == null) + return; - for ( int i = 0; i < info.Switches.Length; ++i ) - { - int idx = info.Switches[i]; + List arenas = Arena.Arenas; - if ( idx >= 0 && idx < arenas.Count ) - m_Entry.Disliked.Add( arenas[idx].Name ); - } - } + AddPage(0); - public PreferencesGump( Mobile from, Preferences prefs ) : base( 50, 50 ) - { - m_From = from; - m_Entry = prefs.Find( from ); + int height = 12 + 20 + arenas.Count * 31 + 24 + 12; - if ( m_Entry == null ) - return; + AddBackground(0, 0, 499 + 40 - 365, height, 0x2436); - List arenas = Arena.Arenas; + for (int i = 1; i < arenas.Count; i += 2) + AddImageTiled(12, 32 + i * 31, 475 + 40 - 365, 30, 0x2430); - AddPage( 0 ); + AddAlphaRegion(10, 10, 479 + 40 - 365, height - 20); - int height = 12 + 20 + (arenas.Count * 31) + 24 + 12; + AddColumnHeader(35, null); + AddColumnHeader(115, "Arena"); - AddBackground( 0, 0, 499+40-365, height, 0x2436 ); + AddButton(499 + 40 - 365 - 12 - 63 - 4 - 63, height - 12 - 24, 247, 248, 1, GumpButtonType.Reply, 0); + AddButton(499 + 40 - 365 - 12 - 63, height - 12 - 24, 241, 242, 2, GumpButtonType.Reply, 0); - for ( int i = 1; i < arenas.Count; i += 2 ) - AddImageTiled( 12, 32 + (i * 31), 475+40-365, 30, 0x2430 ); + for (int i = 0; i < arenas.Count; ++i) + { + Arena ar = arenas[i]; - AddAlphaRegion( 10, 10, 479+40-365, height - 20 ); + string name = ar.Name; - AddColumnHeader( 35, null ); - AddColumnHeader( 115, "Arena" ); + if (name == null) + name = "(no name)"; - AddButton( 499+40-365 - 12 - 63 - 4 - 63, height - 12 - 24, 247, 248, 1, GumpButtonType.Reply, 0 ); - AddButton( 499+40-365 - 12 - 63, height - 12 - 24, 241, 242, 2, GumpButtonType.Reply, 0 ); + int x = 12; + int y = 32 + i * 31; - for ( int i = 0; i < arenas.Count; ++i ) - { - Arena ar = arenas[i]; + int color = 0xCCFFCC; - string name = ar.Name; + AddCheck(x + 3, y + 1, 9730, 9727, m_Entry.Disliked.Contains(name), i); + x += 35; - if ( name == null ) - name = "(no name)"; + AddBorderedText(x + 5, y + 5, 115 - 5, name, color, 0); + x += 115; + } + } - int x = 12; - int y = 32 + (i * 31); + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Entry == null) + return; - int color = 0xCCFFCC; + if (info.ButtonID != 1) + return; - AddCheck( x + 3, y + 1, 9730, 9727, m_Entry.Disliked.Contains(name), i ); - x += 35; + m_Entry.Disliked.Clear(); - AddBorderedText( x + 5, y + 5, 115 - 5, name, color, 0 ); - x += 115; - } - } + List arenas = Arena.Arenas; - public string Center( string text ) - { - return $"
{text}
"; - } + for (int i = 0; i < info.Switches.Length; ++i) + { + int idx = info.Switches[i]; - public string Color( string text, int color ) - { - return $"{text}"; - } + if (idx >= 0 && idx < arenas.Count) + m_Entry.Disliked.Add(arenas[idx].Name); + } + } - private void AddBorderedText( int x, int y, int width, string text, int color, int borderColor ) - { - /*AddColoredText( x - 1, y, width, text, borderColor ); - AddColoredText( x + 1, y, width, text, borderColor ); - AddColoredText( x, y - 1, width, text, borderColor ); - AddColoredText( x, y + 1, width, text, borderColor );*/ - /*AddColoredText( x - 1, y - 1, width, text, borderColor ); - AddColoredText( x + 1, y + 1, width, text, borderColor );*/ - AddColoredText( x, y, width, text, color ); - } + public string Center(string text) + { + return $"
{text}
"; + } - private void AddColoredText( int x, int y, int width, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, 20, text, false, false ); - else - AddHtml( x, y, width, 20, Color( text, color ), false, false ); - } + public string Color(string text, int color) + { + return $"{text}"; + } - private int m_ColumnX = 12; + private void AddBorderedText(int x, int y, int width, string text, int color, int borderColor) + { + /*AddColoredText( x - 1, y, width, text, borderColor ); + AddColoredText( x + 1, y, width, text, borderColor ); + AddColoredText( x, y - 1, width, text, borderColor ); + AddColoredText( x, y + 1, width, text, borderColor );*/ + /*AddColoredText( x - 1, y - 1, width, text, borderColor ); + AddColoredText( x + 1, y + 1, width, text, borderColor );*/ + AddColoredText(x, y, width, text, color); + } - private void AddColumnHeader( int width, string name ) - { - AddBackground( m_ColumnX, 12, width, 20, 0x242C ); - AddImageTiled( m_ColumnX + 2, 14, width - 4, 16, 0x2430 ); + private void AddColoredText(int x, int y, int width, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, 20, text, false, false); + else + AddHtml(x, y, width, 20, Color(text, color), false, false); + } - if ( name != null ) - AddBorderedText( m_ColumnX, 13, width, Center( name ), 0xFFFFFF, 0 ); + private void AddColumnHeader(int width, string name) + { + AddBackground(m_ColumnX, 12, width, 20, 0x242C); + AddImageTiled(m_ColumnX + 2, 14, width - 4, 16, 0x2430); - m_ColumnX += width; - } - } + if (name != null) + AddBorderedText(m_ColumnX, 13, width, Center(name), 0xFFFFFF, 0); + + m_ColumnX += width; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/ReadyGump.cs b/Scripts/Engines/ConPVP/ReadyGump.cs index 9b0f775a9..3853f0f18 100644 --- a/Scripts/Engines/ConPVP/ReadyGump.cs +++ b/Scripts/Engines/ConPVP/ReadyGump.cs @@ -1,110 +1,109 @@ -using System; using System.Collections; using Server.Gumps; using Server.Network; namespace Server.Engines.ConPVP { - public class ReadyGump : Gump - { - private Mobile m_From; - private DuelContext m_Context; - private int m_Count; + public class ReadyGump : Gump + { + private DuelContext m_Context; + private int m_Count; + private Mobile m_From; - public string Center( string text ) - { - return $"
{text}
"; - } + public ReadyGump(Mobile from, DuelContext context, int count) : base(50, 50) + { + m_From = from; + m_Context = context; + m_Count = count; - public ReadyGump( Mobile from, DuelContext context, int count ) : base( 50, 50 ) - { - m_From = from; - m_Context = context; - m_Count = count; + ArrayList parts = context.Participants; - ArrayList parts = context.Participants; + int height = 25 + 20; - int height = 25 + 20; + for (int i = 0; i < parts.Count; ++i) + { + Participant p = (Participant)parts[i]; - for ( int i = 0; i < parts.Count; ++i ) - { - Participant p = (Participant)parts[i]; + height += 4; - height += 4; + if (p.Players.Length > 1) + height += 22; - if ( p.Players.Length > 1 ) - height += 22; + height += p.Players.Length * 22; + } - height += (p.Players.Length * 22); - } + height += 25; - height += 25; + Closable = false; + Dragable = false; - Closable = false; - Dragable = false; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 260, height, 9250); + AddBackground(10, 10, 240, height - 20, 0xDAC); - AddBackground( 0, 0, 260, height, 9250 ); - AddBackground( 10, 10, 240, height - 20, 0xDAC ); + if (count == -1) + { + AddHtml(35, 25, 190, 20, Center("Ready"), false, false); + } + else + { + AddHtml(35, 25, 190, 20, Center("Starting"), false, false); + AddHtml(35, 25, 190, 20, "
" + count, false, false); + } - if ( count == -1 ) - { - AddHtml( 35, 25, 190, 20, Center( "Ready" ), false, false ); - } - else - { - AddHtml( 35, 25, 190, 20, Center( "Starting" ), false, false ); - AddHtml( 35, 25, 190, 20, "
" + count.ToString(), false, false ); - } + int y = 25 + 20; - int y = 25 + 20; + for (int i = 0; i < parts.Count; ++i) + { + Participant p = (Participant)parts[i]; - for ( int i = 0; i < parts.Count; ++i ) - { - Participant p = (Participant)parts[i]; + y += 4; - y += 4; + bool isAllReady = true; + int yStore = y; + int offset = 0; - bool isAllReady = true; - int yStore = y; - int offset = 0; + if (p.Players.Length > 1) + { + AddHtml(35 + 14, y, 176, 20, $"Participant #{i + 1}", false, false); + y += 22; + offset = 10; + } - if ( p.Players.Length > 1 ) - { - AddHtml( 35 + 14, y, 176, 20, $"Participant #{i + 1}", false, false ); - y += 22; - offset = 10; - } + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + if (pl != null && pl.Ready) + { + AddImage(35 + offset, y + 4, 0x939); + } + else + { + AddImage(35 + offset, y + 4, 0x938); + isAllReady = false; + } - if ( pl != null && pl.Ready ) - { - AddImage( 35 + offset, y + 4, 0x939 ); - } - else - { - AddImage( 35 + offset, y + 4, 0x938 ); - isAllReady = false; - } + string name = pl == null ? "(Empty)" : pl.Mobile.Name; - string name = ( pl == null ? "(Empty)" : pl.Mobile.Name ); + AddHtml(35 + offset + 14, y, 166, 20, name, false, false); - AddHtml( 35 + offset + 14, y, 166, 20, name, false, false ); + y += 22; + } - y += 22; - } + if (p.Players.Length > 1) + AddImage(35, yStore + 4, isAllReady ? 0x939 : 0x938); + } + } - if ( p.Players.Length > 1 ) - AddImage( 35, yStore + 4, isAllReady ? 0x939 : 0x938 ); - } - } + public string Center(string text) + { + return $"
{text}
"; + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/ReadyUpGump.cs b/Scripts/Engines/ConPVP/ReadyUpGump.cs index 86cd9835c..fc522ef4d 100644 --- a/Scripts/Engines/ConPVP/ReadyUpGump.cs +++ b/Scripts/Engines/ConPVP/ReadyUpGump.cs @@ -1,233 +1,232 @@ -using System; using System.Collections; using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Engines.ConPVP { - public class ReadyUpGump : Gump - { - private Mobile m_From; - private DuelContext m_Context; + public class ReadyUpGump : Gump + { + private DuelContext m_Context; + private Mobile m_From; - public string Center( string text ) - { - return $"
{text}
"; - } + public ReadyUpGump(Mobile from, DuelContext context) : base(50, 50) + { + m_From = from; + m_Context = context; - public void AddGoldenButton( int x, int y, int bid ) - { - AddButton( x , y , 0xD2, 0xD2, bid, GumpButtonType.Reply, 0 ); - AddButton( x+3, y+3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0 ); - } + Closable = false; + AddPage(0); - public ReadyUpGump( Mobile from, DuelContext context ) : base( 50, 50 ) - { - m_From = from; - m_Context = context; + if (context.Rematch) + { + int height = 25 + 20 + 10 + 22 + 25; - Closable = false; - AddPage( 0 ); + AddBackground(0, 0, 210, height, 9250); + AddBackground(10, 10, 190, height - 20, 0xDAC); - if ( context.Rematch ) - { - int height = 25 + 20 + 10 + 22 + 25; + AddHtml(35, 25, 140, 20, Center("Rematch?"), false, false); - AddBackground( 0, 0, 210, height, 9250 ); - AddBackground( 10, 10, 190, height - 20, 0xDAC ); + AddButton(35, 55, 247, 248, 1, GumpButtonType.Reply, 0); + AddButton(115, 55, 242, 241, 2, GumpButtonType.Reply, 0); + } + else + { + #region Participants - AddHtml( 35, 25, 140, 20, Center( "Rematch?" ), false, false ); + AddPage(1); - AddButton( 35, 55, 247, 248, 1, GumpButtonType.Reply, 0 ); - AddButton( 115, 55, 242, 241, 2, GumpButtonType.Reply, 0 ); - } - else - { - #region Participants - AddPage( 1 ); + ArrayList parts = context.Participants; - ArrayList parts = context.Participants; + int height = 25 + 20; - int height = 25 + 20; + for (int i = 0; i < parts.Count; ++i) + { + Participant p = (Participant)parts[i]; - for ( int i = 0; i < parts.Count; ++i ) - { - Participant p = (Participant)parts[i]; + height += 4; - height += 4; + if (p.Players.Length > 1) + height += 22; - if ( p.Players.Length > 1 ) - height += 22; + height += p.Players.Length * 22; + } - height += (p.Players.Length * 22); - } + height += 10 + 22 + 25; - height += 10 + 22 + 25; + AddBackground(0, 0, 260, height, 9250); + AddBackground(10, 10, 240, height - 20, 0xDAC); - AddBackground( 0, 0, 260, height, 9250 ); - AddBackground( 10, 10, 240, height - 20, 0xDAC ); + AddHtml(35, 25, 190, 20, Center("Participants"), false, false); - AddHtml( 35, 25, 190, 20, Center( "Participants" ), false, false ); + int y = 20 + 25; - int y = 20 + 25; + for (int i = 0; i < parts.Count; ++i) + { + Participant p = (Participant)parts[i]; - for ( int i = 0; i < parts.Count; ++i ) - { - Participant p = (Participant)parts[i]; + y += 4; - y += 4; + int offset = 0; - int offset = 0; + if (p.Players.Length > 1) + { + AddHtml(35, y, 176, 20, $"Team #{i + 1}", false, false); + y += 22; + offset = 10; + } - if ( p.Players.Length > 1 ) - { - AddHtml( 35, y, 176, 20, $"Team #{i + 1}", false, false ); - y += 22; - offset = 10; - } + for (int j = 0; j < p.Players.Length; ++j) + { + DuelPlayer pl = p.Players[j]; - for ( int j = 0; j < p.Players.Length; ++j ) - { - DuelPlayer pl = p.Players[j]; + string name = pl == null ? "(Empty)" : pl.Mobile.Name; - string name = ( pl == null ? "(Empty)" : pl.Mobile.Name ); + AddHtml(35 + offset, y, 166, 20, name, false, false); - AddHtml( 35 + offset, y, 166, 20, name, false, false ); + y += 22; + } + } - y += 22; - } - } + y += 8; - y += 8; + AddHtml(35, y, 176, 20, "Continue?", false, false); - AddHtml( 35, y, 176, 20, "Continue?", false, false ); + y -= 2; - y -= 2; + AddButton(102, y, 247, 248, 0, GumpButtonType.Page, 2); + AddButton(169, y, 242, 241, 2, GumpButtonType.Reply, 0); - AddButton( 102, y, 247, 248, 0, GumpButtonType.Page, 2 ); - AddButton( 169, y, 242, 241, 2, GumpButtonType.Reply, 0 ); - #endregion + #endregion - #region Rules - AddPage( 2 ); + #region Rules - Ruleset ruleset = context.Ruleset; - Ruleset basedef = ruleset.Base; + AddPage(2); - height = 25 + 20 + 5 + 20 + 20 + 4; + Ruleset ruleset = context.Ruleset; + Ruleset basedef = ruleset.Base; - int changes = 0; + height = 25 + 20 + 5 + 20 + 20 + 4; - BitArray defs; + int changes = 0; - if ( ruleset.Flavors.Count > 0 ) - { - defs = new BitArray( basedef.Options ); + BitArray defs; - for ( int i = 0; i < ruleset.Flavors.Count; ++i ) - defs.Or( ((Ruleset)ruleset.Flavors[i]).Options ); + if (ruleset.Flavors.Count > 0) + { + defs = new BitArray(basedef.Options); - height += ruleset.Flavors.Count * 18; - } - else - { - defs = basedef.Options; - } + for (int i = 0; i < ruleset.Flavors.Count; ++i) + defs.Or(((Ruleset)ruleset.Flavors[i]).Options); - BitArray opts = ruleset.Options; + height += ruleset.Flavors.Count * 18; + } + else + { + defs = basedef.Options; + } - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - ++changes; - } + BitArray opts = ruleset.Options; - height += (changes * 22); + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + ++changes; - height += 10 + 22 + 25; + height += changes * 22; - AddBackground( 0, 0, 260, height, 9250 ); - AddBackground( 10, 10, 240, height - 20, 0xDAC ); + height += 10 + 22 + 25; - AddHtml( 35, 25, 190, 20, Center( "Rules" ), false, false ); + AddBackground(0, 0, 260, height, 9250); + AddBackground(10, 10, 240, height - 20, 0xDAC); - AddHtml( 35, 50, 190, 20, $"Set: {basedef.Title}", false, false ); + AddHtml(35, 25, 190, 20, Center("Rules"), false, false); - y = 70; + AddHtml(35, 50, 190, 20, $"Set: {basedef.Title}", false, false); - for ( int i = 0; i < ruleset.Flavors.Count; ++i, y += 18 ) - AddHtml( 35, y, 190, 20, $" + {((Ruleset) ruleset.Flavors[i]).Title}", false, false ); + y = 70; - y += 4; + for (int i = 0; i < ruleset.Flavors.Count; ++i, y += 18) + AddHtml(35, y, 190, 20, $" + {((Ruleset)ruleset.Flavors[i]).Title}", false, false); - if ( changes > 0 ) - { - AddHtml( 35, y, 190, 20, "Modifications:", false, false ); - y += 20; + y += 4; - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - { - string name = ruleset.Layout.FindByIndex( i ); + if (changes > 0) + { + AddHtml(35, y, 190, 20, "Modifications:", false, false); + y += 20; - if ( name != null ) // sanity - { - AddImage( 35, y, opts[i] ? 0xD3 : 0xD2 ); - AddHtml( 60, y, 165, 22, name, false, false ); - } + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + { + string name = ruleset.Layout.FindByIndex(i); - y += 22; - } - } - } - else - { - AddHtml( 35, y, 190, 20, "Modifications: None", false, false ); - y += 20; - } + if (name != null) // sanity + { + AddImage(35, y, opts[i] ? 0xD3 : 0xD2); + AddHtml(60, y, 165, 22, name, false, false); + } - y += 8; + y += 22; + } + } + else + { + AddHtml(35, y, 190, 20, "Modifications: None", false, false); + y += 20; + } - AddHtml( 35, y, 176, 20, "Continue?", false, false ); + y += 8; - y -= 2; + AddHtml(35, y, 176, 20, "Continue?", false, false); - AddButton( 102, y, 247, 248, 1, GumpButtonType.Reply, 0 ); - AddButton( 169, y, 242, 241, 3, GumpButtonType.Reply, 0 ); - #endregion - } - } + y -= 2; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !m_Context.Registered || !m_Context.ReadyWait ) - return; + AddButton(102, y, 247, 248, 1, GumpButtonType.Reply, 0); + AddButton(169, y, 242, 241, 3, GumpButtonType.Reply, 0); - switch ( info.ButtonID ) - { - case 1: // okay - { - if ( !(m_From is PlayerMobile pm) ) - break; + #endregion + } + } - pm.DuelPlayer.Ready = true; - m_Context.SendReadyGump(); + public string Center(string text) + { + return $"
{text}
"; + } - break; - } - case 2: // reject participants - { - m_Context.RejectReady( m_From, "participants" ); - break; - } - case 3: // reject rules - { - m_Context.RejectReady( m_From, "rules" ); - break; - } - } - } - } -} + public void AddGoldenButton(int x, int y, int bid) + { + AddButton(x, y, 0xD2, 0xD2, bid, GumpButtonType.Reply, 0); + AddButton(x + 3, y + 3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_Context.Registered || !m_Context.ReadyWait) + return; + + switch (info.ButtonID) + { + case 1: // okay + { + if (!(m_From is PlayerMobile pm)) + break; + + pm.DuelPlayer.Ready = true; + m_Context.SendReadyGump(); + + break; + } + case 2: // reject participants + { + m_Context.RejectReady(m_From, "participants"); + break; + } + case 3: // reject rules + { + m_Context.RejectReady(m_From, "rules"); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Ruleset.cs b/Scripts/Engines/ConPVP/Ruleset.cs index a7241d06d..ba25e7a5b 100644 --- a/Scripts/Engines/ConPVP/Ruleset.cs +++ b/Scripts/Engines/ConPVP/Ruleset.cs @@ -2,100 +2,100 @@ using System.Collections; namespace Server.Engines.ConPVP { - public class Ruleset - { - public RulesetLayout Layout { get; } + public class Ruleset + { + public Ruleset(RulesetLayout layout) + { + Layout = layout; + Options = new BitArray(layout.TotalLength); + } - public BitArray Options { get; private set; } + public RulesetLayout Layout{ get; } - public string Title { get; set; } + public BitArray Options{ get; private set; } - public Ruleset Base { get; private set; } + public string Title{ get; set; } - public ArrayList Flavors { get; } = new ArrayList(); + public Ruleset Base{ get; private set; } - public bool Changed { get; set; } + public ArrayList Flavors{ get; } = new ArrayList(); - public void ApplyDefault( Ruleset newDefault ) - { - Base = newDefault; - Changed = false; + public bool Changed{ get; set; } - Options = new BitArray( newDefault.Options ); + public void ApplyDefault(Ruleset newDefault) + { + Base = newDefault; + Changed = false; - ApplyFlavorsTo( this ); - } + Options = new BitArray(newDefault.Options); - public void ApplyFlavorsTo( Ruleset ruleset ) - { - for ( int i = 0; i < Flavors.Count; ++i ) - { - Ruleset flavor = (Ruleset)Flavors[i]; + ApplyFlavorsTo(this); + } - Options.Or( flavor.Options ); - } - } + public void ApplyFlavorsTo(Ruleset ruleset) + { + for (int i = 0; i < Flavors.Count; ++i) + { + Ruleset flavor = (Ruleset)Flavors[i]; - public void AddFlavor( Ruleset flavor ) - { - if ( Flavors.Contains( flavor ) ) - return; + Options.Or(flavor.Options); + } + } - Flavors.Add( flavor ); - Options.Or( flavor.Options ); - } + public void AddFlavor(Ruleset flavor) + { + if (Flavors.Contains(flavor)) + return; - public void RemoveFlavor( Ruleset flavor ) - { - if ( !Flavors.Contains( flavor ) ) - return; + Flavors.Add(flavor); + Options.Or(flavor.Options); + } - Flavors.Remove( flavor ); - Options.And( flavor.Options.Not() ); - flavor.Options.Not(); - } + public void RemoveFlavor(Ruleset flavor) + { + if (!Flavors.Contains(flavor)) + return; - public void SetOptionRange( string title, bool value ) - { - RulesetLayout layout = Layout.FindByTitle( title ); + Flavors.Remove(flavor); + Options.And(flavor.Options.Not()); + flavor.Options.Not(); + } - if ( layout == null ) - return; + public void SetOptionRange(string title, bool value) + { + RulesetLayout layout = Layout.FindByTitle(title); - for ( int i = 0; i < layout.TotalLength; ++i ) - Options[i + layout.Offset] = value; + if (layout == null) + return; - Changed = true; - } + for (int i = 0; i < layout.TotalLength; ++i) + Options[i + layout.Offset] = value; - public bool GetOption( string title, string option ) - { - int index = 0; - RulesetLayout layout = Layout.FindByOption( title, option, ref index ); + Changed = true; + } - if ( layout == null ) - return true; + public bool GetOption(string title, string option) + { + int index = 0; + RulesetLayout layout = Layout.FindByOption(title, option, ref index); - return Options[layout.Offset + index]; - } + if (layout == null) + return true; - public void SetOption( string title, string option, bool value ) - { - int index = 0; - RulesetLayout layout = Layout.FindByOption( title, option, ref index ); + return Options[layout.Offset + index]; + } - if ( layout == null ) - return; + public void SetOption(string title, string option, bool value) + { + int index = 0; + RulesetLayout layout = Layout.FindByOption(title, option, ref index); - Options[layout.Offset + index] = value; + if (layout == null) + return; - Changed = true; - } + Options[layout.Offset + index] = value; - public Ruleset( RulesetLayout layout ) - { - Layout = layout; - Options = new BitArray( layout.TotalLength ); - } - } + Changed = true; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/RulesetGump.cs b/Scripts/Engines/ConPVP/RulesetGump.cs index 142f34494..74f893424 100644 --- a/Scripts/Engines/ConPVP/RulesetGump.cs +++ b/Scripts/Engines/ConPVP/RulesetGump.cs @@ -1,136 +1,135 @@ -using System; using System.Collections; using Server.Gumps; using Server.Network; namespace Server.Engines.ConPVP { - public class RulesetGump : Gump - { - private Mobile m_From; - private Ruleset m_Ruleset; - private RulesetLayout m_Page; - private DuelContext m_DuelContext; - private bool m_ReadOnly; + public class RulesetGump : Gump + { + private DuelContext m_DuelContext; + private Mobile m_From; + private RulesetLayout m_Page; + private bool m_ReadOnly; + private Ruleset m_Ruleset; - public string Center( string text ) - { - return $"
{text}
"; - } + public RulesetGump(Mobile from, Ruleset ruleset, RulesetLayout page, DuelContext duelContext) : this(from, ruleset, + page, duelContext, false) + { + } - public void AddGoldenButton( int x, int y, int bid ) - { - AddButton( x , y , 0xD2, 0xD2, bid, GumpButtonType.Reply, 0 ); - AddButton( x+3, y+3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0 ); - } + public RulesetGump(Mobile from, Ruleset ruleset, RulesetLayout page, DuelContext duelContext, bool readOnly) : base( + readOnly ? 310 : 50, 50) + { + m_From = from; + m_Ruleset = ruleset; + m_Page = page; + m_DuelContext = duelContext; + m_ReadOnly = readOnly; - public RulesetGump( Mobile from, Ruleset ruleset, RulesetLayout page, DuelContext duelContext ) : this( from, ruleset, page, duelContext, false ) - { - } + Dragable = !readOnly; - public RulesetGump( Mobile from, Ruleset ruleset, RulesetLayout page, DuelContext duelContext, bool readOnly ) : base( readOnly ? 310 : 50, 50 ) - { - m_From = from; - m_Ruleset = ruleset; - m_Page = page; - m_DuelContext = duelContext; - m_ReadOnly = readOnly; + from.CloseGump(typeof(RulesetGump)); + from.CloseGump(typeof(DuelContextGump)); + from.CloseGump(typeof(ParticipantGump)); - Dragable = !readOnly; + RulesetLayout depthCounter = page; + int depth = 0; - from.CloseGump( typeof( RulesetGump ) ); - from.CloseGump( typeof( DuelContextGump ) ); - from.CloseGump( typeof( ParticipantGump ) ); + while (depthCounter != null) + { + ++depth; + depthCounter = depthCounter.Parent; + } - RulesetLayout depthCounter = page; - int depth = 0; + int count = page.Children.Length + page.Options.Length; - while ( depthCounter != null ) - { - ++depth; - depthCounter = depthCounter.Parent; - } + AddPage(0); - int count = page.Children.Length + page.Options.Length; + int height = 35 + 10 + 2 + count * 22 + 2 + 30; - AddPage( 0 ); + AddBackground(0, 0, 260, height, 9250); + AddBackground(10, 10, 240, height - 20, 0xDAC); - int height = 35 + 10 + 2 + (count * 22) + 2 + 30; + AddHtml(35, 25, 190, 20, Center(page.Title), false, false); - AddBackground( 0, 0, 260, height, 9250 ); - AddBackground( 10, 10, 240, height - 20, 0xDAC ); + int x = 35; + int y = 47; - AddHtml( 35, 25, 190, 20, Center( page.Title ), false, false ); + for (int i = 0; i < page.Children.Length; ++i) + { + AddGoldenButton(x, y, 1 + i); + AddHtml(x + 25, y, 250, 22, page.Children[i].Title, false, false); - int x = 35; - int y = 47; + y += 22; + } - for ( int i = 0; i < page.Children.Length; ++i ) - { - AddGoldenButton( x, y, 1 + i ); - AddHtml( x + 25, y, 250, 22, page.Children[i].Title, false, false ); + for (int i = 0; i < page.Options.Length; ++i) + { + bool enabled = ruleset.Options[page.Offset + i]; - y += 22; - } + if (readOnly) + AddImage(x, y, enabled ? 0xD3 : 0xD2); + else + AddCheck(x, y, 0xD2, 0xD3, enabled, i); - for ( int i = 0; i < page.Options.Length; ++i ) - { - bool enabled = ruleset.Options[page.Offset + i]; + AddHtml(x + 25, y, 250, 22, page.Options[i], false, false); - if ( readOnly ) - AddImage( x, y, enabled ? 0xD3 : 0xD2 ); - else - AddCheck( x, y, 0xD2, 0xD3, enabled, i ); + y += 22; + } + } - AddHtml( x + 25, y, 250, 22, page.Options[i], false, false ); + public string Center(string text) + { + return $"
{text}
"; + } - y += 22; - } - } + public void AddGoldenButton(int x, int y, int bid) + { + AddButton(x, y, 0xD2, 0xD2, bid, GumpButtonType.Reply, 0); + AddButton(x + 3, y + 3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_DuelContext != null && !m_DuelContext.Registered ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_DuelContext != null && !m_DuelContext.Registered) + return; - if ( !m_ReadOnly ) - { - BitArray opts = new BitArray( m_Page.Options.Length ); + if (!m_ReadOnly) + { + BitArray opts = new BitArray(m_Page.Options.Length); - for ( int i = 0; i < info.Switches.Length; ++i ) - { - int sid = info.Switches[i]; + for (int i = 0; i < info.Switches.Length; ++i) + { + int sid = info.Switches[i]; - if ( sid >= 0 && sid < m_Page.Options.Length ) - opts[sid] = true; - } + if (sid >= 0 && sid < m_Page.Options.Length) + opts[sid] = true; + } - for ( int i = 0; i < opts.Length; ++i ) - { - if ( m_Ruleset.Options[m_Page.Offset + i] != opts[i] ) - { - m_Ruleset.Options[m_Page.Offset + i] = opts[i]; - m_Ruleset.Changed = true; - } - } - } + for (int i = 0; i < opts.Length; ++i) + if (m_Ruleset.Options[m_Page.Offset + i] != opts[i]) + { + m_Ruleset.Options[m_Page.Offset + i] = opts[i]; + m_Ruleset.Changed = true; + } + } - int bid = info.ButtonID; + int bid = info.ButtonID; - if ( bid == 0 ) - { - if ( m_Page.Parent != null ) - m_From.SendGump( new RulesetGump( m_From, m_Ruleset, m_Page.Parent, m_DuelContext, m_ReadOnly ) ); - else if ( !m_ReadOnly ) - m_From.SendGump( new PickRulesetGump( m_From, m_DuelContext, m_Ruleset ) ); - } - else - { - bid -= 1; + if (bid == 0) + { + if (m_Page.Parent != null) + m_From.SendGump(new RulesetGump(m_From, m_Ruleset, m_Page.Parent, m_DuelContext, m_ReadOnly)); + else if (!m_ReadOnly) + m_From.SendGump(new PickRulesetGump(m_From, m_DuelContext, m_Ruleset)); + } + else + { + bid -= 1; - if ( bid >= 0 && bid < m_Page.Children.Length ) - m_From.SendGump( new RulesetGump( m_From, m_Ruleset, m_Page.Children[bid], m_DuelContext, m_ReadOnly ) ); - } - } - } + if (bid >= 0 && bid < m_Page.Children.Length) + m_From.SendGump(new RulesetGump(m_From, m_Ruleset, m_Page.Children[bid], m_DuelContext, m_ReadOnly)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/RulesetLayout.cs b/Scripts/Engines/ConPVP/RulesetLayout.cs index 9c894d48f..59248f47c 100644 --- a/Scripts/Engines/ConPVP/RulesetLayout.cs +++ b/Scripts/Engines/ConPVP/RulesetLayout.cs @@ -3,779 +3,777 @@ using System.Collections; namespace Server.Engines.ConPVP { - public class RulesetLayout - { - private static RulesetLayout m_Root; - - public static RulesetLayout Root - { - get - { - if ( m_Root == null ) - { - ArrayList entries = new ArrayList(); - - entries.Add( new RulesetLayout( "Spells", new[] - { - new RulesetLayout( "1st Circle", "Spells", new[] - { - "Reactive Armor", "Clumsy", - "Create Food", "Feeblemind", - "Heal", "Magic Arrow", - "Night Sight", "Weaken" - } ), - new RulesetLayout( "2nd Circle", "Spells", new[] - { - "Agility", "Cunning", - "Cure", "Harm", - "Magic Trap", "Untrap", - "Protection", "Strength" - } ), - new RulesetLayout( "3rd Circle", "Spells", new[] - { - "Bless", "Fireball", - "Magic Lock", "Poison", - "Telekinesis", "Teleport", - "Unlock Spell", "Wall of Stone" - } ), - new RulesetLayout( "4th Circle", "Spells", new[] - { - "Arch Cure", "Arch Protection", - "Curse", "Fire Field", - "Greater Heal", "Lightning", - "Mana Drain", "Recall" - } ), - new RulesetLayout( "5th Circle", "Spells", new[] - { - "Blade Spirits", "Dispel Field", - "Incognito", "Magic Reflection", - "Mind Blast", "Paralyze", - "Poison Field", "Summon Creature" - } ), - new RulesetLayout( "6th Circle", "Spells", new[] - { - "Dispel", "Energy Bolt", - "Explosion", "Invisibility", - "Mark", "Mass Curse", - "Paralyze Field", "Reveal" - } ), - new RulesetLayout( "7th Circle", "Spells", new[] - { - "Chain Lightning", "Energy Field", - "Flame Strike", "Gate Travel", - "Mana Vampire", "Mass Dispel", - "Meteor Swarm", "Polymorph" - } ), - new RulesetLayout( "8th Circle", "Spells", new[] - { - "Earthquake", "Energy Vortex", - "Resurrection", "Air Elemental", - "Summon Daemon", "Earth Elemental", - "Fire Elemental", "Water Elemental" - } ) - } ) ); - - if ( Core.AOS ) - { - entries.Add( new RulesetLayout( "Chivalry", new[] - { - "Cleanse by Fire", - "Close Wounds", - "Consecrate Weapon", - "Dispel Evil", - "Divine Fury", - "Enemy of One", - "Holy Light", - "Noble Sacrifice", - "Remove Curse", - "Sacred Journey" - } ) ); - - entries.Add( new RulesetLayout( "Necromancy", new[] - { - "Animate Dead", - "Blood Oath", - "Corpse Skin", - "Curse Weapon", - "Evil Omen", - "Horrific Beast", - "Lich Form", - "Mind Rot", - "Pain Spike", - "Poison Strike", - "Strangle", - "Summon Familiar", - "Vampiric Embrace", - "Vengeful Spirit", - "Wither", - "Wraith Form" - } ) ); - - if ( Core.SE ) - { - entries.Add( new RulesetLayout( "Bushido", new[] - { - "Confidence", - "Counter Attack", - "Evasion", - "Honorable Execution", - "Lightning Strike", - "Momentum Strike" - } ) ); - - entries.Add( new RulesetLayout( "Ninjitsu", new[] - { - "Animal Form", - "Backstab", - "Death Strike", - "Focus Attack", - "Ki Attack", - "Mirror Image", - "Shadow Jump", - "Suprise Attack" - } ) ); - - if ( Core.ML ) - { - entries.Add( new RulesetLayout( "Spellweaving", new[] - { - "Arcane Circle", - "Arcane Empowerment", - "Attune Weapon", - "Dryad Allure", - "Essence of Wind", - "Ethereal Voyage", - "Gift of Life", - "Gift of Renewal", - "Immolating Weapon", - "Nature's Fury", - "Reaper Form", - "Summon Fey", - "Summon Fiend", - "Thunderstorm", - "Wildfire", - "Word of Death" - } ) ); - } - } - } - - if ( Core.AOS ) - { - if ( Core.SE ) - { - entries.Add( new RulesetLayout( "Combat Abilities", new[] - { - "Stun", - "Disarm", - "Armor Ignore", - "Bleed Attack", - "Concussion Blow", - "Crushing Blow", - "Disarm", - "Dismount", - "Double Strike", - "Infectious Strike", - "Mortal Strike", - "Moving Shot", - "Paralyzing Blow", - "Shadow Strike", - "Whirlwind Attack", - "Riding Swipe", - "Frenzied Whirlwind", - "Block", - "Defense Mastery", - "Nerve Strike", - "Talon Strike", - "Feint", - "Dual Wield", - "Double Shot", - "Armor Pierce" - } ) ); - - //TODO: ADD ML ABILITIES - } - else - { - entries.Add( new RulesetLayout( "Combat Abilities", new[] - { - "Stun", - "Disarm", - "Armor Ignore", - "Bleed Attack", - "Concussion Blow", - "Crushing Blow", - "Disarm", - "Dismount", - "Double Strike", - "Infectious Strike", - "Mortal Strike", - "Moving Shot", - "Paralyzing Blow", - "Shadow Strike", - "Whirlwind Attack" - } ) ); - } - } - else - { - entries.Add( new RulesetLayout( "Combat Abilities", new[] - { - "Stun", - "Disarm", - "Concussion Blow", - "Crushing Blow", - "Paralyzing Blow" - } ) ); - } - - entries.Add( new RulesetLayout( "Skills", new[] - { - "Anatomy", - "Detect Hidden", - "Evaluating Intelligence", - "Hiding", - "Poisoning", - "Snooping", - "Stealing", - "Spirit Speak", - "Stealth" - } ) ); - - if ( Core.AOS ) - { - entries.Add( new RulesetLayout( "Weapons", new[] - { - "Magical", - "Melee", - "Ranged", - "Poisoned", - "Wrestling" - } ) ); - - entries.Add( new RulesetLayout( "Armor", new[] - { - "Magical", - "Shields" - } ) ); - } - else - { - entries.Add( new RulesetLayout( "Weapons", new[] - { - "Magical", - "Melee", - "Ranged", - "Poisoned", - "Wrestling", - "Runics" - } ) ); - - entries.Add( new RulesetLayout( "Armor", new[] - { - "Magical", - "Shields", - "Colored" - } ) ); - } - - if ( Core.SE ) - { - entries.Add( new RulesetLayout( "Items", new[] - { - new RulesetLayout( "Potions", new[] - { - "Agility", - "Cure", - "Explosion", - "Heal", - "Nightsight", - "Poison", - "Refresh", - "Strength" - } ) - }, - new[] - { - "Bandages", - "Wands", - "Trapped Containers", - "Bolas", - "Mounts", - "Orange Petals", - "Shurikens", - "Fukiya Darts", - "Fire Horns" - } ) ); - } - else - { - entries.Add( new RulesetLayout( "Items", new[] - { - new RulesetLayout( "Potions", new[] - { - "Agility", - "Cure", - "Explosion", - "Heal", - "Nightsight", - "Poison", - "Refresh", - "Strength" - } ) - }, - new[] - { - "Bandages", - "Wands", - "Trapped Containers", - "Bolas", - "Mounts", - "Orange Petals", - "Fire Horns" - } ) ); - } - - m_Root = new RulesetLayout( "Rules", (RulesetLayout[])entries.ToArray( typeof( RulesetLayout ) ) ); - m_Root.ComputeOffsets(); - - // Set up default rulesets - - if ( !Core.AOS ) - { - #region Mage 5x - Ruleset m5x = new Ruleset( m_Root ); - - m5x.Title = "Mage 5x"; - - m5x.SetOptionRange( "Spells", true ); - - m5x.SetOption( "Spells", "Wall of Stone", false ); - m5x.SetOption( "Spells", "Fire Field", false ); - m5x.SetOption( "Spells", "Poison Field", false ); - m5x.SetOption( "Spells", "Energy Field", false ); - m5x.SetOption( "Spells", "Reactive Armor", false ); - m5x.SetOption( "Spells", "Protection", false ); - m5x.SetOption( "Spells", "Teleport", false ); - m5x.SetOption( "Spells", "Wall of Stone", false ); - m5x.SetOption( "Spells", "Arch Protection", false ); - m5x.SetOption( "Spells", "Recall", false ); - m5x.SetOption( "Spells", "Blade Spirits", false ); - m5x.SetOption( "Spells", "Incognito", false ); - m5x.SetOption( "Spells", "Magic Reflection", false ); - m5x.SetOption( "Spells", "Paralyze", false ); - m5x.SetOption( "Spells", "Summon Creature", false ); - m5x.SetOption( "Spells", "Invisibility", false ); - m5x.SetOption( "Spells", "Mark", false ); - m5x.SetOption( "Spells", "Paralyze Field", false ); - m5x.SetOption( "Spells", "Energy Field", false ); - m5x.SetOption( "Spells", "Gate Travel", false ); - m5x.SetOption( "Spells", "Polymorph", false ); - m5x.SetOption( "Spells", "Energy Vortex", false ); - m5x.SetOption( "Spells", "Air Elemental", false ); - m5x.SetOption( "Spells", "Summon Daemon", false ); - m5x.SetOption( "Spells", "Earth Elemental", false ); - m5x.SetOption( "Spells", "Fire Elemental", false ); - m5x.SetOption( "Spells", "Water Elemental", false ); - m5x.SetOption( "Spells", "Earthquake", false ); - m5x.SetOption( "Spells", "Meteor Swarm", false ); - m5x.SetOption( "Spells", "Chain Lightning", false ); - m5x.SetOption( "Spells", "Resurrection", false ); - - m5x.SetOption( "Weapons", "Wrestling", true ); - - m5x.SetOption( "Skills", "Anatomy", true ); - m5x.SetOption( "Skills", "Detect Hidden", true ); - m5x.SetOption( "Skills", "Evaluating Intelligence", true ); - - m5x.SetOption( "Items", "Trapped Containers", true ); - #endregion - - #region Mage 7x - Ruleset m7x = new Ruleset( m_Root ); - - m7x.Title = "Mage 7x"; - - m7x.SetOptionRange( "Spells", true ); - - m7x.SetOption( "Spells", "Wall of Stone", false ); - m7x.SetOption( "Spells", "Fire Field", false ); - m7x.SetOption( "Spells", "Poison Field", false ); - m7x.SetOption( "Spells", "Energy Field", false ); - m7x.SetOption( "Spells", "Reactive Armor", false ); - m7x.SetOption( "Spells", "Protection", false ); - m7x.SetOption( "Spells", "Teleport", false ); - m7x.SetOption( "Spells", "Wall of Stone", false ); - m7x.SetOption( "Spells", "Arch Protection", false ); - m7x.SetOption( "Spells", "Recall", false ); - m7x.SetOption( "Spells", "Blade Spirits", false ); - m7x.SetOption( "Spells", "Incognito", false ); - m7x.SetOption( "Spells", "Magic Reflection", false ); - m7x.SetOption( "Spells", "Paralyze", false ); - m7x.SetOption( "Spells", "Summon Creature", false ); - m7x.SetOption( "Spells", "Invisibility", false ); - m7x.SetOption( "Spells", "Mark", false ); - m7x.SetOption( "Spells", "Paralyze Field", false ); - m7x.SetOption( "Spells", "Energy Field", false ); - m7x.SetOption( "Spells", "Gate Travel", false ); - m7x.SetOption( "Spells", "Polymorph", false ); - m7x.SetOption( "Spells", "Energy Vortex", false ); - m7x.SetOption( "Spells", "Air Elemental", false ); - m7x.SetOption( "Spells", "Summon Daemon", false ); - m7x.SetOption( "Spells", "Earth Elemental", false ); - m7x.SetOption( "Spells", "Fire Elemental", false ); - m7x.SetOption( "Spells", "Water Elemental", false ); - m7x.SetOption( "Spells", "Earthquake", false ); - m7x.SetOption( "Spells", "Meteor Swarm", false ); - m7x.SetOption( "Spells", "Chain Lightning", false ); - m7x.SetOption( "Spells", "Resurrection", false ); - - m7x.SetOption( "Combat Abilities", "Stun", true ); - - m7x.SetOption( "Skills", "Anatomy", true ); - m7x.SetOption( "Skills", "Detect Hidden", true ); - m7x.SetOption( "Skills", "Poisoning", true ); - m7x.SetOption( "Skills", "Evaluating Intelligence", true ); - - m7x.SetOption( "Weapons", "Wrestling", true ); - - m7x.SetOption( "Potions", "Refresh", true ); - m7x.SetOption( "Items", "Trapped Containers", true ); - m7x.SetOption( "Items", "Bandages", true ); - #endregion - - #region Standard 7x - Ruleset s7x = new Ruleset( m_Root ); - - s7x.Title = "Standard 7x"; - - s7x.SetOptionRange( "Spells", true ); - - s7x.SetOption( "Spells", "Wall of Stone", false ); - s7x.SetOption( "Spells", "Fire Field", false ); - s7x.SetOption( "Spells", "Poison Field", false ); - s7x.SetOption( "Spells", "Energy Field", false ); - s7x.SetOption( "Spells", "Teleport", false ); - s7x.SetOption( "Spells", "Wall of Stone", false ); - s7x.SetOption( "Spells", "Arch Protection", false ); - s7x.SetOption( "Spells", "Recall", false ); - s7x.SetOption( "Spells", "Blade Spirits", false ); - s7x.SetOption( "Spells", "Incognito", false ); - s7x.SetOption( "Spells", "Magic Reflection", false ); - s7x.SetOption( "Spells", "Paralyze", false ); - s7x.SetOption( "Spells", "Summon Creature", false ); - s7x.SetOption( "Spells", "Invisibility", false ); - s7x.SetOption( "Spells", "Mark", false ); - s7x.SetOption( "Spells", "Paralyze Field", false ); - s7x.SetOption( "Spells", "Energy Field", false ); - s7x.SetOption( "Spells", "Gate Travel", false ); - s7x.SetOption( "Spells", "Polymorph", false ); - s7x.SetOption( "Spells", "Energy Vortex", false ); - s7x.SetOption( "Spells", "Air Elemental", false ); - s7x.SetOption( "Spells", "Summon Daemon", false ); - s7x.SetOption( "Spells", "Earth Elemental", false ); - s7x.SetOption( "Spells", "Fire Elemental", false ); - s7x.SetOption( "Spells", "Water Elemental", false ); - s7x.SetOption( "Spells", "Earthquake", false ); - s7x.SetOption( "Spells", "Meteor Swarm", false ); - s7x.SetOption( "Spells", "Chain Lightning", false ); - s7x.SetOption( "Spells", "Resurrection", false ); - - s7x.SetOptionRange( "Combat Abilities", true ); - - s7x.SetOption( "Skills", "Anatomy", true ); - s7x.SetOption( "Skills", "Detect Hidden", true ); - s7x.SetOption( "Skills", "Poisoning", true ); - s7x.SetOption( "Skills", "Evaluating Intelligence", true ); - - s7x.SetOptionRange( "Weapons", true ); - s7x.SetOption( "Weapons", "Runics", false ); - s7x.SetOptionRange( "Armor", true ); - - s7x.SetOption( "Potions", "Refresh", true ); - s7x.SetOption( "Items", "Bandages", true ); - s7x.SetOption( "Items", "Trapped Containers", true ); - #endregion - - m_Root.Defaults = new[] { m5x, m7x, s7x }; - } - else - { - #region Standard All Skills - - Ruleset all = new Ruleset( m_Root ); - - all.Title = "Standard All Skills"; - - - all.SetOptionRange( "Spells", true ); - - all.SetOption( "Spells", "Wall of Stone", false ); - all.SetOption( "Spells", "Fire Field", false ); - all.SetOption( "Spells", "Poison Field", false ); - all.SetOption( "Spells", "Energy Field", false ); - all.SetOption( "Spells", "Teleport", false ); - all.SetOption( "Spells", "Wall of Stone", false ); - all.SetOption( "Spells", "Arch Protection", false ); - all.SetOption( "Spells", "Recall", false ); - all.SetOption( "Spells", "Blade Spirits", false ); - all.SetOption( "Spells", "Incognito", false ); - all.SetOption( "Spells", "Magic Reflection", false ); - all.SetOption( "Spells", "Paralyze", false ); - all.SetOption( "Spells", "Summon Creature", false ); - all.SetOption( "Spells", "Invisibility", false ); - all.SetOption( "Spells", "Mark", false ); - all.SetOption( "Spells", "Paralyze Field", false ); - all.SetOption( "Spells", "Energy Field", false ); - all.SetOption( "Spells", "Gate Travel", false ); - all.SetOption( "Spells", "Polymorph", false ); - all.SetOption( "Spells", "Energy Vortex", false ); - all.SetOption( "Spells", "Air Elemental", false ); - all.SetOption( "Spells", "Summon Daemon", false ); - all.SetOption( "Spells", "Earth Elemental", false ); - all.SetOption( "Spells", "Fire Elemental", false ); - all.SetOption( "Spells", "Water Elemental", false ); - all.SetOption( "Spells", "Earthquake", false ); - all.SetOption( "Spells", "Meteor Swarm", false ); - all.SetOption( "Spells", "Chain Lightning", false ); - all.SetOption( "Spells", "Resurrection", false ); - - all.SetOptionRange( "Necromancy", true ); - all.SetOption( "Necromancy", "Summon Familiar", false ); - all.SetOption( "Necromancy", "Vengeful Spirit", false ); - all.SetOption( "Necromancy", "Animate Dead", false ); - all.SetOption( "Necromancy", "Wither", false ); - all.SetOption( "Necromancy", "Poison Strike", false ); - - all.SetOptionRange( "Chivalry", true ); - all.SetOption( "Chivalry", "Sacred Journey", false ); - all.SetOption( "Chivalry", "Enemy of One", false ); - all.SetOption( "Chivalry", "Noble Sacrifice", false ); - - all.SetOptionRange( "Combat Abilities", true ); - all.SetOption( "Combat Abilities", "Paralyzing Blow", false ); - all.SetOption( "Combat Abilities", "Shadow Strike", false ); - - all.SetOption( "Skills", "Anatomy", true ); - all.SetOption( "Skills", "Detect Hidden", true ); - all.SetOption( "Skills", "Poisoning", true ); - all.SetOption( "Skills", "Spirit Speak", true ); - all.SetOption( "Skills", "Evaluating Intelligence", true ); - - all.SetOptionRange( "Weapons", true ); - all.SetOption( "Weapons", "Poisoned", false ); - - all.SetOptionRange( "Armor", true ); - - all.SetOptionRange( "Ninjitsu", true ); - all.SetOption( "Ninjitsu", "Animal Form", false ); - all.SetOption( "Ninjitsu", "Mirror Image", false ); - all.SetOption( "Ninjitsu", "Backstab", false ); - all.SetOption( "Ninjitsu", "Suprise Attack", false ); - all.SetOption( "Ninjitsu", "Shadow Jump", false ); - - all.SetOptionRange( "Bushido", true ); - - all.SetOptionRange( "Spellweaving", true ); - all.SetOption( "Spellweaving", "Gift of Life", false ); - all.SetOption( "Spellweaving", "Summon Fey", false ); - all.SetOption( "Spellweaving", "Summon Fiend", false ); - all.SetOption( "Spellweaving", "Nature's Fury", false ); - - all.SetOption( "Potions", "Refresh", true ); - all.SetOption( "Items", "Bandages", true ); - all.SetOption( "Items", "Trapped Containers", true ); - - m_Root.Defaults = new[] { all }; - #endregion - } - - // Set up flavors - - Ruleset pots = new Ruleset( m_Root ); - - pots.Title = "Potions"; - - pots.SetOptionRange( "Potions", true ); - pots.SetOption( "Potions", "Explosion", false ); - - Ruleset para = new Ruleset( m_Root ); - - para.Title = "Paralyze"; - para.SetOption( "Spells", "Paralyze", true ); - para.SetOption( "Spells", "Paralyze Field", true ); - para.SetOption( "Combat Abilities", "Paralyzing Blow", true ); - - Ruleset fields = new Ruleset( m_Root ); - - fields.Title = "Fields"; - fields.SetOption( "Spells", "Wall of Stone", true ); - fields.SetOption( "Spells", "Fire Field", true ); - fields.SetOption( "Spells", "Poison Field", true ); - fields.SetOption( "Spells", "Energy Field", true ); - fields.SetOption( "Spells", "Wildfire", true ); - - Ruleset area = new Ruleset( m_Root ); - - area.Title = "Area Effect"; - area.SetOption( "Spells", "Earthquake", true ); - area.SetOption( "Spells", "Meteor Swarm", true ); - area.SetOption( "Spells", "Chain Lightning", true ); - area.SetOption( "Necromancy", "Wither", true ); - area.SetOption( "Necromancy", "Poison Strike", true ); - - Ruleset summons = new Ruleset( m_Root ); - - summons.Title = "Summons"; - summons.SetOption( "Spells", "Blade Spirits", true ); - summons.SetOption( "Spells", "Energy Vortex", true ); - summons.SetOption( "Spells", "Air Elemental", true ); - summons.SetOption( "Spells", "Summon Daemon", true ); - summons.SetOption( "Spells", "Earth Elemental", true ); - summons.SetOption( "Spells", "Fire Elemental", true ); - summons.SetOption( "Spells", "Water Elemental", true ); - summons.SetOption( "Necromancy", "Summon Familiar", true ); - summons.SetOption( "Necromancy", "Vengeful Spirit", true ); - summons.SetOption( "Necromancy", "Animate Dead", true ); - summons.SetOption( "Ninjitsu", "Mirror Image", true ); - summons.SetOption( "Spellweaving", "Summon Fey", true ); - summons.SetOption( "Spellweaving", "Summon Fiend", true ); - summons.SetOption( "Spellweaving", "Nature's Fury", true ); + public class RulesetLayout + { + private static RulesetLayout m_Root; + + public RulesetLayout(string title, string[] options) : this(title, title, new RulesetLayout[0], options) + { + } + + public RulesetLayout(string title, string description, string[] options) : this(title, description, + new RulesetLayout[0], options) + { + } + + public RulesetLayout(string title, RulesetLayout[] children) : this(title, title, children, new string[0]) + { + } + + public RulesetLayout(string title, string description, RulesetLayout[] children) : this(title, description, children, + new string[0]) + { + } + + public RulesetLayout(string title, RulesetLayout[] children, string[] options) : this(title, title, children, + options) + { + } + + public RulesetLayout(string title, string description, RulesetLayout[] children, string[] options) + { + Title = title; + Description = description; + Children = children; + Options = options; + + for (int i = 0; i < children.Length; ++i) + children[i].Parent = this; + } + + public static RulesetLayout Root + { + get + { + if (m_Root == null) + { + ArrayList entries = new ArrayList(); + + entries.Add(new RulesetLayout("Spells", new[] + { + new RulesetLayout("1st Circle", "Spells", new[] + { + "Reactive Armor", "Clumsy", + "Create Food", "Feeblemind", + "Heal", "Magic Arrow", + "Night Sight", "Weaken" + }), + new RulesetLayout("2nd Circle", "Spells", new[] + { + "Agility", "Cunning", + "Cure", "Harm", + "Magic Trap", "Untrap", + "Protection", "Strength" + }), + new RulesetLayout("3rd Circle", "Spells", new[] + { + "Bless", "Fireball", + "Magic Lock", "Poison", + "Telekinesis", "Teleport", + "Unlock Spell", "Wall of Stone" + }), + new RulesetLayout("4th Circle", "Spells", new[] + { + "Arch Cure", "Arch Protection", + "Curse", "Fire Field", + "Greater Heal", "Lightning", + "Mana Drain", "Recall" + }), + new RulesetLayout("5th Circle", "Spells", new[] + { + "Blade Spirits", "Dispel Field", + "Incognito", "Magic Reflection", + "Mind Blast", "Paralyze", + "Poison Field", "Summon Creature" + }), + new RulesetLayout("6th Circle", "Spells", new[] + { + "Dispel", "Energy Bolt", + "Explosion", "Invisibility", + "Mark", "Mass Curse", + "Paralyze Field", "Reveal" + }), + new RulesetLayout("7th Circle", "Spells", new[] + { + "Chain Lightning", "Energy Field", + "Flame Strike", "Gate Travel", + "Mana Vampire", "Mass Dispel", + "Meteor Swarm", "Polymorph" + }), + new RulesetLayout("8th Circle", "Spells", new[] + { + "Earthquake", "Energy Vortex", + "Resurrection", "Air Elemental", + "Summon Daemon", "Earth Elemental", + "Fire Elemental", "Water Elemental" + }) + })); + + if (Core.AOS) + { + entries.Add(new RulesetLayout("Chivalry", new[] + { + "Cleanse by Fire", + "Close Wounds", + "Consecrate Weapon", + "Dispel Evil", + "Divine Fury", + "Enemy of One", + "Holy Light", + "Noble Sacrifice", + "Remove Curse", + "Sacred Journey" + })); + + entries.Add(new RulesetLayout("Necromancy", new[] + { + "Animate Dead", + "Blood Oath", + "Corpse Skin", + "Curse Weapon", + "Evil Omen", + "Horrific Beast", + "Lich Form", + "Mind Rot", + "Pain Spike", + "Poison Strike", + "Strangle", + "Summon Familiar", + "Vampiric Embrace", + "Vengeful Spirit", + "Wither", + "Wraith Form" + })); + + if (Core.SE) + { + entries.Add(new RulesetLayout("Bushido", new[] + { + "Confidence", + "Counter Attack", + "Evasion", + "Honorable Execution", + "Lightning Strike", + "Momentum Strike" + })); + + entries.Add(new RulesetLayout("Ninjitsu", new[] + { + "Animal Form", + "Backstab", + "Death Strike", + "Focus Attack", + "Ki Attack", + "Mirror Image", + "Shadow Jump", + "Suprise Attack" + })); + + if (Core.ML) + entries.Add(new RulesetLayout("Spellweaving", new[] + { + "Arcane Circle", + "Arcane Empowerment", + "Attune Weapon", + "Dryad Allure", + "Essence of Wind", + "Ethereal Voyage", + "Gift of Life", + "Gift of Renewal", + "Immolating Weapon", + "Nature's Fury", + "Reaper Form", + "Summon Fey", + "Summon Fiend", + "Thunderstorm", + "Wildfire", + "Word of Death" + })); + } + } + + if (Core.AOS) + { + if (Core.SE) + entries.Add(new RulesetLayout("Combat Abilities", new[] + { + "Stun", + "Disarm", + "Armor Ignore", + "Bleed Attack", + "Concussion Blow", + "Crushing Blow", + "Disarm", + "Dismount", + "Double Strike", + "Infectious Strike", + "Mortal Strike", + "Moving Shot", + "Paralyzing Blow", + "Shadow Strike", + "Whirlwind Attack", + "Riding Swipe", + "Frenzied Whirlwind", + "Block", + "Defense Mastery", + "Nerve Strike", + "Talon Strike", + "Feint", + "Dual Wield", + "Double Shot", + "Armor Pierce" + })); + else + entries.Add(new RulesetLayout("Combat Abilities", new[] + { + "Stun", + "Disarm", + "Armor Ignore", + "Bleed Attack", + "Concussion Blow", + "Crushing Blow", + "Disarm", + "Dismount", + "Double Strike", + "Infectious Strike", + "Mortal Strike", + "Moving Shot", + "Paralyzing Blow", + "Shadow Strike", + "Whirlwind Attack" + })); + } + else + { + entries.Add(new RulesetLayout("Combat Abilities", new[] + { + "Stun", + "Disarm", + "Concussion Blow", + "Crushing Blow", + "Paralyzing Blow" + })); + } + + entries.Add(new RulesetLayout("Skills", new[] + { + "Anatomy", + "Detect Hidden", + "Evaluating Intelligence", + "Hiding", + "Poisoning", + "Snooping", + "Stealing", + "Spirit Speak", + "Stealth" + })); + + if (Core.AOS) + { + entries.Add(new RulesetLayout("Weapons", new[] + { + "Magical", + "Melee", + "Ranged", + "Poisoned", + "Wrestling" + })); + + entries.Add(new RulesetLayout("Armor", new[] + { + "Magical", + "Shields" + })); + } + else + { + entries.Add(new RulesetLayout("Weapons", new[] + { + "Magical", + "Melee", + "Ranged", + "Poisoned", + "Wrestling", + "Runics" + })); + + entries.Add(new RulesetLayout("Armor", new[] + { + "Magical", + "Shields", + "Colored" + })); + } + + if (Core.SE) + entries.Add(new RulesetLayout("Items", new[] + { + new RulesetLayout("Potions", new[] + { + "Agility", + "Cure", + "Explosion", + "Heal", + "Nightsight", + "Poison", + "Refresh", + "Strength" + }) + }, + new[] + { + "Bandages", + "Wands", + "Trapped Containers", + "Bolas", + "Mounts", + "Orange Petals", + "Shurikens", + "Fukiya Darts", + "Fire Horns" + })); + else + entries.Add(new RulesetLayout("Items", new[] + { + new RulesetLayout("Potions", new[] + { + "Agility", + "Cure", + "Explosion", + "Heal", + "Nightsight", + "Poison", + "Refresh", + "Strength" + }) + }, + new[] + { + "Bandages", + "Wands", + "Trapped Containers", + "Bolas", + "Mounts", + "Orange Petals", + "Fire Horns" + })); + + m_Root = new RulesetLayout("Rules", (RulesetLayout[])entries.ToArray(typeof(RulesetLayout))); + m_Root.ComputeOffsets(); + + // Set up default rulesets + + if (!Core.AOS) + { + #region Mage 5x + + Ruleset m5x = new Ruleset(m_Root); + + m5x.Title = "Mage 5x"; + + m5x.SetOptionRange("Spells", true); + + m5x.SetOption("Spells", "Wall of Stone", false); + m5x.SetOption("Spells", "Fire Field", false); + m5x.SetOption("Spells", "Poison Field", false); + m5x.SetOption("Spells", "Energy Field", false); + m5x.SetOption("Spells", "Reactive Armor", false); + m5x.SetOption("Spells", "Protection", false); + m5x.SetOption("Spells", "Teleport", false); + m5x.SetOption("Spells", "Wall of Stone", false); + m5x.SetOption("Spells", "Arch Protection", false); + m5x.SetOption("Spells", "Recall", false); + m5x.SetOption("Spells", "Blade Spirits", false); + m5x.SetOption("Spells", "Incognito", false); + m5x.SetOption("Spells", "Magic Reflection", false); + m5x.SetOption("Spells", "Paralyze", false); + m5x.SetOption("Spells", "Summon Creature", false); + m5x.SetOption("Spells", "Invisibility", false); + m5x.SetOption("Spells", "Mark", false); + m5x.SetOption("Spells", "Paralyze Field", false); + m5x.SetOption("Spells", "Energy Field", false); + m5x.SetOption("Spells", "Gate Travel", false); + m5x.SetOption("Spells", "Polymorph", false); + m5x.SetOption("Spells", "Energy Vortex", false); + m5x.SetOption("Spells", "Air Elemental", false); + m5x.SetOption("Spells", "Summon Daemon", false); + m5x.SetOption("Spells", "Earth Elemental", false); + m5x.SetOption("Spells", "Fire Elemental", false); + m5x.SetOption("Spells", "Water Elemental", false); + m5x.SetOption("Spells", "Earthquake", false); + m5x.SetOption("Spells", "Meteor Swarm", false); + m5x.SetOption("Spells", "Chain Lightning", false); + m5x.SetOption("Spells", "Resurrection", false); + + m5x.SetOption("Weapons", "Wrestling", true); + + m5x.SetOption("Skills", "Anatomy", true); + m5x.SetOption("Skills", "Detect Hidden", true); + m5x.SetOption("Skills", "Evaluating Intelligence", true); + + m5x.SetOption("Items", "Trapped Containers", true); + + #endregion + + #region Mage 7x + + Ruleset m7x = new Ruleset(m_Root); + + m7x.Title = "Mage 7x"; + + m7x.SetOptionRange("Spells", true); + + m7x.SetOption("Spells", "Wall of Stone", false); + m7x.SetOption("Spells", "Fire Field", false); + m7x.SetOption("Spells", "Poison Field", false); + m7x.SetOption("Spells", "Energy Field", false); + m7x.SetOption("Spells", "Reactive Armor", false); + m7x.SetOption("Spells", "Protection", false); + m7x.SetOption("Spells", "Teleport", false); + m7x.SetOption("Spells", "Wall of Stone", false); + m7x.SetOption("Spells", "Arch Protection", false); + m7x.SetOption("Spells", "Recall", false); + m7x.SetOption("Spells", "Blade Spirits", false); + m7x.SetOption("Spells", "Incognito", false); + m7x.SetOption("Spells", "Magic Reflection", false); + m7x.SetOption("Spells", "Paralyze", false); + m7x.SetOption("Spells", "Summon Creature", false); + m7x.SetOption("Spells", "Invisibility", false); + m7x.SetOption("Spells", "Mark", false); + m7x.SetOption("Spells", "Paralyze Field", false); + m7x.SetOption("Spells", "Energy Field", false); + m7x.SetOption("Spells", "Gate Travel", false); + m7x.SetOption("Spells", "Polymorph", false); + m7x.SetOption("Spells", "Energy Vortex", false); + m7x.SetOption("Spells", "Air Elemental", false); + m7x.SetOption("Spells", "Summon Daemon", false); + m7x.SetOption("Spells", "Earth Elemental", false); + m7x.SetOption("Spells", "Fire Elemental", false); + m7x.SetOption("Spells", "Water Elemental", false); + m7x.SetOption("Spells", "Earthquake", false); + m7x.SetOption("Spells", "Meteor Swarm", false); + m7x.SetOption("Spells", "Chain Lightning", false); + m7x.SetOption("Spells", "Resurrection", false); + + m7x.SetOption("Combat Abilities", "Stun", true); + + m7x.SetOption("Skills", "Anatomy", true); + m7x.SetOption("Skills", "Detect Hidden", true); + m7x.SetOption("Skills", "Poisoning", true); + m7x.SetOption("Skills", "Evaluating Intelligence", true); + + m7x.SetOption("Weapons", "Wrestling", true); + + m7x.SetOption("Potions", "Refresh", true); + m7x.SetOption("Items", "Trapped Containers", true); + m7x.SetOption("Items", "Bandages", true); + + #endregion + + #region Standard 7x + + Ruleset s7x = new Ruleset(m_Root); + + s7x.Title = "Standard 7x"; + + s7x.SetOptionRange("Spells", true); + + s7x.SetOption("Spells", "Wall of Stone", false); + s7x.SetOption("Spells", "Fire Field", false); + s7x.SetOption("Spells", "Poison Field", false); + s7x.SetOption("Spells", "Energy Field", false); + s7x.SetOption("Spells", "Teleport", false); + s7x.SetOption("Spells", "Wall of Stone", false); + s7x.SetOption("Spells", "Arch Protection", false); + s7x.SetOption("Spells", "Recall", false); + s7x.SetOption("Spells", "Blade Spirits", false); + s7x.SetOption("Spells", "Incognito", false); + s7x.SetOption("Spells", "Magic Reflection", false); + s7x.SetOption("Spells", "Paralyze", false); + s7x.SetOption("Spells", "Summon Creature", false); + s7x.SetOption("Spells", "Invisibility", false); + s7x.SetOption("Spells", "Mark", false); + s7x.SetOption("Spells", "Paralyze Field", false); + s7x.SetOption("Spells", "Energy Field", false); + s7x.SetOption("Spells", "Gate Travel", false); + s7x.SetOption("Spells", "Polymorph", false); + s7x.SetOption("Spells", "Energy Vortex", false); + s7x.SetOption("Spells", "Air Elemental", false); + s7x.SetOption("Spells", "Summon Daemon", false); + s7x.SetOption("Spells", "Earth Elemental", false); + s7x.SetOption("Spells", "Fire Elemental", false); + s7x.SetOption("Spells", "Water Elemental", false); + s7x.SetOption("Spells", "Earthquake", false); + s7x.SetOption("Spells", "Meteor Swarm", false); + s7x.SetOption("Spells", "Chain Lightning", false); + s7x.SetOption("Spells", "Resurrection", false); + + s7x.SetOptionRange("Combat Abilities", true); + + s7x.SetOption("Skills", "Anatomy", true); + s7x.SetOption("Skills", "Detect Hidden", true); + s7x.SetOption("Skills", "Poisoning", true); + s7x.SetOption("Skills", "Evaluating Intelligence", true); + + s7x.SetOptionRange("Weapons", true); + s7x.SetOption("Weapons", "Runics", false); + s7x.SetOptionRange("Armor", true); + + s7x.SetOption("Potions", "Refresh", true); + s7x.SetOption("Items", "Bandages", true); + s7x.SetOption("Items", "Trapped Containers", true); + + #endregion + + m_Root.Defaults = new[] { m5x, m7x, s7x }; + } + else + { + #region Standard All Skills + + Ruleset all = new Ruleset(m_Root); + + all.Title = "Standard All Skills"; + + + all.SetOptionRange("Spells", true); + + all.SetOption("Spells", "Wall of Stone", false); + all.SetOption("Spells", "Fire Field", false); + all.SetOption("Spells", "Poison Field", false); + all.SetOption("Spells", "Energy Field", false); + all.SetOption("Spells", "Teleport", false); + all.SetOption("Spells", "Wall of Stone", false); + all.SetOption("Spells", "Arch Protection", false); + all.SetOption("Spells", "Recall", false); + all.SetOption("Spells", "Blade Spirits", false); + all.SetOption("Spells", "Incognito", false); + all.SetOption("Spells", "Magic Reflection", false); + all.SetOption("Spells", "Paralyze", false); + all.SetOption("Spells", "Summon Creature", false); + all.SetOption("Spells", "Invisibility", false); + all.SetOption("Spells", "Mark", false); + all.SetOption("Spells", "Paralyze Field", false); + all.SetOption("Spells", "Energy Field", false); + all.SetOption("Spells", "Gate Travel", false); + all.SetOption("Spells", "Polymorph", false); + all.SetOption("Spells", "Energy Vortex", false); + all.SetOption("Spells", "Air Elemental", false); + all.SetOption("Spells", "Summon Daemon", false); + all.SetOption("Spells", "Earth Elemental", false); + all.SetOption("Spells", "Fire Elemental", false); + all.SetOption("Spells", "Water Elemental", false); + all.SetOption("Spells", "Earthquake", false); + all.SetOption("Spells", "Meteor Swarm", false); + all.SetOption("Spells", "Chain Lightning", false); + all.SetOption("Spells", "Resurrection", false); + + all.SetOptionRange("Necromancy", true); + all.SetOption("Necromancy", "Summon Familiar", false); + all.SetOption("Necromancy", "Vengeful Spirit", false); + all.SetOption("Necromancy", "Animate Dead", false); + all.SetOption("Necromancy", "Wither", false); + all.SetOption("Necromancy", "Poison Strike", false); + + all.SetOptionRange("Chivalry", true); + all.SetOption("Chivalry", "Sacred Journey", false); + all.SetOption("Chivalry", "Enemy of One", false); + all.SetOption("Chivalry", "Noble Sacrifice", false); + + all.SetOptionRange("Combat Abilities", true); + all.SetOption("Combat Abilities", "Paralyzing Blow", false); + all.SetOption("Combat Abilities", "Shadow Strike", false); + + all.SetOption("Skills", "Anatomy", true); + all.SetOption("Skills", "Detect Hidden", true); + all.SetOption("Skills", "Poisoning", true); + all.SetOption("Skills", "Spirit Speak", true); + all.SetOption("Skills", "Evaluating Intelligence", true); + + all.SetOptionRange("Weapons", true); + all.SetOption("Weapons", "Poisoned", false); + + all.SetOptionRange("Armor", true); + + all.SetOptionRange("Ninjitsu", true); + all.SetOption("Ninjitsu", "Animal Form", false); + all.SetOption("Ninjitsu", "Mirror Image", false); + all.SetOption("Ninjitsu", "Backstab", false); + all.SetOption("Ninjitsu", "Suprise Attack", false); + all.SetOption("Ninjitsu", "Shadow Jump", false); + + all.SetOptionRange("Bushido", true); + + all.SetOptionRange("Spellweaving", true); + all.SetOption("Spellweaving", "Gift of Life", false); + all.SetOption("Spellweaving", "Summon Fey", false); + all.SetOption("Spellweaving", "Summon Fiend", false); + all.SetOption("Spellweaving", "Nature's Fury", false); + + all.SetOption("Potions", "Refresh", true); + all.SetOption("Items", "Bandages", true); + all.SetOption("Items", "Trapped Containers", true); + + m_Root.Defaults = new[] { all }; + + #endregion + } + + // Set up flavors + + Ruleset pots = new Ruleset(m_Root); + + pots.Title = "Potions"; + + pots.SetOptionRange("Potions", true); + pots.SetOption("Potions", "Explosion", false); + + Ruleset para = new Ruleset(m_Root); + + para.Title = "Paralyze"; + para.SetOption("Spells", "Paralyze", true); + para.SetOption("Spells", "Paralyze Field", true); + para.SetOption("Combat Abilities", "Paralyzing Blow", true); + + Ruleset fields = new Ruleset(m_Root); + + fields.Title = "Fields"; + fields.SetOption("Spells", "Wall of Stone", true); + fields.SetOption("Spells", "Fire Field", true); + fields.SetOption("Spells", "Poison Field", true); + fields.SetOption("Spells", "Energy Field", true); + fields.SetOption("Spells", "Wildfire", true); + + Ruleset area = new Ruleset(m_Root); + + area.Title = "Area Effect"; + area.SetOption("Spells", "Earthquake", true); + area.SetOption("Spells", "Meteor Swarm", true); + area.SetOption("Spells", "Chain Lightning", true); + area.SetOption("Necromancy", "Wither", true); + area.SetOption("Necromancy", "Poison Strike", true); - m_Root.Flavors = new[]{ pots, para, fields, area, summons }; - } + Ruleset summons = new Ruleset(m_Root); - return m_Root; - } - } + summons.Title = "Summons"; + summons.SetOption("Spells", "Blade Spirits", true); + summons.SetOption("Spells", "Energy Vortex", true); + summons.SetOption("Spells", "Air Elemental", true); + summons.SetOption("Spells", "Summon Daemon", true); + summons.SetOption("Spells", "Earth Elemental", true); + summons.SetOption("Spells", "Fire Elemental", true); + summons.SetOption("Spells", "Water Elemental", true); + summons.SetOption("Necromancy", "Summon Familiar", true); + summons.SetOption("Necromancy", "Vengeful Spirit", true); + summons.SetOption("Necromancy", "Animate Dead", true); + summons.SetOption("Ninjitsu", "Mirror Image", true); + summons.SetOption("Spellweaving", "Summon Fey", true); + summons.SetOption("Spellweaving", "Summon Fiend", true); + summons.SetOption("Spellweaving", "Nature's Fury", true); - public string Title { get; } + m_Root.Flavors = new[] { pots, para, fields, area, summons }; + } - public string Description { get; } + return m_Root; + } + } - public string[] Options { get; } + public string Title{ get; } - public int Offset { get; private set; } + public string Description{ get; } - public int TotalLength { get; private set; } + public string[] Options{ get; } - public RulesetLayout Parent { get; private set; } + public int Offset{ get; private set; } - public RulesetLayout[] Children { get; } + public int TotalLength{ get; private set; } - public Ruleset[] Defaults { get; set; } + public RulesetLayout Parent{ get; private set; } - public Ruleset[] Flavors { get; set; } + public RulesetLayout[] Children{ get; } - public RulesetLayout FindByTitle( string title ) - { - if ( Title == title ) - return this; + public Ruleset[] Defaults{ get; set; } - for ( int i = 0; i < Children.Length; ++i ) - { - RulesetLayout layout = Children[i].FindByTitle( title ); + public Ruleset[] Flavors{ get; set; } - if ( layout != null ) - return layout; - } + public RulesetLayout FindByTitle(string title) + { + if (Title == title) + return this; - return null; - } + for (int i = 0; i < Children.Length; ++i) + { + RulesetLayout layout = Children[i].FindByTitle(title); - public string FindByIndex( int index ) - { - if ( index >= Offset && index < (Offset + Options.Length) ) - return Description + ": " + Options[index - Offset]; + if (layout != null) + return layout; + } - for ( int i = 0; i < Children.Length; ++i ) - { - string opt = Children[i].FindByIndex( index ); + return null; + } - if ( opt != null ) - return opt; - } + public string FindByIndex(int index) + { + if (index >= Offset && index < Offset + Options.Length) + return Description + ": " + Options[index - Offset]; - return null; - } + for (int i = 0; i < Children.Length; ++i) + { + string opt = Children[i].FindByIndex(index); - public RulesetLayout FindByOption( string title, string option, ref int index ) - { - if ( title == null || Title == title ) - { - index = GetOptionIndex( option ); + if (opt != null) + return opt; + } - if ( index >= 0 ) - return this; + return null; + } - title = null; - } + public RulesetLayout FindByOption(string title, string option, ref int index) + { + if (title == null || Title == title) + { + index = GetOptionIndex(option); - for ( int i = 0; i < Children.Length; ++i ) - { - RulesetLayout layout = Children[i].FindByOption( title, option, ref index ); + if (index >= 0) + return this; - if ( layout != null ) - return layout; - } + title = null; + } - return null; - } + for (int i = 0; i < Children.Length; ++i) + { + RulesetLayout layout = Children[i].FindByOption(title, option, ref index); - public int GetOptionIndex( string option ) - { - return Array.IndexOf( Options, option ); - } + if (layout != null) + return layout; + } - public void ComputeOffsets() - { - int offset = 0; + return null; + } - RecurseComputeOffsets( ref offset ); - } + public int GetOptionIndex(string option) + { + return Array.IndexOf(Options, option); + } - private int RecurseComputeOffsets( ref int offset ) - { - Offset = offset; + public void ComputeOffsets() + { + int offset = 0; - offset += Options.Length; - TotalLength += Options.Length; + RecurseComputeOffsets(ref offset); + } - for ( int i = 0; i < Children.Length; ++i ) - TotalLength += Children[i].RecurseComputeOffsets( ref offset ); + private int RecurseComputeOffsets(ref int offset) + { + Offset = offset; - return TotalLength; - } + offset += Options.Length; + TotalLength += Options.Length; - public RulesetLayout( string title, string[] options ) : this( title, title, new RulesetLayout[0], options ) - { - } + for (int i = 0; i < Children.Length; ++i) + TotalLength += Children[i].RecurseComputeOffsets(ref offset); - public RulesetLayout( string title, string description, string[] options ) : this( title, description, new RulesetLayout[0], options ) - { - } - - public RulesetLayout( string title, RulesetLayout[] children ) : this( title, title, children, new string[0] ) - { - } - - public RulesetLayout( string title, string description, RulesetLayout[] children ) : this( title, description, children, new string[0] ) - { - } - - public RulesetLayout( string title, RulesetLayout[] children, string[] options ) : this( title, title, children, options ) - { - } - - public RulesetLayout( string title, string description, RulesetLayout[] children, string[] options ) - { - Title = title; - Description = description; - Children = children; - Options = options; - - for ( int i = 0; i < children.Length; ++i ) - children[i].Parent = this; - } - } -} + return TotalLength; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/SafeZone.cs b/Scripts/Engines/ConPVP/SafeZone.cs index 4bb0dea39..e6e7f8f1c 100644 --- a/Scripts/Engines/ConPVP/SafeZone.cs +++ b/Scripts/Engines/ConPVP/SafeZone.cs @@ -1,69 +1,70 @@ +using Server.Factions; using Server.Mobiles; using Server.Regions; namespace Server.Engines.ConPVP { - public class SafeZone : GuardedRegion - { - public static readonly int SafeZonePriority = HouseRegion.HousePriority + 1; + public class SafeZone : GuardedRegion + { + public static readonly int SafeZonePriority = HouseRegion.HousePriority + 1; - /*public override bool AllowReds => true;*/ + /*public override bool AllowReds => true;*/ - public SafeZone( Rectangle2D area, Point3D goloc, Map map, bool isGuarded ) : base( null, map, SafeZonePriority, area ) - { - GoLocation = goloc; + public SafeZone(Rectangle2D area, Point3D goloc, Map map, bool isGuarded) : base(null, map, SafeZonePriority, area) + { + GoLocation = goloc; - Disabled = !isGuarded; + Disabled = !isGuarded; - Register(); - } + Register(); + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - if ( from.AccessLevel < AccessLevel.GameMaster ) - return false; + public override bool AllowHousing(Mobile from, Point3D p) + { + if (from.AccessLevel < AccessLevel.GameMaster) + return false; - return base.AllowHousing( from, p ); - } + return base.AllowHousing(from, p); + } - public override bool OnMoveInto( Mobile m, Direction d, Point3D newLocation, Point3D oldLocation ) - { - if ( m.Player && Factions.Sigil.ExistsOn( m ) ) - { - m.SendMessage( 0x22, "You are holding a sigil and cannot enter this zone." ); - return false; - } + public override bool OnMoveInto(Mobile m, Direction d, Point3D newLocation, Point3D oldLocation) + { + if (m.Player && Sigil.ExistsOn(m)) + { + m.SendMessage(0x22, "You are holding a sigil and cannot enter this zone."); + return false; + } - PlayerMobile pm = m as PlayerMobile; + PlayerMobile pm = m as PlayerMobile; - if ( pm == null && m is BaseCreature bc && bc.Summoned ) - pm = bc.SummonMaster as PlayerMobile; + if (pm == null && m is BaseCreature bc && bc.Summoned) + pm = bc.SummonMaster as PlayerMobile; - if ( pm?.DuelContext != null && pm.DuelContext.StartedBeginCountdown ) - return true; + if (pm?.DuelContext != null && pm.DuelContext.StartedBeginCountdown) + return true; - if ( DuelContext.CheckCombat( m ) ) - { - m.SendMessage( 0x22, "You have recently been in combat and cannot enter this zone." ); - return false; - } + if (DuelContext.CheckCombat(m)) + { + m.SendMessage(0x22, "You have recently been in combat and cannot enter this zone."); + return false; + } - return base.OnMoveInto( m, d, newLocation, oldLocation ); - } + return base.OnMoveInto(m, d, newLocation, oldLocation); + } - public override void OnEnter( Mobile m ) - { - m.SendMessage( "You have entered a dueling safezone. No combat other than duels are allowed in this zone." ); - } + public override void OnEnter(Mobile m) + { + m.SendMessage("You have entered a dueling safezone. No combat other than duels are allowed in this zone."); + } - public override void OnExit( Mobile m ) - { - m.SendMessage( "You have left a dueling safezone. Combat is now unrestricted." ); - } + public override void OnExit(Mobile m) + { + m.SendMessage("You have left a dueling safezone. Combat is now unrestricted."); + } - public override bool CanUseStuckMenu( Mobile m ) - { - return false; - } - } -} + public override bool CanUseStuckMenu(Mobile m) + { + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Tournament.cs b/Scripts/Engines/ConPVP/Tournament.cs index fcb024636..ac2687cd0 100644 --- a/Scripts/Engines/ConPVP/Tournament.cs +++ b/Scripts/Engines/ConPVP/Tournament.cs @@ -1,3447 +1,3565 @@ using System; -using System.Text; using System.Collections; -using Server.Items; -using Server.Gumps; -using Server.Network; -using Server.ContextMenus; -using Server.Mobiles; -using Server.Targeting; using System.Collections.Generic; -using Server.Factions; +using System.Text; +using Server.ContextMenus; using Server.Ethics; +using Server.Factions; +using Server.Gumps; +using Server.Items; +using Server.Mobiles; +using Server.Network; +using Server.Regions; +using Server.Targeting; namespace Server.Engines.ConPVP { - public enum TournamentStage - { - Inactive, - Signup, - Fighting - } - - public enum GroupingType - { - HighVsLow, - Nearest, - Random - } - - public enum TieType - { - Random, - Highest, - Lowest, - FullElimination, - FullAdvancement - } - - public class TournamentRegistrar : Banker - { - [CommandProperty( AccessLevel.GameMaster )] - public TournamentController Tournament { get; set; } - - [Constructible] - public TournamentRegistrar() - { - Timer.DelayCall( TimeSpan.FromSeconds( 30.0 ), TimeSpan.FromSeconds( 30.0 ), Announce_Callback ); - } - - private void Announce_Callback() - { - Tournament tourny = null; - - if ( Tournament != null ) - tourny = Tournament.Tournament; - - if ( tourny != null && tourny.Stage == TournamentStage.Signup ) - PublicOverheadMessage( MessageType.Regular, 0x35, false, "Come one, come all! Do you aspire to be a fighter of great renown? Join this tournament and show the world your abilities." ); - } - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); - - Tournament tourny = null; - - if ( Tournament != null ) - tourny = Tournament.Tournament; - - if ( InRange( m, 4 ) && !InRange( oldLocation, 4 ) && tourny != null && tourny.Stage == TournamentStage.Signup && m.CanBeginAction( this ) ) - { - Ladder ladder = Ladder.Instance; - - LadderEntry entry = ladder?.Find( m ); - - if ( entry != null && Ladder.GetLevel( entry.Experience ) < tourny.LevelRequirement ) - return; - - if ( tourny.IsFactionRestricted && Faction.Find( m ) == null ) - { - return; - } - - if ( tourny.HasParticipant( m ) ) - return; - - PrivateOverheadMessage( MessageType.Regular, 0x35, false, - $"Hello m'{(m.Female ? "Lady" : "Lord")}. Dost thou wish to enter this tournament? You need only to write your name in this book.", m.NetState ); - m.BeginAction( this ); - Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), new TimerStateCallback( ReleaseLock_Callback ), m ); - } - } - - private void ReleaseLock_Callback( object obj ) - { - ((Mobile)obj).EndAction( this ); - } - - public TournamentRegistrar( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - writer.Write( (Item) Tournament ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Tournament = reader.ReadItem() as TournamentController; - break; - } - } - - Timer.DelayCall( TimeSpan.FromSeconds( 30.0 ), TimeSpan.FromSeconds( 30.0 ), Announce_Callback ); - } - } - - public class TournamentSignupItem : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public TournamentController Tournament { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Registrar { get; set; } - - public override string DefaultName => "tournament signup book"; - - [Constructible] - public TournamentSignupItem() : base( 4029 ) - { - Movable = false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that - } - else - { - Tournament tourny = Tournament?.Tournament; - - if ( tourny != null ) - { - if ( Registrar != null ) - Registrar.Direction = Registrar.GetDirectionTo( this ); - - switch ( tourny.Stage ) - { - case TournamentStage.Fighting: - { - if ( Registrar != null ) - { - if ( tourny.HasParticipant( from ) ) - { - Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "Excuse me? You are already signed up.", from.NetState ); - } - else - { - Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "The tournament has already begun. You are too late to signup now.", from.NetState ); - } - } - - break; - } - case TournamentStage.Inactive: - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "The tournament is closed.", from.NetState ); - - break; - } - case TournamentStage.Signup: - { - Ladder ladder = Ladder.Instance; - LadderEntry entry = ladder?.Find( from ); - - if ( entry != null && Ladder.GetLevel( entry.Experience ) < tourny.LevelRequirement ) - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "You have not yet proven yourself a worthy dueler.", from.NetState ); - - break; - } - - if ( tourny.IsFactionRestricted && Faction.Find( from ) == null ) - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "Only those who have declared their faction allegiance may participate.", from.NetState ); - - break; - } - - if ( from.HasGump( typeof( AcceptTeamGump ) ) ) - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "You must first respond to the offer I've given you.", from.NetState ); - } - else if ( from.HasGump( typeof( AcceptDuelGump ) ) ) - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "You must first cancel your duel offer.", from.NetState ); - } - else if ( from is PlayerMobile mobile && mobile.DuelContext != null ) - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "You are already participating in a duel.", mobile.NetState ); - } - else if ( !tourny.HasParticipant( from ) ) - { - ArrayList players = new ArrayList(); - players.Add(from); - from.CloseGump( typeof( ConfirmSignupGump ) ); - from.SendGump( new ConfirmSignupGump( from, Registrar, tourny, players ) ); - } - else - { - Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "You have already entered this tournament.", from.NetState ); - } - - break; - } - } - } - } - } - - public TournamentSignupItem( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - writer.Write( (Item) Tournament ); - writer.Write( (Mobile) Registrar ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Tournament = reader.ReadItem() as TournamentController; - Registrar = reader.ReadMobile(); - break; - } - } - } - } - - public class ConfirmSignupGump : Gump - { - private Mobile m_From; - private Tournament m_Tournament; - private ArrayList m_Players; - private Mobile m_Registrar; - - private const int BlackColor32 = 0x000008; - private const int LabelColor32 = 0xFFFFFF; - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - private void AddBorderedText( int x, int y, int width, int height, string text, int color, int borderColor ) - { - AddColoredText( x - 1, y - 1, width, height, text, borderColor ); - AddColoredText( x - 1, y + 1, width, height, text, borderColor ); - AddColoredText( x + 1, y - 1, width, height, text, borderColor ); - AddColoredText( x + 1, y + 1, width, height, text, borderColor ); - AddColoredText( x, y, width, height, text, color ); - } - - private void AddColoredText( int x, int y, int width, int height, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, height, text, false, false ); - else - AddHtml( x, y, width, height, Color( text, color ), false, false ); - } - - public void AddGoldenButton( int x, int y, int bid ) - { - AddButton( x , y , 0xD2, 0xD2, bid, GumpButtonType.Reply, 0 ); - AddButton( x+3, y+3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0 ); - } - - public ConfirmSignupGump( Mobile from, Mobile registrar, Tournament tourny, ArrayList players ) : base( 50, 50 ) - { - m_From = from; - m_Registrar = registrar; - m_Tournament = tourny; - m_Players = players; - - m_From.CloseGump( typeof( AcceptTeamGump ) ); - m_From.CloseGump( typeof( AcceptDuelGump ) ); - m_From.CloseGump( typeof( DuelContextGump ) ); - m_From.CloseGump( typeof( ConfirmSignupGump ) ); - - #region Rules - Ruleset ruleset = tourny.Ruleset; - Ruleset basedef = ruleset.Base; - - int height = 185 + 60 + 12; - - int changes = 0; - - BitArray defs; - - if ( ruleset.Flavors.Count > 0 ) - { - defs = new BitArray( basedef.Options ); - - for ( int i = 0; i < ruleset.Flavors.Count; ++i ) - defs.Or( ((Ruleset)ruleset.Flavors[i]).Options ); - - height += ruleset.Flavors.Count * 18; - } - else - { - defs = basedef.Options; - } - - BitArray opts = ruleset.Options; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - ++changes; - } - - height += (changes * 22); - - height += 10 + 22 + 25 + 25; - - if ( tourny.PlayersPerParticipant > 1 ) - height += 36 + (tourny.PlayersPerParticipant * 20); - #endregion - - Closable = false; - - AddPage( 0 ); - - //AddBackground( 0, 0, 400, 220, 9150 ); - AddBackground( 1, 1, 398, height, 3600 ); - //AddBackground( 16, 15, 369, 189, 9100 ); - - AddImageTiled( 16, 15, 369, height - 29, 3604 ); - AddAlphaRegion( 16, 15, 369, height - 29 ); - - AddImage( 215, -43, 0xEE40 ); - //AddImage( 330, 141, 0x8BA ); - - StringBuilder sb = new StringBuilder(); - - if ( tourny.TournyType == TournyType.FreeForAll ) - { - sb.Append( "FFA" ); - } - else if ( tourny.TournyType == TournyType.RandomTeam ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-Team" ); - } - else if ( tourny.TournyType == TournyType.Faction ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-Team Faction" ); - } - else if ( tourny.TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else - { - for ( int i = 0; i < tourny.ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); - - sb.Append( tourny.PlayersPerParticipant ); - } - } - - if ( tourny.EventController != null ) - sb.Append( ' ' ).Append( tourny.EventController.Title ); - - sb.Append( " Tournament Signup" ); - - AddBorderedText( 22, 22, 294, 20, Center( sb.ToString() ), LabelColor32, BlackColor32 ); - AddBorderedText( 22, 50, 294, 40, "You have requested to join the tournament. Do you accept the rules?", 0xB0C868, BlackColor32 ); - - AddImageTiled( 32, 88, 264, 1, 9107 ); - AddImageTiled( 42, 90, 264, 1, 9157 ); - - #region Rules - int y = 100; - - string groupText = null; - - switch ( tourny.GroupType ) - { - case GroupingType.HighVsLow: groupText = "High vs Low"; break; - case GroupingType.Nearest: groupText = "Closest opponent"; break; - case GroupingType.Random: groupText = "Random"; break; - } - - AddBorderedText( 35, y, 190, 20, $"Grouping: {groupText}", LabelColor32, BlackColor32 ); - y += 20; - - string tieText = null; - - switch ( tourny.TieType ) - { - case TieType.Random: tieText = "Random"; break; - case TieType.Highest: tieText = "Highest advances"; break; - case TieType.Lowest: tieText = "Lowest advances"; break; - case TieType.FullAdvancement: tieText = ( tourny.ParticipantsPerMatch == 2 ? "Both advance" : "Everyone advances" ); break; - case TieType.FullElimination: tieText = ( tourny.ParticipantsPerMatch == 2 ? "Both eliminated" : "Everyone eliminated" ); break; - } - - AddBorderedText( 35, y, 190, 20, $"Tiebreaker: {tieText}", LabelColor32, BlackColor32 ); - y += 20; - - string sdText = "Off"; - - if ( tourny.SuddenDeath > TimeSpan.Zero ) - { - sdText = $"{(int) tourny.SuddenDeath.TotalMinutes}:{tourny.SuddenDeath.Seconds:D2}"; - - if ( tourny.SuddenDeathRounds > 0 ) - sdText = $"{sdText} (first {tourny.SuddenDeathRounds} rounds)"; - else - sdText = $"{sdText} (all rounds)"; - } - - AddBorderedText( 35, y, 240, 20, $"Sudden Death: {sdText}", LabelColor32, BlackColor32 ); - y += 20; - - y += 6; - AddImageTiled( 32, y-1, 264, 1, 9107 ); - AddImageTiled( 42, y+1, 264, 1, 9157 ); - y += 6; - - AddBorderedText( 35, y, 190, 20, $"Ruleset: {basedef.Title}", LabelColor32, BlackColor32 ); - y += 20; - - for ( int i = 0; i < ruleset.Flavors.Count; ++i, y += 18 ) - AddBorderedText( 35, y, 190, 20, $" + {((Ruleset) ruleset.Flavors[i]).Title}", LabelColor32, BlackColor32 ); - - y += 4; - - if ( changes > 0 ) - { - AddBorderedText( 35, y, 190, 20, "Modifications:", LabelColor32, BlackColor32 ); - y += 20; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - { - string name = ruleset.Layout.FindByIndex( i ); - - if ( name != null ) // sanity - { - AddImage( 35, y, opts[i] ? 0xD3 : 0xD2 ); - AddBorderedText( 60, y, 165, 22, name, LabelColor32, BlackColor32 ); - } - - y += 22; - } - } - } - else - { - AddBorderedText( 35, y, 190, 20, "Modifications: None", LabelColor32, BlackColor32 ); - y += 20; - } - #endregion - - #region Team - if ( tourny.PlayersPerParticipant > 1 ) - { - y += 8; - AddImageTiled( 32, y-1, 264, 1, 9107 ); - AddImageTiled( 42, y+1, 264, 1, 9157 ); - y += 8; - - AddBorderedText( 35, y, 190, 20, "Your Team", LabelColor32, BlackColor32 ); - y += 20; - - for ( int i = 0; i < players.Count; ++i, y += 20 ) - { - if ( i == 0 ) - AddImage( 35, y, 0xD2 ); - else - AddGoldenButton( 35, y, 1 + i ); - - AddBorderedText( 60, y, 200, 20, ((Mobile)players[i]).Name, LabelColor32, BlackColor32 ); - } - - for ( int i = players.Count; i < tourny.PlayersPerParticipant; ++i, y += 20 ) - { - if ( i == 0 ) - AddImage( 35, y, 0xD2 ); - else - AddGoldenButton( 35, y, 1 + i ); - - AddBorderedText( 60, y, 200, 20, "(Empty)", LabelColor32, BlackColor32 ); - } - } - #endregion - - y += 8; - AddImageTiled( 32, y-1, 264, 1, 9107 ); - AddImageTiled( 42, y+1, 264, 1, 9157 ); - y += 8; - - AddRadio( 24, y, 9727, 9730, true, 1 ); - AddBorderedText( 60, y+5, 250, 20, "Yes, I wish to join the tournament.", LabelColor32, BlackColor32 ); - y += 35; - - AddRadio( 24, y, 9727, 9730, false, 2 ); - AddBorderedText( 60, y+5, 250, 20, "No, I do not wish to join.", LabelColor32, BlackColor32 ); - y += 35; - - y -= 3; - AddButton( 314, y, 247, 248, 1, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 && info.IsSwitched( 1 ) ) - { - Tournament tourny = m_Tournament; - Mobile from = m_From; - - switch ( tourny.Stage ) - { - case TournamentStage.Fighting: - { - if ( m_Registrar != null ) - { - if ( m_Tournament.HasParticipant( from ) ) - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "Excuse me? You are already signed up.", from.NetState ); - } - else - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "The tournament has already begun. You are too late to signup now.", from.NetState ); - } - } - - break; - } - case TournamentStage.Inactive: - { - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "The tournament is closed.", from.NetState ); - - break; - } - case TournamentStage.Signup: - { - if ( m_Players.Count != tourny.PlayersPerParticipant ) - { - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "You have not yet chosen your team.", from.NetState ); - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - break; - } - - Ladder ladder = Ladder.Instance; - - for ( int i = 0; i < m_Players.Count; ++i ) - { - Mobile mob = (Mobile)m_Players[i]; - - LadderEntry entry = ladder?.Find( mob ); - - if ( entry != null && Ladder.GetLevel( entry.Experience ) < tourny.LevelRequirement ) - { - if ( m_Registrar != null ) - { - if ( mob == from ) - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "You have not yet proven yourself a worthy dueler.", from.NetState ); - } - else - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, $"{mob.Name} has not yet proven themselves a worthy dueler.", from.NetState ); - } - } - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - return; - } - if ( tourny.IsFactionRestricted && Faction.Find( mob ) == null ) - { - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "Only those who have declared their faction allegiance may participate.", from.NetState ); - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - return; - } - if ( tourny.HasParticipant( mob ) ) - { - if ( m_Registrar != null ) - { - if ( mob == from ) - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "You have already entered this tournament.", from.NetState ); - } - else - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, $"{mob.Name} has already entered this tournament.", from.NetState ); - } - } - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - return; - } - if ( mob is PlayerMobile mobile && mobile.DuelContext != null ) - { - if ( mob == from ) - { - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, "You are already assigned to a duel. You must yield it before joining this tournament.", from.NetState ); - } - else - { - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, - $"{mobile.Name} is already assigned to a duel. They must yield it before joining this tournament.", from.NetState ); - } - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - return; - } - } - - if ( m_Registrar != null ) - { - string fmt; - - if ( tourny.PlayersPerParticipant == 1 ) - fmt = "As you say m'{0}. I've written your name to the bracket. The tournament will begin {1}."; - else if ( tourny.PlayersPerParticipant == 2 ) - fmt = "As you wish m'{0}. The tournament will begin {1}, but first you must name your partner."; - else - fmt = "As you wish m'{0}. The tournament will begin {1}, but first you must name your team."; - - string timeUntil; - int minutesUntil = (int)Math.Round( ( (tourny.SignupStart + tourny.SignupPeriod) - DateTime.UtcNow ).TotalMinutes ); - - if ( minutesUntil == 0 ) - timeUntil = "momentarily"; - else - timeUntil = $"in {minutesUntil} minute{(minutesUntil == 1 ? "" : "s")}"; - - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x35, false, string.Format( fmt, from.Female ? "Lady" : "Lord", timeUntil ), from.NetState ); - } - - TournyParticipant part = new TournyParticipant( from ); - part.Players.Clear(); - part.Players.AddRange( m_Players ); - - tourny.Participants.Add( part ); - - break; - } - } - } - else if ( info.ButtonID > 1 ) - { - int index = info.ButtonID-1; - - if ( index > 0 && index < m_Players.Count ) - { - m_Players.RemoveAt( index ); - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - } - else if ( m_Players.Count < m_Tournament.PlayersPerParticipant ) - { - m_From.BeginTarget( 12, false, TargetFlags.None, AddPlayer_OnTarget ); - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - } - } - } - - private void AddPlayer_OnTarget( Mobile from, object obj ) - { - if ( !(obj is Mobile mob) || mob == from ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "Excuse me?", from.NetState ); - } - else if ( !mob.Player ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - if ( mob.Body.IsHuman ) - mob.SayTo( from, 1005443 ); // Nay, I would rather stay here and watch a nail rust. - else - mob.SayTo( from, 1005444 ); // The creature ignores your offer. - } - else if ( AcceptDuelGump.IsIgnored( mob, from ) || mob.Blessed ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They ignore your invitation.", from.NetState ); - } - else - { - if ( !(mob is PlayerMobile pm) ) - return; - - if ( pm.DuelContext != null ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They are already assigned to another duel.", from.NetState ); - } - else if ( mob.HasGump( typeof( AcceptTeamGump ) ) ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They have already been offered a partnership.", from.NetState ); - } - else if ( mob.HasGump( typeof( ConfirmSignupGump ) ) ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They are already trying to join this tournament.", from.NetState ); - } - else if ( m_Players.Contains( mob ) ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "You have already named them as a team member.", from.NetState ); - } - else if ( m_Tournament.HasParticipant( mob ) ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They have already entered this tournament.", from.NetState ); - } - else if ( m_Players.Count >= m_Tournament.PlayersPerParticipant ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "Your team is full.", from.NetState ); - } - else - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - mob.SendGump( new AcceptTeamGump( from, mob, m_Tournament, m_Registrar, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x59, false, - $"As you command m'{(from.Female ? "Lady" : "Lord")}. I've given your offer to {mob.Name}.", from.NetState ); - } - } - } - } - - public class AcceptTeamGump : Gump - { - private bool m_Active; - - private Mobile m_From; - private Mobile m_Requested; - private Tournament m_Tournament; - private Mobile m_Registrar; - private ArrayList m_Players; - - private const int BlackColor32 = 0x000008; - private const int LabelColor32 = 0xFFFFFF; - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - private void AddBorderedText( int x, int y, int width, int height, string text, int color, int borderColor ) - { - AddColoredText( x - 1, y - 1, width, height, text, borderColor ); - AddColoredText( x - 1, y + 1, width, height, text, borderColor ); - AddColoredText( x + 1, y - 1, width, height, text, borderColor ); - AddColoredText( x + 1, y + 1, width, height, text, borderColor ); - AddColoredText( x, y, width, height, text, color ); - } - - private void AddColoredText( int x, int y, int width, int height, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, height, text, false, false ); - else - AddHtml( x, y, width, height, Color( text, color ), false, false ); - } - - public AcceptTeamGump( Mobile from, Mobile requested, Tournament tourny, Mobile registrar, ArrayList players ) : base( 50, 50 ) - { - m_From = from; - m_Requested = requested; - m_Tournament = tourny; - m_Registrar = registrar; - m_Players = players; - - m_Active = true; - - #region Rules - Ruleset ruleset = tourny.Ruleset; - Ruleset basedef = ruleset.Base; - - int height = 185 + 35 + 60 + 12; - - int changes = 0; - - BitArray defs; - - if ( ruleset.Flavors.Count > 0 ) - { - defs = new BitArray( basedef.Options ); - - for ( int i = 0; i < ruleset.Flavors.Count; ++i ) - defs.Or( ((Ruleset)ruleset.Flavors[i]).Options ); - - height += ruleset.Flavors.Count * 18; - } - else - { - defs = basedef.Options; - } - - BitArray opts = ruleset.Options; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - ++changes; - } - - height += (changes * 22); - - height += 10 + 22 + 25 + 25; - #endregion - - Closable = false; - - AddPage( 0 ); - - AddBackground( 1, 1, 398, height, 3600 ); - - AddImageTiled( 16, 15, 369, height - 29, 3604 ); - AddAlphaRegion( 16, 15, 369, height - 29 ); - - AddImage( 215, -43, 0xEE40 ); - - StringBuilder sb = new StringBuilder(); - - if ( tourny.TournyType == TournyType.FreeForAll ) - { - sb.Append( "FFA" ); - } - else if ( tourny.TournyType == TournyType.RandomTeam ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-Team" ); - } - else if ( tourny.TournyType == TournyType.Faction ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-Team Faction" ); - } - else if ( tourny.TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else - { - for ( int i = 0; i < tourny.ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); - - sb.Append( tourny.PlayersPerParticipant ); - } - } - - if ( tourny.EventController != null ) - sb.Append( ' ' ).Append( tourny.EventController.Title ); - - sb.Append( " Tournament Invitation" ); - - AddBorderedText( 22, 22, 294, 20, Center( sb.ToString() ), LabelColor32, BlackColor32 ); - - AddBorderedText( 22, 50, 294, 40, - $"You have been asked to partner with {from.Name} in a tournament. Do you accept?", - 0xB0C868, BlackColor32 ); - - AddImageTiled( 32, 88, 264, 1, 9107 ); - AddImageTiled( 42, 90, 264, 1, 9157 ); - - #region Rules - int y = 100; - - string groupText = null; + public enum TournamentStage + { + Inactive, + Signup, + Fighting + } + + public enum GroupingType + { + HighVsLow, + Nearest, + Random + } + + public enum TieType + { + Random, + Highest, + Lowest, + FullElimination, + FullAdvancement + } + + public class TournamentRegistrar : Banker + { + [Constructible] + public TournamentRegistrar() + { + Timer.DelayCall(TimeSpan.FromSeconds(30.0), TimeSpan.FromSeconds(30.0), Announce_Callback); + } + + public TournamentRegistrar(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public TournamentController Tournament{ get; set; } + + private void Announce_Callback() + { + Tournament tourny = null; + + if (Tournament != null) + tourny = Tournament.Tournament; + + if (tourny != null && tourny.Stage == TournamentStage.Signup) + PublicOverheadMessage(MessageType.Regular, 0x35, false, + "Come one, come all! Do you aspire to be a fighter of great renown? Join this tournament and show the world your abilities."); + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); + + Tournament tourny = null; + + if (Tournament != null) + tourny = Tournament.Tournament; + + if (InRange(m, 4) && !InRange(oldLocation, 4) && tourny != null && tourny.Stage == TournamentStage.Signup && + m.CanBeginAction(this)) + { + Ladder ladder = Ladder.Instance; + + LadderEntry entry = ladder?.Find(m); + + if (entry != null && Ladder.GetLevel(entry.Experience) < tourny.LevelRequirement) + return; + + if (tourny.IsFactionRestricted && Faction.Find(m) == null) return; + + if (tourny.HasParticipant(m)) + return; + + PrivateOverheadMessage(MessageType.Regular, 0x35, false, + $"Hello m'{(m.Female ? "Lady" : "Lord")}. Dost thou wish to enter this tournament? You need only to write your name in this book.", + m.NetState); + m.BeginAction(this); + Timer.DelayCall(TimeSpan.FromSeconds(10.0), new TimerStateCallback(ReleaseLock_Callback), m); + } + } + + private void ReleaseLock_Callback(object obj) + { + ((Mobile)obj).EndAction(this); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.Write(Tournament); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Tournament = reader.ReadItem() as TournamentController; + break; + } + } + + Timer.DelayCall(TimeSpan.FromSeconds(30.0), TimeSpan.FromSeconds(30.0), Announce_Callback); + } + } + + public class TournamentSignupItem : Item + { + [Constructible] + public TournamentSignupItem() : base(4029) + { + Movable = false; + } + + public TournamentSignupItem(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public TournamentController Tournament{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Registrar{ get; set; } + + public override string DefaultName => "tournament signup book"; + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that + } + else + { + Tournament tourny = Tournament?.Tournament; + + if (tourny != null) + { + if (Registrar != null) + Registrar.Direction = Registrar.GetDirectionTo(this); + + switch (tourny.Stage) + { + case TournamentStage.Fighting: + { + if (Registrar != null) + { + if (tourny.HasParticipant(from)) + Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "Excuse me? You are already signed up.", from.NetState); + else + Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "The tournament has already begun. You are too late to signup now.", + from.NetState); + } + + break; + } + case TournamentStage.Inactive: + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "The tournament is closed.", from.NetState); + + break; + } + case TournamentStage.Signup: + { + Ladder ladder = Ladder.Instance; + LadderEntry entry = ladder?.Find(from); + + if (entry != null && Ladder.GetLevel(entry.Experience) < tourny.LevelRequirement) + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "You have not yet proven yourself a worthy dueler.", from.NetState); + + break; + } + + if (tourny.IsFactionRestricted && Faction.Find(from) == null) + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "Only those who have declared their faction allegiance may participate.", + from.NetState); + + break; + } + + if (from.HasGump(typeof(AcceptTeamGump))) + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "You must first respond to the offer I've given you.", from.NetState); + } + else if (from.HasGump(typeof(AcceptDuelGump))) + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "You must first cancel your duel offer.", from.NetState); + } + else if (from is PlayerMobile mobile && mobile.DuelContext != null) + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "You are already participating in a duel.", mobile.NetState); + } + else if (!tourny.HasParticipant(from)) + { + ArrayList players = new ArrayList(); + players.Add(from); + from.CloseGump(typeof(ConfirmSignupGump)); + from.SendGump(new ConfirmSignupGump(from, Registrar, tourny, players)); + } + else + { + Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "You have already entered this tournament.", from.NetState); + } + + break; + } + } + } + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.Write(Tournament); + writer.Write(Registrar); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Tournament = reader.ReadItem() as TournamentController; + Registrar = reader.ReadMobile(); + break; + } + } + } + } + + public class ConfirmSignupGump : Gump + { + private const int BlackColor32 = 0x000008; + private const int LabelColor32 = 0xFFFFFF; + private Mobile m_From; + private ArrayList m_Players; + private Mobile m_Registrar; + private Tournament m_Tournament; + + public ConfirmSignupGump(Mobile from, Mobile registrar, Tournament tourny, ArrayList players) : base(50, 50) + { + m_From = from; + m_Registrar = registrar; + m_Tournament = tourny; + m_Players = players; + + m_From.CloseGump(typeof(AcceptTeamGump)); + m_From.CloseGump(typeof(AcceptDuelGump)); + m_From.CloseGump(typeof(DuelContextGump)); + m_From.CloseGump(typeof(ConfirmSignupGump)); + + #region Rules + + Ruleset ruleset = tourny.Ruleset; + Ruleset basedef = ruleset.Base; + + int height = 185 + 60 + 12; + + int changes = 0; + + BitArray defs; + + if (ruleset.Flavors.Count > 0) + { + defs = new BitArray(basedef.Options); + + for (int i = 0; i < ruleset.Flavors.Count; ++i) + defs.Or(((Ruleset)ruleset.Flavors[i]).Options); + + height += ruleset.Flavors.Count * 18; + } + else + { + defs = basedef.Options; + } + + BitArray opts = ruleset.Options; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + ++changes; + + height += changes * 22; + + height += 10 + 22 + 25 + 25; + + if (tourny.PlayersPerParticipant > 1) + height += 36 + tourny.PlayersPerParticipant * 20; + + #endregion + + Closable = false; + + AddPage(0); + + //AddBackground( 0, 0, 400, 220, 9150 ); + AddBackground(1, 1, 398, height, 3600); + //AddBackground( 16, 15, 369, 189, 9100 ); + + AddImageTiled(16, 15, 369, height - 29, 3604); + AddAlphaRegion(16, 15, 369, height - 29); + + AddImage(215, -43, 0xEE40); + //AddImage( 330, 141, 0x8BA ); + + StringBuilder sb = new StringBuilder(); + + if (tourny.TournyType == TournyType.FreeForAll) + { + sb.Append("FFA"); + } + else if (tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-Team"); + } + else if (tourny.TournyType == TournyType.Faction) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-Team Faction"); + } + else if (tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (tourny.EventController != null) + sb.Append(' ').Append(tourny.EventController.Title); + + sb.Append(" Tournament Signup"); + + AddBorderedText(22, 22, 294, 20, Center(sb.ToString()), LabelColor32, BlackColor32); + AddBorderedText(22, 50, 294, 40, "You have requested to join the tournament. Do you accept the rules?", 0xB0C868, + BlackColor32); + + AddImageTiled(32, 88, 264, 1, 9107); + AddImageTiled(42, 90, 264, 1, 9157); + + #region Rules + + int y = 100; + + string groupText = null; + + switch (tourny.GroupType) + { + case GroupingType.HighVsLow: + groupText = "High vs Low"; + break; + case GroupingType.Nearest: + groupText = "Closest opponent"; + break; + case GroupingType.Random: + groupText = "Random"; + break; + } + + AddBorderedText(35, y, 190, 20, $"Grouping: {groupText}", LabelColor32, BlackColor32); + y += 20; + + string tieText = null; + + switch (tourny.TieType) + { + case TieType.Random: + tieText = "Random"; + break; + case TieType.Highest: + tieText = "Highest advances"; + break; + case TieType.Lowest: + tieText = "Lowest advances"; + break; + case TieType.FullAdvancement: + tieText = tourny.ParticipantsPerMatch == 2 ? "Both advance" : "Everyone advances"; + break; + case TieType.FullElimination: + tieText = tourny.ParticipantsPerMatch == 2 ? "Both eliminated" : "Everyone eliminated"; + break; + } + + AddBorderedText(35, y, 190, 20, $"Tiebreaker: {tieText}", LabelColor32, BlackColor32); + y += 20; + + string sdText = "Off"; + + if (tourny.SuddenDeath > TimeSpan.Zero) + { + sdText = $"{(int)tourny.SuddenDeath.TotalMinutes}:{tourny.SuddenDeath.Seconds:D2}"; + + if (tourny.SuddenDeathRounds > 0) + sdText = $"{sdText} (first {tourny.SuddenDeathRounds} rounds)"; + else + sdText = $"{sdText} (all rounds)"; + } + + AddBorderedText(35, y, 240, 20, $"Sudden Death: {sdText}", LabelColor32, BlackColor32); + y += 20; + + y += 6; + AddImageTiled(32, y - 1, 264, 1, 9107); + AddImageTiled(42, y + 1, 264, 1, 9157); + y += 6; + + AddBorderedText(35, y, 190, 20, $"Ruleset: {basedef.Title}", LabelColor32, BlackColor32); + y += 20; + + for (int i = 0; i < ruleset.Flavors.Count; ++i, y += 18) + AddBorderedText(35, y, 190, 20, $" + {((Ruleset)ruleset.Flavors[i]).Title}", LabelColor32, BlackColor32); + + y += 4; + + if (changes > 0) + { + AddBorderedText(35, y, 190, 20, "Modifications:", LabelColor32, BlackColor32); + y += 20; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + { + string name = ruleset.Layout.FindByIndex(i); + + if (name != null) // sanity + { + AddImage(35, y, opts[i] ? 0xD3 : 0xD2); + AddBorderedText(60, y, 165, 22, name, LabelColor32, BlackColor32); + } + + y += 22; + } + } + else + { + AddBorderedText(35, y, 190, 20, "Modifications: None", LabelColor32, BlackColor32); + y += 20; + } + + #endregion + + #region Team + + if (tourny.PlayersPerParticipant > 1) + { + y += 8; + AddImageTiled(32, y - 1, 264, 1, 9107); + AddImageTiled(42, y + 1, 264, 1, 9157); + y += 8; + + AddBorderedText(35, y, 190, 20, "Your Team", LabelColor32, BlackColor32); + y += 20; + + for (int i = 0; i < players.Count; ++i, y += 20) + { + if (i == 0) + AddImage(35, y, 0xD2); + else + AddGoldenButton(35, y, 1 + i); + + AddBorderedText(60, y, 200, 20, ((Mobile)players[i]).Name, LabelColor32, BlackColor32); + } + + for (int i = players.Count; i < tourny.PlayersPerParticipant; ++i, y += 20) + { + if (i == 0) + AddImage(35, y, 0xD2); + else + AddGoldenButton(35, y, 1 + i); + + AddBorderedText(60, y, 200, 20, "(Empty)", LabelColor32, BlackColor32); + } + } + + #endregion + + y += 8; + AddImageTiled(32, y - 1, 264, 1, 9107); + AddImageTiled(42, y + 1, 264, 1, 9157); + y += 8; + + AddRadio(24, y, 9727, 9730, true, 1); + AddBorderedText(60, y + 5, 250, 20, "Yes, I wish to join the tournament.", LabelColor32, BlackColor32); + y += 35; + + AddRadio(24, y, 9727, 9730, false, 2); + AddBorderedText(60, y + 5, 250, 20, "No, I do not wish to join.", LabelColor32, BlackColor32); + y += 35; + + y -= 3; + AddButton(314, y, 247, 248, 1, GumpButtonType.Reply, 0); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + + public void AddGoldenButton(int x, int y, int bid) + { + AddButton(x, y, 0xD2, 0xD2, bid, GumpButtonType.Reply, 0); + AddButton(x + 3, y + 3, 0xD8, 0xD8, bid, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1 && info.IsSwitched(1)) + { + Tournament tourny = m_Tournament; + Mobile from = m_From; + + switch (tourny.Stage) + { + case TournamentStage.Fighting: + { + if (m_Registrar != null) + { + if (m_Tournament.HasParticipant(from)) + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "Excuse me? You are already signed up.", from.NetState); + else + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "The tournament has already begun. You are too late to signup now.", + from.NetState); + } + + break; + } + case TournamentStage.Inactive: + { + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "The tournament is closed.", from.NetState); + + break; + } + case TournamentStage.Signup: + { + if (m_Players.Count != tourny.PlayersPerParticipant) + { + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "You have not yet chosen your team.", from.NetState); + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + break; + } + + Ladder ladder = Ladder.Instance; + + for (int i = 0; i < m_Players.Count; ++i) + { + Mobile mob = (Mobile)m_Players[i]; + + LadderEntry entry = ladder?.Find(mob); + + if (entry != null && Ladder.GetLevel(entry.Experience) < tourny.LevelRequirement) + { + if (m_Registrar != null) + { + if (mob == from) + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "You have not yet proven yourself a worthy dueler.", from.NetState); + else + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, $"{mob.Name} has not yet proven themselves a worthy dueler.", + from.NetState); + } + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + return; + } + + if (tourny.IsFactionRestricted && Faction.Find(mob) == null) + { + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "Only those who have declared their faction allegiance may participate.", + from.NetState); + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + return; + } + + if (tourny.HasParticipant(mob)) + { + if (m_Registrar != null) + { + if (mob == from) + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, "You have already entered this tournament.", from.NetState); + else + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, $"{mob.Name} has already entered this tournament.", from.NetState); + } + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + return; + } + + if (mob is PlayerMobile mobile && mobile.DuelContext != null) + { + if (mob == from) + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, + "You are already assigned to a duel. You must yield it before joining this tournament.", + from.NetState); + else + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, + $"{mobile.Name} is already assigned to a duel. They must yield it before joining this tournament.", + from.NetState); + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + return; + } + } + + if (m_Registrar != null) + { + string fmt; + + if (tourny.PlayersPerParticipant == 1) + fmt = + "As you say m'{0}. I've written your name to the bracket. The tournament will begin {1}."; + else if (tourny.PlayersPerParticipant == 2) + fmt = + "As you wish m'{0}. The tournament will begin {1}, but first you must name your partner."; + else + fmt = "As you wish m'{0}. The tournament will begin {1}, but first you must name your team."; + + string timeUntil; + int minutesUntil = (int)Math.Round((tourny.SignupStart + tourny.SignupPeriod - DateTime.UtcNow) + .TotalMinutes); + + if (minutesUntil == 0) + timeUntil = "momentarily"; + else + timeUntil = $"in {minutesUntil} minute{(minutesUntil == 1 ? "" : "s")}"; + + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x35, false, string.Format(fmt, from.Female ? "Lady" : "Lord", timeUntil), from.NetState); + } + + TournyParticipant part = new TournyParticipant(from); + part.Players.Clear(); + part.Players.AddRange(m_Players); + + tourny.Participants.Add(part); + + break; + } + } + } + else if (info.ButtonID > 1) + { + int index = info.ButtonID - 1; + + if (index > 0 && index < m_Players.Count) + { + m_Players.RemoveAt(index); + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + } + else if (m_Players.Count < m_Tournament.PlayersPerParticipant) + { + m_From.BeginTarget(12, false, TargetFlags.None, AddPlayer_OnTarget); + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + } + } + } + + private void AddPlayer_OnTarget(Mobile from, object obj) + { + if (!(obj is Mobile mob) || mob == from) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "Excuse me?", from.NetState); + } + else if (!mob.Player) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + if (mob.Body.IsHuman) + mob.SayTo(from, 1005443); // Nay, I would rather stay here and watch a nail rust. + else + mob.SayTo(from, 1005444); // The creature ignores your offer. + } + else if (AcceptDuelGump.IsIgnored(mob, from) || mob.Blessed) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They ignore your invitation.", from.NetState); + } + else + { + if (!(mob is PlayerMobile pm)) + return; + + if (pm.DuelContext != null) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They are already assigned to another duel.", from.NetState); + } + else if (mob.HasGump(typeof(AcceptTeamGump))) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They have already been offered a partnership.", from.NetState); + } + else if (mob.HasGump(typeof(ConfirmSignupGump))) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They are already trying to join this tournament.", from.NetState); + } + else if (m_Players.Contains(mob)) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "You have already named them as a team member.", from.NetState); + } + else if (m_Tournament.HasParticipant(mob)) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They have already entered this tournament.", from.NetState); + } + else if (m_Players.Count >= m_Tournament.PlayersPerParticipant) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "Your team is full.", from.NetState); + } + else + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + mob.SendGump(new AcceptTeamGump(from, mob, m_Tournament, m_Registrar, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x59, false, + $"As you command m'{(from.Female ? "Lady" : "Lord")}. I've given your offer to {mob.Name}.", + from.NetState); + } + } + } + } + + public class AcceptTeamGump : Gump + { + private const int BlackColor32 = 0x000008; + private const int LabelColor32 = 0xFFFFFF; + private bool m_Active; + + private Mobile m_From; + private ArrayList m_Players; + private Mobile m_Registrar; + private Mobile m_Requested; + private Tournament m_Tournament; + + public AcceptTeamGump(Mobile from, Mobile requested, Tournament tourny, Mobile registrar, ArrayList players) : + base(50, 50) + { + m_From = from; + m_Requested = requested; + m_Tournament = tourny; + m_Registrar = registrar; + m_Players = players; + + m_Active = true; + + #region Rules + + Ruleset ruleset = tourny.Ruleset; + Ruleset basedef = ruleset.Base; + + int height = 185 + 35 + 60 + 12; + + int changes = 0; + + BitArray defs; + + if (ruleset.Flavors.Count > 0) + { + defs = new BitArray(basedef.Options); + + for (int i = 0; i < ruleset.Flavors.Count; ++i) + defs.Or(((Ruleset)ruleset.Flavors[i]).Options); + + height += ruleset.Flavors.Count * 18; + } + else + { + defs = basedef.Options; + } + + BitArray opts = ruleset.Options; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + ++changes; + + height += changes * 22; + + height += 10 + 22 + 25 + 25; + + #endregion + + Closable = false; + + AddPage(0); + + AddBackground(1, 1, 398, height, 3600); + + AddImageTiled(16, 15, 369, height - 29, 3604); + AddAlphaRegion(16, 15, 369, height - 29); + + AddImage(215, -43, 0xEE40); + + StringBuilder sb = new StringBuilder(); + + if (tourny.TournyType == TournyType.FreeForAll) + { + sb.Append("FFA"); + } + else if (tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-Team"); + } + else if (tourny.TournyType == TournyType.Faction) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-Team Faction"); + } + else if (tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (tourny.EventController != null) + sb.Append(' ').Append(tourny.EventController.Title); + + sb.Append(" Tournament Invitation"); + + AddBorderedText(22, 22, 294, 20, Center(sb.ToString()), LabelColor32, BlackColor32); + + AddBorderedText(22, 50, 294, 40, + $"You have been asked to partner with {from.Name} in a tournament. Do you accept?", + 0xB0C868, BlackColor32); + + AddImageTiled(32, 88, 264, 1, 9107); + AddImageTiled(42, 90, 264, 1, 9157); + + #region Rules + + int y = 100; + + string groupText = null; + + switch (tourny.GroupType) + { + case GroupingType.HighVsLow: + groupText = "High vs Low"; + break; + case GroupingType.Nearest: + groupText = "Closest opponent"; + break; + case GroupingType.Random: + groupText = "Random"; + break; + } + + AddBorderedText(35, y, 190, 20, $"Grouping: {groupText}", LabelColor32, BlackColor32); + y += 20; + + string tieText = null; + + switch (tourny.TieType) + { + case TieType.Random: + tieText = "Random"; + break; + case TieType.Highest: + tieText = "Highest advances"; + break; + case TieType.Lowest: + tieText = "Lowest advances"; + break; + case TieType.FullAdvancement: + tieText = tourny.ParticipantsPerMatch == 2 ? "Both advance" : "Everyone advances"; + break; + case TieType.FullElimination: + tieText = tourny.ParticipantsPerMatch == 2 ? "Both eliminated" : "Everyone eliminated"; + break; + } + + AddBorderedText(35, y, 190, 20, $"Tiebreaker: {tieText}", LabelColor32, BlackColor32); + y += 20; + + string sdText = "Off"; + + if (tourny.SuddenDeath > TimeSpan.Zero) + { + sdText = $"{(int)tourny.SuddenDeath.TotalMinutes}:{tourny.SuddenDeath.Seconds:D2}"; + + if (tourny.SuddenDeathRounds > 0) + sdText = $"{sdText} (first {tourny.SuddenDeathRounds} rounds)"; + else + sdText = $"{sdText} (all rounds)"; + } + + AddBorderedText(35, y, 240, 20, $"Sudden Death: {sdText}", LabelColor32, BlackColor32); + y += 20; + + y += 6; + AddImageTiled(32, y - 1, 264, 1, 9107); + AddImageTiled(42, y + 1, 264, 1, 9157); + y += 6; + + AddBorderedText(35, y, 190, 20, $"Ruleset: {basedef.Title}", LabelColor32, BlackColor32); + y += 20; + + for (int i = 0; i < ruleset.Flavors.Count; ++i, y += 18) + AddBorderedText(35, y, 190, 20, $" + {((Ruleset)ruleset.Flavors[i]).Title}", LabelColor32, BlackColor32); + + y += 4; + + if (changes > 0) + { + AddBorderedText(35, y, 190, 20, "Modifications:", LabelColor32, BlackColor32); + y += 20; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + { + string name = ruleset.Layout.FindByIndex(i); + + if (name != null) // sanity + { + AddImage(35, y, opts[i] ? 0xD3 : 0xD2); + AddBorderedText(60, y, 165, 22, name, LabelColor32, BlackColor32); + } + + y += 22; + } + } + else + { + AddBorderedText(35, y, 190, 20, "Modifications: None", LabelColor32, BlackColor32); + y += 20; + } + + #endregion + + y += 8; + AddImageTiled(32, y - 1, 264, 1, 9107); + AddImageTiled(42, y + 1, 264, 1, 9157); + y += 8; + + AddRadio(24, y, 9727, 9730, true, 1); + AddBorderedText(60, y + 5, 250, 20, "Yes, I will join them.", LabelColor32, BlackColor32); + y += 35; + + AddRadio(24, y, 9727, 9730, false, 2); + AddBorderedText(60, y + 5, 250, 20, "No, I do not wish to fight.", LabelColor32, BlackColor32); + y += 35; + + AddRadio(24, y, 9727, 9730, false, 3); + AddBorderedText(60, y + 5, 270, 20, "No, most certainly not. Do not ask again.", LabelColor32, BlackColor32); + y += 35; + + y -= 3; + AddButton(314, y, 247, 248, 1, GumpButtonType.Reply, 0); + + Timer.DelayCall(TimeSpan.FromSeconds(15.0), AutoReject); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + + public void AutoReject() + { + if (!m_Active) + return; + + m_Active = false; + + m_Requested.CloseGump(typeof(AcceptTeamGump)); + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + if (m_Registrar != null) + { + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, $"{m_Requested.Name} seems unresponsive.", m_From.NetState); + + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, $"You have declined the partnership with {m_From.Name}.", m_Requested.NetState); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = m_From; + Mobile mob = m_Requested; + + if (info.ButtonID != 1 || !m_Active) + return; + + m_Active = false; + + if (info.IsSwitched(1)) + { + if (!(mob is PlayerMobile pm)) + return; + + if (AcceptDuelGump.IsIgnored(mob, from) || mob.Blessed) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They ignore your invitation.", from.NetState); + } + else if (pm.DuelContext != null) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They are already assigned to another duel.", from.NetState); + } + else if (m_Players.Contains(mob)) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "You have already named them as a team member.", from.NetState); + } + else if (m_Tournament.HasParticipant(mob)) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "They have already entered this tournament.", from.NetState); + } + else if (m_Players.Count >= m_Tournament.PlayersPerParticipant) + { + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + m_Registrar?.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, "Your team is full.", from.NetState); + } + else + { + m_Players.Add(mob); + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + if (m_Registrar != null) + { + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x59, false, $"{mob.Name} has accepted your offer of partnership.", from.NetState); + + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x59, false, $"You have accepted the partnership with {from.Name}.", mob.NetState); + } + } + } + else + { + if (info.IsSwitched(3)) + AcceptDuelGump.BeginIgnore(m_Requested, m_From); + + m_From.SendGump(new ConfirmSignupGump(m_From, m_Registrar, m_Tournament, m_Players)); + + if (m_Registrar != null) + { + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, $"{mob.Name} has declined your offer of partnership.", from.NetState); + + m_Registrar.PrivateOverheadMessage(MessageType.Regular, + 0x22, false, $"You have declined the partnership with {from.Name}.", mob.NetState); + } + } + } + } + + public class TournamentController : Item + { + private static ArrayList m_Instances = new ArrayList(); + private Tournament m_Tournament; + + [Constructible] + public TournamentController() : base(0x1B7A) + { + Visible = false; + Movable = false; + + m_Tournament = new Tournament(); + m_Instances.Add(this); + } + + public TournamentController(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Tournament Tournament + { + get => m_Tournament; + set { } + } + + public static bool IsActive + { + get + { + for (int i = 0; i < m_Instances.Count; ++i) + { + TournamentController controller = (TournamentController)m_Instances[i]; + + if (controller != null && !controller.Deleted && controller.Tournament != null && + controller.Tournament.Stage != TournamentStage.Inactive) + return true; + } + + return false; + } + } + + public override string DefaultName => "tournament controller"; + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.AccessLevel >= AccessLevel.GameMaster && m_Tournament != null) + { + list.Add(new EditEntry(m_Tournament)); + + if (m_Tournament.CurrentStage == TournamentStage.Inactive) + list.Add(new StartEntry(m_Tournament)); + } + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster && m_Tournament != null) + { + from.CloseGump(typeof(PickRulesetGump)); + from.CloseGump(typeof(RulesetGump)); + from.SendGump(new PickRulesetGump(from, null, m_Tournament.Ruleset)); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + m_Tournament.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Tournament = new Tournament(reader); + break; + } + } + + m_Instances.Add(this); + } + + public override void OnDelete() + { + base.OnDelete(); + + m_Instances.Remove(this); + } + + private class EditEntry : ContextMenuEntry + { + private Tournament m_Tournament; + + public EditEntry(Tournament tourny) : base(5101) + { + m_Tournament = tourny; + } + + public override void OnClick() + { + Owner.From.SendGump(new PropertiesGump(Owner.From, m_Tournament)); + } + } + + private class StartEntry : ContextMenuEntry + { + private Tournament m_Tournament; + + public StartEntry(Tournament tourny) : base(5113) + { + m_Tournament = tourny; + } + + public override void OnClick() + { + if (m_Tournament.Stage == TournamentStage.Inactive) + { + m_Tournament.SignupStart = DateTime.UtcNow; + m_Tournament.Stage = TournamentStage.Signup; + m_Tournament.Participants.Clear(); + m_Tournament.Pyramid.Levels.Clear(); + m_Tournament.Alert("Hear ye! Hear ye!", + "Tournament signup has opened. You can enter by signing up with the registrar."); + } + } + } + } + + public enum TournyType + { + Standard, + FreeForAll, + RandomTeam, + RedVsBlue, + Faction + } + + [PropertyObject] + public class Tournament + { + private static readonly TimeSpan SliceInterval = TimeSpan.FromSeconds(12.0); + private int m_ParticipantsPerMatch; + private int m_PlayersPerParticipant; + + public Tournament(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 5: + { + FactionRestricted = reader.ReadBool(); + + goto case 4; + } + case 4: + { + EventController = reader.ReadItem() as EventController; + + goto case 3; + } + case 3: + { + SuddenDeathRounds = reader.ReadEncodedInt(); + + goto case 2; + } + case 2: + { + TournyType = (TournyType)reader.ReadEncodedInt(); + + goto case 1; + } + case 1: + { + GroupType = (GroupingType)reader.ReadEncodedInt(); + TieType = (TieType)reader.ReadEncodedInt(); + SignupPeriod = reader.ReadTimeSpan(); + + goto case 0; + } + case 0: + { + if (version < 3) + SuddenDeathRounds = 3; + + m_ParticipantsPerMatch = reader.ReadEncodedInt(); + m_PlayersPerParticipant = reader.ReadEncodedInt(); + SignupPeriod = reader.ReadTimeSpan(); + CurrentStage = TournamentStage.Inactive; + Pyramid = new TournyPyramid(); + Ruleset = new Ruleset(RulesetLayout.Root); + Ruleset.ApplyDefault(Ruleset.Layout.Defaults[0]); + Participants = new ArrayList(); + Undefeated = new ArrayList(); + Arenas = new ArrayList(); + + break; + } + } + + Timer.DelayCall(SliceInterval, SliceInterval, Slice); + } + + public Tournament() + { + m_ParticipantsPerMatch = 2; + m_PlayersPerParticipant = 1; + Pyramid = new TournyPyramid(); + Ruleset = new Ruleset(RulesetLayout.Root); + Ruleset.ApplyDefault(Ruleset.Layout.Defaults[0]); + Participants = new ArrayList(); + Undefeated = new ArrayList(); + Arenas = new ArrayList(); + SignupPeriod = TimeSpan.FromMinutes(10.0); + + Timer.DelayCall(SliceInterval, SliceInterval, Slice); + } + + public bool IsNotoRestricted => TournyType != TournyType.Standard; + + [CommandProperty(AccessLevel.GameMaster)] + public EventController EventController{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int SuddenDeathRounds{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TournyType TournyType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public GroupingType GroupType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TieType TieType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan SuddenDeath{ get; set; } + + public Ruleset Ruleset{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ParticipantsPerMatch + { + get => m_ParticipantsPerMatch; + set + { + if (value < 2) value = 2; + else if (value > 10) value = 10; + m_ParticipantsPerMatch = value; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int PlayersPerParticipant + { + get => m_PlayersPerParticipant; + set + { + if (value < 1) value = 1; + else if (value > 10) value = 10; + m_PlayersPerParticipant = value; + } + } - switch ( tourny.GroupType ) - { - case GroupingType.HighVsLow: groupText = "High vs Low"; break; - case GroupingType.Nearest: groupText = "Closest opponent"; break; - case GroupingType.Random: groupText = "Random"; break; - } - - AddBorderedText( 35, y, 190, 20, $"Grouping: {groupText}", LabelColor32, BlackColor32 ); - y += 20; - - string tieText = null; - - switch ( tourny.TieType ) - { - case TieType.Random: tieText = "Random"; break; - case TieType.Highest: tieText = "Highest advances"; break; - case TieType.Lowest: tieText = "Lowest advances"; break; - case TieType.FullAdvancement: tieText = ( tourny.ParticipantsPerMatch == 2 ? "Both advance" : "Everyone advances" ); break; - case TieType.FullElimination: tieText = ( tourny.ParticipantsPerMatch == 2 ? "Both eliminated" : "Everyone eliminated" ); break; - } - - AddBorderedText( 35, y, 190, 20, $"Tiebreaker: {tieText}", LabelColor32, BlackColor32 ); - y += 20; - - string sdText = "Off"; - - if ( tourny.SuddenDeath > TimeSpan.Zero ) - { - sdText = $"{(int) tourny.SuddenDeath.TotalMinutes}:{tourny.SuddenDeath.Seconds:D2}"; - - if ( tourny.SuddenDeathRounds > 0 ) - sdText = $"{sdText} (first {tourny.SuddenDeathRounds} rounds)"; - else - sdText = $"{sdText} (all rounds)"; - } - - AddBorderedText( 35, y, 240, 20, $"Sudden Death: {sdText}", LabelColor32, BlackColor32 ); - y += 20; - - y += 6; - AddImageTiled( 32, y-1, 264, 1, 9107 ); - AddImageTiled( 42, y+1, 264, 1, 9157 ); - y += 6; - - AddBorderedText( 35, y, 190, 20, $"Ruleset: {basedef.Title}", LabelColor32, BlackColor32 ); - y += 20; - - for ( int i = 0; i < ruleset.Flavors.Count; ++i, y += 18 ) - AddBorderedText( 35, y, 190, 20, $" + {((Ruleset) ruleset.Flavors[i]).Title}", LabelColor32, BlackColor32 ); - - y += 4; - - if ( changes > 0 ) - { - AddBorderedText( 35, y, 190, 20, "Modifications:", LabelColor32, BlackColor32 ); - y += 20; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - { - string name = ruleset.Layout.FindByIndex( i ); - - if ( name != null ) // sanity - { - AddImage( 35, y, opts[i] ? 0xD3 : 0xD2 ); - AddBorderedText( 60, y, 165, 22, name, LabelColor32, BlackColor32 ); - } - - y += 22; - } - } - } - else - { - AddBorderedText( 35, y, 190, 20, "Modifications: None", LabelColor32, BlackColor32 ); - y += 20; - } - #endregion - - y += 8; - AddImageTiled( 32, y-1, 264, 1, 9107 ); - AddImageTiled( 42, y+1, 264, 1, 9157 ); - y += 8; - - AddRadio( 24, y, 9727, 9730, true, 1 ); - AddBorderedText( 60, y+5, 250, 20, "Yes, I will join them.", LabelColor32, BlackColor32 ); - y += 35; - - AddRadio( 24, y, 9727, 9730, false, 2 ); - AddBorderedText( 60, y+5, 250, 20, "No, I do not wish to fight.", LabelColor32, BlackColor32 ); - y += 35; - - AddRadio( 24, y, 9727, 9730, false, 3 ); - AddBorderedText( 60, y+5, 270, 20, "No, most certainly not. Do not ask again.", LabelColor32, BlackColor32 ); - y += 35; - - y -= 3; - AddButton( 314, y, 247, 248, 1, GumpButtonType.Reply, 0 ); - - Timer.DelayCall( TimeSpan.FromSeconds( 15.0 ), AutoReject ); - } - - public void AutoReject() - { - if ( !m_Active ) - return; - - m_Active = false; - - m_Requested.CloseGump( typeof( AcceptTeamGump ) ); - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - if ( m_Registrar != null ) - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, $"{m_Requested.Name} seems unresponsive.", m_From.NetState ); - - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, $"You have declined the partnership with {m_From.Name}.", m_Requested.NetState ); - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = m_From; - Mobile mob = m_Requested; - - if ( info.ButtonID != 1 || !m_Active ) - return; - - m_Active = false; - - if ( info.IsSwitched( 1 ) ) - { - if ( !(mob is PlayerMobile pm) ) - return; - - if ( AcceptDuelGump.IsIgnored( mob, from ) || mob.Blessed ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They ignore your invitation.", from.NetState ); - } - else if ( pm.DuelContext != null ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They are already assigned to another duel.", from.NetState ); - } - else if ( m_Players.Contains( mob ) ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "You have already named them as a team member.", from.NetState ); - } - else if ( m_Tournament.HasParticipant( mob ) ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "They have already entered this tournament.", from.NetState ); - } - else if ( m_Players.Count >= m_Tournament.PlayersPerParticipant ) - { - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - m_Registrar?.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, "Your team is full.", from.NetState ); - } - else - { - m_Players.Add( mob ); - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - if ( m_Registrar != null ) - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x59, false, $"{mob.Name} has accepted your offer of partnership.", from.NetState ); - - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x59, false, $"You have accepted the partnership with {from.Name}.", mob.NetState ); - } - } - } - else - { - if ( info.IsSwitched( 3 ) ) - AcceptDuelGump.BeginIgnore( m_Requested, m_From ); - - m_From.SendGump( new ConfirmSignupGump( m_From, m_Registrar, m_Tournament, m_Players ) ); - - if ( m_Registrar != null ) - { - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, $"{mob.Name} has declined your offer of partnership.", from.NetState ); - - m_Registrar.PrivateOverheadMessage( MessageType.Regular, - 0x22, false, $"You have declined the partnership with {from.Name}.", mob.NetState ); - } - } - } - } - - public class TournamentController : Item - { - private Tournament m_Tournament; - - [CommandProperty( AccessLevel.GameMaster )] - public Tournament Tournament{ get => m_Tournament; - set{} } - - private static ArrayList m_Instances = new ArrayList(); - - public static bool IsActive - { - get - { - for ( int i = 0; i < m_Instances.Count; ++i ) - { - TournamentController controller = (TournamentController)m_Instances[i]; - - if ( controller != null && !controller.Deleted && controller.Tournament != null && controller.Tournament.Stage!=TournamentStage.Inactive ) - return true; - } - - return false; - } - } - - public override string DefaultName => "tournament controller"; - - [Constructible] - public TournamentController() : base( 0x1B7A ) - { - Visible = false; - Movable = false; - - m_Tournament = new Tournament(); - m_Instances.Add( this ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.AccessLevel >= AccessLevel.GameMaster && m_Tournament != null ) - { - list.Add( new EditEntry( m_Tournament ) ); - - if ( m_Tournament.CurrentStage == TournamentStage.Inactive ) - list.Add( new StartEntry( m_Tournament ) ); - } - } - - private class EditEntry : ContextMenuEntry - { - private Tournament m_Tournament; - - public EditEntry( Tournament tourny ) : base( 5101 ) - { - m_Tournament = tourny; - } - - public override void OnClick() - { - Owner.From.SendGump( new PropertiesGump( Owner.From, m_Tournament ) ); - } - } - - private class StartEntry : ContextMenuEntry - { - private Tournament m_Tournament; - - public StartEntry( Tournament tourny ) : base( 5113 ) - { - m_Tournament = tourny; - } - - public override void OnClick() - { - if ( m_Tournament.Stage == TournamentStage.Inactive ) - { - m_Tournament.SignupStart = DateTime.UtcNow; - m_Tournament.Stage = TournamentStage.Signup; - m_Tournament.Participants.Clear(); - m_Tournament.Pyramid.Levels.Clear(); - m_Tournament.Alert( "Hear ye! Hear ye!", "Tournament signup has opened. You can enter by signing up with the registrar." ); - } - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster && m_Tournament != null ) - { - from.CloseGump( typeof( PickRulesetGump ) ); - from.CloseGump( typeof( RulesetGump ) ); - from.SendGump( new PickRulesetGump( from, null, m_Tournament.Ruleset ) ); - } - } - - public TournamentController( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - m_Tournament.Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Tournament = new Tournament( reader ); - break; - } - } - - m_Instances.Add( this ); - } - - public override void OnDelete() - { - base.OnDelete(); - - m_Instances.Remove( this ); - } - } - - public enum TournyType - { - Standard, - FreeForAll, - RandomTeam, - RedVsBlue, - Faction - } + [CommandProperty(AccessLevel.GameMaster)] + public int LevelRequirement{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool FactionRestricted{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan SignupPeriod{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime SignupStart{ get; set; } - [PropertyObject] - public class Tournament - { - private int m_ParticipantsPerMatch; - private int m_PlayersPerParticipant; - - public bool IsNotoRestricted => ( TournyType != TournyType.Standard ); + [CommandProperty(AccessLevel.GameMaster)] + public TournamentStage CurrentStage{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public EventController EventController { get; set; } + public TournamentStage Stage + { + get => CurrentStage; + set => CurrentStage = value; + } - [CommandProperty( AccessLevel.GameMaster )] - public int SuddenDeathRounds { get; set; } + public TournyPyramid Pyramid{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TournyType TournyType { get; set; } + public ArrayList Arenas{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public GroupingType GroupType { get; set; } + public ArrayList Participants{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TieType TieType { get; set; } + public ArrayList Undefeated{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan SuddenDeath { get; set; } - - public Ruleset Ruleset { get; set; } + public bool IsFactionRestricted => FactionRestricted || TournyType == TournyType.Faction; - [CommandProperty( AccessLevel.GameMaster )] - public int ParticipantsPerMatch - { - get => m_ParticipantsPerMatch; - set{ if ( value < 2 ) value = 2; else if ( value > 10 ) value = 10; m_ParticipantsPerMatch = value; } - } + public bool HasParticipant(Mobile mob) + { + for (int i = 0; i < Participants.Count; ++i) + { + TournyParticipant part = (TournyParticipant)Participants[i]; - [CommandProperty( AccessLevel.GameMaster )] - public int PlayersPerParticipant - { - get => m_PlayersPerParticipant; - set{ if ( value < 1 ) value = 1; else if ( value > 10 ) value = 10; m_PlayersPerParticipant = value; } - } + if (part.Players.Contains(mob)) + return true; + } - [CommandProperty( AccessLevel.GameMaster )] - public int LevelRequirement { get; set; } + return false; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool FactionRestricted { get; set; } + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(5); // version - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan SignupPeriod { get; set; } + writer.Write(FactionRestricted); - [CommandProperty( AccessLevel.GameMaster )] - public DateTime SignupStart { get; set; } + writer.Write(EventController); - [CommandProperty( AccessLevel.GameMaster )] - public TournamentStage CurrentStage { get; private set; } - - public TournamentStage Stage - { - get => CurrentStage; - set => CurrentStage = value; - } - - public TournyPyramid Pyramid { get; set; } - - public ArrayList Arenas { get; set; } - - public ArrayList Participants { get; set; } - - public ArrayList Undefeated { get; set; } - - public bool IsFactionRestricted => ( FactionRestricted || TournyType == TournyType.Faction ); - - public bool HasParticipant( Mobile mob ) - { - for ( int i = 0; i < Participants.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)Participants[i]; - - if ( part.Players.Contains( mob ) ) - return true; - } - - return false; - } - - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 5 ); // version - - writer.Write( (bool) FactionRestricted ); - - writer.Write( (Item) EventController ); - - writer.WriteEncodedInt( (int) SuddenDeathRounds ); - - writer.WriteEncodedInt( (int) TournyType ); - - writer.WriteEncodedInt( (int) GroupType ); - writer.WriteEncodedInt( (int) TieType ); - writer.Write( (TimeSpan) SuddenDeath ); + writer.WriteEncodedInt(SuddenDeathRounds); - writer.WriteEncodedInt( (int) m_ParticipantsPerMatch ); - writer.WriteEncodedInt( (int) m_PlayersPerParticipant ); - writer.Write( (TimeSpan) SignupPeriod ); - } + writer.WriteEncodedInt((int)TournyType); - public Tournament( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + writer.WriteEncodedInt((int)GroupType); + writer.WriteEncodedInt((int)TieType); + writer.Write(SuddenDeath); - switch ( version ) - { - case 5: { - FactionRestricted = reader.ReadBool(); - - goto case 4; - } - case 4: - { - EventController = reader.ReadItem() as EventController; - - goto case 3; - } - case 3: - { - SuddenDeathRounds = reader.ReadEncodedInt(); - - goto case 2; - } - case 2: - { - TournyType = (TournyType)reader.ReadEncodedInt(); - - goto case 1; - } - case 1: - { - GroupType = (GroupingType)reader.ReadEncodedInt(); - TieType = (TieType)reader.ReadEncodedInt(); - SignupPeriod = reader.ReadTimeSpan(); - - goto case 0; - } - case 0: - { - if ( version < 3 ) - SuddenDeathRounds = 3; - - m_ParticipantsPerMatch = reader.ReadEncodedInt(); - m_PlayersPerParticipant = reader.ReadEncodedInt(); - SignupPeriod = reader.ReadTimeSpan(); - CurrentStage = TournamentStage.Inactive; - Pyramid = new TournyPyramid(); - Ruleset = new Ruleset( RulesetLayout.Root ); - Ruleset.ApplyDefault( Ruleset.Layout.Defaults[0] ); - Participants = new ArrayList(); - Undefeated = new ArrayList(); - Arenas = new ArrayList(); - - break; - } - } - - Timer.DelayCall( SliceInterval, SliceInterval, Slice ); - } - - public Tournament() - { - m_ParticipantsPerMatch = 2; - m_PlayersPerParticipant = 1; - Pyramid = new TournyPyramid(); - Ruleset = new Ruleset( RulesetLayout.Root ); - Ruleset.ApplyDefault( Ruleset.Layout.Defaults[0] ); - Participants = new ArrayList(); - Undefeated = new ArrayList(); - Arenas = new ArrayList(); - SignupPeriod = TimeSpan.FromMinutes( 10.0 ); - - Timer.DelayCall( SliceInterval, SliceInterval, Slice ); - } - - public void HandleTie( Arena arena, TournyMatch match, ArrayList remaining ) - { - if ( remaining.Count == 1 ) - HandleWon( arena, match, (TournyParticipant)remaining[0] ); - - if ( remaining.Count < 2 ) - return; - - StringBuilder sb = new StringBuilder(); - - sb.Append( "The match has ended in a tie " ); - - if ( remaining.Count == 2 ) - sb.Append( "between " ); - else - sb.Append( "among " ); - - sb.Append( remaining.Count ); - - if ( ((TournyParticipant)remaining[0]).Players.Count == 1 ) - sb.Append( " players: " ); - else - sb.Append( " teams: " ); - - bool hasAppended = false; - - for ( int j = 0; j < match.Participants.Count; ++j ) - { - TournyParticipant part = (TournyParticipant)match.Participants[j]; - - if ( remaining.Contains( part ) ) - { - if ( hasAppended ) - sb.Append( ", " ); - - sb.Append( part.NameList ); - hasAppended = true; - } - else - { - Undefeated.Remove( part ); - } - } - - sb.Append( ". " ); - - string whole = ( remaining.Count == 2 ? "both" : "all" ); - - TieType tieType = TieType; - - if ( tieType == TieType.FullElimination && remaining.Count >= Undefeated.Count ) - tieType = TieType.FullAdvancement; - - switch ( TieType ) - { - case TieType.FullAdvancement: - { - sb.AppendFormat( "In accordance with the rules, {0} parties are advanced.", whole ); - break; - } - case TieType.FullElimination: - { - for ( int j = 0; j < remaining.Count; ++j ) - Undefeated.Remove( remaining[j] ); - - sb.AppendFormat( "In accordance with the rules, {0} parties are eliminated.", whole ); - break; - } - case TieType.Random: - { - TournyParticipant advanced = (TournyParticipant)remaining[Utility.Random( remaining.Count )]; - - for ( int i = 0; i < remaining.Count; ++i ) - { - if ( remaining[i] != advanced ) - Undefeated.Remove( remaining[i] ); - } - - if ( advanced != null ) - sb.AppendFormat( "In accordance with the rules, {0} {1} advanced.", advanced.NameList, advanced.Players.Count == 1 ? "is" : "are" ); - - break; - } - case TieType.Highest: - { - TournyParticipant advanced = null; - - for ( int i = 0; i < remaining.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)remaining[i]; - - if ( advanced == null || part.TotalLadderXP > advanced.TotalLadderXP ) - advanced = part; - } + writer.WriteEncodedInt(m_ParticipantsPerMatch); + writer.WriteEncodedInt(m_PlayersPerParticipant); + writer.Write(SignupPeriod); + } - for ( int i = 0; i < remaining.Count; ++i ) - { - if ( remaining[i] != advanced ) - Undefeated.Remove( remaining[i] ); - } + public void HandleTie(Arena arena, TournyMatch match, ArrayList remaining) + { + if (remaining.Count == 1) + HandleWon(arena, match, (TournyParticipant)remaining[0]); - if ( advanced != null ) - sb.AppendFormat( "In accordance with the rules, {0} {1} advanced.", advanced.NameList, advanced.Players.Count == 1 ? "is" : "are" ); + if (remaining.Count < 2) + return; - break; - } - case TieType.Lowest: - { - TournyParticipant advanced = null; + StringBuilder sb = new StringBuilder(); + + sb.Append("The match has ended in a tie "); + + if (remaining.Count == 2) + sb.Append("between "); + else + sb.Append("among "); - for ( int i = 0; i < remaining.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)remaining[i]; - - if ( advanced == null || part.TotalLadderXP < advanced.TotalLadderXP ) - advanced = part; - } - - for ( int i = 0; i < remaining.Count; ++i ) - { - if ( remaining[i] != advanced ) - Undefeated.Remove( remaining[i] ); - } - - if ( advanced != null ) - sb.AppendFormat( "In accordance with the rules, {0} {1} advanced.", advanced.NameList, advanced.Players.Count == 1 ? "is" : "are" ); - - break; - } - } - - Alert( arena, sb.ToString() ); - } - - public void OnEliminated( DuelPlayer player ) - { - Participant part = player.Participant; - - if ( !part.Eliminated ) - return; + sb.Append(remaining.Count); - if ( TournyType == TournyType.FreeForAll ) - { - int rem = 0; + if (((TournyParticipant)remaining[0]).Players.Count == 1) + sb.Append(" players: "); + else + sb.Append(" teams: "); - for ( int i = 0; i < part.Context.Participants.Count; ++i ) - { - Participant check = (Participant)part.Context.Participants[i]; + bool hasAppended = false; - if ( check != null && !check.Eliminated ) - ++rem; - } + for (int j = 0; j < match.Participants.Count; ++j) + { + TournyParticipant part = (TournyParticipant)match.Participants[j]; - TournyParticipant tp = part.TournyPart; - - if ( tp == null ) - return; + if (remaining.Contains(part)) + { + if (hasAppended) + sb.Append(", "); - if ( rem == 1 ) - GiveAwards( tp.Players, TrophyRank.Silver, ComputeCashAward() / 2 ); - else if ( rem == 2 ) - GiveAwards( tp.Players, TrophyRank.Bronze, ComputeCashAward() / 4 ); - } - } + sb.Append(part.NameList); + hasAppended = true; + } + else + { + Undefeated.Remove(part); + } + } - public void HandleWon( Arena arena, TournyMatch match, TournyParticipant winner ) - { - StringBuilder sb = new StringBuilder(); + sb.Append(". "); - sb.Append( "The match is complete. " ); - sb.Append( winner.NameList ); + string whole = remaining.Count == 2 ? "both" : "all"; - if ( winner.Players.Count > 1 ) - sb.Append( " have bested " ); - else - sb.Append( " has bested " ); + TieType tieType = TieType; - if ( match.Participants.Count > 2 ) - sb.AppendFormat( "{0} other {1}: ", match.Participants.Count - 1, winner.Players.Count == 1 ? "players" : "teams" ); + if (tieType == TieType.FullElimination && remaining.Count >= Undefeated.Count) + tieType = TieType.FullAdvancement; - bool hasAppended = false; + switch (TieType) + { + case TieType.FullAdvancement: + { + sb.AppendFormat("In accordance with the rules, {0} parties are advanced.", whole); + break; + } + case TieType.FullElimination: + { + for (int j = 0; j < remaining.Count; ++j) + Undefeated.Remove(remaining[j]); - for ( int j = 0; j < match.Participants.Count; ++j ) - { - TournyParticipant part = (TournyParticipant)match.Participants[j]; + sb.AppendFormat("In accordance with the rules, {0} parties are eliminated.", whole); + break; + } + case TieType.Random: + { + TournyParticipant advanced = (TournyParticipant)remaining[Utility.Random(remaining.Count)]; - if ( part == winner ) - continue; + for (int i = 0; i < remaining.Count; ++i) + if (remaining[i] != advanced) + Undefeated.Remove(remaining[i]); - Undefeated.Remove( part ); + if (advanced != null) + sb.AppendFormat("In accordance with the rules, {0} {1} advanced.", advanced.NameList, + advanced.Players.Count == 1 ? "is" : "are"); - if ( hasAppended ) - sb.Append( ", " ); + break; + } + case TieType.Highest: + { + TournyParticipant advanced = null; - sb.Append( part.NameList ); - hasAppended = true; - } + for (int i = 0; i < remaining.Count; ++i) + { + TournyParticipant part = (TournyParticipant)remaining[i]; - sb.Append( "." ); + if (advanced == null || part.TotalLadderXP > advanced.TotalLadderXP) + advanced = part; + } - if ( TournyType == TournyType.Standard ) - Alert( arena, sb.ToString() ); - } + for (int i = 0; i < remaining.Count; ++i) + if (remaining[i] != advanced) + Undefeated.Remove(remaining[i]); - private static readonly TimeSpan SliceInterval = TimeSpan.FromSeconds( 12.0 ); + if (advanced != null) + sb.AppendFormat("In accordance with the rules, {0} {1} advanced.", advanced.NameList, + advanced.Players.Count == 1 ? "is" : "are"); - private int ComputeCashAward() - { - return Participants.Count * m_PlayersPerParticipant * 2500; - } + break; + } + case TieType.Lowest: + { + TournyParticipant advanced = null; - private void GiveAwards() - { - switch ( TournyType ) - { - case TournyType.FreeForAll: - { - if ( Pyramid.Levels.Count < 1 ) - break; - - PyramidLevel top = Pyramid.Levels[Pyramid.Levels.Count - 1] as PyramidLevel; - - if ( top.FreeAdvance != null || top.Matches.Count != 1 ) - break; - - TournyMatch match = top.Matches[0] as TournyMatch; - TournyParticipant winner = match.Winner; - - if ( winner != null ) - GiveAwards( winner.Players, TrophyRank.Gold, ComputeCashAward() ); + for (int i = 0; i < remaining.Count; ++i) + { + TournyParticipant part = (TournyParticipant)remaining[i]; + + if (advanced == null || part.TotalLadderXP < advanced.TotalLadderXP) + advanced = part; + } + + for (int i = 0; i < remaining.Count; ++i) + if (remaining[i] != advanced) + Undefeated.Remove(remaining[i]); + + if (advanced != null) + sb.AppendFormat("In accordance with the rules, {0} {1} advanced.", advanced.NameList, + advanced.Players.Count == 1 ? "is" : "are"); - break; - } - case TournyType.Standard: - { - if ( Pyramid.Levels.Count < 2 ) - break; + break; + } + } + + Alert(arena, sb.ToString()); + } + + public void OnEliminated(DuelPlayer player) + { + Participant part = player.Participant; + + if (!part.Eliminated) + return; + + if (TournyType == TournyType.FreeForAll) + { + int rem = 0; - PyramidLevel top = Pyramid.Levels[Pyramid.Levels.Count - 1] as PyramidLevel; + for (int i = 0; i < part.Context.Participants.Count; ++i) + { + Participant check = (Participant)part.Context.Participants[i]; - if ( top.FreeAdvance != null || top.Matches.Count != 1 ) - break; + if (check != null && !check.Eliminated) + ++rem; + } - int cash = ComputeCashAward(); + TournyParticipant tp = part.TournyPart; + + if (tp == null) + return; + + if (rem == 1) + GiveAwards(tp.Players, TrophyRank.Silver, ComputeCashAward() / 2); + else if (rem == 2) + GiveAwards(tp.Players, TrophyRank.Bronze, ComputeCashAward() / 4); + } + } - TournyMatch match = top.Matches[0] as TournyMatch; - TournyParticipant winner = match.Winner; + public void HandleWon(Arena arena, TournyMatch match, TournyParticipant winner) + { + StringBuilder sb = new StringBuilder(); - for ( int i = 0; i < match.Participants.Count; ++i ) - { - TournyParticipant part = (TournyParticipant) match.Participants[i]; + sb.Append("The match is complete. "); + sb.Append(winner.NameList); - if ( part == winner ) - GiveAwards( part.Players, TrophyRank.Gold, cash ); - else - GiveAwards( part.Players, TrophyRank.Silver, cash / 2 ); - } - - PyramidLevel next = Pyramid.Levels[Pyramid.Levels.Count - 2] as PyramidLevel; - - if ( next.Matches.Count > 2 ) - break; - - for ( int i = 0; i < next.Matches.Count; ++i ) - { - match = (TournyMatch)next.Matches[i]; - winner = match.Winner; - - for ( int j = 0; j < match.Participants.Count; ++j ) - { - TournyParticipant part = (TournyParticipant) match.Participants[j]; - - if ( part != winner ) - GiveAwards( part.Players, TrophyRank.Bronze, cash / 4 ); - } - } - - break; - } - } - } - - private void GiveAwards( ArrayList players, TrophyRank rank, int cash ) - { - if ( players.Count == 0 ) - return; - - if ( players.Count > 1 ) - cash /= ( players.Count - 1 ); - - cash += 500; - cash /= 1000; - cash *= 1000; - - StringBuilder sb = new StringBuilder(); - - if ( TournyType == TournyType.FreeForAll ) - { - sb.Append( Participants.Count * m_PlayersPerParticipant ); - sb.Append( "-man FFA" ); - } - else if ( TournyType == TournyType.RandomTeam ) - { - sb.Append( m_ParticipantsPerMatch ); - sb.Append( "-Team" ); - } - else if ( TournyType == TournyType.Faction ) - { - sb.Append( m_ParticipantsPerMatch ); - sb.Append( "-Team Faction" ); - } - else if ( TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else - { - for ( int i = 0; i < m_ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); - - sb.Append( m_PlayersPerParticipant ); - } - } - - if ( EventController != null ) - sb.Append( ' ' ).Append( EventController.Title ); - - sb.Append( " Champion" ); - - string title = sb.ToString(); - - for ( int i = 0; i < players.Count; ++i ) - { - Mobile mob = (Mobile) players[i]; - - if ( mob == null || mob.Deleted ) - continue; - - Item item = new Trophy( title, rank ); - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - if ( cash > 0 ) - { - item = new BankCheck( cash ); - - if ( !mob.PlaceInBackpack( item ) ) - mob.BankBox.DropItem( item ); - - mob.SendMessage( "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", rank.ToString().ToLower(), cash ); - } - else - { - mob.SendMessage( "You have been awarded a {0} trophy for your participation in this tournament.", rank.ToString().ToLower() ); - } - } - } - - public void Slice() - { - if ( CurrentStage == TournamentStage.Signup ) - { - TimeSpan until = ( SignupStart + SignupPeriod ) - DateTime.UtcNow; - - if ( until <= TimeSpan.Zero ) - { - for ( int i = Participants.Count - 1; i >= 0; --i ) - { - TournyParticipant part = (TournyParticipant)Participants[i]; - bool bad = false; - - for ( int j = 0; j < part.Players.Count; ++j ) - { - Mobile check = (Mobile) part.Players[j]; - - if ( check.Deleted || check.Map == null || check.Map == Map.Internal || !check.Alive || Sigil.ExistsOn( check ) || check.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - bad = true; - break; - } - } - - if ( bad ) - { - for ( int j = 0; j < part.Players.Count; ++j ) - ((Mobile)part.Players[j]).SendMessage( "You have been disqualified from the tournament." ); - - Participants.RemoveAt( i ); - } - } - - if ( Participants.Count >= 2 ) - { - CurrentStage = TournamentStage.Fighting; - - Undefeated.Clear(); - - Pyramid.Levels.Clear(); - Pyramid.AddLevel( m_ParticipantsPerMatch, Participants, GroupType, TournyType ); - - PyramidLevel level = (PyramidLevel)Pyramid.Levels[0]; - - if ( level.FreeAdvance != null ) - Undefeated.Add( level.FreeAdvance ); - - for ( int i = 0; i < level.Matches.Count; ++i ) - { - TournyMatch match = (TournyMatch)level.Matches[i]; - - Undefeated.AddRange( match.Participants ); - } - - Alert( "Hear ye! Hear ye!", "The tournament will begin shortly." ); - } - else - { - /*Alert( "Is this all?", "Pitiful. Signup extended." ); - m_SignupStart = DateTime.UtcNow;*/ - - Alert("Is this all?", "Pitiful. Tournament cancelled."); - CurrentStage = TournamentStage.Inactive; - } - } - else if ( Math.Abs( until.TotalSeconds - TimeSpan.FromMinutes( 1.0 ).TotalSeconds ) < (SliceInterval.TotalSeconds/2) ) - { - Alert( "Last call!", "If you wish to enter the tournament, sign up with the registrar now." ); - } - else if ( Math.Abs( until.TotalSeconds - TimeSpan.FromMinutes( 5.0 ).TotalSeconds ) < (SliceInterval.TotalSeconds/2) ) - { - Alert( "The tournament will begin in 5 minutes.", "Sign up now before it's too late." ); - } - } - else if ( CurrentStage == TournamentStage.Fighting ) - { - if ( Undefeated.Count == 1 ) - { - TournyParticipant winner = (TournyParticipant)Undefeated[0]; - - try - { - if ( EventController != null ) - Alert( "The tournament has completed!", - $"Team {EventController.GetTeamName(((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner))} has won!"); - else if ( TournyType == TournyType.RandomTeam ) - Alert( "The tournament has completed!", - $"Team {((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); - else if ( TournyType == TournyType.Faction ) { - if ( m_ParticipantsPerMatch == 4 ) - { - string name = "(null)"; - - switch ( ((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf( winner ) ) - { - case 0: { - name = "Minax"; - break; - } - case 1: { - name = "Council of Mages"; - break; - } - case 2: { - name = "True Britannians"; - break; - } - case 3: { - name = "Shadowlords"; - break; - } - } - - Alert( "The tournament has completed!", $"The {name} team has won!"); - } - else if ( m_ParticipantsPerMatch == 2 ) - { - Alert( "The tournament has completed!", - $"The {(((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Evil" : "Hero")} team has won!"); - } - else - { - Alert( "The tournament has completed!", - $"Team {((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); - } - } - else if ( TournyType == TournyType.RedVsBlue ) - Alert( "The tournament has completed!", - $"Team {(((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Red" : "Blue")} has won!"); - else - Alert( "The tournament has completed!", - $"{winner.NameList} {(winner.Players.Count > 1 ? "are" : "is")} the champion{(winner.Players.Count == 1 ? "" : "s")}."); - } - catch - { - } - - GiveAwards(); - - CurrentStage = TournamentStage.Inactive; - Undefeated.Clear(); - } - else if ( Pyramid.Levels.Count > 0 ) - { - PyramidLevel activeLevel = (PyramidLevel)Pyramid.Levels[Pyramid.Levels.Count - 1]; - bool stillGoing = false; - - for ( int i = 0; i < activeLevel.Matches.Count; ++i ) - { - TournyMatch match = (TournyMatch)activeLevel.Matches[i]; - - if ( match.Winner == null ) - { - stillGoing = true; - - if ( !match.InProgress ) - { - for ( int j = 0; j < Arenas.Count; ++j ) - { - Arena arena = (Arena)Arenas[j]; - - if ( !arena.IsOccupied ) - { - match.Start( arena, this ); - break; - } - } - } - } - } - - if ( !stillGoing ) - { - for ( int i = Undefeated.Count - 1; i >= 0; --i ) - { - TournyParticipant part = (TournyParticipant)Undefeated[i]; - bool bad = false; - - for ( int j = 0; j < part.Players.Count; ++j ) - { - Mobile check = (Mobile) part.Players[j]; - - if ( check.Deleted || check.Map == null || check.Map == Map.Internal || !check.Alive || Sigil.ExistsOn( check ) || check.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - bad = true; - break; - } - } - - if ( bad ) - { - for ( int j = 0; j < part.Players.Count; ++j ) - ((Mobile)part.Players[j]).SendMessage( "You have been disqualified from the tournament." ); - - Undefeated.RemoveAt( i ); - - if ( Undefeated.Count == 1 ) - { - TournyParticipant winner = (TournyParticipant)Undefeated[0]; - - try - { - if ( EventController != null ) - Alert( "The tournament has completed!", - $"Team {EventController.GetTeamName(((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner))} has won"); - else if ( TournyType == TournyType.RandomTeam ) - Alert( "The tournament has completed!", - $"Team {((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); - else if ( TournyType == TournyType.Faction ) { - if ( m_ParticipantsPerMatch == 4 ) - { - string name = "(null)"; - - switch ( ((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf( winner ) ) - { - case 0: { - name = "Minax"; - break; - } - case 1: { - name = "Council of Mages"; - break; - } - case 2: { - name = "True Britannians"; - break; - } - case 3: { - name = "Shadowlords"; - break; - } - } - - Alert( "The tournament has completed!", $"The {name} team has won!"); - } - else if ( m_ParticipantsPerMatch == 2 ) - { - Alert( "The tournament has completed!", - $"The {(((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Evil" : "Hero")} team has won!"); - } - else - { - Alert( "The tournament has completed!", - $"Team {((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); - } - } - else if ( TournyType == TournyType.RedVsBlue ) - Alert( "The tournament has completed!", - $"Team {(((TournyMatch) ((PyramidLevel) Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Red" : "Blue")} has won!"); - else - Alert( "The tournament has completed!", - $"{winner.NameList} {(winner.Players.Count > 1 ? "are" : "is")} the champion{(winner.Players.Count == 1 ? "" : "s")}."); - } - catch - { - } - - GiveAwards(); - - CurrentStage = TournamentStage.Inactive; - Undefeated.Clear(); - break; - } - } - } - - if ( Undefeated.Count > 1 ) - Pyramid.AddLevel( m_ParticipantsPerMatch, Undefeated, GroupType, TournyType ); - } - } - } - } - - public void Alert( params string[] alerts ) - { - for ( int i = 0; i < Arenas.Count; ++i ) - Alert( (Arena) Arenas[i], alerts ); - } - - public void Alert( Arena arena, params string[] alerts ) - { - if ( arena?.Announcer != null ) - { - for ( int j = 0; j < alerts.Length; ++j ) - Timer.DelayCall( TimeSpan.FromSeconds( Math.Max( j-0.5, 0.0 ) ), new TimerStateCallback( Alert_Callback ), new object[]{ arena.Announcer, alerts[j] } ); - } - } - - private void Alert_Callback( object state ) - { - object[] states = (object[])state; - - ((Mobile) states[0])?.PublicOverheadMessage( MessageType.Regular, 0x35, false, (string)states[1] ); - } - } - - public class TournyPyramid - { - public ArrayList Levels { get; set; } - - public TournyPyramid() - { - Levels = new ArrayList(); - } - - public void AddLevel( int partsPerMatch, ArrayList participants, GroupingType groupType, TournyType tournyType ) - { - ArrayList copy = new ArrayList( participants ); - - if ( groupType == GroupingType.Nearest || groupType == GroupingType.HighVsLow ) - copy.Sort(); - - PyramidLevel level = new PyramidLevel(); - - switch ( tournyType ) - { - case TournyType.RedVsBlue: - { - TournyParticipant[] parts = new TournyParticipant[2]; - - for ( int i = 0; i < parts.Length; ++i ) - parts[i] = new TournyParticipant( new ArrayList() ); - - for ( int i = 0; i < copy.Count; ++i ) - { - ArrayList players = ((TournyParticipant)copy[i]).Players; - - for ( int j = 0; j < players.Count; ++j ) - { - Mobile mob = (Mobile) players[j]; - - if ( mob.Kills >= 5 ) - parts[0].Players.Add( mob ); - else - parts[1].Players.Add( mob ); - } - } - - level.Matches.Add( new TournyMatch( new ArrayList( parts ) ) ); - break; - } - case TournyType.Faction: - { - TournyParticipant[] parts = new TournyParticipant[partsPerMatch]; - - for ( int i = 0; i < parts.Length; ++i ) - parts[i] = new TournyParticipant( new ArrayList() ); - - for ( int i = 0; i < copy.Count; ++i ) - { - ArrayList players = ((TournyParticipant)copy[i]).Players; - - for ( int j = 0; j < players.Count; ++j ) - { - Mobile mob = (Mobile) players[j]; - - int index = -1; - - if ( partsPerMatch == 4 ) - { - Faction fac = Faction.Find( mob ); - - if ( fac != null ) - { - index = fac.Definition.Sort; - } - } - else if ( partsPerMatch == 2 ) - { - if ( Ethic.Evil.IsEligible( mob ) ) - { - index = 0; - } - else if ( Ethic.Hero.IsEligible( mob ) ) - { - index = 1; - } - } - - if ( index < 0 || index >= partsPerMatch ) - { - index = i % partsPerMatch; - } - - parts[index].Players.Add( mob ); - } - } - - level.Matches.Add( new TournyMatch( new ArrayList( parts ) ) ); - break; - } - case TournyType.RandomTeam: - { - TournyParticipant[] parts = new TournyParticipant[partsPerMatch]; - - for ( int i = 0; i < partsPerMatch; ++i ) - parts[i] = new TournyParticipant( new ArrayList() ); - - for ( int i = 0; i < copy.Count; ++i ) - parts[i % parts.Length].Players.AddRange( ((TournyParticipant)copy[i]).Players ); - - level.Matches.Add( new TournyMatch( new ArrayList( parts ) ) ); - break; - } - case TournyType.FreeForAll: - { - level.Matches.Add( new TournyMatch( copy ) ); - break; - } - case TournyType.Standard: - { - if ( partsPerMatch >= 2 && participants.Count % partsPerMatch == 1 ) - { - int lowAdvances = int.MaxValue; - - for ( int i = 0; i < participants.Count; ++i ) - { - TournyParticipant p = (TournyParticipant)participants[i]; - - if ( p.FreeAdvances < lowAdvances ) - lowAdvances = p.FreeAdvances; - } - - ArrayList toAdvance = new ArrayList(); - - for ( int i = 0; i < participants.Count; ++i ) - { - TournyParticipant p = (TournyParticipant)participants[i]; - - if ( p.FreeAdvances == lowAdvances ) - toAdvance.Add( p ); - } - - if ( toAdvance.Count == 0 ) - toAdvance = copy; // sanity - - int idx = Utility.Random( toAdvance.Count ); - - ((TournyParticipant)toAdvance[idx]).AddLog( "Advanced automatically due to an odd number of challengers." ); - level.FreeAdvance = (TournyParticipant)toAdvance[idx]; - ++level.FreeAdvance.FreeAdvances; - copy.Remove( toAdvance[idx] ); - } - - while ( copy.Count >= partsPerMatch ) - { - ArrayList thisMatch = new ArrayList(); - - for ( int i = 0; i < partsPerMatch; ++i ) - { - int idx = 0; - - switch ( groupType ) - { - case GroupingType.HighVsLow: idx = (i * (copy.Count - 1)) / (partsPerMatch - 1); break; - case GroupingType.Nearest: idx = 0; break; - case GroupingType.Random: idx = Utility.Random( copy.Count ); break; - } - - thisMatch.Add( copy[idx] ); - copy.RemoveAt( idx ); - } - - level.Matches.Add( new TournyMatch( thisMatch ) ); - } - - if ( copy.Count > 1 ) - level.Matches.Add( new TournyMatch( copy ) ); - - break; - } - } - - Levels.Add( level ); - } - } - - public class PyramidLevel - { - public ArrayList Matches { get; set; } + if (winner.Players.Count > 1) + sb.Append(" have bested "); + else + sb.Append(" has bested "); - public TournyParticipant FreeAdvance { get; set; } + if (match.Participants.Count > 2) + sb.AppendFormat("{0} other {1}: ", match.Participants.Count - 1, + winner.Players.Count == 1 ? "players" : "teams"); - public PyramidLevel() - { - Matches = new ArrayList(); - } - } + bool hasAppended = false; - public class TournyMatch - { - public ArrayList Participants { get; set; } + for (int j = 0; j < match.Participants.Count; ++j) + { + TournyParticipant part = (TournyParticipant)match.Participants[j]; - public TournyParticipant Winner { get; set; } + if (part == winner) + continue; - public DuelContext Context { get; set; } + Undefeated.Remove(part); - public bool InProgress => ( Context != null && Context.Registered ); + if (hasAppended) + sb.Append(", "); - public void Start( Arena arena, Tournament tourny ) - { - TournyParticipant first = (TournyParticipant)Participants[0]; + sb.Append(part.NameList); + hasAppended = true; + } - DuelContext dc = new DuelContext( (Mobile)first.Players[0], tourny.Ruleset.Layout, false ); - dc.Ruleset.Options.SetAll(false); - dc.Ruleset.Options.Or(tourny.Ruleset.Options); + sb.Append("."); - for ( int i = 0; i < Participants.Count; ++i ) - { - TournyParticipant tournyPart = (TournyParticipant)Participants[i]; - Participant duelPart = new Participant( dc, tournyPart.Players.Count ); + if (TournyType == TournyType.Standard) + Alert(arena, sb.ToString()); + } - duelPart.TournyPart = tournyPart; + private int ComputeCashAward() + { + return Participants.Count * m_PlayersPerParticipant * 2500; + } - for ( int j = 0; j < tournyPart.Players.Count; ++j ) - duelPart.Add( (Mobile) tournyPart.Players[j] ); + private void GiveAwards() + { + switch (TournyType) + { + case TournyType.FreeForAll: + { + if (Pyramid.Levels.Count < 1) + break; + + PyramidLevel top = Pyramid.Levels[Pyramid.Levels.Count - 1] as PyramidLevel; + + if (top.FreeAdvance != null || top.Matches.Count != 1) + break; + + TournyMatch match = top.Matches[0] as TournyMatch; + TournyParticipant winner = match.Winner; + + if (winner != null) + GiveAwards(winner.Players, TrophyRank.Gold, ComputeCashAward()); + + break; + } + case TournyType.Standard: + { + if (Pyramid.Levels.Count < 2) + break; + + PyramidLevel top = Pyramid.Levels[Pyramid.Levels.Count - 1] as PyramidLevel; + + if (top.FreeAdvance != null || top.Matches.Count != 1) + break; + + int cash = ComputeCashAward(); - for ( int j = 0; j < duelPart.Players.Length; ++j ) - { - if ( duelPart.Players[j] != null ) - duelPart.Players[j].Ready = true; - } + TournyMatch match = top.Matches[0] as TournyMatch; + TournyParticipant winner = match.Winner; + + for (int i = 0; i < match.Participants.Count; ++i) + { + TournyParticipant part = (TournyParticipant)match.Participants[i]; - dc.Participants.Add( duelPart ); - } + if (part == winner) + GiveAwards(part.Players, TrophyRank.Gold, cash); + else + GiveAwards(part.Players, TrophyRank.Silver, cash / 2); + } + + PyramidLevel next = Pyramid.Levels[Pyramid.Levels.Count - 2] as PyramidLevel; + + if (next.Matches.Count > 2) + break; + + for (int i = 0; i < next.Matches.Count; ++i) + { + match = (TournyMatch)next.Matches[i]; + winner = match.Winner; + + for (int j = 0; j < match.Participants.Count; ++j) + { + TournyParticipant part = (TournyParticipant)match.Participants[j]; + + if (part != winner) + GiveAwards(part.Players, TrophyRank.Bronze, cash / 4); + } + } + + break; + } + } + } + + private void GiveAwards(ArrayList players, TrophyRank rank, int cash) + { + if (players.Count == 0) + return; + + if (players.Count > 1) + cash /= players.Count - 1; + + cash += 500; + cash /= 1000; + cash *= 1000; + + StringBuilder sb = new StringBuilder(); + + if (TournyType == TournyType.FreeForAll) + { + sb.Append(Participants.Count * m_PlayersPerParticipant); + sb.Append("-man FFA"); + } + else if (TournyType == TournyType.RandomTeam) + { + sb.Append(m_ParticipantsPerMatch); + sb.Append("-Team"); + } + else if (TournyType == TournyType.Faction) + { + sb.Append(m_ParticipantsPerMatch); + sb.Append("-Team Faction"); + } + else if (TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else + { + for (int i = 0; i < m_ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(m_PlayersPerParticipant); + } + } + + if (EventController != null) + sb.Append(' ').Append(EventController.Title); + + sb.Append(" Champion"); + + string title = sb.ToString(); + + for (int i = 0; i < players.Count; ++i) + { + Mobile mob = (Mobile)players[i]; + + if (mob == null || mob.Deleted) + continue; + + Item item = new Trophy(title, rank); + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + if (cash > 0) + { + item = new BankCheck(cash); + + if (!mob.PlaceInBackpack(item)) + mob.BankBox.DropItem(item); + + mob.SendMessage( + "You have been awarded a {0} trophy and {1:N0}gp for your participation in this tournament.", + rank.ToString().ToLower(), cash); + } + else + { + mob.SendMessage("You have been awarded a {0} trophy for your participation in this tournament.", + rank.ToString().ToLower()); + } + } + } + + public void Slice() + { + if (CurrentStage == TournamentStage.Signup) + { + TimeSpan until = SignupStart + SignupPeriod - DateTime.UtcNow; + + if (until <= TimeSpan.Zero) + { + for (int i = Participants.Count - 1; i >= 0; --i) + { + TournyParticipant part = (TournyParticipant)Participants[i]; + bool bad = false; + + for (int j = 0; j < part.Players.Count; ++j) + { + Mobile check = (Mobile)part.Players[j]; + + if (check.Deleted || check.Map == null || check.Map == Map.Internal || !check.Alive || + Sigil.ExistsOn(check) || check.Region.IsPartOf(typeof(Jail))) + { + bad = true; + break; + } + } + + if (bad) + { + for (int j = 0; j < part.Players.Count; ++j) + ((Mobile)part.Players[j]).SendMessage("You have been disqualified from the tournament."); + + Participants.RemoveAt(i); + } + } + + if (Participants.Count >= 2) + { + CurrentStage = TournamentStage.Fighting; + + Undefeated.Clear(); + + Pyramid.Levels.Clear(); + Pyramid.AddLevel(m_ParticipantsPerMatch, Participants, GroupType, TournyType); + + PyramidLevel level = (PyramidLevel)Pyramid.Levels[0]; + + if (level.FreeAdvance != null) + Undefeated.Add(level.FreeAdvance); + + for (int i = 0; i < level.Matches.Count; ++i) + { + TournyMatch match = (TournyMatch)level.Matches[i]; + + Undefeated.AddRange(match.Participants); + } + + Alert("Hear ye! Hear ye!", "The tournament will begin shortly."); + } + else + { + /*Alert( "Is this all?", "Pitiful. Signup extended." ); + m_SignupStart = DateTime.UtcNow;*/ + + Alert("Is this all?", "Pitiful. Tournament cancelled."); + CurrentStage = TournamentStage.Inactive; + } + } + else if (Math.Abs(until.TotalSeconds - TimeSpan.FromMinutes(1.0).TotalSeconds) < + SliceInterval.TotalSeconds / 2) + { + Alert("Last call!", "If you wish to enter the tournament, sign up with the registrar now."); + } + else if (Math.Abs(until.TotalSeconds - TimeSpan.FromMinutes(5.0).TotalSeconds) < + SliceInterval.TotalSeconds / 2) + { + Alert("The tournament will begin in 5 minutes.", "Sign up now before it's too late."); + } + } + else if (CurrentStage == TournamentStage.Fighting) + { + if (Undefeated.Count == 1) + { + TournyParticipant winner = (TournyParticipant)Undefeated[0]; + + try + { + if (EventController != null) + { + Alert("The tournament has completed!", + $"Team {EventController.GetTeamName(((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner))} has won!"); + } + else if (TournyType == TournyType.RandomTeam) + { + Alert("The tournament has completed!", + $"Team {((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); + } + else if (TournyType == TournyType.Faction) + { + if (m_ParticipantsPerMatch == 4) + { + string name = "(null)"; + + switch (((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf( + winner)) + { + case 0: + { + name = "Minax"; + break; + } + case 1: + { + name = "Council of Mages"; + break; + } + case 2: + { + name = "True Britannians"; + break; + } + case 3: + { + name = "Shadowlords"; + break; + } + } + + Alert("The tournament has completed!", $"The {name} team has won!"); + } + else if (m_ParticipantsPerMatch == 2) + { + Alert("The tournament has completed!", + $"The {(((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Evil" : "Hero")} team has won!"); + } + else + { + Alert("The tournament has completed!", + $"Team {((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); + } + } + else if (TournyType == TournyType.RedVsBlue) + { + Alert("The tournament has completed!", + $"Team {(((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Red" : "Blue")} has won!"); + } + else + { + Alert("The tournament has completed!", + $"{winner.NameList} {(winner.Players.Count > 1 ? "are" : "is")} the champion{(winner.Players.Count == 1 ? "" : "s")}."); + } + } + catch + { + } + + GiveAwards(); + + CurrentStage = TournamentStage.Inactive; + Undefeated.Clear(); + } + else if (Pyramid.Levels.Count > 0) + { + PyramidLevel activeLevel = (PyramidLevel)Pyramid.Levels[Pyramid.Levels.Count - 1]; + bool stillGoing = false; + + for (int i = 0; i < activeLevel.Matches.Count; ++i) + { + TournyMatch match = (TournyMatch)activeLevel.Matches[i]; + + if (match.Winner == null) + { + stillGoing = true; + + if (!match.InProgress) + for (int j = 0; j < Arenas.Count; ++j) + { + Arena arena = (Arena)Arenas[j]; + + if (!arena.IsOccupied) + { + match.Start(arena, this); + break; + } + } + } + } + + if (!stillGoing) + { + for (int i = Undefeated.Count - 1; i >= 0; --i) + { + TournyParticipant part = (TournyParticipant)Undefeated[i]; + bool bad = false; + + for (int j = 0; j < part.Players.Count; ++j) + { + Mobile check = (Mobile)part.Players[j]; + + if (check.Deleted || check.Map == null || check.Map == Map.Internal || !check.Alive || + Sigil.ExistsOn(check) || check.Region.IsPartOf(typeof(Jail))) + { + bad = true; + break; + } + } + + if (bad) + { + for (int j = 0; j < part.Players.Count; ++j) + ((Mobile)part.Players[j]).SendMessage("You have been disqualified from the tournament."); + + Undefeated.RemoveAt(i); + + if (Undefeated.Count == 1) + { + TournyParticipant winner = (TournyParticipant)Undefeated[0]; + + try + { + if (EventController != null) + { + Alert("The tournament has completed!", + $"Team {EventController.GetTeamName(((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner))} has won"); + } + else if (TournyType == TournyType.RandomTeam) + { + Alert("The tournament has completed!", + $"Team {((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); + } + else if (TournyType == TournyType.Faction) + { + if (m_ParticipantsPerMatch == 4) + { + string name = "(null)"; + + switch (((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]) + .Participants.IndexOf(winner)) + { + case 0: + { + name = "Minax"; + break; + } + case 1: + { + name = "Council of Mages"; + break; + } + case 2: + { + name = "True Britannians"; + break; + } + case 3: + { + name = "Shadowlords"; + break; + } + } + + Alert("The tournament has completed!", $"The {name} team has won!"); + } + else if (m_ParticipantsPerMatch == 2) + { + Alert("The tournament has completed!", + $"The {(((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Evil" : "Hero")} team has won!"); + } + else + { + Alert("The tournament has completed!", + $"Team {((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) + 1} has won!"); + } + } + else if (TournyType == TournyType.RedVsBlue) + { + Alert("The tournament has completed!", + $"Team {(((TournyMatch)((PyramidLevel)Pyramid.Levels[0]).Matches[0]).Participants.IndexOf(winner) == 0 ? "Red" : "Blue")} has won!"); + } + else + { + Alert("The tournament has completed!", + $"{winner.NameList} {(winner.Players.Count > 1 ? "are" : "is")} the champion{(winner.Players.Count == 1 ? "" : "s")}."); + } + } + catch + { + } + + GiveAwards(); + + CurrentStage = TournamentStage.Inactive; + Undefeated.Clear(); + break; + } + } + } + + if (Undefeated.Count > 1) + Pyramid.AddLevel(m_ParticipantsPerMatch, Undefeated, GroupType, TournyType); + } + } + } + } + + public void Alert(params string[] alerts) + { + for (int i = 0; i < Arenas.Count; ++i) + Alert((Arena)Arenas[i], alerts); + } + + public void Alert(Arena arena, params string[] alerts) + { + if (arena?.Announcer != null) + for (int j = 0; j < alerts.Length; ++j) + Timer.DelayCall(TimeSpan.FromSeconds(Math.Max(j - 0.5, 0.0)), new TimerStateCallback(Alert_Callback), + new object[] { arena.Announcer, alerts[j] }); + } + + private void Alert_Callback(object state) + { + object[] states = (object[])state; + + ((Mobile)states[0])?.PublicOverheadMessage(MessageType.Regular, 0x35, false, (string)states[1]); + } + } + + public class TournyPyramid + { + public TournyPyramid() + { + Levels = new ArrayList(); + } + + public ArrayList Levels{ get; set; } + + public void AddLevel(int partsPerMatch, ArrayList participants, GroupingType groupType, TournyType tournyType) + { + ArrayList copy = new ArrayList(participants); + + if (groupType == GroupingType.Nearest || groupType == GroupingType.HighVsLow) + copy.Sort(); + + PyramidLevel level = new PyramidLevel(); + + switch (tournyType) + { + case TournyType.RedVsBlue: + { + TournyParticipant[] parts = new TournyParticipant[2]; + + for (int i = 0; i < parts.Length; ++i) + parts[i] = new TournyParticipant(new ArrayList()); + + for (int i = 0; i < copy.Count; ++i) + { + ArrayList players = ((TournyParticipant)copy[i]).Players; + + for (int j = 0; j < players.Count; ++j) + { + Mobile mob = (Mobile)players[j]; + + if (mob.Kills >= 5) + parts[0].Players.Add(mob); + else + parts[1].Players.Add(mob); + } + } + + level.Matches.Add(new TournyMatch(new ArrayList(parts))); + break; + } + case TournyType.Faction: + { + TournyParticipant[] parts = new TournyParticipant[partsPerMatch]; + + for (int i = 0; i < parts.Length; ++i) + parts[i] = new TournyParticipant(new ArrayList()); + + for (int i = 0; i < copy.Count; ++i) + { + ArrayList players = ((TournyParticipant)copy[i]).Players; + + for (int j = 0; j < players.Count; ++j) + { + Mobile mob = (Mobile)players[j]; + + int index = -1; + + if (partsPerMatch == 4) + { + Faction fac = Faction.Find(mob); + + if (fac != null) index = fac.Definition.Sort; + } + else if (partsPerMatch == 2) + { + if (Ethic.Evil.IsEligible(mob)) + index = 0; + else if (Ethic.Hero.IsEligible(mob)) index = 1; + } + + if (index < 0 || index >= partsPerMatch) index = i % partsPerMatch; + + parts[index].Players.Add(mob); + } + } + + level.Matches.Add(new TournyMatch(new ArrayList(parts))); + break; + } + case TournyType.RandomTeam: + { + TournyParticipant[] parts = new TournyParticipant[partsPerMatch]; + + for (int i = 0; i < partsPerMatch; ++i) + parts[i] = new TournyParticipant(new ArrayList()); + + for (int i = 0; i < copy.Count; ++i) + parts[i % parts.Length].Players.AddRange(((TournyParticipant)copy[i]).Players); + + level.Matches.Add(new TournyMatch(new ArrayList(parts))); + break; + } + case TournyType.FreeForAll: + { + level.Matches.Add(new TournyMatch(copy)); + break; + } + case TournyType.Standard: + { + if (partsPerMatch >= 2 && participants.Count % partsPerMatch == 1) + { + int lowAdvances = int.MaxValue; + + for (int i = 0; i < participants.Count; ++i) + { + TournyParticipant p = (TournyParticipant)participants[i]; + + if (p.FreeAdvances < lowAdvances) + lowAdvances = p.FreeAdvances; + } + + ArrayList toAdvance = new ArrayList(); + + for (int i = 0; i < participants.Count; ++i) + { + TournyParticipant p = (TournyParticipant)participants[i]; + + if (p.FreeAdvances == lowAdvances) + toAdvance.Add(p); + } + + if (toAdvance.Count == 0) + toAdvance = copy; // sanity + + int idx = Utility.Random(toAdvance.Count); + + ((TournyParticipant)toAdvance[idx]).AddLog( + "Advanced automatically due to an odd number of challengers."); + level.FreeAdvance = (TournyParticipant)toAdvance[idx]; + ++level.FreeAdvance.FreeAdvances; + copy.Remove(toAdvance[idx]); + } + + while (copy.Count >= partsPerMatch) + { + ArrayList thisMatch = new ArrayList(); + + for (int i = 0; i < partsPerMatch; ++i) + { + int idx = 0; + + switch (groupType) + { + case GroupingType.HighVsLow: + idx = i * (copy.Count - 1) / (partsPerMatch - 1); + break; + case GroupingType.Nearest: + idx = 0; + break; + case GroupingType.Random: + idx = Utility.Random(copy.Count); + break; + } - if ( tourny.EventController != null ) - dc.m_EventGame = tourny.EventController.Construct( dc ); + thisMatch.Add(copy[idx]); + copy.RemoveAt(idx); + } - dc.m_Tournament = tourny; - dc.m_Match = this; + level.Matches.Add(new TournyMatch(thisMatch)); + } - dc.m_OverrideArena = arena; + if (copy.Count > 1) + level.Matches.Add(new TournyMatch(copy)); - if ( tourny.SuddenDeath > TimeSpan.Zero && (tourny.SuddenDeathRounds == 0 || tourny.Pyramid.Levels.Count <= tourny.SuddenDeathRounds) ) - dc.StartSuddenDeath( tourny.SuddenDeath ); + break; + } + } - dc.SendReadyGump( 0 ); + Levels.Add(level); + } + } - if ( dc.StartedBeginCountdown ) - { - Context = dc; + public class PyramidLevel + { + public PyramidLevel() + { + Matches = new ArrayList(); + } - for ( int i = 0; i < Participants.Count; ++i ) - { - TournyParticipant p = (TournyParticipant)Participants[i]; + public ArrayList Matches{ get; set; } - for ( int j = 0; j < p.Players.Count; ++j ) - { - Mobile mob = (Mobile)p.Players[j]; + public TournyParticipant FreeAdvance{ get; set; } + } - foreach ( Mobile view in mob.GetMobilesInRange( 18 ) ) - { - if ( !mob.CanSee( view ) ) - mob.Send( view.RemovePacket ); - } + public class TournyMatch + { + public TournyMatch(ArrayList participants) + { + Participants = participants; - mob.LocalOverheadMessage( MessageType.Emote, 0x3B2, false, "* Your mind focuses intently on the fight and all other distractions fade away *" ); - } - } - } - else - { - dc.Unregister(); - dc.StopCountdown(); - } - } + for (int i = 0; i < participants.Count; ++i) + { + TournyParticipant part = (TournyParticipant)participants[i]; - public TournyMatch( ArrayList participants ) - { - Participants = participants; + StringBuilder sb = new StringBuilder(); - for ( int i = 0; i < participants.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)participants[i]; + sb.Append("Matched in a duel against "); - StringBuilder sb = new StringBuilder(); + if (participants.Count > 2) + sb.AppendFormat("{0} other {1}: ", participants.Count - 1, + part.Players.Count == 1 ? "players" : "teams"); - sb.Append( "Matched in a duel against " ); + bool hasAppended = false; - if ( participants.Count > 2 ) - sb.AppendFormat( "{0} other {1}: ", participants.Count - 1, part.Players.Count == 1 ? "players" : "teams" ); + for (int j = 0; j < participants.Count; ++j) + { + if (i == j) + continue; - bool hasAppended = false; + if (hasAppended) + sb.Append(", "); - for ( int j = 0; j < participants.Count; ++j ) - { - if ( i == j ) - continue; + sb.Append(((TournyParticipant)participants[j]).NameList); + hasAppended = true; + } - if ( hasAppended ) - sb.Append( ", " ); + sb.Append("."); - sb.Append( ((TournyParticipant)participants[j]).NameList ); - hasAppended = true; - } + part.AddLog(sb.ToString()); + } + } - sb.Append( "." ); + public ArrayList Participants{ get; set; } - part.AddLog( sb.ToString() ); - } - } - } - - public class TournyParticipant : IComparable - { - public ArrayList Players { get; set; } - - public ArrayList Log { get; set; } + public TournyParticipant Winner{ get; set; } - public int FreeAdvances { get; set; } + public DuelContext Context{ get; set; } - public int TotalLadderXP - { - get - { - Ladder ladder = Ladder.Instance; - - if ( ladder == null ) - return 0; - - int total = 0; - - for ( int i = 0; i < Players.Count; ++i ) - { - Mobile mob = (Mobile)Players[i]; - LadderEntry entry = ladder.Find( mob ); - - if ( entry != null ) - total += entry.Experience; - } - - return total; - } - } - - public string NameList - { - get - { - StringBuilder sb = new StringBuilder(); - - for ( int i = 0; i < Players.Count; ++i ) - { - if ( Players[i] == null ) - continue; - - Mobile mob = (Mobile) Players[i]; - - if ( sb.Length > 0 ) - { - if ( Players.Count == 2 ) - sb.Append( " and " ); - else if ( (i+1) < Players.Count ) - sb.Append( ", " ); - else - sb.Append( ", and " ); - } - - sb.Append( mob.Name ); - } - - if ( sb.Length == 0 ) - return "Empty"; - - return sb.ToString(); - } - } - - public void AddLog( string text ) - { - Log.Add( text ); - } - - public void AddLog( string format, params object[] args ) - { - AddLog( string.Format( format, args ) ); - } - - public void WonMatch( TournyMatch match ) - { - AddLog( "Match won." ); - } - - public void LostMatch( TournyMatch match ) - { - AddLog( "Match lost." ); - } - - public TournyParticipant( Mobile owner ) - { - Log = new ArrayList(); - Players = new ArrayList(); - Players.Add( owner ); - } - - public TournyParticipant( ArrayList players ) - { - Log = new ArrayList(); - Players = players; - } - - public int CompareTo( object obj ) - { - TournyParticipant p = (TournyParticipant)obj; - - return p.TotalLadderXP - TotalLadderXP; - } - } - - public enum TournyBracketGumpType - { - Index, - Rules_Info, - Participant_List, - Participant_Info, - Round_List, - Round_Info, - Match_Info, - Player_Info - } - - public class TournamentBracketGump : Gump - { - private Mobile m_From; - private Tournament m_Tournament; - private TournyBracketGumpType m_Type; - private ArrayList m_List; - private int m_Page; - private int m_PerPage; - private object m_Object; - - private const int BlackColor32 = 0x000008; - private const int LabelColor32 = 0xFFFFFF; - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - private void AddBorderedText( int x, int y, int width, int height, string text, int color, int borderColor ) - { - AddColoredText( x - 1, y - 1, width, height, text, borderColor ); - AddColoredText( x - 1, y + 1, width, height, text, borderColor ); - AddColoredText( x + 1, y - 1, width, height, text, borderColor ); - AddColoredText( x + 1, y + 1, width, height, text, borderColor ); - AddColoredText( x, y, width, height, text, color ); - } - - private void AddColoredText( int x, int y, int width, int height, string text, int color ) - { - if ( color == 0 ) - AddHtml( x, y, width, height, text, false, false ); - else - AddHtml( x, y, width, height, Color( text, color ), false, false ); - } - - public void AddRightArrow( int x, int y, int bid, string text ) - { - AddButton( x, y, 0x15E1, 0x15E5, bid, GumpButtonType.Reply, 0 ); - - if ( text != null ) - AddHtml( x + 20, y - 1, 230, 20, text, false, false ); - } - - public void AddRightArrow( int x, int y, int bid ) - { - AddRightArrow( x, y, bid, null ); - } - - public void AddLeftArrow( int x, int y, int bid, string text ) - { - AddButton( x, y, 0x15E3, 0x15E7, bid, GumpButtonType.Reply, 0 ); - - if ( text != null ) - AddHtml( x + 20, y - 1, 230, 20, text, false, false ); - } - - public void AddLeftArrow( int x, int y, int bid ) - { - AddLeftArrow( x, y, bid, null ); - } - - public int ToButtonID( int type, int index ) - { - return 1 + (index * 7) + type; - } - - public bool FromButtonID( int bid, out int type, out int index ) - { - type = ( bid - 1 ) % 7; - index = ( bid - 1 ) / 7; - return ( bid >= 1 ); - } - - public void StartPage( out int index, out int count, out int y, int perPage ) - { - m_PerPage = perPage; - - index = Math.Max( m_Page * perPage, 0 ); - count = Math.Max( Math.Min( m_List.Count - index, perPage ), 0 ); - - y = 53 + ((12 - perPage) * 18); - - if ( m_Page > 0 ) - AddLeftArrow( 242, 35, ToButtonID( 1, 0 ) ); - - if ( (m_Page + 1) * perPage < m_List.Count ) - AddRightArrow( 260, 35, ToButtonID( 1, 1 ) ); - } - - public TournamentBracketGump( Mobile from, Tournament tourny, TournyBracketGumpType type, ArrayList list, int page, object obj ) : base( 50, 50 ) - { - m_From = from; - m_Tournament = tourny; - m_Type = type; - m_List = list; - m_Page = page; - m_Object = obj; - m_PerPage = 12; - - switch ( type ) - { - case TournyBracketGumpType.Index: - { - AddPage( 0 ); - AddBackground( 0, 0, 300, 300, 9380 ); - - StringBuilder sb = new StringBuilder(); - - if ( tourny.TournyType == TournyType.FreeForAll ) - { - sb.Append( "FFA" ); - } - else if ( tourny.TournyType == TournyType.RandomTeam ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-Team" ); - } - else if ( tourny.TournyType == TournyType.RedVsBlue ) - { - sb.Append( "Red v Blue" ); - } - else if ( tourny.TournyType == TournyType.Faction ) - { - sb.Append( tourny.ParticipantsPerMatch ); - sb.Append( "-Team Faction" ); - } - else - { - for ( int i = 0; i < tourny.ParticipantsPerMatch; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( 'v' ); - - sb.Append( tourny.PlayersPerParticipant ); - } - } - - if ( tourny.EventController != null ) - sb.Append( ' ' ).Append( tourny.EventController.Title ); - - sb.Append( " Tournament Bracket" ); - - AddHtml( 25, 35, 250, 20, Center( sb.ToString() ), false, false ); - - AddRightArrow( 25, 53, ToButtonID( 0, 4 ), "Rules" ); - AddRightArrow( 25, 71, ToButtonID( 0, 1 ), "Participants" ); - - if ( m_Tournament.Stage == TournamentStage.Signup ) - { - TimeSpan until = ( m_Tournament.SignupStart + m_Tournament.SignupPeriod ) - DateTime.UtcNow; - string text; - int secs = (int) until.TotalSeconds; - - if ( secs > 0 ) - { - int mins = secs / 60; - secs %= 60; - - if ( mins > 0 && secs > 0 ) - text = - $"The tournament will begin in {mins} minute{(mins == 1 ? "" : "s")} and {secs} second{(secs == 1 ? "" : "s")}."; - else if ( mins > 0 ) - text = $"The tournament will begin in {mins} minute{(mins == 1 ? "" : "s")}."; - else if ( secs > 0 ) - text = $"The tournament will begin in {secs} second{(secs == 1 ? "" : "s")}."; - else - text = "The tournament will begin shortly."; - } - else - { - text = "The tournament will begin shortly."; - } - - AddHtml( 25, 92, 250, 40, text, false, false ); - } - else - { - AddRightArrow( 25, 89, ToButtonID( 0, 2 ), "Rounds" ); - } - - break; - } - case TournyBracketGumpType.Rules_Info: - { - Ruleset ruleset = tourny.Ruleset; - Ruleset basedef = ruleset.Base; - - BitArray defs; - - if ( ruleset.Flavors.Count > 0 ) - { - defs = new BitArray( basedef.Options ); - - for ( int i = 0; i < ruleset.Flavors.Count; ++i ) - defs.Or( ((Ruleset)ruleset.Flavors[i]).Options ); - } - else - { - defs = basedef.Options; - } - - int changes = 0; - - BitArray opts = ruleset.Options; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - ++changes; - } - - AddPage( 0 ); - AddBackground( 0, 0, 300, 60 + 18 + 20 + 20 + 20 + 8 + 20 + (ruleset.Flavors.Count * 18) + 4 + 20 + (changes * 22) + 6, 9380 ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 0 ) ); - AddHtml( 25, 35, 250, 20, Center( "Rules" ), false, false ); - - int y = 53; - - string groupText = null; - - switch ( tourny.GroupType ) - { - case GroupingType.HighVsLow: groupText = "High vs Low"; break; - case GroupingType.Nearest: groupText = "Closest opponent"; break; - case GroupingType.Random: groupText = "Random"; break; - } - - AddHtml( 35, y, 190, 20, $"Grouping: {groupText}", false, false ); - y += 20; - - string tieText = null; - - switch ( tourny.TieType ) - { - case TieType.Random: tieText = "Random"; break; - case TieType.Highest: tieText = "Highest advances"; break; - case TieType.Lowest: tieText = "Lowest advances"; break; - case TieType.FullAdvancement: tieText = ( tourny.ParticipantsPerMatch == 2 ? "Both advance" : "Everyone advances" ); break; - case TieType.FullElimination: tieText = ( tourny.ParticipantsPerMatch == 2 ? "Both eliminated" : "Everyone eliminated" ); break; - } - - AddHtml( 35, y, 190, 20, $"Tiebreaker: {tieText}", false, false ); - y += 20; - - string sdText = "Off"; - - if ( tourny.SuddenDeath > TimeSpan.Zero ) - { - sdText = $"{(int) tourny.SuddenDeath.TotalMinutes}:{tourny.SuddenDeath.Seconds:D2}"; - - if ( tourny.SuddenDeathRounds > 0 ) - sdText = $"{sdText} (first {tourny.SuddenDeathRounds} rounds)"; - else - sdText = $"{sdText} (all rounds)"; - } - - AddHtml( 35, y, 240, 20, $"Sudden Death: {sdText}", false, false ); - y += 20; - - y += 8; - - AddHtml( 35, y, 190, 20, $"Ruleset: {basedef.Title}", false, false ); - y += 20; - - for ( int i = 0; i < ruleset.Flavors.Count; ++i, y += 18 ) - AddHtml( 35, y, 190, 20, $" + {((Ruleset) ruleset.Flavors[i]).Title}", false, false ); - - y += 4; - - if ( changes > 0 ) - { - AddHtml( 35, y, 190, 20, "Modifications:", false, false ); - y += 20; - - for ( int i = 0; i < opts.Length; ++i ) - { - if ( defs[i] != opts[i] ) - { - string name = ruleset.Layout.FindByIndex( i ); - - if ( name != null ) // sanity - { - AddImage( 35, y, opts[i] ? 0xD3 : 0xD2 ); - AddHtml( 60, y, 165, 22, name, false, false ); - } + public bool InProgress => Context != null && Context.Registered; - y += 22; - } - } - } - else - { - AddHtml( 35, y, 190, 20, "Modifications: None", false, false ); - y += 20; - } + public void Start(Arena arena, Tournament tourny) + { + TournyParticipant first = (TournyParticipant)Participants[0]; - break; - } - case TournyBracketGumpType.Participant_List: - { - AddPage( 0 ); - AddBackground( 0, 0, 300, 300, 9380 ); - - if ( m_List == null ) - m_List = new ArrayList( tourny.Participants ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 0 ) ); - AddHtml( 25, 35, 250, 20, Center($"{m_List.Count} Participant{(m_List.Count == 1 ? "" : "s")}"), false, false ); - - int index, count, y; - StartPage( out index, out count, out y, 12 ); - - for ( int i = 0; i < count; ++i, y += 18 ) - { - TournyParticipant part = (TournyParticipant)m_List[index + i]; - string name = part.NameList; - - if ( m_Tournament.TournyType != TournyType.Standard && part.Players.Count == 1 ) - { - if ( part.Players[0] is PlayerMobile pm && pm.DuelPlayer != null ) - name = Color( name, pm.DuelPlayer.Eliminated ? 0x6633333 : 0x336666 ); - } - - AddRightArrow( 25, y, ToButtonID( 2, index + i ), name ); - } - - break; - } - case TournyBracketGumpType.Participant_Info: - { - if ( !(obj is TournyParticipant part) ) - break; - - AddPage( 0 ); - AddBackground( 0, 0, 300, 60 + 18 + 20 + (part.Players.Count * 18) + 20 + 20 + 160, 9380 ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 1 ) ); - AddHtml( 25, 35, 250, 20, Center( "Participants" ), false, false ); - - int y = 53; + DuelContext dc = new DuelContext((Mobile)first.Players[0], tourny.Ruleset.Layout, false); + dc.Ruleset.Options.SetAll(false); + dc.Ruleset.Options.Or(tourny.Ruleset.Options); - AddHtml( 25, y, 200, 20, part.Players.Count == 1 ? "Players" : "Team", false, false ); - y += 20; + for (int i = 0; i < Participants.Count; ++i) + { + TournyParticipant tournyPart = (TournyParticipant)Participants[i]; + Participant duelPart = new Participant(dc, tournyPart.Players.Count); - for ( int i = 0; i < part.Players.Count; ++i ) - { - Mobile mob = (Mobile)part.Players[i]; - string name = mob.Name; + duelPart.TournyPart = tournyPart; - if ( m_Tournament.TournyType != TournyType.Standard ) - { - if ( mob is PlayerMobile pm && pm.DuelPlayer != null ) - name = Color( name, pm.DuelPlayer.Eliminated ? 0x6633333 : 0x336666 ); - } + for (int j = 0; j < tournyPart.Players.Count; ++j) + duelPart.Add((Mobile)tournyPart.Players[j]); - AddRightArrow( 35, y, ToButtonID( 4, i ), name ); - y += 18; - } + for (int j = 0; j < duelPart.Players.Length; ++j) + if (duelPart.Players[j] != null) + duelPart.Players[j].Ready = true; - AddHtml( 25, y, 200, 20, - $"Free Advances: {(part.FreeAdvances == 0 ? "None" : part.FreeAdvances.ToString())}", false, false ); - y += 20; + dc.Participants.Add(duelPart); + } - AddHtml( 25, y, 200, 20, "Log:", false, false ); - y += 20; + if (tourny.EventController != null) + dc.m_EventGame = tourny.EventController.Construct(dc); - StringBuilder sb = new StringBuilder(); - - for ( int i = 0; i < part.Log.Count; ++i ) - { - if ( sb.Length > 0 ) - sb.Append( "
" ); - - sb.Append( part.Log[i] ); - } - - if ( sb.Length == 0 ) - sb.Append( "Nothing logged yet." ); - - AddHtml( 25, y, 250, 150, Color( sb.ToString(), BlackColor32 ), false, true ); - - break; - } - case TournyBracketGumpType.Player_Info: - { - AddPage( 0 ); - AddBackground( 0, 0, 300, 300, 9380 ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 3 ) ); - AddHtml( 25, 35, 250, 20, Center( "Participants" ), false, false ); - - if ( !(obj is Mobile mob) ) - break; + dc.m_Tournament = tourny; + dc.m_Match = this; - Ladder ladder = Ladder.Instance; - LadderEntry entry = ladder?.Find( mob ); - - AddHtml( 25, 53, 250, 20, $"Name: {mob.Name}", false, false ); - AddHtml( 25, 73, 250, 20, - $"Guild: {(mob.Guild == null ? "None" : mob.Guild.Name + " [" + mob.Guild.Abbreviation + "]")}", false, false ); - AddHtml( 25, 93, 250, 20, $"Rank: {(entry == null ? "N/A" : LadderGump.Rank(entry.Index + 1))}", false, false ); - AddHtml( 25, 113, 250, 20, $"Level: {(entry == null ? 0 : Ladder.GetLevel(entry.Experience))}", false, false ); - AddHtml( 25, 133, 250, 20, $"Wins: {entry?.Wins ?? 0:N0}", false, false ); - AddHtml( 25, 153, 250, 20, $"Losses: {entry?.Losses ?? 0:N0}", false, false ); - - break; - } - case TournyBracketGumpType.Round_List: - { - AddPage( 0 ); - AddBackground( 0, 0, 300, 300, 9380 ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 0 ) ); - AddHtml( 25, 35, 250, 20, Center( "Rounds" ), false, false ); - - if ( m_List == null ) - m_List = new ArrayList( tourny.Pyramid.Levels ); - - int index, count, y; - StartPage( out index, out count, out y, 12 ); - - for ( int i = 0; i < count; ++i, y += 18 ) - { - // PyramidLevel level = (PyramidLevel)m_List[index + i]; - - AddRightArrow( 25, y, ToButtonID( 3, index + i ), "Round #" + (index + i + 1) ); - } - - break; - } - case TournyBracketGumpType.Round_Info: - { - AddPage( 0 ); - AddBackground( 0, 0, 300, 300, 9380 ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 2 ) ); - AddHtml( 25, 35, 250, 20, Center( "Rounds" ), false, false ); - - if ( !(m_Object is PyramidLevel level) ) - break; - - if ( m_List == null ) - m_List = new ArrayList( level.Matches ); - - AddRightArrow( 25, 53, ToButtonID( 5, 0 ), - $"Free Advance: {(level.FreeAdvance == null ? "None" : level.FreeAdvance.NameList)}"); - - AddHtml( 25, 73, 200, 20, $"{m_List.Count} Match{(m_List.Count == 1 ? "" : "es")}", false, false ); - - int index, count, y; - StartPage( out index, out count, out y, 10 ); - - for ( int i = 0; i < count; ++i, y += 18 ) - { - TournyMatch match = (TournyMatch)m_List[index + i]; - - int color = -1; - - if ( match.InProgress ) - color = 0x336666; - else if ( match.Context != null && match.Winner == null ) - color = 0x666666; - - StringBuilder sb = new StringBuilder(); - - if ( m_Tournament.TournyType == TournyType.Standard ) - { - for ( int j = 0; j < match.Participants.Count; ++j ) - { - if ( sb.Length > 0 ) - sb.Append( " vs " ); - - TournyParticipant part = (TournyParticipant)match.Participants[j]; - string txt = part.NameList; - - if ( color == -1 && match.Context != null && match.Winner == part ) - txt = Color( txt, 0x336633 ); - else if ( color == -1 && match.Context != null ) - txt = Color( txt, 0x663333 ); - - sb.Append( txt ); - } - } - else if ( m_Tournament.EventController != null || m_Tournament.TournyType == TournyType.RandomTeam || m_Tournament.TournyType == TournyType.RedVsBlue || m_Tournament.TournyType == TournyType.Faction ) - { - for ( int j = 0; j < match.Participants.Count; ++j ) - { - if ( sb.Length > 0 ) - sb.Append( " vs " ); - - TournyParticipant part = (TournyParticipant)match.Participants[j]; - string txt; - - if ( m_Tournament.EventController != null ) - txt = $"Team {m_Tournament.EventController.GetTeamName(j)} ({part.Players.Count})"; - else if ( m_Tournament.TournyType == TournyType.RandomTeam ) - txt = $"Team {j + 1} ({part.Players.Count})"; - else if ( m_Tournament.TournyType == TournyType.Faction ) { - if ( m_Tournament.ParticipantsPerMatch == 4 ) - { - string name = "(null)"; - - switch ( j ) - { - case 0: { - name = "Minax"; - break; - } - case 1: { - name = "Council of Mages"; - break; - } - case 2: { - name = "True Britannians"; - break; - } - case 3: { - name = "Shadowlords"; - break; - } - } - - txt = $"{name} ({part.Players.Count})"; - } - else if ( m_Tournament.ParticipantsPerMatch == 2 ) - { - txt = $"{(j == 0 ? "Evil" : "Hero")} Team ({part.Players.Count})"; - } - else - { - txt = $"Team {j + 1} ({part.Players.Count})"; - } - } - else - txt = $"Team {(j == 0 ? "Red" : "Blue")} ({part.Players.Count})"; - - if ( color == -1 && match.Context != null && match.Winner == part ) - txt = Color( txt, 0x336633 ); - else if ( color == -1 && match.Context != null ) - txt = Color( txt, 0x663333 ); - - sb.Append( txt ); - } - } - else if ( m_Tournament.TournyType == TournyType.FreeForAll ) - { - sb.Append( "Free For All" ); - } - - string str = sb.ToString(); - - if ( color >= 0 ) - str = Color( str, color ); - - AddRightArrow( 25, y, ToButtonID( 5, index + i + 1 ), str ); - } - - break; - } - case TournyBracketGumpType.Match_Info: - { - if ( !(obj is TournyMatch match) ) - break; - - int ct = ( m_Tournament.TournyType == TournyType.FreeForAll ? 2 : match.Participants.Count ); - - AddPage( 0 ); - AddBackground( 0, 0, 300, 60 + 18 + 20 + 20 + 20 + (ct*18) + 6, 9380 ); - - AddLeftArrow( 25, 11, ToButtonID( 0, 5 ) ); - AddHtml( 25, 35, 250, 20, Center( "Rounds" ), false, false ); - - AddHtml( 25, 53, 250, 20, $"Winner: {(match.Winner == null ? "N/A" : match.Winner.NameList)}", false, false ); - AddHtml( 25, 73, 250, 20, - $"State: {(match.InProgress ? "In progress" : match.Context != null ? "Complete" : "Waiting")}", false, false ); - AddHtml( 25, 93, 250, 20, "Participants:", false, false ); - - if ( m_Tournament.TournyType == TournyType.Standard ) - { - for ( int i = 0; i < match.Participants.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)match.Participants[i]; - - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), part.NameList ); - } - } - else if ( m_Tournament.EventController != null || m_Tournament.TournyType == TournyType.RandomTeam || m_Tournament.TournyType == TournyType.RedVsBlue || m_Tournament.TournyType == TournyType.Faction ) - { - for ( int i = 0; i < match.Participants.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)match.Participants[i]; - - if ( m_Tournament.EventController != null ) - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), - $"Team {m_Tournament.EventController.GetTeamName(i)} ({part.Players.Count})"); - else if ( m_Tournament.TournyType == TournyType.RandomTeam ) - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), - $"Team {i + 1} ({part.Players.Count})"); - else if ( m_Tournament.TournyType == TournyType.Faction ) { - if ( m_Tournament.ParticipantsPerMatch == 4 ) - { - string name = "(null)"; - - switch ( i ) - { - case 0: { - name = "Minax"; - break; - } - case 1: { - name = "Council of Mages"; - break; - } - case 2: { - name = "True Britannians"; - break; - } - case 3: { - name = "Shadowlords"; - break; - } - } - - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), - $"{name} ({part.Players.Count})"); - } - else if ( m_Tournament.ParticipantsPerMatch == 2 ) - { - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), - $"{(i == 0 ? "Evil" : "Hero")} Team ({part.Players.Count})"); - } - else - { - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), - $"Team {i + 1} ({part.Players.Count})"); - } - } - else - AddRightArrow( 25, 113 + (i * 18), ToButtonID( 6, i ), - $"Team {(i == 0 ? "Red" : "Blue")} ({part.Players.Count})"); - } - } - else if ( m_Tournament.TournyType == TournyType.FreeForAll ) - { - AddHtml( 25, 113, 250, 20, "Free For All", false, false ); - } - - break; - } - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int type, index; - - if ( !FromButtonID( info.ButtonID, out type, out index ) ) - return; - - switch ( type ) - { - case 0: - { - switch ( index ) - { - case 0: m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Index, null, 0, null ) ); break; - case 1: m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Participant_List, null, 0, null ) ); break; - case 2: m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Round_List, null, 0, null ) ); break; - case 4: m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Rules_Info, null, 0, null ) ); break; - case 3: - { - Mobile mob = m_Object as Mobile; - - for ( int i = 0; i < m_Tournament.Participants.Count; ++i ) - { - TournyParticipant part = (TournyParticipant)m_Tournament.Participants[i]; - - if ( part.Players.Contains( mob ) ) - { - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Participant_Info, null, 0, part ) ); - break; - } - } - - break; - } - case 5: - { - if ( !(m_Object is TournyMatch match) ) - break; - - for ( int i = 0; i < m_Tournament.Pyramid.Levels.Count; ++i ) - { - PyramidLevel level = (PyramidLevel)m_Tournament.Pyramid.Levels[i]; - - if ( level.Matches.Contains( match ) ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Round_Info, null, 0, level ) ); - } - - break; - } - } - - break; - } - case 1: - { - switch ( index ) - { - case 0: - { - if ( m_List != null && m_Page > 0 ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, m_Type, m_List, m_Page - 1, m_Object ) ); - - break; - } - case 1: - { - if ( m_List != null && ((m_Page + 1) * m_PerPage) < m_List.Count ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, m_Type, m_List, m_Page + 1, m_Object ) ); - - break; - } - } - - break; - } - case 2: - { - if ( m_Type != TournyBracketGumpType.Participant_List ) - break; - - if ( index >= 0 && index < m_List.Count ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Participant_Info, null, 0, m_List[index] ) ); - - break; - } - case 3: - { - if ( m_Type != TournyBracketGumpType.Round_List ) - break; - - if ( index >= 0 && index < m_List.Count ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Round_Info, null, 0, m_List[index] ) ); - - break; - } - case 4: - { - if ( m_Type != TournyBracketGumpType.Participant_Info ) - break; - - if ( m_Object is TournyParticipant part && index >= 0 && index < part.Players.Count ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Player_Info, null, 0, part.Players[index] ) ); - - break; - } - case 5: - { - if ( m_Type != TournyBracketGumpType.Round_Info ) - break; - - if ( !(m_Object is PyramidLevel level) ) - break; - - if ( index == 0 ) - { - if ( level.FreeAdvance != null ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Participant_Info, null, 0, level.FreeAdvance ) ); - else - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, m_Type, m_List, m_Page, m_Object ) ); - } - else if ( index >= 1 && index <= level.Matches.Count ) - { - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Match_Info, null, 0, level.Matches[index-1] ) ); - } - - break; - } - case 6: - { - if ( m_Type != TournyBracketGumpType.Match_Info ) - break; - - if ( m_Object is TournyMatch match && index >= 0 && index < match.Participants.Count ) - m_From.SendGump( new TournamentBracketGump( m_From, m_Tournament, TournyBracketGumpType.Participant_Info, null, 0, match.Participants[index] ) ); - - break; - } - } - } - } - - public class TournamentBracketItem : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public TournamentController Tournament { get; set; } - - public override string DefaultName => "tournament bracket"; - - [Constructible] - public TournamentBracketItem() : base( 3774 ) - { - Movable = false; - } - - public override void OnDoubleClick(Mobile from) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that - } - else - { - Tournament tourny = Tournament?.Tournament; - - if ( tourny != null ) - { - from.CloseGump( typeof( TournamentBracketGump ) ); - from.SendGump( new TournamentBracketGump( from, tourny, TournyBracketGumpType.Index, null, 0, null ) ); - - /*if ( tourny.Stage == TournamentStage.Fighting && tourny.Pyramid.Levels.Count > 0 ) - from.SendGump( new TournamentBracketGump( tourny, (PyramidLevel)tourny.Pyramid.Levels[tourny.Pyramid.Levels.Count - 1] ) ); - else - from.SendGump( new TournamentBracketGump( tourny, 0 ) );*/ - } - } - } - - public TournamentBracketItem( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - writer.Write( (Item) Tournament ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Tournament = reader.ReadItem() as TournamentController; - break; - } - } - } - } -} + dc.m_OverrideArena = arena; + + if (tourny.SuddenDeath > TimeSpan.Zero && + (tourny.SuddenDeathRounds == 0 || tourny.Pyramid.Levels.Count <= tourny.SuddenDeathRounds)) + dc.StartSuddenDeath(tourny.SuddenDeath); + + dc.SendReadyGump(0); + + if (dc.StartedBeginCountdown) + { + Context = dc; + + for (int i = 0; i < Participants.Count; ++i) + { + TournyParticipant p = (TournyParticipant)Participants[i]; + + for (int j = 0; j < p.Players.Count; ++j) + { + Mobile mob = (Mobile)p.Players[j]; + + foreach (Mobile view in mob.GetMobilesInRange(18)) + if (!mob.CanSee(view)) + mob.Send(view.RemovePacket); + + mob.LocalOverheadMessage(MessageType.Emote, 0x3B2, false, + "* Your mind focuses intently on the fight and all other distractions fade away *"); + } + } + } + else + { + dc.Unregister(); + dc.StopCountdown(); + } + } + } + + public class TournyParticipant : IComparable + { + public TournyParticipant(Mobile owner) + { + Log = new ArrayList(); + Players = new ArrayList(); + Players.Add(owner); + } + + public TournyParticipant(ArrayList players) + { + Log = new ArrayList(); + Players = players; + } + + public ArrayList Players{ get; set; } + + public ArrayList Log{ get; set; } + + public int FreeAdvances{ get; set; } + + public int TotalLadderXP + { + get + { + Ladder ladder = Ladder.Instance; + + if (ladder == null) + return 0; + + int total = 0; + + for (int i = 0; i < Players.Count; ++i) + { + Mobile mob = (Mobile)Players[i]; + LadderEntry entry = ladder.Find(mob); + + if (entry != null) + total += entry.Experience; + } + + return total; + } + } + + public string NameList + { + get + { + StringBuilder sb = new StringBuilder(); + + for (int i = 0; i < Players.Count; ++i) + { + if (Players[i] == null) + continue; + + Mobile mob = (Mobile)Players[i]; + + if (sb.Length > 0) + { + if (Players.Count == 2) + sb.Append(" and "); + else if (i + 1 < Players.Count) + sb.Append(", "); + else + sb.Append(", and "); + } + + sb.Append(mob.Name); + } + + if (sb.Length == 0) + return "Empty"; + + return sb.ToString(); + } + } + + public int CompareTo(object obj) + { + TournyParticipant p = (TournyParticipant)obj; + + return p.TotalLadderXP - TotalLadderXP; + } + + public void AddLog(string text) + { + Log.Add(text); + } + + public void AddLog(string format, params object[] args) + { + AddLog(string.Format(format, args)); + } + + public void WonMatch(TournyMatch match) + { + AddLog("Match won."); + } + + public void LostMatch(TournyMatch match) + { + AddLog("Match lost."); + } + } + + public enum TournyBracketGumpType + { + Index, + Rules_Info, + Participant_List, + Participant_Info, + Round_List, + Round_Info, + Match_Info, + Player_Info + } + + public class TournamentBracketGump : Gump + { + private const int BlackColor32 = 0x000008; + private const int LabelColor32 = 0xFFFFFF; + private Mobile m_From; + private ArrayList m_List; + private object m_Object; + private int m_Page; + private int m_PerPage; + private Tournament m_Tournament; + private TournyBracketGumpType m_Type; + + public TournamentBracketGump(Mobile from, Tournament tourny, TournyBracketGumpType type, ArrayList list, int page, + object obj) : base(50, 50) + { + m_From = from; + m_Tournament = tourny; + m_Type = type; + m_List = list; + m_Page = page; + m_Object = obj; + m_PerPage = 12; + + switch (type) + { + case TournyBracketGumpType.Index: + { + AddPage(0); + AddBackground(0, 0, 300, 300, 9380); + + StringBuilder sb = new StringBuilder(); + + if (tourny.TournyType == TournyType.FreeForAll) + { + sb.Append("FFA"); + } + else if (tourny.TournyType == TournyType.RandomTeam) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-Team"); + } + else if (tourny.TournyType == TournyType.RedVsBlue) + { + sb.Append("Red v Blue"); + } + else if (tourny.TournyType == TournyType.Faction) + { + sb.Append(tourny.ParticipantsPerMatch); + sb.Append("-Team Faction"); + } + else + { + for (int i = 0; i < tourny.ParticipantsPerMatch; ++i) + { + if (sb.Length > 0) + sb.Append('v'); + + sb.Append(tourny.PlayersPerParticipant); + } + } + + if (tourny.EventController != null) + sb.Append(' ').Append(tourny.EventController.Title); + + sb.Append(" Tournament Bracket"); + + AddHtml(25, 35, 250, 20, Center(sb.ToString()), false, false); + + AddRightArrow(25, 53, ToButtonID(0, 4), "Rules"); + AddRightArrow(25, 71, ToButtonID(0, 1), "Participants"); + + if (m_Tournament.Stage == TournamentStage.Signup) + { + TimeSpan until = m_Tournament.SignupStart + m_Tournament.SignupPeriod - DateTime.UtcNow; + string text; + int secs = (int)until.TotalSeconds; + + if (secs > 0) + { + int mins = secs / 60; + secs %= 60; + + if (mins > 0 && secs > 0) + text = + $"The tournament will begin in {mins} minute{(mins == 1 ? "" : "s")} and {secs} second{(secs == 1 ? "" : "s")}."; + else if (mins > 0) + text = $"The tournament will begin in {mins} minute{(mins == 1 ? "" : "s")}."; + else if (secs > 0) + text = $"The tournament will begin in {secs} second{(secs == 1 ? "" : "s")}."; + else + text = "The tournament will begin shortly."; + } + else + { + text = "The tournament will begin shortly."; + } + + AddHtml(25, 92, 250, 40, text, false, false); + } + else + { + AddRightArrow(25, 89, ToButtonID(0, 2), "Rounds"); + } + + break; + } + case TournyBracketGumpType.Rules_Info: + { + Ruleset ruleset = tourny.Ruleset; + Ruleset basedef = ruleset.Base; + + BitArray defs; + + if (ruleset.Flavors.Count > 0) + { + defs = new BitArray(basedef.Options); + + for (int i = 0; i < ruleset.Flavors.Count; ++i) + defs.Or(((Ruleset)ruleset.Flavors[i]).Options); + } + else + { + defs = basedef.Options; + } + + int changes = 0; + + BitArray opts = ruleset.Options; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + ++changes; + + AddPage(0); + AddBackground(0, 0, 300, + 60 + 18 + 20 + 20 + 20 + 8 + 20 + ruleset.Flavors.Count * 18 + 4 + 20 + changes * 22 + 6, 9380); + + AddLeftArrow(25, 11, ToButtonID(0, 0)); + AddHtml(25, 35, 250, 20, Center("Rules"), false, false); + + int y = 53; + + string groupText = null; + + switch (tourny.GroupType) + { + case GroupingType.HighVsLow: + groupText = "High vs Low"; + break; + case GroupingType.Nearest: + groupText = "Closest opponent"; + break; + case GroupingType.Random: + groupText = "Random"; + break; + } + + AddHtml(35, y, 190, 20, $"Grouping: {groupText}", false, false); + y += 20; + + string tieText = null; + + switch (tourny.TieType) + { + case TieType.Random: + tieText = "Random"; + break; + case TieType.Highest: + tieText = "Highest advances"; + break; + case TieType.Lowest: + tieText = "Lowest advances"; + break; + case TieType.FullAdvancement: + tieText = tourny.ParticipantsPerMatch == 2 ? "Both advance" : "Everyone advances"; + break; + case TieType.FullElimination: + tieText = tourny.ParticipantsPerMatch == 2 ? "Both eliminated" : "Everyone eliminated"; + break; + } + + AddHtml(35, y, 190, 20, $"Tiebreaker: {tieText}", false, false); + y += 20; + + string sdText = "Off"; + + if (tourny.SuddenDeath > TimeSpan.Zero) + { + sdText = $"{(int)tourny.SuddenDeath.TotalMinutes}:{tourny.SuddenDeath.Seconds:D2}"; + + if (tourny.SuddenDeathRounds > 0) + sdText = $"{sdText} (first {tourny.SuddenDeathRounds} rounds)"; + else + sdText = $"{sdText} (all rounds)"; + } + + AddHtml(35, y, 240, 20, $"Sudden Death: {sdText}", false, false); + y += 20; + + y += 8; + + AddHtml(35, y, 190, 20, $"Ruleset: {basedef.Title}", false, false); + y += 20; + + for (int i = 0; i < ruleset.Flavors.Count; ++i, y += 18) + AddHtml(35, y, 190, 20, $" + {((Ruleset)ruleset.Flavors[i]).Title}", false, false); + + y += 4; + + if (changes > 0) + { + AddHtml(35, y, 190, 20, "Modifications:", false, false); + y += 20; + + for (int i = 0; i < opts.Length; ++i) + if (defs[i] != opts[i]) + { + string name = ruleset.Layout.FindByIndex(i); + + if (name != null) // sanity + { + AddImage(35, y, opts[i] ? 0xD3 : 0xD2); + AddHtml(60, y, 165, 22, name, false, false); + } + + y += 22; + } + } + else + { + AddHtml(35, y, 190, 20, "Modifications: None", false, false); + y += 20; + } + + break; + } + case TournyBracketGumpType.Participant_List: + { + AddPage(0); + AddBackground(0, 0, 300, 300, 9380); + + if (m_List == null) + m_List = new ArrayList(tourny.Participants); + + AddLeftArrow(25, 11, ToButtonID(0, 0)); + AddHtml(25, 35, 250, 20, Center($"{m_List.Count} Participant{(m_List.Count == 1 ? "" : "s")}"), false, + false); + + int index, count, y; + StartPage(out index, out count, out y, 12); + + for (int i = 0; i < count; ++i, y += 18) + { + TournyParticipant part = (TournyParticipant)m_List[index + i]; + string name = part.NameList; + + if (m_Tournament.TournyType != TournyType.Standard && part.Players.Count == 1) + if (part.Players[0] is PlayerMobile pm && pm.DuelPlayer != null) + name = Color(name, pm.DuelPlayer.Eliminated ? 0x6633333 : 0x336666); + + AddRightArrow(25, y, ToButtonID(2, index + i), name); + } + + break; + } + case TournyBracketGumpType.Participant_Info: + { + if (!(obj is TournyParticipant part)) + break; + + AddPage(0); + AddBackground(0, 0, 300, 60 + 18 + 20 + part.Players.Count * 18 + 20 + 20 + 160, 9380); + + AddLeftArrow(25, 11, ToButtonID(0, 1)); + AddHtml(25, 35, 250, 20, Center("Participants"), false, false); + + int y = 53; + + AddHtml(25, y, 200, 20, part.Players.Count == 1 ? "Players" : "Team", false, false); + y += 20; + + for (int i = 0; i < part.Players.Count; ++i) + { + Mobile mob = (Mobile)part.Players[i]; + string name = mob.Name; + + if (m_Tournament.TournyType != TournyType.Standard) + if (mob is PlayerMobile pm && pm.DuelPlayer != null) + name = Color(name, pm.DuelPlayer.Eliminated ? 0x6633333 : 0x336666); + + AddRightArrow(35, y, ToButtonID(4, i), name); + y += 18; + } + + AddHtml(25, y, 200, 20, + $"Free Advances: {(part.FreeAdvances == 0 ? "None" : part.FreeAdvances.ToString())}", false, false); + y += 20; + + AddHtml(25, y, 200, 20, "Log:", false, false); + y += 20; + + StringBuilder sb = new StringBuilder(); + + for (int i = 0; i < part.Log.Count; ++i) + { + if (sb.Length > 0) + sb.Append("
"); + + sb.Append(part.Log[i]); + } + + if (sb.Length == 0) + sb.Append("Nothing logged yet."); + + AddHtml(25, y, 250, 150, Color(sb.ToString(), BlackColor32), false, true); + + break; + } + case TournyBracketGumpType.Player_Info: + { + AddPage(0); + AddBackground(0, 0, 300, 300, 9380); + + AddLeftArrow(25, 11, ToButtonID(0, 3)); + AddHtml(25, 35, 250, 20, Center("Participants"), false, false); + + if (!(obj is Mobile mob)) + break; + + Ladder ladder = Ladder.Instance; + LadderEntry entry = ladder?.Find(mob); + + AddHtml(25, 53, 250, 20, $"Name: {mob.Name}", false, false); + AddHtml(25, 73, 250, 20, + $"Guild: {(mob.Guild == null ? "None" : mob.Guild.Name + " [" + mob.Guild.Abbreviation + "]")}", + false, false); + AddHtml(25, 93, 250, 20, $"Rank: {(entry == null ? "N/A" : LadderGump.Rank(entry.Index + 1))}", false, + false); + AddHtml(25, 113, 250, 20, $"Level: {(entry == null ? 0 : Ladder.GetLevel(entry.Experience))}", false, + false); + AddHtml(25, 133, 250, 20, $"Wins: {entry?.Wins ?? 0:N0}", false, false); + AddHtml(25, 153, 250, 20, $"Losses: {entry?.Losses ?? 0:N0}", false, false); + + break; + } + case TournyBracketGumpType.Round_List: + { + AddPage(0); + AddBackground(0, 0, 300, 300, 9380); + + AddLeftArrow(25, 11, ToButtonID(0, 0)); + AddHtml(25, 35, 250, 20, Center("Rounds"), false, false); + + if (m_List == null) + m_List = new ArrayList(tourny.Pyramid.Levels); + + int index, count, y; + StartPage(out index, out count, out y, 12); + + for (int i = 0; i < count; ++i, y += 18) + // PyramidLevel level = (PyramidLevel)m_List[index + i]; + + AddRightArrow(25, y, ToButtonID(3, index + i), "Round #" + (index + i + 1)); + + break; + } + case TournyBracketGumpType.Round_Info: + { + AddPage(0); + AddBackground(0, 0, 300, 300, 9380); + + AddLeftArrow(25, 11, ToButtonID(0, 2)); + AddHtml(25, 35, 250, 20, Center("Rounds"), false, false); + + if (!(m_Object is PyramidLevel level)) + break; + + if (m_List == null) + m_List = new ArrayList(level.Matches); + + AddRightArrow(25, 53, ToButtonID(5, 0), + $"Free Advance: {(level.FreeAdvance == null ? "None" : level.FreeAdvance.NameList)}"); + + AddHtml(25, 73, 200, 20, $"{m_List.Count} Match{(m_List.Count == 1 ? "" : "es")}", false, false); + + int index, count, y; + StartPage(out index, out count, out y, 10); + + for (int i = 0; i < count; ++i, y += 18) + { + TournyMatch match = (TournyMatch)m_List[index + i]; + + int color = -1; + + if (match.InProgress) + color = 0x336666; + else if (match.Context != null && match.Winner == null) + color = 0x666666; + + StringBuilder sb = new StringBuilder(); + + if (m_Tournament.TournyType == TournyType.Standard) + for (int j = 0; j < match.Participants.Count; ++j) + { + if (sb.Length > 0) + sb.Append(" vs "); + + TournyParticipant part = (TournyParticipant)match.Participants[j]; + string txt = part.NameList; + + if (color == -1 && match.Context != null && match.Winner == part) + txt = Color(txt, 0x336633); + else if (color == -1 && match.Context != null) + txt = Color(txt, 0x663333); + + sb.Append(txt); + } + else if (m_Tournament.EventController != null || m_Tournament.TournyType == TournyType.RandomTeam || + m_Tournament.TournyType == TournyType.RedVsBlue || + m_Tournament.TournyType == TournyType.Faction) + for (int j = 0; j < match.Participants.Count; ++j) + { + if (sb.Length > 0) + sb.Append(" vs "); + + TournyParticipant part = (TournyParticipant)match.Participants[j]; + string txt; + + if (m_Tournament.EventController != null) + { + txt = $"Team {m_Tournament.EventController.GetTeamName(j)} ({part.Players.Count})"; + } + else if (m_Tournament.TournyType == TournyType.RandomTeam) + { + txt = $"Team {j + 1} ({part.Players.Count})"; + } + else if (m_Tournament.TournyType == TournyType.Faction) + { + if (m_Tournament.ParticipantsPerMatch == 4) + { + string name = "(null)"; + + switch (j) + { + case 0: + { + name = "Minax"; + break; + } + case 1: + { + name = "Council of Mages"; + break; + } + case 2: + { + name = "True Britannians"; + break; + } + case 3: + { + name = "Shadowlords"; + break; + } + } + + txt = $"{name} ({part.Players.Count})"; + } + else if (m_Tournament.ParticipantsPerMatch == 2) + { + txt = $"{(j == 0 ? "Evil" : "Hero")} Team ({part.Players.Count})"; + } + else + { + txt = $"Team {j + 1} ({part.Players.Count})"; + } + } + else + { + txt = $"Team {(j == 0 ? "Red" : "Blue")} ({part.Players.Count})"; + } + + if (color == -1 && match.Context != null && match.Winner == part) + txt = Color(txt, 0x336633); + else if (color == -1 && match.Context != null) + txt = Color(txt, 0x663333); + + sb.Append(txt); + } + else if (m_Tournament.TournyType == TournyType.FreeForAll) sb.Append("Free For All"); + + string str = sb.ToString(); + + if (color >= 0) + str = Color(str, color); + + AddRightArrow(25, y, ToButtonID(5, index + i + 1), str); + } + + break; + } + case TournyBracketGumpType.Match_Info: + { + if (!(obj is TournyMatch match)) + break; + + int ct = m_Tournament.TournyType == TournyType.FreeForAll ? 2 : match.Participants.Count; + + AddPage(0); + AddBackground(0, 0, 300, 60 + 18 + 20 + 20 + 20 + ct * 18 + 6, 9380); + + AddLeftArrow(25, 11, ToButtonID(0, 5)); + AddHtml(25, 35, 250, 20, Center("Rounds"), false, false); + + AddHtml(25, 53, 250, 20, $"Winner: {(match.Winner == null ? "N/A" : match.Winner.NameList)}", false, + false); + AddHtml(25, 73, 250, 20, + $"State: {(match.InProgress ? "In progress" : match.Context != null ? "Complete" : "Waiting")}", + false, false); + AddHtml(25, 93, 250, 20, "Participants:", false, false); + + if (m_Tournament.TournyType == TournyType.Standard) + for (int i = 0; i < match.Participants.Count; ++i) + { + TournyParticipant part = (TournyParticipant)match.Participants[i]; + + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), part.NameList); + } + else if (m_Tournament.EventController != null || m_Tournament.TournyType == TournyType.RandomTeam || + m_Tournament.TournyType == TournyType.RedVsBlue || + m_Tournament.TournyType == TournyType.Faction) + for (int i = 0; i < match.Participants.Count; ++i) + { + TournyParticipant part = (TournyParticipant)match.Participants[i]; + + if (m_Tournament.EventController != null) + { + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), + $"Team {m_Tournament.EventController.GetTeamName(i)} ({part.Players.Count})"); + } + else if (m_Tournament.TournyType == TournyType.RandomTeam) + { + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), + $"Team {i + 1} ({part.Players.Count})"); + } + else if (m_Tournament.TournyType == TournyType.Faction) + { + if (m_Tournament.ParticipantsPerMatch == 4) + { + string name = "(null)"; + + switch (i) + { + case 0: + { + name = "Minax"; + break; + } + case 1: + { + name = "Council of Mages"; + break; + } + case 2: + { + name = "True Britannians"; + break; + } + case 3: + { + name = "Shadowlords"; + break; + } + } + + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), + $"{name} ({part.Players.Count})"); + } + else if (m_Tournament.ParticipantsPerMatch == 2) + { + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), + $"{(i == 0 ? "Evil" : "Hero")} Team ({part.Players.Count})"); + } + else + { + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), + $"Team {i + 1} ({part.Players.Count})"); + } + } + else + { + AddRightArrow(25, 113 + i * 18, ToButtonID(6, i), + $"Team {(i == 0 ? "Red" : "Blue")} ({part.Players.Count})"); + } + } + else if (m_Tournament.TournyType == TournyType.FreeForAll) + AddHtml(25, 113, 250, 20, "Free For All", false, false); + + break; + } + } + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + private void AddBorderedText(int x, int y, int width, int height, string text, int color, int borderColor) + { + AddColoredText(x - 1, y - 1, width, height, text, borderColor); + AddColoredText(x - 1, y + 1, width, height, text, borderColor); + AddColoredText(x + 1, y - 1, width, height, text, borderColor); + AddColoredText(x + 1, y + 1, width, height, text, borderColor); + AddColoredText(x, y, width, height, text, color); + } + + private void AddColoredText(int x, int y, int width, int height, string text, int color) + { + if (color == 0) + AddHtml(x, y, width, height, text, false, false); + else + AddHtml(x, y, width, height, Color(text, color), false, false); + } + + public void AddRightArrow(int x, int y, int bid, string text) + { + AddButton(x, y, 0x15E1, 0x15E5, bid, GumpButtonType.Reply, 0); + + if (text != null) + AddHtml(x + 20, y - 1, 230, 20, text, false, false); + } + + public void AddRightArrow(int x, int y, int bid) + { + AddRightArrow(x, y, bid, null); + } + + public void AddLeftArrow(int x, int y, int bid, string text) + { + AddButton(x, y, 0x15E3, 0x15E7, bid, GumpButtonType.Reply, 0); + + if (text != null) + AddHtml(x + 20, y - 1, 230, 20, text, false, false); + } + + public void AddLeftArrow(int x, int y, int bid) + { + AddLeftArrow(x, y, bid, null); + } + + public int ToButtonID(int type, int index) + { + return 1 + index * 7 + type; + } + + public bool FromButtonID(int bid, out int type, out int index) + { + type = (bid - 1) % 7; + index = (bid - 1) / 7; + return bid >= 1; + } + + public void StartPage(out int index, out int count, out int y, int perPage) + { + m_PerPage = perPage; + + index = Math.Max(m_Page * perPage, 0); + count = Math.Max(Math.Min(m_List.Count - index, perPage), 0); + + y = 53 + (12 - perPage) * 18; + + if (m_Page > 0) + AddLeftArrow(242, 35, ToButtonID(1, 0)); + + if ((m_Page + 1) * perPage < m_List.Count) + AddRightArrow(260, 35, ToButtonID(1, 1)); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int type, index; + + if (!FromButtonID(info.ButtonID, out type, out index)) + return; + + switch (type) + { + case 0: + { + switch (index) + { + case 0: + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, TournyBracketGumpType.Index, + null, 0, null)); + break; + case 1: + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, + TournyBracketGumpType.Participant_List, null, 0, null)); + break; + case 2: + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, TournyBracketGumpType.Round_List, + null, 0, null)); + break; + case 4: + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, TournyBracketGumpType.Rules_Info, + null, 0, null)); + break; + case 3: + { + Mobile mob = m_Object as Mobile; + + for (int i = 0; i < m_Tournament.Participants.Count; ++i) + { + TournyParticipant part = (TournyParticipant)m_Tournament.Participants[i]; + + if (part.Players.Contains(mob)) + { + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, + TournyBracketGumpType.Participant_Info, null, 0, part)); + break; + } + } + + break; + } + case 5: + { + if (!(m_Object is TournyMatch match)) + break; + + for (int i = 0; i < m_Tournament.Pyramid.Levels.Count; ++i) + { + PyramidLevel level = (PyramidLevel)m_Tournament.Pyramid.Levels[i]; + + if (level.Matches.Contains(match)) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, + TournyBracketGumpType.Round_Info, null, 0, level)); + } + + break; + } + } + + break; + } + case 1: + { + switch (index) + { + case 0: + { + if (m_List != null && m_Page > 0) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, m_Type, m_List, m_Page - 1, + m_Object)); + + break; + } + case 1: + { + if (m_List != null && (m_Page + 1) * m_PerPage < m_List.Count) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, m_Type, m_List, m_Page + 1, + m_Object)); + + break; + } + } + + break; + } + case 2: + { + if (m_Type != TournyBracketGumpType.Participant_List) + break; + + if (index >= 0 && index < m_List.Count) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, + TournyBracketGumpType.Participant_Info, null, 0, m_List[index])); + + break; + } + case 3: + { + if (m_Type != TournyBracketGumpType.Round_List) + break; + + if (index >= 0 && index < m_List.Count) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, TournyBracketGumpType.Round_Info, + null, 0, m_List[index])); + + break; + } + case 4: + { + if (m_Type != TournyBracketGumpType.Participant_Info) + break; + + if (m_Object is TournyParticipant part && index >= 0 && index < part.Players.Count) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, TournyBracketGumpType.Player_Info, + null, 0, part.Players[index])); + + break; + } + case 5: + { + if (m_Type != TournyBracketGumpType.Round_Info) + break; + + if (!(m_Object is PyramidLevel level)) + break; + + if (index == 0) + { + if (level.FreeAdvance != null) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, + TournyBracketGumpType.Participant_Info, null, 0, level.FreeAdvance)); + else + m_From.SendGump( + new TournamentBracketGump(m_From, m_Tournament, m_Type, m_List, m_Page, m_Object)); + } + else if (index >= 1 && index <= level.Matches.Count) + { + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, TournyBracketGumpType.Match_Info, + null, 0, level.Matches[index - 1])); + } + + break; + } + case 6: + { + if (m_Type != TournyBracketGumpType.Match_Info) + break; + + if (m_Object is TournyMatch match && index >= 0 && index < match.Participants.Count) + m_From.SendGump(new TournamentBracketGump(m_From, m_Tournament, + TournyBracketGumpType.Participant_Info, null, 0, match.Participants[index])); + + break; + } + } + } + } + + public class TournamentBracketItem : Item + { + [Constructible] + public TournamentBracketItem() : base(3774) + { + Movable = false; + } + + public TournamentBracketItem(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public TournamentController Tournament{ get; set; } + + public override string DefaultName => "tournament bracket"; + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that + } + else + { + Tournament tourny = Tournament?.Tournament; + + if (tourny != null) + { + from.CloseGump(typeof(TournamentBracketGump)); + from.SendGump(new TournamentBracketGump(from, tourny, TournyBracketGumpType.Index, null, 0, null)); + + /*if ( tourny.Stage == TournamentStage.Fighting && tourny.Pyramid.Levels.Count > 0 ) + from.SendGump( new TournamentBracketGump( tourny, (PyramidLevel)tourny.Pyramid.Levels[tourny.Pyramid.Levels.Count - 1] ) ); + else + from.SendGump( new TournamentBracketGump( tourny, 0 ) );*/ + } + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.Write(Tournament); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Tournament = reader.ReadItem() as TournamentController; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/ConPVP/Trophy.cs b/Scripts/Engines/ConPVP/Trophy.cs index c65d5d858..3a97c3155 100644 --- a/Scripts/Engines/ConPVP/Trophy.cs +++ b/Scripts/Engines/ConPVP/Trophy.cs @@ -2,105 +2,118 @@ using System; namespace Server.Items { - public enum TrophyRank - { - Bronze, - Silver, - Gold - } + public enum TrophyRank + { + Bronze, + Silver, + Gold + } - [Flippable( 5020, 4647 )] - public class Trophy : Item - { - private TrophyRank m_Rank; + [Flippable(5020, 4647)] + public class Trophy : Item + { + private TrophyRank m_Rank; - [CommandProperty( AccessLevel.GameMaster )] - public string Title { get; set; } + [Constructible] + public Trophy(string title, TrophyRank rank) : base(5020) + { + Title = title; + m_Rank = rank; + Date = DateTime.UtcNow; - [CommandProperty( AccessLevel.GameMaster )] - public TrophyRank Rank{ get => m_Rank; - set{ m_Rank = value; UpdateStyle(); } } + LootType = LootType.Blessed; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } + UpdateStyle(); + } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime Date { get; private set; } + public Trophy(Serial serial) : base(serial) + { + } - [Constructible] - public Trophy( string title, TrophyRank rank ) : base( 5020 ) - { - Title = title; - m_Rank = rank; - Date = DateTime.UtcNow; + [CommandProperty(AccessLevel.GameMaster)] + public string Title{ get; set; } - LootType = LootType.Blessed; + [CommandProperty(AccessLevel.GameMaster)] + public TrophyRank Rank + { + get => m_Rank; + set + { + m_Rank = value; + UpdateStyle(); + } + } - UpdateStyle(); - } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } - public Trophy( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public DateTime Date{ get; private set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (string) Title ); - writer.Write( (int) m_Rank ); - writer.Write( (Mobile) Owner ); - writer.Write( (DateTime) Date ); - } + writer.Write(Title); + writer.Write((int)m_Rank); + writer.Write(Owner); + writer.Write(Date); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Title = reader.ReadString(); - m_Rank = (TrophyRank) reader.ReadInt(); - Owner = reader.ReadMobile(); - Date = reader.ReadDateTime(); + Title = reader.ReadString(); + m_Rank = (TrophyRank)reader.ReadInt(); + Owner = reader.ReadMobile(); + Date = reader.ReadDateTime(); - if ( version == 0 ) - LootType = LootType.Blessed; - } + if (version == 0) + LootType = LootType.Blessed; + } - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - if ( Owner == null ) - Owner = RootParent as Mobile; - } + if (Owner == null) + Owner = RootParent as Mobile; + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - if ( Owner != null ) - LabelTo( from, "{0} -- {1}", Title, Owner.RawName ); - else if ( Title != null ) - LabelTo( from, Title ); + if (Owner != null) + LabelTo(from, "{0} -- {1}", Title, Owner.RawName); + else if (Title != null) + LabelTo(from, Title); - if ( Date != DateTime.MinValue ) - LabelTo( from, Date.ToString( "d" ) ); - } + if (Date != DateTime.MinValue) + LabelTo(from, Date.ToString("d")); + } - public void UpdateStyle() - { - Name = $"{m_Rank.ToString().ToLower()} trophy"; + public void UpdateStyle() + { + Name = $"{m_Rank.ToString().ToLower()} trophy"; - switch ( m_Rank ) - { - case TrophyRank.Gold: Hue = 2213; break; - case TrophyRank.Silver: Hue = 0; break; - case TrophyRank.Bronze: Hue = 2206; break; - } - } - } + switch (m_Rank) + { + case TrophyRank.Gold: + Hue = 2213; + break; + case TrophyRank.Silver: + Hue = 0; + break; + case TrophyRank.Bronze: + Hue = 2206; + break; + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftContext.cs b/Scripts/Engines/Craft/Core/CraftContext.cs index 60c8c5c1b..38bc10757 100644 --- a/Scripts/Engines/Craft/Core/CraftContext.cs +++ b/Scripts/Engines/Craft/Core/CraftContext.cs @@ -2,54 +2,54 @@ using System.Collections.Generic; namespace Server.Engines.Craft { - public enum CraftMarkOption - { - MarkItem, - DoNotMark, - PromptForMark - } + public enum CraftMarkOption + { + MarkItem, + DoNotMark, + PromptForMark + } - public class CraftContext - { - public List Items { get; } + public class CraftContext + { + public CraftContext() + { + Items = new List(); + LastResourceIndex = -1; + LastResourceIndex2 = -1; + LastGroupIndex = -1; + } - public int LastResourceIndex { get; set; } + public List Items{ get; } - public int LastResourceIndex2 { get; set; } + public int LastResourceIndex{ get; set; } - public int LastGroupIndex { get; set; } + public int LastResourceIndex2{ get; set; } - public bool DoNotColor { get; set; } + public int LastGroupIndex{ get; set; } - public CraftMarkOption MarkOption { get; set; } + public bool DoNotColor{ get; set; } - public CraftContext() - { - Items = new List(); - LastResourceIndex = -1; - LastResourceIndex2 = -1; - LastGroupIndex = -1; - } + public CraftMarkOption MarkOption{ get; set; } - public CraftItem LastMade - { - get - { - if ( Items.Count > 0 ) - return Items[0]; + public CraftItem LastMade + { + get + { + if (Items.Count > 0) + return Items[0]; - return null; - } - } + return null; + } + } - public void OnMade( CraftItem item ) - { - Items.Remove( item ); + public void OnMade(CraftItem item) + { + Items.Remove(item); - if ( Items.Count == 10 ) - Items.RemoveAt( 9 ); + if (Items.Count == 10) + Items.RemoveAt(9); - Items.Insert( 0, item ); - } - } -} + Items.Insert(0, item); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftGroup.cs b/Scripts/Engines/Craft/Core/CraftGroup.cs index 72755ff5b..c3fe8d237 100644 --- a/Scripts/Engines/Craft/Core/CraftGroup.cs +++ b/Scripts/Engines/Craft/Core/CraftGroup.cs @@ -1,23 +1,23 @@ namespace Server.Engines.Craft { - public class CraftGroup - { - public CraftGroup( TextDefinition groupName ) - { - NameNumber = groupName; - NameString = groupName; - CraftItems = new CraftItemCol(); - } + public class CraftGroup + { + public CraftGroup(TextDefinition groupName) + { + NameNumber = groupName; + NameString = groupName; + CraftItems = new CraftItemCol(); + } - public void AddCraftItem( CraftItem craftItem ) - { - CraftItems.Add( craftItem ); - } + public CraftItemCol CraftItems{ get; } - public CraftItemCol CraftItems { get; } + public string NameString{ get; } - public string NameString { get; } + public int NameNumber{ get; } - public int NameNumber { get; } - } + public void AddCraftItem(CraftItem craftItem) + { + CraftItems.Add(craftItem); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftGroupCol.cs b/Scripts/Engines/Craft/Core/CraftGroupCol.cs index 4ea5dc174..f6d698c97 100644 --- a/Scripts/Engines/Craft/Core/CraftGroupCol.cs +++ b/Scripts/Engines/Craft/Core/CraftGroupCol.cs @@ -1,46 +1,45 @@ +using System.Collections; + namespace Server.Engines.Craft { - public class CraftGroupCol : System.Collections.CollectionBase - { - public CraftGroupCol() - { - } + public class CraftGroupCol : CollectionBase + { + public int Add(CraftGroup craftGroup) + { + return List.Add(craftGroup); + } - public int Add( CraftGroup craftGroup ) - { - return List.Add( craftGroup ); - } + public void Remove(int index) + { + if (index > Count - 1 || index < 0) + { + } + else + { + List.RemoveAt(index); + } + } - public void Remove( int index ) - { - if ( index > Count - 1 || index < 0 ) - { - } - else - { - List.RemoveAt( index ); - } - } + public CraftGroup GetAt(int index) + { + return (CraftGroup)List[index]; + } - public CraftGroup GetAt( int index ) - { - return ( CraftGroup ) List[index]; - } + public int SearchFor(TextDefinition groupName) + { + for (int i = 0; i < List.Count; i++) + { + CraftGroup craftGroup = (CraftGroup)List[i]; - public int SearchFor( TextDefinition groupName ) - { - for ( int i = 0; i < List.Count; i++ ) - { - CraftGroup craftGroup = (CraftGroup)List[i]; + int nameNumber = craftGroup.NameNumber; + string nameString = craftGroup.NameString; - int nameNumber = craftGroup.NameNumber; - string nameString = craftGroup.NameString; + if (nameNumber != 0 && nameNumber == groupName.Number || + nameString != null && nameString == groupName.String) + return i; + } - if ( ( nameNumber != 0 && nameNumber == groupName.Number ) || ( nameString != null && nameString == groupName.String ) ) - return i; - } - - return -1; - } - } + return -1; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftGump.cs b/Scripts/Engines/Craft/Core/CraftGump.cs index 33fcc1425..dda11c379 100644 --- a/Scripts/Engines/Craft/Core/CraftGump.cs +++ b/Scripts/Engines/Craft/Core/CraftGump.cs @@ -1,618 +1,622 @@ using System; using System.Collections.Generic; using Server.Gumps; -using Server.Network; using Server.Items; +using Server.Network; namespace Server.Engines.Craft { - public class CraftGump : Gump - { - private Mobile m_From; - private CraftSystem m_CraftSystem; - private BaseTool m_Tool; - - private CraftPage m_Page; - - private const int LabelHue = 0x480; - private const int LabelColor = 0x7FFF; - private const int FontColor = 0xFFFFFF; - - private enum CraftPage - { - None, - PickResource, - PickResource2 - } - - /*public CraftGump( Mobile from, CraftSystem craftSystem, BaseTool tool ): this( from, craftSystem, -1, -1, tool, null ) - { - }*/ - - public CraftGump( Mobile from, CraftSystem craftSystem, BaseTool tool, object notice ) : this( from, craftSystem, tool, notice, CraftPage.None ) - { - } - - private CraftGump( Mobile from, CraftSystem craftSystem, BaseTool tool, object notice, CraftPage page ) : base( 40, 40 ) - { - m_From = from; - m_CraftSystem = craftSystem; - m_Tool = tool; - m_Page = page; - - CraftContext context = craftSystem.GetContext( from ); - - from.CloseGump( typeof( CraftGump ) ); - from.CloseGump( typeof( CraftGumpItem ) ); - - AddPage( 0 ); - - AddBackground( 0, 0, 530, 437, 5054 ); - AddImageTiled( 10, 10, 510, 22, 2624 ); - AddImageTiled( 10, 292, 150, 45, 2624 ); - AddImageTiled( 165, 292, 355, 45, 2624 ); - AddImageTiled( 10, 342, 510, 85, 2624 ); - AddImageTiled( 10, 37, 200, 250, 2624 ); - AddImageTiled( 215, 37, 305, 250, 2624 ); - AddAlphaRegion( 10, 10, 510, 417 ); - - if ( craftSystem.GumpTitleNumber > 0 ) - AddHtmlLocalized( 10, 12, 510, 20, craftSystem.GumpTitleNumber, LabelColor, false, false ); - else - AddHtml( 10, 12, 510, 20, craftSystem.GumpTitleString, false, false ); - - AddHtmlLocalized( 10, 37, 200, 22, 1044010, LabelColor, false, false ); //
CATEGORIES
- AddHtmlLocalized( 215, 37, 305, 22, 1044011, LabelColor, false, false ); //
SELECTIONS
- AddHtmlLocalized( 10, 302, 150, 25, 1044012, LabelColor, false, false ); //
NOTICES
- - AddButton( 15, 402, 4017, 4019, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 405, 150, 18, 1011441, LabelColor, false, false ); // EXIT - - AddButton( 270, 402, 4005, 4007, GetButtonID( 6, 2 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 305, 405, 150, 18, 1044013, LabelColor, false, false ); // MAKE LAST - - // Mark option - if ( craftSystem.MarkOption ) - { - AddButton( 270, 362, 4005, 4007, GetButtonID( 6, 6 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 305, 365, 150, 18, 1044017 + (context == null ? 0 : (int)context.MarkOption), LabelColor, false, false ); // MARK ITEM - } - // **************************************** - - // Resmelt option - if ( craftSystem.Resmelt ) - { - AddButton( 15, 342, 4005, 4007, GetButtonID( 6, 1 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 345, 150, 18, 1044259, LabelColor, false, false ); // SMELT ITEM - } - // **************************************** - - // Repair option - if ( craftSystem.Repair ) - { - AddButton( 270, 342, 4005, 4007, GetButtonID( 6, 5 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 305, 345, 150, 18, 1044260, LabelColor, false, false ); // REPAIR ITEM - } - // **************************************** - - // Enhance option - if ( craftSystem.CanEnhance ) - { - AddButton( 270, 382, 4005, 4007, GetButtonID( 6, 8 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 305, 385, 150, 18, 1061001, LabelColor, false, false ); // ENHANCE ITEM - } - // **************************************** - - if ( notice is int noticeInt && noticeInt > 0 ) - AddHtmlLocalized( 170, 295, 350, 40, noticeInt, LabelColor, false, false ); - else if ( notice is string ) - AddHtml( 170, 295, 350, 40, $"{notice}", false, false ); - - // If the system has more than one resource - if ( craftSystem.CraftSubRes.Init ) - { - string nameString = craftSystem.CraftSubRes.NameString; - int nameNumber = craftSystem.CraftSubRes.NameNumber; - - int resIndex = context?.LastResourceIndex ?? -1; - - Type resourceType = craftSystem.CraftSubRes.ResType; - - if ( resIndex > -1 ) - { - CraftSubRes subResource = craftSystem.CraftSubRes.GetAt( resIndex ); - - nameString = subResource.NameString; - nameNumber = subResource.NameNumber; - resourceType = subResource.ItemType; - } - - int resourceCount = 0; - - if ( from.Backpack != null ) - { - Item[] items = from.Backpack.FindItemsByType( resourceType, true ); - - for ( int i = 0; i < items.Length; ++i ) - resourceCount += items[i].Amount; - } - - AddButton( 15, 362, 4005, 4007, GetButtonID( 6, 0 ), GumpButtonType.Reply, 0 ); - - if ( nameNumber > 0 ) - AddHtmlLocalized( 50, 365, 250, 18, nameNumber, resourceCount.ToString(), LabelColor, false, false ); - else - AddLabel( 50, 362, LabelHue, $"{nameString} ({resourceCount} Available)"); - } - // **************************************** - - // For dragon scales - if ( craftSystem.CraftSubRes2.Init ) - { - string nameString = craftSystem.CraftSubRes2.NameString; - int nameNumber = craftSystem.CraftSubRes2.NameNumber; - - int resIndex = context?.LastResourceIndex2 ?? -1; - - Type resourceType = craftSystem.CraftSubRes2.ResType; + public class CraftGump : Gump + { + private const int LabelHue = 0x480; + private const int LabelColor = 0x7FFF; + private const int FontColor = 0xFFFFFF; + private CraftSystem m_CraftSystem; + private Mobile m_From; + + private CraftPage m_Page; + private BaseTool m_Tool; + + /*public CraftGump( Mobile from, CraftSystem craftSystem, BaseTool tool ): this( from, craftSystem, -1, -1, tool, null ) + { + }*/ + + public CraftGump(Mobile from, CraftSystem craftSystem, BaseTool tool, object notice) : this(from, craftSystem, tool, + notice, CraftPage.None) + { + } + + private CraftGump(Mobile from, CraftSystem craftSystem, BaseTool tool, object notice, CraftPage page) : base(40, 40) + { + m_From = from; + m_CraftSystem = craftSystem; + m_Tool = tool; + m_Page = page; + + CraftContext context = craftSystem.GetContext(from); + + from.CloseGump(typeof(CraftGump)); + from.CloseGump(typeof(CraftGumpItem)); + + AddPage(0); + + AddBackground(0, 0, 530, 437, 5054); + AddImageTiled(10, 10, 510, 22, 2624); + AddImageTiled(10, 292, 150, 45, 2624); + AddImageTiled(165, 292, 355, 45, 2624); + AddImageTiled(10, 342, 510, 85, 2624); + AddImageTiled(10, 37, 200, 250, 2624); + AddImageTiled(215, 37, 305, 250, 2624); + AddAlphaRegion(10, 10, 510, 417); + + if (craftSystem.GumpTitleNumber > 0) + AddHtmlLocalized(10, 12, 510, 20, craftSystem.GumpTitleNumber, LabelColor, false, false); + else + AddHtml(10, 12, 510, 20, craftSystem.GumpTitleString, false, false); + + AddHtmlLocalized(10, 37, 200, 22, 1044010, LabelColor, false, false); //
CATEGORIES
+ AddHtmlLocalized(215, 37, 305, 22, 1044011, LabelColor, false, false); //
SELECTIONS
+ AddHtmlLocalized(10, 302, 150, 25, 1044012, LabelColor, false, false); //
NOTICES
+ + AddButton(15, 402, 4017, 4019, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 405, 150, 18, 1011441, LabelColor, false, false); // EXIT + + AddButton(270, 402, 4005, 4007, GetButtonID(6, 2), GumpButtonType.Reply, 0); + AddHtmlLocalized(305, 405, 150, 18, 1044013, LabelColor, false, false); // MAKE LAST + + // Mark option + if (craftSystem.MarkOption) + { + AddButton(270, 362, 4005, 4007, GetButtonID(6, 6), GumpButtonType.Reply, 0); + AddHtmlLocalized(305, 365, 150, 18, 1044017 + (context == null ? 0 : (int)context.MarkOption), LabelColor, + false, false); // MARK ITEM + } + // **************************************** + + // Resmelt option + if (craftSystem.Resmelt) + { + AddButton(15, 342, 4005, 4007, GetButtonID(6, 1), GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 345, 150, 18, 1044259, LabelColor, false, false); // SMELT ITEM + } + // **************************************** + + // Repair option + if (craftSystem.Repair) + { + AddButton(270, 342, 4005, 4007, GetButtonID(6, 5), GumpButtonType.Reply, 0); + AddHtmlLocalized(305, 345, 150, 18, 1044260, LabelColor, false, false); // REPAIR ITEM + } + // **************************************** + + // Enhance option + if (craftSystem.CanEnhance) + { + AddButton(270, 382, 4005, 4007, GetButtonID(6, 8), GumpButtonType.Reply, 0); + AddHtmlLocalized(305, 385, 150, 18, 1061001, LabelColor, false, false); // ENHANCE ITEM + } + // **************************************** + + if (notice is int noticeInt && noticeInt > 0) + AddHtmlLocalized(170, 295, 350, 40, noticeInt, LabelColor, false, false); + else if (notice is string) + AddHtml(170, 295, 350, 40, $"{notice}", false, false); + + // If the system has more than one resource + if (craftSystem.CraftSubRes.Init) + { + string nameString = craftSystem.CraftSubRes.NameString; + int nameNumber = craftSystem.CraftSubRes.NameNumber; + + int resIndex = context?.LastResourceIndex ?? -1; + + Type resourceType = craftSystem.CraftSubRes.ResType; + + if (resIndex > -1) + { + CraftSubRes subResource = craftSystem.CraftSubRes.GetAt(resIndex); + + nameString = subResource.NameString; + nameNumber = subResource.NameNumber; + resourceType = subResource.ItemType; + } + + int resourceCount = 0; + + if (from.Backpack != null) + { + Item[] items = from.Backpack.FindItemsByType(resourceType, true); + + for (int i = 0; i < items.Length; ++i) + resourceCount += items[i].Amount; + } + + AddButton(15, 362, 4005, 4007, GetButtonID(6, 0), GumpButtonType.Reply, 0); + + if (nameNumber > 0) + AddHtmlLocalized(50, 365, 250, 18, nameNumber, resourceCount.ToString(), LabelColor, false, false); + else + AddLabel(50, 362, LabelHue, $"{nameString} ({resourceCount} Available)"); + } + // **************************************** + + // For dragon scales + if (craftSystem.CraftSubRes2.Init) + { + string nameString = craftSystem.CraftSubRes2.NameString; + int nameNumber = craftSystem.CraftSubRes2.NameNumber; + + int resIndex = context?.LastResourceIndex2 ?? -1; + + Type resourceType = craftSystem.CraftSubRes2.ResType; + + if (resIndex > -1) + { + CraftSubRes subResource = craftSystem.CraftSubRes2.GetAt(resIndex); + + nameString = subResource.NameString; + nameNumber = subResource.NameNumber; + resourceType = subResource.ItemType; + } + + int resourceCount = 0; + + if (from.Backpack != null) + { + Item[] items = from.Backpack.FindItemsByType(resourceType, true); + + for (int i = 0; i < items.Length; ++i) + resourceCount += items[i].Amount; + } + + AddButton(15, 382, 4005, 4007, GetButtonID(6, 7), GumpButtonType.Reply, 0); + + if (nameNumber > 0) + AddHtmlLocalized(50, 385, 250, 18, nameNumber, resourceCount.ToString(), LabelColor, false, false); + else + AddLabel(50, 385, LabelHue, $"{nameString} ({resourceCount} Available)"); + } + // **************************************** + + CreateGroupList(); + + if (page == CraftPage.PickResource) + CreateResList(false, from); + else if (page == CraftPage.PickResource2) + CreateResList(true, from); + else if (context != null && context.LastGroupIndex > -1) + CreateItemList(context.LastGroupIndex); + } + + public void CreateResList(bool opt, Mobile from) + { + CraftSubResCol res = opt ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes; + + for (int i = 0; i < res.Count; ++i) + { + int index = i % 10; - if ( resIndex > -1 ) - { - CraftSubRes subResource = craftSystem.CraftSubRes2.GetAt( resIndex ); - - nameString = subResource.NameString; - nameNumber = subResource.NameNumber; - resourceType = subResource.ItemType; - } - - int resourceCount = 0; - - if ( from.Backpack != null ) - { - Item[] items = from.Backpack.FindItemsByType( resourceType, true ); - - for ( int i = 0; i < items.Length; ++i ) - resourceCount += items[i].Amount; - } - - AddButton( 15, 382, 4005, 4007, GetButtonID( 6, 7 ), GumpButtonType.Reply, 0 ); - - if ( nameNumber > 0 ) - AddHtmlLocalized( 50, 385, 250, 18, nameNumber, resourceCount.ToString(), LabelColor, false, false ); - else - AddLabel( 50, 385, LabelHue, $"{nameString} ({resourceCount} Available)"); - } - // **************************************** - - CreateGroupList(); - - if ( page == CraftPage.PickResource ) - CreateResList( false, from ); - else if ( page == CraftPage.PickResource2 ) - CreateResList( true, from ); - else if ( context != null && context.LastGroupIndex > -1 ) - CreateItemList( context.LastGroupIndex ); - } + CraftSubRes subResource = res.GetAt(i); - public void CreateResList( bool opt, Mobile from ) - { - CraftSubResCol res = ( opt ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes ); - - for ( int i = 0; i < res.Count; ++i ) - { - int index = i % 10; + if (index == 0) + { + if (i > 0) + AddButton(485, 260, 4005, 4007, 0, GumpButtonType.Page, i / 10 + 1); - CraftSubRes subResource = res.GetAt( i ); + AddPage(i / 10 + 1); - if ( index == 0 ) - { - if ( i > 0 ) - AddButton( 485, 260, 4005, 4007, 0, GumpButtonType.Page, (i / 10) + 1 ); + if (i > 0) + AddButton(455, 260, 4014, 4015, 0, GumpButtonType.Page, i / 10); - AddPage( (i / 10) + 1 ); + CraftContext context = m_CraftSystem.GetContext(m_From); - if ( i > 0 ) - AddButton( 455, 260, 4014, 4015, 0, GumpButtonType.Page, i / 10 ); + AddButton(220, 260, 4005, 4007, GetButtonID(6, 4), GumpButtonType.Reply, 0); + AddHtmlLocalized(255, 263, 200, 18, context == null || !context.DoNotColor ? 1061591 : 1061590, + LabelColor, false, false); + } + + int resourceCount = 0; + + if (from.Backpack != null) + { + Item[] items = from.Backpack.FindItemsByType(subResource.ItemType, true); - CraftContext context = m_CraftSystem.GetContext( m_From ); + for (int j = 0; j < items.Length; ++j) + resourceCount += items[j].Amount; + } + + AddButton(220, 60 + index * 20, 4005, 4007, GetButtonID(5, i), GumpButtonType.Reply, 0); - AddButton( 220, 260, 4005, 4007, GetButtonID( 6, 4 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 255, 263, 200, 18, (context == null || !context.DoNotColor) ? 1061591 : 1061590, LabelColor, false, false ); - } + if (subResource.NameNumber > 0) + AddHtmlLocalized(255, 63 + index * 20, 250, 18, subResource.NameNumber, resourceCount.ToString(), + LabelColor, false, false); + else + AddLabel(255, 60 + index * 20, LabelHue, $"{subResource.NameString} ({resourceCount})"); + } + } + + public void CreateMakeLastList() + { + CraftContext context = m_CraftSystem.GetContext(m_From); - int resourceCount = 0; + if (context == null) + return; - if ( from.Backpack != null ) - { - Item[] items = from.Backpack.FindItemsByType( subResource.ItemType, true ); + List items = context.Items; - for ( int j = 0; j < items.Length; ++j ) - resourceCount += items[j].Amount; - } - - AddButton( 220, 60 + (index * 20), 4005, 4007, GetButtonID( 5, i ), GumpButtonType.Reply, 0 ); - - if ( subResource.NameNumber > 0 ) - AddHtmlLocalized( 255, 63 + (index * 20), 250, 18, subResource.NameNumber, resourceCount.ToString(), LabelColor, false, false ); - else - AddLabel( 255, 60 + ( index * 20 ), LabelHue, $"{subResource.NameString} ({resourceCount})"); - } - } - - public void CreateMakeLastList() - { - CraftContext context = m_CraftSystem.GetContext( m_From ); - - if ( context == null ) - return; + if (items.Count > 0) + for (int i = 0; i < items.Count; ++i) + { + int index = i % 10; - List items = context.Items; + CraftItem craftItem = items[i]; + + if (index == 0) + { + if (i > 0) + { + AddButton(370, 260, 4005, 4007, 0, GumpButtonType.Page, i / 10 + 1); + AddHtmlLocalized(405, 263, 100, 18, 1044045, LabelColor, false, false); // NEXT PAGE + } - if ( items.Count > 0 ) - { - for ( int i = 0; i < items.Count; ++i ) - { - int index = i % 10; - - CraftItem craftItem = items[i]; - - if ( index == 0 ) - { - if ( i > 0 ) - { - AddButton( 370, 260, 4005, 4007, 0, GumpButtonType.Page, (i / 10) + 1 ); - AddHtmlLocalized( 405, 263, 100, 18, 1044045, LabelColor, false, false ); // NEXT PAGE - } - - AddPage( (i / 10) + 1 ); - - if ( i > 0 ) - { - AddButton( 220, 260, 4014, 4015, 0, GumpButtonType.Page, i / 10 ); - AddHtmlLocalized( 255, 263, 100, 18, 1044044, LabelColor, false, false ); // PREV PAGE - } - } - - AddButton( 220, 60 + (index * 20), 4005, 4007, GetButtonID( 3, i ), GumpButtonType.Reply, 0 ); - - if ( craftItem.NameNumber > 0 ) - AddHtmlLocalized( 255, 63 + (index * 20), 220, 18, craftItem.NameNumber, LabelColor, false, false ); - else - AddLabel( 255, 60 + (index * 20), LabelHue, craftItem.NameString ); - - AddButton( 480, 60 + (index * 20), 4011, 4012, GetButtonID( 4, i ), GumpButtonType.Reply, 0 ); - } - } - else - { - // NOTE: This is not as OSI; it is an intentional difference - - AddHtmlLocalized( 230, 62, 200, 22, 1044165, LabelColor, false, false ); // You haven't made anything yet. - } - } - - public void CreateItemList( int selectedGroup ) - { - if ( selectedGroup == 501 ) // 501 : Last 10 - { - CreateMakeLastList(); - return; - } - - CraftGroupCol craftGroupCol = m_CraftSystem.CraftGroups; - CraftGroup craftGroup = craftGroupCol.GetAt( selectedGroup ); - CraftItemCol craftItemCol = craftGroup.CraftItems; - - for ( int i = 0; i < craftItemCol.Count; ++i ) - { - int index = i % 10; - - CraftItem craftItem = craftItemCol.GetAt( i ); - - if ( index == 0 ) - { - if ( i > 0 ) - { - AddButton( 370, 260, 4005, 4007, 0, GumpButtonType.Page, (i / 10) + 1 ); - AddHtmlLocalized( 405, 263, 100, 18, 1044045, LabelColor, false, false ); // NEXT PAGE - } - - AddPage( (i / 10) + 1 ); - - if ( i > 0 ) - { - AddButton( 220, 260, 4014, 4015, 0, GumpButtonType.Page, i / 10 ); - AddHtmlLocalized( 255, 263, 100, 18, 1044044, LabelColor, false, false ); // PREV PAGE - } - } - - AddButton( 220, 60 + (index * 20), 4005, 4007, GetButtonID( 1, i ), GumpButtonType.Reply, 0 ); - - if ( craftItem.NameNumber > 0 ) - AddHtmlLocalized( 255, 63 + (index * 20), 220, 18, craftItem.NameNumber, LabelColor, false, false ); - else - AddLabel( 255, 60 + (index * 20), LabelHue, craftItem.NameString ); - - AddButton( 480, 60 + (index * 20), 4011, 4012, GetButtonID( 2, i ), GumpButtonType.Reply, 0 ); - } - } - - public int CreateGroupList() - { - CraftGroupCol craftGroupCol = m_CraftSystem.CraftGroups; - - AddButton( 15, 60, 4005, 4007, GetButtonID( 6, 3 ), GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 63, 150, 18, 1044014, LabelColor, false, false ); // LAST TEN - - for ( int i = 0; i < craftGroupCol.Count; i++ ) - { - CraftGroup craftGroup = craftGroupCol.GetAt( i ); - - AddButton( 15, 80 + (i * 20), 4005, 4007, GetButtonID( 0, i ), GumpButtonType.Reply, 0 ); - - if ( craftGroup.NameNumber > 0 ) - AddHtmlLocalized( 50, 83 + (i * 20), 150, 18, craftGroup.NameNumber, LabelColor, false, false ); - else - AddLabel( 50, 80 + (i * 20), LabelHue, craftGroup.NameString ); - } - - return craftGroupCol.Count; - } - - public static int GetButtonID( int type, int index ) - { - return 1 + type + (index * 7); - } - - public void CraftItem( CraftItem item ) - { - int num = m_CraftSystem.CanCraft( m_From, m_Tool, item.ItemType ); - - if ( num > 0 ) - { - m_From.SendGump( new CraftGump( m_From, m_CraftSystem, m_Tool, num ) ); - } - else - { - Type type = null; - - CraftContext context = m_CraftSystem.GetContext( m_From ); - - if ( context != null ) - { - CraftSubResCol res = ( item.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes ); - int resIndex = ( item.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex ); - - if ( resIndex >= 0 && resIndex < res.Count ) - type = res.GetAt( resIndex ).ItemType; - } - - m_CraftSystem.CreateItem( m_From, item.ItemType, type, m_Tool, item ); - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID <= 0 ) - return; // Canceled - - int buttonID = info.ButtonID - 1; - int type = buttonID % 7; - int index = buttonID / 7; - - CraftSystem system = m_CraftSystem; - CraftGroupCol groups = system.CraftGroups; - CraftContext context = system.GetContext( m_From ); - - switch ( type ) - { - case 0: // Show group - { - if ( context == null ) - break; - - if ( index >= 0 && index < groups.Count ) - { - context.LastGroupIndex = index; - m_From.SendGump( new CraftGump( m_From, system, m_Tool, null ) ); - } - - break; - } - case 1: // Create item - { - if ( context == null ) - break; - - int groupIndex = context.LastGroupIndex; - - if ( groupIndex >= 0 && groupIndex < groups.Count ) - { - CraftGroup group = groups.GetAt( groupIndex ); - - if ( index >= 0 && index < group.CraftItems.Count ) - CraftItem( group.CraftItems.GetAt( index ) ); - } - - break; - } - case 2: // Item details - { - if ( context == null ) - break; - - int groupIndex = context.LastGroupIndex; - - if ( groupIndex >= 0 && groupIndex < groups.Count ) - { - CraftGroup group = groups.GetAt( groupIndex ); - - if ( index >= 0 && index < group.CraftItems.Count ) - m_From.SendGump( new CraftGumpItem( m_From, system, group.CraftItems.GetAt( index ), m_Tool ) ); - } - - break; - } - case 3: // Create item (last 10) - { - if ( context == null ) - break; - - List lastTen = context.Items; - - if ( index >= 0 && index < lastTen.Count ) - CraftItem( lastTen[index] ); - - break; - } - case 4: // Item details (last 10) - { - if ( context == null ) - break; - - List lastTen = context.Items; - - if ( index >= 0 && index < lastTen.Count ) - m_From.SendGump( new CraftGumpItem( m_From, system, lastTen[index], m_Tool ) ); - - break; - } - case 5: // Resource selected - { - if ( m_Page == CraftPage.PickResource && index >= 0 && index < system.CraftSubRes.Count ) - { - int groupIndex = context?.LastGroupIndex ?? -1; - - CraftSubRes res = system.CraftSubRes.GetAt( index ); - - if ( m_From.Skills[system.MainSkill].Base < res.RequiredSkill ) - { - m_From.SendGump( new CraftGump( m_From, system, m_Tool, res.Message ) ); - } - else - { - if ( context != null ) - context.LastResourceIndex = index; - - m_From.SendGump( new CraftGump( m_From, system, m_Tool, null ) ); - } - } - else if ( m_Page == CraftPage.PickResource2 && index >= 0 && index < system.CraftSubRes2.Count ) - { - int groupIndex = context?.LastGroupIndex ?? -1; - - CraftSubRes res = system.CraftSubRes2.GetAt( index ); - - if ( m_From.Skills[system.MainSkill].Base < res.RequiredSkill ) - { - m_From.SendGump( new CraftGump( m_From, system, m_Tool, res.Message ) ); - } - else - { - if ( context != null ) - context.LastResourceIndex2 = index; - - m_From.SendGump( new CraftGump( m_From, system, m_Tool, null ) ); - } - } - - break; - } - case 6: // Misc. buttons - { - switch ( index ) - { - case 0: // Resource selection - { - if ( system.CraftSubRes.Init ) - m_From.SendGump( new CraftGump( m_From, system, m_Tool, null, CraftPage.PickResource ) ); - - break; - } - case 1: // Smelt item - { - if ( system.Resmelt ) - Resmelt.Do( m_From, system, m_Tool ); - - break; - } - case 2: // Make last - { - if ( context == null ) - break; - - CraftItem item = context.LastMade; - - if ( item != null ) - CraftItem( item ); - else - m_From.SendGump( new CraftGump( m_From, m_CraftSystem, m_Tool, 1044165, m_Page ) ); // You haven't made anything yet. - - break; - } - case 3: // Last 10 - { - if ( context == null ) - break; - - context.LastGroupIndex = 501; - m_From.SendGump( new CraftGump( m_From, system, m_Tool, null ) ); - - break; - } - case 4: // Toggle use resource hue - { - if ( context == null ) - break; - - context.DoNotColor = !context.DoNotColor; - - m_From.SendGump( new CraftGump( m_From, m_CraftSystem, m_Tool, null, m_Page ) ); - - break; - } - case 5: // Repair item - { - if ( system.Repair ) - Repair.Do( m_From, system, m_Tool ); - - break; - } - case 6: // Toggle mark option - { - if ( context == null || !system.MarkOption ) - break; - - switch ( context.MarkOption ) - { - case CraftMarkOption.MarkItem: context.MarkOption = CraftMarkOption.DoNotMark; break; - case CraftMarkOption.DoNotMark: context.MarkOption = CraftMarkOption.PromptForMark; break; - case CraftMarkOption.PromptForMark: context.MarkOption = CraftMarkOption.MarkItem; break; - } - - m_From.SendGump( new CraftGump( m_From, m_CraftSystem, m_Tool, null, m_Page ) ); - - break; - } - case 7: // Resource selection 2 - { - if ( system.CraftSubRes2.Init ) - m_From.SendGump( new CraftGump( m_From, system, m_Tool, null, CraftPage.PickResource2 ) ); - - break; - } - case 8: // Enhance item - { - if ( system.CanEnhance ) - Enhance.BeginTarget( m_From, system, m_Tool ); - - break; - } - } - - break; - } - } - } - } -} + AddPage(i / 10 + 1); + + if (i > 0) + { + AddButton(220, 260, 4014, 4015, 0, GumpButtonType.Page, i / 10); + AddHtmlLocalized(255, 263, 100, 18, 1044044, LabelColor, false, false); // PREV PAGE + } + } + + AddButton(220, 60 + index * 20, 4005, 4007, GetButtonID(3, i), GumpButtonType.Reply, 0); + + if (craftItem.NameNumber > 0) + AddHtmlLocalized(255, 63 + index * 20, 220, 18, craftItem.NameNumber, LabelColor, false, false); + else + AddLabel(255, 60 + index * 20, LabelHue, craftItem.NameString); + + AddButton(480, 60 + index * 20, 4011, 4012, GetButtonID(4, i), GumpButtonType.Reply, 0); + } + else + AddHtmlLocalized(230, 62, 200, 22, 1044165, LabelColor, false, false); // You haven't made anything yet. + } + + public void CreateItemList(int selectedGroup) + { + if (selectedGroup == 501) // 501 : Last 10 + { + CreateMakeLastList(); + return; + } + + CraftGroupCol craftGroupCol = m_CraftSystem.CraftGroups; + CraftGroup craftGroup = craftGroupCol.GetAt(selectedGroup); + CraftItemCol craftItemCol = craftGroup.CraftItems; + + for (int i = 0; i < craftItemCol.Count; ++i) + { + int index = i % 10; + + CraftItem craftItem = craftItemCol.GetAt(i); + + if (index == 0) + { + if (i > 0) + { + AddButton(370, 260, 4005, 4007, 0, GumpButtonType.Page, i / 10 + 1); + AddHtmlLocalized(405, 263, 100, 18, 1044045, LabelColor, false, false); // NEXT PAGE + } + + AddPage(i / 10 + 1); + + if (i > 0) + { + AddButton(220, 260, 4014, 4015, 0, GumpButtonType.Page, i / 10); + AddHtmlLocalized(255, 263, 100, 18, 1044044, LabelColor, false, false); // PREV PAGE + } + } + + AddButton(220, 60 + index * 20, 4005, 4007, GetButtonID(1, i), GumpButtonType.Reply, 0); + + if (craftItem.NameNumber > 0) + AddHtmlLocalized(255, 63 + index * 20, 220, 18, craftItem.NameNumber, LabelColor, false, false); + else + AddLabel(255, 60 + index * 20, LabelHue, craftItem.NameString); + + AddButton(480, 60 + index * 20, 4011, 4012, GetButtonID(2, i), GumpButtonType.Reply, 0); + } + } + + public int CreateGroupList() + { + CraftGroupCol craftGroupCol = m_CraftSystem.CraftGroups; + + AddButton(15, 60, 4005, 4007, GetButtonID(6, 3), GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 63, 150, 18, 1044014, LabelColor, false, false); // LAST TEN + + for (int i = 0; i < craftGroupCol.Count; i++) + { + CraftGroup craftGroup = craftGroupCol.GetAt(i); + + AddButton(15, 80 + i * 20, 4005, 4007, GetButtonID(0, i), GumpButtonType.Reply, 0); + + if (craftGroup.NameNumber > 0) + AddHtmlLocalized(50, 83 + i * 20, 150, 18, craftGroup.NameNumber, LabelColor, false, false); + else + AddLabel(50, 80 + i * 20, LabelHue, craftGroup.NameString); + } + + return craftGroupCol.Count; + } + + public static int GetButtonID(int type, int index) + { + return 1 + type + index * 7; + } + + public void CraftItem(CraftItem item) + { + int num = m_CraftSystem.CanCraft(m_From, m_Tool, item.ItemType); + + if (num > 0) + { + m_From.SendGump(new CraftGump(m_From, m_CraftSystem, m_Tool, num)); + } + else + { + Type type = null; + + CraftContext context = m_CraftSystem.GetContext(m_From); + + if (context != null) + { + CraftSubResCol res = item.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes; + int resIndex = item.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex; + + if (resIndex >= 0 && resIndex < res.Count) + type = res.GetAt(resIndex).ItemType; + } + + m_CraftSystem.CreateItem(m_From, item.ItemType, type, m_Tool, item); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID <= 0) + return; // Canceled + + int buttonID = info.ButtonID - 1; + int type = buttonID % 7; + int index = buttonID / 7; + + CraftSystem system = m_CraftSystem; + CraftGroupCol groups = system.CraftGroups; + CraftContext context = system.GetContext(m_From); + + switch (type) + { + case 0: // Show group + { + if (context == null) + break; + + if (index >= 0 && index < groups.Count) + { + context.LastGroupIndex = index; + m_From.SendGump(new CraftGump(m_From, system, m_Tool, null)); + } + + break; + } + case 1: // Create item + { + if (context == null) + break; + + int groupIndex = context.LastGroupIndex; + + if (groupIndex >= 0 && groupIndex < groups.Count) + { + CraftGroup group = groups.GetAt(groupIndex); + + if (index >= 0 && index < group.CraftItems.Count) + CraftItem(group.CraftItems.GetAt(index)); + } + + break; + } + case 2: // Item details + { + if (context == null) + break; + + int groupIndex = context.LastGroupIndex; + + if (groupIndex >= 0 && groupIndex < groups.Count) + { + CraftGroup group = groups.GetAt(groupIndex); + + if (index >= 0 && index < group.CraftItems.Count) + m_From.SendGump(new CraftGumpItem(m_From, system, group.CraftItems.GetAt(index), m_Tool)); + } + + break; + } + case 3: // Create item (last 10) + { + if (context == null) + break; + + List lastTen = context.Items; + + if (index >= 0 && index < lastTen.Count) + CraftItem(lastTen[index]); + + break; + } + case 4: // Item details (last 10) + { + if (context == null) + break; + + List lastTen = context.Items; + + if (index >= 0 && index < lastTen.Count) + m_From.SendGump(new CraftGumpItem(m_From, system, lastTen[index], m_Tool)); + + break; + } + case 5: // Resource selected + { + if (m_Page == CraftPage.PickResource && index >= 0 && index < system.CraftSubRes.Count) + { + int groupIndex = context?.LastGroupIndex ?? -1; + + CraftSubRes res = system.CraftSubRes.GetAt(index); + + if (m_From.Skills[system.MainSkill].Base < res.RequiredSkill) + { + m_From.SendGump(new CraftGump(m_From, system, m_Tool, res.Message)); + } + else + { + if (context != null) + context.LastResourceIndex = index; + + m_From.SendGump(new CraftGump(m_From, system, m_Tool, null)); + } + } + else if (m_Page == CraftPage.PickResource2 && index >= 0 && index < system.CraftSubRes2.Count) + { + int groupIndex = context?.LastGroupIndex ?? -1; + + CraftSubRes res = system.CraftSubRes2.GetAt(index); + + if (m_From.Skills[system.MainSkill].Base < res.RequiredSkill) + { + m_From.SendGump(new CraftGump(m_From, system, m_Tool, res.Message)); + } + else + { + if (context != null) + context.LastResourceIndex2 = index; + + m_From.SendGump(new CraftGump(m_From, system, m_Tool, null)); + } + } + + break; + } + case 6: // Misc. buttons + { + switch (index) + { + case 0: // Resource selection + { + if (system.CraftSubRes.Init) + m_From.SendGump(new CraftGump(m_From, system, m_Tool, null, CraftPage.PickResource)); + + break; + } + case 1: // Smelt item + { + if (system.Resmelt) + Resmelt.Do(m_From, system, m_Tool); + + break; + } + case 2: // Make last + { + if (context == null) + break; + + CraftItem item = context.LastMade; + + if (item != null) + CraftItem(item); + else + m_From.SendGump(new CraftGump(m_From, m_CraftSystem, m_Tool, 1044165, + m_Page)); // You haven't made anything yet. + + break; + } + case 3: // Last 10 + { + if (context == null) + break; + + context.LastGroupIndex = 501; + m_From.SendGump(new CraftGump(m_From, system, m_Tool, null)); + + break; + } + case 4: // Toggle use resource hue + { + if (context == null) + break; + + context.DoNotColor = !context.DoNotColor; + + m_From.SendGump(new CraftGump(m_From, m_CraftSystem, m_Tool, null, m_Page)); + + break; + } + case 5: // Repair item + { + if (system.Repair) + Repair.Do(m_From, system, m_Tool); + + break; + } + case 6: // Toggle mark option + { + if (context == null || !system.MarkOption) + break; + + switch (context.MarkOption) + { + case CraftMarkOption.MarkItem: + context.MarkOption = CraftMarkOption.DoNotMark; + break; + case CraftMarkOption.DoNotMark: + context.MarkOption = CraftMarkOption.PromptForMark; + break; + case CraftMarkOption.PromptForMark: + context.MarkOption = CraftMarkOption.MarkItem; + break; + } + + m_From.SendGump(new CraftGump(m_From, m_CraftSystem, m_Tool, null, m_Page)); + + break; + } + case 7: // Resource selection 2 + { + if (system.CraftSubRes2.Init) + m_From.SendGump(new CraftGump(m_From, system, m_Tool, null, CraftPage.PickResource2)); + + break; + } + case 8: // Enhance item + { + if (system.CanEnhance) + Enhance.BeginTarget(m_From, system, m_Tool); + + break; + } + } + + break; + } + } + } + + private enum CraftPage + { + None, + PickResource, + PickResource2 + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftGumpItem.cs b/Scripts/Engines/Craft/Core/CraftGumpItem.cs index 0883cf13a..7acc3ebf8 100644 --- a/Scripts/Engines/Craft/Core/CraftGumpItem.cs +++ b/Scripts/Engines/Craft/Core/CraftGumpItem.cs @@ -1,287 +1,295 @@ using System; using Server.Gumps; -using Server.Network; using Server.Items; using Server.Mobiles; +using Server.Network; namespace Server.Engines.Craft { - public class CraftGumpItem : Gump - { - private Mobile m_From; - private CraftSystem m_CraftSystem; - private CraftItem m_CraftItem; - private BaseTool m_Tool; + public class CraftGumpItem : Gump + { + private const int LabelHue = 0x480; // 0x384 + private const int RedLabelHue = 0x20; - private const int LabelHue = 0x480; // 0x384 - private const int RedLabelHue = 0x20; + private const int LabelColor = 0x7FFF; + private const int RedLabelColor = 0x6400; - private const int LabelColor = 0x7FFF; - private const int RedLabelColor = 0x6400; + private const int GreyLabelColor = 0x3DEF; - private const int GreyLabelColor = 0x3DEF; + private static Type typeofBlankScroll = typeof(BlankScroll); + private static Type typeofSpellScroll = typeof(SpellScroll); + private CraftItem m_CraftItem; + private CraftSystem m_CraftSystem; + private Mobile m_From; - private int m_OtherCount; + private int m_OtherCount; - public CraftGumpItem( Mobile from, CraftSystem craftSystem, CraftItem craftItem, BaseTool tool ) : base( 40, 40 ) - { - m_From = from; - m_CraftSystem = craftSystem; - m_CraftItem = craftItem; - m_Tool = tool; + private bool m_ShowExceptionalChance; + private BaseTool m_Tool; - from.CloseGump( typeof( CraftGump ) ); - from.CloseGump( typeof( CraftGumpItem ) ); + public CraftGumpItem(Mobile from, CraftSystem craftSystem, CraftItem craftItem, BaseTool tool) : base(40, 40) + { + m_From = from; + m_CraftSystem = craftSystem; + m_CraftItem = craftItem; + m_Tool = tool; - AddPage( 0 ); - AddBackground( 0, 0, 530, 417, 5054 ); - AddImageTiled( 10, 10, 510, 22, 2624 ); - AddImageTiled( 10, 37, 150, 148, 2624 ); - AddImageTiled( 165, 37, 355, 90, 2624 ); - AddImageTiled( 10, 190, 155, 22, 2624 ); - AddImageTiled( 10, 217, 150, 53, 2624 ); - AddImageTiled( 165, 132, 355, 80, 2624 ); - AddImageTiled( 10, 275, 155, 22, 2624 ); - AddImageTiled( 10, 302, 150, 53, 2624 ); - AddImageTiled( 165, 217, 355, 80, 2624 ); - AddImageTiled( 10, 360, 155, 22, 2624 ); - AddImageTiled( 165, 302, 355, 80, 2624 ); - AddImageTiled( 10, 387, 510, 22, 2624 ); - AddAlphaRegion( 10, 10, 510, 399 ); + from.CloseGump(typeof(CraftGump)); + from.CloseGump(typeof(CraftGumpItem)); - AddHtmlLocalized( 170, 40, 150, 20, 1044053, LabelColor, false, false ); // ITEM - AddHtmlLocalized( 10, 192, 150, 22, 1044054, LabelColor, false, false ); //
SKILLS
- AddHtmlLocalized( 10, 277, 150, 22, 1044055, LabelColor, false, false ); //
MATERIALS
- AddHtmlLocalized( 10, 362, 150, 22, 1044056, LabelColor, false, false ); //
OTHER
+ AddPage(0); + AddBackground(0, 0, 530, 417, 5054); + AddImageTiled(10, 10, 510, 22, 2624); + AddImageTiled(10, 37, 150, 148, 2624); + AddImageTiled(165, 37, 355, 90, 2624); + AddImageTiled(10, 190, 155, 22, 2624); + AddImageTiled(10, 217, 150, 53, 2624); + AddImageTiled(165, 132, 355, 80, 2624); + AddImageTiled(10, 275, 155, 22, 2624); + AddImageTiled(10, 302, 150, 53, 2624); + AddImageTiled(165, 217, 355, 80, 2624); + AddImageTiled(10, 360, 155, 22, 2624); + AddImageTiled(165, 302, 355, 80, 2624); + AddImageTiled(10, 387, 510, 22, 2624); + AddAlphaRegion(10, 10, 510, 399); - if ( craftSystem.GumpTitleNumber > 0 ) - AddHtmlLocalized( 10, 12, 510, 20, craftSystem.GumpTitleNumber, LabelColor, false, false ); - else - AddHtml( 10, 12, 510, 20, craftSystem.GumpTitleString, false, false ); + AddHtmlLocalized(170, 40, 150, 20, 1044053, LabelColor, false, false); // ITEM + AddHtmlLocalized(10, 192, 150, 22, 1044054, LabelColor, false, false); //
SKILLS
+ AddHtmlLocalized(10, 277, 150, 22, 1044055, LabelColor, false, false); //
MATERIALS
+ AddHtmlLocalized(10, 362, 150, 22, 1044056, LabelColor, false, false); //
OTHER
- AddButton( 15, 387, 4014, 4016, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 390, 150, 18, 1044150, LabelColor, false, false ); // BACK + if (craftSystem.GumpTitleNumber > 0) + AddHtmlLocalized(10, 12, 510, 20, craftSystem.GumpTitleNumber, LabelColor, false, false); + else + AddHtml(10, 12, 510, 20, craftSystem.GumpTitleString, false, false); - bool needsRecipe = ( craftItem.Recipe != null && from is PlayerMobile mobile && !mobile.HasRecipe( craftItem.Recipe ) ); + AddButton(15, 387, 4014, 4016, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 390, 150, 18, 1044150, LabelColor, false, false); // BACK - if ( needsRecipe ) - { - AddButton( 270, 387, 4005, 4007, 0, GumpButtonType.Page, 0 ); - AddHtmlLocalized( 305, 390, 150, 18, 1044151, GreyLabelColor, false, false ); // MAKE NOW - } - else - { - AddButton( 270, 387, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 305, 390, 150, 18, 1044151, LabelColor, false, false ); // MAKE NOW - } + bool needsRecipe = craftItem.Recipe != null && from is PlayerMobile mobile && + !mobile.HasRecipe(craftItem.Recipe); - if ( craftItem.NameNumber > 0 ) - AddHtmlLocalized( 330, 40, 180, 18, craftItem.NameNumber, LabelColor, false, false ); - else - AddLabel( 330, 40, LabelHue, craftItem.NameString ); + if (needsRecipe) + { + AddButton(270, 387, 4005, 4007, 0, GumpButtonType.Page, 0); + AddHtmlLocalized(305, 390, 150, 18, 1044151, GreyLabelColor, false, false); // MAKE NOW + } + else + { + AddButton(270, 387, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(305, 390, 150, 18, 1044151, LabelColor, false, false); // MAKE NOW + } - if ( craftItem.UseAllRes ) - AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 310, 18, 1048176, LabelColor, false, false ); // Makes as many as possible at once + if (craftItem.NameNumber > 0) + AddHtmlLocalized(330, 40, 180, 18, craftItem.NameNumber, LabelColor, false, false); + else + AddLabel(330, 40, LabelHue, craftItem.NameString); - DrawItem(); - DrawSkill(); - DrawResource(); + if (craftItem.UseAllRes) + AddHtmlLocalized(170, 302 + m_OtherCount++ * 20, 310, 18, 1048176, LabelColor, false, + false); // Makes as many as possible at once - /* - if ( craftItem.RequiresSE ) - AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 310, 18, 1063363, LabelColor, false, false ); //* Requires the "Samurai Empire" expansion - * */ + DrawItem(); + DrawSkill(); + DrawResource(); - if ( craftItem.RequiredExpansion != Expansion.None ) - { - bool supportsEx = (from.NetState != null && from.NetState.SupportsExpansion( craftItem.RequiredExpansion )); - TextDefinition.AddHtmlText( this, 170, 302 + (m_OtherCount++ * 20), 310, 18, RequiredExpansionMessage( craftItem.RequiredExpansion ), false, false, supportsEx ? LabelColor : RedLabelColor, supportsEx ? LabelHue : RedLabelHue ); - } + /* + if ( craftItem.RequiresSE ) + AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 310, 18, 1063363, LabelColor, false, false ); //* Requires the "Samurai Empire" expansion + * */ - if ( needsRecipe ) - AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 310, 18, 1073620, RedLabelColor, false, false ); // You have not learned this recipe. + if (craftItem.RequiredExpansion != Expansion.None) + { + bool supportsEx = from.NetState != null && from.NetState.SupportsExpansion(craftItem.RequiredExpansion); + TextDefinition.AddHtmlText(this, 170, 302 + m_OtherCount++ * 20, 310, 18, + RequiredExpansionMessage(craftItem.RequiredExpansion), false, false, + supportsEx ? LabelColor : RedLabelColor, supportsEx ? LabelHue : RedLabelHue); + } - } + if (needsRecipe) + AddHtmlLocalized(170, 302 + m_OtherCount++ * 20, 310, 18, 1073620, RedLabelColor, false, + false); // You have not learned this recipe. + } - private TextDefinition RequiredExpansionMessage( Expansion expansion ) - { - switch( expansion ) - { - case Expansion.SE: - return 1063363; // * Requires the "Samurai Empire" expansion - case Expansion.ML: - return 1072651; // * Requires the "Mondain's Legacy" expansion - default: - return $"* Requires the \"{ExpansionInfo.GetInfo(expansion).Name}\" expansion"; - } - } + private TextDefinition RequiredExpansionMessage(Expansion expansion) + { + switch (expansion) + { + case Expansion.SE: + return 1063363; // * Requires the "Samurai Empire" expansion + case Expansion.ML: + return 1072651; // * Requires the "Mondain's Legacy" expansion + default: + return $"* Requires the \"{ExpansionInfo.GetInfo(expansion).Name}\" expansion"; + } + } - private bool m_ShowExceptionalChance; + public void DrawItem() + { + Type type = m_CraftItem.ItemType; - public void DrawItem() - { - Type type = m_CraftItem.ItemType; + AddItem(20, 50, CraftItem.ItemIDOf(type), m_CraftItem.ItemHue); - AddItem( 20, 50, CraftItem.ItemIDOf( type ), m_CraftItem.ItemHue ); + if (m_CraftItem.IsMarkable(type)) + { + AddHtmlLocalized(170, 302 + m_OtherCount++ * 20, 310, 18, 1044059, LabelColor, false, + false); // This item may hold its maker's mark + m_ShowExceptionalChance = true; + } + } - if ( m_CraftItem.IsMarkable( type ) ) - { - AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 310, 18, 1044059, LabelColor, false, false ); // This item may hold its maker's mark - m_ShowExceptionalChance = true; - } - } + public void DrawSkill() + { + for (int i = 0; i < m_CraftItem.Skills.Count; i++) + { + CraftSkill skill = m_CraftItem.Skills.GetAt(i); + double minSkill = skill.MinSkill, maxSkill = skill.MaxSkill; - public void DrawSkill() - { - for ( int i = 0; i < m_CraftItem.Skills.Count; i++ ) - { - CraftSkill skill = m_CraftItem.Skills.GetAt( i ); - double minSkill = skill.MinSkill, maxSkill = skill.MaxSkill; + if (minSkill < 0) + minSkill = 0; - if ( minSkill < 0 ) - minSkill = 0; + AddHtmlLocalized(170, 132 + i * 20, 200, 18, AosSkillBonuses.GetLabel(skill.SkillToMake), LabelColor, false, + false); + AddLabel(430, 132 + i * 20, LabelHue, $"{minSkill:F1}"); + } - AddHtmlLocalized( 170, 132 + (i * 20), 200, 18, AosSkillBonuses.GetLabel( skill.SkillToMake ), LabelColor, false, false ); - AddLabel( 430, 132 + (i * 20), LabelHue, $"{minSkill:F1}"); - } + CraftSubResCol res = m_CraftItem.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes; + int resIndex = -1; - CraftSubResCol res = ( m_CraftItem.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes ); - int resIndex = -1; + CraftContext context = m_CraftSystem.GetContext(m_From); - CraftContext context = m_CraftSystem.GetContext( m_From ); + if (context != null) + resIndex = m_CraftItem.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex; - if ( context != null ) - resIndex = ( m_CraftItem.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex ); + bool allRequiredSkills = true; + double chance = m_CraftItem.GetSuccessChance(m_From, resIndex > -1 ? res.GetAt(resIndex).ItemType : null, + m_CraftSystem, false, ref allRequiredSkills); + double excepChance = m_CraftItem.GetExceptionalChance(m_CraftSystem, chance, m_From); - bool allRequiredSkills = true; - double chance = m_CraftItem.GetSuccessChance( m_From, resIndex > -1 ? res.GetAt( resIndex ).ItemType : null, m_CraftSystem, false, ref allRequiredSkills ); - double excepChance = m_CraftItem.GetExceptionalChance( m_CraftSystem, chance, m_From ); + if (chance < 0.0) + chance = 0.0; + else if (chance > 1.0) + chance = 1.0; - if ( chance < 0.0 ) - chance = 0.0; - else if ( chance > 1.0 ) - chance = 1.0; + AddHtmlLocalized(170, 80, 250, 18, 1044057, LabelColor, false, false); // Success Chance: + AddLabel(430, 80, LabelHue, $"{chance * 100:F1}%"); - AddHtmlLocalized( 170, 80, 250, 18, 1044057, LabelColor, false, false ); // Success Chance: - AddLabel( 430, 80, LabelHue, $"{chance * 100:F1}%"); + if (m_ShowExceptionalChance) + { + if (excepChance < 0.0) + excepChance = 0.0; + else if (excepChance > 1.0) + excepChance = 1.0; - if ( m_ShowExceptionalChance ) - { - if ( excepChance < 0.0 ) - excepChance = 0.0; - else if ( excepChance > 1.0 ) - excepChance = 1.0; + AddHtmlLocalized(170, 100, 250, 18, 1044058, 32767, false, false); // Exceptional Chance: + AddLabel(430, 100, LabelHue, $"{excepChance * 100:F1}%"); + } + } - AddHtmlLocalized( 170, 100, 250, 18, 1044058, 32767, false, false ); // Exceptional Chance: - AddLabel( 430, 100, LabelHue, $"{excepChance * 100:F1}%"); - } - } + public void DrawResource() + { + bool retainedColor = false; - private static Type typeofBlankScroll = typeof( BlankScroll ); - private static Type typeofSpellScroll = typeof( SpellScroll ); + CraftContext context = m_CraftSystem.GetContext(m_From); - public void DrawResource() - { - bool retainedColor = false; + CraftSubResCol res = m_CraftItem.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes; + int resIndex = -1; - CraftContext context = m_CraftSystem.GetContext( m_From ); + if (context != null) + resIndex = m_CraftItem.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex; - CraftSubResCol res = ( m_CraftItem.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes ); - int resIndex = -1; + bool cropScroll = m_CraftItem.Resources.Count > 1 + && m_CraftItem.Resources.GetAt(m_CraftItem.Resources.Count - 1).ItemType == typeofBlankScroll + && typeofSpellScroll.IsAssignableFrom(m_CraftItem.ItemType); - if ( context != null ) - resIndex = ( m_CraftItem.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex ); + for (int i = 0; i < m_CraftItem.Resources.Count - (cropScroll ? 1 : 0) && i < 4; i++) + { + Type type; + string nameString; + int nameNumber; - bool cropScroll = ( m_CraftItem.Resources.Count > 1 ) - && m_CraftItem.Resources.GetAt( m_CraftItem.Resources.Count - 1 ).ItemType == typeofBlankScroll - && typeofSpellScroll.IsAssignableFrom( m_CraftItem.ItemType ); + CraftRes craftResource = m_CraftItem.Resources.GetAt(i); - for ( int i = 0; i < m_CraftItem.Resources.Count - (cropScroll ? 1 : 0) && i < 4; i++ ) - { - Type type; - string nameString; - int nameNumber; + type = craftResource.ItemType; + nameString = craftResource.NameString; + nameNumber = craftResource.NameNumber; - CraftRes craftResource = m_CraftItem.Resources.GetAt( i ); + // Resource Mutation + if (type == res.ResType && resIndex > -1) + { + CraftSubRes subResource = res.GetAt(resIndex); - type = craftResource.ItemType; - nameString = craftResource.NameString; - nameNumber = craftResource.NameNumber; + type = subResource.ItemType; - // Resource Mutation - if ( type == res.ResType && resIndex > -1 ) - { - CraftSubRes subResource = res.GetAt( resIndex ); + nameString = subResource.NameString; + nameNumber = subResource.GenericNameNumber; - type = subResource.ItemType; + if (nameNumber <= 0) + nameNumber = subResource.NameNumber; + } + // ****************** - nameString = subResource.NameString; - nameNumber = subResource.GenericNameNumber; + if (!retainedColor && m_CraftItem.RetainsColorFrom(m_CraftSystem, type)) + { + retainedColor = true; + AddHtmlLocalized(170, 302 + m_OtherCount++ * 20, 310, 18, 1044152, LabelColor, false, + false); // * The item retains the color of this material + AddLabel(500, 219 + i * 20, LabelHue, "*"); + } - if ( nameNumber <= 0 ) - nameNumber = subResource.NameNumber; - } - // ****************** + if (nameNumber > 0) + AddHtmlLocalized(170, 219 + i * 20, 310, 18, nameNumber, LabelColor, false, false); + else + AddLabel(170, 219 + i * 20, LabelHue, nameString); - if ( !retainedColor && m_CraftItem.RetainsColorFrom( m_CraftSystem, type ) ) - { - retainedColor = true; - AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 310, 18, 1044152, LabelColor, false, false ); // * The item retains the color of this material - AddLabel( 500, 219 + (i * 20), LabelHue, "*" ); - } + AddLabel(430, 219 + i * 20, LabelHue, craftResource.Amount.ToString()); + } - if ( nameNumber > 0 ) - AddHtmlLocalized( 170, 219 + (i * 20), 310, 18, nameNumber, LabelColor, false, false ); - else - AddLabel( 170, 219 + (i * 20), LabelHue, nameString ); + if (m_CraftItem.NameNumber == 1041267) // runebook + { + AddHtmlLocalized(170, 219 + m_CraftItem.Resources.Count * 20, 310, 18, 1044447, LabelColor, false, false); + AddLabel(430, 219 + m_CraftItem.Resources.Count * 20, LabelHue, "1"); + } - AddLabel( 430, 219 + (i * 20), LabelHue, craftResource.Amount.ToString() ); - } + if (cropScroll) + AddHtmlLocalized(170, 302 + m_OtherCount++ * 20, 360, 18, 1044379, LabelColor, false, + false); // Inscribing scrolls also requires a blank scroll and mana. + } - if ( m_CraftItem.NameNumber == 1041267 ) // runebook - { - AddHtmlLocalized( 170, 219 + (m_CraftItem.Resources.Count * 20), 310, 18, 1044447, LabelColor, false, false ); - AddLabel( 430, 219 + (m_CraftItem.Resources.Count * 20), LabelHue, "1" ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + // Back Button + if (info.ButtonID == 0) + { + CraftGump craftGump = new CraftGump(m_From, m_CraftSystem, m_Tool, null); + m_From.SendGump(craftGump); + } + else // Make Button + { + int num = m_CraftSystem.CanCraft(m_From, m_Tool, m_CraftItem.ItemType); - if ( cropScroll ) - AddHtmlLocalized( 170, 302 + (m_OtherCount++ * 20), 360, 18, 1044379, LabelColor, false, false ); // Inscribing scrolls also requires a blank scroll and mana. - } + if (num > 0) + { + m_From.SendGump(new CraftGump(m_From, m_CraftSystem, m_Tool, num)); + } + else + { + Type type = null; - public override void OnResponse( NetState sender, RelayInfo info ) - { - // Back Button - if ( info.ButtonID == 0 ) - { - CraftGump craftGump = new CraftGump( m_From, m_CraftSystem, m_Tool, null ); - m_From.SendGump( craftGump ); - } - else // Make Button - { - int num = m_CraftSystem.CanCraft( m_From, m_Tool, m_CraftItem.ItemType ); + CraftContext context = m_CraftSystem.GetContext(m_From); - if ( num > 0 ) - { - m_From.SendGump( new CraftGump( m_From, m_CraftSystem, m_Tool, num ) ); - } - else - { - Type type = null; + if (context != null) + { + CraftSubResCol res = m_CraftItem.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes; + int resIndex = m_CraftItem.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex; - CraftContext context = m_CraftSystem.GetContext( m_From ); + if (resIndex > -1) + type = res.GetAt(resIndex).ItemType; + } - if ( context != null ) - { - CraftSubResCol res = ( m_CraftItem.UseSubRes2 ? m_CraftSystem.CraftSubRes2 : m_CraftSystem.CraftSubRes ); - int resIndex = ( m_CraftItem.UseSubRes2 ? context.LastResourceIndex2 : context.LastResourceIndex ); - - if ( resIndex > -1 ) - type = res.GetAt( resIndex ).ItemType; - } - - m_CraftSystem.CreateItem( m_From, m_CraftItem.ItemType, type, m_Tool, m_CraftItem ); - } - } - } - } -} + m_CraftSystem.CreateItem(m_From, m_CraftItem.ItemType, type, m_Tool, m_CraftItem); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftItem.cs b/Scripts/Engines/Craft/Core/CraftItem.cs index 37b31965e..4ac07323b 100644 --- a/Scripts/Engines/Craft/Core/CraftItem.cs +++ b/Scripts/Engines/Craft/Core/CraftItem.cs @@ -1,1228 +1,1261 @@ using System; using System.Collections.Generic; -using Server.Items; -using Server.Factions; -using Server.Mobiles; using Server.Commands; +using Server.Factions; +using Server.Items; +using Server.Mobiles; namespace Server.Engines.Craft { - public enum ConsumeType - { - All, Half, None - } + public enum ConsumeType + { + All, + Half, + None + } - public interface ICraftable - { - int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ); - } + public interface ICraftable + { + int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue); + } - public class CraftItem - { - public bool ForceNonExceptional { get; set; } + public class CraftItem + { + private static Dictionary _itemIds = new Dictionary(); + private int m_ResAmount; - public Expansion RequiredExpansion { get; set; } + private int m_ResHue; + private CraftSystem m_System; - public Recipe Recipe { get; private set; } + public CraftItem(Type type, TextDefinition groupName, TextDefinition name) + { + Resources = new CraftResCol(); + Skills = new CraftSkillCol(); - public void AddRecipe( int id, CraftSystem system ) - { - if ( Recipe != null ) - { - Console.WriteLine( "Warning: Attempted add of recipe #{0} to the crafting of {1} in CraftSystem {2}.", id, ItemType.Name, system ); - return; - } + ItemType = type; - Recipe = new Recipe( id, system, this ); - } + GroupNameString = groupName; + NameString = name; - public static int LabelNumber( Type type ) { - int number = ItemIDOf( type ); + GroupNameNumber = groupName; + NameNumber = name; - if ( number >= 0x4000 ) - number += 1078872; - else - number += 1020000; + RequiredBeverage = BeverageType.Water; + } - return number; - } + public bool ForceNonExceptional{ get; set; } - private static Dictionary _itemIds = new Dictionary(); + public Expansion RequiredExpansion{ get; set; } - public static int ItemIDOf( Type type ) { - if (!_itemIds.TryGetValue( type, out int itemId )) { - if ( type == typeof( FactionExplosionTrap ) ) { - itemId = 14034; - } else if ( type == typeof( FactionGasTrap ) ) { - itemId = 4523; - } else if ( type == typeof( FactionSawTrap ) ) { - itemId = 4359; - } else if ( type == typeof( FactionSpikeTrap ) ) { - itemId = 4517; - } + public Recipe Recipe{ get; private set; } - if ( itemId == 0 ) { - object[] attrs = type.GetCustomAttributes( typeof( CraftItemIDAttribute ), false ); + public BeverageType RequiredBeverage{ get; set; } - if ( attrs.Length > 0 ) { - CraftItemIDAttribute craftItemID = ( CraftItemIDAttribute ) attrs[0]; - itemId = craftItemID.ItemID; - } - } + public int Mana{ get; set; } - if ( itemId == 0 ) { - Item item = null; + public int Hits{ get; set; } - try { item = Activator.CreateInstance( type ) as Item; } catch { } + public int Stam{ get; set; } - if ( item != null ) { - itemId = item.ItemID; - item.Delete(); - } - } + public bool UseSubRes2{ get; set; } - _itemIds[type] = itemId; - } + public bool UseAllRes{ get; set; } - return itemId; - } + public bool NeedHeat{ get; set; } - public CraftItem( Type type, TextDefinition groupName, TextDefinition name ) - { - Resources = new CraftResCol(); - Skills = new CraftSkillCol(); + public bool NeedOven{ get; set; } - ItemType = type; + public bool NeedMill{ get; set; } - GroupNameString = groupName; - NameString = name; + public Type ItemType{ get; } - GroupNameNumber = groupName; - NameNumber = name; + public int ItemHue{ get; set; } - RequiredBeverage = BeverageType.Water; - } + public string GroupNameString{ get; } - public BeverageType RequiredBeverage { get; set; } + public int GroupNameNumber{ get; } - public void AddRes( Type type, TextDefinition name, int amount ) - { - AddRes( type, name, amount, "" ); - } + public string NameString{ get; } - public void AddRes( Type type, TextDefinition name, int amount, TextDefinition message ) - { - CraftRes craftRes = new CraftRes( type, name, amount, message ); - Resources.Add( craftRes ); - } + public int NameNumber{ get; } + public CraftResCol Resources{ get; } - public void AddSkill( SkillName skillToMake, double minSkill, double maxSkill ) - { - CraftSkill craftSkill = new CraftSkill( skillToMake, minSkill, maxSkill ); - Skills.Add( craftSkill ); - } + public CraftSkillCol Skills{ get; } - public int Mana { get; set; } + public void AddRecipe(int id, CraftSystem system) + { + if (Recipe != null) + { + Console.WriteLine("Warning: Attempted add of recipe #{0} to the crafting of {1} in CraftSystem {2}.", id, + ItemType.Name, system); + return; + } - public int Hits { get; set; } + Recipe = new Recipe(id, system, this); + } - public int Stam { get; set; } + public static int LabelNumber(Type type) + { + int number = ItemIDOf(type); - public bool UseSubRes2 { get; set; } + if (number >= 0x4000) + number += 1078872; + else + number += 1020000; - public bool UseAllRes { get; set; } + return number; + } - public bool NeedHeat { get; set; } + public static int ItemIDOf(Type type) + { + if (!_itemIds.TryGetValue(type, out int itemId)) + { + if (type == typeof(FactionExplosionTrap)) + itemId = 14034; + else if (type == typeof(FactionGasTrap)) + itemId = 4523; + else if (type == typeof(FactionSawTrap)) + itemId = 4359; + else if (type == typeof(FactionSpikeTrap)) itemId = 4517; - public bool NeedOven { get; set; } + if (itemId == 0) + { + object[] attrs = type.GetCustomAttributes(typeof(CraftItemIDAttribute), false); - public bool NeedMill { get; set; } + if (attrs.Length > 0) + { + CraftItemIDAttribute craftItemID = (CraftItemIDAttribute)attrs[0]; + itemId = craftItemID.ItemID; + } + } - public Type ItemType { get; } + if (itemId == 0) + { + Item item = null; - public int ItemHue { get; set; } + try + { + item = Activator.CreateInstance(type) as Item; + } + catch + { + } - public string GroupNameString { get; } + if (item != null) + { + itemId = item.ItemID; + item.Delete(); + } + } - public int GroupNameNumber { get; } + _itemIds[type] = itemId; + } - public string NameString { get; } + return itemId; + } - public int NameNumber { get; } + public void AddRes(Type type, TextDefinition name, int amount) + { + AddRes(type, name, amount, ""); + } - public CraftResCol Resources { get; } + public void AddRes(Type type, TextDefinition name, int amount, TextDefinition message) + { + CraftRes craftRes = new CraftRes(type, name, amount, message); + Resources.Add(craftRes); + } - public CraftSkillCol Skills { get; } - public bool ConsumeAttributes( Mobile from, ref object message, bool consume ) - { - bool consumMana = false; - bool consumHits = false; - bool consumStam = false; + public void AddSkill(SkillName skillToMake, double minSkill, double maxSkill) + { + CraftSkill craftSkill = new CraftSkill(skillToMake, minSkill, maxSkill); + Skills.Add(craftSkill); + } - if ( Hits > 0 && from.Hits < Hits ) - { - message = "You lack the required hit points to make that."; - return false; - } - - consumHits = consume; + public bool ConsumeAttributes(Mobile from, ref object message, bool consume) + { + bool consumMana = false; + bool consumHits = false; + bool consumStam = false; - if ( Mana > 0 && from.Mana < Mana ) - { - message = "You lack the required mana to make that."; - return false; - } - - consumMana = consume; - - if ( Stam > 0 && from.Stam < Stam ) - { - message = "You lack the required stamina to make that."; - return false; - } - - consumStam = consume; - - if ( consumMana ) - from.Mana -= Mana; - - if ( consumHits ) - from.Hits -= Hits; - - if ( consumStam ) - from.Stam -= Stam; - - return true; - } - - #region Tables - private static int[] m_HeatSources = { - 0x461, 0x48E, // Sandstone oven/fireplace - 0x92B, 0x96C, // Stone oven/fireplace - 0xDE3, 0xDE9, // Campfire - 0xFAC, 0xFAC, // Firepit - 0x184A, 0x184C, // Heating stand (left) - 0x184E, 0x1850, // Heating stand (right) - 0x398C, 0x399F, // Fire field - 0x2DDB, 0x2DDC, //Elven stove - 0x19AA, 0x19BB, // Veteran Reward Brazier - 0x197A, 0x19A9, // Large Forge - 0x0FB1, 0x0FB1, // Small Forge - 0x2DD8, 0x2DD8 // Elven Forge - }; - - private static int[] m_Ovens = { - 0x461, 0x46F, // Sandstone oven - 0x92B, 0x93F, // Stone oven - 0x2DDB, 0x2DDC //Elven stove - }; - - private static int[] m_Mills = { - 0x1920, 0x1921, 0x1922, 0x1923, 0x1924, 0x1295, 0x1926, 0x1928, - 0x192C, 0x192D, 0x192E, 0x129F, 0x1930, 0x1931, 0x1932, 0x1934 - }; + if (Hits > 0 && from.Hits < Hits) + { + message = "You lack the required hit points to make that."; + return false; + } + + consumHits = consume; + + if (Mana > 0 && from.Mana < Mana) + { + message = "You lack the required mana to make that."; + return false; + } + + consumMana = consume; - private static Type[][] m_TypesTable = { - new[]{ typeof( Log ), typeof( Board ) }, - new[]{ typeof( HeartwoodLog ), typeof( HeartwoodBoard ) }, - new[]{ typeof( BloodwoodLog ), typeof( BloodwoodBoard ) }, - new[]{ typeof( FrostwoodLog ), typeof( FrostwoodBoard ) }, - new[]{ typeof( OakLog ), typeof( OakBoard ) }, - new[]{ typeof( AshLog ), typeof( AshBoard ) }, - new[]{ typeof( YewLog ), typeof( YewBoard ) }, - new[]{ typeof( Leather ), typeof( Hides ) }, - new[]{ typeof( SpinedLeather ), typeof( SpinedHides ) }, - new[]{ typeof( HornedLeather ), typeof( HornedHides ) }, - new[]{ typeof( BarbedLeather ), typeof( BarbedHides ) }, - new[]{ typeof( BlankMap ), typeof( BlankScroll ) }, - new[]{ typeof( Cloth ), typeof( UncutCloth ) }, - new[]{ typeof( CheeseWheel ), typeof( CheeseWedge ) }, - new[]{ typeof( Pumpkin ), typeof( SmallPumpkin ) }, - new[]{ typeof( WoodenBowlOfPeas ), typeof( PewterBowlOfPeas ) } - }; - - private static Type[] m_ColoredItemTable = { - typeof( BaseWeapon ), typeof( BaseArmor ), typeof( BaseClothing ), - typeof( BaseJewel ), typeof( DragonBardingDeed ) - }; - - private static Type[] m_ColoredResourceTable = { - typeof( BaseIngot ), typeof( BaseOre ), - typeof( BaseLeather ), typeof( BaseHides ), - typeof( UncutCloth ), typeof( Cloth ), - typeof( BaseGranite ), typeof( BaseScales ) - }; - - private static Type[] m_MarkableTable = { - typeof( BaseArmor ), - typeof( BaseWeapon ), - typeof( BaseClothing ), - typeof( BaseInstrument ), - typeof( DragonBardingDeed ), - typeof( BaseTool ), - typeof( BaseHarvestTool ), - typeof( FukiyaDarts ), typeof( Shuriken ), - typeof( Spellbook ), typeof( Runebook ), - typeof( BaseQuiver ) - }; - - private static Type[] m_NeverColorTable = { - typeof( OrcHelm ) - }; - #endregion - - public bool IsMarkable( Type type ) - { - if ( ForceNonExceptional ) //Don't even display the stuff for marking if it can't ever be exceptional. - return false; - - for ( int i = 0; i < m_MarkableTable.Length; ++i ) - { - if ( type == m_MarkableTable[i] || type.IsSubclassOf( m_MarkableTable[i] ) ) - return true; - } - - return false; - } - - public static bool RetainsColor( Type type ) - { - bool neverColor = false; - - for ( int i = 0; !neverColor && i < m_NeverColorTable.Length; ++i ) - neverColor = ( type == m_NeverColorTable[i] || type.IsSubclassOf( m_NeverColorTable[i] ) ); - - if ( neverColor ) - return false; - - bool inItemTable = false; - - for ( int i = 0; !inItemTable && i < m_ColoredItemTable.Length; ++i ) - inItemTable = ( type == m_ColoredItemTable[i] || type.IsSubclassOf( m_ColoredItemTable[i] ) ); - - return inItemTable; - } - - public bool RetainsColorFrom( CraftSystem system, Type type ) - { - if ( system.RetainsColorFrom( this, type ) ) - return true; - - bool inItemTable = RetainsColor( ItemType ); - - if ( !inItemTable ) - return false; - - bool inResourceTable = false; - - for ( int i = 0; !inResourceTable && i < m_ColoredResourceTable.Length; ++i ) - inResourceTable = ( type == m_ColoredResourceTable[i] || type.IsSubclassOf( m_ColoredResourceTable[i] ) ); - - return inResourceTable; - } - - public bool Find( Mobile from, int[] itemIDs ) - { - Map map = from.Map; - - if ( map == null ) - return false; - - IPooledEnumerable eable = map.GetItemsInRange( from.Location, 2 ); - - foreach ( Item item in eable ) - { - if ( (item.Z + 16) > from.Z && (from.Z + 16) > item.Z && Find( item.ItemID, itemIDs ) ) - { - eable.Free(); - return true; - } - } - - eable.Free(); - - for ( int x = -2; x <= 2; ++x ) - { - for ( int y = -2; y <= 2; ++y ) - { - int vx = from.X + x; - int vy = from.Y + y; - - StaticTile[] tiles = map.Tiles.GetStaticTiles( vx, vy, true ); - - for ( int i = 0; i < tiles.Length; ++i ) - { - int z = tiles[i].Z; - int id = tiles[i].ID; - - if ( (z + 16) > from.Z && (from.Z + 16) > z && Find( id, itemIDs ) ) - return true; - } - } - } - - return false; - } - - public bool Find( int itemID, int[] itemIDs ) - { - bool contains = false; - - for ( int i = 0; !contains && i < itemIDs.Length; i += 2 ) - contains = ( itemID >= itemIDs[i] && itemID <= itemIDs[i + 1] ); - - return contains; - } - - public bool IsQuantityType( Type[][] types ) - { - for ( int i = 0; i < types.Length; ++i ) - { - Type[] check = types[i]; - - for ( int j = 0; j < check.Length; ++j ) - { - if ( typeof( IHasQuantity ).IsAssignableFrom( check[j] ) ) - return true; - } - } - - return false; - } - - public int ConsumeQuantity( Container cont, Type[][] types, int[] amounts ) - { - if ( types.Length != amounts.Length ) - throw new ArgumentException(); - - Item[][] items = new Item[types.Length][]; - int[] totals = new int[types.Length]; - - for ( int i = 0; i < types.Length; ++i ) - { - items[i] = cont.FindItemsByType( types[i], true ); - - for ( int j = 0; j < items[i].Length; ++j ) - { - if ( !(items[i][j] is IHasQuantity hq) ) - { - totals[i] += items[i][j].Amount; - } - else - { - if ( hq is BaseBeverage beverage && beverage.Content != RequiredBeverage ) - continue; - - totals[i] += hq.Quantity; - } - } - - if ( totals[i] < amounts[i] ) - return i; - } - - for ( int i = 0; i < types.Length; ++i ) - { - int need = amounts[i]; - - for ( int j = 0; j < items[i].Length; ++j ) - { - Item item = items[i][j]; - - if ( !(item is IHasQuantity hq) ) - { - int theirAmount = item.Amount; - - if ( theirAmount < need ) - { - item.Delete(); - need -= theirAmount; - } - else - { - item.Consume( need ); - break; - } - } - else - { - if ( hq is BaseBeverage beverage && beverage.Content != RequiredBeverage ) - continue; - - int theirAmount = hq.Quantity; - - if ( theirAmount < need ) - { - hq.Quantity -= theirAmount; - need -= theirAmount; - } - else - { - hq.Quantity -= need; - break; - } - } - } - } - - return -1; - } - - public int GetQuantity( Container cont, Type[] types ) - { - Item[] items = cont.FindItemsByType( types, true ); - - int amount = 0; - - for ( int i = 0; i < items.Length; ++i ) - { - if ( !(items[i] is IHasQuantity hq) ) - { - amount += items[i].Amount; - } - else - { - if ( hq is BaseBeverage beverage && beverage.Content != RequiredBeverage ) - continue; - - amount += hq.Quantity; - } - } - - return amount; - } - - public bool ConsumeRes( Mobile from, Type typeRes, CraftSystem craftSystem, ref int resHue, ref int maxAmount, ConsumeType consumeType, ref object message ) - { - return ConsumeRes( from, typeRes, craftSystem, ref resHue, ref maxAmount, consumeType, ref message, false ); - } - - public bool ConsumeRes( Mobile from, Type typeRes, CraftSystem craftSystem, ref int resHue, ref int maxAmount, ConsumeType consumeType, ref object message, bool isFailure ) - { - Container ourPack = from.Backpack; - - if ( ourPack == null ) - return false; - - if ( NeedHeat && !Find( from, m_HeatSources ) ) - { - message = 1044487; // You must be near a fire source to cook. - return false; - } - - if ( NeedOven && !Find( from, m_Ovens ) ) - { - message = 1044493; // You must be near an oven to bake that. - return false; - } - - if ( NeedMill && !Find( from, m_Mills ) ) - { - message = 1044491; // You must be near a flour mill to do that. - return false; - } - - Type[][] types = new Type[Resources.Count][]; - int[] amounts = new int[Resources.Count]; - - maxAmount = int.MaxValue; - - CraftSubResCol resCol = ( UseSubRes2 ? craftSystem.CraftSubRes2 : craftSystem.CraftSubRes ); - - for ( int i = 0; i < types.Length; ++i ) - { - CraftRes craftRes = Resources.GetAt( i ); - Type baseType = craftRes.ItemType; - - // Resource Mutation - if ( (baseType == resCol.ResType) && ( typeRes != null ) ) - { - baseType = typeRes; - - CraftSubRes subResource = resCol.SearchFor( baseType ); - - if ( subResource != null && from.Skills[craftSystem.MainSkill].Base < subResource.RequiredSkill ) - { - message = subResource.Message; - return false; - } - } - // ****************** - - for ( int j = 0; types[i] == null && j < m_TypesTable.Length; ++j ) - { - if ( m_TypesTable[j][0] == baseType ) - types[i] = m_TypesTable[j]; - } - - if ( types[i] == null ) - types[i] = new[]{ baseType }; - - amounts[i] = craftRes.Amount; - - // For stackable items that can ben crafted more than one at a time - if ( UseAllRes ) - { - int tempAmount = ourPack.GetAmount( types[i] ); - tempAmount /= amounts[i]; - if ( tempAmount < maxAmount ) - { - maxAmount = tempAmount; - - if ( maxAmount == 0 ) - { - CraftRes res = Resources.GetAt( i ); - - if ( res.MessageNumber > 0 ) - message = res.MessageNumber; - else if ( !string.IsNullOrEmpty( res.MessageString ) ) - message = res.MessageString; - else - message = 502925; // You don't have the resources required to make that item. - - return false; - } - } - } - // **************************** - - if ( isFailure && !craftSystem.ConsumeOnFailure( from, types[i][0], this ) ) - amounts[i] = 0; - } - - // We adjust the amount of each resource to consume the max posible - if ( UseAllRes ) - { - for ( int i = 0; i < amounts.Length; ++i ) - amounts[i] *= maxAmount; - } - else - maxAmount = -1; - - Item consumeExtra = null; - - if ( NameNumber == 1041267 ) - { - // Runebooks are a special case, they need a blank recall rune - - List runes = ourPack.FindItemsByType(); - - for ( int i = 0; i < runes.Count; ++i ) - { - RecallRune rune = runes[i]; - - if ( rune != null && !rune.Marked ) - { - consumeExtra = rune; - break; - } - } - - if ( consumeExtra == null ) - { - message = 1044253; // You don't have the components needed to make that. - return false; - } - } - - int index = 0; - - // Consume ALL - if ( consumeType == ConsumeType.All ) - { - m_ResHue = 0; m_ResAmount = 0; m_System = craftSystem; - - if ( IsQuantityType( types ) ) - index = ConsumeQuantity( ourPack, types, amounts ); - else - index = ourPack.ConsumeTotalGrouped( types, amounts, true, OnResourceConsumed, CheckHueGrouping ); - - resHue = m_ResHue; - } - - // Consume Half ( for use all resource craft type ) - else if ( consumeType == ConsumeType.Half ) - { - for ( int i = 0; i < amounts.Length; i++ ) - { - amounts[i] /= 2; - - if ( amounts[i] < 1 ) - amounts[i] = 1; - } - - m_ResHue = 0; m_ResAmount = 0; m_System = craftSystem; - - if ( IsQuantityType( types ) ) - index = ConsumeQuantity( ourPack, types, amounts ); - else - index = ourPack.ConsumeTotalGrouped( types, amounts, true, OnResourceConsumed, CheckHueGrouping ); - - resHue = m_ResHue; - } - - else // ConstumeType.None ( it's basicaly used to know if the crafter has enough resource before starting the process ) - { - index = -1; - - if ( IsQuantityType( types ) ) - { - for ( int i = 0; i < types.Length; i++ ) - { - if ( GetQuantity( ourPack, types[i] ) < amounts[i] ) - { - index = i; - break; - } - } - } - else - { - for ( int i = 0; i < types.Length; i++ ) - { - if ( ourPack.GetBestGroupAmount( types[i], true, CheckHueGrouping ) < amounts[i] ) - { - index = i; - break; - } - } - } - } - - if ( index == -1 ) - { - if ( consumeType != ConsumeType.None ) - { - consumeExtra?.Delete(); - } - - return true; - } - - { - CraftRes res = Resources.GetAt( index ); - - if ( res.MessageNumber > 0 ) - message = res.MessageNumber; - else if ( res.MessageString != null && res.MessageString != string.Empty ) - message = res.MessageString; - else - message = 502925; // You don't have the resources required to make that item. - - return false; - } - } - - private int m_ResHue; - private int m_ResAmount; - private CraftSystem m_System; - - private void OnResourceConsumed( Item item, int amount ) - { - if ( !RetainsColorFrom( m_System, item.GetType() ) ) - return; - - if ( amount >= m_ResAmount ) - { - m_ResHue = item.Hue; - m_ResAmount = amount; - } - } - - private int CheckHueGrouping( Item a, Item b ) - { - return b.Hue.CompareTo( a.Hue ); - } - - public double GetExceptionalChance( CraftSystem system, double chance, Mobile from ) - { - if ( ForceNonExceptional ) - return 0.0; - - double bonus = 0.0; - - if ( from.Talisman is BaseTalisman talisman && talisman.Skill == system.MainSkill ) - { - chance -= talisman.SuccessBonus / 100.0; - bonus = talisman.ExceptionalBonus / 100.0; - } - - switch ( system.ECA ) - { - default: chance -= 0.6; break; - case CraftECA.FiftyPercentChanceMinusTenPercent: chance = chance * 0.5 - 0.1; break; - case CraftECA.ChanceMinusSixtyToFourtyFive: - { - double offset = 0.60 - ((from.Skills[system.MainSkill].Value - 95.0) * 0.03); - - if ( offset < 0.45 ) - offset = 0.45; - else if ( offset > 0.60 ) - offset = 0.60; - - chance -= offset; - break; - } - } - - if ( chance > 0 ) - return chance + bonus; - - return chance; - } - - public bool CheckSkills( Mobile from, Type typeRes, CraftSystem craftSystem, ref int quality, ref bool allRequiredSkills ) - { - return CheckSkills( from, typeRes, craftSystem, ref quality, ref allRequiredSkills, true ); - } - - public bool CheckSkills( Mobile from, Type typeRes, CraftSystem craftSystem, ref int quality, ref bool allRequiredSkills, bool gainSkills ) - { - double chance = GetSuccessChance( from, typeRes, craftSystem, gainSkills, ref allRequiredSkills ); - - if ( GetExceptionalChance( craftSystem, chance, from ) > Utility.RandomDouble() ) - quality = 2; - - return ( chance > Utility.RandomDouble() ); - } - - public double GetSuccessChance( Mobile from, Type typeRes, CraftSystem craftSystem, bool gainSkills, ref bool allRequiredSkills ) - { - double minMainSkill = 0.0; - double maxMainSkill = 0.0; - double valMainSkill = 0.0; - - allRequiredSkills = true; - - for ( int i = 0; i < Skills.Count; i++) - { - CraftSkill craftSkill = Skills.GetAt(i); - - double minSkill = craftSkill.MinSkill; - double maxSkill = craftSkill.MaxSkill; - double valSkill = from.Skills[craftSkill.SkillToMake].Value; - - if ( valSkill < minSkill ) - allRequiredSkills = false; - - if ( craftSkill.SkillToMake == craftSystem.MainSkill ) - { - minMainSkill = minSkill; - maxMainSkill = maxSkill; - valMainSkill = valSkill; - } - - if ( gainSkills ) // This is a passive check. Success chance is entirely dependant on the main skill - from.CheckSkill( craftSkill.SkillToMake, minSkill, maxSkill ); - } - - double chance; - - if ( allRequiredSkills ) - chance = craftSystem.GetChanceAtMin( this ) + ((valMainSkill - minMainSkill) / (maxMainSkill - minMainSkill) * (1.0 - craftSystem.GetChanceAtMin( this ))); - else - chance = 0.0; - - if ( allRequiredSkills && from.Talisman is BaseTalisman talisman && talisman.Skill == craftSystem.MainSkill ) - chance += talisman.SuccessBonus / 100.0; - - if ( allRequiredSkills && valMainSkill == maxMainSkill ) - chance = 1.0; - - return chance; - } - - public void Craft( Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool ) - { - if ( from.BeginAction( typeof( CraftSystem ) ) ) - { - if ( RequiredExpansion == Expansion.None || ( from.NetState != null && from.NetState.SupportsExpansion( RequiredExpansion ) ) ) - { - bool allRequiredSkills = true; - double chance = GetSuccessChance( from, typeRes, craftSystem, false, ref allRequiredSkills ); - - if ( allRequiredSkills && chance >= 0.0 ) - { - if ( Recipe == null || !(from is PlayerMobile) || ((PlayerMobile)from).HasRecipe( Recipe ) ) - { - int badCraft = craftSystem.CanCraft( from, tool, ItemType ); - - if ( badCraft <= 0 ) - { - int resHue = 0; - int maxAmount = 0; - object message = null; - - if ( ConsumeRes( from, typeRes, craftSystem, ref resHue, ref maxAmount, ConsumeType.None, ref message ) ) - { - message = null; - - if ( ConsumeAttributes( from, ref message, false ) ) - { - CraftContext context = craftSystem.GetContext( from ); - - context?.OnMade( this ); - - int iMin = craftSystem.MinCraftEffect; - int iMax = (craftSystem.MaxCraftEffect - iMin) + 1; - int iRandom = Utility.Random( iMax ); - iRandom += iMin + 1; - new InternalTimer( from, craftSystem, this, typeRes, tool, iRandom ).Start(); - } - else - { - from.EndAction( typeof( CraftSystem ) ); - from.SendGump( new CraftGump( from, craftSystem, tool, message ) ); - } - } - else - { - from.EndAction( typeof( CraftSystem ) ); - from.SendGump( new CraftGump( from, craftSystem, tool, message ) ); - } - } - else - { - from.EndAction( typeof( CraftSystem ) ); - from.SendGump( new CraftGump( from, craftSystem, tool, badCraft ) ); - } - } - else - { - from.EndAction( typeof( CraftSystem ) ); - from.SendGump( new CraftGump( from, craftSystem, tool, 1072847 ) ); // You must learn that recipe from a scroll. - } - } - else - { - from.EndAction( typeof( CraftSystem ) ); - from.SendGump( new CraftGump( from, craftSystem, tool, 1044153 ) ); // You don't have the required skills to attempt this item. - } - } - else - { - from.EndAction( typeof( CraftSystem ) ); - from.SendGump( new CraftGump( from, craftSystem, tool, RequiredExpansionMessage( RequiredExpansion ) ) ); //The {0} expansion is required to attempt this item. - } - } - else - { - from.SendLocalizedMessage( 500119 ); // You must wait to perform another action - } - } - - private object RequiredExpansionMessage( Expansion expansion ) //Eventually convert to TextDefinition, but that requires that we convert all the gumps to ues it too. Not that it wouldn't be a bad idea. - { - switch( expansion ) - { - case Expansion.SE: - return 1063307; // The "Samurai Empire" expansion is required to attempt this item. - case Expansion.ML: - return 1072650; // The "Mondain's Legacy" expansion is required to attempt this item. - default: - return - $"The \"{ExpansionInfo.GetInfo(expansion).Name}\" expansion is required to attempt this item."; - } - } - - public void CompleteCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CustomCraft customCraft ) - { - int badCraft = craftSystem.CanCraft( from, tool, ItemType ); - - if ( badCraft > 0 ) - { - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, badCraft ) ); - else - from.SendLocalizedMessage( badCraft ); - - return; - } - - int checkResHue = 0, checkMaxAmount = 0; - object checkMessage = null; - - // Not enough resource to craft it - if ( !(ConsumeRes( from, typeRes, craftSystem, ref checkResHue, ref checkMaxAmount, ConsumeType.None, ref checkMessage ) - && ConsumeAttributes( from, ref checkMessage, false ))) - { - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, checkMessage ) ); - else if ( checkMessage is int messageInt && messageInt > 0 ) - from.SendLocalizedMessage( messageInt ); - else - from.SendMessage( checkMessage.ToString() ); - - return; - } - - bool toolBroken = false; - - int ignored = 1; - int endquality = 1; - - bool allRequiredSkills = true; - - if ( CheckSkills( from, typeRes, craftSystem, ref ignored, ref allRequiredSkills ) ) - { - // Resource - int resHue = 0; - int maxAmount = 0; - - object message = null; - - // Not enough resource to craft it - if ( !(ConsumeRes( from, typeRes, craftSystem, ref resHue, ref maxAmount, ConsumeType.All, ref message ) - && ConsumeAttributes( from, ref message, true ))) - { - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, message ) ); - else if ( message is int messageIn && messageIn > 0 ) - from.SendLocalizedMessage( messageIn ); - else - from.SendMessage( message.ToString() ); - - return; - } - - tool.UsesRemaining--; - - if ( craftSystem is DefBlacksmithy ) - { - if ( from.FindItemOnLayer( Layer.OneHanded ) is AncientSmithyHammer hammer && hammer != tool ) - { - hammer.UsesRemaining--; - if ( hammer.UsesRemaining < 1 ) - hammer.Delete(); - } - } - - if ( tool.UsesRemaining < 1 && tool.BreakOnDepletion ) - toolBroken = true; - - if ( toolBroken ) - tool.Delete(); - - int num = 0; - - Item item; - if ( customCraft != null ) - { - item = customCraft.CompleteCraft( out num ); - } - else if ( typeof( MapItem ).IsAssignableFrom( ItemType ) && from.Map != Map.Trammel && from.Map != Map.Felucca ) - { - item = new IndecipherableMap(); - from.SendLocalizedMessage( 1070800 ); // The map you create becomes mysteriously indecipherable. - } - else - { - item = Activator.CreateInstance( ItemType ) as Item; - } - - if ( item != null ) - { - if ( item is ICraftable craftable ) - endquality = craftable.OnCraft( quality, makersMark, from, craftSystem, typeRes, tool, this, resHue ); - else if ( item.Hue == 0 ) - item.Hue = resHue; - - if ( maxAmount > 0 ) - { - if ( !item.Stackable && item is IUsesRemaining remaining ) - remaining.UsesRemaining *= maxAmount; - else - item.Amount = maxAmount; - } - - from.AddToBackpack( item ); - - if ( from.AccessLevel > AccessLevel.Player ) - CommandLogging.WriteLine( from, "Crafting {0} with craft system {1}", CommandLogging.Format( item ), craftSystem.GetType().Name ); - - //from.PlaySound( 0x57 ); - } - - if ( num == 0 ) - num = craftSystem.PlayEndingEffect( from, false, true, toolBroken, endquality, makersMark, this ); - - bool queryFactionImbue = false; - int availableSilver = 0; - FactionItemDefinition def = null; - Faction faction = null; - - if ( item is IFactionItem ) - { - def = FactionItemDefinition.Identify( item ); - - if ( def != null ) - { - faction = Faction.Find( from ); - - if ( faction != null ) - { - Town town = Town.FromRegion( from.Region ); - - if ( town != null && town.Owner == faction ) - { - Container pack = from.Backpack; - - if ( pack != null ) - { - availableSilver = pack.GetAmount( typeof( Silver ) ); - - if ( availableSilver >= def.SilverCost ) - queryFactionImbue = Faction.IsNearType( from, def.VendorType, 12 ); - } - } - } - } - } - - // TODO: Scroll imbuing - - if ( queryFactionImbue ) - from.SendGump( new FactionImbueGump( quality, item, from, craftSystem, tool, num, availableSilver, faction, def ) ); - else if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, num ) ); - else if ( num > 0 ) - from.SendLocalizedMessage( num ); - } - else if ( !allRequiredSkills ) - { - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, 1044153 ) ); - else - from.SendLocalizedMessage( 1044153 ); // You don't have the required skills to attempt this item. - } - else - { - ConsumeType consumeType = ( UseAllRes ? ConsumeType.Half : ConsumeType.All ); - int resHue = 0; - int maxAmount = 0; - - object message = null; - - // Not enough resource to craft it - if ( !ConsumeRes( from, typeRes, craftSystem, ref resHue, ref maxAmount, consumeType, ref message, true ) ) - { - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, message ) ); - else if ( message is int messageInt && messageInt > 0 ) - from.SendLocalizedMessage( messageInt ); - else - from.SendMessage( message.ToString() ); - - return; - } - - tool.UsesRemaining--; - - if ( tool.UsesRemaining < 1 && tool.BreakOnDepletion ) - toolBroken = true; - - if ( toolBroken ) - tool.Delete(); - - // SkillCheck failed. - int num = craftSystem.PlayEndingEffect( from, true, true, toolBroken, endquality, false, this ); - - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, craftSystem, tool, num ) ); - else if ( num > 0 ) - from.SendLocalizedMessage( num ); - } - } - - private class InternalTimer : Timer - { - private Mobile m_From; - private int m_iCount; - private int m_iCountMax; - private CraftItem m_CraftItem; - private CraftSystem m_CraftSystem; - private Type m_TypeRes; - private BaseTool m_Tool; - - public InternalTimer( Mobile from, CraftSystem craftSystem, CraftItem craftItem, Type typeRes, BaseTool tool, int iCountMax ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( craftSystem.Delay ), iCountMax ) - { - m_From = from; - m_CraftItem = craftItem; - m_iCount = 0; - m_iCountMax = iCountMax; - m_CraftSystem = craftSystem; - m_TypeRes = typeRes; - m_Tool = tool; - } - - protected override void OnTick() - { - m_iCount++; - - m_From.DisruptiveAction(); - - if ( m_iCount < m_iCountMax ) - { - m_CraftSystem.PlayCraftEffect( m_From ); - } - else - { - m_From.EndAction( typeof( CraftSystem ) ); - - int badCraft = m_CraftSystem.CanCraft( m_From, m_Tool, m_CraftItem.ItemType ); - - if ( badCraft > 0 ) - { - if ( m_Tool != null && !m_Tool.Deleted && m_Tool.UsesRemaining > 0 ) - m_From.SendGump( new CraftGump( m_From, m_CraftSystem, m_Tool, badCraft ) ); - else - m_From.SendLocalizedMessage( badCraft ); - - return; - } - - int quality = 1; - bool allRequiredSkills = true; - - m_CraftItem.CheckSkills( m_From, m_TypeRes, m_CraftSystem, ref quality, ref allRequiredSkills, false ); - - CraftContext context = m_CraftSystem.GetContext( m_From ); - - if ( context == null ) - return; - - if ( typeof( CustomCraft ).IsAssignableFrom( m_CraftItem.ItemType ) ) - { - CustomCraft cc = null; - - try{ cc = Activator.CreateInstance( m_CraftItem.ItemType, new object[] { m_From, m_CraftItem, m_CraftSystem, m_TypeRes, m_Tool, quality } ) as CustomCraft; } - catch{} - - cc?.EndCraftAction(); - - return; - } - - bool makersMark = false; - - if ( quality == 2 && m_From.Skills[m_CraftSystem.MainSkill].Base >= 100.0 ) - makersMark = m_CraftItem.IsMarkable( m_CraftItem.ItemType ); - - if ( makersMark && context.MarkOption == CraftMarkOption.PromptForMark ) - { - m_From.SendGump( new QueryMakersMarkGump( quality, m_From, m_CraftItem, m_CraftSystem, m_TypeRes, m_Tool ) ); - } - else - { - if ( context.MarkOption == CraftMarkOption.DoNotMark ) - makersMark = false; - - m_CraftItem.CompleteCraft( quality, makersMark, m_From, m_CraftSystem, m_TypeRes, m_Tool, null ); - } - } - } - } - } -} + if (Stam > 0 && from.Stam < Stam) + { + message = "You lack the required stamina to make that."; + return false; + } + + consumStam = consume; + + if (consumMana) + from.Mana -= Mana; + + if (consumHits) + from.Hits -= Hits; + + if (consumStam) + from.Stam -= Stam; + + return true; + } + + public bool IsMarkable(Type type) + { + if (ForceNonExceptional) //Don't even display the stuff for marking if it can't ever be exceptional. + return false; + + for (int i = 0; i < m_MarkableTable.Length; ++i) + if (type == m_MarkableTable[i] || type.IsSubclassOf(m_MarkableTable[i])) + return true; + + return false; + } + + public static bool RetainsColor(Type type) + { + bool neverColor = false; + + for (int i = 0; !neverColor && i < m_NeverColorTable.Length; ++i) + neverColor = type == m_NeverColorTable[i] || type.IsSubclassOf(m_NeverColorTable[i]); + + if (neverColor) + return false; + + bool inItemTable = false; + + for (int i = 0; !inItemTable && i < m_ColoredItemTable.Length; ++i) + inItemTable = type == m_ColoredItemTable[i] || type.IsSubclassOf(m_ColoredItemTable[i]); + + return inItemTable; + } + + public bool RetainsColorFrom(CraftSystem system, Type type) + { + if (system.RetainsColorFrom(this, type)) + return true; + + bool inItemTable = RetainsColor(ItemType); + + if (!inItemTable) + return false; + + bool inResourceTable = false; + + for (int i = 0; !inResourceTable && i < m_ColoredResourceTable.Length; ++i) + inResourceTable = type == m_ColoredResourceTable[i] || type.IsSubclassOf(m_ColoredResourceTable[i]); + + return inResourceTable; + } + + public bool Find(Mobile from, int[] itemIDs) + { + Map map = from.Map; + + if (map == null) + return false; + + IPooledEnumerable eable = map.GetItemsInRange(from.Location, 2); + + foreach (Item item in eable) + if (item.Z + 16 > from.Z && from.Z + 16 > item.Z && Find(item.ItemID, itemIDs)) + { + eable.Free(); + return true; + } + + eable.Free(); + + for (int x = -2; x <= 2; ++x) + for (int y = -2; y <= 2; ++y) + { + int vx = from.X + x; + int vy = from.Y + y; + + StaticTile[] tiles = map.Tiles.GetStaticTiles(vx, vy, true); + + for (int i = 0; i < tiles.Length; ++i) + { + int z = tiles[i].Z; + int id = tiles[i].ID; + + if (z + 16 > from.Z && from.Z + 16 > z && Find(id, itemIDs)) + return true; + } + } + + return false; + } + + public bool Find(int itemID, int[] itemIDs) + { + bool contains = false; + + for (int i = 0; !contains && i < itemIDs.Length; i += 2) + contains = itemID >= itemIDs[i] && itemID <= itemIDs[i + 1]; + + return contains; + } + + public bool IsQuantityType(Type[][] types) + { + for (int i = 0; i < types.Length; ++i) + { + Type[] check = types[i]; + + for (int j = 0; j < check.Length; ++j) + if (typeof(IHasQuantity).IsAssignableFrom(check[j])) + return true; + } + + return false; + } + + public int ConsumeQuantity(Container cont, Type[][] types, int[] amounts) + { + if (types.Length != amounts.Length) + throw new ArgumentException(); + + Item[][] items = new Item[types.Length][]; + int[] totals = new int[types.Length]; + + for (int i = 0; i < types.Length; ++i) + { + items[i] = cont.FindItemsByType(types[i], true); + + for (int j = 0; j < items[i].Length; ++j) + if (!(items[i][j] is IHasQuantity hq)) + { + totals[i] += items[i][j].Amount; + } + else + { + if (hq is BaseBeverage beverage && beverage.Content != RequiredBeverage) + continue; + + totals[i] += hq.Quantity; + } + + if (totals[i] < amounts[i]) + return i; + } + + for (int i = 0; i < types.Length; ++i) + { + int need = amounts[i]; + + for (int j = 0; j < items[i].Length; ++j) + { + Item item = items[i][j]; + + if (!(item is IHasQuantity hq)) + { + int theirAmount = item.Amount; + + if (theirAmount < need) + { + item.Delete(); + need -= theirAmount; + } + else + { + item.Consume(need); + break; + } + } + else + { + if (hq is BaseBeverage beverage && beverage.Content != RequiredBeverage) + continue; + + int theirAmount = hq.Quantity; + + if (theirAmount < need) + { + hq.Quantity -= theirAmount; + need -= theirAmount; + } + else + { + hq.Quantity -= need; + break; + } + } + } + } + + return -1; + } + + public int GetQuantity(Container cont, Type[] types) + { + Item[] items = cont.FindItemsByType(types, true); + + int amount = 0; + + for (int i = 0; i < items.Length; ++i) + if (!(items[i] is IHasQuantity hq)) + { + amount += items[i].Amount; + } + else + { + if (hq is BaseBeverage beverage && beverage.Content != RequiredBeverage) + continue; + + amount += hq.Quantity; + } + + return amount; + } + + public bool ConsumeRes(Mobile from, Type typeRes, CraftSystem craftSystem, ref int resHue, ref int maxAmount, + ConsumeType consumeType, ref object message) + { + return ConsumeRes(from, typeRes, craftSystem, ref resHue, ref maxAmount, consumeType, ref message, false); + } + + public bool ConsumeRes(Mobile from, Type typeRes, CraftSystem craftSystem, ref int resHue, ref int maxAmount, + ConsumeType consumeType, ref object message, bool isFailure) + { + Container ourPack = from.Backpack; + + if (ourPack == null) + return false; + + if (NeedHeat && !Find(from, m_HeatSources)) + { + message = 1044487; // You must be near a fire source to cook. + return false; + } + + if (NeedOven && !Find(from, m_Ovens)) + { + message = 1044493; // You must be near an oven to bake that. + return false; + } + + if (NeedMill && !Find(from, m_Mills)) + { + message = 1044491; // You must be near a flour mill to do that. + return false; + } + + Type[][] types = new Type[Resources.Count][]; + int[] amounts = new int[Resources.Count]; + + maxAmount = int.MaxValue; + + CraftSubResCol resCol = UseSubRes2 ? craftSystem.CraftSubRes2 : craftSystem.CraftSubRes; + + for (int i = 0; i < types.Length; ++i) + { + CraftRes craftRes = Resources.GetAt(i); + Type baseType = craftRes.ItemType; + + // Resource Mutation + if (baseType == resCol.ResType && typeRes != null) + { + baseType = typeRes; + + CraftSubRes subResource = resCol.SearchFor(baseType); + + if (subResource != null && from.Skills[craftSystem.MainSkill].Base < subResource.RequiredSkill) + { + message = subResource.Message; + return false; + } + } + // ****************** + + for (int j = 0; types[i] == null && j < m_TypesTable.Length; ++j) + if (m_TypesTable[j][0] == baseType) + types[i] = m_TypesTable[j]; + + if (types[i] == null) + types[i] = new[] { baseType }; + + amounts[i] = craftRes.Amount; + + // For stackable items that can ben crafted more than one at a time + if (UseAllRes) + { + int tempAmount = ourPack.GetAmount(types[i]); + tempAmount /= amounts[i]; + if (tempAmount < maxAmount) + { + maxAmount = tempAmount; + + if (maxAmount == 0) + { + CraftRes res = Resources.GetAt(i); + + if (res.MessageNumber > 0) + message = res.MessageNumber; + else if (!string.IsNullOrEmpty(res.MessageString)) + message = res.MessageString; + else + message = 502925; // You don't have the resources required to make that item. + + return false; + } + } + } + // **************************** + + if (isFailure && !craftSystem.ConsumeOnFailure(from, types[i][0], this)) + amounts[i] = 0; + } + + // We adjust the amount of each resource to consume the max possible + if (UseAllRes) + for (int i = 0; i < amounts.Length; ++i) + amounts[i] *= maxAmount; + else + maxAmount = -1; + + Item consumeExtra = null; + + if (NameNumber == 1041267) + { + // Runebooks are a special case, they need a blank recall rune + + List runes = ourPack.FindItemsByType(); + + for (int i = 0; i < runes.Count; ++i) + { + RecallRune rune = runes[i]; + + if (rune != null && !rune.Marked) + { + consumeExtra = rune; + break; + } + } + + if (consumeExtra == null) + { + message = 1044253; // You don't have the components needed to make that. + return false; + } + } + + int index = 0; + + // Consume ALL + if (consumeType == ConsumeType.All) + { + m_ResHue = 0; + m_ResAmount = 0; + m_System = craftSystem; + + if (IsQuantityType(types)) + index = ConsumeQuantity(ourPack, types, amounts); + else + index = ourPack.ConsumeTotalGrouped(types, amounts, true, OnResourceConsumed, CheckHueGrouping); + + resHue = m_ResHue; + } + + // Consume Half ( for use all resource craft type ) + else if (consumeType == ConsumeType.Half) + { + for (int i = 0; i < amounts.Length; i++) + { + amounts[i] /= 2; + + if (amounts[i] < 1) + amounts[i] = 1; + } + + m_ResHue = 0; + m_ResAmount = 0; + m_System = craftSystem; + + if (IsQuantityType(types)) + index = ConsumeQuantity(ourPack, types, amounts); + else + index = ourPack.ConsumeTotalGrouped(types, amounts, true, OnResourceConsumed, CheckHueGrouping); + + resHue = m_ResHue; + } + + else // ConstumeType.None ( it's basically used to know if the crafter has enough resource before starting the process ) + { + index = -1; + + // TODO: Optimize this + if (IsQuantityType(types)) + for (int i = 0; i < types.Length; i++) + if (GetQuantity(ourPack, types[i]) < amounts[i]) + { + index = i; + break; + } + else + { + for (int j = 0; j < types.Length; j++) + if (ourPack.GetBestGroupAmount(types[j], true, CheckHueGrouping) < amounts[j]) + { + index = j; + break; + } + } + } + + if (index == -1) + { + if (consumeType != ConsumeType.None) consumeExtra?.Delete(); + + return true; + } + + { + CraftRes res = Resources.GetAt(index); + + if (res.MessageNumber > 0) + message = res.MessageNumber; + else if (!string.IsNullOrEmpty(res.MessageString)) + message = res.MessageString; + else + message = 502925; // You don't have the resources required to make that item. + + return false; + } + } + + private void OnResourceConsumed(Item item, int amount) + { + if (!RetainsColorFrom(m_System, item.GetType())) + return; + + if (amount >= m_ResAmount) + { + m_ResHue = item.Hue; + m_ResAmount = amount; + } + } + + private int CheckHueGrouping(Item a, Item b) + { + return b.Hue.CompareTo(a.Hue); + } + + public double GetExceptionalChance(CraftSystem system, double chance, Mobile from) + { + if (ForceNonExceptional) + return 0.0; + + double bonus = 0.0; + + if (from.Talisman is BaseTalisman talisman && talisman.Skill == system.MainSkill) + { + chance -= talisman.SuccessBonus / 100.0; + bonus = talisman.ExceptionalBonus / 100.0; + } + + switch (system.ECA) + { + default: + chance -= 0.6; + break; + case CraftECA.FiftyPercentChanceMinusTenPercent: + chance = chance * 0.5 - 0.1; + break; + case CraftECA.ChanceMinusSixtyToFourtyFive: + { + double offset = 0.60 - (from.Skills[system.MainSkill].Value - 95.0) * 0.03; + + if (offset < 0.45) + offset = 0.45; + else if (offset > 0.60) + offset = 0.60; + + chance -= offset; + break; + } + } + + if (chance > 0) + return chance + bonus; + + return chance; + } + + public bool CheckSkills(Mobile from, Type typeRes, CraftSystem craftSystem, ref int quality, + ref bool allRequiredSkills) + { + return CheckSkills(from, typeRes, craftSystem, ref quality, ref allRequiredSkills, true); + } + + public bool CheckSkills(Mobile from, Type typeRes, CraftSystem craftSystem, ref int quality, + ref bool allRequiredSkills, bool gainSkills) + { + double chance = GetSuccessChance(from, typeRes, craftSystem, gainSkills, ref allRequiredSkills); + + if (GetExceptionalChance(craftSystem, chance, from) > Utility.RandomDouble()) + quality = 2; + + return chance > Utility.RandomDouble(); + } + + public double GetSuccessChance(Mobile from, Type typeRes, CraftSystem craftSystem, bool gainSkills, + ref bool allRequiredSkills) + { + double minMainSkill = 0.0; + double maxMainSkill = 0.0; + double valMainSkill = 0.0; + + allRequiredSkills = true; + + for (int i = 0; i < Skills.Count; i++) + { + CraftSkill craftSkill = Skills.GetAt(i); + + double minSkill = craftSkill.MinSkill; + double maxSkill = craftSkill.MaxSkill; + double valSkill = from.Skills[craftSkill.SkillToMake].Value; + + if (valSkill < minSkill) + allRequiredSkills = false; + + if (craftSkill.SkillToMake == craftSystem.MainSkill) + { + minMainSkill = minSkill; + maxMainSkill = maxSkill; + valMainSkill = valSkill; + } + + if (gainSkills) // This is a passive check. Success chance is entirely dependant on the main skill + from.CheckSkill(craftSkill.SkillToMake, minSkill, maxSkill); + } + + double chance; + + if (allRequiredSkills) + chance = craftSystem.GetChanceAtMin(this) + (valMainSkill - minMainSkill) / (maxMainSkill - minMainSkill) * + (1.0 - craftSystem.GetChanceAtMin(this)); + else + chance = 0.0; + + if (allRequiredSkills && from.Talisman is BaseTalisman talisman && talisman.Skill == craftSystem.MainSkill) + chance += talisman.SuccessBonus / 100.0; + + if (allRequiredSkills && valMainSkill == maxMainSkill) + chance = 1.0; + + return chance; + } + + public void Craft(Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool) + { + if (from.BeginAction(typeof(CraftSystem))) + { + if (RequiredExpansion == Expansion.None || + from.NetState != null && from.NetState.SupportsExpansion(RequiredExpansion)) + { + bool allRequiredSkills = true; + double chance = GetSuccessChance(from, typeRes, craftSystem, false, ref allRequiredSkills); + + if (allRequiredSkills && chance >= 0.0) + { + if (Recipe == null || !(from is PlayerMobile) || ((PlayerMobile)from).HasRecipe(Recipe)) + { + int badCraft = craftSystem.CanCraft(from, tool, ItemType); + + if (badCraft <= 0) + { + int resHue = 0; + int maxAmount = 0; + object message = null; + + if (ConsumeRes(from, typeRes, craftSystem, ref resHue, ref maxAmount, ConsumeType.None, + ref message)) + { + message = null; + + if (ConsumeAttributes(from, ref message, false)) + { + CraftContext context = craftSystem.GetContext(from); + + context?.OnMade(this); + + int iMin = craftSystem.MinCraftEffect; + int iMax = craftSystem.MaxCraftEffect - iMin + 1; + int iRandom = Utility.Random(iMax); + iRandom += iMin + 1; + new InternalTimer(from, craftSystem, this, typeRes, tool, iRandom).Start(); + } + else + { + from.EndAction(typeof(CraftSystem)); + from.SendGump(new CraftGump(from, craftSystem, tool, message)); + } + } + else + { + from.EndAction(typeof(CraftSystem)); + from.SendGump(new CraftGump(from, craftSystem, tool, message)); + } + } + else + { + from.EndAction(typeof(CraftSystem)); + from.SendGump(new CraftGump(from, craftSystem, tool, badCraft)); + } + } + else + { + from.EndAction(typeof(CraftSystem)); + from.SendGump(new CraftGump(from, craftSystem, tool, + 1072847)); // You must learn that recipe from a scroll. + } + } + else + { + from.EndAction(typeof(CraftSystem)); + from.SendGump(new CraftGump(from, craftSystem, tool, + 1044153)); // You don't have the required skills to attempt this item. + } + } + else + { + from.EndAction(typeof(CraftSystem)); + from.SendGump(new CraftGump(from, craftSystem, tool, + RequiredExpansionMessage(RequiredExpansion))); //The {0} expansion is required to attempt this item. + } + } + else + { + from.SendLocalizedMessage(500119); // You must wait to perform another action + } + } + + private object + RequiredExpansionMessage( + Expansion expansion) //Eventually convert to TextDefinition, but that requires that we convert all the gumps to ues it too. Not that it wouldn't be a bad idea. + { + switch (expansion) + { + case Expansion.SE: + return 1063307; // The "Samurai Empire" expansion is required to attempt this item. + case Expansion.ML: + return 1072650; // The "Mondain's Legacy" expansion is required to attempt this item. + default: + return + $"The \"{ExpansionInfo.GetInfo(expansion).Name}\" expansion is required to attempt this item."; + } + } + + public void CompleteCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, + BaseTool tool, CustomCraft customCraft) + { + int badCraft = craftSystem.CanCraft(from, tool, ItemType); + + if (badCraft > 0) + { + if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, badCraft)); + else + from.SendLocalizedMessage(badCraft); + + return; + } + + int checkResHue = 0, checkMaxAmount = 0; + object checkMessage = null; + + // Not enough resource to craft it + if (!(ConsumeRes(from, typeRes, craftSystem, ref checkResHue, ref checkMaxAmount, ConsumeType.None, + ref checkMessage) + && ConsumeAttributes(from, ref checkMessage, false))) + { + if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, checkMessage)); + else if (checkMessage is int messageInt && messageInt > 0) + from.SendLocalizedMessage(messageInt); + else + from.SendMessage(checkMessage.ToString()); + + return; + } + + bool toolBroken = false; + + int ignored = 1; + int endquality = 1; + + bool allRequiredSkills = true; + + if (CheckSkills(from, typeRes, craftSystem, ref ignored, ref allRequiredSkills)) + { + // Resource + int resHue = 0; + int maxAmount = 0; + + object message = null; + + // Not enough resource to craft it + if (!(ConsumeRes(from, typeRes, craftSystem, ref resHue, ref maxAmount, ConsumeType.All, ref message) + && ConsumeAttributes(from, ref message, true))) + { + if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, message)); + else if (message is int messageIn && messageIn > 0) + from.SendLocalizedMessage(messageIn); + else + from.SendMessage(message.ToString()); + + return; + } + + tool.UsesRemaining--; + + if (craftSystem is DefBlacksmithy) + if (from.FindItemOnLayer(Layer.OneHanded) is AncientSmithyHammer hammer && hammer != tool) + { + hammer.UsesRemaining--; + if (hammer.UsesRemaining < 1) + hammer.Delete(); + } + + if (tool.UsesRemaining < 1 && tool.BreakOnDepletion) + toolBroken = true; + + if (toolBroken) + tool.Delete(); + + int num = 0; + + Item item; + if (customCraft != null) + { + item = customCraft.CompleteCraft(out num); + } + else if (typeof(MapItem).IsAssignableFrom(ItemType) && from.Map != Map.Trammel && from.Map != Map.Felucca) + { + item = new IndecipherableMap(); + from.SendLocalizedMessage(1070800); // The map you create becomes mysteriously indecipherable. + } + else + { + item = Activator.CreateInstance(ItemType) as Item; + } + + if (item != null) + { + if (item is ICraftable craftable) + endquality = craftable.OnCraft(quality, makersMark, from, craftSystem, typeRes, tool, this, resHue); + else if (item.Hue == 0) + item.Hue = resHue; + + if (maxAmount > 0) + { + if (!item.Stackable && item is IUsesRemaining remaining) + remaining.UsesRemaining *= maxAmount; + else + item.Amount = maxAmount; + } + + from.AddToBackpack(item); + + if (from.AccessLevel > AccessLevel.Player) + CommandLogging.WriteLine(from, "Crafting {0} with craft system {1}", CommandLogging.Format(item), + craftSystem.GetType().Name); + + //from.PlaySound( 0x57 ); + } + + if (num == 0) + num = craftSystem.PlayEndingEffect(from, false, true, toolBroken, endquality, makersMark, this); + + bool queryFactionImbue = false; + int availableSilver = 0; + FactionItemDefinition def = null; + Faction faction = null; + + if (item is IFactionItem) + { + def = FactionItemDefinition.Identify(item); + + if (def != null) + { + faction = Faction.Find(from); + + if (faction != null) + { + Town town = Town.FromRegion(from.Region); + + if (town != null && town.Owner == faction) + { + Container pack = from.Backpack; + + if (pack != null) + { + availableSilver = pack.GetAmount(typeof(Silver)); + + if (availableSilver >= def.SilverCost) + queryFactionImbue = Faction.IsNearType(from, def.VendorType, 12); + } + } + } + } + } + + // TODO: Scroll imbuing + + if (queryFactionImbue) + from.SendGump(new FactionImbueGump(quality, item, from, craftSystem, tool, num, availableSilver, faction, + def)); + else if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, num)); + else if (num > 0) + from.SendLocalizedMessage(num); + } + else if (!allRequiredSkills) + { + if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, 1044153)); + else + from.SendLocalizedMessage(1044153); // You don't have the required skills to attempt this item. + } + else + { + ConsumeType consumeType = UseAllRes ? ConsumeType.Half : ConsumeType.All; + int resHue = 0; + int maxAmount = 0; + + object message = null; + + // Not enough resource to craft it + if (!ConsumeRes(from, typeRes, craftSystem, ref resHue, ref maxAmount, consumeType, ref message, true)) + { + if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, message)); + else if (message is int messageInt && messageInt > 0) + from.SendLocalizedMessage(messageInt); + else + from.SendMessage(message.ToString()); + + return; + } + + tool.UsesRemaining--; + + if (tool.UsesRemaining < 1 && tool.BreakOnDepletion) + toolBroken = true; + + if (toolBroken) + tool.Delete(); + + // SkillCheck failed. + int num = craftSystem.PlayEndingEffect(from, true, true, toolBroken, endquality, false, this); + + if (!tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, craftSystem, tool, num)); + else if (num > 0) + from.SendLocalizedMessage(num); + } + } + + private class InternalTimer : Timer + { + private CraftItem m_CraftItem; + private CraftSystem m_CraftSystem; + private Mobile m_From; + private int m_iCount; + private int m_iCountMax; + private BaseTool m_Tool; + private Type m_TypeRes; + + public InternalTimer(Mobile from, CraftSystem craftSystem, CraftItem craftItem, Type typeRes, BaseTool tool, + int iCountMax) : base(TimeSpan.Zero, TimeSpan.FromSeconds(craftSystem.Delay), iCountMax) + { + m_From = from; + m_CraftItem = craftItem; + m_iCount = 0; + m_iCountMax = iCountMax; + m_CraftSystem = craftSystem; + m_TypeRes = typeRes; + m_Tool = tool; + } + + protected override void OnTick() + { + m_iCount++; + + m_From.DisruptiveAction(); + + if (m_iCount < m_iCountMax) + { + m_CraftSystem.PlayCraftEffect(m_From); + } + else + { + m_From.EndAction(typeof(CraftSystem)); + + int badCraft = m_CraftSystem.CanCraft(m_From, m_Tool, m_CraftItem.ItemType); + + if (badCraft > 0) + { + if (m_Tool != null && !m_Tool.Deleted && m_Tool.UsesRemaining > 0) + m_From.SendGump(new CraftGump(m_From, m_CraftSystem, m_Tool, badCraft)); + else + m_From.SendLocalizedMessage(badCraft); + + return; + } + + int quality = 1; + bool allRequiredSkills = true; + + m_CraftItem.CheckSkills(m_From, m_TypeRes, m_CraftSystem, ref quality, ref allRequiredSkills, false); + + CraftContext context = m_CraftSystem.GetContext(m_From); + + if (context == null) + return; + + if (typeof(CustomCraft).IsAssignableFrom(m_CraftItem.ItemType)) + { + CustomCraft cc = null; + + try + { + cc = Activator.CreateInstance(m_CraftItem.ItemType, m_From, m_CraftItem, m_CraftSystem, + m_TypeRes, m_Tool, quality) as CustomCraft; + } + catch + { + // ignored + } + + cc?.EndCraftAction(); + + return; + } + + bool makersMark = false; + + if (quality == 2 && m_From.Skills[m_CraftSystem.MainSkill].Base >= 100.0) + makersMark = m_CraftItem.IsMarkable(m_CraftItem.ItemType); + + if (makersMark && context.MarkOption == CraftMarkOption.PromptForMark) + { + m_From.SendGump(new QueryMakersMarkGump(quality, m_From, m_CraftItem, m_CraftSystem, m_TypeRes, + m_Tool)); + } + else + { + if (context.MarkOption == CraftMarkOption.DoNotMark) + makersMark = false; + + m_CraftItem.CompleteCraft(quality, makersMark, m_From, m_CraftSystem, m_TypeRes, m_Tool, null); + } + } + } + } + + #region Tables + + private static int[] m_HeatSources = + { + 0x461, 0x48E, // Sandstone oven/fireplace + 0x92B, 0x96C, // Stone oven/fireplace + 0xDE3, 0xDE9, // Campfire + 0xFAC, 0xFAC, // Firepit + 0x184A, 0x184C, // Heating stand (left) + 0x184E, 0x1850, // Heating stand (right) + 0x398C, 0x399F, // Fire field + 0x2DDB, 0x2DDC, //Elven stove + 0x19AA, 0x19BB, // Veteran Reward Brazier + 0x197A, 0x19A9, // Large Forge + 0x0FB1, 0x0FB1, // Small Forge + 0x2DD8, 0x2DD8 // Elven Forge + }; + + private static int[] m_Ovens = + { + 0x461, 0x46F, // Sandstone oven + 0x92B, 0x93F, // Stone oven + 0x2DDB, 0x2DDC //Elven stove + }; + + private static int[] m_Mills = + { + 0x1920, 0x1921, 0x1922, 0x1923, 0x1924, 0x1295, 0x1926, 0x1928, + 0x192C, 0x192D, 0x192E, 0x129F, 0x1930, 0x1931, 0x1932, 0x1934 + }; + + private static Type[][] m_TypesTable = + { + new[] { typeof(Log), typeof(Board) }, + new[] { typeof(HeartwoodLog), typeof(HeartwoodBoard) }, + new[] { typeof(BloodwoodLog), typeof(BloodwoodBoard) }, + new[] { typeof(FrostwoodLog), typeof(FrostwoodBoard) }, + new[] { typeof(OakLog), typeof(OakBoard) }, + new[] { typeof(AshLog), typeof(AshBoard) }, + new[] { typeof(YewLog), typeof(YewBoard) }, + new[] { typeof(Leather), typeof(Hides) }, + new[] { typeof(SpinedLeather), typeof(SpinedHides) }, + new[] { typeof(HornedLeather), typeof(HornedHides) }, + new[] { typeof(BarbedLeather), typeof(BarbedHides) }, + new[] { typeof(BlankMap), typeof(BlankScroll) }, + new[] { typeof(Cloth), typeof(UncutCloth) }, + new[] { typeof(CheeseWheel), typeof(CheeseWedge) }, + new[] { typeof(Pumpkin), typeof(SmallPumpkin) }, + new[] { typeof(WoodenBowlOfPeas), typeof(PewterBowlOfPeas) } + }; + + private static Type[] m_ColoredItemTable = + { + typeof(BaseWeapon), typeof(BaseArmor), typeof(BaseClothing), + typeof(BaseJewel), typeof(DragonBardingDeed) + }; + + private static Type[] m_ColoredResourceTable = + { + typeof(BaseIngot), typeof(BaseOre), + typeof(BaseLeather), typeof(BaseHides), + typeof(UncutCloth), typeof(Cloth), + typeof(BaseGranite), typeof(BaseScales) + }; + + private static Type[] m_MarkableTable = + { + typeof(BaseArmor), + typeof(BaseWeapon), + typeof(BaseClothing), + typeof(BaseInstrument), + typeof(DragonBardingDeed), + typeof(BaseTool), + typeof(BaseHarvestTool), + typeof(FukiyaDarts), typeof(Shuriken), + typeof(Spellbook), typeof(Runebook), + typeof(BaseQuiver) + }; + + private static Type[] m_NeverColorTable = + { + typeof(OrcHelm) + }; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftItemCol.cs b/Scripts/Engines/Craft/Core/CraftItemCol.cs index 44e8fe835..b9eebad2d 100644 --- a/Scripts/Engines/Craft/Core/CraftItemCol.cs +++ b/Scripts/Engines/Craft/Core/CraftItemCol.cs @@ -1,58 +1,53 @@ using System; +using System.Collections; namespace Server.Engines.Craft { - public class CraftItemCol : System.Collections.CollectionBase - { - public CraftItemCol() - { - } + public class CraftItemCol : CollectionBase + { + public int Add(CraftItem craftItem) + { + return List.Add(craftItem); + } - public int Add( CraftItem craftItem ) - { - return List.Add( craftItem ); - } + public void Remove(int index) + { + if (index > Count - 1 || index < 0) + { + } + else + { + List.RemoveAt(index); + } + } - public void Remove( int index ) - { - if ( index > Count - 1 || index < 0 ) - { - } - else - { - List.RemoveAt( index ); - } - } + public CraftItem GetAt(int index) + { + return (CraftItem)List[index]; + } - public CraftItem GetAt( int index ) - { - return ( CraftItem ) List[index]; - } + public CraftItem SearchForSubclass(Type type) + { + for (int i = 0; i < List.Count; i++) + { + CraftItem craftItem = (CraftItem)List[i]; - public CraftItem SearchForSubclass( Type type ) - { - for ( int i = 0; i < List.Count; i++ ) - { - CraftItem craftItem = ( CraftItem )List[i]; + if (craftItem.ItemType == type || type.IsSubclassOf(craftItem.ItemType)) + return craftItem; + } - if ( craftItem.ItemType == type || type.IsSubclassOf( craftItem.ItemType ) ) - return craftItem; - } + return null; + } - return null; - } + public CraftItem SearchFor(Type type) + { + for (int i = 0; i < List.Count; i++) + { + CraftItem craftItem = (CraftItem)List[i]; + if (craftItem.ItemType == type) return craftItem; + } - public CraftItem SearchFor( Type type ) - { - for ( int i = 0; i < List.Count; i++ ) - { - CraftItem craftItem = ( CraftItem )List[i]; - if ( craftItem.ItemType == type ) - { - return craftItem; - } - } - return null; - } - } + return null; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftItemIDAttribute.cs b/Scripts/Engines/Craft/Core/CraftItemIDAttribute.cs index 7e8cc0d18..0e336ce1b 100644 --- a/Scripts/Engines/Craft/Core/CraftItemIDAttribute.cs +++ b/Scripts/Engines/Craft/Core/CraftItemIDAttribute.cs @@ -2,14 +2,14 @@ using System; namespace Server.Engines.Craft { - [AttributeUsage( AttributeTargets.Class )] - public class CraftItemIDAttribute : Attribute - { - public int ItemID { get; } + [AttributeUsage(AttributeTargets.Class)] + public class CraftItemIDAttribute : Attribute + { + public CraftItemIDAttribute(int itemID) + { + ItemID = itemID; + } - public CraftItemIDAttribute( int itemID ) - { - ItemID = itemID; - } - } + public int ItemID{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftRes.cs b/Scripts/Engines/Craft/Core/CraftRes.cs index f6588d846..6e2c53294 100644 --- a/Scripts/Engines/Craft/Core/CraftRes.cs +++ b/Scripts/Engines/Craft/Core/CraftRes.cs @@ -2,43 +2,43 @@ using System; namespace Server.Engines.Craft { - public class CraftRes - { - public CraftRes( Type type, int amount ) - { - ItemType = type; - Amount = amount; - } + public class CraftRes + { + public CraftRes(Type type, int amount) + { + ItemType = type; + Amount = amount; + } - public CraftRes( Type type, TextDefinition name, int amount, TextDefinition message ): this ( type, amount ) - { - NameNumber = name; - MessageNumber = message; + public CraftRes(Type type, TextDefinition name, int amount, TextDefinition message) : this(type, amount) + { + NameNumber = name; + MessageNumber = message; - NameString = name; - MessageString = message; - } + NameString = name; + MessageString = message; + } - public void SendMessage( Mobile from ) - { - if ( MessageNumber > 0 ) - from.SendLocalizedMessage( MessageNumber ); - else if ( !string.IsNullOrEmpty( MessageString ) ) - from.SendMessage( MessageString ); - else - from.SendLocalizedMessage( 502925 ); // You don't have the resources required to make that item. - } + public Type ItemType{ get; } - public Type ItemType { get; } + public string MessageString{ get; } - public string MessageString { get; } + public int MessageNumber{ get; } - public int MessageNumber { get; } + public string NameString{ get; } - public string NameString { get; } + public int NameNumber{ get; } - public int NameNumber { get; } + public int Amount{ get; } - public int Amount { get; } - } -} + public void SendMessage(Mobile from) + { + if (MessageNumber > 0) + from.SendLocalizedMessage(MessageNumber); + else if (!string.IsNullOrEmpty(MessageString)) + from.SendMessage(MessageString); + else + from.SendLocalizedMessage(502925); // You don't have the resources required to make that item. + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftResCol.cs b/Scripts/Engines/Craft/Core/CraftResCol.cs index dd882d24c..ee49696c4 100644 --- a/Scripts/Engines/Craft/Core/CraftResCol.cs +++ b/Scripts/Engines/Craft/Core/CraftResCol.cs @@ -1,30 +1,28 @@ +using System.Collections; + namespace Server.Engines.Craft { - public class CraftResCol : System.Collections.CollectionBase - { - public CraftResCol() - { - } + public class CraftResCol : CollectionBase + { + public void Add(CraftRes craftRes) + { + List.Add(craftRes); + } - public void Add( CraftRes craftRes ) - { - List.Add( craftRes ); - } + public void Remove(int index) + { + if (index > Count - 1 || index < 0) + { + } + else + { + List.RemoveAt(index); + } + } - public void Remove( int index ) - { - if ( index > Count - 1 || index < 0 ) - { - } - else - { - List.RemoveAt( index ); - } - } - - public CraftRes GetAt( int index ) - { - return ( CraftRes ) List[index]; - } - } + public CraftRes GetAt(int index) + { + return (CraftRes)List[index]; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftSkill.cs b/Scripts/Engines/Craft/Core/CraftSkill.cs index 54b0e0a71..5fa2fbb2b 100644 --- a/Scripts/Engines/Craft/Core/CraftSkill.cs +++ b/Scripts/Engines/Craft/Core/CraftSkill.cs @@ -1,18 +1,18 @@ namespace Server.Engines.Craft { - public class CraftSkill - { - public CraftSkill( SkillName skillToMake, double minSkill, double maxSkill ) - { - SkillToMake = skillToMake; - MinSkill = minSkill; - MaxSkill = maxSkill; - } + public class CraftSkill + { + public CraftSkill(SkillName skillToMake, double minSkill, double maxSkill) + { + SkillToMake = skillToMake; + MinSkill = minSkill; + MaxSkill = maxSkill; + } - public SkillName SkillToMake { get; } + public SkillName SkillToMake{ get; } - public double MinSkill { get; } + public double MinSkill{ get; } - public double MaxSkill { get; } - } + public double MaxSkill{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftSkillCol.cs b/Scripts/Engines/Craft/Core/CraftSkillCol.cs index 9ee8fcdce..ffc23c919 100644 --- a/Scripts/Engines/Craft/Core/CraftSkillCol.cs +++ b/Scripts/Engines/Craft/Core/CraftSkillCol.cs @@ -1,30 +1,28 @@ +using System.Collections; + namespace Server.Engines.Craft { - public class CraftSkillCol : System.Collections.CollectionBase - { - public CraftSkillCol() - { - } + public class CraftSkillCol : CollectionBase + { + public void Add(CraftSkill craftSkill) + { + List.Add(craftSkill); + } - public void Add( CraftSkill craftSkill ) - { - List.Add( craftSkill ); - } + public void Remove(int index) + { + if (index > Count - 1 || index < 0) + { + } + else + { + List.RemoveAt(index); + } + } - public void Remove( int index ) - { - if ( index > Count - 1 || index < 0 ) - { - } - else - { - List.RemoveAt( index ); - } - } - - public CraftSkill GetAt( int index ) - { - return ( CraftSkill ) List[index]; - } - } + public CraftSkill GetAt(int index) + { + return (CraftSkill)List[index]; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftSubRes.cs b/Scripts/Engines/Craft/Core/CraftSubRes.cs index 4519b8ac3..5c1191853 100644 --- a/Scripts/Engines/Craft/Core/CraftSubRes.cs +++ b/Scripts/Engines/Craft/Core/CraftSubRes.cs @@ -2,32 +2,33 @@ using System; namespace Server.Engines.Craft { - public class CraftSubRes - { - public CraftSubRes( Type type, TextDefinition name, double reqSkill, object message ) : this( type, name, reqSkill, 0, message ) - { - } + public class CraftSubRes + { + public CraftSubRes(Type type, TextDefinition name, double reqSkill, object message) : this(type, name, reqSkill, 0, + message) + { + } - public CraftSubRes( Type type, TextDefinition name, double reqSkill, int genericNameNumber, object message ) - { - ItemType = type; - NameNumber = name; - NameString = name; - RequiredSkill = reqSkill; - GenericNameNumber = genericNameNumber; - Message = message; - } + public CraftSubRes(Type type, TextDefinition name, double reqSkill, int genericNameNumber, object message) + { + ItemType = type; + NameNumber = name; + NameString = name; + RequiredSkill = reqSkill; + GenericNameNumber = genericNameNumber; + Message = message; + } - public Type ItemType { get; } + public Type ItemType{ get; } - public string NameString { get; } + public string NameString{ get; } - public int NameNumber { get; } + public int NameNumber{ get; } - public int GenericNameNumber { get; } + public int GenericNameNumber{ get; } - public object Message { get; } + public object Message{ get; } - public double RequiredSkill { get; } - } + public double RequiredSkill{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftSubResCol.cs b/Scripts/Engines/Craft/Core/CraftSubResCol.cs index 579e38f6b..aea002dd1 100644 --- a/Scripts/Engines/Craft/Core/CraftSubResCol.cs +++ b/Scripts/Engines/Craft/Core/CraftSubResCol.cs @@ -1,54 +1,53 @@ using System; +using System.Collections; namespace Server.Engines.Craft { - public class CraftSubResCol : System.Collections.CollectionBase - { - public bool Init { get; set; } + public class CraftSubResCol : CollectionBase + { + public CraftSubResCol() + { + Init = false; + } - public Type ResType { get; set; } + public bool Init{ get; set; } - public string NameString { get; set; } + public Type ResType{ get; set; } - public int NameNumber { get; set; } + public string NameString{ get; set; } - public CraftSubResCol() - { - Init = false; - } + public int NameNumber{ get; set; } - public void Add( CraftSubRes craftSubRes ) - { - List.Add( craftSubRes ); - } + public void Add(CraftSubRes craftSubRes) + { + List.Add(craftSubRes); + } - public void Remove( int index ) - { - if ( index > Count - 1 || index < 0 ) - { - } - else - { - List.RemoveAt( index ); - } - } + public void Remove(int index) + { + if (index > Count - 1 || index < 0) + { + } + else + { + List.RemoveAt(index); + } + } - public CraftSubRes GetAt( int index ) - { - return ( CraftSubRes ) List[index]; - } + public CraftSubRes GetAt(int index) + { + return (CraftSubRes)List[index]; + } - public CraftSubRes SearchFor( Type type ) - { - for ( int i = 0; i < List.Count; i++ ) - { - CraftSubRes craftSubRes = ( CraftSubRes )List[i]; - if ( craftSubRes.ItemType == type ) - { - return craftSubRes; - } - } - return null; - } - } + public CraftSubRes SearchFor(Type type) + { + for (int i = 0; i < List.Count; i++) + { + CraftSubRes craftSubRes = (CraftSubRes)List[i]; + if (craftSubRes.ItemType == type) return craftSubRes; + } + + return null; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CraftSystem.cs b/Scripts/Engines/Craft/Core/CraftSystem.cs index 6929c45bc..74aa79d29 100644 --- a/Scripts/Engines/Craft/Core/CraftSystem.cs +++ b/Scripts/Engines/Craft/Core/CraftSystem.cs @@ -4,360 +4,359 @@ using Server.Items; namespace Server.Engines.Craft { - public enum CraftECA - { - ChanceMinusSixty, - FiftyPercentChanceMinusTenPercent, - ChanceMinusSixtyToFourtyFive - } + public enum CraftECA + { + ChanceMinusSixty, + FiftyPercentChanceMinusTenPercent, + ChanceMinusSixtyToFourtyFive + } - public abstract class CraftSystem - { - private List m_Recipes; - private List m_RareRecipes; + public abstract class CraftSystem + { + private Dictionary m_ContextTable = new Dictionary(); + private List m_RareRecipes; + private List m_Recipes; - public int MinCraftEffect { get; } + public CraftSystem(int minCraftEffect, int maxCraftEffect, double delay) + { + MinCraftEffect = minCraftEffect; + MaxCraftEffect = maxCraftEffect; + Delay = delay; - public int MaxCraftEffect { get; } + CraftItems = new CraftItemCol(); + CraftGroups = new CraftGroupCol(); + CraftSubRes = new CraftSubResCol(); + CraftSubRes2 = new CraftSubResCol(); - public double Delay { get; } + m_Recipes = new List(); + m_RareRecipes = new List(); - public CraftItemCol CraftItems { get; } + InitCraftList(); + } - public CraftGroupCol CraftGroups { get; } + public int MinCraftEffect{ get; } - public CraftSubResCol CraftSubRes { get; } + public int MaxCraftEffect{ get; } - public CraftSubResCol CraftSubRes2 { get; } + public double Delay{ get; } - public abstract SkillName MainSkill{ get; } + public CraftItemCol CraftItems{ get; } - public virtual int GumpTitleNumber => 0; - public virtual string GumpTitleString => ""; + public CraftGroupCol CraftGroups{ get; } - public virtual CraftECA ECA => CraftECA.ChanceMinusSixty; + public CraftSubResCol CraftSubRes{ get; } - private Dictionary m_ContextTable = new Dictionary(); + public CraftSubResCol CraftSubRes2{ get; } - public abstract double GetChanceAtMin( CraftItem item ); + public abstract SkillName MainSkill{ get; } - public virtual bool RetainsColorFrom( CraftItem item, Type type ) - { - return false; - } + public virtual int GumpTitleNumber => 0; + public virtual string GumpTitleString => ""; - public CraftContext GetContext( Mobile m ) - { - if ( m == null ) - return null; + public virtual CraftECA ECA => CraftECA.ChanceMinusSixty; - if ( m.Deleted ) - { - m_ContextTable.Remove( m ); - return null; - } + public bool Resmelt{ get; set; } - m_ContextTable.TryGetValue( m, out CraftContext c ); + public bool Repair{ get; set; } - if ( c == null ) - m_ContextTable[m] = c = new CraftContext(); + public bool MarkOption{ get; set; } - return c; - } + public bool CanEnhance{ get; set; } - public void OnMade( Mobile m, CraftItem item ) - { - CraftContext c = GetContext( m ); + public abstract double GetChanceAtMin(CraftItem item); - c?.OnMade( item ); - } + public virtual bool RetainsColorFrom(CraftItem item, Type type) + { + return false; + } - public bool Resmelt { get; set; } + public CraftContext GetContext(Mobile m) + { + if (m == null) + return null; - public bool Repair { get; set; } + if (m.Deleted) + { + m_ContextTable.Remove(m); + return null; + } - public bool MarkOption { get; set; } + m_ContextTable.TryGetValue(m, out CraftContext c); - public bool CanEnhance { get; set; } + if (c == null) + m_ContextTable[m] = c = new CraftContext(); - public CraftSystem( int minCraftEffect, int maxCraftEffect, double delay ) - { - MinCraftEffect = minCraftEffect; - MaxCraftEffect = maxCraftEffect; - Delay = delay; + return c; + } - CraftItems = new CraftItemCol(); - CraftGroups = new CraftGroupCol(); - CraftSubRes = new CraftSubResCol(); - CraftSubRes2 = new CraftSubResCol(); + public void OnMade(Mobile m, CraftItem item) + { + CraftContext c = GetContext(m); - m_Recipes = new List(); - m_RareRecipes = new List(); + c?.OnMade(item); + } - InitCraftList(); - } + public virtual bool ConsumeOnFailure(Mobile from, Type resourceType, CraftItem craftItem) + { + return true; + } - public virtual bool ConsumeOnFailure( Mobile from, Type resourceType, CraftItem craftItem ) - { - return true; - } + public void CreateItem(Mobile from, Type type, Type typeRes, BaseTool tool, CraftItem realCraftItem) + { + // Verify if the type is in the list of the craftable item + CraftItem craftItem = CraftItems.SearchFor(type); + if (craftItem != null) realCraftItem.Craft(from, this, typeRes, tool); + } - public void CreateItem( Mobile from, Type type, Type typeRes, BaseTool tool, CraftItem realCraftItem ) - { - // Verify if the type is in the list of the craftable item - CraftItem craftItem = CraftItems.SearchFor( type ); - if ( craftItem != null ) - { - // The item is in the list, try to create it - // Test code: items like sextant parts can be crafted either directly from ingots, or from different parts - realCraftItem.Craft( from, this, typeRes, tool ); - //craftItem.Craft( from, this, typeRes, tool ); - } - } + public int RandomRecipe() + { + if (m_Recipes.Count == 0) + return -1; - public int RandomRecipe() - { - if ( m_Recipes.Count == 0 ) - return -1; + return m_Recipes[Utility.Random(m_Recipes.Count)]; + } - return m_Recipes[Utility.Random( m_Recipes.Count )]; - } - - public int RandomRareRecipe() - { - if ( m_RareRecipes.Count == 0 ) - return -1; - - return m_RareRecipes[Utility.Random( m_RareRecipes.Count )]; - } - - - public int AddCraft( Type typeItem, TextDefinition group, TextDefinition name, double minSkill, double maxSkill, Type typeRes, TextDefinition nameRes, int amount ) - { - return AddCraft( typeItem, group, name, MainSkill, minSkill, maxSkill, typeRes, nameRes, amount, "" ); - } - - public int AddCraft( Type typeItem, TextDefinition group, TextDefinition name, double minSkill, double maxSkill, Type typeRes, TextDefinition nameRes, int amount, TextDefinition message ) - { - return AddCraft( typeItem, group, name, MainSkill, minSkill, maxSkill, typeRes, nameRes, amount, message ); - } - - public int AddCraft( Type typeItem, TextDefinition group, TextDefinition name, SkillName skillToMake, double minSkill, double maxSkill, Type typeRes, TextDefinition nameRes, int amount ) - { - return AddCraft( typeItem, group, name, skillToMake, minSkill, maxSkill, typeRes, nameRes, amount, "" ); - } - - public int AddCraft( Type typeItem, TextDefinition group, TextDefinition name, SkillName skillToMake, double minSkill, double maxSkill, Type typeRes, TextDefinition nameRes, int amount, TextDefinition message ) - { - CraftItem craftItem = new CraftItem( typeItem, group, name ); - craftItem.AddRes( typeRes, nameRes, amount, message ); - craftItem.AddSkill( skillToMake, minSkill, maxSkill ); - - DoGroup( group, craftItem ); - return CraftItems.Add( craftItem ); - } - - - private void DoGroup( TextDefinition groupName, CraftItem craftItem ) - { - int index = CraftGroups.SearchFor( groupName ); - - if ( index == -1) - { - CraftGroup craftGroup = new CraftGroup( groupName ); - craftGroup.AddCraftItem( craftItem ); - CraftGroups.Add( craftGroup ); - } - else - { - CraftGroups.GetAt( index ).AddCraftItem( craftItem ); - } - } - - - public void SetItemHue( int index, int hue ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.ItemHue = hue; - } - - public void SetManaReq( int index, int mana ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.Mana = mana; - } - - public void SetStamReq( int index, int stam ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.Stam = stam; - } - - public void SetHitsReq( int index, int hits ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.Hits = hits; - } - - public void SetUseAllRes( int index, bool useAll ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.UseAllRes = useAll; - } - - public void SetNeedHeat( int index, bool needHeat ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.NeedHeat = needHeat; - } - - public void SetNeedOven( int index, bool needOven ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.NeedOven = needOven; - } - - public void SetBeverageType( int index, BeverageType requiredBeverage ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.RequiredBeverage = requiredBeverage; - } - - public void SetNeedMill( int index, bool needMill ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.NeedMill = needMill; - } - - public void SetNeededExpansion( int index, Expansion expansion ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.RequiredExpansion = expansion; - } - - public void AddRes( int index, Type type, TextDefinition name, int amount ) - { - AddRes( index, type, name, amount, "" ); - } - - public void AddRes( int index, Type type, TextDefinition name, int amount, TextDefinition message ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.AddRes( type, name, amount, message ); - } - - public void AddSkill( int index, SkillName skillToMake, double minSkill, double maxSkill ) - { - CraftItem craftItem = CraftItems.GetAt(index); - craftItem.AddSkill(skillToMake, minSkill, maxSkill); - } - - public void SetUseSubRes2( int index, bool val ) - { - CraftItem craftItem = CraftItems.GetAt(index); - craftItem.UseSubRes2 = val; - } - - private void AddRecipeBase( int index, int id ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.AddRecipe( id, this ); - } - - public void AddRecipe( int index, int id ) - { - AddRecipeBase( index, id ); - m_Recipes.Add( id ); - } - - public void AddRareRecipe( int index, int id ) - { - AddRecipeBase( index, id ); - m_RareRecipes.Add( id ); - } - - public void AddQuestRecipe( int index, int id ) - { - AddRecipeBase( index, id ); - } - - public void ForceNonExceptional( int index ) - { - CraftItem craftItem = CraftItems.GetAt( index ); - craftItem.ForceNonExceptional = true; - } - - - public void SetSubRes( Type type, string name ) - { - CraftSubRes.ResType = type; - CraftSubRes.NameString = name; - CraftSubRes.Init = true; - } - - public void SetSubRes( Type type, int name ) - { - CraftSubRes.ResType = type; - CraftSubRes.NameNumber = name; - CraftSubRes.Init = true; - } - - public void AddSubRes( Type type, int name, double reqSkill, object message ) - { - CraftSubRes craftSubRes = new CraftSubRes( type, name, reqSkill, message ); - CraftSubRes.Add( craftSubRes ); - } - - public void AddSubRes( Type type, int name, double reqSkill, int genericName, object message ) - { - CraftSubRes craftSubRes = new CraftSubRes( type, name, reqSkill, genericName, message ); - CraftSubRes.Add( craftSubRes ); - } - - public void AddSubRes( Type type, string name, double reqSkill, object message ) - { - CraftSubRes craftSubRes = new CraftSubRes( type, name, reqSkill, message ); - CraftSubRes.Add( craftSubRes ); - } - - - public void SetSubRes2( Type type, string name ) - { - CraftSubRes2.ResType = type; - CraftSubRes2.NameString = name; - CraftSubRes2.Init = true; - } - - public void SetSubRes2( Type type, int name ) - { - CraftSubRes2.ResType = type; - CraftSubRes2.NameNumber = name; - CraftSubRes2.Init = true; - } - - public void AddSubRes2( Type type, int name, double reqSkill, object message ) - { - CraftSubRes craftSubRes = new CraftSubRes( type, name, reqSkill, message ); - CraftSubRes2.Add( craftSubRes ); - } - - public void AddSubRes2( Type type, int name, double reqSkill, int genericName, object message ) - { - CraftSubRes craftSubRes = new CraftSubRes( type, name, reqSkill, genericName, message ); - CraftSubRes2.Add( craftSubRes ); - } - - public void AddSubRes2( Type type, string name, double reqSkill, object message ) - { - CraftSubRes craftSubRes = new CraftSubRes( type, name, reqSkill, message ); - CraftSubRes2.Add( craftSubRes ); - } - - public abstract void InitCraftList(); - - public abstract void PlayCraftEffect( Mobile from ); - public abstract int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ); - - public abstract int CanCraft( Mobile from, BaseTool tool, Type itemType ); - } -} + public int RandomRareRecipe() + { + if (m_RareRecipes.Count == 0) + return -1; + + return m_RareRecipes[Utility.Random(m_RareRecipes.Count)]; + } + + + public int AddCraft(Type typeItem, TextDefinition group, TextDefinition name, double minSkill, double maxSkill, + Type typeRes, TextDefinition nameRes, int amount) + { + return AddCraft(typeItem, group, name, MainSkill, minSkill, maxSkill, typeRes, nameRes, amount, ""); + } + + public int AddCraft(Type typeItem, TextDefinition group, TextDefinition name, double minSkill, double maxSkill, + Type typeRes, TextDefinition nameRes, int amount, TextDefinition message) + { + return AddCraft(typeItem, group, name, MainSkill, minSkill, maxSkill, typeRes, nameRes, amount, message); + } + + public int AddCraft(Type typeItem, TextDefinition group, TextDefinition name, SkillName skillToMake, double minSkill, + double maxSkill, Type typeRes, TextDefinition nameRes, int amount) + { + return AddCraft(typeItem, group, name, skillToMake, minSkill, maxSkill, typeRes, nameRes, amount, ""); + } + + public int AddCraft(Type typeItem, TextDefinition group, TextDefinition name, SkillName skillToMake, double minSkill, + double maxSkill, Type typeRes, TextDefinition nameRes, int amount, TextDefinition message) + { + CraftItem craftItem = new CraftItem(typeItem, group, name); + craftItem.AddRes(typeRes, nameRes, amount, message); + craftItem.AddSkill(skillToMake, minSkill, maxSkill); + + DoGroup(group, craftItem); + return CraftItems.Add(craftItem); + } + + + private void DoGroup(TextDefinition groupName, CraftItem craftItem) + { + int index = CraftGroups.SearchFor(groupName); + + if (index == -1) + { + CraftGroup craftGroup = new CraftGroup(groupName); + craftGroup.AddCraftItem(craftItem); + CraftGroups.Add(craftGroup); + } + else + { + CraftGroups.GetAt(index).AddCraftItem(craftItem); + } + } + + + public void SetItemHue(int index, int hue) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.ItemHue = hue; + } + + public void SetManaReq(int index, int mana) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.Mana = mana; + } + + public void SetStamReq(int index, int stam) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.Stam = stam; + } + + public void SetHitsReq(int index, int hits) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.Hits = hits; + } + + public void SetUseAllRes(int index, bool useAll) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.UseAllRes = useAll; + } + + public void SetNeedHeat(int index, bool needHeat) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.NeedHeat = needHeat; + } + + public void SetNeedOven(int index, bool needOven) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.NeedOven = needOven; + } + + public void SetBeverageType(int index, BeverageType requiredBeverage) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.RequiredBeverage = requiredBeverage; + } + + public void SetNeedMill(int index, bool needMill) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.NeedMill = needMill; + } + + public void SetNeededExpansion(int index, Expansion expansion) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.RequiredExpansion = expansion; + } + + public void AddRes(int index, Type type, TextDefinition name, int amount) + { + AddRes(index, type, name, amount, ""); + } + + public void AddRes(int index, Type type, TextDefinition name, int amount, TextDefinition message) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.AddRes(type, name, amount, message); + } + + public void AddSkill(int index, SkillName skillToMake, double minSkill, double maxSkill) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.AddSkill(skillToMake, minSkill, maxSkill); + } + + public void SetUseSubRes2(int index, bool val) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.UseSubRes2 = val; + } + + private void AddRecipeBase(int index, int id) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.AddRecipe(id, this); + } + + public void AddRecipe(int index, int id) + { + AddRecipeBase(index, id); + m_Recipes.Add(id); + } + + public void AddRareRecipe(int index, int id) + { + AddRecipeBase(index, id); + m_RareRecipes.Add(id); + } + + public void AddQuestRecipe(int index, int id) + { + AddRecipeBase(index, id); + } + + public void ForceNonExceptional(int index) + { + CraftItem craftItem = CraftItems.GetAt(index); + craftItem.ForceNonExceptional = true; + } + + + public void SetSubRes(Type type, string name) + { + CraftSubRes.ResType = type; + CraftSubRes.NameString = name; + CraftSubRes.Init = true; + } + + public void SetSubRes(Type type, int name) + { + CraftSubRes.ResType = type; + CraftSubRes.NameNumber = name; + CraftSubRes.Init = true; + } + + public void AddSubRes(Type type, int name, double reqSkill, object message) + { + CraftSubRes craftSubRes = new CraftSubRes(type, name, reqSkill, message); + CraftSubRes.Add(craftSubRes); + } + + public void AddSubRes(Type type, int name, double reqSkill, int genericName, object message) + { + CraftSubRes craftSubRes = new CraftSubRes(type, name, reqSkill, genericName, message); + CraftSubRes.Add(craftSubRes); + } + + public void AddSubRes(Type type, string name, double reqSkill, object message) + { + CraftSubRes craftSubRes = new CraftSubRes(type, name, reqSkill, message); + CraftSubRes.Add(craftSubRes); + } + + + public void SetSubRes2(Type type, string name) + { + CraftSubRes2.ResType = type; + CraftSubRes2.NameString = name; + CraftSubRes2.Init = true; + } + + public void SetSubRes2(Type type, int name) + { + CraftSubRes2.ResType = type; + CraftSubRes2.NameNumber = name; + CraftSubRes2.Init = true; + } + + public void AddSubRes2(Type type, int name, double reqSkill, object message) + { + CraftSubRes craftSubRes = new CraftSubRes(type, name, reqSkill, message); + CraftSubRes2.Add(craftSubRes); + } + + public void AddSubRes2(Type type, int name, double reqSkill, int genericName, object message) + { + CraftSubRes craftSubRes = new CraftSubRes(type, name, reqSkill, genericName, message); + CraftSubRes2.Add(craftSubRes); + } + + public void AddSubRes2(Type type, string name, double reqSkill, object message) + { + CraftSubRes craftSubRes = new CraftSubRes(type, name, reqSkill, message); + CraftSubRes2.Add(craftSubRes); + } + + public abstract void InitCraftList(); + + public abstract void PlayCraftEffect(Mobile from); + + public abstract int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item); + + public abstract int CanCraft(Mobile from, BaseTool tool, Type itemType); + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/CustomCraft.cs b/Scripts/Engines/Craft/Core/CustomCraft.cs index a4892f2c8..656c6e3d1 100644 --- a/Scripts/Engines/Craft/Core/CustomCraft.cs +++ b/Scripts/Engines/Craft/Core/CustomCraft.cs @@ -3,31 +3,32 @@ using Server.Items; namespace Server.Engines.Craft { - public abstract class CustomCraft - { - public Mobile From { get; } + public abstract class CustomCraft + { + public CustomCraft(Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, + int quality) + { + From = from; + CraftItem = craftItem; + CraftSystem = craftSystem; + TypeRes = typeRes; + Tool = tool; + Quality = quality; + } - public CraftItem CraftItem { get; } + public Mobile From{ get; } - public CraftSystem CraftSystem { get; } + public CraftItem CraftItem{ get; } - public Type TypeRes { get; } + public CraftSystem CraftSystem{ get; } - public BaseTool Tool { get; } + public Type TypeRes{ get; } - public int Quality { get; } + public BaseTool Tool{ get; } - public CustomCraft( Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, int quality ) - { - From = from; - CraftItem = craftItem; - CraftSystem = craftSystem; - TypeRes = typeRes; - Tool = tool; - Quality = quality; - } + public int Quality{ get; } - public abstract void EndCraftAction(); - public abstract Item CompleteCraft( out int message ); - } + public abstract void EndCraftAction(); + public abstract Item CompleteCraft(out int message); + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/Enhance.cs b/Scripts/Engines/Craft/Core/Enhance.cs index 3feba96b0..7be1b7cfe 100644 --- a/Scripts/Engines/Craft/Core/Enhance.cs +++ b/Scripts/Engines/Craft/Core/Enhance.cs @@ -1,317 +1,340 @@ using System; -using Server.Targeting; using Server.Items; +using Server.Targeting; namespace Server.Engines.Craft { - public enum EnhanceResult - { - None, - NotInBackpack, - BadItem, - BadResource, - AlreadyEnhanced, - Success, - Failure, - Broken, - NoResources, - NoSkill - } + public enum EnhanceResult + { + None, + NotInBackpack, + BadItem, + BadResource, + AlreadyEnhanced, + Success, + Failure, + Broken, + NoResources, + NoSkill + } - public class Enhance - { - public static EnhanceResult Invoke( Mobile from, CraftSystem craftSystem, BaseTool tool, Item item, CraftResource resource, Type resType, ref object resMessage ) - { - if ( item == null ) - return EnhanceResult.BadItem; + public class Enhance + { + public static EnhanceResult Invoke(Mobile from, CraftSystem craftSystem, BaseTool tool, Item item, + CraftResource resource, Type resType, ref object resMessage) + { + if (item == null) + return EnhanceResult.BadItem; - if ( !item.IsChildOf( from.Backpack ) ) - return EnhanceResult.NotInBackpack; + if (!item.IsChildOf(from.Backpack)) + return EnhanceResult.NotInBackpack; - if ( !(item is BaseArmor) && !(item is BaseWeapon) ) - return EnhanceResult.BadItem; + if (!(item is BaseArmor) && !(item is BaseWeapon)) + return EnhanceResult.BadItem; - if ( item is IArcaneEquip eq && eq.IsArcane ) - return EnhanceResult.BadItem; + if (item is IArcaneEquip eq && eq.IsArcane) + return EnhanceResult.BadItem; - if ( CraftResources.IsStandard( resource ) ) - return EnhanceResult.BadResource; + if (CraftResources.IsStandard(resource)) + return EnhanceResult.BadResource; - int num = craftSystem.CanCraft( from, tool, item.GetType() ); + int num = craftSystem.CanCraft(from, tool, item.GetType()); - if ( num > 0 ) - { - resMessage = num; - return EnhanceResult.None; - } + if (num > 0) + { + resMessage = num; + return EnhanceResult.None; + } - CraftItem craftItem = craftSystem.CraftItems.SearchFor( item.GetType() ); + CraftItem craftItem = craftSystem.CraftItems.SearchFor(item.GetType()); - if ( craftItem == null || craftItem.Resources.Count == 0 ) - return EnhanceResult.BadItem; + if (craftItem == null || craftItem.Resources.Count == 0) + return EnhanceResult.BadItem; - bool allRequiredSkills = false; - if ( craftItem.GetSuccessChance( from, resType, craftSystem, false, ref allRequiredSkills ) <= 0.0 ) - return EnhanceResult.NoSkill; + bool allRequiredSkills = false; + if (craftItem.GetSuccessChance(from, resType, craftSystem, false, ref allRequiredSkills) <= 0.0) + return EnhanceResult.NoSkill; - CraftResourceInfo info = CraftResources.GetInfo( resource ); + CraftResourceInfo info = CraftResources.GetInfo(resource); - if ( info == null || info.ResourceTypes.Length == 0 ) - return EnhanceResult.BadResource; + if (info == null || info.ResourceTypes.Length == 0) + return EnhanceResult.BadResource; - CraftAttributeInfo attributes = info.AttributeInfo; + CraftAttributeInfo attributes = info.AttributeInfo; - if ( attributes == null ) - return EnhanceResult.BadResource; + if (attributes == null) + return EnhanceResult.BadResource; - int resHue = 0, maxAmount = 0; + int resHue = 0, maxAmount = 0; - if ( !craftItem.ConsumeRes( from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.None, ref resMessage ) ) - return EnhanceResult.NoResources; + if (!craftItem.ConsumeRes(from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.None, + ref resMessage)) + return EnhanceResult.NoResources; - if ( craftSystem is DefBlacksmithy ) - { - if ( from.FindItemOnLayer( Layer.OneHanded ) is AncientSmithyHammer hammer ) - { - hammer.UsesRemaining--; - if ( hammer.UsesRemaining < 1 ) - hammer.Delete(); - } - } + if (craftSystem is DefBlacksmithy) + if (from.FindItemOnLayer(Layer.OneHanded) is AncientSmithyHammer hammer) + { + hammer.UsesRemaining--; + if (hammer.UsesRemaining < 1) + hammer.Delete(); + } - int phys = 0, fire = 0, cold = 0, pois = 0, nrgy = 0; - int dura = 0, luck = 0, lreq = 0, dinc = 0; - int baseChance = 0; + int phys = 0, fire = 0, cold = 0, pois = 0, nrgy = 0; + int dura = 0, luck = 0, lreq = 0, dinc = 0; + int baseChance = 0; - bool physBonus = false; - bool fireBonus = false; - bool coldBonus = false; - bool nrgyBonus = false; - bool poisBonus = false; - bool duraBonus = false; - bool luckBonus = false; - bool lreqBonus = false; - bool dincBonus = false; + bool physBonus = false; + bool fireBonus = false; + bool coldBonus = false; + bool nrgyBonus = false; + bool poisBonus = false; + bool duraBonus = false; + bool luckBonus = false; + bool lreqBonus = false; + bool dincBonus = false; - if ( item is BaseWeapon weapon ) - { - if ( !CraftResources.IsStandard( weapon.Resource ) ) - return EnhanceResult.AlreadyEnhanced; + if (item is BaseWeapon weapon) + { + if (!CraftResources.IsStandard(weapon.Resource)) + return EnhanceResult.AlreadyEnhanced; - baseChance = 20; + baseChance = 20; - dura = weapon.MaxHitPoints; - luck = weapon.Attributes.Luck; - lreq = weapon.WeaponAttributes.LowerStatReq; - dinc = weapon.Attributes.WeaponDamage; + dura = weapon.MaxHitPoints; + luck = weapon.Attributes.Luck; + lreq = weapon.WeaponAttributes.LowerStatReq; + dinc = weapon.Attributes.WeaponDamage; - fireBonus = ( attributes.WeaponFireDamage > 0 ); - coldBonus = ( attributes.WeaponColdDamage > 0 ); - nrgyBonus = ( attributes.WeaponEnergyDamage > 0 ); - poisBonus = ( attributes.WeaponPoisonDamage > 0 ); + fireBonus = attributes.WeaponFireDamage > 0; + coldBonus = attributes.WeaponColdDamage > 0; + nrgyBonus = attributes.WeaponEnergyDamage > 0; + poisBonus = attributes.WeaponPoisonDamage > 0; - duraBonus = ( attributes.WeaponDurability > 0 ); - luckBonus = ( attributes.WeaponLuck > 0 ); - lreqBonus = ( attributes.WeaponLowerRequirements > 0 ); - dincBonus = ( dinc > 0 ); - } - else - { - BaseArmor armor = (BaseArmor)item; + duraBonus = attributes.WeaponDurability > 0; + luckBonus = attributes.WeaponLuck > 0; + lreqBonus = attributes.WeaponLowerRequirements > 0; + dincBonus = dinc > 0; + } + else + { + BaseArmor armor = (BaseArmor)item; - if ( !CraftResources.IsStandard( armor.Resource ) ) - return EnhanceResult.AlreadyEnhanced; + if (!CraftResources.IsStandard(armor.Resource)) + return EnhanceResult.AlreadyEnhanced; - baseChance = 20; + baseChance = 20; - phys = armor.PhysicalResistance; - fire = armor.FireResistance; - cold = armor.ColdResistance; - pois = armor.PoisonResistance; - nrgy = armor.EnergyResistance; + phys = armor.PhysicalResistance; + fire = armor.FireResistance; + cold = armor.ColdResistance; + pois = armor.PoisonResistance; + nrgy = armor.EnergyResistance; - dura = armor.MaxHitPoints; - luck = armor.Attributes.Luck; - lreq = armor.ArmorAttributes.LowerStatReq; + dura = armor.MaxHitPoints; + luck = armor.Attributes.Luck; + lreq = armor.ArmorAttributes.LowerStatReq; - physBonus = ( attributes.ArmorPhysicalResist > 0 ); - fireBonus = ( attributes.ArmorFireResist > 0 ); - coldBonus = ( attributes.ArmorColdResist > 0 ); - nrgyBonus = ( attributes.ArmorEnergyResist > 0 ); - poisBonus = ( attributes.ArmorPoisonResist > 0 ); + physBonus = attributes.ArmorPhysicalResist > 0; + fireBonus = attributes.ArmorFireResist > 0; + coldBonus = attributes.ArmorColdResist > 0; + nrgyBonus = attributes.ArmorEnergyResist > 0; + poisBonus = attributes.ArmorPoisonResist > 0; - duraBonus = ( attributes.ArmorDurability > 0 ); - luckBonus = ( attributes.ArmorLuck > 0 ); - lreqBonus = ( attributes.ArmorLowerRequirements > 0 ); - dincBonus = false; - } + duraBonus = attributes.ArmorDurability > 0; + luckBonus = attributes.ArmorLuck > 0; + lreqBonus = attributes.ArmorLowerRequirements > 0; + dincBonus = false; + } - int skill = from.Skills[craftSystem.MainSkill].Fixed / 10; + int skill = from.Skills[craftSystem.MainSkill].Fixed / 10; - if ( skill >= 100 ) - baseChance -= (skill - 90) / 10; + if (skill >= 100) + baseChance -= (skill - 90) / 10; - EnhanceResult res = EnhanceResult.Success; + EnhanceResult res = EnhanceResult.Success; - if ( physBonus ) - CheckResult( ref res, baseChance + phys ); + if (physBonus) + CheckResult(ref res, baseChance + phys); - if ( fireBonus ) - CheckResult( ref res, baseChance + fire ); + if (fireBonus) + CheckResult(ref res, baseChance + fire); - if ( coldBonus ) - CheckResult( ref res, baseChance + cold ); + if (coldBonus) + CheckResult(ref res, baseChance + cold); - if ( nrgyBonus ) - CheckResult( ref res, baseChance + nrgy ); + if (nrgyBonus) + CheckResult(ref res, baseChance + nrgy); - if ( poisBonus ) - CheckResult( ref res, baseChance + pois ); + if (poisBonus) + CheckResult(ref res, baseChance + pois); - if ( duraBonus ) - CheckResult( ref res, baseChance + (dura / 40) ); + if (duraBonus) + CheckResult(ref res, baseChance + dura / 40); - if ( luckBonus ) - CheckResult( ref res, baseChance + 10 + (luck / 2) ); + if (luckBonus) + CheckResult(ref res, baseChance + 10 + luck / 2); - if ( lreqBonus ) - CheckResult( ref res, baseChance + (lreq / 4) ); + if (lreqBonus) + CheckResult(ref res, baseChance + lreq / 4); - if ( dincBonus ) - CheckResult( ref res, baseChance + (dinc / 4) ); + if (dincBonus) + CheckResult(ref res, baseChance + dinc / 4); - switch ( res ) - { - case EnhanceResult.Broken: - { - if ( !craftItem.ConsumeRes( from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.Half, ref resMessage ) ) - return EnhanceResult.NoResources; + switch (res) + { + case EnhanceResult.Broken: + { + if (!craftItem.ConsumeRes(from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.Half, + ref resMessage)) + return EnhanceResult.NoResources; - item.Delete(); - break; - } - case EnhanceResult.Success: - { - if ( !craftItem.ConsumeRes( from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.All, ref resMessage ) ) - return EnhanceResult.NoResources; + item.Delete(); + break; + } + case EnhanceResult.Success: + { + if (!craftItem.ConsumeRes(from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.All, + ref resMessage)) + return EnhanceResult.NoResources; - if ( item is BaseWeapon w ) - { - w.Resource = resource; + if (item is BaseWeapon w) + { + w.Resource = resource; - int hue = w.GetElementalDamageHue(); - if ( hue > 0 ) - w.Hue = hue; - } - else - { - ((BaseArmor)item).Resource = resource; - } + int hue = w.GetElementalDamageHue(); + if (hue > 0) + w.Hue = hue; + } + else + { + ((BaseArmor)item).Resource = resource; + } - break; - } - case EnhanceResult.Failure: - { - if ( !craftItem.ConsumeRes( from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.Half, ref resMessage ) ) - return EnhanceResult.NoResources; + break; + } + case EnhanceResult.Failure: + { + if (!craftItem.ConsumeRes(from, resType, craftSystem, ref resHue, ref maxAmount, ConsumeType.Half, + ref resMessage)) + return EnhanceResult.NoResources; - break; - } - } + break; + } + } - return res; - } + return res; + } - public static void CheckResult( ref EnhanceResult res, int chance ) - { - if ( res != EnhanceResult.Success ) - return; // we've already failed.. + public static void CheckResult(ref EnhanceResult res, int chance) + { + if (res != EnhanceResult.Success) + return; // we've already failed.. - int random = Utility.Random( 100 ); + int random = Utility.Random(100); - if ( 10 > random ) - res = EnhanceResult.Failure; - else if ( chance > random ) - res = EnhanceResult.Broken; - } + if (10 > random) + res = EnhanceResult.Failure; + else if (chance > random) + res = EnhanceResult.Broken; + } - public static void BeginTarget( Mobile from, CraftSystem craftSystem, BaseTool tool ) - { - CraftContext context = craftSystem.GetContext( from ); + public static void BeginTarget(Mobile from, CraftSystem craftSystem, BaseTool tool) + { + CraftContext context = craftSystem.GetContext(from); - if ( context == null ) - return; + if (context == null) + return; - int lastRes = context.LastResourceIndex; - CraftSubResCol subRes = craftSystem.CraftSubRes; + int lastRes = context.LastResourceIndex; + CraftSubResCol subRes = craftSystem.CraftSubRes; - if ( lastRes >= 0 && lastRes < subRes.Count ) - { - CraftSubRes res = subRes.GetAt( lastRes ); + if (lastRes >= 0 && lastRes < subRes.Count) + { + CraftSubRes res = subRes.GetAt(lastRes); - if ( from.Skills[craftSystem.MainSkill].Value < res.RequiredSkill ) - { - from.SendGump( new CraftGump( from, craftSystem, tool, res.Message ) ); - } - else - { - CraftResource resource = CraftResources.GetFromType( res.ItemType ); + if (from.Skills[craftSystem.MainSkill].Value < res.RequiredSkill) + { + from.SendGump(new CraftGump(from, craftSystem, tool, res.Message)); + } + else + { + CraftResource resource = CraftResources.GetFromType(res.ItemType); - if ( resource != CraftResource.None ) - { - from.Target = new InternalTarget( craftSystem, tool, res.ItemType, resource ); - from.SendLocalizedMessage( 1061004 ); // Target an item to enhance with the properties of your selected material. - } - else - { - from.SendGump( new CraftGump( from, craftSystem, tool, 1061010 ) ); // You must select a special material in order to enhance an item with its properties. - } - } - } - else - { - from.SendGump( new CraftGump( from, craftSystem, tool, 1061010 ) ); // You must select a special material in order to enhance an item with its properties. - } + if (resource != CraftResource.None) + { + from.Target = new InternalTarget(craftSystem, tool, res.ItemType, resource); + from.SendLocalizedMessage( + 1061004); // Target an item to enhance with the properties of your selected material. + } + else + { + from.SendGump(new CraftGump(from, craftSystem, tool, + 1061010)); // You must select a special material in order to enhance an item with its properties. + } + } + } + else + { + from.SendGump(new CraftGump(from, craftSystem, tool, + 1061010)); // You must select a special material in order to enhance an item with its properties. + } + } - } + private class InternalTarget : Target + { + private CraftSystem m_CraftSystem; + private CraftResource m_Resource; + private Type m_ResourceType; + private BaseTool m_Tool; - private class InternalTarget : Target - { - private CraftSystem m_CraftSystem; - private BaseTool m_Tool; - private Type m_ResourceType; - private CraftResource m_Resource; + public InternalTarget(CraftSystem craftSystem, BaseTool tool, Type resourceType, CraftResource resource) : base( + 2, false, TargetFlags.None) + { + m_CraftSystem = craftSystem; + m_Tool = tool; + m_ResourceType = resourceType; + m_Resource = resource; + } - public InternalTarget( CraftSystem craftSystem, BaseTool tool, Type resourceType, CraftResource resource ) : base ( 2, false, TargetFlags.None ) - { - m_CraftSystem = craftSystem; - m_Tool = tool; - m_ResourceType = resourceType; - m_Resource = resource; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Item item) + { + object message = null; + EnhanceResult res = Enhance.Invoke(from, m_CraftSystem, m_Tool, item, m_Resource, m_ResourceType, + ref message); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Item item ) - { - object message = null; - EnhanceResult res = Enhance.Invoke( from, m_CraftSystem, m_Tool, item, m_Resource, m_ResourceType, ref message ); + switch (res) + { + case EnhanceResult.NotInBackpack: + message = 1061005; + break; // The item must be in your backpack to enhance it. + case EnhanceResult.AlreadyEnhanced: + message = 1061012; + break; // This item is already enhanced with the properties of a special material. + case EnhanceResult.BadItem: + message = 1061011; + break; // You cannot enhance this type of item with the properties of the selected special material. + case EnhanceResult.BadResource: + message = 1061010; + break; // You must select a special material in order to enhance an item with its properties. + case EnhanceResult.Broken: + message = 1061080; + break; // You attempt to enhance the item, but fail catastrophically. The item is lost. + case EnhanceResult.Failure: + message = 1061082; + break; // You attempt to enhance the item, but fail. Some material is lost in the process. + case EnhanceResult.Success: + message = 1061008; + break; // You enhance the item with the properties of the special material. + case EnhanceResult.NoSkill: + message = 1044153; + break; // You don't have the required skills to attempt this item. + } - switch ( res ) - { - case EnhanceResult.NotInBackpack: message = 1061005; break; // The item must be in your backpack to enhance it. - case EnhanceResult.AlreadyEnhanced: message = 1061012; break; // This item is already enhanced with the properties of a special material. - case EnhanceResult.BadItem: message = 1061011; break; // You cannot enhance this type of item with the properties of the selected special material. - case EnhanceResult.BadResource: message = 1061010; break; // You must select a special material in order to enhance an item with its properties. - case EnhanceResult.Broken: message = 1061080; break; // You attempt to enhance the item, but fail catastrophically. The item is lost. - case EnhanceResult.Failure: message = 1061082; break; // You attempt to enhance the item, but fail. Some material is lost in the process. - case EnhanceResult.Success: message = 1061008; break; // You enhance the item with the properties of the special material. - case EnhanceResult.NoSkill: message = 1044153; break; // You don't have the required skills to attempt this item. - } - - from.SendGump( new CraftGump( from, m_CraftSystem, m_Tool, message ) ); - } - } - } - } -} + from.SendGump(new CraftGump(from, m_CraftSystem, m_Tool, message)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/QueryMakersMarkGump.cs b/Scripts/Engines/Craft/Core/QueryMakersMarkGump.cs index 3643d75bb..3a76d1d0a 100644 --- a/Scripts/Engines/Craft/Core/QueryMakersMarkGump.cs +++ b/Scripts/Engines/Craft/Core/QueryMakersMarkGump.cs @@ -1,53 +1,55 @@ using System; using Server.Gumps; using Server.Items; +using Server.Network; namespace Server.Engines.Craft { - public class QueryMakersMarkGump : Gump - { - private int m_Quality; - private Mobile m_From; - private CraftItem m_CraftItem; - private CraftSystem m_CraftSystem; - private Type m_TypeRes; - private BaseTool m_Tool; + public class QueryMakersMarkGump : Gump + { + private CraftItem m_CraftItem; + private CraftSystem m_CraftSystem; + private Mobile m_From; + private int m_Quality; + private BaseTool m_Tool; + private Type m_TypeRes; - public QueryMakersMarkGump( int quality, Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool ) : base( 100, 200 ) - { - from.CloseGump( typeof( QueryMakersMarkGump ) ); + public QueryMakersMarkGump(int quality, Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, + BaseTool tool) : base(100, 200) + { + from.CloseGump(typeof(QueryMakersMarkGump)); - m_Quality = quality; - m_From = from; - m_CraftItem = craftItem; - m_CraftSystem = craftSystem; - m_TypeRes = typeRes; - m_Tool = tool; + m_Quality = quality; + m_From = from; + m_CraftItem = craftItem; + m_CraftSystem = craftSystem; + m_TypeRes = typeRes; + m_Tool = tool; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 220, 170, 5054 ); - AddBackground( 10, 10, 200, 150, 3000 ); + AddBackground(0, 0, 220, 170, 5054); + AddBackground(10, 10, 200, 150, 3000); - AddHtmlLocalized( 20, 20, 180, 80, 1018317, false, false ); // Do you wish to place your maker's mark on this item? + AddHtmlLocalized(20, 20, 180, 80, 1018317, false, false); // Do you wish to place your maker's mark on this item? - AddHtmlLocalized( 55, 100, 140, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 100, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 100, 140, 25, 1011011, false, false); // CONTINUE + AddButton(20, 100, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 125, 140, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 125, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(55, 125, 140, 25, 1011012, false, false); // CANCEL + AddButton(20, 125, 4005, 4007, 0, GumpButtonType.Reply, 0); + } - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - bool makersMark = ( info.ButtonID == 1 ); + public override void OnResponse(NetState sender, RelayInfo info) + { + bool makersMark = info.ButtonID == 1; - if ( makersMark ) - m_From.SendLocalizedMessage( 501808 ); // You mark the item. - else - m_From.SendLocalizedMessage( 501809 ); // Cancelled mark. + if (makersMark) + m_From.SendLocalizedMessage(501808); // You mark the item. + else + m_From.SendLocalizedMessage(501809); // Cancelled mark. - m_CraftItem.CompleteCraft( m_Quality, makersMark, m_From, m_CraftSystem, m_TypeRes, m_Tool, null ); - } - } + m_CraftItem.CompleteCraft(m_Quality, makersMark, m_From, m_CraftSystem, m_TypeRes, m_Tool, null); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/Recipes.cs b/Scripts/Engines/Craft/Core/Recipes.cs index 3d287b4c4..8ee5d1034 100644 --- a/Scripts/Engines/Craft/Core/Recipes.cs +++ b/Scripts/Engines/Craft/Core/Recipes.cs @@ -1,97 +1,99 @@ using System; using System.Collections.Generic; -using Server.Mobiles; using Server.Commands; +using Server.Mobiles; +using Server.Targeting; namespace Server.Engines.Craft { - public class Recipe - { - public static void Initialize() - { - CommandSystem.Register( "LearnAllRecipes", AccessLevel.GameMaster, LearnAllRecipes_OnCommand ); - CommandSystem.Register( "ForgetAllRecipes", AccessLevel.GameMaster, ForgetAllRecipes_OnCommand ); - } + public class Recipe + { + private TextDefinition m_TD; - [Usage( "LearnAllRecipes" )] - [Description( "Teaches a player all available recipes." )] - private static void LearnAllRecipes_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - m.SendMessage( "Target a player to teach them all of the recipies." ); + public Recipe(int id, CraftSystem system, CraftItem item) + { + ID = id; + CraftSystem = system; + CraftItem = item; - m.BeginTarget( -1, false, Targeting.TargetFlags.None, delegate( Mobile from, object targeted ) - { - if ( targeted is PlayerMobile mobile ) - { - foreach( KeyValuePair kvp in Recipes ) - mobile.AcquireRecipe( kvp.Key ); + if (Recipes.ContainsKey(id)) + throw new Exception("Attempting to create recipe with preexisting ID."); - m.SendMessage( "You teach them all of the recipies." ); - } - else - { - m.SendMessage( "That is not a player!" ); - } - } ); - } - - [Usage( "ForgetAllRecipes" )] - [Description( "Makes a player forget all the recipies they've learned." )] - private static void ForgetAllRecipes_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - m.SendMessage( "Target a player to have them forget all of the recipies they've learned." ); - - m.BeginTarget( -1, false, Targeting.TargetFlags.None, delegate( Mobile from, object targeted ) - { - if ( targeted is PlayerMobile mobile ) - { - mobile.ResetRecipes(); - - m.SendMessage( "They forget all their recipies." ); - } - else - { - m.SendMessage( "That is not a player!" ); - } - } ); - } + Recipes.Add(id, this); + LargestRecipeID = Math.Max(id, LargestRecipeID); + } - public static Dictionary Recipes { get; } = new Dictionary(); + public static Dictionary Recipes{ get; } = new Dictionary(); - public static int LargestRecipeID { get; private set; } + public static int LargestRecipeID{ get; private set; } - public CraftSystem CraftSystem { get; set; } + public CraftSystem CraftSystem{ get; set; } - public CraftItem CraftItem { get; set; } + public CraftItem CraftItem{ get; set; } - public int ID { get; } + public int ID{ get; } - private TextDefinition m_TD; - public TextDefinition TextDefinition - { - get - { - if ( m_TD == null ) - m_TD = new TextDefinition( CraftItem.NameNumber, CraftItem.NameString ); + public TextDefinition TextDefinition + { + get + { + if (m_TD == null) + m_TD = new TextDefinition(CraftItem.NameNumber, CraftItem.NameString); - return m_TD; - } - } + return m_TD; + } + } - public Recipe( int id, CraftSystem system, CraftItem item ) - { - ID = id; - CraftSystem = system; - CraftItem = item; + public static void Initialize() + { + CommandSystem.Register("LearnAllRecipes", AccessLevel.GameMaster, LearnAllRecipes_OnCommand); + CommandSystem.Register("ForgetAllRecipes", AccessLevel.GameMaster, ForgetAllRecipes_OnCommand); + } - if ( Recipes.ContainsKey( id ) ) - throw new Exception( "Attempting to create recipe with preexisting ID." ); + [Usage("LearnAllRecipes")] + [Description("Teaches a player all available recipes.")] + private static void LearnAllRecipes_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + m.SendMessage("Target a player to teach them all of the recipies."); - Recipes.Add( id, this ); - LargestRecipeID = Math.Max( id, LargestRecipeID ); - } - } -} + m.BeginTarget(-1, false, TargetFlags.None, delegate(Mobile from, object targeted) + { + if (targeted is PlayerMobile mobile) + { + foreach (KeyValuePair kvp in Recipes) + mobile.AcquireRecipe(kvp.Key); + + m.SendMessage("You teach them all of the recipies."); + } + else + { + m.SendMessage("That is not a player!"); + } + }); + } + + [Usage("ForgetAllRecipes")] + [Description("Makes a player forget all the recipies they've learned.")] + private static void ForgetAllRecipes_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + m.SendMessage("Target a player to have them forget all of the recipies they've learned."); + + m.BeginTarget(-1, false, TargetFlags.None, delegate(Mobile from, object targeted) + { + if (targeted is PlayerMobile mobile) + { + mobile.ResetRecipes(); + + m.SendMessage("They forget all their recipies."); + } + else + { + m.SendMessage("That is not a player!"); + } + }); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/Repair.cs b/Scripts/Engines/Craft/Core/Repair.cs index 95e055c7b..f71d91249 100644 --- a/Scripts/Engines/Craft/Core/Repair.cs +++ b/Scripts/Engines/Craft/Core/Repair.cs @@ -1,512 +1,523 @@ using System; +using Server.Items; using Server.Mobiles; using Server.Targeting; -using Server.Items; namespace Server.Engines.Craft { - public class Repair - { - public Repair() - { - } + public class Repair + { + public static void Do(Mobile from, CraftSystem craftSystem, BaseTool tool) + { + from.Target = new InternalTarget(craftSystem, tool); + from.SendLocalizedMessage(1044276); // Target an item to repair. + } - public static void Do( Mobile from, CraftSystem craftSystem, BaseTool tool ) - { - from.Target = new InternalTarget( craftSystem, tool ); - from.SendLocalizedMessage( 1044276 ); // Target an item to repair. - } + public static void Do(Mobile from, CraftSystem craftSystem, RepairDeed deed) + { + from.Target = new InternalTarget(craftSystem, deed); + from.SendLocalizedMessage(1044276); // Target an item to repair. + } - public static void Do( Mobile from, CraftSystem craftSystem, RepairDeed deed ) - { - from.Target = new InternalTarget( craftSystem, deed ); - from.SendLocalizedMessage( 1044276 ); // Target an item to repair. - } + private class InternalTarget : Target + { + private CraftSystem m_CraftSystem; + private RepairDeed m_Deed; + private BaseTool m_Tool; - private class InternalTarget : Target - { - private CraftSystem m_CraftSystem; - private BaseTool m_Tool; - private RepairDeed m_Deed; + public InternalTarget(CraftSystem craftSystem, BaseTool tool) : base(2, false, TargetFlags.None) + { + m_CraftSystem = craftSystem; + m_Tool = tool; + } - public InternalTarget( CraftSystem craftSystem, BaseTool tool ) : base ( 2, false, TargetFlags.None ) - { - m_CraftSystem = craftSystem; - m_Tool = tool; - } + public InternalTarget(CraftSystem craftSystem, RepairDeed deed) : base(2, false, TargetFlags.None) + { + m_CraftSystem = craftSystem; + m_Deed = deed; + } - public InternalTarget( CraftSystem craftSystem, RepairDeed deed ) : base( 2, false, TargetFlags.None ) - { - m_CraftSystem = craftSystem; - m_Deed = deed; - } + private static void EndGolemRepair(object state) + { + ((Mobile)state).EndAction(typeof(Golem)); + } - private static void EndGolemRepair( object state ) - { - ((Mobile)state).EndAction( typeof( Golem ) ); - } + private int GetWeakenChance(Mobile mob, SkillName skill, int curHits, int maxHits) + { + // 40% - (1% per hp lost) - (1% per 10 craft skill) + return 40 + (maxHits - curHits) - (int)((m_Deed?.SkillLevel ?? mob.Skills[skill].Value) / 10); + } - private int GetWeakenChance( Mobile mob, SkillName skill, int curHits, int maxHits ) - { - // 40% - (1% per hp lost) - (1% per 10 craft skill) - return (40 + (maxHits - curHits)) - (int)((m_Deed?.SkillLevel ?? mob.Skills[skill].Value) / 10); - } + private bool CheckWeaken(Mobile mob, SkillName skill, int curHits, int maxHits) + { + return GetWeakenChance(mob, skill, curHits, maxHits) > Utility.Random(100); + } - private bool CheckWeaken( Mobile mob, SkillName skill, int curHits, int maxHits ) - { - return ( GetWeakenChance( mob, skill, curHits, maxHits ) > Utility.Random( 100 ) ); - } + private int GetRepairDifficulty(int curHits, int maxHits) + { + return (maxHits - curHits) * 1250 / Math.Max(maxHits, 1) - 250; + } - private int GetRepairDifficulty( int curHits, int maxHits ) - { - return (((maxHits - curHits) * 1250) / Math.Max( maxHits, 1 )) - 250; - } - - private bool CheckRepairDifficulty( Mobile mob, SkillName skill, int curHits, int maxHits ) - { - double difficulty = GetRepairDifficulty( curHits, maxHits ) * 0.1; + private bool CheckRepairDifficulty(Mobile mob, SkillName skill, int curHits, int maxHits) + { + double difficulty = GetRepairDifficulty(curHits, maxHits) * 0.1; - if ( m_Deed != null ) - { - double value = m_Deed.SkillLevel; - double minSkill = difficulty - 25.0; - double maxSkill = difficulty + 25; + if (m_Deed != null) + { + double value = m_Deed.SkillLevel; + double minSkill = difficulty - 25.0; + double maxSkill = difficulty + 25; - if ( value < minSkill ) - return false; // Too difficult - if ( value >= maxSkill ) - return true; // No challenge + if (value < minSkill) + return false; // Too difficult + if (value >= maxSkill) + return true; // No challenge - double chance = (value - minSkill) / (maxSkill - minSkill); + double chance = (value - minSkill) / (maxSkill - minSkill); - return (chance >= Utility.RandomDouble()); - } + return chance >= Utility.RandomDouble(); + } - return mob.CheckSkill( skill, difficulty - 25.0, difficulty + 25.0 ); - } + return mob.CheckSkill(skill, difficulty - 25.0, difficulty + 25.0); + } - private bool CheckDeed( Mobile from ) - { - if ( m_Deed != null ) - { - return m_Deed.Check( from ); - } + private bool CheckDeed(Mobile from) + { + if (m_Deed != null) return m_Deed.Check(from); - return true; - } + return true; + } - private bool IsSpecialClothing( BaseClothing clothing ) - { - // Clothing repairable but not craftable + private bool IsSpecialClothing(BaseClothing clothing) + { + // Clothing repairable but not craftable - if ( m_CraftSystem is DefTailoring ) - { - return ( clothing is BearMask ) - || ( clothing is DeerMask ) - || ( clothing is TheMostKnowledgePerson ) - || ( clothing is TheRobeOfBritanniaAri ) - || ( clothing is EmbroideredOakLeafCloak ); - } + if (m_CraftSystem is DefTailoring) + return clothing is BearMask + || clothing is DeerMask + || clothing is TheMostKnowledgePerson + || clothing is TheRobeOfBritanniaAri + || clothing is EmbroideredOakLeafCloak; - return false; - } + return false; + } - private bool IsSpecialWeapon( BaseWeapon weapon ) - { - // Weapons repairable but not craftable + private bool IsSpecialWeapon(BaseWeapon weapon) + { + // Weapons repairable but not craftable - if ( m_CraftSystem is DefTinkering ) - { - return ( weapon is Cleaver ) - || ( weapon is Hatchet ) - || ( weapon is Pickaxe ) - || ( weapon is ButcherKnife ) - || ( weapon is SkinningKnife ); - } + if (m_CraftSystem is DefTinkering) + return weapon is Cleaver + || weapon is Hatchet + || weapon is Pickaxe + || weapon is ButcherKnife + || weapon is SkinningKnife; - if ( m_CraftSystem is DefCarpentry ) - { - return ( weapon is Club ) - || ( weapon is BlackStaff ) - || ( weapon is MagicWand ) - #region Temporary - // TODO: Make these items craftable - || ( weapon is WildStaff ); - #endregion - } - if ( m_CraftSystem is DefBlacksmithy ) - { - return ( weapon is Pitchfork ) - #region Temporary - // TODO: Make these items craftable - || ( weapon is RadiantScimitar ) - || ( weapon is WarCleaver ) - || ( weapon is ElvenSpellblade ) - || ( weapon is AssassinSpike ) - || ( weapon is Leafblade ) - || ( weapon is RuneBlade ) - || ( weapon is ElvenMachete ) - || ( weapon is OrnateAxe ) - || ( weapon is DiamondMace ); - #endregion - } - #region Temporary - // TODO: Make these items craftable - if ( m_CraftSystem is DefBowFletching ) - { - return ( weapon is ElvenCompositeLongbow ) - || ( weapon is MagicalShortbow ); - } + if (m_CraftSystem is DefCarpentry) + { + return weapon is Club + || weapon is BlackStaff + || weapon is MagicWand - #endregion + #region Temporary - return false; - } + // TODO: Make these items craftable + || weapon is WildStaff; - private bool IsSpecialArmor( BaseArmor armor ) - { - // Armor repairable but not craftable + #endregion + } - #region Temporary - // TODO: Make these items craftable - if ( m_CraftSystem is DefTailoring ) - { - return ( armor is LeafTonlet ) - || ( armor is LeafArms ) - || ( armor is LeafChest ) - || ( armor is LeafGloves ) - || ( armor is LeafGorget ) - || ( armor is LeafLegs ) - || ( armor is HideChest ) - || ( armor is HideGloves ) - || ( armor is HideGorget ) - || ( armor is HidePants ) - || ( armor is HidePauldrons ); - } + if (m_CraftSystem is DefBlacksmithy) + { + return weapon is Pitchfork - if ( m_CraftSystem is DefCarpentry ) - { - return ( armor is WingedHelm ) - || ( armor is RavenHelm ) - || ( armor is VultureHelm ) - || ( armor is WoodlandArms ) - || ( armor is WoodlandChest ) - || ( armor is WoodlandGloves ) - || ( armor is WoodlandGorget ) - || ( armor is WoodlandLegs ); - } - if ( m_CraftSystem is DefBlacksmithy ) - { - return ( armor is Circlet ) - || ( armor is RoyalCirclet ) - || ( armor is GemmedCirclet ); - } + #region Temporary - #endregion + // TODO: Make these items craftable + || weapon is RadiantScimitar + || weapon is WarCleaver + || weapon is ElvenSpellblade + || weapon is AssassinSpike + || weapon is Leafblade + || weapon is RuneBlade + || weapon is ElvenMachete + || weapon is OrnateAxe + || weapon is DiamondMace; - return false; - } + #endregion + } - protected override void OnTarget( Mobile from, object targeted ) - { - int number; + #region Temporary - if ( !CheckDeed( from ) ) - return; + // TODO: Make these items craftable + if (m_CraftSystem is DefBowFletching) + return weapon is ElvenCompositeLongbow + || weapon is MagicalShortbow; - bool usingDeed = (m_Deed != null); - bool toDelete = false; + #endregion - // TODO: Make an IRepairable + return false; + } - if ( m_CraftSystem.CanCraft( from, m_Tool, targeted.GetType() ) == 1044267 ) - { - number = 1044282; // You must be near a forge and and anvil to repair items. * Yes, there are two and's * - } - else if ( m_CraftSystem is DefTinkering && targeted is Golem g ) - { - int damage = g.HitsMax - g.Hits; + private bool IsSpecialArmor(BaseArmor armor) + { + // Armor repairable but not craftable - if ( g.IsDeadBondedPet ) - { - number = 500426; // You can't repair that. - } - else if ( damage <= 0 ) - { - number = 500423; // That is already in full repair. - } - else - { - double skillValue = (usingDeed)? m_Deed.SkillLevel : from.Skills[SkillName.Tinkering].Value; + #region Temporary - if ( skillValue < 60.0 ) - { - number = 1044153; // You don't have the required skills to attempt this item. //TODO: How does OSI handle this with deeds with golems? - } - else if ( !from.CanBeginAction( typeof( Golem ) ) ) - { - number = 501789; // You must wait before trying again. - } - else - { - if ( damage > (int)(skillValue * 0.3) ) - damage = (int)(skillValue * 0.3); + // TODO: Make these items craftable + if (m_CraftSystem is DefTailoring) + return armor is LeafTonlet + || armor is LeafArms + || armor is LeafChest + || armor is LeafGloves + || armor is LeafGorget + || armor is LeafLegs + || armor is HideChest + || armor is HideGloves + || armor is HideGorget + || armor is HidePants + || armor is HidePauldrons; - damage += 30; + if (m_CraftSystem is DefCarpentry) + return armor is WingedHelm + || armor is RavenHelm + || armor is VultureHelm + || armor is WoodlandArms + || armor is WoodlandChest + || armor is WoodlandGloves + || armor is WoodlandGorget + || armor is WoodlandLegs; + if (m_CraftSystem is DefBlacksmithy) + return armor is Circlet + || armor is RoyalCirclet + || armor is GemmedCirclet; - if ( !from.CheckSkill( SkillName.Tinkering, 0.0, 100.0 ) ) - damage /= 2; + #endregion - Container pack = from.Backpack; + return false; + } - if ( pack != null ) - { - int v = pack.ConsumeUpTo( typeof( IronIngot ), (damage+4)/5 ); + protected override void OnTarget(Mobile from, object targeted) + { + int number; - if ( v > 0 ) - { - g.Hits += v*5; + if (!CheckDeed(from)) + return; - number = 1044279; // You repair the item. - toDelete = true; + bool usingDeed = m_Deed != null; + bool toDelete = false; - from.BeginAction( typeof( Golem ) ); - Timer.DelayCall( TimeSpan.FromSeconds( 12.0 ), new TimerStateCallback( EndGolemRepair ), from ); - } - else - { - number = 1044037; // You do not have sufficient metal to make that. - } - } - else - { - number = 1044037; // You do not have sufficient metal to make that. - } - } - } - } - else if ( targeted is BaseWeapon weapon ) - { - SkillName skill = m_CraftSystem.MainSkill; - int toWeaken = 0; + // TODO: Make an IRepairable - if ( Core.AOS ) - { - toWeaken = 1; - } - else if ( skill != SkillName.Tailoring ) - { - double skillLevel = (usingDeed)? m_Deed.SkillLevel : from.Skills[skill].Base; + if (m_CraftSystem.CanCraft(from, m_Tool, targeted.GetType()) == 1044267) + { + number = 1044282; // You must be near a forge and and anvil to repair items. * Yes, there are two and's * + } + else if (m_CraftSystem is DefTinkering && targeted is Golem g) + { + int damage = g.HitsMax - g.Hits; - if ( skillLevel >= 90.0 ) - toWeaken = 1; - else if ( skillLevel >= 70.0 ) - toWeaken = 2; - else - toWeaken = 3; - } + if (g.IsDeadBondedPet) + { + number = 500426; // You can't repair that. + } + else if (damage <= 0) + { + number = 500423; // That is already in full repair. + } + else + { + double skillValue = usingDeed ? m_Deed.SkillLevel : from.Skills[SkillName.Tinkering].Value; - if ( m_CraftSystem.CraftItems.SearchForSubclass( weapon.GetType() ) == null && !IsSpecialWeapon( weapon ) ) - { - number = (usingDeed)? 1061136 : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. - } - else if ( !weapon.IsChildOf( from.Backpack ) && ( !Core.ML || weapon.Parent != from ) ) - { - number = 1044275; // The item must be in your backpack to repair it. - } - else if ( !Core.AOS && weapon.PoisonCharges != 0 ) - { - number = 1005012; // You cannot repair an item while a caustic substance is on it. - } - else if ( weapon.MaxHitPoints <= 0 || weapon.HitPoints == weapon.MaxHitPoints ) - { - number = 1044281; // That item is in full repair - } - else if ( weapon.MaxHitPoints <= toWeaken ) - { - number = 1044278; // That item has been repaired many times, and will break if repairs are attempted again. - } - else - { - if ( CheckWeaken( from, skill, weapon.HitPoints, weapon.MaxHitPoints ) ) - { - weapon.MaxHitPoints -= toWeaken; - weapon.HitPoints = Math.Max( 0, weapon.HitPoints - toWeaken ); - } + if (skillValue < 60.0) + { + number = + 1044153; // You don't have the required skills to attempt this item. //TODO: How does OSI handle this with deeds with golems? + } + else if (!from.CanBeginAction(typeof(Golem))) + { + number = 501789; // You must wait before trying again. + } + else + { + if (damage > (int)(skillValue * 0.3)) + damage = (int)(skillValue * 0.3); - if ( CheckRepairDifficulty( from, skill, weapon.HitPoints, weapon.MaxHitPoints ) ) - { - number = 1044279; // You repair the item. - m_CraftSystem.PlayCraftEffect( from ); - weapon.HitPoints = weapon.MaxHitPoints; - } - else - { - number = (usingDeed)? 1061137 : 1044280; // You fail to repair the item. [And the contract is destroyed] - m_CraftSystem.PlayCraftEffect( from ); - } + damage += 30; - toDelete = true; - } - } - else if ( targeted is BaseArmor armor ) - { - SkillName skill = m_CraftSystem.MainSkill; - int toWeaken = 0; + if (!from.CheckSkill(SkillName.Tinkering, 0.0, 100.0)) + damage /= 2; - if ( Core.AOS ) - { - toWeaken = 1; - } - else if ( skill != SkillName.Tailoring ) - { - double skillLevel = (usingDeed)? m_Deed.SkillLevel : from.Skills[skill].Base; + Container pack = from.Backpack; - if ( skillLevel >= 90.0 ) - toWeaken = 1; - else if ( skillLevel >= 70.0 ) - toWeaken = 2; - else - toWeaken = 3; - } + if (pack != null) + { + int v = pack.ConsumeUpTo(typeof(IronIngot), (damage + 4) / 5); - if ( m_CraftSystem.CraftItems.SearchForSubclass( armor.GetType() ) == null && !IsSpecialArmor( armor ) ) - { - number = (usingDeed)? 1061136 : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. - } - else if ( !armor.IsChildOf( from.Backpack ) && ( !Core.ML || armor.Parent != from ) ) - { - number = 1044275; // The item must be in your backpack to repair it. - } - else if ( armor.MaxHitPoints <= 0 || armor.HitPoints == armor.MaxHitPoints ) - { - number = 1044281; // That item is in full repair - } - else if ( armor.MaxHitPoints <= toWeaken ) - { - number = 1044278; // That item has been repaired many times, and will break if repairs are attempted again. - } - else - { - if ( CheckWeaken( from, skill, armor.HitPoints, armor.MaxHitPoints ) ) - { - armor.MaxHitPoints -= toWeaken; - armor.HitPoints = Math.Max( 0, armor.HitPoints - toWeaken ); - } + if (v > 0) + { + g.Hits += v * 5; - if ( CheckRepairDifficulty( from, skill, armor.HitPoints, armor.MaxHitPoints ) ) - { - number = 1044279; // You repair the item. - m_CraftSystem.PlayCraftEffect( from ); - armor.HitPoints = armor.MaxHitPoints; - } - else - { - number = (usingDeed)? 1061137 : 1044280; // You fail to repair the item. [And the contract is destroyed] - m_CraftSystem.PlayCraftEffect( from ); - } + number = 1044279; // You repair the item. + toDelete = true; - toDelete = true; - } - } - else if ( targeted is BaseClothing clothing ) - { - SkillName skill = m_CraftSystem.MainSkill; - int toWeaken = 0; + from.BeginAction(typeof(Golem)); + Timer.DelayCall(TimeSpan.FromSeconds(12.0), new TimerStateCallback(EndGolemRepair), + from); + } + else + { + number = 1044037; // You do not have sufficient metal to make that. + } + } + else + { + number = 1044037; // You do not have sufficient metal to make that. + } + } + } + } + else if (targeted is BaseWeapon weapon) + { + SkillName skill = m_CraftSystem.MainSkill; + int toWeaken = 0; - if ( Core.AOS ) - { - toWeaken = 1; - } - else if ( skill != SkillName.Tailoring ) - { - double skillLevel = (usingDeed) ? m_Deed.SkillLevel : from.Skills[skill].Base; + if (Core.AOS) + { + toWeaken = 1; + } + else if (skill != SkillName.Tailoring) + { + double skillLevel = usingDeed ? m_Deed.SkillLevel : from.Skills[skill].Base; - if ( skillLevel >= 90.0 ) - toWeaken = 1; - else if ( skillLevel >= 70.0 ) - toWeaken = 2; - else - toWeaken = 3; - } + if (skillLevel >= 90.0) + toWeaken = 1; + else if (skillLevel >= 70.0) + toWeaken = 2; + else + toWeaken = 3; + } - if (m_CraftSystem.CraftItems.SearchForSubclass(clothing.GetType()) == null && !IsSpecialClothing(clothing) && !((clothing is TribalMask) || (clothing is HornedTribalMask)) ) - { - number = (usingDeed) ? 1061136 : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. - } - else if ( !clothing.IsChildOf( from.Backpack ) && ( !Core.ML || clothing.Parent != from ) ) - { - number = 1044275; // The item must be in your backpack to repair it. - } - else if ( clothing.MaxHitPoints <= 0 || clothing.HitPoints == clothing.MaxHitPoints ) - { - number = 1044281; // That item is in full repair - } - else if ( clothing.MaxHitPoints <= toWeaken ) - { - number = 1044278; // That item has been repaired many times, and will break if repairs are attempted again. - } - else - { - if ( CheckWeaken( from, skill, clothing.HitPoints, clothing.MaxHitPoints ) ) - { - clothing.MaxHitPoints -= toWeaken; - clothing.HitPoints = Math.Max( 0, clothing.HitPoints - toWeaken ); - } + if (m_CraftSystem.CraftItems.SearchForSubclass(weapon.GetType()) == null && !IsSpecialWeapon(weapon)) + { + number = usingDeed + ? 1061136 + : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. + } + else if (!weapon.IsChildOf(from.Backpack) && (!Core.ML || weapon.Parent != from)) + { + number = 1044275; // The item must be in your backpack to repair it. + } + else if (!Core.AOS && weapon.PoisonCharges != 0) + { + number = 1005012; // You cannot repair an item while a caustic substance is on it. + } + else if (weapon.MaxHitPoints <= 0 || weapon.HitPoints == weapon.MaxHitPoints) + { + number = 1044281; // That item is in full repair + } + else if (weapon.MaxHitPoints <= toWeaken) + { + number = 1044278; // That item has been repaired many times, and will break if repairs are attempted again. + } + else + { + if (CheckWeaken(from, skill, weapon.HitPoints, weapon.MaxHitPoints)) + { + weapon.MaxHitPoints -= toWeaken; + weapon.HitPoints = Math.Max(0, weapon.HitPoints - toWeaken); + } - if ( CheckRepairDifficulty( from, skill, clothing.HitPoints, clothing.MaxHitPoints ) ) - { - number = 1044279; // You repair the item. - m_CraftSystem.PlayCraftEffect( from ); - clothing.HitPoints = clothing.MaxHitPoints; - } - else - { - number = (usingDeed) ? 1061137 : 1044280; // You fail to repair the item. [And the contract is destroyed] - m_CraftSystem.PlayCraftEffect( from ); - } + if (CheckRepairDifficulty(from, skill, weapon.HitPoints, weapon.MaxHitPoints)) + { + number = 1044279; // You repair the item. + m_CraftSystem.PlayCraftEffect(from); + weapon.HitPoints = weapon.MaxHitPoints; + } + else + { + number = usingDeed + ? 1061137 + : 1044280; // You fail to repair the item. [And the contract is destroyed] + m_CraftSystem.PlayCraftEffect(from); + } - toDelete = true; - } - } - else if ( !usingDeed && targeted is BlankScroll scroll ) - { - SkillName skill = m_CraftSystem.MainSkill; + toDelete = true; + } + } + else if (targeted is BaseArmor armor) + { + SkillName skill = m_CraftSystem.MainSkill; + int toWeaken = 0; - if ( from.Skills[skill].Value >= 50.0 ) - { - scroll.Consume( 1 ); - RepairDeed deed = new RepairDeed( RepairDeed.GetTypeFor( m_CraftSystem ), from.Skills[skill].Value, from ); - from.AddToBackpack( deed ); + if (Core.AOS) + { + toWeaken = 1; + } + else if (skill != SkillName.Tailoring) + { + double skillLevel = usingDeed ? m_Deed.SkillLevel : from.Skills[skill].Base; - number = 500442; // You create the item and put it in your backpack. - } - else - number = 1047005; // You must be at least apprentice level to create a repair service contract. - } - else if ( targeted is Item ) - { - number = (usingDeed)? 1061136 : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. - } - else - { - number = 500426; // You can't repair that. - } + if (skillLevel >= 90.0) + toWeaken = 1; + else if (skillLevel >= 70.0) + toWeaken = 2; + else + toWeaken = 3; + } - if ( !usingDeed ) - { - CraftContext context = m_CraftSystem.GetContext( from ); - from.SendGump( new CraftGump( from, m_CraftSystem, m_Tool, number ) ); - } - else - { - from.SendLocalizedMessage( number ); + if (m_CraftSystem.CraftItems.SearchForSubclass(armor.GetType()) == null && !IsSpecialArmor(armor)) + { + number = usingDeed + ? 1061136 + : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. + } + else if (!armor.IsChildOf(from.Backpack) && (!Core.ML || armor.Parent != from)) + { + number = 1044275; // The item must be in your backpack to repair it. + } + else if (armor.MaxHitPoints <= 0 || armor.HitPoints == armor.MaxHitPoints) + { + number = 1044281; // That item is in full repair + } + else if (armor.MaxHitPoints <= toWeaken) + { + number = 1044278; // That item has been repaired many times, and will break if repairs are attempted again. + } + else + { + if (CheckWeaken(from, skill, armor.HitPoints, armor.MaxHitPoints)) + { + armor.MaxHitPoints -= toWeaken; + armor.HitPoints = Math.Max(0, armor.HitPoints - toWeaken); + } - if ( toDelete ) - m_Deed.Delete(); - } - } - } - } -} + if (CheckRepairDifficulty(from, skill, armor.HitPoints, armor.MaxHitPoints)) + { + number = 1044279; // You repair the item. + m_CraftSystem.PlayCraftEffect(from); + armor.HitPoints = armor.MaxHitPoints; + } + else + { + number = usingDeed + ? 1061137 + : 1044280; // You fail to repair the item. [And the contract is destroyed] + m_CraftSystem.PlayCraftEffect(from); + } + + toDelete = true; + } + } + else if (targeted is BaseClothing clothing) + { + SkillName skill = m_CraftSystem.MainSkill; + int toWeaken = 0; + + if (Core.AOS) + { + toWeaken = 1; + } + else if (skill != SkillName.Tailoring) + { + double skillLevel = usingDeed ? m_Deed.SkillLevel : from.Skills[skill].Base; + + if (skillLevel >= 90.0) + toWeaken = 1; + else if (skillLevel >= 70.0) + toWeaken = 2; + else + toWeaken = 3; + } + + if (m_CraftSystem.CraftItems.SearchForSubclass(clothing.GetType()) == null && + !IsSpecialClothing(clothing) && !(clothing is TribalMask || clothing is HornedTribalMask)) + { + number = usingDeed + ? 1061136 + : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. + } + else if (!clothing.IsChildOf(from.Backpack) && (!Core.ML || clothing.Parent != from)) + { + number = 1044275; // The item must be in your backpack to repair it. + } + else if (clothing.MaxHitPoints <= 0 || clothing.HitPoints == clothing.MaxHitPoints) + { + number = 1044281; // That item is in full repair + } + else if (clothing.MaxHitPoints <= toWeaken) + { + number = 1044278; // That item has been repaired many times, and will break if repairs are attempted again. + } + else + { + if (CheckWeaken(from, skill, clothing.HitPoints, clothing.MaxHitPoints)) + { + clothing.MaxHitPoints -= toWeaken; + clothing.HitPoints = Math.Max(0, clothing.HitPoints - toWeaken); + } + + if (CheckRepairDifficulty(from, skill, clothing.HitPoints, clothing.MaxHitPoints)) + { + number = 1044279; // You repair the item. + m_CraftSystem.PlayCraftEffect(from); + clothing.HitPoints = clothing.MaxHitPoints; + } + else + { + number = usingDeed + ? 1061137 + : 1044280; // You fail to repair the item. [And the contract is destroyed] + m_CraftSystem.PlayCraftEffect(from); + } + + toDelete = true; + } + } + else if (!usingDeed && targeted is BlankScroll scroll) + { + SkillName skill = m_CraftSystem.MainSkill; + + if (from.Skills[skill].Value >= 50.0) + { + scroll.Consume(1); + RepairDeed deed = new RepairDeed(RepairDeed.GetTypeFor(m_CraftSystem), from.Skills[skill].Value, + from); + from.AddToBackpack(deed); + + number = 500442; // You create the item and put it in your backpack. + } + else + { + number = 1047005; // You must be at least apprentice level to create a repair service contract. + } + } + else if (targeted is Item) + { + number = usingDeed + ? 1061136 + : 1044277; // That item cannot be repaired. // You cannot repair that item with this type of repair contract. + } + else + { + number = 500426; // You can't repair that. + } + + if (!usingDeed) + { + CraftContext context = m_CraftSystem.GetContext(from); + from.SendGump(new CraftGump(from, m_CraftSystem, m_Tool, number)); + } + else + { + from.SendLocalizedMessage(number); + + if (toDelete) + m_Deed.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/Core/Resmelt.cs b/Scripts/Engines/Craft/Core/Resmelt.cs index f5f417a6e..28812e68a 100644 --- a/Scripts/Engines/Craft/Core/Resmelt.cs +++ b/Scripts/Engines/Craft/Core/Resmelt.cs @@ -1,166 +1,186 @@ using System; -using Server.Targeting; +using Server.Ethics; using Server.Items; +using Server.Targeting; namespace Server.Engines.Craft { - public enum SmeltResult - { - Success, - Invalid, - NoSkill - } + public enum SmeltResult + { + Success, + Invalid, + NoSkill + } - public class Resmelt - { - public Resmelt() - { - } + public class Resmelt + { + public static void Do(Mobile from, CraftSystem craftSystem, BaseTool tool) + { + int num = craftSystem.CanCraft(from, tool, null); - public static void Do( Mobile from, CraftSystem craftSystem, BaseTool tool ) - { - int num = craftSystem.CanCraft( from, tool, null ); + if (num > 0 && num != 1044267) + { + from.SendGump(new CraftGump(from, craftSystem, tool, num)); + } + else + { + from.Target = new InternalTarget(craftSystem, tool); + from.SendLocalizedMessage(1044273); // Target an item to recycle. + } + } - if ( num > 0 && num != 1044267 ) - { - from.SendGump( new CraftGump( from, craftSystem, tool, num ) ); - } - else - { - from.Target = new InternalTarget( craftSystem, tool ); - from.SendLocalizedMessage( 1044273 ); // Target an item to recycle. - } - } + private class InternalTarget : Target + { + private CraftSystem m_CraftSystem; + private BaseTool m_Tool; - private class InternalTarget : Target - { - private CraftSystem m_CraftSystem; - private BaseTool m_Tool; + public InternalTarget(CraftSystem craftSystem, BaseTool tool) : base(2, false, TargetFlags.None) + { + m_CraftSystem = craftSystem; + m_Tool = tool; + } - public InternalTarget( CraftSystem craftSystem, BaseTool tool ) : base ( 2, false, TargetFlags.None ) - { - m_CraftSystem = craftSystem; - m_Tool = tool; - } + private SmeltResult Resmelt(Mobile from, Item item, CraftResource resource) + { + try + { + if (Ethic.IsImbued(item)) + return SmeltResult.Invalid; - private SmeltResult Resmelt( Mobile from, Item item, CraftResource resource ) - { - try - { + if (CraftResources.GetType(resource) != CraftResourceType.Metal) + return SmeltResult.Invalid; - if ( Ethics.Ethic.IsImbued( item ) ) - return SmeltResult.Invalid; + CraftResourceInfo info = CraftResources.GetInfo(resource); - if ( CraftResources.GetType( resource ) != CraftResourceType.Metal ) - return SmeltResult.Invalid; + if (info == null || info.ResourceTypes.Length == 0) + return SmeltResult.Invalid; - CraftResourceInfo info = CraftResources.GetInfo( resource ); + CraftItem craftItem = m_CraftSystem.CraftItems.SearchFor(item.GetType()); - if ( info == null || info.ResourceTypes.Length == 0 ) - return SmeltResult.Invalid; + if (craftItem == null || craftItem.Resources.Count == 0) + return SmeltResult.Invalid; - CraftItem craftItem = m_CraftSystem.CraftItems.SearchFor( item.GetType() ); + CraftRes craftResource = craftItem.Resources.GetAt(0); - if ( craftItem == null || craftItem.Resources.Count == 0 ) - return SmeltResult.Invalid; + if (craftResource.Amount < 2) + return SmeltResult.Invalid; // Not enough metal to resmelt - CraftRes craftResource = craftItem.Resources.GetAt( 0 ); + double difficulty = 0.0; - if ( craftResource.Amount < 2 ) - return SmeltResult.Invalid; // Not enough metal to resmelt + switch (resource) + { + case CraftResource.DullCopper: + difficulty = 65.0; + break; + case CraftResource.ShadowIron: + difficulty = 70.0; + break; + case CraftResource.Copper: + difficulty = 75.0; + break; + case CraftResource.Bronze: + difficulty = 80.0; + break; + case CraftResource.Gold: + difficulty = 85.0; + break; + case CraftResource.Agapite: + difficulty = 90.0; + break; + case CraftResource.Verite: + difficulty = 95.0; + break; + case CraftResource.Valorite: + difficulty = 99.0; + break; + } - double difficulty = 0.0; + if (difficulty > from.Skills[SkillName.Mining].Value) + return SmeltResult.NoSkill; - switch ( resource ) - { - case CraftResource.DullCopper: difficulty = 65.0; break; - case CraftResource.ShadowIron: difficulty = 70.0; break; - case CraftResource.Copper: difficulty = 75.0; break; - case CraftResource.Bronze: difficulty = 80.0; break; - case CraftResource.Gold: difficulty = 85.0; break; - case CraftResource.Agapite: difficulty = 90.0; break; - case CraftResource.Verite: difficulty = 95.0; break; - case CraftResource.Valorite: difficulty = 99.0; break; - } + Type resourceType = info.ResourceTypes[0]; + Item ingot = (Item)Activator.CreateInstance(resourceType); - if ( difficulty > from.Skills[ SkillName.Mining ].Value ) - return SmeltResult.NoSkill; + if (item is DragonBardingDeed || item is BaseArmor armor && armor.PlayerConstructed || + item is BaseWeapon weapon && weapon.PlayerConstructed || + item is BaseClothing clothing && clothing.PlayerConstructed) + ingot.Amount = craftResource.Amount / 2; + else + ingot.Amount = 1; - Type resourceType = info.ResourceTypes[0]; - Item ingot = (Item)Activator.CreateInstance( resourceType ); + item.Delete(); + from.AddToBackpack(ingot); - if ( item is DragonBardingDeed || (item is BaseArmor armor && armor.PlayerConstructed) || (item is BaseWeapon weapon && weapon.PlayerConstructed) || (item is BaseClothing clothing && clothing.PlayerConstructed) ) - ingot.Amount = craftResource.Amount / 2; - else - ingot.Amount = 1; + from.PlaySound(0x2A); + from.PlaySound(0x240); + return SmeltResult.Success; + } + catch + { + } - item.Delete(); - from.AddToBackpack( ingot ); + return SmeltResult.Invalid; + } - from.PlaySound( 0x2A ); - from.PlaySound( 0x240 ); - return SmeltResult.Success; - } - catch - { - } + protected override void OnTarget(Mobile from, object targeted) + { + int num = m_CraftSystem.CanCraft(from, m_Tool, null); - return SmeltResult.Invalid; - } + if (num > 0) + { + if (num == 1044267) + { + bool anvil, forge; - protected override void OnTarget( Mobile from, object targeted ) - { - int num = m_CraftSystem.CanCraft( from, m_Tool, null ); + DefBlacksmithy.CheckAnvilAndForge(from, 2, out anvil, out forge); - if ( num > 0 ) - { - if ( num == 1044267 ) - { - bool anvil, forge; + if (!anvil) + num = 1044266; // You must be near an anvil + else if (!forge) + num = 1044265; // You must be near a forge. + } - DefBlacksmithy.CheckAnvilAndForge( from, 2, out anvil, out forge ); + from.SendGump(new CraftGump(from, m_CraftSystem, m_Tool, num)); + } + else + { + SmeltResult result = SmeltResult.Invalid; + bool isStoreBought = false; + int message; - if ( !anvil ) - num = 1044266; // You must be near an anvil - else if ( !forge ) - num = 1044265; // You must be near a forge. - } + if (targeted is BaseArmor armor) + { + result = Resmelt(from, armor, armor.Resource); + isStoreBought = !armor.PlayerConstructed; + } + else if (targeted is BaseWeapon weapon) + { + result = Resmelt(from, weapon, weapon.Resource); + isStoreBought = !weapon.PlayerConstructed; + } + else if (targeted is DragonBardingDeed deed) + { + result = Resmelt(from, deed, deed.Resource); + isStoreBought = false; + } - from.SendGump( new CraftGump( from, m_CraftSystem, m_Tool, num ) ); - } - else - { - SmeltResult result = SmeltResult.Invalid; - bool isStoreBought = false; - int message; + switch (result) + { + default: + case SmeltResult.Invalid: + message = 1044272; + break; // You can't melt that down into ingots. + case SmeltResult.NoSkill: + message = 1044269; + break; // You have no idea how to work this metal. + case SmeltResult.Success: + message = isStoreBought ? 500418 : 1044270; + break; // You melt the item down into ingots. + } - if ( targeted is BaseArmor armor ) - { - result = Resmelt( from, armor, armor.Resource ); - isStoreBought = !armor.PlayerConstructed; - } - else if ( targeted is BaseWeapon weapon ) - { - result = Resmelt( from, weapon, weapon.Resource ); - isStoreBought = !weapon.PlayerConstructed; - } - else if ( targeted is DragonBardingDeed deed ) - { - result = Resmelt( from, deed, deed.Resource ); - isStoreBought = false; - } - - switch ( result ) - { - default: - case SmeltResult.Invalid: message = 1044272; break; // You can't melt that down into ingots. - case SmeltResult.NoSkill: message = 1044269; break; // You have no idea how to work this metal. - case SmeltResult.Success: message = isStoreBought ? 500418 : 1044270; break; // You melt the item down into ingots. - } - - from.SendGump( new CraftGump( from, m_CraftSystem, m_Tool, message ) ); - } - } - } - } -} + from.SendGump(new CraftGump(from, m_CraftSystem, m_Tool, message)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefAlchemy.cs b/Scripts/Engines/Craft/DefAlchemy.cs index 083092250..6ac3c1ff2 100644 --- a/Scripts/Engines/Craft/DefAlchemy.cs +++ b/Scripts/Engines/Craft/DefAlchemy.cs @@ -3,165 +3,181 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefAlchemy : CraftSystem - { - public override SkillName MainSkill => SkillName.Alchemy; + public class DefAlchemy : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044001; + private static Type typeofPotion = typeof(BasePotion); - private static CraftSystem m_CraftSystem; + private DefAlchemy() : base(1, 1, 1.25) // base( 1, 1, 3.1 ) + { + } - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefAlchemy(); + public override SkillName MainSkill => SkillName.Alchemy; - return m_CraftSystem; - } - } + public override int GumpTitleNumber => 1044001; - public override double GetChanceAtMin( CraftItem item ) - { - return 0.0; // 0% - } + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefAlchemy(); - private DefAlchemy() : base( 1, 1, 1.25 )// base( 1, 1, 3.1 ) - { - } + return m_CraftSystem; + } + } - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override double GetChanceAtMin(CraftItem item) + { + return 0.0; // 0% + } - return 0; - } + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - public override void PlayCraftEffect( Mobile from ) - { - from.PlaySound( 0x242 ); - } + return 0; + } - private static Type typeofPotion = typeof( BasePotion ); + public override void PlayCraftEffect(Mobile from) + { + from.PlaySound(0x242); + } - public static bool IsPotion( Type type ) - { - return typeofPotion.IsAssignableFrom( type ); - } + public static bool IsPotion(Type type) + { + return typeofPotion.IsAssignableFrom(type); + } - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - if ( failed ) - { - if ( IsPotion( item.ItemType ) ) - { - from.AddToBackpack( new Bottle() ); - return 500287; // You fail to create a useful potion. - } + if (failed) + { + if (IsPotion(item.ItemType)) + { + from.AddToBackpack(new Bottle()); + return 500287; // You fail to create a useful potion. + } - return 1044043; // You failed to create the item, and some of your materials are lost. - } + return 1044043; // You failed to create the item, and some of your materials are lost. + } - from.PlaySound( 0x240 ); // Sound of a filling bottle + from.PlaySound(0x240); // Sound of a filling bottle - if ( IsPotion( item.ItemType ) ) - { - if ( quality == -1 ) - return 1048136; // You create the potion and pour it into a keg. - return 500279; // You pour the potion into a bottle... - } + if (IsPotion(item.ItemType)) + { + if (quality == -1) + return 1048136; // You create the potion and pour it into a keg. + return 500279; // You pour the potion into a bottle... + } - return 1044154; // You create the item. - } + return 1044154; // You create the item. + } - public override void InitCraftList() - { - int index = -1; + public override void InitCraftList() + { + int index = -1; - // Refresh Potion - index = AddCraft( typeof( RefreshPotion ), 1044530, 1044538, -25, 25.0, typeof( BlackPearl ), 1044353, 1, 1044361 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( TotalRefreshPotion ), 1044530, 1044539, 25.0, 75.0, typeof( BlackPearl ), 1044353, 5, 1044361 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Refresh Potion + index = AddCraft(typeof(RefreshPotion), 1044530, 1044538, -25, 25.0, typeof(BlackPearl), 1044353, 1, 1044361); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(TotalRefreshPotion), 1044530, 1044539, 25.0, 75.0, typeof(BlackPearl), 1044353, 5, + 1044361); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Agility Potion - index = AddCraft( typeof( AgilityPotion ), 1044531, 1044540, 15.0, 65.0, typeof( Bloodmoss ), 1044354, 1, 1044362 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( GreaterAgilityPotion ), 1044531, 1044541, 35.0, 85.0, typeof( Bloodmoss ), 1044354, 3, 1044362 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Agility Potion + index = AddCraft(typeof(AgilityPotion), 1044531, 1044540, 15.0, 65.0, typeof(Bloodmoss), 1044354, 1, 1044362); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(GreaterAgilityPotion), 1044531, 1044541, 35.0, 85.0, typeof(Bloodmoss), 1044354, 3, + 1044362); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Nightsight Potion - index = AddCraft( typeof( NightSightPotion ), 1044532, 1044542, -25.0, 25.0, typeof( SpidersSilk ), 1044360, 1, 1044368 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Nightsight Potion + index = AddCraft(typeof(NightSightPotion), 1044532, 1044542, -25.0, 25.0, typeof(SpidersSilk), 1044360, 1, + 1044368); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Heal Potion - index = AddCraft( typeof( LesserHealPotion ), 1044533, 1044543, -25.0, 25.0, typeof( Ginseng ), 1044356, 1, 1044364 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( HealPotion ), 1044533, 1044544, 15.0, 65.0, typeof( Ginseng ), 1044356, 3, 1044364 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( GreaterHealPotion ), 1044533, 1044545, 55.0, 105.0, typeof( Ginseng ), 1044356, 7, 1044364 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Heal Potion + index = AddCraft(typeof(LesserHealPotion), 1044533, 1044543, -25.0, 25.0, typeof(Ginseng), 1044356, 1, 1044364); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(HealPotion), 1044533, 1044544, 15.0, 65.0, typeof(Ginseng), 1044356, 3, 1044364); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(GreaterHealPotion), 1044533, 1044545, 55.0, 105.0, typeof(Ginseng), 1044356, 7, 1044364); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Strength Potion - index = AddCraft( typeof( StrengthPotion ), 1044534, 1044546, 25.0, 75.0, typeof( MandrakeRoot ), 1044357, 2, 1044365 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( GreaterStrengthPotion ), 1044534, 1044547, 45.0, 95.0, typeof( MandrakeRoot ), 1044357, 5, 1044365 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Strength Potion + index = AddCraft(typeof(StrengthPotion), 1044534, 1044546, 25.0, 75.0, typeof(MandrakeRoot), 1044357, 2, + 1044365); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(GreaterStrengthPotion), 1044534, 1044547, 45.0, 95.0, typeof(MandrakeRoot), 1044357, 5, + 1044365); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Poison Potion - index = AddCraft( typeof( LesserPoisonPotion ), 1044535, 1044548, -5.0, 45.0, typeof( Nightshade ), 1044358, 1, 1044366 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( PoisonPotion ), 1044535, 1044549, 15.0, 65.0, typeof( Nightshade ), 1044358, 2, 1044366 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( GreaterPoisonPotion ), 1044535, 1044550, 55.0, 105.0, typeof( Nightshade ), 1044358, 4, 1044366 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( DeadlyPoisonPotion ), 1044535, 1044551, 90.0, 140.0, typeof( Nightshade ), 1044358, 8, 1044366 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Poison Potion + index = AddCraft(typeof(LesserPoisonPotion), 1044535, 1044548, -5.0, 45.0, typeof(Nightshade), 1044358, 1, + 1044366); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(PoisonPotion), 1044535, 1044549, 15.0, 65.0, typeof(Nightshade), 1044358, 2, 1044366); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(GreaterPoisonPotion), 1044535, 1044550, 55.0, 105.0, typeof(Nightshade), 1044358, 4, + 1044366); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(DeadlyPoisonPotion), 1044535, 1044551, 90.0, 140.0, typeof(Nightshade), 1044358, 8, + 1044366); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Cure Potion - index = AddCraft( typeof( LesserCurePotion ), 1044536, 1044552, -10.0, 40.0, typeof( Garlic ), 1044355, 1, 1044363 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( CurePotion ), 1044536, 1044553, 25.0, 75.0, typeof( Garlic ), 1044355, 3, 1044363 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( GreaterCurePotion ), 1044536, 1044554, 65.0, 115.0, typeof( Garlic ), 1044355, 6, 1044363 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Cure Potion + index = AddCraft(typeof(LesserCurePotion), 1044536, 1044552, -10.0, 40.0, typeof(Garlic), 1044355, 1, 1044363); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(CurePotion), 1044536, 1044553, 25.0, 75.0, typeof(Garlic), 1044355, 3, 1044363); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(GreaterCurePotion), 1044536, 1044554, 65.0, 115.0, typeof(Garlic), 1044355, 6, 1044363); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - // Explosion Potion - index = AddCraft( typeof( LesserExplosionPotion ), 1044537, 1044555, 5.0, 55.0, typeof( SulfurousAsh ), 1044359, 3, 1044367 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( ExplosionPotion ), 1044537, 1044556, 35.0, 85.0, typeof( SulfurousAsh ), 1044359, 5, 1044367 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); - index = AddCraft( typeof( GreaterExplosionPotion ), 1044537, 1044557, 65.0, 115.0, typeof( SulfurousAsh ), 1044359, 10, 1044367 ); - AddRes( index, typeof ( Bottle ), 1044529, 1, 500315 ); + // Explosion Potion + index = AddCraft(typeof(LesserExplosionPotion), 1044537, 1044555, 5.0, 55.0, typeof(SulfurousAsh), 1044359, 3, + 1044367); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(ExplosionPotion), 1044537, 1044556, 35.0, 85.0, typeof(SulfurousAsh), 1044359, 5, + 1044367); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + index = AddCraft(typeof(GreaterExplosionPotion), 1044537, 1044557, 65.0, 115.0, typeof(SulfurousAsh), 1044359, + 10, 1044367); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); - if ( Core.SE ) - { - index = AddCraft( typeof( SmokeBomb ), 1044537, 1030248, 90.0, 120.0, typeof( Eggs ), 1044477, 1, 1044253 ); - AddRes( index, typeof ( Ginseng ), 1044356, 3, 1044364 ); - SetNeededExpansion( index, Expansion.SE ); + if (Core.SE) + { + index = AddCraft(typeof(SmokeBomb), 1044537, 1030248, 90.0, 120.0, typeof(Eggs), 1044477, 1, 1044253); + AddRes(index, typeof(Ginseng), 1044356, 3, 1044364); + SetNeededExpansion(index, Expansion.SE); - // Conflagration Potions - index = AddCraft( typeof(ConflagrationPotion), 1044109, 1072096, 55.0, 105.0, typeof(GraveDust), 1023983, 5, 1044253 ); - AddRes( index, typeof(Bottle), 1044529, 1, 500315 ); - SetNeededExpansion(index, Expansion.SE); - index = AddCraft( typeof(GreaterConflagrationPotion), 1044109, 1072099, 65.0, 115.0, typeof(GraveDust), 1023983, 10, 1044253 ); - AddRes( index, typeof(Bottle), 1044529, 1, 500315 ); - SetNeededExpansion(index, Expansion.SE); - // Confusion Blast Potions - index = AddCraft( typeof(ConfusionBlastPotion), 1044109, 1072106, 55.0, 105.0, typeof(PigIron), 1023978, 5, 1044253 ); - AddRes( index, typeof(Bottle), 1044529, 1, 500315 ); - SetNeededExpansion(index, Expansion.SE); - index = AddCraft( typeof(GreaterConfusionBlastPotion), 1044109, 1072109, 65.0, 115.0, typeof(PigIron), 1023978, 10, 1044253 ); - AddRes( index, typeof(Bottle), 1044529, 1, 500315 ); - SetNeededExpansion(index, Expansion.SE); - } - } - } -} + // Conflagration Potions + index = AddCraft(typeof(ConflagrationPotion), 1044109, 1072096, 55.0, 105.0, typeof(GraveDust), 1023983, 5, + 1044253); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(GreaterConflagrationPotion), 1044109, 1072099, 65.0, 115.0, typeof(GraveDust), + 1023983, 10, 1044253); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + SetNeededExpansion(index, Expansion.SE); + // Confusion Blast Potions + index = AddCraft(typeof(ConfusionBlastPotion), 1044109, 1072106, 55.0, 105.0, typeof(PigIron), 1023978, 5, + 1044253); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(GreaterConfusionBlastPotion), 1044109, 1072109, 65.0, 115.0, typeof(PigIron), + 1023978, 10, 1044253); + AddRes(index, typeof(Bottle), 1044529, 1, 500315); + SetNeededExpansion(index, Expansion.SE); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefBlacksmithy.cs b/Scripts/Engines/Craft/DefBlacksmithy.cs index 1b9cd2b6b..f99e59af1 100644 --- a/Scripts/Engines/Craft/DefBlacksmithy.cs +++ b/Scripts/Engines/Craft/DefBlacksmithy.cs @@ -3,729 +3,803 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefBlacksmithy : CraftSystem - { - public override SkillName MainSkill => SkillName.Blacksmith; + public class DefBlacksmithy : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044002; + private static Type typeofAnvil = typeof(AnvilAttribute); + private static Type typeofForge = typeof(ForgeAttribute); - private static CraftSystem m_CraftSystem; + private DefBlacksmithy() : base(1, 1, 1.25) // base( 1, 2, 1.7 ) + { + /* - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefBlacksmithy(); + base( MinCraftEffect, MaxCraftEffect, Delay ) - return m_CraftSystem; - } - } + MinCraftEffect : The minimum number of time the mobile will play the craft effect + MaxCraftEffect : The maximum number of time the mobile will play the craft effect + Delay : The delay between each craft effect - public override CraftECA ECA => CraftECA.ChanceMinusSixtyToFourtyFive; + Example: (3, 6, 1.7) would make the mobile do the PlayCraftEffect override + function between 3 and 6 time, with a 1.7 second delay each time. - public override double GetChanceAtMin( CraftItem item ) - { - return 0.0; // 0% - } + */ + } - private DefBlacksmithy() : base( 1, 1, 1.25 )// base( 1, 2, 1.7 ) - { - /* + public override SkillName MainSkill => SkillName.Blacksmith; - base( MinCraftEffect, MaxCraftEffect, Delay ) + public override int GumpTitleNumber => 1044002; - MinCraftEffect : The minimum number of time the mobile will play the craft effect - MaxCraftEffect : The maximum number of time the mobile will play the craft effect - Delay : The delay between each craft effect + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefBlacksmithy(); - Example: (3, 6, 1.7) would make the mobile do the PlayCraftEffect override - function between 3 and 6 time, with a 1.7 second delay each time. + return m_CraftSystem; + } + } - */ - } + public override CraftECA ECA => CraftECA.ChanceMinusSixtyToFourtyFive; - private static Type typeofAnvil = typeof( AnvilAttribute ); - private static Type typeofForge = typeof( ForgeAttribute ); + public override double GetChanceAtMin(CraftItem item) + { + return 0.0; // 0% + } + + public static void CheckAnvilAndForge(Mobile from, int range, out bool anvil, out bool forge) + { + anvil = false; + forge = false; + + Map map = from.Map; + + if (map == null) + return; + + IPooledEnumerable eable = map.GetItemsInRange(from.Location, range); + + foreach (Item item in eable) + { + Type type = item.GetType(); + + bool isAnvil = type.IsDefined(typeofAnvil, false) || item.ItemID == 4015 || item.ItemID == 4016 || + item.ItemID == 0x2DD5 || item.ItemID == 0x2DD6; + bool isForge = type.IsDefined(typeofForge, false) || item.ItemID == 4017 || + item.ItemID >= 6522 && item.ItemID <= 6569 || item.ItemID == 0x2DD8; + + if (isAnvil || isForge) + { + if (from.Z + 16 < item.Z || item.Z + 16 < from.Z || !from.InLOS(item)) + continue; + + anvil = anvil || isAnvil; + forge = forge || isForge; + + if (anvil && forge) + break; + } + } + + eable.Free(); + + for (int x = -range; (!anvil || !forge) && x <= range; ++x) + for (int y = -range; (!anvil || !forge) && y <= range; ++y) + { + StaticTile[] tiles = map.Tiles.GetStaticTiles(from.X + x, from.Y + y, true); + + for (int i = 0; (!anvil || !forge) && i < tiles.Length; ++i) + { + int id = tiles[i].ID; + + bool isAnvil = id == 4015 || id == 4016 || id == 0x2DD5 || id == 0x2DD6; + bool isForge = id == 4017 || id >= 6522 && id <= 6569 || id == 0x2DD8; + + if (isAnvil || isForge) + { + if (from.Z + 16 < tiles[i].Z || tiles[i].Z + 16 < from.Z || + !from.InLOS(new Point3D(from.X + x, from.Y + y, tiles[i].Z + tiles[i].Height / 2 + 1))) + continue; - public static void CheckAnvilAndForge( Mobile from, int range, out bool anvil, out bool forge ) - { - anvil = false; - forge = false; + anvil = anvil || isAnvil; + forge = forge || isForge; + } + } + } + } + + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckTool(tool, from)) + return 1048146; // If you have a tool equipped, you must use that tool. + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. + + bool anvil, forge; + CheckAnvilAndForge(from, 2, out anvil, out forge); + + if (anvil && forge) + return 0; + + return 1044267; // You must be near an anvil and a forge to smith items. + } + + public override void PlayCraftEffect(Mobile from) + { + // no animation, instant sound + //if ( from.Body.Type == BodyType.Human && !from.Mounted ) + // from.Animate( 9, 5, 1, true, false, 0 ); + //new InternalTimer( from ).Start(); + + from.PlaySound(0x2A); + } + + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool + + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } + + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } + + public override void InitCraftList() + { + /* + Synthax for a SIMPLE craft item + AddCraft( ObjectType, Group, MinSkill, MaxSkill, ResourceType, Amount, Message ) + + ObjectType : The type of the object you want to add to the build list. + Group : The group in wich the object will be showed in the craft menu. + MinSkill : The minimum of skill value + MaxSkill : The maximum of skill value + ResourceType : The type of the resource the mobile need to create the item + Amount : The amount of the ResourceType it need to create the item + Message : String or Int for Localized. The message that will be sent to the mobile, if the specified resource is missing. + + Synthax for a COMPLEXE craft item. A complexe item is an item that need either more than + only one skill, or more than only one resource. + + Coming soon.... + */ + + #region Ringmail + + AddCraft(typeof(RingmailGloves), 1011076, 1025099, 12.0, 62.0, typeof(IronIngot), 1044036, 10, 1044037); + AddCraft(typeof(RingmailLegs), 1011076, 1025104, 19.4, 69.4, typeof(IronIngot), 1044036, 16, 1044037); + AddCraft(typeof(RingmailArms), 1011076, 1025103, 16.9, 66.9, typeof(IronIngot), 1044036, 14, 1044037); + AddCraft(typeof(RingmailChest), 1011076, 1025100, 21.9, 71.9, typeof(IronIngot), 1044036, 18, 1044037); + + #endregion + + #region Chainmail + + AddCraft(typeof(ChainCoif), 1011077, 1025051, 14.5, 64.5, typeof(IronIngot), 1044036, 10, 1044037); + AddCraft(typeof(ChainLegs), 1011077, 1025054, 36.7, 86.7, typeof(IronIngot), 1044036, 18, 1044037); + AddCraft(typeof(ChainChest), 1011077, 1025055, 39.1, 89.1, typeof(IronIngot), 1044036, 20, 1044037); + + #endregion + + int index = -1; + + #region Platemail + + AddCraft(typeof(PlateArms), 1011078, 1025136, 66.3, 116.3, typeof(IronIngot), 1044036, 18, 1044037); + AddCraft(typeof(PlateGloves), 1011078, 1025140, 58.9, 108.9, typeof(IronIngot), 1044036, 12, 1044037); + AddCraft(typeof(PlateGorget), 1011078, 1025139, 56.4, 106.4, typeof(IronIngot), 1044036, 10, 1044037); + AddCraft(typeof(PlateLegs), 1011078, 1025137, 68.8, 118.8, typeof(IronIngot), 1044036, 20, 1044037); + AddCraft(typeof(PlateChest), 1011078, 1046431, 75.0, 125.0, typeof(IronIngot), 1044036, 25, 1044037); + AddCraft(typeof(FemalePlateChest), 1011078, 1046430, 44.1, 94.1, typeof(IronIngot), 1044036, 20, 1044037); + + if (Core.AOS) // exact pre-aos functionality unknown + AddCraft(typeof(DragonBardingDeed), 1011078, 1053012, 72.5, 122.5, typeof(IronIngot), 1044036, 750, 1044037); + + if (Core.SE) + { + index = AddCraft(typeof(PlateMempo), 1011078, 1030180, 80.0, 130.0, typeof(IronIngot), 1044036, 18, 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlateDo), 1011078, 1030184, 80.0, 130.0, typeof(IronIngot), 1044036, 28, + 1044037); //Double check skill + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlateHiroSode), 1011078, 1030187, 80.0, 130.0, typeof(IronIngot), 1044036, 16, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlateSuneate), 1011078, 1030195, 65.0, 115.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlateHaidate), 1011078, 1030200, 65.0, 115.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Helmets + + AddCraft(typeof(Bascinet), 1011079, 1025132, 8.3, 58.3, typeof(IronIngot), 1044036, 15, 1044037); + AddCraft(typeof(CloseHelm), 1011079, 1025128, 37.9, 87.9, typeof(IronIngot), 1044036, 15, 1044037); + AddCraft(typeof(Helmet), 1011079, 1025130, 37.9, 87.9, typeof(IronIngot), 1044036, 15, 1044037); + AddCraft(typeof(NorseHelm), 1011079, 1025134, 37.9, 87.9, typeof(IronIngot), 1044036, 15, 1044037); + AddCraft(typeof(PlateHelm), 1011079, 1025138, 62.6, 112.6, typeof(IronIngot), 1044036, 15, 1044037); + + if (Core.SE) + { + index = AddCraft(typeof(ChainHatsuburi), 1011079, 1030175, 30.0, 80.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlateHatsuburi), 1011079, 1030176, 45.0, 95.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(HeavyPlateJingasa), 1011079, 1030178, 45.0, 95.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(LightPlateJingasa), 1011079, 1030188, 45.0, 95.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(SmallPlateJingasa), 1011079, 1030191, 45.0, 95.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(DecorativePlateKabuto), 1011079, 1030179, 90.0, 140.0, typeof(IronIngot), 1044036, + 25, 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlateBattleKabuto), 1011079, 1030192, 90.0, 140.0, typeof(IronIngot), 1044036, 25, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(StandardPlateKabuto), 1011079, 1030196, 90.0, 140.0, typeof(IronIngot), 1044036, 25, + 1044037); + SetNeededExpansion(index, Expansion.SE); + + if (Core.ML) + { + index = AddCraft(typeof(Circlet), 1011079, 1032645, 62.1, 112.1, typeof(IronIngot), 1044036, 6, 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(RoyalCirclet), 1011079, 1032646, 70.0, 120.0, typeof(IronIngot), 1044036, 6, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(GemmedCirclet), 1011079, 1032647, 75.0, 125.0, typeof(IronIngot), 1044036, 6, + 1044037); + AddRes(index, typeof(Tourmaline), 1044237, 1, 1044240); + AddRes(index, typeof(Amethyst), 1044236, 1, 1044240); + AddRes(index, typeof(BlueDiamond), 1032696, 1, 1044240); + SetNeededExpansion(index, Expansion.ML); + } + } + + #endregion + + #region Shields + + AddCraft(typeof(Buckler), 1011080, 1027027, -25.0, 25.0, typeof(IronIngot), 1044036, 10, 1044037); + AddCraft(typeof(BronzeShield), 1011080, 1027026, -15.2, 34.8, typeof(IronIngot), 1044036, 12, 1044037); + AddCraft(typeof(HeaterShield), 1011080, 1027030, 24.3, 74.3, typeof(IronIngot), 1044036, 18, 1044037); + AddCraft(typeof(MetalShield), 1011080, 1027035, -10.2, 39.8, typeof(IronIngot), 1044036, 14, 1044037); + AddCraft(typeof(MetalKiteShield), 1011080, 1027028, 4.6, 54.6, typeof(IronIngot), 1044036, 16, 1044037); + AddCraft(typeof(WoodenKiteShield), 1011080, 1027032, -15.2, 34.8, typeof(IronIngot), 1044036, 8, 1044037); + + if (Core.AOS) + { + AddCraft(typeof(ChaosShield), 1011080, 1027107, 85.0, 135.0, typeof(IronIngot), 1044036, 25, 1044037); + AddCraft(typeof(OrderShield), 1011080, 1027108, 85.0, 135.0, typeof(IronIngot), 1044036, 25, 1044037); + } + + #endregion + + #region Bladed + + if (Core.AOS) + AddCraft(typeof(BoneHarvester), 1011081, 1029915, 33.0, 83.0, typeof(IronIngot), 1044036, 10, 1044037); + + AddCraft(typeof(Broadsword), 1011081, 1023934, 35.4, 85.4, typeof(IronIngot), 1044036, 10, 1044037); + + if (Core.AOS) + AddCraft(typeof(CrescentBlade), 1011081, 1029921, 45.0, 95.0, typeof(IronIngot), 1044036, 14, 1044037); + + AddCraft(typeof(Cutlass), 1011081, 1025185, 24.3, 74.3, typeof(IronIngot), 1044036, 8, 1044037); + AddCraft(typeof(Dagger), 1011081, 1023921, -0.4, 49.6, typeof(IronIngot), 1044036, 3, 1044037); + AddCraft(typeof(Katana), 1011081, 1025119, 44.1, 94.1, typeof(IronIngot), 1044036, 8, 1044037); + AddCraft(typeof(Kryss), 1011081, 1025121, 36.7, 86.7, typeof(IronIngot), 1044036, 8, 1044037); + AddCraft(typeof(Longsword), 1011081, 1023937, 28.0, 78.0, typeof(IronIngot), 1044036, 12, 1044037); + AddCraft(typeof(Scimitar), 1011081, 1025046, 31.7, 81.7, typeof(IronIngot), 1044036, 10, 1044037); + AddCraft(typeof(VikingSword), 1011081, 1025049, 24.3, 74.3, typeof(IronIngot), 1044036, 14, 1044037); + + if (Core.SE) + { + index = AddCraft(typeof(NoDachi), 1011081, 1030221, 75.0, 125.0, typeof(IronIngot), 1044036, 18, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Wakizashi), 1011081, 1030223, 50.0, 100.0, typeof(IronIngot), 1044036, 8, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Lajatang), 1011081, 1030226, 80.0, 130.0, typeof(IronIngot), 1044036, 25, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Daisho), 1011081, 1030228, 60.0, 110.0, typeof(IronIngot), 1044036, 15, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Tekagi), 1011081, 1030230, 55.0, 105.0, typeof(IronIngot), 1044036, 12, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Shuriken), 1011081, 1030231, 45.0, 95.0, typeof(IronIngot), 1044036, 5, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Kama), 1011081, 1030232, 40.0, 90.0, typeof(IronIngot), 1044036, 14, 1044037); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Sai), 1011081, 1030234, 50.0, 100.0, typeof(IronIngot), 1044036, 12, 1044037); + SetNeededExpansion(index, Expansion.SE); + + if (Core.ML) + { + index = AddCraft(typeof(RadiantScimitar), 1011081, 1031571, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(WarCleaver), 1011081, 1031567, 70.0, 120.0, typeof(IronIngot), 1044036, 18, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ElvenSpellblade), 1011081, 1031564, 70.0, 120.0, typeof(IronIngot), 1044036, 14, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(AssassinSpike), 1011081, 1031565, 70.0, 120.0, typeof(IronIngot), 1044036, 9, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(Leafblade), 1011081, 1031566, 70.0, 120.0, typeof(IronIngot), 1044036, 12, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(RuneBlade), 1011081, 1031570, 70.0, 120.0, typeof(IronIngot), 1044036, 15, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ElvenMachete), 1011081, 1031573, 70.0, 120.0, typeof(IronIngot), 1044036, 14, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(RuneCarvingKnife), 1011081, 1072915, 70.0, 120.0, typeof(IronIngot), 1044036, 9, + 1044037); + AddRes(index, typeof(DreadHornMane), 1032682, 1, 1053098); + AddRes(index, typeof(Putrefication), 1032678, 10, 1053098); + AddRes(index, typeof(Muculent), 1032680, 10, 1053098); + AddRareRecipe(index, 0); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ColdForgedBlade), 1011081, 1072916, 70.0, 120.0, typeof(IronIngot), 1044036, 18, + 1044037); + AddRes(index, typeof(GrizzledBones), 1032684, 1, 1053098); + AddRes(index, typeof(Taint), 1032684, 10, 1053098); + AddRes(index, typeof(Blight), 1032675, 10, 1053098); + AddRareRecipe(index, 1); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(OverseerSunderedBlade), 1011081, 1072920, 70.0, 120.0, typeof(IronIngot), + 1044036, 15, 1044037); + AddRes(index, typeof(GrizzledBones), 1032684, 1, 1053098); + AddRes(index, typeof(Blight), 1032675, 10, 1053098); + AddRes(index, typeof(Scourge), 1032677, 10, 1053098); + AddRareRecipe(index, 2); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(LuminousRuneBlade), 1011081, 1072922, 70.0, 120.0, typeof(IronIngot), 1044036, + 15, 1044037); + AddRes(index, typeof(GrizzledBones), 1032684, 1, 1053098); + AddRes(index, typeof(Corruption), 1032676, 10, 1053098); + AddRes(index, typeof(Putrefication), 1032678, 10, 1053098); + AddRareRecipe(index, 3); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TrueSpellblade), 1011081, 1073513, 75.0, 125.0, typeof(IronIngot), 1044036, 14, + 1044037); + AddRes(index, typeof(BlueDiamond), 1032696, 1, 1044240); + AddRecipe(index, 4); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(IcySpellblade), 1011081, 1073514, 75.0, 125.0, typeof(IronIngot), 1044036, 14, + 1044037); + AddRes(index, typeof(Turquoise), 1032691, 1, 1044240); + AddRecipe(index, 5); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(FierySpellblade), 1011081, 1073515, 75.0, 125.0, typeof(IronIngot), 1044036, 14, + 1044037); + AddRes(index, typeof(FireRuby), 1032695, 1, 1044240); + AddRecipe(index, 6); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SpellbladeOfDefense), 1011081, 1073516, 75.0, 125.0, typeof(IronIngot), 1044036, + 18, 1044037); + AddRes(index, typeof(WhitePearl), 1032694, 1, 1044240); + AddRecipe(index, 7); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TrueAssassinSpike), 1011081, 1073517, 75.0, 125.0, typeof(IronIngot), 1044036, 9, + 1044037); + AddRes(index, typeof(DarkSapphire), 1032690, 1, 1044240); + AddRecipe(index, 8); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ChargedAssassinSpike), 1011081, 1073518, 75.0, 125.0, typeof(IronIngot), 1044036, + 9, 1044037); + AddRes(index, typeof(EcruCitrine), 1032693, 1, 1044240); + AddRecipe(index, 9); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(MagekillerAssassinSpike), 1011081, 1073519, 75.0, 125.0, typeof(IronIngot), + 1044036, 9, 1044037); + AddRes(index, typeof(BrilliantAmber), 1032697, 1, 1044240); + AddRecipe(index, 10); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(WoundingAssassinSpike), 1011081, 1073520, 75.0, 125.0, typeof(IronIngot), + 1044036, 9, 1044037); + AddRes(index, typeof(PerfectEmerald), 1032692, 1, 1044240); + AddRecipe(index, 11); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TrueLeafblade), 1011081, 1073521, 75.0, 125.0, typeof(IronIngot), 1044036, 12, + 1044037); + AddRes(index, typeof(BlueDiamond), 1032696, 1, 1044240); + AddRecipe(index, 12); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(Luckblade), 1011081, 1073522, 75.0, 125.0, typeof(IronIngot), 1044036, 12, + 1044037); + AddRes(index, typeof(WhitePearl), 1032694, 1, 1044240); + AddRecipe(index, 13); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(MagekillerLeafblade), 1011081, 1073523, 75.0, 125.0, typeof(IronIngot), 1044036, + 12, 1044037); + AddRes(index, typeof(FireRuby), 1032695, 1, 1044240); + AddRecipe(index, 14); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(LeafbladeOfEase), 1011081, 1073524, 75.0, 125.0, typeof(IronIngot), 1044036, 12, + 1044037); + AddRes(index, typeof(PerfectEmerald), 1032692, 1, 1044240); + AddRecipe(index, 15); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(KnightsWarCleaver), 1011081, 1073525, 75.0, 125.0, typeof(IronIngot), 1044036, + 18, 1044037); + AddRes(index, typeof(PerfectEmerald), 1032692, 1, 1044240); + AddRecipe(index, 16); + SetNeededExpansion(index, Expansion.ML); + + // TODO + index = AddCraft(typeof(ButchersWarCleaver), 1011081, 1073526, 75.0, 125.0, typeof(IronIngot), 1044036, + 18, 1044037); + AddRes(index, typeof(Turquoise), 1032691, 1, 1044240); + AddRecipe(index, 17); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SerratedWarCleaver), 1011081, 1073527, 75.0, 125.0, typeof(IronIngot), 1044036, + 18, 1044037); + AddRes(index, typeof(EcruCitrine), 1032693, 1, 1044240); + AddRecipe(index, 18); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TrueWarCleaver), 1011081, 1073528, 75.0, 125.0, typeof(IronIngot), 1044036, 18, + 1044037); + AddRes(index, typeof(BrilliantAmber), 1032697, 1, 1044240); + AddRecipe(index, 19); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(AdventurersMachete), 1011081, 1073533, 75.0, 125.0, typeof(IronIngot), 1044036, + 14, 1044037); + AddRes(index, typeof(WhitePearl), 1032694, 1, 1044240); + AddRecipe(index, 20); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(OrcishMachete), 1011081, 1073534, 75.0, 125.0, typeof(IronIngot), 1044036, 14, + 1044037); + AddRes(index, typeof(Scourge), 1072136, 1, 1042081); + AddRecipe(index, 21); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(MacheteOfDefense), 1011081, 1073535, 75.0, 125.0, typeof(IronIngot), 1044036, 14, + 1044037); + AddRes(index, typeof(BrilliantAmber), 1032697, 1, 1044240); + AddRecipe(index, 22); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(DiseasedMachete), 1011081, 1073536, 75.0, 125.0, typeof(IronIngot), 1044036, 14, + 1044037); + AddRes(index, typeof(Blight), 1072134, 1, 1042081); + AddRecipe(index, 23); + SetNeededExpansion(index, Expansion.ML); + + // TODO + index = AddCraft(typeof(Runesabre), 1011081, 1073537, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(Turquoise), 1032691, 1, 1044240); + AddRecipe(index, 24); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(MagesRuneBlade), 1011081, 1073538, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(BlueDiamond), 1032696, 1, 1044240); + AddRecipe(index, 25); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(RuneBladeOfKnowledge), 1011081, 1073539, 75.0, 125.0, typeof(IronIngot), 1044036, + 15, 1044037); + AddRes(index, typeof(EcruCitrine), 1032693, 1, 1044240); + AddRecipe(index, 26); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(CorruptedRuneBlade), 1011081, 1073540, 75.0, 125.0, typeof(IronIngot), 1044036, + 15, 1044037); + AddRes(index, typeof(Corruption), 1072135, 1, 1042081); + AddRecipe(index, 27); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TrueRadiantScimitar), 1011081, 1073541, 75.0, 125.0, typeof(IronIngot), 1044036, + 15, 1044037); + AddRes(index, typeof(BrilliantAmber), 1032697, 1, 1044240); + AddRecipe(index, 28); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(DarkglowScimitar), 1011081, 1073542, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(DarkSapphire), 1032690, 1, 1044240); + AddRecipe(index, 29); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(IcyScimitar), 1011081, 1073543, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(DarkSapphire), 1032690, 1, 1044240); + AddRecipe(index, 30); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TwinklingScimitar), 1011081, 1073544, 75.0, 125.0, typeof(IronIngot), 1044036, + 15, 1044037); + AddRes(index, typeof(DarkSapphire), 1032690, 1, 1044240); + AddRecipe(index, 31); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(BoneMachete), 1011081, 1020526, 45.0, 95.0, typeof(IronIngot), 1044036, 20, + 1044037); + AddRes(index, typeof(Bone), 1049064, 6, 1049063); + AddQuestRecipe(index, 32); + SetNeededExpansion(index, Expansion.ML); + } + } + + #endregion + + #region Axes + + AddCraft(typeof(Axe), 1011082, 1023913, 34.2, 84.2, typeof(IronIngot), 1044036, 14, 1044037); + AddCraft(typeof(BattleAxe), 1011082, 1023911, 30.5, 80.5, typeof(IronIngot), 1044036, 14, 1044037); + AddCraft(typeof(DoubleAxe), 1011082, 1023915, 29.3, 79.3, typeof(IronIngot), 1044036, 12, 1044037); + AddCraft(typeof(ExecutionersAxe), 1011082, 1023909, 34.2, 84.2, typeof(IronIngot), 1044036, 14, 1044037); + AddCraft(typeof(LargeBattleAxe), 1011082, 1025115, 28.0, 78.0, typeof(IronIngot), 1044036, 12, 1044037); + AddCraft(typeof(TwoHandedAxe), 1011082, 1025187, 33.0, 83.0, typeof(IronIngot), 1044036, 16, 1044037); + AddCraft(typeof(WarAxe), 1011082, 1025040, 39.1, 89.1, typeof(IronIngot), 1044036, 16, 1044037); + + if (Core.ML) + { + index = AddCraft(typeof(OrnateAxe), 1011082, 1031572, 70.0, 120.0, typeof(IronIngot), 1044036, 18, 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(GuardianAxe), 1011082, 1073545, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(BlueDiamond), 1032696, 1, 1044240); + AddRecipe(index, 33); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SingingAxe), 1011082, 1073546, 75.0, 125.0, typeof(IronIngot), 1044036, 15, 1044037); + AddRes(index, typeof(BrilliantAmber), 1032697, 1, 1044240); + AddRecipe(index, 34); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ThunderingAxe), 1011082, 1073547, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(EcruCitrine), 1032693, 1, 1044240); + AddRecipe(index, 35); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(HeavyOrnateAxe), 1011082, 1073548, 75.0, 125.0, typeof(IronIngot), 1044036, 15, + 1044037); + AddRes(index, typeof(Turquoise), 1032691, 1, 1044240); + AddRecipe(index, 36); + SetNeededExpansion(index, Expansion.ML); + } + + #endregion + + #region Pole Arms + + AddCraft(typeof(Bardiche), 1011083, 1023917, 31.7, 81.7, typeof(IronIngot), 1044036, 18, 1044037); + + if (Core.AOS) + AddCraft(typeof(BladedStaff), 1011083, 1029917, 40.0, 90.0, typeof(IronIngot), 1044036, 12, 1044037); + + if (Core.AOS) + AddCraft(typeof(DoubleBladedStaff), 1011083, 1029919, 45.0, 95.0, typeof(IronIngot), 1044036, 16, 1044037); + + AddCraft(typeof(Halberd), 1011083, 1025183, 39.1, 89.1, typeof(IronIngot), 1044036, 20, 1044037); + + if (Core.AOS) + AddCraft(typeof(Lance), 1011083, 1029920, 48.0, 98.0, typeof(IronIngot), 1044036, 20, 1044037); + + if (Core.AOS) + AddCraft(typeof(Pike), 1011083, 1029918, 47.0, 97.0, typeof(IronIngot), 1044036, 12, 1044037); + + AddCraft(typeof(ShortSpear), 1011083, 1025123, 45.3, 95.3, typeof(IronIngot), 1044036, 6, 1044037); + + if (Core.AOS) + AddCraft(typeof(Scythe), 1011083, 1029914, 39.0, 89.0, typeof(IronIngot), 1044036, 14, 1044037); + + AddCraft(typeof(Spear), 1011083, 1023938, 49.0, 99.0, typeof(IronIngot), 1044036, 12, 1044037); + AddCraft(typeof(WarFork), 1011083, 1025125, 42.9, 92.9, typeof(IronIngot), 1044036, 12, 1044037); + + // Not craftable (is this an AOS change ??) + //AddCraft( typeof( Pitchfork ), 1011083, 1023720, 36.1, 86.1, typeof( IronIngot ), 1044036, 12, 1044037 ); + + #endregion + + #region Bashing + + AddCraft(typeof(HammerPick), 1011084, 1025181, 34.2, 84.2, typeof(IronIngot), 1044036, 16, 1044037); + AddCraft(typeof(Mace), 1011084, 1023932, 14.5, 64.5, typeof(IronIngot), 1044036, 6, 1044037); + AddCraft(typeof(Maul), 1011084, 1025179, 19.4, 69.4, typeof(IronIngot), 1044036, 10, 1044037); + + if (Core.AOS) + AddCraft(typeof(Scepter), 1011084, 1029916, 21.4, 71.4, typeof(IronIngot), 1044036, 10, 1044037); + + AddCraft(typeof(WarMace), 1011084, 1025127, 28.0, 78.0, typeof(IronIngot), 1044036, 14, 1044037); + AddCraft(typeof(WarHammer), 1011084, 1025177, 34.2, 84.2, typeof(IronIngot), 1044036, 16, 1044037); + + if (Core.SE) + { + index = AddCraft(typeof(Tessen), 1011084, 1030222, 85.0, 135.0, typeof(IronIngot), 1044036, 16, 1044037); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 10, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + if (Core.ML) + { + index = AddCraft(typeof(DiamondMace), 1011084, 1031556, 70.0, 120.0, typeof(IronIngot), 1044036, 20, + 1044037); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ShardThrasher), 1011084, 1072918, 70.0, 120.0, typeof(IronIngot), 1044036, 20, + 1044037); + AddRes(index, typeof(EyeOfTheTravesty), 1073126, 1, 1042081); + AddRes(index, typeof(Muculent), 1072139, 10, 1042081); + AddRes(index, typeof(Corruption), 1072135, 10, 1042081); + AddRareRecipe(index, 37); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(RubyMace), 1011084, 1073529, 75.0, 125.0, typeof(IronIngot), 1044036, 20, 1044037); + AddRes(index, typeof(FireRuby), 1032695, 1, 1044240); + AddRecipe(index, 38); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(EmeraldMace), 1011084, 1073530, 75.0, 125.0, typeof(IronIngot), 1044036, 20, + 1044037); + AddRes(index, typeof(PerfectEmerald), 1032692, 1, 1044240); + AddRecipe(index, 39); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SapphireMace), 1011084, 1073531, 75.0, 125.0, typeof(IronIngot), 1044036, 20, + 1044037); + AddRes(index, typeof(DarkSapphire), 1032690, 1, 1044240); + AddRecipe(index, 40); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SilverEtchedMace), 1011084, 1073532, 75.0, 125.0, typeof(IronIngot), 1044036, 20, + 1044037); + AddRes(index, typeof(BlueDiamond), 1032696, 1, 1044240); + AddRecipe(index, 41); + SetNeededExpansion(index, Expansion.ML); + } + + #endregion + + #region Dragon Scale Armor + + index = AddCraft(typeof(DragonGloves), 1053114, 1029795, 68.9, 118.9, typeof(RedScales), 1060883, 16, 1060884); + SetUseSubRes2(index, true); - Map map = from.Map; - - if ( map == null ) - return; + index = AddCraft(typeof(DragonHelm), 1053114, 1029797, 72.6, 122.6, typeof(RedScales), 1060883, 20, 1060884); + SetUseSubRes2(index, true); - IPooledEnumerable eable = map.GetItemsInRange( from.Location, range ); - - foreach ( Item item in eable ) - { - Type type = item.GetType(); - - bool isAnvil = ( type.IsDefined( typeofAnvil, false ) || item.ItemID == 4015 || item.ItemID == 4016 || item.ItemID == 0x2DD5 || item.ItemID == 0x2DD6 ); - bool isForge = ( type.IsDefined( typeofForge, false ) || item.ItemID == 4017 || (item.ItemID >= 6522 && item.ItemID <= 6569) || item.ItemID == 0x2DD8 ); - - if ( isAnvil || isForge ) - { - if ( (from.Z + 16) < item.Z || (item.Z + 16) < from.Z || !from.InLOS( item ) ) - continue; - - anvil = anvil || isAnvil; - forge = forge || isForge; - - if ( anvil && forge ) - break; - } - } - - eable.Free(); - - for ( int x = -range; (!anvil || !forge) && x <= range; ++x ) - { - for ( int y = -range; (!anvil || !forge) && y <= range; ++y ) - { - StaticTile[] tiles = map.Tiles.GetStaticTiles( from.X+x, from.Y+y, true ); - - for ( int i = 0; (!anvil || !forge) && i < tiles.Length; ++i ) - { - int id = tiles[i].ID; - - bool isAnvil = ( id == 4015 || id == 4016 || id == 0x2DD5 || id == 0x2DD6 ); - bool isForge = ( id == 4017 || (id >= 6522 && id <= 6569) || id == 0x2DD8 ); - - if ( isAnvil || isForge ) - { - if ( (from.Z + 16) < tiles[i].Z || (tiles[i].Z + 16) < from.Z || !from.InLOS( new Point3D( from.X+x, from.Y+y, tiles[i].Z + (tiles[i].Height/2) + 1 ) ) ) - continue; - - anvil = anvil || isAnvil; - forge = forge || isForge; - } - } - } - } - } - - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckTool( tool, from ) ) - return 1048146; // If you have a tool equipped, you must use that tool. - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. - - bool anvil, forge; - CheckAnvilAndForge( from, 2, out anvil, out forge ); - - if ( anvil && forge ) - return 0; - - return 1044267; // You must be near an anvil and a forge to smith items. - } - - public override void PlayCraftEffect( Mobile from ) - { - // no animation, instant sound - //if ( from.Body.Type == BodyType.Human && !from.Mounted ) - // from.Animate( 9, 5, 1, true, false, 0 ); - //new InternalTimer( from ).Start(); - - from.PlaySound( 0x2A ); - } - - // Delay to synchronize the sound with the hit on the anvil - private class InternalTimer : Timer - { - private Mobile m_From; - - public InternalTimer( Mobile from ) : base( TimeSpan.FromSeconds( 0.7 ) ) - { - m_From = from; - } - - protected override void OnTick() - { - m_From.PlaySound( 0x2A ); - } - } - - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool - - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } - - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } - - public override void InitCraftList() - { - /* - Synthax for a SIMPLE craft item - AddCraft( ObjectType, Group, MinSkill, MaxSkill, ResourceType, Amount, Message ) - - ObjectType : The type of the object you want to add to the build list. - Group : The group in wich the object will be showed in the craft menu. - MinSkill : The minimum of skill value - MaxSkill : The maximum of skill value - ResourceType : The type of the resource the mobile need to create the item - Amount : The amount of the ResourceType it need to create the item - Message : String or Int for Localized. The message that will be sent to the mobile, if the specified resource is missing. - - Synthax for a COMPLEXE craft item. A complexe item is an item that need either more than - only one skill, or more than only one resource. - - Coming soon.... - */ - - #region Ringmail - AddCraft( typeof( RingmailGloves ), 1011076, 1025099, 12.0, 62.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddCraft( typeof( RingmailLegs ), 1011076, 1025104, 19.4, 69.4, typeof( IronIngot ), 1044036, 16, 1044037 ); - AddCraft( typeof( RingmailArms ), 1011076, 1025103, 16.9, 66.9, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddCraft( typeof( RingmailChest ), 1011076, 1025100, 21.9, 71.9, typeof( IronIngot ), 1044036, 18, 1044037 ); - #endregion - - #region Chainmail - AddCraft( typeof( ChainCoif ), 1011077, 1025051, 14.5, 64.5, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddCraft( typeof( ChainLegs ), 1011077, 1025054, 36.7, 86.7, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddCraft( typeof( ChainChest ), 1011077, 1025055, 39.1, 89.1, typeof( IronIngot ), 1044036, 20, 1044037 ); - #endregion - - int index = -1; - - #region Platemail - AddCraft( typeof( PlateArms ), 1011078, 1025136, 66.3, 116.3, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddCraft( typeof( PlateGloves ), 1011078, 1025140, 58.9, 108.9, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddCraft( typeof( PlateGorget ), 1011078, 1025139, 56.4, 106.4, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddCraft( typeof( PlateLegs ), 1011078, 1025137, 68.8, 118.8, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddCraft( typeof( PlateChest ), 1011078, 1046431, 75.0, 125.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - AddCraft( typeof( FemalePlateChest ), 1011078, 1046430, 44.1, 94.1, typeof( IronIngot ), 1044036, 20, 1044037 ); - - if ( Core.AOS ) // exact pre-aos functionality unknown - AddCraft( typeof( DragonBardingDeed ), 1011078, 1053012, 72.5, 122.5, typeof( IronIngot ), 1044036, 750, 1044037 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( PlateMempo ), 1011078, 1030180, 80.0, 130.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlateDo ), 1011078, 1030184, 80.0, 130.0, typeof( IronIngot ), 1044036, 28, 1044037 ); //Double check skill - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlateHiroSode ), 1011078, 1030187, 80.0, 130.0, typeof( IronIngot ), 1044036, 16, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlateSuneate ), 1011078, 1030195, 65.0, 115.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlateHaidate ), 1011078, 1030200, 65.0, 115.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - } - #endregion - - #region Helmets - AddCraft( typeof( Bascinet ), 1011079, 1025132, 8.3, 58.3, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddCraft( typeof( CloseHelm ), 1011079, 1025128, 37.9, 87.9, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddCraft( typeof( Helmet ), 1011079, 1025130, 37.9, 87.9, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddCraft( typeof( NorseHelm ), 1011079, 1025134, 37.9, 87.9, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddCraft( typeof( PlateHelm ), 1011079, 1025138, 62.6, 112.6, typeof( IronIngot ), 1044036, 15, 1044037 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( ChainHatsuburi ), 1011079, 1030175, 30.0, 80.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlateHatsuburi ), 1011079, 1030176, 45.0, 95.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( HeavyPlateJingasa ), 1011079, 1030178, 45.0, 95.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( LightPlateJingasa ), 1011079, 1030188, 45.0, 95.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( SmallPlateJingasa ), 1011079, 1030191, 45.0, 95.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( DecorativePlateKabuto ), 1011079, 1030179, 90.0, 140.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlateBattleKabuto ), 1011079, 1030192, 90.0, 140.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( StandardPlateKabuto ), 1011079, 1030196, 90.0, 140.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - if ( Core.ML ) - { - index = AddCraft( typeof( Circlet ), 1011079, 1032645, 62.1, 112.1, typeof( IronIngot ), 1044036, 6, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( RoyalCirclet ), 1011079, 1032646, 70.0, 120.0, typeof( IronIngot ), 1044036, 6, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( GemmedCirclet ), 1011079, 1032647, 75.0, 125.0, typeof( IronIngot ), 1044036, 6, 1044037 ); - AddRes( index, typeof( Tourmaline ), 1044237, 1, 1044240 ); - AddRes( index, typeof( Amethyst ), 1044236, 1, 1044240 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 1, 1044240 ); - SetNeededExpansion( index, Expansion.ML ); - } - } - #endregion - - #region Shields - AddCraft( typeof( Buckler ), 1011080, 1027027, -25.0, 25.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddCraft( typeof( BronzeShield ), 1011080, 1027026, -15.2, 34.8, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddCraft( typeof( HeaterShield ), 1011080, 1027030, 24.3, 74.3, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddCraft( typeof( MetalShield ), 1011080, 1027035, -10.2, 39.8, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddCraft( typeof( MetalKiteShield ), 1011080, 1027028, 4.6, 54.6, typeof( IronIngot ), 1044036, 16, 1044037 ); - AddCraft( typeof( WoodenKiteShield ), 1011080, 1027032, -15.2, 34.8, typeof( IronIngot ), 1044036, 8, 1044037 ); - - if ( Core.AOS ) - { - AddCraft( typeof( ChaosShield ), 1011080, 1027107, 85.0, 135.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - AddCraft( typeof( OrderShield ), 1011080, 1027108, 85.0, 135.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - } - #endregion - - #region Bladed - - if ( Core.AOS ) - AddCraft( typeof( BoneHarvester ), 1011081, 1029915, 33.0, 83.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - - AddCraft( typeof( Broadsword ), 1011081, 1023934, 35.4, 85.4, typeof( IronIngot ), 1044036, 10, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( CrescentBlade ), 1011081, 1029921, 45.0, 95.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - - AddCraft( typeof( Cutlass ), 1011081, 1025185, 24.3, 74.3, typeof( IronIngot ), 1044036, 8, 1044037 ); - AddCraft( typeof( Dagger ), 1011081, 1023921, -0.4, 49.6, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddCraft( typeof( Katana ),1011081, 1025119, 44.1, 94.1, typeof( IronIngot ), 1044036, 8, 1044037 ); - AddCraft( typeof( Kryss ), 1011081, 1025121, 36.7, 86.7, typeof( IronIngot ), 1044036, 8, 1044037 ); - AddCraft( typeof( Longsword ), 1011081, 1023937, 28.0, 78.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddCraft( typeof( Scimitar ), 1011081, 1025046, 31.7, 81.7, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddCraft( typeof( VikingSword ), 1011081, 1025049, 24.3, 74.3, typeof( IronIngot ), 1044036, 14, 1044037 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( NoDachi ), 1011081, 1030221, 75.0, 125.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Wakizashi ), 1011081, 1030223, 50.0, 100.0, typeof( IronIngot ), 1044036, 8, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Lajatang ), 1011081, 1030226, 80.0, 130.0, typeof( IronIngot ), 1044036, 25, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Daisho ), 1011081, 1030228, 60.0, 110.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Tekagi ), 1011081, 1030230, 55.0, 105.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Shuriken ), 1011081, 1030231, 45.0, 95.0, typeof( IronIngot ), 1044036, 5, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Kama ), 1011081, 1030232, 40.0, 90.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Sai ), 1011081, 1030234, 50.0, 100.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - if ( Core.ML ) - { - index = AddCraft( typeof( RadiantScimitar ), 1011081, 1031571, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( WarCleaver ), 1011081, 1031567, 70.0, 120.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ElvenSpellblade ), 1011081, 1031564, 70.0, 120.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( AssassinSpike ), 1011081, 1031565, 70.0, 120.0, typeof( IronIngot ), 1044036, 9, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( Leafblade ), 1011081, 1031566, 70.0, 120.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( RuneBlade ), 1011081, 1031570, 70.0, 120.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ElvenMachete ), 1011081, 1031573, 70.0, 120.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( RuneCarvingKnife ), 1011081, 1072915, 70.0, 120.0, typeof( IronIngot ), 1044036, 9, 1044037 ); - AddRes( index, typeof( DreadHornMane ), 1032682, 1, 1053098 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); - AddRes( index, typeof( Muculent ), 1032680, 10, 1053098 ); - AddRareRecipe( index, 0 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ColdForgedBlade ), 1011081, 1072916, 70.0, 120.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddRes( index, typeof( GrizzledBones ), 1032684, 1, 1053098 ); - AddRes( index, typeof( Taint ), 1032684, 10, 1053098 ); - AddRes( index, typeof( Blight ), 1032675, 10, 1053098 ); - AddRareRecipe( index, 1 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( OverseerSunderedBlade ), 1011081, 1072920, 70.0, 120.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( GrizzledBones ), 1032684, 1, 1053098 ); - AddRes( index, typeof( Blight ), 1032675, 10, 1053098 ); - AddRes( index, typeof( Scourge ), 1032677, 10, 1053098 ); - AddRareRecipe( index, 2 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( LuminousRuneBlade ), 1011081, 1072922, 70.0, 120.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( GrizzledBones ), 1032684, 1, 1053098 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1053098 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); - AddRareRecipe( index, 3 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TrueSpellblade ), 1011081, 1073513, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 1, 1044240 ); - AddRecipe( index, 4 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( IcySpellblade ), 1011081, 1073514, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( Turquoise ), 1032691, 1, 1044240 ); - AddRecipe( index, 5 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( FierySpellblade ), 1011081, 1073515, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( FireRuby ), 1032695, 1, 1044240 ); - AddRecipe( index, 6 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SpellbladeOfDefense ), 1011081, 1073516, 75.0, 125.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddRes( index, typeof( WhitePearl ), 1032694, 1, 1044240 ); - AddRecipe( index, 7 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TrueAssassinSpike ), 1011081, 1073517, 75.0, 125.0, typeof( IronIngot ), 1044036, 9, 1044037 ); - AddRes( index, typeof( DarkSapphire ), 1032690, 1, 1044240 ); - AddRecipe( index, 8 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ChargedAssassinSpike ), 1011081, 1073518, 75.0, 125.0, typeof( IronIngot ), 1044036, 9, 1044037 ); - AddRes( index, typeof( EcruCitrine ), 1032693, 1, 1044240 ); - AddRecipe( index, 9 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( MagekillerAssassinSpike ), 1011081, 1073519, 75.0, 125.0, typeof( IronIngot ), 1044036, 9, 1044037 ); - AddRes( index, typeof( BrilliantAmber ), 1032697, 1, 1044240 ); - AddRecipe( index, 10 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( WoundingAssassinSpike ), 1011081, 1073520, 75.0, 125.0, typeof( IronIngot ), 1044036, 9, 1044037 ); - AddRes( index, typeof( PerfectEmerald ), 1032692, 1, 1044240 ); - AddRecipe( index, 11 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TrueLeafblade ), 1011081, 1073521, 75.0, 125.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 1, 1044240 ); - AddRecipe( index, 12 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( Luckblade ), 1011081, 1073522, 75.0, 125.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddRes( index, typeof( WhitePearl ), 1032694, 1, 1044240 ); - AddRecipe( index, 13 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( MagekillerLeafblade ), 1011081, 1073523, 75.0, 125.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddRes( index, typeof( FireRuby ), 1032695, 1, 1044240 ); - AddRecipe( index, 14 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( LeafbladeOfEase ), 1011081, 1073524, 75.0, 125.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddRes( index, typeof( PerfectEmerald ), 1032692, 1, 1044240 ); - AddRecipe( index, 15 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( KnightsWarCleaver ), 1011081, 1073525, 75.0, 125.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddRes( index, typeof( PerfectEmerald ), 1032692, 1, 1044240 ); - AddRecipe( index, 16 ); - SetNeededExpansion( index, Expansion.ML ); - - // TODO - index = AddCraft( typeof( ButchersWarCleaver ), 1011081, 1073526, 75.0, 125.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddRes( index, typeof( Turquoise ), 1032691, 1, 1044240 ); - AddRecipe( index, 17 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SerratedWarCleaver ), 1011081, 1073527, 75.0, 125.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddRes( index, typeof( EcruCitrine ), 1032693, 1, 1044240 ); - AddRecipe( index, 18 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TrueWarCleaver ), 1011081, 1073528, 75.0, 125.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - AddRes( index, typeof( BrilliantAmber ), 1032697, 1, 1044240 ); - AddRecipe( index, 19 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( AdventurersMachete ), 1011081, 1073533, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( WhitePearl ), 1032694, 1, 1044240 ); - AddRecipe( index, 20 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( OrcishMachete ), 1011081, 1073534, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( Scourge ), 1072136, 1, 1042081 ); - AddRecipe( index, 21 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( MacheteOfDefense ), 1011081, 1073535, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( BrilliantAmber ), 1032697, 1, 1044240 ); - AddRecipe( index, 22 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( DiseasedMachete ), 1011081, 1073536, 75.0, 125.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddRes( index, typeof( Blight ), 1072134, 1, 1042081 ); - AddRecipe( index, 23 ); - SetNeededExpansion( index, Expansion.ML ); - - // TODO - index = AddCraft( typeof( Runesabre ), 1011081, 1073537, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( Turquoise ), 1032691, 1, 1044240 ); - AddRecipe( index, 24 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( MagesRuneBlade ), 1011081, 1073538, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 1, 1044240 ); - AddRecipe( index, 25 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( RuneBladeOfKnowledge ), 1011081, 1073539, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( EcruCitrine ), 1032693, 1, 1044240 ); - AddRecipe( index, 26 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( CorruptedRuneBlade ), 1011081, 1073540, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( Corruption ), 1072135, 1, 1042081 ); - AddRecipe( index, 27 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TrueRadiantScimitar ), 1011081, 1073541, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( BrilliantAmber ), 1032697, 1, 1044240 ); - AddRecipe( index, 28 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( DarkglowScimitar ), 1011081, 1073542, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( DarkSapphire ), 1032690, 1, 1044240 ); - AddRecipe( index, 29 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( IcyScimitar ), 1011081, 1073543, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( DarkSapphire ), 1032690, 1, 1044240 ); - AddRecipe( index, 30 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TwinklingScimitar ), 1011081, 1073544, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( DarkSapphire ), 1032690, 1, 1044240 ); - AddRecipe( index, 31 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( BoneMachete ), 1011081, 1020526, 45.0, 95.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddRes( index, typeof( Bone ), 1049064, 6, 1049063 ); - AddQuestRecipe( index, 32 ); - SetNeededExpansion( index, Expansion.ML ); - } - } - #endregion - - #region Axes - AddCraft( typeof( Axe ), 1011082, 1023913, 34.2, 84.2, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddCraft( typeof( BattleAxe ), 1011082, 1023911, 30.5, 80.5, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddCraft( typeof( DoubleAxe ), 1011082, 1023915, 29.3, 79.3, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddCraft( typeof( ExecutionersAxe ), 1011082, 1023909, 34.2, 84.2, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddCraft( typeof( LargeBattleAxe ), 1011082, 1025115, 28.0, 78.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddCraft( typeof( TwoHandedAxe ), 1011082, 1025187, 33.0, 83.0, typeof( IronIngot ), 1044036, 16, 1044037 ); - AddCraft( typeof( WarAxe ), 1011082, 1025040, 39.1, 89.1, typeof( IronIngot ), 1044036, 16, 1044037 ); - - if ( Core.ML ) - { - index = AddCraft( typeof( OrnateAxe ), 1011082, 1031572, 70.0, 120.0, typeof( IronIngot ), 1044036, 18, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( GuardianAxe ), 1011082, 1073545, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 1, 1044240 ); - AddRecipe( index, 33 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SingingAxe ), 1011082, 1073546, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( BrilliantAmber ), 1032697, 1, 1044240 ); - AddRecipe( index, 34 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ThunderingAxe ), 1011082, 1073547, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( EcruCitrine ), 1032693, 1, 1044240 ); - AddRecipe( index, 35 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( HeavyOrnateAxe ), 1011082, 1073548, 75.0, 125.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - AddRes( index, typeof( Turquoise ), 1032691, 1, 1044240 ); - AddRecipe( index, 36 ); - SetNeededExpansion( index, Expansion.ML ); - - } - #endregion - - #region Pole Arms - - AddCraft( typeof( Bardiche ), 1011083, 1023917, 31.7, 81.7, typeof( IronIngot ), 1044036, 18, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( BladedStaff ), 1011083, 1029917, 40.0, 90.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( DoubleBladedStaff ), 1011083, 1029919, 45.0, 95.0, typeof( IronIngot ), 1044036, 16, 1044037 ); - - AddCraft( typeof( Halberd ), 1011083, 1025183, 39.1, 89.1, typeof( IronIngot ), 1044036, 20, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( Lance ), 1011083, 1029920, 48.0, 98.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( Pike ), 1011083, 1029918, 47.0, 97.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - - AddCraft( typeof( ShortSpear ), 1011083, 1025123, 45.3, 95.3, typeof( IronIngot ), 1044036, 6, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( Scythe ), 1011083, 1029914, 39.0, 89.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - - AddCraft( typeof( Spear ), 1011083, 1023938, 49.0, 99.0, typeof( IronIngot ), 1044036, 12, 1044037 ); - AddCraft( typeof( WarFork ), 1011083, 1025125, 42.9, 92.9, typeof( IronIngot ), 1044036, 12, 1044037 ); - - // Not craftable (is this an AOS change ??) - //AddCraft( typeof( Pitchfork ), 1011083, 1023720, 36.1, 86.1, typeof( IronIngot ), 1044036, 12, 1044037 ); - #endregion - - #region Bashing - AddCraft( typeof( HammerPick ), 1011084, 1025181, 34.2, 84.2, typeof( IronIngot ), 1044036, 16, 1044037 ); - AddCraft( typeof( Mace ), 1011084, 1023932, 14.5, 64.5, typeof( IronIngot ), 1044036, 6, 1044037 ); - AddCraft( typeof( Maul ), 1011084, 1025179, 19.4, 69.4, typeof( IronIngot ), 1044036, 10, 1044037 ); - - if ( Core.AOS ) - AddCraft( typeof( Scepter ), 1011084, 1029916, 21.4, 71.4, typeof( IronIngot ), 1044036, 10, 1044037 ); - - AddCraft( typeof( WarMace ), 1011084, 1025127, 28.0, 78.0, typeof( IronIngot ), 1044036, 14, 1044037 ); - AddCraft( typeof( WarHammer ), 1011084, 1025177, 34.2, 84.2, typeof( IronIngot ), 1044036, 16, 1044037 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( Tessen ), 1011084, 1030222, 85.0, 135.0, typeof( IronIngot ), 1044036, 16, 1044037 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 10, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - if ( Core.ML ) - { - index = AddCraft( typeof( DiamondMace ), 1011084, 1031556, 70.0, 120.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ShardThrasher ), 1011084, 1072918, 70.0, 120.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddRes( index, typeof( EyeOfTheTravesty ), 1073126, 1, 1042081 ); - AddRes( index, typeof( Muculent ), 1072139, 10, 1042081 ); - AddRes( index, typeof( Corruption ), 1072135, 10, 1042081 ); - AddRareRecipe( index, 37 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( RubyMace ), 1011084, 1073529, 75.0, 125.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddRes( index, typeof( FireRuby ), 1032695, 1, 1044240 ); - AddRecipe( index, 38 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( EmeraldMace ), 1011084, 1073530, 75.0, 125.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddRes( index, typeof( PerfectEmerald ), 1032692, 1, 1044240 ); - AddRecipe( index, 39 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SapphireMace ), 1011084, 1073531, 75.0, 125.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddRes( index, typeof( DarkSapphire ), 1032690, 1, 1044240 ); - AddRecipe( index, 40 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SilverEtchedMace ), 1011084, 1073532, 75.0, 125.0, typeof( IronIngot ), 1044036, 20, 1044037 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 1, 1044240 ); - AddRecipe( index, 41 ); - SetNeededExpansion( index, Expansion.ML ); - } - #endregion - - #region Dragon Scale Armor - index = AddCraft( typeof( DragonGloves ), 1053114, 1029795, 68.9, 118.9, typeof( RedScales ), 1060883, 16, 1060884 ); - SetUseSubRes2( index, true ); - - index = AddCraft( typeof( DragonHelm ), 1053114, 1029797, 72.6, 122.6, typeof( RedScales ), 1060883, 20, 1060884 ); - SetUseSubRes2( index, true ); - - index = AddCraft( typeof( DragonLegs ), 1053114, 1029799, 78.8, 128.8, typeof( RedScales ), 1060883, 28, 1060884 ); - SetUseSubRes2( index, true ); - - index = AddCraft( typeof( DragonArms ), 1053114, 1029815, 76.3, 126.3, typeof( RedScales ), 1060883, 24, 1060884 ); - SetUseSubRes2( index, true ); - - index = AddCraft( typeof( DragonChest ), 1053114, 1029793, 85.0, 135.0, typeof( RedScales ), 1060883, 36, 1060884 ); - SetUseSubRes2( index, true ); - #endregion - - // Set the overridable material - SetSubRes( typeof( IronIngot ), 1044022 ); - - // Add every material you want the player to be able to choose from - // This will override the overridable material - AddSubRes( typeof( IronIngot ), 1044022, 00.0, 1044036, 1044267 ); - AddSubRes( typeof( DullCopperIngot ), 1044023, 65.0, 1044036, 1044268 ); - AddSubRes( typeof( ShadowIronIngot ), 1044024, 70.0, 1044036, 1044268 ); - AddSubRes( typeof( CopperIngot ), 1044025, 75.0, 1044036, 1044268 ); - AddSubRes( typeof( BronzeIngot ), 1044026, 80.0, 1044036, 1044268 ); - AddSubRes( typeof( GoldIngot ), 1044027, 85.0, 1044036, 1044268 ); - AddSubRes( typeof( AgapiteIngot ), 1044028, 90.0, 1044036, 1044268 ); - AddSubRes( typeof( VeriteIngot ), 1044029, 95.0, 1044036, 1044268 ); - AddSubRes( typeof( ValoriteIngot ), 1044030, 99.0, 1044036, 1044268 ); - - SetSubRes2( typeof( RedScales ), 1060875 ); - - AddSubRes2( typeof( RedScales ), 1060875, 0.0, 1053137, 1044268 ); - AddSubRes2( typeof( YellowScales ), 1060876, 0.0, 1053137, 1044268 ); - AddSubRes2( typeof( BlackScales ), 1060877, 0.0, 1053137, 1044268 ); - AddSubRes2( typeof( GreenScales ), 1060878, 0.0, 1053137, 1044268 ); - AddSubRes2( typeof( WhiteScales ), 1060879, 0.0, 1053137, 1044268 ); - AddSubRes2( typeof( BlueScales ), 1060880, 0.0, 1053137, 1044268 ); - - Resmelt = true; - Repair = true; - MarkOption = true; - CanEnhance = Core.AOS; - } - } - - public class ForgeAttribute : Attribute - { - public ForgeAttribute() - { - } - } - - public class AnvilAttribute : Attribute - { - public AnvilAttribute() - { - } - } -} + index = AddCraft(typeof(DragonLegs), 1053114, 1029799, 78.8, 128.8, typeof(RedScales), 1060883, 28, 1060884); + SetUseSubRes2(index, true); + + index = AddCraft(typeof(DragonArms), 1053114, 1029815, 76.3, 126.3, typeof(RedScales), 1060883, 24, 1060884); + SetUseSubRes2(index, true); + + index = AddCraft(typeof(DragonChest), 1053114, 1029793, 85.0, 135.0, typeof(RedScales), 1060883, 36, 1060884); + SetUseSubRes2(index, true); + + #endregion + + // Set the overridable material + SetSubRes(typeof(IronIngot), 1044022); + + // Add every material you want the player to be able to choose from + // This will override the overridable material + AddSubRes(typeof(IronIngot), 1044022, 00.0, 1044036, 1044267); + AddSubRes(typeof(DullCopperIngot), 1044023, 65.0, 1044036, 1044268); + AddSubRes(typeof(ShadowIronIngot), 1044024, 70.0, 1044036, 1044268); + AddSubRes(typeof(CopperIngot), 1044025, 75.0, 1044036, 1044268); + AddSubRes(typeof(BronzeIngot), 1044026, 80.0, 1044036, 1044268); + AddSubRes(typeof(GoldIngot), 1044027, 85.0, 1044036, 1044268); + AddSubRes(typeof(AgapiteIngot), 1044028, 90.0, 1044036, 1044268); + AddSubRes(typeof(VeriteIngot), 1044029, 95.0, 1044036, 1044268); + AddSubRes(typeof(ValoriteIngot), 1044030, 99.0, 1044036, 1044268); + + SetSubRes2(typeof(RedScales), 1060875); + + AddSubRes2(typeof(RedScales), 1060875, 0.0, 1053137, 1044268); + AddSubRes2(typeof(YellowScales), 1060876, 0.0, 1053137, 1044268); + AddSubRes2(typeof(BlackScales), 1060877, 0.0, 1053137, 1044268); + AddSubRes2(typeof(GreenScales), 1060878, 0.0, 1053137, 1044268); + AddSubRes2(typeof(WhiteScales), 1060879, 0.0, 1053137, 1044268); + AddSubRes2(typeof(BlueScales), 1060880, 0.0, 1053137, 1044268); + + Resmelt = true; + Repair = true; + MarkOption = true; + CanEnhance = Core.AOS; + } + + // Delay to synchronize the sound with the hit on the anvil + private class InternalTimer : Timer + { + private Mobile m_From; + + public InternalTimer(Mobile from) : base(TimeSpan.FromSeconds(0.7)) + { + m_From = from; + } + + protected override void OnTick() + { + m_From.PlaySound(0x2A); + } + } + } + + public class ForgeAttribute : Attribute + { + } + + public class AnvilAttribute : Attribute + { + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefBowFletching.cs b/Scripts/Engines/Craft/DefBowFletching.cs index 3c0c4345e..52c3c371f 100644 --- a/Scripts/Engines/Craft/DefBowFletching.cs +++ b/Scripts/Engines/Craft/DefBowFletching.cs @@ -3,208 +3,213 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefBowFletching : CraftSystem - { - public override SkillName MainSkill => SkillName.Fletching; + public class DefBowFletching : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044006; + private DefBowFletching() : base(1, 1, 1.25) // base( 1, 2, 1.7 ) + { + } - private static CraftSystem m_CraftSystem; + public override SkillName MainSkill => SkillName.Fletching; - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefBowFletching(); + public override int GumpTitleNumber => 1044006; - return m_CraftSystem; - } - } + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefBowFletching(); - public override double GetChanceAtMin( CraftItem item ) - { - return 0.5; // 50% - } + return m_CraftSystem; + } + } - private DefBowFletching() : base( 1, 1, 1.25 )// base( 1, 2, 1.7 ) - { - } + public override CraftECA ECA => CraftECA.FiftyPercentChanceMinusTenPercent; - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override double GetChanceAtMin(CraftItem item) + { + return 0.5; // 50% + } - return 0; - } + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - public override void PlayCraftEffect( Mobile from ) - { - // no animation - //if ( from.Body.Type == BodyType.Human && !from.Mounted ) - // from.Animate( 33, 5, 1, true, false, 0 ); + return 0; + } - from.PlaySound( 0x55 ); - } + public override void PlayCraftEffect(Mobile from) + { + // no animation + //if ( from.Body.Type == BodyType.Human && !from.Mounted ) + // from.Animate( 33, 5, 1, true, false, 0 ); - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + from.PlaySound(0x55); + } - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } - public override CraftECA ECA => CraftECA.FiftyPercentChanceMinusTenPercent; + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } - public override void InitCraftList() - { - int index = -1; + public override void InitCraftList() + { + int index = -1; - // Materials - AddCraft( typeof( Kindling ), 1044457, 1023553, 0.0, 00.0, typeof( Log ), 1044041, 1, 1044351 ); + // Materials + AddCraft(typeof(Kindling), 1044457, 1023553, 0.0, 00.0, typeof(Log), 1044041, 1, 1044351); - index = AddCraft( typeof( Shaft ), 1044457, 1027124, 0.0, 40.0, typeof( Log ), 1044041, 1, 1044351 ); - SetUseAllRes( index, true ); + index = AddCraft(typeof(Shaft), 1044457, 1027124, 0.0, 40.0, typeof(Log), 1044041, 1, 1044351); + SetUseAllRes(index, true); - // Ammunition - index = AddCraft( typeof( Arrow ), 1044565, 1023903, 0.0, 40.0, typeof( Shaft ), 1044560, 1, 1044561 ); - AddRes( index, typeof( Feather ), 1044562, 1, 1044563 ); - SetUseAllRes( index, true ); + // Ammunition + index = AddCraft(typeof(Arrow), 1044565, 1023903, 0.0, 40.0, typeof(Shaft), 1044560, 1, 1044561); + AddRes(index, typeof(Feather), 1044562, 1, 1044563); + SetUseAllRes(index, true); - index = AddCraft( typeof( Bolt ), 1044565, 1027163, 0.0, 40.0, typeof( Shaft ), 1044560, 1, 1044561 ); - AddRes( index, typeof( Feather ), 1044562, 1, 1044563 ); - SetUseAllRes( index, true ); + index = AddCraft(typeof(Bolt), 1044565, 1027163, 0.0, 40.0, typeof(Shaft), 1044560, 1, 1044561); + AddRes(index, typeof(Feather), 1044562, 1, 1044563); + SetUseAllRes(index, true); - if ( Core.SE ) - { - index = AddCraft( typeof( FukiyaDarts ), 1044565, 1030246, 50.0, 90.0, typeof( Log ), 1044041, 1, 1044351 ); - SetUseAllRes( index, true ); - SetNeededExpansion( index, Expansion.SE ); - } + if (Core.SE) + { + index = AddCraft(typeof(FukiyaDarts), 1044565, 1030246, 50.0, 90.0, typeof(Log), 1044041, 1, 1044351); + SetUseAllRes(index, true); + SetNeededExpansion(index, Expansion.SE); + } - // Weapons - AddCraft( typeof( Bow ), 1044566, 1025042, 30.0, 70.0, typeof( Log ), 1044041, 7, 1044351 ); - AddCraft( typeof( Crossbow ), 1044566, 1023919, 60.0, 100.0, typeof( Log ), 1044041, 7, 1044351 ); - AddCraft( typeof( HeavyCrossbow ), 1044566, 1025117, 80.0, 120.0, typeof( Log ), 1044041, 10, 1044351 ); + // Weapons + AddCraft(typeof(Bow), 1044566, 1025042, 30.0, 70.0, typeof(Log), 1044041, 7, 1044351); + AddCraft(typeof(Crossbow), 1044566, 1023919, 60.0, 100.0, typeof(Log), 1044041, 7, 1044351); + AddCraft(typeof(HeavyCrossbow), 1044566, 1025117, 80.0, 120.0, typeof(Log), 1044041, 10, 1044351); - if ( Core.AOS ) - { - AddCraft( typeof( CompositeBow ), 1044566, 1029922, 70.0, 110.0, typeof( Log ), 1044041, 7, 1044351 ); - AddCraft( typeof( RepeatingCrossbow ), 1044566, 1029923, 90.0, 130.0, typeof( Log ), 1044041, 10, 1044351 ); - } + if (Core.AOS) + { + AddCraft(typeof(CompositeBow), 1044566, 1029922, 70.0, 110.0, typeof(Log), 1044041, 7, 1044351); + AddCraft(typeof(RepeatingCrossbow), 1044566, 1029923, 90.0, 130.0, typeof(Log), 1044041, 10, 1044351); + } - if ( Core.SE ) - { - index = AddCraft( typeof( Yumi ), 1044566, 1030224, 90.0, 130.0, typeof( Log ), 1044041, 10, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - } + if (Core.SE) + { + index = AddCraft(typeof(Yumi), 1044566, 1030224, 90.0, 130.0, typeof(Log), 1044041, 10, 1044351); + SetNeededExpansion(index, Expansion.SE); + } - if ( Core.ML ) - { - index = AddCraft( typeof( BlightGrippedLongbow ), 1044566, 1072907, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); - AddRes( index, typeof( LardOfParoxysmus ), 1032681, 1, 1053098 ); - AddRes( index, typeof( Blight ), 1032675, 10, 1053098 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1053098 ); - AddRareRecipe( index, 200 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); + if (Core.ML) + { + index = AddCraft(typeof(BlightGrippedLongbow), 1044566, 1072907, 75.0, 125.0, typeof(Log), 1044041, 20, + 1044351); + AddRes(index, typeof(LardOfParoxysmus), 1032681, 1, 1053098); + AddRes(index, typeof(Blight), 1032675, 10, 1053098); + AddRes(index, typeof(Corruption), 1032676, 10, 1053098); + AddRareRecipe(index, 200); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); - /* TODO - index = AddCraft( typeof( FaerieFire ), 1044566, 1072908, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); - AddRes( index, typeof( LardOfParoxysmus ), 1032681, 1, 1053098 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); - AddRes( index, typeof( Taint ), 1032679, 10, 1053098 ); - AddRareRecipe( index, 201 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - */ + /* TODO + index = AddCraft( typeof( FaerieFire ), 1044566, 1072908, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); + AddRes( index, typeof( LardOfParoxysmus ), 1032681, 1, 1053098 ); + AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); + AddRes( index, typeof( Taint ), 1032679, 10, 1053098 ); + AddRareRecipe( index, 201 ); + ForceNonExceptional( index ); + SetNeededExpansion( index, Expansion.ML ); + */ - index = AddCraft( typeof( SilvanisFeywoodBow ), 1044566, 1072955, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); - AddRes( index, typeof( LardOfParoxysmus ), 1032681, 1, 1053098 ); - AddRes( index, typeof( Scourge ), 1032677, 10, 1053098 ); - AddRes( index, typeof( Muculent ), 1032680, 10, 1053098 ); - AddRareRecipe( index, 202 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(SilvanisFeywoodBow), 1044566, 1072955, 75.0, 125.0, typeof(Log), 1044041, 20, + 1044351); + AddRes(index, typeof(LardOfParoxysmus), 1032681, 1, 1053098); + AddRes(index, typeof(Scourge), 1032677, 10, 1053098); + AddRes(index, typeof(Muculent), 1032680, 10, 1053098); + AddRareRecipe(index, 202); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); - /* TODO - index = AddCraft( typeof( MischiefMaker ), 1044566, 1072910, 75.0, 125.0, typeof( Log ), 1044041, 15, 1044351 ); - AddRes( index, typeof( DreadHornMane ), 1032682, 1, 1053098 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1053098 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); - AddRareRecipe( index, 203 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - */ + /* TODO + index = AddCraft( typeof( MischiefMaker ), 1044566, 1072910, 75.0, 125.0, typeof( Log ), 1044041, 15, 1044351 ); + AddRes( index, typeof( DreadHornMane ), 1032682, 1, 1053098 ); + AddRes( index, typeof( Corruption ), 1032676, 10, 1053098 ); + AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); + AddRareRecipe( index, 203 ); + ForceNonExceptional( index ); + SetNeededExpansion( index, Expansion.ML ); + */ - index = AddCraft( typeof( TheNightReaper ), 1044566, 1072912, 75.0, 125.0, typeof( Log ), 1044041, 10, 1044351 ); - AddRes( index, typeof( DreadHornMane ), 1032682, 1, 1053098 ); - AddRes( index, typeof( Blight ), 1032675, 10, 1053098 ); - AddRes( index, typeof( Scourge ), 1032677, 10, 1053098 ); - AddRareRecipe( index, 204 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(TheNightReaper), 1044566, 1072912, 75.0, 125.0, typeof(Log), 1044041, 10, 1044351); + AddRes(index, typeof(DreadHornMane), 1032682, 1, 1053098); + AddRes(index, typeof(Blight), 1032675, 10, 1053098); + AddRes(index, typeof(Scourge), 1032677, 10, 1053098); + AddRareRecipe(index, 204); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( BarbedLongbow ), 1044566, 1073505, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); - AddRes( index, typeof( FireRuby ), 1026254, 1, 1053098 ); - AddRecipe( index, 205 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(BarbedLongbow), 1044566, 1073505, 75.0, 125.0, typeof(Log), 1044041, 20, 1044351); + AddRes(index, typeof(FireRuby), 1026254, 1, 1053098); + AddRecipe(index, 205); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( SlayerLongbow ), 1044566, 1073506, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); - AddRes( index, typeof( BrilliantAmber ), 1026256, 1, 1053098 ); - AddRecipe( index, 206 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(SlayerLongbow), 1044566, 1073506, 75.0, 125.0, typeof(Log), 1044041, 20, 1044351); + AddRes(index, typeof(BrilliantAmber), 1026256, 1, 1053098); + AddRecipe(index, 206); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( FrozenLongbow ), 1044566, 1073507, 75.0, 125.0, typeof( Log ), 1044041, 20, 1044351 ); - AddRes( index, typeof( Turquoise ), 1026250, 1, 1053098 ); - AddRecipe( index, 207 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(FrozenLongbow), 1044566, 1073507, 75.0, 125.0, typeof(Log), 1044041, 20, 1044351); + AddRes(index, typeof(Turquoise), 1026250, 1, 1053098); + AddRecipe(index, 207); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( LongbowOfMight ), 1044566, 1073508, 75.0, 125.0, typeof( Log ), 1044041, 10, 1044351 ); - AddRes( index, typeof( BlueDiamond ), 1026255, 1, 1053098 ); - AddRecipe( index, 208 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(LongbowOfMight), 1044566, 1073508, 75.0, 125.0, typeof(Log), 1044041, 10, 1044351); + AddRes(index, typeof(BlueDiamond), 1026255, 1, 1053098); + AddRecipe(index, 208); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( RangersShortbow ), 1044566, 1073509, 75.0, 125.0, typeof( Log ), 1044041, 15, 1044351 ); - AddRes( index, typeof( PerfectEmerald ), 1026251, 1, 1053098 ); - AddRecipe( index, 209 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(RangersShortbow), 1044566, 1073509, 75.0, 125.0, typeof(Log), 1044041, 15, 1044351); + AddRes(index, typeof(PerfectEmerald), 1026251, 1, 1053098); + AddRecipe(index, 209); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( LightweightShortbow ), 1044566, 1073510, 75.0, 125.0, typeof( Log ), 1044041, 15, 1044351 ); - AddRes( index, typeof( WhitePearl ), 1026253, 1, 1053098 ); - AddRecipe( index, 210 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(LightweightShortbow), 1044566, 1073510, 75.0, 125.0, typeof(Log), 1044041, 15, + 1044351); + AddRes(index, typeof(WhitePearl), 1026253, 1, 1053098); + AddRecipe(index, 210); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( MysticalShortbow ), 1044566, 1073511, 75.0, 125.0, typeof( Log ), 1044041, 15, 1044351 ); - AddRes( index, typeof( EcruCitrine ), 1026252, 1, 1053098 ); - AddRecipe( index, 211 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(MysticalShortbow), 1044566, 1073511, 75.0, 125.0, typeof(Log), 1044041, 15, 1044351); + AddRes(index, typeof(EcruCitrine), 1026252, 1, 1053098); + AddRecipe(index, 211); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( AssassinsShortbow ), 1044566, 1073512, 75.0, 125.0, typeof( Log ), 1044041, 15, 1044351 ); - AddRes( index, typeof( DarkSapphire ), 1026249, 1, 1053098 ); - AddRecipe( index, 212 ); - SetNeededExpansion( index, Expansion.ML ); - } + index = AddCraft(typeof(AssassinsShortbow), 1044566, 1073512, 75.0, 125.0, typeof(Log), 1044041, 15, + 1044351); + AddRes(index, typeof(DarkSapphire), 1026249, 1, 1053098); + AddRecipe(index, 212); + SetNeededExpansion(index, Expansion.ML); + } - MarkOption = true; - Repair = Core.AOS; - } - } -} + MarkOption = true; + Repair = Core.AOS; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefCarpentry.cs b/Scripts/Engines/Craft/DefCarpentry.cs index a760c1d13..d4868f49d 100644 --- a/Scripts/Engines/Craft/DefCarpentry.cs +++ b/Scripts/Engines/Craft/DefCarpentry.cs @@ -3,510 +3,546 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefCarpentry : CraftSystem - { - public override SkillName MainSkill => SkillName.Carpentry; - - public override int GumpTitleNumber => 1044004; - - private static CraftSystem m_CraftSystem; - - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefCarpentry(); - - return m_CraftSystem; - } - } - - public override double GetChanceAtMin( CraftItem item ) - { - return 0.5; // 50% - } - - private DefCarpentry() : base( 1, 1, 1.25 )// base( 1, 1, 3.0 ) - { - } - - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. - - return 0; - } - - public override void PlayCraftEffect( Mobile from ) - { - // no animation - //if ( from.Body.Type == BodyType.Human && !from.Mounted ) - // from.Animate( 9, 5, 1, true, false, 0 ); - - from.PlaySound( 0x23D ); - } - - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool - - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } - - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } - - public override void InitCraftList() - { - int index = -1; - - // Other Items - if ( Core.Expansion == Expansion.AOS || Core.Expansion == Expansion.SE ) - { - index = AddCraft( typeof( Board ), 1044294, 1027127, 0.0, 0.0, typeof( Log ), 1044466, 1, 1044465 ); - SetUseAllRes( index, true ); - } - - AddCraft( typeof( BarrelStaves ), 1044294, 1027857, 00.0, 25.0, typeof( Log ), 1044041, 5, 1044351 ); - AddCraft( typeof( BarrelLid ), 1044294, 1027608, 11.0, 36.0, typeof( Log ), 1044041, 4, 1044351 ); - AddCraft( typeof( ShortMusicStand ), 1044294, 1044313, 78.9, 103.9, typeof( Log ), 1044041, 15, 1044351 ); - AddCraft( typeof( TallMusicStand ), 1044294, 1044315, 81.5, 106.5, typeof( Log ), 1044041, 20, 1044351 ); - AddCraft( typeof( Easle ), 1044294, 1044317, 86.8, 111.8, typeof( Log ), 1044041, 20, 1044351 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( RedHangingLantern ), 1044294, 1029412, 65.0, 90.0, typeof( Log ), 1044041, 5, 1044351 ); - AddRes( index, typeof( BlankScroll ), 1044377, 10, 1044378 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( WhiteHangingLantern ), 1044294, 1029416, 65.0, 90.0, typeof( Log ), 1044041, 5, 1044351 ); - AddRes( index, typeof( BlankScroll ), 1044377, 10, 1044378 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( ShojiScreen ), 1044294, 1029423, 80.0, 105.0, typeof( Log ), 1044041, 75, 1044351 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 60, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( BambooScreen ), 1044294, 1029428, 80.0, 105.0, typeof( Log ), 1044041, 75, 1044351 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 60, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - if ( Core.AOS ) //Duplicate Entries to preserve ordering depending on era - { - index = AddCraft( typeof( FishingPole ), 1044294, 1023519, 68.4, 93.4, typeof( Log ), 1044041, 5, 1044351 ); //This is in the categor of Other during AoS - AddSkill( index, SkillName.Tailoring, 40.0, 45.0 ); - AddRes( index, typeof( Cloth ), 1044286, 5, 1044287 ); - } - - if ( Core.ML ) - { - index = AddCraft( typeof( RunedSwitch ), 1044294, 1072896, 70.0, 120.0, typeof( Log ), 1044041, 2, 1044351 ); - AddRes( index, typeof( EnchantedSwitch ), 1072893, 1, 1053098 ); - AddRes( index, typeof( RunedPrism ), 1073465, 1, 1053098 ); - AddRes( index, typeof( JeweledFiligree ), 1072894, 1, 1053098 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( WarriorStatueSouthDeed ), 1044294, 1072887, 0.0, 35.0, typeof( Log ), 1044041, 250, 1044351 ); - AddRecipe( index, 300 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( WarriorStatueEastDeed ), 1044294, 1072888, 0.0, 35.0, typeof( Log ), 1044041, 250, 1044351 ); - AddRecipe( index, 301 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SquirrelStatueSouthDeed ), 1044294, 1072884, 0.0, 35.0, typeof( Log ), 1044041, 250, 1044351 ); - AddRecipe( index, 302 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SquirrelStatueEastDeed ), 1044294, 1073398, 0.0, 35.0, typeof( Log ), 1044041, 250, 1044351 ); - AddRecipe( index, 303 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( AcidProofRope ), 1044294, 1074886, 80, 130.0, typeof( GreaterStrengthPotion ), 1073466, 2, 1044253 ); - AddRes( index, typeof( ProtectionScroll ), 1044395, 1, 1053098 ); - AddRes( index, typeof( SwitchItem ), 1032127, 1, 1053098 ); - AddRareRecipe( index, 304 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } - - // Furniture - AddCraft( typeof( FootStool ), 1044291, 1022910, 11.0, 36.0, typeof( Log ), 1044041, 9, 1044351 ); - AddCraft( typeof( Stool ), 1044291, 1022602, 11.0, 36.0, typeof( Log ), 1044041, 9, 1044351 ); - AddCraft( typeof( BambooChair ), 1044291, 1044300, 21.0, 46.0, typeof( Log ), 1044041, 13, 1044351 ); - AddCraft( typeof( WoodenChair ), 1044291, 1044301, 21.0, 46.0, typeof( Log ), 1044041, 13, 1044351 ); - AddCraft( typeof( FancyWoodenChairCushion ), 1044291, 1044302, 42.1, 67.1, typeof( Log ), 1044041, 15, 1044351 ); - AddCraft( typeof( WoodenChairCushion ), 1044291, 1044303, 42.1, 67.1, typeof( Log ), 1044041, 13, 1044351 ); - AddCraft( typeof( WoodenBench ), 1044291, 1022860, 52.6, 77.6, typeof( Log ), 1044041, 17, 1044351 ); - AddCraft( typeof( WoodenThrone ), 1044291, 1044304, 52.6, 77.6, typeof( Log ), 1044041, 17, 1044351 ); - AddCraft( typeof( Throne ), 1044291, 1044305, 73.6, 98.6, typeof( Log ), 1044041, 19, 1044351 ); - AddCraft( typeof( Nightstand ), 1044291, 1044306, 42.1, 67.1, typeof( Log ), 1044041, 17, 1044351 ); - AddCraft( typeof( WritingTable ), 1044291, 1022890, 63.1, 88.1, typeof( Log ), 1044041, 17, 1044351 ); - AddCraft( typeof( YewWoodTable ), 1044291, 1044307, 63.1, 88.1, typeof( Log ), 1044041, 23, 1044351 ); - AddCraft( typeof( LargeTable ), 1044291, 1044308, 84.2, 109.2, typeof( Log ), 1044041, 27, 1044351 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( ElegantLowTable ), 1044291, 1030265, 80.0, 105.0, typeof( Log ), 1044041, 35, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PlainLowTable ), 1044291, 1030266, 80.0, 105.0, typeof( Log ), 1044041, 35, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - } - - if ( Core.ML ) - { - index = AddCraft( typeof( OrnateElvenChair ), 1044291, 1072870, 80.0, 105.0, typeof( Log ), 1044041, 30, 1044351 ); - AddRecipe( index, 305 ); - SetNeededExpansion( index, Expansion.ML ); - } - - // Containers - AddCraft( typeof( WoodenBox ), 1044292, 1023709, 21.0, 46.0, typeof( Log ), 1044041, 10, 1044351 ); - AddCraft( typeof( SmallCrate ), 1044292, 1044309, 10.0, 35.0, typeof( Log ), 1044041, 8 , 1044351 ); - AddCraft( typeof( MediumCrate ), 1044292, 1044310, 31.0, 56.0, typeof( Log ), 1044041, 15, 1044351 ); - AddCraft( typeof( LargeCrate ), 1044292, 1044311, 47.3, 72.3, typeof( Log ), 1044041, 18, 1044351 ); - AddCraft( typeof( WoodenChest ), 1044292, 1023650, 73.6, 98.6, typeof( Log ), 1044041, 20, 1044351 ); - AddCraft( typeof( EmptyBookcase ), 1044292, 1022718, 31.5, 56.5, typeof( Log ), 1044041, 25, 1044351 ); - AddCraft( typeof( FancyArmoire ), 1044292, 1044312, 84.2, 109.2, typeof( Log ), 1044041, 35, 1044351 ); - AddCraft( typeof( Armoire ), 1044292, 1022643, 84.2, 109.2, typeof( Log ), 1044041, 35, 1044351 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( PlainWoodenChest ), 1044292, 1030251, 90.0, 115.0, typeof( Log ), 1044041, 30, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( OrnateWoodenChest ), 1044292, 1030253, 90.0, 115.0, typeof( Log ), 1044041, 30, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( GildedWoodenChest ), 1044292, 1030255, 90.0, 115.0, typeof( Log ), 1044041, 30, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( WoodenFootLocker ), 1044292, 1030257, 90.0, 115.0, typeof( Log ), 1044041, 30, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( FinishedWoodenChest ),1044292, 1030259, 90.0, 115.0, typeof( Log ), 1044041, 30, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( TallCabinet ), 1044292, 1030261, 90.0, 115.0, typeof( Log ), 1044041, 35, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( ShortCabinet ), 1044292, 1030263, 90.0, 115.0, typeof( Log ), 1044041, 35, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( RedArmoire ), 1044292, 1030328, 90.0, 115.0, typeof( Log ), 1044041, 40, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( ElegantArmoire ), 1044292, 1030330, 90.0, 115.0, typeof( Log ), 1044041, 40, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( MapleArmoire ), 1044292, 1030332, 90.0, 115.0, typeof( Log ), 1044041, 40, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( CherryArmoire ), 1044292, 1030334, 90.0, 115.0, typeof( Log ), 1044041, 40, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - } - - index = AddCraft( typeof( Keg ), 1044292, 1023711, 57.8, 82.8, typeof( BarrelStaves ), 1044288, 3, 1044253 ); - AddRes( index, typeof( BarrelHoops ), 1044289, 1, 1044253 ); - AddRes( index, typeof( BarrelLid ), 1044251, 1, 1044253 ); - - if ( Core.ML ) - { - index = AddCraft( typeof( ArcaneBookshelfSouthDeed ), 1044292, 1072871, 94.7, 119.7, typeof( Log ), 1044041, 80, 1044351 ); - AddRecipe( index, 306 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ArcaneBookshelfEastDeed ), 1044292, 1073371, 94.7, 119.7, typeof( Log ), 1044041, 80, 1044351 ); - AddRecipe( index, 307 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - /* TODO - index = AddCraft( typeof( OrnateElvenChestSouthDeed ), 1044292, 1072862, 94.7, 119.7, typeof( Log ), 1044041, 40, 1044351 ); - AddRecipe( index, 308 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( OrnateElvenChestEastDeed ), 1044292, 1073383, 94.7, 119.7, typeof( Log ), 1044041, 40, 1044351 ); - AddRecipe( index, 309 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - */ - - index = AddCraft( typeof( ElvenDresserSouthDeed ), 1044292, 1072864, 75.0, 100.0, typeof( Log ), 1044041, 45, 1044351 ); - AddRecipe( index, 310 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ElvenDresserEastDeed ), 1044292, 1073388, 75.0, 100.0, typeof( Log ), 1044041, 45, 1044351 ); - AddRecipe( index, 311 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - /* TODO - index = AddCraft( typeof( FancyElvenArmoire ), 1044292, 1072866, 80.0, 105.0, typeof( Log ), 1044041, 60, 1044351 ); - AddRecipe( index, 312 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - */ - } - - // Staves and Shields - AddCraft( typeof( ShepherdsCrook ), Core.ML ? 1044566 : 1044295, 1023713, 78.9, 103.9, typeof( Log ), 1044041, 7, 1044351 ); - AddCraft( typeof( QuarterStaff ), Core.ML ? 1044566 : 1044295, 1023721, 73.6, 98.6, typeof( Log ), 1044041, 6, 1044351 ); - AddCraft( typeof( GnarledStaff ), Core.ML ? 1044566 : 1044295, 1025112, 78.9, 103.9, typeof( Log ), 1044041, 7, 1044351 ); - AddCraft( typeof( WoodenShield ), Core.ML ? 1062760 : 1044295, 1027034, 52.6, 77.6, typeof( Log ), 1044041, 9, 1044351 ); - - if ( !Core.AOS ) //Duplicate Entries to preserve ordering depending on era - { - index = AddCraft( typeof( FishingPole ), Core.ML ? 1044294 : 1044295, 1023519, 68.4, 93.4, typeof( Log ), 1044041, 5, 1044351 ); //This is in the categor of Other during AoS - AddSkill( index, SkillName.Tailoring, 40.0, 45.0 ); - AddRes( index, typeof( Cloth ), 1044286, 5, 1044287 ); - } - - if ( Core.SE ) - { - index = AddCraft( typeof( Bokuto ), Core.ML ? 1044566 : 1044295, 1030227, 70.0, 95.0, typeof( Log ), 1044041, 6, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( Fukiya ), Core.ML ? 1044566 : 1044295, 1030229, 60.0, 85.0, typeof( Log ), 1044041, 6, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( Tetsubo ), Core.ML ? 1044566 : 1044295, 1030225, 80.0, 140.3, typeof( Log ), 1044041, 10, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - } - - if ( Core.ML ) - { - index = AddCraft( typeof( PhantomStaff ), 1044566, 1072919, 90.0, 130.0, typeof( Log ), 1044041, 16, 1044351 ); - AddRes( index, typeof( DiseasedBark ), 1032683, 1, 1053098 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); - AddRes( index, typeof( Taint ), 1032679, 10, 1053098 ); - AddRareRecipe( index, 313 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ArcanistsWildStaff ), 1044566, 1073549, 63.8, 113.8, typeof( Log ), 1044041, 16, 1044351 ); - AddRes( index, typeof( WhitePearl ), 1026253, 1, 1053098 ); - AddRecipe( index, 314 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( AncientWildStaff ), 1044566, 1073550, 63.8, 113.8, typeof( Log ), 1044041, 16, 1044351 ); - AddRes( index, typeof( PerfectEmerald ), 1026251, 1, 1053098 ); - AddRecipe( index, 315 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( ThornedWildStaff ), 1044566, 1073551, 63.8, 113.8, typeof( Log ), 1044041, 16, 1044351 ); - AddRes( index, typeof( FireRuby ), 1026254, 1, 1053098 ); - AddRecipe( index, 316 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( HardenedWildStaff ), 1044566, 1073552, 63.8, 113.8, typeof( Log ), 1044041, 16, 1044351 ); - AddRes( index, typeof( Turquoise ), 1026250, 1, 1053098 ); - AddRecipe( index, 317 ); - SetNeededExpansion( index, Expansion.ML ); - } - - // Armor - if ( Core.ML ) - { - index = AddCraft( typeof( IronwoodCrown ), 1062760, 1072924, 85.0, 120.0, typeof( Log ), 1044041, 10, 1044351 ); - AddRes( index, typeof( DiseasedBark ), 1032683, 1, 1053098 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1053098 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1053098 ); - AddRareRecipe( index, 318 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( BrambleCoat ), 1062760, 1072925, 85.0, 120.0, typeof( Log ), 1044041, 10, 1044351 ); - AddRes( index, typeof( DiseasedBark ), 1032683, 1, 1053098 ); - AddRes( index, typeof( Taint ), 1032679, 10, 1053098 ); - AddRes( index, typeof( Scourge ), 1032677, 10, 1053098 ); - AddRareRecipe( index, 319 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } - - // Instruments - index = AddCraft( typeof( LapHarp ), 1044293, 1023762, 63.1, 88.1, typeof( Log ), 1044041, 20, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - AddRes( index, typeof( Cloth ), 1044286, 10, 1044287 ); - - index = AddCraft( typeof( Harp ), 1044293, 1023761, 78.9, 103.9, typeof( Log ), 1044041, 35, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - AddRes( index, typeof( Cloth ), 1044286, 15, 1044287 ); - - index = AddCraft( typeof( Drums ), 1044293, 1023740, 57.8, 82.8, typeof( Log ), 1044041, 20, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - AddRes( index, typeof( Cloth ), 1044286, 10, 1044287 ); - - index = AddCraft( typeof( Lute ), 1044293, 1023763, 68.4, 93.4, typeof( Log ), 1044041, 25, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - AddRes( index, typeof( Cloth ), 1044286, 10, 1044287 ); - - index = AddCraft( typeof( Tambourine ), 1044293, 1023741, 57.8, 82.8, typeof( Log ), 1044041, 15, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - AddRes( index, typeof( Cloth ), 1044286, 10, 1044287 ); - - index = AddCraft( typeof( TambourineTassel ), 1044293, 1044320, 57.8, 82.8, typeof( Log ), 1044041, 15, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - AddRes( index, typeof( Cloth ), 1044286, 15, 1044287 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( BambooFlute ), 1044293, 1030247, 80.0, 105.0, typeof( Log ), 1044041, 15, 1044351 ); - AddSkill( index, SkillName.Musicianship, 45.0, 50.0 ); - SetNeededExpansion( index, Expansion.SE ); - } - - if ( Core.ML ) - { - index = AddCraft( typeof( TallElvenBedSouthDeed ), 1044290, 1072858, 94.7, 119.7, typeof( Log ), 1044041, 200, 1044351 ); - AddSkill( index, SkillName.Tailoring, 75.0, 80.0 ); - AddRes( index, typeof( Cloth ), 1044286, 100, 1044287 ); - AddRecipe( index, 320 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( TallElvenBedEastDeed ), 1044290, 1072859, 94.7, 119.7, typeof( Log ), 1044041, 200, 1044351 ); - AddSkill( index, SkillName.Tailoring, 75.0, 80.0 ); - AddRes( index, typeof( Cloth ), 1044286, 100, 1044287 ); - AddRecipe( index, 321 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } - - // Misc - index = AddCraft( typeof( SmallBedSouthDeed ), 1044290, 1044321, 94.7, 119.8, typeof( Log ), 1044041, 100, 1044351 ); - AddSkill( index, SkillName.Tailoring, 75.0, 80.0 ); - AddRes( index, typeof( Cloth ), 1044286, 100, 1044287 ); - index = AddCraft(typeof(SmallBedEastDeed), 1044290, 1044322, 94.7, 119.8, typeof(Log), 1044041, 100, 1044351); - AddSkill( index, SkillName.Tailoring, 75.0, 80.0 ); - AddRes( index, typeof( Cloth ), 1044286, 100, 1044287 ); - index = AddCraft(typeof(LargeBedSouthDeed), 1044290, 1044323, 94.7, 119.8, typeof(Log), 1044041, 150, 1044351); - AddSkill( index, SkillName.Tailoring, 75.0, 80.0 ); - AddRes( index, typeof( Cloth ), 1044286, 150, 1044287 ); - index = AddCraft(typeof(LargeBedEastDeed), 1044290, 1044324, 94.7, 119.8, typeof(Log), 1044041, 150, 1044351); - AddSkill( index, SkillName.Tailoring, 75.0, 80.0 ); - AddRes( index, typeof( Cloth ), 1044286, 150, 1044287 ); - AddCraft( typeof( DartBoardSouthDeed ), 1044290, 1044325, 15.7, 40.7, typeof( Log ), 1044041, 5, 1044351 ); - AddCraft( typeof( DartBoardEastDeed ), 1044290, 1044326, 15.7, 40.7, typeof( Log ), 1044041, 5, 1044351 ); - AddCraft( typeof( BallotBoxDeed ), 1044290, 1044327, 47.3, 72.3, typeof( Log ), 1044041, 5, 1044351 ); - index = AddCraft( typeof( PentagramDeed ), 1044290, 1044328, 100.0, 125.0, typeof( Log ), 1044041, 100, 1044351 ); - AddSkill( index, SkillName.Magery, 75.0, 80.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 40, 1044037 ); - index = AddCraft( typeof( AbbatoirDeed ), 1044290, 1044329, 100.0, 125.0, typeof( Log ), 1044041, 100, 1044351 ); - AddSkill( index, SkillName.Magery, 50.0, 55.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 40, 1044037 ); - - if ( Core.AOS ) - { - AddCraft( typeof( PlayerBBEast ), 1044290, 1062420, 85.0, 110.0, typeof( Log ), 1044041, 50, 1044351 ); - AddCraft( typeof( PlayerBBSouth ), 1044290, 1062421, 85.0, 110.0, typeof( Log ), 1044041, 50, 1044351 ); - } - - // Blacksmithy - This changed to Anvils and Forges (1111809) for SA - index = AddCraft( typeof( SmallForgeDeed ), 1044296, 1044330, 73.6, 98.6, typeof( Log ), 1044041, 5, 1044351 ); - AddSkill( index, SkillName.Blacksmith, 75.0, 80.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 75, 1044037 ); - index = AddCraft( typeof( LargeForgeEastDeed ), 1044296, 1044331, 78.9, 103.9, typeof( Log ), 1044041, 5, 1044351 ); - AddSkill( index, SkillName.Blacksmith, 80.0, 85.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 100, 1044037 ); - index = AddCraft( typeof( LargeForgeSouthDeed ), 1044296, 1044332, 78.9, 103.9, typeof( Log ), 1044041, 5, 1044351 ); - AddSkill( index, SkillName.Blacksmith, 80.0, 85.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 100, 1044037 ); - index = AddCraft( typeof( AnvilEastDeed ), 1044296, 1044333, 73.6, 98.6, typeof( Log ), 1044041, 5, 1044351 ); - AddSkill( index, SkillName.Blacksmith, 75.0, 80.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 150, 1044037 ); - index = AddCraft( typeof( AnvilSouthDeed ), 1044296, 1044334, 73.6, 98.6, typeof( Log ), 1044041, 5, 1044351 ); - AddSkill( index, SkillName.Blacksmith, 75.0, 80.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 150, 1044037 ); - - // Training - index = AddCraft( typeof( TrainingDummyEastDeed ), 1044297, 1044335, 68.4, 93.4, typeof( Log ), 1044041, 55, 1044351 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 60, 1044287 ); - index = AddCraft( typeof( TrainingDummySouthDeed ), 1044297, 1044336, 68.4, 93.4, typeof( Log ), 1044041, 55, 1044351 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 60, 1044287 ); - index = AddCraft( typeof( PickpocketDipEastDeed ), 1044297, 1044337, 73.6, 98.6, typeof( Log ), 1044041, 65, 1044351 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 60, 1044287 ); - index = AddCraft( typeof( PickpocketDipSouthDeed ), 1044297, 1044338, 73.6, 98.6, typeof( Log ), 1044041, 65, 1044351 ); - AddSkill( index, SkillName.Tailoring, 50.0, 55.0 ); - AddRes( index, typeof( Cloth ), 1044286, 60, 1044287 ); - - // Tailoring - index = AddCraft( typeof( Dressform ), 1044298, 1044339, 63.1, 88.1, typeof( Log ), 1044041, 25, 1044351 ); - AddSkill( index, SkillName.Tailoring, 65.0, 70.0 ); - AddRes( index, typeof( Cloth ), 1044286, 10, 1044287 ); - index = AddCraft( typeof( SpinningwheelEastDeed ), 1044298, 1044341, 73.6, 98.6, typeof( Log ), 1044041, 75, 1044351 ); - AddSkill( index, SkillName.Tailoring, 65.0, 70.0 ); - AddRes( index, typeof( Cloth ), 1044286, 25, 1044287 ); - index = AddCraft( typeof( SpinningwheelSouthDeed ), 1044298, 1044342, 73.6, 98.6, typeof( Log ), 1044041, 75, 1044351 ); - AddSkill( index, SkillName.Tailoring, 65.0, 70.0 ); - AddRes( index, typeof( Cloth ), 1044286, 25, 1044287 ); - index = AddCraft( typeof( LoomEastDeed ), 1044298, 1044343, 84.2, 109.2, typeof( Log ), 1044041, 85, 1044351 ); - AddSkill( index, SkillName.Tailoring, 65.0, 70.0 ); - AddRes( index, typeof( Cloth ), 1044286, 25, 1044287 ); - index = AddCraft( typeof( LoomSouthDeed ), 1044298, 1044344, 84.2, 109.2, typeof( Log ), 1044041, 85, 1044351 ); - AddSkill( index, SkillName.Tailoring, 65.0, 70.0 ); - AddRes( index, typeof( Cloth ), 1044286, 25, 1044287 ); - - // Cooking - index = AddCraft( typeof( StoneOvenEastDeed ), Core.ML ? 1044298 : 1044299, 1044345, 68.4, 93.4, typeof( Log ), 1044041, 85, 1044351 ); - AddSkill( index, SkillName.Tinkering, 50.0, 55.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 125, 1044037 ); - index = AddCraft( typeof( StoneOvenSouthDeed ), Core.ML ? 1044298 : 1044299, 1044346, 68.4, 93.4, typeof( Log ), 1044041, 85, 1044351 ); - AddSkill( index, SkillName.Tinkering, 50.0, 55.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 125, 1044037 ); - index = AddCraft( typeof( FlourMillEastDeed ), Core.ML ? 1044298 : 1044299, 1044347, 94.7, 119.7, typeof( Log ), 1044041, 100, 1044351 ); - AddSkill( index, SkillName.Tinkering, 50.0, 55.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 50, 1044037 ); - index = AddCraft( typeof( FlourMillSouthDeed ), Core.ML ? 1044298 : 1044299, 1044348, 94.7, 119.7, typeof( Log ), 1044041, 100, 1044351 ); - AddSkill( index, SkillName.Tinkering, 50.0, 55.0 ); - AddRes( index, typeof( IronIngot ), 1044036, 50, 1044037 ); - AddCraft( typeof( WaterTroughEastDeed ), Core.ML ? 1044298 : 1044299, 1044349, 94.7, 119.7, typeof( Log ), 1044041, 150, 1044351 ); - AddCraft( typeof( WaterTroughSouthDeed ), Core.ML ? 1044298 : 1044299, 1044350, 94.7, 119.7, typeof( Log ), 1044041, 150, 1044351 ); - - MarkOption = true; - Repair = Core.AOS; - - SetSubRes( typeof( Log ), 1072643 ); - - // Add every material you want the player to be able to choose from - // This will override the overridable material TODO: Verify the required skill amount - AddSubRes( typeof( Log ), 1072643, 00.0, 1044041, 1072652 ); - AddSubRes( typeof( OakLog ), 1072644, 65.0, 1044041, 1072652 ); - AddSubRes( typeof( AshLog ), 1072645, 80.0, 1044041, 1072652 ); - AddSubRes( typeof( YewLog ), 1072646, 95.0, 1044041, 1072652 ); - AddSubRes( typeof( HeartwoodLog ), 1072647, 100.0, 1044041, 1072652 ); - AddSubRes( typeof( BloodwoodLog ), 1072648, 100.0, 1044041, 1072652 ); - AddSubRes( typeof( FrostwoodLog ), 1072649, 100.0, 1044041, 1072652 ); - } - } -} + public class DefCarpentry : CraftSystem + { + private static CraftSystem m_CraftSystem; + + private DefCarpentry() : base(1, 1, 1.25) // base( 1, 1, 3.0 ) + { + } + + public override SkillName MainSkill => SkillName.Carpentry; + + public override int GumpTitleNumber => 1044004; + + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefCarpentry(); + + return m_CraftSystem; + } + } + + public override double GetChanceAtMin(CraftItem item) + { + return 0.5; // 50% + } + + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. + + return 0; + } + + public override void PlayCraftEffect(Mobile from) + { + // no animation + //if ( from.Body.Type == BodyType.Human && !from.Mounted ) + // from.Animate( 9, 5, 1, true, false, 0 ); + + from.PlaySound(0x23D); + } + + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool + + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } + + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } + + public override void InitCraftList() + { + int index = -1; + + // Other Items + if (Core.Expansion == Expansion.AOS || Core.Expansion == Expansion.SE) + { + index = AddCraft(typeof(Board), 1044294, 1027127, 0.0, 0.0, typeof(Log), 1044466, 1, 1044465); + SetUseAllRes(index, true); + } + + AddCraft(typeof(BarrelStaves), 1044294, 1027857, 00.0, 25.0, typeof(Log), 1044041, 5, 1044351); + AddCraft(typeof(BarrelLid), 1044294, 1027608, 11.0, 36.0, typeof(Log), 1044041, 4, 1044351); + AddCraft(typeof(ShortMusicStand), 1044294, 1044313, 78.9, 103.9, typeof(Log), 1044041, 15, 1044351); + AddCraft(typeof(TallMusicStand), 1044294, 1044315, 81.5, 106.5, typeof(Log), 1044041, 20, 1044351); + AddCraft(typeof(Easle), 1044294, 1044317, 86.8, 111.8, typeof(Log), 1044041, 20, 1044351); + + if (Core.SE) + { + index = AddCraft(typeof(RedHangingLantern), 1044294, 1029412, 65.0, 90.0, typeof(Log), 1044041, 5, 1044351); + AddRes(index, typeof(BlankScroll), 1044377, 10, 1044378); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(WhiteHangingLantern), 1044294, 1029416, 65.0, 90.0, typeof(Log), 1044041, 5, + 1044351); + AddRes(index, typeof(BlankScroll), 1044377, 10, 1044378); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(ShojiScreen), 1044294, 1029423, 80.0, 105.0, typeof(Log), 1044041, 75, 1044351); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 60, 1044287); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(BambooScreen), 1044294, 1029428, 80.0, 105.0, typeof(Log), 1044041, 75, 1044351); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 60, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + if (Core.AOS) //Duplicate Entries to preserve ordering depending on era + { + index = AddCraft(typeof(FishingPole), 1044294, 1023519, 68.4, 93.4, typeof(Log), 1044041, 5, + 1044351); //This is in the categor of Other during AoS + AddSkill(index, SkillName.Tailoring, 40.0, 45.0); + AddRes(index, typeof(Cloth), 1044286, 5, 1044287); + } + + if (Core.ML) + { + index = AddCraft(typeof(RunedSwitch), 1044294, 1072896, 70.0, 120.0, typeof(Log), 1044041, 2, 1044351); + AddRes(index, typeof(EnchantedSwitch), 1072893, 1, 1053098); + AddRes(index, typeof(RunedPrism), 1073465, 1, 1053098); + AddRes(index, typeof(JeweledFiligree), 1072894, 1, 1053098); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(WarriorStatueSouthDeed), 1044294, 1072887, 0.0, 35.0, typeof(Log), 1044041, 250, + 1044351); + AddRecipe(index, 300); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(WarriorStatueEastDeed), 1044294, 1072888, 0.0, 35.0, typeof(Log), 1044041, 250, + 1044351); + AddRecipe(index, 301); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SquirrelStatueSouthDeed), 1044294, 1072884, 0.0, 35.0, typeof(Log), 1044041, 250, + 1044351); + AddRecipe(index, 302); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SquirrelStatueEastDeed), 1044294, 1073398, 0.0, 35.0, typeof(Log), 1044041, 250, + 1044351); + AddRecipe(index, 303); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(AcidProofRope), 1044294, 1074886, 80, 130.0, typeof(GreaterStrengthPotion), 1073466, + 2, 1044253); + AddRes(index, typeof(ProtectionScroll), 1044395, 1, 1053098); + AddRes(index, typeof(SwitchItem), 1032127, 1, 1053098); + AddRareRecipe(index, 304); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + } + + // Furniture + AddCraft(typeof(FootStool), 1044291, 1022910, 11.0, 36.0, typeof(Log), 1044041, 9, 1044351); + AddCraft(typeof(Stool), 1044291, 1022602, 11.0, 36.0, typeof(Log), 1044041, 9, 1044351); + AddCraft(typeof(BambooChair), 1044291, 1044300, 21.0, 46.0, typeof(Log), 1044041, 13, 1044351); + AddCraft(typeof(WoodenChair), 1044291, 1044301, 21.0, 46.0, typeof(Log), 1044041, 13, 1044351); + AddCraft(typeof(FancyWoodenChairCushion), 1044291, 1044302, 42.1, 67.1, typeof(Log), 1044041, 15, 1044351); + AddCraft(typeof(WoodenChairCushion), 1044291, 1044303, 42.1, 67.1, typeof(Log), 1044041, 13, 1044351); + AddCraft(typeof(WoodenBench), 1044291, 1022860, 52.6, 77.6, typeof(Log), 1044041, 17, 1044351); + AddCraft(typeof(WoodenThrone), 1044291, 1044304, 52.6, 77.6, typeof(Log), 1044041, 17, 1044351); + AddCraft(typeof(Throne), 1044291, 1044305, 73.6, 98.6, typeof(Log), 1044041, 19, 1044351); + AddCraft(typeof(Nightstand), 1044291, 1044306, 42.1, 67.1, typeof(Log), 1044041, 17, 1044351); + AddCraft(typeof(WritingTable), 1044291, 1022890, 63.1, 88.1, typeof(Log), 1044041, 17, 1044351); + AddCraft(typeof(YewWoodTable), 1044291, 1044307, 63.1, 88.1, typeof(Log), 1044041, 23, 1044351); + AddCraft(typeof(LargeTable), 1044291, 1044308, 84.2, 109.2, typeof(Log), 1044041, 27, 1044351); + + if (Core.SE) + { + index = AddCraft(typeof(ElegantLowTable), 1044291, 1030265, 80.0, 105.0, typeof(Log), 1044041, 35, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PlainLowTable), 1044291, 1030266, 80.0, 105.0, typeof(Log), 1044041, 35, 1044351); + SetNeededExpansion(index, Expansion.SE); + } + + if (Core.ML) + { + index = AddCraft(typeof(OrnateElvenChair), 1044291, 1072870, 80.0, 105.0, typeof(Log), 1044041, 30, 1044351); + AddRecipe(index, 305); + SetNeededExpansion(index, Expansion.ML); + } + + // Containers + AddCraft(typeof(WoodenBox), 1044292, 1023709, 21.0, 46.0, typeof(Log), 1044041, 10, 1044351); + AddCraft(typeof(SmallCrate), 1044292, 1044309, 10.0, 35.0, typeof(Log), 1044041, 8, 1044351); + AddCraft(typeof(MediumCrate), 1044292, 1044310, 31.0, 56.0, typeof(Log), 1044041, 15, 1044351); + AddCraft(typeof(LargeCrate), 1044292, 1044311, 47.3, 72.3, typeof(Log), 1044041, 18, 1044351); + AddCraft(typeof(WoodenChest), 1044292, 1023650, 73.6, 98.6, typeof(Log), 1044041, 20, 1044351); + AddCraft(typeof(EmptyBookcase), 1044292, 1022718, 31.5, 56.5, typeof(Log), 1044041, 25, 1044351); + AddCraft(typeof(FancyArmoire), 1044292, 1044312, 84.2, 109.2, typeof(Log), 1044041, 35, 1044351); + AddCraft(typeof(Armoire), 1044292, 1022643, 84.2, 109.2, typeof(Log), 1044041, 35, 1044351); + + if (Core.SE) + { + index = AddCraft(typeof(PlainWoodenChest), 1044292, 1030251, 90.0, 115.0, typeof(Log), 1044041, 30, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(OrnateWoodenChest), 1044292, 1030253, 90.0, 115.0, typeof(Log), 1044041, 30, + 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(GildedWoodenChest), 1044292, 1030255, 90.0, 115.0, typeof(Log), 1044041, 30, + 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(WoodenFootLocker), 1044292, 1030257, 90.0, 115.0, typeof(Log), 1044041, 30, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(FinishedWoodenChest), 1044292, 1030259, 90.0, 115.0, typeof(Log), 1044041, 30, + 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(TallCabinet), 1044292, 1030261, 90.0, 115.0, typeof(Log), 1044041, 35, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(ShortCabinet), 1044292, 1030263, 90.0, 115.0, typeof(Log), 1044041, 35, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(RedArmoire), 1044292, 1030328, 90.0, 115.0, typeof(Log), 1044041, 40, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(ElegantArmoire), 1044292, 1030330, 90.0, 115.0, typeof(Log), 1044041, 40, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(MapleArmoire), 1044292, 1030332, 90.0, 115.0, typeof(Log), 1044041, 40, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(CherryArmoire), 1044292, 1030334, 90.0, 115.0, typeof(Log), 1044041, 40, 1044351); + SetNeededExpansion(index, Expansion.SE); + } + + index = AddCraft(typeof(Keg), 1044292, 1023711, 57.8, 82.8, typeof(BarrelStaves), 1044288, 3, 1044253); + AddRes(index, typeof(BarrelHoops), 1044289, 1, 1044253); + AddRes(index, typeof(BarrelLid), 1044251, 1, 1044253); + + if (Core.ML) + { + index = AddCraft(typeof(ArcaneBookshelfSouthDeed), 1044292, 1072871, 94.7, 119.7, typeof(Log), 1044041, 80, + 1044351); + AddRecipe(index, 306); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ArcaneBookshelfEastDeed), 1044292, 1073371, 94.7, 119.7, typeof(Log), 1044041, 80, + 1044351); + AddRecipe(index, 307); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + /* TODO + index = AddCraft( typeof( OrnateElvenChestSouthDeed ), 1044292, 1072862, 94.7, 119.7, typeof( Log ), 1044041, 40, 1044351 ); + AddRecipe( index, 308 ); + ForceNonExceptional( index ); + SetNeededExpansion( index, Expansion.ML ); + + index = AddCraft( typeof( OrnateElvenChestEastDeed ), 1044292, 1073383, 94.7, 119.7, typeof( Log ), 1044041, 40, 1044351 ); + AddRecipe( index, 309 ); + ForceNonExceptional( index ); + SetNeededExpansion( index, Expansion.ML ); + */ + + index = AddCraft(typeof(ElvenDresserSouthDeed), 1044292, 1072864, 75.0, 100.0, typeof(Log), 1044041, 45, + 1044351); + AddRecipe(index, 310); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ElvenDresserEastDeed), 1044292, 1073388, 75.0, 100.0, typeof(Log), 1044041, 45, + 1044351); + AddRecipe(index, 311); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + /* TODO + index = AddCraft( typeof( FancyElvenArmoire ), 1044292, 1072866, 80.0, 105.0, typeof( Log ), 1044041, 60, 1044351 ); + AddRecipe( index, 312 ); + ForceNonExceptional( index ); + SetNeededExpansion( index, Expansion.ML ); + */ + } + + // Staves and Shields + AddCraft(typeof(ShepherdsCrook), Core.ML ? 1044566 : 1044295, 1023713, 78.9, 103.9, typeof(Log), 1044041, 7, + 1044351); + AddCraft(typeof(QuarterStaff), Core.ML ? 1044566 : 1044295, 1023721, 73.6, 98.6, typeof(Log), 1044041, 6, + 1044351); + AddCraft(typeof(GnarledStaff), Core.ML ? 1044566 : 1044295, 1025112, 78.9, 103.9, typeof(Log), 1044041, 7, + 1044351); + AddCraft(typeof(WoodenShield), Core.ML ? 1062760 : 1044295, 1027034, 52.6, 77.6, typeof(Log), 1044041, 9, + 1044351); + + if (!Core.AOS) //Duplicate Entries to preserve ordering depending on era + { + index = AddCraft(typeof(FishingPole), Core.ML ? 1044294 : 1044295, 1023519, 68.4, 93.4, typeof(Log), 1044041, + 5, 1044351); //This is in the categor of Other during AoS + AddSkill(index, SkillName.Tailoring, 40.0, 45.0); + AddRes(index, typeof(Cloth), 1044286, 5, 1044287); + } + + if (Core.SE) + { + index = AddCraft(typeof(Bokuto), Core.ML ? 1044566 : 1044295, 1030227, 70.0, 95.0, typeof(Log), 1044041, 6, + 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(Fukiya), Core.ML ? 1044566 : 1044295, 1030229, 60.0, 85.0, typeof(Log), 1044041, 6, + 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(Tetsubo), Core.ML ? 1044566 : 1044295, 1030225, 80.0, 140.3, typeof(Log), 1044041, + 10, 1044351); + SetNeededExpansion(index, Expansion.SE); + } + + if (Core.ML) + { + index = AddCraft(typeof(PhantomStaff), 1044566, 1072919, 90.0, 130.0, typeof(Log), 1044041, 16, 1044351); + AddRes(index, typeof(DiseasedBark), 1032683, 1, 1053098); + AddRes(index, typeof(Putrefication), 1032678, 10, 1053098); + AddRes(index, typeof(Taint), 1032679, 10, 1053098); + AddRareRecipe(index, 313); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ArcanistsWildStaff), 1044566, 1073549, 63.8, 113.8, typeof(Log), 1044041, 16, + 1044351); + AddRes(index, typeof(WhitePearl), 1026253, 1, 1053098); + AddRecipe(index, 314); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(AncientWildStaff), 1044566, 1073550, 63.8, 113.8, typeof(Log), 1044041, 16, 1044351); + AddRes(index, typeof(PerfectEmerald), 1026251, 1, 1053098); + AddRecipe(index, 315); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(ThornedWildStaff), 1044566, 1073551, 63.8, 113.8, typeof(Log), 1044041, 16, 1044351); + AddRes(index, typeof(FireRuby), 1026254, 1, 1053098); + AddRecipe(index, 316); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(HardenedWildStaff), 1044566, 1073552, 63.8, 113.8, typeof(Log), 1044041, 16, + 1044351); + AddRes(index, typeof(Turquoise), 1026250, 1, 1053098); + AddRecipe(index, 317); + SetNeededExpansion(index, Expansion.ML); + } + + // Armor + if (Core.ML) + { + index = AddCraft(typeof(IronwoodCrown), 1062760, 1072924, 85.0, 120.0, typeof(Log), 1044041, 10, 1044351); + AddRes(index, typeof(DiseasedBark), 1032683, 1, 1053098); + AddRes(index, typeof(Corruption), 1032676, 10, 1053098); + AddRes(index, typeof(Putrefication), 1032678, 10, 1053098); + AddRareRecipe(index, 318); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(BrambleCoat), 1062760, 1072925, 85.0, 120.0, typeof(Log), 1044041, 10, 1044351); + AddRes(index, typeof(DiseasedBark), 1032683, 1, 1053098); + AddRes(index, typeof(Taint), 1032679, 10, 1053098); + AddRes(index, typeof(Scourge), 1032677, 10, 1053098); + AddRareRecipe(index, 319); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + } + + // Instruments + index = AddCraft(typeof(LapHarp), 1044293, 1023762, 63.1, 88.1, typeof(Log), 1044041, 20, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + AddRes(index, typeof(Cloth), 1044286, 10, 1044287); + + index = AddCraft(typeof(Harp), 1044293, 1023761, 78.9, 103.9, typeof(Log), 1044041, 35, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + AddRes(index, typeof(Cloth), 1044286, 15, 1044287); + + index = AddCraft(typeof(Drums), 1044293, 1023740, 57.8, 82.8, typeof(Log), 1044041, 20, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + AddRes(index, typeof(Cloth), 1044286, 10, 1044287); + + index = AddCraft(typeof(Lute), 1044293, 1023763, 68.4, 93.4, typeof(Log), 1044041, 25, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + AddRes(index, typeof(Cloth), 1044286, 10, 1044287); + + index = AddCraft(typeof(Tambourine), 1044293, 1023741, 57.8, 82.8, typeof(Log), 1044041, 15, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + AddRes(index, typeof(Cloth), 1044286, 10, 1044287); + + index = AddCraft(typeof(TambourineTassel), 1044293, 1044320, 57.8, 82.8, typeof(Log), 1044041, 15, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + AddRes(index, typeof(Cloth), 1044286, 15, 1044287); + + if (Core.SE) + { + index = AddCraft(typeof(BambooFlute), 1044293, 1030247, 80.0, 105.0, typeof(Log), 1044041, 15, 1044351); + AddSkill(index, SkillName.Musicianship, 45.0, 50.0); + SetNeededExpansion(index, Expansion.SE); + } + + if (Core.ML) + { + index = AddCraft(typeof(TallElvenBedSouthDeed), 1044290, 1072858, 94.7, 119.7, typeof(Log), 1044041, 200, + 1044351); + AddSkill(index, SkillName.Tailoring, 75.0, 80.0); + AddRes(index, typeof(Cloth), 1044286, 100, 1044287); + AddRecipe(index, 320); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(TallElvenBedEastDeed), 1044290, 1072859, 94.7, 119.7, typeof(Log), 1044041, 200, + 1044351); + AddSkill(index, SkillName.Tailoring, 75.0, 80.0); + AddRes(index, typeof(Cloth), 1044286, 100, 1044287); + AddRecipe(index, 321); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + } + + // Misc + index = AddCraft(typeof(SmallBedSouthDeed), 1044290, 1044321, 94.7, 119.8, typeof(Log), 1044041, 100, 1044351); + AddSkill(index, SkillName.Tailoring, 75.0, 80.0); + AddRes(index, typeof(Cloth), 1044286, 100, 1044287); + index = AddCraft(typeof(SmallBedEastDeed), 1044290, 1044322, 94.7, 119.8, typeof(Log), 1044041, 100, 1044351); + AddSkill(index, SkillName.Tailoring, 75.0, 80.0); + AddRes(index, typeof(Cloth), 1044286, 100, 1044287); + index = AddCraft(typeof(LargeBedSouthDeed), 1044290, 1044323, 94.7, 119.8, typeof(Log), 1044041, 150, 1044351); + AddSkill(index, SkillName.Tailoring, 75.0, 80.0); + AddRes(index, typeof(Cloth), 1044286, 150, 1044287); + index = AddCraft(typeof(LargeBedEastDeed), 1044290, 1044324, 94.7, 119.8, typeof(Log), 1044041, 150, 1044351); + AddSkill(index, SkillName.Tailoring, 75.0, 80.0); + AddRes(index, typeof(Cloth), 1044286, 150, 1044287); + AddCraft(typeof(DartBoardSouthDeed), 1044290, 1044325, 15.7, 40.7, typeof(Log), 1044041, 5, 1044351); + AddCraft(typeof(DartBoardEastDeed), 1044290, 1044326, 15.7, 40.7, typeof(Log), 1044041, 5, 1044351); + AddCraft(typeof(BallotBoxDeed), 1044290, 1044327, 47.3, 72.3, typeof(Log), 1044041, 5, 1044351); + index = AddCraft(typeof(PentagramDeed), 1044290, 1044328, 100.0, 125.0, typeof(Log), 1044041, 100, 1044351); + AddSkill(index, SkillName.Magery, 75.0, 80.0); + AddRes(index, typeof(IronIngot), 1044036, 40, 1044037); + index = AddCraft(typeof(AbbatoirDeed), 1044290, 1044329, 100.0, 125.0, typeof(Log), 1044041, 100, 1044351); + AddSkill(index, SkillName.Magery, 50.0, 55.0); + AddRes(index, typeof(IronIngot), 1044036, 40, 1044037); + + if (Core.AOS) + { + AddCraft(typeof(PlayerBBEast), 1044290, 1062420, 85.0, 110.0, typeof(Log), 1044041, 50, 1044351); + AddCraft(typeof(PlayerBBSouth), 1044290, 1062421, 85.0, 110.0, typeof(Log), 1044041, 50, 1044351); + } + + // Blacksmithy - This changed to Anvils and Forges (1111809) for SA + index = AddCraft(typeof(SmallForgeDeed), 1044296, 1044330, 73.6, 98.6, typeof(Log), 1044041, 5, 1044351); + AddSkill(index, SkillName.Blacksmith, 75.0, 80.0); + AddRes(index, typeof(IronIngot), 1044036, 75, 1044037); + index = AddCraft(typeof(LargeForgeEastDeed), 1044296, 1044331, 78.9, 103.9, typeof(Log), 1044041, 5, 1044351); + AddSkill(index, SkillName.Blacksmith, 80.0, 85.0); + AddRes(index, typeof(IronIngot), 1044036, 100, 1044037); + index = AddCraft(typeof(LargeForgeSouthDeed), 1044296, 1044332, 78.9, 103.9, typeof(Log), 1044041, 5, 1044351); + AddSkill(index, SkillName.Blacksmith, 80.0, 85.0); + AddRes(index, typeof(IronIngot), 1044036, 100, 1044037); + index = AddCraft(typeof(AnvilEastDeed), 1044296, 1044333, 73.6, 98.6, typeof(Log), 1044041, 5, 1044351); + AddSkill(index, SkillName.Blacksmith, 75.0, 80.0); + AddRes(index, typeof(IronIngot), 1044036, 150, 1044037); + index = AddCraft(typeof(AnvilSouthDeed), 1044296, 1044334, 73.6, 98.6, typeof(Log), 1044041, 5, 1044351); + AddSkill(index, SkillName.Blacksmith, 75.0, 80.0); + AddRes(index, typeof(IronIngot), 1044036, 150, 1044037); + + // Training + index = AddCraft(typeof(TrainingDummyEastDeed), 1044297, 1044335, 68.4, 93.4, typeof(Log), 1044041, 55, 1044351); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 60, 1044287); + index = AddCraft(typeof(TrainingDummySouthDeed), 1044297, 1044336, 68.4, 93.4, typeof(Log), 1044041, 55, + 1044351); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 60, 1044287); + index = AddCraft(typeof(PickpocketDipEastDeed), 1044297, 1044337, 73.6, 98.6, typeof(Log), 1044041, 65, 1044351); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 60, 1044287); + index = AddCraft(typeof(PickpocketDipSouthDeed), 1044297, 1044338, 73.6, 98.6, typeof(Log), 1044041, 65, + 1044351); + AddSkill(index, SkillName.Tailoring, 50.0, 55.0); + AddRes(index, typeof(Cloth), 1044286, 60, 1044287); + + // Tailoring + index = AddCraft(typeof(Dressform), 1044298, 1044339, 63.1, 88.1, typeof(Log), 1044041, 25, 1044351); + AddSkill(index, SkillName.Tailoring, 65.0, 70.0); + AddRes(index, typeof(Cloth), 1044286, 10, 1044287); + index = AddCraft(typeof(SpinningwheelEastDeed), 1044298, 1044341, 73.6, 98.6, typeof(Log), 1044041, 75, 1044351); + AddSkill(index, SkillName.Tailoring, 65.0, 70.0); + AddRes(index, typeof(Cloth), 1044286, 25, 1044287); + index = AddCraft(typeof(SpinningwheelSouthDeed), 1044298, 1044342, 73.6, 98.6, typeof(Log), 1044041, 75, + 1044351); + AddSkill(index, SkillName.Tailoring, 65.0, 70.0); + AddRes(index, typeof(Cloth), 1044286, 25, 1044287); + index = AddCraft(typeof(LoomEastDeed), 1044298, 1044343, 84.2, 109.2, typeof(Log), 1044041, 85, 1044351); + AddSkill(index, SkillName.Tailoring, 65.0, 70.0); + AddRes(index, typeof(Cloth), 1044286, 25, 1044287); + index = AddCraft(typeof(LoomSouthDeed), 1044298, 1044344, 84.2, 109.2, typeof(Log), 1044041, 85, 1044351); + AddSkill(index, SkillName.Tailoring, 65.0, 70.0); + AddRes(index, typeof(Cloth), 1044286, 25, 1044287); + + // Cooking + index = AddCraft(typeof(StoneOvenEastDeed), Core.ML ? 1044298 : 1044299, 1044345, 68.4, 93.4, typeof(Log), + 1044041, 85, 1044351); + AddSkill(index, SkillName.Tinkering, 50.0, 55.0); + AddRes(index, typeof(IronIngot), 1044036, 125, 1044037); + index = AddCraft(typeof(StoneOvenSouthDeed), Core.ML ? 1044298 : 1044299, 1044346, 68.4, 93.4, typeof(Log), + 1044041, 85, 1044351); + AddSkill(index, SkillName.Tinkering, 50.0, 55.0); + AddRes(index, typeof(IronIngot), 1044036, 125, 1044037); + index = AddCraft(typeof(FlourMillEastDeed), Core.ML ? 1044298 : 1044299, 1044347, 94.7, 119.7, typeof(Log), + 1044041, 100, 1044351); + AddSkill(index, SkillName.Tinkering, 50.0, 55.0); + AddRes(index, typeof(IronIngot), 1044036, 50, 1044037); + index = AddCraft(typeof(FlourMillSouthDeed), Core.ML ? 1044298 : 1044299, 1044348, 94.7, 119.7, typeof(Log), + 1044041, 100, 1044351); + AddSkill(index, SkillName.Tinkering, 50.0, 55.0); + AddRes(index, typeof(IronIngot), 1044036, 50, 1044037); + AddCraft(typeof(WaterTroughEastDeed), Core.ML ? 1044298 : 1044299, 1044349, 94.7, 119.7, typeof(Log), 1044041, + 150, 1044351); + AddCraft(typeof(WaterTroughSouthDeed), Core.ML ? 1044298 : 1044299, 1044350, 94.7, 119.7, typeof(Log), 1044041, + 150, 1044351); + + MarkOption = true; + Repair = Core.AOS; + + SetSubRes(typeof(Log), 1072643); + + // Add every material you want the player to be able to choose from + // This will override the overridable material TODO: Verify the required skill amount + AddSubRes(typeof(Log), 1072643, 00.0, 1044041, 1072652); + AddSubRes(typeof(OakLog), 1072644, 65.0, 1044041, 1072652); + AddSubRes(typeof(AshLog), 1072645, 80.0, 1044041, 1072652); + AddSubRes(typeof(YewLog), 1072646, 95.0, 1044041, 1072652); + AddSubRes(typeof(HeartwoodLog), 1072647, 100.0, 1044041, 1072652); + AddSubRes(typeof(BloodwoodLog), 1072648, 100.0, 1044041, 1072652); + AddSubRes(typeof(FrostwoodLog), 1072649, 100.0, 1044041, 1072652); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefCartography.cs b/Scripts/Engines/Craft/DefCartography.cs index 52be748ba..edd2567c8 100644 --- a/Scripts/Engines/Craft/DefCartography.cs +++ b/Scripts/Engines/Craft/DefCartography.cs @@ -3,76 +3,77 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefCartography : CraftSystem - { - public override SkillName MainSkill => SkillName.Cartography; + public class DefCartography : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044008; + private DefCartography() : base(1, 1, 1.25) // base( 1, 1, 3.0 ) + { + } - public override double GetChanceAtMin( CraftItem item ) - { - return 0.0; // 0% - } + public override SkillName MainSkill => SkillName.Cartography; - private static CraftSystem m_CraftSystem; + public override int GumpTitleNumber => 1044008; - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefCartography(); + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefCartography(); - return m_CraftSystem; - } - } + return m_CraftSystem; + } + } - private DefCartography() : base( 1, 1, 1.25 )// base( 1, 1, 3.0 ) - { - } + public override double GetChanceAtMin(CraftItem item) + { + return 0.0; // 0% + } - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - return 0; - } + return 0; + } - public override void PlayCraftEffect( Mobile from ) - { - from.PlaySound( 0x249 ); - } + public override void PlayCraftEffect(Mobile from) + { + from.PlaySound(0x249); + } - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } - public override void InitCraftList() - { - AddCraft( typeof( LocalMap ), 1044448, 1015230, 10.0, 70.0, typeof( BlankMap ), 1044449, 1, 1044450 ); - AddCraft( typeof( CityMap ), 1044448, 1015231, 25.0, 85.0, typeof( BlankMap ), 1044449, 1, 1044450 ); - AddCraft( typeof( SeaChart ), 1044448, 1015232, 35.0, 95.0, typeof( BlankMap ), 1044449, 1, 1044450 ); - AddCraft( typeof( WorldMap ), 1044448, 1015233, 39.5, 99.5, typeof( BlankMap ), 1044449, 1, 1044450 ); - } - } -} + public override void InitCraftList() + { + AddCraft(typeof(LocalMap), 1044448, 1015230, 10.0, 70.0, typeof(BlankMap), 1044449, 1, 1044450); + AddCraft(typeof(CityMap), 1044448, 1015231, 25.0, 85.0, typeof(BlankMap), 1044449, 1, 1044450); + AddCraft(typeof(SeaChart), 1044448, 1015232, 35.0, 95.0, typeof(BlankMap), 1044449, 1, 1044450); + AddCraft(typeof(WorldMap), 1044448, 1015233, 39.5, 99.5, typeof(BlankMap), 1044449, 1, 1044450); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefCooking.cs b/Scripts/Engines/Craft/DefCooking.cs index 0a8340dd6..c6751b967 100644 --- a/Scripts/Engines/Craft/DefCooking.cs +++ b/Scripts/Engines/Craft/DefCooking.cs @@ -3,276 +3,293 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefCooking : CraftSystem - { - public override SkillName MainSkill => SkillName.Cooking; + public class DefCooking : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044003; + private DefCooking() : base(1, 1, 1.25) // base( 1, 1, 1.5 ) + { + } - private static CraftSystem m_CraftSystem; + public override SkillName MainSkill => SkillName.Cooking; - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefCooking(); + public override int GumpTitleNumber => 1044003; - return m_CraftSystem; - } - } + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefCooking(); - public override CraftECA ECA => CraftECA.ChanceMinusSixtyToFourtyFive; + return m_CraftSystem; + } + } - public override double GetChanceAtMin( CraftItem item ) - { - return 0.0; // 0% - } + public override CraftECA ECA => CraftECA.ChanceMinusSixtyToFourtyFive; - private DefCooking() : base( 1, 1, 1.25 )// base( 1, 1, 1.5 ) - { - } + public override double GetChanceAtMin(CraftItem item) + { + return 0.0; // 0% + } - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - return 0; - } + return 0; + } - public override void PlayCraftEffect( Mobile from ) - { - } + public override void PlayCraftEffect(Mobile from) + { + } - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } - public override void InitCraftList() - { - int index = -1; + public override void InitCraftList() + { + int index = -1; - /* Begin Ingredients */ - index = AddCraft( typeof( SackFlour ), 1044495, 1024153, 0.0, 100.0, typeof( WheatSheaf ), 1044489, 2, 1044490 ); - SetNeedMill( index, true ); + /* Begin Ingredients */ + index = AddCraft(typeof(SackFlour), 1044495, 1024153, 0.0, 100.0, typeof(WheatSheaf), 1044489, 2, 1044490); + SetNeedMill(index, true); - index = AddCraft( typeof( Dough ), 1044495, 1024157, 0.0, 100.0, typeof( SackFlour ), 1044468, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1046458, 1, 1044253 ); + index = AddCraft(typeof(Dough), 1044495, 1024157, 0.0, 100.0, typeof(SackFlour), 1044468, 1, 1044253); + AddRes(index, typeof(BaseBeverage), 1046458, 1, 1044253); - index = AddCraft( typeof( SweetDough ), 1044495, 1041340, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( JarHoney ), 1044472, 1, 1044253 ); + index = AddCraft(typeof(SweetDough), 1044495, 1041340, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(JarHoney), 1044472, 1, 1044253); - index = AddCraft( typeof( CakeMix ), 1044495, 1041002, 0.0, 100.0, typeof( SackFlour ), 1044468, 1, 1044253 ); - AddRes( index, typeof( SweetDough ), 1044475, 1, 1044253 ); + index = AddCraft(typeof(CakeMix), 1044495, 1041002, 0.0, 100.0, typeof(SackFlour), 1044468, 1, 1044253); + AddRes(index, typeof(SweetDough), 1044475, 1, 1044253); - index = AddCraft( typeof( CookieMix ), 1044495, 1024159, 0.0, 100.0, typeof( JarHoney ), 1044472, 1, 1044253 ); - AddRes( index, typeof( SweetDough ), 1044475, 1, 1044253 ); + index = AddCraft(typeof(CookieMix), 1044495, 1024159, 0.0, 100.0, typeof(JarHoney), 1044472, 1, 1044253); + AddRes(index, typeof(SweetDough), 1044475, 1, 1044253); - if ( Core.ML ) - { - index = AddCraft( typeof( CocoaButter ), 1044495, 1079998, 0.0, 100.0, typeof( CocoaPulp ), 1080530, 1, 1044253 ); - SetItemHue( index, 0x457 ); - SetNeededExpansion( index, Expansion.ML ); - SetNeedOven( index, true ); + if (Core.ML) + { + index = AddCraft(typeof(CocoaButter), 1044495, 1079998, 0.0, 100.0, typeof(CocoaPulp), 1080530, 1, 1044253); + SetItemHue(index, 0x457); + SetNeededExpansion(index, Expansion.ML); + SetNeedOven(index, true); - index = AddCraft( typeof( CocoaLiquor ), 1044495, 1079999, 0.0, 100.0, typeof( CocoaPulp ), 1080530, 1, 1044253 ); - AddRes( index, typeof( EmptyPewterBowl ), 1025629, 1, 1044253 ); - SetItemHue( index, 0x46A ); - SetNeededExpansion( index, Expansion.ML ); - SetNeedOven( index, true ); - } - /* End Ingredients */ + index = AddCraft(typeof(CocoaLiquor), 1044495, 1079999, 0.0, 100.0, typeof(CocoaPulp), 1080530, 1, 1044253); + AddRes(index, typeof(EmptyPewterBowl), 1025629, 1, 1044253); + SetItemHue(index, 0x46A); + SetNeededExpansion(index, Expansion.ML); + SetNeedOven(index, true); + } + /* End Ingredients */ - /* Begin Preparations */ - index = AddCraft( typeof( UnbakedQuiche ), 1044496, 1041339, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( Eggs ), 1044477, 1, 1044253 ); + /* Begin Preparations */ + index = AddCraft(typeof(UnbakedQuiche), 1044496, 1041339, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(Eggs), 1044477, 1, 1044253); - // TODO: This must also support chicken and lamb legs - index = AddCraft( typeof( UnbakedMeatPie ), 1044496, 1041338, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( RawRibs ), 1044482, 1, 1044253 ); + // TODO: This must also support chicken and lamb legs + index = AddCraft(typeof(UnbakedMeatPie), 1044496, 1041338, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(RawRibs), 1044482, 1, 1044253); - index = AddCraft( typeof( UncookedSausagePizza ), 1044496, 1041337, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( Sausage ), 1044483, 1, 1044253 ); + index = AddCraft(typeof(UncookedSausagePizza), 1044496, 1041337, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(Sausage), 1044483, 1, 1044253); - index = AddCraft( typeof( UncookedCheesePizza ), 1044496, 1041341, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( CheeseWheel ), 1044486, 1, 1044253 ); + index = AddCraft(typeof(UncookedCheesePizza), 1044496, 1041341, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(CheeseWheel), 1044486, 1, 1044253); - index = AddCraft( typeof( UnbakedFruitPie ), 1044496, 1041334, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( Pear ), 1044481, 1, 1044253 ); + index = AddCraft(typeof(UnbakedFruitPie), 1044496, 1041334, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(Pear), 1044481, 1, 1044253); - index = AddCraft( typeof( UnbakedPeachCobbler ), 1044496, 1041335, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( Peach ), 1044480, 1, 1044253 ); + index = AddCraft(typeof(UnbakedPeachCobbler), 1044496, 1041335, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(Peach), 1044480, 1, 1044253); - index = AddCraft( typeof( UnbakedApplePie ), 1044496, 1041336, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( Apple ), 1044479, 1, 1044253 ); + index = AddCraft(typeof(UnbakedApplePie), 1044496, 1041336, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(Apple), 1044479, 1, 1044253); - index = AddCraft( typeof( UnbakedPumpkinPie ), 1044496, 1041342, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - AddRes( index, typeof( Pumpkin ), 1044484, 1, 1044253 ); + index = AddCraft(typeof(UnbakedPumpkinPie), 1044496, 1041342, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + AddRes(index, typeof(Pumpkin), 1044484, 1, 1044253); - if ( Core.SE ) - { - index = AddCraft( typeof( GreenTea ), 1044496, 1030315, 80.0, 130.0, typeof( GreenTeaBasket ), 1030316, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - SetNeedOven( index, true ); + if (Core.SE) + { + index = AddCraft(typeof(GreenTea), 1044496, 1030315, 80.0, 130.0, typeof(GreenTeaBasket), 1030316, 1, + 1044253); + AddRes(index, typeof(BaseBeverage), 1046458, 1, 1044253); + SetNeededExpansion(index, Expansion.SE); + SetNeedOven(index, true); - index = AddCraft( typeof( WasabiClumps ), 1044496, 1029451, 70.0, 120.0, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - AddRes( index, typeof( WoodenBowlOfPeas ), 1025633, 3, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); + index = AddCraft(typeof(WasabiClumps), 1044496, 1029451, 70.0, 120.0, typeof(BaseBeverage), 1046458, 1, + 1044253); + AddRes(index, typeof(WoodenBowlOfPeas), 1025633, 3, 1044253); + SetNeededExpansion(index, Expansion.SE); - index = AddCraft( typeof( SushiRolls ), 1044496, 1030303, 90.0, 120.0, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - AddRes( index, typeof( RawFishSteak ), 1044476, 10, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); + index = AddCraft(typeof(SushiRolls), 1044496, 1030303, 90.0, 120.0, typeof(BaseBeverage), 1046458, 1, + 1044253); + AddRes(index, typeof(RawFishSteak), 1044476, 10, 1044253); + SetNeededExpansion(index, Expansion.SE); - index = AddCraft( typeof( SushiPlatter ), 1044496, 1030305, 90.0, 120.0, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - AddRes( index, typeof( RawFishSteak ), 1044476, 10, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - } + index = AddCraft(typeof(SushiPlatter), 1044496, 1030305, 90.0, 120.0, typeof(BaseBeverage), 1046458, 1, + 1044253); + AddRes(index, typeof(RawFishSteak), 1044476, 10, 1044253); + SetNeededExpansion(index, Expansion.SE); + } - index = AddCraft( typeof( TribalPaint ), 1044496, 1040000, Core.ML? 55.0 : 80.0, Core.ML? 105.0 : 80.0, typeof( SackFlour ), 1044468, 1, 1044253 ); - AddRes( index, typeof( TribalBerry ), 1046460, 1, 1044253 ); + index = AddCraft(typeof(TribalPaint), 1044496, 1040000, Core.ML ? 55.0 : 80.0, Core.ML ? 105.0 : 80.0, + typeof(SackFlour), 1044468, 1, 1044253); + AddRes(index, typeof(TribalBerry), 1046460, 1, 1044253); - if ( Core.SE ) - { - index = AddCraft( typeof( EggBomb ), 1044496, 1030249, 90.0, 120.0, typeof( Eggs ), 1044477, 1, 1044253 ); - AddRes( index, typeof( SackFlour ), 1044468, 3, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - } - /* End Preparations */ + if (Core.SE) + { + index = AddCraft(typeof(EggBomb), 1044496, 1030249, 90.0, 120.0, typeof(Eggs), 1044477, 1, 1044253); + AddRes(index, typeof(SackFlour), 1044468, 3, 1044253); + SetNeededExpansion(index, Expansion.SE); + } + /* End Preparations */ - /* Begin Baking */ - index = AddCraft( typeof( BreadLoaf ), 1044497, 1024156, 0.0, 100.0, typeof( Dough ), 1044469, 1, 1044253 ); - SetNeedOven( index, true ); + /* Begin Baking */ + index = AddCraft(typeof(BreadLoaf), 1044497, 1024156, 0.0, 100.0, typeof(Dough), 1044469, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( Cookies ), 1044497, 1025643, 0.0, 100.0, typeof( CookieMix ), 1044474, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(Cookies), 1044497, 1025643, 0.0, 100.0, typeof(CookieMix), 1044474, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( Cake ), 1044497, 1022537, 0.0, 100.0, typeof( CakeMix ), 1044471, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(Cake), 1044497, 1022537, 0.0, 100.0, typeof(CakeMix), 1044471, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( Muffins ), 1044497, 1022539, 0.0, 100.0, typeof( SweetDough ), 1044475, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(Muffins), 1044497, 1022539, 0.0, 100.0, typeof(SweetDough), 1044475, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( Quiche ), 1044497, 1041345, 0.0, 100.0, typeof( UnbakedQuiche ), 1044518, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(Quiche), 1044497, 1041345, 0.0, 100.0, typeof(UnbakedQuiche), 1044518, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( MeatPie ), 1044497, 1041347, 0.0, 100.0, typeof( UnbakedMeatPie ), 1044519, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(MeatPie), 1044497, 1041347, 0.0, 100.0, typeof(UnbakedMeatPie), 1044519, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( SausagePizza ), 1044497, 1044517, 0.0, 100.0, typeof( UncookedSausagePizza ), 1044520, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(SausagePizza), 1044497, 1044517, 0.0, 100.0, typeof(UncookedSausagePizza), 1044520, 1, + 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( CheesePizza ), 1044497, 1044516, 0.0, 100.0, typeof( UncookedCheesePizza ), 1044521, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(CheesePizza), 1044497, 1044516, 0.0, 100.0, typeof(UncookedCheesePizza), 1044521, 1, + 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( FruitPie ), 1044497, 1041346, 0.0, 100.0, typeof( UnbakedFruitPie ), 1044522, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(FruitPie), 1044497, 1041346, 0.0, 100.0, typeof(UnbakedFruitPie), 1044522, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( PeachCobbler ), 1044497, 1041344, 0.0, 100.0, typeof( UnbakedPeachCobbler ), 1044523, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(PeachCobbler), 1044497, 1041344, 0.0, 100.0, typeof(UnbakedPeachCobbler), 1044523, 1, + 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( ApplePie ), 1044497, 1041343, 0.0, 100.0, typeof( UnbakedApplePie ), 1044524, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(ApplePie), 1044497, 1041343, 0.0, 100.0, typeof(UnbakedApplePie), 1044524, 1, 1044253); + SetNeedOven(index, true); - index = AddCraft( typeof( PumpkinPie ), 1044497, 1041348, 0.0, 100.0, typeof( UnbakedPumpkinPie ), 1046461, 1, 1044253 ); - SetNeedOven( index, true ); + index = AddCraft(typeof(PumpkinPie), 1044497, 1041348, 0.0, 100.0, typeof(UnbakedPumpkinPie), 1046461, 1, + 1044253); + SetNeedOven(index, true); - if ( Core.SE ) - { - index = AddCraft( typeof( MisoSoup ), 1044497, 1030317, 60.0, 110.0, typeof( RawFishSteak ), 1044476, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - SetNeedOven( index, true ); + if (Core.SE) + { + index = AddCraft(typeof(MisoSoup), 1044497, 1030317, 60.0, 110.0, typeof(RawFishSteak), 1044476, 1, 1044253); + AddRes(index, typeof(BaseBeverage), 1046458, 1, 1044253); + SetNeededExpansion(index, Expansion.SE); + SetNeedOven(index, true); - index = AddCraft( typeof( WhiteMisoSoup ), 1044497, 1030318, 60.0, 110.0, typeof( RawFishSteak ), 1044476, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - SetNeedOven( index, true ); + index = AddCraft(typeof(WhiteMisoSoup), 1044497, 1030318, 60.0, 110.0, typeof(RawFishSteak), 1044476, 1, + 1044253); + AddRes(index, typeof(BaseBeverage), 1046458, 1, 1044253); + SetNeededExpansion(index, Expansion.SE); + SetNeedOven(index, true); - index = AddCraft( typeof( RedMisoSoup ), 1044497, 1030319, 60.0, 110.0, typeof( RawFishSteak ), 1044476, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - SetNeedOven( index, true ); + index = AddCraft(typeof(RedMisoSoup), 1044497, 1030319, 60.0, 110.0, typeof(RawFishSteak), 1044476, 1, + 1044253); + AddRes(index, typeof(BaseBeverage), 1046458, 1, 1044253); + SetNeededExpansion(index, Expansion.SE); + SetNeedOven(index, true); - index = AddCraft( typeof( AwaseMisoSoup ), 1044497, 1030320, 60.0, 110.0, typeof( RawFishSteak ), 1044476, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1046458, 1, 1044253 ); - SetNeededExpansion( index, Expansion.SE ); - SetNeedOven( index, true ); - } - /* End Baking */ + index = AddCraft(typeof(AwaseMisoSoup), 1044497, 1030320, 60.0, 110.0, typeof(RawFishSteak), 1044476, 1, + 1044253); + AddRes(index, typeof(BaseBeverage), 1046458, 1, 1044253); + SetNeededExpansion(index, Expansion.SE); + SetNeedOven(index, true); + } + /* End Baking */ - /* Begin Barbecue */ - index = AddCraft( typeof( CookedBird ), 1044498, 1022487, 0.0, 100.0, typeof( RawBird ), 1044470, 1, 1044253 ); - SetNeedHeat( index, true ); - SetUseAllRes( index, true ); + /* Begin Barbecue */ + index = AddCraft(typeof(CookedBird), 1044498, 1022487, 0.0, 100.0, typeof(RawBird), 1044470, 1, 1044253); + SetNeedHeat(index, true); + SetUseAllRes(index, true); - index = AddCraft( typeof( ChickenLeg ), 1044498, 1025640, 0.0, 100.0, typeof( RawChickenLeg ), 1044473, 1, 1044253 ); - SetNeedHeat( index, true ); - SetUseAllRes( index, true ); + index = AddCraft(typeof(ChickenLeg), 1044498, 1025640, 0.0, 100.0, typeof(RawChickenLeg), 1044473, 1, 1044253); + SetNeedHeat(index, true); + SetUseAllRes(index, true); - index = AddCraft( typeof( FishSteak ), 1044498, 1022427, 0.0, 100.0, typeof( RawFishSteak ), 1044476, 1, 1044253 ); - SetNeedHeat( index, true ); - SetUseAllRes( index, true ); + index = AddCraft(typeof(FishSteak), 1044498, 1022427, 0.0, 100.0, typeof(RawFishSteak), 1044476, 1, 1044253); + SetNeedHeat(index, true); + SetUseAllRes(index, true); - index = AddCraft( typeof( FriedEggs ), 1044498, 1022486, 0.0, 100.0, typeof( Eggs ), 1044477, 1, 1044253 ); - SetNeedHeat( index, true ); - SetUseAllRes( index, true ); + index = AddCraft(typeof(FriedEggs), 1044498, 1022486, 0.0, 100.0, typeof(Eggs), 1044477, 1, 1044253); + SetNeedHeat(index, true); + SetUseAllRes(index, true); - index = AddCraft( typeof( LambLeg ), 1044498, 1025642, 0.0, 100.0, typeof( RawLambLeg ), 1044478, 1, 1044253 ); - SetNeedHeat( index, true ); - SetUseAllRes( index, true ); + index = AddCraft(typeof(LambLeg), 1044498, 1025642, 0.0, 100.0, typeof(RawLambLeg), 1044478, 1, 1044253); + SetNeedHeat(index, true); + SetUseAllRes(index, true); - index = AddCraft( typeof( Ribs ), 1044498, 1022546, 0.0, 100.0, typeof( RawRibs ), 1044485, 1, 1044253 ); - SetNeedHeat( index, true ); - SetUseAllRes( index, true ); - /* End Barbecue */ + index = AddCraft(typeof(Ribs), 1044498, 1022546, 0.0, 100.0, typeof(RawRibs), 1044485, 1, 1044253); + SetNeedHeat(index, true); + SetUseAllRes(index, true); + /* End Barbecue */ - /* Begin Chocolatiering */ - if ( Core.ML ) - { - index = AddCraft( typeof( DarkChocolate ), 1080001, 1079994, 15.0, 100.0, typeof( SackOfSugar ), 1079997, 1, 1044253 ); - AddRes( index, typeof( CocoaButter ), 1079998, 1, 1044253 ); - AddRes( index, typeof( CocoaLiquor ), 1079999, 1, 1044253 ); - SetItemHue( index, 0x465 ); - SetNeededExpansion( index, Expansion.ML ); + /* Begin Chocolatiering */ + if (Core.ML) + { + index = AddCraft(typeof(DarkChocolate), 1080001, 1079994, 15.0, 100.0, typeof(SackOfSugar), 1079997, 1, + 1044253); + AddRes(index, typeof(CocoaButter), 1079998, 1, 1044253); + AddRes(index, typeof(CocoaLiquor), 1079999, 1, 1044253); + SetItemHue(index, 0x465); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( MilkChocolate ), 1080001, 1079995, 32.5, 107.5, typeof( SackOfSugar ), 1079997, 1, 1044253 ); - AddRes( index, typeof( CocoaButter ), 1079998, 1, 1044253 ); - AddRes( index, typeof( CocoaLiquor ), 1079999, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1022544, 1, 1044253 ); - SetBeverageType( index, BeverageType.Milk ); - SetItemHue( index, 0x461 ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(MilkChocolate), 1080001, 1079995, 32.5, 107.5, typeof(SackOfSugar), 1079997, 1, + 1044253); + AddRes(index, typeof(CocoaButter), 1079998, 1, 1044253); + AddRes(index, typeof(CocoaLiquor), 1079999, 1, 1044253); + AddRes(index, typeof(BaseBeverage), 1022544, 1, 1044253); + SetBeverageType(index, BeverageType.Milk); + SetItemHue(index, 0x461); + SetNeededExpansion(index, Expansion.ML); - index = AddCraft( typeof( WhiteChocolate ), 1080001, 1079996, 52.5, 127.5, typeof( SackOfSugar ), 1079997, 1, 1044253 ); - AddRes( index, typeof( CocoaButter ), 1079998, 1, 1044253 ); - AddRes( index, typeof( Vanilla ), 1080000, 1, 1044253 ); - AddRes( index, typeof( BaseBeverage ), 1022544, 1, 1044253 ); - SetBeverageType( index, BeverageType.Milk ); - SetItemHue( index, 0x47E ); - SetNeededExpansion( index, Expansion.ML ); - } - /* End Chocolatiering */ - } - } -} + index = AddCraft(typeof(WhiteChocolate), 1080001, 1079996, 52.5, 127.5, typeof(SackOfSugar), 1079997, 1, + 1044253); + AddRes(index, typeof(CocoaButter), 1079998, 1, 1044253); + AddRes(index, typeof(Vanilla), 1080000, 1, 1044253); + AddRes(index, typeof(BaseBeverage), 1022544, 1, 1044253); + SetBeverageType(index, BeverageType.Milk); + SetItemHue(index, 0x47E); + SetNeededExpansion(index, Expansion.ML); + } + + /* End Chocolatiering */ + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefGlassblowing.cs b/Scripts/Engines/Craft/DefGlassblowing.cs index 182e48188..0ba7a8040 100644 --- a/Scripts/Engines/Craft/DefGlassblowing.cs +++ b/Scripts/Engines/Craft/DefGlassblowing.cs @@ -4,129 +4,130 @@ using Server.Mobiles; namespace Server.Engines.Craft { - public class DefGlassblowing : CraftSystem - { - public override SkillName MainSkill => SkillName.Alchemy; + public class DefGlassblowing : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044622; + private DefGlassblowing() : base(1, 1, 1.25) // base( 1, 2, 1.7 ) + { + } - private static CraftSystem m_CraftSystem; + public override SkillName MainSkill => SkillName.Alchemy; - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefGlassblowing(); + public override int GumpTitleNumber => 1044622; - return m_CraftSystem; - } - } + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefGlassblowing(); - public override double GetChanceAtMin( CraftItem item ) - { - if ( item.ItemType == typeof( HollowPrism ) ) - return 0.5; // 50% + return m_CraftSystem; + } + } - return 0.0; // 0% - } + public override double GetChanceAtMin(CraftItem item) + { + if (item.ItemType == typeof(HollowPrism)) + return 0.5; // 50% - private DefGlassblowing() : base( 1, 1, 1.25 )// base( 1, 2, 1.7 ) - { - } + return 0.0; // 0% + } - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckTool( tool, from ) ) - return 1048146; // If you have a tool equipped, you must use that tool. - if ( !(from is PlayerMobile mobile && mobile.Glassblowing && mobile.Skills[SkillName.Alchemy].Base >= 100.0) ) - return 1044634; // You havent learned glassblowing. - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckTool(tool, from)) + return 1048146; // If you have a tool equipped, you must use that tool. + if (!(from is PlayerMobile mobile && mobile.Glassblowing && mobile.Skills[SkillName.Alchemy].Base >= 100.0)) + return 1044634; // You havent learned glassblowing. + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - bool anvil, forge; + bool anvil, forge; - DefBlacksmithy.CheckAnvilAndForge( from, 2, out anvil, out forge ); + DefBlacksmithy.CheckAnvilAndForge(from, 2, out anvil, out forge); - if ( forge ) - return 0; + if (forge) + return 0; - return 1044628; // You must be near a forge to blow glass. - } + return 1044628; // You must be near a forge to blow glass. + } - public override void PlayCraftEffect( Mobile from ) - { - from.PlaySound( 0x2B ); // bellows + public override void PlayCraftEffect(Mobile from) + { + from.PlaySound(0x2B); // bellows - //if ( from.Body.Type == BodyType.Human && !from.Mounted ) - // from.Animate( 9, 5, 1, true, false, 0 ); + //if ( from.Body.Type == BodyType.Human && !from.Mounted ) + // from.Animate( 9, 5, 1, true, false, 0 ); - //new InternalTimer( from ).Start(); - } + //new InternalTimer( from ).Start(); + } - // Delay to synchronize the sound with the hit on the anvil - private class InternalTimer : Timer - { - private Mobile m_From; + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - public InternalTimer( Mobile from ) : base( TimeSpan.FromSeconds( 0.7 ) ) - { - m_From = from; - } + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } - protected override void OnTick() - { - m_From.PlaySound( 0x2A ); - } - } + from.PlaySound(0x41); // glass breaking - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } + public override void InitCraftList() + { + int index = AddCraft(typeof(Bottle), 1044050, 1023854, 52.5, 102.5, typeof(Sand), 1044625, 1, 1044627); + SetUseAllRes(index, true); - from.PlaySound( 0x41 ); // glass breaking + AddCraft(typeof(SmallFlask), 1044050, 1044610, 52.5, 102.5, typeof(Sand), 1044625, 2, 1044627); + AddCraft(typeof(MediumFlask), 1044050, 1044611, 52.5, 102.5, typeof(Sand), 1044625, 3, 1044627); + AddCraft(typeof(CurvedFlask), 1044050, 1044612, 55.0, 105.0, typeof(Sand), 1044625, 2, 1044627); + AddCraft(typeof(LongFlask), 1044050, 1044613, 57.5, 107.5, typeof(Sand), 1044625, 4, 1044627); + AddCraft(typeof(LargeFlask), 1044050, 1044623, 60.0, 110.0, typeof(Sand), 1044625, 5, 1044627); + AddCraft(typeof(AniSmallBlueFlask), 1044050, 1044614, 60.0, 110.0, typeof(Sand), 1044625, 5, 1044627); + AddCraft(typeof(AniLargeVioletFlask), 1044050, 1044615, 60.0, 110.0, typeof(Sand), 1044625, 5, 1044627); + AddCraft(typeof(AniRedRibbedFlask), 1044050, 1044624, 60.0, 110.0, typeof(Sand), 1044625, 7, 1044627); + AddCraft(typeof(EmptyVialsWRack), 1044050, 1044616, 65.0, 115.0, typeof(Sand), 1044625, 8, 1044627); + AddCraft(typeof(FullVialsWRack), 1044050, 1044617, 65.0, 115.0, typeof(Sand), 1044625, 9, 1044627); + AddCraft(typeof(SpinningHourglass), 1044050, 1044618, 75.0, 125.0, typeof(Sand), 1044625, 10, 1044627); - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } + if (Core.ML) + { + index = AddCraft(typeof(HollowPrism), 1044050, 1072895, 100.0, 150.0, typeof(Sand), 1044625, 8, 1044627); + SetNeededExpansion(index, Expansion.ML); + } + } - public override void InitCraftList() - { - int index = AddCraft( typeof( Bottle ), 1044050, 1023854, 52.5, 102.5, typeof( Sand ), 1044625, 1, 1044627 ); - SetUseAllRes( index, true ); + // Delay to synchronize the sound with the hit on the anvil + private class InternalTimer : Timer + { + private Mobile m_From; - AddCraft( typeof( SmallFlask ), 1044050, 1044610, 52.5, 102.5, typeof( Sand ), 1044625, 2, 1044627 ); - AddCraft( typeof( MediumFlask ), 1044050, 1044611, 52.5, 102.5, typeof( Sand ), 1044625, 3, 1044627 ); - AddCraft( typeof( CurvedFlask ), 1044050, 1044612, 55.0, 105.0, typeof( Sand ), 1044625, 2, 1044627 ); - AddCraft( typeof( LongFlask ), 1044050, 1044613, 57.5, 107.5, typeof( Sand ), 1044625, 4, 1044627 ); - AddCraft( typeof( LargeFlask ), 1044050, 1044623, 60.0, 110.0, typeof( Sand ), 1044625, 5, 1044627 ); - AddCraft( typeof( AniSmallBlueFlask ), 1044050, 1044614, 60.0, 110.0, typeof( Sand ), 1044625, 5, 1044627 ); - AddCraft( typeof( AniLargeVioletFlask ), 1044050, 1044615, 60.0, 110.0, typeof( Sand ), 1044625, 5, 1044627 ); - AddCraft( typeof( AniRedRibbedFlask ), 1044050, 1044624, 60.0, 110.0, typeof( Sand ), 1044625, 7, 1044627 ); - AddCraft( typeof( EmptyVialsWRack ), 1044050, 1044616, 65.0, 115.0, typeof( Sand ), 1044625, 8, 1044627 ); - AddCraft( typeof( FullVialsWRack ), 1044050, 1044617, 65.0, 115.0, typeof( Sand ), 1044625, 9, 1044627 ); - AddCraft( typeof( SpinningHourglass ), 1044050, 1044618, 75.0, 125.0, typeof( Sand ), 1044625, 10, 1044627 ); + public InternalTimer(Mobile from) : base(TimeSpan.FromSeconds(0.7)) + { + m_From = from; + } - if ( Core.ML ) - { - index = AddCraft( typeof( HollowPrism ), 1044050, 1072895, 100.0, 150.0, typeof( Sand ), 1044625, 8, 1044627 ); - SetNeededExpansion( index, Expansion.ML ); - } - } - } -} + protected override void OnTick() + { + m_From.PlaySound(0x2A); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefInscription.cs b/Scripts/Engines/Craft/DefInscription.cs index d13c88ef1..80d6aeb99 100644 --- a/Scripts/Engines/Craft/DefInscription.cs +++ b/Scripts/Engines/Craft/DefInscription.cs @@ -1,393 +1,412 @@ using System; +using Server.Engines.BulkOrders; using Server.Items; using Server.Spells; namespace Server.Engines.Craft { - public class DefInscription : CraftSystem - { - public override SkillName MainSkill => SkillName.Inscribe; + public class DefInscription : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044009; + private static Type typeofSpellScroll = typeof(SpellScroll); - private static CraftSystem m_CraftSystem; + private int m_Circle, m_Mana; - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefInscription(); + private int m_Index; - return m_CraftSystem; - } - } + private Type[] m_RegTypes = + { + typeof(BlackPearl), + typeof(Bloodmoss), + typeof(Garlic), + typeof(Ginseng), + typeof(MandrakeRoot), + typeof(Nightshade), + typeof(SulfurousAsh), + typeof(SpidersSilk) + }; - public override double GetChanceAtMin( CraftItem item ) - { - return 0.0; // 0% - } + private DefInscription() + : base(1, 1, 1.25) // base( 1, 1, 3.0 ) + { + } - private DefInscription() - : base( 1, 1, 1.25 ) // base( 1, 1, 3.0 ) - { - } + public override SkillName MainSkill => SkillName.Inscribe; - public override int CanCraft( Mobile from, BaseTool tool, Type typeItem ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override int GumpTitleNumber => 1044009; - if ( typeItem != null ) - { - var o = Activator.CreateInstance( typeItem ); + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefInscription(); - if ( o is SpellScroll scroll ) - { - var book = Spellbook.Find( from, scroll.SpellID ); + return m_CraftSystem; + } + } - var hasSpell = ( book != null && book.HasSpell( scroll.SpellID ) ); + public override double GetChanceAtMin(CraftItem item) + { + return 0.0; // 0% + } - scroll.Delete(); + public override int CanCraft(Mobile from, BaseTool tool, Type typeItem) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - return ( hasSpell ? 0 : 1042404 ); // null : You don't have that spell! - } + if (typeItem != null) + { + object o = Activator.CreateInstance(typeItem); - if ( o is Item item ) - { - item.Delete(); - } - } + if (o is SpellScroll scroll) + { + Spellbook book = Spellbook.Find(from, scroll.SpellID); - return 0; - } + bool hasSpell = book != null && book.HasSpell(scroll.SpellID); - public override void PlayCraftEffect( Mobile from ) - { - from.PlaySound( 0x249 ); - } + scroll.Delete(); - private static Type typeofSpellScroll = typeof( SpellScroll ); + return hasSpell ? 0 : 1042404; // null : You don't have that spell! + } - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + if (o is Item item) item.Delete(); + } - if ( !typeofSpellScroll.IsAssignableFrom( item.ItemType ) ) // not a scroll - { - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } + return 0; + } - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } + public override void PlayCraftEffect(Mobile from) + { + from.PlaySound(0x249); + } - if ( failed ) - return 501630; // You fail to inscribe the scroll, and the scroll is ruined. - return 501629; // You inscribe the spell and put the scroll in your backpack. - } + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - private int m_Circle, m_Mana; + if (!typeofSpellScroll.IsAssignableFrom(item.ItemType)) // not a scroll + { + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } - private enum Reg - { - BlackPearl, - Bloodmoss, - Garlic, - Ginseng, - MandrakeRoot, - Nightshade, - SulfurousAsh, - SpidersSilk - } + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } - private Type[] m_RegTypes = { - typeof( BlackPearl ), - typeof( Bloodmoss ), - typeof( Garlic ), - typeof( Ginseng ), - typeof( MandrakeRoot ), - typeof( Nightshade ), - typeof( SulfurousAsh ), - typeof( SpidersSilk ) - }; + if (failed) + return 501630; // You fail to inscribe the scroll, and the scroll is ruined. + return 501629; // You inscribe the spell and put the scroll in your backpack. + } - private int m_Index; + private void AddSpell(Type type, params Reg[] regs) + { + double minSkill, maxSkill; - private void AddSpell( Type type, params Reg[] regs ) - { - double minSkill, maxSkill; + switch (m_Circle) + { + default: + case 0: + minSkill = -25.0; + maxSkill = 25.0; + break; + case 1: + minSkill = -10.8; + maxSkill = 39.2; + break; + case 2: + minSkill = 03.5; + maxSkill = 53.5; + break; + case 3: + minSkill = 17.8; + maxSkill = 67.8; + break; + case 4: + minSkill = 32.1; + maxSkill = 82.1; + break; + case 5: + minSkill = 46.4; + maxSkill = 96.4; + break; + case 6: + minSkill = 60.7; + maxSkill = 110.7; + break; + case 7: + minSkill = 75.0; + maxSkill = 125.0; + break; + } - switch ( m_Circle ) - { - default: - case 0: - minSkill = -25.0; - maxSkill = 25.0; - break; - case 1: - minSkill = -10.8; - maxSkill = 39.2; - break; - case 2: - minSkill = 03.5; - maxSkill = 53.5; - break; - case 3: - minSkill = 17.8; - maxSkill = 67.8; - break; - case 4: - minSkill = 32.1; - maxSkill = 82.1; - break; - case 5: - minSkill = 46.4; - maxSkill = 96.4; - break; - case 6: - minSkill = 60.7; - maxSkill = 110.7; - break; - case 7: - minSkill = 75.0; - maxSkill = 125.0; - break; - } + int index = AddCraft(type, 1044369 + m_Circle, 1044381 + m_Index++, minSkill, maxSkill, m_RegTypes[(int)regs[0]], + 1044353 + (int)regs[0], 1, 1044361 + (int)regs[0]); - int index = AddCraft( type, 1044369 + m_Circle, 1044381 + m_Index++, minSkill, maxSkill, m_RegTypes[(int) regs[0]], 1044353 + (int) regs[0], 1, 1044361 + (int) regs[0] ); + for (int i = 1; i < regs.Length; ++i) + AddRes(index, m_RegTypes[(int)regs[i]], 1044353 + (int)regs[i], 1, 1044361 + (int)regs[i]); - for ( int i = 1; i < regs.Length; ++i ) - AddRes( index, m_RegTypes[(int) regs[i]], 1044353 + (int) regs[i], 1, 1044361 + (int) regs[i] ); + AddRes(index, typeof(BlankScroll), 1044377, 1, 1044378); - AddRes( index, typeof( BlankScroll ), 1044377, 1, 1044378 ); + SetManaReq(index, m_Mana); + } - SetManaReq( index, m_Mana ); - } + private void AddNecroSpell(int spell, int mana, double minSkill, Type type, params Type[] regs) + { + int index = AddCraft(type, 1061677, 1060509 + spell, minSkill, minSkill + 1.0, regs[0], + CraftItem.LabelNumber(regs[0]), 1, + 501627); //Yes, on OSI it's only 1.0 skill diff'. Don't blame me, blame OSI. - private void AddNecroSpell( int spell, int mana, double minSkill, Type type, params Type[] regs ) - { - int index = AddCraft( type, 1061677, 1060509 + spell, minSkill, minSkill + 1.0, regs[0], CraftItem.LabelNumber( regs[0] ), 1, 501627 ); //Yes, on OSI it's only 1.0 skill diff'. Don't blame me, blame OSI. + for (int i = 1; i < regs.Length; ++i) + AddRes(index, regs[i], CraftItem.LabelNumber(regs[0]), 1, 501627); - for ( int i = 1; i < regs.Length; ++i ) - AddRes( index, regs[i], CraftItem.LabelNumber( regs[0] ), 1, 501627 ); + AddRes(index, typeof(BlankScroll), 1044377, 1, 1044378); + SetManaReq(index, mana); + } - AddRes( index, typeof( BlankScroll ), 1044377, 1, 1044378 ); - SetManaReq( index, mana ); - } + private void AddMysticismSpell(int spell, int mana, double minSkill, double maxSkill, Type type, params Type[] regs) + { + int index = AddCraft(type, 1111671, 1031678 + spell, minSkill, maxSkill, regs[0], CraftItem.LabelNumber(regs[0]), + 1, 501627); - private void AddMysticismSpell( int spell, int mana, double minSkill, double maxSkill, Type type, params Type[] regs ) - { - int index = AddCraft( type, 1111671, 1031678 + spell, minSkill, maxSkill, regs[0], CraftItem.LabelNumber( regs[0] ), 1, 501627 ); + for (int i = 1; i < regs.Length; ++i) + AddRes(index, regs[i], CraftItem.LabelNumber(regs[i]), 1, 501627); - for ( int i = 1; i < regs.Length; ++i ) - AddRes( index, regs[i], CraftItem.LabelNumber( regs[i] ), 1, 501627 ); + AddRes(index, typeof(BlankScroll), 1044377, 1, 1044378); + SetManaReq(index, mana); + } - AddRes( index, typeof( BlankScroll ), 1044377, 1, 1044378 ); - SetManaReq( index, mana) ; - } + public override void InitCraftList() + { + m_Circle = 0; + m_Mana = 4; - public override void InitCraftList() - { - m_Circle = 0; - m_Mana = 4; + AddSpell(typeof(ReactiveArmorScroll), Reg.Garlic, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(ClumsyScroll), Reg.Bloodmoss, Reg.Nightshade); + AddSpell(typeof(CreateFoodScroll), Reg.Garlic, Reg.Ginseng, Reg.MandrakeRoot); + AddSpell(typeof(FeeblemindScroll), Reg.Nightshade, Reg.Ginseng); + AddSpell(typeof(HealScroll), Reg.Garlic, Reg.Ginseng, Reg.SpidersSilk); + AddSpell(typeof(MagicArrowScroll), Reg.SulfurousAsh); + AddSpell(typeof(NightSightScroll), Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(WeakenScroll), Reg.Garlic, Reg.Nightshade); - AddSpell( typeof( ReactiveArmorScroll ), Reg.Garlic, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( ClumsyScroll ), Reg.Bloodmoss, Reg.Nightshade ); - AddSpell( typeof( CreateFoodScroll ), Reg.Garlic, Reg.Ginseng, Reg.MandrakeRoot ); - AddSpell( typeof( FeeblemindScroll ), Reg.Nightshade, Reg.Ginseng ); - AddSpell( typeof( HealScroll ), Reg.Garlic, Reg.Ginseng, Reg.SpidersSilk ); - AddSpell( typeof( MagicArrowScroll ), Reg.SulfurousAsh ); - AddSpell( typeof( NightSightScroll ), Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( WeakenScroll ), Reg.Garlic, Reg.Nightshade ); + m_Circle = 1; + m_Mana = 6; - m_Circle = 1; - m_Mana = 6; + AddSpell(typeof(AgilityScroll), Reg.Bloodmoss, Reg.MandrakeRoot); + AddSpell(typeof(CunningScroll), Reg.Nightshade, Reg.MandrakeRoot); + AddSpell(typeof(CureScroll), Reg.Garlic, Reg.Ginseng); + AddSpell(typeof(HarmScroll), Reg.Nightshade, Reg.SpidersSilk); + AddSpell(typeof(MagicTrapScroll), Reg.Garlic, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(MagicUnTrapScroll), Reg.Bloodmoss, Reg.SulfurousAsh); + AddSpell(typeof(ProtectionScroll), Reg.Garlic, Reg.Ginseng, Reg.SulfurousAsh); + AddSpell(typeof(StrengthScroll), Reg.Nightshade, Reg.MandrakeRoot); - AddSpell( typeof( AgilityScroll ), Reg.Bloodmoss, Reg.MandrakeRoot ); - AddSpell( typeof( CunningScroll ), Reg.Nightshade, Reg.MandrakeRoot ); - AddSpell( typeof( CureScroll ), Reg.Garlic, Reg.Ginseng ); - AddSpell( typeof( HarmScroll ), Reg.Nightshade, Reg.SpidersSilk ); - AddSpell( typeof( MagicTrapScroll ), Reg.Garlic, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( MagicUnTrapScroll ), Reg.Bloodmoss, Reg.SulfurousAsh ); - AddSpell( typeof( ProtectionScroll ), Reg.Garlic, Reg.Ginseng, Reg.SulfurousAsh ); - AddSpell( typeof( StrengthScroll ), Reg.Nightshade, Reg.MandrakeRoot ); + m_Circle = 2; + m_Mana = 9; - m_Circle = 2; - m_Mana = 9; + AddSpell(typeof(BlessScroll), Reg.Garlic, Reg.MandrakeRoot); + AddSpell(typeof(FireballScroll), Reg.BlackPearl); + AddSpell(typeof(MagicLockScroll), Reg.Bloodmoss, Reg.Garlic, Reg.SulfurousAsh); + AddSpell(typeof(PoisonScroll), Reg.Nightshade); + AddSpell(typeof(TelekinisisScroll), Reg.Bloodmoss, Reg.MandrakeRoot); + AddSpell(typeof(TeleportScroll), Reg.Bloodmoss, Reg.MandrakeRoot); + AddSpell(typeof(UnlockScroll), Reg.Bloodmoss, Reg.SulfurousAsh); + AddSpell(typeof(WallOfStoneScroll), Reg.Bloodmoss, Reg.Garlic); - AddSpell( typeof( BlessScroll ), Reg.Garlic, Reg.MandrakeRoot ); - AddSpell( typeof( FireballScroll ), Reg.BlackPearl ); - AddSpell( typeof( MagicLockScroll ), Reg.Bloodmoss, Reg.Garlic, Reg.SulfurousAsh ); - AddSpell( typeof( PoisonScroll ), Reg.Nightshade ); - AddSpell( typeof( TelekinisisScroll ), Reg.Bloodmoss, Reg.MandrakeRoot ); - AddSpell( typeof( TeleportScroll ), Reg.Bloodmoss, Reg.MandrakeRoot ); - AddSpell( typeof( UnlockScroll ), Reg.Bloodmoss, Reg.SulfurousAsh ); - AddSpell( typeof( WallOfStoneScroll ), Reg.Bloodmoss, Reg.Garlic ); + m_Circle = 3; + m_Mana = 11; - m_Circle = 3; - m_Mana = 11; + AddSpell(typeof(ArchCureScroll), Reg.Garlic, Reg.Ginseng, Reg.MandrakeRoot); + AddSpell(typeof(ArchProtectionScroll), Reg.Garlic, Reg.Ginseng, Reg.MandrakeRoot, Reg.SulfurousAsh); + AddSpell(typeof(CurseScroll), Reg.Garlic, Reg.Nightshade, Reg.SulfurousAsh); + AddSpell(typeof(FireFieldScroll), Reg.BlackPearl, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(GreaterHealScroll), Reg.Garlic, Reg.SpidersSilk, Reg.MandrakeRoot, Reg.Ginseng); + AddSpell(typeof(LightningScroll), Reg.MandrakeRoot, Reg.SulfurousAsh); + AddSpell(typeof(ManaDrainScroll), Reg.BlackPearl, Reg.SpidersSilk, Reg.MandrakeRoot); + AddSpell(typeof(RecallScroll), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot); - AddSpell( typeof( ArchCureScroll ), Reg.Garlic, Reg.Ginseng, Reg.MandrakeRoot ); - AddSpell( typeof( ArchProtectionScroll ), Reg.Garlic, Reg.Ginseng, Reg.MandrakeRoot, Reg.SulfurousAsh ); - AddSpell( typeof( CurseScroll ), Reg.Garlic, Reg.Nightshade, Reg.SulfurousAsh ); - AddSpell( typeof( FireFieldScroll ), Reg.BlackPearl, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( GreaterHealScroll ), Reg.Garlic, Reg.SpidersSilk, Reg.MandrakeRoot, Reg.Ginseng ); - AddSpell( typeof( LightningScroll ), Reg.MandrakeRoot, Reg.SulfurousAsh ); - AddSpell( typeof( ManaDrainScroll ), Reg.BlackPearl, Reg.SpidersSilk, Reg.MandrakeRoot ); - AddSpell( typeof( RecallScroll ), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot ); + m_Circle = 4; + m_Mana = 14; - m_Circle = 4; - m_Mana = 14; + AddSpell(typeof(BladeSpiritsScroll), Reg.BlackPearl, Reg.Nightshade, Reg.MandrakeRoot); + AddSpell(typeof(DispelFieldScroll), Reg.BlackPearl, Reg.Garlic, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(IncognitoScroll), Reg.Bloodmoss, Reg.Garlic, Reg.Nightshade); + AddSpell(typeof(MagicReflectScroll), Reg.Garlic, Reg.MandrakeRoot, Reg.SpidersSilk); + AddSpell(typeof(MindBlastScroll), Reg.BlackPearl, Reg.MandrakeRoot, Reg.Nightshade, Reg.SulfurousAsh); + AddSpell(typeof(ParalyzeScroll), Reg.Garlic, Reg.MandrakeRoot, Reg.SpidersSilk); + AddSpell(typeof(PoisonFieldScroll), Reg.BlackPearl, Reg.Nightshade, Reg.SpidersSilk); + AddSpell(typeof(SummonCreatureScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk); - AddSpell( typeof( BladeSpiritsScroll ), Reg.BlackPearl, Reg.Nightshade, Reg.MandrakeRoot ); - AddSpell( typeof( DispelFieldScroll ), Reg.BlackPearl, Reg.Garlic, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( IncognitoScroll ), Reg.Bloodmoss, Reg.Garlic, Reg.Nightshade ); - AddSpell( typeof( MagicReflectScroll ), Reg.Garlic, Reg.MandrakeRoot, Reg.SpidersSilk ); - AddSpell( typeof( MindBlastScroll ), Reg.BlackPearl, Reg.MandrakeRoot, Reg.Nightshade, Reg.SulfurousAsh ); - AddSpell( typeof( ParalyzeScroll ), Reg.Garlic, Reg.MandrakeRoot, Reg.SpidersSilk ); - AddSpell( typeof( PoisonFieldScroll ), Reg.BlackPearl, Reg.Nightshade, Reg.SpidersSilk ); - AddSpell( typeof( SummonCreatureScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk ); + m_Circle = 5; + m_Mana = 20; - m_Circle = 5; - m_Mana = 20; + AddSpell(typeof(DispelScroll), Reg.Garlic, Reg.MandrakeRoot, Reg.SulfurousAsh); + AddSpell(typeof(EnergyBoltScroll), Reg.BlackPearl, Reg.Nightshade); + AddSpell(typeof(ExplosionScroll), Reg.Bloodmoss, Reg.MandrakeRoot); + AddSpell(typeof(InvisibilityScroll), Reg.Bloodmoss, Reg.Nightshade); + AddSpell(typeof(MarkScroll), Reg.Bloodmoss, Reg.BlackPearl, Reg.MandrakeRoot); + AddSpell(typeof(MassCurseScroll), Reg.Garlic, Reg.MandrakeRoot, Reg.Nightshade, Reg.SulfurousAsh); + AddSpell(typeof(ParalyzeFieldScroll), Reg.BlackPearl, Reg.Ginseng, Reg.SpidersSilk); + AddSpell(typeof(RevealScroll), Reg.Bloodmoss, Reg.SulfurousAsh); - AddSpell( typeof( DispelScroll ), Reg.Garlic, Reg.MandrakeRoot, Reg.SulfurousAsh ); - AddSpell( typeof( EnergyBoltScroll ), Reg.BlackPearl, Reg.Nightshade ); - AddSpell( typeof( ExplosionScroll ), Reg.Bloodmoss, Reg.MandrakeRoot ); - AddSpell( typeof( InvisibilityScroll ), Reg.Bloodmoss, Reg.Nightshade ); - AddSpell( typeof( MarkScroll ), Reg.Bloodmoss, Reg.BlackPearl, Reg.MandrakeRoot ); - AddSpell( typeof( MassCurseScroll ), Reg.Garlic, Reg.MandrakeRoot, Reg.Nightshade, Reg.SulfurousAsh ); - AddSpell( typeof( ParalyzeFieldScroll ), Reg.BlackPearl, Reg.Ginseng, Reg.SpidersSilk ); - AddSpell( typeof( RevealScroll ), Reg.Bloodmoss, Reg.SulfurousAsh ); + m_Circle = 6; + m_Mana = 40; - m_Circle = 6; - m_Mana = 40; + AddSpell(typeof(ChainLightningScroll), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SulfurousAsh); + AddSpell(typeof(EnergyFieldScroll), Reg.BlackPearl, Reg.MandrakeRoot, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(FlamestrikeScroll), Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(GateTravelScroll), Reg.BlackPearl, Reg.MandrakeRoot, Reg.SulfurousAsh); + AddSpell(typeof(ManaVampireScroll), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk); + AddSpell(typeof(MassDispelScroll), Reg.BlackPearl, Reg.Garlic, Reg.MandrakeRoot, Reg.SulfurousAsh); + AddSpell(typeof(MeteorSwarmScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SulfurousAsh, Reg.SpidersSilk); + AddSpell(typeof(PolymorphScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk); - AddSpell( typeof( ChainLightningScroll ), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SulfurousAsh ); - AddSpell( typeof( EnergyFieldScroll ), Reg.BlackPearl, Reg.MandrakeRoot, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( FlamestrikeScroll ), Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( GateTravelScroll ), Reg.BlackPearl, Reg.MandrakeRoot, Reg.SulfurousAsh ); - AddSpell( typeof( ManaVampireScroll ), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk ); - AddSpell( typeof( MassDispelScroll ), Reg.BlackPearl, Reg.Garlic, Reg.MandrakeRoot, Reg.SulfurousAsh ); - AddSpell( typeof( MeteorSwarmScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SulfurousAsh, Reg.SpidersSilk ); - AddSpell( typeof( PolymorphScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk ); + m_Circle = 7; + m_Mana = 50; - m_Circle = 7; - m_Mana = 50; + AddSpell(typeof(EarthquakeScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.Ginseng, Reg.SulfurousAsh); + AddSpell(typeof(EnergyVortexScroll), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot, Reg.Nightshade); + AddSpell(typeof(ResurrectionScroll), Reg.Bloodmoss, Reg.Garlic, Reg.Ginseng); + AddSpell(typeof(SummonAirElementalScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk); + AddSpell(typeof(SummonDaemonScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(SummonEarthElementalScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk); + AddSpell(typeof(SummonFireElementalScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk, Reg.SulfurousAsh); + AddSpell(typeof(SummonWaterElementalScroll), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk); - AddSpell( typeof( EarthquakeScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.Ginseng, Reg.SulfurousAsh ); - AddSpell( typeof( EnergyVortexScroll ), Reg.BlackPearl, Reg.Bloodmoss, Reg.MandrakeRoot, Reg.Nightshade ); - AddSpell( typeof( ResurrectionScroll ), Reg.Bloodmoss, Reg.Garlic, Reg.Ginseng ); - AddSpell( typeof( SummonAirElementalScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk ); - AddSpell( typeof( SummonDaemonScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( SummonEarthElementalScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk ); - AddSpell( typeof( SummonFireElementalScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk, Reg.SulfurousAsh ); - AddSpell( typeof( SummonWaterElementalScroll ), Reg.Bloodmoss, Reg.MandrakeRoot, Reg.SpidersSilk ); + if (Core.SE) + { + AddNecroSpell(0, 23, 39.6, typeof(AnimateDeadScroll), Reagent.GraveDust, Reagent.DaemonBlood); + AddNecroSpell(1, 13, 19.6, typeof(BloodOathScroll), Reagent.DaemonBlood); + AddNecroSpell(2, 11, 19.6, typeof(CorpseSkinScroll), Reagent.BatWing, Reagent.GraveDust); + AddNecroSpell(3, 7, 19.6, typeof(CurseWeaponScroll), Reagent.PigIron); + AddNecroSpell(4, 11, 19.6, typeof(EvilOmenScroll), Reagent.BatWing, Reagent.NoxCrystal); + AddNecroSpell(5, 11, 39.6, typeof(HorrificBeastScroll), Reagent.BatWing, Reagent.DaemonBlood); + AddNecroSpell(6, 23, 69.6, typeof(LichFormScroll), Reagent.GraveDust, Reagent.DaemonBlood, + Reagent.NoxCrystal); + AddNecroSpell(7, 17, 29.6, typeof(MindRotScroll), Reagent.BatWing, Reagent.DaemonBlood, Reagent.PigIron); + AddNecroSpell(8, 5, 19.6, typeof(PainSpikeScroll), Reagent.GraveDust, Reagent.PigIron); + AddNecroSpell(9, 17, 49.6, typeof(PoisonStrikeScroll), Reagent.NoxCrystal); + AddNecroSpell(10, 29, 64.6, typeof(StrangleScroll), Reagent.DaemonBlood, Reagent.NoxCrystal); + AddNecroSpell(11, 17, 29.6, typeof(SummonFamiliarScroll), Reagent.BatWing, Reagent.GraveDust, + Reagent.DaemonBlood); + AddNecroSpell(12, 23, 98.6, typeof(VampiricEmbraceScroll), Reagent.BatWing, Reagent.NoxCrystal, + Reagent.PigIron); + AddNecroSpell(13, 41, 79.6, typeof(VengefulSpiritScroll), Reagent.BatWing, Reagent.GraveDust, + Reagent.PigIron); + AddNecroSpell(14, 23, 59.6, typeof(WitherScroll), Reagent.GraveDust, Reagent.NoxCrystal, Reagent.PigIron); + AddNecroSpell(15, 17, 79.6, typeof(WraithFormScroll), Reagent.NoxCrystal, Reagent.PigIron); + AddNecroSpell(16, 40, 79.6, typeof(ExorcismScroll), Reagent.NoxCrystal, Reagent.GraveDust); + } - if ( Core.SE ) - { - AddNecroSpell( 0, 23, 39.6, typeof( AnimateDeadScroll ), Reagent.GraveDust, Reagent.DaemonBlood ); - AddNecroSpell( 1, 13, 19.6, typeof( BloodOathScroll ), Reagent.DaemonBlood ); - AddNecroSpell( 2, 11, 19.6, typeof( CorpseSkinScroll ), Reagent.BatWing, Reagent.GraveDust ); - AddNecroSpell( 3, 7, 19.6, typeof( CurseWeaponScroll ), Reagent.PigIron ); - AddNecroSpell( 4, 11, 19.6, typeof( EvilOmenScroll ), Reagent.BatWing, Reagent.NoxCrystal ); - AddNecroSpell( 5, 11, 39.6, typeof( HorrificBeastScroll ), Reagent.BatWing, Reagent.DaemonBlood ); - AddNecroSpell( 6, 23, 69.6, typeof( LichFormScroll ), Reagent.GraveDust, Reagent.DaemonBlood, Reagent.NoxCrystal ); - AddNecroSpell( 7, 17, 29.6, typeof( MindRotScroll ), Reagent.BatWing, Reagent.DaemonBlood, Reagent.PigIron ); - AddNecroSpell( 8, 5, 19.6, typeof( PainSpikeScroll ), Reagent.GraveDust, Reagent.PigIron ); - AddNecroSpell( 9, 17, 49.6, typeof( PoisonStrikeScroll ), Reagent.NoxCrystal ); - AddNecroSpell( 10, 29, 64.6, typeof( StrangleScroll ), Reagent.DaemonBlood, Reagent.NoxCrystal ); - AddNecroSpell( 11, 17, 29.6, typeof( SummonFamiliarScroll ), Reagent.BatWing, Reagent.GraveDust, Reagent.DaemonBlood ); - AddNecroSpell( 12, 23, 98.6, typeof( VampiricEmbraceScroll ), Reagent.BatWing, Reagent.NoxCrystal, Reagent.PigIron ); - AddNecroSpell( 13, 41, 79.6, typeof( VengefulSpiritScroll ), Reagent.BatWing, Reagent.GraveDust, Reagent.PigIron ); - AddNecroSpell( 14, 23, 59.6, typeof( WitherScroll ), Reagent.GraveDust, Reagent.NoxCrystal, Reagent.PigIron ); - AddNecroSpell( 15, 17, 79.6, typeof( WraithFormScroll ), Reagent.NoxCrystal, Reagent.PigIron ); - AddNecroSpell( 16, 40, 79.6, typeof( ExorcismScroll ), Reagent.NoxCrystal, Reagent.GraveDust ); - } + int index; - int index; + if (Core.ML) + { + index = AddCraft(typeof(EnchantedSwitch), 1044294, 1072893, 45.0, 95.0, typeof(BlankScroll), 1044377, 1, + 1044378); + AddRes(index, typeof(SpidersSilk), 1044360, 1, 1044253); + AddRes(index, typeof(BlackPearl), 1044353, 1, 1044253); + AddRes(index, typeof(SwitchItem), 1073464, 1, 1044253); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); - if ( Core.ML ) - { - index = AddCraft( typeof( EnchantedSwitch ), 1044294, 1072893, 45.0, 95.0, typeof( BlankScroll ), 1044377, 1, 1044378 ); - AddRes( index, typeof( SpidersSilk ), 1044360, 1, 1044253 ); - AddRes( index, typeof( BlackPearl ), 1044353, 1, 1044253 ); - AddRes( index, typeof( SwitchItem ), 1073464, 1, 1044253 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); + index = AddCraft(typeof(RunedPrism), 1044294, 1073465, 45.0, 95.0, typeof(BlankScroll), 1044377, 1, 1044378); + AddRes(index, typeof(SpidersSilk), 1044360, 1, 1044253); + AddRes(index, typeof(BlackPearl), 1044353, 1, 1044253); + AddRes(index, typeof(HollowPrism), 1072895, 1, 1044253); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + } - index = AddCraft( typeof( RunedPrism ), 1044294, 1073465, 45.0, 95.0, typeof( BlankScroll ), 1044377, 1, 1044378 ); - AddRes( index, typeof( SpidersSilk ), 1044360, 1, 1044253 ); - AddRes( index, typeof( BlackPearl ), 1044353, 1, 1044253 ); - AddRes( index, typeof( HollowPrism ), 1072895, 1, 1044253 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } + // Runebook + index = AddCraft(typeof(Runebook), 1044294, 1041267, 45.0, 95.0, typeof(BlankScroll), 1044377, 8, 1044378); + AddRes(index, typeof(RecallScroll), 1044445, 1, 1044253); + AddRes(index, typeof(GateTravelScroll), 1044446, 1, 1044253); - // Runebook - index = AddCraft( typeof( Runebook ), 1044294, 1041267, 45.0, 95.0, typeof( BlankScroll ), 1044377, 8, 1044378 ); - AddRes( index, typeof( RecallScroll ), 1044445, 1, 1044253 ); - AddRes( index, typeof( GateTravelScroll ), 1044446, 1, 1044253 ); + if (Core.AOS) + AddCraft(typeof(BulkOrderBook), 1044294, 1028793, 65.0, 115.0, typeof(BlankScroll), 1044377, 10, 1044378); - if ( Core.AOS ) - { - AddCraft( typeof( BulkOrders.BulkOrderBook ), 1044294, 1028793, 65.0, 115.0, typeof( BlankScroll ), 1044377, 10, 1044378 ); - } + if (Core.SE) AddCraft(typeof(Spellbook), 1044294, 1023834, 50.0, 126, typeof(BlankScroll), 1044377, 10, 1044378); - if ( Core.SE ) - { - AddCraft( typeof( Spellbook ), 1044294, 1023834, 50.0, 126, typeof( BlankScroll ), 1044377, 10, 1044378 ); - } + /* TODO + if ( Core.ML ) + { + index = AddCraft( typeof( ScrappersCompendium ), 1044294, 1072940, 75.0, 125.0, typeof( BlankScroll ), 1044377, 100, 1044378 ); + AddRes( index, typeof( DreadHornMane ), 1032682, 1, 1044253 ); + AddRes( index, typeof( Taint ), 1032679, 10, 1044253 ); + AddRes( index, typeof( Corruption ), 1032676, 10, 1044253 ); + AddRareRecipe( index, 400 ); + ForceNonExceptional( index ); + SetNeededExpansion( index, Expansion.ML ); + } + */ - /* TODO - if ( Core.ML ) - { - index = AddCraft( typeof( ScrappersCompendium ), 1044294, 1072940, 75.0, 125.0, typeof( BlankScroll ), 1044377, 100, 1044378 ); - AddRes( index, typeof( DreadHornMane ), 1032682, 1, 1044253 ); - AddRes( index, typeof( Taint ), 1032679, 10, 1044253 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1044253 ); - AddRareRecipe( index, 400 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } - */ + if (Core.SA) + { + AddCraft(typeof(MysticSpellbook), 1044294, 1031677, 50.0, 150.0, typeof(BlankScroll), 1044377, 10, 1044378); - if ( Core.SA ) - { - AddCraft( typeof( MysticSpellbook ), 1044294, 1031677, 50.0, 150.0, typeof( BlankScroll ), 1044377, 10, 1044378 ); + AddMysticismSpell(0, 4, -25.0, 25.0, typeof(NetherBoltScroll), Reagent.BlackPearl, Reagent.SulfurousAsh); + AddMysticismSpell(1, 4, -25.0, 25.0, typeof(HealingStoneScroll), Reagent.Bone, Reagent.Garlic, + Reagent.Ginseng, Reagent.SpidersSilk); + AddMysticismSpell(2, 6, -10.8, 39.2, typeof(PurgeMagicScroll), Reagent.FertileDirt, Reagent.Garlic, + Reagent.MandrakeRoot, Reagent.SulfurousAsh); + AddMysticismSpell(3, 6, -10.8, 39.2, typeof(EnchantScroll), Reagent.SpidersSilk, Reagent.MandrakeRoot, + Reagent.SulfurousAsh); + AddMysticismSpell(4, 9, 3.5, 53.5, typeof(SleepScroll), Reagent.Nightshade, Reagent.SpidersSilk, + Reagent.BlackPearl); + AddMysticismSpell(5, 9, 3.5, 53.5, typeof(EagleStrikeScroll), Reagent.Bloodmoss, Reagent.Bone, + Reagent.SpidersSilk, Reagent.MandrakeRoot); + AddMysticismSpell(6, 11, 17.8, 67.8, typeof(AnimatedWeaponScroll), Reagent.Bone, Reagent.BlackPearl, + Reagent.MandrakeRoot, Reagent.Nightshade); + AddMysticismSpell(7, 11, 17.8, 67.8, typeof(StoneFormScroll), Reagent.Bloodmoss, Reagent.FertileDirt, + Reagent.Garlic); + AddMysticismSpell(8, 14, 32.1, 82.1, typeof(SpellTriggerScroll), Reagent.DragonsBlood, Reagent.Garlic, + Reagent.MandrakeRoot, Reagent.SpidersSilk); + AddMysticismSpell(9, 14, 32.1, 82.1, typeof(MassSleepScroll), Reagent.Ginseng, Reagent.Nightshade, + Reagent.SpidersSilk); + AddMysticismSpell(10, 20, 46.4, 96.4, typeof(CleansingWindsScroll), Reagent.DragonsBlood, Reagent.Garlic, + Reagent.Ginseng, Reagent.MandrakeRoot); + AddMysticismSpell(11, 20, 46.4, 96.4, typeof(BombardScroll), Reagent.Bloodmoss, Reagent.DragonsBlood, + Reagent.Garlic, Reagent.SulfurousAsh); + AddMysticismSpell(12, 40, 60.7, 110.7, typeof(SpellPlagueScroll), Reagent.DaemonBone, Reagent.DragonsBlood, + Reagent.Nightshade, Reagent.SulfurousAsh); + AddMysticismSpell(13, 40, 60.7, 110.7, typeof(HailStormScroll), Reagent.DragonsBlood, Reagent.Bloodmoss, + Reagent.BlackPearl, Reagent.MandrakeRoot); + AddMysticismSpell(14, 50, 75.0, 125.0, typeof(NetherCycloneScroll), Reagent.MandrakeRoot, Reagent.Nightshade, + Reagent.SulfurousAsh, Reagent.Bloodmoss); + AddMysticismSpell(15, 50, 75.0, 125.0, typeof(RisingColossusScroll), Reagent.DaemonBone, + Reagent.DragonsBlood, Reagent.FertileDirt, Reagent.Nightshade); + } - AddMysticismSpell( 0, 4, -25.0, 25.0, typeof( NetherBoltScroll ), Reagent.BlackPearl, Reagent.SulfurousAsh ); - AddMysticismSpell( 1, 4, -25.0, 25.0, typeof( HealingStoneScroll ), Reagent.Bone, Reagent.Garlic, Reagent.Ginseng, Reagent.SpidersSilk ); - AddMysticismSpell( 2, 6, -10.8, 39.2, typeof( PurgeMagicScroll ), Reagent.FertileDirt, Reagent.Garlic, Reagent.MandrakeRoot, Reagent.SulfurousAsh ); - AddMysticismSpell( 3, 6, -10.8, 39.2, typeof( EnchantScroll ), Reagent.SpidersSilk, Reagent.MandrakeRoot, Reagent.SulfurousAsh ); - AddMysticismSpell( 4, 9, 3.5, 53.5, typeof( SleepScroll ), Reagent.Nightshade, Reagent.SpidersSilk, Reagent.BlackPearl ); - AddMysticismSpell( 5, 9, 3.5, 53.5, typeof( EagleStrikeScroll ), Reagent.Bloodmoss, Reagent.Bone, Reagent.SpidersSilk, Reagent.MandrakeRoot ); - AddMysticismSpell( 6, 11, 17.8, 67.8, typeof( AnimatedWeaponScroll ), Reagent.Bone, Reagent.BlackPearl, Reagent.MandrakeRoot, Reagent.Nightshade ); - AddMysticismSpell( 7, 11, 17.8, 67.8, typeof( StoneFormScroll ), Reagent.Bloodmoss, Reagent.FertileDirt, Reagent.Garlic ); - AddMysticismSpell( 8, 14, 32.1, 82.1, typeof( SpellTriggerScroll ), Reagent.DragonsBlood, Reagent.Garlic, Reagent.MandrakeRoot, Reagent.SpidersSilk ); - AddMysticismSpell( 9, 14, 32.1, 82.1, typeof( MassSleepScroll ), Reagent.Ginseng, Reagent.Nightshade, Reagent.SpidersSilk ); - AddMysticismSpell( 10, 20, 46.4, 96.4, typeof( CleansingWindsScroll ), Reagent.DragonsBlood, Reagent.Garlic, Reagent.Ginseng, Reagent.MandrakeRoot ); - AddMysticismSpell( 11, 20, 46.4, 96.4, typeof( BombardScroll ), Reagent.Bloodmoss, Reagent.DragonsBlood, Reagent.Garlic, Reagent.SulfurousAsh ); - AddMysticismSpell( 12, 40, 60.7, 110.7, typeof( SpellPlagueScroll ), Reagent.DaemonBone, Reagent.DragonsBlood, Reagent.Nightshade, Reagent.SulfurousAsh ); - AddMysticismSpell( 13, 40, 60.7, 110.7, typeof( HailStormScroll ), Reagent.DragonsBlood, Reagent.Bloodmoss, Reagent.BlackPearl, Reagent.MandrakeRoot ); - AddMysticismSpell( 14, 50, 75.0, 125.0, typeof( NetherCycloneScroll ), Reagent.MandrakeRoot, Reagent.Nightshade, Reagent.SulfurousAsh, Reagent.Bloodmoss ); - AddMysticismSpell( 15, 50, 75.0, 125.0, typeof( RisingColossusScroll ), Reagent.DaemonBone, Reagent.DragonsBlood, Reagent.FertileDirt, Reagent.Nightshade ); - } + MarkOption = true; + } - MarkOption = true; - } - } -} + private enum Reg + { + BlackPearl, + Bloodmoss, + Garlic, + Ginseng, + MandrakeRoot, + Nightshade, + SulfurousAsh, + SpidersSilk + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefMasonry.cs b/Scripts/Engines/Craft/DefMasonry.cs index 6b1dda543..44d9d83e4 100644 --- a/Scripts/Engines/Craft/DefMasonry.cs +++ b/Scripts/Engines/Craft/DefMasonry.cs @@ -4,137 +4,139 @@ using Server.Mobiles; namespace Server.Engines.Craft { - public class DefMasonry : CraftSystem - { - public override SkillName MainSkill => SkillName.Carpentry; + public class DefMasonry : CraftSystem + { + private static CraftSystem m_CraftSystem; - public override int GumpTitleNumber => 1044500; + private DefMasonry() : base(1, 1, 1.25) // base( 1, 2, 1.7 ) + { + } - private static CraftSystem m_CraftSystem; + public override SkillName MainSkill => SkillName.Carpentry; - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefMasonry(); + public override int GumpTitleNumber => 1044500; - return m_CraftSystem; - } - } + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefMasonry(); - public override double GetChanceAtMin( CraftItem item ) - { - return 0.0; // 0% - } + return m_CraftSystem; + } + } - private DefMasonry() : base( 1, 1, 1.25 )// base( 1, 2, 1.7 ) - { - } + public override double GetChanceAtMin(CraftItem item) + { + return 0.0; // 0% + } - public override bool RetainsColorFrom( CraftItem item, Type type ) - { - return true; - } + public override bool RetainsColorFrom(CraftItem item, Type type) + { + return true; + } - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckTool( tool, from ) ) - return 1048146; // If you have a tool equipped, you must use that tool. - if ( !(from is PlayerMobile mobile && mobile.Masonry && mobile.Skills[SkillName.Carpentry].Base >= 100.0) ) - return 1044633; // You havent learned stonecraft. - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckTool(tool, from)) + return 1048146; // If you have a tool equipped, you must use that tool. + if (!(from is PlayerMobile mobile && mobile.Masonry && mobile.Skills[SkillName.Carpentry].Base >= 100.0)) + return 1044633; // You havent learned stonecraft. + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. - return 0; - } + return 0; + } - public override void PlayCraftEffect( Mobile from ) - { - // no effects - //if ( from.Body.Type == BodyType.Human && !from.Mounted ) - // from.Animate( 9, 5, 1, true, false, 0 ); - //new InternalTimer( from ).Start(); - } + public override void PlayCraftEffect(Mobile from) + { + // no effects + //if ( from.Body.Type == BodyType.Human && !from.Mounted ) + // from.Animate( 9, 5, 1, true, false, 0 ); + //new InternalTimer( from ).Start(); + } - // Delay to synchronize the sound with the hit on the anvil - private class InternalTimer : Timer - { - private Mobile m_From; + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool - public InternalTimer( Mobile from ) : base( TimeSpan.FromSeconds( 0.7 ) ) - { - m_From = from; - } + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } - protected override void OnTick() - { - m_From.PlaySound( 0x23D ); - } - } + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool + public override void InitCraftList() + { + // Decorations + AddCraft(typeof(Vase), 1044501, 1022888, 52.5, 102.5, typeof(Granite), 1044514, 1, 1044513); + AddCraft(typeof(LargeVase), 1044501, 1022887, 52.5, 102.5, typeof(Granite), 1044514, 3, 1044513); - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } + if (Core.SE) + { + int index = AddCraft(typeof(SmallUrn), 1044501, 1029244, 82.0, 132.0, typeof(Granite), 1044514, 3, 1044513); + SetNeededExpansion(index, Expansion.SE); - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } + index = AddCraft(typeof(SmallTowerSculpture), 1044501, 1029242, 82.0, 132.0, typeof(Granite), 1044514, 3, + 1044513); + SetNeededExpansion(index, Expansion.SE); + } - public override void InitCraftList() - { - // Decorations - AddCraft( typeof( Vase ), 1044501, 1022888, 52.5, 102.5, typeof( Granite ), 1044514, 1, 1044513 ); - AddCraft( typeof( LargeVase ), 1044501, 1022887, 52.5, 102.5, typeof( Granite ), 1044514, 3, 1044513 ); + // Furniture + AddCraft(typeof(StoneChair), 1044502, 1024635, 55.0, 105.0, typeof(Granite), 1044514, 4, 1044513); + AddCraft(typeof(MediumStoneTableEastDeed), 1044502, 1044508, 65.0, 115.0, typeof(Granite), 1044514, 6, 1044513); + AddCraft(typeof(MediumStoneTableSouthDeed), 1044502, 1044509, 65.0, 115.0, typeof(Granite), 1044514, 6, 1044513); + AddCraft(typeof(LargeStoneTableEastDeed), 1044502, 1044511, 75.0, 125.0, typeof(Granite), 1044514, 9, 1044513); + AddCraft(typeof(LargeStoneTableSouthDeed), 1044502, 1044512, 75.0, 125.0, typeof(Granite), 1044514, 9, 1044513); - if ( Core.SE ) - { - int index = AddCraft( typeof( SmallUrn ), 1044501, 1029244, 82.0, 132.0, typeof( Granite ), 1044514, 3, 1044513 ); - SetNeededExpansion( index, Expansion.SE ); + // Statues + AddCraft(typeof(StatueSouth), 1044503, 1044505, 60.0, 120.0, typeof(Granite), 1044514, 3, 1044513); + AddCraft(typeof(StatueNorth), 1044503, 1044506, 60.0, 120.0, typeof(Granite), 1044514, 3, 1044513); + AddCraft(typeof(StatueEast), 1044503, 1044507, 60.0, 120.0, typeof(Granite), 1044514, 3, 1044513); + AddCraft(typeof(StatuePegasus), 1044503, 1044510, 70.0, 130.0, typeof(Granite), 1044514, 4, 1044513); - index = AddCraft( typeof( SmallTowerSculpture ), 1044501, 1029242, 82.0, 132.0, typeof( Granite ), 1044514, 3, 1044513 ); - SetNeededExpansion( index, Expansion.SE ); - } + SetSubRes(typeof(Granite), 1044525); - // Furniture - AddCraft( typeof( StoneChair ), 1044502, 1024635, 55.0, 105.0, typeof( Granite ), 1044514, 4, 1044513 ); - AddCraft( typeof( MediumStoneTableEastDeed ), 1044502, 1044508, 65.0, 115.0, typeof( Granite ), 1044514, 6, 1044513 ); - AddCraft( typeof( MediumStoneTableSouthDeed ), 1044502, 1044509, 65.0, 115.0, typeof( Granite ), 1044514, 6, 1044513 ); - AddCraft( typeof( LargeStoneTableEastDeed ), 1044502, 1044511, 75.0, 125.0, typeof( Granite ), 1044514, 9, 1044513 ); - AddCraft( typeof( LargeStoneTableSouthDeed ), 1044502, 1044512, 75.0, 125.0, typeof( Granite ), 1044514, 9, 1044513 ); + AddSubRes(typeof(Granite), 1044525, 00.0, 1044514, 1044526); + AddSubRes(typeof(DullCopperGranite), 1044023, 65.0, 1044514, 1044527); + AddSubRes(typeof(ShadowIronGranite), 1044024, 70.0, 1044514, 1044527); + AddSubRes(typeof(CopperGranite), 1044025, 75.0, 1044514, 1044527); + AddSubRes(typeof(BronzeGranite), 1044026, 80.0, 1044514, 1044527); + AddSubRes(typeof(GoldGranite), 1044027, 85.0, 1044514, 1044527); + AddSubRes(typeof(AgapiteGranite), 1044028, 90.0, 1044514, 1044527); + AddSubRes(typeof(VeriteGranite), 1044029, 95.0, 1044514, 1044527); + AddSubRes(typeof(ValoriteGranite), 1044030, 99.0, 1044514, 1044527); + } - // Statues - AddCraft( typeof( StatueSouth ), 1044503, 1044505, 60.0, 120.0, typeof( Granite ), 1044514, 3, 1044513 ); - AddCraft( typeof( StatueNorth ), 1044503, 1044506, 60.0, 120.0, typeof( Granite ), 1044514, 3, 1044513 ); - AddCraft( typeof( StatueEast ), 1044503, 1044507, 60.0, 120.0, typeof( Granite ), 1044514, 3, 1044513 ); - AddCraft( typeof( StatuePegasus ), 1044503, 1044510, 70.0, 130.0, typeof( Granite ), 1044514, 4, 1044513 ); + // Delay to synchronize the sound with the hit on the anvil + private class InternalTimer : Timer + { + private Mobile m_From; - SetSubRes( typeof( Granite ), 1044525 ); + public InternalTimer(Mobile from) : base(TimeSpan.FromSeconds(0.7)) + { + m_From = from; + } - AddSubRes( typeof( Granite ), 1044525, 00.0, 1044514, 1044526 ); - AddSubRes( typeof( DullCopperGranite ), 1044023, 65.0, 1044514, 1044527 ); - AddSubRes( typeof( ShadowIronGranite ), 1044024, 70.0, 1044514, 1044527 ); - AddSubRes( typeof( CopperGranite ), 1044025, 75.0, 1044514, 1044527 ); - AddSubRes( typeof( BronzeGranite ), 1044026, 80.0, 1044514, 1044527 ); - AddSubRes( typeof( GoldGranite ), 1044027, 85.0, 1044514, 1044527 ); - AddSubRes( typeof( AgapiteGranite ), 1044028, 90.0, 1044514, 1044527 ); - AddSubRes( typeof( VeriteGranite ), 1044029, 95.0, 1044514, 1044527 ); - AddSubRes( typeof( ValoriteGranite ), 1044030, 99.0, 1044514, 1044527 ); - } - } -} + protected override void OnTick() + { + m_From.PlaySound(0x23D); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefTailoring.cs b/Scripts/Engines/Craft/DefTailoring.cs index 91e7ae955..86b335a8a 100644 --- a/Scripts/Engines/Craft/DefTailoring.cs +++ b/Scripts/Engines/Craft/DefTailoring.cs @@ -3,390 +3,428 @@ using Server.Items; namespace Server.Engines.Craft { - public class DefTailoring : CraftSystem - { - public override SkillName MainSkill => SkillName.Tailoring; - - public override int GumpTitleNumber => 1044005; - - private static CraftSystem m_CraftSystem; - - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefTailoring(); - - return m_CraftSystem; - } - } - - public override CraftECA ECA => CraftECA.ChanceMinusSixtyToFourtyFive; - - public override double GetChanceAtMin( CraftItem item ) - { - return 0.5; // 50% - } - - private DefTailoring() : base( 1, 1, 1.25 )// base( 1, 1, 4.5 ) - { - } - - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. - - return 0; - } - - private static Type[] m_TailorColorables = { - typeof( GozaMatEastDeed ), typeof( GozaMatSouthDeed ), - typeof( SquareGozaMatEastDeed ), typeof( SquareGozaMatSouthDeed ), - typeof( BrocadeGozaMatEastDeed ), typeof( BrocadeGozaMatSouthDeed ), - typeof( BrocadeSquareGozaMatEastDeed ), typeof( BrocadeSquareGozaMatSouthDeed ) - }; - - public override bool RetainsColorFrom( CraftItem item, Type type ) - { - if ( type != typeof( Cloth ) && type != typeof( UncutCloth ) ) - return false; - - type = item.ItemType; - - bool contains = false; - - for ( int i = 0; !contains && i < m_TailorColorables.Length; ++i ) - contains = ( m_TailorColorables[i] == type ); - - return contains; - } - - public override void PlayCraftEffect( Mobile from ) - { - from.PlaySound( 0x248 ); - } - - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool - - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } - - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } - - public override void InitCraftList() - { - int index = -1; - - #region Hats - AddCraft( typeof( SkullCap ), 1011375, 1025444, 0.0, 25.0, typeof( Cloth ), 1044286, 2, 1044287 ); - AddCraft( typeof( Bandana ), 1011375, 1025440, 0.0, 25.0, typeof( Cloth ), 1044286, 2, 1044287 ); - AddCraft( typeof( FloppyHat ), 1011375, 1025907, 6.2, 31.2, typeof( Cloth ), 1044286, 11, 1044287 ); - AddCraft( typeof( Cap ), 1011375, 1025909, 6.2, 31.2, typeof( Cloth ), 1044286, 11, 1044287 ); - AddCraft( typeof( WideBrimHat ), 1011375, 1025908, 6.2, 31.2, typeof( Cloth ), 1044286, 12, 1044287 ); - AddCraft( typeof( StrawHat ), 1011375, 1025911, 6.2, 31.2, typeof( Cloth ), 1044286, 10, 1044287 ); - AddCraft( typeof( TallStrawHat ), 1011375, 1025910, 6.7, 31.7, typeof( Cloth ), 1044286, 13, 1044287 ); - AddCraft( typeof( WizardsHat ), 1011375, 1025912, 7.2, 32.2, typeof( Cloth ), 1044286, 15, 1044287 ); - AddCraft( typeof( Bonnet ), 1011375, 1025913, 6.2, 31.2, typeof( Cloth ), 1044286, 11, 1044287 ); - AddCraft( typeof( FeatheredHat ), 1011375, 1025914, 6.2, 31.2, typeof( Cloth ), 1044286, 12, 1044287 ); - AddCraft( typeof( TricorneHat ), 1011375, 1025915, 6.2, 31.2, typeof( Cloth ), 1044286, 12, 1044287 ); - AddCraft( typeof( JesterHat ), 1011375, 1025916, 7.2, 32.2, typeof( Cloth ), 1044286, 15, 1044287 ); - - if ( Core.AOS ) - AddCraft( typeof( FlowerGarland ), 1011375, 1028965, 10.0, 35.0, typeof( Cloth ), 1044286, 5, 1044287 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( ClothNinjaHood ), 1011375, 1030202, 80.0, 105.0, typeof( Cloth ), 1044286, 13, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( Kasa ), 1011375, 1030211, 60.0, 85.0, typeof( Cloth ), 1044286, 12, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - #endregion - - #region Shirts - AddCraft( typeof( Doublet ), 1015269, 1028059, 0, 25.0, typeof( Cloth ), 1044286, 8, 1044287 ); - AddCraft( typeof( Shirt ), 1015269, 1025399, 20.7, 45.7, typeof( Cloth ), 1044286, 8, 1044287 ); - AddCraft( typeof( FancyShirt ), 1015269, 1027933, 24.8, 49.8, typeof( Cloth ), 1044286, 8, 1044287 ); - AddCraft( typeof( Tunic ), 1015269, 1028097, 00.0, 25.0, typeof( Cloth ), 1044286, 12, 1044287 ); - AddCraft( typeof( Surcoat ), 1015269, 1028189, 8.2, 33.2, typeof( Cloth ), 1044286, 14, 1044287 ); - AddCraft( typeof( PlainDress ), 1015269, 1027937, 12.4, 37.4, typeof( Cloth ), 1044286, 10, 1044287 ); - AddCraft( typeof( FancyDress ), 1015269, 1027935, 33.1, 58.1, typeof( Cloth ), 1044286, 12, 1044287 ); - AddCraft( typeof( Cloak ), 1015269, 1025397, 41.4, 66.4, typeof( Cloth ), 1044286, 14, 1044287 ); - AddCraft( typeof( Robe ), 1015269, 1027939, 53.9, 78.9, typeof( Cloth ), 1044286, 16, 1044287 ); - AddCraft( typeof( JesterSuit ), 1015269, 1028095, 8.2, 33.2, typeof( Cloth ), 1044286, 24, 1044287 ); - - if ( Core.AOS ) - { - AddCraft( typeof( FurCape ), 1015269, 1028969, 35.0, 60.0, typeof( Cloth ), 1044286, 13, 1044287 ); - AddCraft( typeof( GildedDress ), 1015269, 1028973, 37.5, 62.5, typeof( Cloth ), 1044286, 16, 1044287 ); - AddCraft( typeof( FormalShirt ), 1015269, 1028975, 26.0, 51.0, typeof( Cloth ), 1044286, 16, 1044287 ); - } - - if ( Core.SE ) - { - index = AddCraft( typeof( ClothNinjaJacket ), 1015269, 1030207, 75.0, 100.0, typeof( Cloth ), 1044286, 12, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( Kamishimo ), 1015269, 1030212, 75.0, 100.0, typeof( Cloth ), 1044286, 15, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( HakamaShita ), 1015269, 1030215, 40.0, 65.0, typeof( Cloth ), 1044286, 14, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( MaleKimono ), 1015269, 1030189, 50.0, 75.0, typeof( Cloth ), 1044286, 16, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( FemaleKimono ), 1015269, 1030190, 50.0, 75.0, typeof( Cloth ), 1044286, 16, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( JinBaori ), 1015269, 1030220, 30.0, 55.0, typeof( Cloth ), 1044286, 12, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - #endregion - - #region Pants - AddCraft( typeof( ShortPants ), 1015279, 1025422, 24.8, 49.8, typeof( Cloth ), 1044286, 6, 1044287 ); - AddCraft( typeof( LongPants ), 1015279, 1025433, 24.8, 49.8, typeof( Cloth ), 1044286, 8, 1044287 ); - AddCraft( typeof( Kilt ), 1015279, 1025431, 20.7, 45.7, typeof( Cloth ), 1044286, 8, 1044287 ); - AddCraft( typeof( Skirt ), 1015279, 1025398, 29.0, 54.0, typeof( Cloth ), 1044286, 10, 1044287 ); - - if ( Core.AOS ) - AddCraft( typeof( FurSarong ), 1015279, 1028971, 35.0, 60.0, typeof( Cloth ), 1044286, 12, 1044287 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( Hakama ), 1015279, 1030213, 50.0, 75.0, typeof( Cloth ), 1044286, 16, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( TattsukeHakama ), 1015279, 1030214, 50.0, 75.0, typeof( Cloth ), 1044286, 16, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - #endregion - - #region Misc - AddCraft( typeof( BodySash ), 1015283, 1025441, 4.1, 29.1, typeof( Cloth ), 1044286, 4, 1044287 ); - AddCraft( typeof( HalfApron ), 1015283, 1025435, 20.7, 45.7, typeof( Cloth ), 1044286, 6, 1044287 ); - AddCraft( typeof( FullApron ), 1015283, 1025437, 29.0, 54.0, typeof( Cloth ), 1044286, 10, 1044287 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( Obi ), 1015283, 1030219, 20.0, 45.0, typeof( Cloth ), 1044286, 6, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - if ( Core.ML ) - { - index = AddCraft( typeof( ElvenQuiver ), 1015283, 1032657, 65.0, 115.0, typeof( Leather ), 1044462, 28, 1044463 ); - AddRecipe( index, 501 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( QuiverOfFire ), 1015283, 1073109, 65.0, 115.0, typeof( Leather ), 1044462, 28, 1044463 ); - AddRes( index, typeof( FireRuby ), 1032695, 15, 1042081 ); - AddRecipe( index, 502 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( QuiverOfIce ), 1015283, 1073110, 65.0, 115.0, typeof( Leather ), 1044462, 28, 1044463 ); - AddRes( index, typeof( WhitePearl ), 1032694, 15, 1042081 ); - AddRecipe( index, 503 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( QuiverOfBlight ), 1015283, 1073111, 65.0, 115.0, typeof( Leather ), 1044462, 28, 1044463 ); - AddRes( index, typeof( Blight ), 1032675, 10, 1042081 ); - AddRecipe( index, 504 ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( QuiverOfLightning ), 1015283, 1073112, 65.0, 115.0, typeof( Leather ), 1044462, 28, 1044463 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1042081 ); - AddRecipe( index, 505 ); - SetNeededExpansion( index, Expansion.ML ); - } - - AddCraft( typeof( OilCloth ), 1015283, 1041498, 74.6, 99.6, typeof( Cloth ), 1044286, 1, 1044287 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( GozaMatEastDeed ), 1015283, 1030404, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( GozaMatSouthDeed ), 1015283, 1030405, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( SquareGozaMatEastDeed ), 1015283, 1030407, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( SquareGozaMatSouthDeed ), 1015283, 1030406, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( BrocadeGozaMatEastDeed ), 1015283, 1030408, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( BrocadeGozaMatSouthDeed ), 1015283, 1030409, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( BrocadeSquareGozaMatEastDeed ), 1015283, 1030411, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( BrocadeSquareGozaMatSouthDeed ), 1015283, 1030410, 55.0, 80.0, typeof( Cloth ), 1044286, 25, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - #endregion - - #region Footwear - if ( Core.AOS ) - AddCraft( typeof( FurBoots ), 1015288, 1028967, 50.0, 75.0, typeof( Cloth ), 1044286, 12, 1044287 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( NinjaTabi ), 1015288, 1030210, 70.0, 95.0, typeof( Cloth ), 1044286, 10, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( SamuraiTabi ), 1015288, 1030209, 20.0, 45.0, typeof( Cloth ), 1044286, 6, 1044287 ); - SetNeededExpansion( index, Expansion.SE ); - } - - AddCraft( typeof( Sandals ), 1015288, 1025901, 12.4, 37.4, typeof( Leather ), 1044462, 4, 1044463 ); - AddCraft( typeof( Shoes ), 1015288, 1025904, 16.5, 41.5, typeof( Leather ), 1044462, 6, 1044463 ); - AddCraft( typeof( Boots ), 1015288, 1025899, 33.1, 58.1, typeof( Leather ), 1044462, 8, 1044463 ); - AddCraft( typeof( ThighBoots ), 1015288, 1025906, 41.4, 66.4, typeof( Leather ), 1044462, 10, 1044463 ); - #endregion - - #region Leather Armor - - if ( Core.ML ) - { - index = AddCraft( typeof( SpellWovenBritches ), 1015293, 1072929, 92.5, 117.5, typeof( Leather ), 1044462, 15, 1044463 ); - AddRes( index, typeof( EyeOfTheTravesty ), 1032685, 1, 1044253 ); - AddRes( index, typeof( Putrefication ), 1032678, 10, 1044253 ); - AddRes( index, typeof( Scourge ), 1032677, 10, 1044253 ); - AddRareRecipe( index, 506 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( SongWovenMantle ), 1015293, 1072931, 92.5, 117.5, typeof( Leather ), 1044462, 15, 1044463 ); - AddRes( index, typeof( EyeOfTheTravesty ), 1032685, 1, 1044253 ); - AddRes( index, typeof( Blight ), 1032675, 10, 1044253 ); - AddRes( index, typeof( Muculent ), 1032680, 10, 1044253 ); - AddRareRecipe( index, 507 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( StitchersMittens ), 1015293, 1072932, 92.5, 117.5, typeof( Leather ), 1044462, 15, 1044463 ); - AddRes( index, typeof( CapturedEssence ), 1032686, 1, 1044253 ); - AddRes( index, typeof( Corruption ), 1032676, 10, 1044253 ); - AddRes( index, typeof( Taint ), 1032679, 10, 1044253 ); - AddRareRecipe( index, 508 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } - - AddCraft( typeof( LeatherGorget ), 1015293, 1025063, 53.9, 78.9, typeof( Leather ), 1044462, 4, 1044463 ); - AddCraft( typeof( LeatherCap ), 1015293, 1027609, 6.2, 31.2, typeof( Leather ), 1044462, 2, 1044463 ); - AddCraft( typeof( LeatherGloves ), 1015293, 1025062, 51.8, 76.8, typeof( Leather ), 1044462, 3, 1044463 ); - AddCraft( typeof( LeatherArms ), 1015293, 1025061, 53.9, 78.9, typeof( Leather ), 1044462, 4, 1044463 ); - AddCraft( typeof( LeatherLegs ), 1015293, 1025067, 66.3, 91.3, typeof( Leather ), 1044462, 10, 1044463 ); - AddCraft( typeof( LeatherChest ), 1015293, 1025068, 70.5, 95.5, typeof( Leather ), 1044462, 12, 1044463 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( LeatherJingasa ), 1015293, 1030177, 45.0, 70.0, typeof( Leather ), 1044462, 4, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherMempo ), 1015293, 1030181, 80.0, 105.0, typeof( Leather ), 1044462, 8, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherDo ), 1015293, 1030182, 75.0, 100.0, typeof( Leather ), 1044462, 12, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherHiroSode ), 1015293, 1030185, 55.0, 80.0, typeof( Leather ), 1044462, 5, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherSuneate ), 1015293, 1030193, 68.0, 93.0, typeof( Leather ), 1044462, 12, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherHaidate ), 1015293, 1030197, 68.0, 93.0, typeof( Leather ), 1044462, 12, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherNinjaPants ), 1015293, 1030204, 80.0, 105.0, typeof( Leather ), 1044462, 13, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherNinjaJacket ), 1015293, 1030206, 85.0, 110.0, typeof( Leather ), 1044462, 13, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherNinjaBelt ), 1015293, 1030203, 50.0, 75.0, typeof( Leather ), 1044462, 5, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherNinjaMitts ), 1015293, 1030205, 65.0, 90.0, typeof( Leather ), 1044462, 12, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( LeatherNinjaHood ), 1015293, 1030201, 90.0, 115.0, typeof( Leather ), 1044462, 14, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - } - - #endregion - - #region Studded Armor - AddCraft( typeof( StuddedGorget ), 1015300, 1025078, 78.8, 103.8, typeof( Leather ), 1044462, 6, 1044463 ); - AddCraft( typeof( StuddedGloves ), 1015300, 1025077, 82.9, 107.9, typeof( Leather ), 1044462, 8, 1044463 ); - AddCraft( typeof( StuddedArms ), 1015300, 1025076, 87.1, 112.1, typeof( Leather ), 1044462, 10, 1044463 ); - AddCraft( typeof( StuddedLegs ), 1015300, 1025082, 91.2, 116.2, typeof( Leather ), 1044462, 12, 1044463 ); - AddCraft( typeof( StuddedChest ), 1015300, 1025083, 94.0, 119.0, typeof( Leather ), 1044462, 14, 1044463 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( StuddedMempo ), 1015300, 1030216, 80.0, 105.0, typeof( Leather ), 1044462, 8, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( StuddedDo ), 1015300, 1030183, 95.0, 120.0, typeof( Leather ), 1044462, 14, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( StuddedHiroSode ), 1015300, 1030186, 85.0, 110.0, typeof( Leather ), 1044462, 8, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( StuddedSuneate ), 1015300, 1030194, 92.0, 117.0, typeof( Leather ), 1044462, 14, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - index = AddCraft( typeof( StuddedHaidate ), 1015300, 1030198, 92.0, 117.0, typeof( Leather ), 1044462, 14, 1044463 ); - SetNeededExpansion( index, Expansion.SE ); - } - - #endregion - - #region Female Armor - AddCraft( typeof( LeatherShorts ), 1015306, 1027168, 62.2, 87.2, typeof( Leather ), 1044462, 8, 1044463 ); - AddCraft( typeof( LeatherSkirt ), 1015306, 1027176, 58.0, 83.0, typeof( Leather ), 1044462, 6, 1044463 ); - AddCraft( typeof( LeatherBustierArms ), 1015306, 1027178, 58.0, 83.0, typeof( Leather ), 1044462, 6, 1044463 ); - AddCraft( typeof( StuddedBustierArms ), 1015306, 1027180, 82.9, 107.9, typeof( Leather ), 1044462, 8, 1044463 ); - AddCraft( typeof( FemaleLeatherChest ), 1015306, 1027174, 62.2, 87.2, typeof( Leather ), 1044462, 8, 1044463 ); - AddCraft( typeof( FemaleStuddedChest ), 1015306, 1027170, 87.1, 112.1, typeof( Leather ), 1044462, 10, 1044463 ); - #endregion - - #region Bone Armor - index = AddCraft( typeof( BoneHelm ), 1049149, 1025206, 85.0, 110.0, typeof( Leather ), 1044462, 4, 1044463 ); - AddRes( index, typeof( Bone ), 1049064, 2, 1049063 ); - - index = AddCraft( typeof( BoneGloves ), 1049149, 1025205, 89.0, 114.0, typeof( Leather ), 1044462, 6, 1044463 ); - AddRes( index, typeof( Bone ), 1049064, 2, 1049063 ); - - index = AddCraft( typeof( BoneArms ), 1049149, 1025203, 92.0, 117.0, typeof( Leather ), 1044462, 8, 1044463 ); - AddRes( index, typeof( Bone ), 1049064, 4, 1049063 ); - - index = AddCraft( typeof( BoneLegs ), 1049149, 1025202, 95.0, 120.0, typeof( Leather ), 1044462, 10, 1044463 ); - AddRes( index, typeof( Bone ), 1049064, 6, 1049063 ); - - index = AddCraft( typeof( BoneChest ), 1049149, 1025199, 96.0, 121.0, typeof( Leather ), 1044462, 12, 1044463 ); - AddRes( index, typeof( Bone ), 1049064, 10, 1049063 ); - - index = AddCraft(typeof(OrcHelm), 1049149, 1027947, 90.0, 115.0, typeof(Leather), 1044462, 6, 1044463); - AddRes(index, typeof(Bone), 1049064, 4, 1049063); - #endregion - - // Set the overridable material - SetSubRes( typeof( Leather ), 1049150 ); - - // Add every material you want the player to be able to choose from - // This will override the overridable material - AddSubRes( typeof( Leather ), 1049150, 00.0, 1044462, 1049311 ); - AddSubRes( typeof( SpinedLeather ), 1049151, 65.0, 1044462, 1049311 ); - AddSubRes( typeof( HornedLeather ), 1049152, 80.0, 1044462, 1049311 ); - AddSubRes( typeof( BarbedLeather ), 1049153, 99.0, 1044462, 1049311 ); - - MarkOption = true; - Repair = Core.AOS; - CanEnhance = Core.AOS; - } - } -} + public class DefTailoring : CraftSystem + { + private static CraftSystem m_CraftSystem; + + private static Type[] m_TailorColorables = + { + typeof(GozaMatEastDeed), typeof(GozaMatSouthDeed), + typeof(SquareGozaMatEastDeed), typeof(SquareGozaMatSouthDeed), + typeof(BrocadeGozaMatEastDeed), typeof(BrocadeGozaMatSouthDeed), + typeof(BrocadeSquareGozaMatEastDeed), typeof(BrocadeSquareGozaMatSouthDeed) + }; + + private DefTailoring() : base(1, 1, 1.25) // base( 1, 1, 4.5 ) + { + } + + public override SkillName MainSkill => SkillName.Tailoring; + + public override int GumpTitleNumber => 1044005; + + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefTailoring(); + + return m_CraftSystem; + } + } + + public override CraftECA ECA => CraftECA.ChanceMinusSixtyToFourtyFive; + + public override double GetChanceAtMin(CraftItem item) + { + return 0.5; // 50% + } + + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. + + return 0; + } + + public override bool RetainsColorFrom(CraftItem item, Type type) + { + if (type != typeof(Cloth) && type != typeof(UncutCloth)) + return false; + + type = item.ItemType; + + bool contains = false; + + for (int i = 0; !contains && i < m_TailorColorables.Length; ++i) + contains = m_TailorColorables[i] == type; + + return contains; + } + + public override void PlayCraftEffect(Mobile from) + { + from.PlaySound(0x248); + } + + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool + + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } + + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } + + public override void InitCraftList() + { + int index = -1; + + #region Hats + + AddCraft(typeof(SkullCap), 1011375, 1025444, 0.0, 25.0, typeof(Cloth), 1044286, 2, 1044287); + AddCraft(typeof(Bandana), 1011375, 1025440, 0.0, 25.0, typeof(Cloth), 1044286, 2, 1044287); + AddCraft(typeof(FloppyHat), 1011375, 1025907, 6.2, 31.2, typeof(Cloth), 1044286, 11, 1044287); + AddCraft(typeof(Cap), 1011375, 1025909, 6.2, 31.2, typeof(Cloth), 1044286, 11, 1044287); + AddCraft(typeof(WideBrimHat), 1011375, 1025908, 6.2, 31.2, typeof(Cloth), 1044286, 12, 1044287); + AddCraft(typeof(StrawHat), 1011375, 1025911, 6.2, 31.2, typeof(Cloth), 1044286, 10, 1044287); + AddCraft(typeof(TallStrawHat), 1011375, 1025910, 6.7, 31.7, typeof(Cloth), 1044286, 13, 1044287); + AddCraft(typeof(WizardsHat), 1011375, 1025912, 7.2, 32.2, typeof(Cloth), 1044286, 15, 1044287); + AddCraft(typeof(Bonnet), 1011375, 1025913, 6.2, 31.2, typeof(Cloth), 1044286, 11, 1044287); + AddCraft(typeof(FeatheredHat), 1011375, 1025914, 6.2, 31.2, typeof(Cloth), 1044286, 12, 1044287); + AddCraft(typeof(TricorneHat), 1011375, 1025915, 6.2, 31.2, typeof(Cloth), 1044286, 12, 1044287); + AddCraft(typeof(JesterHat), 1011375, 1025916, 7.2, 32.2, typeof(Cloth), 1044286, 15, 1044287); + + if (Core.AOS) + AddCraft(typeof(FlowerGarland), 1011375, 1028965, 10.0, 35.0, typeof(Cloth), 1044286, 5, 1044287); + + if (Core.SE) + { + index = AddCraft(typeof(ClothNinjaHood), 1011375, 1030202, 80.0, 105.0, typeof(Cloth), 1044286, 13, 1044287); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(Kasa), 1011375, 1030211, 60.0, 85.0, typeof(Cloth), 1044286, 12, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Shirts + + AddCraft(typeof(Doublet), 1015269, 1028059, 0, 25.0, typeof(Cloth), 1044286, 8, 1044287); + AddCraft(typeof(Shirt), 1015269, 1025399, 20.7, 45.7, typeof(Cloth), 1044286, 8, 1044287); + AddCraft(typeof(FancyShirt), 1015269, 1027933, 24.8, 49.8, typeof(Cloth), 1044286, 8, 1044287); + AddCraft(typeof(Tunic), 1015269, 1028097, 00.0, 25.0, typeof(Cloth), 1044286, 12, 1044287); + AddCraft(typeof(Surcoat), 1015269, 1028189, 8.2, 33.2, typeof(Cloth), 1044286, 14, 1044287); + AddCraft(typeof(PlainDress), 1015269, 1027937, 12.4, 37.4, typeof(Cloth), 1044286, 10, 1044287); + AddCraft(typeof(FancyDress), 1015269, 1027935, 33.1, 58.1, typeof(Cloth), 1044286, 12, 1044287); + AddCraft(typeof(Cloak), 1015269, 1025397, 41.4, 66.4, typeof(Cloth), 1044286, 14, 1044287); + AddCraft(typeof(Robe), 1015269, 1027939, 53.9, 78.9, typeof(Cloth), 1044286, 16, 1044287); + AddCraft(typeof(JesterSuit), 1015269, 1028095, 8.2, 33.2, typeof(Cloth), 1044286, 24, 1044287); + + if (Core.AOS) + { + AddCraft(typeof(FurCape), 1015269, 1028969, 35.0, 60.0, typeof(Cloth), 1044286, 13, 1044287); + AddCraft(typeof(GildedDress), 1015269, 1028973, 37.5, 62.5, typeof(Cloth), 1044286, 16, 1044287); + AddCraft(typeof(FormalShirt), 1015269, 1028975, 26.0, 51.0, typeof(Cloth), 1044286, 16, 1044287); + } + + if (Core.SE) + { + index = AddCraft(typeof(ClothNinjaJacket), 1015269, 1030207, 75.0, 100.0, typeof(Cloth), 1044286, 12, + 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(Kamishimo), 1015269, 1030212, 75.0, 100.0, typeof(Cloth), 1044286, 15, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(HakamaShita), 1015269, 1030215, 40.0, 65.0, typeof(Cloth), 1044286, 14, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(MaleKimono), 1015269, 1030189, 50.0, 75.0, typeof(Cloth), 1044286, 16, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(FemaleKimono), 1015269, 1030190, 50.0, 75.0, typeof(Cloth), 1044286, 16, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(JinBaori), 1015269, 1030220, 30.0, 55.0, typeof(Cloth), 1044286, 12, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Pants + + AddCraft(typeof(ShortPants), 1015279, 1025422, 24.8, 49.8, typeof(Cloth), 1044286, 6, 1044287); + AddCraft(typeof(LongPants), 1015279, 1025433, 24.8, 49.8, typeof(Cloth), 1044286, 8, 1044287); + AddCraft(typeof(Kilt), 1015279, 1025431, 20.7, 45.7, typeof(Cloth), 1044286, 8, 1044287); + AddCraft(typeof(Skirt), 1015279, 1025398, 29.0, 54.0, typeof(Cloth), 1044286, 10, 1044287); + + if (Core.AOS) + AddCraft(typeof(FurSarong), 1015279, 1028971, 35.0, 60.0, typeof(Cloth), 1044286, 12, 1044287); + + if (Core.SE) + { + index = AddCraft(typeof(Hakama), 1015279, 1030213, 50.0, 75.0, typeof(Cloth), 1044286, 16, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(TattsukeHakama), 1015279, 1030214, 50.0, 75.0, typeof(Cloth), 1044286, 16, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Misc + + AddCraft(typeof(BodySash), 1015283, 1025441, 4.1, 29.1, typeof(Cloth), 1044286, 4, 1044287); + AddCraft(typeof(HalfApron), 1015283, 1025435, 20.7, 45.7, typeof(Cloth), 1044286, 6, 1044287); + AddCraft(typeof(FullApron), 1015283, 1025437, 29.0, 54.0, typeof(Cloth), 1044286, 10, 1044287); + + if (Core.SE) + { + index = AddCraft(typeof(Obi), 1015283, 1030219, 20.0, 45.0, typeof(Cloth), 1044286, 6, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + if (Core.ML) + { + index = AddCraft(typeof(ElvenQuiver), 1015283, 1032657, 65.0, 115.0, typeof(Leather), 1044462, 28, 1044463); + AddRecipe(index, 501); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(QuiverOfFire), 1015283, 1073109, 65.0, 115.0, typeof(Leather), 1044462, 28, 1044463); + AddRes(index, typeof(FireRuby), 1032695, 15, 1042081); + AddRecipe(index, 502); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(QuiverOfIce), 1015283, 1073110, 65.0, 115.0, typeof(Leather), 1044462, 28, 1044463); + AddRes(index, typeof(WhitePearl), 1032694, 15, 1042081); + AddRecipe(index, 503); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(QuiverOfBlight), 1015283, 1073111, 65.0, 115.0, typeof(Leather), 1044462, 28, + 1044463); + AddRes(index, typeof(Blight), 1032675, 10, 1042081); + AddRecipe(index, 504); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(QuiverOfLightning), 1015283, 1073112, 65.0, 115.0, typeof(Leather), 1044462, 28, + 1044463); + AddRes(index, typeof(Corruption), 1032676, 10, 1042081); + AddRecipe(index, 505); + SetNeededExpansion(index, Expansion.ML); + } + + AddCraft(typeof(OilCloth), 1015283, 1041498, 74.6, 99.6, typeof(Cloth), 1044286, 1, 1044287); + + if (Core.SE) + { + index = AddCraft(typeof(GozaMatEastDeed), 1015283, 1030404, 55.0, 80.0, typeof(Cloth), 1044286, 25, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(GozaMatSouthDeed), 1015283, 1030405, 55.0, 80.0, typeof(Cloth), 1044286, 25, + 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(SquareGozaMatEastDeed), 1015283, 1030407, 55.0, 80.0, typeof(Cloth), 1044286, 25, + 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(SquareGozaMatSouthDeed), 1015283, 1030406, 55.0, 80.0, typeof(Cloth), 1044286, 25, + 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(BrocadeGozaMatEastDeed), 1015283, 1030408, 55.0, 80.0, typeof(Cloth), 1044286, 25, + 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(BrocadeGozaMatSouthDeed), 1015283, 1030409, 55.0, 80.0, typeof(Cloth), 1044286, 25, + 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(BrocadeSquareGozaMatEastDeed), 1015283, 1030411, 55.0, 80.0, typeof(Cloth), 1044286, + 25, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(BrocadeSquareGozaMatSouthDeed), 1015283, 1030410, 55.0, 80.0, typeof(Cloth), 1044286, + 25, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Footwear + + if (Core.AOS) + AddCraft(typeof(FurBoots), 1015288, 1028967, 50.0, 75.0, typeof(Cloth), 1044286, 12, 1044287); + + if (Core.SE) + { + index = AddCraft(typeof(NinjaTabi), 1015288, 1030210, 70.0, 95.0, typeof(Cloth), 1044286, 10, 1044287); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(SamuraiTabi), 1015288, 1030209, 20.0, 45.0, typeof(Cloth), 1044286, 6, 1044287); + SetNeededExpansion(index, Expansion.SE); + } + + AddCraft(typeof(Sandals), 1015288, 1025901, 12.4, 37.4, typeof(Leather), 1044462, 4, 1044463); + AddCraft(typeof(Shoes), 1015288, 1025904, 16.5, 41.5, typeof(Leather), 1044462, 6, 1044463); + AddCraft(typeof(Boots), 1015288, 1025899, 33.1, 58.1, typeof(Leather), 1044462, 8, 1044463); + AddCraft(typeof(ThighBoots), 1015288, 1025906, 41.4, 66.4, typeof(Leather), 1044462, 10, 1044463); + + #endregion + + #region Leather Armor + + if (Core.ML) + { + index = AddCraft(typeof(SpellWovenBritches), 1015293, 1072929, 92.5, 117.5, typeof(Leather), 1044462, 15, + 1044463); + AddRes(index, typeof(EyeOfTheTravesty), 1032685, 1, 1044253); + AddRes(index, typeof(Putrefication), 1032678, 10, 1044253); + AddRes(index, typeof(Scourge), 1032677, 10, 1044253); + AddRareRecipe(index, 506); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(SongWovenMantle), 1015293, 1072931, 92.5, 117.5, typeof(Leather), 1044462, 15, + 1044463); + AddRes(index, typeof(EyeOfTheTravesty), 1032685, 1, 1044253); + AddRes(index, typeof(Blight), 1032675, 10, 1044253); + AddRes(index, typeof(Muculent), 1032680, 10, 1044253); + AddRareRecipe(index, 507); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(StitchersMittens), 1015293, 1072932, 92.5, 117.5, typeof(Leather), 1044462, 15, + 1044463); + AddRes(index, typeof(CapturedEssence), 1032686, 1, 1044253); + AddRes(index, typeof(Corruption), 1032676, 10, 1044253); + AddRes(index, typeof(Taint), 1032679, 10, 1044253); + AddRareRecipe(index, 508); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + } + + AddCraft(typeof(LeatherGorget), 1015293, 1025063, 53.9, 78.9, typeof(Leather), 1044462, 4, 1044463); + AddCraft(typeof(LeatherCap), 1015293, 1027609, 6.2, 31.2, typeof(Leather), 1044462, 2, 1044463); + AddCraft(typeof(LeatherGloves), 1015293, 1025062, 51.8, 76.8, typeof(Leather), 1044462, 3, 1044463); + AddCraft(typeof(LeatherArms), 1015293, 1025061, 53.9, 78.9, typeof(Leather), 1044462, 4, 1044463); + AddCraft(typeof(LeatherLegs), 1015293, 1025067, 66.3, 91.3, typeof(Leather), 1044462, 10, 1044463); + AddCraft(typeof(LeatherChest), 1015293, 1025068, 70.5, 95.5, typeof(Leather), 1044462, 12, 1044463); + + if (Core.SE) + { + index = AddCraft(typeof(LeatherJingasa), 1015293, 1030177, 45.0, 70.0, typeof(Leather), 1044462, 4, 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherMempo), 1015293, 1030181, 80.0, 105.0, typeof(Leather), 1044462, 8, 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherDo), 1015293, 1030182, 75.0, 100.0, typeof(Leather), 1044462, 12, 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherHiroSode), 1015293, 1030185, 55.0, 80.0, typeof(Leather), 1044462, 5, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherSuneate), 1015293, 1030193, 68.0, 93.0, typeof(Leather), 1044462, 12, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherHaidate), 1015293, 1030197, 68.0, 93.0, typeof(Leather), 1044462, 12, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherNinjaPants), 1015293, 1030204, 80.0, 105.0, typeof(Leather), 1044462, 13, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherNinjaJacket), 1015293, 1030206, 85.0, 110.0, typeof(Leather), 1044462, 13, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherNinjaBelt), 1015293, 1030203, 50.0, 75.0, typeof(Leather), 1044462, 5, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherNinjaMitts), 1015293, 1030205, 65.0, 90.0, typeof(Leather), 1044462, 12, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(LeatherNinjaHood), 1015293, 1030201, 90.0, 115.0, typeof(Leather), 1044462, 14, + 1044463); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Studded Armor + + AddCraft(typeof(StuddedGorget), 1015300, 1025078, 78.8, 103.8, typeof(Leather), 1044462, 6, 1044463); + AddCraft(typeof(StuddedGloves), 1015300, 1025077, 82.9, 107.9, typeof(Leather), 1044462, 8, 1044463); + AddCraft(typeof(StuddedArms), 1015300, 1025076, 87.1, 112.1, typeof(Leather), 1044462, 10, 1044463); + AddCraft(typeof(StuddedLegs), 1015300, 1025082, 91.2, 116.2, typeof(Leather), 1044462, 12, 1044463); + AddCraft(typeof(StuddedChest), 1015300, 1025083, 94.0, 119.0, typeof(Leather), 1044462, 14, 1044463); + + if (Core.SE) + { + index = AddCraft(typeof(StuddedMempo), 1015300, 1030216, 80.0, 105.0, typeof(Leather), 1044462, 8, 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(StuddedDo), 1015300, 1030183, 95.0, 120.0, typeof(Leather), 1044462, 14, 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(StuddedHiroSode), 1015300, 1030186, 85.0, 110.0, typeof(Leather), 1044462, 8, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(StuddedSuneate), 1015300, 1030194, 92.0, 117.0, typeof(Leather), 1044462, 14, + 1044463); + SetNeededExpansion(index, Expansion.SE); + index = AddCraft(typeof(StuddedHaidate), 1015300, 1030198, 92.0, 117.0, typeof(Leather), 1044462, 14, + 1044463); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Female Armor + + AddCraft(typeof(LeatherShorts), 1015306, 1027168, 62.2, 87.2, typeof(Leather), 1044462, 8, 1044463); + AddCraft(typeof(LeatherSkirt), 1015306, 1027176, 58.0, 83.0, typeof(Leather), 1044462, 6, 1044463); + AddCraft(typeof(LeatherBustierArms), 1015306, 1027178, 58.0, 83.0, typeof(Leather), 1044462, 6, 1044463); + AddCraft(typeof(StuddedBustierArms), 1015306, 1027180, 82.9, 107.9, typeof(Leather), 1044462, 8, 1044463); + AddCraft(typeof(FemaleLeatherChest), 1015306, 1027174, 62.2, 87.2, typeof(Leather), 1044462, 8, 1044463); + AddCraft(typeof(FemaleStuddedChest), 1015306, 1027170, 87.1, 112.1, typeof(Leather), 1044462, 10, 1044463); + + #endregion + + #region Bone Armor + + index = AddCraft(typeof(BoneHelm), 1049149, 1025206, 85.0, 110.0, typeof(Leather), 1044462, 4, 1044463); + AddRes(index, typeof(Bone), 1049064, 2, 1049063); + + index = AddCraft(typeof(BoneGloves), 1049149, 1025205, 89.0, 114.0, typeof(Leather), 1044462, 6, 1044463); + AddRes(index, typeof(Bone), 1049064, 2, 1049063); + + index = AddCraft(typeof(BoneArms), 1049149, 1025203, 92.0, 117.0, typeof(Leather), 1044462, 8, 1044463); + AddRes(index, typeof(Bone), 1049064, 4, 1049063); + + index = AddCraft(typeof(BoneLegs), 1049149, 1025202, 95.0, 120.0, typeof(Leather), 1044462, 10, 1044463); + AddRes(index, typeof(Bone), 1049064, 6, 1049063); + + index = AddCraft(typeof(BoneChest), 1049149, 1025199, 96.0, 121.0, typeof(Leather), 1044462, 12, 1044463); + AddRes(index, typeof(Bone), 1049064, 10, 1049063); + + index = AddCraft(typeof(OrcHelm), 1049149, 1027947, 90.0, 115.0, typeof(Leather), 1044462, 6, 1044463); + AddRes(index, typeof(Bone), 1049064, 4, 1049063); + + #endregion + + // Set the overridable material + SetSubRes(typeof(Leather), 1049150); + + // Add every material you want the player to be able to choose from + // This will override the overridable material + AddSubRes(typeof(Leather), 1049150, 00.0, 1044462, 1049311); + AddSubRes(typeof(SpinedLeather), 1049151, 65.0, 1044462, 1049311); + AddSubRes(typeof(HornedLeather), 1049152, 80.0, 1044462, 1049311); + AddSubRes(typeof(BarbedLeather), 1049153, 99.0, 1044462, 1049311); + + MarkOption = true; + Repair = Core.AOS; + CanEnhance = Core.AOS; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Craft/DefTinkering.cs b/Scripts/Engines/Craft/DefTinkering.cs index 5304f00cb..5ac122fa3 100644 --- a/Scripts/Engines/Craft/DefTinkering.cs +++ b/Scripts/Engines/Craft/DefTinkering.cs @@ -1,511 +1,552 @@ using System; -using Server.Items; using Server.Factions; +using Server.Items; using Server.Targeting; namespace Server.Engines.Craft { - public class DefTinkering : CraftSystem - { - public override SkillName MainSkill => SkillName.Tinkering; - - public override int GumpTitleNumber => 1044007; - - private static CraftSystem m_CraftSystem; - - public static CraftSystem CraftSystem - { - get - { - if ( m_CraftSystem == null ) - m_CraftSystem = new DefTinkering(); - - return m_CraftSystem; - } - } - - private DefTinkering() : base( 1, 1, 1.25 )// base( 1, 1, 3.0 ) - { - } - - public override double GetChanceAtMin( CraftItem item ) - { - if ( item.NameNumber == 1044258 || item.NameNumber == 1046445 ) // potion keg and faction trap removal kit - return 0.5; // 50% - - return 0.0; // 0% - } - - public override int CanCraft( Mobile from, BaseTool tool, Type itemType ) - { - if ( tool == null || tool.Deleted || tool.UsesRemaining < 0 ) - return 1044038; // You have worn out your tool! - if ( !BaseTool.CheckAccessible( tool, from ) ) - return 1044263; // The tool must be on your person to use. - if ( itemType != null && ( itemType.IsSubclassOf( typeof( BaseFactionTrapDeed ) ) || itemType == typeof( FactionTrapRemovalKit ) ) && Faction.Find( from ) == null ) - return 1044573; // You have to be in a faction to do that. - - return 0; - } - - private static Type[] m_TinkerColorables = { - typeof( ForkLeft ), typeof( ForkRight ), - typeof( SpoonLeft ), typeof( SpoonRight ), - typeof( KnifeLeft ), typeof( KnifeRight ), - typeof( Plate ), - typeof( Goblet ), typeof( PewterMug ), - typeof( KeyRing ), - typeof( Candelabra ), typeof( Scales ), - typeof( Key ), typeof( Globe ), - typeof( Spyglass ), typeof( Lantern ), - typeof( HeatingStand ) - }; - - public override bool RetainsColorFrom( CraftItem item, Type type ) - { - if ( !type.IsSubclassOf( typeof( BaseIngot ) ) ) - return false; - - type = item.ItemType; - - bool contains = false; - - for ( int i = 0; !contains && i < m_TinkerColorables.Length; ++i ) - contains = ( m_TinkerColorables[i] == type ); - - return contains; - } - - public override void PlayCraftEffect( Mobile from ) - { - // no sound - //from.PlaySound( 0x241 ); - } - - public override int PlayEndingEffect( Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, bool makersMark, CraftItem item ) - { - if ( toolBroken ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool - - if ( failed ) - { - if ( lostMaterial ) - return 1044043; // You failed to create the item, and some of your materials are lost. - return 1044157; // You failed to create the item, but no materials were lost. - } - - if ( quality == 0 ) - return 502785; // You were barely able to make this item. It's quality is below average. - if ( makersMark && quality == 2 ) - return 1044156; // You create an exceptional quality item and affix your maker's mark. - if ( quality == 2 ) - return 1044155; // You create an exceptional quality item. - return 1044154; // You create the item. - } - - public override bool ConsumeOnFailure( Mobile from, Type resourceType, CraftItem craftItem ) - { - if ( resourceType == typeof( Silver ) ) - return false; - - return base.ConsumeOnFailure( from, resourceType, craftItem ); - } - - public void AddJewelrySet( GemType gemType, Type itemType ) - { - int offset = (int)gemType - 1; - - int index = AddCraft( typeof( GoldRing ), 1044049, 1044176 + offset, 40.0, 90.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, itemType, 1044231 + offset, 1, 1044240 ); - - index = AddCraft( typeof( SilverBeadNecklace ), 1044049, 1044185 + offset, 40.0, 90.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, itemType, 1044231 + offset, 1, 1044240 ); - - index = AddCraft( typeof( GoldNecklace ), 1044049, 1044194 + offset, 40.0, 90.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, itemType, 1044231 + offset, 1, 1044240 ); - - index = AddCraft( typeof( GoldEarrings ), 1044049, 1044203 + offset, 40.0, 90.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, itemType, 1044231 + offset, 1, 1044240 ); - - index = AddCraft( typeof( GoldBeadNecklace ), 1044049, 1044212 + offset, 40.0, 90.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, itemType, 1044231 + offset, 1, 1044240 ); - - index = AddCraft( typeof( GoldBracelet ), 1044049, 1044221 + offset, 40.0, 90.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, itemType, 1044231 + offset, 1, 1044240 ); - } - - public override void InitCraftList() - { - int index = -1; - - #region Wooden Items - AddCraft( typeof( JointingPlane ), 1044042, 1024144, 0.0, 50.0, typeof( Log ), 1044041, 4, 1044351 ); - AddCraft( typeof( MouldingPlane ), 1044042, 1024140, 0.0, 50.0, typeof( Log ), 1044041, 4, 1044351 ); - AddCraft( typeof( SmoothingPlane ), 1044042, 1024146, 0.0, 50.0, typeof( Log ), 1044041, 4, 1044351 ); - AddCraft( typeof( ClockFrame ), 1044042, 1024173, 0.0, 50.0, typeof( Log ), 1044041, 6, 1044351 ); - AddCraft( typeof( Axle ), 1044042, 1024187, -25.0, 25.0, typeof( Log ), 1044041, 2, 1044351 ); - AddCraft( typeof( RollingPin ), 1044042, 1024163, 0.0, 50.0, typeof( Log ), 1044041, 5, 1044351 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( Nunchaku ), 1044042, 1030158, 70.0, 120.0, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddRes( index, typeof( Log ), 1044041, 8, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - } - #endregion - - #region Tools - AddCraft( typeof( Scissors ), 1044046, 1023998, 5.0, 55.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( MortarPestle ), 1044046, 1023739, 20.0, 70.0, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddCraft( typeof( Scorp ), 1044046, 1024327, 30.0, 80.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( TinkerTools ), 1044046, 1044164, 10.0, 60.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( Hatchet ), 1044046, 1023907, 30.0, 80.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( DrawKnife ), 1044046, 1024324, 30.0, 80.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( SewingKit ), 1044046, 1023997, 10.0, 70.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( Saw ), 1044046, 1024148, 30.0, 80.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( DovetailSaw ), 1044046, 1024136, 30.0, 80.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Froe ), 1044046, 1024325, 30.0, 80.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( Shovel ), 1044046, 1023898, 40.0, 90.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Hammer ), 1044046, 1024138, 30.0, 80.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( Tongs ), 1044046, 1024028, 35.0, 85.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( SmithHammer ), 1044046, 1025091, 40.0, 90.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( SledgeHammer ), 1044046, 1024021, 40.0, 90.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Inshave ), 1044046, 1024326, 30.0, 80.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( Pickaxe ), 1044046, 1023718, 40.0, 90.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Lockpick ), 1044046, 1025371, 45.0, 95.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( Skillet ), 1044046, 1044567, 30.0, 80.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( FlourSifter ), 1044046, 1024158, 50.0, 100.0, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddCraft( typeof( FletcherTools ), 1044046, 1044166, 35.0, 85.0, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddCraft( typeof( MapmakersPen ), 1044046, 1044167, 25.0, 75.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( ScribesPen ), 1044046, 1044168, 25.0, 75.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - #endregion - - #region Parts - AddCraft( typeof( Gears ), 1044047, 1024179, 5.0, 55.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( ClockParts ), 1044047, 1024175, 25.0, 75.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( BarrelTap ), 1044047, 1024100, 35.0, 85.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( Springs ), 1044047, 1024189, 5.0, 55.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( SextantParts ), 1044047, 1024185, 30.0, 80.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( BarrelHoops ), 1044047, 1024321, -15.0, 35.0, typeof( IronIngot ), 1044036, 5, 1044037 ); - AddCraft( typeof( Hinge ), 1044047, 1024181, 5.0, 55.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( BolaBall ), 1044047, 1023699, 45.0, 95.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - - if ( Core.ML ) - { - index = AddCraft( typeof( JeweledFiligree ), 1044047, 1072894, 70.0, 110.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, typeof( StarSapphire ), 1044231, 1, 1044253 ); - AddRes( index, typeof( Ruby ), 1044234, 1, 1044253 ); - SetNeededExpansion( index, Expansion.ML ); - } - #endregion - - #region Utensils - AddCraft( typeof( ButcherKnife ), 1044048, 1025110, 25.0, 75.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( SpoonLeft ), 1044048, 1044158, 0.0, 50.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( SpoonRight ), 1044048, 1044159, 0.0, 50.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( Plate ), 1044048, 1022519, 0.0, 50.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( ForkLeft ), 1044048, 1044160, 0.0, 50.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( ForkRight ), 1044048, 1044161, 0.0, 50.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( Cleaver ), 1044048, 1023778, 20.0, 70.0, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddCraft( typeof( KnifeLeft ), 1044048, 1044162, 0.0, 50.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( KnifeRight ), 1044048, 1044163, 0.0, 50.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddCraft( typeof( Goblet ), 1044048, 1022458, 10.0, 60.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( PewterMug ), 1044048, 1024097, 10.0, 60.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( SkinningKnife ), 1044048, 1023781, 25.0, 75.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - #endregion - - #region Misc - AddCraft( typeof( KeyRing ), 1044050, 1024113, 10.0, 60.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( Candelabra ), 1044050, 1022599, 55.0, 105.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Scales ), 1044050, 1026225, 60.0, 110.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Key ), 1044050, 1024112, 20.0, 70.0, typeof( IronIngot ), 1044036, 3, 1044037 ); - AddCraft( typeof( Globe ), 1044050, 1024167, 55.0, 105.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Spyglass ), 1044050, 1025365, 60.0, 110.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - AddCraft( typeof( Lantern ), 1044050, 1022597, 30.0, 80.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddCraft( typeof( HeatingStand ), 1044050, 1026217, 60.0, 110.0, typeof( IronIngot ), 1044036, 4, 1044037 ); - - if ( Core.SE ) - { - index = AddCraft( typeof( ShojiLantern ), 1044050, 1029404, 65.0, 115.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( Log ), 1044041, 5, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( PaperLantern ), 1044050, 1029406, 65.0, 115.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( Log ), 1044041, 5, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( RoundPaperLantern ), 1044050, 1029418, 65.0, 115.0, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( Log ), 1044041, 5, 1044351 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( WindChimes ), 1044050, 1030290, 80.0, 130.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - - index = AddCraft( typeof( FancyWindChimes ), 1044050, 1030291, 80.0, 130.0, typeof( IronIngot ), 1044036, 15, 1044037 ); - SetNeededExpansion( index, Expansion.SE ); - } - #endregion - - #region Jewelry - AddJewelrySet( GemType.StarSapphire, typeof( StarSapphire ) ); - AddJewelrySet( GemType.Emerald, typeof( Emerald ) ); - AddJewelrySet( GemType.Sapphire, typeof( Sapphire ) ); - AddJewelrySet( GemType.Ruby, typeof( Ruby ) ); - AddJewelrySet( GemType.Citrine, typeof( Citrine ) ); - AddJewelrySet( GemType.Amethyst, typeof( Amethyst ) ); - AddJewelrySet( GemType.Tourmaline, typeof( Tourmaline ) ); - AddJewelrySet( GemType.Amber, typeof( Amber ) ); - AddJewelrySet( GemType.Diamond, typeof( Diamond ) ); - #endregion - - #region Multi-Component Items - index = AddCraft( typeof( AxleGears ), 1044051, 1024177, 0.0, 0.0, typeof( Axle ), 1044169, 1, 1044253 ); - AddRes( index, typeof( Gears ), 1044254, 1, 1044253 ); - - index = AddCraft( typeof( ClockParts ), 1044051, 1024175, 0.0, 0.0, typeof( AxleGears ), 1044170, 1, 1044253 ); - AddRes( index, typeof( Springs ), 1044171, 1, 1044253 ); - - index = AddCraft( typeof( SextantParts ), 1044051, 1024185, 0.0, 0.0, typeof( AxleGears ), 1044170, 1, 1044253 ); - AddRes( index, typeof( Hinge ), 1044172, 1, 1044253 ); - - index = AddCraft( typeof( ClockRight ), 1044051, 1044257, 0.0, 0.0, typeof( ClockFrame ), 1044174, 1, 1044253 ); - AddRes( index, typeof( ClockParts ), 1044173, 1, 1044253 ); - - index = AddCraft( typeof( ClockLeft ), 1044051, 1044256, 0.0, 0.0, typeof( ClockFrame ), 1044174, 1, 1044253 ); - AddRes( index, typeof( ClockParts ), 1044173, 1, 1044253 ); - - AddCraft( typeof( Sextant ), 1044051, 1024183, 0.0, 0.0, typeof( SextantParts ), 1044175, 1, 1044253 ); - - index = AddCraft( typeof( Bola ), 1044051, 1046441, 60.0, 80.0, typeof( BolaBall ), 1046440, 4, 1042613 ); - AddRes( index, typeof( Leather ), 1044462, 3, 1044463 ); - - index = AddCraft( typeof( PotionKeg ), 1044051, 1044258, 75.0, 100.0, typeof( Keg ), 1044255, 1, 1044253 ); - AddRes( index, typeof( Bottle ), 1044250, 10, 1044253 ); - AddRes( index, typeof( BarrelLid ), 1044251, 1, 1044253 ); - AddRes( index, typeof( BarrelTap ), 1044252, 1, 1044253 ); - - #endregion - - #region Traps - // Dart Trap - index = AddCraft( typeof( DartTrapCraft ), 1044052, 1024396, 30.0, 80.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddRes( index, typeof( Bolt ), 1044570, 1, 1044253 ); - - // Poison Trap - index = AddCraft( typeof( PoisonTrapCraft ), 1044052, 1044593, 30.0, 80.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddRes( index, typeof( BasePoisonPotion ), 1044571, 1, 1044253 ); - - // Explosion Trap - index = AddCraft( typeof( ExplosionTrapCraft ), 1044052, 1044597, 55.0, 105.0, typeof( IronIngot ), 1044036, 1, 1044037 ); - AddRes( index, typeof( BaseExplosionPotion ), 1044569, 1, 1044253 ); - - // Faction Gas Trap - index = AddCraft( typeof( FactionGasTrapDeed ), 1044052, 1044598, 65.0, 115.0, typeof( Silver ), 1044572, Core.AOS ? 250 : 1000, 1044253 ); - AddRes( index, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( BasePoisonPotion ), 1044571, 1, 1044253 ); - - // Faction explosion Trap - index = AddCraft( typeof( FactionExplosionTrapDeed ), 1044052, 1044599, 65.0, 115.0, typeof( Silver ), 1044572, Core.AOS ? 250 : 1000, 1044253 ); - AddRes( index, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( BaseExplosionPotion ), 1044569, 1, 1044253 ); - - // Faction Saw Trap - index = AddCraft( typeof( FactionSawTrapDeed ), 1044052, 1044600, 65.0, 115.0, typeof( Silver ), 1044572, Core.AOS ? 250 : 1000, 1044253 ); - AddRes( index, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( Gears ), 1044254, 1, 1044253 ); - - // Faction Spike Trap - index = AddCraft( typeof( FactionSpikeTrapDeed ), 1044052, 1044601, 65.0, 115.0, typeof( Silver ), 1044572, Core.AOS ? 250 : 1000, 1044253 ); - AddRes( index, typeof( IronIngot ), 1044036, 10, 1044037 ); - AddRes( index, typeof( Springs ), 1044171, 1, 1044253 ); - - // Faction trap removal kit - index = AddCraft( typeof( FactionTrapRemovalKit ), 1044052, 1046445, 90.0, 115.0, typeof( Silver ), 1044572, 500, 1044253 ); - AddRes( index, typeof( IronIngot ), 1044036, 10, 1044037 ); - #endregion - - // Magic Jewelry - if ( Core.ML ) - { - index = AddCraft( typeof( ResilientBracer ), 1073107, 1072933, 100.0, 125.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, typeof( CapturedEssence ), 1032686, 1, 1044253 ); - AddRes( index, typeof( BlueDiamond ), 1032696, 10, 1044253 ); - AddRes( index, typeof( Diamond ), 1062608, 50, 1044253 ); - AddRareRecipe( index, 600 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( EssenceOfBattle ), 1073107, 1072935, 100.0, 125.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, typeof( CapturedEssence ), 1032686, 1, 1044253 ); - AddRes( index, typeof( FireRuby ), 1032695, 10, 1044253 ); - AddRes( index, typeof( Ruby ), 1062603, 50, 1044253 ); - AddRareRecipe( index, 601 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - - index = AddCraft( typeof( PendantOfTheMagi ), 1073107, 1072937, 100.0, 125.0, typeof( IronIngot ), 1044036, 2, 1044037 ); - AddRes( index, typeof( EyeOfTheTravesty ), 1032685, 1, 1044253 ); - AddRes( index, typeof( WhitePearl ), 1032694, 10, 1044253 ); - AddRes( index, typeof( StarSapphire ), 1062600, 50, 1044253 ); - AddRareRecipe( index, 602 ); - ForceNonExceptional( index ); - SetNeededExpansion( index, Expansion.ML ); - } - - // Set the overridable material - SetSubRes( typeof( IronIngot ), 1044022 ); - - // Add every material you want the player to be able to choose from - // This will override the overridable material - AddSubRes( typeof( IronIngot ), 1044022, 00.0, 1044036, 1044267 ); - AddSubRes( typeof( DullCopperIngot ), 1044023, 65.0, 1044036, 1044268 ); - AddSubRes( typeof( ShadowIronIngot ), 1044024, 70.0, 1044036, 1044268 ); - AddSubRes( typeof( CopperIngot ), 1044025, 75.0, 1044036, 1044268 ); - AddSubRes( typeof( BronzeIngot ), 1044026, 80.0, 1044036, 1044268 ); - AddSubRes( typeof( GoldIngot ), 1044027, 85.0, 1044036, 1044268 ); - AddSubRes( typeof( AgapiteIngot ), 1044028, 90.0, 1044036, 1044268 ); - AddSubRes( typeof( VeriteIngot ), 1044029, 95.0, 1044036, 1044268 ); - AddSubRes( typeof( ValoriteIngot ), 1044030, 99.0, 1044036, 1044268 ); - - MarkOption = true; - Repair = true; - CanEnhance = Core.AOS; - } - } - - public abstract class TrapCraft : CustomCraft - { - public LockableContainer Container { get; private set; } - - public abstract TrapType TrapType{ get; } - - public TrapCraft( Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, int quality ) : base( from, craftItem, craftSystem, typeRes, tool, quality ) - { - } - - private int Verify( LockableContainer container ) - { - if ( container == null || container.KeyValue == 0 ) - return 1005638; // You can only trap lockable chests. - if ( From.Map != container.Map || !From.InRange( container.GetWorldLocation(), 2 ) ) - return 500446; // That is too far away. - if ( !container.Movable ) - return 502944; // You cannot trap this item because it is locked down. - if ( !container.IsAccessibleTo( From ) ) - return 502946; // That belongs to someone else. - if ( container.Locked ) - return 502943; // You can only trap an unlocked object. - if ( container.TrapType != TrapType.None ) - return 502945; // You can only place one trap on an object at a time. - - return 0; - } - - private bool Acquire( object target, out int message ) - { - LockableContainer container = target as LockableContainer; - - message = Verify( container ); - - if ( message > 0 ) - { - return false; - } - - Container = container; - return true; - } - - public override void EndCraftAction() - { - From.SendLocalizedMessage( 502921 ); // What would you like to set a trap on? - From.Target = new ContainerTarget( this ); - } - - private class ContainerTarget : Target - { - private TrapCraft m_TrapCraft; - - public ContainerTarget( TrapCraft trapCraft ) : base( -1, false, TargetFlags.None ) - { - m_TrapCraft = trapCraft; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - int message; - - if ( m_TrapCraft.Acquire( targeted, out message ) ) - m_TrapCraft.CraftItem.CompleteCraft( m_TrapCraft.Quality, false, m_TrapCraft.From, m_TrapCraft.CraftSystem, m_TrapCraft.TypeRes, m_TrapCraft.Tool, m_TrapCraft ); - else - Failure( message ); - } - - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - if ( cancelType == TargetCancelType.Canceled ) - Failure( 0 ); - } - - private void Failure( int message ) - { - Mobile from = m_TrapCraft.From; - BaseTool tool = m_TrapCraft.Tool; - - if ( tool != null && !tool.Deleted && tool.UsesRemaining > 0 ) - from.SendGump( new CraftGump( from, m_TrapCraft.CraftSystem, tool, message ) ); - else if ( message > 0 ) - from.SendLocalizedMessage( message ); - } - } - - public override Item CompleteCraft( out int message ) - { - message = Verify( Container ); - - if ( message == 0 ) - { - int trapLevel = (int)(From.Skills.Tinkering.Value / 10); - - Container.TrapType = TrapType; - Container.TrapPower = trapLevel * 9; - Container.TrapLevel = trapLevel; - Container.TrapOnLockpick = true; - - message = 1005639; // Trap is disabled until you lock the chest. - } - - return null; - } - } - - [CraftItemID( 0x1BFC )] - public class DartTrapCraft : TrapCraft - { - public override TrapType TrapType => TrapType.DartTrap; - - public DartTrapCraft( Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, int quality ) : base( from, craftItem, craftSystem, typeRes, tool, quality ) - { - } - } - - [CraftItemID( 0x113E )] - public class PoisonTrapCraft : TrapCraft - { - public override TrapType TrapType => TrapType.PoisonTrap; - - public PoisonTrapCraft( Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, int quality ) : base( from, craftItem, craftSystem, typeRes, tool, quality ) - { - } - } - - [CraftItemID( 0x370C )] - public class ExplosionTrapCraft : TrapCraft - { - public override TrapType TrapType => TrapType.ExplosionTrap; - - public ExplosionTrapCraft( Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, int quality ) : base( from, craftItem, craftSystem, typeRes, tool, quality ) - { - } - } -} + public class DefTinkering : CraftSystem + { + private static CraftSystem m_CraftSystem; + + private static Type[] m_TinkerColorables = + { + typeof(ForkLeft), typeof(ForkRight), + typeof(SpoonLeft), typeof(SpoonRight), + typeof(KnifeLeft), typeof(KnifeRight), + typeof(Plate), + typeof(Goblet), typeof(PewterMug), + typeof(KeyRing), + typeof(Candelabra), typeof(Scales), + typeof(Key), typeof(Globe), + typeof(Spyglass), typeof(Lantern), + typeof(HeatingStand) + }; + + private DefTinkering() : base(1, 1, 1.25) // base( 1, 1, 3.0 ) + { + } + + public override SkillName MainSkill => SkillName.Tinkering; + + public override int GumpTitleNumber => 1044007; + + public static CraftSystem CraftSystem + { + get + { + if (m_CraftSystem == null) + m_CraftSystem = new DefTinkering(); + + return m_CraftSystem; + } + } + + public override double GetChanceAtMin(CraftItem item) + { + if (item.NameNumber == 1044258 || item.NameNumber == 1046445) // potion keg and faction trap removal kit + return 0.5; // 50% + + return 0.0; // 0% + } + + public override int CanCraft(Mobile from, BaseTool tool, Type itemType) + { + if (tool == null || tool.Deleted || tool.UsesRemaining < 0) + return 1044038; // You have worn out your tool! + if (!BaseTool.CheckAccessible(tool, from)) + return 1044263; // The tool must be on your person to use. + if (itemType != null && + (itemType.IsSubclassOf(typeof(BaseFactionTrapDeed)) || itemType == typeof(FactionTrapRemovalKit)) && + Faction.Find(from) == null) + return 1044573; // You have to be in a faction to do that. + + return 0; + } + + public override bool RetainsColorFrom(CraftItem item, Type type) + { + if (!type.IsSubclassOf(typeof(BaseIngot))) + return false; + + type = item.ItemType; + + bool contains = false; + + for (int i = 0; !contains && i < m_TinkerColorables.Length; ++i) + contains = m_TinkerColorables[i] == type; + + return contains; + } + + public override void PlayCraftEffect(Mobile from) + { + // no sound + //from.PlaySound( 0x241 ); + } + + public override int PlayEndingEffect(Mobile from, bool failed, bool lostMaterial, bool toolBroken, int quality, + bool makersMark, CraftItem item) + { + if (toolBroken) + from.SendLocalizedMessage(1044038); // You have worn out your tool + + if (failed) + { + if (lostMaterial) + return 1044043; // You failed to create the item, and some of your materials are lost. + return 1044157; // You failed to create the item, but no materials were lost. + } + + if (quality == 0) + return 502785; // You were barely able to make this item. It's quality is below average. + if (makersMark && quality == 2) + return 1044156; // You create an exceptional quality item and affix your maker's mark. + if (quality == 2) + return 1044155; // You create an exceptional quality item. + return 1044154; // You create the item. + } + + public override bool ConsumeOnFailure(Mobile from, Type resourceType, CraftItem craftItem) + { + if (resourceType == typeof(Silver)) + return false; + + return base.ConsumeOnFailure(from, resourceType, craftItem); + } + + public void AddJewelrySet(GemType gemType, Type itemType) + { + int offset = (int)gemType - 1; + + int index = AddCraft(typeof(GoldRing), 1044049, 1044176 + offset, 40.0, 90.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, itemType, 1044231 + offset, 1, 1044240); + + index = AddCraft(typeof(SilverBeadNecklace), 1044049, 1044185 + offset, 40.0, 90.0, typeof(IronIngot), 1044036, + 2, 1044037); + AddRes(index, itemType, 1044231 + offset, 1, 1044240); + + index = AddCraft(typeof(GoldNecklace), 1044049, 1044194 + offset, 40.0, 90.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, itemType, 1044231 + offset, 1, 1044240); + + index = AddCraft(typeof(GoldEarrings), 1044049, 1044203 + offset, 40.0, 90.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, itemType, 1044231 + offset, 1, 1044240); + + index = AddCraft(typeof(GoldBeadNecklace), 1044049, 1044212 + offset, 40.0, 90.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, itemType, 1044231 + offset, 1, 1044240); + + index = AddCraft(typeof(GoldBracelet), 1044049, 1044221 + offset, 40.0, 90.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, itemType, 1044231 + offset, 1, 1044240); + } + + public override void InitCraftList() + { + int index = -1; + + #region Wooden Items + + AddCraft(typeof(JointingPlane), 1044042, 1024144, 0.0, 50.0, typeof(Log), 1044041, 4, 1044351); + AddCraft(typeof(MouldingPlane), 1044042, 1024140, 0.0, 50.0, typeof(Log), 1044041, 4, 1044351); + AddCraft(typeof(SmoothingPlane), 1044042, 1024146, 0.0, 50.0, typeof(Log), 1044041, 4, 1044351); + AddCraft(typeof(ClockFrame), 1044042, 1024173, 0.0, 50.0, typeof(Log), 1044041, 6, 1044351); + AddCraft(typeof(Axle), 1044042, 1024187, -25.0, 25.0, typeof(Log), 1044041, 2, 1044351); + AddCraft(typeof(RollingPin), 1044042, 1024163, 0.0, 50.0, typeof(Log), 1044041, 5, 1044351); + + if (Core.SE) + { + index = AddCraft(typeof(Nunchaku), 1044042, 1030158, 70.0, 120.0, typeof(IronIngot), 1044036, 3, 1044037); + AddRes(index, typeof(Log), 1044041, 8, 1044351); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Tools + + AddCraft(typeof(Scissors), 1044046, 1023998, 5.0, 55.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(MortarPestle), 1044046, 1023739, 20.0, 70.0, typeof(IronIngot), 1044036, 3, 1044037); + AddCraft(typeof(Scorp), 1044046, 1024327, 30.0, 80.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(TinkerTools), 1044046, 1044164, 10.0, 60.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(Hatchet), 1044046, 1023907, 30.0, 80.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(DrawKnife), 1044046, 1024324, 30.0, 80.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(SewingKit), 1044046, 1023997, 10.0, 70.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(Saw), 1044046, 1024148, 30.0, 80.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(DovetailSaw), 1044046, 1024136, 30.0, 80.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Froe), 1044046, 1024325, 30.0, 80.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(Shovel), 1044046, 1023898, 40.0, 90.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Hammer), 1044046, 1024138, 30.0, 80.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(Tongs), 1044046, 1024028, 35.0, 85.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(SmithHammer), 1044046, 1025091, 40.0, 90.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(SledgeHammer), 1044046, 1024021, 40.0, 90.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Inshave), 1044046, 1024326, 30.0, 80.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(Pickaxe), 1044046, 1023718, 40.0, 90.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Lockpick), 1044046, 1025371, 45.0, 95.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(Skillet), 1044046, 1044567, 30.0, 80.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(FlourSifter), 1044046, 1024158, 50.0, 100.0, typeof(IronIngot), 1044036, 3, 1044037); + AddCraft(typeof(FletcherTools), 1044046, 1044166, 35.0, 85.0, typeof(IronIngot), 1044036, 3, 1044037); + AddCraft(typeof(MapmakersPen), 1044046, 1044167, 25.0, 75.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(ScribesPen), 1044046, 1044168, 25.0, 75.0, typeof(IronIngot), 1044036, 1, 1044037); + + #endregion + + #region Parts + + AddCraft(typeof(Gears), 1044047, 1024179, 5.0, 55.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(ClockParts), 1044047, 1024175, 25.0, 75.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(BarrelTap), 1044047, 1024100, 35.0, 85.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(Springs), 1044047, 1024189, 5.0, 55.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(SextantParts), 1044047, 1024185, 30.0, 80.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(BarrelHoops), 1044047, 1024321, -15.0, 35.0, typeof(IronIngot), 1044036, 5, 1044037); + AddCraft(typeof(Hinge), 1044047, 1024181, 5.0, 55.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(BolaBall), 1044047, 1023699, 45.0, 95.0, typeof(IronIngot), 1044036, 10, 1044037); + + if (Core.ML) + { + index = AddCraft(typeof(JeweledFiligree), 1044047, 1072894, 70.0, 110.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, typeof(StarSapphire), 1044231, 1, 1044253); + AddRes(index, typeof(Ruby), 1044234, 1, 1044253); + SetNeededExpansion(index, Expansion.ML); + } + + #endregion + + #region Utensils + + AddCraft(typeof(ButcherKnife), 1044048, 1025110, 25.0, 75.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(SpoonLeft), 1044048, 1044158, 0.0, 50.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(SpoonRight), 1044048, 1044159, 0.0, 50.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(Plate), 1044048, 1022519, 0.0, 50.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(ForkLeft), 1044048, 1044160, 0.0, 50.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(ForkRight), 1044048, 1044161, 0.0, 50.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(Cleaver), 1044048, 1023778, 20.0, 70.0, typeof(IronIngot), 1044036, 3, 1044037); + AddCraft(typeof(KnifeLeft), 1044048, 1044162, 0.0, 50.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(KnifeRight), 1044048, 1044163, 0.0, 50.0, typeof(IronIngot), 1044036, 1, 1044037); + AddCraft(typeof(Goblet), 1044048, 1022458, 10.0, 60.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(PewterMug), 1044048, 1024097, 10.0, 60.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(SkinningKnife), 1044048, 1023781, 25.0, 75.0, typeof(IronIngot), 1044036, 2, 1044037); + + #endregion + + #region Misc + + AddCraft(typeof(KeyRing), 1044050, 1024113, 10.0, 60.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(Candelabra), 1044050, 1022599, 55.0, 105.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Scales), 1044050, 1026225, 60.0, 110.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Key), 1044050, 1024112, 20.0, 70.0, typeof(IronIngot), 1044036, 3, 1044037); + AddCraft(typeof(Globe), 1044050, 1024167, 55.0, 105.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Spyglass), 1044050, 1025365, 60.0, 110.0, typeof(IronIngot), 1044036, 4, 1044037); + AddCraft(typeof(Lantern), 1044050, 1022597, 30.0, 80.0, typeof(IronIngot), 1044036, 2, 1044037); + AddCraft(typeof(HeatingStand), 1044050, 1026217, 60.0, 110.0, typeof(IronIngot), 1044036, 4, 1044037); + + if (Core.SE) + { + index = AddCraft(typeof(ShojiLantern), 1044050, 1029404, 65.0, 115.0, typeof(IronIngot), 1044036, 10, + 1044037); + AddRes(index, typeof(Log), 1044041, 5, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(PaperLantern), 1044050, 1029406, 65.0, 115.0, typeof(IronIngot), 1044036, 10, + 1044037); + AddRes(index, typeof(Log), 1044041, 5, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(RoundPaperLantern), 1044050, 1029418, 65.0, 115.0, typeof(IronIngot), 1044036, 10, + 1044037); + AddRes(index, typeof(Log), 1044041, 5, 1044351); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(WindChimes), 1044050, 1030290, 80.0, 130.0, typeof(IronIngot), 1044036, 15, 1044037); + SetNeededExpansion(index, Expansion.SE); + + index = AddCraft(typeof(FancyWindChimes), 1044050, 1030291, 80.0, 130.0, typeof(IronIngot), 1044036, 15, + 1044037); + SetNeededExpansion(index, Expansion.SE); + } + + #endregion + + #region Jewelry + + AddJewelrySet(GemType.StarSapphire, typeof(StarSapphire)); + AddJewelrySet(GemType.Emerald, typeof(Emerald)); + AddJewelrySet(GemType.Sapphire, typeof(Sapphire)); + AddJewelrySet(GemType.Ruby, typeof(Ruby)); + AddJewelrySet(GemType.Citrine, typeof(Citrine)); + AddJewelrySet(GemType.Amethyst, typeof(Amethyst)); + AddJewelrySet(GemType.Tourmaline, typeof(Tourmaline)); + AddJewelrySet(GemType.Amber, typeof(Amber)); + AddJewelrySet(GemType.Diamond, typeof(Diamond)); + + #endregion + + #region Multi-Component Items + + index = AddCraft(typeof(AxleGears), 1044051, 1024177, 0.0, 0.0, typeof(Axle), 1044169, 1, 1044253); + AddRes(index, typeof(Gears), 1044254, 1, 1044253); + + index = AddCraft(typeof(ClockParts), 1044051, 1024175, 0.0, 0.0, typeof(AxleGears), 1044170, 1, 1044253); + AddRes(index, typeof(Springs), 1044171, 1, 1044253); + + index = AddCraft(typeof(SextantParts), 1044051, 1024185, 0.0, 0.0, typeof(AxleGears), 1044170, 1, 1044253); + AddRes(index, typeof(Hinge), 1044172, 1, 1044253); + + index = AddCraft(typeof(ClockRight), 1044051, 1044257, 0.0, 0.0, typeof(ClockFrame), 1044174, 1, 1044253); + AddRes(index, typeof(ClockParts), 1044173, 1, 1044253); + + index = AddCraft(typeof(ClockLeft), 1044051, 1044256, 0.0, 0.0, typeof(ClockFrame), 1044174, 1, 1044253); + AddRes(index, typeof(ClockParts), 1044173, 1, 1044253); + + AddCraft(typeof(Sextant), 1044051, 1024183, 0.0, 0.0, typeof(SextantParts), 1044175, 1, 1044253); + + index = AddCraft(typeof(Bola), 1044051, 1046441, 60.0, 80.0, typeof(BolaBall), 1046440, 4, 1042613); + AddRes(index, typeof(Leather), 1044462, 3, 1044463); + + index = AddCraft(typeof(PotionKeg), 1044051, 1044258, 75.0, 100.0, typeof(Keg), 1044255, 1, 1044253); + AddRes(index, typeof(Bottle), 1044250, 10, 1044253); + AddRes(index, typeof(BarrelLid), 1044251, 1, 1044253); + AddRes(index, typeof(BarrelTap), 1044252, 1, 1044253); + + #endregion + + #region Traps + + // Dart Trap + index = AddCraft(typeof(DartTrapCraft), 1044052, 1024396, 30.0, 80.0, typeof(IronIngot), 1044036, 1, 1044037); + AddRes(index, typeof(Bolt), 1044570, 1, 1044253); + + // Poison Trap + index = AddCraft(typeof(PoisonTrapCraft), 1044052, 1044593, 30.0, 80.0, typeof(IronIngot), 1044036, 1, 1044037); + AddRes(index, typeof(BasePoisonPotion), 1044571, 1, 1044253); + + // Explosion Trap + index = AddCraft(typeof(ExplosionTrapCraft), 1044052, 1044597, 55.0, 105.0, typeof(IronIngot), 1044036, 1, + 1044037); + AddRes(index, typeof(BaseExplosionPotion), 1044569, 1, 1044253); + + // Faction Gas Trap + index = AddCraft(typeof(FactionGasTrapDeed), 1044052, 1044598, 65.0, 115.0, typeof(Silver), 1044572, + Core.AOS ? 250 : 1000, 1044253); + AddRes(index, typeof(IronIngot), 1044036, 10, 1044037); + AddRes(index, typeof(BasePoisonPotion), 1044571, 1, 1044253); + + // Faction explosion Trap + index = AddCraft(typeof(FactionExplosionTrapDeed), 1044052, 1044599, 65.0, 115.0, typeof(Silver), 1044572, + Core.AOS ? 250 : 1000, 1044253); + AddRes(index, typeof(IronIngot), 1044036, 10, 1044037); + AddRes(index, typeof(BaseExplosionPotion), 1044569, 1, 1044253); + + // Faction Saw Trap + index = AddCraft(typeof(FactionSawTrapDeed), 1044052, 1044600, 65.0, 115.0, typeof(Silver), 1044572, + Core.AOS ? 250 : 1000, 1044253); + AddRes(index, typeof(IronIngot), 1044036, 10, 1044037); + AddRes(index, typeof(Gears), 1044254, 1, 1044253); + + // Faction Spike Trap + index = AddCraft(typeof(FactionSpikeTrapDeed), 1044052, 1044601, 65.0, 115.0, typeof(Silver), 1044572, + Core.AOS ? 250 : 1000, 1044253); + AddRes(index, typeof(IronIngot), 1044036, 10, 1044037); + AddRes(index, typeof(Springs), 1044171, 1, 1044253); + + // Faction trap removal kit + index = AddCraft(typeof(FactionTrapRemovalKit), 1044052, 1046445, 90.0, 115.0, typeof(Silver), 1044572, 500, + 1044253); + AddRes(index, typeof(IronIngot), 1044036, 10, 1044037); + + #endregion + + // Magic Jewelry + if (Core.ML) + { + index = AddCraft(typeof(ResilientBracer), 1073107, 1072933, 100.0, 125.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, typeof(CapturedEssence), 1032686, 1, 1044253); + AddRes(index, typeof(BlueDiamond), 1032696, 10, 1044253); + AddRes(index, typeof(Diamond), 1062608, 50, 1044253); + AddRareRecipe(index, 600); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(EssenceOfBattle), 1073107, 1072935, 100.0, 125.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, typeof(CapturedEssence), 1032686, 1, 1044253); + AddRes(index, typeof(FireRuby), 1032695, 10, 1044253); + AddRes(index, typeof(Ruby), 1062603, 50, 1044253); + AddRareRecipe(index, 601); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + + index = AddCraft(typeof(PendantOfTheMagi), 1073107, 1072937, 100.0, 125.0, typeof(IronIngot), 1044036, 2, + 1044037); + AddRes(index, typeof(EyeOfTheTravesty), 1032685, 1, 1044253); + AddRes(index, typeof(WhitePearl), 1032694, 10, 1044253); + AddRes(index, typeof(StarSapphire), 1062600, 50, 1044253); + AddRareRecipe(index, 602); + ForceNonExceptional(index); + SetNeededExpansion(index, Expansion.ML); + } + + // Set the overridable material + SetSubRes(typeof(IronIngot), 1044022); + + // Add every material you want the player to be able to choose from + // This will override the overridable material + AddSubRes(typeof(IronIngot), 1044022, 00.0, 1044036, 1044267); + AddSubRes(typeof(DullCopperIngot), 1044023, 65.0, 1044036, 1044268); + AddSubRes(typeof(ShadowIronIngot), 1044024, 70.0, 1044036, 1044268); + AddSubRes(typeof(CopperIngot), 1044025, 75.0, 1044036, 1044268); + AddSubRes(typeof(BronzeIngot), 1044026, 80.0, 1044036, 1044268); + AddSubRes(typeof(GoldIngot), 1044027, 85.0, 1044036, 1044268); + AddSubRes(typeof(AgapiteIngot), 1044028, 90.0, 1044036, 1044268); + AddSubRes(typeof(VeriteIngot), 1044029, 95.0, 1044036, 1044268); + AddSubRes(typeof(ValoriteIngot), 1044030, 99.0, 1044036, 1044268); + + MarkOption = true; + Repair = true; + CanEnhance = Core.AOS; + } + } + + public abstract class TrapCraft : CustomCraft + { + public TrapCraft(Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, int quality) + : base(from, craftItem, craftSystem, typeRes, tool, quality) + { + } + + public LockableContainer Container{ get; private set; } + + public abstract TrapType TrapType{ get; } + + private int Verify(LockableContainer container) + { + if (container == null || container.KeyValue == 0) + return 1005638; // You can only trap lockable chests. + if (From.Map != container.Map || !From.InRange(container.GetWorldLocation(), 2)) + return 500446; // That is too far away. + if (!container.Movable) + return 502944; // You cannot trap this item because it is locked down. + if (!container.IsAccessibleTo(From)) + return 502946; // That belongs to someone else. + if (container.Locked) + return 502943; // You can only trap an unlocked object. + if (container.TrapType != TrapType.None) + return 502945; // You can only place one trap on an object at a time. + + return 0; + } + + private bool Acquire(object target, out int message) + { + LockableContainer container = target as LockableContainer; + + message = Verify(container); + + if (message > 0) return false; + + Container = container; + return true; + } + + public override void EndCraftAction() + { + From.SendLocalizedMessage(502921); // What would you like to set a trap on? + From.Target = new ContainerTarget(this); + } + + public override Item CompleteCraft(out int message) + { + message = Verify(Container); + + if (message == 0) + { + int trapLevel = (int)(From.Skills.Tinkering.Value / 10); + + Container.TrapType = TrapType; + Container.TrapPower = trapLevel * 9; + Container.TrapLevel = trapLevel; + Container.TrapOnLockpick = true; + + message = 1005639; // Trap is disabled until you lock the chest. + } + + return null; + } + + private class ContainerTarget : Target + { + private TrapCraft m_TrapCraft; + + public ContainerTarget(TrapCraft trapCraft) : base(-1, false, TargetFlags.None) + { + m_TrapCraft = trapCraft; + } + + protected override void OnTarget(Mobile from, object targeted) + { + int message; + + if (m_TrapCraft.Acquire(targeted, out message)) + m_TrapCraft.CraftItem.CompleteCraft(m_TrapCraft.Quality, false, m_TrapCraft.From, + m_TrapCraft.CraftSystem, m_TrapCraft.TypeRes, m_TrapCraft.Tool, m_TrapCraft); + else + Failure(message); + } + + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + if (cancelType == TargetCancelType.Canceled) + Failure(0); + } + + private void Failure(int message) + { + Mobile from = m_TrapCraft.From; + BaseTool tool = m_TrapCraft.Tool; + + if (tool != null && !tool.Deleted && tool.UsesRemaining > 0) + from.SendGump(new CraftGump(from, m_TrapCraft.CraftSystem, tool, message)); + else if (message > 0) + from.SendLocalizedMessage(message); + } + } + } + + [CraftItemID(0x1BFC)] + public class DartTrapCraft : TrapCraft + { + public DartTrapCraft(Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, + int quality) : base(from, craftItem, craftSystem, typeRes, tool, quality) + { + } + + public override TrapType TrapType => TrapType.DartTrap; + } + + [CraftItemID(0x113E)] + public class PoisonTrapCraft : TrapCraft + { + public PoisonTrapCraft(Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, + int quality) : base(from, craftItem, craftSystem, typeRes, tool, quality) + { + } + + public override TrapType TrapType => TrapType.PoisonTrap; + } + + [CraftItemID(0x370C)] + public class ExplosionTrapCraft : TrapCraft + { + public ExplosionTrapCraft(Mobile from, CraftItem craftItem, CraftSystem craftSystem, Type typeRes, BaseTool tool, + int quality) : base(from, craftItem, craftSystem, typeRes, tool, quality) + { + } + + public override TrapType TrapType => TrapType.ExplosionTrap; + } +} \ No newline at end of file diff --git a/Scripts/Engines/Doom/GauntletSpawner.cs b/Scripts/Engines/Doom/GauntletSpawner.cs index 75bfb2e0c..0bf7249d8 100644 --- a/Scripts/Engines/Doom/GauntletSpawner.cs +++ b/Scripts/Engines/Doom/GauntletSpawner.cs @@ -1,649 +1,659 @@ using System; +using System.Collections.Generic; +using Server.Commands; using Server.Items; using Server.Mobiles; using Server.Regions; -using Server.Commands; -using System.Collections.Generic; namespace Server.Engines.Doom { - public enum GauntletSpawnerState - { - InSequence, - InProgress, - Completed - } - - public class GauntletSpawner : Item - { - public const int PlayersPerSpawn = 5; - - public const int InSequenceItemHue = 0x000; - public const int InProgressItemHue = 0x676; - public const int CompletedItemHue = 0x455; - - private GauntletSpawnerState m_State; - - [CommandProperty( AccessLevel.GameMaster )] - public string TypeName { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public BaseDoor Door { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public BaseAddon Addon { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public GauntletSpawner Sequence { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool HasCompleted - { - get - { - if ( Creatures.Count == 0 ) - return false; - - for ( int i = 0; i < Creatures.Count; ++i ) - { - Mobile mob = Creatures[i]; - - if ( !mob.Deleted ) - return false; - } - - return true; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Rectangle2D RegionBounds { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public GauntletSpawnerState State - { - get => m_State; - set - { - if ( m_State == value ) - return; - - m_State = value; + public enum GauntletSpawnerState + { + InSequence, + InProgress, + Completed + } + + public class GauntletSpawner : Item + { + public const int PlayersPerSpawn = 5; + + public const int InSequenceItemHue = 0x000; + public const int InProgressItemHue = 0x676; + public const int CompletedItemHue = 0x455; + + private GauntletSpawnerState m_State; + + private Timer m_Timer; + + [Constructible] + public GauntletSpawner() : this(null) + { + } + + [Constructible] + public GauntletSpawner(string typeName) : base(0x36FE) + { + Visible = false; + Movable = false; + + TypeName = typeName; + Creatures = new List(); + Traps = new List(); + } + + public GauntletSpawner(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string TypeName{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public BaseDoor Door{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public BaseAddon Addon{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public GauntletSpawner Sequence{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool HasCompleted + { + get + { + if (Creatures.Count == 0) + return false; + + for (int i = 0; i < Creatures.Count; ++i) + { + Mobile mob = Creatures[i]; + + if (!mob.Deleted) + return false; + } + + return true; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Rectangle2D RegionBounds{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public GauntletSpawnerState State + { + get => m_State; + set + { + if (m_State == value) + return; + + m_State = value; + + int hue = 0; + bool lockDoors = m_State == GauntletSpawnerState.InProgress; + + switch (m_State) + { + case GauntletSpawnerState.InSequence: + hue = InSequenceItemHue; + break; + case GauntletSpawnerState.InProgress: + hue = InProgressItemHue; + break; + case GauntletSpawnerState.Completed: + hue = CompletedItemHue; + break; + } + + if (Door != null) + { + Door.Hue = hue; + Door.Locked = lockDoors; + + if (lockDoors) + { + Door.KeyValue = Key.RandomValue(); + Door.Open = false; + } + + if (Door.Link != null) + { + Door.Link.Hue = hue; + Door.Link.Locked = lockDoors; + + if (lockDoors) + { + Door.Link.KeyValue = Key.RandomValue(); + Door.Open = false; + } + } + } + + if (Addon != null) + Addon.Hue = hue; + + if (m_State == GauntletSpawnerState.InProgress) + { + CreateRegion(); + FullSpawn(); + + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0), Slice); + } + else + { + ClearCreatures(); + ClearTraps(); + DestroyRegion(); + + m_Timer?.Stop(); + + m_Timer = null; + } + } + } + + public List Creatures{ get; set; } + + public List Traps{ get; set; } + + public Region Region{ get; set; } + + public override string DefaultName => "doom spawner"; + + public virtual void CreateRegion() + { + if (Region != null) + return; - int hue = 0; - bool lockDoors = ( m_State == GauntletSpawnerState.InProgress ); - - switch ( m_State ) - { - case GauntletSpawnerState.InSequence: hue = InSequenceItemHue; break; - case GauntletSpawnerState.InProgress: hue = InProgressItemHue; break; - case GauntletSpawnerState.Completed: hue = CompletedItemHue; break; - } + Map map = Map; - if ( Door != null ) - { - Door.Hue = hue; - Door.Locked = lockDoors; + if (map == null || map == Map.Internal) + return; - if ( lockDoors ) - { - Door.KeyValue = Key.RandomValue(); - Door.Open = false; - } - - if ( Door.Link != null ) - { - Door.Link.Hue = hue; - Door.Link.Locked = lockDoors; - - if ( lockDoors ) - { - Door.Link.KeyValue = Key.RandomValue(); - Door.Open = false; - } - } - } - - if ( Addon != null ) - Addon.Hue = hue; - - if ( m_State == GauntletSpawnerState.InProgress ) - { - CreateRegion(); - FullSpawn(); + Region = new GauntletRegion(this, map); + } - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ), Slice ); - } - else - { - ClearCreatures(); - ClearTraps(); - DestroyRegion(); + public virtual void DestroyRegion() + { + Region?.Unregister(); - m_Timer?.Stop(); + Region = null; + } - m_Timer = null; - } - } - } + public virtual int ComputeTrapCount() + { + int area = RegionBounds.Width * RegionBounds.Height; - private Timer m_Timer; + return area / 100; + } - public List Creatures { get; set; } + public virtual void ClearTraps() + { + for (int i = 0; i < Traps.Count; ++i) + Traps[i].Delete(); - public List Traps { get; set; } + Traps.Clear(); + } - public Region Region { get; set; } + public virtual void SpawnTrap() + { + Map map = Map; - public virtual void CreateRegion() - { - if ( Region != null ) - return; + if (map == null) + return; - Map map = Map; + BaseTrap trap = null; - if ( map == null || map == Map.Internal ) - return; + int random = Utility.Random(100); - Region = new GauntletRegion( this, map ); - } + if (22 > random) + trap = new SawTrap(Utility.RandomBool() ? SawTrapType.WestFloor : SawTrapType.NorthFloor); + else if (44 > random) + trap = new SpikeTrap(Utility.RandomBool() ? SpikeTrapType.WestFloor : SpikeTrapType.NorthFloor); + else if (66 > random) + trap = new GasTrap(Utility.RandomBool() ? GasTrapType.NorthWall : GasTrapType.WestWall); + else if (88 > random) + trap = new FireColumnTrap(); + else + trap = new MushroomTrap(); - public virtual void DestroyRegion() - { - Region?.Unregister(); + if (trap == null) + return; - Region = null; - } + if (trap is FireColumnTrap || trap is MushroomTrap) + trap.Hue = 0x451; - public virtual int ComputeTrapCount() - { - int area = RegionBounds.Width * RegionBounds.Height; + // try 10 times to find a valid location + for (int i = 0; i < 10; ++i) + { + int x = Utility.Random(RegionBounds.X, RegionBounds.Width); + int y = Utility.Random(RegionBounds.Y, RegionBounds.Height); + int z = Z; - return area / 100; - } + if (!map.CanFit(x, y, z, 16, false, false)) + z = map.GetAverageZ(x, y); - public virtual void ClearTraps() - { - for ( int i = 0; i < Traps.Count; ++i ) - Traps[i].Delete(); + if (!map.CanFit(x, y, z, 16, false, false)) + continue; - Traps.Clear(); - } + trap.MoveToWorld(new Point3D(x, y, z), map); + Traps.Add(trap); - public virtual void SpawnTrap() - { - Map map = Map; + return; + } - if ( map == null ) - return; + trap.Delete(); + } - BaseTrap trap = null; + public virtual int ComputeSpawnCount() + { + int playerCount = 0; - int random = Utility.Random( 100 ); + Map map = Map; - if ( 22 > random ) - trap = new SawTrap( Utility.RandomBool() ? SawTrapType.WestFloor : SawTrapType.NorthFloor ); - else if ( 44 > random ) - trap = new SpikeTrap( Utility.RandomBool() ? SpikeTrapType.WestFloor : SpikeTrapType.NorthFloor ); - else if ( 66 > random ) - trap = new GasTrap( Utility.RandomBool() ? GasTrapType.NorthWall : GasTrapType.WestWall ); - else if ( 88 > random ) - trap = new FireColumnTrap(); - else - trap = new MushroomTrap(); + if (map != null) + { + Point3D loc = GetWorldLocation(); - if ( trap == null ) - return; + Region reg = Region.Find(loc, map).GetRegion("Doom Gauntlet"); - if ( trap is FireColumnTrap || trap is MushroomTrap ) - trap.Hue = 0x451; + if (reg != null) + playerCount = reg.GetPlayerCount(); + } - // try 10 times to find a valid location - for ( int i = 0; i < 10; ++i ) - { - int x = Utility.Random( RegionBounds.X, RegionBounds.Width ); - int y = Utility.Random( RegionBounds.Y, RegionBounds.Height ); - int z = Z; + if (playerCount == 0 && Region != null) + playerCount = Region.GetPlayerCount(); - if ( !map.CanFit( x, y, z, 16, false, false ) ) - z = map.GetAverageZ( x, y ); + int count = (playerCount + PlayersPerSpawn - 1) / PlayersPerSpawn; - if ( !map.CanFit( x, y, z, 16, false, false ) ) - continue; + if (count < 1) + count = 1; - trap.MoveToWorld( new Point3D( x, y, z ), map ); - Traps.Add( trap ); + return count; + } - return; - } + public virtual void ClearCreatures() + { + for (int i = 0; i < Creatures.Count; ++i) + Creatures[i].Delete(); - trap.Delete(); - } + Creatures.Clear(); + } - public virtual int ComputeSpawnCount() - { - int playerCount = 0; + public virtual void FullSpawn() + { + ClearCreatures(); - Map map = Map; + int count = ComputeSpawnCount(); - if ( map != null ) - { - Point3D loc = GetWorldLocation(); + for (int i = 0; i < count; ++i) + Spawn(); - Region reg = Region.Find( loc, map ).GetRegion( "Doom Gauntlet" ); + ClearTraps(); - if ( reg != null ) - playerCount = reg.GetPlayerCount(); - } + count = ComputeTrapCount(); - if ( playerCount == 0 && Region != null ) - playerCount = Region.GetPlayerCount(); + for (int i = 0; i < count; ++i) + SpawnTrap(); + } - int count = (playerCount + PlayersPerSpawn - 1) / PlayersPerSpawn; + public virtual void Spawn() + { + try + { + if (TypeName == null) + return; - if ( count < 1 ) - count = 1; + Type type = ScriptCompiler.FindTypeByName(TypeName, true); - return count; - } + if (type == null) + return; - public virtual void ClearCreatures() - { - for ( int i = 0; i < Creatures.Count; ++i ) - Creatures[i].Delete(); + object obj = Activator.CreateInstance(type); - Creatures.Clear(); - } + if (obj is Item item) + { + item.Delete(); + } + else if (obj is Mobile mob) + { + mob.MoveToWorld(GetWorldLocation(), Map); - public virtual void FullSpawn() - { - ClearCreatures(); + Creatures.Add(mob); + } + } + catch + { + } + } - int count = ComputeSpawnCount(); + public virtual void RecurseReset() + { + if (m_State != GauntletSpawnerState.InSequence) + { + State = GauntletSpawnerState.InSequence; - for ( int i = 0; i < count; ++i ) - Spawn(); + if (Sequence != null && !Sequence.Deleted) + Sequence.RecurseReset(); + } + } - ClearTraps(); + public virtual void Slice() + { + if (m_State != GauntletSpawnerState.InProgress) + return; - count = ComputeTrapCount(); + int count = ComputeSpawnCount(); - for ( int i = 0; i < count; ++i ) - SpawnTrap(); - } + for (int i = Creatures.Count; i < count; ++i) + Spawn(); - public virtual void Spawn() - { - try - { - if ( TypeName == null ) - return; + if (HasCompleted) + { + State = GauntletSpawnerState.Completed; - Type type = ScriptCompiler.FindTypeByName( TypeName, true ); + if (Sequence != null && !Sequence.Deleted) + { + if (Sequence.State == GauntletSpawnerState.Completed) + RecurseReset(); - if ( type == null ) - return; + Sequence.State = GauntletSpawnerState.InProgress; + } + } + } - object obj = Activator.CreateInstance( type ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( obj is Item item ) - item.Delete(); - else if ( obj is Mobile mob ) - { - mob.MoveToWorld( GetWorldLocation(), Map ); + writer.Write(1); // version - Creatures.Add( mob ); - } - } - catch - { - } - } + writer.Write(RegionBounds); - public virtual void RecurseReset() - { - if ( m_State != GauntletSpawnerState.InSequence ) - { - State = GauntletSpawnerState.InSequence; + writer.WriteItemList(Traps, false); - if ( Sequence != null && !Sequence.Deleted ) - Sequence.RecurseReset(); - } - } + writer.Write(Creatures, false); - public virtual void Slice() - { - if ( m_State != GauntletSpawnerState.InProgress ) - return; + writer.Write(TypeName); + writer.WriteItem(Door); + writer.WriteItem(Addon); + writer.WriteItem(Sequence); - int count = ComputeSpawnCount(); + writer.Write((int)m_State); + } - for ( int i = Creatures.Count; i < count; ++i ) - Spawn(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( HasCompleted ) - { - State = GauntletSpawnerState.Completed; + int version = reader.ReadInt(); - if ( Sequence != null && !Sequence.Deleted ) - { - if ( Sequence.State == GauntletSpawnerState.Completed ) - RecurseReset(); + switch (version) + { + case 1: + { + RegionBounds = reader.ReadRect2D(); + Traps = reader.ReadStrongItemList(); - Sequence.State = GauntletSpawnerState.InProgress; - } - } - } + goto case 0; + } + case 0: + { + if (version < 1) + { + Traps = new List(); + RegionBounds = new Rectangle2D(X - 40, Y - 40, 80, 80); + } - public override string DefaultName => "doom spawner"; + Creatures = reader.ReadStrongMobileList(); - [Constructible] - public GauntletSpawner() : this( null ) - { - } + TypeName = reader.ReadString(); + Door = reader.ReadItem(); + ; + Addon = reader.ReadItem(); + ; + Sequence = reader.ReadItem(); - [Constructible] - public GauntletSpawner( string typeName ) : base( 0x36FE ) - { - Visible = false; - Movable = false; + State = (GauntletSpawnerState)reader.ReadInt(); - TypeName = typeName; - Creatures = new List(); - Traps = new List(); - } + break; + } + } + } - public GauntletSpawner( Serial serial ) : base( serial ) - { - } + public static void Initialize() + { + CommandSystem.Register("GenGauntlet", AccessLevel.Administrator, GenGauntlet_OnCommand); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public static void CreateTeleporter(int xFrom, int yFrom, int xTo, int yTo) + { + Static telePad = new Static(0x1822); + Teleporter teleItem = new Teleporter(new Point3D(xTo, yTo, -1), Map.Malas, false); - writer.Write( (int) 1 ); // version + telePad.Hue = 0x482; + telePad.MoveToWorld(new Point3D(xFrom, yFrom, -1), Map.Malas); - writer.Write( RegionBounds ); + teleItem.MoveToWorld(new Point3D(xFrom, yFrom, -1), Map.Malas); - writer.WriteItemList( Traps, false ); + teleItem.SourceEffect = true; + teleItem.DestEffect = true; + teleItem.SoundID = 0x1FE; + } - writer.Write( Creatures, false ); + public static BaseDoor CreateDoorSet(int xDoor, int yDoor, bool doorEastToWest, int hue) + { + BaseDoor hiDoor = new MetalDoor(doorEastToWest ? DoorFacing.NorthCCW : DoorFacing.WestCW); + BaseDoor loDoor = new MetalDoor(doorEastToWest ? DoorFacing.SouthCW : DoorFacing.EastCCW); - writer.Write( TypeName ); - writer.WriteItem( Door ); - writer.WriteItem( Addon ); - writer.WriteItem( Sequence ); + hiDoor.MoveToWorld(new Point3D(xDoor, yDoor, -1), Map.Malas); + loDoor.MoveToWorld(new Point3D(xDoor + (doorEastToWest ? 0 : 1), yDoor + (doorEastToWest ? 1 : 0), -1), + Map.Malas); - writer.Write( (int) m_State ); - } + hiDoor.Link = loDoor; + loDoor.Link = hiDoor; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + hiDoor.Hue = hue; + loDoor.Hue = hue; - int version = reader.ReadInt(); + return hiDoor; + } - switch ( version ) - { - case 1: - { - RegionBounds = reader.ReadRect2D(); - Traps = reader.ReadStrongItemList(); + public static GauntletSpawner CreateSpawner(string typeName, int xSpawner, int ySpawner, int xDoor, int yDoor, + int xPentagram, int yPentagram, bool doorEastToWest, int xStart, int yStart, int xWidth, int yHeight) + { + GauntletSpawner spawner = new GauntletSpawner(typeName); - goto case 0; - } - case 0: - { - if ( version < 1 ) - { - Traps = new List(); - RegionBounds = new Rectangle2D( X - 40, Y - 40, 80, 80 ); - } + spawner.MoveToWorld(new Point3D(xSpawner, ySpawner, -1), Map.Malas); - Creatures = reader.ReadStrongMobileList(); + if (xDoor > 0 && yDoor > 0) + spawner.Door = CreateDoorSet(xDoor, yDoor, doorEastToWest, 0); - TypeName = reader.ReadString(); - Door = reader.ReadItem(); ; - Addon = reader.ReadItem(); ; - Sequence = reader.ReadItem(); + spawner.RegionBounds = new Rectangle2D(xStart, yStart, xWidth, yHeight); - State = (GauntletSpawnerState)reader.ReadInt(); + if (xPentagram > 0 && yPentagram > 0) + { + PentagramAddon pentagram = new PentagramAddon(); - break; - } - } - } + pentagram.MoveToWorld(new Point3D(xPentagram, yPentagram, -1), Map.Malas); - public static void Initialize() - { - CommandSystem.Register( "GenGauntlet", AccessLevel.Administrator, GenGauntlet_OnCommand ); - } + spawner.Addon = pentagram; + } - public static void CreateTeleporter( int xFrom, int yFrom, int xTo, int yTo ) - { - Static telePad = new Static( 0x1822 ); - Teleporter teleItem = new Teleporter( new Point3D( xTo, yTo, -1 ), Map.Malas, false ); + return spawner; + } - telePad.Hue = 0x482; - telePad.MoveToWorld( new Point3D( xFrom, yFrom, -1 ), Map.Malas ); + public static void CreatePricedHealer(int price, int x, int y) + { + PricedHealer healer = new PricedHealer(price); - teleItem.MoveToWorld( new Point3D( xFrom, yFrom, -1 ), Map.Malas ); + healer.MoveToWorld(new Point3D(x, y, -1), Map.Malas); - teleItem.SourceEffect = true; - teleItem.DestEffect = true; - teleItem.SoundID = 0x1FE; - } + healer.Home = healer.Location; + healer.RangeHome = 5; + } - public static BaseDoor CreateDoorSet( int xDoor, int yDoor, bool doorEastToWest, int hue ) - { - BaseDoor hiDoor = new MetalDoor( doorEastToWest ? DoorFacing.NorthCCW : DoorFacing.WestCW ); - BaseDoor loDoor = new MetalDoor( doorEastToWest ? DoorFacing.SouthCW : DoorFacing.EastCCW ); + public static void CreateMorphItem(int x, int y, int inactiveItemID, int activeItemID, int range, int hue) + { + MorphItem item = new MorphItem(inactiveItemID, activeItemID, range); - hiDoor.MoveToWorld( new Point3D( xDoor, yDoor, -1 ), Map.Malas ); - loDoor.MoveToWorld( new Point3D( xDoor + (doorEastToWest ? 0 : 1), yDoor + (doorEastToWest ? 1 : 0), -1 ), Map.Malas ); + item.Hue = hue; + item.MoveToWorld(new Point3D(x, y, -1), Map.Malas); + } - hiDoor.Link = loDoor; - loDoor.Link = hiDoor; + public static void CreateVarietyDealer(int x, int y) + { + VarietyDealer dealer = new VarietyDealer(); - hiDoor.Hue = hue; - loDoor.Hue = hue; + /* Begin outfit */ + dealer.Name = "Nix"; + dealer.Title = "the Variety Dealer"; - return hiDoor; - } + dealer.Body = 400; + dealer.Female = false; + dealer.Hue = 0x8835; - public static GauntletSpawner CreateSpawner( string typeName, int xSpawner, int ySpawner, int xDoor, int yDoor, int xPentagram, int yPentagram, bool doorEastToWest, int xStart, int yStart, int xWidth, int yHeight ) - { - GauntletSpawner spawner = new GauntletSpawner( typeName ); + List items = new List(dealer.Items); - spawner.MoveToWorld( new Point3D( xSpawner, ySpawner, -1 ), Map.Malas ); + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; - if ( xDoor > 0 && yDoor > 0 ) - spawner.Door = CreateDoorSet( xDoor, yDoor, doorEastToWest, 0 ); + if (item.Layer != Layer.ShopBuy && item.Layer != Layer.ShopResale && item.Layer != Layer.ShopSell) + item.Delete(); + } - spawner.RegionBounds = new Rectangle2D( xStart, yStart, xWidth, yHeight ); + dealer.HairItemID = 0x2049; // Pig Tails + dealer.HairHue = 0x482; - if ( xPentagram > 0 && yPentagram > 0 ) - { - PentagramAddon pentagram = new PentagramAddon(); + dealer.FacialHairItemID = 0x203E; + dealer.FacialHairHue = 0x482; - pentagram.MoveToWorld( new Point3D( xPentagram, yPentagram, -1 ), Map.Malas ); + dealer.AddItem(new FloppyHat(1)); + dealer.AddItem(new Robe(1)); - spawner.Addon = pentagram; - } + dealer.AddItem(new LanternOfSouls()); - return spawner; - } + dealer.AddItem(new Sandals(0x482)); + /* End outfit */ - public static void CreatePricedHealer( int price, int x, int y ) - { - PricedHealer healer = new PricedHealer( price ); + dealer.MoveToWorld(new Point3D(x, y, -1), Map.Malas); - healer.MoveToWorld( new Point3D( x, y, -1 ), Map.Malas ); + dealer.Home = dealer.Location; + dealer.RangeHome = 2; + } - healer.Home = healer.Location; - healer.RangeHome = 5; - } + public static void GenGauntlet_OnCommand(CommandEventArgs e) + { + /* Begin healer room */ + CreatePricedHealer(5000, 387, 400); + CreateTeleporter(390, 407, 394, 405); - public static void CreateMorphItem( int x, int y, int inactiveItemID, int activeItemID, int range, int hue ) - { - MorphItem item = new MorphItem( inactiveItemID, activeItemID, range ); + BaseDoor healerDoor = CreateDoorSet(393, 404, true, 0x44E); - item.Hue = hue; - item.MoveToWorld( new Point3D( x, y, -1 ), Map.Malas ); - } + healerDoor.Locked = true; + healerDoor.KeyValue = Key.RandomValue(); - public static void CreateVarietyDealer( int x, int y ) - { - VarietyDealer dealer = new VarietyDealer(); + if (healerDoor.Link != null) + { + healerDoor.Link.Locked = true; + healerDoor.Link.KeyValue = Key.RandomValue(); + } + /* End healer room */ - /* Begin outfit */ - dealer.Name = "Nix"; - dealer.Title = "the Variety Dealer"; + /* Begin supply room */ + CreateMorphItem(433, 371, 0x29F, 0x116, 3, 0x44E); + CreateMorphItem(433, 372, 0x29F, 0x115, 3, 0x44E); - dealer.Body = 400; - dealer.Female = false; - dealer.Hue = 0x8835; + CreateVarietyDealer(492, 369); - List items = new List( dealer.Items ); + for (int x = 434; x <= 478; ++x) + for (int y = 371; y <= 372; ++y) + { + Static item = new Static(0x524); - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; + item.Hue = 1; + item.MoveToWorld(new Point3D(x, y, -1), Map.Malas); + } + /* End supply room */ - if ( item.Layer != Layer.ShopBuy && item.Layer != Layer.ShopResale && item.Layer != Layer.ShopSell ) - item.Delete(); - } + /* Begin gauntlet cycle */ + CreateTeleporter(471, 428, 474, 428); + CreateTeleporter(462, 494, 462, 498); + CreateTeleporter(403, 502, 399, 506); + CreateTeleporter(357, 476, 356, 480); + CreateTeleporter(361, 433, 357, 434); - dealer.HairItemID = 0x2049; // Pig Tails - dealer.HairHue = 0x482; + GauntletSpawner sp1 = CreateSpawner("DarknightCreeper", 491, 456, 473, 432, 417, 426, true, 473, 412, 39, 60); + GauntletSpawner sp2 = CreateSpawner("FleshRenderer", 482, 520, 468, 496, 426, 422, false, 448, 496, 56, 48); + GauntletSpawner sp3 = CreateSpawner("Impaler", 406, 538, 408, 504, 432, 430, false, 376, 504, 64, 48); + GauntletSpawner sp4 = CreateSpawner("ShadowKnight", 335, 512, 360, 478, 424, 439, false, 300, 478, 72, 64); + GauntletSpawner sp5 = CreateSpawner("AbysmalHorror", 326, 433, 360, 429, 416, 435, true, 300, 408, 60, 56); + GauntletSpawner sp6 = CreateSpawner("DemonKnight", 423, 430, 0, 0, 423, 430, true, 392, 392, 72, 96); - dealer.FacialHairItemID = 0x203E; - dealer.FacialHairHue = 0x482; + sp1.Sequence = sp2; + sp2.Sequence = sp3; + sp3.Sequence = sp4; + sp4.Sequence = sp5; + sp5.Sequence = sp6; + sp6.Sequence = sp1; - dealer.AddItem( new FloppyHat( 1 ) ); - dealer.AddItem( new Robe( 1 ) ); + sp1.State = GauntletSpawnerState.InProgress; + /* End gauntlet cycle */ - dealer.AddItem( new LanternOfSouls() ); + /* Begin exit gate */ + ConfirmationMoongate gate = new ConfirmationMoongate(); - dealer.AddItem( new Sandals( 0x482 ) ); - /* End outfit */ + gate.Dispellable = false; - dealer.MoveToWorld( new Point3D( x, y, -1 ), Map.Malas ); + gate.Target = new Point3D(2350, 1270, -85); + gate.TargetMap = Map.Malas; - dealer.Home = dealer.Location; - dealer.RangeHome = 2; - } + gate.GumpWidth = 420; + gate.GumpHeight = 280; - public static void GenGauntlet_OnCommand( CommandEventArgs e ) - { - /* Begin healer room */ - CreatePricedHealer( 5000, 387, 400 ); - CreateTeleporter( 390, 407, 394, 405 ); + gate.MessageColor = 0x7F00; + gate.MessageNumber = 1062109; // You are about to exit Dungeon Doom. Do you wish to continue? - BaseDoor healerDoor = CreateDoorSet( 393, 404, true, 0x44E ); + gate.TitleColor = 0x7800; + gate.TitleNumber = 1062108; // Please verify... - healerDoor.Locked = true; - healerDoor.KeyValue = Key.RandomValue(); + gate.Hue = 0x44E; - if ( healerDoor.Link != null ) - { - healerDoor.Link.Locked = true; - healerDoor.Link.KeyValue = Key.RandomValue(); - } - /* End healer room */ + gate.MoveToWorld(new Point3D(433, 326, 4), Map.Malas); + /* End exit gate */ + } + } - /* Begin supply room */ - CreateMorphItem( 433, 371, 0x29F, 0x116, 3, 0x44E ); - CreateMorphItem( 433, 372, 0x29F, 0x115, 3, 0x44E ); - CreateVarietyDealer( 492, 369 ); + public class GauntletRegion : BaseRegion + { + private GauntletSpawner m_Spawner; - for ( int x = 434; x <= 478; ++x ) - { - for ( int y = 371; y <= 372; ++y ) - { - Static item = new Static( 0x524 ); + public GauntletRegion(GauntletSpawner spawner, Map map) + : base(null, map, Find(spawner.Location, spawner.Map), spawner.RegionBounds) + { + m_Spawner = spawner; - item.Hue = 1; - item.MoveToWorld( new Point3D( x, y, -1 ), Map.Malas ); - } - } - /* End supply room */ + GoLocation = spawner.Location; - /* Begin gauntlet cycle */ - CreateTeleporter( 471, 428, 474, 428 ); - CreateTeleporter( 462, 494, 462, 498 ); - CreateTeleporter( 403, 502, 399, 506 ); - CreateTeleporter( 357, 476, 356, 480 ); - CreateTeleporter( 361, 433, 357, 434 ); + Register(); + } - GauntletSpawner sp1 = CreateSpawner( "DarknightCreeper", 491, 456, 473, 432, 417, 426, true, 473, 412, 39, 60 ); - GauntletSpawner sp2 = CreateSpawner( "FleshRenderer", 482, 520, 468, 496, 426, 422, false, 448, 496, 56, 48 ); - GauntletSpawner sp3 = CreateSpawner( "Impaler", 406, 538, 408, 504, 432, 430, false, 376, 504, 64, 48 ); - GauntletSpawner sp4 = CreateSpawner( "ShadowKnight", 335, 512, 360, 478, 424, 439, false, 300, 478, 72, 64 ); - GauntletSpawner sp5 = CreateSpawner( "AbysmalHorror", 326, 433, 360, 429, 416, 435, true, 300, 408, 60, 56 ); - GauntletSpawner sp6 = CreateSpawner( "DemonKnight", 423, 430, 0, 0, 423, 430, true, 392, 392, 72, 96 ); + public override void AlterLightLevel(Mobile m, ref int global, ref int personal) + { + global = 12; + } - sp1.Sequence = sp2; - sp2.Sequence = sp3; - sp3.Sequence = sp4; - sp4.Sequence = sp5; - sp5.Sequence = sp6; - sp6.Sequence = sp1; + public override void OnEnter(Mobile m) + { + } - sp1.State = GauntletSpawnerState.InProgress; - /* End gauntlet cycle */ - - /* Begin exit gate */ - ConfirmationMoongate gate = new ConfirmationMoongate(); - - gate.Dispellable = false; - - gate.Target = new Point3D( 2350, 1270, -85 ); - gate.TargetMap = Map.Malas; - - gate.GumpWidth = 420; - gate.GumpHeight = 280; - - gate.MessageColor = 0x7F00; - gate.MessageNumber = 1062109; // You are about to exit Dungeon Doom. Do you wish to continue? - - gate.TitleColor = 0x7800; - gate.TitleNumber = 1062108; // Please verify... - - gate.Hue = 0x44E; - - gate.MoveToWorld( new Point3D( 433, 326, 4 ), Map.Malas ); - /* End exit gate */ - } - } - - - public class GauntletRegion : BaseRegion - { - private GauntletSpawner m_Spawner; - - public GauntletRegion( GauntletSpawner spawner, Map map ) - : base( null, map, Find( spawner.Location, spawner.Map ), spawner.RegionBounds ) - { - m_Spawner = spawner; - - GoLocation = spawner.Location; - - Register(); - } - - public override void AlterLightLevel( Mobile m, ref int global, ref int personal ) - { - global = 12; - } - - public override void OnEnter( Mobile m ) - { - } - - public override void OnExit( Mobile m ) - { - } - } -} + public override void OnExit(Mobile m) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleController.cs b/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleController.cs index 5fec79208..2c555c966 100644 --- a/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleController.cs +++ b/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleController.cs @@ -1,714 +1,651 @@ using System; -using Server.Spells; -using Server.Network; -using Server.Mobiles; -using Server.Commands; using System.Collections.Generic; +using Server.Commands; +using Server.Mobiles; +using Server.Network; +using Server.Spells; - /* +/* this is From me to you, Under no terms, Conditions... K? to apply you just simply Unpatch/delete, Stick these in, Same location.. Restart */ namespace Server.Engines.Doom { - public class LeverPuzzleController : Item - { - private static bool installed; - - private List m_Levers; - private List m_Teles; - private List m_Statues; - private List m_Tiles; - private LampRoomBox m_Box; - private Region m_LampRoom; - - private Timer m_Timer; - private Timer l_Timer; - - public static void Initialize() - { - CommandSystem.Register( "GenLeverPuzzle", AccessLevel.Administrator, GenLampPuzzle_OnCommand ); - } - - [Usage( "GenLeverPuzzle" )] - [Description( "Generates lamp room and lever puzzle in doom." )] - public static void GenLampPuzzle_OnCommand( CommandEventArgs e ) - { - foreach ( Item item in Map.Malas.GetItemsInRange( lp_Center, 0 ) ) - { - if ( item is LeverPuzzleController ) - { - e.Mobile.SendMessage( "Lamp room puzzle already exists: please delete the existing controller first ..." ); - return; - } - } - e.Mobile.SendMessage( "Generating Lamp Room puzzle..." ); - new LeverPuzzleController().MoveToWorld( lp_Center, Map.Malas ); - - if ( !installed ) - e.Mobile.SendMessage( "There was a problem generating the puzzle." ); - else - e.Mobile.SendMessage( "Lamp room puzzle successfully generated." ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public ushort MyKey { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public ushort TheirKey { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Enabled { get; set; } - - public Mobile Successful { get; private set; } - - public bool CircleComplete - { - get /* OSI: all 5 must be occupied */ - { - for (int i=0; i<5; i++) - { - if ( GetOccupant( i ) == null) - { - return false; - } - } - return true; - } - } - - public LeverPuzzleController() : base( 0x1822 ) - { - Movable=false; - Hue=0x4c; - installed=true; - int i=0; - - m_Levers = new List(); /* codes are 0x1 shifted left x # of bits, easily handled here */ - for (; i<4; i++) - m_Levers.Add( AddLeverPuzzlePart( TA[i], new LeverPuzzleLever( (ushort)(1<(); - for (; i<9; i++) - m_Tiles.Add( new LeverPuzzleRegion( this, TA[i] )); - - m_Teles = new List(); - for (; i<15; i++) - m_Teles.Add( AddLeverPuzzlePart( TA[i], new LampRoomTeleporter( TA[++i] ))); - - m_Statues = new List(); - for (; i<19; i++) - m_Statues.Add( AddLeverPuzzlePart( TA[i], new LeverPuzzleStatue( TA[++i], this ))); - - if (!installed) - Delete(); - else - Enabled=true; - - m_Box = (LampRoomBox)AddLeverPuzzlePart( TA[i], new LampRoomBox( this )); - m_LampRoom = new LampRoomRegion( this ); - GenKey(); - } - - public static Item AddLeverPuzzlePart( int[] Loc, Item newitem ) - { - if ( newitem == null || newitem.Deleted ) - { - installed=false; - } - else - { - newitem.MoveToWorld( new Point3D(Loc[0], Loc[1], Loc[2]), Map.Malas ); - } - return newitem; - } - - public override void OnDelete() - { - KillTimers(); - base.OnDelete(); - } - public override void OnAfterDelete() - { - NukeItemList( m_Teles ); - NukeItemList( m_Statues ); - NukeItemList( m_Levers ); - - m_LampRoom?.Unregister(); - if ( m_Tiles != null ) - { - foreach( Region region in m_Tiles ) - { - region.Unregister(); - } - } - if ( m_Box != null && !m_Box.Deleted ) - { - m_Box.Delete(); - } - } - - public static void NukeItemList( List list ) - { - if ( list != null && list.Count != 0 ) - { - foreach ( Item item in list ) - { - if ( item != null && !item.Deleted ) - { - item.Delete(); - } - } - } - } - - public virtual PlayerMobile GetOccupant( int index ) - { - LeverPuzzleRegion region = (LeverPuzzleRegion)m_Tiles[index]; - - if ( region?.Occupant != null && region.Occupant.Alive ) - { - return (PlayerMobile)region.Occupant; - } - return null; - } - - public virtual LeverPuzzleStatue GetStatue( int index ) - { - LeverPuzzleStatue statue = (LeverPuzzleStatue)m_Statues[index]; - - if ( statue != null && !statue.Deleted ) - { - return statue; - } - return null; - } - - public virtual LeverPuzzleLever GetLever( int index ) - { - LeverPuzzleLever lever = (LeverPuzzleLever)m_Levers[index]; - - if ( lever != null && !lever.Deleted ) - { - return lever; - } - return null; - } - - public virtual void PuzzleStatus( int message, string fstring ) - { - for( int i=0; i<2; i++) - { - Item s; - if (( s = GetStatue( i )) != null ) - { - s.PublicOverheadMessage( MessageType.Regular, 0x3B2, message, fstring ); - } - } - } - - public virtual void ResetPuzzle() - { - PuzzleStatus( 1062053, null ); - ResetLevers(); - } - - public virtual void ResetLevers() - { - for(int i=0;i<4; i++) - { - Item l; - if (( l = GetLever( i )) != null ) - { - l.ItemID=0x108E; - Effects.PlaySound( l.Location, Map, 0x3E8 ); - } - } - TheirKey^=TheirKey; - } - - public virtual void KillTimers () - { - if ( l_Timer != null && l_Timer.Running ) - { - l_Timer.Stop(); - } - if ( m_Timer != null && m_Timer.Running ) - { - m_Timer.Stop(); - } - } - - public virtual void RemoveSuccessful() - { - Successful=null; - } - - public virtual void LeverPulled( ushort code ) - { - int Correct=0; - Mobile m_Player; - - KillTimers(); - - /* if one bit in each of the four nibbles is set, this is false */ - - if ( (TheirKey=(ushort)(code|(TheirKey<<=4))) < 0x0FFF ) - { - l_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 30.0 ), ResetPuzzle); - return; - } - - if ( !CircleComplete ) - { - PuzzleStatus( 1050004, null ); // The circle is the key... - } - else - { - if ( TheirKey == MyKey ) - { - GenKey(); - if (( Successful = ( m_Player=GetOccupant( 0 ))) != null ) - { - SendLocationEffect( lp_Center, 0x1153, 0, 60, 1 ); - PlaySounds( lp_Center, cs1 ); - - Effects.SendBoltEffect( m_Player, true ); - m_Player.MoveToWorld( lr_Enter, Map.Malas ); - - m_Timer = new LampRoomTimer( this ); - m_Timer.Start(); - Enabled = false; - } - } - else - { - for(int i=0; i<16; i++) /* Count matching SET bits, ie correct codes */ - { - if ( (((MyKey>>i)&1)==1)&&(((TheirKey>>i)&1)==1) ) - { - Correct++; - } - } - - PuzzleStatus( Statue_Msg[Correct], (Correct>0) ? Correct.ToString() : null ); - - for (int i=0; i<5; i++) - { - if (( m_Player=GetOccupant( i )) != null ) - { - Timer smash = new RockTimer( m_Player, this ); - smash.Start(); - } - } - } - } - ResetLevers(); - } - - public virtual void GenKey() /* Shuffle & build key */ - { - ushort tmp; int n, i; ushort[] CA = { 1,2,4,8 }; - for (i=0; i<4; i++) - { - n=(((n = Utility.Random(0,3))==i) ? n&~i : n ); /* if (i==n) { return pointless; } */ - tmp = CA[i]; - CA[i]=CA[n]; - CA[n]=tmp; - } - for(i=0; i<4; MyKey=(ushort)(CA[(i++)]|(MyKey<<=4))) {} - } - - public class RockTimer : Timer - { - private int Count; - private Mobile m_Player; - private LeverPuzzleController m_Controller; - - public RockTimer( Mobile player, LeverPuzzleController Controller ) - : base( TimeSpan.Zero, TimeSpan.FromSeconds( .25 ) ) - { - Count = 0; - m_Player=player; - m_Controller = Controller; - } - - private int Rock() - { - return 0x1363+Utility.Random( 0, 11 ); - } - - protected override void OnTick() - { - if ( m_Player == null || !(m_Player.Map == Map.Malas) ) - { - Stop(); - } - else - { - Count++; - if ( Count == 1 ) /* TODO consolidate */ - { - m_Player.Paralyze( TimeSpan.FromSeconds(2) ); - Effects.SendTargetEffect( m_Player, 0x11B7, 20, 10 ); - PlayerSendASCII( m_Player, 0 ); // You are pinned down ... - - PlaySounds( m_Player.Location, ( !m_Player.Female ) ? fs : ms ); - PlayEffect( ZAdjustedIEFromMobile( m_Player, 50 ), m_Player, 0x11B7, 20, false ); - } - else if ( Count == 2 ) - { - DoDamage( m_Player, 80, 90, false ); - Effects.SendTargetEffect( m_Player, 0x36BD, 20, 10 ); - PlaySounds( m_Player.Location, exp ); - PlayerSendASCII( m_Player, 1 ); // A speeding rock ... - - if ( AniSafe( m_Player )) - { - m_Player.Animate( 21, 10, 1, true, true, 0 ); - } - } - else if ( Count == 3 ) - { - Stop(); - - Effects.SendTargetEffect( m_Player, 0x36B0, 20, 10 ); - PlayerSendASCII( m_Player, 1 ); // A speeding rock ... - PlaySounds( m_Player.Location, ( !m_Player.Female ) ? fs2 : ms2 ); - - int j = Utility.Random(6,10); - for(int i=0; i mobiles = new List(); - foreach( Mobile m in m_IEntity.Map.GetMobilesInRange( m_IEntity.Location, 2 )) - { - mobiles.Add( m ); - } - for( int k=0; k mobiles = m_Controller.m_LampRoom.GetMobiles(); - - if ( ticks >= 71 || m_Controller.m_LampRoom.GetPlayerCount() == 0 ) - { - foreach ( Mobile mobile in mobiles ) - { - if ( mobile != null && !mobile.Deleted && !mobile.IsDeadBondedPet ) - { - mobile.Kill(); - } - } - m_Controller.Enabled=true; - Stop(); - } - else - { - if ( ticks % 12 == 0 ) - { - level++; - } - foreach ( Mobile mobile in mobiles ) - { - if ( IsValidDamagable( mobile ) ) - { - if ( ticks % 2 == 0 && level == 5 ) - { - if ( mobile.Player ) - { - mobile.Say( 1062092 ); - if ( AniSafe( mobile )) - { - mobile.Animate( 32, 5, 1, true, false, 0 ); - } - } - DoDamage( mobile, 15, 20, true ); - } - if ( Utility.Random( (int)(level & ~0xfffffffc), 3) == 3 ) - { - mobile.ApplyPoison( mobile, PA2[level] ); - } - if ( ticks % 12 == 0 && level > 0 && mobile.Player ) - { - mobile.SendLocalizedMessage( PA[level][0], null, PA[level][1] ); - } - } - } - for( int i=0; i<=level; i++ ) - { - SendLocationEffect( RandomPointIn( lr_Rect, -1 ), 0x36B0, Utility.Random( 150, 200 ), 0, PA[level][2] ); - } - } - } - } - - private static bool IsValidDamagable( Mobile m ) - { - if ( m != null && !m.Deleted ) - { - if ( m.Player && m.Alive ) - return true; - - return m is BaseCreature bc && (bc.Controlled || bc.Summoned) && !bc.IsDeadBondedPet; - } - return false; - } - - public static void MoveMobileOut( Mobile m ) - { - if ( m != null ) - { - if ( m is PlayerMobile && !m.Alive ) - { - if ( m.Corpse != null && !m.Corpse.Deleted ) - { - m.Corpse.MoveToWorld( lr_Exit, Map.Malas ); - } - } - BaseCreature.TeleportPets( m, lr_Exit, Map.Malas ); - m.Location = lr_Exit; - m.ProcessDelta(); - } - } - - public static bool AniSafe( Mobile m ) - { - return ( m != null && !TransformationSpellHelper.UnderTransformation( m ) && m.BodyMod == 0 && m.Alive ); - } - - public static IEntity ZAdjustedIEFromMobile( Mobile m, int ZDelta ) - { - return new Entity( Serial.Zero, new Point3D( m.X, m.Y, m.Z+ZDelta ), m.Map ); - } - - public static void DoDamage( Mobile m, int min, int max, bool poison ) - { - if ( m != null && !m.Deleted && m.Alive ) - { - int damage = Utility.Random(min,max); - AOS.Damage( m, damage,(poison) ? 0 : 100 , 0, 0,(poison) ? 100 : 0, 0 ); - } - } - - public static Point3D RandomPointIn( Point3D point, int range ) - { - return RandomPointIn( point.X-range, point.Y-range, range*2, range*2, point.Z ); - } - public static Point3D RandomPointIn( Rectangle2D rect, int z ) - { - return RandomPointIn( rect.X, rect.Y, rect.Height, rect.Width, z ); - } - public static Point3D RandomPointIn( int x, int y, int x2, int y2, int z ) - { - return new Point3D( Utility.Random( x, x2 ), Utility.Random( y, y2 ), z ); - } - - public static void PlaySounds( Point3D location, int[] sounds ) - { - foreach( int soundid in sounds ) - Effects.PlaySound( location, Map.Malas, soundid ); - } - - public static void PlayEffect( IEntity from, IEntity to, int itemid, int speed, bool explodes ) - { - Effects.SendMovingParticles( from, to, itemid, speed, 0, true, explodes, 2, 0, 0 ); - } - - public static void SendLocationEffect( IPoint3D p, int itemID, int speed, int duration, int hue ) - { - Effects.SendPacket( p, Map.Malas, new LocationEffect( p, itemID, speed, duration, hue, 0 ) ); - } - - public static void PlayerSendASCII( Mobile player, int index ) - { - player.Send( new AsciiMessage( Serial.MinusOne, 0xFFFF, MessageType.Label, MsgParams[index][0], MsgParams[index][1], null, Msgs[index] )); - } - - /* I cant find any better way to send "speech" using fonts other than default */ - public static void POHMessage( Mobile from, int index ) - { - Packet p = new AsciiMessage( from.Serial, from.Body, MessageType.Regular, MsgParams[index][0], MsgParams[index][1], from.Name, Msgs[index] ); - p.Acquire(); - foreach( NetState state in from.Map.GetClientsInRange( from.Location ) ) - state.Send( p ); - - Packet.Release( p ); - } - - public static string[] Msgs = - { - "You are pinned down by the weight of the boulder!!!", // 0 - "A speeding rock hits you in the head!", // 1 - "OUCH!" // 2 - }; - /* font&hue for above msgs. index matches */ - - public static int[][] MsgParams = - { - new[]{ 0x66d, 3 }, - new[]{ 0x66d, 3 }, - new[]{ 0x34, 3 } - }; - /* World data for items */ - - public static int[][] TA = - { - - new[]{316, 64, 5}, /* 3D Coords for levers */ - new[]{323, 58, 5}, - new[]{332, 63, 5}, - new[]{323, 71, 5}, - - new[]{324, 64}, /* 2D Coords for standing regions */ - new[]{316, 65}, - new[]{324, 58}, - new[]{332, 64}, - new[]{323, 72}, - - new[]{468, 92, -1}, new[]{0x181D, 0x482}, /* 3D coord, itemid+hue for L.R. teles */ - new[]{469, 92, -1}, new[]{0x1821, 0x3fd}, - new[]{470, 92, -1}, new[]{0x1825, 0x66d}, - - new[]{319, 70, 18}, new[]{0x12d8}, /* 3D coord, itemid for statues */ - new[]{329, 60, 18}, new[]{0x12d9}, - - new[]{469, 96, 6} /* 3D Coords for Fake Box */ - }; - - /* CLILOC data for statue "correct souls" messages */ - - public static int[] Statue_Msg = { 1050009, 1050007, 1050008, 1050008 }; - - /* Exit & Enter locations for the lamp room */ - - public static Point3D lr_Exit = new Point3D( 353, 172, -1 ); - public static Point3D lr_Enter = new Point3D( 467, 96, -1 ); - - /* "Center" location in puzzle */ - - public static Point3D lp_Center = new Point3D( 324, 64, -1 ); - - /* Lamp Room Area */ - - public static Rectangle2D lr_Rect = new Rectangle2D( 465, 92, 10, 10 ); - - /* Lamp Room area Poison message data */ - - public static int[][] PA = - { - new[]{ 0, 0, 0xA6 }, - new[]{ 1050001, 0x485, 0xAA }, - new[]{ 1050003, 0x485, 0xAC }, - new[]{ 1050056, 0x485, 0xA8 }, - new[]{ 1050057, 0x485, 0xA4 }, - new[]{ 1062091, 0x23F3, 0xAC } - }; - public static Poison[] PA2 = - { - Poison.Lesser, - Poison.Regular, - Poison.Greater, - Poison.Deadly, - Poison.Lethal, - Poison.Lethal - }; - - /* SOUNDS */ - - private static int[] fs={0x144, 0x154}; - private static int[] ms={0x144, 0x14B}; - private static int[] fs2={0x13F, 0x154}; - private static int[] ms2={0x13F, 0x14B}; - private static int[] cs1={0x244}; - private static int[] exp={0x307}; - - public LeverPuzzleController( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - writer.WriteItemList( m_Levers, true ); - writer.WriteItemList( m_Statues, true ); - writer.WriteItemList( m_Teles, true ); - writer.Write( m_Box ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Levers = reader.ReadStrongItemList(); - m_Statues = reader.ReadStrongItemList(); - m_Teles = reader.ReadStrongItemList(); - - m_Box = reader.ReadItem() as LampRoomBox; - - m_Tiles = new List(); - for (int i = 4; i<9; i++) - m_Tiles.Add( new LeverPuzzleRegion( this, TA[i] )); - - m_LampRoom = new LampRoomRegion( this ); - Enabled = true; - TheirKey = 0; - MyKey = 0; - GenKey(); - } - } -} - + public class LeverPuzzleController : Item + { + private static bool installed; + + public static string[] Msgs = + { + "You are pinned down by the weight of the boulder!!!", // 0 + "A speeding rock hits you in the head!", // 1 + "OUCH!" // 2 + }; + /* font&hue for above msgs. index matches */ + + public static int[][] MsgParams = + { + new[] { 0x66d, 3 }, + new[] { 0x66d, 3 }, + new[] { 0x34, 3 } + }; + /* World data for items */ + + public static int[][] TA = + { + new[] { 316, 64, 5 }, /* 3D Coords for levers */ + new[] { 323, 58, 5 }, + new[] { 332, 63, 5 }, + new[] { 323, 71, 5 }, + + new[] { 324, 64 }, /* 2D Coords for standing regions */ + new[] { 316, 65 }, + new[] { 324, 58 }, + new[] { 332, 64 }, + new[] { 323, 72 }, + + new[] { 468, 92, -1 }, new[] { 0x181D, 0x482 }, /* 3D coord, itemid+hue for L.R. teles */ + new[] { 469, 92, -1 }, new[] { 0x1821, 0x3fd }, + new[] { 470, 92, -1 }, new[] { 0x1825, 0x66d }, + + new[] { 319, 70, 18 }, new[] { 0x12d8 }, /* 3D coord, itemid for statues */ + new[] { 329, 60, 18 }, new[] { 0x12d9 }, + + new[] { 469, 96, 6 } /* 3D Coords for Fake Box */ + }; + + /* CLILOC data for statue "correct souls" messages */ + + public static int[] Statue_Msg = { 1050009, 1050007, 1050008, 1050008 }; + + /* Exit & Enter locations for the lamp room */ + + public static Point3D lr_Exit = new Point3D(353, 172, -1); + public static Point3D lr_Enter = new Point3D(467, 96, -1); + + /* "Center" location in puzzle */ + + public static Point3D lp_Center = new Point3D(324, 64, -1); + + /* Lamp Room Area */ + + public static Rectangle2D lr_Rect = new Rectangle2D(465, 92, 10, 10); + + /* Lamp Room area Poison message data */ + + public static int[][] PA = + { + new[] { 0, 0, 0xA6 }, + new[] { 1050001, 0x485, 0xAA }, + new[] { 1050003, 0x485, 0xAC }, + new[] { 1050056, 0x485, 0xA8 }, + new[] { 1050057, 0x485, 0xA4 }, + new[] { 1062091, 0x23F3, 0xAC } + }; + + public static Poison[] PA2 = + { + Poison.Lesser, + Poison.Regular, + Poison.Greater, + Poison.Deadly, + Poison.Lethal, + Poison.Lethal + }; + + /* SOUNDS */ + + private static int[] fs = { 0x144, 0x154 }; + private static int[] ms = { 0x144, 0x14B }; + private static int[] fs2 = { 0x13F, 0x154 }; + private static int[] ms2 = { 0x13F, 0x14B }; + private static int[] cs1 = { 0x244 }; + private static int[] exp = { 0x307 }; + private Timer l_Timer; + private LampRoomBox m_Box; + private Region m_LampRoom; + + private List m_Levers; + private List m_Statues; + private List m_Teles; + private List m_Tiles; + + private Timer m_Timer; + + public LeverPuzzleController() : base(0x1822) + { + Movable = false; + Hue = 0x4c; + installed = true; + int i = 0; + + m_Levers = new List(); /* codes are 0x1 shifted left x # of bits, easily handled here */ + for (; i < 4; i++) + m_Levers.Add(AddLeverPuzzlePart(TA[i], new LeverPuzzleLever((ushort)(1 << i), this))); + + m_Tiles = new List(); + for (; i < 9; i++) + m_Tiles.Add(new LeverPuzzleRegion(this, TA[i])); + + m_Teles = new List(); + for (; i < 15; i++) + m_Teles.Add(AddLeverPuzzlePart(TA[i], new LampRoomTeleporter(TA[++i]))); + + m_Statues = new List(); + for (; i < 19; i++) + m_Statues.Add(AddLeverPuzzlePart(TA[i], new LeverPuzzleStatue(TA[++i], this))); + + if (!installed) + Delete(); + else + Enabled = true; + + m_Box = (LampRoomBox)AddLeverPuzzlePart(TA[i], new LampRoomBox(this)); + m_LampRoom = new LampRoomRegion(this); + GenKey(); + } + + public LeverPuzzleController(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public ushort MyKey{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public ushort TheirKey{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Enabled{ get; set; } + + public Mobile Successful{ get; private set; } + + public bool CircleComplete + { + get /* OSI: all 5 must be occupied */ + { + for (int i = 0; i < 5; i++) + if (GetOccupant(i) == null) + return false; + return true; + } + } + + public static void Initialize() + { + CommandSystem.Register("GenLeverPuzzle", AccessLevel.Administrator, GenLampPuzzle_OnCommand); + } + + [Usage("GenLeverPuzzle")] + [Description("Generates lamp room and lever puzzle in doom.")] + public static void GenLampPuzzle_OnCommand(CommandEventArgs e) + { + foreach (Item item in Map.Malas.GetItemsInRange(lp_Center, 0)) + if (item is LeverPuzzleController) + { + e.Mobile.SendMessage("Lamp room puzzle already exists: please delete the existing controller first ..."); + return; + } + + e.Mobile.SendMessage("Generating Lamp Room puzzle..."); + new LeverPuzzleController().MoveToWorld(lp_Center, Map.Malas); + + if (!installed) + e.Mobile.SendMessage("There was a problem generating the puzzle."); + else + e.Mobile.SendMessage("Lamp room puzzle successfully generated."); + } + + public static Item AddLeverPuzzlePart(int[] Loc, Item newitem) + { + if (newitem == null || newitem.Deleted) + installed = false; + else + newitem.MoveToWorld(new Point3D(Loc[0], Loc[1], Loc[2]), Map.Malas); + return newitem; + } + + public override void OnDelete() + { + KillTimers(); + base.OnDelete(); + } + + public override void OnAfterDelete() + { + NukeItemList(m_Teles); + NukeItemList(m_Statues); + NukeItemList(m_Levers); + + m_LampRoom?.Unregister(); + if (m_Tiles != null) + foreach (Region region in m_Tiles) + region.Unregister(); + if (m_Box != null && !m_Box.Deleted) m_Box.Delete(); + } + + public static void NukeItemList(List list) + { + if (list != null && list.Count != 0) + foreach (Item item in list) + if (item != null && !item.Deleted) + item.Delete(); + } + + public virtual PlayerMobile GetOccupant(int index) + { + LeverPuzzleRegion region = m_Tiles[index]; + + if (region?.Occupant != null && region.Occupant.Alive) return (PlayerMobile)region.Occupant; + return null; + } + + public virtual LeverPuzzleStatue GetStatue(int index) + { + LeverPuzzleStatue statue = (LeverPuzzleStatue)m_Statues[index]; + + if (statue != null && !statue.Deleted) return statue; + return null; + } + + public virtual LeverPuzzleLever GetLever(int index) + { + LeverPuzzleLever lever = (LeverPuzzleLever)m_Levers[index]; + + if (lever != null && !lever.Deleted) return lever; + return null; + } + + public virtual void PuzzleStatus(int message, string fstring) + { + for (int i = 0; i < 2; i++) + { + Item s; + if ((s = GetStatue(i)) != null) s.PublicOverheadMessage(MessageType.Regular, 0x3B2, message, fstring); + } + } + + public virtual void ResetPuzzle() + { + PuzzleStatus(1062053, null); + ResetLevers(); + } + + public virtual void ResetLevers() + { + for (int i = 0; i < 4; i++) + { + Item l; + if ((l = GetLever(i)) != null) + { + l.ItemID = 0x108E; + Effects.PlaySound(l.Location, Map, 0x3E8); + } + } + + TheirKey ^= TheirKey; + } + + public virtual void KillTimers() + { + if (l_Timer != null && l_Timer.Running) l_Timer.Stop(); + if (m_Timer != null && m_Timer.Running) m_Timer.Stop(); + } + + public virtual void RemoveSuccessful() + { + Successful = null; + } + + public virtual void LeverPulled(ushort code) + { + int Correct = 0; + Mobile m_Player; + + KillTimers(); + + /* if one bit in each of the four nibbles is set, this is false */ + + if ((TheirKey = (ushort)(code | (TheirKey <<= 4))) < 0x0FFF) + { + l_Timer = Timer.DelayCall(TimeSpan.FromSeconds(30.0), ResetPuzzle); + return; + } + + if (!CircleComplete) + { + PuzzleStatus(1050004, null); // The circle is the key... + } + else + { + if (TheirKey == MyKey) + { + GenKey(); + if ((Successful = m_Player = GetOccupant(0)) != null) + { + SendLocationEffect(lp_Center, 0x1153, 0, 60, 1); + PlaySounds(lp_Center, cs1); + + Effects.SendBoltEffect(m_Player, true); + m_Player.MoveToWorld(lr_Enter, Map.Malas); + + m_Timer = new LampRoomTimer(this); + m_Timer.Start(); + Enabled = false; + } + } + else + { + for (int i = 0; i < 16; i++) /* Count matching SET bits, ie correct codes */ + if (((MyKey >> i) & 1) == 1 && ((TheirKey >> i) & 1) == 1) + Correct++; + + PuzzleStatus(Statue_Msg[Correct], Correct > 0 ? Correct.ToString() : null); + + for (int i = 0; i < 5; i++) + if ((m_Player = GetOccupant(i)) != null) + { + Timer smash = new RockTimer(m_Player, this); + smash.Start(); + } + } + } + + ResetLevers(); + } + + public virtual void GenKey() /* Shuffle & build key */ + { + ushort tmp; + int n, i; + ushort[] CA = { 1, 2, 4, 8 }; + for (i = 0; i < 4; i++) + { + n = (n = Utility.Random(0, 3)) == i ? n & ~i : n; /* if (i==n) { return pointless; } */ + tmp = CA[i]; + CA[i] = CA[n]; + CA[n] = tmp; + } + + for (i = 0; i < 4; MyKey = (ushort)(CA[i++] | (MyKey <<= 4))) + { + } + } + + private static bool IsValidDamagable(Mobile m) + { + if (m != null && !m.Deleted) + { + if (m.Player && m.Alive) + return true; + + return m is BaseCreature bc && (bc.Controlled || bc.Summoned) && !bc.IsDeadBondedPet; + } + + return false; + } + + public static void MoveMobileOut(Mobile m) + { + if (m != null) + { + if (m is PlayerMobile && !m.Alive) + if (m.Corpse != null && !m.Corpse.Deleted) + m.Corpse.MoveToWorld(lr_Exit, Map.Malas); + BaseCreature.TeleportPets(m, lr_Exit, Map.Malas); + m.Location = lr_Exit; + m.ProcessDelta(); + } + } + + public static bool AniSafe(Mobile m) + { + return m != null && !TransformationSpellHelper.UnderTransformation(m) && m.BodyMod == 0 && m.Alive; + } + + public static IEntity ZAdjustedIEFromMobile(Mobile m, int ZDelta) + { + return new Entity(Serial.Zero, new Point3D(m.X, m.Y, m.Z + ZDelta), m.Map); + } + + public static void DoDamage(Mobile m, int min, int max, bool poison) + { + if (m != null && !m.Deleted && m.Alive) + { + int damage = Utility.Random(min, max); + AOS.Damage(m, damage, poison ? 0 : 100, 0, 0, poison ? 100 : 0, 0); + } + } + + public static Point3D RandomPointIn(Point3D point, int range) + { + return RandomPointIn(point.X - range, point.Y - range, range * 2, range * 2, point.Z); + } + + public static Point3D RandomPointIn(Rectangle2D rect, int z) + { + return RandomPointIn(rect.X, rect.Y, rect.Height, rect.Width, z); + } + + public static Point3D RandomPointIn(int x, int y, int x2, int y2, int z) + { + return new Point3D(Utility.Random(x, x2), Utility.Random(y, y2), z); + } + + public static void PlaySounds(Point3D location, int[] sounds) + { + foreach (int soundid in sounds) + Effects.PlaySound(location, Map.Malas, soundid); + } + + public static void PlayEffect(IEntity from, IEntity to, int itemid, int speed, bool explodes) + { + Effects.SendMovingParticles(from, to, itemid, speed, 0, true, explodes, 2, 0, 0); + } + + public static void SendLocationEffect(IPoint3D p, int itemID, int speed, int duration, int hue) + { + Effects.SendPacket(p, Map.Malas, new LocationEffect(p, itemID, speed, duration, hue, 0)); + } + + public static void PlayerSendASCII(Mobile player, int index) + { + player.Send(new AsciiMessage(Serial.MinusOne, 0xFFFF, MessageType.Label, MsgParams[index][0], + MsgParams[index][1], null, Msgs[index])); + } + + /* I cant find any better way to send "speech" using fonts other than default */ + public static void POHMessage(Mobile from, int index) + { + Packet p = new AsciiMessage(from.Serial, from.Body, MessageType.Regular, MsgParams[index][0], + MsgParams[index][1], from.Name, Msgs[index]); + p.Acquire(); + foreach (NetState state in from.Map.GetClientsInRange(from.Location)) + state.Send(p); + + Packet.Release(p); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + writer.WriteItemList(m_Levers, true); + writer.WriteItemList(m_Statues, true); + writer.WriteItemList(m_Teles, true); + writer.Write(m_Box); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Levers = reader.ReadStrongItemList(); + m_Statues = reader.ReadStrongItemList(); + m_Teles = reader.ReadStrongItemList(); + + m_Box = reader.ReadItem() as LampRoomBox; + + m_Tiles = new List(); + for (int i = 4; i < 9; i++) + m_Tiles.Add(new LeverPuzzleRegion(this, TA[i])); + + m_LampRoom = new LampRoomRegion(this); + Enabled = true; + TheirKey = 0; + MyKey = 0; + GenKey(); + } + + public class RockTimer : Timer + { + private int Count; + private LeverPuzzleController m_Controller; + private Mobile m_Player; + + public RockTimer(Mobile player, LeverPuzzleController Controller) + : base(TimeSpan.Zero, TimeSpan.FromSeconds(.25)) + { + Count = 0; + m_Player = player; + m_Controller = Controller; + } + + private int Rock() + { + return 0x1363 + Utility.Random(0, 11); + } + + protected override void OnTick() + { + if (m_Player == null || !(m_Player.Map == Map.Malas)) + { + Stop(); + } + else + { + Count++; + if (Count == 1) /* TODO consolidate */ + { + m_Player.Paralyze(TimeSpan.FromSeconds(2)); + Effects.SendTargetEffect(m_Player, 0x11B7, 20, 10); + PlayerSendASCII(m_Player, 0); // You are pinned down ... + + PlaySounds(m_Player.Location, !m_Player.Female ? fs : ms); + PlayEffect(ZAdjustedIEFromMobile(m_Player, 50), m_Player, 0x11B7, 20, false); + } + else if (Count == 2) + { + DoDamage(m_Player, 80, 90, false); + Effects.SendTargetEffect(m_Player, 0x36BD, 20, 10); + PlaySounds(m_Player.Location, exp); + PlayerSendASCII(m_Player, 1); // A speeding rock ... + + if (AniSafe(m_Player)) m_Player.Animate(21, 10, 1, true, true, 0); + } + else if (Count == 3) + { + Stop(); + + Effects.SendTargetEffect(m_Player, 0x36B0, 20, 10); + PlayerSendASCII(m_Player, 1); // A speeding rock ... + PlaySounds(m_Player.Location, !m_Player.Female ? fs2 : ms2); + + int j = Utility.Random(6, 10); + for (int i = 0; i < j; i++) + { + IEntity m_IEntity = new Entity(Serial.Zero, RandomPointIn(m_Player.Location, 10), m_Player.Map); + + List mobiles = new List(); + foreach (Mobile m in m_IEntity.Map.GetMobilesInRange(m_IEntity.Location, 2)) mobiles.Add(m); + for (int k = 0; k < mobiles.Count; k++) + if (IsValidDamagable(mobiles[k]) && mobiles[k] != m_Player) + { + PlayEffect(m_Player, mobiles[k], Rock(), 8, true); + DoDamage(mobiles[k], 25, 30, false); + + if (mobiles[k].Player) POHMessage(mobiles[k], 2); // OUCH! + } + + PlayEffect(m_Player, m_IEntity, Rock(), 8, false); + } + } + } + } + } + + public class LampRoomKickTimer : Timer + { + private Mobile m; + + public LampRoomKickTimer(Mobile player) + : base(TimeSpan.FromSeconds(.25)) + { + m = player; + } + + protected override void OnTick() + { + MoveMobileOut(m); + } + } + + public class LampRoomTimer : Timer + { + public int level; + public LeverPuzzleController m_Controller; + public int ticks; + + public LampRoomTimer(LeverPuzzleController controller) + : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + level = 0; + ticks = 0; + m_Controller = controller; + } + + protected override void OnTick() + { + ticks++; + List mobiles = m_Controller.m_LampRoom.GetMobiles(); + + if (ticks >= 71 || m_Controller.m_LampRoom.GetPlayerCount() == 0) + { + foreach (Mobile mobile in mobiles) + if (mobile != null && !mobile.Deleted && !mobile.IsDeadBondedPet) + mobile.Kill(); + m_Controller.Enabled = true; + Stop(); + } + else + { + if (ticks % 12 == 0) level++; + foreach (Mobile mobile in mobiles) + if (IsValidDamagable(mobile)) + { + if (ticks % 2 == 0 && level == 5) + { + if (mobile.Player) + { + mobile.Say(1062092); + if (AniSafe(mobile)) mobile.Animate(32, 5, 1, true, false, 0); + } + + DoDamage(mobile, 15, 20, true); + } + + if (Utility.Random((int)(level & ~0xfffffffc), 3) == 3) mobile.ApplyPoison(mobile, PA2[level]); + if (ticks % 12 == 0 && level > 0 && mobile.Player) + mobile.SendLocalizedMessage(PA[level][0], null, PA[level][1]); + } + + for (int i = 0; i <= level; i++) + SendLocationEffect(RandomPointIn(lr_Rect, -1), 0x36B0, Utility.Random(150, 200), 0, PA[level][2]); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleItems.cs b/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleItems.cs index d4d5c00d4..76e3dbfd9 100644 --- a/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleItems.cs +++ b/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleItems.cs @@ -1,195 +1,205 @@ using System; -using Server.Spells; using Server.Mobiles; using Server.Network; +using Server.Spells; namespace Server.Engines.Doom { - public class LampRoomBox : Item - { - private LeverPuzzleController m_Controller; - private Mobile m_Wanderer; + public class LampRoomBox : Item + { + private LeverPuzzleController m_Controller; + private Mobile m_Wanderer; - public LampRoomBox( LeverPuzzleController controller ) : base( 0xe80 ) - { - m_Controller = controller; - ItemID = 0xe80; - Movable = false; - } + public LampRoomBox(LeverPuzzleController controller) : base(0xe80) + { + m_Controller = controller; + ItemID = 0xe80; + Movable = false; + } - public override void OnDoubleClick( Mobile m ) - { - if ( !m.InRange( GetWorldLocation(), 3 ) ) - return; - if ( m_Controller.Enabled ) - return; + public LampRoomBox(Serial serial) : base(serial) + { + } - if ( (m_Wanderer == null || !m_Wanderer.Alive) ) - { - m_Wanderer = new WandererOfTheVoid(); - m_Wanderer.MoveToWorld( LeverPuzzleController.lr_Enter, Map.Malas ); - m_Wanderer.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1060002, "" ); // I am the guardian of... - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), CallBackMessage ); - } - } + public override void OnDoubleClick(Mobile m) + { + if (!m.InRange(GetWorldLocation(), 3)) + return; + if (m_Controller.Enabled) + return; - public void CallBackMessage() - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1060003, "" ); // You try to pry the box open... - } - public override void OnAfterDelete() - { - if ( m_Controller!=null && !m_Controller.Deleted ) - m_Controller.Delete(); - } - public LampRoomBox( Serial serial ) : base( serial ) - { - } + if (m_Wanderer == null || !m_Wanderer.Alive) + { + m_Wanderer = new WandererOfTheVoid(); + m_Wanderer.MoveToWorld(LeverPuzzleController.lr_Enter, Map.Malas); + m_Wanderer.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1060002, ""); // I am the guardian of... + Timer.DelayCall(TimeSpan.FromSeconds(5.0), CallBackMessage); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - writer.Write( m_Controller ); - } + public void CallBackMessage() + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1060003, ""); // You try to pry the box open... + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - m_Controller = reader.ReadItem() as LeverPuzzleController; - } - } + public override void OnAfterDelete() + { + if (m_Controller != null && !m_Controller.Deleted) + m_Controller.Delete(); + } - public class LeverPuzzleStatue : Item - { - private LeverPuzzleController m_Controller; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + writer.Write(m_Controller); + } - public LeverPuzzleStatue( int[] dat, LeverPuzzleController controller ) : base( dat[0] ) - { - m_Controller=controller; - Hue = 0x44E; - Movable = false; - } - public override void OnAfterDelete() - { - if ( m_Controller!=null && !m_Controller.Deleted ) - m_Controller.Delete(); - } - public LeverPuzzleStatue( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - writer.Write( m_Controller ); - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - m_Controller = reader.ReadItem() as LeverPuzzleController; - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + m_Controller = reader.ReadItem() as LeverPuzzleController; + } + } - public class LeverPuzzleLever : Item - { - private LeverPuzzleController m_Controller; + public class LeverPuzzleStatue : Item + { + private LeverPuzzleController m_Controller; - [CommandProperty( AccessLevel.GameMaster )] - public ushort Code { get; private set; } + public LeverPuzzleStatue(int[] dat, LeverPuzzleController controller) : base(dat[0]) + { + m_Controller = controller; + Hue = 0x44E; + Movable = false; + } - public LeverPuzzleLever( ushort code, LeverPuzzleController controller ) : base( 0x108E ) - { - m_Controller=controller; - Code = code; - Hue = 0x66D; - Movable = false; - } + public LeverPuzzleStatue(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile m ) - { - if ( m != null && m_Controller.Enabled ) - { - ItemID^=2; - Effects.PlaySound( Location, Map, 0x3E8 ); - m_Controller.LeverPulled( Code ); - } - else - { - m.SendLocalizedMessage( 1060001 ); // You throw the switch, but the mechanism cannot be engaged again so soon. - } - } + public override void OnAfterDelete() + { + if (m_Controller != null && !m_Controller.Deleted) + m_Controller.Delete(); + } - public override void OnAfterDelete() - { - if ( m_Controller != null && !m_Controller.Deleted ) - m_Controller.Delete(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + writer.Write(m_Controller); + } - public LeverPuzzleLever( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - writer.Write( (ushort) Code ); - writer.Write( m_Controller ); - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - Code = reader.ReadUShort(); - m_Controller = reader.ReadItem() as LeverPuzzleController; - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + m_Controller = reader.ReadItem() as LeverPuzzleController; + } + } - [TypeAlias( "Server.Engines.Doom.LampRoomTelePorter" )] - public class LampRoomTeleporter : Item - { - public LampRoomTeleporter( int[] dat ) - { - Hue = dat[1]; - ItemID = dat[0]; - Movable = false; - } + public class LeverPuzzleLever : Item + { + private LeverPuzzleController m_Controller; - public override bool HandlesOnMovement => true; - public override bool OnMoveOver( Mobile m ) - { - if ( m is PlayerMobile ) - { - if ( SpellHelper.CheckCombat( m ) ) - { - m.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - } - else - { - BaseCreature.TeleportPets( m, LeverPuzzleController.lr_Exit, Map.Malas ); - m.MoveToWorld( LeverPuzzleController.lr_Exit, Map.Malas ); - return false; - } - } - return true; - } + public LeverPuzzleLever(ushort code, LeverPuzzleController controller) : base(0x108E) + { + m_Controller = controller; + Code = code; + Hue = 0x66D; + Movable = false; + } - public LampRoomTeleporter( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public LeverPuzzleLever(Serial serial) : base(serial) + { + } + [CommandProperty(AccessLevel.GameMaster)] + public ushort Code{ get; private set; } + public override void OnDoubleClick(Mobile m) + { + if (m != null && m_Controller.Enabled) + { + ItemID ^= 2; + Effects.PlaySound(Location, Map, 0x3E8); + m_Controller.LeverPulled(Code); + } + else + { + m.SendLocalizedMessage(1060001); // You throw the switch, but the mechanism cannot be engaged again so soon. + } + } + + public override void OnAfterDelete() + { + if (m_Controller != null && !m_Controller.Deleted) + m_Controller.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + writer.Write(Code); + writer.Write(m_Controller); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + Code = reader.ReadUShort(); + m_Controller = reader.ReadItem() as LeverPuzzleController; + } + } + + [TypeAlias("Server.Engines.Doom.LampRoomTelePorter")] + public class LampRoomTeleporter : Item + { + public LampRoomTeleporter(int[] dat) + { + Hue = dat[1]; + ItemID = dat[0]; + Movable = false; + } + + public LampRoomTeleporter(Serial serial) : base(serial) + { + } + + public override bool HandlesOnMovement => true; + + public override bool OnMoveOver(Mobile m) + { + if (m is PlayerMobile) + { + if (SpellHelper.CheckCombat(m)) + { + m.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + } + else + { + BaseCreature.TeleportPets(m, LeverPuzzleController.lr_Exit, Map.Malas); + m.MoveToWorld(LeverPuzzleController.lr_Exit, Map.Malas); + return false; + } + } + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleRegions.cs b/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleRegions.cs index 118a720d1..5d3e91ec5 100644 --- a/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleRegions.cs +++ b/Scripts/Engines/Doom/LeverPuzzle/LeverPuzzleRegions.cs @@ -3,118 +3,114 @@ using Server.Regions; namespace Server.Engines.Doom { - public class LampRoomRegion : BaseRegion - { - private LeverPuzzleController Controller; + public class LampRoomRegion : BaseRegion + { + private LeverPuzzleController Controller; - public LampRoomRegion ( LeverPuzzleController controller ) - : base( null, Map.Malas, Find( LeverPuzzleController.lr_Enter, Map.Malas ), LeverPuzzleController.lr_Rect ) - { - Controller = controller; - Register(); - } + public LampRoomRegion(LeverPuzzleController controller) + : base(null, Map.Malas, Find(LeverPuzzleController.lr_Enter, Map.Malas), LeverPuzzleController.lr_Rect) + { + Controller = controller; + Register(); + } - public static void Initialize() - { - EventSink.Login += OnLogin; - } + public static void Initialize() + { + EventSink.Login += OnLogin; + } - public static void OnLogin( LoginEventArgs e ) - { - Mobile m = e.Mobile; - Rectangle2D rect = LeverPuzzleController.lr_Rect; - if ( m.X >= rect.X && m.X <= (rect.X+10) && m.Y >= rect.Y && m.Y <= (rect.Y+10) && m.Map == Map.Internal ) - { - Timer kick = new LeverPuzzleController.LampRoomKickTimer( m ); - kick.Start(); - } - } + public static void OnLogin(LoginEventArgs e) + { + Mobile m = e.Mobile; + Rectangle2D rect = LeverPuzzleController.lr_Rect; + if (m.X >= rect.X && m.X <= rect.X + 10 && m.Y >= rect.Y && m.Y <= rect.Y + 10 && m.Map == Map.Internal) + { + Timer kick = new LeverPuzzleController.LampRoomKickTimer(m); + kick.Start(); + } + } - public override void OnEnter( Mobile m ) - { - if ( m == null || m is WandererOfTheVoid ) - return; + public override void OnEnter(Mobile m) + { + if (m == null || m is WandererOfTheVoid) + return; - if ( m.AccessLevel > AccessLevel.Player ) - return; + if (m.AccessLevel > AccessLevel.Player) + return; - if ( Controller.Successful != null ) - { - if ( m is PlayerMobile ) - { - if ( m == Controller.Successful ) - { - return; - } - } - else if (m is BaseCreature bc && ((bc.Controlled && bc.ControlMaster == Controller.Successful) || - bc.Summoned)) - return; - } - Timer kick = new LeverPuzzleController.LampRoomKickTimer( m ); - kick.Start(); - } + if (Controller.Successful != null) + { + if (m is PlayerMobile) + { + if (m == Controller.Successful) return; + } + else if (m is BaseCreature bc && (bc.Controlled && bc.ControlMaster == Controller.Successful || + bc.Summoned)) + { + return; + } + } - public override void OnExit( Mobile m ) - { - if ( m != null && m == Controller.Successful ) - Controller.RemoveSuccessful(); - } + Timer kick = new LeverPuzzleController.LampRoomKickTimer(m); + kick.Start(); + } - public override void OnDeath( Mobile m ) - { - if ( m != null && !m.Deleted && !(m is WandererOfTheVoid) ) - { - Timer kick = new LeverPuzzleController.LampRoomKickTimer( m ); - kick.Start(); - } - } + public override void OnExit(Mobile m) + { + if (m != null && m == Controller.Successful) + Controller.RemoveSuccessful(); + } - public override bool OnSkillUse( Mobile m, int Skill ) /* just in case */ - { - if (( Controller.Successful == null ) || ( m.AccessLevel == AccessLevel.Player && m != Controller.Successful )) - { - return false; - } - return true; - } - } + public override void OnDeath(Mobile m) + { + if (m != null && !m.Deleted && !(m is WandererOfTheVoid)) + { + Timer kick = new LeverPuzzleController.LampRoomKickTimer(m); + kick.Start(); + } + } - public class LeverPuzzleRegion : BaseRegion - { - private LeverPuzzleController Controller; - public Mobile m_Occupant; + public override bool OnSkillUse(Mobile m, int Skill) /* just in case */ + { + if (Controller.Successful == null || m.AccessLevel == AccessLevel.Player && m != Controller.Successful) + return false; + return true; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Occupant - { - get - { - if ( m_Occupant != null && m_Occupant.Alive ) - return m_Occupant; - return null; - } - } + public class LeverPuzzleRegion : BaseRegion + { + private LeverPuzzleController Controller; + public Mobile m_Occupant; - public LeverPuzzleRegion ( LeverPuzzleController controller, int[] loc ) - : base( null, Map.Malas, Find( LeverPuzzleController.lr_Enter, Map.Malas ), new Rectangle2D(loc[0],loc[1],1,1) ) - { - Controller = controller; - Register(); - } + public LeverPuzzleRegion(LeverPuzzleController controller, int[] loc) + : base(null, Map.Malas, Find(LeverPuzzleController.lr_Enter, Map.Malas), new Rectangle2D(loc[0], loc[1], 1, 1)) + { + Controller = controller; + Register(); + } - public override void OnEnter( Mobile m ) - { - if ( m != null && m_Occupant == null && m is PlayerMobile && m.Alive ) - m_Occupant = m; - } - - public override void OnExit( Mobile m ) - { - if ( m != null && m == m_Occupant ) - m_Occupant = null; - } - } -} + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Occupant + { + get + { + if (m_Occupant != null && m_Occupant.Alive) + return m_Occupant; + return null; + } + } + public override void OnEnter(Mobile m) + { + if (m != null && m_Occupant == null && m is PlayerMobile && m.Alive) + m_Occupant = m; + } + public override void OnExit(Mobile m) + { + if (m != null && m == m_Occupant) + m_Occupant = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Core/Ethic.cs b/Scripts/Engines/Ethics/Core/Ethic.cs index 167f9947a..7b728ef22 100644 --- a/Scripts/Engines/Ethics/Core/Ethic.cs +++ b/Scripts/Engines/Ethics/Core/Ethic.cs @@ -1,244 +1,242 @@ using System; +using Server.Ethics.Evil; +using Server.Ethics.Hero; +using Server.Items; using Server.Mobiles; namespace Server.Ethics { - public abstract class Ethic - { - public static readonly bool Enabled = false; + public abstract class Ethic + { + public static readonly bool Enabled = false; - public static Ethic Find( Item item ) - { - if ( ( item.SavedFlags & 0x100 ) != 0 ) - { - if ( item.Hue == Hero.Definition.PrimaryHue ) - return Hero; + public static readonly Ethic Hero = new HeroEthic(); + public static readonly Ethic Evil = new EvilEthic(); - item.SavedFlags &= ~0x100; - } + public static readonly Ethic[] Ethics = + { + Hero, + Evil + }; - if ( ( item.SavedFlags & 0x200 ) != 0 ) - { - if ( item.Hue == Evil.Definition.PrimaryHue ) - return Evil; + protected EthicDefinition m_Definition; - item.SavedFlags &= ~0x200; - } + protected PlayerCollection m_Players; - return null; - } + public Ethic() + { + m_Players = new PlayerCollection(); + } - public static bool CheckTrade( Mobile from, Mobile to, Mobile newOwner, Item item ) - { - Ethic itemEthic = Find( item ); + public EthicDefinition Definition => m_Definition; - if ( itemEthic == null || Find( newOwner ) == itemEthic ) - return true; + public PlayerCollection Players => m_Players; - if ( itemEthic == Hero ) - ( from == newOwner ? to : from ).SendMessage( "Only heros may receive this item." ); - else if ( itemEthic == Evil ) - ( from == newOwner ? to : from ).SendMessage( "Only the evil may receive this item." ); + public static Ethic Find(Item item) + { + if ((item.SavedFlags & 0x100) != 0) + { + if (item.Hue == Hero.Definition.PrimaryHue) + return Hero; - return false; - } + item.SavedFlags &= ~0x100; + } - public static bool CheckEquip( Mobile from, Item item ) - { - Ethic itemEthic = Find( item ); + if ((item.SavedFlags & 0x200) != 0) + { + if (item.Hue == Evil.Definition.PrimaryHue) + return Evil; - if ( itemEthic == null || Find( from ) == itemEthic ) - return true; + item.SavedFlags &= ~0x200; + } - if ( itemEthic == Hero ) - from.SendMessage( "Only heros may wear this item." ); - else if ( itemEthic == Evil ) - from.SendMessage( "Only the evil may wear this item." ); + return null; + } - return false; - } + public static bool CheckTrade(Mobile from, Mobile to, Mobile newOwner, Item item) + { + Ethic itemEthic = Find(item); - public static bool IsImbued( Item item ) - { - return IsImbued( item, false ); - } + if (itemEthic == null || Find(newOwner) == itemEthic) + return true; - public static bool IsImbued( Item item, bool recurse ) - { - if ( Find( item ) != null ) - return true; + if (itemEthic == Hero) + (from == newOwner ? to : from).SendMessage("Only heros may receive this item."); + else if (itemEthic == Evil) + (from == newOwner ? to : from).SendMessage("Only the evil may receive this item."); - if ( recurse ) - { - foreach ( Item child in item.Items ) - { - if ( IsImbued( child, true ) ) - return true; - } - } + return false; + } - return false; - } + public static bool CheckEquip(Mobile from, Item item) + { + Ethic itemEthic = Find(item); - public static void Initialize() - { - if ( Enabled ) - EventSink.Speech += EventSink_Speech; - } + if (itemEthic == null || Find(from) == itemEthic) + return true; - public static void EventSink_Speech( SpeechEventArgs e ) - { - if ( e.Blocked || e.Handled ) - return; + if (itemEthic == Hero) + from.SendMessage("Only heros may wear this item."); + else if (itemEthic == Evil) + from.SendMessage("Only the evil may wear this item."); - Player pl = Player.Find( e.Mobile ); + return false; + } - if ( pl == null ) - { - for ( int i = 0; i < Ethics.Length; ++i ) - { - Ethic ethic = Ethics[i]; + public static bool IsImbued(Item item) + { + return IsImbued(item, false); + } - if ( !ethic.IsEligible( e.Mobile ) ) - continue; + public static bool IsImbued(Item item, bool recurse) + { + if (Find(item) != null) + return true; - if ( !Insensitive.Equals( ethic.Definition.JoinPhrase.String, e.Speech ) ) - continue; + if (recurse) + foreach (Item child in item.Items) + if (IsImbued(child, true)) + return true; - bool isNearAnkh = false; + return false; + } - foreach ( Item item in e.Mobile.GetItemsInRange( 2 ) ) - { - if ( item is Items.AnkhNorth || item is Items.AnkhWest ) - { - isNearAnkh = true; - break; - } - } + public static void Initialize() + { + if (Enabled) + EventSink.Speech += EventSink_Speech; + } - if ( !isNearAnkh ) - continue; + public static void EventSink_Speech(SpeechEventArgs e) + { + if (e.Blocked || e.Handled) + return; - pl = new Player( ethic, e.Mobile ); + Player pl = Player.Find(e.Mobile); - pl.Attach(); + if (pl == null) + { + for (int i = 0; i < Ethics.Length; ++i) + { + Ethic ethic = Ethics[i]; - e.Mobile.FixedEffect( 0x373A, 10, 30 ); - e.Mobile.PlaySound( 0x209 ); + if (!ethic.IsEligible(e.Mobile)) + continue; - e.Handled = true; - break; - } - } - else - { - if ( e.Mobile is PlayerMobile mobile && mobile.DuelContext != null ) - return; + if (!Insensitive.Equals(ethic.Definition.JoinPhrase.String, e.Speech)) + continue; - Ethic ethic = pl.Ethic; + bool isNearAnkh = false; - for ( int i = 0; i < ethic.Definition.Powers.Length; ++i ) - { - Power power = ethic.Definition.Powers[i]; + foreach (Item item in e.Mobile.GetItemsInRange(2)) + if (item is AnkhNorth || item is AnkhWest) + { + isNearAnkh = true; + break; + } - if ( !Insensitive.Equals( power.Definition.Phrase.String, e.Speech ) ) - continue; + if (!isNearAnkh) + continue; - if ( !power.CheckInvoke( pl ) ) - continue; + pl = new Player(ethic, e.Mobile); - power.BeginInvoke( pl ); - e.Handled = true; + pl.Attach(); - break; - } - } - } + e.Mobile.FixedEffect(0x373A, 10, 30); + e.Mobile.PlaySound(0x209); - protected EthicDefinition m_Definition; + e.Handled = true; + break; + } + } + else + { + if (e.Mobile is PlayerMobile mobile && mobile.DuelContext != null) + return; - protected PlayerCollection m_Players; + Ethic ethic = pl.Ethic; - public EthicDefinition Definition => m_Definition; + for (int i = 0; i < ethic.Definition.Powers.Length; ++i) + { + Power power = ethic.Definition.Powers[i]; - public PlayerCollection Players => m_Players; + if (!Insensitive.Equals(power.Definition.Phrase.String, e.Speech)) + continue; - public static Ethic Find( Mobile mob ) - { - return Find( mob, false, false ); - } + if (!power.CheckInvoke(pl)) + continue; - public static Ethic Find( Mobile mob, bool inherit ) - { - return Find( mob, inherit, false ); - } + power.BeginInvoke(pl); + e.Handled = true; - public static Ethic Find( Mobile mob, bool inherit, bool allegiance ) - { - Player pl = Player.Find( mob ); + break; + } + } + } - if ( pl != null ) - return pl.Ethic; + public static Ethic Find(Mobile mob) + { + return Find(mob, false, false); + } - if ( inherit && mob is BaseCreature bc ) - { - if ( bc.Controlled ) - return Find( bc.ControlMaster, false ); - if ( bc.Summoned ) - return Find( bc.SummonMaster, false ); - if ( allegiance ) - return bc.EthicAllegiance; - } + public static Ethic Find(Mobile mob, bool inherit) + { + return Find(mob, inherit, false); + } - return null; - } + public static Ethic Find(Mobile mob, bool inherit, bool allegiance) + { + Player pl = Player.Find(mob); - public Ethic() - { - m_Players = new PlayerCollection(); - } + if (pl != null) + return pl.Ethic; - public abstract bool IsEligible( Mobile mob ); + if (inherit && mob is BaseCreature bc) + { + if (bc.Controlled) + return Find(bc.ControlMaster, false); + if (bc.Summoned) + return Find(bc.SummonMaster, false); + if (allegiance) + return bc.EthicAllegiance; + } - public virtual void Deserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + return null; + } - switch ( version ) - { - case 0: - { - int playerCount = reader.ReadEncodedInt(); + public abstract bool IsEligible(Mobile mob); - for ( int i = 0; i < playerCount; ++i ) - { - Player pl = new Player( this, reader ); + public virtual void Deserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - if ( pl.Mobile != null ) - Timer.DelayCall( TimeSpan.Zero, pl.CheckAttach ); - } + switch (version) + { + case 0: + { + int playerCount = reader.ReadEncodedInt(); - break; - } - } - } + for (int i = 0; i < playerCount; ++i) + { + Player pl = new Player(this, reader); - public virtual void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + if (pl.Mobile != null) + Timer.DelayCall(TimeSpan.Zero, pl.CheckAttach); + } - writer.WriteEncodedInt( m_Players.Count ); + break; + } + } + } - for ( int i = 0; i < m_Players.Count; ++i ) - m_Players[i].Serialize( writer ); - } + public virtual void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public static readonly Ethic Hero = new Hero.HeroEthic(); - public static readonly Ethic Evil = new Evil.EvilEthic(); + writer.WriteEncodedInt(m_Players.Count); - public static readonly Ethic[] Ethics = { - Hero, - Evil - }; - } -} + for (int i = 0; i < m_Players.Count; ++i) + m_Players[i].Serialize(writer); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Core/Persistance.cs b/Scripts/Engines/Ethics/Core/Persistance.cs index e7b687d16..8a5b200dc 100644 --- a/Scripts/Engines/Ethics/Core/Persistance.cs +++ b/Scripts/Engines/Ethics/Core/Persistance.cs @@ -1,59 +1,59 @@ namespace Server.Ethics { - public class EthicsPersistance : Item - { - public static EthicsPersistance Instance { get; private set; } + public class EthicsPersistance : Item + { + [Constructible] + public EthicsPersistance() + : base(1) + { + Movable = false; - public override string DefaultName => "Ethics Persistance - Internal"; + if (Instance == null || Instance.Deleted) + Instance = this; + else + base.Delete(); + } - [Constructible] - public EthicsPersistance() - : base( 1 ) - { - Movable = false; + public EthicsPersistance(Serial serial) + : base(serial) + { + Instance = this; + } - if ( Instance == null || Instance.Deleted ) - Instance = this; - else - base.Delete(); - } + public static EthicsPersistance Instance{ get; private set; } - public EthicsPersistance( Serial serial ) - : base( serial ) - { - Instance = this; - } + public override string DefaultName => "Ethics Persistance - Internal"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - for ( int i = 0; i < Ethic.Ethics.Length; ++i ) - Ethic.Ethics[i].Serialize( writer ); - } + for (int i = 0; i < Ethic.Ethics.Length; ++i) + Ethic.Ethics[i].Serialize(writer); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - for ( int i = 0; i < Ethic.Ethics.Length; ++i ) - Ethic.Ethics[i].Deserialize( reader ); + switch (version) + { + case 0: + { + for (int i = 0; i < Ethic.Ethics.Length; ++i) + Ethic.Ethics[i].Deserialize(reader); - break; - } - } - } + break; + } + } + } - public override void Delete() - { - } - } -} + public override void Delete() + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Core/Player.cs b/Scripts/Engines/Ethics/Core/Player.cs index 36ecd1292..4069f89c7 100644 --- a/Scripts/Engines/Ethics/Core/Player.cs +++ b/Scripts/Engines/Ethics/Core/Player.cs @@ -1,159 +1,160 @@ using System; +using System.Collections.ObjectModel; using Server.Mobiles; namespace Server.Ethics { - public class PlayerCollection : System.Collections.ObjectModel.Collection - { - } + public class PlayerCollection : Collection + { + } - [PropertyObject] - public class Player - { - public static Player Find( Mobile mob ) - { - return Find( mob, false ); - } + [PropertyObject] + public class Player + { + private DateTime m_Shield; - public static Player Find( Mobile mob, bool inherit ) - { - PlayerMobile pm = mob as PlayerMobile; + public Player(Ethic ethic, Mobile mobile) + { + Ethic = ethic; + Mobile = mobile; - if ( pm == null ) - { - if ( inherit && mob is BaseCreature bc ) - { - if ( bc.Controlled ) - pm = bc.ControlMaster as PlayerMobile; - else if ( bc.Summoned ) - pm = bc.SummonMaster as PlayerMobile; - } + Power = 5; + History = 5; + } - if ( pm == null ) - return null; - } + public Player(Ethic ethic, GenericReader reader) + { + Ethic = ethic; - Player pl = pm.EthicPlayer; + int version = reader.ReadEncodedInt(); - if ( pl != null && !pl.Ethic.IsEligible( pl.Mobile ) ) - pm.EthicPlayer = pl = null; + switch (version) + { + case 0: + { + Mobile = reader.ReadMobile(); - return pl; - } + Power = reader.ReadEncodedInt(); + History = reader.ReadEncodedInt(); - private DateTime m_Shield; + Steed = reader.ReadMobile(); + Familiar = reader.ReadMobile(); - public Ethic Ethic { get; } + m_Shield = reader.ReadDeltaTime(); - public Mobile Mobile { get; } + break; + } + } + } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public int Power { get; set; } + public Ethic Ethic{ get; } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public int History { get; set; } + public Mobile Mobile{ get; } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Mobile Steed { get; set; } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public int Power{ get; set; } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Mobile Familiar { get; set; } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public int History{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsShielded - { - get - { - if ( m_Shield == DateTime.MinValue ) - return false; + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Mobile Steed{ get; set; } - if ( DateTime.UtcNow < ( m_Shield + TimeSpan.FromHours( 1.0 ) ) ) - return true; + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Mobile Familiar{ get; set; } - FinishShield(); - return false; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsShielded + { + get + { + if (m_Shield == DateTime.MinValue) + return false; - public void BeginShield() - { - m_Shield = DateTime.UtcNow; - } + if (DateTime.UtcNow < m_Shield + TimeSpan.FromHours(1.0)) + return true; - public void FinishShield() - { - m_Shield = DateTime.MinValue; - } + FinishShield(); + return false; + } + } - public Player( Ethic ethic, Mobile mobile ) - { - Ethic = ethic; - Mobile = mobile; + public static Player Find(Mobile mob) + { + return Find(mob, false); + } - Power = 5; - History = 5; - } + public static Player Find(Mobile mob, bool inherit) + { + PlayerMobile pm = mob as PlayerMobile; - public void CheckAttach() - { - if ( Ethic.IsEligible( Mobile ) ) - Attach(); - } + if (pm == null) + { + if (inherit && mob is BaseCreature bc) + { + if (bc.Controlled) + pm = bc.ControlMaster as PlayerMobile; + else if (bc.Summoned) + pm = bc.SummonMaster as PlayerMobile; + } - public void Attach() - { - if ( Mobile is PlayerMobile mobile ) - mobile.EthicPlayer = this; + if (pm == null) + return null; + } - Ethic.Players.Add( this ); - } + Player pl = pm.EthicPlayer; - public void Detach() - { - if ( Mobile is PlayerMobile mobile ) - mobile.EthicPlayer = null; + if (pl != null && !pl.Ethic.IsEligible(pl.Mobile)) + pm.EthicPlayer = pl = null; - Ethic.Players.Remove( this ); - } + return pl; + } - public Player( Ethic ethic, GenericReader reader ) - { - Ethic = ethic; + public void BeginShield() + { + m_Shield = DateTime.UtcNow; + } - int version = reader.ReadEncodedInt(); + public void FinishShield() + { + m_Shield = DateTime.MinValue; + } - switch ( version ) - { - case 0: - { - Mobile = reader.ReadMobile(); + public void CheckAttach() + { + if (Ethic.IsEligible(Mobile)) + Attach(); + } - Power = reader.ReadEncodedInt(); - History = reader.ReadEncodedInt(); + public void Attach() + { + if (Mobile is PlayerMobile mobile) + mobile.EthicPlayer = this; - Steed = reader.ReadMobile(); - Familiar = reader.ReadMobile(); + Ethic.Players.Add(this); + } - m_Shield = reader.ReadDeltaTime(); + public void Detach() + { + if (Mobile is PlayerMobile mobile) + mobile.EthicPlayer = null; - break; - } - } - } + Ethic.Players.Remove(this); + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( Mobile ); + writer.Write(Mobile); - writer.WriteEncodedInt( Power ); - writer.WriteEncodedInt( History ); + writer.WriteEncodedInt(Power); + writer.WriteEncodedInt(History); - writer.Write( Steed ); - writer.Write( Familiar ); + writer.Write(Steed); + writer.Write(Familiar); - writer.WriteDeltaTime( m_Shield ); - } - } -} + writer.WriteDeltaTime(m_Shield); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Core/Power.cs b/Scripts/Engines/Ethics/Core/Power.cs index b1cf219be..2e50bc2de 100644 --- a/Scripts/Engines/Ethics/Core/Power.cs +++ b/Scripts/Engines/Ethics/Core/Power.cs @@ -1,30 +1,33 @@ +using Server.Network; + namespace Server.Ethics { - public abstract class Power - { - protected PowerDefinition m_Definition; + public abstract class Power + { + protected PowerDefinition m_Definition; - public PowerDefinition Definition => m_Definition; + public PowerDefinition Definition => m_Definition; - public virtual bool CheckInvoke( Player from ) - { - if ( !from.Mobile.CheckAlive() ) - return false; + public virtual bool CheckInvoke(Player from) + { + if (!from.Mobile.CheckAlive()) + return false; - if ( from.Power < m_Definition.Power ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You lack the power to invoke this ability." ); - return false; - } + if (from.Power < m_Definition.Power) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You lack the power to invoke this ability."); + return false; + } - return true; - } + return true; + } - public abstract void BeginInvoke( Player from ); + public abstract void BeginInvoke(Player from); - public virtual void FinishInvoke( Player from ) - { - from.Power -= m_Definition.Power; - } - } -} + public virtual void FinishInvoke(Player from) + { + from.Power -= m_Definition.Power; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Definitions/EthicDefinition.cs b/Scripts/Engines/Ethics/Definitions/EthicDefinition.cs index 4b5fbde92..cbcaf9cb3 100644 --- a/Scripts/Engines/Ethics/Definitions/EthicDefinition.cs +++ b/Scripts/Engines/Ethics/Definitions/EthicDefinition.cs @@ -1,27 +1,28 @@ namespace Server.Ethics { - public class EthicDefinition - { - public int PrimaryHue { get; } + public class EthicDefinition + { + public EthicDefinition(int primaryHue, TextDefinition title, TextDefinition adjunct, TextDefinition joinPhrase, + Power[] powers) + { + PrimaryHue = primaryHue; - public TextDefinition Title { get; } + Title = title; + Adjunct = adjunct; - public TextDefinition Adjunct { get; } + JoinPhrase = joinPhrase; - public TextDefinition JoinPhrase { get; } + Powers = powers; + } - public Power[] Powers { get; } + public int PrimaryHue{ get; } - public EthicDefinition( int primaryHue, TextDefinition title, TextDefinition adjunct, TextDefinition joinPhrase, Power[] powers ) - { - PrimaryHue = primaryHue; + public TextDefinition Title{ get; } - Title = title; - Adjunct = adjunct; + public TextDefinition Adjunct{ get; } - JoinPhrase = joinPhrase; + public TextDefinition JoinPhrase{ get; } - Powers = powers; - } - } -} + public Power[] Powers{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Definitions/PowerDefinition.cs b/Scripts/Engines/Ethics/Definitions/PowerDefinition.cs index 0c927bd8c..2c5d5c972 100644 --- a/Scripts/Engines/Ethics/Definitions/PowerDefinition.cs +++ b/Scripts/Engines/Ethics/Definitions/PowerDefinition.cs @@ -1,22 +1,22 @@ namespace Server.Ethics { - public class PowerDefinition - { - public int Power { get; } + public class PowerDefinition + { + public PowerDefinition(int power, TextDefinition name, TextDefinition phrase, TextDefinition description) + { + Power = power; - public TextDefinition Name { get; } + Name = name; + Phrase = phrase; + Description = description; + } - public TextDefinition Phrase { get; } + public int Power{ get; } - public TextDefinition Description { get; } + public TextDefinition Name{ get; } - public PowerDefinition( int power, TextDefinition name, TextDefinition phrase, TextDefinition description ) - { - Power = power; + public TextDefinition Phrase{ get; } - Name = name; - Phrase = phrase; - Description = description; - } - } -} + public TextDefinition Description{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Ethic.cs b/Scripts/Engines/Ethics/Evil/Ethic.cs index 1a2a1722c..6aa035c76 100644 --- a/Scripts/Engines/Ethics/Evil/Ethic.cs +++ b/Scripts/Engines/Ethics/Evil/Ethic.cs @@ -2,33 +2,33 @@ using Server.Factions; namespace Server.Ethics.Evil { - public sealed class EvilEthic : Ethic - { - public EvilEthic() - { - m_Definition = new EthicDefinition( - 0x455, - "Evil", "(Evil)", - "I am evil incarnate", - new Power[] - { - new UnholySense(), - new UnholyItem(), - new SummonFamiliar(), - new VileBlade(), - new Blight(), - new UnholyShield(), - new UnholySteed(), - new UnholyWord() - } - ); - } + public sealed class EvilEthic : Ethic + { + public EvilEthic() + { + m_Definition = new EthicDefinition( + 0x455, + "Evil", "(Evil)", + "I am evil incarnate", + new Power[] + { + new UnholySense(), + new UnholyItem(), + new SummonFamiliar(), + new VileBlade(), + new Blight(), + new UnholyShield(), + new UnholySteed(), + new UnholyWord() + } + ); + } - public override bool IsEligible( Mobile mob ) - { - Faction fac = Faction.Find( mob ); + public override bool IsEligible(Mobile mob) + { + Faction fac = Faction.Find(mob); - return ( fac is Minax || fac is Shadowlords ); - } - } + return fac is Minax || fac is Shadowlords; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Mobiles/UnholyFamiliar.cs b/Scripts/Engines/Ethics/Evil/Mobiles/UnholyFamiliar.cs index a01c41641..b768f793b 100644 --- a/Scripts/Engines/Ethics/Evil/Mobiles/UnholyFamiliar.cs +++ b/Scripts/Engines/Ethics/Evil/Mobiles/UnholyFamiliar.cs @@ -1,84 +1,83 @@ -using System; using Server.Ethics; namespace Server.Mobiles { - public class UnholyFamiliar : BaseCreature - { - public override string CorpseName => "an evil corpse"; - public override bool IsDispellable => false; - public override bool IsBondable => false; - public override string DefaultName => "a dark wolf"; + public class UnholyFamiliar : BaseCreature + { + [Constructible] + public UnholyFamiliar() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 99; + BaseSoundID = 0xE5; - [Constructible] - public UnholyFamiliar() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 99; - BaseSoundID = 0xE5; + SetStr(96, 120); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(58, 72); + SetMana(0); - SetHits( 58, 72 ); - SetMana( 0 ); + SetDamage(11, 17); - SetDamage( 11, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 57.6, 75.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.MagicResist, 57.6, 75.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 2500; + Karma = 2500; - Fame = 2500; - Karma = 2500; + VirtualArmor = 22; - VirtualArmor = 22; + Tamable = false; + ControlSlots = 1; + } - Tamable = false; - ControlSlots = 1; - } + public UnholyFamiliar(Serial serial) + : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 7; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string CorpseName => "an evil corpse"; + public override bool IsDispellable => false; + public override bool IsBondable => false; + public override string DefaultName => "a dark wolf"; - public UnholyFamiliar( Serial serial ) - : base( serial ) - { - } + public override int Meat => 1; + public override int Hides => 7; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override string ApplyNameSuffix( string suffix ) - { - if ( suffix.Length == 0 ) - suffix = Ethic.Evil.Definition.Adjunct.String; - else - suffix = string.Concat( suffix, " ", Ethic.Evil.Definition.Adjunct.String ); + public override string ApplyNameSuffix(string suffix) + { + if (suffix.Length == 0) + suffix = Ethic.Evil.Definition.Adjunct.String; + else + suffix = string.Concat(suffix, " ", Ethic.Evil.Definition.Adjunct.String); - return base.ApplyNameSuffix( suffix ); - } + return base.ApplyNameSuffix(suffix); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Mobiles/UnholySteed.cs b/Scripts/Engines/Ethics/Evil/Mobiles/UnholySteed.cs index 543848412..837af47c0 100644 --- a/Scripts/Engines/Ethics/Evil/Mobiles/UnholySteed.cs +++ b/Scripts/Engines/Ethics/Evil/Mobiles/UnholySteed.cs @@ -1,89 +1,88 @@ -using System; using Server.Ethics; namespace Server.Mobiles { - public class UnholySteed : BaseMount - { - public override string CorpseName => "an unholy corpse"; - public override bool IsDispellable => false; - public override bool IsBondable => false; + public class UnholySteed : BaseMount + { + [Constructible] + public UnholySteed() + : base("a dark steed", 0x74, 0x3EA7, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + SetStr(496, 525); + SetDex(86, 105); + SetInt(86, 125); - public override bool HasBreath => true; - public override bool CanBreath => true; + SetHits(298, 315); - [Constructible] - public UnholySteed() - : base( "a dark steed", 0x74, 0x3EA7, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - SetStr( 496, 525 ); - SetDex( 86, 105 ); - SetInt( 86, 125 ); + SetDamage(16, 22); - SetHits( 298, 315 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Fire, 40); + SetDamageType(ResistanceType.Energy, 20); - SetDamage( 16, 22 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Fire, 40 ); - SetDamageType( ResistanceType.Energy, 20 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 80.5, 92.5); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 14000; + Karma = -14000; - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 80.5, 92.5 ); + VirtualArmor = 60; - Fame = 14000; - Karma = -14000; + Tamable = false; + ControlSlots = 1; + } - VirtualArmor = 60; + public UnholySteed(Serial serial) + : base(serial) + { + } - Tamable = false; - ControlSlots = 1; - } + public override string CorpseName => "an unholy corpse"; + public override bool IsDispellable => false; + public override bool IsBondable => false; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override bool HasBreath => true; + public override bool CanBreath => true; - public UnholySteed( Serial serial ) - : base( serial ) - { - } + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override string ApplyNameSuffix( string suffix ) - { - if ( suffix.Length == 0 ) - suffix = Ethic.Evil.Definition.Adjunct.String; - else - suffix = string.Concat( suffix, " ", Ethic.Evil.Definition.Adjunct.String ); + public override string ApplyNameSuffix(string suffix) + { + if (suffix.Length == 0) + suffix = Ethic.Evil.Definition.Adjunct.String; + else + suffix = string.Concat(suffix, " ", Ethic.Evil.Definition.Adjunct.String); - return base.ApplyNameSuffix( suffix ); - } + return base.ApplyNameSuffix(suffix); + } - public override void OnDoubleClick( Mobile from ) - { - if ( Ethic.Find( from ) != Ethic.Evil ) - from.SendMessage( "You may not ride this steed." ); - else - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (Ethic.Find(from) != Ethic.Evil) + from.SendMessage("You may not ride this steed."); + else + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/Blight.cs b/Scripts/Engines/Ethics/Evil/Powers/Blight.cs index 130e862ae..e23350625 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/Blight.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/Blight.cs @@ -1,76 +1,78 @@ using System; +using Server.Network; using Server.Spells; +using Server.Targeting; namespace Server.Ethics.Evil { - public sealed class Blight : Power - { - public Blight() - { - m_Definition = new PowerDefinition( - 15, - "Blight", - "Velgo Ontawl", - "" - ); - } + public sealed class Blight : Power + { + public Blight() + { + m_Definition = new PowerDefinition( + 15, + "Blight", + "Velgo Ontawl", + "" + ); + } - public override void BeginInvoke( Player from ) - { - from.Mobile.BeginTarget( 12, true, Targeting.TargetFlags.None, new TargetStateCallback( Power_OnTarget ), from ); - from.Mobile.SendMessage( "Where do you wish to blight?" ); - } + public override void BeginInvoke(Player from) + { + from.Mobile.BeginTarget(12, true, TargetFlags.None, new TargetStateCallback(Power_OnTarget), from); + from.Mobile.SendMessage("Where do you wish to blight?"); + } - private void Power_OnTarget( Mobile fromMobile, object obj, object state ) - { - Player from = state as Player; + private void Power_OnTarget(Mobile fromMobile, object obj, object state) + { + Player from = state as Player; - if ( !(obj is IPoint3D p) ) - return; + if (!(obj is IPoint3D p)) + return; - if ( !CheckInvoke( from ) ) - return; + if (!CheckInvoke(from)) + return; - bool powerFunctioned = false; + bool powerFunctioned = false; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - foreach ( Mobile mob in from.Mobile.GetMobilesInRange( 6 ) ) - { - if ( mob == from.Mobile || !SpellHelper.ValidIndirectTarget( from.Mobile, mob ) ) - continue; + foreach (Mobile mob in from.Mobile.GetMobilesInRange(6)) + { + if (mob == from.Mobile || !SpellHelper.ValidIndirectTarget(from.Mobile, mob)) + continue; - if ( mob.GetStatMod( "Holy Curse" ) != null ) - continue; + if (mob.GetStatMod("Holy Curse") != null) + continue; - if ( !from.Mobile.CanBeHarmful( mob, false ) ) - continue; + if (!from.Mobile.CanBeHarmful(mob, false)) + continue; - from.Mobile.DoHarmful( mob, true ); + from.Mobile.DoHarmful(mob, true); - mob.AddStatMod( new StatMod( StatType.All, "Holy Curse", -10, TimeSpan.FromMinutes( 30.0 ) ) ); + mob.AddStatMod(new StatMod(StatType.All, "Holy Curse", -10, TimeSpan.FromMinutes(30.0))); - mob.FixedParticles( 0x374A, 10, 15, 5028, EffectLayer.Waist ); - mob.PlaySound( 0x1FB ); + mob.FixedParticles(0x374A, 10, 15, 5028, EffectLayer.Waist); + mob.PlaySound(0x1FB); - powerFunctioned = true; - } + powerFunctioned = true; + } - if ( powerFunctioned ) - { - SpellHelper.Turn( from.Mobile, p ); + if (powerFunctioned) + { + SpellHelper.Turn(from.Mobile, p); - Effects.PlaySound( p, from.Mobile.Map, 0x1FB ); + Effects.PlaySound(p, from.Mobile.Map, 0x1FB); - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You curse the area." ); + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You curse the area."); - FinishInvoke( from ); - } - else - { - from.Mobile.FixedEffect( 0x3735, 6, 30 ); - from.Mobile.PlaySound( 0x5C ); - } - } - } -} + FinishInvoke(from); + } + else + { + from.Mobile.FixedEffect(0x3735, 6, 30); + from.Mobile.PlaySound(0x5C); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/SummonFamiliar.cs b/Scripts/Engines/Ethics/Evil/Powers/SummonFamiliar.cs index adfd5c8cc..f4f52d4ce 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/SummonFamiliar.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/SummonFamiliar.cs @@ -1,45 +1,46 @@ using System; using Server.Mobiles; +using Server.Network; namespace Server.Ethics.Evil { - public sealed class SummonFamiliar : Power - { - public SummonFamiliar() - { - m_Definition = new PowerDefinition( - 5, - "Summon Familiar", - "Trubechs Vingir", - "" - ); - } + public sealed class SummonFamiliar : Power + { + public SummonFamiliar() + { + m_Definition = new PowerDefinition( + 5, + "Summon Familiar", + "Trubechs Vingir", + "" + ); + } - public override void BeginInvoke( Player from ) - { - if ( from.Familiar != null && from.Familiar.Deleted ) - from.Familiar = null; + public override void BeginInvoke(Player from) + { + if (from.Familiar != null && from.Familiar.Deleted) + from.Familiar = null; - if ( from.Familiar != null ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You already have an unholy familiar." ); - return; - } + if (from.Familiar != null) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You already have an unholy familiar."); + return; + } - if ( ( from.Mobile.Followers + 1 ) > from.Mobile.FollowersMax ) - { - from.Mobile.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return; - } + if (from.Mobile.Followers + 1 > from.Mobile.FollowersMax) + { + from.Mobile.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return; + } - UnholyFamiliar familiar = new UnholyFamiliar(); + UnholyFamiliar familiar = new UnholyFamiliar(); - if ( BaseCreature.Summon( familiar, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours( 1.0 ) ) ) - { - from.Familiar = familiar; + if (BaseCreature.Summon(familiar, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours(1.0))) + { + from.Familiar = familiar; - FinishInvoke( from ); - } - } - } -} + FinishInvoke(from); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/UnholyItem.cs b/Scripts/Engines/Ethics/Evil/Powers/UnholyItem.cs index c0146b1b5..a161b9338 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/UnholyItem.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/UnholyItem.cs @@ -1,67 +1,71 @@ using Server.Items; +using Server.Network; +using Server.Targeting; namespace Server.Ethics.Evil { - public sealed class UnholyItem : Power - { - public UnholyItem() - { - m_Definition = new PowerDefinition( - 5, - "Unholy Item", - "Vidda K'balc", - "" - ); - } + public sealed class UnholyItem : Power + { + public UnholyItem() + { + m_Definition = new PowerDefinition( + 5, + "Unholy Item", + "Vidda K'balc", + "" + ); + } - public override void BeginInvoke( Player from ) - { - from.Mobile.BeginTarget( 12, false, Targeting.TargetFlags.None, new TargetStateCallback( Power_OnTarget ), from ); - from.Mobile.SendMessage( "Which item do you wish to imbue?" ); - } + public override void BeginInvoke(Player from) + { + from.Mobile.BeginTarget(12, false, TargetFlags.None, new TargetStateCallback(Power_OnTarget), from); + from.Mobile.SendMessage("Which item do you wish to imbue?"); + } - private void Power_OnTarget( Mobile fromMobile, object obj, object state ) - { - if (!(state is Player from)) - return; + private void Power_OnTarget(Mobile fromMobile, object obj, object state) + { + if (!(state is Player from)) + return; - if ( !(obj is Item item) ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You may not imbue that." ); - return; - } + if (!(obj is Item item)) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You may not imbue that."); + return; + } - if ( item.Parent != from.Mobile ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You may only imbue items you are wearing." ); - return; - } + if (item.Parent != from.Mobile) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You may only imbue items you are wearing."); + return; + } - if ( ( item.SavedFlags & 0x300 ) != 0 ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "That has already beem imbued." ); - return; - } + if ((item.SavedFlags & 0x300) != 0) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "That has already beem imbued."); + return; + } - bool canImbue = ( item is Spellbook || item is BaseClothing || item is BaseArmor || item is BaseWeapon ) && ( item.Name == null ); + bool canImbue = (item is Spellbook || item is BaseClothing || item is BaseArmor || item is BaseWeapon) && + item.Name == null; - if ( canImbue ) - { - if ( !CheckInvoke( from ) ) - return; + if (canImbue) + { + if (!CheckInvoke(from)) + return; - item.Hue = Ethic.Evil.Definition.PrimaryHue; - item.SavedFlags |= 0x200; + item.Hue = Ethic.Evil.Definition.PrimaryHue; + item.SavedFlags |= 0x200; - from.Mobile.FixedEffect( 0x375A, 10, 20 ); - from.Mobile.PlaySound( 0x209 ); + from.Mobile.FixedEffect(0x375A, 10, 20); + from.Mobile.PlaySound(0x209); - FinishInvoke( from ); - } - else - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You may not imbue that." ); - } - } - } -} + FinishInvoke(from); + } + else + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You may not imbue that."); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/UnholySense.cs b/Scripts/Engines/Ethics/Evil/Powers/UnholySense.cs index 256dddb99..3cf8f4ef3 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/UnholySense.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/UnholySense.cs @@ -1,93 +1,94 @@ using System; using System.Text; +using Server.Network; namespace Server.Ethics.Evil { - public sealed class UnholySense : Power - { - public UnholySense() - { - m_Definition = new PowerDefinition( - 0, - "Unholy Sense", - "Drewrok Velgo", - "" - ); - } + public sealed class UnholySense : Power + { + public UnholySense() + { + m_Definition = new PowerDefinition( + 0, + "Unholy Sense", + "Drewrok Velgo", + "" + ); + } - public override void BeginInvoke( Player from ) - { - Ethic opposition = Ethic.Hero; + public override void BeginInvoke(Player from) + { + Ethic opposition = Ethic.Hero; - int enemyCount = 0; + int enemyCount = 0; - int maxRange = 18 + from.Power; + int maxRange = 18 + from.Power; - Player primary = null; + Player primary = null; - foreach ( Player pl in opposition.Players ) - { - Mobile mob = pl.Mobile; + foreach (Player pl in opposition.Players) + { + Mobile mob = pl.Mobile; - if ( mob == null || mob.Map != from.Mobile.Map || !mob.Alive ) - continue; + if (mob == null || mob.Map != from.Mobile.Map || !mob.Alive) + continue; - if ( !mob.InRange( from.Mobile, Math.Max( 18, maxRange - pl.Power ) ) ) - continue; + if (!mob.InRange(from.Mobile, Math.Max(18, maxRange - pl.Power))) + continue; - if ( primary == null || pl.Power > primary.Power ) - primary = pl; + if (primary == null || pl.Power > primary.Power) + primary = pl; - ++enemyCount; - } + ++enemyCount; + } - StringBuilder sb = new StringBuilder(); + StringBuilder sb = new StringBuilder(); - sb.Append( "You sense " ); - sb.Append( enemyCount == 0 ? "no" : enemyCount.ToString() ); - sb.Append( enemyCount == 1 ? " enemy" : " enemies" ); + sb.Append("You sense "); + sb.Append(enemyCount == 0 ? "no" : enemyCount.ToString()); + sb.Append(enemyCount == 1 ? " enemy" : " enemies"); - if ( primary != null ) - { - sb.Append( ", and a strong presense" ); + if (primary != null) + { + sb.Append(", and a strong presense"); - switch ( from.Mobile.GetDirectionTo( primary.Mobile ) ) - { - case Direction.West: - sb.Append( " to the west." ); - break; - case Direction.East: - sb.Append( " to the east." ); - break; - case Direction.North: - sb.Append( " to the north." ); - break; - case Direction.South: - sb.Append( " to the south." ); - break; + switch (from.Mobile.GetDirectionTo(primary.Mobile)) + { + case Direction.West: + sb.Append(" to the west."); + break; + case Direction.East: + sb.Append(" to the east."); + break; + case Direction.North: + sb.Append(" to the north."); + break; + case Direction.South: + sb.Append(" to the south."); + break; - case Direction.Up: - sb.Append( " to the north-west." ); - break; - case Direction.Down: - sb.Append( " to the south-east." ); - break; - case Direction.Left: - sb.Append( " to the south-west." ); - break; - case Direction.Right: - sb.Append( " to the north-east." ); - break; - } - } - else - { - sb.Append( '.' ); - } + case Direction.Up: + sb.Append(" to the north-west."); + break; + case Direction.Down: + sb.Append(" to the south-east."); + break; + case Direction.Left: + sb.Append(" to the south-west."); + break; + case Direction.Right: + sb.Append(" to the north-east."); + break; + } + } + else + { + sb.Append('.'); + } - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x59, false, sb.ToString() ); + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x59, false, sb.ToString()); - FinishInvoke( from ); - } - } -} + FinishInvoke(from); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/UnholyShield.cs b/Scripts/Engines/Ethics/Evil/Powers/UnholyShield.cs index a00541497..466067dca 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/UnholyShield.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/UnholyShield.cs @@ -1,30 +1,34 @@ +using Server.Network; + namespace Server.Ethics.Evil { - public sealed class UnholyShield : Power - { - public UnholyShield() - { - m_Definition = new PowerDefinition( - 20, - "Unholy Shield", - "Velgo K'blac", - "" - ); - } + public sealed class UnholyShield : Power + { + public UnholyShield() + { + m_Definition = new PowerDefinition( + 20, + "Unholy Shield", + "Velgo K'blac", + "" + ); + } - public override void BeginInvoke( Player from ) - { - if ( from.IsShielded ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You are already under the protection of an unholy shield." ); - return; - } + public override void BeginInvoke(Player from) + { + if (from.IsShielded) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You are already under the protection of an unholy shield."); + return; + } - from.BeginShield(); + from.BeginShield(); - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You are now under the protection of an unholy shield." ); + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You are now under the protection of an unholy shield."); - FinishInvoke( from ); - } - } -} + FinishInvoke(from); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/UnholySteed.cs b/Scripts/Engines/Ethics/Evil/Powers/UnholySteed.cs index a60cc1495..4e20af9f5 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/UnholySteed.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/UnholySteed.cs @@ -1,44 +1,46 @@ using System; +using Server.Mobiles; +using Server.Network; namespace Server.Ethics.Evil { - public sealed class UnholySteed : Power - { - public UnholySteed() - { - m_Definition = new PowerDefinition( - 30, - "Unholy Steed", - "Trubechs Yeliab", - "" - ); - } + public sealed class UnholySteed : Power + { + public UnholySteed() + { + m_Definition = new PowerDefinition( + 30, + "Unholy Steed", + "Trubechs Yeliab", + "" + ); + } - public override void BeginInvoke( Player from ) - { - if ( from.Steed != null && from.Steed.Deleted ) - from.Steed = null; + public override void BeginInvoke(Player from) + { + if (from.Steed != null && from.Steed.Deleted) + from.Steed = null; - if ( from.Steed != null ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You already have an unholy steed." ); - return; - } + if (from.Steed != null) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You already have an unholy steed."); + return; + } - if ( ( from.Mobile.Followers + 1 ) > from.Mobile.FollowersMax ) - { - from.Mobile.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return; - } + if (from.Mobile.Followers + 1 > from.Mobile.FollowersMax) + { + from.Mobile.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return; + } - Mobiles.UnholySteed steed = new Mobiles.UnholySteed(); + Mobiles.UnholySteed steed = new Mobiles.UnholySteed(); - if ( Mobiles.BaseCreature.Summon( steed, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours( 1.0 ) ) ) - { - from.Steed = steed; + if (BaseCreature.Summon(steed, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours(1.0))) + { + from.Steed = steed; - FinishInvoke( from ); - } - } - } -} + FinishInvoke(from); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/UnholyWord.cs b/Scripts/Engines/Ethics/Evil/Powers/UnholyWord.cs index b8b828887..058ff80d9 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/UnholyWord.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/UnholyWord.cs @@ -1,19 +1,19 @@ namespace Server.Ethics.Evil { - public sealed class UnholyWord : Power - { - public UnholyWord() - { - m_Definition = new PowerDefinition( - 100, - "Unholy Word", - "Velgo Oostrac", - "" - ); - } + public sealed class UnholyWord : Power + { + public UnholyWord() + { + m_Definition = new PowerDefinition( + 100, + "Unholy Word", + "Velgo Oostrac", + "" + ); + } - public override void BeginInvoke( Player from ) - { - } - } -} + public override void BeginInvoke(Player from) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Evil/Powers/VileBlade.cs b/Scripts/Engines/Ethics/Evil/Powers/VileBlade.cs index a90ffda09..ca30b19a7 100644 --- a/Scripts/Engines/Ethics/Evil/Powers/VileBlade.cs +++ b/Scripts/Engines/Ethics/Evil/Powers/VileBlade.cs @@ -1,19 +1,19 @@ namespace Server.Ethics.Evil { - public sealed class VileBlade : Power - { - public VileBlade() - { - m_Definition = new PowerDefinition( - 10, - "Vile Blade", - "Velgo Reyam", - "" - ); - } + public sealed class VileBlade : Power + { + public VileBlade() + { + m_Definition = new PowerDefinition( + 10, + "Vile Blade", + "Velgo Reyam", + "" + ); + } - public override void BeginInvoke( Player from ) - { - } - } -} + public override void BeginInvoke(Player from) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Ethic.cs b/Scripts/Engines/Ethics/Hero/Ethic.cs index 898be1c2f..3c180cb06 100644 --- a/Scripts/Engines/Ethics/Hero/Ethic.cs +++ b/Scripts/Engines/Ethics/Hero/Ethic.cs @@ -2,36 +2,36 @@ using Server.Factions; namespace Server.Ethics.Hero { - public sealed class HeroEthic : Ethic - { - public HeroEthic() - { - m_Definition = new EthicDefinition( - 0x482, - "Hero", "(Hero)", - "I will defend the virtues", - new Power[] - { - new HolySense(), - new HolyItem(), - new SummonFamiliar(), - new HolyBlade(), - new Bless(), - new HolyShield(), - new HolySteed(), - new HolyWord() - } - ); - } + public sealed class HeroEthic : Ethic + { + public HeroEthic() + { + m_Definition = new EthicDefinition( + 0x482, + "Hero", "(Hero)", + "I will defend the virtues", + new Power[] + { + new HolySense(), + new HolyItem(), + new SummonFamiliar(), + new HolyBlade(), + new Bless(), + new HolyShield(), + new HolySteed(), + new HolyWord() + } + ); + } - public override bool IsEligible( Mobile mob ) - { - if ( mob.Kills >= 5 ) - return false; + public override bool IsEligible(Mobile mob) + { + if (mob.Kills >= 5) + return false; - Faction fac = Faction.Find( mob ); + Faction fac = Faction.Find(mob); - return ( fac is TrueBritannians || fac is CouncilOfMages ); - } - } + return fac is TrueBritannians || fac is CouncilOfMages; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Mobiles/HolyFamiliar.cs b/Scripts/Engines/Ethics/Hero/Mobiles/HolyFamiliar.cs index c90c69956..cad69eb9c 100644 --- a/Scripts/Engines/Ethics/Hero/Mobiles/HolyFamiliar.cs +++ b/Scripts/Engines/Ethics/Hero/Mobiles/HolyFamiliar.cs @@ -1,85 +1,84 @@ -using System; using Server.Ethics; namespace Server.Mobiles { - public class HolyFamiliar : BaseCreature - { - public override string CorpseName => "a holy corpse"; - public override bool IsDispellable => false; - public override bool IsBondable => false; + public class HolyFamiliar : BaseCreature + { + [Constructible] + public HolyFamiliar() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 100; + BaseSoundID = 0xE5; - public override string DefaultName => "a silver wolf"; + SetStr(96, 120); + SetDex(81, 105); + SetInt(36, 60); - [Constructible] - public HolyFamiliar() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 100; - BaseSoundID = 0xE5; + SetHits(58, 72); + SetMana(0); - SetStr( 96, 120 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetDamage(11, 17); - SetHits( 58, 72 ); - SetMana( 0 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 11, 17 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 10, 15); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 57.6, 75.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + Fame = 2500; + Karma = 2500; - SetSkill( SkillName.MagicResist, 57.6, 75.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + VirtualArmor = 22; - Fame = 2500; - Karma = 2500; + Tamable = false; + ControlSlots = 1; + } - VirtualArmor = 22; + public HolyFamiliar(Serial serial) + : base(serial) + { + } - Tamable = false; - ControlSlots = 1; - } + public override string CorpseName => "a holy corpse"; + public override bool IsDispellable => false; + public override bool IsBondable => false; - public override int Meat => 1; - public override int Hides => 7; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string DefaultName => "a silver wolf"; - public HolyFamiliar( Serial serial ) - : base( serial ) - { - } + public override int Meat => 1; + public override int Hides => 7; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override string ApplyNameSuffix( string suffix ) - { - if ( suffix.Length == 0 ) - suffix = Ethic.Hero.Definition.Adjunct.String; - else - suffix = string.Concat( suffix, " ", Ethic.Hero.Definition.Adjunct.String ); + public override string ApplyNameSuffix(string suffix) + { + if (suffix.Length == 0) + suffix = Ethic.Hero.Definition.Adjunct.String; + else + suffix = string.Concat(suffix, " ", Ethic.Hero.Definition.Adjunct.String); - return base.ApplyNameSuffix( suffix ); - } + return base.ApplyNameSuffix(suffix); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Mobiles/HolySteed.cs b/Scripts/Engines/Ethics/Hero/Mobiles/HolySteed.cs index 235140c2b..d8ceb96aa 100644 --- a/Scripts/Engines/Ethics/Hero/Mobiles/HolySteed.cs +++ b/Scripts/Engines/Ethics/Hero/Mobiles/HolySteed.cs @@ -1,89 +1,88 @@ -using System; using Server.Ethics; namespace Server.Mobiles { - public class HolySteed : BaseMount - { - public override string CorpseName => "a holy corpse"; - public override bool IsDispellable => false; - public override bool IsBondable => false; + public class HolySteed : BaseMount + { + [Constructible] + public HolySteed() + : base("a silver steed", 0x75, 0x3EA8, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + SetStr(496, 525); + SetDex(86, 105); + SetInt(86, 125); - public override bool HasBreath => true; - public override bool CanBreath => true; + SetHits(298, 315); - [Constructible] - public HolySteed() - : base( "a silver steed", 0x75, 0x3EA8, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - SetStr( 496, 525 ); - SetDex( 86, 105 ); - SetInt( 86, 125 ); + SetDamage(16, 22); - SetHits( 298, 315 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Fire, 40); + SetDamageType(ResistanceType.Energy, 20); - SetDamage( 16, 22 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Fire, 40 ); - SetDamageType( ResistanceType.Energy, 20 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 80.5, 92.5); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 14000; + Karma = 14000; - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 80.5, 92.5 ); + VirtualArmor = 60; - Fame = 14000; - Karma = 14000; + Tamable = false; + ControlSlots = 1; + } - VirtualArmor = 60; + public HolySteed(Serial serial) + : base(serial) + { + } - Tamable = false; - ControlSlots = 1; - } + public override string CorpseName => "a holy corpse"; + public override bool IsDispellable => false; + public override bool IsBondable => false; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override bool HasBreath => true; + public override bool CanBreath => true; - public HolySteed( Serial serial ) - : base( serial ) - { - } + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override string ApplyNameSuffix( string suffix ) - { - if ( suffix.Length == 0 ) - suffix = Ethic.Hero.Definition.Adjunct.String; - else - suffix = string.Concat( suffix, " ", Ethic.Hero.Definition.Adjunct.String ); + public override string ApplyNameSuffix(string suffix) + { + if (suffix.Length == 0) + suffix = Ethic.Hero.Definition.Adjunct.String; + else + suffix = string.Concat(suffix, " ", Ethic.Hero.Definition.Adjunct.String); - return base.ApplyNameSuffix( suffix ); - } + return base.ApplyNameSuffix(suffix); + } - public override void OnDoubleClick( Mobile from ) - { - if ( Ethic.Find( from ) != Ethic.Hero ) - from.SendMessage( "You may not ride this steed." ); - else - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (Ethic.Find(from) != Ethic.Hero) + from.SendMessage("You may not ride this steed."); + else + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/Bless.cs b/Scripts/Engines/Ethics/Hero/Powers/Bless.cs index 753f7c4ec..cfad8bd99 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/Bless.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/Bless.cs @@ -1,77 +1,79 @@ using System; +using Server.Network; using Server.Spells; +using Server.Targeting; namespace Server.Ethics.Hero { - public sealed class Bless : Power - { - public Bless() - { - m_Definition = new PowerDefinition( - 15, - "Bless", - "Erstok Ontawl", - "" - ); - } + public sealed class Bless : Power + { + public Bless() + { + m_Definition = new PowerDefinition( + 15, + "Bless", + "Erstok Ontawl", + "" + ); + } - public override void BeginInvoke( Player from ) - { - from.Mobile.BeginTarget( 12, true, Targeting.TargetFlags.None, new TargetStateCallback( Power_OnTarget ), from ); - from.Mobile.SendMessage( "Where do you wish to bless?" ); - } + public override void BeginInvoke(Player from) + { + from.Mobile.BeginTarget(12, true, TargetFlags.None, new TargetStateCallback(Power_OnTarget), from); + from.Mobile.SendMessage("Where do you wish to bless?"); + } - private void Power_OnTarget( Mobile fromMobile, object obj, object state ) - { - if (!(state is Player from)) - return; + private void Power_OnTarget(Mobile fromMobile, object obj, object state) + { + if (!(state is Player from)) + return; - if ( !(obj is IPoint3D p) ) - return; + if (!(obj is IPoint3D p)) + return; - if ( !CheckInvoke( from ) ) - return; + if (!CheckInvoke(from)) + return; - bool powerFunctioned = false; + bool powerFunctioned = false; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - foreach ( Mobile mob in from.Mobile.GetMobilesInRange( 6 ) ) - { - if ( mob != from.Mobile && SpellHelper.ValidIndirectTarget( from.Mobile, mob ) ) - continue; + foreach (Mobile mob in from.Mobile.GetMobilesInRange(6)) + { + if (mob != from.Mobile && SpellHelper.ValidIndirectTarget(from.Mobile, mob)) + continue; - if ( mob.GetStatMod( "Holy Bless" ) != null ) - continue; + if (mob.GetStatMod("Holy Bless") != null) + continue; - if ( !from.Mobile.CanBeBeneficial( mob, false ) ) - continue; + if (!from.Mobile.CanBeBeneficial(mob, false)) + continue; - from.Mobile.DoBeneficial( mob ); + from.Mobile.DoBeneficial(mob); - mob.AddStatMod( new StatMod( StatType.All, "Holy Bless", 10, TimeSpan.FromMinutes( 30.0 ) ) ); + mob.AddStatMod(new StatMod(StatType.All, "Holy Bless", 10, TimeSpan.FromMinutes(30.0))); - mob.FixedParticles( 0x373A, 10, 15, 5018, EffectLayer.Waist ); - mob.PlaySound( 0x1EA ); + mob.FixedParticles(0x373A, 10, 15, 5018, EffectLayer.Waist); + mob.PlaySound(0x1EA); - powerFunctioned = true; - } + powerFunctioned = true; + } - if ( powerFunctioned ) - { - SpellHelper.Turn( from.Mobile, p ); + if (powerFunctioned) + { + SpellHelper.Turn(from.Mobile, p); - Effects.PlaySound( p, from.Mobile.Map, 0x299 ); + Effects.PlaySound(p, from.Mobile.Map, 0x299); - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You consecrate the area." ); + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You consecrate the area."); - FinishInvoke( from ); - } - else - { - from.Mobile.FixedEffect( 0x3735, 6, 30 ); - from.Mobile.PlaySound( 0x5C ); - } - } - } -} + FinishInvoke(from); + } + else + { + from.Mobile.FixedEffect(0x3735, 6, 30); + from.Mobile.PlaySound(0x5C); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/HolyBlade.cs b/Scripts/Engines/Ethics/Hero/Powers/HolyBlade.cs index cf0801e5e..3a199b687 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/HolyBlade.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/HolyBlade.cs @@ -1,19 +1,19 @@ namespace Server.Ethics.Hero { - public sealed class HolyBlade : Power - { - public HolyBlade() - { - m_Definition = new PowerDefinition( - 10, - "Holy Blade", - "Erstok Reyam", - "" - ); - } + public sealed class HolyBlade : Power + { + public HolyBlade() + { + m_Definition = new PowerDefinition( + 10, + "Holy Blade", + "Erstok Reyam", + "" + ); + } - public override void BeginInvoke( Player from ) - { - } - } -} + public override void BeginInvoke(Player from) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/HolyItem.cs b/Scripts/Engines/Ethics/Hero/Powers/HolyItem.cs index fce594f28..8b4f058f8 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/HolyItem.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/HolyItem.cs @@ -1,67 +1,71 @@ using Server.Items; +using Server.Network; +using Server.Targeting; namespace Server.Ethics.Hero { - public sealed class HolyItem : Power - { - public HolyItem() - { - m_Definition = new PowerDefinition( - 5, - "Holy Item", - "Vidda K'balc", - "" - ); - } + public sealed class HolyItem : Power + { + public HolyItem() + { + m_Definition = new PowerDefinition( + 5, + "Holy Item", + "Vidda K'balc", + "" + ); + } - public override void BeginInvoke( Player from ) - { - from.Mobile.BeginTarget( 12, false, Targeting.TargetFlags.None, new TargetStateCallback( Power_OnTarget ), from ); - from.Mobile.SendMessage( "Which item do you wish to imbue?" ); - } + public override void BeginInvoke(Player from) + { + from.Mobile.BeginTarget(12, false, TargetFlags.None, new TargetStateCallback(Power_OnTarget), from); + from.Mobile.SendMessage("Which item do you wish to imbue?"); + } - private void Power_OnTarget( Mobile fromMobile, object obj, object state ) - { - if (!(state is Player from)) - return; + private void Power_OnTarget(Mobile fromMobile, object obj, object state) + { + if (!(state is Player from)) + return; - if ( !(obj is Item item) ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You may not imbue that." ); - return; - } + if (!(obj is Item item)) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You may not imbue that."); + return; + } - if ( item.Parent != from.Mobile ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You may only imbue items you are wearing." ); - return; - } + if (item.Parent != from.Mobile) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You may only imbue items you are wearing."); + return; + } - if ( ( item.SavedFlags & 0x300 ) != 0 ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "That has already beem imbued." ); - return; - } + if ((item.SavedFlags & 0x300) != 0) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "That has already beem imbued."); + return; + } - bool canImbue = ( item is Spellbook || item is BaseClothing || item is BaseArmor || item is BaseWeapon ) && ( item.Name == null ); + bool canImbue = (item is Spellbook || item is BaseClothing || item is BaseArmor || item is BaseWeapon) && + item.Name == null; - if ( canImbue ) - { - if ( !CheckInvoke( from ) ) - return; + if (canImbue) + { + if (!CheckInvoke(from)) + return; - item.Hue = Ethic.Hero.Definition.PrimaryHue; - item.SavedFlags |= 0x100; + item.Hue = Ethic.Hero.Definition.PrimaryHue; + item.SavedFlags |= 0x100; - from.Mobile.FixedEffect( 0x375A, 10, 20 ); - from.Mobile.PlaySound( 0x209 ); + from.Mobile.FixedEffect(0x375A, 10, 20); + from.Mobile.PlaySound(0x209); - FinishInvoke( from ); - } - else - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You may not imbue that." ); - } - } - } -} + FinishInvoke(from); + } + else + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You may not imbue that."); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/HolySense.cs b/Scripts/Engines/Ethics/Hero/Powers/HolySense.cs index b4a114173..2aa21edd1 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/HolySense.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/HolySense.cs @@ -1,93 +1,94 @@ using System; using System.Text; +using Server.Network; namespace Server.Ethics.Hero { - public sealed class HolySense : Power - { - public HolySense() - { - m_Definition = new PowerDefinition( - 0, - "Holy Sense", - "Drewrok Erstok", - "" - ); - } + public sealed class HolySense : Power + { + public HolySense() + { + m_Definition = new PowerDefinition( + 0, + "Holy Sense", + "Drewrok Erstok", + "" + ); + } - public override void BeginInvoke( Player from ) - { - Ethic opposition = Ethic.Evil; + public override void BeginInvoke(Player from) + { + Ethic opposition = Ethic.Evil; - int enemyCount = 0; + int enemyCount = 0; - int maxRange = 18 + from.Power; + int maxRange = 18 + from.Power; - Player primary = null; + Player primary = null; - foreach ( Player pl in opposition.Players ) - { - Mobile mob = pl.Mobile; + foreach (Player pl in opposition.Players) + { + Mobile mob = pl.Mobile; - if ( mob == null || mob.Map != from.Mobile.Map || !mob.Alive ) - continue; + if (mob == null || mob.Map != from.Mobile.Map || !mob.Alive) + continue; - if ( !mob.InRange( from.Mobile, Math.Max( 18, maxRange - pl.Power ) ) ) - continue; + if (!mob.InRange(from.Mobile, Math.Max(18, maxRange - pl.Power))) + continue; - if ( primary == null || pl.Power > primary.Power ) - primary = pl; + if (primary == null || pl.Power > primary.Power) + primary = pl; - ++enemyCount; - } + ++enemyCount; + } - StringBuilder sb = new StringBuilder(); + StringBuilder sb = new StringBuilder(); - sb.Append( "You sense " ); - sb.Append( enemyCount == 0 ? "no" : enemyCount.ToString() ); - sb.Append( enemyCount == 1 ? " enemy" : " enemies" ); + sb.Append("You sense "); + sb.Append(enemyCount == 0 ? "no" : enemyCount.ToString()); + sb.Append(enemyCount == 1 ? " enemy" : " enemies"); - if ( primary != null ) - { - sb.Append( ", and a strong presense" ); + if (primary != null) + { + sb.Append(", and a strong presense"); - switch ( from.Mobile.GetDirectionTo( primary.Mobile ) ) - { - case Direction.West: - sb.Append( " to the west." ); - break; - case Direction.East: - sb.Append( " to the east." ); - break; - case Direction.North: - sb.Append( " to the north." ); - break; - case Direction.South: - sb.Append( " to the south." ); - break; + switch (from.Mobile.GetDirectionTo(primary.Mobile)) + { + case Direction.West: + sb.Append(" to the west."); + break; + case Direction.East: + sb.Append(" to the east."); + break; + case Direction.North: + sb.Append(" to the north."); + break; + case Direction.South: + sb.Append(" to the south."); + break; - case Direction.Up: - sb.Append( " to the north-west." ); - break; - case Direction.Down: - sb.Append( " to the south-east." ); - break; - case Direction.Left: - sb.Append( " to the south-west." ); - break; - case Direction.Right: - sb.Append( " to the north-east." ); - break; - } - } - else - { - sb.Append( '.' ); - } + case Direction.Up: + sb.Append(" to the north-west."); + break; + case Direction.Down: + sb.Append(" to the south-east."); + break; + case Direction.Left: + sb.Append(" to the south-west."); + break; + case Direction.Right: + sb.Append(" to the north-east."); + break; + } + } + else + { + sb.Append('.'); + } - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x59, false, sb.ToString() ); + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x59, false, sb.ToString()); - FinishInvoke( from ); - } - } -} + FinishInvoke(from); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/HolyShield.cs b/Scripts/Engines/Ethics/Hero/Powers/HolyShield.cs index c8799b925..576fbbde4 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/HolyShield.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/HolyShield.cs @@ -1,30 +1,34 @@ +using Server.Network; + namespace Server.Ethics.Hero { - public sealed class HolyShield : Power - { - public HolyShield() - { - m_Definition = new PowerDefinition( - 20, - "Holy Shield", - "Erstok K'blac", - "" - ); - } + public sealed class HolyShield : Power + { + public HolyShield() + { + m_Definition = new PowerDefinition( + 20, + "Holy Shield", + "Erstok K'blac", + "" + ); + } - public override void BeginInvoke( Player from ) - { - if ( from.IsShielded ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You are already under the protection of a holy shield." ); - return; - } + public override void BeginInvoke(Player from) + { + if (from.IsShielded) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You are already under the protection of a holy shield."); + return; + } - from.BeginShield(); + from.BeginShield(); - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You are now under the protection of a holy shield." ); + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You are now under the protection of a holy shield."); - FinishInvoke( from ); - } - } -} + FinishInvoke(from); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/HolySteed.cs b/Scripts/Engines/Ethics/Hero/Powers/HolySteed.cs index 1c859e089..0f489b2dd 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/HolySteed.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/HolySteed.cs @@ -1,44 +1,46 @@ using System; +using Server.Mobiles; +using Server.Network; namespace Server.Ethics.Hero { - public sealed class HolySteed : Power - { - public HolySteed() - { - m_Definition = new PowerDefinition( - 30, - "Holy Steed", - "Trubechs Yeliab", - "" - ); - } + public sealed class HolySteed : Power + { + public HolySteed() + { + m_Definition = new PowerDefinition( + 30, + "Holy Steed", + "Trubechs Yeliab", + "" + ); + } - public override void BeginInvoke( Player from ) - { - if ( from.Steed != null && from.Steed.Deleted ) - from.Steed = null; + public override void BeginInvoke(Player from) + { + if (from.Steed != null && from.Steed.Deleted) + from.Steed = null; - if ( from.Steed != null ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You already have a holy steed." ); - return; - } + if (from.Steed != null) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You already have a holy steed."); + return; + } - if ( ( from.Mobile.Followers + 1 ) > from.Mobile.FollowersMax ) - { - from.Mobile.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return; - } + if (from.Mobile.Followers + 1 > from.Mobile.FollowersMax) + { + from.Mobile.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return; + } - Mobiles.HolySteed steed = new Mobiles.HolySteed(); + Mobiles.HolySteed steed = new Mobiles.HolySteed(); - if ( Mobiles.BaseCreature.Summon( steed, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours( 1.0 ) ) ) - { - from.Steed = steed; + if (BaseCreature.Summon(steed, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours(1.0))) + { + from.Steed = steed; - FinishInvoke( from ); - } - } - } -} + FinishInvoke(from); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/HolyWord.cs b/Scripts/Engines/Ethics/Hero/Powers/HolyWord.cs index 1830182e5..39de95af5 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/HolyWord.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/HolyWord.cs @@ -1,19 +1,19 @@ namespace Server.Ethics.Hero { - public sealed class HolyWord : Power - { - public HolyWord() - { - m_Definition = new PowerDefinition( - 100, - "Holy Word", - "Erstok Oostrac", - "" - ); - } + public sealed class HolyWord : Power + { + public HolyWord() + { + m_Definition = new PowerDefinition( + 100, + "Holy Word", + "Erstok Oostrac", + "" + ); + } - public override void BeginInvoke( Player from ) - { - } - } -} + public override void BeginInvoke(Player from) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Ethics/Hero/Powers/SummonFamiliar.cs b/Scripts/Engines/Ethics/Hero/Powers/SummonFamiliar.cs index 47194e0c1..b6935fa38 100644 --- a/Scripts/Engines/Ethics/Hero/Powers/SummonFamiliar.cs +++ b/Scripts/Engines/Ethics/Hero/Powers/SummonFamiliar.cs @@ -1,45 +1,46 @@ using System; using Server.Mobiles; +using Server.Network; namespace Server.Ethics.Hero { - public sealed class SummonFamiliar : Power - { - public SummonFamiliar() - { - m_Definition = new PowerDefinition( - 5, - "Summon Familiar", - "Trubechs Vingir", - "" - ); - } + public sealed class SummonFamiliar : Power + { + public SummonFamiliar() + { + m_Definition = new PowerDefinition( + 5, + "Summon Familiar", + "Trubechs Vingir", + "" + ); + } - public override void BeginInvoke( Player from ) - { - if ( from.Familiar != null && from.Familiar.Deleted ) - from.Familiar = null; + public override void BeginInvoke(Player from) + { + if (from.Familiar != null && from.Familiar.Deleted) + from.Familiar = null; - if ( from.Familiar != null ) - { - from.Mobile.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, false, "You already have a holy familiar." ); - return; - } + if (from.Familiar != null) + { + from.Mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You already have a holy familiar."); + return; + } - if ( ( from.Mobile.Followers + 1 ) > from.Mobile.FollowersMax ) - { - from.Mobile.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return; - } + if (from.Mobile.Followers + 1 > from.Mobile.FollowersMax) + { + from.Mobile.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return; + } - HolyFamiliar familiar = new HolyFamiliar(); + HolyFamiliar familiar = new HolyFamiliar(); - if ( BaseCreature.Summon( familiar, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours( 1.0 ) ) ) - { - from.Familiar = familiar; + if (BaseCreature.Summon(familiar, from.Mobile, from.Mobile.Location, 0x217, TimeSpan.FromHours(1.0))) + { + from.Familiar = familiar; - FinishInvoke( from ); - } - } - } -} + FinishInvoke(from); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Election.cs b/Scripts/Engines/Factions/Core/Election.cs index a99e98ef2..5778be84d 100644 --- a/Scripts/Engines/Factions/Core/Election.cs +++ b/Scripts/Engines/Factions/Core/Election.cs @@ -1,536 +1,553 @@ using System; +using System.Collections.Generic; using System.Net; using Server.Mobiles; -using System.Collections.Generic; namespace Server.Factions { - public class Election - { - public static readonly TimeSpan PendingPeriod = TimeSpan.FromDays( 5.0 ); - public static readonly TimeSpan CampaignPeriod = TimeSpan.FromDays( 1.0 ); - public static readonly TimeSpan VotingPeriod = TimeSpan.FromDays( 3.0 ); + public class Election + { + public const int MaxCandidates = 10; + public const int CandidateRank = 5; + public static readonly TimeSpan PendingPeriod = TimeSpan.FromDays(5.0); + public static readonly TimeSpan CampaignPeriod = TimeSpan.FromDays(1.0); + public static readonly TimeSpan VotingPeriod = TimeSpan.FromDays(3.0); + + private Timer m_Timer; + + public Election(Faction faction) + { + Faction = faction; + Candidates = new List(); + + StartTimer(); + } + + public Election(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 0: + { + Faction = Faction.ReadReference(reader); + + LastStateTime = reader.ReadDateTime(); + CurrentState = (ElectionState)reader.ReadEncodedInt(); + + Candidates = new List(); + + int count = reader.ReadEncodedInt(); + + for (int i = 0; i < count; ++i) + { + Candidate cd = new Candidate(reader); + + if (cd.Mobile != null) + Candidates.Add(cd); + } + + break; + } + } + + StartTimer(); + } + + public Faction Faction{ get; } + + public List Candidates{ get; } + + public ElectionState State + { + get => CurrentState; + set + { + CurrentState = value; + LastStateTime = DateTime.UtcNow; + } + } + + public DateTime LastStateTime{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public ElectionState CurrentState{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public TimeSpan NextStateTime + { + get + { + TimeSpan period; + + switch (CurrentState) + { + default: + case ElectionState.Pending: + period = PendingPeriod; + break; + case ElectionState.Election: + period = VotingPeriod; + break; + case ElectionState.Campaign: + period = CampaignPeriod; + break; + } + + TimeSpan until = LastStateTime + period - DateTime.UtcNow; + + if (until < TimeSpan.Zero) + until = TimeSpan.Zero; + + return until; + } + set + { + TimeSpan period; + + switch (CurrentState) + { + default: + case ElectionState.Pending: + period = PendingPeriod; + break; + case ElectionState.Election: + period = VotingPeriod; + break; + case ElectionState.Campaign: + period = CampaignPeriod; + break; + } + + LastStateTime = DateTime.UtcNow - period + value; + } + } + + public void StartTimer() + { + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(1.0), TimeSpan.FromMinutes(1.0), Slice); + } + + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + Faction.WriteReference(writer, Faction); + + writer.Write(LastStateTime); + writer.WriteEncodedInt((int)CurrentState); + + writer.WriteEncodedInt(Candidates.Count); + + for (int i = 0; i < Candidates.Count; ++i) + Candidates[i].Serialize(writer); + } + + public void AddCandidate(Mobile mob) + { + if (IsCandidate(mob)) + return; + + Candidates.Add(new Candidate(mob)); + mob.SendLocalizedMessage(1010117); // You are now running for office. + } + + public void RemoveVoter(Mobile mob) + { + if (CurrentState == ElectionState.Election) + for (int i = 0; i < Candidates.Count; ++i) + { + List voters = Candidates[i].Voters; + + for (int j = 0; j < voters.Count; ++j) + { + Voter voter = voters[j]; + + if (voter.From == mob) + voters.RemoveAt(j--); + } + } + } + + public void RemoveCandidate(Mobile mob) + { + Candidate cd = FindCandidate(mob); + + if (cd == null) + return; + + Candidates.Remove(cd); + mob.SendLocalizedMessage(1038031); + + if (CurrentState == ElectionState.Election) + { + if (Candidates.Count == 1) + { + Faction.Broadcast( + 1038031); // There are no longer any valid candidates in the Faction Commander election. + + Candidate winner = Candidates[0]; + + Mobile winMob = winner.Mobile; + PlayerState pl = PlayerState.Find(winMob); + + if (pl == null || pl.Faction != Faction || winMob == Faction.Commander) + { + Faction.Broadcast(1038026); // Faction leadership has not changed. + } + else + { + Faction.Broadcast(1038028); // The faction has a new commander. + Faction.Commander = winMob; + } + + Candidates.Clear(); + State = ElectionState.Pending; + } + else if (Candidates.Count == 0) // well, I guess this'll never happen + { + Faction.Broadcast( + 1038031); // There are no longer any valid candidates in the Faction Commander election. + + Candidates.Clear(); + State = ElectionState.Pending; + } + } + } + + public bool IsCandidate(Mobile mob) + { + return FindCandidate(mob) != null; + } + + public bool CanVote(Mobile mob) + { + return CurrentState == ElectionState.Election && !HasVoted(mob); + } + + public bool HasVoted(Mobile mob) + { + return FindVoter(mob) != null; + } + + public Candidate FindCandidate(Mobile mob) + { + for (int i = 0; i < Candidates.Count; ++i) + if (Candidates[i].Mobile == mob) + return Candidates[i]; + + return null; + } + + public Candidate FindVoter(Mobile mob) + { + for (int i = 0; i < Candidates.Count; ++i) + { + List voters = Candidates[i].Voters; + + for (int j = 0; j < voters.Count; ++j) + { + Voter voter = voters[j]; + + if (voter.From == mob) + return Candidates[i]; + } + } + + return null; + } + + public bool CanBeCandidate(Mobile mob) + { + if (IsCandidate(mob)) + return false; + + if (Candidates.Count >= MaxCandidates) + return false; + + if (CurrentState != ElectionState.Campaign) + return false; // sanity.. + + PlayerState pl = PlayerState.Find(mob); + + return pl != null && pl.Faction == Faction && pl.Rank.Rank >= CandidateRank; + } + + public void Slice() + { + if (Faction.Election != this) + { + m_Timer?.Stop(); + + m_Timer = null; + + return; + } + + switch (CurrentState) + { + case ElectionState.Pending: + { + if (LastStateTime + PendingPeriod > DateTime.UtcNow) + break; + + Faction.Broadcast(1038023); // Campaigning for the Faction Commander election has begun. + + Candidates.Clear(); + State = ElectionState.Campaign; + + break; + } + case ElectionState.Campaign: + { + if (LastStateTime + CampaignPeriod > DateTime.UtcNow) + break; + + if (Candidates.Count == 0) + { + Faction.Broadcast(1038025); // Nobody ran for office. + State = ElectionState.Pending; + } + else if (Candidates.Count == 1) + { + Faction.Broadcast(1038029); // Only one member ran for office. + + Candidate winner = Candidates[0]; + + Mobile mob = winner.Mobile; + PlayerState pl = PlayerState.Find(mob); + + if (pl == null || pl.Faction != Faction || mob == Faction.Commander) + { + Faction.Broadcast(1038026); // Faction leadership has not changed. + } + else + { + Faction.Broadcast(1038028); // The faction has a new commander. + Faction.Commander = mob; + } + + Candidates.Clear(); + State = ElectionState.Pending; + } + else + { + Faction.Broadcast(1038030); + State = ElectionState.Election; + } + + break; + } + case ElectionState.Election: + { + if (LastStateTime + VotingPeriod > DateTime.UtcNow) + break; + + Faction.Broadcast(1038024); // The results for the Faction Commander election are in + + Candidate winner = null; + + for (int i = 0; i < Candidates.Count; ++i) + { + Candidate cd = Candidates[i]; + + PlayerState pl = PlayerState.Find(cd.Mobile); + + if (pl == null || pl.Faction != Faction) + continue; + + //cd.CleanMuleVotes(); + + if (winner == null || cd.Votes > winner.Votes) + winner = cd; + } - public const int MaxCandidates = 10; - public const int CandidateRank = 5; + if (winner == null) + { + Faction.Broadcast(1038026); // Faction leadership has not changed. + } + else if (winner.Mobile == Faction.Commander) + { + Faction.Broadcast(1038027); // The incumbent won the election. + } + else + { + Faction.Broadcast(1038028); // The faction has a new commander. + Faction.Commander = winner.Mobile; + } + + Candidates.Clear(); + State = ElectionState.Pending; + + break; + } + } + } + } + + public class Voter + { + public Voter(Mobile from, Mobile candidate) + { + From = from; + Candidate = candidate; + + if (From.NetState != null) + Address = From.NetState.Address; + else + Address = IPAddress.None; + + Time = DateTime.UtcNow; + } + + public Voter(GenericReader reader, Mobile candidate) + { + Candidate = candidate; + + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 0: + { + From = reader.ReadMobile(); + Address = Utility.Intern(reader.ReadIPAddress()); + Time = reader.ReadDateTime(); + + break; + } + } + } + + public Mobile From{ get; } + + public Mobile Candidate{ get; } + + public IPAddress Address{ get; } - public Faction Faction { get; } + public DateTime Time{ get; } - public List Candidates { get; } + public object[] AcquireFields() + { + TimeSpan gameTime = TimeSpan.Zero; - public ElectionState State{ get => CurrentState; - set{ CurrentState = value; LastStateTime = DateTime.UtcNow; } } - public DateTime LastStateTime { get; private set; } + if (From is PlayerMobile mobile) + gameTime = mobile.GameTime; - [CommandProperty( AccessLevel.GameMaster )] - public ElectionState CurrentState { get; private set; } + int kp = 0; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public TimeSpan NextStateTime - { - get - { - TimeSpan period; + PlayerState pl = PlayerState.Find(From); - switch ( CurrentState ) - { - default: - case ElectionState.Pending: period = PendingPeriod; break; - case ElectionState.Election: period = VotingPeriod; break; - case ElectionState.Campaign: period = CampaignPeriod; break; - } + if (pl != null) + kp = pl.KillPoints; - TimeSpan until = (LastStateTime + period) - DateTime.UtcNow; + int sk = From.Skills.Total; - if ( until < TimeSpan.Zero ) - until = TimeSpan.Zero; - - return until; - } - set - { - TimeSpan period; - - switch ( CurrentState ) - { - default: - case ElectionState.Pending: period = PendingPeriod; break; - case ElectionState.Election: period = VotingPeriod; break; - case ElectionState.Campaign: period = CampaignPeriod; break; - } - - LastStateTime = DateTime.UtcNow - period + value; - } - } + int factorSkills = 50 + sk * 100 / 10000; + int factorKillPts = 100 + kp * 2; + int factorGameTime = 50 + (int)(gameTime.Ticks * 100 / TimeSpan.TicksPerDay); - private Timer m_Timer; - - public void StartTimer() - { - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 1.0 ), TimeSpan.FromMinutes( 1.0 ), Slice ); - } - - public Election( Faction faction ) - { - Faction = faction; - Candidates = new List(); + int totalFactor = factorSkills * factorKillPts * Math.Max(factorGameTime, 100) / 10000; - StartTimer(); - } - - public Election( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 0: - { - Faction = Faction.ReadReference( reader ); - - LastStateTime = reader.ReadDateTime(); - CurrentState = (ElectionState)reader.ReadEncodedInt(); - - Candidates = new List(); - - int count = reader.ReadEncodedInt(); - - for ( int i = 0; i < count; ++i ) - { - Candidate cd = new Candidate( reader ); - - if ( cd.Mobile != null ) - Candidates.Add( cd ); - } - - break; - } - } - - StartTimer(); - } - - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - Faction.WriteReference( writer, Faction ); - - writer.Write( (DateTime) LastStateTime ); - writer.WriteEncodedInt( (int) CurrentState ); - - writer.WriteEncodedInt( Candidates.Count ); - - for ( int i = 0; i < Candidates.Count; ++i ) - Candidates[i].Serialize( writer ); - } - - public void AddCandidate( Mobile mob ) - { - if ( IsCandidate( mob ) ) - return; - - Candidates.Add( new Candidate( mob ) ); - mob.SendLocalizedMessage( 1010117 ); // You are now running for office. - } - - public void RemoveVoter( Mobile mob ) - { - if ( CurrentState == ElectionState.Election ) - { - for ( int i = 0; i < Candidates.Count; ++i ) - { - List voters = Candidates[i].Voters; - - for ( int j = 0; j < voters.Count; ++j ) - { - Voter voter = voters[j]; - - if ( voter.From == mob ) - voters.RemoveAt( j-- ); - } - } - } - } - - public void RemoveCandidate( Mobile mob ) - { - Candidate cd = FindCandidate( mob ); - - if ( cd == null ) - return; - - Candidates.Remove( cd ); - mob.SendLocalizedMessage( 1038031 ); - - if ( CurrentState == ElectionState.Election ) - { - if ( Candidates.Count == 1 ) - { - Faction.Broadcast( 1038031 ); // There are no longer any valid candidates in the Faction Commander election. - - Candidate winner = Candidates[0]; - - Mobile winMob = winner.Mobile; - PlayerState pl = PlayerState.Find( winMob ); - - if ( pl == null || pl.Faction != Faction || winMob == Faction.Commander ) - { - Faction.Broadcast( 1038026 ); // Faction leadership has not changed. - } - else - { - Faction.Broadcast( 1038028 ); // The faction has a new commander. - Faction.Commander = winMob; - } - - Candidates.Clear(); - State = ElectionState.Pending; - } - else if ( Candidates.Count == 0 ) // well, I guess this'll never happen - { - Faction.Broadcast( 1038031 ); // There are no longer any valid candidates in the Faction Commander election. - - Candidates.Clear(); - State = ElectionState.Pending; - } - } - } - - public bool IsCandidate( Mobile mob ) - { - return ( FindCandidate( mob ) != null ); - } - - public bool CanVote( Mobile mob ) - { - return ( CurrentState == ElectionState.Election && !HasVoted( mob ) ); - } - - public bool HasVoted( Mobile mob ) - { - return ( FindVoter( mob ) != null ); - } - - public Candidate FindCandidate( Mobile mob ) - { - for ( int i = 0; i < Candidates.Count; ++i ) - { - if ( Candidates[i].Mobile == mob ) - return Candidates[i]; - } - - return null; - } - - public Candidate FindVoter( Mobile mob ) - { - for ( int i = 0; i < Candidates.Count; ++i ) - { - List voters = Candidates[i].Voters; - - for ( int j = 0; j < voters.Count; ++j ) - { - Voter voter = voters[j]; - - if ( voter.From == mob ) - return Candidates[i]; - } - } - - return null; - } - - public bool CanBeCandidate( Mobile mob ) - { - if ( IsCandidate( mob ) ) - return false; - - if ( Candidates.Count >= MaxCandidates ) - return false; - - if ( CurrentState != ElectionState.Campaign ) - return false; // sanity.. - - PlayerState pl = PlayerState.Find( mob ); - - return ( pl != null && pl.Faction == Faction && pl.Rank.Rank >= CandidateRank ); - } - - public void Slice() - { - if ( Faction.Election != this ) - { - m_Timer?.Stop(); - - m_Timer = null; - - return; - } - - switch ( CurrentState ) - { - case ElectionState.Pending: - { - if ( (LastStateTime + PendingPeriod) > DateTime.UtcNow ) - break; - - Faction.Broadcast( 1038023 ); // Campaigning for the Faction Commander election has begun. - - Candidates.Clear(); - State = ElectionState.Campaign; - - break; - } - case ElectionState.Campaign: - { - if ( (LastStateTime + CampaignPeriod) > DateTime.UtcNow ) - break; - - if ( Candidates.Count == 0 ) - { - Faction.Broadcast( 1038025 ); // Nobody ran for office. - State = ElectionState.Pending; - } - else if ( Candidates.Count == 1 ) - { - Faction.Broadcast( 1038029 ); // Only one member ran for office. - - Candidate winner = Candidates[0]; - - Mobile mob = winner.Mobile; - PlayerState pl = PlayerState.Find( mob ); - - if ( pl == null || pl.Faction != Faction || mob == Faction.Commander ) - { - Faction.Broadcast( 1038026 ); // Faction leadership has not changed. - } - else - { - Faction.Broadcast( 1038028 ); // The faction has a new commander. - Faction.Commander = mob; - } - - Candidates.Clear(); - State = ElectionState.Pending; - } - else - { - Faction.Broadcast( 1038030 ); - State = ElectionState.Election; - } + if (totalFactor > 100) + totalFactor = 100; + else if (totalFactor < 0) + totalFactor = 0; + + return new object[] { From, Address, Time, totalFactor }; + } + + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); + + writer.Write(From); + writer.Write(Address); + writer.Write(Time); + } + } + + public class Candidate + { + public Candidate(Mobile mob) + { + Mobile = mob; + Voters = new List(); + } - break; - } - case ElectionState.Election: - { - if ( (LastStateTime + VotingPeriod) > DateTime.UtcNow ) - break; + public Candidate(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - Faction.Broadcast( 1038024 ); // The results for the Faction Commander election are in + switch (version) + { + case 1: + { + Mobile = reader.ReadMobile(); - Candidate winner = null; + int count = reader.ReadEncodedInt(); + Voters = new List(count); - for ( int i = 0; i < Candidates.Count; ++i ) - { - Candidate cd = Candidates[i]; - - PlayerState pl = PlayerState.Find( cd.Mobile ); + for (int i = 0; i < count; ++i) + { + Voter voter = new Voter(reader, Mobile); - if ( pl == null || pl.Faction != Faction ) - continue; - - //cd.CleanMuleVotes(); - - if ( winner == null || cd.Votes > winner.Votes ) - winner = cd; - } + if (voter.From != null) + Voters.Add(voter); + } - if ( winner == null ) - { - Faction.Broadcast( 1038026 ); // Faction leadership has not changed. - } - else if ( winner.Mobile == Faction.Commander ) - { - Faction.Broadcast( 1038027 ); // The incumbent won the election. - } - else - { - Faction.Broadcast( 1038028 ); // The faction has a new commander. - Faction.Commander = winner.Mobile; - } - - Candidates.Clear(); - State = ElectionState.Pending; - - break; - } - } - } - } - - public class Voter - { - public Mobile From { get; } - - public Mobile Candidate { get; } - - public IPAddress Address { get; } - - public DateTime Time { get; } - - public object[] AcquireFields() - { - TimeSpan gameTime = TimeSpan.Zero; - - if ( From is PlayerMobile mobile ) - gameTime = mobile.GameTime; - - int kp = 0; - - PlayerState pl = PlayerState.Find( From ); - - if ( pl != null ) - kp = pl.KillPoints; - - int sk = From.Skills.Total; - - int factorSkills = 50 + ( (sk * 100 ) / 10000 ); - int factorKillPts = 100 + (kp*2); - int factorGameTime = 50 + (int) ( (gameTime.Ticks * 100) / TimeSpan.TicksPerDay ); - - int totalFactor = ( factorSkills * factorKillPts * Math.Max( factorGameTime, 100 ) ) / 10000; - - if ( totalFactor > 100 ) - totalFactor = 100; - else if ( totalFactor < 0 ) - totalFactor = 0; - - return new object[]{ From, Address, Time, totalFactor }; - } + break; + } + case 0: + { + Mobile = reader.ReadMobile(); - public Voter( Mobile from, Mobile candidate ) - { - From = from; - Candidate = candidate; + List mobs = reader.ReadStrongMobileList(); + Voters = new List(mobs.Count); - if ( From.NetState != null ) - Address = From.NetState.Address; - else - Address = IPAddress.None; + for (int i = 0; i < mobs.Count; ++i) + Voters.Add(new Voter(mobs[i], Mobile)); - Time = DateTime.UtcNow; - } + break; + } + } + } - public Voter( GenericReader reader, Mobile candidate ) - { - Candidate = candidate; + public Mobile Mobile{ get; } - int version = reader.ReadEncodedInt(); + public List Voters{ get; } - switch ( version ) - { - case 0: - { - From = reader.ReadMobile(); - Address = Utility.Intern( reader.ReadIPAddress() ); - Time = reader.ReadDateTime(); + public int Votes => Voters.Count; - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); - - writer.Write( (Mobile) From ); - writer.Write( (IPAddress) Address ); - writer.Write( (DateTime) Time ); - } - } - - public class Candidate - { - public Mobile Mobile { get; } + public void CleanMuleVotes() + { + for (int i = 0; i < Voters.Count; ++i) + { + Voter voter = Voters[i]; - public List Voters { get; } + if ((int)voter.AcquireFields()[3] < 90) + Voters.RemoveAt(i--); + } + } - public int Votes => Voters.Count; + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(1); // version - public void CleanMuleVotes() - { - for ( int i = 0; i < Voters.Count; ++i ) - { - Voter voter = (Voter)Voters[i]; + writer.Write(Mobile); - if ( (int)voter.AcquireFields()[3] < 90 ) - Voters.RemoveAt( i-- ); - } - } + writer.WriteEncodedInt(Voters.Count); - public Candidate( Mobile mob ) - { - Mobile = mob; - Voters = new List(); - } - - public Candidate( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 1: - { - Mobile = reader.ReadMobile(); - - int count = reader.ReadEncodedInt(); - Voters = new List( count ); - - for ( int i = 0; i < count; ++i ) - { - Voter voter = new Voter( reader, Mobile ); - - if ( voter.From != null ) - Voters.Add( voter ); - } - - break; - } - case 0: - { - Mobile = reader.ReadMobile(); - - List mobs = reader.ReadStrongMobileList(); - Voters = new List( mobs.Count ); - - for ( int i = 0; i < mobs.Count; ++i ) - Voters.Add( new Voter( mobs[i], Mobile ) ); - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 1 ); // version - - writer.Write( (Mobile) Mobile ); - - writer.WriteEncodedInt( (int) Voters.Count ); - - for ( int i = 0; i < Voters.Count; ++i ) - ((Voter)Voters[i]).Serialize( writer ); - } - } - - public enum ElectionState - { - Pending, - Campaign, - Election - } -} + for (int i = 0; i < Voters.Count; ++i) + Voters[i].Serialize(writer); + } + } + + public enum ElectionState + { + Pending, + Campaign, + Election + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Faction.cs b/Scripts/Engines/Factions/Core/Faction.cs index b0ddd856e..a26eb905e 100644 --- a/Scripts/Engines/Factions/Core/Faction.cs +++ b/Scripts/Engines/Factions/Core/Faction.cs @@ -1,1399 +1,1433 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Items; -using Server.Guilds; -using Server.Mobiles; -using Server.Prompts; -using Server.Targeting; using Server.Accounting; using Server.Commands; using Server.Commands.Generic; +using Server.Engines.ConPVP; +using Server.Ethics; +using Server.Guilds; +using Server.Items; +using Server.Mobiles; +using Server.Prompts; +using Server.Targeting; namespace Server.Factions { - [CustomEnum( new[]{ "Minax", "Council of Mages", "True Britannians", "Shadowlords" } )] - public abstract class Faction : IComparable - { - public int ZeroRankOffset; - - private FactionDefinition m_Definition; - - public StrongholdRegion StrongholdRegion { get; set; } - - public FactionDefinition Definition - { - get => m_Definition; - set - { - m_Definition = value; - StrongholdRegion = new StrongholdRegion( this ); - } - } - - public FactionState State { get; set; } - - public Election Election - { - get => State.Election; - set => State.Election = value; - } - - public Mobile Commander - { - get => State.Commander; - set => State.Commander = value; - } - - public int Tithe - { - get => State.Tithe; - set => State.Tithe = value; - } - - public int Silver - { - get => State.Silver; - set => State.Silver = value; - } - - public List Members - { - get => State.Members; - set => State.Members = value; - } - - public static readonly TimeSpan LeavePeriod = TimeSpan.FromDays( 3.0 ); - - public bool FactionMessageReady => State.FactionMessageReady; - - public void Broadcast( string text ) - { - Broadcast( 0x3B2, text ); - } - - public void Broadcast( int hue, string text ) - { - List members = Members; - - for ( int i = 0; i < members.Count; ++i ) - members[i].Mobile.SendMessage( hue, text ); - } - - public void Broadcast( int number ) - { - List members = Members; - - for ( int i = 0; i < members.Count; ++i ) - members[i].Mobile.SendLocalizedMessage( number ); - } - - public void Broadcast( string format, params object[] args ) - { - Broadcast( string.Format( format, args ) ); - } - - public void Broadcast( int hue, string format, params object[] args ) - { - Broadcast( hue, string.Format( format, args ) ); - } - - public void BeginBroadcast( Mobile from ) - { - from.SendLocalizedMessage( 1010265 ); // Enter Faction Message - from.Prompt = new BroadcastPrompt( this ); - } - - public void EndBroadcast( Mobile from, string text ) - { - if ( from.AccessLevel == AccessLevel.Player ) - State.RegisterBroadcast(); - - Broadcast( Definition.HueBroadcast, "{0} [Commander] {1} : {2}", from.Name, Definition.FriendlyName, text ); - } - - private class BroadcastPrompt : Prompt - { - private Faction m_Faction; - - public BroadcastPrompt( Faction faction ) - { - m_Faction = faction; - } - - public override void OnResponse( Mobile from, string text ) - { - m_Faction.EndBroadcast( from, text ); - } - } - - public static void HandleAtrophy() - { - foreach ( Faction f in Factions ) - { - if ( !f.State.IsAtrophyReady ) - return; - } - - List activePlayers = new List(); - - foreach ( Faction f in Factions ) - { - foreach ( PlayerState ps in f.Members ) - { - if ( ps.KillPoints > 0 && ps.IsActive ) - activePlayers.Add( ps ); - } - } - - int distrib = 0; - - foreach ( Faction f in Factions ) - distrib += f.State.CheckAtrophy(); - - if ( activePlayers.Count == 0 ) - return; - - for ( int i = 0; i < distrib; ++i ) - activePlayers[Utility.Random( activePlayers.Count )].KillPoints++; - } - - public static void DistributePoints( int distrib ) { - List activePlayers = new List(); - - foreach ( Faction f in Factions ) { - foreach ( PlayerState ps in f.Members ) { - if ( ps.KillPoints > 0 && ps.IsActive ) { - activePlayers.Add( ps ); - } - } - } - - if ( activePlayers.Count > 0 ) { - for ( int i = 0; i < distrib; ++i ) { - activePlayers[Utility.Random( activePlayers.Count )].KillPoints++; - } - } - } - - public void BeginHonorLeadership( Mobile from ) - { - from.SendLocalizedMessage( 502090 ); // Click on the player whom you wish to honor. - from.BeginTarget( 12, false, TargetFlags.None, HonorLeadership_OnTarget ); - } - - public void HonorLeadership_OnTarget( Mobile from, object obj ) - { - if ( obj is Mobile recv ) - { - PlayerState giveState = PlayerState.Find( from ); - PlayerState recvState = PlayerState.Find( recv ); - - if ( giveState == null ) - return; - - if ( recvState == null || recvState.Faction != giveState.Faction ) - { - from.SendLocalizedMessage( 1042497 ); // Only faction mates can be honored this way. - } - else if ( giveState.KillPoints < 5 ) - { - from.SendLocalizedMessage( 1042499 ); // You must have at least five kill points to honor them. - } - else - { - recvState.LastHonorTime = DateTime.UtcNow; - giveState.KillPoints -= 5; - recvState.KillPoints += 4; - - // TODO: Confirm no message sent to giver - recv.SendLocalizedMessage( 1042500 ); // You have been honored with four kill points. - } - } - else - { - from.SendLocalizedMessage( 1042496 ); // You may only honor another player. - } - } - - public virtual void AddMember( Mobile mob ) - { - Members.Insert( ZeroRankOffset, new PlayerState( mob, this, Members ) ); - - mob.AddToBackpack( FactionItem.Imbue( new Robe(), this, false, Definition.HuePrimary ) ); - mob.SendLocalizedMessage( 1010374 ); // You have been granted a robe which signifies your faction - - mob.InvalidateProperties(); - mob.Delta( MobileDelta.Noto ); - - mob.FixedEffect( 0x373A, 10, 30 ); - mob.PlaySound( 0x209 ); - } - - public static bool IsNearType( Mobile mob, Type type, int range ) - { - bool mobs = type.IsSubclassOf( typeof( Mobile ) ); - bool items = type.IsSubclassOf( typeof( Item ) ); - - if ( !(items || mobs) ) - return false; - - IPooledEnumerable eable = mob.Map.GetObjectsInRange(mob.Location, range, items, mobs); - - foreach ( IEntity obj in eable ) - { - if ( type.IsAssignableFrom( obj.GetType() ) ) - { - eable.Free(); - return true; - } - } - - eable.Free(); - return false; - } - - public static bool IsNearType( Mobile mob, Type[] types, int range ) - { - IPooledEnumerable eable = mob.GetObjectsInRange( range ); - - foreach( IEntity obj in eable ) - { - Type objType = obj.GetType(); - - for( int i = 0; i < types.Length; i++ ) - { - if ( types[i].IsAssignableFrom( objType ) ) - { - eable.Free(); - return true; - } - } - } - - eable.Free(); - return false; - } - - public void RemovePlayerState( PlayerState pl ) - { - if ( pl == null || !Members.Contains( pl ) ) - return; - - int killPoints = pl.KillPoints; - - if ( pl.RankIndex != -1 ) { - while ( ( pl.RankIndex + 1 ) < ZeroRankOffset ) { - PlayerState pNext = Members[pl.RankIndex+1] as PlayerState; - Members[pl.RankIndex+1] = pl; - Members[pl.RankIndex] = pNext; - pl.RankIndex++; - pNext.RankIndex--; - } - - ZeroRankOffset--; - } - - Members.Remove( pl ); - - PlayerMobile pm = (PlayerMobile)pl.Mobile; - if ( pm == null ) - return; - - Mobile mob = pl.Mobile; - if ( pm.FactionPlayerState == pl ) { - pm.FactionPlayerState = null; - - mob.InvalidateProperties(); - mob.Delta( MobileDelta.Noto ); - - if ( Election.IsCandidate( mob ) ) - Election.RemoveCandidate( mob ); - - if ( pl.Finance != null ) - pl.Finance.Finance = null; - - if ( pl.Sheriff != null ) - pl.Sheriff.Sheriff = null; - - Election.RemoveVoter( mob ); - - if ( Commander == mob ) - Commander = null; - - pm.ValidateEquipment(); - } - - if ( killPoints > 0 ) - DistributePoints( killPoints ); - } - - public void RemoveMember( Mobile mob ) - { - PlayerState pl = PlayerState.Find( mob ); - - if ( pl == null || !Members.Contains( pl ) ) - return; - - int killPoints = pl.KillPoints; - - if ( mob.Backpack != null ) - { - //Ordinarily, through normal faction removal, this will never find any sigils. - //Only with a leave delay less than the ReturnPeriod or a Faction Kick/Ban, will this ever do anything - Item[] sigils = mob.Backpack.FindItemsByType( typeof( Sigil ) ); - - for ( int i = 0; i < sigils.Length; ++i ) - ((Sigil)sigils[i]).ReturnHome(); - } - - if ( pl.RankIndex != -1 ) { - while ( ( pl.RankIndex + 1 ) < ZeroRankOffset ) { - PlayerState pNext = Members[pl.RankIndex+1]; - Members[pl.RankIndex+1] = pl; - Members[pl.RankIndex] = pNext; - pl.RankIndex++; - pNext.RankIndex--; - } - - ZeroRankOffset--; - } - - Members.Remove( pl ); - - if ( mob is PlayerMobile mobile ) - mobile.FactionPlayerState = null; - - mob.InvalidateProperties(); - mob.Delta( MobileDelta.Noto ); - - if ( Election.IsCandidate( mob ) ) - Election.RemoveCandidate( mob ); - - Election.RemoveVoter( mob ); - - if ( pl.Finance != null ) - pl.Finance.Finance = null; - - if ( pl.Sheriff != null ) - pl.Sheriff.Sheriff = null; - - if ( Commander == mob ) - Commander = null; - - if ( mob is PlayerMobile playerMobile ) - playerMobile.ValidateEquipment(); - - if ( killPoints > 0 ) - DistributePoints( killPoints ); - } - - public void JoinGuilded( PlayerMobile mob, Guild guild ) - { - if ( mob.Young ) - { - guild.RemoveMember( mob ); - mob.SendLocalizedMessage( 1042283 ); // You have been kicked out of your guild! Young players may not remain in a guild which is allied with a faction. - } - else if ( AlreadyHasCharInFaction( mob ) ) - { - guild.RemoveMember( mob ); - mob.SendLocalizedMessage( 1005281 ); // You have been kicked out of your guild due to factional overlap - } - else if ( IsFactionBanned( mob ) ) - { - guild.RemoveMember( mob ); - mob.SendLocalizedMessage( 1005052 ); // You are currently banned from the faction system - } - else - { - AddMember( mob ); - mob.SendLocalizedMessage( 1042756, true, " " + m_Definition.FriendlyName ); // You are now joining a faction: - } - } - - public void JoinAlone( Mobile mob ) - { - AddMember( mob ); - mob.SendLocalizedMessage( 1005058 ); // You have joined the faction - } - - private bool AlreadyHasCharInFaction( Mobile mob ) - { - if ( mob.Account is Account acct ) - { - for ( int i = 0; i < acct.Length; ++i ) - { - Mobile c = acct[i]; - - if ( Find( c ) != null ) - return true; - } - } - - return false; - } - - public static bool IsFactionBanned( Mobile mob ) - { - if ( !(mob.Account is Account acct) ) - return false; - - return ( acct.GetTag( "FactionBanned" ) != null ); - } - - public void OnJoinAccepted( Mobile mob ) - { - if ( !(mob is PlayerMobile pm) ) - return; // sanity - - PlayerState pl = PlayerState.Find( pm ); - - if ( pm.Young ) - pm.SendLocalizedMessage( 1010104 ); // You cannot join a faction as a young player - else if ( pl != null && pl.IsLeaving ) - pm.SendLocalizedMessage( 1005051 ); // You cannot use the faction stone until you have finished quitting your current faction - else if ( AlreadyHasCharInFaction( pm ) ) - pm.SendLocalizedMessage( 1005059 ); // You cannot join a faction because you already declared your allegiance with another character - else if ( IsFactionBanned( mob ) ) - pm.SendLocalizedMessage( 1005052 ); // You are currently banned from the faction system - else if ( pm.Guild != null ) - { - Guild guild = pm.Guild as Guild; - - if ( guild?.Leader != pm ) - pm.SendLocalizedMessage( 1005057 ); // You cannot join a faction because you are in a guild and not the guildmaster - else if ( guild.Type != GuildType.Regular ) - pm.SendLocalizedMessage( 1042161 ); // You cannot join a faction because your guild is an Order or Chaos type. - else if ( !Guild.NewGuildSystem && guild.Enemies != null && guild.Enemies.Count > 0 ) //CAN join w/wars in new system - pm.SendLocalizedMessage( 1005056 ); // You cannot join a faction with active Wars - else if ( Guild.NewGuildSystem && guild.Alliance != null ) - pm.SendLocalizedMessage( 1080454 ); // Your guild cannot join a faction while in alliance with non-factioned guilds. - else if ( !CanHandleInflux( guild.Members.Count ) ) - pm.SendLocalizedMessage( 1018031 ); // In the interest of faction stability, this faction declines to accept new members for now. - else - { - List members = new List( guild.Members ); - - for ( int i = 0; i < members.Count; ++i ) - { - if ( !(members[i] is PlayerMobile member) ) - continue; - - JoinGuilded( member, guild ); - } - } - } - else if ( !CanHandleInflux( 1 ) ) - { - pm.SendLocalizedMessage( 1018031 ); // In the interest of faction stability, this faction declines to accept new members for now. - } - else - { - JoinAlone( mob ); - } - } - - public bool IsCommander( Mobile mob ) - { - if ( mob == null ) - return false; - - return ( mob.AccessLevel >= AccessLevel.GameMaster || mob == Commander ); - } - - public Faction() - { - State = new FactionState( this ); - } - - public override string ToString() - { - return m_Definition.FriendlyName; - } - - public int CompareTo( object obj ) - { - return m_Definition.Sort - ((Faction)obj).m_Definition.Sort; - } - - public static bool CheckLeaveTimer( Mobile mob ) - { - PlayerState pl = PlayerState.Find( mob ); - - if ( pl == null || !pl.IsLeaving ) - return false; - - if ( (pl.Leaving + LeavePeriod) >= DateTime.UtcNow ) - return false; - - mob.SendLocalizedMessage( 1005163 ); // You have now quit your faction - - pl.Faction.RemoveMember( mob ); - - return true; - } - - public static void Initialize() - { - EventSink.Login += EventSink_Login; - EventSink.Logout += EventSink_Logout; - - Timer.DelayCall( TimeSpan.FromMinutes( 1.0 ), TimeSpan.FromMinutes( 10.0 ), HandleAtrophy ); - - Timer.DelayCall( TimeSpan.FromSeconds( 30.0 ), TimeSpan.FromSeconds( 30.0 ), ProcessTick ); - - CommandSystem.Register( "FactionElection", AccessLevel.GameMaster, FactionElection_OnCommand ); - CommandSystem.Register( "FactionCommander", AccessLevel.Administrator, FactionCommander_OnCommand ); - CommandSystem.Register( "FactionItemReset", AccessLevel.Administrator, FactionItemReset_OnCommand ); - CommandSystem.Register( "FactionReset", AccessLevel.Administrator, FactionReset_OnCommand ); - CommandSystem.Register( "FactionTownReset", AccessLevel.Administrator, FactionTownReset_OnCommand ); - } - - public static void FactionTownReset_OnCommand( CommandEventArgs e ) - { - List monoliths = BaseMonolith.Monoliths; - - for ( int i = 0; i < monoliths.Count; ++i ) - monoliths[i].Sigil = null; - - List towns = Town.Towns; - - for ( int i = 0; i < towns.Count; ++i ) - { - towns[i].Silver = 0; - towns[i].Sheriff = null; - towns[i].Finance = null; - towns[i].Tax = 0; - towns[i].Owner = null; - } - - List sigils = Sigil.Sigils; - - for ( int i = 0; i < sigils.Count; ++i ) - { - sigils[i].Corrupted = null; - sigils[i].Corrupting = null; - sigils[i].LastStolen = DateTime.MinValue; - sigils[i].GraceStart = DateTime.MinValue; - sigils[i].CorruptionStart = DateTime.MinValue; - sigils[i].PurificationStart = DateTime.MinValue; - sigils[i].LastMonolith = null; - sigils[i].ReturnHome(); - } - - List factions = Factions; - - for ( int i = 0; i < factions.Count; ++i ) - { - Faction f = factions[i]; - - List list = new List( f.State.FactionItems ); - - for ( int j = 0; j < list.Count; ++j ) - { - FactionItem fi = list[j]; + [CustomEnum(new[] { "Minax", "Council of Mages", "True Britannians", "Shadowlords" })] + public abstract class Faction : IComparable + { + public const int StabilityFactor = 300; // 300% greater (3 times) than smallest faction + public const int StabilityActivation = 200; // Stablity code goes into effect when largest faction has > 200 people + + public static readonly TimeSpan LeavePeriod = TimeSpan.FromDays(3.0); + + public static readonly Map Facet = Map.Felucca; + + private FactionDefinition m_Definition; + public int ZeroRankOffset; + + public Faction() + { + State = new FactionState(this); + } + + public StrongholdRegion StrongholdRegion{ get; set; } + + public FactionDefinition Definition + { + get => m_Definition; + set + { + m_Definition = value; + StrongholdRegion = new StrongholdRegion(this); + } + } + + public FactionState State{ get; set; } + + public Election Election + { + get => State.Election; + set => State.Election = value; + } + + public Mobile Commander + { + get => State.Commander; + set => State.Commander = value; + } + + public int Tithe + { + get => State.Tithe; + set => State.Tithe = value; + } + + public int Silver + { + get => State.Silver; + set => State.Silver = value; + } + + public List Members + { + get => State.Members; + set => State.Members = value; + } + + public bool FactionMessageReady => State.FactionMessageReady; + + public virtual int MaximumTraps => 15; + + public List Traps + { + get => State.Traps; + set => State.Traps = value; + } + + public static List Factions => Reflector.Factions; + + public int CompareTo(object obj) + { + return m_Definition.Sort - ((Faction)obj).m_Definition.Sort; + } + + public void Broadcast(string text) + { + Broadcast(0x3B2, text); + } + + public void Broadcast(int hue, string text) + { + List members = Members; + + for (int i = 0; i < members.Count; ++i) + members[i].Mobile.SendMessage(hue, text); + } + + public void Broadcast(int number) + { + List members = Members; + + for (int i = 0; i < members.Count; ++i) + members[i].Mobile.SendLocalizedMessage(number); + } + + public void Broadcast(string format, params object[] args) + { + Broadcast(string.Format(format, args)); + } + + public void Broadcast(int hue, string format, params object[] args) + { + Broadcast(hue, string.Format(format, args)); + } + + public void BeginBroadcast(Mobile from) + { + from.SendLocalizedMessage(1010265); // Enter Faction Message + from.Prompt = new BroadcastPrompt(this); + } + + public void EndBroadcast(Mobile from, string text) + { + if (from.AccessLevel == AccessLevel.Player) + State.RegisterBroadcast(); + + Broadcast(Definition.HueBroadcast, "{0} [Commander] {1} : {2}", from.Name, Definition.FriendlyName, text); + } + + public static void HandleAtrophy() + { + foreach (Faction f in Factions) + if (!f.State.IsAtrophyReady) + return; + + List activePlayers = new List(); + + foreach (Faction f in Factions) + foreach (PlayerState ps in f.Members) + if (ps.KillPoints > 0 && ps.IsActive) + activePlayers.Add(ps); + + int distrib = 0; + + foreach (Faction f in Factions) + distrib += f.State.CheckAtrophy(); + + if (activePlayers.Count == 0) + return; + + for (int i = 0; i < distrib; ++i) + activePlayers[Utility.Random(activePlayers.Count)].KillPoints++; + } + + public static void DistributePoints(int distrib) + { + List activePlayers = new List(); + + foreach (Faction f in Factions) + foreach (PlayerState ps in f.Members) + if (ps.KillPoints > 0 && ps.IsActive) + activePlayers.Add(ps); + + if (activePlayers.Count > 0) + for (int i = 0; i < distrib; ++i) + activePlayers[Utility.Random(activePlayers.Count)].KillPoints++; + } + + public void BeginHonorLeadership(Mobile from) + { + from.SendLocalizedMessage(502090); // Click on the player whom you wish to honor. + from.BeginTarget(12, false, TargetFlags.None, HonorLeadership_OnTarget); + } + + public void HonorLeadership_OnTarget(Mobile from, object obj) + { + if (obj is Mobile recv) + { + PlayerState giveState = PlayerState.Find(from); + PlayerState recvState = PlayerState.Find(recv); + + if (giveState == null) + return; + + if (recvState == null || recvState.Faction != giveState.Faction) + { + from.SendLocalizedMessage(1042497); // Only faction mates can be honored this way. + } + else if (giveState.KillPoints < 5) + { + from.SendLocalizedMessage(1042499); // You must have at least five kill points to honor them. + } + else + { + recvState.LastHonorTime = DateTime.UtcNow; + giveState.KillPoints -= 5; + recvState.KillPoints += 4; + + // TODO: Confirm no message sent to giver + recv.SendLocalizedMessage(1042500); // You have been honored with four kill points. + } + } + else + { + from.SendLocalizedMessage(1042496); // You may only honor another player. + } + } + + public virtual void AddMember(Mobile mob) + { + Members.Insert(ZeroRankOffset, new PlayerState(mob, this, Members)); + + mob.AddToBackpack(FactionItem.Imbue(new Robe(), this, false, Definition.HuePrimary)); + mob.SendLocalizedMessage(1010374); // You have been granted a robe which signifies your faction + + mob.InvalidateProperties(); + mob.Delta(MobileDelta.Noto); + + mob.FixedEffect(0x373A, 10, 30); + mob.PlaySound(0x209); + } + + public static bool IsNearType(Mobile mob, Type type, int range) + { + bool mobs = type.IsSubclassOf(typeof(Mobile)); + bool items = type.IsSubclassOf(typeof(Item)); + + if (!(items || mobs)) + return false; + + IPooledEnumerable eable = mob.Map.GetObjectsInRange(mob.Location, range, items, mobs); + + foreach (IEntity obj in eable) + if (type.IsAssignableFrom(obj.GetType())) + { + eable.Free(); + return true; + } + + eable.Free(); + return false; + } + + public static bool IsNearType(Mobile mob, Type[] types, int range) + { + IPooledEnumerable eable = mob.GetObjectsInRange(range); + + foreach (IEntity obj in eable) + { + Type objType = obj.GetType(); + + for (int i = 0; i < types.Length; i++) + if (types[i].IsAssignableFrom(objType)) + { + eable.Free(); + return true; + } + } + + eable.Free(); + return false; + } + + public void RemovePlayerState(PlayerState pl) + { + if (pl == null || !Members.Contains(pl)) + return; + + int killPoints = pl.KillPoints; + + if (pl.RankIndex != -1) + { + while (pl.RankIndex + 1 < ZeroRankOffset) + { + PlayerState pNext = Members[pl.RankIndex + 1]; + Members[pl.RankIndex + 1] = pl; + Members[pl.RankIndex] = pNext; + pl.RankIndex++; + pNext.RankIndex--; + } + + ZeroRankOffset--; + } + + Members.Remove(pl); + + PlayerMobile pm = (PlayerMobile)pl.Mobile; + if (pm == null) + return; + + Mobile mob = pl.Mobile; + if (pm.FactionPlayerState == pl) + { + pm.FactionPlayerState = null; + + mob.InvalidateProperties(); + mob.Delta(MobileDelta.Noto); + + if (Election.IsCandidate(mob)) + Election.RemoveCandidate(mob); + + if (pl.Finance != null) + pl.Finance.Finance = null; + + if (pl.Sheriff != null) + pl.Sheriff.Sheriff = null; + + Election.RemoveVoter(mob); + + if (Commander == mob) + Commander = null; + + pm.ValidateEquipment(); + } + + if (killPoints > 0) + DistributePoints(killPoints); + } + + public void RemoveMember(Mobile mob) + { + PlayerState pl = PlayerState.Find(mob); + + if (pl == null || !Members.Contains(pl)) + return; + + int killPoints = pl.KillPoints; + + if (mob.Backpack != null) + { + //Ordinarily, through normal faction removal, this will never find any sigils. + //Only with a leave delay less than the ReturnPeriod or a Faction Kick/Ban, will this ever do anything + Item[] sigils = mob.Backpack.FindItemsByType(typeof(Sigil)); + + for (int i = 0; i < sigils.Length; ++i) + ((Sigil)sigils[i]).ReturnHome(); + } + + if (pl.RankIndex != -1) + { + while (pl.RankIndex + 1 < ZeroRankOffset) + { + PlayerState pNext = Members[pl.RankIndex + 1]; + Members[pl.RankIndex + 1] = pl; + Members[pl.RankIndex] = pNext; + pl.RankIndex++; + pNext.RankIndex--; + } + + ZeroRankOffset--; + } + + Members.Remove(pl); + + if (mob is PlayerMobile mobile) + mobile.FactionPlayerState = null; + + mob.InvalidateProperties(); + mob.Delta(MobileDelta.Noto); + + if (Election.IsCandidate(mob)) + Election.RemoveCandidate(mob); + + Election.RemoveVoter(mob); + + if (pl.Finance != null) + pl.Finance.Finance = null; + + if (pl.Sheriff != null) + pl.Sheriff.Sheriff = null; + + if (Commander == mob) + Commander = null; + + if (mob is PlayerMobile playerMobile) + playerMobile.ValidateEquipment(); + + if (killPoints > 0) + DistributePoints(killPoints); + } + + public void JoinGuilded(PlayerMobile mob, Guild guild) + { + if (mob.Young) + { + guild.RemoveMember(mob); + mob.SendLocalizedMessage( + 1042283); // You have been kicked out of your guild! Young players may not remain in a guild which is allied with a faction. + } + else if (AlreadyHasCharInFaction(mob)) + { + guild.RemoveMember(mob); + mob.SendLocalizedMessage(1005281); // You have been kicked out of your guild due to factional overlap + } + else if (IsFactionBanned(mob)) + { + guild.RemoveMember(mob); + mob.SendLocalizedMessage(1005052); // You are currently banned from the faction system + } + else + { + AddMember(mob); + mob.SendLocalizedMessage(1042756, true, " " + m_Definition.FriendlyName); // You are now joining a faction: + } + } + + public void JoinAlone(Mobile mob) + { + AddMember(mob); + mob.SendLocalizedMessage(1005058); // You have joined the faction + } + + private bool AlreadyHasCharInFaction(Mobile mob) + { + if (mob.Account is Account acct) + for (int i = 0; i < acct.Length; ++i) + { + Mobile c = acct[i]; + + if (Find(c) != null) + return true; + } + + return false; + } + + public static bool IsFactionBanned(Mobile mob) + { + if (!(mob.Account is Account acct)) + return false; + + return acct.GetTag("FactionBanned") != null; + } + + public void OnJoinAccepted(Mobile mob) + { + if (!(mob is PlayerMobile pm)) + return; // sanity + + PlayerState pl = PlayerState.Find(pm); + + if (pm.Young) + { + pm.SendLocalizedMessage(1010104); // You cannot join a faction as a young player + } + else if (pl != null && pl.IsLeaving) + { + pm.SendLocalizedMessage( + 1005051); // You cannot use the faction stone until you have finished quitting your current faction + } + else if (AlreadyHasCharInFaction(pm)) + { + pm.SendLocalizedMessage( + 1005059); // You cannot join a faction because you already declared your allegiance with another character + } + else if (IsFactionBanned(mob)) + { + pm.SendLocalizedMessage(1005052); // You are currently banned from the faction system + } + else if (pm.Guild != null) + { + Guild guild = pm.Guild as Guild; + + if (guild?.Leader != pm) + { + pm.SendLocalizedMessage( + 1005057); // You cannot join a faction because you are in a guild and not the guildmaster + } + else if (guild.Type != GuildType.Regular) + { + pm.SendLocalizedMessage( + 1042161); // You cannot join a faction because your guild is an Order or Chaos type. + } + else if (!Guild.NewGuildSystem && guild.Enemies != null && guild.Enemies.Count > 0 + ) //CAN join w/wars in new system + { + pm.SendLocalizedMessage(1005056); // You cannot join a faction with active Wars + } + else if (Guild.NewGuildSystem && guild.Alliance != null) + { + pm.SendLocalizedMessage( + 1080454); // Your guild cannot join a faction while in alliance with non-factioned guilds. + } + else if (!CanHandleInflux(guild.Members.Count)) + { + pm.SendLocalizedMessage( + 1018031); // In the interest of faction stability, this faction declines to accept new members for now. + } + else + { + List members = new List(guild.Members); + + for (int i = 0; i < members.Count; ++i) + { + if (!(members[i] is PlayerMobile member)) + continue; + + JoinGuilded(member, guild); + } + } + } + else if (!CanHandleInflux(1)) + { + pm.SendLocalizedMessage( + 1018031); // In the interest of faction stability, this faction declines to accept new members for now. + } + else + { + JoinAlone(mob); + } + } + + public bool IsCommander(Mobile mob) + { + if (mob == null) + return false; + + return mob.AccessLevel >= AccessLevel.GameMaster || mob == Commander; + } + + public override string ToString() + { + return m_Definition.FriendlyName; + } + + public static bool CheckLeaveTimer(Mobile mob) + { + PlayerState pl = PlayerState.Find(mob); + + if (pl == null || !pl.IsLeaving) + return false; + + if (pl.Leaving + LeavePeriod >= DateTime.UtcNow) + return false; + + mob.SendLocalizedMessage(1005163); // You have now quit your faction + + pl.Faction.RemoveMember(mob); + + return true; + } + + public static void Initialize() + { + EventSink.Login += EventSink_Login; + EventSink.Logout += EventSink_Logout; + + Timer.DelayCall(TimeSpan.FromMinutes(1.0), TimeSpan.FromMinutes(10.0), HandleAtrophy); + + Timer.DelayCall(TimeSpan.FromSeconds(30.0), TimeSpan.FromSeconds(30.0), ProcessTick); + + CommandSystem.Register("FactionElection", AccessLevel.GameMaster, FactionElection_OnCommand); + CommandSystem.Register("FactionCommander", AccessLevel.Administrator, FactionCommander_OnCommand); + CommandSystem.Register("FactionItemReset", AccessLevel.Administrator, FactionItemReset_OnCommand); + CommandSystem.Register("FactionReset", AccessLevel.Administrator, FactionReset_OnCommand); + CommandSystem.Register("FactionTownReset", AccessLevel.Administrator, FactionTownReset_OnCommand); + } + + public static void FactionTownReset_OnCommand(CommandEventArgs e) + { + List monoliths = BaseMonolith.Monoliths; + + for (int i = 0; i < monoliths.Count; ++i) + monoliths[i].Sigil = null; + + List towns = Town.Towns; + + for (int i = 0; i < towns.Count; ++i) + { + towns[i].Silver = 0; + towns[i].Sheriff = null; + towns[i].Finance = null; + towns[i].Tax = 0; + towns[i].Owner = null; + } + + List sigils = Sigil.Sigils; + + for (int i = 0; i < sigils.Count; ++i) + { + sigils[i].Corrupted = null; + sigils[i].Corrupting = null; + sigils[i].LastStolen = DateTime.MinValue; + sigils[i].GraceStart = DateTime.MinValue; + sigils[i].CorruptionStart = DateTime.MinValue; + sigils[i].PurificationStart = DateTime.MinValue; + sigils[i].LastMonolith = null; + sigils[i].ReturnHome(); + } + + List factions = Factions; + + for (int i = 0; i < factions.Count; ++i) + { + Faction f = factions[i]; + + List list = new List(f.State.FactionItems); + + for (int j = 0; j < list.Count; ++j) + { + FactionItem fi = list[j]; + + if (fi.Expiration == DateTime.MinValue) + fi.Item.Delete(); + else + fi.Detach(); + } + } + } + + public static void FactionReset_OnCommand(CommandEventArgs e) + { + List monoliths = BaseMonolith.Monoliths; + + for (int i = 0; i < monoliths.Count; ++i) + monoliths[i].Sigil = null; - if ( fi.Expiration == DateTime.MinValue ) - fi.Item.Delete(); - else - fi.Detach(); - } - } - } - - public static void FactionReset_OnCommand( CommandEventArgs e ) - { - List monoliths = BaseMonolith.Monoliths; - - for ( int i = 0; i < monoliths.Count; ++i ) - monoliths[i].Sigil = null; - - List towns = Town.Towns; - - for ( int i = 0; i < towns.Count; ++i ) - { - towns[i].Silver = 0; - towns[i].Sheriff = null; - towns[i].Finance = null; - towns[i].Tax = 0; - towns[i].Owner = null; - } - - List sigils = Sigil.Sigils; - - for ( int i = 0; i < sigils.Count; ++i ) - { - sigils[i].Corrupted = null; - sigils[i].Corrupting = null; - sigils[i].LastStolen = DateTime.MinValue; - sigils[i].GraceStart = DateTime.MinValue; - sigils[i].CorruptionStart = DateTime.MinValue; - sigils[i].PurificationStart = DateTime.MinValue; - sigils[i].LastMonolith = null; - sigils[i].ReturnHome(); - } - - List factions = Factions; - - for ( int i = 0; i < factions.Count; ++i ) - { - Faction f = factions[i]; - - List playerStateList = new List( f.Members ); - - for( int j = 0; j < playerStateList.Count; ++j ) - f.RemoveMember( playerStateList[j].Mobile ); - - List factionItemList = new List( f.State.FactionItems ); - - for( int j = 0; j < factionItemList.Count; ++j ) - { - FactionItem fi = (FactionItem)factionItemList[j]; - - if ( fi.Expiration == DateTime.MinValue ) - fi.Item.Delete(); - else - fi.Detach(); - } - - List factionTrapList = new List( f.Traps ); - - for( int j = 0; j < factionTrapList.Count; ++j ) - factionTrapList[j].Delete(); - } - } - - public static void FactionItemReset_OnCommand( CommandEventArgs e ) - { - ArrayList pots = new ArrayList(); - - foreach ( Item item in World.Items.Values ) - { - if ( item is IFactionItem && !(item is HoodedShroudOfShadows) ) - pots.Add( item ); - } - - int[] hues = new int[Factions.Count * 2]; - - for ( int i = 0; i < Factions.Count; ++i ) - { - hues[0+(i*2)] = Factions[i].Definition.HuePrimary; - hues[1+(i*2)] = Factions[i].Definition.HueSecondary; - } - - int count = 0; - - for ( int i = 0; i < pots.Count; ++i ) - { - Item item = (Item)pots[i]; - IFactionItem fci = (IFactionItem)item; - - if ( fci.FactionItemState != null || item.LootType != LootType.Blessed ) - continue; - - bool isHued = false; - - for ( int j = 0; j < hues.Length; ++j ) - { - if ( item.Hue == hues[j] ) - { - isHued = true; - break; - } - } - - if ( isHued ) - { - fci.FactionItemState = null; - ++count; - } - } - - e.Mobile.SendMessage( "{0} items reset", count ); - } - - public static void FactionCommander_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( "Target a player to make them the faction commander." ); - e.Mobile.BeginTarget( -1, false, TargetFlags.None, FactionCommander_OnTarget ); - } - - public static void FactionCommander_OnTarget( Mobile from, object obj ) - { - if ( obj is PlayerMobile mobile ) - { - Mobile targ = mobile; - PlayerState pl = PlayerState.Find( targ ); - - if ( pl != null ) - { - pl.Faction.Commander = targ; - from.SendMessage( "You have appointed them as the faction commander." ); - } - else - { - from.SendMessage( "They are not in a faction." ); - } - } - else - { - from.SendMessage( "That is not a player." ); - } - } - - public static void FactionElection_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( "Target a faction stone to open its election properties." ); - e.Mobile.BeginTarget( -1, false, TargetFlags.None, FactionElection_OnTarget ); - } - - public static void FactionElection_OnTarget( Mobile from, object obj ) - { - if ( obj is FactionStone stone ) - { - Faction faction = stone.Faction; - - if ( faction != null ) - from.SendGump( new ElectionManagementGump( faction.Election ) ); - //from.SendGump( new Gumps.PropertiesGump( from, faction.Election ) ); - else - from.SendMessage( "That stone has no faction assigned." ); - } - else - { - from.SendMessage( "That is not a faction stone." ); - } - } - - public static void FactionKick_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendMessage( "Target a player to remove them from their faction." ); - e.Mobile.BeginTarget( -1, false, TargetFlags.None, FactionKick_OnTarget ); - } - - public static void FactionKick_OnTarget( Mobile from, object obj ) - { - if ( obj is Mobile mob ) - { - PlayerState pl = PlayerState.Find( mob ); - - if ( pl != null ) - { - pl.Faction.RemoveMember( mob ); - - mob.SendMessage( "You have been kicked from your faction." ); - from.SendMessage( "They have been kicked from their faction." ); - } - else - { - from.SendMessage( "They are not in a faction." ); - } - } - else - { - from.SendMessage( "That is not a player." ); - } - } - - public static void ProcessTick() - { - List sigils = Sigil.Sigils; - - for ( int i = 0; i < sigils.Count; ++i ) - { - Sigil sigil = sigils[i]; - - if ( !sigil.IsBeingCorrupted && sigil.GraceStart != DateTime.MinValue && (sigil.GraceStart + Sigil.CorruptionGrace) < DateTime.UtcNow ) - { - if ( sigil.LastMonolith is StrongholdMonolith && ( sigil.Corrupted == null || sigil.LastMonolith.Faction != sigil.Corrupted )) - { - sigil.Corrupting = sigil.LastMonolith.Faction; - sigil.CorruptionStart = DateTime.UtcNow; - } - else - { - sigil.Corrupting = null; - sigil.CorruptionStart = DateTime.MinValue; - } - - sigil.GraceStart = DateTime.MinValue; - } - - if ( sigil.LastMonolith?.Sigil == null ) - { - if ( (sigil.LastStolen + Sigil.ReturnPeriod) < DateTime.UtcNow ) - sigil.ReturnHome(); - } - else - { - if ( sigil.IsBeingCorrupted && (sigil.CorruptionStart + Sigil.CorruptionPeriod) < DateTime.UtcNow ) - { - sigil.Corrupted = sigil.Corrupting; - sigil.Corrupting = null; - sigil.CorruptionStart = DateTime.MinValue; - sigil.GraceStart = DateTime.MinValue; - } - else if ( sigil.IsPurifying && (sigil.PurificationStart + Sigil.PurificationPeriod) < DateTime.UtcNow ) - { - sigil.PurificationStart = DateTime.MinValue; - sigil.Corrupted = null; - sigil.Corrupting = null; - sigil.CorruptionStart = DateTime.MinValue; - sigil.GraceStart = DateTime.MinValue; - } - } - } - } - - public static void HandleDeath( Mobile mob ) - { - HandleDeath( mob, null ); - } - - #region Skill Loss - public const double SkillLossFactor = 1.0 / 3; - public static readonly TimeSpan SkillLossPeriod = TimeSpan.FromMinutes( 20.0 ); - - private static Dictionary m_SkillLoss = new Dictionary(); - - private class SkillLossContext - { - public Timer m_Timer; - public List m_Mods; - } - - public static bool InSkillLoss( Mobile mob ) - { - return m_SkillLoss.ContainsKey( mob ); - } - - public static void ApplySkillLoss( Mobile mob ) - { - if ( InSkillLoss( mob ) ) - return; - - SkillLossContext context = new SkillLossContext(); - m_SkillLoss[mob] = context; - - List mods = context.m_Mods = new List(); - - for ( int i = 0; i < mob.Skills.Length; ++i ) - { - Skill sk = mob.Skills[i]; - double baseValue = sk.Base; - - if ( baseValue > 0 ) - { - SkillMod mod = new DefaultSkillMod( sk.SkillName, true, -(baseValue * SkillLossFactor) ); - - mods.Add( mod ); - mob.AddSkillMod( mod ); - } - } - - context.m_Timer = Timer.DelayCall( SkillLossPeriod, new TimerStateCallback( ClearSkillLoss_Callback ), mob ); - } - - private static void ClearSkillLoss_Callback( object state ) - { - ClearSkillLoss( (Mobile) state ); - } - - public static bool ClearSkillLoss( Mobile mob ) - { - if (!m_SkillLoss.TryGetValue( mob, out SkillLossContext context )) - return false; - - m_SkillLoss.Remove( mob ); - - List mods = context.m_Mods; - - for ( int i = 0; i < mods.Count; ++i ) - mob.RemoveSkillMod( mods[i] ); - - context.m_Timer.Stop(); - - return true; - } - #endregion - - public int AwardSilver( Mobile mob, int silver ) - { - if ( silver <= 0 ) - return 0; - - int tithed = ( silver * Tithe ) / 100; - - Silver += tithed; - - silver = silver - tithed; - - if ( silver > 0 ) - mob.AddToBackpack( new Silver( silver ) ); - - return silver; - } - - public virtual int MaximumTraps => 15; - - public List Traps - { - get => State.Traps; - set => State.Traps = value; - } + List towns = Town.Towns; + + for (int i = 0; i < towns.Count; ++i) + { + towns[i].Silver = 0; + towns[i].Sheriff = null; + towns[i].Finance = null; + towns[i].Tax = 0; + towns[i].Owner = null; + } + + List sigils = Sigil.Sigils; + + for (int i = 0; i < sigils.Count; ++i) + { + sigils[i].Corrupted = null; + sigils[i].Corrupting = null; + sigils[i].LastStolen = DateTime.MinValue; + sigils[i].GraceStart = DateTime.MinValue; + sigils[i].CorruptionStart = DateTime.MinValue; + sigils[i].PurificationStart = DateTime.MinValue; + sigils[i].LastMonolith = null; + sigils[i].ReturnHome(); + } + + List factions = Factions; + + for (int i = 0; i < factions.Count; ++i) + { + Faction f = factions[i]; + + List playerStateList = new List(f.Members); + + for (int j = 0; j < playerStateList.Count; ++j) + f.RemoveMember(playerStateList[j].Mobile); + + List factionItemList = new List(f.State.FactionItems); + + for (int j = 0; j < factionItemList.Count; ++j) + { + FactionItem fi = factionItemList[j]; + + if (fi.Expiration == DateTime.MinValue) + fi.Item.Delete(); + else + fi.Detach(); + } + + List factionTrapList = new List(f.Traps); + + for (int j = 0; j < factionTrapList.Count; ++j) + factionTrapList[j].Delete(); + } + } + + public static void FactionItemReset_OnCommand(CommandEventArgs e) + { + ArrayList pots = new ArrayList(); + + foreach (Item item in World.Items.Values) + if (item is IFactionItem && !(item is HoodedShroudOfShadows)) + pots.Add(item); + + int[] hues = new int[Factions.Count * 2]; + + for (int i = 0; i < Factions.Count; ++i) + { + hues[0 + i * 2] = Factions[i].Definition.HuePrimary; + hues[1 + i * 2] = Factions[i].Definition.HueSecondary; + } + + int count = 0; + + for (int i = 0; i < pots.Count; ++i) + { + Item item = (Item)pots[i]; + IFactionItem fci = (IFactionItem)item; + + if (fci.FactionItemState != null || item.LootType != LootType.Blessed) + continue; + + bool isHued = false; + + for (int j = 0; j < hues.Length; ++j) + if (item.Hue == hues[j]) + { + isHued = true; + break; + } + + if (isHued) + { + fci.FactionItemState = null; + ++count; + } + } + + e.Mobile.SendMessage("{0} items reset", count); + } + + public static void FactionCommander_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage("Target a player to make them the faction commander."); + e.Mobile.BeginTarget(-1, false, TargetFlags.None, FactionCommander_OnTarget); + } + + public static void FactionCommander_OnTarget(Mobile from, object obj) + { + if (obj is PlayerMobile mobile) + { + Mobile targ = mobile; + PlayerState pl = PlayerState.Find(targ); + + if (pl != null) + { + pl.Faction.Commander = targ; + from.SendMessage("You have appointed them as the faction commander."); + } + else + { + from.SendMessage("They are not in a faction."); + } + } + else + { + from.SendMessage("That is not a player."); + } + } + + public static void FactionElection_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage("Target a faction stone to open its election properties."); + e.Mobile.BeginTarget(-1, false, TargetFlags.None, FactionElection_OnTarget); + } + + public static void FactionElection_OnTarget(Mobile from, object obj) + { + if (obj is FactionStone stone) + { + Faction faction = stone.Faction; + + if (faction != null) + from.SendGump(new ElectionManagementGump(faction.Election)); + //from.SendGump( new Gumps.PropertiesGump( from, faction.Election ) ); + else + from.SendMessage("That stone has no faction assigned."); + } + else + { + from.SendMessage("That is not a faction stone."); + } + } + + public static void FactionKick_OnCommand(CommandEventArgs e) + { + e.Mobile.SendMessage("Target a player to remove them from their faction."); + e.Mobile.BeginTarget(-1, false, TargetFlags.None, FactionKick_OnTarget); + } + + public static void FactionKick_OnTarget(Mobile from, object obj) + { + if (obj is Mobile mob) + { + PlayerState pl = PlayerState.Find(mob); + + if (pl != null) + { + pl.Faction.RemoveMember(mob); + + mob.SendMessage("You have been kicked from your faction."); + from.SendMessage("They have been kicked from their faction."); + } + else + { + from.SendMessage("They are not in a faction."); + } + } + else + { + from.SendMessage("That is not a player."); + } + } + + public static void ProcessTick() + { + List sigils = Sigil.Sigils; + + for (int i = 0; i < sigils.Count; ++i) + { + Sigil sigil = sigils[i]; + + if (!sigil.IsBeingCorrupted && sigil.GraceStart != DateTime.MinValue && + sigil.GraceStart + Sigil.CorruptionGrace < DateTime.UtcNow) + { + if (sigil.LastMonolith is StrongholdMonolith && + (sigil.Corrupted == null || sigil.LastMonolith.Faction != sigil.Corrupted)) + { + sigil.Corrupting = sigil.LastMonolith.Faction; + sigil.CorruptionStart = DateTime.UtcNow; + } + else + { + sigil.Corrupting = null; + sigil.CorruptionStart = DateTime.MinValue; + } + + sigil.GraceStart = DateTime.MinValue; + } + + if (sigil.LastMonolith?.Sigil == null) + { + if (sigil.LastStolen + Sigil.ReturnPeriod < DateTime.UtcNow) + sigil.ReturnHome(); + } + else + { + if (sigil.IsBeingCorrupted && sigil.CorruptionStart + Sigil.CorruptionPeriod < DateTime.UtcNow) + { + sigil.Corrupted = sigil.Corrupting; + sigil.Corrupting = null; + sigil.CorruptionStart = DateTime.MinValue; + sigil.GraceStart = DateTime.MinValue; + } + else if (sigil.IsPurifying && sigil.PurificationStart + Sigil.PurificationPeriod < DateTime.UtcNow) + { + sigil.PurificationStart = DateTime.MinValue; + sigil.Corrupted = null; + sigil.Corrupting = null; + sigil.CorruptionStart = DateTime.MinValue; + sigil.GraceStart = DateTime.MinValue; + } + } + } + } + + public static void HandleDeath(Mobile mob) + { + HandleDeath(mob, null); + } + + public int AwardSilver(Mobile mob, int silver) + { + if (silver <= 0) + return 0; + + int tithed = silver * Tithe / 100; + + Silver += tithed; + + silver = silver - tithed; + + if (silver > 0) + mob.AddToBackpack(new Silver(silver)); + + return silver; + } + + public static Faction FindSmallestFaction() + { + List factions = Factions; + Faction smallest = null; + + for (int i = 0; i < factions.Count; ++i) + { + Faction faction = factions[i]; + + if (smallest == null || faction.Members.Count < smallest.Members.Count) + smallest = faction; + } + + return smallest; + } + + public static bool StabilityActive() + { + List factions = Factions; + + for (int i = 0; i < factions.Count; ++i) + { + Faction faction = factions[i]; + + if (faction.Members.Count > StabilityActivation) + return true; + } + + return false; + } + + public bool CanHandleInflux(int influx) + { + if (!StabilityActive()) + return true; + + Faction smallest = FindSmallestFaction(); + + if (smallest == null) + return true; // sanity + + if (StabilityFactor > 0 && (Members.Count + influx) * 100 / StabilityFactor > smallest.Members.Count) + return false; + + return true; + } + + public static void HandleDeath(Mobile victim, Mobile killer) + { + if (killer == null) + killer = victim.FindMostRecentDamager(true); + + PlayerState killerState = PlayerState.Find(killer); + + Container pack = victim.Backpack; + + if (pack != null) + { + Container killerPack = killer?.Backpack; + Item[] sigils = pack.FindItemsByType(typeof(Sigil)); + + for (int i = 0; i < sigils.Length; ++i) + { + Sigil sigil = (Sigil)sigils[i]; + + if (killerState != null && killerPack != null) + { + if (killer.GetDistanceToSqrt(victim) > 64) + { + sigil.ReturnHome(); + killer.SendLocalizedMessage(1042230); // The sigil has gone back to its home location. + } + else if (Sigil.ExistsOn(killer)) + { + sigil.ReturnHome(); + killer.SendLocalizedMessage( + 1010258); // The sigil has gone back to its home location because you already have a sigil. + } + else if (!killerPack.TryDropItem(killer, sigil, false)) + { + sigil.ReturnHome(); + killer.SendLocalizedMessage(1010259); // The sigil has gone home because your backpack is full. + } + } + else + { + sigil.ReturnHome(); + } + } + } - public const int StabilityFactor = 300; // 300% greater (3 times) than smallest faction - public const int StabilityActivation = 200; // Stablity code goes into effect when largest faction has > 200 people + if (killerState == null) + return; - public static Faction FindSmallestFaction() - { - List factions = Factions; - Faction smallest = null; + if (victim is BaseCreature bc) + { + Faction victimFaction = bc.FactionAllegiance; - for ( int i = 0; i < factions.Count; ++i ) - { - Faction faction = factions[i]; + if (bc.Map == Facet && victimFaction != null && killerState.Faction != victimFaction) + { + int silver = killerState.Faction.AwardSilver(killer, bc.FactionSilverWorth); - if ( smallest == null || faction.Members.Count < smallest.Members.Count ) - smallest = faction; - } - - return smallest; - } - - public static bool StabilityActive() - { - List factions = Factions; + if (silver > 0) + killer.SendLocalizedMessage(1042748, + silver.ToString("N0")); // Thou hast earned ~1_AMOUNT~ silver for vanquishing the vile creature. + } - for ( int i = 0; i < factions.Count; ++i ) - { - Faction faction = factions[i]; + #region Ethics - if ( faction.Members.Count > StabilityActivation ) - return true; - } + if (bc.Map == Facet && bc.GetEthicAllegiance(killer) == BaseCreature.Allegiance.Enemy) + { + Player killerEPL = Player.Find(killer); - return false; - } + if (killerEPL != null && 100 - killerEPL.Power > Utility.Random(100)) + { + ++killerEPL.Power; + ++killerEPL.History; + } + } - public bool CanHandleInflux( int influx ) - { - if ( !StabilityActive()) - return true; + #endregion - Faction smallest = FindSmallestFaction(); - - if ( smallest == null ) - return true; // sanity + return; + } - if ( StabilityFactor > 0 && (((Members.Count + influx) * 100) / StabilityFactor) > smallest.Members.Count ) - return false; + PlayerState victimState = PlayerState.Find(victim); - return true; - } + if (victimState == null) + return; - public static void HandleDeath( Mobile victim, Mobile killer ) - { - if ( killer == null ) - killer = victim.FindMostRecentDamager( true ); + #region Dueling - PlayerState killerState = PlayerState.Find( killer ); + if (victim.Region.IsPartOf(typeof(SafeZone))) + return; - Container pack = victim.Backpack; + #endregion - if ( pack != null ) - { - Container killerPack = killer?.Backpack; - Item[] sigils = pack.FindItemsByType( typeof( Sigil ) ); + if (killer == victim || killerState.Faction != victimState.Faction) + ApplySkillLoss(victim); - for ( int i = 0; i < sigils.Length; ++i ) - { - Sigil sigil = (Sigil)sigils[i]; - - if ( killerState != null && killerPack != null ) - { - if ( killer.GetDistanceToSqrt( victim ) > 64 ) { - sigil.ReturnHome(); - killer.SendLocalizedMessage( 1042230 ); // The sigil has gone back to its home location. - } - else if ( Sigil.ExistsOn( killer ) ) - { - sigil.ReturnHome(); - killer.SendLocalizedMessage( 1010258 ); // The sigil has gone back to its home location because you already have a sigil. - } - else if ( !killerPack.TryDropItem( killer, sigil, false ) ) - { - sigil.ReturnHome(); - killer.SendLocalizedMessage( 1010259 ); // The sigil has gone home because your backpack is full. - } - } - else - { - sigil.ReturnHome(); - } - } - } - - if ( killerState == null ) - return; - - if ( victim is BaseCreature bc ) - { - Faction victimFaction = bc.FactionAllegiance; - - if ( bc.Map == Facet && victimFaction != null && killerState.Faction != victimFaction ) - { - int silver = killerState.Faction.AwardSilver( killer, bc.FactionSilverWorth ); - - if ( silver > 0 ) - killer.SendLocalizedMessage( 1042748, silver.ToString( "N0" ) ); // Thou hast earned ~1_AMOUNT~ silver for vanquishing the vile creature. - } - - #region Ethics - if ( bc.Map == Facet && bc.GetEthicAllegiance( killer ) == BaseCreature.Allegiance.Enemy ) - { - Ethics.Player killerEPL = Ethics.Player.Find( killer ); + if (killerState.Faction != victimState.Faction) + { + if (victimState.KillPoints <= -6) + { + killer.SendLocalizedMessage(501693); // This victim is not worth enough to get kill points from. - if ( killerEPL != null && ( 100 - killerEPL.Power ) > Utility.Random( 100 ) ) - { - ++killerEPL.Power; - ++killerEPL.History; - } - } - #endregion - - return; - } - - PlayerState victimState = PlayerState.Find( victim ); - - if ( victimState == null ) - return; - - #region Dueling - if ( victim.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - return; - #endregion - - if ( killer == victim || killerState.Faction != victimState.Faction ) - ApplySkillLoss( victim ); - - if ( killerState.Faction != victimState.Faction ) - { - if ( victimState.KillPoints <= -6 ) - { - killer.SendLocalizedMessage( 501693 ); // This victim is not worth enough to get kill points from. - - #region Ethics - Ethics.Player killerEPL = Ethics.Player.Find( killer ); - Ethics.Player victimEPL = Ethics.Player.Find( victim ); - - if ( killerEPL != null && victimEPL != null && victimEPL.Power > 0 && victimState.CanGiveSilverTo( killer ) ) - { - int powerTransfer = Math.Max( 1, victimEPL.Power / 5 ); - - if ( powerTransfer > ( 100 - killerEPL.Power ) ) - powerTransfer = 100 - killerEPL.Power; - - if ( powerTransfer > 0 ) - { - victimEPL.Power -= ( powerTransfer + 1 ) / 2; - killerEPL.Power += powerTransfer; - - killerEPL.History += powerTransfer; - - victimState.OnGivenSilverTo( killer ); - } - } - #endregion - } - else - { - int award = Math.Max( victimState.KillPoints / 10, 1 ); - - if ( award > 40 ) - award = 40; - - if ( victimState.CanGiveSilverTo( killer ) ) - { - PowerFactionItem.CheckSpawn( killer, victim ); + #region Ethics - if ( victimState.KillPoints > 0 ) - { - victimState.IsActive = true; + Player killerEPL = Player.Find(killer); + Player victimEPL = Player.Find(victim); - if ( 1 > Utility.Random( 3 ) ) - killerState.IsActive = true; + if (killerEPL != null && victimEPL != null && victimEPL.Power > 0 && victimState.CanGiveSilverTo(killer)) + { + int powerTransfer = Math.Max(1, victimEPL.Power / 5); - int silver = 0; + if (powerTransfer > 100 - killerEPL.Power) + powerTransfer = 100 - killerEPL.Power; - silver = killerState.Faction.AwardSilver( killer, award * 40 ); + if (powerTransfer > 0) + { + victimEPL.Power -= (powerTransfer + 1) / 2; + killerEPL.Power += powerTransfer; - if ( silver > 0 ) - killer.SendLocalizedMessage( 1042736, $"{silver:N0} silver\t{victim.Name}"); // You have earned ~1_SILVER_AMOUNT~ pieces for vanquishing ~2_PLAYER_NAME~! - } + killerEPL.History += powerTransfer; - victimState.KillPoints -= award; - killerState.KillPoints += award; + victimState.OnGivenSilverTo(killer); + } + } - int offset = ( award != 1 ? 0 : 2 ); // for pluralization + #endregion + } + else + { + int award = Math.Max(victimState.KillPoints / 10, 1); - string args = $"{award}\t{victim.Name}\t{killer.Name}"; + if (award > 40) + award = 40; - killer.SendLocalizedMessage( 1042737 + offset, args ); // Thou hast been honored with ~1_KILL_POINTS~ kill point(s) for vanquishing ~2_DEAD_PLAYER~! - victim.SendLocalizedMessage( 1042738 + offset, args ); // Thou has lost ~1_KILL_POINTS~ kill point(s) to ~3_ATTACKER_NAME~ for being vanquished! + if (victimState.CanGiveSilverTo(killer)) + { + PowerFactionItem.CheckSpawn(killer, victim); - #region Ethics - Ethics.Player killerEPL = Ethics.Player.Find( killer ); - Ethics.Player victimEPL = Ethics.Player.Find( victim ); + if (victimState.KillPoints > 0) + { + victimState.IsActive = true; - if ( killerEPL != null && victimEPL != null && victimEPL.Power > 0 ) - { - int powerTransfer = Math.Max( 1, victimEPL.Power / 5 ); + if (1 > Utility.Random(3)) + killerState.IsActive = true; - if ( powerTransfer > ( 100 - killerEPL.Power ) ) - powerTransfer = 100 - killerEPL.Power; + int silver = 0; - if ( powerTransfer > 0 ) - { - victimEPL.Power -= ( powerTransfer + 1 ) / 2; - killerEPL.Power += powerTransfer; + silver = killerState.Faction.AwardSilver(killer, award * 40); - killerEPL.History += powerTransfer; - } - } - #endregion + if (silver > 0) + killer.SendLocalizedMessage(1042736, + $"{silver:N0} silver\t{victim.Name}"); // You have earned ~1_SILVER_AMOUNT~ pieces for vanquishing ~2_PLAYER_NAME~! + } - victimState.OnGivenSilverTo( killer ); - } - else - { - killer.SendLocalizedMessage( 1042231 ); // You have recently defeated this enemy and thus their death brings you no honor. - } - } - } - } + victimState.KillPoints -= award; + killerState.KillPoints += award; - private static void EventSink_Logout( LogoutEventArgs e ) - { - Mobile mob = e.Mobile; + int offset = award != 1 ? 0 : 2; // for pluralization - Container pack = mob.Backpack; + string args = $"{award}\t{victim.Name}\t{killer.Name}"; - if ( pack == null ) - return; + killer.SendLocalizedMessage(1042737 + offset, + args); // Thou hast been honored with ~1_KILL_POINTS~ kill point(s) for vanquishing ~2_DEAD_PLAYER~! + victim.SendLocalizedMessage(1042738 + offset, + args); // Thou has lost ~1_KILL_POINTS~ kill point(s) to ~3_ATTACKER_NAME~ for being vanquished! - Item[] sigils = pack.FindItemsByType( typeof( Sigil ) ); + #region Ethics - for ( int i = 0; i < sigils.Length; ++i ) - ((Sigil)sigils[i]).ReturnHome(); - } + Player killerEPL = Player.Find(killer); + Player victimEPL = Player.Find(victim); - private static void EventSink_Login( LoginEventArgs e ) - { - Mobile mob = e.Mobile; - - CheckLeaveTimer( mob ); - } - - public static readonly Map Facet = Map.Felucca; - - public static void WriteReference( GenericWriter writer, Faction fact ) - { - int idx = Factions.IndexOf( fact ); - - writer.WriteEncodedInt( (int) (idx + 1) ); - } - - public static List Factions => Reflector.Factions; - - public static Faction ReadReference( GenericReader reader ) - { - int idx = reader.ReadEncodedInt() - 1; - - if ( idx >= 0 && idx < Factions.Count ) - return Factions[idx]; - - return null; - } - - public static Faction Find( Mobile mob ) - { - return Find( mob, false, false ); - } - - public static Faction Find( Mobile mob, bool inherit ) - { - return Find( mob, inherit, false ); - } - - public static Faction Find( Mobile mob, bool inherit, bool creatureAllegiances ) - { - PlayerState pl = PlayerState.Find( mob ); - - if ( pl != null ) - return pl.Faction; - - if ( inherit && mob is BaseCreature bc ) - { - if ( bc.Controlled ) - return Find( bc.ControlMaster, false ); - if ( bc.Summoned ) - return Find( bc.SummonMaster, false ); - if ( creatureAllegiances && bc is BaseFactionGuard guard ) - return guard.Faction; - if ( creatureAllegiances ) - return bc.FactionAllegiance; - } - - return null; - } - - public static Faction Parse( string name ) - { - List factions = Factions; - - for ( int i = 0; i < factions.Count; ++i ) - { - Faction faction = factions[i]; - - if ( Insensitive.Equals( faction.Definition.FriendlyName, name ) ) - return faction; - } - - return null; - } - } - - public enum FactionKickType - { - Kick, - Ban, - Unban - } - - public class FactionKickCommand : BaseCommand - { - private FactionKickType m_KickType; - - public FactionKickCommand( FactionKickType kickType ) - { - m_KickType = kickType; - - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllMobiles; - ObjectTypes = ObjectTypes.Mobiles; - - switch ( m_KickType ) - { - case FactionKickType.Kick: - { - Commands = new[]{ "FactionKick" }; - Usage = "FactionKick"; - Description = "Kicks the targeted player out of his current faction. This does not prevent them from rejoining."; - break; - } - case FactionKickType.Ban: - { - Commands = new[]{ "FactionBan" }; - Usage = "FactionBan"; - Description = "Bans the account of a targeted player from joining factions. All players on the account are removed from their current faction, if any."; - break; - } - case FactionKickType.Unban: - { - Commands = new[]{ "FactionUnban" }; - Usage = "FactionUnban"; - Description = "Unbans the account of a targeted player from joining factions."; - break; - } - } - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile mob = (Mobile)obj; - - switch ( m_KickType ) - { - case FactionKickType.Kick: - { - PlayerState pl = PlayerState.Find( mob ); - - if ( pl != null ) - { - pl.Faction.RemoveMember( mob ); - mob.SendMessage( "You have been kicked from your faction." ); - AddResponse( "They have been kicked from their faction." ); - } - else - { - LogFailure( "They are not in a faction." ); - } - - break; - } - case FactionKickType.Ban: - { - if ( mob.Account is Account acct ) - { - if ( acct.GetTag( "FactionBanned" ) == null ) - { - acct.SetTag( "FactionBanned", "true" ); - AddResponse( "The account has been banned from joining factions." ); - } - else - { - AddResponse( "The account is already banned from joining factions." ); - } - - for ( int i = 0; i < acct.Length; ++i ) - { - mob = acct[i]; - - if ( mob != null ) - { - PlayerState pl = PlayerState.Find( mob ); - - if ( pl != null ) - { - pl.Faction.RemoveMember( mob ); - mob.SendMessage( "You have been kicked from your faction." ); - AddResponse( "They have been kicked from their faction." ); - } - } - } - } - else - { - LogFailure( "They have no assigned account." ); - } - - break; - } - case FactionKickType.Unban: - { - if ( mob.Account is Account acct ) - { - if ( acct.GetTag( "FactionBanned" ) == null ) - { - AddResponse( "The account is not already banned from joining factions." ); - } - else - { - acct.RemoveTag( "FactionBanned" ); - AddResponse( "The account may now freely join factions." ); - } - } - else - { - LogFailure( "They have no assigned account." ); - } - - break; - } - } - } - } -} + if (killerEPL != null && victimEPL != null && victimEPL.Power > 0) + { + int powerTransfer = Math.Max(1, victimEPL.Power / 5); + + if (powerTransfer > 100 - killerEPL.Power) + powerTransfer = 100 - killerEPL.Power; + + if (powerTransfer > 0) + { + victimEPL.Power -= (powerTransfer + 1) / 2; + killerEPL.Power += powerTransfer; + + killerEPL.History += powerTransfer; + } + } + + #endregion + + victimState.OnGivenSilverTo(killer); + } + else + { + killer.SendLocalizedMessage( + 1042231); // You have recently defeated this enemy and thus their death brings you no honor. + } + } + } + } + + private static void EventSink_Logout(LogoutEventArgs e) + { + Mobile mob = e.Mobile; + + Container pack = mob.Backpack; + + if (pack == null) + return; + + Item[] sigils = pack.FindItemsByType(typeof(Sigil)); + + for (int i = 0; i < sigils.Length; ++i) + ((Sigil)sigils[i]).ReturnHome(); + } + + private static void EventSink_Login(LoginEventArgs e) + { + Mobile mob = e.Mobile; + + CheckLeaveTimer(mob); + } + + public static void WriteReference(GenericWriter writer, Faction fact) + { + int idx = Factions.IndexOf(fact); + + writer.WriteEncodedInt(idx + 1); + } + + public static Faction ReadReference(GenericReader reader) + { + int idx = reader.ReadEncodedInt() - 1; + + if (idx >= 0 && idx < Factions.Count) + return Factions[idx]; + + return null; + } + + public static Faction Find(Mobile mob) + { + return Find(mob, false, false); + } + + public static Faction Find(Mobile mob, bool inherit) + { + return Find(mob, inherit, false); + } + + public static Faction Find(Mobile mob, bool inherit, bool creatureAllegiances) + { + PlayerState pl = PlayerState.Find(mob); + + if (pl != null) + return pl.Faction; + + if (inherit && mob is BaseCreature bc) + { + if (bc.Controlled) + return Find(bc.ControlMaster, false); + if (bc.Summoned) + return Find(bc.SummonMaster, false); + if (creatureAllegiances && bc is BaseFactionGuard guard) + return guard.Faction; + if (creatureAllegiances) + return bc.FactionAllegiance; + } + + return null; + } + + public static Faction Parse(string name) + { + List factions = Factions; + + for (int i = 0; i < factions.Count; ++i) + { + Faction faction = factions[i]; + + if (Insensitive.Equals(faction.Definition.FriendlyName, name)) + return faction; + } + + return null; + } + + private class BroadcastPrompt : Prompt + { + private Faction m_Faction; + + public BroadcastPrompt(Faction faction) + { + m_Faction = faction; + } + + public override void OnResponse(Mobile from, string text) + { + m_Faction.EndBroadcast(from, text); + } + } + + #region Skill Loss + + public const double SkillLossFactor = 1.0 / 3; + public static readonly TimeSpan SkillLossPeriod = TimeSpan.FromMinutes(20.0); + + private static Dictionary m_SkillLoss = new Dictionary(); + + private class SkillLossContext + { + public List m_Mods; + public Timer m_Timer; + } + + public static bool InSkillLoss(Mobile mob) + { + return m_SkillLoss.ContainsKey(mob); + } + + public static void ApplySkillLoss(Mobile mob) + { + if (InSkillLoss(mob)) + return; + + SkillLossContext context = new SkillLossContext(); + m_SkillLoss[mob] = context; + + List mods = context.m_Mods = new List(); + + for (int i = 0; i < mob.Skills.Length; ++i) + { + Skill sk = mob.Skills[i]; + double baseValue = sk.Base; + + if (baseValue > 0) + { + SkillMod mod = new DefaultSkillMod(sk.SkillName, true, -(baseValue * SkillLossFactor)); + + mods.Add(mod); + mob.AddSkillMod(mod); + } + } + + context.m_Timer = Timer.DelayCall(SkillLossPeriod, new TimerStateCallback(ClearSkillLoss_Callback), mob); + } + + private static void ClearSkillLoss_Callback(object state) + { + ClearSkillLoss((Mobile)state); + } + + public static bool ClearSkillLoss(Mobile mob) + { + if (!m_SkillLoss.TryGetValue(mob, out SkillLossContext context)) + return false; + + m_SkillLoss.Remove(mob); + + List mods = context.m_Mods; + + for (int i = 0; i < mods.Count; ++i) + mob.RemoveSkillMod(mods[i]); + + context.m_Timer.Stop(); + + return true; + } + + #endregion + } + + public enum FactionKickType + { + Kick, + Ban, + Unban + } + + public class FactionKickCommand : BaseCommand + { + private FactionKickType m_KickType; + + public FactionKickCommand(FactionKickType kickType) + { + m_KickType = kickType; + + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllMobiles; + ObjectTypes = ObjectTypes.Mobiles; + + switch (m_KickType) + { + case FactionKickType.Kick: + { + Commands = new[] { "FactionKick" }; + Usage = "FactionKick"; + Description = + "Kicks the targeted player out of his current faction. This does not prevent them from rejoining."; + break; + } + case FactionKickType.Ban: + { + Commands = new[] { "FactionBan" }; + Usage = "FactionBan"; + Description = + "Bans the account of a targeted player from joining factions. All players on the account are removed from their current faction, if any."; + break; + } + case FactionKickType.Unban: + { + Commands = new[] { "FactionUnban" }; + Usage = "FactionUnban"; + Description = "Unbans the account of a targeted player from joining factions."; + break; + } + } + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile mob = (Mobile)obj; + + switch (m_KickType) + { + case FactionKickType.Kick: + { + PlayerState pl = PlayerState.Find(mob); + + if (pl != null) + { + pl.Faction.RemoveMember(mob); + mob.SendMessage("You have been kicked from your faction."); + AddResponse("They have been kicked from their faction."); + } + else + { + LogFailure("They are not in a faction."); + } + + break; + } + case FactionKickType.Ban: + { + if (mob.Account is Account acct) + { + if (acct.GetTag("FactionBanned") == null) + { + acct.SetTag("FactionBanned", "true"); + AddResponse("The account has been banned from joining factions."); + } + else + { + AddResponse("The account is already banned from joining factions."); + } + + for (int i = 0; i < acct.Length; ++i) + { + mob = acct[i]; + + if (mob != null) + { + PlayerState pl = PlayerState.Find(mob); + + if (pl != null) + { + pl.Faction.RemoveMember(mob); + mob.SendMessage("You have been kicked from your faction."); + AddResponse("They have been kicked from their faction."); + } + } + } + } + else + { + LogFailure("They have no assigned account."); + } + + break; + } + case FactionKickType.Unban: + { + if (mob.Account is Account acct) + { + if (acct.GetTag("FactionBanned") == null) + { + AddResponse("The account is not already banned from joining factions."); + } + else + { + acct.RemoveTag("FactionBanned"); + AddResponse("The account may now freely join factions."); + } + } + else + { + LogFailure("They have no assigned account."); + } + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/FactionItem.cs b/Scripts/Engines/Factions/Core/FactionItem.cs index 9b7ddc449..9233cc2df 100644 --- a/Scripts/Engines/Factions/Core/FactionItem.cs +++ b/Scripts/Engines/Factions/Core/FactionItem.cs @@ -2,142 +2,142 @@ using System; namespace Server.Factions { - public interface IFactionItem - { - FactionItem FactionItemState{ get; set; } - } + public interface IFactionItem + { + FactionItem FactionItemState{ get; set; } + } - public class FactionItem - { - public static readonly TimeSpan ExpirationPeriod = TimeSpan.FromDays( 21.0 ); + public class FactionItem + { + public static readonly TimeSpan ExpirationPeriod = TimeSpan.FromDays(21.0); - public Item Item { get; } + public FactionItem(Item item, Faction faction) + { + Item = item; + Faction = faction; + } - public Faction Faction { get; } + public FactionItem(GenericReader reader, Faction faction) + { + int version = reader.ReadEncodedInt(); - public DateTime Expiration { get; private set; } + switch (version) + { + case 0: + { + Item = reader.ReadItem(); + Expiration = reader.ReadDateTime(); + break; + } + } - public bool HasExpired - { - get - { - if ( Item == null || Item.Deleted ) - return true; + Faction = faction; + } - return ( Expiration != DateTime.MinValue && DateTime.UtcNow >= Expiration ); - } - } + public Item Item{ get; } - public void StartExpiration() - { - Expiration = DateTime.UtcNow + ExpirationPeriod; - } + public Faction Faction{ get; } - public void CheckAttach() - { - if ( !HasExpired ) - Attach(); - else - Detach(); - } + public DateTime Expiration{ get; private set; } - public void Attach() - { - if ( Item is IFactionItem item ) - item.FactionItemState = this; + public bool HasExpired + { + get + { + if (Item == null || Item.Deleted) + return true; - Faction?.State.FactionItems.Add( this ); - } + return Expiration != DateTime.MinValue && DateTime.UtcNow >= Expiration; + } + } - public void Detach() - { - if ( Item is IFactionItem item ) - item.FactionItemState = null; + public void StartExpiration() + { + Expiration = DateTime.UtcNow + ExpirationPeriod; + } - if ( Faction != null && Faction.State.FactionItems.Contains( this ) ) - Faction.State.FactionItems.Remove( this ); - } + public void CheckAttach() + { + if (!HasExpired) + Attach(); + else + Detach(); + } - public FactionItem( Item item, Faction faction ) - { - Item = item; - Faction = faction; - } + public void Attach() + { + if (Item is IFactionItem item) + item.FactionItemState = this; - public FactionItem( GenericReader reader, Faction faction ) - { - int version = reader.ReadEncodedInt(); + Faction?.State.FactionItems.Add(this); + } - switch ( version ) - { - case 0: - { - Item = reader.ReadItem(); - Expiration = reader.ReadDateTime(); - break; - } - } + public void Detach() + { + if (Item is IFactionItem item) + item.FactionItemState = null; - Faction = faction; - } + if (Faction != null && Faction.State.FactionItems.Contains(this)) + Faction.State.FactionItems.Remove(this); + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); - writer.Write( (Item) Item ); - writer.Write( (DateTime) Expiration ); - } + writer.Write(Item); + writer.Write(Expiration); + } - public static int GetMaxWearables( Mobile mob ) - { - PlayerState pl = PlayerState.Find( mob ); + public static int GetMaxWearables(Mobile mob) + { + PlayerState pl = PlayerState.Find(mob); - if ( pl == null ) - return 0; + if (pl == null) + return 0; - if ( pl.Faction.IsCommander( mob ) ) - return 9; + if (pl.Faction.IsCommander(mob)) + return 9; - return pl.Rank.MaxWearables; - } + return pl.Rank.MaxWearables; + } - public static FactionItem Find( Item item ) - { - if ( item is IFactionItem factionItem ) - { - FactionItem state = factionItem.FactionItemState; + public static FactionItem Find(Item item) + { + if (item is IFactionItem factionItem) + { + FactionItem state = factionItem.FactionItemState; - if ( state?.HasExpired == true ) - { - state.Detach(); - state = null; - } + if (state?.HasExpired == true) + { + state.Detach(); + state = null; + } - return state; - } + return state; + } - return null; - } + return null; + } - public static Item Imbue( Item item, Faction faction, bool expire, int hue ) - { - if ( !(item is IFactionItem) ) - return item; + public static Item Imbue(Item item, Faction faction, bool expire, int hue) + { + if (!(item is IFactionItem)) + return item; - FactionItem state = Find( item ); + FactionItem state = Find(item); - if ( state == null ) - { - state = new FactionItem( item, faction ); - state.Attach(); - } + if (state == null) + { + state = new FactionItem(item, faction); + state.Attach(); + } - if ( expire ) - state.StartExpiration(); + if (expire) + state.StartExpiration(); - item.Hue = hue; - return item; - } - } -} + item.Hue = hue; + return item; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/FactionState.cs b/Scripts/Engines/Factions/Core/FactionState.cs index 7b6c84393..3bb1e9c86 100644 --- a/Scripts/Engines/Factions/Core/FactionState.cs +++ b/Scripts/Engines/Factions/Core/FactionState.cs @@ -3,277 +3,271 @@ using System.Collections.Generic; namespace Server.Factions { - public class FactionState - { - private Faction m_Faction; - private Mobile m_Commander; + public class FactionState + { + private const int BroadcastsPerPeriod = 2; + private static readonly TimeSpan BroadcastPeriod = TimeSpan.FromHours(1.0); + private Mobile m_Commander; + private Faction m_Faction; + + private DateTime[] m_LastBroadcasts = new DateTime[BroadcastsPerPeriod]; + + public FactionState(Faction faction) + { + m_Faction = faction; + Tithe = 50; + Members = new List(); + Election = new Election(faction); + FactionItems = new List(); + Traps = new List(); + } + + public FactionState(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 5: + { + LastAtrophy = reader.ReadDateTime(); + goto case 4; + } + case 4: + { + int count = reader.ReadEncodedInt(); + + for (int i = 0; i < count; ++i) + { + DateTime time = reader.ReadDateTime(); + + if (i < m_LastBroadcasts.Length) + m_LastBroadcasts[i] = time; + } + + goto case 3; + } + case 3: + case 2: + case 1: + { + Election = new Election(reader); + + goto case 0; + } + case 0: + { + m_Faction = Faction.ReadReference(reader); + + m_Commander = reader.ReadMobile(); + + if (version < 5) + LastAtrophy = DateTime.UtcNow; + + if (version < 4) + { + DateTime time = reader.ReadDateTime(); + + if (m_LastBroadcasts.Length > 0) + m_LastBroadcasts[0] = time; + } - private const int BroadcastsPerPeriod = 2; - private static readonly TimeSpan BroadcastPeriod = TimeSpan.FromHours( 1.0 ); + Tithe = reader.ReadEncodedInt(); + Silver = reader.ReadEncodedInt(); - private DateTime[] m_LastBroadcasts = new DateTime[BroadcastsPerPeriod]; + int memberCount = reader.ReadEncodedInt(); - public DateTime LastAtrophy { get; set; } + Members = new List(); - public bool FactionMessageReady - { - get - { - for ( int i = 0; i < m_LastBroadcasts.Length; ++i ) - { - if ( DateTime.UtcNow >= (m_LastBroadcasts[i] + BroadcastPeriod) ) - return true; - } - - return false; - } - } - - public bool IsAtrophyReady => DateTime.UtcNow >= (LastAtrophy + TimeSpan.FromHours( 47.0 )); - - public int CheckAtrophy() - { - if ( DateTime.UtcNow < (LastAtrophy + TimeSpan.FromHours( 47.0 )) ) - return 0; - - int distrib = 0; - LastAtrophy = DateTime.UtcNow; - - List members = new List( Members ); - - for ( int i = 0; i < members.Count; ++i ) - { - PlayerState ps = members[i]; - - if ( ps.IsActive ) - { - ps.IsActive = false; - continue; - } - - if ( ps.KillPoints > 0 ) - { - int atrophy = ( ps.KillPoints + 9 ) / 10; - ps.KillPoints -= atrophy; - distrib += atrophy; - } - } - - return distrib; - } - - public void RegisterBroadcast() - { - for ( int i = 0; i < m_LastBroadcasts.Length; ++i ) - { - if ( DateTime.UtcNow >= (m_LastBroadcasts[i] + BroadcastPeriod) ) - { - m_LastBroadcasts[i] = DateTime.UtcNow; - break; - } - } - } - - public List FactionItems { get; set; } - - public List Traps { get; set; } - - public Election Election { get; set; } - - public Mobile Commander - { - get => m_Commander; - set - { - m_Commander?.InvalidateProperties(); - - m_Commander = value; - - if ( m_Commander != null ) - { - m_Commander.SendLocalizedMessage( 1042227 ); // You have been elected Commander of your faction - - m_Commander.InvalidateProperties(); - - PlayerState pl = PlayerState.Find( m_Commander ); - - if ( pl?.Finance != null ) - pl.Finance.Finance = null; - - if ( pl?.Sheriff != null ) - pl.Sheriff.Sheriff = null; - } - } - } - - public int Tithe { get; set; } + for (int i = 0; i < memberCount; ++i) + { + PlayerState pl = new PlayerState(reader, m_Faction, Members); - public int Silver { get; set; } - - public List Members { get; set; } - - public FactionState( Faction faction ) - { - m_Faction = faction; - Tithe = 50; - Members = new List(); - Election = new Election( faction ); - FactionItems = new List(); - Traps = new List(); - } + if (pl.Mobile != null) + Members.Add(pl); + } - public FactionState( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 5: - { - LastAtrophy = reader.ReadDateTime(); - goto case 4; - } - case 4: - { - int count = reader.ReadEncodedInt(); - - for ( int i = 0; i < count; ++i ) - { - DateTime time = reader.ReadDateTime(); - - if ( i < m_LastBroadcasts.Length ) - m_LastBroadcasts[i] = time; - } + m_Faction.State = this; - goto case 3; - } - case 3: - case 2: - case 1: - { - Election = new Election( reader ); + m_Faction.ZeroRankOffset = Members.Count; + Members.Sort(); - goto case 0; - } - case 0: - { - m_Faction = Faction.ReadReference( reader ); + for (int i = Members.Count - 1; i >= 0; i--) + { + PlayerState player = Members[i]; - m_Commander = reader.ReadMobile(); + if (player.KillPoints <= 0) + m_Faction.ZeroRankOffset = i; + else + player.RankIndex = i; + } - if ( version < 5 ) - LastAtrophy = DateTime.UtcNow; + FactionItems = new List(); - if ( version < 4 ) - { - DateTime time = reader.ReadDateTime(); + if (version >= 2) + { + int factionItemCount = reader.ReadEncodedInt(); - if ( m_LastBroadcasts.Length > 0 ) - m_LastBroadcasts[0] = time; - } + for (int i = 0; i < factionItemCount; ++i) + { + FactionItem factionItem = new FactionItem(reader, m_Faction); - Tithe = reader.ReadEncodedInt(); - Silver = reader.ReadEncodedInt(); + Timer.DelayCall(TimeSpan.Zero, factionItem.CheckAttach); // sandbox attachment + } + } - int memberCount = reader.ReadEncodedInt(); + Traps = new List(); - Members = new List(); + if (version >= 3) + { + int factionTrapCount = reader.ReadEncodedInt(); - for ( int i = 0; i < memberCount; ++i ) - { - PlayerState pl = new PlayerState( reader, m_Faction, Members ); + for (int i = 0; i < factionTrapCount; ++i) + if (reader.ReadItem() is BaseFactionTrap trap && !trap.CheckDecay()) + Traps.Add(trap); + } - if ( pl.Mobile != null ) - Members.Add( pl ); - } + break; + } + } - m_Faction.State = this; + if (version < 1) + Election = new Election(m_Faction); + } - m_Faction.ZeroRankOffset = Members.Count; - Members.Sort(); + public DateTime LastAtrophy{ get; set; } - for ( int i = Members.Count - 1; i >= 0; i-- ) { - PlayerState player = Members[i]; + public bool FactionMessageReady + { + get + { + for (int i = 0; i < m_LastBroadcasts.Length; ++i) + if (DateTime.UtcNow >= m_LastBroadcasts[i] + BroadcastPeriod) + return true; - if ( player.KillPoints <= 0 ) - m_Faction.ZeroRankOffset = i; - else - player.RankIndex = i; - } + return false; + } + } - FactionItems = new List(); + public bool IsAtrophyReady => DateTime.UtcNow >= LastAtrophy + TimeSpan.FromHours(47.0); - if ( version >= 2 ) - { - int factionItemCount = reader.ReadEncodedInt(); + public List FactionItems{ get; set; } - for ( int i = 0; i < factionItemCount; ++i ) - { - FactionItem factionItem = new FactionItem( reader, m_Faction ); + public List Traps{ get; set; } - Timer.DelayCall( TimeSpan.Zero, factionItem.CheckAttach ); // sandbox attachment - } - } + public Election Election{ get; set; } - Traps = new List(); + public Mobile Commander + { + get => m_Commander; + set + { + m_Commander?.InvalidateProperties(); - if ( version >= 3 ) - { - int factionTrapCount = reader.ReadEncodedInt(); + m_Commander = value; - for ( int i = 0; i < factionTrapCount; ++i ) - { - if ( reader.ReadItem() is BaseFactionTrap trap && !trap.CheckDecay() ) - Traps.Add( trap ); - } - } + if (m_Commander != null) + { + m_Commander.SendLocalizedMessage(1042227); // You have been elected Commander of your faction - break; - } - } + m_Commander.InvalidateProperties(); - if ( version < 1 ) - Election = new Election( m_Faction ); - } + PlayerState pl = PlayerState.Find(m_Commander); - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 5 ); // version + if (pl?.Finance != null) + pl.Finance.Finance = null; - writer.Write( LastAtrophy ); + if (pl?.Sheriff != null) + pl.Sheriff.Sheriff = null; + } + } + } - writer.WriteEncodedInt( (int) m_LastBroadcasts.Length ); + public int Tithe{ get; set; } - for ( int i = 0; i < m_LastBroadcasts.Length; ++i ) - writer.Write( (DateTime) m_LastBroadcasts[i] ); + public int Silver{ get; set; } - Election.Serialize( writer ); + public List Members{ get; set; } - Faction.WriteReference( writer, m_Faction ); + public int CheckAtrophy() + { + if (DateTime.UtcNow < LastAtrophy + TimeSpan.FromHours(47.0)) + return 0; - writer.Write( (Mobile) m_Commander ); + int distrib = 0; + LastAtrophy = DateTime.UtcNow; - writer.WriteEncodedInt( (int) Tithe ); - writer.WriteEncodedInt( (int) Silver ); + List members = new List(Members); - writer.WriteEncodedInt( (int) Members.Count ); + for (int i = 0; i < members.Count; ++i) + { + PlayerState ps = members[i]; - for ( int i = 0; i < Members.Count; ++i ) - { - PlayerState pl = (PlayerState) Members[i]; + if (ps.IsActive) + { + ps.IsActive = false; + continue; + } - pl.Serialize( writer ); - } + if (ps.KillPoints > 0) + { + int atrophy = (ps.KillPoints + 9) / 10; + ps.KillPoints -= atrophy; + distrib += atrophy; + } + } - writer.WriteEncodedInt( (int) FactionItems.Count ); + return distrib; + } - for ( int i = 0; i < FactionItems.Count; ++i ) - FactionItems[i].Serialize( writer ); + public void RegisterBroadcast() + { + for (int i = 0; i < m_LastBroadcasts.Length; ++i) + if (DateTime.UtcNow >= m_LastBroadcasts[i] + BroadcastPeriod) + { + m_LastBroadcasts[i] = DateTime.UtcNow; + break; + } + } - writer.WriteEncodedInt( (int) Traps.Count ); + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(5); // version - for ( int i = 0; i < Traps.Count; ++i ) - writer.Write( (Item) Traps[i] ); - } - } -} + writer.Write(LastAtrophy); + + writer.WriteEncodedInt(m_LastBroadcasts.Length); + + for (int i = 0; i < m_LastBroadcasts.Length; ++i) + writer.Write(m_LastBroadcasts[i]); + + Election.Serialize(writer); + + Faction.WriteReference(writer, m_Faction); + + writer.Write(m_Commander); + + writer.WriteEncodedInt(Tithe); + writer.WriteEncodedInt(Silver); + + writer.WriteEncodedInt(Members.Count); + + for (int i = 0; i < Members.Count; ++i) + { + PlayerState pl = Members[i]; + + pl.Serialize(writer); + } + + writer.WriteEncodedInt(FactionItems.Count); + + for (int i = 0; i < FactionItems.Count; ++i) + FactionItems[i].Serialize(writer); + + writer.WriteEncodedInt(Traps.Count); + + for (int i = 0; i < Traps.Count; ++i) + writer.Write(Traps[i]); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Generator.cs b/Scripts/Engines/Factions/Core/Generator.cs index e788b5a22..5940970de 100644 --- a/Scripts/Engines/Factions/Core/Generator.cs +++ b/Scripts/Engines/Factions/Core/Generator.cs @@ -1,80 +1,78 @@ using System; -using Server.Commands; using System.Collections.Generic; +using Server.Commands; namespace Server.Factions { - public class Generator - { - public static void Initialize() - { - CommandSystem.Register( "GenerateFactions", AccessLevel.Administrator, GenerateFactions_OnCommand ); - } + public class Generator + { + public static void Initialize() + { + CommandSystem.Register("GenerateFactions", AccessLevel.Administrator, GenerateFactions_OnCommand); + } - public static void GenerateFactions_OnCommand( CommandEventArgs e ) - { - new FactionPersistance(); + public static void GenerateFactions_OnCommand(CommandEventArgs e) + { + new FactionPersistance(); - List factions = Faction.Factions; + List factions = Faction.Factions; - foreach ( Faction faction in factions ) - Generate( faction ); + foreach (Faction faction in factions) + Generate(faction); - List towns = Town.Towns; + List towns = Town.Towns; - foreach ( Town town in towns ) - Generate( town ); - } + foreach (Town town in towns) + Generate(town); + } - public static void Generate( Town town ) - { - Map facet = Faction.Facet; + public static void Generate(Town town) + { + Map facet = Faction.Facet; - TownDefinition def = town.Definition; + TownDefinition def = town.Definition; - if ( !CheckExistance( def.Monolith, facet, typeof( TownMonolith ) ) ) - { - TownMonolith mono = new TownMonolith( town ); - mono.MoveToWorld( def.Monolith, facet ); - mono.Sigil = new Sigil( town ); - } + if (!CheckExistance(def.Monolith, facet, typeof(TownMonolith))) + { + TownMonolith mono = new TownMonolith(town); + mono.MoveToWorld(def.Monolith, facet); + mono.Sigil = new Sigil(town); + } - if ( !CheckExistance( def.TownStone, facet, typeof( TownStone ) ) ) - new TownStone( town ).MoveToWorld( def.TownStone, facet ); - } + if (!CheckExistance(def.TownStone, facet, typeof(TownStone))) + new TownStone(town).MoveToWorld(def.TownStone, facet); + } - public static void Generate( Faction faction ) - { - Map facet = Faction.Facet; + public static void Generate(Faction faction) + { + Map facet = Faction.Facet; - List towns = Town.Towns; + List towns = Town.Towns; - StrongholdDefinition stronghold = faction.Definition.Stronghold; + StrongholdDefinition stronghold = faction.Definition.Stronghold; - if ( !CheckExistance( stronghold.JoinStone, facet, typeof( JoinStone ) ) ) - new JoinStone( faction ).MoveToWorld( stronghold.JoinStone, facet ); + if (!CheckExistance(stronghold.JoinStone, facet, typeof(JoinStone))) + new JoinStone(faction).MoveToWorld(stronghold.JoinStone, facet); - if ( !CheckExistance( stronghold.FactionStone, facet, typeof( FactionStone ) ) ) - new FactionStone( faction ).MoveToWorld( stronghold.FactionStone, facet ); + if (!CheckExistance(stronghold.FactionStone, facet, typeof(FactionStone))) + new FactionStone(faction).MoveToWorld(stronghold.FactionStone, facet); - for ( int i = 0; i < stronghold.Monoliths.Length; ++i ) - { - Point3D monolith = stronghold.Monoliths[i]; + for (int i = 0; i < stronghold.Monoliths.Length; ++i) + { + Point3D monolith = stronghold.Monoliths[i]; - if ( !CheckExistance( monolith, facet, typeof( StrongholdMonolith ) ) ) - new StrongholdMonolith( towns[i], faction ).MoveToWorld( monolith, facet ); - } - } + if (!CheckExistance(monolith, facet, typeof(StrongholdMonolith))) + new StrongholdMonolith(towns[i], faction).MoveToWorld(monolith, facet); + } + } - private static bool CheckExistance( Point3D loc, Map facet, Type type ) - { - foreach ( Item item in facet.GetItemsInRange( loc, 0 ) ) - { - if ( type.IsAssignableFrom( item.GetType() ) ) - return true; - } + private static bool CheckExistance(Point3D loc, Map facet, Type type) + { + foreach (Item item in facet.GetItemsInRange(loc, 0)) + if (type.IsAssignableFrom(item.GetType())) + return true; - return false; - } - } + return false; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/GuardList.cs b/Scripts/Engines/Factions/Core/GuardList.cs index 9117e21c3..d6e26dee7 100644 --- a/Scripts/Engines/Factions/Core/GuardList.cs +++ b/Scripts/Engines/Factions/Core/GuardList.cs @@ -3,22 +3,28 @@ using System.Collections.Generic; namespace Server.Factions { - public class GuardList - { - public GuardDefinition Definition { get; } + public class GuardList + { + public GuardList(GuardDefinition definition) + { + Definition = definition; + Guards = new List(); + } - public List Guards { get; } + public GuardDefinition Definition{ get; } - public BaseFactionGuard Construct() - { - try{ return Activator.CreateInstance( Definition.Type ) as BaseFactionGuard; } - catch{ return null; } - } + public List Guards{ get; } - public GuardList( GuardDefinition definition ) - { - Definition = definition; - Guards = new List(); - } - } + public BaseFactionGuard Construct() + { + try + { + return Activator.CreateInstance(Definition.Type) as BaseFactionGuard; + } + catch + { + return null; + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Keywords.cs b/Scripts/Engines/Factions/Core/Keywords.cs index c5ba6a414..4dd124bd2 100644 --- a/Scripts/Engines/Factions/Core/Keywords.cs +++ b/Scripts/Engines/Factions/Core/Keywords.cs @@ -1,154 +1,159 @@ using System; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Factions { - public class Keywords - { - public static void Initialize() - { - EventSink.Speech += EventSink_Speech; - } + public class Keywords + { + public static void Initialize() + { + EventSink.Speech += EventSink_Speech; + } - private static void ShowScore_Sandbox( object state ) - { - PlayerState pl = (PlayerState)state; + private static void ShowScore_Sandbox(object state) + { + PlayerState pl = (PlayerState)state; - pl?.Mobile.PublicOverheadMessage( MessageType.Regular, pl.Mobile.SpeechHue, true, pl.KillPoints.ToString( "N0" ) ); // NOTE: Added 'N0' - } + pl?.Mobile.PublicOverheadMessage(MessageType.Regular, pl.Mobile.SpeechHue, true, + pl.KillPoints.ToString("N0")); // NOTE: Added 'N0' + } - private static void EventSink_Speech( SpeechEventArgs e ) - { - Mobile from = e.Mobile; - int[] keywords = e.Keywords; + private static void EventSink_Speech(SpeechEventArgs e) + { + Mobile from = e.Mobile; + int[] keywords = e.Keywords; - for ( int i = 0; i < keywords.Length; ++i ) - { - switch ( keywords[i] ) - { - case 0x00E4: // *i wish to access the city treasury* - { - Town town = Town.FromRegion( from.Region ); + for (int i = 0; i < keywords.Length; ++i) + switch (keywords[i]) + { + case 0x00E4: // *i wish to access the city treasury* + { + Town town = Town.FromRegion(from.Region); - if ( town == null || !town.IsFinance( from ) || !from.Alive ) - break; + if (town == null || !town.IsFinance(from) || !from.Alive) + break; - if ( FactionGump.Exists( from ) ) - from.SendLocalizedMessage( 1042160 ); // You already have a faction menu open. - else if ( town.Owner != null && from is PlayerMobile mobile ) - mobile.SendGump( new FinanceGump( mobile, town.Owner, town ) ); + if (FactionGump.Exists(from)) + from.SendLocalizedMessage(1042160); // You already have a faction menu open. + else if (town.Owner != null && from is PlayerMobile mobile) + mobile.SendGump(new FinanceGump(mobile, town.Owner, town)); - break; - } - case 0x0ED: // *i am sheriff* - { - Town town = Town.FromRegion( from.Region ); + break; + } + case 0x0ED: // *i am sheriff* + { + Town town = Town.FromRegion(from.Region); - if ( town == null || !town.IsSheriff( from ) || !from.Alive ) - break; + if (town == null || !town.IsSheriff(from) || !from.Alive) + break; - if ( FactionGump.Exists( from ) ) - from.SendLocalizedMessage( 1042160 ); // You already have a faction menu open. - else if ( town.Owner != null ) - from.SendGump( new SheriffGump( (PlayerMobile)from, town.Owner, town ) ); + if (FactionGump.Exists(from)) + from.SendLocalizedMessage(1042160); // You already have a faction menu open. + else if (town.Owner != null) + from.SendGump(new SheriffGump((PlayerMobile)from, town.Owner, town)); - break; - } - case 0x00EF: // *you are fired* - { - Town town = Town.FromRegion( from.Region ); + break; + } + case 0x00EF: // *you are fired* + { + Town town = Town.FromRegion(from.Region); - if ( town == null ) - break; + if (town == null) + break; - if ( town.IsFinance( from ) || town.IsSheriff( from ) ) - town.BeginOrderFiring( from ); + if (town.IsFinance(from) || town.IsSheriff(from)) + town.BeginOrderFiring(from); - break; - } - case 0x00E5: // *i wish to resign as finance minister* - { - PlayerState pl = PlayerState.Find( from ); + break; + } + case 0x00E5: // *i wish to resign as finance minister* + { + PlayerState pl = PlayerState.Find(from); - if ( pl?.Finance != null ) - { - pl.Finance.Finance = null; - from.SendLocalizedMessage( 1005081 ); // You have been fired as Finance Minister - } + if (pl?.Finance != null) + { + pl.Finance.Finance = null; + from.SendLocalizedMessage(1005081); // You have been fired as Finance Minister + } - break; - } - case 0x00EE: // *i wish to resign as sheriff* - { - PlayerState pl = PlayerState.Find( from ); + break; + } + case 0x00EE: // *i wish to resign as sheriff* + { + PlayerState pl = PlayerState.Find(from); - if ( pl?.Sheriff != null ) - { - pl.Sheriff.Sheriff = null; - from.SendLocalizedMessage( 1010270 ); // You have been fired as Sheriff - } + if (pl?.Sheriff != null) + { + pl.Sheriff.Sheriff = null; + from.SendLocalizedMessage(1010270); // You have been fired as Sheriff + } - break; - } - case 0x00E9: // *what is my faction term status* - { - PlayerState pl = PlayerState.Find( from ); + break; + } + case 0x00E9: // *what is my faction term status* + { + PlayerState pl = PlayerState.Find(from); - if ( pl?.IsLeaving == true ) - { - if ( Faction.CheckLeaveTimer( from ) ) - break; + if (pl?.IsLeaving == true) + { + if (Faction.CheckLeaveTimer(from)) + break; - TimeSpan remaining = ( pl.Leaving + Faction.LeavePeriod ) - DateTime.UtcNow; + TimeSpan remaining = pl.Leaving + Faction.LeavePeriod - DateTime.UtcNow; - if ( remaining.TotalDays >= 1 ) - from.SendLocalizedMessage( 1042743, remaining.TotalDays.ToString( "N0" ) ) ;// Your term of service will come to an end in ~1_DAYS~ days. - else if ( remaining.TotalHours >= 1 ) - from.SendLocalizedMessage( 1042741, remaining.TotalHours.ToString( "N0" ) ); // Your term of service will come to an end in ~1_HOURS~ hours. - else - from.SendLocalizedMessage( 1042742 ); // Your term of service will come to an end in less than one hour. - } - else if ( pl != null ) - { - from.SendLocalizedMessage( 1042233 ); // You are not in the process of quitting the faction. - } + if (remaining.TotalDays >= 1) + from.SendLocalizedMessage(1042743, + remaining.TotalDays + .ToString("N0")); // Your term of service will come to an end in ~1_DAYS~ days. + else if (remaining.TotalHours >= 1) + from.SendLocalizedMessage(1042741, + remaining.TotalHours + .ToString("N0")); // Your term of service will come to an end in ~1_HOURS~ hours. + else + from.SendLocalizedMessage( + 1042742); // Your term of service will come to an end in less than one hour. + } + else if (pl != null) + { + from.SendLocalizedMessage(1042233); // You are not in the process of quitting the faction. + } - break; - } - case 0x00EA: // *message faction* - { - Faction faction = Faction.Find( from ); + break; + } + case 0x00EA: // *message faction* + { + Faction faction = Faction.Find(from); - if ( faction == null || !faction.IsCommander( from ) ) - break; + if (faction == null || !faction.IsCommander(from)) + break; - if ( from.AccessLevel == AccessLevel.Player && !faction.FactionMessageReady ) - from.SendLocalizedMessage( 1010264 ); // The required time has not yet passed since the last message was sent - else - faction.BeginBroadcast( from ); + if (from.AccessLevel == AccessLevel.Player && !faction.FactionMessageReady) + from.SendLocalizedMessage( + 1010264); // The required time has not yet passed since the last message was sent + else + faction.BeginBroadcast(from); - break; - } - case 0x00EC: // *showscore* - { - PlayerState pl = PlayerState.Find( from ); + break; + } + case 0x00EC: // *showscore* + { + PlayerState pl = PlayerState.Find(from); - if ( pl != null ) - Timer.DelayCall( TimeSpan.Zero, new TimerStateCallback( ShowScore_Sandbox ), pl ); + if (pl != null) + Timer.DelayCall(TimeSpan.Zero, new TimerStateCallback(ShowScore_Sandbox), pl); - break; - } - case 0x0178: // i honor your leadership - { - Faction faction = Faction.Find( from ); + break; + } + case 0x0178: // i honor your leadership + { + Faction faction = Faction.Find(from); - faction?.BeginHonorLeadership( from ); + faction?.BeginHonorLeadership(from); - break; - } - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/MerchantTitles.cs b/Scripts/Engines/Factions/Core/MerchantTitles.cs index 1a0fb33a6..e14e7f87c 100644 --- a/Scripts/Engines/Factions/Core/MerchantTitles.cs +++ b/Scripts/Engines/Factions/Core/MerchantTitles.cs @@ -1,81 +1,92 @@ namespace Server.Factions { - public enum MerchantTitle - { - None, - Scribe, - Carpenter, - Blacksmith, - Bowyer, - Tialor - } + public enum MerchantTitle + { + None, + Scribe, + Carpenter, + Blacksmith, + Bowyer, + Tialor + } - public class MerchantTitleInfo - { - public SkillName Skill { get; } + public class MerchantTitleInfo + { + public MerchantTitleInfo(SkillName skill, double requirement, TextDefinition title, TextDefinition label, + TextDefinition assigned) + { + Skill = skill; + Requirement = requirement; + Title = title; + Label = label; + Assigned = assigned; + } - public double Requirement { get; } + public SkillName Skill{ get; } - public TextDefinition Title { get; } + public double Requirement{ get; } - public TextDefinition Label { get; } + public TextDefinition Title{ get; } - public TextDefinition Assigned { get; } + public TextDefinition Label{ get; } - public MerchantTitleInfo( SkillName skill, double requirement, TextDefinition title, TextDefinition label, TextDefinition assigned ) - { - Skill = skill; - Requirement = requirement; - Title = title; - Label = label; - Assigned = assigned; - } - } + public TextDefinition Assigned{ get; } + } - public class MerchantTitles - { - public static MerchantTitleInfo[] Info { get; } = - { - new MerchantTitleInfo( SkillName.Inscribe, 90.0, new TextDefinition( 1060773, "Scribe" ), new TextDefinition( 1011468, "SCRIBE" ), new TextDefinition( 1010121, "You now have the faction title of scribe" ) ), - new MerchantTitleInfo( SkillName.Carpentry, 90.0, new TextDefinition( 1060774, "Carpenter" ), new TextDefinition( 1011469, "CARPENTER" ), new TextDefinition( 1010122, "You now have the faction title of carpenter" ) ), - new MerchantTitleInfo( SkillName.Tinkering, 90.0, new TextDefinition( 1022984, "Tinker" ), new TextDefinition( 1011470, "TINKER" ), new TextDefinition( 1010123, "You now have the faction title of tinker" ) ), - new MerchantTitleInfo( SkillName.Blacksmith, 90.0, new TextDefinition( 1023016, "Blacksmith" ), new TextDefinition( 1011471, "BLACKSMITH" ), new TextDefinition( 1010124, "You now have the faction title of blacksmith" ) ), - new MerchantTitleInfo( SkillName.Fletching, 90.0, new TextDefinition( 1023022, "Bowyer" ), new TextDefinition( 1011472, "BOWYER" ), new TextDefinition( 1010125, "You now have the faction title of Bowyer" ) ), - new MerchantTitleInfo( SkillName.Tailoring, 90.0, new TextDefinition( 1022982, "Tailor" ), new TextDefinition( 1018300, "TAILOR" ), new TextDefinition( 1042162, "You now have the faction title of Tailor" ) ), - }; + public class MerchantTitles + { + public static MerchantTitleInfo[] Info{ get; } = + { + new MerchantTitleInfo(SkillName.Inscribe, 90.0, new TextDefinition(1060773, "Scribe"), + new TextDefinition(1011468, "SCRIBE"), + new TextDefinition(1010121, "You now have the faction title of scribe")), + new MerchantTitleInfo(SkillName.Carpentry, 90.0, new TextDefinition(1060774, "Carpenter"), + new TextDefinition(1011469, "CARPENTER"), + new TextDefinition(1010122, "You now have the faction title of carpenter")), + new MerchantTitleInfo(SkillName.Tinkering, 90.0, new TextDefinition(1022984, "Tinker"), + new TextDefinition(1011470, "TINKER"), + new TextDefinition(1010123, "You now have the faction title of tinker")), + new MerchantTitleInfo(SkillName.Blacksmith, 90.0, new TextDefinition(1023016, "Blacksmith"), + new TextDefinition(1011471, "BLACKSMITH"), + new TextDefinition(1010124, "You now have the faction title of blacksmith")), + new MerchantTitleInfo(SkillName.Fletching, 90.0, new TextDefinition(1023022, "Bowyer"), + new TextDefinition(1011472, "BOWYER"), + new TextDefinition(1010125, "You now have the faction title of Bowyer")), + new MerchantTitleInfo(SkillName.Tailoring, 90.0, new TextDefinition(1022982, "Tailor"), + new TextDefinition(1018300, "TAILOR"), + new TextDefinition(1042162, "You now have the faction title of Tailor")) + }; - public static MerchantTitleInfo GetInfo( MerchantTitle title ) - { - int idx = (int)title - 1; + public static MerchantTitleInfo GetInfo(MerchantTitle title) + { + int idx = (int)title - 1; - if ( idx >= 0 && idx < Info.Length ) - return Info[idx]; + if (idx >= 0 && idx < Info.Length) + return Info[idx]; - return null; - } + return null; + } - public static bool HasMerchantQualifications( Mobile mob ) - { - for ( int i = 0; i < Info.Length; ++i ) - { - if ( IsQualified( mob, Info[i] ) ) - return true; - } + public static bool HasMerchantQualifications(Mobile mob) + { + for (int i = 0; i < Info.Length; ++i) + if (IsQualified(mob, Info[i])) + return true; - return false; - } + return false; + } - public static bool IsQualified( Mobile mob, MerchantTitle title ) - { - return IsQualified( mob, GetInfo( title ) ); - } + public static bool IsQualified(Mobile mob, MerchantTitle title) + { + return IsQualified(mob, GetInfo(title)); + } - public static bool IsQualified( Mobile mob, MerchantTitleInfo info ) - { - if ( mob == null || info == null ) - return false; + public static bool IsQualified(Mobile mob, MerchantTitleInfo info) + { + if (mob == null || info == null) + return false; - return ( mob.Skills[info.Skill].Value >= info.Requirement ); - } - } + return mob.Skills[info.Skill].Value >= info.Requirement; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Persistance.cs b/Scripts/Engines/Factions/Core/Persistance.cs index 3e74ebc5d..71c3e01e6 100644 --- a/Scripts/Engines/Factions/Core/Persistance.cs +++ b/Scripts/Engines/Factions/Core/Persistance.cs @@ -2,87 +2,89 @@ using System.Collections.Generic; namespace Server.Factions { - public class FactionPersistance : Item - { - public static FactionPersistance Instance { get; private set; } + public class FactionPersistance : Item + { + public FactionPersistance() : base(1) + { + Movable = false; - public override string DefaultName => "Faction Persistance - Internal"; + if (Instance == null || Instance.Deleted) + Instance = this; + else + base.Delete(); + } - public FactionPersistance() : base( 1 ) - { - Movable = false; + public FactionPersistance(Serial serial) : base(serial) + { + Instance = this; + } - if ( Instance == null || Instance.Deleted ) - Instance = this; - else - base.Delete(); - } + public static FactionPersistance Instance{ get; private set; } - private enum PersistedType - { - Terminator, - Faction, - Town - } + public override string DefaultName => "Faction Persistance - Internal"; - public FactionPersistance( Serial serial ) : base( serial ) - { - Instance = this; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version - writer.Write( (int) 0 ); // version + List factions = Faction.Factions; - List factions = Faction.Factions; + for (int i = 0; i < factions.Count; ++i) + { + writer.WriteEncodedInt((int)PersistedType.Faction); + factions[i].State.Serialize(writer); + } - for ( int i = 0; i < factions.Count; ++i ) - { - writer.WriteEncodedInt( (int) PersistedType.Faction ); - factions[i].State.Serialize( writer ); - } + List towns = Town.Towns; - List towns = Town.Towns; + for (int i = 0; i < towns.Count; ++i) + { + writer.WriteEncodedInt((int)PersistedType.Town); + towns[i].State.Serialize(writer); + } - for ( int i = 0; i < towns.Count; ++i ) - { - writer.WriteEncodedInt( (int) PersistedType.Town ); - towns[i].State.Serialize( writer ); - } + writer.WriteEncodedInt((int)PersistedType.Terminator); + } - writer.WriteEncodedInt( (int) PersistedType.Terminator ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + switch (version) + { + case 0: + { + PersistedType type; - switch ( version ) - { - case 0: - { - PersistedType type; + while ((type = (PersistedType)reader.ReadEncodedInt()) != PersistedType.Terminator) + switch (type) + { + case PersistedType.Faction: + new FactionState(reader); + break; + case PersistedType.Town: + new TownState(reader); + break; + } - while ( (type = (PersistedType)reader.ReadEncodedInt()) != PersistedType.Terminator ) - { - switch ( type ) - { - case PersistedType.Faction: new FactionState( reader ); break; - case PersistedType.Town: new TownState( reader ); break; - } - } + break; + } + } + } - break; - } - } - } + public override void Delete() + { + } - public override void Delete() - { - } - } + private enum PersistedType + { + Terminator, + Faction, + Town + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/PlayerState.cs b/Scripts/Engines/Factions/Core/PlayerState.cs index c408c0d3d..7f43fa40c 100644 --- a/Scripts/Engines/Factions/Core/PlayerState.cs +++ b/Scripts/Engines/Factions/Core/PlayerState.cs @@ -1,251 +1,310 @@ using System; -using Server.Mobiles; using System.Collections.Generic; +using Server.Mobiles; namespace Server.Factions { - public class PlayerState : IComparable - { - private int m_KillPoints; - private MerchantTitle m_MerchantTitle; - private RankDefinition m_Rank; + public class PlayerState : IComparable + { + private Town m_Finance; - private Town m_Sheriff; - private Town m_Finance; + private bool m_InvalidateRank = true; + private int m_KillPoints; + private MerchantTitle m_MerchantTitle; + private RankDefinition m_Rank; + private int m_RankIndex = -1; - public Mobile Mobile { get; } + private Town m_Sheriff; - public Faction Faction { get; } + public PlayerState(Mobile mob, Faction faction, List owner) + { + Mobile = mob; + Faction = faction; + Owner = owner; - public List Owner { get; } + Attach(); + Invalidate(); + } - public MerchantTitle MerchantTitle{ get => m_MerchantTitle; - set{ m_MerchantTitle = value; Invalidate(); } } - public Town Sheriff{ get => m_Sheriff; - set{ m_Sheriff = value; Invalidate(); } } - public Town Finance{ get => m_Finance; - set{ m_Finance = value; Invalidate(); } } - public List SilverGiven { get; private set; } + public PlayerState(GenericReader reader, Faction faction, List owner) + { + Faction = faction; + Owner = owner; - public int KillPoints { - get => m_KillPoints; - set { - if ( m_KillPoints != value ) { - if ( value > m_KillPoints ) { - if ( m_KillPoints <= 0 ) { - if ( value <= 0 ) { - m_KillPoints = value; - Invalidate(); - return; - } + int version = reader.ReadEncodedInt(); - Owner.Remove( this ); - Owner.Insert( Faction.ZeroRankOffset, this ); + switch (version) + { + case 1: + { + IsActive = reader.ReadBool(); + LastHonorTime = reader.ReadDateTime(); + goto case 0; + } + case 0: + { + Mobile = reader.ReadMobile(); - m_RankIndex = Faction.ZeroRankOffset; - Faction.ZeroRankOffset++; - } - while ( ( m_RankIndex - 1 ) >= 0 ) { - PlayerState p = Owner[m_RankIndex-1] as PlayerState; - if ( value > p.KillPoints ) { - Owner[m_RankIndex] = p; - Owner[m_RankIndex-1] = this; - RankIndex--; - p.RankIndex++; - } - else - break; - } - } - else { - if ( value <= 0 ) { - if ( m_KillPoints <= 0 ) { - m_KillPoints = value; - Invalidate(); - return; - } + m_KillPoints = reader.ReadEncodedInt(); + m_MerchantTitle = (MerchantTitle)reader.ReadEncodedInt(); - while ( ( m_RankIndex + 1 ) < Faction.ZeroRankOffset ) { - PlayerState p = Owner[m_RankIndex+1] as PlayerState; - Owner[m_RankIndex+1] = this; - Owner[m_RankIndex] = p; - RankIndex++; - p.RankIndex--; - } + Leaving = reader.ReadDateTime(); - m_RankIndex = -1; - Faction.ZeroRankOffset--; - } - else { - while ( ( m_RankIndex + 1 ) < Faction.ZeroRankOffset ) { - PlayerState p = Owner[m_RankIndex+1] as PlayerState; - if ( value < p.KillPoints ) { - Owner[m_RankIndex+1] = this; - Owner[m_RankIndex] = p; - RankIndex++; - p.RankIndex--; - } - else - break; - } - } - } + break; + } + } - m_KillPoints = value; - Invalidate(); - } - } - } + Attach(); + } - private bool m_InvalidateRank = true; - private int m_RankIndex = -1; + public Mobile Mobile{ get; } - public int RankIndex { get => m_RankIndex; - set { if ( m_RankIndex != value ) { m_RankIndex = value; m_InvalidateRank = true; } } } + public Faction Faction{ get; } - public RankDefinition Rank { - get { - if ( m_InvalidateRank ) { - RankDefinition[] ranks = Faction.Definition.Ranks; - int percent; + public List Owner{ get; } - if ( Owner.Count == 1 ) - percent = 1000; - else if ( m_RankIndex == -1 ) - percent = 0; - else - percent = ( ( Faction.ZeroRankOffset - m_RankIndex ) * 1000 ) / Faction.ZeroRankOffset; + public MerchantTitle MerchantTitle + { + get => m_MerchantTitle; + set + { + m_MerchantTitle = value; + Invalidate(); + } + } - for ( int i = 0; i < ranks.Length; i++ ) { - RankDefinition check = ranks[i]; + public Town Sheriff + { + get => m_Sheriff; + set + { + m_Sheriff = value; + Invalidate(); + } + } - if ( percent >= check.Required ) { - m_Rank = check; - m_InvalidateRank = false; - break; - } - } + public Town Finance + { + get => m_Finance; + set + { + m_Finance = value; + Invalidate(); + } + } - Invalidate(); - } + public List SilverGiven{ get; private set; } - return m_Rank; - } - } + public int KillPoints + { + get => m_KillPoints; + set + { + if (m_KillPoints != value) + { + if (value > m_KillPoints) + { + if (m_KillPoints <= 0) + { + if (value <= 0) + { + m_KillPoints = value; + Invalidate(); + return; + } - public DateTime LastHonorTime { get; set; } + Owner.Remove(this); + Owner.Insert(Faction.ZeroRankOffset, this); - public DateTime Leaving { get; set; } + m_RankIndex = Faction.ZeroRankOffset; + Faction.ZeroRankOffset++; + } - public bool IsLeaving => ( Leaving > DateTime.MinValue ); + while (m_RankIndex - 1 >= 0) + { + PlayerState p = Owner[m_RankIndex - 1]; + if (value > p.KillPoints) + { + Owner[m_RankIndex] = p; + Owner[m_RankIndex - 1] = this; + RankIndex--; + p.RankIndex++; + } + else + { + break; + } + } + } + else + { + if (value <= 0) + { + if (m_KillPoints <= 0) + { + m_KillPoints = value; + Invalidate(); + return; + } - public bool IsActive { get; set; } + while (m_RankIndex + 1 < Faction.ZeroRankOffset) + { + PlayerState p = Owner[m_RankIndex + 1]; + Owner[m_RankIndex + 1] = this; + Owner[m_RankIndex] = p; + RankIndex++; + p.RankIndex--; + } - public bool CanGiveSilverTo( Mobile mob ) - { - if ( SilverGiven == null ) - return true; + m_RankIndex = -1; + Faction.ZeroRankOffset--; + } + else + { + while (m_RankIndex + 1 < Faction.ZeroRankOffset) + { + PlayerState p = Owner[m_RankIndex + 1]; + if (value < p.KillPoints) + { + Owner[m_RankIndex + 1] = this; + Owner[m_RankIndex] = p; + RankIndex++; + p.RankIndex--; + } + else + { + break; + } + } + } + } - for ( int i = 0; i < SilverGiven.Count; ++i ) - { - SilverGivenEntry sge = SilverGiven[i]; + m_KillPoints = value; + Invalidate(); + } + } + } - if ( sge.IsExpired ) - SilverGiven.RemoveAt( i-- ); - else if ( sge.GivenTo == mob ) - return false; - } + public int RankIndex + { + get => m_RankIndex; + set + { + if (m_RankIndex != value) + { + m_RankIndex = value; + m_InvalidateRank = true; + } + } + } - return true; - } + public RankDefinition Rank + { + get + { + if (m_InvalidateRank) + { + RankDefinition[] ranks = Faction.Definition.Ranks; + int percent; - public void OnGivenSilverTo( Mobile mob ) - { - if ( SilverGiven == null ) - SilverGiven = new List(); + if (Owner.Count == 1) + percent = 1000; + else if (m_RankIndex == -1) + percent = 0; + else + percent = (Faction.ZeroRankOffset - m_RankIndex) * 1000 / Faction.ZeroRankOffset; - SilverGiven.Add( new SilverGivenEntry( mob ) ); - } + for (int i = 0; i < ranks.Length; i++) + { + RankDefinition check = ranks[i]; - public void Invalidate() - { - if ( Mobile is PlayerMobile pm ) - { - pm.InvalidateProperties(); - pm.InvalidateMyRunUO(); - } - } + if (percent >= check.Required) + { + m_Rank = check; + m_InvalidateRank = false; + break; + } + } - public void Attach() - { - if ( Mobile is PlayerMobile mobile ) - mobile.FactionPlayerState = this; - } + Invalidate(); + } - public PlayerState( Mobile mob, Faction faction, List owner ) - { - Mobile = mob; - Faction = faction; - Owner = owner; + return m_Rank; + } + } - Attach(); - Invalidate(); - } + public DateTime LastHonorTime{ get; set; } - public PlayerState( GenericReader reader, Faction faction, List owner ) - { - Faction = faction; - Owner = owner; + public DateTime Leaving{ get; set; } - int version = reader.ReadEncodedInt(); + public bool IsLeaving => Leaving > DateTime.MinValue; - switch ( version ) - { - case 1: - { - IsActive = reader.ReadBool(); - LastHonorTime = reader.ReadDateTime(); - goto case 0; - } - case 0: - { - Mobile = reader.ReadMobile(); + public bool IsActive{ get; set; } - m_KillPoints = reader.ReadEncodedInt(); - m_MerchantTitle = (MerchantTitle)reader.ReadEncodedInt(); + public int CompareTo(object obj) + { + return ((PlayerState)obj).m_KillPoints - m_KillPoints; + } - Leaving = reader.ReadDateTime(); + public bool CanGiveSilverTo(Mobile mob) + { + if (SilverGiven == null) + return true; - break; - } - } + for (int i = 0; i < SilverGiven.Count; ++i) + { + SilverGivenEntry sge = SilverGiven[i]; - Attach(); - } + if (sge.IsExpired) + SilverGiven.RemoveAt(i--); + else if (sge.GivenTo == mob) + return false; + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 1 ); // version + return true; + } - writer.Write( IsActive ); - writer.Write( LastHonorTime ); + public void OnGivenSilverTo(Mobile mob) + { + if (SilverGiven == null) + SilverGiven = new List(); - writer.Write( (Mobile) Mobile ); + SilverGiven.Add(new SilverGivenEntry(mob)); + } - writer.WriteEncodedInt( (int) m_KillPoints ); - writer.WriteEncodedInt( (int) m_MerchantTitle ); + public void Invalidate() + { + if (Mobile is PlayerMobile pm) + { + pm.InvalidateProperties(); + pm.InvalidateMyRunUO(); + } + } - writer.Write( (DateTime) Leaving ); - } + public void Attach() + { + if (Mobile is PlayerMobile mobile) + mobile.FactionPlayerState = this; + } - public static PlayerState Find( Mobile mob ) - { - return mob is PlayerMobile mobile ? mobile.FactionPlayerState : null; - } + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(1); // version - public int CompareTo( object obj ) - { - return ((PlayerState)obj).m_KillPoints - m_KillPoints; - } - } -} + writer.Write(IsActive); + writer.Write(LastHonorTime); + + writer.Write(Mobile); + + writer.WriteEncodedInt(m_KillPoints); + writer.WriteEncodedInt((int)m_MerchantTitle); + + writer.Write(Leaving); + } + + public static PlayerState Find(Mobile mob) + { + return mob is PlayerMobile mobile ? mobile.FactionPlayerState : null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Reflector.cs b/Scripts/Engines/Factions/Core/Reflector.cs index c92964ded..4ebba7c36 100644 --- a/Scripts/Engines/Factions/Core/Reflector.cs +++ b/Scripts/Engines/Factions/Core/Reflector.cs @@ -1,72 +1,78 @@ using System; -using System.Reflection; using System.Collections.Generic; +using System.Reflection; namespace Server.Factions { - public class Reflector - { - private static List m_Towns; + public class Reflector + { + private static List m_Towns; - public static List Towns - { - get - { - if ( m_Towns == null ) - ProcessTypes(); + private static List m_Factions; - return m_Towns; - } - } + public static List Towns + { + get + { + if (m_Towns == null) + ProcessTypes(); - private static List m_Factions; + return m_Towns; + } + } - public static List Factions - { - get - { - if ( m_Factions == null ) - ProcessTypes(); + public static List Factions + { + get + { + if (m_Factions == null) + ProcessTypes(); - return m_Factions; - } - } + return m_Factions; + } + } - private static object Construct( Type type ) - { - try{ return Activator.CreateInstance( type ); } - catch{ return null; } - } + private static object Construct(Type type) + { + try + { + return Activator.CreateInstance(type); + } + catch + { + return null; + } + } - private static void ProcessTypes() - { - m_Factions = new List(); - m_Towns = new List(); + private static void ProcessTypes() + { + m_Factions = new List(); + m_Towns = new List(); - Assembly[] asms = ScriptCompiler.Assemblies; + Assembly[] asms = ScriptCompiler.Assemblies; - for ( int i = 0; i < asms.Length; ++i ) - { - Assembly asm = asms[i]; - TypeCache tc = ScriptCompiler.GetTypeCache( asm ); - Type[] types = tc.Types; + for (int i = 0; i < asms.Length; ++i) + { + Assembly asm = asms[i]; + TypeCache tc = ScriptCompiler.GetTypeCache(asm); + Type[] types = tc.Types; - for ( int j = 0; j < types.Length; ++j ) - { - Type type = types[j]; + for (int j = 0; j < types.Length; ++j) + { + Type type = types[j]; - if ( type.IsSubclassOf( typeof( Faction ) ) ) - { - if ( Construct( type ) is Faction faction ) - Faction.Factions.Add( faction ); - } - else if ( type.IsSubclassOf( typeof( Town ) ) ) - { - if ( Construct( type ) is Town town ) - Town.Towns.Add( town ); - } - } - } - } - } -} + if (type.IsSubclassOf(typeof(Faction))) + { + if (Construct(type) is Faction faction) + Faction.Factions.Add(faction); + } + else if (type.IsSubclassOf(typeof(Town))) + { + if (Construct(type) is Town town) + Town.Towns.Add(town); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/SilverGivenEntry.cs b/Scripts/Engines/Factions/Core/SilverGivenEntry.cs index a1a361af8..1a3478848 100644 --- a/Scripts/Engines/Factions/Core/SilverGivenEntry.cs +++ b/Scripts/Engines/Factions/Core/SilverGivenEntry.cs @@ -2,20 +2,20 @@ using System; namespace Server.Factions { - public class SilverGivenEntry - { - public static readonly TimeSpan ExpirePeriod = TimeSpan.FromHours( 3.0 ); + public class SilverGivenEntry + { + public static readonly TimeSpan ExpirePeriod = TimeSpan.FromHours(3.0); - public Mobile GivenTo { get; } + public SilverGivenEntry(Mobile givenTo) + { + GivenTo = givenTo; + TimeOfGift = DateTime.UtcNow; + } - public DateTime TimeOfGift { get; } + public Mobile GivenTo{ get; } - public bool IsExpired => ( TimeOfGift + ExpirePeriod ) < DateTime.UtcNow; + public DateTime TimeOfGift{ get; } - public SilverGivenEntry( Mobile givenTo ) - { - GivenTo = givenTo; - TimeOfGift = DateTime.UtcNow; - } - } + public bool IsExpired => TimeOfGift + ExpirePeriod < DateTime.UtcNow; + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/StrongholdRegion.cs b/Scripts/Engines/Factions/Core/StrongholdRegion.cs index f7b0156ff..71cbc3ee3 100644 --- a/Scripts/Engines/Factions/Core/StrongholdRegion.cs +++ b/Scripts/Engines/Factions/Core/StrongholdRegion.cs @@ -3,36 +3,38 @@ using Server.Regions; namespace Server.Factions { - public class StrongholdRegion : BaseRegion - { - public Faction Faction { get; set; } + public class StrongholdRegion : BaseRegion + { + public StrongholdRegion(Faction faction) : base(faction.Definition.FriendlyName, Faction.Facet, DefaultPriority, + faction.Definition.Stronghold.Area) + { + Faction = faction; - public StrongholdRegion( Faction faction ) : base( faction.Definition.FriendlyName, Faction.Facet, DefaultPriority, faction.Definition.Stronghold.Area ) - { - Faction = faction; + Register(); + } - Register(); - } + public Faction Faction{ get; set; } - public override bool OnMoveInto( Mobile m, Direction d, Point3D newLocation, Point3D oldLocation ) - { - if ( !base.OnMoveInto( m, d, newLocation, oldLocation ) ) - return false; + public override bool OnMoveInto(Mobile m, Direction d, Point3D newLocation, Point3D oldLocation) + { + if (!base.OnMoveInto(m, d, newLocation, oldLocation)) + return false; - if ( m.AccessLevel >= AccessLevel.Counselor || Contains( oldLocation ) ) - return true; + if (m.AccessLevel >= AccessLevel.Counselor || Contains(oldLocation)) + return true; - if ( m is PlayerMobile pm && pm.DuelContext != null) { - pm.SendMessage( "You may not enter this area while participating in a duel or a tournament." ); - return false; - } + if (m is PlayerMobile pm && pm.DuelContext != null) + { + pm.SendMessage("You may not enter this area while participating in a duel or a tournament."); + return false; + } - return ( Faction.Find( m, true, true ) != null ); - } + return Faction.Find(m, true, true) != null; + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } - } -} + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/Town.cs b/Scripts/Engines/Factions/Core/Town.cs index 58d19fbb3..0c094f070 100644 --- a/Scripts/Engines/Factions/Core/Town.cs +++ b/Scripts/Engines/Factions/Core/Town.cs @@ -1,510 +1,514 @@ using System; using System.Collections; -using Server.Targeting; -using Server.Commands; using System.Collections.Generic; +using Server.Commands; +using Server.Targeting; namespace Server.Factions { - [CustomEnum( new[]{ "Britain", "Magincia", "Minoc", "Moonglow", "Skara Brae", "Trinsic", "Vesper", "Yew" } )] - public abstract class Town : IComparable - { - private TownState m_State; - - public TownDefinition Definition { get; set; } - - public TownState State - { - get => m_State; - set{ m_State = value; ConstructGuardLists(); } - } - - public int Silver - { - get => m_State.Silver; - set => m_State.Silver = value; - } - - public Faction Owner - { - get => m_State.Owner; - set => Capture( value ); - } - - public Mobile Sheriff - { - get => m_State.Sheriff; - set => m_State.Sheriff = value; - } - - public Mobile Finance - { - get => m_State.Finance; - set => m_State.Finance = value; - } - - public int Tax - { - get => m_State.Tax; - set => m_State.Tax = value; - } - - public DateTime LastTaxChange - { - get => m_State.LastTaxChange; - set => m_State.LastTaxChange = value; - } - - public static readonly TimeSpan TaxChangePeriod = TimeSpan.FromHours( 12.0 ); - public static readonly TimeSpan IncomePeriod = TimeSpan.FromDays( 1.0 ); - - public bool TaxChangeReady => ( m_State.LastTaxChange + TaxChangePeriod ) < DateTime.UtcNow; - - public static Town FromRegion( Region reg ) - { - if ( reg.Map != Faction.Facet ) - return null; - - List towns = Towns; - - for ( int i = 0; i < towns.Count; ++i ) - { - Town town = towns[i]; - - if ( reg.IsPartOf( town.Definition.Region ) ) - return town; - } - - return null; - } - - public int FinanceUpkeep - { - get - { - List vendorLists = VendorLists; - int upkeep = 0; - - for ( int i = 0; i < vendorLists.Count; ++i ) - upkeep += vendorLists[i].Vendors.Count * vendorLists[i].Definition.Upkeep; - - return upkeep; - } - } - - public int SheriffUpkeep - { - get - { - List guardLists = GuardLists; - int upkeep = 0; - - for ( int i = 0; i < guardLists.Count; ++i ) - upkeep += guardLists[i].Guards.Count * guardLists[i].Definition.Upkeep; - - return upkeep; - } - } - - public int DailyIncome => (10000 * (100 + m_State.Tax)) / 100; - - public int NetCashFlow => DailyIncome - FinanceUpkeep - SheriffUpkeep; - - public TownMonolith Monolith - { - get - { - List monoliths = BaseMonolith.Monoliths; - - foreach ( BaseMonolith monolith in monoliths ) - { - if ( monolith is TownMonolith townMonolith && townMonolith.Town == this ) - return townMonolith; - } - - return null; - } - } - - public DateTime LastIncome - { - get => m_State.LastIncome; - set => m_State.LastIncome = value; - } - - public void BeginOrderFiring( Mobile from ) - { - bool isFinance = IsFinance( from ); - bool isSheriff = IsSheriff( from ); - string type = null; - - // NOTE: Messages not OSI-accurate, intentional - if ( isFinance && isSheriff ) // GM only - type = "vendor or guard"; - else if ( isFinance ) - type = "vendor"; - else if ( isSheriff ) - type = "guard"; - - from.SendMessage( "Target the {0} you wish to dismiss.", type ); - from.BeginTarget( 12, false, TargetFlags.None, EndOrderFiring ); - } + [CustomEnum(new[] { "Britain", "Magincia", "Minoc", "Moonglow", "Skara Brae", "Trinsic", "Vesper", "Yew" })] + public abstract class Town : IComparable + { + public const int SilverCaptureBonus = 10000; + + public static readonly TimeSpan TaxChangePeriod = TimeSpan.FromHours(12.0); + public static readonly TimeSpan IncomePeriod = TimeSpan.FromDays(1.0); + + private Timer m_IncomeTimer; + private TownState m_State; + + public Town() + { + m_State = new TownState(this); + ConstructVendorLists(); + ConstructGuardLists(); + StartIncomeTimer(); + } + + public TownDefinition Definition{ get; set; } + + public TownState State + { + get => m_State; + set + { + m_State = value; + ConstructGuardLists(); + } + } + + public int Silver + { + get => m_State.Silver; + set => m_State.Silver = value; + } + + public Faction Owner + { + get => m_State.Owner; + set => Capture(value); + } + + public Mobile Sheriff + { + get => m_State.Sheriff; + set => m_State.Sheriff = value; + } + + public Mobile Finance + { + get => m_State.Finance; + set => m_State.Finance = value; + } + + public int Tax + { + get => m_State.Tax; + set => m_State.Tax = value; + } + + public DateTime LastTaxChange + { + get => m_State.LastTaxChange; + set => m_State.LastTaxChange = value; + } + + public bool TaxChangeReady => m_State.LastTaxChange + TaxChangePeriod < DateTime.UtcNow; + + public int FinanceUpkeep + { + get + { + List vendorLists = VendorLists; + int upkeep = 0; + + for (int i = 0; i < vendorLists.Count; ++i) + upkeep += vendorLists[i].Vendors.Count * vendorLists[i].Definition.Upkeep; + + return upkeep; + } + } + + public int SheriffUpkeep + { + get + { + List guardLists = GuardLists; + int upkeep = 0; + + for (int i = 0; i < guardLists.Count; ++i) + upkeep += guardLists[i].Guards.Count * guardLists[i].Definition.Upkeep; + + return upkeep; + } + } + + public int DailyIncome => 10000 * (100 + m_State.Tax) / 100; + + public int NetCashFlow => DailyIncome - FinanceUpkeep - SheriffUpkeep; + + public TownMonolith Monolith + { + get + { + List monoliths = BaseMonolith.Monoliths; + + foreach (BaseMonolith monolith in monoliths) + if (monolith is TownMonolith townMonolith && townMonolith.Town == this) + return townMonolith; + + return null; + } + } + + public DateTime LastIncome + { + get => m_State.LastIncome; + set => m_State.LastIncome = value; + } + + public List VendorLists{ get; set; } + + public List GuardLists{ get; set; } + + public static List Towns => Reflector.Towns; + + public int CompareTo(object obj) + { + return Definition.Sort - ((Town)obj).Definition.Sort; + } + + public static Town FromRegion(Region reg) + { + if (reg.Map != Faction.Facet) + return null; + + List towns = Towns; + + for (int i = 0; i < towns.Count; ++i) + { + Town town = towns[i]; + + if (reg.IsPartOf(town.Definition.Region)) + return town; + } + + return null; + } + + public void BeginOrderFiring(Mobile from) + { + bool isFinance = IsFinance(from); + bool isSheriff = IsSheriff(from); + string type = null; + + // NOTE: Messages not OSI-accurate, intentional + if (isFinance && isSheriff) // GM only + type = "vendor or guard"; + else if (isFinance) + type = "vendor"; + else if (isSheriff) + type = "guard"; - public void EndOrderFiring( Mobile from, object obj ) - { - bool isFinance = IsFinance( from ); - bool isSheriff = IsSheriff( from ); - string type = null; + from.SendMessage("Target the {0} you wish to dismiss.", type); + from.BeginTarget(12, false, TargetFlags.None, EndOrderFiring); + } - if ( isFinance && isSheriff ) // GM only - type = "vendor or guard"; - else if ( isFinance ) - type = "vendor"; - else if ( isSheriff ) - type = "guard"; + public void EndOrderFiring(Mobile from, object obj) + { + bool isFinance = IsFinance(from); + bool isSheriff = IsSheriff(from); + string type = null; - if ( obj is BaseFactionVendor vendor && vendor.Town == this && isFinance ) - vendor.Delete(); - else if ( obj is BaseFactionGuard guard && guard.Town == this && isSheriff ) - guard.Delete(); - else - { - from.SendMessage( "That is not a {0}!", type ); - } - } + if (isFinance && isSheriff) // GM only + type = "vendor or guard"; + else if (isFinance) + type = "vendor"; + else if (isSheriff) + type = "guard"; - private Timer m_IncomeTimer; + if (obj is BaseFactionVendor vendor && vendor.Town == this && isFinance) + vendor.Delete(); + else if (obj is BaseFactionGuard guard && guard.Town == this && isSheriff) + guard.Delete(); + else + from.SendMessage("That is not a {0}!", type); + } - public void StartIncomeTimer() - { - m_IncomeTimer?.Stop(); + public void StartIncomeTimer() + { + m_IncomeTimer?.Stop(); - m_IncomeTimer = Timer.DelayCall( TimeSpan.FromMinutes( 1.0 ), TimeSpan.FromMinutes( 1.0 ), CheckIncome ); - } + m_IncomeTimer = Timer.DelayCall(TimeSpan.FromMinutes(1.0), TimeSpan.FromMinutes(1.0), CheckIncome); + } - public void StopIncomeTimer() - { - m_IncomeTimer?.Stop(); + public void StopIncomeTimer() + { + m_IncomeTimer?.Stop(); - m_IncomeTimer = null; - } + m_IncomeTimer = null; + } - public void CheckIncome() - { - if ( (LastIncome + IncomePeriod) > DateTime.UtcNow || Owner == null ) - return; + public void CheckIncome() + { + if (LastIncome + IncomePeriod > DateTime.UtcNow || Owner == null) + return; - ProcessIncome(); - } + ProcessIncome(); + } - public void ProcessIncome() - { - LastIncome = DateTime.UtcNow; + public void ProcessIncome() + { + LastIncome = DateTime.UtcNow; - int flow = NetCashFlow; + int flow = NetCashFlow; - if ( (Silver + flow) < 0 ) - { - ArrayList toDelete = BuildFinanceList(); + if (Silver + flow < 0) + { + ArrayList toDelete = BuildFinanceList(); - while ( (Silver + flow) < 0 && toDelete.Count > 0 ) - { - int index = Utility.Random( toDelete.Count ); - Mobile mob = (Mobile)toDelete[index]; + while (Silver + flow < 0 && toDelete.Count > 0) + { + int index = Utility.Random(toDelete.Count); + Mobile mob = (Mobile)toDelete[index]; - mob.Delete(); + mob.Delete(); - toDelete.RemoveAt( index ); - flow = NetCashFlow; - } - } + toDelete.RemoveAt(index); + flow = NetCashFlow; + } + } - Silver += flow; - } + Silver += flow; + } - public ArrayList BuildFinanceList() - { - ArrayList list = new ArrayList(); + public ArrayList BuildFinanceList() + { + ArrayList list = new ArrayList(); - List vendorLists = VendorLists; + List vendorLists = VendorLists; - for ( int i = 0; i < vendorLists.Count; ++i ) - list.AddRange( vendorLists[i].Vendors ); + for (int i = 0; i < vendorLists.Count; ++i) + list.AddRange(vendorLists[i].Vendors); - List guardLists = GuardLists; + List guardLists = GuardLists; - for ( int i = 0; i < guardLists.Count; ++i ) - list.AddRange( guardLists[i].Guards ); + for (int i = 0; i < guardLists.Count; ++i) + list.AddRange(guardLists[i].Guards); - return list; - } + return list; + } - public List VendorLists { get; set; } + public void ConstructGuardLists() + { + GuardDefinition[] defs = Owner == null ? new GuardDefinition[0] : Owner.Definition.Guards; - public List GuardLists { get; set; } + GuardLists = new List(); - public void ConstructGuardLists() - { - GuardDefinition[] defs = ( Owner == null ? new GuardDefinition[0] : Owner.Definition.Guards ); + for (int i = 0; i < defs.Length; ++i) + GuardLists.Add(new GuardList(defs[i])); + } - GuardLists = new List(); + public GuardList FindGuardList(Type type) + { + List guardLists = GuardLists; - for ( int i = 0; i < defs.Length; ++i ) - GuardLists.Add( new GuardList( defs[i] ) ); - } + for (int i = 0; i < guardLists.Count; ++i) + { + GuardList guardList = guardLists[i]; - public GuardList FindGuardList( Type type ) - { - List guardLists = GuardLists; + if (guardList.Definition.Type == type) + return guardList; + } - for ( int i = 0; i < guardLists.Count; ++i ) - { - GuardList guardList = guardLists[i]; + return null; + } - if ( guardList.Definition.Type == type ) - return guardList; - } + public void ConstructVendorLists() + { + VendorDefinition[] defs = VendorDefinition.Definitions; - return null; - } + VendorLists = new List(); - public void ConstructVendorLists() - { - VendorDefinition[] defs = VendorDefinition.Definitions; + for (int i = 0; i < defs.Length; ++i) + VendorLists.Add(new VendorList(defs[i])); + } - VendorLists = new List(); + public VendorList FindVendorList(Type type) + { + List vendorLists = VendorLists; - for ( int i = 0; i < defs.Length; ++i ) - VendorLists.Add( new VendorList( defs[i] ) ); - } + for (int i = 0; i < vendorLists.Count; ++i) + { + VendorList vendorList = vendorLists[i]; - public VendorList FindVendorList( Type type ) - { - List vendorLists = VendorLists; + if (vendorList.Definition.Type == type) + return vendorList; + } - for ( int i = 0; i < vendorLists.Count; ++i ) - { - VendorList vendorList = vendorLists[i]; + return null; + } - if ( vendorList.Definition.Type == type ) - return vendorList; - } + public bool RegisterGuard(BaseFactionGuard guard) + { + if (guard == null) + return false; - return null; - } + GuardList guardList = FindGuardList(guard.GetType()); - public bool RegisterGuard( BaseFactionGuard guard ) - { - if ( guard == null ) - return false; + if (guardList == null) + return false; - GuardList guardList = FindGuardList( guard.GetType() ); + guardList.Guards.Add(guard); + return true; + } - if ( guardList == null ) - return false; + public bool UnregisterGuard(BaseFactionGuard guard) + { + if (guard == null) + return false; - guardList.Guards.Add( guard ); - return true; - } + GuardList guardList = FindGuardList(guard.GetType()); - public bool UnregisterGuard( BaseFactionGuard guard ) - { - if ( guard == null ) - return false; + if (guardList == null) + return false; - GuardList guardList = FindGuardList( guard.GetType() ); + if (!guardList.Guards.Contains(guard)) + return false; - if ( guardList == null ) - return false; + guardList.Guards.Remove(guard); + return true; + } - if ( !guardList.Guards.Contains( guard ) ) - return false; + public bool RegisterVendor(BaseFactionVendor vendor) + { + if (vendor == null) + return false; - guardList.Guards.Remove( guard ); - return true; - } + VendorList vendorList = FindVendorList(vendor.GetType()); - public bool RegisterVendor( BaseFactionVendor vendor ) - { - if ( vendor == null ) - return false; + if (vendorList == null) + return false; - VendorList vendorList = FindVendorList( vendor.GetType() ); + vendorList.Vendors.Add(vendor); + return true; + } - if ( vendorList == null ) - return false; + public bool UnregisterVendor(BaseFactionVendor vendor) + { + if (vendor == null) + return false; - vendorList.Vendors.Add( vendor ); - return true; - } + VendorList vendorList = FindVendorList(vendor.GetType()); - public bool UnregisterVendor( BaseFactionVendor vendor ) - { - if ( vendor == null ) - return false; + if (vendorList == null) + return false; - VendorList vendorList = FindVendorList( vendor.GetType() ); + if (!vendorList.Vendors.Contains(vendor)) + return false; - if ( vendorList == null ) - return false; + vendorList.Vendors.Remove(vendor); + return true; + } - if ( !vendorList.Vendors.Contains( vendor ) ) - return false; + public static void Initialize() + { + List towns = Towns; - vendorList.Vendors.Remove( vendor ); - return true; - } + for (int i = 0; i < towns.Count; ++i) + { + towns[i].Sheriff = towns[i].Sheriff; + towns[i].Finance = towns[i].Finance; + } - public static void Initialize() - { - List towns = Towns; + CommandSystem.Register("GrantTownSilver", AccessLevel.Administrator, GrantTownSilver_OnCommand); + } - for ( int i = 0; i < towns.Count; ++i ) - { - towns[i].Sheriff = towns[i].Sheriff; - towns[i].Finance = towns[i].Finance; - } + public bool IsSheriff(Mobile mob) + { + if (mob == null || mob.Deleted) + return false; - CommandSystem.Register( "GrantTownSilver", AccessLevel.Administrator, GrantTownSilver_OnCommand ); - } + return mob.AccessLevel >= AccessLevel.GameMaster || mob == Sheriff; + } - public Town() - { - m_State = new TownState( this ); - ConstructVendorLists(); - ConstructGuardLists(); - StartIncomeTimer(); - } + public bool IsFinance(Mobile mob) + { + if (mob == null || mob.Deleted) + return false; - public bool IsSheriff( Mobile mob ) - { - if ( mob == null || mob.Deleted ) - return false; + return mob.AccessLevel >= AccessLevel.GameMaster || mob == Finance; + } - return ( mob.AccessLevel >= AccessLevel.GameMaster || mob == Sheriff ); - } + public void Capture(Faction f) + { + if (m_State.Owner == f) + return; - public bool IsFinance( Mobile mob ) - { - if ( mob == null || mob.Deleted ) - return false; - - return ( mob.AccessLevel >= AccessLevel.GameMaster || mob == Finance ); - } - - public static List Towns => Reflector.Towns; - - public const int SilverCaptureBonus = 10000; - - public void Capture( Faction f ) - { - if ( m_State.Owner == f ) - return; - - if ( m_State.Owner == null ) // going from unowned to owned - { - LastIncome = DateTime.UtcNow; - f.Silver += SilverCaptureBonus; - } - else if ( f == null ) // going from owned to unowned - { - LastIncome = DateTime.MinValue; - } - else // otherwise changing hands, income timer doesn't change - { - f.Silver += SilverCaptureBonus; - } - - m_State.Owner = f; - - Sheriff = null; - Finance = null; - - TownMonolith monolith = Monolith; - - if ( monolith != null ) - monolith.Faction = f; - - List vendorLists = VendorLists; - - for ( int i = 0; i < vendorLists.Count; ++i ) - { - VendorList vendorList = vendorLists[i]; - List vendors = vendorList.Vendors; - - for ( int j = vendors.Count - 1; j >= 0; --j ) - vendors[j].Delete(); - } - - List guardLists = GuardLists; - - for ( int i = 0; i < guardLists.Count; ++i ) - { - GuardList guardList = guardLists[i]; - List guards = guardList.Guards; - - for ( int j = guards.Count - 1; j >= 0; --j ) - guards[j].Delete(); - } - - ConstructGuardLists(); - } - - public int CompareTo( object obj ) - { - return Definition.Sort - ((Town)obj).Definition.Sort; - } - - public override string ToString() - { - return Definition.FriendlyName; - } - - public static void WriteReference( GenericWriter writer, Town town ) - { - int idx = Towns.IndexOf( town ); - - writer.WriteEncodedInt( (int) (idx + 1) ); - } - - public static Town ReadReference( GenericReader reader ) - { - int idx = reader.ReadEncodedInt() - 1; - - if ( idx >= 0 && idx < Towns.Count ) - return Towns[idx]; - - return null; - } - - public static Town Parse( string name ) - { - List towns = Towns; - - for ( int i = 0; i < towns.Count; ++i ) - { - Town town = towns[i]; - - if ( Insensitive.Equals( town.Definition.FriendlyName, name ) ) - return town; - } - - return null; - } - - public static void GrantTownSilver_OnCommand( CommandEventArgs e ) - { - Town town = FromRegion( e.Mobile.Region ); - - if ( town == null ) - e.Mobile.SendMessage( "You are not in a faction town." ); - else if ( e.Length == 0 ) - e.Mobile.SendMessage( "Format: GrantTownSilver " ); - else - { - town.Silver += e.GetInt32( 0 ); - e.Mobile.SendMessage( "You have granted {0:N0} silver to the town. It now has {1:N0} silver.", e.GetInt32( 0 ), town.Silver ); - } - } - } -} + if (m_State.Owner == null) // going from unowned to owned + { + LastIncome = DateTime.UtcNow; + f.Silver += SilverCaptureBonus; + } + else if (f == null) // going from owned to unowned + { + LastIncome = DateTime.MinValue; + } + else // otherwise changing hands, income timer doesn't change + { + f.Silver += SilverCaptureBonus; + } + + m_State.Owner = f; + + Sheriff = null; + Finance = null; + + TownMonolith monolith = Monolith; + + if (monolith != null) + monolith.Faction = f; + + List vendorLists = VendorLists; + + for (int i = 0; i < vendorLists.Count; ++i) + { + VendorList vendorList = vendorLists[i]; + List vendors = vendorList.Vendors; + + for (int j = vendors.Count - 1; j >= 0; --j) + vendors[j].Delete(); + } + + List guardLists = GuardLists; + + for (int i = 0; i < guardLists.Count; ++i) + { + GuardList guardList = guardLists[i]; + List guards = guardList.Guards; + + for (int j = guards.Count - 1; j >= 0; --j) + guards[j].Delete(); + } + + ConstructGuardLists(); + } + + public override string ToString() + { + return Definition.FriendlyName; + } + + public static void WriteReference(GenericWriter writer, Town town) + { + int idx = Towns.IndexOf(town); + + writer.WriteEncodedInt(idx + 1); + } + + public static Town ReadReference(GenericReader reader) + { + int idx = reader.ReadEncodedInt() - 1; + + if (idx >= 0 && idx < Towns.Count) + return Towns[idx]; + + return null; + } + + public static Town Parse(string name) + { + List towns = Towns; + + for (int i = 0; i < towns.Count; ++i) + { + Town town = towns[i]; + + if (Insensitive.Equals(town.Definition.FriendlyName, name)) + return town; + } + + return null; + } + + public static void GrantTownSilver_OnCommand(CommandEventArgs e) + { + Town town = FromRegion(e.Mobile.Region); + + if (town == null) + { + e.Mobile.SendMessage("You are not in a faction town."); + } + else if (e.Length == 0) + { + e.Mobile.SendMessage("Format: GrantTownSilver "); + } + else + { + town.Silver += e.GetInt32(0); + e.Mobile.SendMessage("You have granted {0:N0} silver to the town. It now has {1:N0} silver.", e.GetInt32(0), + town.Silver); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/TownState.cs b/Scripts/Engines/Factions/Core/TownState.cs index 12606d4ef..fcdf7a15e 100644 --- a/Scripts/Engines/Factions/Core/TownState.cs +++ b/Scripts/Engines/Factions/Core/TownState.cs @@ -2,134 +2,134 @@ using System; namespace Server.Factions { - public class TownState - { - private Mobile m_Sheriff; - private Mobile m_Finance; + public class TownState + { + private Mobile m_Finance; + private Mobile m_Sheriff; - public Town Town { get; set; } + public TownState(Town town) + { + Town = town; + } - public Faction Owner { get; set; } + public TownState(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public Mobile Sheriff - { - get => m_Sheriff; - set - { - if ( m_Sheriff != null ) - { - PlayerState pl = PlayerState.Find( m_Sheriff ); + switch (version) + { + case 3: + { + LastIncome = reader.ReadDateTime(); - if ( pl != null ) - pl.Sheriff = null; - } + goto case 2; + } + case 2: + { + Tax = reader.ReadEncodedInt(); + LastTaxChange = reader.ReadDateTime(); - m_Sheriff = value; + goto case 1; + } + case 1: + { + Silver = reader.ReadEncodedInt(); - if ( m_Sheriff != null ) - { - PlayerState pl = PlayerState.Find( m_Sheriff ); + goto case 0; + } + case 0: + { + Town = Town.ReadReference(reader); + Owner = Faction.ReadReference(reader); - if ( pl != null ) - pl.Sheriff = Town; - } - } - } + m_Sheriff = reader.ReadMobile(); + m_Finance = reader.ReadMobile(); - public Mobile Finance - { - get => m_Finance; - set - { - if ( m_Finance != null ) - { - PlayerState pl = PlayerState.Find( m_Finance ); + Town.State = this; - if ( pl != null ) - pl.Finance = null; - } + break; + } + } + } - m_Finance = value; + public Town Town{ get; set; } - if ( m_Finance != null ) - { - PlayerState pl = PlayerState.Find( m_Finance ); + public Faction Owner{ get; set; } - if ( pl != null ) - pl.Finance = Town; - } - } - } + public Mobile Sheriff + { + get => m_Sheriff; + set + { + if (m_Sheriff != null) + { + PlayerState pl = PlayerState.Find(m_Sheriff); - public int Silver { get; set; } + if (pl != null) + pl.Sheriff = null; + } - public int Tax { get; set; } + m_Sheriff = value; - public DateTime LastTaxChange { get; set; } + if (m_Sheriff != null) + { + PlayerState pl = PlayerState.Find(m_Sheriff); - public DateTime LastIncome { get; set; } + if (pl != null) + pl.Sheriff = Town; + } + } + } - public TownState( Town town ) - { - Town = town; - } + public Mobile Finance + { + get => m_Finance; + set + { + if (m_Finance != null) + { + PlayerState pl = PlayerState.Find(m_Finance); - public TownState( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + if (pl != null) + pl.Finance = null; + } - switch ( version ) - { - case 3: - { - LastIncome = reader.ReadDateTime(); + m_Finance = value; - goto case 2; - } - case 2: - { - Tax = reader.ReadEncodedInt(); - LastTaxChange = reader.ReadDateTime(); + if (m_Finance != null) + { + PlayerState pl = PlayerState.Find(m_Finance); - goto case 1; - } - case 1: - { - Silver = reader.ReadEncodedInt(); + if (pl != null) + pl.Finance = Town; + } + } + } - goto case 0; - } - case 0: - { - Town = Town.ReadReference( reader ); - Owner = Faction.ReadReference( reader ); + public int Silver{ get; set; } - m_Sheriff = reader.ReadMobile(); - m_Finance = reader.ReadMobile(); + public int Tax{ get; set; } - Town.State = this; + public DateTime LastTaxChange{ get; set; } - break; - } - } - } + public DateTime LastIncome{ get; set; } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 3 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(3); // version - writer.Write( (DateTime) LastIncome ); + writer.Write(LastIncome); - writer.WriteEncodedInt( (int) Tax ); - writer.Write( (DateTime) LastTaxChange ); + writer.WriteEncodedInt(Tax); + writer.Write(LastTaxChange); - writer.WriteEncodedInt( (int) Silver ); + writer.WriteEncodedInt(Silver); - Town.WriteReference( writer, Town ); - Faction.WriteReference( writer, Owner ); + Town.WriteReference(writer, Town); + Faction.WriteReference(writer, Owner); - writer.Write( (Mobile) m_Sheriff ); - writer.Write( (Mobile) m_Finance ); - } - } + writer.Write(m_Sheriff); + writer.Write(m_Finance); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Core/VendorList.cs b/Scripts/Engines/Factions/Core/VendorList.cs index aa9c0bba5..0150c682b 100644 --- a/Scripts/Engines/Factions/Core/VendorList.cs +++ b/Scripts/Engines/Factions/Core/VendorList.cs @@ -3,22 +3,28 @@ using System.Collections.Generic; namespace Server.Factions { - public class VendorList - { - public VendorDefinition Definition { get; } + public class VendorList + { + public VendorList(VendorDefinition definition) + { + Definition = definition; + Vendors = new List(); + } - public List Vendors { get; } + public VendorDefinition Definition{ get; } - public BaseFactionVendor Construct( Town town, Faction faction ) - { - try{ return Activator.CreateInstance( Definition.Type, new object[]{ town, faction } ) as BaseFactionVendor; } - catch{ return null; } - } + public List Vendors{ get; } - public VendorList( VendorDefinition definition ) - { - Definition = definition; - Vendors = new List(); - } - } -} + public BaseFactionVendor Construct(Town town, Faction faction) + { + try + { + return Activator.CreateInstance(Definition.Type, town, faction) as BaseFactionVendor; + } + catch + { + return null; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/FactionDefinition.cs b/Scripts/Engines/Factions/Definitions/FactionDefinition.cs index da6f6ee06..309bacfe1 100644 --- a/Scripts/Engines/Factions/Definitions/FactionDefinition.cs +++ b/Scripts/Engines/Factions/Definitions/FactionDefinition.cs @@ -1,84 +1,89 @@ namespace Server.Factions { - public class FactionDefinition - { - public int Sort { get; } + public class FactionDefinition + { + public FactionDefinition(int sort, int huePrimary, int hueSecondary, int hueJoin, int hueBroadcast, int warHorseBody, + int warHorseItem, string friendlyName, string keyword, string abbreviation, TextDefinition name, + TextDefinition propName, TextDefinition header, TextDefinition about, TextDefinition cityControl, + TextDefinition sigilControl, TextDefinition signupName, TextDefinition factionStoneName, + TextDefinition ownerLabel, TextDefinition guardIgnore, TextDefinition guardWarn, TextDefinition guardAttack, + StrongholdDefinition stronghold, RankDefinition[] ranks, GuardDefinition[] guards) + { + Sort = sort; + HuePrimary = huePrimary; + HueSecondary = hueSecondary; + HueJoin = hueJoin; + HueBroadcast = hueBroadcast; + WarHorseBody = warHorseBody; + WarHorseItem = warHorseItem; + FriendlyName = friendlyName; + Keyword = keyword; + Abbreviation = abbreviation; + Name = name; + PropName = propName; + Header = header; + About = about; + CityControl = cityControl; + SigilControl = sigilControl; + SignupName = signupName; + FactionStoneName = factionStoneName; + OwnerLabel = ownerLabel; + GuardIgnore = guardIgnore; + GuardWarn = guardWarn; + GuardAttack = guardAttack; + Stronghold = stronghold; + Ranks = ranks; + Guards = guards; + } - public int HuePrimary { get; } + public int Sort{ get; } - public int HueSecondary { get; } + public int HuePrimary{ get; } - public int HueJoin { get; } + public int HueSecondary{ get; } - public int HueBroadcast { get; } + public int HueJoin{ get; } - public int WarHorseBody { get; } + public int HueBroadcast{ get; } - public int WarHorseItem { get; } + public int WarHorseBody{ get; } - public string FriendlyName { get; } + public int WarHorseItem{ get; } - public string Keyword { get; } + public string FriendlyName{ get; } - public string Abbreviation { get; } + public string Keyword{ get; } - public TextDefinition Name { get; } + public string Abbreviation{ get; } - public TextDefinition PropName { get; } + public TextDefinition Name{ get; } - public TextDefinition Header { get; } + public TextDefinition PropName{ get; } - public TextDefinition About { get; } + public TextDefinition Header{ get; } - public TextDefinition CityControl { get; } + public TextDefinition About{ get; } - public TextDefinition SigilControl { get; } + public TextDefinition CityControl{ get; } - public TextDefinition SignupName { get; } + public TextDefinition SigilControl{ get; } - public TextDefinition FactionStoneName { get; } + public TextDefinition SignupName{ get; } - public TextDefinition OwnerLabel { get; } + public TextDefinition FactionStoneName{ get; } - public TextDefinition GuardIgnore { get; } + public TextDefinition OwnerLabel{ get; } - public TextDefinition GuardWarn { get; } + public TextDefinition GuardIgnore{ get; } - public TextDefinition GuardAttack { get; } + public TextDefinition GuardWarn{ get; } - public StrongholdDefinition Stronghold { get; } + public TextDefinition GuardAttack{ get; } - public RankDefinition[] Ranks { get; } + public StrongholdDefinition Stronghold{ get; } - public GuardDefinition[] Guards { get; } + public RankDefinition[] Ranks{ get; } - public FactionDefinition( int sort, int huePrimary, int hueSecondary, int hueJoin, int hueBroadcast, int warHorseBody, int warHorseItem, string friendlyName, string keyword, string abbreviation, TextDefinition name, TextDefinition propName, TextDefinition header, TextDefinition about, TextDefinition cityControl, TextDefinition sigilControl, TextDefinition signupName, TextDefinition factionStoneName, TextDefinition ownerLabel, TextDefinition guardIgnore, TextDefinition guardWarn, TextDefinition guardAttack, StrongholdDefinition stronghold, RankDefinition[] ranks, GuardDefinition[] guards ) - { - Sort = sort; - HuePrimary = huePrimary; - HueSecondary = hueSecondary; - HueJoin = hueJoin; - HueBroadcast = hueBroadcast; - WarHorseBody = warHorseBody; - WarHorseItem = warHorseItem; - FriendlyName = friendlyName; - Keyword = keyword; - Abbreviation = abbreviation; - Name = name; - PropName = propName; - Header = header; - About = about; - CityControl = cityControl; - SigilControl = sigilControl; - SignupName = signupName; - FactionStoneName = factionStoneName; - OwnerLabel = ownerLabel; - GuardIgnore = guardIgnore; - GuardWarn = guardWarn; - GuardAttack = guardAttack; - Stronghold = stronghold; - Ranks = ranks; - Guards = guards; - } - } -} + public GuardDefinition[] Guards{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/FactionItemDefinition.cs b/Scripts/Engines/Factions/Definitions/FactionItemDefinition.cs index dca8e633c..8b48fb621 100644 --- a/Scripts/Engines/Factions/Definitions/FactionItemDefinition.cs +++ b/Scripts/Engines/Factions/Definitions/FactionItemDefinition.cs @@ -4,45 +4,45 @@ using Server.Mobiles; namespace Server.Factions { - public class FactionItemDefinition - { - public int SilverCost { get; } + public class FactionItemDefinition + { + private static FactionItemDefinition m_MetalArmor = new FactionItemDefinition(1000, typeof(Blacksmith)); + private static FactionItemDefinition m_Weapon = new FactionItemDefinition(1000, typeof(Blacksmith)); + private static FactionItemDefinition m_RangedWeapon = new FactionItemDefinition(1000, typeof(Bowyer)); + private static FactionItemDefinition m_LeatherArmor = new FactionItemDefinition(750, typeof(Tailor)); + private static FactionItemDefinition m_Clothing = new FactionItemDefinition(200, typeof(Tailor)); + private static FactionItemDefinition m_Scroll = new FactionItemDefinition(500, typeof(Mage)); - public Type VendorType { get; } + public FactionItemDefinition(int silverCost, Type vendorType) + { + SilverCost = silverCost; + VendorType = vendorType; + } - public FactionItemDefinition( int silverCost, Type vendorType ) - { - SilverCost = silverCost; - VendorType = vendorType; - } + public int SilverCost{ get; } - private static FactionItemDefinition m_MetalArmor = new FactionItemDefinition( 1000, typeof( Blacksmith ) ); - private static FactionItemDefinition m_Weapon = new FactionItemDefinition( 1000, typeof( Blacksmith ) ); - private static FactionItemDefinition m_RangedWeapon = new FactionItemDefinition( 1000, typeof( Bowyer ) ); - private static FactionItemDefinition m_LeatherArmor = new FactionItemDefinition( 750, typeof( Tailor ) ); - private static FactionItemDefinition m_Clothing = new FactionItemDefinition( 200, typeof( Tailor ) ); - private static FactionItemDefinition m_Scroll = new FactionItemDefinition( 500, typeof( Mage ) ); + public Type VendorType{ get; } - public static FactionItemDefinition Identify( Item item ) - { - if ( item is BaseArmor armor ) - { - if ( CraftResources.GetType( armor.Resource ) == CraftResourceType.Leather ) - return m_LeatherArmor; + public static FactionItemDefinition Identify(Item item) + { + if (item is BaseArmor armor) + { + if (CraftResources.GetType(armor.Resource) == CraftResourceType.Leather) + return m_LeatherArmor; - return m_MetalArmor; - } + return m_MetalArmor; + } - if ( item is BaseRanged ) - return m_RangedWeapon; - if ( item is BaseWeapon ) - return m_Weapon; - if ( item is BaseClothing ) - return m_Clothing; - if ( item is SpellScroll ) - return m_Scroll; + if (item is BaseRanged) + return m_RangedWeapon; + if (item is BaseWeapon) + return m_Weapon; + if (item is BaseClothing) + return m_Clothing; + if (item is SpellScroll) + return m_Scroll; - return null; - } - } -} + return null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/GuardDefinition.cs b/Scripts/Engines/Factions/Definitions/GuardDefinition.cs index 86fe1f9ff..a2471710d 100644 --- a/Scripts/Engines/Factions/Definitions/GuardDefinition.cs +++ b/Scripts/Engines/Factions/Definitions/GuardDefinition.cs @@ -2,33 +2,34 @@ using System; namespace Server.Factions { - public class GuardDefinition - { - public Type Type { get; } + public class GuardDefinition + { + public GuardDefinition(Type type, int itemID, int price, int upkeep, int maximum, TextDefinition header, + TextDefinition label) + { + Type = type; - public int Price { get; } + Price = price; + Upkeep = upkeep; + Maximum = maximum; + ItemID = itemID; - public int Upkeep { get; } + Header = header; + Label = label; + } - public int Maximum { get; } + public Type Type{ get; } - public int ItemID { get; } + public int Price{ get; } - public TextDefinition Header { get; } + public int Upkeep{ get; } - public TextDefinition Label { get; } + public int Maximum{ get; } - public GuardDefinition( Type type, int itemID, int price, int upkeep, int maximum, TextDefinition header, TextDefinition label ) - { - Type = type; + public int ItemID{ get; } - Price = price; - Upkeep = upkeep; - Maximum = maximum; - ItemID = itemID; + public TextDefinition Header{ get; } - Header = header; - Label = label; - } - } + public TextDefinition Label{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/RankDefinition.cs b/Scripts/Engines/Factions/Definitions/RankDefinition.cs index 883bf8fab..4481c9aa8 100644 --- a/Scripts/Engines/Factions/Definitions/RankDefinition.cs +++ b/Scripts/Engines/Factions/Definitions/RankDefinition.cs @@ -1,21 +1,21 @@ namespace Server.Factions { - public class RankDefinition - { - public int Rank { get; } + public class RankDefinition + { + public RankDefinition(int rank, int required, int maxWearables, TextDefinition title) + { + Rank = rank; + Required = required; + Title = title; + MaxWearables = maxWearables; + } - public int Required { get; } + public int Rank{ get; } - public int MaxWearables { get; } + public int Required{ get; } - public TextDefinition Title { get; } + public int MaxWearables{ get; } - public RankDefinition( int rank, int required, int maxWearables, TextDefinition title ) - { - Rank = rank; - Required = required; - Title = title; - MaxWearables = maxWearables; - } - } + public TextDefinition Title{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/StrongholdDefintion.cs b/Scripts/Engines/Factions/Definitions/StrongholdDefintion.cs index 1e2eecedd..e74595e21 100644 --- a/Scripts/Engines/Factions/Definitions/StrongholdDefintion.cs +++ b/Scripts/Engines/Factions/Definitions/StrongholdDefintion.cs @@ -1,21 +1,21 @@ namespace Server.Factions { - public class StrongholdDefinition - { - public Rectangle2D[] Area { get; } + public class StrongholdDefinition + { + public StrongholdDefinition(Rectangle2D[] area, Point3D joinStone, Point3D factionStone, Point3D[] monoliths) + { + Area = area; + JoinStone = joinStone; + FactionStone = factionStone; + Monoliths = monoliths; + } - public Point3D JoinStone { get; } + public Rectangle2D[] Area{ get; } - public Point3D FactionStone { get; } + public Point3D JoinStone{ get; } - public Point3D[] Monoliths { get; } + public Point3D FactionStone{ get; } - public StrongholdDefinition( Rectangle2D[] area, Point3D joinStone, Point3D factionStone, Point3D[] monoliths ) - { - Area = area; - JoinStone = joinStone; - FactionStone = factionStone; - Monoliths = monoliths; - } - } + public Point3D[] Monoliths{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/TownDefinition.cs b/Scripts/Engines/Factions/Definitions/TownDefinition.cs index e8a5b3581..a7a4ca727 100644 --- a/Scripts/Engines/Factions/Definitions/TownDefinition.cs +++ b/Scripts/Engines/Factions/Definitions/TownDefinition.cs @@ -1,48 +1,51 @@ namespace Server.Factions { - public class TownDefinition - { - public int Sort { get; } + public class TownDefinition + { + public TownDefinition(int sort, int sigilID, string region, string friendlyName, TextDefinition townName, + TextDefinition townStoneHeader, TextDefinition strongholdMonolithName, TextDefinition townMonolithName, + TextDefinition townStoneName, TextDefinition sigilName, TextDefinition corruptedSigilName, Point3D monolith, + Point3D townStone) + { + Sort = sort; + SigilID = sigilID; + Region = region; + FriendlyName = friendlyName; + TownName = townName; + TownStoneHeader = townStoneHeader; + StrongholdMonolithName = strongholdMonolithName; + TownMonolithName = townMonolithName; + TownStoneName = townStoneName; + SigilName = sigilName; + CorruptedSigilName = corruptedSigilName; + Monolith = monolith; + TownStone = townStone; + } - public int SigilID { get; } + public int Sort{ get; } - public string Region { get; } + public int SigilID{ get; } - public string FriendlyName { get; } + public string Region{ get; } - public TextDefinition TownName { get; } + public string FriendlyName{ get; } - public TextDefinition TownStoneHeader { get; } + public TextDefinition TownName{ get; } - public TextDefinition StrongholdMonolithName { get; } + public TextDefinition TownStoneHeader{ get; } - public TextDefinition TownMonolithName { get; } + public TextDefinition StrongholdMonolithName{ get; } - public TextDefinition TownStoneName { get; } + public TextDefinition TownMonolithName{ get; } - public TextDefinition SigilName { get; } + public TextDefinition TownStoneName{ get; } - public TextDefinition CorruptedSigilName { get; } + public TextDefinition SigilName{ get; } - public Point3D Monolith { get; } + public TextDefinition CorruptedSigilName{ get; } - public Point3D TownStone { get; } + public Point3D Monolith{ get; } - public TownDefinition( int sort, int sigilID, string region, string friendlyName, TextDefinition townName, TextDefinition townStoneHeader, TextDefinition strongholdMonolithName, TextDefinition townMonolithName, TextDefinition townStoneName, TextDefinition sigilName, TextDefinition corruptedSigilName, Point3D monolith, Point3D townStone ) - { - Sort = sort; - SigilID = sigilID; - Region = region; - FriendlyName = friendlyName; - TownName = townName; - TownStoneHeader = townStoneHeader; - StrongholdMonolithName = strongholdMonolithName; - TownMonolithName = townMonolithName; - TownStoneName = townStoneName; - SigilName = sigilName; - CorruptedSigilName = corruptedSigilName; - Monolith = monolith; - TownStone = townStone; - } - } + public Point3D TownStone{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Definitions/VendorDefinition.cs b/Scripts/Engines/Factions/Definitions/VendorDefinition.cs index f7cbc6dd1..61176533d 100644 --- a/Scripts/Engines/Factions/Definitions/VendorDefinition.cs +++ b/Scripts/Engines/Factions/Definitions/VendorDefinition.cs @@ -2,72 +2,73 @@ using System; namespace Server.Factions { - public class VendorDefinition - { - public Type Type { get; } + public class VendorDefinition + { + public VendorDefinition(Type type, int itemID, int price, int upkeep, int maximum, TextDefinition header, + TextDefinition label) + { + Type = type; - public int Price { get; } + Price = price; + Upkeep = upkeep; + Maximum = maximum; + ItemID = itemID; - public int Upkeep { get; } + Header = header; + Label = label; + } - public int Maximum { get; } + public Type Type{ get; } - public int ItemID { get; } + public int Price{ get; } - public TextDefinition Header { get; } + public int Upkeep{ get; } - public TextDefinition Label { get; } + public int Maximum{ get; } - public VendorDefinition( Type type, int itemID, int price, int upkeep, int maximum, TextDefinition header, TextDefinition label ) - { - Type = type; + public int ItemID{ get; } - Price = price; - Upkeep = upkeep; - Maximum = maximum; - ItemID = itemID; + public TextDefinition Header{ get; } - Header = header; - Label = label; - } + public TextDefinition Label{ get; } - public static VendorDefinition[] Definitions { get; } = - { - new VendorDefinition( typeof( FactionBottleVendor ), 0xF0E, - 5000, - 1000, - 10, - new TextDefinition( 1011549, "POTION BOTTLE VENDOR" ), - new TextDefinition( 1011544, "Buy Potion Bottle Vendor" ) - ), - new VendorDefinition( typeof( FactionBoardVendor ), 0x1BD7, - 3000, - 500, - 10, - new TextDefinition( 1011552, "WOOD VENDOR" ), - new TextDefinition( 1011545, "Buy Wooden Board Vendor" ) - ), - new VendorDefinition( typeof( FactionOreVendor ), 0x19B8, - 3000, - 500, - 10, - new TextDefinition( 1011553, "IRON ORE VENDOR" ), - new TextDefinition( 1011546, "Buy Iron Ore Vendor" ) - ), - new VendorDefinition( typeof( FactionReagentVendor ), 0xF86, - 5000, - 1000, - 10, - new TextDefinition( 1011554, "REAGENT VENDOR" ), - new TextDefinition( 1011547, "Buy Reagent Vendor" ) - ), - new VendorDefinition( typeof( FactionHorseVendor ), 0x20DD, - 5000, - 1000, - 1, - new TextDefinition( 1011556, "HORSE BREEDER" ), - new TextDefinition( 1011555, "Buy Horse Breeder" ) - ) - }; - } + public static VendorDefinition[] Definitions{ get; } = + { + new VendorDefinition(typeof(FactionBottleVendor), 0xF0E, + 5000, + 1000, + 10, + new TextDefinition(1011549, "POTION BOTTLE VENDOR"), + new TextDefinition(1011544, "Buy Potion Bottle Vendor") + ), + new VendorDefinition(typeof(FactionBoardVendor), 0x1BD7, + 3000, + 500, + 10, + new TextDefinition(1011552, "WOOD VENDOR"), + new TextDefinition(1011545, "Buy Wooden Board Vendor") + ), + new VendorDefinition(typeof(FactionOreVendor), 0x19B8, + 3000, + 500, + 10, + new TextDefinition(1011553, "IRON ORE VENDOR"), + new TextDefinition(1011546, "Buy Iron Ore Vendor") + ), + new VendorDefinition(typeof(FactionReagentVendor), 0xF86, + 5000, + 1000, + 10, + new TextDefinition(1011554, "REAGENT VENDOR"), + new TextDefinition(1011547, "Buy Reagent Vendor") + ), + new VendorDefinition(typeof(FactionHorseVendor), 0x20DD, + 5000, + 1000, + 1, + new TextDefinition(1011556, "HORSE BREEDER"), + new TextDefinition(1011555, "Buy Horse Breeder") + ) + }; + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/ElectionGump.cs b/Scripts/Engines/Factions/Gumps/ElectionGump.cs index 895f6a5aa..e708adc3e 100644 --- a/Scripts/Engines/Factions/Gumps/ElectionGump.cs +++ b/Scripts/Engines/Factions/Gumps/ElectionGump.cs @@ -5,123 +5,125 @@ using Server.Network; namespace Server.Factions { - public class ElectionGump : FactionGump - { - private PlayerMobile m_From; - private Election m_Election; + public class ElectionGump : FactionGump + { + private Election m_Election; + private PlayerMobile m_From; - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 0: // back - { - m_From.SendGump( new FactionStoneGump( m_From, m_Election.Faction ) ); - break; - } - case 1: // vote - { - if ( m_Election.State == ElectionState.Election ) - m_From.SendGump( new VoteGump( m_From, m_Election ) ); + public ElectionGump(PlayerMobile from, Election election) : base(50, 50) + { + m_From = from; + m_Election = election; - break; - } - case 2: // campaign - { - if ( m_Election.CanBeCandidate( m_From ) ) - m_Election.AddCandidate( m_From ); + AddPage(0); - break; - } - } - } + AddBackground(0, 0, 420, 180, 5054); + AddBackground(10, 10, 400, 160, 3000); - public ElectionGump( PlayerMobile from, Election election ) : base( 50, 50 ) - { - m_From = from; - m_Election = election; + AddHtmlText(20, 20, 380, 20, election.Faction.Definition.Header, false, false); - AddPage( 0 ); + // NOTE: Gump not entirely OSI-accurate, intentionally so - AddBackground( 0, 0, 420, 180, 5054 ); - AddBackground( 10, 10, 400, 160, 3000 ); + switch (election.State) + { + case ElectionState.Pending: + { + TimeSpan toGo = election.LastStateTime + Election.PendingPeriod - DateTime.UtcNow; + int days = (int)(toGo.TotalDays + 0.5); - AddHtmlText( 20, 20, 380, 20, election.Faction.Definition.Header, false, false ); + AddHtmlLocalized(20, 40, 380, 20, 1038034, false, false); // A new election campaign is pending - // NOTE: Gump not entirely OSI-accurate, intentionally so + if (days > 0) + { + AddHtmlLocalized(20, 60, 280, 20, 1018062, false, false); // Days until next election : + AddLabel(300, 60, 0, days.ToString()); + } + else + { + AddHtmlLocalized(20, 60, 280, 20, 1018059, false, false); // Election campaigning begins tonight. + } - switch ( election.State ) - { - case ElectionState.Pending: - { - TimeSpan toGo = ( election.LastStateTime + Election.PendingPeriod ) - DateTime.UtcNow; - int days = (int) (toGo.TotalDays + 0.5); + break; + } + case ElectionState.Campaign: + { + TimeSpan toGo = election.LastStateTime + Election.CampaignPeriod - DateTime.UtcNow; + int days = (int)(toGo.TotalDays + 0.5); - AddHtmlLocalized( 20, 40, 380, 20, 1038034, false, false ); // A new election campaign is pending + AddHtmlLocalized(20, 40, 380, 20, 1018058, false, false); // There is an election campaign in progress. - if ( days > 0 ) - { - AddHtmlLocalized( 20, 60, 280, 20, 1018062, false, false ); // Days until next election : - AddLabel( 300, 60, 0, days.ToString() ); - } - else - { - AddHtmlLocalized( 20, 60, 280, 20, 1018059, false, false ); // Election campaigning begins tonight. - } + if (days > 0) + { + AddHtmlLocalized(20, 60, 280, 20, 1038033, false, false); // Days to go: + AddLabel(300, 60, 0, days.ToString()); + } + else + { + AddHtmlLocalized(20, 60, 280, 20, 1018061, false, + false); // Campaign in progress. Voting begins tonight. + } - break; - } - case ElectionState.Campaign: - { - TimeSpan toGo = ( election.LastStateTime + Election.CampaignPeriod ) - DateTime.UtcNow; - int days = (int) (toGo.TotalDays + 0.5); + if (m_Election.CanBeCandidate(m_From)) + { + AddButton(20, 110, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 110, 350, 20, 1011427, false, false); // CAMPAIGN FOR LEADERSHIP + } + else + { + PlayerState pl = PlayerState.Find(m_From); - AddHtmlLocalized( 20, 40, 380, 20, 1018058, false, false ); // There is an election campaign in progress. + if (pl == null || pl.Rank.Rank < Election.CandidateRank) + AddHtmlLocalized(20, 100, 380, 20, 1010118, false, + false); // You must have a higher rank to run for office + } - if ( days > 0 ) - { - AddHtmlLocalized( 20, 60, 280, 20, 1038033, false, false ); // Days to go: - AddLabel( 300, 60, 0, days.ToString() ); - } - else - { - AddHtmlLocalized( 20, 60, 280, 20, 1018061, false, false ); // Campaign in progress. Voting begins tonight. - } + break; + } + case ElectionState.Election: + { + TimeSpan toGo = election.LastStateTime + Election.VotingPeriod - DateTime.UtcNow; + int days = (int)Math.Ceiling(toGo.TotalDays); - if ( m_Election.CanBeCandidate( m_From ) ) - { - AddButton( 20, 110, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 110, 350, 20, 1011427, false, false ); // CAMPAIGN FOR LEADERSHIP - } - else - { - PlayerState pl = PlayerState.Find( m_From ); + AddHtmlLocalized(20, 40, 380, 20, 1018060, false, false); // There is an election vote in progress. - if ( pl == null || pl.Rank.Rank < Election.CandidateRank ) - AddHtmlLocalized( 20, 100, 380, 20, 1010118, false, false ); // You must have a higher rank to run for office - } + AddHtmlLocalized(20, 60, 280, 20, 1038033, false, false); + AddLabel(300, 60, 0, days.ToString()); - break; - } - case ElectionState.Election: - { - TimeSpan toGo = ( election.LastStateTime + Election.VotingPeriod ) - DateTime.UtcNow; - int days = (int) Math.Ceiling( toGo.TotalDays ); + AddHtmlLocalized(55, 100, 380, 20, 1011428, false, false); // VOTE FOR LEADERSHIP + AddButton(20, 100, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 20, 40, 380, 20, 1018060, false, false ); // There is an election vote in progress. + break; + } + } - AddHtmlLocalized( 20, 60, 280, 20, 1038033, false, false ); - AddLabel( 300, 60, 0, days.ToString() ); + AddButton(20, 140, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 140, 350, 20, 1011012, false, false); // CANCEL + } - AddHtmlLocalized( 55, 100, 380, 20, 1011428, false, false ); // VOTE FOR LEADERSHIP - AddButton( 20, 100, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 0: // back + { + m_From.SendGump(new FactionStoneGump(m_From, m_Election.Faction)); + break; + } + case 1: // vote + { + if (m_Election.State == ElectionState.Election) + m_From.SendGump(new VoteGump(m_From, m_Election)); - break; - } - } + break; + } + case 2: // campaign + { + if (m_Election.CanBeCandidate(m_From)) + m_Election.AddCandidate(m_From); - AddButton( 20, 140, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 140, 350, 20, 1011012, false, false ); // CANCEL - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/ElectionManagementGump.cs b/Scripts/Engines/Factions/Gumps/ElectionManagementGump.cs index 1eb6e5d79..e4f0071dd 100644 --- a/Scripts/Engines/Factions/Gumps/ElectionManagementGump.cs +++ b/Scripts/Engines/Factions/Gumps/ElectionManagementGump.cs @@ -1,216 +1,219 @@ using System; +using System.Net; using Server.Gumps; using Server.Network; namespace Server.Factions { - public class ElectionManagementGump : Gump - { - public string Right( string text ) - { - return $"
{text}
"; - } + public class ElectionManagementGump : Gump + { + public const int LabelColor = 0xFFFFFF; + private Candidate m_Candidate; - public string Center( string text ) - { - return $"
{text}
"; - } + private Election m_Election; + private int m_Page; - public string Color( string text, int color ) - { - return $"{text}"; - } + public ElectionManagementGump(Election election) : this(election, null, 0) + { + } - public static string FormatTimeSpan( TimeSpan ts ) - { - return $"{ts.Days:D2}:{ts.Hours % 24:D2}:{ts.Minutes % 60:D2}:{ts.Seconds % 60:D2}"; - } + public ElectionManagementGump(Election election, Candidate candidate, int page) : base(40, 40) + { + m_Election = election; + m_Candidate = candidate; + m_Page = page; - public const int LabelColor = 0xFFFFFF; + AddPage(0); - private Election m_Election; - private Candidate m_Candidate; - private int m_Page; + if (candidate != null) + { + AddBackground(0, 0, 448, 354, 9270); + AddAlphaRegion(10, 10, 428, 334); - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; - int bid = info.ButtonID; + AddHtml(10, 10, 428, 20, Color(Center("Candidate Management"), LabelColor), false, false); - if ( m_Candidate == null ) - { - if ( bid == 0 ) - { - } - else if ( bid == 1 ) - { - } - else - { - bid -= 2; + AddHtml(45, 35, 100, 20, Color("Player Name:", LabelColor), false, false); + AddHtml(145, 35, 100, 20, Color(candidate.Mobile == null ? "null" : candidate.Mobile.Name, LabelColor), + false, false); - if ( bid >= 0 && bid < m_Election.Candidates.Count ) - from.SendGump( new ElectionManagementGump( m_Election, m_Election.Candidates[bid], 0 ) ); - } - } - else - { - if ( bid == 0 ) - { - from.SendGump( new ElectionManagementGump( m_Election ) ); - } - else if ( bid == 1 ) - { - m_Election.RemoveCandidate( m_Candidate.Mobile ); - from.SendGump( new ElectionManagementGump( m_Election ) ); - } - else if ( bid == 2 && m_Page > 0 ) - { - from.SendGump( new ElectionManagementGump( m_Election, m_Candidate, m_Page - 1 ) ); - } - else if ( bid == 3 && (m_Page + 1) * 10 < m_Candidate.Voters.Count ) - { - from.SendGump( new ElectionManagementGump( m_Election, m_Candidate, m_Page + 1 ) ); - } - else - { - bid -= 4; + AddHtml(45, 55, 100, 20, Color("Vote Count:", LabelColor), false, false); + AddHtml(145, 55, 100, 20, Color(candidate.Votes.ToString(), LabelColor), false, false); - if ( bid >= 0 && bid < m_Candidate.Voters.Count ) - { - m_Candidate.Voters.RemoveAt( bid ); - from.SendGump( new ElectionManagementGump( m_Election, m_Candidate, m_Page ) ); - } - } - } - } + AddButton(12, 73, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtml(45, 75, 100, 20, Color("Drop Candidate", LabelColor), false, false); - public ElectionManagementGump( Election election ) : this( election, null, 0 ) - { - } + AddImageTiled(13, 99, 422, 242, 9264); + AddImageTiled(14, 100, 420, 240, 9274); + AddAlphaRegion(14, 100, 420, 240); - public ElectionManagementGump( Election election, Candidate candidate, int page ) : base( 40, 40 ) - { - m_Election = election; - m_Candidate = candidate; - m_Page = page; + AddHtml(14, 100, 420, 20, Color(Center("Voters"), LabelColor), false, false); - AddPage( 0 ); + if (page > 0) + AddButton(397, 104, 0x15E3, 0x15E7, 2, GumpButtonType.Reply, 0); + else + AddImage(397, 104, 0x25EA); - if ( candidate != null ) - { - AddBackground( 0, 0, 448, 354, 9270 ); - AddAlphaRegion( 10, 10, 428, 334 ); - - AddHtml( 10, 10, 428, 20, Color( Center( "Candidate Management" ), LabelColor ), false, false ); - - AddHtml( 45, 35, 100, 20, Color( "Player Name:", LabelColor ), false, false ); - AddHtml( 145, 35, 100, 20, Color( candidate.Mobile == null ? "null" : candidate.Mobile.Name, LabelColor ), false, false ); - - AddHtml( 45, 55, 100, 20, Color( "Vote Count:", LabelColor ), false, false ); - AddHtml( 145, 55, 100, 20, Color( candidate.Votes.ToString(), LabelColor ), false, false ); - - AddButton( 12, 73, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtml( 45, 75, 100, 20, Color( "Drop Candidate", LabelColor ), false, false ); - - AddImageTiled( 13, 99, 422, 242, 9264 ); - AddImageTiled( 14, 100, 420, 240, 9274 ); - AddAlphaRegion( 14, 100, 420, 240 ); - - AddHtml( 14, 100, 420, 20, Color( Center( "Voters" ), LabelColor ), false, false ); - - if ( page > 0 ) - AddButton( 397, 104, 0x15E3, 0x15E7, 2, GumpButtonType.Reply, 0 ); - else - AddImage( 397, 104, 0x25EA ); - - if ( (page + 1) * 10 < candidate.Voters.Count ) - AddButton( 414, 104, 0x15E1, 0x15E5, 3, GumpButtonType.Reply, 0 ); - else - AddImage( 414, 104, 0x25E6 ); + if ((page + 1) * 10 < candidate.Voters.Count) + AddButton(414, 104, 0x15E1, 0x15E5, 3, GumpButtonType.Reply, 0); + else + AddImage(414, 104, 0x25E6); - AddHtml( 14, 120, 30, 20, Color( Center( "DEL" ), LabelColor ), false, false ); - AddHtml( 47, 120, 150, 20, Color( "Name", LabelColor ), false, false ); - AddHtml( 195, 120, 100, 20, Color( Center( "Address" ), LabelColor ), false, false ); - AddHtml( 295, 120, 80, 20, Color( Center( "Time" ), LabelColor ), false, false ); - AddHtml( 355, 120, 60, 20, Color( Center( "Legit" ), LabelColor ), false, false ); + AddHtml(14, 120, 30, 20, Color(Center("DEL"), LabelColor), false, false); + AddHtml(47, 120, 150, 20, Color("Name", LabelColor), false, false); + AddHtml(195, 120, 100, 20, Color(Center("Address"), LabelColor), false, false); + AddHtml(295, 120, 80, 20, Color(Center("Time"), LabelColor), false, false); + AddHtml(355, 120, 60, 20, Color(Center("Legit"), LabelColor), false, false); - int idx = 0; + int idx = 0; - for ( int i = page*10; i >= 0 && i < candidate.Voters.Count && i < (page+1)*10; ++i, ++idx ) - { - Voter voter = (Voter)candidate.Voters[i]; + for (int i = page * 10; i >= 0 && i < candidate.Voters.Count && i < (page + 1) * 10; ++i, ++idx) + { + Voter voter = candidate.Voters[i]; - AddButton( 13, 138 + (idx * 20), 4002, 4004, 4 + i, GumpButtonType.Reply, 0 ); + AddButton(13, 138 + idx * 20, 4002, 4004, 4 + i, GumpButtonType.Reply, 0); - object[] fields = voter.AcquireFields(); + object[] fields = voter.AcquireFields(); - int x = 45; + int x = 45; - for ( int j = 0; j < fields.Length; ++j ) - { - object obj = fields[j]; + for (int j = 0; j < fields.Length; ++j) + { + object obj = fields[j]; - if ( obj is Mobile mobile ) - { - AddHtml( x + 2, 140 + (idx * 20), 150, 20, Color( mobile.Name, LabelColor ), false, false ); - x += 150; - } - else if ( obj is System.Net.IPAddress ) - { - AddHtml( x, 140 + (idx * 20), 100, 20, Color( Center( obj.ToString() ), LabelColor ), false, false ); - x += 100; - } - else if ( obj is DateTime time ) - { - AddHtml( x, 140 + (idx * 20), 80, 20, Color( Center( FormatTimeSpan( time - election.LastStateTime ) ), LabelColor ), false, false ); - x += 80; - } - else if ( obj is int i1 ) - { - AddHtml( x, 140 + (idx * 20), 60, 20, Color( Center( i1 + "%" ), LabelColor ), false, false ); - x += 60; - } - } - } - } - else - { - AddBackground( 0, 0, 288, 334, 9270 ); - AddAlphaRegion( 10, 10, 268, 314 ); + if (obj is Mobile mobile) + { + AddHtml(x + 2, 140 + idx * 20, 150, 20, Color(mobile.Name, LabelColor), false, false); + x += 150; + } + else if (obj is IPAddress) + { + AddHtml(x, 140 + idx * 20, 100, 20, Color(Center(obj.ToString()), LabelColor), false, false); + x += 100; + } + else if (obj is DateTime time) + { + AddHtml(x, 140 + idx * 20, 80, 20, + Color(Center(FormatTimeSpan(time - election.LastStateTime)), LabelColor), false, false); + x += 80; + } + else if (obj is int i1) + { + AddHtml(x, 140 + idx * 20, 60, 20, Color(Center(i1 + "%"), LabelColor), false, false); + x += 60; + } + } + } + } + else + { + AddBackground(0, 0, 288, 334, 9270); + AddAlphaRegion(10, 10, 268, 314); - AddHtml( 10, 10, 268, 20, Color( Center( "Election Management" ), LabelColor ), false, false ); + AddHtml(10, 10, 268, 20, Color(Center("Election Management"), LabelColor), false, false); - AddHtml( 45, 35, 100, 20, Color( "Current State:", LabelColor ), false, false ); - AddHtml( 145, 35, 100, 20, Color( election.State.ToString(), LabelColor ), false, false ); + AddHtml(45, 35, 100, 20, Color("Current State:", LabelColor), false, false); + AddHtml(145, 35, 100, 20, Color(election.State.ToString(), LabelColor), false, false); - AddButton( 12, 53, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtml( 45, 55, 100, 20, Color( "Transition Time:", LabelColor ), false, false ); - AddHtml( 145, 55, 100, 20, Color( FormatTimeSpan( election.NextStateTime ), LabelColor ), false, false ); + AddButton(12, 53, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtml(45, 55, 100, 20, Color("Transition Time:", LabelColor), false, false); + AddHtml(145, 55, 100, 20, Color(FormatTimeSpan(election.NextStateTime), LabelColor), false, false); - AddImageTiled( 13, 79, 262, 242, 9264 ); - AddImageTiled( 14, 80, 260, 240, 9274 ); - AddAlphaRegion( 14, 80, 260, 240 ); + AddImageTiled(13, 79, 262, 242, 9264); + AddImageTiled(14, 80, 260, 240, 9274); + AddAlphaRegion(14, 80, 260, 240); - AddHtml( 14, 80, 260, 20, Color( Center( "Candidates" ), LabelColor ), false, false ); - AddHtml( 14, 100, 30, 20, Color( Center( "-->" ), LabelColor ), false, false ); - AddHtml( 47, 100, 150, 20, Color( "Name", LabelColor ), false, false ); - AddHtml( 195, 100, 80, 20, Color( Center( "Votes" ), LabelColor ), false, false ); + AddHtml(14, 80, 260, 20, Color(Center("Candidates"), LabelColor), false, false); + AddHtml(14, 100, 30, 20, Color(Center("-->"), LabelColor), false, false); + AddHtml(47, 100, 150, 20, Color("Name", LabelColor), false, false); + AddHtml(195, 100, 80, 20, Color(Center("Votes"), LabelColor), false, false); - for ( int i = 0; i < election.Candidates.Count; ++i ) - { - Candidate cd = election.Candidates[i]; - Mobile mob = cd.Mobile; + for (int i = 0; i < election.Candidates.Count; ++i) + { + Candidate cd = election.Candidates[i]; + Mobile mob = cd.Mobile; - if ( mob == null ) - continue; + if (mob == null) + continue; - AddButton( 13, 118 + (i * 20), 4005, 4007, 2 + i, GumpButtonType.Reply, 0 ); - AddHtml( 47, 120 + (i * 20), 150, 20, Color( mob.Name, LabelColor ), false, false ); - AddHtml( 195, 120 + (i * 20), 80, 20, Color( Center( cd.Votes.ToString() ), LabelColor ), false, false ); - } - } - } - } -} + AddButton(13, 118 + i * 20, 4005, 4007, 2 + i, GumpButtonType.Reply, 0); + AddHtml(47, 120 + i * 20, 150, 20, Color(mob.Name, LabelColor), false, false); + AddHtml(195, 120 + i * 20, 80, 20, Color(Center(cd.Votes.ToString()), LabelColor), false, false); + } + } + } + + public string Right(string text) + { + return $"
{text}
"; + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + public static string FormatTimeSpan(TimeSpan ts) + { + return $"{ts.Days:D2}:{ts.Hours % 24:D2}:{ts.Minutes % 60:D2}:{ts.Seconds % 60:D2}"; + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; + int bid = info.ButtonID; + + if (m_Candidate == null) + { + if (bid == 0) + { + } + else if (bid == 1) + { + } + else + { + bid -= 2; + + if (bid >= 0 && bid < m_Election.Candidates.Count) + from.SendGump(new ElectionManagementGump(m_Election, m_Election.Candidates[bid], 0)); + } + } + else + { + if (bid == 0) + { + from.SendGump(new ElectionManagementGump(m_Election)); + } + else if (bid == 1) + { + m_Election.RemoveCandidate(m_Candidate.Mobile); + from.SendGump(new ElectionManagementGump(m_Election)); + } + else if (bid == 2 && m_Page > 0) + { + from.SendGump(new ElectionManagementGump(m_Election, m_Candidate, m_Page - 1)); + } + else if (bid == 3 && (m_Page + 1) * 10 < m_Candidate.Voters.Count) + { + from.SendGump(new ElectionManagementGump(m_Election, m_Candidate, m_Page + 1)); + } + else + { + bid -= 4; + + if (bid >= 0 && bid < m_Candidate.Voters.Count) + { + m_Candidate.Voters.RemoveAt(bid); + from.SendGump(new ElectionManagementGump(m_Election, m_Candidate, m_Page)); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/FactionGump.cs b/Scripts/Engines/Factions/Gumps/FactionGump.cs index 18816619f..2e6d9b804 100644 --- a/Scripts/Engines/Factions/Gumps/FactionGump.cs +++ b/Scripts/Engines/Factions/Gumps/FactionGump.cs @@ -2,45 +2,45 @@ using Server.Gumps; namespace Server.Factions { - public abstract class FactionGump : Gump - { - public virtual int ButtonTypes => 10; + public abstract class FactionGump : Gump + { + public FactionGump(int x, int y) : base(x, y) + { + } - public int ToButtonID( int type, int index ) - { - return 1 + (index * ButtonTypes) + type; - } + public virtual int ButtonTypes => 10; - public bool FromButtonID( int buttonID, out int type, out int index ) - { - int offset = buttonID - 1; + public int ToButtonID(int type, int index) + { + return 1 + index * ButtonTypes + type; + } - if ( offset >= 0 ) - { - type = offset % ButtonTypes; - index = offset / ButtonTypes; - return true; - } + public bool FromButtonID(int buttonID, out int type, out int index) + { + int offset = buttonID - 1; - type = index = 0; - return false; - } + if (offset >= 0) + { + type = offset % ButtonTypes; + index = offset / ButtonTypes; + return true; + } - public static bool Exists( Mobile mob ) - { - return ( mob.FindGump( typeof( FactionGump ) ) != null ); - } + type = index = 0; + return false; + } - public void AddHtmlText( int x, int y, int width, int height, TextDefinition text, bool back, bool scroll ) - { - if ( text != null && text.Number > 0 ) - AddHtmlLocalized( x, y, width, height, text.Number, back, scroll ); - else if ( text?.String != null ) - AddHtml( x, y, width, height, text.String, back, scroll ); - } + public static bool Exists(Mobile mob) + { + return mob.FindGump(typeof(FactionGump)) != null; + } - public FactionGump( int x, int y ) : base( x, y ) - { - } - } + public void AddHtmlText(int x, int y, int width, int height, TextDefinition text, bool back, bool scroll) + { + if (text != null && text.Number > 0) + AddHtmlLocalized(x, y, width, height, text.Number, back, scroll); + else if (text?.String != null) + AddHtml(x, y, width, height, text.String, back, scroll); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/FactionImbueGump.cs b/Scripts/Engines/Factions/Gumps/FactionImbueGump.cs index 4c2894333..896549c00 100644 --- a/Scripts/Engines/Factions/Gumps/FactionImbueGump.cs +++ b/Scripts/Engines/Factions/Gumps/FactionImbueGump.cs @@ -1,101 +1,102 @@ -using Server.Items; -using Server.Gumps; -using Server.Network; using Server.Engines.Craft; +using Server.Gumps; +using Server.Items; +using Server.Network; namespace Server.Factions { - public class FactionImbueGump : FactionGump - { - private Item m_Item; - private Mobile m_Mobile; - private Faction m_Faction; - private CraftSystem m_CraftSystem; - private BaseTool m_Tool; - private object m_Notice; - private int m_Quality; + public class FactionImbueGump : FactionGump + { + private CraftSystem m_CraftSystem; - private FactionItemDefinition m_Definition; + private FactionItemDefinition m_Definition; + private Faction m_Faction; + private Item m_Item; + private Mobile m_Mobile; + private object m_Notice; + private int m_Quality; + private BaseTool m_Tool; - public FactionImbueGump( int quality, Item item, Mobile from, CraftSystem craftSystem, BaseTool tool, object notice, int availableSilver, Faction faction, FactionItemDefinition def ) : base( 100, 200 ) - { - m_Item = item; - m_Mobile = from; - m_Faction = faction; - m_CraftSystem = craftSystem; - m_Tool = tool; - m_Notice = notice; - m_Quality = quality; - m_Definition = def; + public FactionImbueGump(int quality, Item item, Mobile from, CraftSystem craftSystem, BaseTool tool, object notice, + int availableSilver, Faction faction, FactionItemDefinition def) : base(100, 200) + { + m_Item = item; + m_Mobile = from; + m_Faction = faction; + m_CraftSystem = craftSystem; + m_Tool = tool; + m_Notice = notice; + m_Quality = quality; + m_Definition = def; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 320, 270, 5054 ); - AddBackground( 10, 10, 300, 250, 3000 ); + AddBackground(0, 0, 320, 270, 5054); + AddBackground(10, 10, 300, 250, 3000); - AddHtmlLocalized( 20, 20, 210, 25, 1011569, false, false ); // Imbue with Faction properties? + AddHtmlLocalized(20, 20, 210, 25, 1011569, false, false); // Imbue with Faction properties? - AddHtmlLocalized( 20, 60, 170, 25, 1018302, false, false ); // Item quality: - AddHtmlLocalized( 175, 60, 100, 25, 1018305 - m_Quality, false, false ); // Exceptional, Average, Low + AddHtmlLocalized(20, 60, 170, 25, 1018302, false, false); // Item quality: + AddHtmlLocalized(175, 60, 100, 25, 1018305 - m_Quality, false, false); // Exceptional, Average, Low - AddHtmlLocalized( 20, 80, 170, 25, 1011572, false, false ); // Item Cost : - AddLabel( 175, 80, 0x34, def.SilverCost.ToString( "N0" ) ); // NOTE: Added 'N0' + AddHtmlLocalized(20, 80, 170, 25, 1011572, false, false); // Item Cost : + AddLabel(175, 80, 0x34, def.SilverCost.ToString("N0")); // NOTE: Added 'N0' - AddHtmlLocalized( 20, 100, 170, 25, 1011573, false, false ); // Your Silver : - AddLabel( 175, 100, 0x34, availableSilver.ToString( "N0" ) ); // NOTE: Added 'N0' + AddHtmlLocalized(20, 100, 170, 25, 1011573, false, false); // Your Silver : + AddLabel(175, 100, 0x34, availableSilver.ToString("N0")); // NOTE: Added 'N0' - AddRadio( 20, 140, 210, 211, true, 1 ); - AddLabel( 55, 140, m_Faction.Definition.HuePrimary - 1, "*****" ); - AddHtmlLocalized( 150, 140, 150, 25, 1011570, false, false ); // Primary Color + AddRadio(20, 140, 210, 211, true, 1); + AddLabel(55, 140, m_Faction.Definition.HuePrimary - 1, "*****"); + AddHtmlLocalized(150, 140, 150, 25, 1011570, false, false); // Primary Color - AddRadio( 20, 160, 210, 211, false, 2 ); - AddLabel( 55, 160, m_Faction.Definition.HueSecondary - 1, "*****" ); - AddHtmlLocalized( 150, 160, 150, 25, 1011571, false, false ); // Secondary Color + AddRadio(20, 160, 210, 211, false, 2); + AddLabel(55, 160, m_Faction.Definition.HueSecondary - 1, "*****"); + AddHtmlLocalized(150, 160, 150, 25, 1011571, false, false); // Secondary Color - AddHtmlLocalized( 55, 200, 200, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 200, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 200, 200, 25, 1011011, false, false); // CONTINUE + AddButton(20, 200, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 230, 200, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 230, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(55, 230, 200, 25, 1011012, false, false); // CANCEL + AddButton(20, 230, 4005, 4007, 0, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - { - Container pack = m_Mobile.Backpack; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + { + Container pack = m_Mobile.Backpack; - if ( pack != null && m_Item.IsChildOf( pack ) ) - { - if ( pack.ConsumeTotal( typeof( Silver ), m_Definition.SilverCost ) ) - { - int hue; + if (pack != null && m_Item.IsChildOf(pack)) + { + if (pack.ConsumeTotal(typeof(Silver), m_Definition.SilverCost)) + { + int hue; - if ( m_Item is SpellScroll ) - hue = 0; - else if ( info.IsSwitched( 1 ) ) - hue = m_Faction.Definition.HuePrimary; - else - hue = m_Faction.Definition.HueSecondary; + if (m_Item is SpellScroll) + hue = 0; + else if (info.IsSwitched(1)) + hue = m_Faction.Definition.HuePrimary; + else + hue = m_Faction.Definition.HueSecondary; - FactionItem.Imbue( m_Item, m_Faction, true, hue ); - } - else - { - m_Mobile.SendLocalizedMessage( 1042204 ); // You do not have enough silver. - } - } - } + FactionItem.Imbue(m_Item, m_Faction, true, hue); + } + else + { + m_Mobile.SendLocalizedMessage(1042204); // You do not have enough silver. + } + } + } - if ( m_Tool != null && !m_Tool.Deleted && m_Tool.UsesRemaining > 0 ) - m_Mobile.SendGump( new CraftGump( m_Mobile, m_CraftSystem, m_Tool, m_Notice ) ); - else if ( m_Notice is string s ) - m_Mobile.SendMessage( s ); - else if ( m_Notice is int i && i > 0 ) - m_Mobile.SendLocalizedMessage( i ); - } - } -} + if (m_Tool != null && !m_Tool.Deleted && m_Tool.UsesRemaining > 0) + m_Mobile.SendGump(new CraftGump(m_Mobile, m_CraftSystem, m_Tool, m_Notice)); + else if (m_Notice is string s) + m_Mobile.SendMessage(s); + else if (m_Notice is int i && i > 0) + m_Mobile.SendLocalizedMessage(i); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/FactionStoneGump.cs b/Scripts/Engines/Factions/Gumps/FactionStoneGump.cs index f97e88435..49fb5fded 100644 --- a/Scripts/Engines/Factions/Gumps/FactionStoneGump.cs +++ b/Scripts/Engines/Factions/Gumps/FactionStoneGump.cs @@ -1,345 +1,359 @@ +using System.Collections.Generic; using Server.Gumps; using Server.Mobiles; using Server.Network; -using System.Collections.Generic; namespace Server.Factions { - public class FactionStoneGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; + public class FactionStoneGump : FactionGump + { + private Faction m_Faction; + private PlayerMobile m_From; - public override int ButtonTypes => 4; + public FactionStoneGump(PlayerMobile from, Faction faction) : base(20, 30) + { + m_From = from; + m_Faction = faction; - public FactionStoneGump( PlayerMobile from, Faction faction ) : base( 20, 30 ) - { - m_From = from; - m_Faction = faction; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 550, 440, 5054); + AddBackground(10, 10, 530, 420, 3000); - AddBackground( 0, 0, 550, 440, 5054 ); - AddBackground( 10, 10, 530, 420, 3000 ); + #region General - #region General - AddPage( 1 ); + AddPage(1); - AddHtmlText( 20, 30, 510, 20, faction.Definition.Header, false, false ); + AddHtmlText(20, 30, 510, 20, faction.Definition.Header, false, false); - AddHtmlLocalized( 20, 60, 100, 20, 1011429, false, false ); // Led By : - AddHtml( 125, 60, 200, 20, faction.Commander != null ? faction.Commander.Name : "Nobody", false, false ); + AddHtmlLocalized(20, 60, 100, 20, 1011429, false, false); // Led By : + AddHtml(125, 60, 200, 20, faction.Commander != null ? faction.Commander.Name : "Nobody", false, false); - AddHtmlLocalized( 20, 80, 100, 20, 1011457, false, false ); // Tithe rate : - if ( faction.Tithe >= 0 && faction.Tithe <= 100 && (faction.Tithe % 10) == 0 ) - AddHtmlLocalized( 125, 80, 350, 20, 1011480 + (faction.Tithe / 10), false, false ); - else - AddHtml( 125, 80, 350, 20, faction.Tithe + "%", false, false ); + AddHtmlLocalized(20, 80, 100, 20, 1011457, false, false); // Tithe rate : + if (faction.Tithe >= 0 && faction.Tithe <= 100 && faction.Tithe % 10 == 0) + AddHtmlLocalized(125, 80, 350, 20, 1011480 + faction.Tithe / 10, false, false); + else + AddHtml(125, 80, 350, 20, faction.Tithe + "%", false, false); - AddHtmlLocalized( 20, 100, 100, 20, 1011458, false, false ); // Traps placed : - AddHtml( 125, 100, 50, 20, faction.Traps.Count.ToString(), false, false ); + AddHtmlLocalized(20, 100, 100, 20, 1011458, false, false); // Traps placed : + AddHtml(125, 100, 50, 20, faction.Traps.Count.ToString(), false, false); - AddHtmlLocalized( 55, 225, 200, 20, 1011428, false, false ); // VOTE FOR LEADERSHIP - AddButton( 20, 225, 4005, 4007, ToButtonID( 0, 0 ), GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 225, 200, 20, 1011428, false, false); // VOTE FOR LEADERSHIP + AddButton(20, 225, 4005, 4007, ToButtonID(0, 0), GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 150, 100, 20, 1011430, false, false ); // CITY STATUS - AddButton( 20, 150, 4005, 4007, 0, GumpButtonType.Page, 2 ); + AddHtmlLocalized(55, 150, 100, 20, 1011430, false, false); // CITY STATUS + AddButton(20, 150, 4005, 4007, 0, GumpButtonType.Page, 2); - AddHtmlLocalized( 55, 175, 100, 20, 1011444, false, false ); // STATISTICS - AddButton( 20, 175, 4005, 4007, 0, GumpButtonType.Page, 4 ); + AddHtmlLocalized(55, 175, 100, 20, 1011444, false, false); // STATISTICS + AddButton(20, 175, 4005, 4007, 0, GumpButtonType.Page, 4); - bool isMerchantQualified = MerchantTitles.HasMerchantQualifications( from ); + bool isMerchantQualified = MerchantTitles.HasMerchantQualifications(from); - PlayerState pl = PlayerState.Find( from ); + PlayerState pl = PlayerState.Find(from); - if ( pl != null && pl.MerchantTitle != MerchantTitle.None ) - { - AddHtmlLocalized( 55, 200, 250, 20, 1011460, false, false ); // UNDECLARE FACTION MERCHANT - AddButton( 20, 200, 4005, 4007, ToButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - } - else if ( isMerchantQualified ) - { - AddHtmlLocalized( 55, 200, 250, 20, 1011459, false, false ); // DECLARE FACTION MERCHANT - AddButton( 20, 200, 4005, 4007, 0, GumpButtonType.Page, 5 ); - } - else - { - AddHtmlLocalized( 55, 200, 250, 20, 1011467, false, false ); // MERCHANT OPTIONS - AddImage( 20, 200, 4020 ); - } + if (pl != null && pl.MerchantTitle != MerchantTitle.None) + { + AddHtmlLocalized(55, 200, 250, 20, 1011460, false, false); // UNDECLARE FACTION MERCHANT + AddButton(20, 200, 4005, 4007, ToButtonID(1, 0), GumpButtonType.Reply, 0); + } + else if (isMerchantQualified) + { + AddHtmlLocalized(55, 200, 250, 20, 1011459, false, false); // DECLARE FACTION MERCHANT + AddButton(20, 200, 4005, 4007, 0, GumpButtonType.Page, 5); + } + else + { + AddHtmlLocalized(55, 200, 250, 20, 1011467, false, false); // MERCHANT OPTIONS + AddImage(20, 200, 4020); + } - AddHtmlLocalized( 55, 250, 300, 20, 1011461, false, false ); // COMMANDER OPTIONS - if ( faction.IsCommander( from ) ) - AddButton( 20, 250, 4005, 4007, 0, GumpButtonType.Page, 6 ); - else - AddImage( 20, 250, 4020 ); + AddHtmlLocalized(55, 250, 300, 20, 1011461, false, false); // COMMANDER OPTIONS + if (faction.IsCommander(from)) + AddButton(20, 250, 4005, 4007, 0, GumpButtonType.Page, 6); + else + AddImage(20, 250, 4020); - AddHtmlLocalized( 55, 275, 300, 20, 1011426, false, false ); // LEAVE THIS FACTION - AddButton( 20, 275, 4005, 4007, ToButtonID( 0, 1 ), GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 275, 300, 20, 1011426, false, false); // LEAVE THIS FACTION + AddButton(20, 275, 4005, 4007, ToButtonID(0, 1), GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 300, 200, 20, 1011441, false, false ); // EXIT - AddButton( 20, 300, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - #endregion + AddHtmlLocalized(55, 300, 200, 20, 1011441, false, false); // EXIT + AddButton(20, 300, 4005, 4007, 0, GumpButtonType.Reply, 0); - #region City Status - AddPage( 2 ); + #endregion - AddHtmlLocalized( 20, 30, 250, 20, 1011430, false, false ); // CITY STATUS + #region City Status - List towns = Town.Towns; + AddPage(2); - for ( int i = 0; i < towns.Count; ++i ) - { - Town town = towns[i]; + AddHtmlLocalized(20, 30, 250, 20, 1011430, false, false); // CITY STATUS - AddHtmlText( 40, 55 + (i * 30), 150, 20, town.Definition.TownName, false, false ); + List towns = Town.Towns; - if ( town.Owner == null ) - { - AddHtmlLocalized( 200, 55 + (i * 30), 150, 20, 1011462, false, false ); // : Neutral - } - else - { - AddHtmlLocalized( 200, 55 + (i * 30), 150, 20, town.Owner.Definition.OwnerLabel, false, false ); + for (int i = 0; i < towns.Count; ++i) + { + Town town = towns[i]; - BaseMonolith monolith = town.Monolith; + AddHtmlText(40, 55 + i * 30, 150, 20, town.Definition.TownName, false, false); - AddImage( 20, 60 + (i * 30), ( monolith?.Sigil != null && monolith.Sigil.IsPurifying ) ? 0x938 : 0x939 ); - } - } + if (town.Owner == null) + { + AddHtmlLocalized(200, 55 + i * 30, 150, 20, 1011462, false, false); // : Neutral + } + else + { + AddHtmlLocalized(200, 55 + i * 30, 150, 20, town.Owner.Definition.OwnerLabel, false, false); + BaseMonolith monolith = town.Monolith; - AddImage( 20, 300, 2361 ); - AddHtmlLocalized( 45, 295, 300, 20, 1011491, false, false ); // sigil may be recaptured + AddImage(20, 60 + i * 30, monolith?.Sigil != null && monolith.Sigil.IsPurifying ? 0x938 : 0x939); + } + } - AddImage( 20, 320, 2360 ); - AddHtmlLocalized( 45, 315, 300, 20, 1011492, false, false ); // sigil may not be recaptured - AddHtmlLocalized( 55, 350, 100, 20, 1011447, false, false ); // BACK - AddButton( 20, 350, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + AddImage(20, 300, 2361); + AddHtmlLocalized(45, 295, 300, 20, 1011491, false, false); // sigil may be recaptured - #region Statistics - AddPage( 4 ); + AddImage(20, 320, 2360); + AddHtmlLocalized(45, 315, 300, 20, 1011492, false, false); // sigil may not be recaptured - AddHtmlLocalized( 20, 30, 150, 20, 1011444, false, false ); // STATISTICS + AddHtmlLocalized(55, 350, 100, 20, 1011447, false, false); // BACK + AddButton(20, 350, 4005, 4007, 0, GumpButtonType.Page, 1); - AddHtmlLocalized( 20, 100, 100, 20, 1011445, false, false ); // Name : - AddHtml( 120, 100, 150, 20, from.Name, false, false ); + #endregion - AddHtmlLocalized( 20, 130, 100, 20, 1018064, false, false ); // score : - AddHtml( 120, 130, 100, 20, (pl?.KillPoints ?? 0).ToString(), false, false ); + #region Statistics - AddHtmlLocalized( 20, 160, 100, 20, 1011446, false, false ); // Rank : - AddHtml( 120, 160, 100, 20, (pl?.Rank.Rank ?? 0).ToString(), false, false ); + AddPage(4); - AddHtmlLocalized( 55, 250, 100, 20, 1011447, false, false ); // BACK - AddButton( 20, 250, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + AddHtmlLocalized(20, 30, 150, 20, 1011444, false, false); // STATISTICS - #region Merchant Options - if ( ( pl == null || pl.MerchantTitle == MerchantTitle.None ) && isMerchantQualified ) - { - AddPage( 5 ); + AddHtmlLocalized(20, 100, 100, 20, 1011445, false, false); // Name : + AddHtml(120, 100, 150, 20, from.Name, false, false); - AddHtmlLocalized( 20, 30, 250, 20, 1011467, false, false ); // MERCHANT OPTIONS + AddHtmlLocalized(20, 130, 100, 20, 1018064, false, false); // score : + AddHtml(120, 130, 100, 20, (pl?.KillPoints ?? 0).ToString(), false, false); - AddHtmlLocalized( 20, 80, 300, 20, 1011473, false, false ); // Select the title you wish to display + AddHtmlLocalized(20, 160, 100, 20, 1011446, false, false); // Rank : + AddHtml(120, 160, 100, 20, (pl?.Rank.Rank ?? 0).ToString(), false, false); - MerchantTitleInfo[] infos = MerchantTitles.Info; + AddHtmlLocalized(55, 250, 100, 20, 1011447, false, false); // BACK + AddButton(20, 250, 4005, 4007, 0, GumpButtonType.Page, 1); - for ( int i = 0; i < infos.Length; ++i ) - { - MerchantTitleInfo info = infos[i]; + #endregion - if ( MerchantTitles.IsQualified( from, info ) ) - AddButton( 20, 100 + (i * 30), 4005, 4007, ToButtonID( 1, i + 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 20, 100 + (i * 30), 4020 ); + #region Merchant Options - AddHtmlText( 55, 100 + (i * 30), 200, 20, info.Label, false, false ); - } + if ((pl == null || pl.MerchantTitle == MerchantTitle.None) && isMerchantQualified) + { + AddPage(5); - AddHtmlLocalized( 55, 340, 100, 20, 1011447, false, false ); // BACK - AddButton( 20, 340, 4005, 4007, 0, GumpButtonType.Page, 1 ); - } - #endregion + AddHtmlLocalized(20, 30, 250, 20, 1011467, false, false); // MERCHANT OPTIONS - #region Commander Options - if ( faction.IsCommander( from ) ) - { - #region General - AddPage( 6 ); + AddHtmlLocalized(20, 80, 300, 20, 1011473, false, false); // Select the title you wish to display - AddHtmlLocalized( 20, 30, 200, 20, 1011461, false, false ); // COMMANDER OPTIONS + MerchantTitleInfo[] infos = MerchantTitles.Info; - AddHtmlLocalized( 20, 70, 120, 20, 1011457, false, false ); // Tithe rate : - if ( faction.Tithe >= 0 && faction.Tithe <= 100 && (faction.Tithe % 10) == 0 ) - AddHtmlLocalized( 140, 70, 250, 20, 1011480 + (faction.Tithe / 10), false, false ); - else - AddHtml( 140, 70, 250, 20, faction.Tithe + "%", false, false ); + for (int i = 0; i < infos.Length; ++i) + { + MerchantTitleInfo info = infos[i]; - AddHtmlLocalized( 20, 100, 120, 20, 1011474, false, false ); // Silver available : - AddHtml( 140, 100, 50, 20, faction.Silver.ToString( "N0" ), false, false ); // NOTE: Added 'N0' formatting + if (MerchantTitles.IsQualified(from, info)) + AddButton(20, 100 + i * 30, 4005, 4007, ToButtonID(1, i + 1), GumpButtonType.Reply, 0); + else + AddImage(20, 100 + i * 30, 4020); - AddHtmlLocalized( 55, 130, 200, 20, 1011478, false, false ); // CHANGE TITHE RATE - AddButton( 20, 130, 4005, 4007, 0, GumpButtonType.Page, 8 ); + AddHtmlText(55, 100 + i * 30, 200, 20, info.Label, false, false); + } - AddHtmlLocalized( 55, 160, 200, 20, 1018301, false, false ); // TRANSFER SILVER - if ( faction.Silver >= 10000 ) - AddButton( 20, 160, 4005, 4007, 0, GumpButtonType.Page, 7 ); - else - AddImage( 20, 160, 4020 ); + AddHtmlLocalized(55, 340, 100, 20, 1011447, false, false); // BACK + AddButton(20, 340, 4005, 4007, 0, GumpButtonType.Page, 1); + } - AddHtmlLocalized( 55, 310, 100, 20, 1011447, false, false ); // BACK - AddButton( 20, 310, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion - - #region Town Finance - if ( faction.Silver >= 10000 ) - { - AddPage( 7 ); + #endregion - AddHtmlLocalized( 20, 30, 250, 20, 1011476, false, false ); // TOWN FINANCE + #region Commander Options - AddHtmlLocalized( 20, 50, 400, 20, 1011477, false, false ); // Select a town to transfer 10000 silver to + if (faction.IsCommander(from)) + { + #region General - for ( int i = 0; i < towns.Count; ++i ) - { - Town town = towns[i]; + AddPage(6); - AddHtmlText( 55, 75 + (i * 30), 200, 20, town.Definition.TownName, false, false ); - - if ( town.Owner == faction ) - AddButton( 20, 75 + (i * 30), 4005, 4007, ToButtonID( 2, i ), GumpButtonType.Reply, 0 ); - else - AddImage( 20, 75 + (i * 30), 4020 ); - } - - AddHtmlLocalized( 55, 310, 100, 20, 1011447, false, false ); // BACK - AddButton( 20, 310, 4005, 4007, 0, GumpButtonType.Page, 1 ); - } - #endregion - - #region Change Tithe Rate - AddPage( 8 ); - - AddHtmlLocalized( 20, 30, 400, 20, 1011479, false, false ); // Select the % for the new tithe rate - - int y = 55; - - for ( int i = 0; i <= 10; ++i ) - { - if ( i == 5 ) - y += 5; - - AddHtmlLocalized( 55, y, 300, 20, 1011480 + i, false, false ); - AddButton( 20, y, 4005, 4007, ToButtonID( 3, i ), GumpButtonType.Reply, 0 ); - - y += 20; - - if ( i == 5 ) - y += 5; - } - - AddHtmlLocalized( 55, 310, 300, 20, 1011447, false, false ); // BACK - AddButton( 20, 310, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion - } - #endregion - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int type, index; - - if ( !FromButtonID( info.ButtonID, out type, out index ) ) - return; - - switch ( type ) - { - case 0: // general - { - switch ( index ) - { - case 0: // vote - { - m_From.SendGump( new ElectionGump( m_From, m_Faction.Election ) ); - break; - } - case 1: // leave - { - m_From.SendGump( new LeaveFactionGump( m_From, m_Faction ) ); - break; - } - } - - break; - } - case 1: // merchant title - { - if ( index >= 0 && index <= MerchantTitles.Info.Length ) - { - PlayerState pl = PlayerState.Find( m_From ); - - MerchantTitle newTitle = (MerchantTitle)index; - MerchantTitleInfo mti = MerchantTitles.GetInfo( newTitle ); - - if ( mti == null ) - { - m_From.SendLocalizedMessage( 1010120 ); // Your merchant title has been removed - - if ( pl != null ) - pl.MerchantTitle = newTitle; - } - else if ( MerchantTitles.IsQualified( m_From, mti ) ) - { - m_From.SendLocalizedMessage( mti.Assigned ); - - if ( pl != null ) - pl.MerchantTitle = newTitle; - } - } - - break; - } - case 2: // transfer silver - { - if ( !m_Faction.IsCommander( m_From ) ) - return; - - List towns = Town.Towns; - - if ( index >= 0 && index < towns.Count ) - { - Town town = towns[index]; - - if ( town.Owner == m_Faction ) - { - if ( m_Faction.Silver >= 10000 ) - { - m_Faction.Silver -= 10000; - town.Silver += 10000; - - // 10k in silver has been received by: - m_From.SendLocalizedMessage( 1042726, true, " " + town.Definition.FriendlyName ); - } - } - } - - break; - } - case 3: // change tithe - { - if ( !m_Faction.IsCommander( m_From ) ) - return; - - if ( index >= 0 && index <= 10 ) - m_Faction.Tithe = index*10; - - break; - } - } - } - } -} + AddHtmlLocalized(20, 30, 200, 20, 1011461, false, false); // COMMANDER OPTIONS + + AddHtmlLocalized(20, 70, 120, 20, 1011457, false, false); // Tithe rate : + if (faction.Tithe >= 0 && faction.Tithe <= 100 && faction.Tithe % 10 == 0) + AddHtmlLocalized(140, 70, 250, 20, 1011480 + faction.Tithe / 10, false, false); + else + AddHtml(140, 70, 250, 20, faction.Tithe + "%", false, false); + + AddHtmlLocalized(20, 100, 120, 20, 1011474, false, false); // Silver available : + AddHtml(140, 100, 50, 20, faction.Silver.ToString("N0"), false, false); // NOTE: Added 'N0' formatting + + AddHtmlLocalized(55, 130, 200, 20, 1011478, false, false); // CHANGE TITHE RATE + AddButton(20, 130, 4005, 4007, 0, GumpButtonType.Page, 8); + + AddHtmlLocalized(55, 160, 200, 20, 1018301, false, false); // TRANSFER SILVER + if (faction.Silver >= 10000) + AddButton(20, 160, 4005, 4007, 0, GumpButtonType.Page, 7); + else + AddImage(20, 160, 4020); + + AddHtmlLocalized(55, 310, 100, 20, 1011447, false, false); // BACK + AddButton(20, 310, 4005, 4007, 0, GumpButtonType.Page, 1); + + #endregion + + #region Town Finance + + if (faction.Silver >= 10000) + { + AddPage(7); + + AddHtmlLocalized(20, 30, 250, 20, 1011476, false, false); // TOWN FINANCE + + AddHtmlLocalized(20, 50, 400, 20, 1011477, false, false); // Select a town to transfer 10000 silver to + + for (int i = 0; i < towns.Count; ++i) + { + Town town = towns[i]; + + AddHtmlText(55, 75 + i * 30, 200, 20, town.Definition.TownName, false, false); + + if (town.Owner == faction) + AddButton(20, 75 + i * 30, 4005, 4007, ToButtonID(2, i), GumpButtonType.Reply, 0); + else + AddImage(20, 75 + i * 30, 4020); + } + + AddHtmlLocalized(55, 310, 100, 20, 1011447, false, false); // BACK + AddButton(20, 310, 4005, 4007, 0, GumpButtonType.Page, 1); + } + + #endregion + + #region Change Tithe Rate + + AddPage(8); + + AddHtmlLocalized(20, 30, 400, 20, 1011479, false, false); // Select the % for the new tithe rate + + int y = 55; + + for (int i = 0; i <= 10; ++i) + { + if (i == 5) + y += 5; + + AddHtmlLocalized(55, y, 300, 20, 1011480 + i, false, false); + AddButton(20, y, 4005, 4007, ToButtonID(3, i), GumpButtonType.Reply, 0); + + y += 20; + + if (i == 5) + y += 5; + } + + AddHtmlLocalized(55, 310, 300, 20, 1011447, false, false); // BACK + AddButton(20, 310, 4005, 4007, 0, GumpButtonType.Page, 1); + + #endregion + } + + #endregion + } + + public override int ButtonTypes => 4; + + public override void OnResponse(NetState sender, RelayInfo info) + { + int type, index; + + if (!FromButtonID(info.ButtonID, out type, out index)) + return; + + switch (type) + { + case 0: // general + { + switch (index) + { + case 0: // vote + { + m_From.SendGump(new ElectionGump(m_From, m_Faction.Election)); + break; + } + case 1: // leave + { + m_From.SendGump(new LeaveFactionGump(m_From, m_Faction)); + break; + } + } + + break; + } + case 1: // merchant title + { + if (index >= 0 && index <= MerchantTitles.Info.Length) + { + PlayerState pl = PlayerState.Find(m_From); + + MerchantTitle newTitle = (MerchantTitle)index; + MerchantTitleInfo mti = MerchantTitles.GetInfo(newTitle); + + if (mti == null) + { + m_From.SendLocalizedMessage(1010120); // Your merchant title has been removed + + if (pl != null) + pl.MerchantTitle = newTitle; + } + else if (MerchantTitles.IsQualified(m_From, mti)) + { + m_From.SendLocalizedMessage(mti.Assigned); + + if (pl != null) + pl.MerchantTitle = newTitle; + } + } + + break; + } + case 2: // transfer silver + { + if (!m_Faction.IsCommander(m_From)) + return; + + List towns = Town.Towns; + + if (index >= 0 && index < towns.Count) + { + Town town = towns[index]; + + if (town.Owner == m_Faction) + if (m_Faction.Silver >= 10000) + { + m_Faction.Silver -= 10000; + town.Silver += 10000; + + // 10k in silver has been received by: + m_From.SendLocalizedMessage(1042726, true, " " + town.Definition.FriendlyName); + } + } + + break; + } + case 3: // change tithe + { + if (!m_Faction.IsCommander(m_From)) + return; + + if (index >= 0 && index <= 10) + m_Faction.Tithe = index * 10; + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/FinanceGump.cs b/Scripts/Engines/Factions/Gumps/FinanceGump.cs index 7088c83c4..b4286d38b 100644 --- a/Scripts/Engines/Factions/Gumps/FinanceGump.cs +++ b/Scripts/Engines/Factions/Gumps/FinanceGump.cs @@ -1,278 +1,296 @@ using System; +using System.Collections.Generic; using Server.Gumps; using Server.Mobiles; using Server.Multis; using Server.Network; -using System.Collections.Generic; namespace Server.Factions { - public class FinanceGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; - private Town m_Town; + public class FinanceGump : FactionGump + { + private static int[] m_PriceOffsets = + { + -30, -25, -20, -15, -10, -5, + +50, +100, +150, +200, +250, +300 + }; - private static int[] m_PriceOffsets = { - -30, -25, -20, -15, -10, -5, - +50, +100, +150, +200, +250, +300 - }; + private Faction m_Faction; + private PlayerMobile m_From; + private Town m_Town; - public override int ButtonTypes => 2; + public FinanceGump(PlayerMobile from, Faction faction, Town town) : base(50, 50) + { + m_From = from; + m_Faction = faction; + m_Town = town; - public FinanceGump( PlayerMobile from, Faction faction, Town town ) : base( 50, 50 ) - { - m_From = from; - m_Faction = faction; - m_Town = town; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 320, 410, 5054); + AddBackground(10, 10, 300, 390, 3000); - AddBackground( 0, 0, 320, 410, 5054 ); - AddBackground( 10, 10, 300, 390, 3000 ); + #region General - #region General - AddPage( 1 ); + AddPage(1); - AddHtmlLocalized( 20, 30, 260, 25, 1011541, false, false ); // FINANCE MINISTER + AddHtmlLocalized(20, 30, 260, 25, 1011541, false, false); // FINANCE MINISTER - AddHtmlLocalized( 55, 90, 200, 25, 1011539, false, false ); // CHANGE PRICES - AddButton( 20, 90, 4005, 4007, 0, GumpButtonType.Page, 2 ); + AddHtmlLocalized(55, 90, 200, 25, 1011539, false, false); // CHANGE PRICES + AddButton(20, 90, 4005, 4007, 0, GumpButtonType.Page, 2); - AddHtmlLocalized( 55, 120, 200, 25, 1011540, false, false ); // BUY SHOPKEEPERS - AddButton( 20, 120, 4005, 4007, 0, GumpButtonType.Page, 3 ); + AddHtmlLocalized(55, 120, 200, 25, 1011540, false, false); // BUY SHOPKEEPERS + AddButton(20, 120, 4005, 4007, 0, GumpButtonType.Page, 3); - AddHtmlLocalized( 55, 150, 200, 25, 1011495, false, false ); // VIEW FINANCES - AddButton( 20, 150, 4005, 4007, 0, GumpButtonType.Page, 4 ); + AddHtmlLocalized(55, 150, 200, 25, 1011495, false, false); // VIEW FINANCES + AddButton(20, 150, 4005, 4007, 0, GumpButtonType.Page, 4); - AddHtmlLocalized( 55, 360, 200, 25, 1011441, false, false ); // EXIT - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - #endregion + AddHtmlLocalized(55, 360, 200, 25, 1011441, false, false); // EXIT + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Reply, 0); - #region Change Prices - AddPage( 2 ); + #endregion - AddHtmlLocalized( 20, 30, 200, 25, 1011539, false, false ); // CHANGE PRICES + #region Change Prices - for ( int i = 0; i < m_PriceOffsets.Length; ++i ) - { - int ofs = m_PriceOffsets[i]; + AddPage(2); - int x = 20 + ((i / 6) * 150); - int y = 90 + ((i % 6) * 30); + AddHtmlLocalized(20, 30, 200, 25, 1011539, false, false); // CHANGE PRICES - AddRadio( x, y, 208, 209, ( town.Tax == ofs ), i+1 ); + for (int i = 0; i < m_PriceOffsets.Length; ++i) + { + int ofs = m_PriceOffsets[i]; - if ( ofs < 0 ) - AddLabel( x + 35, y, 0x26, string.Concat( "- ", -ofs, "%" ) ); - else - AddLabel( x + 35, y, 0x12A, string.Concat( "+ ", ofs, "%" ) ); - } + int x = 20 + i / 6 * 150; + int y = 90 + i % 6 * 30; - AddRadio( 20, 270, 208, 209, ( town.Tax == 0 ), 0 ); - AddHtmlLocalized( 55, 270, 90, 25, 1011542, false, false ); // normal + AddRadio(x, y, 208, 209, town.Tax == ofs, i + 1); - AddHtmlLocalized( 55, 330, 200, 25, 1011509, false, false ); // Set Prices - AddButton( 20, 330, 4005, 4007, ToButtonID( 0, 0 ), GumpButtonType.Reply, 0 ); + if (ofs < 0) + AddLabel(x + 35, y, 0x26, string.Concat("- ", -ofs, "%")); + else + AddLabel(x + 35, y, 0x12A, string.Concat("+ ", ofs, "%")); + } - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + AddRadio(20, 270, 208, 209, town.Tax == 0, 0); + AddHtmlLocalized(55, 270, 90, 25, 1011542, false, false); // normal - #region Buy Shopkeepers - AddPage( 3 ); + AddHtmlLocalized(55, 330, 200, 25, 1011509, false, false); // Set Prices + AddButton(20, 330, 4005, 4007, ToButtonID(0, 0), GumpButtonType.Reply, 0); - AddHtmlLocalized( 20, 30, 200, 25, 1011540, false, false ); // BUY SHOPKEEPERS + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 1); - List vendorLists = town.VendorLists; + #endregion - for ( int i = 0; i < vendorLists.Count; ++i ) - { - VendorList list = vendorLists[i]; + #region Buy Shopkeepers - AddButton( 20, 90 + (i * 40), 4005, 4007, 0, GumpButtonType.Page, 5 + i ); - AddItem( 55, 90 + (i * 40), list.Definition.ItemID ); - AddHtmlText( 100, 90 + (i * 40), 200, 25, list.Definition.Label, false, false ); - } + AddPage(3); - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + AddHtmlLocalized(20, 30, 200, 25, 1011540, false, false); // BUY SHOPKEEPERS - #region View Finances - AddPage( 4 ); + List vendorLists = town.VendorLists; - int financeUpkeep = town.FinanceUpkeep; - int sheriffUpkeep = town.SheriffUpkeep; - int dailyIncome = town.DailyIncome; - int netCashFlow = town.NetCashFlow; + for (int i = 0; i < vendorLists.Count; ++i) + { + VendorList list = vendorLists[i]; + AddButton(20, 90 + i * 40, 4005, 4007, 0, GumpButtonType.Page, 5 + i); + AddItem(55, 90 + i * 40, list.Definition.ItemID); + AddHtmlText(100, 90 + i * 40, 200, 25, list.Definition.Label, false, false); + } - AddHtmlLocalized( 20, 30, 300, 25, 1011524, false, false ); // FINANCE STATEMENT + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 1); - AddHtmlLocalized( 20, 80, 300, 25, 1011538, false, false ); // Current total money for town : - AddLabel( 20, 100, 0x44, town.Silver.ToString() ); + #endregion - AddHtmlLocalized( 20, 130, 300, 25, 1011520, false, false ); // Finance Minister Upkeep : - AddLabel( 20, 150, 0x44, financeUpkeep.ToString( "N0" ) ); // NOTE: Added 'N0' + #region View Finances - AddHtmlLocalized( 20, 180, 300, 25, 1011521, false, false ); // Sheriff Upkeep : - AddLabel( 20, 200, 0x44, sheriffUpkeep.ToString( "N0" ) ); // NOTE: Added 'N0' + AddPage(4); - AddHtmlLocalized( 20, 230, 300, 25, 1011522, false, false ); // Town Income : - AddLabel( 20, 250, 0x44, dailyIncome.ToString( "N0" ) ); // NOTE: Added 'N0' + int financeUpkeep = town.FinanceUpkeep; + int sheriffUpkeep = town.SheriffUpkeep; + int dailyIncome = town.DailyIncome; + int netCashFlow = town.NetCashFlow; - AddHtmlLocalized( 20, 280, 300, 25, 1011523, false, false ); // Net Cash flow per day : - AddLabel( 20, 300, 0x44, netCashFlow.ToString( "N0" ) ); // NOTE: Added 'N0' - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + AddHtmlLocalized(20, 30, 300, 25, 1011524, false, false); // FINANCE STATEMENT - #region Shopkeeper Pages - for ( int i = 0; i < vendorLists.Count; ++i ) - { - VendorList vendorList = vendorLists[i]; + AddHtmlLocalized(20, 80, 300, 25, 1011538, false, false); // Current total money for town : + AddLabel(20, 100, 0x44, town.Silver.ToString()); - AddPage( 5 + i ); + AddHtmlLocalized(20, 130, 300, 25, 1011520, false, false); // Finance Minister Upkeep : + AddLabel(20, 150, 0x44, financeUpkeep.ToString("N0")); // NOTE: Added 'N0' - AddHtmlText( 60, 30, 300, 25, vendorList.Definition.Header, false, false ); - AddItem( 20, 30, vendorList.Definition.ItemID ); + AddHtmlLocalized(20, 180, 300, 25, 1011521, false, false); // Sheriff Upkeep : + AddLabel(20, 200, 0x44, sheriffUpkeep.ToString("N0")); // NOTE: Added 'N0' - AddHtmlLocalized( 20, 90, 200, 25, 1011514, false, false ); // You have : - AddLabel( 230, 90, 0x26, vendorList.Vendors.Count.ToString() ); + AddHtmlLocalized(20, 230, 300, 25, 1011522, false, false); // Town Income : + AddLabel(20, 250, 0x44, dailyIncome.ToString("N0")); // NOTE: Added 'N0' - AddHtmlLocalized( 20, 120, 200, 25, 1011515, false, false ); // Maximum : - AddLabel( 230, 120, 0x256, vendorList.Definition.Maximum.ToString() ); + AddHtmlLocalized(20, 280, 300, 25, 1011523, false, false); // Net Cash flow per day : + AddLabel(20, 300, 0x44, netCashFlow.ToString("N0")); // NOTE: Added 'N0' - AddHtmlLocalized( 20, 150, 200, 25, 1011516, false, false ); // Cost : - AddLabel( 230, 150, 0x44, vendorList.Definition.Price.ToString( "N0" ) ); // NOTE: Added 'N0' + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 1); - AddHtmlLocalized( 20, 180, 200, 25, 1011517, false, false ); // Daily Pay : - AddLabel( 230, 180, 0x37, vendorList.Definition.Upkeep.ToString( "N0" ) ); // NOTE: Added 'N0' + #endregion - AddHtmlLocalized( 20, 210, 200, 25, 1011518, false, false ); // Current Silver : - AddLabel( 230, 210, 0x44, town.Silver.ToString( "N0" ) ); // NOTE: Added 'N0' + #region Shopkeeper Pages - AddHtmlLocalized( 20, 240, 200, 25, 1011519, false, false ); // Current Payroll : - AddLabel( 230, 240, 0x44, financeUpkeep.ToString( "N0" ) ); // NOTE: Added 'N0' - - AddHtmlText( 55, 300, 200, 25, vendorList.Definition.Label, false, false ); - if ( town.Silver >= vendorList.Definition.Price ) - AddButton( 20, 300, 4005, 4007, ToButtonID( 1, i ), GumpButtonType.Reply, 0 ); - else - AddImage( 20, 300, 4020 ); - - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 3 ); - } - #endregion - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !m_Town.IsFinance( m_From ) || m_Town.Owner != m_Faction ) - { - m_From.SendLocalizedMessage( 1010339 ); // You no longer control this city - return; - } - - int type, index; - - if ( !FromButtonID( info.ButtonID, out type, out index ) ) - return; - - switch ( type ) - { - case 0: // general - { - switch ( index ) - { - case 0: // set price - { - int[] switches = info.Switches; - - if ( switches.Length == 0 ) - break; - - int opt = switches[0]; - int newTax = 0; - - if ( opt >= 1 && opt <= m_PriceOffsets.Length ) - newTax = m_PriceOffsets[opt - 1]; - - if ( m_Town.Tax == newTax ) - break; - - if ( m_From.AccessLevel == AccessLevel.Player && !m_Town.TaxChangeReady ) - { - TimeSpan remaining = DateTime.UtcNow - ( m_Town.LastTaxChange + Town.TaxChangePeriod ); - - if ( remaining.TotalMinutes < 4 ) - m_From.SendLocalizedMessage( 1042165 ); // You must wait a short while before changing prices again. - else if ( remaining.TotalMinutes < 10 ) - m_From.SendLocalizedMessage( 1042166 ); // You must wait several minutes before changing prices again. - else if ( remaining.TotalHours < 1 ) - m_From.SendLocalizedMessage( 1042167 ); // You must wait up to an hour before changing prices again. - else if ( remaining.TotalHours < 4 ) - m_From.SendLocalizedMessage( 1042168 ); // You must wait a few hours before changing prices again. - else - m_From.SendLocalizedMessage( 1042169 ); // You must wait several hours before changing prices again. - } - else - { - m_Town.Tax = newTax; - - if ( m_From.AccessLevel == AccessLevel.Player ) - m_Town.LastTaxChange = DateTime.UtcNow; - } - - break; - } - } - - break; - } - case 1: // make vendor - { - List vendorLists = m_Town.VendorLists; - - if ( index >= 0 && index < vendorLists.Count ) - { - VendorList vendorList = vendorLists[index]; - - Town town = Town.FromRegion( m_From.Region ); - - if ( Town.FromRegion( m_From.Region ) != m_Town ) - { - m_From.SendLocalizedMessage( 1010305 ); // You must be in your controlled city to buy Items - } - else if ( vendorList.Vendors.Count >= vendorList.Definition.Maximum ) - { - m_From.SendLocalizedMessage( 1010306 ); // You currently have too many of this enhancement type to place another - } - else if ( BaseBoat.FindBoatAt( m_From.Location, m_From.Map ) != null ) { - m_From.SendMessage( "You cannot place a vendor here" ); - } - else if ( m_Town.Silver >= vendorList.Definition.Price ) - { - BaseFactionVendor vendor = vendorList.Construct( m_Town, m_Faction ); - - if ( vendor != null ) - { - m_Town.Silver -= vendorList.Definition.Price; - - vendor.MoveToWorld( m_From.Location, m_From.Map ); - vendor.Home = vendor.Location; - } - } - } - - break; - } - } - } - } -} + for (int i = 0; i < vendorLists.Count; ++i) + { + VendorList vendorList = vendorLists[i]; + + AddPage(5 + i); + + AddHtmlText(60, 30, 300, 25, vendorList.Definition.Header, false, false); + AddItem(20, 30, vendorList.Definition.ItemID); + + AddHtmlLocalized(20, 90, 200, 25, 1011514, false, false); // You have : + AddLabel(230, 90, 0x26, vendorList.Vendors.Count.ToString()); + + AddHtmlLocalized(20, 120, 200, 25, 1011515, false, false); // Maximum : + AddLabel(230, 120, 0x256, vendorList.Definition.Maximum.ToString()); + + AddHtmlLocalized(20, 150, 200, 25, 1011516, false, false); // Cost : + AddLabel(230, 150, 0x44, vendorList.Definition.Price.ToString("N0")); // NOTE: Added 'N0' + + AddHtmlLocalized(20, 180, 200, 25, 1011517, false, false); // Daily Pay : + AddLabel(230, 180, 0x37, vendorList.Definition.Upkeep.ToString("N0")); // NOTE: Added 'N0' + + AddHtmlLocalized(20, 210, 200, 25, 1011518, false, false); // Current Silver : + AddLabel(230, 210, 0x44, town.Silver.ToString("N0")); // NOTE: Added 'N0' + + AddHtmlLocalized(20, 240, 200, 25, 1011519, false, false); // Current Payroll : + AddLabel(230, 240, 0x44, financeUpkeep.ToString("N0")); // NOTE: Added 'N0' + + AddHtmlText(55, 300, 200, 25, vendorList.Definition.Label, false, false); + if (town.Silver >= vendorList.Definition.Price) + AddButton(20, 300, 4005, 4007, ToButtonID(1, i), GumpButtonType.Reply, 0); + else + AddImage(20, 300, 4020); + + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 3); + } + + #endregion + } + + public override int ButtonTypes => 2; + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_Town.IsFinance(m_From) || m_Town.Owner != m_Faction) + { + m_From.SendLocalizedMessage(1010339); // You no longer control this city + return; + } + + int type, index; + + if (!FromButtonID(info.ButtonID, out type, out index)) + return; + + switch (type) + { + case 0: // general + { + switch (index) + { + case 0: // set price + { + int[] switches = info.Switches; + + if (switches.Length == 0) + break; + + int opt = switches[0]; + int newTax = 0; + + if (opt >= 1 && opt <= m_PriceOffsets.Length) + newTax = m_PriceOffsets[opt - 1]; + + if (m_Town.Tax == newTax) + break; + + if (m_From.AccessLevel == AccessLevel.Player && !m_Town.TaxChangeReady) + { + TimeSpan remaining = DateTime.UtcNow - (m_Town.LastTaxChange + Town.TaxChangePeriod); + + if (remaining.TotalMinutes < 4) + m_From.SendLocalizedMessage( + 1042165); // You must wait a short while before changing prices again. + else if (remaining.TotalMinutes < 10) + m_From.SendLocalizedMessage( + 1042166); // You must wait several minutes before changing prices again. + else if (remaining.TotalHours < 1) + m_From.SendLocalizedMessage( + 1042167); // You must wait up to an hour before changing prices again. + else if (remaining.TotalHours < 4) + m_From.SendLocalizedMessage( + 1042168); // You must wait a few hours before changing prices again. + else + m_From.SendLocalizedMessage( + 1042169); // You must wait several hours before changing prices again. + } + else + { + m_Town.Tax = newTax; + + if (m_From.AccessLevel == AccessLevel.Player) + m_Town.LastTaxChange = DateTime.UtcNow; + } + + break; + } + } + + break; + } + case 1: // make vendor + { + List vendorLists = m_Town.VendorLists; + + if (index >= 0 && index < vendorLists.Count) + { + VendorList vendorList = vendorLists[index]; + + Town town = Town.FromRegion(m_From.Region); + + if (Town.FromRegion(m_From.Region) != m_Town) + { + m_From.SendLocalizedMessage(1010305); // You must be in your controlled city to buy Items + } + else if (vendorList.Vendors.Count >= vendorList.Definition.Maximum) + { + m_From.SendLocalizedMessage( + 1010306); // You currently have too many of this enhancement type to place another + } + else if (BaseBoat.FindBoatAt(m_From.Location, m_From.Map) != null) + { + m_From.SendMessage("You cannot place a vendor here"); + } + else if (m_Town.Silver >= vendorList.Definition.Price) + { + BaseFactionVendor vendor = vendorList.Construct(m_Town, m_Faction); + + if (vendor != null) + { + m_Town.Silver -= vendorList.Definition.Price; + + vendor.MoveToWorld(m_From.Location, m_From.Map); + vendor.Home = vendor.Location; + } + } + } + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/HorseBreederGump.cs b/Scripts/Engines/Factions/Gumps/HorseBreederGump.cs index 3eee779bf..513fb6001 100644 --- a/Scripts/Engines/Factions/Gumps/HorseBreederGump.cs +++ b/Scripts/Engines/Factions/Gumps/HorseBreederGump.cs @@ -1,90 +1,91 @@ -using Server.Items; using Server.Gumps; +using Server.Items; using Server.Mobiles; using Server.Network; namespace Server.Factions { - public class HorseBreederGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; + public class HorseBreederGump : FactionGump + { + private Faction m_Faction; + private PlayerMobile m_From; - public HorseBreederGump( PlayerMobile from, Faction faction ) : base( 20, 30 ) - { - m_From = from; - m_Faction = faction; + public HorseBreederGump(PlayerMobile from, Faction faction) : base(20, 30) + { + m_From = from; + m_Faction = faction; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 320, 280, 5054 ); - AddBackground( 10, 10, 300, 260, 3000 ); + AddBackground(0, 0, 320, 280, 5054); + AddBackground(10, 10, 300, 260, 3000); - AddHtmlText( 20, 30, 300, 25, faction.Definition.Header, false, false ); + AddHtmlText(20, 30, 300, 25, faction.Definition.Header, false, false); - AddHtmlLocalized( 20, 60, 300, 25, 1018306, false, false ); // Purchase a Faction War Horse - AddItem( 70, 120, 0x3FFE ); + AddHtmlLocalized(20, 60, 300, 25, 1018306, false, false); // Purchase a Faction War Horse + AddItem(70, 120, 0x3FFE); - AddItem( 150, 120, 0xEF2 ); - AddLabel( 190, 122, 0x3E3, FactionWarHorse.SilverPrice.ToString( "N0" ) ); // NOTE: Added 'N0' + AddItem(150, 120, 0xEF2); + AddLabel(190, 122, 0x3E3, FactionWarHorse.SilverPrice.ToString("N0")); // NOTE: Added 'N0' - AddItem( 150, 150, 0xEEF ); - AddLabel( 190, 152, 0x3E3, FactionWarHorse.GoldPrice.ToString( "N0" ) ); // NOTE: Added 'N0' + AddItem(150, 150, 0xEEF); + AddLabel(190, 152, 0x3E3, FactionWarHorse.GoldPrice.ToString("N0")); // NOTE: Added 'N0' - AddHtmlLocalized( 55, 210, 200, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 210, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 210, 200, 25, 1011011, false, false); // CONTINUE + AddButton(20, 210, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 240, 200, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 240, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(55, 240, 200, 25, 1011012, false, false); // CANCEL + AddButton(20, 240, 4005, 4007, 0, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID != 1 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID != 1) + return; - if ( Faction.Find( m_From ) != m_Faction ) - return; + if (Faction.Find(m_From) != m_Faction) + return; - Container pack = m_From.Backpack; + Container pack = m_From.Backpack; - if ( pack == null ) - return; + if (pack == null) + return; - FactionWarHorse horse = new FactionWarHorse( m_Faction ); + FactionWarHorse horse = new FactionWarHorse(m_Faction); - if ( (m_From.Followers + horse.ControlSlots) > m_From.FollowersMax ) - { - // TODO: Message? - horse.Delete(); - } - else - { - if ( pack.GetAmount( typeof( Silver ) ) < FactionWarHorse.SilverPrice ) - { - sender.Mobile.SendLocalizedMessage( 1042204 ); // You do not have enough silver. - horse.Delete(); - } - else if ( pack.GetAmount( typeof( Gold ) ) < FactionWarHorse.GoldPrice ) - { - sender.Mobile.SendLocalizedMessage( 1042205 ); // You do not have enough gold. - horse.Delete(); - } - else if ( pack.ConsumeTotal( typeof( Silver ), FactionWarHorse.SilverPrice ) && pack.ConsumeTotal( typeof( Gold ), FactionWarHorse.GoldPrice ) ) - { - horse.Controlled = true; - horse.ControlMaster = m_From; + if (m_From.Followers + horse.ControlSlots > m_From.FollowersMax) + { + // TODO: Message? + horse.Delete(); + } + else + { + if (pack.GetAmount(typeof(Silver)) < FactionWarHorse.SilverPrice) + { + sender.Mobile.SendLocalizedMessage(1042204); // You do not have enough silver. + horse.Delete(); + } + else if (pack.GetAmount(typeof(Gold)) < FactionWarHorse.GoldPrice) + { + sender.Mobile.SendLocalizedMessage(1042205); // You do not have enough gold. + horse.Delete(); + } + else if (pack.ConsumeTotal(typeof(Silver), FactionWarHorse.SilverPrice) && + pack.ConsumeTotal(typeof(Gold), FactionWarHorse.GoldPrice)) + { + horse.Controlled = true; + horse.ControlMaster = m_From; - horse.ControlOrder = OrderType.Follow; - horse.ControlTarget = m_From; + horse.ControlOrder = OrderType.Follow; + horse.ControlTarget = m_From; - horse.MoveToWorld( m_From.Location, m_From.Map ); - } - else - { - horse.Delete(); - } - } - } - } + horse.MoveToWorld(m_From.Location, m_From.Map); + } + else + { + horse.Delete(); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/JoinStoneGump.cs b/Scripts/Engines/Factions/Gumps/JoinStoneGump.cs index cc2365b1c..c53811756 100644 --- a/Scripts/Engines/Factions/Gumps/JoinStoneGump.cs +++ b/Scripts/Engines/Factions/Gumps/JoinStoneGump.cs @@ -4,47 +4,47 @@ using Server.Network; namespace Server.Factions { - public class JoinStoneGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; + public class JoinStoneGump : FactionGump + { + private Faction m_Faction; + private PlayerMobile m_From; - public JoinStoneGump( PlayerMobile from, Faction faction ) : base( 20, 30 ) - { - m_From = from; - m_Faction = faction; + public JoinStoneGump(PlayerMobile from, Faction faction) : base(20, 30) + { + m_From = from; + m_Faction = faction; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 550, 440, 5054 ); - AddBackground( 10, 10, 530, 420, 3000 ); + AddBackground(0, 0, 550, 440, 5054); + AddBackground(10, 10, 530, 420, 3000); - AddHtmlText( 20, 30, 510, 20, faction.Definition.Header, false, false ); - AddHtmlText( 20, 130, 510, 100, faction.Definition.About, true, true ); + AddHtmlText(20, 30, 510, 20, faction.Definition.Header, false, false); + AddHtmlText(20, 130, 510, 100, faction.Definition.About, true, true); - AddHtmlLocalized( 20, 60, 100, 20, 1011429, false, false ); // Led By : - AddHtml( 125, 60, 200, 20, faction.Commander != null ? faction.Commander.Name : "Nobody", false, false ); + AddHtmlLocalized(20, 60, 100, 20, 1011429, false, false); // Led By : + AddHtml(125, 60, 200, 20, faction.Commander != null ? faction.Commander.Name : "Nobody", false, false); - AddHtmlLocalized( 20, 80, 100, 20, 1011457, false, false ); // Tithe rate : - if ( faction.Tithe >= 0 && faction.Tithe <= 100 && (faction.Tithe % 10) == 0 ) - AddHtmlLocalized( 125, 80, 350, 20, 1011480 + (faction.Tithe / 10), false, false ); - else - AddHtml( 125, 80, 350, 20, faction.Tithe + "%", false, false ); + AddHtmlLocalized(20, 80, 100, 20, 1011457, false, false); // Tithe rate : + if (faction.Tithe >= 0 && faction.Tithe <= 100 && faction.Tithe % 10 == 0) + AddHtmlLocalized(125, 80, 350, 20, 1011480 + faction.Tithe / 10, false, false); + else + AddHtml(125, 80, 350, 20, faction.Tithe + "%", false, false); - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 200, 20, 1011425, false, false ); // JOIN THIS FACTION + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 200, 20, 1011425, false, false); // JOIN THIS FACTION - AddButton( 300, 400, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 200, 20, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 200, 20, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Faction.OnJoinAccepted( m_From ); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_Faction.OnJoinAccepted(m_From); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/LeaveFactionGump.cs b/Scripts/Engines/Factions/Gumps/LeaveFactionGump.cs index 6e15e83f1..db5d67b56 100644 --- a/Scripts/Engines/Factions/Gumps/LeaveFactionGump.cs +++ b/Scripts/Engines/Factions/Gumps/LeaveFactionGump.cs @@ -1,89 +1,93 @@ using System; -using Server.Gumps; using Server.Guilds; +using Server.Gumps; using Server.Mobiles; using Server.Network; namespace Server.Factions { - public class LeaveFactionGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; + public class LeaveFactionGump : FactionGump + { + private Faction m_Faction; + private PlayerMobile m_From; - public LeaveFactionGump( PlayerMobile from, Faction faction ) : base( 20, 30 ) - { - m_From = from; - m_Faction = faction; + public LeaveFactionGump(PlayerMobile from, Faction faction) : base(20, 30) + { + m_From = from; + m_Faction = faction; - AddBackground( 0, 0, 270, 120, 5054 ); - AddBackground( 10, 10, 250, 100, 3000 ); + AddBackground(0, 0, 270, 120, 5054); + AddBackground(10, 10, 250, 100, 3000); - if ( from.Guild is Guild guild && guild.Leader == from ) - AddHtmlLocalized( 20, 15, 230, 60, 1018057, true, true ); // Are you sure you want your entire guild to leave this faction? - else - AddHtmlLocalized( 20, 15, 230, 60, 1018063, true, true ); // Are you sure you want to leave this faction? + if (from.Guild is Guild guild && guild.Leader == from) + AddHtmlLocalized(20, 15, 230, 60, 1018057, true, + true); // Are you sure you want your entire guild to leave this faction? + else + AddHtmlLocalized(20, 15, 230, 60, 1018063, true, true); // Are you sure you want to leave this faction? - AddHtmlLocalized( 55, 80, 75, 20, 1011011, false, false ); // CONTINUE - AddButton( 20, 80, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 80, 75, 20, 1011011, false, false); // CONTINUE + AddButton(20, 80, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 170, 80, 75, 20, 1011012, false, false ); // CANCEL - AddButton( 135, 80, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(170, 80, 75, 20, 1011012, false, false); // CANCEL + AddButton(135, 80, 4005, 4007, 2, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 1: // continue - { - if ( !(m_From.Guild is Guild guild) ) - { - PlayerState pl = PlayerState.Find( m_From ); + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: // continue + { + if (!(m_From.Guild is Guild guild)) + { + PlayerState pl = PlayerState.Find(m_From); - if ( pl != null ) - { - pl.Leaving = DateTime.UtcNow; + if (pl != null) + { + pl.Leaving = DateTime.UtcNow; - if ( Faction.LeavePeriod == TimeSpan.FromDays( 3.0 ) ) - m_From.SendLocalizedMessage( 1005065 ); // You will be removed from the faction in 3 days - else - m_From.SendMessage( "You will be removed from the faction in {0} days.", Faction.LeavePeriod.TotalDays ); - } - } - else if ( guild.Leader != m_From ) - { - m_From.SendLocalizedMessage( 1005061 ); // You cannot quit the faction because you are not the guild master - } - else - { - m_From.SendLocalizedMessage( 1042285 ); // Your guild is now quitting the faction. + if (Faction.LeavePeriod == TimeSpan.FromDays(3.0)) + m_From.SendLocalizedMessage(1005065); // You will be removed from the faction in 3 days + else + m_From.SendMessage("You will be removed from the faction in {0} days.", + Faction.LeavePeriod.TotalDays); + } + } + else if (guild.Leader != m_From) + { + m_From.SendLocalizedMessage( + 1005061); // You cannot quit the faction because you are not the guild master + } + else + { + m_From.SendLocalizedMessage(1042285); // Your guild is now quitting the faction. - for ( int i = 0; i < guild.Members.Count; ++i ) - { - Mobile mob = (Mobile) guild.Members[i]; - PlayerState pl = PlayerState.Find( mob ); + for (int i = 0; i < guild.Members.Count; ++i) + { + Mobile mob = guild.Members[i]; + PlayerState pl = PlayerState.Find(mob); - if ( pl != null ) - { - pl.Leaving = DateTime.UtcNow; + if (pl != null) + { + pl.Leaving = DateTime.UtcNow; - if ( Faction.LeavePeriod == TimeSpan.FromDays( 3.0 ) ) - mob.SendLocalizedMessage( 1005060 ); // Your guild will quit the faction in 3 days - else - mob.SendMessage( "Your guild will quit the faction in {0} days.", Faction.LeavePeriod.TotalDays ); - } - } - } + if (Faction.LeavePeriod == TimeSpan.FromDays(3.0)) + mob.SendLocalizedMessage(1005060); // Your guild will quit the faction in 3 days + else + mob.SendMessage("Your guild will quit the faction in {0} days.", + Faction.LeavePeriod.TotalDays); + } + } + } - break; - } - case 2: // cancel - { - m_From.SendLocalizedMessage( 500737 ); // Canceled resignation. - break; - } - } - } - } -} + break; + } + case 2: // cancel + { + m_From.SendLocalizedMessage(500737); // Canceled resignation. + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/SheriffGump.cs b/Scripts/Engines/Factions/Gumps/SheriffGump.cs index 7b223f768..c1ab3ed7d 100644 --- a/Scripts/Engines/Factions/Gumps/SheriffGump.cs +++ b/Scripts/Engines/Factions/Gumps/SheriffGump.cs @@ -1,179 +1,189 @@ +using System.Collections.Generic; using Server.Gumps; using Server.Mobiles; using Server.Multis; using Server.Network; -using System.Collections.Generic; namespace Server.Factions { - public class SheriffGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; - private Town m_Town; + public class SheriffGump : FactionGump + { + private Faction m_Faction; + private PlayerMobile m_From; + private Town m_Town; - private void CenterItem( int itemID, int x, int y, int w, int h ) - { - Rectangle2D rc = ItemBounds.Table[itemID]; - AddItem( x + ((w - rc.Width) / 2) - rc.X, y + ((h - rc.Height) / 2) - rc.Y, itemID ); - } - - public SheriffGump( PlayerMobile from, Faction faction, Town town ) : base( 50, 50 ) - { - m_From = from; - m_Faction = faction; - m_Town = town; + public SheriffGump(PlayerMobile from, Faction faction, Town town) : base(50, 50) + { + m_From = from; + m_Faction = faction; + m_Town = town; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 320, 410, 5054 ); - AddBackground( 10, 10, 300, 390, 3000 ); + AddBackground(0, 0, 320, 410, 5054); + AddBackground(10, 10, 300, 390, 3000); - #region General - AddPage( 1 ); + #region General - AddHtmlLocalized( 20, 30, 260, 25, 1011431, false, false ); // Sheriff + AddPage(1); - AddHtmlLocalized( 55, 90, 200, 25, 1011494, false, false ); // HIRE GUARDS - AddButton( 20, 90, 4005, 4007, 0, GumpButtonType.Page, 3 ); + AddHtmlLocalized(20, 30, 260, 25, 1011431, false, false); // Sheriff - AddHtmlLocalized( 55, 120, 200, 25, 1011495, false, false ); // VIEW FINANCES - AddButton( 20, 120, 4005, 4007, 0, GumpButtonType.Page, 2 ); + AddHtmlLocalized(55, 90, 200, 25, 1011494, false, false); // HIRE GUARDS + AddButton(20, 90, 4005, 4007, 0, GumpButtonType.Page, 3); - AddHtmlLocalized( 55, 360, 200, 25, 1011441, false, false ); // Exit - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - #endregion + AddHtmlLocalized(55, 120, 200, 25, 1011495, false, false); // VIEW FINANCES + AddButton(20, 120, 4005, 4007, 0, GumpButtonType.Page, 2); - #region Finances - AddPage( 2 ); + AddHtmlLocalized(55, 360, 200, 25, 1011441, false, false); // Exit + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Reply, 0); - int financeUpkeep = town.FinanceUpkeep; - int sheriffUpkeep = town.SheriffUpkeep; - int dailyIncome = town.DailyIncome; - int netCashFlow = town.NetCashFlow; + #endregion - AddHtmlLocalized( 20, 30, 300, 25, 1011524, false, false ); // FINANCE STATEMENT - - AddHtmlLocalized( 20, 80, 300, 25, 1011538, false, false ); // Current total money for town : - AddLabel( 20, 100, 0x44, town.Silver.ToString( "N0" ) ); // NOTE: Added 'N0' + #region Finances - AddHtmlLocalized( 20, 130, 300, 25, 1011520, false, false ); // Finance Minister Upkeep : - AddLabel( 20, 150, 0x44, financeUpkeep.ToString( "N0" ) ); // NOTE: Added 'N0' - - AddHtmlLocalized( 20, 180, 300, 25, 1011521, false, false ); // Sheriff Upkeep : - AddLabel( 20, 200, 0x44, sheriffUpkeep.ToString( "N0" ) ); // NOTE: Added 'N0' + AddPage(2); - AddHtmlLocalized( 20, 230, 300, 25, 1011522, false, false ); // Town Income : - AddLabel( 20, 250, 0x44, dailyIncome.ToString( "N0" ) ); // NOTE: Added 'N0' + int financeUpkeep = town.FinanceUpkeep; + int sheriffUpkeep = town.SheriffUpkeep; + int dailyIncome = town.DailyIncome; + int netCashFlow = town.NetCashFlow; - AddHtmlLocalized( 20, 280, 300, 25, 1011523, false, false ); // Net Cash flow per day : - AddLabel( 20, 300, 0x44, netCashFlow.ToString( "N0" ) ); // NOTE: Added 'N0' + AddHtmlLocalized(20, 30, 300, 25, 1011524, false, false); // FINANCE STATEMENT - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + AddHtmlLocalized(20, 80, 300, 25, 1011538, false, false); // Current total money for town : + AddLabel(20, 100, 0x44, town.Silver.ToString("N0")); // NOTE: Added 'N0' - #region Hire Guards - AddPage( 3 ); + AddHtmlLocalized(20, 130, 300, 25, 1011520, false, false); // Finance Minister Upkeep : + AddLabel(20, 150, 0x44, financeUpkeep.ToString("N0")); // NOTE: Added 'N0' - AddHtmlLocalized( 20, 30, 300, 25, 1011494, false, false ); // HIRE GUARDS + AddHtmlLocalized(20, 180, 300, 25, 1011521, false, false); // Sheriff Upkeep : + AddLabel(20, 200, 0x44, sheriffUpkeep.ToString("N0")); // NOTE: Added 'N0' - List guardLists = town.GuardLists; + AddHtmlLocalized(20, 230, 300, 25, 1011522, false, false); // Town Income : + AddLabel(20, 250, 0x44, dailyIncome.ToString("N0")); // NOTE: Added 'N0' - for ( int i = 0; i < guardLists.Count; ++i ) - { - GuardList guardList = guardLists[i]; - int y = 90 + (i * 60); + AddHtmlLocalized(20, 280, 300, 25, 1011523, false, false); // Net Cash flow per day : + AddLabel(20, 300, 0x44, netCashFlow.ToString("N0")); // NOTE: Added 'N0' - AddButton( 20, y, 4005, 4007, 0, GumpButtonType.Page, 4 + i ); - CenterItem( guardList.Definition.ItemID, 50, y - 20, 70, 60 ); - AddHtmlText( 120, y, 200, 25, guardList.Definition.Header, false, false ); - } + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 1); - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 1 ); - #endregion + #endregion - #region Guard Pages - for ( int i = 0; i < guardLists.Count; ++i ) - { - GuardList guardList = guardLists[i]; + #region Hire Guards - AddPage( 4 + i ); + AddPage(3); - AddHtmlText( 90, 30, 300, 25, guardList.Definition.Header, false, false ); - CenterItem( guardList.Definition.ItemID, 10, 10, 80, 80 ); + AddHtmlLocalized(20, 30, 300, 25, 1011494, false, false); // HIRE GUARDS - AddHtmlLocalized( 20, 90, 200, 25, 1011514, false, false ); // You have : - AddLabel( 230, 90, 0x26, guardList.Guards.Count.ToString() ); + List guardLists = town.GuardLists; - AddHtmlLocalized( 20, 120, 200, 25, 1011515, false, false ); // Maximum : - AddLabel( 230, 120, 0x12A, guardList.Definition.Maximum.ToString() ); + for (int i = 0; i < guardLists.Count; ++i) + { + GuardList guardList = guardLists[i]; + int y = 90 + i * 60; - AddHtmlLocalized( 20, 150, 200, 25, 1011516, false, false ); // Cost : - AddLabel( 230, 150, 0x44, guardList.Definition.Price.ToString( "N0" ) ); // NOTE: Added 'N0' + AddButton(20, y, 4005, 4007, 0, GumpButtonType.Page, 4 + i); + CenterItem(guardList.Definition.ItemID, 50, y - 20, 70, 60); + AddHtmlText(120, y, 200, 25, guardList.Definition.Header, false, false); + } - AddHtmlLocalized( 20, 180, 200, 25, 1011517, false, false ); // Daily Pay : - AddLabel( 230, 180, 0x37, guardList.Definition.Upkeep.ToString( "N0" ) ); // NOTE: Added 'N0' + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 1); - AddHtmlLocalized( 20, 210, 200, 25, 1011518, false, false ); // Current Silver : - AddLabel( 230, 210, 0x44, town.Silver.ToString( "N0" ) ); // NOTE: Added 'N0' + #endregion - AddHtmlLocalized( 20, 240, 200, 25, 1011519, false, false ); // Current Payroll : - AddLabel( 230, 240, 0x44, sheriffUpkeep.ToString( "N0" ) ); // NOTE: Added 'N0' + #region Guard Pages - AddHtmlText( 55, 300, 200, 25, guardList.Definition.Label, false, false ); - AddButton( 20, 300, 4005, 4007, 1 + i, GumpButtonType.Reply, 0 ); + for (int i = 0; i < guardLists.Count; ++i) + { + GuardList guardList = guardLists[i]; - AddHtmlLocalized( 55, 360, 200, 25, 1011067, false, false ); // Previous page - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Page, 3 ); - } - #endregion - } + AddPage(4 + i); - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !m_Town.IsSheriff( m_From ) || m_Town.Owner != m_Faction ) - { - m_From.SendLocalizedMessage( 1010339 ); // You no longer control this city - return; - } + AddHtmlText(90, 30, 300, 25, guardList.Definition.Header, false, false); + CenterItem(guardList.Definition.ItemID, 10, 10, 80, 80); - int index = info.ButtonID - 1; + AddHtmlLocalized(20, 90, 200, 25, 1011514, false, false); // You have : + AddLabel(230, 90, 0x26, guardList.Guards.Count.ToString()); - if ( index >= 0 && index < m_Town.GuardLists.Count ) - { - GuardList guardList = m_Town.GuardLists[index]; - Town town = Town.FromRegion( m_From.Region ); + AddHtmlLocalized(20, 120, 200, 25, 1011515, false, false); // Maximum : + AddLabel(230, 120, 0x12A, guardList.Definition.Maximum.ToString()); - if ( Town.FromRegion( m_From.Region ) != m_Town ) - { - m_From.SendLocalizedMessage( 1010305 ); // You must be in your controlled city to buy Items - } - else if ( guardList.Guards.Count >= guardList.Definition.Maximum ) - { - m_From.SendLocalizedMessage( 1010306 ); // You currently have too many of this enhancement type to place another - } - else if ( BaseBoat.FindBoatAt( m_From.Location, m_From.Map ) != null ) { - m_From.SendMessage( "You cannot place a guard here" ); - } - else if ( m_Town.Silver >= guardList.Definition.Price ) - { - BaseFactionGuard guard = guardList.Construct(); + AddHtmlLocalized(20, 150, 200, 25, 1011516, false, false); // Cost : + AddLabel(230, 150, 0x44, guardList.Definition.Price.ToString("N0")); // NOTE: Added 'N0' - if ( guard != null ) - { - guard.Faction = m_Faction; - guard.Town = m_Town; + AddHtmlLocalized(20, 180, 200, 25, 1011517, false, false); // Daily Pay : + AddLabel(230, 180, 0x37, guardList.Definition.Upkeep.ToString("N0")); // NOTE: Added 'N0' - m_Town.Silver -= guardList.Definition.Price; + AddHtmlLocalized(20, 210, 200, 25, 1011518, false, false); // Current Silver : + AddLabel(230, 210, 0x44, town.Silver.ToString("N0")); // NOTE: Added 'N0' - guard.MoveToWorld( m_From.Location, m_From.Map ); - guard.Home = guard.Location; - } - } - } - } - } + AddHtmlLocalized(20, 240, 200, 25, 1011519, false, false); // Current Payroll : + AddLabel(230, 240, 0x44, sheriffUpkeep.ToString("N0")); // NOTE: Added 'N0' + + AddHtmlText(55, 300, 200, 25, guardList.Definition.Label, false, false); + AddButton(20, 300, 4005, 4007, 1 + i, GumpButtonType.Reply, 0); + + AddHtmlLocalized(55, 360, 200, 25, 1011067, false, false); // Previous page + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Page, 3); + } + + #endregion + } + + private void CenterItem(int itemID, int x, int y, int w, int h) + { + Rectangle2D rc = ItemBounds.Table[itemID]; + AddItem(x + (w - rc.Width) / 2 - rc.X, y + (h - rc.Height) / 2 - rc.Y, itemID); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_Town.IsSheriff(m_From) || m_Town.Owner != m_Faction) + { + m_From.SendLocalizedMessage(1010339); // You no longer control this city + return; + } + + int index = info.ButtonID - 1; + + if (index >= 0 && index < m_Town.GuardLists.Count) + { + GuardList guardList = m_Town.GuardLists[index]; + Town town = Town.FromRegion(m_From.Region); + + if (Town.FromRegion(m_From.Region) != m_Town) + { + m_From.SendLocalizedMessage(1010305); // You must be in your controlled city to buy Items + } + else if (guardList.Guards.Count >= guardList.Definition.Maximum) + { + m_From.SendLocalizedMessage( + 1010306); // You currently have too many of this enhancement type to place another + } + else if (BaseBoat.FindBoatAt(m_From.Location, m_From.Map) != null) + { + m_From.SendMessage("You cannot place a guard here"); + } + else if (m_Town.Silver >= guardList.Definition.Price) + { + BaseFactionGuard guard = guardList.Construct(); + + if (guard != null) + { + guard.Faction = m_Faction; + guard.Town = m_Town; + + m_Town.Silver -= guardList.Definition.Price; + + guard.MoveToWorld(m_From.Location, m_From.Map); + guard.Home = guard.Location; + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/TownStoneGump.cs b/Scripts/Engines/Factions/Gumps/TownStoneGump.cs index 123e07136..2e78f0c41 100644 --- a/Scripts/Engines/Factions/Gumps/TownStoneGump.cs +++ b/Scripts/Engines/Factions/Gumps/TownStoneGump.cs @@ -5,198 +5,200 @@ using Server.Targeting; namespace Server.Factions { - public class TownStoneGump : FactionGump - { - private PlayerMobile m_From; - private Faction m_Faction; - private Town m_Town; + public class TownStoneGump : FactionGump + { + private Faction m_Faction; + private PlayerMobile m_From; + private Town m_Town; - public TownStoneGump( PlayerMobile from, Faction faction, Town town ) : base( 50, 50 ) - { - m_From = from; - m_Faction = faction; - m_Town = town; + public TownStoneGump(PlayerMobile from, Faction faction, Town town) : base(50, 50) + { + m_From = from; + m_Faction = faction; + m_Town = town; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 320, 250, 5054 ); - AddBackground( 10, 10, 300, 230, 3000 ); + AddBackground(0, 0, 320, 250, 5054); + AddBackground(10, 10, 300, 230, 3000); - AddHtmlText( 25, 30, 250, 25, town.Definition.TownStoneHeader, false, false ); + AddHtmlText(25, 30, 250, 25, town.Definition.TownStoneHeader, false, false); - AddHtmlLocalized( 55, 60, 150, 25, 1011557, false, false ); // Hire Sheriff - AddButton( 20, 60, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 60, 150, 25, 1011557, false, false); // Hire Sheriff + AddButton(20, 60, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 90, 150, 25, 1011559, false, false ); // Hire Finance Minister - AddButton( 20, 90, 4005, 4007, 2, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 90, 150, 25, 1011559, false, false); // Hire Finance Minister + AddButton(20, 90, 4005, 4007, 2, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 120, 150, 25, 1011558, false, false ); // Fire Sheriff - AddButton( 20, 120, 4005, 4007, 3, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 120, 150, 25, 1011558, false, false); // Fire Sheriff + AddButton(20, 120, 4005, 4007, 3, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 150, 150, 25, 1011560, false, false ); // Fire Finance Minister - AddButton( 20, 150, 4005, 4007, 4, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 150, 150, 25, 1011560, false, false); // Fire Finance Minister + AddButton(20, 150, 4005, 4007, 4, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 210, 150, 25, 1011441, false, false ); // EXIT - AddButton( 20, 210, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(55, 210, 150, 25, 1011441, false, false); // EXIT + AddButton(20, 210, 4005, 4007, 0, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Town.Owner != m_Faction || !m_Faction.IsCommander( m_From ) ) - { - m_From.SendLocalizedMessage( 1010339 ); // You no longer control this city - return; - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Town.Owner != m_Faction || !m_Faction.IsCommander(m_From)) + { + m_From.SendLocalizedMessage(1010339); // You no longer control this city + return; + } - switch ( info.ButtonID ) - { - case 1: // hire sheriff - { - if ( m_Town.Sheriff != null ) - { - m_From.SendLocalizedMessage( 1010342 ); // You must fire your Sheriff before you can elect a new one - } - else - { - m_From.SendLocalizedMessage( 1010347 ); // Who shall be your new sheriff - m_From.BeginTarget( 12, false, TargetFlags.None, HireSheriff_OnTarget ); - } + switch (info.ButtonID) + { + case 1: // hire sheriff + { + if (m_Town.Sheriff != null) + { + m_From.SendLocalizedMessage(1010342); // You must fire your Sheriff before you can elect a new one + } + else + { + m_From.SendLocalizedMessage(1010347); // Who shall be your new sheriff + m_From.BeginTarget(12, false, TargetFlags.None, HireSheriff_OnTarget); + } - break; - } - case 2: // hire finance minister - { - if ( m_Town.Finance != null ) - { - m_From.SendLocalizedMessage( 1010345 ); // You must fire your finance minister before you can elect a new one - } - else - { - m_From.SendLocalizedMessage( 1010348 ); // Who shall be your new Minister of Finances? - m_From.BeginTarget( 12, false, TargetFlags.None, HireFinanceMinister_OnTarget ); - } + break; + } + case 2: // hire finance minister + { + if (m_Town.Finance != null) + { + m_From.SendLocalizedMessage( + 1010345); // You must fire your finance minister before you can elect a new one + } + else + { + m_From.SendLocalizedMessage(1010348); // Who shall be your new Minister of Finances? + m_From.BeginTarget(12, false, TargetFlags.None, HireFinanceMinister_OnTarget); + } - break; - } - case 3: // fire sheriff - { - if ( m_Town.Sheriff == null ) - { - m_From.SendLocalizedMessage( 1010350 ); // You need to elect a sheriff before you can fire one - } - else - { - m_From.SendLocalizedMessage( 1010349 ); // You have fired your sheriff - m_Town.Sheriff.SendLocalizedMessage( 1010270 ); // You have been fired as Sheriff - m_Town.Sheriff = null; - } + break; + } + case 3: // fire sheriff + { + if (m_Town.Sheriff == null) + { + m_From.SendLocalizedMessage(1010350); // You need to elect a sheriff before you can fire one + } + else + { + m_From.SendLocalizedMessage(1010349); // You have fired your sheriff + m_Town.Sheriff.SendLocalizedMessage(1010270); // You have been fired as Sheriff + m_Town.Sheriff = null; + } - break; - } - case 4: // fire finance minister - { - if ( m_Town.Finance == null ) - { - m_From.SendLocalizedMessage( 1010352 ); // You need to elect a financial minister before you can fire one - } - else - { - m_From.SendLocalizedMessage( 1010351 ); // You have fired your financial Minister - m_Town.Finance.SendLocalizedMessage( 1010151 ); // You have been fired as Finance Minister - m_Town.Finance = null; - } + break; + } + case 4: // fire finance minister + { + if (m_Town.Finance == null) + { + m_From.SendLocalizedMessage( + 1010352); // You need to elect a financial minister before you can fire one + } + else + { + m_From.SendLocalizedMessage(1010351); // You have fired your financial Minister + m_Town.Finance.SendLocalizedMessage(1010151); // You have been fired as Finance Minister + m_Town.Finance = null; + } - break; - } - } - } + break; + } + } + } - private void HireSheriff_OnTarget( Mobile from, object obj ) - { - if ( m_Town.Owner != m_Faction || !m_Faction.IsCommander( from ) ) - { - from.SendLocalizedMessage( 1010339 ); // You no longer control this city - return; - } + private void HireSheriff_OnTarget(Mobile from, object obj) + { + if (m_Town.Owner != m_Faction || !m_Faction.IsCommander(from)) + { + from.SendLocalizedMessage(1010339); // You no longer control this city + return; + } - if ( m_Town.Sheriff != null ) - { - from.SendLocalizedMessage( 1010342 ); // You must fire your Sheriff before you can elect a new one - } - else if ( obj is Mobile targ ) - { - PlayerState pl = PlayerState.Find( targ ); + if (m_Town.Sheriff != null) + { + from.SendLocalizedMessage(1010342); // You must fire your Sheriff before you can elect a new one + } + else if (obj is Mobile targ) + { + PlayerState pl = PlayerState.Find(targ); - if ( pl == null ) - { - from.SendLocalizedMessage( 1010337 ); // You must pick someone in a faction - } - else if ( pl.Faction != m_Faction ) - { - from.SendLocalizedMessage( 1010338 ); // You must pick someone in the correct faction - } - else if ( m_Faction.Commander == targ ) - { - from.SendLocalizedMessage( 1010335 ); // You cannot elect a commander to a town position - } - else if ( pl.Sheriff != null || pl.Finance != null ) - { - from.SendLocalizedMessage( 1005245 ); // You must pick someone who does not already hold a city post - } - else - { - m_Town.Sheriff = targ; - targ.SendLocalizedMessage( 1010340 ); // You are now the Sheriff - from.SendLocalizedMessage( 1010341 ); // You have elected a Sheriff - } - } - else - { - from.SendLocalizedMessage( 1010334 ); // You must select a player to hold a city position! - } - } + if (pl == null) + { + from.SendLocalizedMessage(1010337); // You must pick someone in a faction + } + else if (pl.Faction != m_Faction) + { + from.SendLocalizedMessage(1010338); // You must pick someone in the correct faction + } + else if (m_Faction.Commander == targ) + { + from.SendLocalizedMessage(1010335); // You cannot elect a commander to a town position + } + else if (pl.Sheriff != null || pl.Finance != null) + { + from.SendLocalizedMessage(1005245); // You must pick someone who does not already hold a city post + } + else + { + m_Town.Sheriff = targ; + targ.SendLocalizedMessage(1010340); // You are now the Sheriff + from.SendLocalizedMessage(1010341); // You have elected a Sheriff + } + } + else + { + from.SendLocalizedMessage(1010334); // You must select a player to hold a city position! + } + } - private void HireFinanceMinister_OnTarget( Mobile from, object obj ) - { - if ( m_Town.Owner != m_Faction || !m_Faction.IsCommander( from ) ) - { - from.SendLocalizedMessage( 1010339 ); // You no longer control this city - } - else if ( m_Town.Finance != null ) - { - from.SendLocalizedMessage( 1010342 ); // You must fire your Sheriff before you can elect a new one - } - else if ( obj is Mobile targ ) - { - PlayerState pl = PlayerState.Find( targ ); + private void HireFinanceMinister_OnTarget(Mobile from, object obj) + { + if (m_Town.Owner != m_Faction || !m_Faction.IsCommander(from)) + { + from.SendLocalizedMessage(1010339); // You no longer control this city + } + else if (m_Town.Finance != null) + { + from.SendLocalizedMessage(1010342); // You must fire your Sheriff before you can elect a new one + } + else if (obj is Mobile targ) + { + PlayerState pl = PlayerState.Find(targ); - if ( pl == null ) - { - from.SendLocalizedMessage( 1010337 ); // You must pick someone in a faction - } - else if ( pl.Faction != m_Faction ) - { - from.SendLocalizedMessage( 1010338 ); // You must pick someone in the correct faction - } - else if ( m_Faction.Commander == targ ) - { - from.SendLocalizedMessage( 1010335 ); // You cannot elect a commander to a town position - } - else if ( pl.Sheriff != null || pl.Finance != null ) - { - from.SendLocalizedMessage( 1005245 ); // You must pick someone who does not already hold a city post - } - else - { - m_Town.Finance = targ; - targ.SendLocalizedMessage( 1010343 ); // You are now the Financial Minister - from.SendLocalizedMessage( 1010344 ); // You have elected a Financial Minister - } - } - else - { - from.SendLocalizedMessage( 1010334 ); // You must select a player to hold a city position! - } - } - } -} + if (pl == null) + { + from.SendLocalizedMessage(1010337); // You must pick someone in a faction + } + else if (pl.Faction != m_Faction) + { + from.SendLocalizedMessage(1010338); // You must pick someone in the correct faction + } + else if (m_Faction.Commander == targ) + { + from.SendLocalizedMessage(1010335); // You cannot elect a commander to a town position + } + else if (pl.Sheriff != null || pl.Finance != null) + { + from.SendLocalizedMessage(1005245); // You must pick someone who does not already hold a city post + } + else + { + m_Town.Finance = targ; + targ.SendLocalizedMessage(1010343); // You are now the Financial Minister + from.SendLocalizedMessage(1010344); // You have elected a Financial Minister + } + } + else + { + from.SendLocalizedMessage(1010334); // You must select a player to hold a city position! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Gumps/VoteGump.cs b/Scripts/Engines/Factions/Gumps/VoteGump.cs index 144854817..fbe278890 100644 --- a/Scripts/Engines/Factions/Gumps/VoteGump.cs +++ b/Scripts/Engines/Factions/Gumps/VoteGump.cs @@ -4,63 +4,63 @@ using Server.Network; namespace Server.Factions { - public class VoteGump : FactionGump - { - private PlayerMobile m_From; - private Election m_Election; + public class VoteGump : FactionGump + { + private Election m_Election; + private PlayerMobile m_From; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 ) - { - m_From.SendGump( new FactionStoneGump( m_From, m_Election.Faction ) ); - } - else - { - if ( !m_Election.CanVote( m_From ) ) - return; + public VoteGump(PlayerMobile from, Election election) : base(50, 50) + { + m_From = from; + m_Election = election; - int index = info.ButtonID - 1; + bool canVote = election.CanVote(from); - if ( index >= 0 && index < m_Election.Candidates.Count ) - m_Election.Candidates[index].Voters.Add( new Voter( m_From, m_Election.Candidates[index].Mobile ) ); + AddPage(0); - m_From.SendGump( new VoteGump( m_From, m_Election ) ); - } - } + AddBackground(0, 0, 420, 350, 5054); + AddBackground(10, 10, 400, 330, 3000); - public VoteGump( PlayerMobile from, Election election ) : base( 50, 50 ) - { - m_From = from; - m_Election = election; + AddHtmlText(20, 20, 380, 20, election.Faction.Definition.Header, false, false); - bool canVote = election.CanVote( from ); + if (canVote) + AddHtmlLocalized(20, 60, 380, 20, 1011428, false, false); // VOTE FOR LEADERSHIP + else + AddHtmlLocalized(20, 60, 380, 20, 1038032, false, false); // You have already voted in this election. - AddPage( 0 ); + for (int i = 0; i < election.Candidates.Count; ++i) + { + Candidate cd = election.Candidates[i]; - AddBackground( 0, 0, 420, 350, 5054 ); - AddBackground( 10, 10, 400, 330, 3000 ); + if (canVote) + AddButton(20, 100 + i * 20, 4005, 4007, i + 1, GumpButtonType.Reply, 0); - AddHtmlText( 20, 20, 380, 20, election.Faction.Definition.Header, false, false ); + AddLabel(55, 100 + i * 20, 0, cd.Mobile.Name); + AddLabel(300, 100 + i * 20, 0, cd.Votes.ToString()); + } - if ( canVote ) - AddHtmlLocalized( 20, 60, 380, 20, 1011428, false, false ); // VOTE FOR LEADERSHIP - else - AddHtmlLocalized( 20, 60, 380, 20, 1038032, false, false ); // You have already voted in this election. + AddButton(20, 310, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 310, 100, 20, 1011012, false, false); // CANCEL + } - for ( int i = 0; i < election.Candidates.Count; ++i ) - { - Candidate cd = election.Candidates[i]; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0) + { + m_From.SendGump(new FactionStoneGump(m_From, m_Election.Faction)); + } + else + { + if (!m_Election.CanVote(m_From)) + return; - if ( canVote ) - AddButton( 20, 100 + (i * 20), 4005, 4007, i + 1, GumpButtonType.Reply, 0 ); + int index = info.ButtonID - 1; - AddLabel( 55, 100 + (i * 20), 0, cd.Mobile.Name ); - AddLabel( 300, 100 + (i * 20), 0, cd.Votes.ToString() ); - } + if (index >= 0 && index < m_Election.Candidates.Count) + m_Election.Candidates[index].Voters.Add(new Voter(m_From, m_Election.Candidates[index].Mobile)); - AddButton( 20, 310, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 310, 100, 20, 1011012, false, false ); // CANCEL - } - } + m_From.SendGump(new VoteGump(m_From, m_Election)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Factions/CouncilOfMages.cs b/Scripts/Engines/Factions/Instances/Factions/CouncilOfMages.cs index a27f21c5d..bfd26b307 100644 --- a/Scripts/Engines/Factions/Instances/Factions/CouncilOfMages.cs +++ b/Scripts/Engines/Factions/Instances/Factions/CouncilOfMages.cs @@ -1,102 +1,106 @@ namespace Server.Factions { - public class CouncilOfMages : Faction - { - public static Faction Instance { get; private set; } + public class CouncilOfMages : Faction + { + public CouncilOfMages() + { + Instance = this; - public CouncilOfMages() - { - Instance = this; + Definition = + new FactionDefinition( + 1, + 1325, // blue + 1310, // bluish white + 1325, // join stone : blue + 1325, // broadcast : blue + 0x77, 0x3EB1, // war horse + "Council of Mages", "council", "CoM", + new TextDefinition(1011535, "COUNCIL OF MAGES"), + new TextDefinition(1060770, "Council of Mages faction"), + new TextDefinition(1011422, "
COUNCIL OF MAGES
"), + new TextDefinition(1011449, + "The council of Mages have their roots in the city of Moonglow, where " + + "they once convened. They began as a small movement, dedicated to " + + "calling forth the Stranger, who saved the lands once before. A " + + "series of war and murders and misbegotten trials by those loyal to " + + "Lord British has caused the group to take up the banner of war."), + new TextDefinition(1011455, "This city is controlled by the Council of Mages."), + new TextDefinition(1042253, "This sigil has been corrupted by the Council of Mages"), + new TextDefinition(1041044, "The faction signup stone for the Council of Mages"), + new TextDefinition(1041382, "The Faction Stone of the Council of Mages"), + new TextDefinition(1011464, ": Council of Mages"), + new TextDefinition(1005187, "Members of the Council of Mages will now be ignored."), + new TextDefinition(1005188, "Members of the Council of Mages will now be warned to leave."), + new TextDefinition(1005189, "Members of the Council of Mages will now be beaten with a stick."), + // Moonglow + new StrongholdDefinition( + new[] + { + new Rectangle2D(4463, 1487, 15, 35), + new Rectangle2D(4450, 1522, 35, 48) + }, + new Point3D(4469, 1486, 0), + new Point3D(4457, 1544, 0), + new[] + { + new Point3D(4464, 1534, 21), + new Point3D(4470, 1536, 21), + new Point3D(4468, 1534, 21), + new Point3D(4470, 1534, 21), + new Point3D(4468, 1536, 21), + new Point3D(4466, 1534, 21), + new Point3D(4466, 1536, 21), + new Point3D(4464, 1536, 21) + }), + // Magincia + /* new StrongholdDefinition( + new Rectangle2D[] + { + new Rectangle2D( 3756, 2232, 4, 23 ), + new Rectangle2D( 3760, 2227, 60, 28 ), + new Rectangle2D( 3782, 2219, 18, 8 ), + new Rectangle2D( 3778, 2255, 35, 17 ) + }, + new Point3D( 3750, 2241, 20 ), + new Point3D( 3795, 2259, 20 ), + new Point3D[] + { + new Point3D( 3793, 2255, 20 ), + new Point3D( 3793, 2252, 20 ), + new Point3D( 3793, 2249, 20 ), + new Point3D( 3793, 2246, 20 ), + new Point3D( 3797, 2255, 20 ), + new Point3D( 3797, 2252, 20 ), + new Point3D( 3797, 2249, 20 ), + new Point3D( 3797, 2246, 20 ) + } ), */ + new[] + { + new RankDefinition(10, 991, 8, new TextDefinition(1060789, "Inquisitor of the Council")), + new RankDefinition(9, 950, 7, new TextDefinition(1060788, "Archon of Principle")), + new RankDefinition(8, 900, 6, new TextDefinition(1060787, "Luminary")), + new RankDefinition(7, 800, 6, new TextDefinition(1060787, "Luminary")), + new RankDefinition(6, 700, 5, new TextDefinition(1060786, "Diviner")), + new RankDefinition(5, 600, 5, new TextDefinition(1060786, "Diviner")), + new RankDefinition(4, 500, 5, new TextDefinition(1060786, "Diviner")), + new RankDefinition(3, 400, 4, new TextDefinition(1060785, "Mystic")), + new RankDefinition(2, 200, 4, new TextDefinition(1060785, "Mystic")), + new RankDefinition(1, 0, 4, new TextDefinition(1060785, "Mystic")) + }, + new[] + { + new GuardDefinition(typeof(FactionHenchman), 0x1403, 5000, 1000, 10, + new TextDefinition(1011526, "HENCHMAN"), new TextDefinition(1011510, "Hire Henchman")), + new GuardDefinition(typeof(FactionMercenary), 0x0F62, 6000, 2000, 10, + new TextDefinition(1011527, "MERCENARY"), new TextDefinition(1011511, "Hire Mercenary")), + new GuardDefinition(typeof(FactionSorceress), 0x0E89, 7000, 3000, 10, + new TextDefinition(1011507, "SORCERESS"), new TextDefinition(1011501, "Hire Sorceress")), + new GuardDefinition(typeof(FactionWizard), 0x13F8, 8000, 4000, 10, + new TextDefinition(1011508, "ELDER WIZARD"), new TextDefinition(1011502, "Hire Elder Wizard")) + } + ); + } - Definition = - new FactionDefinition( - 1, - 1325, // blue - 1310, // bluish white - 1325, // join stone : blue - 1325, // broadcast : blue - 0x77, 0x3EB1, // war horse - "Council of Mages", "council", "CoM", - new TextDefinition( 1011535, "COUNCIL OF MAGES" ), - new TextDefinition( 1060770, "Council of Mages faction" ), - new TextDefinition( 1011422, "
COUNCIL OF MAGES
" ), - new TextDefinition( 1011449, - "The council of Mages have their roots in the city of Moonglow, where " + - "they once convened. They began as a small movement, dedicated to " + - "calling forth the Stranger, who saved the lands once before. A " + - "series of war and murders and misbegotten trials by those loyal to " + - "Lord British has caused the group to take up the banner of war." ), - new TextDefinition( 1011455, "This city is controlled by the Council of Mages." ), - new TextDefinition( 1042253, "This sigil has been corrupted by the Council of Mages" ), - new TextDefinition( 1041044, "The faction signup stone for the Council of Mages" ), - new TextDefinition( 1041382, "The Faction Stone of the Council of Mages" ), - new TextDefinition( 1011464, ": Council of Mages" ), - new TextDefinition( 1005187, "Members of the Council of Mages will now be ignored." ), - new TextDefinition( 1005188, "Members of the Council of Mages will now be warned to leave." ), - new TextDefinition( 1005189, "Members of the Council of Mages will now be beaten with a stick." ), - // Moonglow - new StrongholdDefinition( - new[] - { - new Rectangle2D( 4463, 1487, 15, 35 ), - new Rectangle2D( 4450, 1522, 35, 48 ), - }, - new Point3D( 4469, 1486, 0 ), - new Point3D( 4457, 1544, 0 ), - new[] - { - new Point3D( 4464, 1534, 21 ), - new Point3D( 4470, 1536, 21 ), - new Point3D( 4468, 1534, 21 ), - new Point3D( 4470, 1534, 21 ), - new Point3D( 4468, 1536, 21 ), - new Point3D( 4466, 1534, 21 ), - new Point3D( 4466, 1536, 21 ), - new Point3D( 4464, 1536, 21 ) - } ), - // Magincia - /* new StrongholdDefinition( - new Rectangle2D[] - { - new Rectangle2D( 3756, 2232, 4, 23 ), - new Rectangle2D( 3760, 2227, 60, 28 ), - new Rectangle2D( 3782, 2219, 18, 8 ), - new Rectangle2D( 3778, 2255, 35, 17 ) - }, - new Point3D( 3750, 2241, 20 ), - new Point3D( 3795, 2259, 20 ), - new Point3D[] - { - new Point3D( 3793, 2255, 20 ), - new Point3D( 3793, 2252, 20 ), - new Point3D( 3793, 2249, 20 ), - new Point3D( 3793, 2246, 20 ), - new Point3D( 3797, 2255, 20 ), - new Point3D( 3797, 2252, 20 ), - new Point3D( 3797, 2249, 20 ), - new Point3D( 3797, 2246, 20 ) - } ), */ - new[] - { - new RankDefinition( 10, 991, 8, new TextDefinition( 1060789, "Inquisitor of the Council" ) ), - new RankDefinition( 9, 950, 7, new TextDefinition( 1060788, "Archon of Principle" ) ), - new RankDefinition( 8, 900, 6, new TextDefinition( 1060787, "Luminary" ) ), - new RankDefinition( 7, 800, 6, new TextDefinition( 1060787, "Luminary" ) ), - new RankDefinition( 6, 700, 5, new TextDefinition( 1060786, "Diviner" ) ), - new RankDefinition( 5, 600, 5, new TextDefinition( 1060786, "Diviner" ) ), - new RankDefinition( 4, 500, 5, new TextDefinition( 1060786, "Diviner" ) ), - new RankDefinition( 3, 400, 4, new TextDefinition( 1060785, "Mystic" ) ), - new RankDefinition( 2, 200, 4, new TextDefinition( 1060785, "Mystic" ) ), - new RankDefinition( 1, 0, 4, new TextDefinition( 1060785, "Mystic" ) ) - }, - new[] - { - new GuardDefinition( typeof( FactionHenchman ), 0x1403, 5000, 1000, 10, new TextDefinition( 1011526, "HENCHMAN" ), new TextDefinition( 1011510, "Hire Henchman" ) ), - new GuardDefinition( typeof( FactionMercenary ), 0x0F62, 6000, 2000, 10, new TextDefinition( 1011527, "MERCENARY" ), new TextDefinition( 1011511, "Hire Mercenary" ) ), - new GuardDefinition( typeof( FactionSorceress ), 0x0E89, 7000, 3000, 10, new TextDefinition( 1011507, "SORCERESS" ), new TextDefinition( 1011501, "Hire Sorceress" ) ), - new GuardDefinition( typeof( FactionWizard ), 0x13F8, 8000, 4000, 10, new TextDefinition( 1011508, "ELDER WIZARD" ), new TextDefinition( 1011502, "Hire Elder Wizard" ) ), - } - ); - } - } + public static Faction Instance{ get; private set; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Factions/Minax.cs b/Scripts/Engines/Factions/Instances/Factions/Minax.cs index 888801e9f..5fd3ca359 100644 --- a/Scripts/Engines/Factions/Instances/Factions/Minax.cs +++ b/Scripts/Engines/Factions/Instances/Factions/Minax.cs @@ -1,79 +1,83 @@ namespace Server.Factions { - public class Minax : Faction - { - public static Faction Instance { get; private set; } + public class Minax : Faction + { + public Minax() + { + Instance = this; - public Minax() - { - Instance = this; + Definition = + new FactionDefinition( + 0, + 1645, // dark red + 1109, // shadow + 1645, // join stone : dark red + 1645, // broadcast : dark red + 0x78, 0x3EAF, // war horse + "Minax", "minax", "Min", + new TextDefinition(1011534, "MINAX"), + new TextDefinition(1060769, "Minax faction"), + new TextDefinition(1011421, "
FOLLOWERS OF MINAX
"), + new TextDefinition(1011448, + "The followers of Minax have taken control in the old lands, " + + "and intend to hold it for as long as they can. Allying themselves " + + "with orcs, headless, gazers, trolls, and other beasts, they seek " + + "revenge against Lord British, for slights both real and imagined, " + + "though some of the followers wish only to wreak havoc on the " + + "unsuspecting populace."), + new TextDefinition(1011453, "This city is controlled by Minax."), + new TextDefinition(1042252, "This sigil has been corrupted by the Followers of Minax"), + new TextDefinition(1041043, "The faction signup stone for the Followers of Minax"), + new TextDefinition(1041381, "The Faction Stone of Minax"), + new TextDefinition(1011463, ": Minax"), + new TextDefinition(1005190, "Followers of Minax will now be ignored."), + new TextDefinition(1005191, "Followers of Minax will now be told to go away."), + new TextDefinition(1005192, "Followers of Minax will now be hanged by their toes."), + new StrongholdDefinition( + new[] + { + new Rectangle2D(1097, 2570, 70, 50) + }, + new Point3D(1172, 2593, 0), + new Point3D(1117, 2587, 18), + new[] + { + new Point3D(1113, 2601, 18), + new Point3D(1113, 2598, 18), + new Point3D(1113, 2595, 18), + new Point3D(1113, 2592, 18), + new Point3D(1116, 2601, 18), + new Point3D(1116, 2598, 18), + new Point3D(1116, 2595, 18), + new Point3D(1116, 2592, 18) + }), + new[] + { + new RankDefinition(10, 991, 8, new TextDefinition(1060784, "Avenger of Mondain")), + new RankDefinition(9, 950, 7, new TextDefinition(1060783, "Dread Knight")), + new RankDefinition(8, 900, 6, new TextDefinition(1060782, "Warlord")), + new RankDefinition(7, 800, 6, new TextDefinition(1060782, "Warlord")), + new RankDefinition(6, 700, 5, new TextDefinition(1060781, "Executioner")), + new RankDefinition(5, 600, 5, new TextDefinition(1060781, "Executioner")), + new RankDefinition(4, 500, 5, new TextDefinition(1060781, "Executioner")), + new RankDefinition(3, 400, 4, new TextDefinition(1060780, "Defiler")), + new RankDefinition(2, 200, 4, new TextDefinition(1060780, "Defiler")), + new RankDefinition(1, 0, 4, new TextDefinition(1060780, "Defiler")) + }, + new[] + { + new GuardDefinition(typeof(FactionHenchman), 0x1403, 5000, 1000, 10, + new TextDefinition(1011526, "HENCHMAN"), new TextDefinition(1011510, "Hire Henchman")), + new GuardDefinition(typeof(FactionMercenary), 0x0F62, 6000, 2000, 10, + new TextDefinition(1011527, "MERCENARY"), new TextDefinition(1011511, "Hire Mercenary")), + new GuardDefinition(typeof(FactionBerserker), 0x0F4B, 7000, 3000, 10, + new TextDefinition(1011505, "BERSERKER"), new TextDefinition(1011499, "Hire Berserker")), + new GuardDefinition(typeof(FactionDragoon), 0x1439, 8000, 4000, 10, + new TextDefinition(1011506, "DRAGOON"), new TextDefinition(1011500, "Hire Dragoon")) + } + ); + } - Definition = - new FactionDefinition( - 0, - 1645, // dark red - 1109, // shadow - 1645, // join stone : dark red - 1645, // broadcast : dark red - 0x78, 0x3EAF, // war horse - "Minax", "minax", "Min", - new TextDefinition( 1011534, "MINAX" ), - new TextDefinition( 1060769, "Minax faction" ), - new TextDefinition( 1011421, "
FOLLOWERS OF MINAX
" ), - new TextDefinition( 1011448, - "The followers of Minax have taken control in the old lands, " + - "and intend to hold it for as long as they can. Allying themselves " + - "with orcs, headless, gazers, trolls, and other beasts, they seek " + - "revenge against Lord British, for slights both real and imagined, " + - "though some of the followers wish only to wreak havoc on the " + - "unsuspecting populace." ), - new TextDefinition( 1011453, "This city is controlled by Minax." ), - new TextDefinition( 1042252, "This sigil has been corrupted by the Followers of Minax" ), - new TextDefinition( 1041043, "The faction signup stone for the Followers of Minax" ), - new TextDefinition( 1041381, "The Faction Stone of Minax" ), - new TextDefinition( 1011463, ": Minax" ), - new TextDefinition( 1005190, "Followers of Minax will now be ignored." ), - new TextDefinition( 1005191, "Followers of Minax will now be told to go away." ), - new TextDefinition( 1005192, "Followers of Minax will now be hanged by their toes." ), - new StrongholdDefinition( - new[] - { - new Rectangle2D( 1097, 2570, 70, 50 ) - }, - new Point3D( 1172, 2593, 0 ), - new Point3D( 1117, 2587, 18 ), - new[] - { - new Point3D( 1113, 2601, 18 ), - new Point3D( 1113, 2598, 18 ), - new Point3D( 1113, 2595, 18 ), - new Point3D( 1113, 2592, 18 ), - new Point3D( 1116, 2601, 18 ), - new Point3D( 1116, 2598, 18 ), - new Point3D( 1116, 2595, 18 ), - new Point3D( 1116, 2592, 18 ) - } ), - new[] - { - new RankDefinition( 10, 991, 8, new TextDefinition( 1060784, "Avenger of Mondain" ) ), - new RankDefinition( 9, 950, 7, new TextDefinition( 1060783, "Dread Knight" ) ), - new RankDefinition( 8, 900, 6, new TextDefinition( 1060782, "Warlord" ) ), - new RankDefinition( 7, 800, 6, new TextDefinition( 1060782, "Warlord" ) ), - new RankDefinition( 6, 700, 5, new TextDefinition( 1060781, "Executioner" ) ), - new RankDefinition( 5, 600, 5, new TextDefinition( 1060781, "Executioner" ) ), - new RankDefinition( 4, 500, 5, new TextDefinition( 1060781, "Executioner" ) ), - new RankDefinition( 3, 400, 4, new TextDefinition( 1060780, "Defiler" ) ), - new RankDefinition( 2, 200, 4, new TextDefinition( 1060780, "Defiler" ) ), - new RankDefinition( 1, 0, 4, new TextDefinition( 1060780, "Defiler" ) ) - }, - new[] - { - new GuardDefinition( typeof( FactionHenchman ), 0x1403, 5000, 1000, 10, new TextDefinition( 1011526, "HENCHMAN" ), new TextDefinition( 1011510, "Hire Henchman" ) ), - new GuardDefinition( typeof( FactionMercenary ), 0x0F62, 6000, 2000, 10, new TextDefinition( 1011527, "MERCENARY" ), new TextDefinition( 1011511, "Hire Mercenary" ) ), - new GuardDefinition( typeof( FactionBerserker ), 0x0F4B, 7000, 3000, 10, new TextDefinition( 1011505, "BERSERKER" ), new TextDefinition( 1011499, "Hire Berserker" ) ), - new GuardDefinition( typeof( FactionDragoon ), 0x1439, 8000, 4000, 10, new TextDefinition( 1011506, "DRAGOON" ), new TextDefinition( 1011500, "Hire Dragoon" ) ), - } - ); - } - } + public static Faction Instance{ get; private set; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Factions/Shadowlords.cs b/Scripts/Engines/Factions/Instances/Factions/Shadowlords.cs index bbb9c42ca..e3f5598da 100644 --- a/Scripts/Engines/Factions/Instances/Factions/Shadowlords.cs +++ b/Scripts/Engines/Factions/Instances/Factions/Shadowlords.cs @@ -1,79 +1,83 @@ namespace Server.Factions { - public class Shadowlords : Faction - { - public static Faction Instance { get; private set; } + public class Shadowlords : Faction + { + public Shadowlords() + { + Instance = this; - public Shadowlords() - { - Instance = this; + Definition = + new FactionDefinition( + 3, + 1109, // shadow + 2211, // green + 1109, // join stone : shadow + 2211, // broadcast : green + 0x79, 0x3EB0, // war horse + "Shadowlords", "shadow", "SL", + new TextDefinition(1011537, "SHADOWLORDS"), + new TextDefinition(1060772, "Shadowlords faction"), + new TextDefinition(1011424, "
SHADES OF DARKNESS
"), + new TextDefinition(1011451, + "The Shadow Lords are a faction that has sprung up within the ranks of " + + "Minax. Comprised mostly of undead and those who would seek to be " + + "necromancers, they pose a threat to both the sides of good and evil. " + + "Their plans have disrupted the hold Minax has over Felucca, and their " + + "ultimate goal is to destroy all life."), + new TextDefinition(1011456, "This city is controlled by the Shadow Lords."), + new TextDefinition(1042255, "This sigil has been corrupted by the Shadowlords"), + new TextDefinition(1041046, "The faction signup stone for the Shadowlords"), + new TextDefinition(1041384, "The Faction Stone of the Shadowlords"), + new TextDefinition(1011466, ": Shadowlords"), + new TextDefinition(1005184, "Minions of the Shadowlords will now be ignored."), + new TextDefinition(1005185, "Minions of the Shadowlords will now be warned of their impending deaths."), + new TextDefinition(1005186, "Minions of the Shadowlords will now be attacked at will."), + new StrongholdDefinition( + new[] + { + new Rectangle2D(960, 688, 8, 9), + new Rectangle2D(944, 697, 24, 23) + }, + new Point3D(969, 768, 0), + new Point3D(947, 713, 0), + new[] + { + new Point3D(953, 713, 20), + new Point3D(953, 709, 20), + new Point3D(953, 705, 20), + new Point3D(953, 701, 20), + new Point3D(957, 713, 20), + new Point3D(957, 709, 20), + new Point3D(957, 705, 20), + new Point3D(957, 701, 20) + }), + new[] + { + new RankDefinition(10, 991, 8, new TextDefinition(1060799, "Purveyor of Darkness")), + new RankDefinition(9, 950, 7, new TextDefinition(1060798, "Agent of Evil")), + new RankDefinition(8, 900, 6, new TextDefinition(1060797, "Bringer of Sorrow")), + new RankDefinition(7, 800, 6, new TextDefinition(1060797, "Bringer of Sorrow")), + new RankDefinition(6, 700, 5, new TextDefinition(1060796, "Keeper of Lies")), + new RankDefinition(5, 600, 5, new TextDefinition(1060796, "Keeper of Lies")), + new RankDefinition(4, 500, 5, new TextDefinition(1060796, "Keeper of Lies")), + new RankDefinition(3, 400, 4, new TextDefinition(1060795, "Servant")), + new RankDefinition(2, 200, 4, new TextDefinition(1060795, "Servant")), + new RankDefinition(1, 0, 4, new TextDefinition(1060795, "Servant")) + }, + new[] + { + new GuardDefinition(typeof(FactionHenchman), 0x1403, 5000, 1000, 10, + new TextDefinition(1011526, "HENCHMAN"), new TextDefinition(1011510, "Hire Henchman")), + new GuardDefinition(typeof(FactionMercenary), 0x0F62, 6000, 2000, 10, + new TextDefinition(1011527, "MERCENARY"), new TextDefinition(1011511, "Hire Mercenary")), + new GuardDefinition(typeof(FactionDeathKnight), 0x0F45, 7000, 3000, 10, + new TextDefinition(1011512, "DEATH KNIGHT"), new TextDefinition(1011503, "Hire Death Knight")), + new GuardDefinition(typeof(FactionNecromancer), 0x13F8, 8000, 4000, 10, + new TextDefinition(1011513, "SHADOW MAGE"), new TextDefinition(1011504, "Hire Shadow Mage")) + } + ); + } - Definition = - new FactionDefinition( - 3, - 1109, // shadow - 2211, // green - 1109, // join stone : shadow - 2211, // broadcast : green - 0x79, 0x3EB0, // war horse - "Shadowlords", "shadow", "SL", - new TextDefinition( 1011537, "SHADOWLORDS" ), - new TextDefinition( 1060772, "Shadowlords faction" ), - new TextDefinition( 1011424, "
SHADES OF DARKNESS
" ), - new TextDefinition( 1011451, - "The Shadow Lords are a faction that has sprung up within the ranks of " + - "Minax. Comprised mostly of undead and those who would seek to be " + - "necromancers, they pose a threat to both the sides of good and evil. " + - "Their plans have disrupted the hold Minax has over Felucca, and their " + - "ultimate goal is to destroy all life." ), - new TextDefinition( 1011456, "This city is controlled by the Shadow Lords." ), - new TextDefinition( 1042255, "This sigil has been corrupted by the Shadowlords" ), - new TextDefinition( 1041046, "The faction signup stone for the Shadowlords" ), - new TextDefinition( 1041384, "The Faction Stone of the Shadowlords" ), - new TextDefinition( 1011466, ": Shadowlords" ), - new TextDefinition( 1005184, "Minions of the Shadowlords will now be ignored." ), - new TextDefinition( 1005185, "Minions of the Shadowlords will now be warned of their impending deaths." ), - new TextDefinition( 1005186, "Minions of the Shadowlords will now be attacked at will." ), - new StrongholdDefinition( - new[] - { - new Rectangle2D( 960, 688, 8, 9 ), - new Rectangle2D( 944, 697, 24, 23 ) - }, - new Point3D( 969, 768, 0 ), - new Point3D( 947, 713, 0 ), - new[] - { - new Point3D( 953, 713, 20 ), - new Point3D( 953, 709, 20 ), - new Point3D( 953, 705, 20 ), - new Point3D( 953, 701, 20 ), - new Point3D( 957, 713, 20 ), - new Point3D( 957, 709, 20 ), - new Point3D( 957, 705, 20 ), - new Point3D( 957, 701, 20 ) - } ), - new[] - { - new RankDefinition( 10, 991, 8, new TextDefinition( 1060799, "Purveyor of Darkness" ) ), - new RankDefinition( 9, 950, 7, new TextDefinition( 1060798, "Agent of Evil" ) ), - new RankDefinition( 8, 900, 6, new TextDefinition( 1060797, "Bringer of Sorrow" ) ), - new RankDefinition( 7, 800, 6, new TextDefinition( 1060797, "Bringer of Sorrow" ) ), - new RankDefinition( 6, 700, 5, new TextDefinition( 1060796, "Keeper of Lies" ) ), - new RankDefinition( 5, 600, 5, new TextDefinition( 1060796, "Keeper of Lies" ) ), - new RankDefinition( 4, 500, 5, new TextDefinition( 1060796, "Keeper of Lies" ) ), - new RankDefinition( 3, 400, 4, new TextDefinition( 1060795, "Servant" ) ), - new RankDefinition( 2, 200, 4, new TextDefinition( 1060795, "Servant" ) ), - new RankDefinition( 1, 0, 4, new TextDefinition( 1060795, "Servant" ) ) - }, - new[] - { - new GuardDefinition( typeof( FactionHenchman ), 0x1403, 5000, 1000, 10, new TextDefinition( 1011526, "HENCHMAN" ), new TextDefinition( 1011510, "Hire Henchman" ) ), - new GuardDefinition( typeof( FactionMercenary ), 0x0F62, 6000, 2000, 10, new TextDefinition( 1011527, "MERCENARY" ), new TextDefinition( 1011511, "Hire Mercenary" ) ), - new GuardDefinition( typeof( FactionDeathKnight ), 0x0F45, 7000, 3000, 10, new TextDefinition( 1011512, "DEATH KNIGHT" ), new TextDefinition( 1011503, "Hire Death Knight" ) ), - new GuardDefinition( typeof( FactionNecromancer ), 0x13F8, 8000, 4000, 10, new TextDefinition( 1011513, "SHADOW MAGE" ), new TextDefinition( 1011504, "Hire Shadow Mage" ) ), - } - ); - } - } + public static Faction Instance{ get; private set; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Factions/TrueBritannians.cs b/Scripts/Engines/Factions/Instances/Factions/TrueBritannians.cs index 910345e09..cd9215d10 100644 --- a/Scripts/Engines/Factions/Instances/Factions/TrueBritannians.cs +++ b/Scripts/Engines/Factions/Instances/Factions/TrueBritannians.cs @@ -1,84 +1,88 @@ namespace Server.Factions { - public class TrueBritannians : Faction - { - public static Faction Instance { get; private set; } + public class TrueBritannians : Faction + { + public TrueBritannians() + { + Instance = this; - public TrueBritannians() - { - Instance = this; + Definition = + new FactionDefinition( + 2, + 1254, // dark purple + 2125, // gold + 2214, // join stone : gold + 2125, // broadcast : gold + 0x76, 0x3EB2, // war horse + "True Britannians", "true", "TB", + new TextDefinition(1011536, "LORD BRITISH"), + new TextDefinition(1060771, "True Britannians faction"), + new TextDefinition(1011423, "
TRUE BRITANNIANS
"), + new TextDefinition(1011450, + "True Britannians are loyal to the throne of Lord British. They refuse " + + "to give up their homelands to the vile Minax, and detest the Shadowlords " + + "for their evil ways. In addition, the Council of Mages threatens the " + + "existence of their ruler, and as such they have armed themselves, and " + + "prepare for war with all."), + new TextDefinition(1011454, "This city is controlled by Lord British."), + new TextDefinition(1042254, "This sigil has been corrupted by the True Britannians"), + new TextDefinition(1041045, "The faction signup stone for the True Britannians"), + new TextDefinition(1041383, "The Faction Stone of the True Britannians"), + new TextDefinition(1011465, ": True Britannians"), + new TextDefinition(1005181, "Followers of Lord British will now be ignored."), + new TextDefinition(1005182, "Followers of Lord British will now be warned of their impending doom."), + new TextDefinition(1005183, "Followers of Lord British will now be attacked on sight."), + new StrongholdDefinition( + new[] + { + new Rectangle2D(1292, 1556, 25, 25), + new Rectangle2D(1292, 1676, 120, 25), + new Rectangle2D(1388, 1556, 25, 25), + new Rectangle2D(1317, 1563, 71, 18), + new Rectangle2D(1300, 1581, 105, 95), + new Rectangle2D(1405, 1612, 12, 21), + new Rectangle2D(1405, 1633, 11, 5) + }, + new Point3D(1419, 1622, 20), + new Point3D(1330, 1621, 50), + new[] + { + new Point3D(1328, 1627, 50), + new Point3D(1328, 1621, 50), + new Point3D(1334, 1627, 50), + new Point3D(1334, 1621, 50), + new Point3D(1340, 1627, 50), + new Point3D(1340, 1621, 50), + new Point3D(1345, 1621, 50), + new Point3D(1345, 1627, 50) + }), + new[] + { + new RankDefinition(10, 991, 8, new TextDefinition(1060794, "Knight of the Codex")), + new RankDefinition(9, 950, 7, new TextDefinition(1060793, "Knight of Virtue")), + new RankDefinition(8, 900, 6, new TextDefinition(1060792, "Crusader")), + new RankDefinition(7, 800, 6, new TextDefinition(1060792, "Crusader")), + new RankDefinition(6, 700, 5, new TextDefinition(1060791, "Sentinel")), + new RankDefinition(5, 600, 5, new TextDefinition(1060791, "Sentinel")), + new RankDefinition(4, 500, 5, new TextDefinition(1060791, "Sentinel")), + new RankDefinition(3, 400, 4, new TextDefinition(1060790, "Defender")), + new RankDefinition(2, 200, 4, new TextDefinition(1060790, "Defender")), + new RankDefinition(1, 0, 4, new TextDefinition(1060790, "Defender")) + }, + new[] + { + new GuardDefinition(typeof(FactionHenchman), 0x1403, 5000, 1000, 10, + new TextDefinition(1011526, "HENCHMAN"), new TextDefinition(1011510, "Hire Henchman")), + new GuardDefinition(typeof(FactionMercenary), 0x0F62, 6000, 2000, 10, + new TextDefinition(1011527, "MERCENARY"), new TextDefinition(1011511, "Hire Mercenary")), + new GuardDefinition(typeof(FactionKnight), 0x0F4D, 7000, 3000, 10, + new TextDefinition(1011528, "KNIGHT"), new TextDefinition(1011497, "Hire Knight")), + new GuardDefinition(typeof(FactionPaladin), 0x143F, 8000, 4000, 10, + new TextDefinition(1011529, "PALADIN"), new TextDefinition(1011498, "Hire Paladin")) + } + ); + } - Definition = - new FactionDefinition( - 2, - 1254, // dark purple - 2125, // gold - 2214, // join stone : gold - 2125, // broadcast : gold - 0x76, 0x3EB2, // war horse - "True Britannians", "true", "TB", - new TextDefinition( 1011536, "LORD BRITISH" ), - new TextDefinition( 1060771, "True Britannians faction" ), - new TextDefinition( 1011423, "
TRUE BRITANNIANS
" ), - new TextDefinition( 1011450, - "True Britannians are loyal to the throne of Lord British. They refuse " + - "to give up their homelands to the vile Minax, and detest the Shadowlords " + - "for their evil ways. In addition, the Council of Mages threatens the " + - "existence of their ruler, and as such they have armed themselves, and " + - "prepare for war with all." ), - new TextDefinition( 1011454, "This city is controlled by Lord British." ), - new TextDefinition( 1042254, "This sigil has been corrupted by the True Britannians" ), - new TextDefinition( 1041045, "The faction signup stone for the True Britannians" ), - new TextDefinition( 1041383, "The Faction Stone of the True Britannians" ), - new TextDefinition( 1011465, ": True Britannians" ), - new TextDefinition( 1005181, "Followers of Lord British will now be ignored." ), - new TextDefinition( 1005182, "Followers of Lord British will now be warned of their impending doom." ), - new TextDefinition( 1005183, "Followers of Lord British will now be attacked on sight." ), - new StrongholdDefinition( - new[] - { - new Rectangle2D( 1292, 1556, 25, 25 ), - new Rectangle2D( 1292, 1676, 120, 25 ), - new Rectangle2D( 1388, 1556, 25, 25 ), - new Rectangle2D( 1317, 1563, 71, 18 ), - new Rectangle2D( 1300, 1581, 105, 95 ), - new Rectangle2D( 1405, 1612, 12, 21 ), - new Rectangle2D( 1405, 1633, 11, 5 ) - }, - new Point3D( 1419, 1622, 20 ), - new Point3D( 1330, 1621, 50 ), - new[] - { - new Point3D( 1328, 1627, 50 ), - new Point3D( 1328, 1621, 50 ), - new Point3D( 1334, 1627, 50 ), - new Point3D( 1334, 1621, 50 ), - new Point3D( 1340, 1627, 50 ), - new Point3D( 1340, 1621, 50 ), - new Point3D( 1345, 1621, 50 ), - new Point3D( 1345, 1627, 50 ) - } ), - new[] - { - new RankDefinition( 10, 991, 8, new TextDefinition( 1060794, "Knight of the Codex" ) ), - new RankDefinition( 9, 950, 7, new TextDefinition( 1060793, "Knight of Virtue" ) ), - new RankDefinition( 8, 900, 6, new TextDefinition( 1060792, "Crusader" ) ), - new RankDefinition( 7, 800, 6, new TextDefinition( 1060792, "Crusader" ) ), - new RankDefinition( 6, 700, 5, new TextDefinition( 1060791, "Sentinel" ) ), - new RankDefinition( 5, 600, 5, new TextDefinition( 1060791, "Sentinel" ) ), - new RankDefinition( 4, 500, 5, new TextDefinition( 1060791, "Sentinel" ) ), - new RankDefinition( 3, 400, 4, new TextDefinition( 1060790, "Defender" ) ), - new RankDefinition( 2, 200, 4, new TextDefinition( 1060790, "Defender" ) ), - new RankDefinition( 1, 0, 4, new TextDefinition( 1060790, "Defender" ) ) - }, - new[] - { - new GuardDefinition( typeof( FactionHenchman ), 0x1403, 5000, 1000, 10, new TextDefinition( 1011526, "HENCHMAN" ), new TextDefinition( 1011510, "Hire Henchman" ) ), - new GuardDefinition( typeof( FactionMercenary ), 0x0F62, 6000, 2000, 10, new TextDefinition( 1011527, "MERCENARY" ), new TextDefinition( 1011511, "Hire Mercenary" ) ), - new GuardDefinition( typeof( FactionKnight ), 0x0F4D, 7000, 3000, 10, new TextDefinition( 1011528, "KNIGHT" ), new TextDefinition( 1011497, "Hire Knight" ) ), - new GuardDefinition( typeof( FactionPaladin ), 0x143F, 8000, 4000, 10, new TextDefinition( 1011529, "PALADIN" ), new TextDefinition( 1011498, "Hire Paladin" ) ), - } - ); - } - } + public static Faction Instance{ get; private set; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Britain.cs b/Scripts/Engines/Factions/Instances/Towns/Britain.cs index 6d3e657f9..5d93976ed 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Britain.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Britain.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Britain : Town - { - public Britain() - { - Definition = - new TownDefinition( - 0, - 0x1869, - "Britain", - "Britain", - new TextDefinition( 1011433, "BRITAIN" ), - new TextDefinition( 1011561, "TOWN STONE FOR BRITAIN" ), - new TextDefinition( 1041034, "The Faction Sigil Monolith of Britain" ), - new TextDefinition( 1041404, "The Faction Town Sigil Monolith of Britain" ), - new TextDefinition( 1041413, "Faction Town Stone of Britain" ), - new TextDefinition( 1041395, "Faction Town Sigil of Britain" ), - new TextDefinition( 1041386, "Corrupted Faction Town Sigil of Britain" ), - new Point3D( 1592, 1680, 10 ), - new Point3D( 1588, 1676, 10 ) ); - } - } + public class Britain : Town + { + public Britain() + { + Definition = + new TownDefinition( + 0, + 0x1869, + "Britain", + "Britain", + new TextDefinition(1011433, "BRITAIN"), + new TextDefinition(1011561, "TOWN STONE FOR BRITAIN"), + new TextDefinition(1041034, "The Faction Sigil Monolith of Britain"), + new TextDefinition(1041404, "The Faction Town Sigil Monolith of Britain"), + new TextDefinition(1041413, "Faction Town Stone of Britain"), + new TextDefinition(1041395, "Faction Town Sigil of Britain"), + new TextDefinition(1041386, "Corrupted Faction Town Sigil of Britain"), + new Point3D(1592, 1680, 10), + new Point3D(1588, 1676, 10)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Magincia.cs b/Scripts/Engines/Factions/Instances/Towns/Magincia.cs index 85d196104..965daced1 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Magincia.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Magincia.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Magincia : Town - { - public Magincia() - { - Definition = - new TownDefinition( - 7, - 0x1870, - "Magincia", - "Magincia", - new TextDefinition( 1011440, "MAGINCIA" ), - new TextDefinition( 1011568, "TOWN STONE FOR MAGINCIA" ), - new TextDefinition( 1041041, "The Faction Sigil Monolith of Magincia" ), - new TextDefinition( 1041411, "The Faction Town Sigil Monolith of Magincia" ), - new TextDefinition( 1041420, "Faction Town Stone of Magincia" ), - new TextDefinition( 1041402, "Faction Town Sigil of Magincia" ), - new TextDefinition( 1041393, "Corrupted Faction Town Sigil of Magincia" ), - new Point3D( 3714, 2235, 20 ), - new Point3D( 3712, 2230, 20 ) ); - } - } + public class Magincia : Town + { + public Magincia() + { + Definition = + new TownDefinition( + 7, + 0x1870, + "Magincia", + "Magincia", + new TextDefinition(1011440, "MAGINCIA"), + new TextDefinition(1011568, "TOWN STONE FOR MAGINCIA"), + new TextDefinition(1041041, "The Faction Sigil Monolith of Magincia"), + new TextDefinition(1041411, "The Faction Town Sigil Monolith of Magincia"), + new TextDefinition(1041420, "Faction Town Stone of Magincia"), + new TextDefinition(1041402, "Faction Town Sigil of Magincia"), + new TextDefinition(1041393, "Corrupted Faction Town Sigil of Magincia"), + new Point3D(3714, 2235, 20), + new Point3D(3712, 2230, 20)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Minoc.cs b/Scripts/Engines/Factions/Instances/Towns/Minoc.cs index 0d7caa0cc..8e7dffadd 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Minoc.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Minoc.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Minoc : Town - { - public Minoc() - { - Definition = - new TownDefinition( - 2, - 0x186B, - "Minoc", - "Minoc", - new TextDefinition( 1011437, "MINOC" ), - new TextDefinition( 1011564, "TOWN STONE FOR MINOC" ), - new TextDefinition( 1041036, "The Faction Sigil Monolith of Minoc" ), - new TextDefinition( 1041406, "The Faction Town Sigil Monolith Minoc" ), - new TextDefinition( 1041415, "Faction Town Stone of Minoc" ), - new TextDefinition( 1041397, "Faction Town Sigil of Minoc" ), - new TextDefinition( 1041388, "Corrupted Faction Town Sigil of Minoc" ), - new Point3D( 2471, 439, 15 ), - new Point3D( 2469, 445, 15 ) ); - } - } + public class Minoc : Town + { + public Minoc() + { + Definition = + new TownDefinition( + 2, + 0x186B, + "Minoc", + "Minoc", + new TextDefinition(1011437, "MINOC"), + new TextDefinition(1011564, "TOWN STONE FOR MINOC"), + new TextDefinition(1041036, "The Faction Sigil Monolith of Minoc"), + new TextDefinition(1041406, "The Faction Town Sigil Monolith Minoc"), + new TextDefinition(1041415, "Faction Town Stone of Minoc"), + new TextDefinition(1041397, "Faction Town Sigil of Minoc"), + new TextDefinition(1041388, "Corrupted Faction Town Sigil of Minoc"), + new Point3D(2471, 439, 15), + new Point3D(2469, 445, 15)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Moonglow.cs b/Scripts/Engines/Factions/Instances/Towns/Moonglow.cs index 95dc45d0e..622b5e314 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Moonglow.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Moonglow.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Moonglow : Town - { - public Moonglow() - { - Definition = - new TownDefinition( - 3, - 0x186C, - "Moonglow", - "Moonglow", - new TextDefinition( 1011435, "MOONGLOW" ), - new TextDefinition( 1011563, "TOWN STONE FOR MOONGLOW" ), - new TextDefinition( 1041037, "The Faction Sigil Monolith of Moonglow" ), - new TextDefinition( 1041407, "The Faction Town Sigil Monolith of Moonglow" ), - new TextDefinition( 1041416, "Faction Town Stone of Moonglow" ), - new TextDefinition( 1041398, "Faction Town Sigil of Moonglow" ), - new TextDefinition( 1041389, "Corrupted Faction Town Sigil of Moonglow" ), - new Point3D( 4436, 1083, 0 ), - new Point3D( 4432, 1086, 0 ) ); - } - } + public class Moonglow : Town + { + public Moonglow() + { + Definition = + new TownDefinition( + 3, + 0x186C, + "Moonglow", + "Moonglow", + new TextDefinition(1011435, "MOONGLOW"), + new TextDefinition(1011563, "TOWN STONE FOR MOONGLOW"), + new TextDefinition(1041037, "The Faction Sigil Monolith of Moonglow"), + new TextDefinition(1041407, "The Faction Town Sigil Monolith of Moonglow"), + new TextDefinition(1041416, "Faction Town Stone of Moonglow"), + new TextDefinition(1041398, "Faction Town Sigil of Moonglow"), + new TextDefinition(1041389, "Corrupted Faction Town Sigil of Moonglow"), + new Point3D(4436, 1083, 0), + new Point3D(4432, 1086, 0)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/SkaraBrae.cs b/Scripts/Engines/Factions/Instances/Towns/SkaraBrae.cs index 2f9a6fac7..ec2d1e478 100644 --- a/Scripts/Engines/Factions/Instances/Towns/SkaraBrae.cs +++ b/Scripts/Engines/Factions/Instances/Towns/SkaraBrae.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class SkaraBrae : Town - { - public SkaraBrae() - { - Definition = - new TownDefinition( - 6, - 0x186F, - "Skara Brae", - "Skara Brae", - new TextDefinition( 1011439, "SKARA BRAE" ), - new TextDefinition( 1011567, "TOWN STONE FOR SKARA BRAE" ), - new TextDefinition( 1041040, "The Faction Sigil Monolith of Skara Brae" ), - new TextDefinition( 1041410, "The Faction Town Sigil Monolith of Skara Brae" ), - new TextDefinition( 1041419, "Faction Town Stone of Skara Brae" ), - new TextDefinition( 1041401, "Faction Town Sigil of Skara Brae" ), - new TextDefinition( 1041392, "Corrupted Faction Town Sigil of Skara Brae" ), - new Point3D( 576, 2200, 0 ), - new Point3D( 572, 2196, 0 ) ); - } - } + public class SkaraBrae : Town + { + public SkaraBrae() + { + Definition = + new TownDefinition( + 6, + 0x186F, + "Skara Brae", + "Skara Brae", + new TextDefinition(1011439, "SKARA BRAE"), + new TextDefinition(1011567, "TOWN STONE FOR SKARA BRAE"), + new TextDefinition(1041040, "The Faction Sigil Monolith of Skara Brae"), + new TextDefinition(1041410, "The Faction Town Sigil Monolith of Skara Brae"), + new TextDefinition(1041419, "Faction Town Stone of Skara Brae"), + new TextDefinition(1041401, "Faction Town Sigil of Skara Brae"), + new TextDefinition(1041392, "Corrupted Faction Town Sigil of Skara Brae"), + new Point3D(576, 2200, 0), + new Point3D(572, 2196, 0)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Trinsic.cs b/Scripts/Engines/Factions/Instances/Towns/Trinsic.cs index 73c2f977a..fbf21a9b2 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Trinsic.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Trinsic.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Trinsic : Town - { - public Trinsic() - { - Definition = - new TownDefinition( - 1, - 0x186A, - "Trinsic", - "Trinsic", - new TextDefinition( 1011434, "TRINSIC" ), - new TextDefinition( 1011562, "TOWN STONE FOR TRINSIC" ), - new TextDefinition( 1041035, "The Faction Sigil Monolith of Trinsic" ), - new TextDefinition( 1041405, "The Faction Town Sigil Monolith of Trinsic" ), - new TextDefinition( 1041414, "Faction Town Stone of Trinsic" ), - new TextDefinition( 1041396, "Faction Town Sigil of Trinsic" ), - new TextDefinition( 1041387, "Corrupted Faction Town Sigil of Trinsic" ), - new Point3D( 1914, 2717, 20 ), - new Point3D( 1909, 2720, 20 ) ); - } - } + public class Trinsic : Town + { + public Trinsic() + { + Definition = + new TownDefinition( + 1, + 0x186A, + "Trinsic", + "Trinsic", + new TextDefinition(1011434, "TRINSIC"), + new TextDefinition(1011562, "TOWN STONE FOR TRINSIC"), + new TextDefinition(1041035, "The Faction Sigil Monolith of Trinsic"), + new TextDefinition(1041405, "The Faction Town Sigil Monolith of Trinsic"), + new TextDefinition(1041414, "Faction Town Stone of Trinsic"), + new TextDefinition(1041396, "Faction Town Sigil of Trinsic"), + new TextDefinition(1041387, "Corrupted Faction Town Sigil of Trinsic"), + new Point3D(1914, 2717, 20), + new Point3D(1909, 2720, 20)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Vesper.cs b/Scripts/Engines/Factions/Instances/Towns/Vesper.cs index 41843fda8..9e0a2c6e4 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Vesper.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Vesper.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Vesper : Town - { - public Vesper() - { - Definition = - new TownDefinition( - 5, - 0x186E, - "Vesper", - "Vesper", - new TextDefinition( 1016413, "VESPER" ), - new TextDefinition( 1011566, "TOWN STONE FOR VESPER" ), - new TextDefinition( 1041039, "The Faction Sigil Monolith of Vesper" ), - new TextDefinition( 1041409, "The Faction Town Sigil Monolith of Vesper" ), - new TextDefinition( 1041418, "Faction Town Stone of Vesper" ), - new TextDefinition( 1041400, "Faction Town Sigil of Vesper" ), - new TextDefinition( 1041391, "Corrupted Faction Town Sigil of Vesper" ), - new Point3D( 2982, 818, 0 ), - new Point3D( 2985, 821, 0 ) ); - } - } + public class Vesper : Town + { + public Vesper() + { + Definition = + new TownDefinition( + 5, + 0x186E, + "Vesper", + "Vesper", + new TextDefinition(1016413, "VESPER"), + new TextDefinition(1011566, "TOWN STONE FOR VESPER"), + new TextDefinition(1041039, "The Faction Sigil Monolith of Vesper"), + new TextDefinition(1041409, "The Faction Town Sigil Monolith of Vesper"), + new TextDefinition(1041418, "Faction Town Stone of Vesper"), + new TextDefinition(1041400, "Faction Town Sigil of Vesper"), + new TextDefinition(1041391, "Corrupted Faction Town Sigil of Vesper"), + new Point3D(2982, 818, 0), + new Point3D(2985, 821, 0)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Instances/Towns/Yew.cs b/Scripts/Engines/Factions/Instances/Towns/Yew.cs index a38218d5d..f63c8ab32 100644 --- a/Scripts/Engines/Factions/Instances/Towns/Yew.cs +++ b/Scripts/Engines/Factions/Instances/Towns/Yew.cs @@ -1,24 +1,24 @@ namespace Server.Factions { - public class Yew : Town - { - public Yew() - { - Definition = - new TownDefinition( - 4, - 0x186D, - "Yew", - "Yew", - new TextDefinition( 1011438, "YEW" ), - new TextDefinition( 1011565, "TOWN STONE FOR YEW" ), - new TextDefinition( 1041038, "The Faction Sigil Monolith of Yew" ), - new TextDefinition( 1041408, "The Faction Town Sigil Monolith of Yew" ), - new TextDefinition( 1041417, "Faction Town Stone of Yew" ), - new TextDefinition( 1041399, "Faction Town Sigil of Yew" ), - new TextDefinition( 1041390, "Corrupted Faction Town Sigil of Yew" ), - new Point3D( 548, 979, 0 ), - new Point3D( 542, 980, 0 ) ); - } - } + public class Yew : Town + { + public Yew() + { + Definition = + new TownDefinition( + 4, + 0x186D, + "Yew", + "Yew", + new TextDefinition(1011438, "YEW"), + new TextDefinition(1011565, "TOWN STONE FOR YEW"), + new TextDefinition(1041038, "The Faction Sigil Monolith of Yew"), + new TextDefinition(1041408, "The Faction Town Sigil Monolith of Yew"), + new TextDefinition(1041417, "Faction Town Stone of Yew"), + new TextDefinition(1041399, "Faction Town Sigil of Yew"), + new TextDefinition(1041390, "Corrupted Faction Town Sigil of Yew"), + new Point3D(548, 979, 0), + new Point3D(542, 980, 0)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/BaseMonolith.cs b/Scripts/Engines/Factions/Items/BaseMonolith.cs index 7dec0555d..9675b421c 100644 --- a/Scripts/Engines/Factions/Items/BaseMonolith.cs +++ b/Scripts/Engines/Factions/Items/BaseMonolith.cs @@ -2,128 +2,128 @@ using System.Collections.Generic; namespace Server.Factions { - public abstract class BaseMonolith : BaseSystemController - { - private Town m_Town; - private Faction m_Faction; - private Sigil m_Sigil; + public abstract class BaseMonolith : BaseSystemController + { + private Faction m_Faction; + private Sigil m_Sigil; + private Town m_Town; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Sigil Sigil - { - get => m_Sigil; - set - { - if ( m_Sigil == value ) - return; + public BaseMonolith(Town town, Faction faction) : base(0x1183) + { + Movable = false; + Town = town; + Faction = faction; + Monoliths.Add(this); + } - m_Sigil = value; + public BaseMonolith(Serial serial) : base(serial) + { + Monoliths.Add(this); + } - if ( m_Sigil?.LastMonolith != null && m_Sigil.LastMonolith != this && m_Sigil.LastMonolith.Sigil == m_Sigil ) - m_Sigil.LastMonolith.Sigil = null; + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Sigil Sigil + { + get => m_Sigil; + set + { + if (m_Sigil == value) + return; - if ( m_Sigil != null ) - m_Sigil.LastMonolith = this; + m_Sigil = value; - UpdateSigil(); - } - } + if (m_Sigil?.LastMonolith != null && m_Sigil.LastMonolith != this && m_Sigil.LastMonolith.Sigil == m_Sigil) + m_Sigil.LastMonolith.Sigil = null; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Town Town - { - get => m_Town; - set - { - m_Town = value; - OnTownChanged(); - } - } + if (m_Sigil != null) + m_Sigil.LastMonolith = this; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Faction Faction - { - get => m_Faction; - set - { - m_Faction = value; - Hue = m_Faction?.Definition.HuePrimary ?? 0; - } - } + UpdateSigil(); + } + } - public override void OnLocationChange( Point3D oldLocation ) - { - base.OnLocationChange( oldLocation ); - UpdateSigil(); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Town Town + { + get => m_Town; + set + { + m_Town = value; + OnTownChanged(); + } + } - public override void OnMapChange() - { - base.OnMapChange(); - UpdateSigil(); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Faction Faction + { + get => m_Faction; + set + { + m_Faction = value; + Hue = m_Faction?.Definition.HuePrimary ?? 0; + } + } - public virtual void UpdateSigil() - { - if ( m_Sigil == null || m_Sigil.Deleted ) - return; + public static List Monoliths{ get; set; } = new List(); - m_Sigil.MoveToWorld( new Point3D( X, Y, Z + 18 ), Map ); - } + public override void OnLocationChange(Point3D oldLocation) + { + base.OnLocationChange(oldLocation); + UpdateSigil(); + } - public virtual void OnTownChanged() - { - } + public override void OnMapChange() + { + base.OnMapChange(); + UpdateSigil(); + } - public BaseMonolith( Town town, Faction faction ) : base( 0x1183 ) - { - Movable = false; - Town = town; - Faction = faction; - Monoliths.Add( this ); - } + public virtual void UpdateSigil() + { + if (m_Sigil == null || m_Sigil.Deleted) + return; - public BaseMonolith( Serial serial ) : base( serial ) - { - Monoliths.Add( this ); - } + m_Sigil.MoveToWorld(new Point3D(X, Y, Z + 18), Map); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); - Monoliths.Remove( this ); - } + public virtual void OnTownChanged() + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnAfterDelete() + { + base.OnAfterDelete(); + Monoliths.Remove(this); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Town.WriteReference( writer, m_Town ); - Faction.WriteReference( writer, m_Faction ); + writer.Write(0); // version - writer.Write( (Item) m_Sigil ); - } + Town.WriteReference(writer, m_Town); + Faction.WriteReference(writer, m_Faction); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Sigil); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - Town = Town.ReadReference( reader ); - Faction = Faction.ReadReference( reader ); - m_Sigil = reader.ReadItem() as Sigil; - break; - } - } - } + int version = reader.ReadInt(); - public static List Monoliths { get; set; } = new List(); - } + switch (version) + { + case 0: + { + Town = Town.ReadReference(reader); + Faction = Faction.ReadReference(reader); + m_Sigil = reader.ReadItem() as Sigil; + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/BaseSystemController.cs b/Scripts/Engines/Factions/Items/BaseSystemController.cs index 29dbfe819..964ee8b0a 100644 --- a/Scripts/Engines/Factions/Items/BaseSystemController.cs +++ b/Scripts/Engines/Factions/Items/BaseSystemController.cs @@ -1,64 +1,64 @@ namespace Server.Factions { - public abstract class BaseSystemController : Item - { - private int m_LabelNumber; + public abstract class BaseSystemController : Item + { + private int m_LabelNumber; - public virtual int DefaultLabelNumber => base.LabelNumber; - public new virtual string DefaultName => null; + public BaseSystemController(int itemID) : base(itemID) + { + } - public override int LabelNumber - { - get - { - if ( m_LabelNumber > 0 ) - return m_LabelNumber; + public BaseSystemController(Serial serial) : base(serial) + { + } - return DefaultLabelNumber; - } - } + public virtual int DefaultLabelNumber => base.LabelNumber; + public new virtual string DefaultName => null; - public virtual void AssignName( TextDefinition name ) - { - if ( name != null && name.Number > 0 ) - { - m_LabelNumber = name.Number; - Name = null; - } - else if ( name?.String != null ) - { - m_LabelNumber = 0; - Name = name.String; - } - else - { - m_LabelNumber = 0; - Name = DefaultName; - } + public override int LabelNumber + { + get + { + if (m_LabelNumber > 0) + return m_LabelNumber; - InvalidateProperties(); - } + return DefaultLabelNumber; + } + } - public BaseSystemController( int itemID ) : base( itemID ) - { - } + public virtual void AssignName(TextDefinition name) + { + if (name != null && name.Number > 0) + { + m_LabelNumber = name.Number; + Name = null; + } + else if (name?.String != null) + { + m_LabelNumber = 0; + Name = name.String; + } + else + { + m_LabelNumber = 0; + Name = DefaultName; + } - public BaseSystemController( Serial serial ) : base( serial ) - { - } + InvalidateProperties(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/FactionStone.cs b/Scripts/Engines/Factions/Items/FactionStone.cs index ed0a1d287..aeecf5014 100644 --- a/Scripts/Engines/Factions/Items/FactionStone.cs +++ b/Scripts/Engines/Factions/Items/FactionStone.cs @@ -3,101 +3,102 @@ using Server.Network; namespace Server.Factions { - public class FactionStone : BaseSystemController - { - private Faction m_Faction; + public class FactionStone : BaseSystemController + { + private Faction m_Faction; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Faction Faction - { - get => m_Faction; - set - { - m_Faction = value; + [Constructible] + public FactionStone() : this(null) + { + } - AssignName( m_Faction?.Definition.FactionStoneName ); - } - } + [Constructible] + public FactionStone(Faction faction) : base(0xEDC) + { + Movable = false; + Faction = faction; + } - public override string DefaultName => "faction stone"; + public FactionStone(Serial serial) : base(serial) + { + } - [Constructible] - public FactionStone() : this( null ) - { - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Faction Faction + { + get => m_Faction; + set + { + m_Faction = value; - [Constructible] - public FactionStone( Faction faction ) : base( 0xEDC ) - { - Movable = false; - Faction = faction; - } + AssignName(m_Faction?.Definition.FactionStoneName); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_Faction == null ) - return; + public override string DefaultName => "faction stone"; - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - else if ( FactionGump.Exists( from ) ) - { - from.SendLocalizedMessage( 1042160 ); // You already have a faction menu open. - } - else if ( from is PlayerMobile mobile ) - { - Faction existingFaction = Faction.Find( mobile ); + public override void OnDoubleClick(Mobile from) + { + if (m_Faction == null) + return; - if ( existingFaction == m_Faction || mobile.AccessLevel >= AccessLevel.GameMaster ) - { - PlayerState pl = PlayerState.Find( mobile ); + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + else if (FactionGump.Exists(from)) + { + from.SendLocalizedMessage(1042160); // You already have a faction menu open. + } + else if (from is PlayerMobile mobile) + { + Faction existingFaction = Faction.Find(mobile); - if ( pl != null && pl.IsLeaving ) - mobile.SendLocalizedMessage( 1005051 ); // You cannot use the faction stone until you have finished quitting your current faction - else - mobile.SendGump( new FactionStoneGump( mobile, m_Faction ) ); - } - else if ( existingFaction != null ) - { - // TODO: Validate - mobile.SendLocalizedMessage( 1005053 ); // This is not your faction stone! - } - else - { - mobile.SendGump( new JoinStoneGump( mobile, m_Faction ) ); - } - } - } + if (existingFaction == m_Faction || mobile.AccessLevel >= AccessLevel.GameMaster) + { + PlayerState pl = PlayerState.Find(mobile); - public FactionStone( Serial serial ) : base( serial ) - { - } + if (pl != null && pl.IsLeaving) + mobile.SendLocalizedMessage( + 1005051); // You cannot use the faction stone until you have finished quitting your current faction + else + mobile.SendGump(new FactionStoneGump(mobile, m_Faction)); + } + else if (existingFaction != null) + { + // TODO: Validate + mobile.SendLocalizedMessage(1005053); // This is not your faction stone! + } + else + { + mobile.SendGump(new JoinStoneGump(mobile, m_Faction)); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - Faction.WriteReference( writer, m_Faction ); - } + Faction.WriteReference(writer, m_Faction); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Faction = Faction.ReadReference( reader ); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Faction = Faction.ReadReference(reader); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/JoinStone.cs b/Scripts/Engines/Factions/Items/JoinStone.cs index caf370490..3a29610fb 100644 --- a/Scripts/Engines/Factions/Items/JoinStone.cs +++ b/Scripts/Engines/Factions/Items/JoinStone.cs @@ -3,77 +3,77 @@ using Server.Network; namespace Server.Factions { - public class JoinStone : BaseSystemController - { - private Faction m_Faction; + public class JoinStone : BaseSystemController + { + private Faction m_Faction; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Faction Faction - { - get => m_Faction; - set - { - m_Faction = value; + [Constructible] + public JoinStone() : this(null) + { + } - Hue = m_Faction?.Definition.HueJoin ?? 0; - AssignName( m_Faction?.Definition.SignupName ); - } - } + [Constructible] + public JoinStone(Faction faction) : base(0xEDC) + { + Movable = false; + Faction = faction; + } - public override string DefaultName => "faction signup stone"; + public JoinStone(Serial serial) : base(serial) + { + } - [Constructible] - public JoinStone() : this( null ) - { - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Faction Faction + { + get => m_Faction; + set + { + m_Faction = value; - [Constructible] - public JoinStone( Faction faction ) : base( 0xEDC ) - { - Movable = false; - Faction = faction; - } + Hue = m_Faction?.Definition.HueJoin ?? 0; + AssignName(m_Faction?.Definition.SignupName); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_Faction == null ) - return; + public override string DefaultName => "faction signup stone"; - if ( !from.InRange( GetWorldLocation(), 2 ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else if ( FactionGump.Exists( from ) ) - from.SendLocalizedMessage( 1042160 ); // You already have a faction menu open. - else if ( Faction.Find( from ) == null && from is PlayerMobile mobile ) - mobile.SendGump( new JoinStoneGump( mobile, m_Faction ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (m_Faction == null) + return; - public JoinStone( Serial serial ) : base( serial ) - { - } + if (!from.InRange(GetWorldLocation(), 2)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (FactionGump.Exists(from)) + from.SendLocalizedMessage(1042160); // You already have a faction menu open. + else if (Faction.Find(from) == null && from is PlayerMobile mobile) + mobile.SendGump(new JoinStoneGump(mobile, m_Faction)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - Faction.WriteReference( writer, m_Faction ); - } + Faction.WriteReference(writer, m_Faction); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Faction = Faction.ReadReference( reader ); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Faction = Faction.ReadReference(reader); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Power Faction Items/BloodRose.cs b/Scripts/Engines/Factions/Items/Power Faction Items/BloodRose.cs index 68c63934a..a48862335 100644 --- a/Scripts/Engines/Factions/Items/Power Faction Items/BloodRose.cs +++ b/Scripts/Engines/Factions/Items/Power Faction Items/BloodRose.cs @@ -1,52 +1,59 @@ using System; -namespace Server { - public sealed class BloodRose : PowerFactionItem { - public override string DefaultName => "blood rose"; +namespace Server +{ + public sealed class BloodRose : PowerFactionItem + { + public BloodRose() + : base(Utility.RandomList(6378, 9035)) + { + Hue = 2118; + } - public BloodRose() - : base( Utility.RandomList( 6378, 9035 ) ) { - Hue = 2118; - } + public BloodRose(Serial serial) + : base(serial) + { + } - public BloodRose( Serial serial ) - : base( serial ) { - } + public override string DefaultName => "blood rose"; - public override bool Use( Mobile from ) { - if ( from.GetStatMod( "blood-rose" ) == null ) { - from.PlaySound( Utility.Random( 0x3A, 3 ) ); + public override bool Use(Mobile from) + { + if (from.GetStatMod("blood-rose") == null) + { + from.PlaySound(Utility.Random(0x3A, 3)); - if ( from.Body.IsHuman && !from.Mounted ) { - from.Animate( 34, 5, 1, true, false, 0 ); - } + if (from.Body.IsHuman && !from.Mounted) from.Animate(34, 5, 1, true, false, 0); - int amount = Utility.Dice( 3, 3, 3 ); - int time = Utility.RandomMinMax( 5, 30 ); + int amount = Utility.Dice(3, 3, 3); + int time = Utility.RandomMinMax(5, 30); - from.FixedParticles( 0x373A, 10, 15, 5018, EffectLayer.Waist ); + from.FixedParticles(0x373A, 10, 15, 5018, EffectLayer.Waist); - from.PlaySound( 0x1EE ); - from.AddStatMod( new StatMod( StatType.All, "blood-rose", amount, TimeSpan.FromMinutes( time ) ) ); + from.PlaySound(0x1EE); + from.AddStatMod(new StatMod(StatType.All, "blood-rose", amount, TimeSpan.FromMinutes(time))); - return true; - } + return true; + } - from.SendLocalizedMessage( 1062927 ); // You have eaten one of these recently and eating another would provide no benefit. + from.SendLocalizedMessage( + 1062927); // You have eaten one of these recently and eating another would provide no benefit. - return false; - } + return false; + } - public override void Serialize( GenericWriter writer ) { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( ( int ) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Power Faction Items/ClarityPotion.cs b/Scripts/Engines/Factions/Items/Power Faction Items/ClarityPotion.cs index 20ff5aae0..d647c9361 100644 --- a/Scripts/Engines/Factions/Items/Power Faction Items/ClarityPotion.cs +++ b/Scripts/Engines/Factions/Items/Power Faction Items/ClarityPotion.cs @@ -1,62 +1,67 @@ using System; -namespace Server { - public sealed class ClarityPotion : PowerFactionItem { - public override string DefaultName => "clarity potion"; +namespace Server +{ + public sealed class ClarityPotion : PowerFactionItem + { + public ClarityPotion() + : base(3628) + { + Hue = 1154; + } - public ClarityPotion() - : base( 3628 ) { - Hue = 1154; - } + public ClarityPotion(Serial serial) + : base(serial) + { + } - public ClarityPotion( Serial serial ) - : base( serial ) { - } + public override string DefaultName => "clarity potion"; - public override bool Use( Mobile from ) { - if ( from.BeginAction( typeof( ClarityPotion ) ) ) { - int amount = Utility.Dice( 3, 3, 3 ); - int time = Utility.RandomMinMax( 5, 30 ); + public override bool Use(Mobile from) + { + if (from.BeginAction(typeof(ClarityPotion))) + { + int amount = Utility.Dice(3, 3, 3); + int time = Utility.RandomMinMax(5, 30); - from.PlaySound( 0x2D6 ); + from.PlaySound(0x2D6); - if ( from.Body.IsHuman ) { - from.Animate( 34, 5, 1, true, false, 0 ); - } + if (from.Body.IsHuman) from.Animate(34, 5, 1, true, false, 0); - from.FixedParticles( 0x375A, 10, 15, 5011, EffectLayer.Head ); - from.PlaySound( 0x1EB ); + from.FixedParticles(0x375A, 10, 15, 5011, EffectLayer.Head); + from.PlaySound(0x1EB); - StatMod mod = from.GetStatMod( "Concussion" ); + StatMod mod = from.GetStatMod("Concussion"); - if ( mod != null ) { - from.RemoveStatMod( "Concussion" ); - from.Mana -= mod.Offset; - } + if (mod != null) + { + from.RemoveStatMod("Concussion"); + from.Mana -= mod.Offset; + } - from.PlaySound( 0x1EE ); - from.AddStatMod( new StatMod( StatType.Int, "clarity-potion", amount, TimeSpan.FromMinutes( time ) ) ); + from.PlaySound(0x1EE); + from.AddStatMod(new StatMod(StatType.Int, "clarity-potion", amount, TimeSpan.FromMinutes(time))); - Timer.DelayCall( TimeSpan.FromMinutes( time ), delegate { - from.EndAction( typeof( ClarityPotion ) ); - } ); + Timer.DelayCall(TimeSpan.FromMinutes(time), delegate { from.EndAction(typeof(ClarityPotion)); }); - return true; - } + return true; + } - return false; - } + return false; + } - public override void Serialize( GenericWriter writer ) { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( ( int ) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Power Faction Items/GemOfEmpowerment.cs b/Scripts/Engines/Factions/Items/Power Faction Items/GemOfEmpowerment.cs index cb99b479b..e190614e5 100644 --- a/Scripts/Engines/Factions/Items/Power Faction Items/GemOfEmpowerment.cs +++ b/Scripts/Engines/Factions/Items/Power Faction Items/GemOfEmpowerment.cs @@ -1,42 +1,51 @@ using Server.Factions; +using Server.Network; -namespace Server { - public sealed class GemOfEmpowerment : PowerFactionItem { - public override string DefaultName => "gem of empowerment"; +namespace Server +{ + public sealed class GemOfEmpowerment : PowerFactionItem + { + public GemOfEmpowerment() + : base(7955) + { + Hue = 1154; + } - public GemOfEmpowerment() - : base( 7955 ) { - Hue = 1154; - } + public GemOfEmpowerment(Serial serial) + : base(serial) + { + } - public GemOfEmpowerment( Serial serial ) - : base( serial ) { - } + public override string DefaultName => "gem of empowerment"; - public override bool Use( Mobile from ) { - if ( Faction.ClearSkillLoss( from ) ) { - from.LocalOverheadMessage( Network.MessageType.Regular, 2219, false, "The gem shatters as you invoke its power." ); - from.PlaySound( 909 ); + public override bool Use(Mobile from) + { + if (Faction.ClearSkillLoss(from)) + { + from.LocalOverheadMessage(MessageType.Regular, 2219, false, "The gem shatters as you invoke its power."); + from.PlaySound(909); - from.FixedEffect( 0x373A, 10, 30 ); - from.PlaySound( 0x209 ); + from.FixedEffect(0x373A, 10, 30); + from.PlaySound(0x209); - return true; - } + return true; + } - return false; - } + return false; + } - public override void Serialize( GenericWriter writer ) { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( ( int ) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Power Faction Items/PowerFactionItem.cs b/Scripts/Engines/Factions/Items/Power Faction Items/PowerFactionItem.cs index bd0591b11..e794afd6c 100644 --- a/Scripts/Engines/Factions/Items/Power Faction Items/PowerFactionItem.cs +++ b/Scripts/Engines/Factions/Items/Power Faction Items/PowerFactionItem.cs @@ -1,151 +1,186 @@ using System; -using Server.Mobiles; -using Server.Factions; using System.IO; +using Server.Factions; +using Server.Mobiles; +using Server.Network; -namespace Server { - public abstract class PowerFactionItem : Item { - public abstract bool Use( Mobile mob ); +namespace Server +{ + public abstract class PowerFactionItem : Item + { + private static WeightedItem[] _items = + { + new WeightedItem(30, typeof(GemOfEmpowerment)), + new WeightedItem(25, typeof(BloodRose)), + new WeightedItem(20, typeof(ClarityPotion)), + new WeightedItem(15, typeof(UrnOfAscension)), + new WeightedItem(10, typeof(StormsEye)) + }; - private sealed class DestructionTimer : Timer { - private Mobile _mobile; + public PowerFactionItem(int itemId) + : base(itemId) + { + } - private bool _screamed; + public PowerFactionItem(Serial serial) + : base(serial) + { + } - public DestructionTimer( Mobile mob ) - : base( TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 0.1 ), 10 ) { - _mobile = mob; - } + public abstract bool Use(Mobile mob); - protected override void OnTick() { - if ( _mobile.Alive ) { - if ( !_screamed ) { - _screamed = true; + public static void CheckSpawn(Mobile killer, Mobile victim) + { + if (killer != null && victim != null) + { + PlayerState ps = PlayerState.Find(victim); - _mobile.PlaySound( _mobile.Female ? 814 : 1088 ); - _mobile.PublicOverheadMessage( Network.MessageType.Regular, 2118, false, "Aaaaah!" ); - } + if (ps != null) + { + int chance = ps.Rank.Rank; - _mobile.Damage( Utility.Dice( 2, 6, 0 ) ); - } - } - } + if (chance > Utility.Random(100)) + { + int weight = 0; - private sealed class WeightedItem { - public int Weight { get; } + foreach (WeightedItem item in _items) weight += item.Weight; - public Type Type { get; } + weight = Utility.Random(weight); - public WeightedItem( int weight, Type type ) { - Weight = weight; - Type = type; - } + foreach (WeightedItem item in _items) + { + if (weight < item.Weight) + { + Item obj = item.Construct(); - public Item Construct() { - return Activator.CreateInstance( Type ) as Item; - } - } + if (obj != null) + { + killer.AddToBackpack(obj); - private static WeightedItem[] _items = { - new WeightedItem( 30, typeof( GemOfEmpowerment ) ), - new WeightedItem( 25, typeof( BloodRose ) ), - new WeightedItem( 20, typeof( ClarityPotion ) ), - new WeightedItem( 15, typeof( UrnOfAscension ) ), - new WeightedItem( 10, typeof( StormsEye ) ) - }; + killer.SendSound(1470); + killer.LocalOverheadMessage( + MessageType.Regular, 2119, false, + "You notice a strange item on the corpse, and decide to pick it up." + ); - public static void CheckSpawn( Mobile killer, Mobile victim ) { - if ( killer != null && victim != null ) { - PlayerState ps = PlayerState.Find( victim ); + try + { + using (StreamWriter op = new StreamWriter("faction-power-items.log", true)) + { + op.WriteLine("{0}\t{1}\t{2}\t{3}", DateTime.UtcNow, killer, victim, obj); + } + } + catch + { + } + } - if ( ps != null ) { - int chance = ps.Rank.Rank; + break; + } - if ( chance > Utility.Random( 100 ) ) { - int weight = 0; + weight -= item.Weight; + } + } + } + } + } - foreach ( WeightedItem item in _items ) { - weight += item.Weight; - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + else if (from is PlayerMobile mobile && mobile.DuelContext != null) + { + mobile.SendMessage("You can't use that."); + } + else if (Faction.Find(from) == null) + { + from.LocalOverheadMessage(MessageType.Regular, 2119, false, + "The object vanishes from your hands as you touch it."); - weight = Utility.Random( weight ); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), + delegate + { + from.LocalOverheadMessage(MessageType.Regular, 2118, false, + "You feel a strange tingling sensation throughout your body."); + }); - foreach ( WeightedItem item in _items ) - { - if ( weight < item.Weight ) { - Item obj = item.Construct(); + Timer.DelayCall(TimeSpan.FromSeconds(4.0), + delegate { from.LocalOverheadMessage(MessageType.Regular, 2118, false, "Your skin begins to burn."); }); - if ( obj != null ) { - killer.AddToBackpack( obj ); + new DestructionTimer(from).Start(); + Delete(); - killer.SendSound( 1470 ); - killer.LocalOverheadMessage( - Network.MessageType.Regular, 2119, false, - "You notice a strange item on the corpse, and decide to pick it up." - ); + //from.SendMessage( "You must be in a faction to use this item." ); + } + else if (Use(from)) + { + from.RevealingAction(); + Consume(); + } + } - try { - using ( StreamWriter op = new StreamWriter( "faction-power-items.log", true ) ) { - op.WriteLine( "{0}\t{1}\t{2}\t{3}", DateTime.UtcNow, killer, victim, obj ); - } - } catch { - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - break; - } + writer.WriteEncodedInt(0); // version + } - weight -= item.Weight; - } - } - } - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnDoubleClick( Mobile from ) { - if ( !IsChildOf( from.Backpack ) ) { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } else if ( from is PlayerMobile mobile && mobile.DuelContext != null ) { - mobile.SendMessage( "You can't use that." ); - } else if ( Faction.Find( from ) == null ) { - from.LocalOverheadMessage( Network.MessageType.Regular, 2119, false, "The object vanishes from your hands as you touch it." ); + int version = reader.ReadEncodedInt(); + } - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), delegate { - from.LocalOverheadMessage( Network.MessageType.Regular, 2118, false, "You feel a strange tingling sensation throughout your body." ); - } ); + private sealed class DestructionTimer : Timer + { + private Mobile _mobile; - Timer.DelayCall( TimeSpan.FromSeconds( 4.0 ), delegate { - from.LocalOverheadMessage( Network.MessageType.Regular, 2118, false, "Your skin begins to burn." ); - } ); + private bool _screamed; - new DestructionTimer( from ).Start(); - Delete(); + public DestructionTimer(Mobile mob) + : base(TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(0.1), 10) + { + _mobile = mob; + } - //from.SendMessage( "You must be in a faction to use this item." ); - } else if ( Use( from ) ) { - from.RevealingAction(); - Consume(); - } - } + protected override void OnTick() + { + if (_mobile.Alive) + { + if (!_screamed) + { + _screamed = true; - public PowerFactionItem( int itemId ) - : base( itemId ) { - } + _mobile.PlaySound(_mobile.Female ? 814 : 1088); + _mobile.PublicOverheadMessage(MessageType.Regular, 2118, false, "Aaaaah!"); + } - public PowerFactionItem( Serial serial ) - : base( serial ) { - } + _mobile.Damage(Utility.Dice(2, 6, 0)); + } + } + } - public override void Serialize( GenericWriter writer ) { - base.Serialize( writer ); + private sealed class WeightedItem + { + public WeightedItem(int weight, Type type) + { + Weight = weight; + Type = type; + } - writer.WriteEncodedInt( ( int ) 0 ); // version - } + public int Weight{ get; } - public override void Deserialize( GenericReader reader ) { - base.Deserialize( reader ); + public Type Type{ get; } - int version = reader.ReadEncodedInt(); - } - } -} + public Item Construct() + { + return Activator.CreateInstance(Type) as Item; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Power Faction Items/StormsEye.cs b/Scripts/Engines/Factions/Items/Power Faction Items/StormsEye.cs index bd0249b91..3aa5a6b5a 100644 --- a/Scripts/Engines/Factions/Items/Power Faction Items/StormsEye.cs +++ b/Scripts/Engines/Factions/Items/Power Faction Items/StormsEye.cs @@ -1,106 +1,115 @@ using System; using System.Collections.Generic; -using Server.Spells; using Server.Factions; +using Server.Spells; +using Server.Targeting; -namespace Server { - public sealed class StormsEye : PowerFactionItem { - public override string DefaultName => "storms eye"; +namespace Server +{ + public sealed class StormsEye : PowerFactionItem + { + public StormsEye() + : base(3967) + { + Hue = 1165; + } - public StormsEye() - : base( 3967 ) { - Hue = 1165; - } + public StormsEye(Serial serial) + : base(serial) + { + } - public StormsEye( Serial serial ) - : base( serial ) { - } + public override string DefaultName => "storms eye"; - public override bool Use( Mobile user ) { - if ( Movable ) { - user.BeginTarget( 12, true, Targeting.TargetFlags.None, delegate( Mobile from, object obj ) { - if ( Movable && !Deleted ) { - if ( obj is IPoint3D pt ) { - SpellHelper.GetSurfaceTop( ref pt ); + public override bool Use(Mobile user) + { + if (Movable) + user.BeginTarget(12, true, TargetFlags.None, delegate(Mobile from, object obj) + { + if (Movable && !Deleted) + if (obj is IPoint3D pt) + { + SpellHelper.GetSurfaceTop(ref pt); - Point3D origin = new Point3D( pt ); - Map facet = from.Map; + Point3D origin = new Point3D(pt); + Map facet = from.Map; - if ( facet != null && facet.CanFit( pt.X, pt.Y, pt.Z, 16, false, false, true ) ) { - Movable = false; + if (facet != null && facet.CanFit(pt.X, pt.Y, pt.Z, 16, false, false, true)) + { + Movable = false; - Effects.SendMovingEffect( - from, new Entity( Serial.Zero, origin, facet ), - ItemID & 0x3FFF, 7, 0, false, false, Hue - 1, 0 - ); + Effects.SendMovingEffect( + from, new Entity(Serial.Zero, origin, facet), + ItemID & 0x3FFF, 7, 0, false, false, Hue - 1, 0 + ); - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), delegate { - Delete(); + Timer.DelayCall(TimeSpan.FromSeconds(0.5), delegate + { + Delete(); - Effects.PlaySound( origin, facet, 530 ); - Effects.PlaySound( origin, facet, 263 ); + Effects.PlaySound(origin, facet, 530); + Effects.PlaySound(origin, facet, 263); - Effects.SendLocationEffect( - origin, facet, - 14284, 96, 1, 0, 2 - ); + Effects.SendLocationEffect( + origin, facet, + 14284, 96, 1, 0, 2 + ); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), delegate { - List targets = new List(); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), delegate + { + List targets = new List(); - foreach ( Mobile mob in facet.GetMobilesInRange( origin, 12 ) ) { - if ( from.CanBeHarmful( mob, false ) && mob.InLOS( new Point3D( origin, origin.Z + 1 ) ) ) { - if ( Faction.Find( mob ) != null ) { - targets.Add( mob ); - } - } - } + foreach (Mobile mob in facet.GetMobilesInRange(origin, 12)) + if (from.CanBeHarmful(mob, false) && + mob.InLOS(new Point3D(origin, origin.Z + 1))) + if (Faction.Find(mob) != null) + targets.Add(mob); - foreach ( Mobile mob in targets ) { - int damage = ( mob.Hits * 6 ) / 10; + foreach (Mobile mob in targets) + { + int damage = mob.Hits * 6 / 10; - if ( !mob.Player && damage < 10 ) { - damage = 10; - } else if ( damage > 75 ) { - damage = 75; - } + if (!mob.Player && damage < 10) + damage = 10; + else if (damage > 75) damage = 75; - Effects.SendMovingEffect( - new Entity( Serial.Zero, new Point3D( origin, origin.Z + 4 ), facet ), mob, - 14068, 1, 32, false, false, 1111, 2 - ); + Effects.SendMovingEffect( + new Entity(Serial.Zero, new Point3D(origin, origin.Z + 4), facet), mob, + 14068, 1, 32, false, false, 1111, 2 + ); - from.DoHarmful( mob ); + from.DoHarmful(mob); - SpellHelper.Damage( TimeSpan.FromSeconds( 0.50 ), mob, from, damage / 3, 0, 0, 0, 0, 100 ); - SpellHelper.Damage( TimeSpan.FromSeconds( 0.70 ), mob, from, damage / 3, 0, 0, 0, 0, 100 ); - SpellHelper.Damage( TimeSpan.FromSeconds( 1.00 ), mob, from, damage / 3, 0, 0, 0, 0, 100 ); + SpellHelper.Damage(TimeSpan.FromSeconds(0.50), mob, from, damage / 3, 0, 0, 0, 0, + 100); + SpellHelper.Damage(TimeSpan.FromSeconds(0.70), mob, from, damage / 3, 0, 0, 0, 0, + 100); + SpellHelper.Damage(TimeSpan.FromSeconds(1.00), mob, from, damage / 3, 0, 0, 0, 0, + 100); - Timer.DelayCall( TimeSpan.FromSeconds( 0.50 ), delegate { - mob.PlaySound( 0x1FB ); - } ); - } - } ); - } ); - } - } - } - } ); - } + Timer.DelayCall(TimeSpan.FromSeconds(0.50), delegate { mob.PlaySound(0x1FB); }); + } + }); + }); + } + } + }); - return false; - } + return false; + } - public override void Serialize( GenericWriter writer ) { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( ( int ) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Power Faction Items/UrnOfAscension.cs b/Scripts/Engines/Factions/Items/Power Faction Items/UrnOfAscension.cs index 7d230fc0a..e66bebb8e 100644 --- a/Scripts/Engines/Factions/Items/Power Faction Items/UrnOfAscension.cs +++ b/Scripts/Engines/Factions/Items/Power Faction Items/UrnOfAscension.cs @@ -1,61 +1,69 @@ +using Server.Factions; using Server.Gumps; using Server.Multis; -using Server.Factions; +using Server.Network; -namespace Server { - public sealed class UrnOfAscension : PowerFactionItem { - public override string DefaultName => "urn of ascension"; +namespace Server +{ + public sealed class UrnOfAscension : PowerFactionItem + { + public UrnOfAscension() + : base(9246) + { + } - public UrnOfAscension() - : base( 9246 ) { - } + public UrnOfAscension(Serial serial) + : base(serial) + { + } - public UrnOfAscension( Serial serial ) - : base( serial ) { - } + public override string DefaultName => "urn of ascension"; - public override bool Use( Mobile from ) { - Faction ourFaction = Faction.Find( from ); + public override bool Use(Mobile from) + { + Faction ourFaction = Faction.Find(from); - bool used = false; + bool used = false; - foreach ( Mobile mob in from.GetMobilesInRange( 8 ) ) { - if ( mob.Player && !mob.Alive && from.InLOS( mob ) ) { - if ( Faction.Find( mob ) != ourFaction ) { - continue; - } + foreach (Mobile mob in from.GetMobilesInRange(8)) + if (mob.Player && !mob.Alive && from.InLOS(mob)) + { + if (Faction.Find(mob) != ourFaction) continue; - BaseHouse house = BaseHouse.FindHouseAt( mob ); + BaseHouse house = BaseHouse.FindHouseAt(mob); - if ( house == null || ( house.IsFriend( from ) || house.IsFriend( mob ) ) ) { - Faction.ClearSkillLoss( mob ); + if (house == null || house.IsFriend(from) || house.IsFriend(mob)) + { + Faction.ClearSkillLoss(mob); - mob.SendGump( new ResurrectGump( mob, from, ResurrectMessage.Generic ) ); - used = true; - } - } - } + mob.SendGump(new ResurrectGump(mob, from, ResurrectMessage.Generic)); + used = true; + } + } - if ( used ) { - from.LocalOverheadMessage( Network.MessageType.Regular, 2219, false, "The urn shatters as you invoke its power." ); - from.PlaySound( 64 ); + if (used) + { + from.LocalOverheadMessage(MessageType.Regular, 2219, false, "The urn shatters as you invoke its power."); + from.PlaySound(64); - Effects.PlaySound( from.Location, from.Map, 1481 ); - } + Effects.PlaySound(from.Location, from.Map, 1481); + } - return used; - } + return used; + } - public override void Serialize( GenericWriter writer ) { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( ( int ) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Sigil.cs b/Scripts/Engines/Factions/Items/Sigil.cs index a4a52b809..3035de911 100644 --- a/Scripts/Engines/Factions/Items/Sigil.cs +++ b/Scripts/Engines/Factions/Items/Sigil.cs @@ -1,420 +1,458 @@ using System; +using System.Collections.Generic; using Server.Items; using Server.Mobiles; using Server.Network; -using System.Collections.Generic; +using Server.Targeting; namespace Server.Factions { - public class Sigil : BaseSystemController - { - public const int OwnershipHue = 0xB; - - // ?? time corrupting faction has to return the sigil before corruption time resets ? - public static readonly TimeSpan CorruptionGrace = TimeSpan.FromMinutes( (Core.SE) ? 30.0 : 15.0 ); - - // Sigil must be held at a stronghold for this amount of time in order to become corrupted - public static readonly TimeSpan CorruptionPeriod = ( (Core.SE) ? TimeSpan.FromHours( 10.0 ) : TimeSpan.FromHours( 24.0 ) ); - - // After a sigil has been corrupted it must be returned to the town within this period of time - public static readonly TimeSpan ReturnPeriod = TimeSpan.FromHours( 1.0 ); - - // Once it's been returned the corrupting faction owns the town for this period of time - public static readonly TimeSpan PurificationPeriod = TimeSpan.FromDays( 3.0 ); - - private Town m_Town; - private Faction m_Corrupted; - private Faction m_Corrupting; - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public DateTime LastStolen { get; set; } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public DateTime GraceStart { get; set; } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public DateTime CorruptionStart { get; set; } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public DateTime PurificationStart { get; set; } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Town Town - { - get => m_Town; - set{ m_Town = value; Update(); } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Faction Corrupted - { - get => m_Corrupted; - set{ m_Corrupted = value; Update(); } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Faction Corrupting - { - get => m_Corrupting; - set{ m_Corrupting = value; Update(); } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public BaseMonolith LastMonolith { get; set; } - - [CommandProperty( AccessLevel.Counselor )] - public bool IsBeingCorrupted => ( LastMonolith is StrongholdMonolith && LastMonolith.Faction == m_Corrupting && m_Corrupting != null ); - - [CommandProperty( AccessLevel.Counselor )] - public bool IsCorrupted => ( m_Corrupted != null ); - - [CommandProperty( AccessLevel.Counselor )] - public bool IsPurifying => ( PurificationStart != DateTime.MinValue ); - - [CommandProperty( AccessLevel.Counselor )] - public bool IsCorrupting => ( m_Corrupting != null && m_Corrupting != m_Corrupted ); - - public void Update() - { - ItemID = m_Town?.Definition.SigilID ?? 0x1869; - - if ( m_Town == null ) - AssignName( null ); - else if ( IsCorrupted || IsPurifying ) - AssignName( m_Town.Definition.CorruptedSigilName ); - else - AssignName( m_Town.Definition.SigilName ); - - InvalidateProperties(); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( IsCorrupted ) - TextDefinition.AddTo( list, m_Corrupted.Definition.SigilControl ); - else - list.Add( 1042256 ); // This sigil is not corrupted. - - if ( IsCorrupting ) - list.Add( 1042257 ); // This sigil is in the process of being corrupted. - else if ( IsPurifying ) - list.Add( 1042258 ); // This sigil has recently been corrupted, and is undergoing purification. - else - list.Add( 1042259 ); // This sigil is not in the process of being corrupted. - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( IsCorrupted ) - { - if ( m_Corrupted.Definition.SigilControl.Number > 0 ) - LabelTo( from, m_Corrupted.Definition.SigilControl.Number ); - else if ( m_Corrupted.Definition.SigilControl.String != null ) - LabelTo( from, m_Corrupted.Definition.SigilControl.String ); - } - else - { - LabelTo( from, 1042256 ); // This sigil is not corrupted. - } - - if ( IsCorrupting ) - LabelTo( from, 1042257 ); // This sigil is in the process of being corrupted. - else if ( IsPurifying ) - LabelTo( from, 1042258 ); // This sigil has been recently corrupted, and is undergoing purification. - else - LabelTo( from, 1042259 ); // This sigil is not in the process of being corrupted. - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - from.SendLocalizedMessage( 1005225 ); // You must use the stealing skill to pick up the sigil - return false; - } - - private Mobile FindOwner( object parent ) - { - if ( parent is Item item ) - return item.RootParent as Mobile; - - if ( parent is Mobile mobile ) - return mobile; - - return null; - } - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - Mobile mob = FindOwner( parent ); - - if ( mob != null ) - mob.SolidHueOverride = OwnershipHue; - } - - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); - - Mobile mob = FindOwner( parent ); - - if ( mob != null ) - mob.SolidHueOverride = -1; - } - - public Sigil( Town town ) : base( 0x1869 ) - { - Movable = false; - Town = town; - - Sigils.Add( this ); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.BeginTarget( 1, false, Targeting.TargetFlags.None, Sigil_OnTarget ); - from.SendLocalizedMessage( 1042251 ); // Click on a sigil monolith or player - } - } - - public static bool ExistsOn( Mobile mob ) - { - Container pack = mob.Backpack; - - return ( pack?.FindItemByType( typeof( Sigil ) ) != null ); - } - - private void BeginCorrupting( Faction faction ) - { - m_Corrupting = faction; - CorruptionStart = DateTime.UtcNow; - } - - private void ClearCorrupting() - { - m_Corrupting = null; - CorruptionStart = DateTime.MinValue; - } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan TimeUntilCorruption - { - get - { - if ( !IsBeingCorrupted ) - return TimeSpan.Zero; - - TimeSpan ts = ( CorruptionStart + CorruptionPeriod ) - DateTime.UtcNow; - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - return ts; - } - } - - private void Sigil_OnTarget( Mobile from, object obj ) - { - if ( Deleted || !IsChildOf( from.Backpack ) ) - return; - - #region Give To Mobile - if ( obj is Mobile ) - { - if ( obj is PlayerMobile targ ) - { - Faction toFaction = Faction.Find( targ ); - Faction fromFaction = Faction.Find( from ); - - if ( toFaction == null ) - from.SendLocalizedMessage( 1005223 ); // You cannot give the sigil to someone not in a faction - else if ( fromFaction != toFaction ) - from.SendLocalizedMessage( 1005222 ); // You cannot give the sigil to someone not in your faction - else if ( ExistsOn( targ ) ) - from.SendLocalizedMessage( 1005220 ); // You cannot give this sigil to someone who already has a sigil - else if ( !targ.Alive ) - from.SendLocalizedMessage( 1042248 ); // You cannot give a sigil to a dead person. - else if ( from.NetState != null && targ.NetState != null ) - { - Container pack = targ.Backpack; - - pack?.DropItem( this ); - } - } - else - { - from.SendLocalizedMessage( 1005221 ); //You cannot give the sigil to them - } - } - #endregion - else if ( obj is BaseMonolith ) - { - #region Put in Stronghold - if ( obj is StrongholdMonolith sm ) - { - if ( sm.Faction == null || sm.Faction != Faction.Find( from ) ) - from.SendLocalizedMessage( 1042246 ); // You can't place that on an enemy monolith - else if ( sm.Town == null || sm.Town != m_Town ) - from.SendLocalizedMessage( 1042247 ); // That is not the correct faction monolith - else - { - sm.Sigil = this; - - Faction newController = sm.Faction; - Faction oldController = m_Corrupting; - - if ( oldController == null ) - { - if ( m_Corrupted != newController ) - BeginCorrupting( newController ); - } - else if ( GraceStart > DateTime.MinValue && (GraceStart + CorruptionGrace) < DateTime.UtcNow ) - { - if ( m_Corrupted != newController ) - BeginCorrupting( newController ); // grace time over, reset period - else - ClearCorrupting(); - - GraceStart = DateTime.MinValue; - } - else if ( newController == oldController ) - { - GraceStart = DateTime.MinValue; // returned within grace period - } - else if ( GraceStart == DateTime.MinValue ) - { - GraceStart = DateTime.UtcNow; - } - - PurificationStart = DateTime.MinValue; - } - } - #endregion - - #region Put in Town - else if ( obj is TownMonolith tm ) - { - if ( tm.Town == null || tm.Town != m_Town ) - from.SendLocalizedMessage( 1042245 ); // This is not the correct town sigil monolith - else if ( m_Corrupted == null || m_Corrupted != Faction.Find( from ) ) - from.SendLocalizedMessage( 1042244 ); // Your faction did not corrupt this sigil. Take it to your stronghold. - else - { - tm.Sigil = this; - - m_Corrupting = null; - PurificationStart = DateTime.UtcNow; - CorruptionStart = DateTime.MinValue; - - m_Town.Capture( m_Corrupted ); - m_Corrupted = null; - } - } - #endregion - } - else - { - from.SendLocalizedMessage( 1005224 ); // You can't use the sigil on that - } - - Update(); - } - - public Sigil( Serial serial ) : base( serial ) - { - Sigils.Add( this ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - Town.WriteReference( writer, m_Town ); - Faction.WriteReference( writer, m_Corrupted ); - Faction.WriteReference( writer, m_Corrupting ); - - writer.Write( (Item) LastMonolith ); - - writer.Write( LastStolen ); - writer.Write( GraceStart ); - writer.Write( CorruptionStart ); - writer.Write( PurificationStart ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Town = Town.ReadReference( reader ); - m_Corrupted = Faction.ReadReference( reader ); - m_Corrupting = Faction.ReadReference( reader ); - - LastMonolith = reader.ReadItem() as BaseMonolith; - - LastStolen = reader.ReadDateTime(); - GraceStart = reader.ReadDateTime(); - CorruptionStart = reader.ReadDateTime(); - PurificationStart = reader.ReadDateTime(); - - Update(); - - if ( RootParent is Mobile mob ) - mob.SolidHueOverride = OwnershipHue; - - break; - } - } - } - - public bool ReturnHome() - { - BaseMonolith monolith = LastMonolith; - - if ( monolith == null && m_Town != null ) - monolith = m_Town.Monolith; - - if ( monolith != null && !monolith.Deleted ) - monolith.Sigil = this; - - return ( monolith != null && !monolith.Deleted ); - } - - public override void OnParentDeleted(IEntity parent) - { - base.OnParentDeleted( parent ); - - ReturnHome(); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public class Sigil : BaseSystemController + { + public const int OwnershipHue = 0xB; + + // ?? time corrupting faction has to return the sigil before corruption time resets ? + public static readonly TimeSpan CorruptionGrace = TimeSpan.FromMinutes(Core.SE ? 30.0 : 15.0); + + // Sigil must be held at a stronghold for this amount of time in order to become corrupted + public static readonly TimeSpan CorruptionPeriod = Core.SE ? TimeSpan.FromHours(10.0) : TimeSpan.FromHours(24.0); + + // After a sigil has been corrupted it must be returned to the town within this period of time + public static readonly TimeSpan ReturnPeriod = TimeSpan.FromHours(1.0); + + // Once it's been returned the corrupting faction owns the town for this period of time + public static readonly TimeSpan PurificationPeriod = TimeSpan.FromDays(3.0); + private Faction m_Corrupted; + private Faction m_Corrupting; + + private Town m_Town; + + public Sigil(Town town) : base(0x1869) + { + Movable = false; + Town = town; + + Sigils.Add(this); + } + + public Sigil(Serial serial) : base(serial) + { + Sigils.Add(this); + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public DateTime LastStolen{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public DateTime GraceStart{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public DateTime CorruptionStart{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public DateTime PurificationStart{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Town Town + { + get => m_Town; + set + { + m_Town = value; + Update(); + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Faction Corrupted + { + get => m_Corrupted; + set + { + m_Corrupted = value; + Update(); + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Faction Corrupting + { + get => m_Corrupting; + set + { + m_Corrupting = value; + Update(); + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public BaseMonolith LastMonolith{ get; set; } + + [CommandProperty(AccessLevel.Counselor)] + public bool IsBeingCorrupted => LastMonolith is StrongholdMonolith && LastMonolith.Faction == m_Corrupting && + m_Corrupting != null; + + [CommandProperty(AccessLevel.Counselor)] + public bool IsCorrupted => m_Corrupted != null; + + [CommandProperty(AccessLevel.Counselor)] + public bool IsPurifying => PurificationStart != DateTime.MinValue; + + [CommandProperty(AccessLevel.Counselor)] + public bool IsCorrupting => m_Corrupting != null && m_Corrupting != m_Corrupted; + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan TimeUntilCorruption + { + get + { + if (!IsBeingCorrupted) + return TimeSpan.Zero; + + TimeSpan ts = CorruptionStart + CorruptionPeriod - DateTime.UtcNow; + + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; + + return ts; + } + } + + public static List Sigils{ get; } = new List(); + + public void Update() + { + ItemID = m_Town?.Definition.SigilID ?? 0x1869; + + if (m_Town == null) + AssignName(null); + else if (IsCorrupted || IsPurifying) + AssignName(m_Town.Definition.CorruptedSigilName); + else + AssignName(m_Town.Definition.SigilName); + + InvalidateProperties(); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (IsCorrupted) + TextDefinition.AddTo(list, m_Corrupted.Definition.SigilControl); + else + list.Add(1042256); // This sigil is not corrupted. + + if (IsCorrupting) + list.Add(1042257); // This sigil is in the process of being corrupted. + else if (IsPurifying) + list.Add(1042258); // This sigil has recently been corrupted, and is undergoing purification. + else + list.Add(1042259); // This sigil is not in the process of being corrupted. + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (IsCorrupted) + { + if (m_Corrupted.Definition.SigilControl.Number > 0) + LabelTo(from, m_Corrupted.Definition.SigilControl.Number); + else if (m_Corrupted.Definition.SigilControl.String != null) + LabelTo(from, m_Corrupted.Definition.SigilControl.String); + } + else + { + LabelTo(from, 1042256); // This sigil is not corrupted. + } + + if (IsCorrupting) + LabelTo(from, 1042257); // This sigil is in the process of being corrupted. + else if (IsPurifying) + LabelTo(from, 1042258); // This sigil has been recently corrupted, and is undergoing purification. + else + LabelTo(from, 1042259); // This sigil is not in the process of being corrupted. + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + from.SendLocalizedMessage(1005225); // You must use the stealing skill to pick up the sigil + return false; + } + + private Mobile FindOwner(object parent) + { + if (parent is Item item) + return item.RootParent as Mobile; + + if (parent is Mobile mobile) + return mobile; + + return null; + } + + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); + + Mobile mob = FindOwner(parent); + + if (mob != null) + mob.SolidHueOverride = OwnershipHue; + } + + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); + + Mobile mob = FindOwner(parent); + + if (mob != null) + mob.SolidHueOverride = -1; + } + + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.BeginTarget(1, false, TargetFlags.None, Sigil_OnTarget); + from.SendLocalizedMessage(1042251); // Click on a sigil monolith or player + } + } + + public static bool ExistsOn(Mobile mob) + { + Container pack = mob.Backpack; + + return pack?.FindItemByType(typeof(Sigil)) != null; + } + + private void BeginCorrupting(Faction faction) + { + m_Corrupting = faction; + CorruptionStart = DateTime.UtcNow; + } + + private void ClearCorrupting() + { + m_Corrupting = null; + CorruptionStart = DateTime.MinValue; + } + + private void Sigil_OnTarget(Mobile from, object obj) + { + if (Deleted || !IsChildOf(from.Backpack)) + return; + + #region Give To Mobile + + if (obj is Mobile) + { + if (obj is PlayerMobile targ) + { + Faction toFaction = Faction.Find(targ); + Faction fromFaction = Faction.Find(from); + + if (toFaction == null) + { + from.SendLocalizedMessage(1005223); // You cannot give the sigil to someone not in a faction + } + else if (fromFaction != toFaction) + { + from.SendLocalizedMessage(1005222); // You cannot give the sigil to someone not in your faction + } + else if (ExistsOn(targ)) + { + from.SendLocalizedMessage(1005220); // You cannot give this sigil to someone who already has a sigil + } + else if (!targ.Alive) + { + from.SendLocalizedMessage(1042248); // You cannot give a sigil to a dead person. + } + else if (from.NetState != null && targ.NetState != null) + { + Container pack = targ.Backpack; + + pack?.DropItem(this); + } + } + else + { + from.SendLocalizedMessage(1005221); //You cannot give the sigil to them + } + } + + #endregion + + else if (obj is BaseMonolith) + { + #region Put in Stronghold + + if (obj is StrongholdMonolith sm) + { + if (sm.Faction == null || sm.Faction != Faction.Find(from)) + { + from.SendLocalizedMessage(1042246); // You can't place that on an enemy monolith + } + else if (sm.Town == null || sm.Town != m_Town) + { + from.SendLocalizedMessage(1042247); // That is not the correct faction monolith + } + else + { + sm.Sigil = this; + + Faction newController = sm.Faction; + Faction oldController = m_Corrupting; + + if (oldController == null) + { + if (m_Corrupted != newController) + BeginCorrupting(newController); + } + else if (GraceStart > DateTime.MinValue && GraceStart + CorruptionGrace < DateTime.UtcNow) + { + if (m_Corrupted != newController) + BeginCorrupting(newController); // grace time over, reset period + else + ClearCorrupting(); + + GraceStart = DateTime.MinValue; + } + else if (newController == oldController) + { + GraceStart = DateTime.MinValue; // returned within grace period + } + else if (GraceStart == DateTime.MinValue) + { + GraceStart = DateTime.UtcNow; + } + + PurificationStart = DateTime.MinValue; + } + } + + #endregion + + #region Put in Town + + else if (obj is TownMonolith tm) + { + if (tm.Town == null || tm.Town != m_Town) + { + from.SendLocalizedMessage(1042245); // This is not the correct town sigil monolith + } + else if (m_Corrupted == null || m_Corrupted != Faction.Find(from)) + { + from.SendLocalizedMessage( + 1042244); // Your faction did not corrupt this sigil. Take it to your stronghold. + } + else + { + tm.Sigil = this; + + m_Corrupting = null; + PurificationStart = DateTime.UtcNow; + CorruptionStart = DateTime.MinValue; + + m_Town.Capture(m_Corrupted); + m_Corrupted = null; + } + } + + #endregion + } + else + { + from.SendLocalizedMessage(1005224); // You can't use the sigil on that + } + + Update(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + Town.WriteReference(writer, m_Town); + Faction.WriteReference(writer, m_Corrupted); + Faction.WriteReference(writer, m_Corrupting); + + writer.Write(LastMonolith); + + writer.Write(LastStolen); + writer.Write(GraceStart); + writer.Write(CorruptionStart); + writer.Write(PurificationStart); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Town = Town.ReadReference(reader); + m_Corrupted = Faction.ReadReference(reader); + m_Corrupting = Faction.ReadReference(reader); + + LastMonolith = reader.ReadItem() as BaseMonolith; + + LastStolen = reader.ReadDateTime(); + GraceStart = reader.ReadDateTime(); + CorruptionStart = reader.ReadDateTime(); + PurificationStart = reader.ReadDateTime(); + + Update(); + + if (RootParent is Mobile mob) + mob.SolidHueOverride = OwnershipHue; + + break; + } + } + } + + public bool ReturnHome() + { + BaseMonolith monolith = LastMonolith; + + if (monolith == null && m_Town != null) + monolith = m_Town.Monolith; + + if (monolith != null && !monolith.Deleted) + monolith.Sigil = this; + + return monolith != null && !monolith.Deleted; + } + + public override void OnParentDeleted(IEntity parent) + { + base.OnParentDeleted(parent); + + ReturnHome(); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + Sigils.Remove(this); + } - Sigils.Remove( this ); - } + public override void Delete() + { + if (ReturnHome()) + return; - public override void Delete() - { - if ( ReturnHome() ) - return; - - base.Delete(); - } - - public static List Sigils { get; } = new List(); - } -} + base.Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Silver.cs b/Scripts/Engines/Factions/Items/Silver.cs index a214561a1..596653b11 100644 --- a/Scripts/Engines/Factions/Items/Silver.cs +++ b/Scripts/Engines/Factions/Items/Silver.cs @@ -1,51 +1,51 @@ namespace Server.Factions { - public class Silver : Item - { - public override double DefaultWeight => 0.02; + public class Silver : Item + { + [Constructible] + public Silver() : this(1) + { + } - [Constructible] - public Silver() : this( 1 ) - { - } + [Constructible] + public Silver(int amountFrom, int amountTo) : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } - [Constructible] - public Silver( int amountFrom, int amountTo ) : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } + [Constructible] + public Silver(int amount) : base(0xEF0) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Silver( int amount ) : base( 0xEF0 ) - { - Stackable = true; - Amount = amount; - } + public Silver(Serial serial) : base(serial) + { + } - public Silver( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.02; - public override int GetDropSound() - { - if ( Amount <= 1 ) - return 0x2E4; - if ( Amount <= 5 ) - return 0x2E5; - return 0x2E6; - } + public override int GetDropSound() + { + if (Amount <= 1) + return 0x2E4; + if (Amount <= 5) + return 0x2E5; + return 0x2E6; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/StrongholdMonolith.cs b/Scripts/Engines/Factions/Items/StrongholdMonolith.cs index cc44b15f6..5ac5edd1d 100644 --- a/Scripts/Engines/Factions/Items/StrongholdMonolith.cs +++ b/Scripts/Engines/Factions/Items/StrongholdMonolith.cs @@ -1,38 +1,38 @@ namespace Server.Factions { - public class StrongholdMonolith : BaseMonolith - { - public override int DefaultLabelNumber => 1041042; // A Faction Sigil Monolith + public class StrongholdMonolith : BaseMonolith + { + public StrongholdMonolith() : this(null, null) + { + } - public override void OnTownChanged() - { - AssignName( Town?.Definition.StrongholdMonolithName ); - } + public StrongholdMonolith(Town town, Faction faction) : base(town, faction) + { + } - public StrongholdMonolith() : this( null, null ) - { - } + public StrongholdMonolith(Serial serial) : base(serial) + { + } - public StrongholdMonolith( Town town, Faction faction ) : base( town, faction ) - { - } + public override int DefaultLabelNumber => 1041042; // A Faction Sigil Monolith - public StrongholdMonolith( Serial serial ) : base( serial ) - { - } + public override void OnTownChanged() + { + AssignName(Town?.Definition.StrongholdMonolithName); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/TownMonolith.cs b/Scripts/Engines/Factions/Items/TownMonolith.cs index 77626189a..83b7a95c2 100644 --- a/Scripts/Engines/Factions/Items/TownMonolith.cs +++ b/Scripts/Engines/Factions/Items/TownMonolith.cs @@ -1,38 +1,38 @@ namespace Server.Factions { - public class TownMonolith : BaseMonolith - { - public override int DefaultLabelNumber => 1041403; // A Faction Town Sigil Monolith + public class TownMonolith : BaseMonolith + { + public TownMonolith() : this(null) + { + } - public override void OnTownChanged() - { - AssignName( Town?.Definition.TownMonolithName ); - } + public TownMonolith(Town town) : base(town, null) + { + } - public TownMonolith() : this( null ) - { - } + public TownMonolith(Serial serial) : base(serial) + { + } - public TownMonolith( Town town ) : base( town, null ) - { - } + public override int DefaultLabelNumber => 1041403; // A Faction Town Sigil Monolith - public TownMonolith( Serial serial ) : base( serial ) - { - } + public override void OnTownChanged() + { + AssignName(Town?.Definition.TownMonolithName); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/TownStone.cs b/Scripts/Engines/Factions/Items/TownStone.cs index af2b5e833..31f47229f 100644 --- a/Scripts/Engines/Factions/Items/TownStone.cs +++ b/Scripts/Engines/Factions/Items/TownStone.cs @@ -2,83 +2,83 @@ using Server.Mobiles; namespace Server.Factions { - public class TownStone : BaseSystemController - { - private Town m_Town; + public class TownStone : BaseSystemController + { + private Town m_Town; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Town Town - { - get => m_Town; - set - { - m_Town = value; + [Constructible] + public TownStone() : this(null) + { + } - AssignName( m_Town?.Definition.TownStoneName ); - } - } + [Constructible] + public TownStone(Town town) : base(0xEDE) + { + Movable = false; + Town = town; + } - public override string DefaultName => "faction town stone"; + public TownStone(Serial serial) : base(serial) + { + } - [Constructible] - public TownStone() : this( null ) - { - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Town Town + { + get => m_Town; + set + { + m_Town = value; - [Constructible] - public TownStone( Town town ) : base( 0xEDE ) - { - Movable = false; - Town = town; - } + AssignName(m_Town?.Definition.TownStoneName); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_Town == null ) - return; + public override string DefaultName => "faction town stone"; - Faction faction = Faction.Find( from ); + public override void OnDoubleClick(Mobile from) + { + if (m_Town == null) + return; - if ( faction == null && from.AccessLevel < AccessLevel.GameMaster ) - return; // TODO: Message? + Faction faction = Faction.Find(from); - if ( m_Town.Owner == null || ( from.AccessLevel < AccessLevel.GameMaster && faction != m_Town.Owner ) ) - from.SendLocalizedMessage( 1010332 ); // Your faction does not control this town - else if ( !m_Town.Owner.IsCommander( from ) ) - from.SendLocalizedMessage( 1005242 ); // Only faction Leaders can use townstones - else if ( FactionGump.Exists( from ) ) - from.SendLocalizedMessage( 1042160 ); // You already have a faction menu open. - else if ( from is PlayerMobile mobile ) - mobile.SendGump( new TownStoneGump( mobile, m_Town.Owner, m_Town ) ); - } + if (faction == null && from.AccessLevel < AccessLevel.GameMaster) + return; // TODO: Message? - public TownStone( Serial serial ) : base( serial ) - { - } + if (m_Town.Owner == null || from.AccessLevel < AccessLevel.GameMaster && faction != m_Town.Owner) + from.SendLocalizedMessage(1010332); // Your faction does not control this town + else if (!m_Town.Owner.IsCommander(from)) + from.SendLocalizedMessage(1005242); // Only faction Leaders can use townstones + else if (FactionGump.Exists(from)) + from.SendLocalizedMessage(1042160); // You already have a faction menu open. + else if (from is PlayerMobile mobile) + mobile.SendGump(new TownStoneGump(mobile, m_Town.Owner, m_Town)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - Town.WriteReference( writer, m_Town ); - } + Town.WriteReference(writer, m_Town); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Town = Town.ReadReference( reader ); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Town = Town.ReadReference(reader); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/BaseFactionTrap.cs b/Scripts/Engines/Factions/Items/Traps/BaseFactionTrap.cs index b77d43c8c..14a400b14 100644 --- a/Scripts/Engines/Factions/Items/Traps/BaseFactionTrap.cs +++ b/Scripts/Engines/Factions/Items/Traps/BaseFactionTrap.cs @@ -4,264 +4,261 @@ using Server.Network; namespace Server.Factions { - public enum AllowedPlacing - { - Everywhere, + public enum AllowedPlacing + { + Everywhere, - AnyFactionTown, - ControlledFactionTown, - FactionStronghold - } + AnyFactionTown, + ControlledFactionTown, + FactionStronghold + } - public abstract class BaseFactionTrap : BaseTrap - { - private Timer m_Concealing; + public abstract class BaseFactionTrap : BaseTrap + { + private Timer m_Concealing; - [CommandProperty( AccessLevel.GameMaster )] - public Faction Faction { get; set; } + public BaseFactionTrap(Faction f, Mobile m, int itemID) : base(itemID) + { + Visible = false; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Placer { get; set; } + Faction = f; + TimeOfPlacement = DateTime.UtcNow; + Placer = m; + } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime TimeOfPlacement { get; set; } + public BaseFactionTrap(Serial serial) : base(serial) + { + } - public virtual int EffectSound => 0; + [CommandProperty(AccessLevel.GameMaster)] + public Faction Faction{ get; set; } - public virtual int SilverFromDisarm => 100; + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Placer{ get; set; } - public virtual int MessageHue => 0; - - public virtual int AttackMessage => 0; - public virtual int DisarmMessage => 0; + [CommandProperty(AccessLevel.GameMaster)] + public DateTime TimeOfPlacement{ get; set; } - public virtual AllowedPlacing AllowedPlacing => AllowedPlacing.Everywhere; + public virtual int EffectSound => 0; - public virtual TimeSpan ConcealPeriod => TimeSpan.FromMinutes( 1.0 ); + public virtual int SilverFromDisarm => 100; - public virtual TimeSpan DecayPeriod - { - get - { - if ( Core.AOS ) - return TimeSpan.FromDays( 1.0 ); + public virtual int MessageHue => 0; - return TimeSpan.MaxValue; // no decay - } - } + public virtual int AttackMessage => 0; + public virtual int DisarmMessage => 0; - public override void OnTrigger( Mobile from ) - { - if ( !IsEnemy( from ) ) - return; + public virtual AllowedPlacing AllowedPlacing => AllowedPlacing.Everywhere; - Conceal(); - - DoVisibleEffect(); - Effects.PlaySound( Location, Map, EffectSound ); - DoAttackEffect( from ); + public virtual TimeSpan ConcealPeriod => TimeSpan.FromMinutes(1.0); - int silverToAward = ( from.Alive ? 20 : 40 ); + public virtual TimeSpan DecayPeriod + { + get + { + if (Core.AOS) + return TimeSpan.FromDays(1.0); - if ( silverToAward > 0 && Placer != null && Faction != null ) - { - PlayerState victimState = PlayerState.Find( from ); + return TimeSpan.MaxValue; // no decay + } + } - if ( victimState != null && victimState.CanGiveSilverTo( Placer ) && victimState.KillPoints > 0 ) - { - int silverGiven = Faction.AwardSilver( Placer, silverToAward ); + public override void OnTrigger(Mobile from) + { + if (!IsEnemy(from)) + return; - if ( silverGiven > 0 ) - { - // TODO: Get real message - if ( from.Alive ) - Placer.SendMessage( "You have earned {0} silver pieces because {1} fell for your trap.", silverGiven, from.Name ); - else - Placer.SendLocalizedMessage( 1042736, $"{silverGiven} silver\t{from.Name}"); // You have earned ~1_SILVER_AMOUNT~ pieces for vanquishing ~2_PLAYER_NAME~! - } - - victimState.OnGivenSilverTo( Placer ); - } - } - - from.LocalOverheadMessage( MessageType.Regular, MessageHue, AttackMessage ); - } + Conceal(); - public abstract void DoVisibleEffect(); - public abstract void DoAttackEffect( Mobile m ); + DoVisibleEffect(); + Effects.PlaySound(Location, Map, EffectSound); + DoAttackEffect(from); - public virtual int IsValidLocation() - { - return IsValidLocation( GetWorldLocation(), Map ); - } + int silverToAward = from.Alive ? 20 : 40; - public virtual int IsValidLocation( Point3D p, Map m ) - { - if ( m == null ) - return 502956; // You cannot place a trap on that. - - if ( Core.ML ) - { - foreach( Item item in m.GetItemsInRange( p, 0 ) ) - { - if ( item is BaseFactionTrap trap && trap.Faction == Faction ) - return 1075263; // There is already a trap belonging to your faction at this location.; - } - } + if (silverToAward > 0 && Placer != null && Faction != null) + { + PlayerState victimState = PlayerState.Find(from); - switch( AllowedPlacing ) - { - case AllowedPlacing.FactionStronghold: - { - StrongholdRegion region = (StrongholdRegion) Region.Find( p, m ).GetRegion( typeof( StrongholdRegion ) ); + if (victimState != null && victimState.CanGiveSilverTo(Placer) && victimState.KillPoints > 0) + { + int silverGiven = Faction.AwardSilver(Placer, silverToAward); - if ( region != null && region.Faction == Faction ) - return 0; + if (silverGiven > 0) + { + // TODO: Get real message + if (from.Alive) + Placer.SendMessage("You have earned {0} silver pieces because {1} fell for your trap.", + silverGiven, from.Name); + else + Placer.SendLocalizedMessage(1042736, + $"{silverGiven} silver\t{from.Name}"); // You have earned ~1_SILVER_AMOUNT~ pieces for vanquishing ~2_PLAYER_NAME~! + } - return 1010355; // This trap can only be placed in your stronghold - } - case AllowedPlacing.AnyFactionTown: - { - Town town = Town.FromRegion( Region.Find( p, m ) ); + victimState.OnGivenSilverTo(Placer); + } + } - if ( town != null ) - return 0; + from.LocalOverheadMessage(MessageType.Regular, MessageHue, AttackMessage); + } - return 1010356; // This trap can only be placed in a faction town - } - case AllowedPlacing.ControlledFactionTown: - { - Town town = Town.FromRegion( Region.Find( p, m ) ); - - if ( town != null && town.Owner == Faction ) - return 0; - - return 1010357; // This trap can only be placed in a town your faction controls - } - } - - return 0; - } - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); - - if ( !CheckDecay() && CheckRange( m.Location, oldLocation, 6 ) ) - { - if ( Faction.Find( m ) != null && ((m.Skills[SkillName.DetectHidden].Value - 80.0) / 20.0) > Utility.RandomDouble() ) - PrivateOverheadLocalizedMessage( m, 1010154, MessageHue, "", "" ); // [Faction Trap] - } - } + public abstract void DoVisibleEffect(); + public abstract void DoAttackEffect(Mobile m); - public void PrivateOverheadLocalizedMessage( Mobile to, int number, int hue, string name, string args ) - { - NetState ns = to?.NetState; + public virtual int IsValidLocation() + { + return IsValidLocation(GetWorldLocation(), Map); + } - ns?.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, hue, 3, number, name, args ) ); - } + public virtual int IsValidLocation(Point3D p, Map m) + { + if (m == null) + return 502956; // You cannot place a trap on that. - public BaseFactionTrap( Faction f, Mobile m, int itemID ) : base( itemID ) - { - Visible = false; - - Faction = f; - TimeOfPlacement = DateTime.UtcNow; - Placer = m; - } - - public BaseFactionTrap( Serial serial ) : base( serial ) - { - } - - public virtual bool CheckDecay() - { - TimeSpan decayPeriod = DecayPeriod; + if (Core.ML) + foreach (Item item in m.GetItemsInRange(p, 0)) + if (item is BaseFactionTrap trap && trap.Faction == Faction) + return 1075263; // There is already a trap belonging to your faction at this location.; - if ( decayPeriod == TimeSpan.MaxValue ) - return false; + switch (AllowedPlacing) + { + case AllowedPlacing.FactionStronghold: + { + StrongholdRegion region = (StrongholdRegion)Region.Find(p, m).GetRegion(typeof(StrongholdRegion)); - if ( (TimeOfPlacement + decayPeriod) < DateTime.UtcNow ) - { - Timer.DelayCall( TimeSpan.Zero, Delete ); - return true; - } + if (region != null && region.Faction == Faction) + return 0; - return false; - } + return 1010355; // This trap can only be placed in your stronghold + } + case AllowedPlacing.AnyFactionTown: + { + Town town = Town.FromRegion(Region.Find(p, m)); - public virtual void BeginConceal() - { - m_Concealing?.Stop(); + if (town != null) + return 0; - m_Concealing = Timer.DelayCall( ConcealPeriod, Conceal ); - } + return 1010356; // This trap can only be placed in a faction town + } + case AllowedPlacing.ControlledFactionTown: + { + Town town = Town.FromRegion(Region.Find(p, m)); - public virtual void Conceal() - { - m_Concealing?.Stop(); + if (town != null && town.Owner == Faction) + return 0; - m_Concealing = null; + return 1010357; // This trap can only be placed in a town your faction controls + } + } - if ( !Deleted ) - Visible = false; - } + return 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - writer.Write( (int) 0 ); // version + if (!CheckDecay() && CheckRange(m.Location, oldLocation, 6)) + if (Faction.Find(m) != null && + (m.Skills[SkillName.DetectHidden].Value - 80.0) / 20.0 > Utility.RandomDouble()) + PrivateOverheadLocalizedMessage(m, 1010154, MessageHue, "", ""); // [Faction Trap] + } - Faction.WriteReference( writer, Faction ); - writer.Write( (Mobile) Placer ); - writer.Write( (DateTime) TimeOfPlacement ); + public void PrivateOverheadLocalizedMessage(Mobile to, int number, int hue, string name, string args) + { + NetState ns = to?.NetState; - if ( Visible ) - BeginConceal(); - } + ns?.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, hue, 3, number, name, args)); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public virtual bool CheckDecay() + { + TimeSpan decayPeriod = DecayPeriod; - int version = reader.ReadInt(); + if (decayPeriod == TimeSpan.MaxValue) + return false; - Faction = Faction.ReadReference( reader ); - Placer = reader.ReadMobile(); - TimeOfPlacement = reader.ReadDateTime(); + if (TimeOfPlacement + decayPeriod < DateTime.UtcNow) + { + Timer.DelayCall(TimeSpan.Zero, Delete); + return true; + } - if ( Visible ) - BeginConceal(); + return false; + } - CheckDecay(); - } + public virtual void BeginConceal() + { + m_Concealing?.Stop(); - public override void OnDelete() - { - if ( Faction != null && Faction.Traps.Contains( this ) ) - Faction.Traps.Remove( this ); + m_Concealing = Timer.DelayCall(ConcealPeriod, Conceal); + } - base.OnDelete(); - } + public virtual void Conceal() + { + m_Concealing?.Stop(); - public virtual bool IsEnemy( Mobile mob ) - { - if ( mob.Hidden && mob.AccessLevel > AccessLevel.Player ) - return false; + m_Concealing = null; - if ( !mob.Alive || mob.IsDeadBondedPet ) - return false; + if (!Deleted) + Visible = false; + } - Faction faction = Faction.Find( mob, true ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( faction == null && mob is BaseFactionGuard guard ) - faction = guard.Faction; + writer.Write(0); // version - if ( faction == null ) - return false; + Faction.WriteReference(writer, Faction); + writer.Write(Placer); + writer.Write(TimeOfPlacement); - return ( faction != Faction ); - } - } -} + if (Visible) + BeginConceal(); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Faction = Faction.ReadReference(reader); + Placer = reader.ReadMobile(); + TimeOfPlacement = reader.ReadDateTime(); + + if (Visible) + BeginConceal(); + + CheckDecay(); + } + + public override void OnDelete() + { + if (Faction != null && Faction.Traps.Contains(this)) + Faction.Traps.Remove(this); + + base.OnDelete(); + } + + public virtual bool IsEnemy(Mobile mob) + { + if (mob.Hidden && mob.AccessLevel > AccessLevel.Player) + return false; + + if (!mob.Alive || mob.IsDeadBondedPet) + return false; + + Faction faction = Faction.Find(mob, true); + + if (faction == null && mob is BaseFactionGuard guard) + faction = guard.Faction; + + if (faction == null) + return false; + + return faction != Faction; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/BaseFactionTrapDeed.cs b/Scripts/Engines/Factions/Items/Traps/BaseFactionTrapDeed.cs index cee378c49..254a55fe9 100644 --- a/Scripts/Engines/Factions/Items/Traps/BaseFactionTrapDeed.cs +++ b/Scripts/Engines/Factions/Items/Traps/BaseFactionTrapDeed.cs @@ -1,109 +1,123 @@ using System; -using Server.Items; using Server.Engines.Craft; +using Server.Items; namespace Server.Factions { - public abstract class BaseFactionTrapDeed : Item, ICraftable - { - public abstract Type TrapType{ get; } + public abstract class BaseFactionTrapDeed : Item, ICraftable + { + private Faction m_Faction; - private Faction m_Faction; + public BaseFactionTrapDeed(int itemID) : base(itemID) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public Faction Faction - { - get => m_Faction; - set - { - m_Faction = value; + public BaseFactionTrapDeed(bool createdFromDeed) : this(0x14F0) + { + } - if ( m_Faction != null ) - Hue = m_Faction.Definition.HuePrimary; - } - } + public BaseFactionTrapDeed(Serial serial) : base(serial) + { + } - public BaseFactionTrapDeed( int itemID ) : base( itemID ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public abstract Type TrapType{ get; } - public BaseFactionTrapDeed( bool createdFromDeed ) : this( 0x14F0 ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public Faction Faction + { + get => m_Faction; + set + { + m_Faction = value; - public BaseFactionTrapDeed( Serial serial ) : base( serial ) - { - } + if (m_Faction != null) + Hue = m_Faction.Definition.HuePrimary; + } + } - public virtual BaseFactionTrap Construct( Mobile from ) - { - try{ return Activator.CreateInstance( TrapType, new object[]{ m_Faction, from } ) as BaseFactionTrap; } - catch{ return null; } - } + #region ICraftable Members - public override void OnDoubleClick( Mobile from ) - { - Faction faction = Faction.Find( from ); + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + ItemID = 0x14F0; + Faction = Faction.Find(from); - if ( faction == null ) - from.SendLocalizedMessage( 1010353, "", 0x23 ); // Only faction members may place faction traps - else if ( faction != m_Faction ) - from.SendLocalizedMessage( 1010354, "", 0x23 ); // You may only place faction traps created by your faction - else if ( faction.Traps.Count >= faction.MaximumTraps ) - from.SendLocalizedMessage( 1010358, "", 0x23 ); // Your faction already has the maximum number of traps placed - else - { - BaseFactionTrap trap = Construct( from ); + return 1; + } - if ( trap == null ) - return; + #endregion - int message = trap.IsValidLocation( from.Location, from.Map ); + public virtual BaseFactionTrap Construct(Mobile from) + { + try + { + return Activator.CreateInstance(TrapType, m_Faction, from) as BaseFactionTrap; + } + catch + { + return null; + } + } - if ( message > 0 ) - { - from.SendLocalizedMessage( message, "", 0x23 ); - trap.Delete(); - } - else - { - from.SendLocalizedMessage( 1010360 ); // You arm the trap and carefully hide it from view - trap.MoveToWorld( from.Location, from.Map ); - faction.Traps.Add( trap ); - Delete(); - } - } - } + public override void OnDoubleClick(Mobile from) + { + Faction faction = Faction.Find(from); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (faction == null) + { + from.SendLocalizedMessage(1010353, "", 0x23); // Only faction members may place faction traps + } + else if (faction != m_Faction) + { + from.SendLocalizedMessage(1010354, "", 0x23); // You may only place faction traps created by your faction + } + else if (faction.Traps.Count >= faction.MaximumTraps) + { + from.SendLocalizedMessage(1010358, "", 0x23); // Your faction already has the maximum number of traps placed + } + else + { + BaseFactionTrap trap = Construct(from); - writer.Write( (int) 0 ); // version + if (trap == null) + return; - Faction.WriteReference( writer, m_Faction ); - } + int message = trap.IsValidLocation(from.Location, from.Map); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (message > 0) + { + from.SendLocalizedMessage(message, "", 0x23); + trap.Delete(); + } + else + { + from.SendLocalizedMessage(1010360); // You arm the trap and carefully hide it from view + trap.MoveToWorld(from.Location, from.Map); + faction.Traps.Add(trap); + Delete(); + } + } + } - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Faction = Faction.ReadReference( reader ); - } - #region ICraftable Members + writer.Write(0); // version - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - ItemID = 0x14F0; - Faction = Faction.Find( from ); + Faction.WriteReference(writer, m_Faction); + } - return 1; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion - } -} + int version = reader.ReadInt(); + + m_Faction = Faction.ReadReference(reader); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/FactionExplosionTrap.cs b/Scripts/Engines/Factions/Items/Traps/FactionExplosionTrap.cs index d19fcaf27..bcb193df5 100644 --- a/Scripts/Engines/Factions/Items/Traps/FactionExplosionTrap.cs +++ b/Scripts/Engines/Factions/Items/Traps/FactionExplosionTrap.cs @@ -2,83 +2,83 @@ using System; namespace Server.Factions { - public class FactionExplosionTrap : BaseFactionTrap - { - public override int LabelNumber => 1044599; // faction explosion trap + public class FactionExplosionTrap : BaseFactionTrap + { + [Constructible] + public FactionExplosionTrap() : this(null) + { + } - public override int AttackMessage => 1010543; // You are enveloped in an explosion of fire! - public override int DisarmMessage => 1010539; // You carefully remove the pressure trigger and disable the trap. - public override int EffectSound => 0x307; - public override int MessageHue => 0x78; + public FactionExplosionTrap(Faction f) : this(f, null) + { + } - public override AllowedPlacing AllowedPlacing => AllowedPlacing.AnyFactionTown; + public FactionExplosionTrap(Faction f, Mobile m) : base(f, m, 0x11C1) + { + } - public override void DoVisibleEffect() - { - Effects.SendLocationEffect( GetWorldLocation(), Map, 0x36BD, 15, 10 ); - } + public FactionExplosionTrap(Serial serial) : base(serial) + { + } - public override void DoAttackEffect( Mobile m ) - { - m.Damage( Utility.Dice( 6, 10, 40 ), m ); - } + public override int LabelNumber => 1044599; // faction explosion trap - [Constructible] - public FactionExplosionTrap() : this( null ) - { - } + public override int AttackMessage => 1010543; // You are enveloped in an explosion of fire! + public override int DisarmMessage => 1010539; // You carefully remove the pressure trigger and disable the trap. + public override int EffectSound => 0x307; + public override int MessageHue => 0x78; - public FactionExplosionTrap( Faction f ) : this( f, null ) - { - } + public override AllowedPlacing AllowedPlacing => AllowedPlacing.AnyFactionTown; - public FactionExplosionTrap( Faction f, Mobile m ) : base( f, m, 0x11C1 ) - { - } + public override void DoVisibleEffect() + { + Effects.SendLocationEffect(GetWorldLocation(), Map, 0x36BD, 15, 10); + } - public FactionExplosionTrap( Serial serial ) : base( serial ) - { - } + public override void DoAttackEffect(Mobile m) + { + m.Damage(Utility.Dice(6, 10, 40), m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class FactionExplosionTrapDeed : BaseFactionTrapDeed - { - public override Type TrapType => typeof( FactionExplosionTrap ); - public override int LabelNumber => 1044603; // faction explosion trap deed + public class FactionExplosionTrapDeed : BaseFactionTrapDeed + { + public FactionExplosionTrapDeed() : base(0x36D2) + { + } - public FactionExplosionTrapDeed() : base( 0x36D2 ) - { - } + public FactionExplosionTrapDeed(Serial serial) : base(serial) + { + } - public FactionExplosionTrapDeed( Serial serial ) : base( serial ) - { - } + public override Type TrapType => typeof(FactionExplosionTrap); + public override int LabelNumber => 1044603; // faction explosion trap deed - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/FactionGasTrap.cs b/Scripts/Engines/Factions/Items/Traps/FactionGasTrap.cs index fa2f857b4..8a8fdcfc4 100644 --- a/Scripts/Engines/Factions/Items/Traps/FactionGasTrap.cs +++ b/Scripts/Engines/Factions/Items/Traps/FactionGasTrap.cs @@ -2,83 +2,83 @@ using System; namespace Server.Factions { - public class FactionGasTrap : BaseFactionTrap - { - public override int LabelNumber => 1044598; // faction gas trap + public class FactionGasTrap : BaseFactionTrap + { + [Constructible] + public FactionGasTrap() : this(null) + { + } - public override int AttackMessage => 1010542; // A noxious green cloud of poison gas envelops you! - public override int DisarmMessage => 502376; // The poison leaks harmlessly away due to your deft touch. - public override int EffectSound => 0x230; - public override int MessageHue => 0x44; + public FactionGasTrap(Faction f) : this(f, null) + { + } - public override AllowedPlacing AllowedPlacing => AllowedPlacing.FactionStronghold; + public FactionGasTrap(Faction f, Mobile m) : base(f, m, 0x113C) + { + } - public override void DoVisibleEffect() - { - Effects.SendLocationEffect( Location, Map, 0x3709, 28, 10, 0x1D3, 5 ); - } + public FactionGasTrap(Serial serial) : base(serial) + { + } - public override void DoAttackEffect( Mobile m ) - { - m.ApplyPoison( m, Poison.Lethal ); - } + public override int LabelNumber => 1044598; // faction gas trap - [Constructible] - public FactionGasTrap() : this( null ) - { - } + public override int AttackMessage => 1010542; // A noxious green cloud of poison gas envelops you! + public override int DisarmMessage => 502376; // The poison leaks harmlessly away due to your deft touch. + public override int EffectSound => 0x230; + public override int MessageHue => 0x44; - public FactionGasTrap( Faction f ) : this( f, null ) - { - } + public override AllowedPlacing AllowedPlacing => AllowedPlacing.FactionStronghold; - public FactionGasTrap( Faction f, Mobile m ) : base( f, m, 0x113C ) - { - } + public override void DoVisibleEffect() + { + Effects.SendLocationEffect(Location, Map, 0x3709, 28, 10, 0x1D3, 5); + } - public FactionGasTrap( Serial serial ) : base( serial ) - { - } + public override void DoAttackEffect(Mobile m) + { + m.ApplyPoison(m, Poison.Lethal); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class FactionGasTrapDeed : BaseFactionTrapDeed - { - public override Type TrapType => typeof( FactionGasTrap ); - public override int LabelNumber => 1044602; // faction gas trap deed + public class FactionGasTrapDeed : BaseFactionTrapDeed + { + public FactionGasTrapDeed() : base(0x11AB) + { + } - public FactionGasTrapDeed() : base( 0x11AB ) - { - } + public FactionGasTrapDeed(Serial serial) : base(serial) + { + } - public FactionGasTrapDeed( Serial serial ) : base( serial ) - { - } + public override Type TrapType => typeof(FactionGasTrap); + public override int LabelNumber => 1044602; // faction gas trap deed - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/FactionSawTrap.cs b/Scripts/Engines/Factions/Items/Traps/FactionSawTrap.cs index be27743ee..376652372 100644 --- a/Scripts/Engines/Factions/Items/Traps/FactionSawTrap.cs +++ b/Scripts/Engines/Factions/Items/Traps/FactionSawTrap.cs @@ -2,83 +2,83 @@ using System; namespace Server.Factions { - public class FactionSawTrap : BaseFactionTrap - { - public override int LabelNumber => 1041047; // faction saw trap + public class FactionSawTrap : BaseFactionTrap + { + [Constructible] + public FactionSawTrap() : this(null) + { + } - public override int AttackMessage => 1010544; // The blade cuts deep into your skin! - public override int DisarmMessage => 1010540; // You carefully dismantle the saw mechanism and disable the trap. - public override int EffectSound => 0x218; - public override int MessageHue => 0x5A; + public FactionSawTrap(Serial serial) : base(serial) + { + } - public override AllowedPlacing AllowedPlacing => AllowedPlacing.ControlledFactionTown; + public FactionSawTrap(Faction f) : this(f, null) + { + } - public override void DoVisibleEffect() - { - Effects.SendLocationEffect( Location, Map, 0x11AD, 25, 10 ); - } + public FactionSawTrap(Faction f, Mobile m) : base(f, m, 0x11AC) + { + } - public override void DoAttackEffect( Mobile m ) - { - m.Damage( Utility.Dice( 6, 10, 40 ), m ); - } + public override int LabelNumber => 1041047; // faction saw trap - [Constructible] - public FactionSawTrap() : this( null ) - { - } + public override int AttackMessage => 1010544; // The blade cuts deep into your skin! + public override int DisarmMessage => 1010540; // You carefully dismantle the saw mechanism and disable the trap. + public override int EffectSound => 0x218; + public override int MessageHue => 0x5A; - public FactionSawTrap( Serial serial ) : base( serial ) - { - } + public override AllowedPlacing AllowedPlacing => AllowedPlacing.ControlledFactionTown; - public FactionSawTrap( Faction f ) : this( f, null ) - { - } + public override void DoVisibleEffect() + { + Effects.SendLocationEffect(Location, Map, 0x11AD, 25, 10); + } - public FactionSawTrap( Faction f, Mobile m ) : base( f, m, 0x11AC ) - { - } + public override void DoAttackEffect(Mobile m) + { + m.Damage(Utility.Dice(6, 10, 40), m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class FactionSawTrapDeed : BaseFactionTrapDeed - { - public override Type TrapType => typeof( FactionSawTrap ); - public override int LabelNumber => 1044604; // faction saw trap deed + public class FactionSawTrapDeed : BaseFactionTrapDeed + { + public FactionSawTrapDeed() : base(0x1107) + { + } - public FactionSawTrapDeed() : base( 0x1107 ) - { - } + public FactionSawTrapDeed(Serial serial) : base(serial) + { + } - public FactionSawTrapDeed( Serial serial ) : base( serial ) - { - } + public override Type TrapType => typeof(FactionSawTrap); + public override int LabelNumber => 1044604; // faction saw trap deed - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/FactionSpikeTrap.cs b/Scripts/Engines/Factions/Items/Traps/FactionSpikeTrap.cs index f73e96804..530d6df22 100644 --- a/Scripts/Engines/Factions/Items/Traps/FactionSpikeTrap.cs +++ b/Scripts/Engines/Factions/Items/Traps/FactionSpikeTrap.cs @@ -2,83 +2,86 @@ using System; namespace Server.Factions { - public class FactionSpikeTrap : BaseFactionTrap - { - public override int LabelNumber => 1044601; // faction spike trap + public class FactionSpikeTrap : BaseFactionTrap + { + [Constructible] + public FactionSpikeTrap() : this(null) + { + } - public override int AttackMessage => 1010545; // Large spikes in the ground spring up piercing your skin! - public override int DisarmMessage => 1010541; // You carefully dismantle the trigger on the spikes and disable the trap. - public override int EffectSound => 0x22E; - public override int MessageHue => 0x5A; + public FactionSpikeTrap(Faction f) : this(f, null) + { + } - public override AllowedPlacing AllowedPlacing => AllowedPlacing.ControlledFactionTown; + public FactionSpikeTrap(Faction f, Mobile m) : base(f, m, 0x11A0) + { + } - public override void DoVisibleEffect() - { - Effects.SendLocationEffect( Location, Map, 0x11A4, 12, 6 ); - } + public FactionSpikeTrap(Serial serial) : base(serial) + { + } - public override void DoAttackEffect( Mobile m ) - { - m.Damage( Utility.Dice( 6, 10, 40 ), m ); - } + public override int LabelNumber => 1044601; // faction spike trap - [Constructible] - public FactionSpikeTrap() : this( null ) - { - } + public override int AttackMessage => 1010545; // Large spikes in the ground spring up piercing your skin! - public FactionSpikeTrap( Faction f ) : this( f, null ) - { - } + public override int DisarmMessage => + 1010541; // You carefully dismantle the trigger on the spikes and disable the trap. - public FactionSpikeTrap( Faction f, Mobile m ) : base( f, m, 0x11A0 ) - { - } + public override int EffectSound => 0x22E; + public override int MessageHue => 0x5A; - public FactionSpikeTrap( Serial serial ) : base( serial ) - { - } + public override AllowedPlacing AllowedPlacing => AllowedPlacing.ControlledFactionTown; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void DoVisibleEffect() + { + Effects.SendLocationEffect(Location, Map, 0x11A4, 12, 6); + } - writer.Write( (int) 0 ); // version - } + public override void DoAttackEffect(Mobile m) + { + m.Damage(Utility.Dice(6, 10, 40), m); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } - public class FactionSpikeTrapDeed : BaseFactionTrapDeed - { - public override Type TrapType => typeof( FactionSpikeTrap ); - public override int LabelNumber => 1044605; // faction spike trap deed + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public FactionSpikeTrapDeed() : base( 0x11A5 ) - { - } + int version = reader.ReadInt(); + } + } - public FactionSpikeTrapDeed( Serial serial ) : base( serial ) - { - } + public class FactionSpikeTrapDeed : BaseFactionTrapDeed + { + public FactionSpikeTrapDeed() : base(0x11A5) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public FactionSpikeTrapDeed(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override Type TrapType => typeof(FactionSpikeTrap); + public override int LabelNumber => 1044605; // faction spike trap deed - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Items/Traps/FactionTrapRemovalKit.cs b/Scripts/Engines/Factions/Items/Traps/FactionTrapRemovalKit.cs index 0ac9e701b..2ce074e61 100644 --- a/Scripts/Engines/Factions/Items/Traps/FactionTrapRemovalKit.cs +++ b/Scripts/Engines/Factions/Items/Traps/FactionTrapRemovalKit.cs @@ -1,71 +1,71 @@ namespace Server.Factions { - public class FactionTrapRemovalKit : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public int Charges { get; set; } + public class FactionTrapRemovalKit : Item + { + [Constructible] + public FactionTrapRemovalKit() : base(7867) + { + LootType = LootType.Blessed; + Charges = 25; + } - public override int LabelNumber => 1041508; // a faction trap removal kit + public FactionTrapRemovalKit(Serial serial) : base(serial) + { + } - [Constructible] - public FactionTrapRemovalKit() : base( 7867 ) - { - LootType = LootType.Blessed; - Charges = 25; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Charges{ get; set; } - public void ConsumeCharge( Mobile consumer ) - { - --Charges; + public override int LabelNumber => 1041508; // a faction trap removal kit - if ( Charges <= 0 ) - { - Delete(); + public void ConsumeCharge(Mobile consumer) + { + --Charges; - consumer?.SendLocalizedMessage( 1042531 ); // You have used all of the parts in your trap removal kit. - } - } + if (Charges <= 0) + { + Delete(); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + consumer?.SendLocalizedMessage(1042531); // You have used all of the parts in your trap removal kit. + } + } - // NOTE: OSI does not list uses remaining; intentional difference - list.Add( 1060584, Charges.ToString() ); // uses remaining: ~1_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public FactionTrapRemovalKit( Serial serial ) : base( serial ) - { - } + // NOTE: OSI does not list uses remaining; intentional difference + list.Add(1060584, Charges.ToString()); // uses remaining: ~1_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.WriteEncodedInt( (int) Charges ); - } + writer.WriteEncodedInt(Charges); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Charges = reader.ReadEncodedInt(); - break; - } - case 0: - { - Charges = 25; - break; - } - } - } - } -} + switch (version) + { + case 1: + { + Charges = reader.ReadEncodedInt(); + break; + } + case 0: + { + Charges = 25; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/FactionWarHorse.cs b/Scripts/Engines/Factions/Mobiles/FactionWarHorse.cs index e71f582e2..aa26edf01 100644 --- a/Scripts/Engines/Factions/Mobiles/FactionWarHorse.cs +++ b/Scripts/Engines/Factions/Mobiles/FactionWarHorse.cs @@ -2,109 +2,111 @@ using Server.Mobiles; namespace Server.Factions { - public class FactionWarHorse : BaseMount - { - public override string CorpseName => "a war horse corpse"; - private Faction m_Faction; + public class FactionWarHorse : BaseMount + { + public const int SilverPrice = 500; + public const int GoldPrice = 3000; + private Faction m_Faction; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Faction Faction - { - get => m_Faction; - set - { - m_Faction = value; + [Constructible] + public FactionWarHorse() : this(null) + { + } - Body = m_Faction?.Definition.WarHorseBody ?? 0xE2; - ItemID = m_Faction?.Definition.WarHorseItem ?? 0x3EA0; - } - } + public FactionWarHorse(Faction faction) : base("a war horse", 0xE2, 0x3EA0, AIType.AI_Melee, FightMode.Aggressor, 10, + 1, 0.2, 0.4) + { + BaseSoundID = 0xA8; - public const int SilverPrice = 500; - public const int GoldPrice = 3000; + SetStr(400); + SetDex(125); + SetInt(51, 55); - [Constructible] - public FactionWarHorse() : this( null ) - { - } + SetHits(240); + SetMana(0); - public FactionWarHorse( Faction faction ) : base( "a war horse", 0xE2, 0x3EA0, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0xA8; + SetDamage(5, 8); - SetStr( 400 ); - SetDex( 125 ); - SetInt( 51, 55 ); + SetDamageType(ResistanceType.Physical, 100); - SetHits( 240 ); - SetMana( 0 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamage( 5, 8 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - SetDamageType( ResistanceType.Physical, 100 ); + Fame = 300; + Karma = 300; - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Tamable = true; + ControlSlots = 1; - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + Faction = faction; + } - Fame = 300; - Karma = 300; + public FactionWarHorse(Serial serial) : base(serial) + { + } - Tamable = true; - ControlSlots = 1; + public override string CorpseName => "a war horse corpse"; - Faction = faction; - } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Faction Faction + { + get => m_Faction; + set + { + m_Faction = value; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + Body = m_Faction?.Definition.WarHorseBody ?? 0xE2; + ItemID = m_Faction?.Definition.WarHorseItem ?? 0x3EA0; + } + } - public FactionWarHorse( Serial serial ) : base( serial ) - { - } + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override void OnDoubleClick( Mobile from ) - { - PlayerState pl = PlayerState.Find( from ); + public override void OnDoubleClick(Mobile from) + { + PlayerState pl = PlayerState.Find(from); - if ( pl == null ) - from.SendLocalizedMessage( 1010366 ); // You cannot mount a faction war horse! - else if ( pl.Faction != Faction ) - from.SendLocalizedMessage( 1010367 ); // You cannot ride an opposing faction's war horse! - else if ( pl.Rank.Rank < 2 ) - from.SendLocalizedMessage( 1010368 ); // You must achieve a faction rank of at least two before riding a war horse! - else - base.OnDoubleClick( from ); - } + if (pl == null) + from.SendLocalizedMessage(1010366); // You cannot mount a faction war horse! + else if (pl.Faction != Faction) + from.SendLocalizedMessage(1010367); // You cannot ride an opposing faction's war horse! + else if (pl.Rank.Rank < 2) + from.SendLocalizedMessage( + 1010368); // You must achieve a faction rank of at least two before riding a war horse! + else + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - Faction.WriteReference( writer, m_Faction ); - } + Faction.WriteReference(writer, m_Faction); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Faction = Faction.ReadReference( reader ); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Faction = Faction.ReadReference(reader); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/BaseFactionGuard.cs b/Scripts/Engines/Factions/Mobiles/Guards/BaseFactionGuard.cs index 72628f637..62aaa0d9d 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/BaseFactionGuard.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/BaseFactionGuard.cs @@ -1,491 +1,528 @@ using System; using System.Collections.Generic; +using Server.Factions.AI; using Server.Items; using Server.Mobiles; using Server.Network; -using Server.Factions.AI; namespace Server.Factions { - public abstract class BaseFactionGuard : BaseCreature - { - private Faction m_Faction; - private Town m_Town; + public abstract class BaseFactionGuard : BaseCreature + { + private const int ListenRange = 12; + + private static Type[] m_StrongPotions = + { + typeof(GreaterHealPotion), typeof(GreaterHealPotion), typeof(GreaterHealPotion), + typeof(GreaterCurePotion), typeof(GreaterCurePotion), typeof(GreaterCurePotion), + typeof(GreaterStrengthPotion), typeof(GreaterStrengthPotion), + typeof(GreaterAgilityPotion), typeof(GreaterAgilityPotion), + typeof(TotalRefreshPotion), typeof(TotalRefreshPotion), + typeof(GreaterExplosionPotion) + }; + + private static Type[] m_WeakPotions = + { + typeof(HealPotion), typeof(HealPotion), typeof(HealPotion), + typeof(CurePotion), typeof(CurePotion), typeof(CurePotion), + typeof(StrengthPotion), typeof(StrengthPotion), + typeof(AgilityPotion), typeof(AgilityPotion), + typeof(RefreshPotion), typeof(RefreshPotion), + typeof(ExplosionPotion) + }; + + private Faction m_Faction; + + private DateTime m_OrdersEnd; + private Town m_Town; + + public BaseFactionGuard(string title) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Orders = new Orders(this); + Title = title; + + RangeHome = 6; + } + + public BaseFactionGuard(Serial serial) : base(serial) + { + } + + public override bool BardImmune => true; + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Faction Faction + { + get => m_Faction; + set + { + Unregister(); + m_Faction = value; + Register(); + } + } + + public Orders Orders{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Town Town + { + get => m_Town; + set + { + Unregister(); + m_Town = value; + Register(); + } + } + + public abstract GuardAI GuardAI{ get; } + + protected override BaseAI ForcedAI => new FactionGuardAI(this); + + public override TimeSpan ReacquireDelay => TimeSpan.FromSeconds(2.0); + + public override bool ClickTitle => false; + + public void Register() + { + if (m_Town != null && m_Faction != null) + m_Town.RegisterGuard(this); + } + + public void Unregister() + { + m_Town?.UnregisterGuard(this); + } + + public override bool IsEnemy(Mobile m) + { + Faction ourFaction = m_Faction; + Faction theirFaction = Faction.Find(m); + + if (theirFaction == null && m is BaseFactionGuard guard) + theirFaction = guard.Faction; + + if (ourFaction != null && theirFaction != null && ourFaction != theirFaction) + { + ReactionType reactionType = Orders.GetReaction(theirFaction).Type; + + if (reactionType == ReactionType.Attack) + return true; + + List list = m.Aggressed; + + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo ai = list[i]; + + if (ai.Defender is BaseFactionGuard bf && bf.Faction == ourFaction) + return true; + } + } + + return false; + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m.Player && m.Alive && InRange(m, 10) && !InRange(oldLocation, 10) && InLOS(m) && + Orders.GetReaction(Faction.Find(m)).Type == ReactionType.Warn) + { + Direction = GetDirectionTo(m); + + string warning = null; + + switch (Utility.Random(6)) + { + case 0: + warning = + "I warn you, {0}, you would do well to leave this area before someone shows you the world of gray."; + break; + case 1: + warning = "It would be wise to leave this area, {0}, lest your head become my commanders' trophy."; + break; + case 2: + warning = + "You are bold, {0}, for one of the meager {1}. Leave now, lest you be taught the taste of dirt."; + break; + case 3: + warning = "Your presence here is an insult, {0}. Be gone now, knave."; + break; + case 4: + warning = "Dost thou wish to be hung by your toes, {0}? Nay? Then come no closer."; + break; + case 5: + warning = "Hey, {0}. Yeah, you. Get out of here before I beat you with a stick."; + break; + } + + Faction faction = Faction.Find(m); + + Say(warning, m.Name, faction == null ? "civilians" : faction.Definition.FriendlyName); + } + } + + public override bool HandlesOnSpeech(Mobile from) + { + if (InRange(from, ListenRange)) + return true; + + return base.HandlesOnSpeech(from); + } + + private void ChangeReaction(Faction faction, ReactionType type) + { + if (faction == null) + { + switch (type) + { + case ReactionType.Ignore: + Say(1005179); + break; // Civilians will now be ignored. + case ReactionType.Warn: + Say(1005180); + break; // Civilians will now be warned of their impending deaths. + case ReactionType.Attack: return; + } + } + else + { + TextDefinition def = null; + + switch (type) + { + case ReactionType.Ignore: + def = faction.Definition.GuardIgnore; + break; + case ReactionType.Warn: + def = faction.Definition.GuardWarn; + break; + case ReactionType.Attack: + def = faction.Definition.GuardAttack; + break; + } + + if (def != null && def.Number > 0) + Say(def.Number); + else if (def?.String != null) + Say(def.String); + } + + Orders.SetReaction(faction, type); + } + + private bool WasNamed(string speech) + { + string name = Name; + + return name != null && Insensitive.StartsWith(speech, name); + } + + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); + + Mobile from = e.Mobile; + + if (!e.Handled && InRange(from, ListenRange) && from.Alive) + { + if (e.HasKeyword(0xE6) && (Insensitive.Equals(e.Speech, "orders") || WasNamed(e.Speech))) // *orders* + { + if (m_Town == null || !m_Town.IsSheriff(from)) + { + Say(1042189); // I don't work for you! + } + else if (Town.FromRegion(Region) == m_Town) + { + Say(1042180); // Your orders, sire? + m_OrdersEnd = DateTime.UtcNow + TimeSpan.FromSeconds(10.0); + } + } + else if (DateTime.UtcNow < m_OrdersEnd) + { + if (m_Town != null && m_Town.IsSheriff(from) && Town.FromRegion(Region) == m_Town) + { + m_OrdersEnd = DateTime.UtcNow + TimeSpan.FromSeconds(10.0); + + bool understood = true; + ReactionType newType = 0; + + if (Insensitive.Contains(e.Speech, "attack")) + newType = ReactionType.Attack; + else if (Insensitive.Contains(e.Speech, "warn")) + newType = ReactionType.Warn; + else if (Insensitive.Contains(e.Speech, "ignore")) + newType = ReactionType.Ignore; + else + understood = false; + + if (understood) + { + understood = false; + + if (Insensitive.Contains(e.Speech, "civil")) + { + ChangeReaction(null, newType); + understood = true; + } + + List factions = Faction.Factions; + + for (int i = 0; i < factions.Count; ++i) + { + Faction faction = factions[i]; + + if (faction != m_Faction && Insensitive.Contains(e.Speech, faction.Definition.Keyword)) + { + ChangeReaction(faction, newType); + understood = true; + } + } + } + else if (Insensitive.Contains(e.Speech, "patrol")) + { + Home = Location; + RangeHome = 6; + Combatant = null; + Orders.Movement = MovementType.Patrol; + Say(1005146); // This spot looks like it needs protection! I shall guard it with my life. + understood = true; + } + else if (Insensitive.Contains(e.Speech, "follow")) + { + Home = Location; + RangeHome = 6; + Combatant = null; + Orders.Follow = from; + Orders.Movement = MovementType.Follow; + Say(1005144); // Yes, Sire. + understood = true; + } + + if (!understood) + Say(1042183); // I'm sorry, I don't understand your orders... + } + } + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Faction != null && Map == Faction.Facet) + list.Add(1060846, m_Faction.Definition.PropName); // Guard: ~1_val~ + } + + public override void OnSingleClick(Mobile from) + { + if (m_Faction != null && Map == Faction.Facet) + { + string text = string.Concat("(Guard, ", m_Faction.Definition.FriendlyName, ")"); + + int hue = Faction.Find(from) == m_Faction ? 98 : 38; + + PrivateOverheadMessage(MessageType.Label, hue, true, text, from.NetState); + } + + base.OnSingleClick(from); + } + + public virtual void GenerateRandomHair() + { + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); + } + + public void PackStrongPotions(int min, int max) + { + PackStrongPotions(Utility.RandomMinMax(min, max)); + } + + public void PackStrongPotions(int count) + { + for (int i = 0; i < count; ++i) + PackStrongPotion(); + } + + public void PackStrongPotion() + { + PackItem(Loot.Construct(m_StrongPotions)); + } + + public void PackWeakPotions(int min, int max) + { + PackWeakPotions(Utility.RandomMinMax(min, max)); + } + + public void PackWeakPotions(int count) + { + for (int i = 0; i < count; ++i) + PackWeakPotion(); + } + + public void PackWeakPotion() + { + PackItem(Loot.Construct(m_WeakPotions)); + } + + public Item Immovable(Item item) + { + item.Movable = false; + return item; + } + + public Item Newbied(Item item) + { + item.LootType = LootType.Newbied; + return item; + } + + public Item Rehued(Item item, int hue) + { + item.Hue = hue; + return item; + } + + public Item Layered(Item item, Layer layer) + { + item.Layer = layer; + return item; + } + + public Item Resourced(BaseWeapon weapon, CraftResource resource) + { + weapon.Resource = resource; + return weapon; + } + + public Item Resourced(BaseArmor armor, CraftResource resource) + { + armor.Resource = resource; + return armor; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + Unregister(); + } + + public override void OnDeath(Container c) + { + base.OnDeath(c); + + c.Delete(); + } + + public virtual void GenerateBody(bool isFemale, bool randomHair) + { + Hue = Utility.RandomSkinHue(); + + if (isFemale) + { + Female = true; + Body = 401; + Name = NameList.RandomName("female"); + } + else + { + Female = false; + Body = 400; + Name = NameList.RandomName("male"); + } + + if (randomHair) + GenerateRandomHair(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + Faction.WriteReference(writer, m_Faction); + Town.WriteReference(writer, m_Town); + + Orders.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Faction = Faction.ReadReference(reader); + m_Town = Town.ReadReference(reader); + Orders = new Orders(this, reader); + + Timer.DelayCall(TimeSpan.Zero, Register); + } + } + + public class VirtualMount : IMount + { + private VirtualMountItem m_Item; + + public VirtualMount(VirtualMountItem item) + { + m_Item = item; + } + + public Mobile Rider + { + get => m_Item.Rider; + set { } + } + + public virtual void OnRiderDamaged(int amount, Mobile from, bool willKill) + { + } + } + + public class VirtualMountItem : Item, IMountItem + { + private VirtualMount m_Mount; + + public VirtualMountItem(Mobile mob) : base(0x3EA0) + { + Layer = Layer.Mount; + + Rider = mob; + m_Mount = new VirtualMount(this); + } + + public VirtualMountItem(Serial serial) : base(serial) + { + m_Mount = new VirtualMount(this); + } - public override bool BardImmune => true; + public Mobile Rider{ get; private set; } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Faction Faction - { - get => m_Faction; - set{ Unregister(); m_Faction = value; Register(); } - } - - public Orders Orders { get; private set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Town Town - { - get => m_Town; - set{ Unregister(); m_Town = value; Register(); } - } - - public void Register() - { - if ( m_Town != null && m_Faction != null ) - m_Town.RegisterGuard( this ); - } - - public void Unregister() - { - m_Town?.UnregisterGuard( this ); - } - - public abstract GuardAI GuardAI{ get; } - - protected override BaseAI ForcedAI => new FactionGuardAI( this ); - - public override TimeSpan ReacquireDelay => TimeSpan.FromSeconds( 2.0 ); - - public override bool IsEnemy( Mobile m ) - { - Faction ourFaction = m_Faction; - Faction theirFaction = Faction.Find( m ); - - if ( theirFaction == null && m is BaseFactionGuard guard ) - theirFaction = guard.Faction; - - if ( ourFaction != null && theirFaction != null && ourFaction != theirFaction ) - { - ReactionType reactionType = Orders.GetReaction( theirFaction ).Type; - - if ( reactionType == ReactionType.Attack ) - return true; - - List list = m.Aggressed; - - for ( int i = 0; i < list.Count; ++i ) - { - AggressorInfo ai = list[i]; - - if ( ai.Defender is BaseFactionGuard bf && bf.Faction == ourFaction ) - return true; - } - } - - return false; - } - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m.Player && m.Alive && InRange( m, 10 ) && !InRange( oldLocation, 10 ) && InLOS( m ) && Orders.GetReaction( Faction.Find( m ) ).Type == ReactionType.Warn ) - { - Direction = GetDirectionTo( m ); - - string warning = null; - - switch ( Utility.Random( 6 ) ) - { - case 0: warning = "I warn you, {0}, you would do well to leave this area before someone shows you the world of gray."; break; - case 1: warning = "It would be wise to leave this area, {0}, lest your head become my commanders' trophy."; break; - case 2: warning = "You are bold, {0}, for one of the meager {1}. Leave now, lest you be taught the taste of dirt."; break; - case 3: warning = "Your presence here is an insult, {0}. Be gone now, knave."; break; - case 4: warning = "Dost thou wish to be hung by your toes, {0}? Nay? Then come no closer."; break; - case 5: warning = "Hey, {0}. Yeah, you. Get out of here before I beat you with a stick."; break; - } - - Faction faction = Faction.Find( m ); - - Say( warning, m.Name, faction == null ? "civilians" : faction.Definition.FriendlyName ); - } - } - - private const int ListenRange = 12; - - public override bool HandlesOnSpeech( Mobile from ) - { - if ( InRange( from, ListenRange ) ) - return true; - - return base.HandlesOnSpeech( from ); - } - - private DateTime m_OrdersEnd; - - private void ChangeReaction( Faction faction, ReactionType type ) - { - if ( faction == null ) - { - switch ( type ) - { - case ReactionType.Ignore: Say( 1005179 ); break; // Civilians will now be ignored. - case ReactionType.Warn: Say( 1005180 ); break; // Civilians will now be warned of their impending deaths. - case ReactionType.Attack: return; - } - } - else - { - TextDefinition def = null; - - switch ( type ) - { - case ReactionType.Ignore: def = faction.Definition.GuardIgnore; break; - case ReactionType.Warn: def = faction.Definition.GuardWarn; break; - case ReactionType.Attack: def = faction.Definition.GuardAttack; break; - } - - if ( def != null && def.Number > 0 ) - Say( def.Number ); - else if ( def?.String != null ) - Say( def.String ); - } - - Orders.SetReaction( faction, type ); - } - - private bool WasNamed( string speech ) - { - string name = Name; - - return ( name != null && Insensitive.StartsWith( speech, name ) ); - } - - public override void OnSpeech( SpeechEventArgs e ) - { - base.OnSpeech( e ); - - Mobile from = e.Mobile; - - if ( !e.Handled && InRange( from, ListenRange ) && from.Alive ) - { - if ( e.HasKeyword( 0xE6 ) && (Insensitive.Equals( e.Speech, "orders" ) || WasNamed( e.Speech )) ) // *orders* - { - if ( m_Town == null || !m_Town.IsSheriff( from ) ) - { - Say( 1042189 ); // I don't work for you! - } - else if ( Town.FromRegion( Region ) == m_Town ) - { - Say( 1042180 ); // Your orders, sire? - m_OrdersEnd = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 ); - } - } - else if ( DateTime.UtcNow < m_OrdersEnd ) - { - if ( m_Town != null && m_Town.IsSheriff( from ) && Town.FromRegion( Region ) == m_Town ) - { - m_OrdersEnd = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 ); - - bool understood = true; - ReactionType newType = 0; - - if ( Insensitive.Contains( e.Speech, "attack" ) ) - newType = ReactionType.Attack; - else if ( Insensitive.Contains( e.Speech, "warn" ) ) - newType = ReactionType.Warn; - else if ( Insensitive.Contains( e.Speech, "ignore" ) ) - newType = ReactionType.Ignore; - else - understood = false; - - if ( understood ) - { - understood = false; - - if ( Insensitive.Contains( e.Speech, "civil" ) ) - { - ChangeReaction( null, newType ); - understood = true; - } - - List factions = Faction.Factions; - - for ( int i = 0; i < factions.Count; ++i ) - { - Faction faction = factions[i]; - - if ( faction != m_Faction && Insensitive.Contains( e.Speech, faction.Definition.Keyword ) ) - { - ChangeReaction( faction, newType ); - understood = true; - } - } - } - else if ( Insensitive.Contains( e.Speech, "patrol" ) ) - { - Home = Location; - RangeHome = 6; - Combatant = null; - Orders.Movement = MovementType.Patrol; - Say( 1005146 ); // This spot looks like it needs protection! I shall guard it with my life. - understood = true; - } - else if ( Insensitive.Contains( e.Speech, "follow" ) ) - { - Home = Location; - RangeHome = 6; - Combatant = null; - Orders.Follow = from; - Orders.Movement = MovementType.Follow; - Say( 1005144 ); // Yes, Sire. - understood = true; - } - - if ( !understood ) - Say( 1042183 ); // I'm sorry, I don't understand your orders... - } - } - } - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_Faction != null && Map == Faction.Facet ) - list.Add( 1060846, m_Faction.Definition.PropName ); // Guard: ~1_val~ - } - - public override void OnSingleClick( Mobile from ) - { - if ( m_Faction != null && Map == Faction.Facet ) - { - string text = string.Concat( "(Guard, ", m_Faction.Definition.FriendlyName, ")" ); - - int hue = ( Faction.Find( from ) == m_Faction ? 98 : 38 ); - - PrivateOverheadMessage( MessageType.Label, hue, true, text, from.NetState ); - } - - base.OnSingleClick( from ); - } - - public virtual void GenerateRandomHair() - { - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); - } - - private static Type[] m_StrongPotions = { - typeof( GreaterHealPotion ), typeof( GreaterHealPotion ), typeof( GreaterHealPotion ), - typeof( GreaterCurePotion ), typeof( GreaterCurePotion ), typeof( GreaterCurePotion ), - typeof( GreaterStrengthPotion ), typeof( GreaterStrengthPotion ), - typeof( GreaterAgilityPotion ), typeof( GreaterAgilityPotion ), - typeof( TotalRefreshPotion ), typeof( TotalRefreshPotion ), - typeof( GreaterExplosionPotion ) - }; - - private static Type[] m_WeakPotions = { - typeof( HealPotion ), typeof( HealPotion ), typeof( HealPotion ), - typeof( CurePotion ), typeof( CurePotion ), typeof( CurePotion ), - typeof( StrengthPotion ), typeof( StrengthPotion ), - typeof( AgilityPotion ), typeof( AgilityPotion ), - typeof( RefreshPotion ), typeof( RefreshPotion ), - typeof( ExplosionPotion ) - }; - - public void PackStrongPotions( int min, int max ) - { - PackStrongPotions( Utility.RandomMinMax( min, max ) ); - } - - public void PackStrongPotions( int count ) - { - for ( int i = 0; i < count; ++i ) - PackStrongPotion(); - } - - public void PackStrongPotion() - { - PackItem( Loot.Construct( m_StrongPotions ) ); - } - - public void PackWeakPotions( int min, int max ) - { - PackWeakPotions( Utility.RandomMinMax( min, max ) ); - } - - public void PackWeakPotions( int count ) - { - for ( int i = 0; i < count; ++i ) - PackWeakPotion(); - } - - public void PackWeakPotion() - { - PackItem( Loot.Construct( m_WeakPotions ) ); - } - - public Item Immovable( Item item ) - { - item.Movable = false; - return item; - } - - public Item Newbied( Item item ) - { - item.LootType = LootType.Newbied; - return item; - } - - public Item Rehued( Item item, int hue ) - { - item.Hue = hue; - return item; - } - - public Item Layered( Item item, Layer layer ) - { - item.Layer = layer; - return item; - } - - public Item Resourced( BaseWeapon weapon, CraftResource resource ) - { - weapon.Resource = resource; - return weapon; - } - - public Item Resourced( BaseArmor armor, CraftResource resource ) - { - armor.Resource = resource; - return armor; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - Unregister(); - } - - public override void OnDeath( Container c ) - { - base.OnDeath( c ); - - c.Delete(); - } - - public virtual void GenerateBody( bool isFemale, bool randomHair ) - { - Hue = Utility.RandomSkinHue(); - - if ( isFemale ) - { - Female = true; - Body = 401; - Name = NameList.RandomName( "female" ); - } - else - { - Female = false; - Body = 400; - Name = NameList.RandomName( "male" ); - } - - if ( randomHair ) - GenerateRandomHair(); - } - - public override bool ClickTitle => false; - - public BaseFactionGuard( string title ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Orders = new Orders( this ); - Title = title; - - RangeHome = 6; - } - - public BaseFactionGuard( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - Faction.WriteReference( writer, m_Faction ); - Town.WriteReference( writer, m_Town ); - - Orders.Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Faction = Faction.ReadReference( reader ); - m_Town = Town.ReadReference( reader ); - Orders = new Orders( this, reader ); - - Timer.DelayCall( TimeSpan.Zero, Register ); - } - } - - public class VirtualMount : IMount - { - private VirtualMountItem m_Item; - - public Mobile Rider - { - get => m_Item.Rider; - set{} - } - - public VirtualMount( VirtualMountItem item ) - { - m_Item = item; - } - - public virtual void OnRiderDamaged( int amount, Mobile from, bool willKill ) - { - } - } + public IMount Mount => m_Mount; - public class VirtualMountItem : Item, IMountItem - { - private VirtualMount m_Mount; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public Mobile Rider { get; private set; } + writer.Write(0); // version - public VirtualMountItem( Mobile mob ) : base( 0x3EA0 ) - { - Layer = Layer.Mount; + writer.Write(Rider); + } - Rider = mob; - m_Mount = new VirtualMount( this ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public IMount Mount => m_Mount; + int version = reader.ReadInt(); - public VirtualMountItem( Serial serial ) : base( serial ) - { - m_Mount = new VirtualMount( this ); - } + Rider = reader.ReadMobile(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( (Mobile) Rider ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Rider = reader.ReadMobile(); - - if ( Rider == null ) - Delete(); - } - } -} + if (Rider == null) + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/GuardAI.cs b/Scripts/Engines/Factions/Mobiles/Guards/GuardAI.cs index 33c1208b7..f8c45ffbb 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/GuardAI.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/GuardAI.cs @@ -1,754 +1,773 @@ using System; using System.Collections.Generic; +using Server.Factions.AI; using Server.Items; using Server.Mobiles; -using Server.Targeting; -using Server.Factions.AI; using Server.Spells; -using Server.Spells.First; -using Server.Spells.Second; -using Server.Spells.Third; -using Server.Spells.Fourth; using Server.Spells.Fifth; -using Server.Spells.Sixth; +using Server.Spells.First; +using Server.Spells.Fourth; +using Server.Spells.Second; using Server.Spells.Seventh; +using Server.Spells.Sixth; +using Server.Spells.Third; +using Server.Targeting; namespace Server.Factions { - public enum GuardAI - { - Bless = 0x01, // heal, cure, +stats - Curse = 0x02, // poison, -stats - Melee = 0x04, // weapons - Magic = 0x08, // damage spells - Smart = 0x10 // smart weapons/damage spells - } - - public class ComboEntry - { - public Type Spell { get; } - - public TimeSpan Hold { get; } - - public int Chance { get; } - - public ComboEntry( Type spell ) : this( spell, 100, TimeSpan.Zero ) - { - } - - public ComboEntry( Type spell, int chance ) : this( spell, chance, TimeSpan.Zero ) - { - } - - public ComboEntry( Type spell, int chance, TimeSpan hold ) - { - Spell = spell; - Chance = chance; - Hold = hold; - } - } - - public class SpellCombo - { - public int Mana { get; } - - public ComboEntry[] Entries { get; } - - public SpellCombo( int mana, params ComboEntry[] entries ) - { - Mana = mana; - Entries = entries; - } - - public static readonly SpellCombo Simple = new SpellCombo( 50, - new ComboEntry( typeof( ParalyzeSpell ), 20 ), - new ComboEntry( typeof( ExplosionSpell ), 100, TimeSpan.FromSeconds( 2.8 ) ), - new ComboEntry( typeof( PoisonSpell ), 30 ), - new ComboEntry( typeof( EnergyBoltSpell ) ) - ); - - public static readonly SpellCombo Strong = new SpellCombo( 90, - new ComboEntry( typeof( ParalyzeSpell ), 20 ), - new ComboEntry( typeof( ExplosionSpell ), 50, TimeSpan.FromSeconds( 2.8 ) ), - new ComboEntry( typeof( PoisonSpell ), 30 ), - new ComboEntry( typeof( ExplosionSpell ), 100, TimeSpan.FromSeconds( 2.8 ) ), - new ComboEntry( typeof( EnergyBoltSpell ) ), - new ComboEntry( typeof( PoisonSpell ), 30 ), - new ComboEntry( typeof( EnergyBoltSpell ) ) - ); - - public static Spell Process( Mobile mob, Mobile targ, ref SpellCombo combo, ref int index, ref DateTime releaseTime ) - { - while ( ++index < combo.Entries.Length ) - { - ComboEntry entry = combo.Entries[index]; - - if ( entry.Spell == typeof( PoisonSpell ) && targ.Poisoned ) - continue; - - if ( entry.Chance > Utility.Random( 100 ) ) - { - releaseTime = DateTime.UtcNow + entry.Hold; - return (Spell) Activator.CreateInstance( entry.Spell, new object[]{ mob, null } ); - } - } - - combo = null; - index = -1; - return null; - } - } - - public class FactionGuardAI : BaseAI - { - private BaseFactionGuard m_Guard; + public enum GuardAI + { + Bless = 0x01, // heal, cure, +stats + Curse = 0x02, // poison, -stats + Melee = 0x04, // weapons + Magic = 0x08, // damage spells + Smart = 0x10 // smart weapons/damage spells + } + + public class ComboEntry + { + public ComboEntry(Type spell) : this(spell, 100, TimeSpan.Zero) + { + } + + public ComboEntry(Type spell, int chance) : this(spell, chance, TimeSpan.Zero) + { + } + + public ComboEntry(Type spell, int chance, TimeSpan hold) + { + Spell = spell; + Chance = chance; + Hold = hold; + } + + public Type Spell{ get; } + + public TimeSpan Hold{ get; } + + public int Chance{ get; } + } + + public class SpellCombo + { + public static readonly SpellCombo Simple = new SpellCombo(50, + new ComboEntry(typeof(ParalyzeSpell), 20), + new ComboEntry(typeof(ExplosionSpell), 100, TimeSpan.FromSeconds(2.8)), + new ComboEntry(typeof(PoisonSpell), 30), + new ComboEntry(typeof(EnergyBoltSpell)) + ); + + public static readonly SpellCombo Strong = new SpellCombo(90, + new ComboEntry(typeof(ParalyzeSpell), 20), + new ComboEntry(typeof(ExplosionSpell), 50, TimeSpan.FromSeconds(2.8)), + new ComboEntry(typeof(PoisonSpell), 30), + new ComboEntry(typeof(ExplosionSpell), 100, TimeSpan.FromSeconds(2.8)), + new ComboEntry(typeof(EnergyBoltSpell)), + new ComboEntry(typeof(PoisonSpell), 30), + new ComboEntry(typeof(EnergyBoltSpell)) + ); + + public SpellCombo(int mana, params ComboEntry[] entries) + { + Mana = mana; + Entries = entries; + } + + public int Mana{ get; } + + public ComboEntry[] Entries{ get; } + + public static Spell Process(Mobile mob, Mobile targ, ref SpellCombo combo, ref int index, ref DateTime releaseTime) + { + while (++index < combo.Entries.Length) + { + ComboEntry entry = combo.Entries[index]; + + if (entry.Spell == typeof(PoisonSpell) && targ.Poisoned) + continue; + + if (entry.Chance > Utility.Random(100)) + { + releaseTime = DateTime.UtcNow + entry.Hold; + return (Spell)Activator.CreateInstance(entry.Spell, mob, null); + } + } + + combo = null; + index = -1; + return null; + } + } + + public class FactionGuardAI : BaseAI + { + private const int ManaReserve = 30; + + private BandageContext m_Bandage; + private DateTime m_BandageStart; + + private SpellCombo m_Combo; + private int m_ComboIndex = -1; + private BaseFactionGuard m_Guard; + private DateTime m_ReleaseTarget; + + public FactionGuardAI(BaseFactionGuard guard) : base(guard) + { + m_Guard = guard; + } + + public bool IsDamaged => m_Guard.Hits < m_Guard.HitsMax; - private BandageContext m_Bandage; - private DateTime m_BandageStart; + public bool IsPoisoned => m_Guard.Poisoned; - private SpellCombo m_Combo; - private int m_ComboIndex = -1; - private DateTime m_ReleaseTarget; + public TimeSpan TimeUntilBandage + { + get + { + if (m_Bandage != null && m_Bandage.Timer == null) + m_Bandage = null; - private const int ManaReserve = 30; + if (m_Bandage == null) + return TimeSpan.MaxValue; - public bool IsAllowed( GuardAI flag ) - { - return ( ( m_Guard.GuardAI & flag ) == flag ); - } + TimeSpan ts = m_BandageStart + m_Bandage.Timer.Delay - DateTime.UtcNow; - public bool IsDamaged => ( m_Guard.Hits < m_Guard.HitsMax ); + if (ts < TimeSpan.FromSeconds(-1.0)) + { + m_Bandage = null; + return TimeSpan.MaxValue; + } - public bool IsPoisoned => m_Guard.Poisoned; + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; - public TimeSpan TimeUntilBandage - { - get - { - if ( m_Bandage != null && m_Bandage.Timer == null ) - m_Bandage = null; + return ts; + } + } + + public bool IsAllowed(GuardAI flag) + { + return (m_Guard.GuardAI & flag) == flag; + } + + public bool DequipWeapon() + { + Container pack = m_Guard.Backpack; + + if (pack == null) + return false; + + if (m_Guard.Weapon is Item weapon && weapon.Parent == m_Guard && !(weapon is Fists)) + { + pack.DropItem(weapon); + return true; + } - if ( m_Bandage == null ) - return TimeSpan.MaxValue; + return false; + } - TimeSpan ts = ( m_BandageStart + m_Bandage.Timer.Delay ) - DateTime.UtcNow; + public bool EquipWeapon() + { + Container pack = m_Guard.Backpack; - if ( ts < TimeSpan.FromSeconds( -1.0 ) ) - { - m_Bandage = null; - return TimeSpan.MaxValue; - } - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - return ts; - } - } + Item weapon = pack?.FindItemByType(typeof(BaseWeapon)); - public bool DequipWeapon() - { - Container pack = m_Guard.Backpack; + if (weapon == null) + return false; - if ( pack == null ) - return false; + return m_Guard.EquipItem(weapon); + } - if ( m_Guard.Weapon is Item weapon && weapon.Parent == m_Guard && !(weapon is Fists) ) - { - pack.DropItem( weapon ); - return true; - } + public bool StartBandage() + { + m_Bandage = null; - return false; - } + Container pack = m_Guard.Backpack; - public bool EquipWeapon() - { - Container pack = m_Guard.Backpack; + Item bandage = pack?.FindItemByType(typeof(Bandage)); - Item weapon = pack?.FindItemByType( typeof( BaseWeapon ) ); + if (bandage == null) + return false; - if ( weapon == null ) - return false; + m_Bandage = BandageContext.BeginHeal(m_Guard, m_Guard); + m_BandageStart = DateTime.UtcNow; + return m_Bandage != null; + } - return m_Guard.EquipItem( weapon ); - } + public bool UseItemByType(Type type) + { + Container pack = m_Guard.Backpack; - public bool StartBandage() - { - m_Bandage = null; + Item item = pack?.FindItemByType(type); - Container pack = m_Guard.Backpack; + if (item == null) + return false; - Item bandage = pack?.FindItemByType( typeof( Bandage ) ); + bool requip = DequipWeapon(); - if ( bandage == null ) - return false; + item.OnDoubleClick(m_Guard); - m_Bandage = BandageContext.BeginHeal( m_Guard, m_Guard ); - m_BandageStart = DateTime.UtcNow; - return ( m_Bandage != null ); - } + if (requip) + EquipWeapon(); - public bool UseItemByType( Type type ) - { - Container pack = m_Guard.Backpack; + return true; + } - Item item = pack?.FindItemByType( type ); + public int GetStatMod(Mobile mob, StatType type) + { + StatMod mod = mob.GetStatMod($"[Magic] {type} Offset"); - if ( item == null ) - return false; + if (mod == null) + return 0; - bool requip = DequipWeapon(); + return mod.Offset; + } - item.OnDoubleClick( m_Guard ); + public Spell RandomOffenseSpell() + { + int maxCircle = (int)((m_Guard.Skills.Magery.Value + 20.0) / (100.0 / 7.0)); - if ( requip ) - EquipWeapon(); + if (maxCircle < 1) + maxCircle = 1; - return true; - } - - public int GetStatMod( Mobile mob, StatType type ) - { - StatMod mod = mob.GetStatMod($"[Magic] {type} Offset"); - - if ( mod == null ) - return 0; - - return mod.Offset; - } - - public Spell RandomOffenseSpell() - { - int maxCircle = (int)((m_Guard.Skills.Magery.Value + 20.0) / (100.0 / 7.0)); - - if ( maxCircle < 1 ) - maxCircle = 1; - - switch ( Utility.Random( maxCircle*2 ) ) - { - case 0: case 1: return new MagicArrowSpell( m_Guard, null ); - case 2: case 3: return new HarmSpell( m_Guard, null ); - case 4: case 5: return new FireballSpell( m_Guard, null ); - case 6: case 7: return new LightningSpell( m_Guard, null ); - case 8: return new MindBlastSpell( m_Guard, null ); - case 9: return new ParalyzeSpell( m_Guard, null ); - case 10: return new EnergyBoltSpell( m_Guard, null ); - case 11: return new ExplosionSpell( m_Guard, null ); - default: return new FlameStrikeSpell( m_Guard, null ); - } - } - - public Mobile FindDispelTarget( bool activeOnly ) - { - if ( m_Mobile.Deleted || m_Mobile.Int < 95 || CanDispel( m_Mobile ) || m_Mobile.AutoDispel ) - return null; - - if ( activeOnly ) - { - List aggressed = m_Mobile.Aggressed; - List aggressors = m_Mobile.Aggressors; - - Mobile active = null; - double activePrio = 0.0; - - Mobile comb = m_Mobile.Combatant; - - if ( comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && m_Mobile.InRange( comb, 12 ) && CanDispel( comb ) ) - { - active = comb; - activePrio = m_Mobile.GetDistanceToSqrt( comb ); - - if ( activePrio <= 2 ) - return active; - } - - for ( int i = 0; i < aggressed.Count; ++i ) - { - AggressorInfo info = aggressed[i]; - Mobile m = info.Defender; - - if ( m != comb && m.Combatant == m_Mobile && m_Mobile.InRange( m, 12 ) && CanDispel( m ) ) - { - double prio = m_Mobile.GetDistanceToSqrt( m ); - - if ( active == null || prio < activePrio ) - { - active = m; - activePrio = prio; - - if ( activePrio <= 2 ) - return active; - } - } - } - - for ( int i = 0; i < aggressors.Count; ++i ) - { - AggressorInfo info = aggressors[i]; - Mobile m = info.Attacker; - - if ( m != comb && m.Combatant == m_Mobile && m_Mobile.InRange( m, 12 ) && CanDispel( m ) ) - { - double prio = m_Mobile.GetDistanceToSqrt( m ); - - if ( active == null || prio < activePrio ) - { - active = m; - activePrio = prio; - - if ( activePrio <= 2 ) - return active; - } - } - } - - return active; - } - - Map map = m_Mobile.Map; - - if ( map != null ) - { - Mobile active = null, inactive = null; - double actPrio = 0.0, inactPrio = 0.0; - - Mobile comb = m_Mobile.Combatant; - - if ( comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && CanDispel( comb ) ) - { - active = inactive = comb; - actPrio = inactPrio = m_Mobile.GetDistanceToSqrt( comb ); - } - - foreach ( Mobile m in m_Mobile.GetMobilesInRange( 12 ) ) - { - if ( m != m_Mobile && CanDispel( m ) ) - { - double prio = m_Mobile.GetDistanceToSqrt( m ); - - if ( !activeOnly && (inactive == null || prio < inactPrio) ) - { - inactive = m; - inactPrio = prio; - } - - if ( (m_Mobile.Combatant == m || m.Combatant == m_Mobile) && (active == null || prio < actPrio) ) - { - active = m; - actPrio = prio; - } - } - } - - return active ?? inactive; - } - - return null; - } - - public bool CanDispel( Mobile m ) - { - return ( m is BaseCreature creature && creature.Summoned && m_Mobile.CanBeHarmful( creature, false ) && !creature.IsAnimatedDead ); - } - - public void RunTo( Mobile m ) - { - /*if ( m.Paralyzed || m.Frozen ) - { - if ( m_Mobile.InRange( m, 1 ) ) - RunFrom( m ); - else if ( !m_Mobile.InRange( m, m_Mobile.RangeFight > 2 ? m_Mobile.RangeFight : 2 ) && !MoveTo( m, true, 1 ) ) - OnFailedMove(); - } - else - {*/ - if ( !m_Mobile.InRange( m, m_Mobile.RangeFight ) ) - { - if ( !MoveTo( m, true, 1 ) ) - OnFailedMove(); - } - else if ( m_Mobile.InRange( m, m_Mobile.RangeFight - 1 ) ) - { - RunFrom( m ); - } - /*}*/ - } - - public void RunFrom( Mobile m ) - { - Run( (m_Mobile.GetDirectionTo( m ) - 4) & Direction.Mask ); - } - - public void OnFailedMove() - { - /*if ( !m_Mobile.DisallowAllMoves && 20 > Utility.Random( 100 ) && IsAllowed( GuardAI.Magic ) ) - { - if ( m_Mobile.Target != null ) - m_Mobile.Target.Cancel( m_Mobile, TargetCancelType.Canceled ); - - new TeleportSpell( m_Mobile, null ).Cast(); - - m_Mobile.DebugSay( "I am stuck, I'm going to try teleporting away" ); - } - else*/ if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "My move is blocked, so I am going to attack {0}", m_Mobile.FocusMob.Name ); - - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - m_Mobile.DebugSay( "I am stuck" ); - } - } - - public void Run( Direction d ) - { - if ( (m_Mobile.Spell != null && m_Mobile.Spell.IsCasting) || m_Mobile.Paralyzed || m_Mobile.Frozen || m_Mobile.DisallowAllMoves ) - return; - - m_Mobile.Direction = d | Direction.Running; - - if ( !DoMove( m_Mobile.Direction, true ) ) - OnFailedMove(); - } - - public FactionGuardAI( BaseFactionGuard guard ) : base( guard ) - { - m_Guard = guard; - } - - public override bool Think() - { - if ( m_Mobile.Deleted ) - return false; - - Mobile combatant = m_Guard.Combatant; - - if ( combatant == null || combatant.Deleted || !combatant.Alive || combatant.IsDeadBondedPet || !m_Mobile.CanSee( combatant ) || !m_Mobile.CanBeHarmful( combatant, false ) || combatant.Map != m_Mobile.Map ) - { - // Our combatant is deleted, dead, hidden, or we cannot hurt them - // Try to find another combatant - - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.Combatant = combatant = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - else - { - m_Mobile.Combatant = combatant = null; - } - } - - if ( combatant != null && (!m_Mobile.InLOS( combatant ) || !m_Mobile.InRange( combatant, 12 )) ) - { - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.Combatant = combatant = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - else if ( !m_Mobile.InRange( combatant, 36 ) ) - { - m_Mobile.Combatant = combatant = null; - } - } - - Mobile dispelTarget = FindDispelTarget( true ); - - if ( m_Guard.Target != null && m_ReleaseTarget == DateTime.MinValue ) - m_ReleaseTarget = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 ); - - if ( m_Guard.Target != null && DateTime.UtcNow > m_ReleaseTarget ) - { - Target targ = m_Guard.Target; - - Mobile toHarm = dispelTarget ?? combatant; - - if ( (targ.Flags & TargetFlags.Harmful) != 0 && toHarm != null ) - { - if ( m_Guard.Map == toHarm.Map && ( targ.Range < 0 || m_Guard.InRange( toHarm, targ.Range ) ) && m_Guard.CanSee( toHarm ) && m_Guard.InLOS( toHarm ) ) - targ.Invoke( m_Guard, toHarm ); - else if ( targ is DispelSpell.InternalTarget ) - targ.Cancel( m_Guard, TargetCancelType.Canceled ); - } - else if ( (targ.Flags & TargetFlags.Beneficial) != 0 ) - { - targ.Invoke( m_Guard, m_Guard ); - } - else - { - targ.Cancel( m_Guard, TargetCancelType.Canceled ); - } - - m_ReleaseTarget = DateTime.MinValue; - } - - if ( dispelTarget != null ) - { - if ( Action != ActionType.Combat ) - Action = ActionType.Combat; - - m_Guard.Warmode = true; - - RunFrom( dispelTarget ); - } - else if ( combatant != null ) - { - if ( Action != ActionType.Combat ) - Action = ActionType.Combat; - - m_Guard.Warmode = true; - - RunTo( combatant ); - } - else if ( m_Guard.Orders.Movement != MovementType.Stand ) - { - Mobile toFollow = null; - - if ( m_Guard.Town != null && m_Guard.Orders.Movement == MovementType.Follow ) - { - toFollow = m_Guard.Orders.Follow; - - if ( toFollow == null ) - toFollow = m_Guard.Town.Sheriff; - } - - if ( toFollow != null && toFollow.Map == m_Guard.Map && toFollow.InRange( m_Guard, m_Guard.RangePerception * 3 ) && Town.FromRegion( toFollow.Region ) == m_Guard.Town ) - { - if ( Action != ActionType.Combat ) - Action = ActionType.Combat; - - if ( m_Mobile.CurrentSpeed != m_Mobile.ActiveSpeed ) - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - - m_Guard.Warmode = true; - - RunTo( toFollow ); - } - else - { - if ( Action != ActionType.Wander ) - Action = ActionType.Wander; - - if ( m_Mobile.CurrentSpeed != m_Mobile.PassiveSpeed ) - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - - m_Guard.Warmode = false; - - WalkRandomInHome( 2, 2, 1 ); - } - } - else - { - if ( Action != ActionType.Wander ) - Action = ActionType.Wander; - - m_Guard.Warmode = false; - } - - if ( (IsDamaged || IsPoisoned) && m_Guard.Skills.Healing.Base > 20.0 ) - { - TimeSpan ts = TimeUntilBandage; - - if ( ts == TimeSpan.MaxValue ) - StartBandage(); - } - - Spell spell = m_Mobile.Spell as Spell; - - if ( spell == null && Core.TickCount - m_Mobile.NextSpellTime >= 0 ) - { - DateTime toRelease = DateTime.MinValue; - - if ( IsPoisoned ) - { - Poison p = m_Guard.Poison; - - TimeSpan ts = TimeUntilBandage; - - if ( p != Poison.Lesser || ts == TimeSpan.MaxValue || TimeUntilBandage < TimeSpan.FromSeconds( 1.5 ) || (m_Guard.HitsMax - m_Guard.Hits) > Utility.Random( 250 ) ) - { - if ( IsAllowed( GuardAI.Bless ) ) - spell = new CureSpell( m_Guard, null ); - else - UseItemByType( typeof( BaseCurePotion ) ); - } - } - else if ( IsDamaged && (m_Guard.HitsMax - m_Guard.Hits) > Utility.Random( 200 ) ) - { - if ( IsAllowed( GuardAI.Magic ) && ((m_Guard.Hits * 100) / Math.Max( m_Guard.HitsMax, 1 )) < 10 && m_Guard.Home != Point3D.Zero && !Utility.InRange( m_Guard.Location, m_Guard.Home, 15 ) && m_Guard.Mana >= 11 ) - { - spell = new RecallSpell( m_Guard, null, new RunebookEntry( m_Guard.Home, m_Guard.Map, "Guard's Home", null ), null ); - } - else if ( IsAllowed( GuardAI.Bless ) ) - { - if ( m_Guard.Mana >= 11 && (m_Guard.Hits + 30) < m_Guard.HitsMax ) - spell = new GreaterHealSpell( m_Guard, null ); - else if ( (m_Guard.Hits + 10) < m_Guard.HitsMax && (m_Guard.Mana < 11 || (m_Guard.NextCombatTime - Core.TickCount) > 2000) ) - spell = new HealSpell( m_Guard, null ); - } - else if ( m_Guard.CanBeginAction( typeof( BaseHealPotion ) ) ) - { - UseItemByType( typeof( BaseHealPotion ) ); - } - } - else if ( dispelTarget != null && (IsAllowed( GuardAI.Magic ) || IsAllowed( GuardAI.Bless ) || IsAllowed( GuardAI.Curse )) ) - { - if ( !dispelTarget.Paralyzed && m_Guard.Mana > (ManaReserve + 20) && 40 > Utility.Random( 100 ) ) - spell = new ParalyzeSpell( m_Guard, null ); - else - spell = new DispelSpell( m_Guard, null ); - } - - if ( combatant != null ) - { - if ( m_Combo != null ) - { - if ( spell == null ) - { - spell = SpellCombo.Process( m_Guard, combatant, ref m_Combo, ref m_ComboIndex, ref toRelease ); - } - else - { - m_Combo = null; - m_ComboIndex = -1; - } - } - else if ( 20 > Utility.Random( 100 ) && IsAllowed( GuardAI.Magic ) ) - { - if ( 80 > Utility.Random( 100 ) ) - { - m_Combo = ( IsAllowed( GuardAI.Smart ) ? SpellCombo.Simple : SpellCombo.Strong ); - m_ComboIndex = -1; - - if ( m_Guard.Mana >= (ManaReserve + m_Combo.Mana) ) - spell = SpellCombo.Process( m_Guard, combatant, ref m_Combo, ref m_ComboIndex, ref toRelease ); - else - { - m_Combo = null; - - if ( m_Guard.Mana >= (ManaReserve + 40) ) - spell = RandomOffenseSpell(); - } - } - else if ( m_Guard.Mana >= (ManaReserve + 40) ) - { - spell = RandomOffenseSpell(); - } - } - - if ( spell == null && 2 > Utility.Random( 100 ) && m_Guard.Mana >= (ManaReserve + 10) ) - { - int strMod = GetStatMod( m_Guard, StatType.Str ); - int dexMod = GetStatMod( m_Guard, StatType.Dex ); - int intMod = GetStatMod( m_Guard, StatType.Int ); - - List types = new List(); - - if ( strMod <= 0 ) - types.Add( typeof( StrengthSpell ) ); - - if ( dexMod <= 0 && IsAllowed( GuardAI.Melee ) ) - types.Add( typeof( AgilitySpell ) ); - - if ( intMod <= 0 && IsAllowed( GuardAI.Magic ) ) - types.Add( typeof( CunningSpell ) ); - - if ( IsAllowed( GuardAI.Bless ) ) - { - if ( types.Count > 1 ) - spell = new BlessSpell( m_Guard, null ); - else if ( types.Count == 1 ) - spell = Activator.CreateInstance( types[0], new object[]{ m_Guard, null } ) as Spell; - } - else if ( types.Count > 0 ) - { - if ( types[0] == typeof( StrengthSpell ) ) - UseItemByType( typeof( BaseStrengthPotion ) ); - else if ( types[0] == typeof( AgilitySpell ) ) - UseItemByType( typeof( BaseAgilityPotion ) ); - } - } - - if ( spell == null && 2 > Utility.Random( 100 ) && m_Guard.Mana >= (ManaReserve + 10) && IsAllowed( GuardAI.Curse ) ) - { - if ( !combatant.Poisoned && 40 > Utility.Random( 100 ) ) - { - spell = new PoisonSpell( m_Guard, null ); - } - else - { - int strMod = GetStatMod( combatant, StatType.Str ); - int dexMod = GetStatMod( combatant, StatType.Dex ); - int intMod = GetStatMod( combatant, StatType.Int ); - - List types = new List(); - - if ( strMod >= 0 ) - types.Add( typeof( WeakenSpell ) ); - - if ( dexMod >= 0 && IsAllowed( GuardAI.Melee ) ) - types.Add( typeof( ClumsySpell ) ); - - if ( intMod >= 0 && IsAllowed( GuardAI.Magic ) ) - types.Add( typeof( FeeblemindSpell ) ); - - if ( types.Count > 1 ) - spell = new CurseSpell( m_Guard, null ); - else if ( types.Count == 1 ) - spell = (Spell) Activator.CreateInstance( types[0], new object[]{ m_Guard, null } ); - } - } - } - - if ( spell != null && (m_Guard.HitsMax - m_Guard.Hits + 10) > Utility.Random( 100 ) ) - { - Type type = null; - - if ( spell is GreaterHealSpell ) - type = typeof( BaseHealPotion ); - else if ( spell is CureSpell ) - type = typeof( BaseCurePotion ); - else if ( spell is StrengthSpell ) - type = typeof( BaseStrengthPotion ); - else if ( spell is AgilitySpell ) - type = typeof( BaseAgilityPotion ); - - if ( type == typeof( BaseHealPotion ) && !m_Guard.CanBeginAction( type ) ) - type = null; - - if ( type != null && m_Guard.Target == null && UseItemByType( type ) ) - { - if ( spell is GreaterHealSpell ) - { - if ( (m_Guard.Hits + 30) > m_Guard.HitsMax && (m_Guard.Hits + 10) < m_Guard.HitsMax ) - spell = new HealSpell( m_Guard, null ); - } - else - { - spell = null; - } - } - } - else if ( spell == null && m_Guard.Stam < (m_Guard.StamMax / 3) && IsAllowed( GuardAI.Melee ) ) - { - UseItemByType( typeof( BaseRefreshPotion ) ); - } - - if ( spell == null || !spell.Cast() ) - EquipWeapon(); - } - else if ( spell?.State == SpellState.Sequencing ) - { - EquipWeapon(); - } - - return true; - } - } -} + switch (Utility.Random(maxCircle * 2)) + { + case 0: + case 1: return new MagicArrowSpell(m_Guard, null); + case 2: + case 3: return new HarmSpell(m_Guard, null); + case 4: + case 5: return new FireballSpell(m_Guard, null); + case 6: + case 7: return new LightningSpell(m_Guard, null); + case 8: return new MindBlastSpell(m_Guard, null); + case 9: return new ParalyzeSpell(m_Guard, null); + case 10: return new EnergyBoltSpell(m_Guard, null); + case 11: return new ExplosionSpell(m_Guard, null); + default: return new FlameStrikeSpell(m_Guard, null); + } + } + + public Mobile FindDispelTarget(bool activeOnly) + { + if (m_Mobile.Deleted || m_Mobile.Int < 95 || CanDispel(m_Mobile) || m_Mobile.AutoDispel) + return null; + + if (activeOnly) + { + List aggressed = m_Mobile.Aggressed; + List aggressors = m_Mobile.Aggressors; + + Mobile active = null; + double activePrio = 0.0; + + Mobile comb = m_Mobile.Combatant; + + if (comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && m_Mobile.InRange(comb, 12) && + CanDispel(comb)) + { + active = comb; + activePrio = m_Mobile.GetDistanceToSqrt(comb); + + if (activePrio <= 2) + return active; + } + + for (int i = 0; i < aggressed.Count; ++i) + { + AggressorInfo info = aggressed[i]; + Mobile m = info.Defender; + + if (m != comb && m.Combatant == m_Mobile && m_Mobile.InRange(m, 12) && CanDispel(m)) + { + double prio = m_Mobile.GetDistanceToSqrt(m); + + if (active == null || prio < activePrio) + { + active = m; + activePrio = prio; + + if (activePrio <= 2) + return active; + } + } + } + + for (int i = 0; i < aggressors.Count; ++i) + { + AggressorInfo info = aggressors[i]; + Mobile m = info.Attacker; + + if (m != comb && m.Combatant == m_Mobile && m_Mobile.InRange(m, 12) && CanDispel(m)) + { + double prio = m_Mobile.GetDistanceToSqrt(m); + + if (active == null || prio < activePrio) + { + active = m; + activePrio = prio; + + if (activePrio <= 2) + return active; + } + } + } + + return active; + } + + Map map = m_Mobile.Map; + + if (map != null) + { + Mobile active = null, inactive = null; + double actPrio = 0.0, inactPrio = 0.0; + + Mobile comb = m_Mobile.Combatant; + + if (comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && CanDispel(comb)) + { + active = inactive = comb; + actPrio = inactPrio = m_Mobile.GetDistanceToSqrt(comb); + } + + foreach (Mobile m in m_Mobile.GetMobilesInRange(12)) + if (m != m_Mobile && CanDispel(m)) + { + double prio = m_Mobile.GetDistanceToSqrt(m); + + if (!activeOnly && (inactive == null || prio < inactPrio)) + { + inactive = m; + inactPrio = prio; + } + + if ((m_Mobile.Combatant == m || m.Combatant == m_Mobile) && (active == null || prio < actPrio)) + { + active = m; + actPrio = prio; + } + } + + return active ?? inactive; + } + + return null; + } + + public bool CanDispel(Mobile m) + { + return m is BaseCreature creature && creature.Summoned && m_Mobile.CanBeHarmful(creature, false) && + !creature.IsAnimatedDead; + } + + public void RunTo(Mobile m) + { + /*if ( m.Paralyzed || m.Frozen ) + { + if ( m_Mobile.InRange( m, 1 ) ) + RunFrom( m ); + else if ( !m_Mobile.InRange( m, m_Mobile.RangeFight > 2 ? m_Mobile.RangeFight : 2 ) && !MoveTo( m, true, 1 ) ) + OnFailedMove(); + } + else + {*/ + if (!m_Mobile.InRange(m, m_Mobile.RangeFight)) + { + if (!MoveTo(m, true, 1)) + OnFailedMove(); + } + else if (m_Mobile.InRange(m, m_Mobile.RangeFight - 1)) + { + RunFrom(m); + } + + /*}*/ + } + + public void RunFrom(Mobile m) + { + Run((m_Mobile.GetDirectionTo(m) - 4) & Direction.Mask); + } + + public void OnFailedMove() + { + /*if ( !m_Mobile.DisallowAllMoves && 20 > Utility.Random( 100 ) && IsAllowed( GuardAI.Magic ) ) + { + if ( m_Mobile.Target != null ) + m_Mobile.Target.Cancel( m_Mobile, TargetCancelType.Canceled ); + + new TeleportSpell( m_Mobile, null ).Cast(); + + m_Mobile.DebugSay( "I am stuck, I'm going to try teleporting away" ); + } + else*/ + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("My move is blocked, so I am going to attack {0}", m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + m_Mobile.DebugSay("I am stuck"); + } + } + + public void Run(Direction d) + { + if (m_Mobile.Spell != null && m_Mobile.Spell.IsCasting || m_Mobile.Paralyzed || m_Mobile.Frozen || + m_Mobile.DisallowAllMoves) + return; + + m_Mobile.Direction = d | Direction.Running; + + if (!DoMove(m_Mobile.Direction, true)) + OnFailedMove(); + } + + public override bool Think() + { + if (m_Mobile.Deleted) + return false; + + Mobile combatant = m_Guard.Combatant; + + if (combatant == null || combatant.Deleted || !combatant.Alive || combatant.IsDeadBondedPet || + !m_Mobile.CanSee(combatant) || !m_Mobile.CanBeHarmful(combatant, false) || combatant.Map != m_Mobile.Map) + { + // Our combatant is deleted, dead, hidden, or we cannot hurt them + // Try to find another combatant + + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.Combatant = combatant = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + else + { + m_Mobile.Combatant = combatant = null; + } + } + + if (combatant != null && (!m_Mobile.InLOS(combatant) || !m_Mobile.InRange(combatant, 12))) + { + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.Combatant = combatant = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + else if (!m_Mobile.InRange(combatant, 36)) + { + m_Mobile.Combatant = combatant = null; + } + } + + Mobile dispelTarget = FindDispelTarget(true); + + if (m_Guard.Target != null && m_ReleaseTarget == DateTime.MinValue) + m_ReleaseTarget = DateTime.UtcNow + TimeSpan.FromSeconds(10.0); + + if (m_Guard.Target != null && DateTime.UtcNow > m_ReleaseTarget) + { + Target targ = m_Guard.Target; + + Mobile toHarm = dispelTarget ?? combatant; + + if ((targ.Flags & TargetFlags.Harmful) != 0 && toHarm != null) + { + if (m_Guard.Map == toHarm.Map && (targ.Range < 0 || m_Guard.InRange(toHarm, targ.Range)) && + m_Guard.CanSee(toHarm) && m_Guard.InLOS(toHarm)) + targ.Invoke(m_Guard, toHarm); + else if (targ is DispelSpell.InternalTarget) + targ.Cancel(m_Guard, TargetCancelType.Canceled); + } + else if ((targ.Flags & TargetFlags.Beneficial) != 0) + { + targ.Invoke(m_Guard, m_Guard); + } + else + { + targ.Cancel(m_Guard, TargetCancelType.Canceled); + } + + m_ReleaseTarget = DateTime.MinValue; + } + + if (dispelTarget != null) + { + if (Action != ActionType.Combat) + Action = ActionType.Combat; + + m_Guard.Warmode = true; + + RunFrom(dispelTarget); + } + else if (combatant != null) + { + if (Action != ActionType.Combat) + Action = ActionType.Combat; + + m_Guard.Warmode = true; + + RunTo(combatant); + } + else if (m_Guard.Orders.Movement != MovementType.Stand) + { + Mobile toFollow = null; + + if (m_Guard.Town != null && m_Guard.Orders.Movement == MovementType.Follow) + { + toFollow = m_Guard.Orders.Follow; + + if (toFollow == null) + toFollow = m_Guard.Town.Sheriff; + } + + if (toFollow != null && toFollow.Map == m_Guard.Map && + toFollow.InRange(m_Guard, m_Guard.RangePerception * 3) && + Town.FromRegion(toFollow.Region) == m_Guard.Town) + { + if (Action != ActionType.Combat) + Action = ActionType.Combat; + + if (m_Mobile.CurrentSpeed != m_Mobile.ActiveSpeed) + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + + m_Guard.Warmode = true; + + RunTo(toFollow); + } + else + { + if (Action != ActionType.Wander) + Action = ActionType.Wander; + + if (m_Mobile.CurrentSpeed != m_Mobile.PassiveSpeed) + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + + m_Guard.Warmode = false; + + WalkRandomInHome(2, 2, 1); + } + } + else + { + if (Action != ActionType.Wander) + Action = ActionType.Wander; + + m_Guard.Warmode = false; + } + + if ((IsDamaged || IsPoisoned) && m_Guard.Skills.Healing.Base > 20.0) + { + TimeSpan ts = TimeUntilBandage; + + if (ts == TimeSpan.MaxValue) + StartBandage(); + } + + Spell spell = m_Mobile.Spell as Spell; + + if (spell == null && Core.TickCount - m_Mobile.NextSpellTime >= 0) + { + DateTime toRelease = DateTime.MinValue; + + if (IsPoisoned) + { + Poison p = m_Guard.Poison; + + TimeSpan ts = TimeUntilBandage; + + if (p != Poison.Lesser || ts == TimeSpan.MaxValue || TimeUntilBandage < TimeSpan.FromSeconds(1.5) || + m_Guard.HitsMax - m_Guard.Hits > Utility.Random(250)) + { + if (IsAllowed(GuardAI.Bless)) + spell = new CureSpell(m_Guard, null); + else + UseItemByType(typeof(BaseCurePotion)); + } + } + else if (IsDamaged && m_Guard.HitsMax - m_Guard.Hits > Utility.Random(200)) + { + if (IsAllowed(GuardAI.Magic) && m_Guard.Hits * 100 / Math.Max(m_Guard.HitsMax, 1) < 10 && + m_Guard.Home != Point3D.Zero && !Utility.InRange(m_Guard.Location, m_Guard.Home, 15) && + m_Guard.Mana >= 11) + { + spell = new RecallSpell(m_Guard, null, + new RunebookEntry(m_Guard.Home, m_Guard.Map, "Guard's Home", null), null); + } + else if (IsAllowed(GuardAI.Bless)) + { + if (m_Guard.Mana >= 11 && m_Guard.Hits + 30 < m_Guard.HitsMax) + spell = new GreaterHealSpell(m_Guard, null); + else if (m_Guard.Hits + 10 < m_Guard.HitsMax && + (m_Guard.Mana < 11 || m_Guard.NextCombatTime - Core.TickCount > 2000)) + spell = new HealSpell(m_Guard, null); + } + else if (m_Guard.CanBeginAction(typeof(BaseHealPotion))) + { + UseItemByType(typeof(BaseHealPotion)); + } + } + else if (dispelTarget != null && + (IsAllowed(GuardAI.Magic) || IsAllowed(GuardAI.Bless) || IsAllowed(GuardAI.Curse))) + { + if (!dispelTarget.Paralyzed && m_Guard.Mana > ManaReserve + 20 && 40 > Utility.Random(100)) + spell = new ParalyzeSpell(m_Guard, null); + else + spell = new DispelSpell(m_Guard, null); + } + + if (combatant != null) + { + if (m_Combo != null) + { + if (spell == null) + { + spell = SpellCombo.Process(m_Guard, combatant, ref m_Combo, ref m_ComboIndex, ref toRelease); + } + else + { + m_Combo = null; + m_ComboIndex = -1; + } + } + else if (20 > Utility.Random(100) && IsAllowed(GuardAI.Magic)) + { + if (80 > Utility.Random(100)) + { + m_Combo = IsAllowed(GuardAI.Smart) ? SpellCombo.Simple : SpellCombo.Strong; + m_ComboIndex = -1; + + if (m_Guard.Mana >= ManaReserve + m_Combo.Mana) + { + spell = SpellCombo.Process(m_Guard, combatant, ref m_Combo, ref m_ComboIndex, ref toRelease); + } + else + { + m_Combo = null; + + if (m_Guard.Mana >= ManaReserve + 40) + spell = RandomOffenseSpell(); + } + } + else if (m_Guard.Mana >= ManaReserve + 40) + { + spell = RandomOffenseSpell(); + } + } + + if (spell == null && 2 > Utility.Random(100) && m_Guard.Mana >= ManaReserve + 10) + { + int strMod = GetStatMod(m_Guard, StatType.Str); + int dexMod = GetStatMod(m_Guard, StatType.Dex); + int intMod = GetStatMod(m_Guard, StatType.Int); + + List types = new List(); + + if (strMod <= 0) + types.Add(typeof(StrengthSpell)); + + if (dexMod <= 0 && IsAllowed(GuardAI.Melee)) + types.Add(typeof(AgilitySpell)); + + if (intMod <= 0 && IsAllowed(GuardAI.Magic)) + types.Add(typeof(CunningSpell)); + + if (IsAllowed(GuardAI.Bless)) + { + if (types.Count > 1) + spell = new BlessSpell(m_Guard, null); + else if (types.Count == 1) + spell = Activator.CreateInstance(types[0], m_Guard, null) as Spell; + } + else if (types.Count > 0) + { + if (types[0] == typeof(StrengthSpell)) + UseItemByType(typeof(BaseStrengthPotion)); + else if (types[0] == typeof(AgilitySpell)) + UseItemByType(typeof(BaseAgilityPotion)); + } + } + + if (spell == null && 2 > Utility.Random(100) && m_Guard.Mana >= ManaReserve + 10 && + IsAllowed(GuardAI.Curse)) + { + if (!combatant.Poisoned && 40 > Utility.Random(100)) + { + spell = new PoisonSpell(m_Guard, null); + } + else + { + int strMod = GetStatMod(combatant, StatType.Str); + int dexMod = GetStatMod(combatant, StatType.Dex); + int intMod = GetStatMod(combatant, StatType.Int); + + List types = new List(); + + if (strMod >= 0) + types.Add(typeof(WeakenSpell)); + + if (dexMod >= 0 && IsAllowed(GuardAI.Melee)) + types.Add(typeof(ClumsySpell)); + + if (intMod >= 0 && IsAllowed(GuardAI.Magic)) + types.Add(typeof(FeeblemindSpell)); + + if (types.Count > 1) + spell = new CurseSpell(m_Guard, null); + else if (types.Count == 1) + spell = (Spell)Activator.CreateInstance(types[0], m_Guard, null); + } + } + } + + if (spell != null && m_Guard.HitsMax - m_Guard.Hits + 10 > Utility.Random(100)) + { + Type type = null; + + if (spell is GreaterHealSpell) + type = typeof(BaseHealPotion); + else if (spell is CureSpell) + type = typeof(BaseCurePotion); + else if (spell is StrengthSpell) + type = typeof(BaseStrengthPotion); + else if (spell is AgilitySpell) + type = typeof(BaseAgilityPotion); + + if (type == typeof(BaseHealPotion) && !m_Guard.CanBeginAction(type)) + type = null; + + if (type != null && m_Guard.Target == null && UseItemByType(type)) + { + if (spell is GreaterHealSpell) + { + if (m_Guard.Hits + 30 > m_Guard.HitsMax && m_Guard.Hits + 10 < m_Guard.HitsMax) + spell = new HealSpell(m_Guard, null); + } + else + { + spell = null; + } + } + } + else if (spell == null && m_Guard.Stam < m_Guard.StamMax / 3 && IsAllowed(GuardAI.Melee)) + { + UseItemByType(typeof(BaseRefreshPotion)); + } + + if (spell == null || !spell.Cast()) + EquipWeapon(); + } + else if (spell?.State == SpellState.Sequencing) + { + EquipWeapon(); + } + + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Orders.cs b/Scripts/Engines/Factions/Mobiles/Guards/Orders.cs index 28ba65ce9..7320d5396 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Orders.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Orders.cs @@ -2,139 +2,140 @@ using System.Collections.Generic; namespace Server.Factions.AI { - public enum ReactionType - { - Ignore, - Warn, - Attack - } + public enum ReactionType + { + Ignore, + Warn, + Attack + } - public enum MovementType - { - Stand, - Patrol, - Follow - } + public enum MovementType + { + Stand, + Patrol, + Follow + } - public class Reaction - { - public Faction Faction { get; } + public class Reaction + { + public Reaction(Faction faction, ReactionType type) + { + Faction = faction; + Type = type; + } - public ReactionType Type { get; set; } + public Reaction(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public Reaction( Faction faction, ReactionType type ) - { - Faction = faction; - Type = type; - } + switch (version) + { + case 0: + { + Faction = Faction.ReadReference(reader); + Type = (ReactionType)reader.ReadEncodedInt(); - public Reaction( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + break; + } + } + } - switch ( version ) - { - case 0: - { - Faction = Faction.ReadReference( reader ); - Type = (ReactionType) reader.ReadEncodedInt(); + public Faction Faction{ get; } - break; - } - } - } + public ReactionType Type{ get; set; } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - Faction.WriteReference( writer, Faction ); - writer.WriteEncodedInt( (int) Type ); - } - } + Faction.WriteReference(writer, Faction); + writer.WriteEncodedInt((int)Type); + } + } - public class Orders - { - private List m_Reactions; + public class Orders + { + private List m_Reactions; - public BaseFactionGuard Guard { get; } + public Orders(BaseFactionGuard guard) + { + Guard = guard; + m_Reactions = new List(); + Movement = MovementType.Patrol; + } - public MovementType Movement { get; set; } + public Orders(BaseFactionGuard guard, GenericReader reader) + { + Guard = guard; - public Mobile Follow { get; set; } + int version = reader.ReadEncodedInt(); - public Reaction GetReaction( Faction faction ) - { - Reaction reaction; + switch (version) + { + case 1: + { + Follow = reader.ReadMobile(); + goto case 0; + } + case 0: + { + int count = reader.ReadEncodedInt(); + m_Reactions = new List(count); - for ( int i = 0; i < m_Reactions.Count; ++i ) - { - reaction = m_Reactions[i]; + for (int i = 0; i < count; ++i) + m_Reactions.Add(new Reaction(reader)); - if ( reaction.Faction == faction ) - return reaction; - } + Movement = (MovementType)reader.ReadEncodedInt(); - reaction = new Reaction( faction, ( faction == null || faction == Guard.Faction ) ? ReactionType.Ignore : ReactionType.Attack ); - m_Reactions.Add( reaction ); + break; + } + } + } - return reaction; - } + public BaseFactionGuard Guard{ get; } - public void SetReaction( Faction faction, ReactionType type ) - { - Reaction reaction = GetReaction( faction ); + public MovementType Movement{ get; set; } - reaction.Type = type; - } + public Mobile Follow{ get; set; } - public Orders( BaseFactionGuard guard ) - { - Guard = guard; - m_Reactions = new List(); - Movement = MovementType.Patrol; - } + public Reaction GetReaction(Faction faction) + { + Reaction reaction; - public Orders( BaseFactionGuard guard, GenericReader reader ) - { - Guard = guard; + for (int i = 0; i < m_Reactions.Count; ++i) + { + reaction = m_Reactions[i]; - int version = reader.ReadEncodedInt(); + if (reaction.Faction == faction) + return reaction; + } - switch ( version ) - { - case 1: - { - Follow = reader.ReadMobile(); - goto case 0; - } - case 0: - { - int count = reader.ReadEncodedInt(); - m_Reactions = new List( count ); + reaction = new Reaction(faction, + faction == null || faction == Guard.Faction ? ReactionType.Ignore : ReactionType.Attack); + m_Reactions.Add(reaction); - for ( int i = 0; i < count; ++i ) - m_Reactions.Add( new Reaction( reader ) ); + return reaction; + } - Movement = (MovementType)reader.ReadEncodedInt(); + public void SetReaction(Faction faction, ReactionType type) + { + Reaction reaction = GetReaction(faction); - break; - } - } - } + reaction.Type = type; + } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 1 ); // version + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(1); // version - writer.Write( (Mobile) Follow ); + writer.Write(Follow); - writer.WriteEncodedInt( (int) m_Reactions.Count ); + writer.WriteEncodedInt(m_Reactions.Count); - for ( int i = 0; i < m_Reactions.Count; ++i ) - m_Reactions[i].Serialize( writer ); + for (int i = 0; i < m_Reactions.Count; ++i) + m_Reactions[i].Serialize(writer); - writer.WriteEncodedInt( (int) Movement ); - } - } + writer.WriteEncodedInt((int)Movement); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionBerserker.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionBerserker.cs index c0b54afab..0a1046568 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionBerserker.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionBerserker.cs @@ -2,71 +2,71 @@ using Server.Items; namespace Server.Factions { - public class FactionBerserker : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Melee | GuardAI.Curse | GuardAI.Bless; + public class FactionBerserker : BaseFactionGuard + { + [Constructible] + public FactionBerserker() : base("the berserker") + { + GenerateBody(false, false); - [Constructible] - public FactionBerserker() : base( "the berserker" ) - { - GenerateBody( false, false ); + SetStr(126, 150); + SetDex(61, 85); + SetInt(81, 95); - SetStr( 126, 150 ); - SetDex( 61, 85 ); - SetInt( 81, 95 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 50); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 30, 50); + SetResistance(ResistanceType.Energy, 30, 50); + SetResistance(ResistanceType.Poison, 30, 50); - SetResistance( ResistanceType.Physical, 30, 50 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 30, 50 ); - SetResistance( ResistanceType.Energy, 30, 50 ); - SetResistance( ResistanceType.Poison, 30, 50 ); + VirtualArmor = 24; - VirtualArmor = 24; + SetSkill(SkillName.Swords, 100.0, 110.0); + SetSkill(SkillName.Wrestling, 100.0, 110.0); + SetSkill(SkillName.Tactics, 100.0, 110.0); + SetSkill(SkillName.MagicResist, 100.0, 110.0); + SetSkill(SkillName.Healing, 100.0, 110.0); + SetSkill(SkillName.Anatomy, 100.0, 110.0); - SetSkill( SkillName.Swords, 100.0, 110.0 ); - SetSkill( SkillName.Wrestling, 100.0, 110.0 ); - SetSkill( SkillName.Tactics, 100.0, 110.0 ); - SetSkill( SkillName.MagicResist, 100.0, 110.0 ); - SetSkill( SkillName.Healing, 100.0, 110.0 ); - SetSkill( SkillName.Anatomy, 100.0, 110.0 ); + SetSkill(SkillName.Magery, 100.0, 110.0); + SetSkill(SkillName.EvalInt, 100.0, 110.0); + SetSkill(SkillName.Meditation, 100.0, 110.0); - SetSkill( SkillName.Magery, 100.0, 110.0 ); - SetSkill( SkillName.EvalInt, 100.0, 110.0 ); - SetSkill( SkillName.Meditation, 100.0, 110.0 ); + AddItem(Immovable(Rehued(new BodySash(), 1645))); + AddItem(Immovable(Rehued(new Kilt(), 1645))); + AddItem(Immovable(Rehued(new Sandals(), 1645))); + AddItem(Newbied(new DoubleAxe())); - AddItem( Immovable( Rehued( new BodySash(), 1645 ) ) ); - AddItem( Immovable( Rehued( new Kilt(), 1645 ) ) ); - AddItem( Immovable( Rehued( new Sandals(), 1645 ) ) ); - AddItem( Newbied( new DoubleAxe() ) ); + HairItemID = 0x2047; // Afro + HairHue = 0x29; - HairItemID = 0x2047; // Afro - HairHue = 0x29; + FacialHairItemID = 0x204B; // Medium Short Beard + FacialHairHue = 0x29; - FacialHairItemID = 0x204B; // Medium Short Beard - FacialHairHue = 0x29; + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionBerserker(Serial serial) : base(serial) + { + } - public FactionBerserker( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Melee | GuardAI.Curse | GuardAI.Bless; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDeathKnight.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDeathKnight.cs index aabf3bc28..1cf8a11ad 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDeathKnight.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDeathKnight.cs @@ -2,67 +2,67 @@ using Server.Items; namespace Server.Factions { - public class FactionDeathKnight : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Melee | GuardAI.Curse | GuardAI.Bless; + public class FactionDeathKnight : BaseFactionGuard + { + [Constructible] + public FactionDeathKnight() : base("the death knight") + { + GenerateBody(false, false); + Hue = 1; - [Constructible] - public FactionDeathKnight() : base( "the death knight" ) - { - GenerateBody( false, false ); - Hue = 1; + SetStr(126, 150); + SetDex(61, 85); + SetInt(81, 95); - SetStr( 126, 150 ); - SetDex( 61, 85 ); - SetInt( 81, 95 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 50); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 30, 50); + SetResistance(ResistanceType.Energy, 30, 50); + SetResistance(ResistanceType.Poison, 30, 50); - SetResistance( ResistanceType.Physical, 30, 50 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 30, 50 ); - SetResistance( ResistanceType.Energy, 30, 50 ); - SetResistance( ResistanceType.Poison, 30, 50 ); + VirtualArmor = 24; - VirtualArmor = 24; + SetSkill(SkillName.Swords, 100.0, 110.0); + SetSkill(SkillName.Wrestling, 100.0, 110.0); + SetSkill(SkillName.Tactics, 100.0, 110.0); + SetSkill(SkillName.MagicResist, 100.0, 110.0); + SetSkill(SkillName.Healing, 100.0, 110.0); + SetSkill(SkillName.Anatomy, 100.0, 110.0); - SetSkill( SkillName.Swords, 100.0, 110.0 ); - SetSkill( SkillName.Wrestling, 100.0, 110.0 ); - SetSkill( SkillName.Tactics, 100.0, 110.0 ); - SetSkill( SkillName.MagicResist, 100.0, 110.0 ); - SetSkill( SkillName.Healing, 100.0, 110.0 ); - SetSkill( SkillName.Anatomy, 100.0, 110.0 ); + SetSkill(SkillName.Magery, 100.0, 110.0); + SetSkill(SkillName.EvalInt, 100.0, 110.0); + SetSkill(SkillName.Meditation, 100.0, 110.0); - SetSkill( SkillName.Magery, 100.0, 110.0 ); - SetSkill( SkillName.EvalInt, 100.0, 110.0 ); - SetSkill( SkillName.Meditation, 100.0, 110.0 ); + Item shroud = new Item(0x204E); + shroud.Layer = Layer.OuterTorso; - Item shroud = new Item( 0x204E ); - shroud.Layer = Layer.OuterTorso; + AddItem(Immovable(Rehued(shroud, 1109))); + AddItem(Newbied(Rehued(new ExecutionersAxe(), 2211))); - AddItem( Immovable( Rehued( shroud, 1109 ) ) ); - AddItem( Newbied( Rehued( new ExecutionersAxe(), 2211 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionDeathKnight(Serial serial) : base(serial) + { + } - public FactionDeathKnight( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Melee | GuardAI.Curse | GuardAI.Bless; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDragoon.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDragoon.cs index c3ca49d9d..b45f29219 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDragoon.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionDragoon.cs @@ -2,71 +2,71 @@ using Server.Items; namespace Server.Factions { - public class FactionDragoon : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Melee | GuardAI.Smart | GuardAI.Bless | GuardAI.Curse; + public class FactionDragoon : BaseFactionGuard + { + [Constructible] + public FactionDragoon() : base("the dragoon") + { + GenerateBody(false, false); - [Constructible] - public FactionDragoon() : base( "the dragoon" ) - { - GenerateBody( false, false ); + SetStr(151, 175); + SetDex(61, 85); + SetInt(151, 175); - SetStr( 151, 175 ); - SetDex( 61, 85 ); - SetInt( 151, 175 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Energy, 40, 60); + SetResistance(ResistanceType.Poison, 40, 60); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Energy, 40, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); + VirtualArmor = 32; - VirtualArmor = 32; + SetSkill(SkillName.Macing, 110.0, 120.0); + SetSkill(SkillName.Wrestling, 110.0, 120.0); + SetSkill(SkillName.Tactics, 110.0, 120.0); + SetSkill(SkillName.MagicResist, 110.0, 120.0); + SetSkill(SkillName.Healing, 110.0, 120.0); + SetSkill(SkillName.Anatomy, 110.0, 120.0); - SetSkill( SkillName.Macing, 110.0, 120.0 ); - SetSkill( SkillName.Wrestling, 110.0, 120.0 ); - SetSkill( SkillName.Tactics, 110.0, 120.0 ); - SetSkill( SkillName.MagicResist, 110.0, 120.0 ); - SetSkill( SkillName.Healing, 110.0, 120.0 ); - SetSkill( SkillName.Anatomy, 110.0, 120.0 ); + SetSkill(SkillName.Magery, 110.0, 120.0); + SetSkill(SkillName.EvalInt, 110.0, 120.0); + SetSkill(SkillName.Meditation, 110.0, 120.0); - SetSkill( SkillName.Magery, 110.0, 120.0 ); - SetSkill( SkillName.EvalInt, 110.0, 120.0 ); - SetSkill( SkillName.Meditation, 110.0, 120.0 ); + AddItem(Immovable(Rehued(new Cloak(), 1645))); - AddItem( Immovable( Rehued( new Cloak(), 1645 ) ) ); + AddItem(Immovable(Rehued(new PlateChest(), 1645))); + AddItem(Immovable(Rehued(new PlateLegs(), 1109))); + AddItem(Immovable(Rehued(new PlateArms(), 1109))); + AddItem(Immovable(Rehued(new PlateGloves(), 1109))); + AddItem(Immovable(Rehued(new PlateGorget(), 1109))); + AddItem(Immovable(Rehued(new PlateHelm(), 1109))); - AddItem( Immovable( Rehued( new PlateChest(), 1645 ) ) ); - AddItem( Immovable( Rehued( new PlateLegs(), 1109 ) ) ); - AddItem( Immovable( Rehued( new PlateArms(), 1109 ) ) ); - AddItem( Immovable( Rehued( new PlateGloves(), 1109 ) ) ); - AddItem( Immovable( Rehued( new PlateGorget(), 1109 ) ) ); - AddItem( Immovable( Rehued( new PlateHelm(), 1109 ) ) ); + AddItem(Newbied(new WarHammer())); - AddItem( Newbied( new WarHammer() ) ); + AddItem(Immovable(Rehued(new VirtualMountItem(this), 1109))); - AddItem( Immovable( Rehued( new VirtualMountItem( this ), 1109 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionDragoon(Serial serial) : base(serial) + { + } - public FactionDragoon( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Melee | GuardAI.Smart | GuardAI.Bless | GuardAI.Curse; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionHenchman.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionHenchman.cs index 57db832c3..44d405378 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionHenchman.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionHenchman.cs @@ -2,64 +2,64 @@ using Server.Items; namespace Server.Factions { - public class FactionHenchman : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Melee; + public class FactionHenchman : BaseFactionGuard + { + [Constructible] + public FactionHenchman() : base("the henchman") + { + GenerateBody(false, true); - [Constructible] - public FactionHenchman() : base( "the henchman" ) - { - GenerateBody( false, true ); + SetStr(91, 115); + SetDex(61, 85); + SetInt(81, 95); - SetStr( 91, 115 ); - SetDex( 61, 85 ); - SetInt( 81, 95 ); + SetDamage(10, 14); - SetDamage( 10, 14 ); + SetResistance(ResistanceType.Physical, 10, 30); + SetResistance(ResistanceType.Fire, 10, 30); + SetResistance(ResistanceType.Cold, 10, 30); + SetResistance(ResistanceType.Energy, 10, 30); + SetResistance(ResistanceType.Poison, 10, 30); - SetResistance( ResistanceType.Physical, 10, 30 ); - SetResistance( ResistanceType.Fire, 10, 30 ); - SetResistance( ResistanceType.Cold, 10, 30 ); - SetResistance( ResistanceType.Energy, 10, 30 ); - SetResistance( ResistanceType.Poison, 10, 30 ); + VirtualArmor = 8; - VirtualArmor = 8; + SetSkill(SkillName.Fencing, 80.0, 90.0); + SetSkill(SkillName.Wrestling, 80.0, 90.0); + SetSkill(SkillName.Tactics, 80.0, 90.0); + SetSkill(SkillName.MagicResist, 80.0, 90.0); + SetSkill(SkillName.Healing, 80.0, 90.0); + SetSkill(SkillName.Anatomy, 80.0, 90.0); - SetSkill( SkillName.Fencing, 80.0, 90.0 ); - SetSkill( SkillName.Wrestling, 80.0, 90.0 ); - SetSkill( SkillName.Tactics, 80.0, 90.0 ); - SetSkill( SkillName.MagicResist, 80.0, 90.0 ); - SetSkill( SkillName.Healing, 80.0, 90.0 ); - SetSkill( SkillName.Anatomy, 80.0, 90.0 ); + AddItem(new StuddedChest()); + AddItem(new StuddedLegs()); + AddItem(new StuddedArms()); + AddItem(new StuddedGloves()); + AddItem(new StuddedGorget()); + AddItem(new Boots()); + AddItem(Newbied(new Spear())); - AddItem( new StuddedChest() ); - AddItem( new StuddedLegs() ); - AddItem( new StuddedArms() ); - AddItem( new StuddedGloves() ); - AddItem( new StuddedGorget() ); - AddItem( new Boots() ); - AddItem( Newbied( new Spear() ) ); + PackItem(new Bandage(Utility.RandomMinMax(10, 20))); + PackWeakPotions(1, 4); + } - PackItem( new Bandage( Utility.RandomMinMax( 10, 20 ) ) ); - PackWeakPotions( 1, 4 ); - } + public FactionHenchman(Serial serial) : base(serial) + { + } - public FactionHenchman( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Melee; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionKnight.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionKnight.cs index 074e1ef7e..0cdae6bfe 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionKnight.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionKnight.cs @@ -2,72 +2,72 @@ using Server.Items; namespace Server.Factions { - public class FactionKnight : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Melee | GuardAI.Smart | GuardAI.Curse | GuardAI.Bless; + public class FactionKnight : BaseFactionGuard + { + [Constructible] + public FactionKnight() : base("the knight") + { + GenerateBody(false, false); - [Constructible] - public FactionKnight() : base( "the knight" ) - { - GenerateBody( false, false ); + SetStr(126, 150); + SetDex(61, 85); + SetInt(81, 95); - SetStr( 126, 150 ); - SetDex( 61, 85 ); - SetInt( 81, 95 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 50); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 30, 50); + SetResistance(ResistanceType.Energy, 30, 50); + SetResistance(ResistanceType.Poison, 30, 50); - SetResistance( ResistanceType.Physical, 30, 50 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 30, 50 ); - SetResistance( ResistanceType.Energy, 30, 50 ); - SetResistance( ResistanceType.Poison, 30, 50 ); + VirtualArmor = 24; - VirtualArmor = 24; + SetSkill(SkillName.Swords, 100.0, 110.0); + SetSkill(SkillName.Wrestling, 100.0, 110.0); + SetSkill(SkillName.Tactics, 100.0, 110.0); + SetSkill(SkillName.MagicResist, 100.0, 110.0); + SetSkill(SkillName.Healing, 100.0, 110.0); + SetSkill(SkillName.Anatomy, 100.0, 110.0); - SetSkill( SkillName.Swords, 100.0, 110.0 ); - SetSkill( SkillName.Wrestling, 100.0, 110.0 ); - SetSkill( SkillName.Tactics, 100.0, 110.0 ); - SetSkill( SkillName.MagicResist, 100.0, 110.0 ); - SetSkill( SkillName.Healing, 100.0, 110.0 ); - SetSkill( SkillName.Anatomy, 100.0, 110.0 ); + SetSkill(SkillName.Magery, 100.0, 110.0); + SetSkill(SkillName.EvalInt, 100.0, 110.0); + SetSkill(SkillName.Meditation, 100.0, 110.0); - SetSkill( SkillName.Magery, 100.0, 110.0 ); - SetSkill( SkillName.EvalInt, 100.0, 110.0 ); - SetSkill( SkillName.Meditation, 100.0, 110.0 ); + AddItem(Immovable(Rehued(new ChainChest(), 2125))); + AddItem(Immovable(Rehued(new ChainLegs(), 2125))); + AddItem(Immovable(Rehued(new ChainCoif(), 2125))); + AddItem(Immovable(Rehued(new PlateArms(), 2125))); + AddItem(Immovable(Rehued(new PlateGloves(), 2125))); - AddItem( Immovable( Rehued( new ChainChest(), 2125 ) ) ); - AddItem( Immovable( Rehued( new ChainLegs(), 2125 ) ) ); - AddItem( Immovable( Rehued( new ChainCoif (), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateArms(), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateGloves(), 2125 ) ) ); + AddItem(Immovable(Rehued(new BodySash(), 1254))); + AddItem(Immovable(Rehued(new Kilt(), 1254))); + AddItem(Immovable(Rehued(new Sandals(), 1254))); - AddItem( Immovable( Rehued( new BodySash(), 1254 ) ) ); - AddItem( Immovable( Rehued( new Kilt(), 1254 ) ) ); - AddItem( Immovable( Rehued( new Sandals(), 1254 ) ) ); + AddItem(Newbied(new Bardiche())); - AddItem( Newbied( new Bardiche() ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionKnight(Serial serial) : base(serial) + { + } - public FactionKnight( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Melee | GuardAI.Smart | GuardAI.Curse | GuardAI.Bless; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionMercenary.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionMercenary.cs index 405b692dc..76944c6d5 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionMercenary.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionMercenary.cs @@ -2,62 +2,62 @@ using Server.Items; namespace Server.Factions { - public class FactionMercenary : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Melee | GuardAI.Smart; + public class FactionMercenary : BaseFactionGuard + { + [Constructible] + public FactionMercenary() : base("the mercenary") + { + GenerateBody(false, true); - [Constructible] - public FactionMercenary() : base( "the mercenary" ) - { - GenerateBody( false, true ); + SetStr(116, 125); + SetDex(61, 85); + SetInt(81, 95); - SetStr( 116, 125 ); - SetDex( 61, 85 ); - SetInt( 81, 95 ); + SetResistance(ResistanceType.Physical, 20, 40); + SetResistance(ResistanceType.Fire, 20, 40); + SetResistance(ResistanceType.Cold, 20, 40); + SetResistance(ResistanceType.Energy, 20, 40); + SetResistance(ResistanceType.Poison, 20, 40); - SetResistance( ResistanceType.Physical, 20, 40 ); - SetResistance( ResistanceType.Fire, 20, 40 ); - SetResistance( ResistanceType.Cold, 20, 40 ); - SetResistance( ResistanceType.Energy, 20, 40 ); - SetResistance( ResistanceType.Poison, 20, 40 ); + VirtualArmor = 16; - VirtualArmor = 16; + SetSkill(SkillName.Fencing, 90.0, 100.0); + SetSkill(SkillName.Wrestling, 90.0, 100.0); + SetSkill(SkillName.Tactics, 90.0, 100.0); + SetSkill(SkillName.MagicResist, 90.0, 100.0); + SetSkill(SkillName.Healing, 90.0, 100.0); + SetSkill(SkillName.Anatomy, 90.0, 100.0); - SetSkill( SkillName.Fencing, 90.0, 100.0 ); - SetSkill( SkillName.Wrestling, 90.0, 100.0 ); - SetSkill( SkillName.Tactics, 90.0, 100.0 ); - SetSkill( SkillName.MagicResist, 90.0, 100.0 ); - SetSkill( SkillName.Healing, 90.0, 100.0 ); - SetSkill( SkillName.Anatomy, 90.0, 100.0 ); + AddItem(new ChainChest()); + AddItem(new ChainLegs()); + AddItem(new RingmailArms()); + AddItem(new RingmailGloves()); + AddItem(new ChainCoif()); + AddItem(new Boots()); + AddItem(Newbied(new ShortSpear())); - AddItem( new ChainChest() ); - AddItem( new ChainLegs() ); - AddItem( new RingmailArms() ); - AddItem( new RingmailGloves() ); - AddItem( new ChainCoif () ); - AddItem( new Boots() ); - AddItem( Newbied( new ShortSpear() ) ); + PackItem(new Bandage(Utility.RandomMinMax(20, 30))); + PackStrongPotions(3, 8); + } - PackItem( new Bandage( Utility.RandomMinMax( 20, 30 ) ) ); - PackStrongPotions( 3, 8 ); - } + public FactionMercenary(Serial serial) : base(serial) + { + } - public FactionMercenary( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Melee | GuardAI.Smart; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionNecromancer.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionNecromancer.cs index 25634359d..be98dea85 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionNecromancer.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionNecromancer.cs @@ -2,65 +2,65 @@ using Server.Items; namespace Server.Factions { - public class FactionNecromancer : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Smart | GuardAI.Bless | GuardAI.Curse; + public class FactionNecromancer : BaseFactionGuard + { + [Constructible] + public FactionNecromancer() : base("the necromancer") + { + GenerateBody(false, false); + Hue = 1; - [Constructible] - public FactionNecromancer() : base( "the necromancer" ) - { - GenerateBody( false, false ); - Hue = 1; + SetStr(151, 175); + SetDex(61, 85); + SetInt(151, 175); - SetStr( 151, 175 ); - SetDex( 61, 85 ); - SetInt( 151, 175 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Energy, 40, 60); + SetResistance(ResistanceType.Poison, 40, 60); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Energy, 40, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); + VirtualArmor = 32; - VirtualArmor = 32; + SetSkill(SkillName.Macing, 110.0, 120.0); + SetSkill(SkillName.Wrestling, 110.0, 120.0); + SetSkill(SkillName.Tactics, 110.0, 120.0); + SetSkill(SkillName.MagicResist, 110.0, 120.0); + SetSkill(SkillName.Healing, 110.0, 120.0); + SetSkill(SkillName.Anatomy, 110.0, 120.0); - SetSkill( SkillName.Macing, 110.0, 120.0 ); - SetSkill( SkillName.Wrestling, 110.0, 120.0 ); - SetSkill( SkillName.Tactics, 110.0, 120.0 ); - SetSkill( SkillName.MagicResist, 110.0, 120.0 ); - SetSkill( SkillName.Healing, 110.0, 120.0 ); - SetSkill( SkillName.Anatomy, 110.0, 120.0 ); + SetSkill(SkillName.Magery, 110.0, 120.0); + SetSkill(SkillName.EvalInt, 110.0, 120.0); + SetSkill(SkillName.Meditation, 110.0, 120.0); - SetSkill( SkillName.Magery, 110.0, 120.0 ); - SetSkill( SkillName.EvalInt, 110.0, 120.0 ); - SetSkill( SkillName.Meditation, 110.0, 120.0 ); + Item shroud = new Item(0x204E); + shroud.Layer = Layer.OuterTorso; - Item shroud = new Item( 0x204E ); - shroud.Layer = Layer.OuterTorso; + AddItem(Immovable(Rehued(shroud, 1109))); + AddItem(Newbied(Rehued(new GnarledStaff(), 2211))); - AddItem( Immovable( Rehued( shroud, 1109 ) ) ); - AddItem( Newbied( Rehued( new GnarledStaff(), 2211 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionNecromancer(Serial serial) : base(serial) + { + } - public FactionNecromancer( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Smart | GuardAI.Bless | GuardAI.Curse; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionPaladin.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionPaladin.cs index fc240468e..4484fa2f8 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionPaladin.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionPaladin.cs @@ -2,72 +2,72 @@ using Server.Items; namespace Server.Factions { - public class FactionPaladin : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Melee | GuardAI.Smart | GuardAI.Curse | GuardAI.Bless; + public class FactionPaladin : BaseFactionGuard + { + [Constructible] + public FactionPaladin() : base("the paladin") + { + GenerateBody(false, false); - [Constructible] - public FactionPaladin() : base( "the paladin" ) - { - GenerateBody( false, false ); + SetStr(151, 175); + SetDex(61, 85); + SetInt(81, 95); - SetStr( 151, 175 ); - SetDex( 61, 85 ); - SetInt( 81, 95 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Energy, 40, 60); + SetResistance(ResistanceType.Poison, 40, 60); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Energy, 40, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); + VirtualArmor = 32; - VirtualArmor = 32; + SetSkill(SkillName.Swords, 110.0, 120.0); + SetSkill(SkillName.Wrestling, 110.0, 120.0); + SetSkill(SkillName.Tactics, 110.0, 120.0); + SetSkill(SkillName.MagicResist, 110.0, 120.0); + SetSkill(SkillName.Healing, 110.0, 120.0); + SetSkill(SkillName.Anatomy, 110.0, 120.0); - SetSkill( SkillName.Swords, 110.0, 120.0 ); - SetSkill( SkillName.Wrestling, 110.0, 120.0 ); - SetSkill( SkillName.Tactics, 110.0, 120.0 ); - SetSkill( SkillName.MagicResist, 110.0, 120.0 ); - SetSkill( SkillName.Healing, 110.0, 120.0 ); - SetSkill( SkillName.Anatomy, 110.0, 120.0 ); + SetSkill(SkillName.Magery, 110.0, 120.0); + SetSkill(SkillName.EvalInt, 110.0, 120.0); + SetSkill(SkillName.Meditation, 110.0, 120.0); - SetSkill( SkillName.Magery, 110.0, 120.0 ); - SetSkill( SkillName.EvalInt, 110.0, 120.0 ); - SetSkill( SkillName.Meditation, 110.0, 120.0 ); + AddItem(Immovable(Rehued(new PlateChest(), 2125))); + AddItem(Immovable(Rehued(new PlateLegs(), 2125))); + AddItem(Immovable(Rehued(new PlateHelm(), 2125))); + AddItem(Immovable(Rehued(new PlateGorget(), 2125))); + AddItem(Immovable(Rehued(new PlateArms(), 2125))); + AddItem(Immovable(Rehued(new PlateGloves(), 2125))); - AddItem( Immovable( Rehued( new PlateChest(), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateLegs(), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateHelm(), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateGorget(), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateArms(), 2125 ) ) ); - AddItem( Immovable( Rehued( new PlateGloves(), 2125 ) ) ); + AddItem(Immovable(Rehued(new BodySash(), 1254))); + AddItem(Immovable(Rehued(new Cloak(), 1254))); - AddItem( Immovable( Rehued( new BodySash(), 1254 ) ) ); - AddItem( Immovable( Rehued( new Cloak(), 1254 ) ) ); + AddItem(Newbied(new Halberd())); - AddItem( Newbied( new Halberd() ) ); + AddItem(Immovable(Rehued(new VirtualMountItem(this), 1254))); - AddItem( Immovable( Rehued( new VirtualMountItem( this ), 1254 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionPaladin(Serial serial) : base(serial) + { + } - public FactionPaladin( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Melee | GuardAI.Smart | GuardAI.Curse | GuardAI.Bless; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionSorceress.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionSorceress.cs index bdfadd83d..744a3a4b5 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionSorceress.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionSorceress.cs @@ -2,69 +2,69 @@ using Server.Items; namespace Server.Factions { - public class FactionSorceress : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Bless | GuardAI.Curse; + public class FactionSorceress : BaseFactionGuard + { + [Constructible] + public FactionSorceress() : base("the sorceress") + { + GenerateBody(true, false); - [Constructible] - public FactionSorceress() : base( "the sorceress" ) - { - GenerateBody( true, false ); + SetStr(126, 150); + SetDex(61, 85); + SetInt(126, 150); - SetStr( 126, 150 ); - SetDex( 61, 85 ); - SetInt( 126, 150 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 50); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 30, 50); + SetResistance(ResistanceType.Energy, 30, 50); + SetResistance(ResistanceType.Poison, 30, 50); - SetResistance( ResistanceType.Physical, 30, 50 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 30, 50 ); - SetResistance( ResistanceType.Energy, 30, 50 ); - SetResistance( ResistanceType.Poison, 30, 50 ); + VirtualArmor = 24; - VirtualArmor = 24; + SetSkill(SkillName.Macing, 100.0, 110.0); + SetSkill(SkillName.Wrestling, 100.0, 110.0); + SetSkill(SkillName.Tactics, 100.0, 110.0); + SetSkill(SkillName.MagicResist, 100.0, 110.0); + SetSkill(SkillName.Healing, 100.0, 110.0); + SetSkill(SkillName.Anatomy, 100.0, 110.0); - SetSkill( SkillName.Macing, 100.0, 110.0 ); - SetSkill( SkillName.Wrestling, 100.0, 110.0 ); - SetSkill( SkillName.Tactics, 100.0, 110.0 ); - SetSkill( SkillName.MagicResist, 100.0, 110.0 ); - SetSkill( SkillName.Healing, 100.0, 110.0 ); - SetSkill( SkillName.Anatomy, 100.0, 110.0 ); + SetSkill(SkillName.Magery, 100.0, 110.0); + SetSkill(SkillName.EvalInt, 100.0, 110.0); + SetSkill(SkillName.Meditation, 100.0, 110.0); - SetSkill( SkillName.Magery, 100.0, 110.0 ); - SetSkill( SkillName.EvalInt, 100.0, 110.0 ); - SetSkill( SkillName.Meditation, 100.0, 110.0 ); + AddItem(Immovable(Rehued(new WizardsHat(), 1325))); + AddItem(Immovable(Rehued(new Sandals(), 1325))); + AddItem(Immovable(Rehued(new LeatherGorget(), 1325))); + AddItem(Immovable(Rehued(new LeatherGloves(), 1325))); + AddItem(Immovable(Rehued(new LeatherLegs(), 1325))); + AddItem(Immovable(Rehued(new Skirt(), 1325))); + AddItem(Immovable(Rehued(new FemaleLeatherChest(), 1325))); + AddItem(Newbied(Rehued(new QuarterStaff(), 1310))); - AddItem( Immovable( Rehued( new WizardsHat(), 1325 ) ) ); - AddItem( Immovable( Rehued( new Sandals(), 1325 ) ) ); - AddItem( Immovable( Rehued( new LeatherGorget(), 1325 ) ) ); - AddItem( Immovable( Rehued( new LeatherGloves(), 1325 ) ) ); - AddItem( Immovable( Rehued( new LeatherLegs(), 1325 ) ) ); - AddItem( Immovable( Rehued( new Skirt(), 1325 ) ) ); - AddItem( Immovable( Rehued( new FemaleLeatherChest(), 1325 ) ) ); - AddItem( Newbied( Rehued( new QuarterStaff(), 1310 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionSorceress(Serial serial) : base(serial) + { + } - public FactionSorceress( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Bless | GuardAI.Curse; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionWizard.cs b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionWizard.cs index aa35bb372..8ef89f912 100644 --- a/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionWizard.cs +++ b/Scripts/Engines/Factions/Mobiles/Guards/Types/FactionWizard.cs @@ -2,66 +2,66 @@ using Server.Items; namespace Server.Factions { - public class FactionWizard : BaseFactionGuard - { - public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Smart | GuardAI.Bless | GuardAI.Curse; + public class FactionWizard : BaseFactionGuard + { + [Constructible] + public FactionWizard() : base("the wizard") + { + GenerateBody(false, false); - [Constructible] - public FactionWizard() : base( "the wizard" ) - { - GenerateBody( false, false ); + SetStr(151, 175); + SetDex(61, 85); + SetInt(151, 175); - SetStr( 151, 175 ); - SetDex( 61, 85 ); - SetInt( 151, 175 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Energy, 40, 60); + SetResistance(ResistanceType.Poison, 40, 60); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Energy, 40, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); + VirtualArmor = 32; - VirtualArmor = 32; + SetSkill(SkillName.Macing, 110.0, 120.0); + SetSkill(SkillName.Wrestling, 110.0, 120.0); + SetSkill(SkillName.Tactics, 110.0, 120.0); + SetSkill(SkillName.MagicResist, 110.0, 120.0); + SetSkill(SkillName.Healing, 110.0, 120.0); + SetSkill(SkillName.Anatomy, 110.0, 120.0); - SetSkill( SkillName.Macing, 110.0, 120.0 ); - SetSkill( SkillName.Wrestling, 110.0, 120.0 ); - SetSkill( SkillName.Tactics, 110.0, 120.0 ); - SetSkill( SkillName.MagicResist, 110.0, 120.0 ); - SetSkill( SkillName.Healing, 110.0, 120.0 ); - SetSkill( SkillName.Anatomy, 110.0, 120.0 ); + SetSkill(SkillName.Magery, 110.0, 120.0); + SetSkill(SkillName.EvalInt, 110.0, 120.0); + SetSkill(SkillName.Meditation, 110.0, 120.0); - SetSkill( SkillName.Magery, 110.0, 120.0 ); - SetSkill( SkillName.EvalInt, 110.0, 120.0 ); - SetSkill( SkillName.Meditation, 110.0, 120.0 ); + AddItem(Immovable(Rehued(new WizardsHat(), 1325))); + AddItem(Immovable(Rehued(new Sandals(), 1325))); + AddItem(Immovable(Rehued(new Robe(), 1310))); + AddItem(Immovable(Rehued(new LeatherGloves(), 1325))); + AddItem(Newbied(Rehued(new GnarledStaff(), 1310))); - AddItem( Immovable( Rehued( new WizardsHat(), 1325 ) ) ); - AddItem( Immovable( Rehued( new Sandals(), 1325 ) ) ); - AddItem( Immovable( Rehued( new Robe(), 1310 ) ) ); - AddItem( Immovable( Rehued( new LeatherGloves(), 1325 ) ) ); - AddItem( Newbied( Rehued( new GnarledStaff(), 1310 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(30, 40))); + PackStrongPotions(6, 12); + } - PackItem( new Bandage( Utility.RandomMinMax( 30, 40 ) ) ); - PackStrongPotions( 6, 12 ); - } + public FactionWizard(Serial serial) : base(serial) + { + } - public FactionWizard( Serial serial ) : base( serial ) - { - } + public override GuardAI GuardAI => GuardAI.Magic | GuardAI.Smart | GuardAI.Bless | GuardAI.Curse; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Vendors/BaseFactionVendor.cs b/Scripts/Engines/Factions/Mobiles/Vendors/BaseFactionVendor.cs index f90c8ac1f..7d743e263 100644 --- a/Scripts/Engines/Factions/Mobiles/Vendors/BaseFactionVendor.cs +++ b/Scripts/Engines/Factions/Mobiles/Vendors/BaseFactionVendor.cs @@ -3,109 +3,119 @@ using Server.Mobiles; namespace Server.Factions { - public abstract class BaseFactionVendor : BaseVendor - { - private Town m_Town; - private Faction m_Faction; + public abstract class BaseFactionVendor : BaseVendor + { + private Faction m_Faction; + private Town m_Town; - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Town Town - { - get => m_Town; - set{ Unregister(); m_Town = value; Register(); } - } + public BaseFactionVendor(Town town, Faction faction, string title) : base(title) + { + Frozen = true; + CantWalk = true; + Female = false; + BodyValue = 400; + Name = NameList.RandomName("male"); - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public Faction Faction - { - get => m_Faction; - set{ Unregister(); m_Faction = value; Register(); } - } + RangeHome = 0; - public void Register() - { - if ( m_Town != null && m_Faction != null ) - m_Town.RegisterVendor( this ); - } + m_Town = town; + m_Faction = faction; + Register(); + } - public override bool OnMoveOver( Mobile m ) - { - if ( Core.ML ) - return true; + public BaseFactionVendor(Serial serial) : base(serial) + { + } - return base.OnMoveOver( m ); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Town Town + { + get => m_Town; + set + { + Unregister(); + m_Town = value; + Register(); + } + } - public void Unregister() - { - m_Town?.UnregisterVendor( this ); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public Faction Faction + { + get => m_Faction; + set + { + Unregister(); + m_Faction = value; + Register(); + } + } - protected override List SBInfos { get; } = new List(); + protected override List SBInfos{ get; } = new List(); - public override void InitSBInfo() - { - } + public void Register() + { + if (m_Town != null && m_Faction != null) + m_Town.RegisterVendor(this); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override bool OnMoveOver(Mobile m) + { + if (Core.ML) + return true; - Unregister(); - } + return base.OnMoveOver(m); + } - public override bool CheckVendorAccess( Mobile from ) - { - return true; - } + public void Unregister() + { + m_Town?.UnregisterVendor(this); + } - public BaseFactionVendor( Town town, Faction faction, string title ) : base( title ) - { - Frozen = true; - CantWalk = true; - Female = false; - BodyValue = 400; - Name = NameList.RandomName( "male" ); + public override void InitSBInfo() + { + } - RangeHome = 0; + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Town = town; - m_Faction = faction; - Register(); - } + Unregister(); + } - public BaseFactionVendor( Serial serial ) : base( serial ) - { - } + public override bool CheckVendorAccess(Mobile from) + { + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - Town.WriteReference( writer, m_Town ); - Faction.WriteReference( writer, m_Faction ); - } + Town.WriteReference(writer, m_Town); + Faction.WriteReference(writer, m_Faction); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Town = Town.ReadReference( reader ); - m_Faction = Faction.ReadReference( reader ); - Register(); - break; - } - } + switch (version) + { + case 0: + { + m_Town = Town.ReadReference(reader); + m_Faction = Faction.ReadReference(reader); + Register(); + break; + } + } - Frozen = true; - } - } + Frozen = true; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Vendors/FactionBoardVendor.cs b/Scripts/Engines/Factions/Mobiles/Vendors/FactionBoardVendor.cs index fe90c0a6b..5d7db298f 100644 --- a/Scripts/Engines/Factions/Mobiles/Vendors/FactionBoardVendor.cs +++ b/Scripts/Engines/Factions/Mobiles/Vendors/FactionBoardVendor.cs @@ -4,69 +4,63 @@ using Server.Mobiles; namespace Server.Factions { - public class FactionBoardVendor : BaseFactionVendor - { - public FactionBoardVendor( Town town, Faction faction ) : base( town, faction, "the LumberMan" ) // NOTE: title inconsistant, as OSI - { - SetSkill( SkillName.Carpentry, 85.0, 100.0 ); - SetSkill( SkillName.Lumberjacking, 60.0, 83.0 ); - } + public class FactionBoardVendor : BaseFactionVendor + { + public FactionBoardVendor(Town town, Faction faction) : + base(town, faction, "the LumberMan") // NOTE: title inconsistant, as OSI + { + SetSkill(SkillName.Carpentry, 85.0, 100.0); + SetSkill(SkillName.Lumberjacking, 60.0, 83.0); + } - public override void InitSBInfo() - { - SBInfos.Add( new SBFactionBoard() ); - } + public FactionBoardVendor(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + SBInfos.Add(new SBFactionBoard()); + } - AddItem( new HalfApron() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public FactionBoardVendor( Serial serial ) : base( serial ) - { - } + AddItem(new HalfApron()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SBFactionBoard : SBInfo - { - public SBFactionBoard() - { - } + public class SBFactionBoard : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + for (int i = 0; i < 5; ++i) + Add(new GenericBuyInfo(typeof(Board), 3, 20, 0x1BD7, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - for ( int i = 0; i < 5; ++i ) - Add( new GenericBuyInfo( typeof( Board ), 3, 20, 0x1BD7, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Vendors/FactionBottleVendor.cs b/Scripts/Engines/Factions/Mobiles/Vendors/FactionBottleVendor.cs index b92e7e654..dc04b663c 100644 --- a/Scripts/Engines/Factions/Mobiles/Vendors/FactionBottleVendor.cs +++ b/Scripts/Engines/Factions/Mobiles/Vendors/FactionBottleVendor.cs @@ -4,71 +4,64 @@ using Server.Mobiles; namespace Server.Factions { - public class FactionBottleVendor : BaseFactionVendor - { - public FactionBottleVendor( Town town, Faction faction ) : base( town, faction, "the Bottle Seller" ) - { - SetSkill( SkillName.Alchemy, 85.0, 100.0 ); - SetSkill( SkillName.TasteID, 65.0, 88.0 ); - } + public class FactionBottleVendor : BaseFactionVendor + { + public FactionBottleVendor(Town town, Faction faction) : base(town, faction, "the Bottle Seller") + { + SetSkill(SkillName.Alchemy, 85.0, 100.0); + SetSkill(SkillName.TasteID, 65.0, 88.0); + } - public override void InitSBInfo() - { - SBInfos.Add( new SBFactionBottle() ); - } + public FactionBottleVendor(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + SBInfos.Add(new SBFactionBottle()); + } - AddItem( new Robe( Utility.RandomPinkHue() ) ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public FactionBottleVendor( Serial serial ) : base( serial ) - { - } + AddItem(new Robe(Utility.RandomPinkHue())); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SBFactionBottle : SBInfo - { - public SBFactionBottle() - { - } + public class SBFactionBottle : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + for (int i = 0; i < 5; ++i) + Add(new GenericBuyInfo(typeof(Bottle), 5, 20, 0xF0E, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - for ( int i = 0; i < 5; ++i ) - Add( new GenericBuyInfo( typeof( Bottle ), 5, 20, 0xF0E, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Vendors/FactionHorseVendor.cs b/Scripts/Engines/Factions/Mobiles/Vendors/FactionHorseVendor.cs index 037d015f9..0b26cf2eb 100644 --- a/Scripts/Engines/Factions/Mobiles/Vendors/FactionHorseVendor.cs +++ b/Scripts/Engines/Factions/Mobiles/Vendors/FactionHorseVendor.cs @@ -1,77 +1,78 @@ +using System.Collections.Generic; using Server.Items; using Server.Mobiles; using Server.Network; -using System.Collections.Generic; namespace Server.Factions { - public class FactionHorseVendor : BaseFactionVendor - { - public FactionHorseVendor( Town town, Faction faction ) : base( town, faction, "the Horse Breeder" ) - { - SetSkill( SkillName.AnimalLore, 64.0, 100.0 ); - SetSkill( SkillName.AnimalTaming, 90.0, 100.0 ); - SetSkill( SkillName.Veterinary, 65.0, 88.0 ); - } + public class FactionHorseVendor : BaseFactionVendor + { + public FactionHorseVendor(Town town, Faction faction) : base(town, faction, "the Horse Breeder") + { + SetSkill(SkillName.AnimalLore, 64.0, 100.0); + SetSkill(SkillName.AnimalTaming, 90.0, 100.0); + SetSkill(SkillName.Veterinary, 65.0, 88.0); + } - public override void InitSBInfo() - { - } + public FactionHorseVendor(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; + public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; - public override int GetShoeHue() - { - return 0; - } + public override void InitSBInfo() + { + } - public override void InitOutfit() - { - base.InitOutfit(); + public override int GetShoeHue() + { + return 0; + } - AddItem( Utility.RandomBool() ? (Item)new QuarterStaff() : (Item)new ShepherdsCrook() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public FactionHorseVendor( Serial serial ) : base( serial ) - { - } + AddItem(Utility.RandomBool() ? new QuarterStaff() : (Item)new ShepherdsCrook()); + } - public override void VendorBuy( Mobile from ) - { - if ( Faction == null || Faction.Find( from, true ) != Faction ) - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042201, from.NetState ); // You are not in my faction, I cannot sell you a horse! - else if ( FactionGump.Exists( from ) ) - from.SendLocalizedMessage( 1042160 ); // You already have a faction menu open. - else if ( from is PlayerMobile mobile ) - mobile.SendGump( new HorseBreederGump( mobile, Faction ) ); - } + public override void VendorBuy(Mobile from) + { + if (Faction == null || Faction.Find(from, true) != Faction) + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042201, + from.NetState); // You are not in my faction, I cannot sell you a horse! + else if (FactionGump.Exists(from)) + from.SendLocalizedMessage(1042160); // You already have a faction menu open. + else if (from is PlayerMobile mobile) + mobile.SendGump(new HorseBreederGump(mobile, Faction)); + } - public override void VendorSell( Mobile from ) - { - } + public override void VendorSell(Mobile from) + { + } - public override bool OnBuyItems( Mobile buyer, List list ) - { - return false; - } + public override bool OnBuyItems(Mobile buyer, List list) + { + return false; + } - public override bool OnSellItems( Mobile seller, List list ) - { - return false; - } + public override bool OnSellItems(Mobile seller, List list) + { + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Vendors/FactionOreVendor.cs b/Scripts/Engines/Factions/Mobiles/Vendors/FactionOreVendor.cs index 7db88c5c7..d690b2bb1 100644 --- a/Scripts/Engines/Factions/Mobiles/Vendors/FactionOreVendor.cs +++ b/Scripts/Engines/Factions/Mobiles/Vendors/FactionOreVendor.cs @@ -4,72 +4,65 @@ using Server.Mobiles; namespace Server.Factions { - public class FactionOreVendor : BaseFactionVendor - { - public FactionOreVendor( Town town, Faction faction ) : base( town, faction, "the Ore Man" ) - { - // NOTE: Skills verified - SetSkill( SkillName.Carpentry, 85.0, 100.0 ); - SetSkill( SkillName.Lumberjacking, 60.0, 83.0 ); - } + public class FactionOreVendor : BaseFactionVendor + { + public FactionOreVendor(Town town, Faction faction) : base(town, faction, "the Ore Man") + { + // NOTE: Skills verified + SetSkill(SkillName.Carpentry, 85.0, 100.0); + SetSkill(SkillName.Lumberjacking, 60.0, 83.0); + } - public override void InitSBInfo() - { - SBInfos.Add( new SBFactionOre() ); - } + public FactionOreVendor(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + SBInfos.Add(new SBFactionOre()); + } - AddItem( new HalfApron() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public FactionOreVendor( Serial serial ) : base( serial ) - { - } + AddItem(new HalfApron()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SBFactionOre : SBInfo - { - private static readonly object[] m_FixedSizeArgs = { true }; + public class SBFactionOre : SBInfo + { + private static readonly object[] m_FixedSizeArgs = { true }; - public SBFactionOre() - { - } + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + for (int i = 0; i < 5; ++i) + Add(new GenericBuyInfo(typeof(IronOre), 16, 20, 0x19B8, 0, m_FixedSizeArgs)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - for ( int i = 0; i < 5; ++i ) - Add( new GenericBuyInfo( typeof( IronOre ), 16, 20, 0x19B8, 0, m_FixedSizeArgs ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Factions/Mobiles/Vendors/FactionReagentVendor.cs b/Scripts/Engines/Factions/Mobiles/Vendors/FactionReagentVendor.cs index 599e3b15e..3f50876ba 100644 --- a/Scripts/Engines/Factions/Mobiles/Vendors/FactionReagentVendor.cs +++ b/Scripts/Engines/Factions/Mobiles/Vendors/FactionReagentVendor.cs @@ -4,85 +4,78 @@ using Server.Mobiles; namespace Server.Factions { - public class FactionReagentVendor : BaseFactionVendor - { - public FactionReagentVendor( Town town, Faction faction ) : base( town, faction, "the Reagent Man" ) - { - SetSkill( SkillName.EvalInt, 65.0, 88.0 ); - SetSkill( SkillName.Inscribe, 60.0, 83.0 ); - SetSkill( SkillName.Magery, 64.0, 100.0 ); - SetSkill( SkillName.Meditation, 60.0, 83.0 ); - SetSkill( SkillName.MagicResist, 65.0, 88.0 ); - SetSkill( SkillName.Wrestling, 36.0, 68.0 ); - } + public class FactionReagentVendor : BaseFactionVendor + { + public FactionReagentVendor(Town town, Faction faction) : base(town, faction, "the Reagent Man") + { + SetSkill(SkillName.EvalInt, 65.0, 88.0); + SetSkill(SkillName.Inscribe, 60.0, 83.0); + SetSkill(SkillName.Magery, 64.0, 100.0); + SetSkill(SkillName.Meditation, 60.0, 83.0); + SetSkill(SkillName.MagicResist, 65.0, 88.0); + SetSkill(SkillName.Wrestling, 36.0, 68.0); + } - public override void InitSBInfo() - { - SBInfos.Add( new SBFactionReagent() ); - } + public FactionReagentVendor(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + SBInfos.Add(new SBFactionReagent()); + } - AddItem( new Robe( Utility.RandomBlueHue() ) ); - AddItem( new GnarledStaff() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public FactionReagentVendor( Serial serial ) : base( serial ) - { - } + AddItem(new Robe(Utility.RandomBlueHue())); + AddItem(new GnarledStaff()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SBFactionReagent : SBInfo - { - public SBFactionReagent() - { - } + public class SBFactionReagent : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + for (int i = 0; i < 2; ++i) + { + Add(new GenericBuyInfo(typeof(BlackPearl), 5, 20, 0xF7A, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 20, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(SulfurousAsh), 3, 20, 0xF8C, 0)); + } + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - for ( int i = 0; i < 2; ++i ) - { - Add( new GenericBuyInfo( typeof( BlackPearl ), 5, 20, 0xF7A, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 20, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( SulfurousAsh ), 3, 20, 0xF8C, 0 ) ); - } - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/BonusHarvestResource.cs b/Scripts/Engines/Harvest/Core/BonusHarvestResource.cs index b4683891e..ce189171a 100644 --- a/Scripts/Engines/Harvest/Core/BonusHarvestResource.cs +++ b/Scripts/Engines/Harvest/Core/BonusHarvestResource.cs @@ -2,28 +2,28 @@ using System; namespace Server.Engines.Harvest { - public class BonusHarvestResource - { - public Type Type { get; set; } + public class BonusHarvestResource + { + public BonusHarvestResource(double reqSkill, double chance, TextDefinition message, Type type) + { + ReqSkill = reqSkill; - public double ReqSkill { get; set; } + Chance = chance; + Type = type; + SuccessMessage = message; + } - public double Chance { get; set; } + public Type Type{ get; set; } - public TextDefinition SuccessMessage { get; } + public double ReqSkill{ get; set; } - public void SendSuccessTo( Mobile m ) - { - TextDefinition.SendMessageTo( m, SuccessMessage ); - } + public double Chance{ get; set; } - public BonusHarvestResource( double reqSkill, double chance, TextDefinition message, Type type ) - { - ReqSkill = reqSkill; + public TextDefinition SuccessMessage{ get; } - Chance = chance; - Type = type; - SuccessMessage = message; - } - } -} + public void SendSuccessTo(Mobile m) + { + TextDefinition.SendMessageTo(m, SuccessMessage); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestBank.cs b/Scripts/Engines/Harvest/Core/HarvestBank.cs index c17199f3d..887449f33 100644 --- a/Scripts/Engines/Harvest/Core/HarvestBank.cs +++ b/Scripts/Engines/Harvest/Core/HarvestBank.cs @@ -2,93 +2,90 @@ using System; namespace Server.Engines.Harvest { - public class HarvestBank - { - private int m_Current; - private int m_Maximum; - private DateTime m_NextRespawn; - private HarvestVein m_Vein, m_DefaultVein; + public class HarvestBank + { + private int m_Current; + private int m_Maximum; + private DateTime m_NextRespawn; + private HarvestVein m_Vein, m_DefaultVein; - public HarvestDefinition Definition { get; } + public HarvestBank(HarvestDefinition def, HarvestVein defaultVein) + { + m_Maximum = Utility.RandomMinMax(def.MinTotal, def.MaxTotal); + m_Current = m_Maximum; + m_DefaultVein = defaultVein; + m_Vein = m_DefaultVein; - public int Current - { - get - { - CheckRespawn(); - return m_Current; - } - } + Definition = def; + } - public HarvestVein Vein - { - get - { - CheckRespawn(); - return m_Vein; - } - set => m_Vein = value; - } + public HarvestDefinition Definition{ get; } - public HarvestVein DefaultVein - { - get - { - CheckRespawn(); - return m_DefaultVein; - } - } + public int Current + { + get + { + CheckRespawn(); + return m_Current; + } + } - public void CheckRespawn() - { - if ( m_Current == m_Maximum || m_NextRespawn > DateTime.UtcNow ) - return; + public HarvestVein Vein + { + get + { + CheckRespawn(); + return m_Vein; + } + set => m_Vein = value; + } - m_Current = m_Maximum; + public HarvestVein DefaultVein + { + get + { + CheckRespawn(); + return m_DefaultVein; + } + } - if ( Definition.RandomizeVeins ) - { - m_DefaultVein = Definition.GetVeinFrom( Utility.RandomDouble() ); - } + public void CheckRespawn() + { + if (m_Current == m_Maximum || m_NextRespawn > DateTime.UtcNow) + return; - m_Vein = m_DefaultVein; - } + m_Current = m_Maximum; - public void Consume( int amount, Mobile from ) - { - CheckRespawn(); + if (Definition.RandomizeVeins) m_DefaultVein = Definition.GetVeinFrom(Utility.RandomDouble()); - if ( m_Current == m_Maximum ) - { - double min = Definition.MinRespawn.TotalMinutes; - double max = Definition.MaxRespawn.TotalMinutes; - double rnd = Utility.RandomDouble(); + m_Vein = m_DefaultVein; + } - m_Current = m_Maximum - amount; + public void Consume(int amount, Mobile from) + { + CheckRespawn(); - double minutes = min + (rnd * (max - min)); - if ( Definition.RaceBonus && from.Race == Race.Elf ) //def.RaceBonus = Core.ML - minutes *= .75; //25% off the time. + if (m_Current == m_Maximum) + { + double min = Definition.MinRespawn.TotalMinutes; + double max = Definition.MaxRespawn.TotalMinutes; + double rnd = Utility.RandomDouble(); - m_NextRespawn = DateTime.UtcNow + TimeSpan.FromMinutes( minutes ); - } - else - { - m_Current -= amount; - } + m_Current = m_Maximum - amount; - if ( m_Current < 0 ) - m_Current = 0; - } + double minutes = min + rnd * (max - min); + if (Definition.RaceBonus && from.Race == Race.Elf) //def.RaceBonus = Core.ML + minutes *= .75; //25% off the time. - public HarvestBank( HarvestDefinition def, HarvestVein defaultVein ) - { - m_Maximum = Utility.RandomMinMax( def.MinTotal, def.MaxTotal ); - m_Current = m_Maximum; - m_DefaultVein = defaultVein; - m_Vein = m_DefaultVein; + m_NextRespawn = DateTime.UtcNow + TimeSpan.FromMinutes(minutes); + } + else + { + m_Current -= amount; + } - Definition = def; - } - } + if (m_Current < 0) + m_Current = 0; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestDefinition.cs b/Scripts/Engines/Harvest/Core/HarvestDefinition.cs index a49fcd256..a83826ebb 100644 --- a/Scripts/Engines/Harvest/Core/HarvestDefinition.cs +++ b/Scripts/Engines/Harvest/Core/HarvestDefinition.cs @@ -3,179 +3,179 @@ using System.Collections.Generic; namespace Server.Engines.Harvest { - public class HarvestDefinition - { - public int BankWidth { get; set; } + public class HarvestDefinition + { + public HarvestDefinition() + { + Banks = new Dictionary>(); + } - public int BankHeight { get; set; } + public int BankWidth{ get; set; } - public int MinTotal { get; set; } + public int BankHeight{ get; set; } - public int MaxTotal { get; set; } + public int MinTotal{ get; set; } - public int[] Tiles { get; set; } + public int MaxTotal{ get; set; } - public bool RangedTiles { get; set; } + public int[] Tiles{ get; set; } - public TimeSpan MinRespawn { get; set; } + public bool RangedTiles{ get; set; } - public TimeSpan MaxRespawn { get; set; } + public TimeSpan MinRespawn{ get; set; } - public int MaxRange { get; set; } + public TimeSpan MaxRespawn{ get; set; } - public int ConsumedPerHarvest { get; set; } + public int MaxRange{ get; set; } - public int ConsumedPerFeluccaHarvest { get; set; } + public int ConsumedPerHarvest{ get; set; } - public bool PlaceAtFeetIfFull { get; set; } + public int ConsumedPerFeluccaHarvest{ get; set; } - public SkillName Skill { get; set; } + public bool PlaceAtFeetIfFull{ get; set; } - public int[] EffectActions { get; set; } + public SkillName Skill{ get; set; } - public int[] EffectCounts { get; set; } + public int[] EffectActions{ get; set; } - public int[] EffectSounds { get; set; } + public int[] EffectCounts{ get; set; } - public TimeSpan EffectSoundDelay { get; set; } + public int[] EffectSounds{ get; set; } - public TimeSpan EffectDelay { get; set; } + public TimeSpan EffectSoundDelay{ get; set; } - public object NoResourcesMessage { get; set; } + public TimeSpan EffectDelay{ get; set; } - public object OutOfRangeMessage { get; set; } + public object NoResourcesMessage{ get; set; } - public object TimedOutOfRangeMessage { get; set; } + public object OutOfRangeMessage{ get; set; } - public object DoubleHarvestMessage { get; set; } + public object TimedOutOfRangeMessage{ get; set; } - public object FailMessage { get; set; } + public object DoubleHarvestMessage{ get; set; } - public object PackFullMessage { get; set; } + public object FailMessage{ get; set; } - public object ToolBrokeMessage { get; set; } + public object PackFullMessage{ get; set; } - public HarvestResource[] Resources { get; set; } + public object ToolBrokeMessage{ get; set; } - public HarvestVein[] Veins { get; set; } + public HarvestResource[] Resources{ get; set; } - public BonusHarvestResource[] BonusResources { get; set; } + public HarvestVein[] Veins{ get; set; } - public bool RaceBonus { get; set; } + public BonusHarvestResource[] BonusResources{ get; set; } - public bool RandomizeVeins { get; set; } + public bool RaceBonus{ get; set; } - public Dictionary> Banks { get; set; } + public bool RandomizeVeins{ get; set; } - public void SendMessageTo( Mobile from, object message ) - { - if ( message is int messageInt ) - from.SendLocalizedMessage( messageInt ); - else - from.SendMessage( message.ToString() ); - } + public Dictionary> Banks{ get; set; } - public HarvestBank GetBank( Map map, int x, int y ) - { - if ( map == null || map == Map.Internal ) - return null; + public void SendMessageTo(Mobile from, object message) + { + if (message is int messageInt) + from.SendLocalizedMessage(messageInt); + else + from.SendMessage(message.ToString()); + } - x /= BankWidth; - y /= BankHeight; + public HarvestBank GetBank(Map map, int x, int y) + { + if (map == null || map == Map.Internal) + return null; - Banks.TryGetValue( map, out Dictionary banks ); + x /= BankWidth; + y /= BankHeight; - if ( banks == null ) - Banks[map] = banks = new Dictionary(); + Banks.TryGetValue(map, out Dictionary banks); - Point2D key = new Point2D( x, y ); - banks.TryGetValue( key, out HarvestBank bank ); + if (banks == null) + Banks[map] = banks = new Dictionary(); - if ( bank == null ) - banks[key] = bank = new HarvestBank( this, GetVeinAt( map, x, y ) ); + Point2D key = new Point2D(x, y); + banks.TryGetValue(key, out HarvestBank bank); - return bank; - } + if (bank == null) + banks[key] = bank = new HarvestBank(this, GetVeinAt(map, x, y)); - public HarvestVein GetVeinAt( Map map, int x, int y ) - { - if ( Veins.Length == 1 ) - return Veins[0]; + return bank; + } - double randomValue; + public HarvestVein GetVeinAt(Map map, int x, int y) + { + if (Veins.Length == 1) + return Veins[0]; - if ( RandomizeVeins ) - { - randomValue = Utility.RandomDouble(); - } - else - { - Random random = new Random( ( x * 17 ) + ( y * 11 ) + ( map.MapID * 3 ) ); - randomValue = random.NextDouble(); - } + double randomValue; - return GetVeinFrom( randomValue ); - } + if (RandomizeVeins) + { + randomValue = Utility.RandomDouble(); + } + else + { + Random random = new Random(x * 17 + y * 11 + map.MapID * 3); + randomValue = random.NextDouble(); + } - public HarvestVein GetVeinFrom( double randomValue ) - { - if ( Veins.Length == 1 ) - return Veins[0]; + return GetVeinFrom(randomValue); + } - randomValue *= 100; + public HarvestVein GetVeinFrom(double randomValue) + { + if (Veins.Length == 1) + return Veins[0]; - for ( int i = 0; i < Veins.Length; ++i ) - { - if ( randomValue <= Veins[i].VeinChance ) - return Veins[i]; + randomValue *= 100; - randomValue -= Veins[i].VeinChance; - } + for (int i = 0; i < Veins.Length; ++i) + { + if (randomValue <= Veins[i].VeinChance) + return Veins[i]; - return null; - } + randomValue -= Veins[i].VeinChance; + } - public BonusHarvestResource GetBonusResource() - { - if ( BonusResources == null ) - return null; + return null; + } - double randomValue = Utility.RandomDouble() * 100; + public BonusHarvestResource GetBonusResource() + { + if (BonusResources == null) + return null; - for ( int i = 0; i < BonusResources.Length; ++i ) - { - if ( randomValue <= BonusResources[i].Chance ) - return BonusResources[i]; + double randomValue = Utility.RandomDouble() * 100; - randomValue -= BonusResources[i].Chance; - } + for (int i = 0; i < BonusResources.Length; ++i) + { + if (randomValue <= BonusResources[i].Chance) + return BonusResources[i]; - return null; - } + randomValue -= BonusResources[i].Chance; + } - public HarvestDefinition() - { - Banks = new Dictionary>(); - } + return null; + } - public bool Validate( int tileID ) - { - if ( RangedTiles ) - { - bool contains = false; + public bool Validate(int tileID) + { + if (RangedTiles) + { + bool contains = false; - for ( int i = 0; !contains && i < Tiles.Length; i += 2 ) - contains = ( tileID >= Tiles[i] && tileID <= Tiles[i + 1] ); + for (int i = 0; !contains && i < Tiles.Length; i += 2) + contains = tileID >= Tiles[i] && tileID <= Tiles[i + 1]; - return contains; - } + return contains; + } - int dist = -1; + int dist = -1; - for ( int i = 0; dist < 0 && i < Tiles.Length; ++i ) - dist = ( Tiles[i] - tileID ); + for (int i = 0; dist < 0 && i < Tiles.Length; ++i) + dist = Tiles[i] - tileID; - return ( dist == 0 ); - } - } -} + return dist == 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestResource.cs b/Scripts/Engines/Harvest/Core/HarvestResource.cs index 3027ac19e..e48fb8d91 100644 --- a/Scripts/Engines/Harvest/Core/HarvestResource.cs +++ b/Scripts/Engines/Harvest/Core/HarvestResource.cs @@ -2,33 +2,33 @@ using System; namespace Server.Engines.Harvest { - public class HarvestResource - { - public Type[] Types { get; set; } + public class HarvestResource + { + public HarvestResource(double reqSkill, double minSkill, double maxSkill, object message, params Type[] types) + { + ReqSkill = reqSkill; + MinSkill = minSkill; + MaxSkill = maxSkill; + Types = types; + SuccessMessage = message; + } - public double ReqSkill { get; set; } + public Type[] Types{ get; set; } - public double MinSkill { get; set; } + public double ReqSkill{ get; set; } - public double MaxSkill { get; set; } + public double MinSkill{ get; set; } - public object SuccessMessage { get; } + public double MaxSkill{ get; set; } - public void SendSuccessTo( Mobile m ) - { - if ( SuccessMessage is int messageInt ) - m.SendLocalizedMessage( messageInt ); - else - m.SendMessage( SuccessMessage.ToString() ); - } + public object SuccessMessage{ get; } - public HarvestResource( double reqSkill, double minSkill, double maxSkill, object message, params Type[] types ) - { - ReqSkill = reqSkill; - MinSkill = minSkill; - MaxSkill = maxSkill; - Types = types; - SuccessMessage = message; - } - } -} + public void SendSuccessTo(Mobile m) + { + if (SuccessMessage is int messageInt) + m.SendLocalizedMessage(messageInt); + else + m.SendMessage(SuccessMessage.ToString()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestSoundTimer.cs b/Scripts/Engines/Harvest/Core/HarvestSoundTimer.cs index 4063126e7..076031bd8 100644 --- a/Scripts/Engines/Harvest/Core/HarvestSoundTimer.cs +++ b/Scripts/Engines/Harvest/Core/HarvestSoundTimer.cs @@ -1,31 +1,32 @@ namespace Server.Engines.Harvest { - public class HarvestSoundTimer : Timer - { - private Mobile m_From; - private Item m_Tool; - private HarvestSystem m_System; - private HarvestDefinition m_Definition; - private object m_ToHarvest, m_Locked; - private bool m_Last; + public class HarvestSoundTimer : Timer + { + private HarvestDefinition m_Definition; + private Mobile m_From; + private bool m_Last; + private HarvestSystem m_System; + private object m_ToHarvest, m_Locked; + private Item m_Tool; - public HarvestSoundTimer( Mobile from, Item tool, HarvestSystem system, HarvestDefinition def, object toHarvest, object locked, bool last ) : base( def.EffectSoundDelay ) - { - m_From = from; - m_Tool = tool; - m_System = system; - m_Definition = def; - m_ToHarvest = toHarvest; - m_Locked = locked; - m_Last = last; - } + public HarvestSoundTimer(Mobile from, Item tool, HarvestSystem system, HarvestDefinition def, object toHarvest, + object locked, bool last) : base(def.EffectSoundDelay) + { + m_From = from; + m_Tool = tool; + m_System = system; + m_Definition = def; + m_ToHarvest = toHarvest; + m_Locked = locked; + m_Last = last; + } - protected override void OnTick() - { - m_System.DoHarvestingSound( m_From, m_Tool, m_Definition, m_ToHarvest ); + protected override void OnTick() + { + m_System.DoHarvestingSound(m_From, m_Tool, m_Definition, m_ToHarvest); - if ( m_Last ) - m_System.FinishHarvesting( m_From, m_Tool, m_Definition, m_ToHarvest, m_Locked ); - } - } + if (m_Last) + m_System.FinishHarvesting(m_From, m_Tool, m_Definition, m_ToHarvest, m_Locked); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestSystem.cs b/Scripts/Engines/Harvest/Core/HarvestSystem.cs index 81ca2a85d..1164e7a34 100644 --- a/Scripts/Engines/Harvest/Core/HarvestSystem.cs +++ b/Scripts/Engines/Harvest/Core/HarvestSystem.cs @@ -5,492 +5,502 @@ using Server.Targeting; namespace Server.Engines.Harvest { - public abstract class HarvestSystem - { - public List Definitions { get; } - - public HarvestSystem() - { - Definitions = new List(); - } - - public virtual bool CheckTool( Mobile from, Item tool ) - { - bool wornOut = ( tool == null || tool.Deleted || (tool is IUsesRemaining remaining && remaining.UsesRemaining <= 0) ); - - if ( wornOut ) - from.SendLocalizedMessage( 1044038 ); // You have worn out your tool! - - return !wornOut; - } - - public virtual bool CheckHarvest( Mobile from, Item tool ) - { - return CheckTool( from, tool ); - } - - public virtual bool CheckHarvest( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - return CheckTool( from, tool ); - } - - public virtual bool CheckRange( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, bool timed ) - { - bool inRange = ( from.Map == map && from.InRange( loc, def.MaxRange ) ); - - if ( !inRange ) - def.SendMessageTo( from, timed ? def.TimedOutOfRangeMessage : def.OutOfRangeMessage ); - - return inRange; - } + public abstract class HarvestSystem + { + public HarvestSystem() + { + Definitions = new List(); + } + + public List Definitions{ get; } + + public virtual bool CheckTool(Mobile from, Item tool) + { + bool wornOut = tool == null || tool.Deleted || tool is IUsesRemaining remaining && remaining.UsesRemaining <= 0; + + if (wornOut) + from.SendLocalizedMessage(1044038); // You have worn out your tool! + + return !wornOut; + } + + public virtual bool CheckHarvest(Mobile from, Item tool) + { + return CheckTool(from, tool); + } + + public virtual bool CheckHarvest(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + return CheckTool(from, tool); + } + + public virtual bool CheckRange(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, bool timed) + { + bool inRange = from.Map == map && from.InRange(loc, def.MaxRange); + + if (!inRange) + def.SendMessageTo(from, timed ? def.TimedOutOfRangeMessage : def.OutOfRangeMessage); + + return inRange; + } - public virtual bool CheckResources( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, bool timed ) - { - HarvestBank bank = def.GetBank( map, loc.X, loc.Y ); - bool available = ( bank != null && bank.Current >= def.ConsumedPerHarvest ); + public virtual bool CheckResources(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, bool timed) + { + HarvestBank bank = def.GetBank(map, loc.X, loc.Y); + bool available = bank != null && bank.Current >= def.ConsumedPerHarvest; - if ( !available ) - def.SendMessageTo( from, timed ? def.DoubleHarvestMessage : def.NoResourcesMessage ); + if (!available) + def.SendMessageTo(from, timed ? def.DoubleHarvestMessage : def.NoResourcesMessage); - return available; - } + return available; + } - public virtual void OnBadHarvestTarget( Mobile from, Item tool, object toHarvest ) - { - } + public virtual void OnBadHarvestTarget(Mobile from, Item tool, object toHarvest) + { + } - public virtual object GetLock( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - /* Here we prevent multiple harvesting. - * - * Some options: - * - 'return tool;' : This will allow the player to harvest more than once concurrently, but only if they use multiple tools. This seems to be as OSI. - * - 'return GetType();' : This will disallow multiple harvesting of the same type. That is, we couldn't mine more than once concurrently, but we could be both mining and lumberjacking. - * - 'return typeof( HarvestSystem );' : This will completely restrict concurrent harvesting. - */ - - return tool; - } - - public virtual void OnConcurrentHarvest( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - } - - public virtual void OnHarvestStarted( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - } - - public virtual bool BeginHarvesting( Mobile from, Item tool ) - { - if ( !CheckHarvest( from, tool ) ) - return false; - - from.Target = new HarvestTarget( tool, this ); - return true; - } - - public virtual void FinishHarvesting( Mobile from, Item tool, HarvestDefinition def, object toHarvest, object locked ) - { - from.EndAction( locked ); - - if ( !CheckHarvest( from, tool ) ) - return; - - int tileID; - Map map; - Point3D loc; - - if ( !GetHarvestDetails( from, tool, toHarvest, out tileID, out map, out loc ) ) - { - OnBadHarvestTarget( from, tool, toHarvest ); - return; - } - - if ( !def.Validate( tileID ) ) - { - OnBadHarvestTarget( from, tool, toHarvest ); - return; - } - - if ( !CheckRange( from, tool, def, map, loc, true ) ) - return; - if ( !CheckResources( from, tool, def, map, loc, true ) ) - return; - if ( !CheckHarvest( from, tool, def, toHarvest ) ) - return; - - if ( SpecialHarvest( from, tool, def, map, loc ) ) - return; - - HarvestBank bank = def.GetBank( map, loc.X, loc.Y ); - - if ( bank == null ) - return; - - HarvestVein vein = bank.Vein; - - if ( vein != null ) - vein = MutateVein( from, tool, def, bank, toHarvest, vein ); - - if ( vein == null ) - return; - - HarvestResource primary = vein.PrimaryResource; - HarvestResource fallback = vein.FallbackResource; - HarvestResource resource = MutateResource( from, tool, def, map, loc, vein, primary, fallback ); - - double skillBase = from.Skills[def.Skill].Base; - double skillValue = from.Skills[def.Skill].Value; - - Type type = null; - - if ( skillBase >= resource.ReqSkill && from.CheckSkill( def.Skill, resource.MinSkill, resource.MaxSkill ) ) - { - type = GetResourceType( from, tool, def, map, loc, resource ); - - if ( type != null ) - type = MutateType( type, from, tool, def, map, loc, resource ); - - if ( type != null ) - { - Item item = Construct( type, from ); - - if ( item == null ) - { - type = null; - } - else - { - //The whole harvest system is kludgy and I'm sure this is just adding to it. - if ( item.Stackable ) - { - int amount = def.ConsumedPerHarvest; - int feluccaAmount = def.ConsumedPerFeluccaHarvest; - - int racialAmount = (int)Math.Ceiling( amount * 1.1 ); - int feluccaRacialAmount = (int)Math.Ceiling( feluccaAmount * 1.1 ); - - bool eligableForRacialBonus = ( def.RaceBonus && from.Race == Race.Human ); - bool inFelucca = (map == Map.Felucca); - - if ( eligableForRacialBonus && inFelucca && bank.Current >= feluccaRacialAmount && 0.1 > Utility.RandomDouble() ) - item.Amount = feluccaRacialAmount; - else if ( inFelucca && bank.Current >= feluccaAmount ) - item.Amount = feluccaAmount; - else if ( eligableForRacialBonus && bank.Current >= racialAmount && 0.1 > Utility.RandomDouble() ) - item.Amount = racialAmount; - else - item.Amount = amount; - } - - bank.Consume( item.Amount, from ); - - if ( Give( from, item, def.PlaceAtFeetIfFull ) ) - { - SendSuccessTo( from, item, resource ); - } - else - { - SendPackFullTo( from, item, def, resource ); - item.Delete(); - } - - BonusHarvestResource bonus = def.GetBonusResource(); - - if ( bonus != null && bonus.Type != null && skillBase >= bonus.ReqSkill ) - { - Item bonusItem = Construct( bonus.Type, from ); - - if ( Give( from, bonusItem, true ) ) //Bonuses always allow placing at feet, even if pack is full irregrdless of def - { - bonus.SendSuccessTo( from ); - } - else - { - item.Delete(); - } - } - - if ( tool is IUsesRemaining toolWithUses ) - { - toolWithUses.ShowUsesRemaining = true; - - if ( toolWithUses.UsesRemaining > 0 ) - --toolWithUses.UsesRemaining; - - if ( toolWithUses.UsesRemaining < 1 ) - { - tool.Delete(); - def.SendMessageTo( from, def.ToolBrokeMessage ); - } - } - } - } - } - - if ( type == null ) - def.SendMessageTo( from, def.FailMessage ); - - OnHarvestFinished( from, tool, def, vein, bank, resource, toHarvest ); - } - - public virtual void OnHarvestFinished( Mobile from, Item tool, HarvestDefinition def, HarvestVein vein, HarvestBank bank, HarvestResource resource, object harvested ) - { - } - - public virtual bool SpecialHarvest( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc ) - { - return false; - } - - public virtual Item Construct( Type type, Mobile from ) - { - try{ return Activator.CreateInstance( type ) as Item; } - catch{ return null; } - } - - public virtual HarvestVein MutateVein( Mobile from, Item tool, HarvestDefinition def, HarvestBank bank, object toHarvest, HarvestVein vein ) - { - return vein; - } - - public virtual void SendSuccessTo( Mobile from, Item item, HarvestResource resource ) - { - resource.SendSuccessTo( from ); - } - - public virtual void SendPackFullTo( Mobile from, Item item, HarvestDefinition def, HarvestResource resource ) - { - def.SendMessageTo( from, def.PackFullMessage ); - } - - public virtual bool Give( Mobile m, Item item, bool placeAtFeet ) - { - if ( m.PlaceInBackpack( item ) ) - return true; - - if ( !placeAtFeet ) - return false; - - Map map = m.Map; - - if ( map == null ) - return false; - - List atFeet = new List(); - - foreach ( Item obj in m.GetItemsInRange( 0 ) ) - atFeet.Add( obj ); - - for ( int i = 0; i < atFeet.Count; ++i ) - { - Item check = atFeet[i]; - - if ( check.StackWith( m, item, false ) ) - return true; - } - - item.MoveToWorld( m.Location, map ); - return true; - } - - public virtual Type MutateType( Type type, Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, HarvestResource resource ) - { - return from.Region.GetResource( type ); - } - - public virtual Type GetResourceType( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, HarvestResource resource ) - { - if ( resource.Types.Length > 0 ) - return resource.Types[Utility.Random( resource.Types.Length )]; - - return null; - } - - public virtual HarvestResource MutateResource( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, HarvestVein vein, HarvestResource primary, HarvestResource fallback ) - { - bool racialBonus = (def.RaceBonus && from.Race == Race.Elf ); - - if ( vein.ChanceToFallback > (Utility.RandomDouble() + (racialBonus ? .20 : 0)) ) - return fallback; - - double skillValue = from.Skills[def.Skill].Value; - - if ( fallback != null && (skillValue < primary.ReqSkill || skillValue < primary.MinSkill) ) - return fallback; - - return primary; - } - - public virtual bool OnHarvesting( Mobile from, Item tool, HarvestDefinition def, object toHarvest, object locked, bool last ) - { - if ( !CheckHarvest( from, tool ) ) - { - from.EndAction( locked ); - return false; - } - - int tileID; - Map map; - Point3D loc; - - if ( !GetHarvestDetails( from, tool, toHarvest, out tileID, out map, out loc ) ) - { - from.EndAction( locked ); - OnBadHarvestTarget( from, tool, toHarvest ); - return false; - } - - if ( !def.Validate( tileID ) ) - { - from.EndAction( locked ); - OnBadHarvestTarget( from, tool, toHarvest ); - return false; - } - if ( !CheckRange( from, tool, def, map, loc, true ) ) - { - from.EndAction( locked ); - return false; - } - if ( !CheckResources( from, tool, def, map, loc, true ) ) - { - from.EndAction( locked ); - return false; - } - if ( !CheckHarvest( from, tool, def, toHarvest ) ) - { - from.EndAction( locked ); - return false; - } - - DoHarvestingEffect( from, tool, def, map, loc ); - - new HarvestSoundTimer( from, tool, this, def, toHarvest, locked, last ).Start(); - - return !last; - } - - public virtual void DoHarvestingSound( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - if ( def.EffectSounds.Length > 0 ) - from.PlaySound( Utility.RandomList( def.EffectSounds ) ); - } - - public virtual void DoHarvestingEffect( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc ) - { - from.Direction = from.GetDirectionTo( loc ); - - if ( !from.Mounted ) - from.Animate( Utility.RandomList( def.EffectActions ), 5, 1, true, false, 0 ); - } - - public virtual HarvestDefinition GetDefinition( int tileID ) - { - HarvestDefinition def = null; - - for ( int i = 0; def == null && i < Definitions.Count; ++i ) - { - HarvestDefinition check = Definitions[i]; - - if ( check.Validate( tileID ) ) - def = check; - } - - return def; - } - - public virtual void StartHarvesting( Mobile from, Item tool, object toHarvest ) - { - if ( !CheckHarvest( from, tool ) ) - return; - - int tileID; - Map map; - Point3D loc; - - if ( !GetHarvestDetails( from, tool, toHarvest, out tileID, out map, out loc ) ) - { - OnBadHarvestTarget( from, tool, toHarvest ); - return; - } - - HarvestDefinition def = GetDefinition( tileID ); - - if ( def == null ) - { - OnBadHarvestTarget( from, tool, toHarvest ); - return; - } - - if ( !CheckRange( from, tool, def, map, loc, false ) ) - return; - if ( !CheckResources( from, tool, def, map, loc, false ) ) - return; - if ( !CheckHarvest( from, tool, def, toHarvest ) ) - return; - - object toLock = GetLock( from, tool, def, toHarvest ); - - if ( !from.BeginAction( toLock ) ) - { - OnConcurrentHarvest( from, tool, def, toHarvest ); - return; - } - - new HarvestTimer( from, tool, this, def, toHarvest, toLock ).Start(); - OnHarvestStarted( from, tool, def, toHarvest ); - } - - public virtual bool GetHarvestDetails( Mobile from, Item tool, object toHarvest, out int tileID, out Map map, out Point3D loc ) - { - if ( toHarvest is Static staticObj && !staticObj.Movable ) - { - tileID = (staticObj.ItemID & 0x3FFF) | 0x4000; - map = staticObj.Map; - loc = staticObj.GetWorldLocation(); - } - else if ( toHarvest is StaticTarget staticTarget ) - { - tileID = (staticTarget.ItemID & 0x3FFF) | 0x4000; - map = from.Map; - loc = staticTarget.Location; - } - else if ( toHarvest is LandTarget landTarget ) - { - tileID = landTarget.TileID; - map = from.Map; - loc = landTarget.Location; - } - else - { - tileID = 0; - map = null; - loc = Point3D.Zero; - return false; - } - - return ( map != null && map != Map.Internal ); - } - } + public virtual object GetLock(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + /* Here we prevent multiple harvesting. + * + * Some options: + * - 'return tool;' : This will allow the player to harvest more than once concurrently, but only if they use multiple tools. This seems to be as OSI. + * - 'return GetType();' : This will disallow multiple harvesting of the same type. That is, we couldn't mine more than once concurrently, but we could be both mining and lumberjacking. + * - 'return typeof( HarvestSystem );' : This will completely restrict concurrent harvesting. + */ + + return tool; + } + + public virtual void OnConcurrentHarvest(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + } + + public virtual void OnHarvestStarted(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + } + + public virtual bool BeginHarvesting(Mobile from, Item tool) + { + if (!CheckHarvest(from, tool)) + return false; + + from.Target = new HarvestTarget(tool, this); + return true; + } + + public virtual void FinishHarvesting(Mobile from, Item tool, HarvestDefinition def, object toHarvest, object locked) + { + from.EndAction(locked); + + if (!CheckHarvest(from, tool)) + return; + + int tileID; + Map map; + Point3D loc; + + if (!GetHarvestDetails(from, tool, toHarvest, out tileID, out map, out loc)) + { + OnBadHarvestTarget(from, tool, toHarvest); + return; + } + + if (!def.Validate(tileID)) + { + OnBadHarvestTarget(from, tool, toHarvest); + return; + } + + if (!CheckRange(from, tool, def, map, loc, true)) + return; + if (!CheckResources(from, tool, def, map, loc, true)) + return; + if (!CheckHarvest(from, tool, def, toHarvest)) + return; + + if (SpecialHarvest(from, tool, def, map, loc)) + return; + + HarvestBank bank = def.GetBank(map, loc.X, loc.Y); + + if (bank == null) + return; + + HarvestVein vein = bank.Vein; + + if (vein != null) + vein = MutateVein(from, tool, def, bank, toHarvest, vein); + + if (vein == null) + return; + + HarvestResource primary = vein.PrimaryResource; + HarvestResource fallback = vein.FallbackResource; + HarvestResource resource = MutateResource(from, tool, def, map, loc, vein, primary, fallback); + + double skillBase = from.Skills[def.Skill].Base; + double skillValue = from.Skills[def.Skill].Value; + + Type type = null; + + if (skillBase >= resource.ReqSkill && from.CheckSkill(def.Skill, resource.MinSkill, resource.MaxSkill)) + { + type = GetResourceType(from, tool, def, map, loc, resource); + + if (type != null) + type = MutateType(type, from, tool, def, map, loc, resource); + + if (type != null) + { + Item item = Construct(type, from); + + if (item == null) + { + type = null; + } + else + { + //The whole harvest system is kludgy and I'm sure this is just adding to it. + if (item.Stackable) + { + int amount = def.ConsumedPerHarvest; + int feluccaAmount = def.ConsumedPerFeluccaHarvest; + + int racialAmount = (int)Math.Ceiling(amount * 1.1); + int feluccaRacialAmount = (int)Math.Ceiling(feluccaAmount * 1.1); + + bool eligableForRacialBonus = def.RaceBonus && from.Race == Race.Human; + bool inFelucca = map == Map.Felucca; + + if (eligableForRacialBonus && inFelucca && bank.Current >= feluccaRacialAmount && + 0.1 > Utility.RandomDouble()) + item.Amount = feluccaRacialAmount; + else if (inFelucca && bank.Current >= feluccaAmount) + item.Amount = feluccaAmount; + else if (eligableForRacialBonus && bank.Current >= racialAmount && 0.1 > Utility.RandomDouble()) + item.Amount = racialAmount; + else + item.Amount = amount; + } + + bank.Consume(item.Amount, from); + + if (Give(from, item, def.PlaceAtFeetIfFull)) + { + SendSuccessTo(from, item, resource); + } + else + { + SendPackFullTo(from, item, def, resource); + item.Delete(); + } + + BonusHarvestResource bonus = def.GetBonusResource(); + + if (bonus != null && bonus.Type != null && skillBase >= bonus.ReqSkill) + { + Item bonusItem = Construct(bonus.Type, from); + + if (Give(from, bonusItem, true) + ) //Bonuses always allow placing at feet, even if pack is full irregrdless of def + bonus.SendSuccessTo(from); + else + item.Delete(); + } + + if (tool is IUsesRemaining toolWithUses) + { + toolWithUses.ShowUsesRemaining = true; + + if (toolWithUses.UsesRemaining > 0) + --toolWithUses.UsesRemaining; + + if (toolWithUses.UsesRemaining < 1) + { + tool.Delete(); + def.SendMessageTo(from, def.ToolBrokeMessage); + } + } + } + } + } + + if (type == null) + def.SendMessageTo(from, def.FailMessage); + + OnHarvestFinished(from, tool, def, vein, bank, resource, toHarvest); + } + + public virtual void OnHarvestFinished(Mobile from, Item tool, HarvestDefinition def, HarvestVein vein, + HarvestBank bank, HarvestResource resource, object harvested) + { + } + + public virtual bool SpecialHarvest(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc) + { + return false; + } + + public virtual Item Construct(Type type, Mobile from) + { + try + { + return Activator.CreateInstance(type) as Item; + } + catch + { + return null; + } + } + + public virtual HarvestVein MutateVein(Mobile from, Item tool, HarvestDefinition def, HarvestBank bank, + object toHarvest, HarvestVein vein) + { + return vein; + } + + public virtual void SendSuccessTo(Mobile from, Item item, HarvestResource resource) + { + resource.SendSuccessTo(from); + } + + public virtual void SendPackFullTo(Mobile from, Item item, HarvestDefinition def, HarvestResource resource) + { + def.SendMessageTo(from, def.PackFullMessage); + } + + public virtual bool Give(Mobile m, Item item, bool placeAtFeet) + { + if (m.PlaceInBackpack(item)) + return true; + + if (!placeAtFeet) + return false; + + Map map = m.Map; + + if (map == null) + return false; + + List atFeet = new List(); + + foreach (Item obj in m.GetItemsInRange(0)) + atFeet.Add(obj); + + for (int i = 0; i < atFeet.Count; ++i) + { + Item check = atFeet[i]; + + if (check.StackWith(m, item, false)) + return true; + } + + item.MoveToWorld(m.Location, map); + return true; + } + + public virtual Type MutateType(Type type, Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, + HarvestResource resource) + { + return from.Region.GetResource(type); + } + + public virtual Type GetResourceType(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, + HarvestResource resource) + { + if (resource.Types.Length > 0) + return resource.Types[Utility.Random(resource.Types.Length)]; + + return null; + } + + public virtual HarvestResource MutateResource(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, + HarvestVein vein, HarvestResource primary, HarvestResource fallback) + { + bool racialBonus = def.RaceBonus && from.Race == Race.Elf; + + if (vein.ChanceToFallback > Utility.RandomDouble() + (racialBonus ? .20 : 0)) + return fallback; + + double skillValue = from.Skills[def.Skill].Value; + + if (fallback != null && (skillValue < primary.ReqSkill || skillValue < primary.MinSkill)) + return fallback; + + return primary; + } + + public virtual bool OnHarvesting(Mobile from, Item tool, HarvestDefinition def, object toHarvest, object locked, + bool last) + { + if (!CheckHarvest(from, tool)) + { + from.EndAction(locked); + return false; + } + + int tileID; + Map map; + Point3D loc; + + if (!GetHarvestDetails(from, tool, toHarvest, out tileID, out map, out loc)) + { + from.EndAction(locked); + OnBadHarvestTarget(from, tool, toHarvest); + return false; + } + + if (!def.Validate(tileID)) + { + from.EndAction(locked); + OnBadHarvestTarget(from, tool, toHarvest); + return false; + } + + if (!CheckRange(from, tool, def, map, loc, true)) + { + from.EndAction(locked); + return false; + } + + if (!CheckResources(from, tool, def, map, loc, true)) + { + from.EndAction(locked); + return false; + } + + if (!CheckHarvest(from, tool, def, toHarvest)) + { + from.EndAction(locked); + return false; + } + + DoHarvestingEffect(from, tool, def, map, loc); + + new HarvestSoundTimer(from, tool, this, def, toHarvest, locked, last).Start(); + + return !last; + } + + public virtual void DoHarvestingSound(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + if (def.EffectSounds.Length > 0) + from.PlaySound(Utility.RandomList(def.EffectSounds)); + } + + public virtual void DoHarvestingEffect(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc) + { + from.Direction = from.GetDirectionTo(loc); + + if (!from.Mounted) + from.Animate(Utility.RandomList(def.EffectActions), 5, 1, true, false, 0); + } + + public virtual HarvestDefinition GetDefinition(int tileID) + { + HarvestDefinition def = null; + + for (int i = 0; def == null && i < Definitions.Count; ++i) + { + HarvestDefinition check = Definitions[i]; + + if (check.Validate(tileID)) + def = check; + } + + return def; + } + + public virtual void StartHarvesting(Mobile from, Item tool, object toHarvest) + { + if (!CheckHarvest(from, tool)) + return; + + int tileID; + Map map; + Point3D loc; + + if (!GetHarvestDetails(from, tool, toHarvest, out tileID, out map, out loc)) + { + OnBadHarvestTarget(from, tool, toHarvest); + return; + } + + HarvestDefinition def = GetDefinition(tileID); + + if (def == null) + { + OnBadHarvestTarget(from, tool, toHarvest); + return; + } + + if (!CheckRange(from, tool, def, map, loc, false)) + return; + if (!CheckResources(from, tool, def, map, loc, false)) + return; + if (!CheckHarvest(from, tool, def, toHarvest)) + return; + + object toLock = GetLock(from, tool, def, toHarvest); + + if (!from.BeginAction(toLock)) + { + OnConcurrentHarvest(from, tool, def, toHarvest); + return; + } + + new HarvestTimer(from, tool, this, def, toHarvest, toLock).Start(); + OnHarvestStarted(from, tool, def, toHarvest); + } + + public virtual bool GetHarvestDetails(Mobile from, Item tool, object toHarvest, out int tileID, out Map map, + out Point3D loc) + { + if (toHarvest is Static staticObj && !staticObj.Movable) + { + tileID = (staticObj.ItemID & 0x3FFF) | 0x4000; + map = staticObj.Map; + loc = staticObj.GetWorldLocation(); + } + else if (toHarvest is StaticTarget staticTarget) + { + tileID = (staticTarget.ItemID & 0x3FFF) | 0x4000; + map = from.Map; + loc = staticTarget.Location; + } + else if (toHarvest is LandTarget landTarget) + { + tileID = landTarget.TileID; + map = from.Map; + loc = landTarget.Location; + } + else + { + tileID = 0; + map = null; + loc = Point3D.Zero; + return false; + } + + return map != null && map != Map.Internal; + } + } } namespace Server { - public interface IChopable - { - void OnChop( Mobile from ); - } + public interface IChopable + { + void OnChop(Mobile from); + } - [AttributeUsage( AttributeTargets.Class )] - public class FurnitureAttribute : Attribute - { - public static bool Check( Item item ) - { - return ( item != null && item.GetType().IsDefined( typeof( FurnitureAttribute ), false ) ); - } - - public FurnitureAttribute() - { - } - } -} + [AttributeUsage(AttributeTargets.Class)] + public class FurnitureAttribute : Attribute + { + public static bool Check(Item item) + { + return item != null && item.GetType().IsDefined(typeof(FurnitureAttribute), false); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestTarget.cs b/Scripts/Engines/Harvest/Core/HarvestTarget.cs index 75f7d7f86..f7f7c23c7 100644 --- a/Scripts/Engines/Harvest/Core/HarvestTarget.cs +++ b/Scripts/Engines/Harvest/Core/HarvestTarget.cs @@ -1,96 +1,109 @@ -using Server.Items; -using Server.Targeting; -using Server.Mobiles; using Server.Engines.Quests; using Server.Engines.Quests.Hag; +using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.Engines.Harvest { - public class HarvestTarget : Target - { - private Item m_Tool; - private HarvestSystem m_System; + public class HarvestTarget : Target + { + private HarvestSystem m_System; + private Item m_Tool; - public HarvestTarget( Item tool, HarvestSystem system ) : base( -1, true, TargetFlags.None ) - { - m_Tool = tool; - m_System = system; + public HarvestTarget(Item tool, HarvestSystem system) : base(-1, true, TargetFlags.None) + { + m_Tool = tool; + m_System = system; - DisallowMultis = true; - } + DisallowMultis = true; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_System is Mining && targeted is StaticTarget target ) - { - int itemID = target.ItemID; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_System is Mining && targeted is StaticTarget target) + { + int itemID = target.ItemID; - // grave - if ( itemID == 0xED3 || itemID == 0xEDF || itemID == 0xEE0 || itemID == 0xEE1 || itemID == 0xEE2 || itemID == 0xEE8 ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + // grave + if (itemID == 0xED3 || itemID == 0xEDF || itemID == 0xEE0 || itemID == 0xEE1 || itemID == 0xEE2 || + itemID == 0xEE8) + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( qs is WitchApprenticeQuest && qs.FindObjective( typeof( FindIngredientObjective ) ) is FindIngredientObjective obj && !obj.Completed && obj.Ingredient == Ingredient.Bones ) - { - player.SendLocalizedMessage( 1055037 ); // You finish your grim work, finding some of the specific bones listed in the Hag's recipe. - obj.Complete(); + if (qs is WitchApprenticeQuest && + qs.FindObjective(typeof(FindIngredientObjective)) is FindIngredientObjective obj && + !obj.Completed && obj.Ingredient == Ingredient.Bones) + { + player.SendLocalizedMessage( + 1055037); // You finish your grim work, finding some of the specific bones listed in the Hag's recipe. + obj.Complete(); - return; - } - } - } - } + return; + } + } + } - if ( m_System is Lumberjacking && targeted is IChopable chopable ) - chopable.OnChop( from ); - else if ( m_System is Lumberjacking && targeted is IAxe obj && m_Tool is BaseAxe axe ) - { - Item item = (Item)obj; + if (m_System is Lumberjacking && targeted is IChopable chopable) + { + chopable.OnChop(from); + } + else if (m_System is Lumberjacking && targeted is IAxe obj && m_Tool is BaseAxe axe) + { + Item item = (Item)obj; - if ( !item.IsChildOf( from.Backpack ) ) - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - else if ( obj.Axe( from, axe ) ) - from.PlaySound( 0x13E ); - } - else if ( m_System is Lumberjacking && targeted is ICarvable carvable ) - carvable.Carve( from, m_Tool ); - else if ( m_System is Lumberjacking && FurnitureAttribute.Check( targeted as Item ) ) - DestroyFurniture( from, (Item)targeted ); - else if ( m_System is Mining && targeted is TreasureMap map ) - map.OnBeginDig( from ); - else - m_System.StartHarvesting( from, m_Tool, targeted ); - } + if (!item.IsChildOf(from.Backpack)) + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + else if (obj.Axe(from, axe)) + from.PlaySound(0x13E); + } + else if (m_System is Lumberjacking && targeted is ICarvable carvable) + { + carvable.Carve(from, m_Tool); + } + else if (m_System is Lumberjacking && FurnitureAttribute.Check(targeted as Item)) + { + DestroyFurniture(from, (Item)targeted); + } + else if (m_System is Mining && targeted is TreasureMap map) + { + map.OnBeginDig(from); + } + else + { + m_System.StartHarvesting(from, m_Tool, targeted); + } + } - private void DestroyFurniture( Mobile from, Item item ) - { - if ( !from.InRange( item.GetWorldLocation(), 3 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - return; - } - if ( !item.IsChildOf( from.Backpack ) && !item.Movable ) - { - from.SendLocalizedMessage( 500462 ); // You can't destroy that while it is here. - return; - } + private void DestroyFurniture(Mobile from, Item item) + { + if (!from.InRange(item.GetWorldLocation(), 3)) + { + from.SendLocalizedMessage(500446); // That is too far away. + return; + } - from.SendLocalizedMessage( 500461 ); // You destroy the item. - Effects.PlaySound( item.GetWorldLocation(), item.Map, 0x3B3 ); + if (!item.IsChildOf(from.Backpack) && !item.Movable) + { + from.SendLocalizedMessage(500462); // You can't destroy that while it is here. + return; + } - if ( item is Container container ) - { - if ( container is TrappableContainer trappableContainer ) - trappableContainer.ExecuteTrap( from ); + from.SendLocalizedMessage(500461); // You destroy the item. + Effects.PlaySound(item.GetWorldLocation(), item.Map, 0x3B3); - container.Destroy(); - } - else - { - item.Delete(); - } - } - } -} + if (item is Container container) + { + if (container is TrappableContainer trappableContainer) + trappableContainer.ExecuteTrap(from); + + container.Destroy(); + } + else + { + item.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestTimer.cs b/Scripts/Engines/Harvest/Core/HarvestTimer.cs index a91c6f7f0..dae664e40 100644 --- a/Scripts/Engines/Harvest/Core/HarvestTimer.cs +++ b/Scripts/Engines/Harvest/Core/HarvestTimer.cs @@ -2,30 +2,31 @@ using System; namespace Server.Engines.Harvest { - public class HarvestTimer : Timer - { - private Mobile m_From; - private Item m_Tool; - private HarvestSystem m_System; - private HarvestDefinition m_Definition; - private object m_ToHarvest, m_Locked; - private int m_Index, m_Count; + public class HarvestTimer : Timer + { + private HarvestDefinition m_Definition; + private Mobile m_From; + private int m_Index, m_Count; + private HarvestSystem m_System; + private object m_ToHarvest, m_Locked; + private Item m_Tool; - public HarvestTimer( Mobile from, Item tool, HarvestSystem system, HarvestDefinition def, object toHarvest, object locked ) : base( TimeSpan.Zero, def.EffectDelay ) - { - m_From = from; - m_Tool = tool; - m_System = system; - m_Definition = def; - m_ToHarvest = toHarvest; - m_Locked = locked; - m_Count = Utility.RandomList( def.EffectCounts ); - } + public HarvestTimer(Mobile from, Item tool, HarvestSystem system, HarvestDefinition def, object toHarvest, + object locked) : base(TimeSpan.Zero, def.EffectDelay) + { + m_From = from; + m_Tool = tool; + m_System = system; + m_Definition = def; + m_ToHarvest = toHarvest; + m_Locked = locked; + m_Count = Utility.RandomList(def.EffectCounts); + } - protected override void OnTick() - { - if ( !m_System.OnHarvesting( m_From, m_Tool, m_Definition, m_ToHarvest, m_Locked, ++m_Index == m_Count ) ) - Stop(); - } - } + protected override void OnTick() + { + if (!m_System.OnHarvesting(m_From, m_Tool, m_Definition, m_ToHarvest, m_Locked, ++m_Index == m_Count)) + Stop(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Core/HarvestVein.cs b/Scripts/Engines/Harvest/Core/HarvestVein.cs index 20431d747..fde929958 100644 --- a/Scripts/Engines/Harvest/Core/HarvestVein.cs +++ b/Scripts/Engines/Harvest/Core/HarvestVein.cs @@ -1,21 +1,22 @@ namespace Server.Engines.Harvest { - public class HarvestVein - { - public double VeinChance { get; set; } + public class HarvestVein + { + public HarvestVein(double veinChance, double chanceToFallback, HarvestResource primaryResource, + HarvestResource fallbackResource) + { + VeinChance = veinChance; + ChanceToFallback = chanceToFallback; + PrimaryResource = primaryResource; + FallbackResource = fallbackResource; + } - public double ChanceToFallback { get; set; } + public double VeinChance{ get; set; } - public HarvestResource PrimaryResource { get; set; } + public double ChanceToFallback{ get; set; } - public HarvestResource FallbackResource { get; set; } + public HarvestResource PrimaryResource{ get; set; } - public HarvestVein( double veinChance, double chanceToFallback, HarvestResource primaryResource, HarvestResource fallbackResource ) - { - VeinChance = veinChance; - ChanceToFallback = chanceToFallback; - PrimaryResource = primaryResource; - FallbackResource = fallbackResource; - } - } + public HarvestResource FallbackResource{ get; set; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Fishing.cs b/Scripts/Engines/Harvest/Fishing.cs index 1169902e4..013f905db 100644 --- a/Scripts/Engines/Harvest/Fishing.cs +++ b/Scripts/Engines/Harvest/Fishing.cs @@ -1,556 +1,568 @@ using System; +using System.Collections.Generic; +using Server.Engines.Quests; +using Server.Engines.Quests.Collector; using Server.Items; using Server.Mobiles; using Server.Network; -using Server.Engines.Quests; -using Server.Engines.Quests.Collector; -using System.Collections.Generic; +using Server.Spells; namespace Server.Engines.Harvest { - public class Fishing : HarvestSystem - { - private static Fishing m_System; - - public static Fishing System - { - get - { - if ( m_System == null ) - m_System = new Fishing(); - - return m_System; - } - } - - public HarvestDefinition Definition { get; } - - private Fishing() - { - HarvestResource[] res; - HarvestVein[] veins; - - #region Fishing - HarvestDefinition fish = new HarvestDefinition(); - - // Resource banks are every 8x8 tiles - fish.BankWidth = 8; - fish.BankHeight = 8; - - // Every bank holds from 5 to 15 fish - fish.MinTotal = 5; - fish.MaxTotal = 15; - - // A resource bank will respawn its content every 10 to 20 minutes - fish.MinRespawn = TimeSpan.FromMinutes( 10.0 ); - fish.MaxRespawn = TimeSpan.FromMinutes( 20.0 ); - - // Skill checking is done on the Fishing skill - fish.Skill = SkillName.Fishing; - - // Set the list of harvestable tiles - fish.Tiles = m_WaterTiles; - fish.RangedTiles = true; - - // Players must be within 4 tiles to harvest - fish.MaxRange = 4; - - // One fish per harvest action - fish.ConsumedPerHarvest = 1; - fish.ConsumedPerFeluccaHarvest = 1; - - // The fishing - fish.EffectActions = new[]{ 12 }; - fish.EffectSounds = new int[0]; - fish.EffectCounts = new[]{ 1 }; - fish.EffectDelay = TimeSpan.Zero; - fish.EffectSoundDelay = TimeSpan.FromSeconds( 8.0 ); - - fish.NoResourcesMessage = 503172; // The fish don't seem to be biting here. - fish.FailMessage = 503171; // You fish a while, but fail to catch anything. - fish.TimedOutOfRangeMessage = 500976; // You need to be closer to the water to fish! - fish.OutOfRangeMessage = 500976; // You need to be closer to the water to fish! - fish.PackFullMessage = 503176; // You do not have room in your backpack for a fish. - fish.ToolBrokeMessage = 503174; // You broke your fishing pole. - - res = new[] - { - new HarvestResource( 00.0, 00.0, 100.0, 1043297, typeof( Fish ) ) - }; - - veins = new[] - { - new HarvestVein( 100.0, 0.0, res[0], null ) - }; - - fish.Resources = res; - fish.Veins = veins; - - if ( Core.ML ) - { - fish.BonusResources = new[] - { - new BonusHarvestResource( 0, 99.4, null, null ), //set to same chance as mining ml gems - new BonusHarvestResource( 80.0, .6, 1072597, typeof( WhitePearl ) ) - }; - } - - Definition = fish; - Definitions.Add( fish ); - #endregion - } - - public override void OnConcurrentHarvest( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - from.SendLocalizedMessage( 500972 ); // You are already fishing. - } - - private class MutateEntry - { - public double m_ReqSkill, m_MinSkill, m_MaxSkill; - public bool m_DeepWater; - public Type[] m_Types; - - public MutateEntry( double reqSkill, double minSkill, double maxSkill, bool deepWater, params Type[] types ) - { - m_ReqSkill = reqSkill; - m_MinSkill = minSkill; - m_MaxSkill = maxSkill; - m_DeepWater = deepWater; - m_Types = types; - } - } - - private static MutateEntry[] m_MutateTable = { - new MutateEntry( 80.0, 80.0, 4080.0, true, typeof( SpecialFishingNet ) ), - new MutateEntry( 80.0, 80.0, 4080.0, true, typeof( BigFish ) ), - new MutateEntry( 90.0, 80.0, 4080.0, true, typeof( TreasureMap ) ), - new MutateEntry( 100.0, 80.0, 4080.0, true, typeof( MessageInABottle ) ), - new MutateEntry( 0.0, 125.0, -2375.0, false, typeof( PrizedFish ), typeof( WondrousFish ), typeof( TrulyRareFish ), typeof( PeculiarFish ) ), - new MutateEntry( 0.0, 105.0, -420.0, false, typeof( Boots ), typeof( Shoes ), typeof( Sandals ), typeof( ThighBoots ) ), - new MutateEntry( 0.0, 200.0, -200.0, false, new Type[1]{ null } ) - }; - - public override bool SpecialHarvest( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; - - if ( qs is CollectorQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( FishPearlsObjective ) ); - - if ( obj != null && !obj.Completed ) - { - if ( Utility.RandomDouble() < 0.5 ) - { - player.SendLocalizedMessage( 1055086, "", 0x59 ); // You pull a shellfish out of the water, and find a rainbow pearl inside of it. - - obj.CurProgress++; - } - else - { - player.SendLocalizedMessage( 1055087, "", 0x2C ); // You pull a shellfish out of the water, but it doesn't have a rainbow pearl. - } - - return true; - } - } - } - - return false; - } - - public override Type MutateType( Type type, Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, HarvestResource resource ) - { - bool deepWater = SpecialFishingNet.FullValidation( map, loc.X, loc.Y ); - - double skillBase = from.Skills[SkillName.Fishing].Base; - double skillValue = from.Skills[SkillName.Fishing].Value; - - for ( int i = 0; i < m_MutateTable.Length; ++i ) - { - MutateEntry entry = m_MutateTable[i]; - - if ( !deepWater && entry.m_DeepWater ) - continue; - - if ( skillBase >= entry.m_ReqSkill ) - { - double chance = (skillValue - entry.m_MinSkill) / (entry.m_MaxSkill - entry.m_MinSkill); - - if ( chance > Utility.RandomDouble() ) - return entry.m_Types[Utility.Random( entry.m_Types.Length )]; - } - } - - return type; - } - - private static Map SafeMap( Map map ) - { - if ( map == null || map == Map.Internal ) - return Map.Trammel; - - return map; - } - - public override bool CheckResources( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, bool timed ) - { - Container pack = from.Backpack; - - if ( pack != null ) - { - List messages = pack.FindItemsByType(); - - for ( int i = 0; i < messages.Count; ++i ) - { - SOS sos = messages[i]; - - if ( ( from.Map == Map.Felucca || from.Map == Map.Trammel ) && from.InRange( sos.TargetLocation, 60 ) ) - return true; - } - } - - return base.CheckResources( from, tool, def, map, loc, timed ); - } - - public override Item Construct( Type type, Mobile from ) - { - if ( type == typeof( TreasureMap ) ) - { - int level; - if ( from is PlayerMobile mobile && mobile.Young && mobile.Map == Map.Trammel && TreasureMap.IsInHavenIsland( from ) ) - level = 0; - else - level = 1; - - return new TreasureMap( level, from.Map == Map.Felucca ? Map.Felucca : Map.Trammel ); - } - if ( type == typeof( MessageInABottle ) ) - { - return new MessageInABottle( from.Map == Map.Felucca ? Map.Felucca : Map.Trammel ); - } - - Container pack = from.Backpack; - - if ( pack != null ) - { - List messages = pack.FindItemsByType(); - - for ( int i = 0; i < messages.Count; ++i ) - { - SOS sos = messages[i]; - - if ( ( from.Map == Map.Felucca || from.Map == Map.Trammel ) && from.InRange( sos.TargetLocation, 60 ) ) - { - Item preLoot = null; - - switch ( Utility.Random( 8 ) ) - { - case 0: // Body parts - { - int[] list = { - 0x1CDD, 0x1CE5, // arm - 0x1CE0, 0x1CE8, // torso - 0x1CE1, 0x1CE9, // head - 0x1CE2, 0x1CEC // leg - }; - - preLoot = new ShipwreckedItem( Utility.RandomList( list ) ); - break; - } - case 1: // Bone parts - { - int[] list = { - 0x1AE0, 0x1AE1, 0x1AE2, 0x1AE3, 0x1AE4, // skulls - 0x1B09, 0x1B0A, 0x1B0B, 0x1B0C, 0x1B0D, 0x1B0E, 0x1B0F, 0x1B10, // bone piles - 0x1B15, 0x1B16 // pelvis bones - }; - - preLoot = new ShipwreckedItem( Utility.RandomList( list ) ); - break; - } - case 2: // Paintings and portraits - { - preLoot = new ShipwreckedItem( Utility.Random( 0xE9F, 10 ) ); - break; - } - case 3: // Pillows - { - preLoot = new ShipwreckedItem( Utility.Random( 0x13A4, 11 ) ); - break; - } - case 4: // Shells - { - preLoot = new ShipwreckedItem( Utility.Random( 0xFC4, 9 ) ); - break; - } - case 5: //Hats - { - if ( Utility.RandomBool() ) - preLoot = new SkullCap(); - else - preLoot = new TricorneHat(); - - break; - } - case 6: // Misc - { - int[] list = { - 0x1EB5, // unfinished barrel - 0xA2A, // stool - 0xC1F, // broken clock - 0x1047, 0x1048, // globe - 0x1EB1, 0x1EB2, 0x1EB3, 0x1EB4 // barrel staves - }; - - if ( Utility.Random( list.Length + 1 ) == 0 ) - preLoot = new Candelabra(); - else - preLoot = new ShipwreckedItem( Utility.RandomList( list ) ); - - break; - } - } - - if ( preLoot != null ) - { - if ( preLoot is IShipwreckedItem shipwreckedItem ) - shipwreckedItem.IsShipwreckedItem = true; - - return preLoot; - } - - LockableContainer chest; - - if ( Utility.RandomBool() ) - chest = new MetalGoldenChest(); - else - chest = new WoodenChest(); - - if ( sos.IsAncient ) - chest.Hue = 0x481; - - TreasureMapChest.Fill( chest, Math.Max( 1, Math.Min( 4, sos.Level ) ) ); - - if ( sos.IsAncient ) - chest.DropItem( new FabledFishingNet() ); - else - chest.DropItem( new SpecialFishingNet() ); - - chest.Movable = true; - chest.Locked = false; - chest.TrapType = TrapType.None; - chest.TrapPower = 0; - chest.TrapLevel = 0; - - sos.Delete(); - - return chest; - } - } - } - - return base.Construct( type, from ); - } - - public override bool Give( Mobile m, Item item, bool placeAtFeet ) - { - if ( item is TreasureMap || item is MessageInABottle || item is SpecialFishingNet ) - { - BaseCreature serp; - - if ( 0.25 > Utility.RandomDouble() ) - serp = new DeepSeaSerpent(); - else - serp = new SeaSerpent(); - - int x = m.X, y = m.Y; - - Map map = m.Map; - - for ( int i = 0; map != null && i < 20; ++i ) - { - int tx = m.X - 10 + Utility.Random( 21 ); - int ty = m.Y - 10 + Utility.Random( 21 ); - - LandTile t = map.Tiles.GetLandTile( tx, ty ); - - if ( t.Z == -5 && ( (t.ID >= 0xA8 && t.ID <= 0xAB) || (t.ID >= 0x136 && t.ID <= 0x137) ) && !Spells.SpellHelper.CheckMulti( new Point3D( tx, ty, -5 ), map ) ) - { - x = tx; - y = ty; - break; - } - } - - serp.MoveToWorld( new Point3D( x, y, -5 ), map ); - - serp.Home = serp.Location; - serp.RangeHome = 10; - - serp.PackItem( item ); - - m.SendLocalizedMessage( 503170 ); // Uh oh! That doesn't look like a fish! - - return true; // we don't want to give the item to the player, it's on the serpent - } - - if ( item is BigFish || item is WoodenChest || item is MetalGoldenChest ) - placeAtFeet = true; - - return base.Give( m, item, placeAtFeet ); - } - - public override void SendSuccessTo( Mobile from, Item item, HarvestResource resource ) - { - if ( item is BigFish fish ) - { - from.SendLocalizedMessage( 1042635 ); // Your fishing pole bends as you pull a big fish from the depths! - fish.Fisher = from; - } - else if ( item is WoodenChest || item is MetalGoldenChest ) - { - from.SendLocalizedMessage( 503175 ); // You pull up a heavy chest from the depths of the ocean! - } - else - { - int number; - string name; - - if ( item is BaseMagicFish ) - { - number = 1008124; - name = "a mess of small fish"; - } - else if ( item is Fish ) - { - number = 1008124; - name = item.ItemData.Name; - } - else if ( item is BaseShoes ) - { - number = 1008124; - name = item.ItemData.Name; - } - else if ( item is TreasureMap ) - { - number = 1008125; - name = "a sodden piece of parchment"; - } - else if ( item is MessageInABottle ) - { - number = 1008125; - name = "a bottle, with a message in it"; - } - else if ( item is SpecialFishingNet ) - { - number = 1008125; - name = "a special fishing net"; // TODO: this is just a guess--what should it really be named? - } - else - { - number = 1043297; - - if ( (item.ItemData.Flags & TileFlag.ArticleA) != 0 ) - name = "a " + item.ItemData.Name; - else if ( (item.ItemData.Flags & TileFlag.ArticleAn) != 0 ) - name = "an " + item.ItemData.Name; - else - name = item.ItemData.Name; - } - - NetState ns = from.NetState; - - if ( ns == null ) - return; - - if ( number == 1043297 || ns.HighSeas ) - from.SendLocalizedMessage( number, name ); - else - from.SendLocalizedMessage( number, true, name ); - } - } - - public override void OnHarvestStarted( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - base.OnHarvestStarted( from, tool, def, toHarvest ); - - int tileID; - Map map; - Point3D loc; - - if ( GetHarvestDetails( from, tool, toHarvest, out tileID, out map, out loc ) ) - Timer.DelayCall( TimeSpan.FromSeconds( 1.5 ), - delegate - { - if ( Core.ML ) - from.RevealingAction(); - - Effects.SendLocationEffect( loc, map, 0x352D, 16, 4 ); - Effects.PlaySound( loc, map, 0x364 ); - } ); - } - - public override void OnHarvestFinished( Mobile from, Item tool, HarvestDefinition def, HarvestVein vein, HarvestBank bank, HarvestResource resource, object harvested ) - { - base.OnHarvestFinished( from, tool, def, vein, bank, resource, harvested ); - - if ( Core.ML ) - from.RevealingAction(); - } - - public override object GetLock( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - return this; - } - - public override bool BeginHarvesting( Mobile from, Item tool ) - { - if ( !base.BeginHarvesting( from, tool ) ) - return false; - - from.SendLocalizedMessage( 500974 ); // What water do you want to fish in? - return true; - } - - public override bool CheckHarvest( Mobile from, Item tool ) - { - if ( !base.CheckHarvest( from, tool ) ) - return false; - - if ( from.Mounted ) - { - from.SendLocalizedMessage( 500971 ); // You can't fish while riding! - return false; - } - - return true; - } - - public override bool CheckHarvest( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - if ( !base.CheckHarvest( from, tool, def, toHarvest ) ) - return false; - - if ( from.Mounted ) - { - from.SendLocalizedMessage( 500971 ); // You can't fish while riding! - return false; - } - - return true; - } - - private static int[] m_WaterTiles = { - 0x00A8, 0x00AB, - 0x0136, 0x0137, - 0x5797, 0x579C, - 0x746E, 0x7485, - 0x7490, 0x74AB, - 0x74B5, 0x75D5 - }; - } -} + public class Fishing : HarvestSystem + { + private static Fishing m_System; + + private static MutateEntry[] m_MutateTable = + { + new MutateEntry(80.0, 80.0, 4080.0, true, typeof(SpecialFishingNet)), + new MutateEntry(80.0, 80.0, 4080.0, true, typeof(BigFish)), + new MutateEntry(90.0, 80.0, 4080.0, true, typeof(TreasureMap)), + new MutateEntry(100.0, 80.0, 4080.0, true, typeof(MessageInABottle)), + new MutateEntry(0.0, 125.0, -2375.0, false, typeof(PrizedFish), typeof(WondrousFish), typeof(TrulyRareFish), + typeof(PeculiarFish)), + new MutateEntry(0.0, 105.0, -420.0, false, typeof(Boots), typeof(Shoes), typeof(Sandals), typeof(ThighBoots)), + new MutateEntry(0.0, 200.0, -200.0, false, new Type[1] { null }) + }; + + private static int[] m_WaterTiles = + { + 0x00A8, 0x00AB, + 0x0136, 0x0137, + 0x5797, 0x579C, + 0x746E, 0x7485, + 0x7490, 0x74AB, + 0x74B5, 0x75D5 + }; + + private Fishing() + { + HarvestResource[] res; + HarvestVein[] veins; + + #region Fishing + + HarvestDefinition fish = new HarvestDefinition(); + + // Resource banks are every 8x8 tiles + fish.BankWidth = 8; + fish.BankHeight = 8; + + // Every bank holds from 5 to 15 fish + fish.MinTotal = 5; + fish.MaxTotal = 15; + + // A resource bank will respawn its content every 10 to 20 minutes + fish.MinRespawn = TimeSpan.FromMinutes(10.0); + fish.MaxRespawn = TimeSpan.FromMinutes(20.0); + + // Skill checking is done on the Fishing skill + fish.Skill = SkillName.Fishing; + + // Set the list of harvestable tiles + fish.Tiles = m_WaterTiles; + fish.RangedTiles = true; + + // Players must be within 4 tiles to harvest + fish.MaxRange = 4; + + // One fish per harvest action + fish.ConsumedPerHarvest = 1; + fish.ConsumedPerFeluccaHarvest = 1; + + // The fishing + fish.EffectActions = new[] { 12 }; + fish.EffectSounds = new int[0]; + fish.EffectCounts = new[] { 1 }; + fish.EffectDelay = TimeSpan.Zero; + fish.EffectSoundDelay = TimeSpan.FromSeconds(8.0); + + fish.NoResourcesMessage = 503172; // The fish don't seem to be biting here. + fish.FailMessage = 503171; // You fish a while, but fail to catch anything. + fish.TimedOutOfRangeMessage = 500976; // You need to be closer to the water to fish! + fish.OutOfRangeMessage = 500976; // You need to be closer to the water to fish! + fish.PackFullMessage = 503176; // You do not have room in your backpack for a fish. + fish.ToolBrokeMessage = 503174; // You broke your fishing pole. + + res = new[] + { + new HarvestResource(00.0, 00.0, 100.0, 1043297, typeof(Fish)) + }; + + veins = new[] + { + new HarvestVein(100.0, 0.0, res[0], null) + }; + + fish.Resources = res; + fish.Veins = veins; + + if (Core.ML) + fish.BonusResources = new[] + { + new BonusHarvestResource(0, 99.4, null, null), //set to same chance as mining ml gems + new BonusHarvestResource(80.0, .6, 1072597, typeof(WhitePearl)) + }; + + Definition = fish; + Definitions.Add(fish); + + #endregion + } + + public static Fishing System + { + get + { + if (m_System == null) + m_System = new Fishing(); + + return m_System; + } + } + + public HarvestDefinition Definition{ get; } + + public override void OnConcurrentHarvest(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + from.SendLocalizedMessage(500972); // You are already fishing. + } + + public override bool SpecialHarvest(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; + + if (qs is CollectorQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FishPearlsObjective)); + + if (obj != null && !obj.Completed) + { + if (Utility.RandomDouble() < 0.5) + { + player.SendLocalizedMessage(1055086, "", + 0x59); // You pull a shellfish out of the water, and find a rainbow pearl inside of it. + + obj.CurProgress++; + } + else + { + player.SendLocalizedMessage(1055087, "", + 0x2C); // You pull a shellfish out of the water, but it doesn't have a rainbow pearl. + } + + return true; + } + } + } + + return false; + } + + public override Type MutateType(Type type, Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, + HarvestResource resource) + { + bool deepWater = SpecialFishingNet.FullValidation(map, loc.X, loc.Y); + + double skillBase = from.Skills[SkillName.Fishing].Base; + double skillValue = from.Skills[SkillName.Fishing].Value; + + for (int i = 0; i < m_MutateTable.Length; ++i) + { + MutateEntry entry = m_MutateTable[i]; + + if (!deepWater && entry.m_DeepWater) + continue; + + if (skillBase >= entry.m_ReqSkill) + { + double chance = (skillValue - entry.m_MinSkill) / (entry.m_MaxSkill - entry.m_MinSkill); + + if (chance > Utility.RandomDouble()) + return entry.m_Types[Utility.Random(entry.m_Types.Length)]; + } + } + + return type; + } + + private static Map SafeMap(Map map) + { + if (map == null || map == Map.Internal) + return Map.Trammel; + + return map; + } + + public override bool CheckResources(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, bool timed) + { + Container pack = from.Backpack; + + if (pack != null) + { + List messages = pack.FindItemsByType(); + + for (int i = 0; i < messages.Count; ++i) + { + SOS sos = messages[i]; + + if ((from.Map == Map.Felucca || from.Map == Map.Trammel) && from.InRange(sos.TargetLocation, 60)) + return true; + } + } + + return base.CheckResources(from, tool, def, map, loc, timed); + } + + public override Item Construct(Type type, Mobile from) + { + if (type == typeof(TreasureMap)) + { + int level; + if (from is PlayerMobile mobile && mobile.Young && mobile.Map == Map.Trammel && + TreasureMap.IsInHavenIsland(from)) + level = 0; + else + level = 1; + + return new TreasureMap(level, from.Map == Map.Felucca ? Map.Felucca : Map.Trammel); + } + + if (type == typeof(MessageInABottle)) + return new MessageInABottle(from.Map == Map.Felucca ? Map.Felucca : Map.Trammel); + + Container pack = from.Backpack; + + if (pack != null) + { + List messages = pack.FindItemsByType(); + + for (int i = 0; i < messages.Count; ++i) + { + SOS sos = messages[i]; + + if ((from.Map == Map.Felucca || from.Map == Map.Trammel) && from.InRange(sos.TargetLocation, 60)) + { + Item preLoot = null; + + switch (Utility.Random(8)) + { + case 0: // Body parts + { + int[] list = + { + 0x1CDD, 0x1CE5, // arm + 0x1CE0, 0x1CE8, // torso + 0x1CE1, 0x1CE9, // head + 0x1CE2, 0x1CEC // leg + }; + + preLoot = new ShipwreckedItem(Utility.RandomList(list)); + break; + } + case 1: // Bone parts + { + int[] list = + { + 0x1AE0, 0x1AE1, 0x1AE2, 0x1AE3, 0x1AE4, // skulls + 0x1B09, 0x1B0A, 0x1B0B, 0x1B0C, 0x1B0D, 0x1B0E, 0x1B0F, 0x1B10, // bone piles + 0x1B15, 0x1B16 // pelvis bones + }; + + preLoot = new ShipwreckedItem(Utility.RandomList(list)); + break; + } + case 2: // Paintings and portraits + { + preLoot = new ShipwreckedItem(Utility.Random(0xE9F, 10)); + break; + } + case 3: // Pillows + { + preLoot = new ShipwreckedItem(Utility.Random(0x13A4, 11)); + break; + } + case 4: // Shells + { + preLoot = new ShipwreckedItem(Utility.Random(0xFC4, 9)); + break; + } + case 5: //Hats + { + if (Utility.RandomBool()) + preLoot = new SkullCap(); + else + preLoot = new TricorneHat(); + + break; + } + case 6: // Misc + { + int[] list = + { + 0x1EB5, // unfinished barrel + 0xA2A, // stool + 0xC1F, // broken clock + 0x1047, 0x1048, // globe + 0x1EB1, 0x1EB2, 0x1EB3, 0x1EB4 // barrel staves + }; + + if (Utility.Random(list.Length + 1) == 0) + preLoot = new Candelabra(); + else + preLoot = new ShipwreckedItem(Utility.RandomList(list)); + + break; + } + } + + if (preLoot != null) + { + if (preLoot is IShipwreckedItem shipwreckedItem) + shipwreckedItem.IsShipwreckedItem = true; + + return preLoot; + } + + LockableContainer chest; + + if (Utility.RandomBool()) + chest = new MetalGoldenChest(); + else + chest = new WoodenChest(); + + if (sos.IsAncient) + chest.Hue = 0x481; + + TreasureMapChest.Fill(chest, Math.Max(1, Math.Min(4, sos.Level))); + + if (sos.IsAncient) + chest.DropItem(new FabledFishingNet()); + else + chest.DropItem(new SpecialFishingNet()); + + chest.Movable = true; + chest.Locked = false; + chest.TrapType = TrapType.None; + chest.TrapPower = 0; + chest.TrapLevel = 0; + + sos.Delete(); + + return chest; + } + } + } + + return base.Construct(type, from); + } + + public override bool Give(Mobile m, Item item, bool placeAtFeet) + { + if (item is TreasureMap || item is MessageInABottle || item is SpecialFishingNet) + { + BaseCreature serp; + + if (0.25 > Utility.RandomDouble()) + serp = new DeepSeaSerpent(); + else + serp = new SeaSerpent(); + + int x = m.X, y = m.Y; + + Map map = m.Map; + + for (int i = 0; map != null && i < 20; ++i) + { + int tx = m.X - 10 + Utility.Random(21); + int ty = m.Y - 10 + Utility.Random(21); + + LandTile t = map.Tiles.GetLandTile(tx, ty); + + if (t.Z == -5 && (t.ID >= 0xA8 && t.ID <= 0xAB || t.ID >= 0x136 && t.ID <= 0x137) && + !SpellHelper.CheckMulti(new Point3D(tx, ty, -5), map)) + { + x = tx; + y = ty; + break; + } + } + + serp.MoveToWorld(new Point3D(x, y, -5), map); + + serp.Home = serp.Location; + serp.RangeHome = 10; + + serp.PackItem(item); + + m.SendLocalizedMessage(503170); // Uh oh! That doesn't look like a fish! + + return true; // we don't want to give the item to the player, it's on the serpent + } + + if (item is BigFish || item is WoodenChest || item is MetalGoldenChest) + placeAtFeet = true; + + return base.Give(m, item, placeAtFeet); + } + + public override void SendSuccessTo(Mobile from, Item item, HarvestResource resource) + { + if (item is BigFish fish) + { + from.SendLocalizedMessage(1042635); // Your fishing pole bends as you pull a big fish from the depths! + fish.Fisher = from; + } + else if (item is WoodenChest || item is MetalGoldenChest) + { + from.SendLocalizedMessage(503175); // You pull up a heavy chest from the depths of the ocean! + } + else + { + int number; + string name; + + if (item is BaseMagicFish) + { + number = 1008124; + name = "a mess of small fish"; + } + else if (item is Fish) + { + number = 1008124; + name = item.ItemData.Name; + } + else if (item is BaseShoes) + { + number = 1008124; + name = item.ItemData.Name; + } + else if (item is TreasureMap) + { + number = 1008125; + name = "a sodden piece of parchment"; + } + else if (item is MessageInABottle) + { + number = 1008125; + name = "a bottle, with a message in it"; + } + else if (item is SpecialFishingNet) + { + number = 1008125; + name = "a special fishing net"; // TODO: this is just a guess--what should it really be named? + } + else + { + number = 1043297; + + if ((item.ItemData.Flags & TileFlag.ArticleA) != 0) + name = "a " + item.ItemData.Name; + else if ((item.ItemData.Flags & TileFlag.ArticleAn) != 0) + name = "an " + item.ItemData.Name; + else + name = item.ItemData.Name; + } + + NetState ns = from.NetState; + + if (ns == null) + return; + + if (number == 1043297 || ns.HighSeas) + from.SendLocalizedMessage(number, name); + else + from.SendLocalizedMessage(number, true, name); + } + } + + public override void OnHarvestStarted(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + base.OnHarvestStarted(from, tool, def, toHarvest); + + int tileID; + Map map; + Point3D loc; + + if (GetHarvestDetails(from, tool, toHarvest, out tileID, out map, out loc)) + Timer.DelayCall(TimeSpan.FromSeconds(1.5), + delegate + { + if (Core.ML) + from.RevealingAction(); + + Effects.SendLocationEffect(loc, map, 0x352D, 16, 4); + Effects.PlaySound(loc, map, 0x364); + }); + } + + public override void OnHarvestFinished(Mobile from, Item tool, HarvestDefinition def, HarvestVein vein, + HarvestBank bank, HarvestResource resource, object harvested) + { + base.OnHarvestFinished(from, tool, def, vein, bank, resource, harvested); + + if (Core.ML) + from.RevealingAction(); + } + + public override object GetLock(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + return this; + } + + public override bool BeginHarvesting(Mobile from, Item tool) + { + if (!base.BeginHarvesting(from, tool)) + return false; + + from.SendLocalizedMessage(500974); // What water do you want to fish in? + return true; + } + + public override bool CheckHarvest(Mobile from, Item tool) + { + if (!base.CheckHarvest(from, tool)) + return false; + + if (from.Mounted) + { + from.SendLocalizedMessage(500971); // You can't fish while riding! + return false; + } + + return true; + } + + public override bool CheckHarvest(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + if (!base.CheckHarvest(from, tool, def, toHarvest)) + return false; + + if (from.Mounted) + { + from.SendLocalizedMessage(500971); // You can't fish while riding! + return false; + } + + return true; + } + + private class MutateEntry + { + public bool m_DeepWater; + public double m_ReqSkill, m_MinSkill, m_MaxSkill; + public Type[] m_Types; + + public MutateEntry(double reqSkill, double minSkill, double maxSkill, bool deepWater, params Type[] types) + { + m_ReqSkill = reqSkill; + m_MinSkill = minSkill; + m_MaxSkill = maxSkill; + m_DeepWater = deepWater; + m_Types = types; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Lumberjacking.cs b/Scripts/Engines/Harvest/Lumberjacking.cs index 21cd1e70d..4219a96e5 100644 --- a/Scripts/Engines/Harvest/Lumberjacking.cs +++ b/Scripts/Engines/Harvest/Lumberjacking.cs @@ -1,208 +1,215 @@ using System; using Server.Items; using Server.Network; +using Server.Targeting; namespace Server.Engines.Harvest { - public class Lumberjacking : HarvestSystem - { - private static Lumberjacking m_System; + public class Lumberjacking : HarvestSystem + { + private static Lumberjacking m_System; - public static Lumberjacking System - { - get - { - if ( m_System == null ) - m_System = new Lumberjacking(); + #region Tile lists - return m_System; - } - } + private static int[] m_TreeTiles = + { + 0x4CCA, 0x4CCB, 0x4CCC, 0x4CCD, 0x4CD0, 0x4CD3, 0x4CD6, 0x4CD8, + 0x4CDA, 0x4CDD, 0x4CE0, 0x4CE3, 0x4CE6, 0x4CF8, 0x4CFB, 0x4CFE, + 0x4D01, 0x4D41, 0x4D42, 0x4D43, 0x4D44, 0x4D57, 0x4D58, 0x4D59, + 0x4D5A, 0x4D5B, 0x4D6E, 0x4D6F, 0x4D70, 0x4D71, 0x4D72, 0x4D84, + 0x4D85, 0x4D86, 0x52B5, 0x52B6, 0x52B7, 0x52B8, 0x52B9, 0x52BA, + 0x52BB, 0x52BC, 0x52BD, - public HarvestDefinition Definition { get; } + 0x4CCE, 0x4CCF, 0x4CD1, 0x4CD2, 0x4CD4, 0x4CD5, 0x4CD7, 0x4CD9, + 0x4CDB, 0x4CDC, 0x4CDE, 0x4CDF, 0x4CE1, 0x4CE2, 0x4CE4, 0x4CE5, + 0x4CE7, 0x4CE8, 0x4CF9, 0x4CFA, 0x4CFC, 0x4CFD, 0x4CFF, 0x4D00, + 0x4D02, 0x4D03, 0x4D45, 0x4D46, 0x4D47, 0x4D48, 0x4D49, 0x4D4A, + 0x4D4B, 0x4D4C, 0x4D4D, 0x4D4E, 0x4D4F, 0x4D50, 0x4D51, 0x4D52, + 0x4D53, 0x4D5C, 0x4D5D, 0x4D5E, 0x4D5F, 0x4D60, 0x4D61, 0x4D62, + 0x4D63, 0x4D64, 0x4D65, 0x4D66, 0x4D67, 0x4D68, 0x4D69, 0x4D73, + 0x4D74, 0x4D75, 0x4D76, 0x4D77, 0x4D78, 0x4D79, 0x4D7A, 0x4D7B, + 0x4D7C, 0x4D7D, 0x4D7E, 0x4D7F, 0x4D87, 0x4D88, 0x4D89, 0x4D8A, + 0x4D8B, 0x4D8C, 0x4D8D, 0x4D8E, 0x4D8F, 0x4D90, 0x4D95, 0x4D96, + 0x4D97, 0x4D99, 0x4D9A, 0x4D9B, 0x4D9D, 0x4D9E, 0x4D9F, 0x4DA1, + 0x4DA2, 0x4DA3, 0x4DA5, 0x4DA6, 0x4DA7, 0x4DA9, 0x4DAA, 0x4DAB, + 0x52BE, 0x52BF, 0x52C0, 0x52C1, 0x52C2, 0x52C3, 0x52C4, 0x52C5, + 0x52C6, 0x52C7 + }; - private Lumberjacking() - { - HarvestResource[] res; - HarvestVein[] veins; + #endregion - #region Lumberjacking - HarvestDefinition lumber = new HarvestDefinition(); + private Lumberjacking() + { + HarvestResource[] res; + HarvestVein[] veins; - // Resource banks are every 4x3 tiles - lumber.BankWidth = 4; - lumber.BankHeight = 3; + #region Lumberjacking - // Every bank holds from 20 to 45 logs - lumber.MinTotal = 20; - lumber.MaxTotal = 45; + HarvestDefinition lumber = new HarvestDefinition(); - // A resource bank will respawn its content every 20 to 30 minutes - lumber.MinRespawn = TimeSpan.FromMinutes( 20.0 ); - lumber.MaxRespawn = TimeSpan.FromMinutes( 30.0 ); + // Resource banks are every 4x3 tiles + lumber.BankWidth = 4; + lumber.BankHeight = 3; - // Skill checking is done on the Lumberjacking skill - lumber.Skill = SkillName.Lumberjacking; + // Every bank holds from 20 to 45 logs + lumber.MinTotal = 20; + lumber.MaxTotal = 45; - // Set the list of harvestable tiles - lumber.Tiles = m_TreeTiles; + // A resource bank will respawn its content every 20 to 30 minutes + lumber.MinRespawn = TimeSpan.FromMinutes(20.0); + lumber.MaxRespawn = TimeSpan.FromMinutes(30.0); - // Players must be within 2 tiles to harvest - lumber.MaxRange = 2; + // Skill checking is done on the Lumberjacking skill + lumber.Skill = SkillName.Lumberjacking; - // Ten logs per harvest action - lumber.ConsumedPerHarvest = 10; - lumber.ConsumedPerFeluccaHarvest = 20; + // Set the list of harvestable tiles + lumber.Tiles = m_TreeTiles; - // The chopping effect - lumber.EffectActions = new[]{ 13 }; - lumber.EffectSounds = new[]{ 0x13E }; - lumber.EffectCounts = (Core.AOS ? new[]{ 1 } : new[]{ 1, 2, 2, 2, 3 }); - lumber.EffectDelay = TimeSpan.FromSeconds( 1.6 ); - lumber.EffectSoundDelay = TimeSpan.FromSeconds( 0.9 ); + // Players must be within 2 tiles to harvest + lumber.MaxRange = 2; - lumber.NoResourcesMessage = 500493; // There's not enough wood here to harvest. - lumber.FailMessage = 500495; // You hack at the tree for a while, but fail to produce any useable wood. - lumber.OutOfRangeMessage = 500446; // That is too far away. - lumber.PackFullMessage = 500497; // You can't place any wood into your backpack! - lumber.ToolBrokeMessage = 500499; // You broke your axe. + // Ten logs per harvest action + lumber.ConsumedPerHarvest = 10; + lumber.ConsumedPerFeluccaHarvest = 20; - if ( Core.ML ) - { - res = new[] - { - new HarvestResource( 00.0, 00.0, 100.0, 1072540, typeof( Log ) ), - new HarvestResource( 65.0, 25.0, 105.0, 1072541, typeof( OakLog ) ), - new HarvestResource( 80.0, 40.0, 120.0, 1072542, typeof( AshLog ) ), - new HarvestResource( 95.0, 55.0, 135.0, 1072543, typeof( YewLog ) ), - new HarvestResource( 100.0, 60.0, 140.0, 1072544, typeof( HeartwoodLog ) ), - new HarvestResource( 100.0, 60.0, 140.0, 1072545, typeof( BloodwoodLog ) ), - new HarvestResource( 100.0, 60.0, 140.0, 1072546, typeof( FrostwoodLog ) ), - }; + // The chopping effect + lumber.EffectActions = new[] { 13 }; + lumber.EffectSounds = new[] { 0x13E }; + lumber.EffectCounts = Core.AOS ? new[] { 1 } : new[] { 1, 2, 2, 2, 3 }; + lumber.EffectDelay = TimeSpan.FromSeconds(1.6); + lumber.EffectSoundDelay = TimeSpan.FromSeconds(0.9); + + lumber.NoResourcesMessage = 500493; // There's not enough wood here to harvest. + lumber.FailMessage = 500495; // You hack at the tree for a while, but fail to produce any useable wood. + lumber.OutOfRangeMessage = 500446; // That is too far away. + lumber.PackFullMessage = 500497; // You can't place any wood into your backpack! + lumber.ToolBrokeMessage = 500499; // You broke your axe. + + if (Core.ML) + { + res = new[] + { + new HarvestResource(00.0, 00.0, 100.0, 1072540, typeof(Log)), + new HarvestResource(65.0, 25.0, 105.0, 1072541, typeof(OakLog)), + new HarvestResource(80.0, 40.0, 120.0, 1072542, typeof(AshLog)), + new HarvestResource(95.0, 55.0, 135.0, 1072543, typeof(YewLog)), + new HarvestResource(100.0, 60.0, 140.0, 1072544, typeof(HeartwoodLog)), + new HarvestResource(100.0, 60.0, 140.0, 1072545, typeof(BloodwoodLog)), + new HarvestResource(100.0, 60.0, 140.0, 1072546, typeof(FrostwoodLog)) + }; - veins = new[] - { - new HarvestVein( 49.0, 0.0, res[0], null ), // Ordinary Logs - new HarvestVein( 30.0, 0.5, res[1], res[0] ), // Oak - new HarvestVein( 10.0, 0.5, res[2], res[0] ), // Ash - new HarvestVein( 05.0, 0.5, res[3], res[0] ), // Yew - new HarvestVein( 03.0, 0.5, res[4], res[0] ), // Heartwood - new HarvestVein( 02.0, 0.5, res[5], res[0] ), // Bloodwood - new HarvestVein( 01.0, 0.5, res[6], res[0] ), // Frostwood - }; + veins = new[] + { + new HarvestVein(49.0, 0.0, res[0], null), // Ordinary Logs + new HarvestVein(30.0, 0.5, res[1], res[0]), // Oak + new HarvestVein(10.0, 0.5, res[2], res[0]), // Ash + new HarvestVein(05.0, 0.5, res[3], res[0]), // Yew + new HarvestVein(03.0, 0.5, res[4], res[0]), // Heartwood + new HarvestVein(02.0, 0.5, res[5], res[0]), // Bloodwood + new HarvestVein(01.0, 0.5, res[6], res[0]) // Frostwood + }; - lumber.BonusResources = new[] - { - new BonusHarvestResource( 0, 83.9, null, null ), //Nothing - new BonusHarvestResource( 100, 10.0, 1072548, typeof( BarkFragment ) ), - new BonusHarvestResource( 100, 03.0, 1072550, typeof( LuminescentFungi ) ), - new BonusHarvestResource( 100, 02.0, 1072547, typeof( SwitchItem ) ), - new BonusHarvestResource( 100, 01.0, 1072549, typeof( ParasiticPlant ) ), - new BonusHarvestResource( 100, 00.1, 1072551, typeof( BrilliantAmber ) ) - }; - } - else - { - res = new[] - { - new HarvestResource( 00.0, 00.0, 100.0, 500498, typeof( Log ) ) - }; + lumber.BonusResources = new[] + { + new BonusHarvestResource(0, 83.9, null, null), //Nothing + new BonusHarvestResource(100, 10.0, 1072548, typeof(BarkFragment)), + new BonusHarvestResource(100, 03.0, 1072550, typeof(LuminescentFungi)), + new BonusHarvestResource(100, 02.0, 1072547, typeof(SwitchItem)), + new BonusHarvestResource(100, 01.0, 1072549, typeof(ParasiticPlant)), + new BonusHarvestResource(100, 00.1, 1072551, typeof(BrilliantAmber)) + }; + } + else + { + res = new[] + { + new HarvestResource(00.0, 00.0, 100.0, 500498, typeof(Log)) + }; - veins = new[] - { - new HarvestVein( 100.0, 0.0, res[0], null ) - }; - } + veins = new[] + { + new HarvestVein(100.0, 0.0, res[0], null) + }; + } - lumber.Resources = res; - lumber.Veins = veins; + lumber.Resources = res; + lumber.Veins = veins; - lumber.RaceBonus = Core.ML; - lumber.RandomizeVeins = Core.ML; + lumber.RaceBonus = Core.ML; + lumber.RandomizeVeins = Core.ML; - Definition = lumber; - Definitions.Add( lumber ); - #endregion - } + Definition = lumber; + Definitions.Add(lumber); - public override bool CheckHarvest( Mobile from, Item tool ) - { - if ( !base.CheckHarvest( from, tool ) ) - return false; + #endregion + } - if ( tool.Parent != from ) - { - from.SendLocalizedMessage( 500487 ); // The axe must be equipped for any serious wood chopping. - return false; - } + public static Lumberjacking System + { + get + { + if (m_System == null) + m_System = new Lumberjacking(); - return true; - } + return m_System; + } + } - public override bool CheckHarvest( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - if ( !base.CheckHarvest( from, tool, def, toHarvest ) ) - return false; + public HarvestDefinition Definition{ get; } - if ( tool.Parent != from ) - { - from.SendLocalizedMessage( 500487 ); // The axe must be equipped for any serious wood chopping. - return false; - } + public override bool CheckHarvest(Mobile from, Item tool) + { + if (!base.CheckHarvest(from, tool)) + return false; - return true; - } + if (tool.Parent != from) + { + from.SendLocalizedMessage(500487); // The axe must be equipped for any serious wood chopping. + return false; + } - public override void OnBadHarvestTarget( Mobile from, Item tool, object toHarvest ) - { - if ( toHarvest is Mobile mobile ) - mobile.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500450, from.NetState ); // You can only skin dead creatures. - else if ( toHarvest is Item item ) - item.LabelTo( from, 500464 ); // Use this on corpses to carve away meat and hide - else if ( toHarvest is Targeting.StaticTarget || toHarvest is Targeting.LandTarget ) - from.SendLocalizedMessage( 500489 ); // You can't use an axe on that. - else - from.SendLocalizedMessage( 1005213 ); // You can't do that - } + return true; + } - public override void OnHarvestStarted( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - base.OnHarvestStarted( from, tool, def, toHarvest ); + public override bool CheckHarvest(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + if (!base.CheckHarvest(from, tool, def, toHarvest)) + return false; - if ( Core.ML ) - from.RevealingAction(); - } + if (tool.Parent != from) + { + from.SendLocalizedMessage(500487); // The axe must be equipped for any serious wood chopping. + return false; + } - public static void Initialize() - { - Array.Sort( m_TreeTiles ); - } + return true; + } - #region Tile lists - private static int[] m_TreeTiles = { - 0x4CCA, 0x4CCB, 0x4CCC, 0x4CCD, 0x4CD0, 0x4CD3, 0x4CD6, 0x4CD8, - 0x4CDA, 0x4CDD, 0x4CE0, 0x4CE3, 0x4CE6, 0x4CF8, 0x4CFB, 0x4CFE, - 0x4D01, 0x4D41, 0x4D42, 0x4D43, 0x4D44, 0x4D57, 0x4D58, 0x4D59, - 0x4D5A, 0x4D5B, 0x4D6E, 0x4D6F, 0x4D70, 0x4D71, 0x4D72, 0x4D84, - 0x4D85, 0x4D86, 0x52B5, 0x52B6, 0x52B7, 0x52B8, 0x52B9, 0x52BA, - 0x52BB, 0x52BC, 0x52BD, + public override void OnBadHarvestTarget(Mobile from, Item tool, object toHarvest) + { + if (toHarvest is Mobile mobile) + mobile.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500450, + from.NetState); // You can only skin dead creatures. + else if (toHarvest is Item item) + item.LabelTo(from, 500464); // Use this on corpses to carve away meat and hide + else if (toHarvest is StaticTarget || toHarvest is LandTarget) + from.SendLocalizedMessage(500489); // You can't use an axe on that. + else + from.SendLocalizedMessage(1005213); // You can't do that + } - 0x4CCE, 0x4CCF, 0x4CD1, 0x4CD2, 0x4CD4, 0x4CD5, 0x4CD7, 0x4CD9, - 0x4CDB, 0x4CDC, 0x4CDE, 0x4CDF, 0x4CE1, 0x4CE2, 0x4CE4, 0x4CE5, - 0x4CE7, 0x4CE8, 0x4CF9, 0x4CFA, 0x4CFC, 0x4CFD, 0x4CFF, 0x4D00, - 0x4D02, 0x4D03, 0x4D45, 0x4D46, 0x4D47, 0x4D48, 0x4D49, 0x4D4A, - 0x4D4B, 0x4D4C, 0x4D4D, 0x4D4E, 0x4D4F, 0x4D50, 0x4D51, 0x4D52, - 0x4D53, 0x4D5C, 0x4D5D, 0x4D5E, 0x4D5F, 0x4D60, 0x4D61, 0x4D62, - 0x4D63, 0x4D64, 0x4D65, 0x4D66, 0x4D67, 0x4D68, 0x4D69, 0x4D73, - 0x4D74, 0x4D75, 0x4D76, 0x4D77, 0x4D78, 0x4D79, 0x4D7A, 0x4D7B, - 0x4D7C, 0x4D7D, 0x4D7E, 0x4D7F, 0x4D87, 0x4D88, 0x4D89, 0x4D8A, - 0x4D8B, 0x4D8C, 0x4D8D, 0x4D8E, 0x4D8F, 0x4D90, 0x4D95, 0x4D96, - 0x4D97, 0x4D99, 0x4D9A, 0x4D9B, 0x4D9D, 0x4D9E, 0x4D9F, 0x4DA1, - 0x4DA2, 0x4DA3, 0x4DA5, 0x4DA6, 0x4DA7, 0x4DA9, 0x4DAA, 0x4DAB, - 0x52BE, 0x52BF, 0x52C0, 0x52C1, 0x52C2, 0x52C3, 0x52C4, 0x52C5, - 0x52C6, 0x52C7 - }; - #endregion - } -} + public override void OnHarvestStarted(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + base.OnHarvestStarted(from, tool, def, toHarvest); + + if (Core.ML) + from.RevealingAction(); + } + + public static void Initialize() + { + Array.Sort(m_TreeTiles); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Harvest/Mining.cs b/Scripts/Engines/Harvest/Mining.cs index e49364fc9..1d2e9b2c6 100644 --- a/Scripts/Engines/Harvest/Mining.cs +++ b/Scripts/Engines/Harvest/Mining.cs @@ -5,413 +5,433 @@ using Server.Targeting; namespace Server.Engines.Harvest { - public class Mining : HarvestSystem - { - private static Mining m_System; - - public static Mining System - { - get - { - if ( m_System == null ) - m_System = new Mining(); - - return m_System; - } - } - - public HarvestDefinition OreAndStone { get; } - - public HarvestDefinition Sand { get; } - - private Mining() - { - HarvestResource[] res; - HarvestVein[] veins; - - #region Mining for ore and stone - HarvestDefinition oreAndStone = OreAndStone = new HarvestDefinition(); - - // Resource banks are every 8x8 tiles - oreAndStone.BankWidth = 8; - oreAndStone.BankHeight = 8; - - // Every bank holds from 10 to 34 ore - oreAndStone.MinTotal = 10; - oreAndStone.MaxTotal = 34; - - // A resource bank will respawn its content every 10 to 20 minutes - oreAndStone.MinRespawn = TimeSpan.FromMinutes( 10.0 ); - oreAndStone.MaxRespawn = TimeSpan.FromMinutes( 20.0 ); - - // Skill checking is done on the Mining skill - oreAndStone.Skill = SkillName.Mining; - - // Set the list of harvestable tiles - oreAndStone.Tiles = m_MountainAndCaveTiles; - - // Players must be within 2 tiles to harvest - oreAndStone.MaxRange = 2; - - // One ore per harvest action - oreAndStone.ConsumedPerHarvest = 1; - oreAndStone.ConsumedPerFeluccaHarvest = 2; - - // The digging effect - oreAndStone.EffectActions = new[]{ 11 }; - oreAndStone.EffectSounds = new[]{ 0x125, 0x126 }; - oreAndStone.EffectCounts = new[]{ 1 }; - oreAndStone.EffectDelay = TimeSpan.FromSeconds( 1.6 ); - oreAndStone.EffectSoundDelay = TimeSpan.FromSeconds( 0.9 ); - - oreAndStone.NoResourcesMessage = 503040; // There is no metal here to mine. - oreAndStone.DoubleHarvestMessage = 503042; // Someone has gotten to the metal before you. - oreAndStone.TimedOutOfRangeMessage = 503041; // You have moved too far away to continue mining. - oreAndStone.OutOfRangeMessage = 500446; // That is too far away. - oreAndStone.FailMessage = 503043; // You loosen some rocks but fail to find any useable ore. - oreAndStone.PackFullMessage = 1010481; // Your backpack is full, so the ore you mined is lost. - oreAndStone.ToolBrokeMessage = 1044038; // You have worn out your tool! - - res = new[] - { - new HarvestResource( 00.0, 00.0, 100.0, 1007072, typeof( IronOre ), typeof( Granite ) ), - new HarvestResource( 65.0, 25.0, 105.0, 1007073, typeof( DullCopperOre ), typeof( DullCopperGranite ), typeof( DullCopperElemental ) ), - new HarvestResource( 70.0, 30.0, 110.0, 1007074, typeof( ShadowIronOre ), typeof( ShadowIronGranite ), typeof( ShadowIronElemental ) ), - new HarvestResource( 75.0, 35.0, 115.0, 1007075, typeof( CopperOre ), typeof( CopperGranite ), typeof( CopperElemental ) ), - new HarvestResource( 80.0, 40.0, 120.0, 1007076, typeof( BronzeOre ), typeof( BronzeGranite ), typeof( BronzeElemental ) ), - new HarvestResource( 85.0, 45.0, 125.0, 1007077, typeof( GoldOre ), typeof( GoldGranite ), typeof( GoldenElemental ) ), - new HarvestResource( 90.0, 50.0, 130.0, 1007078, typeof( AgapiteOre ), typeof( AgapiteGranite ), typeof( AgapiteElemental ) ), - new HarvestResource( 95.0, 55.0, 135.0, 1007079, typeof( VeriteOre ), typeof( VeriteGranite ), typeof( VeriteElemental ) ), - new HarvestResource( 99.0, 59.0, 139.0, 1007080, typeof( ValoriteOre ), typeof( ValoriteGranite ), typeof( ValoriteElemental ) ) - }; - - veins = new[] - { - new HarvestVein( 49.6, 0.0, res[0], null ), // Iron - new HarvestVein( 11.2, 0.5, res[1], res[0] ), // Dull Copper - new HarvestVein( 09.8, 0.5, res[2], res[0] ), // Shadow Iron - new HarvestVein( 08.4, 0.5, res[3], res[0] ), // Copper - new HarvestVein( 07.0, 0.5, res[4], res[0] ), // Bronze - new HarvestVein( 05.6, 0.5, res[5], res[0] ), // Gold - new HarvestVein( 04.2, 0.5, res[6], res[0] ), // Agapite - new HarvestVein( 02.8, 0.5, res[7], res[0] ), // Verite - new HarvestVein( 01.4, 0.5, res[8], res[0] ) // Valorite - }; - - oreAndStone.Resources = res; - oreAndStone.Veins = veins; - - if ( Core.ML ) - { - oreAndStone.BonusResources = new[] - { - new BonusHarvestResource( 0, 99.4, null, null ), //Nothing - new BonusHarvestResource( 100, .1, 1072562, typeof( BlueDiamond ) ), - new BonusHarvestResource( 100, .1, 1072567, typeof( DarkSapphire ) ), - new BonusHarvestResource( 100, .1, 1072570, typeof( EcruCitrine ) ), - new BonusHarvestResource( 100, .1, 1072564, typeof( FireRuby ) ), - new BonusHarvestResource( 100, .1, 1072566, typeof( PerfectEmerald ) ), - new BonusHarvestResource( 100, .1, 1072568, typeof( Turquoise ) ) - }; - } - - oreAndStone.RaceBonus = Core.ML; - oreAndStone.RandomizeVeins = Core.ML; - - Definitions.Add( oreAndStone ); - #endregion - - #region Mining for sand - HarvestDefinition sand = Sand = new HarvestDefinition(); - - // Resource banks are every 8x8 tiles - sand.BankWidth = 8; - sand.BankHeight = 8; - - // Every bank holds from 6 to 12 sand - sand.MinTotal = 6; - sand.MaxTotal = 12; - - // A resource bank will respawn its content every 10 to 20 minutes - sand.MinRespawn = TimeSpan.FromMinutes( 10.0 ); - sand.MaxRespawn = TimeSpan.FromMinutes( 20.0 ); - - // Skill checking is done on the Mining skill - sand.Skill = SkillName.Mining; - - // Set the list of harvestable tiles - sand.Tiles = m_SandTiles; - - // Players must be within 2 tiles to harvest - sand.MaxRange = 2; - - // One sand per harvest action - sand.ConsumedPerHarvest = 1; - sand.ConsumedPerFeluccaHarvest = 1; - - // The digging effect - sand.EffectActions = new[]{ 11 }; - sand.EffectSounds = new[]{ 0x125, 0x126 }; - sand.EffectCounts = new[]{ 6 }; - sand.EffectDelay = TimeSpan.FromSeconds( 1.6 ); - sand.EffectSoundDelay = TimeSpan.FromSeconds( 0.9 ); - - sand.NoResourcesMessage = 1044629; // There is no sand here to mine. - sand.DoubleHarvestMessage = 1044629; // There is no sand here to mine. - sand.TimedOutOfRangeMessage = 503041; // You have moved too far away to continue mining. - sand.OutOfRangeMessage = 500446; // That is too far away. - sand.FailMessage = 1044630; // You dig for a while but fail to find any of sufficient quality for glassblowing. - sand.PackFullMessage = 1044632; // Your backpack can't hold the sand, and it is lost! - sand.ToolBrokeMessage = 1044038; // You have worn out your tool! - - res = new[] - { - new HarvestResource( 100.0, 70.0, 400.0, 1044631, typeof( Sand ) ) - }; - - veins = new[] - { - new HarvestVein( 100.0, 0.0, res[0], null ) - }; - - sand.Resources = res; - sand.Veins = veins; - - Definitions.Add( sand ); - #endregion - } - - public override Type GetResourceType( Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, HarvestResource resource ) - { - if ( def == OreAndStone ) - { - if ( from is PlayerMobile pm && pm.StoneMining && pm.ToggleMiningStone && from.Skills[SkillName.Mining].Base >= 100.0 && 0.1 > Utility.RandomDouble() ) - return resource.Types[1]; - - return resource.Types[0]; - } - - return base.GetResourceType( from, tool, def, map, loc, resource ); - } - - public override bool CheckHarvest( Mobile from, Item tool ) - { - if ( !base.CheckHarvest( from, tool ) ) - return false; - - if ( from.Mounted ) - { - from.SendLocalizedMessage( 501864 ); // You can't mine while riding. - return false; - } - - if ( from.IsBodyMod && !from.Body.IsHuman ) - { - from.SendLocalizedMessage( 501865 ); // You can't mine while polymorphed. - return false; - } - - return true; - } - - public override void SendSuccessTo( Mobile from, Item item, HarvestResource resource ) - { - if ( item is BaseGranite ) - from.SendLocalizedMessage( 1044606 ); // You carefully extract some workable stone from the ore vein! - else - base.SendSuccessTo( from, item, resource ); - } - - public override bool CheckHarvest( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - if ( !base.CheckHarvest( from, tool, def, toHarvest ) ) - return false; - - if ( def == Sand && !(from is PlayerMobile mobile && mobile.Skills[SkillName.Mining].Base >= 100.0 && mobile.SandMining) ) - { - OnBadHarvestTarget( from, tool, toHarvest ); - return false; - } - if ( from.Mounted ) - { - from.SendLocalizedMessage( 501864 ); // You can't mine while riding. - return false; - } - if ( from.IsBodyMod && !from.Body.IsHuman ) - { - from.SendLocalizedMessage( 501865 ); // You can't mine while polymorphed. - return false; - } - - return true; - } - - public override HarvestVein MutateVein( Mobile from, Item tool, HarvestDefinition def, HarvestBank bank, object toHarvest, HarvestVein vein ) - { - if ( tool is GargoylesPickaxe && def == OreAndStone ) - { - int veinIndex = Array.IndexOf( def.Veins, vein ); - - if ( veinIndex >= 0 && veinIndex < (def.Veins.Length - 1) ) - return def.Veins[veinIndex + 1]; - } - - return base.MutateVein( from, tool, def, bank, toHarvest, vein ); - } - - private static int[] m_Offsets = { - -1, -1, - -1, 0, - -1, 1, - 0, -1, - 0, 1, - 1, -1, - 1, 0, - 1, 1 - }; - - public override void OnHarvestFinished( Mobile from, Item tool, HarvestDefinition def, HarvestVein vein, HarvestBank bank, HarvestResource resource, object harvested ) - { - if ( tool is GargoylesPickaxe && def == OreAndStone && 0.1 > Utility.RandomDouble() ) - { - HarvestResource res = vein.PrimaryResource; - - if ( res == resource && res.Types.Length >= 3 ) - { - try - { - Map map = from.Map; - - if ( map == null ) - return; - - if ( Activator.CreateInstance( res.Types[2], new object[]{ 25 } ) is BaseCreature spawned ) - { - int offset = Utility.Random( 8 ) * 2; - - for ( int i = 0; i < m_Offsets.Length; i += 2 ) - { - int x = from.X + m_Offsets[(offset + i) % m_Offsets.Length]; - int y = from.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; - - if ( map.CanSpawnMobile( x, y, from.Z ) ) - { - spawned.OnBeforeSpawn( new Point3D( x, y, from.Z ), map ); - spawned.MoveToWorld( new Point3D( x, y, from.Z ), map ); - spawned.Combatant = from; - return; - } - - int z = map.GetAverageZ( x, y ); - - if ( Math.Abs( z - from.Z ) < 10 && map.CanSpawnMobile( x, y, z ) ) - { - spawned.OnBeforeSpawn( new Point3D( x, y, z ), map ); - spawned.MoveToWorld( new Point3D( x, y, z ), map ); - spawned.Combatant = from; - return; - } - } - - spawned.OnBeforeSpawn( from.Location, from.Map ); - spawned.MoveToWorld( from.Location, from.Map ); - spawned.Combatant = from; - } - } - catch - { - } - } - } - } - - public override bool BeginHarvesting( Mobile from, Item tool ) - { - if ( !base.BeginHarvesting( from, tool ) ) - return false; - - from.SendLocalizedMessage( 503033 ); // Where do you wish to dig? - return true; - } - - public override void OnHarvestStarted( Mobile from, Item tool, HarvestDefinition def, object toHarvest ) - { - base.OnHarvestStarted( from, tool, def, toHarvest ); - - if ( Core.ML ) - from.RevealingAction(); - } - - public override void OnBadHarvestTarget( Mobile from, Item tool, object toHarvest ) - { - if ( toHarvest is LandTarget ) - from.SendLocalizedMessage( 501862 ); // You can't mine there. - else - from.SendLocalizedMessage( 501863 ); // You can't mine that. - } - - #region Tile lists - private static int[] m_MountainAndCaveTiles = { - 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, - 230, 231, 236, 237, 238, 239, 240, 241, 242, 243, - 244, 245, 246, 247, 252, 253, 254, 255, 256, 257, - 258, 259, 260, 261, 262, 263, 268, 269, 270, 271, - 272, 273, 274, 275, 276, 277, 278, 279, 286, 287, - 288, 289, 290, 291, 292, 293, 294, 296, 296, 297, - 321, 322, 323, 324, 467, 468, 469, 470, 471, 472, - 473, 474, 476, 477, 478, 479, 480, 481, 482, 483, - 484, 485, 486, 487, 492, 493, 494, 495, 543, 544, - 545, 546, 547, 548, 549, 550, 551, 552, 553, 554, - 555, 556, 557, 558, 559, 560, 561, 562, 563, 564, - 565, 566, 567, 568, 569, 570, 571, 572, 573, 574, - 575, 576, 577, 578, 579, 581, 582, 583, 584, 585, - 586, 587, 588, 589, 590, 591, 592, 593, 594, 595, - 596, 597, 598, 599, 600, 601, 610, 611, 612, 613, - - 1010, 1741, 1742, 1743, 1744, 1745, 1746, 1747, 1748, 1749, - 1750, 1751, 1752, 1753, 1754, 1755, 1756, 1757, 1771, 1772, - 1773, 1774, 1775, 1776, 1777, 1778, 1779, 1780, 1781, 1782, - 1783, 1784, 1785, 1786, 1787, 1788, 1789, 1790, 1801, 1802, - 1803, 1804, 1805, 1806, 1807, 1808, 1809, 1811, 1812, 1813, - 1814, 1815, 1816, 1817, 1818, 1819, 1820, 1821, 1822, 1823, - 1824, 1831, 1832, 1833, 1834, 1835, 1836, 1837, 1838, 1839, - 1840, 1841, 1842, 1843, 1844, 1845, 1846, 1847, 1848, 1849, - 1850, 1851, 1852, 1853, 1854, 1861, 1862, 1863, 1864, 1865, - 1866, 1867, 1868, 1869, 1870, 1871, 1872, 1873, 1874, 1875, - 1876, 1877, 1878, 1879, 1880, 1881, 1882, 1883, 1884, 1981, - 1982, 1983, 1984, 1985, 1986, 1987, 1988, 1989, 1990, 1991, - 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, - 2002, 2003, 2004, 2028, 2029, 2030, 2031, 2032, 2033, 2100, - 2101, 2102, 2103, 2104, 2105, - - 0x453B, 0x453C, 0x453D, 0x453E, 0x453F, 0x4540, 0x4541, - 0x4542, 0x4543, 0x4544, 0x4545, 0x4546, 0x4547, 0x4548, - 0x4549, 0x454A, 0x454B, 0x454C, 0x454D, 0x454E, 0x454F - }; - - private static int[] m_SandTiles = { - 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, - 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, - 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, - 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, - 62, 68, 69, 70, 71, 72, 73, 74, 75, - - 286, 287, 288, 289, 290, 291, 292, 293, 294, 295, - 296, 297, 298, 299, 300, 301, 402, 424, 425, 426, - 427, 441, 442, 443, 444, 445, 446, 447, 448, 449, - 450, 451, 452, 453, 454, 455, 456, 457, 458, 459, - 460, 461, 462, 463, 464, 465, 642, 643, 644, 645, - 650, 651, 652, 653, 654, 655, 656, 657, 821, 822, - 823, 824, 825, 826, 827, 828, 833, 834, 835, 836, - 845, 846, 847, 848, 849, 850, 851, 852, 857, 858, - 859, 860, 951, 952, 953, 954, 955, 956, 957, 958, - 967, 968, 969, 970, - - 1447, 1448, 1449, 1450, 1451, 1452, 1453, 1454, 1455, - 1456, 1457, 1458, 1611, 1612, 1613, 1614, 1615, 1616, - 1617, 1618, 1623, 1624, 1625, 1626, 1635, 1636, 1637, - 1638, 1639, 1640, 1641, 1642, 1647, 1648, 1649, 1650 - }; - #endregion - } -} + public class Mining : HarvestSystem + { + private static Mining m_System; + + private static int[] m_Offsets = + { + -1, -1, + -1, 0, + -1, 1, + 0, -1, + 0, 1, + 1, -1, + 1, 0, + 1, 1 + }; + + private Mining() + { + HarvestResource[] res; + HarvestVein[] veins; + + #region Mining for ore and stone + + HarvestDefinition oreAndStone = OreAndStone = new HarvestDefinition(); + + // Resource banks are every 8x8 tiles + oreAndStone.BankWidth = 8; + oreAndStone.BankHeight = 8; + + // Every bank holds from 10 to 34 ore + oreAndStone.MinTotal = 10; + oreAndStone.MaxTotal = 34; + + // A resource bank will respawn its content every 10 to 20 minutes + oreAndStone.MinRespawn = TimeSpan.FromMinutes(10.0); + oreAndStone.MaxRespawn = TimeSpan.FromMinutes(20.0); + + // Skill checking is done on the Mining skill + oreAndStone.Skill = SkillName.Mining; + + // Set the list of harvestable tiles + oreAndStone.Tiles = m_MountainAndCaveTiles; + + // Players must be within 2 tiles to harvest + oreAndStone.MaxRange = 2; + + // One ore per harvest action + oreAndStone.ConsumedPerHarvest = 1; + oreAndStone.ConsumedPerFeluccaHarvest = 2; + + // The digging effect + oreAndStone.EffectActions = new[] { 11 }; + oreAndStone.EffectSounds = new[] { 0x125, 0x126 }; + oreAndStone.EffectCounts = new[] { 1 }; + oreAndStone.EffectDelay = TimeSpan.FromSeconds(1.6); + oreAndStone.EffectSoundDelay = TimeSpan.FromSeconds(0.9); + + oreAndStone.NoResourcesMessage = 503040; // There is no metal here to mine. + oreAndStone.DoubleHarvestMessage = 503042; // Someone has gotten to the metal before you. + oreAndStone.TimedOutOfRangeMessage = 503041; // You have moved too far away to continue mining. + oreAndStone.OutOfRangeMessage = 500446; // That is too far away. + oreAndStone.FailMessage = 503043; // You loosen some rocks but fail to find any useable ore. + oreAndStone.PackFullMessage = 1010481; // Your backpack is full, so the ore you mined is lost. + oreAndStone.ToolBrokeMessage = 1044038; // You have worn out your tool! + + res = new[] + { + new HarvestResource(00.0, 00.0, 100.0, 1007072, typeof(IronOre), typeof(Granite)), + new HarvestResource(65.0, 25.0, 105.0, 1007073, typeof(DullCopperOre), typeof(DullCopperGranite), + typeof(DullCopperElemental)), + new HarvestResource(70.0, 30.0, 110.0, 1007074, typeof(ShadowIronOre), typeof(ShadowIronGranite), + typeof(ShadowIronElemental)), + new HarvestResource(75.0, 35.0, 115.0, 1007075, typeof(CopperOre), typeof(CopperGranite), + typeof(CopperElemental)), + new HarvestResource(80.0, 40.0, 120.0, 1007076, typeof(BronzeOre), typeof(BronzeGranite), + typeof(BronzeElemental)), + new HarvestResource(85.0, 45.0, 125.0, 1007077, typeof(GoldOre), typeof(GoldGranite), + typeof(GoldenElemental)), + new HarvestResource(90.0, 50.0, 130.0, 1007078, typeof(AgapiteOre), typeof(AgapiteGranite), + typeof(AgapiteElemental)), + new HarvestResource(95.0, 55.0, 135.0, 1007079, typeof(VeriteOre), typeof(VeriteGranite), + typeof(VeriteElemental)), + new HarvestResource(99.0, 59.0, 139.0, 1007080, typeof(ValoriteOre), typeof(ValoriteGranite), + typeof(ValoriteElemental)) + }; + + veins = new[] + { + new HarvestVein(49.6, 0.0, res[0], null), // Iron + new HarvestVein(11.2, 0.5, res[1], res[0]), // Dull Copper + new HarvestVein(09.8, 0.5, res[2], res[0]), // Shadow Iron + new HarvestVein(08.4, 0.5, res[3], res[0]), // Copper + new HarvestVein(07.0, 0.5, res[4], res[0]), // Bronze + new HarvestVein(05.6, 0.5, res[5], res[0]), // Gold + new HarvestVein(04.2, 0.5, res[6], res[0]), // Agapite + new HarvestVein(02.8, 0.5, res[7], res[0]), // Verite + new HarvestVein(01.4, 0.5, res[8], res[0]) // Valorite + }; + + oreAndStone.Resources = res; + oreAndStone.Veins = veins; + + if (Core.ML) + oreAndStone.BonusResources = new[] + { + new BonusHarvestResource(0, 99.4, null, null), //Nothing + new BonusHarvestResource(100, .1, 1072562, typeof(BlueDiamond)), + new BonusHarvestResource(100, .1, 1072567, typeof(DarkSapphire)), + new BonusHarvestResource(100, .1, 1072570, typeof(EcruCitrine)), + new BonusHarvestResource(100, .1, 1072564, typeof(FireRuby)), + new BonusHarvestResource(100, .1, 1072566, typeof(PerfectEmerald)), + new BonusHarvestResource(100, .1, 1072568, typeof(Turquoise)) + }; + + oreAndStone.RaceBonus = Core.ML; + oreAndStone.RandomizeVeins = Core.ML; + + Definitions.Add(oreAndStone); + + #endregion + + #region Mining for sand + + HarvestDefinition sand = Sand = new HarvestDefinition(); + + // Resource banks are every 8x8 tiles + sand.BankWidth = 8; + sand.BankHeight = 8; + + // Every bank holds from 6 to 12 sand + sand.MinTotal = 6; + sand.MaxTotal = 12; + + // A resource bank will respawn its content every 10 to 20 minutes + sand.MinRespawn = TimeSpan.FromMinutes(10.0); + sand.MaxRespawn = TimeSpan.FromMinutes(20.0); + + // Skill checking is done on the Mining skill + sand.Skill = SkillName.Mining; + + // Set the list of harvestable tiles + sand.Tiles = m_SandTiles; + + // Players must be within 2 tiles to harvest + sand.MaxRange = 2; + + // One sand per harvest action + sand.ConsumedPerHarvest = 1; + sand.ConsumedPerFeluccaHarvest = 1; + + // The digging effect + sand.EffectActions = new[] { 11 }; + sand.EffectSounds = new[] { 0x125, 0x126 }; + sand.EffectCounts = new[] { 6 }; + sand.EffectDelay = TimeSpan.FromSeconds(1.6); + sand.EffectSoundDelay = TimeSpan.FromSeconds(0.9); + + sand.NoResourcesMessage = 1044629; // There is no sand here to mine. + sand.DoubleHarvestMessage = 1044629; // There is no sand here to mine. + sand.TimedOutOfRangeMessage = 503041; // You have moved too far away to continue mining. + sand.OutOfRangeMessage = 500446; // That is too far away. + sand.FailMessage = 1044630; // You dig for a while but fail to find any of sufficient quality for glassblowing. + sand.PackFullMessage = 1044632; // Your backpack can't hold the sand, and it is lost! + sand.ToolBrokeMessage = 1044038; // You have worn out your tool! + + res = new[] + { + new HarvestResource(100.0, 70.0, 400.0, 1044631, typeof(Sand)) + }; + + veins = new[] + { + new HarvestVein(100.0, 0.0, res[0], null) + }; + + sand.Resources = res; + sand.Veins = veins; + + Definitions.Add(sand); + + #endregion + } + + public static Mining System + { + get + { + if (m_System == null) + m_System = new Mining(); + + return m_System; + } + } + + public HarvestDefinition OreAndStone{ get; } + + public HarvestDefinition Sand{ get; } + + public override Type GetResourceType(Mobile from, Item tool, HarvestDefinition def, Map map, Point3D loc, + HarvestResource resource) + { + if (def == OreAndStone) + { + if (from is PlayerMobile pm && pm.StoneMining && pm.ToggleMiningStone && + from.Skills[SkillName.Mining].Base >= 100.0 && 0.1 > Utility.RandomDouble()) + return resource.Types[1]; + + return resource.Types[0]; + } + + return base.GetResourceType(from, tool, def, map, loc, resource); + } + + public override bool CheckHarvest(Mobile from, Item tool) + { + if (!base.CheckHarvest(from, tool)) + return false; + + if (from.Mounted) + { + from.SendLocalizedMessage(501864); // You can't mine while riding. + return false; + } + + if (from.IsBodyMod && !from.Body.IsHuman) + { + from.SendLocalizedMessage(501865); // You can't mine while polymorphed. + return false; + } + + return true; + } + + public override void SendSuccessTo(Mobile from, Item item, HarvestResource resource) + { + if (item is BaseGranite) + from.SendLocalizedMessage(1044606); // You carefully extract some workable stone from the ore vein! + else + base.SendSuccessTo(from, item, resource); + } + + public override bool CheckHarvest(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + if (!base.CheckHarvest(from, tool, def, toHarvest)) + return false; + + if (def == Sand && !(from is PlayerMobile mobile && mobile.Skills[SkillName.Mining].Base >= 100.0 && + mobile.SandMining)) + { + OnBadHarvestTarget(from, tool, toHarvest); + return false; + } + + if (from.Mounted) + { + from.SendLocalizedMessage(501864); // You can't mine while riding. + return false; + } + + if (from.IsBodyMod && !from.Body.IsHuman) + { + from.SendLocalizedMessage(501865); // You can't mine while polymorphed. + return false; + } + + return true; + } + + public override HarvestVein MutateVein(Mobile from, Item tool, HarvestDefinition def, HarvestBank bank, + object toHarvest, HarvestVein vein) + { + if (tool is GargoylesPickaxe && def == OreAndStone) + { + int veinIndex = Array.IndexOf(def.Veins, vein); + + if (veinIndex >= 0 && veinIndex < def.Veins.Length - 1) + return def.Veins[veinIndex + 1]; + } + + return base.MutateVein(from, tool, def, bank, toHarvest, vein); + } + + public override void OnHarvestFinished(Mobile from, Item tool, HarvestDefinition def, HarvestVein vein, + HarvestBank bank, HarvestResource resource, object harvested) + { + if (tool is GargoylesPickaxe && def == OreAndStone && 0.1 > Utility.RandomDouble()) + { + HarvestResource res = vein.PrimaryResource; + + if (res == resource && res.Types.Length >= 3) + try + { + Map map = from.Map; + + if (map == null) + return; + + if (Activator.CreateInstance(res.Types[2], 25) is BaseCreature spawned) + { + int offset = Utility.Random(8) * 2; + + for (int i = 0; i < m_Offsets.Length; i += 2) + { + int x = from.X + m_Offsets[(offset + i) % m_Offsets.Length]; + int y = from.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; + + if (map.CanSpawnMobile(x, y, from.Z)) + { + spawned.OnBeforeSpawn(new Point3D(x, y, from.Z), map); + spawned.MoveToWorld(new Point3D(x, y, from.Z), map); + spawned.Combatant = from; + return; + } + + int z = map.GetAverageZ(x, y); + + if (Math.Abs(z - from.Z) < 10 && map.CanSpawnMobile(x, y, z)) + { + spawned.OnBeforeSpawn(new Point3D(x, y, z), map); + spawned.MoveToWorld(new Point3D(x, y, z), map); + spawned.Combatant = from; + return; + } + } + + spawned.OnBeforeSpawn(from.Location, from.Map); + spawned.MoveToWorld(from.Location, from.Map); + spawned.Combatant = from; + } + } + catch + { + } + } + } + + public override bool BeginHarvesting(Mobile from, Item tool) + { + if (!base.BeginHarvesting(from, tool)) + return false; + + from.SendLocalizedMessage(503033); // Where do you wish to dig? + return true; + } + + public override void OnHarvestStarted(Mobile from, Item tool, HarvestDefinition def, object toHarvest) + { + base.OnHarvestStarted(from, tool, def, toHarvest); + + if (Core.ML) + from.RevealingAction(); + } + + public override void OnBadHarvestTarget(Mobile from, Item tool, object toHarvest) + { + if (toHarvest is LandTarget) + from.SendLocalizedMessage(501862); // You can't mine there. + else + from.SendLocalizedMessage(501863); // You can't mine that. + } + + #region Tile lists + + private static int[] m_MountainAndCaveTiles = + { + 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, + 230, 231, 236, 237, 238, 239, 240, 241, 242, 243, + 244, 245, 246, 247, 252, 253, 254, 255, 256, 257, + 258, 259, 260, 261, 262, 263, 268, 269, 270, 271, + 272, 273, 274, 275, 276, 277, 278, 279, 286, 287, + 288, 289, 290, 291, 292, 293, 294, 296, 296, 297, + 321, 322, 323, 324, 467, 468, 469, 470, 471, 472, + 473, 474, 476, 477, 478, 479, 480, 481, 482, 483, + 484, 485, 486, 487, 492, 493, 494, 495, 543, 544, + 545, 546, 547, 548, 549, 550, 551, 552, 553, 554, + 555, 556, 557, 558, 559, 560, 561, 562, 563, 564, + 565, 566, 567, 568, 569, 570, 571, 572, 573, 574, + 575, 576, 577, 578, 579, 581, 582, 583, 584, 585, + 586, 587, 588, 589, 590, 591, 592, 593, 594, 595, + 596, 597, 598, 599, 600, 601, 610, 611, 612, 613, + + 1010, 1741, 1742, 1743, 1744, 1745, 1746, 1747, 1748, 1749, + 1750, 1751, 1752, 1753, 1754, 1755, 1756, 1757, 1771, 1772, + 1773, 1774, 1775, 1776, 1777, 1778, 1779, 1780, 1781, 1782, + 1783, 1784, 1785, 1786, 1787, 1788, 1789, 1790, 1801, 1802, + 1803, 1804, 1805, 1806, 1807, 1808, 1809, 1811, 1812, 1813, + 1814, 1815, 1816, 1817, 1818, 1819, 1820, 1821, 1822, 1823, + 1824, 1831, 1832, 1833, 1834, 1835, 1836, 1837, 1838, 1839, + 1840, 1841, 1842, 1843, 1844, 1845, 1846, 1847, 1848, 1849, + 1850, 1851, 1852, 1853, 1854, 1861, 1862, 1863, 1864, 1865, + 1866, 1867, 1868, 1869, 1870, 1871, 1872, 1873, 1874, 1875, + 1876, 1877, 1878, 1879, 1880, 1881, 1882, 1883, 1884, 1981, + 1982, 1983, 1984, 1985, 1986, 1987, 1988, 1989, 1990, 1991, + 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, + 2002, 2003, 2004, 2028, 2029, 2030, 2031, 2032, 2033, 2100, + 2101, 2102, 2103, 2104, 2105, + + 0x453B, 0x453C, 0x453D, 0x453E, 0x453F, 0x4540, 0x4541, + 0x4542, 0x4543, 0x4544, 0x4545, 0x4546, 0x4547, 0x4548, + 0x4549, 0x454A, 0x454B, 0x454C, 0x454D, 0x454E, 0x454F + }; + + private static int[] m_SandTiles = + { + 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, + 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, + 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, + 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, + 62, 68, 69, 70, 71, 72, 73, 74, 75, + + 286, 287, 288, 289, 290, 291, 292, 293, 294, 295, + 296, 297, 298, 299, 300, 301, 402, 424, 425, 426, + 427, 441, 442, 443, 444, 445, 446, 447, 448, 449, + 450, 451, 452, 453, 454, 455, 456, 457, 458, 459, + 460, 461, 462, 463, 464, 465, 642, 643, 644, 645, + 650, 651, 652, 653, 654, 655, 656, 657, 821, 822, + 823, 824, 825, 826, 827, 828, 833, 834, 835, 836, + 845, 846, 847, 848, 849, 850, 851, 852, 857, 858, + 859, 860, 951, 952, 953, 954, 955, 956, 957, 958, + 967, 968, 969, 970, + + 1447, 1448, 1449, 1450, 1451, 1452, 1453, 1454, 1455, + 1456, 1457, 1458, 1611, 1612, 1613, 1614, 1615, 1616, + 1617, 1618, 1623, 1624, 1625, 1626, 1635, 1636, 1637, + 1638, 1639, 1640, 1641, 1642, 1647, 1648, 1649, 1650 + }; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Help/HelpGump.cs b/Scripts/Engines/Help/HelpGump.cs index c7b01f3ee..385ddb0e0 100644 --- a/Scripts/Engines/Help/HelpGump.cs +++ b/Scripts/Engines/Help/HelpGump.cs @@ -1,157 +1,149 @@ using System; +using Server.Engines.ConPVP; +using Server.Factions; using Server.Gumps; -using Server.Network; using Server.Menus.Questions; -using Server.Multis; using Server.Mobiles; +using Server.Multis; +using Server.Network; +using Server.Regions; namespace Server.Engines.Help { - public class ContainedMenu : QuestionMenu - { - private Mobile m_From; + public class ContainedMenu : QuestionMenu + { + private Mobile m_From; - public ContainedMenu( Mobile from ) : base( "You already have an open help request. We will have someone assist you as soon as possible. What would you like to do?", new[]{ "Leave my old help request like it is.", "Remove my help request from the queue." } ) - { - m_From = from; - } + public ContainedMenu(Mobile from) : base( + "You already have an open help request. We will have someone assist you as soon as possible. What would you like to do?", + new[] { "Leave my old help request like it is.", "Remove my help request from the queue." }) + { + m_From = from; + } - public override void OnCancel( NetState state ) - { - m_From.SendLocalizedMessage( 1005306, "", 0x35 ); // Help request unchanged. - } + public override void OnCancel(NetState state) + { + m_From.SendLocalizedMessage(1005306, "", 0x35); // Help request unchanged. + } - public override void OnResponse( NetState state, int index ) - { - if ( index == 0 ) - { - m_From.SendLocalizedMessage( 1005306, "", 0x35 ); // Help request unchanged. - } - else if ( index == 1 ) - { - PageEntry entry = PageQueue.GetEntry( m_From ); + public override void OnResponse(NetState state, int index) + { + if (index == 0) + { + m_From.SendLocalizedMessage(1005306, "", 0x35); // Help request unchanged. + } + else if (index == 1) + { + PageEntry entry = PageQueue.GetEntry(m_From); - if ( entry != null && entry.Handler == null ) - { - m_From.SendLocalizedMessage( 1005307, "", 0x35 ); // Removed help request. - entry.AddResponse( entry.Sender, "[Canceled]" ); - PageQueue.Remove( entry ); - } - else - { - m_From.SendLocalizedMessage( 1005306, "", 0x35 ); // Help request unchanged. - } - } - } - } + if (entry != null && entry.Handler == null) + { + m_From.SendLocalizedMessage(1005307, "", 0x35); // Removed help request. + entry.AddResponse(entry.Sender, "[Canceled]"); + PageQueue.Remove(entry); + } + else + { + m_From.SendLocalizedMessage(1005306, "", 0x35); // Help request unchanged. + } + } + } + } - public class HelpGump : Gump - { - public static void Initialize() - { - EventSink.HelpRequest += EventSink_HelpRequest; - } + public class HelpGump : Gump + { + public HelpGump(Mobile from) : base(0, 0) + { + from.CloseGump(typeof(HelpGump)); - private static void EventSink_HelpRequest( HelpRequestEventArgs e ) - { - foreach ( Gump g in e.Mobile.NetState.Gumps ) - { - if ( g is HelpGump ) - return; - } + bool isYoung = IsYoung(from); - if ( !PageQueue.CheckAllowedToPage( e.Mobile ) ) - return; + AddBackground(50, 25, 540, 430, 2600); - if ( PageQueue.Contains( e.Mobile ) ) - e.Mobile.SendMenu( new ContainedMenu( e.Mobile ) ); - else - e.Mobile.SendGump( new HelpGump( e.Mobile ) ); - } + AddPage(0); - private static bool IsYoung( Mobile m ) - { - return m is PlayerMobile mobile && mobile.Young; - } + AddHtmlLocalized(150, 50, 360, 40, 1001002, false, false); //
Ultima Online Help Menu
+ AddButton(425, 415, 2073, 2072, 0, GumpButtonType.Reply, 0); // Close - public static bool CheckCombat( Mobile m ) - { - for ( int i = 0; i < m.Aggressed.Count; ++i ) - { - AggressorInfo info = m.Aggressed[i]; + AddPage(1); - if ( DateTime.UtcNow - info.LastCombatTime < TimeSpan.FromSeconds( 30.0 ) ) - return true; - } + if (isYoung) + { + AddButton(80, 75, 5540, 5541, 9, GumpButtonType.Reply, 2); + AddHtml(110, 75, 450, 58, + @"Young Player Haven Transport. Select this option if you want to be transported to Haven.", + true, true); - return false; - } + AddButton(80, 140, 5540, 5541, 1, GumpButtonType.Reply, 2); + AddHtml(110, 140, 450, 58, + @"General question about Ultima Online. Select this option if you have a general gameplay question, need help learning to use a skill, or if you would like to search the UO Knowledge Base.", + true, true); - public HelpGump( Mobile from ) : base( 0, 0 ) - { - from.CloseGump( typeof( HelpGump ) ); + AddButton(80, 205, 5540, 5541, 2, GumpButtonType.Reply, 0); + AddHtml(110, 205, 450, 58, + @"My character is physically stuck in the game. This choice only covers cases where your character is physically stuck in a location they cannot move out of. This option will only work two times in 24 hours.", + true, true); - bool isYoung = IsYoung( from ); + AddButton(80, 270, 5540, 5541, 0, GumpButtonType.Page, 3); + AddHtml(110, 270, 450, 58, + @"Another player is harassing me. Another player is verbally harassing your character. When you select this option you will be sending a text log to Origin Systems. To see what constitutes harassment please visit http://support.uo.com/gm_9.html.", + true, true); - AddBackground( 50, 25, 540, 430, 2600 ); + AddButton(80, 335, 5540, 5541, 0, GumpButtonType.Page, 2); + AddHtml(110, 335, 450, 58, + @"Other. If you are experiencing a problem in the game that does not fall into one of the other categories or is not addressed on the Support web page (located at http://support.uo.com), please use this option.", + true, true); + } + else + { + AddButton(80, 90, 5540, 5541, 1, GumpButtonType.Reply, 2); + AddHtml(110, 90, 450, 74, + @"General question about Ultima Online. Select this option if you have a general gameplay question, need help learning to use a skill, or if you would like to search the UO Knowledge Base.", + true, true); - AddPage( 0 ); + AddButton(80, 170, 5540, 5541, 2, GumpButtonType.Reply, 0); + AddHtml(110, 170, 450, 74, + @"My character is physically stuck in the game. This choice only covers cases where your character is physically stuck in a location they cannot move out of. This option will only work two times in 24 hours.", + true, true); - AddHtmlLocalized( 150, 50, 360, 40, 1001002, false, false ); //
Ultima Online Help Menu
- AddButton( 425, 415, 2073, 2072, 0, GumpButtonType.Reply, 0 ); // Close + AddButton(80, 250, 5540, 5541, 0, GumpButtonType.Page, 3); + AddHtml(110, 250, 450, 74, + @"Another player is harassing me. Another player is verbally harassing your character. When you select this option you will be sending a text log to Origin Systems. To see what constitutes harassment please visit http://support.uo.com/gm_9.html.", + true, true); - AddPage( 1 ); + AddButton(80, 330, 5540, 5541, 0, GumpButtonType.Page, 2); + AddHtml(110, 330, 450, 74, + @"Other. If you are experiencing a problem in the game that does not fall into one of the other categories or is not addressed on the Support web page (located at http://support.uo.com), please use this option.", + true, true); + } - if ( isYoung ) - { - AddButton( 80, 75, 5540, 5541, 9, GumpButtonType.Reply, 2 ); - AddHtml( 110, 75, 450, 58, @"Young Player Haven Transport. Select this option if you want to be transported to Haven.", true, true ); + AddPage(2); - AddButton( 80, 140, 5540, 5541, 1, GumpButtonType.Reply, 2 ); - AddHtml( 110, 140, 450, 58, @"General question about Ultima Online. Select this option if you have a general gameplay question, need help learning to use a skill, or if you would like to search the UO Knowledge Base.", true, true ); + AddButton(80, 90, 5540, 5541, 3, GumpButtonType.Reply, 0); + AddHtml(110, 90, 450, 74, + @"Report a bug or contact Origin. Use this option to launch your web browser and mail in a bug report. Your report will be read by our Quality Assurance Staff. We apologize for not being able to reply to individual reports. ", + true, true); - AddButton( 80, 205, 5540, 5541, 2, GumpButtonType.Reply, 0 ); - AddHtml( 110, 205, 450, 58, @"My character is physically stuck in the game. This choice only covers cases where your character is physically stuck in a location they cannot move out of. This option will only work two times in 24 hours.", true, true ); + AddButton(80, 170, 5540, 5541, 4, GumpButtonType.Reply, 0); + AddHtml(110, 170, 450, 74, + @"Suggestion for the Game. If you'd like to make a suggestion for the game, it should be directed to the Development Team Members who participate in the discussion forums on the UO.Com web site. Choosing this option will take you to the Discussion Forums. ", + true, true); - AddButton( 80, 270, 5540, 5541, 0, GumpButtonType.Page, 3 ); - AddHtml( 110, 270, 450, 58, @"Another player is harassing me. Another player is verbally harassing your character. When you select this option you will be sending a text log to Origin Systems. To see what constitutes harassment please visit http://support.uo.com/gm_9.html.", true, true ); + AddButton(80, 250, 5540, 5541, 5, GumpButtonType.Reply, 0); + AddHtml(110, 250, 450, 74, + @"Account Management For questions regarding your account such as forgotten passwords, payment options, account activation, and account transfer, please choose this option.", + true, true); - AddButton( 80, 335, 5540, 5541, 0, GumpButtonType.Page, 2 ); - AddHtml( 110, 335, 450, 58, @"Other. If you are experiencing a problem in the game that does not fall into one of the other categories or is not addressed on the Support web page (located at http://support.uo.com), please use this option.", true, true ); - } - else - { - AddButton( 80, 90, 5540, 5541, 1, GumpButtonType.Reply, 2 ); - AddHtml( 110, 90, 450, 74, @"General question about Ultima Online. Select this option if you have a general gameplay question, need help learning to use a skill, or if you would like to search the UO Knowledge Base.", true, true ); + AddButton(80, 330, 5540, 5541, 6, GumpButtonType.Reply, 0); + AddHtml(110, 330, 450, 74, + @"Other. If you are experiencing a problem in the game that does not fall into one of the other categories or is not addressed on the Support web page (located at http://support.uo.com), and requires in-game assistance, use this option. ", + true, true); - AddButton( 80, 170, 5540, 5541, 2, GumpButtonType.Reply, 0 ); - AddHtml( 110, 170, 450, 74, @"My character is physically stuck in the game. This choice only covers cases where your character is physically stuck in a location they cannot move out of. This option will only work two times in 24 hours.", true, true ); + AddPage(3); - AddButton( 80, 250, 5540, 5541, 0, GumpButtonType.Page, 3 ); - AddHtml( 110, 250, 450, 74, @"Another player is harassing me. Another player is verbally harassing your character. When you select this option you will be sending a text log to Origin Systems. To see what constitutes harassment please visit http://support.uo.com/gm_9.html.", true, true ); - - AddButton( 80, 330, 5540, 5541, 0, GumpButtonType.Page, 2 ); - AddHtml( 110, 330, 450, 74, @"Other. If you are experiencing a problem in the game that does not fall into one of the other categories or is not addressed on the Support web page (located at http://support.uo.com), please use this option.", true, true ); - } - - AddPage( 2 ); - - AddButton( 80, 90, 5540, 5541, 3, GumpButtonType.Reply, 0 ); - AddHtml( 110, 90, 450, 74, @"Report a bug or contact Origin. Use this option to launch your web browser and mail in a bug report. Your report will be read by our Quality Assurance Staff. We apologize for not being able to reply to individual reports. ", true, true ); - - AddButton( 80, 170, 5540, 5541, 4, GumpButtonType.Reply, 0 ); - AddHtml( 110, 170, 450, 74, @"Suggestion for the Game. If you'd like to make a suggestion for the game, it should be directed to the Development Team Members who participate in the discussion forums on the UO.Com web site. Choosing this option will take you to the Discussion Forums. ", true, true ); - - AddButton( 80, 250, 5540, 5541, 5, GumpButtonType.Reply, 0 ); - AddHtml( 110, 250, 450, 74, @"Account Management For questions regarding your account such as forgotten passwords, payment options, account activation, and account transfer, please choose this option.", true, true ); - - AddButton( 80, 330, 5540, 5541, 6, GumpButtonType.Reply, 0 ); - AddHtml( 110, 330, 450, 74, @"Other. If you are experiencing a problem in the game that does not fall into one of the other categories or is not addressed on the Support web page (located at http://support.uo.com), and requires in-game assistance, use this option. ", true, true ); - - AddPage( 3 ); - - AddButton( 80, 90, 5540, 5541, 7, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 110, 90, 450, 145, 1062572, true, true ); /*
Another player is harassing me (or Exploiting).

+ AddButton(80, 90, 5540, 5541, 7, GumpButtonType.Reply, 0); + AddHtmlLocalized(110, 90, 450, 145, 1062572, true, + true); /*
Another player is harassing me (or Exploiting).

* VERBAL HARASSMENT
* Use this option when another player is verbally harassing your character. * Verbal harassment behaviors include but are not limited to, using bad language, threats etc.. @@ -173,8 +165,9 @@ namespace Server.Engines.Help * � What constitutes an exploit? */ - AddButton( 80, 240, 5540, 5541, 8, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 110, 240, 450, 145, 1062573, true, true ); /*
Another player is harassing me using game mechanics.

+ AddButton(80, 240, 5540, 5541, 8, GumpButtonType.Reply, 0); + AddHtmlLocalized(110, 240, 450, 145, 1062573, true, + true); /*
Another player is harassing me using game mechanics.

*
* PHYSICAL HARASSMENT
* Use this option when another player is harassing your character using game mechanics. @@ -194,114 +187,148 @@ namespace Server.Engines.Help * Abuse of this system is a violation of the Rules of Conduct. */ - AddButton( 150, 390, 5540, 5541, 0, GumpButtonType.Page, 1 ); - AddHtmlLocalized( 180, 390, 335, 40, 1001015, false, false ); // NO - I meant to ask for help with another matter. - } + AddButton(150, 390, 5540, 5541, 0, GumpButtonType.Page, 1); + AddHtmlLocalized(180, 390, 335, 40, 1001015, false, false); // NO - I meant to ask for help with another matter. + } - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; + public static void Initialize() + { + EventSink.HelpRequest += EventSink_HelpRequest; + } - PageType type = (PageType)(-1); + private static void EventSink_HelpRequest(HelpRequestEventArgs e) + { + foreach (Gump g in e.Mobile.NetState.Gumps) + if (g is HelpGump) + return; - switch ( info.ButtonID ) - { - case 0: // Close/Cancel - { - from.SendLocalizedMessage( 501235, "", 0x35 ); // Help request aborted. + if (!PageQueue.CheckAllowedToPage(e.Mobile)) + return; - break; - } - case 1: // General question - { - type = PageType.Question; - break; - } - case 2: // Stuck - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (PageQueue.Contains(e.Mobile)) + e.Mobile.SendMenu(new ContainedMenu(e.Mobile)); + else + e.Mobile.SendGump(new HelpGump(e.Mobile)); + } - if ( house != null && house.IsAosRules && !from.Region.IsPartOf( typeof( ConPVP.SafeZone ) ) ) // Dueling - { - from.Location = house.BanLocation; - } - else if ( from.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - from.SendLocalizedMessage( 1114345, "", 0x35 ); // You'll need a better jailbreak plan than that! - } - else if ( Factions.Sigil.ExistsOn( from ) ) - { - from.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( from is PlayerMobile mobile && mobile.CanUseStuckMenu() && mobile.Region.CanUseStuckMenu( mobile ) && !CheckCombat( mobile ) && !mobile.Frozen && !mobile.Criminal && (Core.AOS || mobile.Kills < 5) ) - { - StuckMenu menu = new StuckMenu( mobile, mobile, true ); + private static bool IsYoung(Mobile m) + { + return m is PlayerMobile mobile && mobile.Young; + } - menu.BeginClose(); + public static bool CheckCombat(Mobile m) + { + for (int i = 0; i < m.Aggressed.Count; ++i) + { + AggressorInfo info = m.Aggressed[i]; - mobile.SendGump( menu ); - } - else - { - type = PageType.Stuck; - } + if (DateTime.UtcNow - info.LastCombatTime < TimeSpan.FromSeconds(30.0)) + return true; + } - break; - } - case 3: // Report bug or contact Origin - { - type = PageType.Bug; - break; - } - case 4: // Game suggestion - { - type = PageType.Suggestion; - break; - } - case 5: // Account management - { - type = PageType.Account; - break; - } - case 6: // Other - { - type = PageType.Other; - break; - } - case 7: // Harassment: verbal/exploit - { - type = PageType.VerbalHarassment; - break; - } - case 8: // Harassment: physical - { - type = PageType.PhysicalHarassment; - break; - } - case 9: // Young player transport - { - if ( IsYoung( from ) ) - { - if ( from.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - from.SendLocalizedMessage( 1114345, "", 0x35 ); // You'll need a better jailbreak plan than that! - } - else if ( from.Region.IsPartOf( "Haven Island" ) ) - { - from.SendLocalizedMessage( 1041529 ); // You're already in Haven - } - else - { - from.MoveToWorld( new Point3D( 3503, 2574, 14 ), Map.Trammel ); - } - } + return false; + } - break; - } - } + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; - if ( type != (PageType)(-1) && PageQueue.CheckAllowedToPage( from ) ) - from.SendGump( new PagePromptGump( from, type ) ); - } - } -} + PageType type = (PageType)(-1); + + switch (info.ButtonID) + { + case 0: // Close/Cancel + { + from.SendLocalizedMessage(501235, "", 0x35); // Help request aborted. + + break; + } + case 1: // General question + { + type = PageType.Question; + break; + } + case 2: // Stuck + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsAosRules && !from.Region.IsPartOf(typeof(SafeZone))) // Dueling + { + from.Location = house.BanLocation; + } + else if (from.Region.IsPartOf(typeof(Jail))) + { + from.SendLocalizedMessage(1114345, "", 0x35); // You'll need a better jailbreak plan than that! + } + else if (Sigil.ExistsOn(from)) + { + from.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (from is PlayerMobile mobile && mobile.CanUseStuckMenu() && + mobile.Region.CanUseStuckMenu(mobile) && !CheckCombat(mobile) && !mobile.Frozen && + !mobile.Criminal && (Core.AOS || mobile.Kills < 5)) + { + StuckMenu menu = new StuckMenu(mobile, mobile, true); + + menu.BeginClose(); + + mobile.SendGump(menu); + } + else + { + type = PageType.Stuck; + } + + break; + } + case 3: // Report bug or contact Origin + { + type = PageType.Bug; + break; + } + case 4: // Game suggestion + { + type = PageType.Suggestion; + break; + } + case 5: // Account management + { + type = PageType.Account; + break; + } + case 6: // Other + { + type = PageType.Other; + break; + } + case 7: // Harassment: verbal/exploit + { + type = PageType.VerbalHarassment; + break; + } + case 8: // Harassment: physical + { + type = PageType.PhysicalHarassment; + break; + } + case 9: // Young player transport + { + if (IsYoung(from)) + { + if (from.Region.IsPartOf(typeof(Jail))) + from.SendLocalizedMessage(1114345, "", 0x35); // You'll need a better jailbreak plan than that! + else if (from.Region.IsPartOf("Haven Island")) + from.SendLocalizedMessage(1041529); // You're already in Haven + else + from.MoveToWorld(new Point3D(3503, 2574, 14), Map.Trammel); + } + + break; + } + } + + if (type != (PageType)(-1) && PageQueue.CheckAllowedToPage(from)) + from.SendGump(new PagePromptGump(from, type)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Help/PagePrompt.cs b/Scripts/Engines/Help/PagePrompt.cs index c8156354a..58ff9f060 100644 --- a/Scripts/Engines/Help/PagePrompt.cs +++ b/Scripts/Engines/Help/PagePrompt.cs @@ -2,27 +2,28 @@ using Server.Prompts; namespace Server.Engines.Help { - public class PagePrompt : Prompt - { - private PageType m_Type; + public class PagePrompt : Prompt + { + private PageType m_Type; - public PagePrompt( PageType type ) - { - m_Type = type; - } + public PagePrompt(PageType type) + { + m_Type = type; + } - public override void OnCancel( Mobile from ) - { - from.SendLocalizedMessage( 501235, "", 0x35 ); // Help request aborted. - } + public override void OnCancel(Mobile from) + { + from.SendLocalizedMessage(501235, "", 0x35); // Help request aborted. + } - public override void OnResponse( Mobile from, string text ) - { - from.SendLocalizedMessage( 501234, "", 0x35 ); /* The next available Counselor/Game Master will respond as soon as possible. + public override void OnResponse(Mobile from, string text) + { + from.SendLocalizedMessage(501234, "", + 0x35); /* The next available Counselor/Game Master will respond as soon as possible. * Please check your Journal for messages every few minutes. */ - PageQueue.Enqueue( new PageEntry( from, text, m_Type ) ); - } - } + PageQueue.Enqueue(new PageEntry(from, text, m_Type)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Help/PagePromptGump.cs b/Scripts/Engines/Help/PagePromptGump.cs index 04caa444c..0008af466 100644 --- a/Scripts/Engines/Help/PagePromptGump.cs +++ b/Scripts/Engines/Help/PagePromptGump.cs @@ -3,57 +3,59 @@ using Server.Network; namespace Server.Engines.Help { - public class PagePromptGump : Gump - { - private Mobile m_From; - private PageType m_Type; + public class PagePromptGump : Gump + { + private Mobile m_From; + private PageType m_Type; - public PagePromptGump( Mobile from, PageType type ) : base( 0, 0 ) - { - m_From = from; - m_Type = type; + public PagePromptGump(Mobile from, PageType type) : base(0, 0) + { + m_From = from; + m_Type = type; - from.CloseGump( typeof( PagePromptGump ) ); + from.CloseGump(typeof(PagePromptGump)); - AddBackground( 50, 50, 540, 350, 2600 ); + AddBackground(50, 50, 540, 350, 2600); - AddPage( 0 ); + AddPage(0); - AddHtmlLocalized( 264, 80, 200, 24, 1062524, false, false ); // Enter Description - AddHtmlLocalized( 120, 108, 420, 48, 1062638, false, false ); // Please enter a brief description (up to 200 characters) of your problem: + AddHtmlLocalized(264, 80, 200, 24, 1062524, false, false); // Enter Description + AddHtmlLocalized(120, 108, 420, 48, 1062638, false, + false); // Please enter a brief description (up to 200 characters) of your problem: - AddBackground( 100, 148, 440, 200, 3500 ); - AddTextEntry( 120, 168, 400, 200, 1153, 0, "" ); + AddBackground(100, 148, 440, 200, 3500); + AddTextEntry(120, 168, 400, 200, 1153, 0, ""); - AddButton( 175, 355, 2074, 2075, 1, GumpButtonType.Reply, 0 ); // Okay - AddButton( 405, 355, 2073, 2072, 0, GumpButtonType.Reply, 0 ); // Cancel - } + AddButton(175, 355, 2074, 2075, 1, GumpButtonType.Reply, 0); // Okay + AddButton(405, 355, 2073, 2072, 0, GumpButtonType.Reply, 0); // Cancel + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 ) - { - m_From.SendLocalizedMessage( 501235, "", 0x35 ); // Help request aborted. - } - else - { - TextRelay entry = info.GetTextEntry( 0 ); - string text = ( entry == null ? "" : entry.Text.Trim() ); + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0) + { + m_From.SendLocalizedMessage(501235, "", 0x35); // Help request aborted. + } + else + { + TextRelay entry = info.GetTextEntry(0); + string text = entry == null ? "" : entry.Text.Trim(); - if ( text.Length == 0 ) - { - m_From.SendMessage( 0x35, "You must enter a description." ); - m_From.SendGump( new PagePromptGump( m_From, m_Type ) ); - } - else - { - m_From.SendLocalizedMessage( 501234, "", 0x35 ); /* The next available Counselor/Game Master will respond as soon as possible. + if (text.Length == 0) + { + m_From.SendMessage(0x35, "You must enter a description."); + m_From.SendGump(new PagePromptGump(m_From, m_Type)); + } + else + { + m_From.SendLocalizedMessage(501234, "", + 0x35); /* The next available Counselor/Game Master will respond as soon as possible. * Please check your Journal for messages every few minutes. */ - PageQueue.Enqueue( new PageEntry( m_From, text, m_Type ) ); - } - } - } - } -} + PageQueue.Enqueue(new PageEntry(m_From, text, m_Type)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Help/PageQueue.cs b/Scripts/Engines/Help/PageQueue.cs index 7ba84c190..390667b58 100644 --- a/Scripts/Engines/Help/PageQueue.cs +++ b/Scripts/Engines/Help/PageQueue.cs @@ -1,324 +1,329 @@ using System; using System.Collections; -using System.Net.Mail; +using System.Collections.Generic; using System.IO; +using System.Net.Mail; +using Server.Accounting; +using Server.Commands; +using Server.Engines.Reports; +using Server.Misc; using Server.Mobiles; using Server.Network; -using Server.Misc; -using Server.Accounting; -using Server.Engines.Reports; -using Server.Commands; -using System.Collections.Generic; namespace Server.Engines.Help { - public enum PageType - { - Bug, - Stuck, - Account, - Question, - Suggestion, - Other, - VerbalHarassment, - PhysicalHarassment - } - - public class PageEntry - { - // What page types should have a speech log as attachment? - public static readonly PageType[] SpeechLogAttachment = { - PageType.VerbalHarassment - }; - - private Mobile m_Handler; - - public PageInfo PageInfo { get; } - - public Mobile Sender { get; } - - public Mobile Handler - { - get => m_Handler; - set - { - PageQueue.OnHandlerChanged( m_Handler, value, this ); - m_Handler = value; - } - } - - public DateTime Sent { get; } - - public string Message { get; } - - public PageType Type { get; } - - public Point3D PageLocation { get; } - - public Map PageMap { get; } - - public List SpeechLog { get; } - - private Timer m_Timer; - - public void Stop() - { - m_Timer?.Stop(); - - m_Timer = null; - } - - public void AddResponse( Mobile mob, string text ) - { - if ( PageInfo != null ) - { - lock ( PageInfo ) - PageInfo.Responses.Add( PageInfo.GetAccount( mob ), text ); - - if ( PageInfo.ResFromResp( text ) != PageResolution.None ) - PageInfo.UpdateResolver(); - } - } - - public PageEntry( Mobile sender, string message, PageType type ) - { - Sender = sender; - Sent = DateTime.UtcNow; - Message = Utility.FixHtml( message ); - Type = type; - PageLocation = sender.Location; - PageMap = sender.Map; - - if ( sender is PlayerMobile pm && pm.SpeechLog != null && Array.IndexOf( SpeechLogAttachment, type ) >= 0 ) - SpeechLog = new List( pm.SpeechLog ); - - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - - StaffHistory history = Reports.Reports.StaffHistory; - - if ( history != null ) - { - PageInfo = new PageInfo( this ); - - history.AddPage( PageInfo ); - } - } - - private class InternalTimer : Timer - { - private static TimeSpan StatusDelay = TimeSpan.FromMinutes( 2.0 ); - - private PageEntry m_Entry; - - public InternalTimer( PageEntry entry ) : base( TimeSpan.FromSeconds( 1.0 ), StatusDelay ) - { - m_Entry = entry; - } - - protected override void OnTick() - { - int index = PageQueue.IndexOf( m_Entry ); - - if ( m_Entry.Sender.NetState != null && index != -1 ) - { - m_Entry.Sender.SendLocalizedMessage( 1008077, true, (index + 1).ToString() ); // Thank you for paging. Queue status : - m_Entry.Sender.SendLocalizedMessage( 1008084 ); // You can reference our website at www.uo.com or contact us at support@uo.com. To cancel your page, please select the help button again and select cancel. - - if ( m_Entry.Handler != null && m_Entry.Handler.NetState == null ) { - m_Entry.Handler = null; - } - } - else - { - if ( index != -1 ) - m_Entry.AddResponse( m_Entry.Sender, "[Logout]" ); - - PageQueue.Remove( m_Entry ); - } - } - } - } - - public class PageQueue - { - private static Hashtable m_KeyedByHandler = new Hashtable(); - private static Hashtable m_KeyedBySender = new Hashtable(); - - public static void Initialize() - { - CommandSystem.Register( "Pages", AccessLevel.Counselor, Pages_OnCommand ); - } - - public static bool CheckAllowedToPage( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return true; - - if ( pm.DesignContext != null ) - { - from.SendLocalizedMessage( 500182 ); // You cannot request help while customizing a house or transferring a character. - return false; - } - if ( pm.PagingSquelched ) - { - from.SendMessage( "You cannot request help, sorry." ); - return false; - } - - return true; - } - - public static string GetPageTypeName( PageType type ) - { - if ( type == PageType.VerbalHarassment ) - return "Verbal Harassment"; - if ( type == PageType.PhysicalHarassment ) - return "Physical Harassment"; - return type.ToString(); - } - - public static void OnHandlerChanged( Mobile old, Mobile value, PageEntry entry ) - { - if ( old != null ) - m_KeyedByHandler.Remove( old ); - - if ( value != null ) - m_KeyedByHandler[value] = entry; - } - - [Usage( "Pages" )] - [Description( "Opens the page queue menu." )] - private static void Pages_OnCommand( CommandEventArgs e ) - { - PageEntry entry = (PageEntry)m_KeyedByHandler[e.Mobile]; - - if ( entry != null ) - { - e.Mobile.SendGump( new PageEntryGump( e.Mobile, entry ) ); - } - else if ( List.Count > 0 ) - { - e.Mobile.SendGump( new PageQueueGump() ); - } - else - { - e.Mobile.SendMessage( "The page queue is empty." ); - } - } - - public static bool IsHandling( Mobile check ) - { - return m_KeyedByHandler.ContainsKey( check ); - } - - public static bool Contains( Mobile sender ) - { - return m_KeyedBySender.ContainsKey( sender ); - } - - public static int IndexOf( PageEntry e ) - { - return List.IndexOf( e ); - } - - public static void Cancel( Mobile sender ) - { - Remove( (PageEntry) m_KeyedBySender[sender] ); - } - - public static void Remove( PageEntry e ) - { - if ( e == null ) - return; - - e.Stop(); - - List.Remove( e ); - m_KeyedBySender.Remove( e.Sender ); - - if ( e.Handler != null ) - m_KeyedByHandler.Remove( e.Handler ); - } - - public static PageEntry GetEntry( Mobile sender ) - { - return (PageEntry)m_KeyedBySender[sender]; - } - - public static void Remove( Mobile sender ) - { - Remove( GetEntry( sender ) ); - } - - public static ArrayList List { get; } = new ArrayList(); - - public static void Enqueue( PageEntry entry ) - { - List.Add( entry ); - m_KeyedBySender[entry.Sender] = entry; - - bool isStaffOnline = false; - - foreach ( NetState ns in NetState.Instances ) - { - Mobile m = ns.Mobile; - - if ( m != null && m.AccessLevel >= AccessLevel.Counselor && m.AutoPageNotify && !IsHandling( m ) ) - m.SendMessage( "A new page has been placed in the queue." ); - - if (m != null && m.AccessLevel >= AccessLevel.Counselor && m.AutoPageNotify && Core.TickCount - m.LastMoveTime < 600000) - isStaffOnline = true; - } - - if ( !isStaffOnline ) - entry.Sender.SendMessage( "We are sorry, but no staff members are currently available to assist you. Your page will remain in the queue until one becomes available, or until you cancel it manually." ); - - if ( Email.FromAddress != null && Email.SpeechLogPageAddresses != null && entry.SpeechLog != null ) - SendEmail( entry ); - } - - private static void SendEmail( PageEntry entry ) - { - Mobile sender = entry.Sender; - DateTime time = DateTime.UtcNow; - - MailMessage mail = new MailMessage( Email.FromAddress, Email.SpeechLogPageAddresses ); - - mail.Subject = "RunUO Speech Log Page Forwarding"; - - using ( StringWriter writer = new StringWriter() ) - { - writer.WriteLine( "RunUO Speech Log Page - {0}", GetPageTypeName( entry.Type ) ); - writer.WriteLine(); - - writer.WriteLine( "From: '{0}', Account: '{1}'", sender.RawName, sender.Account is Account ? sender.Account.Username : "???" ); - writer.WriteLine( "Location: {0} [{1}]", sender.Location, sender.Map ); - writer.WriteLine( "Sent on: {0}/{1:00}/{2:00} {3}:{4:00}:{5:00}", time.Year, time.Month, time.Day, time.Hour, time.Minute, time.Second ); - writer.WriteLine(); - - writer.WriteLine( "Message:" ); - writer.WriteLine( "'{0}'", entry.Message ); - writer.WriteLine(); - - writer.WriteLine( "Speech Log" ); - writer.WriteLine( "==========" ); - - foreach ( SpeechLogEntry logEntry in entry.SpeechLog ) - { - Mobile from = logEntry.From; - string fromName = from.RawName; - string fromAccount = from.Account is Account ? from.Account.Username : "???"; - DateTime created = logEntry.Created; - string speech = logEntry.Speech; - - writer.WriteLine( "{0}:{1:00}:{2:00} - {3} ({4}): '{5}'", created.Hour, created.Minute, created.Second, fromName, fromAccount, speech ); - } - - mail.Body = writer.ToString(); - } - - Email.AsyncSend( mail ); - } - } -} + public enum PageType + { + Bug, + Stuck, + Account, + Question, + Suggestion, + Other, + VerbalHarassment, + PhysicalHarassment + } + + public class PageEntry + { + // What page types should have a speech log as attachment? + public static readonly PageType[] SpeechLogAttachment = + { + PageType.VerbalHarassment + }; + + private Mobile m_Handler; + + private Timer m_Timer; + + public PageEntry(Mobile sender, string message, PageType type) + { + Sender = sender; + Sent = DateTime.UtcNow; + Message = Utility.FixHtml(message); + Type = type; + PageLocation = sender.Location; + PageMap = sender.Map; + + if (sender is PlayerMobile pm && pm.SpeechLog != null && Array.IndexOf(SpeechLogAttachment, type) >= 0) + SpeechLog = new List(pm.SpeechLog); + + m_Timer = new InternalTimer(this); + m_Timer.Start(); + + StaffHistory history = Reports.Reports.StaffHistory; + + if (history != null) + { + PageInfo = new PageInfo(this); + + history.AddPage(PageInfo); + } + } + + public PageInfo PageInfo{ get; } + + public Mobile Sender{ get; } + + public Mobile Handler + { + get => m_Handler; + set + { + PageQueue.OnHandlerChanged(m_Handler, value, this); + m_Handler = value; + } + } + + public DateTime Sent{ get; } + + public string Message{ get; } + + public PageType Type{ get; } + + public Point3D PageLocation{ get; } + + public Map PageMap{ get; } + + public List SpeechLog{ get; } + + public void Stop() + { + m_Timer?.Stop(); + + m_Timer = null; + } + + public void AddResponse(Mobile mob, string text) + { + if (PageInfo != null) + { + lock (PageInfo) + { + PageInfo.Responses.Add(PageInfo.GetAccount(mob), text); + } + + if (PageInfo.ResFromResp(text) != PageResolution.None) + PageInfo.UpdateResolver(); + } + } + + private class InternalTimer : Timer + { + private static TimeSpan StatusDelay = TimeSpan.FromMinutes(2.0); + + private PageEntry m_Entry; + + public InternalTimer(PageEntry entry) : base(TimeSpan.FromSeconds(1.0), StatusDelay) + { + m_Entry = entry; + } + + protected override void OnTick() + { + int index = PageQueue.IndexOf(m_Entry); + + if (m_Entry.Sender.NetState != null && index != -1) + { + m_Entry.Sender.SendLocalizedMessage(1008077, true, + (index + 1).ToString()); // Thank you for paging. Queue status : + m_Entry.Sender + .SendLocalizedMessage( + 1008084); // You can reference our website at www.uo.com or contact us at support@uo.com. To cancel your page, please select the help button again and select cancel. + + if (m_Entry.Handler != null && m_Entry.Handler.NetState == null) m_Entry.Handler = null; + } + else + { + if (index != -1) + m_Entry.AddResponse(m_Entry.Sender, "[Logout]"); + + PageQueue.Remove(m_Entry); + } + } + } + } + + public class PageQueue + { + private static Hashtable m_KeyedByHandler = new Hashtable(); + private static Hashtable m_KeyedBySender = new Hashtable(); + + public static ArrayList List{ get; } = new ArrayList(); + + public static void Initialize() + { + CommandSystem.Register("Pages", AccessLevel.Counselor, Pages_OnCommand); + } + + public static bool CheckAllowedToPage(Mobile from) + { + if (!(from is PlayerMobile pm)) + return true; + + if (pm.DesignContext != null) + { + from.SendLocalizedMessage( + 500182); // You cannot request help while customizing a house or transferring a character. + return false; + } + + if (pm.PagingSquelched) + { + from.SendMessage("You cannot request help, sorry."); + return false; + } + + return true; + } + + public static string GetPageTypeName(PageType type) + { + if (type == PageType.VerbalHarassment) + return "Verbal Harassment"; + if (type == PageType.PhysicalHarassment) + return "Physical Harassment"; + return type.ToString(); + } + + public static void OnHandlerChanged(Mobile old, Mobile value, PageEntry entry) + { + if (old != null) + m_KeyedByHandler.Remove(old); + + if (value != null) + m_KeyedByHandler[value] = entry; + } + + [Usage("Pages")] + [Description("Opens the page queue menu.")] + private static void Pages_OnCommand(CommandEventArgs e) + { + PageEntry entry = (PageEntry)m_KeyedByHandler[e.Mobile]; + + if (entry != null) + e.Mobile.SendGump(new PageEntryGump(e.Mobile, entry)); + else if (List.Count > 0) + e.Mobile.SendGump(new PageQueueGump()); + else + e.Mobile.SendMessage("The page queue is empty."); + } + + public static bool IsHandling(Mobile check) + { + return m_KeyedByHandler.ContainsKey(check); + } + + public static bool Contains(Mobile sender) + { + return m_KeyedBySender.ContainsKey(sender); + } + + public static int IndexOf(PageEntry e) + { + return List.IndexOf(e); + } + + public static void Cancel(Mobile sender) + { + Remove((PageEntry)m_KeyedBySender[sender]); + } + + public static void Remove(PageEntry e) + { + if (e == null) + return; + + e.Stop(); + + List.Remove(e); + m_KeyedBySender.Remove(e.Sender); + + if (e.Handler != null) + m_KeyedByHandler.Remove(e.Handler); + } + + public static PageEntry GetEntry(Mobile sender) + { + return (PageEntry)m_KeyedBySender[sender]; + } + + public static void Remove(Mobile sender) + { + Remove(GetEntry(sender)); + } + + public static void Enqueue(PageEntry entry) + { + List.Add(entry); + m_KeyedBySender[entry.Sender] = entry; + + bool isStaffOnline = false; + + foreach (NetState ns in NetState.Instances) + { + Mobile m = ns.Mobile; + + if (m != null && m.AccessLevel >= AccessLevel.Counselor && m.AutoPageNotify && !IsHandling(m)) + m.SendMessage("A new page has been placed in the queue."); + + if (m != null && m.AccessLevel >= AccessLevel.Counselor && m.AutoPageNotify && + Core.TickCount - m.LastMoveTime < 600000) + isStaffOnline = true; + } + + if (!isStaffOnline) + entry.Sender.SendMessage( + "We are sorry, but no staff members are currently available to assist you. Your page will remain in the queue until one becomes available, or until you cancel it manually."); + + if (Email.FromAddress != null && Email.SpeechLogPageAddresses != null && entry.SpeechLog != null) + SendEmail(entry); + } + + private static void SendEmail(PageEntry entry) + { + Mobile sender = entry.Sender; + DateTime time = DateTime.UtcNow; + + MailMessage mail = new MailMessage(Email.FromAddress, Email.SpeechLogPageAddresses); + + mail.Subject = "RunUO Speech Log Page Forwarding"; + + using (StringWriter writer = new StringWriter()) + { + writer.WriteLine("RunUO Speech Log Page - {0}", GetPageTypeName(entry.Type)); + writer.WriteLine(); + + writer.WriteLine("From: '{0}', Account: '{1}'", sender.RawName, + sender.Account is Account ? sender.Account.Username : "???"); + writer.WriteLine("Location: {0} [{1}]", sender.Location, sender.Map); + writer.WriteLine("Sent on: {0}/{1:00}/{2:00} {3}:{4:00}:{5:00}", time.Year, time.Month, time.Day, time.Hour, + time.Minute, time.Second); + writer.WriteLine(); + + writer.WriteLine("Message:"); + writer.WriteLine("'{0}'", entry.Message); + writer.WriteLine(); + + writer.WriteLine("Speech Log"); + writer.WriteLine("=========="); + + foreach (SpeechLogEntry logEntry in entry.SpeechLog) + { + Mobile from = logEntry.From; + string fromName = from.RawName; + string fromAccount = from.Account is Account ? from.Account.Username : "???"; + DateTime created = logEntry.Created; + string speech = logEntry.Speech; + + writer.WriteLine("{0}:{1:00}:{2:00} - {3} ({4}): '{5}'", created.Hour, created.Minute, created.Second, + fromName, fromAccount, speech); + } + + mail.Body = writer.ToString(); + } + + Email.AsyncSend(mail); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Help/PageQueueGump.cs b/Scripts/Engines/Help/PageQueueGump.cs index 7eabb0d19..7a9d7cc03 100644 --- a/Scripts/Engines/Help/PageQueueGump.cs +++ b/Scripts/Engines/Help/PageQueueGump.cs @@ -1,832 +1,831 @@ using System; -using System.IO; using System.Collections; -using Server.Network; +using System.IO; using Server.Gumps; +using Server.Network; namespace Server.Engines.Help { - public class MessageSentGump : Gump - { - private string m_Name, m_Text; - private Mobile m_Mobile; - - public MessageSentGump( Mobile mobile, string name, string text ) : base( 30, 30 ) - { - m_Name = name; - m_Text = text; - m_Mobile = mobile; - - Closable = false; - - AddPage( 0 ); - - AddBackground( 0, 0, 92, 75, 0xA3C ); - - AddImageTiled( 5, 7, 82, 61, 0xA40 ); - AddAlphaRegion( 5, 7, 82, 61 ); - - AddImageTiled( 9, 11, 21, 53, 0xBBC ); - - AddButton( 10, 12, 0x7D2, 0x7D2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 34, 28, 65, 24, 3001002, 0xFFFFFF, false, false ); // Message - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - m_Mobile.SendGump( new PageResponseGump( m_Mobile, m_Name, m_Text ) ); - - //m_Mobile.SendMessage( 0x482, "{0} tells you:", m_Name ); - //m_Mobile.SendMessage( 0x482, m_Text ); - } - } - - public class PageQueueGump : Gump - { - private PageEntry[] m_List; - - public PageQueueGump() : base( 30, 30 ) - { - Add( new GumpPage( 0 ) ); - //Add( new GumpBackground( 0, 0, 410, 448, 9200 ) ); - Add( new GumpImageTiled( 0, 0, 410, 448, 0xA40 ) ); - Add( new GumpAlphaRegion( 1, 1, 408, 446 ) ); - - Add( new GumpLabel( 180, 12, 2100, "Page Queue" ) ); - - ArrayList list = PageQueue.List; - - for ( int i = 0; i < list.Count; ) - { - PageEntry e = (PageEntry)list[i]; - - if ( e.Sender.Deleted || e.Sender.NetState == null ) - { - e.AddResponse( e.Sender, "[Logout]" ); - PageQueue.Remove( e ); - } - else - { - ++i; - } - } - - m_List = (PageEntry[])list.ToArray( typeof( PageEntry ) ); - - if ( m_List.Length > 0 ) - { - Add( new GumpPage( 1 ) ); - - for ( int i = 0; i < m_List.Length; ++i ) - { - PageEntry e = m_List[i]; - - if ( i >= 5 && (i % 5) == 0 ) - { - Add( new GumpButton( 368, 12, 0xFA5, 0xFA7, 0, GumpButtonType.Page, (i / 5) + 1 ) ); - Add( new GumpLabel( 298, 12, 2100, "Next Page" ) ); - Add( new GumpPage( (i / 5) + 1 ) ); - Add( new GumpButton( 12, 12, 0xFAE, 0xFB0, 0, GumpButtonType.Page, (i / 5) ) ); - Add( new GumpLabel( 48, 12, 2100, "Previous Page" ) ); - } - - string typeString = PageQueue.GetPageTypeName( e.Type ); - - string html = - $"[{typeString}] {e.Message} [{(e.Handler == null ? "Unhandled" : "Handling")}]"; - - Add( new GumpHtml( 12, 44 + ((i % 5) * 80), 350, 70, html, true, true ) ); - Add( new GumpButton( 370, 44 + ((i % 5) * 80) + 24, 0xFA5, 0xFA7, i + 1, GumpButtonType.Reply, 0 ) ); - } - } - else - { - Add( new GumpLabel( 12, 44, 2100, "The page queue is empty." ) ); - } - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID >= 1 && info.ButtonID <= m_List.Length ) - { - if ( PageQueue.List.IndexOf( m_List[info.ButtonID - 1] ) >= 0 ) - { - PageEntryGump g = new PageEntryGump( state.Mobile, m_List[info.ButtonID - 1] ); - - g.SendTo( state ); - } - else - { - state.Mobile.SendGump( new PageQueueGump() ); - state.Mobile.SendMessage( "That page has been removed." ); - } - } - } - } - - public class PredefinedResponse - { - public string Title { get; set; } - - public string Message { get; set; } - - public PredefinedResponse( string title, string message ) - { - Title = title; - Message = message; - } - - private static ArrayList m_List; - - public static ArrayList List - { - get - { - if ( m_List == null ) - m_List = Load(); - - return m_List; - } - } - - public static PredefinedResponse Add( string title, string message ) - { - if ( m_List == null ) - m_List = Load(); - - PredefinedResponse resp = new PredefinedResponse( title, message ); - - m_List.Add( resp ); - Save(); - - return resp; - } - - public static void Save() - { - if ( m_List == null ) - m_List = Load(); - - try - { - string path = Path.Combine( Core.BaseDirectory, "Data/pageresponse.cfg" ); - - using ( StreamWriter op = new StreamWriter( path ) ) - { - for ( int i = 0; i < m_List.Count; ++i ) - { - PredefinedResponse resp = (PredefinedResponse)m_List[i]; - - op.WriteLine( "{0}\t{1}", resp.Title, resp.Message ); - } - } - } - catch ( Exception e ) - { - Console.WriteLine( e ); - } - } - - public static ArrayList Load() - { - ArrayList list = new ArrayList(); - - string path = Path.Combine( Core.BaseDirectory, "Data/pageresponse.cfg" ); - - if ( File.Exists( path ) ) - { - try - { - using ( StreamReader ip = new StreamReader( path ) ) - { - string line; - - while ( (line = ip.ReadLine()) != null ) - { - try - { - line = line.Trim(); - - if ( line.Length == 0 || line.StartsWith( "#" ) ) - continue; - - string[] split = line.Split( '\t' ); - - if ( split.Length == 2 ) - list.Add( new PredefinedResponse( split[0], split[1] ) ); - } - catch - { - } - } - } - } - catch ( Exception e ) - { - Console.WriteLine( e ); - } - } - - return list; - } - } - - public class PredefGump : Gump - { - private const int LabelColor32 = 0xFFFFFF; - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - public void AddTextInput( int x, int y, int w, int h, int id, string def ) - { - AddImageTiled( x, y, w, h, 0xA40 ); - AddImageTiled( x + 1, y + 1, w - 2, h - 2, 0xBBC ); - AddTextEntry( x + 3, y + 1, w - 4, h - 2, 0x480, id, def ); - } - - private Mobile m_From; - private PredefinedResponse m_Response; - - public PredefGump( Mobile from, PredefinedResponse response ) : base( 30, 30 ) - { - m_From = from; - m_Response = response; - - from.CloseGump( typeof( PredefGump ) ); - - bool canEdit = ( from.AccessLevel >= AccessLevel.GameMaster ); - - AddPage( 0 ); - - if ( response == null ) - { - AddImageTiled( 0, 0, 410, 448, 0xA40 ); - AddAlphaRegion( 1, 1, 408, 446 ); - - AddHtml( 10, 10, 390, 20, Color( Center( "Predefined Responses" ), LabelColor32 ), false, false ); - - ArrayList list = PredefinedResponse.List; - - AddPage( 1 ); - - int i; - - for ( i = 0; i < list.Count; ++i ) - { - if ( i >= 5 && (i % 5) == 0 ) - { - AddButton( 368, 10, 0xFA5, 0xFA7, 0, GumpButtonType.Page, (i / 5) + 1 ); - AddLabel( 298, 10, 2100, "Next Page" ); - AddPage( (i / 5) + 1 ); - AddButton( 12, 10, 0xFAE, 0xFB0, 0, GumpButtonType.Page, i / 5 ); - AddLabel( 48, 10, 2100, "Previous Page" ); - } - - PredefinedResponse resp = (PredefinedResponse)list[i]; - - string html = $"{resp.Title}
{resp.Message}"; - - AddHtml( 12, 44 + ((i % 5) * 80), 350, 70, html, true, true ); - - if ( canEdit ) - { - AddButton( 370, 44 + ((i % 5) * 80) + 24, 0xFA5, 0xFA7, 2 + (i * 3), GumpButtonType.Reply, 0 ); - - if ( i > 0 ) - AddButton( 377, 44 + ((i % 5) * 80) + 2, 0x15E0, 0x15E4, 3 + (i * 3), GumpButtonType.Reply, 0 ); - else - AddImage( 377, 44 + ((i % 5) * 80) + 2, 0x25E4 ); - - if ( i < (list.Count - 1) ) - AddButton( 377, 44 + ((i % 5) * 80) + 70 - 2 - 16, 0x15E2, 0x15E6, 4 + (i * 3), GumpButtonType.Reply, 0 ); - else - AddImage( 377, 44 + ((i % 5) * 80) + 70 - 2 - 16, 0x25E8 ); - } - } - - if ( canEdit ) - { - if ( i >= 5 && (i % 5) == 0 ) - { - AddButton( 368, 10, 0xFA5, 0xFA7, 0, GumpButtonType.Page, (i / 5) + 1 ); - AddLabel( 298, 10, 2100, "Next Page" ); - AddPage( (i / 5) + 1 ); - AddButton( 12, 10, 0xFAE, 0xFB0, 0, GumpButtonType.Page, i / 5 ); - AddLabel( 48, 10, 2100, "Previous Page" ); - } - - AddButton( 12, 44 + ((i % 5) * 80), 0xFAB, 0xFAD, 1, GumpButtonType.Reply, 0 ); - AddHtml( 45, 44 + ((i % 5) * 80), 200, 20, Color( "New Response", LabelColor32 ), false, false ); - } - } - else if ( canEdit ) - { - AddImageTiled( 0, 0, 410, 250, 0xA40 ); - AddAlphaRegion( 1, 1, 408, 248 ); - - AddHtml( 10, 10, 390, 20, Color( Center( "Predefined Response Editor" ), LabelColor32 ), false, false ); - - AddButton( 10, 40, 0xFB1, 0xFB3, 1, GumpButtonType.Reply, 0 ); - AddHtml( 45, 40, 200, 20, Color( "Remove", LabelColor32 ), false, false ); - - AddButton( 10, 70, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0 ); - AddHtml( 45, 70, 200, 20, Color( "Title:", LabelColor32 ), false, false ); - AddTextInput( 10, 90, 300, 20, 0, response.Title ); - - AddButton( 10, 120, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0 ); - AddHtml( 45, 120, 200, 20, Color( "Message:", LabelColor32 ), false, false ); - AddTextInput( 10, 140, 390, 100, 1, response.Message ); - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_From.AccessLevel < AccessLevel.Administrator ) - return; - - if ( m_Response == null ) - { - int index = info.ButtonID - 1; - - if ( index == 0 ) - { - PredefinedResponse resp = new PredefinedResponse( "", "" ); - - ArrayList list = PredefinedResponse.List; - list.Add( resp ); - - m_From.SendGump( new PredefGump( m_From, resp ) ); - } - else - { - --index; - - int type = index % 3; - index /= 3; - - ArrayList list = PredefinedResponse.List; - - if ( index >= 0 && index < list.Count ) - { - PredefinedResponse resp = (PredefinedResponse)list[index]; - - switch ( type ) - { - case 0: // edit - { - m_From.SendGump( new PredefGump( m_From, resp ) ); - break; - } - case 1: // move up - { - if ( index > 0 ) - { - list.RemoveAt( index ); - list.Insert( index - 1, resp ); - - PredefinedResponse.Save(); - m_From.SendGump( new PredefGump( m_From, null ) ); - } - - break; - } - case 2: // move down - { - if ( index < (list.Count - 1) ) - { - list.RemoveAt( index ); - list.Insert( index + 1, resp ); - - PredefinedResponse.Save(); - m_From.SendGump( new PredefGump( m_From, null ) ); - } - - break; - } - } - } - } - } - else - { - ArrayList list = PredefinedResponse.List; - - switch ( info.ButtonID ) - { - case 1: - { - list.Remove( m_Response ); - - PredefinedResponse.Save(); - m_From.SendGump( new PredefGump( m_From, null ) ); - break; - } - case 2: - { - TextRelay te = info.GetTextEntry( 0 ); - - if ( te != null ) - m_Response.Title = te.Text; - - PredefinedResponse.Save(); - m_From.SendGump( new PredefGump( m_From, m_Response ) ); - - break; - } - case 3: - { - TextRelay te = info.GetTextEntry( 1 ); - - if ( te != null ) - m_Response.Message = te.Text; - - PredefinedResponse.Save(); - m_From.SendGump( new PredefGump( m_From, m_Response ) ); - - break; - } - } - } - } - } - - public class PageEntryGump : Gump - { - private PageEntry m_Entry; - private Mobile m_Mobile; - - private static int[] m_AccessLevelHues = { - 2100, - 2122, - 2117, - 2129, - 2415, - 2415, - 2415 - }; - - public PageEntryGump( Mobile m, PageEntry entry ) : base( 30, 30 ) - { - try - { - m_Mobile = m; - m_Entry = entry; - - int buttons = 0; - - int bottom = 356; - - AddPage( 0 ); - - AddImageTiled( 0, 0, 410, 456, 0xA40 ); - AddAlphaRegion( 1, 1, 408, 454 ); - - AddPage( 1 ); - - AddLabel( 18, 18, 2100, "Sent:" ); - AddLabelCropped( 128, 18, 264, 20, 2100, entry.Sent.ToString() ); - - AddLabel( 18, 38, 2100, "Sender:" ); - AddLabelCropped( 128, 38, 264, 20, 2100, - $"{entry.Sender.RawName} {entry.Sender.Location} [{entry.Sender.Map}]"); - - AddButton( 18, bottom - (buttons * 22), 0xFAB, 0xFAD, 8, GumpButtonType.Reply, 0 ); - AddImageTiled( 52, bottom - (buttons * 22) + 1, 340, 80, 0xA40/*0xBBC*//*0x2458*/ ); - AddImageTiled( 53, bottom - (buttons * 22) + 2, 338, 78, 0xBBC/*0x2426*/ ); - AddTextEntry( 55, bottom - (buttons++ * 22) + 2, 336, 78, 0x480, 0, "" ); - - AddButton( 18, bottom - (buttons * 22), 0xFA5, 0xFA7, 0, GumpButtonType.Page, 2 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Predefined Response" ); - - if ( entry.Sender != m ) - { - AddButton( 18, bottom - (buttons * 22), 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Go to Sender" ); - } - - AddLabel( 18, 58, 2100, "Handler:" ); - - if ( entry.Handler == null ) - { - AddLabelCropped( 128, 58, 264, 20, 2100, "Unhandled" ); - - AddButton( 18, bottom - (buttons * 22), 0xFB1, 0xFB3, 5, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Delete Page" ); - - AddButton( 18, bottom - (buttons * 22), 0xFB7, 0xFB9, 4, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Handle Page" ); - } - else - { - AddLabelCropped( 128, 58, 264, 20, m_AccessLevelHues[(int)entry.Handler.AccessLevel], entry.Handler.Name ); - - if ( entry.Handler != m ) - { - AddButton( 18, bottom - (buttons * 22), 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Go to Handler" ); - } - else - { - AddButton( 18, bottom - (buttons * 22), 0xFA2, 0xFA4, 6, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Abandon Page" ); - - AddButton( 18, bottom - (buttons * 22), 0xFB7, 0xFB9, 7, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Page Handled" ); - } - } - - AddLabel( 18, 78, 2100, "Page Location:" ); - AddLabelCropped( 128, 78, 264, 20, 2100, $"{entry.PageLocation} [{entry.PageMap}]"); - - AddButton( 18, bottom - (buttons * 22), 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "Go to Page Location" ); - - if ( entry.SpeechLog != null ) - { - AddButton( 18, bottom - (buttons * 22), 0xFA5, 0xFA7, 10, GumpButtonType.Reply, 0 ); - AddLabel( 52, bottom - (buttons++ * 22), 2100, "View Speech Log" ); - } - - AddLabel( 18, 98, 2100, "Page Type:" ); - AddLabelCropped( 128, 98, 264, 20, 2100, PageQueue.GetPageTypeName( entry.Type ) ); - - AddLabel( 18, 118, 2100, "Message:" ); - AddHtml( 128, 118, 250, 100, entry.Message, true, true ); - - AddPage( 2 ); - - ArrayList preresp = PredefinedResponse.List; - - AddButton( 18, 18, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1 ); - AddButton( 410 - 18 - 32, 18, 0xFAB, 0xFAC, 9, GumpButtonType.Reply, 0 ); - - if ( preresp.Count == 0 ) - { - AddLabel( 52, 18, 2100, "There are no predefined responses." ); - } - else - { - AddLabel( 52, 18, 2100, "Back" ); - - for ( int i = 0; i < preresp.Count; ++i ) - { - AddButton( 18, 40 + (i * 22), 0xFA5, 0xFA7, 100 + i, GumpButtonType.Reply, 0 ); - AddLabel( 52, 40 + (i * 22), 2100, ((PredefinedResponse)preresp[i]).Title ); - } - } - } - catch ( Exception e ) - { - Console.WriteLine(e); - } - } - - public void Resend( NetState state ) - { - PageEntryGump g = new PageEntryGump( m_Mobile, m_Entry ); - - g.SendTo( state ); - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID != 0 && PageQueue.List.IndexOf( m_Entry ) < 0 ) - { - state.Mobile.SendGump( new PageQueueGump() ); - state.Mobile.SendMessage( "That page has been removed." ); - return; - } - - switch ( info.ButtonID ) - { - case 0: // close - { - if ( m_Entry.Handler != state.Mobile ) - { - PageQueueGump g = new PageQueueGump(); - - g.SendTo( state ); - } - - break; - } - case 1: // go to sender - { - Mobile m = state.Mobile; - - if ( m_Entry.Sender.Deleted ) - { - m.SendMessage( "That character no longer exists." ); - } - else if ( m_Entry.Sender.Map == null || m_Entry.Sender.Map == Map.Internal ) - { - m.SendMessage( "That character is not in the world." ); - } - else - { - m_Entry.AddResponse( state.Mobile, "[Go Sender]" ); - m.MoveToWorld( m_Entry.Sender.Location, m_Entry.Sender.Map ); - - m.SendMessage( "You have been teleported to that page's sender." ); - - Resend( state ); - } - - break; - } - case 2: // go to handler - { - Mobile m = state.Mobile; - Mobile h = m_Entry.Handler; - - if ( h != null ) - { - if ( h.Deleted ) - { - m.SendMessage( "That character no longer exists." ); - } - else if ( h.Map == null || h.Map == Map.Internal ) - { - m.SendMessage( "That character is not in the world." ); - } - else - { - m_Entry.AddResponse( state.Mobile, "[Go Handler]" ); - m.MoveToWorld( h.Location, h.Map ); - - m.SendMessage( "You have been teleported to that page's handler." ); - Resend( state ); - } - } - else - { - m.SendMessage( "Nobody is handling that page." ); - Resend( state ); - } - - break; - } - case 3: // go to page location - { - Mobile m = state.Mobile; - - if ( m_Entry.PageMap == null || m_Entry.PageMap == Map.Internal ) - { - m.SendMessage( "That location is not in the world." ); - } - else - { - m_Entry.AddResponse( state.Mobile, "[Go PageLoc]" ); - m.MoveToWorld( m_Entry.PageLocation, m_Entry.PageMap ); - - state.Mobile.SendMessage( "You have been teleported to the original page location." ); - - Resend( state ); - } - - break; - } - case 4: // handle page - { - if ( m_Entry.Handler == null ) - { - m_Entry.AddResponse( state.Mobile, "[Handling]" ); - m_Entry.Handler = state.Mobile; - - state.Mobile.SendMessage( "You are now handling the page." ); - } - else - { - state.Mobile.SendMessage( "Someone is already handling that page." ); - } - - Resend( state ); - - break; - } - case 5: // delete page - { - if ( m_Entry.Handler == null ) - { - m_Entry.AddResponse( state.Mobile, "[Deleting]" ); - PageQueue.Remove( m_Entry ); - - state.Mobile.SendMessage( "You delete the page." ); - - PageQueueGump g = new PageQueueGump(); - - g.SendTo( state ); - } - else - { - state.Mobile.SendMessage( "Someone is handling that page, it can not be deleted." ); - - Resend( state ); - } - - break; - } - case 6: // abandon page - { - if ( m_Entry.Handler == state.Mobile ) - { - m_Entry.AddResponse( state.Mobile, "[Abandoning]" ); - state.Mobile.SendMessage( "You abandon the page." ); - - m_Entry.Handler = null; - } - else - { - state.Mobile.SendMessage( "You are not handling that page." ); - } - - Resend( state ); - - break; - } - case 7: // page handled - { - if ( m_Entry.Handler == state.Mobile ) - { - m_Entry.AddResponse( state.Mobile, "[Handled]" ); - PageQueue.Remove( m_Entry ); - - m_Entry.Handler = null; - - state.Mobile.SendMessage( "You mark the page as handled, and remove it from the queue." ); - - PageQueueGump g = new PageQueueGump(); - - g.SendTo( state ); - } - else - { - state.Mobile.SendMessage( "You are not handling that page." ); - - Resend( state ); - } - - break; - } - case 8: // Send message - { - TextRelay text = info.GetTextEntry( 0 ); - - if ( text != null ) - { - m_Entry.AddResponse( state.Mobile, "[Response] " + text.Text ); - m_Entry.Sender.SendGump( new MessageSentGump( m_Entry.Sender, state.Mobile.Name, text.Text ) ); - //m_Entry.Sender.SendMessage( 0x482, "{0} tells you:", state.Mobile.Name ); - //m_Entry.Sender.SendMessage( 0x482, text.Text ); - } - - Resend( state ); - - break; - } - case 9: // predef overview - { - Resend( state ); - state.Mobile.SendGump( new PredefGump( state.Mobile, null ) ); - - break; - } - case 10: // View Speech Log - { - Resend( state ); - - if ( m_Entry.SpeechLog != null ) - { - Gump gump = new SpeechLogGump( m_Entry.Sender, m_Entry.SpeechLog ); - state.Mobile.SendGump( gump ); - } - - break; - } - default: - { - int index = info.ButtonID - 100; - ArrayList preresp = PredefinedResponse.List; - - if ( index >= 0 && index < preresp.Count ) - { - m_Entry.AddResponse( state.Mobile, "[PreDef] " + ((PredefinedResponse)preresp[index]).Title ); - m_Entry.Sender.SendGump( new MessageSentGump( m_Entry.Sender, state.Mobile.Name, ((PredefinedResponse)preresp[index]).Message ) ); - } - - Resend( state ); - - break; - } - } - } - } + public class MessageSentGump : Gump + { + private Mobile m_Mobile; + private string m_Name, m_Text; + + public MessageSentGump(Mobile mobile, string name, string text) : base(30, 30) + { + m_Name = name; + m_Text = text; + m_Mobile = mobile; + + Closable = false; + + AddPage(0); + + AddBackground(0, 0, 92, 75, 0xA3C); + + AddImageTiled(5, 7, 82, 61, 0xA40); + AddAlphaRegion(5, 7, 82, 61); + + AddImageTiled(9, 11, 21, 53, 0xBBC); + + AddButton(10, 12, 0x7D2, 0x7D2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(34, 28, 65, 24, 3001002, 0xFFFFFF, false, false); // Message + } + + public override void OnResponse(NetState state, RelayInfo info) + { + m_Mobile.SendGump(new PageResponseGump(m_Mobile, m_Name, m_Text)); + + //m_Mobile.SendMessage( 0x482, "{0} tells you:", m_Name ); + //m_Mobile.SendMessage( 0x482, m_Text ); + } + } + + public class PageQueueGump : Gump + { + private PageEntry[] m_List; + + public PageQueueGump() : base(30, 30) + { + Add(new GumpPage(0)); + //Add( new GumpBackground( 0, 0, 410, 448, 9200 ) ); + Add(new GumpImageTiled(0, 0, 410, 448, 0xA40)); + Add(new GumpAlphaRegion(1, 1, 408, 446)); + + Add(new GumpLabel(180, 12, 2100, "Page Queue")); + + ArrayList list = PageQueue.List; + + for (int i = 0; i < list.Count;) + { + PageEntry e = (PageEntry)list[i]; + + if (e.Sender.Deleted || e.Sender.NetState == null) + { + e.AddResponse(e.Sender, "[Logout]"); + PageQueue.Remove(e); + } + else + { + ++i; + } + } + + m_List = (PageEntry[])list.ToArray(typeof(PageEntry)); + + if (m_List.Length > 0) + { + Add(new GumpPage(1)); + + for (int i = 0; i < m_List.Length; ++i) + { + PageEntry e = m_List[i]; + + if (i >= 5 && i % 5 == 0) + { + Add(new GumpButton(368, 12, 0xFA5, 0xFA7, 0, GumpButtonType.Page, i / 5 + 1)); + Add(new GumpLabel(298, 12, 2100, "Next Page")); + Add(new GumpPage(i / 5 + 1)); + Add(new GumpButton(12, 12, 0xFAE, 0xFB0, 0, GumpButtonType.Page, i / 5)); + Add(new GumpLabel(48, 12, 2100, "Previous Page")); + } + + string typeString = PageQueue.GetPageTypeName(e.Type); + + string html = + $"[{typeString}] {e.Message} [{(e.Handler == null ? "Unhandled" : "Handling")}]"; + + Add(new GumpHtml(12, 44 + i % 5 * 80, 350, 70, html, true, true)); + Add(new GumpButton(370, 44 + i % 5 * 80 + 24, 0xFA5, 0xFA7, i + 1, GumpButtonType.Reply, 0)); + } + } + else + { + Add(new GumpLabel(12, 44, 2100, "The page queue is empty.")); + } + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID >= 1 && info.ButtonID <= m_List.Length) + { + if (PageQueue.List.IndexOf(m_List[info.ButtonID - 1]) >= 0) + { + PageEntryGump g = new PageEntryGump(state.Mobile, m_List[info.ButtonID - 1]); + + g.SendTo(state); + } + else + { + state.Mobile.SendGump(new PageQueueGump()); + state.Mobile.SendMessage("That page has been removed."); + } + } + } + } + + public class PredefinedResponse + { + private static ArrayList m_List; + + public PredefinedResponse(string title, string message) + { + Title = title; + Message = message; + } + + public string Title{ get; set; } + + public string Message{ get; set; } + + public static ArrayList List + { + get + { + if (m_List == null) + m_List = Load(); + + return m_List; + } + } + + public static PredefinedResponse Add(string title, string message) + { + if (m_List == null) + m_List = Load(); + + PredefinedResponse resp = new PredefinedResponse(title, message); + + m_List.Add(resp); + Save(); + + return resp; + } + + public static void Save() + { + if (m_List == null) + m_List = Load(); + + try + { + string path = Path.Combine(Core.BaseDirectory, "Data/pageresponse.cfg"); + + using (StreamWriter op = new StreamWriter(path)) + { + for (int i = 0; i < m_List.Count; ++i) + { + PredefinedResponse resp = (PredefinedResponse)m_List[i]; + + op.WriteLine("{0}\t{1}", resp.Title, resp.Message); + } + } + } + catch (Exception e) + { + Console.WriteLine(e); + } + } + + public static ArrayList Load() + { + ArrayList list = new ArrayList(); + + string path = Path.Combine(Core.BaseDirectory, "Data/pageresponse.cfg"); + + if (File.Exists(path)) + try + { + using (StreamReader ip = new StreamReader(path)) + { + string line; + + while ((line = ip.ReadLine()) != null) + try + { + line = line.Trim(); + + if (line.Length == 0 || line.StartsWith("#")) + continue; + + string[] split = line.Split('\t'); + + if (split.Length == 2) + list.Add(new PredefinedResponse(split[0], split[1])); + } + catch + { + } + } + } + catch (Exception e) + { + Console.WriteLine(e); + } + + return list; + } + } + + public class PredefGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + + private Mobile m_From; + private PredefinedResponse m_Response; + + public PredefGump(Mobile from, PredefinedResponse response) : base(30, 30) + { + m_From = from; + m_Response = response; + + from.CloseGump(typeof(PredefGump)); + + bool canEdit = from.AccessLevel >= AccessLevel.GameMaster; + + AddPage(0); + + if (response == null) + { + AddImageTiled(0, 0, 410, 448, 0xA40); + AddAlphaRegion(1, 1, 408, 446); + + AddHtml(10, 10, 390, 20, Color(Center("Predefined Responses"), LabelColor32), false, false); + + ArrayList list = PredefinedResponse.List; + + AddPage(1); + + int i; + + for (i = 0; i < list.Count; ++i) + { + if (i >= 5 && i % 5 == 0) + { + AddButton(368, 10, 0xFA5, 0xFA7, 0, GumpButtonType.Page, i / 5 + 1); + AddLabel(298, 10, 2100, "Next Page"); + AddPage(i / 5 + 1); + AddButton(12, 10, 0xFAE, 0xFB0, 0, GumpButtonType.Page, i / 5); + AddLabel(48, 10, 2100, "Previous Page"); + } + + PredefinedResponse resp = (PredefinedResponse)list[i]; + + string html = $"{resp.Title}
{resp.Message}"; + + AddHtml(12, 44 + i % 5 * 80, 350, 70, html, true, true); + + if (canEdit) + { + AddButton(370, 44 + i % 5 * 80 + 24, 0xFA5, 0xFA7, 2 + i * 3, GumpButtonType.Reply, 0); + + if (i > 0) + AddButton(377, 44 + i % 5 * 80 + 2, 0x15E0, 0x15E4, 3 + i * 3, GumpButtonType.Reply, 0); + else + AddImage(377, 44 + i % 5 * 80 + 2, 0x25E4); + + if (i < list.Count - 1) + AddButton(377, 44 + i % 5 * 80 + 70 - 2 - 16, 0x15E2, 0x15E6, 4 + i * 3, GumpButtonType.Reply, + 0); + else + AddImage(377, 44 + i % 5 * 80 + 70 - 2 - 16, 0x25E8); + } + } + + if (canEdit) + { + if (i >= 5 && i % 5 == 0) + { + AddButton(368, 10, 0xFA5, 0xFA7, 0, GumpButtonType.Page, i / 5 + 1); + AddLabel(298, 10, 2100, "Next Page"); + AddPage(i / 5 + 1); + AddButton(12, 10, 0xFAE, 0xFB0, 0, GumpButtonType.Page, i / 5); + AddLabel(48, 10, 2100, "Previous Page"); + } + + AddButton(12, 44 + i % 5 * 80, 0xFAB, 0xFAD, 1, GumpButtonType.Reply, 0); + AddHtml(45, 44 + i % 5 * 80, 200, 20, Color("New Response", LabelColor32), false, false); + } + } + else if (canEdit) + { + AddImageTiled(0, 0, 410, 250, 0xA40); + AddAlphaRegion(1, 1, 408, 248); + + AddHtml(10, 10, 390, 20, Color(Center("Predefined Response Editor"), LabelColor32), false, false); + + AddButton(10, 40, 0xFB1, 0xFB3, 1, GumpButtonType.Reply, 0); + AddHtml(45, 40, 200, 20, Color("Remove", LabelColor32), false, false); + + AddButton(10, 70, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0); + AddHtml(45, 70, 200, 20, Color("Title:", LabelColor32), false, false); + AddTextInput(10, 90, 300, 20, 0, response.Title); + + AddButton(10, 120, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0); + AddHtml(45, 120, 200, 20, Color("Message:", LabelColor32), false, false); + AddTextInput(10, 140, 390, 100, 1, response.Message); + } + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + public void AddTextInput(int x, int y, int w, int h, int id, string def) + { + AddImageTiled(x, y, w, h, 0xA40); + AddImageTiled(x + 1, y + 1, w - 2, h - 2, 0xBBC); + AddTextEntry(x + 3, y + 1, w - 4, h - 2, 0x480, id, def); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_From.AccessLevel < AccessLevel.Administrator) + return; + + if (m_Response == null) + { + int index = info.ButtonID - 1; + + if (index == 0) + { + PredefinedResponse resp = new PredefinedResponse("", ""); + + ArrayList list = PredefinedResponse.List; + list.Add(resp); + + m_From.SendGump(new PredefGump(m_From, resp)); + } + else + { + --index; + + int type = index % 3; + index /= 3; + + ArrayList list = PredefinedResponse.List; + + if (index >= 0 && index < list.Count) + { + PredefinedResponse resp = (PredefinedResponse)list[index]; + + switch (type) + { + case 0: // edit + { + m_From.SendGump(new PredefGump(m_From, resp)); + break; + } + case 1: // move up + { + if (index > 0) + { + list.RemoveAt(index); + list.Insert(index - 1, resp); + + PredefinedResponse.Save(); + m_From.SendGump(new PredefGump(m_From, null)); + } + + break; + } + case 2: // move down + { + if (index < list.Count - 1) + { + list.RemoveAt(index); + list.Insert(index + 1, resp); + + PredefinedResponse.Save(); + m_From.SendGump(new PredefGump(m_From, null)); + } + + break; + } + } + } + } + } + else + { + ArrayList list = PredefinedResponse.List; + + switch (info.ButtonID) + { + case 1: + { + list.Remove(m_Response); + + PredefinedResponse.Save(); + m_From.SendGump(new PredefGump(m_From, null)); + break; + } + case 2: + { + TextRelay te = info.GetTextEntry(0); + + if (te != null) + m_Response.Title = te.Text; + + PredefinedResponse.Save(); + m_From.SendGump(new PredefGump(m_From, m_Response)); + + break; + } + case 3: + { + TextRelay te = info.GetTextEntry(1); + + if (te != null) + m_Response.Message = te.Text; + + PredefinedResponse.Save(); + m_From.SendGump(new PredefGump(m_From, m_Response)); + + break; + } + } + } + } + } + + public class PageEntryGump : Gump + { + private static int[] m_AccessLevelHues = + { + 2100, + 2122, + 2117, + 2129, + 2415, + 2415, + 2415 + }; + + private PageEntry m_Entry; + private Mobile m_Mobile; + + public PageEntryGump(Mobile m, PageEntry entry) : base(30, 30) + { + try + { + m_Mobile = m; + m_Entry = entry; + + int buttons = 0; + + int bottom = 356; + + AddPage(0); + + AddImageTiled(0, 0, 410, 456, 0xA40); + AddAlphaRegion(1, 1, 408, 454); + + AddPage(1); + + AddLabel(18, 18, 2100, "Sent:"); + AddLabelCropped(128, 18, 264, 20, 2100, entry.Sent.ToString()); + + AddLabel(18, 38, 2100, "Sender:"); + AddLabelCropped(128, 38, 264, 20, 2100, + $"{entry.Sender.RawName} {entry.Sender.Location} [{entry.Sender.Map}]"); + + AddButton(18, bottom - buttons * 22, 0xFAB, 0xFAD, 8, GumpButtonType.Reply, 0); + AddImageTiled(52, bottom - buttons * 22 + 1, 340, 80, 0xA40 /*0xBBC*/ /*0x2458*/); + AddImageTiled(53, bottom - buttons * 22 + 2, 338, 78, 0xBBC /*0x2426*/); + AddTextEntry(55, bottom - buttons++ * 22 + 2, 336, 78, 0x480, 0, ""); + + AddButton(18, bottom - buttons * 22, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 2); + AddLabel(52, bottom - buttons++ * 22, 2100, "Predefined Response"); + + if (entry.Sender != m) + { + AddButton(18, bottom - buttons * 22, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Go to Sender"); + } + + AddLabel(18, 58, 2100, "Handler:"); + + if (entry.Handler == null) + { + AddLabelCropped(128, 58, 264, 20, 2100, "Unhandled"); + + AddButton(18, bottom - buttons * 22, 0xFB1, 0xFB3, 5, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Delete Page"); + + AddButton(18, bottom - buttons * 22, 0xFB7, 0xFB9, 4, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Handle Page"); + } + else + { + AddLabelCropped(128, 58, 264, 20, m_AccessLevelHues[(int)entry.Handler.AccessLevel], entry.Handler.Name); + + if (entry.Handler != m) + { + AddButton(18, bottom - buttons * 22, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Go to Handler"); + } + else + { + AddButton(18, bottom - buttons * 22, 0xFA2, 0xFA4, 6, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Abandon Page"); + + AddButton(18, bottom - buttons * 22, 0xFB7, 0xFB9, 7, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Page Handled"); + } + } + + AddLabel(18, 78, 2100, "Page Location:"); + AddLabelCropped(128, 78, 264, 20, 2100, $"{entry.PageLocation} [{entry.PageMap}]"); + + AddButton(18, bottom - buttons * 22, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "Go to Page Location"); + + if (entry.SpeechLog != null) + { + AddButton(18, bottom - buttons * 22, 0xFA5, 0xFA7, 10, GumpButtonType.Reply, 0); + AddLabel(52, bottom - buttons++ * 22, 2100, "View Speech Log"); + } + + AddLabel(18, 98, 2100, "Page Type:"); + AddLabelCropped(128, 98, 264, 20, 2100, PageQueue.GetPageTypeName(entry.Type)); + + AddLabel(18, 118, 2100, "Message:"); + AddHtml(128, 118, 250, 100, entry.Message, true, true); + + AddPage(2); + + ArrayList preresp = PredefinedResponse.List; + + AddButton(18, 18, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1); + AddButton(410 - 18 - 32, 18, 0xFAB, 0xFAC, 9, GumpButtonType.Reply, 0); + + if (preresp.Count == 0) + { + AddLabel(52, 18, 2100, "There are no predefined responses."); + } + else + { + AddLabel(52, 18, 2100, "Back"); + + for (int i = 0; i < preresp.Count; ++i) + { + AddButton(18, 40 + i * 22, 0xFA5, 0xFA7, 100 + i, GumpButtonType.Reply, 0); + AddLabel(52, 40 + i * 22, 2100, ((PredefinedResponse)preresp[i]).Title); + } + } + } + catch (Exception e) + { + Console.WriteLine(e); + } + } + + public void Resend(NetState state) + { + PageEntryGump g = new PageEntryGump(m_Mobile, m_Entry); + + g.SendTo(state); + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID != 0 && PageQueue.List.IndexOf(m_Entry) < 0) + { + state.Mobile.SendGump(new PageQueueGump()); + state.Mobile.SendMessage("That page has been removed."); + return; + } + + switch (info.ButtonID) + { + case 0: // close + { + if (m_Entry.Handler != state.Mobile) + { + PageQueueGump g = new PageQueueGump(); + + g.SendTo(state); + } + + break; + } + case 1: // go to sender + { + Mobile m = state.Mobile; + + if (m_Entry.Sender.Deleted) + { + m.SendMessage("That character no longer exists."); + } + else if (m_Entry.Sender.Map == null || m_Entry.Sender.Map == Map.Internal) + { + m.SendMessage("That character is not in the world."); + } + else + { + m_Entry.AddResponse(state.Mobile, "[Go Sender]"); + m.MoveToWorld(m_Entry.Sender.Location, m_Entry.Sender.Map); + + m.SendMessage("You have been teleported to that page's sender."); + + Resend(state); + } + + break; + } + case 2: // go to handler + { + Mobile m = state.Mobile; + Mobile h = m_Entry.Handler; + + if (h != null) + { + if (h.Deleted) + { + m.SendMessage("That character no longer exists."); + } + else if (h.Map == null || h.Map == Map.Internal) + { + m.SendMessage("That character is not in the world."); + } + else + { + m_Entry.AddResponse(state.Mobile, "[Go Handler]"); + m.MoveToWorld(h.Location, h.Map); + + m.SendMessage("You have been teleported to that page's handler."); + Resend(state); + } + } + else + { + m.SendMessage("Nobody is handling that page."); + Resend(state); + } + + break; + } + case 3: // go to page location + { + Mobile m = state.Mobile; + + if (m_Entry.PageMap == null || m_Entry.PageMap == Map.Internal) + { + m.SendMessage("That location is not in the world."); + } + else + { + m_Entry.AddResponse(state.Mobile, "[Go PageLoc]"); + m.MoveToWorld(m_Entry.PageLocation, m_Entry.PageMap); + + state.Mobile.SendMessage("You have been teleported to the original page location."); + + Resend(state); + } + + break; + } + case 4: // handle page + { + if (m_Entry.Handler == null) + { + m_Entry.AddResponse(state.Mobile, "[Handling]"); + m_Entry.Handler = state.Mobile; + + state.Mobile.SendMessage("You are now handling the page."); + } + else + { + state.Mobile.SendMessage("Someone is already handling that page."); + } + + Resend(state); + + break; + } + case 5: // delete page + { + if (m_Entry.Handler == null) + { + m_Entry.AddResponse(state.Mobile, "[Deleting]"); + PageQueue.Remove(m_Entry); + + state.Mobile.SendMessage("You delete the page."); + + PageQueueGump g = new PageQueueGump(); + + g.SendTo(state); + } + else + { + state.Mobile.SendMessage("Someone is handling that page, it can not be deleted."); + + Resend(state); + } + + break; + } + case 6: // abandon page + { + if (m_Entry.Handler == state.Mobile) + { + m_Entry.AddResponse(state.Mobile, "[Abandoning]"); + state.Mobile.SendMessage("You abandon the page."); + + m_Entry.Handler = null; + } + else + { + state.Mobile.SendMessage("You are not handling that page."); + } + + Resend(state); + + break; + } + case 7: // page handled + { + if (m_Entry.Handler == state.Mobile) + { + m_Entry.AddResponse(state.Mobile, "[Handled]"); + PageQueue.Remove(m_Entry); + + m_Entry.Handler = null; + + state.Mobile.SendMessage("You mark the page as handled, and remove it from the queue."); + + PageQueueGump g = new PageQueueGump(); + + g.SendTo(state); + } + else + { + state.Mobile.SendMessage("You are not handling that page."); + + Resend(state); + } + + break; + } + case 8: // Send message + { + TextRelay text = info.GetTextEntry(0); + + if (text != null) + { + m_Entry.AddResponse(state.Mobile, "[Response] " + text.Text); + m_Entry.Sender.SendGump(new MessageSentGump(m_Entry.Sender, state.Mobile.Name, text.Text)); + //m_Entry.Sender.SendMessage( 0x482, "{0} tells you:", state.Mobile.Name ); + //m_Entry.Sender.SendMessage( 0x482, text.Text ); + } + + Resend(state); + + break; + } + case 9: // predef overview + { + Resend(state); + state.Mobile.SendGump(new PredefGump(state.Mobile, null)); + + break; + } + case 10: // View Speech Log + { + Resend(state); + + if (m_Entry.SpeechLog != null) + { + Gump gump = new SpeechLogGump(m_Entry.Sender, m_Entry.SpeechLog); + state.Mobile.SendGump(gump); + } + + break; + } + default: + { + int index = info.ButtonID - 100; + ArrayList preresp = PredefinedResponse.List; + + if (index >= 0 && index < preresp.Count) + { + m_Entry.AddResponse(state.Mobile, "[PreDef] " + ((PredefinedResponse)preresp[index]).Title); + m_Entry.Sender.SendGump(new MessageSentGump(m_Entry.Sender, state.Mobile.Name, + ((PredefinedResponse)preresp[index]).Message)); + } + + Resend(state); + + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Help/PageResponseGump.cs b/Scripts/Engines/Help/PageResponseGump.cs index b4bc1142c..c7a272b74 100644 --- a/Scripts/Engines/Help/PageResponseGump.cs +++ b/Scripts/Engines/Help/PageResponseGump.cs @@ -1,38 +1,38 @@ -using System; using Server.Gumps; using Server.Network; namespace Server.Engines.Help { - public class PageResponseGump : Gump - { - private Mobile m_From; - private string m_Name, m_Text; + public class PageResponseGump : Gump + { + private Mobile m_From; + private string m_Name, m_Text; - public PageResponseGump( Mobile from, string name, string text ) : base( 0, 0 ) - { - m_From = from; - m_Name = name; - m_Text = text; + public PageResponseGump(Mobile from, string name, string text) : base(0, 0) + { + m_From = from; + m_Name = name; + m_Text = text; - AddBackground( 50, 25, 540, 430, 2600 ); + AddBackground(50, 25, 540, 430, 2600); - AddPage( 0 ); + AddPage(0); - AddHtmlLocalized( 150, 40, 360, 40, 1062610, false, false ); //
Ultima Online Help Response
+ AddHtmlLocalized(150, 40, 360, 40, 1062610, false, false); //
Ultima Online Help Response
- AddHtml( 80, 90, 480, 290, $"{name} tells {from.Name}: {text}", true, true ); + AddHtml(80, 90, 480, 290, $"{name} tells {from.Name}: {text}", true, true); - AddHtmlLocalized( 80, 390, 480, 40, 1062611, false, false ); // Clicking the OKAY button will remove the reponse you have received. - AddButton( 400, 417, 2074, 2075, 1, GumpButtonType.Reply, 0 ); // OKAY + AddHtmlLocalized(80, 390, 480, 40, 1062611, false, + false); // Clicking the OKAY button will remove the reponse you have received. + AddButton(400, 417, 2074, 2075, 1, GumpButtonType.Reply, 0); // OKAY - AddButton( 475, 417, 2073, 2072, 0, GumpButtonType.Reply, 0 ); // CANCEL - } + AddButton(475, 417, 2073, 2072, 0, GumpButtonType.Reply, 0); // CANCEL + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID != 1 ) - m_From.SendGump( new MessageSentGump( m_From, m_Name, m_Text ) ); - } - } -} + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID != 1) + m_From.SendGump(new MessageSentGump(m_From, m_Name, m_Text)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Help/SpeechLog.cs b/Scripts/Engines/Help/SpeechLog.cs index 51d93de07..9a5c4a8ba 100644 --- a/Scripts/Engines/Help/SpeechLog.cs +++ b/Scripts/Engines/Help/SpeechLog.cs @@ -1,143 +1,145 @@ using System; using System.Collections; +using System.Collections.Generic; +using Server.Commands; +using Server.Gumps; using Server.Mobiles; using Server.Targeting; -using Server.Gumps; -using Server.Commands; -using System.Collections.Generic; namespace Server.Engines.Help { - public class SpeechLog : IEnumerable - { - // Are speech logs enabled? - public static readonly bool Enabled = true; + public class SpeechLog : IEnumerable + { + // Are speech logs enabled? + public static readonly bool Enabled = true; - // How long should we maintain each speech entry? - public static readonly TimeSpan EntryDuration = TimeSpan.FromMinutes( 20.0 ); + // How long should we maintain each speech entry? + public static readonly TimeSpan EntryDuration = TimeSpan.FromMinutes(20.0); - // What is the maximum number of entries a log can contain? (0 -> no limit) - public static readonly int MaxLength = 0; + // What is the maximum number of entries a log can contain? (0 -> no limit) + public static readonly int MaxLength = 0; - public static void Initialize() - { - CommandSystem.Register( "SpeechLog", AccessLevel.Counselor, SpeechLog_OnCommand ); - } + private Queue m_Queue; - [Usage( "SpeechLog" )] - [Description( "Opens the speech log of a given target." )] - private static void SpeechLog_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; + public SpeechLog() + { + m_Queue = new Queue(); + } - from.SendMessage( "Target a player to view his speech log." ); - e.Mobile.Target = new SpeechLogTarget(); - } + public int Count => m_Queue.Count; - private class SpeechLogTarget : Target - { - public SpeechLogTarget() : base( -1, false, TargetFlags.None ) - { - } + #region IEnumerable Members - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !(targeted is PlayerMobile pm) ) - { - from.SendMessage( "Speech logs aren't supported on that target." ); - } - else if ( from != targeted && from.AccessLevel <= pm.AccessLevel && from.AccessLevel != AccessLevel.Owner ) - { - from.SendMessage( "You don't have the required access level to view {0} speech log.", pm.Female ? "her" : "his" ); - } - else if ( pm.SpeechLog == null ) - { - from.SendMessage( "{0} has no speech log.", pm.Female ? "She" : "He" ); - } - else - { - CommandLogging.WriteLine( from, "{0} {1} viewing speech log of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( targeted ) ); + IEnumerator IEnumerable.GetEnumerator() + { + return m_Queue.GetEnumerator(); + } - Gump gump = new SpeechLogGump( pm, pm.SpeechLog ); - from.SendGump( gump ); - } - } - } + #endregion - private Queue m_Queue; + #region IEnumerable Members - public int Count => m_Queue.Count; + IEnumerator IEnumerable.GetEnumerator() + { + return m_Queue.GetEnumerator(); + } - public SpeechLog() - { - m_Queue = new Queue(); - } + #endregion - public void Add( Mobile from, string speech ) - { - Add( new SpeechLogEntry( from, speech ) ); - } + public static void Initialize() + { + CommandSystem.Register("SpeechLog", AccessLevel.Counselor, SpeechLog_OnCommand); + } - public void Add( SpeechLogEntry entry ) - { - if ( MaxLength > 0 && m_Queue.Count >= MaxLength ) - m_Queue.Dequeue(); + [Usage("SpeechLog")] + [Description("Opens the speech log of a given target.")] + private static void SpeechLog_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; - Clean(); + from.SendMessage("Target a player to view his speech log."); + e.Mobile.Target = new SpeechLogTarget(); + } - m_Queue.Enqueue( entry ); - } + public void Add(Mobile from, string speech) + { + Add(new SpeechLogEntry(from, speech)); + } - public void Clean() - { - while ( m_Queue.Count > 0 ) - { - SpeechLogEntry entry = (SpeechLogEntry) m_Queue.Peek(); + public void Add(SpeechLogEntry entry) + { + if (MaxLength > 0 && m_Queue.Count >= MaxLength) + m_Queue.Dequeue(); - if ( DateTime.UtcNow - entry.Created > EntryDuration ) - m_Queue.Dequeue(); - else - break; - } - } + Clean(); - public void CopyTo( SpeechLogEntry[] array, int index ) - { - m_Queue.CopyTo( array, index ); - } + m_Queue.Enqueue(entry); + } - #region IEnumerable Members + public void Clean() + { + while (m_Queue.Count > 0) + { + SpeechLogEntry entry = m_Queue.Peek(); - IEnumerator IEnumerable.GetEnumerator() - { - return m_Queue.GetEnumerator(); - } + if (DateTime.UtcNow - entry.Created > EntryDuration) + m_Queue.Dequeue(); + else + break; + } + } - #endregion + public void CopyTo(SpeechLogEntry[] array, int index) + { + m_Queue.CopyTo(array, index); + } - #region IEnumerable Members + private class SpeechLogTarget : Target + { + public SpeechLogTarget() : base(-1, false, TargetFlags.None) + { + } - IEnumerator IEnumerable.GetEnumerator() - { - return m_Queue.GetEnumerator(); - } + protected override void OnTarget(Mobile from, object targeted) + { + if (!(targeted is PlayerMobile pm)) + { + from.SendMessage("Speech logs aren't supported on that target."); + } + else if (from != targeted && from.AccessLevel <= pm.AccessLevel && from.AccessLevel != AccessLevel.Owner) + { + from.SendMessage("You don't have the required access level to view {0} speech log.", + pm.Female ? "her" : "his"); + } + else if (pm.SpeechLog == null) + { + from.SendMessage("{0} has no speech log.", pm.Female ? "She" : "He"); + } + else + { + CommandLogging.WriteLine(from, "{0} {1} viewing speech log of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(targeted)); - #endregion - } + Gump gump = new SpeechLogGump(pm, pm.SpeechLog); + from.SendGump(gump); + } + } + } + } - public class SpeechLogEntry - { - public Mobile From { get; } + public class SpeechLogEntry + { + public SpeechLogEntry(Mobile from, string speech) + { + From = from; + Speech = speech; + Created = DateTime.UtcNow; + } - public string Speech { get; } + public Mobile From{ get; } - public DateTime Created { get; } + public string Speech{ get; } - public SpeechLogEntry( Mobile from, string speech ) - { - From = from; - Speech = speech; - Created = DateTime.UtcNow; - } - } -} + public DateTime Created{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Help/SpeechLogGump.cs b/Scripts/Engines/Help/SpeechLogGump.cs index 4d7032168..959a9a8c0 100644 --- a/Scripts/Engines/Help/SpeechLogGump.cs +++ b/Scripts/Engines/Help/SpeechLogGump.cs @@ -1,111 +1,114 @@ using System; using System.Collections.Generic; using System.Text; -using Server.Gumps; using Server.Accounting; +using Server.Gumps; using Server.Network; namespace Server.Engines.Help { - public class SpeechLogGump : Gump - { - public static readonly int MaxEntriesPerPage = 30; + public class SpeechLogGump : Gump + { + public static readonly int MaxEntriesPerPage = 30; + private List m_Log; + private int m_Page; - private Mobile m_Player; - private List m_Log; - private int m_Page; + private Mobile m_Player; - public SpeechLogGump( Mobile player, SpeechLog log ) - : this( player, new List( log ) ) - { - } + public SpeechLogGump(Mobile player, SpeechLog log) + : this(player, new List(log)) + { + } - public SpeechLogGump( Mobile player, List log ) : this( player, log, ( log.Count - 1 ) / MaxEntriesPerPage ) - { - } + public SpeechLogGump(Mobile player, List log) : this(player, log, + (log.Count - 1) / MaxEntriesPerPage) + { + } - public SpeechLogGump( Mobile player, List log, int page ) - : base( 500, 30 ) - { - m_Player = player; - m_Log = log; - m_Page = page; + public SpeechLogGump(Mobile player, List log, int page) + : base(500, 30) + { + m_Player = player; + m_Log = log; + m_Page = page; - AddImageTiled( 0, 0, 300, 425, 0xA40 ); - AddAlphaRegion( 1, 1, 298, 423 ); + AddImageTiled(0, 0, 300, 425, 0xA40); + AddAlphaRegion(1, 1, 298, 423); - string playerName = player.Name; - string playerAccount = player.Account is Account ? player.Account.Username : "???"; + string playerName = player.Name; + string playerAccount = player.Account is Account ? player.Account.Username : "???"; - AddHtml( 10, 10, 280, 20, - $"
SPEECH LOG - {playerName} ({Utility.FixHtml(playerAccount)})
", false, false ); + AddHtml(10, 10, 280, 20, + $"
SPEECH LOG - {playerName} ({Utility.FixHtml(playerAccount)})
", + false, false); - int lastPage = ( log.Count - 1 ) / MaxEntriesPerPage; + int lastPage = (log.Count - 1) / MaxEntriesPerPage; - string sLog; + string sLog; - if ( page < 0 || page > lastPage ) - { - sLog = ""; - } - else - { - int max = log.Count - ( lastPage - page ) * MaxEntriesPerPage; - int min = Math.Max( max - MaxEntriesPerPage, 0 ); + if (page < 0 || page > lastPage) + { + sLog = ""; + } + else + { + int max = log.Count - (lastPage - page) * MaxEntriesPerPage; + int min = Math.Max(max - MaxEntriesPerPage, 0); - StringBuilder builder = new StringBuilder(); + StringBuilder builder = new StringBuilder(); - for ( int i = min; i < max; i++ ) - { - SpeechLogEntry entry = log[i]; + for (int i = min; i < max; i++) + { + SpeechLogEntry entry = log[i]; - Mobile m = entry.From; + Mobile m = entry.From; - string name = m.Name; - string account = m.Account is Account ? m.Account.Username : "???"; - string speech = entry.Speech; + string name = m.Name; + string account = m.Account is Account ? m.Account.Username : "???"; + string speech = entry.Speech; - if ( i != min ) - builder.Append( "
" ); + if (i != min) + builder.Append("
"); - builder.AppendFormat( "{0} ({1}): {2}", name, Utility.FixHtml( account ), Utility.FixHtml( speech ) ); - } + builder.AppendFormat("{0} ({1}): {2}", name, Utility.FixHtml(account), + Utility.FixHtml(speech)); + } - sLog = builder.ToString(); - } + sLog = builder.ToString(); + } - AddHtml( 10, 40, 280, 350, sLog, false, true ); + AddHtml(10, 40, 280, 350, sLog, false, true); - if ( page > 0 ) - AddButton( 10, 395, 0xFAE, 0xFB0, 1, GumpButtonType.Reply, 0 ); // Previous page + if (page > 0) + AddButton(10, 395, 0xFAE, 0xFB0, 1, GumpButtonType.Reply, 0); // Previous page - AddLabel( 45, 395, 0x481, $"Current page: {page + 1}/{lastPage + 1}"); + AddLabel(45, 395, 0x481, $"Current page: {page + 1}/{lastPage + 1}"); - if ( page < lastPage ) - AddButton( 261, 395, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0 ); // Next page - } + if (page < lastPage) + AddButton(261, 395, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0); // Next page + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - switch ( info.ButtonID ) - { - case 1: // Previous page - { - if ( m_Page - 1 >= 0 ) - from.SendGump( new SpeechLogGump( m_Player, m_Log, m_Page - 1 ) ); + switch (info.ButtonID) + { + case 1: // Previous page + { + if (m_Page - 1 >= 0) + from.SendGump(new SpeechLogGump(m_Player, m_Log, m_Page - 1)); - break; - } - case 2: // Next page - { - if ( ( m_Page + 1 ) * MaxEntriesPerPage < m_Log.Count ) - from.SendGump( new SpeechLogGump( m_Player, m_Log, m_Page + 1 ) ); + break; + } + case 2: // Next page + { + if ((m_Page + 1) * MaxEntriesPerPage < m_Log.Count) + from.SendGump(new SpeechLogGump(m_Player, m_Log, m_Page + 1)); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Help/StuckMenu.cs b/Scripts/Engines/Help/StuckMenu.cs index 9079e7a35..644ed1cab 100644 --- a/Scripts/Engines/Help/StuckMenu.cs +++ b/Scripts/Engines/Help/StuckMenu.cs @@ -1,287 +1,292 @@ using System; +using Server.Factions; +using Server.Gumps; using Server.Mobiles; using Server.Network; -using Server.Gumps; namespace Server.Menus.Questions { - public class StuckMenuEntry - { - public int Name { get; } + public class StuckMenuEntry + { + public StuckMenuEntry(int name, Point3D[] locations) + { + Name = name; + Locations = locations; + } - public Point3D[] Locations { get; } + public int Name{ get; } - public StuckMenuEntry( int name, Point3D[] locations ) - { - Name = name; - Locations = locations; - } - } + public Point3D[] Locations{ get; } + } - public class StuckMenu : Gump - { - private static StuckMenuEntry[] m_Entries = { - // Britain - new StuckMenuEntry( 1011028, new[] - { - new Point3D( 1522, 1757, 28 ), - new Point3D( 1519, 1619, 10 ), - new Point3D( 1457, 1538, 30 ), - new Point3D( 1607, 1568, 20 ), - new Point3D( 1643, 1680, 18 ) - } ), + public class StuckMenu : Gump + { + private static StuckMenuEntry[] m_Entries = + { + // Britain + new StuckMenuEntry(1011028, new[] + { + new Point3D(1522, 1757, 28), + new Point3D(1519, 1619, 10), + new Point3D(1457, 1538, 30), + new Point3D(1607, 1568, 20), + new Point3D(1643, 1680, 18) + }), - // Trinsic - new StuckMenuEntry( 1011029, new[] - { - new Point3D( 2005, 2754, 30 ), - new Point3D( 1993, 2827, 0 ), - new Point3D( 2044, 2883, 0 ), - new Point3D( 1876, 2859, 20 ), - new Point3D( 1865, 2687, 0 ) - } ), + // Trinsic + new StuckMenuEntry(1011029, new[] + { + new Point3D(2005, 2754, 30), + new Point3D(1993, 2827, 0), + new Point3D(2044, 2883, 0), + new Point3D(1876, 2859, 20), + new Point3D(1865, 2687, 0) + }), - // Vesper - new StuckMenuEntry( 1011030, new[] - { - new Point3D( 2973, 891, 0 ), - new Point3D( 3003, 776, 0 ), - new Point3D( 2910, 727, 0 ), - new Point3D( 2865, 804, 0 ), - new Point3D( 2832, 927, 0 ) - } ), + // Vesper + new StuckMenuEntry(1011030, new[] + { + new Point3D(2973, 891, 0), + new Point3D(3003, 776, 0), + new Point3D(2910, 727, 0), + new Point3D(2865, 804, 0), + new Point3D(2832, 927, 0) + }), - // Minoc - new StuckMenuEntry( 1011031, new[] - { - new Point3D( 2498, 392, 0 ), - new Point3D( 2433, 541, 0 ), - new Point3D( 2445, 501, 15 ), - new Point3D( 2501, 469, 15 ), - new Point3D( 2444, 420, 15 ) - } ), + // Minoc + new StuckMenuEntry(1011031, new[] + { + new Point3D(2498, 392, 0), + new Point3D(2433, 541, 0), + new Point3D(2445, 501, 15), + new Point3D(2501, 469, 15), + new Point3D(2444, 420, 15) + }), - // Yew - new StuckMenuEntry( 1011032, new[] - { - new Point3D( 490, 1166, 0 ), - new Point3D( 652, 1098, 0 ), - new Point3D( 650, 1013, 0 ), - new Point3D( 536, 979, 0 ), - new Point3D( 464, 970, 0 ) - } ), + // Yew + new StuckMenuEntry(1011032, new[] + { + new Point3D(490, 1166, 0), + new Point3D(652, 1098, 0), + new Point3D(650, 1013, 0), + new Point3D(536, 979, 0), + new Point3D(464, 970, 0) + }), - // Cove - new StuckMenuEntry( 1011033, new[] - { - new Point3D( 2230, 1159, 0 ), - new Point3D( 2218, 1203, 0 ), - new Point3D( 2247, 1194, 0 ), - new Point3D( 2236, 1224, 0 ), - new Point3D( 2273, 1231, 0 ) - } ) - }; + // Cove + new StuckMenuEntry(1011033, new[] + { + new Point3D(2230, 1159, 0), + new Point3D(2218, 1203, 0), + new Point3D(2247, 1194, 0), + new Point3D(2236, 1224, 0), + new Point3D(2273, 1231, 0) + }) + }; - private static StuckMenuEntry[] m_T2AEntries = { - // Papua - new StuckMenuEntry( 1011057, new[] - { - new Point3D( 5720, 3109, -1 ), - new Point3D( 5677, 3176, -3 ), - new Point3D( 5678, 3227, 0 ), - new Point3D( 5769, 3206, -2 ), - new Point3D( 5777, 3270, -1 ) - } ), + private static StuckMenuEntry[] m_T2AEntries = + { + // Papua + new StuckMenuEntry(1011057, new[] + { + new Point3D(5720, 3109, -1), + new Point3D(5677, 3176, -3), + new Point3D(5678, 3227, 0), + new Point3D(5769, 3206, -2), + new Point3D(5777, 3270, -1) + }), - // Delucia - new StuckMenuEntry( 1011058, new[] - { - new Point3D( 5216, 4033, 37 ), - new Point3D( 5262, 4049, 37 ), - new Point3D( 5284, 4006, 37 ), - new Point3D( 5189, 3971, 39 ), - new Point3D( 5243, 3960, 37 ) - } ) - }; + // Delucia + new StuckMenuEntry(1011058, new[] + { + new Point3D(5216, 4033, 37), + new Point3D(5262, 4049, 37), + new Point3D(5284, 4006, 37), + new Point3D(5189, 3971, 39), + new Point3D(5243, 3960, 37) + }) + }; - private static bool IsInSecondAgeArea( Mobile m ) - { - if ( m.Map != Map.Trammel && m.Map != Map.Felucca ) - return false; + private bool m_MarkUse; - if ( m.X >= 5120 && m.Y >= 2304 ) - return true; + private Mobile m_Mobile, m_Sender; - if ( m.Region.IsPartOf( "Terathan Keep" ) ) - return true; + private Timer m_Timer; - return false; - } + public StuckMenu(Mobile beholder, Mobile beheld, bool markUse) : base(150, 50) + { + m_Sender = beholder; + m_Mobile = beheld; + m_MarkUse = markUse; - private Mobile m_Mobile, m_Sender; - private bool m_MarkUse; + Closable = false; + Dragable = false; + Disposable = false; - private Timer m_Timer; + AddBackground(0, 0, 270, 320, 2600); - public StuckMenu( Mobile beholder, Mobile beheld, bool markUse ) : base( 150, 50 ) - { - m_Sender = beholder; - m_Mobile = beheld; - m_MarkUse = markUse; + AddHtmlLocalized(50, 20, 250, 35, 1011027, false, false); // Chose a town: - Closable = false; - Dragable = false; - Disposable = false; + StuckMenuEntry[] entries = IsInSecondAgeArea(beheld) ? m_T2AEntries : m_Entries; - AddBackground( 0, 0, 270, 320, 2600 ); + for (int i = 0; i < entries.Length; i++) + { + StuckMenuEntry entry = entries[i]; - AddHtmlLocalized( 50, 20, 250, 35, 1011027, false, false ); // Chose a town: + AddButton(50, 55 + 35 * i, 208, 209, i + 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(75, 55 + 35 * i, 335, 40, entry.Name, false, false); + } - StuckMenuEntry[] entries = IsInSecondAgeArea( beheld ) ? m_T2AEntries : m_Entries; + AddButton(55, 263, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(90, 265, 200, 35, 1011012, false, false); // CANCEL + } - for ( int i = 0; i < entries.Length; i++ ) - { - StuckMenuEntry entry = entries[i]; + private static bool IsInSecondAgeArea(Mobile m) + { + if (m.Map != Map.Trammel && m.Map != Map.Felucca) + return false; - AddButton( 50, 55 + 35 * i, 208, 209, i + 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 75, 55 + 35 * i, 335, 40, entry.Name, false, false ); - } + if (m.X >= 5120 && m.Y >= 2304) + return true; - AddButton( 55, 263, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 90, 265, 200, 35, 1011012, false, false ); // CANCEL - } + if (m.Region.IsPartOf("Terathan Keep")) + return true; - public void BeginClose() - { - StopClose(); + return false; + } - m_Timer = new CloseTimer( m_Mobile ); - m_Timer.Start(); + public void BeginClose() + { + StopClose(); - m_Mobile.Frozen = true; - } + m_Timer = new CloseTimer(m_Mobile); + m_Timer.Start(); - public void StopClose() - { - m_Timer?.Stop(); + m_Mobile.Frozen = true; + } - m_Mobile.Frozen = false; - } + public void StopClose() + { + m_Timer?.Stop(); - public override void OnResponse( NetState state, RelayInfo info ) - { - StopClose(); + m_Mobile.Frozen = false; + } - if ( Factions.Sigil.ExistsOn( m_Mobile ) ) - { - m_Mobile.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( info.ButtonID == 0 ) - { - if ( m_Mobile == m_Sender ) - m_Mobile.SendLocalizedMessage( 1010588 ); // You choose not to go to any city. - } - else - { - int index = info.ButtonID - 1; - StuckMenuEntry[] entries = IsInSecondAgeArea( m_Mobile ) ? m_T2AEntries : m_Entries; + public override void OnResponse(NetState state, RelayInfo info) + { + StopClose(); - if ( index >= 0 && index < entries.Length ) - Teleport( entries[index] ); - } - } + if (Sigil.ExistsOn(m_Mobile)) + { + m_Mobile.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (info.ButtonID == 0) + { + if (m_Mobile == m_Sender) + m_Mobile.SendLocalizedMessage(1010588); // You choose not to go to any city. + } + else + { + int index = info.ButtonID - 1; + StuckMenuEntry[] entries = IsInSecondAgeArea(m_Mobile) ? m_T2AEntries : m_Entries; - private void Teleport( StuckMenuEntry entry ) - { - if ( m_MarkUse ) - { - m_Mobile.SendLocalizedMessage( 1010589 ); // You will be teleported within the next two minutes. + if (index >= 0 && index < entries.Length) + Teleport(entries[index]); + } + } - new TeleportTimer( m_Mobile, entry, TimeSpan.FromSeconds( 10.0 + (Utility.RandomDouble() * 110.0) ) ).Start(); + private void Teleport(StuckMenuEntry entry) + { + if (m_MarkUse) + { + m_Mobile.SendLocalizedMessage(1010589); // You will be teleported within the next two minutes. - if (m_Mobile is PlayerMobile mobile) - mobile.UsedStuckMenu(); - } - else - { - new TeleportTimer( m_Mobile, entry, TimeSpan.Zero ).Start(); - } - } + new TeleportTimer(m_Mobile, entry, TimeSpan.FromSeconds(10.0 + Utility.RandomDouble() * 110.0)).Start(); - private class CloseTimer : Timer - { - private Mobile m_Mobile; - private DateTime m_End; + if (m_Mobile is PlayerMobile mobile) + mobile.UsedStuckMenu(); + } + else + { + new TeleportTimer(m_Mobile, entry, TimeSpan.Zero).Start(); + } + } - public CloseTimer( Mobile m ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_End = DateTime.UtcNow + TimeSpan.FromMinutes( 3.0 ); - } + private class CloseTimer : Timer + { + private DateTime m_End; + private Mobile m_Mobile; - protected override void OnTick() - { - if ( m_Mobile.NetState == null || DateTime.UtcNow > m_End ) - { - m_Mobile.Frozen = false; - m_Mobile.CloseGump( typeof( StuckMenu ) ); + public CloseTimer(Mobile m) : base(TimeSpan.Zero, TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_End = DateTime.UtcNow + TimeSpan.FromMinutes(3.0); + } - Stop(); - } - else - { - m_Mobile.Frozen = true; - } - } - } + protected override void OnTick() + { + if (m_Mobile.NetState == null || DateTime.UtcNow > m_End) + { + m_Mobile.Frozen = false; + m_Mobile.CloseGump(typeof(StuckMenu)); - private class TeleportTimer : Timer - { - private Mobile m_Mobile; - private StuckMenuEntry m_Destination; - private DateTime m_End; + Stop(); + } + else + { + m_Mobile.Frozen = true; + } + } + } - public TeleportTimer( Mobile mobile, StuckMenuEntry destination, TimeSpan delay ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ) ) - { - Priority = TimerPriority.TwoFiftyMS; + private class TeleportTimer : Timer + { + private StuckMenuEntry m_Destination; + private DateTime m_End; + private Mobile m_Mobile; - m_Mobile = mobile; - m_Destination = destination; - m_End = DateTime.UtcNow + delay; - } + public TeleportTimer(Mobile mobile, StuckMenuEntry destination, TimeSpan delay) : base(TimeSpan.Zero, + TimeSpan.FromSeconds(1.0)) + { + Priority = TimerPriority.TwoFiftyMS; - protected override void OnTick() - { - if ( DateTime.UtcNow < m_End ) - { - m_Mobile.Frozen = true; - } - else - { - m_Mobile.Frozen = false; - Stop(); + m_Mobile = mobile; + m_Destination = destination; + m_End = DateTime.UtcNow + delay; + } - if ( Factions.Sigil.ExistsOn( m_Mobile ) ) - { - m_Mobile.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return; - } + protected override void OnTick() + { + if (DateTime.UtcNow < m_End) + { + m_Mobile.Frozen = true; + } + else + { + m_Mobile.Frozen = false; + Stop(); - int idx = Utility.Random( m_Destination.Locations.Length ); - Point3D dest = m_Destination.Locations[idx]; + if (Sigil.ExistsOn(m_Mobile)) + { + m_Mobile.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return; + } - Map destMap; - if ( m_Mobile.Map == Map.Trammel ) - destMap = Map.Trammel; - else if ( m_Mobile.Map == Map.Felucca ) - destMap = Map.Felucca; - else - destMap = m_Mobile.Kills >= 5 ? Map.Felucca : Map.Trammel; + int idx = Utility.Random(m_Destination.Locations.Length); + Point3D dest = m_Destination.Locations[idx]; - BaseCreature.TeleportPets( m_Mobile, dest, destMap ); - m_Mobile.MoveToWorld( dest, destMap ); - } - } - } - } -} + Map destMap; + if (m_Mobile.Map == Map.Trammel) + destMap = Map.Trammel; + else if (m_Mobile.Map == Map.Felucca) + destMap = Map.Felucca; + else + destMap = m_Mobile.Kills >= 5 ? Map.Felucca : Map.Trammel; + + BaseCreature.TeleportPets(m_Mobile, dest, destMap); + m_Mobile.MoveToWorld(dest, destMap); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Books/GrimmochJournal.cs b/Scripts/Engines/Khaldun/Books/GrimmochJournal.cs index 741ecc877..01bcc8d2e 100644 --- a/Scripts/Engines/Khaldun/Books/GrimmochJournal.cs +++ b/Scripts/Engines/Khaldun/Books/GrimmochJournal.cs @@ -1,776 +1,776 @@ namespace Server.Items { - public class GrimmochJournal1 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day One :", - "", - "'Tis a grand sight, this", - "primeval tomb, I agree", - "with Tavara on that.", - "And we've a good crew", - "here, they've strong", - "backs and a good" - ), - new BookPageInfo - ( - "attitude. I'm a bit", - "concerned by those", - "that worked as guides", - "for us, however. All", - "seemed well enough", - "until we revealed the", - "immense stone doors", - "of the tomb structure" - ), - new BookPageInfo - ( - "itself. Seemed to send", - "a shiver up their", - "spines and get them all", - "stirred up with", - "whispering. I'll", - "watch the lot of them", - "with a close eye, but", - "I'm confident we won't" - ), - new BookPageInfo - ( - "have any real", - "problems on the dig.", - "I'm especially proud to", - "see Thomas standing", - "out - he was a good", - "hire, despite the", - "warnings from his", - "previous employers." - ), - new BookPageInfo - ( - "He's drummed up the", - "workers into a", - "furious pace - we've", - "nearly halved the", - "estimate on the", - "timeline for", - "excavating the Tomb's", - "entrance." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal1() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal1( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal2 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Two :", - "", - "We managed to dig out", - "the last of the", - "remaining rubble", - "today, revealing the", - "entirety of the giant", - "stone doors that sealed" - ), - new BookPageInfo - ( - "ol' Khal Ankur and", - "his folk up ages ago.", - "Actually getting them", - "open was another", - "matter altogether,", - "however. As the", - "workers set to the", - "task with picks and" - ), - new BookPageInfo - ( - "crowbars, I could have", - "sworn I saw Lysander", - "Gathenwale fiddling", - "with something in that", - "musty old tome of his.", - " I've no great", - "knowledge of things", - "magical, but the way" - ), - new BookPageInfo - ( - "his hand moved over", - "that book, and the look", - "of concentration on his", - "face as he whispered", - "something to himself", - "looked like every", - "description of an", - "incantation I've ever" - ), - new BookPageInfo - ( - "heard. The strange", - "thing is, this set of", - "doors that an entire", - "crew of excavators", - "was laboring over for", - "hours, right when", - "Gathenwale finishes", - "with his mumbling..." - ), - new BookPageInfo - ( - "well, I swore the doors", - "just gave open at the", - "exact moment he", - "spoke his last bit of", - "whisper and shut the", - "tome tight in his", - "hands. When he", - "looked up, it was" - ), - new BookPageInfo - ( - "almost as if he was", - "expecting the doors to", - "be open, rather than", - "shocked that they'd", - "finally given way." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal2() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal3 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Three - Day Five:", - "", - "I might have", - "written too hastily in", - "my first entry - this", - "place doesn't seem too", - "bent on giving up any", - "secrets. Though the" - ), - new BookPageInfo - ( - "main antechamber is", - "open to us, the main", - "exit hall is blocked by", - "yet another pile of", - "rubble. Doesn't look a", - "bit like anything", - "caused by a quake or", - "instability in the" - ), - new BookPageInfo - ( - "stonework... I swear it", - "looks as if someone", - "actually piled the", - "stones up themselves,", - "some time after the", - "tomb was built. The", - "stones aren't of the", - "same set nor quality" - ), - new BookPageInfo - ( - "of the carved work", - "that surrounds them", - "- if anything, they", - "resemble the grade of", - "common rock we saw", - "in great quantities on", - "the trip here. Which", - "makes it feel all the" - ), - new BookPageInfo - ( - "more like someone", - "hauled them in and", - "deliberately covered", - "this passage. But then", - "why not decorate them", - "in the same ornate", - "manner as the rest of", - "the stone in this" - ), - new BookPageInfo - ( - "place? Lysander", - "wouldn't hear a word", - "of what I had to say -", - "to him, it was a quake", - "some time in the", - "history of the tomb,", - "and that was it, shut", - "up and move on. So I" - ), - new BookPageInfo - ( - "shut up, and got back", - "to work." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal3() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal3( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal6 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Six :", - "", - "The camp was", - "attacked last night by", - "a pack of, well, I don't", - "have a clue. I've never", - "seen the like of these", - "beasts anywhere." - ), - new BookPageInfo - ( - "Huge things, with", - "fangs the size of your", - "forefinger, covered in", - "hair and with the", - "strangest arched back", - "I've ever seen. And so", - "many of them. We", - "were forced back into" - ), - new BookPageInfo - ( - "the Tomb for the", - "night, just to keep our", - "hides on us. And", - "today Gathenwale", - "practically orders us", - "all to move the entire", - "exterior camp into the", - "Tomb. Now, I don't" - ), - new BookPageInfo - ( - "disagree that we'd be", - "well off to use the", - "place as a point of", - "fortification... but I", - "don't like it one bit, in", - "any case. I don't like", - "the look of this place,", - "nor the sound of it." - ), - new BookPageInfo - ( - "The way the wind", - "gets into the", - "passageways,", - "whistling up the", - "strangest noises.", - "Deep, sustained echoes", - "of the wind, not so", - "much flute-like as..." - ), - new BookPageInfo - ( - "well, it sounds", - "ridiculous. In any", - "case, we've set to work", - "moving the bulk of the", - "exterior camp into the", - "main antechamber, so", - "there's no use moaning", - "about it now." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal6() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal6( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal7 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Seven - Day Ten:", - "", - "I cannot stand this", - "place, I cannot bear it.", - "I've got to get out.", - "Something evil lurks", - "in this ancient place,", - "something best left" - ), - new BookPageInfo - ( - "alone. I hear them,", - "yet none of the others", - "do. And yet they", - "must. Hands, claws,", - "scratching at stone,", - "the awful scratching", - "and the piteous cries", - "that sound almost like" - ), - new BookPageInfo - ( - "laughter. I can hear", - "them above even the", - "cracks of the", - "workmen's picks, and", - "at night they are all I", - "can hear. And yet the", - "others hear nothing.", - "We must leave this" - ), - new BookPageInfo - ( - "place, we must.", - "Three workers have", - "gone missing - Tavara", - "expects they've", - "abandoned us - and I", - "count them lucky if", - "they have. I don't care", - "what the others say," - ), - new BookPageInfo - ( - "we must leave this", - "place. We must do as", - "those before and pile", - "up the stones, block all", - "access to this primeval", - "crypt, seal it up again", - "for all eternity." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal7() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal7( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal11 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Eleven - Day", - "Thirteen :", - "", - "Lysander is gone, and", - "two more workers", - "with him. Good", - "riddance to the first.", - "He knows something." - ), - new BookPageInfo - ( - "He heard them too, I", - "know he did - and yet", - "he scowled at me", - "when I mentioned", - "them. I cannot stop", - "the noise in my head,", - "the scratching, the", - "clawing tears at my" - ), - new BookPageInfo - ( - "senses. What is it?", - "What does Lysander", - "seek that I can only", - "turn from? Where", - "has he gone? The", - "only answer to my", - "questions comes as", - "laughter from behind" - ), - new BookPageInfo - ( - "the stones." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal11() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal11( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal14 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Fourteen - Day", - "Sixteen :", - "", - "We are lost... we are", - "lost... all is lost. The", - "dead are piled up at", - "my feet. Bergen and I", - "somehow managed in" - ), - new BookPageInfo - ( - "the madness to piece", - "together a barricade,", - "barring access to the", - "camp antechamber.", - "He knows as well as I", - "that we cannot hold it", - "forever. The dead", - "come. They took" - ), - new BookPageInfo - ( - "Lysander before our", - "eyes. I pity the soul", - "of even such a", - "madman - no one", - "should die in such a", - "manner. And yet so", - "many have. We're", - "trapped here in this" - ), - new BookPageInfo - ( - "horror. So many have", - "died, and for what?", - "What curse have we", - "stumbled upon? I", - "cannot bear it, the", - "moaning, wailing cries", - "of the dead. Poor", - "Thomas, cut to pieces" - ), - new BookPageInfo - ( - "by their blades. We", - "had only an hour to", - "properly bury those", - "we could, before the", - "undead legions struck", - "again. I cannot go on...", - "I cannot go on." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal14() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal14( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal17 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Seventeen - Day", - "Twenty-Two :", - "", - "The fighting never", - "ceases... the blood", - "never stops flowing,", - "like a river through", - "the bloated corpses of" - ), - new BookPageInfo - ( - "the dead. And yet", - "there are still more.", - "Always more, with", - "the red fire gleaming", - "in their eyes. My", - "arm aches, I've taken", - "to the sword as my", - "bow seems to do little" - ), - new BookPageInfo - ( - "good... the dull ache in", - "my arm... so many", - "swings, cleaving a", - "mountain of decaying", - "flesh. And Thomas...", - "he was there, in the", - "thick of it... Thomas", - "was beside me..." - ), - new BookPageInfo - ( - "his face cleaved in", - "twain - and yet beside", - "me, fighting with us", - "against the horde until", - "he was cut down once", - "again. And I swear I", - "see him even now,", - "there in the dark" - ), - new BookPageInfo - ( - "corner of the", - "antechamber, his eyes", - "flickering in the last", - "dying embers of the", - "fire... and he stares at", - "me, and a scream fills", - "the vault - whether", - "his or mine, I can no" - ), - new BookPageInfo - ( - "longer tell." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal17() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal17( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class GrimmochJournal23 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The daily journal of Grimmoch Drummel", "Grimmoch", - new BookPageInfo - ( - "Day Twenty-Three :", - "", - "We no longer bury the", - "dead." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrimmochJournal23() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public GrimmochJournal23( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + public class GrimmochJournal1 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day One :", + "", + "'Tis a grand sight, this", + "primeval tomb, I agree", + "with Tavara on that.", + "And we've a good crew", + "here, they've strong", + "backs and a good" + ), + new BookPageInfo + ( + "attitude. I'm a bit", + "concerned by those", + "that worked as guides", + "for us, however. All", + "seemed well enough", + "until we revealed the", + "immense stone doors", + "of the tomb structure" + ), + new BookPageInfo + ( + "itself. Seemed to send", + "a shiver up their", + "spines and get them all", + "stirred up with", + "whispering. I'll", + "watch the lot of them", + "with a close eye, but", + "I'm confident we won't" + ), + new BookPageInfo + ( + "have any real", + "problems on the dig.", + "I'm especially proud to", + "see Thomas standing", + "out - he was a good", + "hire, despite the", + "warnings from his", + "previous employers." + ), + new BookPageInfo + ( + "He's drummed up the", + "workers into a", + "furious pace - we've", + "nearly halved the", + "estimate on the", + "timeline for", + "excavating the Tomb's", + "entrance." + ) + ); + + [Constructible] + public GrimmochJournal1() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal1(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal2 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Two :", + "", + "We managed to dig out", + "the last of the", + "remaining rubble", + "today, revealing the", + "entirety of the giant", + "stone doors that sealed" + ), + new BookPageInfo + ( + "ol' Khal Ankur and", + "his folk up ages ago.", + "Actually getting them", + "open was another", + "matter altogether,", + "however. As the", + "workers set to the", + "task with picks and" + ), + new BookPageInfo + ( + "crowbars, I could have", + "sworn I saw Lysander", + "Gathenwale fiddling", + "with something in that", + "musty old tome of his.", + " I've no great", + "knowledge of things", + "magical, but the way" + ), + new BookPageInfo + ( + "his hand moved over", + "that book, and the look", + "of concentration on his", + "face as he whispered", + "something to himself", + "looked like every", + "description of an", + "incantation I've ever" + ), + new BookPageInfo + ( + "heard. The strange", + "thing is, this set of", + "doors that an entire", + "crew of excavators", + "was laboring over for", + "hours, right when", + "Gathenwale finishes", + "with his mumbling..." + ), + new BookPageInfo + ( + "well, I swore the doors", + "just gave open at the", + "exact moment he", + "spoke his last bit of", + "whisper and shut the", + "tome tight in his", + "hands. When he", + "looked up, it was" + ), + new BookPageInfo + ( + "almost as if he was", + "expecting the doors to", + "be open, rather than", + "shocked that they'd", + "finally given way." + ) + ); + + [Constructible] + public GrimmochJournal2() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal2(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal3 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Three - Day Five:", + "", + "I might have", + "written too hastily in", + "my first entry - this", + "place doesn't seem too", + "bent on giving up any", + "secrets. Though the" + ), + new BookPageInfo + ( + "main antechamber is", + "open to us, the main", + "exit hall is blocked by", + "yet another pile of", + "rubble. Doesn't look a", + "bit like anything", + "caused by a quake or", + "instability in the" + ), + new BookPageInfo + ( + "stonework... I swear it", + "looks as if someone", + "actually piled the", + "stones up themselves,", + "some time after the", + "tomb was built. The", + "stones aren't of the", + "same set nor quality" + ), + new BookPageInfo + ( + "of the carved work", + "that surrounds them", + "- if anything, they", + "resemble the grade of", + "common rock we saw", + "in great quantities on", + "the trip here. Which", + "makes it feel all the" + ), + new BookPageInfo + ( + "more like someone", + "hauled them in and", + "deliberately covered", + "this passage. But then", + "why not decorate them", + "in the same ornate", + "manner as the rest of", + "the stone in this" + ), + new BookPageInfo + ( + "place? Lysander", + "wouldn't hear a word", + "of what I had to say -", + "to him, it was a quake", + "some time in the", + "history of the tomb,", + "and that was it, shut", + "up and move on. So I" + ), + new BookPageInfo + ( + "shut up, and got back", + "to work." + ) + ); + + [Constructible] + public GrimmochJournal3() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal3(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal6 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Six :", + "", + "The camp was", + "attacked last night by", + "a pack of, well, I don't", + "have a clue. I've never", + "seen the like of these", + "beasts anywhere." + ), + new BookPageInfo + ( + "Huge things, with", + "fangs the size of your", + "forefinger, covered in", + "hair and with the", + "strangest arched back", + "I've ever seen. And so", + "many of them. We", + "were forced back into" + ), + new BookPageInfo + ( + "the Tomb for the", + "night, just to keep our", + "hides on us. And", + "today Gathenwale", + "practically orders us", + "all to move the entire", + "exterior camp into the", + "Tomb. Now, I don't" + ), + new BookPageInfo + ( + "disagree that we'd be", + "well off to use the", + "place as a point of", + "fortification... but I", + "don't like it one bit, in", + "any case. I don't like", + "the look of this place,", + "nor the sound of it." + ), + new BookPageInfo + ( + "The way the wind", + "gets into the", + "passageways,", + "whistling up the", + "strangest noises.", + "Deep, sustained echoes", + "of the wind, not so", + "much flute-like as..." + ), + new BookPageInfo + ( + "well, it sounds", + "ridiculous. In any", + "case, we've set to work", + "moving the bulk of the", + "exterior camp into the", + "main antechamber, so", + "there's no use moaning", + "about it now." + ) + ); + + [Constructible] + public GrimmochJournal6() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal6(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal7 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Seven - Day Ten:", + "", + "I cannot stand this", + "place, I cannot bear it.", + "I've got to get out.", + "Something evil lurks", + "in this ancient place,", + "something best left" + ), + new BookPageInfo + ( + "alone. I hear them,", + "yet none of the others", + "do. And yet they", + "must. Hands, claws,", + "scratching at stone,", + "the awful scratching", + "and the piteous cries", + "that sound almost like" + ), + new BookPageInfo + ( + "laughter. I can hear", + "them above even the", + "cracks of the", + "workmen's picks, and", + "at night they are all I", + "can hear. And yet the", + "others hear nothing.", + "We must leave this" + ), + new BookPageInfo + ( + "place, we must.", + "Three workers have", + "gone missing - Tavara", + "expects they've", + "abandoned us - and I", + "count them lucky if", + "they have. I don't care", + "what the others say," + ), + new BookPageInfo + ( + "we must leave this", + "place. We must do as", + "those before and pile", + "up the stones, block all", + "access to this primeval", + "crypt, seal it up again", + "for all eternity." + ) + ); + + [Constructible] + public GrimmochJournal7() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal7(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal11 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Eleven - Day", + "Thirteen :", + "", + "Lysander is gone, and", + "two more workers", + "with him. Good", + "riddance to the first.", + "He knows something." + ), + new BookPageInfo + ( + "He heard them too, I", + "know he did - and yet", + "he scowled at me", + "when I mentioned", + "them. I cannot stop", + "the noise in my head,", + "the scratching, the", + "clawing tears at my" + ), + new BookPageInfo + ( + "senses. What is it?", + "What does Lysander", + "seek that I can only", + "turn from? Where", + "has he gone? The", + "only answer to my", + "questions comes as", + "laughter from behind" + ), + new BookPageInfo + ( + "the stones." + ) + ); + + [Constructible] + public GrimmochJournal11() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal11(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal14 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Fourteen - Day", + "Sixteen :", + "", + "We are lost... we are", + "lost... all is lost. The", + "dead are piled up at", + "my feet. Bergen and I", + "somehow managed in" + ), + new BookPageInfo + ( + "the madness to piece", + "together a barricade,", + "barring access to the", + "camp antechamber.", + "He knows as well as I", + "that we cannot hold it", + "forever. The dead", + "come. They took" + ), + new BookPageInfo + ( + "Lysander before our", + "eyes. I pity the soul", + "of even such a", + "madman - no one", + "should die in such a", + "manner. And yet so", + "many have. We're", + "trapped here in this" + ), + new BookPageInfo + ( + "horror. So many have", + "died, and for what?", + "What curse have we", + "stumbled upon? I", + "cannot bear it, the", + "moaning, wailing cries", + "of the dead. Poor", + "Thomas, cut to pieces" + ), + new BookPageInfo + ( + "by their blades. We", + "had only an hour to", + "properly bury those", + "we could, before the", + "undead legions struck", + "again. I cannot go on...", + "I cannot go on." + ) + ); + + [Constructible] + public GrimmochJournal14() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal14(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal17 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Seventeen - Day", + "Twenty-Two :", + "", + "The fighting never", + "ceases... the blood", + "never stops flowing,", + "like a river through", + "the bloated corpses of" + ), + new BookPageInfo + ( + "the dead. And yet", + "there are still more.", + "Always more, with", + "the red fire gleaming", + "in their eyes. My", + "arm aches, I've taken", + "to the sword as my", + "bow seems to do little" + ), + new BookPageInfo + ( + "good... the dull ache in", + "my arm... so many", + "swings, cleaving a", + "mountain of decaying", + "flesh. And Thomas...", + "he was there, in the", + "thick of it... Thomas", + "was beside me..." + ), + new BookPageInfo + ( + "his face cleaved in", + "twain - and yet beside", + "me, fighting with us", + "against the horde until", + "he was cut down once", + "again. And I swear I", + "see him even now,", + "there in the dark" + ), + new BookPageInfo + ( + "corner of the", + "antechamber, his eyes", + "flickering in the last", + "dying embers of the", + "fire... and he stares at", + "me, and a scream fills", + "the vault - whether", + "his or mine, I can no" + ), + new BookPageInfo + ( + "longer tell." + ) + ); + + [Constructible] + public GrimmochJournal17() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal17(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class GrimmochJournal23 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The daily journal of Grimmoch Drummel", "Grimmoch", + new BookPageInfo + ( + "Day Twenty-Three :", + "", + "We no longer bury the", + "dead." + ) + ); + + [Constructible] + public GrimmochJournal23() : base(Utility.Random(0xFF1, 2), false) + { + } + + public GrimmochJournal23(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Books/LysanderNotebook.cs b/Scripts/Engines/Khaldun/Books/LysanderNotebook.cs index 5202dc5ae..219ccffb4 100644 --- a/Scripts/Engines/Khaldun/Books/LysanderNotebook.cs +++ b/Scripts/Engines/Khaldun/Books/LysanderNotebook.cs @@ -1,536 +1,536 @@ namespace Server.Items { - public class LysanderNotebook1 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Lysander's Notebook", "L. Gathenwale", - new BookPageInfo - ( - "Day One :", - "", - "At last, it stands", - "before me. The doors", - "of Thy Sanctum will", - "open to me now, after", - "all these years of", - "searching. I give" - ), - new BookPageInfo - ( - "myself unto Thee,", - "Khal Ankur, I have", - "come for Thy secrets", - "and I will kneel", - "prostrate before Thee.", - " Blessed are the", - "Keepers, praise unto", - "Thee, a thousand" - ), - new BookPageInfo - ( - "fortunes in the night." - ) - ); + public class LysanderNotebook1 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Lysander's Notebook", "L. Gathenwale", + new BookPageInfo + ( + "Day One :", + "", + "At last, it stands", + "before me. The doors", + "of Thy Sanctum will", + "open to me now, after", + "all these years of", + "searching. I give" + ), + new BookPageInfo + ( + "myself unto Thee,", + "Khal Ankur, I have", + "come for Thy secrets", + "and I will kneel", + "prostrate before Thee.", + " Blessed are the", + "Keepers, praise unto", + "Thee, a thousand" + ), + new BookPageInfo + ( + "fortunes in the night." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public LysanderNotebook1() : base(Utility.Random(0xFF1, 2), false) + { + } - [Constructible] - public LysanderNotebook1() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } + public LysanderNotebook1(Serial serial) : base(serial) + { + } - public LysanderNotebook1( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LysanderNotebook2 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Lysander's Notebook", "L. Gathenwale", - new BookPageInfo - ( - "Day Two:", - "", - "The woman, Tavara", - "Sewel, is unbearable.", - "Her entire demeanor", - "sickens me. I would", - "take her life for Thee", - "now, my Lord. But I" - ), - new BookPageInfo - ( - "cannot alert the", - "others. Progress is", - "made too slowly, I", - "cannot stand this", - "perpetual waiting.", - "Today I knelt down", - "with the workers,", - "tossing stones and dirt" - ), - new BookPageInfo - ( - "aside with my very", - "hands as they dug at", - "the last of the rubble", - "covering the entrance", - "to Thy Sanctum. The", - "Sewel woman was", - "shocked at my", - "demeanor, dirtying" - ), - new BookPageInfo - ( - "my robes, on my", - "knees in the muck as I", - "clawed at the rocks.", - "She thought I did this", - "for those sickly", - "scholars, or for her,", - "or for what she", - "laughably calls 'The" - ), - new BookPageInfo - ( - "Gift of Discovery', of", - "learning. As if I did", - "not know what I went", - "to find! I come for", - "Thee, Master. Soon", - "shall I receive Thy", - "gifts, Thy blessings.", - "Patience, eternal" - ), - new BookPageInfo - ( - "patience. I must take", - "my lessons well. I", - "have learned from", - "Thee, Master, I have." - ) - ); + public class LysanderNotebook2 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Lysander's Notebook", "L. Gathenwale", + new BookPageInfo + ( + "Day Two:", + "", + "The woman, Tavara", + "Sewel, is unbearable.", + "Her entire demeanor", + "sickens me. I would", + "take her life for Thee", + "now, my Lord. But I" + ), + new BookPageInfo + ( + "cannot alert the", + "others. Progress is", + "made too slowly, I", + "cannot stand this", + "perpetual waiting.", + "Today I knelt down", + "with the workers,", + "tossing stones and dirt" + ), + new BookPageInfo + ( + "aside with my very", + "hands as they dug at", + "the last of the rubble", + "covering the entrance", + "to Thy Sanctum. The", + "Sewel woman was", + "shocked at my", + "demeanor, dirtying" + ), + new BookPageInfo + ( + "my robes, on my", + "knees in the muck as I", + "clawed at the rocks.", + "She thought I did this", + "for those sickly", + "scholars, or for her,", + "or for what she", + "laughably calls 'The" + ), + new BookPageInfo + ( + "Gift of Discovery', of", + "learning. As if I did", + "not know what I went", + "to find! I come for", + "Thee, Master. Soon", + "shall I receive Thy", + "gifts, Thy blessings.", + "Patience, eternal" + ), + new BookPageInfo + ( + "patience. I must take", + "my lessons well. I", + "have learned from", + "Thee, Master, I have." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public LysanderNotebook2() : base(Utility.Random(0xFF1, 2), false) + { + } - [Constructible] - public LysanderNotebook2() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } + public LysanderNotebook2(Serial serial) : base(serial) + { + } - public LysanderNotebook2( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LysanderNotebook3 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Lysander's Notebook", "L. Gathenwale", - new BookPageInfo - ( - "Day Three - Day Six:", - "", - "What are these Beasts", - "that dare to defy our", - "presence here? Hast", - "Thou sent them,", - "Master? To tear", - "apart these foolish" - ), - new BookPageInfo - ( - "ones that accompany", - "me? That repugnant", - "pustule, Drummel, put", - "forth his absurd little", - "theories as to the", - "nature of the Beasts", - "that attacked our", - "camp, but I'll have" - ), - new BookPageInfo - ( - "none of his words. He", - "asks too many", - "questions. He is a", - "taint upon the grounds", - "of Thy Sanctum,", - "Master - I will deal", - "with him after the", - "Sewel woman." - ), - new BookPageInfo - ( - "Speaking of Sewel, I", - "have convinced that", - "empty-headed harlot", - "that we should move", - "our encampment", - "within the", - "antechamber. She", - "thinks I worry for" - ), - new BookPageInfo - ( - "her safety. I come", - "for thee, Master. I", - "make my camp in Thy", - "chambers. I sleep", - "under Thy roof. I can", - "feel Thine presence", - "even now. Soon,", - "Master. Soon." - ) - ); + public class LysanderNotebook3 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Lysander's Notebook", "L. Gathenwale", + new BookPageInfo + ( + "Day Three - Day Six:", + "", + "What are these Beasts", + "that dare to defy our", + "presence here? Hast", + "Thou sent them,", + "Master? To tear", + "apart these foolish" + ), + new BookPageInfo + ( + "ones that accompany", + "me? That repugnant", + "pustule, Drummel, put", + "forth his absurd little", + "theories as to the", + "nature of the Beasts", + "that attacked our", + "camp, but I'll have" + ), + new BookPageInfo + ( + "none of his words. He", + "asks too many", + "questions. He is a", + "taint upon the grounds", + "of Thy Sanctum,", + "Master - I will deal", + "with him after the", + "Sewel woman." + ), + new BookPageInfo + ( + "Speaking of Sewel, I", + "have convinced that", + "empty-headed harlot", + "that we should move", + "our encampment", + "within the", + "antechamber. She", + "thinks I worry for" + ), + new BookPageInfo + ( + "her safety. I come", + "for thee, Master. I", + "make my camp in Thy", + "chambers. I sleep", + "under Thy roof. I can", + "feel Thine presence", + "even now. Soon,", + "Master. Soon." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public LysanderNotebook3() : base(Utility.Random(0xFF1, 2), false) + { + } - [Constructible] - public LysanderNotebook3() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } + public LysanderNotebook3(Serial serial) : base(serial) + { + } - public LysanderNotebook3( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LysanderNotebook7 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Lysander's Notebook", "L. Gathenwale", - new BookPageInfo - ( - "Day Seven :", - "", - "The Sewel woman", - "pratters on endlessly.", - "And she dares to", - "speak Thy Name,", - "Master! I wish so", - "vehemently to take a" - ), - new BookPageInfo - ( - "knife to that little", - "neck of hers. She", - "struts around the", - "chambers of Thy", - "Sanctum with her", - "repugnant airs, her", - "scholarly conjecture", - "on this or that. That I" - ), - new BookPageInfo - ( - "could peel the skin", - "from her face and", - "show her how vile and", - "ugly she truly is, how", - "unworthy of entrance", - "to Thy Sanctum. I", - "must take her,", - "Master. I must rend" - ), - new BookPageInfo - ( - "that little wench to", - "pieces. I ask this gift", - "of Thee, that I might", - "cleanse Thy Sanctum", - "of her presence. Give", - "me the Sewel woman", - "and I shall show you", - "my mastery of Death," - ), - new BookPageInfo - ( - "Master. I shall cut", - "her to bits and scatter", - "them before the", - "others as a warning.", - "I cannot stand her", - "presence, I cannot", - "abide it. And", - "Drummel! He is a" - ), - new BookPageInfo - ( - "pustule that must be", - "lanced, a sickness that", - "I must cure by blade", - "and fire. Not a trace", - "of him will be left", - "when I'm done with", - "him. Praises to Thee,", - "Master. I shall honor" - ), - new BookPageInfo - ( - "Thee with many", - "sacrifices, soon", - "enough." - ) - ); + public class LysanderNotebook7 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Lysander's Notebook", "L. Gathenwale", + new BookPageInfo + ( + "Day Seven :", + "", + "The Sewel woman", + "pratters on endlessly.", + "And she dares to", + "speak Thy Name,", + "Master! I wish so", + "vehemently to take a" + ), + new BookPageInfo + ( + "knife to that little", + "neck of hers. She", + "struts around the", + "chambers of Thy", + "Sanctum with her", + "repugnant airs, her", + "scholarly conjecture", + "on this or that. That I" + ), + new BookPageInfo + ( + "could peel the skin", + "from her face and", + "show her how vile and", + "ugly she truly is, how", + "unworthy of entrance", + "to Thy Sanctum. I", + "must take her,", + "Master. I must rend" + ), + new BookPageInfo + ( + "that little wench to", + "pieces. I ask this gift", + "of Thee, that I might", + "cleanse Thy Sanctum", + "of her presence. Give", + "me the Sewel woman", + "and I shall show you", + "my mastery of Death," + ), + new BookPageInfo + ( + "Master. I shall cut", + "her to bits and scatter", + "them before the", + "others as a warning.", + "I cannot stand her", + "presence, I cannot", + "abide it. And", + "Drummel! He is a" + ), + new BookPageInfo + ( + "pustule that must be", + "lanced, a sickness that", + "I must cure by blade", + "and fire. Not a trace", + "of him will be left", + "when I'm done with", + "him. Praises to Thee,", + "Master. I shall honor" + ), + new BookPageInfo + ( + "Thee with many", + "sacrifices, soon", + "enough." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public LysanderNotebook7() : base(Utility.Random(0xFF1, 2), false) + { + } - [Constructible] - public LysanderNotebook7() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } + public LysanderNotebook7(Serial serial) : base(serial) + { + } - public LysanderNotebook7( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LysanderNotebook8 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Lysander's Notebook", "L. Gathenwale", - new BookPageInfo - ( - "Day Eight - Day Ten :", - "", - "Have you taken them,", - "Master? They could", - "not have found a way", - "past the stones that", - "block our path! The", - "three workers, My" - ), - new BookPageInfo - ( - "Master, where have", - "they gone? Curses", - "upon them! I'll cut", - "them all to pieces if", - "they show their faces", - "again, then burn the", - "rest alive upon a pyre,", - "for all to see, as a" - ), - new BookPageInfo - ( - "warning of Thy", - "Power. How could", - "they have gotten past", - "me? I sleep against", - "the very walls, to", - "hear Thy Words, to", - "feel Thy Breath. I", - "can find no egress" - ), - new BookPageInfo - ( - "from the chambers", - "that the Sewel woman", - "does not know of nor", - "have men working at", - "excavating. Where", - "have they gone,", - "Master? Have you", - "taken them, or do they" - ), - new BookPageInfo - ( - "truly flee from Thy", - "Presence? I will kill", - "them if they show", - "their faces again.", - "Give me Strength, my", - "Master, to let them", - "live a while longer,", - "until they have" - ), - new BookPageInfo - ( - "fulfilled their", - "purpose and I kneel", - "before Thee, covered", - "in their blood." - ) - ); + public class LysanderNotebook8 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Lysander's Notebook", "L. Gathenwale", + new BookPageInfo + ( + "Day Eight - Day Ten :", + "", + "Have you taken them,", + "Master? They could", + "not have found a way", + "past the stones that", + "block our path! The", + "three workers, My" + ), + new BookPageInfo + ( + "Master, where have", + "they gone? Curses", + "upon them! I'll cut", + "them all to pieces if", + "they show their faces", + "again, then burn the", + "rest alive upon a pyre,", + "for all to see, as a" + ), + new BookPageInfo + ( + "warning of Thy", + "Power. How could", + "they have gotten past", + "me? I sleep against", + "the very walls, to", + "hear Thy Words, to", + "feel Thy Breath. I", + "can find no egress" + ), + new BookPageInfo + ( + "from the chambers", + "that the Sewel woman", + "does not know of nor", + "have men working at", + "excavating. Where", + "have they gone,", + "Master? Have you", + "taken them, or do they" + ), + new BookPageInfo + ( + "truly flee from Thy", + "Presence? I will kill", + "them if they show", + "their faces again.", + "Give me Strength, my", + "Master, to let them", + "live a while longer,", + "until they have" + ), + new BookPageInfo + ( + "fulfilled their", + "purpose and I kneel", + "before Thee, covered", + "in their blood." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public LysanderNotebook8() : base(Utility.Random(0xFF1, 2), false) + { + } - [Constructible] - public LysanderNotebook8() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } + public LysanderNotebook8(Serial serial) : base(serial) + { + } - public LysanderNotebook8( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LysanderNotebook11 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Lysander's Notebook", "L. Gathenwale", - new BookPageInfo - ( - "Day Eleven - Day", - "Thirteen:", - "", - "I come for Thee, my", - "Master. I come! The", - "way is clear, I have", - "found Thy path and", - "washed it in the blood" - ), - new BookPageInfo - ( - "of the two workers", - "that caught sight of", - "me. Ah, how sweet it", - "was to cut them open,", - "to see the blood pour", - "out in great torrents, to", - "stand in it, to revel in", - "it. If only I had time" - ), - new BookPageInfo - ( - "for the Sewel woman.", - "But there will be time", - "enough for her. I", - "have learned Thy", - "Patience, Master. I", - "come for Thee. I walk", - "Thy halls in penance,", - "my last steps in this" - ), - new BookPageInfo - ( - "repulsive living", - "frame. I come for", - "Thee and Thy Gifts,", - "my Master. Glory", - "Unto Thee, Khal", - "Ankur, Keeper of the", - "Seventh Death,", - "Master, Leader of the" - ), - new BookPageInfo - ( - "Chosen, the Khaldun.", - "Praises in Thy", - "Name, Master of Life", - "and Death, Lord of All.", - " Khal Ankur, Master,", - "Prophet, I join Thy", - "ranks this night, a", - "member of the" - ), - new BookPageInfo - ( - "Khaldun at last!" - ) - ); + public class LysanderNotebook11 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Lysander's Notebook", "L. Gathenwale", + new BookPageInfo + ( + "Day Eleven - Day", + "Thirteen:", + "", + "I come for Thee, my", + "Master. I come! The", + "way is clear, I have", + "found Thy path and", + "washed it in the blood" + ), + new BookPageInfo + ( + "of the two workers", + "that caught sight of", + "me. Ah, how sweet it", + "was to cut them open,", + "to see the blood pour", + "out in great torrents, to", + "stand in it, to revel in", + "it. If only I had time" + ), + new BookPageInfo + ( + "for the Sewel woman.", + "But there will be time", + "enough for her. I", + "have learned Thy", + "Patience, Master. I", + "come for Thee. I walk", + "Thy halls in penance,", + "my last steps in this" + ), + new BookPageInfo + ( + "repulsive living", + "frame. I come for", + "Thee and Thy Gifts,", + "my Master. Glory", + "Unto Thee, Khal", + "Ankur, Keeper of the", + "Seventh Death,", + "Master, Leader of the" + ), + new BookPageInfo + ( + "Chosen, the Khaldun.", + "Praises in Thy", + "Name, Master of Life", + "and Death, Lord of All.", + " Khal Ankur, Master,", + "Prophet, I join Thy", + "ranks this night, a", + "member of the" + ), + new BookPageInfo + ( + "Khaldun at last!" + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public LysanderNotebook11() : base(Utility.Random(0xFF1, 2), false) + { + } - [Constructible] - public LysanderNotebook11() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } + public LysanderNotebook11(Serial serial) : base(serial) + { + } - public LysanderNotebook11( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Books/TavarasJournal.cs b/Scripts/Engines/Khaldun/Books/TavarasJournal.cs index dcba5ea95..0d82eb98f 100644 --- a/Scripts/Engines/Khaldun/Books/TavarasJournal.cs +++ b/Scripts/Engines/Khaldun/Books/TavarasJournal.cs @@ -1,1330 +1,1330 @@ namespace Server.Items { - public class TavarasJournal1 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day One:", - "", - "The workers continue", - "tirelessly in their", - "efforts to unload our", - "supplies even as light", - "fades. I feel I should", - "lend a hand in the" - ), - new BookPageInfo - ( - "effort, and yet I", - "cannot bear to take my", - "attention away from", - "the magnificent stone", - "doors of the tomb.", - "Every inch of their", - "massive frame is", - "covered with" - ), - new BookPageInfo - ( - "intricately carved", - "design work - 'tis", - "truly a sight to see.", - "I've spent the day", - "sketching and", - "cataloging what I can", - "of them while my", - "companions set up our" - ), - new BookPageInfo - ( - "camp and make", - "preparations for", - "tomorrow's work.", - "Though the stonework", - "symbols inspire me to", - "new flights of fancy,", - "some of the workers", - "seem strangely" - ), - new BookPageInfo - ( - "fearful of them. I", - "cannot wait 'til the", - "morrow when those", - "ancient works of stone", - "shall swing open and", - "deliver unto me", - "everything I have", - "dreamed of for the" - ), - new BookPageInfo - ( - "last ten years of my", - "life." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal1() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal1( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal2 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Two:", - "", - "Everything we'd", - "heard and read of the", - "tomb has proved", - "correct - and yet,", - "nothing could prepare", - "me for the sight of it" - ), - new BookPageInfo - ( - "with my own eyes.", - "The Tomb of Khal", - "Ankur has given up", - "its secrets at last! The", - "intricate stonework", - "that covered the tomb", - "doors seems to", - "continue throughout" - ), - new BookPageInfo - ( - "the entirety of the", - "catacombs, each", - "hallway and room", - "yielding a seemingly", - "endless amount of", - "information for my", - "companions and I to", - "record. It will take" - ), - new BookPageInfo - ( - "years to catalogue the", - "entirety of the Tomb,", - "if those legends of its", - "massive size prove", - "true. Sadly, a good", - "deal of the Tomb's", - "interior has been", - "damaged or utterly" - ), - new BookPageInfo - ( - "destroyed, whether", - "by seismic activity in", - "the surrounding", - "mountainside or", - "merely the slow", - "efforts of Time", - "itself, I do not know.", - "A good deal of the" - ), - new BookPageInfo - ( - "stonework has been", - "cracked or collapsed", - "entirely, especially", - "near the entrance", - "supports of the main", - "hall. Our passage has", - "indeed already been", - "entirely blocked in the" - ), - new BookPageInfo - ( - "first major room", - "we've discovered, a", - "massive pile of", - "boulders and stones", - "blocking any exit", - "from the", - "antechamber. What", - "could have caused" - ), - new BookPageInfo - ( - "such a localized", - "disruption of the", - "support structures,", - "one can only guess -", - "but it will surely take", - "an entire afternoon's", - "effort to remove even", - "a fraction of it. I look" - ), - new BookPageInfo - ( - "forward to more", - "progress tomorrow", - "once the workers have", - "set to excavating the", - "hall." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal2() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal3 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Three - Day Five:", - "", - "I do not understand", - "this place... not as I", - "once thought I did.", - "Something palatable", - "seems to hinder our", - "every attempt to" - ), - new BookPageInfo - ( - "investigate this", - "ancient site.", - "Excavation work on", - "the first major", - "hallway finished only", - "yesterday - the", - "amount of stone and", - "rubble blocking the" - ), - new BookPageInfo - ( - "egress was", - "astounding, it stands", - "in immense piles", - "outside the Tomb's", - "entrance, as if we", - "were digging the", - "tunnels of this", - "abhorred place" - ), - new BookPageInfo - ( - "ourselves! The", - "satisfaction of", - "completing our efforts", - "was quickly thwarted,", - "however, as we", - "discovered the end of", - "the hallway we had", - "just revealed was" - ), - new BookPageInfo - ( - "blocked by yet another", - "colossal pile of stone.", - "I've had a few of the", - "workers set up", - "primitive scaffolding", - "in the main", - "antechamber so that I", - "can spend my time" - ), - new BookPageInfo - ( - "pouring over the detail", - "work on the stone", - "carvings while the", - "rest of our crew", - "continue excavating", - "the inner halls." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal3() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal3( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal6 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Six:", - "", - "Late last night our", - "camp was set upon by", - "a pack of wild beasts", - "- behemoth creatures", - "with a speed and", - "viciousness I'd n'ere" - ), - new BookPageInfo - ( - "before seen. Even", - "Grimmoch, well", - "versed in all manner", - "of wildlife, was", - "unsure as to their", - "nature - though I lay", - "blame upon the", - "darkness covering" - ), - new BookPageInfo - ( - "their movements", - "rather than on his", - "skill as a huntsman.", - "The attacks did not let", - "up the entire night,", - "and we were", - "eventually forced to", - "flee into the Tomb" - ), - new BookPageInfo - ( - "itself to take refuge", - "from the ravenous", - "creatures - e'en", - "Lysander's spells", - "could not keep the foul", - "things from attacking", - "in great numbers.", - "The Tomb performed" - ), - new BookPageInfo - ( - "well as an impromptu", - "fortress, and we", - "managed to spend the", - "night unscathed.", - "Morning's light", - "seemed to have", - "scattered the beasts,", - "as not a single one of" - ), - new BookPageInfo - ( - "them was to be seen as", - "we exited the Tomb -", - "not even a carcass of", - "the few that were", - "slain a'fore we fled.", - "Lysander set the crew", - "to work, moving our", - "supplies and gear into" - ), - new BookPageInfo - ( - "the Tomb, in case the", - "creatures did opt to", - "return. Such savage", - "fury had the beasts -", - "and not a single one", - "ever turned to run,", - "even in the face of", - "certain death." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal6() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal6( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal7 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Seven:", - "", - "T'was written that,", - "upon his death, Khal", - "Ankur's followers,", - "those known as the", - "Keepers of the", - "Seventh Death, sealed" - ), - new BookPageInfo - ( - "themselves within the", - "Sanctum they had", - "carved from the", - "mountains in his", - "honor. The Zealots of", - "his order entombed", - "the lesser followers", - "alive, then, when all" - ), - new BookPageInfo - ( - "but two remained, slit", - "their throats and", - "joined Khal Ankur in", - "death. Surely this is", - "not surprising for a", - "Cult that worshipped", - "death and sacrifice so", - "vehemently as it is" - ), - new BookPageInfo - ( - "said that the Keepers", - "did - and yet, to be in", - "this Tomb, to know", - "that somewhere in its", - "depths hundreds upon", - "hundreds of bodies", - "lay, sealed alive at", - "their own behest..." - ), - new BookPageInfo - ( - "I must confess that", - "the very thought of it", - "troubles my dreams at", - "night. I've asked", - "Lysander if we might", - "reestablish the camp", - "outside the Tomb,", - "setting up night" - ), - new BookPageInfo - ( - "watches and some sort", - "of fortification, but", - "he'll have none of it. I", - "did not press the", - "issue, as I suddenly", - "felt foolish even at", - "my askance." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal7() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal7( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal8 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Eight :", - "", - "Astounding progress", - "was made today, and", - "my very head spins", - "with the excitement", - "of it. Upon full", - "excavation of the far" - ), - new BookPageInfo - ( - "western hall, another", - "large antechamber", - "was revealed. By the", - "larger, mosaic style of", - "the wall carvings and", - "their framing, as well", - "as the numerous", - "vellum scrolls and" - ), - new BookPageInfo - ( - "tomes held within, the", - "room appears to have", - "been a great museum", - "or library of sorts.", - "The sheer amount of", - "written information", - "encased within this", - "room would surely" - ), - new BookPageInfo - ( - "take me decades to", - "study e'en if I could", - "immediately decipher", - "the strange text with", - "which it was written.", - "My sheer joy at the", - "discovery was quickly", - "noted by the brute" - ), - new BookPageInfo - ( - "known as Morg", - "Bergen, who, even in", - "his simple way,", - "seemed just as", - "delighted as I that", - "some progress had", - "been made. I must", - "confess, upon his" - ), - new BookPageInfo - ( - "inclusion in our party", - "at the beginning of", - "this journey I was", - "somewhat suspect of", - "his nature, but he has", - "a startlingly quick wit", - "about him for such a", - "massive, calloused" - ), - new BookPageInfo - ( - "warrior. While", - "Lysander and e'en", - "Grimmoch always", - "seem to investigate the", - "tomb with a scowling", - "determination, Bergen", - "seems to feel the same", - "thrill of discovery as" - ), - new BookPageInfo - ( - "I. I am proud to now", - "count him as a friend,", - "and am thankful for", - "his laughter as well", - "as his strength." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal8() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal8( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal9 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Nine - Day Ten:", - "", - "The excavation of the", - "next set of tunnels", - "has ceased, as three", - "of the workers have", - "gone missing in the", - "night. Bergen voiced" - ), - new BookPageInfo - ( - "the opinion that they", - "had most likely", - "abandoned our group", - "altogether and headed", - "back, as they were of", - "the number that", - "seemed especially", - "disturbed by the" - ), - new BookPageInfo - ( - "Tomb. Lysander had", - "other ideas, however.", - "In the middle of our", - "discussion on the", - "matter, he went into a", - "wild tirade on the", - "possibility that they", - "had somehow" - ), - new BookPageInfo - ( - "infiltrated the tomb's", - "interior without us.", - "The pure, hateful", - "venom in his voice", - "when he spoke of the", - "workers shocked me,", - "as I had always", - "thought him to be a" - ), - new BookPageInfo - ( - "levelheaded man of", - "great learning. As we", - "are still at work", - "digging out the rubble", - "that blocks all access", - "to the inner chambers,", - "I cannot help but", - "believe the workers" - ), - new BookPageInfo - ( - "must have fled the", - "site altogether, as", - "Bergen said." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal9() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal9( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal11 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Eleven - Day", - "Thirteen:", - "", - "Two more workers", - "have gone missing.", - "Even more disturbing", - "is the fact that", - "Lysander has joined" - ), - new BookPageInfo - ( - "them. Late last night", - "the workers finished", - "excavating the next", - "main hall, and we", - "retired to the main", - "antechamber and our", - "camp to rest up for", - "exploration on the" - ), - new BookPageInfo - ( - "'morrow. In the", - "middle of the night we", - "woke to a strange", - "howling sound, and as", - "the men prepared", - "themselves for", - "another onslaught of", - "the beasts that had" - ), - new BookPageInfo - ( - "troubled our outer", - "camp, it was noticed", - "that Lysander was", - "nowhere in our", - "number. I cannot", - "fathom where he has", - "gone - the newly", - "revealed chamber" - ), - new BookPageInfo - ( - "holds no immediate", - "egress, blocked again", - "by piles of stone and", - "rubble, and I cannot", - "believe that Lysander,", - "of all people, would", - "have fled this site -", - "indeed, he had lately" - ), - new BookPageInfo - ( - "grown almost fanatical", - "in his work to", - "discover more of the", - "secrets barred to us", - "by the consistently", - "slow progress of", - "excavating each new", - "hallway. The men are" - ), - new BookPageInfo - ( - "at work even now, and", - "as the ceaseless", - "thumps and cracks of", - "their picks", - "reverberate", - "throughout the", - "entirety of the tomb,", - "the dust continues to" - ), - new BookPageInfo - ( - "pour down from the", - "ancient stonework", - "above us like some", - "horrible, eldritch", - "curse upon us all." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal11() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal11( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal14 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Fourteen - Day", - "Fifteen:", - "", - "Lysander has", - "returned... and yet,", - "how can I describe the", - "horror of it? He", - "stands across the" - ), - new BookPageInfo - ( - "chamber from me", - "even now, a changed", - "man. His hair hangs", - "in grimy knots across", - "his face, his clothes", - "filthy and torn in", - "places... and the blood", - "- covered in blood, his" - ), - new BookPageInfo - ( - "skin shining in", - "scarlet reflections of", - "the torchlight. He", - "will let no one", - "approach; a thick,", - "rusted dagger in his", - "hand warding off any", - "attempts to overcome" - ), - new BookPageInfo - ( - "him. And the blood,", - "which runs down in", - "great rivulets from", - "his arms and hands -", - "it is not his own, and", - "this is enough to keep", - "us at a wary distance.", - "Morg Bergen wishes" - ), - new BookPageInfo - ( - "to subdue him", - "quickly, but there is", - "something in", - "Lysander's eyes - and", - "I remember the power", - "of his spells, even as", - "he swings the jagged", - "dagger back and forth" - ), - new BookPageInfo - ( - "in a wide swath", - "before him.", - "Something about the", - "sight of it makes my", - "stomach churn.", - "Something has", - "happened, something", - "that changes" - ), - new BookPageInfo - ( - "everything. Lysander", - "has lost his sanity to", - "this tomb... or to", - "something within it.", - "Do we dare approach?", - "We must make a", - "decision soon." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal14() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal14( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal16 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Sixteen:", - "", - "Why do I write? I", - "must... not so much", - "because there must be", - "some record of", - "this... what's", - "happened here... as" - ), - new BookPageInfo - ( - "for my own sanity.", - "The act of putting pen", - "to paper calms me,", - "focuses me, even in", - "this madness.", - "Lysander is dead. So", - "many are dead. And", - "we're trapped here," - ), - new BookPageInfo - ( - "trapped forever in", - "this nightmare. He", - "would not let us pass,", - "wild in his psychosis,", - "furious, spitting,", - "covered in blood, he", - "swung the ancient", - "dagger at any who" - ), - new BookPageInfo - ( - "approached. He", - "babbled incoherently,", - "cursed at us, the most", - "hateful curses,", - "prophecy, doom upon", - "us. Bergen would", - "have none of it.", - "Finally, he leapt at" - ), - new BookPageInfo - ( - "Lysander, his", - "massive axe at his", - "side. But he would not", - "be the end of the mad", - "mage... no... they", - "were... those hands,", - "covered in the dirt of", - "the grave, maggots," - ), - new BookPageInfo - ( - "filth. They rose up", - "behind Lysander.", - "That look of curiosity", - "on the mage's face as", - "Bergen skidded to a", - "halt... t'was almost a", - "moment of sanity for", - "him, surely, to" - ), - new BookPageInfo - ( - "attempt to comprehend", - "what could have", - "stopped the warrior in", - "his tracks. And then", - "they were upon him.", - "Skeletal hands, arms", - "and faces with loose,", - "corrupted flesh" - ), - new BookPageInfo - ( - "hanging from yellow", - "bone. Inhuman, yet", - "once human,", - "staggering towards us", - "as their companions", - "tore at Lysander,", - "coming towards us in", - "droves." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal16() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal16( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal16b : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Sixteen, Later :", - "", - "We ran. What could", - "we do? We ran back", - "towards the entrance,", - "cutting at them when", - "we could. T'was a", - "nightmare, and yet" - ), - new BookPageInfo - ( - "nothing to prepare us", - "for what would come.", - "We were almost there,", - "the entrance to this", - "abhorred crypt in", - "sight. Then the earth", - "shook with such a", - "force that we were" - ), - new BookPageInfo - ( - "dropped to our hands", - "and knees, stumbling", - "in the darkness with", - "those... those things", - "surely behind us.", - "The noise of falling", - "rock and crumbling", - "stone drowned out our" - ), - new BookPageInfo - ( - "piteous cries. No sign", - "of the entrance", - "remained.", - "We owe our lives to", - "Bergen, whose wits", - "returned quickly.", - "That he could make us", - "hurry back into the" - ), - new BookPageInfo - ( - "main antechamber...", - "actually run back", - "towards those eldritch", - "dead that stalked us.", - "But we did, the", - "strength of his", - "convictions enough for", - "us in the moment." - ), - new BookPageInfo - ( - "And at our campsite", - "we erected our last", - "defense, a pitiable", - "wall of wood and", - "stone, anything at", - "hand that might block", - "the tide of those", - "nightmare creatures." - ), - new BookPageInfo - ( - "And I sit against it", - "even now. I can hear", - "their moans, their", - "wailing cries in the", - "distance - they'll be", - "here soon, even at the", - "unhurried pace of the", - "shuffling dead." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal16b() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal16b( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal17 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Seventeen - Day", - "Eighteen :", - "", - "I cannot go on much", - "longer. I know now", - "t'was no work of the", - "earth that trapped us", - "here - I can feel His" - ), - new BookPageInfo - ( - "force in it. It was His", - "will, His power that", - "has sealed us here in", - "this nightmare. The", - "barricade will not be", - "enough. So many of", - "them. They come like", - "unto the ocean's waves" - ), - new BookPageInfo - ( - "- ceaseless,", - "neverending. For", - "every five we strike", - "down, another ten rise", - "up against us. And", - "like the sands we", - "cannot help but be", - "brought down, wasted" - ), - new BookPageInfo - ( - "away in this ocean of", - "blood." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal17() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal17( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class TavarasJournal19 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal: Discovery of the Tomb", "Tavara Sewel", - new BookPageInfo - ( - "Day Nineteen - Day", - "Twenty-One :", - "", - "The barricade won't", - "hold - never, and", - "they'll come, they", - "come even now. I", - "would tear the last of" - ), - new BookPageInfo - ( - "it down, let them in to", - "devour us all, if only", - "to stop the screaming", - "- the awful, wailing", - "cries that fill the tomb", - "with their presence.", - "May my ancestors", - "forgive me, but it" - ), - new BookPageInfo - ( - "must be done. I must", - "end this." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TavarasJournal19() : base( Utility.Random( 0xFF1, 2 ), false ) - { - } - - public TavarasJournal19( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + public class TavarasJournal1 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day One:", + "", + "The workers continue", + "tirelessly in their", + "efforts to unload our", + "supplies even as light", + "fades. I feel I should", + "lend a hand in the" + ), + new BookPageInfo + ( + "effort, and yet I", + "cannot bear to take my", + "attention away from", + "the magnificent stone", + "doors of the tomb.", + "Every inch of their", + "massive frame is", + "covered with" + ), + new BookPageInfo + ( + "intricately carved", + "design work - 'tis", + "truly a sight to see.", + "I've spent the day", + "sketching and", + "cataloging what I can", + "of them while my", + "companions set up our" + ), + new BookPageInfo + ( + "camp and make", + "preparations for", + "tomorrow's work.", + "Though the stonework", + "symbols inspire me to", + "new flights of fancy,", + "some of the workers", + "seem strangely" + ), + new BookPageInfo + ( + "fearful of them. I", + "cannot wait 'til the", + "morrow when those", + "ancient works of stone", + "shall swing open and", + "deliver unto me", + "everything I have", + "dreamed of for the" + ), + new BookPageInfo + ( + "last ten years of my", + "life." + ) + ); + + [Constructible] + public TavarasJournal1() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal1(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal2 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Two:", + "", + "Everything we'd", + "heard and read of the", + "tomb has proved", + "correct - and yet,", + "nothing could prepare", + "me for the sight of it" + ), + new BookPageInfo + ( + "with my own eyes.", + "The Tomb of Khal", + "Ankur has given up", + "its secrets at last! The", + "intricate stonework", + "that covered the tomb", + "doors seems to", + "continue throughout" + ), + new BookPageInfo + ( + "the entirety of the", + "catacombs, each", + "hallway and room", + "yielding a seemingly", + "endless amount of", + "information for my", + "companions and I to", + "record. It will take" + ), + new BookPageInfo + ( + "years to catalogue the", + "entirety of the Tomb,", + "if those legends of its", + "massive size prove", + "true. Sadly, a good", + "deal of the Tomb's", + "interior has been", + "damaged or utterly" + ), + new BookPageInfo + ( + "destroyed, whether", + "by seismic activity in", + "the surrounding", + "mountainside or", + "merely the slow", + "efforts of Time", + "itself, I do not know.", + "A good deal of the" + ), + new BookPageInfo + ( + "stonework has been", + "cracked or collapsed", + "entirely, especially", + "near the entrance", + "supports of the main", + "hall. Our passage has", + "indeed already been", + "entirely blocked in the" + ), + new BookPageInfo + ( + "first major room", + "we've discovered, a", + "massive pile of", + "boulders and stones", + "blocking any exit", + "from the", + "antechamber. What", + "could have caused" + ), + new BookPageInfo + ( + "such a localized", + "disruption of the", + "support structures,", + "one can only guess -", + "but it will surely take", + "an entire afternoon's", + "effort to remove even", + "a fraction of it. I look" + ), + new BookPageInfo + ( + "forward to more", + "progress tomorrow", + "once the workers have", + "set to excavating the", + "hall." + ) + ); + + [Constructible] + public TavarasJournal2() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal2(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal3 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Three - Day Five:", + "", + "I do not understand", + "this place... not as I", + "once thought I did.", + "Something palatable", + "seems to hinder our", + "every attempt to" + ), + new BookPageInfo + ( + "investigate this", + "ancient site.", + "Excavation work on", + "the first major", + "hallway finished only", + "yesterday - the", + "amount of stone and", + "rubble blocking the" + ), + new BookPageInfo + ( + "egress was", + "astounding, it stands", + "in immense piles", + "outside the Tomb's", + "entrance, as if we", + "were digging the", + "tunnels of this", + "abhorred place" + ), + new BookPageInfo + ( + "ourselves! The", + "satisfaction of", + "completing our efforts", + "was quickly thwarted,", + "however, as we", + "discovered the end of", + "the hallway we had", + "just revealed was" + ), + new BookPageInfo + ( + "blocked by yet another", + "colossal pile of stone.", + "I've had a few of the", + "workers set up", + "primitive scaffolding", + "in the main", + "antechamber so that I", + "can spend my time" + ), + new BookPageInfo + ( + "pouring over the detail", + "work on the stone", + "carvings while the", + "rest of our crew", + "continue excavating", + "the inner halls." + ) + ); + + [Constructible] + public TavarasJournal3() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal3(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal6 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Six:", + "", + "Late last night our", + "camp was set upon by", + "a pack of wild beasts", + "- behemoth creatures", + "with a speed and", + "viciousness I'd n'ere" + ), + new BookPageInfo + ( + "before seen. Even", + "Grimmoch, well", + "versed in all manner", + "of wildlife, was", + "unsure as to their", + "nature - though I lay", + "blame upon the", + "darkness covering" + ), + new BookPageInfo + ( + "their movements", + "rather than on his", + "skill as a huntsman.", + "The attacks did not let", + "up the entire night,", + "and we were", + "eventually forced to", + "flee into the Tomb" + ), + new BookPageInfo + ( + "itself to take refuge", + "from the ravenous", + "creatures - e'en", + "Lysander's spells", + "could not keep the foul", + "things from attacking", + "in great numbers.", + "The Tomb performed" + ), + new BookPageInfo + ( + "well as an impromptu", + "fortress, and we", + "managed to spend the", + "night unscathed.", + "Morning's light", + "seemed to have", + "scattered the beasts,", + "as not a single one of" + ), + new BookPageInfo + ( + "them was to be seen as", + "we exited the Tomb -", + "not even a carcass of", + "the few that were", + "slain a'fore we fled.", + "Lysander set the crew", + "to work, moving our", + "supplies and gear into" + ), + new BookPageInfo + ( + "the Tomb, in case the", + "creatures did opt to", + "return. Such savage", + "fury had the beasts -", + "and not a single one", + "ever turned to run,", + "even in the face of", + "certain death." + ) + ); + + [Constructible] + public TavarasJournal6() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal6(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal7 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Seven:", + "", + "T'was written that,", + "upon his death, Khal", + "Ankur's followers,", + "those known as the", + "Keepers of the", + "Seventh Death, sealed" + ), + new BookPageInfo + ( + "themselves within the", + "Sanctum they had", + "carved from the", + "mountains in his", + "honor. The Zealots of", + "his order entombed", + "the lesser followers", + "alive, then, when all" + ), + new BookPageInfo + ( + "but two remained, slit", + "their throats and", + "joined Khal Ankur in", + "death. Surely this is", + "not surprising for a", + "Cult that worshipped", + "death and sacrifice so", + "vehemently as it is" + ), + new BookPageInfo + ( + "said that the Keepers", + "did - and yet, to be in", + "this Tomb, to know", + "that somewhere in its", + "depths hundreds upon", + "hundreds of bodies", + "lay, sealed alive at", + "their own behest..." + ), + new BookPageInfo + ( + "I must confess that", + "the very thought of it", + "troubles my dreams at", + "night. I've asked", + "Lysander if we might", + "reestablish the camp", + "outside the Tomb,", + "setting up night" + ), + new BookPageInfo + ( + "watches and some sort", + "of fortification, but", + "he'll have none of it. I", + "did not press the", + "issue, as I suddenly", + "felt foolish even at", + "my askance." + ) + ); + + [Constructible] + public TavarasJournal7() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal7(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal8 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Eight :", + "", + "Astounding progress", + "was made today, and", + "my very head spins", + "with the excitement", + "of it. Upon full", + "excavation of the far" + ), + new BookPageInfo + ( + "western hall, another", + "large antechamber", + "was revealed. By the", + "larger, mosaic style of", + "the wall carvings and", + "their framing, as well", + "as the numerous", + "vellum scrolls and" + ), + new BookPageInfo + ( + "tomes held within, the", + "room appears to have", + "been a great museum", + "or library of sorts.", + "The sheer amount of", + "written information", + "encased within this", + "room would surely" + ), + new BookPageInfo + ( + "take me decades to", + "study e'en if I could", + "immediately decipher", + "the strange text with", + "which it was written.", + "My sheer joy at the", + "discovery was quickly", + "noted by the brute" + ), + new BookPageInfo + ( + "known as Morg", + "Bergen, who, even in", + "his simple way,", + "seemed just as", + "delighted as I that", + "some progress had", + "been made. I must", + "confess, upon his" + ), + new BookPageInfo + ( + "inclusion in our party", + "at the beginning of", + "this journey I was", + "somewhat suspect of", + "his nature, but he has", + "a startlingly quick wit", + "about him for such a", + "massive, calloused" + ), + new BookPageInfo + ( + "warrior. While", + "Lysander and e'en", + "Grimmoch always", + "seem to investigate the", + "tomb with a scowling", + "determination, Bergen", + "seems to feel the same", + "thrill of discovery as" + ), + new BookPageInfo + ( + "I. I am proud to now", + "count him as a friend,", + "and am thankful for", + "his laughter as well", + "as his strength." + ) + ); + + [Constructible] + public TavarasJournal8() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal8(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal9 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Nine - Day Ten:", + "", + "The excavation of the", + "next set of tunnels", + "has ceased, as three", + "of the workers have", + "gone missing in the", + "night. Bergen voiced" + ), + new BookPageInfo + ( + "the opinion that they", + "had most likely", + "abandoned our group", + "altogether and headed", + "back, as they were of", + "the number that", + "seemed especially", + "disturbed by the" + ), + new BookPageInfo + ( + "Tomb. Lysander had", + "other ideas, however.", + "In the middle of our", + "discussion on the", + "matter, he went into a", + "wild tirade on the", + "possibility that they", + "had somehow" + ), + new BookPageInfo + ( + "infiltrated the tomb's", + "interior without us.", + "The pure, hateful", + "venom in his voice", + "when he spoke of the", + "workers shocked me,", + "as I had always", + "thought him to be a" + ), + new BookPageInfo + ( + "levelheaded man of", + "great learning. As we", + "are still at work", + "digging out the rubble", + "that blocks all access", + "to the inner chambers,", + "I cannot help but", + "believe the workers" + ), + new BookPageInfo + ( + "must have fled the", + "site altogether, as", + "Bergen said." + ) + ); + + [Constructible] + public TavarasJournal9() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal9(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal11 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Eleven - Day", + "Thirteen:", + "", + "Two more workers", + "have gone missing.", + "Even more disturbing", + "is the fact that", + "Lysander has joined" + ), + new BookPageInfo + ( + "them. Late last night", + "the workers finished", + "excavating the next", + "main hall, and we", + "retired to the main", + "antechamber and our", + "camp to rest up for", + "exploration on the" + ), + new BookPageInfo + ( + "'morrow. In the", + "middle of the night we", + "woke to a strange", + "howling sound, and as", + "the men prepared", + "themselves for", + "another onslaught of", + "the beasts that had" + ), + new BookPageInfo + ( + "troubled our outer", + "camp, it was noticed", + "that Lysander was", + "nowhere in our", + "number. I cannot", + "fathom where he has", + "gone - the newly", + "revealed chamber" + ), + new BookPageInfo + ( + "holds no immediate", + "egress, blocked again", + "by piles of stone and", + "rubble, and I cannot", + "believe that Lysander,", + "of all people, would", + "have fled this site -", + "indeed, he had lately" + ), + new BookPageInfo + ( + "grown almost fanatical", + "in his work to", + "discover more of the", + "secrets barred to us", + "by the consistently", + "slow progress of", + "excavating each new", + "hallway. The men are" + ), + new BookPageInfo + ( + "at work even now, and", + "as the ceaseless", + "thumps and cracks of", + "their picks", + "reverberate", + "throughout the", + "entirety of the tomb,", + "the dust continues to" + ), + new BookPageInfo + ( + "pour down from the", + "ancient stonework", + "above us like some", + "horrible, eldritch", + "curse upon us all." + ) + ); + + [Constructible] + public TavarasJournal11() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal11(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal14 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Fourteen - Day", + "Fifteen:", + "", + "Lysander has", + "returned... and yet,", + "how can I describe the", + "horror of it? He", + "stands across the" + ), + new BookPageInfo + ( + "chamber from me", + "even now, a changed", + "man. His hair hangs", + "in grimy knots across", + "his face, his clothes", + "filthy and torn in", + "places... and the blood", + "- covered in blood, his" + ), + new BookPageInfo + ( + "skin shining in", + "scarlet reflections of", + "the torchlight. He", + "will let no one", + "approach; a thick,", + "rusted dagger in his", + "hand warding off any", + "attempts to overcome" + ), + new BookPageInfo + ( + "him. And the blood,", + "which runs down in", + "great rivulets from", + "his arms and hands -", + "it is not his own, and", + "this is enough to keep", + "us at a wary distance.", + "Morg Bergen wishes" + ), + new BookPageInfo + ( + "to subdue him", + "quickly, but there is", + "something in", + "Lysander's eyes - and", + "I remember the power", + "of his spells, even as", + "he swings the jagged", + "dagger back and forth" + ), + new BookPageInfo + ( + "in a wide swath", + "before him.", + "Something about the", + "sight of it makes my", + "stomach churn.", + "Something has", + "happened, something", + "that changes" + ), + new BookPageInfo + ( + "everything. Lysander", + "has lost his sanity to", + "this tomb... or to", + "something within it.", + "Do we dare approach?", + "We must make a", + "decision soon." + ) + ); + + [Constructible] + public TavarasJournal14() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal14(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal16 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Sixteen:", + "", + "Why do I write? I", + "must... not so much", + "because there must be", + "some record of", + "this... what's", + "happened here... as" + ), + new BookPageInfo + ( + "for my own sanity.", + "The act of putting pen", + "to paper calms me,", + "focuses me, even in", + "this madness.", + "Lysander is dead. So", + "many are dead. And", + "we're trapped here," + ), + new BookPageInfo + ( + "trapped forever in", + "this nightmare. He", + "would not let us pass,", + "wild in his psychosis,", + "furious, spitting,", + "covered in blood, he", + "swung the ancient", + "dagger at any who" + ), + new BookPageInfo + ( + "approached. He", + "babbled incoherently,", + "cursed at us, the most", + "hateful curses,", + "prophecy, doom upon", + "us. Bergen would", + "have none of it.", + "Finally, he leapt at" + ), + new BookPageInfo + ( + "Lysander, his", + "massive axe at his", + "side. But he would not", + "be the end of the mad", + "mage... no... they", + "were... those hands,", + "covered in the dirt of", + "the grave, maggots," + ), + new BookPageInfo + ( + "filth. They rose up", + "behind Lysander.", + "That look of curiosity", + "on the mage's face as", + "Bergen skidded to a", + "halt... t'was almost a", + "moment of sanity for", + "him, surely, to" + ), + new BookPageInfo + ( + "attempt to comprehend", + "what could have", + "stopped the warrior in", + "his tracks. And then", + "they were upon him.", + "Skeletal hands, arms", + "and faces with loose,", + "corrupted flesh" + ), + new BookPageInfo + ( + "hanging from yellow", + "bone. Inhuman, yet", + "once human,", + "staggering towards us", + "as their companions", + "tore at Lysander,", + "coming towards us in", + "droves." + ) + ); + + [Constructible] + public TavarasJournal16() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal16(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal16b : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Sixteen, Later :", + "", + "We ran. What could", + "we do? We ran back", + "towards the entrance,", + "cutting at them when", + "we could. T'was a", + "nightmare, and yet" + ), + new BookPageInfo + ( + "nothing to prepare us", + "for what would come.", + "We were almost there,", + "the entrance to this", + "abhorred crypt in", + "sight. Then the earth", + "shook with such a", + "force that we were" + ), + new BookPageInfo + ( + "dropped to our hands", + "and knees, stumbling", + "in the darkness with", + "those... those things", + "surely behind us.", + "The noise of falling", + "rock and crumbling", + "stone drowned out our" + ), + new BookPageInfo + ( + "piteous cries. No sign", + "of the entrance", + "remained.", + "We owe our lives to", + "Bergen, whose wits", + "returned quickly.", + "That he could make us", + "hurry back into the" + ), + new BookPageInfo + ( + "main antechamber...", + "actually run back", + "towards those eldritch", + "dead that stalked us.", + "But we did, the", + "strength of his", + "convictions enough for", + "us in the moment." + ), + new BookPageInfo + ( + "And at our campsite", + "we erected our last", + "defense, a pitiable", + "wall of wood and", + "stone, anything at", + "hand that might block", + "the tide of those", + "nightmare creatures." + ), + new BookPageInfo + ( + "And I sit against it", + "even now. I can hear", + "their moans, their", + "wailing cries in the", + "distance - they'll be", + "here soon, even at the", + "unhurried pace of the", + "shuffling dead." + ) + ); + + [Constructible] + public TavarasJournal16b() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal16b(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal17 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Seventeen - Day", + "Eighteen :", + "", + "I cannot go on much", + "longer. I know now", + "t'was no work of the", + "earth that trapped us", + "here - I can feel His" + ), + new BookPageInfo + ( + "force in it. It was His", + "will, His power that", + "has sealed us here in", + "this nightmare. The", + "barricade will not be", + "enough. So many of", + "them. They come like", + "unto the ocean's waves" + ), + new BookPageInfo + ( + "- ceaseless,", + "neverending. For", + "every five we strike", + "down, another ten rise", + "up against us. And", + "like the sands we", + "cannot help but be", + "brought down, wasted" + ), + new BookPageInfo + ( + "away in this ocean of", + "blood." + ) + ); + + [Constructible] + public TavarasJournal17() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal17(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class TavarasJournal19 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal: Discovery of the Tomb", "Tavara Sewel", + new BookPageInfo + ( + "Day Nineteen - Day", + "Twenty-One :", + "", + "The barricade won't", + "hold - never, and", + "they'll come, they", + "come even now. I", + "would tear the last of" + ), + new BookPageInfo + ( + "it down, let them in to", + "devour us all, if only", + "to stop the screaming", + "- the awful, wailing", + "cries that fill the tomb", + "with their presence.", + "May my ancestors", + "forgive me, but it" + ), + new BookPageInfo + ( + "must be done. I must", + "end this." + ) + ); + + [Constructible] + public TavarasJournal19() : base(Utility.Random(0xFF1, 2), false) + { + } + + public TavarasJournal19(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/KhaldunGen.cs b/Scripts/Engines/Khaldun/KhaldunGen.cs index 94f8e5a84..67e814510 100644 --- a/Scripts/Engines/Khaldun/KhaldunGen.cs +++ b/Scripts/Engines/Khaldun/KhaldunGen.cs @@ -3,208 +3,208 @@ using Server.Items; namespace Server.Commands { - public class GenKhaldun - { - private static int m_Count; + public class GenKhaldun + { + private static int m_Count; - public static void Initialize() - { - CommandSystem.Register( "GenKhaldun", AccessLevel.Administrator, GenKhaldun_OnCommand ); - } + public static void Initialize() + { + CommandSystem.Register("GenKhaldun", AccessLevel.Administrator, GenKhaldun_OnCommand); + } - public static bool FindMorphItem( int x, int y, int z, int inactiveItemID, int activeItemID ) - { - IPooledEnumerable eable = Map.Felucca.GetItemsInRange( new Point3D( x, y, z ), 0 ); + public static bool FindMorphItem(int x, int y, int z, int inactiveItemID, int activeItemID) + { + IPooledEnumerable eable = Map.Felucca.GetItemsInRange(new Point3D(x, y, z), 0); - foreach ( Item item in eable ) - { - if ( item is MorphItem morphItem && morphItem.Z == z && morphItem.InactiveItemID == inactiveItemID && morphItem.ActiveItemID == activeItemID ) - { - eable.Free(); - return true; - } - } + foreach (Item item in eable) + if (item is MorphItem morphItem && morphItem.Z == z && morphItem.InactiveItemID == inactiveItemID && + morphItem.ActiveItemID == activeItemID) + { + eable.Free(); + return true; + } - eable.Free(); - return false; - } + eable.Free(); + return false; + } - public static bool FindEffectController( int x, int y, int z ) - { - IPooledEnumerable eable = Map.Felucca.GetItemsInRange( new Point3D( x, y, z ), 0 ); + public static bool FindEffectController(int x, int y, int z) + { + IPooledEnumerable eable = Map.Felucca.GetItemsInRange(new Point3D(x, y, z), 0); - foreach ( Item item in eable ) - { - if ( item is EffectController && item.Z == z ) - { - eable.Free(); - return true; - } - } + foreach (Item item in eable) + if (item is EffectController && item.Z == z) + { + eable.Free(); + return true; + } - eable.Free(); - return false; - } + eable.Free(); + return false; + } - public static Item TryCreateItem( int x, int y, int z, Item srcItem ) - { - IPooledEnumerable eable = Map.Felucca.GetItemsInBounds( new Rectangle2D( x, y, 1, 1 ) ); + public static Item TryCreateItem(int x, int y, int z, Item srcItem) + { + IPooledEnumerable eable = Map.Felucca.GetItemsInBounds(new Rectangle2D(x, y, 1, 1)); - foreach ( Item item in eable ) - { - if ( item.GetType() == srcItem.GetType() ) - { - eable.Free(); - srcItem.Delete(); - return item; - } - } + foreach (Item item in eable) + if (item.GetType() == srcItem.GetType()) + { + eable.Free(); + srcItem.Delete(); + return item; + } - eable.Free(); - srcItem.MoveToWorld( new Point3D( x, y, z ), Map.Felucca ); - m_Count++; + eable.Free(); + srcItem.MoveToWorld(new Point3D(x, y, z), Map.Felucca); + m_Count++; - return srcItem; - } + return srcItem; + } - public static void CreateMorphItem( int x, int y, int z, int inactiveItemID, int activeItemID, int range ) - { - if ( FindMorphItem( x, y, z, inactiveItemID, activeItemID ) ) - return; + public static void CreateMorphItem(int x, int y, int z, int inactiveItemID, int activeItemID, int range) + { + if (FindMorphItem(x, y, z, inactiveItemID, activeItemID)) + return; - MorphItem item = new MorphItem( inactiveItemID, activeItemID, range, 3 ); + MorphItem item = new MorphItem(inactiveItemID, activeItemID, range, 3); - item.MoveToWorld( new Point3D( x, y, z ), Map.Felucca ); - m_Count++; - } + item.MoveToWorld(new Point3D(x, y, z), Map.Felucca); + m_Count++; + } - public static void CreateApproachLight( int x, int y, int z, int off, int on, LightType light ) - { - if ( FindMorphItem( x, y, z, off, on ) ) - return; + public static void CreateApproachLight(int x, int y, int z, int off, int on, LightType light) + { + if (FindMorphItem(x, y, z, off, on)) + return; - MorphItem item = new MorphItem( off, on, 2, 3 ); - item.Light = light; + MorphItem item = new MorphItem(off, on, 2, 3); + item.Light = light; - item.MoveToWorld( new Point3D( x, y, z ), Map.Felucca ); - m_Count++; - } + item.MoveToWorld(new Point3D(x, y, z), Map.Felucca); + m_Count++; + } - public static void CreateSoundEffect( int x, int y, int z, int sound, int range ) - { - if ( FindEffectController( x, y, z ) ) - return; + public static void CreateSoundEffect(int x, int y, int z, int sound, int range) + { + if (FindEffectController(x, y, z)) + return; - EffectController item = new EffectController(); - item.SoundID = sound; - item.TriggerType = EffectTriggerType.InRange; - item.TriggerRange = range; + EffectController item = new EffectController(); + item.SoundID = sound; + item.TriggerType = EffectTriggerType.InRange; + item.TriggerRange = range; - item.MoveToWorld( new Point3D( x, y, z ), Map.Felucca ); - m_Count++; - } + item.MoveToWorld(new Point3D(x, y, z), Map.Felucca); + m_Count++; + } - public static void CreateBigTeleporterItem( int x, int y, bool reverse ) - { - if ( FindMorphItem( x, y, 0, reverse ? 0x17DC : 0x17EE, reverse ? 0x17EE : 0x17DC ) ) - return; + public static void CreateBigTeleporterItem(int x, int y, bool reverse) + { + if (FindMorphItem(x, y, 0, reverse ? 0x17DC : 0x17EE, reverse ? 0x17EE : 0x17DC)) + return; - MorphItem item = new MorphItem( reverse ? 0x17DC : 0x17EE, reverse ? 0x17EE : 0x17DC, 1, 3 ); + MorphItem item = new MorphItem(reverse ? 0x17DC : 0x17EE, reverse ? 0x17EE : 0x17DC, 1, 3); - item.MoveToWorld( new Point3D( x, y, 0 ), Map.Felucca ); - m_Count++; - } + item.MoveToWorld(new Point3D(x, y, 0), Map.Felucca); + m_Count++; + } - public static void GenKhaldun_OnCommand( CommandEventArgs e ) - { - m_Count = 0; + public static void GenKhaldun_OnCommand(CommandEventArgs e) + { + m_Count = 0; - // Generate Morph Items - CreateMorphItem( 5459, 1416, 0, 0x1D0, 0x1, 1 ); - CreateMorphItem( 5460, 1416, 0, 0x1D0, 0x1, 1 ); - CreateMorphItem( 5459, 1416, 0, 0x1, 0x53D, 1 ); - CreateMorphItem( 5460, 1416, 0, 0x1, 0x53B, 1 ); + // Generate Morph Items + CreateMorphItem(5459, 1416, 0, 0x1D0, 0x1, 1); + CreateMorphItem(5460, 1416, 0, 0x1D0, 0x1, 1); + CreateMorphItem(5459, 1416, 0, 0x1, 0x53D, 1); + CreateMorphItem(5460, 1416, 0, 0x1, 0x53B, 1); - CreateMorphItem( 5459, 1425, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5459, 1426, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5459, 1427, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5460, 1425, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5460, 1426, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5460, 1427, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5461, 1427, 0, 0x1, 0x53B, 2 ); - CreateMorphItem( 5460, 1422, 0, 0x1, 0x544, 2 ); - CreateMorphItem( 5460, 1419, 0, 0x1, 0x545, 2 ); - CreateMorphItem( 5460, 1420, 0, 0x1, 0x545, 2 ); - CreateMorphItem( 5460, 1423, 0, 0x1, 0x545, 2 ); - CreateMorphItem( 5460, 1424, 0, 0x1, 0x545, 2 ); - CreateMorphItem( 5461, 1426, 0, 0x1, 0x545, 2 ); - CreateMorphItem( 5460, 1417, 0, 0x1, 0x546, 1 ); - CreateMorphItem( 5460, 1418, 0, 0x1, 0x546, 2 ); - CreateMorphItem( 5460, 1421, 0, 0x1, 0x546, 2 ); - CreateMorphItem( 5461, 1425, 0, 0x1, 0x548, 2 ); - CreateMorphItem( 5459, 1420, 0, 0x1, 0x54A, 2 ); - CreateMorphItem( 5459, 1421, 0, 0x1, 0x54A, 2 ); - CreateMorphItem( 5459, 1423, 0, 0x1, 0x54A, 2 ); - CreateMorphItem( 5459, 1418, 0, 0x1, 0x54B, 2 ); - CreateMorphItem( 5459, 1422, 0, 0x1, 0x54B, 2 ); - CreateMorphItem( 5459, 1417, 0, 0x1, 0x54C, 1 ); - CreateMorphItem( 5459, 1419, 0, 0x1, 0x54C, 2 ); - CreateMorphItem( 5459, 1424, 0, 0x1, 0x54C, 2 ); + CreateMorphItem(5459, 1425, 0, 0x1, 0x53B, 2); + CreateMorphItem(5459, 1426, 0, 0x1, 0x53B, 2); + CreateMorphItem(5459, 1427, 0, 0x1, 0x53B, 2); + CreateMorphItem(5460, 1425, 0, 0x1, 0x53B, 2); + CreateMorphItem(5460, 1426, 0, 0x1, 0x53B, 2); + CreateMorphItem(5460, 1427, 0, 0x1, 0x53B, 2); + CreateMorphItem(5461, 1427, 0, 0x1, 0x53B, 2); + CreateMorphItem(5460, 1422, 0, 0x1, 0x544, 2); + CreateMorphItem(5460, 1419, 0, 0x1, 0x545, 2); + CreateMorphItem(5460, 1420, 0, 0x1, 0x545, 2); + CreateMorphItem(5460, 1423, 0, 0x1, 0x545, 2); + CreateMorphItem(5460, 1424, 0, 0x1, 0x545, 2); + CreateMorphItem(5461, 1426, 0, 0x1, 0x545, 2); + CreateMorphItem(5460, 1417, 0, 0x1, 0x546, 1); + CreateMorphItem(5460, 1418, 0, 0x1, 0x546, 2); + CreateMorphItem(5460, 1421, 0, 0x1, 0x546, 2); + CreateMorphItem(5461, 1425, 0, 0x1, 0x548, 2); + CreateMorphItem(5459, 1420, 0, 0x1, 0x54A, 2); + CreateMorphItem(5459, 1421, 0, 0x1, 0x54A, 2); + CreateMorphItem(5459, 1423, 0, 0x1, 0x54A, 2); + CreateMorphItem(5459, 1418, 0, 0x1, 0x54B, 2); + CreateMorphItem(5459, 1422, 0, 0x1, 0x54B, 2); + CreateMorphItem(5459, 1417, 0, 0x1, 0x54C, 1); + CreateMorphItem(5459, 1419, 0, 0x1, 0x54C, 2); + CreateMorphItem(5459, 1424, 0, 0x1, 0x54C, 2); - CreateMorphItem( 5458, 1426, 0, 0x1, 0x1D1, 2 ); - CreateMorphItem( 5459, 1427, 0, 0x1, 0x1E3, 2 ); - CreateMorphItem( 5458, 1425, 3, 0x1, 0x1E4, 2 ); - CreateMorphItem( 5458, 1427, 6, 0x1, 0x1E5, 2 ); - CreateMorphItem( 5461, 1427, 0, 0x1, 0x1E8, 2 ); - CreateMorphItem( 5460, 1427, 0, 0x1, 0x1E9, 2 ); - CreateMorphItem( 5458, 1425, 0, 0x1, 0x1EA, 2 ); - CreateMorphItem( 5458, 1427, 0, 0x1, 0x1EA, 2 ); - CreateMorphItem( 5458, 1427, 3, 0x1, 0x1EA, 2 ); + CreateMorphItem(5458, 1426, 0, 0x1, 0x1D1, 2); + CreateMorphItem(5459, 1427, 0, 0x1, 0x1E3, 2); + CreateMorphItem(5458, 1425, 3, 0x1, 0x1E4, 2); + CreateMorphItem(5458, 1427, 6, 0x1, 0x1E5, 2); + CreateMorphItem(5461, 1427, 0, 0x1, 0x1E8, 2); + CreateMorphItem(5460, 1427, 0, 0x1, 0x1E9, 2); + CreateMorphItem(5458, 1425, 0, 0x1, 0x1EA, 2); + CreateMorphItem(5458, 1427, 0, 0x1, 0x1EA, 2); + CreateMorphItem(5458, 1427, 3, 0x1, 0x1EA, 2); - // Generate Approach Lights - CreateApproachLight( 5393, 1417, 0, 0x1857, 0x1858, LightType.Circle150 ); - CreateApproachLight( 5393, 1420, 0, 0x1857, 0x1858, LightType.Circle150 ); - CreateApproachLight( 5395, 1421, 0, 0x1857, 0x1858, LightType.Circle150 ); - CreateApproachLight( 5396, 1417, 0, 0x1857, 0x1858, LightType.Circle150 ); - CreateApproachLight( 5397, 1419, 0, 0x1857, 0x1858, LightType.Circle150 ); + // Generate Approach Lights + CreateApproachLight(5393, 1417, 0, 0x1857, 0x1858, LightType.Circle150); + CreateApproachLight(5393, 1420, 0, 0x1857, 0x1858, LightType.Circle150); + CreateApproachLight(5395, 1421, 0, 0x1857, 0x1858, LightType.Circle150); + CreateApproachLight(5396, 1417, 0, 0x1857, 0x1858, LightType.Circle150); + CreateApproachLight(5397, 1419, 0, 0x1857, 0x1858, LightType.Circle150); - CreateApproachLight( 5441, 1393, 5, 0x1F2B, 0x19BB, LightType.Circle225 ); - CreateApproachLight( 5446, 1393, 5, 0x1F2B, 0x19BB, LightType.Circle225 ); + CreateApproachLight(5441, 1393, 5, 0x1F2B, 0x19BB, LightType.Circle225); + CreateApproachLight(5446, 1393, 5, 0x1F2B, 0x19BB, LightType.Circle225); - // Generate Sound Effects - CreateSoundEffect( 5425, 1489, 5, 0x102, 1 ); - CreateSoundEffect( 5425, 1491, 5, 0x102, 1 ); + // Generate Sound Effects + CreateSoundEffect(5425, 1489, 5, 0x102, 1); + CreateSoundEffect(5425, 1491, 5, 0x102, 1); - CreateSoundEffect( 5449, 1499, 10, 0xF5, 1 ); - CreateSoundEffect( 5451, 1499, 10, 0xF5, 1 ); - CreateSoundEffect( 5453, 1499, 10, 0xF5, 1 ); + CreateSoundEffect(5449, 1499, 10, 0xF5, 1); + CreateSoundEffect(5451, 1499, 10, 0xF5, 1); + CreateSoundEffect(5453, 1499, 10, 0xF5, 1); - CreateSoundEffect( 5524, 1367, 0, 0x102, 1 ); + CreateSoundEffect(5524, 1367, 0, 0x102, 1); - CreateSoundEffect( 5450, 1370, 0, 0x220, 2 ); - CreateSoundEffect( 5450, 1372, 0, 0x220, 2 ); + CreateSoundEffect(5450, 1370, 0, 0x220, 2); + CreateSoundEffect(5450, 1372, 0, 0x220, 2); - CreateSoundEffect( 5460, 1416, 0, 0x244, 2 ); + CreateSoundEffect(5460, 1416, 0, 0x244, 2); - CreateSoundEffect( 5483, 1439, 5, 0x14, 3 ); + CreateSoundEffect(5483, 1439, 5, 0x14, 3); - // Generate Big Teleporter - CreateBigTeleporterItem( 5387, 1325, true ); - CreateBigTeleporterItem( 5388, 1326, true ); - CreateBigTeleporterItem( 5388, 1325, false ); - CreateBigTeleporterItem( 5387, 1326, false ); + // Generate Big Teleporter + CreateBigTeleporterItem(5387, 1325, true); + CreateBigTeleporterItem(5388, 1326, true); + CreateBigTeleporterItem(5388, 1325, false); + CreateBigTeleporterItem(5387, 1326, false); - // Generate Central Khaldun entrance - DisappearingRaiseSwitch sw = TryCreateItem( 5459, 1426, 10, new DisappearingRaiseSwitch() ) as DisappearingRaiseSwitch; - RaiseSwitch lv = TryCreateItem( 5403, 1359, 0, new RaiseSwitch() ) as RaiseSwitch; + // Generate Central Khaldun entrance + DisappearingRaiseSwitch sw = + TryCreateItem(5459, 1426, 10, new DisappearingRaiseSwitch()) as DisappearingRaiseSwitch; + RaiseSwitch lv = TryCreateItem(5403, 1359, 0, new RaiseSwitch()) as RaiseSwitch; - RaisableItem stone = TryCreateItem( 5403, 1360, 0, new RaisableItem( 0x788, 10, 0x477, 0x475, TimeSpan.FromMinutes( 1.5 ) ) ) as RaisableItem; - RaisableItem door = TryCreateItem( 5524, 1367, 0, new RaisableItem( 0x1D0, 20, 0x477, 0x475, TimeSpan.FromMinutes( 5.0 ) ) ) as RaisableItem; + RaisableItem stone = + TryCreateItem(5403, 1360, 0, new RaisableItem(0x788, 10, 0x477, 0x475, TimeSpan.FromMinutes(1.5))) as + RaisableItem; + RaisableItem door = + TryCreateItem(5524, 1367, 0, new RaisableItem(0x1D0, 20, 0x477, 0x475, TimeSpan.FromMinutes(5.0))) as + RaisableItem; - sw.RaisableItem = stone; - lv.RaisableItem = door; + sw.RaisableItem = stone; + lv.RaisableItem = door; - e.Mobile.SendMessage($"{m_Count} dynamic Khaldun item{(m_Count == 1 ? "" : "s")} generated."); - } - } -} + e.Mobile.SendMessage($"{m_Count} dynamic Khaldun item{(m_Count == 1 ? "" : "s")} generated."); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/KhaldunPitTeleporter.cs b/Scripts/Engines/Khaldun/KhaldunPitTeleporter.cs index 0ee3f128b..a1a49df10 100644 --- a/Scripts/Engines/Khaldun/KhaldunPitTeleporter.cs +++ b/Scripts/Engines/Khaldun/KhaldunPitTeleporter.cs @@ -1,90 +1,93 @@ +using Server.Mobiles; + namespace Server.Items { - public class KhaldunPitTeleporter : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public bool Active { get; set; } + public class KhaldunPitTeleporter : Item + { + [Constructible] + public KhaldunPitTeleporter() : this(new Point3D(5451, 1374, 0), Map.Felucca) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public Point3D PointDest { get; set; } + [Constructible] + public KhaldunPitTeleporter(Point3D pointDest, Map mapDest) : base(0x053B) + { + Movable = false; + Hue = 1; - [CommandProperty( AccessLevel.GameMaster )] - public Map MapDest { get; set; } + Active = true; + PointDest = pointDest; + MapDest = mapDest; + } - public override int LabelNumber => 1016511; // the floor of the cavern seems to have collapsed here - a faint light is visible at the bottom of the pit + public KhaldunPitTeleporter(Serial serial) : base(serial) + { + } - [Constructible] - public KhaldunPitTeleporter() : this( new Point3D( 5451, 1374, 0 ), Map.Felucca ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Active{ get; set; } - [Constructible] - public KhaldunPitTeleporter( Point3D pointDest, Map mapDest ) : base( 0x053B ) - { - Movable = false; - Hue = 1; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D PointDest{ get; set; } - Active = true; - PointDest = pointDest; - MapDest = mapDest; - } + [CommandProperty(AccessLevel.GameMaster)] + public Map MapDest{ get; set; } - public KhaldunPitTeleporter( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => + 1016511; // the floor of the cavern seems to have collapsed here - a faint light is visible at the bottom of the pit - public override void OnDoubleClick( Mobile m ) - { - if ( !Active ) - return; + public override void OnDoubleClick(Mobile m) + { + if (!Active) + return; - Map map = MapDest; + Map map = MapDest; - if ( map == null || map == Map.Internal ) - map = m.Map; + if (map == null || map == Map.Internal) + map = m.Map; - Point3D p = PointDest; + Point3D p = PointDest; - if ( p == Point3D.Zero ) - p = m.Location; + if (p == Point3D.Zero) + p = m.Location; - if ( m.InRange( this, 3 ) ) - { - Mobiles.BaseCreature.TeleportPets( m, PointDest, MapDest ); + if (m.InRange(this, 3)) + { + BaseCreature.TeleportPets(m, PointDest, MapDest); - m.MoveToWorld( PointDest, MapDest ); - } - else - { - m.SendLocalizedMessage( 1019045 ); // I can't reach that. - } - } + m.MoveToWorld(PointDest, MapDest); + } + else + { + m.SendLocalizedMessage(1019045); // I can't reach that. + } + } - public override void OnDoubleClickDead( Mobile m ) - { - OnDoubleClick( m ); - } + public override void OnDoubleClickDead(Mobile m) + { + OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version + writer.Write(0); // version - writer.Write( Active ); - writer.Write( PointDest ); - writer.Write( MapDest ); - } + writer.Write(Active); + writer.Write(PointDest); + writer.Write(MapDest); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Active = reader.ReadBool(); - PointDest = reader.ReadPoint3D(); - MapDest = reader.ReadMap(); - } - } -} + Active = reader.ReadBool(); + PointDest = reader.ReadPoint3D(); + MapDest = reader.ReadMap(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Mobiles/GrimmochDrummel.cs b/Scripts/Engines/Khaldun/Mobiles/GrimmochDrummel.cs index 5443ee081..6b679d94b 100644 --- a/Scripts/Engines/Khaldun/Mobiles/GrimmochDrummel.cs +++ b/Scripts/Engines/Khaldun/Mobiles/GrimmochDrummel.cs @@ -2,129 +2,129 @@ using Server.Items; namespace Server.Mobiles { - public class GrimmochDrummel : BaseCreature - { - public override bool ClickTitle => false; - public override bool ShowFameTitle => false; - public override bool DeleteCorpseOnDeath => true; - public override string DefaultName => "Grimmoch Drummel"; + public class GrimmochDrummel : BaseCreature + { + [Constructible] + public GrimmochDrummel() : base(AIType.AI_Archer, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Title = "the Cursed"; - [Constructible] - public GrimmochDrummel() : base( AIType.AI_Archer, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Title = "the Cursed"; + Hue = 0x8596; + Body = 0x190; - Hue = 0x8596; - Body = 0x190; + HairItemID = 0x204A; //Krisna - HairItemID = 0x204A; //Krisna + Bow bow = new Bow(); + bow.Movable = false; + AddItem(bow); - Bow bow = new Bow(); - bow.Movable = false; - AddItem( bow ); + AddItem(new Boots(0x8A4)); + AddItem(new BodySash(0x8A4)); - AddItem( new Boots( 0x8A4 ) ); - AddItem( new BodySash( 0x8A4 ) ); + Backpack backpack = new Backpack(); + backpack.Movable = false; + AddItem(backpack); - Backpack backpack = new Backpack(); - backpack.Movable = false; - AddItem( backpack ); + LeatherGloves gloves = new LeatherGloves(); + LeatherChest chest = new LeatherChest(); + gloves.Hue = 0x96F; + chest.Hue = 0x96F; - LeatherGloves gloves = new LeatherGloves(); - LeatherChest chest = new LeatherChest(); - gloves.Hue = 0x96F; - chest.Hue = 0x96F; + AddItem(gloves); + AddItem(chest); - AddItem( gloves ); - AddItem( chest ); + SetStr(111, 120); + SetDex(151, 160); + SetInt(41, 50); - SetStr( 111, 120 ); - SetDex( 151, 160 ); - SetInt( 41, 50 ); + SetHits(180, 207); + SetMana(0); - SetHits( 180, 207 ); - SetMana( 0 ); + SetDamage(13, 16); - SetDamage( 13, 16 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 45, 55); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 25); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 45, 55 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 25 ); + SetSkill(SkillName.Archery, 90.1, 110.0); + SetSkill(SkillName.Swords, 60.1, 70.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 60.1, 70.0); + SetSkill(SkillName.Anatomy, 90.1, 100.0); - SetSkill( SkillName.Archery, 90.1, 110.0 ); - SetSkill( SkillName.Swords, 60.1, 70.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 60.1, 70.0 ); - SetSkill( SkillName.Anatomy, 90.1, 100.0 ); + Fame = 5000; + Karma = -1000; - Fame = 5000; - Karma = -1000; + PackItem(new Arrow(40)); - PackItem( new Arrow( 40 ) ); + if (3 > Utility.Random(100)) + PackItem(new FireHorn()); - if ( 3 > Utility.Random( 100 ) ) - PackItem( new FireHorn() ); + if (1 > Utility.Random(3)) + PackItem(Loot.RandomGrimmochJournal()); + } - if ( 1 > Utility.Random( 3 ) ) - PackItem( Loot.RandomGrimmochJournal() ); - } + public GrimmochDrummel(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x178; - } + public override bool ClickTitle => false; + public override bool ShowFameTitle => false; + public override bool DeleteCorpseOnDeath => true; + public override string DefaultName => "Grimmoch Drummel"; - public override int GetAngerSound() - { - return 0x1AC; - } + public override bool AlwaysMurderer => true; - public override int GetDeathSound() - { - return 0x27E; - } + public override int GetIdleSound() + { + return 0x178; + } - public override int GetHurtSound() - { - return 0x177; - } + public override int GetAngerSound() + { + return 0x1AC; + } - public override bool OnBeforeDeath() - { - Gold gold = new Gold( Utility.RandomMinMax( 190, 230 ) ); - gold.MoveToWorld( Location, Map ); + public override int GetDeathSound() + { + return 0x27E; + } - Container pack = Backpack; - if ( pack != null ) - { - pack.Movable = true; - pack.MoveToWorld( Location, Map ); - } + public override int GetHurtSound() + { + return 0x177; + } - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + public override bool OnBeforeDeath() + { + Gold gold = new Gold(Utility.RandomMinMax(190, 230)); + gold.MoveToWorld(Location, Map); - public override bool AlwaysMurderer => true; + Container pack = Backpack; + if (pack != null) + { + pack.Movable = true; + pack.MoveToWorld(Location, Map); + } - public GrimmochDrummel( Serial serial ) : base( serial ) - { - } + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Mobiles/LysanderGathenwale.cs b/Scripts/Engines/Khaldun/Mobiles/LysanderGathenwale.cs index b328642d2..9f087c484 100644 --- a/Scripts/Engines/Khaldun/Mobiles/LysanderGathenwale.cs +++ b/Scripts/Engines/Khaldun/Mobiles/LysanderGathenwale.cs @@ -2,129 +2,129 @@ using Server.Items; namespace Server.Mobiles { - public class LysanderGathenwale : BaseCreature - { - public override bool ClickTitle => false; - public override bool ShowFameTitle => false; - public override bool DeleteCorpseOnDeath => true; - public override string DefaultName => "Lysander Gatherwale"; + public class LysanderGathenwale : BaseCreature + { + [Constructible] + public LysanderGathenwale() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Title = "the Cursed"; - [Constructible] - public LysanderGathenwale() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Title = "the Cursed"; + Hue = 0x8838; + Body = 0x190; - Hue = 0x8838; - Body = 0x190; + AddItem(new Boots(0x599)); + AddItem(new Cloak(0x96F)); - AddItem( new Boots( 0x599 ) ); - AddItem( new Cloak( 0x96F ) ); + Spellbook spellbook = new Spellbook(); + RingmailGloves gloves = new RingmailGloves(); + StuddedChest chest = new StuddedChest(); + PlateArms arms = new PlateArms(); - Spellbook spellbook = new Spellbook(); - RingmailGloves gloves = new RingmailGloves(); - StuddedChest chest = new StuddedChest(); - PlateArms arms = new PlateArms(); + spellbook.Hue = 0x599; + gloves.Hue = 0x599; + chest.Hue = 0x96F; + arms.Hue = 0x599; - spellbook.Hue = 0x599; - gloves.Hue = 0x599; - chest.Hue = 0x96F; - arms.Hue = 0x599; + AddItem(spellbook); + AddItem(gloves); + AddItem(chest); + AddItem(arms); - AddItem( spellbook ); - AddItem( gloves ); - AddItem( chest ); - AddItem( arms ); + SetStr(111, 120); + SetDex(71, 80); + SetInt(121, 130); - SetStr( 111, 120 ); - SetDex( 71, 80 ); - SetInt( 121, 130 ); + SetHits(180, 207); + SetMana(227, 265); - SetHits( 180, 207 ); - SetMana( 227, 265 ); + SetDamage(5, 13); - SetDamage( 5, 13 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.Wrestling, 80.1, 90.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 80.1, 90.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.EvalInt, 95.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 80.1, 90.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.EvalInt, 95.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); + Fame = 5000; + Karma = -10000; - Fame = 5000; - Karma = -10000; + Item reags = Loot.RandomReagent(); + reags.Amount = 30; + PackItem(reags); + } - Item reags = Loot.RandomReagent(); - reags.Amount = 30; - PackItem( reags ); - } + public LysanderGathenwale(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x1CE; - } + public override bool ClickTitle => false; + public override bool ShowFameTitle => false; + public override bool DeleteCorpseOnDeath => true; + public override string DefaultName => "Lysander Gatherwale"; - public override int GetAngerSound() - { - return 0x1AC; - } + public override bool AlwaysMurderer => true; - public override int GetDeathSound() - { - return 0x182; - } + public override int GetIdleSound() + { + return 0x1CE; + } - public override int GetHurtSound() - { - return 0x28D; - } + public override int GetAngerSound() + { + return 0x1AC; + } - public override void GenerateLoot() - { - AddLoot( LootPack.MedScrolls, 2 ); - } + public override int GetDeathSound() + { + return 0x182; + } - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + public override int GetHurtSound() + { + return 0x28D; + } - Backpack?.Destroy(); + public override void GenerateLoot() + { + AddLoot(LootPack.MedScrolls, 2); + } - if ( Utility.Random( 3 ) == 0 ) - { - BaseBook notebook = Loot.RandomLysanderNotebook(); - notebook.MoveToWorld( Location, Map ); - } + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + Backpack?.Destroy(); - public override bool AlwaysMurderer => true; + if (Utility.Random(3) == 0) + { + BaseBook notebook = Loot.RandomLysanderNotebook(); + notebook.MoveToWorld(Location, Map); + } - public LysanderGathenwale( Serial serial ) : base( serial ) - { - } + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Mobiles/MorgBergen.cs b/Scripts/Engines/Khaldun/Mobiles/MorgBergen.cs index 241cda216..a93e47d68 100644 --- a/Scripts/Engines/Khaldun/Mobiles/MorgBergen.cs +++ b/Scripts/Engines/Khaldun/Mobiles/MorgBergen.cs @@ -2,108 +2,109 @@ using Server.Items; namespace Server.Mobiles { - public class MorgBergen : BaseCreature - { - public override bool ShowFameTitle => false; - public override bool DeleteCorpseOnDeath => true; - public override string DefaultName => "Morg Bergen"; + public class MorgBergen : BaseCreature + { + [Constructible] + public MorgBergen() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Title = "the Cursed"; - [Constructible] - public MorgBergen() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Title = "the Cursed"; + Hue = 0x8596; + Body = 0x190; - Hue = 0x8596; - Body = 0x190; + AddItem(new ShortPants(0x59C)); - AddItem( new ShortPants( 0x59C ) ); + Bardiche bardiche = new Bardiche(); + LeatherGloves gloves = new LeatherGloves(); + LeatherArms arms = new LeatherArms(); - Bardiche bardiche = new Bardiche(); - LeatherGloves gloves = new LeatherGloves(); - LeatherArms arms = new LeatherArms(); + bardiche.Hue = 0x96F; + bardiche.Movable = false; + gloves.Hue = 0x96F; + arms.Hue = 0x96F; - bardiche.Hue = 0x96F; bardiche.Movable = false; - gloves.Hue = 0x96F; - arms.Hue = 0x96F; + AddItem(bardiche); + AddItem(gloves); + AddItem(arms); - AddItem( bardiche ); - AddItem( gloves ); - AddItem( arms ); + SetStr(111, 120); + SetDex(111, 120); + SetInt(51, 60); - SetStr( 111, 120 ); - SetDex( 111, 120 ); - SetInt( 51, 60 ); + SetHits(180, 207); + SetMana(0); - SetHits( 180, 207 ); - SetMana( 0 ); + SetDamage(9, 17); - SetDamage( 9, 17 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.Swords, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 80.1, 90.0); + SetSkill(SkillName.Anatomy, 90.1, 100.0); - SetSkill( SkillName.Swords, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 80.1, 90.0 ); - SetSkill( SkillName.Anatomy, 90.1, 100.0 ); + Fame = 5000; + Karma = -1000; + } - Fame = 5000; - Karma = -1000; - } + public MorgBergen(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x1CE; - } + public override bool ShowFameTitle => false; + public override bool DeleteCorpseOnDeath => true; + public override string DefaultName => "Morg Bergen"; - public override int GetAngerSound() - { - return 0x263; - } + public override bool AlwaysMurderer => true; - public override int GetDeathSound() - { - return 0x1D1; - } + public override int GetIdleSound() + { + return 0x1CE; + } - public override int GetHurtSound() - { - return 0x25E; - } + public override int GetAngerSound() + { + return 0x263; + } - public override bool OnBeforeDeath() - { - Gold gold = new Gold( Utility.RandomMinMax( 190, 230 ) ); - gold.MoveToWorld( Location, Map ); + public override int GetDeathSound() + { + return 0x1D1; + } - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + public override int GetHurtSound() + { + return 0x25E; + } - public override bool AlwaysMurderer => true; + public override bool OnBeforeDeath() + { + Gold gold = new Gold(Utility.RandomMinMax(190, 230)); + gold.MoveToWorld(Location, Map); - public MorgBergen( Serial serial ) : base( serial ) - { - } + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/Mobiles/TavaraSewel.cs b/Scripts/Engines/Khaldun/Mobiles/TavaraSewel.cs index a96573df8..f2bf55fd1 100644 --- a/Scripts/Engines/Khaldun/Mobiles/TavaraSewel.cs +++ b/Scripts/Engines/Khaldun/Mobiles/TavaraSewel.cs @@ -2,117 +2,119 @@ using Server.Items; namespace Server.Mobiles { - public class TavaraSewel : BaseCreature - { - public override bool ShowFameTitle => false; - public override bool DeleteCorpseOnDeath => true; - public override string DefaultName => "Tavara Sewel"; + public class TavaraSewel : BaseCreature + { + [Constructible] + public TavaraSewel() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Title = "the Cursed"; - [Constructible] - public TavaraSewel () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Title = "the Cursed"; + Hue = 0x8838; + Female = true; + Body = 0x191; - Hue = 0x8838; - Female = true; - Body = 0x191; + AddItem(new Kilt(0x59C)); + AddItem(new Sandals(0x599)); - AddItem( new Kilt( 0x59C ) ); - AddItem( new Sandals( 0x599 ) ); + Kryss kryss = new Kryss(); + Buckler buckler = new Buckler(); + RingmailGloves gloves = new RingmailGloves(); + FemalePlateChest chest = new FemalePlateChest(); - Kryss kryss = new Kryss(); - Buckler buckler = new Buckler(); - RingmailGloves gloves = new RingmailGloves(); - FemalePlateChest chest = new FemalePlateChest(); + kryss.Hue = 0x96F; + kryss.Movable = false; + buckler.Hue = 0x96F; + buckler.Movable = false; + gloves.Hue = 0x599; + chest.Hue = 0x96F; - kryss.Hue = 0x96F; kryss.Movable = false; - buckler.Hue = 0x96F; buckler.Movable = false; - gloves.Hue = 0x599; - chest.Hue = 0x96F; + AddItem(kryss); + AddItem(buckler); + AddItem(gloves); + AddItem(chest); - AddItem( kryss ); - AddItem( buckler ); - AddItem( gloves ); - AddItem( chest ); + SetStr(111, 120); + SetDex(111, 120); + SetInt(111, 120); - SetStr( 111, 120 ); - SetDex( 111, 120 ); - SetInt( 111, 120 ); + SetHits(180, 207); + SetStam(126, 150); + SetMana(0); - SetHits( 180, 207 ); - SetStam( 126, 150 ); - SetMana( 0 ); + SetDamage(13, 16); - SetDamage( 13, 16 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.Fencing, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 80.1, 90.0); + SetSkill(SkillName.Anatomy, 90.1, 100.0); - SetSkill( SkillName.Fencing, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 80.1, 90.0 ); - SetSkill( SkillName.Anatomy, 90.1, 100.0 ); + Fame = 5000; + Karma = -1000; + } - Fame = 5000; - Karma = -1000; - } + public TavaraSewel(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x27F; - } + public override bool ShowFameTitle => false; + public override bool DeleteCorpseOnDeath => true; + public override string DefaultName => "Tavara Sewel"; - public override int GetAngerSound() - { - return 0x258; - } + public override bool AlwaysMurderer => true; - public override int GetDeathSound() - { - return 0x25B; - } + public override int GetIdleSound() + { + return 0x27F; + } - public override int GetHurtSound() - { - return 0x257; - } + public override int GetAngerSound() + { + return 0x258; + } - public override bool OnBeforeDeath() - { - Gold gold = new Gold( Utility.RandomMinMax( 190, 230 ) ); - gold.MoveToWorld( Location, Map ); + public override int GetDeathSound() + { + return 0x25B; + } - if ( Utility.Random( 3 ) == 0 ) - { - BaseBook journal = Loot.RandomTavarasJournal(); - journal.MoveToWorld( Location, Map ); - } + public override int GetHurtSound() + { + return 0x257; + } - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + public override bool OnBeforeDeath() + { + Gold gold = new Gold(Utility.RandomMinMax(190, 230)); + gold.MoveToWorld(Location, Map); - public override bool AlwaysMurderer => true; + if (Utility.Random(3) == 0) + { + BaseBook journal = Loot.RandomTavarasJournal(); + journal.MoveToWorld(Location, Map); + } - public TavaraSewel( Serial serial ) : base( serial ) - { - } + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/PuzzleChest.cs b/Scripts/Engines/Khaldun/PuzzleChest.cs index 360dba56d..4cfac16d7 100644 --- a/Scripts/Engines/Khaldun/PuzzleChest.cs +++ b/Scripts/Engines/Khaldun/PuzzleChest.cs @@ -5,775 +5,806 @@ using Server.Network; namespace Server.Items { - public enum PuzzleChestCylinder - { - None = 0xE73, - LightBlue = 0x186F, - Blue = 0x186A, - Green = 0x186B, - Orange = 0x186C, - Purple = 0x186D, - Red = 0x186E, - DarkBlue = 0x1869, - Yellow = 0x1870 - } - - public class PuzzleChestSolution - { - public const int Length = 5; - - public PuzzleChestCylinder[] Cylinders { get; } = new PuzzleChestCylinder[Length]; - - public PuzzleChestCylinder First{ get => Cylinders[0]; - set => Cylinders[0] = value; - } - public PuzzleChestCylinder Second{ get => Cylinders[1]; - set => Cylinders[1] = value; - } - public PuzzleChestCylinder Third{ get => Cylinders[2]; - set => Cylinders[2] = value; - } - public PuzzleChestCylinder Fourth{ get => Cylinders[3]; - set => Cylinders[3] = value; - } - public PuzzleChestCylinder Fifth{ get => Cylinders[4]; - set => Cylinders[4] = value; - } - - public static PuzzleChestCylinder RandomCylinder() - { - switch ( Utility.Random( 8 ) ) - { - case 0: return PuzzleChestCylinder.LightBlue; - case 1: return PuzzleChestCylinder.Blue; - case 2: return PuzzleChestCylinder.Green; - case 3: return PuzzleChestCylinder.Orange; - case 4: return PuzzleChestCylinder.Purple; - case 5: return PuzzleChestCylinder.Red; - case 6: return PuzzleChestCylinder.DarkBlue; - default: return PuzzleChestCylinder.Yellow; - } - } - - public PuzzleChestSolution() - { - for ( int i = 0; i < Cylinders.Length; i++ ) { - Cylinders[i] = RandomCylinder(); - } - } - - public PuzzleChestSolution( PuzzleChestCylinder first, PuzzleChestCylinder second, PuzzleChestCylinder third, PuzzleChestCylinder fourth, PuzzleChestCylinder fifth ) - { - First = first; - Second = second; - Third = third; - Fourth = fourth; - Fifth = fifth; - } - - public PuzzleChestSolution( PuzzleChestSolution solution ) - { - for ( int i = 0; i < Cylinders.Length; i++ ) { - Cylinders[i] = solution.Cylinders[i]; - } - } - - public bool Matches( PuzzleChestSolution solution, out int cylinders, out int colors ) - { - cylinders = 0; - colors = 0; - - bool[] matchesSrc = new bool[solution.Cylinders.Length]; - bool[] matchesDst = new bool[solution.Cylinders.Length]; - - for ( int i = 0; i < Cylinders.Length; i++ ) - { - if ( Cylinders[i] == solution.Cylinders[i] ) - { - cylinders++; - - matchesSrc[i] = true; - matchesDst[i] = true; - } - } - - for ( int i = 0; i < Cylinders.Length; i++ ) - { - if ( !matchesSrc[i] ) - { - for ( int j = 0; j < solution.Cylinders.Length; j++ ) - { - if ( Cylinders[i] == solution.Cylinders[j] && !matchesDst[j] ) - { - colors++; - - matchesDst[j] = true; - } - } - } - } - - return cylinders == Cylinders.Length; - } - - public virtual void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) Cylinders.Length ); - for ( int i = 0; i < Cylinders.Length; i++ ) - { - writer.Write( (int) Cylinders[i] ); - } - } - - public PuzzleChestSolution( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - int length = reader.ReadEncodedInt(); - for ( int i = 0; ; i++ ) - { - if ( i < length ) - { - PuzzleChestCylinder cylinder = (PuzzleChestCylinder) reader.ReadInt(); - - if ( i < Cylinders.Length ) - Cylinders[i] = cylinder; - } - else if ( i < Cylinders.Length ) - { - Cylinders[i] = RandomCylinder(); - } - else - { - break; - } - } - } - } - - public class PuzzleChestSolutionAndTime : PuzzleChestSolution - { - public DateTime When { get; } - - public PuzzleChestSolutionAndTime( DateTime when, PuzzleChestSolution solution ) : base( solution ) - { - When = when; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteDeltaTime( When ); - } - - public PuzzleChestSolutionAndTime( GenericReader reader ) : base( reader ) - { - int version = reader.ReadEncodedInt(); - - When = reader.ReadDeltaTime(); - } - } - - public abstract class PuzzleChest : BaseTreasureChest - { - public const int HintsCount = 3; - public readonly TimeSpan CleanupTime = TimeSpan.FromHours( 1.0 ); - - private PuzzleChestSolution m_Solution; - private Dictionary m_Guesses = new Dictionary(); - - public PuzzleChestSolution Solution - { - get => m_Solution; - set - { - m_Solution = value; - InitHints(); - } - } - - public PuzzleChestCylinder[] Hints { get; private set; } = new PuzzleChestCylinder[HintsCount]; - - public PuzzleChestCylinder FirstHint{ get => Hints[0]; - set => Hints[0] = value; - } - public PuzzleChestCylinder SecondHint{ get => Hints[1]; - set => Hints[1] = value; - } - public PuzzleChestCylinder ThirdHint{ get => Hints[2]; - set => Hints[2] = value; - } - - public override string DefaultName => null; - - public PuzzleChest( int itemID ) : base( itemID ) - { - } - - private void InitHints() - { - List list = new List( Solution.Cylinders.Length - 1 ); - for ( int i = 1; i < Solution.Cylinders.Length; i++ ) - list.Add( Solution.Cylinders[i] ); - - Hints = new PuzzleChestCylinder[HintsCount]; - - for ( int i = 0; i < Hints.Length; i++ ) { - int pos = Utility.Random( list.Count ); - Hints[i] = list[pos]; - list.RemoveAt( pos ); - } - } - - protected override void SetLockLevel() - { - LockLevel = 0; // Can't be unlocked - } - - public override bool CheckLocked( Mobile from ) - { - if ( Locked ) - { - PuzzleChestSolution solution = GetLastGuess( from ); - if ( solution != null ) - solution = new PuzzleChestSolution( solution ); - else - solution = new PuzzleChestSolution( PuzzleChestCylinder.None, PuzzleChestCylinder.None, PuzzleChestCylinder.None, PuzzleChestCylinder.None, PuzzleChestCylinder.None ); - - from.CloseGump( typeof( PuzzleGump ) ); - from.CloseGump( typeof( StatusGump ) ); - from.SendGump( new PuzzleGump( from, this, solution, 0 ) ); - - return true; - } - - return false; - } - - public PuzzleChestSolutionAndTime GetLastGuess( Mobile m ) - { - m_Guesses.TryGetValue( m, out PuzzleChestSolutionAndTime pcst ); - return pcst; - } - - public void SubmitSolution( Mobile m, PuzzleChestSolution solution ) - { - int correctCylinders, correctColors; - - if ( solution.Matches( Solution, out correctCylinders, out correctColors ) ) - { - LockPick( m ); - - DisplayTo( m ); - } - else - { - m_Guesses[m] = new PuzzleChestSolutionAndTime( DateTime.UtcNow, solution ); - - m.SendGump( new StatusGump( correctCylinders, correctColors ) ); - - DoDamage( m ); - } - } - - public void DoDamage( Mobile to ) - { - switch ( Utility.Random( 4 ) ) - { - case 0: - { - Effects.SendLocationEffect( to, to.Map, 0x113A, 20, 10 ); - to.PlaySound( 0x231 ); - to.LocalOverheadMessage( MessageType.Regular, 0x44, 1010523 ); // A toxic vapor envelops thee. - - to.ApplyPoison( to, Poison.Regular ); - - break; - } - case 1: - { - Effects.SendLocationEffect( to, to.Map, 0x3709, 30 ); - to.PlaySound( 0x54 ); - to.LocalOverheadMessage( MessageType.Regular, 0xEE, 1010524 ); // Searing heat scorches thy skin. - - AOS.Damage( to, to, Utility.RandomMinMax( 10, 40 ), 0, 100, 0, 0, 0 ); - - break; - } - case 2: - { - to.PlaySound( 0x223 ); - to.LocalOverheadMessage( MessageType.Regular, 0x62, 1010525 ); // Pain lances through thee from a sharp metal blade. - - AOS.Damage( to, to, Utility.RandomMinMax( 10, 40 ), 100, 0, 0, 0, 0 ); - - break; - } - default: - { - to.BoltEffect( 0 ); - to.LocalOverheadMessage( MessageType.Regular, 0xDA, 1010526 ); // Lightning arcs through thy body. - - AOS.Damage( to, to, Utility.RandomMinMax( 10, 40 ), 0, 0, 0, 0, 100 ); - - break; - } - } - } - - private class PuzzleGump : Gump - { - private Mobile m_From; - private PuzzleChest m_Chest; - private PuzzleChestSolution m_Solution; - - public PuzzleGump( Mobile from, PuzzleChest chest, PuzzleChestSolution solution, int check ) : base( 50, 50 ) - { - m_From = from; - m_Chest = chest; - m_Solution = solution; - - Dragable = false; - - AddBackground( 25, 0, 500, 410, 0x53 ); - - AddImage( 62, 20, 0x67 ); - - AddHtmlLocalized( 80, 36, 110, 70, 1018309, true, false ); // A Puzzle Lock - - /* Correctly choose the sequence of cylinders needed to open the latch. Each cylinder - * may potentially be used more than once. Beware! A false attempt could be deadly! - */ - AddHtmlLocalized( 214, 26, 270, 90, 1018310, true, true ); - - AddLeftCylinderButton( 62, 130, PuzzleChestCylinder.LightBlue, 10 ); - AddLeftCylinderButton( 62, 180, PuzzleChestCylinder.Blue, 11 ); - AddLeftCylinderButton( 62, 230, PuzzleChestCylinder.Green, 12 ); - AddLeftCylinderButton( 62, 280, PuzzleChestCylinder.Orange, 13 ); - - AddRightCylinderButton( 451, 130, PuzzleChestCylinder.Purple, 14 ); - AddRightCylinderButton( 451, 180, PuzzleChestCylinder.Red, 15 ); - AddRightCylinderButton( 451, 230, PuzzleChestCylinder.DarkBlue, 16 ); - AddRightCylinderButton( 451, 280, PuzzleChestCylinder.Yellow, 17 ); - - double lockpicking = from.Skills.Lockpicking.Base; - if ( lockpicking >= 60.0 ) - { - AddHtmlLocalized( 160, 125, 230, 24, 1018308, false, false ); // Lockpicking hint: - - AddBackground( 159, 150, 230, 95, 0x13EC ); - - if ( lockpicking >= 80.0 ) - { - AddHtmlLocalized( 165, 157, 200, 40, 1018312, false, false ); // In the first slot: - AddCylinder( 350, 165, chest.Solution.First ); - - AddHtmlLocalized( 165, 197, 200, 40, 1018313, false, false ); // Used in unknown slot: - AddCylinder( 350, 200, chest.FirstHint ); - - if ( lockpicking >= 90.0 ) - AddCylinder( 350, 212, chest.SecondHint ); - - if ( lockpicking >= 100.0 ) - AddCylinder( 350, 224, chest.ThirdHint ); - } - else - { - AddHtmlLocalized( 165, 157, 200, 40, 1018313, false, false ); // Used in unknown slot: - AddCylinder( 350, 160, chest.FirstHint ); - - if ( lockpicking >= 70.0 ) - AddCylinder( 350, 172, chest.SecondHint ); - } - } - - PuzzleChestSolution lastGuess = chest.GetLastGuess( from ); - if ( lastGuess != null ) - { - AddHtmlLocalized( 127, 249, 170, 20, 1018311, false, false ); // Thy previous guess: - - AddBackground( 290, 247, 115, 25, 0x13EC ); - - AddCylinder( 281, 254, lastGuess.First ); - AddCylinder( 303, 254, lastGuess.Second ); - AddCylinder( 325, 254, lastGuess.Third ); - AddCylinder( 347, 254, lastGuess.Fourth ); - AddCylinder( 369, 254, lastGuess.Fifth ); - } - - AddPedestal( 140, 270, solution.First, 0, check == 0 ); - AddPedestal( 195, 270, solution.Second, 1, check == 1 ); - AddPedestal( 250, 270, solution.Third, 2, check == 2 ); - AddPedestal( 305, 270, solution.Fourth, 3, check == 3 ); - AddPedestal( 360, 270, solution.Fifth, 4, check == 4 ); - - AddButton( 258, 370, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - } - - private void AddLeftCylinderButton( int x, int y, PuzzleChestCylinder cylinder, int buttonID ) - { - AddBackground( x, y, 30, 30, 0x13EC ); - AddCylinder( x - 7, y + 10, cylinder ); - AddButton( x + 38, y + 9, 0x13A8, 0x4B9, buttonID, GumpButtonType.Reply, 0 ); - } - - private void AddRightCylinderButton( int x, int y, PuzzleChestCylinder cylinder, int buttonID ) - { - AddBackground( x, y, 30, 30, 0x13EC ); - AddCylinder( x - 7, y + 10, cylinder ); - AddButton( x - 26, y + 9, 0x13A8, 0x4B9, buttonID, GumpButtonType.Reply, 0 ); - } - - private void AddPedestal( int x, int y, PuzzleChestCylinder cylinder, int switchID, bool initialState ) - { - AddItem( x, y, 0xB10 ); - AddItem( x - 23, y + 12, 0xB12 ); - AddItem( x + 23, y + 12, 0xB13 ); - AddItem( x, y + 23, 0xB11 ); - - if ( cylinder != PuzzleChestCylinder.None ) - { - AddItem( x, y + 2, 0x51A ); - AddCylinder( x - 1, y + 19, cylinder ); - } - else - { - AddItem( x, y + 2, 0x521 ); - } - - AddRadio( x + 7, y + 65, 0x867, 0x86A, initialState, switchID ); - } - - private void AddCylinder( int x, int y, PuzzleChestCylinder cylinder ) - { - if ( cylinder != PuzzleChestCylinder.None ) - AddItem( x, y, (int)cylinder ); - else - AddItem( x + 9, y, (int)cylinder ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Chest.Deleted || info.ButtonID == 0 || !m_From.CheckAlive() ) - return; - - if ( m_From.AccessLevel == AccessLevel.Player && ( m_From.Map != m_Chest.Map || !m_From.InRange( m_Chest.GetWorldLocation(), 2 ) ) ) - { - m_From.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500446 ); // That is too far away. - return; - } - - if ( info.ButtonID == 1 ) - { - m_Chest.SubmitSolution( m_From, m_Solution ); - } - else - { - if ( info.Switches.Length == 0 ) - return; - - int pedestal = info.Switches[0]; - if ( pedestal < 0 || pedestal >= m_Solution.Cylinders.Length ) - return; - - PuzzleChestCylinder cylinder; - switch ( info.ButtonID ) - { - case 10: cylinder = PuzzleChestCylinder.LightBlue; break; - case 11: cylinder = PuzzleChestCylinder.Blue; break; - case 12: cylinder = PuzzleChestCylinder.Green; break; - case 13: cylinder = PuzzleChestCylinder.Orange; break; - case 14: cylinder = PuzzleChestCylinder.Purple; break; - case 15: cylinder = PuzzleChestCylinder.Red; break; - case 16: cylinder = PuzzleChestCylinder.DarkBlue; break; - case 17: cylinder = PuzzleChestCylinder.Yellow; break; - default: return; - } - - m_Solution.Cylinders[pedestal] = cylinder; - - m_From.SendGump( new PuzzleGump( m_From, m_Chest, m_Solution, pedestal ) ); - } - } - } - - private class StatusGump : Gump - { - public StatusGump( int correctCylinders, int correctColors ) : base( 50, 50 ) - { - AddBackground( 15, 250, 305, 163, 0x53 ); - AddBackground( 28, 265, 280, 133, 0xBB8 ); - - AddHtmlLocalized( 35, 271, 270, 24, 1018314, false, false ); // Thou hast failed to solve the puzzle! - - AddHtmlLocalized( 35, 297, 250, 24, 1018315, false, false ); // Correctly placed colors: - AddLabel( 285, 297, 0x44, correctCylinders.ToString() ); - - AddHtmlLocalized( 35, 323, 250, 24, 1018316, false, false ); // Used colors in wrong slots: - AddLabel( 285, 323, 0x44, correctColors.ToString() ); - - AddButton( 152, 369, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - } - } - - public override void LockPick( Mobile from ) - { - base.LockPick( from ); - - m_Guesses.Clear(); - } - - private static void GetRandomAOSStats( out int attributeCount, out int min, out int max ) - { - int rnd = Utility.Random( 15 ); - - if ( rnd < 1 ) - { - attributeCount = Utility.RandomMinMax( 2, 6 ); - min = 20; max = 70; - } - else if ( rnd < 3 ) - { - attributeCount = Utility.RandomMinMax( 2, 4 ); - min = 20; max = 50; - } - else if ( rnd < 6 ) - { - attributeCount = Utility.RandomMinMax( 2, 3 ); - min = 20; max = 40; - } - else if ( rnd < 10 ) - { - attributeCount = Utility.RandomMinMax( 1, 2 ); - min = 10; max = 30; - } - else - { - attributeCount = 1; - min = 10; max = 20; - } - } - - protected override void GenerateTreasure() - { - DropItem( new Gold( 600, 900 ) ); - - List gems = new List(); - for ( int i = 0; i < 9; i++ ) - { - Item gem = Loot.RandomGem(); - Type gemType = gem.GetType(); - - foreach ( Item listGem in gems ) { - if ( listGem.GetType() == gemType ) { - listGem.Amount++; - gem.Delete(); - break; - } - } - - if ( !gem.Deleted ) - gems.Add( gem ); - } - - foreach ( Item gem in gems ) - DropItem( gem ); - - if ( 0.2 > Utility.RandomDouble() ) - DropItem( new BagOfReagents( 50 ) ); - - for ( int i = 0; i < 2; i++ ) - { - Item item; - - if ( Core.AOS ) - item = Loot.RandomArmorOrShieldOrWeaponOrJewelry(); - else - item = Loot.RandomArmorOrShieldOrWeapon(); - - if ( item is BaseWeapon weapon ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out int attributeCount, out int min, out int max ); - - BaseRunicTool.ApplyAttributesTo( weapon, attributeCount, min, max ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)Utility.Random( 6 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random( 6 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random( 6 ); - } - - DropItem( weapon ); - } - else if ( item is BaseArmor armor ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out int attributeCount, out int min, out int max ); - - BaseRunicTool.ApplyAttributesTo( armor, attributeCount, min, max ); - } - else - { - armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random( 6 ); - armor.Durability = (ArmorDurabilityLevel)Utility.Random( 6 ); - } - - DropItem( armor ); - } - else if ( item is BaseHat hat ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out int attributeCount, out int min, out int max ); - - BaseRunicTool.ApplyAttributesTo( hat, attributeCount, min, max ); - } - - DropItem( hat ); - } - else if ( item is BaseJewel jewel ) - { - GetRandomAOSStats( out int attributeCount, out int min, out int max ); - - BaseRunicTool.ApplyAttributesTo( jewel, attributeCount, min, max ); - - DropItem( jewel ); - } - } - - Solution = new PuzzleChestSolution(); - } - - public void CleanupGuesses() - { - List toDelete = new List(); - - foreach ( KeyValuePair kvp in m_Guesses ) { - if ( DateTime.UtcNow - kvp.Value.When > CleanupTime ) - toDelete.Add( kvp.Key ); - } - - foreach ( Mobile m in toDelete ) - m_Guesses.Remove( m ); - } - - public PuzzleChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - CleanupGuesses(); - - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - - m_Solution.Serialize( writer ); - - writer.WriteEncodedInt( (int) Hints.Length ); - for ( int i = 0; i < Hints.Length; i++ ) - { - writer.Write( (int) Hints[i] ); - } - - writer.WriteEncodedInt( (int) m_Guesses.Count ); - foreach ( KeyValuePair kvp in m_Guesses ) { - writer.Write( kvp.Key ); - kvp.Value.Serialize( writer ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Solution = new PuzzleChestSolution( reader ); - - int length = reader.ReadEncodedInt(); - for ( int i = 0; i < length; i++ ) - { - PuzzleChestCylinder cylinder = (PuzzleChestCylinder) reader.ReadInt(); - - if ( length == Hints.Length ) - Hints[i] = cylinder; - } - if ( length != Hints.Length ) - InitHints(); - - int guesses = reader.ReadEncodedInt(); - for ( int i = 0; i < guesses; i++ ) - { - Mobile m = reader.ReadMobile(); - PuzzleChestSolutionAndTime sol = new PuzzleChestSolutionAndTime( reader ); - - m_Guesses[m] = sol; - } - } - } - - [FlippableAttribute( 0xE41, 0xE40 )] - public class MetalGoldenPuzzleChest : PuzzleChest - { - [Constructible] - public MetalGoldenPuzzleChest() : base( 0xE41 ) - { - } - - public MetalGoldenPuzzleChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - [FlippableAttribute( 0xE80, 0x9A8 )] - public class StrongBoxPuzzle : PuzzleChest - { - [Constructible] - public StrongBoxPuzzle() : base( 0xE80 ) - { - } - - public StrongBoxPuzzle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + public enum PuzzleChestCylinder + { + None = 0xE73, + LightBlue = 0x186F, + Blue = 0x186A, + Green = 0x186B, + Orange = 0x186C, + Purple = 0x186D, + Red = 0x186E, + DarkBlue = 0x1869, + Yellow = 0x1870 + } + + public class PuzzleChestSolution + { + public const int Length = 5; + + public PuzzleChestSolution() + { + for (int i = 0; i < Cylinders.Length; i++) Cylinders[i] = RandomCylinder(); + } + + public PuzzleChestSolution(PuzzleChestCylinder first, PuzzleChestCylinder second, PuzzleChestCylinder third, + PuzzleChestCylinder fourth, PuzzleChestCylinder fifth) + { + First = first; + Second = second; + Third = third; + Fourth = fourth; + Fifth = fifth; + } + + public PuzzleChestSolution(PuzzleChestSolution solution) + { + for (int i = 0; i < Cylinders.Length; i++) Cylinders[i] = solution.Cylinders[i]; + } + + public PuzzleChestSolution(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + int length = reader.ReadEncodedInt(); + for (int i = 0;; i++) + if (i < length) + { + PuzzleChestCylinder cylinder = (PuzzleChestCylinder)reader.ReadInt(); + + if (i < Cylinders.Length) + Cylinders[i] = cylinder; + } + else if (i < Cylinders.Length) + { + Cylinders[i] = RandomCylinder(); + } + else + { + break; + } + } + + public PuzzleChestCylinder[] Cylinders{ get; } = new PuzzleChestCylinder[Length]; + + public PuzzleChestCylinder First + { + get => Cylinders[0]; + set => Cylinders[0] = value; + } + + public PuzzleChestCylinder Second + { + get => Cylinders[1]; + set => Cylinders[1] = value; + } + + public PuzzleChestCylinder Third + { + get => Cylinders[2]; + set => Cylinders[2] = value; + } + + public PuzzleChestCylinder Fourth + { + get => Cylinders[3]; + set => Cylinders[3] = value; + } + + public PuzzleChestCylinder Fifth + { + get => Cylinders[4]; + set => Cylinders[4] = value; + } + + public static PuzzleChestCylinder RandomCylinder() + { + switch (Utility.Random(8)) + { + case 0: return PuzzleChestCylinder.LightBlue; + case 1: return PuzzleChestCylinder.Blue; + case 2: return PuzzleChestCylinder.Green; + case 3: return PuzzleChestCylinder.Orange; + case 4: return PuzzleChestCylinder.Purple; + case 5: return PuzzleChestCylinder.Red; + case 6: return PuzzleChestCylinder.DarkBlue; + default: return PuzzleChestCylinder.Yellow; + } + } + + public bool Matches(PuzzleChestSolution solution, out int cylinders, out int colors) + { + cylinders = 0; + colors = 0; + + bool[] matchesSrc = new bool[solution.Cylinders.Length]; + bool[] matchesDst = new bool[solution.Cylinders.Length]; + + for (int i = 0; i < Cylinders.Length; i++) + if (Cylinders[i] == solution.Cylinders[i]) + { + cylinders++; + + matchesSrc[i] = true; + matchesDst[i] = true; + } + + for (int i = 0; i < Cylinders.Length; i++) + if (!matchesSrc[i]) + for (int j = 0; j < solution.Cylinders.Length; j++) + if (Cylinders[i] == solution.Cylinders[j] && !matchesDst[j]) + { + colors++; + + matchesDst[j] = true; + } + + return cylinders == Cylinders.Length; + } + + public virtual void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(Cylinders.Length); + for (int i = 0; i < Cylinders.Length; i++) writer.Write((int)Cylinders[i]); + } + } + + public class PuzzleChestSolutionAndTime : PuzzleChestSolution + { + public PuzzleChestSolutionAndTime(DateTime when, PuzzleChestSolution solution) : base(solution) + { + When = when; + } + + public PuzzleChestSolutionAndTime(GenericReader reader) : base(reader) + { + int version = reader.ReadEncodedInt(); + + When = reader.ReadDeltaTime(); + } + + public DateTime When{ get; } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteDeltaTime(When); + } + } + + public abstract class PuzzleChest : BaseTreasureChest + { + public const int HintsCount = 3; + public readonly TimeSpan CleanupTime = TimeSpan.FromHours(1.0); + + private Dictionary m_Guesses = + new Dictionary(); + + private PuzzleChestSolution m_Solution; + + public PuzzleChest(int itemID) : base(itemID) + { + } + + public PuzzleChest(Serial serial) : base(serial) + { + } + + public PuzzleChestSolution Solution + { + get => m_Solution; + set + { + m_Solution = value; + InitHints(); + } + } + + public PuzzleChestCylinder[] Hints{ get; private set; } = new PuzzleChestCylinder[HintsCount]; + + public PuzzleChestCylinder FirstHint + { + get => Hints[0]; + set => Hints[0] = value; + } + + public PuzzleChestCylinder SecondHint + { + get => Hints[1]; + set => Hints[1] = value; + } + + public PuzzleChestCylinder ThirdHint + { + get => Hints[2]; + set => Hints[2] = value; + } + + public override string DefaultName => null; + + private void InitHints() + { + List list = new List(Solution.Cylinders.Length - 1); + for (int i = 1; i < Solution.Cylinders.Length; i++) + list.Add(Solution.Cylinders[i]); + + Hints = new PuzzleChestCylinder[HintsCount]; + + for (int i = 0; i < Hints.Length; i++) + { + int pos = Utility.Random(list.Count); + Hints[i] = list[pos]; + list.RemoveAt(pos); + } + } + + protected override void SetLockLevel() + { + LockLevel = 0; // Can't be unlocked + } + + public override bool CheckLocked(Mobile from) + { + if (Locked) + { + PuzzleChestSolution solution = GetLastGuess(from); + if (solution != null) + solution = new PuzzleChestSolution(solution); + else + solution = new PuzzleChestSolution(PuzzleChestCylinder.None, PuzzleChestCylinder.None, + PuzzleChestCylinder.None, PuzzleChestCylinder.None, PuzzleChestCylinder.None); + + from.CloseGump(typeof(PuzzleGump)); + from.CloseGump(typeof(StatusGump)); + from.SendGump(new PuzzleGump(from, this, solution, 0)); + + return true; + } + + return false; + } + + public PuzzleChestSolutionAndTime GetLastGuess(Mobile m) + { + m_Guesses.TryGetValue(m, out PuzzleChestSolutionAndTime pcst); + return pcst; + } + + public void SubmitSolution(Mobile m, PuzzleChestSolution solution) + { + int correctCylinders, correctColors; + + if (solution.Matches(Solution, out correctCylinders, out correctColors)) + { + LockPick(m); + + DisplayTo(m); + } + else + { + m_Guesses[m] = new PuzzleChestSolutionAndTime(DateTime.UtcNow, solution); + + m.SendGump(new StatusGump(correctCylinders, correctColors)); + + DoDamage(m); + } + } + + public void DoDamage(Mobile to) + { + switch (Utility.Random(4)) + { + case 0: + { + Effects.SendLocationEffect(to, to.Map, 0x113A, 20, 10); + to.PlaySound(0x231); + to.LocalOverheadMessage(MessageType.Regular, 0x44, 1010523); // A toxic vapor envelops thee. + + to.ApplyPoison(to, Poison.Regular); + + break; + } + case 1: + { + Effects.SendLocationEffect(to, to.Map, 0x3709, 30); + to.PlaySound(0x54); + to.LocalOverheadMessage(MessageType.Regular, 0xEE, 1010524); // Searing heat scorches thy skin. + + AOS.Damage(to, to, Utility.RandomMinMax(10, 40), 0, 100, 0, 0, 0); + + break; + } + case 2: + { + to.PlaySound(0x223); + to.LocalOverheadMessage(MessageType.Regular, 0x62, + 1010525); // Pain lances through thee from a sharp metal blade. + + AOS.Damage(to, to, Utility.RandomMinMax(10, 40), 100, 0, 0, 0, 0); + + break; + } + default: + { + to.BoltEffect(0); + to.LocalOverheadMessage(MessageType.Regular, 0xDA, 1010526); // Lightning arcs through thy body. + + AOS.Damage(to, to, Utility.RandomMinMax(10, 40), 0, 0, 0, 0, 100); + + break; + } + } + } + + public override void LockPick(Mobile from) + { + base.LockPick(from); + + m_Guesses.Clear(); + } + + private static void GetRandomAOSStats(out int attributeCount, out int min, out int max) + { + int rnd = Utility.Random(15); + + if (rnd < 1) + { + attributeCount = Utility.RandomMinMax(2, 6); + min = 20; + max = 70; + } + else if (rnd < 3) + { + attributeCount = Utility.RandomMinMax(2, 4); + min = 20; + max = 50; + } + else if (rnd < 6) + { + attributeCount = Utility.RandomMinMax(2, 3); + min = 20; + max = 40; + } + else if (rnd < 10) + { + attributeCount = Utility.RandomMinMax(1, 2); + min = 10; + max = 30; + } + else + { + attributeCount = 1; + min = 10; + max = 20; + } + } + + protected override void GenerateTreasure() + { + DropItem(new Gold(600, 900)); + + List gems = new List(); + for (int i = 0; i < 9; i++) + { + Item gem = Loot.RandomGem(); + Type gemType = gem.GetType(); + + foreach (Item listGem in gems) + if (listGem.GetType() == gemType) + { + listGem.Amount++; + gem.Delete(); + break; + } + + if (!gem.Deleted) + gems.Add(gem); + } + + foreach (Item gem in gems) + DropItem(gem); + + if (0.2 > Utility.RandomDouble()) + DropItem(new BagOfReagents(50)); + + for (int i = 0; i < 2; i++) + { + Item item; + + if (Core.AOS) + item = Loot.RandomArmorOrShieldOrWeaponOrJewelry(); + else + item = Loot.RandomArmorOrShieldOrWeapon(); + + if (item is BaseWeapon weapon) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + + BaseRunicTool.ApplyAttributesTo(weapon, attributeCount, min, max); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)Utility.Random(6); + weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random(6); + weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random(6); + } + + DropItem(weapon); + } + else if (item is BaseArmor armor) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + + BaseRunicTool.ApplyAttributesTo(armor, attributeCount, min, max); + } + else + { + armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random(6); + armor.Durability = (ArmorDurabilityLevel)Utility.Random(6); + } + + DropItem(armor); + } + else if (item is BaseHat hat) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + + BaseRunicTool.ApplyAttributesTo(hat, attributeCount, min, max); + } + + DropItem(hat); + } + else if (item is BaseJewel jewel) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + + BaseRunicTool.ApplyAttributesTo(jewel, attributeCount, min, max); + + DropItem(jewel); + } + } + + Solution = new PuzzleChestSolution(); + } + + public void CleanupGuesses() + { + List toDelete = new List(); + + foreach (KeyValuePair kvp in m_Guesses) + if (DateTime.UtcNow - kvp.Value.When > CleanupTime) + toDelete.Add(kvp.Key); + + foreach (Mobile m in toDelete) + m_Guesses.Remove(m); + } + + public override void Serialize(GenericWriter writer) + { + CleanupGuesses(); + + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + m_Solution.Serialize(writer); + + writer.WriteEncodedInt(Hints.Length); + for (int i = 0; i < Hints.Length; i++) writer.Write((int)Hints[i]); + + writer.WriteEncodedInt(m_Guesses.Count); + foreach (KeyValuePair kvp in m_Guesses) + { + writer.Write(kvp.Key); + kvp.Value.Serialize(writer); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Solution = new PuzzleChestSolution(reader); + + int length = reader.ReadEncodedInt(); + for (int i = 0; i < length; i++) + { + PuzzleChestCylinder cylinder = (PuzzleChestCylinder)reader.ReadInt(); + + if (length == Hints.Length) + Hints[i] = cylinder; + } + + if (length != Hints.Length) + InitHints(); + + int guesses = reader.ReadEncodedInt(); + for (int i = 0; i < guesses; i++) + { + Mobile m = reader.ReadMobile(); + PuzzleChestSolutionAndTime sol = new PuzzleChestSolutionAndTime(reader); + + m_Guesses[m] = sol; + } + } + + private class PuzzleGump : Gump + { + private PuzzleChest m_Chest; + private Mobile m_From; + private PuzzleChestSolution m_Solution; + + public PuzzleGump(Mobile from, PuzzleChest chest, PuzzleChestSolution solution, int check) : base(50, 50) + { + m_From = from; + m_Chest = chest; + m_Solution = solution; + + Dragable = false; + + AddBackground(25, 0, 500, 410, 0x53); + + AddImage(62, 20, 0x67); + + AddHtmlLocalized(80, 36, 110, 70, 1018309, true, false); // A Puzzle Lock + + /* Correctly choose the sequence of cylinders needed to open the latch. Each cylinder + * may potentially be used more than once. Beware! A false attempt could be deadly! + */ + AddHtmlLocalized(214, 26, 270, 90, 1018310, true, true); + + AddLeftCylinderButton(62, 130, PuzzleChestCylinder.LightBlue, 10); + AddLeftCylinderButton(62, 180, PuzzleChestCylinder.Blue, 11); + AddLeftCylinderButton(62, 230, PuzzleChestCylinder.Green, 12); + AddLeftCylinderButton(62, 280, PuzzleChestCylinder.Orange, 13); + + AddRightCylinderButton(451, 130, PuzzleChestCylinder.Purple, 14); + AddRightCylinderButton(451, 180, PuzzleChestCylinder.Red, 15); + AddRightCylinderButton(451, 230, PuzzleChestCylinder.DarkBlue, 16); + AddRightCylinderButton(451, 280, PuzzleChestCylinder.Yellow, 17); + + double lockpicking = from.Skills.Lockpicking.Base; + if (lockpicking >= 60.0) + { + AddHtmlLocalized(160, 125, 230, 24, 1018308, false, false); // Lockpicking hint: + + AddBackground(159, 150, 230, 95, 0x13EC); + + if (lockpicking >= 80.0) + { + AddHtmlLocalized(165, 157, 200, 40, 1018312, false, false); // In the first slot: + AddCylinder(350, 165, chest.Solution.First); + + AddHtmlLocalized(165, 197, 200, 40, 1018313, false, false); // Used in unknown slot: + AddCylinder(350, 200, chest.FirstHint); + + if (lockpicking >= 90.0) + AddCylinder(350, 212, chest.SecondHint); + + if (lockpicking >= 100.0) + AddCylinder(350, 224, chest.ThirdHint); + } + else + { + AddHtmlLocalized(165, 157, 200, 40, 1018313, false, false); // Used in unknown slot: + AddCylinder(350, 160, chest.FirstHint); + + if (lockpicking >= 70.0) + AddCylinder(350, 172, chest.SecondHint); + } + } + + PuzzleChestSolution lastGuess = chest.GetLastGuess(from); + if (lastGuess != null) + { + AddHtmlLocalized(127, 249, 170, 20, 1018311, false, false); // Thy previous guess: + + AddBackground(290, 247, 115, 25, 0x13EC); + + AddCylinder(281, 254, lastGuess.First); + AddCylinder(303, 254, lastGuess.Second); + AddCylinder(325, 254, lastGuess.Third); + AddCylinder(347, 254, lastGuess.Fourth); + AddCylinder(369, 254, lastGuess.Fifth); + } + + AddPedestal(140, 270, solution.First, 0, check == 0); + AddPedestal(195, 270, solution.Second, 1, check == 1); + AddPedestal(250, 270, solution.Third, 2, check == 2); + AddPedestal(305, 270, solution.Fourth, 3, check == 3); + AddPedestal(360, 270, solution.Fifth, 4, check == 4); + + AddButton(258, 370, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + } + + private void AddLeftCylinderButton(int x, int y, PuzzleChestCylinder cylinder, int buttonID) + { + AddBackground(x, y, 30, 30, 0x13EC); + AddCylinder(x - 7, y + 10, cylinder); + AddButton(x + 38, y + 9, 0x13A8, 0x4B9, buttonID, GumpButtonType.Reply, 0); + } + + private void AddRightCylinderButton(int x, int y, PuzzleChestCylinder cylinder, int buttonID) + { + AddBackground(x, y, 30, 30, 0x13EC); + AddCylinder(x - 7, y + 10, cylinder); + AddButton(x - 26, y + 9, 0x13A8, 0x4B9, buttonID, GumpButtonType.Reply, 0); + } + + private void AddPedestal(int x, int y, PuzzleChestCylinder cylinder, int switchID, bool initialState) + { + AddItem(x, y, 0xB10); + AddItem(x - 23, y + 12, 0xB12); + AddItem(x + 23, y + 12, 0xB13); + AddItem(x, y + 23, 0xB11); + + if (cylinder != PuzzleChestCylinder.None) + { + AddItem(x, y + 2, 0x51A); + AddCylinder(x - 1, y + 19, cylinder); + } + else + { + AddItem(x, y + 2, 0x521); + } + + AddRadio(x + 7, y + 65, 0x867, 0x86A, initialState, switchID); + } + + private void AddCylinder(int x, int y, PuzzleChestCylinder cylinder) + { + if (cylinder != PuzzleChestCylinder.None) + AddItem(x, y, (int)cylinder); + else + AddItem(x + 9, y, (int)cylinder); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Chest.Deleted || info.ButtonID == 0 || !m_From.CheckAlive()) + return; + + if (m_From.AccessLevel == AccessLevel.Player && + (m_From.Map != m_Chest.Map || !m_From.InRange(m_Chest.GetWorldLocation(), 2))) + { + m_From.LocalOverheadMessage(MessageType.Regular, 0x3B2, 500446); // That is too far away. + return; + } + + if (info.ButtonID == 1) + { + m_Chest.SubmitSolution(m_From, m_Solution); + } + else + { + if (info.Switches.Length == 0) + return; + + int pedestal = info.Switches[0]; + if (pedestal < 0 || pedestal >= m_Solution.Cylinders.Length) + return; + + PuzzleChestCylinder cylinder; + switch (info.ButtonID) + { + case 10: + cylinder = PuzzleChestCylinder.LightBlue; + break; + case 11: + cylinder = PuzzleChestCylinder.Blue; + break; + case 12: + cylinder = PuzzleChestCylinder.Green; + break; + case 13: + cylinder = PuzzleChestCylinder.Orange; + break; + case 14: + cylinder = PuzzleChestCylinder.Purple; + break; + case 15: + cylinder = PuzzleChestCylinder.Red; + break; + case 16: + cylinder = PuzzleChestCylinder.DarkBlue; + break; + case 17: + cylinder = PuzzleChestCylinder.Yellow; + break; + default: return; + } + + m_Solution.Cylinders[pedestal] = cylinder; + + m_From.SendGump(new PuzzleGump(m_From, m_Chest, m_Solution, pedestal)); + } + } + } + + private class StatusGump : Gump + { + public StatusGump(int correctCylinders, int correctColors) : base(50, 50) + { + AddBackground(15, 250, 305, 163, 0x53); + AddBackground(28, 265, 280, 133, 0xBB8); + + AddHtmlLocalized(35, 271, 270, 24, 1018314, false, false); // Thou hast failed to solve the puzzle! + + AddHtmlLocalized(35, 297, 250, 24, 1018315, false, false); // Correctly placed colors: + AddLabel(285, 297, 0x44, correctCylinders.ToString()); + + AddHtmlLocalized(35, 323, 250, 24, 1018316, false, false); // Used colors in wrong slots: + AddLabel(285, 323, 0x44, correctColors.ToString()); + + AddButton(152, 369, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + } + } + } + + [Flippable(0xE41, 0xE40)] + public class MetalGoldenPuzzleChest : PuzzleChest + { + [Constructible] + public MetalGoldenPuzzleChest() : base(0xE41) + { + } + + public MetalGoldenPuzzleChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + [Flippable(0xE80, 0x9A8)] + public class StrongBoxPuzzle : PuzzleChest + { + [Constructible] + public StrongBoxPuzzle() : base(0xE80) + { + } + + public StrongBoxPuzzle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/RaisableItem.cs b/Scripts/Engines/Khaldun/RaisableItem.cs index f2aaa9abb..4b6ea9f9e 100644 --- a/Scripts/Engines/Khaldun/RaisableItem.cs +++ b/Scripts/Engines/Khaldun/RaisableItem.cs @@ -2,169 +2,169 @@ using System; namespace Server.Items { - public class RaisableItem : Item - { - private int m_MaxElevation; + public class RaisableItem : Item + { + private int m_Elevation; + private int m_MaxElevation; + private RaiseTimer m_RaiseTimer; - [CommandProperty( AccessLevel.GameMaster )] - public int MaxElevation - { - get => m_MaxElevation; - set - { - if ( value <= 0 ) - m_MaxElevation = 0; - else if ( value >= 60 ) - m_MaxElevation = 60; - else - m_MaxElevation = value; - } - } + [Constructible] + public RaisableItem(int itemID) : this(itemID, 20, -1, -1, TimeSpan.FromMinutes(1.0)) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int MoveSound { get; set; } + [Constructible] + public RaisableItem(int itemID, int maxElevation, TimeSpan closeDelay) : this(itemID, maxElevation, -1, -1, + closeDelay) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int StopSound { get; set; } + [Constructible] + public RaisableItem(int itemID, int maxElevation, int moveSound, int stopSound, TimeSpan closeDelay) : base(itemID) + { + Movable = false; - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan CloseDelay { get; set; } + m_MaxElevation = maxElevation; + MoveSound = moveSound; + StopSound = stopSound; + CloseDelay = closeDelay; + } - [Constructible] - public RaisableItem( int itemID ) : this( itemID, 20, -1, -1, TimeSpan.FromMinutes( 1.0 ) ) - { - } + public RaisableItem(Serial serial) : base(serial) + { + } - [Constructible] - public RaisableItem( int itemID, int maxElevation, TimeSpan closeDelay ) : this( itemID, maxElevation, -1, -1, closeDelay ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxElevation + { + get => m_MaxElevation; + set + { + if (value <= 0) + m_MaxElevation = 0; + else if (value >= 60) + m_MaxElevation = 60; + else + m_MaxElevation = value; + } + } - [Constructible] - public RaisableItem( int itemID, int maxElevation, int moveSound, int stopSound, TimeSpan closeDelay ) : base( itemID ) - { - Movable = false; + [CommandProperty(AccessLevel.GameMaster)] + public int MoveSound{ get; set; } - m_MaxElevation = maxElevation; - MoveSound = moveSound; - StopSound = stopSound; - CloseDelay = closeDelay; - } + [CommandProperty(AccessLevel.GameMaster)] + public int StopSound{ get; set; } - private int m_Elevation; - private RaiseTimer m_RaiseTimer; + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan CloseDelay{ get; set; } - public bool IsRaisable => m_RaiseTimer == null; + public bool IsRaisable => m_RaiseTimer == null; - public void Raise() - { - if ( !IsRaisable ) - return; + public void Raise() + { + if (!IsRaisable) + return; - m_RaiseTimer = new RaiseTimer( this ); - m_RaiseTimer.Start(); - } + m_RaiseTimer = new RaiseTimer(this); + m_RaiseTimer.Start(); + } - private class RaiseTimer : Timer - { - private RaisableItem m_Item; - private DateTime m_CloseTime; - private bool m_Up; - private int m_Step; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public RaiseTimer( RaisableItem item ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 0.5 ) ) - { - m_Item = item; - m_CloseTime = DateTime.UtcNow + item.CloseDelay; - m_Up = true; + writer.WriteEncodedInt(0); // version - Priority = TimerPriority.TenMS; - } + writer.WriteEncodedInt(m_MaxElevation); + writer.WriteEncodedInt(MoveSound); + writer.WriteEncodedInt(StopSound); + writer.Write(CloseDelay); - protected override void OnTick() - { - if ( m_Item.Deleted ) - { - Stop(); - return; - } + writer.WriteEncodedInt(m_Elevation); + } - if ( m_Step++ % 3 == 0 ) - { - if ( m_Up ) - { - m_Item.Z++; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( ++m_Item.m_Elevation >= m_Item.MaxElevation ) - { - Stop(); + int version = reader.ReadEncodedInt(); - if ( m_Item.StopSound >= 0 ) - Effects.PlaySound( m_Item.Location, m_Item.Map, m_Item.StopSound ); + m_MaxElevation = reader.ReadEncodedInt(); + MoveSound = reader.ReadEncodedInt(); + StopSound = reader.ReadEncodedInt(); + CloseDelay = reader.ReadTimeSpan(); - m_Up = false; - m_Step = 0; + int elevation = reader.ReadEncodedInt(); + Z -= elevation; + } - TimeSpan delay = m_CloseTime - DateTime.UtcNow; - DelayCall( delay > TimeSpan.Zero ? delay : TimeSpan.Zero, Start ); + private class RaiseTimer : Timer + { + private DateTime m_CloseTime; + private RaisableItem m_Item; + private int m_Step; + private bool m_Up; - return; - } - } - else - { - m_Item.Z--; + public RaiseTimer(RaisableItem item) : base(TimeSpan.Zero, TimeSpan.FromSeconds(0.5)) + { + m_Item = item; + m_CloseTime = DateTime.UtcNow + item.CloseDelay; + m_Up = true; - if ( --m_Item.m_Elevation <= 0 ) - { - Stop(); + Priority = TimerPriority.TenMS; + } - if ( m_Item.StopSound >= 0 ) - Effects.PlaySound( m_Item.Location, m_Item.Map, m_Item.StopSound ); + protected override void OnTick() + { + if (m_Item.Deleted) + { + Stop(); + return; + } - m_Item.m_RaiseTimer = null; + if (m_Step++ % 3 == 0) + { + if (m_Up) + { + m_Item.Z++; - return; - } - } - } + if (++m_Item.m_Elevation >= m_Item.MaxElevation) + { + Stop(); - if ( m_Item.MoveSound >= 0 ) - Effects.PlaySound( m_Item.Location, m_Item.Map, m_Item.MoveSound ); - } - } + if (m_Item.StopSound >= 0) + Effects.PlaySound(m_Item.Location, m_Item.Map, m_Item.StopSound); - public RaisableItem( Serial serial ) : base( serial ) - { - } + m_Up = false; + m_Step = 0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + TimeSpan delay = m_CloseTime - DateTime.UtcNow; + DelayCall(delay > TimeSpan.Zero ? delay : TimeSpan.Zero, Start); - writer.WriteEncodedInt( (int) 0 ); // version + return; + } + } + else + { + m_Item.Z--; - writer.WriteEncodedInt( (int) m_MaxElevation ); - writer.WriteEncodedInt( (int) MoveSound ); - writer.WriteEncodedInt( (int) StopSound ); - writer.Write( (TimeSpan) CloseDelay ); + if (--m_Item.m_Elevation <= 0) + { + Stop(); - writer.WriteEncodedInt( (int) m_Elevation ); - } + if (m_Item.StopSound >= 0) + Effects.PlaySound(m_Item.Location, m_Item.Map, m_Item.StopSound); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + m_Item.m_RaiseTimer = null; - int version = reader.ReadEncodedInt(); + return; + } + } + } - m_MaxElevation = reader.ReadEncodedInt(); - MoveSound = reader.ReadEncodedInt(); - StopSound = reader.ReadEncodedInt(); - CloseDelay = reader.ReadTimeSpan(); - - int elevation = reader.ReadEncodedInt(); - Z -= elevation; - } - } + if (m_Item.MoveSound >= 0) + Effects.PlaySound(m_Item.Location, m_Item.Map, m_Item.MoveSound); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Khaldun/RaiseSwitch.cs b/Scripts/Engines/Khaldun/RaiseSwitch.cs index d7fc4ba9c..213d167e2 100644 --- a/Scripts/Engines/Khaldun/RaiseSwitch.cs +++ b/Scripts/Engines/Khaldun/RaiseSwitch.cs @@ -3,214 +3,216 @@ using Server.Network; namespace Server.Items { - public class RaiseSwitch : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public RaisableItem RaisableItem { get; set; } + public class RaiseSwitch : Item + { + private ResetTimer m_ResetTimer; - [Constructible] - public RaiseSwitch() : this( 0x1093 ) - { - } + [Constructible] + public RaiseSwitch() : this(0x1093) + { + } - protected RaiseSwitch( int itemID ) : base( itemID ) - { - Movable = false; - } + protected RaiseSwitch(int itemID) : base(itemID) + { + Movable = false; + } - public override void OnDoubleClick( Mobile m ) - { - if ( !m.InRange( this, 2 ) ) - { - m.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + public RaiseSwitch(Serial serial) : base(serial) + { + } - if ( RaisableItem != null && RaisableItem.Deleted ) - RaisableItem = null; + [CommandProperty(AccessLevel.GameMaster)] + public RaisableItem RaisableItem{ get; set; } - Flip(); + public override void OnDoubleClick(Mobile m) + { + if (!m.InRange(this, 2)) + { + m.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } - if ( RaisableItem != null ) - { - if ( RaisableItem.IsRaisable ) - { - RaisableItem.Raise(); - m.LocalOverheadMessage( MessageType.Regular, 0x5A, true, "You hear a grinding noise echoing in the distance." ); - } - else - { - m.LocalOverheadMessage( MessageType.Regular, 0x5A, true, "You flip the switch again, but nothing happens." ); - } - } - } + if (RaisableItem != null && RaisableItem.Deleted) + RaisableItem = null; - protected virtual void Flip() - { - if ( ItemID != 0x1093 ) - { - ItemID = 0x1093; + Flip(); - StopResetTimer(); - } - else - { - ItemID = 0x1095; + if (RaisableItem != null) + { + if (RaisableItem.IsRaisable) + { + RaisableItem.Raise(); + m.LocalOverheadMessage(MessageType.Regular, 0x5A, true, + "You hear a grinding noise echoing in the distance."); + } + else + { + m.LocalOverheadMessage(MessageType.Regular, 0x5A, true, + "You flip the switch again, but nothing happens."); + } + } + } - if ( RaisableItem != null && RaisableItem.CloseDelay >= TimeSpan.Zero ) - StartResetTimer( RaisableItem.CloseDelay ); - else - StartResetTimer( TimeSpan.FromMinutes( 2.0 ) ); - } + protected virtual void Flip() + { + if (ItemID != 0x1093) + { + ItemID = 0x1093; - Effects.PlaySound( Location, Map, 0x3E8 ); - } + StopResetTimer(); + } + else + { + ItemID = 0x1095; - private ResetTimer m_ResetTimer; + if (RaisableItem != null && RaisableItem.CloseDelay >= TimeSpan.Zero) + StartResetTimer(RaisableItem.CloseDelay); + else + StartResetTimer(TimeSpan.FromMinutes(2.0)); + } - protected void StartResetTimer( TimeSpan delay ) - { - StopResetTimer(); + Effects.PlaySound(Location, Map, 0x3E8); + } - m_ResetTimer = new ResetTimer( this, delay ); - m_ResetTimer.Start(); - } + protected void StartResetTimer(TimeSpan delay) + { + StopResetTimer(); - protected void StopResetTimer() - { - if ( m_ResetTimer != null ) - { - m_ResetTimer.Stop(); - m_ResetTimer = null; - } - } + m_ResetTimer = new ResetTimer(this, delay); + m_ResetTimer.Start(); + } - protected virtual void Reset() - { - if ( ItemID != 0x1093 ) - Flip(); - } + protected void StopResetTimer() + { + if (m_ResetTimer != null) + { + m_ResetTimer.Stop(); + m_ResetTimer = null; + } + } - private class ResetTimer : Timer - { - private RaiseSwitch m_RaiseSwitch; + protected virtual void Reset() + { + if (ItemID != 0x1093) + Flip(); + } - public ResetTimer( RaiseSwitch raiseSwitch, TimeSpan delay ) : base( delay ) - { - m_RaiseSwitch = raiseSwitch; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Priority = ComputePriority( delay ); - } + writer.WriteEncodedInt(0); // version - protected override void OnTick() - { - if ( m_RaiseSwitch.Deleted ) - return; + writer.Write(RaisableItem); + } - m_RaiseSwitch.m_ResetTimer = null; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_RaiseSwitch.Reset(); - } - } + int version = reader.ReadEncodedInt(); - public RaiseSwitch( Serial serial ) : base( serial ) - { - } + RaisableItem = (RaisableItem)reader.ReadItem(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Reset(); + } - writer.WriteEncodedInt( (int) 0 ); // version + private class ResetTimer : Timer + { + private RaiseSwitch m_RaiseSwitch; - writer.Write( (Item) RaisableItem ); - } + public ResetTimer(RaiseSwitch raiseSwitch, TimeSpan delay) : base(delay) + { + m_RaiseSwitch = raiseSwitch; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Priority = ComputePriority(delay); + } - int version = reader.ReadEncodedInt(); + protected override void OnTick() + { + if (m_RaiseSwitch.Deleted) + return; - RaisableItem = (RaisableItem) reader.ReadItem(); + m_RaiseSwitch.m_ResetTimer = null; - Reset(); - } - } + m_RaiseSwitch.Reset(); + } + } + } - public class DisappearingRaiseSwitch : RaiseSwitch - { - public int CurrentRange => Visible ? 3 : 2; + public class DisappearingRaiseSwitch : RaiseSwitch + { + [Constructible] + public DisappearingRaiseSwitch() : base(0x108F) + { + } - [Constructible] - public DisappearingRaiseSwitch() : base( 0x108F ) - { - } + public DisappearingRaiseSwitch(Serial serial) : base(serial) + { + } - protected override void Flip() - { - } + public int CurrentRange => Visible ? 3 : 2; - protected override void Reset() - { - } + public override bool HandlesOnMovement => true; - public override bool HandlesOnMovement => true; + protected override void Flip() + { + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Utility.InRange( m.Location, Location, CurrentRange ) || Utility.InRange( oldLocation, Location, CurrentRange ) ) - Refresh(); - } + protected override void Reset() + { + } - public override void OnMapChange() - { - if ( !Deleted ) - Refresh(); - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Utility.InRange(m.Location, Location, CurrentRange) || Utility.InRange(oldLocation, Location, CurrentRange)) + Refresh(); + } - public override void OnLocationChange( Point3D oldLoc ) - { - if ( !Deleted ) - Refresh(); - } + public override void OnMapChange() + { + if (!Deleted) + Refresh(); + } - public void Refresh() - { - bool found = false; - foreach ( Mobile mob in GetMobilesInRange( CurrentRange ) ) - { - if ( mob.Hidden && mob.AccessLevel > AccessLevel.Player ) - continue; + public override void OnLocationChange(Point3D oldLoc) + { + if (!Deleted) + Refresh(); + } - found = true; - break; - } + public void Refresh() + { + bool found = false; + foreach (Mobile mob in GetMobilesInRange(CurrentRange)) + { + if (mob.Hidden && mob.AccessLevel > AccessLevel.Player) + continue; - Visible = found; - } + found = true; + break; + } - public DisappearingRaiseSwitch( Serial serial ) : base( serial ) - { - } + Visible = found; + } - public override void Serialize( GenericWriter writer ) - { - if ( RaisableItem != null && RaisableItem.Deleted ) - RaisableItem = null; + public override void Serialize(GenericWriter writer) + { + if (RaisableItem != null && RaisableItem.Deleted) + RaisableItem = null; - base.Serialize( writer ); + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Timer.DelayCall( TimeSpan.Zero, Refresh ); - } - } -} + Timer.DelayCall(TimeSpan.Zero, Refresh); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/AGhostOfCovetous.cs b/Scripts/Engines/MLQuests/Definitions/AGhostOfCovetous.cs index eaeea907b0fbe5d137b3be80c37673b268b074d1..8425f10cd86f5e363453939bdfdfae42d75ca10e 100644 GIT binary patch literal 18694 zcmeI3Yfl_U7KZzCe#L}*2#$7H-$ORaM%alBl5cC+SWy(MxY@xBmu0|&jq=lXv+q-H zAF8T*U_3VVIuRPdbT`#i=YHOEs`&43%~3OIwwm4MMKfrYn-kp~Hk-{(^JVi<=WmV94KTj{;gThIAa^Bp&$*ZV)A9d}#y?Mz-AWSJ)2t)S{fmAE z`g|fTHYN2ft-q`LQhLz9n0-lfO_XhkhJk*DqGqJepjl|{H$Ul3r2Say+|@O@In*~A z9W;N{PpuWt8SD4wpET!ebETz=cguOWUpUqDYLfhho_(dCL-C1SAX&!6XGL5cCaHVe zwdQK`d2_3|-puR!OO5-BKFm8PcpZqp=X%oRx1Jl>k3`Rb*4Wo7A>*$)G(bza?(JgT zXOb_Re62B$b^RxOpCsuHlGL$6(+{Uu%g6d&)`$arPSW_L=2QJ;pm_#Ki-)Hizm!aN zMB9mc2R)tW_fFC--glt8`})15m5w#zQ13CrrbZkjpJUC#mO{_};?y1n={Yulg<-wB zXh!=VT+l7NgT_YE-WqB~eo}R92 zO|)>7=ox6O!z7(GJ%O(!{V+%T9BY=LK1iIg%!5pj2OhPl^}PZkyvCZI;xCMQuHQtR zVUj9d;wW{PR#-~*6PiSZaJ#Ly{p=udF-)V@^)6Jew!GT2;F0G@9174f^bV3YkyN%FQ%?vF(snnniD&$C*$NSXPO`(``Ze&~2( z%`=ZR&D*Si_J+E4{@hG47;igD&#}O+M3yx6iD=l944?#g^yN~N1zj^M00$f?`1Knl+H-9z^1TdG!gLzDdDNseZ&RFRr_lA>`43~!S4I^ zU(G+ac>jj}x+{IMo}<`vak-VE3vrLwwb4edLArDNE2$!0?koS) zk{zdwM_LWdIL?!wCyiPbZ}`li^b)uva`-rmHz%EK=rfyWJ=O|jV=#=dWB;95&3%$$ zH}amX^jOBqD@k70((jpSR2@@i(ujJ_d&$?xagJwKq>C$KI3iv}3T4HR|`zTyUvHDo#4wv7wh+IYmSW2M+jl#50gy>l6a&U!9w^ZcI&(lvk-%L zV*MCP@GPWI#;;#13#ielV~4Xeavn4*tyTvO6#OiXGsY$M|4n0REiH>atYlHtjAS>f zvZJn+CawBPe1c{`Q1%}3H?lY%zpiN%J~=n`y}s=~NihN~tx8sS=|N%h-RHL2Tdf6O zP2c`~qqXNdiP{Y8w~-$V2J;$cP9 zP{WX;hOG?4Yx(}LslS(~24R4DYym+%Hpq3h#o8juDruZOy-8&>Zl3e4>7uHk8`67O z4Fx42ZhVC3ikH-ppNKnc{liKn-f~UyT(di>93)FykY#S9STaiYrh)o~Oc*H3sN=hqTG0OwFM z;s1={3O|_B-J-6b!816wkrSx1!4^~{QDc?p9IBzzHJDcmYBGl2&`iV->Q>eU9U5IA z9rJJLe5Y~HZ93k@&>?~(UF zqNU7TWvojhJ9;;$rKYq^Qd3d&5%F2awP+V%QRD3X_Mb#eAW5hNGeuQY+WFTVZ+fb+ z=hZM7tKUd5IpbIQ2Dz?9X066V4fdNc9J*LfTtu&e(ed+G9PFtJ!Ee5OmH%GmXkz1% zBr&!0P{o36wI&AA{K6e(f zucOf%lfs*b6m@JWz5O^@53zt~wXaW9HPDDRchPy*11Hre?jTMY_4bv_N^4Ua9orvQ z)5KUKK_U}eg29)?Khh^)JLU%4VtiQeA^i`a*OT1j1<#EpMPmSD&g(ZDB|9h zdyZwVr;I*iV)p>ZNa)c~#@&d>Vr5*&NR=2{qt!q=AQ1HPCRNjdEGwh5QR*CX4KbG8$lyj1BNt>t zh2OV`lAciQ``I6fK47-#E5n;wJ4a`uLGrn)H}HkKzV6Ku9ipOgEp$&KKoYz|T~t<( z5lyKSK{`$Bh)yFJReUbx8OzjNE9wKwOk|l@p+;e~k zJs(jeU5RTXZMwTyYEm^*+e^19sCP)M7v%}92#x5>yPsJSu9t%v#u&+(1MkTpYwn}( zZpz^^ur9p8Y3i1@{B28ywi)&XYm8bWgxDtlYnJvmXle{VUBR5*+bel+t%zQCgyd=& zT|~82_IS?b6A8H*h$<)co{a2j-ZFx*f3QbKcNObSm`ZYV&xA@ny2YjB?BCg@y_b!h zXSsogaxELS$Qs|a9e<(%8VJlAwFO3 ze&Rd?Qe^Gm*Kw%a%VGxB!l%&np!rPS^sheCwR?;avt4ncrIK3S87G0*iDpgfH#mwY z5`4KsXxYH&Pl=DkL>W5yvp&`Y8O10(OC{DRX@W+31?P7{!$cQH2y4OJNB1&ZD@3ns zRU=;}nYhzYzaT*TeUH614v=G&U?maaY5|92PeVyQo`mID_) zNg2oet&7+JEv#N%Zb_cK4|+@0Q0%JCe<1R|cn;3fL4POo6U8J~SNUXVoZ0w9kt#nW z_m<~gV^rOJ`GH@v)TMu;OKf? zuT|ILSR7|sK~SvC*`OsM1D_n>q{dS7&xTz!Bmm~aBdI(&@pG8?CAZJ%Gy;gur*C5a z+}=Ca#)j*%zKropexQPSzC5`)qdRB$1>s0)I-|nKx{q{E^;w_4m{CQY*I-`Gx@?G_ z@5JFy5(S%(v9Idv#5MIuIR#d~L7%i7H7}pIry9RMjt<^|B;?$+q%nE!>zesy+WYO! z?zg(DZ~}o&L_L~b1Up#JzNp`m*1P*!Gn~D4y*f1*T3OZ)_DEly2=C~gudb()63|}1 zzaYtPoXRJkUBc4o5c?eXwq|vw`t{!SjsqQ+SyA$H(&4qKW_XZn^@U>XsyH-Xwud{i zmuYB0KkRRvNJgMkPIQ?nPF>&b&2=8G2>)D`^?~luxof<*EB&YMxltAHUODoYLM!L3 z-|w2&xCU!@CEpn88w%ZDv8VXdQSMhm9iKV^^;d8NiyDJI8XXzdI8;OlWbc0XjC4Z` zu#ab3nY2dkh?kPxYW}U+W{Y!4M3!es@=>)P7k6h#6fPrr&ZS+b&{nKa&(imj^6zs6 z1=vx!e?vt?zt6RE=6^b!W@#Yp(q@9*`$@{S!S#g5UBA&eA_~Xd>q+FSRqC1gQo$yu z)oQLCU(0vrPASAb@xFRr2I-)qETtcc6LWAGb~Y=^q9(?o@9W$D2NLI1qn-}Au;WKJ zgDm9^0O;z+cD33j%Z%Tjhy44lbANZ$4;2NRpRE^q*{z?+ZYl0!O^!eQ4flJ=-*@%A zyH8M$#fqlOd9hNqFrL&F(3gK1i!P&l&LVH?gLNdSwb0K$IU1Jw7#|5Qb3->*+l}Do=Y?@q95p_3 zQ4>4ngDi&$@pNY|vq+|fD_6aoF4|UB*i97r%zJl^>GMXNcm5$H!QLpjhyQO{5T#(f z7h1KXB&tCEzr($Fs%-ZGHe2jd&-|fQVNaEl*Q6cSOShG`KNtOd^p?4)y)*kr8M`lY zX_-qyMwc}c-KlIz=V7(;P{LW&%pbjGsy(mFi)DBA{p7}S#ou3kyrUTJ?pOZbj(&!m zKHrr&j9wQ1A9q!~v2LE4wxh_2_3SrPHsfaKu6|R|{M+7}k-L_ZugK2hI;MS!>OU)Av)y?~nfaKc7xaaR2}S literal 17966 zcmeI3=}+9p8OP@>`774sMeL}h1{()AN+W!NrdC=>C%WsVcG^qdrZ4*5wbN00qjyJX zCf(07nAg^fne;e4N`KdQ?z;KO)3lym>wZJ`+j(B+!Z4o;-rKY$3^ujKcnp_&bW9re zI2{Pn?X;V52j&-|YE2w~mP1`_=nCGPkN$fazm++=ojGtIs2#!nRiCN!rD$l2=i6F+ zU(jpbfx(nkJ{DfP8nL1G8@gK4{En^{)5G*i^WgMTt#Mb^$fc`aq}fV;)u$;DAbRC~ z$ew#7e740^C|#8n9OkPh`u;_53wEvaUHY5GbbDhCwEk7yuLwJESQ3;@x~IEMJ-wD? z#M=FQL}QcKs{ds#bU*NrCP6g8Nk0f70(smQyRs z4_!8<@C%*0qTdybKq4o3{BrtAZ(4%W%KFefrR}xo-V-h-vOpw$qVGM8vkf2V?qSBZ zBda;k+-`=@)`+8QxvbgkVQBa-Pc^HRpQBA^DmJj6*JX{aAnfEPEn#rj8-pJ~gZA_2 zmhRAO;3J2AuC_GxSR-EQEj9oJOL=4`!vI(K0fYm6Z)i=pew^_EdN*@tT~8RhtPe2a z^Hy_r^#{ip3mhyM>0y`FA68(5*I3tGORF$$OW)|*ZsscXW?$FMD=cSC2}wdD)b41u zpB+gCtdBlzXf9Z<^=P$?!Y7`?aWFv2;M>Yx0b2@K@Byx`2(#^sKh)gO?9c?}uL&OV z44mMX`Hvn2g~PZQa|+JzFtiTIqoZq?!oa1eWoXy2aA$qAC46*1<|%&cmBxU}md2x< z9nIn?SN5)qYKy~Rb9nqMjp}IqU1>NL$TeCsXxj^w<*f=XmiLv$W7#{pYuXd5gDtBc zWL>k2Tf!fW0k6G`DPx*agrC5N!|mQ^COwD{WEo7M{5SZ9$tkxOl!(4zn zldU_bVkABb?;JjK5>>MmRafP;k!a|7SG+0u4d1~B>F_(=W@1#$hmNR5Z_rD49^M0f zV0VrYVdeIcw!E;wj_89|{qt>&#tW%#NGCgrb1g|3ZZOB*Xj5(xGw>;k_xo4=>WNP4>G;hoh)#_}NB6!FTw33&0T zX~P4BKO@r}Mio&QA6<`ymOAgaSwWBdgYk}NwQgXk_yWsxv&d8*bK|=)_eLt zGjwzNb0=dson?epg~mS1G~fqsNPCg# zT)LTVDT`#(P5Ilo9@P2Mxp4hZnzAaqs3Y+EyZLR&Q2!`2Jjl2crO6y3qsQja1Ap_| z)P=fQ8D1HD_zGn)JrD)93^E<8hI=CYv9y$E;d%w?n)D3nHW84Fnmnl^uSqUI1V!ff zY4Q`S2knoFsZ=TU$;~x}@oAWyT)YapAziMkpjeswo9YceP5l;;1Ft=)?g3_+_5##WRC`1z)^QEm zpNmo3?Em)Pj7{X6U`uut)ljYH-=EsebB#J%?Q$bWl9IX8DJYdJ-0I0nc%Zo@&qE3u z8UN@;FgiX@h5LcBGrsxtRe2vVeM(;Je6tD!4J=g4a;XKMnr6*h`ay6Ou{+|xMMocR9GKHD>T9~z4_N6lm10b2An z&_P?P^YB`0pnNI&0V^&O|(w8bEoM?jXch8-IXgm zE*zU|rS4hP9Sql2tc%?tyW(NOHn97qr>SlCZPpVk8{c!Nzo=%w5!>v~%Zoits!iMv zm^A8Q70hZ+XEytEdw4Aqqn(lBU!acsdqs3_=n8+_$$8~1<&xJ$zpI-5D(K#+UIHup z=!&lFbDOnL866ccegbb7Glthh#U`(1Od=zSOaPA-^}xHv?Va=kX^$3m*0E&Z%E;C(0edx?fZKlM=^?BgoBu!`+66Jz?peSB2y{X?nme z&srWwO*E=n7#s<4+`4OWKX|Hx-1S3)YZtq_6T|0IUHHxm_vbN>e# zL50ek#T+3@#S~c#l@Yl>)IcSFeIXp_9${&Crf!d_5~)kyyD!%EM$%vRE*G6B_XeGB zM;`1N~{z+(AP#i!L!Bat&8GK#6LLs8;8fjt%UU z0n3#eQIF@&S4!>ze==lI4X2HF$u`cHy*Ky#ECFR`f( z%@#fNJ}kOhI7D_(st}M(~YIW>&W<`;-;_IxnPA*cU@M*ooe5>r+r8c4acgn zX762l2gX{T`>GE_}bdtIiNzweAF*bylWY=n)YrzjNSnj>P)z$ zlOwJKfwtPS)UuOm>j4K#{E9~1(KQrNO~6|!vCY#e-Mgjsh}0r@S5pgSwM3o8S$mNW z`?X*Jjq!)IW$@VKrWvECY6<_zON?3c2p z@^$8k`(h`e7+(y3v2!8|dR07OSX<~5KCt+fyMooffA~btsOBB3KFxis z!R|&!dJOHQBiF3r24{FLyE$ukCD-(W*Th|a>V1^S)!eeUO7F2AS?_C+PdU5quUG5! z2lJ`G#`R@XfYls%F7InKJM@k(pI3bqJ5b>T&sJC6R`+e8S69vV_CP;gUG;m?FuIE=2cU~4&%ZnBa7dQj?waH?g)M<&*9yka?a5w2EJ4bE6<3G z^$E;Lryspj>obmcLZa^73=v=96FvBeUwheTbC)glhltaTe$85#%=L|+?CO_j?plK= zIk<~=mVH8Mkdl8;KT??hzpMTDh>?apt#|;>rmM3RKjjk{nT0&}_>Jhw>~v_6eFtvhE5i^74bj_qTmNnwJWYz zK49{T?9Zp5q86dASifJ8wLVbyw(P|(2?`Z=M7w3ZbuSrsbAoy^?`;-{9^Vg{a{+W0 zVjP_X_GZBGENk4IFn9ENu_D?FuUGWJ8r)gt6pA}va+39#-$Wu!uoRjEbQ-EWFLm%sRGu67_bX7QD z^=Oham(nw%%Af=0dUU)D#&H9GTl2VJ-Q)=Qt*aq=EBK>wH;yBt;rGL+xnjCoz1~1j zX^&ISo5^`Mm|)jvX*r+LjI}>iC-mW5L>BlwohwQ_;6v%V|7##lF-A3N-QCcb6=nPA z#w+m+Z|@Aqk)|0*>oY!saOh8eZqb>_{N4FjG~oO(y`R6IQgr7`=IB_wSjDu#_%$zo z3t#O2q4FU6tbJ)ue`h~NT_nbh@~DISz4Yi2AL{?%nNl`TV#lRN51oAf9(}a0jXuHW zSpfxg7ps8+%BSQf$5lc7=bq|X=ecr`($|c;nS8>?oz&t%$NS=DT|^zvd@4zMTPoAt zoG%rKwa+eVbLDE0lPo(qlk> zg|JEfBD4|lirTF-bu1mFL8b-yjqW72a>oR^}&86b0 zD~o=M_>l3d?n{22F|4NWVsWg7^v8&0ccgRf6_peHbu>FqgsNi?-f%&Exa;a3mFRTd z4jU(yBMJf7%6BM348;xkFa$ ztCnut`8#*xx^0|zJzwwc{q_Or!taWAK3BAV8gy@ob&$z;`Xfo diff --git a/Scripts/Engines/MLQuests/Definitions/BaseEscort.cs b/Scripts/Engines/MLQuests/Definitions/BaseEscort.cs index a1c5fdddf..93cdd2b30 100644 --- a/Scripts/Engines/MLQuests/Definitions/BaseEscort.cs +++ b/Scripts/Engines/MLQuests/Definitions/BaseEscort.cs @@ -1,21 +1,21 @@ namespace Server.Engines.MLQuests.Definitions { - // Base class for escorts providing the AwardHumanInNeed option - public class BaseEscort : MLQuest - { - public virtual bool AwardHumanInNeed => true; + // Base class for escorts providing the AwardHumanInNeed option + public class BaseEscort : MLQuest + { + public BaseEscort() + { + CompletionNotice = CompletionNoticeShort; + } - public BaseEscort() - { - CompletionNotice = CompletionNoticeShort; - } + public virtual bool AwardHumanInNeed => true; - public override void GetRewards( MLQuestInstance instance ) - { - if ( AwardHumanInNeed ) - HumanInNeed.AwardTo( instance.Player ); + public override void GetRewards(MLQuestInstance instance) + { + if (AwardHumanInNeed) + HumanInNeed.AwardTo(instance.Player); - base.GetRewards( instance ); - } - } -} + base.GetRewards(instance); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Bedlam.cs b/Scripts/Engines/MLQuests/Definitions/Bedlam.cs index ec14236a6..95b0c47d6 100644 --- a/Scripts/Engines/MLQuests/Definitions/Bedlam.cs +++ b/Scripts/Engines/MLQuests/Definitions/Bedlam.cs @@ -1,4 +1,3 @@ -using System; using Server.Engines.MLQuests.Objectives; using Server.Engines.MLQuests.Rewards; using Server.Items; @@ -6,218 +5,226 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class Momento : MLQuest - { - public Momento() - { - Activated = true; - Title = 1074750; // Momento! - Description = 1074751; // I was going to march right out there and get it myself, but no ... Master Gnosos won't let me. But you see, that bridle means so much to me. A momento of happier, less-dead ... well undead horseback riding. Could you fetch it for me? I think my horse, formerly known as 'Resolve', may still be wearing it. - RefusalMessage = 1074752; // Hrmph. - InProgressMessage = 1074753; // The bridle would be hard to miss on him now ... since he's skeletal. Please do what you need to do to retrieve it for me. - CompletionMessage = 1074754; // I'd know that jingling sound anywhere! You have recovered my bridle. Thank you. + public class Momento : MLQuest + { + public Momento() + { + Activated = true; + Title = 1074750; // Momento! + Description = + 1074751; // I was going to march right out there and get it myself, but no ... Master Gnosos won't let me. But you see, that bridle means so much to me. A momento of happier, less-dead ... well undead horseback riding. Could you fetch it for me? I think my horse, formerly known as 'Resolve', may still be wearing it. + RefusalMessage = 1074752; // Hrmph. + InProgressMessage = + 1074753; // The bridle would be hard to miss on him now ... since he's skeletal. Please do what you need to do to retrieve it for me. + CompletionMessage = 1074754; // I'd know that jingling sound anywhere! You have recovered my bridle. Thank you. - Objectives.Add( new CollectObjective( 1, typeof( ResolvesBridle ), "Resolve's Bridle" ) ); + Objectives.Add(new CollectObjective(1, typeof(ResolvesBridle), "Resolve's Bridle")); - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } + Rewards.Add(ItemReward.LargeBagOfTreasure); + } - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Kia" ), new Point3D( 87, 1640, 0 ), Map.Malas ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Nythalia" ), new Point3D( 91, 1639, 0 ), Map.Malas ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Kia"), new Point3D(87, 1640, 0), Map.Malas); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Nythalia"), new Point3D(91, 1639, 0), Map.Malas); + } + } - public class CulinaryCrisis : MLQuest - { - public CulinaryCrisis() - { - Activated = true; - Title = 1074755; // Culinary Crisis - Description = 1074756; // You have NO idea how impossible this is. Simply intolerable! How can one expect an artiste' like me to create masterpieces of culinary delight without the best, fresh ingredients? Ever since this whositwhatsit started this uproar, my thrice-daily produce deliveries have ended. I can't survive another hour without produce! - RefusalMessage = 1074757; // You have no artistry in your soul. - InProgressMessage = 1074758; // I must have fresh produce and cheese at once! - CompletionMessage = 1074759; // Those dates look bruised! Oh no, and you fetched a soft cheese. *deep pained sigh* Well, even I can only do so much with inferior ingredients. BAM! + public class CulinaryCrisis : MLQuest + { + public CulinaryCrisis() + { + Activated = true; + Title = 1074755; // Culinary Crisis + Description = + 1074756; // You have NO idea how impossible this is. Simply intolerable! How can one expect an artiste' like me to create masterpieces of culinary delight without the best, fresh ingredients? Ever since this whositwhatsit started this uproar, my thrice-daily produce deliveries have ended. I can't survive another hour without produce! + RefusalMessage = 1074757; // You have no artistry in your soul. + InProgressMessage = 1074758; // I must have fresh produce and cheese at once! + CompletionMessage = + 1074759; // Those dates look bruised! Oh no, and you fetched a soft cheese. *deep pained sigh* Well, even I can only do so much with inferior ingredients. BAM! - Objectives.Add( new CollectObjective( 20, typeof( Dates ), 1025927 ) ); // bunch of dates - Objectives.Add( new CollectObjective( 5, typeof( CheeseWheel ), 1022430 ) ); // wheel of cheese + Objectives.Add(new CollectObjective(20, typeof(Dates), 1025927)); // bunch of dates + Objectives.Add(new CollectObjective(5, typeof(CheeseWheel), 1022430)); // wheel of cheese - Rewards.Add( ItemReward.BagOfTreasure ); - } + Rewards.Add(ItemReward.BagOfTreasure); + } - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Emerillo" ), new Point3D( 90, 1639, 0 ), Map.Malas ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Emerillo"), new Point3D(90, 1639, 0), Map.Malas); + } + } - public class GoneNative : MLQuest - { - public GoneNative() - { - Activated = true; - Title = 1074855; // Gone Native - Description = 1074856; // Pathetic really. I must say, a senior instructor going native -- forgetting about his students and peers and engaging in such disgraceful behavior! I'm speaking, of course, of Theophilus. Master Theophilus to you. He may have gone native but he still holds a Mastery Degree from Bedlam College! But, well, that's neither here nor there. I need you to take care of my colleague. Convince him of the error of his ways. He may resist. In fact, assume he will and kill him. We'll get him resurrected and be ready to cure his folly. What do you say? - RefusalMessage = 1074857; // I understand. A Master of Bedlam, even one entirely off his rocker, is too much for you to handle. - InProgressMessage = 1074858; // You had better get going. Master Theophilus isn't likely to kill himself just to save me this embarrassment. - CompletionMessage = 1074859; // You look a bit worse for wear! He put up a good fight did he? Hah! That's the spirit … a Master of Bedlam is a match for most. + public class GoneNative : MLQuest + { + public GoneNative() + { + Activated = true; + Title = 1074855; // Gone Native + Description = + 1074856; // Pathetic really. I must say, a senior instructor going native -- forgetting about his students and peers and engaging in such disgraceful behavior! I'm speaking, of course, of Theophilus. Master Theophilus to you. He may have gone native but he still holds a Mastery Degree from Bedlam College! But, well, that's neither here nor there. I need you to take care of my colleague. Convince him of the error of his ways. He may resist. In fact, assume he will and kill him. We'll get him resurrected and be ready to cure his folly. What do you say? + RefusalMessage = + 1074857; // I understand. A Master of Bedlam, even one entirely off his rocker, is too much for you to handle. + InProgressMessage = + 1074858; // You had better get going. Master Theophilus isn't likely to kill himself just to save me this embarrassment. + CompletionMessage = + 1074859; // You look a bit worse for wear! He put up a good fight did he? Hah! That's the spirit … a Master of Bedlam is a match for most. - Objectives.Add( new KillObjective( 1, new[] { typeof( MasterTheophilus ) }, "Master Theophilus" ) ); + Objectives.Add(new KillObjective(1, new[] { typeof(MasterTheophilus) }, "Master Theophilus")); - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } - #endregion + #endregion - #region Mobiles + #region Mobiles - [QuesterName( "Kia (Bedlam)" )] - public class Kia : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Kia"; + [QuesterName("Kia (Bedlam)")] + public class Kia : BaseCreature + { + [Constructible] + public Kia() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the student"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Kia() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the student"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + AddItem(new Backpack()); + AddItem(new Sandals(0x709)); + AddItem(new Robe(0x497)); + } - AddItem( new Backpack() ); - AddItem( new Sandals( 0x709 ) ); - AddItem( new Robe( 0x497 ) ); - } + public Kia(Serial serial) + : base(serial) + { + } - public Kia( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Kia"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [QuesterName( "Emerillo (Bedlam)" )] - public class Emerillo : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Emerillo"; + [QuesterName("Emerillo (Bedlam)")] + public class Emerillo : BaseCreature + { + [Constructible] + public Emerillo() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the cook"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - public override bool CanShout => true; + Utility.AssignRandomHair(this, true); - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074222 ); // Could I trouble you for some assistance? - } + AddItem(new Backpack()); + AddItem(new Sandals(Utility.RandomNeutralHue())); + AddItem(new ShortPants(Utility.RandomPinkHue())); + AddItem(new Shirt()); + AddItem(new HalfApron(0x8FD)); + } - [Constructible] - public Emerillo() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the cook"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + public Emerillo(Serial serial) + : base(serial) + { + } - Utility.AssignRandomHair( this, true ); + public override bool IsInvulnerable => true; + public override string DefaultName => "Emerillo"; - AddItem( new Backpack() ); - AddItem( new Sandals( Utility.RandomNeutralHue() ) ); - AddItem( new ShortPants( Utility.RandomPinkHue() ) ); - AddItem( new Shirt() ); - AddItem( new HalfApron( 0x8FD ) ); - } + public override bool CanShout => true; - public Emerillo( Serial serial ) - : base( serial ) - { - } + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074222); // Could I trouble you for some assistance? + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Nythalia : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Mythalia"; + public class Nythalia : BaseCreature + { + [Constructible] + public Nythalia() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the student"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Nythalia() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the student"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + AddItem(new Backpack()); + AddItem(new Shoes(Utility.RandomNeutralHue())); + AddItem(new Robe(Utility.RandomBool() ? 0x497 : 0x498)); + } - AddItem( new Backpack() ); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); - AddItem( new Robe( Utility.RandomBool() ? 0x497 : 0x498 ) ); - } + public Nythalia(Serial serial) + : base(serial) + { + } - public Nythalia( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Mythalia"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - #endregion -} + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/BlightedGrove.cs b/Scripts/Engines/MLQuests/Definitions/BlightedGrove.cs index 0992db483..a92dee904 100644 --- a/Scripts/Engines/MLQuests/Definitions/BlightedGrove.cs +++ b/Scripts/Engines/MLQuests/Definitions/BlightedGrove.cs @@ -1,271 +1,287 @@ using System; -using Server.Mobiles; -using Server.Items; using Server.Engines.MLQuests.Objectives; using Server.Engines.MLQuests.Rewards; +using Server.Items; +using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class VilePoison : MLQuest - { - public override Type NextQuest => typeof( ARockAndAHardPlace ); + public class VilePoison : MLQuest + { + public VilePoison() + { + Activated = true; + Title = 1074950; // Vile Poison + Description = + 1074956; // Heya! I'm sure glad to see you. Listen I'm in a bit of a bind here. I'm supposed to be gathering poisoned water at the base of that corrupted tree there, but I can't get in under the roots to get a good sample. The branches and brush are so tainted that they can't be cut, burned or even magically passed. It's put my work at a real standstill. If you help me out, I'll help you get in there too. Whadda ya say? + RefusalMessage = 1074964; // Okay. If you change your mind, I'll probably still be stuck here trying to get in. + InProgressMessage = 1074968; // My friend, Iosep, is a weaponsmith in Jhelom. If anyone can help us, he can! + CompletionMessage = + 1074991; // Greetings. What have you there? Ah, a sample from a poisonous tree, you say? My friend Jamal sent you? Well, let me see that then, and we'll get to work. - public VilePoison() - { - Activated = true; - Title = 1074950; // Vile Poison - Description = 1074956; // Heya! I'm sure glad to see you. Listen I'm in a bit of a bind here. I'm supposed to be gathering poisoned water at the base of that corrupted tree there, but I can't get in under the roots to get a good sample. The branches and brush are so tainted that they can't be cut, burned or even magically passed. It's put my work at a real standstill. If you help me out, I'll help you get in there too. Whadda ya say? - RefusalMessage = 1074964; // Okay. If you change your mind, I'll probably still be stuck here trying to get in. - InProgressMessage = 1074968; // My friend, Iosep, is a weaponsmith in Jhelom. If anyone can help us, he can! - CompletionMessage = 1074991; // Greetings. What have you there? Ah, a sample from a poisonous tree, you say? My friend Jamal sent you? Well, let me see that then, and we'll get to work. + Objectives.Add(new DeliverObjective(typeof(TaintedTreeSample), 1, "tainted tree sample", typeof(Iosep))); - Objectives.Add( new DeliverObjective( typeof( TaintedTreeSample ), 1, "tainted tree sample", typeof( Iosep ) ) ); + Rewards.Add(new DummyReward(1074962)); // A step closer to entering Blighted Grove. + } - Rewards.Add( new DummyReward( 1074962 ) ); // A step closer to entering Blighted Grove. - } + public override Type NextQuest => typeof(ARockAndAHardPlace); - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Jamal" ), new Point3D( 559, 1651, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Jamal" ), new Point3D( 559, 1651, 0 ), Map.Trammel ); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Jamal"), new Point3D(559, 1651, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Jamal"), new Point3D(559, 1651, 0), Map.Trammel); - PutSpawner( new Spawner( 1, 5, 10, 0, 2, "Iosep" ), new Point3D( 1354, 3754, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 2, "Iosep" ), new Point3D( 1354, 3754, 0 ), Map.Trammel ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 2, "Iosep"), new Point3D(1354, 3754, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 2, "Iosep"), new Point3D(1354, 3754, 0), Map.Trammel); + } + } - public class ARockAndAHardPlace : MLQuest - { - public override Type NextQuest => typeof( SympatheticMagic ); - public override bool IsChainTriggered => true; + public class ARockAndAHardPlace : MLQuest + { + public ARockAndAHardPlace() + { + Activated = true; + Title = 1074951; // A Rock and a Hard Place + Description = + 1074957; // This is some nasty stuff, that's for certain. I don't even want to think about what sort of blight caused this venomous reaction from that old tree. Let's get to work … we'll need to try something really hard but still workable as our base material. Nothing's harder than stone and diamond. Let's try them first. + RefusalMessage = 1074965; // Sure, no problem. I thought you were interested in figuring this out. + InProgressMessage = + 1074969; // If you're a miner, you should have no trouble getting that stuff. If not, you can probably buy some samples from a miner? + CompletionMessage = + 1074992; // Have you got the granite and diamonds? Great, let me see them and we'll see what effect this venom has upon them. - public ARockAndAHardPlace() - { - Activated = true; - Title = 1074951; // A Rock and a Hard Place - Description = 1074957; // This is some nasty stuff, that's for certain. I don't even want to think about what sort of blight caused this venomous reaction from that old tree. Let's get to work … we'll need to try something really hard but still workable as our base material. Nothing's harder than stone and diamond. Let's try them first. - RefusalMessage = 1074965; // Sure, no problem. I thought you were interested in figuring this out. - InProgressMessage = 1074969; // If you're a miner, you should have no trouble getting that stuff. If not, you can probably buy some samples from a miner? - CompletionMessage = 1074992; // Have you got the granite and diamonds? Great, let me see them and we'll see what effect this venom has upon them. + // Any type of granite works + Objectives.Add(new CollectObjective(4, typeof(BaseGranite), 1026009)); // rock + Objectives.Add(new CollectObjective(2, typeof(BlueDiamond), 1032696)); // Blue Diamond - // Any type of granite works - Objectives.Add( new CollectObjective( 4, typeof( BaseGranite ), 1026009 ) ); // rock - Objectives.Add( new CollectObjective( 2, typeof( BlueDiamond ), 1032696 ) ); // Blue Diamond + Rewards.Add(new DummyReward(1074962)); // A step closer to entering Blighted Grove. + } - Rewards.Add( new DummyReward( 1074962 ) ); // A step closer to entering Blighted Grove. - } - } + public override Type NextQuest => typeof(SympatheticMagic); + public override bool IsChainTriggered => true; + } - public class SympatheticMagic : MLQuest - { - public override Type NextQuest => typeof( AlreadyDead ); - public override bool IsChainTriggered => true; + public class SympatheticMagic : MLQuest + { + public SympatheticMagic() + { + Activated = true; + Title = 1074952; // Sympathetic Magic + Description = + 1074958; // Hmm, I've never even heard of something that can damage diamond like that. I guess we'll have to go with plan B. Let's try something similar. Sometimes there's a natural immunity to be found when you use a substance that's like the one you're trying to cut. A sort of "sympathetic" thing. Y'know? + RefusalMessage = 1074965; // Sure, no problem. I thought you were interested in figuring this out. + InProgressMessage = 1074970; // I think a lumberjack can help supply bark. + CompletionMessage = 1074993; // You're back with the bark already? Terrific! I bet this will do the trick. - public SympatheticMagic() - { - Activated = true; - Title = 1074952; // Sympathetic Magic - Description = 1074958; // Hmm, I've never even heard of something that can damage diamond like that. I guess we'll have to go with plan B. Let's try something similar. Sometimes there's a natural immunity to be found when you use a substance that's like the one you're trying to cut. A sort of "sympathetic" thing. Y'know? - RefusalMessage = 1074965; // Sure, no problem. I thought you were interested in figuring this out. - InProgressMessage = 1074970; // I think a lumberjack can help supply bark. - CompletionMessage = 1074993; // You're back with the bark already? Terrific! I bet this will do the trick. + Objectives.Add(new CollectObjective(10, typeof(BarkFragment), 1032687)); // Bark Fragment - Objectives.Add( new CollectObjective( 10, typeof( BarkFragment ), 1032687 ) ); // Bark Fragment + Rewards.Add(new DummyReward(1074962)); // A step closer to entering Blighted Grove. + } - Rewards.Add( new DummyReward( 1074962 ) ); // A step closer to entering Blighted Grove. - } - } + public override Type NextQuest => typeof(AlreadyDead); + public override bool IsChainTriggered => true; + } - public class AlreadyDead : MLQuest - { - public override Type NextQuest => typeof( Eureka ); - public override bool IsChainTriggered => true; + public class AlreadyDead : MLQuest + { + public AlreadyDead() + { + Activated = true; + Title = 1074953; // Already Dead + Description = + 1074959; // Amazing! The bark was reduced to ash in seconds. Whatever this taint is, it plays havok with living things. And of course, it took the edge off both diamonds and granite even faster. What we need is something workable but dead; something that can hold an edge without melting. See what you can come up with, please. + RefusalMessage = 1074965; // Sure, no problem. I thought you were interested in figuring this out. + InProgressMessage = + 1074971; // I'm thinking we need something fairly brittle or it won't hold an edge. And, it can't be alive, of course. + CompletionMessage = 1074994; // Great thought! Bone might just do the trick. - public AlreadyDead() - { - Activated = true; - Title = 1074953; // Already Dead - Description = 1074959; // Amazing! The bark was reduced to ash in seconds. Whatever this taint is, it plays havok with living things. And of course, it took the edge off both diamonds and granite even faster. What we need is something workable but dead; something that can hold an edge without melting. See what you can come up with, please. - RefusalMessage = 1074965; // Sure, no problem. I thought you were interested in figuring this out. - InProgressMessage = 1074971; // I'm thinking we need something fairly brittle or it won't hold an edge. And, it can't be alive, of course. - CompletionMessage = 1074994; // Great thought! Bone might just do the trick. + Objectives.Add(new InternalObjective()); - Objectives.Add( new InternalObjective() ); + Rewards.Add(new DummyReward(1074962)); // A step closer to entering Blighted Grove. + } - Rewards.Add( new DummyReward( 1074962 ) ); // A step closer to entering Blighted Grove. - } + public override Type NextQuest => typeof(Eureka); + public override bool IsChainTriggered => true; - private class InternalObjective : CollectObjective - { - public override bool ShowDetailed => false; + private class InternalObjective : CollectObjective + { + public InternalObjective() + : base(10, typeof(Bone), 1074963) // (10) workable samples + { + } - public InternalObjective() - : base( 10, typeof( Bone ), 1074963 ) // (10) workable samples - { - } - } - } + public override bool ShowDetailed => false; + } + } - public class Eureka : MLQuest - { - public override Type NextQuest => typeof( SubContracting ); - public override bool IsChainTriggered => true; + public class Eureka : MLQuest + { + public Eureka() + { + Activated = true; + Title = 1074954; // Eureka! + Description = + 1074960; // We're in business! I've put together the instructions for chopping sort of sword, in the style of one of those new-fangled elven machetes. Take those back to Jamal for me, if you would. + RefusalMessage = 1074966; // Well, okay. I guess I thought you'd want to see this through. + InProgressMessage = + 1074972; // I'm sure Jamal is eager to get this information. He's probably still hanging around near that big old blighted tree. + CompletionMessage = 1074995; // Heya! You're back. Was Iosep able to help? Let me see what he's sent. - public Eureka() - { - Activated = true; - Title = 1074954; // Eureka! - Description = 1074960; // We're in business! I've put together the instructions for chopping sort of sword, in the style of one of those new-fangled elven machetes. Take those back to Jamal for me, if you would. - RefusalMessage = 1074966; // Well, okay. I guess I thought you'd want to see this through. - InProgressMessage = 1074972; // I'm sure Jamal is eager to get this information. He's probably still hanging around near that big old blighted tree. - CompletionMessage = 1074995; // Heya! You're back. Was Iosep able to help? Let me see what he's sent. + Objectives.Add(new DeliverObjective(typeof(SealedNotesForJamal), 1, "sealed note for Jamal", typeof(Jamal))); - Objectives.Add( new DeliverObjective( typeof( SealedNotesForJamal ), 1, "sealed note for Jamal", typeof( Jamal ) ) ); + Rewards.Add(new DummyReward(1074962)); // A step closer to entering Blighted Grove. + } - Rewards.Add( new DummyReward( 1074962 ) ); // A step closer to entering Blighted Grove. - } + public override Type NextQuest => typeof(SubContracting); + public override bool IsChainTriggered => true; - public override void GetRewards( MLQuestInstance instance ) - { - PlayerMobile pm = instance.Player; + public override void GetRewards(MLQuestInstance instance) + { + PlayerMobile pm = instance.Player; - if ( !pm.HasRecipe( 32 ) ) - { - // The ability is awarded regardless of blacksmithy skill - pm.AcquireRecipe( 32 ); + if (!pm.HasRecipe(32)) + { + // The ability is awarded regardless of blacksmithy skill + pm.AcquireRecipe(32); - if ( pm.Skills[SkillName.Blacksmith].Base < 45.0 ) // TODO: Verify threshold - pm.SendLocalizedMessage( 1075005 ); // You observe carefully but you can't grasp the complexities of smithing a bone handled machete. - else - pm.SendLocalizedMessage( 1075006 ); // You have learned how to smith a bone handled machete! - } + if (pm.Skills[SkillName.Blacksmith].Base < 45.0) // TODO: Verify threshold + pm.SendLocalizedMessage( + 1075005); // You observe carefully but you can't grasp the complexities of smithing a bone handled machete. + else + pm.SendLocalizedMessage(1075006); // You have learned how to smith a bone handled machete! + } - base.GetRewards( instance ); - } - } + base.GetRewards(instance); + } + } - public class SubContracting : MLQuest - { - public override bool IsChainTriggered => true; + public class SubContracting : MLQuest + { + public SubContracting() + { + Activated = true; + Title = 1074955; // Sub Contracting + Description = + 1074961; // Wonderful! Now we can both get in there! Let me show you these instructions for making this machete. If you're not skilled in smithing, I'm not sure how much sense it will make though. Listen, if you're heading in there anyway … maybe you'd do me one more favor? I'm ah ... buried in work out here ... so if you'd go in and get me a few water samples, I'd be obliged. + RefusalMessage = 1074967; // Oh. Right, I guess you're really ... ah ... busy too. + InProgressMessage = + 1074973; // Once you're inside, look for places where the water has twisted and warped the natural creatures. + CompletionMessage = + 1074996; // I hear sloshing ... that must mean you've got my water samples. Whew, I'm so glad you braved the dangers in there ... I mean, I would have but I'm so busy out here. Here's your reward! - public SubContracting() - { - Activated = true; - Title = 1074955; // Sub Contracting - Description = 1074961; // Wonderful! Now we can both get in there! Let me show you these instructions for making this machete. If you're not skilled in smithing, I'm not sure how much sense it will make though. Listen, if you're heading in there anyway … maybe you'd do me one more favor? I'm ah ... buried in work out here ... so if you'd go in and get me a few water samples, I'd be obliged. - RefusalMessage = 1074967; // Oh. Right, I guess you're really ... ah ... busy too. - InProgressMessage = 1074973; // Once you're inside, look for places where the water has twisted and warped the natural creatures. - CompletionMessage = 1074996; // I hear sloshing ... that must mean you've got my water samples. Whew, I'm so glad you braved the dangers in there ... I mean, I would have but I'm so busy out here. Here's your reward! + Objectives.Add(new CollectObjective(3, typeof(SamplesOfCorruptedWater), + "samples of corrupted water")); // On OSI the label is "#1074999" + // TODO: "Return to" should say "Jamal (near Blighted Grove)" + // Maybe every quest NPC has directions as a property? - Objectives.Add( new CollectObjective( 3, typeof( SamplesOfCorruptedWater ), "samples of corrupted water" ) ); // On OSI the label is "#1074999" - // TODO: "Return to" should say "Jamal (near Blighted Grove)" - // Maybe every quest NPC has directions as a property? + Rewards.Add(ItemReward.LargeBagOfTreasure); + } - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } + public override bool IsChainTriggered => true; + } - #endregion + #endregion - #region Mobiles + #region Mobiles - [QuesterName( "Jamal (near Blighted Grove)" )] - public class Jamal : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Jamal"; + [QuesterName("Jamal (near Blighted Grove)")] + public class Jamal : BaseCreature + { + [Constructible] + public Jamal() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.2, 0.4) + { + Title = "the Fisherman"; + Body = 400; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Jamal() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.2, 0.4 ) - { - Title = "the Fisherman"; - Body = 400; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); + AddItem(new Shirt(0x1BB)); + AddItem(new ShortPants(Utility.RandomNeutralHue())); + AddItem(new ThighBoots(Utility.RandomAnimalHue())); + AddItem(new Backpack()); + } - AddItem( new Shirt( 0x1BB ) ); - AddItem( new ShortPants( Utility.RandomNeutralHue() ) ); - AddItem( new ThighBoots( Utility.RandomAnimalHue() ) ); - AddItem( new Backpack() ); - } + public Jamal(Serial serial) + : base(serial) + { + } - public Jamal( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Jamal"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - reader.ReadInt(); - } - } + reader.ReadInt(); + } + } - [QuesterName( "Iosep (Jhelom)" )] - public class Iosep : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Iosep"; + [QuesterName("Iosep (Jhelom)")] + public class Iosep : BaseCreature + { + [Constructible] + public Iosep() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.2, 0.4) + { + Title = "the Exporter"; + Body = 400; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074209, // Hey, could you help me out with something? - 1074215 // Don’t test my patience you sniveling worm! - ) ); - } + AddItem(new FancyShirt(Utility.RandomBlueHue())); + AddItem(new LongPants(0x1BB)); + AddItem(new Shoes(Utility.RandomNeutralHue())); + AddItem(new Backpack()); + } - [Constructible] - public Iosep() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.2, 0.4 ) - { - Title = "the Exporter"; - Body = 400; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + public Iosep(Serial serial) + : base(serial) + { + } - AddItem( new FancyShirt( Utility.RandomBlueHue() ) ); - AddItem( new LongPants( 0x1BB ) ); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); - AddItem( new Backpack() ); - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Iosep"; - public Iosep( Serial serial ) - : base( serial ) - { - } + public override bool CanShout => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074209, // Hey, could you help me out with something? + 1074215 // Don’t test my patience you sniveling worm! + )); + } - writer.Write( (int)0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion -} + reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Britannia.cs b/Scripts/Engines/MLQuests/Definitions/Britannia.cs index e43a3639f..632e95a57 100644 --- a/Scripts/Engines/MLQuests/Definitions/Britannia.cs +++ b/Scripts/Engines/MLQuests/Definitions/Britannia.cs @@ -6,188 +6,199 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class Aemaeth1 : MLQuest - { - public override Type NextQuest => typeof( Aemaeth2 ); + public class Aemaeth1 : MLQuest + { + public Aemaeth1() + { + Activated = true; + Title = 1075321; // Aemaeth + Description = + 1075322; // My father died in an accident some months ago. My mother refused to accept his death. We had a little money set by, and she took it to a necromancer, who promised to restore my father to life. Well, he revived my father, all right, the cheat! Now my father is a walking corpse, a travesty . . . a monster. My mother is beside herself -- she won't eat, she can't sleep. I prayed at the shrine of Spirituality for guidance, and I must have fallen asleep. When I awoke, there was this basin of clear water. I cannot leave my mother, for I fear what she might do to herself. Could you take this to the graveyard, and give it to what is left of my father? + RefusalMessage = + 1075324; // Oh! Alright then. I hope someone comes along soon who can help me, or I dont know what will become of us. + InProgressMessage = + 1075325; // My father - or what remains of him - can be found in the graveyard northwest of the city. + CompletionMessage = 1075326; // What is this you give me? A basin of water? + CompletionNotice = CompletionNoticeShort; - public Aemaeth1() - { - Activated = true; - Title = 1075321; // Aemaeth - Description = 1075322; // My father died in an accident some months ago. My mother refused to accept his death. We had a little money set by, and she took it to a necromancer, who promised to restore my father to life. Well, he revived my father, all right, the cheat! Now my father is a walking corpse, a travesty . . . a monster. My mother is beside herself -- she won't eat, she can't sleep. I prayed at the shrine of Spirituality for guidance, and I must have fallen asleep. When I awoke, there was this basin of clear water. I cannot leave my mother, for I fear what she might do to herself. Could you take this to the graveyard, and give it to what is left of my father? - RefusalMessage = 1075324; // Oh! Alright then. I hope someone comes along soon who can help me, or I dont know what will become of us. - InProgressMessage = 1075325; // My father - or what remains of him - can be found in the graveyard northwest of the city. - CompletionMessage = 1075326; // What is this you give me? A basin of water? - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(BasinOfCrystalClearWater), 1, "Basin of Crystal Clear Water", + typeof(SkeletonOfSzandor))); - Objectives.Add( new DeliverObjective( typeof( BasinOfCrystalClearWater ), 1, "Basin of Crystal Clear Water", typeof( SkeletonOfSzandor ) ) ); + Rewards.Add(new DummyReward(1075323)); // Aurelia's gratitude. + } - Rewards.Add( new DummyReward( 1075323 ) ); // Aurelia's gratitude. - } + public override Type NextQuest => typeof(Aemaeth2); - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Aurelia" ), new Point3D( 1459, 3795, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Aurelia" ), new Point3D( 1459, 3795, 0 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Aurelia"), new Point3D(1459, 3795, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Aurelia"), new Point3D(1459, 3795, 0), Map.Felucca); + } + } - public class Aemaeth2 : MLQuest - { - public override bool IsChainTriggered => true; + public class Aemaeth2 : MLQuest + { + public Aemaeth2() + { + Activated = true; + OneTimeOnly = true; + Title = 1075327; // Aemaeth + Description = + 1075328; // You tell me it is time to leave this flesh. I did not understand until now. I thought: I can see my wife and my daughter, I can speak. Is this not life? But now, as I regard my reflection, I see what I have become. This only a mockery of life. Thank you for having the courage to show me the truth. For the love I bear my wife and daughter, I know now that I must pass beyond the veil. Will you return this basin to Aurelia? She will know by this that I am at rest. + RefusalMessage = + 1075330; // You wont take this back to my daughter? Please, I cannot leave until she knows I am at peace. + InProgressMessage = 1075331; // My daughter will be at my home, on the east side of the city. + CompletionMessage = + 1075332; // Thank goodness! Now we can honor my father for the great man he was while he lived, rather than the horror he became. + CompletionNotice = CompletionNoticeShort; - public Aemaeth2() - { - Activated = true; - OneTimeOnly = true; - Title = 1075327; // Aemaeth - Description = 1075328; // You tell me it is time to leave this flesh. I did not understand until now. I thought: I can see my wife and my daughter, I can speak. Is this not life? But now, as I regard my reflection, I see what I have become. This only a mockery of life. Thank you for having the courage to show me the truth. For the love I bear my wife and daughter, I know now that I must pass beyond the veil. Will you return this basin to Aurelia? She will know by this that I am at rest. - RefusalMessage = 1075330; // You wont take this back to my daughter? Please, I cannot leave until she knows I am at peace. - InProgressMessage = 1075331; // My daughter will be at my home, on the east side of the city. - CompletionMessage = 1075332; // Thank goodness! Now we can honor my father for the great man he was while he lived, rather than the horror he became. - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(BasinOfCrystalClearWater), 1, "Basin of Crystal Clear Water", + typeof(Aurelia))); - Objectives.Add( new DeliverObjective( typeof( BasinOfCrystalClearWater ), 1, "Basin of Crystal Clear Water", typeof( Aurelia ) ) ); + Rewards.Add(new ItemReward(1075304, typeof(MirrorOfPurification))); // Mirror of Purification + } - Rewards.Add( new ItemReward( 1075304, typeof( MirrorOfPurification ) ) ); // Mirror of Purification - } + public override bool IsChainTriggered => true; - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 2, "SkeletonOfSzandor" ), new Point3D( 1277, 3731, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 2, "SkeletonOfSzandor" ), new Point3D( 1277, 3731, 0 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 2, "SkeletonOfSzandor"), new Point3D(1277, 3731, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 2, "SkeletonOfSzandor"), new Point3D(1277, 3731, 0), Map.Felucca); + } + } - public class OddsAndEnds : MLQuest - { - public OddsAndEnds() - { - Activated = true; - Title = 1074354; // Odds and Ends - Description = 1074677; // I've always been fascinated by primitive cultures -- especially the artifacts. I'm a collector, you see. I'm working on building my troglodyte display and I'm saddened to say that I'm short on examples of religion and superstition amongst the creatures. If you come across any primitive fetishes, I'd be happy to trade you something interesting for them. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1074678; // I don't really want to know where you get the primitive fetishes, as I can't support the destruction of their lifestyle and culture. That would be wrong. - CompletionMessage = 1074679; // Bravo! These fetishes are just what I needed. You've earned this reward. + public class OddsAndEnds : MLQuest + { + public OddsAndEnds() + { + Activated = true; + Title = 1074354; // Odds and Ends + Description = + 1074677; // I've always been fascinated by primitive cultures -- especially the artifacts. I'm a collector, you see. I'm working on building my troglodyte display and I'm saddened to say that I'm short on examples of religion and superstition amongst the creatures. If you come across any primitive fetishes, I'd be happy to trade you something interesting for them. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = + 1074678; // I don't really want to know where you get the primitive fetishes, as I can't support the destruction of their lifestyle and culture. That would be wrong. + CompletionMessage = 1074679; // Bravo! These fetishes are just what I needed. You've earned this reward. - Objectives.Add( new CollectObjective( 12, typeof( PrimitiveFetish ), "Primitive Fetishes" ) ); + Objectives.Add(new CollectObjective(12, typeof(PrimitiveFetish), "Primitive Fetishes")); - Rewards.Add( ItemReward.BagOfTreasure ); - } - } + Rewards.Add(ItemReward.BagOfTreasure); + } + } - public class EmbracingHumanity : MLQuest - { - public EmbracingHumanity() - { - Activated = true; - OneTimeOnly = true; // OSI has no limit or delay, VERY exploitable - Title = 1074349; // Embracing Humanity - Description = 1074357; // Well, I don't mind saying it -- I'm flabbergasted! Absolutely astonished. I just heard that some elves want to convert themselves to humans through some magical process. My cousin Nedrick does whatever needs doing. I guess you could check it out for yourself if you're curious. Anyway, I wonder if you'll bring my cousin, Drithen, this here treat my wife baked up for him special. - RefusalMessage = 1074459; // That's okay, I'll find someone else to make the delivery. - InProgressMessage = 1074460; // If I knew where my cousin was, I'd make the delivery myself. - CompletionMessage = 1074461; // Oh, hello there. What do you have for me? + public class EmbracingHumanity : MLQuest + { + public EmbracingHumanity() + { + Activated = true; + OneTimeOnly = true; // OSI has no limit or delay, VERY exploitable + Title = 1074349; // Embracing Humanity + Description = + 1074357; // Well, I don't mind saying it -- I'm flabbergasted! Absolutely astonished. I just heard that some elves want to convert themselves to humans through some magical process. My cousin Nedrick does whatever needs doing. I guess you could check it out for yourself if you're curious. Anyway, I wonder if you'll bring my cousin, Drithen, this here treat my wife baked up for him special. + RefusalMessage = 1074459; // That's okay, I'll find someone else to make the delivery. + InProgressMessage = 1074460; // If I knew where my cousin was, I'd make the delivery myself. + CompletionMessage = 1074461; // Oh, hello there. What do you have for me? - Objectives.Add( new DeliverObjective( typeof( SpecialTreatForDrithen ), 1, "treat for Drithen", typeof( Drithen ) ) ); + Objectives.Add(new DeliverObjective(typeof(SpecialTreatForDrithen), 1, "treat for Drithen", typeof(Drithen))); - Rewards.Add( ItemReward.BagOfTreasure ); - } - } + Rewards.Add(ItemReward.BagOfTreasure); + } + } - #endregion + #endregion - #region Mobiles + #region Mobiles - public class Aurelia : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Aurelia"; + public class Aurelia : BaseCreature + { + [Constructible] + public Aurelia() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Architect's Daughter"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Aurelia() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Architect's Daughter"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + AddItem(new Backpack()); + AddItem(new Sandals(Utility.RandomPinkHue())); - AddItem( new Backpack() ); - AddItem( new Sandals( Utility.RandomPinkHue() ) ); + if (Utility.RandomBool()) + AddItem(new Kilt(Utility.RandomPinkHue())); + else + AddItem(new Skirt(Utility.RandomPinkHue())); - if ( Utility.RandomBool() ) - AddItem( new Kilt( Utility.RandomPinkHue() ) ); - else - AddItem( new Skirt( Utility.RandomPinkHue() ) ); + AddItem(new FancyShirt(Utility.RandomRedHue())); + } - AddItem( new FancyShirt( Utility.RandomRedHue() ) ); - } + public Aurelia(Serial serial) + : base(serial) + { + } - public Aurelia( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Aurelia"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [QuesterName( "Szandor" )] - public class SkeletonOfSzandor : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Skeleton of Szandor"; + [QuesterName("Szandor")] + public class SkeletonOfSzandor : BaseCreature + { + [Constructible] + public SkeletonOfSzandor() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Late Architect"; + Hue = 0x83F2; // TODO: Random human hue? Why??? + Body = 0x32; + InitStats(100, 100, 25); + } - [Constructible] - public SkeletonOfSzandor() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Late Architect"; - Hue = 0x83F2; // TODO: Random human hue? Why??? - Body = 0x32; - InitStats( 100, 100, 25 ); - } + public SkeletonOfSzandor(Serial serial) + : base(serial) + { + } - public SkeletonOfSzandor( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Skeleton of Szandor"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - #endregion -} + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Heartwood.cs b/Scripts/Engines/MLQuests/Definitions/Heartwood.cs index 726e9b7f7..7e958a886 100644 --- a/Scripts/Engines/MLQuests/Definitions/Heartwood.cs +++ b/Scripts/Engines/MLQuests/Definitions/Heartwood.cs @@ -1,4 +1,3 @@ -using System; using Server.Engines.MLQuests.Objectives; using Server.Engines.MLQuests.Rewards; using Server.Items; @@ -6,4541 +5,4676 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests - - public class TheyreBreedingLikeRabbits : MLQuest - { - public TheyreBreedingLikeRabbits() - { - Activated = true; - Title = 1072244; // They're Breeding Like Rabbits - Description = 1072259; // Aaaahhhh! They're everywhere! Aaaaahhh! Ahem. Actually, friend, how do you feel about rabbits? Well, we're being overrun by them. We're finding fuzzy bunnies everywhere. Aaaaahhh! - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Rabbit ) }, "rabbits" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Saril" ), new Point3D( 7075, 376, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Saril" ), new Point3D( 7075, 376, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Cailla" ), new Point3D( 7075, 377, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Cailla" ), new Point3D( 7075, 377, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Tamm" ), new Point3D( 7075, 378, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Tamm" ), new Point3D( 7075, 378, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Landy" ), new Point3D( 7089, 390, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Landy" ), new Point3D( 7089, 390, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Alejaha" ), new Point3D( 7043, 387, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Alejaha" ), new Point3D( 7043, 387, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Mielan" ), new Point3D( 7063, 350, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Mielan" ), new Point3D( 7063, 350, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Ciala" ), new Point3D( 7031, 411, 7 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Ciala" ), new Point3D( 7031, 411, 7 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Aniel" ), new Point3D( 7034, 412, 6 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Aniel" ), new Point3D( 7034, 412, 6 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Aulan" ), new Point3D( 6986, 340, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Aulan" ), new Point3D( 6986, 340, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Brinnae" ), new Point3D( 6996, 351, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Brinnae" ), new Point3D( 6996, 351, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Caelas" ), new Point3D( 7039, 390, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Caelas" ), new Point3D( 7039, 390, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Clehin" ), new Point3D( 7092, 390, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Clehin" ), new Point3D( 7092, 390, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Cloorne" ), new Point3D( 7010, 364, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Cloorne" ), new Point3D( 7010, 364, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Salaenih" ), new Point3D( 7009, 362, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Salaenih" ), new Point3D( 7009, 362, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Vilo" ), new Point3D( 7029, 377, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Vilo" ), new Point3D( 7029, 377, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Tholef" ), new Point3D( 6986, 386, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Tholef" ), new Point3D( 6986, 386, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Tillanil" ), new Point3D( 6987, 388, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Tillanil" ), new Point3D( 6987, 388, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Waelian" ), new Point3D( 6996, 381, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Waelian" ), new Point3D( 6996, 381, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Sleen" ), new Point3D( 6997, 381, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Sleen" ), new Point3D( 6997, 381, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Unoelil" ), new Point3D( 7010, 388, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Unoelil" ), new Point3D( 7010, 388, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Anolly" ), new Point3D( 7009, 388, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Anolly" ), new Point3D( 7009, 388, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Jusae" ), new Point3D( 7042, 377, 2 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Jusae" ), new Point3D( 7042, 377, 2 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Cillitha" ), new Point3D( 7043, 377, 2 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Cillitha" ), new Point3D( 7043, 377, 2 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Lohn" ), new Point3D( 7062, 410, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Lohn" ), new Point3D( 7062, 410, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Olla" ), new Point3D( 7063, 410, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Olla" ), new Point3D( 7063, 410, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Thallary" ), new Point3D( 7032, 439, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Thallary" ), new Point3D( 7032, 439, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Ahie" ), new Point3D( 7033, 440, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Ahie" ), new Point3D( 7033, 440, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Tyeelor" ), new Point3D( 7010, 364, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Tyeelor" ), new Point3D( 7010, 364, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Athailon" ), new Point3D( 7011, 365, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Athailon" ), new Point3D( 7011, 365, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderTaellia" ), new Point3D( 7038, 387, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderTaellia" ), new Point3D( 7038, 387, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderMallew" ), new Point3D( 7047, 390, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderMallew" ), new Point3D( 7047, 390, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderAbbein" ), new Point3D( 7043, 390, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderAbbein" ), new Point3D( 7043, 390, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderVicaie" ), new Point3D( 7054, 390, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderVicaie" ), new Point3D( 7054, 390, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderJothan" ), new Point3D( 7056, 383, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderJothan" ), new Point3D( 7056, 383, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "ElderAlethanian" ), new Point3D( 7056, 380, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "ElderAlethanian" ), new Point3D( 7056, 380, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Rebinil" ), new Point3D( 7089, 380, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Rebinil" ), new Point3D( 7089, 380, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Aluniol" ), new Point3D( 7089, 383, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Aluniol" ), new Point3D( 7089, 383, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Olaeni" ), new Point3D( 7080, 363, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Olaeni" ), new Point3D( 7080, 363, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Bolaevin" ), new Point3D( 7066, 351, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Bolaevin" ), new Point3D( 7066, 351, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "LorekeeperAneen" ), new Point3D( 7053, 337, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "LorekeeperAneen" ), new Point3D( 7053, 337, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Daelas" ), new Point3D( 7036, 412, 7 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Daelas" ), new Point3D( 7036, 412, 7 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Alelle" ), new Point3D( 7028, 406, 7 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Alelle" ), new Point3D( 7028, 406, 7 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "LorekeeperNillaen" ), new Point3D( 7061, 370, 14 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "LorekeeperNillaen" ), new Point3D( 7061, 370, 14 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "LorekeeperRyal" ), new Point3D( 7009, 375, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "LorekeeperRyal" ), new Point3D( 7009, 375, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Braen" ), new Point3D( 7081, 366, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Braen" ), new Point3D( 7081, 366, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderAcob" ), new Point3D( 7037, 387, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "ElderAcob" ), new Point3D( 7037, 387, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "LorekeeperCalendor" ), new Point3D( 7062, 370, 14 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "LorekeeperCalendor" ), new Point3D( 7062, 370, 14 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "LorekeeperSiarra" ), new Point3D( 7051, 339, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "LorekeeperSiarra" ), new Point3D( 7051, 339, 0 ), Map.Felucca ); - } - } - - public class TheyllEatAnything : MLQuest - { - public TheyllEatAnything() - { - Activated = true; - Title = 1072248; // They'll Eat Anything - Description = 1072262; // Pork is the fruit of the land! You can barbeque it, boil it, bake it, sautee it. There's pork kebabs, pork creole, pork gumbo, pan fried, deep fried, stir fried. There's apple pork, peppered pork, pork soup, pork salad, pork and potatoes, pork burger, pork sandwich, pork stew, pork chops, pork loins, shredded pork. So, lets get some piggies butchered! - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Pig ) }, "pigs" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class NoGoodFishStealing : MLQuest - { - public NoGoodFishStealing() - { - Activated = true; - Title = 1072251; // No Good, Fish Stealing ... - Description = 1072265; // Mighty creatures they are, aye. Fierce and strong, can't blame 'em for wanting to feed themselves an' all. Blame or no, they're eating all the fish up, so they got to go. Lend a hand? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Walrus ) }, "walruses" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class AHeroInTheMaking : MLQuest - { - public AHeroInTheMaking() - { - Activated = true; - Title = 1072246; // A Hero in the Making - Description = 1072257; // Are you new around here? Well, nevermind that. You look ready for adventure, I can see the gleam of glory in your eyes! Nothing is more valiant, more noble, more praiseworthy than mongbat slaying. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Mongbat ) }, "mongbats" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class BullfightingSortOf : MLQuest - { - public BullfightingSortOf() - { - Activated = true; - Title = 1072247; // Bullfighting ... Sort Of - Description = 1072254; // You there! Yes, you. Listen, I've got a little problem on my hands, but a brave, bold hero like yourself should find it a snap to solve. Bottom line -- we need some of the bulls in the area culled. You're welcome to any meat or hides, and of course, I'll give you a nice reward. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Bull ) }, "bulls" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class AFineFeast : MLQuest - { - public AFineFeast() - { - Activated = true; - Title = 1072243; // A Fine Feast. - Description = 1072261; // Mmm, I do love mutton! It's slaughtering time again and my usual hirelings haven't turned up. I've arranged for a butcher to come by and cut everything up but the basic sheep killing part I haven't gotten worked out yet. Are you up for the task? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Sheep ) }, "sheep" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class ForcedMigration : MLQuest - { - public ForcedMigration() - { - Activated = true; - Title = 1072250; // Forced Migration - Description = 1072264; // Chirp chirp ... tweet chirp. Tra la la. Bloody birds and their blasted noise. I've tried everything but they just won't stop that infernal clamor. Return me to blessed silence and I'll make it worth your while. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Bird ) }, "birds" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class FilthyPests : MLQuest - { - public FilthyPests() - { - Activated = true; - Title = 1072242; // Filthy Pests! - Description = 1072253; // They're everywhere I tell you! They crawl in the walls, they scurry in the bushes. Disgusting critters. Say ... I don't suppose you're up for some sewer rat killing? Sewer rats now, not any other kind of squeaker will do. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( SewerRat ) }, "sewer rats" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class DeadManWalking : MLQuest - { - public DeadManWalking() - { - Activated = true; - Title = 1072983; // Dead Man Walking - Description = 1073009; // Why? I ask you why? They walk around after they're put in the ground. It's just wrong in so many ways. Put them to proper rest, I beg you. I'll find some way to pay you for the kindness. Just kill five zombies and five skeletons. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 5, new[] { typeof( Zombie ) }, "zombies" ) ); - Objectives.Add( new KillObjective( 5, new[] { typeof( Skeleton ) }, "skeletons" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class KingOfBears : MLQuest - { - public KingOfBears() - { - Activated = true; - Title = 1072996; // King of Bears - Description = 1073030; // A pity really. With the balance of nature awry, we have no choice but to accept the responsibility of making it all right. It's all a part of the circle of life, after all. So, yes, the grizzly bears are running rampant. There are far too many in the region. Will you shoulder your obligations as a higher life form? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( GrizzlyBear ) }, "grizzly bears" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class Specimens : MLQuest - { - public Specimens() - { - Activated = true; - Title = 1072999; // Specimens - Description = 1073032; // I admire them, you know. The solen have their place -- regimented, organized. They're fascinating to watch with their constant strife between red and black. I can't help but want to stir things up from time to time. And that's where you come in. Kill either twelve red or twelve black solen workers and let's see what happens next! - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - ObjectiveType = ObjectiveType.Any; - - Objectives.Add( new KillObjective( 12, new[] { typeof( RedSolenWorker ) }, "red solen workers" ) ); - Objectives.Add( new KillObjective( 12, new[] { typeof( BlackSolenWorker ) }, "black solen workers" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class Spirits : MLQuest - { - public Spirits() - { - Activated = true; - Title = 1073076; // Spirits - Description = 1073566; // It is a piteous thing when the dead continue to walk the earth. Restless spirits are known to inhabit these parts, taking the lives of unwary travelers. It is about time a hero put the dead back in their graves. I'm sure such a hero would be justly rewarded. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073586; // The restless spirts still walk -- you must kill 15 of them. - - Objectives.Add( new KillObjective( 15, new[] { typeof( Spectre ), typeof( Shade ), typeof( Wraith ) }, "spectres or shades or wraiths" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class RollTheBones : MLQuest - { - public RollTheBones() - { - Activated = true; - Title = 1073002; // Roll the Bones - Description = 1073011; // Why? I ask you why? They walk around after they're put in the ground. It's just wrong in so many ways. Put them to proper rest, I beg you. I'll find some way to pay you for the kindness. Just kill eight patchwork skeletons. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 8, new[] { typeof( PatchworkSkeleton ) }, "patchwork skeletons" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class ItsAGhastlyJob : MLQuest - { - public ItsAGhastlyJob() - { - Activated = true; - Title = 1073008; // It's a Ghastly Job - Description = 1073012; // Why? I ask you why? They walk around after they're put in the ground. It's just wrong in so many ways. Put them to proper rest, I beg you. I'll find some way to pay you for the kindness. Just kill twelve ghouls. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 12, new[] { typeof( Ghoul ) }, "ghouls" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class Troglodytes : MLQuest - { - public Troglodytes() - { - Activated = true; - Title = 1074688; // Troglodytes! - Description = 1074689; // Oh nevermind, you don't look capable of my task afterall. Haha! What was I thinking - you could never handle killing troglodytes. It'd be suicide. What? I don't know, I don't want to be responsible ... well okay if you're really sure? - RefusalMessage = 1074690; // Probably the wiser course of action. - InProgressMessage = 1074691; // You still need to kill those troglodytes, remember? - - Objectives.Add( new KillObjective( 12, new[] { typeof( Troglodyte ) }, "troglodytes" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class UnholyKnights : MLQuest - { - public UnholyKnights() - { - Activated = true; - Title = 1073075; // Unholy Knights - Description = 1073565; // Please, hear me kind traveler. You know when a knight falls, sometimes they are cursed to roam the earth as undead mockeries of their former glory? That is too grim a fate for even any knight to suffer! Please, put them out of their misery. I will offer you what payment I can if you will end the torment of these undead wretches. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073585; // Your task is not done. Continue putting the Skeleton and Bone Knights to rest. - - Objectives.Add( new KillObjective( 16, new[] { typeof( BoneKnight ), typeof( SkeletalKnight ) }, "bone knights or skeletal knights" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class AFeatherInYerCap : MLQuest - { - public AFeatherInYerCap() - { - Activated = true; - Title = 1074738; // A Feather in Yer Cap - Description = 1074737; // I've seen how you strut about, as if you were something special. I have some news for you, you don't impress me at all. It's not enough to have a fancy hat you know. That may impress people in the big city, but not here. If you want a reputation you have to climb a mountain, slay some great beast, and then write about it. Trust me, it's a long process. The first step is doing a great feat. If I were you, I'd go pluck a feather from the harpy Saliva, that would give you a good start. - RefusalMessage = 1074736; // The path to greatness isn't for everyone obviously. - InProgressMessage = 1074735; // If you're going to get anywhere in the adventuring game, you have to take some risks. A harpy, well, it's bad, but it's not a dragon. - CompletionMessage = 1074734; // The hero returns from the glorious battle and - oh, such a small feather? - - Objectives.Add( new CollectObjective( 1, typeof( SalivasFeather ), "Saliva's Feather" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ATaleOfTail : MLQuest - { - public ATaleOfTail() - { - Activated = true; - Title = 1074726; // A Tale of Tail - Description = 1074727; // I've heard of you, adventurer. Your reputation is impressive, and now I'll put it to the test. This is not something I ask lightly, for this task is fraught with danger, but it is vital. Seek out the vile hydra Abscess, slay it, and return to me with it's tail. - RefusalMessage = 1074728; // Well, the beast will still be there when you are ready I suppose. - InProgressMessage = 1074729; // Em, I thought I had explained already. Abscess, the hydra, you know? Lots of heads but just the one tail. I need the tail. I have my reasons. Go go go. - CompletionMessage = 1074730; // Ah, the tail. You did it! You know the rumours about dried ground hydra tail powder are all true? Thank you so much! - - Objectives.Add( new CollectObjective( 1, typeof( AbscessTail ), "Abscess' Tail" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ATrogAndHisDog : MLQuest - { - public ATrogAndHisDog() - { - Activated = true; - Title = 1074681; // A Trog and His Dog - Description = 1074680; // I don't know if you can handle it, but I'll give you a go at it. Troglodyte chief - name of Lurg and his mangy wolf pet need killing. Do the deed and I'll reward you. - RefusalMessage = 1074655; // Perhaps I thought too highly of you. - InProgressMessage = 1074682; // The trog chief and his mutt should be easy enough to find. Just kill them and report back. Easy enough. - CompletionMessage = 1074683; // Not half bad. Here's your prize. - - Objectives.Add( new KillObjective( 1, new[] { typeof( Lurg ) }, "Lurg" ) ); - Objectives.Add( new KillObjective( 1, new[] { typeof( Grobu ) }, "Grobu" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class Overpopulation : MLQuest - { - public Overpopulation() - { - Activated = true; - Title = 1072252; // Overpopulation - Description = 1072267; // I just can't bear it any longer. Sure, it's my job to thin the deer out so they don't overeat the area and starve themselves come winter time. Sure, I know we killed off the predators that would do this naturally so now we have to make up for it. But they're so graceful and innocent. I just can't do it. Will you? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Hind ) }, "hinds" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class WildBoarCull : MLQuest - { - public WildBoarCull() - { - Activated = true; - Title = 1072245; // Wild Boar Cull - Description = 1072260; // A pity really. With the balance of nature awry, we have no choice but to accept the responsibility of making it all right. It's all a part of the circle of life, after all. So, yes, the boars are running rampant. There are far too many in the region. Will you shoulder your obligations as a higher life form? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Boar ) }, "boars" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class ItsElemental : MLQuest - { - public ItsElemental() - { - Activated = true; - Title = 1073089; // It's Elemental - Description = 1073579; // The universe is all about balance my friend. Tip one end, you must balance the other. That's why I must ask you to kill not just one kind of elemental, but three kinds. Snuff out some Fire, douse a few Water, and crush some Earth elementals and I'll pay you for your trouble. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073599; // Four of each, that's all I ask. Water, earth and fire. - - Objectives.Add( new KillObjective( 4, new[] { typeof( FireElemental ) }, "fire elementals" ) ); - Objectives.Add( new KillObjective( 4, new[] { typeof( WaterElemental ) }, "water elementals" ) ); - Objectives.Add( new KillObjective( 4, new[] { typeof( EarthElemental ) }, "earth elementals" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class CircleOfLife : MLQuest - { - public CircleOfLife() - { - Activated = true; - Title = 1073656; // Circle of Life - Description = 1073695; // There's been a bumper crop of evil with the Bog Things in these parts, my friend. Though they are foul creatures, they are also most fecund. Slay one and you make the land more fertile. Even better, slay several and I will give you whatever coin I can spare. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073736; // Continue to seek and kill the Bog Things. - - Objectives.Add( new KillObjective( 8, new[] { typeof( BogThing ) }, "bog things" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class DustToDust : MLQuest - { - public DustToDust() - { - Activated = true; - Title = 1073074; // Dust to Dust - Description = 1073564; // You want to hear about trouble? I got trouble. How's angry piles of granite walking around for trouble? Maybe they don't like the mining, maybe it's the farming. I don't know. All I know is someone's got to turn them back to potting soil. And it'd be worth a pretty penny to the soul that does it. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073584; // You got rocks in your head? I said to kill 12 earth elementals, okay? - - Objectives.Add( new KillObjective( 12, new[] { typeof( EarthElemental ) }, "earth elementals" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class CreepyCrawlies : MLQuest - { - public CreepyCrawlies() - { - Activated = true; - Title = 1072987; // Creepy Crawlies - Description = 1073016; // Disgusting! The way they scuttle on those hairy legs just makes me want to gag. I hate spiders! Rid the world of twelve and I'll find something nice to give you in thanks. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 12, new[] { typeof( GiantSpider ) }, "giant spiders" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class VoraciousPlants : MLQuest - { - public VoraciousPlants() - { - Activated = true; - Title = 1073001; // Voracious Plants - Description = 1073024; // I bet you can't tangle with those nasty plants ... say eight corpsers and two swamp tentacles! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 8, new[] { typeof( Corpser ) }, "corpsers" ) ); - Objectives.Add( new KillObjective( 2, new[] { typeof( SwampTentacle ) }, "swamp tentacles" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class GibberJabber : MLQuest - { - public GibberJabber() - { - Activated = true; - Title = 1073004; // Gibber Jabber - Description = 1073024; // I bet you can't kill ... ten gibberlings! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Gibberling ) }, "gibberlings" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class AnimatedMonstrosity : MLQuest - { - public AnimatedMonstrosity() - { - Activated = true; - Title = 1072990; // Animated Monstrosity - Description = 1073020; // I bet you can't kill ... say twelve ... flesh golems! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 12, new[] { typeof( FleshGolem ) }, "flesh golems" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class BirdsOfAFeather : MLQuest - { - public BirdsOfAFeather() - { - Activated = true; - Title = 1073007; // Birds of a Feather - Description = 1073022; // I bet you can't kill ... ten harpies! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Harpy ) }, "harpies" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class Frightmares : MLQuest - { - public Frightmares() - { - Activated = true; - Title = 1073000; // Frightmares - Description = 1073036; // I bet you can't handle ten plague spawns! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( PlagueSpawn ) }, "plague spawns" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class MoltenReptiles : MLQuest - { - public MoltenReptiles() - { - Activated = true; - Title = 1072989; // Molten Reptiles - Description = 1073018; // I bet you can't kill ... say ten ... lava lizards! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( LavaLizard ) }, "lava lizards" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class BloodyNuisance : MLQuest - { - public BloodyNuisance() - { - Activated = true; - Title = 1072992; // Bloody Nuisance - Description = 1073021; // I bet you can't kill ... ten gore fiends! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( GoreFiend ) }, "gore fiends" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class BloodSuckers : MLQuest - { - public BloodSuckers() - { - Activated = true; - Title = 1072997; // Blood Suckers - Description = 1073025; // I bet you can't tangle with those bloodsuckers ... say around ten vampire bats! I bet they're too much for you. You may as well confess you can't ... - RefusalMessage = 1073019; // Hahahaha! I knew it! - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( VampireBat ) }, "vampire bats" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class TheAfterlife : MLQuest - { - public TheAfterlife() - { - Activated = true; - Title = 1073073; // The Afterlife - Description = 1073563; // Nobody told me about the Mummy's Curse. How was I supposed to know you shouldn't disturb the tombs? Oh, sure, now all I hear about is the curse of the vengeful dead. I'll tell you what - make a few of these mummies go away and we'll keep this between you and me. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073583; // Uh, I don't think you're quite done killing Mummies yet. - - Objectives.Add( new KillObjective( 15, new[] { typeof( Mummy ) }, "mummies" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ForkedTongue : MLQuest - { - public ForkedTongue() - { - Activated = true; - Title = 1073655; // Forked Tongue - Description = 1073694; // I must implore you, brave traveler, to do battle with the vile reptiles which haunt these parts. Those hideous abominations, the Ophidians, are a blight across the land. If you were able to put down a host of the scaly warriors, the Knights or the Avengers, I would forever be in your debt. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073735; // Have you killed the Ophidian Knights or Avengers? - - Objectives.Add( new KillObjective( 10, new[] { typeof( OphidianKnight ) }, "ophidian avengers or ophidian knight-errants" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class ImpishDelights : MLQuest - { - public ImpishDelights() - { - Activated = true; - Title = 1073077; // Impish Delights - Description = 1073567; // Imps! Do you hear me? Imps! They're everywhere! They're in everything! Oh, don't be fooled by their size - they vicious little devils! Half-sized evil incarnate, they are! Somebody needs to send them back to where they came from, if you know what I mean. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073587; // Don't let the little devils scare you! You kill 12 imps - then we'll talk reward. - - Objectives.Add( new KillObjective( 12, new[] { typeof( Imp ) }, "imps" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ThreeWishes : MLQuest - { - public ThreeWishes() - { - Activated = true; - Title = 1073660; // Three Wishes - Description = 1073699; // If I had but one wish, it would be to rid myself of these dread Efreet! Fire and ash, they are cunning and deadly! You look a brave soul - would you be interested in earning a rich reward for slaughtering a few of the smoky devils? - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073740; // Those smoky devils, the Efreets, are still about. - - Objectives.Add( new KillObjective( 8, new[] { typeof( Efreet ) }, "efreets" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class EvilEye : MLQuest - { - public EvilEye() - { - Activated = true; - Title = 1073084; // Evil Eye - Description = 1073574; // Kind traveler, hear my plea. You know of the evil orbs? The wrathful eyes? Some call them gazers? They must be a nest nearby, for they are tormenting us poor folk. We need to drive back their numbers. But we are not strong enough to face such horrors ourselves, we need a true hero. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073594; // Have you annihilated a dozen Gazers yet, kind traveler? - - Objectives.Add( new KillObjective( 12, new[] { typeof( Gazer ) }, "gazers" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class GargoylesWrath : MLQuest - { - public GargoylesWrath() - { - Activated = true; - Title = 1073658; // Gargoyle's Wrath - Description = 1073697; // It is regretable that the Gargoyles insist upon warring with us. Their Enforcers attack men on sight, despite all efforts at reason. To help maintain order in this region, I have been authorized to encourage bounty hunters to reduce their numbers. Eradicate their number and I will reward you handsomely. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073738; // I won't be able to pay you until you've gotten enough Gargoyle Enforcers. - - Objectives.Add( new KillObjective( 6, new[] { typeof( GargoyleEnforcer ) }, "gargoyle enforcers" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class UndeadMages : MLQuest - { - public UndeadMages() - { - Activated = true; - Title = 1073080; // Undead Mages - Description = 1073570; // Why must the dead plague the living? With their foul necromancy and dark sorceries, the undead menace the countryside. I fear what will happen if no one is strong enough to face these nightmare sorcerers and thin their numbers. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073590; // Surely, a brave soul like yourself can kill 10 Bone Magi and Skeletal Mages? - - Objectives.Add( new KillObjective( 10, new[] { typeof( BoneMagi ), typeof( SkeletalMage ) }, "bone mages or skeletal mages" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class FriendlyNeighborhoodSpiderkiller : MLQuest - { - public FriendlyNeighborhoodSpiderkiller() - { - Activated = true; - Title = 1073662; // Friendly Neighborhood Spider-killer - Description = 1073701; // They aren't called Dread Spiders because they're fluffy and cuddly now, are they? No, there's nothing appealing about those wretches so I sure wouldn't lose any sleep if you were to exterminate a few. I'd even part with a generous amount of gold, I would. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073742; // Dread Spiders? I say keep exterminating the arachnid vermin. - - Objectives.Add( new KillObjective( 8, new[] { typeof( DreadSpider ) }, "dread spiders" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class MongbatMenace : MLQuest - { - public MongbatMenace() - { - Activated = true; - Title = 1073003; // Mongbat Menace! - Description = 1073033; // I imagine you don't know about the mongbats. Well, you may think you do, but I know more than just about anyone. You see they come in two varieties ... the stronger and the weaker. Either way, they're a menace. Exterminate ten of the weaker ones and four of the stronger and I'll pay you an honest wage. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Mongbat ) }, "mongbats" ) ); - Objectives.Add( new KillObjective( 4, new[] { typeof( GreaterMongbat ) }, "greater mongbats" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class StirringTheNest : MLQuest - { - public StirringTheNest() - { - Activated = true; - Title = 1073087; // Stirring the Nest - Description = 1073577; // Were you the sort of child that enjoyed knocking over anthills? Well, perhaps you'd like to try something a little bigger? There's a Solen nest nearby and I bet if you killed a queen or two, it would be quite the sight to behold. I'd even pay to see that - what do you say? - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073597; // Dead Solen Queens isn't too much to ask, is it? - - ObjectiveType = ObjectiveType.Any; - - Objectives.Add( new KillObjective( 3, new[] { typeof( RedSolenQueen ) }, "red solen queens" ) ); - Objectives.Add( new KillObjective( 3, new[] { typeof( BlackSolenQueen ) }, "black solen queens" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class WarriorCaste : MLQuest - { - public WarriorCaste() - { - Activated = true; - Title = 1073078; // Warrior Caste - Description = 1073568; // The Terathan are an aggressive species. Left unchecked, they will swarm across our lands. And where will that leave us? Compost in the hive, that's what! Stop them, stop them cold my friend. Kill their warriors and you'll check their movement, that is certain. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073588; // Unless you kill at least 10 Terathan Warriors, you won't have any impact on their hive. - - Objectives.Add( new KillObjective( 10, new[] { typeof( TerathanWarrior ) }, "terathan warriors" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class BigWorms : MLQuest - { - public BigWorms() - { - Activated = true; - Title = 1073088; // Big Worms - Description = 1073578; // It makes no sense! Cold blooded serpents cannot live in the ice! It's a biological impossibility! They are an abomination against reason! Please, I beg you - kill them! Make them disappear for me! Do this and I will reward you. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073598; // You wouldn't try and just pretend you murdered 10 Giant Ice Worms, would you? - - Objectives.Add( new KillObjective( 10, new[] { typeof( IceSerpent ) }, "giant ice serpents" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class OrcishElite : MLQuest - { - public OrcishElite() - { - Activated = true; - Title = 1073081; // Orcish Elite - Description = 1073571; // Foul brutes! No one loves an orc, but some of them are worse than the rest. Their Captains and their Bombers, for instance, they're the worst of the lot. Kill a few of those, and the rest are just a rabble. Exterminate a few of them and you'll make the world a sunnier place, don't you know. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073591; // The only good orc is a dead orc - and 4 dead Captains and 6 dead Bombers is even better! - - Objectives.Add( new KillObjective( 6, new[] { typeof( OrcBomber ) }, "orc bombers" ) ); - Objectives.Add( new KillObjective( 4, new[] { typeof( OrcCaptain ) }, "orc captain" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ThinningTheHerd : MLQuest - { - public ThinningTheHerd() - { - Activated = true; - Title = 1072249; // Thinning the Herd - Description = 1072263; // Psst! Hey ... psst! Listen, I need some help here but it's gotta be hush hush. I don't want THEM to know I'm onto them. They watch me. I've seen them, but they don't know that I know what I know. You know? Anyway, I need you to scare them off by killing a few of them. That'll send a clear message that I won't suffer goats watching me! - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Goat ) }, "goats" ) ); - - Rewards.Add( ItemReward.SmallBagOfTrinkets ); - } - } - - public class Squishy : MLQuest - { - public Squishy() - { - Activated = true; - Title = 1072998; // Squishy - Description = 1073031; // Have you ever seen what a slime can do to good gear? Well, it's not pretty, let me tell you! If you take on my task to destroy twelve of them, bear that in mind. They'll corrode your equipment faster than anything. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 12, new[] { typeof( Slime ) }, "slimes" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class OrcSlaying : MLQuest - { - public OrcSlaying() - { - Activated = true; - Title = 1072986; // Orc Slaying - Description = 1073015; // Those green-skinned freaks have run off with more of my livestock. I want an orc scout killed for each sheep I lost and an orc for each chicken. So that's four orc scouts and eight orcs I'll pay you to slay. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 8, new[] { typeof( Orc ) }, "orcs" ) ); - // TODO: This needs to be orc scouts but they aren't in the SVN - Objectives.Add( new KillObjective( 4, new[] { typeof( OrcishLord ) }, "orcish lords" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class ABigJob : MLQuest - { - public ABigJob() - { - Activated = true; - Title = 1072988; // A Big Job - Description = 1073017; // It's a big job but you look to be just the adventurer to do it! I'm so glad you came by ... I'm paying well for the death of five ogres and five ettins. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 5, new[] { typeof( Ogre ) }, "ogres" ) ); - Objectives.Add( new KillObjective( 5, new[] { typeof( Ettin ) }, "ettins" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class TrollingForTrolls : MLQuest - { - public TrollingForTrolls() - { - Activated = true; - Title = 1072985; // Trolling for Trolls - Description = 1073014; // They may not be bright, but they're incredibly destructive. Kill off ten trolls and I'll consider it a favor done for me. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Troll ) }, "trolls" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class ColdHearted : MLQuest - { - public ColdHearted() - { - Activated = true; - Title = 1072991; // Cold Hearted - Description = 1073027; // It's a big job but you look to be just the adventurer to do it! I'm so glad you came by ... I'm paying well for the death of six giant ice serpents and six frost spiders. Hop to it, if you're so inclined. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 6, new[] { typeof( IceSerpent ) }, "giant ice serpents" ) ); - Objectives.Add( new KillObjective( 6, new[] { typeof( FrostSpider ) }, "frost spiders" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class ForkedTongues : MLQuest - { - public ForkedTongues() - { - Activated = true; - Title = 1072984; // Forked Tongues - Description = 1073013; // You can't trust them, you know. Lizardmen I mean. They have forked tongues ... and you know what that means. Exterminate ten of them and I'll reward you. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Lizardman ) }, "lizardmen" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class ShakingThingsUp : MLQuest - { - public ShakingThingsUp() - { - Activated = true; - Title = 1073083; // Shaking Things Up - Description = 1073573; // A Solen hive is a fascinating piece of ecology. It's put together like a finely crafted clock. Who knows what happens if you remove something? So let's find out. Exterminate a few of the warriors and I'll make it worth your while. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073593; // I don't think you've gotten their attention yet -- you need to kill at least 10 Solen Warriors. - - ObjectiveType = ObjectiveType.Any; - - Objectives.Add( new KillObjective( 10, new[] { typeof( RedSolenWarrior ) }, "red solen warriors" ) ); - Objectives.Add( new KillObjective( 10, new[] { typeof( BlackSolenWarrior ) }, "black solen warriors" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class Arachnophobia : MLQuest - { - public Arachnophobia() - { - Activated = true; - Title = 1073079; // Arachnophobia - Description = 1073569; // I've seen them hiding in their webs among the woods. Glassy eyes, spindly legs, poisonous fangs. Monsters, I say! Deadly horrors, these black widows. Someone must exterminate the abominations! If only I could find a worthy hero for such a task, then I could give them this considerable reward. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073589; // You've got a good start, but to stop the black-eyed fiends, you need to kill a dozen. - - Objectives.Add( new KillObjective( 12, new[] { typeof( GiantBlackWidow ) }, "giant black widows" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class MiniSwampThing : MLQuest - { - public MiniSwampThing() - { - Activated = true; - Title = 1073072; // Mini Swamp Thing - Description = 1073562; // Some say killing a boggling brings good luck. I don't place much stock in old wives' tales, but I can say a few dead bogglings would certainly be lucky for me! Help me out and I can reward you for your efforts. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073582; // Go back and kill all 20 bogglings! - - Objectives.Add( new KillObjective( 12, new[] { typeof( Bogling ) }, "boglings" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ThePerilsOfFarming : MLQuest - { - public ThePerilsOfFarming() - { - Activated = true; - Title = 1073664; // The Perils of Farming - Description = 1073703; // I should be trimming back the vegetation here, but something nasty has taken root. Viscious vines I can't go near. If there's any hope of getting things under control, some one's going to need to destroy a few of those Whipping Vines. Someone strong and fast and tough. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073744; // How are farmers supposed to work with these Whipping Vines around? - - Objectives.Add( new KillObjective( 15, new[] { typeof( WhippingVine ) }, "whipping vines" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class IndustriousAsAnAntLion : MLQuest - { - public IndustriousAsAnAntLion() - { - Activated = true; - Title = 1073665; // Industrious as an Ant Lion - Description = 1073704; // Ants are industrious and Lions are noble so who'd think an Ant Lion would be such a problem? The Ant Lion's have been causing mindless destruction in these parts. I suppose it's just how ants are. But I need you to help eliminate the infestation. Would you be willing to help for a bit of reward? - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073745; // Please, rid us of the Ant Lion infestation. - - Objectives.Add( new KillObjective( 12, new[] { typeof( AntLion ) }, "ant lions" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class UnholyConstruct : MLQuest - { - public UnholyConstruct() - { - Activated = true; - Title = 1073666; // Unholy Construct - Description = 1073705; // They're unholy, I say. Golems, a walking mockery of all life, born of blackest magic. They're not truly alive, so destroying them isn't a crime, it's a service. A service I will gladly pay for. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073746; // The unholy brutes, the Golems, must be smited! - CompletionMessage = 1073787; // Reduced those Golems to component parts? Good, then -- you deserve this reward! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Golem ) }, "golems" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class AChillInTheAir : MLQuest - { - public AChillInTheAir() - { - Activated = true; - Title = 1073663; // A Chill in the Air - Description = 1073702; // Feel that chill in the air? It means an icy death for the unwary, for deadly Ice Elementals are about. Who knows what magic summoned them, what's important now is getting rid of them. I don't have much, but I'll give all I can if you'd only stop the cold-hearted monsters. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073746; // The chill won't lift until you eradicate a few Ice Elemenals. - - Objectives.Add( new KillObjective( 15, new[] { typeof( IceElemental ) }, "ice elementals" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class TheKingOfClothing : MLQuest - { - public TheKingOfClothing() - { - Activated = true; - HasRestartDelay = true; - Title = 1073902; // The King of Clothing - Description = 1074092; // I have heard noble tales of a fine and proud human garment. An article of clothing fit for both man and god alike. It is called a "kilt" I believe? Could you fetch for me some of these kilts so I that I might revel in their majesty and glory? - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073948; // I will be in your debt if you bring me kilts. - CompletionMessage = 1073974; // I say truly - that is a magnificent garment! You have more than earned a reward. - - Objectives.Add( new CollectObjective( 10, typeof( Kilt ), 1025431 ) ); // kilt - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class ThePuffyShirt : MLQuest - { - public ThePuffyShirt() - { - Activated = true; - HasRestartDelay = true; - Title = 1073903; // The Puffy Shirt - Description = 1074093; // We elves believe that beauty is expressed in all things, including the garments we wear. I wish to understand more about human aesthetics, so please kind traveler - could you bring to me magnificent examples of human fancy shirts? For my thanks, I could teach you more about the beauty of elven vestements. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073949; // I will be in your debt if you bring me fancy shirts. - CompletionMessage = 1073973; // I appreciate your service. Now, see what elven hands can create. - - Objectives.Add( new CollectObjective( 10, typeof( FancyShirt ), 1027933 ) ); // fancy shirt - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class FromTheGaultierCollection : MLQuest - { - public FromTheGaultierCollection() - { - Activated = true; - HasRestartDelay = true; - Title = 1073905; // From the Gaultier Collection - Description = 1074095; // It is my understanding, the females of humankind actually wear on certain occasions a studded bustier? This is not simply a fanciful tale? Remarkable! It sounds hideously uncomfortable as well as ludicrously impracticle. But perhaps, I simply do not understand the nuances of human clothing. Perhaps, I need to see such a studded bustier for myself? - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073951; // I will be in your debt if you bring me studded bustiers. - CompletionMessage = 1073976; // Truly, it is worse than I feared. Still, I appreciate your efforts on my behalf. - - Objectives.Add( new CollectObjective( 10, typeof( StuddedBustierArms ), 1027180 ) ); // studded bustier - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class HauteCouture : MLQuest - { - public HauteCouture() - { - Activated = true; - HasRestartDelay = true; - Title = 1073901; // Hâute Couture - Description = 1074091; // Most human apparel is interesting to elven eyes. But there is one garment - the flower garland - which sounds very elven indeed. Could I see how a human crafts such an object of beauty? In exchange, I could share with you the wonders of elven garments. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073947; // I will be in your debt if you bring me flower garlands. - CompletionMessage = 1073973; // I appreciate your service. Now, see what elven hands can create. - - Objectives.Add( new CollectObjective( 10, typeof( FlowerGarland ), 1028965 ) ); // flower garland - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class TheSongOfTheWind : MLQuest - { - public TheSongOfTheWind() - { - Activated = true; - HasRestartDelay = true; - Title = 1073910; // The Song of the Wind - Description = 1074100; // To give voice to the passing wind, this is an idea worthy of an elf! Friend, bring me some of the amazing fancy wind chimes so that I may listen to the song of the passing breeze. Do this, and I will share with you treasured elven secrets. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073956; // I will be in your debt if you bring me fancy wind chimes. - CompletionMessage = 1073980; // Such a delightful sound, I think I shall never tire of it. - - Objectives.Add( new CollectObjective( 10, typeof( FancyWindChimes ), "fancy wind chimes" ) ); - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class BeerGoggles : MLQuest - { - public BeerGoggles() - { - Activated = true; - HasRestartDelay = true; - Title = 1073895; // Beer Goggles - Description = 1074085; // Oh, the deviltry! Why would humans lock their precious liquors inside a wooden coffin? I understand I need a "keg tap" to access the golden brew within such a wooden abomination. Perhaps, if you could bring me such a tap, we could share a drink and I could teach you. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073941; // I will be in your debt if you bring me barrel taps. - CompletionMessage = 1073971; // My thanks for your service. Here is something for you to enjoy. - - Objectives.Add( new CollectObjective( 25, typeof( BarrelTap ), 1024100 ) ); // barrel tap - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class MessageInABottleQuest : MLQuest - { - public MessageInABottleQuest() - { - Activated = true; - HasRestartDelay = true; - Title = 1073894; // Message in a Bottle - Description = 1074084; // We elves are interested in trading our wines with humans but we understand human usually trade such brew in strange transparent bottles. If you could provide some of these empty glass bottles, I might engage in a bit of elven winemaking. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073940; // I will be in your debt if you bring me empty bottles. - CompletionMessage = 1073971; // My thanks for your service. Here is something for you to enjoy. - - Objectives.Add( new CollectObjective( 50, typeof( Bottle ), 1023854 ) ); // empty bottle - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class NecessitysMother : MLQuest - { - public NecessitysMother() - { - Activated = true; - HasRestartDelay = true; - Title = 1073906; // Necessity's Mother - Description = 1074096; // What a thing, this human need to tinker. It seems there is no end to what might be produced with a set of Tinker's Tools. Who knows what an elf might build with some? Could you obtain some tinker's tools and bring them to me? In exchange, I offer you elven lore and knowledge. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073952; // I will be in your debt if you bring me tinker's tools. - CompletionMessage = 1073977; // Now, I shall see what an elf can invent! - - Objectives.Add( new CollectObjective( 10, typeof( TinkerTools ), 1027868 ) ); // tinker's tools - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class TickTock : MLQuest - { - public TickTock() - { - Activated = true; - HasRestartDelay = true; - Title = 1073907; // Tick Tock - Description = 1074097; // Elves find it remarkable the human preoccupation with the passage of time. To have built instruments to try and capture time -- it is a fascinating notion. I would like to see how a clock is put together. Maybe you could provide some clocks for my experimentation? - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073953; // I will be in your debt if you bring me clocks. - CompletionMessage = 1073978; // Enjoy my thanks for your service. - - Objectives.Add( new CollectObjective( 10, typeof( Clock ), 1024171 ) ); // clock - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class ReptilianDentist : MLQuest - { - public ReptilianDentist() - { - Activated = true; - Title = 1074280; // Reptilian Dentist - Description = 1074710; // I'm working on a striking necklace -- something really unique -- and I know just what I need to finish it up. A huge fang! Won't that catch the eye? I would like to employ you to find me such an item, perhaps a snake would make the ideal donor. I'll make it worth your while, of course. - RefusalMessage = 1074723; // I understand. I don't like snakes much either. They're so creepy. - InProgressMessage = 1074722; // Those really big snakes like swamps, I've heard. You might try the blighted grove. - CompletionMessage = 1074721; // Do you have it? *gasp* What a tooth! Here � I must get right to work. - - Objectives.Add( new CollectObjective( 1, typeof( CoilsFang ), "coil's fang" ) ); - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class StopHarpingOnMe : MLQuest - { - public StopHarpingOnMe() - { - Activated = true; - HasRestartDelay = true; - Title = 1073881; // Stop Harping on Me - Description = 1074071; // Humans artistry can be a remarkable thing. For instance, I have heard of a wonderful instrument which creates the most melodious of music. A lap harp. I would be ever so grateful if I could examine one in person. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073927; // I will be in your debt if you bring me lap harp. - CompletionMessage = 1073969; // My thanks for your service. Now, I will show you something of elven carpentry. - - Objectives.Add( new CollectObjective( 20, typeof( LapHarp ), 1023762 ) ); // lap harp - - Rewards.Add( ItemReward.CarpentrySatchel ); - } - } - - public class TheFarEye : MLQuest - { - public TheFarEye() - { - Activated = true; - HasRestartDelay = true; - Title = 1073908; // The Far Eye - Description = 1074098; // The wonders of human invention! Turning sand and metal into a far-seeing eye! This is something I must experience for myself. Bring me some of these spyglasses friend human. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073954; // I will be in your debt if you bring me spyglasses. - CompletionMessage = 1073978; // Enjoy my thanks for your service. - - Objectives.Add( new CollectObjective( 20, typeof( Spyglass ), 1025365 ) ); // spyglass - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class LethalDarts : MLQuest - { - public LethalDarts() - { - Activated = true; - HasRestartDelay = true; - Title = 1073876; // Lethal Darts - Description = 1074066; // We elves are no strangers to archery but I would be interested in learning whether there is anything to learn from the human approach. I would gladly trade you something I have if you could teach me of the deadly crossbow bolt. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073922; // I will be in your debt if you bring me crossbow bolts. - CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. - CompletionNotice = CompletionNoticeCraft; - - Objectives.Add( new CollectObjective( 10, typeof( Bolt ), 1027163 ) ); // crossbow bolt - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class ASimpleBow : MLQuest - { - public ASimpleBow() - { - Activated = true; - HasRestartDelay = true; - Title = 1073877; // A Simple Bow - Description = 1074067; // I wish to try a bow crafted in the human style. Is it possible for you to bring me such a weapon? I would be happy to return this favor. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073923; // I will be in your debt if you bring me bows. - CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. - CompletionNotice = CompletionNoticeCraft; - - Objectives.Add( new CollectObjective( 10, typeof( Bow ), 1025041 ) ); // bow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class IngeniousArcheryPartOne : MLQuest - { - public IngeniousArcheryPartOne() - { - Activated = true; - HasRestartDelay = true; - Title = 1073878; // Ingenious Archery, Part I - Description = 1074068; // I have heard of a curious type of bow, you call it a "crossbow". It sounds fascinating and I would very much like to examine one closely. Would you be able to obtain such an instrument for me? - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073924; // I will be in your debt if you bring me crossbows. - CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. - CompletionNotice = CompletionNoticeCraft; - - Objectives.Add( new CollectObjective( 10, typeof( Crossbow ), 1023919 ) ); // crossbow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class IngeniousArcheryPartTwo : MLQuest - { - public IngeniousArcheryPartTwo() - { - Activated = true; - HasRestartDelay = true; - Title = 1073879; // Ingenious Archery, Part II - Description = 1074069; // These human "crossbows" are complex and clever. The "heavy crossbow" is a remarkable instrument of war. I am interested in seeing one up close, if you could arrange for one to make its way to my hands. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073925; // I will be in your debt if you bring me heavy crossbows. - CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. - CompletionNotice = CompletionNoticeCraft; - - Objectives.Add( new CollectObjective( 8, typeof( HeavyCrossbow ), 1025116 ) ); // heavy crossbow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class IngeniousArcheryPartThree : MLQuest - { - public IngeniousArcheryPartThree() - { - Activated = true; - HasRestartDelay = true; - Title = 1073880; // Ingenious Archery, Part III - Description = 1074070; // My friend, I am in search of a device, a instrument of remarkable human ingenuity. It is a repeating crossbow. If you were to obtain such a device, I would gladly reveal to you some of the secrets of elven craftsmanship. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073926; // I will be in your debt if you bring me repeating crossbows. - CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. - CompletionNotice = CompletionNoticeCraft; - - Objectives.Add( new CollectObjective( 10, typeof( RepeatingCrossbow ), 1029923 ) ); // repeating crossbow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class ScaleArmor : MLQuest - { - public ScaleArmor() - { - Activated = true; - Title = 1074711; // Scale Armor - Description = 1074712; // Here's what I need ... there are some creatures called hydra, fearsome beasts, whose scales are especially suitable for a new sort of armor that I'm developing. I need a few such pieces and then some supple alligator skin for the backing. I'm going to need a really large piece that's shaped just right ... the tail I think would do nicely. I appreciate your help. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1074724; // Hydras have been spotted in the Blighted Grove. You won't get those scales without getting your feet wet, I'm afraid. - CompletionMessage = 1074725; // I can't wait to get to work now that you've returned with my scales. - - Objectives.Add( new CollectObjective( 1, typeof( ThrashersTail ), "Thrasher's Tail" ) ); - Objectives.Add( new CollectObjective( 10, typeof( HydraScale ), "Hydra Scales" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class CutsBothWays : MLQuest - { - public CutsBothWays() - { - Activated = true; - HasRestartDelay = true; - Title = 1073913; // Cuts Both Ways - Description = 1074103; // What would you say is a typical human instrument of war? Is a broadsword a typical example? I wish to see more of such human weapons, so I would gladly trade elven knowledge for human steel. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073959; // I will be in your debt if you bring me broadswords. - CompletionMessage = 1073978; // Enjoy my thanks for your service. - - Objectives.Add( new CollectObjective( 12, typeof( Broadsword ), 1023934 ) ); // broadsword - - Rewards.Add( ItemReward.BlacksmithSatchel ); - } - } - - public class DragonProtection : MLQuest - { - public DragonProtection() - { - Activated = true; - HasRestartDelay = true; - Title = 1073915; // Dragon Protection - Description = 1074105; // Mankind, I am told, knows how to take the scales of a terrible dragon and forge them into powerful armor. Such a feat of craftsmanship! I would give anything to view such a creation - I would even teach some of the prize secrets of the elven people. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073961; // I will be in your debt if you bring me dragon armor. - CompletionMessage = 1073978; // Enjoy my thanks for your service. - - Objectives.Add( new CollectObjective( 10, typeof( DragonHelm ), 1029797 ) ); // dragon helm - - Rewards.Add( ItemReward.BlacksmithSatchel ); - } - } - - public class NothingFancy : MLQuest - { - public NothingFancy() - { - Activated = true; - HasRestartDelay = true; - Title = 1073911; // Nothing Fancy - Description = 1074101; // I am curious to see the results of human blacksmithing. To examine the care and quality of a simple item. Perhaps, a simple bascinet helmet? Yes, indeed -- if you could bring to me some bascinet helmets, I would demonstrate my gratitude. - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073957; // I will be in your debt if you bring me bascinets. - CompletionMessage = 1073978; // Enjoy my thanks for your service. - - Objectives.Add( new CollectObjective( 15, typeof( Bascinet ), 1025132 ) ); // bascinet - - Rewards.Add( ItemReward.BlacksmithSatchel ); - } - } - - public class TheBulwark : MLQuest - { - public TheBulwark() - { - Activated = true; - HasRestartDelay = true; - Title = 1073912; // The Bulwark - Description = 1074102; // The clank of human iron and steel is strange to elven ears. For instance, the metallic heater shield which human warriors carry into battle. It is odd to an elf, but nevertheless intriguing. Tell me friend, could you bring me such an example of human smithing skill? - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073958; // I will be in your debt if you bring me heater shields. - CompletionMessage = 1073978; // Enjoy my thanks for your service. - - Objectives.Add( new CollectObjective( 10, typeof( HeaterShield ), 1027030 ) ); // heater shield - - Rewards.Add( ItemReward.BlacksmithSatchel ); - } - } - - public class ArchSupport : MLQuest - { - public ArchSupport() - { - Activated = true; - HasRestartDelay = true; - Title = 1073882; // Arch Support - Description = 1074072; // How clever humans are - to understand the need of feet to rest from time to time! Imagine creating a special stool just for weary toes. I would like to examine and learn the secret of their making. Would you bring me some foot stools to examine? - RefusalMessage = 1073921; // I will patiently await your reconsideration. - InProgressMessage = 1073928; // I will be in your debt if you bring me foot stools. - CompletionMessage = 1073969; // My thanks for your service. Now, I will show you something of elven carpentry. - - Objectives.Add( new CollectObjective( 10, typeof( FootStool ), 1022910 ) ); // foot stool - - Rewards.Add( ItemReward.CarpentrySatchel ); - } - } - - public class ParoxysmusSuccubi : MLQuest - { - public ParoxysmusSuccubi() - { - Activated = true; - Title = 1073067; // Paroxysmus' Succubi - Description = 1074696; // The succubi that have congregated within the sinkhole to worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 3, new[] { typeof( Succubus ) }, "succubi", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class ParoxysmusMoloch : MLQuest - { - public ParoxysmusMoloch() - { - Activated = true; - Title = 1073068; // Paroxysmus' Moloch - Description = 1074695; // The moloch daemons that have congregated to worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 3, new[] { typeof( Moloch ) }, "molochs", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class ParoxysmusDaemons : MLQuest - { - public ParoxysmusDaemons() - { - Activated = true; - Title = 1073069; // Paroxysmus' Daemons - Description = 1074694; // The daemons that have congregated to worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Daemon ) }, "daemons", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class ParoxysmusArcaneDaemons : MLQuest - { - public ParoxysmusArcaneDaemons() - { - Activated = true; - Title = 1073070; // Paroxysmus' Arcane Daemons - Description = 1074697; // The arcane daemons that worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( ArcaneDaemon ) }, "arcane daemons", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class CausticCombo : MLQuest - { - public CausticCombo() - { - Activated = true; - Title = 1073062; // Caustic Combo - Description = 1074693; // Vile creatures have exited the sinkhole and begun terrorizing the surrounding area. The demons are bad enough, but the elementals are an abomination, their poisons seeping into the fertile ground here. Will you enter the sinkhole and put a stop to their depredations? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 3, new[] { typeof( PoisonElemental ) }, "poison elementals", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - Objectives.Add( new KillObjective( 6, new[] { typeof( AcidElemental ) }, "acid elementals", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class PlagueLord : MLQuest - { - public PlagueLord() - { - Activated = true; - Title = 1073061; // Plague Lord - Description = 1074692; // Some of the most horrific creatures have slithered out of the sinkhole there and begun terrorizing the surrounding area. The plague creatures are one of the most destruction of the minions of Paroxysmus. Are you willing to do something about them? - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 10, new[] { typeof( PlagueSpawn ) }, "plague spawns", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - Objectives.Add( new KillObjective( 3, new[] { typeof( PlagueBeast ) }, "plague beasts", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - Objectives.Add( new KillObjective( 1, new[] { typeof( PlagueBeastLord ) }, "plague beast lord", new QuestArea( 1074806, "The Palace of Paroxysmus" ) ) ); // The Palace of Paroxysmus - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class GlassyFoe : MLQuest - { - public GlassyFoe() - { - Activated = true; - Title = 1073055; // Glassy Foe - Description = 1074669; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal lattice seekers. - RefusalMessage = 1074671; // These abominations must not be permitted to fester! - InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. - CompletionMessage = 1074673; // You have done well. Enjoy this reward. - - Objectives.Add( new KillObjective( 5, new[] { typeof( CrystalLatticeSeeker ) }, "crystal lattice seekers", new QuestArea( 1074805, "The Prism of Light" ) ) ); // The Prism of Light - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class DaemonicPrism : MLQuest - { - public DaemonicPrism() - { - Activated = true; - Title = 1073053; // Daemonic Prism - Description = 1074668; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal daemons. - RefusalMessage = 1074671; // These abominations must not be permitted to fester! - InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. - CompletionMessage = 1074673; // You have done well. Enjoy this reward. - - Objectives.Add( new KillObjective( 3, new[] { typeof( CrystalDaemon ) }, "crystal daemons", new QuestArea( 1074805, "The Prism of Light" ) ) ); // The Prism of Light - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class Hailstorm : MLQuest - { - public Hailstorm() - { - Activated = true; - Title = 1073057; // Hailstorm - Description = 1074670; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal vortices. - RefusalMessage = 1074671; // These abominations must not be permitted to fester! - InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. - CompletionMessage = 1074673; // You have done well. Enjoy this reward. - - Objectives.Add( new KillObjective( 8, new[] { typeof( CrystalVortex ) }, "crystal vortices", new QuestArea( 1074805, "The Prism of Light" ) ) ); // The Prism of Light - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - /* TODO: Uncomment when Crystal Hydra is added - public class HowManyHeads : MLQuest - { - public HowManyHeads() - { - Activated = true; - Title = 1073050; // How Many Heads? - Description = 1074674; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal hydras. - RefusalMessage = 1074671; // These abominations must not be permitted to fester! - InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. - CompletionMessage = 1074673; // You have done well. Enjoy this reward. - - Objectives.Add( new KillObjective( 3, new Type[] { typeof( CrystalHydra ) }, "crystal hydras", new QuestArea( 1074805, "The Prism of Light" ) ) ); // The Prism of Light - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - */ - - /* TODO: Uncomment when Dreadhorn is added - public class DreadhornQuest : MLQuest - { - public DreadhornQuest() - { - Activated = true; - Title = 1074645; // Dreadhorn - Description = 1074646; // Can you comprehend it? I cannot, I confess. The most pristine and perfect Lord of Sosaria has fallen prey to the blight. From the depths of my heart I mourn his corruption; my thoughts are filled with pity for this glorious creature now tainted. And my blood boils with fury at those responsible for the innocent creature's undoing. Will you find Dread Horn, as he is now called, and free him from this misery? - RefusalMessage = 1074647; // How can you not feel as I do? - InProgressMessage = 1074648; // The lush and fertile land where Dread Horn now lives is twisted and tainted, a result of his corruption. The fey folk have sealed the land off through their magics, but you can enter through an enchanted mushroom fairy circle. - CompletionMessage = 1074649; // Thank you. I haven't the words to express my gratitude. - - Objectives.Add( new KillObjective( 1, new Type[] { typeof( DreadHorn ) }, "dread horn" ) ); - - Rewards.Add( ItemReward.RewardStrongbox ); - } - } - */ - - /* TODO: Uncomment when SerpentsFangHighExecutioner, TigersClawThief and DragonsFlameGrandMage are added - public class NewLeadership : MLQuest - { - public NewLeadership() - { - Activated = true; - Title = 1072905; // New Leadership - Description = 1072963; // I have a task for you ... adventurer. Will you risk all to win great renown? The Black Order is organized into three sects, each with their own speciality. The Dragon's Flame serves the will of the Grand Mage, the Tiger's Claw answers to the Master Thief, and the Serpent's Fang kills at the direction of the High Executioner. Slay all three and you will strike the order a devastating blow! - RefusalMessage = 1072973; // I do not fault your decision. - InProgressMessage = 1072974; // Once you gain entrance into The Citadel, you will need to move cautiously to find the sect leaders. - - Objectives.Add( new KillObjective( 1, new Type[] { typeof( SerpentsFangHighExecutioner ) }, "serpent's fang high executioner", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - Objectives.Add( new KillObjective( 1, new Type[] { typeof( TigersClawThief ) }, "tiger's claw thief", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - Objectives.Add( new KillObjective( 1, new Type[] { typeof( DragonsFlameGrandMage ) }, "dragon's flame mage", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - - Rewards.Add( ItemReward.RewardStrongbox ); - } - } - */ - - /* TODO: Uncomment when SerpentsFangAssassin is added - public class ExAssassins : MLQuest - { - public ExAssassins() - { - Activated = true; - Title = 1072917; // Ex-Assassins - Description = 1072969; // The Serpent's Fang sect members have gone too far! Express to them my displeasure by slaying ten of them. But remember, I do not condone war on women, so I will only accept the deaths of men, human and elf. - RefusalMessage = 1072979; // As you wish. - InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. - - // TODO: This has to be MALES only! - Objectives.Add( new KillObjective( 10, new Type[] { typeof( SerpentsFangAssassin ) }, "male serpent's fang assassins", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - */ - - /* TODO: Uncomment when DragonsFlameMage is added - public class ExtinguishingTheFlame : MLQuest - { - public ExtinguishingTheFlame() - { - Activated = true; - Title = 1072911; // Extinguishing the Flame - Description = 1072966; // The Dragon's Flame sect members have gone too far! Express to them my displeasure by slaying ten of them. But remember, I do not condone war on women, so I will only accept the deaths of men, human or elf. Either race will do, I care not for the shape of their ears. Yes, this action will properly make clear my disapproval and has a pleasing harmony. - RefusalMessage = 1072979; // As you wish. - InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. - - // TODO: This has to be MALES only! - Objectives.Add( new KillObjective( 10, new Type[] { typeof( DragonsFlameMage ) }, "male dragon's flame mages", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - */ - - public class DeathToTheNinja : MLQuest - { - public DeathToTheNinja() - { - Activated = true; - Title = 1072913; // Death to the Ninja! - Description = 1072966; // I wish to make a statement of censure against the elite ninjas of the Black Order. Deliver, in the strongest manner, my disdain. But do not make war on women, even those that take arms against you. It is not ... fitting. - RefusalMessage = 1072979; // As you wish. - InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. - - // TODO: Verify that this has to be males only (as per the description) - Objectives.Add( new KillObjective( 10, new[] { typeof( EliteNinja ) }, "elite ninjas", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - /* TODO: Uncomment when TigersClawThief is added - public class CrimeAndPunishment : MLQuest - { - public CrimeAndPunishment() - { - Activated = true; - Title = 1072914; // Crime and Punishment - Description = 1072968; // The Tiger's Claw sect members have gone too far! Express to them my displeasure by slaying ten of them. But remember, I do not condone war on women, so I will only accept the deaths of men, human and elf. - RefusalMessage = 1072979; // As you wish. - InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. - - // TODO: This has to be MALES only! - Objectives.Add( new KillObjective( 10, new Type[] { typeof( TigersClawThief ) }, "male tiger's claw thieves", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - */ - - /* TODO: Uncomment when ShimmeringEffusion is added - public class AllThatGlittersIsNotGood : MLQuest - { - public AllThatGlittersIsNotGood() - { - Activated = true; - Title = 1073048; // All That Glitters is Not Good - Description = 1074654; // The most incredible tale has reached my ears! Deep within the bowels of Sosaria, somewhere under the city of Nu'Jelm, a twisted creature feeds. What created this abomination, no one knows ... though there is some speculation that the fumbling initial efforts to open the portal to The Heartwood, brought it into existence. Regardless of it's origin, it must be destroyed before it damages Sosaria. Will you undertake this quest? - RefusalMessage = 1074655; // Perhaps I thought too highly of you. - InProgressMessage = 1074656; // An explorer discovered the cave system under Nu'Jelm. He made multiple trips into the place bringing back fascinating crystals and artifacts that suggested the hollow place in Sosaria was inhabited by other creatures at some point. You'll need to follow in his footsteps to find this abomination and destroy it. - CompletionMessage = 1074657; // I am overjoyed with your efforts! Your devotion to Sosaria is noted and appreciated. - - Objectives.Add( new KillObjective( 1, new Type[] { typeof( ShimmeringEffusion ) }, "shimmering effusion" ) ); - - Rewards.Add( ItemReward.RewardStrongbox ); - } - } - */ - - #endregion - - #region Mobiles - - [QuesterName( "Saril (The Heartwood)" )] - public class Saril : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Saril"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074186, // Come here, I have a task. - 1074183 // You there! I have a job for you. - ) ); - } - - [Constructible] - public Saril() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the guard"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new WoodlandLegs() ); - AddItem( new WoodlandArms() ); - AddItem( new WoodlandBelt() ); - AddItem( new WingedHelm() ); - AddItem( new FemaleElvenPlateChest() ); - AddItem( new RadiantScimitar() ); - } - - public Saril( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Cailla (The Heartwood)" )] - public class Cailla : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Cailla"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074187, // Want a job? - 1074210 // Hi.� Looking for something to do? - ) ); - } - - [Constructible] - public Cailla() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the guard"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new HidePants() ); - AddItem( new HidePauldrons() ); - AddItem( new HideGloves() ); - AddItem( new WoodlandBelt() ); - AddItem( new RavenHelm() ); - AddItem( new HideFemaleChest() ); - AddItem( new MagicalShortbow() ); - } - - public Cailla( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Tamm (The Heartwood)" )] - public class Tamm : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Tamm"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074213, // Hey buddy.� Looking for work? - 1074187 // Want a job? - ) ); - } - - [Constructible] - public Tamm() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the guard"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new HidePants() ); - AddItem( new HidePauldrons() ); - AddItem( new WingedHelm() ); - AddItem( new HideChest() ); - AddItem( new ElvenCompositeLongbow() ); - } - - public Tamm( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Landy (The Heartwood)" )] - public class Landy : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Landy"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074211, // I could use some help. - 1074218 // Hey!� I want to talk to you, now. - ) ); - } - - [Constructible] - public Landy() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the soil nurturer"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( Utility.RandomYellowHue() ) ); - AddItem( new ShortPants( Utility.RandomYellowHue() ) ); - AddItem( new Tunic( Utility.RandomYellowHue() ) ); - - Item gloves = new LeafGloves(); - gloves.Hue = Utility.RandomYellowHue(); - AddItem( gloves ); - } - - public Landy( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Elder Alejaha (The Heartwood)" )] - public class Alejaha : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Alejaha"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074223 ); // Have you done it yet?� Oh, I haven�t told you, have I? - } - - [Constructible] - public Alejaha() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( Utility.RandomYellowHue() ) ); - AddItem( new ElvenShirt( Utility.RandomYellowHue() ) ); - AddItem( new GemmedCirclet() ); - AddItem( new Cloak( Utility.RandomBrightHue() ) ); - - if ( Utility.RandomBool() ) - AddItem( new Kilt( 0x387 ) ); - else - AddItem( new Skirt( 0x387 ) ); - } - - public Alejaha( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Mielan (The Heartwood)" )] - public class Mielan : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Mielan"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074219, // Hello there, can I have a moment of your time? - 1074223 // Have you done it yet?� Oh, I haven�t told you, have I? - ) ); - } - - [Constructible] - public Mielan() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the arcanist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new ElvenShirt( 0x56 ) ); - AddItem( new GemmedCirclet() ); - AddItem( new ElvenPants( 0x901 ) ); - } - - public Mielan( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Ciala (The Heartwood)" )] - public class Ciala : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Ciala"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074206, // Excuse me please traveler, might I have a little of your time? - 1074186 // Come here, I have a task. - ) ); - } - - [Constructible] - public Ciala() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the arborist"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Skirt( Utility.RandomBlueHue() ) ); - AddItem( new ElvenShirt( Utility.RandomYellowHue() ) ); - AddItem( new RoyalCirclet() ); - - if ( Utility.RandomBool() ) - AddItem( new Boots( Utility.RandomYellowHue() ) ); - else - AddItem( new ThighBoots( Utility.RandomYellowHue() ) ); - } - - public Ciala( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Aniel (The Heartwood)" )] - public class Aniel : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Aniel"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074220, // May I call you friend?� I have a favor to beg of you. - 1074222 // Could I trouble you for some assistance? - ) ); - } - - [Constructible] - public Aniel() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the arborist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenPants( 0x901 ) ); - AddItem( new LeafChest() ); - AddItem( new HalfApron( Utility.RandomYellowHue() ) ); - AddItem( new ElvenBoots( 0x901 ) ); - } - - public Aniel( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Aulan (The Heartwood)" )] - public class Aulan : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Aulan"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074188, // Weakling! You are not up to the task I have. - 1074191, // Just keep walking away!� I thought so. Coward!� I�ll bite your legs off! - 1074195 // You there, in the stupid hat! Come here. - ) ); - } - - [Constructible] - public Aulan() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the expeditionist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - Item item; - - item = new ElvenBoots(); - item.Hue = Utility.RandomYellowHue(); - AddItem( item ); - - AddItem( new ElvenPants( Utility.RandomGreenHue() ) ); - AddItem( new Cloak( Utility.RandomGreenHue() ) ); - AddItem( new Circlet() ); - - item = new HideChest(); - item.Hue = Utility.RandomYellowHue(); - AddItem( item ); - - item = new HideGloves(); - item.Hue = Utility.RandomYellowHue(); - AddItem( item ); - } - - public Aulan( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Brinnae (The Heartwood)" )] - public class Brinnae : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Brinnae"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074212, // *yawn* You busy? - 1074210 // Hi.� Looking for something to do? - ) ); - } - - [Constructible] - public Brinnae() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots() ); - AddItem( new FemaleLeafChest() ); - AddItem( new LeafArms() ); - AddItem( new HidePants() ); - AddItem( new ElvenCompositeLongbow() ); - } - - public Brinnae( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Elder Caelas (The Heartwood)" )] - public class Caelas : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Caelas"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074204, // Greetings seeker.� I have an urgent matter for you, if you are willing. - 1074201 // Waste not a minute! There�s work to be done. - ) ); - } - - [Constructible] - public Caelas() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x1BB ) ); - AddItem( new MaleElvenRobe( 0x489 ) ); - AddItem( new Cloak( 0x718 ) ); - AddItem( new RoyalCirclet() ); - } - - public Caelas( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Clehin (The Heartwood)" )] - public class Clehin : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Clehin"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074211, // I could use some help. - 1074186 // Come here, I have a task. - ) ); - } - - [Constructible] - public Clehin() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the soil nurturer"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new ElvenShirt() ); - AddItem( new LeafTonlet() ); - } - - public Clehin( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Cloorne : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Cloorne"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074185, // Hey you! Want to help me out? - 1074186 //Come here, I have a task. - ) ); - } - - [Constructible] - public Cloorne() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the expeditionist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x3B2 ) ); - AddItem( new RadiantScimitar() ); - AddItem( new WingedHelm() ); - - Item item; - - item = new WoodlandLegs(); - item.Hue = 0x74A; - AddItem( item ); - - item = new HideChest(); - item.Hue = 0x726; - AddItem( item ); - - item = new LeafArms(); - item.Hue = 0x73E; - AddItem( item ); - } - - public Cloorne( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Salaenih (The Heartwood)" )] - public class Salaenih : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Salaenih"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074207, // Good day to you friend! Allow me to offer you a fabulous opportunity!� Thrills and adventure await! - 1074209 // Hey, could you help me out with something? - ) ); - } - - [Constructible] - public Salaenih() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the expeditionist"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new WarCleaver() ); - - Item item; - - item = new WoodlandBelt(); - item.Hue = 0x597; - AddItem( item ); - - item = new VultureHelm(); - item.Hue = 0x1BB; - AddItem( item ); - - item = new WoodlandLegs(); - item.Hue = 0x1BB; - AddItem( item ); - - item = new WoodlandChest(); - item.Hue = 0x1BB; - AddItem( item ); - - item = new WoodlandArms(); - item.Hue = 0x1BB; - AddItem( item ); - } - - public Salaenih( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Vilo (The Heartwood)" )] - public class Vilo : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Vilo"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074210, // Hi.� Looking for something to do? - 1074220 // May I call you friend?� I have a favor to beg of you. - ) ); - } - - [Constructible] - public Vilo() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the guard"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new OrnateAxe() ); - AddItem( new WoodlandBelt( 0x592 ) ); - AddItem( new VultureHelm() ); - AddItem( new WoodlandLegs() ); - AddItem( new WoodlandChest() ); - AddItem( new WoodlandArms() ); - AddItem( new WoodlandGorget() ); - } - - public Vilo( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Tholef (The Heartwood)" )] - public class Tholef : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Tholef"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074209, // Hey, could you help me out with something? - 1074184 // Come here, I have work for you. - ) ); - } - - [Constructible] - public Tholef() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the grape tender"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x901 ) ); - AddItem( new FullApron( 0x756 ) ); - AddItem( new ShortPants( 0x28C ) ); - AddItem( new Shirt( 0x28C ) ); - - Item item; - - item = new LeafArms(); - item.Hue = 0x28C; - AddItem( item ); - } - - public Tholef( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Tillanil (The Heartwood)" )] - public class Tillanil : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Tillanil"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074187, // Want a job? - 1074222 // Could I trouble you for some assistance? - ) ); - } - - [Constructible] - public Tillanil() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the grape tender"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x1BB ) ); - AddItem( new Tunic( 0x759 ) ); - AddItem( new ShortPants( 0x21 ) ); - } - - public Tillanil( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Waelian (The Heartwood)" )] - public class Waelian : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Waelian"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074221, // Greetings!� I have a small task for you good traveler. - 1074201 // Waste not a minute! There�s work to be done. - ) ); - } - - [Constructible] - public Waelian() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the trinket weaver"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Shoes( 0x901 ) ); - AddItem( new SmithHammer() ); - AddItem( new LongPants( 0x340 ) ); - AddItem( new GemmedCirclet() ); - - Item item; - - item = new LeafChest(); - item.Hue = 0x344; - AddItem( item ); - } - - public Waelian( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Sleen (The Heartwood)" )] - public class Sleen : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Sleen"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074200, // Thank goodness you are here, there�s no time to lose. - 1074206 // Excuse me please traveler, might I have a little of your time? - ) ); - } - - [Constructible] - public Sleen() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the trinket weaver"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new SmithHammer() ); - AddItem( new Cloak( 0x75A ) ); - AddItem( new ElvenShirt() ); - } - - public Sleen( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Unoelil (The Heartwood)" )] - public class Unoelil : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Unoelil"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074186, // Come here, I have a task. - 1074209 // Hey, could you help me out with something? - ) ); - } - - [Constructible] - public Unoelil() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the bark weaver"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x1BB ) ); - AddItem( new ShortPants( 0x1BB ) ); - AddItem( new Tunic( 0x64D ) ); - } - - public Unoelil( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Anolly (The Heartwood)" )] - public class Anolly : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Anolly"; - public override bool CanTeach => true; - - [Constructible] - public Anolly() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the bark weaver"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x901 ) ); - AddItem( new ShortPants( 0x3B3 ) ); - AddItem( new FullApron( 0x1BB ) ); - AddItem( new SmithHammer() ); - } - - public Anolly( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Jusae (The Heartwood)" )] - public class Jusae : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Jusae"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074210, // Hi.� Looking for something to do? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Jusae() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the bowcrafter"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x901 ) ); - AddItem( new ShortPants( 0x661 ) ); - AddItem( new MagicalShortbow() ); - - Item item; - - item = new HideChest(); - item.Hue = 0x27B; - AddItem( item ); - - item = new HidePauldrons(); - item.Hue = 0x27E; - AddItem( item ); - } - - public Jusae( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Cillitha (The Heartwood)" )] - public class Cillitha : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Cillitha"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074223, // Have you done it yet?� Oh, I haven�t told you, have I? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Cillitha() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the bowcrafter"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new ElvenShirt( 0x731 ) ); - AddItem( new LeafLegs() ); - } - - public Cillitha( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Lohn (The Heartwood)" )] - public class Lohn : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lohn"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074187, // Want a job? - 1074209 // Hey, could you help me out with something? - ) ); - } - - [Constructible] - public Lohn() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the metal weaver"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Shoes( 0x901 ) ); - AddItem( new LongPants( 0x359 ) ); - AddItem( new SmithHammer() ); - AddItem( new GemmedCirclet() ); - - Item item; - - item = new LeafChest(); - item.Hue = 0x359; - AddItem( item ); - } - - public Lohn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Olla (The Heartwood)" )] - public class Olla : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Olla"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074187, // Want a job? - 1074185 // Hey you! Want to help me out? - ) ); - } - - [Constructible] - public Olla() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the metal weaver"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new LongPants( 0x3B3 ) ); - AddItem( new SmithHammer() ); - AddItem( new FullApron( 0x1BB ) ); - AddItem( new ElvenShirt() ); - - } - - public Olla( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Thallary (The Heartwood)" )] - public class Thallary : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Thallary"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074221, // Greetings!� I have a small task for you good traveler. - 1074212 // *yawn* You busy? - ) ); - } - - [Constructible] - public Thallary() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the cloth weaver"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x901 ) ); - AddItem( new LongPants( 0x72E ) ); - AddItem( new Cloak( 0x3B3 ) ); - AddItem( new FancyShirt( 0x13 ) ); - - } - - public Thallary( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Ahie (The Heartwood)" )] - public class Ahie : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Ahie"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074206, // Excuse me please traveler, might I have a little of your time? - 1074203 // Hello friend. I realize you are busy but if you would be willing to render me a service I can assure you that you will be judiciously renumerated. - ) ); - } - - [Constructible] - public Ahie() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the cloth weaver"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Boots( 0x901 ) ); - AddItem( new Skirt( 0x1C ) ); - AddItem( new Cloak( 0x62 ) ); - AddItem( new FancyShirt( 0x738 ) ); - - } - - public Ahie( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Tyeelor : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Tyeelor"; - - [Constructible] - public Tyeelor() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the expeditionist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x1BB ) ); - - Item item; - - item = new WoodlandLegs(); - item.Hue = 0x236; - AddItem( item ); - - item = new WoodlandChest(); - item.Hue = 0x236; - AddItem( item ); - - item = new WoodlandArms(); - item.Hue = 0x236; - AddItem( item ); - - item = new VultureHelm(); - item.Hue = 0x236; - AddItem( item ); - - item = new WoodlandBelt(); - item.Hue = 0x236; - AddItem( item ); - - } - - public Tyeelor( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Athailon : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Athailon"; - - [Constructible] - public Athailon() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the expeditionist"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new WoodlandBelt() ); - AddItem( new DiamondMace() ); - - Item item; - - item = new WoodlandLegs(); - item.Hue = 0x3B2; - AddItem( item ); - - item = new FemaleElvenPlateChest(); - item.Hue = 0x3B2; - AddItem( item ); - - item = new WoodlandArms(); - item.Hue = 0x3B2; - AddItem( item ); - - item = new WingedHelm(); - item.Hue = 0x3B2; - AddItem( item ); - - } - - public Athailon( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ElderTaellia : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Taellia"; - - [Constructible] - public ElderTaellia() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ThighBoots( 0x127 ) ); - AddItem( new FemaleElvenRobe( Utility.RandomBrightHue() ) ); - AddItem( new MagicWand() ); - AddItem( new Circlet() ); - - } - - public ElderTaellia( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ElderMallew : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Mallew"; - - [Constructible] - public ElderMallew() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x1BB ) ); - AddItem( new Cloak( 0x3B2 ) ); - AddItem( new Circlet() ); - - Item item; - - item = new LeafTonlet(); - item.Hue = 0x544; - AddItem( item ); - - item = new LeafChest(); - item.Hue = 0x538; - AddItem( item ); - - item = new LeafArms(); - item.Hue = 0x528; - AddItem( item ); - - } - - public ElderMallew( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ElderAbbein : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Abbein"; - - [Constructible] - public ElderAbbein() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x72C ) ); - AddItem( new FemaleElvenRobe( 0x8B0 ) ); - AddItem( new RoyalCirclet() ); - - } - - public ElderAbbein( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ElderVicaie : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Vicaie"; - - [Constructible] - public ElderVicaie() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots() ); - AddItem( new Tunic( 0x732 ) ); - - Item item; - - item = new LeafLegs(); - item.Hue = 0x3B2; - AddItem( item ); - - } - - public ElderVicaie( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ElderJothan : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Jothan"; - - [Constructible] - public ElderJothan() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ThighBoots() ); - AddItem( new ElvenPants( 0x58D ) ); - AddItem( new ElvenShirt( Utility.RandomYellowHue() ) ); - AddItem( new Cloak( Utility.RandomBrightHue() ) ); - AddItem( new Circlet() ); - - } - - public ElderJothan( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ElderAlethanian : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Alethanian"; - - [Constructible] - public ElderAlethanian() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots() ); - AddItem( new HidePants() ); - AddItem( new HideFemaleChest() ); - AddItem( new HidePauldrons() ); - AddItem( new GemmedCirclet() ); - - } - - public ElderAlethanian( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Rebinil : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Rebinil"; - - [Constructible] - public Rebinil() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the healer"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Sandals( 0x715 ) ); - AddItem( new FemaleElvenRobe( 0x742 ) ); - AddItem( new RoyalCirclet() ); - - } - - public Rebinil( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Aluniol : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Aluniol"; - - [Constructible] - public Aluniol() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the healer"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x1BB ) ); - AddItem( new MaleElvenRobe( 0x47E ) ); - AddItem( new WildStaff() ); - - } - - public Aluniol( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Olaeni : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Olaeni"; - - [Constructible] - public Olaeni() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the thaumaturgist"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Shoes( 0x75A ) ); - AddItem( new FemaleElvenRobe( 0x13 ) ); - AddItem( new MagicWand() ); - AddItem( new GemmedCirclet() ); - - } - - public Olaeni( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Bolaevin : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Bolaevin"; - - [Constructible] - public Bolaevin() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the arcanist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x3B2 ) ); - AddItem( new RoyalCirclet() ); - AddItem( new LeafChest() ); - AddItem( new LeafArms() ); - - Item item; - - item = new LeafLegs(); - item.Hue = 0x1BB; - AddItem( item ); - - } - - public Bolaevin( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LorekeeperAneen : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lorekeeper Aneen"; - - [Constructible] - public LorekeeperAneen() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Sandals( 0x1BB ) ); - AddItem( new MaleElvenRobe( 0x48F) ); - AddItem( new MagicWand() ); - - } - - public LorekeeperAneen( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Daelas : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Daelas"; - - [Constructible] - public Daelas() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the arborist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new ElvenPants( 0x8AB) ); - - Item item; - - item = new LeafChest(); - item.Hue = 0x8B0; - AddItem( item ); - - item = new LeafGloves(); - item.Hue = 0x1BB; - AddItem( item ); - - } - - public Daelas( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Alelle : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Alelle"; - - [Constructible] - public Alelle() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the arborist"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots( 0x1BB ) ); - - Item item; - - item = new FemaleLeafChest(); - item.Hue = 0x3A; - AddItem( item ); - - item = new LeafLegs(); - item.Hue = 0x74C; - AddItem( item ); - - item = new LeafGloves(); - item.Hue = 0x1BB; - AddItem( item ); - - } - - public Alelle( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Nillaen (The Heartwood)" )] - public class LorekeeperNillaen : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lorekeeper Nillaen"; - public override bool CanTeach => true; - - [Constructible] - public LorekeeperNillaen() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Shoes( 0x1BB ) ); - AddItem( new LongPants( 0x1FB ) ); - AddItem( new ElvenShirt() ); - AddItem( new GemmedCirclet() ); - AddItem( new BodySash( 0x25 ) ); - AddItem( new BlackStaff() ); - } - - public LorekeeperNillaen( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Ryal (The Heartwood)" )] - public class LorekeeperRyal : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lorekeeper Ryal"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074204, // Greetings seeker.� I have an urgent matter for you, if you are willing. - 1074200 // Thank goodness you are here, there�s no time to lose. - ) ); - } - - [Constructible] - public LorekeeperRyal() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x1BB ) ); - AddItem( new LeafTonlet() ); - AddItem( new ElvenShirt( 0x2DD ) ); - AddItem( new Cloak( 0x219 ) ); - AddItem( new GnarledStaff() ); - } - - public LorekeeperRyal( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Braen (The Heartwood)" )] - public class Braen : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Braen"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074187 ); // Want a job? - } - - [Constructible] - public Braen() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the thaumaturgist"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x714 ) ); - AddItem( new MaleElvenRobe( 0x64A ) ); - AddItem( new MagicWand() ); - } - - public Braen( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Elder Acob (The Heartwood)" )] - public class ElderAcob : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Elder Acob"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074197 ); // Pardon me, but if you could spare some time I�d greatly appreciate it. - } - - [Constructible] - public ElderAcob() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x714 ) ); - AddItem( new ElvenShirt( Utility.RandomBrightHue() ) ); - AddItem( new HidePants() ); - } - - public ElderAcob( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LorekeeperCalendor : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lorekeeper Calendor"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074204 ); // Greetings seeker.� I have an urgent matter for you, if you are willing. - } - - [Constructible] - public LorekeeperCalendor() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x714 ) ); - AddItem( new ElvenShirt( Utility.RandomOrangeHue() ) ); - AddItem( new Kilt( Utility.RandomOrangeHue() ) ); - AddItem( new RoyalCirclet() ); - } - - public LorekeeperCalendor( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LorekeeperSiarra : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lorekeeper Siarra"; - public override bool CanTeach => true; - - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074206 ); // Excuse me please traveler, might I have a little of your time? - } - - [Constructible] - public LorekeeperSiarra() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x1BB ) ); - AddItem( new ElvenShirt() ); - AddItem( new LeafTonlet() ); - AddItem( new GemmedCirclet() ); - } - - public LorekeeperSiarra( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #region Quests + + public class TheyreBreedingLikeRabbits : MLQuest + { + public TheyreBreedingLikeRabbits() + { + Activated = true; + Title = 1072244; // They're Breeding Like Rabbits + Description = + 1072259; // Aaaahhhh! They're everywhere! Aaaaahhh! Ahem. Actually, friend, how do you feel about rabbits? Well, we're being overrun by them. We're finding fuzzy bunnies everywhere. Aaaaahhh! + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Rabbit) }, "rabbits")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Saril"), new Point3D(7075, 376, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Saril"), new Point3D(7075, 376, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Cailla"), new Point3D(7075, 377, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Cailla"), new Point3D(7075, 377, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Tamm"), new Point3D(7075, 378, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Tamm"), new Point3D(7075, 378, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Landy"), new Point3D(7089, 390, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Landy"), new Point3D(7089, 390, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Alejaha"), new Point3D(7043, 387, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Alejaha"), new Point3D(7043, 387, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Mielan"), new Point3D(7063, 350, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Mielan"), new Point3D(7063, 350, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Ciala"), new Point3D(7031, 411, 7), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Ciala"), new Point3D(7031, 411, 7), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Aniel"), new Point3D(7034, 412, 6), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Aniel"), new Point3D(7034, 412, 6), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Aulan"), new Point3D(6986, 340, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Aulan"), new Point3D(6986, 340, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Brinnae"), new Point3D(6996, 351, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Brinnae"), new Point3D(6996, 351, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Caelas"), new Point3D(7039, 390, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Caelas"), new Point3D(7039, 390, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Clehin"), new Point3D(7092, 390, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Clehin"), new Point3D(7092, 390, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Cloorne"), new Point3D(7010, 364, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Cloorne"), new Point3D(7010, 364, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Salaenih"), new Point3D(7009, 362, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Salaenih"), new Point3D(7009, 362, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Vilo"), new Point3D(7029, 377, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Vilo"), new Point3D(7029, 377, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Tholef"), new Point3D(6986, 386, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Tholef"), new Point3D(6986, 386, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Tillanil"), new Point3D(6987, 388, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Tillanil"), new Point3D(6987, 388, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Waelian"), new Point3D(6996, 381, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Waelian"), new Point3D(6996, 381, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Sleen"), new Point3D(6997, 381, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Sleen"), new Point3D(6997, 381, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Unoelil"), new Point3D(7010, 388, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Unoelil"), new Point3D(7010, 388, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Anolly"), new Point3D(7009, 388, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Anolly"), new Point3D(7009, 388, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Jusae"), new Point3D(7042, 377, 2), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Jusae"), new Point3D(7042, 377, 2), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Cillitha"), new Point3D(7043, 377, 2), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Cillitha"), new Point3D(7043, 377, 2), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Lohn"), new Point3D(7062, 410, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Lohn"), new Point3D(7062, 410, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Olla"), new Point3D(7063, 410, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Olla"), new Point3D(7063, 410, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Thallary"), new Point3D(7032, 439, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Thallary"), new Point3D(7032, 439, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Ahie"), new Point3D(7033, 440, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Ahie"), new Point3D(7033, 440, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Tyeelor"), new Point3D(7010, 364, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Tyeelor"), new Point3D(7010, 364, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Athailon"), new Point3D(7011, 365, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Athailon"), new Point3D(7011, 365, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderTaellia"), new Point3D(7038, 387, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderTaellia"), new Point3D(7038, 387, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderMallew"), new Point3D(7047, 390, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderMallew"), new Point3D(7047, 390, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderAbbein"), new Point3D(7043, 390, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderAbbein"), new Point3D(7043, 390, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderVicaie"), new Point3D(7054, 390, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderVicaie"), new Point3D(7054, 390, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderJothan"), new Point3D(7056, 383, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderJothan"), new Point3D(7056, 383, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "ElderAlethanian"), new Point3D(7056, 380, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "ElderAlethanian"), new Point3D(7056, 380, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Rebinil"), new Point3D(7089, 380, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Rebinil"), new Point3D(7089, 380, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Aluniol"), new Point3D(7089, 383, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Aluniol"), new Point3D(7089, 383, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Olaeni"), new Point3D(7080, 363, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Olaeni"), new Point3D(7080, 363, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Bolaevin"), new Point3D(7066, 351, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Bolaevin"), new Point3D(7066, 351, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "LorekeeperAneen"), new Point3D(7053, 337, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "LorekeeperAneen"), new Point3D(7053, 337, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Daelas"), new Point3D(7036, 412, 7), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Daelas"), new Point3D(7036, 412, 7), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Alelle"), new Point3D(7028, 406, 7), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Alelle"), new Point3D(7028, 406, 7), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "LorekeeperNillaen"), new Point3D(7061, 370, 14), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "LorekeeperNillaen"), new Point3D(7061, 370, 14), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "LorekeeperRyal"), new Point3D(7009, 375, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "LorekeeperRyal"), new Point3D(7009, 375, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Braen"), new Point3D(7081, 366, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Braen"), new Point3D(7081, 366, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderAcob"), new Point3D(7037, 387, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "ElderAcob"), new Point3D(7037, 387, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "LorekeeperCalendor"), new Point3D(7062, 370, 14), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "LorekeeperCalendor"), new Point3D(7062, 370, 14), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "LorekeeperSiarra"), new Point3D(7051, 339, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "LorekeeperSiarra"), new Point3D(7051, 339, 0), Map.Felucca); + } + } + + public class TheyllEatAnything : MLQuest + { + public TheyllEatAnything() + { + Activated = true; + Title = 1072248; // They'll Eat Anything + Description = + 1072262; // Pork is the fruit of the land! You can barbeque it, boil it, bake it, sautee it. There's pork kebabs, pork creole, pork gumbo, pan fried, deep fried, stir fried. There's apple pork, peppered pork, pork soup, pork salad, pork and potatoes, pork burger, pork sandwich, pork stew, pork chops, pork loins, shredded pork. So, lets get some piggies butchered! + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Pig) }, "pigs")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class NoGoodFishStealing : MLQuest + { + public NoGoodFishStealing() + { + Activated = true; + Title = 1072251; // No Good, Fish Stealing ... + Description = + 1072265; // Mighty creatures they are, aye. Fierce and strong, can't blame 'em for wanting to feed themselves an' all. Blame or no, they're eating all the fish up, so they got to go. Lend a hand? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Walrus) }, "walruses")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class AHeroInTheMaking : MLQuest + { + public AHeroInTheMaking() + { + Activated = true; + Title = 1072246; // A Hero in the Making + Description = + 1072257; // Are you new around here? Well, nevermind that. You look ready for adventure, I can see the gleam of glory in your eyes! Nothing is more valiant, more noble, more praiseworthy than mongbat slaying. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Mongbat) }, "mongbats")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class BullfightingSortOf : MLQuest + { + public BullfightingSortOf() + { + Activated = true; + Title = 1072247; // Bullfighting ... Sort Of + Description = + 1072254; // You there! Yes, you. Listen, I've got a little problem on my hands, but a brave, bold hero like yourself should find it a snap to solve. Bottom line -- we need some of the bulls in the area culled. You're welcome to any meat or hides, and of course, I'll give you a nice reward. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Bull) }, "bulls")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class AFineFeast : MLQuest + { + public AFineFeast() + { + Activated = true; + Title = 1072243; // A Fine Feast. + Description = + 1072261; // Mmm, I do love mutton! It's slaughtering time again and my usual hirelings haven't turned up. I've arranged for a butcher to come by and cut everything up but the basic sheep killing part I haven't gotten worked out yet. Are you up for the task? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Sheep) }, "sheep")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class ForcedMigration : MLQuest + { + public ForcedMigration() + { + Activated = true; + Title = 1072250; // Forced Migration + Description = + 1072264; // Chirp chirp ... tweet chirp. Tra la la. Bloody birds and their blasted noise. I've tried everything but they just won't stop that infernal clamor. Return me to blessed silence and I'll make it worth your while. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Bird) }, "birds")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class FilthyPests : MLQuest + { + public FilthyPests() + { + Activated = true; + Title = 1072242; // Filthy Pests! + Description = + 1072253; // They're everywhere I tell you! They crawl in the walls, they scurry in the bushes. Disgusting critters. Say ... I don't suppose you're up for some sewer rat killing? Sewer rats now, not any other kind of squeaker will do. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(SewerRat) }, "sewer rats")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class DeadManWalking : MLQuest + { + public DeadManWalking() + { + Activated = true; + Title = 1072983; // Dead Man Walking + Description = + 1073009; // Why? I ask you why? They walk around after they're put in the ground. It's just wrong in so many ways. Put them to proper rest, I beg you. I'll find some way to pay you for the kindness. Just kill five zombies and five skeletons. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(5, new[] { typeof(Zombie) }, "zombies")); + Objectives.Add(new KillObjective(5, new[] { typeof(Skeleton) }, "skeletons")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class KingOfBears : MLQuest + { + public KingOfBears() + { + Activated = true; + Title = 1072996; // King of Bears + Description = + 1073030; // A pity really. With the balance of nature awry, we have no choice but to accept the responsibility of making it all right. It's all a part of the circle of life, after all. So, yes, the grizzly bears are running rampant. There are far too many in the region. Will you shoulder your obligations as a higher life form? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(GrizzlyBear) }, "grizzly bears")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class Specimens : MLQuest + { + public Specimens() + { + Activated = true; + Title = 1072999; // Specimens + Description = + 1073032; // I admire them, you know. The solen have their place -- regimented, organized. They're fascinating to watch with their constant strife between red and black. I can't help but want to stir things up from time to time. And that's where you come in. Kill either twelve red or twelve black solen workers and let's see what happens next! + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + ObjectiveType = ObjectiveType.Any; + + Objectives.Add(new KillObjective(12, new[] { typeof(RedSolenWorker) }, "red solen workers")); + Objectives.Add(new KillObjective(12, new[] { typeof(BlackSolenWorker) }, "black solen workers")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class Spirits : MLQuest + { + public Spirits() + { + Activated = true; + Title = 1073076; // Spirits + Description = + 1073566; // It is a piteous thing when the dead continue to walk the earth. Restless spirits are known to inhabit these parts, taking the lives of unwary travelers. It is about time a hero put the dead back in their graves. I'm sure such a hero would be justly rewarded. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073586; // The restless spirts still walk -- you must kill 15 of them. + + Objectives.Add(new KillObjective(15, new[] { typeof(Spectre), typeof(Shade), typeof(Wraith) }, + "spectres or shades or wraiths")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class RollTheBones : MLQuest + { + public RollTheBones() + { + Activated = true; + Title = 1073002; // Roll the Bones + Description = + 1073011; // Why? I ask you why? They walk around after they're put in the ground. It's just wrong in so many ways. Put them to proper rest, I beg you. I'll find some way to pay you for the kindness. Just kill eight patchwork skeletons. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(8, new[] { typeof(PatchworkSkeleton) }, "patchwork skeletons")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class ItsAGhastlyJob : MLQuest + { + public ItsAGhastlyJob() + { + Activated = true; + Title = 1073008; // It's a Ghastly Job + Description = + 1073012; // Why? I ask you why? They walk around after they're put in the ground. It's just wrong in so many ways. Put them to proper rest, I beg you. I'll find some way to pay you for the kindness. Just kill twelve ghouls. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(12, new[] { typeof(Ghoul) }, "ghouls")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class Troglodytes : MLQuest + { + public Troglodytes() + { + Activated = true; + Title = 1074688; // Troglodytes! + Description = + 1074689; // Oh nevermind, you don't look capable of my task afterall. Haha! What was I thinking - you could never handle killing troglodytes. It'd be suicide. What? I don't know, I don't want to be responsible ... well okay if you're really sure? + RefusalMessage = 1074690; // Probably the wiser course of action. + InProgressMessage = 1074691; // You still need to kill those troglodytes, remember? + + Objectives.Add(new KillObjective(12, new[] { typeof(Troglodyte) }, "troglodytes")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class UnholyKnights : MLQuest + { + public UnholyKnights() + { + Activated = true; + Title = 1073075; // Unholy Knights + Description = + 1073565; // Please, hear me kind traveler. You know when a knight falls, sometimes they are cursed to roam the earth as undead mockeries of their former glory? That is too grim a fate for even any knight to suffer! Please, put them out of their misery. I will offer you what payment I can if you will end the torment of these undead wretches. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073585; // Your task is not done. Continue putting the Skeleton and Bone Knights to rest. + + Objectives.Add(new KillObjective(16, new[] { typeof(BoneKnight), typeof(SkeletalKnight) }, + "bone knights or skeletal knights")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class AFeatherInYerCap : MLQuest + { + public AFeatherInYerCap() + { + Activated = true; + Title = 1074738; // A Feather in Yer Cap + Description = + 1074737; // I've seen how you strut about, as if you were something special. I have some news for you, you don't impress me at all. It's not enough to have a fancy hat you know. That may impress people in the big city, but not here. If you want a reputation you have to climb a mountain, slay some great beast, and then write about it. Trust me, it's a long process. The first step is doing a great feat. If I were you, I'd go pluck a feather from the harpy Saliva, that would give you a good start. + RefusalMessage = 1074736; // The path to greatness isn't for everyone obviously. + InProgressMessage = + 1074735; // If you're going to get anywhere in the adventuring game, you have to take some risks. A harpy, well, it's bad, but it's not a dragon. + CompletionMessage = 1074734; // The hero returns from the glorious battle and - oh, such a small feather? + + Objectives.Add(new CollectObjective(1, typeof(SalivasFeather), "Saliva's Feather")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ATaleOfTail : MLQuest + { + public ATaleOfTail() + { + Activated = true; + Title = 1074726; // A Tale of Tail + Description = + 1074727; // I've heard of you, adventurer. Your reputation is impressive, and now I'll put it to the test. This is not something I ask lightly, for this task is fraught with danger, but it is vital. Seek out the vile hydra Abscess, slay it, and return to me with it's tail. + RefusalMessage = 1074728; // Well, the beast will still be there when you are ready I suppose. + InProgressMessage = + 1074729; // Em, I thought I had explained already. Abscess, the hydra, you know? Lots of heads but just the one tail. I need the tail. I have my reasons. Go go go. + CompletionMessage = + 1074730; // Ah, the tail. You did it! You know the rumours about dried ground hydra tail powder are all true? Thank you so much! + + Objectives.Add(new CollectObjective(1, typeof(AbscessTail), "Abscess' Tail")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ATrogAndHisDog : MLQuest + { + public ATrogAndHisDog() + { + Activated = true; + Title = 1074681; // A Trog and His Dog + Description = + 1074680; // I don't know if you can handle it, but I'll give you a go at it. Troglodyte chief - name of Lurg and his mangy wolf pet need killing. Do the deed and I'll reward you. + RefusalMessage = 1074655; // Perhaps I thought too highly of you. + InProgressMessage = + 1074682; // The trog chief and his mutt should be easy enough to find. Just kill them and report back. Easy enough. + CompletionMessage = 1074683; // Not half bad. Here's your prize. + + Objectives.Add(new KillObjective(1, new[] { typeof(Lurg) }, "Lurg")); + Objectives.Add(new KillObjective(1, new[] { typeof(Grobu) }, "Grobu")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class Overpopulation : MLQuest + { + public Overpopulation() + { + Activated = true; + Title = 1072252; // Overpopulation + Description = + 1072267; // I just can't bear it any longer. Sure, it's my job to thin the deer out so they don't overeat the area and starve themselves come winter time. Sure, I know we killed off the predators that would do this naturally so now we have to make up for it. But they're so graceful and innocent. I just can't do it. Will you? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Hind) }, "hinds")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class WildBoarCull : MLQuest + { + public WildBoarCull() + { + Activated = true; + Title = 1072245; // Wild Boar Cull + Description = + 1072260; // A pity really. With the balance of nature awry, we have no choice but to accept the responsibility of making it all right. It's all a part of the circle of life, after all. So, yes, the boars are running rampant. There are far too many in the region. Will you shoulder your obligations as a higher life form? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Boar) }, "boars")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class ItsElemental : MLQuest + { + public ItsElemental() + { + Activated = true; + Title = 1073089; // It's Elemental + Description = + 1073579; // The universe is all about balance my friend. Tip one end, you must balance the other. That's why I must ask you to kill not just one kind of elemental, but three kinds. Snuff out some Fire, douse a few Water, and crush some Earth elementals and I'll pay you for your trouble. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073599; // Four of each, that's all I ask. Water, earth and fire. + + Objectives.Add(new KillObjective(4, new[] { typeof(FireElemental) }, "fire elementals")); + Objectives.Add(new KillObjective(4, new[] { typeof(WaterElemental) }, "water elementals")); + Objectives.Add(new KillObjective(4, new[] { typeof(EarthElemental) }, "earth elementals")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class CircleOfLife : MLQuest + { + public CircleOfLife() + { + Activated = true; + Title = 1073656; // Circle of Life + Description = + 1073695; // There's been a bumper crop of evil with the Bog Things in these parts, my friend. Though they are foul creatures, they are also most fecund. Slay one and you make the land more fertile. Even better, slay several and I will give you whatever coin I can spare. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073736; // Continue to seek and kill the Bog Things. + + Objectives.Add(new KillObjective(8, new[] { typeof(BogThing) }, "bog things")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class DustToDust : MLQuest + { + public DustToDust() + { + Activated = true; + Title = 1073074; // Dust to Dust + Description = + 1073564; // You want to hear about trouble? I got trouble. How's angry piles of granite walking around for trouble? Maybe they don't like the mining, maybe it's the farming. I don't know. All I know is someone's got to turn them back to potting soil. And it'd be worth a pretty penny to the soul that does it. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073584; // You got rocks in your head? I said to kill 12 earth elementals, okay? + + Objectives.Add(new KillObjective(12, new[] { typeof(EarthElemental) }, "earth elementals")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class CreepyCrawlies : MLQuest + { + public CreepyCrawlies() + { + Activated = true; + Title = 1072987; // Creepy Crawlies + Description = + 1073016; // Disgusting! The way they scuttle on those hairy legs just makes me want to gag. I hate spiders! Rid the world of twelve and I'll find something nice to give you in thanks. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(12, new[] { typeof(GiantSpider) }, "giant spiders")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class VoraciousPlants : MLQuest + { + public VoraciousPlants() + { + Activated = true; + Title = 1073001; // Voracious Plants + Description = + 1073024; // I bet you can't tangle with those nasty plants ... say eight corpsers and two swamp tentacles! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(8, new[] { typeof(Corpser) }, "corpsers")); + Objectives.Add(new KillObjective(2, new[] { typeof(SwampTentacle) }, "swamp tentacles")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class GibberJabber : MLQuest + { + public GibberJabber() + { + Activated = true; + Title = 1073004; // Gibber Jabber + Description = + 1073024; // I bet you can't kill ... ten gibberlings! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Gibberling) }, "gibberlings")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class AnimatedMonstrosity : MLQuest + { + public AnimatedMonstrosity() + { + Activated = true; + Title = 1072990; // Animated Monstrosity + Description = + 1073020; // I bet you can't kill ... say twelve ... flesh golems! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(12, new[] { typeof(FleshGolem) }, "flesh golems")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class BirdsOfAFeather : MLQuest + { + public BirdsOfAFeather() + { + Activated = true; + Title = 1073007; // Birds of a Feather + Description = + 1073022; // I bet you can't kill ... ten harpies! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Harpy) }, "harpies")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class Frightmares : MLQuest + { + public Frightmares() + { + Activated = true; + Title = 1073000; // Frightmares + Description = + 1073036; // I bet you can't handle ten plague spawns! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(PlagueSpawn) }, "plague spawns")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class MoltenReptiles : MLQuest + { + public MoltenReptiles() + { + Activated = true; + Title = 1072989; // Molten Reptiles + Description = + 1073018; // I bet you can't kill ... say ten ... lava lizards! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(LavaLizard) }, "lava lizards")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class BloodyNuisance : MLQuest + { + public BloodyNuisance() + { + Activated = true; + Title = 1072992; // Bloody Nuisance + Description = + 1073021; // I bet you can't kill ... ten gore fiends! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(GoreFiend) }, "gore fiends")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class BloodSuckers : MLQuest + { + public BloodSuckers() + { + Activated = true; + Title = 1072997; // Blood Suckers + Description = + 1073025; // I bet you can't tangle with those bloodsuckers ... say around ten vampire bats! I bet they're too much for you. You may as well confess you can't ... + RefusalMessage = 1073019; // Hahahaha! I knew it! + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(VampireBat) }, "vampire bats")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class TheAfterlife : MLQuest + { + public TheAfterlife() + { + Activated = true; + Title = 1073073; // The Afterlife + Description = + 1073563; // Nobody told me about the Mummy's Curse. How was I supposed to know you shouldn't disturb the tombs? Oh, sure, now all I hear about is the curse of the vengeful dead. I'll tell you what - make a few of these mummies go away and we'll keep this between you and me. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073583; // Uh, I don't think you're quite done killing Mummies yet. + + Objectives.Add(new KillObjective(15, new[] { typeof(Mummy) }, "mummies")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ForkedTongue : MLQuest + { + public ForkedTongue() + { + Activated = true; + Title = 1073655; // Forked Tongue + Description = + 1073694; // I must implore you, brave traveler, to do battle with the vile reptiles which haunt these parts. Those hideous abominations, the Ophidians, are a blight across the land. If you were able to put down a host of the scaly warriors, the Knights or the Avengers, I would forever be in your debt. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073735; // Have you killed the Ophidian Knights or Avengers? + + Objectives.Add(new KillObjective(10, new[] { typeof(OphidianKnight) }, + "ophidian avengers or ophidian knight-errants")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class ImpishDelights : MLQuest + { + public ImpishDelights() + { + Activated = true; + Title = 1073077; // Impish Delights + Description = + 1073567; // Imps! Do you hear me? Imps! They're everywhere! They're in everything! Oh, don't be fooled by their size - they vicious little devils! Half-sized evil incarnate, they are! Somebody needs to send them back to where they came from, if you know what I mean. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1073587; // Don't let the little devils scare you! You kill 12 imps - then we'll talk reward. + + Objectives.Add(new KillObjective(12, new[] { typeof(Imp) }, "imps")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ThreeWishes : MLQuest + { + public ThreeWishes() + { + Activated = true; + Title = 1073660; // Three Wishes + Description = + 1073699; // If I had but one wish, it would be to rid myself of these dread Efreet! Fire and ash, they are cunning and deadly! You look a brave soul - would you be interested in earning a rich reward for slaughtering a few of the smoky devils? + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073740; // Those smoky devils, the Efreets, are still about. + + Objectives.Add(new KillObjective(8, new[] { typeof(Efreet) }, "efreets")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class EvilEye : MLQuest + { + public EvilEye() + { + Activated = true; + Title = 1073084; // Evil Eye + Description = + 1073574; // Kind traveler, hear my plea. You know of the evil orbs? The wrathful eyes? Some call them gazers? They must be a nest nearby, for they are tormenting us poor folk. We need to drive back their numbers. But we are not strong enough to face such horrors ourselves, we need a true hero. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073594; // Have you annihilated a dozen Gazers yet, kind traveler? + + Objectives.Add(new KillObjective(12, new[] { typeof(Gazer) }, "gazers")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class GargoylesWrath : MLQuest + { + public GargoylesWrath() + { + Activated = true; + Title = 1073658; // Gargoyle's Wrath + Description = + 1073697; // It is regretable that the Gargoyles insist upon warring with us. Their Enforcers attack men on sight, despite all efforts at reason. To help maintain order in this region, I have been authorized to encourage bounty hunters to reduce their numbers. Eradicate their number and I will reward you handsomely. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073738; // I won't be able to pay you until you've gotten enough Gargoyle Enforcers. + + Objectives.Add(new KillObjective(6, new[] { typeof(GargoyleEnforcer) }, "gargoyle enforcers")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class UndeadMages : MLQuest + { + public UndeadMages() + { + Activated = true; + Title = 1073080; // Undead Mages + Description = + 1073570; // Why must the dead plague the living? With their foul necromancy and dark sorceries, the undead menace the countryside. I fear what will happen if no one is strong enough to face these nightmare sorcerers and thin their numbers. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073590; // Surely, a brave soul like yourself can kill 10 Bone Magi and Skeletal Mages? + + Objectives.Add(new KillObjective(10, new[] { typeof(BoneMagi), typeof(SkeletalMage) }, + "bone mages or skeletal mages")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class FriendlyNeighborhoodSpiderkiller : MLQuest + { + public FriendlyNeighborhoodSpiderkiller() + { + Activated = true; + Title = 1073662; // Friendly Neighborhood Spider-killer + Description = + 1073701; // They aren't called Dread Spiders because they're fluffy and cuddly now, are they? No, there's nothing appealing about those wretches so I sure wouldn't lose any sleep if you were to exterminate a few. I'd even part with a generous amount of gold, I would. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073742; // Dread Spiders? I say keep exterminating the arachnid vermin. + + Objectives.Add(new KillObjective(8, new[] { typeof(DreadSpider) }, "dread spiders")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class MongbatMenace : MLQuest + { + public MongbatMenace() + { + Activated = true; + Title = 1073003; // Mongbat Menace! + Description = + 1073033; // I imagine you don't know about the mongbats. Well, you may think you do, but I know more than just about anyone. You see they come in two varieties ... the stronger and the weaker. Either way, they're a menace. Exterminate ten of the weaker ones and four of the stronger and I'll pay you an honest wage. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Mongbat) }, "mongbats")); + Objectives.Add(new KillObjective(4, new[] { typeof(GreaterMongbat) }, "greater mongbats")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class StirringTheNest : MLQuest + { + public StirringTheNest() + { + Activated = true; + Title = 1073087; // Stirring the Nest + Description = + 1073577; // Were you the sort of child that enjoyed knocking over anthills? Well, perhaps you'd like to try something a little bigger? There's a Solen nest nearby and I bet if you killed a queen or two, it would be quite the sight to behold. I'd even pay to see that - what do you say? + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073597; // Dead Solen Queens isn't too much to ask, is it? + + ObjectiveType = ObjectiveType.Any; + + Objectives.Add(new KillObjective(3, new[] { typeof(RedSolenQueen) }, "red solen queens")); + Objectives.Add(new KillObjective(3, new[] { typeof(BlackSolenQueen) }, "black solen queens")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class WarriorCaste : MLQuest + { + public WarriorCaste() + { + Activated = true; + Title = 1073078; // Warrior Caste + Description = + 1073568; // The Terathan are an aggressive species. Left unchecked, they will swarm across our lands. And where will that leave us? Compost in the hive, that's what! Stop them, stop them cold my friend. Kill their warriors and you'll check their movement, that is certain. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1073588; // Unless you kill at least 10 Terathan Warriors, you won't have any impact on their hive. + + Objectives.Add(new KillObjective(10, new[] { typeof(TerathanWarrior) }, "terathan warriors")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class BigWorms : MLQuest + { + public BigWorms() + { + Activated = true; + Title = 1073088; // Big Worms + Description = + 1073578; // It makes no sense! Cold blooded serpents cannot live in the ice! It's a biological impossibility! They are an abomination against reason! Please, I beg you - kill them! Make them disappear for me! Do this and I will reward you. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073598; // You wouldn't try and just pretend you murdered 10 Giant Ice Worms, would you? + + Objectives.Add(new KillObjective(10, new[] { typeof(IceSerpent) }, "giant ice serpents")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class OrcishElite : MLQuest + { + public OrcishElite() + { + Activated = true; + Title = 1073081; // Orcish Elite + Description = + 1073571; // Foul brutes! No one loves an orc, but some of them are worse than the rest. Their Captains and their Bombers, for instance, they're the worst of the lot. Kill a few of those, and the rest are just a rabble. Exterminate a few of them and you'll make the world a sunnier place, don't you know. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1073591; // The only good orc is a dead orc - and 4 dead Captains and 6 dead Bombers is even better! + + Objectives.Add(new KillObjective(6, new[] { typeof(OrcBomber) }, "orc bombers")); + Objectives.Add(new KillObjective(4, new[] { typeof(OrcCaptain) }, "orc captain")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ThinningTheHerd : MLQuest + { + public ThinningTheHerd() + { + Activated = true; + Title = 1072249; // Thinning the Herd + Description = + 1072263; // Psst! Hey ... psst! Listen, I need some help here but it's gotta be hush hush. I don't want THEM to know I'm onto them. They watch me. I've seen them, but they don't know that I know what I know. You know? Anyway, I need you to scare them off by killing a few of them. That'll send a clear message that I won't suffer goats watching me! + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Goat) }, "goats")); + + Rewards.Add(ItemReward.SmallBagOfTrinkets); + } + } + + public class Squishy : MLQuest + { + public Squishy() + { + Activated = true; + Title = 1072998; // Squishy + Description = + 1073031; // Have you ever seen what a slime can do to good gear? Well, it's not pretty, let me tell you! If you take on my task to destroy twelve of them, bear that in mind. They'll corrode your equipment faster than anything. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(12, new[] { typeof(Slime) }, "slimes")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class OrcSlaying : MLQuest + { + public OrcSlaying() + { + Activated = true; + Title = 1072986; // Orc Slaying + Description = + 1073015; // Those green-skinned freaks have run off with more of my livestock. I want an orc scout killed for each sheep I lost and an orc for each chicken. So that's four orc scouts and eight orcs I'll pay you to slay. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(8, new[] { typeof(Orc) }, "orcs")); + // TODO: This needs to be orc scouts but they aren't in the SVN + Objectives.Add(new KillObjective(4, new[] { typeof(OrcishLord) }, "orcish lords")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class ABigJob : MLQuest + { + public ABigJob() + { + Activated = true; + Title = 1072988; // A Big Job + Description = + 1073017; // It's a big job but you look to be just the adventurer to do it! I'm so glad you came by ... I'm paying well for the death of five ogres and five ettins. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(5, new[] { typeof(Ogre) }, "ogres")); + Objectives.Add(new KillObjective(5, new[] { typeof(Ettin) }, "ettins")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class TrollingForTrolls : MLQuest + { + public TrollingForTrolls() + { + Activated = true; + Title = 1072985; // Trolling for Trolls + Description = + 1073014; // They may not be bright, but they're incredibly destructive. Kill off ten trolls and I'll consider it a favor done for me. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Troll) }, "trolls")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class ColdHearted : MLQuest + { + public ColdHearted() + { + Activated = true; + Title = 1072991; // Cold Hearted + Description = + 1073027; // It's a big job but you look to be just the adventurer to do it! I'm so glad you came by ... I'm paying well for the death of six giant ice serpents and six frost spiders. Hop to it, if you're so inclined. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(6, new[] { typeof(IceSerpent) }, "giant ice serpents")); + Objectives.Add(new KillObjective(6, new[] { typeof(FrostSpider) }, "frost spiders")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class ForkedTongues : MLQuest + { + public ForkedTongues() + { + Activated = true; + Title = 1072984; // Forked Tongues + Description = + 1073013; // You can't trust them, you know. Lizardmen I mean. They have forked tongues ... and you know what that means. Exterminate ten of them and I'll reward you. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Lizardman) }, "lizardmen")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class ShakingThingsUp : MLQuest + { + public ShakingThingsUp() + { + Activated = true; + Title = 1073083; // Shaking Things Up + Description = + 1073573; // A Solen hive is a fascinating piece of ecology. It's put together like a finely crafted clock. Who knows what happens if you remove something? So let's find out. Exterminate a few of the warriors and I'll make it worth your while. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1073593; // I don't think you've gotten their attention yet -- you need to kill at least 10 Solen Warriors. + + ObjectiveType = ObjectiveType.Any; + + Objectives.Add(new KillObjective(10, new[] { typeof(RedSolenWarrior) }, "red solen warriors")); + Objectives.Add(new KillObjective(10, new[] { typeof(BlackSolenWarrior) }, "black solen warriors")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class Arachnophobia : MLQuest + { + public Arachnophobia() + { + Activated = true; + Title = 1073079; // Arachnophobia + Description = + 1073569; // I've seen them hiding in their webs among the woods. Glassy eyes, spindly legs, poisonous fangs. Monsters, I say! Deadly horrors, these black widows. Someone must exterminate the abominations! If only I could find a worthy hero for such a task, then I could give them this considerable reward. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1073589; // You've got a good start, but to stop the black-eyed fiends, you need to kill a dozen. + + Objectives.Add(new KillObjective(12, new[] { typeof(GiantBlackWidow) }, "giant black widows")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class MiniSwampThing : MLQuest + { + public MiniSwampThing() + { + Activated = true; + Title = 1073072; // Mini Swamp Thing + Description = + 1073562; // Some say killing a boggling brings good luck. I don't place much stock in old wives' tales, but I can say a few dead bogglings would certainly be lucky for me! Help me out and I can reward you for your efforts. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073582; // Go back and kill all 20 bogglings! + + Objectives.Add(new KillObjective(12, new[] { typeof(Bogling) }, "boglings")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ThePerilsOfFarming : MLQuest + { + public ThePerilsOfFarming() + { + Activated = true; + Title = 1073664; // The Perils of Farming + Description = + 1073703; // I should be trimming back the vegetation here, but something nasty has taken root. Viscious vines I can't go near. If there's any hope of getting things under control, some one's going to need to destroy a few of those Whipping Vines. Someone strong and fast and tough. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073744; // How are farmers supposed to work with these Whipping Vines around? + + Objectives.Add(new KillObjective(15, new[] { typeof(WhippingVine) }, "whipping vines")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class IndustriousAsAnAntLion : MLQuest + { + public IndustriousAsAnAntLion() + { + Activated = true; + Title = 1073665; // Industrious as an Ant Lion + Description = + 1073704; // Ants are industrious and Lions are noble so who'd think an Ant Lion would be such a problem? The Ant Lion's have been causing mindless destruction in these parts. I suppose it's just how ants are. But I need you to help eliminate the infestation. Would you be willing to help for a bit of reward? + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073745; // Please, rid us of the Ant Lion infestation. + + Objectives.Add(new KillObjective(12, new[] { typeof(AntLion) }, "ant lions")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class UnholyConstruct : MLQuest + { + public UnholyConstruct() + { + Activated = true; + Title = 1073666; // Unholy Construct + Description = + 1073705; // They're unholy, I say. Golems, a walking mockery of all life, born of blackest magic. They're not truly alive, so destroying them isn't a crime, it's a service. A service I will gladly pay for. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073746; // The unholy brutes, the Golems, must be smited! + CompletionMessage = 1073787; // Reduced those Golems to component parts? Good, then -- you deserve this reward! + + Objectives.Add(new KillObjective(10, new[] { typeof(Golem) }, "golems")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class AChillInTheAir : MLQuest + { + public AChillInTheAir() + { + Activated = true; + Title = 1073663; // A Chill in the Air + Description = + 1073702; // Feel that chill in the air? It means an icy death for the unwary, for deadly Ice Elementals are about. Who knows what magic summoned them, what's important now is getting rid of them. I don't have much, but I'll give all I can if you'd only stop the cold-hearted monsters. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073746; // The chill won't lift until you eradicate a few Ice Elemenals. + + Objectives.Add(new KillObjective(15, new[] { typeof(IceElemental) }, "ice elementals")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class TheKingOfClothing : MLQuest + { + public TheKingOfClothing() + { + Activated = true; + HasRestartDelay = true; + Title = 1073902; // The King of Clothing + Description = + 1074092; // I have heard noble tales of a fine and proud human garment. An article of clothing fit for both man and god alike. It is called a "kilt" I believe? Could you fetch for me some of these kilts so I that I might revel in their majesty and glory? + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073948; // I will be in your debt if you bring me kilts. + CompletionMessage = 1073974; // I say truly - that is a magnificent garment! You have more than earned a reward. + + Objectives.Add(new CollectObjective(10, typeof(Kilt), 1025431)); // kilt + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class ThePuffyShirt : MLQuest + { + public ThePuffyShirt() + { + Activated = true; + HasRestartDelay = true; + Title = 1073903; // The Puffy Shirt + Description = + 1074093; // We elves believe that beauty is expressed in all things, including the garments we wear. I wish to understand more about human aesthetics, so please kind traveler - could you bring to me magnificent examples of human fancy shirts? For my thanks, I could teach you more about the beauty of elven vestements. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073949; // I will be in your debt if you bring me fancy shirts. + CompletionMessage = 1073973; // I appreciate your service. Now, see what elven hands can create. + + Objectives.Add(new CollectObjective(10, typeof(FancyShirt), 1027933)); // fancy shirt + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class FromTheGaultierCollection : MLQuest + { + public FromTheGaultierCollection() + { + Activated = true; + HasRestartDelay = true; + Title = 1073905; // From the Gaultier Collection + Description = + 1074095; // It is my understanding, the females of humankind actually wear on certain occasions a studded bustier? This is not simply a fanciful tale? Remarkable! It sounds hideously uncomfortable as well as ludicrously impracticle. But perhaps, I simply do not understand the nuances of human clothing. Perhaps, I need to see such a studded bustier for myself? + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073951; // I will be in your debt if you bring me studded bustiers. + CompletionMessage = 1073976; // Truly, it is worse than I feared. Still, I appreciate your efforts on my behalf. + + Objectives.Add(new CollectObjective(10, typeof(StuddedBustierArms), 1027180)); // studded bustier + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class HauteCouture : MLQuest + { + public HauteCouture() + { + Activated = true; + HasRestartDelay = true; + Title = 1073901; // Hâute Couture + Description = + 1074091; // Most human apparel is interesting to elven eyes. But there is one garment - the flower garland - which sounds very elven indeed. Could I see how a human crafts such an object of beauty? In exchange, I could share with you the wonders of elven garments. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073947; // I will be in your debt if you bring me flower garlands. + CompletionMessage = 1073973; // I appreciate your service. Now, see what elven hands can create. + + Objectives.Add(new CollectObjective(10, typeof(FlowerGarland), 1028965)); // flower garland + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class TheSongOfTheWind : MLQuest + { + public TheSongOfTheWind() + { + Activated = true; + HasRestartDelay = true; + Title = 1073910; // The Song of the Wind + Description = + 1074100; // To give voice to the passing wind, this is an idea worthy of an elf! Friend, bring me some of the amazing fancy wind chimes so that I may listen to the song of the passing breeze. Do this, and I will share with you treasured elven secrets. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073956; // I will be in your debt if you bring me fancy wind chimes. + CompletionMessage = 1073980; // Such a delightful sound, I think I shall never tire of it. + + Objectives.Add(new CollectObjective(10, typeof(FancyWindChimes), "fancy wind chimes")); + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class BeerGoggles : MLQuest + { + public BeerGoggles() + { + Activated = true; + HasRestartDelay = true; + Title = 1073895; // Beer Goggles + Description = + 1074085; // Oh, the deviltry! Why would humans lock their precious liquors inside a wooden coffin? I understand I need a "keg tap" to access the golden brew within such a wooden abomination. Perhaps, if you could bring me such a tap, we could share a drink and I could teach you. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073941; // I will be in your debt if you bring me barrel taps. + CompletionMessage = 1073971; // My thanks for your service. Here is something for you to enjoy. + + Objectives.Add(new CollectObjective(25, typeof(BarrelTap), 1024100)); // barrel tap + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class MessageInABottleQuest : MLQuest + { + public MessageInABottleQuest() + { + Activated = true; + HasRestartDelay = true; + Title = 1073894; // Message in a Bottle + Description = + 1074084; // We elves are interested in trading our wines with humans but we understand human usually trade such brew in strange transparent bottles. If you could provide some of these empty glass bottles, I might engage in a bit of elven winemaking. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073940; // I will be in your debt if you bring me empty bottles. + CompletionMessage = 1073971; // My thanks for your service. Here is something for you to enjoy. + + Objectives.Add(new CollectObjective(50, typeof(Bottle), 1023854)); // empty bottle + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class NecessitysMother : MLQuest + { + public NecessitysMother() + { + Activated = true; + HasRestartDelay = true; + Title = 1073906; // Necessity's Mother + Description = + 1074096; // What a thing, this human need to tinker. It seems there is no end to what might be produced with a set of Tinker's Tools. Who knows what an elf might build with some? Could you obtain some tinker's tools and bring them to me? In exchange, I offer you elven lore and knowledge. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073952; // I will be in your debt if you bring me tinker's tools. + CompletionMessage = 1073977; // Now, I shall see what an elf can invent! + + Objectives.Add(new CollectObjective(10, typeof(TinkerTools), 1027868)); // tinker's tools + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class TickTock : MLQuest + { + public TickTock() + { + Activated = true; + HasRestartDelay = true; + Title = 1073907; // Tick Tock + Description = + 1074097; // Elves find it remarkable the human preoccupation with the passage of time. To have built instruments to try and capture time -- it is a fascinating notion. I would like to see how a clock is put together. Maybe you could provide some clocks for my experimentation? + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073953; // I will be in your debt if you bring me clocks. + CompletionMessage = 1073978; // Enjoy my thanks for your service. + + Objectives.Add(new CollectObjective(10, typeof(Clock), 1024171)); // clock + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class ReptilianDentist : MLQuest + { + public ReptilianDentist() + { + Activated = true; + Title = 1074280; // Reptilian Dentist + Description = + 1074710; // I'm working on a striking necklace -- something really unique -- and I know just what I need to finish it up. A huge fang! Won't that catch the eye? I would like to employ you to find me such an item, perhaps a snake would make the ideal donor. I'll make it worth your while, of course. + RefusalMessage = 1074723; // I understand. I don't like snakes much either. They're so creepy. + InProgressMessage = + 1074722; // Those really big snakes like swamps, I've heard. You might try the blighted grove. + CompletionMessage = 1074721; // Do you have it? *gasp* What a tooth! Here � I must get right to work. + + Objectives.Add(new CollectObjective(1, typeof(CoilsFang), "coil's fang")); + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class StopHarpingOnMe : MLQuest + { + public StopHarpingOnMe() + { + Activated = true; + HasRestartDelay = true; + Title = 1073881; // Stop Harping on Me + Description = + 1074071; // Humans artistry can be a remarkable thing. For instance, I have heard of a wonderful instrument which creates the most melodious of music. A lap harp. I would be ever so grateful if I could examine one in person. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073927; // I will be in your debt if you bring me lap harp. + CompletionMessage = 1073969; // My thanks for your service. Now, I will show you something of elven carpentry. + + Objectives.Add(new CollectObjective(20, typeof(LapHarp), 1023762)); // lap harp + + Rewards.Add(ItemReward.CarpentrySatchel); + } + } + + public class TheFarEye : MLQuest + { + public TheFarEye() + { + Activated = true; + HasRestartDelay = true; + Title = 1073908; // The Far Eye + Description = + 1074098; // The wonders of human invention! Turning sand and metal into a far-seeing eye! This is something I must experience for myself. Bring me some of these spyglasses friend human. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073954; // I will be in your debt if you bring me spyglasses. + CompletionMessage = 1073978; // Enjoy my thanks for your service. + + Objectives.Add(new CollectObjective(20, typeof(Spyglass), 1025365)); // spyglass + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class LethalDarts : MLQuest + { + public LethalDarts() + { + Activated = true; + HasRestartDelay = true; + Title = 1073876; // Lethal Darts + Description = + 1074066; // We elves are no strangers to archery but I would be interested in learning whether there is anything to learn from the human approach. I would gladly trade you something I have if you could teach me of the deadly crossbow bolt. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073922; // I will be in your debt if you bring me crossbow bolts. + CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. + CompletionNotice = CompletionNoticeCraft; + + Objectives.Add(new CollectObjective(10, typeof(Bolt), 1027163)); // crossbow bolt + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class ASimpleBow : MLQuest + { + public ASimpleBow() + { + Activated = true; + HasRestartDelay = true; + Title = 1073877; // A Simple Bow + Description = + 1074067; // I wish to try a bow crafted in the human style. Is it possible for you to bring me such a weapon? I would be happy to return this favor. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073923; // I will be in your debt if you bring me bows. + CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. + CompletionNotice = CompletionNoticeCraft; + + Objectives.Add(new CollectObjective(10, typeof(Bow), 1025041)); // bow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class IngeniousArcheryPartOne : MLQuest + { + public IngeniousArcheryPartOne() + { + Activated = true; + HasRestartDelay = true; + Title = 1073878; // Ingenious Archery, Part I + Description = + 1074068; // I have heard of a curious type of bow, you call it a "crossbow". It sounds fascinating and I would very much like to examine one closely. Would you be able to obtain such an instrument for me? + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073924; // I will be in your debt if you bring me crossbows. + CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. + CompletionNotice = CompletionNoticeCraft; + + Objectives.Add(new CollectObjective(10, typeof(Crossbow), 1023919)); // crossbow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class IngeniousArcheryPartTwo : MLQuest + { + public IngeniousArcheryPartTwo() + { + Activated = true; + HasRestartDelay = true; + Title = 1073879; // Ingenious Archery, Part II + Description = + 1074069; // These human "crossbows" are complex and clever. The "heavy crossbow" is a remarkable instrument of war. I am interested in seeing one up close, if you could arrange for one to make its way to my hands. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073925; // I will be in your debt if you bring me heavy crossbows. + CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. + CompletionNotice = CompletionNoticeCraft; + + Objectives.Add(new CollectObjective(8, typeof(HeavyCrossbow), 1025116)); // heavy crossbow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class IngeniousArcheryPartThree : MLQuest + { + public IngeniousArcheryPartThree() + { + Activated = true; + HasRestartDelay = true; + Title = 1073880; // Ingenious Archery, Part III + Description = + 1074070; // My friend, I am in search of a device, a instrument of remarkable human ingenuity. It is a repeating crossbow. If you were to obtain such a device, I would gladly reveal to you some of the secrets of elven craftsmanship. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073926; // I will be in your debt if you bring me repeating crossbows. + CompletionMessage = 1073968; // My thanks for your service. Now, I shall teach you of elven archery. + CompletionNotice = CompletionNoticeCraft; + + Objectives.Add(new CollectObjective(10, typeof(RepeatingCrossbow), 1029923)); // repeating crossbow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class ScaleArmor : MLQuest + { + public ScaleArmor() + { + Activated = true; + Title = 1074711; // Scale Armor + Description = + 1074712; // Here's what I need ... there are some creatures called hydra, fearsome beasts, whose scales are especially suitable for a new sort of armor that I'm developing. I need a few such pieces and then some supple alligator skin for the backing. I'm going to need a really large piece that's shaped just right ... the tail I think would do nicely. I appreciate your help. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1074724; // Hydras have been spotted in the Blighted Grove. You won't get those scales without getting your feet wet, I'm afraid. + CompletionMessage = 1074725; // I can't wait to get to work now that you've returned with my scales. + + Objectives.Add(new CollectObjective(1, typeof(ThrashersTail), "Thrasher's Tail")); + Objectives.Add(new CollectObjective(10, typeof(HydraScale), "Hydra Scales")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class CutsBothWays : MLQuest + { + public CutsBothWays() + { + Activated = true; + HasRestartDelay = true; + Title = 1073913; // Cuts Both Ways + Description = + 1074103; // What would you say is a typical human instrument of war? Is a broadsword a typical example? I wish to see more of such human weapons, so I would gladly trade elven knowledge for human steel. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073959; // I will be in your debt if you bring me broadswords. + CompletionMessage = 1073978; // Enjoy my thanks for your service. + + Objectives.Add(new CollectObjective(12, typeof(Broadsword), 1023934)); // broadsword + + Rewards.Add(ItemReward.BlacksmithSatchel); + } + } + + public class DragonProtection : MLQuest + { + public DragonProtection() + { + Activated = true; + HasRestartDelay = true; + Title = 1073915; // Dragon Protection + Description = + 1074105; // Mankind, I am told, knows how to take the scales of a terrible dragon and forge them into powerful armor. Such a feat of craftsmanship! I would give anything to view such a creation - I would even teach some of the prize secrets of the elven people. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073961; // I will be in your debt if you bring me dragon armor. + CompletionMessage = 1073978; // Enjoy my thanks for your service. + + Objectives.Add(new CollectObjective(10, typeof(DragonHelm), 1029797)); // dragon helm + + Rewards.Add(ItemReward.BlacksmithSatchel); + } + } + + public class NothingFancy : MLQuest + { + public NothingFancy() + { + Activated = true; + HasRestartDelay = true; + Title = 1073911; // Nothing Fancy + Description = + 1074101; // I am curious to see the results of human blacksmithing. To examine the care and quality of a simple item. Perhaps, a simple bascinet helmet? Yes, indeed -- if you could bring to me some bascinet helmets, I would demonstrate my gratitude. + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073957; // I will be in your debt if you bring me bascinets. + CompletionMessage = 1073978; // Enjoy my thanks for your service. + + Objectives.Add(new CollectObjective(15, typeof(Bascinet), 1025132)); // bascinet + + Rewards.Add(ItemReward.BlacksmithSatchel); + } + } + + public class TheBulwark : MLQuest + { + public TheBulwark() + { + Activated = true; + HasRestartDelay = true; + Title = 1073912; // The Bulwark + Description = + 1074102; // The clank of human iron and steel is strange to elven ears. For instance, the metallic heater shield which human warriors carry into battle. It is odd to an elf, but nevertheless intriguing. Tell me friend, could you bring me such an example of human smithing skill? + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073958; // I will be in your debt if you bring me heater shields. + CompletionMessage = 1073978; // Enjoy my thanks for your service. + + Objectives.Add(new CollectObjective(10, typeof(HeaterShield), 1027030)); // heater shield + + Rewards.Add(ItemReward.BlacksmithSatchel); + } + } + + public class ArchSupport : MLQuest + { + public ArchSupport() + { + Activated = true; + HasRestartDelay = true; + Title = 1073882; // Arch Support + Description = + 1074072; // How clever humans are - to understand the need of feet to rest from time to time! Imagine creating a special stool just for weary toes. I would like to examine and learn the secret of their making. Would you bring me some foot stools to examine? + RefusalMessage = 1073921; // I will patiently await your reconsideration. + InProgressMessage = 1073928; // I will be in your debt if you bring me foot stools. + CompletionMessage = 1073969; // My thanks for your service. Now, I will show you something of elven carpentry. + + Objectives.Add(new CollectObjective(10, typeof(FootStool), 1022910)); // foot stool + + Rewards.Add(ItemReward.CarpentrySatchel); + } + } + + public class ParoxysmusSuccubi : MLQuest + { + public ParoxysmusSuccubi() + { + Activated = true; + Title = 1073067; // Paroxysmus' Succubi + Description = + 1074696; // The succubi that have congregated within the sinkhole to worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(3, new[] { typeof(Succubus) }, "succubi", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class ParoxysmusMoloch : MLQuest + { + public ParoxysmusMoloch() + { + Activated = true; + Title = 1073068; // Paroxysmus' Moloch + Description = + 1074695; // The moloch daemons that have congregated to worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(3, new[] { typeof(Moloch) }, "molochs", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class ParoxysmusDaemons : MLQuest + { + public ParoxysmusDaemons() + { + Activated = true; + Title = 1073069; // Paroxysmus' Daemons + Description = + 1074694; // The daemons that have congregated to worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(Daemon) }, "daemons", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class ParoxysmusArcaneDaemons : MLQuest + { + public ParoxysmusArcaneDaemons() + { + Activated = true; + Title = 1073070; // Paroxysmus' Arcane Daemons + Description = + 1074697; // The arcane daemons that worship Paroxysmus pose a tremendous danger. Will you enter the lair and see to their destruction? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(ArcaneDaemon) }, "arcane daemons", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class CausticCombo : MLQuest + { + public CausticCombo() + { + Activated = true; + Title = 1073062; // Caustic Combo + Description = + 1074693; // Vile creatures have exited the sinkhole and begun terrorizing the surrounding area. The demons are bad enough, but the elementals are an abomination, their poisons seeping into the fertile ground here. Will you enter the sinkhole and put a stop to their depredations? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(3, new[] { typeof(PoisonElemental) }, "poison elementals", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + Objectives.Add(new KillObjective(6, new[] { typeof(AcidElemental) }, "acid elementals", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class PlagueLord : MLQuest + { + public PlagueLord() + { + Activated = true; + Title = 1073061; // Plague Lord + Description = + 1074692; // Some of the most horrific creatures have slithered out of the sinkhole there and begun terrorizing the surrounding area. The plague creatures are one of the most destruction of the minions of Paroxysmus. Are you willing to do something about them? + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(10, new[] { typeof(PlagueSpawn) }, "plague spawns", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + Objectives.Add(new KillObjective(3, new[] { typeof(PlagueBeast) }, "plague beasts", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + Objectives.Add(new KillObjective(1, new[] { typeof(PlagueBeastLord) }, "plague beast lord", + new QuestArea(1074806, "The Palace of Paroxysmus"))); // The Palace of Paroxysmus + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class GlassyFoe : MLQuest + { + public GlassyFoe() + { + Activated = true; + Title = 1073055; // Glassy Foe + Description = + 1074669; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal lattice seekers. + RefusalMessage = 1074671; // These abominations must not be permitted to fester! + InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. + CompletionMessage = 1074673; // You have done well. Enjoy this reward. + + Objectives.Add(new KillObjective(5, new[] { typeof(CrystalLatticeSeeker) }, "crystal lattice seekers", + new QuestArea(1074805, "The Prism of Light"))); // The Prism of Light + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class DaemonicPrism : MLQuest + { + public DaemonicPrism() + { + Activated = true; + Title = 1073053; // Daemonic Prism + Description = + 1074668; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal daemons. + RefusalMessage = 1074671; // These abominations must not be permitted to fester! + InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. + CompletionMessage = 1074673; // You have done well. Enjoy this reward. + + Objectives.Add(new KillObjective(3, new[] { typeof(CrystalDaemon) }, "crystal daemons", + new QuestArea(1074805, "The Prism of Light"))); // The Prism of Light + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class Hailstorm : MLQuest + { + public Hailstorm() + { + Activated = true; + Title = 1073057; // Hailstorm + Description = + 1074670; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal vortices. + RefusalMessage = 1074671; // These abominations must not be permitted to fester! + InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. + CompletionMessage = 1074673; // You have done well. Enjoy this reward. + + Objectives.Add(new KillObjective(8, new[] { typeof(CrystalVortex) }, "crystal vortices", + new QuestArea(1074805, "The Prism of Light"))); // The Prism of Light + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + /* TODO: Uncomment when Crystal Hydra is added + public class HowManyHeads : MLQuest + { + public HowManyHeads() + { + Activated = true; + Title = 1073050; // How Many Heads? + Description = 1074674; // Good, you're here. The presence of a twisted creature deep under the earth near Nu'Jelm has corrupted the natural growth of crystals in that region. They've become infused with the twisting energy - they've come to a sort of life. This is an abomination that festers within Sosaria. You must eradicate the crystal hydras. + RefusalMessage = 1074671; // These abominations must not be permitted to fester! + InProgressMessage = 1074672; // You must not waste time. Do not suffer these crystalline abominations to live. + CompletionMessage = 1074673; // You have done well. Enjoy this reward. + + Objectives.Add( new KillObjective( 3, new Type[] { typeof( CrystalHydra ) }, "crystal hydras", new QuestArea( 1074805, "The Prism of Light" ) ) ); // The Prism of Light + + Rewards.Add( ItemReward.LargeBagOfTreasure ); + } + } + */ + + /* TODO: Uncomment when Dreadhorn is added + public class DreadhornQuest : MLQuest + { + public DreadhornQuest() + { + Activated = true; + Title = 1074645; // Dreadhorn + Description = 1074646; // Can you comprehend it? I cannot, I confess. The most pristine and perfect Lord of Sosaria has fallen prey to the blight. From the depths of my heart I mourn his corruption; my thoughts are filled with pity for this glorious creature now tainted. And my blood boils with fury at those responsible for the innocent creature's undoing. Will you find Dread Horn, as he is now called, and free him from this misery? + RefusalMessage = 1074647; // How can you not feel as I do? + InProgressMessage = 1074648; // The lush and fertile land where Dread Horn now lives is twisted and tainted, a result of his corruption. The fey folk have sealed the land off through their magics, but you can enter through an enchanted mushroom fairy circle. + CompletionMessage = 1074649; // Thank you. I haven't the words to express my gratitude. + + Objectives.Add( new KillObjective( 1, new Type[] { typeof( DreadHorn ) }, "dread horn" ) ); + + Rewards.Add( ItemReward.RewardStrongbox ); + } + } + */ + + /* TODO: Uncomment when SerpentsFangHighExecutioner, TigersClawThief and DragonsFlameGrandMage are added + public class NewLeadership : MLQuest + { + public NewLeadership() + { + Activated = true; + Title = 1072905; // New Leadership + Description = 1072963; // I have a task for you ... adventurer. Will you risk all to win great renown? The Black Order is organized into three sects, each with their own speciality. The Dragon's Flame serves the will of the Grand Mage, the Tiger's Claw answers to the Master Thief, and the Serpent's Fang kills at the direction of the High Executioner. Slay all three and you will strike the order a devastating blow! + RefusalMessage = 1072973; // I do not fault your decision. + InProgressMessage = 1072974; // Once you gain entrance into The Citadel, you will need to move cautiously to find the sect leaders. + + Objectives.Add( new KillObjective( 1, new Type[] { typeof( SerpentsFangHighExecutioner ) }, "serpent's fang high executioner", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel + Objectives.Add( new KillObjective( 1, new Type[] { typeof( TigersClawThief ) }, "tiger's claw thief", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel + Objectives.Add( new KillObjective( 1, new Type[] { typeof( DragonsFlameGrandMage ) }, "dragon's flame mage", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel + + Rewards.Add( ItemReward.RewardStrongbox ); + } + } + */ + + /* TODO: Uncomment when SerpentsFangAssassin is added + public class ExAssassins : MLQuest + { + public ExAssassins() + { + Activated = true; + Title = 1072917; // Ex-Assassins + Description = 1072969; // The Serpent's Fang sect members have gone too far! Express to them my displeasure by slaying ten of them. But remember, I do not condone war on women, so I will only accept the deaths of men, human and elf. + RefusalMessage = 1072979; // As you wish. + InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. + + // TODO: This has to be MALES only! + Objectives.Add( new KillObjective( 10, new Type[] { typeof( SerpentsFangAssassin ) }, "male serpent's fang assassins", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel + + Rewards.Add( ItemReward.BagOfTreasure ); + } + } + */ + + /* TODO: Uncomment when DragonsFlameMage is added + public class ExtinguishingTheFlame : MLQuest + { + public ExtinguishingTheFlame() + { + Activated = true; + Title = 1072911; // Extinguishing the Flame + Description = 1072966; // The Dragon's Flame sect members have gone too far! Express to them my displeasure by slaying ten of them. But remember, I do not condone war on women, so I will only accept the deaths of men, human or elf. Either race will do, I care not for the shape of their ears. Yes, this action will properly make clear my disapproval and has a pleasing harmony. + RefusalMessage = 1072979; // As you wish. + InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. + + // TODO: This has to be MALES only! + Objectives.Add( new KillObjective( 10, new Type[] { typeof( DragonsFlameMage ) }, "male dragon's flame mages", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel + + Rewards.Add( ItemReward.BagOfTreasure ); + } + } + */ + + public class DeathToTheNinja : MLQuest + { + public DeathToTheNinja() + { + Activated = true; + Title = 1072913; // Death to the Ninja! + Description = + 1072966; // I wish to make a statement of censure against the elite ninjas of the Black Order. Deliver, in the strongest manner, my disdain. But do not make war on women, even those that take arms against you. It is not ... fitting. + RefusalMessage = 1072979; // As you wish. + InProgressMessage = + 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. + + // TODO: Verify that this has to be males only (as per the description) + Objectives.Add(new KillObjective(10, new[] { typeof(EliteNinja) }, "elite ninjas", + new QuestArea(1074804, "The Citadel"))); // The Citadel + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + /* TODO: Uncomment when TigersClawThief is added + public class CrimeAndPunishment : MLQuest + { + public CrimeAndPunishment() + { + Activated = true; + Title = 1072914; // Crime and Punishment + Description = 1072968; // The Tiger's Claw sect members have gone too far! Express to them my displeasure by slaying ten of them. But remember, I do not condone war on women, so I will only accept the deaths of men, human and elf. + RefusalMessage = 1072979; // As you wish. + InProgressMessage = 1072980; // The Black Order's fortress home is well hidden. Legend has it that a humble fishing village disguises the magical portal. + + // TODO: This has to be MALES only! + Objectives.Add( new KillObjective( 10, new Type[] { typeof( TigersClawThief ) }, "male tiger's claw thieves", new QuestArea( 1074804, "The Citadel" ) ) ); // The Citadel + + Rewards.Add( ItemReward.BagOfTreasure ); + } + } + */ + + /* TODO: Uncomment when ShimmeringEffusion is added + public class AllThatGlittersIsNotGood : MLQuest + { + public AllThatGlittersIsNotGood() + { + Activated = true; + Title = 1073048; // All That Glitters is Not Good + Description = 1074654; // The most incredible tale has reached my ears! Deep within the bowels of Sosaria, somewhere under the city of Nu'Jelm, a twisted creature feeds. What created this abomination, no one knows ... though there is some speculation that the fumbling initial efforts to open the portal to The Heartwood, brought it into existence. Regardless of it's origin, it must be destroyed before it damages Sosaria. Will you undertake this quest? + RefusalMessage = 1074655; // Perhaps I thought too highly of you. + InProgressMessage = 1074656; // An explorer discovered the cave system under Nu'Jelm. He made multiple trips into the place bringing back fascinating crystals and artifacts that suggested the hollow place in Sosaria was inhabited by other creatures at some point. You'll need to follow in his footsteps to find this abomination and destroy it. + CompletionMessage = 1074657; // I am overjoyed with your efforts! Your devotion to Sosaria is noted and appreciated. + + Objectives.Add( new KillObjective( 1, new Type[] { typeof( ShimmeringEffusion ) }, "shimmering effusion" ) ); + + Rewards.Add( ItemReward.RewardStrongbox ); + } + } + */ + + #endregion + + #region Mobiles + + [QuesterName("Saril (The Heartwood)")] + public class Saril : BaseCreature + { + [Constructible] + public Saril() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the guard"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new WoodlandLegs()); + AddItem(new WoodlandArms()); + AddItem(new WoodlandBelt()); + AddItem(new WingedHelm()); + AddItem(new FemaleElvenPlateChest()); + AddItem(new RadiantScimitar()); + } + + public Saril(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Saril"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074186, // Come here, I have a task. + 1074183 // You there! I have a job for you. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Cailla (The Heartwood)")] + public class Cailla : BaseCreature + { + [Constructible] + public Cailla() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the guard"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new HidePants()); + AddItem(new HidePauldrons()); + AddItem(new HideGloves()); + AddItem(new WoodlandBelt()); + AddItem(new RavenHelm()); + AddItem(new HideFemaleChest()); + AddItem(new MagicalShortbow()); + } + + public Cailla(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Cailla"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074187, // Want a job? + 1074210 // Hi.� Looking for something to do? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Tamm (The Heartwood)")] + public class Tamm : BaseCreature + { + [Constructible] + public Tamm() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the guard"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new HidePants()); + AddItem(new HidePauldrons()); + AddItem(new WingedHelm()); + AddItem(new HideChest()); + AddItem(new ElvenCompositeLongbow()); + } + + public Tamm(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Tamm"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074213, // Hey buddy.� Looking for work? + 1074187 // Want a job? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Landy (The Heartwood)")] + public class Landy : BaseCreature + { + [Constructible] + public Landy() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the soil nurturer"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(Utility.RandomYellowHue())); + AddItem(new ShortPants(Utility.RandomYellowHue())); + AddItem(new Tunic(Utility.RandomYellowHue())); + + Item gloves = new LeafGloves(); + gloves.Hue = Utility.RandomYellowHue(); + AddItem(gloves); + } + + public Landy(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Landy"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074211, // I could use some help. + 1074218 // Hey!� I want to talk to you, now. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Elder Alejaha (The Heartwood)")] + public class Alejaha : BaseCreature + { + [Constructible] + public Alejaha() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(Utility.RandomYellowHue())); + AddItem(new ElvenShirt(Utility.RandomYellowHue())); + AddItem(new GemmedCirclet()); + AddItem(new Cloak(Utility.RandomBrightHue())); + + if (Utility.RandomBool()) + AddItem(new Kilt(0x387)); + else + AddItem(new Skirt(0x387)); + } + + public Alejaha(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Alejaha"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074223); // Have you done it yet?� Oh, I haven�t told you, have I? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Mielan (The Heartwood)")] + public class Mielan : BaseCreature + { + [Constructible] + public Mielan() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the arcanist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x901)); + AddItem(new ElvenShirt(0x56)); + AddItem(new GemmedCirclet()); + AddItem(new ElvenPants(0x901)); + } + + public Mielan(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Mielan"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074219, // Hello there, can I have a moment of your time? + 1074223 // Have you done it yet?� Oh, I haven�t told you, have I? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Ciala (The Heartwood)")] + public class Ciala : BaseCreature + { + [Constructible] + public Ciala() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the arborist"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Skirt(Utility.RandomBlueHue())); + AddItem(new ElvenShirt(Utility.RandomYellowHue())); + AddItem(new RoyalCirclet()); + + if (Utility.RandomBool()) + AddItem(new Boots(Utility.RandomYellowHue())); + else + AddItem(new ThighBoots(Utility.RandomYellowHue())); + } + + public Ciala(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Ciala"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074206, // Excuse me please traveler, might I have a little of your time? + 1074186 // Come here, I have a task. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Aniel (The Heartwood)")] + public class Aniel : BaseCreature + { + [Constructible] + public Aniel() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the arborist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenPants(0x901)); + AddItem(new LeafChest()); + AddItem(new HalfApron(Utility.RandomYellowHue())); + AddItem(new ElvenBoots(0x901)); + } + + public Aniel(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Aniel"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074220, // May I call you friend?� I have a favor to beg of you. + 1074222 // Could I trouble you for some assistance? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Aulan (The Heartwood)")] + public class Aulan : BaseCreature + { + [Constructible] + public Aulan() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the expeditionist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + Item item; + + item = new ElvenBoots(); + item.Hue = Utility.RandomYellowHue(); + AddItem(item); + + AddItem(new ElvenPants(Utility.RandomGreenHue())); + AddItem(new Cloak(Utility.RandomGreenHue())); + AddItem(new Circlet()); + + item = new HideChest(); + item.Hue = Utility.RandomYellowHue(); + AddItem(item); + + item = new HideGloves(); + item.Hue = Utility.RandomYellowHue(); + AddItem(item); + } + + public Aulan(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Aulan"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074188, // Weakling! You are not up to the task I have. + 1074191, // Just keep walking away!� I thought so. Coward!� I�ll bite your legs off! + 1074195 // You there, in the stupid hat! Come here. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Brinnae (The Heartwood)")] + public class Brinnae : BaseCreature + { + [Constructible] + public Brinnae() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots()); + AddItem(new FemaleLeafChest()); + AddItem(new LeafArms()); + AddItem(new HidePants()); + AddItem(new ElvenCompositeLongbow()); + } + + public Brinnae(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Brinnae"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074212, // *yawn* You busy? + 1074210 // Hi.� Looking for something to do? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Elder Caelas (The Heartwood)")] + public class Caelas : BaseCreature + { + [Constructible] + public Caelas() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x1BB)); + AddItem(new MaleElvenRobe(0x489)); + AddItem(new Cloak(0x718)); + AddItem(new RoyalCirclet()); + } + + public Caelas(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Caelas"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074204, // Greetings seeker.� I have an urgent matter for you, if you are willing. + 1074201 // Waste not a minute! There�s work to be done. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Clehin (The Heartwood)")] + public class Clehin : BaseCreature + { + [Constructible] + public Clehin() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the soil nurturer"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new ElvenShirt()); + AddItem(new LeafTonlet()); + } + + public Clehin(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Clehin"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074211, // I could use some help. + 1074186 // Come here, I have a task. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Cloorne : BaseCreature + { + [Constructible] + public Cloorne() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the expeditionist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x3B2)); + AddItem(new RadiantScimitar()); + AddItem(new WingedHelm()); + + Item item; + + item = new WoodlandLegs(); + item.Hue = 0x74A; + AddItem(item); + + item = new HideChest(); + item.Hue = 0x726; + AddItem(item); + + item = new LeafArms(); + item.Hue = 0x73E; + AddItem(item); + } + + public Cloorne(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Cloorne"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074185, // Hey you! Want to help me out? + 1074186 //Come here, I have a task. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Salaenih (The Heartwood)")] + public class Salaenih : BaseCreature + { + [Constructible] + public Salaenih() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the expeditionist"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new WarCleaver()); + + Item item; + + item = new WoodlandBelt(); + item.Hue = 0x597; + AddItem(item); + + item = new VultureHelm(); + item.Hue = 0x1BB; + AddItem(item); + + item = new WoodlandLegs(); + item.Hue = 0x1BB; + AddItem(item); + + item = new WoodlandChest(); + item.Hue = 0x1BB; + AddItem(item); + + item = new WoodlandArms(); + item.Hue = 0x1BB; + AddItem(item); + } + + public Salaenih(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Salaenih"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074207, // Good day to you friend! Allow me to offer you a fabulous opportunity!� Thrills and adventure await! + 1074209 // Hey, could you help me out with something? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Vilo (The Heartwood)")] + public class Vilo : BaseCreature + { + [Constructible] + public Vilo() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the guard"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x901)); + AddItem(new OrnateAxe()); + AddItem(new WoodlandBelt(0x592)); + AddItem(new VultureHelm()); + AddItem(new WoodlandLegs()); + AddItem(new WoodlandChest()); + AddItem(new WoodlandArms()); + AddItem(new WoodlandGorget()); + } + + public Vilo(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Vilo"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074210, // Hi.� Looking for something to do? + 1074220 // May I call you friend?� I have a favor to beg of you. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Tholef (The Heartwood)")] + public class Tholef : BaseCreature + { + [Constructible] + public Tholef() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the grape tender"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x901)); + AddItem(new FullApron(0x756)); + AddItem(new ShortPants(0x28C)); + AddItem(new Shirt(0x28C)); + + Item item; + + item = new LeafArms(); + item.Hue = 0x28C; + AddItem(item); + } + + public Tholef(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Tholef"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074209, // Hey, could you help me out with something? + 1074184 // Come here, I have work for you. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Tillanil (The Heartwood)")] + public class Tillanil : BaseCreature + { + [Constructible] + public Tillanil() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the grape tender"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x1BB)); + AddItem(new Tunic(0x759)); + AddItem(new ShortPants(0x21)); + } + + public Tillanil(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Tillanil"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074187, // Want a job? + 1074222 // Could I trouble you for some assistance? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Waelian (The Heartwood)")] + public class Waelian : BaseCreature + { + [Constructible] + public Waelian() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the trinket weaver"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Shoes(0x901)); + AddItem(new SmithHammer()); + AddItem(new LongPants(0x340)); + AddItem(new GemmedCirclet()); + + Item item; + + item = new LeafChest(); + item.Hue = 0x344; + AddItem(item); + } + + public Waelian(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Waelian"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074221, // Greetings!� I have a small task for you good traveler. + 1074201 // Waste not a minute! There�s work to be done. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Sleen (The Heartwood)")] + public class Sleen : BaseCreature + { + [Constructible] + public Sleen() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the trinket weaver"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x901)); + AddItem(new SmithHammer()); + AddItem(new Cloak(0x75A)); + AddItem(new ElvenShirt()); + } + + public Sleen(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Sleen"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074200, // Thank goodness you are here, there�s no time to lose. + 1074206 // Excuse me please traveler, might I have a little of your time? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Unoelil (The Heartwood)")] + public class Unoelil : BaseCreature + { + [Constructible] + public Unoelil() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the bark weaver"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x1BB)); + AddItem(new ShortPants(0x1BB)); + AddItem(new Tunic(0x64D)); + } + + public Unoelil(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Unoelil"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074186, // Come here, I have a task. + 1074209 // Hey, could you help me out with something? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Anolly (The Heartwood)")] + public class Anolly : BaseCreature + { + [Constructible] + public Anolly() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the bark weaver"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x901)); + AddItem(new ShortPants(0x3B3)); + AddItem(new FullApron(0x1BB)); + AddItem(new SmithHammer()); + } + + public Anolly(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Anolly"; + public override bool CanTeach => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Jusae (The Heartwood)")] + public class Jusae : BaseCreature + { + [Constructible] + public Jusae() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the bowcrafter"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x901)); + AddItem(new ShortPants(0x661)); + AddItem(new MagicalShortbow()); + + Item item; + + item = new HideChest(); + item.Hue = 0x27B; + AddItem(item); + + item = new HidePauldrons(); + item.Hue = 0x27E; + AddItem(item); + } + + public Jusae(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Jusae"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074210, // Hi.� Looking for something to do? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Cillitha (The Heartwood)")] + public class Cillitha : BaseCreature + { + [Constructible] + public Cillitha() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the bowcrafter"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x901)); + AddItem(new ElvenShirt(0x731)); + AddItem(new LeafLegs()); + } + + public Cillitha(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Cillitha"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074223, // Have you done it yet?� Oh, I haven�t told you, have I? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Lohn (The Heartwood)")] + public class Lohn : BaseCreature + { + [Constructible] + public Lohn() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the metal weaver"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Shoes(0x901)); + AddItem(new LongPants(0x359)); + AddItem(new SmithHammer()); + AddItem(new GemmedCirclet()); + + Item item; + + item = new LeafChest(); + item.Hue = 0x359; + AddItem(item); + } + + public Lohn(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lohn"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074187, // Want a job? + 1074209 // Hey, could you help me out with something? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Olla (The Heartwood)")] + public class Olla : BaseCreature + { + [Constructible] + public Olla() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the metal weaver"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new LongPants(0x3B3)); + AddItem(new SmithHammer()); + AddItem(new FullApron(0x1BB)); + AddItem(new ElvenShirt()); + } + + public Olla(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Olla"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074187, // Want a job? + 1074185 // Hey you! Want to help me out? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Thallary (The Heartwood)")] + public class Thallary : BaseCreature + { + [Constructible] + public Thallary() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the cloth weaver"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x901)); + AddItem(new LongPants(0x72E)); + AddItem(new Cloak(0x3B3)); + AddItem(new FancyShirt(0x13)); + } + + public Thallary(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Thallary"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074221, // Greetings!� I have a small task for you good traveler. + 1074212 // *yawn* You busy? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Ahie (The Heartwood)")] + public class Ahie : BaseCreature + { + [Constructible] + public Ahie() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the cloth weaver"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Boots(0x901)); + AddItem(new Skirt(0x1C)); + AddItem(new Cloak(0x62)); + AddItem(new FancyShirt(0x738)); + } + + public Ahie(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Ahie"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074206, // Excuse me please traveler, might I have a little of your time? + 1074203 // Hello friend. I realize you are busy but if you would be willing to render me a service I can assure you that you will be judiciously renumerated. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Tyeelor : BaseCreature + { + [Constructible] + public Tyeelor() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the expeditionist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x1BB)); + + Item item; + + item = new WoodlandLegs(); + item.Hue = 0x236; + AddItem(item); + + item = new WoodlandChest(); + item.Hue = 0x236; + AddItem(item); + + item = new WoodlandArms(); + item.Hue = 0x236; + AddItem(item); + + item = new VultureHelm(); + item.Hue = 0x236; + AddItem(item); + + item = new WoodlandBelt(); + item.Hue = 0x236; + AddItem(item); + } + + public Tyeelor(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Tyeelor"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Athailon : BaseCreature + { + [Constructible] + public Athailon() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the expeditionist"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x901)); + AddItem(new WoodlandBelt()); + AddItem(new DiamondMace()); + + Item item; + + item = new WoodlandLegs(); + item.Hue = 0x3B2; + AddItem(item); + + item = new FemaleElvenPlateChest(); + item.Hue = 0x3B2; + AddItem(item); + + item = new WoodlandArms(); + item.Hue = 0x3B2; + AddItem(item); + + item = new WingedHelm(); + item.Hue = 0x3B2; + AddItem(item); + } + + public Athailon(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Athailon"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ElderTaellia : BaseCreature + { + [Constructible] + public ElderTaellia() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ThighBoots(0x127)); + AddItem(new FemaleElvenRobe(Utility.RandomBrightHue())); + AddItem(new MagicWand()); + AddItem(new Circlet()); + } + + public ElderTaellia(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Taellia"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ElderMallew : BaseCreature + { + [Constructible] + public ElderMallew() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x1BB)); + AddItem(new Cloak(0x3B2)); + AddItem(new Circlet()); + + Item item; + + item = new LeafTonlet(); + item.Hue = 0x544; + AddItem(item); + + item = new LeafChest(); + item.Hue = 0x538; + AddItem(item); + + item = new LeafArms(); + item.Hue = 0x528; + AddItem(item); + } + + public ElderMallew(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Mallew"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ElderAbbein : BaseCreature + { + [Constructible] + public ElderAbbein() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x72C)); + AddItem(new FemaleElvenRobe(0x8B0)); + AddItem(new RoyalCirclet()); + } + + public ElderAbbein(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Abbein"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ElderVicaie : BaseCreature + { + [Constructible] + public ElderVicaie() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots()); + AddItem(new Tunic(0x732)); + + Item item; + + item = new LeafLegs(); + item.Hue = 0x3B2; + AddItem(item); + } + + public ElderVicaie(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Vicaie"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ElderJothan : BaseCreature + { + [Constructible] + public ElderJothan() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ThighBoots()); + AddItem(new ElvenPants(0x58D)); + AddItem(new ElvenShirt(Utility.RandomYellowHue())); + AddItem(new Cloak(Utility.RandomBrightHue())); + AddItem(new Circlet()); + } + + public ElderJothan(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Jothan"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ElderAlethanian : BaseCreature + { + [Constructible] + public ElderAlethanian() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots()); + AddItem(new HidePants()); + AddItem(new HideFemaleChest()); + AddItem(new HidePauldrons()); + AddItem(new GemmedCirclet()); + } + + public ElderAlethanian(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Alethanian"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Rebinil : BaseCreature + { + [Constructible] + public Rebinil() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the healer"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Sandals(0x715)); + AddItem(new FemaleElvenRobe(0x742)); + AddItem(new RoyalCirclet()); + } + + public Rebinil(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Rebinil"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Aluniol : BaseCreature + { + [Constructible] + public Aluniol() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the healer"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x1BB)); + AddItem(new MaleElvenRobe(0x47E)); + AddItem(new WildStaff()); + } + + public Aluniol(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Aluniol"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Olaeni : BaseCreature + { + [Constructible] + public Olaeni() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the thaumaturgist"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Shoes(0x75A)); + AddItem(new FemaleElvenRobe(0x13)); + AddItem(new MagicWand()); + AddItem(new GemmedCirclet()); + } + + public Olaeni(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Olaeni"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Bolaevin : BaseCreature + { + [Constructible] + public Bolaevin() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the arcanist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x3B2)); + AddItem(new RoyalCirclet()); + AddItem(new LeafChest()); + AddItem(new LeafArms()); + + Item item; + + item = new LeafLegs(); + item.Hue = 0x1BB; + AddItem(item); + } + + public Bolaevin(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Bolaevin"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LorekeeperAneen : BaseCreature + { + [Constructible] + public LorekeeperAneen() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Sandals(0x1BB)); + AddItem(new MaleElvenRobe(0x48F)); + AddItem(new MagicWand()); + } + + public LorekeeperAneen(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lorekeeper Aneen"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Daelas : BaseCreature + { + [Constructible] + public Daelas() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the arborist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x901)); + AddItem(new ElvenPants(0x8AB)); + + Item item; + + item = new LeafChest(); + item.Hue = 0x8B0; + AddItem(item); + + item = new LeafGloves(); + item.Hue = 0x1BB; + AddItem(item); + } + + public Daelas(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Daelas"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Alelle : BaseCreature + { + [Constructible] + public Alelle() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the arborist"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots(0x1BB)); + + Item item; + + item = new FemaleLeafChest(); + item.Hue = 0x3A; + AddItem(item); + + item = new LeafLegs(); + item.Hue = 0x74C; + AddItem(item); + + item = new LeafGloves(); + item.Hue = 0x1BB; + AddItem(item); + } + + public Alelle(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Alelle"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Nillaen (The Heartwood)")] + public class LorekeeperNillaen : BaseCreature + { + [Constructible] + public LorekeeperNillaen() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Shoes(0x1BB)); + AddItem(new LongPants(0x1FB)); + AddItem(new ElvenShirt()); + AddItem(new GemmedCirclet()); + AddItem(new BodySash(0x25)); + AddItem(new BlackStaff()); + } + + public LorekeeperNillaen(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lorekeeper Nillaen"; + public override bool CanTeach => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Ryal (The Heartwood)")] + public class LorekeeperRyal : BaseCreature + { + [Constructible] + public LorekeeperRyal() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x1BB)); + AddItem(new LeafTonlet()); + AddItem(new ElvenShirt(0x2DD)); + AddItem(new Cloak(0x219)); + AddItem(new GnarledStaff()); + } + + public LorekeeperRyal(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lorekeeper Ryal"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074204, // Greetings seeker.� I have an urgent matter for you, if you are willing. + 1074200 // Thank goodness you are here, there�s no time to lose. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Braen (The Heartwood)")] + public class Braen : BaseCreature + { + [Constructible] + public Braen() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the thaumaturgist"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x714)); + AddItem(new MaleElvenRobe(0x64A)); + AddItem(new MagicWand()); + } + + public Braen(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Braen"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074187); // Want a job? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Elder Acob (The Heartwood)")] + public class ElderAcob : BaseCreature + { + [Constructible] + public ElderAcob() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x714)); + AddItem(new ElvenShirt(Utility.RandomBrightHue())); + AddItem(new HidePants()); + } + + public ElderAcob(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Elder Acob"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074197); // Pardon me, but if you could spare some time I�d greatly appreciate it. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LorekeeperCalendor : BaseCreature + { + [Constructible] + public LorekeeperCalendor() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x714)); + AddItem(new ElvenShirt(Utility.RandomOrangeHue())); + AddItem(new Kilt(Utility.RandomOrangeHue())); + AddItem(new RoyalCirclet()); + } + + public LorekeeperCalendor(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lorekeeper Calendor"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074204); // Greetings seeker.� I have an urgent matter for you, if you are willing. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LorekeeperSiarra : BaseCreature + { + [Constructible] + public LorekeeperSiarra() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x1BB)); + AddItem(new ElvenShirt()); + AddItem(new LeafTonlet()); + AddItem(new GemmedCirclet()); + } + + public LorekeeperSiarra(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lorekeeper Siarra"; + public override bool CanTeach => true; + + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074206); // Excuse me please traveler, might I have a little of your time? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Heritage.cs b/Scripts/Engines/MLQuests/Definitions/Heritage.cs index 6b2d2ecc9..6ea3053b0 100644 --- a/Scripts/Engines/MLQuests/Definitions/Heritage.cs +++ b/Scripts/Engines/MLQuests/Definitions/Heritage.cs @@ -1,792 +1,833 @@ using System; -using Server.Engines.MLQuests.Rewards; using Server.Engines.MLQuests.Objectives; +using Server.Engines.MLQuests.Rewards; using Server.Items; using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Human To Elf Quests - - public class Seasons : MLQuest - { - public override bool RecordCompletion => true; - - public Seasons() - { - Activated = true; - Title = 1072782; // Seasons - Description = 1072802; // *rumbling growl* *sniff* ... not-smell ... seek-fight ... not-smell ... fear-stench ... *rumble* ... cold-soon-time comes ... hungry ... eat-fish ... sleep-soon-time ... *deep fang-filled yawn* ... much-fish. - RefusalMessage = 1072810; // *yawn* ... cold-soon-time ... *growl* - InProgressMessage = 1072811; // *sniff* *sniff* ... not-much-fish ... hungry ... *grumble* - CompletionMessage = 1074174; // *sniff* fish! much-fish! - - Objectives.Add( new CollectObjective( 20, typeof( RawFishSteak ), 1022426 ) ); // raw fish steak - - Rewards.Add( new DummyReward( 1072803 ) ); // The boon of Maul. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074940, "", 0x2A ); // You have gained the boon of Maul! Your understanding of the seasons grows. You are one step closer to claiming your elven heritage. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Darius" ), new Point3D( 4310, 954, 10 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Darius" ), new Point3D( 4310, 954, 10 ), Map.Trammel ); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "MaulTheBear" ), new Point3D( 1730, 257, 16 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "MaulTheBear" ), new Point3D( 1730, 257, 16 ), Map.Trammel ); - } - } - - public class CaretakerOfTheLand : MLQuest - { - public override bool RecordCompletion => true; - - public CaretakerOfTheLand() - { - Activated = true; - Title = 1072783; // Caretaker of the Land - Description = 1072812; // Hrrrrr. Hurrrr. Huuuman. *creaking branches* Suuun on baaark, roooooots diiig deeeeeep, wiiind caaaresses leeeaves … Hrrrrr. Saaap of Sooosaria feeeeeeds us. Hrrrrr. Huuuman leeearn. Caaaretaker of plaaants … teeend … prooove.
- RefusalMessage = 1072813; // Hrrrrr. Hrrrrr. Huuuman. - InProgressMessage = 1072814; // Hrrrr. Hrrrr. Roooooots neeeeeed saaap of Sooosaria. Hrrrrr. Roooooots tiiingle neeeaaar Yeeew. Seeeaaarch. Hrrrr! - CompletionMessage = 1074175; // Thiiirsty. Hurrr. Hurrr. - - Objectives.Add( new CollectObjective( 1, typeof( SapOfSosaria ), "sap of sosaria" ) ); - - Rewards.Add( new DummyReward( 1072804 ) ); // The boon of Strongroot. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074941, "", 0x2A ); // You have gained the boon of Strongroot! You have been approved by one whose roots touch the bones of Sosaria. You are one step closer to claiming your elven heritage. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Strongroot" ), new Point3D( 597, 1744, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Strongroot" ), new Point3D( 597, 1744, 0 ), Map.Trammel ); - - PutSpawner( new Spawner( 1, TimeSpan.FromSeconds( 30 ), TimeSpan.FromMinutes( 2 ), 0, 12, "SapOfSosaria" ), new Point3D( 757, 1004, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, TimeSpan.FromSeconds( 30 ), TimeSpan.FromMinutes( 2 ), 0, 12, "SapOfSosaria" ), new Point3D( 757, 1004, 0 ), Map.Trammel ); - } - } - - public class WisdomOfTheSphynx : MLQuest - { - public override bool RecordCompletion => true; - - public WisdomOfTheSphynx() - { - Activated = true; - Title = 1072784; // Wisdom of the Sphynx - Description = 1072822; // I greet thee human and divine my boon thou seek. Convey hence the object of my riddle and I shall reward thee with thy desire.

Three lives have I.
Gentle enough to soothe the skin,
Light enough to caress the sky,
Hard enough to crack rocks
What am I? - RefusalMessage = 1072823; // As thou wish, human. - InProgressMessage = 1072824; // I give thee a hint then human. The answer to my riddle must be held carefully or it cannot be contained at all. Bring this elusive item to me in a suitable container. - CompletionMessage = 1074176; // Ah, thus it ends. - - Objectives.Add( new InternalObjective() ); - - Rewards.Add( new DummyReward( 1072805 ) ); // The boon of Enigma. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074945, "", 0x2A ); // You have gained the boon of Enigma! You are wise enough to know how little you know. You are one step closer to claiming your elven heritage. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Enigma" ), new Point3D( 1828, 961, 7 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Enigma" ), new Point3D( 1828, 961, 7 ), Map.Trammel ); - } - - private class InternalObjective : CollectObjective - { - public override bool ShowDetailed => false; - - public InternalObjective() - : base( 1, typeof( Pitcher ), 1074869 ) // The answer to the riddle. - { - } - - public override bool CheckItem( Item item ) - { - return ( item is Pitcher pitcher && pitcher.Content == BeverageType.Water && pitcher.Quantity > 0 ); - } - } - } - - public class DefendingTheHerd : MLQuest - { - public override bool RecordCompletion => true; - - public DefendingTheHerd() - { - Activated = true; - Title = 1072785; // Defending the Herd - Description = 1072825; // *snort* ... guard-mates ... guard-herd *hoof stomp* ... defend-with-hoof-and-horn ... thirsty-drink. *proud head-toss* - RefusalMessage = 1072826; // *snort* - InProgressMessage = 1072827; // *impatient hoof stomp* ... thirsty herd ... water scent. - CompletionNotice = CompletionNoticeShort; - - Objectives.Add( new EscortObjective( new QuestArea( 1074779, "Bravehorn's drinking pool" ) ) ); // Bravehorn's drinking pool - - Rewards.Add( new DummyReward( 1072806 ) ); // The boon of Bravehorn. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074942, "", 0x2A ); // You have gained the boon of Bravehorn! You have glimpsed the nobility of those that sacrifice themselves for their people. You are one step closer to claiming your elven heritage. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, TimeSpan.FromSeconds( 30 ), TimeSpan.FromSeconds( 90 ), 0, 5, "Bravehorn" ), new Point3D( 1193, 2467, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, TimeSpan.FromSeconds( 30 ), TimeSpan.FromSeconds( 90 ), 0, 5, "Bravehorn" ), new Point3D( 1193, 2467, 0 ), Map.Trammel ); - - PutSpawner( new Spawner( 5, TimeSpan.FromSeconds( 20 ), TimeSpan.FromSeconds( 30 ), 0, 8, "BravehornsMate" ), new Point3D( 1192, 2467, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 5, TimeSpan.FromSeconds( 20 ), TimeSpan.FromSeconds( 30 ), 0, 8, "BravehornsMate" ), new Point3D( 1192, 2467, 0 ), Map.Trammel ); - } - } - - public class TheBalanceOfNature : MLQuest - { - public override bool RecordCompletion => true; - - public TheBalanceOfNature() - { - Activated = true; - Title = 1072786; // The Balance of Nature - Description = 1072829; // Ho, there human. Why do you seek out the Huntsman? The hunter serves the land by culling both predators and prey. The hunter maintains the essential balance of life and does not kill for sport or glory. If you seek my favor, human, then demonstrate you are capable of the duty. Cull the wolves nearby. - RefusalMessage = 1072830; // Then begone. I have no time to waste on you, human. - InProgressMessage = 1072831; // The timber wolves are easily tracked, human. - - Objectives.Add( new KillObjective( 15, new[] { typeof( TimberWolf ) }, "timber wolves", new QuestArea( 1074833, "Huntsman's Forest" ) ) ); // Huntsman's Forest - - Rewards.Add( new DummyReward( 1072807 ) ); // The boon of the Huntsman. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074943, "", 0x2A ); // You have gained the boon of the Huntsman! You have been given a taste of the bittersweet duty of those who guard the balance. You are one step closer to claiming your elven heritage. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Huntsman" ), new Point3D( 1676, 593, 16 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Huntsman" ), new Point3D( 1676, 593, 16 ), Map.Trammel ); - - PutSpawner( new Spawner( 5, TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 15 ), 0, 10, "TimberWolf" ), new Point3D( 1671, 592, 16 ), Map.Felucca ); - PutSpawner( new Spawner( 5, TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 15 ), 0, 10, "TimberWolf" ), new Point3D( 1671, 592, 16 ), Map.Trammel ); - } - } - - public class TheJoysOfLife : MLQuest - { - public override bool RecordCompletion => true; - - public TheJoysOfLife() - { - Activated = true; - Title = 1072787; // The Joys of Life - Description = 1072832; // *giggle* So serious, so grim! *tickle* Enjoy life! Have fun! Laugh! Be merry! *giggle* Find three of my baubles ... *giggle* I hid them! *giggles hysterically* Hid them! La la la! Bring them quickly! They are magical and will hide themselves again if you are too slow. - RefusalMessage = 1072833; // *giggle* Too serious. Too thinky! - InProgressMessage = 1072834; // Magical baubles hidden, find them as you're bidden! *giggle* - CompletionMessage = 1074177; // *giggle* So pretty! - - Objectives.Add( new CollectObjective( 3, typeof( ABauble ), "arielle's baubles" ) ); - - Rewards.Add( new DummyReward( 1072809 ) ); // The boon of Arielle. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074944, "", 0x2A ); // You have gained the boon of Arielle! You have been taught the importance of laughter and light spirits. You are one step closer to claiming your elven heritage. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Arielle" ), new Point3D( 1560, 1182, -27 ), Map.Ilshenar ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Arielle" ), new Point3D( 3366, 292, 9 ), Map.Felucca ); // Felucca spawn for reds - - PutSpawner( new Spawner( 6, TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 30 ), 0, 20, "ABauble" ), new Point3D( 1585, 1212, -13 ), Map.Ilshenar ); - } - } - - #endregion - - #region Human To Elf Mobiles - - [QuesterName( "Maul" )] - public class MaulTheBear : GrizzlyBear - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Maul"; - - [Constructible] - public MaulTheBear() - { - AI = AIType.AI_Vendor; - FightMode = FightMode.None; - Tamable = false; - } - - public MaulTheBear( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Strongroot : Treefellow - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Strongroot"; - - [Constructible] - public Strongroot() - { - AI = AIType.AI_Vendor; - FightMode = FightMode.None; - } - - public Strongroot( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Enigma : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Enigma"; - - [Constructible] - public Enigma() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - BodyValue = 788; - BaseSoundID = 0x3EE; - - InitStats( 100, 100, 25 ); - } - - public Enigma( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Bravehorn : BaseEscortable - { - public override bool StaticMLQuester => true; - public override bool InitialInnocent => true; - public override string DefaultName => "Bravehorn"; - - [Constructible] - public Bravehorn() - { - } - - public override void InitBody() - { - Body = 0xEA; - - SetStr( 41, 71 ); - SetDex( 47, 77 ); - SetInt( 27, 57 ); - - SetHits( 27, 41 ); - SetMana( 0 ); - - SetDamage( 5, 9 ); - - SetDamageType( ResistanceType.Physical, 100 ); - - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - - SetSkill( SkillName.MagicResist, 26.8, 44.5 ); - SetSkill( SkillName.Tactics, 29.8, 47.5 ); - SetSkill( SkillName.Wrestling, 29.8, 47.5 ); - - Fame = 300; - Karma = 0; - - VirtualArmor = 24; - } - - public override void InitOutfit() - { - } - - public override int GetAttackSound() - { - return 0x82; - } - - public override int GetHurtSound() - { - return 0x83; - } - - public override int GetDeathSound() - { - return 0x84; - } - - public Bravehorn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BravehornsMate : Hind - { - public override string DefaultName => "bravehorn's mate"; - - [Constructible] - public BravehornsMate() - { - Tamable = false; - } - - public BravehornsMate( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Huntsman : Centaur - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Huntsman"; - - [Constructible] - public Huntsman() - { - AI = AIType.AI_Vendor; - FightMode = FightMode.None; - } - - public Huntsman( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Arielle : Pixie - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Arielle"; - - [Constructible] - public Arielle() - { - AI = AIType.AI_Vendor; - FightMode = FightMode.None; - } - - public Arielle( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion - - #region Elf To Human Quests - - public class Ingenuity : MLQuest - { - public override bool RecordCompletion => true; - - public Ingenuity() - { - Activated = true; - Title = 1074350; // Ingenuity - Description = 1074462; // The best thing about my job is that I do a little bit of everything, every day. It's what we're good at really. Just picking up something and making it do something else. Listen, I'm really low on parts. Are you interested in fetching me some supplies? - RefusalMessage = 1074508; // Okay. Best of luck with your other endeavors. - InProgressMessage = 1074509; // Lord overseers are the best source I know for power crystals of the type I need. Iron golems too, can have them but they're harder to find. - CompletionMessage = 1074510; // Do you have those power crystals? I'm ready to put the finishing touches on my latest experiment. - CompletionNotice = CompletionNoticeShortReturn; - - Objectives.Add( new CollectObjective( 10, typeof( PowerCrystal ), "Power Crystals" ) ); - - Rewards.Add( new DummyReward( 1074875 ) ); // Another step closer to becoming human. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074946, "", 0x2A ); // You have demonstrated your ingenuity! Humans are jacks of all trades and know a little about a lot of things. You are one step closer to achieving humanity. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Nedrick" ), new Point3D( 2958, 3466, 15 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Nedrick" ), new Point3D( 2958, 3466, 15 ), Map.Trammel ); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Sledge" ), new Point3D( 2673, 2129, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Sledge" ), new Point3D( 2673, 2129, 0 ), Map.Trammel ); - } - } - - public class HeaveHo : MLQuest - { - public override bool RecordCompletion => true; - - public HeaveHo() - { - Activated = true; - Title = 1074351; // Heave Ho! - Description = 1074519; // Ho there! There's nothing quite like a day's honest labor to make you appreciate being alive. Hey, maybe you'd like to help out with this project? These crates need to be delivered to Sledge. The only thing is -- it's a bit of a rush job and if you don't make it in time, he won't take them. Can I trust you to help out? - RefusalMessage = 1074521; // Oh yah, if you're too busy, no problem. - InProgressMessage = 1074522; // Sledge can be found in Buc's Den. Better hurry, he won't take those crates if you take too long with them. - CompletionMessage = 1074523; // Hey, if you have cargo for me, you can start unloading over here. - CompletionNotice = CompletionNoticeShort; - - Objectives.Add( new TimedDeliverObjective( TimeSpan.FromHours( 1 ), typeof( CrateForSledge ), 5, "Crates for Sledge", typeof( Sledge ) ) ); - - Rewards.Add( new DummyReward( 1074875 ) ); // Another step closer to becoming human. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074948, "", 0x2A ); // You have demonstrated your physical strength! Humans can carry vast loads without complaint. You are one step closer to achieving humanity. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Patricus" ), new Point3D( 3007, 823, -2 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Patricus" ), new Point3D( 3007, 823, -2 ), Map.Trammel ); - } - } - - // This is not a real quest, it is only used as a reference - public class HumanInNeed : MLQuest - { - public override bool RecordCompletion => true; - - public HumanInNeed() - { - Title = 1075011; // A quest that asks you to defend a human in need. - Description = 0; - RefusalMessage = 0; - InProgressMessage = 0; - } - - public static void AwardTo( PlayerMobile pm ) - { - MLQuestSystem.GetOrCreateContext( pm ).SetDoneQuest( MLQuestSystem.FindQuest( typeof( HumanInNeed ) ) ); - pm.SendLocalizedMessage( 1074949, "", 0x2A ); // You have demonstrated your compassion! Your kind actions have been noted. - } - } - - public class AllSeasonAdventurer : MLQuest - { - public override bool RecordCompletion => true; - - public AllSeasonAdventurer() - { - Activated = true; - Title = 1074353; // All Season Adventurer - Description = 1074527; // It's all about hardship, suffering, struggle and pain. Without challenges, you've got nothing to test yourself against -- and that's what life is all about. Self improvement! Honing your body and mind! Overcoming obstacles ... You'll see what I mean if you take on my challenge. - RefusalMessage = 1074528; // My way of life isn't for everyone, that's true enough. - InProgressMessage = 1074529; // You're not making much progress in the honing-mind-and-body department, are you? - CompletionNotice = CompletionNoticeShortReturn; - - Objectives.Add( new KillObjective( 5, new[] { typeof( Efreet ) }, "efreets", new QuestArea( 1074808, "Fire" ) ) ); // Fire - Objectives.Add( new KillObjective( 5, new[] { typeof( IceFiend ) }, "ice fiends", new QuestArea( 1074809, "Ice" ) ) ); // Ice - - Rewards.Add( new DummyReward( 1074875 ) ); // Another step closer to becoming human. - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.Player.SendLocalizedMessage( 1074947, "", 0x2A ); // You have demonstrated your toughness! Humans are able to endure unimaginable hardships in pursuit of their goals. You are one step closer to achieving humanity. - instance.ClaimRewards(); // skip gump - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Belulah" ), new Point3D( 3782, 1266, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Belulah" ), new Point3D( 3782, 1266, 0 ), Map.Trammel ); - } - } - - #endregion - - #region Elf To Human Mobiles - - [QuesterName( "Sledge (Buc's Den)" )] - public class Sledge : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Sledge"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074188, // Weakling! You are not up to the task I have. - 1074195 // You there, in the stupid hat! Come here. - ) ); - } - - [Constructible] - public Sledge() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Versatile"; - Body = 400; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - AddItem( new Tunic( Utility.RandomNeutralHue() ) ); - AddItem( new LongPants( Utility.RandomBlueHue() ) ); - AddItem( new Cloak( Utility.RandomBrightHue() ) ); - AddItem( new ElvenBoots( Utility.RandomNeutralHue() ) ); - AddItem( new Backpack() ); - } - - public Sledge( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Patricus (Vesper)" )] - public class Patricus : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Patricus"; - - [Constructible] - public Patricus() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Trader"; - Body = 400; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - AddItem( new FancyShirt( Utility.RandomNeutralHue() ) ); - AddItem( new LongPants( Utility.RandomBrightHue() ) ); - AddItem( new Cloak( 0x1BB ) ); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); - AddItem( new Backpack() ); - } - - public Patricus( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Belulah (Nujel'm)" )] // On OSI it's "Belulah (Nu'Jelm)" (incorrect spelling) - public class Belulah : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Belulah"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - /* - * 1074205 - Oh great adventurer, would you please assist a weak soul in need of aid? - * 1074206 - Excuse me please traveler, might I have a little of your time? - */ - MLQuestSystem.Tell( this, pm, Utility.Random( 1074205, 2 ) ); - } - - [Constructible] - public Belulah() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the scorned"; - Female = true; - Body = 401; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new FancyShirt( Utility.RandomBlueHue() ) ); - AddItem( new LongPants( Utility.RandomNondyedHue() ) ); - AddItem( new Boots() ); - } - - public Belulah( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #region Human To Elf Quests + + public class Seasons : MLQuest + { + public Seasons() + { + Activated = true; + Title = 1072782; // Seasons + Description = + 1072802; // *rumbling growl* *sniff* ... not-smell ... seek-fight ... not-smell ... fear-stench ... *rumble* ... cold-soon-time comes ... hungry ... eat-fish ... sleep-soon-time ... *deep fang-filled yawn* ... much-fish. + RefusalMessage = 1072810; // *yawn* ... cold-soon-time ... *growl* + InProgressMessage = 1072811; // *sniff* *sniff* ... not-much-fish ... hungry ... *grumble* + CompletionMessage = 1074174; // *sniff* fish! much-fish! + + Objectives.Add(new CollectObjective(20, typeof(RawFishSteak), 1022426)); // raw fish steak + + Rewards.Add(new DummyReward(1072803)); // The boon of Maul. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074940, "", + 0x2A); // You have gained the boon of Maul! Your understanding of the seasons grows. You are one step closer to claiming your elven heritage. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Darius"), new Point3D(4310, 954, 10), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Darius"), new Point3D(4310, 954, 10), Map.Trammel); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "MaulTheBear"), new Point3D(1730, 257, 16), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "MaulTheBear"), new Point3D(1730, 257, 16), Map.Trammel); + } + } + + public class CaretakerOfTheLand : MLQuest + { + public CaretakerOfTheLand() + { + Activated = true; + Title = 1072783; // Caretaker of the Land + Description = + 1072812; // Hrrrrr. Hurrrr. Huuuman. *creaking branches* Suuun on baaark, roooooots diiig deeeeeep, wiiind caaaresses leeeaves … Hrrrrr. Saaap of Sooosaria feeeeeeds us. Hrrrrr. Huuuman leeearn. Caaaretaker of plaaants … teeend … prooove.
+ RefusalMessage = 1072813; // Hrrrrr. Hrrrrr. Huuuman. + InProgressMessage = + 1072814; // Hrrrr. Hrrrr. Roooooots neeeeeed saaap of Sooosaria. Hrrrrr. Roooooots tiiingle neeeaaar Yeeew. Seeeaaarch. Hrrrr! + CompletionMessage = 1074175; // Thiiirsty. Hurrr. Hurrr. + + Objectives.Add(new CollectObjective(1, typeof(SapOfSosaria), "sap of sosaria")); + + Rewards.Add(new DummyReward(1072804)); // The boon of Strongroot. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074941, "", + 0x2A); // You have gained the boon of Strongroot! You have been approved by one whose roots touch the bones of Sosaria. You are one step closer to claiming your elven heritage. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Strongroot"), new Point3D(597, 1744, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Strongroot"), new Point3D(597, 1744, 0), Map.Trammel); + + PutSpawner(new Spawner(1, TimeSpan.FromSeconds(30), TimeSpan.FromMinutes(2), 0, 12, "SapOfSosaria"), + new Point3D(757, 1004, 0), Map.Felucca); + PutSpawner(new Spawner(1, TimeSpan.FromSeconds(30), TimeSpan.FromMinutes(2), 0, 12, "SapOfSosaria"), + new Point3D(757, 1004, 0), Map.Trammel); + } + } + + public class WisdomOfTheSphynx : MLQuest + { + public WisdomOfTheSphynx() + { + Activated = true; + Title = 1072784; // Wisdom of the Sphynx + Description = + 1072822; // I greet thee human and divine my boon thou seek. Convey hence the object of my riddle and I shall reward thee with thy desire.

Three lives have I.
Gentle enough to soothe the skin,
Light enough to caress the sky,
Hard enough to crack rocks
What am I? + RefusalMessage = 1072823; // As thou wish, human. + InProgressMessage = + 1072824; // I give thee a hint then human. The answer to my riddle must be held carefully or it cannot be contained at all. Bring this elusive item to me in a suitable container. + CompletionMessage = 1074176; // Ah, thus it ends. + + Objectives.Add(new InternalObjective()); + + Rewards.Add(new DummyReward(1072805)); // The boon of Enigma. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074945, "", + 0x2A); // You have gained the boon of Enigma! You are wise enough to know how little you know. You are one step closer to claiming your elven heritage. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Enigma"), new Point3D(1828, 961, 7), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Enigma"), new Point3D(1828, 961, 7), Map.Trammel); + } + + private class InternalObjective : CollectObjective + { + public InternalObjective() + : base(1, typeof(Pitcher), 1074869) // The answer to the riddle. + { + } + + public override bool ShowDetailed => false; + + public override bool CheckItem(Item item) + { + return item is Pitcher pitcher && pitcher.Content == BeverageType.Water && pitcher.Quantity > 0; + } + } + } + + public class DefendingTheHerd : MLQuest + { + public DefendingTheHerd() + { + Activated = true; + Title = 1072785; // Defending the Herd + Description = + 1072825; // *snort* ... guard-mates ... guard-herd *hoof stomp* ... defend-with-hoof-and-horn ... thirsty-drink. *proud head-toss* + RefusalMessage = 1072826; // *snort* + InProgressMessage = 1072827; // *impatient hoof stomp* ... thirsty herd ... water scent. + CompletionNotice = CompletionNoticeShort; + + Objectives.Add( + new EscortObjective(new QuestArea(1074779, "Bravehorn's drinking pool"))); // Bravehorn's drinking pool + + Rewards.Add(new DummyReward(1072806)); // The boon of Bravehorn. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074942, "", + 0x2A); // You have gained the boon of Bravehorn! You have glimpsed the nobility of those that sacrifice themselves for their people. You are one step closer to claiming your elven heritage. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, TimeSpan.FromSeconds(30), TimeSpan.FromSeconds(90), 0, 5, "Bravehorn"), + new Point3D(1193, 2467, 0), Map.Felucca); + PutSpawner(new Spawner(1, TimeSpan.FromSeconds(30), TimeSpan.FromSeconds(90), 0, 5, "Bravehorn"), + new Point3D(1193, 2467, 0), Map.Trammel); + + PutSpawner(new Spawner(5, TimeSpan.FromSeconds(20), TimeSpan.FromSeconds(30), 0, 8, "BravehornsMate"), + new Point3D(1192, 2467, 0), Map.Felucca); + PutSpawner(new Spawner(5, TimeSpan.FromSeconds(20), TimeSpan.FromSeconds(30), 0, 8, "BravehornsMate"), + new Point3D(1192, 2467, 0), Map.Trammel); + } + } + + public class TheBalanceOfNature : MLQuest + { + public TheBalanceOfNature() + { + Activated = true; + Title = 1072786; // The Balance of Nature + Description = + 1072829; // Ho, there human. Why do you seek out the Huntsman? The hunter serves the land by culling both predators and prey. The hunter maintains the essential balance of life and does not kill for sport or glory. If you seek my favor, human, then demonstrate you are capable of the duty. Cull the wolves nearby. + RefusalMessage = 1072830; // Then begone. I have no time to waste on you, human. + InProgressMessage = 1072831; // The timber wolves are easily tracked, human. + + Objectives.Add(new KillObjective(15, new[] { typeof(TimberWolf) }, "timber wolves", + new QuestArea(1074833, "Huntsman's Forest"))); // Huntsman's Forest + + Rewards.Add(new DummyReward(1072807)); // The boon of the Huntsman. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074943, "", + 0x2A); // You have gained the boon of the Huntsman! You have been given a taste of the bittersweet duty of those who guard the balance. You are one step closer to claiming your elven heritage. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Huntsman"), new Point3D(1676, 593, 16), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Huntsman"), new Point3D(1676, 593, 16), Map.Trammel); + + PutSpawner(new Spawner(5, TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(15), 0, 10, "TimberWolf"), + new Point3D(1671, 592, 16), Map.Felucca); + PutSpawner(new Spawner(5, TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(15), 0, 10, "TimberWolf"), + new Point3D(1671, 592, 16), Map.Trammel); + } + } + + public class TheJoysOfLife : MLQuest + { + public TheJoysOfLife() + { + Activated = true; + Title = 1072787; // The Joys of Life + Description = + 1072832; // *giggle* So serious, so grim! *tickle* Enjoy life! Have fun! Laugh! Be merry! *giggle* Find three of my baubles ... *giggle* I hid them! *giggles hysterically* Hid them! La la la! Bring them quickly! They are magical and will hide themselves again if you are too slow. + RefusalMessage = 1072833; // *giggle* Too serious. Too thinky! + InProgressMessage = 1072834; // Magical baubles hidden, find them as you're bidden! *giggle* + CompletionMessage = 1074177; // *giggle* So pretty! + + Objectives.Add(new CollectObjective(3, typeof(ABauble), "arielle's baubles")); + + Rewards.Add(new DummyReward(1072809)); // The boon of Arielle. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074944, "", + 0x2A); // You have gained the boon of Arielle! You have been taught the importance of laughter and light spirits. You are one step closer to claiming your elven heritage. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Arielle"), new Point3D(1560, 1182, -27), Map.Ilshenar); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Arielle"), new Point3D(3366, 292, 9), + Map.Felucca); // Felucca spawn for reds + + PutSpawner(new Spawner(6, TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(30), 0, 20, "ABauble"), + new Point3D(1585, 1212, -13), Map.Ilshenar); + } + } + + #endregion + + #region Human To Elf Mobiles + + [QuesterName("Maul")] + public class MaulTheBear : GrizzlyBear + { + [Constructible] + public MaulTheBear() + { + AI = AIType.AI_Vendor; + FightMode = FightMode.None; + Tamable = false; + } + + public MaulTheBear(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Maul"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Strongroot : Treefellow + { + [Constructible] + public Strongroot() + { + AI = AIType.AI_Vendor; + FightMode = FightMode.None; + } + + public Strongroot(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Strongroot"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Enigma : BaseCreature + { + [Constructible] + public Enigma() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + BodyValue = 788; + BaseSoundID = 0x3EE; + + InitStats(100, 100, 25); + } + + public Enigma(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Enigma"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Bravehorn : BaseEscortable + { + [Constructible] + public Bravehorn() + { + } + + public Bravehorn(Serial serial) + : base(serial) + { + } + + public override bool StaticMLQuester => true; + public override bool InitialInnocent => true; + public override string DefaultName => "Bravehorn"; + + public override void InitBody() + { + Body = 0xEA; + + SetStr(41, 71); + SetDex(47, 77); + SetInt(27, 57); + + SetHits(27, 41); + SetMana(0); + + SetDamage(5, 9); + + SetDamageType(ResistanceType.Physical, 100); + + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Cold, 5, 10); + + SetSkill(SkillName.MagicResist, 26.8, 44.5); + SetSkill(SkillName.Tactics, 29.8, 47.5); + SetSkill(SkillName.Wrestling, 29.8, 47.5); + + Fame = 300; + Karma = 0; + + VirtualArmor = 24; + } + + public override void InitOutfit() + { + } + + public override int GetAttackSound() + { + return 0x82; + } + + public override int GetHurtSound() + { + return 0x83; + } + + public override int GetDeathSound() + { + return 0x84; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BravehornsMate : Hind + { + [Constructible] + public BravehornsMate() + { + Tamable = false; + } + + public BravehornsMate(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "bravehorn's mate"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Huntsman : Centaur + { + [Constructible] + public Huntsman() + { + AI = AIType.AI_Vendor; + FightMode = FightMode.None; + } + + public Huntsman(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Huntsman"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Arielle : Pixie + { + [Constructible] + public Arielle() + { + AI = AIType.AI_Vendor; + FightMode = FightMode.None; + } + + public Arielle(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Arielle"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion + + #region Elf To Human Quests + + public class Ingenuity : MLQuest + { + public Ingenuity() + { + Activated = true; + Title = 1074350; // Ingenuity + Description = + 1074462; // The best thing about my job is that I do a little bit of everything, every day. It's what we're good at really. Just picking up something and making it do something else. Listen, I'm really low on parts. Are you interested in fetching me some supplies? + RefusalMessage = 1074508; // Okay. Best of luck with your other endeavors. + InProgressMessage = + 1074509; // Lord overseers are the best source I know for power crystals of the type I need. Iron golems too, can have them but they're harder to find. + CompletionMessage = + 1074510; // Do you have those power crystals? I'm ready to put the finishing touches on my latest experiment. + CompletionNotice = CompletionNoticeShortReturn; + + Objectives.Add(new CollectObjective(10, typeof(PowerCrystal), "Power Crystals")); + + Rewards.Add(new DummyReward(1074875)); // Another step closer to becoming human. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074946, "", + 0x2A); // You have demonstrated your ingenuity! Humans are jacks of all trades and know a little about a lot of things. You are one step closer to achieving humanity. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Nedrick"), new Point3D(2958, 3466, 15), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Nedrick"), new Point3D(2958, 3466, 15), Map.Trammel); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Sledge"), new Point3D(2673, 2129, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Sledge"), new Point3D(2673, 2129, 0), Map.Trammel); + } + } + + public class HeaveHo : MLQuest + { + public HeaveHo() + { + Activated = true; + Title = 1074351; // Heave Ho! + Description = + 1074519; // Ho there! There's nothing quite like a day's honest labor to make you appreciate being alive. Hey, maybe you'd like to help out with this project? These crates need to be delivered to Sledge. The only thing is -- it's a bit of a rush job and if you don't make it in time, he won't take them. Can I trust you to help out? + RefusalMessage = 1074521; // Oh yah, if you're too busy, no problem. + InProgressMessage = + 1074522; // Sledge can be found in Buc's Den. Better hurry, he won't take those crates if you take too long with them. + CompletionMessage = 1074523; // Hey, if you have cargo for me, you can start unloading over here. + CompletionNotice = CompletionNoticeShort; + + Objectives.Add(new TimedDeliverObjective(TimeSpan.FromHours(1), typeof(CrateForSledge), 5, "Crates for Sledge", + typeof(Sledge))); + + Rewards.Add(new DummyReward(1074875)); // Another step closer to becoming human. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074948, "", + 0x2A); // You have demonstrated your physical strength! Humans can carry vast loads without complaint. You are one step closer to achieving humanity. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Patricus"), new Point3D(3007, 823, -2), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Patricus"), new Point3D(3007, 823, -2), Map.Trammel); + } + } + + // This is not a real quest, it is only used as a reference + public class HumanInNeed : MLQuest + { + public HumanInNeed() + { + Title = 1075011; // A quest that asks you to defend a human in need. + Description = 0; + RefusalMessage = 0; + InProgressMessage = 0; + } + + public override bool RecordCompletion => true; + + public static void AwardTo(PlayerMobile pm) + { + MLQuestSystem.GetOrCreateContext(pm).SetDoneQuest(MLQuestSystem.FindQuest(typeof(HumanInNeed))); + pm.SendLocalizedMessage(1074949, "", + 0x2A); // You have demonstrated your compassion! Your kind actions have been noted. + } + } + + public class AllSeasonAdventurer : MLQuest + { + public AllSeasonAdventurer() + { + Activated = true; + Title = 1074353; // All Season Adventurer + Description = + 1074527; // It's all about hardship, suffering, struggle and pain. Without challenges, you've got nothing to test yourself against -- and that's what life is all about. Self improvement! Honing your body and mind! Overcoming obstacles ... You'll see what I mean if you take on my challenge. + RefusalMessage = 1074528; // My way of life isn't for everyone, that's true enough. + InProgressMessage = 1074529; // You're not making much progress in the honing-mind-and-body department, are you? + CompletionNotice = CompletionNoticeShortReturn; + + Objectives.Add(new KillObjective(5, new[] { typeof(Efreet) }, "efreets", + new QuestArea(1074808, "Fire"))); // Fire + Objectives.Add(new KillObjective(5, new[] { typeof(IceFiend) }, "ice fiends", + new QuestArea(1074809, "Ice"))); // Ice + + Rewards.Add(new DummyReward(1074875)); // Another step closer to becoming human. + } + + public override bool RecordCompletion => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.Player.SendLocalizedMessage(1074947, "", + 0x2A); // You have demonstrated your toughness! Humans are able to endure unimaginable hardships in pursuit of their goals. You are one step closer to achieving humanity. + instance.ClaimRewards(); // skip gump + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Belulah"), new Point3D(3782, 1266, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Belulah"), new Point3D(3782, 1266, 0), Map.Trammel); + } + } + + #endregion + + #region Elf To Human Mobiles + + [QuesterName("Sledge (Buc's Den)")] + public class Sledge : BaseCreature + { + [Constructible] + public Sledge() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Versatile"; + Body = 400; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + AddItem(new Tunic(Utility.RandomNeutralHue())); + AddItem(new LongPants(Utility.RandomBlueHue())); + AddItem(new Cloak(Utility.RandomBrightHue())); + AddItem(new ElvenBoots(Utility.RandomNeutralHue())); + AddItem(new Backpack()); + } + + public Sledge(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Sledge"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074188, // Weakling! You are not up to the task I have. + 1074195 // You there, in the stupid hat! Come here. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Patricus (Vesper)")] + public class Patricus : BaseCreature + { + [Constructible] + public Patricus() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Trader"; + Body = 400; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + AddItem(new FancyShirt(Utility.RandomNeutralHue())); + AddItem(new LongPants(Utility.RandomBrightHue())); + AddItem(new Cloak(0x1BB)); + AddItem(new Shoes(Utility.RandomNeutralHue())); + AddItem(new Backpack()); + } + + public Patricus(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Patricus"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Belulah (Nujel'm)")] // On OSI it's "Belulah (Nu'Jelm)" (incorrect spelling) + public class Belulah : BaseCreature + { + [Constructible] + public Belulah() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the scorned"; + Female = true; + Body = 401; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new FancyShirt(Utility.RandomBlueHue())); + AddItem(new LongPants(Utility.RandomNondyedHue())); + AddItem(new Boots()); + } + + public Belulah(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Belulah"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + /* + * 1074205 - Oh great adventurer, would you please assist a weak soul in need of aid? + * 1074206 - Excuse me please traveler, might I have a little of your time? + */ + MLQuestSystem.Tell(this, pm, Utility.Random(1074205, 2)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/HonestBeggar.cs b/Scripts/Engines/MLQuests/Definitions/HonestBeggar.cs index cc3facbe0..add1244f7 100644 --- a/Scripts/Engines/MLQuests/Definitions/HonestBeggar.cs +++ b/Scripts/Engines/MLQuests/Definitions/HonestBeggar.cs @@ -6,156 +6,159 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class HonestBeggar : MLQuest - { - public override Type NextQuest => typeof( ReginasThanks ); + public class HonestBeggar : MLQuest + { + public HonestBeggar() + { + Activated = true; + Title = 1075392; // Honest Beggar + Description = + 1075393; // Beg pardon, sir. I mean, madam. Uh, can I ask a favor of you? I found this jeweled ring. Most people would sell it and keep the money, but not me. I ain't never stole nothing, and I ain't about to start. I tried to take it over to Brit castle, figgerin' it must belong to some highborn lady, but the guards threw me out. You look like they might let you pass. Will you take the ring over there and see if you can find the owner? + RefusalMessage = 1075395; // I see. Too good to help an honest beggar like me, eh? + InProgressMessage = + 1075396; // A jewel like this must be worth a lot, so it must belong to some noble or another. I would show it around the castle. Someone�s bound to recognize it. + CompletionMessage = + 1075397; // Didst thou find my ring? I thank thee very much! It is an old ring, and a gift from my husband. I was most distraught when I realized it was missing. + CompletionNotice = CompletionNoticeShort; - public HonestBeggar() - { - Activated = true; - Title = 1075392; // Honest Beggar - Description = 1075393; // Beg pardon, sir. I mean, madam. Uh, can I ask a favor of you? I found this jeweled ring. Most people would sell it and keep the money, but not me. I ain't never stole nothing, and I ain't about to start. I tried to take it over to Brit castle, figgerin' it must belong to some highborn lady, but the guards threw me out. You look like they might let you pass. Will you take the ring over there and see if you can find the owner? - RefusalMessage = 1075395; // I see. Too good to help an honest beggar like me, eh? - InProgressMessage = 1075396; // A jewel like this must be worth a lot, so it must belong to some noble or another. I would show it around the castle. Someone�s bound to recognize it. - CompletionMessage = 1075397; // Didst thou find my ring? I thank thee very much! It is an old ring, and a gift from my husband. I was most distraught when I realized it was missing. - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(ReginasRing), 1, "Regina's Ring", typeof(Regina))); - Objectives.Add( new DeliverObjective( typeof( ReginasRing ), 1, "Regina's Ring", typeof( Regina ) ) ); + Rewards.Add(new DummyReward(1075394)); // Find the ring�s owner. + } - Rewards.Add( new DummyReward( 1075394 ) ); // Find the ring�s owner. - } + public override Type NextQuest => typeof(ReginasThanks); - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Evan" ), new Point3D( 1486, 1706, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Evan" ), new Point3D( 1486, 1706, 0 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Evan"), new Point3D(1486, 1706, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Evan"), new Point3D(1486, 1706, 0), Map.Felucca); + } + } - public class ReginasThanks : MLQuest - { - public override bool IsChainTriggered => true; + public class ReginasThanks : MLQuest + { + public ReginasThanks() + { + Activated = true; + OneTimeOnly = true; + Title = 1075398; // Regina�s Thanks + Description = + 1075399; // What�s that you say? It was a humble beggar that found my ring? Such honesty must be rewarded. Here, take this packet and return it to him, and I will be in your debt. + RefusalMessage = 1075401; // Hmph. Very well. What did you say his name was? + InProgressMessage = 1075402; // Take the packet and return it to the beggar who found my ring. + CompletionMessage = + 1075403; // What? For me? Let me see . . . these sapphire earrings are for you, it says. Oh, she wants to offer me a job! This is the most wonderful thing that ever happened to me! + CompletionNotice = CompletionNoticeShort; - public ReginasThanks() - { - Activated = true; - OneTimeOnly = true; - Title = 1075398; // Regina�s Thanks - Description = 1075399; // What�s that you say? It was a humble beggar that found my ring? Such honesty must be rewarded. Here, take this packet and return it to him, and I will be in your debt. - RefusalMessage = 1075401; // Hmph. Very well. What did you say his name was? - InProgressMessage = 1075402; // Take the packet and return it to the beggar who found my ring. - CompletionMessage = 1075403; // What? For me? Let me see . . . these sapphire earrings are for you, it says. Oh, she wants to offer me a job! This is the most wonderful thing that ever happened to me! - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(ReginasLetter), 1, "Regina's Letter", typeof(Evan))); - Objectives.Add( new DeliverObjective( typeof( ReginasLetter ), 1, "Regina's Letter", typeof( Evan ) ) ); + Rewards.Add(new ItemReward(1075400, typeof(TransparentHeart))); // Transparent Heart + } - Rewards.Add( new ItemReward( 1075400, typeof( TransparentHeart ) ) ); // Transparent Heart - } + public override bool IsChainTriggered => true; - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Regina" ), new Point3D( 1362, 1622, 50 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Regina" ), new Point3D( 1422, 1621, 20 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Regina"), new Point3D(1362, 1622, 50), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Regina"), new Point3D(1422, 1621, 20), Map.Felucca); + } + } - #endregion + #endregion - #region Mobiles + #region Mobiles - public class Evan : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Evan"; + public class Evan : BaseCreature + { + [Constructible] + public Evan() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Beggar"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Evan() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Beggar"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + AddItem(new Backpack()); + AddItem(new Doublet()); + AddItem(new ShortPants(0x755)); + } - AddItem( new Backpack() ); - AddItem( new Doublet() ); - AddItem( new ShortPants( 0x755 ) ); + public Evan(Serial serial) + : base(serial) + { + } - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Evan"; - public Evan( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + public class Regina : BaseCreature + { + [Constructible] + public Regina() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Noble"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - public class Regina : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Regina"; + Utility.AssignRandomHair(this, true); - [Constructible] - public Regina() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Noble"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + AddItem(new Backpack()); + AddItem(new GildedDress()); + AddItem(new Boots()); + } - Utility.AssignRandomHair( this, true ); + public Regina(Serial serial) + : base(serial) + { + } - AddItem( new Backpack() ); - AddItem( new GildedDress() ); - AddItem( new Boots() ); + public override bool IsInvulnerable => true; + public override string DefaultName => "Regina"; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public Regina( Serial serial ) - : base( serial ) - { - } + writer.Write(0); // version + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version - } + int version = reader.ReadInt(); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Ilshenar.cs b/Scripts/Engines/MLQuests/Definitions/Ilshenar.cs index bfaaccad4..6fbec765e 100644 --- a/Scripts/Engines/MLQuests/Definitions/Ilshenar.cs +++ b/Scripts/Engines/MLQuests/Definitions/Ilshenar.cs @@ -6,328 +6,342 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - public class Responsibility : BaseEscort - { - public Responsibility() - { - Activated = true; - Title = 1074352; // Responsibility - Description = 1074524; // Oh! I just don't know what to do. My mother is away and my father told me not to talk to strangers ... *worried frown* But my grandfather has sent word that he has been hurt and needs me to tend his wounds. He has a small farm southeast of here. Would you ... could you ... escort me there safely? - RefusalMessage = 1074525; // I hope my grandfather will be alright. - InProgressMessage = 1074526; // Grandfather's farm is a ways west of the Shrine of Spirituality. So, we're not quite there yet. Thank you again for keeping me safe. + public class Responsibility : BaseEscort + { + public Responsibility() + { + Activated = true; + Title = 1074352; // Responsibility + Description = + 1074524; // Oh! I just don't know what to do. My mother is away and my father told me not to talk to strangers ... *worried frown* But my grandfather has sent word that he has been hurt and needs me to tend his wounds. He has a small farm southeast of here. Would you ... could you ... escort me there safely? + RefusalMessage = 1074525; // I hope my grandfather will be alright. + InProgressMessage = + 1074526; // Grandfather's farm is a ways west of the Shrine of Spirituality. So, we're not quite there yet. Thank you again for keeping me safe. - Objectives.Add( new EscortObjective( new QuestArea( 1074781, "Sheep Farm" ) ) ); // Sheep Farm + Objectives.Add(new EscortObjective(new QuestArea(1074781, "Sheep Farm"))); // Sheep Farm - Rewards.Add( ItemReward.BagOfTrinkets ); - } + Rewards.Add(ItemReward.BagOfTrinkets); + } - // OSI sends this instead, but it doesn't make sense for an escortable - //public override void OnComplete( MLQuestInstance instance ) - //{ - // instance.Player.SendLocalizedMessage( 1073775, "", 0x23 ); // Your quest is complete. Return for your reward. - //} + // OSI sends this instead, but it doesn't make sense for an escortable + //public override void OnComplete( MLQuestInstance instance ) + //{ + // instance.Player.SendLocalizedMessage( 1073775, "", 0x23 ); // Your quest is complete. Return for your reward. + //} - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, TimeSpan.FromSeconds( 10 ), TimeSpan.FromSeconds( 30 ), 0, 5, "Lissbet" ), new Point3D( 1568, 1040, -7 ), Map.Ilshenar ); - PutSpawner( new Spawner( 1, 5, 10, 0, 8, "GrandpaCharley" ), new Point3D( 1322, 1331, -14 ), Map.Ilshenar ); - PutSpawner( new Spawner( 1, TimeSpan.FromSeconds( 10 ), TimeSpan.FromSeconds( 30 ), 0, 3, "Sheep" ), new Point3D( 1308, 1324, -14 ), Map.Ilshenar ); - } - } + PutSpawner(new Spawner(1, TimeSpan.FromSeconds(10), TimeSpan.FromSeconds(30), 0, 5, "Lissbet"), + new Point3D(1568, 1040, -7), Map.Ilshenar); + PutSpawner(new Spawner(1, 5, 10, 0, 8, "GrandpaCharley"), new Point3D(1322, 1331, -14), Map.Ilshenar); + PutSpawner(new Spawner(1, TimeSpan.FromSeconds(10), TimeSpan.FromSeconds(30), 0, 3, "Sheep"), + new Point3D(1308, 1324, -14), Map.Ilshenar); + } + } - public class SomethingToWailAbout : MLQuest - { - public SomethingToWailAbout() - { - Activated = true; - Title = 1073071; // Something to Wail About - Description = 1073561; // Can you hear them? The never-ending howling? The incessant wailing? These banshees, they never cease! Never! They haunt my nights. Please, I beg you -- will you silence them? I would be ever so grateful. - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073581; // Until you kill 12 Wailing Banshees, there will be no peace. + public class SomethingToWailAbout : MLQuest + { + public SomethingToWailAbout() + { + Activated = true; + Title = 1073071; // Something to Wail About + Description = + 1073561; // Can you hear them? The never-ending howling? The incessant wailing? These banshees, they never cease! Never! They haunt my nights. Please, I beg you -- will you silence them? I would be ever so grateful. + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073581; // Until you kill 12 Wailing Banshees, there will be no peace. - Objectives.Add( new KillObjective( 12, new[] { typeof( WailingBanshee ) }, "wailing banshees" ) ); + Objectives.Add(new KillObjective(12, new[] { typeof(WailingBanshee) }, "wailing banshees")); - Rewards.Add( ItemReward.BagOfTreasure ); - } + Rewards.Add(ItemReward.BagOfTreasure); + } - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Jelrice" ), new Point3D( 1176, 1196, -25 ), Map.Ilshenar ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Jelrice"), new Point3D(1176, 1196, -25), Map.Ilshenar); + } + } - public class Runaways : MLQuest - { - public Runaways() - { - Activated = true; - Title = 1072993; // Runaways! - Description = 1073026; // You've got to help me out! Those wild ostards have been causing absolute havok around here. Kill them off before they destroy my land. There are around twelve of them. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + public class Runaways : MLQuest + { + public Runaways() + { + Activated = true; + Title = 1072993; // Runaways! + Description = + 1073026; // You've got to help me out! Those wild ostards have been causing absolute havok around here. Kill them off before they destroy my land. There are around twelve of them. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - Objectives.Add( new KillObjective( 12, new[] { typeof( FrenziedOstard ) }, "frenzied ostards" ) ); + Objectives.Add(new KillObjective(12, new[] { typeof(FrenziedOstard) }, "frenzied ostards")); - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } + Rewards.Add(ItemReward.BagOfTrinkets); + } + } - public class ViciousPredator : MLQuest - { - public ViciousPredator() - { - Activated = true; - Title = 1072994; // Vicious Predator - Description = 1073028; // You've got to help me out! Those dire wolves have been causing absolute havok around here. Kill them off before they destroy my land. They run around in a pack of around ten. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + public class ViciousPredator : MLQuest + { + public ViciousPredator() + { + Activated = true; + Title = 1072994; // Vicious Predator + Description = + 1073028; // You've got to help me out! Those dire wolves have been causing absolute havok around here. Kill them off before they destroy my land. They run around in a pack of around ten. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - Objectives.Add( new KillObjective( 10, new[] { typeof( DireWolf ) }, "dire wolves" ) ); + Objectives.Add(new KillObjective(10, new[] { typeof(DireWolf) }, "dire wolves")); - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } + Rewards.Add(ItemReward.BagOfTrinkets); + } + } - public class GuileIrkAndSpite : MLQuest - { - public GuileIrkAndSpite() - { - Activated = true; - Title = 1074739; // Guile, Irk and Spite - Description = 1074740; // You know them, don't you. The three? They look like you, you'll see. They looked like me, I remember, they looked like, well, you'll see. The three. They'll drive you mad too, if you let them. They are trouble, and they need to be slain. Seek them out. - RefusalMessage = 1074745; // You just don't understand the gravity of the situation. If you did, you'd agree to my task. - InProgressMessage = 1074746; // Perhaps I was unclear. You'll know them when you see them, because you'll see you, and you, and you. Hurry now. - CompletionMessage = 1074747; // Are you one of THEM? Ahhhh! Oh, wait, if you were them, then you'd be me. So you're -- you. Good job! + public class GuileIrkAndSpite : MLQuest + { + public GuileIrkAndSpite() + { + Activated = true; + Title = 1074739; // Guile, Irk and Spite + Description = + 1074740; // You know them, don't you. The three? They look like you, you'll see. They looked like me, I remember, they looked like, well, you'll see. The three. They'll drive you mad too, if you let them. They are trouble, and they need to be slain. Seek them out. + RefusalMessage = + 1074745; // You just don't understand the gravity of the situation. If you did, you'd agree to my task. + InProgressMessage = + 1074746; // Perhaps I was unclear. You'll know them when you see them, because you'll see you, and you, and you. Hurry now. + CompletionMessage = + 1074747; // Are you one of THEM? Ahhhh! Oh, wait, if you were them, then you'd be me. So you're -- you. Good job! - Objectives.Add( new KillObjective( 1, new[] { typeof( Guile ) }, "Guile" ) ); - Objectives.Add( new KillObjective( 1, new[] { typeof( Irk ) }, "Irk" ) ); - Objectives.Add( new KillObjective( 1, new[] { typeof( Spite ) }, "Spite" ) ); + Objectives.Add(new KillObjective(1, new[] { typeof(Guile) }, "Guile")); + Objectives.Add(new KillObjective(1, new[] { typeof(Irk) }, "Irk")); + Objectives.Add(new KillObjective(1, new[] { typeof(Spite) }, "Spite")); - Rewards.Add( ItemReward.Strongbox ); - } + Rewards.Add(ItemReward.Strongbox); + } - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "Yorus" ), new Point3D( 1389, 423, -24 ), Map.Ilshenar ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 5, "Yorus"), new Point3D(1389, 423, -24), Map.Ilshenar); + } + } - public class Lissbet : BaseEscortable - { - public override bool StaticMLQuester => true; - public override bool InitialInnocent => true; - public override string DefaultName => "Lissbet"; + public class Lissbet : BaseEscortable + { + [Constructible] + public Lissbet() + { + } - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074204, // Greetings seeker.  I have an urgent matter for you, if you are willing. - 1074222 // Could I trouble you for some assistance? - ) ); - } + public Lissbet(Serial serial) + : base(serial) + { + } - [Constructible] - public Lissbet() - { - } + public override bool StaticMLQuester => true; + public override bool InitialInnocent => true; + public override string DefaultName => "Lissbet"; - public override void InitBody() - { - SetStr( 40, 50 ); - SetDex( 70, 80 ); - SetInt( 80, 90 ); + public override bool CanShout => true; - Hue = Utility.RandomSkinHue(); - Female = true; - Body = 401; + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074204, // Greetings seeker.  I have an urgent matter for you, if you are willing. + 1074222 // Could I trouble you for some assistance? + )); + } - Title = "the flower girl"; + public override void InitBody() + { + SetStr(40, 50); + SetDex(70, 80); + SetInt(80, 90); - HairItemID = 0x203D; - HairHue = 0x1BB; - } + Hue = Utility.RandomSkinHue(); + Female = true; + Body = 401; - public override void InitOutfit() - { - AddItem( new Kilt( Utility.RandomYellowHue() ) ); - AddItem( new FancyShirt( Utility.RandomYellowHue() ) ); - AddItem( new Sandals() ); - } + Title = "the flower girl"; - public Lissbet( Serial serial ) - : base( serial ) - { - } + HairItemID = 0x203D; + HairHue = 0x1BB; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitOutfit() + { + AddItem(new Kilt(Utility.RandomYellowHue())); + AddItem(new FancyShirt(Utility.RandomYellowHue())); + AddItem(new Sandals()); + } - writer.Write( (int)0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public class GrandpaCharley : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Grandpa Charley"; - public override bool CanTeach => true; + int version = reader.ReadInt(); + } + } - [Constructible] - public GrandpaCharley() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the farmer"; - Body = 400; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + public class GrandpaCharley : BaseCreature + { + [Constructible] + public GrandpaCharley() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the farmer"; + Body = 400; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - int hairHue = 0x3B2 + Utility.Random( 2 ); - Utility.AssignRandomHair( this, hairHue ); + int hairHue = 0x3B2 + Utility.Random(2); + Utility.AssignRandomHair(this, hairHue); - FacialHairItemID = 0x203E; // Long Beard - FacialHairHue = hairHue; + FacialHairItemID = 0x203E; // Long Beard + FacialHairHue = hairHue; - SetSkill( SkillName.ItemID, 80, 90 ); + SetSkill(SkillName.ItemID, 80, 90); - AddItem( new WideBrimHat( Utility.RandomNondyedHue() ) ); - AddItem( new FancyShirt( Utility.RandomNondyedHue() ) ); - AddItem( new LongPants( Utility.RandomNondyedHue() ) ); - AddItem( new Sandals( Utility.RandomNeutralHue() ) ); - AddItem( new ShepherdsCrook() ); - AddItem( new Backpack() ); - } + AddItem(new WideBrimHat(Utility.RandomNondyedHue())); + AddItem(new FancyShirt(Utility.RandomNondyedHue())); + AddItem(new LongPants(Utility.RandomNondyedHue())); + AddItem(new Sandals(Utility.RandomNeutralHue())); + AddItem(new ShepherdsCrook()); + AddItem(new Backpack()); + } - public GrandpaCharley( Serial serial ) - : base( serial ) - { - } + public GrandpaCharley(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool IsInvulnerable => true; + public override string DefaultName => "Grandpa Charley"; + public override bool CanTeach => true; - writer.Write( (int)0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [QuesterName( "Jelrice (Ilshenar)" )] - public class Jelrice : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Jelrice"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074221 ); // Greetings!  I have a small task for you good traveler. - } + int version = reader.ReadInt(); + } + } - [Constructible] - public Jelrice() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the trader"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + [QuesterName("Jelrice (Ilshenar)")] + public class Jelrice : BaseCreature + { + [Constructible] + public Jelrice() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the trader"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - Utility.AssignRandomHair( this, true ); + Utility.AssignRandomHair(this, true); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); - AddItem( new Skirt( Utility.RandomBlueHue() ) ); - AddItem( new FancyShirt( Utility.RandomRedHue() ) ); - } + AddItem(new Shoes(Utility.RandomNeutralHue())); + AddItem(new Skirt(Utility.RandomBlueHue())); + AddItem(new FancyShirt(Utility.RandomRedHue())); + } - public Jelrice( Serial serial ) - : base( serial ) - { - } + public Jelrice(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool IsInvulnerable => true; + public override string DefaultName => "Jelrice"; + public override bool CanShout => true; - writer.Write( (int) 0 ); // version - } + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074221); // Greetings!  I have a small task for you good traveler. + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } - [QuesterName( "Yorus (Ilshenar)" )] - public class Yorus : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Yorus"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074218 ); // Hey!  I want to talk to you, now. - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public Yorus() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the tinker"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + int version = reader.ReadInt(); + } + } - Utility.AssignRandomHair( this, true ); + [QuesterName("Yorus (Ilshenar)")] + public class Yorus : BaseCreature + { + [Constructible] + public Yorus() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the tinker"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); - AddItem( new LongPants( Utility.RandomBlueHue() ) ); - AddItem( new FancyShirt( Utility.RandomOrangeHue() ) ); - AddItem( new Cloak( Utility.RandomBrightHue() ) ); - } + Utility.AssignRandomHair(this, true); - public Yorus( Serial serial ) - : base( serial ) - { - } + AddItem(new Shoes(Utility.RandomNeutralHue())); + AddItem(new LongPants(Utility.RandomBlueHue())); + AddItem(new FancyShirt(Utility.RandomOrangeHue())); + AddItem(new Cloak(Utility.RandomBrightHue())); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Yorus(Serial serial) + : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Yorus"; + public override bool CanShout => true; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074218); // Hey!  I want to talk to you, now. + } - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/LostItems.cs b/Scripts/Engines/MLQuests/Definitions/LostItems.cs index a12934350..201762325 100644 --- a/Scripts/Engines/MLQuests/Definitions/LostItems.cs +++ b/Scripts/Engines/MLQuests/Definitions/LostItems.cs @@ -5,64 +5,67 @@ using Server.Engines.MLQuests.Rewards; namespace Server.Engines.MLQuests.Definitions { - // TODO: Assassination Contract, Evidence, Lost in Transit, Last Words + // TODO: Assassination Contract, Evidence, Lost in Transit, Last Words - #region Quests + #region Quests - public class LostAndFound : MLQuest - { - public LostAndFound() - { - Activated = true; - Title = 1072370; // Lost and Found - Description = 1072589; // The battered, old bucket is inscribed with barely legible writing that indicates it belongs to someone named "Dallid". Maybe they'd pay for its return? - RefusalMessage = 1072590; // You're right, who cares if Dallid might pay for his battered old bucket back. This way you can carry it around with you! - InProgressMessage = 1072591; // Whoever this "Dallid" might be, he's probably looking for his bucket. - CompletionMessage = 1074580; // Is that my bucket? I had to ditch my favorite bucket when a group of ratmen jumped me! + public class LostAndFound : MLQuest + { + public LostAndFound() + { + Activated = true; + Title = 1072370; // Lost and Found + Description = + 1072589; // The battered, old bucket is inscribed with barely legible writing that indicates it belongs to someone named "Dallid". Maybe they'd pay for its return? + RefusalMessage = + 1072590; // You're right, who cares if Dallid might pay for his battered old bucket back. This way you can carry it around with you! + InProgressMessage = 1072591; // Whoever this "Dallid" might be, he's probably looking for his bucket. + CompletionMessage = + 1074580; // Is that my bucket? I had to ditch my favorite bucket when a group of ratmen jumped me! - Objectives.Add( new TimedDeliverObjective( TimeSpan.FromSeconds( 600 ), typeof( BatteredBucket ), 1, "battered bucket", typeof( Dallid ), false ) ); + Objectives.Add(new TimedDeliverObjective(TimeSpan.FromSeconds(600), typeof(BatteredBucket), 1, "battered bucket", + typeof(Dallid), false)); - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } + Rewards.Add(ItemReward.BagOfTrinkets); + } + } - #endregion + #endregion - #region Items + #region Items - public class BatteredBucket : TransientQuestGiverItem - { - // Original label, doesn't fit the expiration message well - //public override int LabelNumber => 1073129; // A battered bucket. + public class BatteredBucket : TransientQuestGiverItem + { + [Constructible] + public BatteredBucket() + : base(0x2004, TimeSpan.FromMinutes(10)) + { + LootType = LootType.Blessed; + } - public override string DefaultName => "battered bucket"; + public BatteredBucket(Serial serial) + : base(serial) + { + } + // Original label, doesn't fit the expiration message well + //public override int LabelNumber => 1073129; // A battered bucket. - [Constructible] - public BatteredBucket() - : base( 0x2004, TimeSpan.FromMinutes( 10 ) ) - { - LootType = LootType.Blessed; - } + public override string DefaultName => "battered bucket"; - public BatteredBucket( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int)0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } - - #endregion -} + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Malas.cs b/Scripts/Engines/MLQuests/Definitions/Malas.cs index 7a1a3cdca..5b8e4b975 100644 --- a/Scripts/Engines/MLQuests/Definitions/Malas.cs +++ b/Scripts/Engines/MLQuests/Definitions/Malas.cs @@ -5,87 +5,89 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class PointyEars : MLQuest - { - public PointyEars() - { - Activated = true; - Title = 1074640; // Pointy Ears - Description = 1074641; // I've heard ... there's some that will pay a good bounty for pointed ears, much like we used to pay for each wolf skin. I've got nothing personal against these elves. It's just business. You want in on this? I'm not fussy who I work with. - RefusalMessage = 1074642; // Suit yourself. - InProgressMessage = 1074643; // I can't pay a bounty if you don't bring bag the ears. - CompletionMessage = 1074644; // Here to collect on a bounty? + public class PointyEars : MLQuest + { + public PointyEars() + { + Activated = true; + Title = 1074640; // Pointy Ears + Description = + 1074641; // I've heard ... there's some that will pay a good bounty for pointed ears, much like we used to pay for each wolf skin. I've got nothing personal against these elves. It's just business. You want in on this? I'm not fussy who I work with. + RefusalMessage = 1074642; // Suit yourself. + InProgressMessage = 1074643; // I can't pay a bounty if you don't bring bag the ears. + CompletionMessage = 1074644; // Here to collect on a bounty? - Objectives.Add( new CollectObjective( 20, typeof( SeveredElfEars ), 1032590 ) ); // severed elf ears + Objectives.Add(new CollectObjective(20, typeof(SeveredElfEars), 1032590)); // severed elf ears - Rewards.Add( ItemReward.BagOfTrinkets ); - } + Rewards.Add(ItemReward.BagOfTrinkets); + } - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Drithen" ), new Point3D( 1983, 1364, -80 ), Map.Malas ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Drithen"), new Point3D(1983, 1364, -80), Map.Malas); + } + } - #endregion + #endregion - #region Mobiles + #region Mobiles - [QuesterName( "Drithen (Umbra)" )] - public class Drithen : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Drithen"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074188 ); // Weakling! You are not up to the task I have. - } + [QuesterName("Drithen (Umbra)")] + public class Drithen : BaseCreature + { + [Constructible] + public Drithen() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Fierce"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Drithen() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Fierce"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + AddItem(new Backpack()); + AddItem(new ElvenBoots(Utility.RandomNeutralHue())); + AddItem(new LongPants(Utility.RandomBlueHue())); + AddItem(new Tunic(Utility.RandomNeutralHue())); + AddItem(new Cloak(Utility.RandomBrightHue())); - AddItem( new Backpack() ); - AddItem( new ElvenBoots( Utility.RandomNeutralHue() ) ); - AddItem( new LongPants( Utility.RandomBlueHue() ) ); - AddItem( new Tunic( Utility.RandomNeutralHue() ) ); - AddItem( new Cloak( Utility.RandomBrightHue() ) ); + SetSkill(SkillName.Focus, 60.0, 80.0); + } - SetSkill( SkillName.Focus, 60.0, 80.0 ); - } + public Drithen(Serial serial) + : base(serial) + { + } - public Drithen( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Drithen"; + public override bool CanShout => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074188); // Weakling! You are not up to the task I have. + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion -} + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/MistakenIdentity.cs b/Scripts/Engines/MLQuests/Definitions/MistakenIdentity.cs index cd8cf9276..175a51992 100644 --- a/Scripts/Engines/MLQuests/Definitions/MistakenIdentity.cs +++ b/Scripts/Engines/MLQuests/Definitions/MistakenIdentity.cs @@ -7,330 +7,350 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class MistakenIdentity : MLQuest - { - public override Type NextQuest => typeof( YouScratchMyBack ); + public class MistakenIdentity : MLQuest + { + public MistakenIdentity() + { + Activated = true; + Title = 1074573; // Mistaken Identity + Description = + 1074574; // What do you want? Wonderful, another whining request for a refund on tuition. You know, experiences like that are invaluable ... and infrequent. Having the opportunity to test yourself under such realistic situations isn't something the college offers all students. Fine. Fine. You'll need to submit a refund request form in triplicate before I can return your 1,000,000 gold tuition. You'll need to get some signatures and a few other odds and ends. + RefusalMessage = 1074606; // If you're not willing to follow the proper process then go away. + InProgressMessage = 1074605; // You're not getting a refund without the proper forms and signatures. + CompletionMessage = 1074607; // Oh blast! Not another of those forms. I'm so sick of this endless paperwork. + CompletionNotice = CompletionNoticeShort; - public MistakenIdentity() - { - Activated = true; - Title = 1074573; // Mistaken Identity - Description = 1074574; // What do you want? Wonderful, another whining request for a refund on tuition. You know, experiences like that are invaluable ... and infrequent. Having the opportunity to test yourself under such realistic situations isn't something the college offers all students. Fine. Fine. You'll need to submit a refund request form in triplicate before I can return your 1,000,000 gold tuition. You'll need to get some signatures and a few other odds and ends. - RefusalMessage = 1074606; // If you're not willing to follow the proper process then go away. - InProgressMessage = 1074605; // You're not getting a refund without the proper forms and signatures. - CompletionMessage = 1074607; // Oh blast! Not another of those forms. I'm so sick of this endless paperwork. - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(TuitionReimbursementForm), 1, "Tuition Reimbursement Form", + typeof(Gorrow))); - Objectives.Add( new DeliverObjective( typeof( TuitionReimbursementForm ), 1, "Tuition Reimbursement Form", typeof( Gorrow ) ) ); + Rewards.Add(new DummyReward(1074634)); // Tuition Reimbursement + } - Rewards.Add( new DummyReward( 1074634 ) ); // Tuition Reimbursement - } + public override Type NextQuest => typeof(YouScratchMyBack); - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Aernya" ), new Point3D( 2095, 1380, -90 ), Map.Malas ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Aernya"), new Point3D(2095, 1380, -90), Map.Malas); + } + } - public class YouScratchMyBack : MLQuest - { - public override Type NextQuest => typeof( FoolingAernya ); - public override bool IsChainTriggered => true; + public class YouScratchMyBack : MLQuest + { + public YouScratchMyBack() + { + Activated = true; + Title = 1074608; // You Scratch My Back + Description = + 1074609; // Heh. Heheheh. Good one. You're not a Bedlam student and you're definitely not eligible for a tuition refund. Heheheh. That old witch Aernya doesn't see as well as she used to you know. Otherwise, she would have ... hmmm, wait a minute. I sense a certain 'opportunity' here. I'll sign your forms in return for a little help with a project of my own. What do you say? + RefusalMessage = 1074615; // Hehehe. Your choice. + InProgressMessage = + 1074616; // I'm something of a gourmet, you see. It's tough getting some of the ingredients, though. Bring me back some pixie legs, unicorn ribs and ki-rin brains and I'll sign your form. + CompletionMessage = + 1074617; // Oh excellent, you're back. I'll get the oven going. That thing about pixie legs, you see, is that they burn and dry out if you're not really careful. Taste just like chicken too! + CompletionNotice = CompletionNoticeShortReturn; - public YouScratchMyBack() - { - Activated = true; - Title = 1074608; // You Scratch My Back - Description = 1074609; // Heh. Heheheh. Good one. You're not a Bedlam student and you're definitely not eligible for a tuition refund. Heheheh. That old witch Aernya doesn't see as well as she used to you know. Otherwise, she would have ... hmmm, wait a minute. I sense a certain 'opportunity' here. I'll sign your forms in return for a little help with a project of my own. What do you say? - RefusalMessage = 1074615; // Hehehe. Your choice. - InProgressMessage = 1074616; // I'm something of a gourmet, you see. It's tough getting some of the ingredients, though. Bring me back some pixie legs, unicorn ribs and ki-rin brains and I'll sign your form. - CompletionMessage = 1074617; // Oh excellent, you're back. I'll get the oven going. That thing about pixie legs, you see, is that they burn and dry out if you're not really careful. Taste just like chicken too! - CompletionNotice = CompletionNoticeShortReturn; + Objectives.Add(new CollectObjective(1, typeof(UnicornRibs), "Unicorn Ribs")); + Objectives.Add(new CollectObjective(2, typeof(KirinBrains), "Ki-Rin Brains")); + Objectives.Add(new CollectObjective(5, typeof(PixieLeg), "Pixie Leg")); - Objectives.Add( new CollectObjective( 1, typeof( UnicornRibs ), "Unicorn Ribs" ) ); - Objectives.Add( new CollectObjective( 2, typeof( KirinBrains ), "Ki-Rin Brains" ) ); - Objectives.Add( new CollectObjective( 5, typeof( PixieLeg ), "Pixie Leg" ) ); + Rewards.Add(new DummyReward(1074634)); // Tuition Reimbursement + } - Rewards.Add( new DummyReward( 1074634 ) ); // Tuition Reimbursement - } + public override Type NextQuest => typeof(FoolingAernya); + public override bool IsChainTriggered => true; - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 4, "Gorrow" ), new Point3D( 993, 512, -50 ), Map.Malas ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 4, "Gorrow"), new Point3D(993, 512, -50), Map.Malas); + } + } - public class FoolingAernya : MLQuest - { - public override Type NextQuest => typeof( NotQuiteThatEasy ); - public override bool IsChainTriggered => true; + public class FoolingAernya : MLQuest + { + public FoolingAernya() + { + Activated = true; + Title = 1074618; // Fooling Aernya + Description = + 1074619; // Now that I've signed your papers you'd better get back to that witch Aernya. Mmmm mmm smell those ribs! + RefusalMessage = 1074620; // Giving up on your scheme eh? Suit yourself. + InProgressMessage = + 1074621; // You better hurry back to Mistress Aernya with that signed form. The college only has so much money and with enough claims you may find yourself unable to get your tuition refunded. *wink* + CompletionMessage = 1074622; // What? Hrmph. Gorrow signed your form did he? Let me see that. *squint* + CompletionNotice = CompletionNoticeShort; - public FoolingAernya() - { - Activated = true; - Title = 1074618; // Fooling Aernya - Description = 1074619; // Now that I've signed your papers you'd better get back to that witch Aernya. Mmmm mmm smell those ribs! - RefusalMessage = 1074620; // Giving up on your scheme eh? Suit yourself. - InProgressMessage = 1074621; // You better hurry back to Mistress Aernya with that signed form. The college only has so much money and with enough claims you may find yourself unable to get your tuition refunded. *wink* - CompletionMessage = 1074622; // What? Hrmph. Gorrow signed your form did he? Let me see that. *squint* - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(SignedTuitionReimbursementForm), 1, + "Signed Tuition Reimbursement Form", typeof(Aernya))); - Objectives.Add( new DeliverObjective( typeof( SignedTuitionReimbursementForm ), 1, "Signed Tuition Reimbursement Form", typeof( Aernya ) ) ); + Rewards.Add(new DummyReward(1074634)); // Tuition Reimbursement + } - Rewards.Add( new DummyReward( 1074634 ) ); // Tuition Reimbursement - } - } + public override Type NextQuest => typeof(NotQuiteThatEasy); + public override bool IsChainTriggered => true; + } - public class NotQuiteThatEasy : MLQuest - { - public override Type NextQuest => typeof( ConvinceMe ); - public override bool IsChainTriggered => true; + public class NotQuiteThatEasy : MLQuest + { + public NotQuiteThatEasy() + { + Activated = true; + Title = 1074623; // Not Quite That Easy + Description = + 1074624; // I wouldn't be too smug just yet, whiner. You still need Master Gnosos' signature before I can cut your refund. Last I heard, he's coordinating the recovery of the portions of the college that are currently overrun. *nasty smile* Off with you. + RefusalMessage = 1074626; // Coward. + InProgressMessage = 1074627; // What are you waiting for? The iron maiden is still the portal to Bedlam. + CompletionMessage = + 1074628; // Made it through did you? Did you happen to see Red Death out there? Big horse, skeletal ... burning eyes? No? What's this? Forms? FORMS? I'm up to my eyebrows in ravenous out-of-control undead and you want a signature? + CompletionNotice = CompletionNoticeShort; - public NotQuiteThatEasy() - { - Activated = true; - Title = 1074623; // Not Quite That Easy - Description = 1074624; // I wouldn't be too smug just yet, whiner. You still need Master Gnosos' signature before I can cut your refund. Last I heard, he's coordinating the recovery of the portions of the college that are currently overrun. *nasty smile* Off with you. - RefusalMessage = 1074626; // Coward. - InProgressMessage = 1074627; // What are you waiting for? The iron maiden is still the portal to Bedlam. - CompletionMessage = 1074628; // Made it through did you? Did you happen to see Red Death out there? Big horse, skeletal ... burning eyes? No? What's this? Forms? FORMS? I'm up to my eyebrows in ravenous out-of-control undead and you want a signature? - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(SignedTuitionReimbursementForm), 1, + "Signed Tuition Reimbursement Form", typeof(MasterGnosos))); - Objectives.Add( new DeliverObjective( typeof( SignedTuitionReimbursementForm ), 1, "Signed Tuition Reimbursement Form", typeof( MasterGnosos ) ) ); + Rewards.Add(new DummyReward(1074634)); // Tuition Reimbursement + } - Rewards.Add( new DummyReward( 1074634 ) ); // Tuition Reimbursement - } + public override Type NextQuest => typeof(ConvinceMe); + public override bool IsChainTriggered => true; - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutDeco( new BedlamTeleporter(), new Point3D( 2067, 1371, -75 ), Map.Malas ); - } + PutDeco(new BedlamTeleporter(), new Point3D(2067, 1371, -75), Map.Malas); + } - public override void OnAccepted( MLQuestInstance instance ) - { - instance.PlayerContext.BedlamAccess = true; // Permanent access - } - } + public override void OnAccepted(MLQuestInstance instance) + { + instance.PlayerContext.BedlamAccess = true; // Permanent access + } + } - public class ConvinceMe : MLQuest - { - public override Type NextQuest => typeof( TuitionReimbursement ); - public override bool IsChainTriggered => true; + public class ConvinceMe : MLQuest + { + public ConvinceMe() + { + Activated = true; + Title = 1074629; // Convince Me + Description = + 1074630; // I'm not signing any forms until the situation here is under control. So, you can either help out or you can forget getting your tuition refund. Which will it be? Help control the shambling dead? + RefusalMessage = 1074631; // No signature for you. + InProgressMessage = + 1074632; // No signature for you until you kill off some of the shambling dead out there and destroy that blasted horse. + CompletionMessage = 1074633; // Pulled it off huh? Well then you've earned this signature! + CompletionNotice = CompletionNoticeShortReturn; - public ConvinceMe() - { - Activated = true; - Title = 1074629; // Convince Me - Description = 1074630; // I'm not signing any forms until the situation here is under control. So, you can either help out or you can forget getting your tuition refund. Which will it be? Help control the shambling dead? - RefusalMessage = 1074631; // No signature for you. - InProgressMessage = 1074632; // No signature for you until you kill off some of the shambling dead out there and destroy that blasted horse. - CompletionMessage = 1074633; // Pulled it off huh? Well then you've earned this signature! - CompletionNotice = CompletionNoticeShortReturn; + QuestArea bedlam = new QuestArea(1074835, "Bedlam"); // Bedlam - QuestArea bedlam = new QuestArea( 1074835, "Bedlam" ); // Bedlam + Objectives.Add(new KillObjective(1, new[] { typeof(RedDeath) }, "Red Death", bedlam)); + Objectives.Add(new KillObjective(10, new[] { typeof(GoreFiend) }, "gore fiends", bedlam)); + Objectives.Add(new KillObjective(8, new[] { typeof(RottingCorpse) }, "rotting corpses", bedlam)); - Objectives.Add( new KillObjective( 1, new[] { typeof( RedDeath ) }, "Red Death", bedlam ) ); - Objectives.Add( new KillObjective( 10, new[] { typeof( GoreFiend ) }, "gore fiends", bedlam ) ); - Objectives.Add( new KillObjective( 8, new[] { typeof( RottingCorpse ) }, "rotting corpses", bedlam ) ); + Rewards.Add(new DummyReward(1074634)); // Tuition Reimbursement + } - Rewards.Add( new DummyReward( 1074634 ) ); // Tuition Reimbursement - } + public override Type NextQuest => typeof(TuitionReimbursement); + public override bool IsChainTriggered => true; - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "MasterGnosos" ), new Point3D( 87, 1639, 0 ), Map.Malas ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 3, "MasterGnosos"), new Point3D(87, 1639, 0), Map.Malas); + } + } - public class TuitionReimbursement : MLQuest - { - public override bool IsChainTriggered => true; + public class TuitionReimbursement : MLQuest + { + public TuitionReimbursement() + { + Activated = true; + Title = 1074634; // Tuition Reimbursement + Description = + 1074635; // Well, there you are. I've added my signature to that of Gorrow, so you should be set to return to Mistress Aernya and get your tuition refunded. + RefusalMessage = + 1074636; // Great! If you're going to stick around here, I know we have more tasks for you to perform. + InProgressMessage = + 1074637; // Just head out the main gates there and you'll find yourself embracing the iron maiden in the Bloodletter's Guild. + CompletionMessage = + 1074638; // *disinterested stare* What? Oh, you've gotten your form filled in. How nice. *glare* And I'd hoped you'd drop this charade before I was forced to rub your nose in it. *nasty smile* You're not even a student and as such, you're not eligible for a refund -- you've never paid tuition. For your services, Master Gnosos has recommended you receive pay. So here. Now go away. + CompletionNotice = CompletionNoticeShort; - public TuitionReimbursement() - { - Activated = true; - Title = 1074634; // Tuition Reimbursement - Description = 1074635; // Well, there you are. I've added my signature to that of Gorrow, so you should be set to return to Mistress Aernya and get your tuition refunded. - RefusalMessage = 1074636; // Great! If you're going to stick around here, I know we have more tasks for you to perform. - InProgressMessage = 1074637; // Just head out the main gates there and you'll find yourself embracing the iron maiden in the Bloodletter's Guild. - CompletionMessage = 1074638; // *disinterested stare* What? Oh, you've gotten your form filled in. How nice. *glare* And I'd hoped you'd drop this charade before I was forced to rub your nose in it. *nasty smile* You're not even a student and as such, you're not eligible for a refund -- you've never paid tuition. For your services, Master Gnosos has recommended you receive pay. So here. Now go away. - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(CompletedTuitionReimbursementForm), 1, + "Completed Tuition Reimbursement Form", typeof(Aernya))); - Objectives.Add( new DeliverObjective( typeof( CompletedTuitionReimbursementForm ), 1, "Completed Tuition Reimbursement Form", typeof( Aernya ) ) ); + Rewards.Add(ItemReward.Strongbox); + } - Rewards.Add( ItemReward.Strongbox ); - } - } + public override bool IsChainTriggered => true; + } - #endregion + #endregion - #region Mobiles + #region Mobiles - [QuesterName( "Aernya (Umbra)" )] - public class Aernya : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Aernya"; + [QuesterName("Aernya (Umbra)")] + public class Aernya : BaseCreature + { + [Constructible] + public Aernya() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Mistress of Admissions"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Aernya() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Mistress of Admissions"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + AddItem(new Backpack()); + AddItem(new Sandals(Utility.RandomNeutralHue())); + AddItem(new Skirt(Utility.RandomBool() ? 0x1 : 0x0)); + AddItem(new Cloak(Utility.RandomBrightHue())); + AddItem(new FancyShirt(Utility.RandomBool() ? 0x3B2 : 0x3B3)); + } - AddItem( new Backpack() ); - AddItem( new Sandals( Utility.RandomNeutralHue() ) ); - AddItem( new Skirt( Utility.RandomBool() ? 0x1 : 0x0 ) ); - AddItem( new Cloak( Utility.RandomBrightHue() ) ); - AddItem( new FancyShirt( Utility.RandomBool() ? 0x3B2 : 0x3B3 ) ); - } + public Aernya(Serial serial) + : base(serial) + { + } - public Aernya( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Aernya"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [QuesterName( "Gorrow (Luna)" )] - public class Gorrow : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Gorrow"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074200, // Thank goodness you are here, there�s no time to lose. - 1074203 // Hello friend. I realize you are busy but if you would be willing to render me a service I can assure you that you will be judiciously renumerated. - ) ); - } + [QuesterName("Gorrow (Luna)")] + public class Gorrow : BaseCreature + { + [Constructible] + public Gorrow() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Mayor"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Gorrow() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Mayor"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + AddItem(new Backpack()); + AddItem(new Shoes(0x1BB)); + AddItem(new Tunic(Utility.RandomNeutralHue())); + AddItem(new LongPants(0x901)); + AddItem(new Cloak(Utility.RandomRedHue())); + } - AddItem( new Backpack() ); - AddItem( new Shoes( 0x1BB ) ); - AddItem( new Tunic( Utility.RandomNeutralHue() ) ); - AddItem( new LongPants( 0x901 ) ); - AddItem( new Cloak( Utility.RandomRedHue() ) ); - } + public Gorrow(Serial serial) + : base(serial) + { + } - public Gorrow( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override string DefaultName => "Gorrow"; + public override bool CanShout => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074200, // Thank goodness you are here, there�s no time to lose. + 1074203 // Hello friend. I realize you are busy but if you would be willing to render me a service I can assure you that you will be judiciously renumerated. + )); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [QuesterName( "Master Gnosos (Bedlam)" )] - public class MasterGnosos : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Master Gnosos"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074186 ); // Come here, I have a task. - } + int version = reader.ReadInt(); + } + } - [Constructible] - public MasterGnosos() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the necromancer"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = 0x83E8; - InitStats( 100, 100, 25 ); + [QuesterName("Master Gnosos (Bedlam)")] + public class MasterGnosos : BaseCreature + { + [Constructible] + public MasterGnosos() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the necromancer"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = 0x83E8; + InitStats(100, 100, 25); - HairItemID = 0x2049; - FacialHairItemID = 0x204B; + HairItemID = 0x2049; + FacialHairItemID = 0x204B; - AddItem( new Backpack() ); - AddItem( new Shoes( 0x485 ) ); - AddItem( new Robe( 0x497 ) ); + AddItem(new Backpack()); + AddItem(new Shoes(0x485)); + AddItem(new Robe(0x497)); - SetSkill( SkillName.EvalInt, 60.0, 80.0 ); - SetSkill( SkillName.Inscribe, 60.0, 80.0 ); - SetSkill( SkillName.MagicResist, 60.0, 80.0 ); - SetSkill( SkillName.SpiritSpeak, 60.0, 80.0 ); - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Necromancy, 60.0, 80.0 ); - } + SetSkill(SkillName.EvalInt, 60.0, 80.0); + SetSkill(SkillName.Inscribe, 60.0, 80.0); + SetSkill(SkillName.MagicResist, 60.0, 80.0); + SetSkill(SkillName.SpiritSpeak, 60.0, 80.0); + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Necromancy, 60.0, 80.0); + } - public MasterGnosos( Serial serial ) - : base( serial ) - { - } + public MasterGnosos(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Master Gnosos"; + public override bool CanShout => true; - writer.Write( (int) 0 ); // version - } + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074186); // Come here, I have a task. + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } - #endregion -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/NewHaven.cs b/Scripts/Engines/MLQuests/Definitions/NewHaven.cs index c339cde24..71fcdac89 100644 --- a/Scripts/Engines/MLQuests/Definitions/NewHaven.cs +++ b/Scripts/Engines/MLQuests/Definitions/NewHaven.cs @@ -4,121 +4,122 @@ using Server.Items; namespace Server.Engines.MLQuests.Definitions { - public class NewHavenEscort : BaseEscort - { - // New Haven escorts do not count for 'helping a human in need' - public override bool AwardHumanInNeed => false; + public class NewHavenEscort : BaseEscort + { + // Escort reward + private static readonly BaseReward m_Reward = new ItemReward("Gold", typeof(Gold), 500); - // Escort reward - private static readonly BaseReward m_Reward = new ItemReward( "Gold", typeof( Gold ), 500 ); + public NewHavenEscort(int title, int description, int progress, int destination, string region) + { + Activated = true; + Title = title; + Description = description; + RefusalMessage = + 1072288; // I wish you would reconsider my offer. I'll be waiting right here for someone brave enough to assist me. + InProgressMessage = progress; - public NewHavenEscort( int title, int description, int progress, int destination, string region ) - { - Activated = true; - Title = title; - Description = description; - RefusalMessage = 1072288; // I wish you would reconsider my offer. I'll be waiting right here for someone brave enough to assist me. - InProgressMessage = progress; + Objectives.Add(new EscortObjective(new QuestArea(destination, region))); - Objectives.Add( new EscortObjective( new QuestArea( destination, region ) ) ); + Rewards.Add(m_Reward); + } - Rewards.Add( m_Reward ); - } - } + // New Haven escorts do not count for 'helping a human in need' + public override bool AwardHumanInNeed => false; + } - public class EscortToNHAlchemist : NewHavenEscort - { - public EscortToNHAlchemist() - : base( 1072314, 1042769, 1072326, 1073864, "the New Haven Alchemist" ) - { - } - } + public class EscortToNHAlchemist : NewHavenEscort + { + public EscortToNHAlchemist() + : base(1072314, 1042769, 1072326, 1073864, "the New Haven Alchemist") + { + } + } - public class EscortToNHBard : NewHavenEscort - { - public EscortToNHBard() - : base( 1072315, 1042772, 1072327, 1073865, "the New Haven Bard" ) - { - } - } + public class EscortToNHBard : NewHavenEscort + { + public EscortToNHBard() + : base(1072315, 1042772, 1072327, 1073865, "the New Haven Bard") + { + } + } - public class EscortToNHWarrior : NewHavenEscort - { - public EscortToNHWarrior() - : base( 1072316, 1042787, 1072328, 1073866, "the New Haven Warrior" ) - { - } - } + public class EscortToNHWarrior : NewHavenEscort + { + public EscortToNHWarrior() + : base(1072316, 1042787, 1072328, 1073866, "the New Haven Warrior") + { + } + } - public class EscortToNHTailor : NewHavenEscort - { - public EscortToNHTailor() - : base( 1072317, 1042781, 1072329, 1073867, "the New Haven Tailor" ) - { - } - } + public class EscortToNHTailor : NewHavenEscort + { + public EscortToNHTailor() + : base(1072317, 1042781, 1072329, 1073867, "the New Haven Tailor") + { + } + } - public class EscortToNHCarpenter : NewHavenEscort - { - public EscortToNHCarpenter() - : base( 1072318, 1042775, 1072330, 1073868, "the New Haven Carpenter" ) - { - } - } + public class EscortToNHCarpenter : NewHavenEscort + { + public EscortToNHCarpenter() + : base(1072318, 1042775, 1072330, 1073868, "the New Haven Carpenter") + { + } + } - public class EscortToNHMapmaker : NewHavenEscort - { - public EscortToNHMapmaker() - : base( 1072319, 1042793, 1072331, 1073869, "the New Haven Mapmaker" ) - { - } - } + public class EscortToNHMapmaker : NewHavenEscort + { + public EscortToNHMapmaker() + : base(1072319, 1042793, 1072331, 1073869, "the New Haven Mapmaker") + { + } + } - public class EscortToNHMage : NewHavenEscort - { - public EscortToNHMage() - : base( 1072320, 1042790, 1072332, 1073870, "the New Haven Mage" ) - { - } - } + public class EscortToNHMage : NewHavenEscort + { + public EscortToNHMage() + : base(1072320, 1042790, 1072332, 1073870, "the New Haven Mage") + { + } + } - public class EscortToNHInn : NewHavenEscort - { - public EscortToNHInn() - : base( 1072321, 1042796, 1072333, 1073871, "the New Haven Inn" ) - { - } - } + public class EscortToNHInn : NewHavenEscort + { + public EscortToNHInn() + : base(1072321, 1042796, 1072333, 1073871, "the New Haven Inn") + { + } + } - public class EscortToNHFarm : NewHavenEscort - { - public EscortToNHFarm() - : base( 1072322, 1042799, 1072334, 1073872, "the New Haven Farm" ) - { - } - } + public class EscortToNHFarm : NewHavenEscort + { + public EscortToNHFarm() + : base(1072322, 1042799, 1072334, 1073872, "the New Haven Farm") + { + } + } - public class EscortToNHDocks : NewHavenEscort - { - public EscortToNHDocks() - : base( 1072323, 1042802, 1072335, 1073873, "the New Haven Docks" ) - { - } - } + public class EscortToNHDocks : NewHavenEscort + { + public EscortToNHDocks() + : base(1072323, 1042802, 1072335, 1073873, "the New Haven Docks") + { + } + } - public class EscortToNHBowyer : NewHavenEscort - { - public EscortToNHBowyer() - : base( 1072324, 1042805, 1072336, 1073874, "the New Haven Bowyer" ) - { - } - } + public class EscortToNHBowyer : NewHavenEscort + { + public EscortToNHBowyer() + : base(1072324, 1042805, 1072336, 1073874, "the New Haven Bowyer") + { + } + } - public class EscortToNHBank : NewHavenEscort - { - public EscortToNHBank() - : base( 1072325, 1042784, 1072337, 1073875, "the New Haven Bank" ) - { - } - } -} + public class EscortToNHBank : NewHavenEscort + { + public EscortToNHBank() + : base(1072325, 1042784, 1072337, 1073875, "the New Haven Bank") + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/NewHavenSkillTraining.cs b/Scripts/Engines/MLQuests/Definitions/NewHavenSkillTraining.cs index 8b0bcd8a8..71644f7ee 100644 --- a/Scripts/Engines/MLQuests/Definitions/NewHavenSkillTraining.cs +++ b/Scripts/Engines/MLQuests/Definitions/NewHavenSkillTraining.cs @@ -6,2384 +6,2534 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests - - public class CleansingOldHaven : MLQuest - { - public CleansingOldHaven() - { - Activated = true; - OneTimeOnly = true; - Title = 1077719; // Cleansing Old Haven - Description = 1077722; // Head East out of town to Old Haven. Consecrate your weapon, cast Divine Fury, and battle monsters there until you have raised your Chivalry skill to 50.
------

Hail, friend. The life of a Paladin is a life of much sacrifice, humility, bravery, and righteousness. If you wish to pursue such a life, I have an assignment for you. Adventure east to Old Haven, consecrate your weapon, and lay to rest the undead that inhabit there.

Each ability a Paladin wishes to invoke will require a certain amount of "tithing points" to use. A Paladin can earn these tithing points by donating gold at a shrine or holy place. You may tithe at this shrine.

Return to me once you feel that you are worthy of the rank of Apprentice Paladin. - RefusalMessage = 1077723; // Farewell to you my friend. Return to me if you wish to live the life of a Paladin. - InProgressMessage = 1077724; // There are still more undead to lay to rest. You still have more to learn. Return to me once you have done so. - CompletionMessage = 1077726; // Well done, friend. While I know you understand Chivalry is its own reward, I would like to reward you with something that will protect you in battle. It was passed down to me when I was a lad. Now, I am passing it on you. It is called the Bulwark Leggings. Thank you for your service. - CompletionNotice = 1077725; // You have achieved the rank of Apprentice Paladin. Return to Aelorn in New Haven to report your progress. - - Objectives.Add( new GainSkillObjective( SkillName.Chivalry, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077727, typeof( BulwarkLeggings ) ) ); // Bulwark Leggings - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Aelorn" ), new Point3D( 3527, 2516, 45 ), Map.Trammel ); - } - } - - public class TheRudimentsOfSelfDefense : MLQuest - { - public TheRudimentsOfSelfDefense() - { - Activated = true; - OneTimeOnly = true; - Title = 1077609; // The Rudiments of Self Defense - Description = 1077610; // Head East out of town and go to Old Haven. Battle monster there until you have raised your Wrestling skill to 50.Listen up! If you want to learn the rudiments of self-defense, you need toughening up, and there's no better way to toughen up than engaging in combat. Head East out of town to Old Haven and battle the undead there in hand to hand combat. Afraid of dying, you say? Well, you should be! Being an adventurer isn't a bed of posies, or roses, or however that saying goes. If you take a dirt nap, go to one of the nearby wandering healers and they'll get you back on your feet.Come back to me once you feel that you are worthy of the rank Apprentice Wrestler and i will reward you wit a prize. - RefusalMessage = 1077611; // Ok, featherweight. come back to me if you want to learn the rudiments of self-defense. - InProgressMessage = 1077630; // You have not achived the rank of Apprentice Wrestler. Come back to me once you feel that you are worthy of the rank Apprentice Wrestler and i will reward you with something useful. - CompletionMessage = 1077613; // It's about time! Looks like you managed to make it through your self-defense training. As i promised, here's a little something for you. When worn, these Gloves of Safeguarding will increase your awareness and resistances to most elements except poison. Oh yeah, they also increase your natural health regeneration aswell. Pretty handy gloves, indeed. Oh, if you are wondering if your meditation will be hinered while wearing these gloves, it won't be. Mages can wear cloth and leather items without needing to worry about that. Now get out of here and make something of yourself. - CompletionNotice = 1077612; // You have achieved the rank of Apprentice Wrestler. Return to Dimethro in New Haven to receive your prize. - - Objectives.Add( new GainSkillObjective( SkillName.Wrestling, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077614, typeof( GlovesOfSafeguarding ) ) ); // Gloves Of Safeguarding - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Dimethro" ), new Point3D( 3528, 2520, 25 ), Map.Trammel ); - } - } - - public class CrushingBonesAndTakingNames : MLQuest - { - public CrushingBonesAndTakingNames() - { - Activated = true; - OneTimeOnly = true; - Title = 1078070; // Crushing Bones and Taking Names - Description = 1078065; // Head East out of town and go to Old Haven. While wielding your mace,battle monster there until you have raised your Mace Fighting skill to 50. I see you want to learn a real weapon skill and not that toothpick training Jockles hasto offer. Real warriors are called Armsmen, and they wield mace weapons. No doubt about it. Nothing is more satisfying than knocking the wind out of your enemies, smashing there armor, crushing their bones, and taking there names. Want to learn how to wield a mace? Well i have an assignment for you. Head East out of town and go to Old Haven. Undead have plagued the town, so there are plenty of bones for you to smash there. Come back to me after you have ahcived the rank of Apprentice Armsman, and i will reward you with a real weapon. - RefusalMessage = 1078068; // I thought you wanted to be an Armsman and really make something of yourself. You have potential, kid, but if you want to play with toothpicks, run to Jockles and he will teach you how to clean your teeth with a sword. If you change your mind, come back to me, and i will show you how to wield a real weapon. - InProgressMessage = 1078067; // Listen kid. There are a lot of undead in Old Haven, and you haven't smashed enough of them yet. So get back there and do some more cleansing. - CompletionMessage = 1078069; // Now that's what I'm talking about! Well done! Don't you like crushing bones and taking names? As i promised, here is a war mace for you. It hits hard. It swings fast. It hits often. What more do you need? Now get out of here and crush some more enemies! - CompletionNotice = 1078068; // You have achieved the rank of Apprentice Armsman. Return to Churchill in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Macing, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078062, typeof( ChurchillsWarMace ) ) ); // Churchill's War Mace - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Churchill" ), new Point3D( 3531, 2531, 20 ), Map.Trammel ); - } - } - - public class SwiftAsAnArrow : MLQuest - { - public SwiftAsAnArrow() - { - Activated = true; - OneTimeOnly = true; - Title = 1078201; // Swift as an Arrow - Description = 1078205; // Head East out of town and go to Old Haven. While wielding your bow or crossbow, battle monster there until you have raised your Archery skill to 50. Well met, friend. Imagine yourself in a distant grove of trees, You raise your bow, take slow, careful aim, and with the twitch of a finger, you impale your prey with a deadly arrow. You look like you would make a excellent archer, but you will need practice. There is no better way to practice Archery than when you life is on the line. I have a challenge for you. Head East out of town and go to Old Haven. While wielding your bow or crossbow, battle the undead that reside there. Make sure you bring a healthy supply of arrows (or bolts if you prefer a crossbow). If you wish to purchase a bow, crossbow, arrows, or bolts, you can purchase them from me or the Archery shop in town. You can also make your own arrows with the Bowcraft/Fletching skill. You will need fletcher's tools, wood to turn into sharft's, and feathers to make arrows or bolts. Come back to me after you have achived the rank of Apprentice Archer, and i will reward you with a fine Archery weapon. - RefusalMessage = 1078206; // I understand that Archery may not be for you. Feel free to visit me in the future if you change your mind. - InProgressMessage = 1078207; // You're doing great as an Archer! however, you need more practice. - CompletionMessage = 1078209; // Congratulation! I want to reward you for your accomplishment. Take this composite bow. It is called " Heartseeker". With it, you will shoot with swiftness, precision, and power. I hope "Heartseeker" serves you well. - CompletionNotice = 1078208; // You have achieved the rank of Apprentice Archer. Return to Robyn in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Archery, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078210, typeof( Heartseeker ) ) ); // Heartseeker - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Robyn" ), new Point3D( 3535, 2531, 20 ), Map.Trammel ); - } - } - - public class EnGuarde : MLQuest - { - public EnGuarde() - { - Activated = true; - OneTimeOnly = true; - Title = 1078186; // En Guarde! - Description = 1078190; // Head East out of town to Old Haven. Battle monsters there until you have raised your Fencing skill to 50.
------

Well hello there, lad. Fighting with elegance and precision is far more enriching than slugging an enemy with a club or butchering an enemy with a sword. Learn the art of Fencing if you want to master combat and look good doing it!

The key to being a successful fencer is to be the complement and not the opposition to your opponent's strength. Watch for your opponent to become off balance. Then finish him off with finesse and flair.

There are some undead that need cleansing out in Old Haven towards the East. Head over there and slay them, but remember, do it with style!

Come back to me once you have achieved the rank of Apprentice Fencer, and I will reward you with a prize. - RefusalMessage = 1078191; // I understand, lad. Being a hero isn't for everyone. Run along, then. Come back to me if you change your mind. - InProgressMessage = 1078192; // You're doing well so far, but you're not quite ready yet. Head back to Old Haven, to the East, and kill some more undead. - CompletionMessage = 1078194; // Excellent! You are beginning to appreciate the art of Fencing. I told you fighting with elegance and precision is more enriching than fighting like an ogre.

Since you have returned victorious, please take this war fork and use it well. The war fork is a finesse weapon, and this one is magical! I call it "Recaro's Riposte". With it, you will be able to parry and counterstrike with ease! Your enemies will bask in your greatness and glory! Good luck to you, lad, and keep practicing! - CompletionNotice = 1078193; // You have achieved the rank of Apprentice Fencer. Return to Recaro in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Fencing, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078195, typeof( RecarosRiposte ) ) ); // Recaro's Riposte - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Recaro" ), new Point3D( 3536, 2534, 20 ), Map.Trammel ); - } - } - - public class TheArtOfWar : MLQuest - { - public TheArtOfWar() - { - Activated = true; - OneTimeOnly = true; - Title = 1077667; // The Art of War - Description = 1077670; // Head East out of town to Old Haven. Battle monsters there until you have raised your Tactics skill to 50.
------

Knowing how to hold a weapon is only half of the battle. The other half is knowing how to use it against an opponent. It's one thing to kill a few bunnies now and then for fun, but a true warrior knows that the right moves to use against a lich will pretty much get your arse fried by a dragon.

I'll help teach you how to fight so that when you do come up against that dragon, maybe you won't have to walk out of there "OooOOooOOOooOO'ing" and looking for a healer.

There are some undead that need cleaning out in Old Haven towards the east. Why don't you head on over there and practice killing things?

When you feel like you've got the basics down, come back to me and I'll see if I can scrounge up an item to help you in your adventures later on. - RefusalMessage = 1077671; // That's too bad. I really thought you had it in you. Well, I'm sure those undead will still be there later, so if you change your mind, feel free to stop on by and I'll help you the best I can. - InProgressMessage = 1077672; // You're making some progress, that i can tell, but you're not quite good enough to last for very long out there by yourself. Head back to Old Haven, to the east, and kill some more undead. - CompletionMessage = 1077674; // Hey, good job killing those undead! Hopefully someone will come along and clean up the mess. All that blood and guts tends to stink after a few days, and when the wind blows in from the east, it can raise a mighty stink!

Since you performed valiantly, please take these arms and use them well. I've seen a few too many harvests to be running around out there myself, so you might as well take it.

There is a lot left for you to learn, but I think you'll do fine. Remember to keep your elbows in and stick'em where it hurts the most! - CompletionNotice = 1077673; // You have achieved the rank of Apprentice Warrior. Return to Alden Armstrong in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Tactics, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077675, typeof( ArmsOfArmstrong ) ) ); // Arms of Armstrong - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "AldenArmstrong" ), new Point3D( 3535, 2538, 20 ), Map.Trammel ); - } - } - - public class TheWayOfTheBlade : MLQuest - { - public TheWayOfTheBlade() - { - Activated = true; - OneTimeOnly = true; - Title = 1077658; // The way of The Blade - Description = 1077661; // Head East out of town and go to Old Haven. While wielding your sword, battle monster there until you have raised your Swordsmanship skill to 50. *as you approach, you notice Jockles sizing you up with a skeptical look on his face* i can see you want to learn how to handle a blade. It's a lot harder than it looks, and you're going to have to put alot of time and effort if you ever want to be half as good as i am. I'll tell you what, kid, I'll help you get started, but you're going to have to do all the work if you want to learn something. East of here, outside of town, is Old Haven. It's been overrun with the nastiest of undead you've seen, which makes it a perfect place for you to turn that sloppy grin on your face into actual skill at handling a sword. Make sure you have a sturdy Swordsmanship weapon in good repair before you leave. 'tis no fun to travel all the way down there just to find out you forgot your blade! When you feel that you've cut down enough of those foul smelling things to learn how to handle a blade without hurting yourself, come back to me. If i think you've improved enough, I'll give you something suited for a real warrior. - RefusalMessage = 1077662; // Ha! I had a feeling you were a lily-livered pansy. You might have potential, but you're scared by a few smelly undead, maybe it's better that you stay away from sharp objects. After all, you wouldn't want to hurt yourself swinging a sword. If you change your mind, I might give you another chance...maybe. - InProgressMessage = 1077663; // *Jockles looks you up and down* Come on! You've got to work harder than that to get better. Now get out of here, go kill some more of those undead to the east in Old Haven, and don't come back till you've got real skill. - CompletionMessage = 1077665; // Well, well, look at what we have here! You managed to do it after all. I have to say, I'm a little surprised that you came back in one piece, but since you did. I've got a little something for you. This is a fine blade that served me well in my younger days. Of course I've got much better swords at my disposal now, so I'll let you go ahead and use it under one condition. Take goodcare of it and treat it with the respect that a fine sword deserves. You're one of the quickers learners I've seen, but you still have a long way to go. Keep at it, and you'll get there someday. Happy hunting, kid. - CompletionNotice = 1077664; // You have achieved the rank of Apprentice Swordsman. Return to Jockles in New Haven to see what kind of reward he has waiting for you. Hopefully he'll be a little nicer this time! - - Objectives.Add( new GainSkillObjective( SkillName.Swords, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077666, typeof( JocklesQuicksword ) ) ); // Jockles' Quicksword - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Jockles" ), new Point3D( 3535, 2544, 20 ), Map.Trammel ); - } - } - - public class ThouAndThineShield : MLQuest - { - public ThouAndThineShield() - { - Activated = true; - OneTimeOnly = true; - Title = 1077704; // Thou and Thine Shield - Description = 1077707; // Head East out of town and go to Old Haven. Battle monsters, or simply let them hit you, while holding a shield or a weapon until you have raised your Parrying skill to 50. Oh, hello. You probably want me to teach you how to parry, don't you? Very Well. First, you'll need a weapon or a shield. Obviously shields work best of all, but you can parry with a 2-handed weapon. Or if you're feeling particularly brave, a 1-handed weapon will do in a pinch, I'd advise you to go to Old Haven, which you'll find to the East, and practice blocking incoming blows from the undead there. You'll learn quickly if you have more than one opponent attacking you at the same time to practice parrying lots of blows at once. That's the quickest way to master the art of parrying. If you manage to improve your skill enough, i have a shield that you might find useful. Come back to me when you've trained to an apprentice level. - RefusalMessage = 1077708; // It's your choice, obviously, but I'd highly suggest that you learn to parry before adventuring out into the world. Come talk to me again when you get tired of being beat on by your opponents - InProgressMessage = 1077709; // You're doing well, but in my opinion, I Don't think you really want to continue on without improving your parrying skill a bit more. Go to Old Haven, to the East, and practice blocking blows with a shield. - CompletionMessage = 1077711; // Well done! You're much better at parrying blows than you were when we first met. You should be proud of your new ability and I bet your body is greatful to you aswell. *Tyl Ariadne laughs loudly at his ownn (mostly lame) joke* Oh yes, I did promise you a shield if I thought you were worthy of having it, so here you go. My father made these shields for the guards who served my father faithfully for many years, and I just happen to have obe that i can part with. You should find it useful as you explore the lands.Good luck, and may the Virtues be your guide. - CompletionNotice = 1077710; // You have achieved the rank of Apprentice Warrior (for Parrying). Return to Tyl Ariadne in New Haven as soon as you can to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Parry, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077694, typeof( EscutcheonDeAriadne ) ) ); // Escutcheon de Ariadne - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "TylAriadne" ), new Point3D( 3525, 2556, 20 ), Map.Trammel ); - } - } - - public class DefyingTheArcane : MLQuest - { - public DefyingTheArcane() - { - Activated = true; - OneTimeOnly = true; - Title = 1077621; // Defying the Arcane - Description = 1077623; // Head East out of town and go to Old Haven. Battle spell casting monsters there until you have raised your Resisting Spells skill to 50.
------

Hail and well met! To become a true master of the arcane art of Magery, I suggest learning the complementary skill known as Resisting Spells. While the name of this skill may suggest that it helps with resisting all spells, this is not the case. This skill helps you lessen the severity of spells that lower your stats or ones that last for a specific duration of time. It does not lessen damage from spells such as Energy Bolt or Flamestrike.

The Magery spells that can be resisted are Clumsy, Curse, Feeblemind, Mana Drain, Mana Vampire, Paralyze, Paralyze Field, Poison, Poison Field, and Weaken.

The Necromancy spells that can be resisted are Blood Oath, Corpse Skin, Mind Rot, and Pain Spike.

At higher ranks, the Resisting Spells skill also benefits you by adding a bonus to your minimum elemental resists. This bonus is only applied after all other resist modifications - such as from equipment - has been calculated. It's also not cumulative. It compares the number of your minimum resists to the calculated value of your modifications and uses the higher of the two values.

As you can see, Resisting Spells is a difficult skill to understand, and even more difficult to master. This is because in order to improve it, you will have to put yourself in harm's way - as in the path of one of the above spells.

Undead have plagued the town of Old Haven. We need your assistance in cleansing the town of this evil influence. Old Haven is located east of here. Battle the undead spell casters that inhabit there.

Comeback to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. - RefusalMessage = 1077624; // The ability to resist powerful spells is a taxing experience. I understand your resistance in wanting to pursue it. If you wish to reconsider, feel free to return to me for Resisting Spells training. Good journey to you! - InProgressMessage = 1077632; // You have not achieved the rank of Apprentice Mage. Come back to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. - CompletionMessage = 1077626; // You have successfully begun your journey in becoming a true master of Magery. On behalf of the New Haven Mage Council I wish to present you with this bracelet. When worn, the Bracelet of Resilience will enhance your resistances vs. the elements, physical, and poison harm. The Bracelet of Resilience also magically enhances your ability fend off ranged and melee attacks. I hope it serves you well. - CompletionNotice = 1077625; // You have achieved the rank of Apprentice Mage (for Resisting Spells). Return to Alefian in New Haven to receive your arcane prize. - - Objectives.Add( new GainSkillObjective( SkillName.MagicResist, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077627, typeof( BraceletOfResilience ) ) ); // Bracelet of Resilience - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Alefian" ), new Point3D( 3473, 2497, 72 ), Map.Trammel ); - } - } - - public class StoppingTheWorld : MLQuest - { - public StoppingTheWorld() - { - Activated = true; - OneTimeOnly = true; - Title = 1077597; // Stopping the World - Description = 1077598; // Head East out of town and go to Old Haven. Use spells and abilities to deplete your mana and meditate there until you have raised your Meditation skill to 50. Well met! I can teach you how to 'Stop the World' around you and focus your inner energies on replenishing you mana. What is mana? Mana is the life force for everyone who practices arcane arts. When a practitioner of magic invokes a spell or scribes a scroll. It consumes mana. Having a abundant supply of mana is vital to excelling as a practitioner of the arcane. Those of us who study the art of Meditation are also known as stotics. The Meditation skill allows stoics to increase the rate at which they regenerate mana A Stoic needs to perform abilities or cast spells to deplete mana before he can meditate to replenish it. Meditation can occur passively or actively. Actively Meditation is more difficult to master but allows for the stoic to replenish mana at a significantly faster rate. Metal armor inerferes with the regenerative properties of Meditation. It is wise to wear leather or cloth protection when meditating. Head east out of town and go to Old Haven. Use spells and abilities to deplete your mana and actively meditate to replenish it. Come back once you feel you are at the worthy rank of Apprentice Stoic and i will reward you with a arcane prize. - RefusalMessage = 1077599; // Seek me out if you ever wish to study the art of Meditation. Good journey. - InProgressMessage = 1077628; // You have not achieved the rank of Apprentice Stoic. Come back to me once you feel that you are worthy of the rank Apprentice Stoic and i will reward you with a arcane prize. - CompletionMessage = 1077626; // You have successfully begun your journey in becoming a true master of Magery. On behalf of the New Haven Mage Council I wish to present you with this bracelet. When worn, the Bracelet of Resilience will enhance your resistances vs. the elements, physical, and poison harm. The Bracelet of Resilience also magically enhances your ability fend off ranged and melee attacks. I hope it serves you well. - CompletionNotice = 1077600; // You have achieved the rank of Apprentice Stoic (for Meditation). Return to Gustar in New Haven to receive your arcane prize. - - Objectives.Add( new GainSkillObjective( SkillName.Meditation, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077602, typeof( PhilosophersHat ) ) ); // Philosopher's Hat - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Gustar" ), new Point3D( 3474, 2492, 91 ), Map.Trammel ); - } - } - - public class ScribingArcaneKnowledge : MLQuest - { - public ScribingArcaneKnowledge() - { - Activated = true; - OneTimeOnly = true; - Title = 1077615; // Scribing Arcane Knowledge - Description = 1077616; // While here at the New Haven Magery Library, use a scribe's pen and scribe and 3rd and 4th circle Magery scrolls that you have in your spellbook. Remember, you will need blank scrolls as well. Do this until you have raised your Inscription skill to 50.
------

Greetings and welcome to the New Haven Magery Library! You wish to learn how to scribe spell scrolls? You have come to the right place! Inscribed in a steady hand and imbued with the power of reagents, a scroll can mean the difference between life and death in a perilous situation. Those knowledgeable in Inscription may transcribe spells to create useful and valuable magical scrolls.

Before you inscribe a spell, you must first be able to cast the spell without the aid of a scroll. This means that you need the appropriate level of proficiency as a mage, the required mana, and the required reagents. Second, you will need a blank scroll to write on and a scribe's pen. Then, you will need to decide which particular spell you wish to scribe. It may sound easy, but there is a bit more to it. As with the development of all skills, you need to practice Inscription of lower level spells before you can move onto the more difficult ones.

The most important aspect of Inscription is mana. Inscribing a scroll with a magic spell drains your mana. When inscribing 3rd circle or lower spells this will not be much of a problem for these spells consume a small amount of mana. However, when you are inscribing higher circle spells, you may see your mana drain rapidly. When this happens, pause or meditate before continuing.

I suggest you begin scribing any 3rd and 4th circle spells that you know. If you don't possess any, you can always barter with one of the local mage merchants or a fellow adventurer that is a seasoned Scribe.

Come back to me once you feel that you are worthy of the rank of Apprentice Scribe and I will reward you with an arcane prize. - RefusalMessage = 1077617; // I understand. When you are ready, feel free to return to me for Inscription training. Thanks for stopping by! - InProgressMessage = 1077631; // You have not achieved the rank of Apprentice Scribe. Come back to me once you feel that you are worthy of the rank Apprentice Scribe and i will reward you with a arcane prize. - CompletionMessage = 1077619; // Scribing is a very fulfilling pursuit. I am pleased to see you embark on this journey. You sling a pen well! On behalf of the New Haven Mage Council I wish to present you with this spellbook. When equipped, the Hallowed Spellbook greatly enhances the potency of your offensive spells when used against Undead. Be mindful, though. While this book is equipped, when you invoke your powerful spells and abilities vs. Humanoids such as other humans, orcs, ettins, trolls, and the like, your offensive spells will diminish in effectiveness. I suggest unequipping the Hallowed Spellbook when battling Humanoids. I hope this spellbook serves you well. - CompletionNotice = 1077618; // You have achieved the rank of Apprentice Scribe. Return to Jillian in New Haven to receive your arcane prize. - - Objectives.Add( new GainSkillObjective( SkillName.Inscribe, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077620, typeof( HallowedSpellbook ) ) ); // Hallowed Spellbook - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Jillian" ), new Point3D( 3465, 2490, 71 ), Map.Trammel ); - } - } - - public class TheMagesApprentice : MLQuest - { - public TheMagesApprentice() - { - Activated = true; - OneTimeOnly = true; - Title = 1077576; // The Mage's Apprentice - Description = 1077577; // Head East out of town and go to Old Haven. Cast fireballs and lightning bolts against monsters there until you have raised your Magery skill to 50. Greetings. You seek to unlock the secrets of the arcane art of Magery. The New Haven Mage Council has an assignment for you. Undead have plagued the town of Old Haven. We need your assistance in cleansing the town of this evil influence. Old Haven is located east of here. I suggest using your offensive Magery spells such as Fireball and Lightning Bolt against the Undead that inhabit there. Make sure you have plenty of reagents before embarking on your journey. Reagents are required to cast Magery spells. You can purchase extra reagents at the nearby Reagent shop, or you can find reagents growing in the nearby wooded areas. You can see which reagents are required for each spell by looking in your spellbook. Come back to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. - RefusalMessage = 1077578; // Very well, come back to me when you are ready to practice Magery. You have so much arcane potential. 'Tis a shame to see it go to waste. The New Haven Mage Council could really use your help. - InProgressMessage = 1077579; // You have not achieved the rank of Apprentice Mage. Come back to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. - CompletionMessage = 1077581; // Well done! On behalf of the New Haven Mage Council I wish to present you with this staff. Normally a mage must unequip weapons before spell casting. While wielding your new Ember Staff, however, you will be able to invoke your Magery spells. Even if you do not currently possess skill in Mace Fighting, the Ember Staff will allow you to fight as if you do. However, your Magery skill will be temporarily reduced while doing so. Finally, the Ember Staff occasionally smites a foe with a Fireball while wielding it in melee combat. I hope the Ember Staff serves you well. - CompletionNotice = 1077580; // You have achieved the rank of Apprentice Mage. Return to Kaelynna in New Haven to receive your arcane prize. - - Objectives.Add( new GainSkillObjective( SkillName.Magery, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077582, typeof( EmberStaff ) ) ); // Ember Staff - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Kaelynna" ), new Point3D( 3486, 2491, 52 ), Map.Trammel ); - } - } - - public class ScholarlyTask : MLQuest - { - public ScholarlyTask() - { - Activated = true; - OneTimeOnly = true; - Title = 1077603; // A Scholarly Task - Description = 1077604; // Head East out of town and go to Old Haven. Use Evaluating Intelligence on all creatures you see there. You can also cast Magery spells as well to raise Evaluating Intelligence. Do these activities until you have raised your Evaluating Intelligence skill to 50.
------

Hello. Truly knowing your opponent is essential for landing your offensive spells with precision. I can teach you how to enhance the effectiveness of your offensive spells, but first you must learn how to size up your opponents intellectually. I have a scholarly task for you. Head East out of town and go to Old Haven. Use Evaluating Intelligence on all creatures you see there. You can also cast Magery spells as well to raise Evaluating Intelligence.

Come back to me once you feel that you are worthy of the rank of Apprentice Scholar and I will reward you with an arcane prize. - RefusalMessage = 1077605; // Return to me if you reconsider and wish to become an Apprentice Scholar. - InProgressMessage = 1077629; // You have not achieved the rank of Apprentice Scholar. Come back to me once you feel that you are worthy of the rank of Apprentice Scholar and I will reward you with an arcane prize. - CompletionMessage = 1077607; // You have completed the task. Well done. On behalf of the New Haven Mage Council I wish to present you with this ring. When worn, the Ring of the Savant enhances your intellectual aptitude and increases your mana pool. Your spell casting abilities will take less time to invoke and recovering from such spell casting will be hastened. I hope the Ring of the Savant serves you well. - CompletionNotice = 1077606; // You have achieved the rank of Apprentice Scholar. Return to Mithneral in New Haven to receive your arcane prize. - - Objectives.Add( new GainSkillObjective( SkillName.EvalInt, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077608, typeof( RingOfTheSavant ) ) ); // Ring of the Savant - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Mithneral" ), new Point3D( 3485, 2491, 71 ), Map.Trammel ); - } - } - - public class TheRightToolForTheJob : MLQuest - { - public TheRightToolForTheJob() - { - Activated = true; - OneTimeOnly = true; - Title = 1077741; // The Right Tool for the Job - Description = 1077744; // Create new scissors and hammers while inside Amelia's workshop. Try making scissors up to 45 skill, the switch to making hammers until 50 skill.
-----

Hello! I guess you're here to learn something about Tinkering, eh? You've come to the right place, as Tinkering is what I've dedicated my life to.

You'll need two things to get started: a supply of ingots and the right tools for the job. You can either buy ingots from the market, or go mine them yourself. As for tools, you can try making your own set of Tinker's Tools, or if you'd prefer to buy them, I have some for sale.

Working here in my shop will let me give you pointers as you go, so you'll be able to learn faster than anywhere else. Start off making scissors until you reach 45 tinkering skill, then switch to hammers until you've achieved 50. Once you've done that, come talk to me and I'll give you something for your hard work. - RefusalMessage = 1077745; // I’m disappointed that you aren’t interested in learning more about Tinkering. It’s really such a useful skill!

*Amelia smiles*

At least you know where to find me if you change your mind, since I rarely spend time outside of this shop. - InProgressMessage = 1077746; // Nice going! You're not quite at Apprentice Tinkering yet, though, so you better get back to work. Remember that the quickest way to learn is to make scissors up until 45 skill, and then switch to hammers. Also, don't forget that working here in my shop will let me give you tips so you can learn faster. - CompletionMessage = 1077748; // You've done it! Look at our brand new Apprentice Tinker! You've still got quite a lot to learn if you want to be a Grandmaster Tinker, but I believe you can do it! Just keep in mind that if you're tinkering just to practice and improve your skill, make items that are moderately difficult (60-80% success chance), and try to stick to ones that use less ingots.

Come here, my brand new Apprentice Tinker, I want to give you something special. I created this just for you, so I hope you like it. It's a set of Tinker's Tools that contains a bit of magic. These tools have more charges than any Tinker's Tools a Tinker can make. You can even use them to make a normal set of tools, so that way you won't ever find yourself stuck somewhere with no tools! - CompletionNotice = 1077747; // You have achieved the rank of Apprentice Tinker. Talk to Amelia Youngstone in New Haven to see what kind of reward she has waiting for you. - - Objectives.Add( new GainSkillObjective( SkillName.Tinkering, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077749, typeof( AmeliasToolbox ) ) ); // Amelia’s Toolbox - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "AmeliaYoungstone" ), new Point3D( 3459, 2529, 53 ), Map.Trammel ); - } - } - - public class KnowThineEnemy : MLQuest - { - public KnowThineEnemy() - { - Activated = true; - OneTimeOnly = true; - Title = 1077685; // Know Thine Enemy - Description = 1077688; // Head East out of town to Old Haven. Battle monsters there, or heal yourself and other players, until you have raised your Anatomy skill to 50.
------

Hail and well met. You must be here to improve your knowledge of Anatomy. Well, you've come to the right place because I can teach you what you need to know. At least all you'll need to know for now. Haha!

Knowing about how living things work inside can be a very useful skill. Not only can you learn where to strike an opponent to hurt him the most, but you can use what you learn to heal wounds better as well. Just walking around town, you can even tell if someone is strong or weak or if they happen to be particularly dexterous or not.

If you're interested in learning more, I'd advise you to head out to Old Haven, just to the east, and jump into the fray. You'll learn best by engaging in combat while keeping you and your fellow adventurers healed, or you can even try sizing up your opponents.

While you're gone, I'll dig up something you may find useful. - RefusalMessage = 1077689; // It's your choice, but I wouldn't head out there without knowing what makes those things tick inside! If you change your mind, you can find me right here dissecting frogs, cats or even the occasional unlucky adventurer. - InProgressMessage = 1077690; // I'm surprised to see you back so soon. You've still got a ways to go if you want to really understand the science of Anatomy. Head out to Old Haven and practice combat and healing yourself or other adventurers. - CompletionMessage = 1077692; // By the Virtues, you've done it! Congratulations mate! You still have quite a ways to go if you want to perfect your knowledge of Anatomy, but I know you'll get there someday. Just keep at it.

In the meantime, here's a piece of armor that you might find useful. It's not fancy, but it'll serve you well if you choose to wear it.

Happy adventuring, and remember to keep your cranium separate from your clavicle! - CompletionNotice = 1077691; // You have achieved the rank of Apprentice Healer (for Anatomy). Return to Andreas Vesalius in New Haven as soon as you can to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Anatomy, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077693, typeof( TunicOfGuarding ) ) ); // Tunic of Guarding - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "AndreasVesalius" ), new Point3D( 3457, 2550, 35 ), Map.Trammel ); - } - } - - public class BruisesBandagesAndBlood : MLQuest - { - public BruisesBandagesAndBlood() - { - Activated = true; - OneTimeOnly = true; - Title = 1077676; // Bruises, Bandages and Blood - Description = 1077679; // Head East out of town and go to Old Haven. Heal yourself and other players until you have raised your Healing skill to 50.
------

Ah, welcome to my humble practice. I am Avicenna, New Haven's resident Healer. A lot of adventurers head out into the wild from here, so I keep rather busy when they come back bruised, bleeding, or worse.

I can teach you how to bandage a wound, sure, but it's not a job for the queasy! For some folks, the mere sight of blood is too much for them, but it's something you'll get used to over time. It is one thing to cut open a living thing, but it's quite another to sew it back up and save it from sure death. 'Tis noble work, healing.

Best way for you to practice fixing up wounds is to head east out to Old Haven and either practice binding up your own wounds, or practice on someone else. Surely they'll be grateful for the assistance.

Make sure to take enough bandages with you! You don't want to run out in the middle of a tough fight. - RefusalMessage = 1077680; // No? Are you sure? Well, when you feel that you're ready to practice your healing, come back to me. I'll be right here, fixing up adventurers and curing the occasional cold! - InProgressMessage = 1077681; // Hail! 'Tis good to see you again. Unfortunately, you're not quite ready to call yourself an Apprentice Healer quite yet. Head back out to Old Haven, due east from here, and bandage up some wounds. Yours or someone else's, it doesn't much matter. - CompletionMessage = 1077683; // Hello there, friend. I see you've returned in one piece, and you're an Apprentice Healer to boot! You should be proud of your accomplishment, as not everyone has "the touch" when it comes to healing.

I can't stand to see such good work go unrewarded, so I have something I'd like you to have. It's not much, but it'll help you heal just a little faster, and maybe keep you alive.

Good luck out there, friend, and don't forget to help your fellow adventurer whenever possible! - CompletionNotice = 1077682; // You have achieved the rank of Apprentice Healer. Return to Avicenna in New Haven as soon as you can to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Healing, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077684, typeof( HealersTouch ) ) ); // Healer's Touch - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Avicenna" ), new Point3D( 3464, 2558, 35 ), Map.Trammel ); - } - } - - public class TheInnerWarrior : MLQuest - { - public TheInnerWarrior() - { - Activated = true; - OneTimeOnly = true; - Title = 1077696; // The Inner Warrior - Description = 1077699; // Head East out of town to Old Haven. Expend stamina and mana until you have raised your Focus skill to 50.
------

Well, hello there. Don't you look like quite the adventurer!

You want to learn more about Focus, do you? I can teach you something about that, but first you should know that not everyone can be disciplined enough to excel at it. Focus is the ability to achieve inner balance in both body and spirit, so that you recover from physical and mental exertion faster than you otherwise would.

If you want to practice Focus, the best place to do that is east of here, in Old Haven, where you'll find an undead infestation. Exert yourself physically by engaging in combat and moving quickly. For testing your mental balance, expend mana in whatever way you find most suitable to your abilities. Casting spells and using abilities work well for consuming your mana.

Go. Train hard, and you will find that your concentration will improve naturally. When you've improved your ability to focus yourself at an Apprentice level, come back to me and I shall give you something worthy of your new ability. - RefusalMessage = 1077700; // I'm disappointed. You have a lot of inner potential, and it would pain me greatly to see you waste that. Oh well. If you change your mind, I'll be right here. - InProgressMessage = 1077701; // Hello again. I see you've returned, but it seems that your Focus skill hasn't improved as much as it could have. Just head east, to Old Haven, and exert yourself physically and mentally as much as possible. To do this physically, engage in combat and move as quickly as you can. For exerting yourself mentally, expend mana in whatever way you find most suitable to your abilities. Casting spells and using abilities work well for consuming your mana.

Return to me when you have gained enough Focus skill to be considered an Apprentice Stoic. - CompletionMessage = 1077703; // Look who it is! I knew you could do it if you just had the discipline to apply yourself. It feels good to recover from battle so quickly, doesn't it? Just wait until you become a Grandmaster, it's amazing!

Please take this gift, as you've more than earned it with your hard work. It will help you recover even faster during battle, and provides a bit of protection as well.

You have so much more potential, so don't stop trying to improve your Focus now! Safe travels! - CompletionNotice = 1077702; // You have achieved the rank of Apprentice Stoic (for Focus). Return to Sarsmea Smythe in New Haven to see what kind of reward she has waiting for you. - - Objectives.Add( new GainSkillObjective( SkillName.Focus, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077695, typeof( ClaspOfConcentration ) ) ); // Clasp of Concentration - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "SarsmeaSmythe" ), new Point3D( 3492, 2577, 15 ), Map.Trammel ); - } - } - - public class TheArtOfStealth : MLQuest - { - public TheArtOfStealth() - { - Activated = true; - OneTimeOnly = true; - Title = 1078154; // The Art of Stealth - Description = 1078158; // Head East out of town and go to Old Haven. While wielding your fencing weapon, battle monsters with focus attack and summon mirror images up to 40 Ninjitsu skill, and continue practicing focus attack on monsters until 50 Ninjitsu skill.
------

Welcome, young one. You seek to learn Ninjitsu. With it, and the book of Ninjitsu, a Ninja can evoke a number of special abilities including transforming into a variety of creatures that give unique bonuses, using stealth to attack unsuspecting opponents or just plain disappear into thin air! If you do not have a book of Ninjitsu, you can purchase one from me.

I have an assignment for you. Head East out of town and go to Old Haven. While wielding your fencing weapon, battle monsters with focus attack and summon mirror images up to Novice rank, and continue focusing your attacks for greater damage on monsters until you become an Apprentice Ninja. Each image will absorb one attack. The art of deception is a strong defense. Use it wisely.

Come back to me once you have achieved the rank of Apprentice Ninja, and I shall reward you with something useful. - RefusalMessage = 1078159; // Come back to me if you with to learn Ninjitsu in the future. - InProgressMessage = 1078160; // You have not achieved the rank of Apprentice Ninja. Come back to me once you have done so. - CompletionMessage = 1078162; // You have done well, young one. Please accept this kryss as a gift. It is called the "Silver Serpent Blade". With it, you will strike with precision and power. This should aid you in your journey as a Ninja. Farewell. - CompletionNotice = 1078161; // You have achieved the rank of Apprentice Ninja. Return to Ryuichi in New Haven to see what kind of reward he has waiting for you. - - Objectives.Add( new GainSkillObjective( SkillName.Ninjitsu, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078163, typeof( SilverSerpentBlade ) ) ); // Silver Serpent Blade - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Ryuichi" ), new Point3D( 3422, 2520, 21 ), Map.Trammel ); - } - } - - public class BecomingOneWithTheShadows : MLQuest - { - public BecomingOneWithTheShadows() - { - Activated = true; - OneTimeOnly = true; - Title = 1078164; // Becoming One with the Shadows - Description = 1078168; // Practice hiding in the Ninja Dojo until you reach 50 Hiding skill.
------

Come closer. Don't be afraid. The shadows will not harm you. To be a successful Ninja, you must learn to become one with the shadows. The Ninja Dojo is the ideal place to learn the art of concealment. Practice hiding here.

Talk to me once you have achieved the rank of Apprentice Rogue (for Hiding), and I shall reward you. - RefusalMessage = 1078169; // If you wish to become one with the shadows, come back and talk to me. - InProgressMessage = 1078170; // You have not achieved the rank of Apprentice Rogue (for Hiding). Talk to me when you feel you have accomplished this. - CompletionMessage = 1078172; // Not bad at all. You have learned to control your fear of the dark and you are becoming one with the shadows. If you haven't already talked to Jun, I advise you do so. Jun can teach you how to stealth undetected. Hiding and Stealth are essential skills to master when becoming a Ninja.

As promised, I have a reward for you. Here are some smokebombs. As long as you are an Apprentice Ninja and have mana available you will be able to use them. They will allow you to hide while in the middle of combat. I hope these serve you well. - CompletionNotice = 1078171; // You have achieved the rank of Apprentice Rogue (for Hiding). Return to Chiyo in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Hiding, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078173, typeof( BagOfSmokeBombs ) ) ); // Bag of Smoke Bombs - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Chiyo" ), new Point3D( 3420, 2516, 21 ), Map.Trammel ); - } - } - - public class WalkingSilently : MLQuest - { - public WalkingSilently() - { - Activated = true; - OneTimeOnly = true; - Title = 1078174; // Walking Silently - Description = 1078178; // Head East out of town and go to Old Haven. While wearing normal clothes, practice Stealth there until you reach 50 Stealth skill.
------

You there. You're not very quiet in your movements. I can help you with that. Not only must you must learn to become one with the shadows, but also you must learn to quiet your movements. Old Haven is the ideal place to learn how to Stealth.

Head East out of town and go to Old Haven. While wearing normal clothes, practice Stealth there. Stealth becomes more difficult as you wear heavier pieces of armor, so for now, only wear clothes while practicing Stealth.

You can only Stealth once you are hidden. If you become visible, use your Hiding skill, and begin slowing walking.

Come back to me once you have achieved the rank of Apprentice Rogue (for Stealth), and I will reward you with something useful. - RefusalMessage = 1078179; // If you want to learn to quiet your movements, talk to me, and I will help you. - InProgressMessage = 1078180; // You have not achieved the rank of Apprentice Rogue (for Stealth). Come back to me when you feel you have accomplished this. - CompletionMessage = 1078182; // Good. You have learned to quiet your movements. If you haven't already talked to Chiyo, I advise you do so. Chiyo can teach you how to become one with the shadows. Hiding and Stealth are essential skills to master when becoming a Ninja.

Here is your reward. This leather Ninja jacket is called "Twilight Jacket". It will offer greater protection to you. I hope this serve you well. - CompletionNotice = 1078181; // You have achieved the rank of Apprentice Rogue (for Stealth). Return to Jun in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Stealth, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078183, typeof( TwilightJacket ) ) ); // Twilight Jacket - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Jun" ), new Point3D( 3422, 2516, 21 ), Map.Trammel ); - } - } - - public class EyesOfARanger : MLQuest - { - public EyesOfARanger() - { - Activated = true; - OneTimeOnly = true; - Title = 1078211; // Eyes of a Ranger - Description = 1078217; // Track animals, monsters, and people on Haven Island until you have raised your Tracking skill to 50.
------

Hello friend. I am Walker, Grandmaster Ranger. An adventurer needs to keep alive in the wilderness. Being able to track those around you is essential to surviving in dangerous places. Certain Ninja abilities are more potent when the Ninja possesses Tracking knowledge. If you want to be a Ninja, or if you simply want to get a leg up on the creatures that habit these parts, I advise you learn how to track them.

You can track any animals, monsters, or people on Haven Island. Clear your mind, focus, and note any tracks in the ground or sounds in the air that can help you find your mark. You can do it, friend. I have faith in you.

Come back to me once you have achieved the rank of Apprentice Ranger (for Tracking), and I will give you something that may help you in your travels. Take care, friend. - RefusalMessage = 1078218; // Farewell, friend. Be careful out here. If you change your mind and want to learn Tracking, come back and talk to me. - InProgressMessage = 1078219; // So far so good, kid. You are still alive, and you are getting the hang of Tracking. There are many more animals, monsters, and people to track. Come back to me once you have tracked them. - CompletionMessage = 1078221; // I knew you could do it! You have become a fine Ranger. Just keep practicing, and one day you will become a Grandmaster Ranger. Just like me.

I have a little something for you that will hopefully aid you in your journeys. These leggings offer some resistances that will hopefully protect you from harm. I hope these serve you well. Farewell, friend. - CompletionNotice = 1078220; // You have achieved the rank of Apprentice Ranger (for Tracking). Return to Walker in New Haven to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Tracking, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078222, typeof( WalkersLeggings ) ) ); // Walker's Leggings - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Walker" ), new Point3D( 3429, 2518, 19 ), Map.Trammel ); - } - } - - public class TheWayOfTheSamurai : MLQuest - { - public TheWayOfTheSamurai() - { - Activated = true; - OneTimeOnly = true; - Title = 1078007; // The Way of the Samurai - Description = 1078010; // Head East out of town and go to Old Haven. use the Confidence defensive stance and attempt to honorably execute monsters there until you have raised your Bushido skill to 50.
------

Greetings. I see you wish to learn the Way of the Samurai. Wielding a blade is easy. Anyone can grasp a sword's hilt. Learning how to fight properly and skillfully is to become an Armsman. Learning how to master weapons, and even more importantly when not to use them, is the Way of the Warrior. The Way of the Samurai. The Code of the Bushido. That is why you are here.

Adventure East to Old Haven. Use the Confidence defensive stance and attempt to honorably execute the undead that inhabit there. You will need a book of Bushido to perform these abilities. If you do not possess a book of Bushido, you can purchase one from me.

If you fail to honorably execute the undead, your defenses will be greatly weakened: Resistances will suffer and Resisting Spells will suffer. A successful parry instantly ends the weakness. If you succeed, however, you will be infused with strength and healing. Your swing speed will also be boosted for a short duration. With practice, you will learn how to master your Bushido abilities.

Return to me once you feel that you have become an Apprentice Samurai. - RefusalMessage = 1078011; // Good journey to you. Return to me if you wish to live the life of a Samurai. - InProgressMessage = 1078012; // You are not ready to become an Apprentice Samurai. There are still more undead to lay to rest. Return to me once you have done so. - CompletionMessage = 1078014; // You have proven yourself young one. You will continue to improve as your skills are honed with age. You are an honorable warrior, worthy of the rank of Apprentice Samurai. Please accept this no-dachi as a gift. It is called "The Dragon's Tail". Upon a successful strike in combat, there is a chance this mighty weapon will replenish your stamina equal to the damage of your attack. I hope "The Dragon's Tail" serves you well. You have earned it. Farewell for now. - CompletionNotice = 1078013; // You have achieved the rank of Apprentice Samurai. Return to Hamato in New Haven to report your progress. - - Objectives.Add( new GainSkillObjective( SkillName.Bushido, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078015, typeof( TheDragonsTail ) ) ); // The Dragon's Tail - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Hamato" ), new Point3D( 3493, 2414, 55 ), Map.Trammel ); - } - } - - public class TheAllureOfDarkMagic : MLQuest - { - public TheAllureOfDarkMagic() - { - Activated = true; - OneTimeOnly = true; - Title = 1078036; // The Allure of Dark Magic - Description = 1078039; // Head East out of town and go to Old Haven. Cast Evil Omen and Pain Spike against monsters there until you have raised your Necromancy skill to 50.
------

Welcome! I see you are allured by the dark magic of Necromancy. First, you must prove yourself worthy of such knowledge. Undead currently occupy the town of Old Haven. Practice your harmful Necromancy spells on them such as Evil Omen and Pain Spike.

Make sure you have plenty of reagents before embarking on your journey. Reagents are required to cast Necromancy spells. You can purchase extra reagents from me, or you can find reagents growing in the nearby wooded areas. You can see which reagents are required for each spell by looking in your spellbook.

Come back to me once you feel that you are worthy of the rank of Apprentice Necromancer and I will reward you with the knowledge you desire. - RefusalMessage = 1078040; // You are weak after all. Come back to me when you are ready to practice Necromancy. - InProgressMessage = 1078041; // You have not achieved the rank of Apprentice Necromancer. Come back to me once you feel that you are worthy of the rank of Apprentice Necromancer and I will reward you with the knowledge you desire. - CompletionMessage = 1078043; // You have done well, my young apprentice. Behold! I now present to you the knowledge you desire. This spellbook contains all the Necromancer spells. The power is intoxicating, isn't it? - CompletionNotice = 1078042; // You have achieved the rank of Apprentice Necromancer. Return to Mulcivikh in New Haven to receive the knowledge you desire. - - Objectives.Add( new GainSkillObjective( SkillName.Necromancy, 500, true, true ) ); - - Rewards.Add( new InternalReward() ); - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Mulcivikh" ), new Point3D( 3548, 2456, 15 ), Map.Trammel ); - } - - private class InternalReward : ItemReward - { - public InternalReward() - : base( 1078052, typeof( NecromancerSpellbook ) ) // Complete Necromancer Spellbook - { - } - - public override Item CreateItem() - { - Item item = base.CreateItem(); - - if ( item is Spellbook book ) - book.Content = ( 1ul << book.BookCount ) - 1; - - return item; - } - } - } - - public class ChannelingTheSupernatural : MLQuest - { - public ChannelingTheSupernatural() - { - Activated = true; - OneTimeOnly = true; - Title = 1078044; // Channeling the Supernatural - Description = 1078047; // Head East out of town and go to Old Haven. Use Spirit Speak and channel energy from either yourself or nearby corpses there. You can also cast Necromancy spells as well to raise Spirit Speak. Do these activities until you have raised your Spirit Speak skill to 50.
------

How do you do? Channeling the supernatural through Spirit Speak allows you heal your wounds. Such channeling expends your mana, so be mindful of this. Spirit Speak enhances the potency of your Necromancy spells. The channeling powers of a Medium are quite useful when practicing the dark magic of Necromancy.

It is best to practice Spirit Speak where there are a lot of corpses. Head East out of town and go to Old Haven. Undead currently reside there. Use Spirit Speak and channel energy from either yourself or nearby corpses. You can also cast Necromancy spells as well to raise Spirit Speak.

Come back to me once you feel that you are worthy of the rank of Apprentice Medium and I will reward you with something useful. - RefusalMessage = 1078048; // Channeling the supernatural isn't for everyone. It is a dark art. See me if you ever wish to pursue the life of a Medium. - InProgressMessage = 1078049; // Back so soon? You have not achieved the rank of Apprentice Medium. Come back to me once you feel that you are worthy of the rank of Apprentice Medium and I will reward you with something useful. - CompletionMessage = 1078051; // Well done! Channeling the supernatural is taxing, indeed. As promised, I will reward you with this bag of Necromancer reagents. You will need these if you wish to also pursue the dark magic of Necromancy. Good journey to you. - CompletionNotice = 1078050; // You have achieved the rank of Apprentice Medium. Return to Morganna in New Haven to receive your reward. - - Objectives.Add( new GainSkillObjective( SkillName.SpiritSpeak, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1078053, typeof( BagOfNecromancerReagents ) ) ); // Bag of Necromancer Reagents - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Morganna" ), new Point3D( 3547, 2463, 15 ), Map.Trammel ); - } - } - - public class TheDeluciansLostMine : MLQuest - { - public TheDeluciansLostMine() - { - Activated = true; - OneTimeOnly = true; - Title = 1077750; // The Delucian’s Lost Mine - Description = 1077753; // Find Jacob's Lost Mine and mine iron ore there, using a pickaxe or shovel. Bring it back to Jacob's forge and smelt the ore into ingots, until you have raised your Mining skill to 50. You may find a packhorse useful for hauling the ore around. The animal trainer in New Haven has packhorses for sale.
-----

Howdy! Welcome to my camp. It's not much, I know, but it's all I'll be needin' up here. I don't need them fancy things those townspeople have down there in New Haven. Nope, not one bit. Just me, Bessie, my pick and a thick vein 'o valorite.

Anyhows, I'm guessin' that you're up here to ask me about minin', aren't ya? Well, don't be expectin' me to tell you where the valorite's at, cause I ain't gonna tell the King of Britannia, much less the likes of you. But I will show ya how to mine and smelt iron, cause there certainly is a 'nough of up in these hills.

*Jacob looks around, with a perplexed look on his face*

Problem is, I can't remember where my iron mine's at, so you'll have to find it yourself. Once you're there, have at it with a pickaxe or shovel, then haul it back to camp and I'll show ya how to smelt it. Ya look a bit wimpy, so you might wanna go buy yourself a packhorse in town from the animal trainer to help you haul around all that ore.

When you're an Apprentice Miner, talk to me and I'll give ya a little somethin' I've got layin' around here... somewhere. - RefusalMessage = 1077754; // Couldn’t find my iron mine, could ya? Well, neither can I!

*Jacob laughs*

Oh, ya don’t wanna find it? Well, allrighty then, ya might as well head on back down to town then and stop cluttering up my camp. Come back and talk to me if you’re interested in learnin’ ‘bout minin’. - InProgressMessage = 1077755; // Where ya been off a gallivantin’ all day, pilgrim? You ain’t seen no hard work yet! Get yer arse back out there to my mine and dig up some more iron. Don’t forget to take a pickaxe or shovel, and if you’re so inclined, a packhorse too. - CompletionMessage = 1077757; // Dang gun it! If that don't beat all! Ya went and did it, didn’t ya? What we got ourselves here is a mighty fine brand spankin’ new Apprentice Miner!

I can see ya put some meat on them bones too while you were at it!

Here’s that little somethin’ I told ya I had for ya. It’s a pickaxe with some high falutin’ magic inside that’ll help you find the good stuff when you’re off minin’. It wears out fast, though, so you can only use it a few times a day.

Welp, I’ve got some smeltin’ to do, so off with ya. Good luck, pilgrim! - CompletionNotice = 1077756; // You have achieved the rank of Apprentice Miner. Return to Jacob Waltz in at his camp in the hills above New Haven as soon as you can to claim your reward. - - Objectives.Add( new GainSkillObjective( SkillName.Mining, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077758, typeof( JacobsPickaxe ) ) ); // Jacob's Pickaxe - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "JacobWaltz" ), new Point3D( 3504, 2741, 0 ), Map.Trammel ); - } - } - - public class ItsHammerTime : MLQuest - { - public ItsHammerTime() - { - Activated = true; - OneTimeOnly = true; - Title = 1077732; // It’s Hammer Time! - Description = 1077735; // Create new daggers and maces using the forge and anvil in George's shop. Try making daggers up to 45 skill, the switch to making maces until 50 skill.
-----

Hail, and welcome to my humble shop. I'm George Hephaestus, New Haven's blacksmith. I assume that you're here to ask me to train you to be an Apprentice Blacksmith. I certainly can do that, but you're going to have to supply your own ingots.

You can always buy them at the market, but I highly suggest that you mine your own. That way, any items you sell will be pure profit!

So, once you have a supply of ingots, use my forge and anvil here to create items. You'll also need a supply of the proper tools; you can use a smith's hammer, a sledgehammer or tongs. You can either make them yourself if you have the tinkering skill, or buy them from a tinker at the market.

Since I'll be around to give you advice, you'll learn faster here than anywhere else. Start off making daggers until you reach 45 blacksmithing skill, then switch to maces until you've achieved 50. Once you've done that, come talk to me and I'll give you something for your hard work. - RefusalMessage = 1077736; // You're not interested in learning to be a smith, eh? I thought for sure that's why you were here. Oh well, if you change your mind, you can always come back and talk to me. - InProgressMessage = 1077737; // You’re doing well, but you’re not quite there yet. Remember that the quickest way to learn is to make daggers up until 45 skill, and then switch to maces. Also, don’t forget that using my forge and anvil will help you learn faster. - CompletionMessage = 1077739; // I've been watching you get better and better as you've been smithing, and I have to say, you're a natural! It's a long road to being a Grandmaster Blacksmith, but I have no doubt that if you put your mind to it you'll get there someday. Let me give you one final piece of advice. If you're smithing just to practice and improve your skill, make items that are moderately difficult (60-80% success chance), and try to stick to ones that use less ingots.

Now that you're an Apprentice Blacksmith, I have something for you. While you were busy practicing, I was crafting this hammer for you. It's finely balanced, and has a bit of magic imbued within that will help you craft better items. However, that magic needs to restore itself over time, so you can only use it so many times per day. I hope you find it useful! - CompletionNotice = 1077738; // You have achieved the rank of Apprentice Blacksmith. Return to George Hephaestus in New Haven to see what kind of reward he has waiting for you. - - Objectives.Add( new GainSkillObjective( SkillName.Blacksmith, 500, true, true ) ); - - Rewards.Add( new ItemReward( 1077740, typeof( HammerOfHephaestus ) ) ); // Hammer of Hephaestus - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "GeorgeHephaestus" ), new Point3D( 3471, 2542, 36 ), Map.Trammel ); - } - } - - #endregion - - #region Mobiles - - public class Aelorn : KeeperOfChivalry - { - public override string DefaultName => "Aelorn"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078133 ); // Hail, friend. Want to live the life of a paladin? - } - - [Constructible] - public Aelorn() - { - Title = "the Chivalry Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x47D; - FacialHairItemID = 0x204D; - FacialHairHue = 0x47D; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - SetSkill( SkillName.Chivalry, 120.0 ); - } - - public override void InitOutfit() - { - AddItem( new Backpack() ); - AddItem( new VikingSword() ); - AddItem( new PlateChest() ); - AddItem( new PlateLegs() ); - AddItem( new PlateGloves() ); - AddItem( new PlateArms() ); - AddItem( new PlateGorget() ); - AddItem( new OrderShield() ); - } - - public Aelorn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Dimethro : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Dimethro"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078128 ); // You there! Wanna master hand to hand defense? Of course you do! - } - - [Constructible] - public Dimethro() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Wrestling Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203D; - HairHue = 0x455; - FacialHairItemID = 0x204D; - FacialHairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Inscribe, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Sandals( 0x455 ) ); - AddItem( new BodySash( 0x455 ) ); - AddItem( new LongPants( 0x455 ) ); - } - - public Dimethro( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Churchill : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Churchill"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078141 ); // Don't listen to Jockles. Real warriors wield mace weapons! - } - - [Constructible] - public Churchill() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Mace Fighting Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Macing, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new OrderShield() ); - AddItem( new WarMace() ); - - Item item; - - item = new PlateLegs(); - item.Hue = 0x966; - AddItem( item ); - - item = new PlateGloves(); - item.Hue = 0x966; - AddItem( item ); - - item = new PlateGorget(); - item.Hue = 0x966; - AddItem( item ); - - item = new PlateChest(); - item.Hue = 0x966; - AddItem( item ); - - item = new PlateArms(); - item.Hue = 0x966; - AddItem( item ); - } - - public Churchill( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Robyn : Bowyer - { - public override string DefaultName => "Robyn"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078202 ); // Archery requires a steady aim and dexterous fingers. - } - - [Constructible] - public Robyn() - { - Title = "the Archery Instructor"; - BodyValue = 0x191; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x47D; - Female = true; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Fletching, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Archery, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - } - - public override void InitOutfit() - { - AddItem( new Backpack() ); - AddItem( new Boots( 0x592 ) ); - AddItem( new Cloak( 0x592 ) ); - AddItem( new Bandana( 0x592 ) ); - AddItem( new CompositeBow() ); - - Item item; - - item = new StuddedLegs(); - item.Hue = 0x592; - AddItem( item ); - - item = new StuddedGloves(); - item.Hue = 0x592; - AddItem( item ); - - item = new StuddedGorget(); - item.Hue = 0x592; - AddItem( item ); - - item = new StuddedChest(); - item.Hue = 0x592; - AddItem( item ); - - item = new StuddedArms(); - item.Hue = 0x592; - AddItem( item ); - } - - public Robyn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Recaro : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Recaro"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078187 ); // The art of fencing requires a dexterous hand, a quick wit and fleet feet. - } - - [Constructible] - public Recaro() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Fencer Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x455; - FacialHairItemID = 0x204D; - FacialHairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Fencing, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Shoes( 0x455 ) ); - AddItem( new WarFork() ); - - Item item; - - item = new StuddedLegs(); - item.Hue = 0x455; - AddItem( item ); - - item = new StuddedGloves(); - item.Hue = 0x455; - AddItem( item ); - - item = new StuddedGorget(); - item.Hue = 0x455; - AddItem( item ); - - item = new StuddedChest(); - item.Hue = 0x455; - AddItem( item ); - - item = new StuddedArms(); - item.Hue = 0x455; - AddItem( item ); - } - - public Recaro( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AldenArmstrong : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Alden Armstrong"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078136 ); // There is an art to slaying your enemies swiftly. It's called tactics, and I can teach it to you. - } - - [Constructible] - public AldenArmstrong() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Tactics Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203B; - HairHue = 0x44E; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Shoes() ); - AddItem( new StuddedLegs() ); - AddItem( new StuddedGloves() ); - AddItem( new StuddedGorget() ); - AddItem( new StuddedChest() ); - AddItem( new StuddedArms() ); - AddItem( new Katana() ); - } - - public AldenArmstrong( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Jockles : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Jockles"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078135 ); // Talk to me to learn the way of the blade. - } - - [Constructible] - public Jockles() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Swordsmanship Instructor"; - BodyValue = 0x190; - Hue = 0x83FA; - HairItemID = 0x203C; - HairHue = 0x8A7; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Broadsword() ); - AddItem( new PlateChest() ); - AddItem( new PlateLegs() ); - AddItem( new PlateGloves() ); - AddItem( new PlateArms() ); - AddItem( new PlateGorget() ); - AddItem( new OrderShield() ); - } - - public Jockles( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TylAriadne : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Tyl Ariadne"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078140 ); // Want to learn how to parry blows? - } - - [Constructible] - public TylAriadne() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Parrying Instructor"; - BodyValue = 0x190; - Hue = 0x8374; - HairItemID = 0; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new ElvenBoots( 0x96D ) ); - - Item item; - - item = new StuddedLegs(); - item.Hue = 0x96D; - AddItem( item ); - - item = new StuddedGloves(); - item.Hue = 0x96D; - AddItem( item ); - - item = new StuddedGorget(); - item.Hue = 0x96D; - AddItem( item ); - - item = new StuddedChest(); - item.Hue = 0x96D; - AddItem( item ); - - item = new StuddedArms(); - item.Hue = 0x96D; - AddItem( item ); - - item = new DiamondMace(); - item.Hue = 0x96D; - AddItem( item ); - } - - public TylAriadne( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Alefian : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Alefian"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078130 ); // A mage should learn how to resist spells. - } - - [Constructible] - public Alefian() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Resisting Spells Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203D; - HairHue = 0x457; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Inscribe, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Robe() ); - AddItem( new Sandals() ); - } - - public Alefian( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Gustar : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Gustar"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078126 ); // Meditation allows a mage to replenish mana quickly. I can teach you. - } - - [Constructible] - public Gustar() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Meditation Instructor"; - BodyValue = 0x190; - Hue = 0x83F5; - HairItemID = 0x203B; - HairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Inscribe, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new GustarShroud() ); - AddItem( new Sandals() ); - } - - public Gustar( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GustarShroud : BaseOuterTorso - { - public override string DefaultName => " "; - [Constructible] - public GustarShroud() : base( 0x2684 ) - { - Hue = 0x479; - } - - public GustarShroud( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // Version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Jillian : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Jillian"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078129 ); // I can teach you how to scribe magic scrolls. - } - - [Constructible] - public Jillian() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Inscription Instructor"; - BodyValue = 0x191; - Female = true; - Hue = 0x83EA; - HairItemID = 0x203D; - HairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Inscribe, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Robe( 0x479 ) ); - AddItem( new Sandals() ); - } - - public Jillian( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Kaelynna : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Kaelynna"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078125 ); // Want to unlock the secrets of magery? - } - - [Constructible] - public Kaelynna() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Magery Instructor"; - BodyValue = 0x191; - Female = true; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x47D; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Inscribe, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Robe( 0x592 ) ); - AddItem( new Sandals() ); - } - - public Kaelynna( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Mithneral : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Mithneral"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078127 ); // Want to maximize your spell damage? I have a scholarly task for you! - } - - [Constructible] - public Mithneral() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Evaluating Intelligence Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Inscribe, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Sandals() ); - - Item item; - - item = new GustarShroud(); - item.Hue = 0x51C; - AddItem( item ); - } - - public Mithneral( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AmeliaYoungstone : Tinker - { - public override string DefaultName => "Amelia Youngstone"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078123 ); // Tinkering is very useful for a blacksmith. You can make your own tools. - } - - [Constructible] - public AmeliaYoungstone() - { - Title = "the Tinkering Instructor"; - BodyValue = 0x191; - Female = true; - Hue = 0x83EA; - HairItemID = 0x203D; - HairHue = 0x46C; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.ArmsLore, 120.0 ); - SetSkill( SkillName.Blacksmith, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Tinkering, 120.0 ); - SetSkill( SkillName.Mining, 120.0 ); - } - - public override void InitOutfit() - { - AddItem( new Backpack() ); - AddItem( new Sandals() ); - AddItem( new Doublet() ); - AddItem( new ShortPants() ); - AddItem( new HalfApron( 0x8AB ) ); - } - - public AmeliaYoungstone( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AndreasVesalius : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Andreas Vesalius"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078138 ); // Learning of the body will allow you to excel in combat. - } - - [Constructible] - public AndreasVesalius() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Anatomy Instructor"; - BodyValue = 0x190; - Hue = 0x83EC; - HairItemID = 0x203C; - HairHue = 0x477; - FacialHairItemID = 0x203E; - FacialHairHue = 0x477; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Boots() ); - AddItem( new BlackStaff() ); - AddItem( new LongPants() ); - AddItem( new Tunic( 0x66D ) ); - } - - public AndreasVesalius( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Avicenna : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Avicenna"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078137 ); // A warrior needs to learn how to apply bandages to wounds. - } - - [Constructible] - public Avicenna() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Healing Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203B; - HairHue = 0x477; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Robe( 0x66D ) ); - AddItem( new Boots() ); - AddItem( new GnarledStaff() ); - } - - public Avicenna( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SarsmeaSmythe : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Sarsmea Smythe"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078139 ); // Know yourself, and you will become a true warrior. - } - - [Constructible] - public SarsmeaSmythe() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Focus Instructor"; - BodyValue = 0x191; - Female = true; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x456; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Focus, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new ThighBoots() ); - AddItem( new StuddedGorget() ); - AddItem( new LeatherLegs() ); - AddItem( new FemaleLeatherChest() ); - AddItem( new StuddedGloves() ); - AddItem( new LeatherNinjaBelt() ); - AddItem( new LightPlateJingasa() ); - } - - public SarsmeaSmythe( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Ryuichi : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; - - public override string DefaultName => "Ryuichi"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078155 ); // I can teach you Ninjitsu. The Art of Stealth. - } - - [Constructible] - public Ryuichi() - : base( "the Ninjitsu Instructor" ) - { - Hue = 0x8403; - - SetSkill( SkillName.Hiding, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Tracking, 120.0 ); - SetSkill( SkillName.Fencing, 120.0 ); - SetSkill( SkillName.Stealth, 120.0 ); - SetSkill( SkillName.Ninjitsu, 120.0 ); - } - - public override void InitSBInfo() - { - m_SBInfos.Add( new SBNinja() ); - } - - public override bool GetGender() - { - return false; - } - - public override void InitOutfit() - { - HairItemID = 0x203B; - HairHue = 0x455; - - AddItem( new SamuraiTabi() ); - AddItem( new LeatherNinjaPants() ); - AddItem( new LeatherNinjaMitts() ); - AddItem( new LeatherNinjaHood() ); - AddItem( new LeatherNinjaJacket() ); - AddItem( new LeatherNinjaBelt() ); - - PackGold( 100, 200 ); - } - - public Ryuichi( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Chiyo : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Chiyo"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078165 ); // To be undetected means you cannot be harmed. - } - - [Constructible] - public Chiyo() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Hiding Instructor"; - BodyValue = 0xF7; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Hiding, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Tracking, 120.0 ); - SetSkill( SkillName.Fencing, 120.0 ); - SetSkill( SkillName.Stealth, 120.0 ); - SetSkill( SkillName.Ninjitsu, 120.0 ); - } - - public Chiyo( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Jun : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Jun"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078175 ); // Walk Silently. Remain unseen. I can teach you. - } - - [Constructible] - public Jun() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Stealth Instructor"; - BodyValue = 0x190; - Hue = 0x8403; - HairItemID = 0x203B; - HairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Hiding, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Tracking, 120.0 ); - SetSkill( SkillName.Fencing, 120.0 ); - SetSkill( SkillName.Stealth, 120.0 ); - SetSkill( SkillName.Ninjitsu, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new SamuraiTabi() ); - AddItem( new LeatherNinjaPants() ); - AddItem( new LeatherNinjaMitts() ); - AddItem( new LeatherNinjaHood() ); - AddItem( new LeatherNinjaJacket() ); - AddItem( new LeatherNinjaBelt() ); - } - - public Jun( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Walker : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Walker"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1078213, // I don't sleep. I wait. - 1078212, // There is no theory of evolution. Just a list of creatures I allow to live. - 1078214 // I can lead a horse to water and make it drink. - ) ); - } - - [Constructible] - public Walker() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Tracking Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203B; - HairHue = 0x47D; - FacialHairItemID = 0x204B; - FacialHairHue = 0x47D; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Hiding, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Tracking, 120.0 ); - SetSkill( SkillName.Fencing, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Stealth, 120.0 ); - SetSkill( SkillName.Ninjitsu, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x455 ) ); - AddItem( new LongPants( 0x455 ) ); - AddItem( new FancyShirt( 0x47D ) ); - AddItem( new FloppyHat( 0x455 ) ); - } - - public Walker( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Hamato : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; - - public override string DefaultName => "Hamato"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078134 ); // Seek me to learn the way of the samurai. - } - - [Constructible] - public Hamato() - : base( "the Bushido Instructor" ) - { - Hue = 0x8403; - - SetSkill( SkillName.Anatomy, 120.0 ); - SetSkill( SkillName.Parry, 120.0 ); - SetSkill( SkillName.Healing, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Bushido, 120.0 ); - } - - public override void InitSBInfo() - { - m_SBInfos.Add( new SBSamurai() ); - } - - public override bool GetGender() - { - return false; - } - - public override void InitOutfit() - { - HairItemID = 0x203D; - HairHue = 0x497; - - AddItem( new Backpack() ); - AddItem( new NoDachi() ); - AddItem( new NinjaTabi() ); - AddItem( new PlateSuneate() ); - AddItem( new LightPlateJingasa() ); - AddItem( new LeatherDo() ); - AddItem( new LeatherHiroSode() ); - - PackGold( 100, 200 ); - } - - public Hamato( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Mulcivikh : Mage - { - public override string DefaultName => "Mulcivikh"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078131 ); // Allured by dark magic, aren't you? - } - - [Constructible] - public Mulcivikh() - { - Title = "the Necromancy Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203D; - HairHue = 0x457; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.SpiritSpeak, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.Necromancy, 120.0 ); - } - - public override void InitOutfit() - { - AddItem( new Backpack() ); - AddItem( new Sandals( 0x8FD ) ); - AddItem( new BoneHelm() ); - - Item item; - - item = new LeatherLegs(); - item.Hue = 0x2C3; - AddItem( item ); - - item = new LeatherGloves(); - item.Hue = 0x2C3; - AddItem( item ); - - item = new LeatherGorget(); - item.Hue = 0x2C3; - AddItem( item ); - - item = new LeatherChest(); - item.Hue = 0x2C3; - AddItem( item ); - - item = new LeatherArms(); - item.Hue = 0x2C3; - AddItem( item ); - } - - public Mulcivikh( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Morganna : Mage - { - public override string DefaultName => "Morganna"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078132 ); // Want to learn how to channel the supernatural? - } - - [Constructible] - public Morganna() - { - Title = "the Spirit Speak Instructor"; - BodyValue = 0x191; - Female = true; - Hue = 0x83EA; - HairItemID = 0x203C; - HairHue = 0x455; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.SpiritSpeak, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.Necromancy, 120.0 ); - } - - public override void InitOutfit() - { - AddItem( new Backpack() ); - AddItem( new Sandals() ); - AddItem( new Robe( 0x47D ) ); - AddItem( new SkullCap( 0x455 ) ); - } - - public Morganna( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class JacobWaltz : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Jacob Waltz"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078124 ); // You there! I can use some help mining these rocks! - } - - [Constructible] - public JacobWaltz() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Miner Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x2048; - HairHue = 0x44E; - FacialHairItemID = 0x204D; - FacialHairHue = 0x44E; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.ArmsLore, 120.0 ); - SetSkill( SkillName.Blacksmith, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Tinkering, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Mining, 120.0 ); - - AddItem( new Backpack() ); - AddItem( new Pickaxe() ); - AddItem( new Boots() ); - AddItem( new WideBrimHat( 0x966 ) ); - AddItem( new ShortPants( 0x370 ) ); - AddItem( new Shirt( 0x966 ) ); - AddItem( new HalfApron( 0x1BB ) ); - } - - public JacobWaltz( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GeorgeHephaestus : Blacksmith - { - public override string DefaultName => "George Hephaestus"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1078122 ); // Wanna learn how to make powerful weapons and armor? Talk to me. - } - - [Constructible] - public GeorgeHephaestus() - { - Title = "the Blacksmith Instructor"; - BodyValue = 0x190; - Hue = 0x83EA; - HairItemID = 0x203B; - HairHue = 0x47B; - - InitStats( 100, 100, 25 ); - - SetSkill( SkillName.ArmsLore, 120.0 ); - SetSkill( SkillName.Blacksmith, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Tinkering, 120.0 ); - SetSkill( SkillName.Swords, 120.0 ); - SetSkill( SkillName.Mining, 120.0 ); - - } - - public override void InitOutfit() - { - AddItem( new Backpack() ); - AddItem( new Boots( 0x973 ) ); - AddItem( new LongPants() ); - AddItem( new Bascinet() ); - AddItem( new FullApron( 0x8AB ) ); - - Item item; - - item = new SmithHammer(); - item.Hue = 0x8AB; - AddItem( item ); - } - - public GeorgeHephaestus( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #region Quests + + public class CleansingOldHaven : MLQuest + { + public CleansingOldHaven() + { + Activated = true; + OneTimeOnly = true; + Title = 1077719; // Cleansing Old Haven + Description = + 1077722; // Head East out of town to Old Haven. Consecrate your weapon, cast Divine Fury, and battle monsters there until you have raised your Chivalry skill to 50.
------

Hail, friend. The life of a Paladin is a life of much sacrifice, humility, bravery, and righteousness. If you wish to pursue such a life, I have an assignment for you. Adventure east to Old Haven, consecrate your weapon, and lay to rest the undead that inhabit there.

Each ability a Paladin wishes to invoke will require a certain amount of "tithing points" to use. A Paladin can earn these tithing points by donating gold at a shrine or holy place. You may tithe at this shrine.

Return to me once you feel that you are worthy of the rank of Apprentice Paladin. + RefusalMessage = 1077723; // Farewell to you my friend. Return to me if you wish to live the life of a Paladin. + InProgressMessage = + 1077724; // There are still more undead to lay to rest. You still have more to learn. Return to me once you have done so. + CompletionMessage = + 1077726; // Well done, friend. While I know you understand Chivalry is its own reward, I would like to reward you with something that will protect you in battle. It was passed down to me when I was a lad. Now, I am passing it on you. It is called the Bulwark Leggings. Thank you for your service. + CompletionNotice = + 1077725; // You have achieved the rank of Apprentice Paladin. Return to Aelorn in New Haven to report your progress. + + Objectives.Add(new GainSkillObjective(SkillName.Chivalry, 500, true, true)); + + Rewards.Add(new ItemReward(1077727, typeof(BulwarkLeggings))); // Bulwark Leggings + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Aelorn"), new Point3D(3527, 2516, 45), Map.Trammel); + } + } + + public class TheRudimentsOfSelfDefense : MLQuest + { + public TheRudimentsOfSelfDefense() + { + Activated = true; + OneTimeOnly = true; + Title = 1077609; // The Rudiments of Self Defense + Description = + 1077610; // Head East out of town and go to Old Haven. Battle monster there until you have raised your Wrestling skill to 50.Listen up! If you want to learn the rudiments of self-defense, you need toughening up, and there's no better way to toughen up than engaging in combat. Head East out of town to Old Haven and battle the undead there in hand to hand combat. Afraid of dying, you say? Well, you should be! Being an adventurer isn't a bed of posies, or roses, or however that saying goes. If you take a dirt nap, go to one of the nearby wandering healers and they'll get you back on your feet.Come back to me once you feel that you are worthy of the rank Apprentice Wrestler and i will reward you wit a prize. + RefusalMessage = + 1077611; // Ok, featherweight. come back to me if you want to learn the rudiments of self-defense. + InProgressMessage = + 1077630; // You have not achived the rank of Apprentice Wrestler. Come back to me once you feel that you are worthy of the rank Apprentice Wrestler and i will reward you with something useful. + CompletionMessage = + 1077613; // It's about time! Looks like you managed to make it through your self-defense training. As i promised, here's a little something for you. When worn, these Gloves of Safeguarding will increase your awareness and resistances to most elements except poison. Oh yeah, they also increase your natural health regeneration aswell. Pretty handy gloves, indeed. Oh, if you are wondering if your meditation will be hinered while wearing these gloves, it won't be. Mages can wear cloth and leather items without needing to worry about that. Now get out of here and make something of yourself. + CompletionNotice = + 1077612; // You have achieved the rank of Apprentice Wrestler. Return to Dimethro in New Haven to receive your prize. + + Objectives.Add(new GainSkillObjective(SkillName.Wrestling, 500, true, true)); + + Rewards.Add(new ItemReward(1077614, typeof(GlovesOfSafeguarding))); // Gloves Of Safeguarding + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Dimethro"), new Point3D(3528, 2520, 25), Map.Trammel); + } + } + + public class CrushingBonesAndTakingNames : MLQuest + { + public CrushingBonesAndTakingNames() + { + Activated = true; + OneTimeOnly = true; + Title = 1078070; // Crushing Bones and Taking Names + Description = + 1078065; // Head East out of town and go to Old Haven. While wielding your mace,battle monster there until you have raised your Mace Fighting skill to 50. I see you want to learn a real weapon skill and not that toothpick training Jockles hasto offer. Real warriors are called Armsmen, and they wield mace weapons. No doubt about it. Nothing is more satisfying than knocking the wind out of your enemies, smashing there armor, crushing their bones, and taking there names. Want to learn how to wield a mace? Well i have an assignment for you. Head East out of town and go to Old Haven. Undead have plagued the town, so there are plenty of bones for you to smash there. Come back to me after you have ahcived the rank of Apprentice Armsman, and i will reward you with a real weapon. + RefusalMessage = + 1078068; // I thought you wanted to be an Armsman and really make something of yourself. You have potential, kid, but if you want to play with toothpicks, run to Jockles and he will teach you how to clean your teeth with a sword. If you change your mind, come back to me, and i will show you how to wield a real weapon. + InProgressMessage = + 1078067; // Listen kid. There are a lot of undead in Old Haven, and you haven't smashed enough of them yet. So get back there and do some more cleansing. + CompletionMessage = + 1078069; // Now that's what I'm talking about! Well done! Don't you like crushing bones and taking names? As i promised, here is a war mace for you. It hits hard. It swings fast. It hits often. What more do you need? Now get out of here and crush some more enemies! + CompletionNotice = + 1078068; // You have achieved the rank of Apprentice Armsman. Return to Churchill in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Macing, 500, true, true)); + + Rewards.Add(new ItemReward(1078062, typeof(ChurchillsWarMace))); // Churchill's War Mace + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Churchill"), new Point3D(3531, 2531, 20), Map.Trammel); + } + } + + public class SwiftAsAnArrow : MLQuest + { + public SwiftAsAnArrow() + { + Activated = true; + OneTimeOnly = true; + Title = 1078201; // Swift as an Arrow + Description = + 1078205; // Head East out of town and go to Old Haven. While wielding your bow or crossbow, battle monster there until you have raised your Archery skill to 50. Well met, friend. Imagine yourself in a distant grove of trees, You raise your bow, take slow, careful aim, and with the twitch of a finger, you impale your prey with a deadly arrow. You look like you would make a excellent archer, but you will need practice. There is no better way to practice Archery than when you life is on the line. I have a challenge for you. Head East out of town and go to Old Haven. While wielding your bow or crossbow, battle the undead that reside there. Make sure you bring a healthy supply of arrows (or bolts if you prefer a crossbow). If you wish to purchase a bow, crossbow, arrows, or bolts, you can purchase them from me or the Archery shop in town. You can also make your own arrows with the Bowcraft/Fletching skill. You will need fletcher's tools, wood to turn into sharft's, and feathers to make arrows or bolts. Come back to me after you have achived the rank of Apprentice Archer, and i will reward you with a fine Archery weapon. + RefusalMessage = + 1078206; // I understand that Archery may not be for you. Feel free to visit me in the future if you change your mind. + InProgressMessage = 1078207; // You're doing great as an Archer! however, you need more practice. + CompletionMessage = + 1078209; // Congratulation! I want to reward you for your accomplishment. Take this composite bow. It is called " Heartseeker". With it, you will shoot with swiftness, precision, and power. I hope "Heartseeker" serves you well. + CompletionNotice = + 1078208; // You have achieved the rank of Apprentice Archer. Return to Robyn in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Archery, 500, true, true)); + + Rewards.Add(new ItemReward(1078210, typeof(Heartseeker))); // Heartseeker + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Robyn"), new Point3D(3535, 2531, 20), Map.Trammel); + } + } + + public class EnGuarde : MLQuest + { + public EnGuarde() + { + Activated = true; + OneTimeOnly = true; + Title = 1078186; // En Guarde! + Description = + 1078190; // Head East out of town to Old Haven. Battle monsters there until you have raised your Fencing skill to 50.
------

Well hello there, lad. Fighting with elegance and precision is far more enriching than slugging an enemy with a club or butchering an enemy with a sword. Learn the art of Fencing if you want to master combat and look good doing it!

The key to being a successful fencer is to be the complement and not the opposition to your opponent's strength. Watch for your opponent to become off balance. Then finish him off with finesse and flair.

There are some undead that need cleansing out in Old Haven towards the East. Head over there and slay them, but remember, do it with style!

Come back to me once you have achieved the rank of Apprentice Fencer, and I will reward you with a prize. + RefusalMessage = + 1078191; // I understand, lad. Being a hero isn't for everyone. Run along, then. Come back to me if you change your mind. + InProgressMessage = + 1078192; // You're doing well so far, but you're not quite ready yet. Head back to Old Haven, to the East, and kill some more undead. + CompletionMessage = + 1078194; // Excellent! You are beginning to appreciate the art of Fencing. I told you fighting with elegance and precision is more enriching than fighting like an ogre.

Since you have returned victorious, please take this war fork and use it well. The war fork is a finesse weapon, and this one is magical! I call it "Recaro's Riposte". With it, you will be able to parry and counterstrike with ease! Your enemies will bask in your greatness and glory! Good luck to you, lad, and keep practicing! + CompletionNotice = + 1078193; // You have achieved the rank of Apprentice Fencer. Return to Recaro in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Fencing, 500, true, true)); + + Rewards.Add(new ItemReward(1078195, typeof(RecarosRiposte))); // Recaro's Riposte + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Recaro"), new Point3D(3536, 2534, 20), Map.Trammel); + } + } + + public class TheArtOfWar : MLQuest + { + public TheArtOfWar() + { + Activated = true; + OneTimeOnly = true; + Title = 1077667; // The Art of War + Description = + 1077670; // Head East out of town to Old Haven. Battle monsters there until you have raised your Tactics skill to 50.
------

Knowing how to hold a weapon is only half of the battle. The other half is knowing how to use it against an opponent. It's one thing to kill a few bunnies now and then for fun, but a true warrior knows that the right moves to use against a lich will pretty much get your arse fried by a dragon.

I'll help teach you how to fight so that when you do come up against that dragon, maybe you won't have to walk out of there "OooOOooOOOooOO'ing" and looking for a healer.

There are some undead that need cleaning out in Old Haven towards the east. Why don't you head on over there and practice killing things?

When you feel like you've got the basics down, come back to me and I'll see if I can scrounge up an item to help you in your adventures later on. + RefusalMessage = + 1077671; // That's too bad. I really thought you had it in you. Well, I'm sure those undead will still be there later, so if you change your mind, feel free to stop on by and I'll help you the best I can. + InProgressMessage = + 1077672; // You're making some progress, that i can tell, but you're not quite good enough to last for very long out there by yourself. Head back to Old Haven, to the east, and kill some more undead. + CompletionMessage = + 1077674; // Hey, good job killing those undead! Hopefully someone will come along and clean up the mess. All that blood and guts tends to stink after a few days, and when the wind blows in from the east, it can raise a mighty stink!

Since you performed valiantly, please take these arms and use them well. I've seen a few too many harvests to be running around out there myself, so you might as well take it.

There is a lot left for you to learn, but I think you'll do fine. Remember to keep your elbows in and stick'em where it hurts the most! + CompletionNotice = + 1077673; // You have achieved the rank of Apprentice Warrior. Return to Alden Armstrong in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Tactics, 500, true, true)); + + Rewards.Add(new ItemReward(1077675, typeof(ArmsOfArmstrong))); // Arms of Armstrong + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "AldenArmstrong"), new Point3D(3535, 2538, 20), Map.Trammel); + } + } + + public class TheWayOfTheBlade : MLQuest + { + public TheWayOfTheBlade() + { + Activated = true; + OneTimeOnly = true; + Title = 1077658; // The way of The Blade + Description = + 1077661; // Head East out of town and go to Old Haven. While wielding your sword, battle monster there until you have raised your Swordsmanship skill to 50. *as you approach, you notice Jockles sizing you up with a skeptical look on his face* i can see you want to learn how to handle a blade. It's a lot harder than it looks, and you're going to have to put alot of time and effort if you ever want to be half as good as i am. I'll tell you what, kid, I'll help you get started, but you're going to have to do all the work if you want to learn something. East of here, outside of town, is Old Haven. It's been overrun with the nastiest of undead you've seen, which makes it a perfect place for you to turn that sloppy grin on your face into actual skill at handling a sword. Make sure you have a sturdy Swordsmanship weapon in good repair before you leave. 'tis no fun to travel all the way down there just to find out you forgot your blade! When you feel that you've cut down enough of those foul smelling things to learn how to handle a blade without hurting yourself, come back to me. If i think you've improved enough, I'll give you something suited for a real warrior. + RefusalMessage = + 1077662; // Ha! I had a feeling you were a lily-livered pansy. You might have potential, but you're scared by a few smelly undead, maybe it's better that you stay away from sharp objects. After all, you wouldn't want to hurt yourself swinging a sword. If you change your mind, I might give you another chance...maybe. + InProgressMessage = + 1077663; // *Jockles looks you up and down* Come on! You've got to work harder than that to get better. Now get out of here, go kill some more of those undead to the east in Old Haven, and don't come back till you've got real skill. + CompletionMessage = + 1077665; // Well, well, look at what we have here! You managed to do it after all. I have to say, I'm a little surprised that you came back in one piece, but since you did. I've got a little something for you. This is a fine blade that served me well in my younger days. Of course I've got much better swords at my disposal now, so I'll let you go ahead and use it under one condition. Take goodcare of it and treat it with the respect that a fine sword deserves. You're one of the quickers learners I've seen, but you still have a long way to go. Keep at it, and you'll get there someday. Happy hunting, kid. + CompletionNotice = + 1077664; // You have achieved the rank of Apprentice Swordsman. Return to Jockles in New Haven to see what kind of reward he has waiting for you. Hopefully he'll be a little nicer this time! + + Objectives.Add(new GainSkillObjective(SkillName.Swords, 500, true, true)); + + Rewards.Add(new ItemReward(1077666, typeof(JocklesQuicksword))); // Jockles' Quicksword + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Jockles"), new Point3D(3535, 2544, 20), Map.Trammel); + } + } + + public class ThouAndThineShield : MLQuest + { + public ThouAndThineShield() + { + Activated = true; + OneTimeOnly = true; + Title = 1077704; // Thou and Thine Shield + Description = + 1077707; // Head East out of town and go to Old Haven. Battle monsters, or simply let them hit you, while holding a shield or a weapon until you have raised your Parrying skill to 50. Oh, hello. You probably want me to teach you how to parry, don't you? Very Well. First, you'll need a weapon or a shield. Obviously shields work best of all, but you can parry with a 2-handed weapon. Or if you're feeling particularly brave, a 1-handed weapon will do in a pinch, I'd advise you to go to Old Haven, which you'll find to the East, and practice blocking incoming blows from the undead there. You'll learn quickly if you have more than one opponent attacking you at the same time to practice parrying lots of blows at once. That's the quickest way to master the art of parrying. If you manage to improve your skill enough, i have a shield that you might find useful. Come back to me when you've trained to an apprentice level. + RefusalMessage = + 1077708; // It's your choice, obviously, but I'd highly suggest that you learn to parry before adventuring out into the world. Come talk to me again when you get tired of being beat on by your opponents + InProgressMessage = + 1077709; // You're doing well, but in my opinion, I Don't think you really want to continue on without improving your parrying skill a bit more. Go to Old Haven, to the East, and practice blocking blows with a shield. + CompletionMessage = + 1077711; // Well done! You're much better at parrying blows than you were when we first met. You should be proud of your new ability and I bet your body is greatful to you aswell. *Tyl Ariadne laughs loudly at his ownn (mostly lame) joke* Oh yes, I did promise you a shield if I thought you were worthy of having it, so here you go. My father made these shields for the guards who served my father faithfully for many years, and I just happen to have obe that i can part with. You should find it useful as you explore the lands.Good luck, and may the Virtues be your guide. + CompletionNotice = + 1077710; // You have achieved the rank of Apprentice Warrior (for Parrying). Return to Tyl Ariadne in New Haven as soon as you can to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Parry, 500, true, true)); + + Rewards.Add(new ItemReward(1077694, typeof(EscutcheonDeAriadne))); // Escutcheon de Ariadne + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "TylAriadne"), new Point3D(3525, 2556, 20), Map.Trammel); + } + } + + public class DefyingTheArcane : MLQuest + { + public DefyingTheArcane() + { + Activated = true; + OneTimeOnly = true; + Title = 1077621; // Defying the Arcane + Description = + 1077623; // Head East out of town and go to Old Haven. Battle spell casting monsters there until you have raised your Resisting Spells skill to 50.
------

Hail and well met! To become a true master of the arcane art of Magery, I suggest learning the complementary skill known as Resisting Spells. While the name of this skill may suggest that it helps with resisting all spells, this is not the case. This skill helps you lessen the severity of spells that lower your stats or ones that last for a specific duration of time. It does not lessen damage from spells such as Energy Bolt or Flamestrike.

The Magery spells that can be resisted are Clumsy, Curse, Feeblemind, Mana Drain, Mana Vampire, Paralyze, Paralyze Field, Poison, Poison Field, and Weaken.

The Necromancy spells that can be resisted are Blood Oath, Corpse Skin, Mind Rot, and Pain Spike.

At higher ranks, the Resisting Spells skill also benefits you by adding a bonus to your minimum elemental resists. This bonus is only applied after all other resist modifications - such as from equipment - has been calculated. It's also not cumulative. It compares the number of your minimum resists to the calculated value of your modifications and uses the higher of the two values.

As you can see, Resisting Spells is a difficult skill to understand, and even more difficult to master. This is because in order to improve it, you will have to put yourself in harm's way - as in the path of one of the above spells.

Undead have plagued the town of Old Haven. We need your assistance in cleansing the town of this evil influence. Old Haven is located east of here. Battle the undead spell casters that inhabit there.

Comeback to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. + RefusalMessage = + 1077624; // The ability to resist powerful spells is a taxing experience. I understand your resistance in wanting to pursue it. If you wish to reconsider, feel free to return to me for Resisting Spells training. Good journey to you! + InProgressMessage = + 1077632; // You have not achieved the rank of Apprentice Mage. Come back to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. + CompletionMessage = + 1077626; // You have successfully begun your journey in becoming a true master of Magery. On behalf of the New Haven Mage Council I wish to present you with this bracelet. When worn, the Bracelet of Resilience will enhance your resistances vs. the elements, physical, and poison harm. The Bracelet of Resilience also magically enhances your ability fend off ranged and melee attacks. I hope it serves you well. + CompletionNotice = + 1077625; // You have achieved the rank of Apprentice Mage (for Resisting Spells). Return to Alefian in New Haven to receive your arcane prize. + + Objectives.Add(new GainSkillObjective(SkillName.MagicResist, 500, true, true)); + + Rewards.Add(new ItemReward(1077627, typeof(BraceletOfResilience))); // Bracelet of Resilience + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Alefian"), new Point3D(3473, 2497, 72), Map.Trammel); + } + } + + public class StoppingTheWorld : MLQuest + { + public StoppingTheWorld() + { + Activated = true; + OneTimeOnly = true; + Title = 1077597; // Stopping the World + Description = + 1077598; // Head East out of town and go to Old Haven. Use spells and abilities to deplete your mana and meditate there until you have raised your Meditation skill to 50. Well met! I can teach you how to 'Stop the World' around you and focus your inner energies on replenishing you mana. What is mana? Mana is the life force for everyone who practices arcane arts. When a practitioner of magic invokes a spell or scribes a scroll. It consumes mana. Having a abundant supply of mana is vital to excelling as a practitioner of the arcane. Those of us who study the art of Meditation are also known as stotics. The Meditation skill allows stoics to increase the rate at which they regenerate mana A Stoic needs to perform abilities or cast spells to deplete mana before he can meditate to replenish it. Meditation can occur passively or actively. Actively Meditation is more difficult to master but allows for the stoic to replenish mana at a significantly faster rate. Metal armor inerferes with the regenerative properties of Meditation. It is wise to wear leather or cloth protection when meditating. Head east out of town and go to Old Haven. Use spells and abilities to deplete your mana and actively meditate to replenish it. Come back once you feel you are at the worthy rank of Apprentice Stoic and i will reward you with a arcane prize. + RefusalMessage = 1077599; // Seek me out if you ever wish to study the art of Meditation. Good journey. + InProgressMessage = + 1077628; // You have not achieved the rank of Apprentice Stoic. Come back to me once you feel that you are worthy of the rank Apprentice Stoic and i will reward you with a arcane prize. + CompletionMessage = + 1077626; // You have successfully begun your journey in becoming a true master of Magery. On behalf of the New Haven Mage Council I wish to present you with this bracelet. When worn, the Bracelet of Resilience will enhance your resistances vs. the elements, physical, and poison harm. The Bracelet of Resilience also magically enhances your ability fend off ranged and melee attacks. I hope it serves you well. + CompletionNotice = + 1077600; // You have achieved the rank of Apprentice Stoic (for Meditation). Return to Gustar in New Haven to receive your arcane prize. + + Objectives.Add(new GainSkillObjective(SkillName.Meditation, 500, true, true)); + + Rewards.Add(new ItemReward(1077602, typeof(PhilosophersHat))); // Philosopher's Hat + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Gustar"), new Point3D(3474, 2492, 91), Map.Trammel); + } + } + + public class ScribingArcaneKnowledge : MLQuest + { + public ScribingArcaneKnowledge() + { + Activated = true; + OneTimeOnly = true; + Title = 1077615; // Scribing Arcane Knowledge + Description = + 1077616; // While here at the New Haven Magery Library, use a scribe's pen and scribe and 3rd and 4th circle Magery scrolls that you have in your spellbook. Remember, you will need blank scrolls as well. Do this until you have raised your Inscription skill to 50.
------

Greetings and welcome to the New Haven Magery Library! You wish to learn how to scribe spell scrolls? You have come to the right place! Inscribed in a steady hand and imbued with the power of reagents, a scroll can mean the difference between life and death in a perilous situation. Those knowledgeable in Inscription may transcribe spells to create useful and valuable magical scrolls.

Before you inscribe a spell, you must first be able to cast the spell without the aid of a scroll. This means that you need the appropriate level of proficiency as a mage, the required mana, and the required reagents. Second, you will need a blank scroll to write on and a scribe's pen. Then, you will need to decide which particular spell you wish to scribe. It may sound easy, but there is a bit more to it. As with the development of all skills, you need to practice Inscription of lower level spells before you can move onto the more difficult ones.

The most important aspect of Inscription is mana. Inscribing a scroll with a magic spell drains your mana. When inscribing 3rd circle or lower spells this will not be much of a problem for these spells consume a small amount of mana. However, when you are inscribing higher circle spells, you may see your mana drain rapidly. When this happens, pause or meditate before continuing.

I suggest you begin scribing any 3rd and 4th circle spells that you know. If you don't possess any, you can always barter with one of the local mage merchants or a fellow adventurer that is a seasoned Scribe.

Come back to me once you feel that you are worthy of the rank of Apprentice Scribe and I will reward you with an arcane prize. + RefusalMessage = + 1077617; // I understand. When you are ready, feel free to return to me for Inscription training. Thanks for stopping by! + InProgressMessage = + 1077631; // You have not achieved the rank of Apprentice Scribe. Come back to me once you feel that you are worthy of the rank Apprentice Scribe and i will reward you with a arcane prize. + CompletionMessage = + 1077619; // Scribing is a very fulfilling pursuit. I am pleased to see you embark on this journey. You sling a pen well! On behalf of the New Haven Mage Council I wish to present you with this spellbook. When equipped, the Hallowed Spellbook greatly enhances the potency of your offensive spells when used against Undead. Be mindful, though. While this book is equipped, when you invoke your powerful spells and abilities vs. Humanoids such as other humans, orcs, ettins, trolls, and the like, your offensive spells will diminish in effectiveness. I suggest unequipping the Hallowed Spellbook when battling Humanoids. I hope this spellbook serves you well. + CompletionNotice = + 1077618; // You have achieved the rank of Apprentice Scribe. Return to Jillian in New Haven to receive your arcane prize. + + Objectives.Add(new GainSkillObjective(SkillName.Inscribe, 500, true, true)); + + Rewards.Add(new ItemReward(1077620, typeof(HallowedSpellbook))); // Hallowed Spellbook + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Jillian"), new Point3D(3465, 2490, 71), Map.Trammel); + } + } + + public class TheMagesApprentice : MLQuest + { + public TheMagesApprentice() + { + Activated = true; + OneTimeOnly = true; + Title = 1077576; // The Mage's Apprentice + Description = + 1077577; // Head East out of town and go to Old Haven. Cast fireballs and lightning bolts against monsters there until you have raised your Magery skill to 50. Greetings. You seek to unlock the secrets of the arcane art of Magery. The New Haven Mage Council has an assignment for you. Undead have plagued the town of Old Haven. We need your assistance in cleansing the town of this evil influence. Old Haven is located east of here. I suggest using your offensive Magery spells such as Fireball and Lightning Bolt against the Undead that inhabit there. Make sure you have plenty of reagents before embarking on your journey. Reagents are required to cast Magery spells. You can purchase extra reagents at the nearby Reagent shop, or you can find reagents growing in the nearby wooded areas. You can see which reagents are required for each spell by looking in your spellbook. Come back to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. + RefusalMessage = + 1077578; // Very well, come back to me when you are ready to practice Magery. You have so much arcane potential. 'Tis a shame to see it go to waste. The New Haven Mage Council could really use your help. + InProgressMessage = + 1077579; // You have not achieved the rank of Apprentice Mage. Come back to me once you feel that you are worthy of the rank of Apprentice Mage and I will reward you with an arcane prize. + CompletionMessage = + 1077581; // Well done! On behalf of the New Haven Mage Council I wish to present you with this staff. Normally a mage must unequip weapons before spell casting. While wielding your new Ember Staff, however, you will be able to invoke your Magery spells. Even if you do not currently possess skill in Mace Fighting, the Ember Staff will allow you to fight as if you do. However, your Magery skill will be temporarily reduced while doing so. Finally, the Ember Staff occasionally smites a foe with a Fireball while wielding it in melee combat. I hope the Ember Staff serves you well. + CompletionNotice = + 1077580; // You have achieved the rank of Apprentice Mage. Return to Kaelynna in New Haven to receive your arcane prize. + + Objectives.Add(new GainSkillObjective(SkillName.Magery, 500, true, true)); + + Rewards.Add(new ItemReward(1077582, typeof(EmberStaff))); // Ember Staff + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Kaelynna"), new Point3D(3486, 2491, 52), Map.Trammel); + } + } + + public class ScholarlyTask : MLQuest + { + public ScholarlyTask() + { + Activated = true; + OneTimeOnly = true; + Title = 1077603; // A Scholarly Task + Description = + 1077604; // Head East out of town and go to Old Haven. Use Evaluating Intelligence on all creatures you see there. You can also cast Magery spells as well to raise Evaluating Intelligence. Do these activities until you have raised your Evaluating Intelligence skill to 50.
------

Hello. Truly knowing your opponent is essential for landing your offensive spells with precision. I can teach you how to enhance the effectiveness of your offensive spells, but first you must learn how to size up your opponents intellectually. I have a scholarly task for you. Head East out of town and go to Old Haven. Use Evaluating Intelligence on all creatures you see there. You can also cast Magery spells as well to raise Evaluating Intelligence.

Come back to me once you feel that you are worthy of the rank of Apprentice Scholar and I will reward you with an arcane prize. + RefusalMessage = 1077605; // Return to me if you reconsider and wish to become an Apprentice Scholar. + InProgressMessage = + 1077629; // You have not achieved the rank of Apprentice Scholar. Come back to me once you feel that you are worthy of the rank of Apprentice Scholar and I will reward you with an arcane prize. + CompletionMessage = + 1077607; // You have completed the task. Well done. On behalf of the New Haven Mage Council I wish to present you with this ring. When worn, the Ring of the Savant enhances your intellectual aptitude and increases your mana pool. Your spell casting abilities will take less time to invoke and recovering from such spell casting will be hastened. I hope the Ring of the Savant serves you well. + CompletionNotice = + 1077606; // You have achieved the rank of Apprentice Scholar. Return to Mithneral in New Haven to receive your arcane prize. + + Objectives.Add(new GainSkillObjective(SkillName.EvalInt, 500, true, true)); + + Rewards.Add(new ItemReward(1077608, typeof(RingOfTheSavant))); // Ring of the Savant + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Mithneral"), new Point3D(3485, 2491, 71), Map.Trammel); + } + } + + public class TheRightToolForTheJob : MLQuest + { + public TheRightToolForTheJob() + { + Activated = true; + OneTimeOnly = true; + Title = 1077741; // The Right Tool for the Job + Description = + 1077744; // Create new scissors and hammers while inside Amelia's workshop. Try making scissors up to 45 skill, the switch to making hammers until 50 skill.
-----

Hello! I guess you're here to learn something about Tinkering, eh? You've come to the right place, as Tinkering is what I've dedicated my life to.

You'll need two things to get started: a supply of ingots and the right tools for the job. You can either buy ingots from the market, or go mine them yourself. As for tools, you can try making your own set of Tinker's Tools, or if you'd prefer to buy them, I have some for sale.

Working here in my shop will let me give you pointers as you go, so you'll be able to learn faster than anywhere else. Start off making scissors until you reach 45 tinkering skill, then switch to hammers until you've achieved 50. Once you've done that, come talk to me and I'll give you something for your hard work. + RefusalMessage = + 1077745; // I’m disappointed that you aren’t interested in learning more about Tinkering. It’s really such a useful skill!

*Amelia smiles*

At least you know where to find me if you change your mind, since I rarely spend time outside of this shop. + InProgressMessage = + 1077746; // Nice going! You're not quite at Apprentice Tinkering yet, though, so you better get back to work. Remember that the quickest way to learn is to make scissors up until 45 skill, and then switch to hammers. Also, don't forget that working here in my shop will let me give you tips so you can learn faster. + CompletionMessage = + 1077748; // You've done it! Look at our brand new Apprentice Tinker! You've still got quite a lot to learn if you want to be a Grandmaster Tinker, but I believe you can do it! Just keep in mind that if you're tinkering just to practice and improve your skill, make items that are moderately difficult (60-80% success chance), and try to stick to ones that use less ingots.

Come here, my brand new Apprentice Tinker, I want to give you something special. I created this just for you, so I hope you like it. It's a set of Tinker's Tools that contains a bit of magic. These tools have more charges than any Tinker's Tools a Tinker can make. You can even use them to make a normal set of tools, so that way you won't ever find yourself stuck somewhere with no tools! + CompletionNotice = + 1077747; // You have achieved the rank of Apprentice Tinker. Talk to Amelia Youngstone in New Haven to see what kind of reward she has waiting for you. + + Objectives.Add(new GainSkillObjective(SkillName.Tinkering, 500, true, true)); + + Rewards.Add(new ItemReward(1077749, typeof(AmeliasToolbox))); // Amelia’s Toolbox + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "AmeliaYoungstone"), new Point3D(3459, 2529, 53), Map.Trammel); + } + } + + public class KnowThineEnemy : MLQuest + { + public KnowThineEnemy() + { + Activated = true; + OneTimeOnly = true; + Title = 1077685; // Know Thine Enemy + Description = + 1077688; // Head East out of town to Old Haven. Battle monsters there, or heal yourself and other players, until you have raised your Anatomy skill to 50.
------

Hail and well met. You must be here to improve your knowledge of Anatomy. Well, you've come to the right place because I can teach you what you need to know. At least all you'll need to know for now. Haha!

Knowing about how living things work inside can be a very useful skill. Not only can you learn where to strike an opponent to hurt him the most, but you can use what you learn to heal wounds better as well. Just walking around town, you can even tell if someone is strong or weak or if they happen to be particularly dexterous or not.

If you're interested in learning more, I'd advise you to head out to Old Haven, just to the east, and jump into the fray. You'll learn best by engaging in combat while keeping you and your fellow adventurers healed, or you can even try sizing up your opponents.

While you're gone, I'll dig up something you may find useful. + RefusalMessage = + 1077689; // It's your choice, but I wouldn't head out there without knowing what makes those things tick inside! If you change your mind, you can find me right here dissecting frogs, cats or even the occasional unlucky adventurer. + InProgressMessage = + 1077690; // I'm surprised to see you back so soon. You've still got a ways to go if you want to really understand the science of Anatomy. Head out to Old Haven and practice combat and healing yourself or other adventurers. + CompletionMessage = + 1077692; // By the Virtues, you've done it! Congratulations mate! You still have quite a ways to go if you want to perfect your knowledge of Anatomy, but I know you'll get there someday. Just keep at it.

In the meantime, here's a piece of armor that you might find useful. It's not fancy, but it'll serve you well if you choose to wear it.

Happy adventuring, and remember to keep your cranium separate from your clavicle! + CompletionNotice = + 1077691; // You have achieved the rank of Apprentice Healer (for Anatomy). Return to Andreas Vesalius in New Haven as soon as you can to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Anatomy, 500, true, true)); + + Rewards.Add(new ItemReward(1077693, typeof(TunicOfGuarding))); // Tunic of Guarding + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "AndreasVesalius"), new Point3D(3457, 2550, 35), Map.Trammel); + } + } + + public class BruisesBandagesAndBlood : MLQuest + { + public BruisesBandagesAndBlood() + { + Activated = true; + OneTimeOnly = true; + Title = 1077676; // Bruises, Bandages and Blood + Description = + 1077679; // Head East out of town and go to Old Haven. Heal yourself and other players until you have raised your Healing skill to 50.
------

Ah, welcome to my humble practice. I am Avicenna, New Haven's resident Healer. A lot of adventurers head out into the wild from here, so I keep rather busy when they come back bruised, bleeding, or worse.

I can teach you how to bandage a wound, sure, but it's not a job for the queasy! For some folks, the mere sight of blood is too much for them, but it's something you'll get used to over time. It is one thing to cut open a living thing, but it's quite another to sew it back up and save it from sure death. 'Tis noble work, healing.

Best way for you to practice fixing up wounds is to head east out to Old Haven and either practice binding up your own wounds, or practice on someone else. Surely they'll be grateful for the assistance.

Make sure to take enough bandages with you! You don't want to run out in the middle of a tough fight. + RefusalMessage = + 1077680; // No? Are you sure? Well, when you feel that you're ready to practice your healing, come back to me. I'll be right here, fixing up adventurers and curing the occasional cold! + InProgressMessage = + 1077681; // Hail! 'Tis good to see you again. Unfortunately, you're not quite ready to call yourself an Apprentice Healer quite yet. Head back out to Old Haven, due east from here, and bandage up some wounds. Yours or someone else's, it doesn't much matter. + CompletionMessage = + 1077683; // Hello there, friend. I see you've returned in one piece, and you're an Apprentice Healer to boot! You should be proud of your accomplishment, as not everyone has "the touch" when it comes to healing.

I can't stand to see such good work go unrewarded, so I have something I'd like you to have. It's not much, but it'll help you heal just a little faster, and maybe keep you alive.

Good luck out there, friend, and don't forget to help your fellow adventurer whenever possible! + CompletionNotice = + 1077682; // You have achieved the rank of Apprentice Healer. Return to Avicenna in New Haven as soon as you can to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Healing, 500, true, true)); + + Rewards.Add(new ItemReward(1077684, typeof(HealersTouch))); // Healer's Touch + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Avicenna"), new Point3D(3464, 2558, 35), Map.Trammel); + } + } + + public class TheInnerWarrior : MLQuest + { + public TheInnerWarrior() + { + Activated = true; + OneTimeOnly = true; + Title = 1077696; // The Inner Warrior + Description = + 1077699; // Head East out of town to Old Haven. Expend stamina and mana until you have raised your Focus skill to 50.
------

Well, hello there. Don't you look like quite the adventurer!

You want to learn more about Focus, do you? I can teach you something about that, but first you should know that not everyone can be disciplined enough to excel at it. Focus is the ability to achieve inner balance in both body and spirit, so that you recover from physical and mental exertion faster than you otherwise would.

If you want to practice Focus, the best place to do that is east of here, in Old Haven, where you'll find an undead infestation. Exert yourself physically by engaging in combat and moving quickly. For testing your mental balance, expend mana in whatever way you find most suitable to your abilities. Casting spells and using abilities work well for consuming your mana.

Go. Train hard, and you will find that your concentration will improve naturally. When you've improved your ability to focus yourself at an Apprentice level, come back to me and I shall give you something worthy of your new ability. + RefusalMessage = + 1077700; // I'm disappointed. You have a lot of inner potential, and it would pain me greatly to see you waste that. Oh well. If you change your mind, I'll be right here. + InProgressMessage = + 1077701; // Hello again. I see you've returned, but it seems that your Focus skill hasn't improved as much as it could have. Just head east, to Old Haven, and exert yourself physically and mentally as much as possible. To do this physically, engage in combat and move as quickly as you can. For exerting yourself mentally, expend mana in whatever way you find most suitable to your abilities. Casting spells and using abilities work well for consuming your mana.

Return to me when you have gained enough Focus skill to be considered an Apprentice Stoic. + CompletionMessage = + 1077703; // Look who it is! I knew you could do it if you just had the discipline to apply yourself. It feels good to recover from battle so quickly, doesn't it? Just wait until you become a Grandmaster, it's amazing!

Please take this gift, as you've more than earned it with your hard work. It will help you recover even faster during battle, and provides a bit of protection as well.

You have so much more potential, so don't stop trying to improve your Focus now! Safe travels! + CompletionNotice = + 1077702; // You have achieved the rank of Apprentice Stoic (for Focus). Return to Sarsmea Smythe in New Haven to see what kind of reward she has waiting for you. + + Objectives.Add(new GainSkillObjective(SkillName.Focus, 500, true, true)); + + Rewards.Add(new ItemReward(1077695, typeof(ClaspOfConcentration))); // Clasp of Concentration + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "SarsmeaSmythe"), new Point3D(3492, 2577, 15), Map.Trammel); + } + } + + public class TheArtOfStealth : MLQuest + { + public TheArtOfStealth() + { + Activated = true; + OneTimeOnly = true; + Title = 1078154; // The Art of Stealth + Description = + 1078158; // Head East out of town and go to Old Haven. While wielding your fencing weapon, battle monsters with focus attack and summon mirror images up to 40 Ninjitsu skill, and continue practicing focus attack on monsters until 50 Ninjitsu skill.
------

Welcome, young one. You seek to learn Ninjitsu. With it, and the book of Ninjitsu, a Ninja can evoke a number of special abilities including transforming into a variety of creatures that give unique bonuses, using stealth to attack unsuspecting opponents or just plain disappear into thin air! If you do not have a book of Ninjitsu, you can purchase one from me.

I have an assignment for you. Head East out of town and go to Old Haven. While wielding your fencing weapon, battle monsters with focus attack and summon mirror images up to Novice rank, and continue focusing your attacks for greater damage on monsters until you become an Apprentice Ninja. Each image will absorb one attack. The art of deception is a strong defense. Use it wisely.

Come back to me once you have achieved the rank of Apprentice Ninja, and I shall reward you with something useful. + RefusalMessage = 1078159; // Come back to me if you with to learn Ninjitsu in the future. + InProgressMessage = + 1078160; // You have not achieved the rank of Apprentice Ninja. Come back to me once you have done so. + CompletionMessage = + 1078162; // You have done well, young one. Please accept this kryss as a gift. It is called the "Silver Serpent Blade". With it, you will strike with precision and power. This should aid you in your journey as a Ninja. Farewell. + CompletionNotice = + 1078161; // You have achieved the rank of Apprentice Ninja. Return to Ryuichi in New Haven to see what kind of reward he has waiting for you. + + Objectives.Add(new GainSkillObjective(SkillName.Ninjitsu, 500, true, true)); + + Rewards.Add(new ItemReward(1078163, typeof(SilverSerpentBlade))); // Silver Serpent Blade + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Ryuichi"), new Point3D(3422, 2520, 21), Map.Trammel); + } + } + + public class BecomingOneWithTheShadows : MLQuest + { + public BecomingOneWithTheShadows() + { + Activated = true; + OneTimeOnly = true; + Title = 1078164; // Becoming One with the Shadows + Description = + 1078168; // Practice hiding in the Ninja Dojo until you reach 50 Hiding skill.
------

Come closer. Don't be afraid. The shadows will not harm you. To be a successful Ninja, you must learn to become one with the shadows. The Ninja Dojo is the ideal place to learn the art of concealment. Practice hiding here.

Talk to me once you have achieved the rank of Apprentice Rogue (for Hiding), and I shall reward you. + RefusalMessage = 1078169; // If you wish to become one with the shadows, come back and talk to me. + InProgressMessage = + 1078170; // You have not achieved the rank of Apprentice Rogue (for Hiding). Talk to me when you feel you have accomplished this. + CompletionMessage = + 1078172; // Not bad at all. You have learned to control your fear of the dark and you are becoming one with the shadows. If you haven't already talked to Jun, I advise you do so. Jun can teach you how to stealth undetected. Hiding and Stealth are essential skills to master when becoming a Ninja.

As promised, I have a reward for you. Here are some smokebombs. As long as you are an Apprentice Ninja and have mana available you will be able to use them. They will allow you to hide while in the middle of combat. I hope these serve you well. + CompletionNotice = + 1078171; // You have achieved the rank of Apprentice Rogue (for Hiding). Return to Chiyo in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Hiding, 500, true, true)); + + Rewards.Add(new ItemReward(1078173, typeof(BagOfSmokeBombs))); // Bag of Smoke Bombs + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Chiyo"), new Point3D(3420, 2516, 21), Map.Trammel); + } + } + + public class WalkingSilently : MLQuest + { + public WalkingSilently() + { + Activated = true; + OneTimeOnly = true; + Title = 1078174; // Walking Silently + Description = + 1078178; // Head East out of town and go to Old Haven. While wearing normal clothes, practice Stealth there until you reach 50 Stealth skill.
------

You there. You're not very quiet in your movements. I can help you with that. Not only must you must learn to become one with the shadows, but also you must learn to quiet your movements. Old Haven is the ideal place to learn how to Stealth.

Head East out of town and go to Old Haven. While wearing normal clothes, practice Stealth there. Stealth becomes more difficult as you wear heavier pieces of armor, so for now, only wear clothes while practicing Stealth.

You can only Stealth once you are hidden. If you become visible, use your Hiding skill, and begin slowing walking.

Come back to me once you have achieved the rank of Apprentice Rogue (for Stealth), and I will reward you with something useful. + RefusalMessage = 1078179; // If you want to learn to quiet your movements, talk to me, and I will help you. + InProgressMessage = + 1078180; // You have not achieved the rank of Apprentice Rogue (for Stealth). Come back to me when you feel you have accomplished this. + CompletionMessage = + 1078182; // Good. You have learned to quiet your movements. If you haven't already talked to Chiyo, I advise you do so. Chiyo can teach you how to become one with the shadows. Hiding and Stealth are essential skills to master when becoming a Ninja.

Here is your reward. This leather Ninja jacket is called "Twilight Jacket". It will offer greater protection to you. I hope this serve you well. + CompletionNotice = + 1078181; // You have achieved the rank of Apprentice Rogue (for Stealth). Return to Jun in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Stealth, 500, true, true)); + + Rewards.Add(new ItemReward(1078183, typeof(TwilightJacket))); // Twilight Jacket + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Jun"), new Point3D(3422, 2516, 21), Map.Trammel); + } + } + + public class EyesOfARanger : MLQuest + { + public EyesOfARanger() + { + Activated = true; + OneTimeOnly = true; + Title = 1078211; // Eyes of a Ranger + Description = + 1078217; // Track animals, monsters, and people on Haven Island until you have raised your Tracking skill to 50.
------

Hello friend. I am Walker, Grandmaster Ranger. An adventurer needs to keep alive in the wilderness. Being able to track those around you is essential to surviving in dangerous places. Certain Ninja abilities are more potent when the Ninja possesses Tracking knowledge. If you want to be a Ninja, or if you simply want to get a leg up on the creatures that habit these parts, I advise you learn how to track them.

You can track any animals, monsters, or people on Haven Island. Clear your mind, focus, and note any tracks in the ground or sounds in the air that can help you find your mark. You can do it, friend. I have faith in you.

Come back to me once you have achieved the rank of Apprentice Ranger (for Tracking), and I will give you something that may help you in your travels. Take care, friend. + RefusalMessage = + 1078218; // Farewell, friend. Be careful out here. If you change your mind and want to learn Tracking, come back and talk to me. + InProgressMessage = + 1078219; // So far so good, kid. You are still alive, and you are getting the hang of Tracking. There are many more animals, monsters, and people to track. Come back to me once you have tracked them. + CompletionMessage = + 1078221; // I knew you could do it! You have become a fine Ranger. Just keep practicing, and one day you will become a Grandmaster Ranger. Just like me.

I have a little something for you that will hopefully aid you in your journeys. These leggings offer some resistances that will hopefully protect you from harm. I hope these serve you well. Farewell, friend. + CompletionNotice = + 1078220; // You have achieved the rank of Apprentice Ranger (for Tracking). Return to Walker in New Haven to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Tracking, 500, true, true)); + + Rewards.Add(new ItemReward(1078222, typeof(WalkersLeggings))); // Walker's Leggings + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Walker"), new Point3D(3429, 2518, 19), Map.Trammel); + } + } + + public class TheWayOfTheSamurai : MLQuest + { + public TheWayOfTheSamurai() + { + Activated = true; + OneTimeOnly = true; + Title = 1078007; // The Way of the Samurai + Description = + 1078010; // Head East out of town and go to Old Haven. use the Confidence defensive stance and attempt to honorably execute monsters there until you have raised your Bushido skill to 50.
------

Greetings. I see you wish to learn the Way of the Samurai. Wielding a blade is easy. Anyone can grasp a sword's hilt. Learning how to fight properly and skillfully is to become an Armsman. Learning how to master weapons, and even more importantly when not to use them, is the Way of the Warrior. The Way of the Samurai. The Code of the Bushido. That is why you are here.

Adventure East to Old Haven. Use the Confidence defensive stance and attempt to honorably execute the undead that inhabit there. You will need a book of Bushido to perform these abilities. If you do not possess a book of Bushido, you can purchase one from me.

If you fail to honorably execute the undead, your defenses will be greatly weakened: Resistances will suffer and Resisting Spells will suffer. A successful parry instantly ends the weakness. If you succeed, however, you will be infused with strength and healing. Your swing speed will also be boosted for a short duration. With practice, you will learn how to master your Bushido abilities.

Return to me once you feel that you have become an Apprentice Samurai. + RefusalMessage = 1078011; // Good journey to you. Return to me if you wish to live the life of a Samurai. + InProgressMessage = + 1078012; // You are not ready to become an Apprentice Samurai. There are still more undead to lay to rest. Return to me once you have done so. + CompletionMessage = + 1078014; // You have proven yourself young one. You will continue to improve as your skills are honed with age. You are an honorable warrior, worthy of the rank of Apprentice Samurai. Please accept this no-dachi as a gift. It is called "The Dragon's Tail". Upon a successful strike in combat, there is a chance this mighty weapon will replenish your stamina equal to the damage of your attack. I hope "The Dragon's Tail" serves you well. You have earned it. Farewell for now. + CompletionNotice = + 1078013; // You have achieved the rank of Apprentice Samurai. Return to Hamato in New Haven to report your progress. + + Objectives.Add(new GainSkillObjective(SkillName.Bushido, 500, true, true)); + + Rewards.Add(new ItemReward(1078015, typeof(TheDragonsTail))); // The Dragon's Tail + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Hamato"), new Point3D(3493, 2414, 55), Map.Trammel); + } + } + + public class TheAllureOfDarkMagic : MLQuest + { + public TheAllureOfDarkMagic() + { + Activated = true; + OneTimeOnly = true; + Title = 1078036; // The Allure of Dark Magic + Description = + 1078039; // Head East out of town and go to Old Haven. Cast Evil Omen and Pain Spike against monsters there until you have raised your Necromancy skill to 50.
------

Welcome! I see you are allured by the dark magic of Necromancy. First, you must prove yourself worthy of such knowledge. Undead currently occupy the town of Old Haven. Practice your harmful Necromancy spells on them such as Evil Omen and Pain Spike.

Make sure you have plenty of reagents before embarking on your journey. Reagents are required to cast Necromancy spells. You can purchase extra reagents from me, or you can find reagents growing in the nearby wooded areas. You can see which reagents are required for each spell by looking in your spellbook.

Come back to me once you feel that you are worthy of the rank of Apprentice Necromancer and I will reward you with the knowledge you desire. + RefusalMessage = 1078040; // You are weak after all. Come back to me when you are ready to practice Necromancy. + InProgressMessage = + 1078041; // You have not achieved the rank of Apprentice Necromancer. Come back to me once you feel that you are worthy of the rank of Apprentice Necromancer and I will reward you with the knowledge you desire. + CompletionMessage = + 1078043; // You have done well, my young apprentice. Behold! I now present to you the knowledge you desire. This spellbook contains all the Necromancer spells. The power is intoxicating, isn't it? + CompletionNotice = + 1078042; // You have achieved the rank of Apprentice Necromancer. Return to Mulcivikh in New Haven to receive the knowledge you desire. + + Objectives.Add(new GainSkillObjective(SkillName.Necromancy, 500, true, true)); + + Rewards.Add(new InternalReward()); + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Mulcivikh"), new Point3D(3548, 2456, 15), Map.Trammel); + } + + private class InternalReward : ItemReward + { + public InternalReward() + : base(1078052, typeof(NecromancerSpellbook)) // Complete Necromancer Spellbook + { + } + + public override Item CreateItem() + { + Item item = base.CreateItem(); + + if (item is Spellbook book) + book.Content = (1ul << book.BookCount) - 1; + + return item; + } + } + } + + public class ChannelingTheSupernatural : MLQuest + { + public ChannelingTheSupernatural() + { + Activated = true; + OneTimeOnly = true; + Title = 1078044; // Channeling the Supernatural + Description = + 1078047; // Head East out of town and go to Old Haven. Use Spirit Speak and channel energy from either yourself or nearby corpses there. You can also cast Necromancy spells as well to raise Spirit Speak. Do these activities until you have raised your Spirit Speak skill to 50.
------

How do you do? Channeling the supernatural through Spirit Speak allows you heal your wounds. Such channeling expends your mana, so be mindful of this. Spirit Speak enhances the potency of your Necromancy spells. The channeling powers of a Medium are quite useful when practicing the dark magic of Necromancy.

It is best to practice Spirit Speak where there are a lot of corpses. Head East out of town and go to Old Haven. Undead currently reside there. Use Spirit Speak and channel energy from either yourself or nearby corpses. You can also cast Necromancy spells as well to raise Spirit Speak.

Come back to me once you feel that you are worthy of the rank of Apprentice Medium and I will reward you with something useful. + RefusalMessage = + 1078048; // Channeling the supernatural isn't for everyone. It is a dark art. See me if you ever wish to pursue the life of a Medium. + InProgressMessage = + 1078049; // Back so soon? You have not achieved the rank of Apprentice Medium. Come back to me once you feel that you are worthy of the rank of Apprentice Medium and I will reward you with something useful. + CompletionMessage = + 1078051; // Well done! Channeling the supernatural is taxing, indeed. As promised, I will reward you with this bag of Necromancer reagents. You will need these if you wish to also pursue the dark magic of Necromancy. Good journey to you. + CompletionNotice = + 1078050; // You have achieved the rank of Apprentice Medium. Return to Morganna in New Haven to receive your reward. + + Objectives.Add(new GainSkillObjective(SkillName.SpiritSpeak, 500, true, true)); + + Rewards.Add(new ItemReward(1078053, typeof(BagOfNecromancerReagents))); // Bag of Necromancer Reagents + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Morganna"), new Point3D(3547, 2463, 15), Map.Trammel); + } + } + + public class TheDeluciansLostMine : MLQuest + { + public TheDeluciansLostMine() + { + Activated = true; + OneTimeOnly = true; + Title = 1077750; // The Delucian’s Lost Mine + Description = + 1077753; // Find Jacob's Lost Mine and mine iron ore there, using a pickaxe or shovel. Bring it back to Jacob's forge and smelt the ore into ingots, until you have raised your Mining skill to 50. You may find a packhorse useful for hauling the ore around. The animal trainer in New Haven has packhorses for sale.
-----

Howdy! Welcome to my camp. It's not much, I know, but it's all I'll be needin' up here. I don't need them fancy things those townspeople have down there in New Haven. Nope, not one bit. Just me, Bessie, my pick and a thick vein 'o valorite.

Anyhows, I'm guessin' that you're up here to ask me about minin', aren't ya? Well, don't be expectin' me to tell you where the valorite's at, cause I ain't gonna tell the King of Britannia, much less the likes of you. But I will show ya how to mine and smelt iron, cause there certainly is a 'nough of up in these hills.

*Jacob looks around, with a perplexed look on his face*

Problem is, I can't remember where my iron mine's at, so you'll have to find it yourself. Once you're there, have at it with a pickaxe or shovel, then haul it back to camp and I'll show ya how to smelt it. Ya look a bit wimpy, so you might wanna go buy yourself a packhorse in town from the animal trainer to help you haul around all that ore.

When you're an Apprentice Miner, talk to me and I'll give ya a little somethin' I've got layin' around here... somewhere. + RefusalMessage = + 1077754; // Couldn’t find my iron mine, could ya? Well, neither can I!

*Jacob laughs*

Oh, ya don’t wanna find it? Well, allrighty then, ya might as well head on back down to town then and stop cluttering up my camp. Come back and talk to me if you’re interested in learnin’ ‘bout minin’. + InProgressMessage = + 1077755; // Where ya been off a gallivantin’ all day, pilgrim? You ain’t seen no hard work yet! Get yer arse back out there to my mine and dig up some more iron. Don’t forget to take a pickaxe or shovel, and if you’re so inclined, a packhorse too. + CompletionMessage = + 1077757; // Dang gun it! If that don't beat all! Ya went and did it, didn’t ya? What we got ourselves here is a mighty fine brand spankin’ new Apprentice Miner!

I can see ya put some meat on them bones too while you were at it!

Here’s that little somethin’ I told ya I had for ya. It’s a pickaxe with some high falutin’ magic inside that’ll help you find the good stuff when you’re off minin’. It wears out fast, though, so you can only use it a few times a day.

Welp, I’ve got some smeltin’ to do, so off with ya. Good luck, pilgrim! + CompletionNotice = + 1077756; // You have achieved the rank of Apprentice Miner. Return to Jacob Waltz in at his camp in the hills above New Haven as soon as you can to claim your reward. + + Objectives.Add(new GainSkillObjective(SkillName.Mining, 500, true, true)); + + Rewards.Add(new ItemReward(1077758, typeof(JacobsPickaxe))); // Jacob's Pickaxe + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "JacobWaltz"), new Point3D(3504, 2741, 0), Map.Trammel); + } + } + + public class ItsHammerTime : MLQuest + { + public ItsHammerTime() + { + Activated = true; + OneTimeOnly = true; + Title = 1077732; // It’s Hammer Time! + Description = + 1077735; // Create new daggers and maces using the forge and anvil in George's shop. Try making daggers up to 45 skill, the switch to making maces until 50 skill.
-----

Hail, and welcome to my humble shop. I'm George Hephaestus, New Haven's blacksmith. I assume that you're here to ask me to train you to be an Apprentice Blacksmith. I certainly can do that, but you're going to have to supply your own ingots.

You can always buy them at the market, but I highly suggest that you mine your own. That way, any items you sell will be pure profit!

So, once you have a supply of ingots, use my forge and anvil here to create items. You'll also need a supply of the proper tools; you can use a smith's hammer, a sledgehammer or tongs. You can either make them yourself if you have the tinkering skill, or buy them from a tinker at the market.

Since I'll be around to give you advice, you'll learn faster here than anywhere else. Start off making daggers until you reach 45 blacksmithing skill, then switch to maces until you've achieved 50. Once you've done that, come talk to me and I'll give you something for your hard work. + RefusalMessage = + 1077736; // You're not interested in learning to be a smith, eh? I thought for sure that's why you were here. Oh well, if you change your mind, you can always come back and talk to me. + InProgressMessage = + 1077737; // You’re doing well, but you’re not quite there yet. Remember that the quickest way to learn is to make daggers up until 45 skill, and then switch to maces. Also, don’t forget that using my forge and anvil will help you learn faster. + CompletionMessage = + 1077739; // I've been watching you get better and better as you've been smithing, and I have to say, you're a natural! It's a long road to being a Grandmaster Blacksmith, but I have no doubt that if you put your mind to it you'll get there someday. Let me give you one final piece of advice. If you're smithing just to practice and improve your skill, make items that are moderately difficult (60-80% success chance), and try to stick to ones that use less ingots.

Now that you're an Apprentice Blacksmith, I have something for you. While you were busy practicing, I was crafting this hammer for you. It's finely balanced, and has a bit of magic imbued within that will help you craft better items. However, that magic needs to restore itself over time, so you can only use it so many times per day. I hope you find it useful! + CompletionNotice = + 1077738; // You have achieved the rank of Apprentice Blacksmith. Return to George Hephaestus in New Haven to see what kind of reward he has waiting for you. + + Objectives.Add(new GainSkillObjective(SkillName.Blacksmith, 500, true, true)); + + Rewards.Add(new ItemReward(1077740, typeof(HammerOfHephaestus))); // Hammer of Hephaestus + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "GeorgeHephaestus"), new Point3D(3471, 2542, 36), Map.Trammel); + } + } + + #endregion + + #region Mobiles + + public class Aelorn : KeeperOfChivalry + { + [Constructible] + public Aelorn() + { + Title = "the Chivalry Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x47D; + FacialHairItemID = 0x204D; + FacialHairHue = 0x47D; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.Focus, 120.0); + SetSkill(SkillName.Chivalry, 120.0); + } + + public Aelorn(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Aelorn"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078133); // Hail, friend. Want to live the life of a paladin? + } + + public override void InitOutfit() + { + AddItem(new Backpack()); + AddItem(new VikingSword()); + AddItem(new PlateChest()); + AddItem(new PlateLegs()); + AddItem(new PlateGloves()); + AddItem(new PlateArms()); + AddItem(new PlateGorget()); + AddItem(new OrderShield()); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Dimethro : BaseCreature + { + [Constructible] + public Dimethro() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Wrestling Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203D; + HairHue = 0x455; + FacialHairItemID = 0x204D; + FacialHairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Inscribe, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + AddItem(new Backpack()); + AddItem(new Sandals(0x455)); + AddItem(new BodySash(0x455)); + AddItem(new LongPants(0x455)); + } + + public Dimethro(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Dimethro"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078128); // You there! Wanna master hand to hand defense? Of course you do! + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Churchill : BaseCreature + { + [Constructible] + public Churchill() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Mace Fighting Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Macing, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new OrderShield()); + AddItem(new WarMace()); + + Item item; + + item = new PlateLegs(); + item.Hue = 0x966; + AddItem(item); + + item = new PlateGloves(); + item.Hue = 0x966; + AddItem(item); + + item = new PlateGorget(); + item.Hue = 0x966; + AddItem(item); + + item = new PlateChest(); + item.Hue = 0x966; + AddItem(item); + + item = new PlateArms(); + item.Hue = 0x966; + AddItem(item); + } + + public Churchill(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Churchill"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078141); // Don't listen to Jockles. Real warriors wield mace weapons! + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Robyn : Bowyer + { + [Constructible] + public Robyn() + { + Title = "the Archery Instructor"; + BodyValue = 0x191; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x47D; + Female = true; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Fletching, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Archery, 120.0); + SetSkill(SkillName.Focus, 120.0); + } + + public Robyn(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Robyn"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078202); // Archery requires a steady aim and dexterous fingers. + } + + public override void InitOutfit() + { + AddItem(new Backpack()); + AddItem(new Boots(0x592)); + AddItem(new Cloak(0x592)); + AddItem(new Bandana(0x592)); + AddItem(new CompositeBow()); + + Item item; + + item = new StuddedLegs(); + item.Hue = 0x592; + AddItem(item); + + item = new StuddedGloves(); + item.Hue = 0x592; + AddItem(item); + + item = new StuddedGorget(); + item.Hue = 0x592; + AddItem(item); + + item = new StuddedChest(); + item.Hue = 0x592; + AddItem(item); + + item = new StuddedArms(); + item.Hue = 0x592; + AddItem(item); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Recaro : BaseCreature + { + [Constructible] + public Recaro() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Fencer Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x455; + FacialHairItemID = 0x204D; + FacialHairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Fencing, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new Shoes(0x455)); + AddItem(new WarFork()); + + Item item; + + item = new StuddedLegs(); + item.Hue = 0x455; + AddItem(item); + + item = new StuddedGloves(); + item.Hue = 0x455; + AddItem(item); + + item = new StuddedGorget(); + item.Hue = 0x455; + AddItem(item); + + item = new StuddedChest(); + item.Hue = 0x455; + AddItem(item); + + item = new StuddedArms(); + item.Hue = 0x455; + AddItem(item); + } + + public Recaro(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Recaro"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, + 1078187); // The art of fencing requires a dexterous hand, a quick wit and fleet feet. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AldenArmstrong : BaseCreature + { + [Constructible] + public AldenArmstrong() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Tactics Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203B; + HairHue = 0x44E; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new Shoes()); + AddItem(new StuddedLegs()); + AddItem(new StuddedGloves()); + AddItem(new StuddedGorget()); + AddItem(new StuddedChest()); + AddItem(new StuddedArms()); + AddItem(new Katana()); + } + + public AldenArmstrong(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Alden Armstrong"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, + 1078136); // There is an art to slaying your enemies swiftly. It's called tactics, and I can teach it to you. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Jockles : BaseCreature + { + [Constructible] + public Jockles() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Swordsmanship Instructor"; + BodyValue = 0x190; + Hue = 0x83FA; + HairItemID = 0x203C; + HairHue = 0x8A7; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new Broadsword()); + AddItem(new PlateChest()); + AddItem(new PlateLegs()); + AddItem(new PlateGloves()); + AddItem(new PlateArms()); + AddItem(new PlateGorget()); + AddItem(new OrderShield()); + } + + public Jockles(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Jockles"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078135); // Talk to me to learn the way of the blade. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TylAriadne : BaseCreature + { + [Constructible] + public TylAriadne() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Parrying Instructor"; + BodyValue = 0x190; + Hue = 0x8374; + HairItemID = 0; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new ElvenBoots(0x96D)); + + Item item; + + item = new StuddedLegs(); + item.Hue = 0x96D; + AddItem(item); + + item = new StuddedGloves(); + item.Hue = 0x96D; + AddItem(item); + + item = new StuddedGorget(); + item.Hue = 0x96D; + AddItem(item); + + item = new StuddedChest(); + item.Hue = 0x96D; + AddItem(item); + + item = new StuddedArms(); + item.Hue = 0x96D; + AddItem(item); + + item = new DiamondMace(); + item.Hue = 0x96D; + AddItem(item); + } + + public TylAriadne(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Tyl Ariadne"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078140); // Want to learn how to parry blows? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Alefian : BaseCreature + { + [Constructible] + public Alefian() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Resisting Spells Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203D; + HairHue = 0x457; + + InitStats(100, 100, 25); + + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Inscribe, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + AddItem(new Backpack()); + AddItem(new Robe()); + AddItem(new Sandals()); + } + + public Alefian(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Alefian"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078130); // A mage should learn how to resist spells. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Gustar : BaseCreature + { + [Constructible] + public Gustar() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Meditation Instructor"; + BodyValue = 0x190; + Hue = 0x83F5; + HairItemID = 0x203B; + HairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Inscribe, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + AddItem(new Backpack()); + AddItem(new GustarShroud()); + AddItem(new Sandals()); + } + + public Gustar(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Gustar"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078126); // Meditation allows a mage to replenish mana quickly. I can teach you. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GustarShroud : BaseOuterTorso + { + [Constructible] + public GustarShroud() : base(0x2684) + { + Hue = 0x479; + } + + public GustarShroud(Serial serial) : base(serial) + { + } + + public override string DefaultName => " "; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // Version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Jillian : BaseCreature + { + [Constructible] + public Jillian() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Inscription Instructor"; + BodyValue = 0x191; + Female = true; + Hue = 0x83EA; + HairItemID = 0x203D; + HairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Inscribe, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + AddItem(new Backpack()); + AddItem(new Robe(0x479)); + AddItem(new Sandals()); + } + + public Jillian(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Jillian"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078129); // I can teach you how to scribe magic scrolls. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Kaelynna : BaseCreature + { + [Constructible] + public Kaelynna() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Magery Instructor"; + BodyValue = 0x191; + Female = true; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x47D; + + InitStats(100, 100, 25); + + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Inscribe, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + AddItem(new Backpack()); + AddItem(new Robe(0x592)); + AddItem(new Sandals()); + } + + public Kaelynna(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Kaelynna"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078125); // Want to unlock the secrets of magery? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Mithneral : BaseCreature + { + [Constructible] + public Mithneral() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Evaluating Intelligence Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Inscribe, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + AddItem(new Backpack()); + AddItem(new Sandals()); + + Item item; + + item = new GustarShroud(); + item.Hue = 0x51C; + AddItem(item); + } + + public Mithneral(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Mithneral"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078127); // Want to maximize your spell damage? I have a scholarly task for you! + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AmeliaYoungstone : Tinker + { + [Constructible] + public AmeliaYoungstone() + { + Title = "the Tinkering Instructor"; + BodyValue = 0x191; + Female = true; + Hue = 0x83EA; + HairItemID = 0x203D; + HairHue = 0x46C; + + InitStats(100, 100, 25); + + SetSkill(SkillName.ArmsLore, 120.0); + SetSkill(SkillName.Blacksmith, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Tinkering, 120.0); + SetSkill(SkillName.Mining, 120.0); + } + + public AmeliaYoungstone(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Amelia Youngstone"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078123); // Tinkering is very useful for a blacksmith. You can make your own tools. + } + + public override void InitOutfit() + { + AddItem(new Backpack()); + AddItem(new Sandals()); + AddItem(new Doublet()); + AddItem(new ShortPants()); + AddItem(new HalfApron(0x8AB)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AndreasVesalius : BaseCreature + { + [Constructible] + public AndreasVesalius() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Anatomy Instructor"; + BodyValue = 0x190; + Hue = 0x83EC; + HairItemID = 0x203C; + HairHue = 0x477; + FacialHairItemID = 0x203E; + FacialHairHue = 0x477; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new Boots()); + AddItem(new BlackStaff()); + AddItem(new LongPants()); + AddItem(new Tunic(0x66D)); + } + + public AndreasVesalius(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Andreas Vesalius"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078138); // Learning of the body will allow you to excel in combat. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Avicenna : BaseCreature + { + [Constructible] + public Avicenna() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Healing Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203B; + HairHue = 0x477; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new Robe(0x66D)); + AddItem(new Boots()); + AddItem(new GnarledStaff()); + } + + public Avicenna(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Avicenna"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078137); // A warrior needs to learn how to apply bandages to wounds. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SarsmeaSmythe : BaseCreature + { + [Constructible] + public SarsmeaSmythe() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Focus Instructor"; + BodyValue = 0x191; + Female = true; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x456; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Focus, 120.0); + + AddItem(new Backpack()); + AddItem(new ThighBoots()); + AddItem(new StuddedGorget()); + AddItem(new LeatherLegs()); + AddItem(new FemaleLeatherChest()); + AddItem(new StuddedGloves()); + AddItem(new LeatherNinjaBelt()); + AddItem(new LightPlateJingasa()); + } + + public SarsmeaSmythe(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Sarsmea Smythe"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078139); // Know yourself, and you will become a true warrior. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Ryuichi : BaseVendor + { + private List m_SBInfos = new List(); + + [Constructible] + public Ryuichi() + : base("the Ninjitsu Instructor") + { + Hue = 0x8403; + + SetSkill(SkillName.Hiding, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Tracking, 120.0); + SetSkill(SkillName.Fencing, 120.0); + SetSkill(SkillName.Stealth, 120.0); + SetSkill(SkillName.Ninjitsu, 120.0); + } + + public Ryuichi(Serial serial) + : base(serial) + { + } + + protected override List SBInfos => m_SBInfos; + + public override string DefaultName => "Ryuichi"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078155); // I can teach you Ninjitsu. The Art of Stealth. + } + + public override void InitSBInfo() + { + m_SBInfos.Add(new SBNinja()); + } + + public override bool GetGender() + { + return false; + } + + public override void InitOutfit() + { + HairItemID = 0x203B; + HairHue = 0x455; + + AddItem(new SamuraiTabi()); + AddItem(new LeatherNinjaPants()); + AddItem(new LeatherNinjaMitts()); + AddItem(new LeatherNinjaHood()); + AddItem(new LeatherNinjaJacket()); + AddItem(new LeatherNinjaBelt()); + + PackGold(100, 200); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Chiyo : BaseCreature + { + [Constructible] + public Chiyo() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Hiding Instructor"; + BodyValue = 0xF7; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Hiding, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Tracking, 120.0); + SetSkill(SkillName.Fencing, 120.0); + SetSkill(SkillName.Stealth, 120.0); + SetSkill(SkillName.Ninjitsu, 120.0); + } + + public Chiyo(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Chiyo"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078165); // To be undetected means you cannot be harmed. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Jun : BaseCreature + { + [Constructible] + public Jun() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Stealth Instructor"; + BodyValue = 0x190; + Hue = 0x8403; + HairItemID = 0x203B; + HairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Hiding, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Tracking, 120.0); + SetSkill(SkillName.Fencing, 120.0); + SetSkill(SkillName.Stealth, 120.0); + SetSkill(SkillName.Ninjitsu, 120.0); + + AddItem(new Backpack()); + AddItem(new SamuraiTabi()); + AddItem(new LeatherNinjaPants()); + AddItem(new LeatherNinjaMitts()); + AddItem(new LeatherNinjaHood()); + AddItem(new LeatherNinjaJacket()); + AddItem(new LeatherNinjaBelt()); + } + + public Jun(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Jun"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078175); // Walk Silently. Remain unseen. I can teach you. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Walker : BaseCreature + { + [Constructible] + public Walker() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Tracking Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203B; + HairHue = 0x47D; + FacialHairItemID = 0x204B; + FacialHairHue = 0x47D; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Hiding, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Tracking, 120.0); + SetSkill(SkillName.Fencing, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Stealth, 120.0); + SetSkill(SkillName.Ninjitsu, 120.0); + + AddItem(new Backpack()); + AddItem(new Boots(0x455)); + AddItem(new LongPants(0x455)); + AddItem(new FancyShirt(0x47D)); + AddItem(new FloppyHat(0x455)); + } + + public Walker(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Walker"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1078213, // I don't sleep. I wait. + 1078212, // There is no theory of evolution. Just a list of creatures I allow to live. + 1078214 // I can lead a horse to water and make it drink. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Hamato : BaseVendor + { + private List m_SBInfos = new List(); + + [Constructible] + public Hamato() + : base("the Bushido Instructor") + { + Hue = 0x8403; + + SetSkill(SkillName.Anatomy, 120.0); + SetSkill(SkillName.Parry, 120.0); + SetSkill(SkillName.Healing, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Bushido, 120.0); + } + + public Hamato(Serial serial) + : base(serial) + { + } + + protected override List SBInfos => m_SBInfos; + + public override string DefaultName => "Hamato"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078134); // Seek me to learn the way of the samurai. + } + + public override void InitSBInfo() + { + m_SBInfos.Add(new SBSamurai()); + } + + public override bool GetGender() + { + return false; + } + + public override void InitOutfit() + { + HairItemID = 0x203D; + HairHue = 0x497; + + AddItem(new Backpack()); + AddItem(new NoDachi()); + AddItem(new NinjaTabi()); + AddItem(new PlateSuneate()); + AddItem(new LightPlateJingasa()); + AddItem(new LeatherDo()); + AddItem(new LeatherHiroSode()); + + PackGold(100, 200); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Mulcivikh : Mage + { + [Constructible] + public Mulcivikh() + { + Title = "the Necromancy Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203D; + HairHue = 0x457; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.SpiritSpeak, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.Necromancy, 120.0); + } + + public Mulcivikh(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Mulcivikh"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078131); // Allured by dark magic, aren't you? + } + + public override void InitOutfit() + { + AddItem(new Backpack()); + AddItem(new Sandals(0x8FD)); + AddItem(new BoneHelm()); + + Item item; + + item = new LeatherLegs(); + item.Hue = 0x2C3; + AddItem(item); + + item = new LeatherGloves(); + item.Hue = 0x2C3; + AddItem(item); + + item = new LeatherGorget(); + item.Hue = 0x2C3; + AddItem(item); + + item = new LeatherChest(); + item.Hue = 0x2C3; + AddItem(item); + + item = new LeatherArms(); + item.Hue = 0x2C3; + AddItem(item); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Morganna : Mage + { + [Constructible] + public Morganna() + { + Title = "the Spirit Speak Instructor"; + BodyValue = 0x191; + Female = true; + Hue = 0x83EA; + HairItemID = 0x203C; + HairHue = 0x455; + + InitStats(100, 100, 25); + + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.SpiritSpeak, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.Necromancy, 120.0); + } + + public Morganna(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Morganna"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078132); // Want to learn how to channel the supernatural? + } + + public override void InitOutfit() + { + AddItem(new Backpack()); + AddItem(new Sandals()); + AddItem(new Robe(0x47D)); + AddItem(new SkullCap(0x455)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class JacobWaltz : BaseCreature + { + [Constructible] + public JacobWaltz() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Miner Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x2048; + HairHue = 0x44E; + FacialHairItemID = 0x204D; + FacialHairHue = 0x44E; + + InitStats(100, 100, 25); + + SetSkill(SkillName.ArmsLore, 120.0); + SetSkill(SkillName.Blacksmith, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Tinkering, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Mining, 120.0); + + AddItem(new Backpack()); + AddItem(new Pickaxe()); + AddItem(new Boots()); + AddItem(new WideBrimHat(0x966)); + AddItem(new ShortPants(0x370)); + AddItem(new Shirt(0x966)); + AddItem(new HalfApron(0x1BB)); + } + + public JacobWaltz(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Jacob Waltz"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078124); // You there! I can use some help mining these rocks! + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GeorgeHephaestus : Blacksmith + { + [Constructible] + public GeorgeHephaestus() + { + Title = "the Blacksmith Instructor"; + BodyValue = 0x190; + Hue = 0x83EA; + HairItemID = 0x203B; + HairHue = 0x47B; + + InitStats(100, 100, 25); + + SetSkill(SkillName.ArmsLore, 120.0); + SetSkill(SkillName.Blacksmith, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Tinkering, 120.0); + SetSkill(SkillName.Swords, 120.0); + SetSkill(SkillName.Mining, 120.0); + } + + public GeorgeHephaestus(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "George Hephaestus"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1078122); // Wanna learn how to make powerful weapons and armor? Talk to me. + } + + public override void InitOutfit() + { + AddItem(new Backpack()); + AddItem(new Boots(0x973)); + AddItem(new LongPants()); + AddItem(new Bascinet()); + AddItem(new FullApron(0x8AB)); + + Item item; + + item = new SmithHammer(); + item.Hue = 0x8AB; + AddItem(item); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/NewHavenTraining.cs b/Scripts/Engines/MLQuests/Definitions/NewHavenTraining.cs index 494d3dd55..e8200317d 100644 --- a/Scripts/Engines/MLQuests/Definitions/NewHavenTraining.cs +++ b/Scripts/Engines/MLQuests/Definitions/NewHavenTraining.cs @@ -1,4 +1,3 @@ -using System; using Server.Engines.MLQuests.Objectives; using Server.Engines.MLQuests.Rewards; using Server.Items; @@ -6,998 +5,1035 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests - - public class SplitEnds : MLQuest - { - public SplitEnds() - { - Activated = true; - HasRestartDelay = true; - Title = 1075506; // Split Ends - Description = 1075507; // *sighs* I think bowcrafting is a might beyond my talents. Say there, you look a bit more confident with tools. Can I persuade thee to make a few arrows? You could have my satchel in return... 'tis useless to me! You'll need a fletching kit to start, some feathers, and a few arrow shafts. Just use the fletching kit while you have the other things, and I'm sure you'll figure out the rest. - RefusalMessage = 1075508; // Oh. Well. I'll just keep trying alone, I suppose... - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - CompletionMessage = 1072272; // Thanks for helping me out. Here's the reward I promised you. - - Objectives.Add( new CollectObjective( 20, typeof( Arrow ), 1023902 ) ); // arrow - - Rewards.Add( new ItemReward( 1074282, typeof( AndricSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Andric" ), new Point3D( 3742, 2582, 40 ), Map.Trammel ); - } - } - - public class IShotAnArrowIntoTheAir : MLQuest - { - public IShotAnArrowIntoTheAir() - { - Activated = true; - Title = 1075486; // I Shot an Arrow Into the Air... - Description = 1075482; // Truth be told, the only way to get a feel for the bow is to shoot one and there's no better practice target than a sheep. If ye can shoot ten of them I think ye will have proven yer abilities. Just grab a bow and make sure to take enough ammunition. Bows tend to use arrows and crossbows use bolts. Ye can buy 'em or have someone craft 'em. How about it then? Come back here when ye are done. - RefusalMessage = 1075483; // Fair enough, the bow isn't for everyone. Good day then. - InProgressMessage = 1075484; // Return once ye have killed ten sheep with a bow and not a moment before. - - Objectives.Add( new KillObjective( 10, new[] { typeof( Sheep ) }, 1018270 ) ); // sheep - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Kashiel" ), new Point3D( 3744, 2586, 40 ), Map.Trammel ); - } - } - - public class BakersDozen : MLQuest - { - public BakersDozen() - { - Activated = true; - HasRestartDelay = true; - Title = 1075478; // Baker's Dozen - Description = 1075479; // You there! Do you know much about the ways of cooking? If you help me out, I'll show you a thing or two about how it's done. Bring me some cookie mix, about 5 batches will do it, and I will reward you. Although, I don't think you can buy it, you can make some in a snap! First get a rolling pin or frying pan or even a flour sifter. Then you mix one pinch of flour with some water and you've got some dough! Take that dough and add one dollop of honey and you've got sweet dough. add one more drop of honey and you've got cookie mix. See? Nothing to it! Now get to work! - RefusalMessage = 1075480; // Argh, I absolutely must have more of these 'cookies!' Come back if you change your mind. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - CompletionMessage = 1075481; // Thank you! I haven't been this excited about food in months! - - Objectives.Add( new CollectObjective( 5, typeof( CookieMix ), 1024159 ) ); // cookie mix - - Rewards.Add( new ItemReward( 1074282, typeof( AsandosSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Asandos" ), new Point3D( 3505, 2513, 27 ), Map.Trammel ); - } - } - - public class AStitchInTime : MLQuest - { - public AStitchInTime() - { - Activated = true; - HasRestartDelay = true; - Title = 1075523; // A Stitch in Time - Description = 1075522; // Oh how I wish I had a fancy dress like the noble ladies of Castle British! I don't have much... but I have a few trinkets I might trade for it. It would mean the world to me to go to a fancy ball and dance the night away. Oh, and I could tell you how to make one! You just need to use your sewing kit on enough cut cloth, that's all. - RefusalMessage = 1075526; // Won't you reconsider? It'd mean the world to me, it would! - InProgressMessage = 1075527; // Hello again! Do you need anything? You may want to visit the tailor's shop for cloth and a sewing kit, if you don't already have them. - CompletionMessage = 1075528; // It's gorgeous! I only have a few things to give you in return, but I can't thank you enough! Maybe I'll even catch Uzeraan's eye at the, er, *blushes* I mean, I can't wait to wear it to the next town dance! - - Objectives.Add( new CollectObjective( 1, typeof( FancyDress ), 1027935 ) ); // fancy dress - - Rewards.Add( new ItemReward( 1075524, typeof( AnOldRing ) ) ); // an old ring - Rewards.Add( new ItemReward( 1075525, typeof( AnOldNecklace ) ) ); // an old necklace - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Clairesse" ), new Point3D( 3492, 2546, 20 ), Map.Trammel ); - } - } - - public class BatteredBucklers : MLQuest - { - public BatteredBucklers() - { - Activated = true; - HasRestartDelay = true; - Title = 1075511; // Battered Bucklers - Description = 1075512; // Hey there! Yeah... you! Ya' any good with a hammer? Tell ya what, if yer thinking about tryin' some metal work, and have a bit of skill, I can show ya how to bend it into shape. Just get some of those ingots there, and grab a hammer and use it over here at this forge. I need a few more bucklers hammered out to fill this here order with... hmmm about ten more. that'll give some taste of how to work the metal. - RefusalMessage = 1075514; // Not enough muscle on yer bones to use it? hmph, probably afraid of the sparks markin' up yer loverly skin... to good for some honest labor... ha!... off with ya! - InProgressMessage = 1075515; // Come On! Whats that... a bucket? We need ten bucklers... not spitoons. - CompletionMessage = 1075516; // Thanks for the help. Here's something for ya to remember me by. - - Objectives.Add( new CollectObjective( 10, typeof( Buckler ), 1027027 ) ); // buckler - - Rewards.Add( new ItemReward( 1074282, typeof( GervisSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Gervis" ), new Point3D( 3505, 2749, 0 ), Map.Trammel ); - } - } - - public class MoreOrePlease : MLQuest - { - public MoreOrePlease() - { - Activated = true; - HasRestartDelay = true; - Title = 1075530; // More Ore Please - Description = 1075529; // Have a pickaxe? My supplier is late and I need some iron ore so I can complete a bulk order for another merchant. If you can get me some soon I'll pay you double what it's worth on the market. Just find a cave or mountainside and try to use your pickaxe there, maybe you'll strike a good vein! 5 large pieces should do it. - RefusalMessage = 1075531; // Not feeling strong enough today? Its alright, I didn't need a bucket of rocks anyway. - InProgressMessage = 1075532; // Hmmm� we need some more Ore. Try finding a mountain or cave, and give it a whack. - CompletionMessage = 1075533; // I see you found a good vien! Great! This will help get this order out on time. Good work! - - Objectives.Add( new InternalObjective() ); - - Rewards.Add( new ItemReward( 1074282, typeof( MuggSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Mugg" ), new Point3D( 3507, 2747, 0 ), Map.Trammel ); - } - - private class InternalObjective : CollectObjective - { - // Any type of ore is allowed - public InternalObjective() - : base( 5, typeof( BaseOre ), 1026585 ) // ore - { - } - - public override bool CheckItem( Item item ) - { - return ( item.ItemID == 6585 ); // Only large pieces count - } - } - } - - public class ComfortableSeating : MLQuest - { - public ComfortableSeating() - { - Activated = true; - HasRestartDelay = true; - Title = 1075517; // Comfortable Seating - Description = 1075518; // Hail friend, hast thou a moment? A mishap with a saw hath left me in a sorry state, for it shall be a while before I canst return to carpentry. In the meantime, I need a comfortable chair that I may rest. Could thou craft a straw chair? Only a tool, such as a dovetail saw, a few boards, and some skill as a carpenter is needed. Remember, this is a piece of furniture, so please pay attention to detail. - RefusalMessage = 1072687; // I quite understand your reluctance. If you reconsider, I'll be here. - InProgressMessage = 1075509; // Is all going well? I look forward to the simple comforts in my very own home. - CompletionMessage = 1074720; // This is perfect! - - Objectives.Add( new CollectObjective( 1, typeof( BambooChair ), "straw chair" ) ); - - Rewards.Add( new ItemReward( 1074282, typeof( LowelSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Lowel" ), new Point3D( 3440, 2645, 27 ), Map.Trammel ); - } - } - - public class ThePenIsMightier : MLQuest - { - public ThePenIsMightier() - { - Activated = true; - HasRestartDelay = true; - Title = 1075542; // The Pen is Mightier - Description = 1075543; // Do you know anything about 'Inscription?' I've been trying to get my hands on some hand crafted Recall scrolls for a while now, and I could really use some help. I don't have a scribe's pen, let alone a spellbook with Recall in it, or blank scrolls, so there's no way I can do it on my own. How about you though? I could trade you one of my old leather bound books for some. - RefusalMessage = 1075546; // Hmm, thought I had your interest there for a moment. It's not everyday you see a book made from real daemon skin, after all! - InProgressMessage = 1075547; // Inscribing... yes, you'll need a scribe's pen, some reagents, some blank scroll, and of course your own magery book. You might want to visit the magery shop if you're lacking some materials. - CompletionMessage = 1075548; // Ha! Finally! I've had a rune to the waterfalls near Justice Isle that I've been wanting to use for the longest time, and now I can visit at last. Here's that book I promised you... glad to be rid of it, to be honest. - - Objectives.Add( new CollectObjective( 5, typeof( RecallScroll ), "recall scroll" ) ); - - Rewards.Add( new ItemReward( 1075545, typeof( RedLeatherBook ) ) ); // a book bound in red leather - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Lyle" ), new Point3D( 3503, 2584, 14 ), Map.Trammel ); - } - } - - public class AClockworkPuzzle : MLQuest - { - public AClockworkPuzzle() - { - Activated = true; - HasRestartDelay = true; - Title = 1075535; // A clockwork puzzle - Description = 1075534; // 'Tis a riddle, you see! "What kind of clock is only right twice per day? A broken one!" *laughs heartily* Ah, yes *wipes eye*, that's one of my favorites! Ah... to business. Could you fashion me some clock parts? I wish my own clocks to be right all the day long! You'll need some tinker's tools and some iron ingots, I think, but from there it should be just a matter of working the metal. - RefusalMessage = 1072981; // Or perhaps you'd rather not. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - CompletionMessage = 1075536; // Wonderful! Tick tock, tick tock, soon all shall be well with grandfather's clock! - - Objectives.Add( new CollectObjective( 5, typeof( ClockParts ), 1024175 ) ); // clock parts - - Rewards.Add( new ItemReward( 1074282, typeof( NibbetSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Nibbet" ), new Point3D( 3459, 2525, 53 ), Map.Trammel ); - } - } - - public class DeliciousFishes : MLQuest - { - public DeliciousFishes() - { - Activated = true; - HasRestartDelay = true; - Title = 1075555; // Delicious Fishes - Description = 1075556; // Ello there, looking for a good place on the dock to fish? I like the southeast corner meself. What's that? Oh, no, *sighs* me pole is broken and in for fixin'. My grandpappy gave me that pole, means a lot you see. Miss the taste of fish though... Oh say, since you're here, could you catch me a few fish? I can cook a mean fish steak, and I'll split 'em with you! But make sure it's one of the green kind, they're the best for seasoning! - RefusalMessage = 1075558; // Ah, you're missin' out my friend, you're missing out. My peppercorn fishsteaks are famous on this little isle of ours! - InProgressMessage = 1075559; // Eh? Find yerself a pole and get close to some water. Just toss the line on in and hopefully you won't snag someone's old boots! Remember, that's twenty of them green fish we'll be needin', so come back when you've got em, 'aight? - CompletionMessage = 1075560; // Just a moment my friend, just a moment! *rummages in his pack* Here we are! My secret blend of peppers always does the trick, never fails, no not once. These'll fill you up much faster than that tripe they sell in the market! - - Objectives.Add( new CollectObjective( 5, typeof( Fish ), 1022508 ) ); // fish - - Rewards.Add( new ItemReward( 1075557, typeof( PeppercornFishsteak ), 3 ) ); // peppercorn fishsteak - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Norton" ), new Point3D( 3502, 2603, 1 ), Map.Trammel ); - } - } - - public class FleeAndFatigue : MLQuest - { - public FleeAndFatigue() - { - Activated = true; - HasRestartDelay = true; - Title = 1075487; // Flee and Fatigue - Description = 1075488; // I was just *coughs* ambushed near the moongate. *wheeze* Why do I pay my taxes? Where were the guards? You then, you an Alchemist? If you can make me a few Refresh potions, I will be back on my feet and can give those lizards the what for! Find a mortar and pestle, a good amount of black pearl, and ten empty bottles to store the finished potions in. Just use the mortar and pestle and the rest will surely come to you. When you return, the favor will be repaid. - RefusalMessage = 1075489; // Fine fine, off with *cough* thee then! The next time you see a lizardman though, give him a whallop for me, eh? - InProgressMessage = 1075490; // Just remember you need to use your mortar and pestle while you have empty bottles and some black pearl. Refresh potions are what I need. - CompletionMessage = 1075491; // *glug* *glug* Ahh... Yes! Yes! That feels great! Those lizardmen will never know what hit 'em! Here, take this, I can get more from the lizards. - - Objectives.Add( new CollectObjective( 10, typeof( RefreshPotion ), "refresh potions" ) ); - - Rewards.Add( new ItemReward( 1074282, typeof( SadrahSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Sadrah" ), new Point3D( 3742, 2731, 7 ), Map.Trammel ); - } - } - - public class ChopChopOnTheDouble : MLQuest - { - public ChopChopOnTheDouble() - { - Activated = true; - HasRestartDelay = true; - Title = 1075537; // Chop Chop, On The Double! - Description = 1075538; // That's right, move it! I need sixty logs on the double, and they need to be freshly cut! If you can get them to me fast I'll have your payment in your hands before you have the scent of pine out from beneath your nostrils. Just get a sharp axe and hack away at some of the trees in the land and your lumberjacking skill will rise in no time. - RefusalMessage = 1072981; // Or perhaps you'd rather not. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - CompletionMessage = 1075539; // Ahhh! The smell of fresh cut lumber. And look at you, all strong and proud, as if you had done an honest days work! - - Objectives.Add( new CollectObjective( 60, typeof( Log ), 1027133 ) ); // log - - Rewards.Add( new ItemReward( 1074282, typeof( HargroveSatchel ) ) ); // Craftsmans's Satchel - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Hargrove" ), new Point3D( 3445, 2633, 28 ), Map.Trammel ); - } - } - - #endregion - - #region Mobiles - - public class Andric : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Andric"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Andric() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the archer trainer"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Archery, 60.0, 80.0 ); - - AddItem( new Backpack() ); - - Item item; - - item = new LeatherChest(); - item.Hue = 0x1BB; - AddItem( item ); - - item = new LeatherLegs(); - item.Hue = 0x6AD; - AddItem( item ); - - item = new LeatherArms(); - item.Hue = 0x6AD; - AddItem( item ); - - item = new LeatherGloves(); - item.Hue = 0x1BB; - AddItem( item ); - - AddItem( new Boots( 0x1BB ) ); - AddItem( new CompositeBow() ); - } - - public Andric( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Kashiel : BaseCreature - { - public override string DefaultName => "Kashiel"; - public override bool IsInvulnerable => true; - - [Constructible] - public Kashiel() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the archer"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - - Item item; - - item = new LeatherChest(); - item.Hue = 0x1BB; - AddItem( item ); - - item = new LeatherLegs(); - item.Hue = 0x901; - AddItem( item ); - - item = new LeatherArms(); - item.Hue = 0x901; - AddItem( item ); - - item = new LeatherGloves(); - item.Hue = 0x1BB; - AddItem( item ); - - AddItem( new Boots( 0x1BB ) ); - AddItem( new CompositeBow() ); - } - - public Kashiel( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Asandos : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Asandos"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Asandos() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the chef"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x901 ) ); - AddItem( new ShortPants() ); - AddItem( new Shirt() ); - AddItem( new Cap() ); - AddItem( new HalfApron( 0x28 ) ); - } - - public Asandos( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - //[QuesterName( "Clarisse" )] // On OSI the gumps refer to her as this, different from actual name - public class Clairesse : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Clairesse"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Clairesse() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the servant"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); - AddItem( new PlainDress( 0x3C9 ) ); - } - - public Clairesse( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Gervis : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Gervis"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213, // Hey buddy.� Looking for work? - 1074211 // I could use some help. - ) ); - } - - [Constructible] - public Gervis() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the blacksmith trainer"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Blacksmith, 60.0, 80.0 ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x3B3 ) ); - AddItem( new ShortPants( 0x1BB ) ); - AddItem( new Doublet( 0x652 ) ); - AddItem( new SmithHammer() ); - - Item item; - - item = new LeatherGloves(); - item.Hue = 0x3B2; - AddItem( item ); - } - - public Gervis( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Mugg : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Mugg"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074211 ); // I could use some help. - } - - [Constructible] - public Mugg() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the miner"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x901 ) ); - AddItem( new ShortPants( 0x3B3 ) ); - AddItem( new Shirt( 0x22B ) ); - AddItem( new HalfApron( 0x5F1 ) ); - AddItem( new SkullCap( 0x177 ) ); - AddItem( new Pickaxe() ); - } - - public Mugg( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Lowel : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lowel"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Lowel() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the carpenter"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x543 ) ); - AddItem( new ShortPants( 0x758 ) ); - AddItem( new FancyShirt( 0x53A ) ); - AddItem( new HalfApron( 0x6D2 ) ); - } - - public Lowel( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Lyle : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Lyle"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213 // Hey buddy.� Looking for work? - ) ); - } - - [Constructible] - public Lyle() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the mage"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Robe( 0x2FD ) ); - AddItem( new ThighBoots() ); - } - - public Lyle( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Nibbet : BaseCreature - { - public override string DefaultName => "Nibbet"; - public override bool IsInvulnerable => true; - - [Constructible] - public Nibbet() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the tinker"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x591 ) ); - AddItem( new ShortPants( 0xF8 ) ); - AddItem( new Shirt( 0x2D ) ); - AddItem( new FullApron( 0x288 ) ); - } - - public Nibbet( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Norton : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Norton"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213, // Hey buddy.� Looking for work? - 1074211 // I could use some help. - ) ); - } - - [Constructible] - public Norton() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the fisher"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new ThighBoots() ); - AddItem( new LongPants( 0x6C2 ) ); - AddItem( new Shirt( 0x11D ) ); - } - - public Norton( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Sadrah : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Sadrah"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? - 1074213, // Hey buddy.� Looking for work? - 1074211 // I could use some help. - ) ); - } - - [Constructible] - public Sadrah() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the courier"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x901 ) ); - AddItem( new Skirt( 0x52 ) ); - AddItem( new Shirt( 0x127 ) ); - AddItem( new Cloak( 0x65) ); - AddItem( new Longsword() ); - } - - public Sadrah( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Hargrove : BaseCreature - { - public override bool IsInvulnerable => true; - public override string DefaultName => "Hargrove"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074213, // Hey buddy.� Looking for work? - 1074211 // I could use some help. - ) ); - } - - [Constructible] - public Hargrove() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Lumberjack"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new Backpack() ); - AddItem( new Boots( 0x901 ) ); - AddItem( new StuddedLegs() ); - AddItem( new Shirt( 0x288 ) ); - AddItem( new Bandana( 0x20 ) ); - AddItem( new BattleAxe() ); - - Item item; - - item = new PlateGloves(); - item.Hue = 0x21E; - AddItem( item ); - - } - - public Hargrove( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #region Quests + + public class SplitEnds : MLQuest + { + public SplitEnds() + { + Activated = true; + HasRestartDelay = true; + Title = 1075506; // Split Ends + Description = + 1075507; // *sighs* I think bowcrafting is a might beyond my talents. Say there, you look a bit more confident with tools. Can I persuade thee to make a few arrows? You could have my satchel in return... 'tis useless to me! You'll need a fletching kit to start, some feathers, and a few arrow shafts. Just use the fletching kit while you have the other things, and I'm sure you'll figure out the rest. + RefusalMessage = 1075508; // Oh. Well. I'll just keep trying alone, I suppose... + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + CompletionMessage = 1072272; // Thanks for helping me out. Here's the reward I promised you. + + Objectives.Add(new CollectObjective(20, typeof(Arrow), 1023902)); // arrow + + Rewards.Add(new ItemReward(1074282, typeof(AndricSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Andric"), new Point3D(3742, 2582, 40), Map.Trammel); + } + } + + public class IShotAnArrowIntoTheAir : MLQuest + { + public IShotAnArrowIntoTheAir() + { + Activated = true; + Title = 1075486; // I Shot an Arrow Into the Air... + Description = + 1075482; // Truth be told, the only way to get a feel for the bow is to shoot one and there's no better practice target than a sheep. If ye can shoot ten of them I think ye will have proven yer abilities. Just grab a bow and make sure to take enough ammunition. Bows tend to use arrows and crossbows use bolts. Ye can buy 'em or have someone craft 'em. How about it then? Come back here when ye are done. + RefusalMessage = 1075483; // Fair enough, the bow isn't for everyone. Good day then. + InProgressMessage = 1075484; // Return once ye have killed ten sheep with a bow and not a moment before. + + Objectives.Add(new KillObjective(10, new[] { typeof(Sheep) }, 1018270)); // sheep + + Rewards.Add(ItemReward.BagOfTrinkets); + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Kashiel"), new Point3D(3744, 2586, 40), Map.Trammel); + } + } + + public class BakersDozen : MLQuest + { + public BakersDozen() + { + Activated = true; + HasRestartDelay = true; + Title = 1075478; // Baker's Dozen + Description = + 1075479; // You there! Do you know much about the ways of cooking? If you help me out, I'll show you a thing or two about how it's done. Bring me some cookie mix, about 5 batches will do it, and I will reward you. Although, I don't think you can buy it, you can make some in a snap! First get a rolling pin or frying pan or even a flour sifter. Then you mix one pinch of flour with some water and you've got some dough! Take that dough and add one dollop of honey and you've got sweet dough. add one more drop of honey and you've got cookie mix. See? Nothing to it! Now get to work! + RefusalMessage = + 1075480; // Argh, I absolutely must have more of these 'cookies!' Come back if you change your mind. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + CompletionMessage = 1075481; // Thank you! I haven't been this excited about food in months! + + Objectives.Add(new CollectObjective(5, typeof(CookieMix), 1024159)); // cookie mix + + Rewards.Add(new ItemReward(1074282, typeof(AsandosSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Asandos"), new Point3D(3505, 2513, 27), Map.Trammel); + } + } + + public class AStitchInTime : MLQuest + { + public AStitchInTime() + { + Activated = true; + HasRestartDelay = true; + Title = 1075523; // A Stitch in Time + Description = + 1075522; // Oh how I wish I had a fancy dress like the noble ladies of Castle British! I don't have much... but I have a few trinkets I might trade for it. It would mean the world to me to go to a fancy ball and dance the night away. Oh, and I could tell you how to make one! You just need to use your sewing kit on enough cut cloth, that's all. + RefusalMessage = 1075526; // Won't you reconsider? It'd mean the world to me, it would! + InProgressMessage = + 1075527; // Hello again! Do you need anything? You may want to visit the tailor's shop for cloth and a sewing kit, if you don't already have them. + CompletionMessage = + 1075528; // It's gorgeous! I only have a few things to give you in return, but I can't thank you enough! Maybe I'll even catch Uzeraan's eye at the, er, *blushes* I mean, I can't wait to wear it to the next town dance! + + Objectives.Add(new CollectObjective(1, typeof(FancyDress), 1027935)); // fancy dress + + Rewards.Add(new ItemReward(1075524, typeof(AnOldRing))); // an old ring + Rewards.Add(new ItemReward(1075525, typeof(AnOldNecklace))); // an old necklace + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Clairesse"), new Point3D(3492, 2546, 20), Map.Trammel); + } + } + + public class BatteredBucklers : MLQuest + { + public BatteredBucklers() + { + Activated = true; + HasRestartDelay = true; + Title = 1075511; // Battered Bucklers + Description = + 1075512; // Hey there! Yeah... you! Ya' any good with a hammer? Tell ya what, if yer thinking about tryin' some metal work, and have a bit of skill, I can show ya how to bend it into shape. Just get some of those ingots there, and grab a hammer and use it over here at this forge. I need a few more bucklers hammered out to fill this here order with... hmmm about ten more. that'll give some taste of how to work the metal. + RefusalMessage = + 1075514; // Not enough muscle on yer bones to use it? hmph, probably afraid of the sparks markin' up yer loverly skin... to good for some honest labor... ha!... off with ya! + InProgressMessage = 1075515; // Come On! Whats that... a bucket? We need ten bucklers... not spitoons. + CompletionMessage = 1075516; // Thanks for the help. Here's something for ya to remember me by. + + Objectives.Add(new CollectObjective(10, typeof(Buckler), 1027027)); // buckler + + Rewards.Add(new ItemReward(1074282, typeof(GervisSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Gervis"), new Point3D(3505, 2749, 0), Map.Trammel); + } + } + + public class MoreOrePlease : MLQuest + { + public MoreOrePlease() + { + Activated = true; + HasRestartDelay = true; + Title = 1075530; // More Ore Please + Description = + 1075529; // Have a pickaxe? My supplier is late and I need some iron ore so I can complete a bulk order for another merchant. If you can get me some soon I'll pay you double what it's worth on the market. Just find a cave or mountainside and try to use your pickaxe there, maybe you'll strike a good vein! 5 large pieces should do it. + RefusalMessage = + 1075531; // Not feeling strong enough today? Its alright, I didn't need a bucket of rocks anyway. + InProgressMessage = 1075532; // Hmmm� we need some more Ore. Try finding a mountain or cave, and give it a whack. + CompletionMessage = + 1075533; // I see you found a good vien! Great! This will help get this order out on time. Good work! + + Objectives.Add(new InternalObjective()); + + Rewards.Add(new ItemReward(1074282, typeof(MuggSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Mugg"), new Point3D(3507, 2747, 0), Map.Trammel); + } + + private class InternalObjective : CollectObjective + { + // Any type of ore is allowed + public InternalObjective() + : base(5, typeof(BaseOre), 1026585) // ore + { + } + + public override bool CheckItem(Item item) + { + return item.ItemID == 6585; // Only large pieces count + } + } + } + + public class ComfortableSeating : MLQuest + { + public ComfortableSeating() + { + Activated = true; + HasRestartDelay = true; + Title = 1075517; // Comfortable Seating + Description = + 1075518; // Hail friend, hast thou a moment? A mishap with a saw hath left me in a sorry state, for it shall be a while before I canst return to carpentry. In the meantime, I need a comfortable chair that I may rest. Could thou craft a straw chair? Only a tool, such as a dovetail saw, a few boards, and some skill as a carpenter is needed. Remember, this is a piece of furniture, so please pay attention to detail. + RefusalMessage = 1072687; // I quite understand your reluctance. If you reconsider, I'll be here. + InProgressMessage = 1075509; // Is all going well? I look forward to the simple comforts in my very own home. + CompletionMessage = 1074720; // This is perfect! + + Objectives.Add(new CollectObjective(1, typeof(BambooChair), "straw chair")); + + Rewards.Add(new ItemReward(1074282, typeof(LowelSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Lowel"), new Point3D(3440, 2645, 27), Map.Trammel); + } + } + + public class ThePenIsMightier : MLQuest + { + public ThePenIsMightier() + { + Activated = true; + HasRestartDelay = true; + Title = 1075542; // The Pen is Mightier + Description = + 1075543; // Do you know anything about 'Inscription?' I've been trying to get my hands on some hand crafted Recall scrolls for a while now, and I could really use some help. I don't have a scribe's pen, let alone a spellbook with Recall in it, or blank scrolls, so there's no way I can do it on my own. How about you though? I could trade you one of my old leather bound books for some. + RefusalMessage = + 1075546; // Hmm, thought I had your interest there for a moment. It's not everyday you see a book made from real daemon skin, after all! + InProgressMessage = + 1075547; // Inscribing... yes, you'll need a scribe's pen, some reagents, some blank scroll, and of course your own magery book. You might want to visit the magery shop if you're lacking some materials. + CompletionMessage = + 1075548; // Ha! Finally! I've had a rune to the waterfalls near Justice Isle that I've been wanting to use for the longest time, and now I can visit at last. Here's that book I promised you... glad to be rid of it, to be honest. + + Objectives.Add(new CollectObjective(5, typeof(RecallScroll), "recall scroll")); + + Rewards.Add(new ItemReward(1075545, typeof(RedLeatherBook))); // a book bound in red leather + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Lyle"), new Point3D(3503, 2584, 14), Map.Trammel); + } + } + + public class AClockworkPuzzle : MLQuest + { + public AClockworkPuzzle() + { + Activated = true; + HasRestartDelay = true; + Title = 1075535; // A clockwork puzzle + Description = + 1075534; // 'Tis a riddle, you see! "What kind of clock is only right twice per day? A broken one!" *laughs heartily* Ah, yes *wipes eye*, that's one of my favorites! Ah... to business. Could you fashion me some clock parts? I wish my own clocks to be right all the day long! You'll need some tinker's tools and some iron ingots, I think, but from there it should be just a matter of working the metal. + RefusalMessage = 1072981; // Or perhaps you'd rather not. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + CompletionMessage = 1075536; // Wonderful! Tick tock, tick tock, soon all shall be well with grandfather's clock! + + Objectives.Add(new CollectObjective(5, typeof(ClockParts), 1024175)); // clock parts + + Rewards.Add(new ItemReward(1074282, typeof(NibbetSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Nibbet"), new Point3D(3459, 2525, 53), Map.Trammel); + } + } + + public class DeliciousFishes : MLQuest + { + public DeliciousFishes() + { + Activated = true; + HasRestartDelay = true; + Title = 1075555; // Delicious Fishes + Description = + 1075556; // Ello there, looking for a good place on the dock to fish? I like the southeast corner meself. What's that? Oh, no, *sighs* me pole is broken and in for fixin'. My grandpappy gave me that pole, means a lot you see. Miss the taste of fish though... Oh say, since you're here, could you catch me a few fish? I can cook a mean fish steak, and I'll split 'em with you! But make sure it's one of the green kind, they're the best for seasoning! + RefusalMessage = + 1075558; // Ah, you're missin' out my friend, you're missing out. My peppercorn fishsteaks are famous on this little isle of ours! + InProgressMessage = + 1075559; // Eh? Find yerself a pole and get close to some water. Just toss the line on in and hopefully you won't snag someone's old boots! Remember, that's twenty of them green fish we'll be needin', so come back when you've got em, 'aight? + CompletionMessage = + 1075560; // Just a moment my friend, just a moment! *rummages in his pack* Here we are! My secret blend of peppers always does the trick, never fails, no not once. These'll fill you up much faster than that tripe they sell in the market! + + Objectives.Add(new CollectObjective(5, typeof(Fish), 1022508)); // fish + + Rewards.Add(new ItemReward(1075557, typeof(PeppercornFishsteak), 3)); // peppercorn fishsteak + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Norton"), new Point3D(3502, 2603, 1), Map.Trammel); + } + } + + public class FleeAndFatigue : MLQuest + { + public FleeAndFatigue() + { + Activated = true; + HasRestartDelay = true; + Title = 1075487; // Flee and Fatigue + Description = + 1075488; // I was just *coughs* ambushed near the moongate. *wheeze* Why do I pay my taxes? Where were the guards? You then, you an Alchemist? If you can make me a few Refresh potions, I will be back on my feet and can give those lizards the what for! Find a mortar and pestle, a good amount of black pearl, and ten empty bottles to store the finished potions in. Just use the mortar and pestle and the rest will surely come to you. When you return, the favor will be repaid. + RefusalMessage = + 1075489; // Fine fine, off with *cough* thee then! The next time you see a lizardman though, give him a whallop for me, eh? + InProgressMessage = + 1075490; // Just remember you need to use your mortar and pestle while you have empty bottles and some black pearl. Refresh potions are what I need. + CompletionMessage = + 1075491; // *glug* *glug* Ahh... Yes! Yes! That feels great! Those lizardmen will never know what hit 'em! Here, take this, I can get more from the lizards. + + Objectives.Add(new CollectObjective(10, typeof(RefreshPotion), "refresh potions")); + + Rewards.Add(new ItemReward(1074282, typeof(SadrahSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Sadrah"), new Point3D(3742, 2731, 7), Map.Trammel); + } + } + + public class ChopChopOnTheDouble : MLQuest + { + public ChopChopOnTheDouble() + { + Activated = true; + HasRestartDelay = true; + Title = 1075537; // Chop Chop, On The Double! + Description = + 1075538; // That's right, move it! I need sixty logs on the double, and they need to be freshly cut! If you can get them to me fast I'll have your payment in your hands before you have the scent of pine out from beneath your nostrils. Just get a sharp axe and hack away at some of the trees in the land and your lumberjacking skill will rise in no time. + RefusalMessage = 1072981; // Or perhaps you'd rather not. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + CompletionMessage = + 1075539; // Ahhh! The smell of fresh cut lumber. And look at you, all strong and proud, as if you had done an honest days work! + + Objectives.Add(new CollectObjective(60, typeof(Log), 1027133)); // log + + Rewards.Add(new ItemReward(1074282, typeof(HargroveSatchel))); // Craftsmans's Satchel + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Hargrove"), new Point3D(3445, 2633, 28), Map.Trammel); + } + } + + #endregion + + #region Mobiles + + public class Andric : BaseCreature + { + [Constructible] + public Andric() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the archer trainer"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Archery, 60.0, 80.0); + + AddItem(new Backpack()); + + Item item; + + item = new LeatherChest(); + item.Hue = 0x1BB; + AddItem(item); + + item = new LeatherLegs(); + item.Hue = 0x6AD; + AddItem(item); + + item = new LeatherArms(); + item.Hue = 0x6AD; + AddItem(item); + + item = new LeatherGloves(); + item.Hue = 0x1BB; + AddItem(item); + + AddItem(new Boots(0x1BB)); + AddItem(new CompositeBow()); + } + + public Andric(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Andric"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Kashiel : BaseCreature + { + [Constructible] + public Kashiel() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the archer"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + + Item item; + + item = new LeatherChest(); + item.Hue = 0x1BB; + AddItem(item); + + item = new LeatherLegs(); + item.Hue = 0x901; + AddItem(item); + + item = new LeatherArms(); + item.Hue = 0x901; + AddItem(item); + + item = new LeatherGloves(); + item.Hue = 0x1BB; + AddItem(item); + + AddItem(new Boots(0x1BB)); + AddItem(new CompositeBow()); + } + + public Kashiel(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Kashiel"; + public override bool IsInvulnerable => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Asandos : BaseCreature + { + [Constructible] + public Asandos() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the chef"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Boots(0x901)); + AddItem(new ShortPants()); + AddItem(new Shirt()); + AddItem(new Cap()); + AddItem(new HalfApron(0x28)); + } + + public Asandos(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Asandos"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + //[QuesterName( "Clarisse" )] // On OSI the gumps refer to her as this, different from actual name + public class Clairesse : BaseCreature + { + [Constructible] + public Clairesse() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the servant"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Shoes(Utility.RandomNeutralHue())); + AddItem(new PlainDress(0x3C9)); + } + + public Clairesse(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Clairesse"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Gervis : BaseCreature + { + [Constructible] + public Gervis() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the blacksmith trainer"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Blacksmith, 60.0, 80.0); + + AddItem(new Backpack()); + AddItem(new Boots(0x3B3)); + AddItem(new ShortPants(0x1BB)); + AddItem(new Doublet(0x652)); + AddItem(new SmithHammer()); + + Item item; + + item = new LeatherGloves(); + item.Hue = 0x3B2; + AddItem(item); + } + + public Gervis(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Gervis"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213, // Hey buddy.� Looking for work? + 1074211 // I could use some help. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Mugg : BaseCreature + { + [Constructible] + public Mugg() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the miner"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Boots(0x901)); + AddItem(new ShortPants(0x3B3)); + AddItem(new Shirt(0x22B)); + AddItem(new HalfApron(0x5F1)); + AddItem(new SkullCap(0x177)); + AddItem(new Pickaxe()); + } + + public Mugg(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Mugg"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074211); // I could use some help. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Lowel : BaseCreature + { + [Constructible] + public Lowel() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the carpenter"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Boots(0x543)); + AddItem(new ShortPants(0x758)); + AddItem(new FancyShirt(0x53A)); + AddItem(new HalfApron(0x6D2)); + } + + public Lowel(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lowel"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Lyle : BaseCreature + { + [Constructible] + public Lyle() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the mage"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Robe(0x2FD)); + AddItem(new ThighBoots()); + } + + public Lyle(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Lyle"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213 // Hey buddy.� Looking for work? + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Nibbet : BaseCreature + { + [Constructible] + public Nibbet() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the tinker"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Boots(0x591)); + AddItem(new ShortPants(0xF8)); + AddItem(new Shirt(0x2D)); + AddItem(new FullApron(0x288)); + } + + public Nibbet(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Nibbet"; + public override bool IsInvulnerable => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Norton : BaseCreature + { + [Constructible] + public Norton() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the fisher"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new ThighBoots()); + AddItem(new LongPants(0x6C2)); + AddItem(new Shirt(0x11D)); + } + + public Norton(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Norton"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213, // Hey buddy.� Looking for work? + 1074211 // I could use some help. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Sadrah : BaseCreature + { + [Constructible] + public Sadrah() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the courier"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Boots(0x901)); + AddItem(new Skirt(0x52)); + AddItem(new Shirt(0x127)); + AddItem(new Cloak(0x65)); + AddItem(new Longsword()); + } + + public Sadrah(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Sadrah"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074205, // Oh great adventurer, would you please assist a weak soul in need of aid? + 1074213, // Hey buddy.� Looking for work? + 1074211 // I could use some help. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Hargrove : BaseCreature + { + [Constructible] + public Hargrove() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Lumberjack"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new Backpack()); + AddItem(new Boots(0x901)); + AddItem(new StuddedLegs()); + AddItem(new Shirt(0x288)); + AddItem(new Bandana(0x20)); + AddItem(new BattleAxe()); + + Item item; + + item = new PlateGloves(); + item.Hue = 0x21E; + AddItem(item); + } + + public Hargrove(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override string DefaultName => "Hargrove"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074213, // Hey buddy.� Looking for work? + 1074211 // I could use some help. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Sanctuary.cs b/Scripts/Engines/MLQuests/Definitions/Sanctuary.cs index e56d93808..ccfcd5fd3 100644 --- a/Scripts/Engines/MLQuests/Definitions/Sanctuary.cs +++ b/Scripts/Engines/MLQuests/Definitions/Sanctuary.cs @@ -6,1223 +6,1309 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests - - public class BrokenShaft : MLQuest - { - public BrokenShaft() - { - Activated = true; - HasRestartDelay = true; - Title = 1074018; // Broken Shaft - Description = 1074112; // What do humans know of archery? Humans can barely shoot straight. Why, your efforts are absurd. In fact, I will make a wager - if these so called human arrows I've heard about are really as effective and innovative as human braggarts would have me believe, then I'll trade you something useful. I might even teach you something of elven craftsmanship. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( Arrow ), 1023902 ) ); // arrow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Beotham" ), new Point3D( 6285, 114, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Beotham" ), new Point3D( 6285, 114, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Danoel" ), new Point3D( 6282, 116, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Danoel" ), new Point3D( 6282, 116, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Tallinin" ), new Point3D( 6279, 122, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Tallinin" ), new Point3D( 6279, 122, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Tiana" ), new Point3D( 6257, 112, -10 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Tiana" ), new Point3D( 6257, 112, -10 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "LorekeeperOolua" ), new Point3D( 6250, 124, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "LorekeeperOolua" ), new Point3D( 6250, 124, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "LorekeeperRollarn" ), new Point3D( 6244, 110, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "LorekeeperRollarn" ), new Point3D( 6244, 110, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Dallid" ), new Point3D( 6277, 104, -10 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Dallid" ), new Point3D( 6277, 104, -10 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Canir" ), new Point3D( 6274, 130, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Canir" ), new Point3D( 6274, 130, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Yellienir" ), new Point3D( 6257, 126, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Yellienir" ), new Point3D( 6257, 126, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "ElderOnallan" ), new Point3D( 6258, 108, -10 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "ElderOnallan" ), new Point3D( 6258, 108, -10 ), Map.Felucca ); - } - } - - public class BendingTheBow : MLQuest - { - public BendingTheBow() - { - Activated = true; - HasRestartDelay = true; - Title = 1074019; // Bending the Bow - Description = 1074113; // Human craftsmanship! Ha! Why, take an elven bow. It will last for a lifetime, never break and always shoot an arrow straight and true. Can't say the same for a human, can you? Bring me some of these human made bows, and I will show you. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( Bow ), 1025041 ) ); // bow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class ArmsRace : MLQuest - { - public ArmsRace() - { - Activated = true; - HasRestartDelay = true; - Title = 1074020; // Arms Race - Description = 1074114; // Leave it to a human to try and improve upon perfection. To take a bow and turn it into a mechanical contraption like a crossbow. I wish to see more of this sort of "invention". Fetch for me a crossbow, human. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( Crossbow ), 1023919 ) ); // crossbow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class ImprovedCrossbows : MLQuest - { - public ImprovedCrossbows() - { - Activated = true; - HasRestartDelay = true; - Title = 1074021; // Improved Crossbows - Description = 1074115; // How lazy is man! You cannot even be bothered to pull your own drawstring and hold an arrow ready? You must invent a device to do it for you? I cannot understand, but perhaps if I examine a heavy crossbow for myself, I will see their appeal. Go and bring me such a device and I will repay your meager favor. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( HeavyCrossbow ), 1025116 ) ); // heavy crossbow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class BuildingTheBetterCrossbow : MLQuest - { - public BuildingTheBetterCrossbow() - { - Activated = true; - HasRestartDelay = true; - Title = 1074022; // Building the Better Crossbow - Description = 1074116; // More is always better for a human, eh? Take these repeating crossbows. What sort of mind invents such a thing? I must look at it more closely. Bring such a contraption to me and you'll receive a token for your efforts. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( RepeatingCrossbow ), 1029923 ) ); // repeating crossbow - - Rewards.Add( ItemReward.FletchingSatchel ); - } - } - - public class InstrumentOfWar : MLQuest - { - public InstrumentOfWar() - { - Activated = true; - HasRestartDelay = true; - Title = 1074055; // Instrument of War - Description = 1074149; // Pathetic, this human craftsmanship! Take their broadswords - overgrown butter knives, in reality. No, I cannot do them justice - you must see for yourself. Bring me broadswords and I will demonstrate their feebleness. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 12, typeof( Broadsword ), 1023934 ) ); // broadsword - - Rewards.Add( ItemReward.BlacksmithSatchel ); - } - } - - public class TheShield : MLQuest - { - public TheShield() - { - Activated = true; - HasRestartDelay = true; - Title = 1074054; // The Shield - Description = 1074148; // I doubt very much a human shield would stop a good stout elven arrow. You doubt me? I will show you - get me some of these heater shields and I will piece them with sharp elven arrows! - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( HeaterShield ), 1027030 ) ); // heater shield - - Rewards.Add( ItemReward.BlacksmithSatchel ); - } - } - - public class MusicToMyEars : MLQuest - { - public MusicToMyEars() - { - Activated = true; - HasRestartDelay = true; - Title = 1074023; // Music to my Ears - Description = 1074117; // You think you know something of music? Laughable! Take your lap harp. Crude, indelicate instruments that make a noise not unlike the wailing of a choleric child or a dying cat. I will show you - bring lap harps, and I will demonstrate. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( LapHarp ), 1023762 ) ); // lap harp - - Rewards.Add( ItemReward.CarpentrySatchel ); - } - } - - public class TheGlassEye : MLQuest - { - public TheGlassEye() - { - Activated = true; - HasRestartDelay = true; - Title = 1074050; // The Glass Eye - Description = 1074144; // Humans are so pathetically weak, they must be augmented by glass and metal! Imagine such a thing! I must see one of these spyglasses for myself, to understand the pathetic limits of human sight! - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( Spyglass ), 1025365 ) ); // spyglass - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class LazyHumans : MLQuest - { - public LazyHumans() - { - Activated = true; - HasRestartDelay = true; - Title = 1074024; // Lazy Humans - Description = 1074118; // Human fancy knows no bounds! It's pathetic that they are so weak that they must create a special stool upon which to rest their feet when they recline! Humans don't have any clue how to live. Bring me some of these foot stools to examine and I may teach you something worthwhile. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( FootStool ), 1022910 ) ); // foot stool - - Rewards.Add( ItemReward.CarpentrySatchel ); - } - } - - public class InventiveTools : MLQuest - { - public InventiveTools() - { - Activated = true; - HasRestartDelay = true; - Title = 1074048; // Inventive Tools - Description = 1074142; // Bring me some of these tinker's tools! I am certain, in the hands of an elf, they will fashion objects of ingenuity and delight that will shame all human invention! Hurry, do this quickly and I might deign to show you my skill. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( TinkerTools ), 1027868 ) ); // tinker's tools - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class PixieDustToDust : MLQuest - { - public PixieDustToDust() - { - Activated = true; - Title = 1073661; // Pixie dust to dust - Description = 1073700; // Is there anything more foul than a pixie? They have cruel eyes and a mind for mischief, I say. I don't care if some think they're cute -- I say kill them and let the Avatar sort them out. In fact, if you were to kill a few pixies, I'd make sure you had a few coins to rub together, if you get my meaning. - RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. - InProgressMessage = 1073741; // There's too much cuteness in the world -- kill those pixies! - - Objectives.Add( new KillObjective( 10, new[] { typeof( Pixie ) }, "pixies" ) ); - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class AnImpressivePlaid : MLQuest - { - public AnImpressivePlaid() - { - Activated = true; - HasRestartDelay = true; - Title = 1074044; // An Impressive Plaid - Description = 1074138; // I do not believe humans are so ridiculous as to wear something called a "kilt". Bring for me some of these kilts, if they truly exist, and I will offer you meager reward. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( Kilt ), 1025431 ) ); // kilt - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class ANiceShirt : MLQuest - { - public ANiceShirt() - { - Activated = true; - HasRestartDelay = true; - Title = 1074045; // A Nice Shirt - Description = 1074139; // Humans call that a fancy shirt? I would wager the ends are frayed, the collar worn, the buttons loosely stitched. Bring me fancy shirts and I will demonstrate the many ways in which they are inferior. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( FancyShirt ), 1027933 ) ); // fancy shirt - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class LeatherAndLace : MLQuest - { - public LeatherAndLace() - { - Activated = true; - HasRestartDelay = true; - Title = 1074047; // Leather and Lace - Description = 1074141; // No self respecting elf female would ever wear a studded bustier! I will prove it - bring me such clothing and I will show you how ridiculous they are! - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( StuddedBustierArms ), 1027180 ) ); // studded bustier - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class FeyHeadgear : MLQuest - { - public FeyHeadgear() - { - Activated = true; - HasRestartDelay = true; - Title = 1074043; // Fey Headgear - Description = 1074137; // Humans do not deserve to wear a thing such as a flower garland. Help me prevent such things from falling into the clumsy hands of humans -- bring me flower garlands! - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( FlowerGarland ), 1028965 ) ); // flower garland - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class NewCloak : MLQuest - { - public NewCloak() - { - Activated = true; - Title = 1074684; // New Cloak - Description = 1074685; // I have created a masterpiece! And all I need to finish it off is the soft fur of a wolf. But not just ANY wolf -- oh no, no, that wouldn't do. I've heard tales of a mighty beast, Grobu, who is bonded to the leader of the troglodytes. Only Grobu's fur will do. Will you retrieve it for me? - RefusalMessage = 1074655; // Perhaps I thought too highly of you. - InProgressMessage = 1074686; // I've told you all I know of the creature. Until you return with Grobu's fur I can't finish my cloak. - CompletionMessage = 1074687; // Ah! So soft, so supple. What a wonderful texture. Here you are ... my thanks. - - Objectives.Add( new CollectObjective( 1, typeof( GrobusFur ), "Grobu's Fur" ) ); - - Rewards.Add( ItemReward.TailorSatchel ); - } - } - - public class ADishBestServedCold : MLQuest - { - public ADishBestServedCold() - { - Activated = true; - Title = 1072372; // A Dish Best Served Cold - Description = 1072657; // *mutter* I'll have my revenge. Oh! You there. Fancy some orc extermination? I despise them all. Bombers, brutes -- you name it, if it's orcish I want it killed. - RefusalMessage = 1072667; // Hrmph. Well maybe another time then. - InProgressMessage = 1072668; // Shouldn't you be slaying orcs? - - Objectives.Add( new KillObjective( 10, new[] { typeof( Orc ) }, "orcs", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - Objectives.Add( new KillObjective( 5, new[] { typeof( OrcBomber ) }, "orc bombers", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - Objectives.Add( new KillObjective( 3, new[] { typeof( OrcBrute ) }, "orc brutes", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class ArchEnemies : MLQuest - { - public ArchEnemies() - { - Activated = true; - Title = 1073085; // Arch Enemies - Description = 1073575; // Vermin! They get into everything! I told the boy to leave out some poisoned cheese -- and they shot him. What else can I do? Unless�these ratmen are skilled with a bow, but I'd lay a wager you're better, eh? Could you skin a few of the wretches for me? - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073595; // I don't see 10 tails from Ratman Archers on your belt -- and until I do, no reward for you. - - Objectives.Add( new KillObjective( 10, new[] { typeof( RatmanArcher ) }, "ratman archers" ) ); - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class Vermin : MLQuest - { - public Vermin() - { - Activated = true; - Title = 1072995; // Vermin - Description = 1073029; // You've got to help me out! Those ratmen have been causing absolute havok around here. Kill them off before they destroy my land. I'll pay you if you kill off twelve of those dirty rats. - RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. - InProgressMessage = 1072271; // You're not quite done yet. Get back to work! - - Objectives.Add( new KillObjective( 12, new[] { typeof( Ratman ) }, "ratmen" ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class MougGuurMustDie : MLQuest - { - public override Type NextQuest => typeof( LeaderOfThePack ); - - public MougGuurMustDie() - { - Activated = true; - Title = 1072368; // Moug-Guur Must Die - Description = 1072561; // You there! Yes, you. Kill Moug-Guur, the leader of the orcs in this depressing place, and I'll make it worth your while. - RefusalMessage = 1072571; // Fine. It's no skin off my teeth. - InProgressMessage = 1072572; // Small words. Kill Moug-Guur. Go. Now! - CompletionMessage = 1072573; // You're better than I thought you'd be. Not particularly bad, but not entirely inept. - - Objectives.Add( new KillObjective( 1, new[] { typeof( MougGuur ) }, "Moug-Guur", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class LeaderOfThePack : MLQuest - { - public override Type NextQuest => typeof( SayonaraSzavetra ); - public override bool IsChainTriggered => true; - - public LeaderOfThePack() - { - Activated = true; - Title = 1072560; // Leader of the Pack - Description = 1072574; // Well now that Moug-Guur is no more -- and I can't say I'm weeping for his demise -- it's time for the ratmen to experience a similar loss of leadership. Slay Chiikkaha. In return, I'll satisfy your greed temporarily. - RefusalMessage = 1072575; // Alright, if you'd rather not, then run along and do whatever worthless things you do when I'm not giving you direction. - InProgressMessage = 1072576; // How difficult is this? The rats live in the tunnels. Go into the tunnels and find the biggest, meanest rat and execute him. Loitering around here won't get the task done. - CompletionMessage = 1072577; // It's about time! Could you have taken longer? - - Objectives.Add( new KillObjective( 1, new[] { typeof( Chiikkaha ) }, "Chiikkaha", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class SayonaraSzavetra : MLQuest - { - public override bool IsChainTriggered => true; - - public SayonaraSzavetra() - { - Activated = true; - Title = 1072375; // Sayonara, Szavetra - Description = 1072578; // Hmm, maybe you aren't entirely worthless. I suspect a demoness of Szavetra's calibre will tear you apart ... We might as well find out. Kill the succubus, yada yada, and you'll be richly rewarded. - RefusalMessage = 1072579; // Hah! I knew you couldn't handle it. - InProgressMessage = 1072581; // Hahahaha! I can see the fear in your eyes. Pathetic. Szavetra is waiting for you. - CompletionMessage = 1072582; // Amazing! Simply astonishing ... you survived. Well, I supposed I should indulge your avarice with a reward. - - Objectives.Add( new KillObjective( 1, new[] { typeof( Szavetra ) }, "Szavetra", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.Strongbox ); - } - } - - public class TappingTheKeg : MLQuest - { - public TappingTheKeg() - { - Activated = true; - HasRestartDelay = true; - Title = 1074037; // Tapping the Keg - Description = 1074131; // I have acquired a barrel of human brewed beer. I am loathe to drink it, but how else to prove how inferior it is? I suppose I shall need a barrel tap to drink. Go, bring me a barrel tap quickly, so I might get this over with. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( BarrelTap ), 1024100 ) ); // barrel tap - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class WaitingToBeFilled : MLQuest - { - public WaitingToBeFilled() - { - Activated = true; - HasRestartDelay = true; - Title = 1074036; // Waiting to be Filled - Description = 1074130; // The only good thing I can say about human made bottles is that they are empty and may yet still be filled with elven wine. Go now, fetch a number of empty bottles so that I might save them from the fate of carrying human-made wine. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 20, typeof( Bottle ), 1023854 ) ); // empty bottle - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class BreezesSong : MLQuest - { - public BreezesSong() - { - Activated = true; - HasRestartDelay = true; - Title = 1074052; // Breeze's Song - Description = 1074146; // I understand humans cruely enslave the very wind to their selfish whims! Fancy wind chimes, what a monstrous idea! You must bring me proof of this terrible depredation - hurry, bring me wind chimes! - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! - CompletionMessage = 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! - - Objectives.Add( new CollectObjective( 10, typeof( FancyWindChimes ), 1030291 ) ); // fancy wind chimes - - Rewards.Add( ItemReward.TinkerSatchel ); - } - } - - public class ProofOfTheDeed : MLQuest - { - public ProofOfTheDeed() - { - Activated = true; - Title = 1072339; // Proof of the Deed - Description = 1072340; // These human vermin must be erradicated! They despoil fair Sosaria with their every footfall upon her soil, every exhalation of breath upon her pristine air. Prove yourself an ally of Sosaria and bring me 20 human ears as proof of your devotion to our cause. - RefusalMessage = 1072342; // Do you find the task distasteful? Are you too weak to shoulder the duty of cleansing Sosaria? So be it. - InProgressMessage = 1072343; // Well, where is the proof of your deed? I will honor your actions when you have brought me the ears of the human scum. - CompletionMessage = 1072344; // Ah, well done. You have chosen the path of duty and fulfilled your task with honor. - - Objectives.Add( new CollectObjective( 20, typeof( SeveredHumanEars ), 1032591 ) ); // severed human ears - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class Marauders : MLQuest - { - public override Type NextQuest => typeof( TheBrainsOfTheOperation ); - - public Marauders() - { - Activated = true; - Title = 1072374; // Marauders - Description = 1072686; // What a miserable place we live in. Look around you at the changes we've wrought. The trees are sprouting leaves once more and the grass is reclaiming the blood-soaked soil. Who would have imagined we'd find ourselves here? Our "neighbors" are anything but friendly and those ogres are the worst of the lot. Maybe you'd be interested in helping our community by disposing of some of our least amiable neighbors? - RefusalMessage = 1072687; // I quite understand your reluctance. If you reconsider, I'll be here. - InProgressMessage = 1072688; // You can't miss those ogres, they're huge and just outside the gates here. - - Objectives.Add( new KillObjective( 10, new[] { typeof( Ogre ) }, "ogres", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - public class TheBrainsOfTheOperation : MLQuest - { - public override Type NextQuest => typeof( TheBrawn ); - public override bool IsChainTriggered => true; - - public TheBrainsOfTheOperation() - { - Activated = true; - Title = 1072692; // The Brains of the Operation - Description = 1072707; // *sigh* We have so much to do to clean this area up. Even the fine work you did on those ogres didn't have much of an impact on the community. It's the ogre lords that direct the actions of the other ogres, let's strike at the leaders and perhaps that will thwart the miserable curs. - RefusalMessage = 1072708; // Reluctance doesn't become a hero like you. But, as you wish. - InProgressMessage = 1072709; // Ogre Lords are pretty easy to recognize. They're the ones ordering the other ogres about in a lordly manner. Striking down their leadership will throw the ogres into confusion and dismay! - - Objectives.Add( new KillObjective( 10, new[] { typeof( OgreLord ) }, "ogre lords", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class TheBrawn : MLQuest - { - public override Type NextQuest => typeof( TheBiggerTheyAre ); - public override bool IsChainTriggered => true; - - public TheBrawn() - { - Activated = true; - Title = 1072693; // The Brawn - Description = 1072710; // Inconceiveable! We've learned that the ogre leadership has recruited some heavy-duty guards to their cause. I've never personally fought a cyclopian warrior, but I'm sure you could easily best a few and report back how much trouble they'll cause to our growing community? - RefusalMessage = 1072711; // Oh, I see. *sigh* Perhaps I overestimated your abilities. - InProgressMessage = 1072712; // Make sure you fully assess all of the cyclopian tactical abilities! - - Objectives.Add( new KillObjective( 6, new[] { typeof( Cyclops ) }, "cyclops", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class TheBiggerTheyAre : MLQuest - { - public override bool IsChainTriggered => true; - - public TheBiggerTheyAre() - { - Activated = true; - Title = 1072694; // The Bigger They Are ... - Description = 1072713; // The ogre insurgency has taken a turn for the worse! I've just been advised that the titans have concluded their discussions with the ogres and they've allied. We have virtually no information about titans. Engage them and appraise their mettle. - RefusalMessage = 1072714; // Certainly. You've done enough to merit a breather. When you're ready for more, report back to me. - InProgressMessage = 1072715; // Those titans don't skulk very well. You should be able to track them easily ... their footsteps are easily the largest around. - - Objectives.Add( new KillObjective( 3, new[] { typeof( Titan ) }, "titans", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.LargeBagOfTreasure ); - } - } - - public class TroubleOnTheWing : MLQuest - { - public TroubleOnTheWing() - { - Activated = true; - Title = 1072371; // Trouble on the Wing - Description = 1072593; // Those gargoyles need to get knocked down a peg or two, if you ask me. They're always flying over here and lobbing things at us. What a nuisance. Drop a dozen of them for me, would you? - RefusalMessage = 1072594; // Don't tell me you're a gargoyle sympathizer? *spits* - InProgressMessage = 1072595; // Those blasted gargoyles hang around the old tower. That's the best place to hunt them down. - - Objectives.Add( new KillObjective( 12, new[] { typeof( Gargoyle ) }, "gargoyles", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class BrotherlyLove : MLQuest - { - public BrotherlyLove() - { - Activated = true; - OneTimeOnly = true; - Title = 1072369; // Brotherly Love - Description = 1072585; // *looks around nervously* Do you travel to The Heartwood? I have an urgent letter that must be delivered there in the next 30 minutes -- to Ahie the Cloth Weaver. Will you undertake this journey? - RefusalMessage = 1072587; // *looks disappointed* Let me know if you change your mind. - InProgressMessage = 1072588; // You haven't lost the letter have you? It must be delivered to Ahie directly. Give it into no other hands. - CompletionMessage = 1074579; // Yes, can I help you? - CompletionNotice = CompletionNoticeShort; - - Objectives.Add( new DeliverObjective( typeof( APersonalLetterAddressedToAhie ), 1, "letter", typeof( Ahie ) ) ); - - Rewards.Add( ItemReward.BagOfTrinkets ); - } - } - - public class CommonBrigands : MLQuest - { - public CommonBrigands() - { - Activated = true; - Title = 1073082; // Common Brigands - Description = 1073572; // Thank goodness, a hero like you has arrived! Brigands have descended upon this area like locusts, stealing and looting where ever they go. We need someone to put these vile curs where they belong -- in their graves. Are you up to the task? - RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. - InProgressMessage = 1073592; // The Brigands still plague us. Have you killed 20 of their number?
- - Objectives.Add( new KillObjective( 20, new[] { typeof( Brigand ) }, 1074894 ) ); // Common brigands - - Rewards.Add( ItemReward.BagOfTreasure ); - } - } - - #endregion - - #region Mobiles - - [QuesterName( "Beotham (Sanctuary)" )] - public class Beotham : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Beotham"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074187, // Want a job? - 1074184 // Come here, I have work for you. - ) ); - } - - [Constructible] - public Beotham() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the bowcrafter"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x901 ) ); - AddItem( new ShortPants( 0x522 ) ); - AddItem( new FancyShirt( 0x515 ) ); - - Item item; - - item = new LeafGloves(); - item.Hue = 0x901; - AddItem( item ); - } - - public Beotham( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Danoel (Sanctuary)" )] - public class Danoel : BaseCreature - { - // TODO: Add quests: Spring Cleaning - - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Danoel"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074197 ); // Pardon me, but if you could spare some time I�d greatly appreciate it. - } - - [Constructible] - public Danoel() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the metal weaver"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new ElvenPants( 0x386 ) ); - AddItem( new ElvenShirt( 0x75F ) ); - AddItem( new FullApron( 0x1BB ) ); - AddItem( new RoyalCirclet() ); - AddItem( new SmithHammer() ); - } - - public Danoel( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Tallinin (Sanctuary)" )] - public class Tallinin : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Tallinin"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074188, // Weakling! You are not up to the task I have. - 1074211 // I could use some help. - ) ); - } - - [Constructible] - public Tallinin() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the cloth weaver"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x901 ) ); - AddItem( new Tunic( 0x37 ) ); - AddItem( new Cloak( 0x735 ) ); - } - - public Tallinin( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Tiana (Sanctuary)" )] - public class Tiana : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Tiana"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074214, // Knave! Come here right now! - 1074218 // Hey!� I want to talk to you, now. - ) ); - } - - [Constructible] - public Tiana() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the guard"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots() ); - AddItem( new HidePants() ); - AddItem( new HideFemaleChest() ); - AddItem( new HidePauldrons() ); - - Item item; - - item = new WoodlandBelt(); - item.Hue = 0x673; - AddItem( item ); - - item = new RavenHelm(); - item.Hue = 0x443; - AddItem( item ); - } - - public Tiana( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Oolua (Sanctuary)" )] - public class LorekeeperOolua : BaseCreature - { - // TODO: Add quest Dreadhorn - - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Lorekeeper Oolua"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074187 ); // Want a job? - } - - [Constructible] - public LorekeeperOolua() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenBoots( 0x75A ) ); - AddItem( new Skirt( Utility.RandomBrightHue() ) ); - AddItem( new FancyShirt( 0x742 ) ); - AddItem( new Cloak( 0x1BB ) ); - AddItem( new WildStaff() ); - } - - public LorekeeperOolua( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Rollarn (Sanctuary)" )] - public class LorekeeperRollarn : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Lorekeeper Rollarn"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074196, // Excuse me! I�m sorry to interrupt but I urgently need some assistance. - 1074197 // Pardon me, but if you could spare some time I�d greatly appreciate it. - ) ); - } - - [Constructible] - public LorekeeperRollarn() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x1BB ) ); - AddItem( new Cloak( 0x296 ) ); - AddItem( new Circlet() ); - AddItem( new LeafChest() ); - - Item item; - - item = new LeafLegs(); - item.Hue = 0x71A; - AddItem( item ); - } - - public LorekeeperRollarn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Dallid (Sanctuary)" )] - public class Dallid : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Dallid"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074185, // Hey you! Want to help me out? - 1074195 // You there, in the stupid hat! Come here. - ) ); - } - - [Constructible] - public Dallid() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the cook"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Boots( 0x901 ) ); - AddItem( new ShortPants( 0x73C ) ); - AddItem( new Shirt( 0x744 ) ); - AddItem( new FullApron( 0x1BE ) ); - AddItem( new Cleaver() ); - } - - public Dallid( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Canir (Sanctuary)" )] - public class Canir : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Canir"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074193, // You there! Yes you. Stop looking about like a toadie and come here. - 1074186 // Come here, I have a task. - ) ); - } - - [Constructible] - public Canir() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the thaumaturgist"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Sandals( 0x1BB ) ); - AddItem( new FemaleElvenRobe( 0x5A7 ) ); - AddItem( new GemmedCirclet() ); - AddItem( new MagicWand() ); - } - - public Canir( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Yellienir : BaseCreature - { - public override string DefaultName => "Yellienir"; - public override bool IsInvulnerable => true; - - [Constructible] - public Yellienir() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the bark weaver"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - AddItem( new ElvenBoots() ); - AddItem( new LeafTonlet() ); - AddItem( new FemaleLeafChest() ); - AddItem( new LeafArms() ); - AddItem( new Cloak( 0x3B2 ) ); - } - - public Yellienir( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Elder Onallan (Sanctuary)" )] - public class ElderOnallan : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Elder Onallan"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074217, // I want to make you an offer you�d be a fool to �refuse. - 1074218 // Hey!� I want to talk to you, now. - ) ); - } - - [Constructible] - public ElderOnallan() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the wise"; - Race = Race.Elf; - BodyValue = 0x25D; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new Shoes( 0x729 ) ); - AddItem( new WildStaff() ); - AddItem( new Cloak( 0x64E ) ); - } - - public ElderOnallan( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #region Quests + + public class BrokenShaft : MLQuest + { + public BrokenShaft() + { + Activated = true; + HasRestartDelay = true; + Title = 1074018; // Broken Shaft + Description = + 1074112; // What do humans know of archery? Humans can barely shoot straight. Why, your efforts are absurd. In fact, I will make a wager - if these so called human arrows I've heard about are really as effective and innovative as human braggarts would have me believe, then I'll trade you something useful. I might even teach you something of elven craftsmanship. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(Arrow), 1023902)); // arrow + + Rewards.Add(ItemReward.FletchingSatchel); + } + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Beotham"), new Point3D(6285, 114, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Beotham"), new Point3D(6285, 114, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Danoel"), new Point3D(6282, 116, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Danoel"), new Point3D(6282, 116, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Tallinin"), new Point3D(6279, 122, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Tallinin"), new Point3D(6279, 122, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Tiana"), new Point3D(6257, 112, -10), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Tiana"), new Point3D(6257, 112, -10), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "LorekeeperOolua"), new Point3D(6250, 124, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "LorekeeperOolua"), new Point3D(6250, 124, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "LorekeeperRollarn"), new Point3D(6244, 110, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "LorekeeperRollarn"), new Point3D(6244, 110, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Dallid"), new Point3D(6277, 104, -10), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Dallid"), new Point3D(6277, 104, -10), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Canir"), new Point3D(6274, 130, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Canir"), new Point3D(6274, 130, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Yellienir"), new Point3D(6257, 126, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Yellienir"), new Point3D(6257, 126, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "ElderOnallan"), new Point3D(6258, 108, -10), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "ElderOnallan"), new Point3D(6258, 108, -10), Map.Felucca); + } + } + + public class BendingTheBow : MLQuest + { + public BendingTheBow() + { + Activated = true; + HasRestartDelay = true; + Title = 1074019; // Bending the Bow + Description = + 1074113; // Human craftsmanship! Ha! Why, take an elven bow. It will last for a lifetime, never break and always shoot an arrow straight and true. Can't say the same for a human, can you? Bring me some of these human made bows, and I will show you. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(Bow), 1025041)); // bow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class ArmsRace : MLQuest + { + public ArmsRace() + { + Activated = true; + HasRestartDelay = true; + Title = 1074020; // Arms Race + Description = + 1074114; // Leave it to a human to try and improve upon perfection. To take a bow and turn it into a mechanical contraption like a crossbow. I wish to see more of this sort of "invention". Fetch for me a crossbow, human. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(Crossbow), 1023919)); // crossbow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class ImprovedCrossbows : MLQuest + { + public ImprovedCrossbows() + { + Activated = true; + HasRestartDelay = true; + Title = 1074021; // Improved Crossbows + Description = + 1074115; // How lazy is man! You cannot even be bothered to pull your own drawstring and hold an arrow ready? You must invent a device to do it for you? I cannot understand, but perhaps if I examine a heavy crossbow for myself, I will see their appeal. Go and bring me such a device and I will repay your meager favor. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(HeavyCrossbow), 1025116)); // heavy crossbow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class BuildingTheBetterCrossbow : MLQuest + { + public BuildingTheBetterCrossbow() + { + Activated = true; + HasRestartDelay = true; + Title = 1074022; // Building the Better Crossbow + Description = + 1074116; // More is always better for a human, eh? Take these repeating crossbows. What sort of mind invents such a thing? I must look at it more closely. Bring such a contraption to me and you'll receive a token for your efforts. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(RepeatingCrossbow), 1029923)); // repeating crossbow + + Rewards.Add(ItemReward.FletchingSatchel); + } + } + + public class InstrumentOfWar : MLQuest + { + public InstrumentOfWar() + { + Activated = true; + HasRestartDelay = true; + Title = 1074055; // Instrument of War + Description = + 1074149; // Pathetic, this human craftsmanship! Take their broadswords - overgrown butter knives, in reality. No, I cannot do them justice - you must see for yourself. Bring me broadswords and I will demonstrate their feebleness. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(12, typeof(Broadsword), 1023934)); // broadsword + + Rewards.Add(ItemReward.BlacksmithSatchel); + } + } + + public class TheShield : MLQuest + { + public TheShield() + { + Activated = true; + HasRestartDelay = true; + Title = 1074054; // The Shield + Description = + 1074148; // I doubt very much a human shield would stop a good stout elven arrow. You doubt me? I will show you - get me some of these heater shields and I will piece them with sharp elven arrows! + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(HeaterShield), 1027030)); // heater shield + + Rewards.Add(ItemReward.BlacksmithSatchel); + } + } + + public class MusicToMyEars : MLQuest + { + public MusicToMyEars() + { + Activated = true; + HasRestartDelay = true; + Title = 1074023; // Music to my Ears + Description = + 1074117; // You think you know something of music? Laughable! Take your lap harp. Crude, indelicate instruments that make a noise not unlike the wailing of a choleric child or a dying cat. I will show you - bring lap harps, and I will demonstrate. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(LapHarp), 1023762)); // lap harp + + Rewards.Add(ItemReward.CarpentrySatchel); + } + } + + public class TheGlassEye : MLQuest + { + public TheGlassEye() + { + Activated = true; + HasRestartDelay = true; + Title = 1074050; // The Glass Eye + Description = + 1074144; // Humans are so pathetically weak, they must be augmented by glass and metal! Imagine such a thing! I must see one of these spyglasses for myself, to understand the pathetic limits of human sight! + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(Spyglass), 1025365)); // spyglass + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class LazyHumans : MLQuest + { + public LazyHumans() + { + Activated = true; + HasRestartDelay = true; + Title = 1074024; // Lazy Humans + Description = + 1074118; // Human fancy knows no bounds! It's pathetic that they are so weak that they must create a special stool upon which to rest their feet when they recline! Humans don't have any clue how to live. Bring me some of these foot stools to examine and I may teach you something worthwhile. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(FootStool), 1022910)); // foot stool + + Rewards.Add(ItemReward.CarpentrySatchel); + } + } + + public class InventiveTools : MLQuest + { + public InventiveTools() + { + Activated = true; + HasRestartDelay = true; + Title = 1074048; // Inventive Tools + Description = + 1074142; // Bring me some of these tinker's tools! I am certain, in the hands of an elf, they will fashion objects of ingenuity and delight that will shame all human invention! Hurry, do this quickly and I might deign to show you my skill. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(TinkerTools), 1027868)); // tinker's tools + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class PixieDustToDust : MLQuest + { + public PixieDustToDust() + { + Activated = true; + Title = 1073661; // Pixie dust to dust + Description = + 1073700; // Is there anything more foul than a pixie? They have cruel eyes and a mind for mischief, I say. I don't care if some think they're cute -- I say kill them and let the Avatar sort them out. In fact, if you were to kill a few pixies, I'd make sure you had a few coins to rub together, if you get my meaning. + RefusalMessage = 1073733; // Perhaps you'll change your mind and return at some point. + InProgressMessage = 1073741; // There's too much cuteness in the world -- kill those pixies! + + Objectives.Add(new KillObjective(10, new[] { typeof(Pixie) }, "pixies")); + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + } + + public class AnImpressivePlaid : MLQuest + { + public AnImpressivePlaid() + { + Activated = true; + HasRestartDelay = true; + Title = 1074044; // An Impressive Plaid + Description = + 1074138; // I do not believe humans are so ridiculous as to wear something called a "kilt". Bring for me some of these kilts, if they truly exist, and I will offer you meager reward. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(Kilt), 1025431)); // kilt + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class ANiceShirt : MLQuest + { + public ANiceShirt() + { + Activated = true; + HasRestartDelay = true; + Title = 1074045; // A Nice Shirt + Description = + 1074139; // Humans call that a fancy shirt? I would wager the ends are frayed, the collar worn, the buttons loosely stitched. Bring me fancy shirts and I will demonstrate the many ways in which they are inferior. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(FancyShirt), 1027933)); // fancy shirt + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class LeatherAndLace : MLQuest + { + public LeatherAndLace() + { + Activated = true; + HasRestartDelay = true; + Title = 1074047; // Leather and Lace + Description = + 1074141; // No self respecting elf female would ever wear a studded bustier! I will prove it - bring me such clothing and I will show you how ridiculous they are! + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(StuddedBustierArms), 1027180)); // studded bustier + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class FeyHeadgear : MLQuest + { + public FeyHeadgear() + { + Activated = true; + HasRestartDelay = true; + Title = 1074043; // Fey Headgear + Description = + 1074137; // Humans do not deserve to wear a thing such as a flower garland. Help me prevent such things from falling into the clumsy hands of humans -- bring me flower garlands! + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(FlowerGarland), 1028965)); // flower garland + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class NewCloak : MLQuest + { + public NewCloak() + { + Activated = true; + Title = 1074684; // New Cloak + Description = + 1074685; // I have created a masterpiece! And all I need to finish it off is the soft fur of a wolf. But not just ANY wolf -- oh no, no, that wouldn't do. I've heard tales of a mighty beast, Grobu, who is bonded to the leader of the troglodytes. Only Grobu's fur will do. Will you retrieve it for me? + RefusalMessage = 1074655; // Perhaps I thought too highly of you. + InProgressMessage = + 1074686; // I've told you all I know of the creature. Until you return with Grobu's fur I can't finish my cloak. + CompletionMessage = 1074687; // Ah! So soft, so supple. What a wonderful texture. Here you are ... my thanks. + + Objectives.Add(new CollectObjective(1, typeof(GrobusFur), "Grobu's Fur")); + + Rewards.Add(ItemReward.TailorSatchel); + } + } + + public class ADishBestServedCold : MLQuest + { + public ADishBestServedCold() + { + Activated = true; + Title = 1072372; // A Dish Best Served Cold + Description = + 1072657; // *mutter* I'll have my revenge. Oh! You there. Fancy some orc extermination? I despise them all. Bombers, brutes -- you name it, if it's orcish I want it killed. + RefusalMessage = 1072667; // Hrmph. Well maybe another time then. + InProgressMessage = 1072668; // Shouldn't you be slaying orcs? + + Objectives.Add(new KillObjective(10, new[] { typeof(Orc) }, "orcs", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + Objectives.Add(new KillObjective(5, new[] { typeof(OrcBomber) }, "orc bombers", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + Objectives.Add(new KillObjective(3, new[] { typeof(OrcBrute) }, "orc brutes", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class ArchEnemies : MLQuest + { + public ArchEnemies() + { + Activated = true; + Title = 1073085; // Arch Enemies + Description = + 1073575; // Vermin! They get into everything! I told the boy to leave out some poisoned cheese -- and they shot him. What else can I do? Unless�these ratmen are skilled with a bow, but I'd lay a wager you're better, eh? Could you skin a few of the wretches for me? + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = + 1073595; // I don't see 10 tails from Ratman Archers on your belt -- and until I do, no reward for you. + + Objectives.Add(new KillObjective(10, new[] { typeof(RatmanArcher) }, "ratman archers")); + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + public class Vermin : MLQuest + { + public Vermin() + { + Activated = true; + Title = 1072995; // Vermin + Description = + 1073029; // You've got to help me out! Those ratmen have been causing absolute havok around here. Kill them off before they destroy my land. I'll pay you if you kill off twelve of those dirty rats. + RefusalMessage = 1072270; // Well, okay. But if you decide you are up for it after all, c'mon back and see me. + InProgressMessage = 1072271; // You're not quite done yet. Get back to work! + + Objectives.Add(new KillObjective(12, new[] { typeof(Ratman) }, "ratmen")); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class MougGuurMustDie : MLQuest + { + public MougGuurMustDie() + { + Activated = true; + Title = 1072368; // Moug-Guur Must Die + Description = + 1072561; // You there! Yes, you. Kill Moug-Guur, the leader of the orcs in this depressing place, and I'll make it worth your while. + RefusalMessage = 1072571; // Fine. It's no skin off my teeth. + InProgressMessage = 1072572; // Small words. Kill Moug-Guur. Go. Now! + CompletionMessage = + 1072573; // You're better than I thought you'd be. Not particularly bad, but not entirely inept. + + Objectives.Add( + new KillObjective(1, new[] { typeof(MougGuur) }, "Moug-Guur", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.BagOfTreasure); + } + + public override Type NextQuest => typeof(LeaderOfThePack); + } + + public class LeaderOfThePack : MLQuest + { + public LeaderOfThePack() + { + Activated = true; + Title = 1072560; // Leader of the Pack + Description = + 1072574; // Well now that Moug-Guur is no more -- and I can't say I'm weeping for his demise -- it's time for the ratmen to experience a similar loss of leadership. Slay Chiikkaha. In return, I'll satisfy your greed temporarily. + RefusalMessage = + 1072575; // Alright, if you'd rather not, then run along and do whatever worthless things you do when I'm not giving you direction. + InProgressMessage = + 1072576; // How difficult is this? The rats live in the tunnels. Go into the tunnels and find the biggest, meanest rat and execute him. Loitering around here won't get the task done. + CompletionMessage = 1072577; // It's about time! Could you have taken longer? + + Objectives.Add(new KillObjective(1, new[] { typeof(Chiikkaha) }, "Chiikkaha", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.BagOfTreasure); + } + + public override Type NextQuest => typeof(SayonaraSzavetra); + public override bool IsChainTriggered => true; + } + + public class SayonaraSzavetra : MLQuest + { + public SayonaraSzavetra() + { + Activated = true; + Title = 1072375; // Sayonara, Szavetra + Description = + 1072578; // Hmm, maybe you aren't entirely worthless. I suspect a demoness of Szavetra's calibre will tear you apart ... We might as well find out. Kill the succubus, yada yada, and you'll be richly rewarded. + RefusalMessage = 1072579; // Hah! I knew you couldn't handle it. + InProgressMessage = + 1072581; // Hahahaha! I can see the fear in your eyes. Pathetic. Szavetra is waiting for you. + CompletionMessage = + 1072582; // Amazing! Simply astonishing ... you survived. Well, I supposed I should indulge your avarice with a reward. + + Objectives.Add(new KillObjective(1, new[] { typeof(Szavetra) }, "Szavetra", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.Strongbox); + } + + public override bool IsChainTriggered => true; + } + + public class TappingTheKeg : MLQuest + { + public TappingTheKeg() + { + Activated = true; + HasRestartDelay = true; + Title = 1074037; // Tapping the Keg + Description = + 1074131; // I have acquired a barrel of human brewed beer. I am loathe to drink it, but how else to prove how inferior it is? I suppose I shall need a barrel tap to drink. Go, bring me a barrel tap quickly, so I might get this over with. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(BarrelTap), 1024100)); // barrel tap + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class WaitingToBeFilled : MLQuest + { + public WaitingToBeFilled() + { + Activated = true; + HasRestartDelay = true; + Title = 1074036; // Waiting to be Filled + Description = + 1074130; // The only good thing I can say about human made bottles is that they are empty and may yet still be filled with elven wine. Go now, fetch a number of empty bottles so that I might save them from the fate of carrying human-made wine. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(20, typeof(Bottle), 1023854)); // empty bottle + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class BreezesSong : MLQuest + { + public BreezesSong() + { + Activated = true; + HasRestartDelay = true; + Title = 1074052; // Breeze's Song + Description = + 1074146; // I understand humans cruely enslave the very wind to their selfish whims! Fancy wind chimes, what a monstrous idea! You must bring me proof of this terrible depredation - hurry, bring me wind chimes! + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074064; // Hurry up! I don't have all day to wait for you to bring what I desire! + CompletionMessage = + 1074065; // These human made goods are laughable! It offends so -- I must show you what elven skill is capable of! + + Objectives.Add(new CollectObjective(10, typeof(FancyWindChimes), 1030291)); // fancy wind chimes + + Rewards.Add(ItemReward.TinkerSatchel); + } + } + + public class ProofOfTheDeed : MLQuest + { + public ProofOfTheDeed() + { + Activated = true; + Title = 1072339; // Proof of the Deed + Description = + 1072340; // These human vermin must be erradicated! They despoil fair Sosaria with their every footfall upon her soil, every exhalation of breath upon her pristine air. Prove yourself an ally of Sosaria and bring me 20 human ears as proof of your devotion to our cause. + RefusalMessage = + 1072342; // Do you find the task distasteful? Are you too weak to shoulder the duty of cleansing Sosaria? So be it. + InProgressMessage = + 1072343; // Well, where is the proof of your deed? I will honor your actions when you have brought me the ears of the human scum. + CompletionMessage = + 1072344; // Ah, well done. You have chosen the path of duty and fulfilled your task with honor. + + Objectives.Add(new CollectObjective(20, typeof(SeveredHumanEars), 1032591)); // severed human ears + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class Marauders : MLQuest + { + public Marauders() + { + Activated = true; + Title = 1072374; // Marauders + Description = + 1072686; // What a miserable place we live in. Look around you at the changes we've wrought. The trees are sprouting leaves once more and the grass is reclaiming the blood-soaked soil. Who would have imagined we'd find ourselves here? Our "neighbors" are anything but friendly and those ogres are the worst of the lot. Maybe you'd be interested in helping our community by disposing of some of our least amiable neighbors? + RefusalMessage = 1072687; // I quite understand your reluctance. If you reconsider, I'll be here. + InProgressMessage = 1072688; // You can't miss those ogres, they're huge and just outside the gates here. + + Objectives.Add(new KillObjective(10, new[] { typeof(Ogre) }, "ogres", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.BagOfTreasure); + } + + public override Type NextQuest => typeof(TheBrainsOfTheOperation); + } + + public class TheBrainsOfTheOperation : MLQuest + { + public TheBrainsOfTheOperation() + { + Activated = true; + Title = 1072692; // The Brains of the Operation + Description = + 1072707; // *sigh* We have so much to do to clean this area up. Even the fine work you did on those ogres didn't have much of an impact on the community. It's the ogre lords that direct the actions of the other ogres, let's strike at the leaders and perhaps that will thwart the miserable curs. + RefusalMessage = 1072708; // Reluctance doesn't become a hero like you. But, as you wish. + InProgressMessage = + 1072709; // Ogre Lords are pretty easy to recognize. They're the ones ordering the other ogres about in a lordly manner. Striking down their leadership will throw the ogres into confusion and dismay! + + Objectives.Add(new KillObjective(10, new[] { typeof(OgreLord) }, "ogre lords", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + + public override Type NextQuest => typeof(TheBrawn); + public override bool IsChainTriggered => true; + } + + public class TheBrawn : MLQuest + { + public TheBrawn() + { + Activated = true; + Title = 1072693; // The Brawn + Description = + 1072710; // Inconceiveable! We've learned that the ogre leadership has recruited some heavy-duty guards to their cause. I've never personally fought a cyclopian warrior, but I'm sure you could easily best a few and report back how much trouble they'll cause to our growing community? + RefusalMessage = 1072711; // Oh, I see. *sigh* Perhaps I overestimated your abilities. + InProgressMessage = 1072712; // Make sure you fully assess all of the cyclopian tactical abilities! + + Objectives.Add(new KillObjective(6, new[] { typeof(Cyclops) }, "cyclops", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + + public override Type NextQuest => typeof(TheBiggerTheyAre); + public override bool IsChainTriggered => true; + } + + public class TheBiggerTheyAre : MLQuest + { + public TheBiggerTheyAre() + { + Activated = true; + Title = 1072694; // The Bigger They Are ... + Description = + 1072713; // The ogre insurgency has taken a turn for the worse! I've just been advised that the titans have concluded their discussions with the ogres and they've allied. We have virtually no information about titans. Engage them and appraise their mettle. + RefusalMessage = + 1072714; // Certainly. You've done enough to merit a breather. When you're ready for more, report back to me. + InProgressMessage = + 1072715; // Those titans don't skulk very well. You should be able to track them easily ... their footsteps are easily the largest around. + + Objectives.Add(new KillObjective(3, new[] { typeof(Titan) }, "titans", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.LargeBagOfTreasure); + } + + public override bool IsChainTriggered => true; + } + + public class TroubleOnTheWing : MLQuest + { + public TroubleOnTheWing() + { + Activated = true; + Title = 1072371; // Trouble on the Wing + Description = + 1072593; // Those gargoyles need to get knocked down a peg or two, if you ask me. They're always flying over here and lobbing things at us. What a nuisance. Drop a dozen of them for me, would you? + RefusalMessage = 1072594; // Don't tell me you're a gargoyle sympathizer? *spits* + InProgressMessage = + 1072595; // Those blasted gargoyles hang around the old tower. That's the best place to hunt them down. + + Objectives.Add(new KillObjective(12, new[] { typeof(Gargoyle) }, "gargoyles", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class BrotherlyLove : MLQuest + { + public BrotherlyLove() + { + Activated = true; + OneTimeOnly = true; + Title = 1072369; // Brotherly Love + Description = + 1072585; // *looks around nervously* Do you travel to The Heartwood? I have an urgent letter that must be delivered there in the next 30 minutes -- to Ahie the Cloth Weaver. Will you undertake this journey? + RefusalMessage = 1072587; // *looks disappointed* Let me know if you change your mind. + InProgressMessage = + 1072588; // You haven't lost the letter have you? It must be delivered to Ahie directly. Give it into no other hands. + CompletionMessage = 1074579; // Yes, can I help you? + CompletionNotice = CompletionNoticeShort; + + Objectives.Add(new DeliverObjective(typeof(APersonalLetterAddressedToAhie), 1, "letter", typeof(Ahie))); + + Rewards.Add(ItemReward.BagOfTrinkets); + } + } + + public class CommonBrigands : MLQuest + { + public CommonBrigands() + { + Activated = true; + Title = 1073082; // Common Brigands + Description = + 1073572; // Thank goodness, a hero like you has arrived! Brigands have descended upon this area like locusts, stealing and looting where ever they go. We need someone to put these vile curs where they belong -- in their graves. Are you up to the task? + RefusalMessage = 1073580; // I hope you'll reconsider. Until then, farwell. + InProgressMessage = 1073592; // The Brigands still plague us. Have you killed 20 of their number?
+ + Objectives.Add(new KillObjective(20, new[] { typeof(Brigand) }, 1074894)); // Common brigands + + Rewards.Add(ItemReward.BagOfTreasure); + } + } + + #endregion + + #region Mobiles + + [QuesterName("Beotham (Sanctuary)")] + public class Beotham : BaseCreature + { + [Constructible] + public Beotham() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the bowcrafter"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x901)); + AddItem(new ShortPants(0x522)); + AddItem(new FancyShirt(0x515)); + + Item item; + + item = new LeafGloves(); + item.Hue = 0x901; + AddItem(item); + } + + public Beotham(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Beotham"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074187, // Want a job? + 1074184 // Come here, I have work for you. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Danoel (Sanctuary)")] + public class Danoel : BaseCreature + { + [Constructible] + public Danoel() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the metal weaver"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x901)); + AddItem(new ElvenPants(0x386)); + AddItem(new ElvenShirt(0x75F)); + AddItem(new FullApron(0x1BB)); + AddItem(new RoyalCirclet()); + AddItem(new SmithHammer()); + } + + public Danoel(Serial serial) + : base(serial) + { + } + // TODO: Add quests: Spring Cleaning + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Danoel"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074197); // Pardon me, but if you could spare some time I�d greatly appreciate it. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Tallinin (Sanctuary)")] + public class Tallinin : BaseCreature + { + [Constructible] + public Tallinin() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the cloth weaver"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x901)); + AddItem(new Tunic(0x37)); + AddItem(new Cloak(0x735)); + } + + public Tallinin(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Tallinin"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074188, // Weakling! You are not up to the task I have. + 1074211 // I could use some help. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Tiana (Sanctuary)")] + public class Tiana : BaseCreature + { + [Constructible] + public Tiana() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the guard"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots()); + AddItem(new HidePants()); + AddItem(new HideFemaleChest()); + AddItem(new HidePauldrons()); + + Item item; + + item = new WoodlandBelt(); + item.Hue = 0x673; + AddItem(item); + + item = new RavenHelm(); + item.Hue = 0x443; + AddItem(item); + } + + public Tiana(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Tiana"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074214, // Knave! Come here right now! + 1074218 // Hey!� I want to talk to you, now. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Oolua (Sanctuary)")] + public class LorekeeperOolua : BaseCreature + { + [Constructible] + public LorekeeperOolua() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenBoots(0x75A)); + AddItem(new Skirt(Utility.RandomBrightHue())); + AddItem(new FancyShirt(0x742)); + AddItem(new Cloak(0x1BB)); + AddItem(new WildStaff()); + } + + public LorekeeperOolua(Serial serial) + : base(serial) + { + } + // TODO: Add quest Dreadhorn + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Lorekeeper Oolua"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074187); // Want a job? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Rollarn (Sanctuary)")] + public class LorekeeperRollarn : BaseCreature + { + [Constructible] + public LorekeeperRollarn() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x1BB)); + AddItem(new Cloak(0x296)); + AddItem(new Circlet()); + AddItem(new LeafChest()); + + Item item; + + item = new LeafLegs(); + item.Hue = 0x71A; + AddItem(item); + } + + public LorekeeperRollarn(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Lorekeeper Rollarn"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074196, // Excuse me! I�m sorry to interrupt but I urgently need some assistance. + 1074197 // Pardon me, but if you could spare some time I�d greatly appreciate it. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Dallid (Sanctuary)")] + public class Dallid : BaseCreature + { + [Constructible] + public Dallid() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the cook"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Boots(0x901)); + AddItem(new ShortPants(0x73C)); + AddItem(new Shirt(0x744)); + AddItem(new FullApron(0x1BE)); + AddItem(new Cleaver()); + } + + public Dallid(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Dallid"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074185, // Hey you! Want to help me out? + 1074195 // You there, in the stupid hat! Come here. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Canir (Sanctuary)")] + public class Canir : BaseCreature + { + [Constructible] + public Canir() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the thaumaturgist"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Sandals(0x1BB)); + AddItem(new FemaleElvenRobe(0x5A7)); + AddItem(new GemmedCirclet()); + AddItem(new MagicWand()); + } + + public Canir(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Canir"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074193, // You there! Yes you. Stop looking about like a toadie and come here. + 1074186 // Come here, I have a task. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Yellienir : BaseCreature + { + [Constructible] + public Yellienir() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the bark weaver"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + AddItem(new ElvenBoots()); + AddItem(new LeafTonlet()); + AddItem(new FemaleLeafChest()); + AddItem(new LeafArms()); + AddItem(new Cloak(0x3B2)); + } + + public Yellienir(Serial serial) + : base(serial) + { + } + + public override string DefaultName => "Yellienir"; + public override bool IsInvulnerable => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Elder Onallan (Sanctuary)")] + public class ElderOnallan : BaseCreature + { + [Constructible] + public ElderOnallan() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the wise"; + Race = Race.Elf; + BodyValue = 0x25D; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new Shoes(0x729)); + AddItem(new WildStaff()); + AddItem(new Cloak(0x64E)); + } + + public ElderOnallan(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Elder Onallan"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074217, // I want to make you an offer you�d be a fool to �refuse. + 1074218 // Hey!� I want to talk to you, now. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/Spellweaving.cs b/Scripts/Engines/MLQuests/Definitions/Spellweaving.cs index 9b538f41d..f4df926c5 100644 --- a/Scripts/Engines/MLQuests/Definitions/Spellweaving.cs +++ b/Scripts/Engines/MLQuests/Definitions/Spellweaving.cs @@ -1,685 +1,727 @@ using System; using Server.Engines.MLQuests.Objectives; -using Server.Items; using Server.Engines.MLQuests.Rewards; +using Server.Items; using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - public static class Spellweaving - { - public static void AwardTo( PlayerMobile pm ) - { - if ( pm == null ) - return; - - MLQuestContext context = MLQuestSystem.GetOrCreateContext( pm ); - - if ( !context.Spellweaving ) - { - context.Spellweaving = true; - - Effects.SendLocationParticles( EffectItem.Create( pm.Location, pm.Map, EffectItem.DefaultDuration ), 0, 0, 0, 0, 0, 5060, 0 ); - Effects.PlaySound( pm.Location, pm.Map, 0x243 ); - - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( pm.X - 6, pm.Y - 6, pm.Z + 15 ), pm.Map ), pm, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( pm.X - 4, pm.Y - 6, pm.Z + 15 ), pm.Map ), pm, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( pm.X - 6, pm.Y - 4, pm.Z + 15 ), pm.Map ), pm, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - - Effects.SendTargetParticles( pm, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); - } - } - } - - #region Patience - - public class Patience : MLQuest - { - public override Type NextQuest => typeof( NeedsOfTheManyHeartwood1 ); - - public Patience() - { - Activated = true; - Title = 1072753; // Patience - Description = 1072762; // Learning to weave spells and control the forces of nature requires sacrifice, discipline, focus, and an unwavering dedication to Sosaria herself. We do not teach the unworthy. They do not comprehend the lessons nor the dedication required. If you would walk the path of the Arcanist, then you must do as I require without hesitation or question. Your first task is to gather miniature mushrooms ... 20 of them from the branches of our mighty home. I give you one hour to complete the task. - RefusalMessage = 1072767; // *nods* Not everyone has the temperment to undertake the way of the Arcanist. - InProgressMessage = 1072774; // The mushrooms I seek can be found growing here in The Heartwood. Seek them out and gather them. You are running out of time. - CompletionMessage = 1074166; // Have you gathered the mushrooms? - - Objectives.Add( new TimedCollectObjective( TimeSpan.FromHours( 1 ), 20, typeof( MiniatureMushroom ), "miniature mushrooms" ) ); - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Aeluva" ), new Point3D( 7064, 349, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Aeluva" ), new Point3D( 7064, 349, 0 ), Map.Trammel ); - - // Split up to prevent stacking on the spawner - PutSpawner( new Spawner( 20, TimeSpan.FromSeconds( 15 ), TimeSpan.FromSeconds( 30 ), 0, 30, "MiniatureMushroom" ), new Point3D( 7015, 366, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 20, TimeSpan.FromSeconds( 15 ), TimeSpan.FromSeconds( 30 ), 0, 30, "MiniatureMushroom" ), new Point3D( 7015, 366, 0 ), Map.Trammel ); - - PutSpawner( new Spawner( 5, TimeSpan.FromSeconds( 15 ), TimeSpan.FromSeconds( 30 ), 0, 20, "MiniatureMushroom" ), new Point3D( 7081, 373, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 5, TimeSpan.FromSeconds( 15 ), TimeSpan.FromSeconds( 30 ), 0, 20, "MiniatureMushroom" ), new Point3D( 7081, 373, 0 ), Map.Trammel ); - - PutSpawner( new Spawner( 15, TimeSpan.FromSeconds( 15 ), TimeSpan.FromSeconds( 30 ), 0, 20, "MiniatureMushroom" ), new Point3D( 7052, 414, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 15, TimeSpan.FromSeconds( 15 ), TimeSpan.FromSeconds( 30 ), 0, 20, "MiniatureMushroom" ), new Point3D( 7052, 414, 0 ), Map.Trammel ); - } - } - - public class NeedsOfTheManyHeartwood1 : MLQuest - { - public override Type NextQuest => typeof( NeedsOfTheManyHeartwood2 ); - public override bool IsChainTriggered => true; - - public NeedsOfTheManyHeartwood1() - { - Activated = true; - Title = 1072797; // Needs of the Many - The Heartwood - Description = 1072763; // The way of the Arcanist involves cooperation with others and a strong commitment to the community of your people. We have run low on the cotton we use to pack wounds and our people have need. Bring 10 bales of cotton to me. - RefusalMessage = 1072768; // You endanger your progress along the path with your unwillingness. - InProgressMessage = 1072775; // I care not where you acquire the cotton, merely that you provide it. - CompletionMessage = 1074110; // Well, where are the cotton bales? - - Objectives.Add( new CollectObjective( 10, typeof( Cotton ), 1023577 ) ); // bale of cotton - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - } - - public class NeedsOfTheManyHeartwood2 : MLQuest - { - public override Type NextQuest => typeof( MakingAContributionHeartwood ); - public override bool IsChainTriggered => true; - - public NeedsOfTheManyHeartwood2() - { - Activated = true; - Title = 1072797; // Needs of the Many - The Heartwood - Description = 1072764; // We must look to the defense of our people! Bring boards for new arrows. - RefusalMessage = 1072769; // The people have need of these items. You are proving yourself inadequate to the demands of a member of this community. - InProgressMessage = 1072776; // The requirements are simple -- 250 boards. - CompletionMessage = 1074152; // Well, where are the boards? - - Objectives.Add( new CollectObjective( 250, typeof( Board ), 1027127 ) ); // board - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - } - - public class MakingAContributionHeartwood : MLQuest - { - public override Type NextQuest => typeof( UnnaturalCreations ); - public override bool IsChainTriggered => true; - - public MakingAContributionHeartwood() - { - Activated = true; - Title = 1072798; // Making a Contribution - The Heartwood - Description = 1072765; // With health and defense assured, we need look to the need of the community for food and drink. We will feast on fish steaks, sweets, and wine. You will supply the ingredients, the cooks will prepare the meal. As a Arcanist relies upon others to build focus and lend their power to her workings, the community needs the effort of all to survive. - RefusalMessage = 1072770; // Do not falter now. You have begun to show promise. - InProgressMessage = 1072777; // Where are the items you've been tasked to supply for the feast? - CompletionMessage = 1074158; // Ah good, you're back. We're eager for the feast. - - Objectives.Add( new CollectObjective( 1, typeof( SackFlour ), 1024153 ) ); // sack of flour - Objectives.Add( new CollectObjective( 10, typeof( JarHoney ), 1022540 ) ); // jar of honey - Objectives.Add( new CollectObjective( 20, typeof( FishSteak ), 1022427 ) ); // fish steak - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - } - - public class UnnaturalCreations : MLQuest - { - public override bool IsChainTriggered => true; - - public UnnaturalCreations() - { - Activated = true; - Title = 1072758; // Unnatural Creations - Description = 1072780; // You have proven your desire to contribute to the community and serve the people. Now you must demonstrate your willingness to defend Sosaria from the greatest blight that plagues her. Unnatural creatures, brought to a sort of perverted life, despoil our fair world. Destroy them -- 5 Exodus Overseers and 2 Exodus Minions. - RefusalMessage = 1072771; // You must serve Sosaria with all your heart and strength. Your unwillingness does not reflect favorably upon you. - InProgressMessage = 1072779; // Every moment you procrastinate, these unnatural creatures damage Sosaria. - CompletionMessage = 1074167; // Well done! Well done, indeed. You are worthy to become an arcanist! - - Objectives.Add( new KillObjective( 5, new[] { typeof( ExodusOverseer ) }, "Exodus Overseers" ) ); - Objectives.Add( new KillObjective( 2, new[] { typeof( ExodusMinion ) }, "Exodus Minions" ) ); - - Rewards.Add( new ItemReward( 1031601, typeof( ArcaneCircleScroll ) ) ); // Arcane Circle - Rewards.Add( new ItemReward( 1031600, typeof( SpellweavingBook ) ) ); // Spellweaving Spellbook - Rewards.Add( new ItemReward( 1031602, typeof( GiftOfRenewalScroll ) ) ); // Gift of Renewal - } - - public override void GetRewards( MLQuestInstance instance ) - { - Spellweaving.AwardTo( instance.Player ); - base.GetRewards( instance ); - } - } - - #endregion - - #region Discipline - - public class Discipline : MLQuest - { - public override Type NextQuest => typeof( NeedsOfTheManySanctuary ); - - public Discipline() - { - Activated = true; - Title = 1072752; // Discipline - Description = 1072761; // Learning to weave spells and control the forces of nature requires sacrifice, discipline, focus, and an unwavering dedication to Sosaria herself. We do not teach the unworthy. They do not comprehend the lessons nor the dedication required. If you would walk the path of the Arcanist, then you must do as I require without hesitation or question. Your first task is to rid our home of rats ... 50 of them in the next hour. - RefusalMessage = 1072767; // *nods* Not everyone has the temperament to undertake the way of the Arcanist. - InProgressMessage = 1072773; // You waste my time. The task is simple. Kill 50 rats in an hour. - // No completion message - - Objectives.Add( new TimedKillObjective( TimeSpan.FromHours( 1 ), 50, new[] { typeof( Rat ) }, "rats", new QuestArea( 1074807, "Sanctuary" ) ) ); // Sanctuary - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Koole" ), new Point3D( 6257, 110, -10 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "Koole" ), new Point3D( 6257, 110, -10 ), Map.Trammel ); - } - } - - public class NeedsOfTheManySanctuary : MLQuest - { - public override Type NextQuest => typeof( MakingAContributionSanctuary ); - public override bool IsChainTriggered => true; - - public NeedsOfTheManySanctuary() - { - Activated = true; - Title = 1072754; // Needs of the Many - Sanctuary - Description = 1072763; // The way of the Arcanist involves cooperation with others and a strong commitment to the community of your people. We have run low on the cotton we use to pack wounds and our people have need. Bring 10 bales of cotton to me. - RefusalMessage = 1072768; // You endanger your progress along the path with your unwillingness. - InProgressMessage = 1072775; // I care not where you acquire the cotton, merely that you provide it. - CompletionMessage = 1074110; // Well, where are the cotton bales? - - Objectives.Add( new CollectObjective( 10, typeof( Cotton ), 1023577 ) ); // bale of cotton - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - } - - public class MakingAContributionSanctuary : MLQuest - { - public override Type NextQuest => typeof( SuppliesForSanctuary ); - public override bool IsChainTriggered => true; - - public MakingAContributionSanctuary() - { - Activated = true; - Title = 1072755; // Making a Contribution - Sanctuary - Description = 1072764; // We must look to the defense of our people! Bring boards for new arrows. - RefusalMessage = 1072769; // The people have need of these items. You are proving yourself inadequate to the demands of a member of this community. - InProgressMessage = 1072776; // The requirements are simple -- 250 boards. - CompletionMessage = 1074152; // Well, where are the boards? - - Objectives.Add( new CollectObjective( 250, typeof( Board ), 1027127 ) ); // board - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - } - - public class SuppliesForSanctuary : MLQuest - { - public override Type NextQuest => typeof( TheHumanBlight ); - public override bool IsChainTriggered => true; - - public SuppliesForSanctuary() - { - Activated = true; - Title = 1072756; // Supplies for Sanctuary - Description = 1072765; // With health and defense assured, we need look to the need of the community for food and drink. We will feast on fish steaks, sweets, and wine. You will supply the ingredients, the cooks will prepare the meal. As a Arcanist relies upon others to build focus and lend their power to her workings, the community needs the effort of all to survive. - RefusalMessage = 1072770; // Do not falter now. You have begun to show promise. - InProgressMessage = 1072777; // Where are the items you've been tasked to supply for the feast? - CompletionMessage = 1074158; // Ah good, you're back. We're eager for the feast. - - Objectives.Add( new CollectObjective( 1, typeof( SackFlour ), 1024153 ) ); // sack of flour - Objectives.Add( new CollectObjective( 10, typeof( JarHoney ), 1022540 ) ); // jar of honey - Objectives.Add( new CollectObjective( 20, typeof( FishSteak ), 1022427 ) ); // fish steak - - Rewards.Add( new DummyReward( 1074872 ) ); // The opportunity to learn the ways of the Arcanist. - } - } - - public class TheHumanBlight : MLQuest - { - public override bool IsChainTriggered => true; - - public TheHumanBlight() - { - Activated = true; - Title = 1072757; // The Human Blight - Description = 1072766; // You have proven your desire to contribute to the community and serve the people. Now you must demonstrate your willingness to defend Sosaria from the greatest blight that plagues her. The human vermin that have spread as a disease, despoiling the land are the greatest blight we face. Kill humans and return to me the proof of your actions. Bring me 30 human ears. - RefusalMessage = 1072771; // You must serve Sosaria with all your heart and strength. Your unwillingness does not reflect favorably upon you. - InProgressMessage = 1072778; // Why do you delay? The human blight must be averted. - CompletionMessage = 1074160; // I will take the ears you have collected now. Hand them here. - - Objectives.Add( new CollectObjective( 30, typeof( SeveredHumanEars ), 1032591 ) ); // severed human ears - - Rewards.Add( new ItemReward( 1031601, typeof( ArcaneCircleScroll ) ) ); // Arcane Circle - Rewards.Add( new ItemReward( 1031600, typeof( SpellweavingBook ) ) ); // Spellweaving Spellbook - Rewards.Add( new ItemReward( 1031602, typeof( GiftOfRenewalScroll ) ) ); // Gift of Renewal - } - - public override void GetRewards( MLQuestInstance instance ) - { - Spellweaving.AwardTo( instance.Player ); - base.GetRewards( instance ); - } - } - - #endregion - - #region Friend of the Fey - - public class FriendOfTheFey : MLQuest - { - public override Type NextQuest => typeof( TokenOfFriendship ); - - public FriendOfTheFey() - { - Activated = true; - Title = 1074284; // Friend of the Fey - Description = 1074286; // The children of Sosaria understand the dedication and committment of an arcanist -- and will, from time to time offer their friendship. If you would forge such a bond, first seek out a goodwill offering to present. Pixies enjoy sweets and pretty things. - RefusalMessage = 1074288; // There's always time to make new friends. - InProgressMessage = 1074290; // I think honey and some sparkly beads would please a pixie. - CompletionMessage = 1074292; // What have we here? Oh yes, gifts for a pixie. - - Objectives.Add( new CollectObjective( 1, typeof( Beads ), 1024235 ) ); // beads - Objectives.Add( new CollectObjective( 1, typeof( JarHoney ), 1022540 ) ); // jar of honey - - Rewards.Add( new DummyReward( 1074874 ) ); // The opportunity to prove yourself worthy of learning to Summon Fey. (Sufficient spellweaving skill is required to cast the spell) - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Synaeva" ), new Point3D( 7064, 350, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Synaeva" ), new Point3D( 7064, 350, 0 ), Map.Trammel ); - } - } - - public class TokenOfFriendship : MLQuest - { - public override Type NextQuest => typeof( Alliance ); - public override bool IsChainTriggered => true; - - public TokenOfFriendship() - { - Activated = true; - Title = 1074293; // Token of Friendship - Description = 1074297; // I've wrapped your gift suitably to present to a pixie of discriminating taste. Seek out Arielle and give her your offering. - RefusalMessage = 1074310; // I'll hold onto this gift in case you change your mind. - InProgressMessage = 1074315; // Arielle wanders quite a bit, so I'm not sure exactly where to find her. I'm sure she's going to love your gift. - CompletionMessage = 1074319; // *giggle* Oooh! For me? - - Objectives.Add( new DeliverObjective( typeof( GiftForArielle ), 1, "gift for Arielle", typeof( Arielle ) ) ); - - Rewards.Add( new DummyReward( 1074874 ) ); // The opportunity to prove yourself worthy of learning to Summon Fey. (Sufficient spellweaving skill is required to cast the spell) - } - } - - public class Alliance : MLQuest - { - public override bool IsChainTriggered => true; - - public Alliance() - { - Activated = true; - Title = 1074294; // Alliance - Description = 1074298; // *giggle* Mean reapers make pixies unhappy. *light-hearted giggle* You could fix them! - RefusalMessage = 1074311; // *giggle* Okies! - InProgressMessage = 1074316; // Mean reapers are all around trees! *giggle* You fix them up, please. - CompletionNotice = CompletionNoticeShortReturn; - - Objectives.Add( new KillObjective( 20, new[] { typeof( Reaper ) }, "reapers" ) ); - - Rewards.Add( new ItemReward( 1031607, typeof( SummonFeyScroll ) ) ); // Summon Fey - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.PlayerContext.SummonFey = true; - instance.Player.SendLocalizedMessage( 1074320, "", 0x2A ); // *giggle* Mean reapers got fixed! Pixie friend now! *giggle* When mean thingies bother you, a brave pixie will help. - - base.GetRewards( instance ); - } - } - - #endregion - - #region Fiendish Friends - - public class FiendishFriends : MLQuest - { - public override Type NextQuest => typeof( CrackingTheWhipI ); - - public FiendishFriends() - { - Activated = true; - Title = 1074283; // Fiendish Friends - Description = 1074285; // It is true that a skilled arcanist can summon and dominate an imp to serve at their pleasure. To do such at thing though, you must master the miserable little fiends utterly by demonstrating your superiority. Rough them up some -- kill a few. That will do the trick. - RefusalMessage = 1074287; // You're probably right. They're not worth the effort. - InProgressMessage = 1074289; // Surely you're not having difficulties swatting down those annoying pests? - // TODO: Verify - CompletionMessage = 1074291; // Hah! You showed them! - - Objectives.Add( new KillObjective( 50, new[] { typeof( Imp ) }, "imps" ) ); - - Rewards.Add( new DummyReward( 1074873 ) ); // The opportunity to prove yourself worthy of learning to Summon Fiends. (Sufficient spellweaving skill is required to cast the spell) - } - - public override void Generate() - { - base.Generate(); - - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "ElderBrae" ), new Point3D( 6266, 124, 0 ), Map.Felucca ); - PutSpawner( new Spawner( 1, 5, 10, 0, 0, "ElderBrae" ), new Point3D( 6266, 124, 0 ), Map.Trammel ); - } - } - - // TODO: Verify - public class CrackingTheWhipI : MLQuest - { - public override Type NextQuest => typeof( CrackingTheWhipII ); - public override bool IsChainTriggered => true; - - public CrackingTheWhipI() - { - Activated = true; - Title = 1074295; // Cracking the Whip - Description = 1074300; // Now that you've shown those mini pests your might, you should collect suitable implements to use to train your summoned pet. I suggest a stout whip. - RefusalMessage = 1074313; // Heh. Changed your mind, eh? - InProgressMessage = 1074317; // Well, hurry up. If you don't get a whip how do you expect to control the little devil? - CompletionMessage = 1074321; // That's a well-made whip. No imp will ignore the sting of that lash. - - Objectives.Add( new CollectObjective( 1, typeof( StoutWhip ), "Stout Whip" ) ); - - Rewards.Add( new DummyReward( 1074873 ) ); // The opportunity to prove yourself worthy of learning to Summon Fiends. (Sufficient spellweaving skill is required to cast the spell) - } - } - - // TODO: Verify - public class CrackingTheWhipII : MLQuest - { - public override bool IsChainTriggered => true; - - public CrackingTheWhipII() - { - Activated = true; - Title = 1074295; // Cracking the Whip - Description = 1074302; // Now you just need to make the little buggers fear you -- if you can slay an arcane daemon, you'll earn their subservience. - RefusalMessage = 1074314; // If you're not up for it, so be it. - InProgressMessage = 1074318; // You need to vanquish an arcane daemon before the imps will fear you properly. - - Objectives.Add( new KillObjective( 1, new[] { typeof( ArcaneDaemon ) }, 1029733 ) ); // arcane demon - - Rewards.Add( new ItemReward( 1031608, typeof( SummonFiendScroll ) ) ); // Summon Fiend - } - - public override void GetRewards( MLQuestInstance instance ) - { - instance.PlayerContext.SummonFiend = true; - instance.Player.SendLocalizedMessage( 1074322, "", 0x2A ); // You've demonstrated your strength, got a means of control, and taught the imps to fear you. You're ready now to summon them. - - base.GetRewards( instance ); - } - } - - #endregion - - #region Mobiles - - [QuesterName( "Aeluva (The Heartwood)" )] - public class Aeluva : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Aeluva"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - /* - * 1074206 - Excuse me please traveler, might I have a little of your time? - * 1074207 - Good day to you friend! Allow me to offer you a fabulous opportunity!  Thrills and adventure await! - */ - MLQuestSystem.Tell( this, pm, Utility.Random( 1074206, 2 ) ); - } - - [Constructible] - public Aeluva() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0 ) - { - Title = "the arcanist"; - Race = Race.Elf; - Female = true; - Body = 606; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new ElvenShirt() ); - AddItem( new Kilt( Utility.RandomNondyedHue() ) ); // Note: OSI hue = 0x1516, typo? - AddItem( new ElvenBoots() ); - AddItem( new Circlet() ); - } - - public Aeluva( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Koole (Sanctuary)" )] - public class Koole : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Koole"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074186, // Come here, I have a task. - 1074218 // Hey! I want to talk to you, now. - ) ); - } - - [Constructible] - public Koole() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0 ) - { - Title = "the arcanist"; - Race = Race.Elf; - Body = 605; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - Item item; - - item = new LeafChest(); - item.Hue = 443; - AddItem( item ); - - item = new LeafArms(); - item.Hue = 443; - AddItem( item ); - - AddItem( new LeafTonlet() ); - AddItem( new ThighBoots( Utility.RandomAnimalHue() ) ); - AddItem( new RoyalCirclet() ); - } - - public Koole( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Synaeva (The Heartwood)" )] - public class Synaeva : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Synaeva"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074223 ); // Have you done it yet?  Oh, I haven’t told you, have I? - } - - [Constructible] - public Synaeva() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0 ) - { - Title = "the arcanist"; - Race = Race.Elf; - Female = true; - Body = 606; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - Item item = new RavenHelm(); - item.Hue = Utility.RandomGreenHue(); - AddItem( item ); - - AddItem( new FemaleLeafChest() ); - AddItem( new LeafArms() ); - AddItem( new LeafTonlet() ); - AddItem( new ElvenBoots() ); - AddItem( new WildStaff() ); - } - - public Synaeva( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [QuesterName( "Elder Brae (Sanctuary)" )] - public class ElderBrae : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Elder Brae"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, Utility.RandomList( - 1074215, // Don’t test my patience you sniveling worm! - 1074218 // Hey!  I want to talk to you, now. - ) ); - } - - [Constructible] - public ElderBrae() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0 ) - { - Title = "the wise"; - Race = Race.Elf; - Female = true; - Body = 606; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); - - Utility.AssignRandomHair( this, true ); - - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); - - AddItem( new GemmedCirclet() ); - AddItem( new FemaleElvenRobe( Utility.RandomBrightHue() ) ); - AddItem( new ElvenBoots( Utility.RandomAnimalHue() ) ); - } - - public ElderBrae( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + public static class Spellweaving + { + public static void AwardTo(PlayerMobile pm) + { + if (pm == null) + return; + + MLQuestContext context = MLQuestSystem.GetOrCreateContext(pm); + + if (!context.Spellweaving) + { + context.Spellweaving = true; + + Effects.SendLocationParticles(EffectItem.Create(pm.Location, pm.Map, EffectItem.DefaultDuration), 0, 0, 0, 0, + 0, 5060, 0); + Effects.PlaySound(pm.Location, pm.Map, 0x243); + + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(pm.X - 6, pm.Y - 6, pm.Z + 15), pm.Map), pm, + 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(pm.X - 4, pm.Y - 6, pm.Z + 15), pm.Map), pm, + 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(pm.X - 6, pm.Y - 4, pm.Z + 15), pm.Map), pm, + 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + + Effects.SendTargetParticles(pm, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); + } + } + } + + #region Patience + + public class Patience : MLQuest + { + public Patience() + { + Activated = true; + Title = 1072753; // Patience + Description = + 1072762; // Learning to weave spells and control the forces of nature requires sacrifice, discipline, focus, and an unwavering dedication to Sosaria herself. We do not teach the unworthy. They do not comprehend the lessons nor the dedication required. If you would walk the path of the Arcanist, then you must do as I require without hesitation or question. Your first task is to gather miniature mushrooms ... 20 of them from the branches of our mighty home. I give you one hour to complete the task. + RefusalMessage = 1072767; // *nods* Not everyone has the temperment to undertake the way of the Arcanist. + InProgressMessage = + 1072774; // The mushrooms I seek can be found growing here in The Heartwood. Seek them out and gather them. You are running out of time. + CompletionMessage = 1074166; // Have you gathered the mushrooms? + + Objectives.Add(new TimedCollectObjective(TimeSpan.FromHours(1), 20, typeof(MiniatureMushroom), + "miniature mushrooms")); + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(NeedsOfTheManyHeartwood1); + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Aeluva"), new Point3D(7064, 349, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Aeluva"), new Point3D(7064, 349, 0), Map.Trammel); + + // Split up to prevent stacking on the spawner + PutSpawner(new Spawner(20, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(30), 0, 30, "MiniatureMushroom"), + new Point3D(7015, 366, 0), Map.Felucca); + PutSpawner(new Spawner(20, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(30), 0, 30, "MiniatureMushroom"), + new Point3D(7015, 366, 0), Map.Trammel); + + PutSpawner(new Spawner(5, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(30), 0, 20, "MiniatureMushroom"), + new Point3D(7081, 373, 0), Map.Felucca); + PutSpawner(new Spawner(5, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(30), 0, 20, "MiniatureMushroom"), + new Point3D(7081, 373, 0), Map.Trammel); + + PutSpawner(new Spawner(15, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(30), 0, 20, "MiniatureMushroom"), + new Point3D(7052, 414, 0), Map.Felucca); + PutSpawner(new Spawner(15, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(30), 0, 20, "MiniatureMushroom"), + new Point3D(7052, 414, 0), Map.Trammel); + } + } + + public class NeedsOfTheManyHeartwood1 : MLQuest + { + public NeedsOfTheManyHeartwood1() + { + Activated = true; + Title = 1072797; // Needs of the Many - The Heartwood + Description = + 1072763; // The way of the Arcanist involves cooperation with others and a strong commitment to the community of your people. We have run low on the cotton we use to pack wounds and our people have need. Bring 10 bales of cotton to me. + RefusalMessage = 1072768; // You endanger your progress along the path with your unwillingness. + InProgressMessage = 1072775; // I care not where you acquire the cotton, merely that you provide it. + CompletionMessage = 1074110; // Well, where are the cotton bales? + + Objectives.Add(new CollectObjective(10, typeof(Cotton), 1023577)); // bale of cotton + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(NeedsOfTheManyHeartwood2); + public override bool IsChainTriggered => true; + } + + public class NeedsOfTheManyHeartwood2 : MLQuest + { + public NeedsOfTheManyHeartwood2() + { + Activated = true; + Title = 1072797; // Needs of the Many - The Heartwood + Description = 1072764; // We must look to the defense of our people! Bring boards for new arrows. + RefusalMessage = + 1072769; // The people have need of these items. You are proving yourself inadequate to the demands of a member of this community. + InProgressMessage = 1072776; // The requirements are simple -- 250 boards. + CompletionMessage = 1074152; // Well, where are the boards? + + Objectives.Add(new CollectObjective(250, typeof(Board), 1027127)); // board + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(MakingAContributionHeartwood); + public override bool IsChainTriggered => true; + } + + public class MakingAContributionHeartwood : MLQuest + { + public MakingAContributionHeartwood() + { + Activated = true; + Title = 1072798; // Making a Contribution - The Heartwood + Description = + 1072765; // With health and defense assured, we need look to the need of the community for food and drink. We will feast on fish steaks, sweets, and wine. You will supply the ingredients, the cooks will prepare the meal. As a Arcanist relies upon others to build focus and lend their power to her workings, the community needs the effort of all to survive. + RefusalMessage = 1072770; // Do not falter now. You have begun to show promise. + InProgressMessage = 1072777; // Where are the items you've been tasked to supply for the feast? + CompletionMessage = 1074158; // Ah good, you're back. We're eager for the feast. + + Objectives.Add(new CollectObjective(1, typeof(SackFlour), 1024153)); // sack of flour + Objectives.Add(new CollectObjective(10, typeof(JarHoney), 1022540)); // jar of honey + Objectives.Add(new CollectObjective(20, typeof(FishSteak), 1022427)); // fish steak + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(UnnaturalCreations); + public override bool IsChainTriggered => true; + } + + public class UnnaturalCreations : MLQuest + { + public UnnaturalCreations() + { + Activated = true; + Title = 1072758; // Unnatural Creations + Description = + 1072780; // You have proven your desire to contribute to the community and serve the people. Now you must demonstrate your willingness to defend Sosaria from the greatest blight that plagues her. Unnatural creatures, brought to a sort of perverted life, despoil our fair world. Destroy them -- 5 Exodus Overseers and 2 Exodus Minions. + RefusalMessage = + 1072771; // You must serve Sosaria with all your heart and strength. Your unwillingness does not reflect favorably upon you. + InProgressMessage = 1072779; // Every moment you procrastinate, these unnatural creatures damage Sosaria. + CompletionMessage = 1074167; // Well done! Well done, indeed. You are worthy to become an arcanist! + + Objectives.Add(new KillObjective(5, new[] { typeof(ExodusOverseer) }, "Exodus Overseers")); + Objectives.Add(new KillObjective(2, new[] { typeof(ExodusMinion) }, "Exodus Minions")); + + Rewards.Add(new ItemReward(1031601, typeof(ArcaneCircleScroll))); // Arcane Circle + Rewards.Add(new ItemReward(1031600, typeof(SpellweavingBook))); // Spellweaving Spellbook + Rewards.Add(new ItemReward(1031602, typeof(GiftOfRenewalScroll))); // Gift of Renewal + } + + public override bool IsChainTriggered => true; + + public override void GetRewards(MLQuestInstance instance) + { + Spellweaving.AwardTo(instance.Player); + base.GetRewards(instance); + } + } + + #endregion + + #region Discipline + + public class Discipline : MLQuest + { + public Discipline() + { + Activated = true; + Title = 1072752; // Discipline + Description = + 1072761; // Learning to weave spells and control the forces of nature requires sacrifice, discipline, focus, and an unwavering dedication to Sosaria herself. We do not teach the unworthy. They do not comprehend the lessons nor the dedication required. If you would walk the path of the Arcanist, then you must do as I require without hesitation or question. Your first task is to rid our home of rats ... 50 of them in the next hour. + RefusalMessage = 1072767; // *nods* Not everyone has the temperament to undertake the way of the Arcanist. + InProgressMessage = 1072773; // You waste my time. The task is simple. Kill 50 rats in an hour. + // No completion message + + Objectives.Add(new TimedKillObjective(TimeSpan.FromHours(1), 50, new[] { typeof(Rat) }, "rats", + new QuestArea(1074807, "Sanctuary"))); // Sanctuary + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(NeedsOfTheManySanctuary); + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Koole"), new Point3D(6257, 110, -10), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "Koole"), new Point3D(6257, 110, -10), Map.Trammel); + } + } + + public class NeedsOfTheManySanctuary : MLQuest + { + public NeedsOfTheManySanctuary() + { + Activated = true; + Title = 1072754; // Needs of the Many - Sanctuary + Description = + 1072763; // The way of the Arcanist involves cooperation with others and a strong commitment to the community of your people. We have run low on the cotton we use to pack wounds and our people have need. Bring 10 bales of cotton to me. + RefusalMessage = 1072768; // You endanger your progress along the path with your unwillingness. + InProgressMessage = 1072775; // I care not where you acquire the cotton, merely that you provide it. + CompletionMessage = 1074110; // Well, where are the cotton bales? + + Objectives.Add(new CollectObjective(10, typeof(Cotton), 1023577)); // bale of cotton + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(MakingAContributionSanctuary); + public override bool IsChainTriggered => true; + } + + public class MakingAContributionSanctuary : MLQuest + { + public MakingAContributionSanctuary() + { + Activated = true; + Title = 1072755; // Making a Contribution - Sanctuary + Description = 1072764; // We must look to the defense of our people! Bring boards for new arrows. + RefusalMessage = + 1072769; // The people have need of these items. You are proving yourself inadequate to the demands of a member of this community. + InProgressMessage = 1072776; // The requirements are simple -- 250 boards. + CompletionMessage = 1074152; // Well, where are the boards? + + Objectives.Add(new CollectObjective(250, typeof(Board), 1027127)); // board + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(SuppliesForSanctuary); + public override bool IsChainTriggered => true; + } + + public class SuppliesForSanctuary : MLQuest + { + public SuppliesForSanctuary() + { + Activated = true; + Title = 1072756; // Supplies for Sanctuary + Description = + 1072765; // With health and defense assured, we need look to the need of the community for food and drink. We will feast on fish steaks, sweets, and wine. You will supply the ingredients, the cooks will prepare the meal. As a Arcanist relies upon others to build focus and lend their power to her workings, the community needs the effort of all to survive. + RefusalMessage = 1072770; // Do not falter now. You have begun to show promise. + InProgressMessage = 1072777; // Where are the items you've been tasked to supply for the feast? + CompletionMessage = 1074158; // Ah good, you're back. We're eager for the feast. + + Objectives.Add(new CollectObjective(1, typeof(SackFlour), 1024153)); // sack of flour + Objectives.Add(new CollectObjective(10, typeof(JarHoney), 1022540)); // jar of honey + Objectives.Add(new CollectObjective(20, typeof(FishSteak), 1022427)); // fish steak + + Rewards.Add(new DummyReward(1074872)); // The opportunity to learn the ways of the Arcanist. + } + + public override Type NextQuest => typeof(TheHumanBlight); + public override bool IsChainTriggered => true; + } + + public class TheHumanBlight : MLQuest + { + public TheHumanBlight() + { + Activated = true; + Title = 1072757; // The Human Blight + Description = + 1072766; // You have proven your desire to contribute to the community and serve the people. Now you must demonstrate your willingness to defend Sosaria from the greatest blight that plagues her. The human vermin that have spread as a disease, despoiling the land are the greatest blight we face. Kill humans and return to me the proof of your actions. Bring me 30 human ears. + RefusalMessage = + 1072771; // You must serve Sosaria with all your heart and strength. Your unwillingness does not reflect favorably upon you. + InProgressMessage = 1072778; // Why do you delay? The human blight must be averted. + CompletionMessage = 1074160; // I will take the ears you have collected now. Hand them here. + + Objectives.Add(new CollectObjective(30, typeof(SeveredHumanEars), 1032591)); // severed human ears + + Rewards.Add(new ItemReward(1031601, typeof(ArcaneCircleScroll))); // Arcane Circle + Rewards.Add(new ItemReward(1031600, typeof(SpellweavingBook))); // Spellweaving Spellbook + Rewards.Add(new ItemReward(1031602, typeof(GiftOfRenewalScroll))); // Gift of Renewal + } + + public override bool IsChainTriggered => true; + + public override void GetRewards(MLQuestInstance instance) + { + Spellweaving.AwardTo(instance.Player); + base.GetRewards(instance); + } + } + + #endregion + + #region Friend of the Fey + + public class FriendOfTheFey : MLQuest + { + public FriendOfTheFey() + { + Activated = true; + Title = 1074284; // Friend of the Fey + Description = + 1074286; // The children of Sosaria understand the dedication and committment of an arcanist -- and will, from time to time offer their friendship. If you would forge such a bond, first seek out a goodwill offering to present. Pixies enjoy sweets and pretty things. + RefusalMessage = 1074288; // There's always time to make new friends. + InProgressMessage = 1074290; // I think honey and some sparkly beads would please a pixie. + CompletionMessage = 1074292; // What have we here? Oh yes, gifts for a pixie. + + Objectives.Add(new CollectObjective(1, typeof(Beads), 1024235)); // beads + Objectives.Add(new CollectObjective(1, typeof(JarHoney), 1022540)); // jar of honey + + Rewards.Add(new DummyReward( + 1074874)); // The opportunity to prove yourself worthy of learning to Summon Fey. (Sufficient spellweaving skill is required to cast the spell) + } + + public override Type NextQuest => typeof(TokenOfFriendship); + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Synaeva"), new Point3D(7064, 350, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Synaeva"), new Point3D(7064, 350, 0), Map.Trammel); + } + } + + public class TokenOfFriendship : MLQuest + { + public TokenOfFriendship() + { + Activated = true; + Title = 1074293; // Token of Friendship + Description = + 1074297; // I've wrapped your gift suitably to present to a pixie of discriminating taste. Seek out Arielle and give her your offering. + RefusalMessage = 1074310; // I'll hold onto this gift in case you change your mind. + InProgressMessage = + 1074315; // Arielle wanders quite a bit, so I'm not sure exactly where to find her. I'm sure she's going to love your gift. + CompletionMessage = 1074319; // *giggle* Oooh! For me? + + Objectives.Add(new DeliverObjective(typeof(GiftForArielle), 1, "gift for Arielle", typeof(Arielle))); + + Rewards.Add(new DummyReward( + 1074874)); // The opportunity to prove yourself worthy of learning to Summon Fey. (Sufficient spellweaving skill is required to cast the spell) + } + + public override Type NextQuest => typeof(Alliance); + public override bool IsChainTriggered => true; + } + + public class Alliance : MLQuest + { + public Alliance() + { + Activated = true; + Title = 1074294; // Alliance + Description = 1074298; // *giggle* Mean reapers make pixies unhappy. *light-hearted giggle* You could fix them! + RefusalMessage = 1074311; // *giggle* Okies! + InProgressMessage = 1074316; // Mean reapers are all around trees! *giggle* You fix them up, please. + CompletionNotice = CompletionNoticeShortReturn; + + Objectives.Add(new KillObjective(20, new[] { typeof(Reaper) }, "reapers")); + + Rewards.Add(new ItemReward(1031607, typeof(SummonFeyScroll))); // Summon Fey + } + + public override bool IsChainTriggered => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.PlayerContext.SummonFey = true; + instance.Player.SendLocalizedMessage(1074320, "", + 0x2A); // *giggle* Mean reapers got fixed! Pixie friend now! *giggle* When mean thingies bother you, a brave pixie will help. + + base.GetRewards(instance); + } + } + + #endregion + + #region Fiendish Friends + + public class FiendishFriends : MLQuest + { + public FiendishFriends() + { + Activated = true; + Title = 1074283; // Fiendish Friends + Description = + 1074285; // It is true that a skilled arcanist can summon and dominate an imp to serve at their pleasure. To do such at thing though, you must master the miserable little fiends utterly by demonstrating your superiority. Rough them up some -- kill a few. That will do the trick. + RefusalMessage = 1074287; // You're probably right. They're not worth the effort. + InProgressMessage = 1074289; // Surely you're not having difficulties swatting down those annoying pests? + // TODO: Verify + CompletionMessage = 1074291; // Hah! You showed them! + + Objectives.Add(new KillObjective(50, new[] { typeof(Imp) }, "imps")); + + Rewards.Add(new DummyReward( + 1074873)); // The opportunity to prove yourself worthy of learning to Summon Fiends. (Sufficient spellweaving skill is required to cast the spell) + } + + public override Type NextQuest => typeof(CrackingTheWhipI); + + public override void Generate() + { + base.Generate(); + + PutSpawner(new Spawner(1, 5, 10, 0, 0, "ElderBrae"), new Point3D(6266, 124, 0), Map.Felucca); + PutSpawner(new Spawner(1, 5, 10, 0, 0, "ElderBrae"), new Point3D(6266, 124, 0), Map.Trammel); + } + } + + // TODO: Verify + public class CrackingTheWhipI : MLQuest + { + public CrackingTheWhipI() + { + Activated = true; + Title = 1074295; // Cracking the Whip + Description = + 1074300; // Now that you've shown those mini pests your might, you should collect suitable implements to use to train your summoned pet. I suggest a stout whip. + RefusalMessage = 1074313; // Heh. Changed your mind, eh? + InProgressMessage = + 1074317; // Well, hurry up. If you don't get a whip how do you expect to control the little devil? + CompletionMessage = 1074321; // That's a well-made whip. No imp will ignore the sting of that lash. + + Objectives.Add(new CollectObjective(1, typeof(StoutWhip), "Stout Whip")); + + Rewards.Add(new DummyReward( + 1074873)); // The opportunity to prove yourself worthy of learning to Summon Fiends. (Sufficient spellweaving skill is required to cast the spell) + } + + public override Type NextQuest => typeof(CrackingTheWhipII); + public override bool IsChainTriggered => true; + } + + // TODO: Verify + public class CrackingTheWhipII : MLQuest + { + public CrackingTheWhipII() + { + Activated = true; + Title = 1074295; // Cracking the Whip + Description = + 1074302; // Now you just need to make the little buggers fear you -- if you can slay an arcane daemon, you'll earn their subservience. + RefusalMessage = 1074314; // If you're not up for it, so be it. + InProgressMessage = 1074318; // You need to vanquish an arcane daemon before the imps will fear you properly. + + Objectives.Add(new KillObjective(1, new[] { typeof(ArcaneDaemon) }, 1029733)); // arcane demon + + Rewards.Add(new ItemReward(1031608, typeof(SummonFiendScroll))); // Summon Fiend + } + + public override bool IsChainTriggered => true; + + public override void GetRewards(MLQuestInstance instance) + { + instance.PlayerContext.SummonFiend = true; + instance.Player.SendLocalizedMessage(1074322, "", + 0x2A); // You've demonstrated your strength, got a means of control, and taught the imps to fear you. You're ready now to summon them. + + base.GetRewards(instance); + } + } + + #endregion + + #region Mobiles + + [QuesterName("Aeluva (The Heartwood)")] + public class Aeluva : BaseCreature + { + [Constructible] + public Aeluva() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0) + { + Title = "the arcanist"; + Race = Race.Elf; + Female = true; + Body = 606; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new ElvenShirt()); + AddItem(new Kilt(Utility.RandomNondyedHue())); // Note: OSI hue = 0x1516, typo? + AddItem(new ElvenBoots()); + AddItem(new Circlet()); + } + + public Aeluva(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Aeluva"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + /* + * 1074206 - Excuse me please traveler, might I have a little of your time? + * 1074207 - Good day to you friend! Allow me to offer you a fabulous opportunity!  Thrills and adventure await! + */ + MLQuestSystem.Tell(this, pm, Utility.Random(1074206, 2)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Koole (Sanctuary)")] + public class Koole : BaseCreature + { + [Constructible] + public Koole() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0) + { + Title = "the arcanist"; + Race = Race.Elf; + Body = 605; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + Item item; + + item = new LeafChest(); + item.Hue = 443; + AddItem(item); + + item = new LeafArms(); + item.Hue = 443; + AddItem(item); + + AddItem(new LeafTonlet()); + AddItem(new ThighBoots(Utility.RandomAnimalHue())); + AddItem(new RoyalCirclet()); + } + + public Koole(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Koole"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074186, // Come here, I have a task. + 1074218 // Hey! I want to talk to you, now. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Synaeva (The Heartwood)")] + public class Synaeva : BaseCreature + { + [Constructible] + public Synaeva() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0) + { + Title = "the arcanist"; + Race = Race.Elf; + Female = true; + Body = 606; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + Item item = new RavenHelm(); + item.Hue = Utility.RandomGreenHue(); + AddItem(item); + + AddItem(new FemaleLeafChest()); + AddItem(new LeafArms()); + AddItem(new LeafTonlet()); + AddItem(new ElvenBoots()); + AddItem(new WildStaff()); + } + + public Synaeva(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Synaeva"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074223); // Have you done it yet?  Oh, I haven’t told you, have I? + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [QuesterName("Elder Brae (Sanctuary)")] + public class ElderBrae : BaseCreature + { + [Constructible] + public ElderBrae() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2.0) + { + Title = "the wise"; + Race = Race.Elf; + Female = true; + Body = 606; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); + + Utility.AssignRandomHair(this, true); + + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); + + AddItem(new GemmedCirclet()); + AddItem(new FemaleElvenRobe(Utility.RandomBrightHue())); + AddItem(new ElvenBoots(Utility.RandomAnimalHue())); + } + + public ElderBrae(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Elder Brae"; + public override bool CanShout => true; + + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, Utility.RandomList( + 1074215, // Don’t test my patience you sniveling worm! + 1074218 // Hey!  I want to talk to you, now. + )); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/TheAncientWorld.cs b/Scripts/Engines/MLQuests/Definitions/TheAncientWorld.cs index 7e821a2a2..affbc8551 100644 --- a/Scripts/Engines/MLQuests/Definitions/TheAncientWorld.cs +++ b/Scripts/Engines/MLQuests/Definitions/TheAncientWorld.cs @@ -6,150 +6,161 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class TheAncientWorld : MLQuest - { - public override Type NextQuest => typeof( TheGoldenHorn ); + public class TheAncientWorld : MLQuest + { + public TheAncientWorld() + { + Activated = true; + Title = 1074534; // The Ancient World + Description = + 1074535; // The lore of my people mentions Mondain many times. In one tale, it is revealed that he created and enslaved a race -- a sort of man bull, known as a 'minotaur'. The tales speak of mighty warriors who charged with blood-soaked horns into the heat of battle. But, alas, the fate of the bull-men is unknown after the rupture. Will you seek information about their civilization? + RefusalMessage = 1074538; // I am disappointed, but I respect your decision. + InProgressMessage = + 1074539; // A traveler has told me that worshippers of Mondain still exist and wander the land. Perhaps their lore speaks of whether the bull-men survived. I do not think they share their secrets gladly. You may need to be 'persuasive'. + CompletionMessage = 1074542; // What have you found? - public TheAncientWorld() - { - Activated = true; - Title = 1074534; // The Ancient World - Description = 1074535; // The lore of my people mentions Mondain many times. In one tale, it is revealed that he created and enslaved a race -- a sort of man bull, known as a 'minotaur'. The tales speak of mighty warriors who charged with blood-soaked horns into the heat of battle. But, alas, the fate of the bull-men is unknown after the rupture. Will you seek information about their civilization? - RefusalMessage = 1074538; // I am disappointed, but I respect your decision. - InProgressMessage = 1074539; // A traveler has told me that worshippers of Mondain still exist and wander the land. Perhaps their lore speaks of whether the bull-men survived. I do not think they share their secrets gladly. You may need to be 'persuasive'. - CompletionMessage = 1074542; // What have you found? + Objectives.Add(new CollectObjective(1, typeof(FragmentOfAMap), "fragment of a map")); - Objectives.Add( new CollectObjective( 1, typeof( FragmentOfAMap ), "fragment of a map" ) ); + Rewards.Add(new DummyReward(1074876)); // Knowledge of the legendary minotaur. + } - Rewards.Add( new DummyReward( 1074876 ) ); // Knowledge of the legendary minotaur. - } + public override Type NextQuest => typeof(TheGoldenHorn); - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "LorekeeperBroolol" ), new Point3D( 7011, 375, 0 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 5, "LorekeeperBroolol" ), new Point3D( 7011, 375, 0 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 5, "LorekeeperBroolol"), new Point3D(7011, 375, 0), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 5, "LorekeeperBroolol"), new Point3D(7011, 375, 0), Map.Felucca); + } + } - public class TheGoldenHorn : MLQuest - { - public override Type NextQuest => typeof( Bullish ); - public override bool IsChainTriggered => true; + public class TheGoldenHorn : MLQuest + { + public TheGoldenHorn() + { + Activated = true; + Title = 1074543; // The Golden Horn + Description = + 1074545; // Ah ha! You see here ... and over here ... The map fragment places the city of the bull-men, Labyrinth, on that piece of Sosaria that was thrown into the sky. Hmmm, I would have you go there and find any artifacts that remain that help tell the story. But, legend speaks of a mighty barrier to prevent invasion of the city. Take this map to Braen and explain the problem. Perhaps he can devise a solution. + RefusalMessage = 1074538; // I am disappointed, but I respect your decision. + InProgressMessage = 1074547; // Braen is nearby, run and speak with him. + CompletionMessage = 1074549; // Yes? What do you want? I'm very busy. - public TheGoldenHorn() - { - Activated = true; - Title = 1074543; // The Golden Horn - Description = 1074545; // Ah ha! You see here ... and over here ... The map fragment places the city of the bull-men, Labyrinth, on that piece of Sosaria that was thrown into the sky. Hmmm, I would have you go there and find any artifacts that remain that help tell the story. But, legend speaks of a mighty barrier to prevent invasion of the city. Take this map to Braen and explain the problem. Perhaps he can devise a solution. - RefusalMessage = 1074538; // I am disappointed, but I respect your decision. - InProgressMessage = 1074547; // Braen is nearby, run and speak with him. - CompletionMessage = 1074549; // Yes? What do you want? I'm very busy. + Objectives.Add(new DeliverObjective(typeof(FragmentOfAMapDelivery), 1, "fragment of a map", typeof(Braen))); - Objectives.Add( new DeliverObjective( typeof( FragmentOfAMapDelivery ), 1, "fragment of a map", typeof( Braen ) ) ); + Rewards.Add(new DummyReward(1074876)); // Knowledge of the legendary minotaur. + } - Rewards.Add( new DummyReward( 1074876 ) ); // Knowledge of the legendary minotaur. - } - } + public override Type NextQuest => typeof(Bullish); + public override bool IsChainTriggered => true; + } - public class Bullish : MLQuest - { - public override Type NextQuest => typeof( LostCivilization ); - public override bool IsChainTriggered => true; + public class Bullish : MLQuest + { + public Bullish() + { + Activated = true; + Title = 1074550; // Bullish + Description = + 1074552; // Oh, I see. I will need some materials to infuse you with the essence of a bull-man, so you can fool their defenses. The most similar beast to the original Baratarian bull that the minotaur were bred from is undoubtedly the mighty Gaman, native to the Lands of the Feudal Lords. I need horns, in great quantity to undertake this magic. + RefusalMessage = 1074554; // Oh come now, don't be afraid. The magic won't harm you. + InProgressMessage = + 1074555; // I cannot grant you the ability to pass through the bull-men's defenses without the gaman horns. + CompletionMessage = + 1074556; // You've returned at last! Give me just a moment to examine what you've brought and I can perform the magic that will allow you enter the Labyrinth. - public Bullish() - { - Activated = true; - Title = 1074550; // Bullish - Description = 1074552; // Oh, I see. I will need some materials to infuse you with the essence of a bull-man, so you can fool their defenses. The most similar beast to the original Baratarian bull that the minotaur were bred from is undoubtedly the mighty Gaman, native to the Lands of the Feudal Lords. I need horns, in great quantity to undertake this magic. - RefusalMessage = 1074554; // Oh come now, don't be afraid. The magic won't harm you. - InProgressMessage = 1074555; // I cannot grant you the ability to pass through the bull-men's defenses without the gaman horns. - CompletionMessage = 1074556; // You've returned at last! Give me just a moment to examine what you've brought and I can perform the magic that will allow you enter the Labyrinth. + Objectives.Add(new CollectObjective(20, typeof(GamanHorns), "gaman horns")); - Objectives.Add( new CollectObjective( 20, typeof( GamanHorns ), "gaman horns" ) ); + Rewards.Add(new DummyReward(1074876)); // Knowledge of the legendary minotaur. + } - Rewards.Add( new DummyReward( 1074876 ) ); // Knowledge of the legendary minotaur. - } - } + public override Type NextQuest => typeof(LostCivilization); + public override bool IsChainTriggered => true; + } - public class LostCivilization : MLQuest - { - public override bool IsChainTriggered => true; + public class LostCivilization : MLQuest + { + public LostCivilization() + { + Activated = true; + Title = 1074823; // Lost Civilization + Description = + 1074825; // *whew* It is done! The fierce essence of the bull has been infused into your aura. You are able now to breach the ancient defenses of the city. Go forth and seek the minotaur -- and then return with wonderous tales and evidence of your visit to the Labyrinth. + RefusalMessage = + 1074827; // As you wish. I can't understand why you'd pass up such a remarkable opportunity. Think of the adventures you would have. + InProgressMessage = + 1074828; // You won't reach the minotaur city by loitering around here! What are you waiting for? You need to get to Malas and find the access point for the island. You'll be renowned for your discovery! + CompletionMessage = + 1074829; // Oh! You've returned at last! I can't wait to hear the tales ... but first, let me see those artifacts. You've certainly earned this reward. - public LostCivilization() - { - Activated = true; - Title = 1074823; // Lost Civilization - Description = 1074825; // *whew* It is done! The fierce essence of the bull has been infused into your aura. You are able now to breach the ancient defenses of the city. Go forth and seek the minotaur -- and then return with wonderous tales and evidence of your visit to the Labyrinth. - RefusalMessage = 1074827; // As you wish. I can't understand why you'd pass up such a remarkable opportunity. Think of the adventures you would have. - InProgressMessage = 1074828; // You won't reach the minotaur city by loitering around here! What are you waiting for? You need to get to Malas and find the access point for the island. You'll be renowned for your discovery! - CompletionMessage = 1074829; // Oh! You've returned at last! I can't wait to hear the tales ... but first, let me see those artifacts. You've certainly earned this reward. + Objectives.Add(new CollectObjective(3, typeof(MinotaurArtifact), "minotaur artifacts")); - Objectives.Add( new CollectObjective( 3, typeof( MinotaurArtifact ), "minotaur artifacts" ) ); + Rewards.Add(ItemReward.Strongbox); + } - Rewards.Add( ItemReward.Strongbox ); - } - } + public override bool IsChainTriggered => true; + } - #endregion + #endregion - #region Mobiles + #region Mobiles - [QuesterName( "Broolol (The Heartwood)" )] - public class LorekeeperBroolol : BaseCreature - { - public override bool IsInvulnerable => true; - public override bool CanTeach => true; - public override string DefaultName => "Lorekeeper Broolol"; - public override bool CanShout => true; - public override void Shout( PlayerMobile pm ) - { - MLQuestSystem.Tell( this, pm, 1074200 ); // Thank goodness you are here, there�s no time to lose. - } + [QuesterName("Broolol (The Heartwood)")] + public class LorekeeperBroolol : BaseCreature + { + [Constructible] + public LorekeeperBroolol() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the keeper of tradition"; + Race = Race.Elf; + BodyValue = 0x25E; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public LorekeeperBroolol() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the keeper of tradition"; - Race = Race.Elf; - BodyValue = 0x25E; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + SetSkill(SkillName.Meditation, 60.0, 80.0); + SetSkill(SkillName.Focus, 60.0, 80.0); - SetSkill( SkillName.Meditation, 60.0, 80.0 ); - SetSkill( SkillName.Focus, 60.0, 80.0 ); + AddItem(new ElvenBoots(0x70D)); + AddItem(new FemaleElvenRobe(0x3A)); + AddItem(new WildStaff()); + } - AddItem( new ElvenBoots( 0x70D ) ); - AddItem( new FemaleElvenRobe( 0x3A ) ); - AddItem( new WildStaff() ); - } + public LorekeeperBroolol(Serial serial) + : base(serial) + { + } - public LorekeeperBroolol( Serial serial ) - : base( serial ) - { - } + public override bool IsInvulnerable => true; + public override bool CanTeach => true; + public override string DefaultName => "Lorekeeper Broolol"; + public override bool CanShout => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Shout(PlayerMobile pm) + { + MLQuestSystem.Tell(this, pm, 1074200); // Thank goodness you are here, there�s no time to lose. + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion -} + int version = reader.ReadInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/TownEscorts.cs b/Scripts/Engines/MLQuests/Definitions/TownEscorts.cs index 1f0fd15aa..57330f5eb 100644 --- a/Scripts/Engines/MLQuests/Definitions/TownEscorts.cs +++ b/Scripts/Engines/MLQuests/Definitions/TownEscorts.cs @@ -4,126 +4,128 @@ using Server.Items; namespace Server.Engines.MLQuests.Definitions { - public class TownEscort : BaseEscort - { - // Escort reward - private static readonly BaseReward m_Reward = new ItemReward( "Gold", typeof( Gold ), 500 ); + public class TownEscort : BaseEscort + { + // Escort reward + private static readonly BaseReward m_Reward = new ItemReward("Gold", typeof(Gold), 500); - public TownEscort( int title, int progress, int destination, string region ) - { - Activated = true; - Title = title; - Description = 1072287; // I seek a worthy escort. I can offer some small pay to any able bodied adventurer who can assist me. It is imperative that I reach my destination. - RefusalMessage = 1072288; // I wish you would reconsider my offer. I'll be waiting right here for someone brave enough to assist me. - InProgressMessage = progress; + public TownEscort(int title, int progress, int destination, string region) + { + Activated = true; + Title = title; + Description = + 1072287; // I seek a worthy escort. I can offer some small pay to any able bodied adventurer who can assist me. It is imperative that I reach my destination. + RefusalMessage = + 1072288; // I wish you would reconsider my offer. I'll be waiting right here for someone brave enough to assist me. + InProgressMessage = progress; - Objectives.Add( new EscortObjective( new QuestArea( destination, region ) ) ); + Objectives.Add(new EscortObjective(new QuestArea(destination, region))); - Rewards.Add( m_Reward ); - } - } + Rewards.Add(m_Reward); + } + } - public class EscortToYew : TownEscort - { - public EscortToYew() - : base( 1072275, 1072289, 1072227, "Yew" ) - { - } - } + public class EscortToYew : TownEscort + { + public EscortToYew() + : base(1072275, 1072289, 1072227, "Yew") + { + } + } - public class EscortToVesper : TownEscort - { - public EscortToVesper() - : base( 1072276, 1072290, 1072229, "Vesper" ) - { - } - } + public class EscortToVesper : TownEscort + { + public EscortToVesper() + : base(1072276, 1072290, 1072229, "Vesper") + { + } + } - public class EscortToTrinsic : TownEscort - { - public EscortToTrinsic() - : base( 1072277, 1072291, 1072236, "Trinsic" ) - { - } - } + public class EscortToTrinsic : TownEscort + { + public EscortToTrinsic() + : base(1072277, 1072291, 1072236, "Trinsic") + { + } + } - public class EscortToSkaraBrae : TownEscort - { - public EscortToSkaraBrae() - : base( 1072278, 1072292, 1072235, "Skara Brae" ) - { - } - } + public class EscortToSkaraBrae : TownEscort + { + public EscortToSkaraBrae() + : base(1072278, 1072292, 1072235, "Skara Brae") + { + } + } - public class EscortToSerpentsHold : TownEscort - { - public EscortToSerpentsHold() - : base( 1072279, 1072293, 1072238, "Serpent's Hold" ) - { - } - } + public class EscortToSerpentsHold : TownEscort + { + public EscortToSerpentsHold() + : base(1072279, 1072293, 1072238, "Serpent's Hold") + { + } + } - public class EscortToNujelm : TownEscort - { - public EscortToNujelm() - : base( 1072280, 1072294, 1072237, "Nujel'm" ) - { - } - } + public class EscortToNujelm : TownEscort + { + public EscortToNujelm() + : base(1072280, 1072294, 1072237, "Nujel'm") + { + } + } - public class EscortToMoonglow : TownEscort - { - public EscortToMoonglow() - : base( 1072281, 1072295, 1072232, "Moonglow" ) - { - } - } + public class EscortToMoonglow : TownEscort + { + public EscortToMoonglow() + : base(1072281, 1072295, 1072232, "Moonglow") + { + } + } - public class EscortToMinoc : TownEscort - { - public EscortToMinoc() - : base( 1072282, 1072296, 1072228, "Minoc" ) - { - } - } + public class EscortToMinoc : TownEscort + { + public EscortToMinoc() + : base(1072282, 1072296, 1072228, "Minoc") + { + } + } - public class EscortToMagincia : TownEscort - { - public EscortToMagincia() - : base( 1072283, 1072297, 1072233, "Magincia" ) - { - } - } + public class EscortToMagincia : TownEscort + { + public EscortToMagincia() + : base(1072283, 1072297, 1072233, "Magincia") + { + } + } - public class EscortToJhelom : TownEscort - { - public EscortToJhelom() - : base( 1072284, 1072298, 1072239, "Jhelom" ) - { - } - } + public class EscortToJhelom : TownEscort + { + public EscortToJhelom() + : base(1072284, 1072298, 1072239, "Jhelom") + { + } + } - public class EscortToCove : TownEscort - { - public EscortToCove() - : base( 1072285, 1072299, 1072230, "Cove" ) - { - } - } + public class EscortToCove : TownEscort + { + public EscortToCove() + : base(1072285, 1072299, 1072230, "Cove") + { + } + } - public class EscortToBritain : TownEscort - { - public EscortToBritain() - : base( 1072286, 1072300, 1072231, "Britain" ) - { - } - } + public class EscortToBritain : TownEscort + { + public EscortToBritain() + : base(1072286, 1072300, 1072231, "Britain") + { + } + } - public class EscortToOcllo : TownEscort - { - public EscortToOcllo() - : base( 1072312, 1072313, 1072234, "Ocllo" ) - { - } - } -} + public class EscortToOcllo : TownEscort + { + public EscortToOcllo() + : base(1072312, 1072313, 1072234, "Ocllo") + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/UnfadingMemories.cs b/Scripts/Engines/MLQuests/Definitions/UnfadingMemories.cs index dd7eec1c1..1bfdff0ab 100644 --- a/Scripts/Engines/MLQuests/Definitions/UnfadingMemories.cs +++ b/Scripts/Engines/MLQuests/Definitions/UnfadingMemories.cs @@ -6,182 +6,191 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Definitions { - #region Quests + #region Quests - public class UnfadingMemoriesPartOne : MLQuest - { - public override Type NextQuest => typeof( UnfadingMemoriesPartTwo ); + public class UnfadingMemoriesPartOne : MLQuest + { + public UnfadingMemoriesPartOne() + { + Activated = true; + Title = 1075355; // Unfading Memories + Description = + 1075356; // Aargh! It�s just not right! It doesn�t capture the unique color of her hair at all! If only I had some Prismatic Amber. That would be perfect. They used to mine it in Malas, but alas, those veins ran dry some time ago. I hear it may have been found in the Prism of Light. Oh, if only there were a bold adventurer within earshot who would go to the Prism of Light and retrieve some for me! + RefusalMessage = 1075358; // Is there no one who can help a humble artist pursue his Muse? + InProgressMessage = + 1075359; // You can find Prismatic Amber in the Prism of Light, located just north of the city of Nujel'm. + CompletionMessage = + 1075360; // I knew it! See, it�s just the color I needed! Look how it brings out the highlights of her wheaten tresses! + CompletionNotice = CompletionNoticeShort; - public UnfadingMemoriesPartOne() - { - Activated = true; - Title = 1075355; // Unfading Memories - Description = 1075356; // Aargh! It�s just not right! It doesn�t capture the unique color of her hair at all! If only I had some Prismatic Amber. That would be perfect. They used to mine it in Malas, but alas, those veins ran dry some time ago. I hear it may have been found in the Prism of Light. Oh, if only there were a bold adventurer within earshot who would go to the Prism of Light and retrieve some for me! - RefusalMessage = 1075358; // Is there no one who can help a humble artist pursue his Muse? - InProgressMessage = 1075359; // You can find Prismatic Amber in the Prism of Light, located just north of the city of Nujel'm. - CompletionMessage = 1075360; // I knew it! See, it�s just the color I needed! Look how it brings out the highlights of her wheaten tresses! - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new CollectObjective(1, typeof(PrismaticAmber), "Prismatic Amber")); - Objectives.Add( new CollectObjective( 1, typeof( PrismaticAmber ), "Prismatic Amber" ) ); + Rewards.Add(new DummyReward( + 1075357)); // The joy of contributing to a noble artistic effort, however paltry the end product. + } - Rewards.Add( new DummyReward( 1075357 ) ); // The joy of contributing to a noble artistic effort, however paltry the end product. - } + public override Type NextQuest => typeof(UnfadingMemoriesPartTwo); - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Emilio" ), new Point3D( 1447, 1664, 10 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Emilio" ), new Point3D( 1447, 1664, 10 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Emilio"), new Point3D(1447, 1664, 10), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Emilio"), new Point3D(1447, 1664, 10), Map.Felucca); + } + } - public class UnfadingMemoriesPartTwo : MLQuest - { - public override Type NextQuest => typeof( UnfadingMemoriesPartThree ); - public override bool IsChainTriggered => true; + public class UnfadingMemoriesPartTwo : MLQuest + { + public UnfadingMemoriesPartTwo() + { + Activated = true; + Title = 1075367; // Unfading Memories + Description = + 1075368; // Finished! With the pigment I was able to create from the Prismatic Amber you brought me, I was able to complete my humble work. I should explain. Once, I loved a noble lady of gentleness and refinement, who possessed such beauty that I have found myself unable to love another to this day. But it was from afar that I admired her, for it is not for one so lowly as I to pay court to the likes of her. You have heard of the fair Thalia, Lady of Nujel'm? No? Well, she was my Muse, my inspiration, and when I heard she was to be married, I lost whatever pitiful talent I possessed. I felt I must compose a portrait of her, my masterpiece, or I would never be able to paint again. You, my friend, have helped me complete my work. Now I ask another favor of you. Will you take it to her as a wedding gift? She will probably reject it, but I must make the offer. + RefusalMessage = + 1075370; // Alright then, you have already helped me more than I deserved. I shall find someone else to undertake this task. + InProgressMessage = + 1075371; // The wedding is taking place in the palace in Nujel'm. You will likely find her there. + CompletionMessage = + 1075372; // I�m sorry, I�m getting ready to be married. I don�t have time to . . . what�s that you say? + CompletionNotice = CompletionNoticeShort; - public UnfadingMemoriesPartTwo() - { - Activated = true; - Title = 1075367; // Unfading Memories - Description = 1075368; // Finished! With the pigment I was able to create from the Prismatic Amber you brought me, I was able to complete my humble work. I should explain. Once, I loved a noble lady of gentleness and refinement, who possessed such beauty that I have found myself unable to love another to this day. But it was from afar that I admired her, for it is not for one so lowly as I to pay court to the likes of her. You have heard of the fair Thalia, Lady of Nujel'm? No? Well, she was my Muse, my inspiration, and when I heard she was to be married, I lost whatever pitiful talent I possessed. I felt I must compose a portrait of her, my masterpiece, or I would never be able to paint again. You, my friend, have helped me complete my work. Now I ask another favor of you. Will you take it to her as a wedding gift? She will probably reject it, but I must make the offer. - RefusalMessage = 1075370; // Alright then, you have already helped me more than I deserved. I shall find someone else to undertake this task. - InProgressMessage = 1075371; // The wedding is taking place in the palace in Nujel'm. You will likely find her there. - CompletionMessage = 1075372; // I�m sorry, I�m getting ready to be married. I don�t have time to . . . what�s that you say? - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(PortraitOfTheBride), 1, "Portrait of the Bride", typeof(Thalia))); - Objectives.Add( new DeliverObjective( typeof( PortraitOfTheBride ), 1, "Portrait of the Bride", typeof( Thalia ) ) ); + Rewards.Add(new DummyReward(1075369)); // The Artist�s gratitude. + } - Rewards.Add( new DummyReward( 1075369 ) ); // The Artist�s gratitude. - } - } + public override Type NextQuest => typeof(UnfadingMemoriesPartThree); + public override bool IsChainTriggered => true; + } - public class UnfadingMemoriesPartThree : MLQuest - { - public override bool IsChainTriggered => true; + public class UnfadingMemoriesPartThree : MLQuest + { + public UnfadingMemoriesPartThree() + { + Activated = true; + OneTimeOnly = true; + Title = 1075373; // Unfading Memories + Description = + 1075374; // Emilio painted this? It is absolutely wonderful! I used to love looking at his paintings, but I don�t remember him creating anything like this before. Would you be so kind as to carry a letter to him? Fate may have it that I am to marry another, yet I am compelled to reveal to him that his love was not entirely unrequited. + RefusalMessage = 1075376; // Very well, then. If you will excuse me, I need to get ready. + InProgressMessage = + 1075377; // Take the letter back to the Artist�s Guild in Britain, if you would do me this kindness. + CompletionMessage = + 1075378; // She said what? She thinks what of me? I . . . I can�t believe it! All this time, I never knew how she truly felt. Thank you, my friend. I believe now I will be able to paint once again. Here, take this bleach. I was going to use it to destroy all of my works. Perhaps you can find a better use for it now. + CompletionNotice = CompletionNoticeShort; - public UnfadingMemoriesPartThree() - { - Activated = true; - OneTimeOnly = true; - Title = 1075373; // Unfading Memories - Description = 1075374; // Emilio painted this? It is absolutely wonderful! I used to love looking at his paintings, but I don�t remember him creating anything like this before. Would you be so kind as to carry a letter to him? Fate may have it that I am to marry another, yet I am compelled to reveal to him that his love was not entirely unrequited. - RefusalMessage = 1075376; // Very well, then. If you will excuse me, I need to get ready. - InProgressMessage = 1075377; // Take the letter back to the Artist�s Guild in Britain, if you would do me this kindness. - CompletionMessage = 1075378; // She said what? She thinks what of me? I . . . I can�t believe it! All this time, I never knew how she truly felt. Thank you, my friend. I believe now I will be able to paint once again. Here, take this bleach. I was going to use it to destroy all of my works. Perhaps you can find a better use for it now. - CompletionNotice = CompletionNoticeShort; + Objectives.Add(new DeliverObjective(typeof(BridesLetter), 1, "Bride's Letter", typeof(Emilio))); - Objectives.Add( new DeliverObjective( typeof( BridesLetter ), 1, "Bride's Letter", typeof( Emilio ) ) ); + Rewards.Add(new ItemReward(1075375, typeof(Bleach))); // Bleach + } - Rewards.Add( new ItemReward( 1075375, typeof( Bleach ) ) ); // Bleach - } + public override bool IsChainTriggered => true; - public override void Generate() - { - base.Generate(); + public override void Generate() + { + base.Generate(); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Thalia" ), new Point3D( 3675, 1322, 20 ), Map.Trammel ); - PutSpawner( new Spawner( 1, 5, 10, 0, 3, "Thalia" ), new Point3D( 3675, 1322, 20 ), Map.Felucca ); - } - } + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Thalia"), new Point3D(3675, 1322, 20), Map.Trammel); + PutSpawner(new Spawner(1, 5, 10, 0, 3, "Thalia"), new Point3D(3675, 1322, 20), Map.Felucca); + } + } - #endregion + #endregion - #region Mobiles + #region Mobiles - [QuesterName( "Emilio (Britain)" )] // OSI's description is "Artist", not very helpful - public class Emilio : BaseCreature - { - public override string DefaultName => "Emilio"; - public override bool IsInvulnerable => true; + [QuesterName("Emilio (Britain)")] // OSI's description is "Artist", not very helpful + public class Emilio : BaseCreature + { + [Constructible] + public Emilio() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Tortured Artist"; + Race = Race.Human; + BodyValue = 0x190; + Female = false; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [Constructible] - public Emilio() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Tortured Artist"; - Race = Race.Human; - BodyValue = 0x190; - Female = false; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + Utility.AssignRandomHair(this, true); - Utility.AssignRandomHair( this, true ); + AddItem(new Backpack()); + AddItem(new Sandals(0x72B)); + AddItem(new LongPants(0x525)); + AddItem(new FancyShirt(0x53F)); + AddItem(new FloppyHat(0x58C)); + AddItem(new BodySash(0x1C)); + } - AddItem( new Backpack() ); - AddItem( new Sandals( 0x72B ) ); - AddItem( new LongPants( 0x525 ) ); - AddItem( new FancyShirt( 0x53F ) ); - AddItem( new FloppyHat( 0x58C ) ); - AddItem( new BodySash( 0x1C ) ); + public Emilio(Serial serial) + : base(serial) + { + } - } + public override string DefaultName => "Emilio"; + public override bool IsInvulnerable => true; - public Emilio( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + [QuesterName("Thalia (Nujel'm)")] // OSI's description is "Bride", not very helpful + public class Thalia : BaseCreature + { + [Constructible] + public Thalia() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + Title = "the Bride"; + Race = Race.Human; + BodyValue = 0x191; + Female = true; + Hue = Race.RandomSkinHue(); + InitStats(100, 100, 25); - [QuesterName( "Thalia (Nujel'm)" )] // OSI's description is "Bride", not very helpful - public class Thalia : BaseCreature - { - public override string DefaultName => "Thalia"; - public override bool IsInvulnerable => true; + Utility.AssignRandomHair(this, true); - [Constructible] - public Thalia() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - Title = "the Bride"; - Race = Race.Human; - BodyValue = 0x191; - Female = true; - Hue = Race.RandomSkinHue(); - InitStats( 100, 100, 25 ); + AddItem(new Backpack()); + AddItem(new Sandals(0x8FD)); + AddItem(new FancyDress(0x8FD)); + } - Utility.AssignRandomHair( this, true ); + public Thalia(Serial serial) + : base(serial) + { + } - AddItem( new Backpack() ); - AddItem( new Sandals( 0x8FD ) ); - AddItem( new FancyDress( 0x8FD ) ); + public override string DefaultName => "Thalia"; + public override bool IsInvulnerable => true; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public Thalia( Serial serial ) - : base( serial ) - { - } + writer.Write(0); // version + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version - } + int version = reader.ReadInt(); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - #endregion -} + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Definitions/WarriorsOfTheGemKeeper.cs b/Scripts/Engines/MLQuests/Definitions/WarriorsOfTheGemKeeper.cs index 27c98e4b0..8b4662682 100644 --- a/Scripts/Engines/MLQuests/Definitions/WarriorsOfTheGemKeeper.cs +++ b/Scripts/Engines/MLQuests/Definitions/WarriorsOfTheGemKeeper.cs @@ -5,81 +5,91 @@ using Server.Items; namespace Server.Engines.MLQuests.Definitions { - public class WarriorsOfTheGemkeeper : MLQuest - { - public override Type NextQuest => typeof( CloseEnough ); + public class WarriorsOfTheGemkeeper : MLQuest + { + public WarriorsOfTheGemkeeper() + { + Activated = true; + Title = 1074536; // Warriors of the Gemkeeper + Description = + 1074537; // Here we honor the Gemkeeper's Apprentice and seek to aid her efforts against the humans responsible for the death of her teacher - and the destruction of the elven way of life. Our tales speak of a fierce race of servants of the Gemkeeper, the men-bulls whose battle-skill was renowned. It is desireable to discover the fate of these noble creatures after the Rupture. Will you seek information? + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = + 1074540; // I care not how you get the information. Kill as many humans as you must ... but find the fate of the minotaurs. Perhaps another of the Gemkeeper's servants has the knowledge we seek. + CompletionMessage = 1074542; // What have you found? - public WarriorsOfTheGemkeeper() - { - Activated = true; - Title = 1074536; // Warriors of the Gemkeeper - Description = 1074537; // Here we honor the Gemkeeper's Apprentice and seek to aid her efforts against the humans responsible for the death of her teacher - and the destruction of the elven way of life. Our tales speak of a fierce race of servants of the Gemkeeper, the men-bulls whose battle-skill was renowned. It is desireable to discover the fate of these noble creatures after the Rupture. Will you seek information? - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074540; // I care not how you get the information. Kill as many humans as you must ... but find the fate of the minotaurs. Perhaps another of the Gemkeeper's servants has the knowledge we seek. - CompletionMessage = 1074542; // What have you found? + Objectives.Add(new CollectObjective(1, typeof(FragmentOfAMap), "fragment of a map")); - Objectives.Add( new CollectObjective( 1, typeof( FragmentOfAMap ), "fragment of a map" ) ); + Rewards.Add(new DummyReward(1074876)); // Knowledge of the legendary minotaur. + } - Rewards.Add( new DummyReward( 1074876 ) ); // Knowledge of the legendary minotaur. - } - } + public override Type NextQuest => typeof(CloseEnough); + } - public class CloseEnough : MLQuest - { - public override Type NextQuest => typeof( TakingTheBullByTheHorns ); - public override bool IsChainTriggered => true; + public class CloseEnough : MLQuest + { + public CloseEnough() + { + Activated = true; + Title = 1074544; // Close Enough + Description = + 1074546; // Ah ha! You see here ... and over here ... The map fragment places the city of the bull-men, Labyrinth, on that piece of Sosaria that was thrown into the sky. Hmmm, I would have you go there and seek out these warriors to see if they might join our cause. But, legend speaks of a mighty barrier to prevent invasion of the city. Take this map to Canir and explain the problem. Perhaps she can devise a solution. + RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. + InProgressMessage = 1074548; // Canir is nearby, run and speak with her. + CompletionMessage = 1074549; // Yes? What do you want? I'm very busy. - public CloseEnough() - { - Activated = true; - Title = 1074544; // Close Enough - Description = 1074546; // Ah ha! You see here ... and over here ... The map fragment places the city of the bull-men, Labyrinth, on that piece of Sosaria that was thrown into the sky. Hmmm, I would have you go there and seek out these warriors to see if they might join our cause. But, legend speaks of a mighty barrier to prevent invasion of the city. Take this map to Canir and explain the problem. Perhaps she can devise a solution. - RefusalMessage = 1074063; // Fine then, I'm shall find another to run my errands then. - InProgressMessage = 1074548; // Canir is nearby, run and speak with her. - CompletionMessage = 1074549; // Yes? What do you want? I'm very busy. + Objectives.Add(new DeliverObjective(typeof(FragmentOfAMapDelivery), 1, "fragment of a map", typeof(Canir))); - Objectives.Add( new DeliverObjective( typeof( FragmentOfAMapDelivery ), 1, "fragment of a map", typeof( Canir ) ) ); + Rewards.Add(new DummyReward(1074876)); // Knowledge of the legendary minotaur. + } - Rewards.Add( new DummyReward( 1074876 ) ); // Knowledge of the legendary minotaur. - } - } + public override Type NextQuest => typeof(TakingTheBullByTheHorns); + public override bool IsChainTriggered => true; + } - public class TakingTheBullByTheHorns : MLQuest - { - public override Type NextQuest => typeof( EmissaryToTheMinotaur ); - public override bool IsChainTriggered => true; + public class TakingTheBullByTheHorns : MLQuest + { + public TakingTheBullByTheHorns() + { + Activated = true; + Title = 1074551; // Taking the Bull by the Horns + Description = + 1074553; // Interesting. I believe I have a way. I will need some materials to infuse you with the essence of a bull-man, so you can fool their defenses. The most similar beast to the original Baratarian bull that the minotaur were bred from is undoubtedly the mighty Gaman, native to the Lands of the Feudal Lords. I need horns, in great quantity to undertake this magic. + RefusalMessage = 1074554; // Oh come now, don't be afraid. The magic won't harm you. + InProgressMessage = + 1074555; // I cannot grant you the ability to pass through the bull-men's defenses without the gaman horns. + CompletionMessage = + 1074556; // You've returned at last! Give me just a moment to examine what you've brought and I can perform the magic that will allow you enter the Labyrinth. - public TakingTheBullByTheHorns() - { - Activated = true; - Title = 1074551; // Taking the Bull by the Horns - Description = 1074553; // Interesting. I believe I have a way. I will need some materials to infuse you with the essence of a bull-man, so you can fool their defenses. The most similar beast to the original Baratarian bull that the minotaur were bred from is undoubtedly the mighty Gaman, native to the Lands of the Feudal Lords. I need horns, in great quantity to undertake this magic. - RefusalMessage = 1074554; // Oh come now, don't be afraid. The magic won't harm you. - InProgressMessage = 1074555; // I cannot grant you the ability to pass through the bull-men's defenses without the gaman horns. - CompletionMessage = 1074556; // You've returned at last! Give me just a moment to examine what you've brought and I can perform the magic that will allow you enter the Labyrinth. + Objectives.Add(new CollectObjective(20, typeof(GamanHorns), "gaman horns")); - Objectives.Add( new CollectObjective( 20, typeof( GamanHorns ), "gaman horns" ) ); + Rewards.Add(new DummyReward(1074876)); // Knowledge of the legendary minotaur. + } - Rewards.Add( new DummyReward( 1074876 ) ); // Knowledge of the legendary minotaur. - } - } + public override Type NextQuest => typeof(EmissaryToTheMinotaur); + public override bool IsChainTriggered => true; + } - public class EmissaryToTheMinotaur : MLQuest - { - public override bool IsChainTriggered => true; + public class EmissaryToTheMinotaur : MLQuest + { + public EmissaryToTheMinotaur() + { + Activated = true; + Title = 1074824; // Emissary to the Minotaur + Description = + 1074825; // *whew* It is done! The fierce essence of the bull has been infused into your aura. You are able now to breach the ancient defenses of the city. Go forth and seek the minotaur -- and then return with wonderous tales and evidence of your visit to the Labyrinth. + RefusalMessage = + 1074827; // As you wish. I can't understand why you'd pass up such a remarkable opportunity. Think of the adventures you would have. + InProgressMessage = + 1074828; // You won't reach the minotaur city by loitering around here! What are you waiting for? You need to get to Malas and find the access point for the island. You'll be renowned for your discovery! + CompletionMessage = + 1074829; // Oh! You've returned at last! I can't wait to hear the tales ... but first, let me see those artifacts. You've certainly earned this reward. - public EmissaryToTheMinotaur() - { - Activated = true; - Title = 1074824; // Emissary to the Minotaur - Description = 1074825; // *whew* It is done! The fierce essence of the bull has been infused into your aura. You are able now to breach the ancient defenses of the city. Go forth and seek the minotaur -- and then return with wonderous tales and evidence of your visit to the Labyrinth. - RefusalMessage = 1074827; // As you wish. I can't understand why you'd pass up such a remarkable opportunity. Think of the adventures you would have. - InProgressMessage = 1074828; // You won't reach the minotaur city by loitering around here! What are you waiting for? You need to get to Malas and find the access point for the island. You'll be renowned for your discovery! - CompletionMessage = 1074829; // Oh! You've returned at last! I can't wait to hear the tales ... but first, let me see those artifacts. You've certainly earned this reward. + Objectives.Add(new CollectObjective(3, typeof(MinotaurArtifact), "minotaur artifacts")); - Objectives.Add( new CollectObjective( 3, typeof( MinotaurArtifact ), "minotaur artifacts" ) ); + Rewards.Add(ItemReward.Strongbox); + } - Rewards.Add( ItemReward.Strongbox ); - } - } -} + public override bool IsChainTriggered => true; + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/BaseQuestGump.cs b/Scripts/Engines/MLQuests/Gumps/BaseQuestGump.cs index 8e9874a05..22c7656c7 100644 --- a/Scripts/Engines/MLQuests/Gumps/BaseQuestGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/BaseQuestGump.cs @@ -1,57 +1,56 @@ -using System; using System.Collections.Generic; -using Server.Gumps; -using Server.Mobiles; using Server.Engines.MLQuests.Objectives; using Server.Engines.MLQuests.Rewards; +using Server.Gumps; +using Server.Mobiles; namespace Server.Engines.MLQuests.Gumps { - public enum ButtonPosition : byte - { - Left, - Right - } + public enum ButtonPosition : byte + { + Left, + Right + } - public enum ButtonGraphic : ushort - { - Invalid, - Accept = 0x2EE0, - Clear = 0x2EE3, - Close = 0x2EE6, - Continue = 0x2EE9, - Okay = 0x2EEC, - Previous = 0x2EEF, - Refuse = 0x2EF2, - Resign = 0x2EF5 - } + public enum ButtonGraphic : ushort + { + Invalid, + Accept = 0x2EE0, + Clear = 0x2EE3, + Close = 0x2EE6, + Continue = 0x2EE9, + Okay = 0x2EEC, + Previous = 0x2EEF, + Refuse = 0x2EF2, + Resign = 0x2EF5 + } - public abstract class BaseQuestGump : Gump - { - private struct ButtonInfo - { - public ButtonPosition Position { get; } + public abstract class BaseQuestGump : Gump + { + private struct ButtonInfo + { + public ButtonPosition Position{ get; } - public ButtonGraphic Graphic { get; } + public ButtonGraphic Graphic{ get; } - public int ButtonID { get; } + public int ButtonID{ get; } - public ButtonInfo( ButtonPosition position, ButtonGraphic graphic, int buttonID ) - { - Position = position; - Graphic = graphic; - ButtonID = buttonID; - } - } + public ButtonInfo(ButtonPosition position, ButtonGraphic graphic, int buttonID) + { + Position = position; + Graphic = graphic; + ButtonID = buttonID; + } + } - private int m_Page; - private int m_MaxPages; - private int m_Label; - private string m_Title; - private List m_Buttons; + private int m_Page; + private int m_MaxPages; + private int m_Label; + private string m_Title; + private List m_Buttons; #if false - // OSI clone, inefficient layout +// OSI clone, inefficient layout public BaseQuestGump( int label ) : base( 75, 25 ) { m_Page = 0; @@ -100,190 +99,197 @@ namespace Server.Engines.MLQuests.Gumps AddHtmlLocalized( 130, 68, 220, 48, 1114513, m_Title, 0x2710, false, false ); //
~1_TOKEN~
} #else - // RunUO optimized version - public BaseQuestGump( int label ) - : base( 75, 25 ) - { - m_Page = 0; - m_MaxPages = 0; - m_Label = label; - m_Title = null; - m_Buttons = new List( 2 ); + // RunUO optimized version + public BaseQuestGump(int label) + : base(75, 25) + { + m_Page = 0; + m_MaxPages = 0; + m_Label = label; + m_Title = null; + m_Buttons = new List(2); - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddImageTiled( 50, 20, 400, 460, 0x1404 ); - AddImageTiled( 50, 29, 30, 450, 0x28DC ); - AddImageTiled( 34, 140, 17, 339, 0x242F ); - AddImage( 48, 135, 0x28AB ); - AddImage( -16, 285, 0x28A2 ); - AddImage( 0, 10, 0x28B5 ); - AddImage( 25, 0, 0x28B4 ); - AddImageTiled( 83, 15, 350, 15, 0x280A ); - AddImage( 34, 479, 0x2842 ); - AddImage( 442, 479, 0x2840 ); - AddImageTiled( 51, 479, 392, 17, 0x2775 ); - AddImageTiled( 415, 29, 44, 450, 0xA2D ); - AddImageTiled( 415, 29, 30, 450, 0x28DC ); - //AddLabel( 100, 50, 0x481, "" ); - AddImage( 370, 50, 0x589 ); - AddImage( 379, 60, 0x15A9 ); - AddImage( 425, 0, 0x28C9 ); - AddImage( 90, 33, 0x232D ); - AddHtmlLocalized( 130, 45, 270, 16, label, 0xFFFFFF, false, false ); - AddImageTiled( 130, 65, 175, 1, 0x238D ); - } + AddImageTiled(50, 20, 400, 460, 0x1404); + AddImageTiled(50, 29, 30, 450, 0x28DC); + AddImageTiled(34, 140, 17, 339, 0x242F); + AddImage(48, 135, 0x28AB); + AddImage(-16, 285, 0x28A2); + AddImage(0, 10, 0x28B5); + AddImage(25, 0, 0x28B4); + AddImageTiled(83, 15, 350, 15, 0x280A); + AddImage(34, 479, 0x2842); + AddImage(442, 479, 0x2840); + AddImageTiled(51, 479, 392, 17, 0x2775); + AddImageTiled(415, 29, 44, 450, 0xA2D); + AddImageTiled(415, 29, 30, 450, 0x28DC); + //AddLabel( 100, 50, 0x481, "" ); + AddImage(370, 50, 0x589); + AddImage(379, 60, 0x15A9); + AddImage(425, 0, 0x28C9); + AddImage(90, 33, 0x232D); + AddHtmlLocalized(130, 45, 270, 16, label, 0xFFFFFF, false, false); + AddImageTiled(130, 65, 175, 1, 0x238D); + } - public void BuildPage() - { - AddPage( ++m_Page ); + public void BuildPage() + { + AddPage(++m_Page); - if ( m_Page > 1 ) - AddButton( 130, 430, (int)ButtonGraphic.Previous, (int)ButtonGraphic.Previous + 2, 0, GumpButtonType.Page, m_Page - 1 ); + if (m_Page > 1) + AddButton(130, 430, (int)ButtonGraphic.Previous, (int)ButtonGraphic.Previous + 2, 0, GumpButtonType.Page, + m_Page - 1); - if ( m_Page < m_MaxPages ) - AddButton( 275, 430, (int)ButtonGraphic.Continue, (int)ButtonGraphic.Continue + 2, 0, GumpButtonType.Page, m_Page + 1 ); + if (m_Page < m_MaxPages) + AddButton(275, 430, (int)ButtonGraphic.Continue, (int)ButtonGraphic.Continue + 2, 0, GumpButtonType.Page, + m_Page + 1); - foreach ( ButtonInfo button in m_Buttons ) - AddButton( button.Position == ButtonPosition.Left ? 95 : 313, 455, (int)button.Graphic, (int)button.Graphic + 2, button.ButtonID, GumpButtonType.Reply, 0 ); + foreach (ButtonInfo button in m_Buttons) + AddButton(button.Position == ButtonPosition.Left ? 95 : 313, 455, (int)button.Graphic, + (int)button.Graphic + 2, button.ButtonID, GumpButtonType.Reply, 0); - if ( m_Title != null ) - AddHtmlLocalized( 130, 68, 220, 48, 1114513, m_Title, 0x2710, false, false ); //
~1_TOKEN~
- } + if (m_Title != null) + AddHtmlLocalized(130, 68, 220, 48, 1114513, m_Title, 0x2710, false, + false); //
~1_TOKEN~
+ } #endif - public void SetPageCount( int maxPages ) - { - m_MaxPages = maxPages; - } + public void SetPageCount(int maxPages) + { + m_MaxPages = maxPages; + } - public void SetTitle( TextDefinition def ) - { - if ( def.Number > 0 ) - m_Title = $"#{def.Number}"; // OSI does "@@#{0}" instead, why? KR client related? - else - m_Title = def.String; - } + public void SetTitle(TextDefinition def) + { + if (def.Number > 0) + m_Title = $"#{def.Number}"; // OSI does "@@#{0}" instead, why? KR client related? + else + m_Title = def.String; + } - public void RegisterButton( ButtonPosition position, ButtonGraphic graphic, int buttonID ) - { - m_Buttons.Add( new ButtonInfo( position, graphic, buttonID ) ); - } + public void RegisterButton(ButtonPosition position, ButtonGraphic graphic, int buttonID) + { + m_Buttons.Add(new ButtonInfo(position, graphic, buttonID)); + } - #region Elaborate Formatting Shortcuts + #region Elaborate Formatting Shortcuts - public void AddDescription( MLQuest quest ) - { - AddHtmlLocalized( 98, 140, 312, 16, ( quest.IsChainTriggered || quest.NextQuest != null ) ? 1075024 : 1072202, 0x2710, false, false ); // Description [(quest chain)] - TextDefinition.AddHtmlText( this, 98, 156, 312, 240, quest.Description, false, true, 0x15F90, 0xBDE784 ); - } + public void AddDescription(MLQuest quest) + { + AddHtmlLocalized(98, 140, 312, 16, quest.IsChainTriggered || quest.NextQuest != null ? 1075024 : 1072202, 0x2710, + false, false); // Description [(quest chain)] + TextDefinition.AddHtmlText(this, 98, 156, 312, 240, quest.Description, false, true, 0x15F90, 0xBDE784); + } - public void AddObjectives( MLQuest quest ) - { - AddHtmlLocalized( 98, 140, 312, 16, 1049073, 0x2710, false, false ); // Objective: - AddHtmlLocalized( 98, 156, 312, 16, ( quest.ObjectiveType == ObjectiveType.All ) ? 1072208 : 1072209, 0x2710, false, false ); // All of the following / Only one of the following + public void AddObjectives(MLQuest quest) + { + AddHtmlLocalized(98, 140, 312, 16, 1049073, 0x2710, false, false); // Objective: + AddHtmlLocalized(98, 156, 312, 16, quest.ObjectiveType == ObjectiveType.All ? 1072208 : 1072209, 0x2710, false, + false); // All of the following / Only one of the following - int y = 172; + int y = 172; - foreach ( BaseObjective objective in quest.Objectives ) - { - objective.WriteToGump( this, ref y ); + foreach (BaseObjective objective in quest.Objectives) + { + objective.WriteToGump(this, ref y); - if ( objective.IsTimed ) - { - if ( objective is CollectObjective ) - y -= 16; + if (objective.IsTimed) + { + if (objective is CollectObjective) + y -= 16; - BaseObjectiveInstance.WriteTimeRemaining( this, ref y, objective.Duration ); - } - } - } + BaseObjectiveInstance.WriteTimeRemaining(this, ref y, objective.Duration); + } + } + } - public void AddObjectivesProgress( MLQuestInstance instance ) - { - MLQuest quest = instance.Quest; + public void AddObjectivesProgress(MLQuestInstance instance) + { + MLQuest quest = instance.Quest; - AddHtmlLocalized( 98, 140, 312, 16, 1049073, 0x2710, false, false ); // Objective: - AddHtmlLocalized( 98, 156, 312, 16, ( quest.ObjectiveType == ObjectiveType.All ) ? 1072208 : 1072209, 0x2710, false, false ); // All of the following / Only one of the following + AddHtmlLocalized(98, 140, 312, 16, 1049073, 0x2710, false, false); // Objective: + AddHtmlLocalized(98, 156, 312, 16, quest.ObjectiveType == ObjectiveType.All ? 1072208 : 1072209, 0x2710, false, + false); // All of the following / Only one of the following - int y = 172; + int y = 172; - foreach ( BaseObjectiveInstance objInstance in instance.Objectives ) - objInstance.WriteToGump( this, ref y ); - } + foreach (BaseObjectiveInstance objInstance in instance.Objectives) + objInstance.WriteToGump(this, ref y); + } - public void AddRewardsPage( MLQuest quest ) // For the quest log/offer gumps - { - AddHtmlLocalized( 98, 140, 312, 16, 1072201, 0x2710, false, false ); // Reward + public void AddRewardsPage(MLQuest quest) // For the quest log/offer gumps + { + AddHtmlLocalized(98, 140, 312, 16, 1072201, 0x2710, false, false); // Reward - int y = 162; + int y = 162; - if ( quest.Rewards.Count > 1 ) - { - // TODO: Is this what this is for? Does "Only one of the following" occur? - AddHtmlLocalized( 98, 156, 312, 16, 1072208, 0x2710, false, false ); // All of the following - y += 16; - } + if (quest.Rewards.Count > 1) + { + // TODO: Is this what this is for? Does "Only one of the following" occur? + AddHtmlLocalized(98, 156, 312, 16, 1072208, 0x2710, false, false); // All of the following + y += 16; + } - AddRewards( quest, 105, y, 16 ); - } + AddRewards(quest, 105, y, 16); + } - public void AddRewards( MLQuest quest ) // For the claim rewards gump - { - int y = 146; + public void AddRewards(MLQuest quest) // For the claim rewards gump + { + int y = 146; - if ( quest.Rewards.Count > 1 ) - { - // TODO: Is this what this is for? Does "Only one of the following" occur? - AddHtmlLocalized( 100, 140, 312, 16, 1072208, 0x2710, false, false ); // All of the following - y += 16; - } + if (quest.Rewards.Count > 1) + { + // TODO: Is this what this is for? Does "Only one of the following" occur? + AddHtmlLocalized(100, 140, 312, 16, 1072208, 0x2710, false, false); // All of the following + y += 16; + } - AddRewards( quest, 107, y, 26 ); - } + AddRewards(quest, 107, y, 26); + } - public void AddRewards( MLQuest quest, int x, int y, int spacing ) - { - int xReward = x + 28; + public void AddRewards(MLQuest quest, int x, int y, int spacing) + { + int xReward = x + 28; - foreach ( BaseReward reward in quest.Rewards ) - { - AddImage( x, y + 1, 0x4B9 ); - reward.WriteToGump( this, xReward, ref y ); - y += spacing; - } - } + foreach (BaseReward reward in quest.Rewards) + { + AddImage(x, y + 1, 0x4B9); + reward.WriteToGump(this, xReward, ref y); + y += spacing; + } + } - public void AddConversation( TextDefinition text ) - { - TextDefinition.AddHtmlText( this, 98, 140, 312, 180, text, false, true, 0x15F90, 0xBDE784 ); - } + public void AddConversation(TextDefinition text) + { + TextDefinition.AddHtmlText(this, 98, 140, 312, 180, text, false, true, 0x15F90, 0xBDE784); + } - #endregion + #endregion - /* OSI gump IDs: - * 800 - QuestOfferGump - * 801 - QuestCancelConfirmGump - * 802 - ?? (gets closed by Toggle Quest Item) - * 803 - QuestRewardGump - * 804 - ?? (gets closed by Toggle Quest Item) - * 805 - QuestLogGump - * 806 - QuestConversationGump (refuse / in progress) - * 807 - ?? (gets closed by Toggle Quest Item and most quest gumps) - * 808 - InfoNPCGump - * 809 - QuestLogDetailedGump - * 810 - QuestReportBackGump - */ - public static void CloseOtherGumps( PlayerMobile pm ) - { - pm.CloseGump( typeof( InfoNPCGump ) ); - pm.CloseGump( typeof( QuestRewardGump ) ); - pm.CloseGump( typeof( QuestConversationGump ) ); - pm.CloseGump( typeof( QuestReportBackGump ) ); - //pm.CloseGump( typeof( UnknownGump807 ) ); - pm.CloseGump( typeof( QuestCancelConfirmGump ) ); - } - } -} + /* OSI gump IDs: + * 800 - QuestOfferGump + * 801 - QuestCancelConfirmGump + * 802 - ?? (gets closed by Toggle Quest Item) + * 803 - QuestRewardGump + * 804 - ?? (gets closed by Toggle Quest Item) + * 805 - QuestLogGump + * 806 - QuestConversationGump (refuse / in progress) + * 807 - ?? (gets closed by Toggle Quest Item and most quest gumps) + * 808 - InfoNPCGump + * 809 - QuestLogDetailedGump + * 810 - QuestReportBackGump + */ + public static void CloseOtherGumps(PlayerMobile pm) + { + pm.CloseGump(typeof(InfoNPCGump)); + pm.CloseGump(typeof(QuestRewardGump)); + pm.CloseGump(typeof(QuestConversationGump)); + pm.CloseGump(typeof(QuestReportBackGump)); + //pm.CloseGump( typeof( UnknownGump807 ) ); + pm.CloseGump(typeof(QuestCancelConfirmGump)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/InfoNPCGump.cs b/Scripts/Engines/MLQuests/Gumps/InfoNPCGump.cs index 0eef12b43..7e9a3a379 100644 --- a/Scripts/Engines/MLQuests/Gumps/InfoNPCGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/InfoNPCGump.cs @@ -1,17 +1,17 @@ namespace Server.Engines.MLQuests.Gumps { - public class InfoNPCGump : BaseQuestGump - { - public InfoNPCGump( TextDefinition title, TextDefinition message ) - : base( 1060668 ) // INFORMATION - { - RegisterButton( ButtonPosition.Left, ButtonGraphic.Close, 3 ); + public class InfoNPCGump : BaseQuestGump + { + public InfoNPCGump(TextDefinition title, TextDefinition message) + : base(1060668) // INFORMATION + { + RegisterButton(ButtonPosition.Left, ButtonGraphic.Close, 3); - SetPageCount( 1 ); + SetPageCount(1); - BuildPage(); - TextDefinition.AddHtmlText( this, 160, 108, 250, 16, title, false, false, 0x2710, 0x4AC684 ); - TextDefinition.AddHtmlText( this, 98, 156, 312, 180, message, false, true, 0x15F90, 0xBDE784 ); - } - } -} + BuildPage(); + TextDefinition.AddHtmlText(this, 160, 108, 250, 16, title, false, false, 0x2710, 0x4AC684); + TextDefinition.AddHtmlText(this, 98, 156, 312, 180, message, false, true, 0x15F90, 0xBDE784); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestCancelConfirmGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestCancelConfirmGump.cs index f2b5b99c6..708f68268 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestCancelConfirmGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestCancelConfirmGump.cs @@ -3,100 +3,101 @@ using Server.Network; namespace Server.Engines.MLQuests.Gumps { - public class QuestCancelConfirmGump : Gump - { - private MLQuestInstance m_Instance; - private bool m_CloseGumps; + public class QuestCancelConfirmGump : Gump + { + private bool m_CloseGumps; + private MLQuestInstance m_Instance; - public QuestCancelConfirmGump( MLQuestInstance instance ) - : this( instance, true ) - { - } + public QuestCancelConfirmGump(MLQuestInstance instance) + : this(instance, true) + { + } - public QuestCancelConfirmGump( MLQuestInstance instance, bool closeGumps ) - : base( 120, 50 ) - { - m_Instance = instance; - m_CloseGumps = closeGumps; + public QuestCancelConfirmGump(MLQuestInstance instance, bool closeGumps) + : base(120, 50) + { + m_Instance = instance; + m_CloseGumps = closeGumps; - if ( closeGumps ) - BaseQuestGump.CloseOtherGumps( instance.Player ); + if (closeGumps) + BaseQuestGump.CloseOtherGumps(instance.Player); - AddPage( 0 ); + AddPage(0); - Closable = false; + Closable = false; - AddImageTiled( 0, 0, 348, 262, 0xA8E ); - AddAlphaRegion( 0, 0, 348, 262 ); + AddImageTiled(0, 0, 348, 262, 0xA8E); + AddAlphaRegion(0, 0, 348, 262); - AddImage( 0, 15, 0x27A8 ); - AddImageTiled( 0, 30, 17, 200, 0x27A7 ); - AddImage( 0, 230, 0x27AA ); + AddImage(0, 15, 0x27A8); + AddImageTiled(0, 30, 17, 200, 0x27A7); + AddImage(0, 230, 0x27AA); - AddImage( 15, 0, 0x280C ); - AddImageTiled( 30, 0, 300, 17, 0x280A ); - AddImage( 315, 0, 0x280E ); + AddImage(15, 0, 0x280C); + AddImageTiled(30, 0, 300, 17, 0x280A); + AddImage(315, 0, 0x280E); - AddImage( 15, 244, 0x280C ); - AddImageTiled( 30, 244, 300, 17, 0x280A ); - AddImage( 315, 244, 0x280E ); + AddImage(15, 244, 0x280C); + AddImageTiled(30, 244, 300, 17, 0x280A); + AddImage(315, 244, 0x280E); - AddImage( 330, 15, 0x27A8 ); - AddImageTiled( 330, 30, 17, 200, 0x27A7 ); - AddImage( 330, 230, 0x27AA ); + AddImage(330, 15, 0x27A8); + AddImageTiled(330, 30, 17, 200, 0x27A7); + AddImage(330, 230, 0x27AA); - AddImage( 333, 2, 0x2716 ); - AddImage( 333, 248, 0x2716 ); - AddImage( 2, 248, 0x2716 ); - AddImage( 2, 2, 0x2716 ); + AddImage(333, 2, 0x2716); + AddImage(333, 248, 0x2716); + AddImage(2, 248, 0x2716); + AddImage(2, 2, 0x2716); - AddHtmlLocalized( 25, 22, 200, 20, 1049000, 0x7D00, false, false ); // Confirm Quest Cancellation - AddImage( 25, 40, 0xBBF ); + AddHtmlLocalized(25, 22, 200, 20, 1049000, 0x7D00, false, false); // Confirm Quest Cancellation + AddImage(25, 40, 0xBBF); - /* - * This quest will give you valuable information, skills - * and equipment that will help you advance in the - * game at a quicker pace.
- *
- * Are you certain you wish to cancel at this time? - */ - AddHtmlLocalized( 25, 55, 300, 120, 1060836, 0xFFFFFF, false, false ); + /* + * This quest will give you valuable information, skills + * and equipment that will help you advance in the + * game at a quicker pace.
+ *
+ * Are you certain you wish to cancel at this time? + */ + AddHtmlLocalized(25, 55, 300, 120, 1060836, 0xFFFFFF, false, false); - MLQuest quest = instance.Quest; + MLQuest quest = instance.Quest; - if ( quest.IsChainTriggered || quest.NextQuest != null ) - { - AddRadio( 25, 145, 0x25F8, 0x25FB, false, 2 ); - AddHtmlLocalized( 60, 150, 280, 20, 1075023, 0xFFFFFF, false, false ); // Yes, I want to quit this entire chain! - } + if (quest.IsChainTriggered || quest.NextQuest != null) + { + AddRadio(25, 145, 0x25F8, 0x25FB, false, 2); + AddHtmlLocalized(60, 150, 280, 20, 1075023, 0xFFFFFF, false, + false); // Yes, I want to quit this entire chain! + } - AddRadio( 25, 180, 0x25F8, 0x25FB, true, 1 ); - AddHtmlLocalized( 60, 185, 280, 20, 1049005, 0xFFFFFF, false, false ); // Yes, I really want to quit this quest! + AddRadio(25, 180, 0x25F8, 0x25FB, true, 1); + AddHtmlLocalized(60, 185, 280, 20, 1049005, 0xFFFFFF, false, false); // Yes, I really want to quit this quest! - AddRadio( 25, 215, 0x25F8, 0x25FB, false, 0 ); - AddHtmlLocalized( 60, 220, 280, 20, 1049006, 0xFFFFFF, false, false ); // No, I don't want to quit. + AddRadio(25, 215, 0x25F8, 0x25FB, false, 0); + AddHtmlLocalized(60, 220, 280, 20, 1049006, 0xFFFFFF, false, false); // No, I don't want to quit. - AddButton( 265, 220, 0xF7, 0xF8, 7, GumpButtonType.Reply, 0 ); - } + AddButton(265, 220, 0xF7, 0xF8, 7, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Instance.Removed ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Instance.Removed) + return; - switch ( info.ButtonID ) - { - case 7: // Okay - { - if ( info.IsSwitched( 2 ) ) - m_Instance.Cancel( true ); - else if ( info.IsSwitched( 1 ) ) - m_Instance.Cancel( false ); + switch (info.ButtonID) + { + case 7: // Okay + { + if (info.IsSwitched(2)) + m_Instance.Cancel(true); + else if (info.IsSwitched(1)) + m_Instance.Cancel(false); - sender.Mobile.SendGump( new QuestLogGump( m_Instance.Player, m_CloseGumps ) ); - break; - } - } - } - } -} + sender.Mobile.SendGump(new QuestLogGump(m_Instance.Player, m_CloseGumps)); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestConversationGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestConversationGump.cs index 366db7e97..5dd13de67 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestConversationGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestConversationGump.cs @@ -2,20 +2,20 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Gumps { - public class QuestConversationGump : BaseQuestGump - { - public QuestConversationGump( MLQuest quest, PlayerMobile pm, TextDefinition text ) - : base( 3006156 ) // Quest Conversation - { - CloseOtherGumps( pm ); + public class QuestConversationGump : BaseQuestGump + { + public QuestConversationGump(MLQuest quest, PlayerMobile pm, TextDefinition text) + : base(3006156) // Quest Conversation + { + CloseOtherGumps(pm); - SetTitle( quest.Title ); - RegisterButton( ButtonPosition.Right, ButtonGraphic.Close, 3 ); + SetTitle(quest.Title); + RegisterButton(ButtonPosition.Right, ButtonGraphic.Close, 3); - SetPageCount( 1 ); + SetPageCount(1); - BuildPage(); - AddConversation( text ); - } - } -} + BuildPage(); + AddConversation(text); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestLogDetailedGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestLogDetailedGump.cs index 6cd322cee..5ba989daa 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestLogDetailedGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestLogDetailedGump.cs @@ -4,75 +4,75 @@ using Server.Network; namespace Server.Engines.MLQuests.Gumps { - public class QuestLogDetailedGump : BaseQuestGump - { - private MLQuestInstance m_Instance; - private bool m_CloseGumps; + public class QuestLogDetailedGump : BaseQuestGump + { + private bool m_CloseGumps; + private MLQuestInstance m_Instance; - public QuestLogDetailedGump( MLQuestInstance instance ) - : this( instance, true ) - { - } + public QuestLogDetailedGump(MLQuestInstance instance) + : this(instance, true) + { + } - public QuestLogDetailedGump( MLQuestInstance instance, bool closeGumps ) - : base( 1046026 ) // Quest Log - { - m_Instance = instance; - m_CloseGumps = closeGumps; + public QuestLogDetailedGump(MLQuestInstance instance, bool closeGumps) + : base(1046026) // Quest Log + { + m_Instance = instance; + m_CloseGumps = closeGumps; - PlayerMobile pm = instance.Player; - MLQuest quest = instance.Quest; + PlayerMobile pm = instance.Player; + MLQuest quest = instance.Quest; - if ( closeGumps ) - { - CloseOtherGumps( pm ); - pm.CloseGump( typeof( QuestLogDetailedGump ) ); - } + if (closeGumps) + { + CloseOtherGumps(pm); + pm.CloseGump(typeof(QuestLogDetailedGump)); + } - SetTitle( quest.Title ); - RegisterButton( ButtonPosition.Left, ButtonGraphic.Resign, 1 ); - RegisterButton( ButtonPosition.Right, ButtonGraphic.Okay, 2 ); + SetTitle(quest.Title); + RegisterButton(ButtonPosition.Left, ButtonGraphic.Resign, 1); + RegisterButton(ButtonPosition.Right, ButtonGraphic.Okay, 2); - SetPageCount( 3 ); + SetPageCount(3); - BuildPage(); - AddDescription( quest ); + BuildPage(); + AddDescription(quest); - if ( instance.Failed ) // only displayed on the first page - AddHtmlLocalized( 160, 80, 250, 16, 500039, 0x3C00, false, false ); // Failed! + if (instance.Failed) // only displayed on the first page + AddHtmlLocalized(160, 80, 250, 16, 500039, 0x3C00, false, false); // Failed! - BuildPage(); - AddObjectivesProgress( instance ); + BuildPage(); + AddObjectivesProgress(instance); - BuildPage(); - AddRewardsPage( quest ); - } + BuildPage(); + AddRewardsPage(quest); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Instance.Removed ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Instance.Removed) + return; - switch ( info.ButtonID ) - { - case 1: // Resign - { - // TODO: Custom reward loss protection? OSI doesn't have this - //if ( m_Instance.ClaimReward ) - // pm.SendMessage( "You cannot cancel a quest with rewards pending." ); - //else + switch (info.ButtonID) + { + case 1: // Resign + { + // TODO: Custom reward loss protection? OSI doesn't have this + //if ( m_Instance.ClaimReward ) + // pm.SendMessage( "You cannot cancel a quest with rewards pending." ); + //else - sender.Mobile.SendGump( new QuestCancelConfirmGump( m_Instance, m_CloseGumps ) ); + sender.Mobile.SendGump(new QuestCancelConfirmGump(m_Instance, m_CloseGumps)); - break; - } - case 2: // Okay - { - sender.Mobile.SendGump( new QuestLogGump( m_Instance.Player, m_CloseGumps ) ); + break; + } + case 2: // Okay + { + sender.Mobile.SendGump(new QuestLogGump(m_Instance.Player, m_CloseGumps)); - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestLogGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestLogGump.cs index 43004b3dc..1ee375daf 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestLogGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestLogGump.cs @@ -5,77 +5,78 @@ using Server.Network; namespace Server.Engines.MLQuests.Gumps { - public class QuestLogGump : BaseQuestGump - { - private PlayerMobile m_Owner; - private bool m_CloseGumps; + public class QuestLogGump : BaseQuestGump + { + private bool m_CloseGumps; + private PlayerMobile m_Owner; - public QuestLogGump( PlayerMobile pm ) - : this( pm, true ) - { - } + public QuestLogGump(PlayerMobile pm) + : this(pm, true) + { + } - public QuestLogGump( PlayerMobile pm, bool closeGumps ) - : base( 1046026 ) // Quest Log - { - m_Owner = pm; - m_CloseGumps = closeGumps; + public QuestLogGump(PlayerMobile pm, bool closeGumps) + : base(1046026) // Quest Log + { + m_Owner = pm; + m_CloseGumps = closeGumps; - if ( closeGumps ) - { - pm.CloseGump( typeof( QuestLogGump ) ); - pm.CloseGump( typeof( QuestLogDetailedGump ) ); - } + if (closeGumps) + { + pm.CloseGump(typeof(QuestLogGump)); + pm.CloseGump(typeof(QuestLogDetailedGump)); + } - RegisterButton( ButtonPosition.Right, ButtonGraphic.Okay, 3 ); + RegisterButton(ButtonPosition.Right, ButtonGraphic.Okay, 3); - SetPageCount( 1 ); + SetPageCount(1); - BuildPage(); + BuildPage(); - int numberColor, stringColor; + int numberColor, stringColor; - MLQuestContext context = MLQuestSystem.GetContext( pm ); + MLQuestContext context = MLQuestSystem.GetContext(pm); - if ( context != null ) - { - List instances = context.QuestInstances; + if (context != null) + { + List instances = context.QuestInstances; - for ( int i = 0; i < instances.Count; ++i ) - { - if ( instances[i].Failed ) - { - numberColor = 0x3C00; - stringColor = 0x7B0000; - } - else - { - numberColor = stringColor = 0xFFFFFF; - } + for (int i = 0; i < instances.Count; ++i) + { + if (instances[i].Failed) + { + numberColor = 0x3C00; + stringColor = 0x7B0000; + } + else + { + numberColor = stringColor = 0xFFFFFF; + } - TextDefinition.AddHtmlText( this, 98, 140 + 21 * i, 270, 21, instances[i].Quest.Title, false, false, numberColor, stringColor ); - AddButton( 368, 140 + 21 * i, 0x26B0, 0x26B1, 6 + i, GumpButtonType.Reply, 1 ); - } - } - } + TextDefinition.AddHtmlText(this, 98, 140 + 21 * i, 270, 21, instances[i].Quest.Title, false, false, + numberColor, stringColor); + AddButton(368, 140 + 21 * i, 0x26B0, 0x26B1, 6 + i, GumpButtonType.Reply, 1); + } + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID < 6 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID < 6) + return; - MLQuestContext context = MLQuestSystem.GetContext( m_Owner ); + MLQuestContext context = MLQuestSystem.GetContext(m_Owner); - if ( context == null ) - return; + if (context == null) + return; - List instances = context.QuestInstances; - int index = info.ButtonID - 6; + List instances = context.QuestInstances; + int index = info.ButtonID - 6; - if ( index >= instances.Count ) - return; + if (index >= instances.Count) + return; - sender.Mobile.SendGump( new QuestLogDetailedGump( instances[index], m_CloseGumps ) ); - } - } -} + sender.Mobile.SendGump(new QuestLogDetailedGump(instances[index], m_CloseGumps)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestOfferGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestOfferGump.cs index 2ef7f137a..f86c62b12 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestOfferGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestOfferGump.cs @@ -4,54 +4,54 @@ using Server.Network; namespace Server.Engines.MLQuests.Gumps { - public class QuestOfferGump : BaseQuestGump - { - private MLQuest m_Quest; - private IQuestGiver m_Quester; + public class QuestOfferGump : BaseQuestGump + { + private MLQuest m_Quest; + private IQuestGiver m_Quester; - public QuestOfferGump( MLQuest quest, IQuestGiver quester, PlayerMobile pm ) - : base( 1049010 ) // Quest Offer - { - m_Quest = quest; - m_Quester = quester; + public QuestOfferGump(MLQuest quest, IQuestGiver quester, PlayerMobile pm) + : base(1049010) // Quest Offer + { + m_Quest = quest; + m_Quester = quester; - CloseOtherGumps( pm ); - pm.CloseGump( typeof( QuestOfferGump ) ); + CloseOtherGumps(pm); + pm.CloseGump(typeof(QuestOfferGump)); - SetTitle( quest.Title ); - RegisterButton( ButtonPosition.Left, ButtonGraphic.Accept, 1 ); - RegisterButton( ButtonPosition.Right, ButtonGraphic.Refuse, 2 ); + SetTitle(quest.Title); + RegisterButton(ButtonPosition.Left, ButtonGraphic.Accept, 1); + RegisterButton(ButtonPosition.Right, ButtonGraphic.Refuse, 2); - SetPageCount( 3 ); + SetPageCount(3); - BuildPage(); - AddDescription( quest ); + BuildPage(); + AddDescription(quest); - BuildPage(); - AddObjectives( quest ); + BuildPage(); + AddObjectives(quest); - BuildPage(); - AddRewardsPage( quest ); - } + BuildPage(); + AddRewardsPage(quest); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !(sender.Mobile is PlayerMobile pm) ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!(sender.Mobile is PlayerMobile pm)) + return; - switch ( info.ButtonID ) - { - case 1: // Accept - { - m_Quest.OnAccept( m_Quester, pm ); - break; - } - case 2: // Refuse - { - m_Quest.OnRefuse( m_Quester, pm ); - break; - } - } - } - } -} + switch (info.ButtonID) + { + case 1: // Accept + { + m_Quest.OnAccept(m_Quester, pm); + break; + } + case 2: // Refuse + { + m_Quest.OnRefuse(m_Quester, pm); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestReportBackGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestReportBackGump.cs index b8420f861..26c8f596c 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestReportBackGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestReportBackGump.cs @@ -4,35 +4,35 @@ using Server.Network; namespace Server.Engines.MLQuests.Gumps { - public class QuestReportBackGump : BaseQuestGump - { - private MLQuestInstance m_Instance; + public class QuestReportBackGump : BaseQuestGump + { + private MLQuestInstance m_Instance; - public QuestReportBackGump( MLQuestInstance instance ) - : base( 3006156 ) // Quest Conversation - { - m_Instance = instance; + public QuestReportBackGump(MLQuestInstance instance) + : base(3006156) // Quest Conversation + { + m_Instance = instance; - MLQuest quest = instance.Quest; - PlayerMobile pm = instance.Player; + MLQuest quest = instance.Quest; + PlayerMobile pm = instance.Player; - // TODO: Check close sequence - CloseOtherGumps( pm ); + // TODO: Check close sequence + CloseOtherGumps(pm); - SetTitle( quest.Title ); - RegisterButton( ButtonPosition.Left, ButtonGraphic.Continue, 4 ); - RegisterButton( ButtonPosition.Right, ButtonGraphic.Close, 3 ); + SetTitle(quest.Title); + RegisterButton(ButtonPosition.Left, ButtonGraphic.Continue, 4); + RegisterButton(ButtonPosition.Right, ButtonGraphic.Close, 3); - SetPageCount( 1 ); + SetPageCount(1); - BuildPage(); - AddConversation( quest.CompletionMessage ); - } + BuildPage(); + AddConversation(quest.CompletionMessage); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 4 ) - m_Instance.ContinueReportBack( true ); - } - } -} + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 4) + m_Instance.ContinueReportBack(true); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/QuestRewardGump.cs b/Scripts/Engines/MLQuests/Gumps/QuestRewardGump.cs index 2ca50e65b..60bf5a53a 100644 --- a/Scripts/Engines/MLQuests/Gumps/QuestRewardGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/QuestRewardGump.cs @@ -4,33 +4,33 @@ using Server.Network; namespace Server.Engines.MLQuests.Gumps { - public class QuestRewardGump : BaseQuestGump - { - private MLQuestInstance m_Instance; + public class QuestRewardGump : BaseQuestGump + { + private MLQuestInstance m_Instance; - public QuestRewardGump( MLQuestInstance instance ) - : base( 1072201 ) // Reward - { - m_Instance = instance; + public QuestRewardGump(MLQuestInstance instance) + : base(1072201) // Reward + { + m_Instance = instance; - MLQuest quest = instance.Quest; - PlayerMobile pm = instance.Player; + MLQuest quest = instance.Quest; + PlayerMobile pm = instance.Player; - CloseOtherGumps( pm ); + CloseOtherGumps(pm); - SetTitle( quest.Title ); - RegisterButton( ButtonPosition.Left, ButtonGraphic.Accept, 1 ); + SetTitle(quest.Title); + RegisterButton(ButtonPosition.Left, ButtonGraphic.Accept, 1); - SetPageCount( 1 ); + SetPageCount(1); - BuildPage(); - AddRewards( quest ); - } + BuildPage(); + AddRewards(quest); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Instance.ClaimRewards(); - } - } -} + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_Instance.ClaimRewards(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Gumps/RaceChangeGump.cs b/Scripts/Engines/MLQuests/Gumps/RaceChangeGump.cs index 6fa52e396..69208f4bf 100644 --- a/Scripts/Engines/MLQuests/Gumps/RaceChangeGump.cs +++ b/Scripts/Engines/MLQuests/Gumps/RaceChangeGump.cs @@ -10,334 +10,336 @@ using Server.Spells.Seventh; namespace Server.Engines.MLQuests.Gumps { - public interface IRaceChanger - { - bool CheckComplete( PlayerMobile from ); - void ConsumeNeeded( PlayerMobile from ); - void OnCancel( PlayerMobile from ); - } + public interface IRaceChanger + { + bool CheckComplete(PlayerMobile from); + void ConsumeNeeded(PlayerMobile from); + void OnCancel(PlayerMobile from); + } - public class RaceChangeConfirmGump : Gump - { - public static readonly Type Type = typeof( RaceChangeConfirmGump ); + public class RaceChangeConfirmGump : Gump + { + public static readonly Type Type = typeof(RaceChangeConfirmGump); - private IRaceChanger m_Owner; - private PlayerMobile m_From; - private Race m_Race; + private static Dictionary m_Pending; + private PlayerMobile m_From; - public RaceChangeConfirmGump( IRaceChanger owner, PlayerMobile from, Race targetRace ) - : base( 50, 50 ) - { - from.CloseGump( Type ); + private IRaceChanger m_Owner; + private Race m_Race; - m_Owner = owner; - m_From = from; - m_Race = targetRace; + public RaceChangeConfirmGump(IRaceChanger owner, PlayerMobile from, Race targetRace) + : base(50, 50) + { + from.CloseGump(Type); - AddPage( 0 ); - AddBackground( 0, 0, 240, 135, 0x2422 ); + m_Owner = owner; + m_From = from; + m_Race = targetRace; - if ( targetRace == Race.Human ) - AddHtmlLocalized( 15, 15, 210, 75, 1073643, 0, false, false ); // Are you sure you wish to embrace your humanity? - else if ( targetRace == Race.Elf ) - AddHtmlLocalized( 15, 15, 210, 75, 1073642, 0, false, false ); // Are you sure you want to follow the elven ways? - else - AddHtml( 15, 15, 210, 75, $"Are you sure you want to change your race to {targetRace.Name}?", false, false ); + AddPage(0); + AddBackground(0, 0, 240, 135, 0x2422); - AddButton( 160, 95, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0 ); - AddButton( 90, 95, 0xF2, 0xF1, 0, GumpButtonType.Reply, 0 ); - } + if (targetRace == Race.Human) + AddHtmlLocalized(15, 15, 210, 75, 1073643, 0, false, + false); // Are you sure you wish to embrace your humanity? + else if (targetRace == Race.Elf) + AddHtmlLocalized(15, 15, 210, 75, 1073642, 0, false, + false); // Are you sure you want to follow the elven ways? + else + AddHtml(15, 15, 210, 75, $"Are you sure you want to change your race to {targetRace.Name}?", false, false); - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 0: // Cancel - { - m_Owner?.OnCancel( m_From ); + AddButton(160, 95, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0); + AddButton(90, 95, 0xF2, 0xF1, 0, GumpButtonType.Reply, 0); + } - break; - } - case 1: // Okay - { - if ( m_Owner == null || m_Owner.CheckComplete( m_From ) ) - Offer( m_Owner, m_From, m_Race ); + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 0: // Cancel + { + m_Owner?.OnCancel(m_From); - break; - } - } - } + break; + } + case 1: // Okay + { + if (m_Owner == null || m_Owner.CheckComplete(m_From)) + Offer(m_Owner, m_From, m_Race); - private class RaceChangeState - { - private static readonly TimeSpan m_TimeoutDelay = TimeSpan.FromMinutes( 1 ); - private static readonly TimerStateCallback m_TimeoutCallback = Timeout; + break; + } + } + } - public IRaceChanger m_Owner; - public Race m_TargetRace; - public Timer m_Timeout; + public static void Initialize() + { + m_Pending = new Dictionary(); - public RaceChangeState( IRaceChanger owner, NetState ns, Race targetRace ) - { - m_Owner = owner; - m_TargetRace = targetRace; - m_Timeout = Timer.DelayCall( m_TimeoutDelay, m_TimeoutCallback, ns ); - } - } + PacketHandlers.RegisterExtended(0x2A, true, RaceChangeReply); + } - private static Dictionary m_Pending; + public static bool IsPending(NetState state) + { + return state != null && m_Pending.ContainsKey(state); + } - public static void Initialize() - { - m_Pending = new Dictionary(); + private static void Offer(IRaceChanger owner, PlayerMobile from, Race targetRace) + { + NetState ns = from.NetState; - PacketHandlers.RegisterExtended( 0x2A, true, RaceChangeReply ); - } + if (ns == null || !CanChange(from, targetRace)) + return; - public static bool IsPending( NetState state ) - { - return ( state != null && m_Pending.ContainsKey( state ) ); - } + CloseCurrent(ns); - private static void Offer( IRaceChanger owner, PlayerMobile from, Race targetRace ) - { - NetState ns = from.NetState; + m_Pending[ns] = new RaceChangeState(owner, ns, targetRace); + ns.Send(new RaceChanger(from.Female, targetRace)); + } - if ( ns == null || !CanChange( from, targetRace ) ) - return; + private static void CloseCurrent(NetState ns) + { + if (m_Pending.TryGetValue(ns, out RaceChangeState state)) + { + state.m_Timeout.Stop(); + m_Pending.Remove(ns); + } - CloseCurrent( ns ); + ns.Send(CloseRaceChanger.Instance); + } - m_Pending[ns] = new RaceChangeState( owner, ns, targetRace ); - ns.Send( new RaceChanger( from.Female, targetRace ) ); - } + private static void Timeout(NetState ns) + { + if (m_Pending.ContainsKey(ns)) + { + m_Pending.Remove(ns); + ns.Send(CloseRaceChanger.Instance); + } + } - private static void CloseCurrent( NetState ns ) - { - if (m_Pending.TryGetValue( ns, out RaceChangeState state )) - { - state.m_Timeout.Stop(); - m_Pending.Remove( ns ); - } + public static bool IsWearingEquipment(Mobile from) + { + foreach (Item item in from.Items) + switch (item.Layer) + { + case Layer.Hair: + case Layer.FacialHair: + case Layer.Backpack: + case Layer.Mount: + case Layer.Bank: + { + continue; // ignore + } + default: + { + return true; + } + } - ns.Send( CloseRaceChanger.Instance ); - } + return false; + } - private static void Timeout( NetState ns ) - { - if ( m_Pending.ContainsKey( ns ) ) - { - m_Pending.Remove( ns ); - ns.Send( CloseRaceChanger.Instance ); - } - } + private static bool CanChange(PlayerMobile from, Race targetRace) + { + if (from.Deleted) + return false; - public static bool IsWearingEquipment( Mobile from ) - { - foreach ( Item item in from.Items ) - { - switch ( item.Layer ) - { - case Layer.Hair: - case Layer.FacialHair: - case Layer.Backpack: - case Layer.Mount: - case Layer.Bank: - { - continue; // ignore - } - default: - { - return true; - } - } - } + if (from.Race == targetRace) + from.SendLocalizedMessage(1111918); // You are already that race. + else if (!MondainsLegacy.CheckML(from, false)) + from.SendLocalizedMessage(1073651); // You must have Mondain's Legacy before proceeding... + else if (!from.Alive) + from.SendLocalizedMessage(1073646); // Only the living may proceed... + else if (from.Mounted) + from.SendLocalizedMessage(1073647); // You may not continue while mounted... + else if (!from.CanBeginAction(typeof(PolymorphSpell)) || DisguiseTimers.IsDisguised(from) || + AnimalForm.UnderTransformation(from) || !from.CanBeginAction(typeof(IncognitoSpell)) || + from.IsBodyMod) // TODO: Does this cover everything? + from.SendLocalizedMessage(1073648); // You may only proceed while in your original state... + else if (from.Spell != null && from.Spell.IsCasting) + from.SendLocalizedMessage(1073649); // One may not proceed while embracing magic... + else if (from.Poisoned) + from.SendLocalizedMessage(1073652); // You must be healthy to proceed... + else if (IsWearingEquipment(from)) + from.SendLocalizedMessage(1073650); // To proceed you must be unburdened by equipment... + else + return true; - return false; - } + return false; + } - private static bool CanChange( PlayerMobile from, Race targetRace ) - { - if ( from.Deleted ) - return false; + private static void RaceChangeReply(NetState state, PacketReader pvSrc) + { + if (!m_Pending.TryGetValue(state, out RaceChangeState raceChangeState)) + return; - if ( from.Race == targetRace ) - from.SendLocalizedMessage( 1111918 ); // You are already that race. - else if ( !MondainsLegacy.CheckML( from, false ) ) - from.SendLocalizedMessage( 1073651 ); // You must have Mondain's Legacy before proceeding... - else if ( !from.Alive ) - from.SendLocalizedMessage( 1073646 ); // Only the living may proceed... - else if ( from.Mounted ) - from.SendLocalizedMessage( 1073647 ); // You may not continue while mounted... - else if ( !from.CanBeginAction( typeof( PolymorphSpell ) ) || DisguiseTimers.IsDisguised( from ) || AnimalForm.UnderTransformation( from ) || !from.CanBeginAction( typeof( IncognitoSpell ) ) || from.IsBodyMod ) // TODO: Does this cover everything? - from.SendLocalizedMessage( 1073648 ); // You may only proceed while in your original state... - else if ( from.Spell != null && from.Spell.IsCasting ) - from.SendLocalizedMessage( 1073649 ); // One may not proceed while embracing magic... - else if ( from.Poisoned ) - from.SendLocalizedMessage( 1073652 ); // You must be healthy to proceed... - else if ( IsWearingEquipment( from ) ) - from.SendLocalizedMessage( 1073650 ); // To proceed you must be unburdened by equipment... - else - return true; + CloseCurrent(state); - return false; - } + if (!(state.Mobile is PlayerMobile pm)) + return; - private static void RaceChangeReply( NetState state, PacketReader pvSrc ) - { - if (!m_Pending.TryGetValue( state, out RaceChangeState raceChangeState )) - return; + IRaceChanger owner = raceChangeState.m_Owner; + Race targetRace = raceChangeState.m_TargetRace; - CloseCurrent( state ); + if (pvSrc.Size == 5) + { + owner?.OnCancel(pm); - if ( !(state.Mobile is PlayerMobile pm) ) - return; + return; + } - IRaceChanger owner = raceChangeState.m_Owner; - Race targetRace = raceChangeState.m_TargetRace; + if (!CanChange(pm, targetRace) || owner != null && !owner.CheckComplete(pm)) + return; - if ( pvSrc.Size == 5 ) - { - owner?.OnCancel( pm ); + int hue = pvSrc.ReadUInt16(); + int hairItemId = pvSrc.ReadUInt16(); + int hairHue = pvSrc.ReadUInt16(); + int facialHairItemId = pvSrc.ReadUInt16(); + int facialHairHue = pvSrc.ReadUInt16(); - return; - } + pm.Race = targetRace; + pm.Hue = targetRace.ClipSkinHue(hue) | 0x8000; - if ( !CanChange( pm, targetRace ) || ( owner != null && !owner.CheckComplete( pm ) ) ) - return; + if (targetRace.ValidateHair(pm, hairItemId)) + { + pm.HairItemID = hairItemId; + pm.HairHue = targetRace.ClipHairHue(hairHue); + } + else + { + pm.HairItemID = 0; + } - int hue = pvSrc.ReadUInt16(); - int hairItemId = pvSrc.ReadUInt16(); - int hairHue = pvSrc.ReadUInt16(); - int facialHairItemId = pvSrc.ReadUInt16(); - int facialHairHue = pvSrc.ReadUInt16(); + if (targetRace.ValidateFacialHair(pm, facialHairItemId)) + { + pm.FacialHairItemID = facialHairItemId; + pm.FacialHairHue = targetRace.ClipHairHue(facialHairHue); + } + else + { + pm.FacialHairItemID = 0; + } - pm.Race = targetRace; - pm.Hue = targetRace.ClipSkinHue( hue ) | 0x8000; + if (targetRace == Race.Human) + pm.SendLocalizedMessage(1073654); // You are now fully human. + else if (targetRace == Race.Elf) + pm.SendLocalizedMessage(1073653); // You are now fully initiated into the Elven culture. + else + pm.SendMessage("You have fully changed your race to {0}.", targetRace.Name); - if ( targetRace.ValidateHair( pm, hairItemId ) ) - { - pm.HairItemID = hairItemId; - pm.HairHue = targetRace.ClipHairHue( hairHue ); - } - else - { - pm.HairItemID = 0; - } + owner?.ConsumeNeeded(pm); + } - if ( targetRace.ValidateFacialHair( pm, facialHairItemId ) ) - { - pm.FacialHairItemID = facialHairItemId; - pm.FacialHairHue = targetRace.ClipHairHue( facialHairHue ); - } - else - { - pm.FacialHairItemID = 0; - } + private class RaceChangeState + { + private static readonly TimeSpan m_TimeoutDelay = TimeSpan.FromMinutes(1); + private static readonly TimerStateCallback m_TimeoutCallback = Timeout; - if ( targetRace == Race.Human ) - pm.SendLocalizedMessage( 1073654 ); // You are now fully human. - else if ( targetRace == Race.Elf ) - pm.SendLocalizedMessage( 1073653 ); // You are now fully initiated into the Elven culture. - else - pm.SendMessage( "You have fully changed your race to {0}.", targetRace.Name ); + public IRaceChanger m_Owner; + public Race m_TargetRace; + public Timer m_Timeout; - owner?.ConsumeNeeded( pm ); - } - } + public RaceChangeState(IRaceChanger owner, NetState ns, Race targetRace) + { + m_Owner = owner; + m_TargetRace = targetRace; + m_Timeout = Timer.DelayCall(m_TimeoutDelay, m_TimeoutCallback, ns); + } + } + } - public sealed class RaceChanger : Packet - { - public RaceChanger( bool female, Race targetRace ) - : base( 0xBF ) - { - EnsureCapacity( 7 ); + public sealed class RaceChanger : Packet + { + public RaceChanger(bool female, Race targetRace) + : base(0xBF) + { + EnsureCapacity(7); - m_Stream.Write( (short)0x2A ); - m_Stream.Write( (byte)( female ? 1 : 0 ) ); - m_Stream.Write( (byte)( targetRace.RaceID + 1 ) ); - } - } + m_Stream.Write((short)0x2A); + m_Stream.Write((byte)(female ? 1 : 0)); + m_Stream.Write((byte)(targetRace.RaceID + 1)); + } + } - public sealed class CloseRaceChanger : Packet - { - public static readonly Packet Instance = SetStatic( new CloseRaceChanger() ); + public sealed class CloseRaceChanger : Packet + { + public static readonly Packet Instance = SetStatic(new CloseRaceChanger()); - private CloseRaceChanger() - : base( 0xBF ) - { - EnsureCapacity( 7 ); + private CloseRaceChanger() + : base(0xBF) + { + EnsureCapacity(7); - m_Stream.Write( (short)0x2A ); - m_Stream.Write( (byte)0 ); - m_Stream.Write( (byte)0xFF ); - } - } + m_Stream.Write((short)0x2A); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0xFF); + } + } - #region For testing + #region For testing - public class RaceChangeDeed : Item, IRaceChanger - { - public override string DefaultName => "a race change deed"; + public class RaceChangeDeed : Item, IRaceChanger + { + [Constructible] + public RaceChangeDeed() + : base(0x14F0) + { + LootType = LootType.Blessed; + } - [Constructible] - public RaceChangeDeed() - : base( 0x14F0 ) - { - LootType = LootType.Blessed; - } + public RaceChangeDeed(Serial serial) + : base(serial) + { + } - public bool CheckComplete( PlayerMobile pm ) - { - if ( Deleted ) - return false; + public override string DefaultName => "a race change deed"; - if ( !IsChildOf( pm.Backpack ) ) - { - pm.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return false; - } + public bool CheckComplete(PlayerMobile pm) + { + if (Deleted) + return false; - return true; - } + if (!IsChildOf(pm.Backpack)) + { + pm.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return false; + } - public void ConsumeNeeded( PlayerMobile pm ) - { - Consume(); - } + return true; + } - public void OnCancel( PlayerMobile pm ) - { - } + public void ConsumeNeeded(PlayerMobile pm) + { + Consume(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return; + public void OnCancel(PlayerMobile pm) + { + } - if ( CheckComplete( pm ) ) - pm.SendGump( new RaceChangeConfirmGump( this, pm, ( pm.Race == Race.Human ) ? Race.Elf : Race.Human ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (!(from is PlayerMobile pm)) + return; - public RaceChangeDeed( Serial serial ) - : base( serial ) - { - } + if (CheckComplete(pm)) + pm.SendGump(new RaceChangeConfirmGump(this, pm, pm.Race == Race.Human ? Race.Elf : Race.Human)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - #endregion -} + #endregion +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/IQuestGiver.cs b/Scripts/Engines/MLQuests/IQuestGiver.cs index 18a44b15b..3b26f11e1 100644 --- a/Scripts/Engines/MLQuests/IQuestGiver.cs +++ b/Scripts/Engines/MLQuests/IQuestGiver.cs @@ -3,13 +3,13 @@ using System.Collections.Generic; namespace Server.Engines.MLQuests { - public interface IQuestGiver - { - List MLQuests { get; } + public interface IQuestGiver + { + List MLQuests{ get; } - Serial Serial { get; } - bool Deleted { get; } + Serial Serial{ get; } + bool Deleted{ get; } - Type GetType(); - } -} + Type GetType(); + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/ABauble.cs b/Scripts/Engines/MLQuests/Items/ABauble.cs index a14a12366..1ec4e1ef2 100644 --- a/Scripts/Engines/MLQuests/Items/ABauble.cs +++ b/Scripts/Engines/MLQuests/Items/ABauble.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class ABauble : Item - { - public override int LabelNumber => 1073137; // A bauble + public class ABauble : Item + { + [Constructible] + public ABauble() : base(0x23B) + { + LootType = LootType.Blessed; + } - [Constructible] - public ABauble() : base( 0x23B ) - { - LootType = LootType.Blessed; - } + public ABauble(Serial serial) : base(serial) + { + } - public ABauble( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073137; // A bauble - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/APersonalLetterAddressedToAhie.cs b/Scripts/Engines/MLQuests/Items/APersonalLetterAddressedToAhie.cs index a7186e698..a018cbf08 100644 --- a/Scripts/Engines/MLQuests/Items/APersonalLetterAddressedToAhie.cs +++ b/Scripts/Engines/MLQuests/Items/APersonalLetterAddressedToAhie.cs @@ -2,40 +2,40 @@ using System; namespace Server.Items { - public class APersonalLetterAddressedToAhie : TransientItem - { - public override int LabelNumber => 1073128; // A personal letter addressed to: Ahie + public class APersonalLetterAddressedToAhie : TransientItem + { + [Constructible] + public APersonalLetterAddressedToAhie() : base(0x14ED, TimeSpan.FromMinutes(30)) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public APersonalLetterAddressedToAhie(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1073128; // A personal letter addressed to: Ahie - [Constructible] - public APersonalLetterAddressedToAhie() : base( 0x14ED, TimeSpan.FromMinutes( 30 ) ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public APersonalLetterAddressedToAhie( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/AlchemistsBandage.cs b/Scripts/Engines/MLQuests/Items/AlchemistsBandage.cs index c99c06b9b..01ab810c0 100644 --- a/Scripts/Engines/MLQuests/Items/AlchemistsBandage.cs +++ b/Scripts/Engines/MLQuests/Items/AlchemistsBandage.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class AlchemistsBandage : Item - { - public override int LabelNumber => 1075452; // Alchemist's Bandage + public class AlchemistsBandage : Item + { + [Constructible] + public AlchemistsBandage() : base(0xE21) + { + LootType = LootType.Blessed; + Hue = 0x482; + } - public override bool Nontransferable => true; + public AlchemistsBandage(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075452; // Alchemist's Bandage - [Constructible] - public AlchemistsBandage() : base( 0xE21 ) - { - LootType = LootType.Blessed; - Hue = 0x482; - } + public override bool Nontransferable => true; - public AlchemistsBandage( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/AnOldNecklace.cs b/Scripts/Engines/MLQuests/Items/AnOldNecklace.cs index e52092147..e6757ca4a 100644 --- a/Scripts/Engines/MLQuests/Items/AnOldNecklace.cs +++ b/Scripts/Engines/MLQuests/Items/AnOldNecklace.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AnOldNecklace : Necklace - { - public override int LabelNumber => 1075525; // an old necklace + public class AnOldNecklace : Necklace + { + [Constructible] + public AnOldNecklace() + { + Hue = 0x222; + } - [Constructible] - public AnOldNecklace() - { - Hue = 0x222; - } + public AnOldNecklace(Serial serial) : base(serial) + { + } - public AnOldNecklace( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075525; // an old necklace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/AnOldRing.cs b/Scripts/Engines/MLQuests/Items/AnOldRing.cs index 2e13c1366..11086fae2 100644 --- a/Scripts/Engines/MLQuests/Items/AnOldRing.cs +++ b/Scripts/Engines/MLQuests/Items/AnOldRing.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AnOldRing : GoldRing - { - public override int LabelNumber => 1075524; // an old ring + public class AnOldRing : GoldRing + { + [Constructible] + public AnOldRing() + { + Hue = 0x222; + } - [Constructible] - public AnOldRing() - { - Hue = 0x222; - } + public AnOldRing(Serial serial) : base(serial) + { + } - public AnOldRing( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075524; // an old ring - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/AndricSatchel.cs b/Scripts/Engines/MLQuests/Items/AndricSatchel.cs index 1c27c2536..b72eee9a9 100644 --- a/Scripts/Engines/MLQuests/Items/AndricSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/AndricSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class AndricSatchel : Backpack - { - [Constructible] - public AndricSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new Feather( 10 ) ); - DropItem( new FletcherTools() ); - } + public class AndricSatchel : Backpack + { + [Constructible] + public AndricSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new Feather(10)); + DropItem(new FletcherTools()); + } - public AndricSatchel( Serial serial ) - : base( serial ) - { - } + public AndricSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/AndrosGratitude.cs b/Scripts/Engines/MLQuests/Items/AndrosGratitude.cs index 147af7026..489c5c475 100644 --- a/Scripts/Engines/MLQuests/Items/AndrosGratitude.cs +++ b/Scripts/Engines/MLQuests/Items/AndrosGratitude.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AndrosGratitude : SmithHammer - { - public override int LabelNumber => 1075345; // Andros Gratitude + public class AndrosGratitude : SmithHammer + { + [Constructible] + public AndrosGratitude() : base(10) + { + LootType = LootType.Blessed; + } - [Constructible] - public AndrosGratitude() : base( 10 ) - { - LootType = LootType.Blessed; - } + public AndrosGratitude(Serial serial) : base(serial) + { + } - public AndrosGratitude( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075345; // Andros Gratitude - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/AsandosSatchel.cs b/Scripts/Engines/MLQuests/Items/AsandosSatchel.cs index c9b08e2f7..d12221cbb 100644 --- a/Scripts/Engines/MLQuests/Items/AsandosSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/AsandosSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class AsandosSatchel : Backpack - { - [Constructible] - public AsandosSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new SackFlour() ); - DropItem( new Skillet() ); - } + public class AsandosSatchel : Backpack + { + [Constructible] + public AsandosSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new SackFlour()); + DropItem(new Skillet()); + } - public AsandosSatchel( Serial serial ) - : base( serial ) - { - } + public AsandosSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/BasinOfCrystalClearWater.cs b/Scripts/Engines/MLQuests/Items/BasinOfCrystalClearWater.cs index a7d81b59f..ee76c8fd2 100644 --- a/Scripts/Engines/MLQuests/Items/BasinOfCrystalClearWater.cs +++ b/Scripts/Engines/MLQuests/Items/BasinOfCrystalClearWater.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class BasinOfCrystalClearWater : Item - { - public override int LabelNumber => 1075303; // Basin of Crystal-Clear Water + public class BasinOfCrystalClearWater : Item + { + [Constructible] + public BasinOfCrystalClearWater() : base(0x1008) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public BasinOfCrystalClearWater(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075303; // Basin of Crystal-Clear Water - [Constructible] - public BasinOfCrystalClearWater() : base( 0x1008 ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public BasinOfCrystalClearWater( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/BedlamTeleporter.cs b/Scripts/Engines/MLQuests/Items/BedlamTeleporter.cs index 584873c60..b133a10bf 100644 --- a/Scripts/Engines/MLQuests/Items/BedlamTeleporter.cs +++ b/Scripts/Engines/MLQuests/Items/BedlamTeleporter.cs @@ -3,55 +3,55 @@ using Server.Network; namespace Server.Engines.MLQuests.Items { - public class BedlamTeleporter : Item - { - public override int LabelNumber => 1074161; // Access to Bedlam by invitation only + public class BedlamTeleporter : Item + { + private static readonly Point3D PointDest = new Point3D(120, 1682, 0); + private static readonly Map MapDest = Map.Malas; - private static readonly Point3D PointDest = new Point3D( 120, 1682, 0 ); - private static readonly Map MapDest = Map.Malas; + public BedlamTeleporter() + : base(0x124D) + { + Movable = false; + } - public BedlamTeleporter() - : base( 0x124D ) - { - Movable = false; - } + public BedlamTeleporter(Serial serial) + : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + public override int LabelNumber => 1074161; // Access to Bedlam by invitation only - if ( from is PlayerMobile mobile && MLQuestSystem.GetContext( mobile )?.BedlamAccess == true ) - { - BaseCreature.TeleportPets( mobile, PointDest, MapDest ); - mobile.MoveToWorld( PointDest, MapDest ); - } - else - { - from.SendLocalizedMessage( 1074276 ); // You press and push on the iron maiden, but nothing happens. - } - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } - public BedlamTeleporter( Serial serial ) - : base( serial ) - { - } + if (from is PlayerMobile mobile && MLQuestSystem.GetContext(mobile)?.BedlamAccess == true) + { + BaseCreature.TeleportPets(mobile, PointDest, MapDest); + mobile.MoveToWorld(PointDest, MapDest); + } + else + { + from.SendLocalizedMessage(1074276); // You press and push on the iron maiden, but nothing happens. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/Bleach.cs b/Scripts/Engines/MLQuests/Items/Bleach.cs index 01617003c..43512c436 100644 --- a/Scripts/Engines/MLQuests/Items/Bleach.cs +++ b/Scripts/Engines/MLQuests/Items/Bleach.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class Bleach : PigmentsOfTokuno - { - public override int LabelNumber => 1075375; // Bleach + public class Bleach : PigmentsOfTokuno + { + [Constructible] + public Bleach() : base(PigmentType.None) + { + LootType = LootType.Blessed; + } - [Constructible] - public Bleach() : base( PigmentType.None ) - { - LootType = LootType.Blessed; - } + public Bleach(Serial serial) : base(serial) + { + } - public Bleach( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075375; // Bleach - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/BridesLetter.cs b/Scripts/Engines/MLQuests/Items/BridesLetter.cs index 2d2f397ce..a514fedfb 100644 --- a/Scripts/Engines/MLQuests/Items/BridesLetter.cs +++ b/Scripts/Engines/MLQuests/Items/BridesLetter.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class BridesLetter : Item - { - public override int LabelNumber => 1075301; // Bride's Letter + public class BridesLetter : Item + { + [Constructible] + public BridesLetter() : base(0x14ED) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public BridesLetter(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075301; // Bride's Letter - [Constructible] - public BridesLetter() : base( 0x14ED ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public BridesLetter( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/CompletedTuitionReimbursementForm.cs b/Scripts/Engines/MLQuests/Items/CompletedTuitionReimbursementForm.cs index 50c9f4958..83a4438bf 100644 --- a/Scripts/Engines/MLQuests/Items/CompletedTuitionReimbursementForm.cs +++ b/Scripts/Engines/MLQuests/Items/CompletedTuitionReimbursementForm.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class CompletedTuitionReimbursementForm : Item - { - public override int LabelNumber => 1074625; // Completed Tuition Reimbursement Form + public class CompletedTuitionReimbursementForm : Item + { + [Constructible] + public CompletedTuitionReimbursementForm() : base(0x14F0) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public CompletedTuitionReimbursementForm(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074625; // Completed Tuition Reimbursement Form - [Constructible] - public CompletedTuitionReimbursementForm() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public CompletedTuitionReimbursementForm( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/CraftmansSatchel.cs b/Scripts/Engines/MLQuests/Items/CraftmansSatchel.cs index 87a013330..5cbbe4ce3 100644 --- a/Scripts/Engines/MLQuests/Items/CraftmansSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/CraftmansSatchel.cs @@ -4,223 +4,224 @@ using Server.Items; namespace Server.Engines.MLQuests.Items { - public abstract class BaseCraftmansSatchel : Backpack - { - protected static readonly Type[] m_TalismanType = { typeof( RandomTalisman ) }; + public abstract class BaseCraftmansSatchel : Backpack + { + protected static readonly Type[] m_TalismanType = { typeof(RandomTalisman) }; - public BaseCraftmansSatchel() - { - Hue = Utility.RandomBrightHue(); - } + public BaseCraftmansSatchel() + { + Hue = Utility.RandomBrightHue(); + } - protected void AddBaseLoot( params Type[][] lootSets ) - { - Item loot = Loot.Construct( lootSets[Utility.Random( lootSets.Length )] ); + public BaseCraftmansSatchel(Serial serial) + : base(serial) + { + } - if ( loot == null ) - return; + protected void AddBaseLoot(params Type[][] lootSets) + { + Item loot = Loot.Construct(lootSets[Utility.Random(lootSets.Length)]); - RewardBag.Enhance( loot ); - DropItem( loot ); - } + if (loot == null) + return; - protected void AddRecipe( CraftSystem system ) - { - // TODO: change craftable artifact recipes to a rarer drop - int recipeID = system.RandomRecipe(); + RewardBag.Enhance(loot); + DropItem(loot); + } - if ( recipeID != -1 ) - DropItem( new RecipeScroll( recipeID ) ); - } + protected void AddRecipe(CraftSystem system) + { + // TODO: change craftable artifact recipes to a rarer drop + int recipeID = system.RandomRecipe(); - public BaseCraftmansSatchel( Serial serial ) - : base( serial ) - { - } + if (recipeID != -1) + DropItem(new RecipeScroll(recipeID)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class TailorSatchel : BaseCraftmansSatchel - { - [Constructible] - public TailorSatchel() - { - AddBaseLoot( Loot.MLArmorTypes, Loot.JewelryTypes, m_TalismanType ); + public class TailorSatchel : BaseCraftmansSatchel + { + [Constructible] + public TailorSatchel() + { + AddBaseLoot(Loot.MLArmorTypes, Loot.JewelryTypes, m_TalismanType); - if ( Utility.RandomDouble() < 0.50 ) - AddRecipe( DefTailoring.CraftSystem ); - } + if (Utility.RandomDouble() < 0.50) + AddRecipe(DefTailoring.CraftSystem); + } - public TailorSatchel( Serial serial ) - : base( serial ) - { - } + public TailorSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BlacksmithSatchel : BaseCraftmansSatchel - { - [Constructible] - public BlacksmithSatchel() - { - AddBaseLoot( Loot.MLWeaponTypes, Loot.JewelryTypes, m_TalismanType ); + public class BlacksmithSatchel : BaseCraftmansSatchel + { + [Constructible] + public BlacksmithSatchel() + { + AddBaseLoot(Loot.MLWeaponTypes, Loot.JewelryTypes, m_TalismanType); - if ( Utility.RandomDouble() < 0.50 ) - AddRecipe( DefBlacksmithy.CraftSystem ); - } + if (Utility.RandomDouble() < 0.50) + AddRecipe(DefBlacksmithy.CraftSystem); + } - public BlacksmithSatchel( Serial serial ) - : base( serial ) - { - } + public BlacksmithSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class TinkerSatchel : BaseCraftmansSatchel - { - [Constructible] - public TinkerSatchel() - { - AddBaseLoot( Loot.MLArmorTypes, Loot.MLWeaponTypes, Loot.MLRangedWeaponTypes, Loot.JewelryTypes, m_TalismanType ); + public class TinkerSatchel : BaseCraftmansSatchel + { + [Constructible] + public TinkerSatchel() + { + AddBaseLoot(Loot.MLArmorTypes, Loot.MLWeaponTypes, Loot.MLRangedWeaponTypes, Loot.JewelryTypes, m_TalismanType); - if ( Utility.RandomDouble() < 0.50 ) - { - // TODO: Add recipe drops (drops include inscription, alchemy and drops from non-artifact recipes for tailoring, blacksmith, carpentry and fletching. - switch ( Utility.Random( 6 ) ) - { - case 0: AddRecipe( DefInscription.CraftSystem ); break; - case 1: AddRecipe( DefAlchemy.CraftSystem ); break; - // TODO - //case 2: AddNonArtifactRecipe( DefTailoring.CraftSystem ); break; - //case 3: AddNonArtifactRecipe( DefBlacksmithy.CraftSystem ); break; - //case 4: AddNonArtifactRecipe( DefCarpentry.CraftSystem ); break; - //case 5: AddNonArtifactRecipe( DefBowFletching.CraftSystem ); break; - } - } - } + if (Utility.RandomDouble() < 0.50) + switch (Utility.Random(6)) + { + case 0: + AddRecipe(DefInscription.CraftSystem); + break; + case 1: + AddRecipe(DefAlchemy.CraftSystem); + break; + // TODO + //case 2: AddNonArtifactRecipe( DefTailoring.CraftSystem ); break; + //case 3: AddNonArtifactRecipe( DefBlacksmithy.CraftSystem ); break; + //case 4: AddNonArtifactRecipe( DefCarpentry.CraftSystem ); break; + //case 5: AddNonArtifactRecipe( DefBowFletching.CraftSystem ); break; + } + } - public TinkerSatchel( Serial serial ) - : base( serial ) - { - } + public TinkerSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class FletchingSatchel : BaseCraftmansSatchel - { - [Constructible] - public FletchingSatchel() - { - AddBaseLoot( Loot.MLRangedWeaponTypes, Loot.JewelryTypes, m_TalismanType ); + public class FletchingSatchel : BaseCraftmansSatchel + { + [Constructible] + public FletchingSatchel() + { + AddBaseLoot(Loot.MLRangedWeaponTypes, Loot.JewelryTypes, m_TalismanType); - if ( Utility.RandomDouble() < 0.50 ) - AddRecipe( DefBowFletching.CraftSystem ); + if (Utility.RandomDouble() < 0.50) + AddRecipe(DefBowFletching.CraftSystem); - // TODO: runic fletching kit - } + // TODO: runic fletching kit + } - public FletchingSatchel( Serial serial ) - : base( serial ) - { - } + public FletchingSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class CarpentrySatchel : BaseCraftmansSatchel - { - [Constructible] - public CarpentrySatchel() - { - AddBaseLoot( Loot.MLArmorTypes, Loot.MLWeaponTypes, Loot.MLRangedWeaponTypes, Loot.JewelryTypes, m_TalismanType ); + public class CarpentrySatchel : BaseCraftmansSatchel + { + [Constructible] + public CarpentrySatchel() + { + AddBaseLoot(Loot.MLArmorTypes, Loot.MLWeaponTypes, Loot.MLRangedWeaponTypes, Loot.JewelryTypes, m_TalismanType); - if ( Utility.RandomDouble() < 0.50 ) - AddRecipe( DefCarpentry.CraftSystem ); + if (Utility.RandomDouble() < 0.50) + AddRecipe(DefCarpentry.CraftSystem); - // TODO: Add runic dovetail saw - } + // TODO: Add runic dovetail saw + } - public CarpentrySatchel( Serial serial ) - : base( serial ) - { - } + public CarpentrySatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/CrateForSledge.cs b/Scripts/Engines/MLQuests/Items/CrateForSledge.cs index c3cf2d812..058432070 100644 --- a/Scripts/Engines/MLQuests/Items/CrateForSledge.cs +++ b/Scripts/Engines/MLQuests/Items/CrateForSledge.cs @@ -2,40 +2,40 @@ using System; namespace Server.Items { - public class CrateForSledge : TransientItem - { - public override int LabelNumber => 1074520; // Crate for Sledge + public class CrateForSledge : TransientItem + { + [Constructible] + public CrateForSledge() : base(0x1FFF, TimeSpan.FromHours(1)) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public CrateForSledge(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074520; // Crate for Sledge - [Constructible] - public CrateForSledge() : base( 0x1FFF, TimeSpan.FromHours( 1 ) ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public CrateForSledge( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/DreadSpiderSilk.cs b/Scripts/Engines/MLQuests/Items/DreadSpiderSilk.cs index 326563a6f..4c7722cc8 100644 --- a/Scripts/Engines/MLQuests/Items/DreadSpiderSilk.cs +++ b/Scripts/Engines/MLQuests/Items/DreadSpiderSilk.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class DreadSpiderSilk : Item - { - public override int LabelNumber => 1075319; // Dread Spider Silk + public class DreadSpiderSilk : Item + { + [Constructible] + public DreadSpiderSilk() : base(0xDF8) + { + LootType = LootType.Blessed; + Hue = 0x481; + } - public override bool Nontransferable => true; + public DreadSpiderSilk(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075319; // Dread Spider Silk - [Constructible] - public DreadSpiderSilk() : base( 0xDF8 ) - { - LootType = LootType.Blessed; - Hue = 0x481; - } + public override bool Nontransferable => true; - public DreadSpiderSilk( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/FragmentOfAMap.cs b/Scripts/Engines/MLQuests/Items/FragmentOfAMap.cs index 66398e494..374beef8a 100644 --- a/Scripts/Engines/MLQuests/Items/FragmentOfAMap.cs +++ b/Scripts/Engines/MLQuests/Items/FragmentOfAMap.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class FragmentOfAMap : Item - { - public override int LabelNumber => 1074533; // Fragment of a Map + public class FragmentOfAMap : Item + { + [Constructible] + public FragmentOfAMap() : base(0x14ED) + { + LootType = LootType.Blessed; + } - [Constructible] - public FragmentOfAMap() : base( 0x14ED ) - { - LootType = LootType.Blessed; - } + public FragmentOfAMap(Serial serial) : base(serial) + { + } - public FragmentOfAMap( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074533; // Fragment of a Map - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/FragmentOfAMapDelivery.cs b/Scripts/Engines/MLQuests/Items/FragmentOfAMapDelivery.cs index 8d54c5886..22b7e4fe2 100644 --- a/Scripts/Engines/MLQuests/Items/FragmentOfAMapDelivery.cs +++ b/Scripts/Engines/MLQuests/Items/FragmentOfAMapDelivery.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class FragmentOfAMapDelivery : Item - { - public override int LabelNumber => 1074533; // Fragment of a Map + public class FragmentOfAMapDelivery : Item + { + [Constructible] + public FragmentOfAMapDelivery() : base(0x14ED) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public FragmentOfAMapDelivery(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074533; // Fragment of a Map - [Constructible] - public FragmentOfAMapDelivery() : base( 0x14ED ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public FragmentOfAMapDelivery( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/FriendOfTheLibraryToken.cs b/Scripts/Engines/MLQuests/Items/FriendOfTheLibraryToken.cs index cb45e7a36..c077d8921 100644 --- a/Scripts/Engines/MLQuests/Items/FriendOfTheLibraryToken.cs +++ b/Scripts/Engines/MLQuests/Items/FriendOfTheLibraryToken.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class FriendOfTheLibraryToken : Item - { - public override int LabelNumber => 1073136; // Friend of the Library Token (allows donations to be made) + public class FriendOfTheLibraryToken : Item + { + [Constructible] + public FriendOfTheLibraryToken() : base(0x2F58) + { + Layer = Layer.Talisman; + Hue = 0x28A; + } - [Constructible] - public FriendOfTheLibraryToken() : base( 0x2F58 ) - { - Layer = Layer.Talisman; - Hue = 0x28A; - } + public FriendOfTheLibraryToken(Serial serial) : base(serial) + { + } - public FriendOfTheLibraryToken( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073136; // Friend of the Library Token (allows donations to be made) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/FriendsOfTheLibraryApplication.cs b/Scripts/Engines/MLQuests/Items/FriendsOfTheLibraryApplication.cs index 65f4b886a..0f65e1308 100644 --- a/Scripts/Engines/MLQuests/Items/FriendsOfTheLibraryApplication.cs +++ b/Scripts/Engines/MLQuests/Items/FriendsOfTheLibraryApplication.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class FriendsOfTheLibraryApplication : Item - { - public override int LabelNumber => 1073131; // Friends of the Library Application + public class FriendsOfTheLibraryApplication : Item + { + [Constructible] + public FriendsOfTheLibraryApplication() : base(0xEC0) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public FriendsOfTheLibraryApplication(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1073131; // Friends of the Library Application - [Constructible] - public FriendsOfTheLibraryApplication() : base( 0xEC0 ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public FriendsOfTheLibraryApplication( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/GamanHorns.cs b/Scripts/Engines/MLQuests/Items/GamanHorns.cs index dba53eb1d..59372017f 100644 --- a/Scripts/Engines/MLQuests/Items/GamanHorns.cs +++ b/Scripts/Engines/MLQuests/Items/GamanHorns.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class GamanHorns : Item - { - public override int LabelNumber => 1074557; // Gaman Horns + public class GamanHorns : Item + { + [Constructible] + public GamanHorns() : this(1) + { + } - [Constructible] - public GamanHorns() : this( 1 ) - { - } + [Constructible] + public GamanHorns(int amount) : base(0x1084) + { + LootType = LootType.Blessed; + Stackable = true; + Amount = amount; + Hue = 0x395; + } - [Constructible] - public GamanHorns( int amount ) : base( 0x1084 ) - { - LootType = LootType.Blessed; - Stackable = true; - Amount = amount; - Hue = 0x395; - } + public GamanHorns(Serial serial) : base(serial) + { + } - public GamanHorns( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074557; // Gaman Horns - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/GervisSatchel.cs b/Scripts/Engines/MLQuests/Items/GervisSatchel.cs index 4b7b8fd2d..d6e8b5ccb 100644 --- a/Scripts/Engines/MLQuests/Items/GervisSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/GervisSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class GervisSatchel : Backpack - { - [Constructible] - public GervisSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new IronIngot( 10 ) ); - DropItem( new SmithHammer() ); - } + public class GervisSatchel : Backpack + { + [Constructible] + public GervisSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new IronIngot(10)); + DropItem(new SmithHammer()); + } - public GervisSatchel( Serial serial ) - : base( serial ) - { - } + public GervisSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/GiftForArielle.cs b/Scripts/Engines/MLQuests/Items/GiftForArielle.cs index f2a723b9a..9d2b02078 100644 --- a/Scripts/Engines/MLQuests/Items/GiftForArielle.cs +++ b/Scripts/Engines/MLQuests/Items/GiftForArielle.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class GiftForArielle : BaseContainer - { - public override int LabelNumber => 1074356; // gift for arielle - public override int DefaultGumpID => 0x41; + public class GiftForArielle : BaseContainer + { + [Constructible] + public GiftForArielle() : base(0x1882) + { + Hue = 0x2C4; + } - public override bool Nontransferable => true; + public GiftForArielle(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074356; // gift for arielle + public override int DefaultGumpID => 0x41; - [Constructible] - public GiftForArielle() : base( 0x1882 ) - { - Hue = 0x2C4; - } + public override bool Nontransferable => true; - public GiftForArielle( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/HargroveSatchel.cs b/Scripts/Engines/MLQuests/Items/HargroveSatchel.cs index ab993e7ea..3eab50dad 100644 --- a/Scripts/Engines/MLQuests/Items/HargroveSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/HargroveSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class HargroveSatchel : Backpack - { - [Constructible] - public HargroveSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new Gold( 15 ) ); - DropItem( new Hatchet() ); - } + public class HargroveSatchel : Backpack + { + [Constructible] + public HargroveSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new Gold(15)); + DropItem(new Hatchet()); + } - public HargroveSatchel( Serial serial ) - : base( serial ) - { - } + public HargroveSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/KirinBrains.cs b/Scripts/Engines/MLQuests/Items/KirinBrains.cs index 716d485d7..6993d70f4 100644 --- a/Scripts/Engines/MLQuests/Items/KirinBrains.cs +++ b/Scripts/Engines/MLQuests/Items/KirinBrains.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class KirinBrains : Item - { - public override int LabelNumber => 1074612; // Ki-Rin Brains + public class KirinBrains : Item + { + [Constructible] + public KirinBrains() : base(0x1CF0) + { + LootType = LootType.Blessed; + Hue = 0xD7; + } - [Constructible] - public KirinBrains() : base( 0x1CF0 ) - { - LootType = LootType.Blessed; - Hue = 0xD7; - } + public KirinBrains(Serial serial) : base(serial) + { + } - public KirinBrains( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074612; // Ki-Rin Brains - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/LowelSatchel.cs b/Scripts/Engines/MLQuests/Items/LowelSatchel.cs index 678377f95..2cb846f46 100644 --- a/Scripts/Engines/MLQuests/Items/LowelSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/LowelSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class LowelSatchel : Backpack - { - [Constructible] - public LowelSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new Board( 10 ) ); - DropItem( new DovetailSaw() ); - } + public class LowelSatchel : Backpack + { + [Constructible] + public LowelSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new Board(10)); + DropItem(new DovetailSaw()); + } - public LowelSatchel( Serial serial ) - : base( serial ) - { - } + public LowelSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/MiniatureMushroom.cs b/Scripts/Engines/MLQuests/Items/MiniatureMushroom.cs index 17c7237cd..c11083291 100644 --- a/Scripts/Engines/MLQuests/Items/MiniatureMushroom.cs +++ b/Scripts/Engines/MLQuests/Items/MiniatureMushroom.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class MiniatureMushroom : Food - { - public override int LabelNumber => 1073138; // Miniature mushroom + public class MiniatureMushroom : Food + { + [Constructible] + public MiniatureMushroom() : base(0xD16) + { + LootType = LootType.Blessed; + } - [Constructible] - public MiniatureMushroom() : base( 0xD16 ) - { - LootType = LootType.Blessed; - } + public MiniatureMushroom(Serial serial) : base(serial) + { + } - public MiniatureMushroom( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073138; // Miniature mushroom - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/MirrorOfPurification.cs b/Scripts/Engines/MLQuests/Items/MirrorOfPurification.cs index 583805a83..e6c3f241c 100644 --- a/Scripts/Engines/MLQuests/Items/MirrorOfPurification.cs +++ b/Scripts/Engines/MLQuests/Items/MirrorOfPurification.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class MirrorOfPurification : Item - { - public override int LabelNumber => 1075304; // Mirror of Purification + public class MirrorOfPurification : Item + { + [Constructible] + public MirrorOfPurification() : base(0x1008) + { + LootType = LootType.Blessed; + Hue = 0x530; + } - [Constructible] - public MirrorOfPurification() : base( 0x1008 ) - { - LootType = LootType.Blessed; - Hue = 0x530; - } + public MirrorOfPurification(Serial serial) : base(serial) + { + } - public MirrorOfPurification( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075304; // Mirror of Purification - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/MuggSatchel.cs b/Scripts/Engines/MLQuests/Items/MuggSatchel.cs index 49c303f98..029d46bf4 100644 --- a/Scripts/Engines/MLQuests/Items/MuggSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/MuggSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class MuggSatchel : Backpack - { - [Constructible] - public MuggSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new Pickaxe() ); - DropItem( new Pickaxe() ); - } + public class MuggSatchel : Backpack + { + [Constructible] + public MuggSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new Pickaxe()); + DropItem(new Pickaxe()); + } - public MuggSatchel( Serial serial ) - : base( serial ) - { - } + public MuggSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/NibbetSatchel.cs b/Scripts/Engines/MLQuests/Items/NibbetSatchel.cs index e2552c9c5..1361426bf 100644 --- a/Scripts/Engines/MLQuests/Items/NibbetSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/NibbetSatchel.cs @@ -1,46 +1,65 @@ namespace Server.Items { - public class NibbetSatchel : Backpack - { - [Constructible] - public NibbetSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new TinkerTools() ); + public class NibbetSatchel : Backpack + { + [Constructible] + public NibbetSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new TinkerTools()); - switch ( Utility.Random( 10 ) ) - { - case 0: DropItem( new Springs( 3 ) ); break; - case 1: DropItem( new Axle( 3 ) ); break; - case 2: DropItem( new Hinge( 3 ) ); break; - case 3: DropItem( new Key() ); break; - case 4: DropItem( new Scissors() ); break; - case 5: DropItem( new BarrelTap( 3 ) ); break; - case 6: DropItem( new BarrelHoops() ); break; - case 7: DropItem( new Gears( 3 ) ); break; - case 8: DropItem( new Lockpick( 3 ) ); break; - case 9: DropItem( new ClockFrame( 3 ) ); break; + switch (Utility.Random(10)) + { + case 0: + DropItem(new Springs(3)); + break; + case 1: + DropItem(new Axle(3)); + break; + case 2: + DropItem(new Hinge(3)); + break; + case 3: + DropItem(new Key()); + break; + case 4: + DropItem(new Scissors()); + break; + case 5: + DropItem(new BarrelTap(3)); + break; + case 6: + DropItem(new BarrelHoops()); + break; + case 7: + DropItem(new Gears(3)); + break; + case 8: + DropItem(new Lockpick(3)); + break; + case 9: + DropItem(new ClockFrame(3)); + break; + } + } - } - } + public NibbetSatchel(Serial serial) + : base(serial) + { + } - public NibbetSatchel( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/NotarizedApplication.cs b/Scripts/Engines/MLQuests/Items/NotarizedApplication.cs index 5dea30075..48c7d1a8d 100644 --- a/Scripts/Engines/MLQuests/Items/NotarizedApplication.cs +++ b/Scripts/Engines/MLQuests/Items/NotarizedApplication.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class NotarizedApplication : Item - { - public override int LabelNumber => 1073135; // Notarized Application + public class NotarizedApplication : Item + { + [Constructible] + public NotarizedApplication() : base(0x14EF) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public NotarizedApplication(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1073135; // Notarized Application - [Constructible] - public NotarizedApplication() : base( 0x14EF ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public NotarizedApplication( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/OfficialSealingWax.cs b/Scripts/Engines/MLQuests/Items/OfficialSealingWax.cs index 9932fab01..ff8945aab 100644 --- a/Scripts/Engines/MLQuests/Items/OfficialSealingWax.cs +++ b/Scripts/Engines/MLQuests/Items/OfficialSealingWax.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class OfficialSealingWax : Item - { - public override int LabelNumber => 1072744; // Official Sealing Wax + public class OfficialSealingWax : Item + { + [Constructible] + public OfficialSealingWax() : base(0x1426) + { + LootType = LootType.Blessed; + Hue = 0x84; + } - public override bool Nontransferable => true; + public OfficialSealingWax(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1072744; // Official Sealing Wax - [Constructible] - public OfficialSealingWax() : base( 0x1426 ) - { - LootType = LootType.Blessed; - Hue = 0x84; - } + public override bool Nontransferable => true; - public OfficialSealingWax( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/PeppercornFishsteak.cs b/Scripts/Engines/MLQuests/Items/PeppercornFishsteak.cs index 24a2927d9..7317b724b 100644 --- a/Scripts/Engines/MLQuests/Items/PeppercornFishsteak.cs +++ b/Scripts/Engines/MLQuests/Items/PeppercornFishsteak.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class PeppercornFishsteak : FishSteak - { - public override int LabelNumber => 1075557; // peppercorn fishsteak + public class PeppercornFishsteak : FishSteak + { + [Constructible] + public PeppercornFishsteak() + { + Hue = 0x222; + } - [Constructible] - public PeppercornFishsteak() - { - Hue = 0x222; - } + public PeppercornFishsteak(Serial serial) : base(serial) + { + } - public PeppercornFishsteak( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075557; // peppercorn fishsteak - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/PixieLeg.cs b/Scripts/Engines/MLQuests/Items/PixieLeg.cs index 274d308cd..3b546ab4c 100644 --- a/Scripts/Engines/MLQuests/Items/PixieLeg.cs +++ b/Scripts/Engines/MLQuests/Items/PixieLeg.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class PixieLeg : ChickenLeg - { - public override int LabelNumber => 1074613; // Pixie Leg + public class PixieLeg : ChickenLeg + { + [Constructible] + public PixieLeg() : this(1) + { + } - [Constructible] - public PixieLeg() : this( 1 ) - { - } + [Constructible] + public PixieLeg(int amount) : base(amount) + { + LootType = LootType.Blessed; + Hue = 0x1C2; + } - [Constructible] - public PixieLeg( int amount ) : base( amount ) - { - LootType = LootType.Blessed; - Hue = 0x1C2; - } + public PixieLeg(Serial serial) : base(serial) + { + } - public PixieLeg( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074613; // Pixie Leg - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/PortraitOfTheBride.cs b/Scripts/Engines/MLQuests/Items/PortraitOfTheBride.cs index 3b6435cdd..7447eb2b9 100644 --- a/Scripts/Engines/MLQuests/Items/PortraitOfTheBride.cs +++ b/Scripts/Engines/MLQuests/Items/PortraitOfTheBride.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class PortraitOfTheBride : Item - { - public override int LabelNumber => 1075300; // Portrait of the Bride + public class PortraitOfTheBride : Item + { + [Constructible] + public PortraitOfTheBride() : base(0xE9F) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public PortraitOfTheBride(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075300; // Portrait of the Bride - [Constructible] - public PortraitOfTheBride() : base( 0xE9F ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public PortraitOfTheBride( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/PrismaticAmber.cs b/Scripts/Engines/MLQuests/Items/PrismaticAmber.cs index 733800434..5a81de887 100644 --- a/Scripts/Engines/MLQuests/Items/PrismaticAmber.cs +++ b/Scripts/Engines/MLQuests/Items/PrismaticAmber.cs @@ -1,73 +1,73 @@ namespace Server.Items { - public class PrismaticAmber : Amber - { - public override int LabelNumber => 1075299; // Prismatic Amber + public class PrismaticAmber : Amber + { + [Constructible] + public PrismaticAmber() + { + } - [Constructible] - public PrismaticAmber() - { - } + public PrismaticAmber(Serial serial) : base(serial) + { + } - public PrismaticAmber( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075299; // Prismatic Amber - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1075269 ); // Destroyed when dropped - } + list.Add(1075269); // Destroyed when dropped + } - public override bool DropToWorld( Mobile from, Point3D p ) - { - bool ret = base.DropToWorld( from, p ); + public override bool DropToWorld(Mobile from, Point3D p) + { + bool ret = base.DropToWorld(from, p); - if ( ret ) - DestroyItem( from ); + if (ret) + DestroyItem(from); - return ret; - } + return ret; + } - public override bool DropToMobile( Mobile from, Mobile target, Point3D p ) - { - bool ret = base.DropToMobile( from, target, p ); + public override bool DropToMobile(Mobile from, Mobile target, Point3D p) + { + bool ret = base.DropToMobile(from, target, p); - if ( ret ) - DestroyItem( from ); + if (ret) + DestroyItem(from); - return ret; - } + return ret; + } - public override bool DropToItem( Mobile from, Item target, Point3D p ) - { - bool ret = base.DropToItem( from, target, p ); + public override bool DropToItem(Mobile from, Item target, Point3D p) + { + bool ret = base.DropToItem(from, target, p); - if ( ret && Parent != from.Backpack ) - DestroyItem( from ); + if (ret && Parent != from.Backpack) + DestroyItem(from); - return ret; - } + return ret; + } - public virtual void DestroyItem( Mobile from ) - { - from.SendLocalizedMessage( 500424 ); // You destroyed the item. - Delete(); - } + public virtual void DestroyItem(Mobile from) + { + from.SendLocalizedMessage(500424); // You destroyed the item. + Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/PrismaticCrystal.cs b/Scripts/Engines/MLQuests/Items/PrismaticCrystal.cs index c5b5521c3..4756aae7e 100644 --- a/Scripts/Engines/MLQuests/Items/PrismaticCrystal.cs +++ b/Scripts/Engines/MLQuests/Items/PrismaticCrystal.cs @@ -5,62 +5,67 @@ using Server.Network; namespace Server.Items { - public class PrismaticCrystal : Item - { - public override int LabelNumber => 1074269; // prismatic crystal + public class PrismaticCrystal : Item + { + [Constructible] + public PrismaticCrystal() : base(0x2DA) + { + Movable = false; + Hue = 0x32; + } - [Constructible] - public PrismaticCrystal() : base( 0x2DA ) - { - Movable = false; - Hue = 0x32; - } + public PrismaticCrystal(Serial serial) : base(serial) + { + } - public PrismaticCrystal( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074269; // prismatic crystal - public override void OnDoubleClick( Mobile from ) - { - if ( !(from is PlayerMobile pm) || pm.Backpack == null ) - return; + public override void OnDoubleClick(Mobile from) + { + if (!(from is PlayerMobile pm) || pm.Backpack == null) + return; - if ( pm.InRange( GetWorldLocation(), 2 ) ) - { - if ( MLQuestSystem.GetContext( pm )?.IsDoingQuest( typeof( UnfadingMemoriesPartOne ) ) == true && pm.Backpack.FindItemByType( typeof( PrismaticAmber ), false ) == null ) - { - Item amber = new PrismaticAmber(); + if (pm.InRange(GetWorldLocation(), 2)) + { + if (MLQuestSystem.GetContext(pm)?.IsDoingQuest(typeof(UnfadingMemoriesPartOne)) == true && + pm.Backpack.FindItemByType(typeof(PrismaticAmber), false) == null) + { + Item amber = new PrismaticAmber(); - if ( pm.PlaceInBackpack( amber ) ) - { - MLQuestSystem.MarkQuestItem( pm, amber ); - Delete(); - } - else - { - pm.SendLocalizedMessage( 502385 ); // Your pack cannot hold this item. - amber.Delete(); - } - } - else - pm.SendLocalizedMessage( 1075464 ); // You already have as many of those as you need. - } - else - pm.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + if (pm.PlaceInBackpack(amber)) + { + MLQuestSystem.MarkQuestItem(pm, amber); + Delete(); + } + else + { + pm.SendLocalizedMessage(502385); // Your pack cannot hold this item. + amber.Delete(); + } + } + else + { + pm.SendLocalizedMessage(1075464); // You already have as many of those as you need. + } + } + else + { + pm.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/QuestGiverItem.cs b/Scripts/Engines/MLQuests/Items/QuestGiverItem.cs index 8acf77b09..75f2bf189 100644 --- a/Scripts/Engines/MLQuests/Items/QuestGiverItem.cs +++ b/Scripts/Engines/MLQuests/Items/QuestGiverItem.cs @@ -6,161 +6,161 @@ using Server.Network; namespace Server.Engines.MLQuests.Items { - public abstract class QuestGiverItem : Item, IQuestGiver - { - private List m_MLQuests; + public abstract class QuestGiverItem : Item, IQuestGiver + { + private List m_MLQuests; - public List MLQuests - { - get - { - if ( m_MLQuests == null ) - { - m_MLQuests = MLQuestSystem.FindQuestList( GetType() ); + public QuestGiverItem(int itemId) + : base(itemId) + { + } - if ( m_MLQuests == null ) - m_MLQuests = MLQuestSystem.EmptyList; - } + public QuestGiverItem(Serial serial) + : base(serial) + { + } - return m_MLQuests; - } - } + public bool CanGiveMLQuest => MLQuests.Count != 0; - public bool CanGiveMLQuest => ( MLQuests.Count != 0 ); + public override bool Nontransferable => true; - public QuestGiverItem( int itemId ) - : base( itemId ) - { - } + public List MLQuests + { + get + { + if (m_MLQuests == null) + { + m_MLQuests = MLQuestSystem.FindQuestList(GetType()); - public override bool Nontransferable => true; + if (m_MLQuests == null) + m_MLQuests = MLQuestSystem.EmptyList; + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + return m_MLQuests; + } + } - AddQuestItemProperty( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - if ( CanGiveMLQuest ) - list.Add( 1072269 ); // Quest Giver - } + AddQuestItemProperty(list); - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else if ( !IsChildOf( from.Backpack ) ) - from.SendLocalizedMessage( 1042593 ); // That is not in your backpack. - else if ( MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile ) - MLQuestSystem.OnDoubleClick( this, mobile ); - } + if (CanGiveMLQuest) + list.Add(1072269); // Quest Giver + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (!IsChildOf(from.Backpack)) + from.SendLocalizedMessage(1042593); // That is not in your backpack. + else if (MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile) + MLQuestSystem.OnDoubleClick(this, mobile); + } - if ( MLQuestSystem.Enabled ) - MLQuestSystem.HandleDeletion( this ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public QuestGiverItem( Serial serial ) - : base( serial ) - { - } + if (MLQuestSystem.Enabled) + MLQuestSystem.HandleDeletion(this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public abstract class TransientQuestGiverItem : TransientItem, IQuestGiver - { - private List m_MLQuests; + public abstract class TransientQuestGiverItem : TransientItem, IQuestGiver + { + private List m_MLQuests; - public List MLQuests - { - get - { - if ( m_MLQuests == null ) - { - m_MLQuests = MLQuestSystem.FindQuestList( GetType() ); + public TransientQuestGiverItem(int itemId, TimeSpan lifeSpan) + : base(itemId, lifeSpan) + { + } - if ( m_MLQuests == null ) - m_MLQuests = MLQuestSystem.EmptyList; - } + public TransientQuestGiverItem(Serial serial) + : base(serial) + { + } - return m_MLQuests; - } - } + public bool CanGiveMLQuest => MLQuests.Count != 0; - public bool CanGiveMLQuest => ( MLQuests.Count != 0 ); + public override bool Nontransferable => true; - public TransientQuestGiverItem( int itemId, TimeSpan lifeSpan ) - : base( itemId, lifeSpan ) - { - } + public List MLQuests + { + get + { + if (m_MLQuests == null) + { + m_MLQuests = MLQuestSystem.FindQuestList(GetType()); - public override bool Nontransferable => true; + if (m_MLQuests == null) + m_MLQuests = MLQuestSystem.EmptyList; + } - public override void HandleInvalidTransfer( Mobile from ) - { - } + return m_MLQuests; + } + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void HandleInvalidTransfer(Mobile from) + { + } - AddQuestItemProperty( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - if ( CanGiveMLQuest ) - list.Add( 1072269 ); // Quest Giver - } + AddQuestItemProperty(list); - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else if ( !IsChildOf( from.Backpack ) ) - from.SendLocalizedMessage( 1042593 ); // That is not in your backpack. - else if ( MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile ) - MLQuestSystem.OnDoubleClick( this, mobile ); - } + if (CanGiveMLQuest) + list.Add(1072269); // Quest Giver + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (!IsChildOf(from.Backpack)) + from.SendLocalizedMessage(1042593); // That is not in your backpack. + else if (MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile) + MLQuestSystem.OnDoubleClick(this, mobile); + } - if ( MLQuestSystem.Enabled ) - MLQuestSystem.HandleDeletion( this ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public TransientQuestGiverItem( Serial serial ) - : base( serial ) - { - } + if (MLQuestSystem.Enabled) + MLQuestSystem.HandleDeletion(this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/RedLeatherBook.cs b/Scripts/Engines/MLQuests/Items/RedLeatherBook.cs index 80d726b64..747c03a71 100644 --- a/Scripts/Engines/MLQuests/Items/RedLeatherBook.cs +++ b/Scripts/Engines/MLQuests/Items/RedLeatherBook.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class RedLeatherBook : BlueBook - { - [Constructible] - public RedLeatherBook() - { - Hue = 0x485; - } + public class RedLeatherBook : BlueBook + { + [Constructible] + public RedLeatherBook() + { + Hue = 0x485; + } - public RedLeatherBook( Serial serial ) - : base( serial ) - { - } + public RedLeatherBook(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/ReginasLetter.cs b/Scripts/Engines/MLQuests/Items/ReginasLetter.cs index 50c13894d..a641a9c5b 100644 --- a/Scripts/Engines/MLQuests/Items/ReginasLetter.cs +++ b/Scripts/Engines/MLQuests/Items/ReginasLetter.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ReginasLetter : Item - { - public override int LabelNumber => 1075306; // Regina's Letter + public class ReginasLetter : Item + { + [Constructible] + public ReginasLetter() : base(0x14ED) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public ReginasLetter(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075306; // Regina's Letter - [Constructible] - public ReginasLetter() : base( 0x14ED ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public ReginasLetter( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/ReginasRing.cs b/Scripts/Engines/MLQuests/Items/ReginasRing.cs index 5fda482b9..c9dcc2d5b 100644 --- a/Scripts/Engines/MLQuests/Items/ReginasRing.cs +++ b/Scripts/Engines/MLQuests/Items/ReginasRing.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ReginasRing : SilverRing - { - public override int LabelNumber => 1075305; // Regina's Ring + public class ReginasRing : SilverRing + { + [Constructible] + public ReginasRing() + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public ReginasRing(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075305; // Regina's Ring - [Constructible] - public ReginasRing() - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public ReginasRing( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/RewardBags.cs b/Scripts/Engines/MLQuests/Items/RewardBags.cs index deddb0010..53db84abe 100644 --- a/Scripts/Engines/MLQuests/Items/RewardBags.cs +++ b/Scripts/Engines/MLQuests/Items/RewardBags.cs @@ -2,198 +2,202 @@ namespace Server.Engines.MLQuests.Items { - public static class RewardBag - { - public static void Fill( Container c, int itemCount, double talismanChance ) - { - c.Hue = Utility.RandomNondyedHue(); + public static class RewardBag + { + public static void Fill(Container c, int itemCount, double talismanChance) + { + c.Hue = Utility.RandomNondyedHue(); - int done = 0; + int done = 0; - if ( Utility.RandomDouble() < talismanChance ) - { - c.DropItem( new RandomTalisman() ); - ++done; - } + if (Utility.RandomDouble() < talismanChance) + { + c.DropItem(new RandomTalisman()); + ++done; + } - for ( ; done < itemCount; ++done ) - { - Item loot = null; + for (; done < itemCount; ++done) + { + Item loot = null; - switch ( Utility.Random( 5 ) ) - { - case 0: loot = Loot.RandomWeapon( false, true ); break; - case 1: loot = Loot.RandomArmor( false, true ); break; - case 2: loot = Loot.RandomRangedWeapon( false, true ); break; - case 3: loot = Loot.RandomJewelry(); break; - case 4: loot = Loot.RandomHat( false ); break; - } + switch (Utility.Random(5)) + { + case 0: + loot = Loot.RandomWeapon(false, true); + break; + case 1: + loot = Loot.RandomArmor(false, true); + break; + case 2: + loot = Loot.RandomRangedWeapon(false, true); + break; + case 3: + loot = Loot.RandomJewelry(); + break; + case 4: + loot = Loot.RandomHat(false); + break; + } - if ( loot == null ) - continue; + if (loot == null) + continue; - Enhance( loot ); - c.DropItem( loot ); - } - } + Enhance(loot); + c.DropItem(loot); + } + } - public static void Enhance( Item loot ) - { - if (loot is BaseWeapon weapon) - { - BaseRunicTool.ApplyAttributesTo( weapon, Utility.RandomMinMax( 1, 5 ), 10, 80 ); - return; - } + public static void Enhance(Item loot) + { + if (loot is BaseWeapon weapon) + { + BaseRunicTool.ApplyAttributesTo(weapon, Utility.RandomMinMax(1, 5), 10, 80); + return; + } - if (loot is BaseArmor armor) - { - BaseRunicTool.ApplyAttributesTo( armor, Utility.RandomMinMax( 1, 5 ), 10, 80 ); - } + if (loot is BaseArmor armor) BaseRunicTool.ApplyAttributesTo(armor, Utility.RandomMinMax(1, 5), 10, 80); - if (loot is BaseJewel jewel) - { - BaseRunicTool.ApplyAttributesTo(jewel, Utility.RandomMinMax( 1, 5 ), 10, 80 ); - } - } - } + if (loot is BaseJewel jewel) BaseRunicTool.ApplyAttributesTo(jewel, Utility.RandomMinMax(1, 5), 10, 80); + } + } - public class SmallBagOfTrinkets : Bag - { - [Constructible] - public SmallBagOfTrinkets() - { - RewardBag.Fill( this, 1, 0.0 ); - } + public class SmallBagOfTrinkets : Bag + { + [Constructible] + public SmallBagOfTrinkets() + { + RewardBag.Fill(this, 1, 0.0); + } - public SmallBagOfTrinkets( Serial serial ) - : base( serial ) - { - } + public SmallBagOfTrinkets(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BagOfTrinkets : Bag - { - [Constructible] - public BagOfTrinkets() - { - RewardBag.Fill( this, 2, 0.05 ); - } + public class BagOfTrinkets : Bag + { + [Constructible] + public BagOfTrinkets() + { + RewardBag.Fill(this, 2, 0.05); + } - public BagOfTrinkets( Serial serial ) - : base( serial ) - { - } + public BagOfTrinkets(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BagOfTreasure : Bag - { - [Constructible] - public BagOfTreasure() - { - RewardBag.Fill( this, 3, 0.20 ); - } + public class BagOfTreasure : Bag + { + [Constructible] + public BagOfTreasure() + { + RewardBag.Fill(this, 3, 0.20); + } - public BagOfTreasure( Serial serial ) - : base( serial ) - { - } + public BagOfTreasure(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeBagOfTreasure : Bag - { - [Constructible] - public LargeBagOfTreasure() - { - RewardBag.Fill( this, 4, 0.50 ); - } + public class LargeBagOfTreasure : Bag + { + [Constructible] + public LargeBagOfTreasure() + { + RewardBag.Fill(this, 4, 0.50); + } - public LargeBagOfTreasure( Serial serial ) - : base( serial ) - { - } + public LargeBagOfTreasure(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class RewardStrongbox : WoodenBox - { - [Constructible] - public RewardStrongbox() - { - RewardBag.Fill( this, 5, 1.0 ); - } + public class RewardStrongbox : WoodenBox + { + [Constructible] + public RewardStrongbox() + { + RewardBag.Fill(this, 5, 1.0); + } - public RewardStrongbox( Serial serial ) - : base( serial ) - { - } + public RewardStrongbox(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SadrahSatchel.cs b/Scripts/Engines/MLQuests/Items/SadrahSatchel.cs index db3bb1c3f..b444764e7 100644 --- a/Scripts/Engines/MLQuests/Items/SadrahSatchel.cs +++ b/Scripts/Engines/MLQuests/Items/SadrahSatchel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class SadrahSatchel : Backpack - { - [Constructible] - public SadrahSatchel() - { - Hue = Utility.RandomBrightHue(); - DropItem( new Bloodmoss( 10 ) ); - DropItem( new MortarPestle() ); - } + public class SadrahSatchel : Backpack + { + [Constructible] + public SadrahSatchel() + { + Hue = Utility.RandomBrightHue(); + DropItem(new Bloodmoss(10)); + DropItem(new MortarPestle()); + } - public SadrahSatchel( Serial serial ) - : base( serial ) - { - } + public SadrahSatchel(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SapOfSosaria.cs b/Scripts/Engines/MLQuests/Items/SapOfSosaria.cs index d84926b47..8b5551c42 100644 --- a/Scripts/Engines/MLQuests/Items/SapOfSosaria.cs +++ b/Scripts/Engines/MLQuests/Items/SapOfSosaria.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class SapOfSosaria : Item - { - public override int LabelNumber => 1074178; // Sap of Sosaria + public class SapOfSosaria : Item + { + [Constructible] + public SapOfSosaria() : this(1) + { + } - [Constructible] - public SapOfSosaria() : this( 1 ) - { - } + [Constructible] + public SapOfSosaria(int amount) : base(0x1848) + { + LootType = LootType.Blessed; + Stackable = true; + Amount = amount; + } - [Constructible] - public SapOfSosaria( int amount ) : base( 0x1848 ) - { - LootType = LootType.Blessed; - Stackable = true; - Amount = amount; - } + public SapOfSosaria(Serial serial) : base(serial) + { + } - public SapOfSosaria( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074178; // Sap of Sosaria - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SealedNotesForJamal.cs b/Scripts/Engines/MLQuests/Items/SealedNotesForJamal.cs index 452c27afd..9ba2274de 100644 --- a/Scripts/Engines/MLQuests/Items/SealedNotesForJamal.cs +++ b/Scripts/Engines/MLQuests/Items/SealedNotesForJamal.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class SealedNotesForJamal : Item - { - public override int LabelNumber => 1074998; // Sealed Notes For Jamal - public override double DefaultWeight => 1.0; + public class SealedNotesForJamal : Item + { + [Constructible] + public SealedNotesForJamal() : base(0xEF9) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public SealedNotesForJamal(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074998; // Sealed Notes For Jamal + public override double DefaultWeight => 1.0; - [Constructible] - public SealedNotesForJamal() : base( 0xEF9 ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public SealedNotesForJamal( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SealingWaxOrderAddressedToPetrus.cs b/Scripts/Engines/MLQuests/Items/SealingWaxOrderAddressedToPetrus.cs index 783d0dd83..263630634 100644 --- a/Scripts/Engines/MLQuests/Items/SealingWaxOrderAddressedToPetrus.cs +++ b/Scripts/Engines/MLQuests/Items/SealingWaxOrderAddressedToPetrus.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class SealingWaxOrderAddressedToPetrus : Item - { - public override int LabelNumber => 1073132; // Sealing Wax Order addressed to Petrus + public class SealingWaxOrderAddressedToPetrus : Item + { + [Constructible] + public SealingWaxOrderAddressedToPetrus() : base(0xEBF) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public SealingWaxOrderAddressedToPetrus(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1073132; // Sealing Wax Order addressed to Petrus - [Constructible] - public SealingWaxOrderAddressedToPetrus() : base( 0xEBF ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public SealingWaxOrderAddressedToPetrus( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SeveredElfEars.cs b/Scripts/Engines/MLQuests/Items/SeveredElfEars.cs index 52a5fbaf3..6b2681d0c 100644 --- a/Scripts/Engines/MLQuests/Items/SeveredElfEars.cs +++ b/Scripts/Engines/MLQuests/Items/SeveredElfEars.cs @@ -1,36 +1,36 @@ namespace Server.Items { - [Flippable(0x312D, 0x312E)] - public class SeveredElfEars : Item - { - [Constructible] - public SeveredElfEars() : this( 1 ) - { - } + [Flippable(0x312D, 0x312E)] + public class SeveredElfEars : Item + { + [Constructible] + public SeveredElfEars() : this(1) + { + } - [Constructible] - public SeveredElfEars( int amount ) : base( Utility.RandomList( 0x312D, 0x312E ) ) - { - Stackable = true; - Amount = amount; - } + [Constructible] + public SeveredElfEars(int amount) : base(Utility.RandomList(0x312D, 0x312E)) + { + Stackable = true; + Amount = amount; + } - public SeveredElfEars( Serial serial ) : base( serial ) - { - } + public SeveredElfEars(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SeveredHumanEars.cs b/Scripts/Engines/MLQuests/Items/SeveredHumanEars.cs index 7fc65682d..756ee85cf 100644 --- a/Scripts/Engines/MLQuests/Items/SeveredHumanEars.cs +++ b/Scripts/Engines/MLQuests/Items/SeveredHumanEars.cs @@ -1,36 +1,36 @@ namespace Server.Items { - [Flippable(0x312F, 0x3130)] - public class SeveredHumanEars : Item - { - [Constructible] - public SeveredHumanEars() : this( 1 ) - { - } + [Flippable(0x312F, 0x3130)] + public class SeveredHumanEars : Item + { + [Constructible] + public SeveredHumanEars() : this(1) + { + } - [Constructible] - public SeveredHumanEars( int amount ) : base( Utility.RandomList( 0x312F, 0x3130 ) ) - { - Stackable = true; - Amount = amount; - } + [Constructible] + public SeveredHumanEars(int amount) : base(Utility.RandomList(0x312F, 0x3130)) + { + Stackable = true; + Amount = amount; + } - public SeveredHumanEars( Serial serial ) : base( serial ) - { - } + public SeveredHumanEars(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SignedTuitionReimbursementForm.cs b/Scripts/Engines/MLQuests/Items/SignedTuitionReimbursementForm.cs index 852d223eb..ba35a8ce6 100644 --- a/Scripts/Engines/MLQuests/Items/SignedTuitionReimbursementForm.cs +++ b/Scripts/Engines/MLQuests/Items/SignedTuitionReimbursementForm.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class SignedTuitionReimbursementForm : Item - { - public override int LabelNumber => 1074614; // Signed Tuition Reimbursement Form + public class SignedTuitionReimbursementForm : Item + { + [Constructible] + public SignedTuitionReimbursementForm() : base(0x14F0) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public SignedTuitionReimbursementForm(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074614; // Signed Tuition Reimbursement Form - [Constructible] - public SignedTuitionReimbursementForm() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public SignedTuitionReimbursementForm( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SpecialTreatForDrithen.cs b/Scripts/Engines/MLQuests/Items/SpecialTreatForDrithen.cs index 8577a59c9..3df44599c 100644 --- a/Scripts/Engines/MLQuests/Items/SpecialTreatForDrithen.cs +++ b/Scripts/Engines/MLQuests/Items/SpecialTreatForDrithen.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class SpecialTreatForDrithen : Item - { - public override int LabelNumber => 1074517; // Special Treat for Drithen + public class SpecialTreatForDrithen : Item + { + [Constructible] + public SpecialTreatForDrithen() : base(0x21B) + { + LootType = LootType.Blessed; + Hue = 0x489; + } - [Constructible] - public SpecialTreatForDrithen() : base( 0x21B ) - { - LootType = LootType.Blessed; - Hue = 0x489; - } + public SpecialTreatForDrithen(Serial serial) : base(serial) + { + } - public SpecialTreatForDrithen( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074517; // Special Treat for Drithen - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SpeckledPoisonSac.cs b/Scripts/Engines/MLQuests/Items/SpeckledPoisonSac.cs index 6db2ae8d2..d2359237d 100644 --- a/Scripts/Engines/MLQuests/Items/SpeckledPoisonSac.cs +++ b/Scripts/Engines/MLQuests/Items/SpeckledPoisonSac.cs @@ -2,32 +2,32 @@ using System; namespace Server.Items { - public class SpeckledPoisonSac : TransientItem - { - public override int LabelNumber => 1073133; // Speckled Poison Sac + public class SpeckledPoisonSac : TransientItem + { + [Constructible] + public SpeckledPoisonSac() : base(0x23A, TimeSpan.FromHours(1)) + { + LootType = LootType.Blessed; + } - [Constructible] - public SpeckledPoisonSac() : base( 0x23A, TimeSpan.FromHours( 1 ) ) - { - LootType = LootType.Blessed; - } + public SpeckledPoisonSac(Serial serial) : base(serial) + { + } - public SpeckledPoisonSac( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073133; // Speckled Poison Sac - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/SpiritBottle.cs b/Scripts/Engines/MLQuests/Items/SpiritBottle.cs index 5bdd2104a..f1ff1c306 100644 --- a/Scripts/Engines/MLQuests/Items/SpiritBottle.cs +++ b/Scripts/Engines/MLQuests/Items/SpiritBottle.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class SpiritBottle : Item - { - public override int LabelNumber => 1075283; // Spirit bottle + public class SpiritBottle : Item + { + [Constructible] + public SpiritBottle() : base(0xEFB) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public SpiritBottle(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1075283; // Spirit bottle - [Constructible] - public SpiritBottle() : base( 0xEFB ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public SpiritBottle( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/StoutWhip.cs b/Scripts/Engines/MLQuests/Items/StoutWhip.cs index e82e6d216..0b16feaf9 100644 --- a/Scripts/Engines/MLQuests/Items/StoutWhip.cs +++ b/Scripts/Engines/MLQuests/Items/StoutWhip.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class StoutWhip : Item - { - public override int LabelNumber => 1074812; // Stout Whip + public class StoutWhip : Item + { + [Constructible] + public StoutWhip() : base(0x166F) + { + LootType = LootType.Blessed; + } - [Constructible] - public StoutWhip() : base( 0x166F ) - { - LootType = LootType.Blessed; - } + public StoutWhip(Serial serial) : base(serial) + { + } - public StoutWhip( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074812; // Stout Whip - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/TaintedTreeSample.cs b/Scripts/Engines/MLQuests/Items/TaintedTreeSample.cs index e95e8e7af..453b06585 100644 --- a/Scripts/Engines/MLQuests/Items/TaintedTreeSample.cs +++ b/Scripts/Engines/MLQuests/Items/TaintedTreeSample.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class TaintedTreeSample : Item // On OSI the base class is Kindling, and it's ignitable... - { - public override int LabelNumber => 1074997; // Tainted Tree Sample + public class TaintedTreeSample : Item // On OSI the base class is Kindling, and it's ignitable... + { + [Constructible] + public TaintedTreeSample() : base(0xDE2) + { + LootType = LootType.Blessed; + Hue = 0x9D; + } - public override bool Nontransferable => true; + public TaintedTreeSample(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074997; // Tainted Tree Sample - [Constructible] - public TaintedTreeSample() : base( 0xDE2 ) - { - LootType = LootType.Blessed; - Hue = 0x9D; - } + public override bool Nontransferable => true; - public TaintedTreeSample( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/Teleporters.cs b/Scripts/Engines/MLQuests/Items/Teleporters.cs index 8f85ce8d4..136f79c88 100644 --- a/Scripts/Engines/MLQuests/Items/Teleporters.cs +++ b/Scripts/Engines/MLQuests/Items/Teleporters.cs @@ -4,210 +4,212 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Items { - public class MLQuestTeleporter : Teleporter - { - private Type m_QuestType; + public class MLQuestTeleporter : Teleporter + { + private Type m_QuestType; - [CommandProperty(AccessLevel.GameMaster)] - public Type QuestType - { - get => m_QuestType; - set { m_QuestType = value; InvalidateProperties(); } - } + [Constructible] + public MLQuestTeleporter() + : this(Point3D.Zero, null, null, null) + { + } - [CommandProperty(AccessLevel.GameMaster)] - public TextDefinition Message { get; set; } + [Constructible] + public MLQuestTeleporter(Point3D pointDest, Map mapDest) + : this(pointDest, mapDest, null, null) + { + } - [Constructible] - public MLQuestTeleporter() - : this(Point3D.Zero, null, null, null) - { - } + [Constructible] + public MLQuestTeleporter(Point3D pointDest, Map mapDest, Type questType, TextDefinition message) + : base(pointDest, mapDest) + { + m_QuestType = questType; + Message = message; + } - [Constructible] - public MLQuestTeleporter(Point3D pointDest, Map mapDest) - : this(pointDest, mapDest, null, null) - { - } + public MLQuestTeleporter(Serial serial) + : base(serial) + { + } - [Constructible] - public MLQuestTeleporter(Point3D pointDest, Map mapDest, Type questType, TextDefinition message) - : base(pointDest, mapDest) - { - m_QuestType = questType; - Message = message; - } + [CommandProperty(AccessLevel.GameMaster)] + public Type QuestType + { + get => m_QuestType; + set + { + m_QuestType = value; + InvalidateProperties(); + } + } - public override bool CanTeleport(Mobile m) - { - if (!base.CanTeleport(m)) - return false; + [CommandProperty(AccessLevel.GameMaster)] + public TextDefinition Message{ get; set; } - if (m_QuestType == null) - return true; - if (!(m is PlayerMobile pm)) - return false; + public override bool CanTeleport(Mobile m) + { + if (!base.CanTeleport(m)) + return false; - MLQuestContext context = MLQuestSystem.GetContext(pm); + if (m_QuestType == null) + return true; + if (!(m is PlayerMobile pm)) + return false; - if (context?.IsDoingQuest(m_QuestType) == true || context?.HasDoneQuest(m_QuestType) == true) - return true; + MLQuestContext context = MLQuestSystem.GetContext(pm); - TextDefinition.SendMessageTo(m, Message); - return false; + if (context?.IsDoingQuest(m_QuestType) == true || context?.HasDoneQuest(m_QuestType) == true) + return true; - } + TextDefinition.SendMessageTo(m, Message); + return false; + } - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if (m_QuestType != null) - list.Add($"Required quest: {m_QuestType.Name}"); - } + if (m_QuestType != null) + list.Add($"Required quest: {m_QuestType.Name}"); + } - public MLQuestTeleporter(Serial serial) - : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); // version - writer.Write((int)0); // version + writer.Write(m_QuestType != null ? m_QuestType.FullName : null); + TextDefinition.Serialize(writer, Message); + } - writer.Write((m_QuestType != null) ? m_QuestType.FullName : null); - TextDefinition.Serialize(writer, Message); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + string typeName = reader.ReadString(); - string typeName = reader.ReadString(); + if (typeName != null) + m_QuestType = ScriptCompiler.FindTypeByFullName(typeName, false); - if (typeName != null) - m_QuestType = ScriptCompiler.FindTypeByFullName(typeName, false); + Message = TextDefinition.Deserialize(reader); + } + } - Message = TextDefinition.Deserialize(reader); - } - } + public interface ITicket + { + void OnTicketUsed(Mobile from); + } - public interface ITicket - { - void OnTicketUsed(Mobile from); - } + public class TicketTeleporter : Teleporter + { + private Type m_TicketType; - public class TicketTeleporter : Teleporter - { - private Type m_TicketType; + [Constructible] + public TicketTeleporter() + : this(Point3D.Zero, null, null, null) + { + } - [CommandProperty(AccessLevel.GameMaster)] - public Type TicketType - { - get => m_TicketType; - set { m_TicketType = value; InvalidateProperties(); } - } + [Constructible] + public TicketTeleporter(Point3D pointDest, Map mapDest) + : this(pointDest, mapDest, null, null) + { + } - [CommandProperty(AccessLevel.GameMaster)] - public TextDefinition Message { get; set; } + [Constructible] + public TicketTeleporter(Point3D pointDest, Map mapDest, Type ticketType, TextDefinition message) + : base(pointDest, mapDest) + { + m_TicketType = ticketType; + Message = message; + } - [Constructible] - public TicketTeleporter() - : this(Point3D.Zero, null, null, null) - { - } + public TicketTeleporter(Serial serial) + : base(serial) + { + } - [Constructible] - public TicketTeleporter(Point3D pointDest, Map mapDest) - : this(pointDest, mapDest, null, null) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public Type TicketType + { + get => m_TicketType; + set + { + m_TicketType = value; + InvalidateProperties(); + } + } - [Constructible] - public TicketTeleporter(Point3D pointDest, Map mapDest, Type ticketType, TextDefinition message) - : base(pointDest, mapDest) - { - m_TicketType = ticketType; - Message = message; - } + [CommandProperty(AccessLevel.GameMaster)] + public TextDefinition Message{ get; set; } - public override bool CanTeleport(Mobile m) - { - if (!base.CanTeleport(m)) - return false; + public override bool CanTeleport(Mobile m) + { + if (!base.CanTeleport(m)) + return false; - if (m_TicketType != null) - { - Item ticket = null; - Container pack = m.Backpack; + if (m_TicketType != null) + { + Item ticket = null; + Container pack = m.Backpack; - if (pack != null) - ticket = pack.FindItemByType(m_TicketType, false); // Check (top level) backpack + if (pack != null) + ticket = pack.FindItemByType(m_TicketType, false); // Check (top level) backpack - if (ticket == null) - { - foreach (Item item in m.Items) // Check paperdoll - { - if (m_TicketType.IsInstanceOfType(item)) - { - ticket = item; - break; - } - } - } + if (ticket == null) + foreach (Item item in m.Items) // Check paperdoll + if (m_TicketType.IsInstanceOfType(item)) + { + ticket = item; + break; + } - if (ticket == null) - { - TextDefinition.SendMessageTo(m, Message); - return false; - } + if (ticket == null) + { + TextDefinition.SendMessageTo(m, Message); + return false; + } - (ticket as ITicket)?.OnTicketUsed(m); - } + (ticket as ITicket)?.OnTicketUsed(m); + } - return true; - } + return true; + } - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if (m_TicketType != null) - list.Add($"Required ticket: {m_TicketType.Name}"); - } + if (m_TicketType != null) + list.Add($"Required ticket: {m_TicketType.Name}"); + } - public TicketTeleporter(Serial serial) - : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); // version - writer.Write((int)0); // version + writer.Write(m_TicketType != null ? m_TicketType.FullName : null); + TextDefinition.Serialize(writer, Message); + } - writer.Write((m_TicketType != null) ? m_TicketType.FullName : null); - TextDefinition.Serialize(writer, Message); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + string typeName = reader.ReadString(); - string typeName = reader.ReadString(); - - if (typeName != null) - m_TicketType = ScriptCompiler.FindTypeByFullName(typeName, false); - - Message = TextDefinition.Deserialize(reader); - } - } -} + if (typeName != null) + m_TicketType = ScriptCompiler.FindTypeByFullName(typeName, false); + Message = TextDefinition.Deserialize(reader); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/TransparentHeart.cs b/Scripts/Engines/MLQuests/Items/TransparentHeart.cs index f8541055d..8b1804063 100644 --- a/Scripts/Engines/MLQuests/Items/TransparentHeart.cs +++ b/Scripts/Engines/MLQuests/Items/TransparentHeart.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class TransparentHeart : GoldEarrings - { - public override int LabelNumber => 1075400; // Transparent Heart + public class TransparentHeart : GoldEarrings + { + [Constructible] + public TransparentHeart() + { + LootType = LootType.Blessed; + Hue = 0x4AB; + } - [Constructible] - public TransparentHeart() - { - LootType = LootType.Blessed; - Hue = 0x4AB; - } + public TransparentHeart(Serial serial) : base(serial) + { + } - public TransparentHeart( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075400; // Transparent Heart - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/TuitionReimbursementForm.cs b/Scripts/Engines/MLQuests/Items/TuitionReimbursementForm.cs index 87c90a55f..047458736 100644 --- a/Scripts/Engines/MLQuests/Items/TuitionReimbursementForm.cs +++ b/Scripts/Engines/MLQuests/Items/TuitionReimbursementForm.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class TuitionReimbursementForm : Item - { - public override int LabelNumber => 1074610; // Tuition Reimbursement Form (in triplicate) + public class TuitionReimbursementForm : Item + { + [Constructible] + public TuitionReimbursementForm() : base(0xE3A) + { + LootType = LootType.Blessed; + } - public override bool Nontransferable => true; + public TuitionReimbursementForm(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - AddQuestItemProperty( list ); - } + public override int LabelNumber => 1074610; // Tuition Reimbursement Form (in triplicate) - [Constructible] - public TuitionReimbursementForm() : base( 0xE3A ) - { - LootType = LootType.Blessed; - } + public override bool Nontransferable => true; - public TuitionReimbursementForm( Serial serial ) : base( serial ) - { - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + AddQuestItemProperty(list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Items/UnicornRibs.cs b/Scripts/Engines/MLQuests/Items/UnicornRibs.cs index 41a6aebb2..77de253b8 100644 --- a/Scripts/Engines/MLQuests/Items/UnicornRibs.cs +++ b/Scripts/Engines/MLQuests/Items/UnicornRibs.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class UnicornRibs : Item - { - public override int LabelNumber => 1074611; // Unicorn Ribs + public class UnicornRibs : Item + { + [Constructible] + public UnicornRibs() : this(1) + { + } - [Constructible] - public UnicornRibs() : this( 1 ) - { - } + [Constructible] + public UnicornRibs(int amount) : base(0x9F1) + { + LootType = LootType.Blessed; + Hue = 0x14B; + Stackable = true; + Amount = amount; + } - [Constructible] - public UnicornRibs( int amount ) : base( 0x9F1 ) - { - LootType = LootType.Blessed; - Hue = 0x14B; - Stackable = true; - Amount = amount; - } + public UnicornRibs(Serial serial) : base(serial) + { + } - public UnicornRibs( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074611; // Unicorn Ribs - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // Version - } + writer.Write(0); // Version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/MLQuest.cs b/Scripts/Engines/MLQuests/MLQuest.cs index 6982dd1d3..ec1c308b4 100644 --- a/Scripts/Engines/MLQuests/MLQuest.cs +++ b/Scripts/Engines/MLQuests/MLQuest.cs @@ -7,277 +7,277 @@ using Server.Mobiles; namespace Server.Engines.MLQuests { - public enum ObjectiveType - { - All, - Any - } + public enum ObjectiveType + { + All, + Any + } - public class MLQuest - { - public bool Deserialized { get; set; } + public class MLQuest + { + public static readonly TextDefinition + CompletionNoticeDefault = + new TextDefinition(1072273); // You've completed a quest! Don't forget to collect your reward. - public bool SaveEnabled { get; set; } + public static readonly TextDefinition CompletionNoticeShort = new TextDefinition(1046258); // Your quest is complete. - // TODO: Flags? (Deserialized, SaveEnabled, Activated) + public static readonly TextDefinition + CompletionNoticeShortReturn = new TextDefinition(1073775); // Your quest is complete. Return for your reward. - public bool Activated { get; set; } + public static readonly TextDefinition + CompletionNoticeCraft = new TextDefinition(1073967); // You obtained what you seek, now receive your reward. - public List Objectives { get; set; } + public MLQuest() + { + Activated = false; + Objectives = new List(); + ObjectiveType = ObjectiveType.All; + Rewards = new List(); + CompletionNotice = CompletionNoticeDefault; - public ObjectiveType ObjectiveType { get; set; } + Instances = new List(); - public List Rewards { get; set; } + SaveEnabled = true; + } - public List Instances { get; set; } + public bool Deserialized{ get; set; } - public bool OneTimeOnly { get; set; } + public bool SaveEnabled{ get; set; } - public bool HasRestartDelay { get; set; } + // TODO: Flags? (Deserialized, SaveEnabled, Activated) - public bool HasObjective() where T : BaseObjective - { - foreach ( BaseObjective obj in Objectives ) - { - if ( obj is T ) - return true; - } + public bool Activated{ get; set; } - return false; - } + public List Objectives{ get; set; } - public bool IsEscort => HasObjective(); + public ObjectiveType ObjectiveType{ get; set; } - public bool IsSkillTrainer => HasObjective(); + public List Rewards{ get; set; } - public bool RequiresCollection => HasObjective() || HasObjective(); + public List Instances{ get; set; } - public virtual bool RecordCompletion => ( OneTimeOnly || HasRestartDelay ); + public bool OneTimeOnly{ get; set; } - public virtual bool IsChainTriggered => false; - public virtual Type NextQuest => null; + public bool HasRestartDelay{ get; set; } - public TextDefinition Title { get; set; } + public bool IsEscort => HasObjective(); - public TextDefinition Description { get; set; } + public bool IsSkillTrainer => HasObjective(); - public TextDefinition RefusalMessage { get; set; } + public bool RequiresCollection => HasObjective() || HasObjective(); - public TextDefinition InProgressMessage { get; set; } + public virtual bool RecordCompletion => OneTimeOnly || HasRestartDelay; - public TextDefinition CompletionMessage { get; set; } + public virtual bool IsChainTriggered => false; + public virtual Type NextQuest => null; - public TextDefinition CompletionNotice { get; set; } + public TextDefinition Title{ get; set; } - public static readonly TextDefinition CompletionNoticeDefault = new TextDefinition( 1072273 ); // You've completed a quest! Don't forget to collect your reward. - public static readonly TextDefinition CompletionNoticeShort = new TextDefinition( 1046258 ); // Your quest is complete. - public static readonly TextDefinition CompletionNoticeShortReturn = new TextDefinition( 1073775 ); // Your quest is complete. Return for your reward. - public static readonly TextDefinition CompletionNoticeCraft = new TextDefinition( 1073967 ); // You obtained what you seek, now receive your reward. + public TextDefinition Description{ get; set; } - public MLQuest() - { - Activated = false; - Objectives = new List(); - ObjectiveType = ObjectiveType.All; - Rewards = new List(); - CompletionNotice = CompletionNoticeDefault; + public TextDefinition RefusalMessage{ get; set; } - Instances = new List(); + public TextDefinition InProgressMessage{ get; set; } - SaveEnabled = true; - } + public TextDefinition CompletionMessage{ get; set; } - public virtual void Generate() - { - if ( MLQuestSystem.Debug ) - Console.WriteLine( "INFO: Generating quest: {0}", GetType() ); - } + public TextDefinition CompletionNotice{ get; set; } - #region Generation Methods + public virtual int Version => 0; - public void PutSpawner( Spawner s, Point3D loc, Map map ) - { - string name = $"MLQS-{GetType().Name}"; + public bool HasObjective() where T : BaseObjective + { + foreach (BaseObjective obj in Objectives) + if (obj is T) + return true; - // Auto cleanup on regeneration - List toDelete = new List(); + return false; + } - foreach ( Item item in map.GetItemsInRange( loc, 0 ) ) - { - if ( item is Spawner && item.Name == name ) - toDelete.Add( item ); - } + public virtual void Generate() + { + if (MLQuestSystem.Debug) + Console.WriteLine("INFO: Generating quest: {0}", GetType()); + } - foreach ( Item item in toDelete ) - item.Delete(); + public MLQuestInstance CreateInstance(IQuestGiver quester, PlayerMobile pm) + { + return new MLQuestInstance(this, quester, pm); + } - s.Name = name; - s.MoveToWorld( loc, map ); - } + public bool CanOffer(IQuestGiver quester, PlayerMobile pm, bool message) + { + return CanOffer(quester, pm, MLQuestSystem.GetContext(pm), message); + } - public void PutDeco( Item deco, Point3D loc, Map map ) - { - // Auto cleanup on regeneration - List toDelete = new List(); + public virtual bool CanOffer(IQuestGiver quester, PlayerMobile pm, MLQuestContext context, bool message) + { + if (!Activated || quester.Deleted) + return false; - foreach ( Item item in map.GetItemsInRange( loc, 0 ) ) - { - if ( item.ItemID == deco.ItemID && item.Z == loc.Z ) - toDelete.Add( item ); - } + if (context != null) + { + if (context.IsFull) + { + if (message) + MLQuestSystem.Tell(quester, pm, 1080107); // I'm sorry, I have nothing for you at this time. - foreach ( Item item in toDelete ) - item.Delete(); + return false; + } - deco.MoveToWorld( loc, map ); - } + MLQuest checkQuest = this; - #endregion + while (checkQuest != null) + { + DateTime nextAvailable; - public MLQuestInstance CreateInstance( IQuestGiver quester, PlayerMobile pm ) - { - return new MLQuestInstance( this, quester, pm ); - } + if (context.HasDoneQuest(checkQuest, out nextAvailable)) + { + if (checkQuest.OneTimeOnly) + { + if (message) + MLQuestSystem.Tell(quester, pm, 1075454); // I cannot offer you the quest again. - public bool CanOffer( IQuestGiver quester, PlayerMobile pm, bool message ) - { - return CanOffer( quester, pm, MLQuestSystem.GetContext( pm ), message ); - } + return false; + } - public virtual bool CanOffer( IQuestGiver quester, PlayerMobile pm, MLQuestContext context, bool message ) - { - if ( !Activated || quester.Deleted ) - return false; + if (nextAvailable > DateTime.UtcNow) + { + if (message) + MLQuestSystem.Tell(quester, pm, + 1075575); // I'm sorry, but I don't have anything else for you right now. Could you check back with me in a few minutes? - if ( context != null ) - { - if ( context.IsFull ) - { - if ( message ) - MLQuestSystem.Tell( quester, pm, 1080107 ); // I'm sorry, I have nothing for you at this time. + return false; + } + } - return false; - } + if (checkQuest.NextQuest == null) + break; - MLQuest checkQuest = this; + checkQuest = MLQuestSystem.FindQuest(checkQuest.NextQuest); + } + } - while ( checkQuest != null ) - { - DateTime nextAvailable; - - if ( context.HasDoneQuest( checkQuest, out nextAvailable ) ) - { - if ( checkQuest.OneTimeOnly ) - { - if ( message ) - MLQuestSystem.Tell( quester, pm, 1075454 ); // I cannot offer you the quest again. - - return false; - } - - if ( nextAvailable > DateTime.UtcNow ) - { - if ( message ) - MLQuestSystem.Tell( quester, pm, 1075575 ); // I'm sorry, but I don't have anything else for you right now. Could you check back with me in a few minutes? - - return false; - } - } - - if ( checkQuest.NextQuest == null ) - break; - - checkQuest = MLQuestSystem.FindQuest( checkQuest.NextQuest ); - } - } - - foreach ( BaseObjective obj in Objectives ) - { - if ( !obj.CanOffer( quester, pm, message ) ) - return false; - } - - return true; - } - - public virtual void SendOffer( IQuestGiver quester, PlayerMobile pm ) - { - pm.SendGump( new QuestOfferGump( this, quester, pm ) ); - } - - public virtual void OnAccept( IQuestGiver quester, PlayerMobile pm ) - { - if ( !CanOffer( quester, pm, true ) ) - return; - - MLQuestInstance instance = CreateInstance( quester, pm ); - - pm.SendLocalizedMessage( 1049019 ); // You have accepted the Quest. - pm.SendSound( 0x2E7 ); // private sound - - OnAccepted( instance ); - - foreach ( BaseObjectiveInstance obj in instance.Objectives ) - obj.OnQuestAccepted(); - } - - public virtual void OnAccepted( MLQuestInstance instance ) - { - } - - public virtual void OnRefuse( IQuestGiver quester, PlayerMobile pm ) - { - pm.SendGump( new QuestConversationGump( this, pm, RefusalMessage ) ); - } - - public virtual void GetRewards( MLQuestInstance instance ) - { - instance.SendRewardGump(); - } - - public virtual void OnRewardClaimed( MLQuestInstance instance ) - { - } - - public virtual void OnCancel( MLQuestInstance instance ) - { - } - - public virtual void OnQuesterDeleted( MLQuestInstance instance ) - { - } - - public virtual void OnPlayerDeath( MLQuestInstance instance ) - { - } - - public virtual TimeSpan GetRestartDelay() - { - return TimeSpan.FromSeconds( Utility.Random( 1, 5 ) * 30 ); - } + foreach (BaseObjective obj in Objectives) + if (!obj.CanOffer(quester, pm, message)) + return false; - public static void Serialize( GenericWriter writer, MLQuest quest ) - { - MLQuestSystem.WriteQuestRef( writer, quest ); - writer.Write( quest.Version ); - } - - public static void Deserialize( GenericReader reader, int version ) - { - MLQuest quest = MLQuestSystem.ReadQuestRef( reader ); - int oldVersion = reader.ReadInt(); - - if ( quest == null ) - return; // not saved or no longer exists - - quest.Refresh( oldVersion ); - quest.Deserialized = true; - } - - public virtual int Version => 0; - - public virtual void Refresh( int oldVersion ) - { - } - } -} + return true; + } + + public virtual void SendOffer(IQuestGiver quester, PlayerMobile pm) + { + pm.SendGump(new QuestOfferGump(this, quester, pm)); + } + + public virtual void OnAccept(IQuestGiver quester, PlayerMobile pm) + { + if (!CanOffer(quester, pm, true)) + return; + + MLQuestInstance instance = CreateInstance(quester, pm); + + pm.SendLocalizedMessage(1049019); // You have accepted the Quest. + pm.SendSound(0x2E7); // private sound + + OnAccepted(instance); + + foreach (BaseObjectiveInstance obj in instance.Objectives) + obj.OnQuestAccepted(); + } + + public virtual void OnAccepted(MLQuestInstance instance) + { + } + + public virtual void OnRefuse(IQuestGiver quester, PlayerMobile pm) + { + pm.SendGump(new QuestConversationGump(this, pm, RefusalMessage)); + } + + public virtual void GetRewards(MLQuestInstance instance) + { + instance.SendRewardGump(); + } + + public virtual void OnRewardClaimed(MLQuestInstance instance) + { + } + + public virtual void OnCancel(MLQuestInstance instance) + { + } + + public virtual void OnQuesterDeleted(MLQuestInstance instance) + { + } + + public virtual void OnPlayerDeath(MLQuestInstance instance) + { + } + + public virtual TimeSpan GetRestartDelay() + { + return TimeSpan.FromSeconds(Utility.Random(1, 5) * 30); + } + + public static void Serialize(GenericWriter writer, MLQuest quest) + { + MLQuestSystem.WriteQuestRef(writer, quest); + writer.Write(quest.Version); + } + + public static void Deserialize(GenericReader reader, int version) + { + MLQuest quest = MLQuestSystem.ReadQuestRef(reader); + int oldVersion = reader.ReadInt(); + + if (quest == null) + return; // not saved or no longer exists + + quest.Refresh(oldVersion); + quest.Deserialized = true; + } + + public virtual void Refresh(int oldVersion) + { + } + + #region Generation Methods + + public void PutSpawner(Spawner s, Point3D loc, Map map) + { + string name = $"MLQS-{GetType().Name}"; + + // Auto cleanup on regeneration + List toDelete = new List(); + + foreach (Item item in map.GetItemsInRange(loc, 0)) + if (item is Spawner && item.Name == name) + toDelete.Add(item); + + foreach (Item item in toDelete) + item.Delete(); + + s.Name = name; + s.MoveToWorld(loc, map); + } + + public void PutDeco(Item deco, Point3D loc, Map map) + { + // Auto cleanup on regeneration + List toDelete = new List(); + + foreach (Item item in map.GetItemsInRange(loc, 0)) + if (item.ItemID == deco.ItemID && item.Z == loc.Z) + toDelete.Add(item); + + foreach (Item item in toDelete) + item.Delete(); + + deco.MoveToWorld(loc, map); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/MLQuestContext.cs b/Scripts/Engines/MLQuests/MLQuestContext.cs index 7b7c2cce2..c28136897 100644 --- a/Scripts/Engines/MLQuests/MLQuestContext.cs +++ b/Scripts/Engines/MLQuests/MLQuestContext.cs @@ -4,280 +4,272 @@ using Server.Mobiles; namespace Server.Engines.MLQuests { - [Flags] - public enum MLQuestFlag - { - None = 0x00, - Spellweaving = 0x01, - SummonFey = 0x02, - SummonFiend = 0x04, - BedlamAccess = 0x08 - } + [Flags] + public enum MLQuestFlag + { + None = 0x00, + Spellweaving = 0x01, + SummonFey = 0x02, + SummonFiend = 0x04, + BedlamAccess = 0x08 + } - [PropertyObject] - public class MLQuestContext - { - private class MLDoneQuestInfo - { - public MLQuest m_Quest; - public DateTime m_NextAvailable; + [PropertyObject] + public class MLQuestContext + { + private List m_DoneQuests; + private MLQuestFlag m_Flags; - public MLDoneQuestInfo( MLQuest quest, DateTime nextAvailable ) - { - m_Quest = quest; - m_NextAvailable = nextAvailable; - } + public MLQuestContext(PlayerMobile owner) + { + Owner = owner; + QuestInstances = new List(); + m_DoneQuests = new List(); + ChainOffers = new List(); + m_Flags = MLQuestFlag.None; + } - public void Serialize( GenericWriter writer ) - { - MLQuestSystem.WriteQuestRef( writer, m_Quest ); - writer.Write( m_NextAvailable ); - } + public MLQuestContext(GenericReader reader, int version) + { + Owner = reader.ReadMobile(); + QuestInstances = new List(); + m_DoneQuests = new List(); + ChainOffers = new List(); - public static MLDoneQuestInfo Deserialize( GenericReader reader, int version ) - { - MLQuest quest = MLQuestSystem.ReadQuestRef( reader ); - DateTime nextAvailable = reader.ReadDateTime(); + int instances = reader.ReadInt(); - if ( quest == null || !quest.RecordCompletion ) - return null; // forget about this record + for (int i = 0; i < instances; ++i) + { + MLQuestInstance instance = MLQuestInstance.Deserialize(reader, version, Owner); - return new MLDoneQuestInfo( quest, nextAvailable ); - } - } + if (instance != null) + QuestInstances.Add(instance); + } - private List m_DoneQuests; - private MLQuestFlag m_Flags; + int doneQuests = reader.ReadInt(); - public PlayerMobile Owner { get; } + for (int i = 0; i < doneQuests; ++i) + { + MLDoneQuestInfo info = MLDoneQuestInfo.Deserialize(reader, version); - public List QuestInstances { get; } + if (info != null) + m_DoneQuests.Add(info); + } - public List ChainOffers { get; } + int chainOffers = reader.ReadInt(); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsFull => QuestInstances.Count >= MLQuestSystem.MaxConcurrentQuests; + for (int i = 0; i < chainOffers; ++i) + { + MLQuest quest = MLQuestSystem.ReadQuestRef(reader); - [CommandProperty( AccessLevel.GameMaster )] - public bool Spellweaving - { - get => GetFlag( MLQuestFlag.Spellweaving ); - set => SetFlag( MLQuestFlag.Spellweaving, value ); - } + if (quest != null && quest.IsChainTriggered) + ChainOffers.Add(quest); + } - [CommandProperty( AccessLevel.GameMaster )] - public bool SummonFey - { - get => GetFlag( MLQuestFlag.SummonFey ); - set => SetFlag( MLQuestFlag.SummonFey, value ); - } + m_Flags = (MLQuestFlag)reader.ReadEncodedInt(); + } - [CommandProperty( AccessLevel.GameMaster )] - public bool SummonFiend - { - get => GetFlag( MLQuestFlag.SummonFiend ); - set => SetFlag( MLQuestFlag.SummonFiend, value ); - } + public PlayerMobile Owner{ get; } - [CommandProperty( AccessLevel.GameMaster )] - public bool BedlamAccess - { - get => GetFlag( MLQuestFlag.BedlamAccess ); - set => SetFlag( MLQuestFlag.BedlamAccess, value ); - } + public List QuestInstances{ get; } - public MLQuestContext( PlayerMobile owner ) - { - Owner = owner; - QuestInstances = new List(); - m_DoneQuests = new List(); - ChainOffers = new List(); - m_Flags = MLQuestFlag.None; - } + public List ChainOffers{ get; } - public bool HasDoneQuest( Type questType ) - { - MLQuest quest = MLQuestSystem.FindQuest( questType ); + [CommandProperty(AccessLevel.GameMaster)] + public bool IsFull => QuestInstances.Count >= MLQuestSystem.MaxConcurrentQuests; - return ( quest != null && HasDoneQuest( quest ) ); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Spellweaving + { + get => GetFlag(MLQuestFlag.Spellweaving); + set => SetFlag(MLQuestFlag.Spellweaving, value); + } - public bool HasDoneQuest( MLQuest quest ) - { - foreach ( MLDoneQuestInfo info in m_DoneQuests ) - { - if ( info.m_Quest == quest ) - return true; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool SummonFey + { + get => GetFlag(MLQuestFlag.SummonFey); + set => SetFlag(MLQuestFlag.SummonFey, value); + } - return false; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool SummonFiend + { + get => GetFlag(MLQuestFlag.SummonFiend); + set => SetFlag(MLQuestFlag.SummonFiend, value); + } - public bool HasDoneQuest( MLQuest quest, out DateTime nextAvailable ) - { - nextAvailable = DateTime.MinValue; + [CommandProperty(AccessLevel.GameMaster)] + public bool BedlamAccess + { + get => GetFlag(MLQuestFlag.BedlamAccess); + set => SetFlag(MLQuestFlag.BedlamAccess, value); + } - foreach ( MLDoneQuestInfo info in m_DoneQuests ) - { - if ( info.m_Quest == quest ) - { - nextAvailable = info.m_NextAvailable; - return true; - } - } + public bool HasDoneQuest(Type questType) + { + MLQuest quest = MLQuestSystem.FindQuest(questType); - return false; - } + return quest != null && HasDoneQuest(quest); + } - public void SetDoneQuest( MLQuest quest ) - { - SetDoneQuest( quest, DateTime.MinValue ); - } + public bool HasDoneQuest(MLQuest quest) + { + foreach (MLDoneQuestInfo info in m_DoneQuests) + if (info.m_Quest == quest) + return true; - public void SetDoneQuest( MLQuest quest, DateTime nextAvailable ) - { - foreach ( MLDoneQuestInfo info in m_DoneQuests ) - { - if ( info.m_Quest == quest ) - { - info.m_NextAvailable = nextAvailable; - return; - } - } + return false; + } - m_DoneQuests.Add( new MLDoneQuestInfo( quest, nextAvailable ) ); - } + public bool HasDoneQuest(MLQuest quest, out DateTime nextAvailable) + { + nextAvailable = DateTime.MinValue; - public void RemoveDoneQuest( MLQuest quest ) - { - for ( int i = m_DoneQuests.Count - 1; i >= 0; --i ) - { - MLDoneQuestInfo info = m_DoneQuests[i]; + foreach (MLDoneQuestInfo info in m_DoneQuests) + if (info.m_Quest == quest) + { + nextAvailable = info.m_NextAvailable; + return true; + } - if ( info.m_Quest == quest ) - m_DoneQuests.RemoveAt( i ); - } - } + return false; + } - public void HandleDeath() - { - for ( int i = QuestInstances.Count - 1; i >= 0; --i ) - QuestInstances[i].OnPlayerDeath(); - } + public void SetDoneQuest(MLQuest quest) + { + SetDoneQuest(quest, DateTime.MinValue); + } - public void HandleDeletion() - { - for ( int i = QuestInstances.Count - 1; i >= 0; --i ) - QuestInstances[i].Remove(); - } + public void SetDoneQuest(MLQuest quest, DateTime nextAvailable) + { + foreach (MLDoneQuestInfo info in m_DoneQuests) + if (info.m_Quest == quest) + { + info.m_NextAvailable = nextAvailable; + return; + } - public MLQuestInstance FindInstance( Type questType ) - { - MLQuest quest = MLQuestSystem.FindQuest( questType ); + m_DoneQuests.Add(new MLDoneQuestInfo(quest, nextAvailable)); + } - if ( quest == null ) - return null; + public void RemoveDoneQuest(MLQuest quest) + { + for (int i = m_DoneQuests.Count - 1; i >= 0; --i) + { + MLDoneQuestInfo info = m_DoneQuests[i]; - return FindInstance( quest ); - } + if (info.m_Quest == quest) + m_DoneQuests.RemoveAt(i); + } + } - public MLQuestInstance FindInstance( MLQuest quest ) - { - foreach ( MLQuestInstance instance in QuestInstances ) - { - if ( instance.Quest == quest ) - return instance; - } + public void HandleDeath() + { + for (int i = QuestInstances.Count - 1; i >= 0; --i) + QuestInstances[i].OnPlayerDeath(); + } - return null; - } + public void HandleDeletion() + { + for (int i = QuestInstances.Count - 1; i >= 0; --i) + QuestInstances[i].Remove(); + } - public bool IsDoingQuest( Type questType ) - { - MLQuest quest = MLQuestSystem.FindQuest( questType ); + public MLQuestInstance FindInstance(Type questType) + { + MLQuest quest = MLQuestSystem.FindQuest(questType); - return ( quest != null && IsDoingQuest( quest ) ); - } + if (quest == null) + return null; - public bool IsDoingQuest( MLQuest quest ) - { - return ( FindInstance( quest ) != null ); - } + return FindInstance(quest); + } - public void Serialize( GenericWriter writer ) - { - // Version info is written in MLQuestPersistence.Serialize + public MLQuestInstance FindInstance(MLQuest quest) + { + foreach (MLQuestInstance instance in QuestInstances) + if (instance.Quest == quest) + return instance; - writer.WriteMobile( Owner ); - writer.Write( QuestInstances.Count ); + return null; + } - foreach ( MLQuestInstance instance in QuestInstances ) - instance.Serialize( writer ); + public bool IsDoingQuest(Type questType) + { + MLQuest quest = MLQuestSystem.FindQuest(questType); - writer.Write( m_DoneQuests.Count ); + return quest != null && IsDoingQuest(quest); + } - foreach ( MLDoneQuestInfo info in m_DoneQuests ) - info.Serialize( writer ); + public bool IsDoingQuest(MLQuest quest) + { + return FindInstance(quest) != null; + } - writer.Write( ChainOffers.Count ); + public void Serialize(GenericWriter writer) + { + // Version info is written in MLQuestPersistence.Serialize - foreach ( MLQuest quest in ChainOffers ) - MLQuestSystem.WriteQuestRef( writer, quest ); + writer.WriteMobile(Owner); + writer.Write(QuestInstances.Count); - writer.WriteEncodedInt( (int)m_Flags ); - } + foreach (MLQuestInstance instance in QuestInstances) + instance.Serialize(writer); - public MLQuestContext( GenericReader reader, int version ) - { - Owner = reader.ReadMobile(); - QuestInstances = new List(); - m_DoneQuests = new List(); - ChainOffers = new List(); + writer.Write(m_DoneQuests.Count); - int instances = reader.ReadInt(); + foreach (MLDoneQuestInfo info in m_DoneQuests) + info.Serialize(writer); - for ( int i = 0; i < instances; ++i ) - { - MLQuestInstance instance = MLQuestInstance.Deserialize( reader, version, Owner ); + writer.Write(ChainOffers.Count); - if ( instance != null ) - QuestInstances.Add( instance ); - } + foreach (MLQuest quest in ChainOffers) + MLQuestSystem.WriteQuestRef(writer, quest); - int doneQuests = reader.ReadInt(); + writer.WriteEncodedInt((int)m_Flags); + } - for ( int i = 0; i < doneQuests; ++i ) - { - MLDoneQuestInfo info = MLDoneQuestInfo.Deserialize( reader, version ); + public bool GetFlag(MLQuestFlag flag) + { + return (m_Flags & flag) != 0; + } - if ( info != null ) - m_DoneQuests.Add( info ); - } + public void SetFlag(MLQuestFlag flag, bool value) + { + if (value) + m_Flags |= flag; + else + m_Flags &= ~flag; + } - int chainOffers = reader.ReadInt(); + private class MLDoneQuestInfo + { + public DateTime m_NextAvailable; + public MLQuest m_Quest; - for ( int i = 0; i < chainOffers; ++i ) - { - MLQuest quest = MLQuestSystem.ReadQuestRef( reader ); + public MLDoneQuestInfo(MLQuest quest, DateTime nextAvailable) + { + m_Quest = quest; + m_NextAvailable = nextAvailable; + } - if ( quest != null && quest.IsChainTriggered ) - ChainOffers.Add( quest ); - } + public void Serialize(GenericWriter writer) + { + MLQuestSystem.WriteQuestRef(writer, m_Quest); + writer.Write(m_NextAvailable); + } - m_Flags = (MLQuestFlag)reader.ReadEncodedInt(); - } + public static MLDoneQuestInfo Deserialize(GenericReader reader, int version) + { + MLQuest quest = MLQuestSystem.ReadQuestRef(reader); + DateTime nextAvailable = reader.ReadDateTime(); - public bool GetFlag( MLQuestFlag flag ) - { - return ( ( m_Flags & flag ) != 0 ); - } + if (quest == null || !quest.RecordCompletion) + return null; // forget about this record - public void SetFlag( MLQuestFlag flag, bool value ) - { - if ( value ) - m_Flags |= flag; - else - m_Flags &= ~flag; - } - } -} + return new MLDoneQuestInfo(quest, nextAvailable); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/MLQuestEntry.cs b/Scripts/Engines/MLQuests/MLQuestEntry.cs index eb90896e2..f85bf66b8 100644 --- a/Scripts/Engines/MLQuests/MLQuestEntry.cs +++ b/Scripts/Engines/MLQuests/MLQuestEntry.cs @@ -1,496 +1,488 @@ using System; using System.Collections.Generic; -using Server.Engines.MLQuests.Objectives; -using Server.Mobiles; using Server.Engines.MLQuests.Gumps; +using Server.Engines.MLQuests.Objectives; using Server.Engines.MLQuests.Rewards; +using Server.Mobiles; namespace Server.Engines.MLQuests { - [Flags] - public enum MLQuestInstanceFlags : byte - { - None = 0x00, - ClaimReward = 0x01, - Removed = 0x02, - Failed = 0x04 - } + [Flags] + public enum MLQuestInstanceFlags : byte + { + None = 0x00, + ClaimReward = 0x01, + Removed = 0x02, + Failed = 0x04 + } - public class MLQuestInstance - { - private IQuestGiver m_Quester; + public class MLQuestInstance + { + private MLQuestInstanceFlags m_Flags; + private IQuestGiver m_Quester; - private MLQuestInstanceFlags m_Flags; + private Timer m_Timer; - private Timer m_Timer; + public MLQuestInstance(MLQuest quest, IQuestGiver quester, PlayerMobile player) + { + Quest = quest; - public MLQuestInstance( MLQuest quest, IQuestGiver quester, PlayerMobile player ) - { - Quest = quest; + m_Quester = quester; + QuesterType = quester?.GetType(); + Player = player; - m_Quester = quester; - QuesterType = quester?.GetType(); - Player = player; + Accepted = DateTime.UtcNow; + m_Flags = MLQuestInstanceFlags.None; - Accepted = DateTime.UtcNow; - m_Flags = MLQuestInstanceFlags.None; + Objectives = new BaseObjectiveInstance[quest.Objectives.Count]; - Objectives = new BaseObjectiveInstance[quest.Objectives.Count]; + BaseObjectiveInstance obj; + bool timed = false; - BaseObjectiveInstance obj; - bool timed = false; + for (int i = 0; i < quest.Objectives.Count; ++i) + { + Objectives[i] = obj = quest.Objectives[i].CreateInstance(this); - for ( int i = 0; i < quest.Objectives.Count; ++i ) - { - Objectives[i] = obj = quest.Objectives[i].CreateInstance( this ); + if (obj.IsTimed) + timed = true; + } - if ( obj.IsTimed ) - timed = true; - } + Register(); - Register(); + if (timed) + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(5), Slice); + } - if ( timed ) - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 5 ), Slice ); - } + public MLQuest Quest{ get; set; } - private void Register() - { - Quest?.Instances?.Add( this ); + public IQuestGiver Quester + { + get => m_Quester; + set + { + m_Quester = value; + QuesterType = value?.GetType(); + } + } + + public Type QuesterType{ get; private set; } + + public PlayerMobile Player{ get; set; } + + public MLQuestContext PlayerContext => MLQuestSystem.GetOrCreateContext(Player); + + public DateTime Accepted{ get; set; } + + public bool ClaimReward + { + get => GetFlag(MLQuestInstanceFlags.ClaimReward); + set => SetFlag(MLQuestInstanceFlags.ClaimReward, value); + } + + public bool Removed + { + get => GetFlag(MLQuestInstanceFlags.Removed); + set => SetFlag(MLQuestInstanceFlags.Removed, value); + } + + public bool Failed + { + get => GetFlag(MLQuestInstanceFlags.Failed); + set => SetFlag(MLQuestInstanceFlags.Failed, value); + } + + public BaseObjectiveInstance[] Objectives{ get; set; } + + public bool SkipReportBack => TextDefinition.IsNullOrEmpty(Quest.CompletionMessage); + + private void Register() + { + Quest?.Instances?.Add(this); + + if (Player != null) + PlayerContext.QuestInstances.Add(this); + } + + private void Unregister() + { + Quest?.Instances?.Remove(this); + + if (Player != null) + PlayerContext.QuestInstances.Remove(this); + + Removed = true; + } + + public bool AllowsQuestItem(Item item, Type type) + { + foreach (BaseObjectiveInstance objective in Objectives) + if (!objective.Expired && objective.AllowsQuestItem(item, type)) + return true; + + return false; + } + + public bool IsCompleted() + { + bool requiresAll = Quest.ObjectiveType == ObjectiveType.All; + + foreach (BaseObjectiveInstance obj in Objectives) + { + bool complete = obj.IsCompleted(); + + if (complete && !requiresAll) + return true; + if (!complete && requiresAll) + return false; + } + + return requiresAll; + } + + public void CheckComplete() + { + if (IsCompleted()) + { + Player.PlaySound(0x5B5); // public sound + + foreach (BaseObjectiveInstance obj in Objectives) + obj.OnQuestCompleted(); + + TextDefinition.SendMessageTo(Player, Quest.CompletionNotice, 0x23); + + /* + * Advance to the ClaimReward=true stage if this quest has no + * completion message to show anyway. This suppresses further + * triggers of CheckComplete. + * + * For quests that require collections, this is done later when + * the player double clicks the quester. + */ + if (!Removed && SkipReportBack && !Quest.RequiresCollection + ) // An OnQuestCompleted can potentially have removed this instance already + ContinueReportBack(false); + } + } + + public void Fail() + { + Failed = true; + } + + private void Slice() + { + if (ClaimReward || Removed) + { + StopTimer(); + return; + } + + bool hasAnyFails = false; + bool hasAnyLeft = false; + + foreach (BaseObjectiveInstance obj in Objectives) + if (!obj.Expired) + { + if (obj.IsTimed && obj.EndTime <= DateTime.UtcNow) + { + Player.SendLocalizedMessage(1072258); // You failed to complete an objective in time! + + obj.Expired = true; + obj.OnExpire(); + + hasAnyFails = true; + } + else + { + hasAnyLeft = true; + } + } + + if (Quest.ObjectiveType == ObjectiveType.All && hasAnyFails || !hasAnyLeft) + Fail(); + + if (!hasAnyLeft) + StopTimer(); + } + + public void SendProgressGump() + { + Player.SendGump(new QuestConversationGump(Quest, Player, Quest.InProgressMessage)); + } + + public void SendRewardOffer() + { + Quest.GetRewards(this); + } + + // TODO: Split next quest stuff from SendRewardGump stuff? + public void SendRewardGump() + { + Type nextQuestType = Quest.NextQuest; + + if (nextQuestType != null) + { + ClaimRewards(); // skip reward gump + + if (Removed) // rewards were claimed successfully + { + MLQuest nextQuest = MLQuestSystem.FindQuest(nextQuestType); + + nextQuest?.SendOffer(m_Quester, Player); + } + } + else + { + Player.SendGump(new QuestRewardGump(this)); + } + } + + public void SendReportBackGump() + { + if (SkipReportBack) + ContinueReportBack(true); // skip ahead + else + Player.SendGump(new QuestReportBackGump(this)); + } + + public void ContinueReportBack(bool sendRewardGump) + { + // There is a backpack check here on OSI for the rewards as well (even though it's not needed...) + + if (Quest.ObjectiveType == ObjectiveType.All) + { + // TODO: 1115877 - You no longer have the required items to complete this quest. + foreach (BaseObjectiveInstance objective in Objectives) + if (!objective.IsCompleted()) + return; + + foreach (BaseObjectiveInstance objective in Objectives) + if (!objective.OnBeforeClaimReward()) + return; + + foreach (BaseObjectiveInstance objective in Objectives) + objective.OnClaimReward(); + } + else + { + /* The following behavior is unverified, as OSI (currently) has no collect quest requiring + * only one objective to be completed. It is assumed that only one objective is claimed + * (the first completed one), even when multiple are complete. + */ + bool complete = false; + + foreach (BaseObjectiveInstance objective in Objectives) + if (objective.IsCompleted()) + { + if (objective.OnBeforeClaimReward()) + { + complete = true; + objective.OnClaimReward(); + } + + break; + } + + if (!complete) + return; + } + + ClaimReward = true; + + if (Quest.HasRestartDelay) + PlayerContext.SetDoneQuest(Quest, DateTime.UtcNow + Quest.GetRestartDelay()); + + // This is correct for ObjectiveType.Any as well + foreach (BaseObjectiveInstance objective in Objectives) + objective.OnAfterClaimReward(); + + if (sendRewardGump) + SendRewardOffer(); + } + + public void ClaimRewards() + { + if (Quest == null || Player == null || Player.Deleted || !ClaimReward || Removed) + return; + + List rewards = new List(); + + foreach (BaseReward reward in Quest.Rewards) + reward.AddRewardItems(Player, rewards); + + if (rewards.Count != 0) + { + // On OSI a more naive method of checking is used. + // For containers, only the actual container item counts. + bool canFit = true; + + foreach (Item rewardItem in rewards) + if (!Player.AddToBackpack(rewardItem)) + { + canFit = false; + break; + } + + if (!canFit) + { + foreach (Item rewardItem in rewards) + rewardItem.Delete(); + + Player.SendLocalizedMessage( + 1078524); // Your backpack is full. You cannot complete the quest and receive your reward. + return; + } + + foreach (Item rewardItem in rewards) + { + string rewardName = rewardItem.Name ?? string.Concat("#", rewardItem.LabelNumber); + + if (rewardItem.Stackable) + Player.SendLocalizedMessage(1115917, + string.Concat(rewardItem.Amount, "\t", + rewardName)); // You receive a reward: ~1_QUANTITY~ ~2_ITEM~ + else + Player.SendLocalizedMessage(1074360, rewardName); // You receive a reward: ~1_REWARD~ + } + } + + foreach (BaseObjectiveInstance objective in Objectives) + objective.OnRewardClaimed(); + + Quest.OnRewardClaimed(this); + + MLQuestContext context = PlayerContext; + + if (Quest.RecordCompletion && !Quest.HasRestartDelay) // Quests with restart delays are logged earlier as per OSI + context.SetDoneQuest(Quest); + + if (Quest.IsChainTriggered) + context.ChainOffers.Remove(Quest); + + Type nextQuestType = Quest.NextQuest; + + if (nextQuestType != null) + { + MLQuest nextQuest = MLQuestSystem.FindQuest(nextQuestType); + + if (nextQuest != null && !context.ChainOffers.Contains(nextQuest)) + context.ChainOffers.Add(nextQuest); + } + + Remove(); + } + + public void Cancel() + { + Cancel(false); + } + + public void Cancel(bool removeChain) + { + Remove(); + + Player.SendSound(0x5B3); // private sound - if ( Player != null ) - PlayerContext.QuestInstances.Add( this ); - } - - private void Unregister() - { - Quest?.Instances?.Remove( this ); - - if ( Player != null ) - PlayerContext.QuestInstances.Remove( this ); - - Removed = true; - } - - public MLQuest Quest { get; set; } - - public IQuestGiver Quester - { - get => m_Quester; - set - { - m_Quester = value; - QuesterType = value?.GetType(); - } - } - - public Type QuesterType { get; private set; } - - public PlayerMobile Player { get; set; } - - public MLQuestContext PlayerContext => MLQuestSystem.GetOrCreateContext( Player ); - - public DateTime Accepted { get; set; } - - public bool ClaimReward - { - get => GetFlag( MLQuestInstanceFlags.ClaimReward ); - set => SetFlag( MLQuestInstanceFlags.ClaimReward, value ); - } - - public bool Removed - { - get => GetFlag( MLQuestInstanceFlags.Removed ); - set => SetFlag( MLQuestInstanceFlags.Removed, value ); - } - - public bool Failed - { - get => GetFlag( MLQuestInstanceFlags.Failed ); - set => SetFlag( MLQuestInstanceFlags.Failed, value ); - } - - public BaseObjectiveInstance[] Objectives { get; set; } - - public bool AllowsQuestItem( Item item, Type type ) - { - foreach ( BaseObjectiveInstance objective in Objectives ) - { - if ( !objective.Expired && objective.AllowsQuestItem( item, type ) ) - return true; - } - - return false; - } - - public bool IsCompleted() - { - bool requiresAll = ( Quest.ObjectiveType == ObjectiveType.All ); - - foreach ( BaseObjectiveInstance obj in Objectives ) - { - bool complete = obj.IsCompleted(); - - if ( complete && !requiresAll ) - return true; - if ( !complete && requiresAll ) - return false; - } - - return requiresAll; - } - - public void CheckComplete() - { - if ( IsCompleted() ) - { - Player.PlaySound( 0x5B5 ); // public sound - - foreach ( BaseObjectiveInstance obj in Objectives ) - obj.OnQuestCompleted(); - - TextDefinition.SendMessageTo( Player, Quest.CompletionNotice, 0x23 ); - - /* - * Advance to the ClaimReward=true stage if this quest has no - * completion message to show anyway. This suppresses further - * triggers of CheckComplete. - * - * For quests that require collections, this is done later when - * the player double clicks the quester. - */ - if ( !Removed && SkipReportBack && !Quest.RequiresCollection ) // An OnQuestCompleted can potentially have removed this instance already - ContinueReportBack( false ); - } - } - - public void Fail() - { - Failed = true; - } - - private void Slice() - { - if ( ClaimReward || Removed ) - { - StopTimer(); - return; - } - - bool hasAnyFails = false; - bool hasAnyLeft = false; - - foreach ( BaseObjectiveInstance obj in Objectives ) - { - if ( !obj.Expired ) - { - if ( obj.IsTimed && obj.EndTime <= DateTime.UtcNow ) - { - Player.SendLocalizedMessage( 1072258 ); // You failed to complete an objective in time! - - obj.Expired = true; - obj.OnExpire(); - - hasAnyFails = true; - } - else - { - hasAnyLeft = true; - } - } - } - - if ( ( Quest.ObjectiveType == ObjectiveType.All && hasAnyFails ) || !hasAnyLeft ) - Fail(); - - if ( !hasAnyLeft ) - StopTimer(); - } - - public void SendProgressGump() - { - Player.SendGump( new QuestConversationGump( Quest, Player, Quest.InProgressMessage ) ); - } - - public void SendRewardOffer() - { - Quest.GetRewards( this ); - } - - // TODO: Split next quest stuff from SendRewardGump stuff? - public void SendRewardGump() - { - Type nextQuestType = Quest.NextQuest; - - if ( nextQuestType != null ) - { - ClaimRewards(); // skip reward gump - - if ( Removed ) // rewards were claimed successfully - { - MLQuest nextQuest = MLQuestSystem.FindQuest( nextQuestType ); - - nextQuest?.SendOffer( m_Quester, Player ); - } - } - else - { - Player.SendGump( new QuestRewardGump( this ) ); - } - } - - public bool SkipReportBack => TextDefinition.IsNullOrEmpty( Quest.CompletionMessage ); - - public void SendReportBackGump() - { - if ( SkipReportBack ) - ContinueReportBack( true ); // skip ahead - else - Player.SendGump( new QuestReportBackGump( this ) ); - } - - public void ContinueReportBack( bool sendRewardGump ) - { - // There is a backpack check here on OSI for the rewards as well (even though it's not needed...) - - if ( Quest.ObjectiveType == ObjectiveType.All ) - { - // TODO: 1115877 - You no longer have the required items to complete this quest. - foreach ( BaseObjectiveInstance objective in Objectives ) - { - if ( !objective.IsCompleted() ) - return; - } - - foreach ( BaseObjectiveInstance objective in Objectives ) - { - if ( !objective.OnBeforeClaimReward() ) - return; - } - - foreach ( BaseObjectiveInstance objective in Objectives ) - objective.OnClaimReward(); - } - else - { - /* The following behavior is unverified, as OSI (currently) has no collect quest requiring - * only one objective to be completed. It is assumed that only one objective is claimed - * (the first completed one), even when multiple are complete. - */ - bool complete = false; - - foreach ( BaseObjectiveInstance objective in Objectives ) - { - if ( objective.IsCompleted() ) - { - if ( objective.OnBeforeClaimReward() ) - { - complete = true; - objective.OnClaimReward(); - } - - break; - } - } - - if ( !complete ) - return; - } - - ClaimReward = true; - - if ( Quest.HasRestartDelay ) - PlayerContext.SetDoneQuest( Quest, DateTime.UtcNow + Quest.GetRestartDelay() ); - - // This is correct for ObjectiveType.Any as well - foreach ( BaseObjectiveInstance objective in Objectives ) - objective.OnAfterClaimReward(); - - if ( sendRewardGump ) - SendRewardOffer(); - } - - public void ClaimRewards() - { - if ( Quest == null || Player == null || Player.Deleted || !ClaimReward || Removed ) - return; - - List rewards = new List(); - - foreach ( BaseReward reward in Quest.Rewards ) - reward.AddRewardItems( Player, rewards ); - - if ( rewards.Count != 0 ) - { - // On OSI a more naive method of checking is used. - // For containers, only the actual container item counts. - bool canFit = true; - - foreach ( Item rewardItem in rewards ) - { - if ( !Player.AddToBackpack( rewardItem ) ) - { - canFit = false; - break; - } - } - - if ( !canFit ) - { - foreach ( Item rewardItem in rewards ) - rewardItem.Delete(); - - Player.SendLocalizedMessage( 1078524 ); // Your backpack is full. You cannot complete the quest and receive your reward. - return; - } - - foreach ( Item rewardItem in rewards ) - { - string rewardName = rewardItem.Name ?? string.Concat( "#", rewardItem.LabelNumber ); - - if ( rewardItem.Stackable ) - Player.SendLocalizedMessage( 1115917, string.Concat( rewardItem.Amount, "\t", rewardName ) ); // You receive a reward: ~1_QUANTITY~ ~2_ITEM~ - else - Player.SendLocalizedMessage( 1074360, rewardName ); // You receive a reward: ~1_REWARD~ - } - } - - foreach ( BaseObjectiveInstance objective in Objectives ) - objective.OnRewardClaimed(); - - Quest.OnRewardClaimed( this ); - - MLQuestContext context = PlayerContext; - - if ( Quest.RecordCompletion && !Quest.HasRestartDelay ) // Quests with restart delays are logged earlier as per OSI - context.SetDoneQuest( Quest ); - - if ( Quest.IsChainTriggered ) - context.ChainOffers.Remove( Quest ); - - Type nextQuestType = Quest.NextQuest; - - if ( nextQuestType != null ) - { - MLQuest nextQuest = MLQuestSystem.FindQuest( nextQuestType ); - - if ( nextQuest != null && !context.ChainOffers.Contains( nextQuest ) ) - context.ChainOffers.Add( nextQuest ); - } - - Remove(); - } - - public void Cancel() - { - Cancel( false ); - } - - public void Cancel( bool removeChain ) - { - Remove(); + foreach (BaseObjectiveInstance obj in Objectives) + obj.OnQuestCancelled(); + + Quest.OnCancel(this); + + if (removeChain) + PlayerContext.ChainOffers.Remove(Quest); + } + + public void Remove() + { + Unregister(); + StopTimer(); + } + + private void StopTimer() + { + if (m_Timer != null) + { + m_Timer.Stop(); + m_Timer = null; + } + } + + public void OnQuesterDeleted() + { + foreach (BaseObjectiveInstance obj in Objectives) + obj.OnQuesterDeleted(); + + Quest.OnQuesterDeleted(this); + } + + public void OnPlayerDeath() + { + foreach (BaseObjectiveInstance obj in Objectives) + obj.OnPlayerDeath(); + + Quest.OnPlayerDeath(this); + } + + private bool GetFlag(MLQuestInstanceFlags flag) + { + return (m_Flags & flag) != 0; + } - Player.SendSound( 0x5B3 ); // private sound + private void SetFlag(MLQuestInstanceFlags flag, bool value) + { + if (value) + m_Flags |= flag; + else + m_Flags &= ~flag; + } - foreach ( BaseObjectiveInstance obj in Objectives ) - obj.OnQuestCancelled(); - - Quest.OnCancel( this ); + public void Serialize(GenericWriter writer) + { + // Version info is written in MLQuestPersistence.Serialize - if ( removeChain ) - PlayerContext.ChainOffers.Remove( Quest ); - } - - public void Remove() - { - Unregister(); - StopTimer(); - } - - private void StopTimer() - { - if ( m_Timer != null ) - { - m_Timer.Stop(); - m_Timer = null; - } - } - - public void OnQuesterDeleted() - { - foreach ( BaseObjectiveInstance obj in Objectives ) - obj.OnQuesterDeleted(); - - Quest.OnQuesterDeleted( this ); - } - - public void OnPlayerDeath() - { - foreach ( BaseObjectiveInstance obj in Objectives ) - obj.OnPlayerDeath(); - - Quest.OnPlayerDeath( this ); - } + MLQuestSystem.WriteQuestRef(writer, Quest); - private bool GetFlag( MLQuestInstanceFlags flag ) - { - return ( ( m_Flags & flag ) != 0 ); - } + if (m_Quester == null || m_Quester.Deleted) + writer.Write(Serial.MinusOne); + else + writer.Write(m_Quester.Serial); - private void SetFlag( MLQuestInstanceFlags flag, bool value ) - { - if ( value ) - m_Flags |= flag; - else - m_Flags &= ~flag; - } + writer.Write(ClaimReward); + writer.Write(Objectives.Length); - public void Serialize( GenericWriter writer ) - { - // Version info is written in MLQuestPersistence.Serialize - - MLQuestSystem.WriteQuestRef( writer, Quest ); - - if ( m_Quester == null || m_Quester.Deleted ) - writer.Write( Serial.MinusOne ); - else - writer.Write( m_Quester.Serial ); - - writer.Write( ClaimReward ); - writer.Write( Objectives.Length ); - - foreach ( BaseObjectiveInstance objInstance in Objectives ) - objInstance.Serialize( writer ); - } - - public static MLQuestInstance Deserialize( GenericReader reader, int version, PlayerMobile pm ) - { - MLQuest quest = MLQuestSystem.ReadQuestRef( reader ); - - // TODO: Serialize quester TYPE too, the quest giver reference then becomes optional (only for escorts) - IQuestGiver quester = World.FindEntity( reader.ReadInt() ) as IQuestGiver; - - bool claimReward = reader.ReadBool(); - int objectives = reader.ReadInt(); - - MLQuestInstance instance; - - if ( quest != null && quester != null && pm != null ) - { - instance = quest.CreateInstance( quester, pm ); - instance.ClaimReward = claimReward; - } - else - { - instance = null; - } - - for ( int i = 0; i < objectives; ++i ) - BaseObjectiveInstance.Deserialize( reader, version, ( instance != null && i < instance.Objectives.Length ) ? instance.Objectives[i] : null ); - - instance?.Slice(); - - return instance; - } - } -} + foreach (BaseObjectiveInstance objInstance in Objectives) + objInstance.Serialize(writer); + } + + public static MLQuestInstance Deserialize(GenericReader reader, int version, PlayerMobile pm) + { + MLQuest quest = MLQuestSystem.ReadQuestRef(reader); + + // TODO: Serialize quester TYPE too, the quest giver reference then becomes optional (only for escorts) + IQuestGiver quester = World.FindEntity(reader.ReadInt()) as IQuestGiver; + + bool claimReward = reader.ReadBool(); + int objectives = reader.ReadInt(); + + MLQuestInstance instance; + + if (quest != null && quester != null && pm != null) + { + instance = quest.CreateInstance(quester, pm); + instance.ClaimReward = claimReward; + } + else + { + instance = null; + } + + for (int i = 0; i < objectives; ++i) + BaseObjectiveInstance.Deserialize(reader, version, + instance != null && i < instance.Objectives.Length ? instance.Objectives[i] : null); + + instance?.Slice(); + + return instance; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/MLQuestPersistence.cs b/Scripts/Engines/MLQuests/MLQuestPersistence.cs index c674ef8c8..66f041b89 100644 --- a/Scripts/Engines/MLQuests/MLQuestPersistence.cs +++ b/Scripts/Engines/MLQuests/MLQuestPersistence.cs @@ -1,63 +1,63 @@ namespace Server.Engines.MLQuests { - public class MLQuestPersistence : Item - { - private static MLQuestPersistence m_Instance; + public class MLQuestPersistence : Item + { + private static MLQuestPersistence m_Instance; - public static void EnsureExistence() - { - if ( m_Instance == null ) - m_Instance = new MLQuestPersistence(); - } + private MLQuestPersistence() + : base(1) + { + Movable = false; + } - public override string DefaultName => "ML quests persistence - Internal"; + public MLQuestPersistence(Serial serial) : base(serial) + { + m_Instance = this; + } - private MLQuestPersistence() - : base( 1 ) - { - Movable = false; - } + public override string DefaultName => "ML quests persistence - Internal"; - public MLQuestPersistence( Serial serial ) : base( serial ) - { - m_Instance = this; - } + public static void EnsureExistence() + { + if (m_Instance == null) + m_Instance = new MLQuestPersistence(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 2 ); // version - writer.Write( MLQuestSystem.Contexts.Count ); + writer.Write(2); // version + writer.Write(MLQuestSystem.Contexts.Count); - foreach ( MLQuestContext context in MLQuestSystem.Contexts.Values ) - context.Serialize( writer ); + foreach (MLQuestContext context in MLQuestSystem.Contexts.Values) + context.Serialize(writer); - writer.Write( MLQuestSystem.Quests.Count ); + writer.Write(MLQuestSystem.Quests.Count); - foreach ( MLQuest quest in MLQuestSystem.Quests.Values ) - MLQuest.Serialize( writer, quest ); - } + foreach (MLQuest quest in MLQuestSystem.Quests.Values) + MLQuest.Serialize(writer, quest); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - int contexts = reader.ReadInt(); + int version = reader.ReadInt(); + int contexts = reader.ReadInt(); - for ( int i = 0; i < contexts; ++i ) - { - MLQuestContext context = new MLQuestContext( reader, version ); + for (int i = 0; i < contexts; ++i) + { + MLQuestContext context = new MLQuestContext(reader, version); - if ( context.Owner != null ) - MLQuestSystem.Contexts[context.Owner] = context; - } + if (context.Owner != null) + MLQuestSystem.Contexts[context.Owner] = context; + } - int quests = reader.ReadInt(); + int quests = reader.ReadInt(); - for ( int i = 0; i < quests; ++i ) - MLQuest.Deserialize( reader, version ); - } - } -} + for (int i = 0; i < quests; ++i) + MLQuest.Deserialize(reader, version); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/MLQuestSystem.cs b/Scripts/Engines/MLQuests/MLQuestSystem.cs index 7b14756cc..ae797231e 100644 --- a/Scripts/Engines/MLQuests/MLQuestSystem.cs +++ b/Scripts/Engines/MLQuests/MLQuestSystem.cs @@ -1,734 +1,717 @@ using System; +using System.Collections; using System.Collections.Generic; +using System.IO; using Server.Commands; +using Server.Commands.Generic; using Server.Engines.MLQuests.Gumps; using Server.Engines.MLQuests.Objectives; using Server.Gumps; +using Server.Items; using Server.Mobiles; using Server.Network; -using System.Collections; -using Server.Commands.Generic; -using Server.Items; -using System.IO; namespace Server.Engines.MLQuests { - public static class MLQuestSystem - { - public static bool Enabled => Core.ML; + public static class MLQuestSystem + { + public const int MaxConcurrentQuests = 10; + public const int SpeechColor = 0x3B2; - public const int MaxConcurrentQuests = 10; - public const int SpeechColor = 0x3B2; + public static readonly bool AutoGenerateNew = true; + public static readonly bool Debug = false; - public static readonly bool AutoGenerateNew = true; - public static readonly bool Debug = false; + public static readonly List EmptyList = new List(); - public static readonly List EmptyList = new List(); + private static List m_EligiblePool = new List(); - public static Dictionary Quests { get; } + static MLQuestSystem() + { + Quests = new Dictionary(); + QuestGivers = new Dictionary>(); + Contexts = new Dictionary(); - public static Dictionary> QuestGivers { get; } + string cfgPath = Path.Combine(Core.BaseDirectory, Path.Combine("Data", "MLQuests.cfg")); - public static Dictionary Contexts { get; } + Type baseQuestType = typeof(MLQuest); + Type baseQuesterType = typeof(IQuestGiver); - static MLQuestSystem() - { - Quests = new Dictionary(); - QuestGivers = new Dictionary>(); - Contexts = new Dictionary(); + if (File.Exists(cfgPath)) + using (StreamReader sr = new StreamReader(cfgPath)) + { + string line; - string cfgPath = Path.Combine( Core.BaseDirectory, Path.Combine( "Data", "MLQuests.cfg" ) ); + while ((line = sr.ReadLine()) != null) + { + if (line.Length == 0 || line.StartsWith("#")) + continue; - Type baseQuestType = typeof( MLQuest ); - Type baseQuesterType = typeof( IQuestGiver ); + string[] split = line.Split('\t'); - if ( File.Exists( cfgPath ) ) - { - using ( StreamReader sr = new StreamReader( cfgPath ) ) - { - string line; + Type type = ScriptCompiler.FindTypeByName(split[0]); - while ( ( line = sr.ReadLine() ) != null ) - { - if ( line.Length == 0 || line.StartsWith( "#" ) ) - continue; + if (type == null || !baseQuestType.IsAssignableFrom(type)) + { + if (Debug) + Console.WriteLine("Warning: {1} quest type '{0}'", split[0], + type == null ? "Unknown" : "Invalid"); - string[] split = line.Split( '\t' ); + continue; + } - Type type = ScriptCompiler.FindTypeByName( split[0] ); + MLQuest quest = null; - if ( type == null || !baseQuestType.IsAssignableFrom( type ) ) - { - if ( Debug ) - Console.WriteLine( "Warning: {1} quest type '{0}'", split[0], ( type == null ) ? "Unknown" : "Invalid" ); + try + { + quest = Activator.CreateInstance(type) as MLQuest; + } + catch + { + } - continue; - } + if (quest == null) + continue; - MLQuest quest = null; + Register(type, quest); - try - { - quest = Activator.CreateInstance( type ) as MLQuest; - } - catch { } + for (int i = 1; i < split.Length; ++i) + { + Type questerType = ScriptCompiler.FindTypeByName(split[i]); - if ( quest == null ) - continue; + if (questerType == null || !baseQuesterType.IsAssignableFrom(questerType)) + { + if (Debug) + Console.WriteLine("Warning: {1} quester type '{0}'", split[i], + questerType == null ? "Unknown" : "Invalid"); - Register( type, quest ); - - for ( int i = 1; i < split.Length; ++i ) - { - Type questerType = ScriptCompiler.FindTypeByName( split[i] ); - - if ( questerType == null || !baseQuesterType.IsAssignableFrom( questerType ) ) - { - if ( Debug ) - Console.WriteLine( "Warning: {1} quester type '{0}'", split[i], ( questerType == null ) ? "Unknown" : "Invalid" ); - - continue; - } - - RegisterQuestGiver( quest, questerType ); - } - } - } - } - } - - private static void Register( Type type, MLQuest quest ) - { - Quests[type] = quest; - } - - private static void RegisterQuestGiver( MLQuest quest, Type questerType ) - { - if (!QuestGivers.TryGetValue( questerType, out List questList )) - QuestGivers[questerType] = questList = new List(); - - questList.Add( quest ); - } - - public static void Register( MLQuest quest, params Type[] questerTypes ) - { - Register( quest.GetType(), quest ); - - foreach ( Type questerType in questerTypes ) - RegisterQuestGiver( quest, questerType ); - } - - public static void Initialize() - { - if ( !Enabled ) - return; - - if ( AutoGenerateNew ) - { - foreach ( MLQuest quest in Quests.Values ) - { - if ( quest != null && !quest.Deserialized ) - quest.Generate(); - } - } - - MLQuestPersistence.EnsureExistence(); - - CommandSystem.Register( "MLQuestsInfo", AccessLevel.Administrator, MLQuestsInfo_OnCommand ); - CommandSystem.Register( "SaveQuest", AccessLevel.Administrator, SaveQuest_OnCommand ); - CommandSystem.Register( "SaveAllQuests", AccessLevel.Administrator, SaveAllQuests_OnCommand ); - CommandSystem.Register( "InvalidQuestItems", AccessLevel.Administrator, InvalidQuestItems_OnCommand ); - - TargetCommands.Register( new ViewQuestsCommand() ); - TargetCommands.Register( new ViewContextCommand() ); - - EventSink.QuestGumpRequest += EventSink_QuestGumpRequest; - } - - [Usage( "MLQuestsInfo" )] - [Description( "Displays general information about the ML quest system, or a quest by type name." )] - public static void MLQuestsInfo_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - - if ( e.Length == 0 ) - { - m.SendMessage( "Quest table length: {0}", Quests.Count ); - return; - } - - Type index = ScriptCompiler.FindTypeByName( e.GetString( 0 ) ); - MLQuest quest; - - if ( index == null || !Quests.TryGetValue( index, out quest ) ) - { - m.SendMessage( "Invalid quest type name." ); - return; - } - - m.SendMessage( "Activated: {0}", quest.Activated ); - m.SendMessage( "Number of objectives: {0}", quest.Objectives.Count ); - m.SendMessage( "Objective type: {0}", quest.ObjectiveType ); - m.SendMessage( "Number of active instances: {0}", quest.Instances.Count ); - } - - public class ViewQuestsCommand : BaseCommand - { - public ViewQuestsCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Simple; - Commands = new[] { "ViewQuests" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "ViewQuests"; - Description = "Displays a targeted mobile's quest overview."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - Mobile from = e.Mobile; - - if ( !(obj is PlayerMobile pm) ) - { - LogFailure( "That is not a player." ); - return; - } - - CommandLogging.WriteLine( from, "{0} {1} viewing quest overview of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( pm ) ); - from.SendGump( new QuestLogGump( pm, false ) ); - } - } - - private class ViewContextCommand : BaseCommand - { - public ViewContextCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.Simple; - Commands = new[] { "ViewMLContext" }; - ObjectTypes = ObjectTypes.Mobiles; - Usage = "ViewMLContext"; - Description = "Opens the ML quest context for a targeted mobile."; - } - - public override void Execute( CommandEventArgs e, object obj ) - { - if ( !(obj is PlayerMobile pm) ) - LogFailure( "They have no ML quest context." ); - else - e.Mobile.SendGump( new PropertiesGump( e.Mobile, GetOrCreateContext( pm ) ) ); - } - } - - [Usage( "SaveQuest [saveEnabled=true]" )] - [Description( "Allows serialization for a specific quest to be turned on or off." )] - public static void SaveQuest_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - - if ( e.Length == 0 || e.Length > 2 ) - { - m.SendMessage( "Syntax: SaveQuest [saveEnabled=true]" ); - return; - } - - Type index = ScriptCompiler.FindTypeByName( e.GetString( 0 ) ); - - if ( index == null || !Quests.TryGetValue( index, out MLQuest quest ) ) - { - m.SendMessage( "Invalid quest type name." ); - return; - } - - bool enable = ( e.Length == 2 ) ? e.GetBoolean( 1 ) : true; - - quest.SaveEnabled = enable; - m.SendMessage( "Serialization for quest {0} is now {1}.", quest.GetType().Name, enable ? "enabled" : "disabled" ); - - if ( AutoGenerateNew && !enable ) - m.SendMessage( "Please note that automatic generation of new quests is ON. This quest will be regenerated on the next server start." ); - } - - [Usage( "SaveAllQuests [saveEnabled=true]" )] - [Description( "Allows serialization for all quests to be turned on or off." )] - public static void SaveAllQuests_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - - if ( e.Length > 1 ) - { - m.SendMessage( "Syntax: SaveAllQuests [saveEnabled=true]" ); - return; - } - - bool enable = ( e.Length == 1 ) ? e.GetBoolean( 0 ) : true; - - foreach ( MLQuest quest in Quests.Values ) - quest.SaveEnabled = enable; - - m.SendMessage( "Serialization for all quests is now {0}.", enable ? "enabled" : "disabled" ); - - if ( AutoGenerateNew && !enable ) - m.SendMessage( "Please note that automatic generation of new quests is ON. All quests will be regenerated on the next server start." ); - } - - [Usage( "InvalidQuestItems" )] - [Description( "Provides an overview of all quest items not located in the top-level of a player's backpack." )] - public static void InvalidQuestItems_OnCommand( CommandEventArgs e ) - { - Mobile m = e.Mobile; - - ArrayList found = new ArrayList(); - - foreach ( Item item in World.Items.Values ) - { - if ( item.QuestItem ) - { - if ( item.Parent is Backpack pack ) - { - if ( pack.Parent is PlayerMobile player && player.Backpack == pack ) - continue; - } - - found.Add( item ); - } - } - - if ( found.Count == 0 ) - m.SendMessage( "No matching objects found." ); - else - m.SendGump( new InterfaceGump( m, new[] { "Object" }, found, 0, null ) ); - } - - private static bool FindQuest( IQuestGiver quester, PlayerMobile pm, MLQuestContext context, out MLQuest quest, out MLQuestInstance entry ) - { - quest = null; - entry = null; - - List quests = quester.MLQuests; - Type questerType = quester.GetType(); - - // 1. Check quests in progress with this NPC (overriding deliveries is intended) - if ( context != null ) - { - foreach ( MLQuest questEntry in quests ) - { - MLQuestInstance instance = context.FindInstance( questEntry ); - - if ( instance != null && ( instance.Quester == quester || ( !questEntry.IsEscort && instance.QuesterType == questerType ) ) ) - { - entry = instance; - quest = questEntry; - return true; - } - } - } - - // 2. Check deliveries (overriding chain offers is intended) - if ( ( entry = HandleDelivery( pm, quester, questerType ) ) != null ) - { - quest = entry.Quest; - return true; - } - - // 3. Check chain quest offers - if ( context != null ) - { - foreach ( MLQuest questEntry in quests ) - { - if ( questEntry.IsChainTriggered && context.ChainOffers.Contains( questEntry ) ) - { - quest = questEntry; - return true; - } - } - } - - // 4. Random quest - quest = RandomStarterQuest( quester, pm, context ); - - return ( quest != null ); - } - - public static void OnDoubleClick( IQuestGiver quester, PlayerMobile pm ) - { - if ( quester.Deleted || !pm.Alive ) - return; - - MLQuestContext context = GetContext( pm ); - - MLQuest quest; - MLQuestInstance entry; - - if ( !FindQuest( quester, pm, context, out quest, out entry ) ) - { - Tell( quester, pm, 1080107 ); // I'm sorry, I have nothing for you at this time. - return; - } - - if ( entry != null ) - { - TurnToFace( quester, pm ); - - if ( entry.Failed ) - return; // Note: OSI sends no gump at all for failed quests, they have to be cancelled in the quest overview - if ( entry.ClaimReward ) - entry.SendRewardOffer(); - else if ( entry.IsCompleted() ) - entry.SendReportBackGump(); - else - entry.SendProgressGump(); - } - else if ( quest.CanOffer( quester, pm, context, true ) ) - { - TurnToFace( quester, pm ); - - quest.SendOffer( quester, pm ); - } - } - - public static bool CanMarkQuestItem( PlayerMobile pm, Item item, Type type ) - { - MLQuestContext context = GetContext( pm ); - - if ( context != null ) - { - foreach ( MLQuestInstance quest in context.QuestInstances ) - { - if ( !quest.ClaimReward && quest.AllowsQuestItem( item, type ) ) - return true; - } - } - - return false; - } - - private static void OnMarkQuestItem( PlayerMobile pm, Item item, Type type ) - { - MLQuestContext context = GetContext( pm ); - - if ( context == null ) - return; - - List instances = context.QuestInstances; - - // We don't foreach because CheckComplete() can potentially modify the MLQuests list - for ( int i = instances.Count - 1; i >= 0; --i ) - { - MLQuestInstance instance = instances[i]; - - if ( instance.ClaimReward ) - continue; - - foreach ( BaseObjectiveInstance objective in instance.Objectives ) - { - if ( !objective.Expired && objective.AllowsQuestItem( item, type ) ) - { - objective.CheckComplete(); // yes, this can happen multiple times (for multiple quests) - break; - } - } - } - } - - public static bool MarkQuestItem( PlayerMobile pm, Item item ) - { - Type type = item.GetType(); - - if ( CanMarkQuestItem( pm, item, type ) ) - { - item.QuestItem = true; - OnMarkQuestItem( pm, item, type ); - - return true; - } - - return false; - } - - public static void HandleSkillGain( PlayerMobile pm, SkillName skill ) - { - MLQuestContext context = GetContext( pm ); - - if ( context == null ) - return; - - List instances = context.QuestInstances; - - for ( int i = instances.Count - 1; i >= 0; --i ) - { - MLQuestInstance instance = instances[i]; - - if ( instance.ClaimReward ) - continue; - - foreach ( BaseObjectiveInstance objective in instance.Objectives ) - { - if ( !objective.Expired && objective is GainSkillObjectiveInstance objectiveInstance && objectiveInstance.Handles( skill ) ) - { - objectiveInstance.CheckComplete(); - break; - } - } - } - } - - public static void HandleKill( PlayerMobile pm, Mobile mob ) - { - MLQuestContext context = GetContext( pm ); - - if ( context == null ) - return; - - List instances = context.QuestInstances; - - Type type = null; - - for ( int i = instances.Count - 1; i >= 0; --i ) - { - MLQuestInstance instance = instances[i]; - - if ( instance.ClaimReward ) - continue; - - /* A kill only counts for a single objective within a quest, - * but it can count for multiple quests. This is something not - * currently observable on OSI, so it is assumed behavior. - */ - foreach ( BaseObjectiveInstance objective in instance.Objectives ) - { - if ( !objective.Expired && objective is KillObjectiveInstance kill ) - { - if ( type == null ) - type = mob.GetType(); - - if ( kill.AddKill( mob, type ) ) - { - kill.CheckComplete(); - break; - } - } - } - } - } - - public static MLQuestInstance HandleDelivery( PlayerMobile pm, IQuestGiver quester, Type questerType ) - { - MLQuestContext context = GetContext( pm ); - - if ( context == null ) - return null; - - List instances = context.QuestInstances; - MLQuestInstance deliverInstance = null; - - for ( int i = instances.Count - 1; i >= 0; --i ) - { - MLQuestInstance instance = instances[i]; - - // Do NOT skip quests on ClaimReward, because the quester still needs the quest ref! - //if ( instance.ClaimReward ) - // continue; - - foreach ( BaseObjectiveInstance objective in instance.Objectives ) - { - // Note: On OSI, expired deliveries can still be completed. Bug? - if ( !objective.Expired && objective is DeliverObjectiveInstance deliver && deliver.IsDestination( quester, questerType ) ) - { - if ( !deliver.HasCompleted ) // objective completes only once - { - deliver.HasCompleted = true; - deliver.CheckComplete(); - - // The quest is continued with this NPC (important for chains) - instance.Quester = quester; - } - - if ( deliverInstance == null ) - deliverInstance = instance; - - break; // don't return, we may have to complete more deliveries - } - } - } - - return deliverInstance; - } - - public static MLQuestContext GetContext( PlayerMobile pm ) - { - Contexts.TryGetValue( pm, out MLQuestContext context ); - - return context; - } - - public static MLQuestContext GetOrCreateContext( PlayerMobile pm ) - { - if (!Contexts.TryGetValue( pm, out MLQuestContext context )) - Contexts[pm] = context = new MLQuestContext( pm ); - - return context; - } - - public static void HandleDeath( PlayerMobile pm ) - { - MLQuestContext context = GetContext( pm ); - - context?.HandleDeath(); - } - - public static void HandleDeletion( PlayerMobile pm ) - { - MLQuestContext context = GetContext( pm ); - - if ( context != null ) - { - context.HandleDeletion(); - Contexts.Remove( pm ); - } - } - - public static void HandleDeletion( IQuestGiver quester ) - { - foreach ( MLQuest quest in quester.MLQuests ) - { - List instances = quest.Instances; - - for ( int i = instances.Count - 1; i >= 0; --i ) - { - MLQuestInstance instance = instances[i]; - - if ( instance.Quester == quester ) - instance.OnQuesterDeleted(); - } - } - } - - public static void EventSink_QuestGumpRequest( QuestGumpRequestArgs args ) - { - if ( !Enabled || !(args.Mobile is PlayerMobile pm) ) - return; - - pm.SendGump( new QuestLogGump( pm ) ); - } - - private static List m_EligiblePool = new List(); - - public static MLQuest RandomStarterQuest( IQuestGiver quester, PlayerMobile pm, MLQuestContext context ) - { - List quests = quester.MLQuests; - - if ( quests.Count == 0 ) - return null; - - m_EligiblePool.Clear(); - MLQuest fallback = null; - - foreach ( MLQuest quest in quests ) - { - if ( quest.IsChainTriggered || ( context != null && context.IsDoingQuest( quest ) ) ) - continue; - - /* - * Save first quest that reaches the CanOffer call. - * If no quests are valid at all, return this quest for displaying the CanOffer error message. - */ - if ( fallback == null ) - fallback = quest; - - if ( quest.CanOffer( quester, pm, context, false ) ) - m_EligiblePool.Add( quest ); - } - - if ( m_EligiblePool.Count == 0 ) - return fallback; - - return m_EligiblePool[Utility.Random( m_EligiblePool.Count )]; - } - - public static void TurnToFace( IQuestGiver quester, Mobile mob ) - { - if ( quester is Mobile m ) - m.Direction = m.GetDirectionTo( mob ); - } - - public static void Tell( IQuestGiver quester, PlayerMobile pm, int cliloc ) - { - TurnToFace( quester, pm ); - - if ( quester is Mobile mobile ) - mobile.PrivateOverheadMessage( MessageType.Regular, SpeechColor, cliloc, pm.NetState ); - else if ( quester is Item item ) - MessageHelper.SendLocalizedMessageTo( item, pm, cliloc, SpeechColor ); - else - pm.SendLocalizedMessage( cliloc, "", SpeechColor ); - } - - public static void Tell( IQuestGiver quester, PlayerMobile pm, int cliloc, string args ) - { - TurnToFace( quester, pm ); - - if ( quester is Mobile mobile ) - mobile.PrivateOverheadMessage( MessageType.Regular, SpeechColor, cliloc, args, pm.NetState ); - else if ( quester is Item item ) - MessageHelper.SendLocalizedMessageTo( item, pm, cliloc, args, SpeechColor ); - else - pm.SendLocalizedMessage( cliloc, args, SpeechColor ); - } - - public static void Tell( IQuestGiver quester, PlayerMobile pm, string message ) - { - TurnToFace( quester, pm ); - - if ( quester is Mobile mobile ) - mobile.PrivateOverheadMessage( MessageType.Regular, SpeechColor, false, message, pm.NetState ); - else if ( quester is Item item ) - MessageHelper.SendMessageTo( item, pm, message, SpeechColor ); - else - pm.SendMessage( SpeechColor, message ); - } - - public static void TellDef( IQuestGiver quester, PlayerMobile pm, TextDefinition def ) - { - if ( def == null ) - return; - - if ( def.Number > 0 ) - Tell( quester, pm, def.Number ); - else if ( def.String != null ) - Tell( quester, pm, def.String ); - } - - public static void WriteQuestRef( GenericWriter writer, MLQuest quest ) - { - writer.Write( ( quest != null && quest.SaveEnabled ) ? quest.GetType().FullName : null ); - } - - public static MLQuest ReadQuestRef( GenericReader reader ) - { - string typeName = reader.ReadString(); - - if ( typeName == null ) - return null; // not serialized - - Type questType = ScriptCompiler.FindTypeByFullName( typeName ); - - if ( questType == null ) - return null; // no longer a type - - return FindQuest( questType ); - } - - public static MLQuest FindQuest( Type questType ) - { - Quests.TryGetValue( questType, out MLQuest result ); - - return result; - } - - public static List FindQuestList( Type questerType ) - { - return QuestGivers.TryGetValue(questerType, out List result) ? result : EmptyList; - } - } -} + continue; + } + + RegisterQuestGiver(quest, questerType); + } + } + } + } + + public static bool Enabled => Core.ML; + + public static Dictionary Quests{ get; } + + public static Dictionary> QuestGivers{ get; } + + public static Dictionary Contexts{ get; } + + private static void Register(Type type, MLQuest quest) + { + Quests[type] = quest; + } + + private static void RegisterQuestGiver(MLQuest quest, Type questerType) + { + if (!QuestGivers.TryGetValue(questerType, out List questList)) + QuestGivers[questerType] = questList = new List(); + + questList.Add(quest); + } + + public static void Register(MLQuest quest, params Type[] questerTypes) + { + Register(quest.GetType(), quest); + + foreach (Type questerType in questerTypes) + RegisterQuestGiver(quest, questerType); + } + + public static void Initialize() + { + if (!Enabled) + return; + + if (AutoGenerateNew) + foreach (MLQuest quest in Quests.Values) + if (quest != null && !quest.Deserialized) + quest.Generate(); + + MLQuestPersistence.EnsureExistence(); + + CommandSystem.Register("MLQuestsInfo", AccessLevel.Administrator, MLQuestsInfo_OnCommand); + CommandSystem.Register("SaveQuest", AccessLevel.Administrator, SaveQuest_OnCommand); + CommandSystem.Register("SaveAllQuests", AccessLevel.Administrator, SaveAllQuests_OnCommand); + CommandSystem.Register("InvalidQuestItems", AccessLevel.Administrator, InvalidQuestItems_OnCommand); + + TargetCommands.Register(new ViewQuestsCommand()); + TargetCommands.Register(new ViewContextCommand()); + + EventSink.QuestGumpRequest += EventSink_QuestGumpRequest; + } + + [Usage("MLQuestsInfo")] + [Description("Displays general information about the ML quest system, or a quest by type name.")] + public static void MLQuestsInfo_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + + if (e.Length == 0) + { + m.SendMessage("Quest table length: {0}", Quests.Count); + return; + } + + Type index = ScriptCompiler.FindTypeByName(e.GetString(0)); + MLQuest quest; + + if (index == null || !Quests.TryGetValue(index, out quest)) + { + m.SendMessage("Invalid quest type name."); + return; + } + + m.SendMessage("Activated: {0}", quest.Activated); + m.SendMessage("Number of objectives: {0}", quest.Objectives.Count); + m.SendMessage("Objective type: {0}", quest.ObjectiveType); + m.SendMessage("Number of active instances: {0}", quest.Instances.Count); + } + + [Usage("SaveQuest [saveEnabled=true]")] + [Description("Allows serialization for a specific quest to be turned on or off.")] + public static void SaveQuest_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + + if (e.Length == 0 || e.Length > 2) + { + m.SendMessage("Syntax: SaveQuest [saveEnabled=true]"); + return; + } + + Type index = ScriptCompiler.FindTypeByName(e.GetString(0)); + + if (index == null || !Quests.TryGetValue(index, out MLQuest quest)) + { + m.SendMessage("Invalid quest type name."); + return; + } + + bool enable = e.Length == 2 ? e.GetBoolean(1) : true; + + quest.SaveEnabled = enable; + m.SendMessage("Serialization for quest {0} is now {1}.", quest.GetType().Name, enable ? "enabled" : "disabled"); + + if (AutoGenerateNew && !enable) + m.SendMessage( + "Please note that automatic generation of new quests is ON. This quest will be regenerated on the next server start."); + } + + [Usage("SaveAllQuests [saveEnabled=true]")] + [Description("Allows serialization for all quests to be turned on or off.")] + public static void SaveAllQuests_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + + if (e.Length > 1) + { + m.SendMessage("Syntax: SaveAllQuests [saveEnabled=true]"); + return; + } + + bool enable = e.Length == 1 ? e.GetBoolean(0) : true; + + foreach (MLQuest quest in Quests.Values) + quest.SaveEnabled = enable; + + m.SendMessage("Serialization for all quests is now {0}.", enable ? "enabled" : "disabled"); + + if (AutoGenerateNew && !enable) + m.SendMessage( + "Please note that automatic generation of new quests is ON. All quests will be regenerated on the next server start."); + } + + [Usage("InvalidQuestItems")] + [Description("Provides an overview of all quest items not located in the top-level of a player's backpack.")] + public static void InvalidQuestItems_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + + ArrayList found = new ArrayList(); + + foreach (Item item in World.Items.Values) + if (item.QuestItem) + { + if (item.Parent is Backpack pack) + if (pack.Parent is PlayerMobile player && player.Backpack == pack) + continue; + + found.Add(item); + } + + if (found.Count == 0) + m.SendMessage("No matching objects found."); + else + m.SendGump(new InterfaceGump(m, new[] { "Object" }, found, 0, null)); + } + + private static bool FindQuest(IQuestGiver quester, PlayerMobile pm, MLQuestContext context, out MLQuest quest, + out MLQuestInstance entry) + { + quest = null; + entry = null; + + List quests = quester.MLQuests; + Type questerType = quester.GetType(); + + // 1. Check quests in progress with this NPC (overriding deliveries is intended) + if (context != null) + foreach (MLQuest questEntry in quests) + { + MLQuestInstance instance = context.FindInstance(questEntry); + + if (instance != null && (instance.Quester == quester || + !questEntry.IsEscort && instance.QuesterType == questerType)) + { + entry = instance; + quest = questEntry; + return true; + } + } + + // 2. Check deliveries (overriding chain offers is intended) + if ((entry = HandleDelivery(pm, quester, questerType)) != null) + { + quest = entry.Quest; + return true; + } + + // 3. Check chain quest offers + if (context != null) + foreach (MLQuest questEntry in quests) + if (questEntry.IsChainTriggered && context.ChainOffers.Contains(questEntry)) + { + quest = questEntry; + return true; + } + + // 4. Random quest + quest = RandomStarterQuest(quester, pm, context); + + return quest != null; + } + + public static void OnDoubleClick(IQuestGiver quester, PlayerMobile pm) + { + if (quester.Deleted || !pm.Alive) + return; + + MLQuestContext context = GetContext(pm); + + MLQuest quest; + MLQuestInstance entry; + + if (!FindQuest(quester, pm, context, out quest, out entry)) + { + Tell(quester, pm, 1080107); // I'm sorry, I have nothing for you at this time. + return; + } + + if (entry != null) + { + TurnToFace(quester, pm); + + if (entry.Failed) + return; // Note: OSI sends no gump at all for failed quests, they have to be cancelled in the quest overview + if (entry.ClaimReward) + entry.SendRewardOffer(); + else if (entry.IsCompleted()) + entry.SendReportBackGump(); + else + entry.SendProgressGump(); + } + else if (quest.CanOffer(quester, pm, context, true)) + { + TurnToFace(quester, pm); + + quest.SendOffer(quester, pm); + } + } + + public static bool CanMarkQuestItem(PlayerMobile pm, Item item, Type type) + { + MLQuestContext context = GetContext(pm); + + if (context != null) + foreach (MLQuestInstance quest in context.QuestInstances) + if (!quest.ClaimReward && quest.AllowsQuestItem(item, type)) + return true; + + return false; + } + + private static void OnMarkQuestItem(PlayerMobile pm, Item item, Type type) + { + MLQuestContext context = GetContext(pm); + + if (context == null) + return; + + List instances = context.QuestInstances; + + // We don't foreach because CheckComplete() can potentially modify the MLQuests list + for (int i = instances.Count - 1; i >= 0; --i) + { + MLQuestInstance instance = instances[i]; + + if (instance.ClaimReward) + continue; + + foreach (BaseObjectiveInstance objective in instance.Objectives) + if (!objective.Expired && objective.AllowsQuestItem(item, type)) + { + objective.CheckComplete(); // yes, this can happen multiple times (for multiple quests) + break; + } + } + } + + public static bool MarkQuestItem(PlayerMobile pm, Item item) + { + Type type = item.GetType(); + + if (CanMarkQuestItem(pm, item, type)) + { + item.QuestItem = true; + OnMarkQuestItem(pm, item, type); + + return true; + } + + return false; + } + + public static void HandleSkillGain(PlayerMobile pm, SkillName skill) + { + MLQuestContext context = GetContext(pm); + + if (context == null) + return; + + List instances = context.QuestInstances; + + for (int i = instances.Count - 1; i >= 0; --i) + { + MLQuestInstance instance = instances[i]; + + if (instance.ClaimReward) + continue; + + foreach (BaseObjectiveInstance objective in instance.Objectives) + if (!objective.Expired && objective is GainSkillObjectiveInstance objectiveInstance && + objectiveInstance.Handles(skill)) + { + objectiveInstance.CheckComplete(); + break; + } + } + } + + public static void HandleKill(PlayerMobile pm, Mobile mob) + { + MLQuestContext context = GetContext(pm); + + if (context == null) + return; + + List instances = context.QuestInstances; + + Type type = null; + + for (int i = instances.Count - 1; i >= 0; --i) + { + MLQuestInstance instance = instances[i]; + + if (instance.ClaimReward) + continue; + + /* A kill only counts for a single objective within a quest, + * but it can count for multiple quests. This is something not + * currently observable on OSI, so it is assumed behavior. + */ + foreach (BaseObjectiveInstance objective in instance.Objectives) + if (!objective.Expired && objective is KillObjectiveInstance kill) + { + if (type == null) + type = mob.GetType(); + + if (kill.AddKill(mob, type)) + { + kill.CheckComplete(); + break; + } + } + } + } + + public static MLQuestInstance HandleDelivery(PlayerMobile pm, IQuestGiver quester, Type questerType) + { + MLQuestContext context = GetContext(pm); + + if (context == null) + return null; + + List instances = context.QuestInstances; + MLQuestInstance deliverInstance = null; + + for (int i = instances.Count - 1; i >= 0; --i) + { + MLQuestInstance instance = instances[i]; + + // Do NOT skip quests on ClaimReward, because the quester still needs the quest ref! + //if ( instance.ClaimReward ) + // continue; + + foreach (BaseObjectiveInstance objective in instance.Objectives) + // Note: On OSI, expired deliveries can still be completed. Bug? + if (!objective.Expired && objective is DeliverObjectiveInstance deliver && + deliver.IsDestination(quester, questerType)) + { + if (!deliver.HasCompleted) // objective completes only once + { + deliver.HasCompleted = true; + deliver.CheckComplete(); + + // The quest is continued with this NPC (important for chains) + instance.Quester = quester; + } + + if (deliverInstance == null) + deliverInstance = instance; + + break; // don't return, we may have to complete more deliveries + } + } + + return deliverInstance; + } + + public static MLQuestContext GetContext(PlayerMobile pm) + { + Contexts.TryGetValue(pm, out MLQuestContext context); + + return context; + } + + public static MLQuestContext GetOrCreateContext(PlayerMobile pm) + { + if (!Contexts.TryGetValue(pm, out MLQuestContext context)) + Contexts[pm] = context = new MLQuestContext(pm); + + return context; + } + + public static void HandleDeath(PlayerMobile pm) + { + MLQuestContext context = GetContext(pm); + + context?.HandleDeath(); + } + + public static void HandleDeletion(PlayerMobile pm) + { + MLQuestContext context = GetContext(pm); + + if (context != null) + { + context.HandleDeletion(); + Contexts.Remove(pm); + } + } + + public static void HandleDeletion(IQuestGiver quester) + { + foreach (MLQuest quest in quester.MLQuests) + { + List instances = quest.Instances; + + for (int i = instances.Count - 1; i >= 0; --i) + { + MLQuestInstance instance = instances[i]; + + if (instance.Quester == quester) + instance.OnQuesterDeleted(); + } + } + } + + public static void EventSink_QuestGumpRequest(QuestGumpRequestArgs args) + { + if (!Enabled || !(args.Mobile is PlayerMobile pm)) + return; + + pm.SendGump(new QuestLogGump(pm)); + } + + public static MLQuest RandomStarterQuest(IQuestGiver quester, PlayerMobile pm, MLQuestContext context) + { + List quests = quester.MLQuests; + + if (quests.Count == 0) + return null; + + m_EligiblePool.Clear(); + MLQuest fallback = null; + + foreach (MLQuest quest in quests) + { + if (quest.IsChainTriggered || context != null && context.IsDoingQuest(quest)) + continue; + + /* + * Save first quest that reaches the CanOffer call. + * If no quests are valid at all, return this quest for displaying the CanOffer error message. + */ + if (fallback == null) + fallback = quest; + + if (quest.CanOffer(quester, pm, context, false)) + m_EligiblePool.Add(quest); + } + + if (m_EligiblePool.Count == 0) + return fallback; + + return m_EligiblePool[Utility.Random(m_EligiblePool.Count)]; + } + + public static void TurnToFace(IQuestGiver quester, Mobile mob) + { + if (quester is Mobile m) + m.Direction = m.GetDirectionTo(mob); + } + + public static void Tell(IQuestGiver quester, PlayerMobile pm, int cliloc) + { + TurnToFace(quester, pm); + + if (quester is Mobile mobile) + mobile.PrivateOverheadMessage(MessageType.Regular, SpeechColor, cliloc, pm.NetState); + else if (quester is Item item) + MessageHelper.SendLocalizedMessageTo(item, pm, cliloc, SpeechColor); + else + pm.SendLocalizedMessage(cliloc, "", SpeechColor); + } + + public static void Tell(IQuestGiver quester, PlayerMobile pm, int cliloc, string args) + { + TurnToFace(quester, pm); + + if (quester is Mobile mobile) + mobile.PrivateOverheadMessage(MessageType.Regular, SpeechColor, cliloc, args, pm.NetState); + else if (quester is Item item) + MessageHelper.SendLocalizedMessageTo(item, pm, cliloc, args, SpeechColor); + else + pm.SendLocalizedMessage(cliloc, args, SpeechColor); + } + + public static void Tell(IQuestGiver quester, PlayerMobile pm, string message) + { + TurnToFace(quester, pm); + + if (quester is Mobile mobile) + mobile.PrivateOverheadMessage(MessageType.Regular, SpeechColor, false, message, pm.NetState); + else if (quester is Item item) + MessageHelper.SendMessageTo(item, pm, message, SpeechColor); + else + pm.SendMessage(SpeechColor, message); + } + + public static void TellDef(IQuestGiver quester, PlayerMobile pm, TextDefinition def) + { + if (def == null) + return; + + if (def.Number > 0) + Tell(quester, pm, def.Number); + else if (def.String != null) + Tell(quester, pm, def.String); + } + + public static void WriteQuestRef(GenericWriter writer, MLQuest quest) + { + writer.Write(quest != null && quest.SaveEnabled ? quest.GetType().FullName : null); + } + + public static MLQuest ReadQuestRef(GenericReader reader) + { + string typeName = reader.ReadString(); + + if (typeName == null) + return null; // not serialized + + Type questType = ScriptCompiler.FindTypeByFullName(typeName); + + if (questType == null) + return null; // no longer a type + + return FindQuest(questType); + } + + public static MLQuest FindQuest(Type questType) + { + Quests.TryGetValue(questType, out MLQuest result); + + return result; + } + + public static List FindQuestList(Type questerType) + { + return QuestGivers.TryGetValue(questerType, out List result) ? result : EmptyList; + } + + public class ViewQuestsCommand : BaseCommand + { + public ViewQuestsCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Simple; + Commands = new[] { "ViewQuests" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "ViewQuests"; + Description = "Displays a targeted mobile's quest overview."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + Mobile from = e.Mobile; + + if (!(obj is PlayerMobile pm)) + { + LogFailure("That is not a player."); + return; + } + + CommandLogging.WriteLine(from, "{0} {1} viewing quest overview of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(pm)); + from.SendGump(new QuestLogGump(pm, false)); + } + } + + private class ViewContextCommand : BaseCommand + { + public ViewContextCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.Simple; + Commands = new[] { "ViewMLContext" }; + ObjectTypes = ObjectTypes.Mobiles; + Usage = "ViewMLContext"; + Description = "Opens the ML quest context for a targeted mobile."; + } + + public override void Execute(CommandEventArgs e, object obj) + { + if (!(obj is PlayerMobile pm)) + LogFailure("They have no ML quest context."); + else + e.Mobile.SendGump(new PropertiesGump(e.Mobile, GetOrCreateContext(pm))); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Mobiles/BoonCollector.cs b/Scripts/Engines/MLQuests/Mobiles/BoonCollector.cs index 5ba01f591..fb343af6b 100644 --- a/Scripts/Engines/MLQuests/Mobiles/BoonCollector.cs +++ b/Scripts/Engines/MLQuests/Mobiles/BoonCollector.cs @@ -1,428 +1,426 @@ using System; using System.Collections.Generic; -using Server.Mobiles; -using Server.Items; -using Server.Network; -using Server.Engines.MLQuests.Gumps; using Server.Engines.MLQuests.Definitions; +using Server.Engines.MLQuests.Gumps; +using Server.Items; +using Server.Mobiles; +using Server.Network; namespace Server.Engines.MLQuests.Mobiles { - public abstract class DoneQuestCollector : BaseCreature, IRaceChanger - { - public override bool IsInvulnerable => true; - - public abstract TextDefinition[] Offer { get; } - public abstract TextDefinition[] Incomplete { get; } - public abstract TextDefinition[] Complete { get; } - public abstract Type[] Needed { get; } - - private InternalTimer m_Timer; - - public DoneQuestCollector() - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - TryTalkTo( from, true ); - } - - public override void OnDoubleClickDead( Mobile from ) - { - TryTalkTo( from, true ); - } - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m.Player && InRange( m, 6 ) && !InRange( oldLocation, 6 ) ) - TryTalkTo( m, false ); - - base.OnMovement( m, oldLocation ); - } - - public void TryTalkTo( Mobile from, bool fromClick ) - { - if ( !from.Hidden && !from.HasGump( typeOfRaceChangeConfirmGump ) && !RaceChangeConfirmGump.IsPending( from.NetState ) && CanTalkTo( from ) ) - TalkTo( from as PlayerMobile ); - else if ( fromClick ) - DenyTalk( from ); - } - - public virtual bool CanTalkTo( Mobile from ) - { - return true; - } - - public virtual void DenyTalk( Mobile from ) - { - } - - private static Type typeOfRaceChangeConfirmGump = typeof( RaceChangeConfirmGump ); - - public void TalkTo( PlayerMobile pm ) - { - if ( pm == null || ( m_Timer != null && m_Timer.Running ) ) - return; - - int completed = CompletedCount( pm ); - - if ( completed == Needed.Length ) - { - m_Timer = new InternalTimer( this, pm, Complete, true ); - } - else if ( completed == 0 ) - { - m_Timer = new InternalTimer( this, pm, Offer, false ); - } - else - { - List conversation = new List(); - conversation.AddRange( Incomplete ); - - MLQuestContext context = MLQuestSystem.GetContext( pm ); - - if ( context != null ) - { - foreach ( Type type in Needed ) - { - MLQuest quest = MLQuestSystem.FindQuest( type ); - - if ( quest == null || context.HasDoneQuest( quest ) ) - continue; - - conversation.Add( quest.Title ); - } - } - - m_Timer = new InternalTimer( this, pm, conversation, false ); - } - - m_Timer.Start(); - } - - private int CompletedCount( PlayerMobile pm ) - { - MLQuestContext context = MLQuestSystem.GetContext( pm ); - - if ( context == null ) - return 0; - - int result = 0; - - foreach ( Type type in Needed ) - { - MLQuest quest = MLQuestSystem.FindQuest( type ); - - if ( quest == null || context.HasDoneQuest( quest ) ) - ++result; - } - - return result; - } - - public bool CheckComplete( PlayerMobile pm ) - { - if ( CompletedCount( pm ) == Needed.Length ) - return true; - - pm.SendLocalizedMessage( 1073644 ); // You must complete all the tasks before proceeding... - return false; - } - - public void ConsumeNeeded( PlayerMobile pm ) - { - MLQuestContext context = MLQuestSystem.GetContext( pm ); - - if ( context != null ) - { - foreach ( Type type in Needed ) - { - MLQuest quest = MLQuestSystem.FindQuest( type ); - - if ( quest != null ) - context.RemoveDoneQuest( quest ); - } - } - } - - public void OnCancel( PlayerMobile pm ) - { - pm.SendLocalizedMessage( 1073645 ); // You may try this again later... - } - - public virtual void OnComplete( PlayerMobile pm ) - { - } - - public DoneQuestCollector( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - private class InternalTimer : Timer - { - private DoneQuestCollector m_Owner; - private PlayerMobile m_Target; - private IList m_Conversation; - private bool m_IsComplete; - private int m_Index; - - private static TimeSpan GetDelay() - { - return TimeSpan.FromSeconds( Utility.RandomBool() ? 3 : 4 ); - } - - public InternalTimer( DoneQuestCollector owner, PlayerMobile target, IList conversation, bool isComplete ) - : base( TimeSpan.Zero, GetDelay() ) - { - m_Owner = owner; - m_Target = target; - m_Conversation = conversation; - m_IsComplete = isComplete; - m_Index = 0; - } - - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } - - if ( m_Index >= m_Conversation.Count ) - { - if ( m_IsComplete ) - m_Owner.OnComplete( m_Target ); - - Stop(); - } - else - { - if ( m_Index == 0 ) - { - if ( m_Target.ShowFameTitle && m_Target.Fame >= 10000 ) - m_Owner.Say( true, $"{(m_Target.Female ? "Lady" : "Lord")} {m_Target.Name}"); - else - m_Owner.Say( true, m_Target.Name ); - } - - TextDefinition.PublicOverheadMessage( m_Owner, MessageType.Regular, 0x3B2, m_Conversation[m_Index++] ); - Interval = GetDelay(); - } - } - } - } - - public class Darius : DoneQuestCollector - { - private static readonly TextDefinition[] m_Offer = - { - 1073998, // Blessings of Sosaria to you and merry met, friend. - 1073999, // I am glad for your company and wonder if you seek the heritage of your people? I sense within you an elven bloodline -- the purity of which was lost when our brothers and sisters were exiled here in the Rupture. - 1074000, // If it is your desire to reclaim your place amongst the people, you must demonstrate that you understand and embrace the responsibilities expected of you as an elf. - 1074001, // The most basic lessons of our Sosaria are taught by her humblest children. Seek Maul, the great bear, who understands instictively the seasons. - 1074398, // Seek Strongroot, the great treefellow, whose very roots reach to the heart of the world. Seek Enigma, whose wisdom can only be conveyed in riddles and rhymes. Seek Bravehorn, the great hart, who exemplifies the fierce dedication of a protector of his people. - 1074399, // Seek the Huntsman, the centuar tasked with maintaining the balance. And lastly seek Arielle, the pixie, who has perhaps the most important lesson -- not to take yourself too seriously. - 1074400 // Or do none of these things. You must choose your own path in the world, and what use you'll make of your existence. - }; - - private static readonly TextDefinition[] m_Incomplete = - { - 1074002, // You have begun to walk the path of reclaiming your heritage, but you have not learned all the lessons before you. - 1074003 // You yet must perform these services: - }; - - private static readonly TextDefinition[] m_Complete = - { - 1074004, // You have carved a path in history, sought to understand the way from our sage companions. - 1074005, // And now you have returned full circle to the place of your origin within the arms of Mother Sosaria. There is but one thing left to do if you truly wish to embrace your elven heritage. - 1074006, // To be born once more an elf, you must strip of all worldly possessions. Nothing of man or beast much touch your skin. - 1074007 // Then you may step forth into history. - }; - - private static readonly Type[] m_Needed = - { - typeof( Seasons ), - typeof( CaretakerOfTheLand ), - typeof( WisdomOfTheSphynx ), - typeof( DefendingTheHerd ), - typeof( TheBalanceOfNature ), - typeof( TheJoysOfLife ) - }; - - public override TextDefinition[] Offer => m_Offer; - public override TextDefinition[] Incomplete => m_Incomplete; - public override TextDefinition[] Complete => m_Complete; - public override Type[] Needed => m_Needed; - - public override string DefaultName => "Darius"; - - [Constructible] - public Darius() - { - Title = "the wise"; - Race = Race.Elf; - Hue = Race.RandomSkinHue(); - SpeechHue = Utility.RandomDyedHue(); - - AddItem( new WildStaff() ); - AddItem( new Sandals( 0x1BB ) ); - AddItem( new GemmedCirclet() ); - AddItem( new Tunic( Utility.RandomBrightHue() ) ); - - Utility.AssignRandomHair( this ); - - SetStr( 40, 50 ); - SetDex( 60, 70 ); - SetInt( 90, 100 ); // Verified int - } - - public override bool CanTalkTo( Mobile from ) - { - return ( from.Race == Race.Human ); - } - - public override void DenyTalk( Mobile from ) - { - from.SendLocalizedMessage( 1074017 ); // He's too busy right now, so he ignores you. - } - - public override void OnComplete( PlayerMobile from ) - { - from.SendGump( new RaceChangeConfirmGump( this, from, Race.Elf ) ); - } - - public Darius( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Nedrick : DoneQuestCollector - { - private static readonly TextDefinition[] m_Offer = - { - 1074403, // Greetings, traveler and welcome. - 1074404, // Perhaps you have heard of the service I offer? Perhaps you wish to avail yourself of the opportunity I lay before you. - 1074405, // Elves and humans; we lived together once in peace. Mighty relics that attest to our friendship remain, of course. Yet, memories faded when the Gem was shattered and the world torn asunder. Alone in The Heartwood, our elven brothers and sisters wondered what terrible evil had befallen Sosaria. - 1074406, // Violent change marked the sundering of our ties. We are different -- elves and humans. And yet we are much alike. I can give an elf the chance to walk as a human upon Sosaria. I can undertake the transformation. - 1074407, // But you must prove yourself to me. Humans possess a strength of character and back. Humans are quick-witted and able to pick up a smattering of nearly any talent. Humans are tough both mentally and physically. And of course, humans defend their own -- sometimes with their own lives. - 1074408, // Seek Sledge the Versatile and learn about human ingenuity and creativity. Seek Patricus and demonstrate your integrity and strength. - 1074409, // Seek out a human in need and prove your worth as a defender of humanity. Seek Belulah in Nu'Jelm and heartily challenge the elements in a display of toughness to rival any human. - 1074411 // Or turn away and embrace your heritage. It matters not to me. - }; - - private static readonly TextDefinition[] m_Incomplete = - { - 1074412, // You have made a good start but have more yet to do. - 1074413 // You must yet perform these deeds: - }; - - private static readonly TextDefinition[] m_Complete = - { - 1074410, // You have proven yourself capable and commited and so I will grant you the transformation you seek. - 1074531, // The first time you were born, you entered the world bare of all possessions and concerns. So too as you transform to your new life as a human, you must remove all worldly goods from the touch of your flesh. - 1074532 // I call upon all nearby to witness your rebirth! - }; - - private static readonly Type[] m_Needed = - { - typeof( Ingenuity ), - typeof( HeaveHo ), - typeof( HumanInNeed ), - typeof( AllSeasonAdventurer ) - }; - - public override TextDefinition[] Offer => m_Offer; - public override TextDefinition[] Incomplete => m_Incomplete; - public override TextDefinition[] Complete => m_Complete; - public override Type[] Needed => m_Needed; - - public override string DefaultName => "Nedrick"; - - [Constructible] - public Nedrick() - { - Title = "the iron worker"; - Race = Race.Human; - Hue = Race.RandomSkinHue(); - SpeechHue = Utility.RandomDyedHue(); - - AddItem( new Boots() ); - AddItem( new LongPants( Utility.RandomNondyedHue() ) ); - AddItem( new FancyShirt( Utility.RandomNondyedHue() ) ); - - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); - - SetStr( 70, 80 ); - SetDex( 50, 60 ); - SetInt( 60, 70 ); // Verified int - } - - public override bool CanTalkTo( Mobile from ) - { - return ( from.Race == Race.Elf ); - } - - public override void DenyTalk( Mobile from ) - { - from.SendLocalizedMessage( 1074017 ); // He's too busy right now, so he ignores you. - } - - public override void OnComplete( PlayerMobile from ) - { - from.SendGump( new RaceChangeConfirmGump( this, from, Race.Human ) ); - } - - public Nedrick( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public abstract class DoneQuestCollector : BaseCreature, IRaceChanger + { + private static Type typeOfRaceChangeConfirmGump = typeof(RaceChangeConfirmGump); + + private InternalTimer m_Timer; + + public DoneQuestCollector() + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + } + + public DoneQuestCollector(Serial serial) + : base(serial) + { + } + + public override bool IsInvulnerable => true; + + public abstract TextDefinition[] Offer{ get; } + public abstract TextDefinition[] Incomplete{ get; } + public abstract TextDefinition[] Complete{ get; } + public abstract Type[] Needed{ get; } + + public bool CheckComplete(PlayerMobile pm) + { + if (CompletedCount(pm) == Needed.Length) + return true; + + pm.SendLocalizedMessage(1073644); // You must complete all the tasks before proceeding... + return false; + } + + public void ConsumeNeeded(PlayerMobile pm) + { + MLQuestContext context = MLQuestSystem.GetContext(pm); + + if (context != null) + foreach (Type type in Needed) + { + MLQuest quest = MLQuestSystem.FindQuest(type); + + if (quest != null) + context.RemoveDoneQuest(quest); + } + } + + public void OnCancel(PlayerMobile pm) + { + pm.SendLocalizedMessage(1073645); // You may try this again later... + } + + public override void OnDoubleClick(Mobile from) + { + TryTalkTo(from, true); + } + + public override void OnDoubleClickDead(Mobile from) + { + TryTalkTo(from, true); + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m.Player && InRange(m, 6) && !InRange(oldLocation, 6)) + TryTalkTo(m, false); + + base.OnMovement(m, oldLocation); + } + + public void TryTalkTo(Mobile from, bool fromClick) + { + if (!from.Hidden && !from.HasGump(typeOfRaceChangeConfirmGump) && + !RaceChangeConfirmGump.IsPending(from.NetState) && CanTalkTo(from)) + TalkTo(from as PlayerMobile); + else if (fromClick) + DenyTalk(from); + } + + public virtual bool CanTalkTo(Mobile from) + { + return true; + } + + public virtual void DenyTalk(Mobile from) + { + } + + public void TalkTo(PlayerMobile pm) + { + if (pm == null || m_Timer != null && m_Timer.Running) + return; + + int completed = CompletedCount(pm); + + if (completed == Needed.Length) + { + m_Timer = new InternalTimer(this, pm, Complete, true); + } + else if (completed == 0) + { + m_Timer = new InternalTimer(this, pm, Offer, false); + } + else + { + List conversation = new List(); + conversation.AddRange(Incomplete); + + MLQuestContext context = MLQuestSystem.GetContext(pm); + + if (context != null) + foreach (Type type in Needed) + { + MLQuest quest = MLQuestSystem.FindQuest(type); + + if (quest == null || context.HasDoneQuest(quest)) + continue; + + conversation.Add(quest.Title); + } + + m_Timer = new InternalTimer(this, pm, conversation, false); + } + + m_Timer.Start(); + } + + private int CompletedCount(PlayerMobile pm) + { + MLQuestContext context = MLQuestSystem.GetContext(pm); + + if (context == null) + return 0; + + int result = 0; + + foreach (Type type in Needed) + { + MLQuest quest = MLQuestSystem.FindQuest(type); + + if (quest == null || context.HasDoneQuest(quest)) + ++result; + } + + return result; + } + + public virtual void OnComplete(PlayerMobile pm) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + private class InternalTimer : Timer + { + private IList m_Conversation; + private int m_Index; + private bool m_IsComplete; + private DoneQuestCollector m_Owner; + private PlayerMobile m_Target; + + public InternalTimer(DoneQuestCollector owner, PlayerMobile target, IList conversation, + bool isComplete) + : base(TimeSpan.Zero, GetDelay()) + { + m_Owner = owner; + m_Target = target; + m_Conversation = conversation; + m_IsComplete = isComplete; + m_Index = 0; + } + + private static TimeSpan GetDelay() + { + return TimeSpan.FromSeconds(Utility.RandomBool() ? 3 : 4); + } + + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } + + if (m_Index >= m_Conversation.Count) + { + if (m_IsComplete) + m_Owner.OnComplete(m_Target); + + Stop(); + } + else + { + if (m_Index == 0) + { + if (m_Target.ShowFameTitle && m_Target.Fame >= 10000) + m_Owner.Say(true, $"{(m_Target.Female ? "Lady" : "Lord")} {m_Target.Name}"); + else + m_Owner.Say(true, m_Target.Name); + } + + TextDefinition.PublicOverheadMessage(m_Owner, MessageType.Regular, 0x3B2, m_Conversation[m_Index++]); + Interval = GetDelay(); + } + } + } + } + + public class Darius : DoneQuestCollector + { + private static readonly TextDefinition[] m_Offer = + { + 1073998, // Blessings of Sosaria to you and merry met, friend. + 1073999, // I am glad for your company and wonder if you seek the heritage of your people? I sense within you an elven bloodline -- the purity of which was lost when our brothers and sisters were exiled here in the Rupture. + 1074000, // If it is your desire to reclaim your place amongst the people, you must demonstrate that you understand and embrace the responsibilities expected of you as an elf. + 1074001, // The most basic lessons of our Sosaria are taught by her humblest children. Seek Maul, the great bear, who understands instictively the seasons. + 1074398, // Seek Strongroot, the great treefellow, whose very roots reach to the heart of the world. Seek Enigma, whose wisdom can only be conveyed in riddles and rhymes. Seek Bravehorn, the great hart, who exemplifies the fierce dedication of a protector of his people. + 1074399, // Seek the Huntsman, the centuar tasked with maintaining the balance. And lastly seek Arielle, the pixie, who has perhaps the most important lesson -- not to take yourself too seriously. + 1074400 // Or do none of these things. You must choose your own path in the world, and what use you'll make of your existence. + }; + + private static readonly TextDefinition[] m_Incomplete = + { + 1074002, // You have begun to walk the path of reclaiming your heritage, but you have not learned all the lessons before you. + 1074003 // You yet must perform these services: + }; + + private static readonly TextDefinition[] m_Complete = + { + 1074004, // You have carved a path in history, sought to understand the way from our sage companions. + 1074005, // And now you have returned full circle to the place of your origin within the arms of Mother Sosaria. There is but one thing left to do if you truly wish to embrace your elven heritage. + 1074006, // To be born once more an elf, you must strip of all worldly possessions. Nothing of man or beast much touch your skin. + 1074007 // Then you may step forth into history. + }; + + private static readonly Type[] m_Needed = + { + typeof(Seasons), + typeof(CaretakerOfTheLand), + typeof(WisdomOfTheSphynx), + typeof(DefendingTheHerd), + typeof(TheBalanceOfNature), + typeof(TheJoysOfLife) + }; + + [Constructible] + public Darius() + { + Title = "the wise"; + Race = Race.Elf; + Hue = Race.RandomSkinHue(); + SpeechHue = Utility.RandomDyedHue(); + + AddItem(new WildStaff()); + AddItem(new Sandals(0x1BB)); + AddItem(new GemmedCirclet()); + AddItem(new Tunic(Utility.RandomBrightHue())); + + Utility.AssignRandomHair(this); + + SetStr(40, 50); + SetDex(60, 70); + SetInt(90, 100); // Verified int + } + + public Darius(Serial serial) + : base(serial) + { + } + + public override TextDefinition[] Offer => m_Offer; + public override TextDefinition[] Incomplete => m_Incomplete; + public override TextDefinition[] Complete => m_Complete; + public override Type[] Needed => m_Needed; + + public override string DefaultName => "Darius"; + + public override bool CanTalkTo(Mobile from) + { + return from.Race == Race.Human; + } + + public override void DenyTalk(Mobile from) + { + from.SendLocalizedMessage(1074017); // He's too busy right now, so he ignores you. + } + + public override void OnComplete(PlayerMobile from) + { + from.SendGump(new RaceChangeConfirmGump(this, from, Race.Elf)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Nedrick : DoneQuestCollector + { + private static readonly TextDefinition[] m_Offer = + { + 1074403, // Greetings, traveler and welcome. + 1074404, // Perhaps you have heard of the service I offer? Perhaps you wish to avail yourself of the opportunity I lay before you. + 1074405, // Elves and humans; we lived together once in peace. Mighty relics that attest to our friendship remain, of course. Yet, memories faded when the Gem was shattered and the world torn asunder. Alone in The Heartwood, our elven brothers and sisters wondered what terrible evil had befallen Sosaria. + 1074406, // Violent change marked the sundering of our ties. We are different -- elves and humans. And yet we are much alike. I can give an elf the chance to walk as a human upon Sosaria. I can undertake the transformation. + 1074407, // But you must prove yourself to me. Humans possess a strength of character and back. Humans are quick-witted and able to pick up a smattering of nearly any talent. Humans are tough both mentally and physically. And of course, humans defend their own -- sometimes with their own lives. + 1074408, // Seek Sledge the Versatile and learn about human ingenuity and creativity. Seek Patricus and demonstrate your integrity and strength. + 1074409, // Seek out a human in need and prove your worth as a defender of humanity. Seek Belulah in Nu'Jelm and heartily challenge the elements in a display of toughness to rival any human. + 1074411 // Or turn away and embrace your heritage. It matters not to me. + }; + + private static readonly TextDefinition[] m_Incomplete = + { + 1074412, // You have made a good start but have more yet to do. + 1074413 // You must yet perform these deeds: + }; + + private static readonly TextDefinition[] m_Complete = + { + 1074410, // You have proven yourself capable and commited and so I will grant you the transformation you seek. + 1074531, // The first time you were born, you entered the world bare of all possessions and concerns. So too as you transform to your new life as a human, you must remove all worldly goods from the touch of your flesh. + 1074532 // I call upon all nearby to witness your rebirth! + }; + + private static readonly Type[] m_Needed = + { + typeof(Ingenuity), + typeof(HeaveHo), + typeof(HumanInNeed), + typeof(AllSeasonAdventurer) + }; + + [Constructible] + public Nedrick() + { + Title = "the iron worker"; + Race = Race.Human; + Hue = Race.RandomSkinHue(); + SpeechHue = Utility.RandomDyedHue(); + + AddItem(new Boots()); + AddItem(new LongPants(Utility.RandomNondyedHue())); + AddItem(new FancyShirt(Utility.RandomNondyedHue())); + + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); + + SetStr(70, 80); + SetDex(50, 60); + SetInt(60, 70); // Verified int + } + + public Nedrick(Serial serial) + : base(serial) + { + } + + public override TextDefinition[] Offer => m_Offer; + public override TextDefinition[] Incomplete => m_Incomplete; + public override TextDefinition[] Complete => m_Complete; + public override Type[] Needed => m_Needed; + + public override string DefaultName => "Nedrick"; + + public override bool CanTalkTo(Mobile from) + { + return from.Race == Race.Elf; + } + + public override void DenyTalk(Mobile from) + { + from.SendLocalizedMessage(1074017); // He's too busy right now, so he ignores you. + } + + public override void OnComplete(PlayerMobile from) + { + from.SendGump(new RaceChangeConfirmGump(this, from, Race.Human)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Mobiles/SirHelper.cs b/Scripts/Engines/MLQuests/Mobiles/SirHelper.cs index 04cacd67c..e38f08cfc 100644 --- a/Scripts/Engines/MLQuests/Mobiles/SirHelper.cs +++ b/Scripts/Engines/MLQuests/Mobiles/SirHelper.cs @@ -7,132 +7,135 @@ using Server.Network; namespace Server.Engines.MLQuests.Mobiles { - public class SirHelper : Mage - { - private static readonly Gump m_Gump = new InfoNPCGump( 1078029, 1078028 ); - private static readonly TimeSpan m_ShoutDelay = TimeSpan.FromSeconds( 20 ); - private static readonly TimeSpan m_ShoutCooldown = TimeSpan.FromDays( 1 ); // TODO: Verify, could be a lot longer... or until a restart even + public class SirHelper : Mage + { + private static readonly Gump m_Gump = new InfoNPCGump(1078029, 1078028); + private static readonly TimeSpan m_ShoutDelay = TimeSpan.FromSeconds(20); - private DateTime m_NextShout; + private static readonly TimeSpan + m_ShoutCooldown = TimeSpan.FromDays(1); // TODO: Verify, could be a lot longer... or until a restart even - public override string DefaultName => "Sir Helper"; - public override bool IsActiveVendor => false; + private DateTime m_NextShout; - [Constructible] - public SirHelper() - { - Title = "the Profession Guide"; // TODO: Don't display in paperdoll + [Constructible] + public SirHelper() + { + Title = "the Profession Guide"; // TODO: Don't display in paperdoll - Hue = 0x83EA; + Hue = 0x83EA; - Direction = Direction.South; - Frozen = true; - } + Direction = Direction.South; + Frozen = true; + } - public override void InitSBInfo() - { - } + public SirHelper(Serial serial) + : base(serial) + { + } - public override bool GetGender() - { - return false; // male - } + public override string DefaultName => "Sir Helper"; + public override bool IsActiveVendor => false; - public override void CheckMorph() - { - } + public override void InitSBInfo() + { + } - public override void InitOutfit() - { - HairItemID = 0x203C; - FacialHairItemID = 0x204D; - HairHue = FacialHairHue = 0x8A7; + public override bool GetGender() + { + return false; // male + } - AddItem( new Sandals() ); + public override void CheckMorph() + { + } - Item item; + public override void InitOutfit() + { + HairItemID = 0x203C; + FacialHairItemID = 0x204D; + HairHue = FacialHairHue = 0x8A7; - item = new Cloak(); - item.ItemID = 0x26AD; - item.Hue = 0x455; - AddItem( item ); + AddItem(new Sandals()); - item = new Robe(); - item.ItemID = 0x26AE; - item.Hue = 0x4AB; - AddItem( item ); + Item item; - item = new Backpack(); - item.Movable = false; - AddItem( item ); - } + item = new Cloak(); + item.ItemID = 0x26AD; + item.Hue = 0x455; + AddItem(item); - public override void OnDoubleClick( Mobile from ) - { - if ( from.CanBeginAction( this ) ) - { - from.BeginAction( this ); - Timer.DelayCall( m_ShoutCooldown, EndLock, from ); - } + item = new Robe(); + item.ItemID = 0x26AE; + item.Hue = 0x4AB; + AddItem(item); - MLQuestSystem.TurnToFace( this, from ); - from.SendGump( m_Gump ); + item = new Backpack(); + item.Movable = false; + AddItem(item); + } - // Paperdoll doesn't open - //base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (from.CanBeginAction(this)) + { + from.BeginAction(this); + Timer.DelayCall(m_ShoutCooldown, EndLock, from); + } - public override void OnThink() - { - base.OnThink(); + MLQuestSystem.TurnToFace(this, from); + from.SendGump(m_Gump); - if ( m_NextShout <= DateTime.UtcNow ) - { - Packet shoutPacket = null; + // Paperdoll doesn't open + //base.OnDoubleClick( from ); + } - foreach ( NetState state in GetClientsInRange( 12 ) ) - { - Mobile m = state.Mobile; + public override void OnThink() + { + base.OnThink(); - if ( m.CanSee( this ) && m.InLOS( this ) && m.CanBeginAction( this ) ) - { - if ( shoutPacket == null ) - shoutPacket = Packet.Acquire( new MessageLocalized( Serial, Body, MessageType.Regular, 946, 3, 1078099, Name, "" ) ); // Double Click On Me For Help! + if (m_NextShout <= DateTime.UtcNow) + { + Packet shoutPacket = null; - state.Send( shoutPacket ); - } - } + foreach (NetState state in GetClientsInRange(12)) + { + Mobile m = state.Mobile; - Packet.Release( shoutPacket ); + if (m.CanSee(this) && m.InLOS(this) && m.CanBeginAction(this)) + { + if (shoutPacket == null) + shoutPacket = Packet.Acquire(new MessageLocalized(Serial, Body, MessageType.Regular, 946, 3, + 1078099, Name, "")); // Double Click On Me For Help! - m_NextShout = DateTime.UtcNow + m_ShoutDelay; - } - } + state.Send(shoutPacket); + } + } - private void EndLock( Mobile m ) - { - m.EndAction( this ); - } + Packet.Release(shoutPacket); - public SirHelper( Serial serial ) - : base( serial ) - { - } + m_NextShout = DateTime.UtcNow + m_ShoutDelay; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private void EndLock(Mobile m) + { + m.EndAction(this); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Frozen = true; - } - } -} + int version = reader.ReadInt(); + + Frozen = true; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Objectives/BaseObjective.cs b/Scripts/Engines/MLQuests/Objectives/BaseObjective.cs index bb3554803..f229a9a71 100644 --- a/Scripts/Engines/MLQuests/Objectives/BaseObjective.cs +++ b/Scripts/Engines/MLQuests/Objectives/BaseObjective.cs @@ -1,193 +1,189 @@ using System; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; namespace Server.Engines.MLQuests.Objectives { - public abstract class BaseObjective - { - public virtual bool IsTimed => false; - public virtual TimeSpan Duration => TimeSpan.Zero; + public abstract class BaseObjective + { + public virtual bool IsTimed => false; + public virtual TimeSpan Duration => TimeSpan.Zero; - public BaseObjective() - { - } + public virtual bool CanOffer(IQuestGiver quester, PlayerMobile pm, bool message) + { + return true; + } - public virtual bool CanOffer( IQuestGiver quester, PlayerMobile pm, bool message ) - { - return true; - } + public abstract void WriteToGump(Gump g, ref int y); - public abstract void WriteToGump( Gump g, ref int y ); + public virtual BaseObjectiveInstance CreateInstance(MLQuestInstance instance) + { + return null; + } + } - public virtual BaseObjectiveInstance CreateInstance( MLQuestInstance instance ) - { - return null; - } - } + public abstract class BaseObjectiveInstance + { + public enum DataType : byte + { + None, + EscortObjective, + KillObjective, + DeliverObjective + } - public abstract class BaseObjectiveInstance - { - public MLQuestInstance Instance { get; } + public BaseObjectiveInstance(MLQuestInstance instance, BaseObjective obj) + { + Instance = instance; - public bool IsTimed => ( EndTime != DateTime.MinValue ); + if (obj.IsTimed) + EndTime = DateTime.UtcNow + obj.Duration; + } - public DateTime EndTime { get; set; } + public MLQuestInstance Instance{ get; } - public bool Expired { get; set; } + public bool IsTimed => EndTime != DateTime.MinValue; - public BaseObjectiveInstance( MLQuestInstance instance, BaseObjective obj ) - { - Instance = instance; + public DateTime EndTime{ get; set; } - if ( obj.IsTimed ) - EndTime = DateTime.UtcNow + obj.Duration; - } + public bool Expired{ get; set; } - public virtual void WriteToGump( Gump g, ref int y ) - { - if ( IsTimed ) - WriteTimeRemaining( g, ref y, ( EndTime > DateTime.UtcNow ) ? ( EndTime - DateTime.UtcNow ) : TimeSpan.Zero ); - } + public virtual DataType ExtraDataType => DataType.None; - public static void WriteTimeRemaining( Gump g, ref int y, TimeSpan timeRemaining ) - { - g.AddHtmlLocalized( 103, y, 120, 16, 1062379, 0x15F90, false, false ); // Est. time remaining: - g.AddLabel( 223, y, 0x481, timeRemaining.TotalSeconds.ToString( "F0" ) ); - y += 16; - } + public virtual void WriteToGump(Gump g, ref int y) + { + if (IsTimed) + WriteTimeRemaining(g, ref y, EndTime > DateTime.UtcNow ? EndTime - DateTime.UtcNow : TimeSpan.Zero); + } - public virtual bool AllowsQuestItem( Item item, Type type ) - { - return false; - } + public static void WriteTimeRemaining(Gump g, ref int y, TimeSpan timeRemaining) + { + g.AddHtmlLocalized(103, y, 120, 16, 1062379, 0x15F90, false, false); // Est. time remaining: + g.AddLabel(223, y, 0x481, timeRemaining.TotalSeconds.ToString("F0")); + y += 16; + } - public virtual bool IsCompleted() - { - return false; - } + public virtual bool AllowsQuestItem(Item item, Type type) + { + return false; + } - public virtual void CheckComplete() - { - if ( IsCompleted() ) - { - Instance.Player.PlaySound( 0x5B6 ); // public sound - Instance.CheckComplete(); - } - } + public virtual bool IsCompleted() + { + return false; + } - public virtual void OnQuestAccepted() - { - } + public virtual void CheckComplete() + { + if (IsCompleted()) + { + Instance.Player.PlaySound(0x5B6); // public sound + Instance.CheckComplete(); + } + } - public virtual void OnQuestCancelled() - { - } + public virtual void OnQuestAccepted() + { + } - public virtual void OnQuestCompleted() - { - } + public virtual void OnQuestCancelled() + { + } - public virtual bool OnBeforeClaimReward() - { - return true; - } + public virtual void OnQuestCompleted() + { + } - public virtual void OnClaimReward() - { - } + public virtual bool OnBeforeClaimReward() + { + return true; + } - public virtual void OnAfterClaimReward() - { - } + public virtual void OnClaimReward() + { + } - public virtual void OnRewardClaimed() - { - } + public virtual void OnAfterClaimReward() + { + } - public virtual void OnQuesterDeleted() - { - } + public virtual void OnRewardClaimed() + { + } - public virtual void OnPlayerDeath() - { - } + public virtual void OnQuesterDeleted() + { + } - public virtual void OnExpire() - { - } + public virtual void OnPlayerDeath() + { + } - public enum DataType : byte - { - None, - EscortObjective, - KillObjective, - DeliverObjective - } + public virtual void OnExpire() + { + } - public virtual DataType ExtraDataType => DataType.None; + public virtual void Serialize(GenericWriter writer) + { + // Version info is written in MLQuestPersistence.Serialize - public virtual void Serialize( GenericWriter writer ) - { - // Version info is written in MLQuestPersistence.Serialize + if (IsTimed) + { + writer.Write(true); + writer.WriteDeltaTime(EndTime); + } + else + { + writer.Write(false); + } - if ( IsTimed ) - { - writer.Write( true ); - writer.WriteDeltaTime( EndTime ); - } - else - { - writer.Write( false ); - } + // For type checks on deserialization + // (This way quest objectives can be changed without breaking serialization) + writer.Write((byte)ExtraDataType); + } - // For type checks on deserialization - // (This way quest objectives can be changed without breaking serialization) - writer.Write( (byte)ExtraDataType ); - } + public static void Deserialize(GenericReader reader, int version, BaseObjectiveInstance objInstance) + { + if (reader.ReadBool()) + { + DateTime endTime = reader.ReadDeltaTime(); - public static void Deserialize( GenericReader reader, int version, BaseObjectiveInstance objInstance ) - { - if ( reader.ReadBool() ) - { - DateTime endTime = reader.ReadDeltaTime(); + if (objInstance != null) + objInstance.EndTime = endTime; + } - if ( objInstance != null ) - objInstance.EndTime = endTime; - } + DataType extraDataType = (DataType)reader.ReadByte(); - DataType extraDataType = (DataType)reader.ReadByte(); + switch (extraDataType) + { + case DataType.EscortObjective: + { + bool completed = reader.ReadBool(); - switch ( extraDataType ) - { - case DataType.EscortObjective: - { - bool completed = reader.ReadBool(); + if (objInstance is EscortObjectiveInstance instance) + instance.HasCompleted = completed; - if ( objInstance is EscortObjectiveInstance instance ) - instance.HasCompleted = completed; + break; + } + case DataType.KillObjective: + { + int slain = reader.ReadInt(); - break; - } - case DataType.KillObjective: - { - int slain = reader.ReadInt(); + if (objInstance is KillObjectiveInstance instance) + instance.Slain = slain; - if ( objInstance is KillObjectiveInstance instance ) - instance.Slain = slain; + break; + } + case DataType.DeliverObjective: + { + bool completed = reader.ReadBool(); - break; - } - case DataType.DeliverObjective: - { - bool completed = reader.ReadBool(); + if (objInstance is DeliverObjectiveInstance instance) + instance.HasCompleted = completed; - if ( objInstance is DeliverObjectiveInstance instance ) - instance.HasCompleted = completed; - - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Objectives/CollectObjective.cs b/Scripts/Engines/MLQuests/Objectives/CollectObjective.cs index a9f68ac96..bc87f5ba6 100644 --- a/Scripts/Engines/MLQuests/Objectives/CollectObjective.cs +++ b/Scripts/Engines/MLQuests/Objectives/CollectObjective.cs @@ -1,229 +1,224 @@ using System; -using Server.Mobiles; using Server.Gumps; using Server.Items; +using Server.Mobiles; namespace Server.Engines.MLQuests.Objectives { - public class CollectObjective : BaseObjective - { - public int DesiredAmount { get; set; } + public class CollectObjective : BaseObjective + { + public CollectObjective() + : this(0, null, null) + { + } - public Type AcceptedType { get; set; } + public CollectObjective(int amount, Type type, TextDefinition name) + { + DesiredAmount = amount; + AcceptedType = type; + Name = name; - public TextDefinition Name { get; set; } + if (MLQuestSystem.Debug && ShowDetailed && name.Number > 0) + { + int itemid = LabelToItemID(name.Number); - public virtual bool ShowDetailed => true; + if (itemid <= 0 || itemid > 0x4000) + Console.WriteLine("Warning: cliloc {0} is likely giving the wrong item ID", name.Number); + } + } - public CollectObjective() - : this( 0, null, null ) - { - } + public int DesiredAmount{ get; set; } - public CollectObjective( int amount, Type type, TextDefinition name ) - { - DesiredAmount = amount; - AcceptedType = type; - Name = name; + public Type AcceptedType{ get; set; } - if ( MLQuestSystem.Debug && ShowDetailed && name.Number > 0 ) - { - int itemid = LabelToItemID( name.Number ); + public TextDefinition Name{ get; set; } - if ( itemid <= 0 || itemid > 0x4000 ) - Console.WriteLine( "Warning: cliloc {0} is likely giving the wrong item ID", name.Number ); - } - } + public virtual bool ShowDetailed => true; - public bool CheckType( Type type ) - { - return ( AcceptedType != null && AcceptedType.IsAssignableFrom( type ) ); - } + public bool CheckType(Type type) + { + return AcceptedType != null && AcceptedType.IsAssignableFrom(type); + } - public virtual bool CheckItem( Item item ) - { - return true; - } + public virtual bool CheckItem(Item item) + { + return true; + } - public static int LabelToItemID( int label ) - { - if ( label < 1078872 ) - return ( label - 1020000 ); - return ( label - 1078872 ); - } + public static int LabelToItemID(int label) + { + if (label < 1078872) + return label - 1020000; + return label - 1078872; + } - public override void WriteToGump( Gump g, ref int y ) - { - if ( ShowDetailed ) - { - string amount = DesiredAmount.ToString(); + public override void WriteToGump(Gump g, ref int y) + { + if (ShowDetailed) + { + string amount = DesiredAmount.ToString(); - g.AddHtmlLocalized( 98, y, 350, 16, 1072205, 0x15F90, false, false ); // Obtain - g.AddLabel( 143, y, 0x481, amount ); + g.AddHtmlLocalized(98, y, 350, 16, 1072205, 0x15F90, false, false); // Obtain + g.AddLabel(143, y, 0x481, amount); - if ( Name.Number > 0 ) - { - g.AddHtmlLocalized( 143 + amount.Length * 15, y, 190, 18, Name.Number, 0x77BF, false, false ); - g.AddItem( 350, y, LabelToItemID( Name.Number ) ); - } - else if ( Name.String != null ) - { - g.AddLabel( 143 + amount.Length * 15, y, 0x481, Name.String ); - } - } - else - { - if ( Name.Number > 0 ) - g.AddHtmlLocalized( 98, y, 312, 32, Name.Number, 0x15F90, false, false ); - else if ( Name.String != null ) - g.AddLabel( 98, y, 0x481, Name.String ); - } + if (Name.Number > 0) + { + g.AddHtmlLocalized(143 + amount.Length * 15, y, 190, 18, Name.Number, 0x77BF, false, false); + g.AddItem(350, y, LabelToItemID(Name.Number)); + } + else if (Name.String != null) + { + g.AddLabel(143 + amount.Length * 15, y, 0x481, Name.String); + } + } + else + { + if (Name.Number > 0) + g.AddHtmlLocalized(98, y, 312, 32, Name.Number, 0x15F90, false, false); + else if (Name.String != null) + g.AddLabel(98, y, 0x481, Name.String); + } - y += 32; - } + y += 32; + } - public override BaseObjectiveInstance CreateInstance( MLQuestInstance instance ) - { - return new CollectObjectiveInstance( this, instance ); - } - } + public override BaseObjectiveInstance CreateInstance(MLQuestInstance instance) + { + return new CollectObjectiveInstance(this, instance); + } + } - #region Timed + #region Timed - public class TimedCollectObjective : CollectObjective - { - public override bool IsTimed => true; - public override TimeSpan Duration { get; } + public class TimedCollectObjective : CollectObjective + { + public TimedCollectObjective(TimeSpan duration, int amount, Type type, TextDefinition name) + : base(amount, type, name) + { + Duration = duration; + } - public TimedCollectObjective( TimeSpan duration, int amount, Type type, TextDefinition name ) - : base( amount, type, name ) - { - Duration = duration; - } - } + public override bool IsTimed => true; + public override TimeSpan Duration{ get; } + } - #endregion + #endregion - public class CollectObjectiveInstance : BaseObjectiveInstance - { - public CollectObjective Objective { get; set; } + public class CollectObjectiveInstance : BaseObjectiveInstance + { + public CollectObjectiveInstance(CollectObjective objective, MLQuestInstance instance) + : base(instance, objective) + { + Objective = objective; + } - public CollectObjectiveInstance( CollectObjective objective, MLQuestInstance instance ) - : base( instance, objective ) - { - Objective = objective; - } + public CollectObjective Objective{ get; set; } - private int GetCurrentTotal() - { - Container pack = Instance.Player.Backpack; + private int GetCurrentTotal() + { + Container pack = Instance.Player.Backpack; - if ( pack == null ) - return 0; + if (pack == null) + return 0; - Item[] items = pack.FindItemsByType( Objective.AcceptedType, false ); // Note: subclasses are included - int total = 0; + Item[] items = pack.FindItemsByType(Objective.AcceptedType, false); // Note: subclasses are included + int total = 0; - foreach ( Item item in items ) - { - if ( item.QuestItem && Objective.CheckItem( item ) ) - total += item.Amount; - } + foreach (Item item in items) + if (item.QuestItem && Objective.CheckItem(item)) + total += item.Amount; - return total; - } + return total; + } - public override bool AllowsQuestItem( Item item, Type type ) - { - return ( Objective.CheckType( type ) && Objective.CheckItem( item ) ); - } + public override bool AllowsQuestItem(Item item, Type type) + { + return Objective.CheckType(type) && Objective.CheckItem(item); + } - public override bool IsCompleted() - { - return ( GetCurrentTotal() >= Objective.DesiredAmount ); - } + public override bool IsCompleted() + { + return GetCurrentTotal() >= Objective.DesiredAmount; + } - public override void OnQuestCancelled() - { - PlayerMobile pm = Instance.Player; - Container pack = pm.Backpack; + public override void OnQuestCancelled() + { + PlayerMobile pm = Instance.Player; + Container pack = pm.Backpack; - if ( pack == null ) - return; + if (pack == null) + return; - Type checkType = Objective.AcceptedType; - Item[] items = pack.FindItemsByType( checkType, false ); + Type checkType = Objective.AcceptedType; + Item[] items = pack.FindItemsByType(checkType, false); - foreach ( Item item in items ) - { - if ( item.QuestItem && !MLQuestSystem.CanMarkQuestItem( pm, item, checkType ) ) // does another quest still need this item? (OSI just unmarks everything) - item.QuestItem = false; - } - } + foreach (Item item in items) + if (item.QuestItem && !MLQuestSystem.CanMarkQuestItem(pm, item, checkType) + ) // does another quest still need this item? (OSI just unmarks everything) + item.QuestItem = false; + } - // Should only be called after IsComplete() is checked to be true - public override void OnClaimReward() - { - Container pack = Instance.Player.Backpack; + // Should only be called after IsComplete() is checked to be true + public override void OnClaimReward() + { + Container pack = Instance.Player.Backpack; - if ( pack == null ) - return; + if (pack == null) + return; - // TODO: OSI also counts the item in the cursor? + // TODO: OSI also counts the item in the cursor? - Item[] items = pack.FindItemsByType( Objective.AcceptedType, false ); - int left = Objective.DesiredAmount; + Item[] items = pack.FindItemsByType(Objective.AcceptedType, false); + int left = Objective.DesiredAmount; - foreach ( Item item in items ) - { - if ( item.QuestItem && Objective.CheckItem( item ) ) - { - if ( left == 0 ) - return; + foreach (Item item in items) + if (item.QuestItem && Objective.CheckItem(item)) + { + if (left == 0) + return; - if ( item.Amount > left ) - { - item.Consume( left ); - left = 0; - } - else - { - item.Delete(); - left -= item.Amount; - } - } - } - } + if (item.Amount > left) + { + item.Consume(left); + left = 0; + } + else + { + item.Delete(); + left -= item.Amount; + } + } + } - public override void OnAfterClaimReward() - { - OnQuestCancelled(); // same thing, clear other quest items - } + public override void OnAfterClaimReward() + { + OnQuestCancelled(); // same thing, clear other quest items + } - public override void OnExpire() - { - OnQuestCancelled(); + public override void OnExpire() + { + OnQuestCancelled(); - // No message - } + // No message + } - public override void WriteToGump( Gump g, ref int y ) - { - Objective.WriteToGump( g, ref y ); - y -= 16; + public override void WriteToGump(Gump g, ref int y) + { + Objective.WriteToGump(g, ref y); + y -= 16; - if ( Objective.ShowDetailed ) - { - base.WriteToGump( g, ref y ); + if (Objective.ShowDetailed) + { + base.WriteToGump(g, ref y); - g.AddHtmlLocalized( 103, y, 120, 16, 3000087, 0x15F90, false, false ); // Total - g.AddLabel( 223, y, 0x481, GetCurrentTotal().ToString() ); - y += 16; + g.AddHtmlLocalized(103, y, 120, 16, 3000087, 0x15F90, false, false); // Total + g.AddLabel(223, y, 0x481, GetCurrentTotal().ToString()); + y += 16; - g.AddHtmlLocalized( 103, y, 120, 16, 1074782, 0x15F90, false, false ); // Return to - g.AddLabel( 223, y, 0x481, QuesterNameAttribute.GetQuesterNameFor( Instance.QuesterType ) ); - y += 16; - } - } - } -} + g.AddHtmlLocalized(103, y, 120, 16, 1074782, 0x15F90, false, false); // Return to + g.AddLabel(223, y, 0x481, QuesterNameAttribute.GetQuesterNameFor(Instance.QuesterType)); + y += 16; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Objectives/DeliverObjective.cs b/Scripts/Engines/MLQuests/Objectives/DeliverObjective.cs index f5aa27ce1..97fcd05e0 100644 --- a/Scripts/Engines/MLQuests/Objectives/DeliverObjective.cs +++ b/Scripts/Engines/MLQuests/Objectives/DeliverObjective.cs @@ -6,237 +6,238 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Objectives { - public class DeliverObjective : BaseObjective - { - public Type Delivery { get; set; } + public class DeliverObjective : BaseObjective + { + public DeliverObjective(Type delivery, int amount, TextDefinition name, Type destination) + : this(delivery, amount, name, destination, true) + { + } - public int Amount { get; set; } + public DeliverObjective(Type delivery, int amount, TextDefinition name, Type destination, bool spawnsDelivery) + { + Delivery = delivery; + Amount = amount; + Name = name; + Destination = destination; + SpawnsDelivery = spawnsDelivery; - public TextDefinition Name { get; set; } + if (MLQuestSystem.Debug && name.Number > 0) + { + int itemid = CollectObjective.LabelToItemID(name.Number); - public Type Destination { get; set; } + if (itemid <= 0 || itemid > 0x4000) + Console.WriteLine("Warning: cliloc {0} is likely giving the wrong item ID", name.Number); + } + } - public bool SpawnsDelivery { get; set; } + public Type Delivery{ get; set; } - public DeliverObjective( Type delivery, int amount, TextDefinition name, Type destination ) - : this( delivery, amount, name, destination, true ) - { - } + public int Amount{ get; set; } - public DeliverObjective( Type delivery, int amount, TextDefinition name, Type destination, bool spawnsDelivery ) - { - Delivery = delivery; - Amount = amount; - Name = name; - Destination = destination; - SpawnsDelivery = spawnsDelivery; + public TextDefinition Name{ get; set; } - if ( MLQuestSystem.Debug && name.Number > 0 ) - { - int itemid = CollectObjective.LabelToItemID( name.Number ); + public Type Destination{ get; set; } - if ( itemid <= 0 || itemid > 0x4000 ) - Console.WriteLine( "Warning: cliloc {0} is likely giving the wrong item ID", name.Number ); - } - } + public bool SpawnsDelivery{ get; set; } - public virtual void SpawnDelivery( Container pack ) - { - if ( !SpawnsDelivery || pack == null ) - return; + public virtual void SpawnDelivery(Container pack) + { + if (!SpawnsDelivery || pack == null) + return; - List delivery = new List(); + List delivery = new List(); - for ( int i = 0; i < Amount; ++i ) - { - if ( !(Activator.CreateInstance( Delivery ) is Item item) ) - continue; + for (int i = 0; i < Amount; ++i) + { + if (!(Activator.CreateInstance(Delivery) is Item item)) + continue; - delivery.Add( item ); + delivery.Add(item); - if ( item.Stackable && Amount > 1 ) - { - item.Amount = Amount; - break; - } - } + if (item.Stackable && Amount > 1) + { + item.Amount = Amount; + break; + } + } - foreach ( Item item in delivery ) - pack.DropItem( item ); // Confirmed: on OSI items are added even if your pack is full - } + foreach (Item item in delivery) + pack.DropItem(item); // Confirmed: on OSI items are added even if your pack is full + } - public override void WriteToGump( Gump g, ref int y ) - { - string amount = Amount.ToString(); + public override void WriteToGump(Gump g, ref int y) + { + string amount = Amount.ToString(); - g.AddHtmlLocalized( 98, y, 312, 16, 1072207, 0x15F90, false, false ); // Deliver - g.AddLabel( 143, y, 0x481, amount ); + g.AddHtmlLocalized(98, y, 312, 16, 1072207, 0x15F90, false, false); // Deliver + g.AddLabel(143, y, 0x481, amount); - if ( Name.Number > 0 ) - { - g.AddHtmlLocalized( 143 + amount.Length * 15, y, 190, 18, Name.Number, 0x77BF, false, false ); - g.AddItem( 350, y, CollectObjective.LabelToItemID( Name.Number ) ); - } - else if ( Name.String != null ) - { - g.AddLabel( 143 + amount.Length * 15, y, 0x481, Name.String ); - } + if (Name.Number > 0) + { + g.AddHtmlLocalized(143 + amount.Length * 15, y, 190, 18, Name.Number, 0x77BF, false, false); + g.AddItem(350, y, CollectObjective.LabelToItemID(Name.Number)); + } + else if (Name.String != null) + { + g.AddLabel(143 + amount.Length * 15, y, 0x481, Name.String); + } - y += 32; + y += 32; - g.AddHtmlLocalized( 103, y, 120, 16, 1072379, 0x15F90, false, false ); // Deliver to - g.AddLabel( 223, y, 0x481, QuesterNameAttribute.GetQuesterNameFor( Destination ) ); + g.AddHtmlLocalized(103, y, 120, 16, 1072379, 0x15F90, false, false); // Deliver to + g.AddLabel(223, y, 0x481, QuesterNameAttribute.GetQuesterNameFor(Destination)); - y += 16; - } + y += 16; + } - public override BaseObjectiveInstance CreateInstance( MLQuestInstance instance ) - { - return new DeliverObjectiveInstance( this, instance ); - } - } + public override BaseObjectiveInstance CreateInstance(MLQuestInstance instance) + { + return new DeliverObjectiveInstance(this, instance); + } + } - #region Timed + #region Timed - public class TimedDeliverObjective : DeliverObjective - { - public override bool IsTimed => true; - public override TimeSpan Duration { get; } + public class TimedDeliverObjective : DeliverObjective + { + public TimedDeliverObjective(TimeSpan duration, Type delivery, int amount, TextDefinition name, Type destination) + : this(duration, delivery, amount, name, destination, true) + { + } - public TimedDeliverObjective( TimeSpan duration, Type delivery, int amount, TextDefinition name, Type destination ) - : this( duration, delivery, amount, name, destination, true ) - { - } + public TimedDeliverObjective(TimeSpan duration, Type delivery, int amount, TextDefinition name, Type destination, + bool spawnsDelivery) + : base(delivery, amount, name, destination, spawnsDelivery) + { + Duration = duration; + } - public TimedDeliverObjective( TimeSpan duration, Type delivery, int amount, TextDefinition name, Type destination, bool spawnsDelivery ) - : base( delivery, amount, name, destination, spawnsDelivery ) - { - Duration = duration; - } - } + public override bool IsTimed => true; + public override TimeSpan Duration{ get; } + } - #endregion + #endregion - public class DeliverObjectiveInstance : BaseObjectiveInstance - { - public DeliverObjective Objective { get; set; } + public class DeliverObjectiveInstance : BaseObjectiveInstance + { + public DeliverObjectiveInstance(DeliverObjective objective, MLQuestInstance instance) + : base(instance, objective) + { + Objective = objective; + } - public bool HasCompleted { get; set; } + public DeliverObjective Objective{ get; set; } - public DeliverObjectiveInstance( DeliverObjective objective, MLQuestInstance instance ) - : base( instance, objective ) - { - Objective = objective; - } + public bool HasCompleted{ get; set; } - public virtual bool IsDestination( IQuestGiver quester, Type type ) - { - Type destType = Objective.Destination; + public override DataType ExtraDataType => DataType.DeliverObjective; - return ( destType != null && destType.IsAssignableFrom( type ) ); - } + public virtual bool IsDestination(IQuestGiver quester, Type type) + { + Type destType = Objective.Destination; - public override bool IsCompleted() - { - return HasCompleted; - } + return destType != null && destType.IsAssignableFrom(type); + } - public override void OnQuestAccepted() - { - Objective.SpawnDelivery( Instance.Player.Backpack ); - } + public override bool IsCompleted() + { + return HasCompleted; + } - // This is VERY similar to CollectObjective.GetCurrentTotal - private int GetCurrentTotal() - { - Container pack = Instance.Player.Backpack; + public override void OnQuestAccepted() + { + Objective.SpawnDelivery(Instance.Player.Backpack); + } - if ( pack == null ) - return 0; + // This is VERY similar to CollectObjective.GetCurrentTotal + private int GetCurrentTotal() + { + Container pack = Instance.Player.Backpack; - Item[] items = pack.FindItemsByType( Objective.Delivery, false ); // Note: subclasses are included - int total = 0; + if (pack == null) + return 0; - foreach ( Item item in items ) - total += item.Amount; + Item[] items = pack.FindItemsByType(Objective.Delivery, false); // Note: subclasses are included + int total = 0; - return total; - } + foreach (Item item in items) + total += item.Amount; - public override bool OnBeforeClaimReward() - { - PlayerMobile pm = Instance.Player; + return total; + } - int total = GetCurrentTotal(); - int desired = Objective.Amount; + public override bool OnBeforeClaimReward() + { + PlayerMobile pm = Instance.Player; - if ( total < desired ) - { - pm.SendLocalizedMessage( 1074861 ); // You do not have everything you need! - pm.SendLocalizedMessage( 1074885, $"{total}\t{desired}"); // You have ~1_val~ item(s) but require ~2_val~ - return false; - } + int total = GetCurrentTotal(); + int desired = Objective.Amount; - return true; - } + if (total < desired) + { + pm.SendLocalizedMessage(1074861); // You do not have everything you need! + pm.SendLocalizedMessage(1074885, $"{total}\t{desired}"); // You have ~1_val~ item(s) but require ~2_val~ + return false; + } - // TODO: This is VERY similar to CollectObjective.OnClaimReward - public override void OnClaimReward() - { - Container pack = Instance.Player.Backpack; + return true; + } - if ( pack == null ) - return; + // TODO: This is VERY similar to CollectObjective.OnClaimReward + public override void OnClaimReward() + { + Container pack = Instance.Player.Backpack; - Item[] items = pack.FindItemsByType( Objective.Delivery, false ); - int left = Objective.Amount; + if (pack == null) + return; - foreach ( Item item in items ) - { - if ( left == 0 ) - break; + Item[] items = pack.FindItemsByType(Objective.Delivery, false); + int left = Objective.Amount; - if ( item.Amount > left ) - { - item.Consume( left ); - left = 0; - } - else - { - item.Delete(); - left -= item.Amount; - } - } - } + foreach (Item item in items) + { + if (left == 0) + break; - public override void OnQuestCancelled() - { - OnClaimReward(); // same effect - } + if (item.Amount > left) + { + item.Consume(left); + left = 0; + } + else + { + item.Delete(); + left -= item.Amount; + } + } + } - public override void OnExpire() - { - OnQuestCancelled(); + public override void OnQuestCancelled() + { + OnClaimReward(); // same effect + } - Instance.Player.SendLocalizedMessage( 1074813 ); // You have failed to complete your delivery. - } + public override void OnExpire() + { + OnQuestCancelled(); - public override void WriteToGump( Gump g, ref int y ) - { - Objective.WriteToGump( g, ref y ); + Instance.Player.SendLocalizedMessage(1074813); // You have failed to complete your delivery. + } - base.WriteToGump( g, ref y ); + public override void WriteToGump(Gump g, ref int y) + { + Objective.WriteToGump(g, ref y); - // No extra instance stuff printed for this objective - } + base.WriteToGump(g, ref y); - public override DataType ExtraDataType => DataType.DeliverObjective; + // No extra instance stuff printed for this objective + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( HasCompleted ); - } - } -} + writer.Write(HasCompleted); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Objectives/EscortObjective.cs b/Scripts/Engines/MLQuests/Objectives/EscortObjective.cs index d601e258a..24d794829 100644 --- a/Scripts/Engines/MLQuests/Objectives/EscortObjective.cs +++ b/Scripts/Engines/MLQuests/Objectives/EscortObjective.cs @@ -1,270 +1,271 @@ using System; -using Server.Mobiles; using Server.Gumps; using Server.Misc; +using Server.Mobiles; namespace Server.Engines.MLQuests.Objectives { - public class EscortObjective : BaseObjective - { - public QuestArea Destination { get; set; } + public class EscortObjective : BaseObjective + { + public EscortObjective() + : this(null) + { + } - public EscortObjective() - : this( null ) - { - } + public EscortObjective(QuestArea destination) + { + Destination = destination; + } - public EscortObjective( QuestArea destination ) - { - Destination = destination; - } + public QuestArea Destination{ get; set; } - public override bool CanOffer( IQuestGiver quester, PlayerMobile pm, bool message ) - { - if ( ( quester is BaseCreature creature && creature.Controlled ) || ( quester is BaseEscortable escortable && escortable.IsBeingDeleted ) ) - return false; + public override bool CanOffer(IQuestGiver quester, PlayerMobile pm, bool message) + { + if (quester is BaseCreature creature && creature.Controlled || + quester is BaseEscortable escortable && escortable.IsBeingDeleted) + return false; - MLQuestContext context = MLQuestSystem.GetContext( pm ); + MLQuestContext context = MLQuestSystem.GetContext(pm); - if ( context != null ) - { - foreach ( MLQuestInstance instance in context.QuestInstances ) - { - if ( instance.Quest.IsEscort ) - { - if ( message ) - MLQuestSystem.Tell( quester, pm, 500896 ); // I see you already have an escort. + if (context != null) + foreach (MLQuestInstance instance in context.QuestInstances) + if (instance.Quest.IsEscort) + { + if (message) + MLQuestSystem.Tell(quester, pm, 500896); // I see you already have an escort. - return false; - } - } - } + return false; + } - DateTime nextEscort = pm.LastEscortTime + BaseEscortable.EscortDelay; + DateTime nextEscort = pm.LastEscortTime + BaseEscortable.EscortDelay; - if ( nextEscort > DateTime.UtcNow ) - { - if ( message ) - { - int minutes = (int)Math.Ceiling( ( nextEscort - DateTime.UtcNow ).TotalMinutes ); + if (nextEscort > DateTime.UtcNow) + { + if (message) + { + int minutes = (int)Math.Ceiling((nextEscort - DateTime.UtcNow).TotalMinutes); - if ( minutes == 1 ) - MLQuestSystem.Tell( quester, pm, "You must rest 1 minute before we set out on this journey." ); - else - MLQuestSystem.Tell( quester, pm, 1071195, minutes.ToString() ); // You must rest ~1_minsleft~ minutes before we set out on this journey. - } + if (minutes == 1) + MLQuestSystem.Tell(quester, pm, "You must rest 1 minute before we set out on this journey."); + else + MLQuestSystem.Tell(quester, pm, 1071195, + minutes.ToString()); // You must rest ~1_minsleft~ minutes before we set out on this journey. + } - return false; - } + return false; + } - return true; - } + return true; + } - public override void WriteToGump( Gump g, ref int y ) - { - g.AddHtmlLocalized( 98, y, 312, 16, 1072206, 0x15F90, false, false ); // Escort to + public override void WriteToGump(Gump g, ref int y) + { + g.AddHtmlLocalized(98, y, 312, 16, 1072206, 0x15F90, false, false); // Escort to - if ( Destination.Name.Number > 0 ) - g.AddHtmlLocalized( 173, y, 312, 20, Destination.Name.Number, 0xFFFFFF, false, false ); - else if ( Destination.Name.String != null ) - g.AddLabel( 173, y, 0x481, Destination.Name.String ); + if (Destination.Name.Number > 0) + g.AddHtmlLocalized(173, y, 312, 20, Destination.Name.Number, 0xFFFFFF, false, false); + else if (Destination.Name.String != null) + g.AddLabel(173, y, 0x481, Destination.Name.String); - y += 16; - } + y += 16; + } - public override BaseObjectiveInstance CreateInstance( MLQuestInstance instance ) - { - if ( instance == null || Destination == null ) - return null; + public override BaseObjectiveInstance CreateInstance(MLQuestInstance instance) + { + if (instance == null || Destination == null) + return null; - return new EscortObjectiveInstance( this, instance ); - } - } + return new EscortObjectiveInstance(this, instance); + } + } - public class EscortObjectiveInstance : BaseObjectiveInstance - { - private EscortObjective m_Objective; - private Timer m_Timer; - private DateTime m_LastSeenEscorter; - private BaseCreature m_Escort; + public class EscortObjectiveInstance : BaseObjectiveInstance + { + private BaseCreature m_Escort; + private DateTime m_LastSeenEscorter; + private EscortObjective m_Objective; + private Timer m_Timer; - public bool HasCompleted { get; set; } + public EscortObjectiveInstance(EscortObjective objective, MLQuestInstance instance) + : base(instance, objective) + { + m_Objective = objective; + HasCompleted = false; + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(5), CheckDestination); + m_LastSeenEscorter = DateTime.UtcNow; + m_Escort = instance.Quester as BaseCreature; - public EscortObjectiveInstance( EscortObjective objective, MLQuestInstance instance ) - : base( instance, objective ) - { - m_Objective = objective; - HasCompleted = false; - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 5 ), CheckDestination ); - m_LastSeenEscorter = DateTime.UtcNow; - m_Escort = instance.Quester as BaseCreature; + if (MLQuestSystem.Debug && m_Escort == null && instance.Quester != null) + Console.WriteLine("Warning: EscortObjective is not supported for type '{0}'", + instance.Quester.GetType().Name); + } - if ( MLQuestSystem.Debug && m_Escort == null && instance.Quester != null ) - Console.WriteLine( "Warning: EscortObjective is not supported for type '{0}'", instance.Quester.GetType().Name ); - } + public bool HasCompleted{ get; set; } - public override bool IsCompleted() - { - return HasCompleted; - } + public override DataType ExtraDataType => DataType.EscortObjective; - private void CheckDestination() - { - if ( m_Escort == null || HasCompleted ) // Completed by deserialization - { - StopTimer(); - return; - } + public override bool IsCompleted() + { + return HasCompleted; + } - MLQuestInstance instance = Instance; - PlayerMobile pm = instance.Player; + private void CheckDestination() + { + if (m_Escort == null || HasCompleted) // Completed by deserialization + { + StopTimer(); + return; + } - if ( instance.Removed ) - { - Abandon(); - } - else if ( m_Objective.Destination.Contains( m_Escort ) ) - { - m_Escort.Say( 1042809, pm.Name ); // We have arrived! I thank thee, ~1_PLAYER_NAME~! I have no further need of thy services. Here is thy pay. + MLQuestInstance instance = Instance; + PlayerMobile pm = instance.Player; - if ( pm.Young || m_Escort.Region.IsPartOf( "Haven Island" ) ) - Titles.AwardFame( pm, 10, true ); - else - VirtueHelper.AwardVirtue( pm, VirtueName.Compassion, ( m_Escort is BaseEscortable escortable && escortable.IsPrisoner ) ? 400 : 200 ); + if (instance.Removed) + { + Abandon(); + } + else if (m_Objective.Destination.Contains(m_Escort)) + { + m_Escort.Say(1042809, + pm.Name); // We have arrived! I thank thee, ~1_PLAYER_NAME~! I have no further need of thy services. Here is thy pay. - EndFollow( m_Escort ); - StopTimer(); + if (pm.Young || m_Escort.Region.IsPartOf("Haven Island")) + Titles.AwardFame(pm, 10, true); + else + VirtueHelper.AwardVirtue(pm, VirtueName.Compassion, + m_Escort is BaseEscortable escortable && escortable.IsPrisoner ? 400 : 200); - HasCompleted = true; - CheckComplete(); + EndFollow(m_Escort); + StopTimer(); - // Auto claim reward - MLQuestSystem.OnDoubleClick( m_Escort, pm ); - } - else if ( pm.Map != m_Escort.Map || !pm.InRange( m_Escort, 30 ) ) // TODO: verify range - { - if ( m_LastSeenEscorter + BaseEscortable.AbandonDelay <= DateTime.UtcNow ) - Abandon(); - } - else - { - m_LastSeenEscorter = DateTime.UtcNow; - } - } + HasCompleted = true; + CheckComplete(); - private void StopTimer() - { - if ( m_Timer != null ) - { - m_Timer.Stop(); - m_Timer = null; - } - } + // Auto claim reward + MLQuestSystem.OnDoubleClick(m_Escort, pm); + } + else if (pm.Map != m_Escort.Map || !pm.InRange(m_Escort, 30)) // TODO: verify range + { + if (m_LastSeenEscorter + BaseEscortable.AbandonDelay <= DateTime.UtcNow) + Abandon(); + } + else + { + m_LastSeenEscorter = DateTime.UtcNow; + } + } - public static void BeginFollow( BaseCreature quester, PlayerMobile pm ) - { - quester.ControlSlots = 0; - quester.SetControlMaster( pm ); + private void StopTimer() + { + if (m_Timer != null) + { + m_Timer.Stop(); + m_Timer = null; + } + } - quester.ActiveSpeed = 0.1; - quester.PassiveSpeed = 0.2; + public static void BeginFollow(BaseCreature quester, PlayerMobile pm) + { + quester.ControlSlots = 0; + quester.SetControlMaster(pm); - quester.ControlOrder = OrderType.Follow; - quester.ControlTarget = pm; + quester.ActiveSpeed = 0.1; + quester.PassiveSpeed = 0.2; - quester.CantWalk = false; - quester.CurrentSpeed = 0.1; - } + quester.ControlOrder = OrderType.Follow; + quester.ControlTarget = pm; - public static void EndFollow( BaseCreature quester ) - { - quester.ActiveSpeed = 0.2; - quester.PassiveSpeed = 1.0; + quester.CantWalk = false; + quester.CurrentSpeed = 0.1; + } - quester.ControlOrder = OrderType.None; - quester.ControlTarget = null; + public static void EndFollow(BaseCreature quester) + { + quester.ActiveSpeed = 0.2; + quester.PassiveSpeed = 1.0; - quester.CurrentSpeed = 1.0; + quester.ControlOrder = OrderType.None; + quester.ControlTarget = null; - quester.SetControlMaster( null ); + quester.CurrentSpeed = 1.0; - (quester as BaseEscortable)?.BeginDelete(); - } + quester.SetControlMaster(null); - public override void OnQuestAccepted() - { - MLQuestInstance instance = Instance; - PlayerMobile pm = instance.Player; + (quester as BaseEscortable)?.BeginDelete(); + } - pm.LastEscortTime = DateTime.UtcNow; + public override void OnQuestAccepted() + { + MLQuestInstance instance = Instance; + PlayerMobile pm = instance.Player; - if ( m_Escort != null ) - BeginFollow( m_Escort, pm ); - } + pm.LastEscortTime = DateTime.UtcNow; - public void Abandon() - { - StopTimer(); + if (m_Escort != null) + BeginFollow(m_Escort, pm); + } - MLQuestInstance instance = Instance; - PlayerMobile pm = instance.Player; + public void Abandon() + { + StopTimer(); - if ( m_Escort != null && !m_Escort.Deleted ) - { - if ( !pm.Alive ) - m_Escort.Say( 500901 ); // Ack! My escort has come to haunt me! - else - m_Escort.Say( 500902 ); // My escort seems to have abandoned me! + MLQuestInstance instance = Instance; + PlayerMobile pm = instance.Player; - EndFollow( m_Escort ); - } + if (m_Escort != null && !m_Escort.Deleted) + { + if (!pm.Alive) + m_Escort.Say(500901); // Ack! My escort has come to haunt me! + else + m_Escort.Say(500902); // My escort seems to have abandoned me! - // Note: this sound is sent twice on OSI (once here and once in Cancel()) - //m_Player.SendSound( 0x5B3 ); // private sound - pm.SendLocalizedMessage( 1071194 ); // You have failed your escort quest... + EndFollow(m_Escort); + } - if ( !instance.Removed ) - instance.Cancel(); - } + // Note: this sound is sent twice on OSI (once here and once in Cancel()) + //m_Player.SendSound( 0x5B3 ); // private sound + pm.SendLocalizedMessage(1071194); // You have failed your escort quest... - public override void OnQuesterDeleted() - { - if ( IsCompleted() || Instance.Removed ) - return; + if (!instance.Removed) + instance.Cancel(); + } - Abandon(); - } + public override void OnQuesterDeleted() + { + if (IsCompleted() || Instance.Removed) + return; - public override void OnPlayerDeath() - { - // Note: OSI also cancels it when the quest is already complete - if ( /*IsCompleted() ||*/ Instance.Removed ) - return; + Abandon(); + } - Instance.Cancel(); - } + public override void OnPlayerDeath() + { + // Note: OSI also cancels it when the quest is already complete + if ( /*IsCompleted() ||*/ Instance.Removed) + return; - public override void OnExpire() - { - Abandon(); - } + Instance.Cancel(); + } - public override void WriteToGump( Gump g, ref int y ) - { - m_Objective.WriteToGump( g, ref y ); + public override void OnExpire() + { + Abandon(); + } - base.WriteToGump( g, ref y ); + public override void WriteToGump(Gump g, ref int y) + { + m_Objective.WriteToGump(g, ref y); - // No extra instance stuff printed for this objective - } + base.WriteToGump(g, ref y); - public override DataType ExtraDataType => DataType.EscortObjective; + // No extra instance stuff printed for this objective + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( HasCompleted ); - } - } -} + writer.Write(HasCompleted); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Objectives/GainSkillObjective.cs b/Scripts/Engines/MLQuests/Objectives/GainSkillObjective.cs index 52abae1c6..a2c241db9 100644 --- a/Scripts/Engines/MLQuests/Objectives/GainSkillObjective.cs +++ b/Scripts/Engines/MLQuests/Objectives/GainSkillObjective.cs @@ -1,172 +1,174 @@ using System; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; namespace Server.Engines.MLQuests.Objectives { - public enum GainSkillObjectiveFlags : byte - { - None = 0x00, - UseReal = 0x01, - Accelerate = 0x02 - } + public enum GainSkillObjectiveFlags : byte + { + None = 0x00, + UseReal = 0x01, + Accelerate = 0x02 + } - public class GainSkillObjective : BaseObjective - { - private GainSkillObjectiveFlags m_Flags; + public class GainSkillObjective : BaseObjective + { + private GainSkillObjectiveFlags m_Flags; - public SkillName Skill { get; set; } + public GainSkillObjective() + : this(SkillName.Alchemy, 0) + { + } - public int ThresholdFixed { get; set; } + public GainSkillObjective(SkillName skill, int thresholdFixed) + : this(skill, thresholdFixed, false, false) + { + } - public bool UseReal - { - get => GetFlag( GainSkillObjectiveFlags.UseReal ); - set => SetFlag( GainSkillObjectiveFlags.UseReal, value ); - } + public GainSkillObjective(SkillName skill, int thresholdFixed, bool useReal, bool accelerate) + { + Skill = skill; + ThresholdFixed = thresholdFixed; + m_Flags = GainSkillObjectiveFlags.None; - public bool Accelerate - { - get => GetFlag( GainSkillObjectiveFlags.Accelerate ); - set => SetFlag( GainSkillObjectiveFlags.Accelerate, value ); - } + if (useReal) + m_Flags |= GainSkillObjectiveFlags.UseReal; - public GainSkillObjective() - : this( SkillName.Alchemy, 0 ) - { - } + if (accelerate) + m_Flags |= GainSkillObjectiveFlags.Accelerate; + } - public GainSkillObjective( SkillName skill, int thresholdFixed ) - : this( skill, thresholdFixed, false, false ) - { - } + public SkillName Skill{ get; set; } - public GainSkillObjective( SkillName skill, int thresholdFixed, bool useReal, bool accelerate ) - { - Skill = skill; - ThresholdFixed = thresholdFixed; - m_Flags = GainSkillObjectiveFlags.None; + public int ThresholdFixed{ get; set; } - if ( useReal ) - m_Flags |= GainSkillObjectiveFlags.UseReal; + public bool UseReal + { + get => GetFlag(GainSkillObjectiveFlags.UseReal); + set => SetFlag(GainSkillObjectiveFlags.UseReal, value); + } - if ( accelerate ) - m_Flags |= GainSkillObjectiveFlags.Accelerate; - } + public bool Accelerate + { + get => GetFlag(GainSkillObjectiveFlags.Accelerate); + set => SetFlag(GainSkillObjectiveFlags.Accelerate, value); + } - public override bool CanOffer( IQuestGiver quester, PlayerMobile pm, bool message ) - { - Skill skill = pm.Skills[Skill]; + public override bool CanOffer(IQuestGiver quester, PlayerMobile pm, bool message) + { + Skill skill = pm.Skills[Skill]; - if ( ( UseReal ? skill.Fixed : skill.BaseFixedPoint ) >= ThresholdFixed ) - { - if ( message ) - MLQuestSystem.Tell( quester, pm, 1077772 ); // I cannot teach you, for you know all I can teach! + if ((UseReal ? skill.Fixed : skill.BaseFixedPoint) >= ThresholdFixed) + { + if (message) + MLQuestSystem.Tell(quester, pm, 1077772); // I cannot teach you, for you know all I can teach! - return false; - } + return false; + } - return true; - } + return true; + } - public override void WriteToGump( Gump g, ref int y ) - { - int skillLabel = AosSkillBonuses.GetLabel( Skill ); - string args; + public override void WriteToGump(Gump g, ref int y) + { + int skillLabel = AosSkillBonuses.GetLabel(Skill); + string args; - if ( ThresholdFixed % 10 == 0 ) - args = $"#{skillLabel}\t{ThresholdFixed / 10}"; // as seen on OSI - else - args = $"#{skillLabel}\t{(double) ThresholdFixed / 10:0.0}"; // for non-integer skill levels + if (ThresholdFixed % 10 == 0) + args = $"#{skillLabel}\t{ThresholdFixed / 10}"; // as seen on OSI + else + args = $"#{skillLabel}\t{(double)ThresholdFixed / 10:0.0}"; // for non-integer skill levels - g.AddHtmlLocalized( 98, y, 312, 16, 1077485, args, 0x15F90, false, false ); // Increase ~1_SKILL~ to ~2_VALUE~ - y += 16; - } + g.AddHtmlLocalized(98, y, 312, 16, 1077485, args, 0x15F90, false, false); // Increase ~1_SKILL~ to ~2_VALUE~ + y += 16; + } - public override BaseObjectiveInstance CreateInstance( MLQuestInstance instance ) - { - return new GainSkillObjectiveInstance( this, instance ); - } + public override BaseObjectiveInstance CreateInstance(MLQuestInstance instance) + { + return new GainSkillObjectiveInstance(this, instance); + } - private bool GetFlag( GainSkillObjectiveFlags flag ) - { - return ( ( m_Flags & flag ) != 0 ); - } + private bool GetFlag(GainSkillObjectiveFlags flag) + { + return (m_Flags & flag) != 0; + } - private void SetFlag( GainSkillObjectiveFlags flag, bool value ) - { - if ( value ) - m_Flags |= flag; - else - m_Flags &= ~flag; - } - } + private void SetFlag(GainSkillObjectiveFlags flag, bool value) + { + if (value) + m_Flags |= flag; + else + m_Flags &= ~flag; + } + } - // On OSI, once this is complete, it will *stay* complete, even if you lower your skill again - public class GainSkillObjectiveInstance : BaseObjectiveInstance - { - public GainSkillObjective Objective { get; set; } + // On OSI, once this is complete, it will *stay* complete, even if you lower your skill again + public class GainSkillObjectiveInstance : BaseObjectiveInstance + { + public GainSkillObjectiveInstance(GainSkillObjective objective, MLQuestInstance instance) + : base(instance, objective) + { + Objective = objective; + } - public GainSkillObjectiveInstance( GainSkillObjective objective, MLQuestInstance instance ) - : base( instance, objective ) - { - Objective = objective; - } + public GainSkillObjective Objective{ get; set; } - public bool Handles( SkillName skill ) - { - return ( Objective.Skill == skill ); - } + public bool Handles(SkillName skill) + { + return Objective.Skill == skill; + } - public override bool IsCompleted() - { - PlayerMobile pm = Instance.Player; + public override bool IsCompleted() + { + PlayerMobile pm = Instance.Player; - int valueFixed = Objective.UseReal ? pm.Skills[Objective.Skill].Fixed : pm.Skills[Objective.Skill].BaseFixedPoint; + int valueFixed = Objective.UseReal + ? pm.Skills[Objective.Skill].Fixed + : pm.Skills[Objective.Skill].BaseFixedPoint; - return ( valueFixed >= Objective.ThresholdFixed ); - } + return valueFixed >= Objective.ThresholdFixed; + } - // TODO: This may interfere with scrolls, or even quests among each other - // How does OSI deal with this? - public override void OnQuestAccepted() - { - if ( !Objective.Accelerate ) - return; + // TODO: This may interfere with scrolls, or even quests among each other + // How does OSI deal with this? + public override void OnQuestAccepted() + { + if (!Objective.Accelerate) + return; - PlayerMobile pm = Instance.Player; + PlayerMobile pm = Instance.Player; - pm.AcceleratedSkill = Objective.Skill; - pm.AcceleratedStart = DateTime.UtcNow + TimeSpan.FromMinutes( 15 ); // TODO: Is there a max duration? - } + pm.AcceleratedSkill = Objective.Skill; + pm.AcceleratedStart = DateTime.UtcNow + TimeSpan.FromMinutes(15); // TODO: Is there a max duration? + } - public override void OnQuestCancelled() - { - if ( !Objective.Accelerate ) - return; + public override void OnQuestCancelled() + { + if (!Objective.Accelerate) + return; - PlayerMobile pm = Instance.Player; + PlayerMobile pm = Instance.Player; - pm.AcceleratedStart = DateTime.UtcNow; - pm.PlaySound( 0x100 ); - } + pm.AcceleratedStart = DateTime.UtcNow; + pm.PlaySound(0x100); + } - public override void OnQuestCompleted() - { - OnQuestCancelled(); - } + public override void OnQuestCompleted() + { + OnQuestCancelled(); + } - public override void WriteToGump( Gump g, ref int y ) - { - Objective.WriteToGump( g, ref y ); + public override void WriteToGump(Gump g, ref int y) + { + Objective.WriteToGump(g, ref y); - base.WriteToGump( g, ref y ); + base.WriteToGump(g, ref y); - if ( IsCompleted() ) - { - g.AddHtmlLocalized( 113, y, 312, 20, 1055121, 0xFFFFFF, false, false ); // Complete - y += 16; - } - } - } -} + if (IsCompleted()) + { + g.AddHtmlLocalized(113, y, 312, 20, 1055121, 0xFFFFFF, false, false); // Complete + y += 16; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Objectives/KillObjective.cs b/Scripts/Engines/MLQuests/Objectives/KillObjective.cs index 5433fcc93..729ac13c1 100644 --- a/Scripts/Engines/MLQuests/Objectives/KillObjective.cs +++ b/Scripts/Engines/MLQuests/Objectives/KillObjective.cs @@ -1,158 +1,159 @@ using System; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; namespace Server.Engines.MLQuests.Objectives { - public class KillObjective : BaseObjective - { - public int DesiredAmount { get; set; } + public class KillObjective : BaseObjective + { + public KillObjective() + : this(0, null, null, null) + { + } - public Type[] AcceptedTypes { get; set; } + public KillObjective(int amount, Type[] types, TextDefinition name) + : this(amount, types, name, null) + { + } - public TextDefinition Name { get; set; } + public KillObjective(int amount, Type[] types, TextDefinition name, QuestArea area) + { + DesiredAmount = amount; + AcceptedTypes = types; + Name = name; + Area = area; + } - public QuestArea Area { get; set; } + public int DesiredAmount{ get; set; } - public KillObjective() - : this( 0, null, null, null ) - { - } + public Type[] AcceptedTypes{ get; set; } - public KillObjective( int amount, Type[] types, TextDefinition name ) - : this( amount, types, name, null ) - { - } + public TextDefinition Name{ get; set; } - public KillObjective( int amount, Type[] types, TextDefinition name, QuestArea area ) - { - DesiredAmount = amount; - AcceptedTypes = types; - Name = name; - Area = area; - } + public QuestArea Area{ get; set; } - public override void WriteToGump( Gump g, ref int y ) - { - string amount = DesiredAmount.ToString(); + public override void WriteToGump(Gump g, ref int y) + { + string amount = DesiredAmount.ToString(); - g.AddHtmlLocalized( 98, y, 312, 16, 1072204, 0x15F90, false, false ); // Slay - g.AddLabel( 133, y, 0x481, amount ); + g.AddHtmlLocalized(98, y, 312, 16, 1072204, 0x15F90, false, false); // Slay + g.AddLabel(133, y, 0x481, amount); - if ( Name.Number > 0 ) - g.AddHtmlLocalized( 133 + amount.Length * 15, y, 190, 18, Name.Number, 0x77BF, false, false ); - else if ( Name.String != null ) - g.AddLabel( 133 + amount.Length * 15, y, 0x481, Name.String ); + if (Name.Number > 0) + g.AddHtmlLocalized(133 + amount.Length * 15, y, 190, 18, Name.Number, 0x77BF, false, false); + else if (Name.String != null) + g.AddLabel(133 + amount.Length * 15, y, 0x481, Name.String); - y += 16; + y += 16; - #region Location - if ( Area != null ) - { - g.AddHtmlLocalized( 103, y, 312, 20, 1018327, 0x15F90, false, false ); // Location + #region Location - if ( Area.Name.Number > 0 ) - g.AddHtmlLocalized( 223, y, 312, 20, Area.Name.Number, 0xFFFFFF, false, false ); - else if ( Area.Name.String != null ) - g.AddLabel( 223, y, 0x481, Area.Name.String ); + if (Area != null) + { + g.AddHtmlLocalized(103, y, 312, 20, 1018327, 0x15F90, false, false); // Location - y += 16; - } - #endregion - } + if (Area.Name.Number > 0) + g.AddHtmlLocalized(223, y, 312, 20, Area.Name.Number, 0xFFFFFF, false, false); + else if (Area.Name.String != null) + g.AddLabel(223, y, 0x481, Area.Name.String); - public override BaseObjectiveInstance CreateInstance( MLQuestInstance instance ) - { - return new KillObjectiveInstance( this, instance ); - } - } + y += 16; + } - #region Timed + #endregion + } - public class TimedKillObjective : KillObjective - { - public override bool IsTimed => true; - public override TimeSpan Duration { get; } + public override BaseObjectiveInstance CreateInstance(MLQuestInstance instance) + { + return new KillObjectiveInstance(this, instance); + } + } - public TimedKillObjective( TimeSpan duration, int amount, Type[] types, TextDefinition name ) - : this( duration, amount, types, name, null ) - { - } + #region Timed - public TimedKillObjective( TimeSpan duration, int amount, Type[] types, TextDefinition name, QuestArea area ) - : base( amount, types, name, area ) - { - Duration = duration; - } - } + public class TimedKillObjective : KillObjective + { + public TimedKillObjective(TimeSpan duration, int amount, Type[] types, TextDefinition name) + : this(duration, amount, types, name, null) + { + } - #endregion + public TimedKillObjective(TimeSpan duration, int amount, Type[] types, TextDefinition name, QuestArea area) + : base(amount, types, name, area) + { + Duration = duration; + } - public class KillObjectiveInstance : BaseObjectiveInstance - { - public KillObjective Objective { get; set; } + public override bool IsTimed => true; + public override TimeSpan Duration{ get; } + } - public int Slain { get; set; } + #endregion - public KillObjectiveInstance( KillObjective objective, MLQuestInstance instance ) - : base( instance, objective ) - { - Objective = objective; - Slain = 0; - } + public class KillObjectiveInstance : BaseObjectiveInstance + { + public KillObjectiveInstance(KillObjective objective, MLQuestInstance instance) + : base(instance, objective) + { + Objective = objective; + Slain = 0; + } - public bool AddKill( Mobile mob, Type type ) - { - int desired = Objective.DesiredAmount; + public KillObjective Objective{ get; set; } - foreach ( Type acceptedType in Objective.AcceptedTypes ) - { - if ( acceptedType.IsAssignableFrom( type ) ) - { - if ( Objective.Area != null && !Objective.Area.Contains( mob ) ) - return false; + public int Slain{ get; set; } - PlayerMobile pm = Instance.Player; + public override DataType ExtraDataType => DataType.KillObjective; - if ( ++Slain >= desired ) - pm.SendLocalizedMessage( 1075050 ); // You have killed all the required quest creatures of this type. - else - pm.SendLocalizedMessage( 1075051, ( desired - Slain ).ToString() ); // You have killed a quest creature. ~1_val~ more left. + public bool AddKill(Mobile mob, Type type) + { + int desired = Objective.DesiredAmount; - return true; - } - } + foreach (Type acceptedType in Objective.AcceptedTypes) + if (acceptedType.IsAssignableFrom(type)) + { + if (Objective.Area != null && !Objective.Area.Contains(mob)) + return false; - return false; - } + PlayerMobile pm = Instance.Player; - public override bool IsCompleted() - { - return ( Slain >= Objective.DesiredAmount ); - } + if (++Slain >= desired) + pm.SendLocalizedMessage(1075050); // You have killed all the required quest creatures of this type. + else + pm.SendLocalizedMessage(1075051, + (desired - Slain).ToString()); // You have killed a quest creature. ~1_val~ more left. - public override void WriteToGump( Gump g, ref int y ) - { - Objective.WriteToGump( g, ref y ); + return true; + } - base.WriteToGump( g, ref y ); + return false; + } - g.AddHtmlLocalized( 103, y, 120, 16, 3000087, 0x15F90, false, false ); // Total - g.AddLabel( 223, y, 0x481, Slain.ToString() ); - y += 16; + public override bool IsCompleted() + { + return Slain >= Objective.DesiredAmount; + } - g.AddHtmlLocalized( 103, y, 120, 16, 1074782, 0x15F90, false, false ); // Return to - g.AddLabel( 223, y, 0x481, QuesterNameAttribute.GetQuesterNameFor( Instance.QuesterType ) ); - y += 16; - } + public override void WriteToGump(Gump g, ref int y) + { + Objective.WriteToGump(g, ref y); - public override DataType ExtraDataType => DataType.KillObjective; + base.WriteToGump(g, ref y); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + g.AddHtmlLocalized(103, y, 120, 16, 3000087, 0x15F90, false, false); // Total + g.AddLabel(223, y, 0x481, Slain.ToString()); + y += 16; - writer.Write( Slain ); - } - } -} + g.AddHtmlLocalized(103, y, 120, 16, 1074782, 0x15F90, false, false); // Return to + g.AddLabel(223, y, 0x481, QuesterNameAttribute.GetQuesterNameFor(Instance.QuesterType)); + y += 16; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(Slain); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/QuestArea.cs b/Scripts/Engines/MLQuests/QuestArea.cs index 7d2a32c72..a2ef83e38 100644 --- a/Scripts/Engines/MLQuests/QuestArea.cs +++ b/Scripts/Engines/MLQuests/QuestArea.cs @@ -2,58 +2,57 @@ namespace Server.Engines.MLQuests { - public class QuestArea - { - public TextDefinition Name { get; set; } + public class QuestArea + { + public QuestArea(TextDefinition name, string region) + : this(name, region, null) + { + } - public string RegionName { get; set; } + public QuestArea(TextDefinition name, string region, Map forceMap) + { + Name = name; + RegionName = region; + ForceMap = forceMap; - public Map ForceMap { get; set; } + if (MLQuestSystem.Debug) + ValidationQueue.Add(this); + } - public QuestArea( TextDefinition name, string region ) - : this( name, region, null ) - { - } + public TextDefinition Name{ get; set; } - public QuestArea( TextDefinition name, string region, Map forceMap ) - { - Name = name; - RegionName = region; - ForceMap = forceMap; + public string RegionName{ get; set; } - if ( MLQuestSystem.Debug ) - ValidationQueue.Add( this ); - } + public Map ForceMap{ get; set; } - public bool Contains( Mobile mob ) - { - return Contains( mob.Region ); - } + public bool Contains(Mobile mob) + { + return Contains(mob.Region); + } - public bool Contains( Region reg ) - { - if ( reg == null || ( ForceMap != null && reg.Map != ForceMap ) ) - return false; + public bool Contains(Region reg) + { + if (reg == null || ForceMap != null && reg.Map != ForceMap) + return false; - return reg.IsPartOf( RegionName ); - } + return reg.IsPartOf(RegionName); + } - // Debug method - public void Validate() - { - bool found = false; + // Debug method + public void Validate() + { + bool found = false; - foreach ( Region r in Region.Regions ) - { - if ( r.Name == RegionName && ( ForceMap == null || r.Map == ForceMap ) ) - { - found = true; - break; - } - } + foreach (Region r in Region.Regions) + if (r.Name == RegionName && (ForceMap == null || r.Map == ForceMap)) + { + found = true; + break; + } - if ( !found ) - Console.WriteLine( "Warning: QuestArea region '{0}' does not exist (ForceMap = {1})", RegionName, ( ForceMap == null ) ? "-null-" : ForceMap.ToString() ); - } - } -} + if (!found) + Console.WriteLine("Warning: QuestArea region '{0}' does not exist (ForceMap = {1})", RegionName, + ForceMap == null ? "-null-" : ForceMap.ToString()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/QuesterNameAttribute.cs b/Scripts/Engines/MLQuests/QuesterNameAttribute.cs index 58e6f5692..4d9fbe38f 100644 --- a/Scripts/Engines/MLQuests/QuesterNameAttribute.cs +++ b/Scripts/Engines/MLQuests/QuesterNameAttribute.cs @@ -3,35 +3,35 @@ using System.Collections.Generic; namespace Server.Engines.MLQuests { - [AttributeUsage( AttributeTargets.Class )] - public class QuesterNameAttribute : Attribute - { - public string QuesterName { get; } + [AttributeUsage(AttributeTargets.Class)] + public class QuesterNameAttribute : Attribute + { + private static readonly Type m_Type = typeof(QuesterNameAttribute); + private static readonly Dictionary m_Cache = new Dictionary(); - public QuesterNameAttribute( string questerName ) - { - QuesterName = questerName; - } + public QuesterNameAttribute(string questerName) + { + QuesterName = questerName; + } - private static readonly Type m_Type = typeof( QuesterNameAttribute ); - private static readonly Dictionary m_Cache = new Dictionary(); + public string QuesterName{ get; } - public static string GetQuesterNameFor( Type t ) - { - if ( t == null ) - return ""; + public static string GetQuesterNameFor(Type t) + { + if (t == null) + return ""; - if (m_Cache.TryGetValue( t, out string result )) - return result; + if (m_Cache.TryGetValue(t, out string result)) + return result; - object[] attributes = t.GetCustomAttributes( m_Type, false ); + object[] attributes = t.GetCustomAttributes(m_Type, false); - if ( attributes.Length != 0 ) - result = ( (QuesterNameAttribute)attributes[0] ).QuesterName; - else - result = t.Name; + if (attributes.Length != 0) + result = ((QuesterNameAttribute)attributes[0]).QuesterName; + else + result = t.Name; - return ( m_Cache[t] = result ); - } - } -} + return m_Cache[t] = result; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Rewards/BaseReward.cs b/Scripts/Engines/MLQuests/Rewards/BaseReward.cs index dd63b78ef..a0a422386 100644 --- a/Scripts/Engines/MLQuests/Rewards/BaseReward.cs +++ b/Scripts/Engines/MLQuests/Rewards/BaseReward.cs @@ -1,25 +1,25 @@ -using Server.Mobiles; -using Server.Gumps; using System.Collections.Generic; +using Server.Gumps; +using Server.Mobiles; namespace Server.Engines.MLQuests.Rewards { - public abstract class BaseReward - { - public TextDefinition Name { get; set; } + public abstract class BaseReward + { + public BaseReward(TextDefinition name) + { + Name = name; + } - public BaseReward( TextDefinition name ) - { - Name = name; - } + public TextDefinition Name{ get; set; } - protected virtual int LabelHeight => 16; + protected virtual int LabelHeight => 16; - public void WriteToGump( Gump g, int x, ref int y ) - { - TextDefinition.AddHtmlText( g, x, y, 280, LabelHeight, Name, false, false, 0x15F90, 0xBDE784 ); - } + public void WriteToGump(Gump g, int x, ref int y) + { + TextDefinition.AddHtmlText(g, x, y, 280, LabelHeight, Name, false, false, 0x15F90, 0xBDE784); + } - public abstract void AddRewardItems( PlayerMobile pm, List rewards ); - } -} + public abstract void AddRewardItems(PlayerMobile pm, List rewards); + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Rewards/DummyReward.cs b/Scripts/Engines/MLQuests/Rewards/DummyReward.cs index 58c73ec6f..b60df6f0f 100644 --- a/Scripts/Engines/MLQuests/Rewards/DummyReward.cs +++ b/Scripts/Engines/MLQuests/Rewards/DummyReward.cs @@ -1,19 +1,19 @@ -using Server.Mobiles; using System.Collections.Generic; +using Server.Mobiles; namespace Server.Engines.MLQuests.Rewards { - public class DummyReward : BaseReward - { - public DummyReward( TextDefinition name ) - : base( name ) - { - } + public class DummyReward : BaseReward + { + public DummyReward(TextDefinition name) + : base(name) + { + } - protected override int LabelHeight => 180; + protected override int LabelHeight => 180; - public override void AddRewardItems( PlayerMobile pm, List rewards ) - { - } - } -} + public override void AddRewardItems(PlayerMobile pm, List rewards) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MLQuests/Rewards/ItemReward.cs b/Scripts/Engines/MLQuests/Rewards/ItemReward.cs index 46835b235..0f4cb50e8 100644 --- a/Scripts/Engines/MLQuests/Rewards/ItemReward.cs +++ b/Scripts/Engines/MLQuests/Rewards/ItemReward.cs @@ -5,86 +5,104 @@ using Server.Mobiles; namespace Server.Engines.MLQuests.Rewards { - public class ItemReward : BaseReward - { - public static readonly ItemReward SmallBagOfTrinkets = new ItemReward( 1072268, typeof( SmallBagOfTrinkets ) ); // A small bag of trinkets. - public static readonly ItemReward BagOfTrinkets = new ItemReward( 1072341, typeof( BagOfTrinkets ) ); // A bag of trinkets. - public static readonly ItemReward BagOfTreasure = new ItemReward( 1072583, typeof( BagOfTreasure ) ); // A bag of treasure. - public static readonly ItemReward LargeBagOfTreasure = new ItemReward( 1072706, typeof( LargeBagOfTreasure ) ); // A large bag of treasure. - public static readonly ItemReward Strongbox = new ItemReward( 1072584, typeof( RewardStrongbox ) ); // A strongbox. + public class ItemReward : BaseReward + { + public static readonly ItemReward + SmallBagOfTrinkets = new ItemReward(1072268, typeof(SmallBagOfTrinkets)); // A small bag of trinkets. - public static readonly ItemReward TailorSatchel = new ItemReward( 1074282, typeof( TailorSatchel ) ); // Craftsman's Satchel - public static readonly ItemReward BlacksmithSatchel = new ItemReward( 1074282, typeof( BlacksmithSatchel ) ); // Craftsman's Satchel - public static readonly ItemReward FletchingSatchel = new ItemReward( 1074282, typeof( FletchingSatchel ) ); // Craftsman's Satchel - public static readonly ItemReward CarpentrySatchel = new ItemReward( 1074282, typeof( CarpentrySatchel ) ); // Craftsman's Satchel - public static readonly ItemReward TinkerSatchel = new ItemReward( 1074282, typeof( TinkerSatchel ) ); // Craftsman's Satchel + public static readonly ItemReward + BagOfTrinkets = new ItemReward(1072341, typeof(BagOfTrinkets)); // A bag of trinkets. - private Type m_Type; - private int m_Amount; + public static readonly ItemReward + BagOfTreasure = new ItemReward(1072583, typeof(BagOfTreasure)); // A bag of treasure. - public ItemReward() - : this( null, null ) - { - } + public static readonly ItemReward + LargeBagOfTreasure = new ItemReward(1072706, typeof(LargeBagOfTreasure)); // A large bag of treasure. - public ItemReward( TextDefinition name, Type type ) - : this( name, type, 1 ) - { - } + public static readonly ItemReward Strongbox = new ItemReward(1072584, typeof(RewardStrongbox)); // A strongbox. - public ItemReward( TextDefinition name, Type type, int amount ) - : base( name ) - { - m_Type = type; - m_Amount = amount; - } + public static readonly ItemReward + TailorSatchel = new ItemReward(1074282, typeof(TailorSatchel)); // Craftsman's Satchel - public virtual Item CreateItem() - { - Item spawnedItem = null; + public static readonly ItemReward + BlacksmithSatchel = new ItemReward(1074282, typeof(BlacksmithSatchel)); // Craftsman's Satchel - try - { - spawnedItem = Activator.CreateInstance( m_Type ) as Item; - } - catch ( Exception e ) - { - if ( MLQuestSystem.Debug ) - Console.WriteLine( "WARNING: ItemReward.CreateItem failed for {0}: {1}", m_Type, e ); - } + public static readonly ItemReward + FletchingSatchel = new ItemReward(1074282, typeof(FletchingSatchel)); // Craftsman's Satchel - return spawnedItem; - } + public static readonly ItemReward + CarpentrySatchel = new ItemReward(1074282, typeof(CarpentrySatchel)); // Craftsman's Satchel - public override void AddRewardItems( PlayerMobile pm, List rewards ) - { - Item reward = CreateItem(); + public static readonly ItemReward + TinkerSatchel = new ItemReward(1074282, typeof(TinkerSatchel)); // Craftsman's Satchel - if ( reward == null ) - return; + private int m_Amount; - if ( reward.Stackable ) - { - if ( m_Amount > 1 ) - reward.Amount = m_Amount; + private Type m_Type; - rewards.Add( reward ); - } - else - { - for ( int i = 0; i < m_Amount; ++i ) - { - rewards.Add( reward ); + public ItemReward() + : this(null, null) + { + } - if ( i < m_Amount - 1 ) - { - reward = CreateItem(); + public ItemReward(TextDefinition name, Type type) + : this(name, type, 1) + { + } - if ( reward == null ) - return; - } - } - } - } - } -} + public ItemReward(TextDefinition name, Type type, int amount) + : base(name) + { + m_Type = type; + m_Amount = amount; + } + + public virtual Item CreateItem() + { + Item spawnedItem = null; + + try + { + spawnedItem = Activator.CreateInstance(m_Type) as Item; + } + catch (Exception e) + { + if (MLQuestSystem.Debug) + Console.WriteLine("WARNING: ItemReward.CreateItem failed for {0}: {1}", m_Type, e); + } + + return spawnedItem; + } + + public override void AddRewardItems(PlayerMobile pm, List rewards) + { + Item reward = CreateItem(); + + if (reward == null) + return; + + if (reward.Stackable) + { + if (m_Amount > 1) + reward.Amount = m_Amount; + + rewards.Add(reward); + } + else + { + for (int i = 0; i < m_Amount; ++i) + { + rewards.Add(reward); + + if (i < m_Amount - 1) + { + reward = CreateItem(); + + if (reward == null) + return; + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MyRunUO/Config.cs b/Scripts/Engines/MyRunUO/Config.cs index 5f754b8bf..51bd3896a 100644 --- a/Scripts/Engines/MyRunUO/Config.cs +++ b/Scripts/Engines/MyRunUO/Config.cs @@ -4,48 +4,49 @@ using System.Threading; namespace Server.Engines.MyRunUO { - public class Config - { - // Is MyRunUO enabled? - public static bool Enabled = false; + public class Config + { + // Details required for database connection string + public const string DatabaseDriver = "{MySQL ODBC 5.2w Driver}"; + public const string DatabaseServer = "localhost"; + public const string DatabaseName = "MyRunUO"; + public const string DatabaseUserID = "username"; - // Details required for database connection string - public const string DatabaseDriver = "{MySQL ODBC 5.2w Driver}"; - public const string DatabaseServer = "localhost"; - public const string DatabaseName = "MyRunUO"; - public const string DatabaseUserID = "username"; - public const string DatabasePassword = "password"; + public const string DatabasePassword = "password"; - // Should the database use transactions? This is recommended - public static bool UseTransactions = true; + // Is MyRunUO enabled? + public static bool Enabled = false; - // Use optimized table loading techniques? (LOAD DATA INFILE) - public static bool LoadDataInFile = true; + // Should the database use transactions? This is recommended + public static bool UseTransactions = true; - // This must be enabled if the database server is on a remote machine. - public static bool DatabaseNonLocal = ( DatabaseServer != "localhost" ); + // Use optimized table loading techniques? (LOAD DATA INFILE) + public static bool LoadDataInFile = true; - // Text encoding used - public static Encoding EncodingIO = Encoding.ASCII; + // This must be enabled if the database server is on a remote machine. + public static bool DatabaseNonLocal = DatabaseServer != "localhost"; - // Database communication is done in a separate thread. This value is the 'priority' of that thread, or, how much CPU it will try to use - public static ThreadPriority DatabaseThreadPriority = ThreadPriority.BelowNormal; + // Text encoding used + public static Encoding EncodingIO = Encoding.ASCII; - // Any character with an AccessLevel equal to or higher than this will not be displayed - public static AccessLevel HiddenAccessLevel = AccessLevel.Counselor; + // Database communication is done in a separate thread. This value is the 'priority' of that thread, or, how much CPU it will try to use + public static ThreadPriority DatabaseThreadPriority = ThreadPriority.BelowNormal; - // Export character database every 30 minutes - public static TimeSpan CharacterUpdateInterval = TimeSpan.FromMinutes( 30.0 ); + // Any character with an AccessLevel equal to or higher than this will not be displayed + public static AccessLevel HiddenAccessLevel = AccessLevel.Counselor; - // Export online list database every 5 minutes - public static TimeSpan StatusUpdateInterval = TimeSpan.FromMinutes( 5.0 ); + // Export character database every 30 minutes + public static TimeSpan CharacterUpdateInterval = TimeSpan.FromMinutes(30.0); - public static string CompileConnectionString() - { - string connectionString = - $"DRIVER={DatabaseDriver};SERVER={DatabaseServer};DATABASE={DatabaseName};UID={DatabaseUserID};PASSWORD={DatabasePassword};"; + // Export online list database every 5 minutes + public static TimeSpan StatusUpdateInterval = TimeSpan.FromMinutes(5.0); - return connectionString; - } - } + public static string CompileConnectionString() + { + string connectionString = + $"DRIVER={DatabaseDriver};SERVER={DatabaseServer};DATABASE={DatabaseName};UID={DatabaseUserID};PASSWORD={DatabasePassword};"; + + return connectionString; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/MyRunUO/DatabaseCommandQueue.cs b/Scripts/Engines/MyRunUO/DatabaseCommandQueue.cs index e66f4d21e..e5f07a95e 100644 --- a/Scripts/Engines/MyRunUO/DatabaseCommandQueue.cs +++ b/Scripts/Engines/MyRunUO/DatabaseCommandQueue.cs @@ -1,206 +1,243 @@ using System; -using System.Threading; using System.Collections; using System.Data.Odbc; +using System.Threading; namespace Server.Engines.MyRunUO { - public class DatabaseCommandQueue - { - private Queue m_Queue; - private ManualResetEvent m_Sync; - private Thread m_Thread; + public class DatabaseCommandQueue + { + private string m_CompletionString; + private string m_ConnectionString; + private Queue m_Queue; + private ManualResetEvent m_Sync; + private Thread m_Thread; - private string m_CompletionString; - private string m_ConnectionString; + public DatabaseCommandQueue(string completionString, string threadName) : this(Config.CompileConnectionString(), + completionString, threadName) + { + } - public bool HasCompleted { get; private set; } + public DatabaseCommandQueue(string connectionString, string completionString, string threadName) + { + m_CompletionString = completionString; + m_ConnectionString = connectionString; - public void Enqueue( object obj ) - { - lock ( m_Queue.SyncRoot ) - { - m_Queue.Enqueue( obj ); - try{ m_Sync.Set(); } - catch{} - } - } + m_Queue = Queue.Synchronized(new Queue()); - public DatabaseCommandQueue( string completionString, string threadName ) : this( Config.CompileConnectionString(), completionString, threadName ) - { - } + m_Queue.Enqueue(null); // signal connect - public DatabaseCommandQueue( string connectionString, string completionString, string threadName ) - { - m_CompletionString = completionString; - m_ConnectionString = connectionString; + /*m_Queue.Enqueue( "DELETE FROM myrunuo_characters" ); + m_Queue.Enqueue( "DELETE FROM myrunuo_characters_layers" ); + m_Queue.Enqueue( "DELETE FROM myrunuo_characters_skills" ); + m_Queue.Enqueue( "DELETE FROM myrunuo_guilds" ); + m_Queue.Enqueue( "DELETE FROM myrunuo_guilds_wars" );*/ - m_Queue = Queue.Synchronized( new Queue() ); + m_Sync = new ManualResetEvent(true); - m_Queue.Enqueue( null ); // signal connect + m_Thread = new Thread(Thread_Start); + m_Thread.Name = threadName; //"MyRunUO Database Command Queue"; + m_Thread.Priority = Config.DatabaseThreadPriority; + m_Thread.Start(); + } - /*m_Queue.Enqueue( "DELETE FROM myrunuo_characters" ); - m_Queue.Enqueue( "DELETE FROM myrunuo_characters_layers" ); - m_Queue.Enqueue( "DELETE FROM myrunuo_characters_skills" ); - m_Queue.Enqueue( "DELETE FROM myrunuo_guilds" ); - m_Queue.Enqueue( "DELETE FROM myrunuo_guilds_wars" );*/ + public bool HasCompleted{ get; private set; } - m_Sync = new ManualResetEvent( true ); + public void Enqueue(object obj) + { + lock (m_Queue.SyncRoot) + { + m_Queue.Enqueue(obj); + try + { + m_Sync.Set(); + } + catch + { + } + } + } - m_Thread = new Thread( Thread_Start ); - m_Thread.Name = threadName;//"MyRunUO Database Command Queue"; - m_Thread.Priority = Config.DatabaseThreadPriority; - m_Thread.Start(); - } + private void Thread_Start() + { + bool connected = false; - private void Thread_Start() - { - bool connected = false; + OdbcConnection connection = null; + OdbcCommand command = null; + OdbcTransaction transact = null; - OdbcConnection connection = null; - OdbcCommand command = null; - OdbcTransaction transact = null; + DateTime start = DateTime.UtcNow; - DateTime start = DateTime.UtcNow; + bool shouldWriteException = true; - bool shouldWriteException = true; + while (true) + { + m_Sync.WaitOne(); - while ( true ) - { - m_Sync.WaitOne(); + while (m_Queue.Count > 0) + try + { + object obj = m_Queue.Dequeue(); - while ( m_Queue.Count > 0 ) - { - try - { - object obj = m_Queue.Dequeue(); + if (obj == null) + { + if (connected) + { + if (transact != null) + try + { + transact.Commit(); + } + catch (Exception commitException) + { + Console.WriteLine("MyRunUO: Exception caught when committing transaction"); + Console.WriteLine(commitException); - if ( obj == null ) - { - if ( connected ) - { - if ( transact != null ) - { - try{ transact.Commit(); } - catch ( Exception commitException ) - { - Console.WriteLine( "MyRunUO: Exception caught when committing transaction" ); - Console.WriteLine( commitException ); + try + { + transact.Rollback(); + Console.WriteLine("MyRunUO: Transaction has been rolled back"); + } + catch (Exception rollbackException) + { + Console.WriteLine("MyRunUO: Exception caught when rolling back transaction"); + Console.WriteLine(rollbackException); + } + } - try - { - transact.Rollback(); - Console.WriteLine( "MyRunUO: Transaction has been rolled back" ); - } - catch ( Exception rollbackException ) - { - Console.WriteLine( "MyRunUO: Exception caught when rolling back transaction" ); - Console.WriteLine( rollbackException ); - } - } - } + try + { + connection.Close(); + } + catch + { + } - try{ connection.Close(); } - catch{} + try + { + connection.Dispose(); + } + catch + { + } - try{ connection.Dispose(); } - catch{} + try + { + command.Dispose(); + } + catch + { + } - try{ command.Dispose(); } - catch{} + try + { + m_Sync.Close(); + } + catch + { + } - try{ m_Sync.Close(); } - catch{} + Console.WriteLine(m_CompletionString, (DateTime.UtcNow - start).TotalSeconds); + HasCompleted = true; - Console.WriteLine( m_CompletionString, (DateTime.UtcNow - start).TotalSeconds ); - HasCompleted = true; + return; + } - return; - } + try + { + connected = true; + connection = new OdbcConnection(m_ConnectionString); + connection.Open(); + command = connection.CreateCommand(); - try - { - connected = true; - connection = new OdbcConnection( m_ConnectionString ); - connection.Open(); - command = connection.CreateCommand(); + if (Config.UseTransactions) + { + transact = connection.BeginTransaction(); + command.Transaction = transact; + } + } + catch (Exception e) + { + try + { + transact?.Rollback(); + } + catch + { + } - if ( Config.UseTransactions ) - { - transact = connection.BeginTransaction(); - command.Transaction = transact; - } - } - catch ( Exception e ) - { - try - { - transact?.Rollback(); - } - catch{} + try + { + connection?.Close(); + } + catch + { + } - try - { - connection?.Close(); - } - catch{} + try + { + connection?.Dispose(); + } + catch + { + } - try - { - connection?.Dispose(); - } - catch{} + try + { + command?.Dispose(); + } + catch + { + } - try - { - command?.Dispose(); - } - catch{} + try + { + m_Sync.Close(); + } + catch + { + } - try{ m_Sync.Close(); } - catch{} + Console.WriteLine("MyRunUO: Unable to connect to the database"); + Console.WriteLine(e); + HasCompleted = true; + return; + } + } + else if (obj is string s) + { + command.CommandText = s; + command.ExecuteNonQuery(); + } + else + { + string[] parms = (string[])obj; - Console.WriteLine( "MyRunUO: Unable to connect to the database" ); - Console.WriteLine( e ); - HasCompleted = true; - return; - } - } - else if ( obj is string s ) - { - command.CommandText = s; - command.ExecuteNonQuery(); - } - else - { - string[] parms = (string[])obj; + command.CommandText = parms[0]; - command.CommandText = parms[0]; + if (command.ExecuteScalar() == null) + { + command.CommandText = parms[1]; + command.ExecuteNonQuery(); + } + } + } + catch (Exception e) + { + if (shouldWriteException) + { + Console.WriteLine("MyRunUO: Exception caught in database thread"); + Console.WriteLine(e); + shouldWriteException = false; + } + } - if ( command.ExecuteScalar() == null ) - { - command.CommandText = parms[1]; - command.ExecuteNonQuery(); - } - } - } - catch ( Exception e ) - { - if ( shouldWriteException ) - { - Console.WriteLine( "MyRunUO: Exception caught in database thread" ); - Console.WriteLine( e ); - shouldWriteException = false; - } - } - } - - lock ( m_Queue.SyncRoot ) - { - if ( m_Queue.Count == 0 ) - m_Sync.Reset(); - } - } - } - } -} + lock (m_Queue.SyncRoot) + { + if (m_Queue.Count == 0) + m_Sync.Reset(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MyRunUO/LayerComparer.cs b/Scripts/Engines/MyRunUO/LayerComparer.cs index 8130456a4..492361586 100644 --- a/Scripts/Engines/MyRunUO/LayerComparer.cs +++ b/Scripts/Engines/MyRunUO/LayerComparer.cs @@ -2,89 +2,86 @@ using System.Collections; namespace Server.Engines.MyRunUO { - public class LayerComparer : IComparer - { - private static Layer PlateArms = (Layer)255; - private static Layer ChainTunic = (Layer)254; - private static Layer LeatherShorts = (Layer)253; + public class LayerComparer : IComparer + { + private static Layer PlateArms = (Layer)255; + private static Layer ChainTunic = (Layer)254; + private static Layer LeatherShorts = (Layer)253; - private static Layer[] m_DesiredLayerOrder = { - Layer.Cloak, - Layer.Bracelet, - Layer.Ring, - Layer.Shirt, - Layer.Pants, - Layer.InnerLegs, - Layer.Shoes, - LeatherShorts, - Layer.Arms, - Layer.InnerTorso, - LeatherShorts, - PlateArms, - Layer.MiddleTorso, - Layer.OuterLegs, - Layer.Neck, - Layer.Waist, - Layer.Gloves, - Layer.OuterTorso, - Layer.OneHanded, - Layer.TwoHanded, - Layer.FacialHair, - Layer.Hair, - Layer.Helm, - Layer.Talisman - }; + private static Layer[] m_DesiredLayerOrder = + { + Layer.Cloak, + Layer.Bracelet, + Layer.Ring, + Layer.Shirt, + Layer.Pants, + Layer.InnerLegs, + Layer.Shoes, + LeatherShorts, + Layer.Arms, + Layer.InnerTorso, + LeatherShorts, + PlateArms, + Layer.MiddleTorso, + Layer.OuterLegs, + Layer.Neck, + Layer.Waist, + Layer.Gloves, + Layer.OuterTorso, + Layer.OneHanded, + Layer.TwoHanded, + Layer.FacialHair, + Layer.Hair, + Layer.Helm, + Layer.Talisman + }; - public static int[] TranslationTable { get; } + public static readonly IComparer Instance = new LayerComparer(); - static LayerComparer() - { - TranslationTable = new int[256]; + static LayerComparer() + { + TranslationTable = new int[256]; - for ( int i = 0; i < m_DesiredLayerOrder.Length; ++i ) - TranslationTable[(int)m_DesiredLayerOrder[i]] = m_DesiredLayerOrder.Length - i; - } + for (int i = 0; i < m_DesiredLayerOrder.Length; ++i) + TranslationTable[(int)m_DesiredLayerOrder[i]] = m_DesiredLayerOrder.Length - i; + } - public static bool IsValid( Item item ) - { - return ( TranslationTable[(int)item.Layer] > 0 ); - } + public static int[] TranslationTable{ get; } - public static readonly IComparer Instance = new LayerComparer(); + public int Compare(object x, object y) + { + Item a = (Item)x; + Item b = (Item)y; - public LayerComparer() - { - } + Layer aLayer = a.Layer; + Layer bLayer = b.Layer; - public Layer Fix( int itemID, Layer oldLayer ) - { - if ( itemID == 0x1410 || itemID == 0x1417 ) // platemail arms - return PlateArms; + aLayer = Fix(a.ItemID, aLayer); + bLayer = Fix(b.ItemID, bLayer); - if ( itemID == 0x13BF || itemID == 0x13C4 ) // chainmail tunic - return ChainTunic; + return TranslationTable[(int)bLayer] - TranslationTable[(int)aLayer]; + } - if ( itemID == 0x1C08 || itemID == 0x1C09 ) // leather skirt - return LeatherShorts; + public static bool IsValid(Item item) + { + return TranslationTable[(int)item.Layer] > 0; + } - if ( itemID == 0x1C00 || itemID == 0x1C01 ) // leather shorts - return LeatherShorts; + public Layer Fix(int itemID, Layer oldLayer) + { + if (itemID == 0x1410 || itemID == 0x1417) // platemail arms + return PlateArms; - return oldLayer; - } + if (itemID == 0x13BF || itemID == 0x13C4) // chainmail tunic + return ChainTunic; - public int Compare( object x, object y ) - { - Item a = (Item)x; - Item b = (Item)y; + if (itemID == 0x1C08 || itemID == 0x1C09) // leather skirt + return LeatherShorts; - Layer aLayer = a.Layer; - Layer bLayer = b.Layer; + if (itemID == 0x1C00 || itemID == 0x1C01) // leather shorts + return LeatherShorts; - aLayer = Fix( a.ItemID, aLayer ); - bLayer = Fix( b.ItemID, bLayer ); - - return TranslationTable[(int)bLayer] - TranslationTable[(int)aLayer]; - } - } + return oldLayer; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/MyRunUO/MyRunUO.cs b/Scripts/Engines/MyRunUO/MyRunUO.cs index 5db46b754..ba8cf42f9 100644 --- a/Scripts/Engines/MyRunUO/MyRunUO.cs +++ b/Scripts/Engines/MyRunUO/MyRunUO.cs @@ -1,674 +1,724 @@ using System; -using System.IO; -using System.Text; using System.Collections; using System.Collections.Generic; -using Server.Misc; -using Server.Guilds; -using Server.Mobiles; +using System.IO; +using System.Text; using Server.Accounting; using Server.Commands; +using Server.Guilds; +using Server.Misc; +using Server.Mobiles; namespace Server.Engines.MyRunUO { - public class MyRunUO : Timer - { - private static double CpuInterval = 0.1; // Processor runs every 0.1 seconds - private static double CpuPercent = 0.25; // Processor runs for 25% of Interval, or ~25ms. This should take around 25% cpu - - public static void Initialize() - { - if ( Config.Enabled ) - { - DelayCall( TimeSpan.FromSeconds( 10.0 ), Config.CharacterUpdateInterval, Begin ); - - CommandSystem.Register( "InitMyRunUO", AccessLevel.Administrator, InitMyRunUO_OnCommand ); - CommandSystem.Register( "UpdateMyRunUO", AccessLevel.Administrator, UpdateMyRunUO_OnCommand ); - - CommandSystem.Register( "PublicChar", AccessLevel.Player, PublicChar_OnCommand ); - CommandSystem.Register( "PrivateChar", AccessLevel.Player, PrivateChar_OnCommand ); - } - } - - [Usage( "PublicChar" )] - [Description( "Enables showing extended character stats and skills in MyRunUO." )] - public static void PublicChar_OnCommand( CommandEventArgs e ) - { - if ( e.Mobile is PlayerMobile pm ) - { - if ( pm.PublicMyRunUO ) - { - pm.SendMessage( "You have already chosen to show your skills and stats." ); - } - else - { - pm.PublicMyRunUO = true; - pm.SendMessage( "All of your skills and stats will now be shown publicly in MyRunUO." ); - } - } - } - - [Usage( "PrivateChar" )] - [Description( "Disables showing extended character stats and skills in MyRunUO." )] - public static void PrivateChar_OnCommand( CommandEventArgs e ) - { - if ( e.Mobile is PlayerMobile pm ) - { - if ( !pm.PublicMyRunUO ) - { - pm.SendMessage( "You have already chosen to not show your skills and stats." ); - } - else - { - pm.PublicMyRunUO = false; - pm.SendMessage( "Only a general level of your top three skills will be shown in MyRunUO." ); - } - } - } - - [Usage( "InitMyRunUO" )] - [Description( "Initially creates the database schema." )] - public static void InitMyRunUO_OnCommand( CommandEventArgs e ) - { - if ( m_Command != null && m_Command.HasCompleted ) - { - TableCreation(); - e.Mobile.SendMessage( "MyRunUO table creation process has been started." ); - } - else - { - e.Mobile.SendMessage( "MyRunUO table creation is already running." ); - } - } - - public static void TableCreation() - { - if ( m_Command != null && !m_Command.HasCompleted ) - return; - // DateTime start = DateTime.Now; - Console.WriteLine( "MyRunUO: Creating tables" ); - try - { - m_Command = new DatabaseCommandQueue( "MyRunUO: Tables created in {0:F1} seconds", "MyRunUO Status Database Thread" ); - m_Command.Enqueue( "CREATE TABLE IF NOT EXISTS `myrunuo_characters` ( `char_id` int(10) unsigned NOT NULL, `char_name` varchar(255) NOT NULL, `char_str` smallint(3) unsigned NOT NULL, `char_dex` smallint(3) unsigned NOT NULL, `char_int` smallint(3) unsigned NOT NULL, `char_female` tinyint(1) NOT NULL, `char_counts` smallint(6) NOT NULL, `char_guild` varchar(255) DEFAULT NULL, `char_guildtitle` varchar(255) DEFAULT NULL, `char_nototitle` varchar(255) DEFAULT NULL, `char_bodyhue` smallint(5) unsigned DEFAULT NULL, `char_public` tinyint(1) NOT NULL, PRIMARY KEY (`char_id`))" ); - m_Command.Enqueue( "CREATE TABLE IF NOT EXISTS `myrunuo_characters_layers` ( `char_id` int(10) unsigned NOT NULL, `layer_id` tinyint(3) unsigned NOT NULL, `item_id` smallint(5) unsigned NOT NULL, `item_hue` smallint(5) unsigned NOT NULL, PRIMARY KEY (`char_id`,`layer_id`))" ); - m_Command.Enqueue( "CREATE TABLE IF NOT EXISTS `myrunuo_characters_skills` ( `char_id` int(10) unsigned NOT NULL, `skill_id` tinyint(3) NOT NULL, `skill_value` smallint(5) unsigned NOT NULL, PRIMARY KEY (`char_id`,`skill_id`), KEY `skill_id` (`skill_id`))" ); - m_Command.Enqueue( "CREATE TABLE IF NOT EXISTS `myrunuo_guilds` ( `guild_id` smallint(5) unsigned NOT NULL, `guild_name` varchar(255) NOT NULL, `guild_abbreviation` varchar(8) DEFAULT NULL, `guild_website` varchar(255) DEFAULT NULL, `guild_charter` varchar(255) DEFAULT NULL, `guild_type` varchar(8) NOT NULL, `guild_wars` smallint(5) unsigned NOT NULL, `guild_members` smallint(5) unsigned NOT NULL, `guild_master` int(10) unsigned NOT NULL, PRIMARY KEY (`guild_id`))" ); - m_Command.Enqueue( "CREATE TABLE IF NOT EXISTS `myrunuo_guilds_wars` ( `guild_1` smallint(5) unsigned NOT NULL DEFAULT '0', `guild_2` smallint(5) unsigned NOT NULL DEFAULT '0', PRIMARY KEY (`guild_1`,`guild_2`), KEY `guild1` (`guild_1`), KEY `guild2` (`guild_2`))" ); - m_Command.Enqueue( "CREATE TABLE IF NOT EXISTS `myrunuo_status` ( `char_id` int(10) NOT NULL, PRIMARY KEY (`char_id`))" ); - } - catch ( Exception e ) - { - Console.WriteLine( "MyRunUO: Error creating tables." ); - Console.WriteLine( e ); - } - - m_Command?.Enqueue( null ); - } - - [Usage( "UpdateMyRunUO" )] - [Description( "Starts the process of updating the MyRunUO character and guild database." )] - public static void UpdateMyRunUO_OnCommand( CommandEventArgs e ) - { - if ( m_Command != null && m_Command.HasCompleted ) - m_Command = null; - - if ( m_Timer == null && m_Command == null ) - { - Begin(); - e.Mobile.SendMessage( "MyRunUO update process has been started." ); - } - else - { - e.Mobile.SendMessage( "MyRunUO database is already being updated." ); - } - } - - public static void Begin() - { - if ( m_Command != null && m_Command.HasCompleted ) - m_Command = null; - - if ( m_Timer != null || m_Command != null ) - return; - - m_Timer = new MyRunUO(); - m_Timer.Start(); - } - - private static Timer m_Timer; - - private Stage m_Stage; - private ArrayList m_List; - private List m_Collecting; - private int m_Index; - - private static DatabaseCommandQueue m_Command; - - private string m_SkillsPath; - private string m_LayersPath; - private string m_MobilesPath; - - private StreamWriter m_OpSkills; - private StreamWriter m_OpLayers; - private StreamWriter m_OpMobiles; - - private DateTime m_StartTime; - - public MyRunUO() : base( TimeSpan.FromSeconds( CpuInterval ), TimeSpan.FromSeconds( CpuInterval ) ) - { - m_List = new ArrayList(); - m_Collecting = new List(); - - m_StartTime = DateTime.UtcNow; - Console.WriteLine( "MyRunUO: Updating character database" ); - } - - protected override void OnTick() - { - bool shouldExit = false; - - try - { - shouldExit = Process( DateTime.UtcNow + TimeSpan.FromSeconds( CpuInterval * CpuPercent ) ); - - if ( shouldExit ) - Console.WriteLine( "MyRunUO: Database statements compiled in {0:F2} seconds", (DateTime.UtcNow - m_StartTime).TotalSeconds ); - } - catch ( Exception e ) - { - Console.WriteLine( "MyRunUO: {0}: Exception cought while processing", m_Stage ); - Console.WriteLine( e ); - shouldExit = true; - } - - if ( shouldExit ) - { - m_Command.Enqueue( null ); - - Stop(); - m_Timer = null; - } - } - - private enum Stage - { - CollectingMobiles, - DumpingMobiles, - CollectingGuilds, - DumpingGuilds, - Complete - } - - public bool Process( DateTime endTime ) - { - switch ( m_Stage ) - { - case Stage.CollectingMobiles: CollectMobiles( endTime ); break; - case Stage.DumpingMobiles: DumpMobiles( endTime ); break; - case Stage.CollectingGuilds: CollectGuilds( endTime ); break; - case Stage.DumpingGuilds: DumpGuilds( endTime ); break; - } - - return ( m_Stage == Stage.Complete ); - } - - private static ArrayList m_MobilesToUpdate = new ArrayList(); - - public static void QueueMobileUpdate( Mobile m ) - { - if ( !Config.Enabled || Config.LoadDataInFile ) - return; - - m_MobilesToUpdate.Add( m ); - } - - public void CollectMobiles( DateTime endTime ) - { - if ( Config.LoadDataInFile ) - { - if ( m_Index == 0 ) - m_Collecting.AddRange( Accounts.GetAccounts() ); - - for ( int i = m_Index; i < m_Collecting.Count; ++i ) - { - IAccount acct = m_Collecting[i]; - - for ( int j = 0; j < acct.Length; ++j ) - { - Mobile mob = acct[j]; - - if ( mob != null && mob.AccessLevel < Config.HiddenAccessLevel ) - m_List.Add( mob ); - } - - ++m_Index; - - if ( DateTime.UtcNow >= endTime ) - break; - } - - if ( m_Index == m_Collecting.Count ) - { - m_Collecting = new List(); - m_Stage = Stage.DumpingMobiles; - m_Index = 0; - } - } - else - { - m_List = m_MobilesToUpdate; - m_MobilesToUpdate = new ArrayList(); - m_Stage = Stage.DumpingMobiles; - m_Index = 0; - } - } - - public void CheckConnection() - { - if ( m_Command == null ) - { - m_Command = new DatabaseCommandQueue( "MyRunUO: Characeter database updated in {0:F1} seconds", "MyRunUO Character Database Thread" ); - - if ( Config.LoadDataInFile ) - { - m_OpSkills = GetUniqueWriter( "skills", out m_SkillsPath ); - m_OpLayers = GetUniqueWriter( "layers", out m_LayersPath ); - m_OpMobiles = GetUniqueWriter( "mobiles", out m_MobilesPath ); - - m_Command.Enqueue( "TRUNCATE TABLE myrunuo_characters" ); - m_Command.Enqueue( "TRUNCATE TABLE myrunuo_characters_layers" ); - m_Command.Enqueue( "TRUNCATE TABLE myrunuo_characters_skills" ); - } - - m_Command.Enqueue( "TRUNCATE TABLE myrunuo_guilds" ); - m_Command.Enqueue( "TRUNCATE TABLE myrunuo_guilds_wars" ); - } - } - - public void ExecuteNonQuery( string text ) - { - m_Command.Enqueue( text ); - } - - public void ExecuteNonQuery( string format, params string[] args ) - { - ExecuteNonQuery( string.Format( format, args ) ); - } - - public void ExecuteNonQueryIfNull( string select, string insert ) - { - m_Command.Enqueue( new[]{ select, insert } ); - } - - private void AppendCharEntity( string input, int charIndex, ref StringBuilder sb, char c ) - { - if ( sb == null ) - { - if ( charIndex > 0 ) - sb = new StringBuilder( input, 0, charIndex, input.Length + 20 ); - else - sb = new StringBuilder( input.Length + 20 ); - } - - sb.Append( "&#" ); - sb.Append( (int)c ); - sb.Append( ";" ); - } - - private void AppendEntityRef( string input, int charIndex, ref StringBuilder sb, string ent ) - { - if ( sb == null ) - { - if ( charIndex > 0 ) - sb = new StringBuilder( input, 0, charIndex, input.Length + 20 ); - else - sb = new StringBuilder( input.Length + 20 ); - } - - sb.Append( ent ); - } - - private string SafeString( string input ) - { - if ( input == null ) - return ""; - - StringBuilder sb = null; - - for ( int i = 0; i < input.Length; ++i ) - { - char c = input[i]; - - if ( c < 0x20 || c >= 0x7F ) - { - AppendCharEntity( input, i, ref sb, c ); - } - else - { - switch ( c ) - { - case '&': AppendEntityRef( input, i, ref sb, "&" ); break; - case '>': AppendEntityRef( input, i, ref sb, ">" ); break; - case '<': AppendEntityRef( input, i, ref sb, "<" ); break; - case '"': AppendEntityRef( input, i, ref sb, """ ); break; - case '\'': - case ':': - case '/': - case '\\': AppendCharEntity( input, i, ref sb, c ); break; - default: - { - sb?.Append( c ); - - break; - } - } - } - } - - if ( sb != null ) - return sb.ToString(); - - return input; - } - - public const char LineStart = '\"'; - public const string EntrySep = "\",\""; - public const string LineEnd = "\"\n"; - - public void InsertMobile( Mobile mob ) - { - string guildTitle = mob.GuildTitle; - - if ( guildTitle == null || (guildTitle = guildTitle.Trim()).Length == 0 ) - guildTitle = "NULL"; - else - guildTitle = SafeString( guildTitle ); - - string notoTitle = SafeString( Titles.ComputeTitle( null, mob ) ); - string female = ( mob.Female ? "1" : "0" ); - - bool pubBool = mob is PlayerMobile mobile && mobile.PublicMyRunUO; - - string pubString = ( pubBool ? "1" : "0" ); - - string guildId = ( mob.Guild == null ? "NULL" : mob.Guild.Id.ToString() ); - - if ( Config.LoadDataInFile ) - { - m_OpMobiles.Write( LineStart ); - m_OpMobiles.Write( mob.Serial.Value ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( SafeString( mob.Name ) ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( mob.RawStr ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( mob.RawDex ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( mob.RawInt ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( female ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( mob.Kills ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( guildId ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( guildTitle ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( notoTitle ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( mob.Hue ); - m_OpMobiles.Write( EntrySep ); - m_OpMobiles.Write( pubString ); - m_OpMobiles.Write( LineEnd ); - } - else - { - ExecuteNonQuery( "INSERT INTO myrunuo_characters (char_id, char_name, char_str, char_dex, char_int, char_female, char_counts, char_guild, char_guildtitle, char_nototitle, char_bodyhue, char_public ) VALUES ({0}, '{1}', {2}, {3}, {4}, {5}, {6}, {7}, {8}, '{9}', {10}, {11})", mob.Serial.Value.ToString(), SafeString( mob.Name ), mob.RawStr.ToString(), mob.RawDex.ToString(), mob.RawInt.ToString(), female, mob.Kills.ToString(), guildId, guildTitle, notoTitle, mob.Hue.ToString(), pubString ); - } - } - - public void InsertSkills( Mobile mob ) - { - Skills skills = mob.Skills; - string serial = mob.Serial.Value.ToString(); - - for ( int i = 0; i < skills.Length; ++i ) - { - Skill skill = skills[i]; - - if ( skill.BaseFixedPoint > 0 ) - { - if ( Config.LoadDataInFile ) - { - m_OpSkills.Write( LineStart ); - m_OpSkills.Write( serial ); - m_OpSkills.Write( EntrySep ); - m_OpSkills.Write( i ); - m_OpSkills.Write( EntrySep ); - m_OpSkills.Write( skill.BaseFixedPoint ); - m_OpSkills.Write( LineEnd ); - } - else - { - ExecuteNonQuery( "INSERT INTO myrunuo_characters_skills (char_id, skill_id, skill_value) VALUES ({0}, {1}, {2})", serial, i.ToString(), skill.BaseFixedPoint.ToString() ); - } - } - } - } - - private ArrayList m_Items = new ArrayList(); - - private void InsertItem( string serial, int index, int itemID, int hue ) - { - if ( Config.LoadDataInFile ) - { - m_OpLayers.Write( LineStart ); - m_OpLayers.Write( serial ); - m_OpLayers.Write( EntrySep ); - m_OpLayers.Write( index ); - m_OpLayers.Write( EntrySep ); - m_OpLayers.Write( itemID ); - m_OpLayers.Write( EntrySep ); - m_OpLayers.Write( hue ); - m_OpLayers.Write( LineEnd ); - } - else - { - ExecuteNonQuery( "INSERT INTO myrunuo_characters_layers (char_id, layer_id, item_id, item_hue) VALUES ({0}, {1}, {2}, {3})", serial, index.ToString(), itemID.ToString(), hue.ToString() ); - } - } - - public void InsertItems( Mobile mob ) - { - ArrayList items = m_Items; - items.AddRange( mob.Items ); - string serial = mob.Serial.Value.ToString(); - - items.Sort( LayerComparer.Instance ); - - int index = 0; - - bool hidePants = false; - bool alive = mob.Alive; - bool hideHair = !alive; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = (Item)items[i]; - - if ( !LayerComparer.IsValid( item ) ) - break; - - if ( !alive && item.ItemID != 8270 ) - continue; - - if ( item.ItemID == 0x1411 || item.ItemID == 0x141A ) // plate legs - hidePants = true; - else if ( hidePants && item.Layer == Layer.Pants ) - continue; - - if ( !hideHair && item.Layer == Layer.Helm ) - hideHair = true; - - InsertItem( serial, index++, item.ItemID, item.Hue ); - } - - if ( mob.FacialHairItemID != 0 && alive ) - InsertItem( serial, index++, mob.FacialHairItemID, mob.FacialHairHue ); - - if ( mob.HairItemID != 0 && !hideHair ) - InsertItem( serial, index++, mob.HairItemID, mob.HairHue ); - - items.Clear(); - } - - public void DeleteMobile( Mobile mob ) - { - ExecuteNonQuery( "DELETE FROM myrunuo_characters WHERE char_id = {0}", mob.Serial.Value.ToString() ); - ExecuteNonQuery( "DELETE FROM myrunuo_characters_skills WHERE char_id = {0}", mob.Serial.Value.ToString() ); - ExecuteNonQuery( "DELETE FROM myrunuo_characters_layers WHERE char_id = {0}", mob.Serial.Value.ToString() ); - } - - public StreamWriter GetUniqueWriter( string type, out string filePath ) - { - filePath = Path.Combine( Core.BaseDirectory, $"myrunuodb_{type}.txt").Replace( Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar ); - - try - { - return new StreamWriter( filePath ); - } - catch - { - for ( int i = 0; i < 100; ++i ) - { - try - { - filePath = Path.Combine( Core.BaseDirectory, $"myrunuodb_{type}_{i}.txt").Replace( Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar ); - return new StreamWriter( filePath ); - } - catch - { - } - } - } - - return null; - } - - public void DumpMobiles( DateTime endTime ) - { - CheckConnection(); - - for ( int i = m_Index; i < m_List.Count; ++i ) - { - Mobile mob = (Mobile)m_List[i]; - - if ( mob is PlayerMobile mobile ) - mobile.ChangedMyRunUO = false; - - if ( !mob.Deleted && mob.AccessLevel < Config.HiddenAccessLevel ) - { - if ( !Config.LoadDataInFile ) - DeleteMobile( mob ); - - InsertMobile( mob ); - InsertSkills( mob ); - InsertItems( mob ); - } - else if ( !Config.LoadDataInFile ) - { - DeleteMobile( mob ); - } - - ++m_Index; - - if ( DateTime.UtcNow >= endTime ) - break; - } - - if ( m_Index == m_List.Count ) - { - m_List.Clear(); - m_Stage = Stage.CollectingGuilds; - m_Index = 0; - - if ( Config.LoadDataInFile ) - { - m_OpSkills.Close(); - m_OpLayers.Close(); - m_OpMobiles.Close(); - - ExecuteNonQuery( "LOAD DATA {0}INFILE '{1}' INTO TABLE myrunuo_characters FIELDS TERMINATED BY ',' ENCLOSED BY '\"' LINES TERMINATED BY '\n'", Config.DatabaseNonLocal ? "LOCAL " : "", m_MobilesPath ); - ExecuteNonQuery( "LOAD DATA {0}INFILE '{1}' INTO TABLE myrunuo_characters_skills FIELDS TERMINATED BY ',' ENCLOSED BY '\"' LINES TERMINATED BY '\n'", Config.DatabaseNonLocal ? "LOCAL " : "", m_SkillsPath ); - ExecuteNonQuery( "LOAD DATA {0}INFILE '{1}' INTO TABLE myrunuo_characters_layers FIELDS TERMINATED BY ',' ENCLOSED BY '\"' LINES TERMINATED BY '\n'", Config.DatabaseNonLocal ? "LOCAL " : "", m_LayersPath ); - } - } - } - - public void CollectGuilds( DateTime endTime ) - { - m_List.AddRange( BaseGuild.List.Values ); - m_Stage = Stage.DumpingGuilds; - m_Index = 0; - } - - public void InsertGuild( Guild guild ) - { - string guildType = "Standard"; - - switch ( guild.Type ) - { - case GuildType.Chaos: guildType = "Chaos"; break; - case GuildType.Order: guildType = "Order"; break; - } - - ExecuteNonQuery( "INSERT INTO myrunuo_guilds (guild_id, guild_name, guild_abbreviation, guild_website, guild_charter, guild_type, guild_wars, guild_members, guild_master) VALUES ({0}, '{1}', {2}, {3}, {4}, '{5}', {6}, {7}, {8})", guild.Id.ToString(), SafeString( guild.Name ), guild.Abbreviation == "none" ? "NULL" : "'" + SafeString( guild.Abbreviation ) + "'", guild.Website == null ? "NULL" : "'" + SafeString( guild.Website ) + "'", guild.Charter == null ? "NULL" : "'" + SafeString( guild.Charter ) + "'", guildType, guild.Enemies.Count.ToString(), guild.Members.Count.ToString(), guild.Leader.Serial.Value.ToString() ); - } - - public void InsertWars( Guild guild ) - { - List wars = guild.Enemies; - - string ourId = guild.Id.ToString(); - - for ( int i = 0; i < wars.Count; ++i ) - { - Guild them = wars[i]; - string theirId = them.Id.ToString(); - - ExecuteNonQueryIfNull( - string.Format( "SELECT guild_1 FROM myrunuo_guilds_wars WHERE (guild_1={0} AND guild_2={1}) OR (guild_1={1} AND guild_2={0})", ourId, theirId ), - $"INSERT INTO myrunuo_guilds_wars (guild_1, guild_2) VALUES ({ourId}, {theirId})"); - } - } - - public void DumpGuilds( DateTime endTime ) - { - CheckConnection(); - - for ( int i = m_Index; i < m_List.Count; ++i ) - { - Guild guild = (Guild)m_List[i]; - - if ( !guild.Disbanded ) - { - InsertGuild( guild ); - InsertWars( guild ); - } - - ++m_Index; - - if ( DateTime.UtcNow >= endTime ) - break; - } - - if ( m_Index == m_List.Count ) - { - m_List.Clear(); - m_Stage = Stage.Complete; - m_Index = 0; - } - } - } -} + public class MyRunUO : Timer + { + public const char LineStart = '\"'; + public const string EntrySep = "\",\""; + public const string LineEnd = "\"\n"; + private static double CpuInterval = 0.1; // Processor runs every 0.1 seconds + + private static double + CpuPercent = 0.25; // Processor runs for 25% of Interval, or ~25ms. This should take around 25% cpu + + private static Timer m_Timer; + + private static DatabaseCommandQueue m_Command; + + private static ArrayList m_MobilesToUpdate = new ArrayList(); + private List m_Collecting; + private int m_Index; + + private ArrayList m_Items = new ArrayList(); + private string m_LayersPath; + private ArrayList m_List; + private string m_MobilesPath; + private StreamWriter m_OpLayers; + private StreamWriter m_OpMobiles; + + private StreamWriter m_OpSkills; + + private string m_SkillsPath; + + private Stage m_Stage; + + private DateTime m_StartTime; + + public MyRunUO() : base(TimeSpan.FromSeconds(CpuInterval), TimeSpan.FromSeconds(CpuInterval)) + { + m_List = new ArrayList(); + m_Collecting = new List(); + + m_StartTime = DateTime.UtcNow; + Console.WriteLine("MyRunUO: Updating character database"); + } + + public static void Initialize() + { + if (Config.Enabled) + { + DelayCall(TimeSpan.FromSeconds(10.0), Config.CharacterUpdateInterval, Begin); + + CommandSystem.Register("InitMyRunUO", AccessLevel.Administrator, InitMyRunUO_OnCommand); + CommandSystem.Register("UpdateMyRunUO", AccessLevel.Administrator, UpdateMyRunUO_OnCommand); + + CommandSystem.Register("PublicChar", AccessLevel.Player, PublicChar_OnCommand); + CommandSystem.Register("PrivateChar", AccessLevel.Player, PrivateChar_OnCommand); + } + } + + [Usage("PublicChar")] + [Description("Enables showing extended character stats and skills in MyRunUO.")] + public static void PublicChar_OnCommand(CommandEventArgs e) + { + if (e.Mobile is PlayerMobile pm) + { + if (pm.PublicMyRunUO) + { + pm.SendMessage("You have already chosen to show your skills and stats."); + } + else + { + pm.PublicMyRunUO = true; + pm.SendMessage("All of your skills and stats will now be shown publicly in MyRunUO."); + } + } + } + + [Usage("PrivateChar")] + [Description("Disables showing extended character stats and skills in MyRunUO.")] + public static void PrivateChar_OnCommand(CommandEventArgs e) + { + if (e.Mobile is PlayerMobile pm) + { + if (!pm.PublicMyRunUO) + { + pm.SendMessage("You have already chosen to not show your skills and stats."); + } + else + { + pm.PublicMyRunUO = false; + pm.SendMessage("Only a general level of your top three skills will be shown in MyRunUO."); + } + } + } + + [Usage("InitMyRunUO")] + [Description("Initially creates the database schema.")] + public static void InitMyRunUO_OnCommand(CommandEventArgs e) + { + if (m_Command != null && m_Command.HasCompleted) + { + TableCreation(); + e.Mobile.SendMessage("MyRunUO table creation process has been started."); + } + else + { + e.Mobile.SendMessage("MyRunUO table creation is already running."); + } + } + + public static void TableCreation() + { + if (m_Command != null && !m_Command.HasCompleted) + return; + // DateTime start = DateTime.Now; + Console.WriteLine("MyRunUO: Creating tables"); + try + { + m_Command = new DatabaseCommandQueue("MyRunUO: Tables created in {0:F1} seconds", + "MyRunUO Status Database Thread"); + m_Command.Enqueue( + "CREATE TABLE IF NOT EXISTS `myrunuo_characters` ( `char_id` int(10) unsigned NOT NULL, `char_name` varchar(255) NOT NULL, `char_str` smallint(3) unsigned NOT NULL, `char_dex` smallint(3) unsigned NOT NULL, `char_int` smallint(3) unsigned NOT NULL, `char_female` tinyint(1) NOT NULL, `char_counts` smallint(6) NOT NULL, `char_guild` varchar(255) DEFAULT NULL, `char_guildtitle` varchar(255) DEFAULT NULL, `char_nototitle` varchar(255) DEFAULT NULL, `char_bodyhue` smallint(5) unsigned DEFAULT NULL, `char_public` tinyint(1) NOT NULL, PRIMARY KEY (`char_id`))"); + m_Command.Enqueue( + "CREATE TABLE IF NOT EXISTS `myrunuo_characters_layers` ( `char_id` int(10) unsigned NOT NULL, `layer_id` tinyint(3) unsigned NOT NULL, `item_id` smallint(5) unsigned NOT NULL, `item_hue` smallint(5) unsigned NOT NULL, PRIMARY KEY (`char_id`,`layer_id`))"); + m_Command.Enqueue( + "CREATE TABLE IF NOT EXISTS `myrunuo_characters_skills` ( `char_id` int(10) unsigned NOT NULL, `skill_id` tinyint(3) NOT NULL, `skill_value` smallint(5) unsigned NOT NULL, PRIMARY KEY (`char_id`,`skill_id`), KEY `skill_id` (`skill_id`))"); + m_Command.Enqueue( + "CREATE TABLE IF NOT EXISTS `myrunuo_guilds` ( `guild_id` smallint(5) unsigned NOT NULL, `guild_name` varchar(255) NOT NULL, `guild_abbreviation` varchar(8) DEFAULT NULL, `guild_website` varchar(255) DEFAULT NULL, `guild_charter` varchar(255) DEFAULT NULL, `guild_type` varchar(8) NOT NULL, `guild_wars` smallint(5) unsigned NOT NULL, `guild_members` smallint(5) unsigned NOT NULL, `guild_master` int(10) unsigned NOT NULL, PRIMARY KEY (`guild_id`))"); + m_Command.Enqueue( + "CREATE TABLE IF NOT EXISTS `myrunuo_guilds_wars` ( `guild_1` smallint(5) unsigned NOT NULL DEFAULT '0', `guild_2` smallint(5) unsigned NOT NULL DEFAULT '0', PRIMARY KEY (`guild_1`,`guild_2`), KEY `guild1` (`guild_1`), KEY `guild2` (`guild_2`))"); + m_Command.Enqueue( + "CREATE TABLE IF NOT EXISTS `myrunuo_status` ( `char_id` int(10) NOT NULL, PRIMARY KEY (`char_id`))"); + } + catch (Exception e) + { + Console.WriteLine("MyRunUO: Error creating tables."); + Console.WriteLine(e); + } + + m_Command?.Enqueue(null); + } + + [Usage("UpdateMyRunUO")] + [Description("Starts the process of updating the MyRunUO character and guild database.")] + public static void UpdateMyRunUO_OnCommand(CommandEventArgs e) + { + if (m_Command != null && m_Command.HasCompleted) + m_Command = null; + + if (m_Timer == null && m_Command == null) + { + Begin(); + e.Mobile.SendMessage("MyRunUO update process has been started."); + } + else + { + e.Mobile.SendMessage("MyRunUO database is already being updated."); + } + } + + public static void Begin() + { + if (m_Command != null && m_Command.HasCompleted) + m_Command = null; + + if (m_Timer != null || m_Command != null) + return; + + m_Timer = new MyRunUO(); + m_Timer.Start(); + } + + protected override void OnTick() + { + bool shouldExit = false; + + try + { + shouldExit = Process(DateTime.UtcNow + TimeSpan.FromSeconds(CpuInterval * CpuPercent)); + + if (shouldExit) + Console.WriteLine("MyRunUO: Database statements compiled in {0:F2} seconds", + (DateTime.UtcNow - m_StartTime).TotalSeconds); + } + catch (Exception e) + { + Console.WriteLine("MyRunUO: {0}: Exception cought while processing", m_Stage); + Console.WriteLine(e); + shouldExit = true; + } + + if (shouldExit) + { + m_Command.Enqueue(null); + + Stop(); + m_Timer = null; + } + } + + public bool Process(DateTime endTime) + { + switch (m_Stage) + { + case Stage.CollectingMobiles: + CollectMobiles(endTime); + break; + case Stage.DumpingMobiles: + DumpMobiles(endTime); + break; + case Stage.CollectingGuilds: + CollectGuilds(endTime); + break; + case Stage.DumpingGuilds: + DumpGuilds(endTime); + break; + } + + return m_Stage == Stage.Complete; + } + + public static void QueueMobileUpdate(Mobile m) + { + if (!Config.Enabled || Config.LoadDataInFile) + return; + + m_MobilesToUpdate.Add(m); + } + + public void CollectMobiles(DateTime endTime) + { + if (Config.LoadDataInFile) + { + if (m_Index == 0) + m_Collecting.AddRange(Accounts.GetAccounts()); + + for (int i = m_Index; i < m_Collecting.Count; ++i) + { + IAccount acct = m_Collecting[i]; + + for (int j = 0; j < acct.Length; ++j) + { + Mobile mob = acct[j]; + + if (mob != null && mob.AccessLevel < Config.HiddenAccessLevel) + m_List.Add(mob); + } + + ++m_Index; + + if (DateTime.UtcNow >= endTime) + break; + } + + if (m_Index == m_Collecting.Count) + { + m_Collecting = new List(); + m_Stage = Stage.DumpingMobiles; + m_Index = 0; + } + } + else + { + m_List = m_MobilesToUpdate; + m_MobilesToUpdate = new ArrayList(); + m_Stage = Stage.DumpingMobiles; + m_Index = 0; + } + } + + public void CheckConnection() + { + if (m_Command == null) + { + m_Command = new DatabaseCommandQueue("MyRunUO: Characeter database updated in {0:F1} seconds", + "MyRunUO Character Database Thread"); + + if (Config.LoadDataInFile) + { + m_OpSkills = GetUniqueWriter("skills", out m_SkillsPath); + m_OpLayers = GetUniqueWriter("layers", out m_LayersPath); + m_OpMobiles = GetUniqueWriter("mobiles", out m_MobilesPath); + + m_Command.Enqueue("TRUNCATE TABLE myrunuo_characters"); + m_Command.Enqueue("TRUNCATE TABLE myrunuo_characters_layers"); + m_Command.Enqueue("TRUNCATE TABLE myrunuo_characters_skills"); + } + + m_Command.Enqueue("TRUNCATE TABLE myrunuo_guilds"); + m_Command.Enqueue("TRUNCATE TABLE myrunuo_guilds_wars"); + } + } + + public void ExecuteNonQuery(string text) + { + m_Command.Enqueue(text); + } + + public void ExecuteNonQuery(string format, params string[] args) + { + ExecuteNonQuery(string.Format(format, args)); + } + + public void ExecuteNonQueryIfNull(string select, string insert) + { + m_Command.Enqueue(new[] { select, insert }); + } + + private void AppendCharEntity(string input, int charIndex, ref StringBuilder sb, char c) + { + if (sb == null) + { + if (charIndex > 0) + sb = new StringBuilder(input, 0, charIndex, input.Length + 20); + else + sb = new StringBuilder(input.Length + 20); + } + + sb.Append("&#"); + sb.Append((int)c); + sb.Append(";"); + } + + private void AppendEntityRef(string input, int charIndex, ref StringBuilder sb, string ent) + { + if (sb == null) + { + if (charIndex > 0) + sb = new StringBuilder(input, 0, charIndex, input.Length + 20); + else + sb = new StringBuilder(input.Length + 20); + } + + sb.Append(ent); + } + + private string SafeString(string input) + { + if (input == null) + return ""; + + StringBuilder sb = null; + + for (int i = 0; i < input.Length; ++i) + { + char c = input[i]; + + if (c < 0x20 || c >= 0x7F) + AppendCharEntity(input, i, ref sb, c); + else + switch (c) + { + case '&': + AppendEntityRef(input, i, ref sb, "&"); + break; + case '>': + AppendEntityRef(input, i, ref sb, ">"); + break; + case '<': + AppendEntityRef(input, i, ref sb, "<"); + break; + case '"': + AppendEntityRef(input, i, ref sb, """); + break; + case '\'': + case ':': + case '/': + case '\\': + AppendCharEntity(input, i, ref sb, c); + break; + default: + { + sb?.Append(c); + + break; + } + } + } + + if (sb != null) + return sb.ToString(); + + return input; + } + + public void InsertMobile(Mobile mob) + { + string guildTitle = mob.GuildTitle; + + if (guildTitle == null || (guildTitle = guildTitle.Trim()).Length == 0) + guildTitle = "NULL"; + else + guildTitle = SafeString(guildTitle); + + string notoTitle = SafeString(Titles.ComputeTitle(null, mob)); + string female = mob.Female ? "1" : "0"; + + bool pubBool = mob is PlayerMobile mobile && mobile.PublicMyRunUO; + + string pubString = pubBool ? "1" : "0"; + + string guildId = mob.Guild == null ? "NULL" : mob.Guild.Id.ToString(); + + if (Config.LoadDataInFile) + { + m_OpMobiles.Write(LineStart); + m_OpMobiles.Write(mob.Serial.Value); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(SafeString(mob.Name)); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(mob.RawStr); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(mob.RawDex); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(mob.RawInt); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(female); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(mob.Kills); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(guildId); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(guildTitle); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(notoTitle); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(mob.Hue); + m_OpMobiles.Write(EntrySep); + m_OpMobiles.Write(pubString); + m_OpMobiles.Write(LineEnd); + } + else + { + ExecuteNonQuery( + "INSERT INTO myrunuo_characters (char_id, char_name, char_str, char_dex, char_int, char_female, char_counts, char_guild, char_guildtitle, char_nototitle, char_bodyhue, char_public ) VALUES ({0}, '{1}', {2}, {3}, {4}, {5}, {6}, {7}, {8}, '{9}', {10}, {11})", + mob.Serial.Value.ToString(), SafeString(mob.Name), mob.RawStr.ToString(), mob.RawDex.ToString(), + mob.RawInt.ToString(), female, mob.Kills.ToString(), guildId, guildTitle, notoTitle, mob.Hue.ToString(), + pubString); + } + } + + public void InsertSkills(Mobile mob) + { + Skills skills = mob.Skills; + string serial = mob.Serial.Value.ToString(); + + for (int i = 0; i < skills.Length; ++i) + { + Skill skill = skills[i]; + + if (skill.BaseFixedPoint > 0) + { + if (Config.LoadDataInFile) + { + m_OpSkills.Write(LineStart); + m_OpSkills.Write(serial); + m_OpSkills.Write(EntrySep); + m_OpSkills.Write(i); + m_OpSkills.Write(EntrySep); + m_OpSkills.Write(skill.BaseFixedPoint); + m_OpSkills.Write(LineEnd); + } + else + { + ExecuteNonQuery( + "INSERT INTO myrunuo_characters_skills (char_id, skill_id, skill_value) VALUES ({0}, {1}, {2})", + serial, i.ToString(), skill.BaseFixedPoint.ToString()); + } + } + } + } + + private void InsertItem(string serial, int index, int itemID, int hue) + { + if (Config.LoadDataInFile) + { + m_OpLayers.Write(LineStart); + m_OpLayers.Write(serial); + m_OpLayers.Write(EntrySep); + m_OpLayers.Write(index); + m_OpLayers.Write(EntrySep); + m_OpLayers.Write(itemID); + m_OpLayers.Write(EntrySep); + m_OpLayers.Write(hue); + m_OpLayers.Write(LineEnd); + } + else + { + ExecuteNonQuery( + "INSERT INTO myrunuo_characters_layers (char_id, layer_id, item_id, item_hue) VALUES ({0}, {1}, {2}, {3})", + serial, index.ToString(), itemID.ToString(), hue.ToString()); + } + } + + public void InsertItems(Mobile mob) + { + ArrayList items = m_Items; + items.AddRange(mob.Items); + string serial = mob.Serial.Value.ToString(); + + items.Sort(LayerComparer.Instance); + + int index = 0; + + bool hidePants = false; + bool alive = mob.Alive; + bool hideHair = !alive; + + for (int i = 0; i < items.Count; ++i) + { + Item item = (Item)items[i]; + + if (!LayerComparer.IsValid(item)) + break; + + if (!alive && item.ItemID != 8270) + continue; + + if (item.ItemID == 0x1411 || item.ItemID == 0x141A) // plate legs + hidePants = true; + else if (hidePants && item.Layer == Layer.Pants) + continue; + + if (!hideHair && item.Layer == Layer.Helm) + hideHair = true; + + InsertItem(serial, index++, item.ItemID, item.Hue); + } + + if (mob.FacialHairItemID != 0 && alive) + InsertItem(serial, index++, mob.FacialHairItemID, mob.FacialHairHue); + + if (mob.HairItemID != 0 && !hideHair) + InsertItem(serial, index++, mob.HairItemID, mob.HairHue); + + items.Clear(); + } + + public void DeleteMobile(Mobile mob) + { + ExecuteNonQuery("DELETE FROM myrunuo_characters WHERE char_id = {0}", mob.Serial.Value.ToString()); + ExecuteNonQuery("DELETE FROM myrunuo_characters_skills WHERE char_id = {0}", mob.Serial.Value.ToString()); + ExecuteNonQuery("DELETE FROM myrunuo_characters_layers WHERE char_id = {0}", mob.Serial.Value.ToString()); + } + + public StreamWriter GetUniqueWriter(string type, out string filePath) + { + filePath = Path.Combine(Core.BaseDirectory, $"myrunuodb_{type}.txt") + .Replace(Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar); + + try + { + return new StreamWriter(filePath); + } + catch + { + for (int i = 0; i < 100; ++i) + try + { + filePath = Path.Combine(Core.BaseDirectory, $"myrunuodb_{type}_{i}.txt") + .Replace(Path.DirectorySeparatorChar, Path.AltDirectorySeparatorChar); + return new StreamWriter(filePath); + } + catch + { + } + } + + return null; + } + + public void DumpMobiles(DateTime endTime) + { + CheckConnection(); + + for (int i = m_Index; i < m_List.Count; ++i) + { + Mobile mob = (Mobile)m_List[i]; + + if (mob is PlayerMobile mobile) + mobile.ChangedMyRunUO = false; + + if (!mob.Deleted && mob.AccessLevel < Config.HiddenAccessLevel) + { + if (!Config.LoadDataInFile) + DeleteMobile(mob); + + InsertMobile(mob); + InsertSkills(mob); + InsertItems(mob); + } + else if (!Config.LoadDataInFile) + { + DeleteMobile(mob); + } + + ++m_Index; + + if (DateTime.UtcNow >= endTime) + break; + } + + if (m_Index == m_List.Count) + { + m_List.Clear(); + m_Stage = Stage.CollectingGuilds; + m_Index = 0; + + if (Config.LoadDataInFile) + { + m_OpSkills.Close(); + m_OpLayers.Close(); + m_OpMobiles.Close(); + + ExecuteNonQuery( + "LOAD DATA {0}INFILE '{1}' INTO TABLE myrunuo_characters FIELDS TERMINATED BY ',' ENCLOSED BY '\"' LINES TERMINATED BY '\n'", + Config.DatabaseNonLocal ? "LOCAL " : "", m_MobilesPath); + ExecuteNonQuery( + "LOAD DATA {0}INFILE '{1}' INTO TABLE myrunuo_characters_skills FIELDS TERMINATED BY ',' ENCLOSED BY '\"' LINES TERMINATED BY '\n'", + Config.DatabaseNonLocal ? "LOCAL " : "", m_SkillsPath); + ExecuteNonQuery( + "LOAD DATA {0}INFILE '{1}' INTO TABLE myrunuo_characters_layers FIELDS TERMINATED BY ',' ENCLOSED BY '\"' LINES TERMINATED BY '\n'", + Config.DatabaseNonLocal ? "LOCAL " : "", m_LayersPath); + } + } + } + + public void CollectGuilds(DateTime endTime) + { + m_List.AddRange(BaseGuild.List.Values); + m_Stage = Stage.DumpingGuilds; + m_Index = 0; + } + + public void InsertGuild(Guild guild) + { + string guildType = "Standard"; + + switch (guild.Type) + { + case GuildType.Chaos: + guildType = "Chaos"; + break; + case GuildType.Order: + guildType = "Order"; + break; + } + + ExecuteNonQuery( + "INSERT INTO myrunuo_guilds (guild_id, guild_name, guild_abbreviation, guild_website, guild_charter, guild_type, guild_wars, guild_members, guild_master) VALUES ({0}, '{1}', {2}, {3}, {4}, '{5}', {6}, {7}, {8})", + guild.Id.ToString(), SafeString(guild.Name), + guild.Abbreviation == "none" ? "NULL" : "'" + SafeString(guild.Abbreviation) + "'", + guild.Website == null ? "NULL" : "'" + SafeString(guild.Website) + "'", + guild.Charter == null ? "NULL" : "'" + SafeString(guild.Charter) + "'", guildType, + guild.Enemies.Count.ToString(), guild.Members.Count.ToString(), guild.Leader.Serial.Value.ToString()); + } + + public void InsertWars(Guild guild) + { + List wars = guild.Enemies; + + string ourId = guild.Id.ToString(); + + for (int i = 0; i < wars.Count; ++i) + { + Guild them = wars[i]; + string theirId = them.Id.ToString(); + + ExecuteNonQueryIfNull( + string.Format( + "SELECT guild_1 FROM myrunuo_guilds_wars WHERE (guild_1={0} AND guild_2={1}) OR (guild_1={1} AND guild_2={0})", + ourId, theirId), + $"INSERT INTO myrunuo_guilds_wars (guild_1, guild_2) VALUES ({ourId}, {theirId})"); + } + } + + public void DumpGuilds(DateTime endTime) + { + CheckConnection(); + + for (int i = m_Index; i < m_List.Count; ++i) + { + Guild guild = (Guild)m_List[i]; + + if (!guild.Disbanded) + { + InsertGuild(guild); + InsertWars(guild); + } + + ++m_Index; + + if (DateTime.UtcNow >= endTime) + break; + } + + if (m_Index == m_List.Count) + { + m_List.Clear(); + m_Stage = Stage.Complete; + m_Index = 0; + } + } + + private enum Stage + { + CollectingMobiles, + DumpingMobiles, + CollectingGuilds, + DumpingGuilds, + Complete + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/MyRunUO/MyRunUOStatus.cs b/Scripts/Engines/MyRunUO/MyRunUOStatus.cs index e23ba18ee..034ec06b6 100644 --- a/Scripts/Engines/MyRunUO/MyRunUOStatus.cs +++ b/Scripts/Engines/MyRunUO/MyRunUOStatus.cs @@ -5,68 +5,69 @@ using Server.Network; namespace Server.Engines.MyRunUO { - public class MyRunUOStatus - { - public static void Initialize() - { - if ( Config.Enabled ) - { - Timer.DelayCall( TimeSpan.FromSeconds( 20.0 ), Config.StatusUpdateInterval, Begin ); + public class MyRunUOStatus + { + private static DatabaseCommandQueue m_Command; - CommandSystem.Register( "UpdateWebStatus", AccessLevel.Administrator, UpdateWebStatus_OnCommand ); - } - } + public static void Initialize() + { + if (Config.Enabled) + { + Timer.DelayCall(TimeSpan.FromSeconds(20.0), Config.StatusUpdateInterval, Begin); - [Usage( "UpdateWebStatus" )] - [Description( "Starts the process of updating the MyRunUO online status database." )] - public static void UpdateWebStatus_OnCommand( CommandEventArgs e ) - { - if ( m_Command == null || m_Command.HasCompleted ) - { - Begin(); - e.Mobile.SendMessage( "Web status update process has been started." ); - } - else - { - e.Mobile.SendMessage( "Web status database is already being updated." ); - } - } + CommandSystem.Register("UpdateWebStatus", AccessLevel.Administrator, UpdateWebStatus_OnCommand); + } + } - private static DatabaseCommandQueue m_Command; + [Usage("UpdateWebStatus")] + [Description("Starts the process of updating the MyRunUO online status database.")] + public static void UpdateWebStatus_OnCommand(CommandEventArgs e) + { + if (m_Command == null || m_Command.HasCompleted) + { + Begin(); + e.Mobile.SendMessage("Web status update process has been started."); + } + else + { + e.Mobile.SendMessage("Web status database is already being updated."); + } + } - public static void Begin() - { - if ( m_Command != null && !m_Command.HasCompleted ) - return; + public static void Begin() + { + if (m_Command != null && !m_Command.HasCompleted) + return; - DateTime start = DateTime.UtcNow; - Console.WriteLine( "MyRunUO: Updating status database" ); + DateTime start = DateTime.UtcNow; + Console.WriteLine("MyRunUO: Updating status database"); - try - { - m_Command = new DatabaseCommandQueue( "MyRunUO: Status database updated in {0:F1} seconds", "MyRunUO Status Database Thread" ); + try + { + m_Command = new DatabaseCommandQueue("MyRunUO: Status database updated in {0:F1} seconds", + "MyRunUO Status Database Thread"); - m_Command.Enqueue( "DELETE FROM myrunuo_status" ); + m_Command.Enqueue("DELETE FROM myrunuo_status"); - List online = NetState.Instances; + List online = NetState.Instances; - for ( int i = 0; i < online.Count; ++i ) - { - NetState ns = online[i]; - Mobile mob = ns.Mobile; + for (int i = 0; i < online.Count; ++i) + { + NetState ns = online[i]; + Mobile mob = ns.Mobile; - if ( mob != null ) - m_Command.Enqueue( - $"INSERT INTO myrunuo_status (char_id) VALUES ({mob.Serial.Value.ToString()})"); - } - } - catch ( Exception e ) - { - Console.WriteLine( "MyRunUO: Error updating status database" ); - Console.WriteLine( e ); - } + if (mob != null) + m_Command.Enqueue( + $"INSERT INTO myrunuo_status (char_id) VALUES ({mob.Serial.Value.ToString()})"); + } + } + catch (Exception e) + { + Console.WriteLine("MyRunUO: Error updating status database"); + Console.WriteLine(e); + } - m_Command?.Enqueue( null ); - } - } + m_Command?.Enqueue(null); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Party/AddPartyTarget.cs b/Scripts/Engines/Party/AddPartyTarget.cs index f77c400d2..f52152a77 100644 --- a/Scripts/Engines/Party/AddPartyTarget.cs +++ b/Scripts/Engines/Party/AddPartyTarget.cs @@ -2,43 +2,43 @@ using Server.Targeting; namespace Server.Engines.PartySystem { - public class AddPartyTarget : Target - { - public AddPartyTarget( Mobile from ) : base( 8, false, TargetFlags.None ) - { - from.SendLocalizedMessage( 1005454 ); // Who would you like to add to your party? - } + public class AddPartyTarget : Target + { + public AddPartyTarget(Mobile from) : base(8, false, TargetFlags.None) + { + from.SendLocalizedMessage(1005454); // Who would you like to add to your party? + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile m ) - { - Party p = Party.Get( from ); - Party mp = Party.Get( m ); + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile m) + { + Party p = Party.Get(from); + Party mp = Party.Get(m); - if ( from == m ) - from.SendLocalizedMessage( 1005439 ); // You cannot add yourself to a party. - else if ( p != null && p.Leader != from ) - from.SendLocalizedMessage( 1005453 ); // You may only add members to the party if you are the leader. - else if ( m.Party is Mobile ) - return; - else if ( p != null && (p.Members.Count + p.Candidates.Count) >= Party.Capacity ) - from.SendLocalizedMessage( 1008095 ); // You may only have 10 in your party (this includes candidates). - else if ( !m.Player && m.Body.IsHuman ) - m.SayTo( from, 1005443 ); // Nay, I would rather stay here and watch a nail rust. - else if ( !m.Player ) - from.SendLocalizedMessage( 1005444 ); // The creature ignores your offer. - else if ( mp != null && mp == p ) - from.SendLocalizedMessage( 1005440 ); // This person is already in your party! - else if ( mp != null ) - from.SendLocalizedMessage( 1005441 ); // This person is already in a party! - else - Party.Invite( from, m ); - } - else - { - from.SendLocalizedMessage( 1005442 ); // You may only add living things to your party! - } - } - } -} + if (from == m) + from.SendLocalizedMessage(1005439); // You cannot add yourself to a party. + else if (p != null && p.Leader != from) + from.SendLocalizedMessage(1005453); // You may only add members to the party if you are the leader. + else if (m.Party is Mobile) + return; + else if (p != null && p.Members.Count + p.Candidates.Count >= Party.Capacity) + from.SendLocalizedMessage(1008095); // You may only have 10 in your party (this includes candidates). + else if (!m.Player && m.Body.IsHuman) + m.SayTo(from, 1005443); // Nay, I would rather stay here and watch a nail rust. + else if (!m.Player) + from.SendLocalizedMessage(1005444); // The creature ignores your offer. + else if (mp != null && mp == p) + from.SendLocalizedMessage(1005440); // This person is already in your party! + else if (mp != null) + from.SendLocalizedMessage(1005441); // This person is already in a party! + else + Party.Invite(from, m); + } + else + { + from.SendLocalizedMessage(1005442); // You may only add living things to your party! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Party/DeclineTimer.cs b/Scripts/Engines/Party/DeclineTimer.cs index 858e0f683..15d7a5ebe 100644 --- a/Scripts/Engines/Party/DeclineTimer.cs +++ b/Scripts/Engines/Party/DeclineTimer.cs @@ -3,34 +3,33 @@ using System.Collections; namespace Server.Engines.PartySystem { - public class DeclineTimer : Timer - { - private Mobile m_Mobile, m_Leader; + public class DeclineTimer : Timer + { + private static Hashtable m_Table = new Hashtable(); + private Mobile m_Mobile, m_Leader; - private static Hashtable m_Table = new Hashtable(); + private DeclineTimer(Mobile m, Mobile leader) : base(TimeSpan.FromSeconds(30.0)) + { + m_Mobile = m; + m_Leader = leader; + } - public static void Start( Mobile m, Mobile leader ) - { - DeclineTimer t = (DeclineTimer)m_Table[m]; + public static void Start(Mobile m, Mobile leader) + { + DeclineTimer t = (DeclineTimer)m_Table[m]; - t?.Stop(); + t?.Stop(); - m_Table[m] = t = new DeclineTimer( m, leader ); - t.Start(); - } + m_Table[m] = t = new DeclineTimer(m, leader); + t.Start(); + } - private DeclineTimer( Mobile m, Mobile leader ) : base( TimeSpan.FromSeconds( 30.0 ) ) - { - m_Mobile = m; - m_Leader = leader; - } + protected override void OnTick() + { + m_Table.Remove(m_Mobile); - protected override void OnTick() - { - m_Table.Remove( m_Mobile ); - - if ( m_Mobile.Party == m_Leader && PartyCommands.Handler != null ) - PartyCommands.Handler.OnDecline( m_Mobile, m_Leader ); - } - } + if (m_Mobile.Party == m_Leader && PartyCommands.Handler != null) + PartyCommands.Handler.OnDecline(m_Mobile, m_Leader); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Party/Packets.cs b/Scripts/Engines/Party/Packets.cs index 6d6a81d5b..e417d0b3c 100644 --- a/Scripts/Engines/Party/Packets.cs +++ b/Scripts/Engines/Party/Packets.cs @@ -2,76 +2,76 @@ using Server.Network; namespace Server.Engines.PartySystem { - public sealed class PartyEmptyList : Packet - { - public PartyEmptyList( Mobile m ) : base( 0xBF ) - { - EnsureCapacity( 7 ); + public sealed class PartyEmptyList : Packet + { + public PartyEmptyList(Mobile m) : base(0xBF) + { + EnsureCapacity(7); - m_Stream.Write( (short) 0x0006 ); - m_Stream.Write( (byte) 0x02 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (int) m.Serial ); - } - } + m_Stream.Write((short)0x0006); + m_Stream.Write((byte)0x02); + m_Stream.Write((byte)0); + m_Stream.Write(m.Serial); + } + } - public sealed class PartyMemberList : Packet - { - public PartyMemberList( Party p ) : base( 0xBF ) - { - EnsureCapacity( 7 + p.Count*4 ); + public sealed class PartyMemberList : Packet + { + public PartyMemberList(Party p) : base(0xBF) + { + EnsureCapacity(7 + p.Count * 4); - m_Stream.Write( (short) 0x0006 ); - m_Stream.Write( (byte) 0x01 ); - m_Stream.Write( (byte) p.Count ); + m_Stream.Write((short)0x0006); + m_Stream.Write((byte)0x01); + m_Stream.Write((byte)p.Count); - for ( int i = 0; i < p.Count; ++i ) - m_Stream.Write( (int) p[i].Mobile.Serial ); - } - } + for (int i = 0; i < p.Count; ++i) + m_Stream.Write(p[i].Mobile.Serial); + } + } - public sealed class PartyRemoveMember : Packet - { - public PartyRemoveMember( Mobile removed, Party p ) : base( 0xBF ) - { - EnsureCapacity( 11 + p.Count*4 ); + public sealed class PartyRemoveMember : Packet + { + public PartyRemoveMember(Mobile removed, Party p) : base(0xBF) + { + EnsureCapacity(11 + p.Count * 4); - m_Stream.Write( (short) 0x0006 ); - m_Stream.Write( (byte) 0x02 ); - m_Stream.Write( (byte) p.Count ); + m_Stream.Write((short)0x0006); + m_Stream.Write((byte)0x02); + m_Stream.Write((byte)p.Count); - m_Stream.Write( (int) removed.Serial ); + m_Stream.Write(removed.Serial); - for ( int i = 0; i < p.Count; ++i ) - m_Stream.Write( (int) p[i].Mobile.Serial ); - } - } + for (int i = 0; i < p.Count; ++i) + m_Stream.Write(p[i].Mobile.Serial); + } + } - public sealed class PartyTextMessage : Packet - { - public PartyTextMessage( bool toAll, Mobile from, string text ) : base( 0xBF ) - { - if ( text == null ) - text = ""; + public sealed class PartyTextMessage : Packet + { + public PartyTextMessage(bool toAll, Mobile from, string text) : base(0xBF) + { + if (text == null) + text = ""; - EnsureCapacity( 12 + text.Length*2 ); + EnsureCapacity(12 + text.Length * 2); - m_Stream.Write( (short) 0x0006 ); - m_Stream.Write( (byte) (toAll ? 0x04 : 0x03) ); - m_Stream.Write( (int) from.Serial ); - m_Stream.WriteBigUniNull( text ); - } - } + m_Stream.Write((short)0x0006); + m_Stream.Write((byte)(toAll ? 0x04 : 0x03)); + m_Stream.Write(from.Serial); + m_Stream.WriteBigUniNull(text); + } + } - public sealed class PartyInvitation : Packet - { - public PartyInvitation( Mobile leader ) : base( 0xBF ) - { - EnsureCapacity( 10 ); + public sealed class PartyInvitation : Packet + { + public PartyInvitation(Mobile leader) : base(0xBF) + { + EnsureCapacity(10); - m_Stream.Write( (short) 0x0006 ); - m_Stream.Write( (byte) 0x07 ); - m_Stream.Write( (int) leader.Serial ); - } - } + m_Stream.Write((short)0x0006); + m_Stream.Write((byte)0x07); + m_Stream.Write(leader.Serial); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Party/Party.cs b/Scripts/Engines/Party/Party.cs index 73458eb93..060a9b16d 100644 --- a/Scripts/Engines/Party/Party.cs +++ b/Scripts/Engines/Party/Party.cs @@ -1,472 +1,474 @@ using System; +using System.Collections.Generic; +using Server.Commands; +using Server.Factions; using Server.Network; using Server.Targeting; -using Server.Factions; -using Server.Commands; -using System.Collections.Generic; namespace Server.Engines.PartySystem { - public class Party : IParty - { - private List m_Listeners; // staff listening - - public const int Capacity = 10; - - public static void Initialize() - { - EventSink.Logout += EventSink_Logout; - EventSink.Login += EventSink_Login; - EventSink.PlayerDeath += EventSink_PlayerDeath; - - CommandSystem.Register( "ListenToParty", AccessLevel.GameMaster, ListenToParty_OnCommand ); - } - - public static void ListenToParty_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, ListenToParty_OnTarget ); - e.Mobile.SendMessage( "Target a partied player." ); - } - - public static void ListenToParty_OnTarget( Mobile from, object obj ) - { - if ( obj is Mobile mobile ) - { - Party p = Get( mobile ); - - if ( p == null ) - { - from.SendMessage( "They are not in a party." ); - } - else if ( p.m_Listeners.Contains( from ) ) - { - p.m_Listeners.Remove( from ); - from.SendMessage( "You are no longer listening to that party." ); - } - else - { - p.m_Listeners.Add( from ); - from.SendMessage( "You are now listening to that party." ); - } - } - } - - public static void EventSink_PlayerDeath( PlayerDeathEventArgs e ) - { - Mobile from = e.Mobile; - Party p = Get( from ); - - if ( p != null ) - { - Mobile m = from.LastKiller; - - if ( m == from ) - p.SendPublicMessage( from, "I killed myself !!" ); - else if ( m == null ) - p.SendPublicMessage( from, "I was killed !!" ); - else - p.SendPublicMessage( from, $"I was killed by {m.Name} !!"); - } - } - - private class RejoinTimer : Timer - { - private Mobile m_Mobile; - - public RejoinTimer( Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - } - - protected override void OnTick() - { - Party p = Get( m_Mobile ); - - if ( p == null ) - return; - - m_Mobile.SendLocalizedMessage( 1005437 ); // You have rejoined the party. - m_Mobile.Send( new PartyMemberList( p ) ); - - Packet message = Packet.Acquire( new MessageLocalizedAffix( Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008087, "", AffixType.Prepend | AffixType.System, m_Mobile.Name, "" ) ); - Packet attrs = Packet.Acquire( new MobileAttributesN( m_Mobile ) ); - - foreach ( PartyMemberInfo mi in p.Members ) - { - Mobile m = mi.Mobile; - - if ( m != m_Mobile ) - { - m.Send( message ); - m.Send( new MobileStatusCompact( m_Mobile.CanBeRenamedBy( m ), m_Mobile ) ); - m.Send( attrs ); - m_Mobile.Send( new MobileStatusCompact( m.CanBeRenamedBy( m_Mobile ), m ) ); - m_Mobile.Send( new MobileAttributesN( m ) ); - } - } - - Packet.Release( message ); - Packet.Release( attrs ); - } - } - - public static void EventSink_Login( LoginEventArgs e ) - { - Mobile from = e.Mobile; - Party p = Get( from ); - - if ( p != null ) - new RejoinTimer( from ).Start(); - else - from.Party = null; - } - - public static void EventSink_Logout( LogoutEventArgs e ) - { - Mobile from = e.Mobile; - Party p = Get( from ); - - p?.Remove( from ); - - from.Party = null; - } - - public static Party Get( Mobile m ) - { - return m?.Party as Party; - } - - public Party( Mobile leader ) - { - Leader = leader; - - Members = new List(); - Candidates = new List(); - m_Listeners = new List(); - - Members.Add( new PartyMemberInfo( leader ) ); - } - - public void Add( Mobile m ) - { - PartyMemberInfo mi = this[m]; - - if ( mi == null ) - { - Members.Add( new PartyMemberInfo( m ) ); - m.Party = this; - - Packet memberList = Packet.Acquire( new PartyMemberList( this ) ); - Packet attrs = Packet.Acquire( new MobileAttributesN( m ) ); - - for ( int i = 0; i < Members.Count; ++i ) - { - Mobile f = ((PartyMemberInfo)Members[i]).Mobile; - - f.Send( memberList ); - - if ( f != m ) - { - f.Send( new MobileStatusCompact( m.CanBeRenamedBy( f ), m ) ); - f.Send( attrs ); - m.Send( new MobileStatusCompact( f.CanBeRenamedBy( m ), f ) ); - m.Send( new MobileAttributesN( f ) ); - } - } - - Packet.Release( memberList ); - Packet.Release( attrs ); - } - } - - public void OnAccept( Mobile from ) - { - OnAccept( from, false ); - } - - public void OnAccept( Mobile from, bool force ) - { - Faction ourFaction = Faction.Find( Leader ); - Faction theirFaction = Faction.Find( from ); - - if ( !force && ourFaction != null && theirFaction != null && ourFaction != theirFaction ) - return; - - // : joined the party. - SendToAll( new MessageLocalizedAffix( Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008094, "", AffixType.Prepend | AffixType.System, from.Name, "" ) ); - - from.SendLocalizedMessage( 1005445 ); // You have been added to the party. - - Candidates.Remove( from ); - Add( from ); - } - - public void OnDecline( Mobile from, Mobile leader ) - { - // : Does not wish to join the party. - leader.SendLocalizedMessage( 1008091, false, from.Name ); - - from.SendLocalizedMessage( 1008092 ); // You notify them that you do not wish to join the party. - - Candidates.Remove( from ); - from.Send( new PartyEmptyList( from ) ); - - if ( Candidates.Count == 0 && Members.Count <= 1 ) - { - for ( int i = 0; i < Members.Count; ++i ) - { - this[i].Mobile.Send( new PartyEmptyList( this[i].Mobile ) ); - this[i].Mobile.Party = null; - } - - Members.Clear(); - } - } - - public void Remove( Mobile m ) - { - if ( m == Leader ) - { - Disband(); - } - else - { - for ( int i = 0; i < Members.Count; ++i ) - { - if ( ((PartyMemberInfo)Members[i]).Mobile == m ) - { - Members.RemoveAt( i ); - - m.Party = null; - m.Send( new PartyEmptyList( m ) ); - - m.SendLocalizedMessage( 1005451 ); // You have been removed from the party. - - SendToAll( new PartyRemoveMember( m, this ) ); - SendToAll( 1005452 ); // A player has been removed from your party. - - break; - } - } - - if ( Members.Count == 1 ) - { - SendToAll( 1005450 ); // The last person has left the party... - Disband(); - } - } - } - - public bool Contains( Mobile m ) - { - return ( this[m] != null ); - } - - public void Disband() - { - SendToAll( 1005449 ); // Your party has disbanded. - - for ( int i = 0; i < Members.Count; ++i ) - { - this[i].Mobile.Send( new PartyEmptyList( this[i].Mobile ) ); - this[i].Mobile.Party = null; - } - - Members.Clear(); - } - - public static void Invite( Mobile from, Mobile target ) - { - Faction ourFaction = Faction.Find( from ); - Faction theirFaction = Faction.Find( target ); - - if ( ourFaction != null && theirFaction != null && ourFaction != theirFaction ) - { - from.SendLocalizedMessage( 1008088 ); // You cannot have players from opposing factions in the same party! - target.SendLocalizedMessage( 1008093 ); // The party cannot have members from opposing factions. - return; - } - - Party p = Get( from ); - - if ( p == null ) - from.Party = p = new Party( from ); - - if ( !p.Candidates.Contains( target ) ) - p.Candidates.Add( target ); - - // : You are invited to join the party. Type /accept to join or /decline to decline the offer. - target.Send( new MessageLocalizedAffix( Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008089, "", AffixType.Prepend | AffixType.System, from.Name, "" ) ); - - from.SendLocalizedMessage( 1008090 ); // You have invited them to join the party. - - target.Send( new PartyInvitation( from ) ); - target.Party = from; - - DeclineTimer.Start( target, from ); - } - - public void SendToAll( int number ) - { - SendToAll( number, "", 0x3B2 ); - } - - public void SendToAll( int number, string args ) - { - SendToAll( number, args, 0x3B2 ); - } - - public void SendToAll( int number, string args, int hue ) - { - SendToAll( new MessageLocalized( Serial.MinusOne, -1, MessageType.Regular, hue, 3, number, "System", args ) ); - } - - public void SendPublicMessage( Mobile from, string text ) - { - SendToAll( new PartyTextMessage( true, from, text ) ); - - for ( int i = 0; i < m_Listeners.Count; ++i ) - { - Mobile mob = m_Listeners[i]; - - if ( mob.Party != this ) - m_Listeners[i].SendMessage( "[{0}]: {1}", from.Name, text ); - } - - SendToStaffMessage( from, "[Party]: {0}", text ); - } - - public void SendPrivateMessage( Mobile from, Mobile to, string text ) - { - to.Send( new PartyTextMessage( false, from, text ) ); - - for ( int i = 0; i < m_Listeners.Count; ++i ) - { - Mobile mob = m_Listeners[i]; - - if ( mob.Party != this ) - m_Listeners[i].SendMessage( "[{0}]->[{1}]: {2}", from.Name, to.Name, text ); - } - - SendToStaffMessage( from, "[Party]->[{0}]: {1}", to.Name, text ); - } - - private void SendToStaffMessage( Mobile from, string text ) - { - Packet p = null; - - foreach( NetState ns in from.GetClientsInRange( 8 ) ) - { - Mobile mob = ns.Mobile; - - if ( mob != null && mob.AccessLevel >= AccessLevel.GameMaster && mob.AccessLevel > from.AccessLevel && mob.Party != this && !m_Listeners.Contains( mob ) ) - { - if ( p == null ) - p = Packet.Acquire( new UnicodeMessage( from.Serial, from.Body, MessageType.Regular, from.SpeechHue, 3, from.Language, from.Name, text ) ); - - ns.Send( p ); - } - } - - Packet.Release( p ); - } - private void SendToStaffMessage( Mobile from, string format, params object[] args ) - { - SendToStaffMessage( from, string.Format( format, args ) ); - } - - public void SendToAll( Packet p ) - { - p.Acquire(); - - for ( int i = 0; i < Members.Count; ++i ) - Members[i].Mobile.Send( p ); - - if ( p is MessageLocalized || p is MessageLocalizedAffix || p is UnicodeMessage || p is AsciiMessage ) - { - for ( int i = 0; i < m_Listeners.Count; ++i ) - { - Mobile mob = m_Listeners[i]; - - if ( mob.Party != this ) - mob.Send( p ); - } - } - - p.Release(); - } - - public void OnStamChanged( Mobile m ) - { - Packet p = null; - - for ( int i = 0; i < Members.Count; ++i ) - { - Mobile c = Members[i].Mobile; - - if ( c != m && m.Map == c.Map && Utility.InUpdateRange( c, m ) && c.CanSee( m ) ) - { - if ( p == null ) - p = Packet.Acquire( new MobileStamN( m ) ); - - c.Send( p ); - } - } - - Packet.Release( p ); - } - - public void OnManaChanged( Mobile m ) - { - Packet p = null; - - for ( int i = 0; i < Members.Count; ++i ) - { - Mobile c = Members[i].Mobile; - - if ( c != m && m.Map == c.Map && Utility.InUpdateRange( c, m ) && c.CanSee( m ) ) - { - if ( p == null ) - p = Packet.Acquire( new MobileManaN( m ) ); - - c.Send( p ); - } - } - - Packet.Release( p ); - } - - public void OnStatsQuery( Mobile beholder, Mobile beheld ) - { - if ( beholder != beheld && Contains( beholder ) && beholder.Map == beheld.Map && Utility.InUpdateRange( beholder, beheld ) ) - { - if ( !beholder.CanSee( beheld ) ) - beholder.Send( new MobileStatusCompact( beheld.CanBeRenamedBy( beholder ), beheld ) ); - - beholder.Send( new MobileAttributesN( beheld ) ); - } - } - - public int Count => Members.Count; - public bool Active => Members.Count > 1; - public Mobile Leader { get; } - - public List Members { get; } - - public List Candidates { get; } - - public PartyMemberInfo this[int index] => Members[index]; - - public PartyMemberInfo this[Mobile m] - { - get - { - for ( int i = 0; i < Members.Count; ++i ) - if ( Members[i].Mobile == m ) - return Members[i]; - - return null; - } - } - } -} + public class Party : IParty + { + public const int Capacity = 10; + private List m_Listeners; // staff listening + + public Party(Mobile leader) + { + Leader = leader; + + Members = new List(); + Candidates = new List(); + m_Listeners = new List(); + + Members.Add(new PartyMemberInfo(leader)); + } + + public int Count => Members.Count; + public bool Active => Members.Count > 1; + public Mobile Leader{ get; } + + public List Members{ get; } + + public List Candidates{ get; } + + public PartyMemberInfo this[int index] => Members[index]; + + public PartyMemberInfo this[Mobile m] + { + get + { + for (int i = 0; i < Members.Count; ++i) + if (Members[i].Mobile == m) + return Members[i]; + + return null; + } + } + + public void OnStamChanged(Mobile m) + { + Packet p = null; + + for (int i = 0; i < Members.Count; ++i) + { + Mobile c = Members[i].Mobile; + + if (c != m && m.Map == c.Map && Utility.InUpdateRange(c, m) && c.CanSee(m)) + { + if (p == null) + p = Packet.Acquire(new MobileStamN(m)); + + c.Send(p); + } + } + + Packet.Release(p); + } + + public void OnManaChanged(Mobile m) + { + Packet p = null; + + for (int i = 0; i < Members.Count; ++i) + { + Mobile c = Members[i].Mobile; + + if (c != m && m.Map == c.Map && Utility.InUpdateRange(c, m) && c.CanSee(m)) + { + if (p == null) + p = Packet.Acquire(new MobileManaN(m)); + + c.Send(p); + } + } + + Packet.Release(p); + } + + public void OnStatsQuery(Mobile beholder, Mobile beheld) + { + if (beholder != beheld && Contains(beholder) && beholder.Map == beheld.Map && + Utility.InUpdateRange(beholder, beheld)) + { + if (!beholder.CanSee(beheld)) + beholder.Send(new MobileStatusCompact(beheld.CanBeRenamedBy(beholder), beheld)); + + beholder.Send(new MobileAttributesN(beheld)); + } + } + + public static void Initialize() + { + EventSink.Logout += EventSink_Logout; + EventSink.Login += EventSink_Login; + EventSink.PlayerDeath += EventSink_PlayerDeath; + + CommandSystem.Register("ListenToParty", AccessLevel.GameMaster, ListenToParty_OnCommand); + } + + public static void ListenToParty_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, ListenToParty_OnTarget); + e.Mobile.SendMessage("Target a partied player."); + } + + public static void ListenToParty_OnTarget(Mobile from, object obj) + { + if (obj is Mobile mobile) + { + Party p = Get(mobile); + + if (p == null) + { + from.SendMessage("They are not in a party."); + } + else if (p.m_Listeners.Contains(from)) + { + p.m_Listeners.Remove(from); + from.SendMessage("You are no longer listening to that party."); + } + else + { + p.m_Listeners.Add(from); + from.SendMessage("You are now listening to that party."); + } + } + } + + public static void EventSink_PlayerDeath(PlayerDeathEventArgs e) + { + Mobile from = e.Mobile; + Party p = Get(from); + + if (p != null) + { + Mobile m = from.LastKiller; + + if (m == from) + p.SendPublicMessage(from, "I killed myself !!"); + else if (m == null) + p.SendPublicMessage(from, "I was killed !!"); + else + p.SendPublicMessage(from, $"I was killed by {m.Name} !!"); + } + } + + public static void EventSink_Login(LoginEventArgs e) + { + Mobile from = e.Mobile; + Party p = Get(from); + + if (p != null) + new RejoinTimer(from).Start(); + else + from.Party = null; + } + + public static void EventSink_Logout(LogoutEventArgs e) + { + Mobile from = e.Mobile; + Party p = Get(from); + + p?.Remove(from); + + from.Party = null; + } + + public static Party Get(Mobile m) + { + return m?.Party as Party; + } + + public void Add(Mobile m) + { + PartyMemberInfo mi = this[m]; + + if (mi == null) + { + Members.Add(new PartyMemberInfo(m)); + m.Party = this; + + Packet memberList = Packet.Acquire(new PartyMemberList(this)); + Packet attrs = Packet.Acquire(new MobileAttributesN(m)); + + for (int i = 0; i < Members.Count; ++i) + { + Mobile f = Members[i].Mobile; + + f.Send(memberList); + + if (f != m) + { + f.Send(new MobileStatusCompact(m.CanBeRenamedBy(f), m)); + f.Send(attrs); + m.Send(new MobileStatusCompact(f.CanBeRenamedBy(m), f)); + m.Send(new MobileAttributesN(f)); + } + } + + Packet.Release(memberList); + Packet.Release(attrs); + } + } + + public void OnAccept(Mobile from) + { + OnAccept(from, false); + } + + public void OnAccept(Mobile from, bool force) + { + Faction ourFaction = Faction.Find(Leader); + Faction theirFaction = Faction.Find(from); + + if (!force && ourFaction != null && theirFaction != null && ourFaction != theirFaction) + return; + + // : joined the party. + SendToAll(new MessageLocalizedAffix(Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008094, "", + AffixType.Prepend | AffixType.System, from.Name, "")); + + from.SendLocalizedMessage(1005445); // You have been added to the party. + + Candidates.Remove(from); + Add(from); + } + + public void OnDecline(Mobile from, Mobile leader) + { + // : Does not wish to join the party. + leader.SendLocalizedMessage(1008091, false, from.Name); + + from.SendLocalizedMessage(1008092); // You notify them that you do not wish to join the party. + + Candidates.Remove(from); + from.Send(new PartyEmptyList(from)); + + if (Candidates.Count == 0 && Members.Count <= 1) + { + for (int i = 0; i < Members.Count; ++i) + { + this[i].Mobile.Send(new PartyEmptyList(this[i].Mobile)); + this[i].Mobile.Party = null; + } + + Members.Clear(); + } + } + + public void Remove(Mobile m) + { + if (m == Leader) + { + Disband(); + } + else + { + for (int i = 0; i < Members.Count; ++i) + if (Members[i].Mobile == m) + { + Members.RemoveAt(i); + + m.Party = null; + m.Send(new PartyEmptyList(m)); + + m.SendLocalizedMessage(1005451); // You have been removed from the party. + + SendToAll(new PartyRemoveMember(m, this)); + SendToAll(1005452); // A player has been removed from your party. + + break; + } + + if (Members.Count == 1) + { + SendToAll(1005450); // The last person has left the party... + Disband(); + } + } + } + + public bool Contains(Mobile m) + { + return this[m] != null; + } + + public void Disband() + { + SendToAll(1005449); // Your party has disbanded. + + for (int i = 0; i < Members.Count; ++i) + { + this[i].Mobile.Send(new PartyEmptyList(this[i].Mobile)); + this[i].Mobile.Party = null; + } + + Members.Clear(); + } + + public static void Invite(Mobile from, Mobile target) + { + Faction ourFaction = Faction.Find(from); + Faction theirFaction = Faction.Find(target); + + if (ourFaction != null && theirFaction != null && ourFaction != theirFaction) + { + from.SendLocalizedMessage(1008088); // You cannot have players from opposing factions in the same party! + target.SendLocalizedMessage(1008093); // The party cannot have members from opposing factions. + return; + } + + Party p = Get(from); + + if (p == null) + from.Party = p = new Party(from); + + if (!p.Candidates.Contains(target)) + p.Candidates.Add(target); + + // : You are invited to join the party. Type /accept to join or /decline to decline the offer. + target.Send(new MessageLocalizedAffix(Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008089, "", + AffixType.Prepend | AffixType.System, from.Name, "")); + + from.SendLocalizedMessage(1008090); // You have invited them to join the party. + + target.Send(new PartyInvitation(from)); + target.Party = from; + + DeclineTimer.Start(target, from); + } + + public void SendToAll(int number) + { + SendToAll(number, "", 0x3B2); + } + + public void SendToAll(int number, string args) + { + SendToAll(number, args, 0x3B2); + } + + public void SendToAll(int number, string args, int hue) + { + SendToAll(new MessageLocalized(Serial.MinusOne, -1, MessageType.Regular, hue, 3, number, "System", args)); + } + + public void SendPublicMessage(Mobile from, string text) + { + SendToAll(new PartyTextMessage(true, from, text)); + + for (int i = 0; i < m_Listeners.Count; ++i) + { + Mobile mob = m_Listeners[i]; + + if (mob.Party != this) + m_Listeners[i].SendMessage("[{0}]: {1}", from.Name, text); + } + + SendToStaffMessage(from, "[Party]: {0}", text); + } + + public void SendPrivateMessage(Mobile from, Mobile to, string text) + { + to.Send(new PartyTextMessage(false, from, text)); + + for (int i = 0; i < m_Listeners.Count; ++i) + { + Mobile mob = m_Listeners[i]; + + if (mob.Party != this) + m_Listeners[i].SendMessage("[{0}]->[{1}]: {2}", from.Name, to.Name, text); + } + + SendToStaffMessage(from, "[Party]->[{0}]: {1}", to.Name, text); + } + + private void SendToStaffMessage(Mobile from, string text) + { + Packet p = null; + + foreach (NetState ns in from.GetClientsInRange(8)) + { + Mobile mob = ns.Mobile; + + if (mob != null && mob.AccessLevel >= AccessLevel.GameMaster && mob.AccessLevel > from.AccessLevel && + mob.Party != this && !m_Listeners.Contains(mob)) + { + if (p == null) + p = Packet.Acquire(new UnicodeMessage(from.Serial, from.Body, MessageType.Regular, from.SpeechHue, 3, + from.Language, from.Name, text)); + + ns.Send(p); + } + } + + Packet.Release(p); + } + + private void SendToStaffMessage(Mobile from, string format, params object[] args) + { + SendToStaffMessage(from, string.Format(format, args)); + } + + public void SendToAll(Packet p) + { + p.Acquire(); + + for (int i = 0; i < Members.Count; ++i) + Members[i].Mobile.Send(p); + + if (p is MessageLocalized || p is MessageLocalizedAffix || p is UnicodeMessage || p is AsciiMessage) + for (int i = 0; i < m_Listeners.Count; ++i) + { + Mobile mob = m_Listeners[i]; + + if (mob.Party != this) + mob.Send(p); + } + + p.Release(); + } + + private class RejoinTimer : Timer + { + private Mobile m_Mobile; + + public RejoinTimer(Mobile m) : base(TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + } + + protected override void OnTick() + { + Party p = Get(m_Mobile); + + if (p == null) + return; + + m_Mobile.SendLocalizedMessage(1005437); // You have rejoined the party. + m_Mobile.Send(new PartyMemberList(p)); + + Packet message = Packet.Acquire(new MessageLocalizedAffix(Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, + 1008087, "", AffixType.Prepend | AffixType.System, m_Mobile.Name, "")); + Packet attrs = Packet.Acquire(new MobileAttributesN(m_Mobile)); + + foreach (PartyMemberInfo mi in p.Members) + { + Mobile m = mi.Mobile; + + if (m != m_Mobile) + { + m.Send(message); + m.Send(new MobileStatusCompact(m_Mobile.CanBeRenamedBy(m), m_Mobile)); + m.Send(attrs); + m_Mobile.Send(new MobileStatusCompact(m.CanBeRenamedBy(m_Mobile), m)); + m_Mobile.Send(new MobileAttributesN(m)); + } + } + + Packet.Release(message); + Packet.Release(attrs); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Party/PartyCommands.cs b/Scripts/Engines/Party/PartyCommands.cs index 3eb3ed21a..a7b090b02 100644 --- a/Scripts/Engines/Party/PartyCommands.cs +++ b/Scripts/Engines/Party/PartyCommands.cs @@ -1,119 +1,120 @@ namespace Server.Engines.PartySystem { - public class PartyCommandHandlers : PartyCommands - { - public static void Initialize() - { - Handler = new PartyCommandHandlers(); - } + public class PartyCommandHandlers : PartyCommands + { + public static void Initialize() + { + Handler = new PartyCommandHandlers(); + } - public override void OnAdd( Mobile from ) - { - Party p = Party.Get( from ); + public override void OnAdd(Mobile from) + { + Party p = Party.Get(from); - if ( p != null && p.Leader != from ) - from.SendLocalizedMessage( 1005453 ); // You may only add members to the party if you are the leader. - else if ( p != null && (p.Members.Count + p.Candidates.Count) >= Party.Capacity ) - from.SendLocalizedMessage( 1008095 ); // You may only have 10 in your party (this includes candidates). - else - from.Target = new AddPartyTarget( from ); - } + if (p != null && p.Leader != from) + from.SendLocalizedMessage(1005453); // You may only add members to the party if you are the leader. + else if (p != null && p.Members.Count + p.Candidates.Count >= Party.Capacity) + from.SendLocalizedMessage(1008095); // You may only have 10 in your party (this includes candidates). + else + from.Target = new AddPartyTarget(from); + } - public override void OnRemove( Mobile from, Mobile target ) - { - Party p = Party.Get( from ); + public override void OnRemove(Mobile from, Mobile target) + { + Party p = Party.Get(from); - if ( p == null ) - { - from.SendLocalizedMessage( 3000211 ); // You are not in a party. - return; - } + if (p == null) + { + from.SendLocalizedMessage(3000211); // You are not in a party. + return; + } - if ( p.Leader == from && target == null ) - { - from.SendLocalizedMessage( 1005455 ); // Who would you like to remove from your party? - from.Target = new RemovePartyTarget(); - } - else if ( (p.Leader == from || from == target) && p.Contains( target ) ) - { - p.Remove( target ); - } - } + if (p.Leader == from && target == null) + { + from.SendLocalizedMessage(1005455); // Who would you like to remove from your party? + from.Target = new RemovePartyTarget(); + } + else if ((p.Leader == from || from == target) && p.Contains(target)) + { + p.Remove(target); + } + } - public override void OnPrivateMessage( Mobile from, Mobile target, string text ) - { - if ( text.Length > 128 || (text = text.Trim()).Length == 0 ) - return; + public override void OnPrivateMessage(Mobile from, Mobile target, string text) + { + if (text.Length > 128 || (text = text.Trim()).Length == 0) + return; - Party p = Party.Get( from ); + Party p = Party.Get(from); - if ( p != null && p.Contains( target ) ) - p.SendPrivateMessage( from, target, text ); - else - from.SendLocalizedMessage( 3000211 ); // You are not in a party. - } + if (p != null && p.Contains(target)) + p.SendPrivateMessage(from, target, text); + else + from.SendLocalizedMessage(3000211); // You are not in a party. + } - public override void OnPublicMessage( Mobile from, string text ) - { - if ( text.Length > 128 || (text = text.Trim()).Length == 0 ) - return; + public override void OnPublicMessage(Mobile from, string text) + { + if (text.Length > 128 || (text = text.Trim()).Length == 0) + return; - Party p = Party.Get( from ); + Party p = Party.Get(from); - if ( p != null ) - p.SendPublicMessage( from, text ); - else - from.SendLocalizedMessage( 3000211 ); // You are not in a party. - } + if (p != null) + p.SendPublicMessage(from, text); + else + from.SendLocalizedMessage(3000211); // You are not in a party. + } - public override void OnSetCanLoot( Mobile from, bool canLoot ) - { - Party p = Party.Get( from ); + public override void OnSetCanLoot(Mobile from, bool canLoot) + { + Party p = Party.Get(from); - if ( p == null ) - { - from.SendLocalizedMessage( 3000211 ); // You are not in a party. - } - else - { - PartyMemberInfo mi = p[from]; + if (p == null) + { + from.SendLocalizedMessage(3000211); // You are not in a party. + } + else + { + PartyMemberInfo mi = p[from]; - if ( mi != null ) - { - mi.CanLoot = canLoot; + if (mi != null) + { + mi.CanLoot = canLoot; - if ( canLoot ) - from.SendLocalizedMessage( 1005447 ); // You have chosen to allow your party to loot your corpse. - else - from.SendLocalizedMessage( 1005448 ); // You have chosen to prevent your party from looting your corpse. - } - } - } + if (canLoot) + from.SendLocalizedMessage(1005447); // You have chosen to allow your party to loot your corpse. + else + from.SendLocalizedMessage( + 1005448); // You have chosen to prevent your party from looting your corpse. + } + } + } - public override void OnAccept( Mobile from, Mobile sentLeader ) - { - Mobile leader = from.Party as Mobile; - from.Party = null; + public override void OnAccept(Mobile from, Mobile sentLeader) + { + Mobile leader = from.Party as Mobile; + from.Party = null; - Party p = Party.Get( leader ); + Party p = Party.Get(leader); - if ( leader == null || p == null || !p.Candidates.Contains( from ) ) - from.SendLocalizedMessage( 3000222 ); // No one has invited you to be in a party. - else if ( (p.Members.Count + p.Candidates.Count) <= Party.Capacity ) - p.OnAccept( from ); - } + if (leader == null || p == null || !p.Candidates.Contains(from)) + from.SendLocalizedMessage(3000222); // No one has invited you to be in a party. + else if (p.Members.Count + p.Candidates.Count <= Party.Capacity) + p.OnAccept(from); + } - public override void OnDecline( Mobile from, Mobile sentLeader ) - { - Mobile leader = from.Party as Mobile; - from.Party = null; + public override void OnDecline(Mobile from, Mobile sentLeader) + { + Mobile leader = from.Party as Mobile; + from.Party = null; - Party p = Party.Get( leader ); + Party p = Party.Get(leader); - if ( leader == null || p == null || !p.Candidates.Contains( from ) ) - from.SendLocalizedMessage( 3000222 ); // No one has invited you to be in a party. - else - p.OnDecline( from, leader ); - } - } + if (leader == null || p == null || !p.Candidates.Contains(from)) + from.SendLocalizedMessage(3000222); // No one has invited you to be in a party. + else + p.OnDecline(from, leader); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Party/PartyMemberInfo.cs b/Scripts/Engines/Party/PartyMemberInfo.cs index 68df0113d..59f56060f 100644 --- a/Scripts/Engines/Party/PartyMemberInfo.cs +++ b/Scripts/Engines/Party/PartyMemberInfo.cs @@ -1,15 +1,15 @@ namespace Server.Engines.PartySystem { - public class PartyMemberInfo - { - public Mobile Mobile { get; } + public class PartyMemberInfo + { + public PartyMemberInfo(Mobile m) + { + Mobile = m; + CanLoot = !Core.ML; + } - public bool CanLoot { get; set; } + public Mobile Mobile{ get; } - public PartyMemberInfo( Mobile m ) - { - Mobile = m; - CanLoot = !Core.ML; - } - } + public bool CanLoot{ get; set; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Party/RemoveFromParty.cs b/Scripts/Engines/Party/RemoveFromParty.cs index af0a190cf..9e6413dd9 100644 --- a/Scripts/Engines/Party/RemoveFromParty.cs +++ b/Scripts/Engines/Party/RemoveFromParty.cs @@ -2,28 +2,28 @@ using Server.Engines.PartySystem; namespace Server.ContextMenus { - public class RemoveFromPartyEntry : ContextMenuEntry - { - private Mobile m_From; - private Mobile m_Target; - - public RemoveFromPartyEntry( Mobile from, Mobile target ) : base( 0198, 12 ) - { - m_From = from; - m_Target = target; - } + public class RemoveFromPartyEntry : ContextMenuEntry + { + private Mobile m_From; + private Mobile m_Target; - public override void OnClick() - { - Party p = Party.Get( m_From ); + public RemoveFromPartyEntry(Mobile from, Mobile target) : base(0198, 12) + { + m_From = from; + m_Target = target; + } - if ( p == null || p.Leader != m_From || !p.Contains( m_Target ) ) - return; + public override void OnClick() + { + Party p = Party.Get(m_From); - if ( m_From == m_Target ) - m_From.SendLocalizedMessage( 1005446 ); // You may only remove yourself from a party if you are not the leader. - else - p.Remove( m_Target ); - } - } -} + if (p == null || p.Leader != m_From || !p.Contains(m_Target)) + return; + + if (m_From == m_Target) + m_From.SendLocalizedMessage(1005446); // You may only remove yourself from a party if you are not the leader. + else + p.Remove(m_Target); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Party/RemovePartyTarget.cs b/Scripts/Engines/Party/RemovePartyTarget.cs index d978ab6a9..819b99cf1 100644 --- a/Scripts/Engines/Party/RemovePartyTarget.cs +++ b/Scripts/Engines/Party/RemovePartyTarget.cs @@ -2,26 +2,27 @@ using Server.Targeting; namespace Server.Engines.PartySystem { - public class RemovePartyTarget : Target - { - public RemovePartyTarget() : base( 8, false, TargetFlags.None ) - { - } + public class RemovePartyTarget : Target + { + public RemovePartyTarget() : base(8, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile m ) - { - Party p = Party.Get( from ); + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile m) + { + Party p = Party.Get(from); - if ( p == null || p.Leader != from || !p.Contains( m ) ) - return; + if (p == null || p.Leader != from || !p.Contains(m)) + return; - if ( from == m ) - from.SendLocalizedMessage( 1005446 ); // You may only remove yourself from a party if you are not the leader. - else - p.Remove( m ); - } - } - } -} + if (from == m) + from.SendLocalizedMessage( + 1005446); // You may only remove yourself from a party if you are not the leader. + else + p.Remove(m); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Pathing/FastAStarAlgorithm.cs b/Scripts/Engines/Pathing/FastAStarAlgorithm.cs index 23cc8a9a3..c742cb59a 100644 --- a/Scripts/Engines/Pathing/FastAStarAlgorithm.cs +++ b/Scripts/Engines/Pathing/FastAStarAlgorithm.cs @@ -5,288 +5,313 @@ using MoveImpl = Server.Movement.MovementImpl; namespace Server.PathAlgorithms.FastAStar { - public struct PathNode - { - public int cost, total; - public int parent, next, prev; - public int z; - } + public struct PathNode + { + public int cost, total; + public int parent, next, prev; + public int z; + } - public class FastAStarAlgorithm : PathAlgorithm - { - public static PathAlgorithm Instance = new FastAStarAlgorithm(); + public class FastAStarAlgorithm : PathAlgorithm + { + private const int MaxDepth = 300; + private const int AreaSize = 38; - private const int MaxDepth = 300; - private const int AreaSize = 38; + private const int NodeCount = AreaSize * AreaSize * PlaneCount; - private const int NodeCount = AreaSize * AreaSize * PlaneCount; + private const int PlaneOffset = 128; + private const int PlaneCount = 13; + private const int PlaneHeight = 20; + public static PathAlgorithm Instance = new FastAStarAlgorithm(); - private const int PlaneOffset = 128; - private const int PlaneCount = 13; - private const int PlaneHeight = 20; + private static Direction[] m_Path = new Direction[AreaSize * AreaSize]; + private static PathNode[] m_Nodes = new PathNode[NodeCount]; + private static BitArray m_Touched = new BitArray(NodeCount); + private static BitArray m_OnOpen = new BitArray(NodeCount); + private static int[] m_Successors = new int[8]; - private static Direction[] m_Path = new Direction[AreaSize * AreaSize]; - private static PathNode[] m_Nodes = new PathNode[NodeCount]; - private static BitArray m_Touched = new BitArray( NodeCount ); - private static BitArray m_OnOpen = new BitArray( NodeCount ); - private static int[] m_Successors = new int[8]; + private static int m_xOffset, m_yOffset; + private static int m_OpenList; - private static int m_xOffset, m_yOffset; - private static int m_OpenList; + private Point3D m_Goal; - private Point3D m_Goal; + public int Heuristic(int x, int y, int z) + { + x -= m_Goal.X - m_xOffset; + y -= m_Goal.Y - m_yOffset; + z -= m_Goal.Z; - public int Heuristic( int x, int y, int z ) - { - x -= m_Goal.X - m_xOffset; - y -= m_Goal.Y - m_yOffset; - z -= m_Goal.Z; + x *= 11; + y *= 11; - x *= 11; - y *= 11; + return x * x + y * y + z * z; + } - return (x*x)+(y*y)+(z*z); - } + public override bool CheckCondition(Mobile m, Map map, Point3D start, Point3D goal) + { + return Utility.InRange(start, goal, AreaSize); + } - public override bool CheckCondition( Mobile m, Map map, Point3D start, Point3D goal ) - { - return Utility.InRange( start, goal, AreaSize ); - } + private void RemoveFromChain(int node) + { + if (node < 0 || node >= NodeCount) + return; - private void RemoveFromChain( int node ) - { - if ( node < 0 || node >= NodeCount ) - return; + if (!m_Touched[node] || !m_OnOpen[node]) + return; - if ( !m_Touched[node] || !m_OnOpen[node] ) - return; + int prev = m_Nodes[node].prev; + int next = m_Nodes[node].next; - int prev = m_Nodes[node].prev; - int next = m_Nodes[node].next; + if (m_OpenList == node) + m_OpenList = next; - if ( m_OpenList == node ) - m_OpenList = next; + if (prev != -1) + m_Nodes[prev].next = next; - if ( prev != -1 ) - m_Nodes[prev].next = next; + if (next != -1) + m_Nodes[next].prev = prev; - if ( next != -1 ) - m_Nodes[next].prev = prev; + m_Nodes[node].prev = -1; + m_Nodes[node].next = -1; + } - m_Nodes[node].prev = -1; - m_Nodes[node].next = -1; - } + private void AddToChain(int node) + { + if (node < 0 || node >= NodeCount) + return; - private void AddToChain( int node ) - { - if ( node < 0 || node >= NodeCount ) - return; + RemoveFromChain(node); - RemoveFromChain( node ); + if (m_OpenList != -1) + m_Nodes[m_OpenList].prev = node; - if ( m_OpenList != -1 ) - m_Nodes[m_OpenList].prev = node; + m_Nodes[node].next = m_OpenList; + m_Nodes[node].prev = -1; - m_Nodes[node].next = m_OpenList; - m_Nodes[node].prev = -1; + m_OpenList = node; - m_OpenList = node; + m_Touched[node] = true; + m_OnOpen[node] = true; + } - m_Touched[node] = true; - m_OnOpen[node] = true; - } + public override Direction[] Find(Mobile m, Map map, Point3D start, Point3D goal) + { + if (!Utility.InRange(start, goal, AreaSize)) + return null; - public override Direction[] Find( Mobile m, Map map, Point3D start, Point3D goal ) - { - if ( !Utility.InRange( start, goal, AreaSize ) ) - return null; + m_Touched.SetAll(false); - m_Touched.SetAll( false ); + m_Goal = goal; - m_Goal = goal; + m_xOffset = (start.X + goal.X - AreaSize) / 2; + m_yOffset = (start.Y + goal.Y - AreaSize) / 2; - m_xOffset = (start.X + goal.X - AreaSize) / 2; - m_yOffset = (start.Y + goal.Y - AreaSize) / 2; + int fromNode = GetIndex(start.X, start.Y, start.Z); + int destNode = GetIndex(goal.X, goal.Y, goal.Z); - int fromNode = GetIndex( start.X, start.Y, start.Z ); - int destNode = GetIndex( goal.X, goal.Y, goal.Z ); + m_OpenList = fromNode; - m_OpenList = fromNode; + m_Nodes[m_OpenList].cost = 0; + m_Nodes[m_OpenList].total = Heuristic(start.X - m_xOffset, start.Y - m_yOffset, start.Z); + m_Nodes[m_OpenList].parent = -1; + m_Nodes[m_OpenList].next = -1; + m_Nodes[m_OpenList].prev = -1; + m_Nodes[m_OpenList].z = start.Z; - m_Nodes[m_OpenList].cost = 0; - m_Nodes[m_OpenList].total = Heuristic( start.X - m_xOffset, start.Y - m_yOffset, start.Z ); - m_Nodes[m_OpenList].parent = -1; - m_Nodes[m_OpenList].next = -1; - m_Nodes[m_OpenList].prev = -1; - m_Nodes[m_OpenList].z = start.Z; + m_OnOpen[m_OpenList] = true; + m_Touched[m_OpenList] = true; - m_OnOpen[m_OpenList] = true; - m_Touched[m_OpenList] = true; + BaseCreature bc = m as BaseCreature; - BaseCreature bc = m as BaseCreature; + int pathCount, parent; + int backtrack = 0, depth = 0; - int pathCount, parent; - int backtrack = 0, depth = 0; + Direction[] path = m_Path; - Direction[] path = m_Path; + while (m_OpenList != -1) + { + int bestNode = FindBest(m_OpenList); - while ( m_OpenList != -1 ) - { - int bestNode = FindBest( m_OpenList ); + if (++depth > MaxDepth) + break; - if ( ++depth > MaxDepth ) - break; + if (bc != null) + { + MoveImpl.AlwaysIgnoreDoors = bc.CanOpenDoors; + MoveImpl.IgnoreMovableImpassables = bc.CanMoveOverObstacles; + } - if ( bc != null ) - { - MoveImpl.AlwaysIgnoreDoors = bc.CanOpenDoors; - MoveImpl.IgnoreMovableImpassables = bc.CanMoveOverObstacles; - } + MoveImpl.Goal = goal; - MoveImpl.Goal = goal; + int[] vals = m_Successors; + int count = GetSuccessors(bestNode, m, map); - int[] vals = m_Successors; - int count = GetSuccessors( bestNode, m, map ); + MoveImpl.AlwaysIgnoreDoors = false; + MoveImpl.IgnoreMovableImpassables = false; + MoveImpl.Goal = Point3D.Zero; - MoveImpl.AlwaysIgnoreDoors = false; - MoveImpl.IgnoreMovableImpassables = false; - MoveImpl.Goal = Point3D.Zero; + if (count == 0) + break; - if ( count == 0 ) - break; + for (int i = 0; i < count; ++i) + { + int newNode = vals[i]; - for ( int i = 0; i < count; ++i ) - { - int newNode = vals[i]; + bool wasTouched = m_Touched[newNode]; - bool wasTouched = m_Touched[newNode]; + if (!wasTouched) + { + int newCost = m_Nodes[bestNode].cost + 1; + int newTotal = newCost + Heuristic(newNode % AreaSize, newNode / AreaSize % AreaSize, + m_Nodes[newNode].z); - if ( !wasTouched ) - { - int newCost = m_Nodes[bestNode].cost + 1; - int newTotal = newCost + Heuristic( newNode % AreaSize, (newNode / AreaSize) % AreaSize, m_Nodes[newNode].z ); - - if ( !wasTouched || m_Nodes[newNode].total > newTotal ) - { - m_Nodes[newNode].parent = bestNode; - m_Nodes[newNode].cost = newCost; - m_Nodes[newNode].total = newTotal; - - if ( !wasTouched || !m_OnOpen[newNode] ) - { - AddToChain( newNode ); - - if ( newNode == destNode ) - { - pathCount = 0; - parent = m_Nodes[newNode].parent; - - while ( parent != -1 ) - { - path[pathCount++] = GetDirection( parent % AreaSize, (parent / AreaSize) % AreaSize, newNode % AreaSize, (newNode / AreaSize) % AreaSize ); - newNode = parent; - parent = m_Nodes[newNode].parent; - - if ( newNode == fromNode ) - break; - } - - Direction[] dirs = new Direction[pathCount]; - - while ( pathCount > 0 ) - dirs[backtrack++] = path[--pathCount]; - - return dirs; - } - } - } - } - } - } - - return null; - } - - private int GetIndex( int x, int y, int z ) - { - x -= m_xOffset; - y -= m_yOffset; - z += PlaneOffset; - z /= PlaneHeight; - - return x + (y * AreaSize) + (z * AreaSize * AreaSize); - } - - private int FindBest( int node ) - { - int least = m_Nodes[node].total; - int leastNode = node; - - while ( node != -1 ) - { - if ( m_Nodes[node].total < least ) - { - least = m_Nodes[node].total; - leastNode = node; - } - - node = m_Nodes[node].next; - } - - RemoveFromChain( leastNode ); - - m_Touched[leastNode] = true; - m_OnOpen[leastNode] = false; - - return leastNode; - } - - public int GetSuccessors( int p, Mobile m, Map map ) - { - int px = p % AreaSize; - int py = (p / AreaSize) % AreaSize; - int pz = m_Nodes[p].z; - int x, y, z; - - Point3D p3D = new Point3D( px + m_xOffset, py + m_yOffset, pz ); - - int[] vals = m_Successors; - int count = 0; - - for ( int i = 0; i < 8; ++i ) - { - switch ( i ) - { - default: - case 0: x = 0; y = -1; break; - case 1: x = 1; y = -1; break; - case 2: x = 1; y = 0; break; - case 3: x = 1; y = 1; break; - case 4: x = 0; y = 1; break; - case 5: x = -1; y = 1; break; - case 6: x = -1; y = 0; break; - case 7: x = -1; y = -1; break; - } - - x += px; - y += py; - - if ( x < 0 || x >= AreaSize || y < 0 || y >= AreaSize ) - continue; - - if ( CalcMoves.CheckMovement( m, map, p3D, (Direction)i, out z ) ) - { - int idx = GetIndex( x + m_xOffset, y + m_yOffset, z ); - - if ( idx >= 0 && idx < NodeCount ) - { - m_Nodes[idx].z = z; - vals[count++] = idx; - } - } - } - - return count; - } - } -} + if (!wasTouched || m_Nodes[newNode].total > newTotal) + { + m_Nodes[newNode].parent = bestNode; + m_Nodes[newNode].cost = newCost; + m_Nodes[newNode].total = newTotal; + + if (!wasTouched || !m_OnOpen[newNode]) + { + AddToChain(newNode); + + if (newNode == destNode) + { + pathCount = 0; + parent = m_Nodes[newNode].parent; + + while (parent != -1) + { + path[pathCount++] = GetDirection(parent % AreaSize, parent / AreaSize % AreaSize, + newNode % AreaSize, newNode / AreaSize % AreaSize); + newNode = parent; + parent = m_Nodes[newNode].parent; + + if (newNode == fromNode) + break; + } + + Direction[] dirs = new Direction[pathCount]; + + while (pathCount > 0) + dirs[backtrack++] = path[--pathCount]; + + return dirs; + } + } + } + } + } + } + + return null; + } + + private int GetIndex(int x, int y, int z) + { + x -= m_xOffset; + y -= m_yOffset; + z += PlaneOffset; + z /= PlaneHeight; + + return x + y * AreaSize + z * AreaSize * AreaSize; + } + + private int FindBest(int node) + { + int least = m_Nodes[node].total; + int leastNode = node; + + while (node != -1) + { + if (m_Nodes[node].total < least) + { + least = m_Nodes[node].total; + leastNode = node; + } + + node = m_Nodes[node].next; + } + + RemoveFromChain(leastNode); + + m_Touched[leastNode] = true; + m_OnOpen[leastNode] = false; + + return leastNode; + } + + public int GetSuccessors(int p, Mobile m, Map map) + { + int px = p % AreaSize; + int py = p / AreaSize % AreaSize; + int pz = m_Nodes[p].z; + int x, y, z; + + Point3D p3D = new Point3D(px + m_xOffset, py + m_yOffset, pz); + + int[] vals = m_Successors; + int count = 0; + + for (int i = 0; i < 8; ++i) + { + switch (i) + { + default: + case 0: + x = 0; + y = -1; + break; + case 1: + x = 1; + y = -1; + break; + case 2: + x = 1; + y = 0; + break; + case 3: + x = 1; + y = 1; + break; + case 4: + x = 0; + y = 1; + break; + case 5: + x = -1; + y = 1; + break; + case 6: + x = -1; + y = 0; + break; + case 7: + x = -1; + y = -1; + break; + } + + x += px; + y += py; + + if (x < 0 || x >= AreaSize || y < 0 || y >= AreaSize) + continue; + + if (CalcMoves.CheckMovement(m, map, p3D, (Direction)i, out z)) + { + int idx = GetIndex(x + m_xOffset, y + m_yOffset, z); + + if (idx >= 0 && idx < NodeCount) + { + m_Nodes[idx].z = z; + vals[count++] = idx; + } + } + } + + return count; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Pathing/FastMovement.cs b/Scripts/Engines/Pathing/FastMovement.cs index f8d2ab176..ba079494d 100644 --- a/Scripts/Engines/Pathing/FastMovement.cs +++ b/Scripts/Engines/Pathing/FastMovement.cs @@ -1,724 +1,566 @@ #region References + using System; using System.Collections.Generic; using System.Linq; - using Server.Items; using Server.Mobiles; + #endregion namespace Server.Movement { - public class FastMovementImpl : IMovementImpl - { - public static bool Enabled = false; - - private const int PersonHeight = 16; - private const int StepHeight = 2; - - private const TileFlag ImpassableSurface = TileFlag.Impassable | TileFlag.Surface; - - private static IMovementImpl _Successor; - - public static void Initialize() - { - _Successor = Movement.Impl; - Movement.Impl = new FastMovementImpl(); - } - - private FastMovementImpl() - { } - - private static bool IsOk(StaticTile tile, int ourZ, int ourTop) - { - var itemData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - - return tile.Z + itemData.CalcHeight <= ourZ || ourTop <= tile.Z || (itemData.Flags & ImpassableSurface) == 0; - } - - private static bool IsOk(Item item, int ourZ, int ourTop, bool ignoreDoors, bool ignoreSpellFields) - { - var itemID = item.ItemID & TileData.MaxItemValue; - var itemData = TileData.ItemTable[itemID]; - - if ((itemData.Flags & ImpassableSurface) == 0) - { - return true; - } - - if (((itemData.Flags & TileFlag.Door) != 0 || itemID == 0x692 || itemID == 0x846 || itemID == 0x873 || - (itemID >= 0x6F5 && itemID <= 0x6F6)) && ignoreDoors) - { - return true; - } - - if ((itemID == 0x82 || itemID == 0x3946 || itemID == 0x3956) && ignoreSpellFields) - { - return true; - } - - return item.Z + itemData.CalcHeight <= ourZ || ourTop <= item.Z; - } - - private static bool IsOk( - bool ignoreDoors, - bool ignoreSpellFields, - int ourZ, - int ourTop, - IEnumerable tiles, - IEnumerable items) - { - return tiles.All(t => IsOk(t, ourZ, ourTop)) && items.All(i => IsOk(i, ourZ, ourTop, ignoreDoors, ignoreSpellFields)); - } - - private static bool Check( - Map map, - Mobile m, - List items, - int x, - int y, - int startTop, - int startZ, - bool canSwim, - bool cantWalk, - out int newZ) - { - newZ = 0; - - var tiles = map.Tiles.GetStaticTiles(x, y, true); - var landTile = map.Tiles.GetLandTile(x, y); - var landData = TileData.LandTable[landTile.ID & TileData.MaxLandValue]; - var landBlocks = (landData.Flags & TileFlag.Impassable) != 0; - var considerLand = !landTile.Ignored; - - if (landBlocks && canSwim && (landData.Flags & TileFlag.Wet) != 0) - { - //Impassable, Can Swim, and Is water. Don't block it. - landBlocks = false; - } - else if (cantWalk && (landData.Flags & TileFlag.Wet) == 0) - { - //Can't walk and it's not water - landBlocks = true; - } - - int landZ = 0, landCenter = 0, landTop = 0; - - map.GetAverageZ(x, y, ref landZ, ref landCenter, ref landTop); - - var moveIsOk = false; - - var stepTop = startTop + StepHeight; - var checkTop = startZ + PersonHeight; - - var ignoreDoors = MovementImpl.AlwaysIgnoreDoors || !m.Alive || m.IsDeadBondedPet || m.Body.IsGhost || - m.Body.BodyID == 987; - var ignoreSpellFields = m is PlayerMobile && map.MapID != 0; - - int itemZ, itemTop, ourZ, ourTop, testTop; - ItemData itemData; - TileFlag flags; - - #region Tiles - foreach (var tile in tiles) - { - itemData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - - #region SA - if (m.Flying && Insensitive.Equals(itemData.Name, "hover over")) - { - newZ = tile.Z; - return true; - } - - // Stygian Dragon - if (m.Body == 826 && map != null && map.MapID == 5) - { - if (x >= 307 && x <= 354 && y >= 126 && y <= 192) - { - if (tile.Z > newZ) - { - newZ = tile.Z; - } - - moveIsOk = true; - } - else if (x >= 42 && x <= 89) - { - if ((y >= 333 && y <= 399) || (y >= 531 && y <= 597) || (y >= 739 && y <= 805)) - { - if (tile.Z > newZ) - { - newZ = tile.Z; - } - - moveIsOk = true; - } - } - } - #endregion - - flags = itemData.Flags; - - if ((flags & ImpassableSurface) != TileFlag.Surface && (!canSwim || (flags & TileFlag.Wet) == 0)) - { - continue; - } - - if (cantWalk && (flags & TileFlag.Wet) == 0) - { - continue; - } - - itemZ = tile.Z; - itemTop = itemZ; - ourZ = itemZ + itemData.CalcHeight; - ourTop = ourZ + PersonHeight; - testTop = checkTop; - - if (moveIsOk) - { - var cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); - - if (cmp > 0 || (cmp == 0 && ourZ > newZ)) - { - continue; - } - } - - if (ourTop > testTop) - { - testTop = ourTop; - } - - if (!itemData.Bridge) - { - itemTop += itemData.Height; - } - - if (stepTop < itemTop) - { - continue; - } - - var landCheck = itemZ; - - if (itemData.Height >= StepHeight) - { - landCheck += StepHeight; - } - else - { - landCheck += itemData.Height; - } - - if (considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ) - { - continue; - } - - if (!IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) - { - continue; - } - - newZ = ourZ; - moveIsOk = true; - } - #endregion - - #region Items - foreach (var item in items) - { - itemData = item.ItemData; - flags = itemData.Flags; - - #region SA - if (m.Flying && Insensitive.Equals(itemData.Name, "hover over")) - { - newZ = item.Z; - return true; - } - #endregion - - if (item.Movable) - { - continue; - } - - if ((flags & ImpassableSurface) != TileFlag.Surface && (!m.CanSwim || (flags & TileFlag.Wet) == 0)) - { - continue; - } - - if (cantWalk && (flags & TileFlag.Wet) == 0) - { - continue; - } - - itemZ = item.Z; - itemTop = itemZ; - ourZ = itemZ + itemData.CalcHeight; - ourTop = ourZ + PersonHeight; - testTop = checkTop; - - if (moveIsOk) - { - var cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); - - if (cmp > 0 || (cmp == 0 && ourZ > newZ)) - { - continue; - } - } - - if (ourTop > testTop) - { - testTop = ourTop; - } - - if (!itemData.Bridge) - { - itemTop += itemData.Height; - } - - if (stepTop < itemTop) - { - continue; - } - - var landCheck = itemZ; - - if (itemData.Height >= StepHeight) - { - landCheck += StepHeight; - } - else - { - landCheck += itemData.Height; - } - - if (considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ) - { - continue; - } - - if (!IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) - { - continue; - } - - newZ = ourZ; - moveIsOk = true; - } - #endregion - - if (!considerLand || landBlocks || stepTop < landZ) - { - return moveIsOk; - } - - ourZ = landCenter; - ourTop = ourZ + PersonHeight; - testTop = checkTop; - - if (ourTop > testTop) - { - testTop = ourTop; - } - - var shouldCheck = true; - - if (moveIsOk) - { - var cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); - - if (cmp > 0 || (cmp == 0 && ourZ > newZ)) - { - shouldCheck = false; - } - } - - if (!shouldCheck || !IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) - { - return moveIsOk; - } - - newZ = ourZ; - moveIsOk = true; - - return moveIsOk; - } - - public bool CheckMovement(Mobile m, Map map, Point3D loc, Direction d, out int newZ) - { - if (!Enabled && _Successor != null) - { - return _Successor.CheckMovement(m, map, loc, d, out newZ); - } - - if (map == null || map == Map.Internal) - { - newZ = 0; - return false; - } - - var xStart = loc.X; - var yStart = loc.Y; - - int xForward = xStart, yForward = yStart; - int xRight = xStart, yRight = yStart; - int xLeft = xStart, yLeft = yStart; - - var checkDiagonals = ((int)d & 0x1) == 0x1; - - Offset(d, ref xForward, ref yForward); - Offset((Direction)(((int)d - 1) & 0x7), ref xLeft, ref yLeft); - Offset((Direction)(((int)d + 1) & 0x7), ref xRight, ref yRight); - - if (xForward < 0 || yForward < 0 || xForward >= map.Width || yForward >= map.Height) - { - newZ = 0; - return false; - } - - int startZ, startTop; - - IEnumerable itemsStart, itemsForward, itemsLeft, itemsRight; - - var ignoreMovableImpassables = MovementImpl.IgnoreMovableImpassables; - var reqFlags = ImpassableSurface; - - if (m.CanSwim) - { - reqFlags |= TileFlag.Wet; - } - - if (checkDiagonals) - { - var sStart = map.GetSector(xStart, yStart); - var sForward = map.GetSector(xForward, yForward); - var sLeft = map.GetSector(xLeft, yLeft); - var sRight = map.GetSector(xRight, yRight); - - itemsStart = sStart.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xStart, yStart)); - itemsForward = sForward.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xForward, yForward)); - itemsLeft = sLeft.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xLeft, yLeft)); - itemsRight = sRight.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xRight, yRight)); - } - else - { - var sStart = map.GetSector(xStart, yStart); - var sForward = map.GetSector(xForward, yForward); - - itemsStart = sStart.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xStart, yStart)); - itemsForward = sForward.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xForward, yForward)); - itemsLeft = Enumerable.Empty(); - itemsRight = Enumerable.Empty(); - } - - GetStartZ(m, map, loc, itemsStart, out startZ, out startTop); - - List list = null; - - MovementPool.AcquireMoveCache(ref list, itemsForward); - - var moveIsOk = Check(map, m, list, xForward, yForward, startTop, startZ, m.CanSwim, m.CantWalk, out newZ); - - if (moveIsOk && checkDiagonals) - { - int hold; - - if (m.Player && m.AccessLevel < AccessLevel.GameMaster) - { - MovementPool.AcquireMoveCache(ref list, itemsLeft); - - if (!Check(map, m, list, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) - { - moveIsOk = false; - } - else - { - MovementPool.AcquireMoveCache(ref list, itemsRight); - - if (!Check(map, m, list, xRight, yRight, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) - { - moveIsOk = false; - } - } - } - else - { - MovementPool.AcquireMoveCache(ref list, itemsLeft); - - if (!Check(map, m, list, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) - { - MovementPool.AcquireMoveCache(ref list, itemsRight); - - if (!Check(map, m, list, xRight, yRight, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) - { - moveIsOk = false; - } - } - } - } - - MovementPool.ClearMoveCache(ref list, true); - - if (!moveIsOk) - { - newZ = startZ; - } - - return moveIsOk; - } - - public bool CheckMovement(Mobile m, Direction d, out int newZ) - { - if (!Enabled && _Successor != null) - { - return _Successor.CheckMovement(m, d, out newZ); - } - - return CheckMovement(m, m.Map, m.Location, d, out newZ); - } - - private static bool Verify(Item item, int x, int y) - { - return item != null && item.AtWorldPoint(x, y); - } - - private static bool Verify(Item item, TileFlag reqFlags, bool ignoreMovableImpassables) - { - if (item == null) - { - return false; - } - - if (ignoreMovableImpassables && item.Movable && item.ItemData.Impassable) - { - return false; - } - - if ((item.ItemData.Flags & reqFlags) == 0) - { - return false; - } - - if (item is BaseMulti || item.ItemID > TileData.MaxItemValue) - { - return false; - } - - return true; - } - - private static bool Verify(Item item, TileFlag reqFlags, bool ignoreMovableImpassables, int x, int y) - { - return Verify(item, reqFlags, ignoreMovableImpassables) && Verify(item, x, y); - } - - private static void GetStartZ(Mobile m, Map map, Point3D loc, IEnumerable itemList, out int zLow, out int zTop) - { - int xCheck = loc.X, yCheck = loc.Y; - - var landTile = map.Tiles.GetLandTile(xCheck, yCheck); - var landData = TileData.LandTable[landTile.ID & TileData.MaxLandValue]; - var landBlocks = (landData.Flags & TileFlag.Impassable) != 0; - - if (landBlocks && m.CanSwim && (landData.Flags & TileFlag.Wet) != 0) - { - landBlocks = false; - } - else if (m.CantWalk && (landData.Flags & TileFlag.Wet) == 0) - { - landBlocks = true; - } - - int landZ = 0, landCenter = 0, landTop = 0; - - map.GetAverageZ(xCheck, yCheck, ref landZ, ref landCenter, ref landTop); - - var considerLand = !landTile.Ignored; - - var zCenter = zLow = zTop = 0; - var isSet = false; - - if (considerLand && !landBlocks && loc.Z >= landCenter) - { - zLow = landZ; - zCenter = landCenter; - zTop = landTop; - isSet = true; - } - - var staticTiles = map.Tiles.GetStaticTiles(xCheck, yCheck, true); - - foreach (var tile in staticTiles) - { - var tileData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - var calcTop = (tile.Z + tileData.CalcHeight); - - if (isSet && calcTop < zCenter) - { - continue; - } - - if ((tileData.Flags & TileFlag.Surface) == 0 && (!m.CanSwim || (tileData.Flags & TileFlag.Wet) == 0)) - { - continue; - } - - if (loc.Z < calcTop) - { - continue; - } - - if (m.CantWalk && (tileData.Flags & TileFlag.Wet) == 0) - { - continue; - } - - zLow = tile.Z; - zCenter = calcTop; - - var top = tile.Z + tileData.Height; - - if (!isSet || top > zTop) - { - zTop = top; - } - - isSet = true; - } - - ItemData itemData; - - foreach (var item in itemList) - { - itemData = item.ItemData; - - var calcTop = item.Z + itemData.CalcHeight; - - if (isSet && calcTop < zCenter) - { - continue; - } - - if ((itemData.Flags & TileFlag.Surface) == 0 && (!m.CanSwim || (itemData.Flags & TileFlag.Wet) == 0)) - { - continue; - } - - if (loc.Z < calcTop) - { - continue; - } - - if (m.CantWalk && (itemData.Flags & TileFlag.Wet) == 0) - { - continue; - } - - zLow = item.Z; - zCenter = calcTop; - - var top = item.Z + itemData.Height; - - if (!isSet || top > zTop) - { - zTop = top; - } - - isSet = true; - } - - if (!isSet) - { - zLow = zTop = loc.Z; - } - else if (loc.Z > zTop) - { - zTop = loc.Z; - } - } - - public void Offset(Direction d, ref int x, ref int y) - { - switch (d & Direction.Mask) - { - case Direction.North: - --y; - break; - case Direction.South: - ++y; - break; - case Direction.West: - --x; - break; - case Direction.East: - ++x; - break; - case Direction.Right: - ++x; - --y; - break; - case Direction.Left: - --x; - ++y; - break; - case Direction.Down: - ++x; - ++y; - break; - case Direction.Up: - --x; - --y; - break; - } - } - - private static class MovementPool - { - private static readonly object _MovePoolLock = new object(); - private static readonly Queue> _MoveCachePool = new Queue>(0x400); - - public static void AcquireMoveCache(ref List cache, IEnumerable items) - { - if (cache == null) - { - lock (_MovePoolLock) - { - cache = _MoveCachePool.Count > 0 ? _MoveCachePool.Dequeue() : new List(0x10); - } - } - else - { - cache.Clear(); - } - - cache.AddRange(items); - } - - public static void ClearMoveCache(ref List cache, bool free) - { - cache?.Clear(); - - if (!free) - { - return; - } - - lock (_MovePoolLock) - { - if (_MoveCachePool.Count < 0x400) - { - _MoveCachePool.Enqueue(cache); - } - } - - cache = null; - } - } - } + public class FastMovementImpl : IMovementImpl + { + private const int PersonHeight = 16; + private const int StepHeight = 2; + + private const TileFlag ImpassableSurface = TileFlag.Impassable | TileFlag.Surface; + public static bool Enabled = false; + + private static IMovementImpl _Successor; + + private FastMovementImpl() + { + } + + public bool CheckMovement(Mobile m, Map map, Point3D loc, Direction d, out int newZ) + { + if (!Enabled && _Successor != null) return _Successor.CheckMovement(m, map, loc, d, out newZ); + + if (map == null || map == Map.Internal) + { + newZ = 0; + return false; + } + + int xStart = loc.X; + int yStart = loc.Y; + + int xForward = xStart, yForward = yStart; + int xRight = xStart, yRight = yStart; + int xLeft = xStart, yLeft = yStart; + + bool checkDiagonals = ((int)d & 0x1) == 0x1; + + Offset(d, ref xForward, ref yForward); + Offset((Direction)(((int)d - 1) & 0x7), ref xLeft, ref yLeft); + Offset((Direction)(((int)d + 1) & 0x7), ref xRight, ref yRight); + + if (xForward < 0 || yForward < 0 || xForward >= map.Width || yForward >= map.Height) + { + newZ = 0; + return false; + } + + int startZ, startTop; + + IEnumerable itemsStart, itemsForward, itemsLeft, itemsRight; + + bool ignoreMovableImpassables = MovementImpl.IgnoreMovableImpassables; + TileFlag reqFlags = ImpassableSurface; + + if (m.CanSwim) reqFlags |= TileFlag.Wet; + + if (checkDiagonals) + { + Sector sStart = map.GetSector(xStart, yStart); + Sector sForward = map.GetSector(xForward, yForward); + Sector sLeft = map.GetSector(xLeft, yLeft); + Sector sRight = map.GetSector(xRight, yRight); + + itemsStart = sStart.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xStart, yStart)); + itemsForward = sForward.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xForward, yForward)); + itemsLeft = sLeft.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xLeft, yLeft)); + itemsRight = sRight.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xRight, yRight)); + } + else + { + Sector sStart = map.GetSector(xStart, yStart); + Sector sForward = map.GetSector(xForward, yForward); + + itemsStart = sStart.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xStart, yStart)); + itemsForward = sForward.Items.Where(i => Verify(i, reqFlags, ignoreMovableImpassables, xForward, yForward)); + itemsLeft = Enumerable.Empty(); + itemsRight = Enumerable.Empty(); + } + + GetStartZ(m, map, loc, itemsStart, out startZ, out startTop); + + List list = null; + + MovementPool.AcquireMoveCache(ref list, itemsForward); + + bool moveIsOk = Check(map, m, list, xForward, yForward, startTop, startZ, m.CanSwim, m.CantWalk, out newZ); + + if (moveIsOk && checkDiagonals) + { + int hold; + + if (m.Player && m.AccessLevel < AccessLevel.GameMaster) + { + MovementPool.AcquireMoveCache(ref list, itemsLeft); + + if (!Check(map, m, list, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) + { + moveIsOk = false; + } + else + { + MovementPool.AcquireMoveCache(ref list, itemsRight); + + if (!Check(map, m, list, xRight, yRight, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) + moveIsOk = false; + } + } + else + { + MovementPool.AcquireMoveCache(ref list, itemsLeft); + + if (!Check(map, m, list, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) + { + MovementPool.AcquireMoveCache(ref list, itemsRight); + + if (!Check(map, m, list, xRight, yRight, startTop, startZ, m.CanSwim, m.CantWalk, out hold)) + moveIsOk = false; + } + } + } + + MovementPool.ClearMoveCache(ref list, true); + + if (!moveIsOk) newZ = startZ; + + return moveIsOk; + } + + public bool CheckMovement(Mobile m, Direction d, out int newZ) + { + if (!Enabled && _Successor != null) return _Successor.CheckMovement(m, d, out newZ); + + return CheckMovement(m, m.Map, m.Location, d, out newZ); + } + + public static void Initialize() + { + _Successor = Movement.Impl; + Movement.Impl = new FastMovementImpl(); + } + + private static bool IsOk(StaticTile tile, int ourZ, int ourTop) + { + ItemData itemData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + + return tile.Z + itemData.CalcHeight <= ourZ || ourTop <= tile.Z || (itemData.Flags & ImpassableSurface) == 0; + } + + private static bool IsOk(Item item, int ourZ, int ourTop, bool ignoreDoors, bool ignoreSpellFields) + { + int itemID = item.ItemID & TileData.MaxItemValue; + ItemData itemData = TileData.ItemTable[itemID]; + + if ((itemData.Flags & ImpassableSurface) == 0) return true; + + if (((itemData.Flags & TileFlag.Door) != 0 || itemID == 0x692 || itemID == 0x846 || itemID == 0x873 || + itemID >= 0x6F5 && itemID <= 0x6F6) && ignoreDoors) + return true; + + if ((itemID == 0x82 || itemID == 0x3946 || itemID == 0x3956) && ignoreSpellFields) return true; + + return item.Z + itemData.CalcHeight <= ourZ || ourTop <= item.Z; + } + + private static bool IsOk( + bool ignoreDoors, + bool ignoreSpellFields, + int ourZ, + int ourTop, + IEnumerable tiles, + IEnumerable items) + { + return tiles.All(t => IsOk(t, ourZ, ourTop)) && + items.All(i => IsOk(i, ourZ, ourTop, ignoreDoors, ignoreSpellFields)); + } + + private static bool Check( + Map map, + Mobile m, + List items, + int x, + int y, + int startTop, + int startZ, + bool canSwim, + bool cantWalk, + out int newZ) + { + newZ = 0; + + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y, true); + LandTile landTile = map.Tiles.GetLandTile(x, y); + LandData landData = TileData.LandTable[landTile.ID & TileData.MaxLandValue]; + bool landBlocks = (landData.Flags & TileFlag.Impassable) != 0; + bool considerLand = !landTile.Ignored; + + if (landBlocks && canSwim && (landData.Flags & TileFlag.Wet) != 0) + landBlocks = false; + else if (cantWalk && (landData.Flags & TileFlag.Wet) == 0) landBlocks = true; + + int landZ = 0, landCenter = 0, landTop = 0; + + map.GetAverageZ(x, y, ref landZ, ref landCenter, ref landTop); + + bool moveIsOk = false; + + int stepTop = startTop + StepHeight; + int checkTop = startZ + PersonHeight; + + bool ignoreDoors = MovementImpl.AlwaysIgnoreDoors || !m.Alive || m.IsDeadBondedPet || m.Body.IsGhost || + m.Body.BodyID == 987; + bool ignoreSpellFields = m is PlayerMobile && map.MapID != 0; + + int itemZ, itemTop, ourZ, ourTop, testTop; + ItemData itemData; + TileFlag flags; + + #region Tiles + + foreach (StaticTile tile in tiles) + { + itemData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + + #region SA + + if (m.Flying && Insensitive.Equals(itemData.Name, "hover over")) + { + newZ = tile.Z; + return true; + } + + // Stygian Dragon + if (m.Body == 826 && map != null && map.MapID == 5) + { + if (x >= 307 && x <= 354 && y >= 126 && y <= 192) + { + if (tile.Z > newZ) newZ = tile.Z; + + moveIsOk = true; + } + else if (x >= 42 && x <= 89) + { + if (y >= 333 && y <= 399 || y >= 531 && y <= 597 || y >= 739 && y <= 805) + { + if (tile.Z > newZ) newZ = tile.Z; + + moveIsOk = true; + } + } + } + + #endregion + + flags = itemData.Flags; + + if ((flags & ImpassableSurface) != TileFlag.Surface && (!canSwim || (flags & TileFlag.Wet) == 0)) continue; + + if (cantWalk && (flags & TileFlag.Wet) == 0) continue; + + itemZ = tile.Z; + itemTop = itemZ; + ourZ = itemZ + itemData.CalcHeight; + ourTop = ourZ + PersonHeight; + testTop = checkTop; + + if (moveIsOk) + { + int cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); + + if (cmp > 0 || cmp == 0 && ourZ > newZ) continue; + } + + if (ourTop > testTop) testTop = ourTop; + + if (!itemData.Bridge) itemTop += itemData.Height; + + if (stepTop < itemTop) continue; + + int landCheck = itemZ; + + if (itemData.Height >= StepHeight) + landCheck += StepHeight; + else + landCheck += itemData.Height; + + if (considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ) continue; + + if (!IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) continue; + + newZ = ourZ; + moveIsOk = true; + } + + #endregion + + #region Items + + foreach (Item item in items) + { + itemData = item.ItemData; + flags = itemData.Flags; + + #region SA + + if (m.Flying && Insensitive.Equals(itemData.Name, "hover over")) + { + newZ = item.Z; + return true; + } + + #endregion + + if (item.Movable) continue; + + if ((flags & ImpassableSurface) != TileFlag.Surface && (!m.CanSwim || (flags & TileFlag.Wet) == 0)) continue; + + if (cantWalk && (flags & TileFlag.Wet) == 0) continue; + + itemZ = item.Z; + itemTop = itemZ; + ourZ = itemZ + itemData.CalcHeight; + ourTop = ourZ + PersonHeight; + testTop = checkTop; + + if (moveIsOk) + { + int cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); + + if (cmp > 0 || cmp == 0 && ourZ > newZ) continue; + } + + if (ourTop > testTop) testTop = ourTop; + + if (!itemData.Bridge) itemTop += itemData.Height; + + if (stepTop < itemTop) continue; + + int landCheck = itemZ; + + if (itemData.Height >= StepHeight) + landCheck += StepHeight; + else + landCheck += itemData.Height; + + if (considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ) continue; + + if (!IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) continue; + + newZ = ourZ; + moveIsOk = true; + } + + #endregion + + if (!considerLand || landBlocks || stepTop < landZ) return moveIsOk; + + ourZ = landCenter; + ourTop = ourZ + PersonHeight; + testTop = checkTop; + + if (ourTop > testTop) testTop = ourTop; + + bool shouldCheck = true; + + if (moveIsOk) + { + int cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); + + if (cmp > 0 || cmp == 0 && ourZ > newZ) shouldCheck = false; + } + + if (!shouldCheck || !IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) return moveIsOk; + + newZ = ourZ; + moveIsOk = true; + + return moveIsOk; + } + + private static bool Verify(Item item, int x, int y) + { + return item != null && item.AtWorldPoint(x, y); + } + + private static bool Verify(Item item, TileFlag reqFlags, bool ignoreMovableImpassables) + { + if (item == null) return false; + + if (ignoreMovableImpassables && item.Movable && item.ItemData.Impassable) return false; + + if ((item.ItemData.Flags & reqFlags) == 0) return false; + + if (item is BaseMulti || item.ItemID > TileData.MaxItemValue) return false; + + return true; + } + + private static bool Verify(Item item, TileFlag reqFlags, bool ignoreMovableImpassables, int x, int y) + { + return Verify(item, reqFlags, ignoreMovableImpassables) && Verify(item, x, y); + } + + private static void GetStartZ(Mobile m, Map map, Point3D loc, IEnumerable itemList, out int zLow, out int zTop) + { + int xCheck = loc.X, yCheck = loc.Y; + + LandTile landTile = map.Tiles.GetLandTile(xCheck, yCheck); + LandData landData = TileData.LandTable[landTile.ID & TileData.MaxLandValue]; + bool landBlocks = (landData.Flags & TileFlag.Impassable) != 0; + + if (landBlocks && m.CanSwim && (landData.Flags & TileFlag.Wet) != 0) + landBlocks = false; + else if (m.CantWalk && (landData.Flags & TileFlag.Wet) == 0) landBlocks = true; + + int landZ = 0, landCenter = 0, landTop = 0; + + map.GetAverageZ(xCheck, yCheck, ref landZ, ref landCenter, ref landTop); + + bool considerLand = !landTile.Ignored; + + int zCenter = zLow = zTop = 0; + bool isSet = false; + + if (considerLand && !landBlocks && loc.Z >= landCenter) + { + zLow = landZ; + zCenter = landCenter; + zTop = landTop; + isSet = true; + } + + StaticTile[] staticTiles = map.Tiles.GetStaticTiles(xCheck, yCheck, true); + + foreach (StaticTile tile in staticTiles) + { + ItemData tileData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + int calcTop = tile.Z + tileData.CalcHeight; + + if (isSet && calcTop < zCenter) continue; + + if ((tileData.Flags & TileFlag.Surface) == 0 && + (!m.CanSwim || (tileData.Flags & TileFlag.Wet) == 0)) continue; + + if (loc.Z < calcTop) continue; + + if (m.CantWalk && (tileData.Flags & TileFlag.Wet) == 0) continue; + + zLow = tile.Z; + zCenter = calcTop; + + int top = tile.Z + tileData.Height; + + if (!isSet || top > zTop) zTop = top; + + isSet = true; + } + + ItemData itemData; + + foreach (Item item in itemList) + { + itemData = item.ItemData; + + int calcTop = item.Z + itemData.CalcHeight; + + if (isSet && calcTop < zCenter) continue; + + if ((itemData.Flags & TileFlag.Surface) == 0 && + (!m.CanSwim || (itemData.Flags & TileFlag.Wet) == 0)) continue; + + if (loc.Z < calcTop) continue; + + if (m.CantWalk && (itemData.Flags & TileFlag.Wet) == 0) continue; + + zLow = item.Z; + zCenter = calcTop; + + int top = item.Z + itemData.Height; + + if (!isSet || top > zTop) zTop = top; + + isSet = true; + } + + if (!isSet) + zLow = zTop = loc.Z; + else if (loc.Z > zTop) zTop = loc.Z; + } + + public void Offset(Direction d, ref int x, ref int y) + { + switch (d & Direction.Mask) + { + case Direction.North: + --y; + break; + case Direction.South: + ++y; + break; + case Direction.West: + --x; + break; + case Direction.East: + ++x; + break; + case Direction.Right: + ++x; + --y; + break; + case Direction.Left: + --x; + ++y; + break; + case Direction.Down: + ++x; + ++y; + break; + case Direction.Up: + --x; + --y; + break; + } + } + + private static class MovementPool + { + private static readonly object _MovePoolLock = new object(); + private static readonly Queue> _MoveCachePool = new Queue>(0x400); + + public static void AcquireMoveCache(ref List cache, IEnumerable items) + { + if (cache == null) + lock (_MovePoolLock) + { + cache = _MoveCachePool.Count > 0 ? _MoveCachePool.Dequeue() : new List(0x10); + } + else + cache.Clear(); + + cache.AddRange(items); + } + + public static void ClearMoveCache(ref List cache, bool free) + { + cache?.Clear(); + + if (!free) return; + + lock (_MovePoolLock) + { + if (_MoveCachePool.Count < 0x400) _MoveCachePool.Enqueue(cache); + } + + cache = null; + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Pathing/MoveResult.cs b/Scripts/Engines/Pathing/MoveResult.cs index 12431a8de..954c1825d 100644 --- a/Scripts/Engines/Pathing/MoveResult.cs +++ b/Scripts/Engines/Pathing/MoveResult.cs @@ -1,12 +1,12 @@ namespace Server { - public delegate MoveResult MoveMethod( Direction d ); + public delegate MoveResult MoveMethod(Direction d); - public enum MoveResult - { - BadState, - Blocked, - Success, - SuccessAutoTurn - } + public enum MoveResult + { + BadState, + Blocked, + Success, + SuccessAutoTurn + } } \ No newline at end of file diff --git a/Scripts/Engines/Pathing/Movement.cs b/Scripts/Engines/Pathing/Movement.cs index 98353d373..c37103d40 100644 --- a/Scripts/Engines/Pathing/Movement.cs +++ b/Scripts/Engines/Pathing/Movement.cs @@ -5,584 +5,628 @@ using Server.Mobiles; namespace Server.Movement { - public class MovementImpl : IMovementImpl - { - private const int PersonHeight = 16; - private const int StepHeight = 2; + public class MovementImpl : IMovementImpl + { + private const int PersonHeight = 16; + private const int StepHeight = 2; - private const TileFlag ImpassableSurface = TileFlag.Impassable | TileFlag.Surface; + private const TileFlag ImpassableSurface = TileFlag.Impassable | TileFlag.Surface; - public static bool AlwaysIgnoreDoors { get; set; } + private List[] m_MobPools = new List[3] + { + new List(), new List(), + new List() + }; - public static bool IgnoreMovableImpassables { get; set; } + private List[] m_Pools = new List[4] + { + new List(), new List(), + new List(), new List() + }; - public static bool IgnoreSpellFields { get; set; } + private List m_Sectors = new List(); - public static Point3D Goal { get; set; } + private MovementImpl() + { + } - public static void Configure() - { - Movement.Impl = new MovementImpl(); - } + public static bool AlwaysIgnoreDoors{ get; set; } - private MovementImpl() - { - } + public static bool IgnoreMovableImpassables{ get; set; } - private bool IsOk( bool ignoreDoors, bool ignoreSpellFields, int ourZ, int ourTop, StaticTile[] tiles, List items ) - { - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile check = tiles[i]; - ItemData itemData = TileData.ItemTable[check.ID & TileData.MaxItemValue]; + public static bool IgnoreSpellFields{ get; set; } - if ( (itemData.Flags & ImpassableSurface) != 0 ) // Impassable || Surface - { - int checkZ = check.Z; - int checkTop = checkZ + itemData.CalcHeight; + public static Point3D Goal{ get; set; } - if ( checkTop > ourZ && ourTop > checkZ ) - return false; - } - } + public bool CheckMovement(Mobile m, Map map, Point3D loc, Direction d, out int newZ) + { + if (map == null || map == Map.Internal) + { + newZ = 0; + return false; + } + + int xStart = loc.X; + int yStart = loc.Y; + int xForward = xStart, yForward = yStart; + int xRight = xStart, yRight = yStart; + int xLeft = xStart, yLeft = yStart; + + bool checkDiagonals = ((int)d & 0x1) == 0x1; + + Offset(d, ref xForward, ref yForward); + Offset((Direction)(((int)d - 1) & 0x7), ref xLeft, ref yLeft); + Offset((Direction)(((int)d + 1) & 0x7), ref xRight, ref yRight); + + if (xForward < 0 || yForward < 0 || xForward >= map.Width || yForward >= map.Height) + { + newZ = 0; + return false; + } + + int startZ, startTop; + + List itemsStart = m_Pools[0]; + List itemsForward = m_Pools[1]; + List itemsLeft = m_Pools[2]; + List itemsRight = m_Pools[3]; + + bool ignoreMovableImpassables = IgnoreMovableImpassables; + TileFlag reqFlags = ImpassableSurface; + + if (m.CanSwim) + reqFlags |= TileFlag.Wet; + + List mobsForward = m_MobPools[0]; + List mobsLeft = m_MobPools[1]; + List mobsRight = m_MobPools[2]; + + bool checkMobs = m is BaseCreature creature && !creature.Controlled && + (xForward != Goal.X || yForward != Goal.Y); + + if (checkDiagonals) + { + Sector sectorStart = map.GetSector(xStart, yStart); + Sector sectorForward = map.GetSector(xForward, yForward); + Sector sectorLeft = map.GetSector(xLeft, yLeft); + Sector sectorRight = map.GetSector(xRight, yRight); + + List sectors = m_Sectors; + + sectors.Add(sectorStart); + + if (!sectors.Contains(sectorForward)) + sectors.Add(sectorForward); + + if (!sectors.Contains(sectorLeft)) + sectors.Add(sectorLeft); + + if (!sectors.Contains(sectorRight)) + sectors.Add(sectorRight); + + for (int i = 0; i < sectors.Count; ++i) + { + Sector sector = sectors[i]; + + for (int j = 0; j < sector.Items.Count; ++j) + { + Item item = sector.Items[j]; + + if (ignoreMovableImpassables && item.Movable && (item.ItemData.Flags & ImpassableSurface) != 0) + continue; + + if ((item.ItemData.Flags & reqFlags) == 0) + continue; + + if (sector == sectorStart && item.AtWorldPoint(xStart, yStart) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsStart.Add(item); + else if (sector == sectorForward && item.AtWorldPoint(xForward, yForward) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsForward.Add(item); + else if (sector == sectorLeft && item.AtWorldPoint(xLeft, yLeft) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsLeft.Add(item); + else if (sector == sectorRight && item.AtWorldPoint(xRight, yRight) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsRight.Add(item); + } + + if (checkMobs) + for (int j = 0; j < sector.Mobiles.Count; ++j) + { + Mobile mob = sector.Mobiles[j]; + + if (sector == sectorForward && mob.X == xForward && mob.Y == yForward) + mobsForward.Add(mob); + else if (sector == sectorLeft && mob.X == xLeft && mob.Y == yLeft) + mobsLeft.Add(mob); + else if (sector == sectorRight && mob.X == xRight && mob.Y == yRight) + mobsRight.Add(mob); + } + } + + if (m_Sectors.Count > 0) + m_Sectors.Clear(); + } + else + { + Sector sectorStart = map.GetSector(xStart, yStart); + Sector sectorForward = map.GetSector(xForward, yForward); + + if (sectorStart == sectorForward) + { + for (int i = 0; i < sectorStart.Items.Count; ++i) + { + Item item = sectorStart.Items[i]; + + if (ignoreMovableImpassables && item.Movable && (item.ItemData.Flags & ImpassableSurface) != 0) + continue; + + if ((item.ItemData.Flags & reqFlags) == 0) + continue; + + if (item.AtWorldPoint(xStart, yStart) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsStart.Add(item); + else if (item.AtWorldPoint(xForward, yForward) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsForward.Add(item); + } + } + else + { + for (int i = 0; i < sectorForward.Items.Count; ++i) + { + Item item = sectorForward.Items[i]; + + if (ignoreMovableImpassables && item.Movable && (item.ItemData.Flags & ImpassableSurface) != 0) + continue; + + if ((item.ItemData.Flags & reqFlags) == 0) + continue; + + if (item.AtWorldPoint(xForward, yForward) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsForward.Add(item); + } + + for (int i = 0; i < sectorStart.Items.Count; ++i) + { + Item item = sectorStart.Items[i]; + + if (ignoreMovableImpassables && item.Movable && (item.ItemData.Flags & ImpassableSurface) != 0) + continue; + + if ((item.ItemData.Flags & reqFlags) == 0) + continue; + + if (item.AtWorldPoint(xStart, yStart) && !(item is BaseMulti) && + item.ItemID <= TileData.MaxItemValue) + itemsStart.Add(item); + } + } + + if (checkMobs) + for (int i = 0; i < sectorForward.Mobiles.Count; ++i) + { + Mobile mob = sectorForward.Mobiles[i]; + + if (mob.X == xForward && mob.Y == yForward) + mobsForward.Add(mob); + } + } + + GetStartZ(m, map, loc, itemsStart, out startZ, out startTop); + + bool moveIsOk = Check(map, m, itemsForward, mobsForward, xForward, yForward, startTop, startZ, m.CanSwim, + m.CantWalk, out newZ); + + if (moveIsOk && checkDiagonals) + { + int hold; + + if (m.Player && m.AccessLevel < AccessLevel.GameMaster) + { + if (!Check(map, m, itemsLeft, mobsLeft, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, + out hold) || !Check(map, m, itemsRight, mobsRight, xRight, yRight, startTop, startZ, m.CanSwim, + m.CantWalk, out hold)) + moveIsOk = false; + } + else + { + if (!Check(map, m, itemsLeft, mobsLeft, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, + out hold) && !Check(map, m, itemsRight, mobsRight, xRight, yRight, startTop, startZ, m.CanSwim, + m.CantWalk, out hold)) + moveIsOk = false; + } + } + + for (int i = 0; i < (checkDiagonals ? 4 : 2); ++i) + if (m_Pools[i].Count != 0) + m_Pools[i].Clear(); + + for (int i = 0; i < (checkDiagonals ? 3 : 1); ++i) + if (m_MobPools[i].Count != 0) + m_MobPools[i].Clear(); + + if (!moveIsOk) + newZ = startZ; + + return moveIsOk; + } + + public bool CheckMovement(Mobile m, Direction d, out int newZ) + { + return CheckMovement(m, m.Map, m.Location, d, out newZ); + } + + public static void Configure() + { + Movement.Impl = new MovementImpl(); + } + + private bool IsOk(bool ignoreDoors, bool ignoreSpellFields, int ourZ, int ourTop, StaticTile[] tiles, + List items) + { + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile check = tiles[i]; + ItemData itemData = TileData.ItemTable[check.ID & TileData.MaxItemValue]; + + if ((itemData.Flags & ImpassableSurface) != 0) // Impassable || Surface + { + int checkZ = check.Z; + int checkTop = checkZ + itemData.CalcHeight; + + if (checkTop > ourZ && ourTop > checkZ) + return false; + } + } + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + int itemID = item.ItemID & TileData.MaxItemValue; + ItemData itemData = TileData.ItemTable[itemID]; + TileFlag flags = itemData.Flags; + + if ((flags & ImpassableSurface) != 0) // Impassable || Surface + { + if (ignoreDoors && ((flags & TileFlag.Door) != 0 || itemID == 0x692 || itemID == 0x846 || + itemID == 0x873 || itemID >= 0x6F5 && itemID <= 0x6F6)) + continue; + + if (ignoreSpellFields && (itemID == 0x82 || itemID == 0x3946 || itemID == 0x3956)) + continue; + + int checkZ = item.Z; + int checkTop = checkZ + itemData.CalcHeight; + + if (checkTop > ourZ && ourTop > checkZ) + return false; + } + } + + return true; + } + + private bool Check(Map map, Mobile m, List items, List mobiles, int x, int y, int startTop, int startZ, + bool canSwim, bool cantWalk, out int newZ) + { + newZ = 0; + + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y, true); + LandTile landTile = map.Tiles.GetLandTile(x, y); + + bool landBlocks = (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) != 0; + bool considerLand = !landTile.Ignored; + + if (landBlocks && canSwim && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) != 0 + ) //Impassable, Can Swim, and Is water. Don't block it. + landBlocks = false; + else if (cantWalk && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) == 0 + ) //Can't walk and it's not water + landBlocks = true; + + int landZ = 0, landCenter = 0, landTop = 0; + + map.GetAverageZ(x, y, ref landZ, ref landCenter, ref landTop); + + bool moveIsOk = false; + + int stepTop = startTop + StepHeight; + int checkTop = startZ + PersonHeight; + + bool ignoreDoors = AlwaysIgnoreDoors || !m.Alive || m.Body.BodyID == 0x3DB || m.IsDeadBondedPet; + bool ignoreSpellFields = m is PlayerMobile && map != Map.Felucca; + + #region Tiles + + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; + ItemData itemData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + TileFlag flags = itemData.Flags; + + if ((flags & ImpassableSurface) == TileFlag.Surface || canSwim && (flags & TileFlag.Wet) != 0 + ) // Surface && !Impassable + { + if (cantWalk && (flags & TileFlag.Wet) == 0) + continue; + + int itemZ = tile.Z; + int itemTop = itemZ; + int ourZ = itemZ + itemData.CalcHeight; + int ourTop = ourZ + PersonHeight; + int testTop = checkTop; + + if (moveIsOk) + { + int cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); + + if (cmp > 0 || cmp == 0 && ourZ > newZ) + continue; + } + + if (ourZ + PersonHeight > testTop) + testTop = ourZ + PersonHeight; + + if (!itemData.Bridge) + itemTop += itemData.Height; + + if (stepTop >= itemTop) + { + int landCheck = itemZ; + + if (itemData.Height >= StepHeight) + landCheck += StepHeight; + else + landCheck += itemData.Height; + + if (considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ) + continue; + + if (IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) + { + newZ = ourZ; + moveIsOk = true; + } + } + } + } - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - int itemID = item.ItemID & TileData.MaxItemValue; - ItemData itemData = TileData.ItemTable[itemID]; - TileFlag flags = itemData.Flags; + #endregion - if ( (flags & ImpassableSurface) != 0 ) // Impassable || Surface - { - if ( ignoreDoors && ((flags & TileFlag.Door) != 0 || itemID == 0x692 || itemID == 0x846 || itemID == 0x873 || (itemID >= 0x6F5 && itemID <= 0x6F6)) ) - continue; + #region Items - if ( ignoreSpellFields && ( itemID == 0x82 || itemID == 0x3946 || itemID == 0x3956 ) ) - continue; + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + ItemData itemData = item.ItemData; + TileFlag flags = itemData.Flags; + + if (!item.Movable && ((flags & ImpassableSurface) == TileFlag.Surface || + m.CanSwim && (flags & TileFlag.Wet) != 0)) // Surface && !Impassable && !Movable + { + if (cantWalk && (flags & TileFlag.Wet) == 0) + continue; + + int itemZ = item.Z; + int itemTop = itemZ; + int ourZ = itemZ + itemData.CalcHeight; + int ourTop = ourZ + PersonHeight; + int testTop = checkTop; + + if (moveIsOk) + { + int cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); - int checkZ = item.Z; - int checkTop = checkZ + itemData.CalcHeight; + if (cmp > 0 || cmp == 0 && ourZ > newZ) + continue; + } - if ( checkTop > ourZ && ourTop > checkZ ) - return false; - } - } - - return true; - } - - private List[] m_Pools = new List[4] - { - new List(), new List(), - new List(), new List(), - }; - - private List[] m_MobPools = new List[3] - { - new List(), new List(), - new List(), - }; - - private List m_Sectors = new List(); - - private bool Check( Map map, Mobile m, List items, List mobiles, int x, int y, int startTop, int startZ, bool canSwim, bool cantWalk, out int newZ ) - { - newZ = 0; - - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y, true ); - LandTile landTile = map.Tiles.GetLandTile( x, y ); - - bool landBlocks = (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) != 0; - bool considerLand = !landTile.Ignored; - - if ( landBlocks && canSwim && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) != 0 ) //Impassable, Can Swim, and Is water. Don't block it. - landBlocks = false; - else if ( cantWalk && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) == 0 ) //Can't walk and it's not water - landBlocks = true; - - int landZ = 0, landCenter = 0, landTop = 0; - - map.GetAverageZ( x, y, ref landZ, ref landCenter, ref landTop ); - - bool moveIsOk = false; - - int stepTop = startTop + StepHeight; - int checkTop = startZ + PersonHeight; - - bool ignoreDoors = ( AlwaysIgnoreDoors || !m.Alive || m.Body.BodyID == 0x3DB || m.IsDeadBondedPet ); - bool ignoreSpellFields = m is PlayerMobile && map != Map.Felucca; - - #region Tiles - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - ItemData itemData = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - TileFlag flags = itemData.Flags; - - if ( (flags & ImpassableSurface) == TileFlag.Surface || (canSwim && (flags & TileFlag.Wet) != 0) ) // Surface && !Impassable - { - if ( cantWalk && (flags & TileFlag.Wet) == 0 ) - continue; - - int itemZ = tile.Z; - int itemTop = itemZ; - int ourZ = itemZ + itemData.CalcHeight; - int ourTop = ourZ + PersonHeight; - int testTop = checkTop; - - if ( moveIsOk ) - { - int cmp = Math.Abs( ourZ - m.Z ) - Math.Abs( newZ - m.Z ); - - if ( cmp > 0 || (cmp == 0 && ourZ > newZ) ) - continue; - } - - if ( ourZ + PersonHeight > testTop ) - testTop = ourZ + PersonHeight; - - if ( !itemData.Bridge ) - itemTop += itemData.Height; - - if ( stepTop >= itemTop ) - { - int landCheck = itemZ; - - if ( itemData.Height >= StepHeight ) - landCheck += StepHeight; - else - landCheck += itemData.Height; - - if ( considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ ) - continue; - - if ( IsOk( ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items ) ) - { - newZ = ourZ; - moveIsOk = true; - } - } - } - } - #endregion - - #region Items - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - ItemData itemData = item.ItemData; - TileFlag flags = itemData.Flags; - - if ( !item.Movable && ((flags & ImpassableSurface) == TileFlag.Surface || (m.CanSwim && (flags & TileFlag.Wet) != 0)) ) // Surface && !Impassable && !Movable - { - if ( cantWalk && (flags & TileFlag.Wet) == 0 ) - continue; - - int itemZ = item.Z; - int itemTop = itemZ; - int ourZ = itemZ + itemData.CalcHeight; - int ourTop = ourZ + PersonHeight; - int testTop = checkTop; - - if ( moveIsOk ) - { - int cmp = Math.Abs( ourZ - m.Z ) - Math.Abs( newZ - m.Z ); - - if ( cmp > 0 || (cmp == 0 && ourZ > newZ) ) - continue; - } - - if ( ourZ + PersonHeight > testTop ) - testTop = ourZ + PersonHeight; - - if ( !itemData.Bridge ) - itemTop += itemData.Height; - - if ( stepTop >= itemTop ) - { - int landCheck = itemZ; - - if ( itemData.Height >= StepHeight ) - landCheck += StepHeight; - else - landCheck += itemData.Height; - - if ( considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ ) - continue; - - if ( IsOk( ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items ) ) - { - newZ = ourZ; - moveIsOk = true; - } - } - } - } - #endregion - - if ( considerLand && !landBlocks && stepTop >= landZ ) - { - int ourZ = landCenter; - int ourTop = ourZ + PersonHeight; - int testTop = checkTop; - - if ( ourZ + PersonHeight > testTop ) - testTop = ourZ + PersonHeight; - - bool shouldCheck = true; - - if ( moveIsOk ) - { - int cmp = Math.Abs( ourZ - m.Z ) - Math.Abs( newZ - m.Z ); - - if ( cmp > 0 || (cmp == 0 && ourZ > newZ) ) - shouldCheck = false; - } - - if ( shouldCheck && IsOk( ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items ) ) - { - newZ = ourZ; - moveIsOk = true; - } - } - - #region Mobiles - if ( moveIsOk ) - { - for ( int i = 0; moveIsOk && i < mobiles.Count; ++i ) - { - Mobile mob = mobiles[i]; - - if ( mob != m && ( mob.Z + 15 ) > newZ && ( newZ + 15 ) > mob.Z && !CanMoveOver( m, mob ) ) - moveIsOk = false; - } - } - #endregion - - return moveIsOk; - } - - private bool CanMoveOver( Mobile m, Mobile t ) - { - return ( !t.Alive || !m.Alive || t.IsDeadBondedPet || m.IsDeadBondedPet ) || ( t.Hidden && t.AccessLevel > AccessLevel.Player ); - } - - public bool CheckMovement( Mobile m, Map map, Point3D loc, Direction d, out int newZ ) - { - if ( map == null || map == Map.Internal ) - { - newZ = 0; - return false; - } - - int xStart = loc.X; - int yStart = loc.Y; - int xForward = xStart, yForward = yStart; - int xRight = xStart, yRight = yStart; - int xLeft = xStart, yLeft = yStart; - - bool checkDiagonals = ((int)d & 0x1) == 0x1; - - Offset( d, ref xForward, ref yForward ); - Offset( (Direction)(((int)d - 1) & 0x7), ref xLeft, ref yLeft ); - Offset( (Direction)(((int)d + 1) & 0x7), ref xRight, ref yRight ); - - if ( xForward < 0 || yForward < 0 || xForward >= map.Width || yForward >= map.Height ) - { - newZ = 0; - return false; - } - - int startZ, startTop; - - List itemsStart = m_Pools[0]; - List itemsForward = m_Pools[1]; - List itemsLeft = m_Pools[2]; - List itemsRight = m_Pools[3]; - - bool ignoreMovableImpassables = IgnoreMovableImpassables; - TileFlag reqFlags = ImpassableSurface; - - if ( m.CanSwim ) - reqFlags |= TileFlag.Wet; - - List mobsForward = m_MobPools[0]; - List mobsLeft = m_MobPools[1]; - List mobsRight = m_MobPools[2]; - - bool checkMobs = ( m is BaseCreature creature && !creature.Controlled && ( xForward != Goal.X || yForward != Goal.Y ) ); - - if ( checkDiagonals ) - { - Sector sectorStart = map.GetSector( xStart, yStart ); - Sector sectorForward = map.GetSector( xForward, yForward ); - Sector sectorLeft = map.GetSector( xLeft, yLeft ); - Sector sectorRight = map.GetSector( xRight, yRight ); - - List sectors = m_Sectors; - - sectors.Add( sectorStart ); - - if ( !sectors.Contains( sectorForward ) ) - sectors.Add( sectorForward ); - - if ( !sectors.Contains( sectorLeft ) ) - sectors.Add( sectorLeft ); - - if ( !sectors.Contains( sectorRight ) ) - sectors.Add( sectorRight ); - - for ( int i = 0; i < sectors.Count; ++i ) - { - Sector sector = sectors[i]; - - for ( int j = 0; j < sector.Items.Count; ++j ) - { - Item item = sector.Items[j]; - - if ( ignoreMovableImpassables && item.Movable && ( item.ItemData.Flags & ImpassableSurface ) != 0 ) - continue; - - if ( (item.ItemData.Flags & reqFlags) == 0 ) - continue; - - if ( sector == sectorStart && item.AtWorldPoint( xStart, yStart ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsStart.Add( item ); - else if ( sector == sectorForward && item.AtWorldPoint( xForward, yForward ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsForward.Add( item ); - else if ( sector == sectorLeft && item.AtWorldPoint( xLeft, yLeft ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsLeft.Add( item ); - else if ( sector == sectorRight && item.AtWorldPoint( xRight, yRight ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsRight.Add( item ); - } - - if ( checkMobs ) - { - for ( int j = 0; j < sector.Mobiles.Count; ++j ) - { - Mobile mob = sector.Mobiles[j]; - - if ( sector == sectorForward && mob.X == xForward && mob.Y == yForward ) - mobsForward.Add( mob ); - else if ( sector == sectorLeft && mob.X == xLeft && mob.Y == yLeft ) - mobsLeft.Add( mob ); - else if ( sector == sectorRight && mob.X == xRight && mob.Y == yRight ) - mobsRight.Add( mob ); - } - } - } - - if ( m_Sectors.Count > 0 ) - m_Sectors.Clear(); - } - else - { - Sector sectorStart = map.GetSector( xStart, yStart ); - Sector sectorForward = map.GetSector( xForward, yForward ); - - if ( sectorStart == sectorForward ) - { - for ( int i = 0; i < sectorStart.Items.Count; ++i ) - { - Item item = sectorStart.Items[i]; - - if ( ignoreMovableImpassables && item.Movable && ( item.ItemData.Flags & ImpassableSurface ) != 0 ) - continue; - - if ( (item.ItemData.Flags & reqFlags) == 0 ) - continue; - - if ( item.AtWorldPoint( xStart, yStart ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsStart.Add( item ); - else if ( item.AtWorldPoint( xForward, yForward ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsForward.Add( item ); - } - } - else - { - for ( int i = 0; i < sectorForward.Items.Count; ++i ) - { - Item item = sectorForward.Items[i]; - - if ( ignoreMovableImpassables && item.Movable && ( item.ItemData.Flags & ImpassableSurface ) != 0 ) - continue; - - if ( (item.ItemData.Flags & reqFlags) == 0 ) - continue; - - if ( item.AtWorldPoint( xForward, yForward ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsForward.Add( item ); - } - - for ( int i = 0; i < sectorStart.Items.Count; ++i ) - { - Item item = sectorStart.Items[i]; - - if ( ignoreMovableImpassables && item.Movable && ( item.ItemData.Flags & ImpassableSurface ) != 0 ) - continue; - - if ( (item.ItemData.Flags & reqFlags) == 0 ) - continue; - - if ( item.AtWorldPoint( xStart, yStart ) && !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue ) - itemsStart.Add( item ); - } - } - - if ( checkMobs ) - { - for ( int i = 0; i < sectorForward.Mobiles.Count; ++i ) - { - Mobile mob = sectorForward.Mobiles[i]; - - if ( mob.X == xForward && mob.Y == yForward ) - mobsForward.Add( mob ); - } - } - } - - GetStartZ( m, map, loc, itemsStart, out startZ, out startTop ); - - bool moveIsOk = Check( map, m, itemsForward, mobsForward, xForward, yForward, startTop, startZ, m.CanSwim, m.CantWalk, out newZ ); - - if ( moveIsOk && checkDiagonals ) - { - int hold; - - if ( m.Player && m.AccessLevel < AccessLevel.GameMaster ) { - if ( !Check( map, m, itemsLeft, mobsLeft, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, out hold ) || !Check( map, m, itemsRight, mobsRight, xRight, yRight, startTop, startZ, m.CanSwim, m.CantWalk, out hold ) ) - moveIsOk = false; - } else { - if ( !Check( map, m, itemsLeft, mobsLeft, xLeft, yLeft, startTop, startZ, m.CanSwim, m.CantWalk, out hold ) && !Check( map, m, itemsRight, mobsRight, xRight, yRight, startTop, startZ, m.CanSwim, m.CantWalk, out hold ) ) - moveIsOk = false; - } - } - - for ( int i = 0; i < (checkDiagonals ? 4 : 2); ++i ) - { - if ( m_Pools[i].Count != 0 ) - m_Pools[i].Clear(); - } - - for ( int i = 0; i < (checkDiagonals ? 3 : 1); ++i ) - { - if ( m_MobPools[i].Count != 0 ) - m_MobPools[i].Clear(); - } + if (ourZ + PersonHeight > testTop) + testTop = ourZ + PersonHeight; - if ( !moveIsOk ) - newZ = startZ; - - return moveIsOk; - } - - public bool CheckMovement( Mobile m, Direction d, out int newZ ) - { - return CheckMovement( m, m.Map, m.Location, d, out newZ ); - } - - private void GetStartZ( Mobile m, Map map, Point3D loc, List itemList, out int zLow, out int zTop ) - { - int xCheck = loc.X, yCheck = loc.Y; - - LandTile landTile = map.Tiles.GetLandTile( xCheck, yCheck ); - int landZ = 0, landCenter = 0, landTop = 0; - bool landBlocks = (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) != 0; - - if ( landBlocks && m.CanSwim && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) != 0 ) - landBlocks = false; - else if ( m.CantWalk && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) == 0 ) - landBlocks = true; - - map.GetAverageZ( xCheck, yCheck, ref landZ, ref landCenter, ref landTop ); - - bool considerLand = !landTile.Ignored; - - int zCenter = zLow = zTop = 0; - bool isSet = false; - - if ( considerLand && !landBlocks && loc.Z >= landCenter ) - { - zLow = landZ; - zCenter = landCenter; - - if ( !isSet || landTop > zTop ) - zTop = landTop; - - isSet = true; - } - - StaticTile[] staticTiles = map.Tiles.GetStaticTiles( xCheck, yCheck, true ); - - for ( int i = 0; i < staticTiles.Length; ++i ) - { - StaticTile tile = staticTiles[i]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - - int calcTop = (tile.Z + id.CalcHeight); - - if ( (!isSet || calcTop >= zCenter) && ( (id.Flags & TileFlag.Surface) != 0 || ( m.CanSwim && (id.Flags&TileFlag.Wet) != 0 ) ) && loc.Z >= calcTop ) - { - if ( m.CantWalk && (id.Flags & TileFlag.Wet) == 0 ) - continue; - - zLow = tile.Z; - zCenter = calcTop; - - int top = tile.Z + id.Height; - - if ( !isSet || top > zTop ) - zTop = top; - - isSet = true; - } - } - - for ( int i = 0; i < itemList.Count; ++i ) - { - Item item = itemList[i]; - - ItemData id = item.ItemData; - - int calcTop = item.Z + id.CalcHeight; - - if ( (!isSet || calcTop >= zCenter) && ( (id.Flags & TileFlag.Surface) != 0 || ( m.CanSwim && (id.Flags&TileFlag.Wet) != 0 ) ) && loc.Z >= calcTop ) - { - if ( m.CantWalk && (id.Flags & TileFlag.Wet) == 0 ) - continue; - - zLow = item.Z; - zCenter = calcTop; - - int top = item.Z + id.Height; + if (!itemData.Bridge) + itemTop += itemData.Height; - if ( !isSet || top > zTop ) - zTop = top; + if (stepTop >= itemTop) + { + int landCheck = itemZ; + + if (itemData.Height >= StepHeight) + landCheck += StepHeight; + else + landCheck += itemData.Height; + + if (considerLand && landCheck < landCenter && landCenter > ourZ && testTop > landZ) + continue; + + if (IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) + { + newZ = ourZ; + moveIsOk = true; + } + } + } + } - isSet = true; - } - } + #endregion - if ( !isSet ) - zLow = zTop = loc.Z; - else if ( loc.Z > zTop ) - zTop = loc.Z; - } + if (considerLand && !landBlocks && stepTop >= landZ) + { + int ourZ = landCenter; + int ourTop = ourZ + PersonHeight; + int testTop = checkTop; - public void Offset( Direction d, ref int x, ref int y ) - { - switch ( d & Direction.Mask ) - { - case Direction.North: --y; break; - case Direction.South: ++y; break; - case Direction.West: --x; break; - case Direction.East: ++x; break; - case Direction.Right: ++x; --y; break; - case Direction.Left: --x; ++y; break; - case Direction.Down: ++x; ++y; break; - case Direction.Up: --x; --y; break; - } - } - } -} + if (ourZ + PersonHeight > testTop) + testTop = ourZ + PersonHeight; + + bool shouldCheck = true; + + if (moveIsOk) + { + int cmp = Math.Abs(ourZ - m.Z) - Math.Abs(newZ - m.Z); + + if (cmp > 0 || cmp == 0 && ourZ > newZ) + shouldCheck = false; + } + + if (shouldCheck && IsOk(ignoreDoors, ignoreSpellFields, ourZ, testTop, tiles, items)) + { + newZ = ourZ; + moveIsOk = true; + } + } + + #region Mobiles + + if (moveIsOk) + for (int i = 0; moveIsOk && i < mobiles.Count; ++i) + { + Mobile mob = mobiles[i]; + + if (mob != m && mob.Z + 15 > newZ && newZ + 15 > mob.Z && !CanMoveOver(m, mob)) + moveIsOk = false; + } + + #endregion + + return moveIsOk; + } + + private bool CanMoveOver(Mobile m, Mobile t) + { + return !t.Alive || !m.Alive || t.IsDeadBondedPet || m.IsDeadBondedPet || + t.Hidden && t.AccessLevel > AccessLevel.Player; + } + + private void GetStartZ(Mobile m, Map map, Point3D loc, List itemList, out int zLow, out int zTop) + { + int xCheck = loc.X, yCheck = loc.Y; + + LandTile landTile = map.Tiles.GetLandTile(xCheck, yCheck); + int landZ = 0, landCenter = 0, landTop = 0; + bool landBlocks = (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) != 0; + + if (landBlocks && m.CanSwim && + (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) != 0) + landBlocks = false; + else if (m.CantWalk && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) == 0) + landBlocks = true; + + map.GetAverageZ(xCheck, yCheck, ref landZ, ref landCenter, ref landTop); + + bool considerLand = !landTile.Ignored; + + int zCenter = zLow = zTop = 0; + bool isSet = false; + + if (considerLand && !landBlocks && loc.Z >= landCenter) + { + zLow = landZ; + zCenter = landCenter; + + if (!isSet || landTop > zTop) + zTop = landTop; + + isSet = true; + } + + StaticTile[] staticTiles = map.Tiles.GetStaticTiles(xCheck, yCheck, true); + + for (int i = 0; i < staticTiles.Length; ++i) + { + StaticTile tile = staticTiles[i]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + + int calcTop = tile.Z + id.CalcHeight; + + if ((!isSet || calcTop >= zCenter) && + ((id.Flags & TileFlag.Surface) != 0 || m.CanSwim && (id.Flags & TileFlag.Wet) != 0) && loc.Z >= calcTop) + { + if (m.CantWalk && (id.Flags & TileFlag.Wet) == 0) + continue; + + zLow = tile.Z; + zCenter = calcTop; + + int top = tile.Z + id.Height; + + if (!isSet || top > zTop) + zTop = top; + + isSet = true; + } + } + + for (int i = 0; i < itemList.Count; ++i) + { + Item item = itemList[i]; + + ItemData id = item.ItemData; + + int calcTop = item.Z + id.CalcHeight; + + if ((!isSet || calcTop >= zCenter) && + ((id.Flags & TileFlag.Surface) != 0 || m.CanSwim && (id.Flags & TileFlag.Wet) != 0) && loc.Z >= calcTop) + { + if (m.CantWalk && (id.Flags & TileFlag.Wet) == 0) + continue; + + zLow = item.Z; + zCenter = calcTop; + + int top = item.Z + id.Height; + + if (!isSet || top > zTop) + zTop = top; + + isSet = true; + } + } + + if (!isSet) + zLow = zTop = loc.Z; + else if (loc.Z > zTop) + zTop = loc.Z; + } + + public void Offset(Direction d, ref int x, ref int y) + { + switch (d & Direction.Mask) + { + case Direction.North: + --y; + break; + case Direction.South: + ++y; + break; + case Direction.West: + --x; + break; + case Direction.East: + ++x; + break; + case Direction.Right: + ++x; + --y; + break; + case Direction.Left: + --x; + ++y; + break; + case Direction.Down: + ++x; + ++y; + break; + case Direction.Up: + --x; + --y; + break; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Pathing/MovementPath.cs b/Scripts/Engines/Pathing/MovementPath.cs index f341568a8..4f2abb218 100644 --- a/Scripts/Engines/Pathing/MovementPath.cs +++ b/Scripts/Engines/Pathing/MovementPath.cs @@ -1,154 +1,150 @@ using System; -using Server.Targeting; -using Server.PathAlgorithms; -using Server.PathAlgorithms.SlowAStar; -using Server.PathAlgorithms.FastAStar; using Server.Commands; +using Server.Items; +using Server.PathAlgorithms; +using Server.PathAlgorithms.FastAStar; +using Server.PathAlgorithms.SlowAStar; +using Server.Spells; +using Server.Targeting; namespace Server { - public sealed class MovementPath - { - public Map Map { get; } + public sealed class MovementPath + { + public MovementPath(Mobile m, Point3D goal) + { + Point3D start = m.Location; + Map map = m.Map; - public Point3D Start { get; } + Map = map; + Start = start; + Goal = goal; - public Point3D Goal { get; } + if (map == null || map == Map.Internal) + return; - public Direction[] Directions { get; } + if (Utility.InRange(start, goal, 1)) + return; - public bool Success => ( Directions != null && Directions.Length > 0 ); + try + { + PathAlgorithm alg = OverrideAlgorithm; - public static void Initialize() - { - CommandSystem.Register( "Path", AccessLevel.GameMaster, Path_OnCommand ); - } + if (alg == null) alg = FastAStarAlgorithm.Instance; - public static void Path_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, true, TargetFlags.None, Path_OnTarget ); - e.Mobile.SendMessage( "Target a location and a path will be drawn there." ); - } + if (alg != null && alg.CheckCondition(m, map, start, goal)) + Directions = alg.Find(m, map, start, goal); + } + catch (Exception e) + { + Console.WriteLine("Warning: {0}: Pathing error from {1} to {2}", e.GetType().Name, start, goal); + } + } - private static void Path( Mobile from, IPoint3D p, PathAlgorithm alg, string name, int zOffset ) - { - OverrideAlgorithm = alg; + public Map Map{ get; } - long start = DateTime.UtcNow.Ticks; - MovementPath path = new MovementPath( from, new Point3D( p ) ); - long end = DateTime.UtcNow.Ticks; - double len = Math.Round( (end-start) / 10000.0, 2 ); + public Point3D Start{ get; } - if ( !path.Success ) - { - from.SendMessage( "{0} path failed: {1}ms", name, len ); - } - else - { - from.SendMessage( "{0} path success: {1}ms", name, len ); + public Point3D Goal{ get; } - int x = from.X; - int y = from.Y; - int z = from.Z; + public Direction[] Directions{ get; } - for ( int i = 0; i < path.Directions.Length; ++i ) - { - Movement.Movement.Offset( path.Directions[i], ref x, ref y ); + public bool Success => Directions != null && Directions.Length > 0; - new Items.RecallRune().MoveToWorld( new Point3D( x, y, z+zOffset ), from.Map ); - } - } - } + public static PathAlgorithm OverrideAlgorithm{ get; set; } - public static void Path_OnTarget( Mobile from, object obj ) - { - if ( !(obj is IPoint3D p) ) - return; + public static void Initialize() + { + CommandSystem.Register("Path", AccessLevel.GameMaster, Path_OnCommand); + } - Spells.SpellHelper.GetSurfaceTop( ref p ); + public static void Path_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, true, TargetFlags.None, Path_OnTarget); + e.Mobile.SendMessage("Target a location and a path will be drawn there."); + } - Path( from, p, FastAStarAlgorithm.Instance, "Fast", 0 ); - Path( from, p, SlowAStarAlgorithm.Instance, "Slow", 2 ); - OverrideAlgorithm = null; + private static void Path(Mobile from, IPoint3D p, PathAlgorithm alg, string name, int zOffset) + { + OverrideAlgorithm = alg; - /*MovementPath path = new MovementPath( from, new Point3D( p ) ); + long start = DateTime.UtcNow.Ticks; + MovementPath path = new MovementPath(from, new Point3D(p)); + long end = DateTime.UtcNow.Ticks; + double len = Math.Round((end - start) / 10000.0, 2); - if ( !path.Success ) - { - from.SendMessage( "No path to there could be found." ); - } - else - { - //for ( int i = 0; i < path.Directions.Length; ++i ) - // Timer.DelayCall( TimeSpan.FromSeconds( 0.1 + (i * 0.3) ), new TimerStateCallback( Pathfind ), new object[]{ from, path.Directions[i] } ); - int x = from.X; - int y = from.Y; - int z = from.Z; + if (!path.Success) + { + from.SendMessage("{0} path failed: {1}ms", name, len); + } + else + { + from.SendMessage("{0} path success: {1}ms", name, len); - for ( int i = 0; i < path.Directions.Length; ++i ) - { - Movement.Movement.Offset( path.Directions[i], ref x, ref y ); + int x = from.X; + int y = from.Y; + int z = from.Z; - new Items.RecallRune().MoveToWorld( new Point3D( x, y, z ), from.Map ); - } - }*/ - } + for (int i = 0; i < path.Directions.Length; ++i) + { + Movement.Movement.Offset(path.Directions[i], ref x, ref y); - public static void Pathfind( object state ) - { - object[] states = (object[])state; - Mobile from = (Mobile) states[0]; - Direction d = (Direction) states[1]; + new RecallRune().MoveToWorld(new Point3D(x, y, z + zOffset), from.Map); + } + } + } - try - { - from.Direction = d; - from.NetState.BlockAllPackets=true; - from.Move( d ); - from.NetState.BlockAllPackets=false; - from.ProcessDelta(); - } - catch - { - } - } + public static void Path_OnTarget(Mobile from, object obj) + { + if (!(obj is IPoint3D p)) + return; - public static PathAlgorithm OverrideAlgorithm { get; set; } + SpellHelper.GetSurfaceTop(ref p); - public MovementPath( Mobile m, Point3D goal ) - { - Point3D start = m.Location; - Map map = m.Map; + Path(from, p, FastAStarAlgorithm.Instance, "Fast", 0); + Path(from, p, SlowAStarAlgorithm.Instance, "Slow", 2); + OverrideAlgorithm = null; - Map = map; - Start = start; - Goal = goal; + /*MovementPath path = new MovementPath( from, new Point3D( p ) ); - if ( map == null || map == Map.Internal ) - return; + if ( !path.Success ) + { + from.SendMessage( "No path to there could be found." ); + } + else + { + //for ( int i = 0; i < path.Directions.Length; ++i ) + // Timer.DelayCall( TimeSpan.FromSeconds( 0.1 + (i * 0.3) ), new TimerStateCallback( Pathfind ), new object[]{ from, path.Directions[i] } ); + int x = from.X; + int y = from.Y; + int z = from.Z; - if ( Utility.InRange( start, goal, 1 ) ) - return; + for ( int i = 0; i < path.Directions.Length; ++i ) + { + Movement.Movement.Offset( path.Directions[i], ref x, ref y ); - try - { - PathAlgorithm alg = OverrideAlgorithm; + new Items.RecallRune().MoveToWorld( new Point3D( x, y, z ), from.Map ); + } + }*/ + } - if ( alg == null ) - { - alg = FastAStarAlgorithm.Instance; + public static void Pathfind(object state) + { + object[] states = (object[])state; + Mobile from = (Mobile)states[0]; + Direction d = (Direction)states[1]; - //if ( !alg.CheckCondition( m, map, start, goal ) ) // SlowAstar is still broken - // alg = SlowAStarAlgorithm.Instance; // TODO: Fix SlowAstar - } - - if ( alg != null && alg.CheckCondition( m, map, start, goal ) ) - Directions = alg.Find( m, map, start, goal ); - } - catch ( Exception e ) - { - Console.WriteLine( "Warning: {0}: Pathing error from {1} to {2}", e.GetType().Name, start, goal ); - } - } - } -} + try + { + from.Direction = d; + from.NetState.BlockAllPackets = true; + from.Move(d); + from.NetState.BlockAllPackets = false; + from.ProcessDelta(); + } + catch + { + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Pathing/PathAlgorithm.cs b/Scripts/Engines/Pathing/PathAlgorithm.cs index e71e9b059..a3edcf4aa 100644 --- a/Scripts/Engines/Pathing/PathAlgorithm.cs +++ b/Scripts/Engines/Pathing/PathAlgorithm.cs @@ -1,33 +1,33 @@ namespace Server.PathAlgorithms { - public abstract class PathAlgorithm - { - public abstract bool CheckCondition( Mobile m, Map map, Point3D start, Point3D goal ); - public abstract Direction[] Find( Mobile m, Map map, Point3D start, Point3D goal ); + public abstract class PathAlgorithm + { + private static Direction[] m_CalcDirections = new Direction[9] + { + Direction.Up, + Direction.North, + Direction.Right, + Direction.West, + Direction.North, + Direction.East, + Direction.Left, + Direction.South, + Direction.Down + }; - private static Direction[] m_CalcDirections = new Direction[9] - { - Direction.Up, - Direction.North, - Direction.Right, - Direction.West, - Direction.North, - Direction.East, - Direction.Left, - Direction.South, - Direction.Down - }; + public abstract bool CheckCondition(Mobile m, Map map, Point3D start, Point3D goal); + public abstract Direction[] Find(Mobile m, Map map, Point3D start, Point3D goal); - public Direction GetDirection( int xSource, int ySource, int xDest, int yDest ) - { - int x = xDest + 1 - xSource; - int y = yDest + 1 - ySource; - int v = (y * 3) + x; + public Direction GetDirection(int xSource, int ySource, int xDest, int yDest) + { + int x = xDest + 1 - xSource; + int y = yDest + 1 - ySource; + int v = y * 3 + x; - if ( v < 0 || v >= 9 ) - return Direction.North; + if (v < 0 || v >= 9) + return Direction.North; - return m_CalcDirections[v]; - } - } + return m_CalcDirections[v]; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Pathing/PathFollower.cs b/Scripts/Engines/Pathing/PathFollower.cs index 29822b74a..3a49cd028 100644 --- a/Scripts/Engines/Pathing/PathFollower.cs +++ b/Scripts/Engines/Pathing/PathFollower.cs @@ -3,191 +3,191 @@ using CalcMoves = Server.Movement.Movement; namespace Server { - public class PathFollower - { - // Should we use pathfinding? 'false' for not - private static bool Enabled = true; + public class PathFollower + { + // Should we use pathfinding? 'false' for not + private static bool Enabled = true; - private Mobile m_From; - private MovementPath m_Path; - private int m_Index; - private Point3D m_Next, m_LastGoalLoc; - private DateTime m_LastPathTime; + private static TimeSpan RepathDelay = TimeSpan.FromSeconds(2.0); - public MoveMethod Mover { get; set; } + private Mobile m_From; + private int m_Index; + private DateTime m_LastPathTime; + private Point3D m_Next, m_LastGoalLoc; + private MovementPath m_Path; - public IPoint3D Goal { get; } + public PathFollower(Mobile from, IPoint3D goal) + { + m_From = from; + Goal = goal; + } - public PathFollower( Mobile from, IPoint3D goal ) - { - m_From = from; - Goal = goal; - } + public MoveMethod Mover{ get; set; } - public MoveResult Move( Direction d ) - { - if ( Mover == null ) - return ( m_From.Move( d ) ? MoveResult.Success : MoveResult.Blocked ); + public IPoint3D Goal{ get; } - return Mover( d ); - } + public MoveResult Move(Direction d) + { + if (Mover == null) + return m_From.Move(d) ? MoveResult.Success : MoveResult.Blocked; - public Point3D GetGoalLocation() - { - if ( Goal is Item item ) - return item.GetWorldLocation(); + return Mover(d); + } - return new Point3D( Goal ); - } + public Point3D GetGoalLocation() + { + if (Goal is Item item) + return item.GetWorldLocation(); - private static TimeSpan RepathDelay = TimeSpan.FromSeconds( 2.0 ); + return new Point3D(Goal); + } - public void Advance( ref Point3D p, int index ) - { - if ( m_Path != null && m_Path.Success ) - { - Direction[] dirs = m_Path.Directions; + public void Advance(ref Point3D p, int index) + { + if (m_Path != null && m_Path.Success) + { + Direction[] dirs = m_Path.Directions; - if ( index >= 0 && index < dirs.Length ) - { - int x = p.X, y = p.Y; + if (index >= 0 && index < dirs.Length) + { + int x = p.X, y = p.Y; - CalcMoves.Offset( dirs[index], ref x, ref y ); + CalcMoves.Offset(dirs[index], ref x, ref y); - p.X = x; - p.Y = y; - } - } - } + p.X = x; + p.Y = y; + } + } + } - public void ForceRepath() - { - m_Path = null; - } + public void ForceRepath() + { + m_Path = null; + } - public bool CheckPath() - { - if ( !Enabled ) - return false; + public bool CheckPath() + { + if (!Enabled) + return false; - bool repath = false; + bool repath = false; - Point3D goal = GetGoalLocation(); + Point3D goal = GetGoalLocation(); - if ( m_Path == null ) - repath = true; - else if ( (!m_Path.Success || goal != m_LastGoalLoc) && (m_LastPathTime + RepathDelay) <= DateTime.UtcNow ) - repath = true; - else if ( m_Path.Success && Check( m_From.Location, m_LastGoalLoc, 0 ) ) - repath = true; + if (m_Path == null) + repath = true; + else if ((!m_Path.Success || goal != m_LastGoalLoc) && m_LastPathTime + RepathDelay <= DateTime.UtcNow) + repath = true; + else if (m_Path.Success && Check(m_From.Location, m_LastGoalLoc, 0)) + repath = true; - if ( !repath ) - return false; + if (!repath) + return false; - m_LastPathTime = DateTime.UtcNow; - m_LastGoalLoc = goal; + m_LastPathTime = DateTime.UtcNow; + m_LastGoalLoc = goal; - m_Path = new MovementPath( m_From, goal ); + m_Path = new MovementPath(m_From, goal); - m_Index = 0; - m_Next = m_From.Location; + m_Index = 0; + m_Next = m_From.Location; - Advance( ref m_Next, m_Index ); + Advance(ref m_Next, m_Index); - return true; - } + return true; + } - public bool Check( Point3D loc, Point3D goal, int range ) - { - if ( !Utility.InRange( loc, goal, range ) ) - return false; + public bool Check(Point3D loc, Point3D goal, int range) + { + if (!Utility.InRange(loc, goal, range)) + return false; - if ( range <= 1 && Math.Abs( loc.Z - goal.Z ) >= 16 ) - return false; + if (range <= 1 && Math.Abs(loc.Z - goal.Z) >= 16) + return false; - return true; - } + return true; + } - public bool Follow( bool run, int range ) - { - Point3D goal = GetGoalLocation(); - Direction d; + public bool Follow(bool run, int range) + { + Point3D goal = GetGoalLocation(); + Direction d; - if ( Check( m_From.Location, goal, range ) ) - return true; + if (Check(m_From.Location, goal, range)) + return true; - bool repathed = CheckPath(); + bool repathed = CheckPath(); - if ( !Enabled || !m_Path.Success ) - { - d = m_From.GetDirectionTo( goal ); + if (!Enabled || !m_Path.Success) + { + d = m_From.GetDirectionTo(goal); - if ( run ) - d |= Direction.Running; + if (run) + d |= Direction.Running; - m_From.SetDirection( d ); - Move( d ); + m_From.SetDirection(d); + Move(d); - return Check( m_From.Location, goal, range ); - } + return Check(m_From.Location, goal, range); + } - d = m_From.GetDirectionTo( m_Next ); + d = m_From.GetDirectionTo(m_Next); - if ( run ) - d |= Direction.Running; + if (run) + d |= Direction.Running; - m_From.SetDirection( d ); + m_From.SetDirection(d); - MoveResult res = Move( d ); + MoveResult res = Move(d); - if ( res == MoveResult.Blocked ) - { - if ( repathed ) - return false; + if (res == MoveResult.Blocked) + { + if (repathed) + return false; - m_Path = null; - CheckPath(); + m_Path = null; + CheckPath(); - if ( !m_Path.Success ) - { - d = m_From.GetDirectionTo( goal ); + if (!m_Path.Success) + { + d = m_From.GetDirectionTo(goal); - if ( run ) - d |= Direction.Running; + if (run) + d |= Direction.Running; - m_From.SetDirection( d ); - Move( d ); + m_From.SetDirection(d); + Move(d); - return Check( m_From.Location, goal, range ); - } + return Check(m_From.Location, goal, range); + } - d = m_From.GetDirectionTo( m_Next ); + d = m_From.GetDirectionTo(m_Next); - if ( run ) - d |= Direction.Running; + if (run) + d |= Direction.Running; - m_From.SetDirection( d ); + m_From.SetDirection(d); - res = Move( d ); + res = Move(d); - if ( res == MoveResult.Blocked ) - return false; - } + if (res == MoveResult.Blocked) + return false; + } - if ( m_From.X == m_Next.X && m_From.Y == m_Next.Y ) - { - if ( m_From.Z == m_Next.Z ) - { - ++m_Index; - Advance( ref m_Next, m_Index ); - } - else - { - m_Path = null; - } - } + if (m_From.X == m_Next.X && m_From.Y == m_Next.Y) + { + if (m_From.Z == m_Next.Z) + { + ++m_Index; + Advance(ref m_Next, m_Index); + } + else + { + m_Path = null; + } + } - return Check( m_From.Location, goal, range ); - } - } -} + return Check(m_From.Location, goal, range); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Pathing/SlowAStarAlgorithm.cs b/Scripts/Engines/Pathing/SlowAStarAlgorithm.cs index 5fb31992a..5a6511f90 100644 --- a/Scripts/Engines/Pathing/SlowAStarAlgorithm.cs +++ b/Scripts/Engines/Pathing/SlowAStarAlgorithm.cs @@ -5,257 +5,272 @@ using MoveImpl = Server.Movement.MovementImpl; namespace Server.PathAlgorithms.SlowAStar { - public struct PathNode - { - public int x, y, z; - public int g, h; - public int px, py, pz; - public int dir; - } + public struct PathNode + { + public int x, y, z; + public int g, h; + public int px, py, pz; + public int dir; + } - public class SlowAStarAlgorithm : PathAlgorithm - { - public static PathAlgorithm Instance = new SlowAStarAlgorithm(); + public class SlowAStarAlgorithm : PathAlgorithm + { + private const int MaxDepth = 300; + private const int MaxNodes = MaxDepth * 16; + public static PathAlgorithm Instance = new SlowAStarAlgorithm(); - private const int MaxDepth = 300; - private const int MaxNodes = MaxDepth * 16; + private static PathNode[] m_Closed = new PathNode[MaxNodes]; + private static PathNode[] m_Open = new PathNode[MaxNodes]; + private static PathNode[] m_Successors = new PathNode[8]; + private static Direction[] m_Path = new Direction[MaxNodes]; - private static PathNode[] m_Closed = new PathNode[MaxNodes]; - private static PathNode[] m_Open = new PathNode[MaxNodes]; - private static PathNode[] m_Successors = new PathNode[8]; - private static Direction[] m_Path = new Direction[MaxNodes]; + private Point3D m_Goal; - private Point3D m_Goal; + public int Heuristic(int x, int y, int z) + { + x -= m_Goal.X; + y -= m_Goal.Y; + z -= m_Goal.Z; - public int Heuristic( int x, int y, int z ) - { - x -= m_Goal.X; - y -= m_Goal.Y; - z -= m_Goal.Z; + x *= 11; + y *= 11; - x *= 11; - y *= 11; + return x * x + y * y + z * z; + } - return (x*x)+(y*y)+(z*z); - } + public override bool CheckCondition(Mobile m, Map map, Point3D start, Point3D goal) + { + return false; + } - public override bool CheckCondition( Mobile m, Map map, Point3D start, Point3D goal ) - { - return false; - } + public override Direction[] Find(Mobile m, Map map, Point3D start, Point3D goal) + { + m_Goal = goal; - public override Direction[] Find( Mobile m, Map map, Point3D start, Point3D goal ) - { - m_Goal = goal; + BaseCreature bc = m as BaseCreature; - BaseCreature bc = m as BaseCreature; + PathNode curNode; - PathNode curNode; + PathNode goalNode = new PathNode(); + goalNode.x = goal.X; + goalNode.y = goal.Y; + goalNode.z = goal.Z; - PathNode goalNode = new PathNode(); - goalNode.x = goal.X; - goalNode.y = goal.Y; - goalNode.z = goal.Z; + PathNode startNode = new PathNode(); + startNode.x = start.X; + startNode.y = start.Y; + startNode.z = start.Z; + startNode.h = Heuristic(startNode.x, startNode.y, startNode.z); - PathNode startNode = new PathNode(); - startNode.x = start.X; - startNode.y = start.Y; - startNode.z = start.Z; - startNode.h = Heuristic( startNode.x, startNode.y, startNode.z ); + PathNode[] closed = m_Closed, open = m_Open, successors = m_Successors; + Direction[] path = m_Path; - PathNode[] closed = m_Closed, open = m_Open, successors = m_Successors; - Direction[] path = m_Path; + int closedCount = 0, openCount = 0, sucCount = 0, pathCount = 0; + int popIndex, curF; + int x, y, z; + int depth = 0; - int closedCount = 0, openCount = 0, sucCount = 0, pathCount = 0; - int popIndex, curF; - int x, y, z; - int depth = 0; + int xBacktrack, yBacktrack, zBacktrack, iBacktrack = 0; - int xBacktrack, yBacktrack, zBacktrack, iBacktrack = 0; + open[openCount++] = startNode; - open[openCount++] = startNode; + while (openCount > 0) + { + curNode = open[0]; + curF = curNode.g + curNode.h; + popIndex = 0; - while ( openCount > 0 ) - { - curNode = open[0]; - curF = curNode.g + curNode.h; - popIndex = 0; + for (int i = 1; i < openCount; ++i) + if (open[i].g + open[i].h < curF) + { + curNode = open[i]; + curF = curNode.g + curNode.h; + popIndex = i; + } - for ( int i = 1; i < openCount; ++i ) - { - if ( (open[i].g + open[i].h) < curF ) - { - curNode = open[i]; - curF = curNode.g + curNode.h; - popIndex = i; - } - } + if (curNode.x == goalNode.x && curNode.y == goalNode.y && Math.Abs(curNode.z - goalNode.z) < 16) + { + if (closedCount == MaxNodes) + break; - if ( curNode.x == goalNode.x && curNode.y == goalNode.y && Math.Abs( curNode.z-goalNode.z ) < 16 ) - { - if ( closedCount == MaxNodes ) - break; + closed[closedCount++] = curNode; - closed[closedCount++] = curNode; + xBacktrack = curNode.px; + yBacktrack = curNode.py; + zBacktrack = curNode.pz; - xBacktrack = curNode.px; - yBacktrack = curNode.py; - zBacktrack = curNode.pz; + if (pathCount == MaxNodes) + break; - if ( pathCount == MaxNodes ) - break; + path[pathCount++] = (Direction)curNode.dir; - path[pathCount++] = (Direction)curNode.dir; + while (xBacktrack != startNode.x || yBacktrack != startNode.y || zBacktrack != startNode.z) + { + bool found = false; - while ( xBacktrack != startNode.x || yBacktrack != startNode.y || zBacktrack != startNode.z ) - { - bool found = false; + for (int j = 0; !found && j < closedCount; ++j) + if (closed[j].x == xBacktrack && closed[j].y == yBacktrack && closed[j].z == zBacktrack) + { + if (pathCount == MaxNodes) + break; - for ( int j = 0; !found && j < closedCount; ++j ) - { - if ( closed[j].x == xBacktrack && closed[j].y == yBacktrack && closed[j].z == zBacktrack ) - { - if ( pathCount == MaxNodes ) - break; + curNode = closed[j]; + path[pathCount++] = (Direction)curNode.dir; + xBacktrack = curNode.px; + yBacktrack = curNode.py; + zBacktrack = curNode.pz; + found = true; + } - curNode = closed[j]; - path[pathCount++] = (Direction)curNode.dir; - xBacktrack = curNode.px; - yBacktrack = curNode.py; - zBacktrack = curNode.pz; - found = true; - } - } + if (!found) + { + Console.WriteLine("bugaboo.."); + return null; + } - if ( !found ) - { - Console.WriteLine( "bugaboo.." ); - return null; - } + if (pathCount == MaxNodes) + break; + } - if ( pathCount == MaxNodes ) - break; - } + if (pathCount == MaxNodes) + break; - if ( pathCount == MaxNodes ) - break; + Direction[] dirs = new Direction[pathCount]; - Direction[] dirs = new Direction[pathCount]; + while (pathCount > 0) + dirs[iBacktrack++] = path[--pathCount]; - while ( pathCount > 0 ) - dirs[iBacktrack++] = path[--pathCount]; + return dirs; + } - return dirs; - } + --openCount; - --openCount; + for (int i = popIndex; i < openCount; ++i) + open[i] = open[i + 1]; - for ( int i = popIndex; i < openCount; ++i ) - open[i] = open[i + 1]; + sucCount = 0; - sucCount = 0; + if (bc != null) + { + MoveImpl.AlwaysIgnoreDoors = bc.CanOpenDoors; + MoveImpl.IgnoreMovableImpassables = bc.CanMoveOverObstacles; + } - if ( bc != null ) - { - MoveImpl.AlwaysIgnoreDoors = bc.CanOpenDoors; - MoveImpl.IgnoreMovableImpassables = bc.CanMoveOverObstacles; - } + MoveImpl.Goal = goal; - MoveImpl.Goal = goal; + for (int i = 0; i < 8; ++i) + { + switch (i) + { + default: + case 0: + x = 0; + y = -1; + break; + case 1: + x = 1; + y = -1; + break; + case 2: + x = 1; + y = 0; + break; + case 3: + x = 1; + y = 1; + break; + case 4: + x = 0; + y = 1; + break; + case 5: + x = -1; + y = 1; + break; + case 6: + x = -1; + y = 0; + break; + case 7: + x = -1; + y = -1; + break; + } - for ( int i = 0; i < 8; ++i ) - { - switch ( i ) - { - default: - case 0: x = 0; y = -1; break; - case 1: x = 1; y = -1; break; - case 2: x = 1; y = 0; break; - case 3: x = 1; y = 1; break; - case 4: x = 0; y = 1; break; - case 5: x = -1; y = 1; break; - case 6: x = -1; y = 0; break; - case 7: x = -1; y = -1; break; - } + if (CalcMoves.CheckMovement(m, map, new Point3D(curNode.x, curNode.y, curNode.z), (Direction)i, out z)) + { + successors[sucCount].x = x + curNode.x; + successors[sucCount].y = y + curNode.y; + successors[sucCount++].z = z; + } + } - if ( CalcMoves.CheckMovement( m, map, new Point3D( curNode.x, curNode.y, curNode.z ), (Direction)i, out z ) ) - { - successors[sucCount].x = x + curNode.x; - successors[sucCount].y = y + curNode.y; - successors[sucCount++].z = z; - } - } + MoveImpl.AlwaysIgnoreDoors = false; + MoveImpl.IgnoreMovableImpassables = false; + MoveImpl.Goal = Point3D.Zero; - MoveImpl.AlwaysIgnoreDoors = false; - MoveImpl.IgnoreMovableImpassables = false; - MoveImpl.Goal = Point3D.Zero; + if (sucCount == 0 || ++depth > MaxDepth) + break; - if ( sucCount == 0 || ++depth > MaxDepth ) - break; + for (int i = 0; i < sucCount; ++i) + { + x = successors[i].x; + y = successors[i].y; + z = successors[i].z; - for ( int i = 0; i < sucCount; ++i ) - { - x = successors[i].x; - y = successors[i].y; - z = successors[i].z; + successors[i].g = curNode.g + 1; - successors[i].g = curNode.g + 1; + int openIndex = -1, closedIndex = -1; - int openIndex = -1, closedIndex = -1; + for (int j = 0; openIndex == -1 && j < openCount; ++j) + if (open[j].x == x && open[j].y == y && open[j].z == z) + openIndex = j; - for ( int j = 0; openIndex == -1 && j < openCount; ++j ) - { - if ( open[j].x == x && open[j].y == y && open[j].z == z ) - openIndex = j; - } + if (openIndex >= 0 && open[openIndex].g < successors[i].g) + continue; - if ( openIndex >= 0 && open[openIndex].g < successors[i].g ) - continue; + for (int j = 0; closedIndex == -1 && j < closedCount; ++j) + if (closed[j].x == x && closed[j].y == y && closed[j].z == z) + closedIndex = j; - for ( int j = 0; closedIndex == -1 && j < closedCount; ++j ) - { - if ( closed[j].x == x && closed[j].y == y && closed[j].z == z ) - closedIndex = j; - } + if (closedIndex >= 0 && closed[closedIndex].g < successors[i].g) + continue; - if ( closedIndex >= 0 && closed[closedIndex].g < successors[i].g ) - continue; + if (openIndex >= 0) + { + --openCount; - if ( openIndex >= 0 ) - { - --openCount; + for (int j = openIndex; j < openCount; ++j) + open[j] = open[j + 1]; + } - for ( int j = openIndex; j < openCount; ++j ) - open[j] = open[j + 1]; - } + if (closedIndex >= 0) + { + --closedCount; - if ( closedIndex >= 0 ) - { - --closedCount; + for (int j = closedIndex; j < closedCount; ++j) + closed[j] = closed[j + 1]; + } - for ( int j = closedIndex; j < closedCount; ++j ) - closed[j] = closed[j + 1]; - } + successors[i].px = curNode.x; + successors[i].py = curNode.y; + successors[i].pz = curNode.z; + successors[i].dir = (int)GetDirection(curNode.x, curNode.y, x, y); + successors[i].h = Heuristic(x, y, z); - successors[i].px = curNode.x; - successors[i].py = curNode.y; - successors[i].pz = curNode.z; - successors[i].dir = (int)GetDirection( curNode.x, curNode.y, x, y ); - successors[i].h = Heuristic( x, y, z ); + if (openCount == MaxNodes) + break; - if ( openCount == MaxNodes ) - break; + open[openCount++] = successors[i]; + } - open[openCount++] = successors[i]; - } + if (openCount == MaxNodes || closedCount == MaxNodes) + break; - if ( openCount == MaxNodes || closedCount == MaxNodes ) - break; + closed[closedCount++] = curNode; + } - closed[closedCount++] = curNode; - } - - return null; - } - } -} + return null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/EmptyTheBowlGump.cs b/Scripts/Engines/Plants/EmptyTheBowlGump.cs index fd4ef7a2f..04d364f0f 100644 --- a/Scripts/Engines/Plants/EmptyTheBowlGump.cs +++ b/Scripts/Engines/Plants/EmptyTheBowlGump.cs @@ -3,119 +3,119 @@ using Server.Network; namespace Server.Engines.Plants { - public class EmptyTheBowlGump : Gump - { - private PlantItem m_Plant; + public class EmptyTheBowlGump : Gump + { + private PlantItem m_Plant; - public EmptyTheBowlGump( PlantItem plant ) : base( 20, 20 ) - { - m_Plant = plant; + public EmptyTheBowlGump(PlantItem plant) : base(20, 20) + { + m_Plant = plant; - DrawBackground(); + DrawBackground(); - AddLabel( 90, 70, 0x44, "Empty the bowl?" ); + AddLabel(90, 70, 0x44, "Empty the bowl?"); - DrawPicture(); + DrawPicture(); - AddButton( 98, 150, 0x47E, 0x480, 1, GumpButtonType.Reply, 0 ); // Cancel + AddButton(98, 150, 0x47E, 0x480, 1, GumpButtonType.Reply, 0); // Cancel - AddButton( 138, 151, 0xD2, 0xD2, 2, GumpButtonType.Reply, 0 ); // Help - AddLabel( 143, 151, 0x835, "?" ); + AddButton(138, 151, 0xD2, 0xD2, 2, GumpButtonType.Reply, 0); // Help + AddLabel(143, 151, 0x835, "?"); - AddButton( 168, 150, 0x481, 0x483, 3, GumpButtonType.Reply, 0 ); // Ok - } + AddButton(168, 150, 0x481, 0x483, 3, GumpButtonType.Reply, 0); // Ok + } - private void DrawBackground() - { - AddBackground( 50, 50, 200, 150, 0xE10 ); + private void DrawBackground() + { + AddBackground(50, 50, 200, 150, 0xE10); - AddItem( 45, 45, 0xCEF ); - AddItem( 45, 118, 0xCF0 ); + AddItem(45, 45, 0xCEF); + AddItem(45, 118, 0xCF0); - AddItem( 211, 45, 0xCEB ); - AddItem( 211, 118, 0xCEC ); - } + AddItem(211, 45, 0xCEB); + AddItem(211, 118, 0xCEC); + } - private void DrawPicture() - { - AddItem( 90, 100, 0x1602 ); - AddImage( 140, 102, 0x15E1 ); - AddItem( 160, 100, 0x15FD ); + private void DrawPicture() + { + AddItem(90, 100, 0x1602); + AddImage(140, 102, 0x15E1); + AddItem(160, 100, 0x15FD); - if ( m_Plant.PlantStatus != PlantStatus.BowlOfDirt && m_Plant.PlantStatus < PlantStatus.Plant ) - AddItem( 156, 130, 0xDCF ); // Seed - } + if (m_Plant.PlantStatus != PlantStatus.BowlOfDirt && m_Plant.PlantStatus < PlantStatus.Plant) + AddItem(156, 130, 0xDCF); // Seed + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - if ( info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus >= PlantStatus.DecorativePlant ) - return; - - if ( info.ButtonID == 3 && !from.InRange( m_Plant.GetWorldLocation(), 3 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 500446 ); // That is too far away. - return; - } + if (info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus >= PlantStatus.DecorativePlant) + return; - if ( !m_Plant.IsUsableBy( from ) ) - { - m_Plant.LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - return; - } + if (info.ButtonID == 3 && !from.InRange(m_Plant.GetWorldLocation(), 3)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 500446); // That is too far away. + return; + } - switch ( info.ButtonID ) - { - case 1: // Cancel - { - from.SendGump( new MainPlantGump( m_Plant ) ); + if (!m_Plant.IsUsableBy(from)) + { + m_Plant.LabelTo(from, 1061856); // You must have the item in your backpack or locked down in order to use it. + return; + } - break; - } - case 2: // Help - { - from.Send( new DisplayHelpTopic( 71, true ) ); // EMPTYING THE BOWL + switch (info.ButtonID) + { + case 1: // Cancel + { + from.SendGump(new MainPlantGump(m_Plant)); - from.SendGump( new EmptyTheBowlGump( m_Plant ) ); + break; + } + case 2: // Help + { + from.Send(new DisplayHelpTopic(71, true)); // EMPTYING THE BOWL - break; - } - case 3: // Ok - { - PlantBowl bowl = new PlantBowl(); + from.SendGump(new EmptyTheBowlGump(m_Plant)); - if ( !from.PlaceInBackpack( bowl ) ) - { - bowl.Delete(); + break; + } + case 3: // Ok + { + PlantBowl bowl = new PlantBowl(); - m_Plant.LabelTo( from, 1053047 ); // You cannot empty a bowl with a full pack! - from.SendGump( new MainPlantGump( m_Plant ) ); + if (!from.PlaceInBackpack(bowl)) + { + bowl.Delete(); - break; - } + m_Plant.LabelTo(from, 1053047); // You cannot empty a bowl with a full pack! + from.SendGump(new MainPlantGump(m_Plant)); - if ( m_Plant.PlantStatus != PlantStatus.BowlOfDirt && m_Plant.PlantStatus < PlantStatus.Plant ) - { - Seed seed = new Seed( m_Plant.PlantType, m_Plant.PlantHue, m_Plant.ShowType ); + break; + } - if ( !from.PlaceInBackpack( seed ) ) - { - bowl.Delete(); - seed.Delete(); + if (m_Plant.PlantStatus != PlantStatus.BowlOfDirt && m_Plant.PlantStatus < PlantStatus.Plant) + { + Seed seed = new Seed(m_Plant.PlantType, m_Plant.PlantHue, m_Plant.ShowType); - m_Plant.LabelTo( from, 1053047 ); // You cannot empty a bowl with a full pack! - from.SendGump( new MainPlantGump( m_Plant ) ); + if (!from.PlaceInBackpack(seed)) + { + bowl.Delete(); + seed.Delete(); - break; - } - } + m_Plant.LabelTo(from, 1053047); // You cannot empty a bowl with a full pack! + from.SendGump(new MainPlantGump(m_Plant)); - m_Plant.Delete(); + break; + } + } - break; - } - } - } - } + m_Plant.Delete(); + + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Plants/MainPlantGump.cs b/Scripts/Engines/Plants/MainPlantGump.cs index a21091f3e..2beb81dea 100644 --- a/Scripts/Engines/Plants/MainPlantGump.cs +++ b/Scripts/Engines/Plants/MainPlantGump.cs @@ -1,417 +1,436 @@ using System; -using Server.Items; using Server.Gumps; +using Server.Items; using Server.Network; namespace Server.Engines.Plants { - public class MainPlantGump : Gump - { - private PlantItem m_Plant; - - public MainPlantGump( PlantItem plant ) : base( 20, 20 ) - { - m_Plant = plant; - - DrawBackground(); - - DrawPlant(); - - AddButton( 71, 67, 0xD4, 0xD4, 1, GumpButtonType.Reply, 0 ); // Reproduction menu - AddItem( 59, 68, 0xD08 ); - - PlantSystem system = plant.PlantSystem; - - AddButton( 71, 91, 0xD4, 0xD4, 2, GumpButtonType.Reply, 0 ); // Infestation - AddItem( 8, 96, 0x372 ); - AddPlus( 95, 92, system.Infestation ); - - AddButton( 71, 115, 0xD4, 0xD4, 3, GumpButtonType.Reply, 0 ); // Fungus - AddItem( 58, 115, 0xD16 ); - AddPlus( 95, 116, system.Fungus ); - - AddButton( 71, 139, 0xD4, 0xD4, 4, GumpButtonType.Reply, 0 ); // Poison - AddItem( 59, 143, 0x1AE4 ); - AddPlus( 95, 140, system.Poison ); - - AddButton( 71, 163, 0xD4, 0xD4, 5, GumpButtonType.Reply, 0 ); // Disease - AddItem( 55, 167, 0x1727 ); - AddPlus( 95, 164, system.Disease ); - - AddButton( 209, 67, 0xD2, 0xD2, 6, GumpButtonType.Reply, 0 ); // Water - AddItem( 193, 67, 0x1F9D ); - AddPlusMinus( 196, 67, system.Water ); - - AddButton( 209, 91, 0xD4, 0xD4, 7, GumpButtonType.Reply, 0 ); // Poison potion - AddItem( 201, 91, 0xF0A ); - AddLevel( 196, 91, system.PoisonPotion ); - - AddButton( 209, 115, 0xD4, 0xD4, 8, GumpButtonType.Reply, 0 ); // Cure potion - AddItem( 201, 115, 0xF07 ); - AddLevel( 196, 115, system.CurePotion ); - - AddButton( 209, 139, 0xD4, 0xD4, 9, GumpButtonType.Reply, 0 ); // Heal potion - AddItem( 201, 139, 0xF0C ); - AddLevel( 196, 139, system.HealPotion ); - - AddButton( 209, 163, 0xD4, 0xD4, 10, GumpButtonType.Reply, 0 ); // Strength potion - AddItem( 201, 163, 0xF09 ); - AddLevel( 196, 163, system.StrengthPotion ); - - AddImage( 48, 47, 0xD2 ); - AddLevel( 54, 47, (int)m_Plant.PlantStatus ); - - AddImage( 232, 47, 0xD2 ); - AddGrowthIndicator( 239, 47 ); - - AddButton( 48, 183, 0xD2, 0xD2, 11, GumpButtonType.Reply, 0 ); // Help - AddLabel( 54, 183, 0x835, "?" ); - - AddButton( 232, 183, 0xD4, 0xD4, 12, GumpButtonType.Reply, 0 ); // Empty the bowl - AddItem( 219, 180, 0x15FD ); - } - - private void DrawBackground() - { - AddBackground( 50, 50, 200, 150, 0xE10 ); - - AddItem( 45, 45, 0xCEF ); - AddItem( 45, 118, 0xCF0 ); - - AddItem( 211, 45, 0xCEB ); - AddItem( 211, 118, 0xCEC ); - } - - private void DrawPlant() - { - PlantStatus status = m_Plant.PlantStatus; - - if ( status < PlantStatus.FullGrownPlant ) - { - AddImage( 110, 85, 0x589 ); - - AddItem( 122, 94, 0x914 ); - AddItem( 135, 94, 0x914 ); - AddItem( 120, 112, 0x914 ); - AddItem( 135, 112, 0x914 ); - - if ( status >= PlantStatus.Stage2 ) - { - AddItem( 127, 112, 0xC62 ); - } - if ( status == PlantStatus.Stage3 || status == PlantStatus.Stage4 ) - { - AddItem( 129, 85, 0xC7E ); - } - if ( status >= PlantStatus.Stage4 ) - { - AddItem( 121, 117, 0xC62 ); - AddItem( 133, 117, 0xC62 ); - } - if ( status >= PlantStatus.Stage5 ) - { - AddItem( 110, 100, 0xC62 ); - AddItem( 140, 100, 0xC62 ); - AddItem( 110, 130, 0xC62 ); - AddItem( 140, 130, 0xC62 ); - } - if ( status >= PlantStatus.Stage6 ) - { - AddItem( 105, 115, 0xC62 ); - AddItem( 145, 115, 0xC62 ); - AddItem( 125, 90, 0xC62 ); - AddItem( 125, 135, 0xC62 ); - } - } - else - { - PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo( m_Plant.PlantType ); - PlantHueInfo hueInfo = PlantHueInfo.GetInfo( m_Plant.PlantHue ); - - // The large images for these trees trigger a client crash, so use a smaller, generic tree. - if ( m_Plant.PlantType == PlantType.CypressTwisted || m_Plant.PlantType == PlantType.CypressStraight ) - AddItem( 130 + typeInfo.OffsetX, 96 + typeInfo.OffsetY, 0x0CCA, hueInfo.Hue ); - else - AddItem( 130 + typeInfo.OffsetX, 96 + typeInfo.OffsetY, typeInfo.ItemID, hueInfo.Hue ); - } - - if ( status != PlantStatus.BowlOfDirt ) - { - int message = m_Plant.PlantSystem.GetLocalizedHealth(); - - switch ( m_Plant.PlantSystem.Health ) - { - case PlantHealth.Dying: - { - AddItem( 92, 167, 0x1B9D ); - AddItem( 161, 167, 0x1B9D ); - - AddHtmlLocalized( 136, 167, 42, 20, message, 0x00FC00, false, false ); - - break; - } - case PlantHealth.Wilted: - { - AddItem( 91, 164, 0x18E6 ); - AddItem( 161, 164, 0x18E6 ); - - AddHtmlLocalized( 132, 167, 42, 20, message, 0x00C207, false, false ); - - break; - } - case PlantHealth.Healthy: - { - AddItem( 96, 168, 0xC61 ); - AddItem( 162, 168, 0xC61 ); - - AddHtmlLocalized( 129, 167, 42, 20, message, 0x008200, false, false ); - - break; - } - case PlantHealth.Vibrant: - { - AddItem( 93, 162, 0x1A99 ); - AddItem( 162, 162, 0x1A99 ); - - AddHtmlLocalized( 129, 167, 42, 20, message, 0x0083E0, false, false ); - - break; - } - } - } - } - - private void AddPlus( int x, int y, int value ) - { - switch ( value ) - { - case 1: AddLabel( x, y, 0x35, "+" ); break; - case 2: AddLabel( x, y, 0x21, "+" ); break; - } - } - - private void AddPlusMinus( int x, int y, int value ) - { - switch ( value ) - { - case 0: AddLabel( x, y, 0x21, "-" ); break; - case 1: AddLabel( x, y, 0x35, "-" ); break; - case 3: AddLabel( x, y, 0x35, "+" ); break; - case 4: AddLabel( x, y, 0x21, "+" ); break; - } - } - - private void AddLevel( int x, int y, int value ) - { - AddLabel( x, y, 0x835, value.ToString() ); - } - - private void AddGrowthIndicator( int x, int y ) - { - if ( !m_Plant.IsGrowable ) - return; - - switch ( m_Plant.PlantSystem.GrowthIndicator ) - { - case PlantGrowthIndicator.InvalidLocation : AddLabel( x, y, 0x21, "!" ); break; - case PlantGrowthIndicator.NotHealthy : AddLabel( x, y, 0x21, "-" ); break; - case PlantGrowthIndicator.Delay : AddLabel( x, y, 0x35, "-" ); break; - case PlantGrowthIndicator.Grown : AddLabel( x, y, 0x3, "+" ); break; - case PlantGrowthIndicator.DoubleGrown : AddLabel( x, y, 0x3F, "+" ); break; - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; - - if ( info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus >= PlantStatus.DecorativePlant ) - return; - - if ( ( ( info.ButtonID >= 6 && info.ButtonID <= 10 ) || info.ButtonID == 12 ) && !from.InRange( m_Plant.GetWorldLocation(), 3 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 500446 ); // That is too far away. - return; - } - - if ( !m_Plant.IsUsableBy( from ) ) - { - m_Plant.LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - return; - } - - switch ( info.ButtonID ) - { - case 1: // Reproduction menu - { - if ( m_Plant.PlantStatus > PlantStatus.BowlOfDirt ) - { - from.SendGump( new ReproductionGump( m_Plant ) ); - } - else - { - from.SendLocalizedMessage( 1061885 ); // You need to plant a seed in the bowl first. - - from.SendGump( new MainPlantGump( m_Plant ) ); - } - - break; - } - case 2: // Infestation - { - from.Send( new DisplayHelpTopic( 54, true ) ); // INFESTATION LEVEL - - from.SendGump( new MainPlantGump( m_Plant ) ); - - break; - } - case 3: // Fungus - { - from.Send( new DisplayHelpTopic( 56, true ) ); // FUNGUS LEVEL - - from.SendGump( new MainPlantGump( m_Plant ) ); - - break; - } - case 4: // Poison - { - from.Send( new DisplayHelpTopic( 58, true ) ); // POISON LEVEL - - from.SendGump( new MainPlantGump( m_Plant ) ); - - break; - } - case 5: // Disease - { - from.Send( new DisplayHelpTopic( 60, true ) ); // DISEASE LEVEL - - from.SendGump( new MainPlantGump( m_Plant ) ); - - break; - } - case 6: // Water - { - Item[] item = from.Backpack.FindItemsByType( typeof( BaseBeverage ) ); - - bool foundUsableWater = false; - - if ( item != null && item.Length > 0 ) - { - for ( int i = 0; i < item.Length; ++i ) - { - BaseBeverage beverage = (BaseBeverage)item[i]; - - if ( !beverage.IsEmpty && beverage.Pourable && beverage.Content == BeverageType.Water ) - { - foundUsableWater = true; - m_Plant.Pour( from, beverage ); - break; - } - } - } - - if ( !foundUsableWater ) - { - from.Target = new PlantPourTarget( m_Plant ); - from.SendLocalizedMessage( 1060808, "#" + m_Plant.GetLocalizedPlantStatus().ToString() ); // Target the container you wish to use to water the ~1_val~. - } - - from.SendGump( new MainPlantGump( m_Plant ) ); - - break; - } - case 7: // Poison potion - { - AddPotion( from, PotionEffect.PoisonGreater, PotionEffect.PoisonDeadly ); - - break; - } - case 8: // Cure potion - { - AddPotion( from, PotionEffect.CureGreater ); - - break; - } - case 9: // Heal potion - { - AddPotion( from, PotionEffect.HealGreater ); - - break; - } - case 10: // Strength potion - { - AddPotion( from, PotionEffect.StrengthGreater ); - - break; - } - case 11: // Help - { - from.Send( new DisplayHelpTopic( 48, true ) ); // PLANT GROWING - - from.SendGump( new MainPlantGump( m_Plant ) ); - - break; - } - case 12: // Empty the bowl - { - from.SendGump( new EmptyTheBowlGump( m_Plant ) ); - - break; - } - } - } - - private void AddPotion( Mobile from, params PotionEffect[] effects ) - { - Item item = GetPotion( from, effects ); - - if ( item != null ) - { - m_Plant.Pour( from, item ); - } - else - { - int message; - if ( m_Plant.ApplyPotion( effects[0], true, out message ) ) - { - from.SendLocalizedMessage( 1061884 ); // You don't have any strong potions of that type in your pack. - - from.Target = new PlantPourTarget( m_Plant ); - from.SendLocalizedMessage( 1060808, "#" + m_Plant.GetLocalizedPlantStatus().ToString() ); // Target the container you wish to use to water the ~1_val~. - - return; - } - - m_Plant.LabelTo( from, message ); - } - - from.SendGump( new MainPlantGump( m_Plant ) ); - } - - public static Item GetPotion( Mobile from, PotionEffect[] effects ) - { - if ( from.Backpack == null ) - return null; - - Item[] items = from.Backpack.FindItemsByType( new[] { typeof( BasePotion ), typeof( PotionKeg ) } ); - - foreach ( Item item in items ) - { - if ( item is BasePotion potion ) - { - if ( Array.IndexOf( effects, potion.PotionEffect ) >= 0 ) - return potion; - } - else - { - PotionKeg keg = (PotionKeg)item; - - if ( keg.Held > 0 && Array.IndexOf( effects, keg.Type ) >= 0 ) - return keg; - } - } - - return null; - } - } -} + public class MainPlantGump : Gump + { + private PlantItem m_Plant; + + public MainPlantGump(PlantItem plant) : base(20, 20) + { + m_Plant = plant; + + DrawBackground(); + + DrawPlant(); + + AddButton(71, 67, 0xD4, 0xD4, 1, GumpButtonType.Reply, 0); // Reproduction menu + AddItem(59, 68, 0xD08); + + PlantSystem system = plant.PlantSystem; + + AddButton(71, 91, 0xD4, 0xD4, 2, GumpButtonType.Reply, 0); // Infestation + AddItem(8, 96, 0x372); + AddPlus(95, 92, system.Infestation); + + AddButton(71, 115, 0xD4, 0xD4, 3, GumpButtonType.Reply, 0); // Fungus + AddItem(58, 115, 0xD16); + AddPlus(95, 116, system.Fungus); + + AddButton(71, 139, 0xD4, 0xD4, 4, GumpButtonType.Reply, 0); // Poison + AddItem(59, 143, 0x1AE4); + AddPlus(95, 140, system.Poison); + + AddButton(71, 163, 0xD4, 0xD4, 5, GumpButtonType.Reply, 0); // Disease + AddItem(55, 167, 0x1727); + AddPlus(95, 164, system.Disease); + + AddButton(209, 67, 0xD2, 0xD2, 6, GumpButtonType.Reply, 0); // Water + AddItem(193, 67, 0x1F9D); + AddPlusMinus(196, 67, system.Water); + + AddButton(209, 91, 0xD4, 0xD4, 7, GumpButtonType.Reply, 0); // Poison potion + AddItem(201, 91, 0xF0A); + AddLevel(196, 91, system.PoisonPotion); + + AddButton(209, 115, 0xD4, 0xD4, 8, GumpButtonType.Reply, 0); // Cure potion + AddItem(201, 115, 0xF07); + AddLevel(196, 115, system.CurePotion); + + AddButton(209, 139, 0xD4, 0xD4, 9, GumpButtonType.Reply, 0); // Heal potion + AddItem(201, 139, 0xF0C); + AddLevel(196, 139, system.HealPotion); + + AddButton(209, 163, 0xD4, 0xD4, 10, GumpButtonType.Reply, 0); // Strength potion + AddItem(201, 163, 0xF09); + AddLevel(196, 163, system.StrengthPotion); + + AddImage(48, 47, 0xD2); + AddLevel(54, 47, (int)m_Plant.PlantStatus); + + AddImage(232, 47, 0xD2); + AddGrowthIndicator(239, 47); + + AddButton(48, 183, 0xD2, 0xD2, 11, GumpButtonType.Reply, 0); // Help + AddLabel(54, 183, 0x835, "?"); + + AddButton(232, 183, 0xD4, 0xD4, 12, GumpButtonType.Reply, 0); // Empty the bowl + AddItem(219, 180, 0x15FD); + } + + private void DrawBackground() + { + AddBackground(50, 50, 200, 150, 0xE10); + + AddItem(45, 45, 0xCEF); + AddItem(45, 118, 0xCF0); + + AddItem(211, 45, 0xCEB); + AddItem(211, 118, 0xCEC); + } + + private void DrawPlant() + { + PlantStatus status = m_Plant.PlantStatus; + + if (status < PlantStatus.FullGrownPlant) + { + AddImage(110, 85, 0x589); + + AddItem(122, 94, 0x914); + AddItem(135, 94, 0x914); + AddItem(120, 112, 0x914); + AddItem(135, 112, 0x914); + + if (status >= PlantStatus.Stage2) AddItem(127, 112, 0xC62); + if (status == PlantStatus.Stage3 || status == PlantStatus.Stage4) AddItem(129, 85, 0xC7E); + if (status >= PlantStatus.Stage4) + { + AddItem(121, 117, 0xC62); + AddItem(133, 117, 0xC62); + } + + if (status >= PlantStatus.Stage5) + { + AddItem(110, 100, 0xC62); + AddItem(140, 100, 0xC62); + AddItem(110, 130, 0xC62); + AddItem(140, 130, 0xC62); + } + + if (status >= PlantStatus.Stage6) + { + AddItem(105, 115, 0xC62); + AddItem(145, 115, 0xC62); + AddItem(125, 90, 0xC62); + AddItem(125, 135, 0xC62); + } + } + else + { + PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo(m_Plant.PlantType); + PlantHueInfo hueInfo = PlantHueInfo.GetInfo(m_Plant.PlantHue); + + // The large images for these trees trigger a client crash, so use a smaller, generic tree. + if (m_Plant.PlantType == PlantType.CypressTwisted || m_Plant.PlantType == PlantType.CypressStraight) + AddItem(130 + typeInfo.OffsetX, 96 + typeInfo.OffsetY, 0x0CCA, hueInfo.Hue); + else + AddItem(130 + typeInfo.OffsetX, 96 + typeInfo.OffsetY, typeInfo.ItemID, hueInfo.Hue); + } + + if (status != PlantStatus.BowlOfDirt) + { + int message = m_Plant.PlantSystem.GetLocalizedHealth(); + + switch (m_Plant.PlantSystem.Health) + { + case PlantHealth.Dying: + { + AddItem(92, 167, 0x1B9D); + AddItem(161, 167, 0x1B9D); + + AddHtmlLocalized(136, 167, 42, 20, message, 0x00FC00, false, false); + + break; + } + case PlantHealth.Wilted: + { + AddItem(91, 164, 0x18E6); + AddItem(161, 164, 0x18E6); + + AddHtmlLocalized(132, 167, 42, 20, message, 0x00C207, false, false); + + break; + } + case PlantHealth.Healthy: + { + AddItem(96, 168, 0xC61); + AddItem(162, 168, 0xC61); + + AddHtmlLocalized(129, 167, 42, 20, message, 0x008200, false, false); + + break; + } + case PlantHealth.Vibrant: + { + AddItem(93, 162, 0x1A99); + AddItem(162, 162, 0x1A99); + + AddHtmlLocalized(129, 167, 42, 20, message, 0x0083E0, false, false); + + break; + } + } + } + } + + private void AddPlus(int x, int y, int value) + { + switch (value) + { + case 1: + AddLabel(x, y, 0x35, "+"); + break; + case 2: + AddLabel(x, y, 0x21, "+"); + break; + } + } + + private void AddPlusMinus(int x, int y, int value) + { + switch (value) + { + case 0: + AddLabel(x, y, 0x21, "-"); + break; + case 1: + AddLabel(x, y, 0x35, "-"); + break; + case 3: + AddLabel(x, y, 0x35, "+"); + break; + case 4: + AddLabel(x, y, 0x21, "+"); + break; + } + } + + private void AddLevel(int x, int y, int value) + { + AddLabel(x, y, 0x835, value.ToString()); + } + + private void AddGrowthIndicator(int x, int y) + { + if (!m_Plant.IsGrowable) + return; + + switch (m_Plant.PlantSystem.GrowthIndicator) + { + case PlantGrowthIndicator.InvalidLocation: + AddLabel(x, y, 0x21, "!"); + break; + case PlantGrowthIndicator.NotHealthy: + AddLabel(x, y, 0x21, "-"); + break; + case PlantGrowthIndicator.Delay: + AddLabel(x, y, 0x35, "-"); + break; + case PlantGrowthIndicator.Grown: + AddLabel(x, y, 0x3, "+"); + break; + case PlantGrowthIndicator.DoubleGrown: + AddLabel(x, y, 0x3F, "+"); + break; + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; + + if (info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus >= PlantStatus.DecorativePlant) + return; + + if ((info.ButtonID >= 6 && info.ButtonID <= 10 || info.ButtonID == 12) && + !from.InRange(m_Plant.GetWorldLocation(), 3)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 500446); // That is too far away. + return; + } + + if (!m_Plant.IsUsableBy(from)) + { + m_Plant.LabelTo(from, 1061856); // You must have the item in your backpack or locked down in order to use it. + return; + } + + switch (info.ButtonID) + { + case 1: // Reproduction menu + { + if (m_Plant.PlantStatus > PlantStatus.BowlOfDirt) + { + from.SendGump(new ReproductionGump(m_Plant)); + } + else + { + from.SendLocalizedMessage(1061885); // You need to plant a seed in the bowl first. + + from.SendGump(new MainPlantGump(m_Plant)); + } + + break; + } + case 2: // Infestation + { + from.Send(new DisplayHelpTopic(54, true)); // INFESTATION LEVEL + + from.SendGump(new MainPlantGump(m_Plant)); + + break; + } + case 3: // Fungus + { + from.Send(new DisplayHelpTopic(56, true)); // FUNGUS LEVEL + + from.SendGump(new MainPlantGump(m_Plant)); + + break; + } + case 4: // Poison + { + from.Send(new DisplayHelpTopic(58, true)); // POISON LEVEL + + from.SendGump(new MainPlantGump(m_Plant)); + + break; + } + case 5: // Disease + { + from.Send(new DisplayHelpTopic(60, true)); // DISEASE LEVEL + + from.SendGump(new MainPlantGump(m_Plant)); + + break; + } + case 6: // Water + { + Item[] item = from.Backpack.FindItemsByType(typeof(BaseBeverage)); + + bool foundUsableWater = false; + + if (item != null && item.Length > 0) + for (int i = 0; i < item.Length; ++i) + { + BaseBeverage beverage = (BaseBeverage)item[i]; + + if (!beverage.IsEmpty && beverage.Pourable && beverage.Content == BeverageType.Water) + { + foundUsableWater = true; + m_Plant.Pour(from, beverage); + break; + } + } + + if (!foundUsableWater) + { + from.Target = new PlantPourTarget(m_Plant); + from.SendLocalizedMessage(1060808, + "#" + m_Plant + .GetLocalizedPlantStatus()); // Target the container you wish to use to water the ~1_val~. + } + + from.SendGump(new MainPlantGump(m_Plant)); + + break; + } + case 7: // Poison potion + { + AddPotion(from, PotionEffect.PoisonGreater, PotionEffect.PoisonDeadly); + + break; + } + case 8: // Cure potion + { + AddPotion(from, PotionEffect.CureGreater); + + break; + } + case 9: // Heal potion + { + AddPotion(from, PotionEffect.HealGreater); + + break; + } + case 10: // Strength potion + { + AddPotion(from, PotionEffect.StrengthGreater); + + break; + } + case 11: // Help + { + from.Send(new DisplayHelpTopic(48, true)); // PLANT GROWING + + from.SendGump(new MainPlantGump(m_Plant)); + + break; + } + case 12: // Empty the bowl + { + from.SendGump(new EmptyTheBowlGump(m_Plant)); + + break; + } + } + } + + private void AddPotion(Mobile from, params PotionEffect[] effects) + { + Item item = GetPotion(from, effects); + + if (item != null) + { + m_Plant.Pour(from, item); + } + else + { + int message; + if (m_Plant.ApplyPotion(effects[0], true, out message)) + { + from.SendLocalizedMessage(1061884); // You don't have any strong potions of that type in your pack. + + from.Target = new PlantPourTarget(m_Plant); + from.SendLocalizedMessage(1060808, + "#" + m_Plant + .GetLocalizedPlantStatus()); // Target the container you wish to use to water the ~1_val~. + + return; + } + + m_Plant.LabelTo(from, message); + } + + from.SendGump(new MainPlantGump(m_Plant)); + } + + public static Item GetPotion(Mobile from, PotionEffect[] effects) + { + if (from.Backpack == null) + return null; + + Item[] items = from.Backpack.FindItemsByType(new[] { typeof(BasePotion), typeof(PotionKeg) }); + + foreach (Item item in items) + if (item is BasePotion potion) + { + if (Array.IndexOf(effects, potion.PotionEffect) >= 0) + return potion; + } + else + { + PotionKeg keg = (PotionKeg)item; + + if (keg.Held > 0 && Array.IndexOf(effects, keg.Type) >= 0) + return keg; + } + + return null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/MiscItems/FertileDirt.cs b/Scripts/Engines/Plants/MiscItems/FertileDirt.cs index 02146151b..e98e30b34 100644 --- a/Scripts/Engines/Plants/MiscItems/FertileDirt.cs +++ b/Scripts/Engines/Plants/MiscItems/FertileDirt.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class FertileDirt : Item - { - [Constructible] - public FertileDirt() : this( 1 ) - { - } + public class FertileDirt : Item + { + [Constructible] + public FertileDirt() : this(1) + { + } - [Constructible] - public FertileDirt( int amount ) : base( 0xF81 ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } + [Constructible] + public FertileDirt(int amount) : base(0xF81) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } - public FertileDirt( Serial serial ) : base( serial ) - { - } + public FertileDirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Plants/MiscItems/GreenThorns.cs b/Scripts/Engines/Plants/MiscItems/GreenThorns.cs index 30897ce47..df0633400 100644 --- a/Scripts/Engines/Plants/MiscItems/GreenThorns.cs +++ b/Scripts/Engines/Plants/MiscItems/GreenThorns.cs @@ -1,718 +1,755 @@ using System; using Server.Mobiles; -using Server.Targeting; using Server.Network; +using Server.Targeting; namespace Server.Items { - public class GreenThorns : Item - { - public override int LabelNumber => 1060837; // green thorns - - [Constructible] - public GreenThorns() : this( 1 ) - { - } - - [Constructible] - public GreenThorns( int amount ) : base( 0xF42 ) - { - Stackable = true; - Weight = 1.0; - Hue = 0x42; - Amount = amount; - } - - public GreenThorns( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } - - if ( !from.CanBeginAction( typeof( GreenThorns ) ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061908 ); // * You must wait a while before planting another thorn. * - return; - } - - from.Target = new InternalTarget( this ); - from.SendLocalizedMessage( 1061906 ); // Choose a spot to plant the thorn. - } - - private class InternalTarget : Target - { - private GreenThorns m_Thorn; - - public InternalTarget( GreenThorns thorn ) : base( 3, true, TargetFlags.None ) - { - m_Thorn = thorn; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Thorn.Deleted ) - return; - - if ( !m_Thorn.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } - - if ( !from.CanBeginAction( typeof( GreenThorns ) ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061908 ); // * You must wait a while before planting another thorn. * - return; - } - - if ( from.Map != Map.Trammel && from.Map != Map.Felucca ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x2B2, true, "No solen lairs exist on this facet. Try again in Trammel or Felucca." ); - return; - } - - if ( !(targeted is LandTarget land) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061912 ); // * You cannot plant a green thorn there! * - } - else - { - GreenThornsEffect effect = GreenThornsEffect.Create( from, land ); - - if ( effect == null ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061913 ); // * You sense it would be useless to plant a green thorn there. * - } - else - { - m_Thorn.Consume(); - - from.LocalOverheadMessage( MessageType.Emote, 0x961, 1061914 ); // * You push the strange green thorn into the ground * - from.NonlocalOverheadMessage( MessageType.Emote, 0x961, 1061915, from.Name ); // * ~1_PLAYER_NAME~ pushes a strange green thorn into the ground. * - - from.BeginAction( typeof( GreenThorns ) ); - new EndActionTimer( from ).Start(); - - effect.Start(); - } - } - } - - protected override void OnTargetOutOfRange( Mobile from, object targeted ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502825 ); // That location is too far away - } - } - - private class EndActionTimer : Timer - { - private Mobile m_From; - - public EndActionTimer( Mobile from ) : base( TimeSpan.FromMinutes( 3.0 ) ) - { - m_From = from; - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - m_From.EndAction( typeof( GreenThorns ) ); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public abstract class GreenThornsEffect : Timer - { - private class TilesAndEffect - { - public int[] Tiles { get; } - - public Type Effect { get; } - - public TilesAndEffect( int[] tiles, Type effect ) - { - Tiles = tiles; - Effect = effect; - } - } - - private static TilesAndEffect[] m_Table = { - new TilesAndEffect( new[] - { - 0x71, 0x7C, - 0x82, 0xA7, - 0xDC, 0xE3, - 0xE8, 0xEB, - 0x141, 0x144, - 0x14C, 0x14F, - 0x169, 0x174, - 0x1DC, 0x1E7, - 0x1EC, 0x1EF, - 0x272, 0x275, - 0x27E, 0x281, - 0x2D0, 0x2D7, - 0x2E5, 0x2FF, - 0x303, 0x31F, - 0x32C, 0x32F, - 0x33D, 0x340, - 0x345, 0x34C, - 0x355, 0x358, - 0x367, 0x36E, - 0x377, 0x37A, - 0x38D, 0x390, - 0x395, 0x39C, - 0x3A5, 0x3A8, - 0x3F6, 0x405, - 0x547, 0x54E, - 0x553, 0x556, - 0x597, 0x59E, - 0x623, 0x63A, - 0x6F3, 0x6FA, - 0x777, 0x791, - 0x79A, 0x7A9, - 0x7AE, 0x7B1, - }, - typeof( DirtGreenThornsEffect ) ), - - new TilesAndEffect( new[] - { - 0x9, 0x15, - 0x150, 0x15C - }, - typeof( FurrowsGreenThornsEffect ) ), - - new TilesAndEffect( new[] - { - 0x9C4, 0x9EB, - 0x3D65, 0x3D65, - 0x3DC0, 0x3DD9, - 0x3DDB, 0x3DDC, - 0x3DDE, 0x3EF0, - 0x3FF6, 0x3FF6, - 0x3FFC, 0x3FFE, - }, - typeof( SwampGreenThornsEffect ) ), - - new TilesAndEffect( new[] - { - 0x10C, 0x10F, - 0x114, 0x117, - 0x119, 0x11D, - 0x179, 0x18A, - 0x385, 0x38C, - 0x391, 0x394, - 0x39D, 0x3A4, - 0x3A9, 0x3AC, - 0x5BF, 0x5D6, - 0x5DF, 0x5E2, - 0x745, 0x748, - 0x751, 0x758, - 0x75D, 0x760, - 0x76D, 0x773 - }, - typeof( SnowGreenThornsEffect ) ), - - new TilesAndEffect( new[] - { - 0x16, 0x3A, - 0x44, 0x4B, - 0x11E, 0x121, - 0x126, 0x12D, - 0x192, 0x192, - 0x1A8, 0x1AB, - 0x1B9, 0x1D1, - 0x282, 0x285, - 0x28A, 0x291, - 0x335, 0x33C, - 0x341, 0x344, - 0x34D, 0x354, - 0x359, 0x35C, - 0x3B7, 0x3BE, - 0x3C7, 0x3CA, - 0x5A7, 0x5B2, - 0x64B, 0x652, - 0x657, 0x65A, - 0x663, 0x66A, - 0x66F, 0x672, - 0x7BD, 0x7D0 - }, - typeof( SandGreenThornsEffect ) ) - }; - - public static GreenThornsEffect Create( Mobile from, LandTarget land ) - { - if ( !from.Map.CanSpawnMobile( land.Location ) ) - return null; - - int tileID = land.TileID; - - foreach ( TilesAndEffect taep in m_Table ) - { - bool contains = false; - - for ( int i = 0; !contains && i < taep.Tiles.Length; i += 2 ) - contains = ( tileID >= taep.Tiles[i] && tileID <= taep.Tiles[i + 1] ); - - if ( contains ) - { - GreenThornsEffect effect = (GreenThornsEffect)Activator.CreateInstance( taep.Effect, new object[] { land.Location, from.Map, from } ); - return effect; - } - } - - return null; - } - - public Point3D Location { get; } - - public Map Map { get; } - - public Mobile From { get; } - - public GreenThornsEffect( Point3D location, Map map, Mobile from ) : base( TimeSpan.FromSeconds( 2.5 ) ) - { - Location = location; - Map = map; - From = from; - - Priority = TimerPriority.TwoFiftyMS; - } - - private int m_Step; - - protected override void OnTick() - { - TimeSpan nextDelay = Play( m_Step++ ); - - if ( nextDelay > TimeSpan.Zero ) - { - Delay = nextDelay; - - Start(); - } - } - - protected abstract TimeSpan Play( int step ); - - protected bool SpawnItem( Item item ) - { - for ( int i = 0; i < 5; i++ ) // Try 5 times - { - int x = Location.X + Utility.RandomMinMax( -1, 1 ); - int y = Location.Y + Utility.RandomMinMax( -1, 1 ); - int z = Map.GetAverageZ( x, y ); - - if ( Map.CanFit( x, y, Location.Z, 1 ) ) - { - item.MoveToWorld( new Point3D( x, y, Location.Z ), Map ); - return true; - } - - if ( Map.CanFit( x, y, z, 1 ) ) - { - item.MoveToWorld( new Point3D( x, y, z ), Map ); - return true; - } - } - - return false; - } - - protected bool SpawnCreature( BaseCreature creature ) - { - for ( int i = 0; i < 5; i++ ) // Try 5 times - { - int x = Location.X + Utility.RandomMinMax( -1, 1 ); - int y = Location.Y + Utility.RandomMinMax( -1, 1 ); - int z = Map.GetAverageZ( x, y ); - - if ( Map.CanSpawnMobile( x, y, Location.Z ) ) - { - creature.MoveToWorld( new Point3D( x, y, Location.Z ), Map ); - creature.Combatant = From; - return true; - } - - if ( Map.CanSpawnMobile( x, y, z ) ) - { - creature.MoveToWorld( new Point3D( x, y, z ), Map ); - creature.Combatant = From; - return true; - } - } - - return false; - } - } - - public class DirtGreenThornsEffect : GreenThornsEffect - { - public DirtGreenThornsEffect( Point3D location, Map map, Mobile from ) : base( location, map, from ) - { - } - - protected override TimeSpan Play( int step ) - { - switch ( step ) - { - case 0: - { - Effects.PlaySound( Location, Map, 0x106 ); - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3735, 1, 182, 0xBE3 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 1: - { - Effects.PlaySound( Location, Map, 0x222 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 2: - { - Effects.PlaySound( Location, Map, 0x21F ); - - return TimeSpan.FromSeconds( 5.0 ); - } - case 3: - { - EffectItem dummy = EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 20.0 ) ); - dummy.PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* The ground erupts with chaotic growth! *" ); - - Effects.PlaySound( Location, Map, 0x12D ); - - SpawnReagents(); - SpawnReagents(); - - return TimeSpan.FromSeconds( 2.0 ); - } - case 4: - { - Effects.PlaySound( Location, Map, 0x12D ); - - SpawnReagents(); - SpawnReagents(); - - return TimeSpan.FromSeconds( 2.0 ); - } - case 5: - { - Effects.PlaySound( Location, Map, 0x12D ); - - SpawnReagents(); - SpawnReagents(); - - return TimeSpan.FromSeconds( 3.0 ); - } - default: - { - Effects.PlaySound( Location, Map, 0x12D ); - - SpawnReagents(); - SpawnReagents(); - - return TimeSpan.Zero; - } - } - } - - private void SpawnReagents() - { - Item reagents; - int amount = Utility.RandomMinMax( 10, 25 ); - - switch ( Utility.Random( 9 ) ) - { - case 0: reagents = new BlackPearl( amount ); break; - case 1: reagents = new Bloodmoss( amount ); break; - case 2: reagents = new Garlic( amount ); break; - case 3: reagents = new Ginseng( amount ); break; - case 4: reagents = new MandrakeRoot( amount ); break; - case 5: reagents = new Nightshade( amount ); break; - case 6: reagents = new SulfurousAsh( amount ); break; - case 7: reagents = new SpidersSilk( amount ); break; - default: reagents = new FertileDirt( amount ); break; - } - - if ( !SpawnItem( reagents ) ) - reagents.Delete(); - } - } - - public class FurrowsGreenThornsEffect : GreenThornsEffect - { - public FurrowsGreenThornsEffect( Point3D location, Map map, Mobile from ) : base( location, map, from ) - { - } - - protected override TimeSpan Play( int step ) - { - switch ( step ) - { - case 0: - { - Effects.PlaySound( Location, Map, 0x106 ); - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3735, 1, 182, 0xBE3 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 1: - { - EffectItem hole = EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 10.0 ) ); - hole.ItemID = 0x913; - - Effects.PlaySound( Location, Map, 0x222 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 2: - { - Effects.PlaySound( Location, Map, 0x21F ); - - return TimeSpan.FromSeconds( 4.0 ); - } - default: - { - EffectItem dummy = EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 20.0 ) ); - dummy.PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* A magical bunny leaps out of its hole, disturbed by the thorn's effect! *" ); - - BaseCreature spawn = new VorpalBunny(); - if ( !SpawnCreature( spawn ) ) - spawn.Delete(); - - return TimeSpan.Zero; - } - } - } - } - - public class SwampGreenThornsEffect : GreenThornsEffect - { - public SwampGreenThornsEffect( Point3D location, Map map, Mobile from ) : base( location, map, from ) - { - } - - protected override TimeSpan Play( int step ) - { - switch ( step ) - { - case 0: - { - Effects.PlaySound( Location, Map, 0x106 ); - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3735, 1, 182, 0xBE3 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 1: - { - Effects.PlaySound( Location, Map, 0x222 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 2: - { - Effects.PlaySound( Location, Map, 0x21F ); - - return TimeSpan.FromSeconds( 1.0 ); - } - default: - { - EffectItem dummy = EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 20.0 ) ); - dummy.PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* Strange green tendrils rise from the ground, whipping wildly! *" ); - Effects.PlaySound( Location, Map, 0x2B0 ); - - BaseCreature spawn = new WhippingVine(); - if ( !SpawnCreature( spawn ) ) - spawn.Delete(); - - return TimeSpan.Zero; - } - } - } - } - - public class SnowGreenThornsEffect : GreenThornsEffect - { - public SnowGreenThornsEffect( Point3D location, Map map, Mobile from ) : base( location, map, from ) - { - } - - protected override TimeSpan Play( int step ) - { - switch ( step ) - { - case 0: - { - Effects.PlaySound( Location, Map, 0x106 ); - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3735, 1, 182, 0xBE3 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 1: - { - Effects.PlaySound( Location, Map, 0x222 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 2: - { - Effects.PlaySound( Location, Map, 0x21F ); - - return TimeSpan.FromSeconds( 4.0 ); - } - default: - { - EffectItem dummy = EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 20.0 ) ); - dummy.PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* Slithering ice serpents rise to the surface to investigate the disturbance! *" ); - - BaseCreature spawn = new GiantIceWorm(); - if ( !SpawnCreature( spawn ) ) - spawn.Delete(); - - for ( int i = 0; i < 3; i++ ) - { - BaseCreature snake = new IceSnake(); - if ( !SpawnCreature( snake ) ) - snake.Delete(); - } - - return TimeSpan.Zero; - } - } - } - } - - public class SandGreenThornsEffect : GreenThornsEffect - { - public SandGreenThornsEffect( Point3D location, Map map, Mobile from ) : base( location, map, from ) - { - } - - protected override TimeSpan Play( int step ) - { - switch ( step ) - { - case 0: - { - Effects.PlaySound( Location, Map, 0x106 ); - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3735, 1, 182, 0xBE3 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 1: - { - Effects.PlaySound( Location, Map, 0x222 ); - - return TimeSpan.FromSeconds( 4.0 ); - } - case 2: - { - Effects.PlaySound( Location, Map, 0x21F ); - - return TimeSpan.FromSeconds( 5.0 ); - } - default: - { - EffectItem dummy = EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 20.0 ) ); - dummy.PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* The sand collapses, revealing a dark hole. *" ); - - GreenThornsSHTeleporter.Create( Location, Map ); - - return TimeSpan.Zero; - } - } - } - } - - public class GreenThornsSHTeleporter : Item - { - public static readonly Point3D Destination = new Point3D( 5738, 1856, 0 ); - - public static void Create( Point3D location, Map map ) - { - GreenThornsSHTeleporter tele = new GreenThornsSHTeleporter(); - - tele.MoveToWorld( location, map ); - - new InternalTimer( tele ).Start(); - } - - public override string DefaultName => "a hole"; - - private GreenThornsSHTeleporter() : base( 0x913 ) - { - Movable = false; - Hue = 0x1; - } - - public GreenThornsSHTeleporter( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( this, 3 ) ) - { - BaseCreature.TeleportPets( from, Destination, Map ); - - from.Location = Destination; - } - else - { - from.SendLocalizedMessage( 1019045 ); // I can't reach that. - } - } - - private class InternalTimer : Timer - { - private GreenThornsSHTeleporter m_Teleporter; - - public InternalTimer( GreenThornsSHTeleporter teleporter ) : base( TimeSpan.FromMinutes( 1.0 ) ) - { - m_Teleporter = teleporter; - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - m_Teleporter.Delete(); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Delete(); - } - } -} + public class GreenThorns : Item + { + [Constructible] + public GreenThorns() : this(1) + { + } + + [Constructible] + public GreenThorns(int amount) : base(0xF42) + { + Stackable = true; + Weight = 1.0; + Hue = 0x42; + Amount = amount; + } + + public GreenThorns(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1060837; // green thorns + + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } + + if (!from.CanBeginAction(typeof(GreenThorns))) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061908); // * You must wait a while before planting another thorn. * + return; + } + + from.Target = new InternalTarget(this); + from.SendLocalizedMessage(1061906); // Choose a spot to plant the thorn. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + private class InternalTarget : Target + { + private GreenThorns m_Thorn; + + public InternalTarget(GreenThorns thorn) : base(3, true, TargetFlags.None) + { + m_Thorn = thorn; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Thorn.Deleted) + return; + + if (!m_Thorn.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } + + if (!from.CanBeginAction(typeof(GreenThorns))) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061908); // * You must wait a while before planting another thorn. * + return; + } + + if (from.Map != Map.Trammel && from.Map != Map.Felucca) + { + from.LocalOverheadMessage(MessageType.Regular, 0x2B2, true, + "No solen lairs exist on this facet. Try again in Trammel or Felucca."); + return; + } + + if (!(targeted is LandTarget land)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061912); // * You cannot plant a green thorn there! * + } + else + { + GreenThornsEffect effect = GreenThornsEffect.Create(from, land); + + if (effect == null) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061913); // * You sense it would be useless to plant a green thorn there. * + } + else + { + m_Thorn.Consume(); + + from.LocalOverheadMessage(MessageType.Emote, 0x961, + 1061914); // * You push the strange green thorn into the ground * + from.NonlocalOverheadMessage(MessageType.Emote, 0x961, 1061915, + from.Name); // * ~1_PLAYER_NAME~ pushes a strange green thorn into the ground. * + + from.BeginAction(typeof(GreenThorns)); + new EndActionTimer(from).Start(); + + effect.Start(); + } + } + } + + protected override void OnTargetOutOfRange(Mobile from, object targeted) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502825); // That location is too far away + } + } + + private class EndActionTimer : Timer + { + private Mobile m_From; + + public EndActionTimer(Mobile from) : base(TimeSpan.FromMinutes(3.0)) + { + m_From = from; + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + m_From.EndAction(typeof(GreenThorns)); + } + } + } + + public abstract class GreenThornsEffect : Timer + { + private static TilesAndEffect[] m_Table = + { + new TilesAndEffect(new[] + { + 0x71, 0x7C, + 0x82, 0xA7, + 0xDC, 0xE3, + 0xE8, 0xEB, + 0x141, 0x144, + 0x14C, 0x14F, + 0x169, 0x174, + 0x1DC, 0x1E7, + 0x1EC, 0x1EF, + 0x272, 0x275, + 0x27E, 0x281, + 0x2D0, 0x2D7, + 0x2E5, 0x2FF, + 0x303, 0x31F, + 0x32C, 0x32F, + 0x33D, 0x340, + 0x345, 0x34C, + 0x355, 0x358, + 0x367, 0x36E, + 0x377, 0x37A, + 0x38D, 0x390, + 0x395, 0x39C, + 0x3A5, 0x3A8, + 0x3F6, 0x405, + 0x547, 0x54E, + 0x553, 0x556, + 0x597, 0x59E, + 0x623, 0x63A, + 0x6F3, 0x6FA, + 0x777, 0x791, + 0x79A, 0x7A9, + 0x7AE, 0x7B1 + }, + typeof(DirtGreenThornsEffect)), + + new TilesAndEffect(new[] + { + 0x9, 0x15, + 0x150, 0x15C + }, + typeof(FurrowsGreenThornsEffect)), + + new TilesAndEffect(new[] + { + 0x9C4, 0x9EB, + 0x3D65, 0x3D65, + 0x3DC0, 0x3DD9, + 0x3DDB, 0x3DDC, + 0x3DDE, 0x3EF0, + 0x3FF6, 0x3FF6, + 0x3FFC, 0x3FFE + }, + typeof(SwampGreenThornsEffect)), + + new TilesAndEffect(new[] + { + 0x10C, 0x10F, + 0x114, 0x117, + 0x119, 0x11D, + 0x179, 0x18A, + 0x385, 0x38C, + 0x391, 0x394, + 0x39D, 0x3A4, + 0x3A9, 0x3AC, + 0x5BF, 0x5D6, + 0x5DF, 0x5E2, + 0x745, 0x748, + 0x751, 0x758, + 0x75D, 0x760, + 0x76D, 0x773 + }, + typeof(SnowGreenThornsEffect)), + + new TilesAndEffect(new[] + { + 0x16, 0x3A, + 0x44, 0x4B, + 0x11E, 0x121, + 0x126, 0x12D, + 0x192, 0x192, + 0x1A8, 0x1AB, + 0x1B9, 0x1D1, + 0x282, 0x285, + 0x28A, 0x291, + 0x335, 0x33C, + 0x341, 0x344, + 0x34D, 0x354, + 0x359, 0x35C, + 0x3B7, 0x3BE, + 0x3C7, 0x3CA, + 0x5A7, 0x5B2, + 0x64B, 0x652, + 0x657, 0x65A, + 0x663, 0x66A, + 0x66F, 0x672, + 0x7BD, 0x7D0 + }, + typeof(SandGreenThornsEffect)) + }; + + private int m_Step; + + public GreenThornsEffect(Point3D location, Map map, Mobile from) : base(TimeSpan.FromSeconds(2.5)) + { + Location = location; + Map = map; + From = from; + + Priority = TimerPriority.TwoFiftyMS; + } + + public Point3D Location{ get; } + + public Map Map{ get; } + + public Mobile From{ get; } + + public static GreenThornsEffect Create(Mobile from, LandTarget land) + { + if (!from.Map.CanSpawnMobile(land.Location)) + return null; + + int tileID = land.TileID; + + foreach (TilesAndEffect taep in m_Table) + { + bool contains = false; + + for (int i = 0; !contains && i < taep.Tiles.Length; i += 2) + contains = tileID >= taep.Tiles[i] && tileID <= taep.Tiles[i + 1]; + + if (contains) + { + GreenThornsEffect effect = + (GreenThornsEffect)Activator.CreateInstance(taep.Effect, land.Location, from.Map, from); + return effect; + } + } + + return null; + } + + protected override void OnTick() + { + TimeSpan nextDelay = Play(m_Step++); + + if (nextDelay > TimeSpan.Zero) + { + Delay = nextDelay; + + Start(); + } + } + + protected abstract TimeSpan Play(int step); + + protected bool SpawnItem(Item item) + { + for (int i = 0; i < 5; i++) // Try 5 times + { + int x = Location.X + Utility.RandomMinMax(-1, 1); + int y = Location.Y + Utility.RandomMinMax(-1, 1); + int z = Map.GetAverageZ(x, y); + + if (Map.CanFit(x, y, Location.Z, 1)) + { + item.MoveToWorld(new Point3D(x, y, Location.Z), Map); + return true; + } + + if (Map.CanFit(x, y, z, 1)) + { + item.MoveToWorld(new Point3D(x, y, z), Map); + return true; + } + } + + return false; + } + + protected bool SpawnCreature(BaseCreature creature) + { + for (int i = 0; i < 5; i++) // Try 5 times + { + int x = Location.X + Utility.RandomMinMax(-1, 1); + int y = Location.Y + Utility.RandomMinMax(-1, 1); + int z = Map.GetAverageZ(x, y); + + if (Map.CanSpawnMobile(x, y, Location.Z)) + { + creature.MoveToWorld(new Point3D(x, y, Location.Z), Map); + creature.Combatant = From; + return true; + } + + if (Map.CanSpawnMobile(x, y, z)) + { + creature.MoveToWorld(new Point3D(x, y, z), Map); + creature.Combatant = From; + return true; + } + } + + return false; + } + + private class TilesAndEffect + { + public TilesAndEffect(int[] tiles, Type effect) + { + Tiles = tiles; + Effect = effect; + } + + public int[] Tiles{ get; } + + public Type Effect{ get; } + } + } + + public class DirtGreenThornsEffect : GreenThornsEffect + { + public DirtGreenThornsEffect(Point3D location, Map map, Mobile from) : base(location, map, from) + { + } + + protected override TimeSpan Play(int step) + { + switch (step) + { + case 0: + { + Effects.PlaySound(Location, Map, 0x106); + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3735, 1, + 182, 0xBE3); + + return TimeSpan.FromSeconds(4.0); + } + case 1: + { + Effects.PlaySound(Location, Map, 0x222); + + return TimeSpan.FromSeconds(4.0); + } + case 2: + { + Effects.PlaySound(Location, Map, 0x21F); + + return TimeSpan.FromSeconds(5.0); + } + case 3: + { + EffectItem dummy = EffectItem.Create(Location, Map, TimeSpan.FromSeconds(20.0)); + dummy.PublicOverheadMessage(MessageType.Regular, 0x3B2, true, + "* The ground erupts with chaotic growth! *"); + + Effects.PlaySound(Location, Map, 0x12D); + + SpawnReagents(); + SpawnReagents(); + + return TimeSpan.FromSeconds(2.0); + } + case 4: + { + Effects.PlaySound(Location, Map, 0x12D); + + SpawnReagents(); + SpawnReagents(); + + return TimeSpan.FromSeconds(2.0); + } + case 5: + { + Effects.PlaySound(Location, Map, 0x12D); + + SpawnReagents(); + SpawnReagents(); + + return TimeSpan.FromSeconds(3.0); + } + default: + { + Effects.PlaySound(Location, Map, 0x12D); + + SpawnReagents(); + SpawnReagents(); + + return TimeSpan.Zero; + } + } + } + + private void SpawnReagents() + { + Item reagents; + int amount = Utility.RandomMinMax(10, 25); + + switch (Utility.Random(9)) + { + case 0: + reagents = new BlackPearl(amount); + break; + case 1: + reagents = new Bloodmoss(amount); + break; + case 2: + reagents = new Garlic(amount); + break; + case 3: + reagents = new Ginseng(amount); + break; + case 4: + reagents = new MandrakeRoot(amount); + break; + case 5: + reagents = new Nightshade(amount); + break; + case 6: + reagents = new SulfurousAsh(amount); + break; + case 7: + reagents = new SpidersSilk(amount); + break; + default: + reagents = new FertileDirt(amount); + break; + } + + if (!SpawnItem(reagents)) + reagents.Delete(); + } + } + + public class FurrowsGreenThornsEffect : GreenThornsEffect + { + public FurrowsGreenThornsEffect(Point3D location, Map map, Mobile from) : base(location, map, from) + { + } + + protected override TimeSpan Play(int step) + { + switch (step) + { + case 0: + { + Effects.PlaySound(Location, Map, 0x106); + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3735, 1, + 182, 0xBE3); + + return TimeSpan.FromSeconds(4.0); + } + case 1: + { + EffectItem hole = EffectItem.Create(Location, Map, TimeSpan.FromSeconds(10.0)); + hole.ItemID = 0x913; + + Effects.PlaySound(Location, Map, 0x222); + + return TimeSpan.FromSeconds(4.0); + } + case 2: + { + Effects.PlaySound(Location, Map, 0x21F); + + return TimeSpan.FromSeconds(4.0); + } + default: + { + EffectItem dummy = EffectItem.Create(Location, Map, TimeSpan.FromSeconds(20.0)); + dummy.PublicOverheadMessage(MessageType.Regular, 0x3B2, true, + "* A magical bunny leaps out of its hole, disturbed by the thorn's effect! *"); + + BaseCreature spawn = new VorpalBunny(); + if (!SpawnCreature(spawn)) + spawn.Delete(); + + return TimeSpan.Zero; + } + } + } + } + + public class SwampGreenThornsEffect : GreenThornsEffect + { + public SwampGreenThornsEffect(Point3D location, Map map, Mobile from) : base(location, map, from) + { + } + + protected override TimeSpan Play(int step) + { + switch (step) + { + case 0: + { + Effects.PlaySound(Location, Map, 0x106); + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3735, 1, + 182, 0xBE3); + + return TimeSpan.FromSeconds(4.0); + } + case 1: + { + Effects.PlaySound(Location, Map, 0x222); + + return TimeSpan.FromSeconds(4.0); + } + case 2: + { + Effects.PlaySound(Location, Map, 0x21F); + + return TimeSpan.FromSeconds(1.0); + } + default: + { + EffectItem dummy = EffectItem.Create(Location, Map, TimeSpan.FromSeconds(20.0)); + dummy.PublicOverheadMessage(MessageType.Regular, 0x3B2, true, + "* Strange green tendrils rise from the ground, whipping wildly! *"); + Effects.PlaySound(Location, Map, 0x2B0); + + BaseCreature spawn = new WhippingVine(); + if (!SpawnCreature(spawn)) + spawn.Delete(); + + return TimeSpan.Zero; + } + } + } + } + + public class SnowGreenThornsEffect : GreenThornsEffect + { + public SnowGreenThornsEffect(Point3D location, Map map, Mobile from) : base(location, map, from) + { + } + + protected override TimeSpan Play(int step) + { + switch (step) + { + case 0: + { + Effects.PlaySound(Location, Map, 0x106); + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3735, 1, + 182, 0xBE3); + + return TimeSpan.FromSeconds(4.0); + } + case 1: + { + Effects.PlaySound(Location, Map, 0x222); + + return TimeSpan.FromSeconds(4.0); + } + case 2: + { + Effects.PlaySound(Location, Map, 0x21F); + + return TimeSpan.FromSeconds(4.0); + } + default: + { + EffectItem dummy = EffectItem.Create(Location, Map, TimeSpan.FromSeconds(20.0)); + dummy.PublicOverheadMessage(MessageType.Regular, 0x3B2, true, + "* Slithering ice serpents rise to the surface to investigate the disturbance! *"); + + BaseCreature spawn = new GiantIceWorm(); + if (!SpawnCreature(spawn)) + spawn.Delete(); + + for (int i = 0; i < 3; i++) + { + BaseCreature snake = new IceSnake(); + if (!SpawnCreature(snake)) + snake.Delete(); + } + + return TimeSpan.Zero; + } + } + } + } + + public class SandGreenThornsEffect : GreenThornsEffect + { + public SandGreenThornsEffect(Point3D location, Map map, Mobile from) : base(location, map, from) + { + } + + protected override TimeSpan Play(int step) + { + switch (step) + { + case 0: + { + Effects.PlaySound(Location, Map, 0x106); + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3735, 1, + 182, 0xBE3); + + return TimeSpan.FromSeconds(4.0); + } + case 1: + { + Effects.PlaySound(Location, Map, 0x222); + + return TimeSpan.FromSeconds(4.0); + } + case 2: + { + Effects.PlaySound(Location, Map, 0x21F); + + return TimeSpan.FromSeconds(5.0); + } + default: + { + EffectItem dummy = EffectItem.Create(Location, Map, TimeSpan.FromSeconds(20.0)); + dummy.PublicOverheadMessage(MessageType.Regular, 0x3B2, true, + "* The sand collapses, revealing a dark hole. *"); + + GreenThornsSHTeleporter.Create(Location, Map); + + return TimeSpan.Zero; + } + } + } + } + + public class GreenThornsSHTeleporter : Item + { + public static readonly Point3D Destination = new Point3D(5738, 1856, 0); + + private GreenThornsSHTeleporter() : base(0x913) + { + Movable = false; + Hue = 0x1; + } + + public GreenThornsSHTeleporter(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a hole"; + + public static void Create(Point3D location, Map map) + { + GreenThornsSHTeleporter tele = new GreenThornsSHTeleporter(); + + tele.MoveToWorld(location, map); + + new InternalTimer(tele).Start(); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(this, 3)) + { + BaseCreature.TeleportPets(from, Destination, Map); + + from.Location = Destination; + } + else + { + from.SendLocalizedMessage(1019045); // I can't reach that. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Delete(); + } + + private class InternalTimer : Timer + { + private GreenThornsSHTeleporter m_Teleporter; + + public InternalTimer(GreenThornsSHTeleporter teleporter) : base(TimeSpan.FromMinutes(1.0)) + { + m_Teleporter = teleporter; + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + m_Teleporter.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/MiscItems/OrangePetals.cs b/Scripts/Engines/Plants/MiscItems/OrangePetals.cs index 073fba61b..a640d6f66 100644 --- a/Scripts/Engines/Plants/MiscItems/OrangePetals.cs +++ b/Scripts/Engines/Plants/MiscItems/OrangePetals.cs @@ -4,139 +4,137 @@ using Server.Network; namespace Server.Items { - public class OrangePetals : Item - { - public override int LabelNumber => 1053122; // orange petals + public class OrangePetals : Item + { + private static Hashtable m_Table = new Hashtable(); - public override double DefaultWeight => 0.1; + [Constructible] + public OrangePetals() : this(1) + { + } - [Constructible] - public OrangePetals() : this( 1 ) - { - } + [Constructible] + public OrangePetals(int amount) : base(0x1021) + { + Stackable = true; + Hue = 0x2B; + Amount = amount; + } - [Constructible] - public OrangePetals( int amount ) : base( 0x1021 ) - { - Stackable = true; - Hue = 0x2B; - Amount = amount; - } + public OrangePetals(Serial serial) : base(serial) + { + } - public OrangePetals( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1053122; // orange petals - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( item != this ) - return base.CheckItemUse( from, item ); + public override double DefaultWeight => 0.1; - if ( from != RootParent ) - { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - return false; - } + public override bool CheckItemUse(Mobile from, Item item) + { + if (item != this) + return base.CheckItemUse(from, item); - return base.CheckItemUse( from, item ); - } + if (from != RootParent) + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + return false; + } - public override void OnDoubleClick( Mobile from ) - { - OrangePetalsContext context = GetContext( from ); + return base.CheckItemUse(from, item); + } - if ( context != null ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061904 ); - return; - } + public override void OnDoubleClick(Mobile from) + { + OrangePetalsContext context = GetContext(from); - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061905 ); - from.PlaySound( 0x3B ); + if (context != null) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1061904); + return; + } - Timer timer = new OrangePetalsTimer( from ); - timer.Start(); + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1061905); + from.PlaySound(0x3B); - AddContext( from, new OrangePetalsContext( timer ) ); + Timer timer = new OrangePetalsTimer(from); + timer.Start(); - Consume(); - } + AddContext(from, new OrangePetalsContext(timer)); - private static Hashtable m_Table = new Hashtable(); + Consume(); + } - private static void AddContext( Mobile m, OrangePetalsContext context ) - { - m_Table[m] = context; - } + private static void AddContext(Mobile m, OrangePetalsContext context) + { + m_Table[m] = context; + } - public static void RemoveContext( Mobile m ) - { - OrangePetalsContext context = GetContext( m ); + public static void RemoveContext(Mobile m) + { + OrangePetalsContext context = GetContext(m); - if ( context != null ) - RemoveContext( m, context ); - } + if (context != null) + RemoveContext(m, context); + } - private static void RemoveContext( Mobile m, OrangePetalsContext context ) - { - m_Table.Remove( m ); + private static void RemoveContext(Mobile m, OrangePetalsContext context) + { + m_Table.Remove(m); - context.Timer.Stop(); - } + context.Timer.Stop(); + } - private static OrangePetalsContext GetContext( Mobile m ) - { - return ( m_Table[m] as OrangePetalsContext ); - } + private static OrangePetalsContext GetContext(Mobile m) + { + return m_Table[m] as OrangePetalsContext; + } - public static bool UnderEffect( Mobile m ) - { - return ( GetContext( m ) != null ); - } + public static bool UnderEffect(Mobile m) + { + return GetContext(m) != null; + } - private class OrangePetalsTimer : Timer - { - private Mobile m_Mobile; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public OrangePetalsTimer( Mobile from ) : base ( TimeSpan.FromMinutes( 5.0 ) ) - { - m_Mobile = from; - } + writer.Write(0); // version + } - protected override void OnTick() - { - if ( !m_Mobile.Deleted ) - { - m_Mobile.LocalOverheadMessage( MessageType.Regular, 0x3F, true, - "* You feel the effects of your poison resistance wearing off *" ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - RemoveContext( m_Mobile ); - } - } + int version = reader.ReadInt(); + } - private class OrangePetalsContext - { - public Timer Timer { get; } + private class OrangePetalsTimer : Timer + { + private Mobile m_Mobile; - public OrangePetalsContext( Timer timer ) - { - Timer = timer; - } - } + public OrangePetalsTimer(Mobile from) : base(TimeSpan.FromMinutes(5.0)) + { + m_Mobile = from; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + protected override void OnTick() + { + if (!m_Mobile.Deleted) + m_Mobile.LocalOverheadMessage(MessageType.Regular, 0x3F, true, + "* You feel the effects of your poison resistance wearing off *"); - writer.Write( (int) 0 ); // version - } + RemoveContext(m_Mobile); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + private class OrangePetalsContext + { + public OrangePetalsContext(Timer timer) + { + Timer = timer; + } - int version = reader.ReadInt(); - } - } -} + public Timer Timer{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/MiscItems/RedLeaves.cs b/Scripts/Engines/Plants/MiscItems/RedLeaves.cs index f41da4c41..7c1a2bf75 100644 --- a/Scripts/Engines/Plants/MiscItems/RedLeaves.cs +++ b/Scripts/Engines/Plants/MiscItems/RedLeaves.cs @@ -2,100 +2,100 @@ using Server.Targeting; namespace Server.Items { - public class RedLeaves : Item - { - public override int LabelNumber => 1053123; // red leaves + public class RedLeaves : Item + { + [Constructible] + public RedLeaves() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public RedLeaves(int amount) : base(0x1E85) + { + Stackable = true; + Hue = 0x21; + Amount = amount; + } - [Constructible] - public RedLeaves() : this( 1 ) - { - } + public RedLeaves(Serial serial) : base(serial) + { + } - [Constructible] - public RedLeaves( int amount ) : base( 0x1E85 ) - { - Stackable = true; - Hue = 0x21; - Amount = amount; - } + public override int LabelNumber => 1053123; // red leaves - public RedLeaves( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } - from.Target = new InternalTarget( this ); - from.SendLocalizedMessage( 1061907 ); // Choose a book you wish to seal with the wax from the red leaf. - } + from.Target = new InternalTarget(this); + from.SendLocalizedMessage(1061907); // Choose a book you wish to seal with the wax from the red leaf. + } - private class InternalTarget : Target - { - private RedLeaves m_RedLeaves; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public InternalTarget( RedLeaves redLeaves ) : base( 3, false, TargetFlags.None ) - { - m_RedLeaves = redLeaves; - } + writer.Write(0); // version + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_RedLeaves.Deleted ) - return; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( !m_RedLeaves.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } + int version = reader.ReadInt(); + } - if ( !(targeted is Item item) || !item.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else if ( !(item is BaseBook) ) - { - item.LabelTo( from, 1061911 ); // You can only use red leaves to seal the ink into book pages! - } - else - { - BaseBook book = (BaseBook)item; + private class InternalTarget : Target + { + private RedLeaves m_RedLeaves; - if ( !book.Writable ) - { - book.LabelTo( from, 1061909 ); // The ink in this book has already been sealed. - } - else - { - m_RedLeaves.Consume(); - book.Writable = false; + public InternalTarget(RedLeaves redLeaves) : base(3, false, TargetFlags.None) + { + m_RedLeaves = redLeaves; + } - book.LabelTo( from, 1061910 ); // You seal the ink to the page using wax from the red leaf. - } - } - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_RedLeaves.Deleted) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (!m_RedLeaves.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } - writer.Write( (int) 0 ); // version - } + if (!(targeted is Item item) || !item.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else if (!(item is BaseBook)) + { + item.LabelTo(from, 1061911); // You can only use red leaves to seal the ink into book pages! + } + else + { + BaseBook book = (BaseBook)item; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (!book.Writable) + { + book.LabelTo(from, 1061909); // The ink in this book has already been sealed. + } + else + { + m_RedLeaves.Consume(); + book.Writable = false; - int version = reader.ReadInt(); - } - } -} + book.LabelTo(from, 1061910); // You seal the ink to the page using wax from the red leaf. + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/MiscMobiles/GiantIceWorm.cs b/Scripts/Engines/Plants/MiscMobiles/GiantIceWorm.cs index 14e3ba123..523de4de3 100644 --- a/Scripts/Engines/Plants/MiscMobiles/GiantIceWorm.cs +++ b/Scripts/Engines/Plants/MiscMobiles/GiantIceWorm.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class GiantIceWorm : BaseCreature - { - public override string CorpseName => "a giant ice worm corpse"; - public override bool SubdueBeforeTame => true; - public override string DefaultName => "a giant ice worm"; + public class GiantIceWorm : BaseCreature + { + [Constructible] + public GiantIceWorm() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 89; + BaseSoundID = 0xDC; - [Constructible] - public GiantIceWorm() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 89; - BaseSoundID = 0xDC; + SetStr(216, 245); + SetDex(76, 100); + SetInt(66, 85); - SetStr( 216, 245 ); - SetDex( 76, 100 ); - SetInt( 66, 85 ); + SetHits(130, 147); - SetHits( 130, 147 ); + SetDamage(7, 17); - SetDamage( 7, 17 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Cold, 90); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Cold, 90 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 0); + SetResistance(ResistanceType.Cold, 80, 90); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 0 ); - SetResistance( ResistanceType.Cold, 80, 90 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Poisoning, 75.1, 95.0); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 75.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.Poisoning, 75.1, 95.0 ); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 75.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 4500; + Karma = -4500; - Fame = 4500; - Karma = -4500; + VirtualArmor = 40; - VirtualArmor = 40; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 71.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 71.1; - } + public GiantIceWorm(Serial serial) : base(serial) + { + } - public override Poison PoisonImmune => Poison.Greater; + public override string CorpseName => "a giant ice worm corpse"; + public override bool SubdueBeforeTame => true; + public override string DefaultName => "a giant ice worm"; - public override Poison HitPoison => Poison.Greater; + public override Poison PoisonImmune => Poison.Greater; - public override FoodType FavoriteFood => FoodType.Meat; + public override Poison HitPoison => Poison.Greater; - public GiantIceWorm( Serial serial ) : base ( serial ) - { - } + public override FoodType FavoriteFood => FoodType.Meat; - public override void Serialize(GenericWriter writer) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/Network/DisplayHelpTopic.cs b/Scripts/Engines/Plants/Network/DisplayHelpTopic.cs index 2f548bb58..e026d8a03 100644 --- a/Scripts/Engines/Plants/Network/DisplayHelpTopic.cs +++ b/Scripts/Engines/Plants/Network/DisplayHelpTopic.cs @@ -1,15 +1,15 @@ namespace Server.Network { - public class DisplayHelpTopic : Packet - { - public DisplayHelpTopic( int topicID, bool display ) : base( 0xBF ) - { - EnsureCapacity( 11 ); + public class DisplayHelpTopic : Packet + { + public DisplayHelpTopic(int topicID, bool display) : base(0xBF) + { + EnsureCapacity(11); - m_Stream.Write( (short) 0x17 ); - m_Stream.Write( (byte) 1 ); - m_Stream.Write( (int) topicID ); - m_Stream.Write( (bool) display ); - } - } + m_Stream.Write((short)0x17); + m_Stream.Write((byte)1); + m_Stream.Write(topicID); + m_Stream.Write(display); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantBowl.cs b/Scripts/Engines/Plants/PlantBowl.cs index 31b275815..6e517adde 100644 --- a/Scripts/Engines/Plants/PlantBowl.cs +++ b/Scripts/Engines/Plants/PlantBowl.cs @@ -1,188 +1,194 @@ using Server.Items; -using Server.Targeting; using Server.Network; +using Server.Targeting; namespace Server.Engines.Plants { - public class PlantBowl : Item - { - public override int LabelNumber => 1060834; // a plant bowl + public class PlantBowl : Item + { + private static int[] m_DirtPatchTiles = + { + 0x9, 0x15, + 0x71, 0x7C, + 0x82, 0xA7, + 0xDC, 0xE3, + 0xE8, 0xEB, + 0x141, 0x144, + 0x14C, 0x15C, + 0x169, 0x174, + 0x1DC, 0x1EF, + 0x272, 0x275, + 0x27E, 0x281, + 0x2D0, 0x2D7, + 0x2E5, 0x2FF, + 0x303, 0x31F, + 0x32C, 0x32F, + 0x33D, 0x340, + 0x345, 0x34C, + 0x355, 0x358, + 0x367, 0x36E, + 0x377, 0x37A, + 0x38D, 0x390, + 0x395, 0x39C, + 0x3A5, 0x3A8, + 0x3F6, 0x405, + 0x547, 0x54E, + 0x553, 0x556, + 0x597, 0x59E, + 0x623, 0x63A, + 0x6F3, 0x6FA, + 0x777, 0x791, + 0x79A, 0x7A9, + 0x7AE, 0x7B1, + 0x98C, 0x99F, + 0x9AC, 0x9BF, + 0x5B27, 0x5B3E, + 0x71F4, 0x71FB, + 0x72C9, 0x72CA + }; - [Constructible] - public PlantBowl() : base( 0x15FD ) - { - Weight = 1.0; - } + [Constructible] + public PlantBowl() : base(0x15FD) + { + Weight = 1.0; + } - public PlantBowl( Serial serial ) : base( serial ) - { - } + public PlantBowl(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } + public override int LabelNumber => 1060834; // a plant bowl - from.Target = new InternalTarget( this ); - from.SendLocalizedMessage( 1061897 ); // Choose a patch of dirt to scoop up. - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } - private class InternalTarget : Target - { - private PlantBowl m_PlantBowl; + from.Target = new InternalTarget(this); + from.SendLocalizedMessage(1061897); // Choose a patch of dirt to scoop up. + } - public InternalTarget( PlantBowl plantBowl ) : base( 3, true, TargetFlags.None ) - { - m_PlantBowl = plantBowl; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_PlantBowl.Deleted ) - return; + writer.Write(0); // version + } - if ( !m_PlantBowl.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( targeted is FertileDirt dirt ) - { - int _dirtNeeded = Core.ML ? 20 : 40; + int version = reader.ReadInt(); + } - if ( !dirt.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else if ( dirt.Amount < _dirtNeeded ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061896 ); // You need more dirt to fill a plant bowl! - } - else - { - PlantItem fullBowl = new PlantItem( true ); + public static bool IsDirtPatch(object obj) + { + int tileID; - if ( from.PlaceInBackpack( fullBowl ) ) - { - dirt.Consume( _dirtNeeded ); - m_PlantBowl.Delete(); + if (obj is Static staticObj && !staticObj.Movable) + tileID = (staticObj.ItemID & 0x3FFF) | 0x4000; + else if (obj is StaticTarget staticTarget) + tileID = (staticTarget.ItemID & 0x3FFF) | 0x4000; + else if (obj is LandTarget landTarget) + tileID = landTarget.TileID; + else + return false; - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061895 ); // You fill the bowl with fresh dirt. - } - else - { - fullBowl.Delete(); + bool contains = false; - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061894 ); // There is no room in your backpack for a bowl full of dirt! - } - } - } - else if ( IsDirtPatch( targeted ) ) - { - PlantItem fullBowl = new PlantItem( false ); + for (int i = 0; !contains && i < m_DirtPatchTiles.Length; i += 2) + contains = tileID >= m_DirtPatchTiles[i] && tileID <= m_DirtPatchTiles[i + 1]; - if ( from.PlaceInBackpack( fullBowl ) ) - { - m_PlantBowl.Delete(); + return contains; + } - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061895 ); // You fill the bowl with fresh dirt. - } - else - { - fullBowl.Delete(); + private class InternalTarget : Target + { + private PlantBowl m_PlantBowl; - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061894 ); // There is no room in your backpack for a bowl full of dirt! - } - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061893 ); // You'll want to gather fresh dirt in order to raise a healthy plant! - } - } + public InternalTarget(PlantBowl plantBowl) : base(3, true, TargetFlags.None) + { + m_PlantBowl = plantBowl; + } - protected override void OnTargetOutOfRange( Mobile from, object targeted ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502825 ); // That location is too far away - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_PlantBowl.Deleted) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (!m_PlantBowl.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } - writer.Write( (int) 0 ); // version - } + if (targeted is FertileDirt dirt) + { + int _dirtNeeded = Core.ML ? 20 : 40; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (!dirt.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else if (dirt.Amount < _dirtNeeded) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061896); // You need more dirt to fill a plant bowl! + } + else + { + PlantItem fullBowl = new PlantItem(true); - int version = reader.ReadInt(); - } + if (from.PlaceInBackpack(fullBowl)) + { + dirt.Consume(_dirtNeeded); + m_PlantBowl.Delete(); - public static bool IsDirtPatch( object obj ) - { - int tileID; + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061895); // You fill the bowl with fresh dirt. + } + else + { + fullBowl.Delete(); - if ( obj is Static staticObj && !staticObj.Movable ) - tileID = (staticObj.ItemID & 0x3FFF) | 0x4000; - else if ( obj is StaticTarget staticTarget ) - tileID = (staticTarget.ItemID & 0x3FFF) | 0x4000; - else if ( obj is LandTarget landTarget ) - tileID = landTarget.TileID; - else - return false; + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061894); // There is no room in your backpack for a bowl full of dirt! + } + } + } + else if (IsDirtPatch(targeted)) + { + PlantItem fullBowl = new PlantItem(false); - bool contains = false; + if (from.PlaceInBackpack(fullBowl)) + { + m_PlantBowl.Delete(); - for ( int i = 0; !contains && i < m_DirtPatchTiles.Length; i += 2 ) - contains = ( tileID >= m_DirtPatchTiles[i] && tileID <= m_DirtPatchTiles[i + 1] ); + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1061895); // You fill the bowl with fresh dirt. + } + else + { + fullBowl.Delete(); - return contains; - } + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061894); // There is no room in your backpack for a bowl full of dirt! + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061893); // You'll want to gather fresh dirt in order to raise a healthy plant! + } + } - private static int[] m_DirtPatchTiles = { - 0x9, 0x15, - 0x71, 0x7C, - 0x82, 0xA7, - 0xDC, 0xE3, - 0xE8, 0xEB, - 0x141, 0x144, - 0x14C, 0x15C, - 0x169, 0x174, - 0x1DC, 0x1EF, - 0x272, 0x275, - 0x27E, 0x281, - 0x2D0, 0x2D7, - 0x2E5, 0x2FF, - 0x303, 0x31F, - 0x32C, 0x32F, - 0x33D, 0x340, - 0x345, 0x34C, - 0x355, 0x358, - 0x367, 0x36E, - 0x377, 0x37A, - 0x38D, 0x390, - 0x395, 0x39C, - 0x3A5, 0x3A8, - 0x3F6, 0x405, - 0x547, 0x54E, - 0x553, 0x556, - 0x597, 0x59E, - 0x623, 0x63A, - 0x6F3, 0x6FA, - 0x777, 0x791, - 0x79A, 0x7A9, - 0x7AE, 0x7B1, - 0x98C, 0x99F, - 0x9AC, 0x9BF, - 0x5B27, 0x5B3E, - 0x71F4, 0x71FB, - 0x72C9, 0x72CA, - }; - } -} + protected override void OnTargetOutOfRange(Mobile from, object targeted) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502825); // That location is too far away + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantHue.cs b/Scripts/Engines/Plants/PlantHue.cs index 1009a2323..5e8c91312 100644 --- a/Scripts/Engines/Plants/PlantHue.cs +++ b/Scripts/Engines/Plants/PlantHue.cs @@ -3,182 +3,182 @@ using System.Collections.Generic; namespace Server.Engines.Plants { - [Flags] - public enum PlantHue - { - Plain = 0x1 | Crossable | Reproduces, + [Flags] + public enum PlantHue + { + Plain = 0x1 | Crossable | Reproduces, - Red = 0x2 | Crossable | Reproduces, - Blue = 0x4 | Crossable | Reproduces, - Yellow = 0x8 | Crossable | Reproduces, + Red = 0x2 | Crossable | Reproduces, + Blue = 0x4 | Crossable | Reproduces, + Yellow = 0x8 | Crossable | Reproduces, - BrightRed = Red | Bright, - BrightBlue = Blue | Bright, - BrightYellow = Yellow | Bright, + BrightRed = Red | Bright, + BrightBlue = Blue | Bright, + BrightYellow = Yellow | Bright, - Purple = Red | Blue, - Green = Blue | Yellow, - Orange = Red | Yellow, + Purple = Red | Blue, + Green = Blue | Yellow, + Orange = Red | Yellow, - BrightPurple = Purple | Bright, - BrightGreen = Green | Bright, - BrightOrange = Orange | Bright, + BrightPurple = Purple | Bright, + BrightGreen = Green | Bright, + BrightOrange = Orange | Bright, - Black = 0x10, - White = 0x20, - Pink = 0x40, - Magenta = 0x80, - Aqua = 0x100, - FireRed = 0x200, + Black = 0x10, + White = 0x20, + Pink = 0x40, + Magenta = 0x80, + Aqua = 0x100, + FireRed = 0x200, - None = 0, - Reproduces = 0x2000000, - Crossable = 0x4000000, - Bright = 0x8000000 - } + None = 0, + Reproduces = 0x2000000, + Crossable = 0x4000000, + Bright = 0x8000000 + } - public class PlantHueInfo - { - private static Dictionary m_Table; + public class PlantHueInfo + { + private static Dictionary m_Table; - static PlantHueInfo() - { - m_Table = new Dictionary(); + static PlantHueInfo() + { + m_Table = new Dictionary(); - m_Table[PlantHue.Plain] = new PlantHueInfo( 0, 1060813, PlantHue.Plain, 0x835 ); - m_Table[PlantHue.Red] = new PlantHueInfo( 0x66D, 1060814, PlantHue.Red, 0x24 ); - m_Table[PlantHue.Blue] = new PlantHueInfo( 0x53D, 1060815, PlantHue.Blue, 0x6 ); - m_Table[PlantHue.Yellow] = new PlantHueInfo( 0x8A5, 1060818, PlantHue.Yellow, 0x38 ); - m_Table[PlantHue.BrightRed] = new PlantHueInfo( 0x21, 1060814, PlantHue.BrightRed, 0x21 ); - m_Table[PlantHue.BrightBlue] = new PlantHueInfo( 0x5, 1060815, PlantHue.BrightBlue, 0x6 ); - m_Table[PlantHue.BrightYellow] = new PlantHueInfo( 0x38, 1060818, PlantHue.BrightYellow, 0x35 ); - m_Table[PlantHue.Purple] = new PlantHueInfo( 0xD, 1060816, PlantHue.Purple, 0x10 ); - m_Table[PlantHue.Green] = new PlantHueInfo( 0x59B, 1060819, PlantHue.Green, 0x42 ); - m_Table[PlantHue.Orange] = new PlantHueInfo( 0x46F, 1060817, PlantHue.Orange, 0x2E ); - m_Table[PlantHue.BrightPurple] = new PlantHueInfo( 0x10, 1060816, PlantHue.BrightPurple, 0xD ); - m_Table[PlantHue.BrightGreen] = new PlantHueInfo( 0x42, 1060819, PlantHue.BrightGreen, 0x3F ); - m_Table[PlantHue.BrightOrange] = new PlantHueInfo( 0x2B, 1060817, PlantHue.BrightOrange, 0x2B ); - m_Table[PlantHue.Black] = new PlantHueInfo( 0x455, 1060820, PlantHue.Black, 0 ); - m_Table[PlantHue.White] = new PlantHueInfo( 0x481, 1060821, PlantHue.White, 0x481 ); - m_Table[PlantHue.Pink] = new PlantHueInfo( 0x48E, 1061854, PlantHue.Pink ); - m_Table[PlantHue.Magenta] = new PlantHueInfo( 0x486, 1061852, PlantHue.Magenta ); - m_Table[PlantHue.Aqua] = new PlantHueInfo( 0x495, 1061853, PlantHue.Aqua ); - m_Table[PlantHue.FireRed] = new PlantHueInfo( 0x489, 1061855, PlantHue.FireRed ); - } + m_Table[PlantHue.Plain] = new PlantHueInfo(0, 1060813, PlantHue.Plain, 0x835); + m_Table[PlantHue.Red] = new PlantHueInfo(0x66D, 1060814, PlantHue.Red, 0x24); + m_Table[PlantHue.Blue] = new PlantHueInfo(0x53D, 1060815, PlantHue.Blue, 0x6); + m_Table[PlantHue.Yellow] = new PlantHueInfo(0x8A5, 1060818, PlantHue.Yellow, 0x38); + m_Table[PlantHue.BrightRed] = new PlantHueInfo(0x21, 1060814, PlantHue.BrightRed, 0x21); + m_Table[PlantHue.BrightBlue] = new PlantHueInfo(0x5, 1060815, PlantHue.BrightBlue, 0x6); + m_Table[PlantHue.BrightYellow] = new PlantHueInfo(0x38, 1060818, PlantHue.BrightYellow, 0x35); + m_Table[PlantHue.Purple] = new PlantHueInfo(0xD, 1060816, PlantHue.Purple, 0x10); + m_Table[PlantHue.Green] = new PlantHueInfo(0x59B, 1060819, PlantHue.Green, 0x42); + m_Table[PlantHue.Orange] = new PlantHueInfo(0x46F, 1060817, PlantHue.Orange, 0x2E); + m_Table[PlantHue.BrightPurple] = new PlantHueInfo(0x10, 1060816, PlantHue.BrightPurple, 0xD); + m_Table[PlantHue.BrightGreen] = new PlantHueInfo(0x42, 1060819, PlantHue.BrightGreen, 0x3F); + m_Table[PlantHue.BrightOrange] = new PlantHueInfo(0x2B, 1060817, PlantHue.BrightOrange, 0x2B); + m_Table[PlantHue.Black] = new PlantHueInfo(0x455, 1060820, PlantHue.Black, 0); + m_Table[PlantHue.White] = new PlantHueInfo(0x481, 1060821, PlantHue.White, 0x481); + m_Table[PlantHue.Pink] = new PlantHueInfo(0x48E, 1061854, PlantHue.Pink); + m_Table[PlantHue.Magenta] = new PlantHueInfo(0x486, 1061852, PlantHue.Magenta); + m_Table[PlantHue.Aqua] = new PlantHueInfo(0x495, 1061853, PlantHue.Aqua); + m_Table[PlantHue.FireRed] = new PlantHueInfo(0x489, 1061855, PlantHue.FireRed); + } - public static PlantHueInfo GetInfo( PlantHue plantHue ) - { - if (m_Table.TryGetValue( plantHue, out PlantHueInfo info )) - return info; - return m_Table[PlantHue.Plain]; - } + private PlantHueInfo(int hue, int name, PlantHue plantHue) : this(hue, name, plantHue, hue) + { + } - public static PlantHue RandomFirstGeneration() - { - switch ( Utility.Random( 4 ) ) - { - case 0: return PlantHue.Plain; - case 1: return PlantHue.Red; - case 2: return PlantHue.Blue; - default: return PlantHue.Yellow; - } - } + private PlantHueInfo(int hue, int name, PlantHue plantHue, int gumpHue) + { + Hue = hue; + Name = name; + PlantHue = plantHue; + GumpHue = gumpHue; + } - public static bool CanReproduce( PlantHue plantHue ) - { - return (plantHue & PlantHue.Reproduces) != PlantHue.None; - } + public int Hue{ get; } - public static bool IsCrossable( PlantHue plantHue ) - { - return (plantHue & PlantHue.Crossable) != PlantHue.None; - } + public int Name{ get; } - public static bool IsBright( PlantHue plantHue ) - { - return (plantHue & PlantHue.Bright) != PlantHue.None; - } + public PlantHue PlantHue{ get; } - public static PlantHue GetNotBright( PlantHue plantHue ) - { - return plantHue & ~PlantHue.Bright; - } + public int GumpHue{ get; } - public static bool IsPrimary( PlantHue plantHue ) - { - return plantHue == PlantHue.Red || plantHue == PlantHue.Blue || plantHue == PlantHue.Yellow; - } + public static PlantHueInfo GetInfo(PlantHue plantHue) + { + if (m_Table.TryGetValue(plantHue, out PlantHueInfo info)) + return info; + return m_Table[PlantHue.Plain]; + } - public static PlantHue Cross( PlantHue first, PlantHue second ) - { - if ( !IsCrossable( first ) || !IsCrossable( second ) ) - return PlantHue.None; + public static PlantHue RandomFirstGeneration() + { + switch (Utility.Random(4)) + { + case 0: return PlantHue.Plain; + case 1: return PlantHue.Red; + case 2: return PlantHue.Blue; + default: return PlantHue.Yellow; + } + } - if ( Utility.RandomDouble() < 0.01 ) - return Utility.RandomBool() ? PlantHue.Black : PlantHue.White; + public static bool CanReproduce(PlantHue plantHue) + { + return (plantHue & PlantHue.Reproduces) != PlantHue.None; + } - if ( first == PlantHue.Plain || second == PlantHue.Plain ) - return PlantHue.Plain; + public static bool IsCrossable(PlantHue plantHue) + { + return (plantHue & PlantHue.Crossable) != PlantHue.None; + } - PlantHue notBrightFirst = GetNotBright( first ); - PlantHue notBrightSecond = GetNotBright( second ); + public static bool IsBright(PlantHue plantHue) + { + return (plantHue & PlantHue.Bright) != PlantHue.None; + } - if ( notBrightFirst == notBrightSecond ) - return first | PlantHue.Bright; + public static PlantHue GetNotBright(PlantHue plantHue) + { + return plantHue & ~PlantHue.Bright; + } - bool firstPrimary = IsPrimary( notBrightFirst ); - bool secondPrimary = IsPrimary( notBrightSecond ); + public static bool IsPrimary(PlantHue plantHue) + { + return plantHue == PlantHue.Red || plantHue == PlantHue.Blue || plantHue == PlantHue.Yellow; + } - if ( firstPrimary && secondPrimary ) - return notBrightFirst | notBrightSecond; + public static PlantHue Cross(PlantHue first, PlantHue second) + { + if (!IsCrossable(first) || !IsCrossable(second)) + return PlantHue.None; - if ( firstPrimary && !secondPrimary ) - return notBrightFirst; + if (Utility.RandomDouble() < 0.01) + return Utility.RandomBool() ? PlantHue.Black : PlantHue.White; - if ( !firstPrimary && secondPrimary ) - return notBrightSecond; + if (first == PlantHue.Plain || second == PlantHue.Plain) + return PlantHue.Plain; - return notBrightFirst & notBrightSecond; - } + PlantHue notBrightFirst = GetNotBright(first); + PlantHue notBrightSecond = GetNotBright(second); - public int Hue { get; } + if (notBrightFirst == notBrightSecond) + return first | PlantHue.Bright; - public int Name { get; } + bool firstPrimary = IsPrimary(notBrightFirst); + bool secondPrimary = IsPrimary(notBrightSecond); - public PlantHue PlantHue { get; } + if (firstPrimary && secondPrimary) + return notBrightFirst | notBrightSecond; - public int GumpHue { get; } + if (firstPrimary && !secondPrimary) + return notBrightFirst; - private PlantHueInfo( int hue, int name, PlantHue plantHue ) : this( hue, name, plantHue, hue ) - { - } + if (!firstPrimary && secondPrimary) + return notBrightSecond; - private PlantHueInfo( int hue, int name, PlantHue plantHue, int gumpHue ) - { - Hue = hue; - Name = name; - PlantHue = plantHue; - GumpHue = gumpHue; - } + return notBrightFirst & notBrightSecond; + } - public bool IsCrossable() - { - return IsCrossable( PlantHue ); - } + public bool IsCrossable() + { + return IsCrossable(PlantHue); + } - public bool IsBright() - { - return IsBright( PlantHue ); - } + public bool IsBright() + { + return IsBright(PlantHue); + } - public PlantHue GetNotBright() - { - return GetNotBright( PlantHue ); - } + public PlantHue GetNotBright() + { + return GetNotBright(PlantHue); + } - public bool IsPrimary() - { - return IsPrimary( PlantHue ); - } - } -} + public bool IsPrimary() + { + return IsPrimary(PlantHue); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantItem.cs b/Scripts/Engines/Plants/PlantItem.cs index 0ed4215cc..7fa9ce307 100644 --- a/Scripts/Engines/Plants/PlantItem.cs +++ b/Scripts/Engines/Plants/PlantItem.cs @@ -1,566 +1,571 @@ -using System; using System.Collections; using System.Collections.Generic; +using Server.ContextMenus; using Server.Gumps; using Server.Items; using Server.Multis; -using Server.ContextMenus; using Server.Network; namespace Server.Engines.Plants { - public enum PlantStatus - { - BowlOfDirt = 0, - Seed = 1, - Sapling = 2, - Plant = 4, - FullGrownPlant = 7, - DecorativePlant = 10, - DeadTwigs = 11, - - Stage1 = 1, - Stage2 = 2, - Stage3 = 3, - Stage4 = 4, - Stage5 = 5, - Stage6 = 6, - Stage7 = 7, - Stage8 = 8, - Stage9 = 9 - } - - public class PlantItem : Item, ISecurable - { - /* - * Clients 7.0.12.0+ expect a container type in the plant label. - * To support older (and only older) clients, change this to false. - */ - private static readonly bool ShowContainerType = true; - - private PlantStatus m_PlantStatus; - private PlantType m_PlantType; - private PlantHue m_PlantHue; - private bool m_ShowType; - - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } - - public PlantSystem PlantSystem { get; private set; } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void OnSingleClick( Mobile from ) - { - if ( m_PlantStatus >= PlantStatus.DeadTwigs ) - LabelTo( from, LabelNumber ); - else if ( m_PlantStatus >= PlantStatus.DecorativePlant ) - LabelTo( from, 1061924 ); // a decorative plant - else if ( m_PlantStatus >= PlantStatus.FullGrownPlant ) - LabelTo( from, PlantTypeInfo.GetInfo( m_PlantType ).Name ); - else - LabelTo( from, 1029913 ); // plant bowl - } - - [CommandProperty( AccessLevel.GameMaster )] - public PlantStatus PlantStatus - { - get => m_PlantStatus; - set - { - if ( m_PlantStatus == value || value < PlantStatus.BowlOfDirt || value > PlantStatus.DeadTwigs ) - return; - - double ratio; - if ( PlantSystem != null ) - ratio = (double) PlantSystem.Hits / PlantSystem.MaxHits; - else - ratio = 1.0; - - m_PlantStatus = value; - - if ( m_PlantStatus >= PlantStatus.DecorativePlant ) - { - PlantSystem = null; - } - else - { - if ( PlantSystem == null ) - PlantSystem = new PlantSystem( this, false ); - - int hits = (int)( PlantSystem.MaxHits * ratio ); - - if ( hits == 0 && m_PlantStatus > PlantStatus.BowlOfDirt ) - PlantSystem.Hits = hits + 1; - else - PlantSystem.Hits = hits; - } - - Update(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public PlantType PlantType - { - get => m_PlantType; - set - { - m_PlantType = value; - Update(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public PlantHue PlantHue - { - get => m_PlantHue; - set - { - m_PlantHue = value; - Update(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool ShowType - { - get => m_ShowType; - set - { - m_ShowType = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool ValidGrowthLocation - { - get - { - if ( IsLockedDown && RootParent == null ) - return true; - - - if ( !(RootParent is Mobile owner) ) - return false; - - if ( owner.Backpack != null && IsChildOf( owner.Backpack ) ) - return true; - - BankBox bank = owner.FindBankNoCreate(); - if ( bank != null && IsChildOf( bank ) ) - return true; - - return false; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsGrowable => m_PlantStatus >= PlantStatus.BowlOfDirt && m_PlantStatus <= PlantStatus.Stage9; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsCrossable => PlantHueInfo.IsCrossable( PlantHue ) && PlantTypeInfo.IsCrossable( PlantType ); - - [CommandProperty( AccessLevel.GameMaster )] - public bool Reproduces => PlantHueInfo.CanReproduce( PlantHue ) && PlantTypeInfo.CanReproduce( PlantType ); - - public static ArrayList Plants { get; } = new ArrayList(); - - [Constructible] - public PlantItem() : this( false ) - { - } - - [Constructible] - public PlantItem( bool fertileDirt ) : base( 0x1602 ) - { - Weight = 1.0; - - m_PlantStatus = PlantStatus.BowlOfDirt; - PlantSystem = new PlantSystem( this, fertileDirt ); - Level = SecureLevel.Owner; - - Plants.Add( this ); - } - - public PlantItem( Serial serial ) : base( serial ) - { - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } - - public int GetLocalizedPlantStatus() - { - if ( m_PlantStatus >= PlantStatus.Plant ) - return 1060812; // plant - if ( m_PlantStatus >= PlantStatus.Sapling ) - return 1023305; // sapling - if ( m_PlantStatus >= PlantStatus.Seed ) - return 1060810; // seed - return 1026951; // dirt - } - - public int GetLocalizedContainerType() - { - return 1150435; // bowl - } - - private void Update() - { - if ( m_PlantStatus >= PlantStatus.DeadTwigs ) - { - ItemID = 0x1B9D; - Hue = PlantHueInfo.GetInfo( m_PlantHue ).Hue; - } - else if ( m_PlantStatus >= PlantStatus.FullGrownPlant ) - { - ItemID = PlantTypeInfo.GetInfo( m_PlantType ).ItemID; - Hue = PlantHueInfo.GetInfo( m_PlantHue ).Hue; - } - else if ( m_PlantStatus >= PlantStatus.Plant ) - { - ItemID = 0x1600; - Hue = 0; - } - else - { - ItemID = 0x1602; - Hue = 0; - } - - InvalidateProperties(); - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_PlantStatus >= PlantStatus.DeadTwigs ) - { - base.AddNameProperty( list ); - } - else if ( m_PlantStatus < PlantStatus.Seed ) - { - string args; - - if ( ShowContainerType ) - args = $"#{GetLocalizedContainerType()}\t#{PlantSystem.GetLocalizedDirtStatus()}"; - else - args = $"#{PlantSystem.GetLocalizedDirtStatus()}"; - - list.Add( 1060830, args ); // a ~1_val~ of ~2_val~ dirt - } - else - { - PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo( m_PlantType ); - PlantHueInfo hueInfo = PlantHueInfo.GetInfo( m_PlantHue ); - - if ( m_PlantStatus >= PlantStatus.DecorativePlant ) - { - list.Add( typeInfo.GetPlantLabelDecorative( hueInfo ), $"#{hueInfo.Name}\t#{typeInfo.Name}"); - } - else if ( m_PlantStatus >= PlantStatus.FullGrownPlant ) - { - list.Add( typeInfo.GetPlantLabelFullGrown( hueInfo ), - $"#{PlantSystem.GetLocalizedHealth()}\t#{hueInfo.Name}\t#{typeInfo.Name}"); - } - else - { - string args; - - if ( ShowContainerType ) - args = - $"#{GetLocalizedContainerType()}\t#{PlantSystem.GetLocalizedDirtStatus()}\t#{PlantSystem.GetLocalizedHealth()}"; - else - args = $"#{PlantSystem.GetLocalizedDirtStatus()}\t#{PlantSystem.GetLocalizedHealth()}"; - - if ( m_ShowType ) - { - args += $"\t#{hueInfo.Name}\t#{typeInfo.Name}\t#{GetLocalizedPlantStatus()}"; - - if ( m_PlantStatus == PlantStatus.Plant ) - list.Add( typeInfo.GetPlantLabelPlant( hueInfo ), args ); - else - list.Add( typeInfo.GetPlantLabelSeed( hueInfo ), args ); - } - else - { - args += - $"\t#{((typeInfo.PlantCategory == PlantCategory.Default) ? hueInfo.Name : (int) typeInfo.PlantCategory)}\t#{GetLocalizedPlantStatus()}"; - - list.Add( hueInfo.IsBright() ? 1060832 : 1060831, args ); // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ - } - } - } - } - - public bool IsUsableBy( Mobile from ) - { - return IsChildOf( from.Backpack ) || IsChildOf( from.FindBankNoCreate() ) || IsLockedDown && IsAccessibleTo( from ) || RootParent is Item root && root.IsSecure && root.IsAccessibleTo( from ); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_PlantStatus >= PlantStatus.DecorativePlant ) - return; - - Point3D loc = GetWorldLocation(); - - if ( !from.InLOS( loc ) || !from.InRange( loc, 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 1019045 ); // I can't reach that. - return; - } - - if ( !IsUsableBy( from ) ) - { - LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - return; - } - - from.SendGump( new MainPlantGump( this ) ); - } - - public void PlantSeed( Mobile from, Seed seed ) - { - if ( m_PlantStatus >= PlantStatus.FullGrownPlant ) - { - LabelTo( from, 1061919 ); // You must use a seed on some prepared soil! - } - else if ( !IsUsableBy( from ) ) - { - LabelTo( from, 1061921 ); // The bowl of dirt must be in your pack, or you must lock it down. - } - else if ( m_PlantStatus != PlantStatus.BowlOfDirt ) - { - from.SendLocalizedMessage( 1080389, "#" + GetLocalizedPlantStatus().ToString() ); // This bowl of dirt already has a ~1_val~ in it! - } - else if ( PlantSystem.Water < 2 ) - { - LabelTo( from, 1061920 ); // The dirt needs to be softened first. - } - else - { - m_PlantType = seed.PlantType; - m_PlantHue = seed.PlantHue; - m_ShowType = seed.ShowType; - - seed.Consume(); - - PlantStatus = PlantStatus.Seed; - - PlantSystem.Reset( false ); - - LabelTo( from, 1061922 ); // You plant the seed in the bowl of dirt. - } - } - - public void Die() - { - if ( m_PlantStatus >= PlantStatus.FullGrownPlant ) - { - PlantStatus = PlantStatus.DeadTwigs; - } - else - { - PlantStatus = PlantStatus.BowlOfDirt; - PlantSystem.Reset( true ); - } - } - - public void Pour( Mobile from, Item item ) - { - if ( m_PlantStatus >= PlantStatus.DeadTwigs ) - return; - - if ( m_PlantStatus == PlantStatus.DecorativePlant ) - { - LabelTo( from, 1053049 ); // This is a decorative plant, it does not need watering! - return; - } - - if ( !IsUsableBy( from ) ) - { - LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - return; - } - - if ( item is BaseBeverage beverage ) - { - if ( beverage.IsEmpty || !beverage.Pourable || beverage.Content != BeverageType.Water ) - { - LabelTo( from, 1053069 ); // You can't use that on a plant! - return; - } - - if ( !beverage.ValidateUse( from, true ) ) - return; - - beverage.Quantity--; - PlantSystem.Water++; - - from.PlaySound( 0x4E ); - LabelTo( from, 1061858 ); // You soften the dirt with water. - } - else if ( item is BasePotion potion ) - { - if ( ApplyPotion( potion.PotionEffect, false, out int message ) ) - { - potion.Consume(); - from.PlaySound( 0x240 ); - from.AddToBackpack( new Bottle() ); - } - LabelTo( from, message ); - } - else if ( item is PotionKeg keg ) - { - if ( keg.Held <= 0 ) - { - LabelTo( from, 1053069 ); // You can't use that on a plant! - return; - } - - if ( ApplyPotion( keg.Type, false, out int message ) ) - { - keg.Held--; - from.PlaySound( 0x240 ); - } - LabelTo( from, message ); - } - else - { - LabelTo( from, 1053069 ); // You can't use that on a plant! - } - } - - public bool ApplyPotion( PotionEffect effect, bool testOnly, out int message ) - { - if ( m_PlantStatus >= PlantStatus.DecorativePlant ) - { - message = 1053049; // This is a decorative plant, it does not need watering! - return false; - } - - if ( m_PlantStatus == PlantStatus.BowlOfDirt ) - { - message = 1053066; // You should only pour potions on a plant or seed! - return false; - } - - bool full = false; - - if ( effect == PotionEffect.PoisonGreater || effect == PotionEffect.PoisonDeadly ) - { - if ( PlantSystem.IsFullPoisonPotion ) - full = true; - else if ( !testOnly ) - PlantSystem.PoisonPotion++; - } - else if ( effect == PotionEffect.CureGreater ) - { - if ( PlantSystem.IsFullCurePotion ) - full = true; - else if ( !testOnly ) - PlantSystem.CurePotion++; - } - else if ( effect == PotionEffect.HealGreater ) - { - if ( PlantSystem.IsFullHealPotion ) - full = true; - else if ( !testOnly ) - PlantSystem.HealPotion++; - } - else if ( effect == PotionEffect.StrengthGreater ) - { - if ( PlantSystem.IsFullStrengthPotion ) - full = true; - else if ( !testOnly ) - PlantSystem.StrengthPotion++; - } - else if ( effect == PotionEffect.PoisonLesser || effect == PotionEffect.Poison || effect == PotionEffect.CureLesser || effect == PotionEffect.Cure || - effect == PotionEffect.HealLesser || effect == PotionEffect.Heal || effect == PotionEffect.Strength ) - { - message = 1053068; // This potion is not powerful enough to use on a plant! - return false; - } - else - { - message = 1053069; // You can't use that on a plant! - return false; - } - - if ( full ) - { - message = 1053065; // The plant is already soaked with this type of potion! - return false; - } - - message = 1053067; // You pour the potion over the plant. - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - - writer.Write( (int) Level ); - - writer.Write( (int) m_PlantStatus ); - writer.Write( (int) m_PlantType ); - writer.Write( (int) m_PlantHue ); - writer.Write( (bool) m_ShowType ); - - if ( m_PlantStatus < PlantStatus.DecorativePlant ) - PlantSystem.Save( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - case 1: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 0; - } - case 0: - { - if ( version < 1 ) - Level = SecureLevel.CoOwners; - - m_PlantStatus = (PlantStatus)reader.ReadInt(); - m_PlantType = (PlantType)reader.ReadInt(); - m_PlantHue = (PlantHue)reader.ReadInt(); - m_ShowType = reader.ReadBool(); - - if ( m_PlantStatus < PlantStatus.DecorativePlant ) - PlantSystem = new PlantSystem( this, reader ); - - if ( version < 2 && PlantHueInfo.IsCrossable( m_PlantHue ) ) - m_PlantHue |= PlantHue.Reproduces; - - break; - } - } - - Plants.Add( this ); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - Plants.Remove( this ); - } - } -} + public enum PlantStatus + { + BowlOfDirt = 0, + Seed = 1, + Sapling = 2, + Plant = 4, + FullGrownPlant = 7, + DecorativePlant = 10, + DeadTwigs = 11, + + Stage1 = 1, + Stage2 = 2, + Stage3 = 3, + Stage4 = 4, + Stage5 = 5, + Stage6 = 6, + Stage7 = 7, + Stage8 = 8, + Stage9 = 9 + } + + public class PlantItem : Item, ISecurable + { + /* + * Clients 7.0.12.0+ expect a container type in the plant label. + * To support older (and only older) clients, change this to false. + */ + private static readonly bool ShowContainerType = true; + private PlantHue m_PlantHue; + + private PlantStatus m_PlantStatus; + private PlantType m_PlantType; + private bool m_ShowType; + + [Constructible] + public PlantItem() : this(false) + { + } + + [Constructible] + public PlantItem(bool fertileDirt) : base(0x1602) + { + Weight = 1.0; + + m_PlantStatus = PlantStatus.BowlOfDirt; + PlantSystem = new PlantSystem(this, fertileDirt); + Level = SecureLevel.Owner; + + Plants.Add(this); + } + + public PlantItem(Serial serial) : base(serial) + { + } + + public PlantSystem PlantSystem{ get; private set; } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + [CommandProperty(AccessLevel.GameMaster)] + public PlantStatus PlantStatus + { + get => m_PlantStatus; + set + { + if (m_PlantStatus == value || value < PlantStatus.BowlOfDirt || value > PlantStatus.DeadTwigs) + return; + + double ratio; + if (PlantSystem != null) + ratio = (double)PlantSystem.Hits / PlantSystem.MaxHits; + else + ratio = 1.0; + + m_PlantStatus = value; + + if (m_PlantStatus >= PlantStatus.DecorativePlant) + { + PlantSystem = null; + } + else + { + if (PlantSystem == null) + PlantSystem = new PlantSystem(this, false); + + int hits = (int)(PlantSystem.MaxHits * ratio); + + if (hits == 0 && m_PlantStatus > PlantStatus.BowlOfDirt) + PlantSystem.Hits = hits + 1; + else + PlantSystem.Hits = hits; + } + + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public PlantType PlantType + { + get => m_PlantType; + set + { + m_PlantType = value; + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public PlantHue PlantHue + { + get => m_PlantHue; + set + { + m_PlantHue = value; + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool ShowType + { + get => m_ShowType; + set + { + m_ShowType = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool ValidGrowthLocation + { + get + { + if (IsLockedDown && RootParent == null) + return true; + + + if (!(RootParent is Mobile owner)) + return false; + + if (owner.Backpack != null && IsChildOf(owner.Backpack)) + return true; + + BankBox bank = owner.FindBankNoCreate(); + if (bank != null && IsChildOf(bank)) + return true; + + return false; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsGrowable => m_PlantStatus >= PlantStatus.BowlOfDirt && m_PlantStatus <= PlantStatus.Stage9; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsCrossable => PlantHueInfo.IsCrossable(PlantHue) && PlantTypeInfo.IsCrossable(PlantType); + + [CommandProperty(AccessLevel.GameMaster)] + public bool Reproduces => PlantHueInfo.CanReproduce(PlantHue) && PlantTypeInfo.CanReproduce(PlantType); + + public static ArrayList Plants{ get; } = new ArrayList(); + + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } + + public override void OnSingleClick(Mobile from) + { + if (m_PlantStatus >= PlantStatus.DeadTwigs) + LabelTo(from, LabelNumber); + else if (m_PlantStatus >= PlantStatus.DecorativePlant) + LabelTo(from, 1061924); // a decorative plant + else if (m_PlantStatus >= PlantStatus.FullGrownPlant) + LabelTo(from, PlantTypeInfo.GetInfo(m_PlantType).Name); + else + LabelTo(from, 1029913); // plant bowl + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } + + public int GetLocalizedPlantStatus() + { + if (m_PlantStatus >= PlantStatus.Plant) + return 1060812; // plant + if (m_PlantStatus >= PlantStatus.Sapling) + return 1023305; // sapling + if (m_PlantStatus >= PlantStatus.Seed) + return 1060810; // seed + return 1026951; // dirt + } + + public int GetLocalizedContainerType() + { + return 1150435; // bowl + } + + private void Update() + { + if (m_PlantStatus >= PlantStatus.DeadTwigs) + { + ItemID = 0x1B9D; + Hue = PlantHueInfo.GetInfo(m_PlantHue).Hue; + } + else if (m_PlantStatus >= PlantStatus.FullGrownPlant) + { + ItemID = PlantTypeInfo.GetInfo(m_PlantType).ItemID; + Hue = PlantHueInfo.GetInfo(m_PlantHue).Hue; + } + else if (m_PlantStatus >= PlantStatus.Plant) + { + ItemID = 0x1600; + Hue = 0; + } + else + { + ItemID = 0x1602; + Hue = 0; + } + + InvalidateProperties(); + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_PlantStatus >= PlantStatus.DeadTwigs) + { + base.AddNameProperty(list); + } + else if (m_PlantStatus < PlantStatus.Seed) + { + string args; + + if (ShowContainerType) + args = $"#{GetLocalizedContainerType()}\t#{PlantSystem.GetLocalizedDirtStatus()}"; + else + args = $"#{PlantSystem.GetLocalizedDirtStatus()}"; + + list.Add(1060830, args); // a ~1_val~ of ~2_val~ dirt + } + else + { + PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo(m_PlantType); + PlantHueInfo hueInfo = PlantHueInfo.GetInfo(m_PlantHue); + + if (m_PlantStatus >= PlantStatus.DecorativePlant) + { + list.Add(typeInfo.GetPlantLabelDecorative(hueInfo), $"#{hueInfo.Name}\t#{typeInfo.Name}"); + } + else if (m_PlantStatus >= PlantStatus.FullGrownPlant) + { + list.Add(typeInfo.GetPlantLabelFullGrown(hueInfo), + $"#{PlantSystem.GetLocalizedHealth()}\t#{hueInfo.Name}\t#{typeInfo.Name}"); + } + else + { + string args; + + if (ShowContainerType) + args = + $"#{GetLocalizedContainerType()}\t#{PlantSystem.GetLocalizedDirtStatus()}\t#{PlantSystem.GetLocalizedHealth()}"; + else + args = $"#{PlantSystem.GetLocalizedDirtStatus()}\t#{PlantSystem.GetLocalizedHealth()}"; + + if (m_ShowType) + { + args += $"\t#{hueInfo.Name}\t#{typeInfo.Name}\t#{GetLocalizedPlantStatus()}"; + + if (m_PlantStatus == PlantStatus.Plant) + list.Add(typeInfo.GetPlantLabelPlant(hueInfo), args); + else + list.Add(typeInfo.GetPlantLabelSeed(hueInfo), args); + } + else + { + args += + $"\t#{(typeInfo.PlantCategory == PlantCategory.Default ? hueInfo.Name : (int)typeInfo.PlantCategory)}\t#{GetLocalizedPlantStatus()}"; + + list.Add(hueInfo.IsBright() ? 1060832 : 1060831, + args); // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ + } + } + } + } + + public bool IsUsableBy(Mobile from) + { + return IsChildOf(from.Backpack) || IsChildOf(from.FindBankNoCreate()) || IsLockedDown && IsAccessibleTo(from) || + RootParent is Item root && root.IsSecure && root.IsAccessibleTo(from); + } + + public override void OnDoubleClick(Mobile from) + { + if (m_PlantStatus >= PlantStatus.DecorativePlant) + return; + + Point3D loc = GetWorldLocation(); + + if (!from.InLOS(loc) || !from.InRange(loc, 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 1019045); // I can't reach that. + return; + } + + if (!IsUsableBy(from)) + { + LabelTo(from, 1061856); // You must have the item in your backpack or locked down in order to use it. + return; + } + + from.SendGump(new MainPlantGump(this)); + } + + public void PlantSeed(Mobile from, Seed seed) + { + if (m_PlantStatus >= PlantStatus.FullGrownPlant) + { + LabelTo(from, 1061919); // You must use a seed on some prepared soil! + } + else if (!IsUsableBy(from)) + { + LabelTo(from, 1061921); // The bowl of dirt must be in your pack, or you must lock it down. + } + else if (m_PlantStatus != PlantStatus.BowlOfDirt) + { + from.SendLocalizedMessage(1080389, + "#" + GetLocalizedPlantStatus()); // This bowl of dirt already has a ~1_val~ in it! + } + else if (PlantSystem.Water < 2) + { + LabelTo(from, 1061920); // The dirt needs to be softened first. + } + else + { + m_PlantType = seed.PlantType; + m_PlantHue = seed.PlantHue; + m_ShowType = seed.ShowType; + + seed.Consume(); + + PlantStatus = PlantStatus.Seed; + + PlantSystem.Reset(false); + + LabelTo(from, 1061922); // You plant the seed in the bowl of dirt. + } + } + + public void Die() + { + if (m_PlantStatus >= PlantStatus.FullGrownPlant) + { + PlantStatus = PlantStatus.DeadTwigs; + } + else + { + PlantStatus = PlantStatus.BowlOfDirt; + PlantSystem.Reset(true); + } + } + + public void Pour(Mobile from, Item item) + { + if (m_PlantStatus >= PlantStatus.DeadTwigs) + return; + + if (m_PlantStatus == PlantStatus.DecorativePlant) + { + LabelTo(from, 1053049); // This is a decorative plant, it does not need watering! + return; + } + + if (!IsUsableBy(from)) + { + LabelTo(from, 1061856); // You must have the item in your backpack or locked down in order to use it. + return; + } + + if (item is BaseBeverage beverage) + { + if (beverage.IsEmpty || !beverage.Pourable || beverage.Content != BeverageType.Water) + { + LabelTo(from, 1053069); // You can't use that on a plant! + return; + } + + if (!beverage.ValidateUse(from, true)) + return; + + beverage.Quantity--; + PlantSystem.Water++; + + from.PlaySound(0x4E); + LabelTo(from, 1061858); // You soften the dirt with water. + } + else if (item is BasePotion potion) + { + if (ApplyPotion(potion.PotionEffect, false, out int message)) + { + potion.Consume(); + from.PlaySound(0x240); + from.AddToBackpack(new Bottle()); + } + + LabelTo(from, message); + } + else if (item is PotionKeg keg) + { + if (keg.Held <= 0) + { + LabelTo(from, 1053069); // You can't use that on a plant! + return; + } + + if (ApplyPotion(keg.Type, false, out int message)) + { + keg.Held--; + from.PlaySound(0x240); + } + + LabelTo(from, message); + } + else + { + LabelTo(from, 1053069); // You can't use that on a plant! + } + } + + public bool ApplyPotion(PotionEffect effect, bool testOnly, out int message) + { + if (m_PlantStatus >= PlantStatus.DecorativePlant) + { + message = 1053049; // This is a decorative plant, it does not need watering! + return false; + } + + if (m_PlantStatus == PlantStatus.BowlOfDirt) + { + message = 1053066; // You should only pour potions on a plant or seed! + return false; + } + + bool full = false; + + if (effect == PotionEffect.PoisonGreater || effect == PotionEffect.PoisonDeadly) + { + if (PlantSystem.IsFullPoisonPotion) + full = true; + else if (!testOnly) + PlantSystem.PoisonPotion++; + } + else if (effect == PotionEffect.CureGreater) + { + if (PlantSystem.IsFullCurePotion) + full = true; + else if (!testOnly) + PlantSystem.CurePotion++; + } + else if (effect == PotionEffect.HealGreater) + { + if (PlantSystem.IsFullHealPotion) + full = true; + else if (!testOnly) + PlantSystem.HealPotion++; + } + else if (effect == PotionEffect.StrengthGreater) + { + if (PlantSystem.IsFullStrengthPotion) + full = true; + else if (!testOnly) + PlantSystem.StrengthPotion++; + } + else if (effect == PotionEffect.PoisonLesser || effect == PotionEffect.Poison || + effect == PotionEffect.CureLesser || effect == PotionEffect.Cure || + effect == PotionEffect.HealLesser || effect == PotionEffect.Heal || effect == PotionEffect.Strength) + { + message = 1053068; // This potion is not powerful enough to use on a plant! + return false; + } + else + { + message = 1053069; // You can't use that on a plant! + return false; + } + + if (full) + { + message = 1053065; // The plant is already soaked with this type of potion! + return false; + } + + message = 1053067; // You pour the potion over the plant. + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + + writer.Write((int)Level); + + writer.Write((int)m_PlantStatus); + writer.Write((int)m_PlantType); + writer.Write((int)m_PlantHue); + writer.Write(m_ShowType); + + if (m_PlantStatus < PlantStatus.DecorativePlant) + PlantSystem.Save(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: + case 1: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 0; + } + case 0: + { + if (version < 1) + Level = SecureLevel.CoOwners; + + m_PlantStatus = (PlantStatus)reader.ReadInt(); + m_PlantType = (PlantType)reader.ReadInt(); + m_PlantHue = (PlantHue)reader.ReadInt(); + m_ShowType = reader.ReadBool(); + + if (m_PlantStatus < PlantStatus.DecorativePlant) + PlantSystem = new PlantSystem(this, reader); + + if (version < 2 && PlantHueInfo.IsCrossable(m_PlantHue)) + m_PlantHue |= PlantHue.Reproduces; + + break; + } + } + + Plants.Add(this); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + Plants.Remove(this); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantPourTarget.cs b/Scripts/Engines/Plants/PlantPourTarget.cs index c7b2742d0..0fd47354b 100644 --- a/Scripts/Engines/Plants/PlantPourTarget.cs +++ b/Scripts/Engines/Plants/PlantPourTarget.cs @@ -2,32 +2,31 @@ using Server.Targeting; namespace Server.Engines.Plants { - public class PlantPourTarget : Target - { - private PlantItem m_Plant; + public class PlantPourTarget : Target + { + private PlantItem m_Plant; - public PlantPourTarget( PlantItem plant ) : base( 3, true, TargetFlags.None ) - { - m_Plant = plant; - } + public PlantPourTarget(PlantItem plant) : base(3, true, TargetFlags.None) + { + m_Plant = plant; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Plant.Deleted && from.InRange( m_Plant.GetWorldLocation(), 3 ) && targeted is Item item ) - { - m_Plant.Pour( from, item ); - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Plant.Deleted && from.InRange(m_Plant.GetWorldLocation(), 3) && targeted is Item item) + m_Plant.Pour(from, item); + } - protected override void OnTargetFinish( Mobile from ) - { - if ( !m_Plant.Deleted && m_Plant.PlantStatus < PlantStatus.DecorativePlant && from.InRange( m_Plant.GetWorldLocation(), 3 ) && m_Plant.IsUsableBy( from ) ) - { - if ( from.HasGump( typeof( MainPlantGump ) ) ) - from.CloseGump( typeof( MainPlantGump ) ); + protected override void OnTargetFinish(Mobile from) + { + if (!m_Plant.Deleted && m_Plant.PlantStatus < PlantStatus.DecorativePlant && + from.InRange(m_Plant.GetWorldLocation(), 3) && m_Plant.IsUsableBy(from)) + { + if (from.HasGump(typeof(MainPlantGump))) + from.CloseGump(typeof(MainPlantGump)); - from.SendGump( new MainPlantGump( m_Plant ) ); - } - } - } -} + from.SendGump(new MainPlantGump(m_Plant)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantResources.cs b/Scripts/Engines/Plants/PlantResources.cs index f2f18a3cf..cf6bc3356 100644 --- a/Scripts/Engines/Plants/PlantResources.cs +++ b/Scripts/Engines/Plants/PlantResources.cs @@ -3,47 +3,46 @@ using Server.Items; namespace Server.Engines.Plants { - public class PlantResourceInfo - { - private static PlantResourceInfo[] m_ResourceList = { - new PlantResourceInfo( PlantType.ElephantEarPlant, PlantHue.BrightRed, typeof( RedLeaves ) ), - new PlantResourceInfo( PlantType.PonytailPalm, PlantHue.BrightRed, typeof( RedLeaves ) ), - new PlantResourceInfo( PlantType.CenturyPlant, PlantHue.BrightRed, typeof( RedLeaves ) ), - new PlantResourceInfo( PlantType.Poppies, PlantHue.BrightOrange, typeof( OrangePetals ) ), - new PlantResourceInfo( PlantType.Bulrushes, PlantHue.BrightOrange, typeof( OrangePetals ) ), - new PlantResourceInfo( PlantType.PampasGrass, PlantHue.BrightOrange, typeof( OrangePetals ) ), - new PlantResourceInfo( PlantType.SnakePlant, PlantHue.BrightGreen, typeof( GreenThorns ) ), - new PlantResourceInfo( PlantType.BarrelCactus, PlantHue.BrightGreen, typeof( GreenThorns ) ), - new PlantResourceInfo( PlantType.CocoaTree, PlantHue.Plain, typeof( CocoaPulp ) ) - }; + public class PlantResourceInfo + { + private static PlantResourceInfo[] m_ResourceList = + { + new PlantResourceInfo(PlantType.ElephantEarPlant, PlantHue.BrightRed, typeof(RedLeaves)), + new PlantResourceInfo(PlantType.PonytailPalm, PlantHue.BrightRed, typeof(RedLeaves)), + new PlantResourceInfo(PlantType.CenturyPlant, PlantHue.BrightRed, typeof(RedLeaves)), + new PlantResourceInfo(PlantType.Poppies, PlantHue.BrightOrange, typeof(OrangePetals)), + new PlantResourceInfo(PlantType.Bulrushes, PlantHue.BrightOrange, typeof(OrangePetals)), + new PlantResourceInfo(PlantType.PampasGrass, PlantHue.BrightOrange, typeof(OrangePetals)), + new PlantResourceInfo(PlantType.SnakePlant, PlantHue.BrightGreen, typeof(GreenThorns)), + new PlantResourceInfo(PlantType.BarrelCactus, PlantHue.BrightGreen, typeof(GreenThorns)), + new PlantResourceInfo(PlantType.CocoaTree, PlantHue.Plain, typeof(CocoaPulp)) + }; - public static PlantResourceInfo GetInfo( PlantType plantType, PlantHue plantHue ) - { - foreach ( PlantResourceInfo info in m_ResourceList ) - { - if ( info.PlantType == plantType && info.PlantHue == plantHue ) - return info; - } + private PlantResourceInfo(PlantType plantType, PlantHue plantHue, Type resourceType) + { + PlantType = plantType; + PlantHue = plantHue; + ResourceType = resourceType; + } - return null; - } + public PlantType PlantType{ get; } - public PlantType PlantType { get; } + public PlantHue PlantHue{ get; } - public PlantHue PlantHue { get; } + public Type ResourceType{ get; } - public Type ResourceType { get; } + public static PlantResourceInfo GetInfo(PlantType plantType, PlantHue plantHue) + { + foreach (PlantResourceInfo info in m_ResourceList) + if (info.PlantType == plantType && info.PlantHue == plantHue) + return info; - private PlantResourceInfo( PlantType plantType, PlantHue plantHue, Type resourceType ) - { - PlantType = plantType; - PlantHue = plantHue; - ResourceType = resourceType; - } + return null; + } - public Item CreateResource() - { - return (Item)Activator.CreateInstance( ResourceType ); - } - } -} + public Item CreateResource() + { + return (Item)Activator.CreateInstance(ResourceType); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantSystem.cs b/Scripts/Engines/Plants/PlantSystem.cs index b64969c13..bcedd984d 100644 --- a/Scripts/Engines/Plants/PlantSystem.cs +++ b/Scripts/Engines/Plants/PlantSystem.cs @@ -1,685 +1,694 @@ using System; using System.Collections; -using Server.Items; using System.Collections.Generic; +using Server.Items; +using Server.Misc; namespace Server.Engines.Plants { - public enum PlantHealth - { - Dying, - Wilted, - Healthy, - Vibrant - } - - public enum PlantGrowthIndicator - { - None, - InvalidLocation, - NotHealthy, - Delay, - Grown, - DoubleGrown - } - - public class PlantSystem - { - public static readonly TimeSpan CheckDelay = TimeSpan.FromHours( 23.0 ); - - private int m_Water; - - private int m_Hits; - private int m_Infestation; - private int m_Fungus; - private int m_Poison; - private int m_Disease; - private int m_PoisonPotion; - private int m_CurePotion; - private int m_HealPotion; - private int m_StrengthPotion; - - private PlantType m_SeedType; - private PlantHue m_SeedHue; - private int m_AvailableSeeds; - private int m_LeftSeeds; - - private int m_AvailableResources; - private int m_LeftResources; - - public PlantItem Plant { get; } - - public bool FertileDirt { get; set; } - - public DateTime NextGrowth { get; private set; } - - public PlantGrowthIndicator GrowthIndicator { get; private set; } - - public bool IsFullWater => m_Water >= 4; - - public int Water - { - get => m_Water; - set - { - if ( value < 0 ) - m_Water = 0; - else if ( value > 4 ) - m_Water = 4; - else - m_Water = value; - - Plant.InvalidateProperties(); - } - } - - public int Hits - { - get => m_Hits; - set - { - if ( m_Hits == value ) - return; - - if ( value < 0 ) - m_Hits = 0; - else if ( value > MaxHits ) - m_Hits = MaxHits; - else - m_Hits = value; - - if ( m_Hits == 0 ) - Plant.Die(); - - Plant.InvalidateProperties(); - } - } - - public int MaxHits => 10 + (int)Plant.PlantStatus * 2; - - public PlantHealth Health - { - get - { - int perc = m_Hits * 100 / MaxHits; - - if ( perc < 33 ) - return PlantHealth.Dying; - if ( perc < 66 ) - return PlantHealth.Wilted; - if ( perc < 100 ) - return PlantHealth.Healthy; - return PlantHealth.Vibrant; - } - } - - public int Infestation - { - get => m_Infestation; - set - { - if ( value < 0 ) - m_Infestation = 0; - else if ( value > 2 ) - m_Infestation = 2; - else - m_Infestation = value; - } - } - - public int Fungus - { - get => m_Fungus; - set - { - if ( value < 0 ) - m_Fungus = 0; - else if ( value > 2 ) - m_Fungus = 2; - else - m_Fungus = value; - } - } - - public int Poison - { - get => m_Poison; - set - { - if ( value < 0 ) - m_Poison = 0; - else if ( value > 2 ) - m_Poison = 2; - else - m_Poison = value; - } - } - - public int Disease - { - get => m_Disease; - set - { - if ( value < 0 ) - m_Disease = 0; - else if ( value > 2 ) - m_Disease = 2; - else - m_Disease = value; - } - } - - public bool IsFullPoisonPotion => m_PoisonPotion >= 2; - - public int PoisonPotion - { - get => m_PoisonPotion; - set - { - if ( value < 0 ) - m_PoisonPotion = 0; - else if ( value > 2 ) - m_PoisonPotion = 2; - else - m_PoisonPotion = value; - } - } - - public bool IsFullCurePotion => m_CurePotion >= 2; - - public int CurePotion - { - get => m_CurePotion; - set - { - if ( value < 0 ) - m_CurePotion = 0; - else if ( value > 2 ) - m_CurePotion = 2; - else - m_CurePotion = value; - } - } - - public bool IsFullHealPotion => m_HealPotion >= 2; - - public int HealPotion - { - get => m_HealPotion; - set - { - if ( value < 0 ) - m_HealPotion = 0; - else if ( value > 2 ) - m_HealPotion = 2; - else - m_HealPotion = value; - } - } - - public bool IsFullStrengthPotion => m_StrengthPotion >= 2; - - public int StrengthPotion - { - get => m_StrengthPotion; - set - { - if ( value < 0 ) - m_StrengthPotion = 0; - else if ( value > 2 ) - m_StrengthPotion = 2; - else - m_StrengthPotion = value; - } - } - - public bool HasMaladies => Infestation > 0 || Fungus > 0 || Poison > 0 || Disease > 0 || Water != 2; - - public bool PollenProducing => Plant.IsCrossable && Plant.PlantStatus >= PlantStatus.FullGrownPlant; - - public bool Pollinated { get; set; } - - public PlantType SeedType - { - get - { - if ( Pollinated ) - return m_SeedType; - return Plant.PlantType; - } - set => m_SeedType = value; - } - - public PlantHue SeedHue - { - get - { - if ( Pollinated ) - return m_SeedHue; - return Plant.PlantHue; - } - set => m_SeedHue = value; - } - - public int AvailableSeeds - { - get => m_AvailableSeeds; - set { if ( value >= 0 ) m_AvailableSeeds = value; } - } - - public int LeftSeeds - { - get => m_LeftSeeds; - set { if ( value >= 0 ) m_LeftSeeds = value; } - } - - public int AvailableResources - { - get => m_AvailableResources; - set { if ( value >= 0 ) m_AvailableResources = value; } - } - - public int LeftResources - { - get => m_LeftResources; - set { if ( value >= 0 ) m_LeftResources = value; } - } - - public PlantSystem( PlantItem plant, bool fertileDirt ) - { - Plant = plant; - FertileDirt = fertileDirt; - - NextGrowth = DateTime.UtcNow + CheckDelay; - GrowthIndicator = PlantGrowthIndicator.None; - m_Hits = MaxHits; - m_LeftSeeds = 8; - m_LeftResources = 8; - } - - public void Reset( bool potions ) - { - NextGrowth = DateTime.UtcNow + CheckDelay; - GrowthIndicator = PlantGrowthIndicator.None; - - Hits = MaxHits; - m_Infestation = 0; - m_Fungus = 0; - m_Poison = 0; - m_Disease = 0; - - if ( potions ) - { - m_PoisonPotion = 0; - m_CurePotion = 0; - m_HealPotion = 0; - m_StrengthPotion = 0; - } - - Pollinated = false; - m_AvailableSeeds = 0; - m_LeftSeeds = 8; - - m_AvailableResources = 0; - m_LeftResources = 8; - } - - public int GetLocalizedDirtStatus() - { - if ( Water <= 1 ) - return 1060826; // hard - if ( Water <= 2 ) - return 1060827; // soft - if ( Water <= 3 ) - return 1060828; // squishy - return 1060829; // sopping wet - } - - public int GetLocalizedHealth() - { - switch ( Health ) - { - case PlantHealth.Dying: return 1060825; // dying - case PlantHealth.Wilted: return 1060824; // wilted - case PlantHealth.Healthy: return 1060823; // healthy - default: return 1060822; // vibrant - } - } - - public static void Configure() - { - EventSink.WorldLoad += EventSink_WorldLoad; - - if ( !Misc.AutoRestart.Enabled ) - EventSink.WorldSave += EventSink_WorldSave; - - EventSink.Login += EventSink_Login; - } - - private static void EventSink_Login( LoginEventArgs args ) - { - Mobile from = args.Mobile; - - if ( from.Backpack != null ) - { - List plants = from.Backpack.FindItemsByType(); - - foreach ( PlantItem plant in plants ) - { - if ( plant.IsGrowable ) - plant.PlantSystem.DoGrowthCheck(); - } - } - - BankBox bank = from.FindBankNoCreate(); - - if ( bank != null ) - { - List plants = bank.FindItemsByType(); - - foreach ( PlantItem plant in plants ) - { - if ( plant.IsGrowable ) - plant.PlantSystem.DoGrowthCheck(); - } - } - } - - public static void GrowAll() - { - ArrayList plants = PlantItem.Plants; - DateTime now = DateTime.UtcNow; - - for ( int i = plants.Count - 1; i >= 0; --i ) - { - PlantItem plant = (PlantItem) plants[i]; - - if ( plant.IsGrowable && (plant.RootParent as Mobile) == null && now >= plant.PlantSystem.NextGrowth ) - plant.PlantSystem.DoGrowthCheck(); - } - } - - private static void EventSink_WorldLoad() - { - GrowAll(); - } - - private static void EventSink_WorldSave( WorldSaveEventArgs args) - { - GrowAll(); - } - - public void DoGrowthCheck() - { - if ( !Plant.IsGrowable ) - return; - - if ( DateTime.UtcNow < NextGrowth ) - { - GrowthIndicator = PlantGrowthIndicator.Delay; - return; - } - - NextGrowth = DateTime.UtcNow + CheckDelay; - - if ( !Plant.ValidGrowthLocation ) - { - GrowthIndicator = PlantGrowthIndicator.InvalidLocation; - return; - } - - if ( Plant.PlantStatus == PlantStatus.BowlOfDirt) - { - if ( Water > 2 || Utility.RandomDouble() < 0.9 ) - Water--; - return; - } - - ApplyBeneficEffects(); - - if ( !ApplyMaladiesEffects() ) // Dead - return; - - Grow(); - - UpdateMaladies(); - } - - private void ApplyBeneficEffects() - { - if ( PoisonPotion >= Infestation ) - { - PoisonPotion -= Infestation; - Infestation = 0; - } - else - { - Infestation -= PoisonPotion; - PoisonPotion = 0; - } - - if ( CurePotion >= Fungus ) - { - CurePotion -= Fungus; - Fungus = 0; - } - else - { - Fungus -= CurePotion; - CurePotion = 0; - } - - if ( HealPotion >= Poison ) - { - HealPotion -= Poison; - Poison = 0; - } - else - { - Poison -= HealPotion; - HealPotion = 0; - } - - if ( HealPotion >= Disease ) - { - HealPotion -= Disease; - Disease = 0; - } - else - { - Disease -= HealPotion; - HealPotion = 0; - } - - if ( !HasMaladies ) - { - if ( HealPotion > 0 ) - Hits += HealPotion * 7; - else - Hits += 2; - } - - HealPotion = 0; - } - - private bool ApplyMaladiesEffects() - { - int damage = 0; - - if ( Infestation > 0 ) - damage += Infestation * Utility.RandomMinMax( 3, 6 ); - - if ( Fungus > 0 ) - damage += Fungus * Utility.RandomMinMax( 3, 6 ); - - if ( Poison > 0 ) - damage += Poison * Utility.RandomMinMax( 3, 6 ); - - if ( Disease > 0 ) - damage += Disease * Utility.RandomMinMax( 3, 6 ); - - if ( Water > 2 ) - damage += ( Water - 2 ) * Utility.RandomMinMax( 3, 6 ); - else if ( Water < 2 ) - damage += ( 2 - Water ) * Utility.RandomMinMax( 3, 6 ); - - Hits -= damage; - - return Plant.IsGrowable && Plant.PlantStatus != PlantStatus.BowlOfDirt; - } - - private void Grow() - { - if ( Health < PlantHealth.Healthy ) - { - GrowthIndicator = PlantGrowthIndicator.NotHealthy; - } - else if ( FertileDirt && Plant.PlantStatus <= PlantStatus.Stage5 && Utility.RandomDouble() < 0.1 ) - { - int curStage = (int)Plant.PlantStatus; - Plant.PlantStatus = (PlantStatus)( curStage + 2 ); - - GrowthIndicator = PlantGrowthIndicator.DoubleGrown; - } - else if ( Plant.PlantStatus < PlantStatus.Stage9 ) - { - int curStage = (int)Plant.PlantStatus; - Plant.PlantStatus = (PlantStatus)( curStage + 1 ); - - GrowthIndicator = PlantGrowthIndicator.Grown; - } - else - { - if ( Pollinated && LeftSeeds > 0 && Plant.Reproduces ) - { - LeftSeeds--; - AvailableSeeds++; - } - - if ( LeftResources > 0 && PlantResourceInfo.GetInfo( Plant.PlantType, Plant.PlantHue ) != null ) - { - LeftResources--; - AvailableResources++; - } - - GrowthIndicator = PlantGrowthIndicator.Grown; - } - - if ( Plant.PlantStatus >= PlantStatus.Stage9 && !Pollinated ) - { - Pollinated = true; - SeedType = Plant.PlantType; - SeedHue = Plant.PlantHue; - } - } - - private void UpdateMaladies() - { - double infestationChance = 0.30 - StrengthPotion * 0.075 + ( Water - 2 ) * 0.10; - - PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo( Plant.PlantType ); - if ( typeInfo.Flowery ) - infestationChance += 0.10; - - if ( PlantHueInfo.IsBright( Plant.PlantHue ) ) - infestationChance += 0.10; - - if ( Utility.RandomDouble() < infestationChance ) - Infestation++; - - - double fungusChance = 0.15 - StrengthPotion * 0.075 + ( Water - 2 ) * 0.10; - - if ( Utility.RandomDouble() < fungusChance ) - Fungus++; - - if ( Water > 2 || Utility.RandomDouble() < 0.9 ) - Water--; - - if ( PoisonPotion > 0 ) - { - Poison += PoisonPotion; - PoisonPotion = 0; - } - - if ( CurePotion > 0 ) - { - Disease += CurePotion; - CurePotion = 0; - } - - StrengthPotion = 0; - } - - public void Save( GenericWriter writer ) - { - writer.Write( (int) 2 ); // version - - writer.Write( (bool) FertileDirt ); - - writer.Write( (DateTime) NextGrowth ); - writer.Write( (int) GrowthIndicator ); - - writer.Write( (int) m_Water ); - - writer.Write( (int) m_Hits ); - writer.Write( (int) m_Infestation ); - writer.Write( (int) m_Fungus ); - writer.Write( (int) m_Poison ); - writer.Write( (int) m_Disease ); - writer.Write( (int) m_PoisonPotion ); - writer.Write( (int) m_CurePotion ); - writer.Write( (int) m_HealPotion ); - writer.Write( (int) m_StrengthPotion ); - - writer.Write( (bool) Pollinated ); - writer.Write( (int) m_SeedType ); - writer.Write( (int) m_SeedHue ); - writer.Write( (int) m_AvailableSeeds ); - writer.Write( (int) m_LeftSeeds ); - - writer.Write( (int) m_AvailableResources ); - writer.Write( (int) m_LeftResources ); - } - - public PlantSystem( PlantItem plant, GenericReader reader ) - { - Plant = plant; - - int version = reader.ReadInt(); - - FertileDirt = reader.ReadBool(); - - if ( version >= 1 ) - NextGrowth = reader.ReadDateTime(); - else - NextGrowth = reader.ReadDeltaTime(); - - GrowthIndicator = (PlantGrowthIndicator)reader.ReadInt(); - - m_Water = reader.ReadInt(); - - m_Hits = reader.ReadInt(); - m_Infestation = reader.ReadInt(); - m_Fungus = reader.ReadInt(); - m_Poison = reader.ReadInt(); - m_Disease = reader.ReadInt(); - m_PoisonPotion = reader.ReadInt(); - m_CurePotion = reader.ReadInt(); - m_HealPotion = reader.ReadInt(); - m_StrengthPotion = reader.ReadInt(); - - Pollinated = reader.ReadBool(); - m_SeedType = (PlantType)reader.ReadInt(); - m_SeedHue = (PlantHue)reader.ReadInt(); - m_AvailableSeeds = reader.ReadInt(); - m_LeftSeeds = reader.ReadInt(); - - m_AvailableResources = reader.ReadInt(); - m_LeftResources = reader.ReadInt(); - - if ( version < 2 && PlantHueInfo.IsCrossable( m_SeedHue ) ) - m_SeedHue |= PlantHue.Reproduces; - } - } -} + public enum PlantHealth + { + Dying, + Wilted, + Healthy, + Vibrant + } + + public enum PlantGrowthIndicator + { + None, + InvalidLocation, + NotHealthy, + Delay, + Grown, + DoubleGrown + } + + public class PlantSystem + { + public static readonly TimeSpan CheckDelay = TimeSpan.FromHours(23.0); + + private int m_AvailableResources; + private int m_AvailableSeeds; + private int m_CurePotion; + private int m_Disease; + private int m_Fungus; + private int m_HealPotion; + + private int m_Hits; + private int m_Infestation; + private int m_LeftResources; + private int m_LeftSeeds; + private int m_Poison; + private int m_PoisonPotion; + private PlantHue m_SeedHue; + + private PlantType m_SeedType; + private int m_StrengthPotion; + + private int m_Water; + + public PlantSystem(PlantItem plant, bool fertileDirt) + { + Plant = plant; + FertileDirt = fertileDirt; + + NextGrowth = DateTime.UtcNow + CheckDelay; + GrowthIndicator = PlantGrowthIndicator.None; + m_Hits = MaxHits; + m_LeftSeeds = 8; + m_LeftResources = 8; + } + + public PlantSystem(PlantItem plant, GenericReader reader) + { + Plant = plant; + + int version = reader.ReadInt(); + + FertileDirt = reader.ReadBool(); + + if (version >= 1) + NextGrowth = reader.ReadDateTime(); + else + NextGrowth = reader.ReadDeltaTime(); + + GrowthIndicator = (PlantGrowthIndicator)reader.ReadInt(); + + m_Water = reader.ReadInt(); + + m_Hits = reader.ReadInt(); + m_Infestation = reader.ReadInt(); + m_Fungus = reader.ReadInt(); + m_Poison = reader.ReadInt(); + m_Disease = reader.ReadInt(); + m_PoisonPotion = reader.ReadInt(); + m_CurePotion = reader.ReadInt(); + m_HealPotion = reader.ReadInt(); + m_StrengthPotion = reader.ReadInt(); + + Pollinated = reader.ReadBool(); + m_SeedType = (PlantType)reader.ReadInt(); + m_SeedHue = (PlantHue)reader.ReadInt(); + m_AvailableSeeds = reader.ReadInt(); + m_LeftSeeds = reader.ReadInt(); + + m_AvailableResources = reader.ReadInt(); + m_LeftResources = reader.ReadInt(); + + if (version < 2 && PlantHueInfo.IsCrossable(m_SeedHue)) + m_SeedHue |= PlantHue.Reproduces; + } + + public PlantItem Plant{ get; } + + public bool FertileDirt{ get; set; } + + public DateTime NextGrowth{ get; private set; } + + public PlantGrowthIndicator GrowthIndicator{ get; private set; } + + public bool IsFullWater => m_Water >= 4; + + public int Water + { + get => m_Water; + set + { + if (value < 0) + m_Water = 0; + else if (value > 4) + m_Water = 4; + else + m_Water = value; + + Plant.InvalidateProperties(); + } + } + + public int Hits + { + get => m_Hits; + set + { + if (m_Hits == value) + return; + + if (value < 0) + m_Hits = 0; + else if (value > MaxHits) + m_Hits = MaxHits; + else + m_Hits = value; + + if (m_Hits == 0) + Plant.Die(); + + Plant.InvalidateProperties(); + } + } + + public int MaxHits => 10 + (int)Plant.PlantStatus * 2; + + public PlantHealth Health + { + get + { + int perc = m_Hits * 100 / MaxHits; + + if (perc < 33) + return PlantHealth.Dying; + if (perc < 66) + return PlantHealth.Wilted; + if (perc < 100) + return PlantHealth.Healthy; + return PlantHealth.Vibrant; + } + } + + public int Infestation + { + get => m_Infestation; + set + { + if (value < 0) + m_Infestation = 0; + else if (value > 2) + m_Infestation = 2; + else + m_Infestation = value; + } + } + + public int Fungus + { + get => m_Fungus; + set + { + if (value < 0) + m_Fungus = 0; + else if (value > 2) + m_Fungus = 2; + else + m_Fungus = value; + } + } + + public int Poison + { + get => m_Poison; + set + { + if (value < 0) + m_Poison = 0; + else if (value > 2) + m_Poison = 2; + else + m_Poison = value; + } + } + + public int Disease + { + get => m_Disease; + set + { + if (value < 0) + m_Disease = 0; + else if (value > 2) + m_Disease = 2; + else + m_Disease = value; + } + } + + public bool IsFullPoisonPotion => m_PoisonPotion >= 2; + + public int PoisonPotion + { + get => m_PoisonPotion; + set + { + if (value < 0) + m_PoisonPotion = 0; + else if (value > 2) + m_PoisonPotion = 2; + else + m_PoisonPotion = value; + } + } + + public bool IsFullCurePotion => m_CurePotion >= 2; + + public int CurePotion + { + get => m_CurePotion; + set + { + if (value < 0) + m_CurePotion = 0; + else if (value > 2) + m_CurePotion = 2; + else + m_CurePotion = value; + } + } + + public bool IsFullHealPotion => m_HealPotion >= 2; + + public int HealPotion + { + get => m_HealPotion; + set + { + if (value < 0) + m_HealPotion = 0; + else if (value > 2) + m_HealPotion = 2; + else + m_HealPotion = value; + } + } + + public bool IsFullStrengthPotion => m_StrengthPotion >= 2; + + public int StrengthPotion + { + get => m_StrengthPotion; + set + { + if (value < 0) + m_StrengthPotion = 0; + else if (value > 2) + m_StrengthPotion = 2; + else + m_StrengthPotion = value; + } + } + + public bool HasMaladies => Infestation > 0 || Fungus > 0 || Poison > 0 || Disease > 0 || Water != 2; + + public bool PollenProducing => Plant.IsCrossable && Plant.PlantStatus >= PlantStatus.FullGrownPlant; + + public bool Pollinated{ get; set; } + + public PlantType SeedType + { + get + { + if (Pollinated) + return m_SeedType; + return Plant.PlantType; + } + set => m_SeedType = value; + } + + public PlantHue SeedHue + { + get + { + if (Pollinated) + return m_SeedHue; + return Plant.PlantHue; + } + set => m_SeedHue = value; + } + + public int AvailableSeeds + { + get => m_AvailableSeeds; + set + { + if (value >= 0) m_AvailableSeeds = value; + } + } + + public int LeftSeeds + { + get => m_LeftSeeds; + set + { + if (value >= 0) m_LeftSeeds = value; + } + } + + public int AvailableResources + { + get => m_AvailableResources; + set + { + if (value >= 0) m_AvailableResources = value; + } + } + + public int LeftResources + { + get => m_LeftResources; + set + { + if (value >= 0) m_LeftResources = value; + } + } + + public void Reset(bool potions) + { + NextGrowth = DateTime.UtcNow + CheckDelay; + GrowthIndicator = PlantGrowthIndicator.None; + + Hits = MaxHits; + m_Infestation = 0; + m_Fungus = 0; + m_Poison = 0; + m_Disease = 0; + + if (potions) + { + m_PoisonPotion = 0; + m_CurePotion = 0; + m_HealPotion = 0; + m_StrengthPotion = 0; + } + + Pollinated = false; + m_AvailableSeeds = 0; + m_LeftSeeds = 8; + + m_AvailableResources = 0; + m_LeftResources = 8; + } + + public int GetLocalizedDirtStatus() + { + if (Water <= 1) + return 1060826; // hard + if (Water <= 2) + return 1060827; // soft + if (Water <= 3) + return 1060828; // squishy + return 1060829; // sopping wet + } + + public int GetLocalizedHealth() + { + switch (Health) + { + case PlantHealth.Dying: return 1060825; // dying + case PlantHealth.Wilted: return 1060824; // wilted + case PlantHealth.Healthy: return 1060823; // healthy + default: return 1060822; // vibrant + } + } + + public static void Configure() + { + EventSink.WorldLoad += EventSink_WorldLoad; + + if (!AutoRestart.Enabled) + EventSink.WorldSave += EventSink_WorldSave; + + EventSink.Login += EventSink_Login; + } + + private static void EventSink_Login(LoginEventArgs args) + { + Mobile from = args.Mobile; + + if (from.Backpack != null) + { + List plants = from.Backpack.FindItemsByType(); + + foreach (PlantItem plant in plants) + if (plant.IsGrowable) + plant.PlantSystem.DoGrowthCheck(); + } + + BankBox bank = from.FindBankNoCreate(); + + if (bank != null) + { + List plants = bank.FindItemsByType(); + + foreach (PlantItem plant in plants) + if (plant.IsGrowable) + plant.PlantSystem.DoGrowthCheck(); + } + } + + public static void GrowAll() + { + ArrayList plants = PlantItem.Plants; + DateTime now = DateTime.UtcNow; + + for (int i = plants.Count - 1; i >= 0; --i) + { + PlantItem plant = (PlantItem)plants[i]; + + if (plant.IsGrowable && plant.RootParent as Mobile == null && now >= plant.PlantSystem.NextGrowth) + plant.PlantSystem.DoGrowthCheck(); + } + } + + private static void EventSink_WorldLoad() + { + GrowAll(); + } + + private static void EventSink_WorldSave(WorldSaveEventArgs args) + { + GrowAll(); + } + + public void DoGrowthCheck() + { + if (!Plant.IsGrowable) + return; + + if (DateTime.UtcNow < NextGrowth) + { + GrowthIndicator = PlantGrowthIndicator.Delay; + return; + } + + NextGrowth = DateTime.UtcNow + CheckDelay; + + if (!Plant.ValidGrowthLocation) + { + GrowthIndicator = PlantGrowthIndicator.InvalidLocation; + return; + } + + if (Plant.PlantStatus == PlantStatus.BowlOfDirt) + { + if (Water > 2 || Utility.RandomDouble() < 0.9) + Water--; + return; + } + + ApplyBeneficEffects(); + + if (!ApplyMaladiesEffects()) // Dead + return; + + Grow(); + + UpdateMaladies(); + } + + private void ApplyBeneficEffects() + { + if (PoisonPotion >= Infestation) + { + PoisonPotion -= Infestation; + Infestation = 0; + } + else + { + Infestation -= PoisonPotion; + PoisonPotion = 0; + } + + if (CurePotion >= Fungus) + { + CurePotion -= Fungus; + Fungus = 0; + } + else + { + Fungus -= CurePotion; + CurePotion = 0; + } + + if (HealPotion >= Poison) + { + HealPotion -= Poison; + Poison = 0; + } + else + { + Poison -= HealPotion; + HealPotion = 0; + } + + if (HealPotion >= Disease) + { + HealPotion -= Disease; + Disease = 0; + } + else + { + Disease -= HealPotion; + HealPotion = 0; + } + + if (!HasMaladies) + { + if (HealPotion > 0) + Hits += HealPotion * 7; + else + Hits += 2; + } + + HealPotion = 0; + } + + private bool ApplyMaladiesEffects() + { + int damage = 0; + + if (Infestation > 0) + damage += Infestation * Utility.RandomMinMax(3, 6); + + if (Fungus > 0) + damage += Fungus * Utility.RandomMinMax(3, 6); + + if (Poison > 0) + damage += Poison * Utility.RandomMinMax(3, 6); + + if (Disease > 0) + damage += Disease * Utility.RandomMinMax(3, 6); + + if (Water > 2) + damage += (Water - 2) * Utility.RandomMinMax(3, 6); + else if (Water < 2) + damage += (2 - Water) * Utility.RandomMinMax(3, 6); + + Hits -= damage; + + return Plant.IsGrowable && Plant.PlantStatus != PlantStatus.BowlOfDirt; + } + + private void Grow() + { + if (Health < PlantHealth.Healthy) + { + GrowthIndicator = PlantGrowthIndicator.NotHealthy; + } + else if (FertileDirt && Plant.PlantStatus <= PlantStatus.Stage5 && Utility.RandomDouble() < 0.1) + { + int curStage = (int)Plant.PlantStatus; + Plant.PlantStatus = (PlantStatus)(curStage + 2); + + GrowthIndicator = PlantGrowthIndicator.DoubleGrown; + } + else if (Plant.PlantStatus < PlantStatus.Stage9) + { + int curStage = (int)Plant.PlantStatus; + Plant.PlantStatus = (PlantStatus)(curStage + 1); + + GrowthIndicator = PlantGrowthIndicator.Grown; + } + else + { + if (Pollinated && LeftSeeds > 0 && Plant.Reproduces) + { + LeftSeeds--; + AvailableSeeds++; + } + + if (LeftResources > 0 && PlantResourceInfo.GetInfo(Plant.PlantType, Plant.PlantHue) != null) + { + LeftResources--; + AvailableResources++; + } + + GrowthIndicator = PlantGrowthIndicator.Grown; + } + + if (Plant.PlantStatus >= PlantStatus.Stage9 && !Pollinated) + { + Pollinated = true; + SeedType = Plant.PlantType; + SeedHue = Plant.PlantHue; + } + } + + private void UpdateMaladies() + { + double infestationChance = 0.30 - StrengthPotion * 0.075 + (Water - 2) * 0.10; + + PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo(Plant.PlantType); + if (typeInfo.Flowery) + infestationChance += 0.10; + + if (PlantHueInfo.IsBright(Plant.PlantHue)) + infestationChance += 0.10; + + if (Utility.RandomDouble() < infestationChance) + Infestation++; + + + double fungusChance = 0.15 - StrengthPotion * 0.075 + (Water - 2) * 0.10; + + if (Utility.RandomDouble() < fungusChance) + Fungus++; + + if (Water > 2 || Utility.RandomDouble() < 0.9) + Water--; + + if (PoisonPotion > 0) + { + Poison += PoisonPotion; + PoisonPotion = 0; + } + + if (CurePotion > 0) + { + Disease += CurePotion; + CurePotion = 0; + } + + StrengthPotion = 0; + } + + public void Save(GenericWriter writer) + { + writer.Write(2); // version + + writer.Write(FertileDirt); + + writer.Write(NextGrowth); + writer.Write((int)GrowthIndicator); + + writer.Write(m_Water); + + writer.Write(m_Hits); + writer.Write(m_Infestation); + writer.Write(m_Fungus); + writer.Write(m_Poison); + writer.Write(m_Disease); + writer.Write(m_PoisonPotion); + writer.Write(m_CurePotion); + writer.Write(m_HealPotion); + writer.Write(m_StrengthPotion); + + writer.Write(Pollinated); + writer.Write((int)m_SeedType); + writer.Write((int)m_SeedHue); + writer.Write(m_AvailableSeeds); + writer.Write(m_LeftSeeds); + + writer.Write(m_AvailableResources); + writer.Write(m_LeftResources); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PlantType.cs b/Scripts/Engines/Plants/PlantType.cs index ba3dfd838..6417f20cb 100644 --- a/Scripts/Engines/Plants/PlantType.cs +++ b/Scripts/Engines/Plants/PlantType.cs @@ -1,350 +1,372 @@ namespace Server.Engines.Plants { - public enum PlantType - { - CampionFlowers, - Poppies, - Snowdrops, - Bulrushes, - Lilies, - PampasGrass, - Rushes, - ElephantEarPlant, - Fern, - PonytailPalm, - SmallPalm, - CenturyPlant, - WaterPlant, - SnakePlant, - PricklyPearCactus, - BarrelCactus, - TribarrelCactus, - CommonGreenBonsai, - CommonPinkBonsai, - UncommonGreenBonsai, - UncommonPinkBonsai, - RareGreenBonsai, - RarePinkBonsai, - ExceptionalBonsai, - ExoticBonsai, - Cactus, - FlaxFlowers, - FoxgloveFlowers, - HopsEast, - OrfluerFlowers, - CypressTwisted, - HedgeShort, - JuniperBush, - SnowdropPatch, - Cattails, - PoppyPatch, - SpiderTree, - WaterLily, - CypressStraight, - HedgeTall, - HopsSouth, - SugarCanes, - CocoaTree - } + public enum PlantType + { + CampionFlowers, + Poppies, + Snowdrops, + Bulrushes, + Lilies, + PampasGrass, + Rushes, + ElephantEarPlant, + Fern, + PonytailPalm, + SmallPalm, + CenturyPlant, + WaterPlant, + SnakePlant, + PricklyPearCactus, + BarrelCactus, + TribarrelCactus, + CommonGreenBonsai, + CommonPinkBonsai, + UncommonGreenBonsai, + UncommonPinkBonsai, + RareGreenBonsai, + RarePinkBonsai, + ExceptionalBonsai, + ExoticBonsai, + Cactus, + FlaxFlowers, + FoxgloveFlowers, + HopsEast, + OrfluerFlowers, + CypressTwisted, + HedgeShort, + JuniperBush, + SnowdropPatch, + Cattails, + PoppyPatch, + SpiderTree, + WaterLily, + CypressStraight, + HedgeTall, + HopsSouth, + SugarCanes, + CocoaTree + } - public enum PlantCategory - { - Default, - Common = 1063335, // - Uncommon = 1063336, // - Rare = 1063337, // Bonsai - Exceptional = 1063341, // - Exotic = 1063342, // - Peculiar = 1080528, - Fragrant = 1080529 - } + public enum PlantCategory + { + Default, + Common = 1063335, // + Uncommon = 1063336, // + Rare = 1063337, // Bonsai + Exceptional = 1063341, // + Exotic = 1063342, // + Peculiar = 1080528, + Fragrant = 1080529 + } - public class PlantTypeInfo - { - private static PlantTypeInfo[] m_Table = { - new PlantTypeInfo( 0xC83, 0, 0, PlantType.CampionFlowers, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC86, 0, 0, PlantType.Poppies, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC88, 0, 10, PlantType.Snowdrops, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC94, -15, 0, PlantType.Bulrushes, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC8B, 0, 0, PlantType.Lilies, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xCA5, -8, 0, PlantType.PampasGrass, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xCA7, -10, 0, PlantType.Rushes, false, true, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC97, -20, 0, PlantType.ElephantEarPlant, true, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC9F, -20, 0, PlantType.Fern, false, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xCA6, -16, -5, PlantType.PonytailPalm, false, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xC9C, -5, -10, PlantType.SmallPalm, false, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xD31, 0, -27, PlantType.CenturyPlant, true, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xD04, 0, 10, PlantType.WaterPlant, true, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xCA9, 0, 0, PlantType.SnakePlant, true, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xD2C, 0, 10, PlantType.PricklyPearCactus, false, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xD26, 0, 10, PlantType.BarrelCactus, false, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0xD27, 0, 10, PlantType.TribarrelCactus, false, false, true, true, PlantCategory.Default ), - new PlantTypeInfo( 0x28DC, -5, 5, PlantType.CommonGreenBonsai, true, false, false, false, PlantCategory.Common ), - new PlantTypeInfo( 0x28DF, -5, 5, PlantType.CommonPinkBonsai, true, false, false, false, PlantCategory.Common ), - new PlantTypeInfo( 0x28DD, -5, 5, PlantType.UncommonGreenBonsai, true, false, false, false, PlantCategory.Uncommon ), - new PlantTypeInfo( 0x28E0, -5, 5, PlantType.UncommonPinkBonsai, true, false, false, false, PlantCategory.Uncommon ), - new PlantTypeInfo( 0x28DE, -5, 5, PlantType.RareGreenBonsai, true, false, false, false, PlantCategory.Rare ), - new PlantTypeInfo( 0x28E1, -5, 5, PlantType.RarePinkBonsai, true, false, false, false, PlantCategory.Rare ), - new PlantTypeInfo( 0x28E2, -5, 5, PlantType.ExceptionalBonsai, true, false, false, false, PlantCategory.Exceptional ), - new PlantTypeInfo( 0x28E3, -5, 5, PlantType.ExoticBonsai, true, false, false, false, PlantCategory.Exotic ), - new PlantTypeInfo( 0x0D25, 0, 0, PlantType.Cactus, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x1A9A, 5, 10, PlantType.FlaxFlowers, false, true, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0C84, 0, 0, PlantType.FoxgloveFlowers, false, true, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x1A9F, 5, -25, PlantType.HopsEast, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CC1, 0, 0, PlantType.OrfluerFlowers, false, true, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CFE, -45, -30, PlantType.CypressTwisted, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0C8F, 0, 0, PlantType.HedgeShort, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CC8, 0, 0, PlantType.JuniperBush, true, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0C8E, -20, 0, PlantType.SnowdropPatch, false, true, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CB7, 0, 0, PlantType.Cattails, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CBE, -20, 0, PlantType.PoppyPatch, false, true, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CC9, 0, 0, PlantType.SpiderTree, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0DC1, -5, 15, PlantType.WaterLily, false, true, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0CFB, -45, -30, PlantType.CypressStraight, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x0DB8, 0, -20, PlantType.HedgeTall, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x1AA1, 10, -25, PlantType.HopsSouth, false, false, false, false, PlantCategory.Peculiar ), - new PlantTypeInfo( 0x246C, -25, -20, PlantType.SugarCanes, false, false, false, false, PlantCategory.Peculiar, 1114898, 1114898, 1094702, 1094703, 1095221, 1113715 ), - new PlantTypeInfo( 0xC9E, -40, -30, PlantType.CocoaTree, false, false, false, true, PlantCategory.Fragrant, 1080536, 1080536, 1080534, 1080531, 1080533, 1113716 ) - }; + public class PlantTypeInfo + { + private static PlantTypeInfo[] m_Table = + { + new PlantTypeInfo(0xC83, 0, 0, PlantType.CampionFlowers, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC86, 0, 0, PlantType.Poppies, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC88, 0, 10, PlantType.Snowdrops, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC94, -15, 0, PlantType.Bulrushes, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC8B, 0, 0, PlantType.Lilies, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xCA5, -8, 0, PlantType.PampasGrass, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xCA7, -10, 0, PlantType.Rushes, false, true, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC97, -20, 0, PlantType.ElephantEarPlant, true, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC9F, -20, 0, PlantType.Fern, false, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xCA6, -16, -5, PlantType.PonytailPalm, false, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xC9C, -5, -10, PlantType.SmallPalm, false, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xD31, 0, -27, PlantType.CenturyPlant, true, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xD04, 0, 10, PlantType.WaterPlant, true, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xCA9, 0, 0, PlantType.SnakePlant, true, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xD2C, 0, 10, PlantType.PricklyPearCactus, false, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xD26, 0, 10, PlantType.BarrelCactus, false, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0xD27, 0, 10, PlantType.TribarrelCactus, false, false, true, true, PlantCategory.Default), + new PlantTypeInfo(0x28DC, -5, 5, PlantType.CommonGreenBonsai, true, false, false, false, PlantCategory.Common), + new PlantTypeInfo(0x28DF, -5, 5, PlantType.CommonPinkBonsai, true, false, false, false, PlantCategory.Common), + new PlantTypeInfo(0x28DD, -5, 5, PlantType.UncommonGreenBonsai, true, false, false, false, + PlantCategory.Uncommon), + new PlantTypeInfo(0x28E0, -5, 5, PlantType.UncommonPinkBonsai, true, false, false, false, + PlantCategory.Uncommon), + new PlantTypeInfo(0x28DE, -5, 5, PlantType.RareGreenBonsai, true, false, false, false, PlantCategory.Rare), + new PlantTypeInfo(0x28E1, -5, 5, PlantType.RarePinkBonsai, true, false, false, false, PlantCategory.Rare), + new PlantTypeInfo(0x28E2, -5, 5, PlantType.ExceptionalBonsai, true, false, false, false, + PlantCategory.Exceptional), + new PlantTypeInfo(0x28E3, -5, 5, PlantType.ExoticBonsai, true, false, false, false, PlantCategory.Exotic), + new PlantTypeInfo(0x0D25, 0, 0, PlantType.Cactus, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x1A9A, 5, 10, PlantType.FlaxFlowers, false, true, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0C84, 0, 0, PlantType.FoxgloveFlowers, false, true, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x1A9F, 5, -25, PlantType.HopsEast, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CC1, 0, 0, PlantType.OrfluerFlowers, false, true, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CFE, -45, -30, PlantType.CypressTwisted, false, false, false, false, + PlantCategory.Peculiar), + new PlantTypeInfo(0x0C8F, 0, 0, PlantType.HedgeShort, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CC8, 0, 0, PlantType.JuniperBush, true, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0C8E, -20, 0, PlantType.SnowdropPatch, false, true, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CB7, 0, 0, PlantType.Cattails, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CBE, -20, 0, PlantType.PoppyPatch, false, true, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CC9, 0, 0, PlantType.SpiderTree, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0DC1, -5, 15, PlantType.WaterLily, false, true, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x0CFB, -45, -30, PlantType.CypressStraight, false, false, false, false, + PlantCategory.Peculiar), + new PlantTypeInfo(0x0DB8, 0, -20, PlantType.HedgeTall, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x1AA1, 10, -25, PlantType.HopsSouth, false, false, false, false, PlantCategory.Peculiar), + new PlantTypeInfo(0x246C, -25, -20, PlantType.SugarCanes, false, false, false, false, PlantCategory.Peculiar, + 1114898, 1114898, 1094702, 1094703, 1095221, 1113715), + new PlantTypeInfo(0xC9E, -40, -30, PlantType.CocoaTree, false, false, false, true, PlantCategory.Fragrant, + 1080536, 1080536, 1080534, 1080531, 1080533, 1113716) + }; - public static PlantTypeInfo GetInfo( PlantType plantType ) - { - int index = (int)plantType; + private int m_PlantLabelDecorative; + private int m_PlantLabelFullGrown; + private int m_PlantLabelPlant; - if ( index >= 0 && index < m_Table.Length ) - return m_Table[index]; - return m_Table[0]; - } + // Cliloc overrides + private int m_PlantLabelSeed; + private int m_SeedLabel; + private int m_SeedLabelPlural; - public static PlantType RandomFirstGeneration() - { - switch ( Utility.Random( 3 ) ) - { - case 0: return PlantType.CampionFlowers; - case 1: return PlantType.Fern; - default: return PlantType.TribarrelCactus; - } - } + private PlantTypeInfo(int itemID, int offsetX, int offsetY, PlantType plantType, bool containsPlant, bool flowery, + bool crossable, bool reproduces, PlantCategory plantCategory) + : this(itemID, offsetX, offsetY, plantType, containsPlant, flowery, crossable, reproduces, plantCategory, -1, -1, + -1, -1, -1, -1) + { + } - public static PlantType RandomPeculiarGroupOne() - { - switch ( Utility.Random( 6 ) ) - { - case 0: return PlantType.Cactus; - case 1: return PlantType.FlaxFlowers; - case 2: return PlantType.FoxgloveFlowers; - case 3: return PlantType.HopsEast; - case 4: return PlantType.CocoaTree; - default: return PlantType.OrfluerFlowers; - } - } + private PlantTypeInfo(int itemID, int offsetX, int offsetY, PlantType plantType, bool containsPlant, bool flowery, + bool crossable, bool reproduces, PlantCategory plantCategory, int plantLabelSeed, int plantLabelPlant, + int plantLabelFullGrown, int plantLabelDecorative, int seedLabel, int seedLabelPlural) + { + ItemID = itemID; + OffsetX = offsetX; + OffsetY = offsetY; + PlantType = plantType; + ContainsPlant = containsPlant; + Flowery = flowery; + Crossable = crossable; + Reproduces = reproduces; + PlantCategory = plantCategory; + m_PlantLabelSeed = plantLabelSeed; + m_PlantLabelPlant = plantLabelPlant; + m_PlantLabelFullGrown = plantLabelFullGrown; + m_PlantLabelDecorative = plantLabelDecorative; + m_SeedLabel = seedLabel; + m_SeedLabelPlural = seedLabelPlural; + } - public static PlantType RandomPeculiarGroupTwo() - { - switch ( Utility.Random( 5 ) ) - { - case 0: return PlantType.CypressTwisted; - case 1: return PlantType.HedgeShort; - case 2: return PlantType.JuniperBush; - case 3: return PlantType.CocoaTree; - default: return PlantType.SnowdropPatch; - } - } + public int ItemID{ get; } - public static PlantType RandomPeculiarGroupThree() - { - switch ( Utility.Random( 5 ) ) - { - case 0: return PlantType.Cattails; - case 1: return PlantType.PoppyPatch; - case 2: return PlantType.SpiderTree; - case 3: return PlantType.CocoaTree; - default: return PlantType.WaterLily; - } - } + public int OffsetX{ get; } - public static PlantType RandomPeculiarGroupFour() - { - switch ( Utility.Random( 5 ) ) - { - case 0: return PlantType.CypressStraight; - case 1: return PlantType.HedgeTall; - case 2: return PlantType.HopsSouth; - case 3: return PlantType.CocoaTree; - default: return PlantType.SugarCanes; - } - } + public int OffsetY{ get; } - public static PlantType RandomBonsai( double increaseRatio ) - { - /* Chances of each plant type are equal to the chances of the previous plant type * increaseRatio: - * E.g.: - * chances_of_uncommon = chances_of_common * increaseRatio - * chances_of_rare = chances_of_uncommon * increaseRatio - * ... - * - * If increaseRatio < 1 -> rare plants are actually rarer than the others - * If increaseRatio > 1 -> rare plants are actually more common than the others (it might be the case with certain monsters) - * - * If a plant type (common, uncommon, ...) has 2 different colors, they have the same chances: - * chances_of_green_common = chances_of_pink_common = chances_of_common / 2 - * ... - */ + public PlantType PlantType{ get; } - double k1 = increaseRatio >= 0.0 ? increaseRatio : 0.0; - double k2 = k1 * k1; - double k3 = k2 * k1; - double k4 = k3 * k1; + public PlantCategory PlantCategory{ get; } - double exp1 = k1 + 1.0; - double exp2 = k2 + exp1; - double exp3 = k3 + exp2; - double exp4 = k4 + exp3; + public int Name => ItemID < 0x4000 ? 1020000 + ItemID : 1078872 + ItemID; - double rand = Utility.RandomDouble(); + public bool ContainsPlant{ get; } - if ( rand < 0.5 / exp4 ) - return PlantType.CommonGreenBonsai; - if ( rand < 1.0 / exp4 ) - return PlantType.CommonPinkBonsai; - if ( rand < (k1 * 0.5 + 1.0) / exp4 ) - return PlantType.UncommonGreenBonsai; - if ( rand < exp1 / exp4 ) - return PlantType.UncommonPinkBonsai; - if ( rand < (k2 * 0.5 + exp1) / exp4 ) - return PlantType.RareGreenBonsai; - if ( rand < exp2 / exp4 ) - return PlantType.RarePinkBonsai; - if ( rand < exp3 / exp4 ) - return PlantType.ExceptionalBonsai; - return PlantType.ExoticBonsai; - } + public bool Flowery{ get; } - public static bool IsCrossable( PlantType plantType ) - { - return GetInfo( plantType ).Crossable; - } + public bool Crossable{ get; } - public static PlantType Cross( PlantType first, PlantType second ) - { - if ( !IsCrossable( first ) || !IsCrossable( second ) ) - return PlantType.CampionFlowers; + public bool Reproduces{ get; } - int firstIndex = (int)first; - int secondIndex = (int)second; + public static PlantTypeInfo GetInfo(PlantType plantType) + { + int index = (int)plantType; - if ( firstIndex + 1 == secondIndex || firstIndex == secondIndex + 1 ) - return Utility.RandomBool() ? first : second; - return (PlantType)( (firstIndex + secondIndex) / 2 ); - } + if (index >= 0 && index < m_Table.Length) + return m_Table[index]; + return m_Table[0]; + } - public static bool CanReproduce( PlantType plantType ) - { - return GetInfo( plantType ).Reproduces; - } + public static PlantType RandomFirstGeneration() + { + switch (Utility.Random(3)) + { + case 0: return PlantType.CampionFlowers; + case 1: return PlantType.Fern; + default: return PlantType.TribarrelCactus; + } + } - public int GetPlantLabelSeed( PlantHueInfo hueInfo ) - { - if ( m_PlantLabelSeed != -1 ) - return m_PlantLabelSeed; + public static PlantType RandomPeculiarGroupOne() + { + switch (Utility.Random(6)) + { + case 0: return PlantType.Cactus; + case 1: return PlantType.FlaxFlowers; + case 2: return PlantType.FoxgloveFlowers; + case 3: return PlantType.HopsEast; + case 4: return PlantType.CocoaTree; + default: return PlantType.OrfluerFlowers; + } + } - return hueInfo.IsBright() ? 1061887 : 1061888; // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ ~6_val~ - } + public static PlantType RandomPeculiarGroupTwo() + { + switch (Utility.Random(5)) + { + case 0: return PlantType.CypressTwisted; + case 1: return PlantType.HedgeShort; + case 2: return PlantType.JuniperBush; + case 3: return PlantType.CocoaTree; + default: return PlantType.SnowdropPatch; + } + } - public int GetPlantLabelPlant( PlantHueInfo hueInfo ) - { - if ( m_PlantLabelPlant != -1 ) - return m_PlantLabelPlant; + public static PlantType RandomPeculiarGroupThree() + { + switch (Utility.Random(5)) + { + case 0: return PlantType.Cattails; + case 1: return PlantType.PoppyPatch; + case 2: return PlantType.SpiderTree; + case 3: return PlantType.CocoaTree; + default: return PlantType.WaterLily; + } + } - if ( ContainsPlant ) - return hueInfo.IsBright() ? 1060832 : 1060831; // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ - return hueInfo.IsBright() ? 1061887 : 1061888; // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ ~6_val~ - } + public static PlantType RandomPeculiarGroupFour() + { + switch (Utility.Random(5)) + { + case 0: return PlantType.CypressStraight; + case 1: return PlantType.HedgeTall; + case 2: return PlantType.HopsSouth; + case 3: return PlantType.CocoaTree; + default: return PlantType.SugarCanes; + } + } - public int GetPlantLabelFullGrown( PlantHueInfo hueInfo ) - { - if ( m_PlantLabelFullGrown != -1 ) - return m_PlantLabelFullGrown; + public static PlantType RandomBonsai(double increaseRatio) + { + /* Chances of each plant type are equal to the chances of the previous plant type * increaseRatio: + * E.g.: + * chances_of_uncommon = chances_of_common * increaseRatio + * chances_of_rare = chances_of_uncommon * increaseRatio + * ... + * + * If increaseRatio < 1 -> rare plants are actually rarer than the others + * If increaseRatio > 1 -> rare plants are actually more common than the others (it might be the case with certain monsters) + * + * If a plant type (common, uncommon, ...) has 2 different colors, they have the same chances: + * chances_of_green_common = chances_of_pink_common = chances_of_common / 2 + * ... + */ - if ( ContainsPlant ) - return hueInfo.IsBright() ? 1061891 : 1061889; // a ~1_HEALTH~ [bright] ~2_COLOR~ ~3_NAME~ - return hueInfo.IsBright() ? 1061892 : 1061890; // a ~1_HEALTH~ [bright] ~2_COLOR~ ~3_NAME~ plant - } + double k1 = increaseRatio >= 0.0 ? increaseRatio : 0.0; + double k2 = k1 * k1; + double k3 = k2 * k1; + double k4 = k3 * k1; - public int GetPlantLabelDecorative( PlantHueInfo hueInfo ) - { - if ( m_PlantLabelDecorative != -1 ) - return m_PlantLabelDecorative; + double exp1 = k1 + 1.0; + double exp2 = k2 + exp1; + double exp3 = k3 + exp2; + double exp4 = k4 + exp3; - return hueInfo.IsBright() ? 1074267 : 1070973; // a decorative [bright] ~1_COLOR~ ~2_TYPE~ - } + double rand = Utility.RandomDouble(); - public int GetSeedLabel( PlantHueInfo hueInfo ) - { - if ( m_SeedLabel != -1 ) - return m_SeedLabel; + if (rand < 0.5 / exp4) + return PlantType.CommonGreenBonsai; + if (rand < 1.0 / exp4) + return PlantType.CommonPinkBonsai; + if (rand < (k1 * 0.5 + 1.0) / exp4) + return PlantType.UncommonGreenBonsai; + if (rand < exp1 / exp4) + return PlantType.UncommonPinkBonsai; + if (rand < (k2 * 0.5 + exp1) / exp4) + return PlantType.RareGreenBonsai; + if (rand < exp2 / exp4) + return PlantType.RarePinkBonsai; + if (rand < exp3 / exp4) + return PlantType.ExceptionalBonsai; + return PlantType.ExoticBonsai; + } - return hueInfo.IsBright() ? 1061918 : 1061917; // [bright] ~1_COLOR~ ~2_TYPE~ seed - } + public static bool IsCrossable(PlantType plantType) + { + return GetInfo(plantType).Crossable; + } - public int GetSeedLabelPlural( PlantHueInfo hueInfo ) - { - if ( m_SeedLabelPlural != -1 ) - return m_SeedLabelPlural; + public static PlantType Cross(PlantType first, PlantType second) + { + if (!IsCrossable(first) || !IsCrossable(second)) + return PlantType.CampionFlowers; - return hueInfo.IsBright() ? 1113493 : 1113492; // ~1_amount~ [bright] ~2_color~ ~3_type~ seeds - } + int firstIndex = (int)first; + int secondIndex = (int)second; - // Cliloc overrides - private int m_PlantLabelSeed; - private int m_PlantLabelPlant; - private int m_PlantLabelFullGrown; - private int m_PlantLabelDecorative; - private int m_SeedLabel; - private int m_SeedLabelPlural; + if (firstIndex + 1 == secondIndex || firstIndex == secondIndex + 1) + return Utility.RandomBool() ? first : second; + return (PlantType)((firstIndex + secondIndex) / 2); + } - public int ItemID { get; } + public static bool CanReproduce(PlantType plantType) + { + return GetInfo(plantType).Reproduces; + } - public int OffsetX { get; } + public int GetPlantLabelSeed(PlantHueInfo hueInfo) + { + if (m_PlantLabelSeed != -1) + return m_PlantLabelSeed; - public int OffsetY { get; } + return + hueInfo.IsBright() + ? 1061887 + : 1061888; // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ ~6_val~ + } - public PlantType PlantType { get; } + public int GetPlantLabelPlant(PlantHueInfo hueInfo) + { + if (m_PlantLabelPlant != -1) + return m_PlantLabelPlant; - public PlantCategory PlantCategory { get; } + if (ContainsPlant) + return + hueInfo.IsBright() + ? 1060832 + : 1060831; // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ + return + hueInfo.IsBright() + ? 1061887 + : 1061888; // a ~1_val~ of ~2_val~ dirt with a ~3_val~ [bright] ~4_val~ ~5_val~ ~6_val~ + } - public int Name => ( ItemID < 0x4000 ) ? 1020000 + ItemID : 1078872 + ItemID; + public int GetPlantLabelFullGrown(PlantHueInfo hueInfo) + { + if (m_PlantLabelFullGrown != -1) + return m_PlantLabelFullGrown; - public bool ContainsPlant { get; } + if (ContainsPlant) + return hueInfo.IsBright() ? 1061891 : 1061889; // a ~1_HEALTH~ [bright] ~2_COLOR~ ~3_NAME~ + return hueInfo.IsBright() ? 1061892 : 1061890; // a ~1_HEALTH~ [bright] ~2_COLOR~ ~3_NAME~ plant + } - public bool Flowery { get; } + public int GetPlantLabelDecorative(PlantHueInfo hueInfo) + { + if (m_PlantLabelDecorative != -1) + return m_PlantLabelDecorative; - public bool Crossable { get; } + return hueInfo.IsBright() ? 1074267 : 1070973; // a decorative [bright] ~1_COLOR~ ~2_TYPE~ + } - public bool Reproduces { get; } + public int GetSeedLabel(PlantHueInfo hueInfo) + { + if (m_SeedLabel != -1) + return m_SeedLabel; - private PlantTypeInfo( int itemID, int offsetX, int offsetY, PlantType plantType, bool containsPlant, bool flowery, bool crossable, bool reproduces, PlantCategory plantCategory ) - : this( itemID, offsetX, offsetY, plantType, containsPlant, flowery, crossable, reproduces, plantCategory, -1, -1, -1, -1, -1, -1 ) - { - } + return hueInfo.IsBright() ? 1061918 : 1061917; // [bright] ~1_COLOR~ ~2_TYPE~ seed + } - private PlantTypeInfo( int itemID, int offsetX, int offsetY, PlantType plantType, bool containsPlant, bool flowery, bool crossable, bool reproduces, PlantCategory plantCategory, int plantLabelSeed, int plantLabelPlant, int plantLabelFullGrown, int plantLabelDecorative, int seedLabel, int seedLabelPlural ) - { - ItemID = itemID; - OffsetX = offsetX; - OffsetY = offsetY; - PlantType = plantType; - ContainsPlant = containsPlant; - Flowery = flowery; - Crossable = crossable; - Reproduces = reproduces; - PlantCategory = plantCategory; - m_PlantLabelSeed = plantLabelSeed; - m_PlantLabelPlant = plantLabelPlant; - m_PlantLabelFullGrown = plantLabelFullGrown; - m_PlantLabelDecorative = plantLabelDecorative; - m_SeedLabel = seedLabel; - m_SeedLabelPlural = seedLabelPlural; - } - } -} + public int GetSeedLabelPlural(PlantHueInfo hueInfo) + { + if (m_SeedLabelPlural != -1) + return m_SeedLabelPlural; + + return hueInfo.IsBright() ? 1113493 : 1113492; // ~1_amount~ [bright] ~2_color~ ~3_type~ seeds + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/PollinateTarget.cs b/Scripts/Engines/Plants/PollinateTarget.cs index e8501b94a..41e1e364b 100644 --- a/Scripts/Engines/Plants/PollinateTarget.cs +++ b/Scripts/Engines/Plants/PollinateTarget.cs @@ -2,87 +2,90 @@ using Server.Targeting; namespace Server.Engines.Plants { - public class PollinateTarget : Target - { - private PlantItem m_Plant; + public class PollinateTarget : Target + { + private PlantItem m_Plant; - public PollinateTarget( PlantItem plant ) : base( 3, true, TargetFlags.None ) - { - m_Plant = plant; - } + public PollinateTarget(PlantItem plant) : base(3, true, TargetFlags.None) + { + m_Plant = plant; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Plant.Deleted && m_Plant.PlantStatus < PlantStatus.DecorativePlant && from.InRange( m_Plant.GetWorldLocation(), 3 ) ) - { - if ( !m_Plant.IsUsableBy( from ) ) - { - m_Plant.LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - } - else if ( !m_Plant.IsCrossable ) - { - m_Plant.LabelTo( from, 1053050 ); // You cannot gather pollen from a mutated plant! - } - else if ( !m_Plant.PlantSystem.PollenProducing ) - { - m_Plant.LabelTo( from, 1053051 ); // You cannot gather pollen from a plant in this stage of development! - } - else if ( m_Plant.PlantSystem.Health < PlantHealth.Healthy ) - { - m_Plant.LabelTo( from, 1053052 ); // You cannot gather pollen from an unhealthy plant! - } - else - { - if ( !(targeted is PlantItem targ) || targ.PlantStatus >= PlantStatus.DecorativePlant || targ.PlantStatus <= PlantStatus.BowlOfDirt ) - { - m_Plant.LabelTo( from, 1053070 ); // You can only pollinate other specially grown plants! - } - else if ( !targ.IsUsableBy( from ) ) - { - targ.LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - } - else if ( !targ.IsCrossable ) - { - targ.LabelTo( from, 1053073 ); // You cannot cross-pollinate with a mutated plant! - } - else if ( !targ.PlantSystem.PollenProducing ) - { - targ.LabelTo( from, 1053074 ); // This plant is not in the flowering stage. You cannot pollinate it! - } - else if ( targ.PlantSystem.Health < PlantHealth.Healthy ) - { - targ.LabelTo( from, 1053075 ); // You cannot pollinate an unhealthy plant! - } - else if ( targ.PlantSystem.Pollinated ) - { - targ.LabelTo( from, 1053072 ); // This plant has already been pollinated! - } - else if ( targ == m_Plant ) - { - targ.PlantSystem.Pollinated = true; - targ.PlantSystem.SeedType = m_Plant.PlantType; - targ.PlantSystem.SeedHue = m_Plant.PlantHue; + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Plant.Deleted && m_Plant.PlantStatus < PlantStatus.DecorativePlant && + from.InRange(m_Plant.GetWorldLocation(), 3)) + { + if (!m_Plant.IsUsableBy(from)) + { + m_Plant.LabelTo(from, + 1061856); // You must have the item in your backpack or locked down in order to use it. + } + else if (!m_Plant.IsCrossable) + { + m_Plant.LabelTo(from, 1053050); // You cannot gather pollen from a mutated plant! + } + else if (!m_Plant.PlantSystem.PollenProducing) + { + m_Plant.LabelTo(from, 1053051); // You cannot gather pollen from a plant in this stage of development! + } + else if (m_Plant.PlantSystem.Health < PlantHealth.Healthy) + { + m_Plant.LabelTo(from, 1053052); // You cannot gather pollen from an unhealthy plant! + } + else + { + if (!(targeted is PlantItem targ) || targ.PlantStatus >= PlantStatus.DecorativePlant || + targ.PlantStatus <= PlantStatus.BowlOfDirt) + { + m_Plant.LabelTo(from, 1053070); // You can only pollinate other specially grown plants! + } + else if (!targ.IsUsableBy(from)) + { + targ.LabelTo(from, + 1061856); // You must have the item in your backpack or locked down in order to use it. + } + else if (!targ.IsCrossable) + { + targ.LabelTo(from, 1053073); // You cannot cross-pollinate with a mutated plant! + } + else if (!targ.PlantSystem.PollenProducing) + { + targ.LabelTo(from, 1053074); // This plant is not in the flowering stage. You cannot pollinate it! + } + else if (targ.PlantSystem.Health < PlantHealth.Healthy) + { + targ.LabelTo(from, 1053075); // You cannot pollinate an unhealthy plant! + } + else if (targ.PlantSystem.Pollinated) + { + targ.LabelTo(from, 1053072); // This plant has already been pollinated! + } + else if (targ == m_Plant) + { + targ.PlantSystem.Pollinated = true; + targ.PlantSystem.SeedType = m_Plant.PlantType; + targ.PlantSystem.SeedHue = m_Plant.PlantHue; - targ.LabelTo( from, 1053071 ); // You pollinate the plant with its own pollen. - } - else - { - targ.PlantSystem.Pollinated = true; - targ.PlantSystem.SeedType = PlantTypeInfo.Cross( m_Plant.PlantType, targ.PlantType ); - targ.PlantSystem.SeedHue = PlantHueInfo.Cross( m_Plant.PlantHue, targ.PlantHue ); + targ.LabelTo(from, 1053071); // You pollinate the plant with its own pollen. + } + else + { + targ.PlantSystem.Pollinated = true; + targ.PlantSystem.SeedType = PlantTypeInfo.Cross(m_Plant.PlantType, targ.PlantType); + targ.PlantSystem.SeedHue = PlantHueInfo.Cross(m_Plant.PlantHue, targ.PlantHue); - targ.LabelTo( from, 1053076 ); // You successfully cross-pollinate the plant. - } - } - } - } + targ.LabelTo(from, 1053076); // You successfully cross-pollinate the plant. + } + } + } + } - protected override void OnTargetFinish( Mobile from ) - { - if ( !m_Plant.Deleted && m_Plant.PlantStatus < PlantStatus.DecorativePlant && m_Plant.PlantStatus != PlantStatus.BowlOfDirt && from.InRange( m_Plant.GetWorldLocation(), 3 ) && m_Plant.IsUsableBy( from ) ) - { - from.SendGump( new ReproductionGump( m_Plant ) ); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + if (!m_Plant.Deleted && m_Plant.PlantStatus < PlantStatus.DecorativePlant && + m_Plant.PlantStatus != PlantStatus.BowlOfDirt && from.InRange(m_Plant.GetWorldLocation(), 3) && + m_Plant.IsUsableBy(from)) from.SendGump(new ReproductionGump(m_Plant)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/ReproductionGump.cs b/Scripts/Engines/Plants/ReproductionGump.cs index 897ceb3f7..cc0391a6f 100644 --- a/Scripts/Engines/Plants/ReproductionGump.cs +++ b/Scripts/Engines/Plants/ReproductionGump.cs @@ -3,268 +3,261 @@ using Server.Network; namespace Server.Engines.Plants { - public class ReproductionGump : Gump - { - private PlantItem m_Plant; + public class ReproductionGump : Gump + { + private PlantItem m_Plant; - public ReproductionGump( PlantItem plant ) : base( 20, 20 ) - { - m_Plant = plant; + public ReproductionGump(PlantItem plant) : base(20, 20) + { + m_Plant = plant; - DrawBackground(); + DrawBackground(); - AddButton( 70, 67, 0xD4, 0xD4, 1, GumpButtonType.Reply, 0 ); // Main menu - AddItem( 57, 65, 0x1600 ); + AddButton(70, 67, 0xD4, 0xD4, 1, GumpButtonType.Reply, 0); // Main menu + AddItem(57, 65, 0x1600); - AddLabel( 108, 67, 0x835, "Reproduction" ); + AddLabel(108, 67, 0x835, "Reproduction"); - if ( m_Plant.PlantStatus == PlantStatus.Stage9 ) - { - AddButton( 212, 67, 0xD4, 0xD4, 2, GumpButtonType.Reply, 0 ); // Set to decorative - AddItem( 202, 68, 0xC61 ); - AddLabel( 216, 66, 0x21, "/" ); - } + if (m_Plant.PlantStatus == PlantStatus.Stage9) + { + AddButton(212, 67, 0xD4, 0xD4, 2, GumpButtonType.Reply, 0); // Set to decorative + AddItem(202, 68, 0xC61); + AddLabel(216, 66, 0x21, "/"); + } - AddButton( 80, 116, 0xD4, 0xD4, 3, GumpButtonType.Reply, 0 ); // Pollination - AddItem( 66, 117, 0x1AA2 ); - AddPollinationState( 106, 116 ); + AddButton(80, 116, 0xD4, 0xD4, 3, GumpButtonType.Reply, 0); // Pollination + AddItem(66, 117, 0x1AA2); + AddPollinationState(106, 116); - AddButton( 128, 116, 0xD4, 0xD4, 4, GumpButtonType.Reply, 0 ); // Resources - AddItem( 113, 120, 0x1021 ); - AddResourcesState( 149, 116 ); + AddButton(128, 116, 0xD4, 0xD4, 4, GumpButtonType.Reply, 0); // Resources + AddItem(113, 120, 0x1021); + AddResourcesState(149, 116); - AddButton( 177, 116, 0xD4, 0xD4, 5, GumpButtonType.Reply, 0 ); // Seeds - AddItem( 160, 121, 0xDCF ); - AddSeedsState( 199, 116 ); + AddButton(177, 116, 0xD4, 0xD4, 5, GumpButtonType.Reply, 0); // Seeds + AddItem(160, 121, 0xDCF); + AddSeedsState(199, 116); - AddButton( 70, 163, 0xD2, 0xD2, 6, GumpButtonType.Reply, 0 ); // Gather pollen - AddItem( 56, 164, 0x1AA2 ); + AddButton(70, 163, 0xD2, 0xD2, 6, GumpButtonType.Reply, 0); // Gather pollen + AddItem(56, 164, 0x1AA2); - AddButton( 138, 163, 0xD2, 0xD2, 7, GumpButtonType.Reply, 0 ); // Gather resources - AddItem( 123, 167, 0x1021 ); + AddButton(138, 163, 0xD2, 0xD2, 7, GumpButtonType.Reply, 0); // Gather resources + AddItem(123, 167, 0x1021); - AddButton( 212, 163, 0xD2, 0xD2, 8, GumpButtonType.Reply, 0 ); // Gather seeds - AddItem( 195, 168, 0xDCF ); - } + AddButton(212, 163, 0xD2, 0xD2, 8, GumpButtonType.Reply, 0); // Gather seeds + AddItem(195, 168, 0xDCF); + } - private void DrawBackground() - { - AddBackground( 50, 50, 200, 150, 0xE10 ); + private void DrawBackground() + { + AddBackground(50, 50, 200, 150, 0xE10); - AddImage( 60, 90, 0xE17 ); - AddImage( 120, 90, 0xE17 ); + AddImage(60, 90, 0xE17); + AddImage(120, 90, 0xE17); - AddImage( 60, 145, 0xE17 ); - AddImage( 120, 145, 0xE17 ); + AddImage(60, 145, 0xE17); + AddImage(120, 145, 0xE17); - AddItem( 45, 45, 0xCEF ); - AddItem( 45, 118, 0xCF0 ); + AddItem(45, 45, 0xCEF); + AddItem(45, 118, 0xCF0); - AddItem( 211, 45, 0xCEB ); - AddItem( 211, 118, 0xCEC ); - } + AddItem(211, 45, 0xCEB); + AddItem(211, 118, 0xCEC); + } - private void AddPollinationState( int x, int y ) - { - PlantSystem system = m_Plant.PlantSystem; + private void AddPollinationState(int x, int y) + { + PlantSystem system = m_Plant.PlantSystem; - if ( !system.PollenProducing ) - AddLabel( x, y, 0x35, "-" ); - else if ( !system.Pollinated ) - AddLabel( x, y, 0x21, "!" ); - else - AddLabel( x, y, 0x3F, "+" ); - } + if (!system.PollenProducing) + AddLabel(x, y, 0x35, "-"); + else if (!system.Pollinated) + AddLabel(x, y, 0x21, "!"); + else + AddLabel(x, y, 0x3F, "+"); + } - private void AddResourcesState( int x, int y ) - { - PlantResourceInfo resInfo = PlantResourceInfo.GetInfo( m_Plant.PlantType, m_Plant.PlantHue ); + private void AddResourcesState(int x, int y) + { + PlantResourceInfo resInfo = PlantResourceInfo.GetInfo(m_Plant.PlantType, m_Plant.PlantHue); - PlantSystem system = m_Plant.PlantSystem; - int totalResources = system.AvailableResources + system.LeftResources; + PlantSystem system = m_Plant.PlantSystem; + int totalResources = system.AvailableResources + system.LeftResources; - if ( resInfo == null || totalResources == 0 ) - { - AddLabel( x + 5, y, 0x21, "X" ); - } - else - { - AddLabel( x, y, PlantHueInfo.GetInfo( m_Plant.PlantHue ).GumpHue, - $"{system.AvailableResources}/{totalResources}"); - } - } + if (resInfo == null || totalResources == 0) + AddLabel(x + 5, y, 0x21, "X"); + else + AddLabel(x, y, PlantHueInfo.GetInfo(m_Plant.PlantHue).GumpHue, + $"{system.AvailableResources}/{totalResources}"); + } - private void AddSeedsState( int x, int y ) - { - PlantSystem system = m_Plant.PlantSystem; - int totalSeeds = system.AvailableSeeds + system.LeftSeeds; + private void AddSeedsState(int x, int y) + { + PlantSystem system = m_Plant.PlantSystem; + int totalSeeds = system.AvailableSeeds + system.LeftSeeds; - if ( !m_Plant.Reproduces || totalSeeds == 0 ) - { - AddLabel( x + 5, y, 0x21, "X" ); - } - else - { - AddLabel( x, y, PlantHueInfo.GetInfo( system.SeedHue ).GumpHue, - $"{system.AvailableSeeds}/{totalSeeds}"); - } - } + if (!m_Plant.Reproduces || totalSeeds == 0) + AddLabel(x + 5, y, 0x21, "X"); + else + AddLabel(x, y, PlantHueInfo.GetInfo(system.SeedHue).GumpHue, + $"{system.AvailableSeeds}/{totalSeeds}"); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - if ( info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus >= PlantStatus.DecorativePlant || m_Plant.PlantStatus == PlantStatus.BowlOfDirt ) - return; + if (info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus >= PlantStatus.DecorativePlant || + m_Plant.PlantStatus == PlantStatus.BowlOfDirt) + return; - if ( ( info.ButtonID >= 6 && info.ButtonID <= 8 ) && !from.InRange( m_Plant.GetWorldLocation(), 3 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 500446 ); // That is too far away. - return; - } - - if ( !m_Plant.IsUsableBy( from ) ) - { - m_Plant.LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - return; - } + if (info.ButtonID >= 6 && info.ButtonID <= 8 && !from.InRange(m_Plant.GetWorldLocation(), 3)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 500446); // That is too far away. + return; + } - switch ( info.ButtonID ) - { - case 1: // Main menu - { - from.SendGump( new MainPlantGump( m_Plant ) ); + if (!m_Plant.IsUsableBy(from)) + { + m_Plant.LabelTo(from, 1061856); // You must have the item in your backpack or locked down in order to use it. + return; + } - break; - } - case 2: // Set to decorative - { - if ( m_Plant.PlantStatus == PlantStatus.Stage9 ) - { - from.SendGump( new SetToDecorativeGump( m_Plant ) ); - } + switch (info.ButtonID) + { + case 1: // Main menu + { + from.SendGump(new MainPlantGump(m_Plant)); - break; - } - case 3: // Pollination - { - from.Send( new DisplayHelpTopic( 67, true ) ); // POLLINATION STATE + break; + } + case 2: // Set to decorative + { + if (m_Plant.PlantStatus == PlantStatus.Stage9) from.SendGump(new SetToDecorativeGump(m_Plant)); - from.SendGump( new ReproductionGump( m_Plant ) ); + break; + } + case 3: // Pollination + { + from.Send(new DisplayHelpTopic(67, true)); // POLLINATION STATE - break; - } - case 4: // Resources - { - from.Send( new DisplayHelpTopic( 69, true ) ); // RESOURCE PRODUCTION + from.SendGump(new ReproductionGump(m_Plant)); - from.SendGump( new ReproductionGump( m_Plant ) ); + break; + } + case 4: // Resources + { + from.Send(new DisplayHelpTopic(69, true)); // RESOURCE PRODUCTION - break; - } - case 5: // Seeds - { - from.Send( new DisplayHelpTopic( 68, true ) ); // SEED PRODUCTION + from.SendGump(new ReproductionGump(m_Plant)); - from.SendGump( new ReproductionGump( m_Plant ) ); + break; + } + case 5: // Seeds + { + from.Send(new DisplayHelpTopic(68, true)); // SEED PRODUCTION - break; - } - case 6: // Gather pollen - { - if ( !m_Plant.IsCrossable ) - { - m_Plant.LabelTo( from, 1053050 ); // You cannot gather pollen from a mutated plant! - } - else if ( !m_Plant.PlantSystem.PollenProducing ) - { - m_Plant.LabelTo( from, 1053051 ); // You cannot gather pollen from a plant in this stage of development! - } - else if ( m_Plant.PlantSystem.Health < PlantHealth.Healthy ) - { - m_Plant.LabelTo( from, 1053052 ); // You cannot gather pollen from an unhealthy plant! - } - else - { - from.Target = new PollinateTarget( m_Plant ); - from.SendLocalizedMessage( 1053054 ); // Target the plant you wish to cross-pollinate to. + from.SendGump(new ReproductionGump(m_Plant)); - break; - } + break; + } + case 6: // Gather pollen + { + if (!m_Plant.IsCrossable) + { + m_Plant.LabelTo(from, 1053050); // You cannot gather pollen from a mutated plant! + } + else if (!m_Plant.PlantSystem.PollenProducing) + { + m_Plant.LabelTo(from, + 1053051); // You cannot gather pollen from a plant in this stage of development! + } + else if (m_Plant.PlantSystem.Health < PlantHealth.Healthy) + { + m_Plant.LabelTo(from, 1053052); // You cannot gather pollen from an unhealthy plant! + } + else + { + from.Target = new PollinateTarget(m_Plant); + from.SendLocalizedMessage(1053054); // Target the plant you wish to cross-pollinate to. - from.SendGump( new ReproductionGump( m_Plant ) ); + break; + } - break; - } - case 7: // Gather resources - { - PlantResourceInfo resInfo = PlantResourceInfo.GetInfo( m_Plant.PlantType, m_Plant.PlantHue ); - PlantSystem system = m_Plant.PlantSystem; + from.SendGump(new ReproductionGump(m_Plant)); - if ( resInfo == null ) - { - if ( m_Plant.IsCrossable ) - m_Plant.LabelTo( from, 1053056 ); // This plant has no resources to gather! - else - m_Plant.LabelTo( from, 1053055 ); // Mutated plants do not produce resources! - } - else if ( system.AvailableResources == 0 ) - { - m_Plant.LabelTo( from, 1053056 ); // This plant has no resources to gather! - } - else - { - Item resource = resInfo.CreateResource(); + break; + } + case 7: // Gather resources + { + PlantResourceInfo resInfo = PlantResourceInfo.GetInfo(m_Plant.PlantType, m_Plant.PlantHue); + PlantSystem system = m_Plant.PlantSystem; - if ( from.PlaceInBackpack( resource ) ) - { - system.AvailableResources--; - m_Plant.LabelTo( from, 1053059 ); // You gather resources from the plant. - } - else - { - resource.Delete(); - m_Plant.LabelTo( from, 1053058 ); // You attempt to gather as many resources as you can hold, but your backpack is full. - } - } + if (resInfo == null) + { + if (m_Plant.IsCrossable) + m_Plant.LabelTo(from, 1053056); // This plant has no resources to gather! + else + m_Plant.LabelTo(from, 1053055); // Mutated plants do not produce resources! + } + else if (system.AvailableResources == 0) + { + m_Plant.LabelTo(from, 1053056); // This plant has no resources to gather! + } + else + { + Item resource = resInfo.CreateResource(); - from.SendGump( new ReproductionGump( m_Plant ) ); + if (from.PlaceInBackpack(resource)) + { + system.AvailableResources--; + m_Plant.LabelTo(from, 1053059); // You gather resources from the plant. + } + else + { + resource.Delete(); + m_Plant.LabelTo(from, + 1053058); // You attempt to gather as many resources as you can hold, but your backpack is full. + } + } - break; - } - case 8: // Gather seeds - { - PlantSystem system = m_Plant.PlantSystem; + from.SendGump(new ReproductionGump(m_Plant)); - if ( !m_Plant.Reproduces ) - { - m_Plant.LabelTo( from, 1053060 ); // Mutated plants do not produce seeds! - } - else if ( system.AvailableSeeds == 0 ) - { - m_Plant.LabelTo( from, 1053061 ); // This plant has no seeds to gather! - } - else - { - Seed seed = new Seed( system.SeedType, system.SeedHue, true ); + break; + } + case 8: // Gather seeds + { + PlantSystem system = m_Plant.PlantSystem; - if ( from.PlaceInBackpack( seed ) ) - { - system.AvailableSeeds--; - m_Plant.LabelTo( from, 1053063 ); // You gather seeds from the plant. - } - else - { - seed.Delete(); - m_Plant.LabelTo( from, 1053062 ); // You attempt to gather as many seeds as you can hold, but your backpack is full. - } - } + if (!m_Plant.Reproduces) + { + m_Plant.LabelTo(from, 1053060); // Mutated plants do not produce seeds! + } + else if (system.AvailableSeeds == 0) + { + m_Plant.LabelTo(from, 1053061); // This plant has no seeds to gather! + } + else + { + Seed seed = new Seed(system.SeedType, system.SeedHue, true); - from.SendGump( new ReproductionGump( m_Plant ) ); + if (from.PlaceInBackpack(seed)) + { + system.AvailableSeeds--; + m_Plant.LabelTo(from, 1053063); // You gather seeds from the plant. + } + else + { + seed.Delete(); + m_Plant.LabelTo(from, + 1053062); // You attempt to gather as many seeds as you can hold, but your backpack is full. + } + } - break; - } - } - } - } + from.SendGump(new ReproductionGump(m_Plant)); + + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Plants/Seed.cs b/Scripts/Engines/Plants/Seed.cs index 22fb80105..cd3dc4430 100644 --- a/Scripts/Engines/Plants/Seed.cs +++ b/Scripts/Engines/Plants/Seed.cs @@ -1,233 +1,227 @@ -using System; using Server.Targeting; namespace Server.Engines.Plants { - public class Seed : Item - { - private PlantType m_PlantType; - private PlantHue m_PlantHue; - private bool m_ShowType; + public class Seed : Item + { + private PlantHue m_PlantHue; + private PlantType m_PlantType; + private bool m_ShowType; - [CommandProperty( AccessLevel.GameMaster )] - public PlantType PlantType - { - get => m_PlantType; - set - { - m_PlantType = value; - InvalidateProperties(); - } - } + [Constructible] + public Seed() : this(PlantTypeInfo.RandomFirstGeneration(), PlantHueInfo.RandomFirstGeneration(), false) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public PlantHue PlantHue - { - get => m_PlantHue; - set - { - m_PlantHue = value; - Hue = PlantHueInfo.GetInfo( value ).Hue; - InvalidateProperties(); - } - } + [Constructible] + public Seed(PlantType plantType, PlantHue plantHue, bool showType) : base(0xDCF) + { + Weight = 1.0; + Stackable = Core.SA; - [CommandProperty( AccessLevel.GameMaster )] - public bool ShowType - { - get => m_ShowType; - set - { - m_ShowType = value; - InvalidateProperties(); - } - } + m_PlantType = plantType; + m_PlantHue = plantHue; + m_ShowType = showType; - public override int LabelNumber => 1060810; // seed + Hue = PlantHueInfo.GetInfo(plantHue).Hue; + } - public static Seed RandomBonsaiSeed() - { - return RandomBonsaiSeed( 0.5 ); - } + public Seed(Serial serial) : base(serial) + { + } - public static Seed RandomBonsaiSeed( double increaseRatio ) - { - return new Seed( PlantTypeInfo.RandomBonsai( increaseRatio ), PlantHue.Plain, false ); - } + [CommandProperty(AccessLevel.GameMaster)] + public PlantType PlantType + { + get => m_PlantType; + set + { + m_PlantType = value; + InvalidateProperties(); + } + } - public static Seed RandomPeculiarSeed( int group ) - { - switch ( group ) - { - case 1: return new Seed ( PlantTypeInfo.RandomPeculiarGroupOne(), PlantHue.Plain, false ); - case 2: return new Seed ( PlantTypeInfo.RandomPeculiarGroupTwo(), PlantHue.Plain, false ); - case 3: return new Seed ( PlantTypeInfo.RandomPeculiarGroupThree(), PlantHue.Plain, false ); - default: return new Seed ( PlantTypeInfo.RandomPeculiarGroupFour(), PlantHue.Plain, false ); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public PlantHue PlantHue + { + get => m_PlantHue; + set + { + m_PlantHue = value; + Hue = PlantHueInfo.GetInfo(value).Hue; + InvalidateProperties(); + } + } - [Constructible] - public Seed() : this( PlantTypeInfo.RandomFirstGeneration(), PlantHueInfo.RandomFirstGeneration(), false ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool ShowType + { + get => m_ShowType; + set + { + m_ShowType = value; + InvalidateProperties(); + } + } - [Constructible] - public Seed( PlantType plantType, PlantHue plantHue, bool showType ) : base( 0xDCF ) - { - Weight = 1.0; - Stackable = Core.SA; + public override int LabelNumber => 1060810; // seed - m_PlantType = plantType; - m_PlantHue = plantHue; - m_ShowType = showType; + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - Hue = PlantHueInfo.GetInfo( plantHue ).Hue; - } + public static Seed RandomBonsaiSeed() + { + return RandomBonsaiSeed(0.5); + } - public Seed( Serial serial ) : base( serial ) - { - } + public static Seed RandomBonsaiSeed(double increaseRatio) + { + return new Seed(PlantTypeInfo.RandomBonsai(increaseRatio), PlantHue.Plain, false); + } - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public static Seed RandomPeculiarSeed(int group) + { + switch (group) + { + case 1: return new Seed(PlantTypeInfo.RandomPeculiarGroupOne(), PlantHue.Plain, false); + case 2: return new Seed(PlantTypeInfo.RandomPeculiarGroupTwo(), PlantHue.Plain, false); + case 3: return new Seed(PlantTypeInfo.RandomPeculiarGroupThree(), PlantHue.Plain, false); + default: return new Seed(PlantTypeInfo.RandomPeculiarGroupFour(), PlantHue.Plain, false); + } + } - private int GetLabel( out string args ) - { - PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo( m_PlantType ); - PlantHueInfo hueInfo = PlantHueInfo.GetInfo( m_PlantHue ); + private int GetLabel(out string args) + { + PlantTypeInfo typeInfo = PlantTypeInfo.GetInfo(m_PlantType); + PlantHueInfo hueInfo = PlantHueInfo.GetInfo(m_PlantHue); - int title; + int title; - if ( m_ShowType || typeInfo.PlantCategory == PlantCategory.Default ) - title = hueInfo.Name; - else - title = (int)typeInfo.PlantCategory; + if (m_ShowType || typeInfo.PlantCategory == PlantCategory.Default) + title = hueInfo.Name; + else + title = (int)typeInfo.PlantCategory; - if ( Amount == 1 ) - { - if ( m_ShowType ) - { - args = $"#{title}\t#{typeInfo.Name}"; - return typeInfo.GetSeedLabel( hueInfo ); - } + if (Amount == 1) + { + if (m_ShowType) + { + args = $"#{title}\t#{typeInfo.Name}"; + return typeInfo.GetSeedLabel(hueInfo); + } - args = $"#{title}"; - return hueInfo.IsBright() ? 1060839 : 1060838; // [bright] ~1_val~ seed - } + args = $"#{title}"; + return hueInfo.IsBright() ? 1060839 : 1060838; // [bright] ~1_val~ seed + } - if ( m_ShowType ) - { - args = $"{Amount}\t#{title}\t#{typeInfo.Name}"; - return typeInfo.GetSeedLabelPlural( hueInfo ); - } + if (m_ShowType) + { + args = $"{Amount}\t#{title}\t#{typeInfo.Name}"; + return typeInfo.GetSeedLabelPlural(hueInfo); + } - args = $"{Amount}\t#{title}"; - return hueInfo.IsBright() ? 1113491 : 1113490; // ~1_amount~ [bright] ~2_val~ seeds - } + args = $"{Amount}\t#{title}"; + return hueInfo.IsBright() ? 1113491 : 1113490; // ~1_amount~ [bright] ~2_val~ seeds + } - public override void AddNameProperty( ObjectPropertyList list ) - { - string args; - list.Add( GetLabel( out args ), args ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + string args; + list.Add(GetLabel(out args), args); + } - public override void OnSingleClick( Mobile from ) - { - string args; - LabelTo( from, GetLabel( out args ), args ); - } + public override void OnSingleClick(Mobile from) + { + string args; + LabelTo(from, GetLabel(out args), args); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } - from.Target = new InternalTarget( this ); - LabelTo( from, 1061916 ); // Choose a bowl of dirt to plant this seed in. - } + from.Target = new InternalTarget(this); + LabelTo(from, 1061916); // Choose a bowl of dirt to plant this seed in. + } - public override bool StackWith( Mobile from, Item dropped, bool playSound ) - { - return dropped is Seed other && other.PlantType == m_PlantType && other.PlantHue == m_PlantHue && other.ShowType == m_ShowType && base.StackWith( from, other, playSound ); - } + public override bool StackWith(Mobile from, Item dropped, bool playSound) + { + return dropped is Seed other && other.PlantType == m_PlantType && other.PlantHue == m_PlantHue && + other.ShowType == m_ShowType && base.StackWith(from, other, playSound); + } - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is Seed newSeed) ) - return; + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is Seed newSeed)) + return; - newSeed.PlantType = m_PlantType; - newSeed.PlantHue = m_PlantHue; - newSeed.ShowType = m_ShowType; - } + newSeed.PlantType = m_PlantType; + newSeed.PlantHue = m_PlantHue; + newSeed.ShowType = m_ShowType; + } - private class InternalTarget : Target - { - private Seed m_Seed; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public InternalTarget( Seed seed ) : base( -1, false, TargetFlags.None ) - { - m_Seed = seed; - CheckLOS = false; - } + writer.Write(2); // version - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Seed.Deleted ) - return; + writer.Write((int)m_PlantType); + writer.Write((int)m_PlantHue); + writer.Write(m_ShowType); + } - if ( !m_Seed.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - return; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( targeted is PlantItem plant ) - { - plant.PlantSeed( from, m_Seed ); - } - else if ( targeted is Item item ) - { - item.LabelTo( from, 1061919 ); // You must use a seed on a bowl of dirt! - } - else - { - from.SendLocalizedMessage( 1061919 ); // You must use a seed on a bowl of dirt! - } - } - } + int version = reader.ReadInt(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_PlantType = (PlantType)reader.ReadInt(); + m_PlantHue = (PlantHue)reader.ReadInt(); + m_ShowType = reader.ReadBool(); - writer.Write( (int) 2 ); // version + if (Weight != 1.0) + Weight = 1.0; - writer.Write( (int) m_PlantType ); - writer.Write( (int) m_PlantHue ); - writer.Write( (bool) m_ShowType ); - } + if (version < 1) + Stackable = Core.SA; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (version < 2 && PlantHueInfo.IsCrossable(m_PlantHue)) + m_PlantHue |= PlantHue.Reproduces; + } - int version = reader.ReadInt(); + private class InternalTarget : Target + { + private Seed m_Seed; - m_PlantType = (PlantType)reader.ReadInt(); - m_PlantHue = (PlantHue)reader.ReadInt(); - m_ShowType = reader.ReadBool(); + public InternalTarget(Seed seed) : base(-1, false, TargetFlags.None) + { + m_Seed = seed; + CheckLOS = false; + } - if ( Weight != 1.0 ) - Weight = 1.0; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Seed.Deleted) + return; - if ( version < 1 ) - Stackable = Core.SA; + if (!m_Seed.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + return; + } - if ( version < 2 && PlantHueInfo.IsCrossable( m_PlantHue ) ) - m_PlantHue |= PlantHue.Reproduces; - } - } -} + if (targeted is PlantItem plant) + plant.PlantSeed(from, m_Seed); + else if (targeted is Item item) + item.LabelTo(from, 1061919); // You must use a seed on a bowl of dirt! + else + from.SendLocalizedMessage(1061919); // You must use a seed on a bowl of dirt! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Plants/SetToDecorativeGump.cs b/Scripts/Engines/Plants/SetToDecorativeGump.cs index 642afe441..29af96088 100644 --- a/Scripts/Engines/Plants/SetToDecorativeGump.cs +++ b/Scripts/Engines/Plants/SetToDecorativeGump.cs @@ -3,81 +3,82 @@ using Server.Network; namespace Server.Engines.Plants { - public class SetToDecorativeGump : Gump - { - private PlantItem m_Plant; + public class SetToDecorativeGump : Gump + { + private PlantItem m_Plant; - public SetToDecorativeGump( PlantItem plant ) : base( 20, 20 ) - { - m_Plant = plant; + public SetToDecorativeGump(PlantItem plant) : base(20, 20) + { + m_Plant = plant; - DrawBackground(); + DrawBackground(); - AddLabel( 115, 85, 0x44, "Set plant" ); - AddLabel( 82, 105, 0x44, "to decorative mode?" ); + AddLabel(115, 85, 0x44, "Set plant"); + AddLabel(82, 105, 0x44, "to decorative mode?"); - AddButton( 98, 140, 0x47E, 0x480, 1, GumpButtonType.Reply, 0 ); // Cancel + AddButton(98, 140, 0x47E, 0x480, 1, GumpButtonType.Reply, 0); // Cancel - AddButton( 138, 141, 0xD2, 0xD2, 2, GumpButtonType.Reply, 0 ); // Help - AddLabel( 143, 141, 0x835, "?" ); + AddButton(138, 141, 0xD2, 0xD2, 2, GumpButtonType.Reply, 0); // Help + AddLabel(143, 141, 0x835, "?"); - AddButton( 168, 140, 0x481, 0x483, 3, GumpButtonType.Reply, 0 ); // Ok - } + AddButton(168, 140, 0x481, 0x483, 3, GumpButtonType.Reply, 0); // Ok + } - private void DrawBackground() - { - AddBackground( 50, 50, 200, 150, 0xE10 ); + private void DrawBackground() + { + AddBackground(50, 50, 200, 150, 0xE10); - AddItem( 25, 45, 0xCEB ); - AddItem( 25, 118, 0xCEC ); + AddItem(25, 45, 0xCEB); + AddItem(25, 118, 0xCEC); - AddItem( 227, 45, 0xCEF ); - AddItem( 227, 118, 0xCF0 ); - } + AddItem(227, 45, 0xCEF); + AddItem(227, 118, 0xCF0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - if ( info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus != PlantStatus.Stage9 ) - return; - - if ( info.ButtonID == 3 && !from.InRange( m_Plant.GetWorldLocation(), 3 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 500446 ); // That is too far away. - return; - } + if (info.ButtonID == 0 || m_Plant.Deleted || m_Plant.PlantStatus != PlantStatus.Stage9) + return; - if ( !m_Plant.IsUsableBy( from ) ) - { - m_Plant.LabelTo( from, 1061856 ); // You must have the item in your backpack or locked down in order to use it. - return; - } + if (info.ButtonID == 3 && !from.InRange(m_Plant.GetWorldLocation(), 3)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 500446); // That is too far away. + return; + } - switch ( info.ButtonID ) - { - case 1: // Cancel - { - from.SendGump( new ReproductionGump( m_Plant ) ); + if (!m_Plant.IsUsableBy(from)) + { + m_Plant.LabelTo(from, 1061856); // You must have the item in your backpack or locked down in order to use it. + return; + } - break; - } - case 2: // Help - { - from.Send( new DisplayHelpTopic( 70, true ) ); // DECORATIVE MODE + switch (info.ButtonID) + { + case 1: // Cancel + { + from.SendGump(new ReproductionGump(m_Plant)); - from.SendGump( new SetToDecorativeGump( m_Plant ) ); + break; + } + case 2: // Help + { + from.Send(new DisplayHelpTopic(70, true)); // DECORATIVE MODE - break; - } - case 3: // Ok - { - m_Plant.PlantStatus = PlantStatus.DecorativePlant; - m_Plant.LabelTo( from, 1053077 ); // You prune the plant. This plant will no longer produce resources or seeds, but will require no upkeep. + from.SendGump(new SetToDecorativeGump(m_Plant)); - break; - } - } - } - } + break; + } + case 3: // Ok + { + m_Plant.PlantStatus = PlantStatus.DecorativePlant; + m_Plant.LabelTo(from, + 1053077); // You prune the plant. This plant will no longer produce resources or seeds, but will require no upkeep. + + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Ambitious Solen Queen/AmbitiousQueenQuest.cs b/Scripts/Engines/Quests/Ambitious Solen Queen/AmbitiousQueenQuest.cs index 26b4c6f67..bed7d8d5e 100644 --- a/Scripts/Engines/Quests/Ambitious Solen Queen/AmbitiousQueenQuest.cs +++ b/Scripts/Engines/Quests/Ambitious Solen Queen/AmbitiousQueenQuest.cs @@ -1,116 +1,118 @@ using System; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ambitious { - public class AmbitiousQueenQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( DontOfferConversation ), - typeof( AcceptConversation ), - typeof( DuringKillQueensConversation ), - typeof( GatherFungiConversation ), - typeof( DuringFungiGatheringConversation ), - typeof( EndConversation ), - typeof( FullBackpackConversation ), - typeof( End2Conversation ), - typeof( KillQueensObjective ), - typeof( ReturnAfterKillsObjective ), - typeof( GatherFungiObjective ), - typeof( GetRewardObjective ) - }; + public class AmbitiousQueenQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(DontOfferConversation), + typeof(AcceptConversation), + typeof(DuringKillQueensConversation), + typeof(GatherFungiConversation), + typeof(DuringFungiGatheringConversation), + typeof(EndConversation), + typeof(FullBackpackConversation), + typeof(End2Conversation), + typeof(KillQueensObjective), + typeof(ReturnAfterKillsObjective), + typeof(GatherFungiObjective), + typeof(GetRewardObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public AmbitiousQueenQuest(PlayerMobile from, bool redSolen) : base(from) + { + RedSolen = redSolen; + } - public override object Name => 1054146; + // Serialization + public AmbitiousQueenQuest() + { + } - public override object OfferMessage => 1054060; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override TimeSpan RestartDelay => TimeSpan.Zero; - public override bool IsTutorial => false; + public override object Name => 1054146; - public override int Picture => 0x15C9; + public override object OfferMessage => 1054060; - public bool RedSolen { get; private set; } + public override TimeSpan RestartDelay => TimeSpan.Zero; + public override bool IsTutorial => false; - public AmbitiousQueenQuest( PlayerMobile from, bool redSolen ) : base( from ) - { - RedSolen = redSolen; - } + public override int Picture => 0x15C9; - // Serialization - public AmbitiousQueenQuest() - { - } + public bool RedSolen{ get; private set; } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - RedSolen = reader.ReadBool(); - } + RedSolen = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) RedSolen ); - } + writer.Write(RedSolen); + } - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } + AddConversation(new AcceptConversation()); + } - public static void GiveRewardTo( PlayerMobile player, ref bool bagOfSending, ref bool powderOfTranslocation, ref bool gold ) - { - if ( bagOfSending ) - { - Item reward = new BagOfSending(); + public static void GiveRewardTo(PlayerMobile player, ref bool bagOfSending, ref bool powderOfTranslocation, + ref bool gold) + { + if (bagOfSending) + { + Item reward = new BagOfSending(); - if ( player.PlaceInBackpack( reward ) ) - { - player.SendLocalizedMessage( 1054074, "", 0x59 ); // You have been given a bag of sending. - bagOfSending = false; - } - else - { - reward.Delete(); - } - } + if (player.PlaceInBackpack(reward)) + { + player.SendLocalizedMessage(1054074, "", 0x59); // You have been given a bag of sending. + bagOfSending = false; + } + else + { + reward.Delete(); + } + } - if ( powderOfTranslocation ) - { - Item reward = new PowderOfTranslocation( Utility.RandomMinMax( 10, 12 ) ); + if (powderOfTranslocation) + { + Item reward = new PowderOfTranslocation(Utility.RandomMinMax(10, 12)); - if ( player.PlaceInBackpack( reward ) ) - { - player.SendLocalizedMessage( 1054075, "", 0x59 ); // You have been given some powder of translocation. - powderOfTranslocation = false; - } - else - { - reward.Delete(); - } - } + if (player.PlaceInBackpack(reward)) + { + player.SendLocalizedMessage(1054075, "", 0x59); // You have been given some powder of translocation. + powderOfTranslocation = false; + } + else + { + reward.Delete(); + } + } - if ( gold ) - { - Item reward = new Gold( Utility.RandomMinMax( 250, 350 ) ); + if (gold) + { + Item reward = new Gold(Utility.RandomMinMax(250, 350)); - if ( player.PlaceInBackpack( reward ) ) - { - player.SendLocalizedMessage( 1054076, "", 0x59 ); // You have been given some gold. - gold = false; - } - else - { - reward.Delete(); - } - } - } - } -} + if (player.PlaceInBackpack(reward)) + { + player.SendLocalizedMessage(1054076, "", 0x59); // You have been given some gold. + gold = false; + } + else + { + reward.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Ambitious Solen Queen/Conversations.cs b/Scripts/Engines/Quests/Ambitious Solen Queen/Conversations.cs index f5e204062..c2c15abb7 100644 --- a/Scripts/Engines/Quests/Ambitious Solen Queen/Conversations.cs +++ b/Scripts/Engines/Quests/Ambitious Solen Queen/Conversations.cs @@ -1,154 +1,123 @@ namespace Server.Engines.Quests.Ambitious { - public class DontOfferConversation : QuestConversation - { - public override object Message => 1054059; + public class DontOfferConversation : QuestConversation + { + public override object Message => 1054059; - public override bool Logged => false; + public override bool Logged => false; + } - public DontOfferConversation() - { - } - } + public class AcceptConversation : QuestConversation + { + public override object Message => 1054061; - public class AcceptConversation : QuestConversation - { - public override object Message => 1054061; + public override void OnRead() + { + System.AddObjective(new KillQueensObjective()); + } + } - public AcceptConversation() - { - } + public class DuringKillQueensConversation : QuestConversation + { + public override object Message => 1054066; - public override void OnRead() - { - System.AddObjective( new KillQueensObjective() ); - } - } + public override bool Logged => false; + } - public class DuringKillQueensConversation : QuestConversation - { - public override object Message => 1054066; + public class GatherFungiConversation : QuestConversation + { + public override object Message => 1054068; - public override bool Logged => false; + public override void OnRead() + { + System.AddObjective(new GatherFungiObjective()); + } + } - public DuringKillQueensConversation() - { - } - } + public class DuringFungiGatheringConversation : QuestConversation + { + public override object Message => 1054070; - public class GatherFungiConversation : QuestConversation - { - public override object Message => 1054068; + public override bool Logged => false; + } - public GatherFungiConversation() - { - } + public class EndConversation : QuestConversation + { + public override object Message => 1054073; - public override void OnRead() - { - System.AddObjective( new GatherFungiObjective() ); - } - } + public override void OnRead() + { + bool bagOfSending = true; + bool powderOfTranslocation = true; + bool gold = true; - public class DuringFungiGatheringConversation : QuestConversation - { - public override object Message => 1054070; + AmbitiousQueenQuest.GiveRewardTo(System.From, ref bagOfSending, ref powderOfTranslocation, ref gold); - public override bool Logged => false; + if (!bagOfSending && !powderOfTranslocation && !gold) + System.Complete(); + else + System.AddConversation(new FullBackpackConversation(true, bagOfSending, powderOfTranslocation, gold)); + } + } - public DuringFungiGatheringConversation() - { - } - } + public class FullBackpackConversation : QuestConversation + { + private bool m_BagOfSending; + private bool m_Gold; - public class EndConversation : QuestConversation - { - public override object Message => 1054073; + private bool m_Logged; + private bool m_PowderOfTranslocation; - public EndConversation() - { - } + public FullBackpackConversation(bool logged, bool bagOfSending, bool powderOfTranslocation, bool gold) + { + m_Logged = logged; - public override void OnRead() - { - bool bagOfSending = true; - bool powderOfTranslocation = true; - bool gold = true; + m_BagOfSending = bagOfSending; + m_PowderOfTranslocation = powderOfTranslocation; + m_Gold = gold; + } - AmbitiousQueenQuest.GiveRewardTo( System.From, ref bagOfSending, ref powderOfTranslocation, ref gold ); + public FullBackpackConversation() + { + m_Logged = true; + } - if ( !bagOfSending && !powderOfTranslocation && !gold ) - { - System.Complete(); - } - else - { - System.AddConversation( new FullBackpackConversation( true, bagOfSending, powderOfTranslocation, gold ) ); - } - } - } + public override object Message => 1054077; - public class FullBackpackConversation : QuestConversation - { - public override object Message => 1054077; + public override bool Logged => m_Logged; - private bool m_Logged; - private bool m_BagOfSending; - private bool m_PowderOfTranslocation; - private bool m_Gold; + public override void OnRead() + { + if (m_Logged) + System.AddObjective(new GetRewardObjective(m_BagOfSending, m_PowderOfTranslocation, m_Gold)); + } - public override bool Logged => m_Logged; + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public FullBackpackConversation( bool logged, bool bagOfSending, bool powderOfTranslocation, bool gold ) - { - m_Logged = logged; + m_BagOfSending = reader.ReadBool(); + m_PowderOfTranslocation = reader.ReadBool(); + m_Gold = reader.ReadBool(); + } - m_BagOfSending = bagOfSending; - m_PowderOfTranslocation = powderOfTranslocation; - m_Gold = gold; - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public FullBackpackConversation() - { - m_Logged = true; - } + writer.Write(m_BagOfSending); + writer.Write(m_PowderOfTranslocation); + writer.Write(m_Gold); + } + } - public override void OnRead() - { - if ( m_Logged ) - System.AddObjective( new GetRewardObjective( m_BagOfSending, m_PowderOfTranslocation, m_Gold ) ); - } + public class End2Conversation : QuestConversation + { + public override object Message => 1054078; - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_BagOfSending = reader.ReadBool(); - m_PowderOfTranslocation = reader.ReadBool(); - m_Gold = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_BagOfSending ); - writer.Write( (bool) m_PowderOfTranslocation ); - writer.Write( (bool) m_Gold ); - } - } - - public class End2Conversation : QuestConversation - { - public override object Message => 1054078; - - public End2Conversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } -} + public override void OnRead() + { + System.Complete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Ambitious Solen Queen/Mobiles/AmbitiousSolenQueen.cs b/Scripts/Engines/Quests/Ambitious Solen Queen/Mobiles/AmbitiousSolenQueen.cs index 40587b7fc..cdbdf3038 100644 --- a/Scripts/Engines/Quests/Ambitious Solen Queen/Mobiles/AmbitiousSolenQueen.cs +++ b/Scripts/Engines/Quests/Ambitious Solen Queen/Mobiles/AmbitiousSolenQueen.cs @@ -1,207 +1,197 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ambitious { - public abstract class BaseAmbitiousSolenQueen : BaseQuester - { - public abstract bool RedSolen{ get; } - public override string DefaultName => "an ambitious solen queen"; - public override bool DisallowAllMoves => false; + public abstract class BaseAmbitiousSolenQueen : BaseQuester + { + public BaseAmbitiousSolenQueen() + { + } - public BaseAmbitiousSolenQueen() - { - } + public BaseAmbitiousSolenQueen(Serial serial) : base(serial) + { + } - public override void InitBody() - { - Body = 0x30F; + public abstract bool RedSolen{ get; } + public override string DefaultName => "an ambitious solen queen"; + public override bool DisallowAllMoves => false; - if ( !RedSolen ) - Hue = 0x453; + public override void InitBody() + { + Body = 0x30F; - SpeechHue = 0; - } + if (!RedSolen) + Hue = 0x453; - public override int GetIdleSound() - { - return 0x10D; - } + SpeechHue = 0; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - Direction = GetDirectionTo( player ); + public override int GetIdleSound() + { + return 0x10D; + } - if ( player.Quest is AmbitiousQueenQuest qs && qs.RedSolen == RedSolen ) - { - if ( qs.IsObjectiveInProgress( typeof( KillQueensObjective ) ) ) - { - qs.AddConversation( new DuringKillQueensConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( ReturnAfterKillsObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + Direction = GetDirectionTo(player); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( GatherFungiObjective ) ) ) - { - qs.AddConversation( new DuringFungiGatheringConversation() ); - } - else - { - if ( qs.FindObjective( typeof( GetRewardObjective ) ) is GetRewardObjective lastObj && !lastObj.Completed ) - { - bool bagOfSending = lastObj.BagOfSending; - bool powderOfTranslocation = lastObj.PowderOfTranslocation; - bool gold = lastObj.Gold; + if (player.Quest is AmbitiousQueenQuest qs && qs.RedSolen == RedSolen) + { + if (qs.IsObjectiveInProgress(typeof(KillQueensObjective))) + { + qs.AddConversation(new DuringKillQueensConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(ReturnAfterKillsObjective)); - AmbitiousQueenQuest.GiveRewardTo( player, ref bagOfSending, ref powderOfTranslocation, ref gold ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(GatherFungiObjective))) + { + qs.AddConversation(new DuringFungiGatheringConversation()); + } + else + { + if (qs.FindObjective(typeof(GetRewardObjective)) is GetRewardObjective lastObj && !lastObj.Completed) + { + bool bagOfSending = lastObj.BagOfSending; + bool powderOfTranslocation = lastObj.PowderOfTranslocation; + bool gold = lastObj.Gold; - lastObj.BagOfSending = bagOfSending; - lastObj.PowderOfTranslocation = powderOfTranslocation; - lastObj.Gold = gold; + AmbitiousQueenQuest.GiveRewardTo(player, ref bagOfSending, ref powderOfTranslocation, ref gold); - if ( !bagOfSending && !powderOfTranslocation && !gold ) - { - lastObj.Complete(); - } - else - { - qs.AddConversation( new FullBackpackConversation( false, lastObj.BagOfSending, lastObj.PowderOfTranslocation, lastObj.Gold ) ); - } - } - } - } - } - else - { - QuestSystem newQuest = new AmbitiousQueenQuest( player, RedSolen ); + lastObj.BagOfSending = bagOfSending; + lastObj.PowderOfTranslocation = powderOfTranslocation; + lastObj.Gold = gold; - if ( player.Quest == null && QuestSystem.CanOfferQuest( player, typeof( AmbitiousQueenQuest ) ) ) - { - newQuest.SendOffer(); - } - else - { - newQuest.AddConversation( new DontOfferConversation() ); - } - } - } + if (!bagOfSending && !powderOfTranslocation && !gold) + lastObj.Complete(); + else + qs.AddConversation(new FullBackpackConversation(false, lastObj.BagOfSending, + lastObj.PowderOfTranslocation, lastObj.Gold)); + } + } + } + } + else + { + QuestSystem newQuest = new AmbitiousQueenQuest(player, RedSolen); - public override bool OnDragDrop( Mobile from, Item dropped ) - { - Direction = GetDirectionTo( from ); + if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(AmbitiousQueenQuest))) + newQuest.SendOffer(); + else + newQuest.AddConversation(new DontOfferConversation()); + } + } - if ( from is PlayerMobile player ) - { - if ( player.Quest is AmbitiousQueenQuest qs && qs.RedSolen == RedSolen ) - { - QuestObjective obj = qs.FindObjective( typeof( GatherFungiObjective ) ); + public override bool OnDragDrop(Mobile from, Item dropped) + { + Direction = GetDirectionTo(from); - if ( obj != null && !obj.Completed ) - { - if ( dropped is ZoogiFungus fungi ) - { - if ( fungi.Amount >= 50 ) - { - obj.Complete(); + if (from is PlayerMobile player) + if (player.Quest is AmbitiousQueenQuest qs && qs.RedSolen == RedSolen) + { + QuestObjective obj = qs.FindObjective(typeof(GatherFungiObjective)); - fungi.Amount -= 50; + if (obj != null && !obj.Completed) + if (dropped is ZoogiFungus fungi) + { + if (fungi.Amount >= 50) + { + obj.Complete(); - if ( fungi.Amount == 0 ) - { - fungi.Delete(); - return true; - } + fungi.Amount -= 50; - return false; - } + if (fungi.Amount == 0) + { + fungi.Delete(); + return true; + } - SayTo( player, 1054072 ); // Our arrangement was for 50 of the zoogi fungus. Please return to me when you have that amount. - return false; - } - } - } - } + return false; + } - return base.OnDragDrop( from, dropped ); - } + SayTo(player, + 1054072); // Our arrangement was for 50 of the zoogi fungus. Please return to me when you have that amount. + return false; + } + } - public BaseAmbitiousSolenQueen( Serial serial ) : base( serial ) - { - } + return base.OnDragDrop(from, dropped); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class RedAmbitiousSolenQueen : BaseAmbitiousSolenQueen - { - public override bool RedSolen => true; + public class RedAmbitiousSolenQueen : BaseAmbitiousSolenQueen + { + [Constructible] + public RedAmbitiousSolenQueen() + { + } - [Constructible] - public RedAmbitiousSolenQueen() - { - } + public RedAmbitiousSolenQueen(Serial serial) : base(serial) + { + } - public RedAmbitiousSolenQueen( Serial serial ) : base( serial ) - { - } + public override bool RedSolen => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BlackAmbitiousSolenQueen : BaseAmbitiousSolenQueen - { - public override bool RedSolen => false; + public class BlackAmbitiousSolenQueen : BaseAmbitiousSolenQueen + { + [Constructible] + public BlackAmbitiousSolenQueen() + { + } - [Constructible] - public BlackAmbitiousSolenQueen() - { - } + public BlackAmbitiousSolenQueen(Serial serial) : base(serial) + { + } - public BlackAmbitiousSolenQueen( Serial serial ) : base( serial ) - { - } + public override bool RedSolen => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Ambitious Solen Queen/Objectives.cs b/Scripts/Engines/Quests/Ambitious Solen Queen/Objectives.cs index 6314fea1c..088517716 100644 --- a/Scripts/Engines/Quests/Ambitious Solen Queen/Objectives.cs +++ b/Scripts/Engines/Quests/Ambitious Solen Queen/Objectives.cs @@ -1,138 +1,127 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ambitious { - public class KillQueensObjective : QuestObjective - { - public override object Message => ((AmbitiousQueenQuest)System).RedSolen ? 1054062 : 1054063; + public class KillQueensObjective : QuestObjective + { + public override object Message => ((AmbitiousQueenQuest)System).RedSolen ? 1054062 : 1054063; - public override int MaxProgress => 5; + public override int MaxProgress => 5; - public KillQueensObjective() - { - } + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Red/Black Solen Queens killed: + gump.AddHtmlLocalized(70, 260, 270, 100, ((AmbitiousQueenQuest)System).RedSolen ? 1054064 : 1054065, + BaseQuestGump.Blue, false, false); + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, MaxProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Red/Black Solen Queens killed: - gump.AddHtmlLocalized( 70, 260, 270, 100, ((AmbitiousQueenQuest)System).RedSolen ? 1054064 : 1054065, BaseQuestGump.Blue, false, false ); - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, MaxProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } + public override bool IgnoreYoungProtection(Mobile from) + { + if (Completed) + return false; - public override bool IgnoreYoungProtection( Mobile from ) - { - if ( Completed ) - return false; + bool redSolen = ((AmbitiousQueenQuest)System).RedSolen; - bool redSolen = ((AmbitiousQueenQuest)System).RedSolen; + if (redSolen) + return from is RedSolenQueen; + return from is BlackSolenQueen; + } - if ( redSolen ) - return from is RedSolenQueen; - return from is BlackSolenQueen; - } + public override void OnKill(BaseCreature creature, Container corpse) + { + bool redSolen = ((AmbitiousQueenQuest)System).RedSolen; - public override void OnKill( BaseCreature creature, Container corpse ) - { - bool redSolen = ((AmbitiousQueenQuest)System).RedSolen; + if (redSolen) + { + if (creature is RedSolenQueen) + CurProgress++; + } + else + { + if (creature is BlackSolenQueen) + CurProgress++; + } + } - if ( redSolen ) - { - if ( creature is RedSolenQueen ) - CurProgress++; - } - else - { - if ( creature is BlackSolenQueen ) - CurProgress++; - } - } + public override void OnComplete() + { + System.AddObjective(new ReturnAfterKillsObjective()); + } + } - public override void OnComplete() - { - System.AddObjective( new ReturnAfterKillsObjective() ); - } - } + public class ReturnAfterKillsObjective : QuestObjective + { + public override object Message => 1054067; - public class ReturnAfterKillsObjective : QuestObjective - { - public override object Message => 1054067; + public override void OnComplete() + { + System.AddConversation(new GatherFungiConversation()); + } + } - public ReturnAfterKillsObjective() - { - } + public class GatherFungiObjective : QuestObjective + { + public override object Message => 1054069; - public override void OnComplete() - { - System.AddConversation( new GatherFungiConversation() ); - } - } + public override void OnComplete() + { + System.AddConversation(new EndConversation()); + } + } - public class GatherFungiObjective : QuestObjective - { - public override object Message => 1054069; + public class GetRewardObjective : QuestObjective + { + public GetRewardObjective(bool bagOfSending, bool powderOfTranslocation, bool gold) + { + BagOfSending = bagOfSending; + PowderOfTranslocation = powderOfTranslocation; + Gold = gold; + } - public GatherFungiObjective() - { - } + public GetRewardObjective() + { + } - public override void OnComplete() - { - System.AddConversation( new EndConversation() ); - } - } + public override object Message => 1054148; - public class GetRewardObjective : QuestObjective - { - public override object Message => 1054148; + public bool BagOfSending{ get; set; } - public bool BagOfSending { get; set; } + public bool PowderOfTranslocation{ get; set; } - public bool PowderOfTranslocation { get; set; } + public bool Gold{ get; set; } - public bool Gold { get; set; } + public override void OnComplete() + { + System.AddConversation(new End2Conversation()); + } - public GetRewardObjective( bool bagOfSending, bool powderOfTranslocation, bool gold) - { - BagOfSending = bagOfSending; - PowderOfTranslocation = powderOfTranslocation; - Gold = gold; - } + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public GetRewardObjective() - { - } + BagOfSending = reader.ReadBool(); + PowderOfTranslocation = reader.ReadBool(); + Gold = reader.ReadBool(); + } - public override void OnComplete() - { - System.AddConversation( new End2Conversation() ); - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - BagOfSending = reader.ReadBool(); - PowderOfTranslocation = reader.ReadBool(); - Gold = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) BagOfSending ); - writer.Write( (bool) PowderOfTranslocation ); - writer.Write( (bool) Gold ); - } - } -} + writer.Write(BagOfSending); + writer.Write(PowderOfTranslocation); + writer.Write(Gold); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/CollectorQuest.cs b/Scripts/Engines/Quests/Collector/CollectorQuest.cs index 6577a49c1..d8b24691a 100644 --- a/Scripts/Engines/Quests/Collector/CollectorQuest.cs +++ b/Scripts/Engines/Quests/Collector/CollectorQuest.cs @@ -3,86 +3,87 @@ using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public class CollectorQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( DontOfferConversation ), - typeof( DeclineConversation ), - typeof( AcceptConversation ), - typeof( ElwoodDuringFishConversation ), - typeof( ReturnPearlsConversation ), - typeof( AlbertaPaintingConversation ), - typeof( AlbertaStoolConversation ), - typeof( AlbertaEndPaintingConversation ), - typeof( AlbertaAfterPaintingConversation ), - typeof( ElwoodDuringPainting1Conversation ), - typeof( ElwoodDuringPainting2Conversation ), - typeof( ReturnPaintingConversation ), - typeof( GabrielAutographConversation ), - typeof( GabrielNoSheetMusicConversation ), - typeof( NoSheetMusicConversation ), - typeof( GetSheetMusicConversation ), - typeof( GabrielSheetMusicConversation ), - typeof( GabrielIgnoreConversation ), - typeof( ElwoodDuringAutograph1Conversation ), - typeof( ElwoodDuringAutograph2Conversation ), - typeof( ElwoodDuringAutograph3Conversation ), - typeof( ReturnAutographConversation ), - typeof( TomasToysConversation ), - typeof( TomasDuringCollectingConversation ), - typeof( ReturnImagesConversation ), - typeof( ElwoodDuringToys1Conversation ), - typeof( ElwoodDuringToys2Conversation ), - typeof( ElwoodDuringToys3Conversation ), - typeof( FullEndConversation ), - typeof( FishPearlsObjective ), - typeof( ReturnPearlsObjective ), - typeof( FindAlbertaObjective ), - typeof( SitOnTheStoolObjective ), - typeof( ReturnPaintingObjective ), - typeof( FindGabrielObjective ), - typeof( FindSheetMusicObjective ), - typeof( ReturnSheetMusicObjective ), - typeof( ReturnAutographObjective ), - typeof( FindTomasObjective ), - typeof( CaptureImagesObjective ), - typeof( ReturnImagesObjective ), - typeof( ReturnToysObjective ), - typeof( MakeRoomObjective ) - }; + public class CollectorQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(DontOfferConversation), + typeof(DeclineConversation), + typeof(AcceptConversation), + typeof(ElwoodDuringFishConversation), + typeof(ReturnPearlsConversation), + typeof(AlbertaPaintingConversation), + typeof(AlbertaStoolConversation), + typeof(AlbertaEndPaintingConversation), + typeof(AlbertaAfterPaintingConversation), + typeof(ElwoodDuringPainting1Conversation), + typeof(ElwoodDuringPainting2Conversation), + typeof(ReturnPaintingConversation), + typeof(GabrielAutographConversation), + typeof(GabrielNoSheetMusicConversation), + typeof(NoSheetMusicConversation), + typeof(GetSheetMusicConversation), + typeof(GabrielSheetMusicConversation), + typeof(GabrielIgnoreConversation), + typeof(ElwoodDuringAutograph1Conversation), + typeof(ElwoodDuringAutograph2Conversation), + typeof(ElwoodDuringAutograph3Conversation), + typeof(ReturnAutographConversation), + typeof(TomasToysConversation), + typeof(TomasDuringCollectingConversation), + typeof(ReturnImagesConversation), + typeof(ElwoodDuringToys1Conversation), + typeof(ElwoodDuringToys2Conversation), + typeof(ElwoodDuringToys3Conversation), + typeof(FullEndConversation), + typeof(FishPearlsObjective), + typeof(ReturnPearlsObjective), + typeof(FindAlbertaObjective), + typeof(SitOnTheStoolObjective), + typeof(ReturnPaintingObjective), + typeof(FindGabrielObjective), + typeof(FindSheetMusicObjective), + typeof(ReturnSheetMusicObjective), + typeof(ReturnAutographObjective), + typeof(FindTomasObjective), + typeof(CaptureImagesObjective), + typeof(ReturnImagesObjective), + typeof(ReturnToysObjective), + typeof(MakeRoomObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public CollectorQuest(PlayerMobile from) : base(from) + { + } - public override object Name => "Collector's Quest"; + // Serialization + public CollectorQuest() + { + } - public override object OfferMessage => 1055081; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override TimeSpan RestartDelay => TimeSpan.Zero; - public override bool IsTutorial => false; + public override object Name => "Collector's Quest"; - public override int Picture => 0x15A9; + public override object OfferMessage => 1055081; - public CollectorQuest( PlayerMobile from ) : base( from ) - { - } + public override TimeSpan RestartDelay => TimeSpan.Zero; + public override bool IsTutorial => false; - // Serialization - public CollectorQuest() - { - } + public override int Picture => 0x15A9; - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } + AddConversation(new AcceptConversation()); + } - public override void Decline() - { - base.Decline(); + public override void Decline() + { + base.Decline(); - AddConversation( new DeclineConversation() ); - } - } -} + AddConversation(new DeclineConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Conversations.cs b/Scripts/Engines/Quests/Collector/Conversations.cs index eaaa978e2..f0923e572 100644 --- a/Scripts/Engines/Quests/Collector/Conversations.cs +++ b/Scripts/Engines/Quests/Collector/Conversations.cs @@ -1,382 +1,266 @@ namespace Server.Engines.Quests.Collector { - public class DontOfferConversation : QuestConversation - { - public override object Message => 1055080; - - public override bool Logged => false; + public class DontOfferConversation : QuestConversation + { + public override object Message => 1055080; + + public override bool Logged => false; + } + + public class DeclineConversation : QuestConversation + { + public override object Message => 1055082; + + public override bool Logged => false; + } + + public class AcceptConversation : QuestConversation + { + public override object Message => 1055083; + + public override void OnRead() + { + System.AddObjective(new FishPearlsObjective()); + } + } + + public class ElwoodDuringFishConversation : QuestConversation + { + public override object Message => 1055089; + + public override bool Logged => false; + } + + public class ReturnPearlsConversation : QuestConversation + { + public override object Message => 1055090; + + public override void OnRead() + { + System.AddObjective(new FindAlbertaObjective()); + } + } + + public class AlbertaPaintingConversation : QuestConversation + { + public override object Message => 1055092; + + public override void OnRead() + { + System.AddObjective(new SitOnTheStoolObjective()); + } + } + + public class AlbertaStoolConversation : QuestConversation + { + public override object Message => 1055096; + + public override bool Logged => false; + } + + public class AlbertaEndPaintingConversation : QuestConversation + { + public override object Message => 1055098; + + public override void OnRead() + { + System.AddObjective(new ReturnPaintingObjective()); + } + } + + public class AlbertaAfterPaintingConversation : QuestConversation + { + public override object Message => 1055102; + + public override bool Logged => false; + } - public DontOfferConversation() - { - } - } + public class ElwoodDuringPainting1Conversation : QuestConversation + { + public override object Message => 1055094; + + public override bool Logged => false; + } + + public class ElwoodDuringPainting2Conversation : QuestConversation + { + public override object Message => 1055097; + + public override bool Logged => false; + } + + public class ReturnPaintingConversation : QuestConversation + { + public override object Message => 1055100; + + public override void OnRead() + { + System.AddObjective(new FindGabrielObjective()); + } + } + + public class GabrielAutographConversation : QuestConversation + { + public override object Message => 1055103; + + public override void OnRead() + { + System.AddObjective(new FindSheetMusicObjective(true)); + } + } + + public class GabrielNoSheetMusicConversation : QuestConversation + { + public override object Message => 1055111; + + public override bool Logged => false; + } + + public class NoSheetMusicConversation : QuestConversation + { + public override object Message => 1055106; + + public override bool Logged => false; + } + + public class GetSheetMusicConversation : QuestConversation + { + public override object Message => 1055109; + + public override void OnRead() + { + System.AddObjective(new ReturnSheetMusicObjective()); + } + } + + public class GabrielSheetMusicConversation : QuestConversation + { + public override object Message => 1055113; + + public override void OnRead() + { + System.AddObjective(new ReturnAutographObjective()); + } + } + + public class GabrielIgnoreConversation : QuestConversation + { + public override object Message => 1055118; + + public override bool Logged => false; + } + + public class ElwoodDuringAutograph1Conversation : QuestConversation + { + public override object Message => 1055105; + + public override bool Logged => false; + } - public class DeclineConversation : QuestConversation - { - public override object Message => 1055082; + public class ElwoodDuringAutograph2Conversation : QuestConversation + { + public override object Message => 1055112; + + public override bool Logged => false; + } + + public class ElwoodDuringAutograph3Conversation : QuestConversation + { + public override object Message => 1055115; + + public override bool Logged => false; + } + + public class ReturnAutographConversation : QuestConversation + { + public override object Message => 1055116; + + public override void OnRead() + { + System.AddObjective(new FindTomasObjective()); + } + } + + public class TomasToysConversation : QuestConversation + { + public override object Message => 1055119; + + public override void OnRead() + { + System.AddObjective(new CaptureImagesObjective(true)); + } + } + + public class TomasDuringCollectingConversation : QuestConversation + { + public override object Message => 1055129; + + public override bool Logged => false; + } + + public class ReturnImagesConversation : QuestConversation + { + public override object Message => 1055131; + + public override void OnRead() + { + System.AddObjective(new ReturnToysObjective()); + } + } + + public class ElwoodDuringToys1Conversation : QuestConversation + { + public override object Message => 1055123; + + public override bool Logged => false; + } + + public class ElwoodDuringToys2Conversation : QuestConversation + { + public override object Message => 1055130; + + public override bool Logged => false; + } + + public class ElwoodDuringToys3Conversation : QuestConversation + { + public override object Message => 1055133; + + public override bool Logged => false; + } + + public class EndConversation : QuestConversation + { + public override object Message => 1055134; + + public override void OnRead() + { + System.Complete(); + } + } + + public class FullEndConversation : QuestConversation + { + private bool m_Logged; - public override bool Logged => false; - - public DeclineConversation() - { - } - } - - public class AcceptConversation : QuestConversation - { - public override object Message => 1055083; - - public AcceptConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FishPearlsObjective() ); - } - } - - public class ElwoodDuringFishConversation : QuestConversation - { - public override object Message => 1055089; - - public override bool Logged => false; - - public ElwoodDuringFishConversation() - { - } - } - - public class ReturnPearlsConversation : QuestConversation - { - public override object Message => 1055090; - - public ReturnPearlsConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindAlbertaObjective() ); - } - } - - public class AlbertaPaintingConversation : QuestConversation - { - public override object Message => 1055092; - - public AlbertaPaintingConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new SitOnTheStoolObjective() ); - } - } - - public class AlbertaStoolConversation : QuestConversation - { - public override object Message => 1055096; - - public override bool Logged => false; - - public AlbertaStoolConversation() - { - } - } - - public class AlbertaEndPaintingConversation : QuestConversation - { - public override object Message => 1055098; - - public AlbertaEndPaintingConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnPaintingObjective() ); - } - } - - public class AlbertaAfterPaintingConversation : QuestConversation - { - public override object Message => 1055102; - - public override bool Logged => false; - - public AlbertaAfterPaintingConversation() - { - } - } - - public class ElwoodDuringPainting1Conversation : QuestConversation - { - public override object Message => 1055094; - - public override bool Logged => false; - - public ElwoodDuringPainting1Conversation() - { - } - } - - public class ElwoodDuringPainting2Conversation : QuestConversation - { - public override object Message => 1055097; - - public override bool Logged => false; - - public ElwoodDuringPainting2Conversation() - { - } - } - - public class ReturnPaintingConversation : QuestConversation - { - public override object Message => 1055100; - - public ReturnPaintingConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindGabrielObjective() ); - } - } - - public class GabrielAutographConversation : QuestConversation - { - public override object Message => 1055103; - - public GabrielAutographConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindSheetMusicObjective( true ) ); - } - } - - public class GabrielNoSheetMusicConversation : QuestConversation - { - public override object Message => 1055111; - - public override bool Logged => false; - - public GabrielNoSheetMusicConversation() - { - } - } - - public class NoSheetMusicConversation : QuestConversation - { - public override object Message => 1055106; - - public override bool Logged => false; - - public NoSheetMusicConversation() - { - } - } - - public class GetSheetMusicConversation : QuestConversation - { - public override object Message => 1055109; - - public GetSheetMusicConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnSheetMusicObjective() ); - } - } - - public class GabrielSheetMusicConversation : QuestConversation - { - public override object Message => 1055113; - - public GabrielSheetMusicConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnAutographObjective() ); - } - } - - public class GabrielIgnoreConversation : QuestConversation - { - public override object Message => 1055118; - - public override bool Logged => false; - - public GabrielIgnoreConversation() - { - } - } - - public class ElwoodDuringAutograph1Conversation : QuestConversation - { - public override object Message => 1055105; - - public override bool Logged => false; - - public ElwoodDuringAutograph1Conversation() - { - } - } - - public class ElwoodDuringAutograph2Conversation : QuestConversation - { - public override object Message => 1055112; - - public override bool Logged => false; - - public ElwoodDuringAutograph2Conversation() - { - } - } - - public class ElwoodDuringAutograph3Conversation : QuestConversation - { - public override object Message => 1055115; - - public override bool Logged => false; - - public ElwoodDuringAutograph3Conversation() - { - } - } - - public class ReturnAutographConversation : QuestConversation - { - public override object Message => 1055116; - - public ReturnAutographConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindTomasObjective() ); - } - } - - public class TomasToysConversation : QuestConversation - { - public override object Message => 1055119; - - public TomasToysConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new CaptureImagesObjective( true ) ); - } - } - - public class TomasDuringCollectingConversation : QuestConversation - { - public override object Message => 1055129; - - public override bool Logged => false; - - public TomasDuringCollectingConversation() - { - } - } - - public class ReturnImagesConversation : QuestConversation - { - public override object Message => 1055131; - - public ReturnImagesConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnToysObjective() ); - } - } - - public class ElwoodDuringToys1Conversation : QuestConversation - { - public override object Message => 1055123; - - public override bool Logged => false; - - public ElwoodDuringToys1Conversation() - { - } - } - - public class ElwoodDuringToys2Conversation : QuestConversation - { - public override object Message => 1055130; - - public override bool Logged => false; - - public ElwoodDuringToys2Conversation() - { - } - } - - public class ElwoodDuringToys3Conversation : QuestConversation - { - public override object Message => 1055133; - - public override bool Logged => false; - - public ElwoodDuringToys3Conversation() - { - } - } - - public class EndConversation : QuestConversation - { - public override object Message => 1055134; - - public EndConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } - - public class FullEndConversation : QuestConversation - { - private bool m_Logged; - - public override object Message => 1055135; - - public override bool Logged => m_Logged; - - public FullEndConversation( bool logged ) - { - m_Logged = logged; - } - - public FullEndConversation() - { - m_Logged = true; - } - - public override void OnRead() - { - if ( m_Logged ) - System.AddObjective( new MakeRoomObjective() ); - } - } -} + public FullEndConversation(bool logged) + { + m_Logged = logged; + } + + public FullEndConversation() + { + m_Logged = true; + } + + public override object Message => 1055135; + + public override bool Logged => m_Logged; + + public override void OnRead() + { + if (m_Logged) + System.AddObjective(new MakeRoomObjective()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Items/EnchantedPaints.cs b/Scripts/Engines/Quests/Collector/Items/EnchantedPaints.cs index fa50614b9..102b9351c 100644 --- a/Scripts/Engines/Quests/Collector/Items/EnchantedPaints.cs +++ b/Scripts/Engines/Quests/Collector/Items/EnchantedPaints.cs @@ -3,125 +3,127 @@ using Server.Targeting; namespace Server.Engines.Quests.Collector { - public class EnchantedPaints : QuestItem - { - [Constructible] - public EnchantedPaints() : base( 0xFC1 ) - { - LootType = LootType.Blessed; + public class EnchantedPaints : QuestItem + { + [Constructible] + public EnchantedPaints() : base(0xFC1) + { + LootType = LootType.Blessed; - Weight = 1.0; - } + Weight = 1.0; + } - public EnchantedPaints( Serial serial ) : base( serial ) - { - } + public EnchantedPaints(Serial serial) : base(serial) + { + } - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is CollectorQuest); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is CollectorQuest); - /*return !( qs.IsObjectiveInProgress( typeof( CaptureImagesObjective ) ) - || qs.IsObjectiveInProgress( typeof( ReturnImagesObjective ) ) );*/ - } + /*return !( qs.IsObjectiveInProgress( typeof( CaptureImagesObjective ) ) + || qs.IsObjectiveInProgress( typeof( ReturnImagesObjective ) ) );*/ + } - public override void OnDoubleClick( Mobile from ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + public override void OnDoubleClick(Mobile from) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( CaptureImagesObjective ) ) ) - { - player.SendAsciiMessage( 0x59, "Target the creature whose image you wish to create." ); - player.Target = new InternalTarget( this ); + if (qs is CollectorQuest) + if (qs.IsObjectiveInProgress(typeof(CaptureImagesObjective))) + { + player.SendAsciiMessage(0x59, "Target the creature whose image you wish to create."); + player.Target = new InternalTarget(this); - return; - } - } - } + return; + } + } - from.SendLocalizedMessage( 1010085 ); // You cannot use this. - } + from.SendLocalizedMessage(1010085); // You cannot use this. + } - private class InternalTarget : Target - { - private EnchantedPaints m_Paints; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public InternalTarget( EnchantedPaints paints ) : base( -1, false, TargetFlags.None ) - { - CheckLOS = false; - m_Paints = paints; - } + writer.Write(0); // version + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Paints.Deleted || !m_Paints.IsChildOf( from.Backpack ) ) - return; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + int version = reader.ReadInt(); + } - if ( qs is CollectorQuest ) - { - if ( qs.FindObjective( typeof( CaptureImagesObjective ) ) is CaptureImagesObjective obj && !obj.Completed ) - { - if ( targeted is Mobile ) - { - CaptureResponse response = obj.CaptureImage(( targeted.GetType().Name=="GreaterMongbat" ? new Mongbat().GetType() : targeted.GetType() ), out ImageType image ); + private class InternalTarget : Target + { + private EnchantedPaints m_Paints; - switch ( response ) - { - case CaptureResponse.Valid: - { - player.SendLocalizedMessage( 1055125 ); // The enchanted paints swirl for a moment then an image begins to take shape. *Click* - player.AddToBackpack( new PaintedImage( image ) ); + public InternalTarget(EnchantedPaints paints) : base(-1, false, TargetFlags.None) + { + CheckLOS = false; + m_Paints = paints; + } - break; - } - case CaptureResponse.AlreadyDone: - { - player.SendAsciiMessage( 0x2C, "You have already captured the image of this creature" ); + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Paints.Deleted || !m_Paints.IsChildOf(from.Backpack)) + return; - break; - } - case CaptureResponse.Invalid: - { - player.SendLocalizedMessage( 1055124 ); // You have no interest in capturing the image of this creature. + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - break; - } - } - } - else - { - player.SendAsciiMessage( 0x35, "You have no interest in that." ); - } + if (qs is CollectorQuest) + if (qs.FindObjective(typeof(CaptureImagesObjective)) is CaptureImagesObjective obj && !obj.Completed) + { + if (targeted is Mobile) + { + CaptureResponse response = obj.CaptureImage( + targeted.GetType().Name == "GreaterMongbat" + ? new Mongbat().GetType() + : targeted.GetType(), out ImageType image); - return; - } - } - } + switch (response) + { + case CaptureResponse.Valid: + { + player.SendLocalizedMessage( + 1055125); // The enchanted paints swirl for a moment then an image begins to take shape. *Click* + player.AddToBackpack(new PaintedImage(image)); - from.SendLocalizedMessage( 1010085 ); // You cannot use this. - } - } + break; + } + case CaptureResponse.AlreadyDone: + { + player.SendAsciiMessage(0x2C, + "You have already captured the image of this creature"); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + break; + } + case CaptureResponse.Invalid: + { + player.SendLocalizedMessage( + 1055124); // You have no interest in capturing the image of this creature. - writer.Write( (int) 0 ); // version - } + break; + } + } + } + else + { + player.SendAsciiMessage(0x35, "You have no interest in that."); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return; + } + } - int version = reader.ReadInt(); - } - } -} + from.SendLocalizedMessage(1010085); // You cannot use this. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Items/ImageType.cs b/Scripts/Engines/Quests/Collector/Items/ImageType.cs index b3f6dc9a2..8b8bb405a 100644 --- a/Scripts/Engines/Quests/Collector/Items/ImageType.cs +++ b/Scripts/Engines/Quests/Collector/Items/ImageType.cs @@ -4,99 +4,100 @@ using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public enum ImageType - { - Betrayer, - Bogling, - BogThing, - Gazer, - Beetle, - GiantBlackWidow, - Scorpion, - JukaMage, - JukaWarrior, - Lich, - MeerMage, - MeerWarrior, - Mongbat, - Mummy, - Pixie, - PlagueBeast, - SandVortex, - StoneGargoyle, - SwampDragon, - Wisp, - Juggernaut - } + public enum ImageType + { + Betrayer, + Bogling, + BogThing, + Gazer, + Beetle, + GiantBlackWidow, + Scorpion, + JukaMage, + JukaWarrior, + Lich, + MeerMage, + MeerWarrior, + Mongbat, + Mummy, + Pixie, + PlagueBeast, + SandVortex, + StoneGargoyle, + SwampDragon, + Wisp, + Juggernaut + } - public class ImageTypeInfo - { - private static readonly ImageTypeInfo[] m_Table = { - new ImageTypeInfo( 9734, typeof( Betrayer ), 75, 45 ), - new ImageTypeInfo( 9735, typeof( Bogling ), 75, 45 ), - new ImageTypeInfo( 9736, typeof( BogThing ), 60, 47 ), - new ImageTypeInfo( 9615, typeof( Gazer ), 75, 45 ), - new ImageTypeInfo( 9743, typeof( Beetle ), 60, 55 ), - new ImageTypeInfo( 9667, typeof( GiantBlackWidow ), 55, 52 ), - new ImageTypeInfo( 9657, typeof( Scorpion ), 65, 47 ), - new ImageTypeInfo( 9758, typeof( JukaMage ), 75, 45 ), - new ImageTypeInfo( 9759, typeof( JukaWarrior ), 75, 45 ), - new ImageTypeInfo( 9636, typeof( Lich ), 75, 45 ), - new ImageTypeInfo( 9756, typeof( MeerMage ), 75, 45 ), - new ImageTypeInfo( 9757, typeof( MeerWarrior ), 75, 45 ), - new ImageTypeInfo( 9638, typeof( Mongbat ), 70, 50 ), - new ImageTypeInfo( 9639, typeof( Mummy ), 75, 45 ), - new ImageTypeInfo( 9654, typeof( Pixie ), 75, 45 ), - new ImageTypeInfo( 9747, typeof( PlagueBeast ), 60, 45 ), - new ImageTypeInfo( 9750, typeof( SandVortex ), 60, 43 ), - new ImageTypeInfo( 9614, typeof( StoneGargoyle ), 75, 45 ), - new ImageTypeInfo( 9753, typeof( SwampDragon ), 50, 55 ), - new ImageTypeInfo( 8448, typeof( Wisp ), 75, 45 ), - new ImageTypeInfo( 9746, typeof( Juggernaut ), 55, 38 ) - }; + public class ImageTypeInfo + { + private static readonly ImageTypeInfo[] m_Table = + { + new ImageTypeInfo(9734, typeof(Betrayer), 75, 45), + new ImageTypeInfo(9735, typeof(Bogling), 75, 45), + new ImageTypeInfo(9736, typeof(BogThing), 60, 47), + new ImageTypeInfo(9615, typeof(Gazer), 75, 45), + new ImageTypeInfo(9743, typeof(Beetle), 60, 55), + new ImageTypeInfo(9667, typeof(GiantBlackWidow), 55, 52), + new ImageTypeInfo(9657, typeof(Scorpion), 65, 47), + new ImageTypeInfo(9758, typeof(JukaMage), 75, 45), + new ImageTypeInfo(9759, typeof(JukaWarrior), 75, 45), + new ImageTypeInfo(9636, typeof(Lich), 75, 45), + new ImageTypeInfo(9756, typeof(MeerMage), 75, 45), + new ImageTypeInfo(9757, typeof(MeerWarrior), 75, 45), + new ImageTypeInfo(9638, typeof(Mongbat), 70, 50), + new ImageTypeInfo(9639, typeof(Mummy), 75, 45), + new ImageTypeInfo(9654, typeof(Pixie), 75, 45), + new ImageTypeInfo(9747, typeof(PlagueBeast), 60, 45), + new ImageTypeInfo(9750, typeof(SandVortex), 60, 43), + new ImageTypeInfo(9614, typeof(StoneGargoyle), 75, 45), + new ImageTypeInfo(9753, typeof(SwampDragon), 50, 55), + new ImageTypeInfo(8448, typeof(Wisp), 75, 45), + new ImageTypeInfo(9746, typeof(Juggernaut), 55, 38) + }; - public static ImageTypeInfo Get( ImageType image ) - { - int index = (int)image; - if ( index >= 0 && index < m_Table.Length ) - return m_Table[index]; - return m_Table[0]; - } + public ImageTypeInfo(int figurine, Type type, int x, int y) + { + Figurine = figurine; + Type = type; + X = x; + Y = y; + } - public static ImageType[] RandomList( int count ) - { - ArrayList list = new ArrayList( m_Table.Length ); - for ( int i = 0; i < m_Table.Length; i++ ) - list.Add( (ImageType)i ); + public int Figurine{ get; } - ImageType[] images = new ImageType[count]; + public Type Type{ get; } - for ( int i = 0; i < images.Length; i++ ) - { - int index = Utility.Random( list.Count ); - images[i] = (ImageType)list[index]; + public int Name => Figurine < 0x4000 ? 1020000 + Figurine : 1078872 + Figurine; + public int X{ get; } - list.RemoveAt( index ); - } + public int Y{ get; } - return images; - } + public static ImageTypeInfo Get(ImageType image) + { + int index = (int)image; + if (index >= 0 && index < m_Table.Length) + return m_Table[index]; + return m_Table[0]; + } - public int Figurine { get; } + public static ImageType[] RandomList(int count) + { + ArrayList list = new ArrayList(m_Table.Length); + for (int i = 0; i < m_Table.Length; i++) + list.Add((ImageType)i); - public Type Type { get; } + ImageType[] images = new ImageType[count]; - public int Name => Figurine < 0x4000 ? 1020000 + Figurine : 1078872 + Figurine; - public int X { get; } + for (int i = 0; i < images.Length; i++) + { + int index = Utility.Random(list.Count); + images[i] = (ImageType)list[index]; - public int Y { get; } + list.RemoveAt(index); + } - public ImageTypeInfo( int figurine, Type type, int x, int y ) - { - Figurine = figurine; - Type = type; - X = x; - Y = y; - } - } -} + return images; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Items/Obsidian.cs b/Scripts/Engines/Quests/Collector/Items/Obsidian.cs index ff61b06b3..a0f95a65f 100644 --- a/Scripts/Engines/Quests/Collector/Items/Obsidian.cs +++ b/Scripts/Engines/Quests/Collector/Items/Obsidian.cs @@ -1,257 +1,265 @@ using System.Collections.Generic; +using Server.ContextMenus; using Server.Network; using Server.Targeting; -using Server.ContextMenus; namespace Server.Engines.Quests.Collector { - public class Obsidian : Item - { - private static readonly string[] m_Names = { - null, - "an aggressive cavalier", - "a beguiling rogue", - "a benevolent physician", - "a brilliant artisan", - "a capricious adventurer", - "a clever beggar", - "a convincing charlatan", - "a creative inventor", - "a creative tinker", - "a cunning knave", - "a dauntless explorer", - "a despicable ruffian", - "an earnest malcontent", - "an exultant animal tamer", - "a famed adventurer", - "a fanatical crusader", - "a fastidious clerk", - "a fearless hunter", - "a festive harlequin", - "a fidgety assassin", - "a fierce soldier", - "a fierce warrior", - "a frugal magnate", - "a glib pundit", - "a gnomic shaman", - "a graceful noblewoman", - "a idiotic madman", - "a imaginative designer", - "an inept conjurer", - "an innovative architect", - "an inventive blacksmith", - "a judicious mayor", - "a masterful chef", - "a masterful woodworker", - "a melancholy clown", - "a melodic bard", - "a merciful guard", - "a mirthful jester", - "a nervous surgeon", - "a peaceful scholar", - "a prolific gardener", - "a quixotic knight", - "a regal aristocrat", - "a resourceful smith", - "a reticent alchemist", - "a sanctified priest", - "a scheming patrician", - "a shrewd mage", - "a singing minstrel", - "a skilled tailor", - "a squeamish assassin", - "a stoic swordsman", - "a studious scribe", - "a thought provoking writer", - "a treacherous scoundrel", - "a troubled poet", - "an unflappable wizard", - "a valiant warrior", - "a wayward fool" - }; + public class Obsidian : Item + { + private const int m_Partial = 2; + private const int m_Completed = 10; - public static string RandomName( Mobile from ) - { - int index = Utility.Random( m_Names.Length ); - if ( m_Names[index] == null ) - return from.Name; - return m_Names[index]; - } + private static readonly string[] m_Names = + { + null, + "an aggressive cavalier", + "a beguiling rogue", + "a benevolent physician", + "a brilliant artisan", + "a capricious adventurer", + "a clever beggar", + "a convincing charlatan", + "a creative inventor", + "a creative tinker", + "a cunning knave", + "a dauntless explorer", + "a despicable ruffian", + "an earnest malcontent", + "an exultant animal tamer", + "a famed adventurer", + "a fanatical crusader", + "a fastidious clerk", + "a fearless hunter", + "a festive harlequin", + "a fidgety assassin", + "a fierce soldier", + "a fierce warrior", + "a frugal magnate", + "a glib pundit", + "a gnomic shaman", + "a graceful noblewoman", + "a idiotic madman", + "a imaginative designer", + "an inept conjurer", + "an innovative architect", + "an inventive blacksmith", + "a judicious mayor", + "a masterful chef", + "a masterful woodworker", + "a melancholy clown", + "a melodic bard", + "a merciful guard", + "a mirthful jester", + "a nervous surgeon", + "a peaceful scholar", + "a prolific gardener", + "a quixotic knight", + "a regal aristocrat", + "a resourceful smith", + "a reticent alchemist", + "a sanctified priest", + "a scheming patrician", + "a shrewd mage", + "a singing minstrel", + "a skilled tailor", + "a squeamish assassin", + "a stoic swordsman", + "a studious scribe", + "a thought provoking writer", + "a treacherous scoundrel", + "a troubled poet", + "an unflappable wizard", + "a valiant warrior", + "a wayward fool" + }; - private const int m_Partial = 2; - private const int m_Completed = 10; + private int m_Quantity; + private string m_StatueName; - private int m_Quantity; - private string m_StatueName; + [Constructible] + public Obsidian() : base(0x1EA7) + { + Hue = 0x497; - [CommandProperty( AccessLevel.GameMaster )] - public int Quantity - { - get => m_Quantity; - set - { - if ( value <= 1 ) - m_Quantity = 1; - else if ( value >= m_Completed ) - m_Quantity = m_Completed; - else - m_Quantity = value; + m_Quantity = 1; + m_StatueName = ""; + } - if ( m_Quantity < m_Partial ) - ItemID = 0x1EA7; - else if ( m_Quantity < m_Completed ) - ItemID = 0x1F13; - else - ItemID = 0x12CB; + public Obsidian(Serial serial) : base(serial) + { + } - InvalidateProperties(); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public int Quantity + { + get => m_Quantity; + set + { + if (value <= 1) + m_Quantity = 1; + else if (value >= m_Completed) + m_Quantity = m_Completed; + else + m_Quantity = value; - [CommandProperty( AccessLevel.GameMaster )] - public string StatueName - { - get => m_StatueName; - set { m_StatueName = value; InvalidateProperties(); } - } + if (m_Quantity < m_Partial) + ItemID = 0x1EA7; + else if (m_Quantity < m_Completed) + ItemID = 0x1F13; + else + ItemID = 0x12CB; - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + InvalidateProperties(); + } + } - [Constructible] - public Obsidian() : base( 0x1EA7 ) - { - Hue = 0x497; + [CommandProperty(AccessLevel.GameMaster)] + public string StatueName + { + get => m_StatueName; + set + { + m_StatueName = value; + InvalidateProperties(); + } + } - m_Quantity = 1; - m_StatueName = ""; - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_Quantity < m_Partial ) - list.Add( 1055137 ); // a section of an obsidian statue - else if ( m_Quantity < m_Completed ) - list.Add( 1055138 ); // a partially reconstructed obsidian statue - else - list.Add( 1055139, m_StatueName ); // an obsidian statue of ~1_STATUE_NAME~ - } + public static string RandomName(Mobile from) + { + int index = Utility.Random(m_Names.Length); + if (m_Names[index] == null) + return from.Name; + return m_Names[index]; + } - public override void OnSingleClick( Mobile from ) - { - if ( m_Quantity < m_Partial ) - LabelTo( from, 1055137 ); // a section of an obsidian statue - else if ( m_Quantity < m_Completed ) - LabelTo( from, 1055138 ); // a partially reconstructed obsidian statue - else - LabelTo( from, 1055139, m_StatueName ); // an obsidian statue of ~1_STATUE_NAME~ - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_Quantity < m_Partial) + list.Add(1055137); // a section of an obsidian statue + else if (m_Quantity < m_Completed) + list.Add(1055138); // a partially reconstructed obsidian statue + else + list.Add(1055139, m_StatueName); // an obsidian statue of ~1_STATUE_NAME~ + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void OnSingleClick(Mobile from) + { + if (m_Quantity < m_Partial) + LabelTo(from, 1055137); // a section of an obsidian statue + else if (m_Quantity < m_Completed) + LabelTo(from, 1055138); // a partially reconstructed obsidian statue + else + LabelTo(from, 1055139, m_StatueName); // an obsidian statue of ~1_STATUE_NAME~ + } - if ( from.Alive && m_Quantity >= m_Partial && m_Quantity < m_Completed && IsChildOf( from.Backpack ) ) - list.Add( new DisassembleEntry( this ) ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - private class DisassembleEntry : ContextMenuEntry - { - private Obsidian m_Obsidian; + if (from.Alive && m_Quantity >= m_Partial && m_Quantity < m_Completed && IsChildOf(from.Backpack)) + list.Add(new DisassembleEntry(this)); + } - public DisassembleEntry( Obsidian obsidian ) : base( 6142 ) - { - m_Obsidian = obsidian; - } + public override void OnDoubleClick(Mobile from) + { + if (m_Quantity < m_Completed) + { + if (!IsChildOf(from.Backpack)) + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x2C, 3, 500309, "", + "")); // Nothing Happens. + else + from.Target = new InternalTarget(this); + } + } - public override void OnClick() - { - Mobile from = Owner.From; - if ( !m_Obsidian.Deleted && m_Obsidian.Quantity >= m_Partial && m_Obsidian.Quantity < m_Completed && m_Obsidian.IsChildOf( from.Backpack ) && from.CheckAlive() ) - { - for ( int i = 0; i < m_Obsidian.Quantity - 1; i++ ) - from.AddToBackpack( new Obsidian() ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Obsidian.Quantity = 1; - } - } - } + writer.Write(0); // version - public override void OnDoubleClick( Mobile from ) - { - if ( m_Quantity < m_Completed ) - { - if ( !IsChildOf( from.Backpack ) ) - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x2C, 3, 500309, "", "" ) ); // Nothing Happens. - else - from.Target = new InternalTarget( this ); - } - } + writer.WriteEncodedInt(m_Quantity); + writer.Write(m_StatueName); + } - private class InternalTarget : Target - { - private Obsidian m_Obsidian; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalTarget( Obsidian obsidian ) : base( -1, false, TargetFlags.None ) - { - m_Obsidian = obsidian; - } + int version = reader.ReadInt(); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Obsidian.Deleted || m_Obsidian.Quantity >= m_Completed || !(targeted is Item targ) ) - return; + m_Quantity = reader.ReadEncodedInt(); + m_StatueName = Utility.Intern(reader.ReadString()); + } - if ( m_Obsidian.IsChildOf( from.Backpack ) && targ.IsChildOf( from.Backpack ) && targ is Obsidian targObsidian && targ != m_Obsidian ) - { - if ( targObsidian.Quantity < m_Completed ) - { - if ( targObsidian.Quantity + m_Obsidian.Quantity <= m_Completed ) - { - targObsidian.Quantity += m_Obsidian.Quantity; - m_Obsidian.Delete(); - } - else - { - int delta = m_Completed - targObsidian.Quantity; - targObsidian.Quantity += delta; - m_Obsidian.Quantity -= delta; - } + private class DisassembleEntry : ContextMenuEntry + { + private Obsidian m_Obsidian; - if ( targObsidian.Quantity >= m_Completed ) - targObsidian.StatueName = RandomName( from ); + public DisassembleEntry(Obsidian obsidian) : base(6142) + { + m_Obsidian = obsidian; + } - from.Send( new AsciiMessage( targObsidian.Serial, targObsidian.ItemID, MessageType.Regular, 0x59, 3, m_Obsidian.Name, "Something Happened." ) ); + public override void OnClick() + { + Mobile from = Owner.From; + if (!m_Obsidian.Deleted && m_Obsidian.Quantity >= m_Partial && m_Obsidian.Quantity < m_Completed && + m_Obsidian.IsChildOf(from.Backpack) && from.CheckAlive()) + { + for (int i = 0; i < m_Obsidian.Quantity - 1; i++) + from.AddToBackpack(new Obsidian()); - return; - } - } + m_Obsidian.Quantity = 1; + } + } + } - from.Send( new MessageLocalized( m_Obsidian.Serial, m_Obsidian.ItemID, MessageType.Regular, 0x2C, 3, 500309, m_Obsidian.Name, "" ) ); // Nothing Happens. - } - } + private class InternalTarget : Target + { + private Obsidian m_Obsidian; - public Obsidian( Serial serial ) : base( serial ) - { - } + public InternalTarget(Obsidian obsidian) : base(-1, false, TargetFlags.None) + { + m_Obsidian = obsidian; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Obsidian.Deleted || m_Obsidian.Quantity >= m_Completed || !(targeted is Item targ)) + return; - writer.Write( (int) 0 ); // version + if (m_Obsidian.IsChildOf(from.Backpack) && targ.IsChildOf(from.Backpack) && targ is Obsidian targObsidian && + targ != m_Obsidian) + if (targObsidian.Quantity < m_Completed) + { + if (targObsidian.Quantity + m_Obsidian.Quantity <= m_Completed) + { + targObsidian.Quantity += m_Obsidian.Quantity; + m_Obsidian.Delete(); + } + else + { + int delta = m_Completed - targObsidian.Quantity; + targObsidian.Quantity += delta; + m_Obsidian.Quantity -= delta; + } - writer.WriteEncodedInt( m_Quantity ); - writer.Write( (string) m_StatueName ); - } + if (targObsidian.Quantity >= m_Completed) + targObsidian.StatueName = RandomName(from); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + from.Send(new AsciiMessage(targObsidian.Serial, targObsidian.ItemID, MessageType.Regular, 0x59, 3, + m_Obsidian.Name, "Something Happened.")); - int version = reader.ReadInt(); + return; + } - m_Quantity = reader.ReadEncodedInt(); - m_StatueName = Utility.Intern( reader.ReadString() ); - } - } -} + from.Send(new MessageLocalized(m_Obsidian.Serial, m_Obsidian.ItemID, MessageType.Regular, 0x2C, 3, 500309, + m_Obsidian.Name, "")); // Nothing Happens. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Items/PaintedImage.cs b/Scripts/Engines/Quests/Collector/Items/PaintedImage.cs index 2f8f750ea..1bf2a39d6 100644 --- a/Scripts/Engines/Quests/Collector/Items/PaintedImage.cs +++ b/Scripts/Engines/Quests/Collector/Items/PaintedImage.cs @@ -3,82 +3,86 @@ using Server.Network; namespace Server.Engines.Quests.Collector { - public class PaintedImage : Item - { - private ImageType m_Image; + public class PaintedImage : Item + { + private ImageType m_Image; - [CommandProperty( AccessLevel.GameMaster )] - public ImageType Image - { - get => m_Image; - set { m_Image = value; InvalidateProperties(); } - } + [Constructible] + public PaintedImage(ImageType image) : base(0xFF3) + { + Weight = 1.0; + Hue = 0x8FD; - [Constructible] - public PaintedImage( ImageType image ) : base( 0xFF3 ) - { - Weight = 1.0; - Hue = 0x8FD; + m_Image = image; + } - m_Image = image; - } + public PaintedImage(Serial serial) : base(serial) + { + } - public override void AddNameProperty( ObjectPropertyList list ) - { - ImageTypeInfo info = ImageTypeInfo.Get( m_Image ); - list.Add( 1060847, "#1055126\t#" + info.Name ); // a painted image of: - } + [CommandProperty(AccessLevel.GameMaster)] + public ImageType Image + { + get => m_Image; + set + { + m_Image = value; + InvalidateProperties(); + } + } - public override void OnSingleClick( Mobile from ) - { - ImageTypeInfo info = ImageTypeInfo.Get( m_Image ); - LabelTo( from, 1060847, "#1055126\t#" + info.Name ); // a painted image of: - } + public override void AddNameProperty(ObjectPropertyList list) + { + ImageTypeInfo info = ImageTypeInfo.Get(m_Image); + list.Add(1060847, "#1055126\t#" + info.Name); // a painted image of: + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + public override void OnSingleClick(Mobile from) + { + ImageTypeInfo info = ImageTypeInfo.Get(m_Image); + LabelTo(from, 1060847, "#1055126\t#" + info.Name); // a painted image of: + } - from.SendGump( new InternalGump( m_Image ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } - private class InternalGump : Gump - { - public InternalGump( ImageType image ) : base( 75, 25 ) - { - ImageTypeInfo info = ImageTypeInfo.Get( image ); + from.SendGump(new InternalGump(m_Image)); + } - AddBackground( 45, 20, 100, 100, 0xA3C ); - AddBackground( 52, 29, 86, 82, 0xBB8 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - AddItem( info.X, info.Y, info.Figurine ); - } - } + writer.Write(0); // version - public PaintedImage( Serial serial ) : base( serial ) - { - } + writer.WriteEncodedInt((int)m_Image); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version + int version = reader.ReadInt(); - writer.WriteEncodedInt( (int) m_Image ); - } + m_Image = (ImageType)reader.ReadEncodedInt(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + private class InternalGump : Gump + { + public InternalGump(ImageType image) : base(75, 25) + { + ImageTypeInfo info = ImageTypeInfo.Get(image); - int version = reader.ReadInt(); + AddBackground(45, 20, 100, 100, 0xA3C); + AddBackground(52, 29, 86, 82, 0xBB8); - m_Image = (ImageType) reader.ReadEncodedInt(); - } - } + AddItem(info.X, info.Y, info.Figurine); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Mobiles/AlbertaGiacco.cs b/Scripts/Engines/Quests/Collector/Mobiles/AlbertaGiacco.cs index b1b7121b6..b46c7569e 100644 --- a/Scripts/Engines/Quests/Collector/Mobiles/AlbertaGiacco.cs +++ b/Scripts/Engines/Quests/Collector/Mobiles/AlbertaGiacco.cs @@ -1,92 +1,86 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public class AlbertaGiacco : BaseQuester - { - public override string DefaultName => "Alberta Giacco"; + public class AlbertaGiacco : BaseQuester + { + [Constructible] + public AlbertaGiacco() : base("the respected painter") + { + } - [Constructible] - public AlbertaGiacco() : base( "the respected painter" ) - { - } + public AlbertaGiacco(Serial serial) : base(serial) + { + } - public AlbertaGiacco( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Alberta Giacco"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x83F2; + Hue = 0x83F2; - Female = true; - Body = 0x191; - } + Female = true; + Body = 0x191; + } - public override void InitOutfit() - { - AddItem( new FancyShirt() ); - AddItem( new Skirt( 0x59B ) ); - AddItem( new Boots() ); - AddItem( new FeatheredHat( 0x59B ) ); - AddItem( new FullApron( 0x59B ) ); + public override void InitOutfit() + { + AddItem(new FancyShirt()); + AddItem(new Skirt(0x59B)); + AddItem(new Boots()); + AddItem(new FeatheredHat(0x59B)); + AddItem(new FullApron(0x59B)); - HairItemID = 0x203D; // Pony Tail - HairHue = 0x457; - } + HairItemID = 0x203D; // Pony Tail + HairHue = 0x457; + } - public override bool CanTalkTo( PlayerMobile to ) - { - QuestSystem qs = to.Quest as CollectorQuest; + public override bool CanTalkTo(PlayerMobile to) + { + QuestSystem qs = to.Quest as CollectorQuest; - if ( qs == null ) - return false; + if (qs == null) + return false; - return ( qs.IsObjectiveInProgress( typeof( FindAlbertaObjective ) ) - || qs.IsObjectiveInProgress( typeof( SitOnTheStoolObjective ) ) - || qs.IsObjectiveInProgress( typeof( ReturnPaintingObjective ) ) ); - } + return qs.IsObjectiveInProgress(typeof(FindAlbertaObjective)) + || qs.IsObjectiveInProgress(typeof(SitOnTheStoolObjective)) + || qs.IsObjectiveInProgress(typeof(ReturnPaintingObjective)); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - Direction = GetDirectionTo( player ); + if (qs is CollectorQuest) + { + Direction = GetDirectionTo(player); - QuestObjective obj = qs.FindObjective( typeof( FindAlbertaObjective ) ); + QuestObjective obj = qs.FindObjective(typeof(FindAlbertaObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( SitOnTheStoolObjective ) ) ) - { - qs.AddConversation( new AlbertaStoolConversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( ReturnPaintingObjective ) ) ) - { - qs.AddConversation( new AlbertaAfterPaintingConversation() ); - } - } - } + if (obj != null && !obj.Completed) + obj.Complete(); + else if (qs.IsObjectiveInProgress(typeof(SitOnTheStoolObjective))) + qs.AddConversation(new AlbertaStoolConversation()); + else if (qs.IsObjectiveInProgress(typeof(ReturnPaintingObjective))) + qs.AddConversation(new AlbertaAfterPaintingConversation()); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Mobiles/ElwoodMcCarrin.cs b/Scripts/Engines/Quests/Collector/Mobiles/ElwoodMcCarrin.cs index c4343b2ab..56a640fba 100644 --- a/Scripts/Engines/Quests/Collector/Mobiles/ElwoodMcCarrin.cs +++ b/Scripts/Engines/Quests/Collector/Mobiles/ElwoodMcCarrin.cs @@ -1,239 +1,228 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public class ElwoodMcCarrin : BaseQuester - { - public override string DefaultName => "Elwood McCarrin"; + public class ElwoodMcCarrin : BaseQuester + { + [Constructible] + public ElwoodMcCarrin() : base("the well-known collector") + { + } - [Constructible] - public ElwoodMcCarrin() : base( "the well-known collector" ) - { - } + public ElwoodMcCarrin(Serial serial) : base(serial) + { + } - public ElwoodMcCarrin( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Elwood McCarrin"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x83ED; + Hue = 0x83ED; - Female = false; - Body = 0x190; - } + Female = false; + Body = 0x190; + } - public override void InitOutfit() - { - AddItem( new FancyShirt() ); - AddItem( new LongPants( 0x544 ) ); - AddItem( new Shoes( 0x454 ) ); - AddItem( new JesterHat( 0x4D2 ) ); - AddItem( new FullApron( 0x4D2 ) ); + public override void InitOutfit() + { + AddItem(new FancyShirt()); + AddItem(new LongPants(0x544)); + AddItem(new Shoes(0x454)); + AddItem(new JesterHat(0x4D2)); + AddItem(new FullApron(0x4D2)); - HairItemID = 0x203D; // Pony Tail - HairHue = 0x47D; + HairItemID = 0x203D; // Pony Tail + HairHue = 0x47D; - FacialHairItemID = 0x2040; // Goatee - FacialHairHue = 0x47D; - } + FacialHairItemID = 0x2040; // Goatee + FacialHairHue = 0x47D; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - Direction = GetDirectionTo( player ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + Direction = GetDirectionTo(player); - QuestSystem qs = player.Quest; + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FishPearlsObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringFishConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( ReturnPearlsObjective ) ); + if (qs is CollectorQuest) + { + if (qs.IsObjectiveInProgress(typeof(FishPearlsObjective))) + { + qs.AddConversation(new ElwoodDuringFishConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(ReturnPearlsObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( FindAlbertaObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringPainting1Conversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( SitOnTheStoolObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringPainting2Conversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnPaintingObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(FindAlbertaObjective))) + { + qs.AddConversation(new ElwoodDuringPainting1Conversation()); + } + else if (qs.IsObjectiveInProgress(typeof(SitOnTheStoolObjective))) + { + qs.AddConversation(new ElwoodDuringPainting2Conversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnPaintingObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( FindGabrielObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringAutograph1Conversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( FindSheetMusicObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringAutograph2Conversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( ReturnSheetMusicObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringAutograph3Conversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnAutographObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(FindGabrielObjective))) + { + qs.AddConversation(new ElwoodDuringAutograph1Conversation()); + } + else if (qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective))) + { + qs.AddConversation(new ElwoodDuringAutograph2Conversation()); + } + else if (qs.IsObjectiveInProgress(typeof(ReturnSheetMusicObjective))) + { + qs.AddConversation(new ElwoodDuringAutograph3Conversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnAutographObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( FindTomasObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringToys1Conversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( CaptureImagesObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringToys2Conversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( ReturnImagesObjective ) ) ) - { - qs.AddConversation( new ElwoodDuringToys3Conversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnToysObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(FindTomasObjective))) + { + qs.AddConversation(new ElwoodDuringToys1Conversation()); + } + else if (qs.IsObjectiveInProgress(typeof(CaptureImagesObjective))) + { + qs.AddConversation(new ElwoodDuringToys2Conversation()); + } + else if (qs.IsObjectiveInProgress(typeof(ReturnImagesObjective))) + { + qs.AddConversation(new ElwoodDuringToys3Conversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnToysObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); + if (obj != null && !obj.Completed) + { + obj.Complete(); - if ( GiveReward( player ) ) - { - qs.AddConversation( new EndConversation() ); - } - else - { - qs.AddConversation( new FullEndConversation( true ) ); - } - } - else - { - obj = qs.FindObjective( typeof( MakeRoomObjective ) ); + if (GiveReward(player)) + qs.AddConversation(new EndConversation()); + else + qs.AddConversation(new FullEndConversation(true)); + } + else + { + obj = qs.FindObjective(typeof(MakeRoomObjective)); - if ( obj != null && !obj.Completed ) - { - if ( GiveReward( player ) ) - { - obj.Complete(); - qs.AddConversation( new EndConversation() ); - } - else - { - qs.AddConversation( new FullEndConversation( false ) ); - } - } - } - } - } - } - } - } - else - { - QuestSystem newQuest = new CollectorQuest( player ); + if (obj != null && !obj.Completed) + { + if (GiveReward(player)) + { + obj.Complete(); + qs.AddConversation(new EndConversation()); + } + else + { + qs.AddConversation(new FullEndConversation(false)); + } + } + } + } + } + } + } + } + else + { + QuestSystem newQuest = new CollectorQuest(player); - if ( qs == null && QuestSystem.CanOfferQuest( player, typeof( CollectorQuest ) ) ) - { - newQuest.SendOffer(); - } - else - { - newQuest.AddConversation( new DontOfferConversation() ); - } - } - } + if (qs == null && QuestSystem.CanOfferQuest(player, typeof(CollectorQuest))) + newQuest.SendOffer(); + else + newQuest.AddConversation(new DontOfferConversation()); + } + } - public bool GiveReward( Mobile to ) - { - Bag bag = new Bag(); + public bool GiveReward(Mobile to) + { + Bag bag = new Bag(); - bag.DropItem( new Gold( Utility.RandomMinMax( 500, 1000 ) ) ); + bag.DropItem(new Gold(Utility.RandomMinMax(500, 1000))); - if ( Utility.RandomBool() ) - { - BaseWeapon weapon = Loot.RandomWeapon(); + if (Utility.RandomBool()) + { + BaseWeapon weapon = Loot.RandomWeapon(); - if ( Core.AOS ) - { - BaseRunicTool.ApplyAttributesTo( weapon, 2, 20, 30 ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled( 2, 3 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled( 2, 3 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled( 2, 3 ); - } + if (Core.AOS) + { + BaseRunicTool.ApplyAttributesTo(weapon, 2, 20, 30); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(2, 3); + weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(2, 3); + weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(2, 3); + } - bag.DropItem( weapon ); - } - else - { - Item item; + bag.DropItem(weapon); + } + else + { + Item item; - if ( Core.AOS ) - { - item = Loot.RandomArmorOrShieldOrJewelry(); + if (Core.AOS) + { + item = Loot.RandomArmorOrShieldOrJewelry(); - if ( item is BaseArmor armor ) - BaseRunicTool.ApplyAttributesTo( armor, 2, 20, 30 ); - else if ( item is BaseJewel jewel ) - BaseRunicTool.ApplyAttributesTo( jewel, 2, 20, 30 ); - } - else - { - BaseArmor armor = Loot.RandomArmorOrShield(); - item = armor; + if (item is BaseArmor armor) + BaseRunicTool.ApplyAttributesTo(armor, 2, 20, 30); + else if (item is BaseJewel jewel) + BaseRunicTool.ApplyAttributesTo(jewel, 2, 20, 30); + } + else + { + BaseArmor armor = Loot.RandomArmorOrShield(); + item = armor; - armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled( 2, 3 ); - armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled( 2, 3 ); - } + armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled(2, 3); + armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled(2, 3); + } - bag.DropItem( item ); - } + bag.DropItem(item); + } - bag.DropItem( new Obsidian() ); + bag.DropItem(new Obsidian()); - if ( to.PlaceInBackpack( bag ) ) - { - return true; - } + if (to.PlaceInBackpack(bag)) return true; - bag.Delete(); - return false; - } + bag.Delete(); + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Mobiles/GabrielPiete.cs b/Scripts/Engines/Quests/Collector/Mobiles/GabrielPiete.cs index d62380986..a83e4f81f 100644 --- a/Scripts/Engines/Quests/Collector/Mobiles/GabrielPiete.cs +++ b/Scripts/Engines/Quests/Collector/Mobiles/GabrielPiete.cs @@ -1,103 +1,99 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public class GabrielPiete : BaseQuester - { - public override string DefaultName => "Gabriel Piete"; + public class GabrielPiete : BaseQuester + { + [Constructible] + public GabrielPiete() : base("the renowned minstrel") + { + } - [Constructible] - public GabrielPiete() : base( "the renowned minstrel" ) - { - } + public GabrielPiete(Serial serial) : base(serial) + { + } - public GabrielPiete( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Gabriel Piete"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x83EF; + Hue = 0x83EF; - Female = false; - Body = 0x190; - } + Female = false; + Body = 0x190; + } - public override void InitOutfit() - { - AddItem( new FancyShirt() ); - AddItem( new LongPants( 0x5F7 ) ); - AddItem( new Shoes( 0x5F7 ) ); + public override void InitOutfit() + { + AddItem(new FancyShirt()); + AddItem(new LongPants(0x5F7)); + AddItem(new Shoes(0x5F7)); - HairItemID = 0x2049; // Pig Tails - HairHue = 0x460; + HairItemID = 0x2049; // Pig Tails + HairHue = 0x460; - FacialHairItemID = 0x2041; // Mustache - FacialHairHue = 0x460; - } + FacialHairItemID = 0x2041; // Mustache + FacialHairHue = 0x460; + } - public override bool CanTalkTo( PlayerMobile to ) - { - QuestSystem qs = to.Quest as CollectorQuest; + public override bool CanTalkTo(PlayerMobile to) + { + QuestSystem qs = to.Quest as CollectorQuest; - if ( qs == null ) - return false; + if (qs == null) + return false; - return ( qs.IsObjectiveInProgress( typeof( FindGabrielObjective ) ) - || qs.IsObjectiveInProgress( typeof( FindSheetMusicObjective ) ) - || qs.IsObjectiveInProgress( typeof( ReturnSheetMusicObjective ) ) - || qs.IsObjectiveInProgress( typeof( ReturnAutographObjective ) ) ); - } + return qs.IsObjectiveInProgress(typeof(FindGabrielObjective)) + || qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective)) + || qs.IsObjectiveInProgress(typeof(ReturnSheetMusicObjective)) + || qs.IsObjectiveInProgress(typeof(ReturnAutographObjective)); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - Direction = GetDirectionTo( player ); + if (qs is CollectorQuest) + { + Direction = GetDirectionTo(player); - QuestObjective obj = qs.FindObjective( typeof( FindGabrielObjective ) ); + QuestObjective obj = qs.FindObjective(typeof(FindGabrielObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( FindSheetMusicObjective ) ) ) - { - qs.AddConversation( new GabrielNoSheetMusicConversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnSheetMusicObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective))) + { + qs.AddConversation(new GabrielNoSheetMusicConversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnSheetMusicObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( ReturnAutographObjective ) ) ) - { - qs.AddConversation( new GabrielIgnoreConversation() ); - } - } - } - } + if (obj != null && !obj.Completed) + obj.Complete(); + else if (qs.IsObjectiveInProgress(typeof(ReturnAutographObjective))) + qs.AddConversation(new GabrielIgnoreConversation()); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Mobiles/Impresario.cs b/Scripts/Engines/Quests/Collector/Mobiles/Impresario.cs index dd3f46dfa..bd9c4073b 100644 --- a/Scripts/Engines/Quests/Collector/Mobiles/Impresario.cs +++ b/Scripts/Engines/Quests/Collector/Mobiles/Impresario.cs @@ -1,164 +1,157 @@ -using Server.Mobiles; -using Server.Items; using Server.Gumps; +using Server.Items; +using Server.Mobiles; using Server.Network; namespace Server.Engines.Quests.Collector { - public class Impresario : BaseQuester - { - [Constructible] - public Impresario() : base( "the impresario" ) - { - } + public class Impresario : BaseQuester + { + [Constructible] + public Impresario() : base("the impresario") + { + } - public Impresario( Serial serial ) : base( serial ) - { - } + public Impresario(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = Utility.RandomSkinHue(); + Hue = Utility.RandomSkinHue(); - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); + } - public override void InitOutfit() - { - AddItem( new FancyShirt( Utility.RandomDyedHue() ) ); - AddItem( new LongPants( Utility.RandomNondyedHue() ) ); - AddItem( new Shoes( Utility.RandomNeutralHue() ) ); + public override void InitOutfit() + { + AddItem(new FancyShirt(Utility.RandomDyedHue())); + AddItem(new LongPants(Utility.RandomNondyedHue())); + AddItem(new Shoes(Utility.RandomNeutralHue())); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this ); - } + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this); + } - public override bool CanTalkTo( PlayerMobile to ) - { - QuestSystem qs = to.Quest as CollectorQuest; + public override bool CanTalkTo(PlayerMobile to) + { + QuestSystem qs = to.Quest as CollectorQuest; - if ( qs == null ) - return false; + if (qs == null) + return false; - return qs.IsObjectiveInProgress( typeof( FindSheetMusicObjective ) ); - } + return qs.IsObjectiveInProgress(typeof(FindSheetMusicObjective)); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - if ( qs.FindObjective( typeof( FindSheetMusicObjective ) ) is FindSheetMusicObjective obj && !obj.Completed ) - { - Direction = GetDirectionTo( player ); + if (qs is CollectorQuest) + if (qs.FindObjective(typeof(FindSheetMusicObjective)) is FindSheetMusicObjective obj && !obj.Completed) + { + Direction = GetDirectionTo(player); - if ( obj.IsInRightTheater() ) - { - player.CloseGump( typeof( SheetMusicOfferGump ) ); - player.SendGump( new SheetMusicOfferGump() ); - } - else - { - qs.AddConversation( new NoSheetMusicConversation() ); - } - } - } - } + if (obj.IsInRightTheater()) + { + player.CloseGump(typeof(SheetMusicOfferGump)); + player.SendGump(new SheetMusicOfferGump()); + } + else + { + qs.AddConversation(new NoSheetMusicConversation()); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SheetMusicOfferGump : BaseQuestGump - { - public SheetMusicOfferGump() : base( 75, 25 ) - { - Closable = false; + public class SheetMusicOfferGump : BaseQuestGump + { + public SheetMusicOfferGump() : base(75, 25) + { + Closable = false; - AddImage( 349, 10, 0x24B0 ); - AddImageTiled( 349, 130, 100, 120, 0x24B3 ); - AddImageTiled( 149, 10, 200, 140, 0x24AF ); - AddImageTiled( 149, 300, 200, 140, 0x24B5 ); - AddImage( 349, 300, 0x24B6 ); - AddImage( 35, 10, 0x24AE ); - AddImageTiled( 35, 150, 120, 100, 0x24B1 ); - AddImage( 35, 300, 0x24B4 ); + AddImage(349, 10, 0x24B0); + AddImageTiled(349, 130, 100, 120, 0x24B3); + AddImageTiled(149, 10, 200, 140, 0x24AF); + AddImageTiled(149, 300, 200, 140, 0x24B5); + AddImage(349, 300, 0x24B6); + AddImage(35, 10, 0x24AE); + AddImageTiled(35, 150, 120, 100, 0x24B1); + AddImage(35, 300, 0x24B4); - AddHtmlLocalized( 110, 60, 200, 20, 1049069, White, false, false ); // Conversation Event + AddHtmlLocalized(110, 60, 200, 20, 1049069, White, false, false); // Conversation Event - AddImage( 65, 14, 0x2776 ); - AddImageTiled( 81, 14, 349, 17, 0x2775 ); - AddImage( 426, 14, 0x2778 ); + AddImage(65, 14, 0x2776); + AddImageTiled(81, 14, 349, 17, 0x2775); + AddImage(426, 14, 0x2778); - AddImageTiled( 50, 37, 400, 376, 0xA40 ); - AddAlphaRegion( 50, 37, 400, 376 ); + AddImageTiled(50, 37, 400, 376, 0xA40); + AddAlphaRegion(50, 37, 400, 376); - AddImage( 0, 0, 0x28C8 ); + AddImage(0, 0, 0x28C8); - AddImageTiled( 75, 90, 200, 1, 0x238D ); - AddImage( 75, 58, 0x2635 ); - AddImage( 380, 45, 0xDF ); + AddImageTiled(75, 90, 200, 1, 0x238D); + AddImage(75, 58, 0x2635); + AddImage(380, 45, 0xDF); - AddHtmlLocalized( 98, 140, 312, 200, 1055107, LightGreen, false, true ); // Sure, I have some sheet music for a Gabriel Piete song. I'd be happy to sell you a copy for 10 gold. + AddHtmlLocalized(98, 140, 312, 200, 1055107, LightGreen, false, + true); // Sure, I have some sheet music for a Gabriel Piete song. I'd be happy to sell you a copy for 10 gold. - AddRadio( 85, 350, 0x25F8, 0x25FB, true, 1 ); - AddHtmlLocalized( 120, 356, 280, 20, 1014088, White, false, false ); // I accept. + AddRadio(85, 350, 0x25F8, 0x25FB, true, 1); + AddHtmlLocalized(120, 356, 280, 20, 1014088, White, false, false); // I accept. - AddRadio( 85, 385, 0x25F8, 0x25FB, false, 0 ); - AddHtmlLocalized( 120, 391, 280, 20, 1049012, White, false, false ); // No thanks, I decline. + AddRadio(85, 385, 0x25F8, 0x25FB, false, 0); + AddHtmlLocalized(120, 391, 280, 20, 1049012, White, false, false); // No thanks, I decline. - AddButton( 340, 390, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0 ); - } + AddButton(340, 390, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 && info.IsSwitched( 1 ) ) - { - if ( sender.Mobile is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1 && info.IsSwitched(1)) + if (sender.Mobile is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - if ( qs.FindObjective( typeof( FindSheetMusicObjective ) ) is FindSheetMusicObjective obj && !obj.Completed ) - { - if ( player.Backpack!= null && player.Backpack.ConsumeTotal( typeof( Gold ), 10 ) ) - { - obj.Complete(); - } - else - { - BankBox bank = player.FindBankNoCreate(); - if ( bank != null && bank.ConsumeTotal( typeof( Gold ), 10 ) ) - { - obj.Complete(); - } + if (qs is CollectorQuest) + if (qs.FindObjective(typeof(FindSheetMusicObjective)) is FindSheetMusicObjective obj && + !obj.Completed) + { + if (player.Backpack != null && player.Backpack.ConsumeTotal(typeof(Gold), 10)) + { + obj.Complete(); + } + else + { + BankBox bank = player.FindBankNoCreate(); + if (bank != null && bank.ConsumeTotal(typeof(Gold), 10)) + obj.Complete(); - else - { - player.SendLocalizedMessage( 1055108 ); // You don't have enough gold to buy the sheet music. - } - } - } - } - } - } - } - } -} + else + player.SendLocalizedMessage( + 1055108); // You don't have enough gold to buy the sheet music. + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Mobiles/TomasONeerlan.cs b/Scripts/Engines/Quests/Collector/Mobiles/TomasONeerlan.cs index dd662decd..df40f2434 100644 --- a/Scripts/Engines/Quests/Collector/Mobiles/TomasONeerlan.cs +++ b/Scripts/Engines/Quests/Collector/Mobiles/TomasONeerlan.cs @@ -1,108 +1,109 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public class TomasONeerlan : BaseQuester - { - public override string DefaultName => "Tomas O'Neerlan"; + public class TomasONeerlan : BaseQuester + { + [Constructible] + public TomasONeerlan() : base("the famed toymaker") + { + } - [Constructible] - public TomasONeerlan() : base( "the famed toymaker" ) - { - } + public TomasONeerlan(Serial serial) : base(serial) + { + } - public TomasONeerlan( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Tomas O'Neerlan"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x83F8; + Hue = 0x83F8; - Female = false; - Body = 0x190; - } + Female = false; + Body = 0x190; + } - public override void InitOutfit() - { - AddItem( new FancyShirt() ); - AddItem( new LongPants( 0x546 ) ); - AddItem( new Boots( 0x452 ) ); - AddItem( new FullApron( 0x455 ) ); + public override void InitOutfit() + { + AddItem(new FancyShirt()); + AddItem(new LongPants(0x546)); + AddItem(new Boots(0x452)); + AddItem(new FullApron(0x455)); - HairItemID = 0x203B; //ShortHair - HairHue = 0x455; - } + HairItemID = 0x203B; //ShortHair + HairHue = 0x455; + } - public override bool CanTalkTo( PlayerMobile to ) - { - QuestSystem qs = to.Quest as CollectorQuest; + public override bool CanTalkTo(PlayerMobile to) + { + QuestSystem qs = to.Quest as CollectorQuest; - if ( qs == null ) - return false; + if (qs == null) + return false; - return ( qs.IsObjectiveInProgress( typeof( FindTomasObjective ) ) - || qs.IsObjectiveInProgress( typeof( CaptureImagesObjective ) ) - || qs.IsObjectiveInProgress( typeof( ReturnImagesObjective ) ) ); - } + return qs.IsObjectiveInProgress(typeof(FindTomasObjective)) + || qs.IsObjectiveInProgress(typeof(CaptureImagesObjective)) + || qs.IsObjectiveInProgress(typeof(ReturnImagesObjective)); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( qs is CollectorQuest ) - { - Direction = GetDirectionTo( player ); + if (qs is CollectorQuest) + { + Direction = GetDirectionTo(player); - QuestObjective obj = qs.FindObjective( typeof( FindTomasObjective ) ); + QuestObjective obj = qs.FindObjective(typeof(FindTomasObjective)); - if ( obj != null && !obj.Completed ) - { - Item paints = new EnchantedPaints(); + if (obj != null && !obj.Completed) + { + Item paints = new EnchantedPaints(); - if ( !player.PlaceInBackpack( paints ) ) - { - paints.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - else - { - obj.Complete(); - } - } - else if ( qs.IsObjectiveInProgress( typeof( CaptureImagesObjective ) ) ) - { - qs.AddConversation( new TomasDuringCollectingConversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnImagesObjective ) ); + if (!player.PlaceInBackpack(paints)) + { + paints.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + else + { + obj.Complete(); + } + } + else if (qs.IsObjectiveInProgress(typeof(CaptureImagesObjective))) + { + qs.AddConversation(new TomasDuringCollectingConversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnImagesObjective)); - if ( obj != null && !obj.Completed ) - { - player.Backpack?.ConsumeUpTo( typeof( EnchantedPaints ), 1 ); + if (obj != null && !obj.Completed) + { + player.Backpack?.ConsumeUpTo(typeof(EnchantedPaints), 1); - obj.Complete(); - } - } - } - } + obj.Complete(); + } + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Collector/Objectives.cs b/Scripts/Engines/Quests/Collector/Objectives.cs index 7449b82bb..9ae31b2e0 100644 --- a/Scripts/Engines/Quests/Collector/Objectives.cs +++ b/Scripts/Engines/Quests/Collector/Objectives.cs @@ -3,420 +3,370 @@ using Server.Mobiles; namespace Server.Engines.Quests.Collector { - public class FishPearlsObjective : QuestObjective - { - public override object Message => 1055084; - - public override int MaxProgress => 6; - - public FishPearlsObjective() - { - } - - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Rainbow pearls collected: - gump.AddHtmlObject( 70, 260, 270, 100, 1055085, BaseQuestGump.Blue, false, false ); - - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, MaxProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } - - public override void OnComplete() - { - System.AddObjective( new ReturnPearlsObjective() ); - } - } - - public class ReturnPearlsObjective : QuestObjective - { - public override object Message => 1055088; - - public ReturnPearlsObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ReturnPearlsConversation() ); - } - } - - public class FindAlbertaObjective : QuestObjective - { - public override object Message => 1055091; - - public FindAlbertaObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new AlbertaPaintingConversation() ); - } - } - - public class SitOnTheStoolObjective : QuestObjective - { - private static readonly Point3D m_StoolLocation = new Point3D( 2899, 706, 0 ); - private static readonly Map m_StoolMap = Map.Trammel; - - private DateTime m_Begin; - - public override object Message => 1055093; - - public SitOnTheStoolObjective() - { - m_Begin = DateTime.MaxValue; - } - - public override void CheckProgress() - { - PlayerMobile pm = System.From; - - if ( pm.Map == m_StoolMap && pm.Location == m_StoolLocation ) - { - if ( m_Begin == DateTime.MaxValue ) - { - m_Begin = DateTime.UtcNow; - } - else if ( DateTime.UtcNow - m_Begin > TimeSpan.FromSeconds( 30.0 ) ) - { - Complete(); - } - } - else if ( m_Begin != DateTime.MaxValue ) - { - m_Begin = DateTime.MaxValue; - pm.SendLocalizedMessage( 1055095, "", 0x26 ); // You must remain seated on the stool until the portrait is complete. Alberta will now have to start again with a fresh canvas. - } - } - - public override void OnComplete() - { - System.AddConversation( new AlbertaEndPaintingConversation() ); - } - } - - public class ReturnPaintingObjective : QuestObjective - { - public override object Message => 1055099; - - public ReturnPaintingObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ReturnPaintingConversation() ); - } - } - - public class FindGabrielObjective : QuestObjective - { - public override object Message => 1055101; - - public FindGabrielObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new GabrielAutographConversation() ); - } - } - - public enum Theater - { - Britain, - Nujelm, - Jhelom - } - - public class FindSheetMusicObjective : QuestObjective - { - private Theater m_Theater; - - public override object Message => 1055104; - - public FindSheetMusicObjective( bool init ) - { - if ( init ) - InitTheater(); - } - - public FindSheetMusicObjective() - { - } - - public void InitTheater() - { - switch ( Utility.Random( 3 ) ) - { - case 1: m_Theater = Theater.Britain; break; - case 2: m_Theater = Theater.Nujelm; break; - default: m_Theater = Theater.Jhelom; break; - } - } - - public bool IsInRightTheater() - { - PlayerMobile player = System.From; - - Region region = Region.Find( player.Location, player.Map ); - - if ( region == null ) - return false; - - switch ( m_Theater ) - { - case Theater.Britain: return region.IsPartOf( "Britain" ); - case Theater.Nujelm: return region.IsPartOf( "Nujel'm" ); - case Theater.Jhelom: return region.IsPartOf( "Jhelom" ); - - default: return false; - } - } - - public override void OnComplete() - { - System.AddConversation( new GetSheetMusicConversation() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_Theater = (Theater) reader.ReadEncodedInt(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) m_Theater ); - } - } - - public class ReturnSheetMusicObjective : QuestObjective - { - public override object Message => 1055110; - - public ReturnSheetMusicObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new GabrielSheetMusicConversation() ); - } - } - - public class ReturnAutographObjective : QuestObjective - { - public override object Message => 1055114; - - public ReturnAutographObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ReturnAutographConversation() ); - } - } - - public class FindTomasObjective : QuestObjective - { - public override object Message => 1055117; - - public FindTomasObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new TomasToysConversation() ); - } - } - - public enum CaptureResponse - { - Valid, - AlreadyDone, - Invalid - } - - public class CaptureImagesObjective : QuestObjective - { - private ImageType[] m_Images; - private bool[] m_Done; - - public override object Message => 1055120; - - public override bool Completed - { - get - { - for ( int i = 0; i < m_Done.Length; i++ ) - { - if ( !m_Done[i] ) - return false; - } - - return true; - } - } - - public CaptureImagesObjective( bool init ) - { - if ( init ) - { - m_Images = ImageTypeInfo.RandomList( 4 ); - m_Done = new bool[4]; - } - } - - public CaptureImagesObjective() - { - } - - public override bool IgnoreYoungProtection( Mobile from ) - { - if ( Completed ) - return false; - - Type fromType = from.GetType(); - - for ( int i = 0; i < m_Images.Length; i++ ) - { - ImageTypeInfo info = ImageTypeInfo.Get( m_Images[i] ); - - if ( info.Type == fromType ) - return true; - } - - return false; - } - - public CaptureResponse CaptureImage( Type type, out ImageType image ) - { - for ( int i = 0; i < m_Images.Length; i++ ) - { - ImageTypeInfo info = ImageTypeInfo.Get( m_Images[i] ); - - if ( info.Type == type ) - { - image = m_Images[i]; - - if ( m_Done[i] ) - { - return CaptureResponse.AlreadyDone; - } - - m_Done[i] = true; - - CheckCompletionStatus(); - - return CaptureResponse.Valid; - } - } - - image = (ImageType)0; - return CaptureResponse.Invalid; - } - - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - for ( int i = 0; i < m_Images.Length; i++ ) - { - ImageTypeInfo info = ImageTypeInfo.Get( m_Images[i] ); - - gump.AddHtmlObject( 70, 260 + 20 * i, 200, 100, info.Name, BaseQuestGump.Blue, false, false ); - gump.AddLabel( 200, 260 + 20 * i, 0x64, " : " ); - gump.AddHtmlObject( 220, 260 + 20 * i, 100, 100, m_Done[i] ? 1055121 : 1055122, BaseQuestGump.Blue, false, false ); - } - } - else - { - base.RenderProgress( gump ); - } - } - - public override void OnComplete() - { - System.AddObjective( new ReturnImagesObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - int count = reader.ReadEncodedInt(); - - m_Images = new ImageType[count]; - m_Done = new bool[count]; - - for ( int i = 0; i < count; i++ ) - { - m_Images[i] = (ImageType) reader.ReadEncodedInt(); - m_Done[i] = reader.ReadBool(); - } - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) m_Images.Length ); - - for ( int i = 0; i < m_Images.Length; i++ ) - { - writer.WriteEncodedInt( (int) m_Images[i] ); - writer.Write( (bool) m_Done[i] ); - } - } - } - - public class ReturnImagesObjective : QuestObjective - { - public override object Message => 1055128; - - public ReturnImagesObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ReturnImagesConversation() ); - } - } - - public class ReturnToysObjective : QuestObjective - { - public override object Message => 1055132; - - public ReturnToysObjective() - { - } - } - - public class MakeRoomObjective : QuestObjective - { - public override object Message => 1055136; - - public MakeRoomObjective() - { - } - } -} + public class FishPearlsObjective : QuestObjective + { + public override object Message => 1055084; + + public override int MaxProgress => 6; + + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Rainbow pearls collected: + gump.AddHtmlObject(70, 260, 270, 100, 1055085, BaseQuestGump.Blue, false, false); + + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, MaxProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } + + public override void OnComplete() + { + System.AddObjective(new ReturnPearlsObjective()); + } + } + + public class ReturnPearlsObjective : QuestObjective + { + public override object Message => 1055088; + + public override void OnComplete() + { + System.AddConversation(new ReturnPearlsConversation()); + } + } + + public class FindAlbertaObjective : QuestObjective + { + public override object Message => 1055091; + + public override void OnComplete() + { + System.AddConversation(new AlbertaPaintingConversation()); + } + } + + public class SitOnTheStoolObjective : QuestObjective + { + private static readonly Point3D m_StoolLocation = new Point3D(2899, 706, 0); + private static readonly Map m_StoolMap = Map.Trammel; + + private DateTime m_Begin; + + public SitOnTheStoolObjective() + { + m_Begin = DateTime.MaxValue; + } + + public override object Message => 1055093; + + public override void CheckProgress() + { + PlayerMobile pm = System.From; + + if (pm.Map == m_StoolMap && pm.Location == m_StoolLocation) + { + if (m_Begin == DateTime.MaxValue) + m_Begin = DateTime.UtcNow; + else if (DateTime.UtcNow - m_Begin > TimeSpan.FromSeconds(30.0)) Complete(); + } + else if (m_Begin != DateTime.MaxValue) + { + m_Begin = DateTime.MaxValue; + pm.SendLocalizedMessage(1055095, "", + 0x26); // You must remain seated on the stool until the portrait is complete. Alberta will now have to start again with a fresh canvas. + } + } + + public override void OnComplete() + { + System.AddConversation(new AlbertaEndPaintingConversation()); + } + } + + public class ReturnPaintingObjective : QuestObjective + { + public override object Message => 1055099; + + public override void OnComplete() + { + System.AddConversation(new ReturnPaintingConversation()); + } + } + + public class FindGabrielObjective : QuestObjective + { + public override object Message => 1055101; + + public override void OnComplete() + { + System.AddConversation(new GabrielAutographConversation()); + } + } + + public enum Theater + { + Britain, + Nujelm, + Jhelom + } + + public class FindSheetMusicObjective : QuestObjective + { + private Theater m_Theater; + + public FindSheetMusicObjective(bool init) + { + if (init) + InitTheater(); + } + + public FindSheetMusicObjective() + { + } + + public override object Message => 1055104; + + public void InitTheater() + { + switch (Utility.Random(3)) + { + case 1: + m_Theater = Theater.Britain; + break; + case 2: + m_Theater = Theater.Nujelm; + break; + default: + m_Theater = Theater.Jhelom; + break; + } + } + + public bool IsInRightTheater() + { + PlayerMobile player = System.From; + + Region region = Region.Find(player.Location, player.Map); + + if (region == null) + return false; + + switch (m_Theater) + { + case Theater.Britain: return region.IsPartOf("Britain"); + case Theater.Nujelm: return region.IsPartOf("Nujel'm"); + case Theater.Jhelom: return region.IsPartOf("Jhelom"); + + default: return false; + } + } + + public override void OnComplete() + { + System.AddConversation(new GetSheetMusicConversation()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_Theater = (Theater)reader.ReadEncodedInt(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt((int)m_Theater); + } + } + + public class ReturnSheetMusicObjective : QuestObjective + { + public override object Message => 1055110; + + public override void OnComplete() + { + System.AddConversation(new GabrielSheetMusicConversation()); + } + } + + public class ReturnAutographObjective : QuestObjective + { + public override object Message => 1055114; + + public override void OnComplete() + { + System.AddConversation(new ReturnAutographConversation()); + } + } + + public class FindTomasObjective : QuestObjective + { + public override object Message => 1055117; + + public override void OnComplete() + { + System.AddConversation(new TomasToysConversation()); + } + } + + public enum CaptureResponse + { + Valid, + AlreadyDone, + Invalid + } + + public class CaptureImagesObjective : QuestObjective + { + private bool[] m_Done; + private ImageType[] m_Images; + + public CaptureImagesObjective(bool init) + { + if (init) + { + m_Images = ImageTypeInfo.RandomList(4); + m_Done = new bool[4]; + } + } + + public CaptureImagesObjective() + { + } + + public override object Message => 1055120; + + public override bool Completed + { + get + { + for (int i = 0; i < m_Done.Length; i++) + if (!m_Done[i]) + return false; + + return true; + } + } + + public override bool IgnoreYoungProtection(Mobile from) + { + if (Completed) + return false; + + Type fromType = from.GetType(); + + for (int i = 0; i < m_Images.Length; i++) + { + ImageTypeInfo info = ImageTypeInfo.Get(m_Images[i]); + + if (info.Type == fromType) + return true; + } + + return false; + } + + public CaptureResponse CaptureImage(Type type, out ImageType image) + { + for (int i = 0; i < m_Images.Length; i++) + { + ImageTypeInfo info = ImageTypeInfo.Get(m_Images[i]); + + if (info.Type == type) + { + image = m_Images[i]; + + if (m_Done[i]) return CaptureResponse.AlreadyDone; + + m_Done[i] = true; + + CheckCompletionStatus(); + + return CaptureResponse.Valid; + } + } + + image = 0; + return CaptureResponse.Invalid; + } + + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + for (int i = 0; i < m_Images.Length; i++) + { + ImageTypeInfo info = ImageTypeInfo.Get(m_Images[i]); + + gump.AddHtmlObject(70, 260 + 20 * i, 200, 100, info.Name, BaseQuestGump.Blue, false, false); + gump.AddLabel(200, 260 + 20 * i, 0x64, " : "); + gump.AddHtmlObject(220, 260 + 20 * i, 100, 100, m_Done[i] ? 1055121 : 1055122, BaseQuestGump.Blue, false, + false); + } + else + base.RenderProgress(gump); + } + + public override void OnComplete() + { + System.AddObjective(new ReturnImagesObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + int count = reader.ReadEncodedInt(); + + m_Images = new ImageType[count]; + m_Done = new bool[count]; + + for (int i = 0; i < count; i++) + { + m_Images[i] = (ImageType)reader.ReadEncodedInt(); + m_Done[i] = reader.ReadBool(); + } + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(m_Images.Length); + + for (int i = 0; i < m_Images.Length; i++) + { + writer.WriteEncodedInt((int)m_Images[i]); + writer.Write(m_Done[i]); + } + } + } + + public class ReturnImagesObjective : QuestObjective + { + public override object Message => 1055128; + + public override void OnComplete() + { + System.AddConversation(new ReturnImagesConversation()); + } + } + + public class ReturnToysObjective : QuestObjective + { + public override object Message => 1055132; + } + + public class MakeRoomObjective : QuestObjective + { + public override object Message => 1055136; + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/BaseQuester.cs b/Scripts/Engines/Quests/Core/BaseQuester.cs index ec398a483..1b1a56cc6 100644 --- a/Scripts/Engines/Quests/Core/BaseQuester.cs +++ b/Scripts/Engines/Quests/Core/BaseQuester.cs @@ -1,124 +1,125 @@ using System.Collections.Generic; +using Server.ContextMenus; using Server.Items; using Server.Mobiles; -using Server.ContextMenus; namespace Server.Engines.Quests { - public class TalkEntry : ContextMenuEntry - { - private BaseQuester m_Quester; + public class TalkEntry : ContextMenuEntry + { + private BaseQuester m_Quester; - public TalkEntry( BaseQuester quester ) : base( quester.TalkNumber ) - { - m_Quester = quester; - } + public TalkEntry(BaseQuester quester) : base(quester.TalkNumber) + { + m_Quester = quester; + } - public override void OnClick() - { - Mobile from = Owner.From; + public override void OnClick() + { + Mobile from = Owner.From; - if ( from.CheckAlive() && from is PlayerMobile mobile && m_Quester.CanTalkTo( mobile ) ) - m_Quester.OnTalk( mobile, true ); - } - } + if (from.CheckAlive() && from is PlayerMobile mobile && m_Quester.CanTalkTo(mobile)) + m_Quester.OnTalk(mobile, true); + } + } - public abstract class BaseQuester : BaseVendor - { - protected List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public abstract class BaseQuester : BaseVendor + { + protected List m_SBInfos = new List(); - public override bool IsActiveVendor => false; - public override bool IsInvulnerable => true; - public override bool DisallowAllMoves => true; - public override bool ClickTitle => false; - public override bool CanTeach => false; + public BaseQuester() : this(null) + { + } - public virtual int TalkNumber // Talk - => 6146; + public BaseQuester(string title) : base(title) + { + } - public override void InitSBInfo() - { - } + public BaseQuester(Serial serial) : base(serial) + { + } - public BaseQuester() : this( null ) - { - } + protected override List SBInfos => m_SBInfos; - public BaseQuester( string title ) : base( title ) - { - } + public override bool IsActiveVendor => false; + public override bool IsInvulnerable => true; + public override bool DisallowAllMoves => true; + public override bool ClickTitle => false; + public override bool CanTeach => false; - public BaseQuester( Serial serial ) : base( serial ) - { - } + public virtual int TalkNumber // Talk + => 6146; - public abstract void OnTalk( PlayerMobile player, bool contextMenu ); + public override void InitSBInfo() + { + } - public virtual bool CanTalkTo( PlayerMobile to ) - { - return true; - } + public abstract void OnTalk(PlayerMobile player, bool contextMenu); - public virtual int GetAutoTalkRange( PlayerMobile m ) - { - return -1; - } + public virtual bool CanTalkTo(PlayerMobile to) + { + return true; + } - public override bool CanBeDamaged() - { - return false; - } + public virtual int GetAutoTalkRange(PlayerMobile m) + { + return -1; + } - protected Item SetHue( Item item, int hue ) - { - item.Hue = hue; - return item; - } + public override bool CanBeDamaged() + { + return false; + } - public override void AddCustomContextEntries( Mobile from, List list ) - { - base.AddCustomContextEntries( from, list ); + protected Item SetHue(Item item, int hue) + { + item.Hue = hue; + return item; + } - if ( from.Alive && from is PlayerMobile mobile && TalkNumber > 0 && CanTalkTo( mobile ) ) - list.Add( new TalkEntry( this ) ); - } + public override void AddCustomContextEntries(Mobile from, List list) + { + base.AddCustomContextEntries(from, list); - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m.Alive && m is PlayerMobile pm ) - { - int range = GetAutoTalkRange( pm ); + if (from.Alive && from is PlayerMobile mobile && TalkNumber > 0 && CanTalkTo(mobile)) + list.Add(new TalkEntry(this)); + } - if ( pm.Alive && range >= 0 && InRange( m, range ) && !InRange( oldLocation, range ) && CanTalkTo( pm ) ) - OnTalk( pm, false ); - } - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m.Alive && m is PlayerMobile pm) + { + int range = GetAutoTalkRange(pm); - public void FocusTo( Mobile to ) - { - QuestSystem.FocusTo( this, to ); - } + if (pm.Alive && range >= 0 && InRange(m, range) && !InRange(oldLocation, range) && CanTalkTo(pm)) + OnTalk(pm, false); + } + } - public static Container GetNewContainer() - { - Bag bag = new Bag(); - bag.Hue = QuestSystem.RandomBrightHue(); - return bag; - } + public void FocusTo(Mobile to) + { + QuestSystem.FocusTo(this, to); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public static Container GetNewContainer() + { + Bag bag = new Bag(); + bag.Hue = QuestSystem.RandomBrightHue(); + return bag; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Items/DynamicTeleporter.cs b/Scripts/Engines/Quests/Core/Items/DynamicTeleporter.cs index 76a9e1647..cd62993e9 100644 --- a/Scripts/Engines/Quests/Core/Items/DynamicTeleporter.cs +++ b/Scripts/Engines/Quests/Core/Items/DynamicTeleporter.cs @@ -2,64 +2,64 @@ using Server.Mobiles; namespace Server.Engines.Quests { - public abstract class DynamicTeleporter : Item - { - public override int LabelNumber => 1049382; // a magical teleporter + public abstract class DynamicTeleporter : Item + { + public DynamicTeleporter() : this(0x1822, 0x482) + { + } - public DynamicTeleporter() : this( 0x1822, 0x482 ) - { - } + public DynamicTeleporter(int itemID, int hue) : base(itemID) + { + Movable = false; + Hue = hue; + } - public DynamicTeleporter( int itemID, int hue ) : base( itemID ) - { - Movable = false; - Hue = hue; - } + public DynamicTeleporter(Serial serial) : base(serial) + { + } - public abstract bool GetDestination( PlayerMobile player, ref Point3D loc, ref Map map ); + public override int LabelNumber => 1049382; // a magical teleporter - public virtual int NotWorkingMessage // Nothing Happens. - => 500309; + public virtual int NotWorkingMessage // Nothing Happens. + => 500309; - public override bool OnMoveOver( Mobile m ) - { - if ( m is PlayerMobile pm ) - { - Point3D loc = Point3D.Zero; - Map map = null; + public abstract bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map); - if ( GetDestination( pm, ref loc, ref map ) ) - { - BaseCreature.TeleportPets( pm, loc, map ); + public override bool OnMoveOver(Mobile m) + { + if (m is PlayerMobile pm) + { + Point3D loc = Point3D.Zero; + Map map = null; - pm.PlaySound( 0x1FE ); - pm.MoveToWorld( loc, map ); + if (GetDestination(pm, ref loc, ref map)) + { + BaseCreature.TeleportPets(pm, loc, map); - return false; - } + pm.PlaySound(0x1FE); + pm.MoveToWorld(loc, map); - pm.SendLocalizedMessage( NotWorkingMessage ); - } + return false; + } - return base.OnMoveOver( m ); - } + pm.SendLocalizedMessage(NotWorkingMessage); + } - public DynamicTeleporter( Serial serial ) : base( serial ) - { - } + return base.OnMoveOver(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Items/EnchantedSextant.cs b/Scripts/Engines/Quests/Core/Items/EnchantedSextant.cs index a589d1042..0d819f792 100644 --- a/Scripts/Engines/Quests/Core/Items/EnchantedSextant.cs +++ b/Scripts/Engines/Quests/Core/Items/EnchantedSextant.cs @@ -2,186 +2,188 @@ using Server.Network; namespace Server.Items { - public class EnchantedSextant : Item - { - //TODO: Trammel/Haven - private static readonly Point2D[] m_TrammelBanks = { - new Point2D( 652, 820 ), - new Point2D( 1813, 2825 ), - new Point2D( 3734, 2149 ), - new Point2D( 2503, 552 ), - new Point2D( 3764, 1317 ), - new Point2D( 587, 2146 ), - new Point2D( 1655, 1606 ), - new Point2D( 1425, 1690 ), - new Point2D( 4471, 1156 ), - new Point2D( 1317, 3773 ), - new Point2D( 2881, 684 ), - new Point2D( 2731, 2192 ), - new Point2D( 3620, 2617 ), - new Point2D( 2880, 3472 ), - new Point2D( 1897, 2684 ), - new Point2D( 5346, 74 ), - new Point2D( 5275, 3977 ), - new Point2D( 5669, 3131 ) - }; + public class EnchantedSextant : Item + { + private const double m_LongDistance = 300.0; - private static readonly Point2D[] m_FeluccaBanks = { - new Point2D( 652, 820 ), - new Point2D( 1813, 2825 ), - new Point2D( 3734, 2149 ), - new Point2D( 2503, 552 ), - new Point2D( 3764, 1317 ), - new Point2D( 3695, 2511 ), - new Point2D( 587, 2146 ), - new Point2D( 1655, 1606 ), - new Point2D( 1425, 1690 ), - new Point2D( 4471, 1156 ), - new Point2D( 1317, 3773 ), - new Point2D( 2881, 684 ), - new Point2D( 2731, 2192 ), - new Point2D( 2880, 3472 ), - new Point2D( 1897, 2684 ), - new Point2D( 5346, 74 ), - new Point2D( 5275, 3977 ), - new Point2D( 5669, 3131 ) - }; + private const double m_ShortDistance = 5.0; - private static readonly Point2D[] m_IlshenarBanks = { - new Point2D( 854, 680 ), - new Point2D( 855, 603 ), - new Point2D( 1226, 554 ), - new Point2D( 1610, 556 ) - }; + //TODO: Trammel/Haven + private static readonly Point2D[] m_TrammelBanks = + { + new Point2D(652, 820), + new Point2D(1813, 2825), + new Point2D(3734, 2149), + new Point2D(2503, 552), + new Point2D(3764, 1317), + new Point2D(587, 2146), + new Point2D(1655, 1606), + new Point2D(1425, 1690), + new Point2D(4471, 1156), + new Point2D(1317, 3773), + new Point2D(2881, 684), + new Point2D(2731, 2192), + new Point2D(3620, 2617), + new Point2D(2880, 3472), + new Point2D(1897, 2684), + new Point2D(5346, 74), + new Point2D(5275, 3977), + new Point2D(5669, 3131) + }; - private static readonly Point2D[] m_MalasBanks = { - new Point2D( 996, 519 ), - new Point2D( 2048, 1345 ) - }; + private static readonly Point2D[] m_FeluccaBanks = + { + new Point2D(652, 820), + new Point2D(1813, 2825), + new Point2D(3734, 2149), + new Point2D(2503, 552), + new Point2D(3764, 1317), + new Point2D(3695, 2511), + new Point2D(587, 2146), + new Point2D(1655, 1606), + new Point2D(1425, 1690), + new Point2D(4471, 1156), + new Point2D(1317, 3773), + new Point2D(2881, 684), + new Point2D(2731, 2192), + new Point2D(2880, 3472), + new Point2D(1897, 2684), + new Point2D(5346, 74), + new Point2D(5275, 3977), + new Point2D(5669, 3131) + }; - private const double m_LongDistance = 300.0; - private const double m_ShortDistance = 5.0; + private static readonly Point2D[] m_IlshenarBanks = + { + new Point2D(854, 680), + new Point2D(855, 603), + new Point2D(1226, 554), + new Point2D(1610, 556) + }; - public override int LabelNumber => 1046226; // an enchanted sextant + private static readonly Point2D[] m_MalasBanks = + { + new Point2D(996, 519), + new Point2D(2048, 1345) + }; - [Constructible] - public EnchantedSextant() : base( 0x1058 ) - { - Weight = 2.0; - } + [Constructible] + public EnchantedSextant() : base(0x1058) + { + Weight = 2.0; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + public EnchantedSextant(Serial serial) : base(serial) + { + } - Point2D[] banks; - PMList moongates; - if ( from.Map == Map.Trammel ) - { - banks = m_TrammelBanks; - moongates = PMList.Trammel; - } - else if ( from.Map == Map.Felucca ) - { - banks = m_FeluccaBanks; - moongates = PMList.Felucca; - } - else if ( from.Map == Map.Ilshenar ) - { + public override int LabelNumber => 1046226; // an enchanted sextant + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + Point2D[] banks; + PMList moongates; + if (from.Map == Map.Trammel) + { + banks = m_TrammelBanks; + moongates = PMList.Trammel; + } + else if (from.Map == Map.Felucca) + { + banks = m_FeluccaBanks; + moongates = PMList.Felucca; + } + else if (from.Map == Map.Ilshenar) + { #if false banks = m_IlshenarBanks; moongates = PMList.Ilshenar; #else - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, 0x482, 3, 1061684, "", "" ) ); // The magic of the sextant fails... - return; + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, 0x482, 3, 1061684, "", + "")); // The magic of the sextant fails... + return; #endif - } - else if ( from.Map == Map.Malas ) - { - banks = m_MalasBanks; - moongates = PMList.Malas; - } - else - { - banks = null; - moongates = null; - } + } + else if (from.Map == Map.Malas) + { + banks = m_MalasBanks; + moongates = PMList.Malas; + } + else + { + banks = null; + moongates = null; + } - Point3D closestMoongate = Point3D.Zero; - double moongateDistance = double.MaxValue; - if ( moongates != null ) - { - foreach ( PMEntry entry in moongates.Entries ) - { - double dist = from.GetDistanceToSqrt( entry.Location ); - if ( moongateDistance > dist ) - { - closestMoongate = entry.Location; - moongateDistance = dist; - } - } - } + Point3D closestMoongate = Point3D.Zero; + double moongateDistance = double.MaxValue; + if (moongates != null) + foreach (PMEntry entry in moongates.Entries) + { + double dist = from.GetDistanceToSqrt(entry.Location); + if (moongateDistance > dist) + { + closestMoongate = entry.Location; + moongateDistance = dist; + } + } - Point2D closestBank = Point2D.Zero; - double bankDistance = double.MaxValue; - if ( banks != null ) - { - foreach ( Point2D p in banks ) - { - double dist = from.GetDistanceToSqrt( p ); - if ( bankDistance > dist ) - { - closestBank = p; - bankDistance = dist; - } - } - } + Point2D closestBank = Point2D.Zero; + double bankDistance = double.MaxValue; + if (banks != null) + foreach (Point2D p in banks) + { + double dist = from.GetDistanceToSqrt(p); + if (bankDistance > dist) + { + closestBank = p; + bankDistance = dist; + } + } - int moonMsg; - if ( moongateDistance == double.MaxValue ) - moonMsg = 1048021; // The sextant fails to find a Moongate nearby. - else if ( moongateDistance > m_LongDistance ) - moonMsg = 1046449 + (int)from.GetDirectionTo( closestMoongate ); // A moongate is * from here - else if ( moongateDistance > m_ShortDistance ) - moonMsg = 1048010 + (int)from.GetDirectionTo( closestMoongate ); // There is a Moongate * of here. - else - moonMsg = 1048018; // You are next to a Moongate at the moment. + int moonMsg; + if (moongateDistance == double.MaxValue) + moonMsg = 1048021; // The sextant fails to find a Moongate nearby. + else if (moongateDistance > m_LongDistance) + moonMsg = 1046449 + (int)from.GetDirectionTo(closestMoongate); // A moongate is * from here + else if (moongateDistance > m_ShortDistance) + moonMsg = 1048010 + (int)from.GetDirectionTo(closestMoongate); // There is a Moongate * of here. + else + moonMsg = 1048018; // You are next to a Moongate at the moment. - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, 0x482, 3, moonMsg, "", "" ) ); + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, 0x482, 3, moonMsg, "", "")); - int bankMsg; - if ( bankDistance == double.MaxValue ) - bankMsg = 1048020; // The sextant fails to find a Bank nearby. - else if ( bankDistance > m_LongDistance ) - bankMsg = 1046462 + (int)from.GetDirectionTo( closestBank ); // A town is * from here - else if ( bankDistance > m_ShortDistance ) - bankMsg = 1048002 + (int)from.GetDirectionTo( closestBank ); // There is a city Bank * of here. - else - bankMsg = 1048019; // You are next to a Bank at the moment. + int bankMsg; + if (bankDistance == double.MaxValue) + bankMsg = 1048020; // The sextant fails to find a Bank nearby. + else if (bankDistance > m_LongDistance) + bankMsg = 1046462 + (int)from.GetDirectionTo(closestBank); // A town is * from here + else if (bankDistance > m_ShortDistance) + bankMsg = 1048002 + (int)from.GetDirectionTo(closestBank); // There is a city Bank * of here. + else + bankMsg = 1048019; // You are next to a Bank at the moment. - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, 0x5AA, 3, bankMsg, "", "" ) ); - } + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, 0x5AA, 3, bankMsg, "", "")); + } - public EnchantedSextant( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Items/HornOfRetreat.cs b/Scripts/Engines/Quests/Core/Items/HornOfRetreat.cs index 45fc3d8c0..48eacd7e9 100644 --- a/Scripts/Engines/Quests/Core/Items/HornOfRetreat.cs +++ b/Scripts/Engines/Quests/Core/Items/HornOfRetreat.cs @@ -1,192 +1,198 @@ using System; using Server.Items; +using Server.Regions; namespace Server.Engines.Quests { - public class HornOfRetreat : Item - { - private int m_Charges; + public class HornOfRetreat : Item + { + private int m_Charges; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D DestLoc { get; set; } + private Timer m_PlayTimer; - [CommandProperty( AccessLevel.GameMaster )] - public Map DestMap { get; set; } + [Constructible] + public HornOfRetreat() : base(0xFC4) + { + Hue = 0x482; + Weight = 1.0; + Charges = 10; + } - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set{ m_Charges = value; InvalidateProperties(); } - } + public HornOfRetreat(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1049117; // Horn of Retreat + [CommandProperty(AccessLevel.GameMaster)] + public Point3D DestLoc{ get; set; } - [Constructible] - public HornOfRetreat() : base( 0xFC4 ) - { - Hue = 0x482; - Weight = 1.0; - Charges = 10; - } + [CommandProperty(AccessLevel.GameMaster)] + public Map DestMap{ get; set; } - public virtual bool ValidateUse( Mobile from ) - { - return true; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override int LabelNumber => 1049117; // Horn of Retreat - list.Add( 1060741, m_Charges.ToString() ); // charges: ~1_val~ - } + public virtual bool ValidateUse(Mobile from) + { + return true; + } - private Timer m_PlayTimer; + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - if ( !ValidateUse( from ) ) - { - SendLocalizedMessageTo( from, 500309 ); // Nothing Happens. - } - else if ( Core.ML && from.Map != Map.Trammel && from.Map != Map.Malas ) - { - from.SendLocalizedMessage( 1076154 ); // You can only use this in Trammel and Malas. - } - else if ( m_PlayTimer != null ) - { - SendLocalizedMessageTo( from, 1042144 ); // This is currently in use. - } - else if ( Charges > 0 ) - { - from.Animate( 34, 7, 1, true, false, 0 ); - from.PlaySound( 0xFF ); - from.SendLocalizedMessage( 1049115 ); // You play the horn and a sense of peace overcomes you... + list.Add(1060741, m_Charges.ToString()); // charges: ~1_val~ + } - --Charges; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + if (!ValidateUse(from)) + { + SendLocalizedMessageTo(from, 500309); // Nothing Happens. + } + else if (Core.ML && from.Map != Map.Trammel && from.Map != Map.Malas) + { + from.SendLocalizedMessage(1076154); // You can only use this in Trammel and Malas. + } + else if (m_PlayTimer != null) + { + SendLocalizedMessageTo(from, 1042144); // This is currently in use. + } + else if (Charges > 0) + { + from.Animate(34, 7, 1, true, false, 0); + from.PlaySound(0xFF); + from.SendLocalizedMessage(1049115); // You play the horn and a sense of peace overcomes you... - m_PlayTimer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( PlayTimer_Callback ), from ); - } - else - { - SendLocalizedMessageTo( from, 1042544 ); // This item is out of charges. - } - } - else - { - SendLocalizedMessageTo( from, 1042001 ); // That must be in your pack for you to use it. - } - } + --Charges; - public virtual void PlayTimer_Callback( object state ) - { - Mobile from = (Mobile)state; + m_PlayTimer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(PlayTimer_Callback), + from); + } + else + { + SendLocalizedMessageTo(from, 1042544); // This item is out of charges. + } + } + else + { + SendLocalizedMessageTo(from, 1042001); // That must be in your pack for you to use it. + } + } - m_PlayTimer = null; + public virtual void PlayTimer_Callback(object state) + { + Mobile from = (Mobile)state; - HornOfRetreatMoongate gate = new HornOfRetreatMoongate( DestLoc, DestMap, from, Hue ); + m_PlayTimer = null; - gate.MoveToWorld( from.Location, from.Map ); + HornOfRetreatMoongate gate = new HornOfRetreatMoongate(DestLoc, DestMap, from, Hue); - from.PlaySound( 0x20E ); + gate.MoveToWorld(from.Location, from.Map); - gate.SendLocalizedMessageTo( from, 1049102, from.Name ); // Quickly ~1_NAME~! Onward through the gate! - } + from.PlaySound(0x20E); - public HornOfRetreat( Serial serial ) : base( serial ) - { - } + gate.SendLocalizedMessageTo(from, 1049102, from.Name); // Quickly ~1_NAME~! Onward through the gate! + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( DestLoc ); - writer.Write( DestMap ); - writer.Write( m_Charges ); - } + writer.Write(DestLoc); + writer.Write(DestMap); + writer.Write(m_Charges); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - DestLoc = reader.ReadPoint3D(); - DestMap = reader.ReadMap(); - m_Charges = reader.ReadInt(); - break; - } - } - } - } + switch (version) + { + case 0: + { + DestLoc = reader.ReadPoint3D(); + DestMap = reader.ReadMap(); + m_Charges = reader.ReadInt(); + break; + } + } + } + } - public class HornOfRetreatMoongate : Moongate - { - public override int LabelNumber => 1049114; // Sanctuary Gate + public class HornOfRetreatMoongate : Moongate + { + private Mobile m_Caster; - private Mobile m_Caster; + public HornOfRetreatMoongate(Point3D destLoc, Map destMap, Mobile caster, int hue) + { + m_Caster = caster; - public HornOfRetreatMoongate( Point3D destLoc, Map destMap, Mobile caster, int hue ) - { - m_Caster = caster; + Target = destLoc; + TargetMap = destMap; - Target = destLoc; - TargetMap = destMap; + Hue = hue; + Light = LightType.Circle300; - Hue = hue; - Light = LightType.Circle300; + Dispellable = false; - Dispellable = false; + Timer.DelayCall(TimeSpan.FromSeconds(10.0), Delete); + } - Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), Delete ); - } + public HornOfRetreatMoongate(Serial serial) : base(serial) + { + } - public override void BeginConfirmation( Mobile from ) - { - EndConfirmation( from ); - } + public override int LabelNumber => 1049114; // Sanctuary Gate - public override void UseGate( Mobile m ) - { - if ( m.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - m.SendLocalizedMessage( 1114345 ); // You'll need a better jailbreak plan than that! - } - else if ( m == m_Caster ) - { - base.UseGate( m ); - Delete(); - } - } + public override void BeginConfirmation(Mobile from) + { + EndConfirmation(from); + } - public HornOfRetreatMoongate( Serial serial ) : base( serial ) - { - } + public override void UseGate(Mobile m) + { + if (m.Region.IsPartOf(typeof(Jail))) + { + m.SendLocalizedMessage(1114345); // You'll need a better jailbreak plan than that! + } + else if (m == m_Caster) + { + base.UseGate(m); + Delete(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } - } -} + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Items/QuestItem.cs b/Scripts/Engines/Quests/Core/Items/QuestItem.cs index af2c986ef..f58cc2861 100644 --- a/Scripts/Engines/Quests/Core/Items/QuestItem.cs +++ b/Scripts/Engines/Quests/Core/Items/QuestItem.cs @@ -2,105 +2,91 @@ using Server.Mobiles; namespace Server.Engines.Quests { - public abstract class QuestItem : Item - { - public QuestItem( int itemID ) : base( itemID ) - { - } + public abstract class QuestItem : Item + { + public QuestItem(int itemID) : base(itemID) + { + } - public QuestItem( Serial serial ) : base( serial ) - { - } + public QuestItem(Serial serial) : base(serial) + { + } - public abstract bool CanDrop( PlayerMobile pm ); + public virtual bool Accepted => Deleted; - public virtual bool Accepted => Deleted; + public abstract bool CanDrop(PlayerMobile pm); - public override bool DropToWorld( Mobile from, Point3D p ) - { - bool ret = base.DropToWorld( from, p ); + public override bool DropToWorld(Mobile from, Point3D p) + { + bool ret = base.DropToWorld(from, p); - if ( ret && !Accepted && Parent != from.Backpack ) - { - if ( from.AccessLevel > AccessLevel.Player ) - { - return true; - } + if (ret && !Accepted && Parent != from.Backpack) + { + if (from.AccessLevel > AccessLevel.Player) return true; - if ( !(from is PlayerMobile) || CanDrop( (PlayerMobile)from ) ) - { - return true; - } - from.SendLocalizedMessage( 1049343 ); // You can only drop quest items into the top-most level of your backpack while you still need them for your quest. - return false; - } + if (!(from is PlayerMobile) || CanDrop((PlayerMobile)from)) return true; + from.SendLocalizedMessage( + 1049343); // You can only drop quest items into the top-most level of your backpack while you still need them for your quest. + return false; + } - return ret; - } + return ret; + } - public override bool DropToMobile( Mobile from, Mobile target, Point3D p ) - { - bool ret = base.DropToMobile( from, target, p ); + public override bool DropToMobile(Mobile from, Mobile target, Point3D p) + { + bool ret = base.DropToMobile(from, target, p); - if ( ret && !Accepted && Parent != from.Backpack ) - { - if ( from.AccessLevel > AccessLevel.Player ) - { - return true; - } + if (ret && !Accepted && Parent != from.Backpack) + { + if (from.AccessLevel > AccessLevel.Player) return true; - if ( !(from is PlayerMobile) || CanDrop( (PlayerMobile)from ) ) - { - return true; - } - from.SendLocalizedMessage( 1049344 ); // You decide against trading the item. You still need it for your quest. - return false; - } + if (!(from is PlayerMobile) || CanDrop((PlayerMobile)from)) return true; + from.SendLocalizedMessage( + 1049344); // You decide against trading the item. You still need it for your quest. + return false; + } - return ret; - } + return ret; + } - public override bool DropToItem( Mobile from, Item target, Point3D p ) - { - bool ret = base.DropToItem( from, target, p ); + public override bool DropToItem(Mobile from, Item target, Point3D p) + { + bool ret = base.DropToItem(from, target, p); - if ( ret && !Accepted && Parent != from.Backpack ) - { - if ( from.AccessLevel > AccessLevel.Player ) - { - return true; - } + if (ret && !Accepted && Parent != from.Backpack) + { + if (from.AccessLevel > AccessLevel.Player) return true; - if ( !(from is PlayerMobile) || CanDrop( (PlayerMobile)from ) ) - { - return true; - } - from.SendLocalizedMessage( 1049343 ); // You can only drop quest items into the top-most level of your backpack while you still need them for your quest. - return false; - } - return ret; - } + if (!(from is PlayerMobile) || CanDrop((PlayerMobile)from)) return true; + from.SendLocalizedMessage( + 1049343); // You can only drop quest items into the top-most level of your backpack while you still need them for your quest. + return false; + } - public override DeathMoveResult OnParentDeath( Mobile parent ) - { - if ( parent is PlayerMobile mobile && !CanDrop( mobile ) ) - return DeathMoveResult.MoveToBackpack; + return ret; + } - return base.OnParentDeath( parent ); - } + public override DeathMoveResult OnParentDeath(Mobile parent) + { + if (parent is PlayerMobile mobile && !CanDrop(mobile)) + return DeathMoveResult.MoveToBackpack; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return base.OnParentDeath(parent); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestCallbackEntry.cs b/Scripts/Engines/Quests/Core/QuestCallbackEntry.cs index f922db41b..87a1c87f7 100644 --- a/Scripts/Engines/Quests/Core/QuestCallbackEntry.cs +++ b/Scripts/Engines/Quests/Core/QuestCallbackEntry.cs @@ -2,22 +2,22 @@ using Server.ContextMenus; namespace Server.Engines.Quests { - public class QuestCallbackEntry : ContextMenuEntry - { - private QuestCallback m_Callback; + public class QuestCallbackEntry : ContextMenuEntry + { + private QuestCallback m_Callback; - public QuestCallbackEntry( int number, QuestCallback callback ) : this( number, -1, callback ) - { - } + public QuestCallbackEntry(int number, QuestCallback callback) : this(number, -1, callback) + { + } - public QuestCallbackEntry( int number, int range, QuestCallback callback ) : base( number, range ) - { - m_Callback = callback; - } + public QuestCallbackEntry(int number, int range, QuestCallback callback) : base(number, range) + { + m_Callback = callback; + } - public override void OnClick() - { - m_Callback?.Invoke(); - } - } + public override void OnClick() + { + m_Callback?.Invoke(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestConversation.cs b/Scripts/Engines/Quests/Core/QuestConversation.cs index 06e93ae30..876745dee 100644 --- a/Scripts/Engines/Quests/Core/QuestConversation.cs +++ b/Scripts/Engines/Quests/Core/QuestConversation.cs @@ -4,139 +4,135 @@ using Server.Network; namespace Server.Engines.Quests { - public abstract class QuestConversation - { - public abstract object Message{ get; } + public abstract class QuestConversation + { + public abstract object Message{ get; } - public virtual QuestItemInfo[] Info => null; - public virtual bool Logged => true; + public virtual QuestItemInfo[] Info => null; + public virtual bool Logged => true; - public QuestSystem System { get; set; } + public QuestSystem System{ get; set; } - public bool HasBeenRead { get; set; } + public bool HasBeenRead{ get; set; } - public QuestConversation() - { - } + public virtual void BaseDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public virtual void BaseDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + switch (version) + { + case 0: + { + HasBeenRead = reader.ReadBool(); - switch ( version ) - { - case 0: - { - HasBeenRead = reader.ReadBool(); + break; + } + } - break; - } - } + ChildDeserialize(reader); + } - ChildDeserialize( reader ); - } + public virtual void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + } - public virtual void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - } + public virtual void BaseSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public virtual void BaseSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + writer.Write(HasBeenRead); - writer.Write( (bool) HasBeenRead ); + ChildSerialize(writer); + } - ChildSerialize( writer ); - } + public virtual void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + } - public virtual void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - } + public virtual void OnRead() + { + } + } - public virtual void OnRead() - { - } - } + public class QuestConversationsGump : BaseQuestGump + { + private ArrayList m_Conversations; - public class QuestConversationsGump : BaseQuestGump - { - private ArrayList m_Conversations; + public QuestConversationsGump(QuestConversation conv) : this(BuildList(conv)) + { + } - public QuestConversationsGump( QuestConversation conv ) : this( BuildList( conv ) ) - { - } + public QuestConversationsGump(ArrayList conversations) : base(30, 50) + { + m_Conversations = conversations; - public QuestConversationsGump( ArrayList conversations ) : base( 30, 50 ) - { - m_Conversations = conversations; + Closable = false; - Closable = false; + AddPage(0); - AddPage( 0 ); + AddImage(349, 10, 9392); + AddImageTiled(349, 130, 100, 120, 9395); + AddImageTiled(149, 10, 200, 140, 9391); + AddImageTiled(149, 250, 200, 140, 9397); + AddImage(349, 250, 9398); + AddImage(35, 10, 9390); + AddImageTiled(35, 150, 120, 100, 9393); + AddImage(35, 250, 9396); - AddImage( 349, 10, 9392 ); - AddImageTiled( 349, 130, 100, 120, 9395 ); - AddImageTiled( 149, 10, 200, 140, 9391 ); - AddImageTiled( 149, 250, 200, 140, 9397 ); - AddImage( 349, 250, 9398 ); - AddImage( 35, 10, 9390 ); - AddImageTiled( 35, 150, 120, 100, 9393 ); - AddImage( 35, 250, 9396 ); + AddHtmlLocalized(110, 60, 200, 20, 1049069, White, false, false); // Conversation Event - AddHtmlLocalized( 110, 60, 200, 20, 1049069, White, false, false ); // Conversation Event + AddImage(65, 14, 10102); + AddImageTiled(81, 14, 349, 17, 10101); + AddImage(426, 14, 10104); - AddImage( 65, 14, 10102 ); - AddImageTiled( 81, 14, 349, 17, 10101 ); - AddImage( 426, 14, 10104 ); + AddImageTiled(55, 40, 388, 323, 2624); + AddAlphaRegion(55, 40, 388, 323); - AddImageTiled( 55, 40, 388, 323, 2624 ); - AddAlphaRegion( 55, 40, 388, 323 ); + AddImageTiled(75, 90, 200, 1, 9101); + AddImage(75, 58, 9781); + AddImage(380, 45, 223); - AddImageTiled( 75, 90, 200, 1, 9101 ); - AddImage( 75, 58, 9781 ); - AddImage( 380, 45, 223 ); + AddButton(220, 335, 2313, 2312, 1, GumpButtonType.Reply, 0); + AddImage(0, 0, 10440); - AddButton( 220, 335, 2313, 2312, 1, GumpButtonType.Reply, 0 ); - AddImage( 0, 0, 10440 ); + AddPage(1); - AddPage( 1 ); + for (int i = 0; i < conversations.Count; ++i) + { + QuestConversation conv = (QuestConversation)conversations[conversations.Count - 1 - i]; - for ( int i = 0; i < conversations.Count; ++i ) - { - QuestConversation conv = (QuestConversation)conversations[conversations.Count - 1 - i]; + if (i > 0) + { + AddButton(65, 366, 9909, 9911, 0, GumpButtonType.Page, 1 + i); + AddHtmlLocalized(90, 367, 50, 20, 1043354, Black, false, false); // Previous - if ( i > 0 ) - { - AddButton( 65, 366, 9909, 9911, 0, GumpButtonType.Page, 1 + i ); - AddHtmlLocalized( 90, 367, 50, 20, 1043354, Black, false, false ); // Previous + AddPage(1 + i); + } - AddPage( 1 + i ); - } + AddHtmlObject(70, 110, 365, 220, conv.Message, LightGreen, false, true); - AddHtmlObject( 70, 110, 365, 220, conv.Message, LightGreen, false, true ); + if (i > 0) + { + AddButton(420, 366, 9903, 9905, 0, GumpButtonType.Page, i); + AddHtmlLocalized(370, 367, 50, 20, 1043353, Black, false, false); // Next + } + } + } - if ( i > 0 ) - { - AddButton( 420, 366, 9903, 9905, 0, GumpButtonType.Page, i ); - AddHtmlLocalized( 370, 367, 50, 20, 1043353, Black, false, false ); // Next - } - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + for (int i = m_Conversations.Count - 1; i >= 0; --i) + { + QuestConversation qc = (QuestConversation)m_Conversations[i]; - public override void OnResponse( NetState sender, RelayInfo info ) - { - for ( int i = m_Conversations.Count - 1; i >= 0; --i ) - { - QuestConversation qc = (QuestConversation)m_Conversations[i]; - - if ( !qc.HasBeenRead ) - { - qc.HasBeenRead = true; - qc.OnRead(); - } - } - } - } + if (!qc.HasBeenRead) + { + qc.HasBeenRead = true; + qc.OnRead(); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestItemInfo.cs b/Scripts/Engines/Quests/Core/QuestItemInfo.cs index 705b7f44d..d0300d444 100644 --- a/Scripts/Engines/Quests/Core/QuestItemInfo.cs +++ b/Scripts/Engines/Quests/Core/QuestItemInfo.cs @@ -2,58 +2,58 @@ using Server.Gumps; namespace Server.Engines.Quests { - public class QuestItemInfo - { - public object Name { get; set; } + public class QuestItemInfo + { + public QuestItemInfo(object name, int itemID) + { + Name = name; + ItemID = itemID; + } - public int ItemID { get; set; } + public object Name{ get; set; } - public QuestItemInfo( object name, int itemID ) - { - Name = name; - ItemID = itemID; - } - } + public int ItemID{ get; set; } + } - public class QuestItemInfoGump : BaseQuestGump - { - public QuestItemInfoGump( QuestItemInfo[] info ) : base( 485, 75 ) - { - int height = 100 + (info.Length * 75); + public class QuestItemInfoGump : BaseQuestGump + { + public QuestItemInfoGump(QuestItemInfo[] info) : base(485, 75) + { + int height = 100 + info.Length * 75; - AddPage( 0 ); + AddPage(0); - AddBackground( 5, 10, 145, height, 5054 ); + AddBackground(5, 10, 145, height, 5054); - AddImageTiled( 13, 20, 125, 10, 2624 ); - AddAlphaRegion( 13, 20, 125, 10 ); + AddImageTiled(13, 20, 125, 10, 2624); + AddAlphaRegion(13, 20, 125, 10); - AddImageTiled( 13, height - 10, 128, 10, 2624 ); - AddAlphaRegion( 13, height - 10, 128, 10 ); + AddImageTiled(13, height - 10, 128, 10, 2624); + AddAlphaRegion(13, height - 10, 128, 10); - AddImageTiled( 13, 20, 10, height - 30, 2624 ); - AddAlphaRegion( 13, 20, 10, height - 30 ); + AddImageTiled(13, 20, 10, height - 30, 2624); + AddAlphaRegion(13, 20, 10, height - 30); - AddImageTiled( 131, 20, 10, height - 30, 2624 ); - AddAlphaRegion( 131, 20, 10, height - 30 ); + AddImageTiled(131, 20, 10, height - 30, 2624); + AddAlphaRegion(131, 20, 10, height - 30); - AddHtmlLocalized( 67, 35, 120, 20, 1011233, White, false, false ); // INFO + AddHtmlLocalized(67, 35, 120, 20, 1011233, White, false, false); // INFO - AddImage( 62, 52, 9157 ); - AddImage( 72, 52, 9157 ); - AddImage( 82, 52, 9157 ); + AddImage(62, 52, 9157); + AddImage(72, 52, 9157); + AddImage(82, 52, 9157); - AddButton( 25, 31, 1209, 1210, 777, GumpButtonType.Reply, 0 ); + AddButton(25, 31, 1209, 1210, 777, GumpButtonType.Reply, 0); - AddPage( 1 ); + AddPage(1); - for ( int i = 0; i < info.Length; ++i ) - { - QuestItemInfo cur = info[i]; + for (int i = 0; i < info.Length; ++i) + { + QuestItemInfo cur = info[i]; - AddHtmlObject( 25, 65 + (i * 75), 110, 20, cur.Name, 1153, false, false ); - AddItem( 45, 85 + (i * 75), cur.ItemID ); - } - } - } + AddHtmlObject(25, 65 + i * 75, 110, 20, cur.Name, 1153, false, false); + AddItem(45, 85 + i * 75, cur.ItemID); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestObjective.cs b/Scripts/Engines/Quests/Core/QuestObjective.cs index c4017c65b..ca0c819d0 100644 --- a/Scripts/Engines/Quests/Core/QuestObjective.cs +++ b/Scripts/Engines/Quests/Core/QuestObjective.cs @@ -1,255 +1,255 @@ using System.Collections; using Server.Gumps; +using Server.Items; using Server.Mobiles; using Server.Network; -using Server.Items; namespace Server.Engines.Quests { - public abstract class QuestObjective - { - private int m_CurProgress; + public abstract class QuestObjective + { + private int m_CurProgress; - public abstract object Message{ get; } + public abstract object Message{ get; } - public virtual int MaxProgress => 1; - public virtual QuestItemInfo[] Info => null; + public virtual int MaxProgress => 1; + public virtual QuestItemInfo[] Info => null; - public QuestSystem System { get; set; } + public QuestSystem System{ get; set; } - public bool HasBeenRead { get; set; } + public bool HasBeenRead{ get; set; } - public int CurProgress - { - get => m_CurProgress; - set{ m_CurProgress = value; CheckCompletionStatus(); } - } + public int CurProgress + { + get => m_CurProgress; + set + { + m_CurProgress = value; + CheckCompletionStatus(); + } + } - public bool HasCompleted { get; set; } + public bool HasCompleted{ get; set; } - public virtual bool Completed => m_CurProgress >= MaxProgress; + public virtual bool Completed => m_CurProgress >= MaxProgress; - public bool IsSingleObjective => ( MaxProgress == 1 ); + public bool IsSingleObjective => MaxProgress == 1; - public QuestObjective() - { - } + public virtual void BaseDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public virtual void BaseDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + switch (version) + { + case 1: + { + HasBeenRead = reader.ReadBool(); + goto case 0; + } + case 0: + { + m_CurProgress = reader.ReadEncodedInt(); + HasCompleted = reader.ReadBool(); - switch ( version ) - { - case 1: - { - HasBeenRead = reader.ReadBool(); - goto case 0; - } - case 0: - { - m_CurProgress = reader.ReadEncodedInt(); - HasCompleted = reader.ReadBool(); + break; + } + } - break; - } - } + ChildDeserialize(reader); + } - ChildDeserialize( reader ); - } + public virtual void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + } - public virtual void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - } + public virtual void BaseSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(1); // version - public virtual void BaseSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 1 ); // version + writer.Write(HasBeenRead); + writer.WriteEncodedInt(m_CurProgress); + writer.Write(HasCompleted); - writer.Write( (bool) HasBeenRead ); - writer.WriteEncodedInt( (int) m_CurProgress ); - writer.Write( (bool) HasCompleted ); + ChildSerialize(writer); + } - ChildSerialize( writer ); - } + public virtual void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + } - public virtual void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - } + public virtual void Complete() + { + CurProgress = MaxProgress; + } - public virtual void Complete() - { - CurProgress = MaxProgress; - } + public virtual void RenderMessage(BaseQuestGump gump) + { + gump.AddHtmlObject(70, 130, 300, 100, Message, BaseQuestGump.Blue, false, false); + } - public virtual void RenderMessage( BaseQuestGump gump ) - { - gump.AddHtmlObject( 70, 130, 300, 100, Message, BaseQuestGump.Blue, false, false ); - } + public virtual void RenderProgress(BaseQuestGump gump) + { + gump.AddHtmlObject(70, 260, 270, 100, Completed ? 1049077 : 1049078, BaseQuestGump.Blue, false, false); + } - public virtual void RenderProgress( BaseQuestGump gump ) - { - gump.AddHtmlObject( 70, 260, 270, 100, Completed ? 1049077 : 1049078, BaseQuestGump.Blue, false, false ); - } + public virtual void CheckCompletionStatus() + { + if (Completed && !HasCompleted) + { + HasCompleted = true; + OnComplete(); + } + } - public virtual void CheckCompletionStatus() - { - if ( Completed && !HasCompleted ) - { - HasCompleted = true; - OnComplete(); - } - } + public virtual void OnRead() + { + } - public virtual void OnRead() - { - } + public virtual bool GetTimerEvent() + { + return !Completed; + } - public virtual bool GetTimerEvent() - { - return !Completed; - } + public virtual void CheckProgress() + { + } - public virtual void CheckProgress() - { - } + public virtual void OnComplete() + { + } - public virtual void OnComplete() - { - } + public virtual bool GetKillEvent(BaseCreature creature, Container corpse) + { + return !Completed; + } - public virtual bool GetKillEvent( BaseCreature creature, Container corpse ) - { - return !Completed; - } + public virtual void OnKill(BaseCreature creature, Container corpse) + { + } - public virtual void OnKill( BaseCreature creature, Container corpse ) - { - } + public virtual bool IgnoreYoungProtection(Mobile from) + { + return false; + } + } - public virtual bool IgnoreYoungProtection( Mobile from ) - { - return false; - } - } + public class QuestLogUpdatedGump : BaseQuestGump + { + private QuestSystem m_System; - public class QuestLogUpdatedGump : BaseQuestGump - { - private QuestSystem m_System; + public QuestLogUpdatedGump(QuestSystem system) : base(3, 30) + { + m_System = system; - public QuestLogUpdatedGump( QuestSystem system ) : base( 3, 30 ) - { - m_System = system; + AddPage(0); - AddPage( 0 ); + AddImage(20, 5, 1417); - AddImage( 20, 5, 1417 ); + AddHtmlLocalized(0, 78, 120, 40, 1049079, White, false, false); // Quest Log Updated - AddHtmlLocalized( 0, 78, 120, 40, 1049079, White, false, false ); // Quest Log Updated + AddImageTiled(0, 78, 120, 40, 2624); + AddAlphaRegion(0, 78, 120, 40); - AddImageTiled( 0, 78, 120, 40, 2624 ); - AddAlphaRegion( 0, 78, 120, 40 ); + AddButton(30, 15, 5575, 5576, 1, GumpButtonType.Reply, 0); + } - AddButton( 30, 15, 5575, 5576, 1, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_System.ShowQuestLog(); + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_System.ShowQuestLog(); - } - } + public class QuestObjectivesGump : BaseQuestGump + { + private ArrayList m_Objectives; - public class QuestObjectivesGump : BaseQuestGump - { - private ArrayList m_Objectives; + public QuestObjectivesGump(QuestObjective obj) : this(BuildList(obj)) + { + } - public QuestObjectivesGump( QuestObjective obj ) : this( BuildList( obj ) ) - { - } + public QuestObjectivesGump(ArrayList objectives) : base(90, 50) + { + m_Objectives = objectives; - public QuestObjectivesGump( ArrayList objectives ) : base( 90, 50 ) - { - m_Objectives = objectives; + Closable = false; - Closable = false; + AddPage(0); - AddPage( 0 ); + AddImage(0, 0, 3600); + AddImageTiled(0, 14, 15, 375, 3603); + AddImageTiled(380, 14, 14, 375, 3605); + AddImage(0, 376, 3606); + AddImageTiled(15, 376, 370, 16, 3607); + AddImageTiled(15, 0, 370, 16, 3601); + AddImage(380, 0, 3602); + AddImage(380, 376, 3608); - AddImage( 0, 0, 3600 ); - AddImageTiled( 0, 14, 15, 375, 3603 ); - AddImageTiled( 380, 14, 14, 375, 3605 ); - AddImage( 0, 376, 3606 ); - AddImageTiled( 15, 376, 370, 16, 3607 ); - AddImageTiled( 15, 0, 370, 16, 3601 ); - AddImage( 380, 0, 3602 ); - AddImage( 380, 376, 3608 ); + AddImageTiled(15, 15, 365, 365, 2624); + AddAlphaRegion(15, 15, 365, 365); - AddImageTiled( 15, 15, 365, 365, 2624 ); - AddAlphaRegion( 15, 15, 365, 365 ); + AddImage(20, 87, 1231); + AddImage(75, 62, 9307); - AddImage( 20, 87, 1231 ); - AddImage( 75, 62, 9307 ); + AddHtmlLocalized(117, 35, 230, 20, 1046026, Blue, false, false); // Quest Log - AddHtmlLocalized( 117, 35, 230, 20, 1046026, Blue, false, false ); // Quest Log + AddImage(77, 33, 9781); + AddImage(65, 110, 2104); - AddImage( 77, 33, 9781 ); - AddImage( 65, 110, 2104 ); + AddHtmlLocalized(79, 106, 230, 20, 1049073, Blue, false, false); // Objective: - AddHtmlLocalized( 79, 106, 230, 20, 1049073, Blue, false, false ); // Objective: + AddImageTiled(68, 125, 120, 1, 9101); + AddImage(65, 240, 2104); - AddImageTiled( 68, 125, 120, 1, 9101 ); - AddImage( 65, 240, 2104 ); + AddHtmlLocalized(79, 237, 230, 20, 1049076, Blue, false, false); // Progress details: - AddHtmlLocalized( 79, 237, 230, 20, 1049076, Blue, false, false ); // Progress details: + AddImageTiled(68, 255, 120, 1, 9101); + AddButton(175, 355, 2313, 2312, 1, GumpButtonType.Reply, 0); - AddImageTiled( 68, 255, 120, 1, 9101 ); - AddButton( 175, 355, 2313, 2312, 1, GumpButtonType.Reply, 0 ); + AddImage(341, 15, 10450); + AddImage(341, 330, 10450); + AddImage(15, 330, 10450); + AddImage(15, 15, 10450); - AddImage( 341, 15, 10450 ); - AddImage( 341, 330, 10450 ); - AddImage( 15, 330, 10450 ); - AddImage( 15, 15, 10450 ); + AddPage(1); - AddPage( 1 ); + for (int i = 0; i < objectives.Count; ++i) + { + QuestObjective obj = (QuestObjective)objectives[objectives.Count - 1 - i]; - for ( int i = 0; i < objectives.Count; ++i ) - { - QuestObjective obj = (QuestObjective)objectives[objectives.Count - 1 - i]; + if (i > 0) + { + AddButton(55, 346, 9909, 9911, 0, GumpButtonType.Page, 1 + i); + AddHtmlLocalized(82, 347, 50, 20, 1043354, White, false, false); // Previous - if ( i > 0 ) - { - AddButton( 55, 346, 9909, 9911, 0, GumpButtonType.Page, 1 + i ); - AddHtmlLocalized( 82, 347, 50, 20, 1043354, White, false, false ); // Previous + AddPage(1 + i); + } - AddPage( 1 + i ); - } + obj.RenderMessage(this); + obj.RenderProgress(this); - obj.RenderMessage( this ); - obj.RenderProgress( this ); + if (i > 0) + { + AddButton(317, 346, 9903, 9905, 0, GumpButtonType.Page, i); + AddHtmlLocalized(278, 347, 50, 20, 1043353, White, false, false); // Next + } + } + } - if ( i > 0 ) - { - AddButton( 317, 346, 9903, 9905, 0, GumpButtonType.Page, i ); - AddHtmlLocalized( 278, 347, 50, 20, 1043353, White, false, false ); // Next - } - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + for (int i = m_Objectives.Count - 1; i >= 0; --i) + { + QuestObjective obj = (QuestObjective)m_Objectives[i]; - public override void OnResponse( NetState sender, RelayInfo info ) - { - for ( int i = m_Objectives.Count - 1; i >= 0; --i ) - { - QuestObjective obj = (QuestObjective)m_Objectives[i]; - - if ( !obj.HasBeenRead ) - { - obj.HasBeenRead = true; - obj.OnRead(); - } - } - } - } + if (!obj.HasBeenRead) + { + obj.HasBeenRead = true; + obj.OnRead(); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestRestartInfo.cs b/Scripts/Engines/Quests/Core/QuestRestartInfo.cs index c1e3668b7..c65298902 100644 --- a/Scripts/Engines/Quests/Core/QuestRestartInfo.cs +++ b/Scripts/Engines/Quests/Core/QuestRestartInfo.cs @@ -2,30 +2,30 @@ using System; namespace Server.Engines.Quests { - public class QuestRestartInfo - { - public Type QuestType { get; set; } + public class QuestRestartInfo + { + public QuestRestartInfo(Type questType, TimeSpan restartDelay) + { + QuestType = questType; + Reset(restartDelay); + } - public DateTime RestartTime { get; set; } + public QuestRestartInfo(Type questType, DateTime restartTime) + { + QuestType = questType; + RestartTime = restartTime; + } - public void Reset( TimeSpan restartDelay ) - { - if ( restartDelay < TimeSpan.MaxValue ) - RestartTime = DateTime.UtcNow + restartDelay; - else - RestartTime = DateTime.MaxValue; - } + public Type QuestType{ get; set; } - public QuestRestartInfo( Type questType, TimeSpan restartDelay ) - { - QuestType = questType; - Reset( restartDelay ); - } + public DateTime RestartTime{ get; set; } - public QuestRestartInfo( Type questType, DateTime restartTime ) - { - QuestType = questType; - RestartTime = restartTime; - } - } + public void Reset(TimeSpan restartDelay) + { + if (restartDelay < TimeSpan.MaxValue) + RestartTime = DateTime.UtcNow + restartDelay; + else + RestartTime = DateTime.MaxValue; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestSerializer.cs b/Scripts/Engines/Quests/Core/QuestSerializer.cs index 38bd094f0..d37999176 100644 --- a/Scripts/Engines/Quests/Core/QuestSerializer.cs +++ b/Scripts/Engines/Quests/Core/QuestSerializer.cs @@ -2,193 +2,191 @@ using System; namespace Server.Engines.Quests { - public class QuestSerializer - { - public static object Construct( Type type ) - { - try - { - return Activator.CreateInstance( type ); - } - catch - { - return null; - } - } + public class QuestSerializer + { + public static object Construct(Type type) + { + try + { + return Activator.CreateInstance(type); + } + catch + { + return null; + } + } - public static void Write( Type type, Type[] referenceTable, GenericWriter writer ) - { - if ( type == null ) - { - writer.WriteEncodedInt( (int) 0x00 ); - } - else - { - for ( int i = 0; i < referenceTable.Length; ++i ) - { - if ( referenceTable[i] == type ) - { - writer.WriteEncodedInt( (int) 0x01 ); - writer.WriteEncodedInt( (int) i ); - return; - } - } + public static void Write(Type type, Type[] referenceTable, GenericWriter writer) + { + if (type == null) + { + writer.WriteEncodedInt(0x00); + } + else + { + for (int i = 0; i < referenceTable.Length; ++i) + if (referenceTable[i] == type) + { + writer.WriteEncodedInt(0x01); + writer.WriteEncodedInt(i); + return; + } - writer.WriteEncodedInt( (int) 0x02 ); - writer.Write( type.FullName ); - } - } + writer.WriteEncodedInt(0x02); + writer.Write(type.FullName); + } + } - public static Type ReadType( Type[] referenceTable, GenericReader reader ) - { - int encoding = reader.ReadEncodedInt(); + public static Type ReadType(Type[] referenceTable, GenericReader reader) + { + int encoding = reader.ReadEncodedInt(); - switch ( encoding ) - { - default: - case 0x00: // null - { - return null; - } - case 0x01: // indexed - { - int index = reader.ReadEncodedInt(); + switch (encoding) + { + default: + case 0x00: // null + { + return null; + } + case 0x01: // indexed + { + int index = reader.ReadEncodedInt(); - if ( index >= 0 && index < referenceTable.Length ) - return referenceTable[index]; + if (index >= 0 && index < referenceTable.Length) + return referenceTable[index]; - return null; - } - case 0x02: // by name - { - string fullName = reader.ReadString(); + return null; + } + case 0x02: // by name + { + string fullName = reader.ReadString(); - if ( fullName == null ) - return null; + if (fullName == null) + return null; - return ScriptCompiler.FindTypeByFullName( fullName, false ); - } - } - } + return ScriptCompiler.FindTypeByFullName(fullName, false); + } + } + } - public static QuestSystem DeserializeQuest( GenericReader reader ) - { - int encoding = reader.ReadEncodedInt(); + public static QuestSystem DeserializeQuest(GenericReader reader) + { + int encoding = reader.ReadEncodedInt(); - switch ( encoding ) - { - default: - case 0x00: // null - { - return null; - } - case 0x01: - { - Type type = ReadType( QuestSystem.QuestTypes, reader ); + switch (encoding) + { + default: + case 0x00: // null + { + return null; + } + case 0x01: + { + Type type = ReadType(QuestSystem.QuestTypes, reader); - QuestSystem qs = Construct( type ) as QuestSystem; + QuestSystem qs = Construct(type) as QuestSystem; - qs?.BaseDeserialize( reader ); + qs?.BaseDeserialize(reader); - return qs; - } - } - } + return qs; + } + } + } - public static void Serialize( QuestSystem qs, GenericWriter writer ) - { - if ( qs == null ) - { - writer.WriteEncodedInt( 0x00 ); - } - else - { - writer.WriteEncodedInt( 0x01 ); + public static void Serialize(QuestSystem qs, GenericWriter writer) + { + if (qs == null) + { + writer.WriteEncodedInt(0x00); + } + else + { + writer.WriteEncodedInt(0x01); - Write( qs.GetType(), QuestSystem.QuestTypes, writer ); + Write(qs.GetType(), QuestSystem.QuestTypes, writer); - qs.BaseSerialize( writer ); - } - } + qs.BaseSerialize(writer); + } + } - public static QuestObjective DeserializeObjective( Type[] referenceTable, GenericReader reader ) - { - int encoding = reader.ReadEncodedInt(); + public static QuestObjective DeserializeObjective(Type[] referenceTable, GenericReader reader) + { + int encoding = reader.ReadEncodedInt(); - switch ( encoding ) - { - default: - case 0x00: // null - { - return null; - } - case 0x01: - { - Type type = ReadType( referenceTable, reader ); + switch (encoding) + { + default: + case 0x00: // null + { + return null; + } + case 0x01: + { + Type type = ReadType(referenceTable, reader); - QuestObjective obj = Construct( type ) as QuestObjective; + QuestObjective obj = Construct(type) as QuestObjective; - obj?.BaseDeserialize( reader ); + obj?.BaseDeserialize(reader); - return obj; - } - } - } + return obj; + } + } + } - public static void Serialize( Type[] referenceTable, QuestObjective obj, GenericWriter writer ) - { - if ( obj == null ) - { - writer.WriteEncodedInt( 0x00 ); - } - else - { - writer.WriteEncodedInt( 0x01 ); + public static void Serialize(Type[] referenceTable, QuestObjective obj, GenericWriter writer) + { + if (obj == null) + { + writer.WriteEncodedInt(0x00); + } + else + { + writer.WriteEncodedInt(0x01); - Write( obj.GetType(), referenceTable, writer ); + Write(obj.GetType(), referenceTable, writer); - obj.BaseSerialize( writer ); - } - } + obj.BaseSerialize(writer); + } + } - public static QuestConversation DeserializeConversation( Type[] referenceTable, GenericReader reader ) - { - int encoding = reader.ReadEncodedInt(); + public static QuestConversation DeserializeConversation(Type[] referenceTable, GenericReader reader) + { + int encoding = reader.ReadEncodedInt(); - switch ( encoding ) - { - default: - case 0x00: // null - { - return null; - } - case 0x01: - { - Type type = ReadType( referenceTable, reader ); + switch (encoding) + { + default: + case 0x00: // null + { + return null; + } + case 0x01: + { + Type type = ReadType(referenceTable, reader); - QuestConversation conv = Construct( type ) as QuestConversation; + QuestConversation conv = Construct(type) as QuestConversation; - conv?.BaseDeserialize( reader ); + conv?.BaseDeserialize(reader); - return conv; - } - } - } + return conv; + } + } + } - public static void Serialize( Type[] referenceTable, QuestConversation conv, GenericWriter writer ) - { - if ( conv == null ) - { - writer.WriteEncodedInt( 0x00 ); - } - else - { - writer.WriteEncodedInt( 0x01 ); + public static void Serialize(Type[] referenceTable, QuestConversation conv, GenericWriter writer) + { + if (conv == null) + { + writer.WriteEncodedInt(0x00); + } + else + { + writer.WriteEncodedInt(0x01); - Write( conv.GetType(), referenceTable, writer ); + Write(conv.GetType(), referenceTable, writer); - conv.BaseSerialize( writer ); - } - } - } + conv.BaseSerialize(writer); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/QuestSystem.cs b/Scripts/Engines/Quests/Core/QuestSystem.cs index ed4534b86..d925daca0 100644 --- a/Scripts/Engines/Quests/Core/QuestSystem.cs +++ b/Scripts/Engines/Quests/Core/QuestSystem.cs @@ -1,653 +1,669 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Items; +using Server.ContextMenus; +using Server.Engines.Quests.Ambitious; +using Server.Engines.Quests.Collector; +using Server.Engines.Quests.Doom; +using Server.Engines.Quests.Hag; +using Server.Engines.Quests.Haven; +using Server.Engines.Quests.Matriarch; +using Server.Engines.Quests.Naturalist; +using Server.Engines.Quests.Necro; +using Server.Engines.Quests.Ninja; +using Server.Engines.Quests.Samurai; +using Server.Engines.Quests.Zento; using Server.Gumps; +using Server.Items; using Server.Mobiles; using Server.Network; -using Server.ContextMenus; namespace Server.Engines.Quests { - public delegate void QuestCallback(); - - public abstract class QuestSystem - { - public static readonly Type[] QuestTypes = { - typeof( Doom.TheSummoningQuest ), - typeof( Necro.DarkTidesQuest ), - typeof( Haven.UzeraanTurmoilQuest ), - typeof( Collector.CollectorQuest ), - typeof( Hag.WitchApprenticeQuest ), - typeof( Naturalist.StudyOfSolenQuest ), - typeof( Matriarch.SolenMatriarchQuest ), - typeof( Ambitious.AmbitiousQueenQuest ), - typeof( Ninja.EminosUndertakingQuest ), - typeof( Samurai.HaochisTrialsQuest ), - typeof( Zento.TerribleHatchlingsQuest ) - }; - - public abstract object Name{ get; } - public abstract object OfferMessage{ get; } - - public abstract int Picture{ get; } - - public abstract bool IsTutorial{ get; } - public abstract TimeSpan RestartDelay{ get; } + public delegate void QuestCallback(); + + public abstract class QuestSystem + { + public static readonly Type[] QuestTypes = + { + typeof(TheSummoningQuest), + typeof(DarkTidesQuest), + typeof(UzeraanTurmoilQuest), + typeof(CollectorQuest), + typeof(WitchApprenticeQuest), + typeof(StudyOfSolenQuest), + typeof(SolenMatriarchQuest), + typeof(AmbitiousQueenQuest), + typeof(EminosUndertakingQuest), + typeof(HaochisTrialsQuest), + typeof(TerribleHatchlingsQuest) + }; + + private Timer m_Timer; + + public QuestSystem(PlayerMobile from) + { + From = from; + Objectives = new ArrayList(); + Conversations = new ArrayList(); + } + + public QuestSystem() + { + } + + public abstract object Name{ get; } + public abstract object OfferMessage{ get; } + + public abstract int Picture{ get; } + + public abstract bool IsTutorial{ get; } + public abstract TimeSpan RestartDelay{ get; } + + public abstract Type[] TypeReferenceTable{ get; } + + public PlayerMobile From{ get; set; } + + public ArrayList Objectives{ get; set; } + + public ArrayList Conversations{ get; set; } + + public virtual void StartTimer() + { + if (m_Timer != null) + return; + + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5), Slice); + } + + public virtual void StopTimer() + { + m_Timer?.Stop(); + + m_Timer = null; + } - public abstract Type[] TypeReferenceTable{ get; } - - public PlayerMobile From { get; set; } + public virtual void Slice() + { + for (int i = Objectives.Count - 1; i >= 0; --i) + { + QuestObjective obj = (QuestObjective)Objectives[i]; - public ArrayList Objectives { get; set; } - - public ArrayList Conversations { get; set; } - - private Timer m_Timer; - - public virtual void StartTimer() - { - if ( m_Timer != null ) - return; - - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ), Slice ); - } - - public virtual void StopTimer() - { - m_Timer?.Stop(); - - m_Timer = null; - } - - public virtual void Slice() - { - for ( int i = Objectives.Count - 1; i >= 0; --i ) - { - QuestObjective obj = (QuestObjective)Objectives[i]; + if (obj.GetTimerEvent()) + obj.CheckProgress(); + } + } - if ( obj.GetTimerEvent() ) - obj.CheckProgress(); - } - } + public virtual void OnKill(BaseCreature creature, Container corpse) + { + for (int i = Objectives.Count - 1; i >= 0; --i) + { + QuestObjective obj = (QuestObjective)Objectives[i]; - public virtual void OnKill( BaseCreature creature, Container corpse ) - { - for ( int i = Objectives.Count - 1; i >= 0; --i ) - { - QuestObjective obj = (QuestObjective)Objectives[i]; + if (obj.GetKillEvent(creature, corpse)) + obj.OnKill(creature, corpse); + } + } - if ( obj.GetKillEvent( creature, corpse ) ) - obj.OnKill( creature, corpse ); - } - } + public virtual bool IgnoreYoungProtection(Mobile from) + { + for (int i = Objectives.Count - 1; i >= 0; --i) + { + QuestObjective obj = (QuestObjective)Objectives[i]; - public virtual bool IgnoreYoungProtection( Mobile from ) - { - for ( int i = Objectives.Count - 1; i >= 0; --i ) - { - QuestObjective obj = (QuestObjective)Objectives[i]; + if (obj.IgnoreYoungProtection(from)) + return true; + } - if ( obj.IgnoreYoungProtection( from ) ) - return true; - } + return false; + } - return false; - } + public virtual void BaseDeserialize(GenericReader reader) + { + Type[] referenceTable = TypeReferenceTable; - public QuestSystem( PlayerMobile from ) - { - From = from; - Objectives = new ArrayList(); - Conversations = new ArrayList(); - } + int version = reader.ReadEncodedInt(); - public QuestSystem() - { - } + switch (version) + { + case 0: + { + int count = reader.ReadEncodedInt(); - public virtual void BaseDeserialize( GenericReader reader ) - { - Type[] referenceTable = TypeReferenceTable; + Objectives = new ArrayList(count); - int version = reader.ReadEncodedInt(); + for (int i = 0; i < count; ++i) + { + QuestObjective obj = QuestSerializer.DeserializeObjective(referenceTable, reader); - switch ( version ) - { - case 0: - { - int count = reader.ReadEncodedInt(); + if (obj != null) + { + obj.System = this; + Objectives.Add(obj); + } + } - Objectives = new ArrayList( count ); + count = reader.ReadEncodedInt(); - for ( int i = 0; i < count; ++i ) - { - QuestObjective obj = QuestSerializer.DeserializeObjective( referenceTable, reader ); + Conversations = new ArrayList(count); - if ( obj != null ) - { - obj.System = this; - Objectives.Add( obj ); - } - } + for (int i = 0; i < count; ++i) + { + QuestConversation conv = QuestSerializer.DeserializeConversation(referenceTable, reader); - count = reader.ReadEncodedInt(); + if (conv != null) + { + conv.System = this; + Conversations.Add(conv); + } + } - Conversations = new ArrayList( count ); + break; + } + } - for ( int i = 0; i < count; ++i ) - { - QuestConversation conv = QuestSerializer.DeserializeConversation( referenceTable, reader ); + ChildDeserialize(reader); + } - if ( conv != null ) - { - conv.System = this; - Conversations.Add( conv ); - } - } - - break; - } - } - - ChildDeserialize( reader ); - } - - public virtual void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - } - - public virtual void BaseSerialize( GenericWriter writer ) - { - Type[] referenceTable = TypeReferenceTable; - - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) Objectives.Count ); - - for ( int i = 0; i < Objectives.Count; ++i ) - QuestSerializer.Serialize( referenceTable, (QuestObjective) Objectives[i], writer ); - - writer.WriteEncodedInt( (int) Conversations.Count ); - - for ( int i = 0; i < Conversations.Count; ++i ) - QuestSerializer.Serialize( referenceTable, (QuestConversation) Conversations[i], writer ); - - ChildSerialize( writer ); - } - - public virtual void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - } - - public bool IsObjectiveInProgress( Type type ) - { - QuestObjective obj = FindObjective( type ); - - return ( obj != null && !obj.Completed ); - } - - public QuestObjective FindObjective( Type type ) - { - for ( int i = Objectives.Count - 1; i >= 0; --i ) - { - QuestObjective obj = (QuestObjective)Objectives[i]; - - if ( obj.GetType() == type ) - return obj; - } - - return null; - } - - public virtual void SendOffer() - { - From.SendGump( new QuestOfferGump( this ) ); - } - - public virtual void GetContextMenuEntries( List list ) - { - if ( Objectives.Count > 0 ) - list.Add( new QuestCallbackEntry( 6154, ShowQuestLog ) ); // View Quest Log + public virtual void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + } + + public virtual void BaseSerialize(GenericWriter writer) + { + Type[] referenceTable = TypeReferenceTable; + + writer.WriteEncodedInt(0); // version - if ( Conversations.Count > 0 ) - list.Add( new QuestCallbackEntry( 6156, ShowQuestConversation ) ); // Quest Conversation + writer.WriteEncodedInt(Objectives.Count); + + for (int i = 0; i < Objectives.Count; ++i) + QuestSerializer.Serialize(referenceTable, (QuestObjective)Objectives[i], writer); + + writer.WriteEncodedInt(Conversations.Count); + + for (int i = 0; i < Conversations.Count; ++i) + QuestSerializer.Serialize(referenceTable, (QuestConversation)Conversations[i], writer); + + ChildSerialize(writer); + } + + public virtual void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + } + + public bool IsObjectiveInProgress(Type type) + { + QuestObjective obj = FindObjective(type); + + return obj != null && !obj.Completed; + } + + public QuestObjective FindObjective(Type type) + { + for (int i = Objectives.Count - 1; i >= 0; --i) + { + QuestObjective obj = (QuestObjective)Objectives[i]; + + if (obj.GetType() == type) + return obj; + } + + return null; + } + + public virtual void SendOffer() + { + From.SendGump(new QuestOfferGump(this)); + } + + public virtual void GetContextMenuEntries(List list) + { + if (Objectives.Count > 0) + list.Add(new QuestCallbackEntry(6154, ShowQuestLog)); // View Quest Log - list.Add( new QuestCallbackEntry( 6155, BeginCancelQuest ) ); // Cancel Quest - } + if (Conversations.Count > 0) + list.Add(new QuestCallbackEntry(6156, ShowQuestConversation)); // Quest Conversation - public virtual void ShowQuestLogUpdated() - { - From.CloseGump( typeof( QuestLogUpdatedGump ) ); - From.SendGump( new QuestLogUpdatedGump( this ) ); - } - - public virtual void ShowQuestLog() - { - if ( Objectives.Count > 0 ) - { - From.CloseGump( typeof( QuestItemInfoGump ) ); - From.CloseGump( typeof( QuestLogUpdatedGump ) ); - From.CloseGump( typeof( QuestObjectivesGump ) ); - From.CloseGump( typeof( QuestConversationsGump ) ); - - From.SendGump( new QuestObjectivesGump( Objectives ) ); - - QuestObjective last = (QuestObjective)Objectives[Objectives.Count - 1]; - - if ( last.Info != null ) - From.SendGump( new QuestItemInfoGump( last.Info ) ); - } - } - - public virtual void ShowQuestConversation() - { - if ( Conversations.Count > 0 ) - { - From.CloseGump( typeof( QuestItemInfoGump ) ); - From.CloseGump( typeof( QuestObjectivesGump ) ); - From.CloseGump( typeof( QuestConversationsGump ) ); - - From.SendGump( new QuestConversationsGump( Conversations ) ); - - QuestConversation last = (QuestConversation)Conversations[Conversations.Count - 1]; - - if ( last.Info != null ) - From.SendGump( new QuestItemInfoGump( last.Info ) ); - } - } - - public virtual void BeginCancelQuest() - { - From.SendGump( new QuestCancelGump( this ) ); - } - - public virtual void EndCancelQuest( bool shouldCancel ) - { - if ( From.Quest != this ) - return; - - if ( shouldCancel ) - { - From.SendLocalizedMessage( 1049015 ); // You have canceled your quest. - Cancel(); - } - else - { - From.SendLocalizedMessage( 1049014 ); // You have chosen not to cancel your quest. - } - } - - public virtual void Cancel() - { - ClearQuest( false ); - } - - public virtual void Complete() - { - ClearQuest( true ); - } - - public virtual void ClearQuest( bool completed ) - { - StopTimer(); - - if ( From.Quest == this ) - { - From.Quest = null; - - TimeSpan restartDelay = RestartDelay; - - if ( ( completed && restartDelay > TimeSpan.Zero ) || ( !completed && restartDelay == TimeSpan.MaxValue ) ) - { - List doneQuests = From.DoneQuests; - - if ( doneQuests == null ) - From.DoneQuests = doneQuests = new List(); - - bool found = false; - - Type ourQuestType = GetType(); - - for ( int i = 0; i < doneQuests.Count; ++i ) - { - QuestRestartInfo restartInfo = doneQuests[i]; - - if ( restartInfo.QuestType == ourQuestType ) - { - restartInfo.Reset( restartDelay ); - found = true; - break; - } - } - - if ( !found ) - doneQuests.Add( new QuestRestartInfo( ourQuestType, restartDelay ) ); - } - } - } - - public virtual void AddConversation( QuestConversation conv ) - { - conv.System = this; - - if ( conv.Logged ) - Conversations.Add( conv ); - - From.CloseGump( typeof( QuestItemInfoGump ) ); - From.CloseGump( typeof( QuestObjectivesGump ) ); - From.CloseGump( typeof( QuestConversationsGump ) ); - - if ( conv.Logged ) - From.SendGump( new QuestConversationsGump( Conversations ) ); - else - From.SendGump( new QuestConversationsGump( conv ) ); - - if ( conv.Info != null ) - From.SendGump( new QuestItemInfoGump( conv.Info ) ); - } - - public virtual void AddObjective( QuestObjective obj ) - { - obj.System = this; - Objectives.Add( obj ); - - ShowQuestLogUpdated(); - } - - public virtual void Accept() - { - if ( From.Quest != null ) - return; - - From.Quest = this; - From.SendLocalizedMessage( 1049019 ); // You have accepted the Quest. - - StartTimer(); - } - - public virtual void Decline() - { - From.SendLocalizedMessage( 1049018 ); // You have declined the Quest. - } - - public static bool CanOfferQuest( Mobile check, Type questType ) - { - bool inRestartPeriod; - - return CanOfferQuest( check, questType, out inRestartPeriod ); - } + list.Add(new QuestCallbackEntry(6155, BeginCancelQuest)); // Cancel Quest + } - public static bool CanOfferQuest( Mobile check, Type questType, out bool inRestartPeriod ) - { - inRestartPeriod = false; + public virtual void ShowQuestLogUpdated() + { + From.CloseGump(typeof(QuestLogUpdatedGump)); + From.SendGump(new QuestLogUpdatedGump(this)); + } + + public virtual void ShowQuestLog() + { + if (Objectives.Count > 0) + { + From.CloseGump(typeof(QuestItemInfoGump)); + From.CloseGump(typeof(QuestLogUpdatedGump)); + From.CloseGump(typeof(QuestObjectivesGump)); + From.CloseGump(typeof(QuestConversationsGump)); + + From.SendGump(new QuestObjectivesGump(Objectives)); + + QuestObjective last = (QuestObjective)Objectives[Objectives.Count - 1]; + + if (last.Info != null) + From.SendGump(new QuestItemInfoGump(last.Info)); + } + } + + public virtual void ShowQuestConversation() + { + if (Conversations.Count > 0) + { + From.CloseGump(typeof(QuestItemInfoGump)); + From.CloseGump(typeof(QuestObjectivesGump)); + From.CloseGump(typeof(QuestConversationsGump)); + + From.SendGump(new QuestConversationsGump(Conversations)); + + QuestConversation last = (QuestConversation)Conversations[Conversations.Count - 1]; + + if (last.Info != null) + From.SendGump(new QuestItemInfoGump(last.Info)); + } + } + + public virtual void BeginCancelQuest() + { + From.SendGump(new QuestCancelGump(this)); + } + + public virtual void EndCancelQuest(bool shouldCancel) + { + if (From.Quest != this) + return; + + if (shouldCancel) + { + From.SendLocalizedMessage(1049015); // You have canceled your quest. + Cancel(); + } + else + { + From.SendLocalizedMessage(1049014); // You have chosen not to cancel your quest. + } + } + + public virtual void Cancel() + { + ClearQuest(false); + } + + public virtual void Complete() + { + ClearQuest(true); + } + + public virtual void ClearQuest(bool completed) + { + StopTimer(); + + if (From.Quest == this) + { + From.Quest = null; + + TimeSpan restartDelay = RestartDelay; + + if (completed && restartDelay > TimeSpan.Zero || !completed && restartDelay == TimeSpan.MaxValue) + { + List doneQuests = From.DoneQuests; + + if (doneQuests == null) + From.DoneQuests = doneQuests = new List(); + + bool found = false; + + Type ourQuestType = GetType(); + + for (int i = 0; i < doneQuests.Count; ++i) + { + QuestRestartInfo restartInfo = doneQuests[i]; + + if (restartInfo.QuestType == ourQuestType) + { + restartInfo.Reset(restartDelay); + found = true; + break; + } + } + + if (!found) + doneQuests.Add(new QuestRestartInfo(ourQuestType, restartDelay)); + } + } + } + + public virtual void AddConversation(QuestConversation conv) + { + conv.System = this; + + if (conv.Logged) + Conversations.Add(conv); + + From.CloseGump(typeof(QuestItemInfoGump)); + From.CloseGump(typeof(QuestObjectivesGump)); + From.CloseGump(typeof(QuestConversationsGump)); + + if (conv.Logged) + From.SendGump(new QuestConversationsGump(Conversations)); + else + From.SendGump(new QuestConversationsGump(conv)); + + if (conv.Info != null) + From.SendGump(new QuestItemInfoGump(conv.Info)); + } + + public virtual void AddObjective(QuestObjective obj) + { + obj.System = this; + Objectives.Add(obj); + + ShowQuestLogUpdated(); + } + + public virtual void Accept() + { + if (From.Quest != null) + return; + + From.Quest = this; + From.SendLocalizedMessage(1049019); // You have accepted the Quest. + + StartTimer(); + } + + public virtual void Decline() + { + From.SendLocalizedMessage(1049018); // You have declined the Quest. + } + + public static bool CanOfferQuest(Mobile check, Type questType) + { + bool inRestartPeriod; + + return CanOfferQuest(check, questType, out inRestartPeriod); + } + + public static bool CanOfferQuest(Mobile check, Type questType, out bool inRestartPeriod) + { + inRestartPeriod = false; + + if (!(check is PlayerMobile pm)) + return false; + + if (pm.HasGump(typeof(QuestOfferGump))) + return false; - if ( !(check is PlayerMobile pm) ) - return false; - - if ( pm.HasGump( typeof( QuestOfferGump ) ) ) - return false; + if (questType == typeof(DarkTidesQuest) && pm.Profession != 4) // necromancer + return false; + + if (questType == typeof(UzeraanTurmoilQuest) && pm.Profession != 1 && pm.Profession != 2 && pm.Profession != 5 + ) // warrior / magician / paladin + return false; - if ( questType == typeof( Necro.DarkTidesQuest ) && pm.Profession != 4 ) // necromancer - return false; + if (questType == typeof(HaochisTrialsQuest) && pm.Profession != 6) // samurai + return false; + + if (questType == typeof(EminosUndertakingQuest) && pm.Profession != 7) // ninja + return false; + + List doneQuests = pm.DoneQuests; + + if (doneQuests != null) + for (int i = 0; i < doneQuests.Count; ++i) + { + QuestRestartInfo restartInfo = doneQuests[i]; + + if (restartInfo.QuestType == questType) + { + DateTime endTime = restartInfo.RestartTime; + + if (DateTime.UtcNow < endTime) + { + inRestartPeriod = true; + return false; + } + + doneQuests.RemoveAt(i--); + return true; + } + } + + return true; + } + + public static void FocusTo(Mobile who, Mobile to) + { + if (Utility.RandomBool()) + who.Animate(17, 7, 1, true, false, 0); + else + switch (Utility.Random(3)) + { + case 0: + who.Animate(32, 7, 1, true, false, 0); + break; + case 1: + who.Animate(33, 7, 1, true, false, 0); + break; + case 2: + who.Animate(34, 7, 1, true, false, 0); + break; + } + + who.Direction = who.GetDirectionTo(to); + } + + public static int RandomBrightHue() + { + if (0.1 > Utility.RandomDouble()) + return Utility.RandomList(0x62, 0x71); + + return Utility.RandomList(0x03, 0x0D, 0x13, 0x1C, 0x21, 0x30, 0x37, 0x3A, 0x44, 0x59); + } + } + + public class QuestCancelGump : BaseQuestGump + { + private QuestSystem m_System; - if ( questType == typeof( Haven.UzeraanTurmoilQuest ) && pm.Profession != 1 && pm.Profession != 2 && pm.Profession != 5 ) // warrior / magician / paladin - return false; + public QuestCancelGump(QuestSystem system) : base(120, 50) + { + m_System = system; - if ( questType == typeof( Samurai.HaochisTrialsQuest ) && pm.Profession != 6 ) // samurai - return false; - - if ( questType == typeof( Ninja.EminosUndertakingQuest ) && pm.Profession != 7 ) // ninja - return false; - - List doneQuests = pm.DoneQuests; - - if ( doneQuests != null ) - { - for ( int i = 0; i < doneQuests.Count; ++i ) - { - QuestRestartInfo restartInfo = doneQuests[i]; - - if ( restartInfo.QuestType == questType ) - { - DateTime endTime = restartInfo.RestartTime; - - if ( DateTime.UtcNow < endTime ) - { - inRestartPeriod = true; - return false; - } - - doneQuests.RemoveAt( i-- ); - return true; - } - } - } - - return true; - } - - public static void FocusTo( Mobile who, Mobile to ) - { - if ( Utility.RandomBool() ) - { - who.Animate( 17, 7, 1, true, false, 0 ); - } - else - { - switch ( Utility.Random( 3 ) ) - { - case 0: who.Animate( 32, 7, 1, true, false, 0 ); break; - case 1: who.Animate( 33, 7, 1, true, false, 0 ); break; - case 2: who.Animate( 34, 7, 1, true, false, 0 ); break; - } - } - - who.Direction = who.GetDirectionTo( to ); - } - - public static int RandomBrightHue() - { - if ( 0.1 > Utility.RandomDouble() ) - return Utility.RandomList( 0x62, 0x71 ); + Closable = false; - return Utility.RandomList( 0x03, 0x0D, 0x13, 0x1C, 0x21, 0x30, 0x37, 0x3A, 0x44, 0x59 ); - } - } + AddPage(0); + + AddImageTiled(0, 0, 348, 262, 2702); + AddAlphaRegion(0, 0, 348, 262); - public class QuestCancelGump : BaseQuestGump - { - private QuestSystem m_System; + AddImage(0, 15, 10152); + AddImageTiled(0, 30, 17, 200, 10151); + AddImage(0, 230, 10154); - public QuestCancelGump( QuestSystem system ) : base( 120, 50 ) - { - m_System = system; + AddImage(15, 0, 10252); + AddImageTiled(30, 0, 300, 17, 10250); + AddImage(315, 0, 10254); - Closable = false; + AddImage(15, 244, 10252); + AddImageTiled(30, 244, 300, 17, 10250); + AddImage(315, 244, 10254); - AddPage( 0 ); + AddImage(330, 15, 10152); + AddImageTiled(330, 30, 17, 200, 10151); + AddImage(330, 230, 10154); + + AddImage(333, 2, 10006); + AddImage(333, 248, 10006); + AddImage(2, 248, 10006); + AddImage(2, 2, 10006); + + AddHtmlLocalized(25, 22, 200, 20, 1049000, 32000, false, false); // Confirm Quest Cancellation + AddImage(25, 40, 3007); + + if (system.IsTutorial) + { + AddHtmlLocalized(25, 55, 300, 120, 1060836, White, false, + false); // This quest will give you valuable information, skills and equipment that will help you advance in the game at a quicker pace.

Are you certain you wish to cancel at this time? + } + else + { + AddHtmlLocalized(25, 60, 300, 20, 1049001, White, false, false); // You have chosen to abort your quest: + AddImage(25, 81, 0x25E7); + AddHtmlObject(48, 80, 280, 20, system.Name, DarkGreen, false, false); + + AddHtmlLocalized(25, 120, 280, 20, 1049002, White, false, + false); // Can this quest be restarted after quitting? + AddImage(25, 141, 0x25E7); + AddHtmlLocalized(48, 140, 280, 20, system.RestartDelay < TimeSpan.MaxValue ? 1049016 : 1049017, DarkGreen, + false, false); // Yes/No + } + + AddRadio(25, 175, 9720, 9723, true, 1); + AddHtmlLocalized(60, 180, 280, 20, 1049005, White, false, false); // Yes, I really want to quit! + + AddRadio(25, 210, 9720, 9723, false, 0); + AddHtmlLocalized(60, 215, 280, 20, 1049006, White, false, false); // No, I don't want to quit. + + AddButton(265, 220, 247, 248, 1, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_System.EndCancelQuest(info.IsSwitched(1)); + } + } + + public class QuestOfferGump : BaseQuestGump + { + private QuestSystem m_System; + + public QuestOfferGump(QuestSystem system) : base(75, 25) + { + m_System = system; + + Closable = false; + + AddPage(0); + + AddImageTiled(50, 20, 400, 400, 2624); + AddAlphaRegion(50, 20, 400, 400); - AddImageTiled( 0, 0, 348, 262, 2702 ); - AddAlphaRegion( 0, 0, 348, 262 ); - - AddImage( 0, 15, 10152 ); - AddImageTiled( 0, 30, 17, 200, 10151 ); - AddImage( 0, 230, 10154 ); - - AddImage( 15, 0, 10252 ); - AddImageTiled( 30, 0, 300, 17, 10250 ); - AddImage( 315, 0, 10254 ); - - AddImage( 15, 244, 10252 ); - AddImageTiled( 30, 244, 300, 17, 10250 ); - AddImage( 315, 244, 10254 ); - - AddImage( 330, 15, 10152 ); - AddImageTiled( 330, 30, 17, 200, 10151 ); - AddImage( 330, 230, 10154 ); - - AddImage( 333, 2, 10006 ); - AddImage( 333, 248, 10006 ); - AddImage( 2, 248, 10006 ); - AddImage( 2, 2, 10006 ); - - AddHtmlLocalized( 25, 22, 200, 20, 1049000, 32000, false, false ); // Confirm Quest Cancellation - AddImage( 25, 40, 3007 ); - - if ( system.IsTutorial ) - { - AddHtmlLocalized( 25, 55, 300, 120, 1060836, White, false, false ); // This quest will give you valuable information, skills and equipment that will help you advance in the game at a quicker pace.

Are you certain you wish to cancel at this time? - } - else - { - AddHtmlLocalized( 25, 60, 300, 20, 1049001, White, false, false ); // You have chosen to abort your quest: - AddImage( 25, 81, 0x25E7 ); - AddHtmlObject( 48, 80, 280, 20, system.Name, DarkGreen, false, false ); - - AddHtmlLocalized( 25, 120, 280, 20, 1049002, White, false, false ); // Can this quest be restarted after quitting? - AddImage( 25, 141, 0x25E7 ); - AddHtmlLocalized( 48, 140, 280, 20, (system.RestartDelay < TimeSpan.MaxValue) ? 1049016 : 1049017, DarkGreen, false, false ); // Yes/No - } - - AddRadio( 25, 175, 9720, 9723, true, 1 ); - AddHtmlLocalized( 60, 180, 280, 20, 1049005, White, false, false ); // Yes, I really want to quit! - - AddRadio( 25, 210, 9720, 9723, false, 0 ); - AddHtmlLocalized( 60, 215, 280, 20, 1049006, White, false, false ); // No, I don't want to quit. - - AddButton( 265, 220, 247, 248, 1, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_System.EndCancelQuest( info.IsSwitched( 1 ) ); - } - } - - public class QuestOfferGump : BaseQuestGump - { - private QuestSystem m_System; - - public QuestOfferGump( QuestSystem system ) : base( 75, 25 ) - { - m_System = system; - - Closable = false; - - AddPage( 0 ); - - AddImageTiled( 50, 20, 400, 400, 2624 ); - AddAlphaRegion( 50, 20, 400, 400 ); - - AddImage( 90, 33, 9005 ); - AddHtmlLocalized( 130, 45, 270, 20, 1049010, White, false, false ); // Quest Offer - AddImageTiled( 130, 65, 175, 1, 9101 ); - - AddImage( 140, 110, 1209 ); - AddHtmlObject( 160, 108, 250, 20, system.Name, DarkGreen, false, false ); - - AddHtmlObject( 98, 140, 312, 200, system.OfferMessage, LightGreen, false, true ); - - AddRadio( 85, 350, 9720, 9723, true, 1 ); - AddHtmlLocalized( 120, 356, 280, 20, 1049011, White, false, false ); // I accept! - - AddRadio( 85, 385, 9720, 9723, false, 0 ); - AddHtmlLocalized( 120, 391, 280, 20, 1049012, White, false, false ); // No thanks, I decline. - - AddButton( 340, 390, 247, 248, 1, GumpButtonType.Reply, 0 ); - - AddImageTiled( 50, 29, 30, 390, 10460 ); - AddImageTiled( 34, 140, 17, 279, 9263 ); - - AddImage( 48, 135, 10411 ); - AddImage( -16, 285, 10402 ); - AddImage( 0, 10, 10421 ); - AddImage( 25, 0, 10420 ); - - AddImageTiled( 83, 15, 350, 15, 10250 ); - - AddImage( 34, 419, 10306 ); - AddImage( 442, 419, 10304 ); - AddImageTiled( 51, 419, 392, 17, 10101 ); - - AddImageTiled( 415, 29, 44, 390, 2605 ); - AddImageTiled( 415, 29, 30, 390, 10460 ); - AddImage( 425, 0, 10441 ); - - AddImage( 370, 50, 1417 ); - AddImage( 379, 60, system.Picture ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - { - if ( info.IsSwitched( 1 ) ) - m_System.Accept(); - else - m_System.Decline(); - } - } - } - - public abstract class BaseQuestGump : Gump - { - public const int Black = 0x0000; - public const int White = 0x7FFF; - public const int DarkGreen = 10000; - public const int LightGreen = 90000; - public const int Blue = 19777215; - - public static int C16232( int c16 ) - { - c16 &= 0x7FFF; - - int r = ( ((c16 >> 10) & 0x1F) << 3 ); - int g = ( ((c16 >> 05) & 0x1F) << 3 ); - int b = ( ((c16 >> 00) & 0x1F) << 3 ); - - return (r << 16) | (g << 8) | (b << 0); - } - - public static int C16216( int c16 ) - { - return c16 & 0x7FFF; - } - - public static int C32216( int c32 ) - { - c32 &= 0xFFFFFF; - - int r = ( ((c32 >> 16) & 0xFF) >> 3 ); - int g = ( ((c32 >> 08) & 0xFF) >> 3 ); - int b = ( ((c32 >> 00) & 0xFF) >> 3 ); - - return (r << 10) | (g << 5) | (b << 0); - } - - public static string Color( string text, int color ) - { - return $"{text}"; - } - - public static ArrayList BuildList( object obj ) - { - return new ArrayList { obj }; - } - - public void AddHtmlObject( int x, int y, int width, int height, object message, int color, bool back, bool scroll ) - { - if ( message is int html ) - AddHtmlLocalized( x, y, width, height, html, C16216( color ), back, scroll ); - else - AddHtml( x, y, width, height, Color( message.ToString(), C16232( color ) ), back, scroll ); - } - - public BaseQuestGump( int x, int y ) : base( x, y ) - { - } - } -} + AddImage(90, 33, 9005); + AddHtmlLocalized(130, 45, 270, 20, 1049010, White, false, false); // Quest Offer + AddImageTiled(130, 65, 175, 1, 9101); + + AddImage(140, 110, 1209); + AddHtmlObject(160, 108, 250, 20, system.Name, DarkGreen, false, false); + + AddHtmlObject(98, 140, 312, 200, system.OfferMessage, LightGreen, false, true); + + AddRadio(85, 350, 9720, 9723, true, 1); + AddHtmlLocalized(120, 356, 280, 20, 1049011, White, false, false); // I accept! + + AddRadio(85, 385, 9720, 9723, false, 0); + AddHtmlLocalized(120, 391, 280, 20, 1049012, White, false, false); // No thanks, I decline. + + AddButton(340, 390, 247, 248, 1, GumpButtonType.Reply, 0); + + AddImageTiled(50, 29, 30, 390, 10460); + AddImageTiled(34, 140, 17, 279, 9263); + + AddImage(48, 135, 10411); + AddImage(-16, 285, 10402); + AddImage(0, 10, 10421); + AddImage(25, 0, 10420); + + AddImageTiled(83, 15, 350, 15, 10250); + + AddImage(34, 419, 10306); + AddImage(442, 419, 10304); + AddImageTiled(51, 419, 392, 17, 10101); + + AddImageTiled(415, 29, 44, 390, 2605); + AddImageTiled(415, 29, 30, 390, 10460); + AddImage(425, 0, 10441); + + AddImage(370, 50, 1417); + AddImage(379, 60, system.Picture); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + { + if (info.IsSwitched(1)) + m_System.Accept(); + else + m_System.Decline(); + } + } + } + + public abstract class BaseQuestGump : Gump + { + public const int Black = 0x0000; + public const int White = 0x7FFF; + public const int DarkGreen = 10000; + public const int LightGreen = 90000; + public const int Blue = 19777215; + + public BaseQuestGump(int x, int y) : base(x, y) + { + } + + public static int C16232(int c16) + { + c16 &= 0x7FFF; + + int r = ((c16 >> 10) & 0x1F) << 3; + int g = ((c16 >> 05) & 0x1F) << 3; + int b = ((c16 >> 00) & 0x1F) << 3; + + return (r << 16) | (g << 8) | (b << 0); + } + + public static int C16216(int c16) + { + return c16 & 0x7FFF; + } + + public static int C32216(int c32) + { + c32 &= 0xFFFFFF; + + int r = ((c32 >> 16) & 0xFF) >> 3; + int g = ((c32 >> 08) & 0xFF) >> 3; + int b = ((c32 >> 00) & 0xFF) >> 3; + + return (r << 10) | (g << 5) | (b << 0); + } + + public static string Color(string text, int color) + { + return $"{text}"; + } + + public static ArrayList BuildList(object obj) + { + return new ArrayList { obj }; + } + + public void AddHtmlObject(int x, int y, int width, int height, object message, int color, bool back, bool scroll) + { + if (message is int html) + AddHtmlLocalized(x, y, width, height, html, C16216(color), back, scroll); + else + AddHtml(x, y, width, height, Color(message.ToString(), C16232(color)), back, scroll); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Regions/CancelQuestRegion.cs b/Scripts/Engines/Quests/Core/Regions/CancelQuestRegion.cs index f220ded16..34674fc1c 100644 --- a/Scripts/Engines/Quests/Core/Regions/CancelQuestRegion.cs +++ b/Scripts/Engines/Quests/Core/Regions/CancelQuestRegion.cs @@ -1,41 +1,41 @@ using System; using System.Xml; -using Server.Regions; using Server.Mobiles; +using Server.Regions; namespace Server.Engines.Quests { - public class CancelQuestRegion : BaseRegion - { - private Type m_Quest; + public class CancelQuestRegion : BaseRegion + { + private Type m_Quest; - public Type Quest => m_Quest; + public CancelQuestRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + ReadType(xml["quest"], "type", ref m_Quest); + } - public CancelQuestRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - ReadType( xml["quest"], "type", ref m_Quest ); - } + public Type Quest => m_Quest; - public override bool OnMoveInto( Mobile m, Direction d, Point3D newLocation, Point3D oldLocation ) - { - if ( !base.OnMoveInto ( m, d, newLocation, oldLocation ) ) - return false; + public override bool OnMoveInto(Mobile m, Direction d, Point3D newLocation, Point3D oldLocation) + { + if (!base.OnMoveInto(m, d, newLocation, oldLocation)) + return false; - if ( m.AccessLevel > AccessLevel.Player ) - return true; + if (m.AccessLevel > AccessLevel.Player) + return true; - if ( m_Quest == null ) - return true; + if (m_Quest == null) + return true; - if ( m is PlayerMobile player && player.Quest != null && player.Quest.GetType() == m_Quest ) - { - if ( !player.HasGump( typeof( QuestCancelGump ) ) ) - player.Quest.BeginCancelQuest(); + if (m is PlayerMobile player && player.Quest != null && player.Quest.GetType() == m_Quest) + { + if (!player.HasGump(typeof(QuestCancelGump))) + player.Quest.BeginCancelQuest(); - return false; - } + return false; + } - return true; - } - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Regions/QuestCompleteObjectiveRegion.cs b/Scripts/Engines/Quests/Core/Regions/QuestCompleteObjectiveRegion.cs index 985845210..ac739751b 100644 --- a/Scripts/Engines/Quests/Core/Regions/QuestCompleteObjectiveRegion.cs +++ b/Scripts/Engines/Quests/Core/Regions/QuestCompleteObjectiveRegion.cs @@ -1,40 +1,38 @@ using System; using System.Xml; -using Server.Regions; using Server.Mobiles; +using Server.Regions; namespace Server.Engines.Quests { - public class QuestCompleteObjectiveRegion : BaseRegion - { - private Type m_Quest; - private Type m_Objective; + public class QuestCompleteObjectiveRegion : BaseRegion + { + private Type m_Objective; + private Type m_Quest; - public Type Quest => m_Quest; - public Type Objective => m_Objective; + public QuestCompleteObjectiveRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + XmlElement questEl = xml["quest"]; - public QuestCompleteObjectiveRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - XmlElement questEl = xml["quest"]; + ReadType(questEl, "type", ref m_Quest); + ReadType(questEl, "complete", ref m_Objective); + } - ReadType( questEl, "type", ref m_Quest ); - ReadType( questEl, "complete", ref m_Objective ); - } + public Type Quest => m_Quest; + public Type Objective => m_Objective; - public override void OnEnter( Mobile m ) - { - base.OnEnter( m ); + public override void OnEnter(Mobile m) + { + base.OnEnter(m); - if ( m_Quest != null && m_Objective != null ) - { - if ( m is PlayerMobile player && player.Quest != null && player.Quest.GetType() == m_Quest ) - { - QuestObjective obj = player.Quest.FindObjective( m_Objective ); + if (m_Quest != null && m_Objective != null) + if (m is PlayerMobile player && player.Quest != null && player.Quest.GetType() == m_Quest) + { + QuestObjective obj = player.Quest.FindObjective(m_Objective); - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - } - } - } -} + if (obj != null && !obj.Completed) + obj.Complete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Regions/QuestNoEntryRegion.cs b/Scripts/Engines/Quests/Core/Regions/QuestNoEntryRegion.cs index 980b9274a..81c680721 100644 --- a/Scripts/Engines/Quests/Core/Regions/QuestNoEntryRegion.cs +++ b/Scripts/Engines/Quests/Core/Regions/QuestNoEntryRegion.cs @@ -1,57 +1,55 @@ using System; using System.Xml; -using Server.Regions; using Server.Mobiles; +using Server.Regions; namespace Server.Engines.Quests { - public class QuestNoEntryRegion : BaseRegion - { - private Type m_Quest; - private Type m_MinObjective; - private Type m_MaxObjective; - private int m_Message; + public class QuestNoEntryRegion : BaseRegion + { + private Type m_MaxObjective; + private int m_Message; + private Type m_MinObjective; + private Type m_Quest; - public Type Quest => m_Quest; - public Type MinObjective => m_MinObjective; - public Type MaxObjective => m_MaxObjective; - public int Message => m_Message; + public QuestNoEntryRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + XmlElement questEl = xml["quest"]; - public QuestNoEntryRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - XmlElement questEl = xml["quest"]; + ReadType(questEl, "type", ref m_Quest); + ReadType(questEl, "min", ref m_MinObjective, false); + ReadType(questEl, "max", ref m_MaxObjective, false); + ReadInt32(questEl, "message", ref m_Message, false); + } - ReadType( questEl, "type", ref m_Quest ); - ReadType( questEl, "min", ref m_MinObjective, false ); - ReadType( questEl, "max", ref m_MaxObjective, false ); - ReadInt32( questEl, "message", ref m_Message, false ); - } + public Type Quest => m_Quest; + public Type MinObjective => m_MinObjective; + public Type MaxObjective => m_MaxObjective; + public int Message => m_Message; - public override bool OnMoveInto( Mobile m, Direction d, Point3D newLocation, Point3D oldLocation ) - { - if ( !base.OnMoveInto ( m, d, newLocation, oldLocation ) ) - return false; + public override bool OnMoveInto(Mobile m, Direction d, Point3D newLocation, Point3D oldLocation) + { + if (!base.OnMoveInto(m, d, newLocation, oldLocation)) + return false; - if ( m.AccessLevel > AccessLevel.Player ) - return true; + if (m.AccessLevel > AccessLevel.Player) + return true; - if ( m is BaseCreature bc && !bc.Controlled && !bc.Summoned ) - return true; + if (m is BaseCreature bc && !bc.Controlled && !bc.Summoned) + return true; - if ( m_Quest == null ) - return true; + if (m_Quest == null) + return true; - if ( m is PlayerMobile player && player.Quest != null && player.Quest.GetType() == m_Quest - && ( m_MinObjective == null || player.Quest.FindObjective( m_MinObjective ) != null ) - && ( m_MaxObjective == null || player.Quest.FindObjective( m_MaxObjective ) == null ) ) - { - return true; - } + if (m is PlayerMobile player && player.Quest != null && player.Quest.GetType() == m_Quest + && (m_MinObjective == null || player.Quest.FindObjective(m_MinObjective) != null) + && (m_MaxObjective == null || player.Quest.FindObjective(m_MaxObjective) == null)) + return true; - if ( m_Message != 0 ) - m.SendLocalizedMessage( m_Message ); + if (m_Message != 0) + m.SendLocalizedMessage(m_Message); - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Core/Regions/QuestOfferRegion.cs b/Scripts/Engines/Quests/Core/Regions/QuestOfferRegion.cs index ebbb2f00b..6639c203c 100644 --- a/Scripts/Engines/Quests/Core/Regions/QuestOfferRegion.cs +++ b/Scripts/Engines/Quests/Core/Regions/QuestOfferRegion.cs @@ -1,40 +1,38 @@ using System; using System.Xml; -using Server.Regions; using Server.Mobiles; +using Server.Regions; namespace Server.Engines.Quests { - public class QuestOfferRegion : BaseRegion - { - private Type m_Quest; + public class QuestOfferRegion : BaseRegion + { + private Type m_Quest; - public Type Quest => m_Quest; + public QuestOfferRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + ReadType(xml["quest"], "type", ref m_Quest); + } - public QuestOfferRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - ReadType( xml["quest"], "type", ref m_Quest ); - } + public Type Quest => m_Quest; - public override void OnEnter( Mobile m ) - { - base.OnEnter( m ); + public override void OnEnter(Mobile m) + { + base.OnEnter(m); - if ( m_Quest == null ) - return; + if (m_Quest == null) + return; - if ( m is PlayerMobile player && player.Quest == null && QuestSystem.CanOfferQuest( m, m_Quest ) ) - { - try - { - QuestSystem qs = (QuestSystem) Activator.CreateInstance( m_Quest, new object[] { player } ); - qs.SendOffer(); - } - catch ( Exception ex ) - { - Console.WriteLine( "Error creating quest {0}: {1}", m_Quest, ex ); - } - } - } - } -} + if (m is PlayerMobile player && player.Quest == null && QuestSystem.CanOfferQuest(m, m_Quest)) + try + { + QuestSystem qs = (QuestSystem)Activator.CreateInstance(m_Quest, player); + qs.SendOffer(); + } + catch (Exception ex) + { + Console.WriteLine("Error creating quest {0}: {1}", m_Quest, ex); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Conversations.cs b/Scripts/Engines/Quests/Dark Tides/Conversations.cs index 465c6fa46..f02b10fad 100644 --- a/Scripts/Engines/Quests/Dark Tides/Conversations.cs +++ b/Scripts/Engines/Quests/Dark Tides/Conversations.cs @@ -2,268 +2,206 @@ using Server.Items; namespace Server.Engines.Quests.Necro { - public class AcceptConversation : QuestConversation - { - public override object Message => 1049092; + public class AcceptConversation : QuestConversation + { + public override object Message => 1049092; - public AcceptConversation() - { - } + public override void OnRead() + { + Container bag = BaseQuester.GetNewContainer(); - public override void OnRead() - { - Container bag = BaseQuester.GetNewContainer(); + bag.DropItem(new DarkTidesHorn()); - bag.DropItem( new DarkTidesHorn() ); + System.From.AddToBackpack(bag); - System.From.AddToBackpack( bag ); + System.AddConversation(new ReanimateMaabusConversation()); + } + } - System.AddConversation( new ReanimateMaabusConversation() ); - } - } + public class ReanimateMaabusConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1026153, 6178), // teleporter + new QuestItemInfo(1049117, 4036), // Horn of Retreat + new QuestItemInfo(1048032, 3702) // a bag + }; - public class ReanimateMaabusConversation : QuestConversation - { - public override object Message => 1060099; + public override object Message => 1060099; - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1026153, 6178 ), // teleporter - new QuestItemInfo( 1049117, 4036 ), // Horn of Retreat - new QuestItemInfo( 1048032, 3702 ) // a bag - }; + public override QuestItemInfo[] Info => m_Info; - public override QuestItemInfo[] Info => m_Info; + public override void OnRead() + { + System.AddObjective(new FindMaabusTombObjective()); + } + } - public ReanimateMaabusConversation() - { - } + public class MaabasConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1026153, 6178) // teleporter + }; - public override void OnRead() - { - System.AddObjective( new FindMaabusTombObjective() ); - } - } + public override object Message => 1060103; - public class MaabasConversation : QuestConversation - { - public override object Message => 1060103; + public override QuestItemInfo[] Info => m_Info; - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1026153, 6178 ) // teleporter - }; + public override void OnRead() + { + System.AddObjective(new FindCrystalCaveObjective()); + } + } - public override QuestItemInfo[] Info => m_Info; + public class HorusConversation : QuestConversation + { + public override object Message => 1060105; - public MaabasConversation() - { - } + public override void OnRead() + { + System.AddObjective(new FindMardothAboutVaultObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new FindCrystalCaveObjective() ); - } - } + public class MardothVaultConversation : QuestConversation + { + public override object Message => 1060107; - public class HorusConversation : QuestConversation - { - public override object Message => 1060105; + public override void OnRead() + { + System.AddObjective(new FindCityOfLightObjective()); + } + } - public HorusConversation() - { - } + public class VaultOfSecretsConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1023643, 8787) // spellbook + }; - public override void OnRead() - { - System.AddObjective( new FindMardothAboutVaultObjective() ); - } - } + public override object Message => 1060110; - public class MardothVaultConversation : QuestConversation - { - public override object Message => 1060107; + public override QuestItemInfo[] Info => m_Info; - public MardothVaultConversation() - { - } + public override void OnRead() + { + System.AddObjective(new FetchAbraxusScrollObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new FindCityOfLightObjective() ); - } - } + public class ReadAbraxusScrollConversation : QuestConversation + { + public override object Message => 1060114; - public class VaultOfSecretsConversation : QuestConversation - { - public override object Message => 1060110; + public override void OnRead() + { + System.AddObjective(new ReadAbraxusScrollObjective()); + } + } - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1023643, 8787 ) // spellbook - }; + public class SecondHorusConversation : QuestConversation + { + public override object Message => 1060118; - public override QuestItemInfo[] Info => m_Info; + public override void OnRead() + { + System.AddObjective(new FindCallingScrollObjective()); + } + } - public VaultOfSecretsConversation() - { - } + public class HealConversation : QuestConversation + { + public override object Message => 1061610; + } - public override void OnRead() - { - System.AddObjective( new FetchAbraxusScrollObjective() ); - } - } + public class HorusRewardConversation : QuestConversation + { + public override object Message => 1060717; - public class ReadAbraxusScrollConversation : QuestConversation - { - public override object Message => 1060114; + public override bool Logged => false; + } - public ReadAbraxusScrollConversation() - { - } + public class LostCallingScrollConversation : QuestConversation + { + private bool m_FromMardoth; - public override void OnRead() - { - System.AddObjective( new ReadAbraxusScrollObjective() ); - } - } + public LostCallingScrollConversation(bool fromMardoth) + { + m_FromMardoth = fromMardoth; + } - public class SecondHorusConversation : QuestConversation - { - public override object Message => 1060118; + // Serialization + public LostCallingScrollConversation() + { + } - public SecondHorusConversation() - { - } + public override object Message + { + get + { + if (m_FromMardoth) return 1062058; - public override void OnRead() - { - System.AddObjective( new FindCallingScrollObjective() ); - } - } + /* You have arrived at the well, but no longer have the scroll + * of calling. Use Mardoth's teleporter to return to the + * Crystal Cave and fetch another scroll from the box. + */ + return 1060129; + } + } - public class HealConversation : QuestConversation - { - public override object Message => 1061610; + public override bool Logged => false; - public HealConversation() - { - } - } + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public class HorusRewardConversation : QuestConversation - { - public override object Message => 1060717; + m_FromMardoth = reader.ReadBool(); + } - public override bool Logged => false; + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public HorusRewardConversation() - { - } - } + writer.Write(m_FromMardoth); + } + } - public class LostCallingScrollConversation : QuestConversation - { - private bool m_FromMardoth; + public class MardothKronusConversation : QuestConversation + { + public override object Message => 1060121; - public override object Message - { - get - { - if ( m_FromMardoth ) - { - /* You return without the scroll of Calling? I'm afraid that - * won't do. You must return to the Crystal Cave and fetch - * another scroll. Use the teleporter to the West of me to - * get there. Return here when you have the scroll. Do not - * fail me this time, young apprentice of evil. - */ - return 1062058; - } + public override void OnRead() + { + System.AddObjective(new FindWellOfTearsObjective()); + } + } - /* You have arrived at the well, but no longer have the scroll - * of calling. Use Mardoth's teleporter to return to the - * Crystal Cave and fetch another scroll from the box. - */ - return 1060129; - } - } + public class MardothEndConversation : QuestConversation + { + public override object Message => 1060133; - public override bool Logged => false; + public override void OnRead() + { + System.AddObjective(new FindBankObjective()); + } + } - public LostCallingScrollConversation( bool fromMardoth ) - { - m_FromMardoth = fromMardoth; - } + public class BankerConversation : QuestConversation + { + public override object Message => 1060137; - // Serialization - public LostCallingScrollConversation() - { - } + public override void OnRead() + { + System.Complete(); + } + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public class RadarConversation : QuestConversation + { + public override object Message => 1061692; - m_FromMardoth = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_FromMardoth ); - } - } - - public class MardothKronusConversation : QuestConversation - { - public override object Message => 1060121; - - public MardothKronusConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindWellOfTearsObjective() ); - } - } - - public class MardothEndConversation : QuestConversation - { - public override object Message => 1060133; - - public MardothEndConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindBankObjective() ); - } - } - - public class BankerConversation : QuestConversation - { - public override object Message => 1060137; - - public BankerConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } - - public class RadarConversation : QuestConversation - { - public override object Message => 1061692; - - public override bool Logged => false; - - public RadarConversation() - { - } - } -} + public override bool Logged => false; + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/DarkTidesQuest.cs b/Scripts/Engines/Quests/Dark Tides/DarkTidesQuest.cs index 565964bd1..a40936e2d 100644 --- a/Scripts/Engines/Quests/Dark Tides/DarkTidesQuest.cs +++ b/Scripts/Engines/Quests/Dark Tides/DarkTidesQuest.cs @@ -3,97 +3,96 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class DarkTidesQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( AcceptConversation ), - typeof( AnimateMaabusCorpseObjective ), - typeof( BankerConversation ), - typeof( CashBankCheckObjective ), - typeof( FetchAbraxusScrollObjective ), - typeof( FindBankObjective ), - typeof( FindCallingScrollObjective ), - typeof( FindCityOfLightObjective ), - typeof( FindCrystalCaveObjective ), - typeof( FindMaabusCorpseObjective ), - typeof( FindMaabusTombObjective ), - typeof( FindMardothAboutKronusObjective ), - typeof( FindMardothAboutVaultObjective ), - typeof( FindMardothEndObjective ), - typeof( FindVaultOfSecretsObjective ), - typeof( FindWellOfTearsObjective ), - typeof( HorusConversation ), - typeof( LostCallingScrollConversation ), - typeof( MaabasConversation ), - typeof( MardothEndConversation ), - typeof( MardothKronusConversation ), - typeof( MardothVaultConversation ), - typeof( RadarConversation ), - typeof( ReadAbraxusScrollConversation ), - typeof( ReadAbraxusScrollObjective ), - typeof( ReanimateMaabusConversation ), - typeof( RetrieveAbraxusScrollObjective ), - typeof( ReturnToCrystalCaveObjective ), - typeof( SecondHorusConversation ), - typeof( SpeakCavePasswordObjective ), - typeof( UseCallingScrollObjective ), - typeof( VaultOfSecretsConversation ), - typeof( FindHorusAboutRewardObjective ), - typeof( HealConversation ), - typeof( HorusRewardConversation ) - }; + public class DarkTidesQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(AcceptConversation), + typeof(AnimateMaabusCorpseObjective), + typeof(BankerConversation), + typeof(CashBankCheckObjective), + typeof(FetchAbraxusScrollObjective), + typeof(FindBankObjective), + typeof(FindCallingScrollObjective), + typeof(FindCityOfLightObjective), + typeof(FindCrystalCaveObjective), + typeof(FindMaabusCorpseObjective), + typeof(FindMaabusTombObjective), + typeof(FindMardothAboutKronusObjective), + typeof(FindMardothAboutVaultObjective), + typeof(FindMardothEndObjective), + typeof(FindVaultOfSecretsObjective), + typeof(FindWellOfTearsObjective), + typeof(HorusConversation), + typeof(LostCallingScrollConversation), + typeof(MaabasConversation), + typeof(MardothEndConversation), + typeof(MardothKronusConversation), + typeof(MardothVaultConversation), + typeof(RadarConversation), + typeof(ReadAbraxusScrollConversation), + typeof(ReadAbraxusScrollObjective), + typeof(ReanimateMaabusConversation), + typeof(RetrieveAbraxusScrollObjective), + typeof(ReturnToCrystalCaveObjective), + typeof(SecondHorusConversation), + typeof(SpeakCavePasswordObjective), + typeof(UseCallingScrollObjective), + typeof(VaultOfSecretsConversation), + typeof(FindHorusAboutRewardObjective), + typeof(HealConversation), + typeof(HorusRewardConversation) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public DarkTidesQuest(PlayerMobile from) : base(from) + { + } - public override object Name => 1060095; + // Serialization + public DarkTidesQuest() + { + } - public override object OfferMessage => 1060094; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override TimeSpan RestartDelay => TimeSpan.MaxValue; - public override bool IsTutorial => true; + public override object Name => 1060095; - public override int Picture => 0x15B5; + public override object OfferMessage => 1060094; - public DarkTidesQuest( PlayerMobile from ) : base( from ) - { - } + public override TimeSpan RestartDelay => TimeSpan.MaxValue; + public override bool IsTutorial => true; - // Serialization - public DarkTidesQuest() - { - } + public override int Picture => 0x15B5; - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } + AddConversation(new AcceptConversation()); + } - public override bool IgnoreYoungProtection( Mobile from ) - { - if ( from is SummonedPaladin ) - return true; + public override bool IgnoreYoungProtection(Mobile from) + { + if (from is SummonedPaladin) + return true; - return base.IgnoreYoungProtection( from ); - } + return base.IgnoreYoungProtection(from); + } - public static bool HasLostCallingScroll( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostCallingScroll(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is DarkTidesQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FindMardothAboutKronusObjective ) ) || qs.IsObjectiveInProgress( typeof( FindWellOfTearsObjective ) ) || qs.IsObjectiveInProgress( typeof( UseCallingScrollObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( KronusScroll ) ) == null ); - } - } + if (qs is DarkTidesQuest) + if (qs.IsObjectiveInProgress(typeof(FindMardothAboutKronusObjective)) || + qs.IsObjectiveInProgress(typeof(FindWellOfTearsObjective)) || + qs.IsObjectiveInProgress(typeof(UseCallingScrollObjective))) + return from.Backpack?.FindItemByType(typeof(KronusScroll)) == null; - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/CrystalCaveBarrier.cs b/Scripts/Engines/Quests/Dark Tides/Items/CrystalCaveBarrier.cs index 29b3b5a76..3e86329d2 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/CrystalCaveBarrier.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/CrystalCaveBarrier.cs @@ -2,64 +2,66 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class CrystalCaveBarrier : Item - { - [Constructible] - public CrystalCaveBarrier() : base( 0x3967 ) - { - Movable = false; - } + public class CrystalCaveBarrier : Item + { + [Constructible] + public CrystalCaveBarrier() : base(0x3967) + { + Movable = false; + } - public override bool OnMoveOver( Mobile m ) - { - if ( m.AccessLevel > AccessLevel.Player ) - return true; + public CrystalCaveBarrier(Serial serial) : base(serial) + { + } - bool sendMessage = m.Player; + public override bool OnMoveOver(Mobile m) + { + if (m.AccessLevel > AccessLevel.Player) + return true; - if ( m is BaseCreature ) - m = ((BaseCreature)m).ControlMaster; + bool sendMessage = m.Player; - if ( m is PlayerMobile pm ) - { - QuestSystem qs = pm.Quest; + if (m is BaseCreature) + m = ((BaseCreature)m).ControlMaster; - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SpeakCavePasswordObjective ) ); + if (m is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - if ( obj != null && obj.Completed ) - { - if ( sendMessage ) - m.SendLocalizedMessage( 1060648 ); // With Horus' permission, you are able to pass through the barrier. + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SpeakCavePasswordObjective)); - return true; - } - } - } + if (obj != null && obj.Completed) + { + if (sendMessage) + m.SendLocalizedMessage( + 1060648); // With Horus' permission, you are able to pass through the barrier. - if ( sendMessage ) - m.SendLocalizedMessage( 1060649, "", 0x66D ); // Without the permission of the guardian Horus, the magic of the barrier prevents your passage. + return true; + } + } + } - return false; - } + if (sendMessage) + m.SendLocalizedMessage(1060649, "", + 0x66D); // Without the permission of the guardian Horus, the magic of the barrier prevents your passage. - public CrystalCaveBarrier( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesHorn.cs b/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesHorn.cs index 054fcd406..f64fafdd1 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesHorn.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesHorn.cs @@ -2,36 +2,36 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class DarkTidesHorn : HornOfRetreat - { - public override bool ValidateUse( Mobile from ) - { - return ( from is PlayerMobile pm && pm.Quest is DarkTidesQuest ); - } + public class DarkTidesHorn : HornOfRetreat + { + [Constructible] + public DarkTidesHorn() + { + DestLoc = new Point3D(2103, 1319, -68); + DestMap = Map.Malas; + } - [Constructible] - public DarkTidesHorn() - { - DestLoc = new Point3D( 2103, 1319, -68 ); - DestMap = Map.Malas; - } + public DarkTidesHorn(Serial serial) : base(serial) + { + } - public DarkTidesHorn( Serial serial ) : base( serial ) - { - } + public override bool ValidateUse(Mobile from) + { + return from is PlayerMobile pm && pm.Quest is DarkTidesQuest; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesTeleporter.cs b/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesTeleporter.cs index 4ba3a49a6..cad774722 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesTeleporter.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/DarkTidesTeleporter.cs @@ -2,72 +2,75 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class DarkTidesTeleporter : DynamicTeleporter - { - [Constructible] - public DarkTidesTeleporter() - { - } + public class DarkTidesTeleporter : DynamicTeleporter + { + [Constructible] + public DarkTidesTeleporter() + { + } - public override bool GetDestination( PlayerMobile player, ref Point3D loc, ref Map map ) - { - QuestSystem qs = player.Quest; + public DarkTidesTeleporter(Serial serial) : base(serial) + { + } - if ( qs is DarkTidesQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FindMaabusTombObjective ) ) ) - { - loc = new Point3D( 2038, 1263, -90 ); - map = Map.Malas; - qs.AddConversation( new RadarConversation() ); - return true; - } + public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map) + { + QuestSystem qs = player.Quest; - if ( qs.IsObjectiveInProgress( typeof( FindCrystalCaveObjective ) ) ) - { - loc = new Point3D( 1194, 521, -90 ); - map = Map.Malas; - return true; - } - if ( qs.IsObjectiveInProgress( typeof( FindCityOfLightObjective ) ) ) - { - loc = new Point3D( 1091, 519, -90 ); - map = Map.Malas; - return true; - } - if ( qs.IsObjectiveInProgress( typeof( ReturnToCrystalCaveObjective ) ) ) - { - loc = new Point3D( 1194, 521, -90 ); - map = Map.Malas; - return true; - } - if ( DarkTidesQuest.HasLostCallingScroll( player ) ) - { - loc = new Point3D( 1194, 521, -90 ); - map = Map.Malas; - return true; - } - } + if (qs is DarkTidesQuest) + { + if (qs.IsObjectiveInProgress(typeof(FindMaabusTombObjective))) + { + loc = new Point3D(2038, 1263, -90); + map = Map.Malas; + qs.AddConversation(new RadarConversation()); + return true; + } - return false; - } + if (qs.IsObjectiveInProgress(typeof(FindCrystalCaveObjective))) + { + loc = new Point3D(1194, 521, -90); + map = Map.Malas; + return true; + } - public DarkTidesTeleporter( Serial serial ) : base( serial ) - { - } + if (qs.IsObjectiveInProgress(typeof(FindCityOfLightObjective))) + { + loc = new Point3D(1091, 519, -90); + map = Map.Malas; + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (qs.IsObjectiveInProgress(typeof(ReturnToCrystalCaveObjective))) + { + loc = new Point3D(1194, 521, -90); + map = Map.Malas; + return true; + } - writer.Write( (int) 0 ); // version - } + if (DarkTidesQuest.HasLostCallingScroll(player)) + { + loc = new Point3D(1194, 521, -90); + map = Map.Malas; + return true; + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return false; + } - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/KronusScroll.cs b/Scripts/Engines/Quests/Dark Tides/Items/KronusScroll.cs index 3f6aceacb..134a41119 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/KronusScroll.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/KronusScroll.cs @@ -1,159 +1,166 @@ using System; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; using Server.Network; namespace Server.Engines.Quests.Necro { - public class KronusScroll : QuestItem - { - public override int LabelNumber => 1060149; // Calling of Kronus + public class KronusScroll : QuestItem + { + private static readonly Rectangle2D m_WellOfTearsArea = new Rectangle2D(2080, 1346, 10, 10); + private static readonly Map m_WellOfTearsMap = Map.Malas; - [Constructible] - public KronusScroll() : base( 0x227A ) - { - Weight = 1.0; - Hue = 0x44E; - } + [Constructible] + public KronusScroll() : base(0x227A) + { + Weight = 1.0; + Hue = 0x44E; + } - public KronusScroll( Serial serial ) : base( serial ) - { - } + public KronusScroll(Serial serial) : base(serial) + { + } - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is DarkTidesQuest); + public override int LabelNumber => 1060149; // Calling of Kronus - /*return !( qs.IsObjectiveInProgress( typeof( FindCallingScrollObjective ) ) - || qs.IsObjectiveInProgress( typeof( FindMardothAboutKronusObjective ) ) - || qs.IsObjectiveInProgress( typeof( FindWellOfTearsObjective ) ) - || qs.IsObjectiveInProgress( typeof( UseCallingScrollObjective ) ) );*/ - } + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is DarkTidesQuest); - private static readonly Rectangle2D m_WellOfTearsArea = new Rectangle2D( 2080, 1346, 10, 10 ); - private static readonly Map m_WellOfTearsMap = Map.Malas; + /*return !( qs.IsObjectiveInProgress( typeof( FindCallingScrollObjective ) ) + || qs.IsObjectiveInProgress( typeof( FindMardothAboutKronusObjective ) ) + || qs.IsObjectiveInProgress( typeof( FindWellOfTearsObjective ) ) + || qs.IsObjectiveInProgress( typeof( UseCallingScrollObjective ) ) );*/ + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from)) + return; - if ( from is PlayerMobile pm ) - { - QuestSystem qs = pm.Quest; + if (from is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - if ( qs is DarkTidesQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FindMardothAboutKronusObjective ) ) ) - { - pm.SendLocalizedMessage( 1060151, "", 0x41 ); // You read the scroll, but decide against performing the calling until you are instructed to do so by Mardoth. - } - else if ( qs.IsObjectiveInProgress( typeof( FindWellOfTearsObjective ) ) ) - { - pm.SendLocalizedMessage( 1060152, "", 0x41 ); // You must be at the Well of Tears in the city of Necromancers to use this scroll. - } - else if ( qs.IsObjectiveInProgress( typeof( UseCallingScrollObjective ) ) ) - { - if ( pm.Map == m_WellOfTearsMap && m_WellOfTearsArea.Contains( pm ) ) - { - QuestObjective obj = qs.FindObjective( typeof( UseCallingScrollObjective ) ); + if (qs is DarkTidesQuest) + { + if (qs.IsObjectiveInProgress(typeof(FindMardothAboutKronusObjective))) + { + pm.SendLocalizedMessage(1060151, "", + 0x41); // You read the scroll, but decide against performing the calling until you are instructed to do so by Mardoth. + } + else if (qs.IsObjectiveInProgress(typeof(FindWellOfTearsObjective))) + { + pm.SendLocalizedMessage(1060152, "", + 0x41); // You must be at the Well of Tears in the city of Necromancers to use this scroll. + } + else if (qs.IsObjectiveInProgress(typeof(UseCallingScrollObjective))) + { + if (pm.Map == m_WellOfTearsMap && m_WellOfTearsArea.Contains(pm)) + { + QuestObjective obj = qs.FindObjective(typeof(UseCallingScrollObjective)); - if ( obj != null && !obj.Completed ) - obj.Complete(); + if (obj != null && !obj.Completed) + obj.Complete(); - Delete(); - new CallingTimer( pm ).Start(); - } - else - { - pm.SendLocalizedMessage( 1060152, "", 0x41 ); // You must be at the Well of Tears in the city of Necromancers to use this scroll. - } - } - else - { - pm.SendLocalizedMessage( 1060150, "", 0x41 ); // A strange terror grips your heart as you attempt to read the scroll. You decide it would be a bad idea to read it out loud. - } - } - } - } + Delete(); + new CallingTimer(pm).Start(); + } + else + { + pm.SendLocalizedMessage(1060152, "", + 0x41); // You must be at the Well of Tears in the city of Necromancers to use this scroll. + } + } + else + { + pm.SendLocalizedMessage(1060150, "", + 0x41); // A strange terror grips your heart as you attempt to read the scroll. You decide it would be a bad idea to read it out loud. + } + } + } + } - private class CallingTimer : Timer - { - private PlayerMobile m_Player; - private int m_Step; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public CallingTimer( PlayerMobile player ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ), 6 ) - { - Priority = TimerPriority.TwentyFiveMS; + writer.Write(0); // version + } - m_Player = player; - m_Step = 0; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - protected override void OnTick() - { - if ( m_Player.Deleted ) - { - Stop(); - return; - } + int version = reader.ReadInt(); + } - if ( !m_Player.Mounted ) - m_Player.Animate( Utility.RandomBool() ? 16 : 17, 7, 1, true, false, 0 ); + private class CallingTimer : Timer + { + private PlayerMobile m_Player; + private int m_Step; - if ( m_Step == 4 ) - { - int baseX = m_WellOfTearsArea.X; - int baseY = m_WellOfTearsArea.Y; - int width = m_WellOfTearsArea.Width; - int height = m_WellOfTearsArea.Height; - Map map = m_WellOfTearsMap; + public CallingTimer(PlayerMobile player) : base(TimeSpan.Zero, TimeSpan.FromSeconds(1.0), 6) + { + Priority = TimerPriority.TwentyFiveMS; - Effects.SendLocationParticles( EffectItem.Create( m_Player.Location, m_Player.Map, TimeSpan.FromSeconds( 1.0 ) ), 0, 0, 0, 0x13C4 ); - Effects.PlaySound( m_Player.Location, m_Player.Map, 0x243 ); + m_Player = player; + m_Step = 0; + } - for ( int i = 0; i < 15; i++ ) - { - int x = baseX + Utility.Random( width ); - int y = baseY + Utility.Random( height ); - int z = map.GetAverageZ( x, y ); + protected override void OnTick() + { + if (m_Player.Deleted) + { + Stop(); + return; + } - Point3D from = new Point3D( x, y, z + Utility.RandomMinMax( 5, 20 ) ); - Point3D to = new Point3D( x, y, z ); + if (!m_Player.Mounted) + m_Player.Animate(Utility.RandomBool() ? 16 : 17, 7, 1, true, false, 0); - int hue = Utility.RandomList( 0x481, 0x482, 0x489, 0x497, 0x66D ); + if (m_Step == 4) + { + int baseX = m_WellOfTearsArea.X; + int baseY = m_WellOfTearsArea.Y; + int width = m_WellOfTearsArea.Width; + int height = m_WellOfTearsArea.Height; + Map map = m_WellOfTearsMap; - Effects.SendPacket( from, map, new HuedEffect( EffectType.Moving, Serial.Zero, Serial.Zero, 0x36D4, from, to, 0, 0, false, true, hue, 0 ) ); - } - } + Effects.SendLocationParticles( + EffectItem.Create(m_Player.Location, m_Player.Map, TimeSpan.FromSeconds(1.0)), 0, 0, 0, 0x13C4); + Effects.PlaySound(m_Player.Location, m_Player.Map, 0x243); - if ( m_Step < 5 ) - { - m_Player.Frozen = true; - } - else // Cast completed - { - m_Player.Frozen = false; + for (int i = 0; i < 15; i++) + { + int x = baseX + Utility.Random(width); + int y = baseY + Utility.Random(height); + int z = map.GetAverageZ(x, y); - SummonedPaladin.BeginSummon( m_Player ); - } + Point3D from = new Point3D(x, y, z + Utility.RandomMinMax(5, 20)); + Point3D to = new Point3D(x, y, z); - m_Step++; - } - } + int hue = Utility.RandomList(0x481, 0x482, 0x489, 0x497, 0x66D); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Effects.SendPacket(from, map, + new HuedEffect(EffectType.Moving, Serial.Zero, Serial.Zero, 0x36D4, from, to, 0, 0, false, true, + hue, 0)); + } + } - writer.Write( (int) 0 ); // version - } + if (m_Step < 5) + { + m_Player.Frozen = true; + } + else // Cast completed + { + m_Player.Frozen = false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + SummonedPaladin.BeginSummon(m_Player); + } - int version = reader.ReadInt(); - } - } -} + m_Step++; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/KronusScrollBox.cs b/Scripts/Engines/Quests/Dark Tides/Items/KronusScrollBox.cs index 6dbca79c9..56d464e7f 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/KronusScrollBox.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/KronusScrollBox.cs @@ -3,71 +3,72 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class KronusScrollBox : MetalBox - { - [Constructible] - public KronusScrollBox() - { - ItemID = 0xE80; - Movable = false; + public class KronusScrollBox : MetalBox + { + [Constructible] + public KronusScrollBox() + { + ItemID = 0xE80; + Movable = false; - for ( int i = 0; i < 40; i++ ) - { - Item scroll = Loot.RandomScroll( 0, 15, SpellbookType.Necromancer ); - scroll.Movable = false; - DropItem( scroll ); - } - } + for (int i = 0; i < 40; i++) + { + Item scroll = Loot.RandomScroll(0, 15, SpellbookType.Necromancer); + scroll.Movable = false; + DropItem(scroll); + } + } - public KronusScrollBox( Serial serial ) : base( serial ) - { - } + public KronusScrollBox(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( from is PlayerMobile pm && pm.InRange( GetWorldLocation(), 2 ) ) - { - QuestSystem qs = pm.Quest; + public override void OnDoubleClick(Mobile from) + { + if (from is PlayerMobile pm && pm.InRange(GetWorldLocation(), 2)) + { + QuestSystem qs = pm.Quest; - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( FindCallingScrollObjective ) ); + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FindCallingScrollObjective)); - if ( (obj != null && !obj.Completed) || DarkTidesQuest.HasLostCallingScroll( from ) ) - { - Item scroll = new KronusScroll(); + if (obj != null && !obj.Completed || DarkTidesQuest.HasLostCallingScroll(from)) + { + Item scroll = new KronusScroll(); - if ( pm.PlaceInBackpack( scroll ) ) - { - pm.SendLocalizedMessage( 1060120, "", 0x41 ); // You rummage through the scrolls until you find the Scroll of Calling. You quickly put it in your pack. + if (pm.PlaceInBackpack(scroll)) + { + pm.SendLocalizedMessage(1060120, "", + 0x41); // You rummage through the scrolls until you find the Scroll of Calling. You quickly put it in your pack. - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - else - { - pm.SendLocalizedMessage( 1060148, "", 0x41 ); // You were unable to take the scroll. - scroll.Delete(); - } - } - } - } + if (obj != null && !obj.Completed) + obj.Complete(); + } + else + { + pm.SendLocalizedMessage(1060148, "", 0x41); // You were unable to take the scroll. + scroll.Delete(); + } + } + } + } - base.OnDoubleClick( from ); - } + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/MaabusCoffin.cs b/Scripts/Engines/Quests/Dark Tides/Items/MaabusCoffin.cs index d07810b87..fc1b34f6b 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/MaabusCoffin.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/MaabusCoffin.cs @@ -3,152 +3,156 @@ using Server.Items; namespace Server.Engines.Quests.Necro { - public class MaabusCoffin : BaseAddon - { - [CommandProperty( AccessLevel.GameMaster )] - public Maabus Maabus { get; private set; } + public class MaabusCoffin : BaseAddon + { + [Constructible] + public MaabusCoffin() + { + AddComponent(new MaabusCoffinComponent(0x1C2B, 0x1C2B), -1, -1, 0); - [CommandProperty( AccessLevel.GameMaster )] - public Point3D SpawnLocation { get; set; } + AddComponent(new MaabusCoffinComponent(0x1D16, 0x1C2C), 0, -1, 0); + AddComponent(new MaabusCoffinComponent(0x1D17, 0x1C2D), 1, -1, 0); + AddComponent(new MaabusCoffinComponent(0x1D51, 0x1C2E), 2, -1, 0); - [Constructible] - public MaabusCoffin() - { - AddComponent( new MaabusCoffinComponent( 0x1C2B, 0x1C2B ), -1, -1, 0 ); + AddComponent(new MaabusCoffinComponent(0x1D4E, 0x1C2A), 0, 0, 0); + AddComponent(new MaabusCoffinComponent(0x1D4D, 0x1C29), 1, 0, 0); + AddComponent(new MaabusCoffinComponent(0x1D4C, 0x1C28), 2, 0, 0); + } - AddComponent( new MaabusCoffinComponent( 0x1D16, 0x1C2C ), 0, -1, 0 ); - AddComponent( new MaabusCoffinComponent( 0x1D17, 0x1C2D ), 1, -1, 0 ); - AddComponent( new MaabusCoffinComponent( 0x1D51, 0x1C2E ), 2, -1, 0 ); + public MaabusCoffin(Serial serial) : base(serial) + { + } - AddComponent( new MaabusCoffinComponent( 0x1D4E, 0x1C2A ), 0, 0, 0 ); - AddComponent( new MaabusCoffinComponent( 0x1D4D, 0x1C29 ), 1, 0, 0 ); - AddComponent( new MaabusCoffinComponent( 0x1D4C, 0x1C28 ), 2, 0, 0 ); - } + [CommandProperty(AccessLevel.GameMaster)] + public Maabus Maabus{ get; private set; } - public void Awake( Mobile caller ) - { - if ( Maabus != null || SpawnLocation == Point3D.Zero ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D SpawnLocation{ get; set; } - foreach ( MaabusCoffinComponent c in Components ) - c.TurnToEmpty(); + public void Awake(Mobile caller) + { + if (Maabus != null || SpawnLocation == Point3D.Zero) + return; - Maabus = new Maabus(); + foreach (MaabusCoffinComponent c in Components) + c.TurnToEmpty(); - Maabus.Location = SpawnLocation; - Maabus.Map = Map; + Maabus = new Maabus(); - Maabus.Direction = Maabus.GetDirectionTo( caller ); + Maabus.Location = SpawnLocation; + Maabus.Map = Map; - Timer.DelayCall( TimeSpan.FromSeconds( 7.5 ), BeginSleep ); - } + Maabus.Direction = Maabus.GetDirectionTo(caller); - public void BeginSleep() - { - if ( Maabus == null ) - return; + Timer.DelayCall(TimeSpan.FromSeconds(7.5), BeginSleep); + } - Effects.PlaySound( Maabus.Location, Maabus.Map, 0x48E ); + public void BeginSleep() + { + if (Maabus == null) + return; - Timer.DelayCall( TimeSpan.FromSeconds( 2.5 ), Sleep ); - } + Effects.PlaySound(Maabus.Location, Maabus.Map, 0x48E); - public void Sleep() - { - if ( Maabus == null ) - return; + Timer.DelayCall(TimeSpan.FromSeconds(2.5), Sleep); + } - Effects.SendLocationParticles( EffectItem.Create( Maabus.Location, Maabus.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 0x7E7 ); - Effects.PlaySound( Maabus.Location, Maabus.Map, 0x1FE ); + public void Sleep() + { + if (Maabus == null) + return; - Maabus.Delete(); - Maabus = null; + Effects.SendLocationParticles(EffectItem.Create(Maabus.Location, Maabus.Map, EffectItem.DefaultDuration), 0x3728, + 10, 10, 0x7E7); + Effects.PlaySound(Maabus.Location, Maabus.Map, 0x1FE); - foreach ( MaabusCoffinComponent c in Components ) - c.TurnToFull(); - } + Maabus.Delete(); + Maabus = null; - public MaabusCoffin( Serial serial ) : base( serial ) - { - } + foreach (MaabusCoffinComponent c in Components) + c.TurnToFull(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (Mobile) Maabus ); - writer.Write( (Point3D) SpawnLocation ); - } + writer.Write(Maabus); + writer.Write(SpawnLocation); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Maabus = reader.ReadMobile() as Maabus; - SpawnLocation = reader.ReadPoint3D(); + Maabus = reader.ReadMobile() as Maabus; + SpawnLocation = reader.ReadPoint3D(); - Sleep(); - } - } + Sleep(); + } + } - public class MaabusCoffinComponent : AddonComponent - { - private int m_FullItemID; - private int m_EmptyItemID; + public class MaabusCoffinComponent : AddonComponent + { + private int m_EmptyItemID; + private int m_FullItemID; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D SpawnLocation - { - get => Addon is MaabusCoffin coffin ? coffin.SpawnLocation : Point3D.Zero; - set { if ( Addon is MaabusCoffin coffin ) coffin.SpawnLocation = value; } - } + public MaabusCoffinComponent(int itemID) : this(itemID, itemID) + { + } - public MaabusCoffinComponent( int itemID ) : this( itemID, itemID ) - { - } + public MaabusCoffinComponent(int fullItemID, int emptyItemID) : base(fullItemID) + { + m_FullItemID = fullItemID; + m_EmptyItemID = emptyItemID; + } - public MaabusCoffinComponent( int fullItemID, int emptyItemID ) : base( fullItemID ) - { - m_FullItemID = fullItemID; - m_EmptyItemID = emptyItemID; - } + public MaabusCoffinComponent(Serial serial) : base(serial) + { + } - public void TurnToEmpty() - { - ItemID = m_EmptyItemID; - } + [CommandProperty(AccessLevel.GameMaster)] + public Point3D SpawnLocation + { + get => Addon is MaabusCoffin coffin ? coffin.SpawnLocation : Point3D.Zero; + set + { + if (Addon is MaabusCoffin coffin) coffin.SpawnLocation = value; + } + } - public void TurnToFull() - { - ItemID = m_FullItemID; - } + public void TurnToEmpty() + { + ItemID = m_EmptyItemID; + } - public MaabusCoffinComponent( Serial serial ) : base( serial ) - { - } + public void TurnToFull() + { + ItemID = m_FullItemID; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_FullItemID ); - writer.Write( (int) m_EmptyItemID ); - } + writer.Write(m_FullItemID); + writer.Write(m_EmptyItemID); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_FullItemID = reader.ReadInt(); - m_EmptyItemID = reader.ReadInt(); - } - } -} + m_FullItemID = reader.ReadInt(); + m_EmptyItemID = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/ScrollOfAbraxus.cs b/Scripts/Engines/Quests/Dark Tides/Items/ScrollOfAbraxus.cs index 5c8ff927c..23c90491c 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/ScrollOfAbraxus.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/ScrollOfAbraxus.cs @@ -3,131 +3,131 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class ScrollOfAbraxus : QuestItem - { - public override int LabelNumber => 1028827; // Scroll of Abraxus + public class ScrollOfAbraxus : QuestItem + { + [Constructible] + public ScrollOfAbraxus() : base(0x227B) + { + Weight = 1.0; + } - [Constructible] - public ScrollOfAbraxus() : base( 0x227B ) - { - Weight = 1.0; - } + public ScrollOfAbraxus(Serial serial) : base(serial) + { + } - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is DarkTidesQuest); + public override int LabelNumber => 1028827; // Scroll of Abraxus - //return !( qs.IsObjectiveInProgress( typeof( RetrieveAbraxusScrollObjective ) ) || qs.IsObjectiveInProgress( typeof( ReadAbraxusScrollObjective ) ) ); - } + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is DarkTidesQuest); - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); + //return !( qs.IsObjectiveInProgress( typeof( RetrieveAbraxusScrollObjective ) ) || qs.IsObjectiveInProgress( typeof( ReadAbraxusScrollObjective ) ) ); + } - if ( RootParent is PlayerMobile pm ) - { - QuestSystem qs = pm.Quest; + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( RetrieveAbraxusScrollObjective ) ); + if (RootParent is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - } - } + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(RetrieveAbraxusScrollObjective)); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.SendGump( new ScrollOfAbraxusGump() ); + if (obj != null && !obj.Completed) + obj.Complete(); + } + } + } - if ( from is PlayerMobile pm ) - { - QuestSystem qs = pm.Quest; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.SendGump(new ScrollOfAbraxusGump()); - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( ReadAbraxusScrollObjective ) ); + if (from is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(ReadAbraxusScrollObjective)); - public ScrollOfAbraxus( Serial serial ) : base( serial ) - { - } + if (obj != null && !obj.Completed) + obj.Complete(); + } + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class ScrollOfAbraxusGump : Gump - { - public ScrollOfAbraxusGump() : base( 150, 50 ) - { - AddPage( 0 ); + public class ScrollOfAbraxusGump : Gump + { + public ScrollOfAbraxusGump() : base(150, 50) + { + AddPage(0); - AddImage( 0, 0, 1228 ); - AddImage( 340, 255, 9005 ); + AddImage(0, 0, 1228); + AddImage(340, 255, 9005); - /* Security at the Crystal Cave

- * - * We have taken great measuresto ensure the safety of the - * Scroll of Calling, which we have so valiantly taken from - * the Necromancer Maabus during the battle of the wood - * nearly 200 years ago.

- * - * The scroll must never fall into the hands of the - * Necromancers again, lest they use it to summon the ancient - * daemon Kronus. The scroll of calling is a necessity in the - * series of dark rites the Necromancers must perform to once again - * re-awaken Kronus.

- * - * Should Kronus ever rise again, the days of the Paladins, and - * indeed humanity as we know it will be numbered.

- * - * For this reason, we have posted the honorable Horus, former - * General of the Northern Legions to guard the entrance of the - * Crystal Cave where we keep the Scroll of Calling. Horus was - * infused with magical life from the tree Urywen during his last - * battle. The power gave him eternal life, but it also, - * unfortunately, took his eye sight.

- * - * Since Horus cannot see those he admits to the Crystal Cave, - * he will only allow those that know the secret password to enter. - * Speak the following word to Horus and he shall grant you passage - * to the Crystal Cave:

- * - * Urywen

- * - * Do not speak this password anywhere except when seeking passage - * into the Crystal Cave, as our adversaries are lurking in the - * shadows � they are everywhere.

Go with the light, friend.

- * - * - Frater Melkeer - */ - AddHtmlLocalized( 25, 36, 350, 210, 1060116, 1, false, true ); - } - } -} + /* Security at the Crystal Cave

+ * + * We have taken great measuresto ensure the safety of the + * Scroll of Calling, which we have so valiantly taken from + * the Necromancer Maabus during the battle of the wood + * nearly 200 years ago.

+ * + * The scroll must never fall into the hands of the + * Necromancers again, lest they use it to summon the ancient + * daemon Kronus. The scroll of calling is a necessity in the + * series of dark rites the Necromancers must perform to once again + * re-awaken Kronus.

+ * + * Should Kronus ever rise again, the days of the Paladins, and + * indeed humanity as we know it will be numbered.

+ * + * For this reason, we have posted the honorable Horus, former + * General of the Northern Legions to guard the entrance of the + * Crystal Cave where we keep the Scroll of Calling. Horus was + * infused with magical life from the tree Urywen during his last + * battle. The power gave him eternal life, but it also, + * unfortunately, took his eye sight.

+ * + * Since Horus cannot see those he admits to the Crystal Cave, + * he will only allow those that know the secret password to enter. + * Speak the following word to Horus and he shall grant you passage + * to the Crystal Cave:

+ * + * Urywen

+ * + * Do not speak this password anywhere except when seeking passage + * into the Crystal Cave, as our adversaries are lurking in the + * shadows � they are everywhere.

Go with the light, friend.

+ * + * - Frater Melkeer + */ + AddHtmlLocalized(25, 36, 350, 210, 1060116, 1, false, true); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Items/VaultOfSecretsBarrier.cs b/Scripts/Engines/Quests/Dark Tides/Items/VaultOfSecretsBarrier.cs index 088bcb354..f4ad5be85 100644 --- a/Scripts/Engines/Quests/Dark Tides/Items/VaultOfSecretsBarrier.cs +++ b/Scripts/Engines/Quests/Dark Tides/Items/VaultOfSecretsBarrier.cs @@ -2,45 +2,45 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class VaultOfSecretsBarrier : Item - { - [Constructible] - public VaultOfSecretsBarrier() : base( 0x49E ) - { - Movable = false; - Visible = false; - } + public class VaultOfSecretsBarrier : Item + { + [Constructible] + public VaultOfSecretsBarrier() : base(0x49E) + { + Movable = false; + Visible = false; + } - public override bool OnMoveOver( Mobile m ) - { - if ( m.AccessLevel > AccessLevel.Player ) - return true; + public VaultOfSecretsBarrier(Serial serial) : base(serial) + { + } - if ( m is PlayerMobile pm && pm.Profession == 4 ) - { - m.SendLocalizedMessage( 1060188, "", 0x24 ); // The wicked may not enter! - return false; - } + public override bool OnMoveOver(Mobile m) + { + if (m.AccessLevel > AccessLevel.Player) + return true; - return base.OnMoveOver( m ); - } + if (m is PlayerMobile pm && pm.Profession == 4) + { + m.SendLocalizedMessage(1060188, "", 0x24); // The wicked may not enter! + return false; + } - public VaultOfSecretsBarrier( Serial serial ) : base( serial ) - { - } + return base.OnMoveOver(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Mobiles/Horus.cs b/Scripts/Engines/Quests/Dark Tides/Mobiles/Horus.cs index 553df5b01..e2e3ad9a6 100644 --- a/Scripts/Engines/Quests/Dark Tides/Mobiles/Horus.cs +++ b/Scripts/Engines/Quests/Dark Tides/Mobiles/Horus.cs @@ -1,190 +1,191 @@ using System.Collections.Generic; +using Server.ContextMenus; using Server.Items; using Server.Mobiles; using Server.Network; -using Server.ContextMenus; namespace Server.Engines.Quests.Necro { - public class Horus : BaseQuester - { - public override string DefaultName => "Horus"; + public class Horus : BaseQuester + { + [Constructible] + public Horus() : base("the Guardian") + { + } - [Constructible] - public Horus() : base( "the Guardian" ) - { - } + public Horus(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Horus"; - Hue = 0x83F3; - Body = 0x190; - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override void InitOutfit() - { - AddItem( SetHue( new PlateLegs(), 0x849 ) ); - AddItem( SetHue( new PlateChest(), 0x849 ) ); - AddItem( SetHue( new PlateArms(), 0x849 ) ); - AddItem( SetHue( new PlateGloves(), 0x849 ) ); - AddItem( SetHue( new PlateGorget(), 0x849 ) ); + Hue = 0x83F3; + Body = 0x190; + } - AddItem( SetHue( new Bardiche(), 0x482 ) ); + public override void InitOutfit() + { + AddItem(SetHue(new PlateLegs(), 0x849)); + AddItem(SetHue(new PlateChest(), 0x849)); + AddItem(SetHue(new PlateArms(), 0x849)); + AddItem(SetHue(new PlateGloves(), 0x849)); + AddItem(SetHue(new PlateGorget(), 0x849)); - AddItem( SetHue( new Boots(), 0x001 ) ); - AddItem( SetHue( new Cloak(), 0x482 ) ); + AddItem(SetHue(new Bardiche(), 0x482)); - Utility.AssignRandomHair( this, false ); - Utility.AssignRandomFacialHair( this, false ); - } + AddItem(SetHue(new Boots(), 0x001)); + AddItem(SetHue(new Cloak(), 0x482)); - public override int GetAutoTalkRange( PlayerMobile m ) - { - return 3; - } + Utility.AssignRandomHair(this, false); + Utility.AssignRandomFacialHair(this, false); + } - public override bool CanTalkTo( PlayerMobile to ) - { - QuestSystem qs = to.Quest; + public override int GetAutoTalkRange(PlayerMobile m) + { + return 3; + } - return ( qs is DarkTidesQuest && qs.IsObjectiveInProgress( typeof( FindCrystalCaveObjective ) ) ); - } + public override bool CanTalkTo(PlayerMobile to) + { + QuestSystem qs = to.Quest; - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + return qs is DarkTidesQuest && qs.IsObjectiveInProgress(typeof(FindCrystalCaveObjective)); + } - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( FindCrystalCaveObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - } + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FindCrystalCaveObjective)); - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + if (obj != null && !obj.Completed) + obj.Complete(); + } + } - if ( InRange( m.Location, 2 ) && !InRange( oldLocation, 2 ) && m is PlayerMobile pm ) - { - QuestSystem qs = pm.Quest; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( ReturnToCrystalCaveObjective ) ); + if (InRange(m.Location, 2) && !InRange(oldLocation, 2) && m is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - if ( obj != null && !obj.Completed ) - obj.Complete(); - else - { - obj = qs.FindObjective( typeof( FindHorusAboutRewardObjective ) ); + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(ReturnToCrystalCaveObjective)); - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else + { + obj = qs.FindObjective(typeof(FindHorusAboutRewardObjective)); - cont.DropItem( new Gold( 500 ) ); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - BaseJewel jewel = new GoldBracelet(); - if ( Core.AOS ) - BaseRunicTool.ApplyAttributesTo( jewel, 3, 20, 40 ); - cont.DropItem( jewel ); + cont.DropItem(new Gold(500)); - if ( !pm.PlaceInBackpack( cont ) ) - { - cont.Delete(); - pm.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - else - { - obj.Complete(); - } - } - } - } - } - } + BaseJewel jewel = new GoldBracelet(); + if (Core.AOS) + BaseRunicTool.ApplyAttributesTo(jewel, 3, 20, 40); + cont.DropItem(jewel); - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (!pm.PlaceInBackpack(cont)) + { + cont.Delete(); + pm.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + else + { + obj.Complete(); + } + } + } + } + } + } - if ( from.Alive ) - { - if ( from is PlayerMobile pm ) - { - QuestSystem qs = pm.Quest; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SpeakCavePasswordObjective ) ); - bool enabled = ( obj != null && !obj.Completed ); + if (from.Alive) + if (from is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - list.Add( new SpeakPasswordEntry( this, pm, enabled ) ); - } - } - } - } + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SpeakCavePasswordObjective)); + bool enabled = obj != null && !obj.Completed; - public virtual void OnPasswordSpoken( PlayerMobile from ) - { - QuestSystem qs = from.Quest; + list.Add(new SpeakPasswordEntry(this, pm, enabled)); + } + } + } - if ( qs is DarkTidesQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SpeakCavePasswordObjective ) ); + public virtual void OnPasswordSpoken(PlayerMobile from) + { + QuestSystem qs = from.Quest; - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - return; - } - } + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SpeakCavePasswordObjective)); - from.SendLocalizedMessage( 1060185 ); // Horus ignores you. - } + if (obj != null && !obj.Completed) + { + obj.Complete(); + return; + } + } - private class SpeakPasswordEntry : ContextMenuEntry - { - private Horus m_Horus; - private PlayerMobile m_From; + from.SendLocalizedMessage(1060185); // Horus ignores you. + } - public SpeakPasswordEntry( Horus horus, PlayerMobile from, bool enabled ) : base( 6193, 3 ) - { - m_Horus = horus; - m_From = from; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } + writer.Write(0); // version + } - public override void OnClick() - { - if ( m_From.Alive ) - m_Horus.OnPasswordSpoken( m_From ); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public Horus( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private class SpeakPasswordEntry : ContextMenuEntry + { + private PlayerMobile m_From; + private Horus m_Horus; - writer.Write( (int) 0 ); // version - } + public SpeakPasswordEntry(Horus horus, PlayerMobile from, bool enabled) : base(6193, 3) + { + m_Horus = horus; + m_From = from; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (!enabled) + Flags |= CMEFlags.Disabled; + } - int version = reader.ReadInt(); - } - } -} + public override void OnClick() + { + if (m_From.Alive) + m_Horus.OnPasswordSpoken(m_From); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Mobiles/Maabus.cs b/Scripts/Engines/Quests/Dark Tides/Mobiles/Maabus.cs index 6cc045895..795815927 100644 --- a/Scripts/Engines/Quests/Dark Tides/Mobiles/Maabus.cs +++ b/Scripts/Engines/Quests/Dark Tides/Mobiles/Maabus.cs @@ -2,44 +2,44 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class Maabus : BaseQuester - { - public override string DefaultName => "Maabus"; + public class Maabus : BaseQuester + { + public Maabus() + { + } - public Maabus() - { - } + public Maabus(Serial serial) : base(serial) + { + } - public override void InitBody() - { - Body = 0x94; - } + public override string DefaultName => "Maabus"; - public Maabus( Serial serial ) : base( serial ) - { - } + public override void InitBody() + { + Body = 0x94; + } - public override bool CanTalkTo( PlayerMobile to ) - { - return false; - } + public override bool CanTalkTo(PlayerMobile to) + { + return false; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Mobiles/Mardoth.cs b/Scripts/Engines/Quests/Dark Tides/Mobiles/Mardoth.cs index 1817fa981..8b5e4e59e 100644 --- a/Scripts/Engines/Quests/Dark Tides/Mobiles/Mardoth.cs +++ b/Scripts/Engines/Quests/Dark Tides/Mobiles/Mardoth.cs @@ -4,217 +4,216 @@ using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class Mardoth : BaseQuester - { - public override string DefaultName => "Mardoth"; + public class Mardoth : BaseQuester + { + [Constructible] + public Mardoth() : base("the Ancient Necromancer") + { + } - [Constructible] - public Mardoth() : base( "the Ancient Necromancer" ) - { - } + public Mardoth(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Mardoth"; - Hue = 0x8849; - Body = 0x190; - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + Hue = 0x8849; + Body = 0x190; + } - if ( qs is DarkTidesQuest ) - { - if ( dropped is DarkTidesHorn horn ) - { - if ( player.Young ) - { - if ( horn.Charges < 10 ) - { - SayTo( from, 1049384 ); // I have recharged the item for you. - horn.Charges = 10; - } - else - { - SayTo( from, 1049385 ); // That doesn't need recharging yet. - } - } - else - { - player.SendLocalizedMessage(1114333); //You must be young to have this item recharged. - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - return false; - } - } - } + if (qs is DarkTidesQuest) + if (dropped is DarkTidesHorn horn) + { + if (player.Young) + { + if (horn.Charges < 10) + { + SayTo(from, 1049384); // I have recharged the item for you. + horn.Charges = 10; + } + else + { + SayTo(from, 1049385); // That doesn't need recharging yet. + } + } + else + { + player.SendLocalizedMessage(1114333); //You must be young to have this item recharged. + } - return base.OnDragDrop( from, dropped ); - } + return false; + } + } - public override void InitOutfit() - { - AddItem( new Sandals( 0x1 ) ); - AddItem( new Robe( 0x66D ) ); - AddItem( new BlackStaff() ); - AddItem( new WizardsHat( 0x1 ) ); + return base.OnDragDrop(from, dropped); + } - FacialHairItemID = 0x2041; - FacialHairHue = 0x482; + public override void InitOutfit() + { + AddItem(new Sandals(0x1)); + AddItem(new Robe(0x66D)); + AddItem(new BlackStaff()); + AddItem(new WizardsHat(0x1)); - HairItemID = 0x203C; - HairHue = 0x482; + FacialHairItemID = 0x2041; + FacialHairHue = 0x482; - Item gloves = new BoneGloves(); - gloves.Hue = 0x66D; - AddItem( gloves ); + HairItemID = 0x203C; + HairHue = 0x482; - Item gorget = new PlateGorget(); - gorget.Hue = 0x1; - AddItem( gorget ); - } + Item gloves = new BoneGloves(); + gloves.Hue = 0x66D; + AddItem(gloves); - public override int GetAutoTalkRange( PlayerMobile m ) - { - return 3; - } + Item gorget = new PlateGorget(); + gorget.Hue = 0x1; + AddItem(gorget); + } - public override bool CanTalkTo( PlayerMobile to ) - { - if ( !(to.Quest is DarkTidesQuest qs) ) - return ( to.Quest == null && QuestSystem.CanOfferQuest( to, typeof( DarkTidesQuest ) ) ); + public override int GetAutoTalkRange(PlayerMobile m) + { + return 3; + } - return ( qs.FindObjective( typeof( FindMardothAboutVaultObjective ) ) != null ); - } + public override bool CanTalkTo(PlayerMobile to) + { + if (!(to.Quest is DarkTidesQuest qs)) + return to.Quest == null && QuestSystem.CanOfferQuest(to, typeof(DarkTidesQuest)); - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + return qs.FindObjective(typeof(FindMardothAboutVaultObjective)) != null; + } - if ( qs is DarkTidesQuest ) - { - if ( DarkTidesQuest.HasLostCallingScroll( player ) ) - { - qs.AddConversation( new LostCallingScrollConversation( true ) ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( FindMardothAboutVaultObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else - { - obj = qs.FindObjective( typeof( FindMardothAboutKronusObjective ) ); + if (qs is DarkTidesQuest) + { + if (DarkTidesQuest.HasLostCallingScroll(player)) + { + qs.AddConversation(new LostCallingScrollConversation(true)); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(FindMardothAboutVaultObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else - { - obj = qs.FindObjective( typeof( FindMardothEndObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else + { + obj = qs.FindObjective(typeof(FindMardothAboutKronusObjective)); - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else + { + obj = qs.FindObjective(typeof(FindMardothEndObjective)); - cont.DropItem( new PigIron( 20 ) ); - cont.DropItem( new NoxCrystal( 20 ) ); - cont.DropItem( new BatWing( 25 ) ); - cont.DropItem( new DaemonBlood( 20 ) ); - cont.DropItem( new GraveDust( 20 ) ); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - BaseWeapon weapon = new BoneHarvester(); + cont.DropItem(new PigIron(20)); + cont.DropItem(new NoxCrystal(20)); + cont.DropItem(new BatWing(25)); + cont.DropItem(new DaemonBlood(20)); + cont.DropItem(new GraveDust(20)); - weapon.Slayer = SlayerName.OrcSlaying; + BaseWeapon weapon = new BoneHarvester(); - if ( Core.AOS ) - { - BaseRunicTool.ApplyAttributesTo( weapon, 3, 20, 40 ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled( 2, 4 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled( 2, 4 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled( 2, 4 ); - } + weapon.Slayer = SlayerName.OrcSlaying; - cont.DropItem( weapon ); + if (Core.AOS) + { + BaseRunicTool.ApplyAttributesTo(weapon, 3, 20, 40); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(2, 4); + weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(2, 4); + weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(2, 4); + } - cont.DropItem( new BankCheck( 2000 ) ); - cont.DropItem( new EnchantedSextant() ); + cont.DropItem(weapon); - if ( !player.PlaceInBackpack( cont ) ) - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - else - { - obj.Complete(); - } - } - else if ( contextMenu ) - { - FocusTo( player ); - player.SendLocalizedMessage( 1061821 ); // Mardoth has nothing more for you at this time. - } - } - } - } - } - else if ( qs == null && QuestSystem.CanOfferQuest( player, typeof( DarkTidesQuest ) ) ) - { - new DarkTidesQuest( player ).SendOffer(); - } - } + cont.DropItem(new BankCheck(2000)); + cont.DropItem(new EnchantedSextant()); - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + if (!player.PlaceInBackpack(cont)) + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + else + { + obj.Complete(); + } + } + else if (contextMenu) + { + FocusTo(player); + player.SendLocalizedMessage(1061821); // Mardoth has nothing more for you at this time. + } + } + } + } + } + else if (qs == null && QuestSystem.CanOfferQuest(player, typeof(DarkTidesQuest))) + { + new DarkTidesQuest(player).SendOffer(); + } + } - if ( m is PlayerMobile && !m.Frozen && !m.Alive && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && InLOS( m ) ) - { - if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else - { - Direction = GetDirectionTo( m ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m)) + { + if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + else + { + Direction = GetDirectionTo(m); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.Healer ) ); - } - } - } + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - public Mardoth( Serial serial ) : base( serial ) - { - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer)); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Mobiles/SummonedPaladin.cs b/Scripts/Engines/Quests/Dark Tides/Mobiles/SummonedPaladin.cs index bb27a067a..9d0450234 100644 --- a/Scripts/Engines/Quests/Dark Tides/Mobiles/SummonedPaladin.cs +++ b/Scripts/Engines/Quests/Dark Tides/Mobiles/SummonedPaladin.cs @@ -1,240 +1,243 @@ using System; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Necro { - public class SummonedPaladin : BaseCreature - { - private PlayerMobile m_Necromancer; - private bool m_ToDelete; + public class SummonedPaladin : BaseCreature + { + private PlayerMobile m_Necromancer; + private bool m_ToDelete; - public SummonedPaladin( PlayerMobile necromancer ) : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - m_Necromancer = necromancer; + public SummonedPaladin(PlayerMobile necromancer) : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + m_Necromancer = necromancer; - InitStats( 45, 30, 5 ); - Title = "the Paladin"; + InitStats(45, 30, 5); + Title = "the Paladin"; - Hue = 0x83F3; + Hue = 0x83F3; - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, false ); + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, false); - FacialHairHue = HairHue; + FacialHairHue = HairHue; - AddItem( new Boots( 0x1 ) ); - AddItem( new ChainChest() ); - AddItem( new ChainLegs() ); - AddItem( new RingmailArms() ); - AddItem( new PlateHelm() ); - AddItem( new PlateGloves() ); - AddItem( new PlateGorget() ); + AddItem(new Boots(0x1)); + AddItem(new ChainChest()); + AddItem(new ChainLegs()); + AddItem(new RingmailArms()); + AddItem(new PlateHelm()); + AddItem(new PlateGloves()); + AddItem(new PlateGorget()); - AddItem( new Cloak( 0xCF ) ); + AddItem(new Cloak(0xCF)); - AddItem( new ThinLongsword() ); + AddItem(new ThinLongsword()); - SetSkill( SkillName.Swords, 50.0 ); - SetSkill( SkillName.Tactics, 50.0 ); + SetSkill(SkillName.Swords, 50.0); + SetSkill(SkillName.Tactics, 50.0); - PackGold( 500 ); - } + PackGold(500); + } - public override bool IsHarmfulCriminal(Mobile target) - { - if ( target == m_Necromancer ) - return false; + public SummonedPaladin(Serial serial) : base(serial) + { + } - return base.IsHarmfulCriminal( target ); - } + public override bool ClickTitle => false; - public override bool ClickTitle => false; + public override bool PlayerRangeSensitive => false; - public override bool PlayerRangeSensitive => false; + public override bool IsHarmfulCriminal(Mobile target) + { + if (target == m_Necromancer) + return false; - public override void OnThink() - { - if ( !m_ToDelete && !Frozen ) - { - if ( m_Necromancer == null || m_Necromancer.Deleted || m_Necromancer.Map == Map.Internal ) - { - Delete(); - return; - } + return base.IsHarmfulCriminal(target); + } - if ( Combatant != m_Necromancer ) - Combatant = m_Necromancer; + public override void OnThink() + { + if (!m_ToDelete && !Frozen) + { + if (m_Necromancer == null || m_Necromancer.Deleted || m_Necromancer.Map == Map.Internal) + { + Delete(); + return; + } - if ( !m_Necromancer.Alive ) - { - QuestSystem qs = m_Necromancer.Quest; + if (Combatant != m_Necromancer) + Combatant = m_Necromancer; - if ( qs is DarkTidesQuest && qs.FindObjective( typeof( FindMardothEndObjective ) ) == null ) - qs.AddObjective( new FindMardothEndObjective( false ) ); + if (!m_Necromancer.Alive) + { + QuestSystem qs = m_Necromancer.Quest; - Say( 1060139, m_Necromancer.Name ); // You have made my work easy for me, ~1_NAME~. My task here is done. + if (qs is DarkTidesQuest && qs.FindObjective(typeof(FindMardothEndObjective)) == null) + qs.AddObjective(new FindMardothEndObjective(false)); - m_ToDelete = true; + Say(1060139, m_Necromancer.Name); // You have made my work easy for me, ~1_NAME~. My task here is done. - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), Delete ); - } - else if ( m_Necromancer.Map != Map || GetDistanceToSqrt( m_Necromancer ) > RangePerception + 1 ) - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( m_Necromancer.Location, m_Necromancer.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); + m_ToDelete = true; - Map = m_Necromancer.Map; - Location = m_Necromancer.Location; + Timer.DelayCall(TimeSpan.FromSeconds(5.0), Delete); + } + else if (m_Necromancer.Map != Map || GetDistanceToSqrt(m_Necromancer) > RangePerception + 1) + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3728, 10, + 10, 2023); + Effects.SendLocationParticles( + EffectItem.Create(m_Necromancer.Location, m_Necromancer.Map, EffectItem.DefaultDuration), 0x3728, 10, + 10, 5023); - PlaySound( 0x1FE ); + Map = m_Necromancer.Map; + Location = m_Necromancer.Location; - Say( 1060140 ); // You cannot escape me, knave of evil! - } - } + PlaySound(0x1FE); - base.OnThink(); - } + Say(1060140); // You cannot escape me, knave of evil! + } + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + base.OnThink(); + } - QuestSystem qs = m_Necromancer.Quest; + public override void OnDeath(Container c) + { + base.OnDeath(c); - if ( qs is DarkTidesQuest && qs.FindObjective( typeof( FindMardothEndObjective ) ) == null ) - qs.AddObjective( new FindMardothEndObjective( true ) ); - } + QuestSystem qs = m_Necromancer.Quest; - public SummonedPaladin( Serial serial ) : base( serial ) - { - } + if (qs is DarkTidesQuest && qs.FindObjective(typeof(FindMardothEndObjective)) == null) + qs.AddObjective(new FindMardothEndObjective(true)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (Mobile) m_Necromancer ); - writer.Write( (bool) m_ToDelete ); - } + writer.Write(m_Necromancer); + writer.Write(m_ToDelete); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Necromancer = reader.ReadMobile() as PlayerMobile; - m_ToDelete = reader.ReadBool(); + m_Necromancer = reader.ReadMobile() as PlayerMobile; + m_ToDelete = reader.ReadBool(); - if ( m_ToDelete ) - Delete(); - } + if (m_ToDelete) + Delete(); + } - public static void BeginSummon( PlayerMobile player ) - { - new SummonTimer( player ).Start(); - } + public static void BeginSummon(PlayerMobile player) + { + new SummonTimer(player).Start(); + } - private class SummonTimer : Timer - { - private PlayerMobile m_Player; - private SummonedPaladin m_Paladin; - private int m_Step; + private class SummonTimer : Timer + { + private SummonedPaladin m_Paladin; + private PlayerMobile m_Player; + private int m_Step; - public SummonTimer( PlayerMobile player ) : base( TimeSpan.FromSeconds( 4.0 ) ) - { - Priority = TimerPriority.FiftyMS; + public SummonTimer(PlayerMobile player) : base(TimeSpan.FromSeconds(4.0)) + { + Priority = TimerPriority.FiftyMS; - m_Player = player; - } + m_Player = player; + } - protected override void OnTick() - { - if ( m_Player.Deleted ) - { - if ( m_Step > 0 ) - m_Paladin.Delete(); + protected override void OnTick() + { + if (m_Player.Deleted) + { + if (m_Step > 0) + m_Paladin.Delete(); - return; - } + return; + } - if ( m_Step > 0 && m_Paladin.Deleted ) - return; + if (m_Step > 0 && m_Paladin.Deleted) + return; - if ( m_Step == 0 ) - { - SummonedPaladinMoongate moongate = new SummonedPaladinMoongate(); - moongate.MoveToWorld( new Point3D( 2091, 1348, -90 ), Map.Malas ); + if (m_Step == 0) + { + SummonedPaladinMoongate moongate = new SummonedPaladinMoongate(); + moongate.MoveToWorld(new Point3D(2091, 1348, -90), Map.Malas); - Effects.PlaySound( moongate.Location, moongate.Map, 0x20E ); + Effects.PlaySound(moongate.Location, moongate.Map, 0x20E); - m_Paladin = new SummonedPaladin( m_Player ); - m_Paladin.Frozen = true; + m_Paladin = new SummonedPaladin(m_Player); + m_Paladin.Frozen = true; - m_Paladin.Location = moongate.Location; - m_Paladin.Map = moongate.Map; + m_Paladin.Location = moongate.Location; + m_Paladin.Map = moongate.Map; - Delay = TimeSpan.FromSeconds( 2.0 ); - Start(); - } - else if ( m_Step == 1 ) - { - m_Paladin.Direction = m_Paladin.GetDirectionTo( m_Player ); - m_Paladin.Say( 1060122 ); // STOP WICKED ONE! + Delay = TimeSpan.FromSeconds(2.0); + Start(); + } + else if (m_Step == 1) + { + m_Paladin.Direction = m_Paladin.GetDirectionTo(m_Player); + m_Paladin.Say(1060122); // STOP WICKED ONE! - Delay = TimeSpan.FromSeconds( 3.0 ); - Start(); - } - else - { - m_Paladin.Frozen = false; + Delay = TimeSpan.FromSeconds(3.0); + Start(); + } + else + { + m_Paladin.Frozen = false; - m_Paladin.Say( 1060123 ); // I will slay you before I allow you to complete your evil rites! + m_Paladin.Say(1060123); // I will slay you before I allow you to complete your evil rites! - m_Paladin.Combatant = m_Player; - } + m_Paladin.Combatant = m_Player; + } - m_Step++; - } - } - } + m_Step++; + } + } + } - public class SummonedPaladinMoongate : Item - { - public SummonedPaladinMoongate() : base( 0xF6C ) - { - Movable = false; - Hue = 0x482; - Light = LightType.Circle300; + public class SummonedPaladinMoongate : Item + { + public SummonedPaladinMoongate() : base(0xF6C) + { + Movable = false; + Hue = 0x482; + Light = LightType.Circle300; - Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), Delete ); - } + Timer.DelayCall(TimeSpan.FromSeconds(10.0), Delete); + } - public SummonedPaladinMoongate( Serial serial ) : base( serial ) - { - } + public SummonedPaladinMoongate(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } - } -} + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Dark Tides/Objectives.cs b/Scripts/Engines/Quests/Dark Tides/Objectives.cs index 094f4115d..dfdc2b81f 100644 --- a/Scripts/Engines/Quests/Dark Tides/Objectives.cs +++ b/Scripts/Engines/Quests/Dark Tides/Objectives.cs @@ -1,457 +1,379 @@ using Server.Items; using Server.Mobiles; +using Server.Spells.Necromancy; namespace Server.Engines.Quests.Necro { - public class AnimateMaabusCorpseObjective : QuestObjective - { - public override object Message => 1060102; - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1023643, 8787 ) // spellbook - }; - - public override QuestItemInfo[] Info => m_Info; - - public AnimateMaabusCorpseObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new MaabasConversation() ); - } - } - - public class FindCrystalCaveObjective : QuestObjective - { - public override object Message => 1060104; - - public FindCrystalCaveObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new HorusConversation() ); - } - } - - public class FindMardothAboutVaultObjective : QuestObjective - { - public override object Message => 1060106; - - public FindMardothAboutVaultObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new MardothVaultConversation() ); - } - } - - public class FindMaabusTombObjective : QuestObjective - { - public override object Message => 1060124; - - public FindMaabusTombObjective() - { - } - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 2024, 1240, -90 ), 3 ) ) - Complete(); - } - - public override void OnComplete() - { - System.AddObjective( new FindMaabusCorpseObjective() ); - } - } - - public class FindMaabusCorpseObjective : QuestObjective - { - public override object Message => 1061142; - - public FindMaabusCorpseObjective() - { - } - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 2024, 1223, -90 ), 3 ) ) - Complete(); - } - - public override void OnComplete() - { - System.AddObjective( new AnimateMaabusCorpseObjective() ); - } - } - - public class FindCityOfLightObjective : QuestObjective - { - public override object Message => 1060108; - - public FindCityOfLightObjective() - { - } - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 1076, 519, -90 ), 5 ) ) - Complete(); - } - - public override void OnComplete() - { - System.AddObjective( new FindVaultOfSecretsObjective() ); - } - } - - public class FindVaultOfSecretsObjective : QuestObjective - { - public override object Message => 1060109; - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1023676, 3679 ) // glowing rune - }; - - public override QuestItemInfo[] Info => m_Info; - - public FindVaultOfSecretsObjective() - { - } - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 1072, 455, -90 ), 1 ) ) - Complete(); - } - - public override void OnComplete() - { - System.AddConversation( new VaultOfSecretsConversation() ); - } - } - - public class FetchAbraxusScrollObjective : QuestObjective - { - public override object Message => 1060196; - - public FetchAbraxusScrollObjective() - { - } - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 1076, 450, -84 ), 5 ) ) - { - if ( Spells.Necromancy.SummonFamiliarSpell.Table[System.From] is HordeMinionFamiliar hmf && hmf.InRange( System.From, 5 ) && hmf.TargetLocation == null ) - { - System.From.SendLocalizedMessage( 1060113 ); // You instinctively will your familiar to fetch the scroll for you. - hmf.TargetLocation = new Point2D( 1076, 450 ); - } - } - } - - public override void OnComplete() - { - System.AddObjective( new RetrieveAbraxusScrollObjective() ); - } - } - - public class RetrieveAbraxusScrollObjective : QuestObjective - { - public override object Message => 1060199; - - public RetrieveAbraxusScrollObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ReadAbraxusScrollConversation() ); - } - } - - public class ReadAbraxusScrollObjective : QuestObjective - { - public override object Message => 1060125; - - public ReadAbraxusScrollObjective() - { - } - - public override void OnComplete() - { - System.AddObjective( new ReturnToCrystalCaveObjective() ); - } - } - - public class ReturnToCrystalCaveObjective : QuestObjective - { - public override object Message => 1060115; - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1026153, 6178 ) // teleporter - }; - - public override QuestItemInfo[] Info => m_Info; - - public ReturnToCrystalCaveObjective() - { - } - - public override void OnComplete() - { - System.AddObjective( new SpeakCavePasswordObjective() ); - } - } - - public class SpeakCavePasswordObjective : QuestObjective - { - public override object Message => 1060117; - - public SpeakCavePasswordObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new SecondHorusConversation() ); - } - } - - public class FindCallingScrollObjective : QuestObjective - { - public override object Message => 1060119; - - private int m_SkitteringHoppersKilled; - private bool m_HealConversationShown; - private bool m_SkitteringHoppersDisposed; - - public FindCallingScrollObjective() - { - } - - public override bool IgnoreYoungProtection( Mobile from ) - { - return !m_SkitteringHoppersDisposed && from is SkitteringHopper; - } - - public override bool GetKillEvent( BaseCreature creature, Container corpse ) - { - return !m_SkitteringHoppersDisposed; - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is SkitteringHopper ) - { - if ( !m_HealConversationShown ) - { - m_HealConversationShown = true; - System.AddConversation( new HealConversation() ); - } - - if ( ++m_SkitteringHoppersKilled >= 5 ) - { - m_SkitteringHoppersDisposed = true; - System.AddObjective( new FindHorusAboutRewardObjective() ); - } - } - } - - public override void OnComplete() - { - System.AddObjective( new FindMardothAboutKronusObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_SkitteringHoppersKilled = reader.ReadEncodedInt(); - m_HealConversationShown = reader.ReadBool(); - m_SkitteringHoppersDisposed = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) m_SkitteringHoppersKilled ); - writer.Write( (bool) m_HealConversationShown ); - writer.Write( (bool) m_SkitteringHoppersDisposed ); - } - } - - public class FindHorusAboutRewardObjective : QuestObjective - { - public override object Message => 1060126; - - public FindHorusAboutRewardObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new HorusRewardConversation() ); - } - } - - public class FindMardothAboutKronusObjective : QuestObjective - { - public override object Message => 1060127; - - public FindMardothAboutKronusObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new MardothKronusConversation() ); - } - } - - public class FindWellOfTearsObjective : QuestObjective - { - public override object Message => 1060128; - - public FindWellOfTearsObjective() - { - } - - private static readonly Rectangle2D m_WellOfTearsArea = new Rectangle2D( 2080, 1346, 10, 10 ); - - private bool m_Inside; - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && m_WellOfTearsArea.Contains( System.From.Location ) ) - { - if ( DarkTidesQuest.HasLostCallingScroll( System.From ) ) - { - if ( !m_Inside ) - System.AddConversation( new LostCallingScrollConversation( false ) ); - } - else - { - Complete(); - } - - m_Inside = true; - } - else - { - m_Inside = false; - } - } - - public override void OnComplete() - { - System.AddObjective( new UseCallingScrollObjective() ); - } - } - - public class UseCallingScrollObjective : QuestObjective - { - public override object Message => 1060130; - - public UseCallingScrollObjective() - { - } - } - - public class FindMardothEndObjective : QuestObjective - { - private bool m_Victory; - - public override object Message - { - get - { - if ( m_Victory ) - { - /* Victory! You have done as Mardoth has asked of you. - * Take as much of your foe's loot as you can carry - * and return to Mardoth for your reward. - */ - return 1060131; - } - - /* Although you were slain by the cowardly paladin, - * you managed to complete the rite of calling as - * instructed. Return to Mardoth. - */ - return 1060132; - } - } - - public FindMardothEndObjective( bool victory ) - { - m_Victory = victory; - } - - // Serialization - public FindMardothEndObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new MardothEndConversation() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_Victory = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_Victory ); - } - } - - public class FindBankObjective : QuestObjective - { - public override object Message => 1060134; - - public FindBankObjective() - { - } - - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 2048, 1345, -84 ), 5 ) ) - Complete(); - } - - public override void OnComplete() - { - System.AddObjective( new CashBankCheckObjective() ); - } - } - - public class CashBankCheckObjective : QuestObjective - { - public override object Message => 1060644; - - public CashBankCheckObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new BankerConversation() ); - } - } -} + public class AnimateMaabusCorpseObjective : QuestObjective + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1023643, 8787) // spellbook + }; + + public override object Message => 1060102; + + public override QuestItemInfo[] Info => m_Info; + + public override void OnComplete() + { + System.AddConversation(new MaabasConversation()); + } + } + + public class FindCrystalCaveObjective : QuestObjective + { + public override object Message => 1060104; + + public override void OnComplete() + { + System.AddConversation(new HorusConversation()); + } + } + + public class FindMardothAboutVaultObjective : QuestObjective + { + public override object Message => 1060106; + + public override void OnComplete() + { + System.AddConversation(new MardothVaultConversation()); + } + } + + public class FindMaabusTombObjective : QuestObjective + { + public override object Message => 1060124; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(2024, 1240, -90), 3)) + Complete(); + } + + public override void OnComplete() + { + System.AddObjective(new FindMaabusCorpseObjective()); + } + } + + public class FindMaabusCorpseObjective : QuestObjective + { + public override object Message => 1061142; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(2024, 1223, -90), 3)) + Complete(); + } + + public override void OnComplete() + { + System.AddObjective(new AnimateMaabusCorpseObjective()); + } + } + + public class FindCityOfLightObjective : QuestObjective + { + public override object Message => 1060108; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(1076, 519, -90), 5)) + Complete(); + } + + public override void OnComplete() + { + System.AddObjective(new FindVaultOfSecretsObjective()); + } + } + + public class FindVaultOfSecretsObjective : QuestObjective + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1023676, 3679) // glowing rune + }; + + public override object Message => 1060109; + + public override QuestItemInfo[] Info => m_Info; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(1072, 455, -90), 1)) + Complete(); + } + + public override void OnComplete() + { + System.AddConversation(new VaultOfSecretsConversation()); + } + } + + public class FetchAbraxusScrollObjective : QuestObjective + { + public override object Message => 1060196; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(1076, 450, -84), 5)) + if (SummonFamiliarSpell.Table[System.From] is HordeMinionFamiliar hmf && hmf.InRange(System.From, 5) && + hmf.TargetLocation == null) + { + System.From.SendLocalizedMessage( + 1060113); // You instinctively will your familiar to fetch the scroll for you. + hmf.TargetLocation = new Point2D(1076, 450); + } + } + + public override void OnComplete() + { + System.AddObjective(new RetrieveAbraxusScrollObjective()); + } + } + + public class RetrieveAbraxusScrollObjective : QuestObjective + { + public override object Message => 1060199; + + public override void OnComplete() + { + System.AddConversation(new ReadAbraxusScrollConversation()); + } + } + + public class ReadAbraxusScrollObjective : QuestObjective + { + public override object Message => 1060125; + + public override void OnComplete() + { + System.AddObjective(new ReturnToCrystalCaveObjective()); + } + } + + public class ReturnToCrystalCaveObjective : QuestObjective + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1026153, 6178) // teleporter + }; + + public override object Message => 1060115; + + public override QuestItemInfo[] Info => m_Info; + + public override void OnComplete() + { + System.AddObjective(new SpeakCavePasswordObjective()); + } + } + + public class SpeakCavePasswordObjective : QuestObjective + { + public override object Message => 1060117; + + public override void OnComplete() + { + System.AddConversation(new SecondHorusConversation()); + } + } + + public class FindCallingScrollObjective : QuestObjective + { + private bool m_HealConversationShown; + private bool m_SkitteringHoppersDisposed; + + private int m_SkitteringHoppersKilled; + + public override object Message => 1060119; + + public override bool IgnoreYoungProtection(Mobile from) + { + return !m_SkitteringHoppersDisposed && from is SkitteringHopper; + } + + public override bool GetKillEvent(BaseCreature creature, Container corpse) + { + return !m_SkitteringHoppersDisposed; + } + + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is SkitteringHopper) + { + if (!m_HealConversationShown) + { + m_HealConversationShown = true; + System.AddConversation(new HealConversation()); + } + + if (++m_SkitteringHoppersKilled >= 5) + { + m_SkitteringHoppersDisposed = true; + System.AddObjective(new FindHorusAboutRewardObjective()); + } + } + } + + public override void OnComplete() + { + System.AddObjective(new FindMardothAboutKronusObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_SkitteringHoppersKilled = reader.ReadEncodedInt(); + m_HealConversationShown = reader.ReadBool(); + m_SkitteringHoppersDisposed = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(m_SkitteringHoppersKilled); + writer.Write(m_HealConversationShown); + writer.Write(m_SkitteringHoppersDisposed); + } + } + + public class FindHorusAboutRewardObjective : QuestObjective + { + public override object Message => 1060126; + + public override void OnComplete() + { + System.AddConversation(new HorusRewardConversation()); + } + } + + public class FindMardothAboutKronusObjective : QuestObjective + { + public override object Message => 1060127; + + public override void OnComplete() + { + System.AddConversation(new MardothKronusConversation()); + } + } + + public class FindWellOfTearsObjective : QuestObjective + { + private static readonly Rectangle2D m_WellOfTearsArea = new Rectangle2D(2080, 1346, 10, 10); + + private bool m_Inside; + + public override object Message => 1060128; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && m_WellOfTearsArea.Contains(System.From.Location)) + { + if (DarkTidesQuest.HasLostCallingScroll(System.From)) + { + if (!m_Inside) + System.AddConversation(new LostCallingScrollConversation(false)); + } + else + { + Complete(); + } + + m_Inside = true; + } + else + { + m_Inside = false; + } + } + + public override void OnComplete() + { + System.AddObjective(new UseCallingScrollObjective()); + } + } + + public class UseCallingScrollObjective : QuestObjective + { + public override object Message => 1060130; + } + + public class FindMardothEndObjective : QuestObjective + { + private bool m_Victory; + + public FindMardothEndObjective(bool victory) + { + m_Victory = victory; + } + + // Serialization + public FindMardothEndObjective() + { + } + + public override object Message + { + get + { + if (m_Victory) return 1060131; + + /* Although you were slain by the cowardly paladin, + * you managed to complete the rite of calling as + * instructed. Return to Mardoth. + */ + return 1060132; + } + } + + public override void OnComplete() + { + System.AddConversation(new MardothEndConversation()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_Victory = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_Victory); + } + } + + public class FindBankObjective : QuestObjective + { + public override object Message => 1060134; + + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(2048, 1345, -84), 5)) + Complete(); + } + + public override void OnComplete() + { + System.AddObjective(new CashBankCheckObjective()); + } + } + + public class CashBankCheckObjective : QuestObjective + { + public override object Message => 1060644; + + public override void OnComplete() + { + System.AddConversation(new BankerConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Conversations.cs b/Scripts/Engines/Quests/Emino's Undertaking/Conversations.cs index f74e20088..536d5d5c3 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Conversations.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Conversations.cs @@ -1,265 +1,185 @@ namespace Server.Engines.Quests.Ninja { - public class AcceptConversation : QuestConversation - { - public override object Message => 1049092; + public class AcceptConversation : QuestConversation + { + public override object Message => 1049092; - public AcceptConversation() - { - } + public override void OnRead() + { + System.AddObjective(new FindEminoBeginObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new FindEminoBeginObjective() ); - } - } + public class FindZoelConversation : QuestConversation + { + public override object Message => 1063175; - public class FindZoelConversation : QuestConversation - { - public override object Message => 1063175; + public override void OnRead() + { + System.AddObjective(new FindZoelObjective()); + } + } - public FindZoelConversation() - { - } + public class RadarConversation : QuestConversation + { + public override object Message => 1063033; - public override void OnRead() - { - System.AddObjective( new FindZoelObjective() ); - } - } + public override bool Logged => false; + } - public class RadarConversation : QuestConversation - { - public override object Message => 1063033; + public class EnterCaveConversation : QuestConversation + { + public override object Message => 1063177; - public override bool Logged => false; + public override void OnRead() + { + System.AddObjective(new EnterCaveObjective()); + } + } - public RadarConversation() - { - } - } + public class SneakPastGuardiansConversation : QuestConversation + { + public override object Message => 1063180; - public class EnterCaveConversation : QuestConversation - { - public override object Message => 1063177; + public override void OnRead() + { + System.AddObjective(new SneakPastGuardiansObjective()); + } + } - public EnterCaveConversation() - { - } + public class NeedToHideConversation : QuestConversation + { + public override object Message => 1063181; + } - public override void OnRead() - { - System.AddObjective( new EnterCaveObjective() ); - } - } + public class UseTeleporterConversation : QuestConversation + { + public override object Message => 1063182; - public class SneakPastGuardiansConversation : QuestConversation - { - public override object Message => 1063180; + public override void OnRead() + { + System.AddObjective(new UseTeleporterObjective()); + } + } - public SneakPastGuardiansConversation() - { - } + public class GiveZoelNoteConversation : QuestConversation + { + public override object Message => 1063184; - public override void OnRead() - { - System.AddObjective( new SneakPastGuardiansObjective() ); - } - } + public override void OnRead() + { + System.AddObjective(new GiveZoelNoteObjective()); + } + } - public class NeedToHideConversation : QuestConversation - { - public override object Message => 1063181; + public class LostNoteConversation : QuestConversation + { + public override object Message => 1063187; - public NeedToHideConversation() - { - } - } + public override bool Logged => false; + } - public class UseTeleporterConversation : QuestConversation - { - public override object Message => 1063182; + public class GainInnInformationConversation : QuestConversation + { + public override object Message => 1063189; - public UseTeleporterConversation() - { - } + public override void OnRead() + { + System.AddObjective(new GainInnInformationObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new UseTeleporterObjective() ); - } - } + public class ReturnFromInnConversation : QuestConversation + { + public override object Message => 1063196; - public class GiveZoelNoteConversation : QuestConversation - { - public override object Message => 1063184; + public override void OnRead() + { + System.AddObjective(new ReturnFromInnObjective()); + } + } - public GiveZoelNoteConversation() - { - } + public class SearchForSwordConversation : QuestConversation + { + public override object Message => 1063199; - public override void OnRead() - { - System.AddObjective( new GiveZoelNoteObjective() ); - } - } + public override void OnRead() + { + System.AddObjective(new SearchForSwordObjective()); + } + } - public class LostNoteConversation : QuestConversation - { - public override object Message => 1063187; + public class HallwayWalkConversation : QuestConversation + { + public override object Message => 1063201; - public override bool Logged => false; + public override void OnRead() + { + System.AddObjective(new HallwayWalkObjective()); + } + } - public LostNoteConversation() - { - } - } + public class ReturnSwordConversation : QuestConversation + { + public override object Message => 1063203; - public class GainInnInformationConversation : QuestConversation - { - public override object Message => 1063189; + public override void OnRead() + { + System.AddObjective(new ReturnSwordObjective()); + } + } - public GainInnInformationConversation() - { - } + public class SlayHenchmenConversation : QuestConversation + { + public override object Message => 1063205; - public override void OnRead() - { - System.AddObjective( new GainInnInformationObjective() ); - } - } + public override void OnRead() + { + System.AddObjective(new SlayHenchmenObjective()); + } + } - public class ReturnFromInnConversation : QuestConversation - { - public override object Message => 1063196; + public class ContinueSlayHenchmenConversation : QuestConversation + { + public override object Message => 1063208; - public ReturnFromInnConversation() - { - } + public override bool Logged => false; + } - public override void OnRead() - { - System.AddObjective( new ReturnFromInnObjective() ); - } - } + public class GiveEminoSwordConversation : QuestConversation + { + public override object Message => 1063211; - public class SearchForSwordConversation : QuestConversation - { - public override object Message => 1063199; + public override void OnRead() + { + System.AddObjective(new GiveEminoSwordObjective()); + } + } - public SearchForSwordConversation() - { - } + public class LostSwordConversation : QuestConversation + { + public override object Message => 1063212; - public override void OnRead() - { - System.AddObjective( new SearchForSwordObjective() ); - } - } + public override bool Logged => false; + } - public class HallwayWalkConversation : QuestConversation - { - public override object Message => 1063201; + public class EarnGiftsConversation : QuestConversation + { + public override object Message => 1063216; - public HallwayWalkConversation() - { - } + public override void OnRead() + { + System.Complete(); + } + } - public override void OnRead() - { - System.AddObjective( new HallwayWalkObjective() ); - } - } + public class EarnLessGiftsConversation : QuestConversation + { + public override object Message => 1063217; - public class ReturnSwordConversation : QuestConversation - { - public override object Message => 1063203; - - public ReturnSwordConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnSwordObjective() ); - } - } - - public class SlayHenchmenConversation : QuestConversation - { - public override object Message => 1063205; - - public SlayHenchmenConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new SlayHenchmenObjective() ); - } - } - - public class ContinueSlayHenchmenConversation : QuestConversation - { - public override object Message => 1063208; - - public override bool Logged => false; - - public ContinueSlayHenchmenConversation() - { - } - } - - public class GiveEminoSwordConversation : QuestConversation - { - public override object Message => 1063211; - - public GiveEminoSwordConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new GiveEminoSwordObjective() ); - } - } - - public class LostSwordConversation : QuestConversation - { - public override object Message => 1063212; - - public override bool Logged => false; - - public LostSwordConversation() - { - } - } - - public class EarnGiftsConversation : QuestConversation - { - public override object Message => 1063216; - - public EarnGiftsConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } - - public class EarnLessGiftsConversation : QuestConversation - { - public override object Message => 1063217; - - public EarnLessGiftsConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } -} + public override void OnRead() + { + System.Complete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/EminosUndertakingQuest.cs b/Scripts/Engines/Quests/Emino's Undertaking/EminosUndertakingQuest.cs index 1c19a44a8..79396cb2b 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/EminosUndertakingQuest.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/EminosUndertakingQuest.cs @@ -3,132 +3,126 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class EminosUndertakingQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( AcceptConversation ), - typeof( FindZoelConversation ), - typeof( RadarConversation ), - typeof( EnterCaveConversation ), - typeof( SneakPastGuardiansConversation ), - typeof( NeedToHideConversation ), - typeof( UseTeleporterConversation ), - typeof( GiveZoelNoteConversation ), - typeof( LostNoteConversation ), - typeof( GainInnInformationConversation ), - typeof( ReturnFromInnConversation ), - typeof( SearchForSwordConversation ), - typeof( HallwayWalkConversation ), - typeof( ReturnSwordConversation ), - typeof( SlayHenchmenConversation ), - typeof( ContinueSlayHenchmenConversation ), - typeof( GiveEminoSwordConversation ), - typeof( LostSwordConversation ), - typeof( EarnGiftsConversation ), - typeof( EarnLessGiftsConversation ), - typeof( FindEminoBeginObjective ), - typeof( FindZoelObjective ), - typeof( EnterCaveObjective ), - typeof( SneakPastGuardiansObjective ), - typeof( UseTeleporterObjective ), - typeof( GiveZoelNoteObjective ), - typeof( GainInnInformationObjective ), - typeof( ReturnFromInnObjective ), - typeof( SearchForSwordObjective ), - typeof( HallwayWalkObjective ), - typeof( ReturnSwordObjective ), - typeof( SlayHenchmenObjective ), - typeof( GiveEminoSwordObjective ) - }; + public class EminosUndertakingQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(AcceptConversation), + typeof(FindZoelConversation), + typeof(RadarConversation), + typeof(EnterCaveConversation), + typeof(SneakPastGuardiansConversation), + typeof(NeedToHideConversation), + typeof(UseTeleporterConversation), + typeof(GiveZoelNoteConversation), + typeof(LostNoteConversation), + typeof(GainInnInformationConversation), + typeof(ReturnFromInnConversation), + typeof(SearchForSwordConversation), + typeof(HallwayWalkConversation), + typeof(ReturnSwordConversation), + typeof(SlayHenchmenConversation), + typeof(ContinueSlayHenchmenConversation), + typeof(GiveEminoSwordConversation), + typeof(LostSwordConversation), + typeof(EarnGiftsConversation), + typeof(EarnLessGiftsConversation), + typeof(FindEminoBeginObjective), + typeof(FindZoelObjective), + typeof(EnterCaveObjective), + typeof(SneakPastGuardiansObjective), + typeof(UseTeleporterObjective), + typeof(GiveZoelNoteObjective), + typeof(GainInnInformationObjective), + typeof(ReturnFromInnObjective), + typeof(SearchForSwordObjective), + typeof(HallwayWalkObjective), + typeof(ReturnSwordObjective), + typeof(SlayHenchmenObjective), + typeof(GiveEminoSwordObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + private bool m_SentRadarConversion; - public override object Name => 1063173; + public EminosUndertakingQuest(PlayerMobile from) : base(from) + { + } - public override object OfferMessage => 1063174; + // Serialization + public EminosUndertakingQuest() + { + } - public override TimeSpan RestartDelay => TimeSpan.MaxValue; - public override bool IsTutorial => true; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override int Picture => 0x15D5; + public override object Name => 1063173; - public EminosUndertakingQuest( PlayerMobile from ) : base( from ) - { - } + public override object OfferMessage => 1063174; - // Serialization - public EminosUndertakingQuest() - { - } + public override TimeSpan RestartDelay => TimeSpan.MaxValue; + public override bool IsTutorial => true; - public override void Accept() - { - base.Accept(); + public override int Picture => 0x15D5; - AddConversation( new AcceptConversation() ); - } + public override void Accept() + { + base.Accept(); - private bool m_SentRadarConversion; + AddConversation(new AcceptConversation()); + } - public override void Slice() - { - if ( !m_SentRadarConversion && ( From.Map != Map.Malas || From.X < 407 || From.X > 431 || From.Y < 801 || From.Y > 830 ) ) - { - m_SentRadarConversion = true; - AddConversation( new RadarConversation() ); - } + public override void Slice() + { + if (!m_SentRadarConversion && + (From.Map != Map.Malas || From.X < 407 || From.X > 431 || From.Y < 801 || From.Y > 830)) + { + m_SentRadarConversion = true; + AddConversation(new RadarConversation()); + } - base.Slice(); - } + base.Slice(); + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - m_SentRadarConversion = reader.ReadBool(); - } + m_SentRadarConversion = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_SentRadarConversion ); - } + writer.Write(m_SentRadarConversion); + } - public static bool HasLostNoteForZoel( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostNoteForZoel(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is EminosUndertakingQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( GiveZoelNoteObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( NoteForZoel ) ) == null ); - } - } + if (qs is EminosUndertakingQuest) + if (qs.IsObjectiveInProgress(typeof(GiveZoelNoteObjective))) + return from.Backpack?.FindItemByType(typeof(NoteForZoel)) == null; - return false; - } + return false; + } - public static bool HasLostEminosKatana( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostEminosKatana(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is EminosUndertakingQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( GiveEminoSwordObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( EminosKatana ) ) == null ); - } - } + if (qs is EminosUndertakingQuest) + if (qs.IsObjectiveInProgress(typeof(GiveEminoSwordObjective))) + return from.Backpack?.FindItemByType(typeof(EminosKatana)) == null; - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/BlueNinjaQuestTeleporter.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/BlueNinjaQuestTeleporter.cs index 40f85a506..1932f200a 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/BlueNinjaQuestTeleporter.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/BlueNinjaQuestTeleporter.cs @@ -2,48 +2,48 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class BlueNinjaQuestTeleporter : DynamicTeleporter - { - public override int LabelNumber => 1026157; // teleporter + public class BlueNinjaQuestTeleporter : DynamicTeleporter + { + [Constructible] + public BlueNinjaQuestTeleporter() : base(0x51C, 0x2) + { + } - [Constructible] - public BlueNinjaQuestTeleporter() : base( 0x51C, 0x2 ) - { - } + public BlueNinjaQuestTeleporter(Serial serial) : base(serial) + { + } - public override int NotWorkingMessage => 1063198; // You stand on the strange floor tile but nothing happens. + public override int LabelNumber => 1026157; // teleporter - public override bool GetDestination( PlayerMobile player, ref Point3D loc, ref Map map ) - { - QuestSystem qs = player.Quest; + public override int NotWorkingMessage => 1063198; // You stand on the strange floor tile but nothing happens. - if ( qs is EminosUndertakingQuest && qs.FindObjective( typeof( GainInnInformationObjective ) ) != null ) - { - loc = new Point3D( 411, 1116, 0 ); - map = Map.Malas; + public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map) + { + QuestSystem qs = player.Quest; - return true; - } + if (qs is EminosUndertakingQuest && qs.FindObjective(typeof(GainInnInformationObjective)) != null) + { + loc = new Point3D(411, 1116, 0); + map = Map.Malas; - return false; - } + return true; + } - public BlueNinjaQuestTeleporter( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatana.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatana.cs index eded87354..b89c5e14c 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatana.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatana.cs @@ -2,41 +2,41 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class EminosKatana : QuestItem - { - public override int LabelNumber => 1063214; // Daimyo Emino's Katana + public class EminosKatana : QuestItem + { + [Constructible] + public EminosKatana() : base(0x13FF) + { + Weight = 1.0; + } - [Constructible] - public EminosKatana() : base( 0x13FF ) - { - Weight = 1.0; - } + public EminosKatana(Serial serial) : base(serial) + { + } - public EminosKatana( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063214; // Daimyo Emino's Katana - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is EminosUndertakingQuest); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is EminosUndertakingQuest); - /*return !qs.IsObjectiveInProgress( typeof( ReturnSwordObjective ) ) - && !qs.IsObjectiveInProgress( typeof( SlayHenchmenObjective ) ) - && !qs.IsObjectiveInProgress( typeof( GiveEminoSwordObjective ) );*/ - } + /*return !qs.IsObjectiveInProgress( typeof( ReturnSwordObjective ) ) + && !qs.IsObjectiveInProgress( typeof( SlayHenchmenObjective ) ) + && !qs.IsObjectiveInProgress( typeof( GiveEminoSwordObjective ) );*/ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatanaChest.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatanaChest.cs index 53ec9a9ae..c4ea46d37 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatanaChest.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/EminosKatanaChest.cs @@ -4,133 +4,136 @@ using Server.Network; namespace Server.Engines.Quests.Ninja { - public class EminosKatanaChest : WoodenChest - { - [Constructible] - public EminosKatanaChest() - { - Movable = false; - ItemID = 0xE42; + public class EminosKatanaChest : WoodenChest + { + [Constructible] + public EminosKatanaChest() + { + Movable = false; + ItemID = 0xE42; - GenerateTreasure(); - } + GenerateTreasure(); + } - public EminosKatanaChest( Serial serial ) : base( serial ) - { - } + public EminosKatanaChest(Serial serial) : base(serial) + { + } - public override bool IsDecoContainer => false; + public override bool IsDecoContainer => false; - private void GenerateTreasure() - { - for ( int i = Items.Count - 1; i >= 0; i-- ) - Items[i].Delete(); + private void GenerateTreasure() + { + for (int i = Items.Count - 1; i >= 0; i--) + Items[i].Delete(); - for ( int i = 0; i < 75; i++ ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: DropItem( new GoldBracelet() ); break; - case 1: DropItem( new GoldRing() ); break; - case 2: DropItem( Loot.RandomGem() ); break; - } - } - } + for (int i = 0; i < 75; i++) + switch (Utility.Random(3)) + { + case 0: + DropItem(new GoldBracelet()); + break; + case 1: + DropItem(new GoldRing()); + break; + case 2: + DropItem(Loot.RandomGem()); + break; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( from is PlayerMobile player && player.InRange( GetWorldLocation(), 2 ) ) - { - QuestSystem qs = player.Quest; + public override void OnDoubleClick(Mobile from) + { + if (from is PlayerMobile player && player.InRange(GetWorldLocation(), 2)) + { + QuestSystem qs = player.Quest; - if ( qs is EminosUndertakingQuest ) - { - if ( EminosUndertakingQuest.HasLostEminosKatana( from ) ) - { - Item katana = new EminosKatana(); + if (qs is EminosUndertakingQuest) + { + if (EminosUndertakingQuest.HasLostEminosKatana(from)) + { + Item katana = new EminosKatana(); - if ( !player.PlaceInBackpack( katana ) ) - { - katana.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - else - { - QuestObjective obj = qs.FindObjective( typeof( HallwayWalkObjective ) ); + if (!player.PlaceInBackpack(katana)) + { + katana.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + else + { + QuestObjective obj = qs.FindObjective(typeof(HallwayWalkObjective)); - if ( obj != null && !obj.Completed ) - { - Item katana = new EminosKatana(); + if (obj != null && !obj.Completed) + { + Item katana = new EminosKatana(); - if ( player.PlaceInBackpack( katana ) ) - { - GenerateTreasure(); - obj.Complete(); - } - else - { - katana.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - } - } - } + if (player.PlaceInBackpack(katana)) + { + GenerateTreasure(); + obj.Complete(); + } + else + { + katana.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + } + } + } - base.OnDoubleClick( from ); - } + base.OnDoubleClick(from); + } - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - return false; - } + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + return false; + } - public override bool CheckItemUse( Mobile from, Item item ) - { - return item == this; - } + public override bool CheckItemUse(Mobile from, Item item) + { + return item == this; + } - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; - if ( from is PlayerMobile player && player.Quest is EminosUndertakingQuest ) - { - if ( player.Quest.FindObjective( typeof( HallwayWalkObjective ) ) is HallwayWalkObjective obj ) - { - if ( obj.StolenTreasure ) - from.SendLocalizedMessage( 1063247 ); // The guard is watching you carefully! It would be unwise to remove another item from here. - else - return true; - } - } + if (from is PlayerMobile player && player.Quest is EminosUndertakingQuest) + if (player.Quest.FindObjective(typeof(HallwayWalkObjective)) is HallwayWalkObjective obj) + { + if (obj.StolenTreasure) + from.SendLocalizedMessage( + 1063247); // The guard is watching you carefully! It would be unwise to remove another item from here. + else + return true; + } - return false; - } + return false; + } - public override void OnItemLifted( Mobile from, Item item ) - { - if ( from is PlayerMobile player && player.Quest is EminosUndertakingQuest ) - { - if ( player.Quest.FindObjective( typeof( HallwayWalkObjective ) ) is HallwayWalkObjective obj ) - obj.StolenTreasure = true; - } - } + public override void OnItemLifted(Mobile from, Item item) + { + if (from is PlayerMobile player && player.Quest is EminosUndertakingQuest) + if (player.Quest.FindObjective(typeof(HallwayWalkObjective)) is HallwayWalkObjective obj) + obj.StolenTreasure = true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/GreenNinjaQuestTeleporter.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/GreenNinjaQuestTeleporter.cs index edd1a42e9..08a4ed0d2 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/GreenNinjaQuestTeleporter.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/GreenNinjaQuestTeleporter.cs @@ -2,48 +2,48 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class GreenNinjaQuestTeleporter : DynamicTeleporter - { - public override int LabelNumber => 1026157; // teleporter + public class GreenNinjaQuestTeleporter : DynamicTeleporter + { + [Constructible] + public GreenNinjaQuestTeleporter() : base(0x51C, 0x17E) + { + } - [Constructible] - public GreenNinjaQuestTeleporter() : base( 0x51C, 0x17E ) - { - } + public GreenNinjaQuestTeleporter(Serial serial) : base(serial) + { + } - public override int NotWorkingMessage => 1063198; // You stand on the strange floor tile but nothing happens. + public override int LabelNumber => 1026157; // teleporter - public override bool GetDestination( PlayerMobile player, ref Point3D loc, ref Map map ) - { - QuestSystem qs = player.Quest; + public override int NotWorkingMessage => 1063198; // You stand on the strange floor tile but nothing happens. - if ( qs is EminosUndertakingQuest && qs.FindObjective( typeof( UseTeleporterObjective ) ) != null ) - { - loc = new Point3D( 410, 1125, 0 ); - map = Map.Malas; + public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map) + { + QuestSystem qs = player.Quest; - return true; - } + if (qs is EminosUndertakingQuest && qs.FindObjective(typeof(UseTeleporterObjective)) != null) + { + loc = new Point3D(410, 1125, 0); + map = Map.Malas; - return false; - } + return true; + } - public GreenNinjaQuestTeleporter( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/GuardianBarrier.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/GuardianBarrier.cs index bac072b91..41f967fd7 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/GuardianBarrier.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/GuardianBarrier.cs @@ -2,69 +2,65 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class GuardianBarrier : Item - { - [Constructible] - public GuardianBarrier() : base( 0x3967 ) - { - Movable = false; - Visible = false; - } + public class GuardianBarrier : Item + { + [Constructible] + public GuardianBarrier() : base(0x3967) + { + Movable = false; + Visible = false; + } - public override bool OnMoveOver( Mobile m ) - { - if ( m.AccessLevel > AccessLevel.Player ) - return true; + public GuardianBarrier(Serial serial) : base(serial) + { + } - // If the mobile is to the north of the barrier, allow him to pass - if ( Y >= m.Y ) - return true; + public override bool OnMoveOver(Mobile m) + { + if (m.AccessLevel > AccessLevel.Player) + return true; - if ( m is BaseCreature creature ) - { - Mobile master = creature.GetMaster(); + // If the mobile is to the north of the barrier, allow him to pass + if (Y >= m.Y) + return true; - // Allow creatures to cross from the south to the north only if their master is near to the north - return master != null && Y >= master.Y && master.InRange(this, 4); - } + if (m is BaseCreature creature) + { + Mobile master = creature.GetMaster(); - if ( m is PlayerMobile pm ) - { - if ( pm.Quest is EminosUndertakingQuest qs ) - { - if ( qs.FindObjective( typeof( SneakPastGuardiansObjective ) ) is SneakPastGuardiansObjective obj ) - { - if ( m.Hidden ) - return true; // Hidden ninjas can pass + // Allow creatures to cross from the south to the north only if their master is near to the north + return master != null && Y >= master.Y && master.InRange(this, 4); + } - if ( !obj.TaughtHowToUseSkills ) - { - obj.TaughtHowToUseSkills = true; - qs.AddConversation( new NeedToHideConversation() ); - } - } - } - } + if (m is PlayerMobile pm) + if (pm.Quest is EminosUndertakingQuest qs) + if (qs.FindObjective(typeof(SneakPastGuardiansObjective)) is SneakPastGuardiansObjective obj) + { + if (m.Hidden) + return true; // Hidden ninjas can pass - return false; - } + if (!obj.TaughtHowToUseSkills) + { + obj.TaughtHowToUseSkills = true; + qs.AddConversation(new NeedToHideConversation()); + } + } - public GuardianBarrier( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/NoteForZoel.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/NoteForZoel.cs index bded4081b..aee939141 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/NoteForZoel.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/NoteForZoel.cs @@ -2,40 +2,40 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class NoteForZoel : QuestItem - { - public override int LabelNumber => 1063186; // A Note for Zoel + public class NoteForZoel : QuestItem + { + [Constructible] + public NoteForZoel() : base(0x14EF) + { + Weight = 1.0; + Hue = 0x6B9; + } - [Constructible] - public NoteForZoel() : base( 0x14EF ) - { - Weight = 1.0; - Hue = 0x6B9; - } + public NoteForZoel(Serial serial) : base(serial) + { + } - public NoteForZoel( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063186; // A Note for Zoel - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is EminosUndertakingQuest); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is EminosUndertakingQuest); - //return !qs.IsObjectiveInProgress( typeof( GiveZoelNoteObjective ) ); - } + //return !qs.IsObjectiveInProgress( typeof( GiveZoelNoteObjective ) ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Items/WhiteNinjaQuestTeleporter.cs b/Scripts/Engines/Quests/Emino's Undertaking/Items/WhiteNinjaQuestTeleporter.cs index 40f87fd05..688b16c05 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Items/WhiteNinjaQuestTeleporter.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Items/WhiteNinjaQuestTeleporter.cs @@ -2,56 +2,56 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class WhiteNinjaQuestTeleporter : DynamicTeleporter - { - public override int LabelNumber => 1026157; // teleporter + public class WhiteNinjaQuestTeleporter : DynamicTeleporter + { + [Constructible] + public WhiteNinjaQuestTeleporter() : base(0x51C, 0x47E) + { + } - [Constructible] - public WhiteNinjaQuestTeleporter() : base( 0x51C, 0x47E ) - { - } + public WhiteNinjaQuestTeleporter(Serial serial) : base(serial) + { + } - public override int NotWorkingMessage => 1063198; // You stand on the strange floor tile but nothing happens. + public override int LabelNumber => 1026157; // teleporter - public override bool GetDestination( PlayerMobile player, ref Point3D loc, ref Map map ) - { - QuestSystem qs = player.Quest; + public override int NotWorkingMessage => 1063198; // You stand on the strange floor tile but nothing happens. - if ( qs is EminosUndertakingQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SearchForSwordObjective ) ); + public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map) + { + QuestSystem qs = player.Quest; - if ( obj != null ) - { - if ( !obj.Completed ) - obj.Complete(); + if (qs is EminosUndertakingQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SearchForSwordObjective)); - loc = new Point3D( 411, 1085, 0 ); - map = Map.Malas; + if (obj != null) + { + if (!obj.Completed) + obj.Complete(); - return true; - } - } + loc = new Point3D(411, 1085, 0); + map = Map.Malas; - return false; - } + return true; + } + } - public WhiteNinjaQuestTeleporter( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Emino.cs b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Emino.cs index 5f6ad78d9..40aae7830 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Emino.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Emino.cs @@ -1,225 +1,229 @@ -using Server.Mobiles; using Server.Gumps; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class Emino : BaseQuester - { - public override string DefaultName => "Daimyo Emino"; + public class Emino : BaseQuester + { + [Constructible] + public Emino() : base("the Notorious") + { + } - [Constructible] - public Emino() : base( "the Notorious" ) - { - } + public Emino(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Daimyo Emino"; - Hue = 0x83FE; + public override int TalkNumber => -1; - Female = false; - Body = 0x190; - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override void InitOutfit() - { - HairItemID = 0x203B; - HairHue = 0x901; + Hue = 0x83FE; - AddItem( new MaleKimono() ); - AddItem( new SamuraiTabi() ); - AddItem( new Bandana() ); + Female = false; + Body = 0x190; + } - AddItem( new PlateHaidate() ); - AddItem( new PlateDo() ); - AddItem( new PlateHiroSode() ); + public override void InitOutfit() + { + HairItemID = 0x203B; + HairHue = 0x901; - Nunchaku nunchaku = new Nunchaku(); - nunchaku.Movable = false; - AddItem( nunchaku ); - } + AddItem(new MaleKimono()); + AddItem(new SamuraiTabi()); + AddItem(new Bandana()); - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 2; - } + AddItem(new PlateHaidate()); + AddItem(new PlateDo()); + AddItem(new PlateHiroSode()); - public override int TalkNumber => -1; + Nunchaku nunchaku = new Nunchaku(); + nunchaku.Movable = false; + AddItem(nunchaku); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 2; + } - if ( qs is EminosUndertakingQuest ) - { - if ( EminosUndertakingQuest.HasLostNoteForZoel( player ) ) - { - Item note = new NoteForZoel(); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( player.PlaceInBackpack( note ) ) - { - qs.AddConversation( new LostNoteConversation() ); - } - else - { - note.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - else if ( EminosUndertakingQuest.HasLostEminosKatana( player ) ) - { - qs.AddConversation( new LostSwordConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( FindEminoBeginObjective ) ); + if (qs is EminosUndertakingQuest) + { + if (EminosUndertakingQuest.HasLostNoteForZoel(player)) + { + Item note = new NoteForZoel(); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else - { - obj = qs.FindObjective( typeof( UseTeleporterObjective ) ); + if (player.PlaceInBackpack(note)) + { + qs.AddConversation(new LostNoteConversation()); + } + else + { + note.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + else if (EminosUndertakingQuest.HasLostEminosKatana(player)) + { + qs.AddConversation(new LostSwordConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(FindEminoBeginObjective)); - if ( obj != null && !obj.Completed ) - { - Item note = new NoteForZoel(); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else + { + obj = qs.FindObjective(typeof(UseTeleporterObjective)); - if ( player.PlaceInBackpack( note ) ) - { - obj.Complete(); + if (obj != null && !obj.Completed) + { + Item note = new NoteForZoel(); - player.AddToBackpack( new LeatherNinjaPants() ); - player.AddToBackpack( new LeatherNinjaMitts() ); - } - else - { - note.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - else - { - obj = qs.FindObjective( typeof( ReturnFromInnObjective ) ); + if (player.PlaceInBackpack(note)) + { + obj.Complete(); - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + player.AddToBackpack(new LeatherNinjaPants()); + player.AddToBackpack(new LeatherNinjaMitts()); + } + else + { + note.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + else + { + obj = qs.FindObjective(typeof(ReturnFromInnObjective)); - for ( int i = 0; i < 10; i++ ) - cont.DropItem( new LesserHealPotion() ); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - cont.DropItem( new LeatherNinjaHood() ); - cont.DropItem( new LeatherNinjaJacket() ); + for (int i = 0; i < 10; i++) + cont.DropItem(new LesserHealPotion()); - if ( player.PlaceInBackpack( cont ) ) - { - obj.Complete(); - } - else - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - else - { - if ( qs.IsObjectiveInProgress( typeof( SlayHenchmenObjective ) ) ) - { - qs.AddConversation( new ContinueSlayHenchmenConversation() ); - } - else - { - obj = qs.FindObjective( typeof( GiveEminoSwordObjective ) ); + cont.DropItem(new LeatherNinjaHood()); + cont.DropItem(new LeatherNinjaJacket()); - if ( obj != null && !obj.Completed ) - { - Item katana = null; + if (player.PlaceInBackpack(cont)) + { + obj.Complete(); + } + else + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + else + { + if (qs.IsObjectiveInProgress(typeof(SlayHenchmenObjective))) + { + qs.AddConversation(new ContinueSlayHenchmenConversation()); + } + else + { + obj = qs.FindObjective(typeof(GiveEminoSwordObjective)); - if ( player.Backpack != null ) - katana = player.Backpack.FindItemByType( typeof( EminosKatana ) ); + if (obj != null && !obj.Completed) + { + Item katana = null; - if ( katana != null ) - { - bool stolenTreasure = false; + if (player.Backpack != null) + katana = player.Backpack.FindItemByType(typeof(EminosKatana)); - if ( qs.FindObjective( typeof( HallwayWalkObjective ) ) is HallwayWalkObjective walk ) - stolenTreasure = walk.StolenTreasure; + if (katana != null) + { + bool stolenTreasure = false; - Kama kama = new Kama(); + if (qs.FindObjective(typeof(HallwayWalkObjective)) is HallwayWalkObjective walk) + stolenTreasure = walk.StolenTreasure; - if ( stolenTreasure ) - BaseRunicTool.ApplyAttributesTo( kama, 1, 10, 20 ); - else - BaseRunicTool.ApplyAttributesTo( kama, 1, 10, 30 ); + Kama kama = new Kama(); - if ( player.PlaceInBackpack( kama ) ) - { - katana.Delete(); - obj.Complete(); + if (stolenTreasure) + BaseRunicTool.ApplyAttributesTo(kama, 1, 10, 20); + else + BaseRunicTool.ApplyAttributesTo(kama, 1, 10, 30); - if ( stolenTreasure ) - qs.AddConversation( new EarnLessGiftsConversation() ); - else - qs.AddConversation( new EarnGiftsConversation() ); - } - else - { - kama.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - } - } - } - } - } - } - } - } + if (player.PlaceInBackpack(kama)) + { + katana.Delete(); + obj.Complete(); - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + if (stolenTreasure) + qs.AddConversation(new EarnLessGiftsConversation()); + else + qs.AddConversation(new EarnGiftsConversation()); + } + else + { + kama.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + } + } + } + } + } + } + } + } - if ( !m.Frozen && !m.Alive && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && InLOS( m ) ) - { - if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else - { - Direction = GetDirectionTo( m ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + if (!m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m)) + { + if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + else + { + Direction = GetDirectionTo(m); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.Healer ) ); - } - } - } + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - public Emino( Serial serial ) : base( serial ) - { - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer)); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/EnshroudedFigure.cs b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/EnshroudedFigure.cs index 2215384be..5240c6cbe 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/EnshroudedFigure.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/EnshroudedFigure.cs @@ -1,54 +1,54 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class EnshroudedFigure : BaseQuester - { - public override string DefaultName => "an enshrouded figure"; + public class EnshroudedFigure : BaseQuester + { + [Constructible] + public EnshroudedFigure() + { + } - [Constructible] - public EnshroudedFigure() - { - } + public EnshroudedFigure(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "an enshrouded figure"; - Hue = 0x8401; - Female = false; - Body = 0x190; - } + public override int TalkNumber => -1; - public override void InitOutfit() - { - AddItem( new DeathShroud() ); - AddItem( new ThighBoots() ); - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override int TalkNumber => -1; + Hue = 0x8401; + Female = false; + Body = 0x190; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } + public override void InitOutfit() + { + AddItem(new DeathShroud()); + AddItem(new ThighBoots()); + } - public EnshroudedFigure( Serial serial ) : base( serial ) - { - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Henchman.cs b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Henchman.cs index fb419ac3e..0549f5bc0 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Henchman.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Henchman.cs @@ -1,54 +1,54 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class Henchman : BaseCreature - { - public override string DefaultName => "a henchman"; + public class Henchman : BaseCreature + { + [Constructible] + public Henchman() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + InitStats(45, 30, 5); - [Constructible] - public Henchman() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - InitStats( 45, 30, 5 ); + Hue = Utility.RandomSkinHue(); + Body = 0x190; - Hue = Utility.RandomSkinHue(); - Body = 0x190; + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this ); + AddItem(new LeatherNinjaJacket()); + AddItem(new LeatherNinjaPants()); + AddItem(new NinjaTabi()); - AddItem( new LeatherNinjaJacket() ); - AddItem( new LeatherNinjaPants() ); - AddItem( new NinjaTabi() ); + if (Utility.RandomBool()) + AddItem(new Kama()); + else + AddItem(new Tessen()); - if ( Utility.RandomBool() ) - AddItem( new Kama() ); - else - AddItem( new Tessen() ); + SetSkill(SkillName.Swords, 50.0); + SetSkill(SkillName.Tactics, 50.0); + } - SetSkill( SkillName.Swords, 50.0 ); - SetSkill( SkillName.Tactics, 50.0 ); - } + public Henchman(Serial serial) : base(serial) + { + } - public override bool AlwaysMurderer => true; + public override string DefaultName => "a henchman"; - public Henchman( Serial serial ) : base( serial ) - { - } + public override bool AlwaysMurderer => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/HiddenFigure.cs b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/HiddenFigure.cs index df15a6997..ea2f34ed1 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/HiddenFigure.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/HiddenFigure.cs @@ -1,91 +1,92 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; using Server.Network; namespace Server.Engines.Quests.Ninja { - public class HiddenFigure : BaseQuester - { - public static int[] Messages = { - 1063191, // They won�t find me here. - 1063192 // Ah, a quiet hideout. - }; + public class HiddenFigure : BaseQuester + { + public static int[] Messages = + { + 1063191, // They won�t find me here. + 1063192 // Ah, a quiet hideout. + }; - [CommandProperty( AccessLevel.GameMaster )] - public int Message { get; set; } + [Constructible] + public HiddenFigure() + { + Message = Utility.RandomList(Messages); + } - [Constructible] - public HiddenFigure() - { - Message = Utility.RandomList( Messages ); - } + public HiddenFigure(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + [CommandProperty(AccessLevel.GameMaster)] + public int Message{ get; set; } - Hue = Utility.RandomSkinHue(); + public override int TalkNumber => -1; - Female = Utility.RandomBool(); + public override void InitBody() + { + InitStats(100, 100, 25); - if ( Female ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } - } + Hue = Utility.RandomSkinHue(); - public override void InitOutfit() - { - Utility.AssignRandomHair( this ); + Female = Utility.RandomBool(); - AddItem( new TattsukeHakama( GetRandomHue() ) ); - AddItem( new Kasa() ); - AddItem( new HakamaShita( GetRandomHue() ) ); + if (Female) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } + } - if ( Utility.RandomBool() ) - AddItem( new Shoes( GetShoeHue() ) ); - else - AddItem( new Sandals( GetShoeHue() ) ); - } + public override void InitOutfit() + { + Utility.AssignRandomHair(this); - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 3; - } + AddItem(new TattsukeHakama(GetRandomHue())); + AddItem(new Kasa()); + AddItem(new HakamaShita(GetRandomHue())); - public override int TalkNumber => -1; + if (Utility.RandomBool()) + AddItem(new Shoes(GetShoeHue())); + else + AddItem(new Sandals(GetShoeHue())); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - PrivateOverheadMessage( MessageType.Regular, 0x3B2, Message, player.NetState ); - } + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 3; + } - public HiddenFigure( Serial serial ) : base( serial ) - { - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + PrivateOverheadMessage(MessageType.Regular, 0x3B2, Message, player.NetState); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (int) Message ); - } + writer.Write(Message); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Message = reader.ReadInt(); - } - } -} + Message = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/JedahEntille.cs b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/JedahEntille.cs index a567394b8..1a79c4f3d 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/JedahEntille.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/JedahEntille.cs @@ -1,58 +1,58 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class JedahEntille : BaseQuester - { - public override string DefaultName => "Jedah Entille"; + public class JedahEntille : BaseQuester + { + [Constructible] + public JedahEntille() : base("the Silent") + { + } - [Constructible] - public JedahEntille() : base( "the Silent" ) - { - } + public JedahEntille(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Jedah Entille"; - Hue = 0x83FE; - Female = true; - Body = 0x191; - } + public override int TalkNumber => -1; - public override void InitOutfit() - { - HairItemID = 0x203C; - HairHue = 0x6BE; + public override void InitBody() + { + InitStats(100, 100, 25); - AddItem( new PlainDress( 0x528 ) ); - AddItem( new ThighBoots() ); - AddItem( new FloppyHat() ); - } + Hue = 0x83FE; + Female = true; + Body = 0x191; + } - public override int TalkNumber => -1; + public override void InitOutfit() + { + HairItemID = 0x203C; + HairHue = 0x6BE; - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } + AddItem(new PlainDress(0x528)); + AddItem(new ThighBoots()); + AddItem(new FloppyHat()); + } - public JedahEntille( Serial serial ) : base( serial ) - { - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Zoel.cs b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Zoel.cs index ca2751a70..780584f51 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Zoel.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Mobiles/Zoel.cs @@ -1,134 +1,132 @@ -using Server.Mobiles; -using Server.Items; using Server.Gumps; +using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class Zoel : BaseQuester - { - public override string DefaultName => "Elite Ninja Zoel"; + public class Zoel : BaseQuester + { + [Constructible] + public Zoel() : base("the Masterful Tactician") + { + } - [Constructible] - public Zoel() : base( "the Masterful Tactician" ) - { - } + public Zoel(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Elite Ninja Zoel"; - Hue = 0x83FE; + public override int TalkNumber => -1; - Female = false; - Body = 0x190; - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override void InitOutfit() - { - HairItemID = 0x203B; - HairHue = 0x901; + Hue = 0x83FE; - AddItem( new HakamaShita( 0x1 ) ); - AddItem( new NinjaTabi() ); - AddItem( new TattsukeHakama() ); - AddItem( new Bandana() ); + Female = false; + Body = 0x190; + } - AddItem( new LeatherNinjaBelt() ); + public override void InitOutfit() + { + HairItemID = 0x203B; + HairHue = 0x901; - Tekagi tekagi = new Tekagi(); - tekagi.Movable = false; - AddItem( tekagi ); - } + AddItem(new HakamaShita(0x1)); + AddItem(new NinjaTabi()); + AddItem(new TattsukeHakama()); + AddItem(new Bandana()); - public override int TalkNumber => -1; + AddItem(new LeatherNinjaBelt()); - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 2; - } + Tekagi tekagi = new Tekagi(); + tekagi.Movable = false; + AddItem(tekagi); + } - public override bool CanTalkTo( PlayerMobile to ) - { - return to.Quest is EminosUndertakingQuest; - } + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 2; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override bool CanTalkTo(PlayerMobile to) + { + return to.Quest is EminosUndertakingQuest; + } - if ( qs is EminosUndertakingQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( FindZoelObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - } + if (qs is EminosUndertakingQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FindZoelObjective)); - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + if (obj != null && !obj.Completed) + obj.Complete(); + } + } - if ( qs is EminosUndertakingQuest ) - { - if ( dropped is NoteForZoel ) - { - QuestObjective obj = qs.FindObjective( typeof( GiveZoelNoteObjective ) ); + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - { - dropped.Delete(); - obj.Complete(); - return true; - } - } - } - } + if (qs is EminosUndertakingQuest) + if (dropped is NoteForZoel) + { + QuestObjective obj = qs.FindObjective(typeof(GiveZoelNoteObjective)); - return base.OnDragDrop( from, dropped ); - } + if (obj != null && !obj.Completed) + { + dropped.Delete(); + obj.Complete(); + return true; + } + } + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + return base.OnDragDrop(from, dropped); + } - if ( !m.Frozen && !m.Alive && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && InLOS( m ) ) - { - if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else - { - Direction = GetDirectionTo( m ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + if (!m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m)) + { + if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + else + { + Direction = GetDirectionTo(m); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.Healer ) ); - } - } - } + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - public Zoel( Serial serial ) : base( serial ) - { - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer)); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Emino's Undertaking/Objectives.cs b/Scripts/Engines/Quests/Emino's Undertaking/Objectives.cs index 5a49a7f28..ebbba836c 100644 --- a/Scripts/Engines/Quests/Emino's Undertaking/Objectives.cs +++ b/Scripts/Engines/Quests/Emino's Undertaking/Objectives.cs @@ -3,268 +3,216 @@ using Server.Mobiles; namespace Server.Engines.Quests.Ninja { - public class FindEminoBeginObjective : QuestObjective - { - public override object Message => 1063174; + public class FindEminoBeginObjective : QuestObjective + { + public override object Message => 1063174; - public FindEminoBeginObjective() - { - } + public override void OnComplete() + { + System.AddConversation(new FindZoelConversation()); + } + } - public override void OnComplete() - { - System.AddConversation( new FindZoelConversation() ); - } - } + public class FindZoelObjective : QuestObjective + { + public override object Message => 1063176; - public class FindZoelObjective : QuestObjective - { - public override object Message => 1063176; + public override void OnComplete() + { + System.AddConversation(new EnterCaveConversation()); + } + } - public FindZoelObjective() - { - } + public class EnterCaveObjective : QuestObjective + { + public override object Message => 1063179; - public override void OnComplete() - { - System.AddConversation( new EnterCaveConversation() ); - } - } + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(406, 1141, 0), 2)) + Complete(); + } - public class EnterCaveObjective : QuestObjective - { - public override object Message => 1063179; + public override void OnComplete() + { + System.AddConversation(new SneakPastGuardiansConversation()); + } + } - public EnterCaveObjective() - { - } + public class SneakPastGuardiansObjective : QuestObjective + { + public bool TaughtHowToUseSkills{ get; set; } - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 406, 1141, 0 ), 2 ) ) - Complete(); - } + public override object Message => 1063261; - public override void OnComplete() - { - System.AddConversation( new SneakPastGuardiansConversation() ); - } - } + public override void CheckProgress() + { + if (System.From.Map == Map.Malas && System.From.InRange(new Point3D(412, 1123, 0), 3)) + Complete(); + } - public class SneakPastGuardiansObjective : QuestObjective - { - public bool TaughtHowToUseSkills { get; set; } + public override void OnComplete() + { + System.AddConversation(new UseTeleporterConversation()); + } - public override object Message => 1063261; + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public SneakPastGuardiansObjective() - { - } + TaughtHowToUseSkills = reader.ReadBool(); + } - public override void CheckProgress() - { - if ( System.From.Map == Map.Malas && System.From.InRange( new Point3D( 412, 1123, 0 ), 3 ) ) - Complete(); - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public override void OnComplete() - { - System.AddConversation( new UseTeleporterConversation() ); - } + writer.Write(TaughtHowToUseSkills); + } + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public class UseTeleporterObjective : QuestObjective + { + public override object Message => 1063183; - TaughtHowToUseSkills = reader.ReadBool(); - } + public override void OnComplete() + { + System.AddConversation(new GiveZoelNoteConversation()); + } + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public class GiveZoelNoteObjective : QuestObjective + { + public override object Message => 1063185; - writer.Write( (bool) TaughtHowToUseSkills ); - } - } + public override void OnComplete() + { + System.AddConversation(new GainInnInformationConversation()); + } + } - public class UseTeleporterObjective : QuestObjective - { - public override object Message => 1063183; + public class GainInnInformationObjective : QuestObjective + { + public override object Message => 1063190; - public UseTeleporterObjective() - { - } + public override void CheckProgress() + { + Mobile from = System.From; - public override void OnComplete() - { - System.AddConversation( new GiveZoelNoteConversation() ); - } - } + if (from.Map == Map.Malas && from.X > 399 && from.X < 408 && from.Y > 1091 && from.Y < 1099) + Complete(); + } - public class GiveZoelNoteObjective : QuestObjective - { - public override object Message => 1063185; + public override void OnComplete() + { + System.AddConversation(new ReturnFromInnConversation()); + } + } - public GiveZoelNoteObjective() - { - } + public class ReturnFromInnObjective : QuestObjective + { + public override object Message => 1063197; - public override void OnComplete() - { - System.AddConversation( new GainInnInformationConversation() ); - } - } + public override void OnComplete() + { + System.AddConversation(new SearchForSwordConversation()); + } + } - public class GainInnInformationObjective : QuestObjective - { - public override object Message => 1063190; + public class SearchForSwordObjective : QuestObjective + { + public override object Message => 1063200; - public GainInnInformationObjective() - { - } + public override void OnComplete() + { + System.AddConversation(new HallwayWalkConversation()); + } + } - public override void CheckProgress() - { - Mobile from = System.From; + public class HallwayWalkObjective : QuestObjective + { + public bool StolenTreasure{ get; set; } - if ( from.Map == Map.Malas && from.X > 399 && from.X < 408 && from.Y > 1091 && from.Y < 1099 ) - Complete(); - } + public override object Message => 1063202; - public override void OnComplete() - { - System.AddConversation( new ReturnFromInnConversation() ); - } - } + public override void OnComplete() + { + System.AddConversation(new ReturnSwordConversation()); + } - public class ReturnFromInnObjective : QuestObjective - { - public override object Message => 1063197; + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public ReturnFromInnObjective() - { - } + StolenTreasure = reader.ReadBool(); + } - public override void OnComplete() - { - System.AddConversation( new SearchForSwordConversation() ); - } - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public class SearchForSwordObjective : QuestObjective - { - public override object Message => 1063200; + writer.Write(StolenTreasure); + } + } - public SearchForSwordObjective() - { - } + public class ReturnSwordObjective : QuestObjective + { + public override object Message => 1063204; - public override void OnComplete() - { - System.AddConversation( new HallwayWalkConversation() ); - } - } + public override void CheckProgress() + { + Mobile from = System.From; - public class HallwayWalkObjective : QuestObjective - { - public bool StolenTreasure { get; set; } + if (from.Map != Map.Malas || from.Y > 992) + Complete(); + } - public override object Message => 1063202; + public override void OnComplete() + { + System.AddConversation(new SlayHenchmenConversation()); + } + } - public HallwayWalkObjective() - { - } + public class SlayHenchmenObjective : QuestObjective + { + public override object Message => 1063206; - public override void OnComplete() - { - System.AddConversation( new ReturnSwordConversation() ); - } + public override int MaxProgress => 3; - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Henchmen killed: + gump.AddHtmlLocalized(70, 260, 270, 100, 1063207, BaseQuestGump.Blue, false, false); + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, MaxProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } - StolenTreasure = reader.ReadBool(); - } + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is Henchman) + CurProgress++; + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void OnComplete() + { + System.AddConversation(new GiveEminoSwordConversation()); + } + } - writer.Write( (bool) StolenTreasure ); - } - } + public class GiveEminoSwordObjective : QuestObjective + { + public override object Message => 1063210; - public class ReturnSwordObjective : QuestObjective - { - public override object Message => 1063204; - - public ReturnSwordObjective() - { - } - - public override void CheckProgress() - { - Mobile from = System.From; - - if ( from.Map != Map.Malas || from.Y > 992 ) - Complete(); - } - - public override void OnComplete() - { - System.AddConversation( new SlayHenchmenConversation() ); - } - } - - public class SlayHenchmenObjective : QuestObjective - { - public override object Message => 1063206; - - public SlayHenchmenObjective() - { - } - - public override int MaxProgress => 3; - - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Henchmen killed: - gump.AddHtmlLocalized( 70, 260, 270, 100, 1063207, BaseQuestGump.Blue, false, false ); - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, MaxProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is Henchman ) - CurProgress++; - } - - public override void OnComplete() - { - System.AddConversation( new GiveEminoSwordConversation() ); - } - } - - public class GiveEminoSwordObjective : QuestObjective - { - public override object Message => 1063210; - - public GiveEminoSwordObjective() - { - } - - public override void OnComplete() - { - } - } -} + public override void OnComplete() + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Conversations.cs b/Scripts/Engines/Quests/Haochi's Trials/Conversations.cs index d040ed707..e32749bb8 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Conversations.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Conversations.cs @@ -1,478 +1,374 @@ namespace Server.Engines.Quests.Samurai { - public class AcceptConversation : QuestConversation - { - public override object Message => 1049092; - - public AcceptConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindHaochiObjective() ); - } - } - - public class RadarConversation : QuestConversation - { - public override object Message => 1063033; - - public override bool Logged => false; - - public RadarConversation() - { - } - } - - public class FirstTrialIntroConversation : QuestConversation - { - public override object Message => 1063029; - - public FirstTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FirstTrialIntroObjective() ); - } - } - - public class FirstTrialKillConversation : QuestConversation - { - public override object Message => 1063031; - - public FirstTrialKillConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FirstTrialKillObjective() ); - } - } - - public class GainKarmaConversation : QuestConversation - { - public override object Message - { - get - { - if ( m_CursedSoul ) - { - // You have just gained some
Karma for killing a Cursed Soul. - return 1063040; - } - - // You have just gained some Karma for killing a Young Ronin. - return 1063041; - } - } - - public override bool Logged => false; - - private bool m_CursedSoul; - - public GainKarmaConversation( bool cursedSoul ) - { - m_CursedSoul = cursedSoul; - } - - public GainKarmaConversation() - { - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_CursedSoul = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_CursedSoul ); - } - } - - public class SecondTrialIntroConversation : QuestConversation - { - public override object Message - { - get - { - if ( m_CursedSoul ) - { - /* It is good that you rid the land of the Cursed Souls so they can - * be at peace in death. They had been cursed for doing what they - * thought was an honorable deed. Now they can have respect in their death.

- * - * I have placed a reward in your pack.

- * - * The second trial will test your courage. You only have to follow the yellow - * path to see what awaits you. - */ - return 1063045; - } - - /* It is good that you rid the land of those dishonorable Samurai. - * Perhaps they will learn a greater lesson in death.

- * - * I have placed a reward in your pack.

- * - * The second trial will test your courage. You only have to follow - * the yellow path to see what awaits you. - */ - return 1063046; - } - } - - private bool m_CursedSoul; - - public SecondTrialIntroConversation( bool cursedSoul ) - { - m_CursedSoul = cursedSoul; - } - - public SecondTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new SecondTrialIntroObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_CursedSoul = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_CursedSoul ); - } - } - - public class SecondTrialAttackConversation : QuestConversation - { - public override object Message => 1063057; - - public SecondTrialAttackConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new SecondTrialAttackObjective() ); - } - } - - public class ThirdTrialIntroConversation : QuestConversation - { - public override object Message - { - get - { - if ( m_Dragon ) - { - /* You faced the dragon knowing it would be your certain death. - * That is the courage of a Samurai.

- * - * Your spirit speaks as a Samurai already.

- * - * In these lands, death is not forever. The shrines can make you whole - * again as can a helpful mage or healer.

- * - * Seek them out when you have been mortally wounded.

- * - * The next trial will test your benevolence. You only have to walk the blue path. - */ - return 1063060; - } - - /* Fear remains in your eyes but you have learned that not all is - * what it appears to be.

- * - * You must have known the dragon would slay you instantly. - * You elected the weaker opponent though the imp did not come - * here to destroy. You have much to learn.

- * - * In these lands, death is not forever. The shrines can make you whole - * again as can a helpful mage or healer.

- * - * Seek them out when you have been mortally wounded.

- * - * The next trial will test your benevolence. You only have to walk the blue path. - */ - return 1063059; - } - } - - private bool m_Dragon; - - public ThirdTrialIntroConversation( bool dragon ) - { - m_Dragon = dragon; - } - - public ThirdTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ThirdTrialIntroObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_Dragon = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_Dragon ); - } - } - - public class ThirdTrialKillConversation : QuestConversation - { - public override object Message => 1063062; - - public ThirdTrialKillConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ThirdTrialKillObjective() ); - } - } - - public class FourthTrialIntroConversation : QuestConversation - { - public override object Message => 1063065; - - public FourthTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FourthTrialIntroObjective() ); - } - } - - public class FourthTrialCatsConversation : QuestConversation - { - public override object Message => 1063067; - - public FourthTrialCatsConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FourthTrialCatsObjective() ); - } - } - - public class FifthTrialIntroConversation : QuestConversation - { - public override object Message - { - get - { - if ( m_KilledCat ) - { - /* Respect comes from allowing another to make their own decisions. - * By denying the gypsy her animals, you negate the respect she is due. - * Perhaps you will have learned something to use next time a similar - * situation arises.

- * - * And now you must prove yourself again. Please retrieve my katana - * from the treasure room and return it to me. - */ - return 1063071; - } - - /* You showed respect by helping another out while allowing the gypsy - * what little dignity she has left.

- * - * Now she will be able to feed herself and gain enough energy to walk - * to her camp.

- * - * The cats are her family members� cursed by an evil mage.

- * - * Once she has enough strength to walk back to the camp, she will be - * able to undo the spell.

- * - * You have been rewarded for completing your trial. And now you must - * prove yourself again.

Please retrieve my katana from the - * treasure room and return it to me. - */ - return 1063070; - } - } - - private bool m_KilledCat; - - public FifthTrialIntroConversation( bool killedCat ) - { - m_KilledCat = killedCat; - } - - public FifthTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FifthTrialIntroObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_KilledCat = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_KilledCat ); - } - } - - public class FifthTrialReturnConversation : QuestConversation - { - public override object Message => 1063248; - - public FifthTrialReturnConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FifthTrialReturnObjective() ); - } - } - - public class LostSwordConversation : QuestConversation - { - public override object Message => 1063074; - - public override bool Logged => false; - - public LostSwordConversation() - { - } - } - - public class SixthTrialIntroConversation : QuestConversation - { - public override object Message - { - get - { - if ( m_StolenTreasure ) - { - /* I thank you for returning this sword. However, you should admonished - * for also taking treasure that was not asked for nor given back.

- * - * Think about your actions youngling.

- * - * Your training is nearly complete. Before you have your final trial, - * you should pay homage to Samurai who came before you.

- * - * Go into the Altar Room and light a candle for them. - * Afterwards, return to me. - */ - return 1063077; - } - - /* Thank you for returning this sword to me and leaving the remaining - * treasure alone.

- * - * Your training is nearly complete. Before you have your final trial, - * you should pay homage to Samurai who came before you.

- * - * Go into the Altar Room and light a candle for them. Afterwards, return to me. - */ - return 1063076; - } - } - - private bool m_StolenTreasure; - - public SixthTrialIntroConversation( bool stolenTreasure ) - { - m_StolenTreasure = stolenTreasure; - } - - public SixthTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new SixthTrialIntroObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_StolenTreasure = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_StolenTreasure ); - } - } - - public class SeventhTrialIntroConversation : QuestConversation - { - public override object Message => 1063079; - - public SeventhTrialIntroConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new SeventhTrialIntroObjective() ); - } - } - - public class EndConversation : QuestConversation - { - public override object Message => 1063125; - - public EndConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } -} + public class AcceptConversation : QuestConversation + { + public override object Message => 1049092; + + public override void OnRead() + { + System.AddObjective(new FindHaochiObjective()); + } + } + + public class RadarConversation : QuestConversation + { + public override object Message => 1063033; + + public override bool Logged => false; + } + + public class FirstTrialIntroConversation : QuestConversation + { + public override object Message => 1063029; + + public override void OnRead() + { + System.AddObjective(new FirstTrialIntroObjective()); + } + } + + public class FirstTrialKillConversation : QuestConversation + { + public override object Message => 1063031; + + public override void OnRead() + { + System.AddObjective(new FirstTrialKillObjective()); + } + } + + public class GainKarmaConversation : QuestConversation + { + private bool m_CursedSoul; + + public GainKarmaConversation(bool cursedSoul) + { + m_CursedSoul = cursedSoul; + } + + public GainKarmaConversation() + { + } + + public override object Message + { + get + { + if (m_CursedSoul) return 1063040; + + // You have just gained some Karma for killing a Young Ronin. + return 1063041; + } + } + + public override bool Logged => false; + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_CursedSoul = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_CursedSoul); + } + } + + public class SecondTrialIntroConversation : QuestConversation + { + private bool m_CursedSoul; + + public SecondTrialIntroConversation(bool cursedSoul) + { + m_CursedSoul = cursedSoul; + } + + public SecondTrialIntroConversation() + { + } + + public override object Message + { + get + { + if (m_CursedSoul) return 1063045; + + /* It is good that you rid the land of those dishonorable Samurai. + * Perhaps they will learn a greater lesson in death.

+ * + * I have placed a reward in your pack.

+ * + * The second trial will test your courage. You only have to follow + * the yellow path to see what awaits you. + */ + return 1063046; + } + } + + public override void OnRead() + { + System.AddObjective(new SecondTrialIntroObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_CursedSoul = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_CursedSoul); + } + } + + public class SecondTrialAttackConversation : QuestConversation + { + public override object Message => 1063057; + + public override void OnRead() + { + System.AddObjective(new SecondTrialAttackObjective()); + } + } + + public class ThirdTrialIntroConversation : QuestConversation + { + private bool m_Dragon; + + public ThirdTrialIntroConversation(bool dragon) + { + m_Dragon = dragon; + } + + public ThirdTrialIntroConversation() + { + } + + public override object Message + { + get + { + if (m_Dragon) return 1063060; + + /* Fear remains in your eyes but you have learned that not all is + * what it appears to be.

+ * + * You must have known the dragon would slay you instantly. + * You elected the weaker opponent though the imp did not come + * here to destroy. You have much to learn.

+ * + * In these lands, death is not forever. The shrines can make you whole + * again as can a helpful mage or healer.

+ * + * Seek them out when you have been mortally wounded.

+ * + * The next trial will test your benevolence. You only have to walk the blue path. + */ + return 1063059; + } + } + + public override void OnRead() + { + System.AddObjective(new ThirdTrialIntroObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_Dragon = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_Dragon); + } + } + + public class ThirdTrialKillConversation : QuestConversation + { + public override object Message => 1063062; + + public override void OnRead() + { + System.AddObjective(new ThirdTrialKillObjective()); + } + } + + public class FourthTrialIntroConversation : QuestConversation + { + public override object Message => 1063065; + + public override void OnRead() + { + System.AddObjective(new FourthTrialIntroObjective()); + } + } + + public class FourthTrialCatsConversation : QuestConversation + { + public override object Message => 1063067; + + public override void OnRead() + { + System.AddObjective(new FourthTrialCatsObjective()); + } + } + + public class FifthTrialIntroConversation : QuestConversation + { + private bool m_KilledCat; + + public FifthTrialIntroConversation(bool killedCat) + { + m_KilledCat = killedCat; + } + + public FifthTrialIntroConversation() + { + } + + public override object Message + { + get + { + if (m_KilledCat) return 1063071; + + /* You showed respect by helping another out while allowing the gypsy + * what little dignity she has left.

+ * + * Now she will be able to feed herself and gain enough energy to walk + * to her camp.

+ * + * The cats are her family members� cursed by an evil mage.

+ * + * Once she has enough strength to walk back to the camp, she will be + * able to undo the spell.

+ * + * You have been rewarded for completing your trial. And now you must + * prove yourself again.

Please retrieve my katana from the + * treasure room and return it to me. + */ + return 1063070; + } + } + + public override void OnRead() + { + System.AddObjective(new FifthTrialIntroObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_KilledCat = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_KilledCat); + } + } + + public class FifthTrialReturnConversation : QuestConversation + { + public override object Message => 1063248; + + public override void OnRead() + { + System.AddObjective(new FifthTrialReturnObjective()); + } + } + + public class LostSwordConversation : QuestConversation + { + public override object Message => 1063074; + + public override bool Logged => false; + } + + public class SixthTrialIntroConversation : QuestConversation + { + private bool m_StolenTreasure; + + public SixthTrialIntroConversation(bool stolenTreasure) + { + m_StolenTreasure = stolenTreasure; + } + + public SixthTrialIntroConversation() + { + } + + public override object Message + { + get + { + if (m_StolenTreasure) return 1063077; + + /* Thank you for returning this sword to me and leaving the remaining + * treasure alone.

+ * + * Your training is nearly complete. Before you have your final trial, + * you should pay homage to Samurai who came before you.

+ * + * Go into the Altar Room and light a candle for them. Afterwards, return to me. + */ + return 1063076; + } + } + + public override void OnRead() + { + System.AddObjective(new SixthTrialIntroObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_StolenTreasure = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_StolenTreasure); + } + } + + public class SeventhTrialIntroConversation : QuestConversation + { + public override object Message => 1063079; + + public override void OnRead() + { + System.AddObjective(new SeventhTrialIntroObjective()); + } + } + + public class EndConversation : QuestConversation + { + public override object Message => 1063125; + + public override void OnRead() + { + System.Complete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/HaochisTrialsQuest.cs b/Scripts/Engines/Quests/Haochi's Trials/HaochisTrialsQuest.cs index ee2d4c40f..913126a66 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/HaochisTrialsQuest.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/HaochisTrialsQuest.cs @@ -3,117 +3,115 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class HaochisTrialsQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( AcceptConversation ), - typeof( RadarConversation ), - typeof( FirstTrialIntroConversation ), - typeof( FirstTrialKillConversation ), - typeof( GainKarmaConversation ), - typeof( SecondTrialIntroConversation ), - typeof( SecondTrialAttackConversation ), - typeof( ThirdTrialIntroConversation ), - typeof( ThirdTrialKillConversation ), - typeof( FourthTrialIntroConversation ), - typeof( FourthTrialCatsConversation ), - typeof( FifthTrialIntroConversation ), - typeof( FifthTrialReturnConversation ), - typeof( LostSwordConversation ), - typeof( SixthTrialIntroConversation ), - typeof( SeventhTrialIntroConversation ), - typeof( EndConversation ), - typeof( FindHaochiObjective ), - typeof( FirstTrialIntroObjective ), - typeof( FirstTrialKillObjective ), - typeof( FirstTrialReturnObjective ), - typeof( SecondTrialIntroObjective ), - typeof( SecondTrialAttackObjective ), - typeof( SecondTrialReturnObjective ), - typeof( ThirdTrialIntroObjective ), - typeof( ThirdTrialKillObjective ), - typeof( ThirdTrialReturnObjective ), - typeof( FourthTrialIntroObjective ), - typeof( FourthTrialCatsObjective ), - typeof( FourthTrialReturnObjective ), - typeof( FifthTrialIntroObjective ), - typeof( FifthTrialReturnObjective ), - typeof( SixthTrialIntroObjective ), - typeof( SixthTrialReturnObjective ), - typeof( SeventhTrialIntroObjective ), - typeof( SeventhTrialReturnObjective ) - }; + public class HaochisTrialsQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(AcceptConversation), + typeof(RadarConversation), + typeof(FirstTrialIntroConversation), + typeof(FirstTrialKillConversation), + typeof(GainKarmaConversation), + typeof(SecondTrialIntroConversation), + typeof(SecondTrialAttackConversation), + typeof(ThirdTrialIntroConversation), + typeof(ThirdTrialKillConversation), + typeof(FourthTrialIntroConversation), + typeof(FourthTrialCatsConversation), + typeof(FifthTrialIntroConversation), + typeof(FifthTrialReturnConversation), + typeof(LostSwordConversation), + typeof(SixthTrialIntroConversation), + typeof(SeventhTrialIntroConversation), + typeof(EndConversation), + typeof(FindHaochiObjective), + typeof(FirstTrialIntroObjective), + typeof(FirstTrialKillObjective), + typeof(FirstTrialReturnObjective), + typeof(SecondTrialIntroObjective), + typeof(SecondTrialAttackObjective), + typeof(SecondTrialReturnObjective), + typeof(ThirdTrialIntroObjective), + typeof(ThirdTrialKillObjective), + typeof(ThirdTrialReturnObjective), + typeof(FourthTrialIntroObjective), + typeof(FourthTrialCatsObjective), + typeof(FourthTrialReturnObjective), + typeof(FifthTrialIntroObjective), + typeof(FifthTrialReturnObjective), + typeof(SixthTrialIntroObjective), + typeof(SixthTrialReturnObjective), + typeof(SeventhTrialIntroObjective), + typeof(SeventhTrialReturnObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + private bool m_SentRadarConversion; - public override object Name => 1063022; + public HaochisTrialsQuest(PlayerMobile from) : base(from) + { + } - public override object OfferMessage => 1063023; + // Serialization + public HaochisTrialsQuest() + { + } - public override TimeSpan RestartDelay => TimeSpan.MaxValue; - public override bool IsTutorial => true; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override int Picture => 0x15D7; + public override object Name => 1063022; - public HaochisTrialsQuest( PlayerMobile from ) : base( from ) - { - } + public override object OfferMessage => 1063023; - // Serialization - public HaochisTrialsQuest() - { - } + public override TimeSpan RestartDelay => TimeSpan.MaxValue; + public override bool IsTutorial => true; - public override void Accept() - { - base.Accept(); + public override int Picture => 0x15D7; - AddConversation( new AcceptConversation() ); - } + public override void Accept() + { + base.Accept(); - private bool m_SentRadarConversion; + AddConversation(new AcceptConversation()); + } - public override void Slice() - { - if ( !m_SentRadarConversion && ( From.Map != Map.Malas || From.X < 360 || From.X > 400 || From.Y < 760 || From.Y > 780 ) ) - { - m_SentRadarConversion = true; - AddConversation( new RadarConversation() ); - } + public override void Slice() + { + if (!m_SentRadarConversion && + (From.Map != Map.Malas || From.X < 360 || From.X > 400 || From.Y < 760 || From.Y > 780)) + { + m_SentRadarConversion = true; + AddConversation(new RadarConversation()); + } - base.Slice(); - } + base.Slice(); + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - m_SentRadarConversion = reader.ReadBool(); - } + m_SentRadarConversion = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_SentRadarConversion ); - } + writer.Write(m_SentRadarConversion); + } - public static bool HasLostHaochisKatana( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostHaochisKatana(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is HaochisTrialsQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FifthTrialReturnObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( HaochisKatana ) ) == null ); - } - } + if (qs is HaochisTrialsQuest) + if (qs.IsObjectiveInProgress(typeof(FifthTrialReturnObjective))) + return from.Backpack?.FindItemByType(typeof(HaochisKatana)) == null; - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatana.cs b/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatana.cs index f6555c3c4..a10fa87a9 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatana.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatana.cs @@ -2,39 +2,39 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class HaochisKatana : QuestItem - { - public override int LabelNumber => 1063165; // Daimyo Haochi's Katana + public class HaochisKatana : QuestItem + { + [Constructible] + public HaochisKatana() : base(0x13FF) + { + Weight = 1.0; + } - [Constructible] - public HaochisKatana() : base( 0x13FF ) - { - Weight = 1.0; - } + public HaochisKatana(Serial serial) : base(serial) + { + } - public HaochisKatana( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063165; // Daimyo Haochi's Katana - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is HaochisTrialsQuest ); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is HaochisTrialsQuest); - //return !qs.IsObjectiveInProgress( typeof( FifthTrialReturnObjective ) ); - } + //return !qs.IsObjectiveInProgress( typeof( FifthTrialReturnObjective ) ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatanaGenerator.cs b/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatanaGenerator.cs index 8c4a61603..f5279a449 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatanaGenerator.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisKatanaGenerator.cs @@ -2,76 +2,78 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class HaochisKatanaGenerator : Item - { - public override string DefaultName => "Haochi's katana generator"; + public class HaochisKatanaGenerator : Item + { + [Constructible] + public HaochisKatanaGenerator() : base(0x1B7B) + { + Visible = false; + Movable = false; + } - [Constructible] - public HaochisKatanaGenerator() : base( 0x1B7B ) - { - Visible = false; - Movable = false; - } + public HaochisKatanaGenerator(Serial serial) : base(serial) + { + } - public override bool OnMoveOver( Mobile m ) - { - if ( m is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + public override string DefaultName => "Haochi's katana generator"; - if ( qs is HaochisTrialsQuest ) - { - if ( HaochisTrialsQuest.HasLostHaochisKatana( player ) ) - { - Item katana = new HaochisKatana(); + public override bool OnMoveOver(Mobile m) + { + if (m is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( !player.PlaceInBackpack( katana ) ) - { - katana.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - else - { - QuestObjective obj = qs.FindObjective( typeof( FifthTrialIntroObjective ) ); + if (qs is HaochisTrialsQuest) + { + if (HaochisTrialsQuest.HasLostHaochisKatana(player)) + { + Item katana = new HaochisKatana(); - if ( obj != null && !obj.Completed ) - { - Item katana = new HaochisKatana(); + if (!player.PlaceInBackpack(katana)) + { + katana.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + else + { + QuestObjective obj = qs.FindObjective(typeof(FifthTrialIntroObjective)); - if ( player.PlaceInBackpack( katana ) ) - { - obj.Complete(); - } - else - { - katana.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - } - } - } + if (obj != null && !obj.Completed) + { + Item katana = new HaochisKatana(); - return base.OnMoveOver( m ); - } + if (player.PlaceInBackpack(katana)) + { + obj.Complete(); + } + else + { + katana.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + } + } + } - public HaochisKatanaGenerator( Serial serial ) : base( serial ) - { - } + return base.OnMoveOver(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisTreasureChest.cs b/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisTreasureChest.cs index 400014ef2..a01f64893 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisTreasureChest.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Items/HaochisTreasureChest.cs @@ -5,92 +5,93 @@ using Server.Network; namespace Server.Engines.Quests.Samurai { - public class HaochisTreasureChest : WoodenFootLocker - { - [Constructible] - public HaochisTreasureChest() - { - Movable = false; + public class HaochisTreasureChest : WoodenFootLocker + { + [Constructible] + public HaochisTreasureChest() + { + Movable = false; - GenerateTreasure(); - } + GenerateTreasure(); + } - public HaochisTreasureChest( Serial serial ) : base( serial ) - { - } + public HaochisTreasureChest(Serial serial) : base(serial) + { + } - public override bool IsDecoContainer => false; + public override bool IsDecoContainer => false; - private void GenerateTreasure() - { - for ( int i = Items.Count - 1; i >= 0; i-- ) - Items[i].Delete(); + private void GenerateTreasure() + { + for (int i = Items.Count - 1; i >= 0; i--) + Items[i].Delete(); - for ( int i = 0; i < 75; i++ ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: DropItem( new GoldBracelet() ); break; - case 1: DropItem( new GoldRing() ); break; - case 2: DropItem( Loot.RandomGem() ); break; - } - } - } + for (int i = 0; i < 75; i++) + switch (Utility.Random(3)) + { + case 0: + DropItem(new GoldBracelet()); + break; + case 1: + DropItem(new GoldRing()); + break; + case 2: + DropItem(Loot.RandomGem()); + break; + } + } - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - return false; - } + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + return false; + } - public override bool CheckItemUse( Mobile from, Item item ) - { - return item == this; - } + public override bool CheckItemUse(Mobile from, Item item) + { + return item == this; + } - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; - if ( from is PlayerMobile player && player.Quest is HaochisTrialsQuest ) - { - if ( player.Quest.FindObjective( typeof( FifthTrialIntroObjective ) ) is FifthTrialIntroObjective obj ) - { - if ( obj.StolenTreasure ) - from.SendLocalizedMessage( 1063247 ); // The guard is watching you carefully! It would be unwise to remove another item from here. - else - return true; - } - } + if (from is PlayerMobile player && player.Quest is HaochisTrialsQuest) + if (player.Quest.FindObjective(typeof(FifthTrialIntroObjective)) is FifthTrialIntroObjective obj) + { + if (obj.StolenTreasure) + from.SendLocalizedMessage( + 1063247); // The guard is watching you carefully! It would be unwise to remove another item from here. + else + return true; + } - return false; - } + return false; + } - public override void OnItemLifted( Mobile from, Item item ) - { - if ( from is PlayerMobile player && player.Quest is HaochisTrialsQuest ) - { - if ( player.Quest.FindObjective( typeof( FifthTrialIntroObjective ) ) is FifthTrialIntroObjective obj ) - obj.StolenTreasure = true; - } + public override void OnItemLifted(Mobile from, Item item) + { + if (from is PlayerMobile player && player.Quest is HaochisTrialsQuest) + if (player.Quest.FindObjective(typeof(FifthTrialIntroObjective)) is FifthTrialIntroObjective obj) + obj.StolenTreasure = true; - Timer.DelayCall( TimeSpan.FromMinutes( 2.0 ), GenerateTreasure ); - } + Timer.DelayCall(TimeSpan.FromMinutes(2.0), GenerateTreasure); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Timer.DelayCall( TimeSpan.Zero, GenerateTreasure ); - } - } -} + Timer.DelayCall(TimeSpan.Zero, GenerateTreasure); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Items/HonorCandle.cs b/Scripts/Engines/Quests/Haochi's Trials/Items/HonorCandle.cs index f1f08a308..14bb83669 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Items/HonorCandle.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Items/HonorCandle.cs @@ -4,73 +4,73 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class HonorCandle : CandleLong - { - private static readonly TimeSpan LitDuration = TimeSpan.FromSeconds( 20.0 ); + public class HonorCandle : CandleLong + { + private static readonly TimeSpan LitDuration = TimeSpan.FromSeconds(20.0); - public override int LitSound => 0; - public override int UnlitSound => 0; + [Constructible] + public HonorCandle() + { + Movable = false; + Duration = LitDuration; + } - [Constructible] - public HonorCandle() - { - Movable = false; - Duration = LitDuration; - } + public HonorCandle(Serial serial) : base(serial) + { + } - public HonorCandle( Serial serial ) : base( serial ) - { - } + public override int LitSound => 0; + public override int UnlitSound => 0; - public override void OnDoubleClick( Mobile from ) - { - bool wasBurning = Burning; + public override void OnDoubleClick(Mobile from) + { + bool wasBurning = Burning; - base.OnDoubleClick( from ); + base.OnDoubleClick(from); - if ( !wasBurning && Burning ) - { - if ( !(from is PlayerMobile player) ) - return; + if (!wasBurning && Burning) + { + if (!(from is PlayerMobile player)) + return; - QuestSystem qs = player.Quest; + QuestSystem qs = player.Quest; - if ( qs is HaochisTrialsQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SixthTrialIntroObjective ) ); + if (qs is HaochisTrialsQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SixthTrialIntroObjective)); - if ( obj != null && !obj.Completed ) - obj.Complete(); + if (obj != null && !obj.Completed) + obj.Complete(); - SendLocalizedMessageTo( from, 1063251 ); // You light a candle in honor. - } - } - } + SendLocalizedMessageTo(from, 1063251); // You light a candle in honor. + } + } + } - public override void Burn() - { - Douse(); - } + public override void Burn() + { + Douse(); + } - public override void Douse() - { - base.Douse(); + public override void Douse() + { + base.Douse(); - Duration = LitDuration; - } + Duration = LitDuration; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/CursedSoul.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/CursedSoul.cs index 2b039b87c..6225a1297 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/CursedSoul.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/CursedSoul.cs @@ -1,70 +1,90 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class CursedSoul : BaseCreature - { - public override string CorpseName => "a cursed soul corpse"; - public override string DefaultName => "a cursed soul"; + public class CursedSoul : BaseCreature + { + [Constructible] + public CursedSoul() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 3; + BaseSoundID = 471; - [Constructible] - public CursedSoul() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 3; - BaseSoundID = 471; + SetStr(20, 40); + SetDex(40, 60); + SetInt(15, 25); - SetStr( 20, 40 ); - SetDex( 40, 60 ); - SetInt( 15, 25 ); + SetHits(10, 20); - SetHits( 10, 20 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 8, 12); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 8, 12 ); + SetSkill(SkillName.Wrestling, 35.0, 39.0); + SetSkill(SkillName.Tactics, 5.0, 15.0); + SetSkill(SkillName.MagicResist, 10.0); - SetSkill( SkillName.Wrestling, 35.0, 39.0 ); - SetSkill( SkillName.Tactics, 5.0, 15.0 ); - SetSkill( SkillName.MagicResist, 10.0 ); + Fame = 200; + Karma = -200; - Fame = 200; - Karma = -200; + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } + } - switch ( Utility.Random( 10 ) ) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } - } + public CursedSoul(Serial serial) : base(serial) + { + } - public CursedSoul( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a cursed soul corpse"; + public override string DefaultName => "a cursed soul"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DeadlyImp.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DeadlyImp.cs index ceb2981fa..de304084a 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DeadlyImp.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DeadlyImp.cs @@ -2,78 +2,78 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class DeadlyImp : BaseCreature - { - public override string DefaultName => "a deadly imp"; + public class DeadlyImp : BaseCreature + { + [Constructible] + public DeadlyImp() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 74; + BaseSoundID = 422; + Hue = 0x66A; - [Constructible] - public DeadlyImp() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 74; - BaseSoundID = 422; - Hue = 0x66A; + SetStr(91, 115); + SetDex(61, 80); + SetInt(86, 105); - SetStr( 91, 115 ); - SetDex( 61, 80 ); - SetInt( 86, 105 ); + SetHits(1000); - SetHits( 1000 ); + SetDamage(50, 80); - SetDamage( 50, 80 ); + SetDamageType(ResistanceType.Fire, 100); - SetDamageType( ResistanceType.Fire, 100 ); + SetResistance(ResistanceType.Physical, 95, 98); + SetResistance(ResistanceType.Fire, 95, 98); + SetResistance(ResistanceType.Cold, 95, 98); + SetResistance(ResistanceType.Poison, 95, 98); + SetResistance(ResistanceType.Energy, 95, 98); - SetResistance( ResistanceType.Physical, 95, 98 ); - SetResistance( ResistanceType.Fire, 95, 98 ); - SetResistance( ResistanceType.Cold, 95, 98 ); - SetResistance( ResistanceType.Poison, 95, 98 ); - SetResistance( ResistanceType.Energy, 95, 98 ); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Wrestling, 120.0); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + CantWalk = true; + } - CantWalk = true; - } + public DeadlyImp(Serial serial) : base(serial) + { + } - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override string DefaultName => "a deadly imp"; - if ( aggressor is PlayerMobile player ) - { - QuestSystem qs = player.Quest; - if ( qs is HaochisTrialsQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SecondTrialAttackObjective ) ); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - qs.AddObjective( new SecondTrialReturnObjective( false ) ); - } - } - } - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - public DeadlyImp( Serial serial ) : base( serial ) - { - } + if (aggressor is PlayerMobile player) + { + QuestSystem qs = player.Quest; + if (qs is HaochisTrialsQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SecondTrialAttackObjective)); + if (obj != null && !obj.Completed) + { + obj.Complete(); + qs.AddObjective(new SecondTrialReturnObjective(false)); + } + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DiseasedCat.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DiseasedCat.cs index 7b821a466..38742add9 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DiseasedCat.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/DiseasedCat.cs @@ -2,55 +2,55 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class DiseasedCat : BaseCreature - { - public override string DefaultName => "a diseased cat"; + public class DiseasedCat : BaseCreature + { + [Constructible] + public DiseasedCat() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xC9; + Hue = Utility.RandomAnimalHue(); + BaseSoundID = 0x69; - [Constructible] - public DiseasedCat() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xC9; - Hue = Utility.RandomAnimalHue(); - BaseSoundID = 0x69; + SetStr(9); + SetDex(35); + SetInt(5); - SetStr( 9 ); - SetDex( 35 ); - SetInt( 5 ); + SetHits(6); + SetMana(0); - SetHits( 6 ); - SetMana( 0 ); + SetDamage(1); - SetDamage( 1 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 4.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 4.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + VirtualArmor = 8; + } - VirtualArmor = 8; - } + public DiseasedCat(Serial serial) : base(serial) + { + } - public override bool AlwaysMurderer => true; + public override string DefaultName => "a diseased cat"; - public DiseasedCat( Serial serial ) : base( serial ) - { - } + public override bool AlwaysMurderer => true; - public override void Serialize(GenericWriter writer) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/FierceDragon.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/FierceDragon.cs index 58ff52e4f..66f92cee8 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/FierceDragon.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/FierceDragon.cs @@ -2,100 +2,100 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class FierceDragon : BaseCreature - { - public override string DefaultName => "a fierce dragon"; + public class FierceDragon : BaseCreature + { + [Constructible] + public FierceDragon() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 103; + BaseSoundID = 362; - [Constructible] - public FierceDragon() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 103; - BaseSoundID = 362; + SetStr(6000, 6020); + SetDex(0); + SetInt(850, 870); - SetStr( 6000, 6020 ); - SetDex( 0 ); - SetInt( 850, 870 ); + SetDamage(50, 80); - SetDamage( 50, 80 ); + SetDamageType(ResistanceType.Fire, 100); - SetDamageType( ResistanceType.Fire, 100 ); + SetResistance(ResistanceType.Physical, 95, 98); + SetResistance(ResistanceType.Fire, 95, 98); + SetResistance(ResistanceType.Cold, 95, 98); + SetResistance(ResistanceType.Poison, 95, 98); + SetResistance(ResistanceType.Energy, 95, 98); - SetResistance( ResistanceType.Physical, 95, 98 ); - SetResistance( ResistanceType.Fire, 95, 98 ); - SetResistance( ResistanceType.Cold, 95, 98 ); - SetResistance( ResistanceType.Poison, 95, 98 ); - SetResistance( ResistanceType.Energy, 95, 98 ); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Wrestling, 120.0); + SetSkill(SkillName.Magery, 120.0); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); + Fame = 15000; + Karma = 15000; - Fame = 15000; - Karma = 15000; + CantWalk = true; + } - CantWalk = true; - } + public FierceDragon(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x2C4; - } + public override string DefaultName => "a fierce dragon"; - public override int GetAttackSound() - { - return 0x2C0; - } + public override int GetIdleSound() + { + return 0x2C4; + } - public override int GetDeathSound() - { - return 0x2C1; - } + public override int GetAttackSound() + { + return 0x2C0; + } - public override int GetAngerSound() - { - return 0x2C4; - } + public override int GetDeathSound() + { + return 0x2C1; + } - public override int GetHurtSound() - { - return 0x2C3; - } + public override int GetAngerSound() + { + return 0x2C4; + } - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override int GetHurtSound() + { + return 0x2C3; + } - if ( aggressor is PlayerMobile player ) - { - QuestSystem qs = player.Quest; - if ( qs is HaochisTrialsQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( SecondTrialAttackObjective ) ); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - qs.AddObjective( new SecondTrialReturnObjective( true ) ); - } - } - } - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - public FierceDragon( Serial serial ) : base( serial ) - { - } + if (aggressor is PlayerMobile player) + { + QuestSystem qs = player.Quest; + if (qs is HaochisTrialsQuest) + { + QuestObjective obj = qs.FindObjective(typeof(SecondTrialAttackObjective)); + if (obj != null && !obj.Completed) + { + obj.Complete(); + qs.AddObjective(new SecondTrialReturnObjective(true)); + } + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Haochi.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Haochi.cs index 8a0daa3e4..ae6d0b04a 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Haochi.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Haochi.cs @@ -1,176 +1,176 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class Haochi : BaseQuester - { - public override string DefaultName => "Daimyo Haochi"; + public class Haochi : BaseQuester + { + [Constructible] + public Haochi() : base("the Honorable Samurai Legend") + { + } - [Constructible] - public Haochi() : base( "the Honorable Samurai Legend" ) - { - } + public Haochi(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Daimyo Haochi"; - Hue = 0x8403; + public override int TalkNumber => -1; - Female = false; - Body = 0x190; - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override void InitOutfit() - { - HairItemID = 0x204A; - HairHue = 0x901; + Hue = 0x8403; - AddItem( new SamuraiTabi() ); - AddItem( new JinBaori() ); + Female = false; + Body = 0x190; + } - AddItem( new PlateHaidate() ); - AddItem( new StandardPlateKabuto() ); - AddItem( new PlateMempo() ); - AddItem( new PlateDo() ); - AddItem( new PlateHiroSode() ); - } + public override void InitOutfit() + { + HairItemID = 0x204A; + HairHue = 0x901; - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 2; - } + AddItem(new SamuraiTabi()); + AddItem(new JinBaori()); - public override int TalkNumber => -1; + AddItem(new PlateHaidate()); + AddItem(new StandardPlateKabuto()); + AddItem(new PlateMempo()); + AddItem(new PlateDo()); + AddItem(new PlateHiroSode()); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 2; + } - if ( qs is HaochisTrialsQuest ) - { - if ( HaochisTrialsQuest.HasLostHaochisKatana( player ) ) - { - qs.AddConversation( new LostSwordConversation() ); - return; - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - QuestObjective obj = qs.FindObjective( typeof( FindHaochiObjective ) ); + if (qs is HaochisTrialsQuest) + { + if (HaochisTrialsQuest.HasLostHaochisKatana(player)) + { + qs.AddConversation(new LostSwordConversation()); + return; + } - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - return; - } + QuestObjective obj = qs.FindObjective(typeof(FindHaochiObjective)); - obj = qs.FindObjective( typeof( FirstTrialReturnObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + return; + } - if ( obj != null && !obj.Completed ) - { - player.AddToBackpack( new LeatherDo() ); - obj.Complete(); - return; - } + obj = qs.FindObjective(typeof(FirstTrialReturnObjective)); - obj = qs.FindObjective( typeof( SecondTrialReturnObjective ) ); + if (obj != null && !obj.Completed) + { + player.AddToBackpack(new LeatherDo()); + obj.Complete(); + return; + } - if ( obj != null && !obj.Completed ) - { - if ( ((SecondTrialReturnObjective)obj).Dragon ) - player.AddToBackpack( new LeatherSuneate() ); + obj = qs.FindObjective(typeof(SecondTrialReturnObjective)); - obj.Complete(); - return; - } + if (obj != null && !obj.Completed) + { + if (((SecondTrialReturnObjective)obj).Dragon) + player.AddToBackpack(new LeatherSuneate()); - obj = qs.FindObjective( typeof( ThirdTrialReturnObjective ) ); + obj.Complete(); + return; + } - if ( obj != null && !obj.Completed ) - { - player.AddToBackpack( new LeatherHiroSode() ); - obj.Complete(); - return; - } + obj = qs.FindObjective(typeof(ThirdTrialReturnObjective)); - obj = qs.FindObjective( typeof( FourthTrialReturnObjective ) ); + if (obj != null && !obj.Completed) + { + player.AddToBackpack(new LeatherHiroSode()); + obj.Complete(); + return; + } - if ( obj != null && !obj.Completed ) - { - if ( !((FourthTrialReturnObjective)obj).KilledCat ) - { - Container cont = GetNewContainer(); - cont.DropItem( new LeatherHiroSode() ); - cont.DropItem( new JinBaori() ); - player.AddToBackpack( cont ); - } + obj = qs.FindObjective(typeof(FourthTrialReturnObjective)); - obj.Complete(); - return; - } + if (obj != null && !obj.Completed) + { + if (!((FourthTrialReturnObjective)obj).KilledCat) + { + Container cont = GetNewContainer(); + cont.DropItem(new LeatherHiroSode()); + cont.DropItem(new JinBaori()); + player.AddToBackpack(cont); + } - obj = qs.FindObjective( typeof( FifthTrialReturnObjective ) ); + obj.Complete(); + return; + } - if ( obj != null && !obj.Completed ) - { - Container pack = player.Backpack; - Item katana = pack?.FindItemByType( typeof( HaochisKatana ) ); - if ( katana != null ) - { - katana.Delete(); - obj.Complete(); + obj = qs.FindObjective(typeof(FifthTrialReturnObjective)); - obj = qs.FindObjective( typeof( FifthTrialIntroObjective ) ); - if ( obj != null && ((FifthTrialIntroObjective)obj).StolenTreasure ) - qs.AddConversation( new SixthTrialIntroConversation( true ) ); - else - qs.AddConversation( new SixthTrialIntroConversation( false ) ); - } + if (obj != null && !obj.Completed) + { + Container pack = player.Backpack; + Item katana = pack?.FindItemByType(typeof(HaochisKatana)); + if (katana != null) + { + katana.Delete(); + obj.Complete(); - return; - } + obj = qs.FindObjective(typeof(FifthTrialIntroObjective)); + if (obj != null && ((FifthTrialIntroObjective)obj).StolenTreasure) + qs.AddConversation(new SixthTrialIntroConversation(true)); + else + qs.AddConversation(new SixthTrialIntroConversation(false)); + } - obj = qs.FindObjective( typeof( SixthTrialReturnObjective ) ); + return; + } - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - return; - } + obj = qs.FindObjective(typeof(SixthTrialReturnObjective)); - obj = qs.FindObjective( typeof( SeventhTrialReturnObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + return; + } - if ( obj != null && !obj.Completed ) - { - BaseWeapon weapon = new Daisho(); - BaseRunicTool.ApplyAttributesTo( weapon, Utility.Random( 1,3 ), 10, 30 ); - player.AddToBackpack( weapon ); + obj = qs.FindObjective(typeof(SeventhTrialReturnObjective)); - BaseArmor armor = new LeatherDo(); - BaseRunicTool.ApplyAttributesTo( armor, Utility.Random( 1,3 ), 10, 20 ); - player.AddToBackpack( armor ); + if (obj != null && !obj.Completed) + { + BaseWeapon weapon = new Daisho(); + BaseRunicTool.ApplyAttributesTo(weapon, Utility.Random(1, 3), 10, 30); + player.AddToBackpack(weapon); - obj.Complete(); - } - } - } + BaseArmor armor = new LeatherDo(); + BaseRunicTool.ApplyAttributesTo(armor, Utility.Random(1, 3), 10, 20); + player.AddToBackpack(armor); - public Haochi( Serial serial ) : base( serial ) - { - } + obj.Complete(); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/HaochisGuardsman.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/HaochisGuardsman.cs index 31c959cb0..37ba44c88 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/HaochisGuardsman.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/HaochisGuardsman.cs @@ -1,82 +1,103 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class HaochisGuardsman : BaseQuester - { - [Constructible] - public HaochisGuardsman() : base( "the Guardsman of Daimyo Haochi" ) - { - } + public class HaochisGuardsman : BaseQuester + { + [Constructible] + public HaochisGuardsman() : base("the Guardsman of Daimyo Haochi") + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public HaochisGuardsman(Serial serial) : base(serial) + { + } - Hue = Race.Human.RandomSkinHue(); + public override int TalkNumber => -1; - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + public override void InitBody() + { + InitStats(100, 100, 25); - public override void InitOutfit() - { - Utility.AssignRandomHair( this ); + Hue = Race.Human.RandomSkinHue(); - AddItem( new LeatherDo() ); - AddItem( new LeatherHiroSode() ); - AddItem( new SamuraiTabi( Utility.RandomNondyedHue() ) ); + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new StuddedHaidate() ); break; - case 1: AddItem( new PlateSuneate() ); break; - default: AddItem( new LeatherSuneate() ); break; - } + public override void InitOutfit() + { + Utility.AssignRandomHair(this); - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new DecorativePlateKabuto() ); break; - case 1: AddItem( new ChainHatsuburi() ); break; - case 2: AddItem( new LightPlateJingasa() ); break; - default: AddItem( new LeatherJingasa() ); break; - } + AddItem(new LeatherDo()); + AddItem(new LeatherHiroSode()); + AddItem(new SamuraiTabi(Utility.RandomNondyedHue())); - Item weapon; - switch ( Utility.Random( 3 ) ) - { - case 0: weapon = new NoDachi(); break; - case 1: weapon = new Lajatang(); break; - default: weapon = new Wakizashi(); break; - } - weapon.Movable = false; - AddItem( weapon ); - } + switch (Utility.Random(3)) + { + case 0: + AddItem(new StuddedHaidate()); + break; + case 1: + AddItem(new PlateSuneate()); + break; + default: + AddItem(new LeatherSuneate()); + break; + } - public override int TalkNumber => -1; + switch (Utility.Random(4)) + { + case 0: + AddItem(new DecorativePlateKabuto()); + break; + case 1: + AddItem(new ChainHatsuburi()); + break; + case 2: + AddItem(new LightPlateJingasa()); + break; + default: + AddItem(new LeatherJingasa()); + break; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } + Item weapon; + switch (Utility.Random(3)) + { + case 0: + weapon = new NoDachi(); + break; + case 1: + weapon = new Lajatang(); + break; + default: + weapon = new Wakizashi(); + break; + } - public HaochisGuardsman( Serial serial ) : base( serial ) - { - } + weapon.Movable = false; + AddItem(weapon); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } - writer.WriteEncodedInt( 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/InjuredWolf.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/InjuredWolf.cs index 063328510..56d759417 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/InjuredWolf.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/InjuredWolf.cs @@ -2,58 +2,58 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class InjuredWolf : BaseCreature - { - public override string CorpseName => "an injured wolf corpse"; - public override string DefaultName => "an injured wolf"; + public class InjuredWolf : BaseCreature + { + [Constructible] + public InjuredWolf() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xE1; + BaseSoundID = 0xE5; - [Constructible] - public InjuredWolf() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xE1; - BaseSoundID = 0xE5; + Hue = Utility.RandomAnimalHue(); - Hue = Utility.RandomAnimalHue(); + SetStr(10, 20); + SetDex(45, 65); + SetInt(10, 15); - SetStr( 10, 20 ); - SetDex( 45, 65 ); - SetInt( 10, 15 ); + SetHits(1); - SetHits( 1 ); + SetDamage(1, 3); - SetDamage( 1, 3 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15); + SetResistance(ResistanceType.Fire, 5, 10); - SetResistance( ResistanceType.Physical, 15 ); - SetResistance( ResistanceType.Fire, 5, 10 ); + SetSkill(SkillName.MagicResist, 10.0); + SetSkill(SkillName.Tactics, 0.0, 5.0); + SetSkill(SkillName.Wrestling, 20.0, 30.0); + } - SetSkill( SkillName.MagicResist, 10.0 ); - SetSkill( SkillName.Tactics, 0.0, 5.0 ); - SetSkill( SkillName.Wrestling, 20.0, 30.0 ); - } + public InjuredWolf(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0xE9; - } + public override string CorpseName => "an injured wolf corpse"; + public override string DefaultName => "an injured wolf"; - public InjuredWolf( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 0xE9; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Relnia.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Relnia.cs index 8c5323487..dbcd3bb3e 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Relnia.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/Relnia.cs @@ -1,90 +1,88 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class Relnia : BaseQuester - { - public override string DefaultName => "Disheveled Relnia"; - - [Constructible] - public Relnia() : base( "the Gypsy" ) - { - } - - public override void InitBody() - { - InitStats( 100, 100, 25 ); - - Hue = 0x83FF; - - Female = true; - Body = 0x191; - } - - public override void InitOutfit() - { - HairItemID = 0x203C; - HairHue = 0x654; - - AddItem( new ThighBoots( 0x901 ) ); - AddItem( new FancyShirt( 0x5F3 ) ); - AddItem( new SkullCap( 0x6A7 ) ); - AddItem( new Skirt( 0x544 ) ); - } - - public override int TalkNumber => -1; - - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; - - if ( qs is HaochisTrialsQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( FourthTrialCatsObjective ) ); - - if ( obj != null && !obj.Completed ) - { - if ( dropped is Gold gold ) - { - obj.Complete(); - qs.AddObjective( new FourthTrialReturnObjective( false ) ); - - SayTo( from, 1063241 ); // I thank thee. This gold will be a great help to me and mine! - - gold.Consume(); // Intentional difference from OSI: don't take all the gold of poor newbies! - return gold.Deleted; - } - } - } - } - - return base.OnDragDrop( from, dropped ); - } + public class Relnia : BaseQuester + { + [Constructible] + public Relnia() : base("the Gypsy") + { + } - public Relnia( Serial serial ) : base( serial ) - { - } + public Relnia(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string DefaultName => "Disheveled Relnia"; - writer.WriteEncodedInt( 0 ); // version - } + public override int TalkNumber => -1; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void InitBody() + { + InitStats(100, 100, 25); - int version = reader.ReadEncodedInt(); - } - } -} + Hue = 0x83FF; + + Female = true; + Body = 0x191; + } + + public override void InitOutfit() + { + HairItemID = 0x203C; + HairHue = 0x654; + + AddItem(new ThighBoots(0x901)); + AddItem(new FancyShirt(0x5F3)); + AddItem(new SkullCap(0x6A7)); + AddItem(new Skirt(0x544)); + } + + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; + + if (qs is HaochisTrialsQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FourthTrialCatsObjective)); + + if (obj != null && !obj.Completed) + if (dropped is Gold gold) + { + obj.Complete(); + qs.AddObjective(new FourthTrialReturnObjective(false)); + + SayTo(from, 1063241); // I thank thee. This gold will be a great help to me and mine! + + gold.Consume(); // Intentional difference from OSI: don't take all the gold of poor newbies! + return gold.Deleted; + } + } + } + + return base.OnDragDrop(from, dropped); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungNinja.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungNinja.cs index afd30a4a7..78a04e931 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungNinja.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungNinja.cs @@ -1,61 +1,67 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class YoungNinja : BaseCreature - { - public override string CorpseName => "a young ninja's corpse"; - public override string DefaultName => "a young ninja"; + public class YoungNinja : BaseCreature + { + [Constructible] + public YoungNinja() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + InitStats(45, 30, 5); + SetHits(20, 30); - [Constructible] - public YoungNinja() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - InitStats( 45, 30, 5 ); - SetHits( 20, 30 ); + Hue = Utility.RandomSkinHue(); + Body = 0x190; - Hue = Utility.RandomSkinHue(); - Body = 0x190; + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this ); + AddItem(new NinjaTabi()); + AddItem(new LeatherNinjaPants()); + AddItem(new LeatherNinjaJacket()); + AddItem(new LeatherNinjaBelt()); - AddItem( new NinjaTabi() ); - AddItem( new LeatherNinjaPants() ); - AddItem( new LeatherNinjaJacket() ); - AddItem( new LeatherNinjaBelt() ); + AddItem(new Bandana(Utility.RandomNondyedHue())); - AddItem( new Bandana( Utility.RandomNondyedHue() ) ); + switch (Utility.Random(3)) + { + case 0: + AddItem(new Tessen()); + break; + case 1: + AddItem(new Kama()); + break; + default: + AddItem(new Lajatang()); + break; + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new Tessen() ); break; - case 1: AddItem( new Kama() ); break; - default: AddItem( new Lajatang() ); break; - } + SetSkill(SkillName.Swords, 50.0); + SetSkill(SkillName.Tactics, 50.0); + } - SetSkill( SkillName.Swords, 50.0 ); - SetSkill( SkillName.Tactics, 50.0 ); - } + public YoungNinja(Serial serial) : base(serial) + { + } - public override bool AlwaysMurderer => true; + public override string CorpseName => "a young ninja's corpse"; + public override string DefaultName => "a young ninja"; - public YoungNinja( Serial serial ) : base( serial ) - { - } + public override bool AlwaysMurderer => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungRonin.cs b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungRonin.cs index 98f53cdc3..6b963d337 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungRonin.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Mobiles/YoungRonin.cs @@ -1,67 +1,79 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class YoungRonin : BaseCreature - { - public override string CorpseName => "a young ronin's corpse"; - public override string DefaultName => "a young ronin"; + public class YoungRonin : BaseCreature + { + [Constructible] + public YoungRonin() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + InitStats(45, 30, 5); + SetHits(10, 20); - [Constructible] - public YoungRonin() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - InitStats( 45, 30, 5 ); - SetHits( 10, 20 ); + Hue = Utility.RandomSkinHue(); + Body = 0x190; - Hue = Utility.RandomSkinHue(); - Body = 0x190; + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this ); + AddItem(new LeatherDo()); + AddItem(new LeatherHiroSode()); + AddItem(new SamuraiTabi()); - AddItem( new LeatherDo() ); - AddItem( new LeatherHiroSode() ); - AddItem( new SamuraiTabi() ); + switch (Utility.Random(3)) + { + case 0: + AddItem(new StuddedHaidate()); + break; + case 1: + AddItem(new PlateSuneate()); + break; + default: + AddItem(new LeatherSuneate()); + break; + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new StuddedHaidate() ); break; - case 1: AddItem( new PlateSuneate() ); break; - default: AddItem( new LeatherSuneate() ); break; - } + AddItem(new Bandana(Utility.RandomNondyedHue())); - AddItem( new Bandana( Utility.RandomNondyedHue() ) ); + switch (Utility.Random(3)) + { + case 0: + AddItem(new NoDachi()); + break; + case 1: + AddItem(new Lajatang()); + break; + default: + AddItem(new Wakizashi()); + break; + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new NoDachi() ); break; - case 1: AddItem( new Lajatang() ); break; - default: AddItem( new Wakizashi() ); break; - } + SetSkill(SkillName.Swords, 50.0); + SetSkill(SkillName.Tactics, 50.0); + } - SetSkill( SkillName.Swords, 50.0 ); - SetSkill( SkillName.Tactics, 50.0 ); - } + public YoungRonin(Serial serial) : base(serial) + { + } - public override bool AlwaysMurderer => true; + public override string CorpseName => "a young ronin's corpse"; + public override string DefaultName => "a young ronin"; - public YoungRonin( Serial serial ) : base( serial ) - { - } + public override bool AlwaysMurderer => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Haochi's Trials/Objectives.cs b/Scripts/Engines/Quests/Haochi's Trials/Objectives.cs index 125aa8527..fd6b84992 100644 --- a/Scripts/Engines/Quests/Haochi's Trials/Objectives.cs +++ b/Scripts/Engines/Quests/Haochi's Trials/Objectives.cs @@ -4,403 +4,339 @@ using Server.Mobiles; namespace Server.Engines.Quests.Samurai { - public class FindHaochiObjective : QuestObjective - { - public override object Message => 1063026; - - public FindHaochiObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new FirstTrialIntroConversation() ); - } - } - - public class FirstTrialIntroObjective : QuestObjective - { - public override object Message => 1063030; - - public FirstTrialIntroObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new FirstTrialKillConversation() ); - } - } - - public class FirstTrialKillObjective : QuestObjective - { - public override object Message => 1063032; - - public FirstTrialKillObjective() - { - } - - private int m_CursedSoulsKilled; - private int m_YoungRoninKilled; - - public override int MaxProgress => 3; - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is CursedSoul ) - { - if ( m_CursedSoulsKilled == 0 ) - System.AddConversation( new GainKarmaConversation( true ) ); - - m_CursedSoulsKilled++; - - // Cursed Souls killed: ~1_COUNT~ - System.From.SendLocalizedMessage( 1063038, m_CursedSoulsKilled.ToString() ); - } - else if ( creature is YoungRonin ) - { - if ( m_YoungRoninKilled == 0 ) - System.AddConversation( new GainKarmaConversation( false ) ); - - m_YoungRoninKilled++; - - // Young Ronin killed: ~1_COUNT~ - System.From.SendLocalizedMessage( 1063039, m_YoungRoninKilled.ToString() ); - } - - CurProgress = Math.Max( m_CursedSoulsKilled, m_YoungRoninKilled ); - } - - public override void OnComplete() - { - System.AddObjective( new FirstTrialReturnObjective( m_CursedSoulsKilled > m_YoungRoninKilled ) ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_CursedSoulsKilled = reader.ReadEncodedInt(); - m_YoungRoninKilled = reader.ReadEncodedInt(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( m_CursedSoulsKilled ); - writer.WriteEncodedInt( m_YoungRoninKilled ); - } - } - - public class FirstTrialReturnObjective : QuestObjective - { - public override object Message => 1063044; - - bool m_CursedSoul; - - public FirstTrialReturnObjective( bool cursedSoul ) - { - m_CursedSoul = cursedSoul; - } - - public FirstTrialReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new SecondTrialIntroConversation( m_CursedSoul ) ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_CursedSoul = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_CursedSoul ); - } - } - - public class SecondTrialIntroObjective : QuestObjective - { - public override object Message => 1063047; - - public SecondTrialIntroObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new SecondTrialAttackConversation() ); - } - } - - public class SecondTrialAttackObjective : QuestObjective - { - public override object Message => 1063058; - - public SecondTrialAttackObjective() - { - } - } - - public class SecondTrialReturnObjective : QuestObjective - { - public override object Message => 1063229; - - public bool Dragon { get; private set; } - - public SecondTrialReturnObjective( bool dragon ) - { - Dragon = dragon; - } - - public SecondTrialReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ThirdTrialIntroConversation( Dragon ) ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - Dragon = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) Dragon ); - } - } - - public class ThirdTrialIntroObjective : QuestObjective - { - public override object Message => 1063061; - - public ThirdTrialIntroObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new ThirdTrialKillConversation() ); - } - } - - public class ThirdTrialKillObjective : QuestObjective - { - public override object Message => 1063063; - - public ThirdTrialKillObjective() - { - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is InjuredWolf ) - Complete(); - } - - public override void OnComplete() - { - System.AddObjective( new ThirdTrialReturnObjective() ); - } - } - - public class ThirdTrialReturnObjective : QuestObjective - { - public override object Message => 1063064; - - public ThirdTrialReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new FourthTrialIntroConversation() ); - } - } - - public class FourthTrialIntroObjective : QuestObjective - { - public override object Message => 1063066; - - public FourthTrialIntroObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new FourthTrialCatsConversation() ); - } - } - - public class FourthTrialCatsObjective : QuestObjective - { - public override object Message => 1063068; - - public FourthTrialCatsObjective() - { - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is DiseasedCat ) - { - Complete(); - System.AddObjective( new FourthTrialReturnObjective( true ) ); - } - } - } - - public class FourthTrialReturnObjective : QuestObjective - { - public override object Message => 1063242; - - public bool KilledCat { get; private set; } - - public FourthTrialReturnObjective( bool killedCat ) - { - KilledCat = killedCat; - } - - public FourthTrialReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new FifthTrialIntroConversation( KilledCat ) ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - KilledCat = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) KilledCat ); - } - } - - public class FifthTrialIntroObjective : QuestObjective - { - public override object Message => 1063072; - - public bool StolenTreasure { get; set; } - - public FifthTrialIntroObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new FifthTrialReturnConversation() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - StolenTreasure = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) StolenTreasure ); - } - } - - public class FifthTrialReturnObjective : QuestObjective - { - public override object Message => 1063073; - - public FifthTrialReturnObjective() - { - } - } - - public class SixthTrialIntroObjective : QuestObjective - { - public override object Message => 1063078; - - public SixthTrialIntroObjective() - { - } - - public override void OnComplete() - { - System.AddObjective( new SixthTrialReturnObjective() ); - } - } - - public class SixthTrialReturnObjective : QuestObjective - { - public override object Message => 1063252; - - public SixthTrialReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new SeventhTrialIntroConversation() ); - } - } - - public class SeventhTrialIntroObjective : QuestObjective - { - public override object Message => 1063080; - - public override int MaxProgress => 3; - - public SeventhTrialIntroObjective() - { - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is YoungNinja ) - CurProgress++; - } - - public override void OnComplete() - { - System.AddObjective( new SeventhTrialReturnObjective() ); - } - } - - public class SeventhTrialReturnObjective : QuestObjective - { - public override object Message => 1063253; - - public SeventhTrialReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new EndConversation() ); - } - } -} + public class FindHaochiObjective : QuestObjective + { + public override object Message => 1063026; + + public override void OnComplete() + { + System.AddConversation(new FirstTrialIntroConversation()); + } + } + + public class FirstTrialIntroObjective : QuestObjective + { + public override object Message => 1063030; + + public override void OnComplete() + { + System.AddConversation(new FirstTrialKillConversation()); + } + } + + public class FirstTrialKillObjective : QuestObjective + { + private int m_CursedSoulsKilled; + private int m_YoungRoninKilled; + + public override object Message => 1063032; + + public override int MaxProgress => 3; + + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is CursedSoul) + { + if (m_CursedSoulsKilled == 0) + System.AddConversation(new GainKarmaConversation(true)); + + m_CursedSoulsKilled++; + + // Cursed Souls killed: ~1_COUNT~ + System.From.SendLocalizedMessage(1063038, m_CursedSoulsKilled.ToString()); + } + else if (creature is YoungRonin) + { + if (m_YoungRoninKilled == 0) + System.AddConversation(new GainKarmaConversation(false)); + + m_YoungRoninKilled++; + + // Young Ronin killed: ~1_COUNT~ + System.From.SendLocalizedMessage(1063039, m_YoungRoninKilled.ToString()); + } + + CurProgress = Math.Max(m_CursedSoulsKilled, m_YoungRoninKilled); + } + + public override void OnComplete() + { + System.AddObjective(new FirstTrialReturnObjective(m_CursedSoulsKilled > m_YoungRoninKilled)); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_CursedSoulsKilled = reader.ReadEncodedInt(); + m_YoungRoninKilled = reader.ReadEncodedInt(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(m_CursedSoulsKilled); + writer.WriteEncodedInt(m_YoungRoninKilled); + } + } + + public class FirstTrialReturnObjective : QuestObjective + { + private bool m_CursedSoul; + + public FirstTrialReturnObjective(bool cursedSoul) + { + m_CursedSoul = cursedSoul; + } + + public FirstTrialReturnObjective() + { + } + + public override object Message => 1063044; + + public override void OnComplete() + { + System.AddConversation(new SecondTrialIntroConversation(m_CursedSoul)); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_CursedSoul = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_CursedSoul); + } + } + + public class SecondTrialIntroObjective : QuestObjective + { + public override object Message => 1063047; + + public override void OnComplete() + { + System.AddConversation(new SecondTrialAttackConversation()); + } + } + + public class SecondTrialAttackObjective : QuestObjective + { + public override object Message => 1063058; + } + + public class SecondTrialReturnObjective : QuestObjective + { + public SecondTrialReturnObjective(bool dragon) + { + Dragon = dragon; + } + + public SecondTrialReturnObjective() + { + } + + public override object Message => 1063229; + + public bool Dragon{ get; private set; } + + public override void OnComplete() + { + System.AddConversation(new ThirdTrialIntroConversation(Dragon)); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + Dragon = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(Dragon); + } + } + + public class ThirdTrialIntroObjective : QuestObjective + { + public override object Message => 1063061; + + public override void OnComplete() + { + System.AddConversation(new ThirdTrialKillConversation()); + } + } + + public class ThirdTrialKillObjective : QuestObjective + { + public override object Message => 1063063; + + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is InjuredWolf) + Complete(); + } + + public override void OnComplete() + { + System.AddObjective(new ThirdTrialReturnObjective()); + } + } + + public class ThirdTrialReturnObjective : QuestObjective + { + public override object Message => 1063064; + + public override void OnComplete() + { + System.AddConversation(new FourthTrialIntroConversation()); + } + } + + public class FourthTrialIntroObjective : QuestObjective + { + public override object Message => 1063066; + + public override void OnComplete() + { + System.AddConversation(new FourthTrialCatsConversation()); + } + } + + public class FourthTrialCatsObjective : QuestObjective + { + public override object Message => 1063068; + + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is DiseasedCat) + { + Complete(); + System.AddObjective(new FourthTrialReturnObjective(true)); + } + } + } + + public class FourthTrialReturnObjective : QuestObjective + { + public FourthTrialReturnObjective(bool killedCat) + { + KilledCat = killedCat; + } + + public FourthTrialReturnObjective() + { + } + + public override object Message => 1063242; + + public bool KilledCat{ get; private set; } + + public override void OnComplete() + { + System.AddConversation(new FifthTrialIntroConversation(KilledCat)); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + KilledCat = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(KilledCat); + } + } + + public class FifthTrialIntroObjective : QuestObjective + { + public override object Message => 1063072; + + public bool StolenTreasure{ get; set; } + + public override void OnComplete() + { + System.AddConversation(new FifthTrialReturnConversation()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + StolenTreasure = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(StolenTreasure); + } + } + + public class FifthTrialReturnObjective : QuestObjective + { + public override object Message => 1063073; + } + + public class SixthTrialIntroObjective : QuestObjective + { + public override object Message => 1063078; + + public override void OnComplete() + { + System.AddObjective(new SixthTrialReturnObjective()); + } + } + + public class SixthTrialReturnObjective : QuestObjective + { + public override object Message => 1063252; + + public override void OnComplete() + { + System.AddConversation(new SeventhTrialIntroConversation()); + } + } + + public class SeventhTrialIntroObjective : QuestObjective + { + public override object Message => 1063080; + + public override int MaxProgress => 3; + + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is YoungNinja) + CurProgress++; + } + + public override void OnComplete() + { + System.AddObjective(new SeventhTrialReturnObjective()); + } + } + + public class SeventhTrialReturnObjective : QuestObjective + { + public override object Message => 1063253; + + public override void OnComplete() + { + System.AddConversation(new EndConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Solen Matriarch/Conversations.cs b/Scripts/Engines/Quests/Solen Matriarch/Conversations.cs index f85e60e04..19939630d 100644 --- a/Scripts/Engines/Quests/Solen Matriarch/Conversations.cs +++ b/Scripts/Engines/Quests/Solen Matriarch/Conversations.cs @@ -1,231 +1,183 @@ namespace Server.Engines.Quests.Matriarch { - public class DontOfferConversation : QuestConversation - { - private bool m_Friend; + public class DontOfferConversation : QuestConversation + { + private bool m_Friend; - public override object Message - { - get - { - if ( m_Friend ) - { - /* The Solen Matriarch smiles as you greet her.

- * - * It is good to see you again. I would offer to process some zoogi fungus for you, - * but you seem to be busy with another task at the moment. Perhaps you should - * finish whatever is occupying your attention at the moment and return to me once - * you're done. - */ - return 1054081; - } + public DontOfferConversation(bool friend) + { + m_Friend = friend; + } - /* The Solen Matriarch smiles as she eats the seed you offered.

- * - * Thank you for that seed. It was quite delicious.

- * - * I would offer to make you a friend of my colony, but you seem to be busy with - * another task at the moment. Perhaps you should finish whatever is occupying - * your attention at the moment and return to me once you're done. - */ - return 1054079; - } - } + public DontOfferConversation() + { + } - public override bool Logged => false; + public override object Message + { + get + { + if (m_Friend) return 1054081; - public DontOfferConversation( bool friend ) - { - m_Friend = friend; - } + /* The Solen Matriarch smiles as she eats the seed you offered.

+ * + * Thank you for that seed. It was quite delicious.

+ * + * I would offer to make you a friend of my colony, but you seem to be busy with + * another task at the moment. Perhaps you should finish whatever is occupying + * your attention at the moment and return to me once you're done. + */ + return 1054079; + } + } - public DontOfferConversation() - { - } + public override bool Logged => false; - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - m_Friend = reader.ReadBool(); - } + m_Friend = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_Friend ); - } - } + writer.Write(m_Friend); + } + } - public class AcceptConversation : QuestConversation - { - public override object Message => 1054084; + public class AcceptConversation : QuestConversation + { + public override object Message => 1054084; - public AcceptConversation() - { - } + public override void OnRead() + { + System.AddObjective(new KillInfiltratorsObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new KillInfiltratorsObjective() ); - } - } + public class DuringKillInfiltratorsConversation : QuestConversation + { + public override object Message => 1054089; - public class DuringKillInfiltratorsConversation : QuestConversation - { - public override object Message => 1054089; + public override bool Logged => false; + } - public override bool Logged => false; + public class GatherWaterConversation : QuestConversation + { + public override object Message => 1054091; - public DuringKillInfiltratorsConversation() - { - } - } + public override void OnRead() + { + System.AddObjective(new GatherWaterObjective()); + } + } - public class GatherWaterConversation : QuestConversation - { - public override object Message => 1054091; + public class DuringWaterGatheringConversation : QuestConversation + { + public override object Message => 1054094; - public GatherWaterConversation() - { - } + public override bool Logged => false; + } - public override void OnRead() - { - System.AddObjective( new GatherWaterObjective() ); - } - } + public class ProcessFungiConversation : QuestConversation + { + private bool m_Friend; - public class DuringWaterGatheringConversation : QuestConversation - { - public override object Message => 1054094; + public ProcessFungiConversation(bool friend) + { + m_Friend = friend; + } - public override bool Logged => false; + public ProcessFungiConversation() + { + } - public DuringWaterGatheringConversation() - { - } - } + public override object Message + { + get + { + if (m_Friend) return 1054097; - public class ProcessFungiConversation : QuestConversation - { - private bool m_Friend; + /* The Solen Matriarch listens as you report the completion of your + * tasks to her.

+ * + * I give you my thanks for your help, and I will gladly make you a friend of my + * solen colony. My warriors, workers, and queens will not longer look at you + * as an intruder and attack you when you enter our lair.

+ * + * I will also process some zoogi fungus into powder of translocation for you. + * Two of the zoogi fungi are required for each measure of the powder. I will + * process up to 200 zoogi fungi into 100 measures of powder of translocation.

+ * + * I will also give you some gold for assisting me and my colony, but first let's + * take care of your zoogi fungus. + */ + return 1054096; + } + } - public override object Message - { - get - { - if ( m_Friend ) - { - /* The Solen Matriarch listens as you report the completion of your - * tasks to her.

- * - * I give you my thanks for your help, and I will gladly process some zoogi - * fungus into powder of translocation for you. Two of the zoogi fungi are - * required for each measure of the powder. I will process up to 200 zoogi fungi - * into 100 measures of powder of translocation.

- * - * I will also give you some gold for assisting me and my colony, but first let's - * take care of your zoogi fungus. - */ - return 1054097; - } + public override void OnRead() + { + System.AddObjective(new ProcessFungiObjective()); + } - /* The Solen Matriarch listens as you report the completion of your - * tasks to her.

- * - * I give you my thanks for your help, and I will gladly make you a friend of my - * solen colony. My warriors, workers, and queens will not longer look at you - * as an intruder and attack you when you enter our lair.

- * - * I will also process some zoogi fungus into powder of translocation for you. - * Two of the zoogi fungi are required for each measure of the powder. I will - * process up to 200 zoogi fungi into 100 measures of powder of translocation.

- * - * I will also give you some gold for assisting me and my colony, but first let's - * take care of your zoogi fungus. - */ - return 1054096; - } - } + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public ProcessFungiConversation( bool friend ) - { - m_Friend = friend; - } + m_Friend = reader.ReadBool(); + } - public override void OnRead() - { - System.AddObjective( new ProcessFungiObjective() ); - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public ProcessFungiConversation() - { - } + writer.Write(m_Friend); + } + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public class DuringFungiProcessConversation : QuestConversation + { + public override object Message => 1054099; - m_Friend = reader.ReadBool(); - } + public override bool Logged => false; + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public class FullBackpackConversation : QuestConversation + { + private bool m_Logged; - writer.Write( (bool) m_Friend ); - } - } + public FullBackpackConversation(bool logged) + { + m_Logged = logged; + } - public class DuringFungiProcessConversation : QuestConversation - { - public override object Message => 1054099; + public FullBackpackConversation() + { + m_Logged = true; + } - public override bool Logged => false; + public override object Message => 1054102; - public DuringFungiProcessConversation() - { - } - } + public override bool Logged => m_Logged; - public class FullBackpackConversation : QuestConversation - { - public override object Message => 1054102; + public override void OnRead() + { + if (m_Logged) + System.AddObjective(new GetRewardObjective()); + } + } - private bool m_Logged; + public class EndConversation : QuestConversation + { + public override object Message => 1054101; - public override bool Logged => m_Logged; - - public FullBackpackConversation( bool logged ) - { - m_Logged = logged; - } - - public FullBackpackConversation() - { - m_Logged = true; - } - - public override void OnRead() - { - if ( m_Logged ) - System.AddObjective( new GetRewardObjective() ); - } - } - - public class EndConversation : QuestConversation - { - public override object Message => 1054101; - - public EndConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } -} + public override void OnRead() + { + System.Complete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Solen Matriarch/Mobiles/SolenMatriarch.cs b/Scripts/Engines/Quests/Solen Matriarch/Mobiles/SolenMatriarch.cs index a1f5c5301..228bd781e 100644 --- a/Scripts/Engines/Quests/Solen Matriarch/Mobiles/SolenMatriarch.cs +++ b/Scripts/Engines/Quests/Solen Matriarch/Mobiles/SolenMatriarch.cs @@ -1,317 +1,299 @@ using System.Collections.Generic; +using Server.ContextMenus; +using Server.Engines.Plants; using Server.Items; using Server.Mobiles; using Server.Targeting; -using Server.ContextMenus; -using Server.Engines.Plants; namespace Server.Engines.Quests.Matriarch { - public abstract class BaseSolenMatriarch : BaseQuester - { - public abstract bool RedSolen{ get; } - public override string DefaultName => "the solen matriarch"; - public override bool DisallowAllMoves => false; + public abstract class BaseSolenMatriarch : BaseQuester + { + public BaseSolenMatriarch() + { + Body = 0x328; - public BaseSolenMatriarch() - { - Body = 0x328; + if (!RedSolen) + Hue = 0x44E; - if ( !RedSolen ) - Hue = 0x44E; + SpeechHue = 0; + } - SpeechHue = 0; - } + public BaseSolenMatriarch(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x10D; - } + public abstract bool RedSolen{ get; } + public override string DefaultName => "the solen matriarch"; + public override bool DisallowAllMoves => false; - public override bool CanTalkTo( PlayerMobile to ) - { - if ( SolenMatriarchQuest.IsFriend( to, RedSolen ) ) - return true; + public override int GetIdleSound() + { + return 0x10D; + } - return to.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen; - } + public override bool CanTalkTo(PlayerMobile to) + { + if (SolenMatriarchQuest.IsFriend(to, RedSolen)) + return true; - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - Direction = GetDirectionTo( player ); + return to.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen; + } - if ( player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen ) - { - if ( qs.IsObjectiveInProgress( typeof( KillInfiltratorsObjective ) ) ) - { - qs.AddConversation( new DuringKillInfiltratorsConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( ReturnAfterKillsObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + Direction = GetDirectionTo(player); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( GatherWaterObjective ) ) ) - { - qs.AddConversation( new DuringWaterGatheringConversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnAfterWaterObjective ) ); + if (player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen) + { + if (qs.IsObjectiveInProgress(typeof(KillInfiltratorsObjective))) + { + qs.AddConversation(new DuringKillInfiltratorsConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(ReturnAfterKillsObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( ProcessFungiObjective ) ) ) - { - qs.AddConversation( new DuringFungiProcessConversation() ); - } - else - { - obj = qs.FindObjective( typeof( GetRewardObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(GatherWaterObjective))) + { + qs.AddConversation(new DuringWaterGatheringConversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnAfterWaterObjective)); - if ( obj != null && !obj.Completed ) - { - if ( SolenMatriarchQuest.GiveRewardTo( player ) ) - { - obj.Complete(); - } - else - { - qs.AddConversation( new FullBackpackConversation( false ) ); - } - } - } - } - } - } - else if ( SolenMatriarchQuest.IsFriend( player, RedSolen ) ) - { - QuestSystem newQuest = new SolenMatriarchQuest( player, RedSolen ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(ProcessFungiObjective))) + { + qs.AddConversation(new DuringFungiProcessConversation()); + } + else + { + obj = qs.FindObjective(typeof(GetRewardObjective)); - if ( player.Quest == null && QuestSystem.CanOfferQuest( player, typeof( SolenMatriarchQuest ) ) ) - { - newQuest.SendOffer(); - } - else - { - newQuest.AddConversation( new DontOfferConversation( true ) ); - } - } - } + if (obj != null && !obj.Completed) + { + if (SolenMatriarchQuest.GiveRewardTo(player)) + obj.Complete(); + else + qs.AddConversation(new FullBackpackConversation(false)); + } + } + } + } + } + else if (SolenMatriarchQuest.IsFriend(player, RedSolen)) + { + QuestSystem newQuest = new SolenMatriarchQuest(player, RedSolen); - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - if ( dropped is Seed ) - { - if ( player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen ) - { - SayTo( player, 1054080 ); // Thank you for that plant seed. Those have such wonderful flavor. - } - else - { - QuestSystem newQuest = new SolenMatriarchQuest( player, RedSolen ); + if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(SolenMatriarchQuest))) + newQuest.SendOffer(); + else + newQuest.AddConversation(new DontOfferConversation(true)); + } + } - if ( player.Quest == null && QuestSystem.CanOfferQuest( player, typeof( SolenMatriarchQuest ) ) ) - { - newQuest.SendOffer(); - } - else - { - newQuest.AddConversation( new DontOfferConversation( SolenMatriarchQuest.IsFriend( player, RedSolen ) ) ); - } - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + { + if (dropped is Seed) + { + if (player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen) + { + SayTo(player, 1054080); // Thank you for that plant seed. Those have such wonderful flavor. + } + else + { + QuestSystem newQuest = new SolenMatriarchQuest(player, RedSolen); - dropped.Delete(); - return true; - } - if ( dropped is ZoogiFungus fungus ) - { - OnGivenFungi( player, fungus ); + if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(SolenMatriarchQuest))) + newQuest.SendOffer(); + else + newQuest.AddConversation( + new DontOfferConversation(SolenMatriarchQuest.IsFriend(player, RedSolen))); + } - return fungus.Deleted; - } - } + dropped.Delete(); + return true; + } - return base.OnDragDrop( from, dropped ); - } + if (dropped is ZoogiFungus fungus) + { + OnGivenFungi(player, fungus); - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + return fungus.Deleted; + } + } - if ( from.Alive ) - { - if ( from is PlayerMobile pm ) - { - if ( pm.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen ) - { - if ( qs.IsObjectiveInProgress( typeof( ProcessFungiObjective ) ) ) - { - list.Add( new ProcessZoogiFungusEntry( this, pm ) ); - } - } - } - } - } + return base.OnDragDrop(from, dropped); + } - private class ProcessZoogiFungusEntry : ContextMenuEntry - { - private BaseSolenMatriarch m_Matriarch; - private PlayerMobile m_From; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public ProcessZoogiFungusEntry( BaseSolenMatriarch matriarch, PlayerMobile from ) : base( 6184 ) - { - m_Matriarch = matriarch; - m_From = from; - } + if (from.Alive) + if (from is PlayerMobile pm) + if (pm.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen) + if (qs.IsObjectiveInProgress(typeof(ProcessFungiObjective))) + list.Add(new ProcessZoogiFungusEntry(this, pm)); + } - public override void OnClick() - { - if ( m_From.Alive ) - m_From.Target = new ProcessFungiTarget( m_Matriarch, m_From ); - } - } + public void OnGivenFungi(PlayerMobile player, ZoogiFungus fungi) + { + Direction = GetDirectionTo(player); - private class ProcessFungiTarget : Target - { - private BaseSolenMatriarch m_Matriarch; - private PlayerMobile m_From; + if (player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen) + { + QuestObjective obj = qs.FindObjective(typeof(ProcessFungiObjective)); - public ProcessFungiTarget( BaseSolenMatriarch matriarch, PlayerMobile from ) : base( -1, false, TargetFlags.None ) - { - m_Matriarch = matriarch; - m_From = from; - } + if (obj != null && !obj.Completed) + { + int amount = fungi.Amount / 2; - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - from.SendLocalizedMessage( 1042021, "", 0x59 ); // Cancelled. - } + if (amount > 100) + amount = 100; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is ZoogiFungus fungus ) - { - if ( fungus.IsChildOf( m_From.Backpack ) ) - m_Matriarch.OnGivenFungi( m_From, fungus ); - else - m_From.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - } + if (amount > 0) + { + if (amount * 2 >= fungi.Amount) + fungi.Delete(); + else + fungi.Amount -= amount * 2; - public void OnGivenFungi( PlayerMobile player, ZoogiFungus fungi ) - { - Direction = GetDirectionTo( player ); + PowderOfTranslocation powder = new PowderOfTranslocation(amount); + player.AddToBackpack(powder); - if ( player.Quest is SolenMatriarchQuest qs && qs.RedSolen == RedSolen ) - { - QuestObjective obj = qs.FindObjective( typeof( ProcessFungiObjective ) ); + player.SendLocalizedMessage(1054100); // You receive some powder of translocation. - if ( obj != null && !obj.Completed ) - { - int amount = fungi.Amount / 2; + obj.Complete(); + } + } + } + } - if ( amount > 100 ) - amount = 100; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( amount > 0 ) - { - if ( amount * 2 >= fungi.Amount ) - fungi.Delete(); - else - fungi.Amount -= amount * 2; + writer.WriteEncodedInt(0); // version + } - PowderOfTranslocation powder = new PowderOfTranslocation( amount ); - player.AddToBackpack( powder ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - player.SendLocalizedMessage( 1054100 ); // You receive some powder of translocation. + int version = reader.ReadEncodedInt(); + } - obj.Complete(); - } - } - } - } + private class ProcessZoogiFungusEntry : ContextMenuEntry + { + private PlayerMobile m_From; + private BaseSolenMatriarch m_Matriarch; - public BaseSolenMatriarch( Serial serial ) : base( serial ) - { - } + public ProcessZoogiFungusEntry(BaseSolenMatriarch matriarch, PlayerMobile from) : base(6184) + { + m_Matriarch = matriarch; + m_From = from; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnClick() + { + if (m_From.Alive) + m_From.Target = new ProcessFungiTarget(m_Matriarch, m_From); + } + } - writer.WriteEncodedInt( (int) 0 ); // version - } + private class ProcessFungiTarget : Target + { + private PlayerMobile m_From; + private BaseSolenMatriarch m_Matriarch; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public ProcessFungiTarget(BaseSolenMatriarch matriarch, PlayerMobile from) : base(-1, false, TargetFlags.None) + { + m_Matriarch = matriarch; + m_From = from; + } - int version = reader.ReadEncodedInt(); - } - } + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + from.SendLocalizedMessage(1042021, "", 0x59); // Cancelled. + } - public class RedSolenMatriarch : BaseSolenMatriarch - { - public override bool RedSolen => true; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is ZoogiFungus fungus) + { + if (fungus.IsChildOf(m_From.Backpack)) + m_Matriarch.OnGivenFungi(m_From, fungus); + else + m_From.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } + } - [Constructible] - public RedSolenMatriarch() - { - } + public class RedSolenMatriarch : BaseSolenMatriarch + { + [Constructible] + public RedSolenMatriarch() + { + } - public RedSolenMatriarch( Serial serial ) : base( serial ) - { - } + public RedSolenMatriarch(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool RedSolen => true; - writer.WriteEncodedInt( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public class BlackSolenMatriarch : BaseSolenMatriarch - { - public override bool RedSolen => false; + int version = reader.ReadEncodedInt(); + } + } - [Constructible] - public BlackSolenMatriarch() - { - } + public class BlackSolenMatriarch : BaseSolenMatriarch + { + [Constructible] + public BlackSolenMatriarch() + { + } - public BlackSolenMatriarch( Serial serial ) : base( serial ) - { - } + public BlackSolenMatriarch(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool RedSolen => false; - writer.WriteEncodedInt( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Solen Matriarch/Objectives.cs b/Scripts/Engines/Quests/Solen Matriarch/Objectives.cs index 8044382ed..87f35e880 100644 --- a/Scripts/Engines/Quests/Solen Matriarch/Objectives.cs +++ b/Scripts/Engines/Quests/Solen Matriarch/Objectives.cs @@ -1,169 +1,143 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Matriarch { - public class KillInfiltratorsObjective : QuestObjective - { - public override object Message => ((SolenMatriarchQuest)System).RedSolen ? 1054086 : 1054085; + public class KillInfiltratorsObjective : QuestObjective + { + public override object Message => ((SolenMatriarchQuest)System).RedSolen ? 1054086 : 1054085; - public override int MaxProgress => 7; + public override int MaxProgress => 7; - public KillInfiltratorsObjective() - { - } + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Black/Red Solen Infiltrators killed: + gump.AddHtmlLocalized(70, 260, 270, 100, ((SolenMatriarchQuest)System).RedSolen ? 1054088 : 1054087, + BaseQuestGump.Blue, false, false); + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, MaxProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Black/Red Solen Infiltrators killed: - gump.AddHtmlLocalized( 70, 260, 270, 100, ((SolenMatriarchQuest)System).RedSolen ? 1054088 : 1054087, BaseQuestGump.Blue, false, false ); - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, MaxProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } + public override bool IgnoreYoungProtection(Mobile from) + { + if (Completed) + return false; - public override bool IgnoreYoungProtection( Mobile from ) - { - if ( Completed ) - return false; + bool redSolen = ((SolenMatriarchQuest)System).RedSolen; - bool redSolen = ((SolenMatriarchQuest)System).RedSolen; + if (redSolen) + return from is BlackSolenInfiltratorWarrior || from is BlackSolenInfiltratorQueen; + return from is RedSolenInfiltratorWarrior || from is RedSolenInfiltratorQueen; + } - if ( redSolen ) - return from is BlackSolenInfiltratorWarrior || from is BlackSolenInfiltratorQueen; - return from is RedSolenInfiltratorWarrior || from is RedSolenInfiltratorQueen; - } + public override void OnKill(BaseCreature creature, Container corpse) + { + bool redSolen = ((SolenMatriarchQuest)System).RedSolen; - public override void OnKill( BaseCreature creature, Container corpse ) - { - bool redSolen = ((SolenMatriarchQuest)System).RedSolen; + if (redSolen) + { + if (creature is BlackSolenInfiltratorWarrior || creature is BlackSolenInfiltratorQueen) + CurProgress++; + } + else + { + if (creature is RedSolenInfiltratorWarrior || creature is RedSolenInfiltratorQueen) + CurProgress++; + } + } - if ( redSolen ) - { - if ( creature is BlackSolenInfiltratorWarrior || creature is BlackSolenInfiltratorQueen ) - CurProgress++; - } - else - { - if ( creature is RedSolenInfiltratorWarrior || creature is RedSolenInfiltratorQueen ) - CurProgress++; - } - } + public override void OnComplete() + { + System.AddObjective(new ReturnAfterKillsObjective()); + } + } - public override void OnComplete() - { - System.AddObjective( new ReturnAfterKillsObjective() ); - } - } + public class ReturnAfterKillsObjective : QuestObjective + { + public override object Message => 1054090; - public class ReturnAfterKillsObjective : QuestObjective - { - public override object Message => 1054090; + public override void OnComplete() + { + System.AddConversation(new GatherWaterConversation()); + } + } - public ReturnAfterKillsObjective() - { - } + public class GatherWaterObjective : QuestObjective + { + public override object Message => 1054092; - public override void OnComplete() - { - System.AddConversation( new GatherWaterConversation() ); - } - } + public override int MaxProgress => 40; - public class GatherWaterObjective : QuestObjective - { - public override object Message => 1054092; + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + gump.AddHtmlLocalized(70, 260, 270, 100, 1054093, BaseQuestGump.Blue, false, + false); // Gallons of Water gathered: + gump.AddLabel(70, 280, 0x64, (CurProgress / 5).ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, (MaxProgress / 5).ToString()); + } + else + { + base.RenderProgress(gump); + } + } - public override int MaxProgress => 40; + public override void OnComplete() + { + System.AddObjective(new ReturnAfterWaterObjective()); + } + } - public GatherWaterObjective() - { - } + public class ReturnAfterWaterObjective : QuestObjective + { + public override object Message => 1054095; - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - gump.AddHtmlLocalized( 70, 260, 270, 100, 1054093, BaseQuestGump.Blue, false, false ); // Gallons of Water gathered: - gump.AddLabel( 70, 280, 0x64, (CurProgress / 5).ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, (MaxProgress / 5).ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } + public override void OnComplete() + { + PlayerMobile player = System.From; + bool redSolen = ((SolenMatriarchQuest)System).RedSolen; - public override void OnComplete() - { - System.AddObjective( new ReturnAfterWaterObjective() ); - } - } + bool friend = SolenMatriarchQuest.IsFriend(player, redSolen); - public class ReturnAfterWaterObjective : QuestObjective - { - public override object Message => 1054095; + System.AddConversation(new ProcessFungiConversation(friend)); - public ReturnAfterWaterObjective() - { - } + if (redSolen) + player.SolenFriendship = SolenFriendship.Red; + else + player.SolenFriendship = SolenFriendship.Black; + } + } - public override void OnComplete() - { - PlayerMobile player = System.From; - bool redSolen = ((SolenMatriarchQuest)System).RedSolen; + public class ProcessFungiObjective : QuestObjective + { + public override object Message => 1054098; - bool friend = SolenMatriarchQuest.IsFriend( player, redSolen ); + public override void OnComplete() + { + if (SolenMatriarchQuest.GiveRewardTo(System.From)) + System.Complete(); + else + System.AddConversation(new FullBackpackConversation(true)); + } + } - System.AddConversation( new ProcessFungiConversation( friend ) ); + public class GetRewardObjective : QuestObjective + { + public override object Message => 1054149; - if ( redSolen ) - player.SolenFriendship = SolenFriendship.Red; - else - player.SolenFriendship = SolenFriendship.Black; - } - } - - public class ProcessFungiObjective : QuestObjective - { - public override object Message => 1054098; - - public ProcessFungiObjective() - { - } - - public override void OnComplete() - { - if ( SolenMatriarchQuest.GiveRewardTo( System.From ) ) - { - System.Complete(); - } - else - { - System.AddConversation( new FullBackpackConversation( true ) ); - } - } - } - - public class GetRewardObjective : QuestObjective - { - public override object Message => 1054149; - - public GetRewardObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new EndConversation() ); - } - } -} + public override void OnComplete() + { + System.AddConversation(new EndConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Solen Matriarch/SolenMatriarchQuest.cs b/Scripts/Engines/Quests/Solen Matriarch/SolenMatriarchQuest.cs index 3b08a99e9..b7f11e18a 100644 --- a/Scripts/Engines/Quests/Solen Matriarch/SolenMatriarchQuest.cs +++ b/Scripts/Engines/Quests/Solen Matriarch/SolenMatriarchQuest.cs @@ -1,144 +1,124 @@ using System; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Matriarch { - public class SolenMatriarchQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( DontOfferConversation ), - typeof( AcceptConversation ), - typeof( DuringKillInfiltratorsConversation ), - typeof( GatherWaterConversation ), - typeof( DuringWaterGatheringConversation ), - typeof( ProcessFungiConversation ), - typeof( DuringFungiProcessConversation ), - typeof( FullBackpackConversation ), - typeof( EndConversation ), - typeof( KillInfiltratorsObjective ), - typeof( ReturnAfterKillsObjective ), - typeof( GatherWaterObjective ), - typeof( ReturnAfterWaterObjective ), - typeof( ProcessFungiObjective ), - typeof( GetRewardObjective ) - }; + public class SolenMatriarchQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(DontOfferConversation), + typeof(AcceptConversation), + typeof(DuringKillInfiltratorsConversation), + typeof(GatherWaterConversation), + typeof(DuringWaterGatheringConversation), + typeof(ProcessFungiConversation), + typeof(DuringFungiProcessConversation), + typeof(FullBackpackConversation), + typeof(EndConversation), + typeof(KillInfiltratorsObjective), + typeof(ReturnAfterKillsObjective), + typeof(GatherWaterObjective), + typeof(ReturnAfterWaterObjective), + typeof(ProcessFungiObjective), + typeof(GetRewardObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public SolenMatriarchQuest(PlayerMobile from, bool redSolen) : base(from) + { + RedSolen = redSolen; + } - public override object Name => 1054147; + // Serialization + public SolenMatriarchQuest() + { + } - public override object OfferMessage - { - get - { - if ( IsFriend( From, RedSolen ) ) - { - /* The Solen Matriarch smiles happily as you greet her.

- * - * Hello again. It is always good to see a friend of our colony.

- * - * Would you like me to process some zoogi fungus into powder of translocation - * for you? I would be happy to do so if you will first undertake a couple - * tasks for me.

- * - * First, I would like for you to eliminate some infiltrators from the other - * solen colony. They are spying on my colony, and I fear for the safety of my - * people. They must be slain.

- * - * After that, I must ask that you gather some water for me. Our water supplies - * are inadequate, so we must try to supplement our reserve using water vats here - * in our lair.

- * - * Will you accept my offer? - */ - return 1054083; - } + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - /* The Solen Matriarch smiles happily as she eats the seed you offered.

- * - * I think you for that seed. I was quite delicious. So full of flavor.

- * - * Hmm... if you would like, I could make you a friend of my colony. This would stop - * the warriors, workers, and queens of my colony from thinking you are an intruder, - * thus they would not attack you. In addition, as a friend of my colony I will process - * zoogi fungus into powder of translocation for you.

- * - * To become a friend of my colony, I ask that you complete a couple tasks for me. These - * are the same tasks I will ask of you when you wish me to process zoogi fungus, - * by the way.

- * - * First, I would like for you to eliminate some infiltrators from the other solen colony. - * They are spying on my colony, and I fear for the safety of my people. They must - * be slain.

- * - * After that, I must ask that you gather some water for me. Our water supplies are - * inadequate, so we must try to supplement our reserve using water vats here in our - * lair.

- * - * Will you accept my offer? - */ - return 1054082; - } - } + public override object Name => 1054147; - public override TimeSpan RestartDelay => TimeSpan.Zero; - public override bool IsTutorial => false; + public override object OfferMessage + { + get + { + if (IsFriend(From, RedSolen)) return 1054083; - public override int Picture => 0x15C9; + /* The Solen Matriarch smiles happily as she eats the seed you offered.

+ * + * I think you for that seed. I was quite delicious. So full of flavor.

+ * + * Hmm... if you would like, I could make you a friend of my colony. This would stop + * the warriors, workers, and queens of my colony from thinking you are an intruder, + * thus they would not attack you. In addition, as a friend of my colony I will process + * zoogi fungus into powder of translocation for you.

+ * + * To become a friend of my colony, I ask that you complete a couple tasks for me. These + * are the same tasks I will ask of you when you wish me to process zoogi fungus, + * by the way.

+ * + * First, I would like for you to eliminate some infiltrators from the other solen colony. + * They are spying on my colony, and I fear for the safety of my people. They must + * be slain.

+ * + * After that, I must ask that you gather some water for me. Our water supplies are + * inadequate, so we must try to supplement our reserve using water vats here in our + * lair.

+ * + * Will you accept my offer? + */ + return 1054082; + } + } - public bool RedSolen { get; private set; } + public override TimeSpan RestartDelay => TimeSpan.Zero; + public override bool IsTutorial => false; - public SolenMatriarchQuest( PlayerMobile from, bool redSolen ) : base( from ) - { - RedSolen = redSolen; - } + public override int Picture => 0x15C9; - // Serialization - public SolenMatriarchQuest() - { - } + public bool RedSolen{ get; private set; } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - RedSolen = reader.ReadBool(); - } + RedSolen = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) RedSolen ); - } + writer.Write(RedSolen); + } - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } + AddConversation(new AcceptConversation()); + } - public static bool IsFriend( PlayerMobile player, bool redSolen ) - { - if ( redSolen ) - return player.SolenFriendship == SolenFriendship.Red; - return player.SolenFriendship == SolenFriendship.Black; - } + public static bool IsFriend(PlayerMobile player, bool redSolen) + { + if (redSolen) + return player.SolenFriendship == SolenFriendship.Red; + return player.SolenFriendship == SolenFriendship.Black; + } - public static bool GiveRewardTo( PlayerMobile player ) - { - Gold gold = new Gold( Utility.RandomMinMax( 250, 350 ) ); + public static bool GiveRewardTo(PlayerMobile player) + { + Gold gold = new Gold(Utility.RandomMinMax(250, 350)); - if ( player.PlaceInBackpack( gold ) ) - { - player.SendLocalizedMessage( 1054076 ); // You have been given some gold. - return true; - } + if (player.PlaceInBackpack(gold)) + { + player.SendLocalizedMessage(1054076); // You have been given some gold. + return true; + } - gold.Delete(); - return false; - } - } -} + gold.Delete(); + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Study of the Solen Hive/Conversations.cs b/Scripts/Engines/Quests/Study of the Solen Hive/Conversations.cs index e4ef8c891..db4a33c65 100644 --- a/Scripts/Engines/Quests/Study of the Solen Hive/Conversations.cs +++ b/Scripts/Engines/Quests/Study of the Solen Hive/Conversations.cs @@ -1,77 +1,53 @@ namespace Server.Engines.Quests.Naturalist { - public class DontOfferConversation : QuestConversation - { - public override object Message => 1054052; + public class DontOfferConversation : QuestConversation + { + public override object Message => 1054052; - public override bool Logged => false; + public override bool Logged => false; + } - public DontOfferConversation() - { - } - } + public class AcceptConversation : QuestConversation + { + public override object Message => 1054043; - public class AcceptConversation : QuestConversation - { - public override object Message => 1054043; + public override void OnRead() + { + System.AddObjective(new StudyNestsObjective()); + } + } - public AcceptConversation() - { - } + public class NaturalistDuringStudyConversation : QuestConversation + { + public override object Message => 1054049; - public override void OnRead() - { - System.AddObjective( new StudyNestsObjective() ); - } - } + public override bool Logged => false; + } - public class NaturalistDuringStudyConversation : QuestConversation - { - public override object Message => 1054049; + public class EndConversation : QuestConversation + { + public override object Message => 1054050; - public override bool Logged => false; + public override void OnRead() + { + System.Complete(); + } + } - public NaturalistDuringStudyConversation() - { - } - } + public class SpecialEndConversation : QuestConversation + { + public override object Message => 1054051; - public class EndConversation : QuestConversation - { - public override object Message => 1054050; + public override void OnRead() + { + System.Complete(); + } + } - public EndConversation() - { - } + public class FullBackpackConversation : QuestConversation + { + public override object Message => 1054053; - public override void OnRead() - { - System.Complete(); - } - } - - public class SpecialEndConversation : QuestConversation - { - public override object Message => 1054051; - - public SpecialEndConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } - - public class FullBackpackConversation : QuestConversation - { - public override object Message => 1054053; - - public override bool Logged => false; - - public FullBackpackConversation() - { - } - } -} + public override bool Logged => false; + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Study of the Solen Hive/Mobiles/Naturalist.cs b/Scripts/Engines/Quests/Study of the Solen Hive/Mobiles/Naturalist.cs index b4ab07132..e30ed0088 100644 --- a/Scripts/Engines/Quests/Study of the Solen Hive/Mobiles/Naturalist.cs +++ b/Scripts/Engines/Quests/Study of the Solen Hive/Mobiles/Naturalist.cs @@ -1,151 +1,191 @@ -using Server.Mobiles; -using Server.Items; using Server.Engines.Plants; +using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Naturalist { - public class Naturalist : BaseQuester - { - [Constructible] - public Naturalist() : base( "the Naturalist" ) - { - } + public class Naturalist : BaseQuester + { + [Constructible] + public Naturalist() : base("the Naturalist") + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public Naturalist(Serial serial) : base(serial) + { + } - Hue = Utility.RandomSkinHue(); + public override void InitBody() + { + InitStats(100, 100, 25); - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + Hue = Utility.RandomSkinHue(); - public override void InitOutfit() - { - AddItem( new Tunic( 0x598 ) ); - AddItem( new LongPants( 0x59B ) ); - AddItem( new Boots() ); + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); + } + + public override void InitOutfit() + { + AddItem(new Tunic(0x598)); + AddItem(new LongPants(0x59B)); + AddItem(new Boots()); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); - } + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - if ( player.Quest is StudyOfSolenQuest qs && qs.Naturalist == this ) - { - if ( qs.FindObjective( typeof( StudyNestsObjective ) ) is StudyNestsObjective study ) - { - if ( !study.Completed ) - { - PlaySound( 0x41F ); - qs.AddConversation( new NaturalistDuringStudyConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( ReturnToNaturalistObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + if (player.Quest is StudyOfSolenQuest qs && qs.Naturalist == this) + { + if (qs.FindObjective(typeof(StudyNestsObjective)) is StudyNestsObjective study) + { + if (!study.Completed) + { + PlaySound(0x41F); + qs.AddConversation(new NaturalistDuringStudyConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(ReturnToNaturalistObjective)); - if ( obj != null && !obj.Completed ) - { - Seed reward; + if (obj != null && !obj.Completed) + { + Seed reward; - PlantType type; - switch ( Utility.Random( 17 ) ) - { - case 0: type = PlantType.CampionFlowers; break; - case 1: type = PlantType.Poppies; break; - case 2: type = PlantType.Snowdrops; break; - case 3: type = PlantType.Bulrushes; break; - case 4: type = PlantType.Lilies; break; - case 5: type = PlantType.PampasGrass; break; - case 6: type = PlantType.Rushes; break; - case 7: type = PlantType.ElephantEarPlant; break; - case 8: type = PlantType.Fern; break; - case 9: type = PlantType.PonytailPalm; break; - case 10: type = PlantType.SmallPalm; break; - case 11: type = PlantType.CenturyPlant; break; - case 12: type = PlantType.WaterPlant; break; - case 13: type = PlantType.SnakePlant; break; - case 14: type = PlantType.PricklyPearCactus; break; - case 15: type = PlantType.BarrelCactus; break; - default: type = PlantType.TribarrelCactus; break; - } + PlantType type; + switch (Utility.Random(17)) + { + case 0: + type = PlantType.CampionFlowers; + break; + case 1: + type = PlantType.Poppies; + break; + case 2: + type = PlantType.Snowdrops; + break; + case 3: + type = PlantType.Bulrushes; + break; + case 4: + type = PlantType.Lilies; + break; + case 5: + type = PlantType.PampasGrass; + break; + case 6: + type = PlantType.Rushes; + break; + case 7: + type = PlantType.ElephantEarPlant; + break; + case 8: + type = PlantType.Fern; + break; + case 9: + type = PlantType.PonytailPalm; + break; + case 10: + type = PlantType.SmallPalm; + break; + case 11: + type = PlantType.CenturyPlant; + break; + case 12: + type = PlantType.WaterPlant; + break; + case 13: + type = PlantType.SnakePlant; + break; + case 14: + type = PlantType.PricklyPearCactus; + break; + case 15: + type = PlantType.BarrelCactus; + break; + default: + type = PlantType.TribarrelCactus; + break; + } - if ( study.StudiedSpecialNest ) - { - reward = new Seed( type, PlantHue.FireRed, false ); - } - else - { - PlantHue hue; - switch ( Utility.Random( 3 ) ) - { - case 0: hue = PlantHue.Pink; break; - case 1: hue = PlantHue.Magenta; break; - default: hue = PlantHue.Aqua; break; - } + if (study.StudiedSpecialNest) + { + reward = new Seed(type, PlantHue.FireRed, false); + } + else + { + PlantHue hue; + switch (Utility.Random(3)) + { + case 0: + hue = PlantHue.Pink; + break; + case 1: + hue = PlantHue.Magenta; + break; + default: + hue = PlantHue.Aqua; + break; + } - reward = new Seed( type, hue, false ); - } + reward = new Seed(type, hue, false); + } - if ( player.PlaceInBackpack( reward ) ) - { - obj.Complete(); + if (player.PlaceInBackpack(reward)) + { + obj.Complete(); - PlaySound( 0x449 ); - PlaySound( 0x41B ); + PlaySound(0x449); + PlaySound(0x41B); - if ( study.StudiedSpecialNest ) - qs.AddConversation( new SpecialEndConversation() ); - else - qs.AddConversation( new EndConversation() ); - } - else - { - reward.Delete(); + if (study.StudiedSpecialNest) + qs.AddConversation(new SpecialEndConversation()); + else + qs.AddConversation(new EndConversation()); + } + else + { + reward.Delete(); - qs.AddConversation( new FullBackpackConversation() ); - } - } - } - } - } - else - { - QuestSystem newQuest = new StudyOfSolenQuest( player, this ); + qs.AddConversation(new FullBackpackConversation()); + } + } + } + } + } + else + { + QuestSystem newQuest = new StudyOfSolenQuest(player, this); - if ( player.Quest == null && QuestSystem.CanOfferQuest( player, typeof( StudyOfSolenQuest ) ) ) - { - PlaySound( 0x42F ); - newQuest.SendOffer(); - } - else - { - PlaySound( 0x448 ); - newQuest.AddConversation( new DontOfferConversation() ); - } - } - } + if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(StudyOfSolenQuest))) + { + PlaySound(0x42F); + newQuest.SendOffer(); + } + else + { + PlaySound(0x448); + newQuest.AddConversation(new DontOfferConversation()); + } + } + } - public Naturalist( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); // version + } - writer.WriteEncodedInt( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Study of the Solen Hive/NestArea.cs b/Scripts/Engines/Quests/Study of the Solen Hive/NestArea.cs index f3fb3aba5..d62936d6d 100644 --- a/Scripts/Engines/Quests/Study of the Solen Hive/NestArea.cs +++ b/Scripts/Engines/Quests/Study of the Solen Hive/NestArea.cs @@ -1,85 +1,78 @@ namespace Server.Engines.Quests.Naturalist { - public class NestArea - { - private static readonly NestArea[] m_Areas = { - new NestArea( false, new Rectangle2D( 5861, 1787, 26, 25 ) ), + public class NestArea + { + private static readonly NestArea[] m_Areas = + { + new NestArea(false, new Rectangle2D(5861, 1787, 26, 25)), - new NestArea( false, new Rectangle2D( 5734, 1788, 14, 50 ), - new Rectangle2D( 5748, 1800, 3, 34 ), - new Rectangle2D( 5751, 1808, 2, 20 ) ), + new NestArea(false, new Rectangle2D(5734, 1788, 14, 50), + new Rectangle2D(5748, 1800, 3, 34), + new Rectangle2D(5751, 1808, 2, 20)), - new NestArea( false, new Rectangle2D( 5907, 1908, 19, 43 ) ), + new NestArea(false, new Rectangle2D(5907, 1908, 19, 43)), - new NestArea( false, new Rectangle2D( 5721, 1926, 24, 29 ), - new Rectangle2D( 5745, 1935, 7, 22 ) ), + new NestArea(false, new Rectangle2D(5721, 1926, 24, 29), + new Rectangle2D(5745, 1935, 7, 22)), - new NestArea( true, new Rectangle2D( 5651, 1853, 21, 32 ), - new Rectangle2D( 5672, 1857, 6, 20 ) ) - }; + new NestArea(true, new Rectangle2D(5651, 1853, 21, 32), + new Rectangle2D(5672, 1857, 6, 20)) + }; - public static int NonSpecialCount - { - get - { - int n = 0; - foreach ( NestArea area in m_Areas ) - { - if ( !area.Special ) - n++; - } - return n; - } - } + private Rectangle2D[] m_Rects; - public static NestArea Find( IPoint2D p ) - { - foreach ( NestArea area in m_Areas ) - { - if ( area.Contains( p ) ) - return area; - } - return null; - } + private NestArea(bool special, params Rectangle2D[] rects) + { + Special = special; + m_Rects = rects; + } - public static NestArea GetByID( int id ) - { - if ( id >= 0 && id < m_Areas.Length ) - return m_Areas[id]; - return null; - } + public static int NonSpecialCount + { + get + { + int n = 0; + foreach (NestArea area in m_Areas) + if (!area.Special) + n++; + return n; + } + } - private Rectangle2D[] m_Rects; + public bool Special{ get; } - public bool Special { get; } + public int ID + { + get + { + for (int i = 0; i < m_Areas.Length; i++) + if (m_Areas[i] == this) + return i; + return 0; + } + } - public int ID - { - get - { - for ( int i = 0; i < m_Areas.Length; i++ ) - { - if ( m_Areas[i] == this ) - return i; - } - return 0; - } - } + public static NestArea Find(IPoint2D p) + { + foreach (NestArea area in m_Areas) + if (area.Contains(p)) + return area; + return null; + } - private NestArea( bool special, params Rectangle2D[] rects ) - { - Special = special; - m_Rects = rects; - } + public static NestArea GetByID(int id) + { + if (id >= 0 && id < m_Areas.Length) + return m_Areas[id]; + return null; + } - public bool Contains( IPoint2D p ) - { - foreach ( Rectangle2D rect in m_Rects ) - { - if ( rect.Contains( p ) ) - return true; - } - return false; - } - } + public bool Contains(IPoint2D p) + { + foreach (Rectangle2D rect in m_Rects) + if (rect.Contains(p)) + return true; + return false; + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Study of the Solen Hive/Objectives.cs b/Scripts/Engines/Quests/Study of the Solen Hive/Objectives.cs index ee0994d1b..ddcaa35ba 100644 --- a/Scripts/Engines/Quests/Study of the Solen Hive/Objectives.cs +++ b/Scripts/Engines/Quests/Study of the Solen Hive/Objectives.cs @@ -4,176 +4,181 @@ using Server.Mobiles; namespace Server.Engines.Quests.Naturalist { - public class StudyNestsObjective : QuestObjective - { - public override object Message => 1054044; + public class StudyNestsObjective : QuestObjective + { + private NestArea m_CurrentNest; - public override int MaxProgress => NestArea.NonSpecialCount; + private ArrayList m_StudiedNests; + private DateTime m_StudyBegin; + private StudyState m_StudyState; - private NestArea m_CurrentNest; - private DateTime m_StudyBegin; + public StudyNestsObjective() + { + m_StudiedNests = new ArrayList(); + } - private enum StudyState { Inactive, FirstStep, SecondStep } - private StudyState m_StudyState; + public override object Message => 1054044; - private ArrayList m_StudiedNests; + public override int MaxProgress => NestArea.NonSpecialCount; - public bool StudiedSpecialNest { get; private set; } + public bool StudiedSpecialNest{ get; private set; } - public StudyNestsObjective() - { - m_StudiedNests = new ArrayList(); - } + public override bool GetTimerEvent() + { + return true; + } - public override bool GetTimerEvent() - { - return true; - } + public override void CheckProgress() + { + PlayerMobile from = System.From; - public override void CheckProgress() - { - PlayerMobile from = System.From; + if (m_CurrentNest != null) + { + NestArea nest = m_CurrentNest; - if ( m_CurrentNest != null ) - { - NestArea nest = m_CurrentNest; + if ((from.Map == Map.Trammel || from.Map == Map.Felucca) && nest.Contains(from)) + { + if (m_StudyState != StudyState.Inactive) + { + TimeSpan time = DateTime.UtcNow - m_StudyBegin; - if ( ( from.Map == Map.Trammel || from.Map == Map.Felucca ) && nest.Contains( from ) ) - { - if ( m_StudyState != StudyState.Inactive ) - { - TimeSpan time = DateTime.UtcNow - m_StudyBegin; + if (time > TimeSpan.FromSeconds(30.0)) + { + m_StudiedNests.Add(nest); + m_StudyState = StudyState.Inactive; - if ( time > TimeSpan.FromSeconds( 30.0 ) ) - { - m_StudiedNests.Add( nest ); - m_StudyState = StudyState.Inactive; + if (m_CurrentNest.Special) + { + from.SendLocalizedMessage( + 1054057); // You complete your examination of this bizarre Egg Nest. The Naturalist will undoubtedly be quite interested in these notes! + StudiedSpecialNest = true; + } + else + { + from.SendLocalizedMessage( + 1054054); // You have completed your study of this Solen Egg Nest. You put your notes away. + CurProgress++; + } + } + else if (m_StudyState == StudyState.FirstStep && time > TimeSpan.FromSeconds(15.0)) + { + if (!nest.Special) + from.SendLocalizedMessage( + 1054058); // You begin recording your completed notes on a bit of parchment. - if ( m_CurrentNest.Special ) - { - from.SendLocalizedMessage( 1054057 ); // You complete your examination of this bizarre Egg Nest. The Naturalist will undoubtedly be quite interested in these notes! - StudiedSpecialNest = true; - } - else - { - from.SendLocalizedMessage( 1054054 ); // You have completed your study of this Solen Egg Nest. You put your notes away. - CurProgress++; - } - } - else if ( m_StudyState == StudyState.FirstStep && time > TimeSpan.FromSeconds( 15.0 ) ) - { - if ( !nest.Special ) - from.SendLocalizedMessage( 1054058 ); // You begin recording your completed notes on a bit of parchment. + m_StudyState = StudyState.SecondStep; + } + } + } + else + { + if (m_StudyState != StudyState.Inactive) + from.SendLocalizedMessage( + 1054046); // You abandon your study of the Solen Egg Nest without gathering the needed information. - m_StudyState = StudyState.SecondStep; - } - } - } - else - { - if ( m_StudyState != StudyState.Inactive ) - from.SendLocalizedMessage( 1054046 ); // You abandon your study of the Solen Egg Nest without gathering the needed information. + m_CurrentNest = null; + } + } + else if (from.Map == Map.Trammel || from.Map == Map.Felucca) + { + NestArea nest = NestArea.Find(from); - m_CurrentNest = null; - } - } - else if ( from.Map == Map.Trammel || from.Map == Map.Felucca ) - { - NestArea nest = NestArea.Find( from ); + if (nest != null) + { + m_CurrentNest = nest; + m_StudyBegin = DateTime.UtcNow; - if ( nest != null ) - { - m_CurrentNest = nest; - m_StudyBegin = DateTime.UtcNow; + if (m_StudiedNests.Contains(nest)) + { + m_StudyState = StudyState.Inactive; - if ( m_StudiedNests.Contains( nest ) ) - { - m_StudyState = StudyState.Inactive; + from.SendLocalizedMessage( + 1054047); // You glance at the Egg Nest, realizing you've already studied this one. + } + else + { + m_StudyState = StudyState.FirstStep; - from.SendLocalizedMessage( 1054047 ); // You glance at the Egg Nest, realizing you've already studied this one. - } - else - { - m_StudyState = StudyState.FirstStep; + if (nest.Special) + from.SendLocalizedMessage( + 1054056); // You notice something very odd about this Solen Egg Nest. You begin taking notes. + else + from.SendLocalizedMessage( + 1054045); // You begin studying the Solen Egg Nest to gather information. - if ( nest.Special ) - from.SendLocalizedMessage( 1054056 ); // You notice something very odd about this Solen Egg Nest. You begin taking notes. - else - from.SendLocalizedMessage( 1054045 ); // You begin studying the Solen Egg Nest to gather information. + if (from.Female) + from.PlaySound(0x30B); + else + from.PlaySound(0x419); + } + } + } + } - if ( from.Female ) - from.PlaySound( 0x30B ); - else - from.PlaySound( 0x419 ); - } - } - } - } + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + gump.AddHtmlLocalized(70, 260, 270, 100, 1054055, BaseQuestGump.Blue, false, false); // Solen Nests Studied : + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, MaxProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - gump.AddHtmlLocalized( 70, 260, 270, 100, 1054055, BaseQuestGump.Blue, false, false ); // Solen Nests Studied : - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, MaxProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } + public override void OnComplete() + { + System.AddObjective(new ReturnToNaturalistObjective()); + } - public override void OnComplete() - { - System.AddObjective( new ReturnToNaturalistObjective() ); - } + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + int count = reader.ReadEncodedInt(); + for (int i = 0; i < count; i++) + { + NestArea nest = NestArea.GetByID(reader.ReadEncodedInt()); + m_StudiedNests.Add(nest); + } - int count = reader.ReadEncodedInt(); - for ( int i = 0; i < count; i++ ) - { - NestArea nest = NestArea.GetByID( reader.ReadEncodedInt() ); - m_StudiedNests.Add( nest ); - } + StudiedSpecialNest = reader.ReadBool(); + } - StudiedSpecialNest = reader.ReadBool(); - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + writer.WriteEncodedInt(m_StudiedNests.Count); + foreach (NestArea nest in m_StudiedNests) writer.WriteEncodedInt(nest.ID); - writer.WriteEncodedInt( (int) m_StudiedNests.Count ); - foreach ( NestArea nest in m_StudiedNests ) - { - writer.WriteEncodedInt( (int) nest.ID ); - } + writer.Write(StudiedSpecialNest); + } - writer.Write( (bool) StudiedSpecialNest ); - } - } + private enum StudyState + { + Inactive, + FirstStep, + SecondStep + } + } - public class ReturnToNaturalistObjective : QuestObjective - { - public override object Message => 1054048; + public class ReturnToNaturalistObjective : QuestObjective + { + public override object Message => 1054048; - public ReturnToNaturalistObjective() - { - } + public override void RenderProgress(BaseQuestGump gump) + { + string count = NestArea.NonSpecialCount.ToString(); - public override void RenderProgress( BaseQuestGump gump ) - { - string count = NestArea.NonSpecialCount.ToString(); - - gump.AddHtmlLocalized( 70, 260, 270, 100, 1054055, BaseQuestGump.Blue, false, false ); // Solen Nests Studied : - gump.AddLabel( 70, 280, 0x64, count ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, count ); - } - } -} + gump.AddHtmlLocalized(70, 260, 270, 100, 1054055, BaseQuestGump.Blue, false, false); // Solen Nests Studied : + gump.AddLabel(70, 280, 0x64, count); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, count); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Study of the Solen Hive/StudyOfSolenQuest.cs b/Scripts/Engines/Quests/Study of the Solen Hive/StudyOfSolenQuest.cs index fcdd7c81d..aa05412da 100644 --- a/Scripts/Engines/Quests/Study of the Solen Hive/StudyOfSolenQuest.cs +++ b/Scripts/Engines/Quests/Study of the Solen Hive/StudyOfSolenQuest.cs @@ -3,63 +3,64 @@ using Server.Mobiles; namespace Server.Engines.Quests.Naturalist { - public class StudyOfSolenQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( StudyNestsObjective ), - typeof( ReturnToNaturalistObjective ), - typeof( DontOfferConversation ), - typeof( AcceptConversation ), - typeof( NaturalistDuringStudyConversation ), - typeof( EndConversation ), - typeof( SpecialEndConversation ), - typeof( FullBackpackConversation ) - }; + public class StudyOfSolenQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(StudyNestsObjective), + typeof(ReturnToNaturalistObjective), + typeof(DontOfferConversation), + typeof(AcceptConversation), + typeof(NaturalistDuringStudyConversation), + typeof(EndConversation), + typeof(SpecialEndConversation), + typeof(FullBackpackConversation) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public StudyOfSolenQuest(PlayerMobile from, Naturalist naturalist) : base(from) + { + Naturalist = naturalist; + } - public override object Name => 1054041; + // Serialization + public StudyOfSolenQuest() + { + } - public override object OfferMessage => 1054042; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override TimeSpan RestartDelay => TimeSpan.Zero; - public override bool IsTutorial => false; + public override object Name => 1054041; - public override int Picture => 0x15C7; + public override object OfferMessage => 1054042; - public Naturalist Naturalist { get; private set; } + public override TimeSpan RestartDelay => TimeSpan.Zero; + public override bool IsTutorial => false; - public StudyOfSolenQuest( PlayerMobile from, Naturalist naturalist ) : base( from ) - { - Naturalist = naturalist; - } + public override int Picture => 0x15C7; - // Serialization - public StudyOfSolenQuest() - { - } + public Naturalist Naturalist{ get; private set; } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - Naturalist = (Naturalist) reader.ReadMobile(); - } + Naturalist = (Naturalist)reader.ReadMobile(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (Mobile) Naturalist ); - } + writer.Write(Naturalist); + } - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - Naturalist?.PlaySound( 0x431 ); + Naturalist?.PlaySound(0x431); - AddConversation( new AcceptConversation() ); - } - } -} + AddConversation(new AcceptConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Terrible Hatchlings/Conversations.cs b/Scripts/Engines/Quests/Terrible Hatchlings/Conversations.cs index ec6f993e1..f3c3623a3 100644 --- a/Scripts/Engines/Quests/Terrible Hatchlings/Conversations.cs +++ b/Scripts/Engines/Quests/Terrible Hatchlings/Conversations.cs @@ -1,52 +1,36 @@ namespace Server.Engines.Quests.Zento { - public class AcceptConversation : QuestConversation - { - public override object Message => 1049092; + public class AcceptConversation : QuestConversation + { + public override object Message => 1049092; - public AcceptConversation() - { - } + public override void OnRead() + { + System.AddObjective(new FirstKillObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new FirstKillObjective() ); - } - } + public class DirectionConversation : QuestConversation + { + public override object Message => 1063323; - public class DirectionConversation : QuestConversation - { - public override object Message => 1063323; + public override bool Logged => false; + } - public override bool Logged => false; + public class TakeCareConversation : QuestConversation + { + public override object Message => 1063324; - public DirectionConversation() - { - } - } + public override bool Logged => false; + } - public class TakeCareConversation : QuestConversation - { - public override object Message => 1063324; + public class EndConversation : QuestConversation + { + public override object Message => 1063321; - public override bool Logged => false; - - public TakeCareConversation() - { - } - } - - public class EndConversation : QuestConversation - { - public override object Message => 1063321; - - public EndConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } -} + public override void OnRead() + { + System.Complete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Terrible Hatchlings/Mobiles/AnsellaGryen.cs b/Scripts/Engines/Quests/Terrible Hatchlings/Mobiles/AnsellaGryen.cs index 2f0ad16ae..387c6e729 100644 --- a/Scripts/Engines/Quests/Terrible Hatchlings/Mobiles/AnsellaGryen.cs +++ b/Scripts/Engines/Quests/Terrible Hatchlings/Mobiles/AnsellaGryen.cs @@ -1,139 +1,143 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Zento { - public class AnsellaGryen : BaseQuester - { - public override string DefaultName => "Ansella Gryen"; + public class AnsellaGryen : BaseQuester + { + [Constructible] + public AnsellaGryen() + { + } - [Constructible] - public AnsellaGryen() - { - } + public AnsellaGryen(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Ansella Gryen"; - Hue = 0x83EA; + public override void InitBody() + { + InitStats(100, 100, 25); - Female = true; - Body = 0x191; - } + Hue = 0x83EA; - public override void InitOutfit() - { - HairItemID = 0x203B; - HairHue = 0x1BB; + Female = true; + Body = 0x191; + } - AddItem( new SamuraiTabi( 0x8FD ) ); - AddItem( new FemaleKimono( 0x4B6 ) ); - AddItem( new Obi( 0x526 ) ); + public override void InitOutfit() + { + HairItemID = 0x203B; + HairHue = 0x1BB; - AddItem( new GoldBracelet() ); - } + AddItem(new SamuraiTabi(0x8FD)); + AddItem(new FemaleKimono(0x4B6)); + AddItem(new Obi(0x526)); - public override int GetAutoTalkRange( PlayerMobile m ) - { - if ( m.Quest == null ) - return 3; - return -1; - } + AddItem(new GoldBracelet()); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override int GetAutoTalkRange(PlayerMobile m) + { + if (m.Quest == null) + return 3; + return -1; + } - if ( qs is TerribleHatchlingsQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FirstKillObjective ) ) ) - { - qs.AddConversation( new DirectionConversation() ); - } - else if ( qs.IsObjectiveInProgress( typeof( SecondKillObjective ) ) - || qs.IsObjectiveInProgress( typeof( ThirdKillObjective ) ) ) - { - qs.AddConversation( new TakeCareConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( ReturnObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + if (qs is TerribleHatchlingsQuest) + { + if (qs.IsObjectiveInProgress(typeof(FirstKillObjective))) + { + qs.AddConversation(new DirectionConversation()); + } + else if (qs.IsObjectiveInProgress(typeof(SecondKillObjective)) + || qs.IsObjectiveInProgress(typeof(ThirdKillObjective))) + { + qs.AddConversation(new TakeCareConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(ReturnObjective)); - cont.DropItem( new Gold( Utility.RandomMinMax( 100, 200 ) ) ); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - if ( Utility.RandomBool() ) - { - if ( Loot.Construct( Loot.SEWeaponTypes ) is BaseWeapon weapon ) - { - BaseRunicTool.ApplyAttributesTo( weapon, 3, 10, 30 ); - cont.DropItem( weapon ); - } - } - else - { - if ( Loot.Construct( Loot.SEArmorTypes ) is BaseArmor armor ) - { - BaseRunicTool.ApplyAttributesTo( armor, 1, 10, 20 ); - cont.DropItem( armor ); - } - } + cont.DropItem(new Gold(Utility.RandomMinMax(100, 200))); - if ( player.PlaceInBackpack( cont ) ) - { - obj.Complete(); - } - else - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - } - } - else - { - TerribleHatchlingsQuest newQuest = new TerribleHatchlingsQuest( player ); - bool inRestartPeriod = false; + if (Utility.RandomBool()) + { + if (Loot.Construct(Loot.SEWeaponTypes) is BaseWeapon weapon) + { + BaseRunicTool.ApplyAttributesTo(weapon, 3, 10, 30); + cont.DropItem(weapon); + } + } + else + { + if (Loot.Construct(Loot.SEArmorTypes) is BaseArmor armor) + { + BaseRunicTool.ApplyAttributesTo(armor, 1, 10, 20); + cont.DropItem(armor); + } + } - if ( qs != null ) - { - if ( contextMenu ) - SayTo( player, 1063322 ); // Before you can help me with the Terrible Hatchlings, you'll need to finish the quest you've already taken! - } - else if ( QuestSystem.CanOfferQuest( player, typeof( TerribleHatchlingsQuest ), out inRestartPeriod ) ) - { - newQuest.SendOffer(); - } - else if ( inRestartPeriod && contextMenu ) - { - SayTo( player, 1049357 ); // I have nothing more for you at this time. - } - } - } + if (player.PlaceInBackpack(cont)) + { + obj.Complete(); + } + else + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + } + } + else + { + TerribleHatchlingsQuest newQuest = new TerribleHatchlingsQuest(player); + bool inRestartPeriod = false; - public AnsellaGryen( Serial serial ) : base( serial ) - { - } + if (qs != null) + { + if (contextMenu) + SayTo(player, + 1063322); // Before you can help me with the Terrible Hatchlings, you'll need to finish the quest you've already taken! + } + else if (QuestSystem.CanOfferQuest(player, typeof(TerribleHatchlingsQuest), out inRestartPeriod)) + { + newQuest.SendOffer(); + } + else if (inRestartPeriod && contextMenu) + { + SayTo(player, 1049357); // I have nothing more for you at this time. + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - public override void TurnToTokuno() { } - } -} + public override void TurnToTokuno() + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Terrible Hatchlings/Objectives.cs b/Scripts/Engines/Quests/Terrible Hatchlings/Objectives.cs index 17f39546f..345c25265 100644 --- a/Scripts/Engines/Quests/Terrible Hatchlings/Objectives.cs +++ b/Scripts/Engines/Quests/Terrible Hatchlings/Objectives.cs @@ -3,142 +3,130 @@ using Server.Mobiles; namespace Server.Engines.Quests.Zento { - public class FirstKillObjective : QuestObjective - { - public override object Message => 1063316; + public class FirstKillObjective : QuestObjective + { + public override object Message => 1063316; - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Deathwatch Beetle Hatchlings killed: - gump.AddHtmlLocalized( 70, 260, 270, 100, 1063318, 0x12DC6BF, false, false ); + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Deathwatch Beetle Hatchlings killed: + gump.AddHtmlLocalized(70, 260, 270, 100, 1063318, 0x12DC6BF, false, false); - gump.AddLabel( 70, 280, 0x64, "0" ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, "10" ); - } - else - { - base.RenderProgress( gump ); - } - } + gump.AddLabel(70, 280, 0x64, "0"); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, "10"); + } + else + { + base.RenderProgress(gump); + } + } - public FirstKillObjective() - { - } + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is DeathwatchBeetleHatchling) + Complete(); + } - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is DeathwatchBeetleHatchling ) - Complete(); - } + public override void OnComplete() + { + System.AddObjective(new SecondKillObjective()); + } + } - public override void OnComplete() - { - System.AddObjective( new SecondKillObjective() ); - } - } + public class SecondKillObjective : QuestObjective + { + public override object Message => 1063320; - public class SecondKillObjective : QuestObjective - { - public override object Message => 1063320; + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Deathwatch Beetle Hatchlings killed: + gump.AddHtmlLocalized(70, 260, 270, 100, 1063318, 0x12DC6BF, false, false); - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Deathwatch Beetle Hatchlings killed: - gump.AddHtmlLocalized( 70, 260, 270, 100, 1063318, 0x12DC6BF, false, false ); + gump.AddLabel(70, 280, 0x64, "1"); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, "10"); + } + else + { + base.RenderProgress(gump); + } + } - gump.AddLabel( 70, 280, 0x64, "1" ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, "10" ); - } - else - { - base.RenderProgress( gump ); - } - } + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is DeathwatchBeetleHatchling) + { + Complete(); + System.AddObjective(new ThirdKillObjective(2)); + } + } - public SecondKillObjective() - { - } + public override void OnRead() + { + if (!Completed) + { + Complete(); + System.AddObjective(new ThirdKillObjective(1)); + } + } + } - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is DeathwatchBeetleHatchling ) - { - Complete(); - System.AddObjective( new ThirdKillObjective( 2 ) ); - } - } + public class ThirdKillObjective : QuestObjective + { + public ThirdKillObjective(int startingProgress) + { + CurProgress = startingProgress; + } - public override void OnRead() - { - if ( !Completed ) - { - Complete(); - System.AddObjective( new ThirdKillObjective( 1 ) ); - } - } - } + public ThirdKillObjective() + { + } - public class ThirdKillObjective : QuestObjective - { - public override object Message => 1063319; + public override object Message => 1063319; - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - // Deathwatch Beetle Hatchlings killed: - gump.AddHtmlLocalized( 70, 260, 270, 100, 1063318, 0x12DC6BF, false, false ); + public override int MaxProgress => 10; - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, "10" ); - } - else - { - base.RenderProgress( gump ); - } - } + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + // Deathwatch Beetle Hatchlings killed: + gump.AddHtmlLocalized(70, 260, 270, 100, 1063318, 0x12DC6BF, false, false); - public override int MaxProgress => 10; + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, "10"); + } + else + { + base.RenderProgress(gump); + } + } - public ThirdKillObjective( int startingProgress ) - { - CurProgress = startingProgress; - } + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is DeathwatchBeetleHatchling) + CurProgress++; + } - public ThirdKillObjective() - { - } + public override void OnComplete() + { + System.AddObjective(new ReturnObjective()); + } + } - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is DeathwatchBeetleHatchling ) - CurProgress++; - } + public class ReturnObjective : QuestObjective + { + public override object Message => 1063313; - public override void OnComplete() - { - System.AddObjective( new ReturnObjective() ); - } - } - - public class ReturnObjective : QuestObjective - { - public override object Message => 1063313; - - public ReturnObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new EndConversation() ); - } - } -} + public override void OnComplete() + { + System.AddConversation(new EndConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Terrible Hatchlings/TerribleHatchlingsQuest.cs b/Scripts/Engines/Quests/Terrible Hatchlings/TerribleHatchlingsQuest.cs index e52e1b933..24c16ec95 100644 --- a/Scripts/Engines/Quests/Terrible Hatchlings/TerribleHatchlingsQuest.cs +++ b/Scripts/Engines/Quests/Terrible Hatchlings/TerribleHatchlingsQuest.cs @@ -3,44 +3,45 @@ using Server.Mobiles; namespace Server.Engines.Quests.Zento { - public class TerribleHatchlingsQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( AcceptConversation ), - typeof( DirectionConversation ), - typeof( TakeCareConversation ), - typeof( EndConversation ), - typeof( FirstKillObjective ), - typeof( SecondKillObjective ), - typeof( ThirdKillObjective ), - typeof( ReturnObjective ) - }; + public class TerribleHatchlingsQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(AcceptConversation), + typeof(DirectionConversation), + typeof(TakeCareConversation), + typeof(EndConversation), + typeof(FirstKillObjective), + typeof(SecondKillObjective), + typeof(ThirdKillObjective), + typeof(ReturnObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public TerribleHatchlingsQuest(PlayerMobile from) : base(from) + { + } - public override object Name => 1063314; + // Serialization + public TerribleHatchlingsQuest() + { + } - public override object OfferMessage => 1063315; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override TimeSpan RestartDelay => TimeSpan.MaxValue; - public override bool IsTutorial => true; + public override object Name => 1063314; - public override int Picture => 0x15CF; + public override object OfferMessage => 1063315; - public TerribleHatchlingsQuest( PlayerMobile from ) : base( from ) - { - } + public override TimeSpan RestartDelay => TimeSpan.MaxValue; + public override bool IsTutorial => true; - // Serialization - public TerribleHatchlingsQuest() - { - } + public override int Picture => 0x15CF; - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } - } -} + AddConversation(new AcceptConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Conversations.cs b/Scripts/Engines/Quests/The Summoning/Conversations.cs index cf7afd23e..f002f9448 100644 --- a/Scripts/Engines/Quests/The Summoning/Conversations.cs +++ b/Scripts/Engines/Quests/The Summoning/Conversations.cs @@ -2,62 +2,54 @@ using Server.Mobiles; namespace Server.Engines.Quests.Doom { - public class AcceptConversation : QuestConversation - { - public override object Message => 1050027; + public class AcceptConversation : QuestConversation + { + public override object Message => 1050027; - public AcceptConversation() - { - } + public override void OnRead() + { + System.AddObjective(new CollectBonesObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new CollectBonesObjective() ); - } - } + public class VanquishDaemonConversation : QuestConversation + { + public override object Message => 1050021; - public class VanquishDaemonConversation : QuestConversation - { - public override object Message => 1050021; + public override void OnRead() + { + Victoria victoria = ((TheSummoningQuest)System).Victoria; - public VanquishDaemonConversation() - { - } + if (victoria == null) + { + System.From.SendMessage("Internal error: unable to find Victoria. Quest unable to continue."); + System.Cancel(); + } + else + { + SummoningAltar altar = victoria.Altar; - public override void OnRead() - { - Victoria victoria = ((TheSummoningQuest)System).Victoria; + if (altar == null) + { + System.From.SendMessage("Internal error: unable to find summoning altar. Quest unable to continue."); + System.Cancel(); + } + else if (altar.Daemon == null || !altar.Daemon.Alive) + { + BoneDemon daemon = new BoneDemon(); - if ( victoria == null ) - { - System.From.SendMessage( "Internal error: unable to find Victoria. Quest unable to continue." ); - System.Cancel(); - } - else - { - SummoningAltar altar = victoria.Altar; + daemon.MoveToWorld(altar.Location, altar.Map); + altar.Daemon = daemon; - if ( altar == null ) - { - System.From.SendMessage( "Internal error: unable to find summoning altar. Quest unable to continue." ); - System.Cancel(); - } - else if ( altar.Daemon == null || !altar.Daemon.Alive ) - { - BoneDemon daemon = new BoneDemon(); + System.AddObjective(new VanquishDaemonObjective(daemon)); + } + else + { + victoria.SayTo(System.From, "The devourer has already been summoned."); - daemon.MoveToWorld( altar.Location, altar.Map ); - altar.Daemon = daemon; - - System.AddObjective( new VanquishDaemonObjective( daemon ) ); - } - else - { - victoria.SayTo( System.From, "The devourer has already been summoned." ); - - ((TheSummoningQuest)System).WaitForSummon = true; - } - } - } - } + ((TheSummoningQuest)System).WaitForSummon = true; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Items/BellOfTheDead.cs b/Scripts/Engines/Quests/The Summoning/Items/BellOfTheDead.cs index bf870a96f..ed1c0ee08 100644 --- a/Scripts/Engines/Quests/The Summoning/Items/BellOfTheDead.cs +++ b/Scripts/Engines/Quests/The Summoning/Items/BellOfTheDead.cs @@ -5,113 +5,118 @@ using Server.Network; namespace Server.Engines.Quests.Doom { - public class BellOfTheDead : Item - { - public override int LabelNumber => 1050018; // bell of the dead + public class BellOfTheDead : Item + { + [Constructible] + public BellOfTheDead() : base(0x91A) + { + Hue = 0x835; + Movable = false; + } - [Constructible] - public BellOfTheDead() : base( 0x91A ) - { - Hue = 0x835; - Movable = false; - } + public BellOfTheDead(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Chyloth Chyloth { get; set; } + public override int LabelNumber => 1050018; // bell of the dead - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public SkeletalDragon Dragon { get; set; } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Chyloth Chyloth{ get; set; } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public bool Summoning { get; set; } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public SkeletalDragon Dragon{ get; set; } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - BeginSummon( from ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public bool Summoning{ get; set; } - public virtual void BeginSummon( Mobile from ) - { - if ( Chyloth != null && !Chyloth.Deleted ) - { - from.SendLocalizedMessage( 1050010 ); // The ferry man has already been summoned. There is no need to ring for him again. - } - else if ( Dragon != null && !Dragon.Deleted ) - { - from.SendLocalizedMessage( 1050017 ); // The ferryman has recently been summoned already. You decide against ringing the bell again so soon. - } - else if ( !Summoning ) - { - Summoning = true; + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + BeginSummon(from); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - Effects.PlaySound( GetWorldLocation(), Map, 0x100 ); + public virtual void BeginSummon(Mobile from) + { + if (Chyloth != null && !Chyloth.Deleted) + { + from.SendLocalizedMessage( + 1050010); // The ferry man has already been summoned. There is no need to ring for him again. + } + else if (Dragon != null && !Dragon.Deleted) + { + from.SendLocalizedMessage( + 1050017); // The ferryman has recently been summoned already. You decide against ringing the bell again so soon. + } + else if (!Summoning) + { + Summoning = true; - Timer.DelayCall( TimeSpan.FromSeconds( 8.0 ), new TimerStateCallback( EndSummon ), from ); - } - } + Effects.PlaySound(GetWorldLocation(), Map, 0x100); - public virtual void EndSummon( object state ) - { - Mobile from = (Mobile)state; + Timer.DelayCall(TimeSpan.FromSeconds(8.0), new TimerStateCallback(EndSummon), from); + } + } - if ( Chyloth != null && !Chyloth.Deleted ) - { - from.SendLocalizedMessage( 1050010 ); // The ferry man has already been summoned. There is no need to ring for him again. - } - else if ( Dragon != null && !Dragon.Deleted ) - { - from.SendLocalizedMessage( 1050017 ); // The ferryman has recently been summoned already. You decide against ringing the bell again so soon. - } - else if ( Summoning ) - { - Summoning = false; + public virtual void EndSummon(object state) + { + Mobile from = (Mobile)state; - Point3D loc = GetWorldLocation(); + if (Chyloth != null && !Chyloth.Deleted) + { + from.SendLocalizedMessage( + 1050010); // The ferry man has already been summoned. There is no need to ring for him again. + } + else if (Dragon != null && !Dragon.Deleted) + { + from.SendLocalizedMessage( + 1050017); // The ferryman has recently been summoned already. You decide against ringing the bell again so soon. + } + else if (Summoning) + { + Summoning = false; - loc.Z -= 16; + Point3D loc = GetWorldLocation(); - Effects.SendLocationParticles( EffectItem.Create( loc, Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 0, 0, 2023, 0 ); - Effects.PlaySound( loc, Map, 0x1FE ); + loc.Z -= 16; - Chyloth = new Chyloth(); + Effects.SendLocationParticles(EffectItem.Create(loc, Map, EffectItem.DefaultDuration), 0x3728, 10, 10, 0, 0, + 2023, 0); + Effects.PlaySound(loc, Map, 0x1FE); - Chyloth.Direction = (Direction)(7 & (4 + (int)from.GetDirectionTo( loc ))); - Chyloth.MoveToWorld( loc, Map ); + Chyloth = new Chyloth(); - Chyloth.Bell = this; - Chyloth.AngryAt = from; - Chyloth.BeginGiveWarning(); - Chyloth.BeginRemove( TimeSpan.FromSeconds( 40.0 ) ); - } - } + Chyloth.Direction = (Direction)(7 & (4 + (int)from.GetDirectionTo(loc))); + Chyloth.MoveToWorld(loc, Map); - public BellOfTheDead( Serial serial ) : base( serial ) - { - } + Chyloth.Bell = this; + Chyloth.AngryAt = from; + Chyloth.BeginGiveWarning(); + Chyloth.BeginRemove(TimeSpan.FromSeconds(40.0)); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (Mobile) Chyloth ); - writer.Write( (Mobile) Dragon ); - } + writer.Write(Chyloth); + writer.Write(Dragon); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Chyloth = reader.ReadMobile() as Chyloth; - Dragon = reader.ReadMobile() as SkeletalDragon; + Chyloth = reader.ReadMobile() as Chyloth; + Dragon = reader.ReadMobile() as SkeletalDragon; - Chyloth?.Delete(); - } - } -} + Chyloth?.Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Items/ChylothShroud.cs b/Scripts/Engines/Quests/The Summoning/Items/ChylothShroud.cs index 8f1d0f767..10a19da9e 100644 --- a/Scripts/Engines/Quests/The Summoning/Items/ChylothShroud.cs +++ b/Scripts/Engines/Quests/The Summoning/Items/ChylothShroud.cs @@ -1,30 +1,30 @@ namespace Server.Engines.Quests.Doom { - public class ChylothShroud : Item - { - [Constructible] - public ChylothShroud() : base( 0x204E ) - { - Hue = 0x846; - Layer = Layer.OuterTorso; - } + public class ChylothShroud : Item + { + [Constructible] + public ChylothShroud() : base(0x204E) + { + Hue = 0x846; + Layer = Layer.OuterTorso; + } - public ChylothShroud( Serial serial ) : base( serial ) - { - } + public ChylothShroud(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Items/ChylothStaff.cs b/Scripts/Engines/Quests/The Summoning/Items/ChylothStaff.cs index db197bb7a..2da921c56 100644 --- a/Scripts/Engines/Quests/The Summoning/Items/ChylothStaff.cs +++ b/Scripts/Engines/Quests/The Summoning/Items/ChylothStaff.cs @@ -2,32 +2,32 @@ using Server.Items; namespace Server.Engines.Quests.Doom { - public class ChylothStaff : BlackStaff - { - public override int LabelNumber => 1041111; // a magic staff + public class ChylothStaff : BlackStaff + { + [Constructible] + public ChylothStaff() + { + Hue = 0x482; + } - [Constructible] - public ChylothStaff() - { - Hue = 0x482; - } + public ChylothStaff(Serial serial) : base(serial) + { + } - public ChylothStaff( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041111; // a magic staff - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Items/GoldenSkull.cs b/Scripts/Engines/Quests/The Summoning/Items/GoldenSkull.cs index 20a91d262..03457af55 100644 --- a/Scripts/Engines/Quests/The Summoning/Items/GoldenSkull.cs +++ b/Scripts/Engines/Quests/The Summoning/Items/GoldenSkull.cs @@ -1,33 +1,33 @@ namespace Server.Engines.Quests.Doom { - public class GoldenSkull : Item - { - public override int LabelNumber => 1061619; // a golden skull + public class GoldenSkull : Item + { + [Constructible] + public GoldenSkull() : base(Utility.Random(0x1AE2, 3)) + { + Weight = 1.0; + Hue = 0x8A5; + LootType = LootType.Blessed; + } - [Constructible] - public GoldenSkull() : base( Utility.Random( 0x1AE2, 3 ) ) - { - Weight = 1.0; - Hue = 0x8A5; - LootType = LootType.Blessed; - } + public GoldenSkull(Serial serial) : base(serial) + { + } - public GoldenSkull( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1061619; // a golden skull - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Items/GrandGrimoire.cs b/Scripts/Engines/Quests/The Summoning/Items/GrandGrimoire.cs index 371b2908c..a2c5a2c39 100644 --- a/Scripts/Engines/Quests/The Summoning/Items/GrandGrimoire.cs +++ b/Scripts/Engines/Quests/The Summoning/Items/GrandGrimoire.cs @@ -1,34 +1,34 @@ namespace Server.Engines.Quests.Doom { - public class GrandGrimoire : Item - { - public override int LabelNumber => 1060801; // The Grand Grimoire + public class GrandGrimoire : Item + { + [Constructible] + public GrandGrimoire() : base(0xEFA) + { + Weight = 1.0; + Hue = 0x835; + Layer = Layer.OneHanded; + LootType = LootType.Blessed; + } - [Constructible] - public GrandGrimoire() : base( 0xEFA ) - { - Weight = 1.0; - Hue = 0x835; - Layer = Layer.OneHanded; - LootType = LootType.Blessed; - } + public GrandGrimoire(Serial serial) : base(serial) + { + } - public GrandGrimoire( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1060801; // The Grand Grimoire - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Items/SummoningAltar.cs b/Scripts/Engines/Quests/The Summoning/Items/SummoningAltar.cs index 64990c03b..ae7d8f3f7 100644 --- a/Scripts/Engines/Quests/The Summoning/Items/SummoningAltar.cs +++ b/Scripts/Engines/Quests/The Summoning/Items/SummoningAltar.cs @@ -3,60 +3,60 @@ using Server.Mobiles; namespace Server.Engines.Quests.Doom { - public class SummoningAltar : AbbatoirAddon - { - private BoneDemon m_Daemon; + public class SummoningAltar : AbbatoirAddon + { + private BoneDemon m_Daemon; - public BoneDemon Daemon - { - get => m_Daemon; - set - { - m_Daemon = value; - CheckDaemon(); - } - } + [Constructible] + public SummoningAltar() + { + } - public void CheckDaemon() - { - if ( m_Daemon == null || !m_Daemon.Alive ) - { - m_Daemon = null; - Hue = 0; - } - else - { - Hue = 0x66D; - } - } + public SummoningAltar(Serial serial) : base(serial) + { + } - [Constructible] - public SummoningAltar() - { - } + public BoneDemon Daemon + { + get => m_Daemon; + set + { + m_Daemon = value; + CheckDaemon(); + } + } - public SummoningAltar( Serial serial ) : base( serial ) - { - } + public void CheckDaemon() + { + if (m_Daemon == null || !m_Daemon.Alive) + { + m_Daemon = null; + Hue = 0; + } + else + { + Hue = 0x66D; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (Mobile) m_Daemon ); - } + writer.Write(m_Daemon); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Daemon = reader.ReadMobile() as BoneDemon; + m_Daemon = reader.ReadMobile() as BoneDemon; - CheckDaemon(); - } - } + CheckDaemon(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Mobiles/Chyloth.cs b/Scripts/Engines/Quests/The Summoning/Mobiles/Chyloth.cs index bb0bd8cc1..e7405c843 100644 --- a/Scripts/Engines/Quests/The Summoning/Mobiles/Chyloth.cs +++ b/Scripts/Engines/Quests/The Summoning/Mobiles/Chyloth.cs @@ -1,304 +1,311 @@ using System; +using Server.Engines.PartySystem; using Server.Gumps; using Server.Items; using Server.Mobiles; using Server.Network; -using Server.Engines.PartySystem; namespace Server.Engines.Quests.Doom { - public class Chyloth : BaseQuester - { - public override string DefaultName => "Chyloth"; + public class Chyloth : BaseQuester + { + private static int[] m_Offsets = + { + -1, -1, + -1, 0, + -1, 1, + 0, -1, + 0, 1, + 1, -1, + 1, 0, + 1, 1 + }; - [Constructible] - public Chyloth() : base( "the Ferryman" ) - { - } + [Constructible] + public Chyloth() : base("the Ferryman") + { + } - public Chyloth( Serial serial ) : base( serial ) - { - } + public Chyloth(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Chyloth"; - Hue = 0x8455; - Body = 0x190; - } + public BellOfTheDead Bell{ get; set; } - public override void InitOutfit() - { - EquipItem( new ChylothShroud() ); - EquipItem( new ChylothStaff() ); - } + public Mobile AngryAt{ get; set; } - public BellOfTheDead Bell { get; set; } + public override void InitBody() + { + InitStats(100, 100, 25); + + Hue = 0x8455; + Body = 0x190; + } + + public override void InitOutfit() + { + EquipItem(new ChylothShroud()); + EquipItem(new ChylothStaff()); + } - public Mobile AngryAt { get; set; } + public virtual void BeginGiveWarning() + { + if (Deleted || AngryAt == null) + return; + + Timer.DelayCall(TimeSpan.FromSeconds(4.0), EndGiveWarning); + } - public virtual void BeginGiveWarning() - { - if ( Deleted || AngryAt == null ) - return; + public virtual void EndGiveWarning() + { + if (Deleted || AngryAt == null) + return; - Timer.DelayCall( TimeSpan.FromSeconds( 4.0 ), EndGiveWarning ); - } + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1050013, + AngryAt.Name); // You have summoned me in vain ~1_NAME~! Only the dead may cross! + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1050014); // Why have you disturbed me, mortal?!? - public virtual void EndGiveWarning() - { - if ( Deleted || AngryAt == null ) - return; + BeginSummonDragon(); + } - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1050013, AngryAt.Name ); // You have summoned me in vain ~1_NAME~! Only the dead may cross! - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1050014 ); // Why have you disturbed me, mortal?!? + public virtual void BeginSummonDragon() + { + if (Deleted || AngryAt == null) + return; - BeginSummonDragon(); - } + Timer.DelayCall(TimeSpan.FromSeconds(30.0), EndSummonDragon); + } - public virtual void BeginSummonDragon() - { - if ( Deleted || AngryAt == null ) - return; + public virtual void BeginRemove(TimeSpan delay) + { + Timer.DelayCall(delay, EndRemove); + } - Timer.DelayCall( TimeSpan.FromSeconds( 30.0 ), EndSummonDragon ); - } + public virtual void EndRemove() + { + if (Deleted) + return; - public virtual void BeginRemove( TimeSpan delay ) - { - Timer.DelayCall( delay, EndRemove ); - } + Point3D loc = Location; + Map map = Map; + + Effects.SendLocationParticles(EffectItem.Create(loc, map, EffectItem.DefaultDuration), 0x3728, 10, 10, 0, 0, + 2023, 0); + Effects.PlaySound(loc, map, 0x1FE); + + Delete(); + } - public virtual void EndRemove() - { - if ( Deleted ) - return; + public virtual void EndSummonDragon() + { + if (Deleted || AngryAt == null) + return; - Point3D loc = Location; - Map map = Map; + Map map = AngryAt.Map; - Effects.SendLocationParticles( EffectItem.Create( loc, map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 0, 0, 2023, 0 ); - Effects.PlaySound( loc, map, 0x1FE ); + if (map == null) + return; - Delete(); - } + if (!AngryAt.Region.IsPartOf("Doom")) + return; - private static int[] m_Offsets = { - -1, -1, - -1, 0, - -1, 1, - 0, -1, - 0, 1, - 1, -1, - 1, 0, - 1, 1 - }; + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1050015); // Feel the wrath of my legions!!! + PublicOverheadMessage(MessageType.Regular, 0x3B2, false, "MUHAHAHAHA HAHAH HAHA"); // A wee bit crazy, aren't we? - public virtual void EndSummonDragon() - { - if ( Deleted || AngryAt == null ) - return; + SkeletalDragon dragon = new SkeletalDragon(); - Map map = AngryAt.Map; + int offset = Utility.Random(8) * 2; - if ( map == null ) - return; + bool foundLoc = false; - if ( !AngryAt.Region.IsPartOf( "Doom" ) ) - return; + for (int i = 0; i < m_Offsets.Length; i += 2) + { + int x = AngryAt.X + m_Offsets[(offset + i) % m_Offsets.Length]; + int y = AngryAt.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1050015 ); // Feel the wrath of my legions!!! - PublicOverheadMessage( MessageType.Regular, 0x3B2, false, "MUHAHAHAHA HAHAH HAHA" ); // A wee bit crazy, aren't we? + if (map.CanSpawnMobile(x, y, AngryAt.Z)) + { + dragon.MoveToWorld(new Point3D(x, y, AngryAt.Z), map); + foundLoc = true; + break; + } - SkeletalDragon dragon = new SkeletalDragon(); + int z = map.GetAverageZ(x, y); - int offset = Utility.Random( 8 ) * 2; + if (map.CanSpawnMobile(x, y, z)) + { + dragon.MoveToWorld(new Point3D(x, y, z), map); + foundLoc = true; + break; + } + } - bool foundLoc = false; + if (!foundLoc) + dragon.MoveToWorld(AngryAt.Location, map); - for ( int i = 0; i < m_Offsets.Length; i += 2 ) - { - int x = AngryAt.X + m_Offsets[(offset + i) % m_Offsets.Length]; - int y = AngryAt.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; + dragon.Combatant = AngryAt; - if ( map.CanSpawnMobile( x, y, AngryAt.Z ) ) - { - dragon.MoveToWorld( new Point3D( x, y, AngryAt.Z ), map ); - foundLoc = true; - break; - } + if (Bell != null) + Bell.Dragon = dragon; + } - int z = map.GetAverageZ( x, y ); + public static void TeleportToFerry(Mobile from) + { + Point3D loc = new Point3D(408, 251, 2); + Map map = Map.Malas; - if ( map.CanSpawnMobile( x, y, z ) ) - { - dragon.MoveToWorld( new Point3D( x, y, z ), map ); - foundLoc = true; - break; - } - } + Effects.SendLocationParticles(EffectItem.Create(loc, map, EffectItem.DefaultDuration), 0x3728, 10, 10, 0, 0, + 2023, 0); + Effects.PlaySound(loc, map, 0x1FE); - if ( !foundLoc ) - dragon.MoveToWorld( AngryAt.Location, map ); + TeleportPets(from, loc, map); - dragon.Combatant = AngryAt; + from.MoveToWorld(loc, map); + } - if ( Bell != null ) - Bell.Dragon = dragon; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is GoldenSkull) + { + dropped.Delete(); - public static void TeleportToFerry( Mobile from ) - { - Point3D loc = new Point3D( 408, 251, 2 ); - Map map = Map.Malas; + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1050046, + from.Name); // Very well, ~1_NAME~, I accept your token. You may cross. + BeginRemove(TimeSpan.FromSeconds(4.0)); - Effects.SendLocationParticles( EffectItem.Create( loc, map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 0, 0, 2023, 0 ); - Effects.PlaySound( loc, map, 0x1FE ); + Party p = PartySystem.Party.Get(from); - TeleportPets( from, loc, map ); + if (p != null) + for (int i = 0; i < p.Members.Count; ++i) + { + PartyMemberInfo pmi = p.Members[i]; + Mobile member = pmi.Mobile; - from.MoveToWorld( loc, map ); - } + if (member != from && member.Map == Map.Malas && member.Region.IsPartOf("Doom")) + { + if (AngryAt == member) + AngryAt = null; - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is GoldenSkull ) - { - dropped.Delete(); + member.CloseGump(typeof(ChylothPartyGump)); + member.SendGump(new ChylothPartyGump(from, member)); + } + } - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1050046, from.Name ); // Very well, ~1_NAME~, I accept your token. You may cross. - BeginRemove( TimeSpan.FromSeconds( 4.0 ) ); + if (AngryAt == from) + AngryAt = null; - Party p = PartySystem.Party.Get( from ); + TeleportToFerry(from); - if ( p != null ) - { - for ( int i = 0; i < p.Members.Count; ++i ) - { - PartyMemberInfo pmi = (PartyMemberInfo)p.Members[i]; - Mobile member = pmi.Mobile; + return false; + } - if ( member != from && member.Map == Map.Malas && member.Region.IsPartOf( "Doom" ) ) - { - if ( AngryAt == member ) - AngryAt = null; + return base.OnDragDrop(from, dropped); + } - member.CloseGump( typeof( ChylothPartyGump ) ); - member.SendGump( new ChylothPartyGump( from, member ) ); - } - } - } - - if ( AngryAt == from ) - AngryAt = null; - - TeleportToFerry( from ); - - return false; - } - - return base.OnDragDrop( from, dropped ); - } - - public override bool CanTalkTo( PlayerMobile to ) - { - return false; - } - - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ChylothPartyGump : Gump - { - private Mobile m_Leader; - private Mobile m_Member; - - public ChylothPartyGump( Mobile leader, Mobile member ) : base( 150, 50 ) - { - m_Leader = leader; - m_Member = member; - - Closable = false; - - AddPage( 0 ); - - AddImage( 0, 0, 3600 ); - - AddImageTiled( 0, 14, 15, 200, 3603 ); - AddImageTiled( 380, 14, 14, 200, 3605 ); - AddImage( 0, 201, 3606 ); - AddImageTiled( 15, 201, 370, 16, 3607 ); - AddImageTiled( 15, 0, 370, 16, 3601 ); - AddImage( 380, 0, 3602 ); - AddImage( 380, 201, 3608 ); - AddImageTiled( 15, 15, 365, 190, 2624 ); - - AddRadio( 30, 140, 9727, 9730, true, 1 ); - AddHtmlLocalized( 65, 145, 300, 25, 1050050, 0x7FFF, false, false ); // Yes, let's go! - - AddRadio( 30, 175, 9727, 9730, false, 0 ); - AddHtmlLocalized( 65, 178, 300, 25, 1050049, 0x7FFF, false, false ); // No thanks, I'd rather stay here. - - AddHtmlLocalized( 30, 20, 360, 35, 1050047, 0x7FFF, false, false ); // Another player has paid Chyloth for your passage across lake Mortis: - - AddHtmlLocalized( 30, 105, 345, 40, 1050048, 0x5B2D, false, false ); // Do you wish to accept their invitation at this time? - - AddImage( 65, 72, 5605 ); - - AddImageTiled( 80, 90, 200, 1, 9107 ); - AddImageTiled( 95, 92, 200, 1, 9157 ); - - AddLabel( 90, 70, 1645, leader.Name ); - - AddButton( 290, 175, 247, 248, 2, GumpButtonType.Reply, 0 ); - - AddImageTiled( 15, 14, 365, 1, 9107 ); - AddImageTiled( 380, 14, 1, 190, 9105 ); - AddImageTiled( 15, 205, 365, 1, 9107 ); - AddImageTiled( 15, 14, 1, 190, 9105 ); - AddImageTiled( 0, 0, 395, 1, 9157 ); - AddImageTiled( 394, 0, 1, 217, 9155 ); - AddImageTiled( 0, 216, 395, 1, 9157 ); - AddImageTiled( 0, 0, 1, 217, 9155 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 2 && info.IsSwitched( 1 ) ) - { - if ( m_Member.Region.IsPartOf( "Doom" ) ) - { - m_Leader.SendLocalizedMessage( 1050054, m_Member.Name ); // ~1_NAME~ has accepted your invitation to cross lake Mortis. - - Chyloth.TeleportToFerry( m_Member ); - } - else - { - m_Member.SendLocalizedMessage( 1050051 ); // The invitation has been revoked. - } - } - else - { - m_Member.SendLocalizedMessage( 1050052 ); // You have declined their invitation. - m_Leader.SendLocalizedMessage( 1050053, m_Member.Name ); // ~1_NAME~ has declined your invitation to cross lake Mortis. - } - } - } -} + public override bool CanTalkTo(PlayerMobile to) + { + return false; + } + + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ChylothPartyGump : Gump + { + private Mobile m_Leader; + private Mobile m_Member; + + public ChylothPartyGump(Mobile leader, Mobile member) : base(150, 50) + { + m_Leader = leader; + m_Member = member; + + Closable = false; + + AddPage(0); + + AddImage(0, 0, 3600); + + AddImageTiled(0, 14, 15, 200, 3603); + AddImageTiled(380, 14, 14, 200, 3605); + AddImage(0, 201, 3606); + AddImageTiled(15, 201, 370, 16, 3607); + AddImageTiled(15, 0, 370, 16, 3601); + AddImage(380, 0, 3602); + AddImage(380, 201, 3608); + AddImageTiled(15, 15, 365, 190, 2624); + + AddRadio(30, 140, 9727, 9730, true, 1); + AddHtmlLocalized(65, 145, 300, 25, 1050050, 0x7FFF, false, false); // Yes, let's go! + + AddRadio(30, 175, 9727, 9730, false, 0); + AddHtmlLocalized(65, 178, 300, 25, 1050049, 0x7FFF, false, false); // No thanks, I'd rather stay here. + + AddHtmlLocalized(30, 20, 360, 35, 1050047, 0x7FFF, false, + false); // Another player has paid Chyloth for your passage across lake Mortis: + + AddHtmlLocalized(30, 105, 345, 40, 1050048, 0x5B2D, false, + false); // Do you wish to accept their invitation at this time? + + AddImage(65, 72, 5605); + + AddImageTiled(80, 90, 200, 1, 9107); + AddImageTiled(95, 92, 200, 1, 9157); + + AddLabel(90, 70, 1645, leader.Name); + + AddButton(290, 175, 247, 248, 2, GumpButtonType.Reply, 0); + + AddImageTiled(15, 14, 365, 1, 9107); + AddImageTiled(380, 14, 1, 190, 9105); + AddImageTiled(15, 205, 365, 1, 9107); + AddImageTiled(15, 14, 1, 190, 9105); + AddImageTiled(0, 0, 395, 1, 9157); + AddImageTiled(394, 0, 1, 217, 9155); + AddImageTiled(0, 216, 395, 1, 9157); + AddImageTiled(0, 0, 1, 217, 9155); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 2 && info.IsSwitched(1)) + { + if (m_Member.Region.IsPartOf("Doom")) + { + m_Leader.SendLocalizedMessage(1050054, + m_Member.Name); // ~1_NAME~ has accepted your invitation to cross lake Mortis. + + Chyloth.TeleportToFerry(m_Member); + } + else + { + m_Member.SendLocalizedMessage(1050051); // The invitation has been revoked. + } + } + else + { + m_Member.SendLocalizedMessage(1050052); // You have declined their invitation. + m_Leader.SendLocalizedMessage(1050053, + m_Member.Name); // ~1_NAME~ has declined your invitation to cross lake Mortis. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Mobiles/Victoria.cs b/Scripts/Engines/Quests/The Summoning/Mobiles/Victoria.cs index f73baa5fe..4f54a7bd0 100644 --- a/Scripts/Engines/Quests/The Summoning/Mobiles/Victoria.cs +++ b/Scripts/Engines/Quests/The Summoning/Mobiles/Victoria.cs @@ -3,150 +3,144 @@ using Server.Mobiles; namespace Server.Engines.Quests.Doom { - public class Victoria : BaseQuester - { - public override int TalkNumber => 6159; // Ask about Chyloth - public override string DefaultName => "Victoria"; - public override bool ClickTitle => true; - public override bool IsActiveVendor => true; - public override bool DisallowAllMoves => false; + public class Victoria : BaseQuester + { + private const int AltarRange = 24; - public override void InitSBInfo() - { - m_SBInfos.Add( new SBMage() ); - } + private SummoningAltar m_Altar; - [Constructible] - public Victoria() : base( "the Sorceress" ) - { - } + [Constructible] + public Victoria() : base("the Sorceress") + { + } - public Victoria( Serial serial ) : base( serial ) - { - } + public Victoria(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override int TalkNumber => 6159; // Ask about Chyloth + public override string DefaultName => "Victoria"; + public override bool ClickTitle => true; + public override bool IsActiveVendor => true; + public override bool DisallowAllMoves => false; - Female = true; - Hue = 0x8835; - Body = 0x191; - } + public SummoningAltar Altar + { + get + { + if (m_Altar == null || m_Altar.Deleted || m_Altar.Map != Map || + !Utility.InRange(m_Altar.Location, Location, AltarRange)) + foreach (Item item in GetItemsInRange(AltarRange)) + if (item is SummoningAltar altar) + { + m_Altar = altar; + break; + } - private SummoningAltar m_Altar; + return m_Altar; + } + } - private const int AltarRange = 24; + public override void InitSBInfo() + { + m_SBInfos.Add(new SBMage()); + } - public SummoningAltar Altar - { - get - { - if ( m_Altar == null || m_Altar.Deleted || m_Altar.Map != Map || !Utility.InRange( m_Altar.Location, Location, AltarRange ) ) - { - foreach ( Item item in GetItemsInRange( AltarRange ) ) - { - if ( item is SummoningAltar altar ) - { - m_Altar = altar; - break; - } - } - } + public override void InitBody() + { + InitStats(100, 100, 25); - return m_Altar; - } - } + Female = true; + Hue = 0x8835; + Body = 0x191; + } - public override void InitOutfit() - { - EquipItem( new GrandGrimoire() ); + public override void InitOutfit() + { + EquipItem(new GrandGrimoire()); - EquipItem( SetHue( new Sandals(), 0x455 ) ); - EquipItem( SetHue( new SkullCap(), 0x455 ) ); - EquipItem( SetHue( new PlainDress(), 0x455 ) ); + EquipItem(SetHue(new Sandals(), 0x455)); + EquipItem(SetHue(new SkullCap(), 0x455)); + EquipItem(SetHue(new PlainDress(), 0x455)); - HairItemID = 0x203C; - HairHue = 0x482; - } + HairItemID = 0x203C; + HairHue = 0x482; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( qs is TheSummoningQuest ) - { - if ( dropped is DaemonBone bones ) - { - QuestObjective obj = qs.FindObjective( typeof( CollectBonesObjective ) ); + if (qs is TheSummoningQuest) + if (dropped is DaemonBone bones) + { + QuestObjective obj = qs.FindObjective(typeof(CollectBonesObjective)); - if ( obj != null && !obj.Completed ) - { - int need = obj.MaxProgress - obj.CurProgress; + if (obj != null && !obj.Completed) + { + int need = obj.MaxProgress - obj.CurProgress; - if ( bones.Amount < need ) - { - obj.CurProgress += bones.Amount; - bones.Delete(); + if (bones.Amount < need) + { + obj.CurProgress += bones.Amount; + bones.Delete(); - qs.ShowQuestLogUpdated(); - } - else - { - obj.Complete(); - bones.Consume( need ); + qs.ShowQuestLogUpdated(); + } + else + { + obj.Complete(); + bones.Consume(need); - if ( !bones.Deleted ) - { - // TODO: Accurate? - SayTo( from, 1050038 ); // You have already given me all the Daemon bones necessary to weave the spell. Keep these for a later time. - } - } - } - else - { - // TODO: Accurate? - SayTo( from, 1050038 ); // You have already given me all the Daemon bones necessary to weave the spell. Keep these for a later time. - } + if (!bones.Deleted) + SayTo(from, + 1050038); // You have already given me all the Daemon bones necessary to weave the spell. Keep these for a later time. + } + } + else + { + // TODO: Accurate? + SayTo(from, + 1050038); // You have already given me all the Daemon bones necessary to weave the spell. Keep these for a later time. + } - return false; - } - } - } + return false; + } + } - return base.OnDragDrop( from, dropped ); - } + return base.OnDragDrop(from, dropped); + } - public override bool CanTalkTo( PlayerMobile to ) - { - return ( to.Quest == null && QuestSystem.CanOfferQuest( to, typeof( TheSummoningQuest ) ) ); - } + public override bool CanTalkTo(PlayerMobile to) + { + return to.Quest == null && QuestSystem.CanOfferQuest(to, typeof(TheSummoningQuest)); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( qs == null && QuestSystem.CanOfferQuest( player, typeof( TheSummoningQuest ) ) ) - { - Direction = GetDirectionTo( player ); - new TheSummoningQuest( this, player ).SendOffer(); - } - } + if (qs == null && QuestSystem.CanOfferQuest(player, typeof(TheSummoningQuest))) + { + Direction = GetDirectionTo(player); + new TheSummoningQuest(this, player).SendOffer(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/Objectives.cs b/Scripts/Engines/Quests/The Summoning/Objectives.cs index 3a027eff3..7c0cb1355 100644 --- a/Scripts/Engines/Quests/The Summoning/Objectives.cs +++ b/Scripts/Engines/Quests/The Summoning/Objectives.cs @@ -1,162 +1,164 @@ +using System.Collections.Generic; using Server.Items; using Server.Mobiles; -using System.Collections.Generic; namespace Server.Engines.Quests.Doom { - public class CollectBonesObjective : QuestObjective - { - public override object Message => 1050026; + public class CollectBonesObjective : QuestObjective + { + public override object Message => 1050026; - public override int MaxProgress => 1000; + public override int MaxProgress => 1000; - public CollectBonesObjective() - { - } + public override void OnComplete() + { + Victoria victoria = ((TheSummoningQuest)System).Victoria; - public override void OnComplete() - { - Victoria victoria = ((TheSummoningQuest)System).Victoria; + if (victoria == null) + { + System.From.SendMessage("Internal error: unable to find Victoria. Quest unable to continue."); + System.Cancel(); + } + else + { + SummoningAltar altar = victoria.Altar; - if ( victoria == null ) - { - System.From.SendMessage( "Internal error: unable to find Victoria. Quest unable to continue." ); - System.Cancel(); - } - else - { - SummoningAltar altar = victoria.Altar; + if (altar == null) + { + System.From.SendMessage("Internal error: unable to find summoning altar. Quest unable to continue."); + System.Cancel(); + } + else if (altar.Daemon == null || !altar.Daemon.Alive) + { + System.AddConversation(new VanquishDaemonConversation()); + } + else + { + victoria.SayTo(System.From, + "The devourer has already been summoned. Return when the devourer has been slain and I will summon it for you."); + ((TheSummoningQuest)System).WaitForSummon = true; + } + } + } - if ( altar == null ) - { - System.From.SendMessage( "Internal error: unable to find summoning altar. Quest unable to continue." ); - System.Cancel(); - } - else if ( altar.Daemon == null || !altar.Daemon.Alive ) - { - System.AddConversation( new VanquishDaemonConversation() ); - } - else - { - victoria.SayTo( System.From, "The devourer has already been summoned. Return when the devourer has been slain and I will summon it for you." ); - ((TheSummoningQuest)System).WaitForSummon = true; - } - } - } + public override void RenderMessage(BaseQuestGump gump) + { + if (CurProgress > 0 && CurProgress < MaxProgress) + gump.AddHtmlObject(70, 130, 300, 100, 1050028, BaseQuestGump.Blue, false, + false); // Victoria has accepted the Daemon bones, but the requirement is not yet met. + else + base.RenderMessage(gump); + } - public override void RenderMessage( BaseQuestGump gump ) - { - if ( CurProgress > 0 && CurProgress < MaxProgress ) - gump.AddHtmlObject( 70, 130, 300, 100, 1050028, BaseQuestGump.Blue, false, false ); // Victoria has accepted the Daemon bones, but the requirement is not yet met. - else - base.RenderMessage( gump ); - } + public override void RenderProgress(BaseQuestGump gump) + { + if (CurProgress > 0 && CurProgress < MaxProgress) + { + gump.AddHtmlObject(70, 260, 270, 100, 1050019, BaseQuestGump.Blue, false, + false); // Number of bones collected: - public override void RenderProgress( BaseQuestGump gump ) - { - if ( CurProgress > 0 && CurProgress < MaxProgress ) - { - gump.AddHtmlObject( 70, 260, 270, 100, 1050019, BaseQuestGump.Blue, false, false ); // Number of bones collected: + gump.AddLabel(70, 280, 100, CurProgress.ToString()); + gump.AddLabel(100, 280, 100, "/"); + gump.AddLabel(130, 280, 100, MaxProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } + } - gump.AddLabel( 70, 280, 100, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 100, "/" ); - gump.AddLabel( 130, 280, 100, MaxProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } - } + public class VanquishDaemonObjective : QuestObjective + { + private BoneDemon m_Daemon; - public class VanquishDaemonObjective : QuestObjective - { - private BoneDemon m_Daemon; + public VanquishDaemonObjective(BoneDemon daemon) + { + m_Daemon = daemon; + } - public Corpse CorpseWithSkull { get; set; } + // Serialization + public VanquishDaemonObjective() + { + } - public override object Message => 1050037; + public Corpse CorpseWithSkull{ get; set; } - public VanquishDaemonObjective( BoneDemon daemon ) - { - m_Daemon = daemon; - } + public override object Message => 1050037; - // Serialization - public VanquishDaemonObjective() - { - } + public override void CheckProgress() + { + if (m_Daemon == null || !m_Daemon.Alive) + Complete(); + } - public override void CheckProgress() - { - if ( m_Daemon == null || !m_Daemon.Alive ) - Complete(); - } + public override void OnComplete() + { + Victoria victoria = ((TheSummoningQuest)System).Victoria; - public override void OnComplete() - { - Victoria victoria = ((TheSummoningQuest)System).Victoria; + SummoningAltar altar = victoria?.Altar; - SummoningAltar altar = victoria?.Altar; + altar?.CheckDaemon(); - altar?.CheckDaemon(); + PlayerMobile from = System.From; - PlayerMobile from = System.From; + if (!from.Alive) + { + from.SendLocalizedMessage( + 1050033); // The devourer lies dead, unfortunately so do you. You cannot claim your reward while dead. You will need to face him again. + ((TheSummoningQuest)System).WaitForSummon = true; + } + else + { + bool hasRights = true; - if ( !from.Alive ) - { - from.SendLocalizedMessage( 1050033 ); // The devourer lies dead, unfortunately so do you. You cannot claim your reward while dead. You will need to face him again. - ((TheSummoningQuest)System).WaitForSummon = true; - } - else - { - bool hasRights = true; + if (m_Daemon != null) + { + List lootingRights = + BaseCreature.GetLootingRights(m_Daemon.DamageEntries, m_Daemon.HitsMax); - if ( m_Daemon != null ) - { - List lootingRights = BaseCreature.GetLootingRights( m_Daemon.DamageEntries, m_Daemon.HitsMax ); + for (int i = 0; i < lootingRights.Count; ++i) + { + DamageStore ds = lootingRights[i]; - for ( int i = 0; i < lootingRights.Count; ++i ) - { - DamageStore ds = lootingRights[i]; + if (ds.m_HasRight && ds.m_Mobile == from) + { + hasRights = true; + break; + } + } + } - if ( ds.m_HasRight && ds.m_Mobile == from ) - { - hasRights = true; - break; - } - } - } + if (!hasRights) + { + from.SendLocalizedMessage( + 1050034); // The devourer lies dead. Unfortunately you did not sufficiently prove your worth in combating the devourer. Victoria shall summon another incarnation of the devourer to the circle of stones. Try again noble adventurer. + ((TheSummoningQuest)System).WaitForSummon = true; + } + else + { + from.SendLocalizedMessage(1050035); // The devourer lies dead. Search his corpse to claim your prize! - if ( !hasRights ) - { - from.SendLocalizedMessage( 1050034 ); // The devourer lies dead. Unfortunately you did not sufficiently prove your worth in combating the devourer. Victoria shall summon another incarnation of the devourer to the circle of stones. Try again noble adventurer. - ((TheSummoningQuest)System).WaitForSummon = true; - } - else - { - from.SendLocalizedMessage( 1050035 ); // The devourer lies dead. Search his corpse to claim your prize! + if (m_Daemon != null) + CorpseWithSkull = m_Daemon.Corpse as Corpse; + } + } + } - if ( m_Daemon != null ) - CorpseWithSkull = m_Daemon.Corpse as Corpse; - } - } - } + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + m_Daemon = reader.ReadMobile() as BoneDemon; + CorpseWithSkull = reader.ReadItem() as Corpse; + } - m_Daemon = reader.ReadMobile() as BoneDemon; - CorpseWithSkull = reader.ReadItem() as Corpse; - } + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (Mobile) m_Daemon ); - writer.Write( (Item) CorpseWithSkull ); - } - } -} + writer.Write(m_Daemon); + writer.Write(CorpseWithSkull); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/The Summoning/TheSummoningQuest.cs b/Scripts/Engines/Quests/The Summoning/TheSummoningQuest.cs index 4f79ac933..c30a2ec83 100644 --- a/Scripts/Engines/Quests/The Summoning/TheSummoningQuest.cs +++ b/Scripts/Engines/Quests/The Summoning/TheSummoningQuest.cs @@ -4,109 +4,109 @@ using Server.Mobiles; namespace Server.Engines.Quests.Doom { - public class TheSummoningQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( AcceptConversation ), - typeof( CollectBonesObjective ), - typeof( VanquishDaemonConversation ), - typeof( VanquishDaemonObjective ) - }; + public class TheSummoningQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(AcceptConversation), + typeof(CollectBonesObjective), + typeof(VanquishDaemonConversation), + typeof(VanquishDaemonObjective) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + public TheSummoningQuest(Victoria victoria, PlayerMobile from) : base(from) + { + Victoria = victoria; + } - public Victoria Victoria { get; private set; } + public TheSummoningQuest() + { + } - public bool WaitForSummon { get; set; } + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override object Name => 1050025; + public Victoria Victoria{ get; private set; } - public override object OfferMessage => 1050020; + public bool WaitForSummon{ get; set; } - public override bool IsTutorial => false; - public override TimeSpan RestartDelay => TimeSpan.Zero; - public override int Picture => 0x15B5; + public override object Name => 1050025; - // NOTE: Quest not entirely OSI-accurate: some changes made to prevent numerous OSI bugs + public override object OfferMessage => 1050020; - public override void Slice() - { - if ( WaitForSummon && Victoria != null ) - { - SummoningAltar altar = Victoria.Altar; + public override bool IsTutorial => false; + public override TimeSpan RestartDelay => TimeSpan.Zero; + public override int Picture => 0x15B5; - if ( altar != null && (altar.Daemon == null || !altar.Daemon.Alive) ) - { - if ( From.Map == Victoria.Map && From.InRange( Victoria, 8 ) ) - { - WaitForSummon = false; + // NOTE: Quest not entirely OSI-accurate: some changes made to prevent numerous OSI bugs - AddConversation( new VanquishDaemonConversation() ); - } - } - } + public override void Slice() + { + if (WaitForSummon && Victoria != null) + { + SummoningAltar altar = Victoria.Altar; - base.Slice(); - } + if (altar != null && (altar.Daemon == null || !altar.Daemon.Alive)) + if (From.Map == Victoria.Map && From.InRange(Victoria, 8)) + { + WaitForSummon = false; - public static int GetDaemonBonesFor( BaseCreature creature ) - { - if ( creature == null || creature.Controlled || creature.Summoned ) - return 0; + AddConversation(new VanquishDaemonConversation()); + } + } - int fame = creature.Fame; + base.Slice(); + } - if ( fame < 1500 ) - return Utility.Dice( 2, 5, -1 ); - if ( fame < 20000 ) - return Utility.Dice( 2, 4, 8 ); - return 50; - } + public static int GetDaemonBonesFor(BaseCreature creature) + { + if (creature == null || creature.Controlled || creature.Summoned) + return 0; - public TheSummoningQuest( Victoria victoria, PlayerMobile from ) : base( from ) - { - Victoria = victoria; - } + int fame = creature.Fame; - public TheSummoningQuest() - { - } + if (fame < 1500) + return Utility.Dice(2, 5, -1); + if (fame < 20000) + return Utility.Dice(2, 4, 8); + return 50; + } - public override void Cancel() - { - base.Cancel(); + public override void Cancel() + { + base.Cancel(); - QuestObjective obj = FindObjective( typeof( CollectBonesObjective ) ); + QuestObjective obj = FindObjective(typeof(CollectBonesObjective)); - if ( obj != null && obj.CurProgress > 0 ) - { - From.BankBox.DropItem( new DaemonBone( obj.CurProgress ) ); + if (obj != null && obj.CurProgress > 0) + { + From.BankBox.DropItem(new DaemonBone(obj.CurProgress)); - From.SendLocalizedMessage( 1050030 ); // The Daemon bones that you have thus far given to Victoria have been returned to you. - } - } + From.SendLocalizedMessage( + 1050030); // The Daemon bones that you have thus far given to Victoria have been returned to you. + } + } - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } + AddConversation(new AcceptConversation()); + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - Victoria = reader.ReadMobile() as Victoria; - WaitForSummon = reader.ReadBool(); - } + Victoria = reader.ReadMobile() as Victoria; + WaitForSummon = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (Mobile) Victoria ); - writer.Write( (bool) WaitForSummon ); - } - } -} + writer.Write(Victoria); + writer.Write(WaitForSummon); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Conversations.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Conversations.cs index ad0c10af9..c4c3a0ed4 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Conversations.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Conversations.cs @@ -1,101 +1,41 @@ namespace Server.Engines.Quests.Haven { - public class AcceptConversation : QuestConversation - { - public override object Message => 1049092; + public class AcceptConversation : QuestConversation + { + public override object Message => 1049092; - public AcceptConversation() - { - } + public override void OnRead() + { + System.AddObjective(new FindUzeraanBeginObjective()); + } + } - public override void OnRead() - { - System.AddObjective( new FindUzeraanBeginObjective() ); - } - } + public class UzeraanTitheConversation : QuestConversation + { + public override object Message => 1060209; - public class UzeraanTitheConversation : QuestConversation - { - public override object Message => 1060209; + public override void OnRead() + { + System.AddObjective(new TitheGoldObjective()); + } + } - public UzeraanTitheConversation() - { - } + public class UzeraanFirstTaskConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1023676, 0xE68) // glowing rune + }; - public override void OnRead() - { - System.AddObjective( new TitheGoldObjective() ); - } - } + public override object Message + { + get + { + if (System.From.Profession == 1) // warrior + return 1049088; - public class UzeraanFirstTaskConversation : QuestConversation - { - public override object Message - { - get - { - if ( System.From.Profession == 1 ) // warrior - { - /* Uzeraan greets you as you approach...

- * - * Greetings traveler!

- * - * I am Uzeraan, the lord of this house and overseer of this fine city, Haven. - * I know we have just met, but time is short and we need to reinforce the troops - * in the mountain pass, so I will not waste your time with pleasantries.

- * - * We have been trying to fight back the wicked Horde Minions which have - * recently begun attacking our cities - but to no avail. We desperately need - * help!

- * - * Your first task will be to assess the situation in the mountain pass, and - * help our troops defeat the Horde Minions there.

- * - * Take the road marked with glowing runes, that starts just outside of this - * mansion. Before you go into battle, it would be prudent to - * review combat techniques as well as - * information on healing yourself.

- * - * To aid you in your fight, you may also wish to - * purchase equipment from Frank the Blacksmith, - * who is standing just South of here.

- * - * Good luck young warrior. - */ - return 1049088; - } - - if ( System.From.Profession == 2 ) // magician - { - /* Uzeraan greets you as you approach...

- * - * Greetings traveler!

- * - * I am Uzeraan, the lord of this house and overseer of this fine city, Haven. - * I know we have just met, but time is short and we need to reinforce - * the troops in the mountain pass, so I will not waste your time with - * pleasantries.

- * - * We have been trying to fight back the wicked Horde Minions which have - * recently begun attacking our cities - but to no avail. We desperately - * need help!

- * - * Your first task will be to assess the situation in the mountain pass, - * and help our troops defeat the Horde Minions there.

- * - * Take the road marked with glowing runes, that starts just outside of this - * mansion. Before you go into battle, it would be prudent to - * review your magic skills as well as - * information on healing yourself.

- * - * To aid you in your fight, you may also wish to - * purchase equipment from Frank the Blacksmith, - * who is standing just South of here.

- * - * Good luck young mage. - */ - return 1049386; - } + if (System.From.Profession == 2) // magician + return 1049386; /* Uzeraan nods at you with approval and begins to speak...

* * Now that you are ready, let me give you your first task.

@@ -119,572 +59,420 @@ namespace Server.Engines.Quests.Haven * * Good luck young Paladin! */ - return 1060388; - } - } - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1023676, 0xE68 ) // glowing rune - }; - - public override QuestItemInfo[] Info => m_Info; - - public UzeraanFirstTaskConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new KillHordeMinionsObjective() ); - } - } - - public class UzeraanReportConversation : QuestConversation - { - public override object Message - { - get - { - if ( System.From.Profession == 2 ) // magician - { - /* You give your report to Uzeraan and after a while, he begins to - * speak...

- * - * Your report is grim, but all hope is not lost! It has become apparent - * that our swords and spells will not drive the evil from Haven.

- * - * The head of my order, the High Mage Schmendrick, arrived here shortly after - * you went into battle with the Horde Minions. He has brought with him a - * scroll of great power, that should aid us greatly in our battle.

- * - * Unfortunately, the entrance to one of our mining caves collapsed recently, - * trapping our miners inside.

- * - * Schmendrick went to install magical teleporters inside the mines so that - * the miners would have a way out. The miners have since returned, but Schmendrick has not. - * Those who have returned, all seem to have lost their minds to madness; - * mumbling strange things of "the souls of the dead seeking revenge".

- * - * No matter. We must find Schmendrick.

- * - * Step onto the teleporter, located against the wall, and seek Schmendrick in the mines.

- * - * I've given you a bag with some Travel Spells, - * in case you need to make a quick escape. In addition, you may wish to cast - * the Night Sight spell on yourself before going - * into the cave, as it it's pretty dark in there.

- * - * Now please go. Good luck, friend. - */ - return 1049387; - } - - /* You give your report to Uzeraan and after a while, - * he begins to speak...

- * - * Your report is grim, but all hope is not lost! It has become apparent - * that our swords and spells will not drive the evil from Haven.

- * - * The head of my order, the High Mage Schmendrick, arrived here shortly after - * you went into battle with the Horde Minions. He has brought with him a - * scroll of great power, that should aid us greatly in our battle.

- * - * Unfortunately, the entrance to one of our mining caves collapsed recently, - * trapping our miners inside.

- * - * Schmendrick went to install magical teleporters inside the mines so that - * the miners would have a way out. The miners have since returned, but Schmendrick has not. - * Those who have returned, all seem to have lost their minds to madness; - * mumbling strange things of "the souls of the dead seeking revenge".

- * - * No matter. We must find Schmendrick.

- * - * Step onto the teleporter, located against the wall, and seek Schmendrick in the mines.

- * - * I've given you a bag with some Night Sight - * and Healing potions - * to help you out along the way. Good luck. - */ - return 1049119; - } - } - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1026153, 0x1822 ), // teleporter - new QuestItemInfo( 1048032, 0xE76 ) // a bag - }; - - public override QuestItemInfo[] Info => m_Info; - - public UzeraanReportConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindSchmendrickObjective() ); - } - } - - public class SchmendrickConversation : QuestConversation - { - public override object Message - { - get - { - if ( System.From.Profession == 5 ) // paladin - { - /* Schmendrick barely pays you any attention as you approach him. - * His mind seems to be occupied with something else. You explain to him that - * you came for the scroll of power and after a long while he begins to speak, - * but apparently still not giving you his full attention...

- * - * Hmmm.. peculiar indeed. Very strange activity here indeed... I wonder...

- * - * Hmmm. Oh yes! Scroll, you say? I don't have it, sorry. My apprentice - * was carrying it, and he ran off to somewhere in this cave. Find him and - * you will find the scroll.

- * - * Be sure to bring the scroll to Uzeraan once you have it. He's the only person - * aside from myself who can read the ancient markings on the scroll. - * I need to figure out what's going on down here before I can leave. - * Strange activity indeed...

- * - * One more thing...

- * - * Be careful of the restless souls wandering about. They seem to be in the habit - * of spontaneously attacking people. Perhaps using your paladin ability - * Enemy of One might help you overcome the perils - * of these halls.

- * - * Schmendrick goes back to his work and you seem to completely fade from his awareness... - */ - return 1060749; - } - - /* Schmendrick barely pays you any attention as you approach him. His - * mind seems to be occupied with something else. You explain to him that - * you came for the scroll of power and after a long while he begins to speak, - * but apparently still not giving you his full attention...

- * - * Hmmm.. peculiar indeed. Very strange activity here indeed... I wonder...

- * - * Hmmm. Oh yes! Scroll, you say? I don't have it, sorry. My apprentice was - * carrying it, and he ran off to somewhere in this cave. Find him and you will - * find the scroll.

Be sure to bring the scroll to Uzeraan once you - * have it. He's the only person aside from myself who can read the ancient - * markings on the scroll. I need to figure out what's going on down here before - * I can leave. Strange activity indeed...

- * - * Schmendrick goes back to his work and you seem to completely fade from his - * awareness... - */ - return 1049322; - } - } - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1023637, 0xE34 ) // scroll - }; - - public override QuestItemInfo[] Info => m_Info; - - public SchmendrickConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindApprenticeObjective() ); - } - } - - public class UzeraanScrollOfPowerConversation : QuestConversation - { - public override object Message => 1049325; - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1048030, 0x14EB ), // a Treasure Map - new QuestItemInfo( 1023969, 0xF81 ), // Fertile Dirt - new QuestItemInfo( 1049117, 0xFC4 ) // Horn of Retreat - }; - - public override QuestItemInfo[] Info => m_Info; - - public UzeraanScrollOfPowerConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindDryadObjective() ); - } - } - - public class DryadConversation : QuestConversation - { - public override object Message => 1049326; - - public DryadConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnFertileDirtObjective() ); - } - } - - public class UzeraanFertileDirtConversation : QuestConversation - { - public override object Message - { - get - { - if ( System.From.Profession == 2 ) // magician - { - /* Uzeraan takes the dirt from you and smiles...

- * - * Wonderful! I knew I could count on you. As a token of my appreciation - * I've given you a bag with some reagents - * as well as some spell scrolls. They should - * help out a bit.

- * - * The next item I need is a Vial of Blood. I know it seems strange, - * but that's what the formula asks for. I have some locked away in a chest - * not far from here. It's only a short distance from the mansion. Let me - * give you directions...

Exit the front door to the East. Then follow - * the path to the North. You will pass by several pedestals with lanterns on - * them. Continue on this path until you run into a small hut. Walk up the - * stairs and through the door. Inside you will find a chest. Open it and - * bring me a Vial of Blood from inside the chest. It's very easy to find. - * Just follow the road and you can't miss it.

- * - * Good luck! - */ - return 1049388; - } - - /* Uzeraan takes the dirt from you and smiles...

- * - * Wonderful! I knew I could count on you. As a token of my appreciation - * I've given you a bag with some bandages as well as some healing potions. - * They should help out a bit.

- * - * The next item I need is a Vial of Blood. I know it seems strange, - * but that's what the formula asks for. I have some locked away in a chest - * not far from here. It's only a short distance from the mansion. Let me give - * you directions...

- * - * Exit the front door to the East. Then follow the path to the North. - * You will pass by several pedestals with lanterns on them. Continue on this - * path until you run into a small hut. Walk up the stairs and through the door. - * Inside you will find a chest. Open it and bring me a Vial of Blood - * from inside the chest. It's very easy to find. Just follow the road and you - * can't miss it.

- * - * Good luck! - */ - return 1049329; - } - } - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1023965, 0xF7D ), // Daemon Blood - new QuestItemInfo( 1022581, 0xA22 ), // lantern - }; - - public override QuestItemInfo[] Info => m_Info; - - public UzeraanFertileDirtConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new GetDaemonBloodObjective() ); - } - } - - public class UzeraanDaemonBloodConversation : QuestConversation - { - public override object Message - { - get - { - if ( System.From.Profession == 2 ) // magician - { - //return 1049389; // localized message is bugged - return "You hand Uzeraan the Vial of Blood, which he hastily accepts...
" - + "
" - + "Excellent work! Only one reagent remains and the spell is complete! The final " - + "requirement is a Daemon Bone, which will not be as easily acquired as the " - + "previous two components.
" - + "
" - + "There is a haunted graveyard on this island, which is the home to many undead " - + "creatures. Dispose of the undead as you see fit. Be sure to search their remains " - + "after you have smitten them, to check for a Daemon Bone. I'm quite sure " - + "that you will find what we seek, if you are thorough enough with your " - + "extermination.
" - + "
" - + "Take these explosion spell scrolls and magical wizard's hat to aid you in your " - + "battle. The scrolls should help you make short work of the undead.
" - + "
" - + "Return here when you have found a Daemon Bone."; - } - - /* You hand Uzeraan the Vial of Blood, which he hastily accepts...

- * - * Excellent work! Only one reagent remains and the spell is complete! - * The final requirement is a Daemon Bone, which will not be as easily - * acquired as the previous two components.

- * - * There is a haunted graveyard on this island, which is the home to many - * undead creatures. Dispose of the undead as you see fit. Be sure to search - * their remains after you have smitten them, to check for a Daemon Bone. - * I'm quite sure that you will find what we seek, if you are thorough enough - * with your extermination.

- * - * Take this magical silver sword to aid you in your battle. Silver weapons - * will damage the undead twice as much as your regular weapon.

- * - * Return here when you have found a Daemon Bone. - */ - return 1049333; - } - } - - private static QuestItemInfo[] m_Info = { - new QuestItemInfo( 1017412, 0xF80 ), // Daemon Bone - }; - - private static QuestItemInfo[] m_InfoPaladin = { - new QuestItemInfo( 1017412, 0xF80 ), // Daemon Bone - new QuestItemInfo( 1060577, 0x1F14 ), // Recall Rune - }; - - public override QuestItemInfo[] Info - { - get - { - if ( System.From.Profession == 5 ) // paladin - return m_InfoPaladin; - return m_Info; - } - } - - public UzeraanDaemonBloodConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new GetDaemonBoneObjective() ); - } - } - - public class UzeraanDaemonBoneConversation : QuestConversation - { - public override object Message => 1049335; - - public UzeraanDaemonBoneConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new CashBankCheckObjective() ); - } - } - - public class BankerConversation : QuestConversation - { - public override object Message => 1060137; - - public BankerConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } - - public class RadarConversation : QuestConversation - { - public override object Message => 1049660; - - public override bool Logged => false; - - public RadarConversation() - { - } - } - - public class LostScrollOfPowerConversation : QuestConversation - { - private bool m_FromUzeraan; - - public override object Message - { - get - { - if ( m_FromUzeraan ) - { - /* You return without the scroll???

- * - * All hope is lost without it, friend. Return to the mines and talk to - * Schmendrick to see if he can help us out of this predicament. - */ - return 1049377; - } - - /* You've lost the scroll? Argh! I will have to try and re-construct - * the scroll from memory. Bring me a blank scroll, which you can - * purchase from the mage shop just - * East of Uzeraan's mansion in Haven.

- * - * Return the scroll to me and I will try to make another scroll for you.

- * - * When you return, be sure to hand me the scroll (drag and drop). - */ - return 1049345; - } - } - - public override bool Logged => false; - - public LostScrollOfPowerConversation( bool fromUzeraan ) - { - m_FromUzeraan = fromUzeraan; - } - - public LostScrollOfPowerConversation() - { - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_FromUzeraan = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_FromUzeraan ); - } - } - - public class LostFertileDirtConversation : QuestConversation - { - private bool m_FromUzeraan; - - public override object Message - { - get - { - if ( m_FromUzeraan ) - { - /* You return without Fertile Dirt? It is imperative that we - * get all of the ingredients friend.

- * - * Seek out the Dryad and ask her to help you again. - */ - return 1049374; - } - - /* You've lost the dirt I gave you?

- * - * My, my, my... What ever shall we do now?

- * - * I can try to make you some more, but I will need something - * that I can transform. Bring me an apple, and I shall - * see what I can do.

- * - * You can buy apples from the - * Provisioner's Shop, which is located a ways East - * of Uzeraan's mansion.

- * - * Hand me the apple when you have it, and I shall see about transforming - * it for you.

- * - * Good luck.

- */ - return 1049359; - } - } - - public override bool Logged => false; - - public LostFertileDirtConversation( bool fromUzeraan ) - { - m_FromUzeraan = fromUzeraan; - } - - public LostFertileDirtConversation() - { - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_FromUzeraan = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_FromUzeraan ); - } - } - - public class DryadAppleConversation : QuestConversation - { - public override object Message => 1049360; - - public override bool Logged => false; - - public DryadAppleConversation() - { - } - } - - public class LostDaemonBloodConversation : QuestConversation - { - public override object Message => 1049375; - - public override bool Logged => false; - - public LostDaemonBloodConversation() - { - } - } - - public class LostDaemonBoneConversation : QuestConversation - { - public override object Message => 1049376; - - public override bool Logged => false; - - public LostDaemonBoneConversation() - { - } - } - - public class FewReagentsConversation : QuestConversation - { - public override object Message => 1049390; - - public override bool Logged => false; - - public FewReagentsConversation() - { - } - } -} + return 1060388; + } + } + + public override QuestItemInfo[] Info => m_Info; + + public override void OnRead() + { + System.AddObjective(new KillHordeMinionsObjective()); + } + } + + public class UzeraanReportConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1026153, 0x1822), // teleporter + new QuestItemInfo(1048032, 0xE76) // a bag + }; + + public override object Message + { + get + { + if (System.From.Profession == 2) // magician + return 1049387; + + /* You give your report to Uzeraan and after a while, + * he begins to speak...

+ * + * Your report is grim, but all hope is not lost! It has become apparent + * that our swords and spells will not drive the evil from Haven.

+ * + * The head of my order, the High Mage Schmendrick, arrived here shortly after + * you went into battle with the Horde Minions. He has brought with him a + * scroll of great power, that should aid us greatly in our battle.

+ * + * Unfortunately, the entrance to one of our mining caves collapsed recently, + * trapping our miners inside.

+ * + * Schmendrick went to install magical teleporters inside the mines so that + * the miners would have a way out. The miners have since returned, but Schmendrick has not. + * Those who have returned, all seem to have lost their minds to madness; + * mumbling strange things of "the souls of the dead seeking revenge".

+ * + * No matter. We must find Schmendrick.

+ * + * Step onto the teleporter, located against the wall, and seek Schmendrick in the mines.

+ * + * I've given you a bag with some Night Sight + * and Healing potions + * to help you out along the way. Good luck. + */ + return 1049119; + } + } + + public override QuestItemInfo[] Info => m_Info; + + public override void OnRead() + { + System.AddObjective(new FindSchmendrickObjective()); + } + } + + public class SchmendrickConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1023637, 0xE34) // scroll + }; + + public override object Message + { + get + { + if (System.From.Profession == 5) // paladin + return 1060749; + + /* Schmendrick barely pays you any attention as you approach him. His + * mind seems to be occupied with something else. You explain to him that + * you came for the scroll of power and after a long while he begins to speak, + * but apparently still not giving you his full attention...

+ * + * Hmmm.. peculiar indeed. Very strange activity here indeed... I wonder...

+ * + * Hmmm. Oh yes! Scroll, you say? I don't have it, sorry. My apprentice was + * carrying it, and he ran off to somewhere in this cave. Find him and you will + * find the scroll.

Be sure to bring the scroll to Uzeraan once you + * have it. He's the only person aside from myself who can read the ancient + * markings on the scroll. I need to figure out what's going on down here before + * I can leave. Strange activity indeed...

+ * + * Schmendrick goes back to his work and you seem to completely fade from his + * awareness... + */ + return 1049322; + } + } + + public override QuestItemInfo[] Info => m_Info; + + public override void OnRead() + { + System.AddObjective(new FindApprenticeObjective()); + } + } + + public class UzeraanScrollOfPowerConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1048030, 0x14EB), // a Treasure Map + new QuestItemInfo(1023969, 0xF81), // Fertile Dirt + new QuestItemInfo(1049117, 0xFC4) // Horn of Retreat + }; + + public override object Message => 1049325; + + public override QuestItemInfo[] Info => m_Info; + + public override void OnRead() + { + System.AddObjective(new FindDryadObjective()); + } + } + + public class DryadConversation : QuestConversation + { + public override object Message => 1049326; + + public override void OnRead() + { + System.AddObjective(new ReturnFertileDirtObjective()); + } + } + + public class UzeraanFertileDirtConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1023965, 0xF7D), // Daemon Blood + new QuestItemInfo(1022581, 0xA22) // lantern + }; + + public override object Message + { + get + { + if (System.From.Profession == 2) // magician + return 1049388; + + /* Uzeraan takes the dirt from you and smiles...

+ * + * Wonderful! I knew I could count on you. As a token of my appreciation + * I've given you a bag with some bandages as well as some healing potions. + * They should help out a bit.

+ * + * The next item I need is a Vial of Blood. I know it seems strange, + * but that's what the formula asks for. I have some locked away in a chest + * not far from here. It's only a short distance from the mansion. Let me give + * you directions...

+ * + * Exit the front door to the East. Then follow the path to the North. + * You will pass by several pedestals with lanterns on them. Continue on this + * path until you run into a small hut. Walk up the stairs and through the door. + * Inside you will find a chest. Open it and bring me a Vial of Blood + * from inside the chest. It's very easy to find. Just follow the road and you + * can't miss it.

+ * + * Good luck! + */ + return 1049329; + } + } + + public override QuestItemInfo[] Info => m_Info; + + public override void OnRead() + { + System.AddObjective(new GetDaemonBloodObjective()); + } + } + + public class UzeraanDaemonBloodConversation : QuestConversation + { + private static QuestItemInfo[] m_Info = + { + new QuestItemInfo(1017412, 0xF80) // Daemon Bone + }; + + private static QuestItemInfo[] m_InfoPaladin = + { + new QuestItemInfo(1017412, 0xF80), // Daemon Bone + new QuestItemInfo(1060577, 0x1F14) // Recall Rune + }; + + public override object Message + { + get + { + if (System.From.Profession == 2) // magician + return "You hand Uzeraan the Vial of Blood, which he hastily accepts...
" + + "
" + + "Excellent work! Only one reagent remains and the spell is complete! The final " + + "requirement is a Daemon Bone, which will not be as easily acquired as the " + + "previous two components.
" + + "
" + + "There is a haunted graveyard on this island, which is the home to many undead " + + "creatures. Dispose of the undead as you see fit. Be sure to search their remains " + + "after you have smitten them, to check for a Daemon Bone. I'm quite sure " + + "that you will find what we seek, if you are thorough enough with your " + + "extermination.
" + + "
" + + "Take these explosion spell scrolls and magical wizard's hat to aid you in your " + + "battle. The scrolls should help you make short work of the undead.
" + + "
" + + "Return here when you have found a Daemon Bone."; + + /* You hand Uzeraan the Vial of Blood, which he hastily accepts...

+ * + * Excellent work! Only one reagent remains and the spell is complete! + * The final requirement is a Daemon Bone, which will not be as easily + * acquired as the previous two components.

+ * + * There is a haunted graveyard on this island, which is the home to many + * undead creatures. Dispose of the undead as you see fit. Be sure to search + * their remains after you have smitten them, to check for a Daemon Bone. + * I'm quite sure that you will find what we seek, if you are thorough enough + * with your extermination.

+ * + * Take this magical silver sword to aid you in your battle. Silver weapons + * will damage the undead twice as much as your regular weapon.

+ * + * Return here when you have found a Daemon Bone. + */ + return 1049333; + } + } + + public override QuestItemInfo[] Info + { + get + { + if (System.From.Profession == 5) // paladin + return m_InfoPaladin; + return m_Info; + } + } + + public override void OnRead() + { + System.AddObjective(new GetDaemonBoneObjective()); + } + } + + public class UzeraanDaemonBoneConversation : QuestConversation + { + public override object Message => 1049335; + + public override void OnRead() + { + System.AddObjective(new CashBankCheckObjective()); + } + } + + public class BankerConversation : QuestConversation + { + public override object Message => 1060137; + + public override void OnRead() + { + System.Complete(); + } + } + + public class RadarConversation : QuestConversation + { + public override object Message => 1049660; + + public override bool Logged => false; + } + + public class LostScrollOfPowerConversation : QuestConversation + { + private bool m_FromUzeraan; + + public LostScrollOfPowerConversation(bool fromUzeraan) + { + m_FromUzeraan = fromUzeraan; + } + + public LostScrollOfPowerConversation() + { + } + + public override object Message + { + get + { + if (m_FromUzeraan) return 1049377; + + /* You've lost the scroll? Argh! I will have to try and re-construct + * the scroll from memory. Bring me a blank scroll, which you can + * purchase from the mage shop just + * East of Uzeraan's mansion in Haven.

+ * + * Return the scroll to me and I will try to make another scroll for you.

+ * + * When you return, be sure to hand me the scroll (drag and drop). + */ + return 1049345; + } + } + + public override bool Logged => false; + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_FromUzeraan = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_FromUzeraan); + } + } + + public class LostFertileDirtConversation : QuestConversation + { + private bool m_FromUzeraan; + + public LostFertileDirtConversation(bool fromUzeraan) + { + m_FromUzeraan = fromUzeraan; + } + + public LostFertileDirtConversation() + { + } + + public override object Message + { + get + { + if (m_FromUzeraan) return 1049374; + + /* You've lost the dirt I gave you?

+ * + * My, my, my... What ever shall we do now?

+ * + * I can try to make you some more, but I will need something + * that I can transform. Bring me an apple, and I shall + * see what I can do.

+ * + * You can buy apples from the + * Provisioner's Shop, which is located a ways East + * of Uzeraan's mansion.

+ * + * Hand me the apple when you have it, and I shall see about transforming + * it for you.

+ * + * Good luck.

+ */ + return 1049359; + } + } + + public override bool Logged => false; + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_FromUzeraan = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_FromUzeraan); + } + } + + public class DryadAppleConversation : QuestConversation + { + public override object Message => 1049360; + + public override bool Logged => false; + } + + public class LostDaemonBloodConversation : QuestConversation + { + public override object Message => 1049375; + + public override bool Logged => false; + } + + public class LostDaemonBoneConversation : QuestConversation + { + public override object Message => 1049376; + + public override bool Logged => false; + } + + public class FewReagentsConversation : QuestConversation + { + public override object Message => 1049390; + + public override bool Logged => false; + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/Cannon.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/Cannon.cs index f6d749b65..87432363e 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/Cannon.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/Cannon.cs @@ -2,174 +2,185 @@ using Server.Items; namespace Server.Engines.Quests.Haven { - public enum CannonDirection - { - North, - East, - South, - West - } + public enum CannonDirection + { + North, + East, + South, + West + } - public class Cannon : BaseAddon - { - [CommandProperty( AccessLevel.GameMaster )] - public CannonDirection CannonDirection { get; private set; } + public class Cannon : BaseAddon + { + [Constructible] + public Cannon(CannonDirection direction) + { + CannonDirection = direction; - [CommandProperty( AccessLevel.GameMaster )] - public MilitiaCanoneer Canoneer { get; set; } + switch (direction) + { + case CannonDirection.North: + { + AddComponent(new CannonComponent(0xE8D), 0, 0, 0); + AddComponent(new CannonComponent(0xE8C), 0, 1, 0); + AddComponent(new CannonComponent(0xE8B), 0, 2, 0); - [Constructible] - public Cannon( CannonDirection direction ) - { - CannonDirection = direction; + break; + } + case CannonDirection.East: + { + AddComponent(new CannonComponent(0xE96), 0, 0, 0); + AddComponent(new CannonComponent(0xE95), -1, 0, 0); + AddComponent(new CannonComponent(0xE94), -2, 0, 0); - switch ( direction ) - { - case CannonDirection.North: - { - AddComponent( new CannonComponent( 0xE8D ), 0, 0, 0 ); - AddComponent( new CannonComponent( 0xE8C ), 0, 1, 0 ); - AddComponent( new CannonComponent( 0xE8B ), 0, 2, 0 ); + break; + } + case CannonDirection.South: + { + AddComponent(new CannonComponent(0xE91), 0, 0, 0); + AddComponent(new CannonComponent(0xE92), 0, -1, 0); + AddComponent(new CannonComponent(0xE93), 0, -2, 0); - break; - } - case CannonDirection.East: - { - AddComponent( new CannonComponent( 0xE96 ), 0, 0, 0 ); - AddComponent( new CannonComponent( 0xE95 ), -1, 0, 0 ); - AddComponent( new CannonComponent( 0xE94 ), -2, 0, 0 ); + break; + } + default: + { + AddComponent(new CannonComponent(0xE8E), 0, 0, 0); + AddComponent(new CannonComponent(0xE8F), 1, 0, 0); + AddComponent(new CannonComponent(0xE90), 2, 0, 0); - break; - } - case CannonDirection.South: - { - AddComponent( new CannonComponent( 0xE91 ), 0, 0, 0 ); - AddComponent( new CannonComponent( 0xE92 ), 0, -1, 0 ); - AddComponent( new CannonComponent( 0xE93 ), 0, -2, 0 ); + break; + } + } + } - break; - } - default: - { - AddComponent( new CannonComponent( 0xE8E ), 0, 0, 0 ); - AddComponent( new CannonComponent( 0xE8F ), 1, 0, 0 ); - AddComponent( new CannonComponent( 0xE90 ), 2, 0, 0 ); + public Cannon(Serial serial) : base(serial) + { + } - break; - } - } - } + [CommandProperty(AccessLevel.GameMaster)] + public CannonDirection CannonDirection{ get; private set; } - public Cannon( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public MilitiaCanoneer Canoneer{ get; set; } - public void DoFireEffect( IPoint3D target ) - { - Point3D from; - switch ( CannonDirection ) - { - case CannonDirection.North: from = new Point3D( X, Y - 1, Z ); break; - case CannonDirection.East: from = new Point3D( X + 1, Y, Z ); break; - case CannonDirection.South: from = new Point3D( X, Y + 1, Z ); break; - default: from = new Point3D( X - 1, Y, Z ); break; - } + public override bool HandlesOnMovement => Canoneer != null && !Canoneer.Deleted && Canoneer.Active; - Effects.SendLocationEffect( from, Map, 0x36B0, 16, 1 ); - Effects.PlaySound( from, Map, 0x11D ); + public void DoFireEffect(IPoint3D target) + { + Point3D from; + switch (CannonDirection) + { + case CannonDirection.North: + from = new Point3D(X, Y - 1, Z); + break; + case CannonDirection.East: + from = new Point3D(X + 1, Y, Z); + break; + case CannonDirection.South: + from = new Point3D(X, Y + 1, Z); + break; + default: + from = new Point3D(X - 1, Y, Z); + break; + } - Effects.SendLocationEffect( target, Map, 0x36B0, 16, 1 ); - Effects.PlaySound( target, Map, 0x11D ); - } + Effects.SendLocationEffect(from, Map, 0x36B0, 16, 1); + Effects.PlaySound(from, Map, 0x11D); - public void Fire( Mobile from, Mobile target ) - { - DoFireEffect( target ); + Effects.SendLocationEffect(target, Map, 0x36B0, 16, 1); + Effects.PlaySound(target, Map, 0x11D); + } - target.Damage( 9999, from ); - } + public void Fire(Mobile from, Mobile target) + { + DoFireEffect(target); - public override bool HandlesOnMovement => Canoneer != null && !Canoneer.Deleted && Canoneer.Active; + target.Damage(9999, from); + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Canoneer == null || Canoneer.Deleted || !Canoneer.Active ) - return; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Canoneer == null || Canoneer.Deleted || !Canoneer.Active) + return; - bool canFire; - switch ( CannonDirection ) - { - case CannonDirection.North: - canFire = m.X >= X - 7 && m.X <= X + 7 && m.Y == Y - 7 && oldLocation.Y < Y - 7; - break; - case CannonDirection.East: - canFire = m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X + 7 && oldLocation.X > X + 7; - break; - case CannonDirection.South: - canFire = m.X >= X - 7 && m.X <= X + 7 && m.Y == Y + 7 && oldLocation.Y > Y + 7; - break; - default: - canFire = m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X - 7 && oldLocation.X < X - 7; - break; - } + bool canFire; + switch (CannonDirection) + { + case CannonDirection.North: + canFire = m.X >= X - 7 && m.X <= X + 7 && m.Y == Y - 7 && oldLocation.Y < Y - 7; + break; + case CannonDirection.East: + canFire = m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X + 7 && oldLocation.X > X + 7; + break; + case CannonDirection.South: + canFire = m.X >= X - 7 && m.X <= X + 7 && m.Y == Y + 7 && oldLocation.Y > Y + 7; + break; + default: + canFire = m.Y >= Y - 7 && m.Y <= Y + 7 && m.X == X - 7 && oldLocation.X < X - 7; + break; + } - if ( canFire && Canoneer.WillFire( this, m ) ) - Fire( Canoneer, m ); - } + if (canFire && Canoneer.WillFire(this, m)) + Fire(Canoneer, m); + } - public override void Serialize( GenericWriter writer ) - { - if ( Canoneer != null && Canoneer.Deleted ) - Canoneer = null; + public override void Serialize(GenericWriter writer) + { + if (Canoneer != null && Canoneer.Deleted) + Canoneer = null; - base.Serialize( writer ); + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.WriteEncodedInt( (int) CannonDirection ); - writer.Write( (Mobile) Canoneer ); - } + writer.WriteEncodedInt((int)CannonDirection); + writer.Write(Canoneer); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - CannonDirection = (CannonDirection) reader.ReadEncodedInt(); - Canoneer = (MilitiaCanoneer) reader.ReadMobile(); - } - } + CannonDirection = (CannonDirection)reader.ReadEncodedInt(); + Canoneer = (MilitiaCanoneer)reader.ReadMobile(); + } + } - public class CannonComponent : AddonComponent - { - [CommandProperty( AccessLevel.GameMaster )] - public MilitiaCanoneer Canoneer - { - get => Addon is Cannon cannon ? cannon.Canoneer : null; - set { if ( Addon is Cannon cannon ) cannon.Canoneer = value; } - } + public class CannonComponent : AddonComponent + { + public CannonComponent(int itemID) : base(itemID) + { + } - public CannonComponent( int itemID ) : base( itemID ) - { - } + public CannonComponent(Serial serial) : base(serial) + { + } - public CannonComponent( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public MilitiaCanoneer Canoneer + { + get => Addon is Cannon cannon ? cannon.Canoneer : null; + set + { + if (Addon is Cannon cannon) cannon.Canoneer = value; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/DaemonBloodChest.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/DaemonBloodChest.cs index fcd69b8df..dfa2cfac5 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/DaemonBloodChest.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/DaemonBloodChest.cs @@ -3,65 +3,67 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class DaemonBloodChest : MetalChest - { - [Constructible] - public DaemonBloodChest() - { - Movable = false; - } + public class DaemonBloodChest : MetalChest + { + [Constructible] + public DaemonBloodChest() + { + Movable = false; + } - public DaemonBloodChest( Serial serial ) : base( serial ) - { - } + public DaemonBloodChest(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( from is PlayerMobile player && player.InRange( GetWorldLocation(), 2 ) ) - { - QuestSystem qs = player.Quest; + public override void OnDoubleClick(Mobile from) + { + if (from is PlayerMobile player && player.InRange(GetWorldLocation(), 2)) + { + QuestSystem qs = player.Quest; - if ( qs is UzeraanTurmoilQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( GetDaemonBloodObjective ) ); + if (qs is UzeraanTurmoilQuest) + { + QuestObjective obj = qs.FindObjective(typeof(GetDaemonBloodObjective)); - if ( (obj != null && !obj.Completed) || UzeraanTurmoilQuest.HasLostDaemonBlood( player ) ) - { - Item vial = new QuestDaemonBlood(); + if (obj != null && !obj.Completed || UzeraanTurmoilQuest.HasLostDaemonBlood(player)) + { + Item vial = new QuestDaemonBlood(); - if ( player.PlaceInBackpack( vial ) ) - { - player.SendLocalizedMessage( 1049331, "", 0x22 ); // You take a vial of blood from the chest and put it in your pack. + if (player.PlaceInBackpack(vial)) + { + player.SendLocalizedMessage(1049331, "", + 0x22); // You take a vial of blood from the chest and put it in your pack. - if ( obj != null && !obj.Completed ) - obj.Complete(); - } - else - { - player.SendLocalizedMessage( 1049338, "", 0x22 ); // You find a vial of blood, but can't pick it up because your pack is too full. Come back when you have more room in your pack. - vial.Delete(); - } + if (obj != null && !obj.Completed) + obj.Complete(); + } + else + { + player.SendLocalizedMessage(1049338, "", + 0x22); // You find a vial of blood, but can't pick it up because your pack is too full. Come back when you have more room in your pack. + vial.Delete(); + } - return; - } - } - } + return; + } + } + } - base.OnDoubleClick( from ); - } + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBlood.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBlood.cs index 300c4145e..f30b1f1e4 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBlood.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBlood.cs @@ -2,37 +2,37 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class QuestDaemonBlood : QuestItem - { - [Constructible] - public QuestDaemonBlood() : base( 0xF7D ) - { - Weight = 1.0; - } + public class QuestDaemonBlood : QuestItem + { + [Constructible] + public QuestDaemonBlood() : base(0xF7D) + { + Weight = 1.0; + } - public QuestDaemonBlood( Serial serial ) : base( serial ) - { - } + public QuestDaemonBlood(Serial serial) : base(serial) + { + } - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is UzeraanTurmoilQuest); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is UzeraanTurmoilQuest); - /*return !qs.IsObjectiveInProgress( typeof( ReturnDaemonBloodObjective ) );*/ - } + /*return !qs.IsObjectiveInProgress( typeof( ReturnDaemonBloodObjective ) );*/ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBone.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBone.cs index 099b13174..82090d543 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBone.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestDaemonBone.cs @@ -2,37 +2,37 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class QuestDaemonBone : QuestItem - { - [Constructible] - public QuestDaemonBone() : base( 0xF80 ) - { - Weight = 1.0; - } + public class QuestDaemonBone : QuestItem + { + [Constructible] + public QuestDaemonBone() : base(0xF80) + { + Weight = 1.0; + } - public QuestDaemonBone( Serial serial ) : base( serial ) - { - } + public QuestDaemonBone(Serial serial) : base(serial) + { + } - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is UzeraanTurmoilQuest); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is UzeraanTurmoilQuest); - //return !qs.IsObjectiveInProgress( typeof( ReturnDaemonBoneObjective ) ); - } + //return !qs.IsObjectiveInProgress( typeof( ReturnDaemonBoneObjective ) ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestFertileDirt.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestFertileDirt.cs index 1b54a7871..990bcd6a3 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestFertileDirt.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/QuestFertileDirt.cs @@ -2,37 +2,37 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class QuestFertileDirt : QuestItem - { - [Constructible] - public QuestFertileDirt() : base( 0xF81 ) - { - Weight = 1.0; - } + public class QuestFertileDirt : QuestItem + { + [Constructible] + public QuestFertileDirt() : base(0xF81) + { + Weight = 1.0; + } - public QuestFertileDirt( Serial serial ) : base( serial ) - { - } + public QuestFertileDirt(Serial serial) : base(serial) + { + } - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is UzeraanTurmoilQuest); + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is UzeraanTurmoilQuest); - //return !qs.IsObjectiveInProgress( typeof( ReturnFertileDirtObjective ) ); - } + //return !qs.IsObjectiveInProgress( typeof( ReturnFertileDirtObjective ) ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickApprenticeCorpse.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickApprenticeCorpse.cs index 958ecb581..d5907641c 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickApprenticeCorpse.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickApprenticeCorpse.cs @@ -1,199 +1,202 @@ using System.Collections.Generic; using Server.Items; +using Server.Misc; using Server.Mobiles; using Server.Network; namespace Server.Engines.Quests.Haven { - public class SchmendrickApprenticeCorpse : Corpse - { - private static Mobile GetOwner() - { - Mobile apprentice = new Mobile(); + public class SchmendrickApprenticeCorpse : Corpse + { + private static int m_HairHue; - apprentice.Hue = Utility.RandomSkinHue(); - apprentice.Female = false; - apprentice.Body = 0x190; - apprentice.Name = NameList.RandomName( "male" ); + private Lantern m_Lantern; - apprentice.Delete(); + [Constructible] + public SchmendrickApprenticeCorpse() : base(GetOwner(), GetHair(), GetFacialHair(), GetEquipment()) + { + Direction = Direction.West; - return apprentice; - } + foreach (Item item in EquipItems) DropItem(item); - private static List GetEquipment() - { - List list = new List(); + m_Lantern = new Lantern(); + m_Lantern.Movable = false; + m_Lantern.Protected = true; + m_Lantern.Ignite(); + } - list.Add( new Robe( QuestSystem.RandomBrightHue() ) ); - list.Add( new WizardsHat( Utility.RandomNeutralHue() ) ); - list.Add( new Shoes( Utility.RandomNeutralHue() ) ); + public SchmendrickApprenticeCorpse(Serial serial) : base(serial) + { + } - /* - int hairHue = Utility.RandomHairHue(); + private static Mobile GetOwner() + { + Mobile apprentice = new Mobile(); - switch ( Utility.Random( 8 ) ) - { - case 0: list.Add( new Afro( hairHue ) ); break; - case 1: list.Add( new KrisnaHair( hairHue ) ); break; - case 2: list.Add( new PageboyHair( hairHue ) ); break; - case 3: list.Add( new PonyTail( hairHue ) ); break; - case 4: list.Add( new ReceedingHair( hairHue ) ); break; - case 5: list.Add( new TwoPigTails( hairHue ) ); break; - case 6: list.Add( new ShortHair( hairHue ) ); break; - case 7: list.Add( new LongHair( hairHue ) ); break; - } + apprentice.Hue = Utility.RandomSkinHue(); + apprentice.Female = false; + apprentice.Body = 0x190; + apprentice.Name = NameList.RandomName("male"); - switch ( Utility.Random( 5 ) ) - { - case 0: list.Add( new LongBeard( hairHue ) ); break; - case 1: list.Add( new MediumLongBeard( hairHue ) ); break; - case 2: list.Add( new Vandyke( hairHue ) ); break; - case 3: list.Add( new Mustache( hairHue ) ); break; - case 4: list.Add( new Goatee( hairHue ) ); break; - } - * */ + apprentice.Delete(); - list.Add( new Spellbook() ); + return apprentice; + } - return list; - } + private static List GetEquipment() + { + List list = new List(); - private static int m_HairHue; - private static HairInfo GetHair() - { - m_HairHue = Race.Human.RandomHairHue(); + list.Add(new Robe(QuestSystem.RandomBrightHue())); + list.Add(new WizardsHat(Utility.RandomNeutralHue())); + list.Add(new Shoes(Utility.RandomNeutralHue())); - return new HairInfo( Race.Human.RandomHair( false ), m_HairHue ); - } + /* + int hairHue = Utility.RandomHairHue(); - private static FacialHairInfo GetFacialHair() - { - m_HairHue = Race.Human.RandomHairHue(); + switch ( Utility.Random( 8 ) ) + { + case 0: list.Add( new Afro( hairHue ) ); break; + case 1: list.Add( new KrisnaHair( hairHue ) ); break; + case 2: list.Add( new PageboyHair( hairHue ) ); break; + case 3: list.Add( new PonyTail( hairHue ) ); break; + case 4: list.Add( new ReceedingHair( hairHue ) ); break; + case 5: list.Add( new TwoPigTails( hairHue ) ); break; + case 6: list.Add( new ShortHair( hairHue ) ); break; + case 7: list.Add( new LongHair( hairHue ) ); break; + } - return new FacialHairInfo( Race.Human.RandomFacialHair( false ), m_HairHue ); - } + switch ( Utility.Random( 5 ) ) + { + case 0: list.Add( new LongBeard( hairHue ) ); break; + case 1: list.Add( new MediumLongBeard( hairHue ) ); break; + case 2: list.Add( new Vandyke( hairHue ) ); break; + case 3: list.Add( new Mustache( hairHue ) ); break; + case 4: list.Add( new Goatee( hairHue ) ); break; + } + * */ - private Lantern m_Lantern; + list.Add(new Spellbook()); - [Constructible] - public SchmendrickApprenticeCorpse() : base( GetOwner(), GetHair(), GetFacialHair(), GetEquipment() ) - { - Direction = Direction.West; + return list; + } - foreach ( Item item in EquipItems ) - { - DropItem( item ); - } + private static HairInfo GetHair() + { + m_HairHue = Race.Human.RandomHairHue(); - m_Lantern = new Lantern(); - m_Lantern.Movable = false; - m_Lantern.Protected = true; - m_Lantern.Ignite(); - } + return new HairInfo(Race.Human.RandomHair(false), m_HairHue); + } - public SchmendrickApprenticeCorpse( Serial serial ) : base( serial ) - { - } + private static FacialHairInfo GetFacialHair() + { + m_HairHue = Race.Human.RandomHairHue(); - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( ItemID == 0x2006 ) // Corpse form - { - list.Add( "a human corpse" ); - list.Add( 1049144, Name ); // the remains of ~1_NAME~ the apprentice - } - else - { - list.Add( 1049145 ); // the remains of a wizard's apprentice - } - } + return new FacialHairInfo(Race.Human.RandomFacialHair(false), m_HairHue); + } - public override void OnSingleClick( Mobile from ) - { - int hue = Notoriety.GetHue( Misc.NotorietyHandlers.CorpseNotoriety( from, this ) ); + public override void AddNameProperty(ObjectPropertyList list) + { + if (ItemID == 0x2006) // Corpse form + { + list.Add("a human corpse"); + list.Add(1049144, Name); // the remains of ~1_NAME~ the apprentice + } + else + { + list.Add(1049145); // the remains of a wizard's apprentice + } + } - if ( ItemID == 0x2006 ) // Corpse form - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, 1049144, "", Name ) ); // the remains of ~1_NAME~ the apprentice - else - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, 1049145, "", "" ) ); // the remains of a wizard's apprentice - } + public override void OnSingleClick(Mobile from) + { + int hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this)); - public override void Open( Mobile from, bool checkSelfLoot ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - return; + if (ItemID == 0x2006) // Corpse form + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049144, "", + Name)); // the remains of ~1_NAME~ the apprentice + else + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049145, "", + "")); // the remains of a wizard's apprentice + } - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + public override void Open(Mobile from, bool checkSelfLoot) + { + if (!from.InRange(GetWorldLocation(), 2)) + return; - if ( qs is UzeraanTurmoilQuest ) - { - QuestObjective obj = qs.FindObjective( typeof( FindApprenticeObjective ) ); + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - { - Item scroll = new SchmendrickScrollOfPower(); + if (qs is UzeraanTurmoilQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FindApprenticeObjective)); - if ( player.PlaceInBackpack( scroll ) ) - { - player.SendLocalizedMessage( 1049147, "", 0x22 ); // You find the scroll and put it in your pack. - obj.Complete(); - } - else - { - player.SendLocalizedMessage( 1049146, "", 0x22 ); // You find the scroll, but can't pick it up because your pack is too full. Come back when you have more room in your pack. - scroll.Delete(); - } + if (obj != null && !obj.Completed) + { + Item scroll = new SchmendrickScrollOfPower(); - return; - } - } - } + if (player.PlaceInBackpack(scroll)) + { + player.SendLocalizedMessage(1049147, "", 0x22); // You find the scroll and put it in your pack. + obj.Complete(); + } + else + { + player.SendLocalizedMessage(1049146, "", + 0x22); // You find the scroll, but can't pick it up because your pack is too full. Come back when you have more room in your pack. + scroll.Delete(); + } - from.SendLocalizedMessage( 1049143, "", 0x22 ); // This is the corpse of a wizard's apprentice. You can't bring yourself to search it without a good reason. - } + return; + } + } + } - public override void OnLocationChange( Point3D oldLoc ) - { - if ( m_Lantern != null && !m_Lantern.Deleted ) - m_Lantern.Location = new Point3D( X, Y + 1, Z ); - } + from.SendLocalizedMessage(1049143, "", + 0x22); // This is the corpse of a wizard's apprentice. You can't bring yourself to search it without a good reason. + } - public override void OnMapChange() - { - if ( m_Lantern != null && !m_Lantern.Deleted ) - m_Lantern.Map = Map; - } + public override void OnLocationChange(Point3D oldLoc) + { + if (m_Lantern != null && !m_Lantern.Deleted) + m_Lantern.Location = new Point3D(X, Y + 1, Z); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnMapChange() + { + if (m_Lantern != null && !m_Lantern.Deleted) + m_Lantern.Map = Map; + } - if ( m_Lantern != null && !m_Lantern.Deleted ) - m_Lantern.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - if ( m_Lantern != null && m_Lantern.Deleted ) - m_Lantern = null; + if (m_Lantern != null && !m_Lantern.Deleted) + m_Lantern.Delete(); + } - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + if (m_Lantern != null && m_Lantern.Deleted) + m_Lantern = null; - writer.Write( (int) 0 ); // version + base.Serialize(writer); - writer.Write( m_Lantern ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Lantern); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Lantern = (Lantern)reader.ReadItem(); - } - } -} + int version = reader.ReadInt(); + + m_Lantern = (Lantern)reader.ReadItem(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickScrollOfPower.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickScrollOfPower.cs index fca18fed1..ac3eb1a65 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickScrollOfPower.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/SchmendrickScrollOfPower.cs @@ -2,38 +2,38 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class SchmendrickScrollOfPower : QuestItem - { - public override int LabelNumber => 1049118; // a scroll with ancient markings + public class SchmendrickScrollOfPower : QuestItem + { + public SchmendrickScrollOfPower() : base(0xE34) + { + Weight = 1.0; + Hue = 0x34D; + } - public SchmendrickScrollOfPower() : base( 0xE34 ) - { - Weight = 1.0; - Hue = 0x34D; - } + public SchmendrickScrollOfPower(Serial serial) : base(serial) + { + } - public SchmendrickScrollOfPower( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1049118; // a scroll with ancient markings - public override bool CanDrop( PlayerMobile player ) - { - return !(player.Quest is UzeraanTurmoilQuest qs && - qs.IsObjectiveInProgress(typeof(ReturnScrollOfPowerObjective))); - } + public override bool CanDrop(PlayerMobile player) + { + return !(player.Quest is UzeraanTurmoilQuest qs && + qs.IsObjectiveInProgress(typeof(ReturnScrollOfPowerObjective))); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilHorn.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilHorn.cs index 3532cd2de..9ae9687eb 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilHorn.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilHorn.cs @@ -2,36 +2,36 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class UzeraanTurmoilHorn : HornOfRetreat - { - public override bool ValidateUse( Mobile from ) - { - return ( from is PlayerMobile pm && pm.Quest is UzeraanTurmoilQuest ); - } + public class UzeraanTurmoilHorn : HornOfRetreat + { + [Constructible] + public UzeraanTurmoilHorn() + { + DestLoc = new Point3D(3597, 2582, 0); + DestMap = Map.Trammel; + } - [Constructible] - public UzeraanTurmoilHorn() - { - DestLoc = new Point3D( 3597, 2582, 0 ); - DestMap = Map.Trammel; - } + public UzeraanTurmoilHorn(Serial serial) : base(serial) + { + } - public UzeraanTurmoilHorn( Serial serial ) : base( serial ) - { - } + public override bool ValidateUse(Mobile from) + { + return from is PlayerMobile pm && pm.Quest is UzeraanTurmoilQuest; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilTeleporter.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilTeleporter.cs index 3b7902d30..c915c8c9b 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilTeleporter.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Items/UzeraanTurmoilTeleporter.cs @@ -2,70 +2,72 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class UzeraanTurmoilTeleporter : DynamicTeleporter - { - [Constructible] - public UzeraanTurmoilTeleporter() - { - } + public class UzeraanTurmoilTeleporter : DynamicTeleporter + { + [Constructible] + public UzeraanTurmoilTeleporter() + { + } - public override bool GetDestination( PlayerMobile player, ref Point3D loc, ref Map map ) - { - QuestSystem qs = player.Quest; + public UzeraanTurmoilTeleporter(Serial serial) : base(serial) + { + } - if ( qs is UzeraanTurmoilQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FindSchmendrickObjective ) ) - || qs.IsObjectiveInProgress( typeof( FindApprenticeObjective ) ) - || UzeraanTurmoilQuest.HasLostScrollOfPower( player ) ) - { - loc = new Point3D( 5222, 1858, 0 ); - map = Map.Trammel; - return true; - } + public override bool GetDestination(PlayerMobile player, ref Point3D loc, ref Map map) + { + QuestSystem qs = player.Quest; - if ( qs.IsObjectiveInProgress( typeof( FindDryadObjective ) ) - || UzeraanTurmoilQuest.HasLostFertileDirt( player ) ) - { - loc = new Point3D( 3557, 2690, 2 ); - map = Map.Trammel; - return true; - } - if ( player.Profession != 5 // paladin - && ( qs.IsObjectiveInProgress( typeof( GetDaemonBoneObjective ) ) - || UzeraanTurmoilQuest.HasLostDaemonBone( player ) ) ) - { - loc = new Point3D( 3422, 2653, 48 ); - map = Map.Trammel; - return true; - } - if ( qs.IsObjectiveInProgress( typeof( CashBankCheckObjective ) ) ) - { - loc = new Point3D( 3624, 2610, 0 ); - map = Map.Trammel; - return true; - } - } + if (qs is UzeraanTurmoilQuest) + { + if (qs.IsObjectiveInProgress(typeof(FindSchmendrickObjective)) + || qs.IsObjectiveInProgress(typeof(FindApprenticeObjective)) + || UzeraanTurmoilQuest.HasLostScrollOfPower(player)) + { + loc = new Point3D(5222, 1858, 0); + map = Map.Trammel; + return true; + } - return false; - } + if (qs.IsObjectiveInProgress(typeof(FindDryadObjective)) + || UzeraanTurmoilQuest.HasLostFertileDirt(player)) + { + loc = new Point3D(3557, 2690, 2); + map = Map.Trammel; + return true; + } - public UzeraanTurmoilTeleporter( Serial serial ) : base( serial ) - { - } + if (player.Profession != 5 // paladin + && (qs.IsObjectiveInProgress(typeof(GetDaemonBoneObjective)) + || UzeraanTurmoilQuest.HasLostDaemonBone(player))) + { + loc = new Point3D(3422, 2653, 48); + map = Map.Trammel; + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (qs.IsObjectiveInProgress(typeof(CashBankCheckObjective))) + { + loc = new Point3D(3624, 2610, 0); + map = Map.Trammel; + return true; + } + } - writer.Write( (int) 0 ); // version - } + return false; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Dryad.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Dryad.cs index b6223f1b5..3970a7e46 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Dryad.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Dryad.cs @@ -1,188 +1,185 @@ using System.Collections.Generic; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class Dryad : BaseQuester - { - public override bool IsActiveVendor => true; - public override bool DisallowAllMoves => false; - public override bool ClickTitle => true; - public override bool CanTeach => true; - public override string DefaultName => "Anwin Brenna"; + public class Dryad : BaseQuester + { + [Constructible] + public Dryad() : base("the Dryad") + { + SetSkill(SkillName.Peacemaking, 80.0, 100.0); + SetSkill(SkillName.Cooking, 80.0, 100.0); + SetSkill(SkillName.Provocation, 80.0, 100.0); + SetSkill(SkillName.Musicianship, 80.0, 100.0); + SetSkill(SkillName.Poisoning, 80.0, 100.0); + SetSkill(SkillName.Archery, 80.0, 100.0); + SetSkill(SkillName.Tailoring, 80.0, 100.0); + } - [Constructible] - public Dryad() : base( "the Dryad" ) - { - SetSkill( SkillName.Peacemaking, 80.0, 100.0 ); - SetSkill( SkillName.Cooking, 80.0, 100.0 ); - SetSkill( SkillName.Provocation, 80.0, 100.0 ); - SetSkill( SkillName.Musicianship, 80.0, 100.0 ); - SetSkill( SkillName.Poisoning, 80.0, 100.0 ); - SetSkill( SkillName.Archery, 80.0, 100.0 ); - SetSkill( SkillName.Tailoring, 80.0, 100.0 ); - } + public Dryad(Serial serial) : base(serial) + { + } - public Dryad( Serial serial ) : base( serial ) - { - } + public override bool IsActiveVendor => true; + public override bool DisallowAllMoves => false; + public override bool ClickTitle => true; + public override bool CanTeach => true; + public override string DefaultName => "Anwin Brenna"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x85A7; + Hue = 0x85A7; - Female = true; - Body = 0x191; - } + Female = true; + Body = 0x191; + } - public override void InitOutfit() - { - AddItem( new Kilt( 0x301 ) ); - AddItem( new FancyShirt( 0x300 ) ); + public override void InitOutfit() + { + AddItem(new Kilt(0x301)); + AddItem(new FancyShirt(0x300)); - HairItemID = 0x203D; // Pony Tail - HairHue = 0x22; + HairItemID = 0x203D; // Pony Tail + HairHue = 0x22; - Bow bow = new Bow(); - bow.Movable = false; - AddItem( bow ); - } + Bow bow = new Bow(); + bow.Movable = false; + AddItem(bow); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBDryad() ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBDryad()); + } - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 4; - } + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 4; + } - public override bool CanTalkTo( PlayerMobile to ) - { - return ( to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective( typeof( FindDryadObjective ) ) != null ); - } + public override bool CanTalkTo(PlayerMobile to) + { + return to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective(typeof(FindDryadObjective)) != null; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( qs is UzeraanTurmoilQuest ) - { - if ( UzeraanTurmoilQuest.HasLostFertileDirt( player ) ) - { - FocusTo( player ); - qs.AddConversation( new LostFertileDirtConversation( false ) ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( FindDryadObjective ) ); + if (qs is UzeraanTurmoilQuest) + { + if (UzeraanTurmoilQuest.HasLostFertileDirt(player)) + { + FocusTo(player); + qs.AddConversation(new LostFertileDirtConversation(false)); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(FindDryadObjective)); - if ( obj != null && !obj.Completed ) - { - FocusTo( player ); + if (obj != null && !obj.Completed) + { + FocusTo(player); - Item fertileDirt = new QuestFertileDirt(); + Item fertileDirt = new QuestFertileDirt(); - if ( !player.PlaceInBackpack( fertileDirt ) ) - { - fertileDirt.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - else - { - obj.Complete(); - } - } - else if ( contextMenu ) - { - FocusTo( player ); - SayTo( player, 1049357 ); // I have nothing more for you at this time. - } - } - } - } + if (!player.PlaceInBackpack(fertileDirt)) + { + fertileDirt.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + else + { + obj.Complete(); + } + } + else if (contextMenu) + { + FocusTo(player); + SayTo(player, 1049357); // I have nothing more for you at this time. + } + } + } + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - if ( player.Quest is UzeraanTurmoilQuest qs && dropped is Apple && UzeraanTurmoilQuest.HasLostFertileDirt( from ) ) - { - FocusTo( from ); + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + if (player.Quest is UzeraanTurmoilQuest qs && dropped is Apple && + UzeraanTurmoilQuest.HasLostFertileDirt(from)) + { + FocusTo(from); - Item fertileDirt = new QuestFertileDirt(); + Item fertileDirt = new QuestFertileDirt(); - if ( !player.PlaceInBackpack( fertileDirt ) ) - { - fertileDirt.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - return false; - } + if (!player.PlaceInBackpack(fertileDirt)) + { + fertileDirt.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + return false; + } - dropped.Consume(); - qs.AddConversation( new DryadAppleConversation() ); - return dropped.Deleted; - } - } + dropped.Consume(); + qs.AddConversation(new DryadAppleConversation()); + return dropped.Deleted; + } - return base.OnDragDrop( from, dropped ); - } + return base.OnDragDrop(from, dropped); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SBDryad : SBInfo - { - public SBDryad() - { - } + public class SBDryad : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bandage), 5, 20, 0xE21, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 20, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bandage ), 5, 20, 0xE21, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 20, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bandage ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Bloodmoss ), 3 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( SpidersSilk ), 2 ); - Add( typeof( MandrakeRoot ), 2 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bandage), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Bloodmoss), 3); + Add(typeof(Nightshade), 2); + Add(typeof(SpidersSilk), 2); + Add(typeof(MandrakeRoot), 2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MansionGuard.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MansionGuard.cs index 4e3dbdd61..e41f3fadc 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MansionGuard.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MansionGuard.cs @@ -1,77 +1,77 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class MansionGuard : BaseQuester - { - [Constructible] - public MansionGuard() : base( "the Mansion Guard" ) - { - } + public class MansionGuard : BaseQuester + { + [Constructible] + public MansionGuard() : base("the Mansion Guard") + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public MansionGuard(Serial serial) : base(serial) + { + } - Hue = Utility.RandomSkinHue(); + public override void InitBody() + { + InitStats(100, 100, 25); - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + Hue = Utility.RandomSkinHue(); - public override void InitOutfit() - { - AddItem( new PlateChest() ); - AddItem( new PlateArms() ); - AddItem( new PlateGloves() ); - AddItem( new PlateLegs() ); + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); + } - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); + public override void InitOutfit() + { + AddItem(new PlateChest()); + AddItem(new PlateArms()); + AddItem(new PlateGloves()); + AddItem(new PlateLegs()); - Bardiche weapon = new Bardiche(); - weapon.Movable = false; - AddItem( weapon ); - } + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 3; - } + Bardiche weapon = new Bardiche(); + weapon.Movable = false; + AddItem(weapon); + } - public override bool CanTalkTo( PlayerMobile to ) - { - return ( to.Quest == null && QuestSystem.CanOfferQuest( to, typeof( UzeraanTurmoilQuest ) ) ); - } + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 3; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - if ( player.Quest == null && QuestSystem.CanOfferQuest( player, typeof( UzeraanTurmoilQuest ) ) ) - { - Direction = GetDirectionTo( player ); + public override bool CanTalkTo(PlayerMobile to) + { + return to.Quest == null && QuestSystem.CanOfferQuest(to, typeof(UzeraanTurmoilQuest)); + } - new UzeraanTurmoilQuest( player ).SendOffer(); - } - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + if (player.Quest == null && QuestSystem.CanOfferQuest(player, typeof(UzeraanTurmoilQuest))) + { + Direction = GetDirectionTo(player); - public MansionGuard( Serial serial ) : base( serial ) - { - } + new UzeraanTurmoilQuest(player).SendOffer(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaCanoneer.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaCanoneer.cs index f0bd0a865..a0dab7480 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaCanoneer.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaCanoneer.cs @@ -3,100 +3,100 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class MilitiaCanoneer : BaseQuester - { - [CommandProperty( AccessLevel.GameMaster )] - public bool Active { get; set; } + public class MilitiaCanoneer : BaseQuester + { + [Constructible] + public MilitiaCanoneer() : base("the Militia Canoneer") + { + Active = true; + } - [Constructible] - public MilitiaCanoneer() : base( "the Militia Canoneer" ) - { - Active = true; - } + public MilitiaCanoneer(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 125, 25 ); + [CommandProperty(AccessLevel.GameMaster)] + public bool Active{ get; set; } - Hue = Utility.RandomSkinHue(); + public override void InitBody() + { + InitStats(100, 125, 25); - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + Hue = Utility.RandomSkinHue(); - public override void InitOutfit() - { - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); + } - AddItem( new PlateChest() ); - AddItem( new PlateArms() ); - AddItem( new PlateGloves() ); - AddItem( new PlateLegs() ); + public override void InitOutfit() + { + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); - Torch torch = new Torch(); - torch.Movable = false; - AddItem( torch ); - torch.Ignite(); - } + AddItem(new PlateChest()); + AddItem(new PlateArms()); + AddItem(new PlateGloves()); + AddItem(new PlateLegs()); - public override bool CanTalkTo( PlayerMobile to ) - { - return false; - } + Torch torch = new Torch(); + torch.Movable = false; + AddItem(torch); + torch.Ignite(); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } + public override bool CanTalkTo(PlayerMobile to) + { + return false; + } - public override bool IsEnemy( Mobile m ) - { - if ( m.Player || m is BaseVendor ) - return false; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } - if ( m is BaseCreature bc ) - { - Mobile master = bc.GetMaster(); - if ( master != null ) - return IsEnemy( master ); - } + public override bool IsEnemy(Mobile m) + { + if (m.Player || m is BaseVendor) + return false; - return m.Karma < 0; - } + if (m is BaseCreature bc) + { + Mobile master = bc.GetMaster(); + if (master != null) + return IsEnemy(master); + } - public bool WillFire( Cannon cannon, Mobile target ) - { - if ( Active && IsEnemy( target ) ) - { - Direction = GetDirectionTo( target ); - Say( Utility.RandomList( 500651, 1049098, 1049320, 1043149 ) ); - return true; - } + return m.Karma < 0; + } - return false; - } + public bool WillFire(Cannon cannon, Mobile target) + { + if (Active && IsEnemy(target)) + { + Direction = GetDirectionTo(target); + Say(Utility.RandomList(500651, 1049098, 1049320, 1043149)); + return true; + } - public MilitiaCanoneer( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (bool) Active ); - } + writer.Write(Active); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Active = reader.ReadBool(); - } - } -} + Active = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaFighter.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaFighter.cs index 29c616dd2..5bcabf4a4 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaFighter.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/MilitiaFighter.cs @@ -1,146 +1,162 @@ using System.Collections.Generic; using Server.Items; +using Server.Misc; using Server.Mobiles; using Server.Network; namespace Server.Engines.Quests.Haven { - public class MilitiaFighter : BaseCreature - { - [Constructible] - public MilitiaFighter() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - InitStats( 40, 30, 5 ); - Title = "the Militia Fighter"; + public class MilitiaFighter : BaseCreature + { + [Constructible] + public MilitiaFighter() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + InitStats(40, 30, 5); + Title = "the Militia Fighter"; - SpeechHue = Utility.RandomDyedHue(); + SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); + Hue = Utility.RandomSkinHue(); - Female = false; - Body = 0x190; - Name = NameList.RandomName( "male" ); + Female = false; + Body = 0x190; + Name = NameList.RandomName("male"); - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); - AddItem( new ThighBoots( 0x1BB ) ); - AddItem( new LeatherChest() ); - AddItem( new LeatherArms() ); - AddItem( new LeatherLegs() ); - AddItem( new LeatherCap() ); - AddItem( new LeatherGloves() ); - AddItem( new LeatherGorget() ); + AddItem(new ThighBoots(0x1BB)); + AddItem(new LeatherChest()); + AddItem(new LeatherArms()); + AddItem(new LeatherLegs()); + AddItem(new LeatherCap()); + AddItem(new LeatherGloves()); + AddItem(new LeatherGorget()); - Item weapon; - switch ( Utility.Random( 6 ) ) - { - case 0: weapon = new Broadsword(); break; - case 1: weapon = new Cutlass(); break; - case 2: weapon = new Katana(); break; - case 3: weapon = new Longsword(); break; - case 4: weapon = new Scimitar(); break; - default: weapon = new VikingSword(); break; - } - weapon.Movable = false; - AddItem( weapon ); + Item weapon; + switch (Utility.Random(6)) + { + case 0: + weapon = new Broadsword(); + break; + case 1: + weapon = new Cutlass(); + break; + case 2: + weapon = new Katana(); + break; + case 3: + weapon = new Longsword(); + break; + case 4: + weapon = new Scimitar(); + break; + default: + weapon = new VikingSword(); + break; + } - Item shield = new BronzeShield(); - shield.Movable = false; - AddItem( shield ); + weapon.Movable = false; + AddItem(weapon); - SetSkill( SkillName.Swords, 20.0 ); - } + Item shield = new BronzeShield(); + shield.Movable = false; + AddItem(shield); - public override bool ClickTitle => false; + SetSkill(SkillName.Swords, 20.0); + } - public override bool IsEnemy( Mobile m ) - { - if ( m.Player || m is BaseVendor ) - return false; + public MilitiaFighter(Serial serial) : base(serial) + { + } - if ( m is BaseCreature bc ) - { - Mobile master = bc.GetMaster(); - if ( master != null ) - return IsEnemy( master ); - } + public override bool ClickTitle => false; - return m.Karma < 0; - } + public override bool IsEnemy(Mobile m) + { + if (m.Player || m is BaseVendor) + return false; - public MilitiaFighter( Serial serial ) : base( serial ) - { - } + if (m is BaseCreature bc) + { + Mobile master = bc.GetMaster(); + if (master != null) + return IsEnemy(master); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return m.Karma < 0; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public class MilitiaFighterCorpse : Corpse - { - public MilitiaFighterCorpse( Mobile owner, HairInfo hair, FacialHairInfo facialhair, List equipItems ) : base( owner, hair, facialhair, equipItems ) - { - } + int version = reader.ReadInt(); + } + } - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( ItemID == 0x2006 ) // Corpse form - { - list.Add( "a human corpse" ); - list.Add( 1049318, Name ); // the remains of ~1_NAME~ the militia fighter - } - else - { - list.Add( 1049319 ); // the remains of a militia fighter - } - } + public class MilitiaFighterCorpse : Corpse + { + public MilitiaFighterCorpse(Mobile owner, HairInfo hair, FacialHairInfo facialhair, List equipItems) : base( + owner, hair, facialhair, equipItems) + { + } - public override void OnSingleClick( Mobile from ) - { - int hue = Notoriety.GetHue( Misc.NotorietyHandlers.CorpseNotoriety( from, this ) ); + public MilitiaFighterCorpse(Serial serial) : base(serial) + { + } - if ( ItemID == 0x2006 ) // Corpse form - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, 1049318, "", Name ) ); // the remains of ~1_NAME~ the militia fighter - else - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, 1049319, "", "" ) ); // the remains of a militia fighter - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (ItemID == 0x2006) // Corpse form + { + list.Add("a human corpse"); + list.Add(1049318, Name); // the remains of ~1_NAME~ the militia fighter + } + else + { + list.Add(1049319); // the remains of a militia fighter + } + } - public override void Open( Mobile from, bool checkSelfLoot ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - from.SendLocalizedMessage( 1049661, "", 0x22 ); // Thinking about his sacrifice, you can't bring yourself to loot the body of this militia fighter. - } - } + public override void OnSingleClick(Mobile from) + { + int hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this)); - public MilitiaFighterCorpse( Serial serial ) : base( serial ) - { - } + if (ItemID == 0x2006) // Corpse form + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049318, "", + Name)); // the remains of ~1_NAME~ the militia fighter + else + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1049319, "", + "")); // the remains of a militia fighter + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Open(Mobile from, bool checkSelfLoot) + { + if (from.InRange(GetWorldLocation(), 2)) + from.SendLocalizedMessage(1049661, "", + 0x22); // Thinking about his sacrifice, you can't bring yourself to loot the body of this militia fighter. + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Schmendrick.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Schmendrick.cs index 227d1266e..31430e533 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Schmendrick.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Schmendrick.cs @@ -1,150 +1,152 @@ -using Server.Mobiles; -using Server.Items; using Server.Gumps; +using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class Schmendrick : BaseQuester - { - public override string DefaultName => "Schmendrick"; + public class Schmendrick : BaseQuester + { + [Constructible] + public Schmendrick() : base("the High Mage") + { + } - [Constructible] - public Schmendrick() : base( "the High Mage" ) - { - } + public Schmendrick(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Schmendrick"; - Hue = 0x83F3; + public override void InitBody() + { + InitStats(100, 100, 25); - Female = false; - Body = 0x190; - } + Hue = 0x83F3; - public override void InitOutfit() - { - AddItem( new Robe( 0x4DD ) ); - AddItem( new WizardsHat( 0x482 ) ); - AddItem( new Shoes( 0x482 ) ); + Female = false; + Body = 0x190; + } - HairItemID = 0x203C; - HairHue = 0x455; + public override void InitOutfit() + { + AddItem(new Robe(0x4DD)); + AddItem(new WizardsHat(0x482)); + AddItem(new Shoes(0x482)); - FacialHairItemID = 0x203E; - FacialHairHue = 0x455; + HairItemID = 0x203C; + HairHue = 0x455; - GlacialStaff staff = new GlacialStaff(); - staff.Movable = false; - AddItem( staff ); + FacialHairItemID = 0x203E; + FacialHairHue = 0x455; - Backpack pack = new Backpack(); - pack.Movable = false; - AddItem( pack ); - } + GlacialStaff staff = new GlacialStaff(); + staff.Movable = false; + AddItem(staff); - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 7; - } + Backpack pack = new Backpack(); + pack.Movable = false; + AddItem(pack); + } - public override bool CanTalkTo( PlayerMobile to ) - { - return ( to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective( typeof( FindSchmendrickObjective ) ) != null ); - } + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 7; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override bool CanTalkTo(PlayerMobile to) + { + return to.Quest is UzeraanTurmoilQuest qs && qs.FindObjective(typeof(FindSchmendrickObjective)) != null; + } - if ( qs is UzeraanTurmoilQuest ) - { - if ( UzeraanTurmoilQuest.HasLostScrollOfPower( player ) ) - { - FocusTo( player ); - qs.AddConversation( new LostScrollOfPowerConversation( false ) ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( FindSchmendrickObjective ) ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( obj != null && !obj.Completed ) - { - FocusTo( player ); - obj.Complete(); - } - else if ( contextMenu ) - { - FocusTo( player ); - SayTo( player, 1049357 ); // I have nothing more for you at this time. - } - } - } - } + if (qs is UzeraanTurmoilQuest) + { + if (UzeraanTurmoilQuest.HasLostScrollOfPower(player)) + { + FocusTo(player); + qs.AddConversation(new LostScrollOfPowerConversation(false)); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(FindSchmendrickObjective)); - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is BlankScroll && UzeraanTurmoilQuest.HasLostScrollOfPower( from ) ) - { - FocusTo( from ); + if (obj != null && !obj.Completed) + { + FocusTo(player); + obj.Complete(); + } + else if (contextMenu) + { + FocusTo(player); + SayTo(player, 1049357); // I have nothing more for you at this time. + } + } + } + } - Item scroll = new SchmendrickScrollOfPower(); + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is BlankScroll && UzeraanTurmoilQuest.HasLostScrollOfPower(from)) + { + FocusTo(from); - if ( !from.PlaceInBackpack( scroll ) ) - { - scroll.Delete(); - from.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - return false; - } + Item scroll = new SchmendrickScrollOfPower(); - dropped.Consume(); - from.SendLocalizedMessage( 1049346 ); // Schmendrick scribbles on the scroll for a few moments and hands you the finished product. - return dropped.Deleted; - } + if (!from.PlaceInBackpack(scroll)) + { + scroll.Delete(); + from.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + return false; + } - return base.OnDragDrop( from, dropped ); - } + dropped.Consume(); + from.SendLocalizedMessage( + 1049346); // Schmendrick scribbles on the scroll for a few moments and hands you the finished product. + return dropped.Deleted; + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + return base.OnDragDrop(from, dropped); + } - if ( m is PlayerMobile && !m.Frozen && !m.Alive && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && InLOS( m ) ) - { - if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else - { - Direction = GetDirectionTo( m ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m)) + { + if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + else + { + Direction = GetDirectionTo(m); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.Healer ) ); - } - } - } + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - public Schmendrick( Serial serial ) : base( serial ) - { - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer)); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Uzeraan.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Uzeraan.cs index dca3c4bbc..a5f45ac87 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Uzeraan.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Mobiles/Uzeraan.cs @@ -1,420 +1,432 @@ -using Server.Mobiles; -using Server.Items; using Server.Gumps; +using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class Uzeraan : BaseQuester - { - public override string DefaultName => "Uzeraan"; + public class Uzeraan : BaseQuester + { + [Constructible] + public Uzeraan() : base("the Conjurer") + { + } - [Constructible] - public Uzeraan() : base( "the Conjurer" ) - { - } + public Uzeraan(Serial serial) : base(serial) + { + } - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override string DefaultName => "Uzeraan"; - Hue = 0x83F3; + public override void InitBody() + { + InitStats(100, 100, 25); - Female = false; - Body = 0x190; - } + Hue = 0x83F3; - public override void InitOutfit() - { - AddItem( new Robe( 0x4DD ) ); - AddItem( new WizardsHat( 0x8A5 ) ); - AddItem( new Shoes( 0x8A5 ) ); + Female = false; + Body = 0x190; + } - HairItemID = 0x203C; - HairHue = 0x455; + public override void InitOutfit() + { + AddItem(new Robe(0x4DD)); + AddItem(new WizardsHat(0x8A5)); + AddItem(new Shoes(0x8A5)); - FacialHairItemID = 0x203E; - FacialHairHue = 0x455; + HairItemID = 0x203C; + HairHue = 0x455; - BlackStaff staff = new BlackStaff(); - staff.Movable = false; - AddItem( staff ); - } + FacialHairItemID = 0x203E; + FacialHairHue = 0x455; - public override int GetAutoTalkRange( PlayerMobile pm ) - { - return 3; - } + BlackStaff staff = new BlackStaff(); + staff.Movable = false; + AddItem(staff); + } - public override bool CanTalkTo( PlayerMobile to ) - { - return to.Quest is UzeraanTurmoilQuest; - } + public override int GetAutoTalkRange(PlayerMobile pm) + { + return 3; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - QuestSystem qs = player.Quest; + public override bool CanTalkTo(PlayerMobile to) + { + return to.Quest is UzeraanTurmoilQuest; + } - if ( qs is UzeraanTurmoilQuest ) - { - if ( UzeraanTurmoilQuest.HasLostScrollOfPower( player ) ) - { - qs.AddConversation( new LostScrollOfPowerConversation( true ) ); - } - else if ( UzeraanTurmoilQuest.HasLostFertileDirt( player ) ) - { - qs.AddConversation( new LostFertileDirtConversation( true ) ); - } - else if ( UzeraanTurmoilQuest.HasLostDaemonBlood( player ) ) - { - qs.AddConversation( new LostDaemonBloodConversation() ); - } - else if ( UzeraanTurmoilQuest.HasLostDaemonBone( player ) ) - { - qs.AddConversation( new LostDaemonBoneConversation() ); - } - else - { - if ( player.Profession == 2 ) // magician - { - Container backpack = player.Backpack; + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + QuestSystem qs = player.Quest; - if ( backpack == null - || backpack.GetAmount( typeof( BlackPearl ) ) < 30 - || backpack.GetAmount( typeof( Bloodmoss ) ) < 30 - || backpack.GetAmount( typeof( Garlic ) ) < 30 - || backpack.GetAmount( typeof( Ginseng ) ) < 30 - || backpack.GetAmount( typeof( MandrakeRoot ) ) < 30 - || backpack.GetAmount( typeof( Nightshade ) ) < 30 - || backpack.GetAmount( typeof( SulfurousAsh ) ) < 30 - || backpack.GetAmount( typeof( SpidersSilk ) ) < 30 ) - { - qs.AddConversation( new FewReagentsConversation() ); - } - } + if (qs is UzeraanTurmoilQuest) + { + if (UzeraanTurmoilQuest.HasLostScrollOfPower(player)) + { + qs.AddConversation(new LostScrollOfPowerConversation(true)); + } + else if (UzeraanTurmoilQuest.HasLostFertileDirt(player)) + { + qs.AddConversation(new LostFertileDirtConversation(true)); + } + else if (UzeraanTurmoilQuest.HasLostDaemonBlood(player)) + { + qs.AddConversation(new LostDaemonBloodConversation()); + } + else if (UzeraanTurmoilQuest.HasLostDaemonBone(player)) + { + qs.AddConversation(new LostDaemonBoneConversation()); + } + else + { + if (player.Profession == 2) // magician + { + Container backpack = player.Backpack; - QuestObjective obj = qs.FindObjective( typeof( FindUzeraanBeginObjective ) ); + if (backpack == null + || backpack.GetAmount(typeof(BlackPearl)) < 30 + || backpack.GetAmount(typeof(Bloodmoss)) < 30 + || backpack.GetAmount(typeof(Garlic)) < 30 + || backpack.GetAmount(typeof(Ginseng)) < 30 + || backpack.GetAmount(typeof(MandrakeRoot)) < 30 + || backpack.GetAmount(typeof(Nightshade)) < 30 + || backpack.GetAmount(typeof(SulfurousAsh)) < 30 + || backpack.GetAmount(typeof(SpidersSilk)) < 30) + qs.AddConversation(new FewReagentsConversation()); + } - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else - { - obj = qs.FindObjective( typeof( FindUzeraanFirstTaskObjective ) ); + QuestObjective obj = qs.FindObjective(typeof(FindUzeraanBeginObjective)); - if ( obj != null && !obj.Completed ) - { - obj.Complete(); - } - else - { - obj = qs.FindObjective( typeof( FindUzeraanAboutReportObjective ) ); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else + { + obj = qs.FindObjective(typeof(FindUzeraanFirstTaskObjective)); - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + if (obj != null && !obj.Completed) + { + obj.Complete(); + } + else + { + obj = qs.FindObjective(typeof(FindUzeraanAboutReportObjective)); - if ( player.Profession == 2 ) // magician - { - cont.DropItem( new MarkScroll( 5 ) ); - cont.DropItem( new RecallScroll( 5 ) ); - for ( int i = 0; i < 5; i++ ) - { - cont.DropItem( new RecallRune() ); - } - } - else - { - cont.DropItem( new Gold( 300 ) ); - for ( int i = 0; i < 6; i++ ) - { - cont.DropItem( new NightSightPotion() ); - cont.DropItem( new LesserHealPotion() ); - } - } + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - if ( !player.PlaceInBackpack( cont ) ) - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - else - { - obj.Complete(); - } - } - else - { - obj = qs.FindObjective( typeof( ReturnScrollOfPowerObjective ) ); + if (player.Profession == 2) // magician + { + cont.DropItem(new MarkScroll(5)); + cont.DropItem(new RecallScroll(5)); + for (int i = 0; i < 5; i++) cont.DropItem(new RecallRune()); + } + else + { + cont.DropItem(new Gold(300)); + for (int i = 0; i < 6; i++) + { + cont.DropItem(new NightSightPotion()); + cont.DropItem(new LesserHealPotion()); + } + } - if ( obj != null && !obj.Completed ) - { - FocusTo( player ); - SayTo( player, 1049378 ); // Hand me the scroll, if you have it. - } - else - { - obj = qs.FindObjective( typeof( ReturnFertileDirtObjective ) ); + if (!player.PlaceInBackpack(cont)) + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + else + { + obj.Complete(); + } + } + else + { + obj = qs.FindObjective(typeof(ReturnScrollOfPowerObjective)); - if ( obj != null && !obj.Completed ) - { - FocusTo( player ); - SayTo( player, 1049381 ); // Hand me the Fertile Dirt, if you have it. - } - else - { - obj = qs.FindObjective( typeof( ReturnDaemonBloodObjective ) ); + if (obj != null && !obj.Completed) + { + FocusTo(player); + SayTo(player, 1049378); // Hand me the scroll, if you have it. + } + else + { + obj = qs.FindObjective(typeof(ReturnFertileDirtObjective)); - if ( obj != null && !obj.Completed ) - { - FocusTo( player ); - SayTo( player, 1049379 ); // Hand me the Vial of Blood, if you have it. - } - else - { - obj = qs.FindObjective( typeof( ReturnDaemonBoneObjective ) ); + if (obj != null && !obj.Completed) + { + FocusTo(player); + SayTo(player, 1049381); // Hand me the Fertile Dirt, if you have it. + } + else + { + obj = qs.FindObjective(typeof(ReturnDaemonBloodObjective)); - if ( obj != null && !obj.Completed ) - { - FocusTo( player ); - SayTo( player, 1049380 ); // Hand me the Daemon Bone, if you have it. - } - else - { - SayTo( player, 1049357 ); // I have nothing more for you at this time. - } - } - } - } - } - } - } - } - } - } + if (obj != null && !obj.Completed) + { + FocusTo(player); + SayTo(player, 1049379); // Hand me the Vial of Blood, if you have it. + } + else + { + obj = qs.FindObjective(typeof(ReturnDaemonBoneObjective)); - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + if (obj != null && !obj.Completed) + { + FocusTo(player); + SayTo(player, 1049380); // Hand me the Daemon Bone, if you have it. + } + else + { + SayTo(player, 1049357); // I have nothing more for you at this time. + } + } + } + } + } + } + } + } + } + } - if ( qs is UzeraanTurmoilQuest ) - { - if ( dropped is UzeraanTurmoilHorn horn ) - { - if ( player.Young ) - { - if ( horn.Charges < 10 ) - { - SayTo( from, 1049384 ); // I have recharged the item for you. - horn.Charges = 10; - } - else - { - SayTo( from, 1049385 ); // That doesn't need recharging yet. - } - } - else - { - player.SendLocalizedMessage(1114333); //You must be young to have this item recharged. - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - return false; - } + if (qs is UzeraanTurmoilQuest) + { + if (dropped is UzeraanTurmoilHorn horn) + { + if (player.Young) + { + if (horn.Charges < 10) + { + SayTo(from, 1049384); // I have recharged the item for you. + horn.Charges = 10; + } + else + { + SayTo(from, 1049385); // That doesn't need recharging yet. + } + } + else + { + player.SendLocalizedMessage(1114333); //You must be young to have this item recharged. + } - if ( dropped is SchmendrickScrollOfPower ) - { - QuestObjective obj = qs.FindObjective( typeof( ReturnScrollOfPowerObjective ) ); + return false; + } - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + if (dropped is SchmendrickScrollOfPower) + { + QuestObjective obj = qs.FindObjective(typeof(ReturnScrollOfPowerObjective)); - cont.DropItem( new TreasureMap( player.Young ? 0 : 1, Map.Trammel ) ); - cont.DropItem( new Shovel() ); - cont.DropItem( new UzeraanTurmoilHorn() ); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - if ( !player.PlaceInBackpack( cont ) ) - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - return false; - } + cont.DropItem(new TreasureMap(player.Young ? 0 : 1, Map.Trammel)); + cont.DropItem(new Shovel()); + cont.DropItem(new UzeraanTurmoilHorn()); - dropped.Delete(); - obj.Complete(); - return true; - } - } - else if ( dropped is QuestFertileDirt ) - { - QuestObjective obj = qs.FindObjective( typeof( ReturnFertileDirtObjective ) ); + if (!player.PlaceInBackpack(cont)) + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + return false; + } - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + dropped.Delete(); + obj.Complete(); + return true; + } + } + else if (dropped is QuestFertileDirt) + { + QuestObjective obj = qs.FindObjective(typeof(ReturnFertileDirtObjective)); - if ( player.Profession == 2 ) // magician - { - cont.DropItem( new BlackPearl( 20 ) ); - cont.DropItem( new Bloodmoss( 20 ) ); - cont.DropItem( new Garlic( 20 ) ); - cont.DropItem( new Ginseng( 20 ) ); - cont.DropItem( new MandrakeRoot( 20 ) ); - cont.DropItem( new Nightshade( 20 ) ); - cont.DropItem( new SulfurousAsh( 20 ) ); - cont.DropItem( new SpidersSilk( 20 ) ); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - for ( int i = 0; i < 3; i++ ) - cont.DropItem( Loot.RandomScroll( 0, 23, SpellbookType.Regular ) ); - } - else - { - cont.DropItem( new Gold( 300 ) ); - cont.DropItem( new Bandage( 25 ) ); + if (player.Profession == 2) // magician + { + cont.DropItem(new BlackPearl(20)); + cont.DropItem(new Bloodmoss(20)); + cont.DropItem(new Garlic(20)); + cont.DropItem(new Ginseng(20)); + cont.DropItem(new MandrakeRoot(20)); + cont.DropItem(new Nightshade(20)); + cont.DropItem(new SulfurousAsh(20)); + cont.DropItem(new SpidersSilk(20)); - for ( int i = 0; i < 5; i++ ) - cont.DropItem( new LesserHealPotion() ); - } + for (int i = 0; i < 3; i++) + cont.DropItem(Loot.RandomScroll(0, 23, SpellbookType.Regular)); + } + else + { + cont.DropItem(new Gold(300)); + cont.DropItem(new Bandage(25)); - if ( !player.PlaceInBackpack( cont ) ) - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - return false; - } + for (int i = 0; i < 5; i++) + cont.DropItem(new LesserHealPotion()); + } - dropped.Delete(); - obj.Complete(); - return true; - } - } - else if ( dropped is QuestDaemonBlood ) - { - QuestObjective obj = qs.FindObjective( typeof( ReturnDaemonBloodObjective ) ); + if (!player.PlaceInBackpack(cont)) + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + return false; + } - if ( obj != null && !obj.Completed ) - { - Item reward; + dropped.Delete(); + obj.Complete(); + return true; + } + } + else if (dropped is QuestDaemonBlood) + { + QuestObjective obj = qs.FindObjective(typeof(ReturnDaemonBloodObjective)); - if ( player.Profession == 2 ) // magician - { - Container cont = GetNewContainer(); + if (obj != null && !obj.Completed) + { + Item reward; - cont.DropItem( new ExplosionScroll( 4 ) ); - cont.DropItem( new MagicWizardsHat() ); + if (player.Profession == 2) // magician + { + Container cont = GetNewContainer(); - reward = cont; - } - else - { - BaseWeapon weapon; - switch ( Utility.Random( 6 ) ) - { - case 0: weapon = new Broadsword(); break; - case 1: weapon = new Cutlass(); break; - case 2: weapon = new Katana(); break; - case 3: weapon = new Longsword(); break; - case 4: weapon = new Scimitar(); break; - default: weapon = new VikingSword(); break; - } + cont.DropItem(new ExplosionScroll(4)); + cont.DropItem(new MagicWizardsHat()); - if ( Core.AOS ) - { - BaseRunicTool.ApplyAttributesTo( weapon, 3, 20, 40 ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled( 2, 4 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled( 2, 4 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled( 2, 4 ); - } + reward = cont; + } + else + { + BaseWeapon weapon; + switch (Utility.Random(6)) + { + case 0: + weapon = new Broadsword(); + break; + case 1: + weapon = new Cutlass(); + break; + case 2: + weapon = new Katana(); + break; + case 3: + weapon = new Longsword(); + break; + case 4: + weapon = new Scimitar(); + break; + default: + weapon = new VikingSword(); + break; + } - weapon.Slayer = SlayerName.Silver; + if (Core.AOS) + { + BaseRunicTool.ApplyAttributesTo(weapon, 3, 20, 40); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(2, 4); + weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(2, 4); + weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(2, 4); + } - reward = weapon; - } + weapon.Slayer = SlayerName.Silver; - if ( !player.PlaceInBackpack( reward ) ) - { - reward.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - return false; - } + reward = weapon; + } - dropped.Delete(); - obj.Complete(); - return true; - } - } - else if ( dropped is QuestDaemonBone ) - { - QuestObjective obj = qs.FindObjective( typeof( ReturnDaemonBoneObjective ) ); + if (!player.PlaceInBackpack(reward)) + { + reward.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + return false; + } - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); - cont.DropItem( new BankCheck( 2000 ) ); - cont.DropItem( new EnchantedSextant() ); + dropped.Delete(); + obj.Complete(); + return true; + } + } + else if (dropped is QuestDaemonBone) + { + QuestObjective obj = qs.FindObjective(typeof(ReturnDaemonBoneObjective)); - if ( !player.PlaceInBackpack( cont ) ) - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - return false; - } + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); + cont.DropItem(new BankCheck(2000)); + cont.DropItem(new EnchantedSextant()); - dropped.Delete(); - obj.Complete(); - return true; - } - } - } - } + if (!player.PlaceInBackpack(cont)) + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + return false; + } - return base.OnDragDrop( from, dropped ); - } + dropped.Delete(); + obj.Complete(); + return true; + } + } + } + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + return base.OnDragDrop(from, dropped); + } - if ( m is PlayerMobile && !m.Frozen && !m.Alive && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && InLOS( m ) ) - { - if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else - { - Direction = GetDirectionTo( m ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + if (m is PlayerMobile && !m.Frozen && !m.Alive && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m)) + { + if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + else + { + Direction = GetDirectionTo(m); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.Healer ) ); - } - } - } + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - public Uzeraan( Serial serial ) : base( serial ) - { - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer)); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/Objectives.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/Objectives.cs index 97d30be0e..a73c46285 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/Objectives.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/Objectives.cs @@ -1,495 +1,435 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; using Server.Network; namespace Server.Engines.Quests.Haven { - public class FindUzeraanBeginObjective : QuestObjective - { - public override object Message => 1046039; - - public FindUzeraanBeginObjective() - { - } - - public override void OnComplete() - { - if ( System.From.Profession == 5 ) // paladin - System.AddConversation( new UzeraanTitheConversation() ); - else - System.AddConversation( new UzeraanFirstTaskConversation() ); - } - } - - public class TitheGoldObjective : QuestObjective - { - public override object Message => 1060386; - - private int m_OldTithingPoints; - - public TitheGoldObjective() - { - m_OldTithingPoints = -1; - } - - public override void CheckProgress() - { - PlayerMobile pm = System.From; - int curTithingPoints = pm.TithingPoints; - - if ( curTithingPoints >= 500 ) - Complete(); - else if ( curTithingPoints > m_OldTithingPoints && m_OldTithingPoints >= 0 ) - pm.SendLocalizedMessage( 1060240, "", 0x41 ); // You must have at least 500 tithing points before you can continue in your quest. - - m_OldTithingPoints = curTithingPoints; - } - - public override void OnComplete() - { - System.AddObjective( new FindUzeraanFirstTaskObjective() ); - } - } - - public class FindUzeraanFirstTaskObjective : QuestObjective - { - public override object Message => 1060387; - - public FindUzeraanFirstTaskObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new UzeraanFirstTaskConversation() ); - } - } - - public enum KillHordeMinionsStep - { - First, - LearnKarma, - Others - } - - public class KillHordeMinionsObjective : QuestObjective - { - public KillHordeMinionsStep Step { get; private set; } - - public override object Message - { - get - { - switch ( Step ) - { - case KillHordeMinionsStep.First: - /* Find the mountain pass beyond the house which lies at the - * end of the runic road.

- * - * Assist the city Militia by slaying Horde Minions - */ - return 1049089; - - case KillHordeMinionsStep.LearnKarma: - /* You have just gained some Karma - * for killing the horde minion. Learn - * how this affects your Paladin abilities. - */ - return 1060389; - - default: - // Continue driving back the Horde Minions, as Uzeraan instructed you to do. - return 1060507; - } - } - } - - public override int MaxProgress - { - get - { - if ( System.From.Profession == 5 ) // paladin - { - switch ( Step ) - { - case KillHordeMinionsStep.First: return 1; - case KillHordeMinionsStep.LearnKarma: return 2; - default: return 5; - } - } - - return 5; - } - } - - public override bool Completed - { - get - { - if ( Step == KillHordeMinionsStep.LearnKarma && HasBeenRead ) - return true; - return base.Completed; - } - } - - public KillHordeMinionsObjective() - { - } - - public KillHordeMinionsObjective( KillHordeMinionsStep step ) - { - Step = step; - } - - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - gump.AddHtmlObject( 70, 260, 270, 100, 1049090, BaseQuestGump.Blue, false, false ); // Horde Minions killed: - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } - - public override void OnRead() - { - CheckCompletionStatus(); - } - - public override bool IgnoreYoungProtection( Mobile from ) - { - // This restriction continues until the quest is ended - if ( from is HordeMinion && from.Map == Map.Trammel && from.X >= 3314 && from.X <= 3814 && from.Y >= 2345 && from.Y <= 3095 ) // Haven island - return true; - - return false; - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is HordeMinion && corpse.Map == Map.Trammel && corpse.X >= 3314 && corpse.X <= 3814 && corpse.Y >= 2345 && corpse.Y <= 3095 ) // Haven island - { - if ( CurProgress == 0 ) - System.From.Send( new DisplayHelpTopic( 29, false ) ); // HEALING - - CurProgress++; - } - } - - public override void OnComplete() - { - if ( System.From.Profession == 5 ) - { - switch ( Step ) - { - case KillHordeMinionsStep.First: - { - QuestObjective obj = new KillHordeMinionsObjective( KillHordeMinionsStep.LearnKarma ); - System.AddObjective( obj ); - obj.CurProgress = CurProgress; - break; - } - case KillHordeMinionsStep.LearnKarma: - { - QuestObjective obj = new KillHordeMinionsObjective( KillHordeMinionsStep.Others ); - System.AddObjective( obj ); - obj.CurProgress = CurProgress; - break; - } - default: - { - System.AddObjective( new FindUzeraanAboutReportObjective() ); - break; - } - } - } - else - { - System.AddObjective( new FindUzeraanAboutReportObjective() ); - } - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - Step = (KillHordeMinionsStep) reader.ReadEncodedInt(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) Step ); - } - } - - public class FindUzeraanAboutReportObjective : QuestObjective - { - public override object Message => 1049091; - - public FindUzeraanAboutReportObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new UzeraanReportConversation() ); - } - } - - public class FindSchmendrickObjective : QuestObjective - { - public override object Message => 1049120; - - public FindSchmendrickObjective() - { - } - - public override bool IgnoreYoungProtection( Mobile from ) - { - // This restriction begins when this objective is completed, and continues until the quest is ended - if ( Completed && from is RestlessSoul && from.Map == Map.Trammel && from.X >= 5199 && from.X <= 5271 && from.Y >= 1812 && from.Y <= 1865 ) // Schmendrick's cave - return true; - - return false; - } - - public override void OnComplete() - { - System.AddConversation( new SchmendrickConversation() ); - } - } - - public class FindApprenticeObjective : QuestObjective - { - public override object Message => 1049323; - - public FindApprenticeObjective() - { - } - - public override void OnComplete() - { - System.AddObjective( new ReturnScrollOfPowerObjective() ); - } - } - - public class ReturnScrollOfPowerObjective : QuestObjective - { - public override object Message => 1049324; - - public ReturnScrollOfPowerObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new UzeraanScrollOfPowerConversation() ); - } - } - - public class FindDryadObjective : QuestObjective - { - public override object Message => 1049358; - - public FindDryadObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new DryadConversation() ); - } - } - - public class ReturnFertileDirtObjective : QuestObjective - { - public override object Message => 1049327; - - public ReturnFertileDirtObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new UzeraanFertileDirtConversation() ); - } - } - - public class GetDaemonBloodObjective : QuestObjective - { - public override object Message => 1049361; - - private bool m_Ambushed; - - public GetDaemonBloodObjective() - { - } - - public override void CheckProgress() - { - PlayerMobile player = System.From; - - if ( !m_Ambushed && player.Map == Map.Trammel && player.InRange( new Point3D( 3456, 2558, 50 ), 30 ) ) - { - int x = player.X - 1; - int y = player.Y - 2; - int z = Map.Trammel.GetAverageZ( x, y ); - - if ( Map.Trammel.CanSpawnMobile( x, y, z ) ) - { - m_Ambushed = true; - - player.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1049330 ); // You have been ambushed! Fight for your honor!!! - - BaseCreature creature = new HordeMinion(); - creature.MoveToWorld( new Point3D( x, y, z ), Map.Trammel ); - creature.Combatant = player; - } - } - } - - public override void OnComplete() - { - System.AddObjective( new ReturnDaemonBloodObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_Ambushed = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_Ambushed ); - } - } - - public class ReturnDaemonBloodObjective : QuestObjective - { - public override object Message => 1049332; - - public ReturnDaemonBloodObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new UzeraanDaemonBloodConversation() ); - } - } - - public class GetDaemonBoneObjective : QuestObjective - { - public Container CorpseWithBone { get; set; } - - public override object Message - { - get - { - if ( System.From.Profession == 5 ) - { - /* Use your Sacred Journey - * ability on the rune to the North - * of Uzeraan to travel to the graveyard. - */ - return 1060755; - } - - /* Use Uzeraan's teleporter to get to the Haunted graveyard.

- * - * Slay the undead until you find a Daemon Bone. - */ - return 1049362; - } - } - - public GetDaemonBoneObjective() - { - } - - public override void OnComplete() - { - System.AddObjective( new ReturnDaemonBoneObjective() ); - } - - public override bool IgnoreYoungProtection( Mobile from ) - { - // This restriction continues until the end of the quest - if ( ( from is Zombie || from is Skeleton ) && from.Map == Map.Trammel && from.X >= 3391 && from.X <= 3424 && from.Y >= 2639 && from.Y <= 2664 ) // Haven graveyard - return true; - - return false; - } - - public override bool GetKillEvent( BaseCreature creature, Container corpse ) - { - if ( base.GetKillEvent( creature, corpse ) ) - return true; - - return UzeraanTurmoilQuest.HasLostDaemonBone( System.From ); - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( ( creature is Zombie || creature is Skeleton ) && corpse.Map == Map.Trammel && corpse.X >= 3391 && corpse.X <= 3424 && corpse.Y >= 2639 && corpse.Y <= 2664 ) // Haven graveyard - { - if ( Utility.RandomDouble() < 0.25 ) - CorpseWithBone = corpse; - } - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - CorpseWithBone = (Container) reader.ReadItem(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - if ( CorpseWithBone != null && CorpseWithBone.Deleted ) - CorpseWithBone = null; - - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (Item) CorpseWithBone ); - } - } - - public class ReturnDaemonBoneObjective : QuestObjective - { - public override object Message => 1049334; - - public ReturnDaemonBoneObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new UzeraanDaemonBoneConversation() ); - } - } - - public class CashBankCheckObjective : QuestObjective - { - public override object Message => 1049336; - - public CashBankCheckObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new BankerConversation() ); - } - } -} + public class FindUzeraanBeginObjective : QuestObjective + { + public override object Message => 1046039; + + public override void OnComplete() + { + if (System.From.Profession == 5) // paladin + System.AddConversation(new UzeraanTitheConversation()); + else + System.AddConversation(new UzeraanFirstTaskConversation()); + } + } + + public class TitheGoldObjective : QuestObjective + { + private int m_OldTithingPoints; + + public TitheGoldObjective() + { + m_OldTithingPoints = -1; + } + + public override object Message => 1060386; + + public override void CheckProgress() + { + PlayerMobile pm = System.From; + int curTithingPoints = pm.TithingPoints; + + if (curTithingPoints >= 500) + Complete(); + else if (curTithingPoints > m_OldTithingPoints && m_OldTithingPoints >= 0) + pm.SendLocalizedMessage(1060240, "", + 0x41); // You must have at least 500 tithing points before you can continue in your quest. + + m_OldTithingPoints = curTithingPoints; + } + + public override void OnComplete() + { + System.AddObjective(new FindUzeraanFirstTaskObjective()); + } + } + + public class FindUzeraanFirstTaskObjective : QuestObjective + { + public override object Message => 1060387; + + public override void OnComplete() + { + System.AddConversation(new UzeraanFirstTaskConversation()); + } + } + + public enum KillHordeMinionsStep + { + First, + LearnKarma, + Others + } + + public class KillHordeMinionsObjective : QuestObjective + { + public KillHordeMinionsObjective() + { + } + + public KillHordeMinionsObjective(KillHordeMinionsStep step) + { + Step = step; + } + + public KillHordeMinionsStep Step{ get; private set; } + + public override object Message + { + get + { + switch (Step) + { + case KillHordeMinionsStep.First: + /* Find the mountain pass beyond the house which lies at the + * end of the runic road.

+ * + * Assist the city Militia by slaying Horde Minions + */ + return 1049089; + + case KillHordeMinionsStep.LearnKarma: + /* You have just gained some Karma + * for killing the horde minion. Learn + * how this affects your Paladin abilities. + */ + return 1060389; + + default: + // Continue driving back the Horde Minions, as Uzeraan instructed you to do. + return 1060507; + } + } + } + + public override int MaxProgress + { + get + { + if (System.From.Profession == 5) // paladin + switch (Step) + { + case KillHordeMinionsStep.First: return 1; + case KillHordeMinionsStep.LearnKarma: return 2; + default: return 5; + } + + return 5; + } + } + + public override bool Completed + { + get + { + if (Step == KillHordeMinionsStep.LearnKarma && HasBeenRead) + return true; + return base.Completed; + } + } + + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + gump.AddHtmlObject(70, 260, 270, 100, 1049090, BaseQuestGump.Blue, false, false); // Horde Minions killed: + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + } + else + { + base.RenderProgress(gump); + } + } + + public override void OnRead() + { + CheckCompletionStatus(); + } + + public override bool IgnoreYoungProtection(Mobile from) + { + // This restriction continues until the quest is ended + if (from is HordeMinion && from.Map == Map.Trammel && from.X >= 3314 && from.X <= 3814 && from.Y >= 2345 && + from.Y <= 3095) // Haven island + return true; + + return false; + } + + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is HordeMinion && corpse.Map == Map.Trammel && corpse.X >= 3314 && corpse.X <= 3814 && + corpse.Y >= 2345 && corpse.Y <= 3095) // Haven island + { + if (CurProgress == 0) + System.From.Send(new DisplayHelpTopic(29, false)); // HEALING + + CurProgress++; + } + } + + public override void OnComplete() + { + if (System.From.Profession == 5) + switch (Step) + { + case KillHordeMinionsStep.First: + { + QuestObjective obj = new KillHordeMinionsObjective(KillHordeMinionsStep.LearnKarma); + System.AddObjective(obj); + obj.CurProgress = CurProgress; + break; + } + case KillHordeMinionsStep.LearnKarma: + { + QuestObjective obj = new KillHordeMinionsObjective(KillHordeMinionsStep.Others); + System.AddObjective(obj); + obj.CurProgress = CurProgress; + break; + } + default: + { + System.AddObjective(new FindUzeraanAboutReportObjective()); + break; + } + } + else + System.AddObjective(new FindUzeraanAboutReportObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + Step = (KillHordeMinionsStep)reader.ReadEncodedInt(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt((int)Step); + } + } + + public class FindUzeraanAboutReportObjective : QuestObjective + { + public override object Message => 1049091; + + public override void OnComplete() + { + System.AddConversation(new UzeraanReportConversation()); + } + } + + public class FindSchmendrickObjective : QuestObjective + { + public override object Message => 1049120; + + public override bool IgnoreYoungProtection(Mobile from) + { + // This restriction begins when this objective is completed, and continues until the quest is ended + if (Completed && from is RestlessSoul && from.Map == Map.Trammel && from.X >= 5199 && from.X <= 5271 && + from.Y >= 1812 && from.Y <= 1865) // Schmendrick's cave + return true; + + return false; + } + + public override void OnComplete() + { + System.AddConversation(new SchmendrickConversation()); + } + } + + public class FindApprenticeObjective : QuestObjective + { + public override object Message => 1049323; + + public override void OnComplete() + { + System.AddObjective(new ReturnScrollOfPowerObjective()); + } + } + + public class ReturnScrollOfPowerObjective : QuestObjective + { + public override object Message => 1049324; + + public override void OnComplete() + { + System.AddConversation(new UzeraanScrollOfPowerConversation()); + } + } + + public class FindDryadObjective : QuestObjective + { + public override object Message => 1049358; + + public override void OnComplete() + { + System.AddConversation(new DryadConversation()); + } + } + + public class ReturnFertileDirtObjective : QuestObjective + { + public override object Message => 1049327; + + public override void OnComplete() + { + System.AddConversation(new UzeraanFertileDirtConversation()); + } + } + + public class GetDaemonBloodObjective : QuestObjective + { + private bool m_Ambushed; + + public override object Message => 1049361; + + public override void CheckProgress() + { + PlayerMobile player = System.From; + + if (!m_Ambushed && player.Map == Map.Trammel && player.InRange(new Point3D(3456, 2558, 50), 30)) + { + int x = player.X - 1; + int y = player.Y - 2; + int z = Map.Trammel.GetAverageZ(x, y); + + if (Map.Trammel.CanSpawnMobile(x, y, z)) + { + m_Ambushed = true; + + player.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1049330); // You have been ambushed! Fight for your honor!!! + + BaseCreature creature = new HordeMinion(); + creature.MoveToWorld(new Point3D(x, y, z), Map.Trammel); + creature.Combatant = player; + } + } + } + + public override void OnComplete() + { + System.AddObjective(new ReturnDaemonBloodObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_Ambushed = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_Ambushed); + } + } + + public class ReturnDaemonBloodObjective : QuestObjective + { + public override object Message => 1049332; + + public override void OnComplete() + { + System.AddConversation(new UzeraanDaemonBloodConversation()); + } + } + + public class GetDaemonBoneObjective : QuestObjective + { + public Container CorpseWithBone{ get; set; } + + public override object Message + { + get + { + if (System.From.Profession == 5) return 1060755; + + /* Use Uzeraan's teleporter to get to the Haunted graveyard.

+ * + * Slay the undead until you find a Daemon Bone. + */ + return 1049362; + } + } + + public override void OnComplete() + { + System.AddObjective(new ReturnDaemonBoneObjective()); + } + + public override bool IgnoreYoungProtection(Mobile from) + { + // This restriction continues until the end of the quest + if ((from is Zombie || from is Skeleton) && from.Map == Map.Trammel && from.X >= 3391 && from.X <= 3424 && + from.Y >= 2639 && from.Y <= 2664) // Haven graveyard + return true; + + return false; + } + + public override bool GetKillEvent(BaseCreature creature, Container corpse) + { + if (base.GetKillEvent(creature, corpse)) + return true; + + return UzeraanTurmoilQuest.HasLostDaemonBone(System.From); + } + + public override void OnKill(BaseCreature creature, Container corpse) + { + if ((creature is Zombie || creature is Skeleton) && corpse.Map == Map.Trammel && corpse.X >= 3391 && + corpse.X <= 3424 && corpse.Y >= 2639 && corpse.Y <= 2664) // Haven graveyard + if (Utility.RandomDouble() < 0.25) + CorpseWithBone = corpse; + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + CorpseWithBone = (Container)reader.ReadItem(); + } + + public override void ChildSerialize(GenericWriter writer) + { + if (CorpseWithBone != null && CorpseWithBone.Deleted) + CorpseWithBone = null; + + writer.WriteEncodedInt(0); // version + + writer.Write(CorpseWithBone); + } + } + + public class ReturnDaemonBoneObjective : QuestObjective + { + public override object Message => 1049334; + + public override void OnComplete() + { + System.AddConversation(new UzeraanDaemonBoneConversation()); + } + } + + public class CashBankCheckObjective : QuestObjective + { + public override object Message => 1049336; + + public override void OnComplete() + { + System.AddConversation(new BankerConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Uzeraan Turmoil/UzeraanTurmoilQuest.cs b/Scripts/Engines/Quests/Uzeraan Turmoil/UzeraanTurmoilQuest.cs index 6942554b9..9b754f8e0 100644 --- a/Scripts/Engines/Quests/Uzeraan Turmoil/UzeraanTurmoilQuest.cs +++ b/Scripts/Engines/Quests/Uzeraan Turmoil/UzeraanTurmoilQuest.cs @@ -3,179 +3,165 @@ using Server.Mobiles; namespace Server.Engines.Quests.Haven { - public class UzeraanTurmoilQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( AcceptConversation ), - typeof( UzeraanTitheConversation ), - typeof( UzeraanFirstTaskConversation ), - typeof( UzeraanReportConversation ), - typeof( SchmendrickConversation ), - typeof( UzeraanScrollOfPowerConversation ), - typeof( DryadConversation ), - typeof( UzeraanFertileDirtConversation ), - typeof( UzeraanDaemonBloodConversation ), - typeof( UzeraanDaemonBoneConversation ), - typeof( BankerConversation ), - typeof( RadarConversation ), - typeof( LostScrollOfPowerConversation ), - typeof( LostFertileDirtConversation ), - typeof( DryadAppleConversation ), - typeof( LostDaemonBloodConversation ), - typeof( LostDaemonBoneConversation ), - typeof( FindUzeraanBeginObjective ), - typeof( TitheGoldObjective ), - typeof( FindUzeraanFirstTaskObjective ), - typeof( KillHordeMinionsObjective ), - typeof( FindUzeraanAboutReportObjective ), - typeof( FindSchmendrickObjective ), - typeof( FindApprenticeObjective ), - typeof( ReturnScrollOfPowerObjective ), - typeof( FindDryadObjective ), - typeof( ReturnFertileDirtObjective ), - typeof( GetDaemonBloodObjective ), - typeof( ReturnDaemonBloodObjective ), - typeof( GetDaemonBoneObjective ), - typeof( ReturnDaemonBoneObjective ), - typeof( CashBankCheckObjective ), - typeof( FewReagentsConversation ) - }; + public class UzeraanTurmoilQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(AcceptConversation), + typeof(UzeraanTitheConversation), + typeof(UzeraanFirstTaskConversation), + typeof(UzeraanReportConversation), + typeof(SchmendrickConversation), + typeof(UzeraanScrollOfPowerConversation), + typeof(DryadConversation), + typeof(UzeraanFertileDirtConversation), + typeof(UzeraanDaemonBloodConversation), + typeof(UzeraanDaemonBoneConversation), + typeof(BankerConversation), + typeof(RadarConversation), + typeof(LostScrollOfPowerConversation), + typeof(LostFertileDirtConversation), + typeof(DryadAppleConversation), + typeof(LostDaemonBloodConversation), + typeof(LostDaemonBoneConversation), + typeof(FindUzeraanBeginObjective), + typeof(TitheGoldObjective), + typeof(FindUzeraanFirstTaskObjective), + typeof(KillHordeMinionsObjective), + typeof(FindUzeraanAboutReportObjective), + typeof(FindSchmendrickObjective), + typeof(FindApprenticeObjective), + typeof(ReturnScrollOfPowerObjective), + typeof(FindDryadObjective), + typeof(ReturnFertileDirtObjective), + typeof(GetDaemonBloodObjective), + typeof(ReturnDaemonBloodObjective), + typeof(GetDaemonBoneObjective), + typeof(ReturnDaemonBoneObjective), + typeof(CashBankCheckObjective), + typeof(FewReagentsConversation) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + private bool m_HasLeftTheMansion; - public override object Name => 1049007; + public UzeraanTurmoilQuest(PlayerMobile from) : base(from) + { + } - public override object OfferMessage => 1049008; + // Serialization + public UzeraanTurmoilQuest() + { + } - public override TimeSpan RestartDelay => TimeSpan.MaxValue; - public override bool IsTutorial => true; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override int Picture - { - get - { - switch ( From.Profession ) - { - case 1: return 0x15C9; // warrior - case 2: return 0x15C1; // magician - default: return 0x15D3; // paladin - } - } - } + public override object Name => 1049007; - private bool m_HasLeftTheMansion; + public override object OfferMessage => 1049008; - public override void Slice() - { - if ( !m_HasLeftTheMansion && ( From.Map != Map.Trammel || From.X < 3573 || From.X > 3611 || From.Y < 2568 || From.Y > 2606 ) ) - { - m_HasLeftTheMansion = true; - AddConversation( new RadarConversation() ); - } + public override TimeSpan RestartDelay => TimeSpan.MaxValue; + public override bool IsTutorial => true; - base.Slice(); - } + public override int Picture + { + get + { + switch (From.Profession) + { + case 1: return 0x15C9; // warrior + case 2: return 0x15C1; // magician + default: return 0x15D3; // paladin + } + } + } - public UzeraanTurmoilQuest( PlayerMobile from ) : base( from ) - { - } + public override void Slice() + { + if (!m_HasLeftTheMansion && + (From.Map != Map.Trammel || From.X < 3573 || From.X > 3611 || From.Y < 2568 || From.Y > 2606)) + { + m_HasLeftTheMansion = true; + AddConversation(new RadarConversation()); + } - // Serialization - public UzeraanTurmoilQuest() - { - } + base.Slice(); + } - public override void Accept() - { - base.Accept(); + public override void Accept() + { + base.Accept(); - AddConversation( new AcceptConversation() ); - } + AddConversation(new AcceptConversation()); + } - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); - m_HasLeftTheMansion = reader.ReadBool(); - } + m_HasLeftTheMansion = reader.ReadBool(); + } - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_HasLeftTheMansion ); - } + writer.Write(m_HasLeftTheMansion); + } - public static bool HasLostScrollOfPower( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostScrollOfPower(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is UzeraanTurmoilQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( ReturnScrollOfPowerObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( SchmendrickScrollOfPower ) ) == null ); - } - } + if (qs is UzeraanTurmoilQuest) + if (qs.IsObjectiveInProgress(typeof(ReturnScrollOfPowerObjective))) + return from.Backpack?.FindItemByType(typeof(SchmendrickScrollOfPower)) == null; - return false; - } + return false; + } - public static bool HasLostFertileDirt( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostFertileDirt(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is UzeraanTurmoilQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( ReturnFertileDirtObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( QuestFertileDirt ) ) == null ); - } - } + if (qs is UzeraanTurmoilQuest) + if (qs.IsObjectiveInProgress(typeof(ReturnFertileDirtObjective))) + return from.Backpack?.FindItemByType(typeof(QuestFertileDirt)) == null; - return false; - } + return false; + } - public static bool HasLostDaemonBlood( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostDaemonBlood(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is UzeraanTurmoilQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( ReturnDaemonBloodObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( QuestDaemonBlood ) ) == null ); - } - } + if (qs is UzeraanTurmoilQuest) + if (qs.IsObjectiveInProgress(typeof(ReturnDaemonBloodObjective))) + return from.Backpack?.FindItemByType(typeof(QuestDaemonBlood)) == null; - return false; - } + return false; + } - public static bool HasLostDaemonBone( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return false; + public static bool HasLostDaemonBone(Mobile from) + { + if (!(from is PlayerMobile pm)) + return false; - QuestSystem qs = pm.Quest; + QuestSystem qs = pm.Quest; - if ( qs is UzeraanTurmoilQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( ReturnDaemonBoneObjective ) ) ) - { - return ( from.Backpack?.FindItemByType( typeof( QuestDaemonBone ) ) == null ); - } - } + if (qs is UzeraanTurmoilQuest) + if (qs.IsObjectiveInProgress(typeof(ReturnDaemonBoneObjective))) + return from.Backpack?.FindItemByType(typeof(QuestDaemonBone)) == null; - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Conversations.cs b/Scripts/Engines/Quests/Witch Apprentice/Conversations.cs index 0c2874828..25f430f33 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Conversations.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Conversations.cs @@ -1,395 +1,291 @@ namespace Server.Engines.Quests.Hag { - public class DontOfferConversation : QuestConversation - { - public override object Message => 1055000; - - public override bool Logged => false; - - public DontOfferConversation() - { - } - } - - public class AcceptConversation : QuestConversation - { - public override object Message => 1055002; - - public AcceptConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindApprenticeObjective( true ) ); - } - } - - public class HagDuringCorpseSearchConversation : QuestConversation - { - public override object Message => 1055003; - - public override bool Logged => false; - - public HagDuringCorpseSearchConversation() - { - } - } - - public class ApprenticeCorpseConversation : QuestConversation - { - public override object Message => 1055004; - - public ApprenticeCorpseConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindGrizeldaAboutMurderObjective() ); - } - } - - public class MurderConversation : QuestConversation - { - public override object Message => 1055005; - - public MurderConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new KillImpsObjective( true ) ); - } - } - - public class HagDuringImpSearchConversation : QuestConversation - { - public override object Message => 1055006; - - public override bool Logged => false; - - public HagDuringImpSearchConversation() - { - } - } - - public class ImpDeathConversation : QuestConversation - { - private Point3D m_ImpLocation; - - public override object Message => 1055007; - - public ImpDeathConversation( Point3D impLocation ) - { - m_ImpLocation = impLocation; - } - - public ImpDeathConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindZeefzorpulObjective( m_ImpLocation ) ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_ImpLocation = reader.ReadPoint3D(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (Point3D) m_ImpLocation ); - } - } - - public class ZeefzorpulConversation : QuestConversation - { - public override object Message => 1055008; - - public ZeefzorpulConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new ReturnRecipeObjective() ); - } - } - - public class RecipeConversation : QuestConversation - { - public override object Message => 1055009; - - public RecipeConversation() - { - } - - public override void OnRead() - { - System.AddObjective( new FindIngredientObjective( new Ingredient[0] ) ); - } - } - - public class HagDuringIngredientsConversation : QuestConversation - { - public override object Message => 1055012; - - public override bool Logged => false; - - public HagDuringIngredientsConversation() - { - } - } - - public class BlackheartFirstConversation : QuestConversation - { - public override object Message => 1055010; - - public BlackheartFirstConversation() - { - } - - public override void OnRead() - { - if ( System.FindObjective( typeof( FindIngredientObjective ) ) is FindIngredientObjective obj ) - System.AddObjective( new FindIngredientObjective( obj.Ingredients, true ) ); - } - } - - public class BlackheartNoPirateConversation : QuestConversation - { - private bool m_Tricorne; - private bool m_Drunken; - - public override object Message - { - get - { - if ( m_Tricorne) - { - if ( m_Drunken ) - { - /* The filthy Captain flashes a pleased grin at you as he looks you up - * and down.

Well that's more like it, me little deck swabber! - * Ye almost look like ye fit in around here, ready te sail the great seas - * of Britannia, sinking boats and slaying sea serpents!

- * - * But can ye truly handle yerself? Ye might think ye can test me meddle - * with a sip or two of yer dandy wine, but a real pirate walks the decks - * with a belly full of it. Lookit that, yer not even wobblin'!

- * - * Ye've impressed me a bit, ye wee tyke, but it'll take more'n that te - * join me crew!

Captain Blackheart tips his mug in your direction, - * offering up a jolly laugh, but it seems you still haven't impressed him - * enough. - */ - return 1055059; - } - - /* Captain Blackheart looks up from polishing his cutlass, glaring at - * you with red-rimmed eyes.

- * - * Well, well. Lookit the wee little deck swabby. Aren't ye a cute lil' - * lassy? Don't ye look just fancy? Ye think yer ready te join me pirate - * crew? Ye think I should offer ye some've me special Blackheart brew?

- * - * I'll make ye walk the plank, I will! We'll see how sweet n' darlin' ye - * look when the sea serpents get at ye and rip ye te threads! Won't that be - * a pretty picture, eh?

- * - * Ye don't have the stomach fer the pirate life, that's plain enough te me. Ye - * prance around here like a wee lil' princess, ye do. If ye want to join my - * crew ye can't just look tha part - ye have to have the stomach fer it, filled - * up with rotgut until ye can't see straight. I don't drink with just any ol' - * landlubber! Ye'd best prove yer mettle before ye talk te me again!

- * - * The drunken pirate captain leans back in his chair, taking another gulp of - * his drink before he starts in on another bawdy pirate song. - */ - return 1055057; - } - - if ( m_Drunken ) - { - /* The inebriated pirate looks up at you with a wry grin.

- * - * Well hello again, me little matey. I see ye have a belly full of rotgut - * in ye. I bet ye think you're a right hero, ready te face the world. But - * as I told ye before, bein' a member of my pirate crew means more'n just - * being able to hold yer drink. Ye have te look the part - and frankly, me - * little barnacle, ye don't have the cut of cloth te fit in with the crowd I - * like te hang around.

- * - * So scurry off, ye wee sewer rat, and don't come back round these parts all - * liquored up an' three sheets te tha wind, unless yer truly ready te join - * me pirate crew!

- * - * Captain Blackheart shoves you aside, banging his cutlass against the - * table as he calls to the waitress for another round. - */ - return 1055056; - } - - /* Captain Blackheart looks up from his drink, almost tipping over - * his chair as he looks you up and down.

- * - * You again? I thought I told ye te get lost? Go on with ye! Ye ain't - * no pirate - yer not even fit te clean the barnacles off me rear end! - * Don't ye come back babbling te me for any of me Blackheart Whiskey until - * ye look and act like a true pirate!

- * - * Now shove off, sewer rat - I've got drinkin' te do!

- * - * The inebriated pirate bolts back another mug of ale and brushes you - * off with a wave of his hand. - */ - return 1055058; - } - } - - public override bool Logged => false; - - public BlackheartNoPirateConversation( bool tricorne, bool drunken ) - { - m_Tricorne = tricorne; - m_Drunken = drunken; - } - - public BlackheartNoPirateConversation() - { - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_Tricorne = reader.ReadBool(); - m_Drunken = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_Tricorne ); - writer.Write( (bool) m_Drunken ); - } - } - - public class BlackheartPirateConversation : QuestConversation - { - private bool m_FirstMet; - - public override object Message - { - get - { - if ( m_FirstMet ) - { - /* The bawdy old pirate captain looks up from his bottle of Wild Harpy - * whiskey, as drunk as any man you've ever seen.

- * - * Avast ye, ye loveable pirate! Just in from sailin' the glorious sea? Ye - * look right ready te fall down on the spot, ye do!

- * - * I tell ye what, from the look've ye, ye deserve a belt of better brew than - * the slop ye've been drinking, and I've just the thing.

- * - * I call it Captain Blackheart's Whiskey, and it'll give ye hairs on yer chest, - * that's for sure. Why, a keg of this stuff once spilled on my ship, and it - * ate a hole right through the deck!

Go on, drink up, or use it to clean - * the rust off your cutlass - it's the best brew, either way!

- * - * Captain Blackheart hands you a jug of his famous Whiskey. You think it best - * to return it to the Hag, rather than drink any of the noxious swill. - */ - return 1055054; - } - - /* The drunken pirate, Captain Blackheart, looks up from his bottle - * of whiskey with a pleased expression.

- * - * Well looky here! I didn't think a landlubber like yourself had the pirate - * blood in ye! But look at that! You certainly look the part now! Sure - * you can still keep on your feet? Har!

- * - * Avast ye, ye loveable pirate! Ye deserve a belt of better brew than the slop - * ye've been drinking, and I've just the thing.

- * - * I call it Captain Blackheart's Whiskey, and it'll give ye hairs on yer chest, - * that's for sure. Why, a keg of this stuff once spilled on my ship, and it ate - * a hole right through the deck!

- * - * Go on, drink up, or use it to clean the rust off your cutlass - it's the best - * brew, either way!

- * - * Captain Blackheart hands you a jug of his famous Whiskey. You think it best - * to return it to the Hag, rather than drink any of the noxious swill. - */ - return 1055011; - } - } - - public BlackheartPirateConversation( bool firstMet ) - { - m_FirstMet = firstMet; - } - - public BlackheartPirateConversation() - { - } - - public override void OnRead() - { - if ( System.FindObjective( typeof( FindIngredientObjective ) ) is FindIngredientObjective obj ) - obj.NextStep(); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_FirstMet = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (bool) m_FirstMet ); - } - } - - public class EndConversation : QuestConversation - { - public override object Message => 1055013; - - public EndConversation() - { - } - - public override void OnRead() - { - System.Complete(); - } - } - - public class RecentlyFinishedConversation : QuestConversation - { - public override object Message => 1055064; - - public RecentlyFinishedConversation() - { - } - - public override bool Logged => false; - } -} + public class DontOfferConversation : QuestConversation + { + public override object Message => 1055000; + + public override bool Logged => false; + } + + public class AcceptConversation : QuestConversation + { + public override object Message => 1055002; + + public override void OnRead() + { + System.AddObjective(new FindApprenticeObjective(true)); + } + } + + public class HagDuringCorpseSearchConversation : QuestConversation + { + public override object Message => 1055003; + + public override bool Logged => false; + } + + public class ApprenticeCorpseConversation : QuestConversation + { + public override object Message => 1055004; + + public override void OnRead() + { + System.AddObjective(new FindGrizeldaAboutMurderObjective()); + } + } + + public class MurderConversation : QuestConversation + { + public override object Message => 1055005; + + public override void OnRead() + { + System.AddObjective(new KillImpsObjective(true)); + } + } + + public class HagDuringImpSearchConversation : QuestConversation + { + public override object Message => 1055006; + + public override bool Logged => false; + } + + public class ImpDeathConversation : QuestConversation + { + private Point3D m_ImpLocation; + + public ImpDeathConversation(Point3D impLocation) + { + m_ImpLocation = impLocation; + } + + public ImpDeathConversation() + { + } + + public override object Message => 1055007; + + public override void OnRead() + { + System.AddObjective(new FindZeefzorpulObjective(m_ImpLocation)); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_ImpLocation = reader.ReadPoint3D(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_ImpLocation); + } + } + + public class ZeefzorpulConversation : QuestConversation + { + public override object Message => 1055008; + + public override void OnRead() + { + System.AddObjective(new ReturnRecipeObjective()); + } + } + + public class RecipeConversation : QuestConversation + { + public override object Message => 1055009; + + public override void OnRead() + { + System.AddObjective(new FindIngredientObjective(new Ingredient[0])); + } + } + + public class HagDuringIngredientsConversation : QuestConversation + { + public override object Message => 1055012; + + public override bool Logged => false; + } + + public class BlackheartFirstConversation : QuestConversation + { + public override object Message => 1055010; + + public override void OnRead() + { + if (System.FindObjective(typeof(FindIngredientObjective)) is FindIngredientObjective obj) + System.AddObjective(new FindIngredientObjective(obj.Ingredients, true)); + } + } + + public class BlackheartNoPirateConversation : QuestConversation + { + private bool m_Drunken; + private bool m_Tricorne; + + public BlackheartNoPirateConversation(bool tricorne, bool drunken) + { + m_Tricorne = tricorne; + m_Drunken = drunken; + } + + public BlackheartNoPirateConversation() + { + } + + public override object Message + { + get + { + if (m_Tricorne) + { + if (m_Drunken) return 1055059; + + /* Captain Blackheart looks up from polishing his cutlass, glaring at + * you with red-rimmed eyes.

+ * + * Well, well. Lookit the wee little deck swabby. Aren't ye a cute lil' + * lassy? Don't ye look just fancy? Ye think yer ready te join me pirate + * crew? Ye think I should offer ye some've me special Blackheart brew?

+ * + * I'll make ye walk the plank, I will! We'll see how sweet n' darlin' ye + * look when the sea serpents get at ye and rip ye te threads! Won't that be + * a pretty picture, eh?

+ * + * Ye don't have the stomach fer the pirate life, that's plain enough te me. Ye + * prance around here like a wee lil' princess, ye do. If ye want to join my + * crew ye can't just look tha part - ye have to have the stomach fer it, filled + * up with rotgut until ye can't see straight. I don't drink with just any ol' + * landlubber! Ye'd best prove yer mettle before ye talk te me again!

+ * + * The drunken pirate captain leans back in his chair, taking another gulp of + * his drink before he starts in on another bawdy pirate song. + */ + return 1055057; + } + + if (m_Drunken) return 1055056; + + /* Captain Blackheart looks up from his drink, almost tipping over + * his chair as he looks you up and down.

+ * + * You again? I thought I told ye te get lost? Go on with ye! Ye ain't + * no pirate - yer not even fit te clean the barnacles off me rear end! + * Don't ye come back babbling te me for any of me Blackheart Whiskey until + * ye look and act like a true pirate!

+ * + * Now shove off, sewer rat - I've got drinkin' te do!

+ * + * The inebriated pirate bolts back another mug of ale and brushes you + * off with a wave of his hand. + */ + return 1055058; + } + } + + public override bool Logged => false; + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_Tricorne = reader.ReadBool(); + m_Drunken = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_Tricorne); + writer.Write(m_Drunken); + } + } + + public class BlackheartPirateConversation : QuestConversation + { + private bool m_FirstMet; + + public BlackheartPirateConversation(bool firstMet) + { + m_FirstMet = firstMet; + } + + public BlackheartPirateConversation() + { + } + + public override object Message + { + get + { + if (m_FirstMet) return 1055054; + + /* The drunken pirate, Captain Blackheart, looks up from his bottle + * of whiskey with a pleased expression.

+ * + * Well looky here! I didn't think a landlubber like yourself had the pirate + * blood in ye! But look at that! You certainly look the part now! Sure + * you can still keep on your feet? Har!

+ * + * Avast ye, ye loveable pirate! Ye deserve a belt of better brew than the slop + * ye've been drinking, and I've just the thing.

+ * + * I call it Captain Blackheart's Whiskey, and it'll give ye hairs on yer chest, + * that's for sure. Why, a keg of this stuff once spilled on my ship, and it ate + * a hole right through the deck!

+ * + * Go on, drink up, or use it to clean the rust off your cutlass - it's the best + * brew, either way!

+ * + * Captain Blackheart hands you a jug of his famous Whiskey. You think it best + * to return it to the Hag, rather than drink any of the noxious swill. + */ + return 1055011; + } + } + + public override void OnRead() + { + if (System.FindObjective(typeof(FindIngredientObjective)) is FindIngredientObjective obj) + obj.NextStep(); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_FirstMet = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_FirstMet); + } + } + + public class EndConversation : QuestConversation + { + public override object Message => 1055013; + + public override void OnRead() + { + System.Complete(); + } + } + + public class RecentlyFinishedConversation : QuestConversation + { + public override object Message => 1055064; + + public override bool Logged => false; + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Ingredient.cs b/Scripts/Engines/Quests/Witch Apprentice/Ingredient.cs index 3005ef13d..5589c845d 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Ingredient.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Ingredient.cs @@ -3,105 +3,104 @@ using Server.Mobiles; namespace Server.Engines.Quests.Hag { - public enum Ingredient - { - SheepLiver, - RabbitsFoot, - MongbatWing, - ChickenGizzard, - RatTail, - FrogsLeg, - DeerHeart, - LizardTongue, - SlimeOoze, - SpiritEssence, - SwampWater, - RedMushrooms, - Bones, - StarChart, - Whiskey - } + public enum Ingredient + { + SheepLiver, + RabbitsFoot, + MongbatWing, + ChickenGizzard, + RatTail, + FrogsLeg, + DeerHeart, + LizardTongue, + SlimeOoze, + SpiritEssence, + SwampWater, + RedMushrooms, + Bones, + StarChart, + Whiskey + } - public class IngredientInfo - { - private static IngredientInfo[] m_Table = { - // sheep liver - new IngredientInfo( 1055020, 5, typeof( Sheep ) ), - // rabbit's foot - new IngredientInfo( 1055021, 5, typeof( Rabbit ), typeof( JackRabbit ) ), - // mongbat wing - new IngredientInfo( 1055022, 5, typeof( Mongbat ), typeof( GreaterMongbat ) ), - // chicken gizzard - new IngredientInfo( 1055023, 5, typeof( Chicken ) ), - // rat tail - new IngredientInfo( 1055024, 5, typeof( Rat ), typeof( GiantRat ), typeof( SewerRat ) ), - // frog's leg - new IngredientInfo( 1055025, 5, typeof( BullFrog ) ), - // deer heart - new IngredientInfo( 1055026, 5, typeof( Hind ), typeof( GreatHart ) ), - // lizard tongue - new IngredientInfo( 1055027, 5, typeof( LavaLizard ), typeof( Lizardman ) ), - // slime ooze - new IngredientInfo( 1055028, 5, typeof( Slime ) ), - // spirit essence - new IngredientInfo( 1055029, 5, typeof( Ghoul ), typeof( Spectre ), typeof( Shade ), typeof( Wraith ), typeof( Bogle ) ), - // Swamp Water - new IngredientInfo( 1055030, 1 ), - // Freshly Cut Red Mushrooms - new IngredientInfo( 1055031, 1 ), - // Bones Buried In Hallowed Ground - new IngredientInfo( 1055032, 1 ), - // Star Chart - new IngredientInfo( 1055033, 1 ), - // Captain Blackheart's Whiskey - new IngredientInfo( 1055034, 1 ) - }; + public class IngredientInfo + { + private static IngredientInfo[] m_Table = + { + // sheep liver + new IngredientInfo(1055020, 5, typeof(Sheep)), + // rabbit's foot + new IngredientInfo(1055021, 5, typeof(Rabbit), typeof(JackRabbit)), + // mongbat wing + new IngredientInfo(1055022, 5, typeof(Mongbat), typeof(GreaterMongbat)), + // chicken gizzard + new IngredientInfo(1055023, 5, typeof(Chicken)), + // rat tail + new IngredientInfo(1055024, 5, typeof(Rat), typeof(GiantRat), typeof(SewerRat)), + // frog's leg + new IngredientInfo(1055025, 5, typeof(BullFrog)), + // deer heart + new IngredientInfo(1055026, 5, typeof(Hind), typeof(GreatHart)), + // lizard tongue + new IngredientInfo(1055027, 5, typeof(LavaLizard), typeof(Lizardman)), + // slime ooze + new IngredientInfo(1055028, 5, typeof(Slime)), + // spirit essence + new IngredientInfo(1055029, 5, typeof(Ghoul), typeof(Spectre), typeof(Shade), typeof(Wraith), typeof(Bogle)), + // Swamp Water + new IngredientInfo(1055030, 1), + // Freshly Cut Red Mushrooms + new IngredientInfo(1055031, 1), + // Bones Buried In Hallowed Ground + new IngredientInfo(1055032, 1), + // Star Chart + new IngredientInfo(1055033, 1), + // Captain Blackheart's Whiskey + new IngredientInfo(1055034, 1) + }; - public static IngredientInfo Get( Ingredient ingredient ) - { - int index = (int)ingredient; + private IngredientInfo(int name, int quantity, params Type[] creatures) + { + Name = name; + Creatures = creatures; + Quantity = quantity; + } - if ( index >= 0 && index < m_Table.Length ) - return m_Table[index]; - return m_Table[0]; - } + public int Name{ get; } - public static Ingredient RandomIngredient( Ingredient[] oldIngredients ) - { - int length = m_Table.Length - oldIngredients.Length; - Ingredient[] ingredients = new Ingredient[length]; + public Type[] Creatures{ get; } - for ( int i = 0, n = 0; i < m_Table.Length && n < ingredients.Length; i++ ) - { - Ingredient currIngredient = (Ingredient)i; + public int Quantity{ get; } - bool found = false; - for ( int j = 0; !found && j < oldIngredients.Length; j++ ) - { - if ( oldIngredients[j] == currIngredient ) - found = true; - } + public static IngredientInfo Get(Ingredient ingredient) + { + int index = (int)ingredient; - if ( !found ) - ingredients[n++] = currIngredient; - } + if (index >= 0 && index < m_Table.Length) + return m_Table[index]; + return m_Table[0]; + } - int index = Utility.Random( ingredients.Length ); + public static Ingredient RandomIngredient(Ingredient[] oldIngredients) + { + int length = m_Table.Length - oldIngredients.Length; + Ingredient[] ingredients = new Ingredient[length]; - return ingredients[index]; - } + for (int i = 0, n = 0; i < m_Table.Length && n < ingredients.Length; i++) + { + Ingredient currIngredient = (Ingredient)i; - public int Name { get; } + bool found = false; + for (int j = 0; !found && j < oldIngredients.Length; j++) + if (oldIngredients[j] == currIngredient) + found = true; - public Type[] Creatures { get; } + if (!found) + ingredients[n++] = currIngredient; + } - public int Quantity { get; } + int index = Utility.Random(ingredients.Length); - private IngredientInfo( int name, int quantity, params Type[] creatures ) - { - Name = name; - Creatures = creatures; - Quantity = quantity; - } - } -} + return ingredients[index]; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/Cauldron.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/Cauldron.cs index 0d64ce249..dd62cc1b4 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/Cauldron.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/Cauldron.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class Cauldron : Item - { - public override string DefaultName => "a cauldron"; + public class Cauldron : Item + { + [Constructible] + public Cauldron() : base(0x9ED) + { + Weight = 1.0; + } - [Constructible] - public Cauldron() : base( 0x9ED ) - { - Weight = 1.0; - } + public Cauldron(Serial serial) : base(serial) + { + } - public Cauldron( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a cauldron"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/HagApprenticeCorpse.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/HagApprenticeCorpse.cs index 38e3ff6fd..ea47aed2e 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/HagApprenticeCorpse.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/HagApprenticeCorpse.cs @@ -1,101 +1,97 @@ using System.Collections.Generic; using Server.Items; +using Server.Misc; using Server.Mobiles; using Server.Network; -using Server.Misc; namespace Server.Engines.Quests.Hag { - public class HagApprenticeCorpse : Corpse - { - private static Mobile GetOwner() - { - Mobile apprentice = new Mobile(); + public class HagApprenticeCorpse : Corpse + { + [Constructible] + public HagApprenticeCorpse() : base(GetOwner(), GetEquipment()) + { + Direction = Direction.South; - apprentice.Hue = Utility.RandomSkinHue(); - apprentice.Female = false; - apprentice.Body = 0x190; + foreach (Item item in EquipItems) DropItem(item); + } - apprentice.Delete(); + public HagApprenticeCorpse(Serial serial) : base(serial) + { + } - return apprentice; - } + private static Mobile GetOwner() + { + Mobile apprentice = new Mobile(); - private static List GetEquipment() - { - return new List(); - } + apprentice.Hue = Utility.RandomSkinHue(); + apprentice.Female = false; + apprentice.Body = 0x190; - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( "a charred corpse" ); - } + apprentice.Delete(); - public override void OnSingleClick( Mobile from ) - { - int hue = Notoriety.GetHue( NotorietyHandlers.CorpseNotoriety( from, this ) ); + return apprentice; + } - from.Send( new AsciiMessage( Serial, ItemID, MessageType.Label, hue, 3, "", "a charred corpse" ) ); - } + private static List GetEquipment() + { + return new List(); + } - [Constructible] - public HagApprenticeCorpse() : base( GetOwner(), GetEquipment() ) - { - Direction = Direction.South; + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add("a charred corpse"); + } - foreach ( Item item in EquipItems ) - { - DropItem( item ); - } - } + public override void OnSingleClick(Mobile from) + { + int hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this)); - public HagApprenticeCorpse( Serial serial ) : base( serial ) - { - } + from.Send(new AsciiMessage(Serial, ItemID, MessageType.Label, hue, 3, "", "a charred corpse")); + } - public override void Open( Mobile from, bool checkSelfLoot ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - return; + public override void Open(Mobile from, bool checkSelfLoot) + { + if (!from.InRange(GetWorldLocation(), 2)) + return; - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( qs is WitchApprenticeQuest ) - { - if ( qs.FindObjective( typeof( FindApprenticeObjective ) ) is FindApprenticeObjective obj && !obj.Completed ) - { - if ( obj.Corpse == this ) - { - obj.Complete(); - Delete(); - } - else - { - SendLocalizedMessageTo( from, 1055047 ); // You examine the corpse, but it doesn't fit the description of the particular apprentice the Hag tasked you with finding. - } + if (qs is WitchApprenticeQuest) + if (qs.FindObjective(typeof(FindApprenticeObjective)) is FindApprenticeObjective obj && !obj.Completed) + { + if (obj.Corpse == this) + { + obj.Complete(); + Delete(); + } + else + { + SendLocalizedMessageTo(from, + 1055047); // You examine the corpse, but it doesn't fit the description of the particular apprentice the Hag tasked you with finding. + } - return; - } - } - } + return; + } + } - SendLocalizedMessageTo( from, 1055048 ); // You examine the corpse, but find nothing of interest. - } + SendLocalizedMessageTo(from, 1055048); // You examine the corpse, but find nothing of interest. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/HagCauldron.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/HagCauldron.cs index c2c8a91ca..38e657253 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/HagCauldron.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/HagCauldron.cs @@ -1,37 +1,36 @@ namespace Server.Items { - public class HagCauldron : BaseAddon - { + public class HagCauldron : BaseAddon + { + [Constructible] + public HagCauldron() + { + AddonComponent pot; + pot = new AddonComponent(2420); + AddComponent(pot, 0, 0, 0); //pot w/ support - [Constructible] - public HagCauldron() - { - AddonComponent pot; - pot = new AddonComponent(2420); - AddComponent(pot, 0, 0, 0); //pot w/ support + AddonComponent fire; + fire = new AddonComponent(4012); //fire pit + fire.Light = LightType.Circle150; + AddComponent(fire, 0, 0, 0); + } - AddonComponent fire; - fire = new AddonComponent(4012); //fire pit - fire.Light = LightType.Circle150; - AddComponent(fire, 0, 0, 0); - } - - public HagCauldron( Serial serial ) : base( serial ) - { - } + public HagCauldron(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/HagStew.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/HagStew.cs index 15dc3ca50..0ae158f45 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/HagStew.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/HagStew.cs @@ -2,73 +2,72 @@ using System; namespace Server.Items { - public class HagStew : BaseAddon - { + public class HagStew : BaseAddon + { + [Constructible] + public HagStew() + { + AddonComponent stew; + stew = new AddonComponent(2416); + stew.Name = "stew"; + stew.Visible = true; + AddComponent(stew, 0, 0, -7); //stew + } - [Constructible] - public HagStew() + public HagStew(Serial serial) : base(serial) + { + } + + public override void OnComponentUsed(AddonComponent stew, Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.SendMessage("You are too far away."); + } + else + { + stew.Visible = false; + + BreadLoaf hagstew = new BreadLoaf(); //this decides your fillrate + hagstew.Eat(from); + + Timer m_timer = new ShowStew(stew); + m_timer.Start(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public class ShowStew : Timer + { + private AddonComponent stew; + + public ShowStew(AddonComponent ac) : base(TimeSpan.FromSeconds(30)) + { + stew = ac; + Priority = TimerPriority.OneSecond; + } + + protected override void OnTick() + { + if (stew.Visible == false) { - AddonComponent stew; - stew = new AddonComponent(2416); - stew.Name = "stew"; - stew.Visible = true; - AddComponent(stew, 0, 0, -7); //stew + Stop(); + stew.Visible = true; } - - public override void OnComponentUsed(AddonComponent stew, Mobile from) - { - if (!from.InRange(GetWorldLocation(), 2)) - from.SendMessage("You are too far away."); - else - { - { - stew.Visible = false; - - BreadLoaf hagstew = new BreadLoaf(); //this decides your fillrate - hagstew.Eat(from); - - Timer m_timer = new ShowStew(stew); - m_timer.Start(); - } - } - } - - public class ShowStew : Timer - { - private AddonComponent stew; - - public ShowStew(AddonComponent ac) : base(TimeSpan.FromSeconds(30)) - { - stew = ac; - Priority = TimerPriority.OneSecond; - } - - protected override void OnTick() - { - if ( stew.Visible == false ) - { - Stop(); - stew.Visible = true; - } - } - } - - public HagStew( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/HangoverCure.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/HangoverCure.cs index f2ea98834..f528f01fa 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/HangoverCure.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/HangoverCure.cs @@ -1,81 +1,81 @@ namespace Server.Engines.Quests.Hag { - public class HangoverCure : Item - { - public override int LabelNumber => 1055060; // Grizelda's Extra Strength Hangover Cure + public class HangoverCure : Item + { + [Constructible] + public HangoverCure() : base(0xE2B) + { + Weight = 1.0; + Hue = 0x2D; - [CommandProperty( AccessLevel.GameMaster )] - public int Uses { get; set; } + Uses = 20; + } - [Constructible] - public HangoverCure() : base( 0xE2B ) - { - Weight = 1.0; - Hue = 0x2D; + public HangoverCure(Serial serial) : base(serial) + { + } - Uses = 20; - } + public override int LabelNumber => 1055060; // Grizelda's Extra Strength Hangover Cure - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - SendLocalizedMessageTo( from, 1042038 ); // You must have the object in your backpack to use it. - return; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Uses{ get; set; } - if ( Uses > 0 ) - { - from.PlaySound( 0x2D6 ); - from.SendLocalizedMessage( 501206 ); // An awful taste fills your mouth. + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + SendLocalizedMessageTo(from, 1042038); // You must have the object in your backpack to use it. + return; + } - if ( from.BAC > 0 ) - { - from.BAC = 0; - from.SendLocalizedMessage( 501204 ); // You are now sober! - } + if (Uses > 0) + { + from.PlaySound(0x2D6); + from.SendLocalizedMessage(501206); // An awful taste fills your mouth. - Uses--; - } - else - { - Delete(); - from.SendLocalizedMessage( 501201 ); // There wasn't enough left to have any effect. - } - } + if (from.BAC > 0) + { + from.BAC = 0; + from.SendLocalizedMessage(501204); // You are now sober! + } - public HangoverCure( Serial serial ) : base( serial ) - { - } + Uses--; + } + else + { + Delete(); + from.SendLocalizedMessage(501201); // There wasn't enough left to have any effect. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.WriteEncodedInt( Uses ); - } + writer.WriteEncodedInt(Uses); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Uses = reader.ReadEncodedInt(); - break; - } - case 0: - { - Uses = 20; - break; - } - } - } - } -} + switch (version) + { + case 1: + { + Uses = reader.ReadEncodedInt(); + break; + } + case 0: + { + Uses = 20; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/MagicFlute.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/MagicFlute.cs index 0fa051079..10affb8da 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/MagicFlute.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/MagicFlute.cs @@ -2,69 +2,69 @@ using Server.Mobiles; namespace Server.Engines.Quests.Hag { - public class MagicFlute : Item - { - public override int LabelNumber => 1055051; // magic flute + public class MagicFlute : Item + { + [Constructible] + public MagicFlute() : base(0x1421) + { + Hue = 0x8AB; + } - [Constructible] - public MagicFlute() : base( 0x1421 ) - { - Hue = 0x8AB; - } + public MagicFlute(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - SendLocalizedMessageTo( from, 1042292 ); // You must have the object in your backpack to use it. - return; - } + public override int LabelNumber => 1055051; // magic flute - from.PlaySound( 0x3D ); + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + SendLocalizedMessageTo(from, 1042292); // You must have the object in your backpack to use it. + return; + } - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + from.PlaySound(0x3D); - if ( qs is WitchApprenticeQuest ) - { - if ( qs.FindObjective( typeof( FindZeefzorpulObjective ) ) is FindZeefzorpulObjective obj && !obj.Completed ) - { - if ( ( player.Map != Map.Trammel && player.Map != Map.Felucca ) || !player.InRange( obj.ImpLocation, 8 ) ) - { - player.SendLocalizedMessage( 1055053 ); // Nothing happens. Zeefzorpul must not be hiding in this area. - } - else if ( player.InRange( obj.ImpLocation, 4 ) ) - { - Delete(); + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - obj.Complete(); - } - else - { - player.SendLocalizedMessage( 1055052 ); // The flute sparkles. Zeefzorpul must be in a good hiding place nearby. - } - } - } - } - } + if (qs is WitchApprenticeQuest) + if (qs.FindObjective(typeof(FindZeefzorpulObjective)) is FindZeefzorpulObjective obj && !obj.Completed) + { + if (player.Map != Map.Trammel && player.Map != Map.Felucca || !player.InRange(obj.ImpLocation, 8)) + { + player.SendLocalizedMessage( + 1055053); // Nothing happens. Zeefzorpul must not be hiding in this area. + } + else if (player.InRange(obj.ImpLocation, 4)) + { + Delete(); - public MagicFlute( Serial serial ) : base( serial ) - { - } + obj.Complete(); + } + else + { + player.SendLocalizedMessage( + 1055052); // The flute sparkles. Zeefzorpul must be in a good hiding place nearby. + } + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Items/MoonfireBrew.cs b/Scripts/Engines/Quests/Witch Apprentice/Items/MoonfireBrew.cs index 482ea0d48..6f95e11c1 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Items/MoonfireBrew.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Items/MoonfireBrew.cs @@ -1,31 +1,31 @@ namespace Server.Engines.Quests.Hag { - public class MoonfireBrew : Item - { - public override int LabelNumber => 1055065; // a bottle of magical moonfire brew + public class MoonfireBrew : Item + { + [Constructible] + public MoonfireBrew() : base(0xF04) + { + Weight = 1.0; + } - [Constructible] - public MoonfireBrew() : base( 0xF04 ) - { - Weight = 1.0; - } + public MoonfireBrew(Serial serial) : base(serial) + { + } - public MoonfireBrew( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1055065; // a bottle of magical moonfire brew - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Blackheart.cs b/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Blackheart.cs index 18e0aa04f..1d5ae827a 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Blackheart.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Blackheart.cs @@ -1,114 +1,114 @@ using System; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; +using Server.Network; namespace Server.Engines.Quests.Hag { - public class Blackheart : BaseQuester - { - public override string DefaultName => "Captain Blackheart"; + public class Blackheart : BaseQuester + { + [Constructible] + public Blackheart() : base("the Drunken Pirate") + { + } - [Constructible] - public Blackheart() : base( "the Drunken Pirate" ) - { - } + public Blackheart(Serial serial) : base(serial) + { + } - public Blackheart( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Captain Blackheart"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x83EF; + Hue = 0x83EF; - Female = false; - Body = 0x190; - } + Female = false; + Body = 0x190; + } - public override void InitOutfit() - { - AddItem( new FancyShirt() ); - AddItem( new LongPants( 0x66D ) ); - AddItem( new ThighBoots() ); - AddItem( new TricorneHat( 0x1 ) ); - AddItem( new BodySash( 0x66D ) ); + public override void InitOutfit() + { + AddItem(new FancyShirt()); + AddItem(new LongPants(0x66D)); + AddItem(new ThighBoots()); + AddItem(new TricorneHat(0x1)); + AddItem(new BodySash(0x66D)); - LeatherGloves gloves = new LeatherGloves(); - gloves.Hue = 0x66D; - AddItem( gloves ); + LeatherGloves gloves = new LeatherGloves(); + gloves.Hue = 0x66D; + AddItem(gloves); - FacialHairItemID = 0x203E; // Long Beard - FacialHairHue = 0x455; + FacialHairItemID = 0x203E; // Long Beard + FacialHairHue = 0x455; - Item sword = new Cutlass(); - sword.Movable = false; - AddItem( sword ); - } + Item sword = new Cutlass(); + sword.Movable = false; + AddItem(sword); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - Direction = GetDirectionTo( player ); - Animate( 33, 20, 1, true, false, 0 ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + Direction = GetDirectionTo(player); + Animate(33, 20, 1, true, false, 0); - QuestSystem qs = player.Quest; + QuestSystem qs = player.Quest; - if ( qs is WitchApprenticeQuest ) - { - if ( qs.FindObjective( typeof( FindIngredientObjective ) ) is FindIngredientObjective obj && !obj.Completed && obj.Ingredient == Ingredient.Whiskey ) - { - PlaySound( Utility.RandomBool() ? 0x42E : 0x43F ); + if (qs is WitchApprenticeQuest) + if (qs.FindObjective(typeof(FindIngredientObjective)) is FindIngredientObjective obj && !obj.Completed && + obj.Ingredient == Ingredient.Whiskey) + { + PlaySound(Utility.RandomBool() ? 0x42E : 0x43F); - Item hat = player.FindItemOnLayer( Layer.Helm ); - bool tricorne = hat is TricorneHat; + Item hat = player.FindItemOnLayer(Layer.Helm); + bool tricorne = hat is TricorneHat; - if ( tricorne && player.BAC >= 20 ) - { - obj.Complete(); + if (tricorne && player.BAC >= 20) + { + obj.Complete(); - qs.AddConversation( new BlackheartPirateConversation( !obj.BlackheartMet ) ); - } - else if ( !obj.BlackheartMet ) - { - obj.Complete(); + qs.AddConversation(new BlackheartPirateConversation(!obj.BlackheartMet)); + } + else if (!obj.BlackheartMet) + { + obj.Complete(); - qs.AddConversation( new BlackheartFirstConversation() ); - } - else - { - qs.AddConversation( new BlackheartNoPirateConversation( tricorne, player.BAC > 0 ) ); - } + qs.AddConversation(new BlackheartFirstConversation()); + } + else + { + qs.AddConversation(new BlackheartNoPirateConversation(tricorne, player.BAC > 0)); + } - return; - } - } + return; + } - PlaySound( 0x42C ); - SayTo( player, 1055041 ); // The drunken pirate shakes his fist at you and goes back to drinking. - } + PlaySound(0x42C); + SayTo(player, 1055041); // The drunken pirate shakes his fist at you and goes back to drinking. + } - private void Heave() - { - PublicOverheadMessage( Network.MessageType.Regular, 0x3B2, 500849 ); // *hic* + private void Heave() + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 500849); // *hic* - Timer.DelayCall( TimeSpan.FromSeconds( Utility.RandomMinMax( 60, 180 ) ), Heave ); - } + Timer.DelayCall(TimeSpan.FromSeconds(Utility.RandomMinMax(60, 180)), Heave); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Heave(); - } - } -} + Heave(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Grizelda.cs b/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Grizelda.cs index 4d8c03ccb..3f50e97bc 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Grizelda.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Grizelda.cs @@ -1,217 +1,219 @@ -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Hag { - public class Grizelda : BaseQuester - { - public override bool ClickTitle => true; - public override string DefaultName => "Grizelda"; + public class Grizelda : BaseQuester + { + [Constructible] + public Grizelda() : base("the Hag") + { + } - [Constructible] - public Grizelda() : base( "the Hag" ) - { - } + public Grizelda(Serial serial) : base(serial) + { + } - public Grizelda( Serial serial ) : base( serial ) - { - } + public override bool ClickTitle => true; + public override string DefaultName => "Grizelda"; - public override void InitBody() - { - InitStats( 100, 100, 25 ); + public override void InitBody() + { + InitStats(100, 100, 25); - Hue = 0x83EA; + Hue = 0x83EA; - Female = true; - Body = 0x191; - } + Female = true; + Body = 0x191; + } - public override void InitOutfit() - { - AddItem( new Robe( 0x1 ) ); - AddItem( new Sandals() ); - AddItem( new WizardsHat( 0x1 ) ); - AddItem( new GoldBracelet() ); + public override void InitOutfit() + { + AddItem(new Robe(0x1)); + AddItem(new Sandals()); + AddItem(new WizardsHat(0x1)); + AddItem(new GoldBracelet()); - HairItemID = 0x203C; + HairItemID = 0x203C; - Item staff = new GnarledStaff(); - staff.Movable = false; - AddItem( staff ); - } + Item staff = new GnarledStaff(); + staff.Movable = false; + AddItem(staff); + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - Direction = GetDirectionTo( player ); + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + Direction = GetDirectionTo(player); - QuestSystem qs = player.Quest; + QuestSystem qs = player.Quest; - if ( qs is WitchApprenticeQuest ) - { - if ( qs.IsObjectiveInProgress( typeof( FindApprenticeObjective ) ) ) - { - PlaySound( 0x259 ); - PlaySound( 0x206 ); - qs.AddConversation( new HagDuringCorpseSearchConversation() ); - } - else - { - QuestObjective obj = qs.FindObjective( typeof( FindGrizeldaAboutMurderObjective ) ); + if (qs is WitchApprenticeQuest) + { + if (qs.IsObjectiveInProgress(typeof(FindApprenticeObjective))) + { + PlaySound(0x259); + PlaySound(0x206); + qs.AddConversation(new HagDuringCorpseSearchConversation()); + } + else + { + QuestObjective obj = qs.FindObjective(typeof(FindGrizeldaAboutMurderObjective)); - if ( obj != null && !obj.Completed ) - { - PlaySound( 0x420 ); - PlaySound( 0x20 ); - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( KillImpsObjective ) ) - || qs.IsObjectiveInProgress( typeof( FindZeefzorpulObjective ) ) ) - { - PlaySound( 0x259 ); - PlaySound( 0x206 ); - qs.AddConversation( new HagDuringImpSearchConversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnRecipeObjective ) ); + if (obj != null && !obj.Completed) + { + PlaySound(0x420); + PlaySound(0x20); + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(KillImpsObjective)) + || qs.IsObjectiveInProgress(typeof(FindZeefzorpulObjective))) + { + PlaySound(0x259); + PlaySound(0x206); + qs.AddConversation(new HagDuringImpSearchConversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnRecipeObjective)); - if ( obj != null && !obj.Completed ) - { - PlaySound( 0x258 ); - PlaySound( 0x41B ); - obj.Complete(); - } - else if ( qs.IsObjectiveInProgress( typeof( FindIngredientObjective ) ) ) - { - PlaySound( 0x259 ); - PlaySound( 0x206 ); - qs.AddConversation( new HagDuringIngredientsConversation() ); - } - else - { - obj = qs.FindObjective( typeof( ReturnIngredientsObjective ) ); + if (obj != null && !obj.Completed) + { + PlaySound(0x258); + PlaySound(0x41B); + obj.Complete(); + } + else if (qs.IsObjectiveInProgress(typeof(FindIngredientObjective))) + { + PlaySound(0x259); + PlaySound(0x206); + qs.AddConversation(new HagDuringIngredientsConversation()); + } + else + { + obj = qs.FindObjective(typeof(ReturnIngredientsObjective)); - if ( obj != null && !obj.Completed ) - { - Container cont = GetNewContainer(); + if (obj != null && !obj.Completed) + { + Container cont = GetNewContainer(); - cont.DropItem( new BlackPearl( 30 ) ); - cont.DropItem( new Bloodmoss( 30 ) ); - cont.DropItem( new Garlic( 30 ) ); - cont.DropItem( new Ginseng( 30 ) ); - cont.DropItem( new MandrakeRoot( 30 ) ); - cont.DropItem( new Nightshade( 30 ) ); - cont.DropItem( new SulfurousAsh( 30 ) ); - cont.DropItem( new SpidersSilk( 30 ) ); + cont.DropItem(new BlackPearl(30)); + cont.DropItem(new Bloodmoss(30)); + cont.DropItem(new Garlic(30)); + cont.DropItem(new Ginseng(30)); + cont.DropItem(new MandrakeRoot(30)); + cont.DropItem(new Nightshade(30)); + cont.DropItem(new SulfurousAsh(30)); + cont.DropItem(new SpidersSilk(30)); - cont.DropItem( new Cauldron() ); - cont.DropItem( new MoonfireBrew() ); - cont.DropItem( new TreasureMap( Utility.RandomMinMax( 1, 4 ), Map ) ); - cont.DropItem( new Gold( 2000, 2200 ) ); + cont.DropItem(new Cauldron()); + cont.DropItem(new MoonfireBrew()); + cont.DropItem(new TreasureMap(Utility.RandomMinMax(1, 4), Map)); + cont.DropItem(new Gold(2000, 2200)); - if ( Utility.RandomBool() ) - { - BaseWeapon weapon = Loot.RandomWeapon(); + if (Utility.RandomBool()) + { + BaseWeapon weapon = Loot.RandomWeapon(); - if ( Core.AOS ) - { - BaseRunicTool.ApplyAttributesTo( weapon, 2, 20, 30 ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled( 2, 3 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled( 2, 3 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled( 2, 3 ); - } + if (Core.AOS) + { + BaseRunicTool.ApplyAttributesTo(weapon, 2, 20, 30); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(2, 3); + weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(2, 3); + weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(2, 3); + } - cont.DropItem( weapon ); - } - else - { - Item item; + cont.DropItem(weapon); + } + else + { + Item item; - if ( Core.AOS ) - { - item = Loot.RandomArmorOrShieldOrJewelry(); + if (Core.AOS) + { + item = Loot.RandomArmorOrShieldOrJewelry(); - if ( item is BaseArmor armor ) - BaseRunicTool.ApplyAttributesTo( armor, 2, 20, 30 ); - else if ( item is BaseJewel jewel ) - BaseRunicTool.ApplyAttributesTo( jewel, 2, 20, 30 ); - } - else - { - BaseArmor armor = Loot.RandomArmorOrShield(); - item = armor; + if (item is BaseArmor armor) + BaseRunicTool.ApplyAttributesTo(armor, 2, 20, 30); + else if (item is BaseJewel jewel) + BaseRunicTool.ApplyAttributesTo(jewel, 2, 20, 30); + } + else + { + BaseArmor armor = Loot.RandomArmorOrShield(); + item = armor; - armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled( 2, 3 ); - armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled( 2, 3 ); - } + armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled(2, 3); + armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled(2, 3); + } - cont.DropItem( item ); - } + cont.DropItem(item); + } - if ( player.BAC > 0 ) - cont.DropItem( new HangoverCure() ); + if (player.BAC > 0) + cont.DropItem(new HangoverCure()); - if ( player.PlaceInBackpack( cont ) ) - { - bool gainedPath = false; + if (player.PlaceInBackpack(cont)) + { + bool gainedPath = false; - if ( VirtueHelper.Award( player, VirtueName.Sacrifice, 250, ref gainedPath ) ) // TODO: Check amount on OSI. - player.SendLocalizedMessage( 1054160 ); // You have gained in sacrifice. + if (VirtueHelper.Award(player, VirtueName.Sacrifice, 250, ref gainedPath) + ) // TODO: Check amount on OSI. + player.SendLocalizedMessage(1054160); // You have gained in sacrifice. - PlaySound( 0x253 ); - PlaySound( 0x20 ); - obj.Complete(); - } - else - { - cont.Delete(); - player.SendLocalizedMessage( 1046260 ); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. - } - } - } - } - } - } - else - { - QuestSystem newQuest = new WitchApprenticeQuest( player ); - bool inRestartPeriod = false; + PlaySound(0x253); + PlaySound(0x20); + obj.Complete(); + } + else + { + cont.Delete(); + player.SendLocalizedMessage( + 1046260); // You need to clear some space in your inventory to continue with the quest. Come back here when you have more space in your inventory. + } + } + } + } + } + } + else + { + QuestSystem newQuest = new WitchApprenticeQuest(player); + bool inRestartPeriod = false; - if ( qs != null ) - { - newQuest.AddConversation( new DontOfferConversation() ); - } - else if ( QuestSystem.CanOfferQuest( player, typeof( WitchApprenticeQuest ), out inRestartPeriod ) ) - { - PlaySound( 0x20 ); - PlaySound( 0x206 ); - newQuest.SendOffer(); - } - else if ( inRestartPeriod ) - { - PlaySound( 0x259 ); - PlaySound( 0x206 ); - newQuest.AddConversation( new RecentlyFinishedConversation() ); - } - } - } + if (qs != null) + { + newQuest.AddConversation(new DontOfferConversation()); + } + else if (QuestSystem.CanOfferQuest(player, typeof(WitchApprenticeQuest), out inRestartPeriod)) + { + PlaySound(0x20); + PlaySound(0x206); + newQuest.SendOffer(); + } + else if (inRestartPeriod) + { + PlaySound(0x259); + PlaySound(0x206); + newQuest.AddConversation(new RecentlyFinishedConversation()); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Zeefzorpul.cs b/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Zeefzorpul.cs index 05c944295..56596dca7 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Zeefzorpul.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Mobiles/Zeefzorpul.cs @@ -2,46 +2,46 @@ using Server.Mobiles; namespace Server.Engines.Quests.Hag { - public class Zeefzorpul : BaseQuester - { - public override string DefaultName => "Zeefzorpul"; + public class Zeefzorpul : BaseQuester + { + public Zeefzorpul() + { + } - public Zeefzorpul() - { - } + public Zeefzorpul(Serial serial) : base(serial) + { + } - public override void InitBody() - { - Body = 0x4A; - } + public override string DefaultName => "Zeefzorpul"; - public Zeefzorpul( Serial serial ) : base( serial ) - { - } + public override void InitBody() + { + Body = 0x4A; + } - public override bool CanTalkTo( PlayerMobile to ) - { - return false; - } + public override bool CanTalkTo(PlayerMobile to) + { + return false; + } - public override void OnTalk( PlayerMobile player, bool contextMenu ) - { - } + public override void OnTalk(PlayerMobile player, bool contextMenu) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } - } -} + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/Objectives.cs b/Scripts/Engines/Quests/Witch Apprentice/Objectives.cs index ae86c00e5..60cae8b05 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/Objectives.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/Objectives.cs @@ -1,457 +1,442 @@ using System; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; namespace Server.Engines.Quests.Hag { - public class FindApprenticeObjective : QuestObjective - { - private static Point3D[] m_CorpseLocations = { - new Point3D( 778, 1158, 0 ), - new Point3D( 698, 1443, 0 ), - new Point3D( 785, 1548, 0 ), - new Point3D( 734, 1504, 0 ), - new Point3D( 819, 1266, 0 ) - }; - - private static Point3D RandomCorpseLocation() - { - int index = Utility.Random( m_CorpseLocations.Length ); - - return m_CorpseLocations[index]; - } - - private Point3D m_CorpseLocation; - - public override object Message => 1055014; - - public Corpse Corpse { get; private set; } - - public FindApprenticeObjective( bool init ) - { - if ( init ) - m_CorpseLocation = RandomCorpseLocation(); - } - - public FindApprenticeObjective() - { - } - - public override void CheckProgress() - { - PlayerMobile player = System.From; - Map map = player.Map; - - if ( ( Corpse == null || Corpse.Deleted ) && ( map == Map.Trammel || map == Map.Felucca ) && player.InRange( m_CorpseLocation, 8 ) ) - { - Corpse = new HagApprenticeCorpse(); - Corpse.MoveToWorld( m_CorpseLocation, map ); - - Effects.SendLocationEffect( m_CorpseLocation, map, 0x3728, 10, 10 ); - Effects.PlaySound( m_CorpseLocation, map, 0x1FE ); - - Mobile imp = new Zeefzorpul(); - imp.MoveToWorld( m_CorpseLocation, map ); - - // * You see a strange imp stealing a scrap of paper from the bloodied corpse * - Corpse.SendLocalizedMessageTo( player, 1055049 ); - - Timer.DelayCall( TimeSpan.FromSeconds( 3.0 ), new TimerStateCallback( DeleteImp ), imp ); - } - } - - private void DeleteImp( object imp ) - { - if ( imp is Mobile m && !m.Deleted ) - { - Effects.SendLocationEffect( m.Location, m.Map, 0x3728, 10, 10 ); - Effects.PlaySound( m.Location, m.Map, 0x1FE ); - - m.Delete(); - } - } - - public override void OnComplete() - { - System.AddConversation( new ApprenticeCorpseConversation() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 1: - { - m_CorpseLocation = reader.ReadPoint3D(); - goto case 0; - } - case 0: - { - Corpse = (Corpse) reader.ReadItem(); - break; - } - } - - if ( version == 0 ) - m_CorpseLocation = RandomCorpseLocation(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - if ( Corpse != null && Corpse.Deleted ) - Corpse = null; - - writer.WriteEncodedInt( (int) 1 ); // version - - writer.Write( (Point3D) m_CorpseLocation ); - writer.Write( (Item) Corpse ); - } - } - - public class FindGrizeldaAboutMurderObjective : QuestObjective - { - public override object Message => 1055015; + public class FindApprenticeObjective : QuestObjective + { + private static Point3D[] m_CorpseLocations = + { + new Point3D(778, 1158, 0), + new Point3D(698, 1443, 0), + new Point3D(785, 1548, 0), + new Point3D(734, 1504, 0), + new Point3D(819, 1266, 0) + }; + + private Point3D m_CorpseLocation; + + public FindApprenticeObjective(bool init) + { + if (init) + m_CorpseLocation = RandomCorpseLocation(); + } + + public FindApprenticeObjective() + { + } + + public override object Message => 1055014; + + public Corpse Corpse{ get; private set; } + + private static Point3D RandomCorpseLocation() + { + int index = Utility.Random(m_CorpseLocations.Length); + + return m_CorpseLocations[index]; + } + + public override void CheckProgress() + { + PlayerMobile player = System.From; + Map map = player.Map; + + if ((Corpse == null || Corpse.Deleted) && (map == Map.Trammel || map == Map.Felucca) && + player.InRange(m_CorpseLocation, 8)) + { + Corpse = new HagApprenticeCorpse(); + Corpse.MoveToWorld(m_CorpseLocation, map); + + Effects.SendLocationEffect(m_CorpseLocation, map, 0x3728, 10, 10); + Effects.PlaySound(m_CorpseLocation, map, 0x1FE); + + Mobile imp = new Zeefzorpul(); + imp.MoveToWorld(m_CorpseLocation, map); + + // * You see a strange imp stealing a scrap of paper from the bloodied corpse * + Corpse.SendLocalizedMessageTo(player, 1055049); + + Timer.DelayCall(TimeSpan.FromSeconds(3.0), new TimerStateCallback(DeleteImp), imp); + } + } + + private void DeleteImp(object imp) + { + if (imp is Mobile m && !m.Deleted) + { + Effects.SendLocationEffect(m.Location, m.Map, 0x3728, 10, 10); + Effects.PlaySound(m.Location, m.Map, 0x1FE); + + m.Delete(); + } + } + + public override void OnComplete() + { + System.AddConversation(new ApprenticeCorpseConversation()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 1: + { + m_CorpseLocation = reader.ReadPoint3D(); + goto case 0; + } + case 0: + { + Corpse = (Corpse)reader.ReadItem(); + break; + } + } + + if (version == 0) + m_CorpseLocation = RandomCorpseLocation(); + } + + public override void ChildSerialize(GenericWriter writer) + { + if (Corpse != null && Corpse.Deleted) + Corpse = null; + + writer.WriteEncodedInt(1); // version + + writer.Write(m_CorpseLocation); + writer.Write(Corpse); + } + } + + public class FindGrizeldaAboutMurderObjective : QuestObjective + { + public override object Message => 1055015; - public FindGrizeldaAboutMurderObjective() - { - } + public override void OnComplete() + { + System.AddConversation(new MurderConversation()); + } + } - public override void OnComplete() - { - System.AddConversation( new MurderConversation() ); - } - } - - public class KillImpsObjective : QuestObjective - { - private int m_MaxProgress; - - public override object Message => 1055016; - - public override int MaxProgress => m_MaxProgress; + public class KillImpsObjective : QuestObjective + { + private int m_MaxProgress; - public KillImpsObjective( bool init ) - { - if ( init ) - m_MaxProgress = Utility.RandomMinMax( 1, 4 ); - } - - public KillImpsObjective() - { - } + public KillImpsObjective(bool init) + { + if (init) + m_MaxProgress = Utility.RandomMinMax(1, 4); + } + + public KillImpsObjective() + { + } + + public override object Message => 1055016; - public override bool IgnoreYoungProtection( Mobile from ) - { - if ( !Completed && from is Imp ) - return true; + public override int MaxProgress => m_MaxProgress; - return false; - } + public override bool IgnoreYoungProtection(Mobile from) + { + if (!Completed && from is Imp) + return true; - public override void OnKill( BaseCreature creature, Container corpse ) - { - if ( creature is Imp ) - CurProgress++; - } + return false; + } - public override void OnComplete() - { - PlayerMobile from = System.From; + public override void OnKill(BaseCreature creature, Container corpse) + { + if (creature is Imp) + CurProgress++; + } - Point3D loc = WitchApprenticeQuest.RandomZeefzorpulLocation(); - - MapItem mapItem = new MapItem(); - mapItem.SetDisplay( loc.X - 200, loc.Y - 200, loc.X + 200, loc.Y + 200, 200, 200 ); - mapItem.AddWorldPin( loc.X, loc.Y ); - from.AddToBackpack( mapItem ); + public override void OnComplete() + { + PlayerMobile from = System.From; - from.AddToBackpack( new MagicFlute() ); - - from.SendLocalizedMessage( 1055061 ); // You have received a map and a magic flute. - - System.AddConversation( new ImpDeathConversation( loc ) ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - m_MaxProgress = reader.ReadInt(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (int) m_MaxProgress ); - } - } - - public class FindZeefzorpulObjective : QuestObjective - { - public override object Message => 1055017; - - public Point3D ImpLocation { get; private set; } - - public FindZeefzorpulObjective( Point3D impLocation ) - { - ImpLocation = impLocation; - } - - public FindZeefzorpulObjective() - { - } - - public override void OnComplete() - { - Mobile from = System.From; - Map map = from.Map; - - Effects.SendLocationEffect( ImpLocation, map, 0x3728, 10, 10 ); - Effects.PlaySound( ImpLocation, map, 0x1FE ); - - Mobile imp = new Zeefzorpul(); - imp.MoveToWorld( ImpLocation, map ); - - imp.Direction = imp.GetDirectionTo( from ); - - Timer.DelayCall( TimeSpan.FromSeconds( 3.0 ), new TimerStateCallback( DeleteImp ), imp ); - } - - private void DeleteImp( object imp ) - { - if ( imp is Mobile m && !m.Deleted ) - { - Effects.SendLocationEffect( m.Location, m.Map, 0x3728, 10, 10 ); - Effects.PlaySound( m.Location, m.Map, 0x1FE ); - - m.Delete(); - } - - System.From.SendLocalizedMessage( 1055062 ); // You have received the Magic Brew Recipe. - - System.AddConversation( new ZeefzorpulConversation() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - ImpLocation = reader.ReadPoint3D(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (Point3D) ImpLocation ); - } - } - - public class ReturnRecipeObjective : QuestObjective - { - public override object Message => 1055018; - - public ReturnRecipeObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new RecipeConversation() ); - } - } - - public class FindIngredientObjective : QuestObjective - { - public override object Message - { - get - { - if ( !BlackheartMet ) - { - switch ( Step ) - { - case 1: - /* You must gather each ingredient on the Hag's list so that she can cook - * up her vile Magic Brew. The first ingredient is : - */ - return 1055019; - case 2: - /* You must gather each ingredient on the Hag's list so that she can cook - * up her vile Magic Brew. The second ingredient is : - */ - return 1055044; - default: - /* You must gather each ingredient on the Hag's list so that she can cook - * up her vile Magic Brew. The final ingredient is : - */ - return 1055045; - } - } - - /* You are still attempting to obtain a jug of Captain Blackheart's - * Whiskey, but the drunkard Captain refuses to share his unique brew. - * You must prove your worthiness as a pirate to Blackheart before he'll - * offer you a jug. - */ - return 1055055; - } - } - - public override int MaxProgress - { - get - { - IngredientInfo info = IngredientInfo.Get( Ingredient ); - - return info.Quantity; - } - } - - public Ingredient[] Ingredients { get; private set; } - - public Ingredient Ingredient => Ingredients[Ingredients.Length - 1]; - public int Step => Ingredients.Length; - public bool BlackheartMet { get; private set; } - - public FindIngredientObjective( Ingredient[] oldIngredients ) : this( oldIngredients, false ) - { - } - - public FindIngredientObjective( Ingredient[] oldIngredients, bool blackheartMet ) - { - if ( !blackheartMet ) - { - Ingredients = new Ingredient[oldIngredients.Length + 1]; - - for ( int i = 0; i < oldIngredients.Length; i++ ) - Ingredients[i] = oldIngredients[i]; - - Ingredients[Ingredients.Length - 1] = IngredientInfo.RandomIngredient( oldIngredients ); - } - else - { - Ingredients = new Ingredient[oldIngredients.Length]; - - for ( int i = 0; i < oldIngredients.Length; i++ ) - Ingredients[i] = oldIngredients[i]; - } - - BlackheartMet = blackheartMet; - } - - public FindIngredientObjective() - { - } - - public override void RenderProgress( BaseQuestGump gump ) - { - if ( !Completed ) - { - IngredientInfo info = IngredientInfo.Get( Ingredient ); - - gump.AddHtmlLocalized( 70, 260, 270, 100, info.Name, BaseQuestGump.Blue, false, false ); - gump.AddLabel( 70, 280, 0x64, CurProgress.ToString() ); - gump.AddLabel( 100, 280, 0x64, "/" ); - gump.AddLabel( 130, 280, 0x64, info.Quantity.ToString() ); - } - else - { - base.RenderProgress( gump ); - } - } - - public override bool IgnoreYoungProtection( Mobile from ) - { - if ( Completed ) - return false; - - IngredientInfo info = IngredientInfo.Get( Ingredient ); - Type fromType = from.GetType(); - - for ( int i = 0; i < info.Creatures.Length; i++ ) - { - if ( fromType == info.Creatures[i] ) - return true; - } - - return false; - } - - public override void OnKill( BaseCreature creature, Container corpse ) - { - IngredientInfo info = IngredientInfo.Get( Ingredient ); - - for ( int i = 0; i < info.Creatures.Length; i++ ) - { - Type type = info.Creatures[i]; - - if ( creature.GetType() == type ) - { - System.From.SendLocalizedMessage( 1055043, "#" + info.Name ); // You gather a ~1_INGREDIENT_NAME~ from the corpse. - - CurProgress++; - - break; - } - } - } - - public override void OnComplete() - { - if ( Ingredient != Ingredient.Whiskey ) - { - NextStep(); - } - } - - public void NextStep() - { - System.From.SendLocalizedMessage( 1055046 ); // You have completed your current task on the Hag's Magic Brew Recipe list. - - if ( Step < 3 ) - System.AddObjective( new FindIngredientObjective( Ingredients ) ); - else - System.AddObjective( new ReturnIngredientsObjective() ); - } - - public override void ChildDeserialize( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - Ingredients = new Ingredient[reader.ReadEncodedInt()]; - for ( int i = 0; i < Ingredients.Length; i++ ) - Ingredients[i] = (Ingredient) reader.ReadEncodedInt(); - - BlackheartMet = reader.ReadBool(); - } - - public override void ChildSerialize( GenericWriter writer ) - { - writer.WriteEncodedInt( (int) 0 ); // version - - writer.WriteEncodedInt( (int) Ingredients.Length ); - for ( int i = 0; i < Ingredients.Length; i++ ) - writer.WriteEncodedInt( (int) Ingredients[i] ); - - writer.Write( (bool) BlackheartMet ); - } - } - - public class ReturnIngredientsObjective : QuestObjective - { - public override object Message => 1055050; - - public ReturnIngredientsObjective() - { - } - - public override void OnComplete() - { - System.AddConversation( new EndConversation() ); - } - } -} + Point3D loc = WitchApprenticeQuest.RandomZeefzorpulLocation(); + + MapItem mapItem = new MapItem(); + mapItem.SetDisplay(loc.X - 200, loc.Y - 200, loc.X + 200, loc.Y + 200, 200, 200); + mapItem.AddWorldPin(loc.X, loc.Y); + from.AddToBackpack(mapItem); + + from.AddToBackpack(new MagicFlute()); + + from.SendLocalizedMessage(1055061); // You have received a map and a magic flute. + + System.AddConversation(new ImpDeathConversation(loc)); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + m_MaxProgress = reader.ReadInt(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(m_MaxProgress); + } + } + + public class FindZeefzorpulObjective : QuestObjective + { + public FindZeefzorpulObjective(Point3D impLocation) + { + ImpLocation = impLocation; + } + + public FindZeefzorpulObjective() + { + } + + public override object Message => 1055017; + + public Point3D ImpLocation{ get; private set; } + + public override void OnComplete() + { + Mobile from = System.From; + Map map = from.Map; + + Effects.SendLocationEffect(ImpLocation, map, 0x3728, 10, 10); + Effects.PlaySound(ImpLocation, map, 0x1FE); + + Mobile imp = new Zeefzorpul(); + imp.MoveToWorld(ImpLocation, map); + + imp.Direction = imp.GetDirectionTo(from); + + Timer.DelayCall(TimeSpan.FromSeconds(3.0), new TimerStateCallback(DeleteImp), imp); + } + + private void DeleteImp(object imp) + { + if (imp is Mobile m && !m.Deleted) + { + Effects.SendLocationEffect(m.Location, m.Map, 0x3728, 10, 10); + Effects.PlaySound(m.Location, m.Map, 0x1FE); + + m.Delete(); + } + + System.From.SendLocalizedMessage(1055062); // You have received the Magic Brew Recipe. + + System.AddConversation(new ZeefzorpulConversation()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + ImpLocation = reader.ReadPoint3D(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.Write(ImpLocation); + } + } + + public class ReturnRecipeObjective : QuestObjective + { + public override object Message => 1055018; + + public override void OnComplete() + { + System.AddConversation(new RecipeConversation()); + } + } + + public class FindIngredientObjective : QuestObjective + { + public FindIngredientObjective(Ingredient[] oldIngredients) : this(oldIngredients, false) + { + } + + public FindIngredientObjective(Ingredient[] oldIngredients, bool blackheartMet) + { + if (!blackheartMet) + { + Ingredients = new Ingredient[oldIngredients.Length + 1]; + + for (int i = 0; i < oldIngredients.Length; i++) + Ingredients[i] = oldIngredients[i]; + + Ingredients[Ingredients.Length - 1] = IngredientInfo.RandomIngredient(oldIngredients); + } + else + { + Ingredients = new Ingredient[oldIngredients.Length]; + + for (int i = 0; i < oldIngredients.Length; i++) + Ingredients[i] = oldIngredients[i]; + } + + BlackheartMet = blackheartMet; + } + + public FindIngredientObjective() + { + } + + public override object Message + { + get + { + if (!BlackheartMet) + switch (Step) + { + case 1: + /* You must gather each ingredient on the Hag's list so that she can cook + * up her vile Magic Brew. The first ingredient is : + */ + return 1055019; + case 2: + /* You must gather each ingredient on the Hag's list so that she can cook + * up her vile Magic Brew. The second ingredient is : + */ + return 1055044; + default: + /* You must gather each ingredient on the Hag's list so that she can cook + * up her vile Magic Brew. The final ingredient is : + */ + return 1055045; + } + + /* You are still attempting to obtain a jug of Captain Blackheart's + * Whiskey, but the drunkard Captain refuses to share his unique brew. + * You must prove your worthiness as a pirate to Blackheart before he'll + * offer you a jug. + */ + return 1055055; + } + } + + public override int MaxProgress + { + get + { + IngredientInfo info = IngredientInfo.Get(Ingredient); + + return info.Quantity; + } + } + + public Ingredient[] Ingredients{ get; private set; } + + public Ingredient Ingredient => Ingredients[Ingredients.Length - 1]; + public int Step => Ingredients.Length; + public bool BlackheartMet{ get; private set; } + + public override void RenderProgress(BaseQuestGump gump) + { + if (!Completed) + { + IngredientInfo info = IngredientInfo.Get(Ingredient); + + gump.AddHtmlLocalized(70, 260, 270, 100, info.Name, BaseQuestGump.Blue, false, false); + gump.AddLabel(70, 280, 0x64, CurProgress.ToString()); + gump.AddLabel(100, 280, 0x64, "/"); + gump.AddLabel(130, 280, 0x64, info.Quantity.ToString()); + } + else + { + base.RenderProgress(gump); + } + } + + public override bool IgnoreYoungProtection(Mobile from) + { + if (Completed) + return false; + + IngredientInfo info = IngredientInfo.Get(Ingredient); + Type fromType = from.GetType(); + + for (int i = 0; i < info.Creatures.Length; i++) + if (fromType == info.Creatures[i]) + return true; + + return false; + } + + public override void OnKill(BaseCreature creature, Container corpse) + { + IngredientInfo info = IngredientInfo.Get(Ingredient); + + for (int i = 0; i < info.Creatures.Length; i++) + { + Type type = info.Creatures[i]; + + if (creature.GetType() == type) + { + System.From.SendLocalizedMessage(1055043, + "#" + info.Name); // You gather a ~1_INGREDIENT_NAME~ from the corpse. + + CurProgress++; + + break; + } + } + } + + public override void OnComplete() + { + if (Ingredient != Ingredient.Whiskey) NextStep(); + } + + public void NextStep() + { + System.From.SendLocalizedMessage( + 1055046); // You have completed your current task on the Hag's Magic Brew Recipe list. + + if (Step < 3) + System.AddObjective(new FindIngredientObjective(Ingredients)); + else + System.AddObjective(new ReturnIngredientsObjective()); + } + + public override void ChildDeserialize(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + Ingredients = new Ingredient[reader.ReadEncodedInt()]; + for (int i = 0; i < Ingredients.Length; i++) + Ingredients[i] = (Ingredient)reader.ReadEncodedInt(); + + BlackheartMet = reader.ReadBool(); + } + + public override void ChildSerialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(Ingredients.Length); + for (int i = 0; i < Ingredients.Length; i++) + writer.WriteEncodedInt((int)Ingredients[i]); + + writer.Write(BlackheartMet); + } + } + + public class ReturnIngredientsObjective : QuestObjective + { + public override object Message => 1055050; + + public override void OnComplete() + { + System.AddConversation(new EndConversation()); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Quests/Witch Apprentice/WitchApprenticeQuest.cs b/Scripts/Engines/Quests/Witch Apprentice/WitchApprenticeQuest.cs index 2ff628647..a6bef283e 100644 --- a/Scripts/Engines/Quests/Witch Apprentice/WitchApprenticeQuest.cs +++ b/Scripts/Engines/Quests/Witch Apprentice/WitchApprenticeQuest.cs @@ -3,88 +3,90 @@ using Server.Mobiles; namespace Server.Engines.Quests.Hag { - public class WitchApprenticeQuest : QuestSystem - { - private static Type[] m_TypeReferenceTable = { - typeof( FindApprenticeObjective ), - typeof( FindGrizeldaAboutMurderObjective ), - typeof( KillImpsObjective ), - typeof( FindZeefzorpulObjective ), - typeof( ReturnRecipeObjective ), - typeof( FindIngredientObjective ), - typeof( ReturnIngredientsObjective ), - typeof( DontOfferConversation ), - typeof( AcceptConversation ), - typeof( HagDuringCorpseSearchConversation ), - typeof( ApprenticeCorpseConversation ), - typeof( MurderConversation ), - typeof( HagDuringImpSearchConversation ), - typeof( ImpDeathConversation ), - typeof( ZeefzorpulConversation ), - typeof( RecipeConversation ), - typeof( HagDuringIngredientsConversation ), - typeof( BlackheartFirstConversation ), - typeof( BlackheartNoPirateConversation ), - typeof( BlackheartPirateConversation ), - typeof( EndConversation ), - typeof( RecentlyFinishedConversation ) - }; + public class WitchApprenticeQuest : QuestSystem + { + private static Type[] m_TypeReferenceTable = + { + typeof(FindApprenticeObjective), + typeof(FindGrizeldaAboutMurderObjective), + typeof(KillImpsObjective), + typeof(FindZeefzorpulObjective), + typeof(ReturnRecipeObjective), + typeof(FindIngredientObjective), + typeof(ReturnIngredientsObjective), + typeof(DontOfferConversation), + typeof(AcceptConversation), + typeof(HagDuringCorpseSearchConversation), + typeof(ApprenticeCorpseConversation), + typeof(MurderConversation), + typeof(HagDuringImpSearchConversation), + typeof(ImpDeathConversation), + typeof(ZeefzorpulConversation), + typeof(RecipeConversation), + typeof(HagDuringIngredientsConversation), + typeof(BlackheartFirstConversation), + typeof(BlackheartNoPirateConversation), + typeof(BlackheartPirateConversation), + typeof(EndConversation), + typeof(RecentlyFinishedConversation) + }; - public override Type[] TypeReferenceTable => m_TypeReferenceTable; + private static Point3D[] m_ZeefzorpulLocations = + { + new Point3D(1226, 1573, 0), + new Point3D(1929, 1148, 0), + new Point3D(1366, 2723, 0), + new Point3D(1675, 2984, 0), + new Point3D(2177, 3367, 10), + new Point3D(1171, 3594, 0), + new Point3D(1010, 2667, 5), + new Point3D(1591, 2156, 5), + new Point3D(2592, 464, 60), + new Point3D(474, 1654, 0), + new Point3D(897, 2411, 0), + new Point3D(1471, 2505, 5), + new Point3D(1257, 872, 16), + new Point3D(2581, 1118, 0), + new Point3D(2513, 1102, 0), + new Point3D(1608, 3371, 0), + new Point3D(4687, 1179, 0), + new Point3D(3704, 2196, 20), + new Point3D(3346, 572, 0), + new Point3D(569, 1309, 0) + }; - public override object Name => 1055042; + public WitchApprenticeQuest(PlayerMobile from) : base(from) + { + } - public override object OfferMessage => 1055001; + // Serialization + public WitchApprenticeQuest() + { + } - public override TimeSpan RestartDelay => TimeSpan.FromMinutes( 5.0 ); - public override bool IsTutorial => false; + public override Type[] TypeReferenceTable => m_TypeReferenceTable; - public override int Picture => 0x15D3; + public override object Name => 1055042; - public WitchApprenticeQuest( PlayerMobile from ) : base( from ) - { - } + public override object OfferMessage => 1055001; - // Serialization - public WitchApprenticeQuest() - { - } + public override TimeSpan RestartDelay => TimeSpan.FromMinutes(5.0); + public override bool IsTutorial => false; - public override void Accept() - { - base.Accept(); + public override int Picture => 0x15D3; - AddConversation( new AcceptConversation() ); - } + public override void Accept() + { + base.Accept(); - private static Point3D[] m_ZeefzorpulLocations = { - new Point3D( 1226, 1573, 0 ), - new Point3D( 1929, 1148, 0 ), - new Point3D( 1366, 2723, 0 ), - new Point3D( 1675, 2984, 0 ), - new Point3D( 2177, 3367, 10 ), - new Point3D( 1171, 3594, 0 ), - new Point3D( 1010, 2667, 5 ), - new Point3D( 1591, 2156, 5 ), - new Point3D( 2592, 464, 60 ), - new Point3D( 474, 1654, 0 ), - new Point3D( 897, 2411, 0 ), - new Point3D( 1471, 2505, 5 ), - new Point3D( 1257, 872, 16 ), - new Point3D( 2581, 1118, 0 ), - new Point3D( 2513, 1102, 0 ), - new Point3D( 1608, 3371, 0 ), - new Point3D( 4687, 1179, 0 ), - new Point3D( 3704, 2196, 20 ), - new Point3D( 3346, 572, 0 ), - new Point3D( 569, 1309, 0 ) - }; + AddConversation(new AcceptConversation()); + } - public static Point3D RandomZeefzorpulLocation() - { - int index = Utility.Random( m_ZeefzorpulLocations.Length ); + public static Point3D RandomZeefzorpulLocation() + { + int index = Utility.Random(m_ZeefzorpulLocations.Length); - return m_ZeefzorpulLocations[index]; - } - } -} + return m_ZeefzorpulLocations[index]; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/RemoteAdmin/Network.cs b/Scripts/Engines/RemoteAdmin/Network.cs index 5619e4e45..d16eb52d4 100644 --- a/Scripts/Engines/RemoteAdmin/Network.cs +++ b/Scripts/Engines/RemoteAdmin/Network.cs @@ -1,277 +1,283 @@ using System; -using System.Text; using System.Collections; +using System.IO; +using System.Text; using Server.Accounting; +using Server.Items; +using Server.Misc; using Server.Network; namespace Server.RemoteAdmin { - public class AdminNetwork - { - private const string ProtocolVersion = "2"; + public class AdminNetwork + { + private const string ProtocolVersion = "2"; - private static ArrayList m_Auth = new ArrayList(); - private static bool m_NewLine = true; - private static StringBuilder m_ConsoleData = new StringBuilder(); + private const string DateFormat = "MMMM dd hh:mm:ss.f tt"; - private const string DateFormat = "MMMM dd hh:mm:ss.f tt"; + private static ArrayList m_Auth = new ArrayList(); + private static bool m_NewLine = true; + private static StringBuilder m_ConsoleData = new StringBuilder(); - public static void Configure() - { - PacketHandlers.Register( 0xF1, 0, false, OnReceive ); + public static void Configure() + { + PacketHandlers.Register(0xF1, 0, false, OnReceive); #if !MONO - Core.MultiConsoleOut.Add( new EventTextWriter( OnConsoleChar, OnConsoleLine, OnConsoleString ) ); + Core.MultiConsoleOut.Add(new EventTextWriter(OnConsoleChar, OnConsoleLine, OnConsoleString)); #endif - Timer.DelayCall( TimeSpan.FromMinutes( 2.5 ), TimeSpan.FromMinutes( 2.5 ), CleanUp ); - } + Timer.DelayCall(TimeSpan.FromMinutes(2.5), TimeSpan.FromMinutes(2.5), CleanUp); + } - public static void OnConsoleString( string str ) - { - string outStr; - if ( m_NewLine ) - { - outStr = $"[{DateTime.UtcNow.ToString(DateFormat)}]: {str}"; - m_NewLine = false; - } - else - { - outStr = str; - } + public static void OnConsoleString(string str) + { + string outStr; + if (m_NewLine) + { + outStr = $"[{DateTime.UtcNow.ToString(DateFormat)}]: {str}"; + m_NewLine = false; + } + else + { + outStr = str; + } - m_ConsoleData.Append( outStr ); - RoughTrimConsoleData(); + m_ConsoleData.Append(outStr); + RoughTrimConsoleData(); - SendToAll( outStr ); - } + SendToAll(outStr); + } - public static void OnConsoleChar( char ch ) - { - if ( m_NewLine ) - { - string outStr; - outStr = $"[{DateTime.UtcNow.ToString(DateFormat)}]: {ch}"; + public static void OnConsoleChar(char ch) + { + if (m_NewLine) + { + string outStr; + outStr = $"[{DateTime.UtcNow.ToString(DateFormat)}]: {ch}"; - m_ConsoleData.Append( outStr ); - SendToAll( outStr ); + m_ConsoleData.Append(outStr); + SendToAll(outStr); - m_NewLine = false; - } - else - { - m_ConsoleData.Append( ch ); - SendToAll( ch ); - } + m_NewLine = false; + } + else + { + m_ConsoleData.Append(ch); + SendToAll(ch); + } - RoughTrimConsoleData(); - } + RoughTrimConsoleData(); + } - public static void OnConsoleLine( string line ) - { - string outStr; - if ( m_NewLine ) - outStr = $"[{DateTime.UtcNow.ToString(DateFormat)}]: {line}{Console.Out.NewLine}"; - else - outStr = $"{line}{Console.Out.NewLine}"; + public static void OnConsoleLine(string line) + { + string outStr; + if (m_NewLine) + outStr = $"[{DateTime.UtcNow.ToString(DateFormat)}]: {line}{Console.Out.NewLine}"; + else + outStr = $"{line}{Console.Out.NewLine}"; - m_ConsoleData.Append( outStr ); - RoughTrimConsoleData(); + m_ConsoleData.Append(outStr); + RoughTrimConsoleData(); - SendToAll( outStr ); + SendToAll(outStr); - m_NewLine = true; - } + m_NewLine = true; + } - static void SendToAll( string outStr ) - { - SendToAll( new ConsoleData( outStr ) ); - } + private static void SendToAll(string outStr) + { + SendToAll(new ConsoleData(outStr)); + } - static void SendToAll( char ch ) - { - SendToAll( new ConsoleData( ch ) ); - } + private static void SendToAll(char ch) + { + SendToAll(new ConsoleData(ch)); + } - static void SendToAll( ConsoleData packet ) - { - packet.Acquire(); - for ( int i = 0; i < m_Auth.Count; i++ ) - ((NetState)m_Auth[i]).Send( packet ); - packet.Release(); - } + private static void SendToAll(ConsoleData packet) + { + packet.Acquire(); + for (int i = 0; i < m_Auth.Count; i++) + ((NetState)m_Auth[i]).Send(packet); + packet.Release(); + } - static void RoughTrimConsoleData() - { - if ( m_ConsoleData.Length >= 4096 ) - m_ConsoleData.Remove( 0, 2048 ); - } + private static void RoughTrimConsoleData() + { + if (m_ConsoleData.Length >= 4096) + m_ConsoleData.Remove(0, 2048); + } - static void TightTrimConsoleData() - { - if ( m_ConsoleData.Length > 1024 ) - m_ConsoleData.Remove( 0, m_ConsoleData.Length - 1024 ); - } + private static void TightTrimConsoleData() + { + if (m_ConsoleData.Length > 1024) + m_ConsoleData.Remove(0, m_ConsoleData.Length - 1024); + } - public static void OnReceive( NetState state, PacketReader pvSrc ) - { - byte cmd = pvSrc.ReadByte(); - if ( cmd == 0x02 ) - { - Authenticate( state, pvSrc ); - } - else if ( cmd == 0xFE ) - { - state.Send( new CompactServerInfo() ); - state.Dispose(); - } - else if ( cmd == 0xFF ) - { - string statStr = - $", Name={Misc.ServerList.ServerName}, Age={(int) (DateTime.UtcNow - Items.Clock.ServerStart).TotalHours}, Clients={NetState.Instances.Count}, Items={World.Items.Count}, Chars={World.Mobiles.Count}, Mem={(int) (GC.GetTotalMemory(false) / 1024)}K, Ver={ProtocolVersion}"; - state.Send( new UOGInfo( statStr ) ); - state.Dispose(); - } - else if ( !IsAuth( state ) ) - { - Console.WriteLine( "ADMIN: Unauthorized packet from {0}, disconnecting", state ); - Disconnect( state ); - } - else - { - if ( !RemoteAdminHandlers.Handle( cmd, state, pvSrc ) ) - Disconnect( state ); - } - } + public static void OnReceive(NetState state, PacketReader pvSrc) + { + byte cmd = pvSrc.ReadByte(); + if (cmd == 0x02) + { + Authenticate(state, pvSrc); + } + else if (cmd == 0xFE) + { + state.Send(new CompactServerInfo()); + state.Dispose(); + } + else if (cmd == 0xFF) + { + string statStr = + $", Name={ServerList.ServerName}, Age={(int)(DateTime.UtcNow - Clock.ServerStart).TotalHours}, Clients={NetState.Instances.Count}, Items={World.Items.Count}, Chars={World.Mobiles.Count}, Mem={(int)(GC.GetTotalMemory(false) / 1024)}K, Ver={ProtocolVersion}"; + state.Send(new UOGInfo(statStr)); + state.Dispose(); + } + else if (!IsAuth(state)) + { + Console.WriteLine("ADMIN: Unauthorized packet from {0}, disconnecting", state); + Disconnect(state); + } + else + { + if (!RemoteAdminHandlers.Handle(cmd, state, pvSrc)) + Disconnect(state); + } + } - private static void DelayedDisconnect( NetState state ) - { - Timer.DelayCall( TimeSpan.FromSeconds( 15.0 ), new TimerStateCallback( Disconnect ), state ); - } + private static void DelayedDisconnect(NetState state) + { + Timer.DelayCall(TimeSpan.FromSeconds(15.0), new TimerStateCallback(Disconnect), state); + } - private static void Disconnect( object state ) - { - m_Auth.Remove( state ); - ((NetState)state).Dispose(); - } + private static void Disconnect(object state) + { + m_Auth.Remove(state); + ((NetState)state).Dispose(); + } - public static void Authenticate( NetState state, PacketReader pvSrc ) - { - string user = pvSrc.ReadString( 30 ); - string pw = pvSrc.ReadString( 30 ); + public static void Authenticate(NetState state, PacketReader pvSrc) + { + string user = pvSrc.ReadString(30); + string pw = pvSrc.ReadString(30); - if ( !(Accounts.GetAccount( user ) is Account a) ) - { - state.Send( new Login( LoginResponse.NoUser ) ); - Console.WriteLine( "ADMIN: Invalid username '{0}' from {1}", user, state ); - DelayedDisconnect( state ); - } - else if ( !a.HasAccess( state ) ) - { - state.Send( new Login( LoginResponse.BadIP ) ); - Console.WriteLine( "ADMIN: Access to '{0}' from {1} denied.", user, state ); - DelayedDisconnect( state ); - } - else if ( !a.CheckPassword( pw ) ) - { - state.Send( new Login( LoginResponse.BadPass ) ); - Console.WriteLine( "ADMIN: Invalid password for user '{0}' from {1}", user, state ); - DelayedDisconnect( state ); - } - else if ( a.AccessLevel < AccessLevel.Administrator || a.Banned ) - { - Console.WriteLine( "ADMIN: Account '{0}' does not have admin access. Connection Denied.", user ); - state.Send( new Login( LoginResponse.NoAccess ) ); - DelayedDisconnect( state ); - } - else - { - Console.WriteLine( "ADMIN: Access granted to '{0}' from {1}", user, state ); - state.Account = a; - a.LogAccess( state ); - a.LastLogin = DateTime.UtcNow; + if (!(Accounts.GetAccount(user) is Account a)) + { + state.Send(new Login(LoginResponse.NoUser)); + Console.WriteLine("ADMIN: Invalid username '{0}' from {1}", user, state); + DelayedDisconnect(state); + } + else if (!a.HasAccess(state)) + { + state.Send(new Login(LoginResponse.BadIP)); + Console.WriteLine("ADMIN: Access to '{0}' from {1} denied.", user, state); + DelayedDisconnect(state); + } + else if (!a.CheckPassword(pw)) + { + state.Send(new Login(LoginResponse.BadPass)); + Console.WriteLine("ADMIN: Invalid password for user '{0}' from {1}", user, state); + DelayedDisconnect(state); + } + else if (a.AccessLevel < AccessLevel.Administrator || a.Banned) + { + Console.WriteLine("ADMIN: Account '{0}' does not have admin access. Connection Denied.", user); + state.Send(new Login(LoginResponse.NoAccess)); + DelayedDisconnect(state); + } + else + { + Console.WriteLine("ADMIN: Access granted to '{0}' from {1}", user, state); + state.Account = a; + a.LogAccess(state); + a.LastLogin = DateTime.UtcNow; - state.Send( new Login( LoginResponse.OK ) ); - TightTrimConsoleData(); - state.Send( Compress( new ConsoleData( m_ConsoleData.ToString() ) ) ); - m_Auth.Add( state ); - } - } + state.Send(new Login(LoginResponse.OK)); + TightTrimConsoleData(); + state.Send(Compress(new ConsoleData(m_ConsoleData.ToString()))); + m_Auth.Add(state); + } + } - public static bool IsAuth( NetState state ) - { - return m_Auth.Contains( state ); - } + public static bool IsAuth(NetState state) + { + return m_Auth.Contains(state); + } - private static void CleanUp() - {//remove dead instances from m_Auth - ArrayList list = new ArrayList(); - for (int i=0;i 100 && length < 60000 ) - { - byte[] dest = new byte[(int)(length * 1.001) + 10]; - int destSize = dest.Length; + if (length > 100 && length < 60000) + { + byte[] dest = new byte[(int)(length * 1.001) + 10]; + int destSize = dest.Length; - ZLibError error = Compression.Pack( dest, ref destSize, source, length, ZLibQuality.Default ); + ZLibError error = Compression.Pack(dest, ref destSize, source, length, ZLibQuality.Default); - if ( error != ZLibError.Okay ) - { - Console.WriteLine( "WARNING: Unable to compress admin packet, zlib error: {0}", error ); - return p; - } + if (error != ZLibError.Okay) + { + Console.WriteLine("WARNING: Unable to compress admin packet, zlib error: {0}", error); + return p; + } - return new AdminCompressedPacket( dest, destSize, length ); - } + return new AdminCompressedPacket(dest, destSize, length); + } - return p; - } - } + return p; + } + } - public class EventTextWriter : System.IO.TextWriter - { - public delegate void OnConsoleChar( char ch ); - public delegate void OnConsoleLine( string line ); - public delegate void OnConsoleStr( string str ); + public class EventTextWriter : TextWriter + { + public delegate void OnConsoleChar(char ch); - private OnConsoleChar m_OnChar; - private OnConsoleLine m_OnLine; - private OnConsoleStr m_OnStr; + public delegate void OnConsoleLine(string line); - public EventTextWriter( OnConsoleChar onChar, OnConsoleLine onLine, OnConsoleStr onStr ) - { - m_OnChar = onChar; - m_OnLine = onLine; - m_OnStr = onStr; - } + public delegate void OnConsoleStr(string str); - public override void Write( char ch ) - { - m_OnChar?.Invoke( ch ); - } + private OnConsoleChar m_OnChar; + private OnConsoleLine m_OnLine; + private OnConsoleStr m_OnStr; - public override void Write( string str ) - { - m_OnStr?.Invoke( str ); - } + public EventTextWriter(OnConsoleChar onChar, OnConsoleLine onLine, OnConsoleStr onStr) + { + m_OnChar = onChar; + m_OnLine = onLine; + m_OnStr = onStr; + } - public override void WriteLine( string line ) - { - m_OnLine?.Invoke( line ); - } + public override Encoding Encoding => Encoding.ASCII; - public override Encoding Encoding => Encoding.ASCII; - } -} + public override void Write(char ch) + { + m_OnChar?.Invoke(ch); + } + + public override void Write(string str) + { + m_OnStr?.Invoke(str); + } + + public override void WriteLine(string line) + { + m_OnLine?.Invoke(line); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/RemoteAdmin/PacketHandlers.cs b/Scripts/Engines/RemoteAdmin/PacketHandlers.cs index 041145063..4f3c526fc 100644 --- a/Scripts/Engines/RemoteAdmin/PacketHandlers.cs +++ b/Scripts/Engines/RemoteAdmin/PacketHandlers.cs @@ -1,234 +1,257 @@ using System; using System.Collections; -using Server.Network; using Server.Accounting; +using Server.Network; namespace Server.RemoteAdmin { - public class RemoteAdminHandlers - { - public enum AcctSearchType : byte - { - Username = 0, - IP = 1, - } + public class RemoteAdminHandlers + { + public enum AcctSearchType : byte + { + Username = 0, + IP = 1 + } - private static OnPacketReceive[] m_Handlers = new OnPacketReceive[256]; + private static OnPacketReceive[] m_Handlers = new OnPacketReceive[256]; - static RemoteAdminHandlers() - { - //0x02 = login request, handled by AdminNetwork - Register( 0x04, ServerInfoRequest ); - Register( 0x05, AccountSearch ); - Register( 0x06, RemoveAccount ); - Register( 0x07, UpdateAccount ); - } + static RemoteAdminHandlers() + { + //0x02 = login request, handled by AdminNetwork + Register(0x04, ServerInfoRequest); + Register(0x05, AccountSearch); + Register(0x06, RemoveAccount); + Register(0x07, UpdateAccount); + } - public static void Register( byte command, OnPacketReceive handler ) - { - m_Handlers[command] = handler; - } + public static void Register(byte command, OnPacketReceive handler) + { + m_Handlers[command] = handler; + } - public static bool Handle( byte command, NetState state, PacketReader pvSrc ) - { - if ( m_Handlers[command] == null ) - { - Console.WriteLine( "ADMIN: Invalid packet 0x{0:X2} from {1}, disconnecting", command, state ); - return false; - } + public static bool Handle(byte command, NetState state, PacketReader pvSrc) + { + if (m_Handlers[command] == null) + { + Console.WriteLine("ADMIN: Invalid packet 0x{0:X2} from {1}, disconnecting", command, state); + return false; + } - m_Handlers[command]( state, pvSrc ); - return true; - } + m_Handlers[command](state, pvSrc); + return true; + } - private static void ServerInfoRequest( NetState state, PacketReader pvSrc ) - { - state.Send( AdminNetwork.Compress( new ServerInfo() ) ); - } + private static void ServerInfoRequest(NetState state, PacketReader pvSrc) + { + state.Send(AdminNetwork.Compress(new ServerInfo())); + } - private static void AccountSearch( NetState state, PacketReader pvSrc ) - { - AcctSearchType type = (AcctSearchType)pvSrc.ReadByte(); - string term = pvSrc.ReadString(); + private static void AccountSearch(NetState state, PacketReader pvSrc) + { + AcctSearchType type = (AcctSearchType)pvSrc.ReadByte(); + string term = pvSrc.ReadString(); - if ( type == AcctSearchType.IP && !Utility.IsValidIP( term ) ) - { - state.Send( new MessageBoxMessage( "Invalid search term.\nThe IP sent was not valid.", "Invalid IP" ) ); - return; - } + if (type == AcctSearchType.IP && !Utility.IsValidIP(term)) + { + state.Send(new MessageBoxMessage("Invalid search term.\nThe IP sent was not valid.", "Invalid IP")); + return; + } - term = term.ToUpper(); + term = term.ToUpper(); - ArrayList list = new ArrayList(); + ArrayList list = new ArrayList(); - foreach ( Account a in Accounts.GetAccounts() ) - { - if ( !CanAccessAccount( state.Account, a ) ) continue; + foreach (Account a in Accounts.GetAccounts()) + { + if (!CanAccessAccount(state.Account, a)) continue; - switch ( type ) - { - case AcctSearchType.Username: - { - if ( a.Username.ToUpper().IndexOf( term ) != -1 ) - list.Add( a ); - break; - } - case AcctSearchType.IP: - { - for( int i=0;i 0 ) - { - if ( list.Count <= 25 ) - state.Send( AdminNetwork.Compress( new AccountSearchResults( list ) ) ); - else - state.Send( new MessageBoxMessage( "There were more than 25 matches to your search.\nNarrow the search parameters and try again.", "Too Many Results" ) ); - } - else - { - state.Send( new MessageBoxMessage( "There were no results to your search.\nPlease try again.", "No Matches" ) ); - } - } + break; + } + } + } - static bool CanAccessAccount( IAccount beholder, IAccount beheld ) - { - return beholder.AccessLevel == AccessLevel.Owner || beheld.AccessLevel < beholder.AccessLevel; // Cannot see accounts of equal or greater access level unless Owner - } + if (list.Count > 0) + { + if (list.Count <= 25) + state.Send(AdminNetwork.Compress(new AccountSearchResults(list))); + else + state.Send(new MessageBoxMessage( + "There were more than 25 matches to your search.\nNarrow the search parameters and try again.", + "Too Many Results")); + } + else + { + state.Send(new MessageBoxMessage("There were no results to your search.\nPlease try again.", "No Matches")); + } + } - private static void RemoveAccount( NetState state, PacketReader pvSrc ) - { - if ( state.Account.AccessLevel < AccessLevel.Administrator ) - { - state.Send( new MessageBoxMessage( "You do not have permission to delete accounts.", "Account Access Exception" ) ); - return; - } + private static bool CanAccessAccount(IAccount beholder, IAccount beheld) + { + return beholder.AccessLevel == AccessLevel.Owner || + beheld.AccessLevel < + beholder.AccessLevel; // Cannot see accounts of equal or greater access level unless Owner + } - IAccount a = Accounts.GetAccount( pvSrc.ReadString() ); + private static void RemoveAccount(NetState state, PacketReader pvSrc) + { + if (state.Account.AccessLevel < AccessLevel.Administrator) + { + state.Send(new MessageBoxMessage("You do not have permission to delete accounts.", + "Account Access Exception")); + return; + } - if ( a == null ) - { - state.Send( new MessageBoxMessage( "The account could not be found (and thus was not deleted).", "Account Not Found" ) ); - } - else if ( !CanAccessAccount( state.Account, a ) ) - { - state.Send( new MessageBoxMessage( "You cannot delete an account with an access level greater than or equal to your own.", "Account Access Exception" ) ); - } - else if ( a == state.Account ) - { - state.Send( new MessageBoxMessage( "You may not delete your own account.", "Not Allowed" ) ); - } - else - { - RemoteAdminLogging.WriteLine( state, "Deleted Account {0}", a ); - a.Delete(); - state.Send( new MessageBoxMessage( "The requested account (and all it's characters) has been deleted.", "Account Deleted" ) ); - } - } + IAccount a = Accounts.GetAccount(pvSrc.ReadString()); - private static void UpdateAccount( NetState state, PacketReader pvSrc ) - { - if ( state.Account.AccessLevel < AccessLevel.Administrator ) - { - state.Send( new MessageBoxMessage( "You do not have permission to edit accounts.", "Account Access Exception" ) ); - return; - } + if (a == null) + { + state.Send(new MessageBoxMessage("The account could not be found (and thus was not deleted).", + "Account Not Found")); + } + else if (!CanAccessAccount(state.Account, a)) + { + state.Send(new MessageBoxMessage( + "You cannot delete an account with an access level greater than or equal to your own.", + "Account Access Exception")); + } + else if (a == state.Account) + { + state.Send(new MessageBoxMessage("You may not delete your own account.", "Not Allowed")); + } + else + { + RemoteAdminLogging.WriteLine(state, "Deleted Account {0}", a); + a.Delete(); + state.Send(new MessageBoxMessage("The requested account (and all it's characters) has been deleted.", + "Account Deleted")); + } + } - string username = pvSrc.ReadString(); - string pass = pvSrc.ReadString(); + private static void UpdateAccount(NetState state, PacketReader pvSrc) + { + if (state.Account.AccessLevel < AccessLevel.Administrator) + { + state.Send(new MessageBoxMessage("You do not have permission to edit accounts.", + "Account Access Exception")); + return; + } - Account a = Accounts.GetAccount( username ) as Account; + string username = pvSrc.ReadString(); + string pass = pvSrc.ReadString(); - if ( a != null && !CanAccessAccount( state.Account, a ) ) - { - state.Send( new MessageBoxMessage( "You cannot edit an account with an access level greater than or equal to your own.", "Account Access Exception" ) ); - } - else - { - bool CreatedAccount = false; - bool UpdatedPass = false; - bool oldbanned = a?.Banned ?? false; - AccessLevel oldAcessLevel = a?.AccessLevel ?? 0; + Account a = Accounts.GetAccount(username) as Account; - if ( a == null ) - { - a = new Account( username, pass ); - CreatedAccount = true; - } - else if ( pass != "(hidden)" ) - { - a.SetPassword( pass ); - UpdatedPass = true; - } + if (a != null && !CanAccessAccount(state.Account, a)) + { + state.Send(new MessageBoxMessage( + "You cannot edit an account with an access level greater than or equal to your own.", + "Account Access Exception")); + } + else + { + bool CreatedAccount = false; + bool UpdatedPass = false; + bool oldbanned = a?.Banned ?? false; + AccessLevel oldAcessLevel = a?.AccessLevel ?? 0; - if ( a != state.Account ) - { - AccessLevel newAccessLevel = (AccessLevel)pvSrc.ReadByte(); - if ( a.AccessLevel != newAccessLevel ) - { - if ( newAccessLevel >= state.Account.AccessLevel ) - state.Send( new MessageBoxMessage( "Warning: You may not set an access level greater than or equal to your own.", "Account Access Level update denied." ) ); - else - a.AccessLevel = newAccessLevel; - } - bool newBanned = pvSrc.ReadBoolean(); - if ( newBanned != a.Banned ) - { - oldbanned = a.Banned; - a.Banned = newBanned; - a.Comments.Add( new AccountComment( state.Account.Username, newBanned ? "Banned via Remote Admin" : "Unbanned via Remote Admin" ) ); - } - } - else - { - pvSrc.ReadInt16();//skip both - state.Send( new MessageBoxMessage( "Warning: When editing your own account, Account Status and Access Level cannot be changed.", "Editing Own Account" ) ); - } + if (a == null) + { + a = new Account(username, pass); + CreatedAccount = true; + } + else if (pass != "(hidden)") + { + a.SetPassword(pass); + UpdatedPass = true; + } - ArrayList list = new ArrayList(); - ushort length = pvSrc.ReadUInt16(); - bool invalid = false; - for (int i=0;i= state.Account.AccessLevel) + state.Send(new MessageBoxMessage( + "Warning: You may not set an access level greater than or equal to your own.", + "Account Access Level update denied.")); + else + a.AccessLevel = newAccessLevel; + } - if ( list.Count > 0 ) - a.IPRestrictions = (string[])list.ToArray( typeof( string ) ); - else - a.IPRestrictions = new string[0]; + bool newBanned = pvSrc.ReadBoolean(); + if (newBanned != a.Banned) + { + oldbanned = a.Banned; + a.Banned = newBanned; + a.Comments.Add(new AccountComment(state.Account.Username, + newBanned ? "Banned via Remote Admin" : "Unbanned via Remote Admin")); + } + } + else + { + pvSrc.ReadInt16(); //skip both + state.Send(new MessageBoxMessage( + "Warning: When editing your own account, Account Status and Access Level cannot be changed.", + "Editing Own Account")); + } - if ( invalid ) - state.Send( new MessageBoxMessage( "Warning: one or more of the IP Restrictions you specified was not valid.", "Invalid IP Restriction" ) ); + ArrayList list = new ArrayList(); + ushort length = pvSrc.ReadUInt16(); + bool invalid = false; + for (int i = 0; i < length; i++) + { + string add = pvSrc.ReadString(); + if (Utility.IsValidIP(add)) + list.Add(add); + else + invalid = true; + } - if ( CreatedAccount ) - RemoteAdminLogging.WriteLine( state, "Created account {0} with Access Level {1}", a.Username, a.AccessLevel ); - else - { - string changes = string.Empty; - if ( UpdatedPass ) changes += " Password Changed."; - if ( oldAcessLevel != a.AccessLevel ) changes = - $"{changes} Access level changed from {oldAcessLevel} to {a.AccessLevel}."; - if ( oldbanned != a.Banned ) changes += a.Banned ? " Banned." : " Unbanned."; - RemoteAdminLogging.WriteLine( state, "Updated account {0}:{1}", a.Username, changes ); - } + if (list.Count > 0) + a.IPRestrictions = (string[])list.ToArray(typeof(string)); + else + a.IPRestrictions = new string[0]; - state.Send( new MessageBoxMessage( "Account updated successfully.", "Account Updated" ) ); - } - } - } -} + if (invalid) + state.Send(new MessageBoxMessage( + "Warning: one or more of the IP Restrictions you specified was not valid.", + "Invalid IP Restriction")); + + if (CreatedAccount) + { + RemoteAdminLogging.WriteLine(state, "Created account {0} with Access Level {1}", a.Username, + a.AccessLevel); + } + else + { + string changes = string.Empty; + if (UpdatedPass) changes += " Password Changed."; + if (oldAcessLevel != a.AccessLevel) + changes = + $"{changes} Access level changed from {oldAcessLevel} to {a.AccessLevel}."; + if (oldbanned != a.Banned) changes += a.Banned ? " Banned." : " Unbanned."; + RemoteAdminLogging.WriteLine(state, "Updated account {0}:{1}", a.Username, changes); + } + + state.Send(new MessageBoxMessage("Account updated successfully.", "Account Updated")); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/RemoteAdmin/Packets.cs b/Scripts/Engines/RemoteAdmin/Packets.cs index 998f5899a..dfe6b0788 100644 --- a/Scripts/Engines/RemoteAdmin/Packets.cs +++ b/Scripts/Engines/RemoteAdmin/Packets.cs @@ -1,160 +1,162 @@ using System; using System.Collections; +using Server.Accounting; using Server.Items; using Server.Network; -using Server.Accounting; namespace Server.RemoteAdmin { - public enum LoginResponse : byte - { - NoUser = 0, - BadIP, - BadPass, - NoAccess, - OK - } + public enum LoginResponse : byte + { + NoUser = 0, + BadIP, + BadPass, + NoAccess, + OK + } - public sealed class AdminCompressedPacket : Packet - { - public AdminCompressedPacket( byte[] CompData, int CDLen, int unCompSize ) : base( 0x01 ) - { - EnsureCapacity( 1 + 2 + 2 + CDLen ); - m_Stream.Write( (ushort)unCompSize ); - m_Stream.Write( CompData, 0, CDLen ); - } - } - - public sealed class Login : Packet - { - public Login( LoginResponse resp ) : base( 0x02, 2 ) - { - m_Stream.Write( (byte)resp ); - } - } + public sealed class AdminCompressedPacket : Packet + { + public AdminCompressedPacket(byte[] CompData, int CDLen, int unCompSize) : base(0x01) + { + EnsureCapacity(1 + 2 + 2 + CDLen); + m_Stream.Write((ushort)unCompSize); + m_Stream.Write(CompData, 0, CDLen); + } + } - public sealed class ConsoleData : Packet - { - public ConsoleData( string str ) : base( 0x03 ) - { - EnsureCapacity( 1 + 2 + 1 + str.Length + 1 ); - m_Stream.Write( (byte) 2 ); + public sealed class Login : Packet + { + public Login(LoginResponse resp) : base(0x02, 2) + { + m_Stream.Write((byte)resp); + } + } - m_Stream.WriteAsciiNull( str ); - } + public sealed class ConsoleData : Packet + { + public ConsoleData(string str) : base(0x03) + { + EnsureCapacity(1 + 2 + 1 + str.Length + 1); + m_Stream.Write((byte)2); - public ConsoleData( char ch ) : base( 0x03 ) - { - EnsureCapacity( 1 + 2 + 1 + 1 ); - m_Stream.Write( (byte) 3 ); + m_Stream.WriteAsciiNull(str); + } - m_Stream.Write( (byte) ch ); - } - } + public ConsoleData(char ch) : base(0x03) + { + EnsureCapacity(1 + 2 + 1 + 1); + m_Stream.Write((byte)3); - public sealed class ServerInfo : Packet - { - public ServerInfo() : base( 0x04 ) - { - string netVer = Environment.Version.ToString(); - string os = Environment.OSVersion.ToString(); + m_Stream.Write((byte)ch); + } + } - EnsureCapacity( 1 + 2 + (10*4) + netVer.Length+1 + os.Length+1 ); - int banned = 0; - int active = 0; + public sealed class ServerInfo : Packet + { + public ServerInfo() : base(0x04) + { + string netVer = Environment.Version.ToString(); + string os = Environment.OSVersion.ToString(); - foreach ( Account acct in Accounts.GetAccounts() ) - { - if ( acct.Banned ) - ++banned; - else - ++active; - } + EnsureCapacity(1 + 2 + 10 * 4 + netVer.Length + 1 + os.Length + 1); + int banned = 0; + int active = 0; - m_Stream.Write( (int) active ); - m_Stream.Write( (int) banned ); - m_Stream.Write( (int) Firewall.List.Count ); - m_Stream.Write( (int) NetState.Instances.Count ); + foreach (Account acct in Accounts.GetAccounts()) + if (acct.Banned) + ++banned; + else + ++active; - m_Stream.Write( (int) World.Mobiles.Count ); - m_Stream.Write( (int) Core.ScriptMobiles ); - m_Stream.Write( (int) World.Items.Count ); - m_Stream.Write( (int) Core.ScriptItems ); + m_Stream.Write(active); + m_Stream.Write(banned); + m_Stream.Write(Firewall.List.Count); + m_Stream.Write(NetState.Instances.Count); - m_Stream.Write( (uint)(DateTime.UtcNow - Clock.ServerStart).TotalSeconds ); - m_Stream.Write( (uint) GC.GetTotalMemory( false ) ); // TODO: uint not sufficient for TotalMemory (long). Fix protocol. - m_Stream.WriteAsciiNull( netVer ); - m_Stream.WriteAsciiNull( os ); - } - } + m_Stream.Write(World.Mobiles.Count); + m_Stream.Write(Core.ScriptMobiles); + m_Stream.Write(World.Items.Count); + m_Stream.Write(Core.ScriptItems); - public sealed class AccountSearchResults : Packet - { - public AccountSearchResults( ArrayList results ) : base( 0x05 ) - { - EnsureCapacity( 1 + 2 + 2 ); + m_Stream.Write((uint)(DateTime.UtcNow - Clock.ServerStart).TotalSeconds); + m_Stream.Write( + (uint)GC.GetTotalMemory(false)); // TODO: uint not sufficient for TotalMemory (long). Fix protocol. + m_Stream.WriteAsciiNull(netVer); + m_Stream.WriteAsciiNull(os); + } + } - m_Stream.Write( (byte)results.Count ); - - foreach ( Account a in results ) - { - m_Stream.WriteAsciiNull( a.Username ); + public sealed class AccountSearchResults : Packet + { + public AccountSearchResults(ArrayList results) : base(0x05) + { + EnsureCapacity(1 + 2 + 2); - string pwToSend = a.PlainPassword; + m_Stream.Write((byte)results.Count); - if ( pwToSend == null ) - pwToSend = "(hidden)"; + foreach (Account a in results) + { + m_Stream.WriteAsciiNull(a.Username); - m_Stream.WriteAsciiNull( pwToSend ); - m_Stream.Write( (byte)a.AccessLevel ); - m_Stream.Write( a.Banned ); - unchecked { m_Stream.Write( (uint)a.LastLogin.Ticks ); } // TODO: This doesn't work, uint.MaxValue is only 7 minutes of ticks. Fix protocol. - - m_Stream.Write( (ushort)a.LoginIPs.Length ); - for (int i=0;i> 32) ); // Memory high bytes - m_Stream.Write( (uint)memory ); // Memory low bytes - } - } + m_Stream.Write((ushort)a.IPRestrictions.Length); + for (int i = 0; i < a.IPRestrictions.Length; i++) + m_Stream.WriteAsciiNull(a.IPRestrictions[i]); + } + } + } - public sealed class UOGInfo : Packet - { - public UOGInfo( string str ) : base( 0x52, str.Length+6 ) // 'R' - { - m_Stream.WriteAsciiFixed( "unUO", 4 ); - m_Stream.WriteAsciiNull( str ); - } - } + public sealed class CompactServerInfo : Packet + { + public CompactServerInfo() : base(0x51) + { + EnsureCapacity(1 + 2 + 4 * 4 + 8); - public sealed class MessageBoxMessage : Packet - { - public MessageBoxMessage( string msg, string caption ) : base( 0x08 ) - { - EnsureCapacity( 1 + 2 + msg.Length + 1 + caption.Length + 1 ); + m_Stream.Write(NetState.Instances.Count - 1); // Clients + m_Stream.Write(World.Items.Count); // Items + m_Stream.Write(World.Mobiles.Count); // Mobiles + m_Stream.Write((uint)(DateTime.UtcNow - Clock.ServerStart).TotalSeconds); // Age (seconds) - m_Stream.WriteAsciiNull( msg ); - m_Stream.WriteAsciiNull( caption ); - } - } -} + long memory = GC.GetTotalMemory(false); + m_Stream.Write((uint)(memory >> 32)); // Memory high bytes + m_Stream.Write((uint)memory); // Memory low bytes + } + } + + public sealed class UOGInfo : Packet + { + public UOGInfo(string str) : base(0x52, str.Length + 6) // 'R' + { + m_Stream.WriteAsciiFixed("unUO", 4); + m_Stream.WriteAsciiNull(str); + } + } + + public sealed class MessageBoxMessage : Packet + { + public MessageBoxMessage(string msg, string caption) : base(0x08) + { + EnsureCapacity(1 + 2 + msg.Length + 1 + caption.Length + 1); + + m_Stream.WriteAsciiNull(msg); + m_Stream.WriteAsciiNull(caption); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/RemoteAdmin/RemoteAdminLogging.cs b/Scripts/Engines/RemoteAdmin/RemoteAdminLogging.cs index cccbe096e..8803bdae6 100644 --- a/Scripts/Engines/RemoteAdmin/RemoteAdminLogging.cs +++ b/Scripts/Engines/RemoteAdmin/RemoteAdminLogging.cs @@ -1,97 +1,103 @@ using System; using System.IO; using Server.Accounting; +using Server.Commands; using Server.Network; namespace Server.RemoteAdmin { - public class RemoteAdminLogging - { - const string LogBaseDirectory = "Logs"; - const string LogSubDirectory = "RemoteAdmin"; + public class RemoteAdminLogging + { + private const string LogBaseDirectory = "Logs"; + private const string LogSubDirectory = "RemoteAdmin"; - public static bool Enabled { get; set; } = true; + private static bool Initialized; - public static StreamWriter Output { get; private set; } + public static bool Enabled{ get; set; } = true; - private static bool Initialized; - public static void LazyInitialize() - { - if ( Initialized || !Enabled ) return; - Initialized = true; + public static StreamWriter Output{ get; private set; } - if ( !Directory.Exists( LogBaseDirectory ) ) - Directory.CreateDirectory( LogBaseDirectory ); + public static void LazyInitialize() + { + if (Initialized || !Enabled) return; + Initialized = true; - string directory = Path.Combine( LogBaseDirectory, LogSubDirectory ); + if (!Directory.Exists(LogBaseDirectory)) + Directory.CreateDirectory(LogBaseDirectory); - if ( !Directory.Exists( directory ) ) - Directory.CreateDirectory( directory ); + string directory = Path.Combine(LogBaseDirectory, LogSubDirectory); - try - { - Output = new StreamWriter( Path.Combine( directory, string.Format( LogSubDirectory + "{0}.log", DateTime.UtcNow.ToString( "yyyyMMdd" ) ) ), true ); + if (!Directory.Exists(directory)) + Directory.CreateDirectory(directory); - Output.AutoFlush = true; + try + { + Output = new StreamWriter( + Path.Combine(directory, + string.Format(LogSubDirectory + "{0}.log", DateTime.UtcNow.ToString("yyyyMMdd"))), true); - Output.WriteLine( "##############################" ); - Output.WriteLine( "Log started on {0}", DateTime.UtcNow ); - Output.WriteLine(); - } - catch - { - Utility.PushColor( ConsoleColor.Red ); - Console.WriteLine( "RemoteAdminLogging: Failed to initialize LogWriter." ); - Utility.PopColor(); - Enabled = false; - } - } + Output.AutoFlush = true; - public static object Format( object o ) - { - o = Commands.CommandLogging.Format( o ); - if ( o == null ) - return "(null)"; + Output.WriteLine("##############################"); + Output.WriteLine("Log started on {0}", DateTime.UtcNow); + Output.WriteLine(); + } + catch + { + Utility.PushColor(ConsoleColor.Red); + Console.WriteLine("RemoteAdminLogging: Failed to initialize LogWriter."); + Utility.PopColor(); + Enabled = false; + } + } - return o; - } + public static object Format(object o) + { + o = CommandLogging.Format(o); + if (o == null) + return "(null)"; - public static void WriteLine( NetState state, string format, params object[] args ) - { - for ( int i = 0; i < args.Length; i++ ) - args[i] = Commands.CommandLogging.Format( args[i] ); + return o; + } - WriteLine( state, string.Format( format, args ) ); - } + public static void WriteLine(NetState state, string format, params object[] args) + { + for (int i = 0; i < args.Length; i++) + args[i] = CommandLogging.Format(args[i]); - public static void WriteLine( NetState state, string text ) - { - LazyInitialize(); + WriteLine(state, string.Format(format, args)); + } - if ( !Enabled ) return; + public static void WriteLine(NetState state, string text) + { + LazyInitialize(); - try - { - Account acct = state.Account as Account; - string name = acct == null ? "(UNKNOWN)" : acct.Username; - string accesslevel = acct == null ? "NoAccount" : acct.AccessLevel.ToString(); - string statestr = state == null ? "NULLSTATE" : state.ToString(); + if (!Enabled) return; - Output.WriteLine( "{0}: {1}: {2}: {3}", DateTime.UtcNow, statestr, name, text ); + try + { + Account acct = state.Account as Account; + string name = acct == null ? "(UNKNOWN)" : acct.Username; + string accesslevel = acct == null ? "NoAccount" : acct.AccessLevel.ToString(); + string statestr = state == null ? "NULLSTATE" : state.ToString(); - string path = Core.BaseDirectory; + Output.WriteLine("{0}: {1}: {2}: {3}", DateTime.UtcNow, statestr, name, text); - Commands.CommandLogging.AppendPath( ref path, LogBaseDirectory ); - Commands.CommandLogging.AppendPath( ref path, LogSubDirectory ); - Commands.CommandLogging.AppendPath( ref path, accesslevel ); - path = Path.Combine( path, $"{name}.log"); + string path = Core.BaseDirectory; - using ( StreamWriter sw = new StreamWriter( path, true ) ) - sw.WriteLine( "{0}: {1}: {2}", DateTime.UtcNow, statestr, text ); - } - catch - { - } - } - } -} + CommandLogging.AppendPath(ref path, LogBaseDirectory); + CommandLogging.AppendPath(ref path, LogSubDirectory); + CommandLogging.AppendPath(ref path, accesslevel); + path = Path.Combine(path, $"{name}.log"); + + using (StreamWriter sw = new StreamWriter(path, true)) + { + sw.WriteLine("{0}: {1}: {2}", DateTime.UtcNow, statestr, text); + } + } + catch + { + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Charts/BarGraph.cs b/Scripts/Engines/Reports/Objects/Charts/BarGraph.cs index fe7ad6abe..0cc9931a0 100644 --- a/Scripts/Engines/Reports/Objects/Charts/BarGraph.cs +++ b/Scripts/Engines/Reports/Objects/Charts/BarGraph.cs @@ -3,299 +3,305 @@ using System.Collections; namespace Server.Engines.Reports { - public enum BarGraphRenderMode - { - Bars, - Lines - } + public enum BarGraphRenderMode + { + Bars, + Lines + } - public class BarGraph : Chart - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "bg", Construct ); + public class BarGraph : Chart + { + public BarGraph(string name, string fileName, int ticks, string xTitle, string yTitle, BarGraphRenderMode rm) + { + m_Name = name; + m_FileName = fileName; + Ticks = ticks; + this.xTitle = xTitle; + this.yTitle = yTitle; + RenderMode = rm; + } - private static PersistableObject Construct() - { - return new BarGraph(); - } + private BarGraph() + { + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public int Ticks{ get; set; } - public int Ticks { get; set; } + public BarGraphRenderMode RenderMode{ get; set; } - public BarGraphRenderMode RenderMode { get; set; } + public string xTitle{ get; set; } - public string xTitle { get; set; } + public string yTitle{ get; set; } - public string yTitle { get; set; } + public int FontSize{ get; set; } = 7; - public int FontSize { get; set; } = 7; + public int Interval{ get; set; } = 1; - public int Interval { get; set; } = 1; + public BarRegion[] Regions{ get; set; } - public BarRegion[] Regions { get; set; } + public override void SerializeAttributes(PersistanceWriter op) + { + base.SerializeAttributes(op); - public BarGraph( string name, string fileName, int ticks, string xTitle, string yTitle, BarGraphRenderMode rm ) - { - m_Name = name; - m_FileName = fileName; - Ticks = ticks; - this.xTitle = xTitle; - this.yTitle = yTitle; - RenderMode = rm; - } + op.SetInt32("t", Ticks); + op.SetInt32("r", (int)RenderMode); - private BarGraph() - { - } + op.SetString("x", xTitle); + op.SetString("y", yTitle); - public override void SerializeAttributes( PersistanceWriter op ) - { - base.SerializeAttributes( op ); + op.SetInt32("s", FontSize); + op.SetInt32("i", Interval); + } - op.SetInt32( "t", Ticks ); - op.SetInt32( "r", (int) RenderMode ); + public override void DeserializeAttributes(PersistanceReader ip) + { + base.DeserializeAttributes(ip); - op.SetString( "x", xTitle ); - op.SetString( "y", yTitle ); + Ticks = ip.GetInt32("t"); + RenderMode = (BarGraphRenderMode)ip.GetInt32("r"); - op.SetInt32( "s", FontSize ); - op.SetInt32( "i", Interval ); - } + xTitle = Utility.Intern(ip.GetString("x")); + yTitle = Utility.Intern(ip.GetString("y")); - public override void DeserializeAttributes( PersistanceReader ip ) - { - base.DeserializeAttributes( ip ); + FontSize = ip.GetInt32("s"); + Interval = ip.GetInt32("i"); + } - Ticks = ip.GetInt32( "t" ); - RenderMode = (BarGraphRenderMode) ip.GetInt32( "r" ); + public static int LookupReportValue(Snapshot ss, string reportName, string valueName) + { + for (int j = 0; j < ss.Children.Count; ++j) + { + if (!(ss.Children[j] is Report report) || report.Name != reportName) + continue; - xTitle = Utility.Intern( ip.GetString( "x" ) ); - yTitle = Utility.Intern( ip.GetString( "y" ) ); + for (int k = 0; k < report.Items.Count; ++k) + { + ReportItem item = report.Items[k]; - FontSize = ip.GetInt32( "s" ); - Interval = ip.GetInt32( "i" ); - } + if (item.Values[0].Value == valueName) + return Utility.ToInt32(item.Values[1].Value); + } - public static int LookupReportValue( Snapshot ss, string reportName, string valueName ) - { - for ( int j = 0; j < ss.Children.Count; ++j ) - { - if ( !(ss.Children[j] is Report report) || report.Name != reportName ) - continue; + break; + } - for ( int k = 0; k < report.Items.Count; ++k ) - { - ReportItem item = report.Items[k]; + return -1; + } - if ( item.Values[0].Value == valueName ) - return Utility.ToInt32( item.Values[1].Value ); - } + public static BarGraph DailyAverage(SnapshotHistory history, string reportName, string valueName) + { + int[] totals = new int[24]; + int[] counts = new int[24]; - break; - } + int min = history.Snapshots.Count - 7 * 24; // averages over one week - return -1; - } + if (min < 0) + min = 0; - public static BarGraph DailyAverage( SnapshotHistory history, string reportName, string valueName ) - { - int[] totals = new int[24]; - int[] counts = new int[24]; + for (int i = min; i < history.Snapshots.Count; ++i) + { + Snapshot ss = history.Snapshots[i]; - int min = history.Snapshots.Count - (7 * 24); // averages over one week + int val = LookupReportValue(ss, reportName, valueName); - if ( min < 0 ) - min = 0; + if (val == -1) + continue; - for ( int i = min; i < history.Snapshots.Count; ++i ) - { - Snapshot ss = history.Snapshots[i]; + int hour = ss.TimeStamp.TimeOfDay.Hours; - int val = LookupReportValue( ss, reportName, valueName ); + totals[hour] += val; + counts[hour]++; + } - if ( val == -1 ) - continue; + BarGraph barGraph = new BarGraph("Hourly average " + valueName, "graphs_" + valueName.ToLower() + "_avg", 10, + "Time", valueName, BarGraphRenderMode.Lines); - int hour = ss.TimeStamp.TimeOfDay.Hours; + barGraph.FontSize = 6; - totals[hour] += val; - counts[hour]++; - } + for (int i = 7; i <= totals.Length + 7; ++i) + { + int val; - BarGraph barGraph = new BarGraph( "Hourly average " + valueName, "graphs_" + valueName.ToLower() + "_avg", 10, "Time", valueName, BarGraphRenderMode.Lines ); + if (counts[i % totals.Length] == 0) + val = 0; + else + val = (totals[i % totals.Length] + counts[i % totals.Length] / 2) / counts[i % totals.Length]; - barGraph.FontSize = 6; + int realHours = i % totals.Length; + int hours; - for ( int i = 7; i <= totals.Length+7; ++i ) - { - int val; + if (realHours == 0) + hours = 12; + else if (realHours > 12) + hours = realHours - 12; + else + hours = realHours; - if ( counts[i%totals.Length] == 0 ) - val = 0; - else - val = (totals[i%totals.Length] + (counts[i%totals.Length] / 2)) / counts[i%totals.Length]; + barGraph.Items.Add(hours + (realHours >= 12 ? " PM" : " AM"), val); + } - int realHours = i%totals.Length; - int hours; + return barGraph; + } - if ( realHours == 0 ) - hours = 12; - else if ( realHours > 12 ) - hours = realHours - 12; - else - hours = realHours; + public static BarGraph Growth(SnapshotHistory history, string reportName, string valueName) + { + BarGraph barGraph = new BarGraph("Growth of " + valueName + " over time", + "graphs_" + valueName.ToLower() + "_growth", 10, "Time", valueName, BarGraphRenderMode.Lines); - barGraph.Items.Add( hours + (realHours >= 12 ? " PM" : " AM"), val ); - } + barGraph.FontSize = 6; + barGraph.Interval = 7; - return barGraph; - } + DateTime startPeriod = history.Snapshots[0].TimeStamp.Date + TimeSpan.FromDays(1.0); + DateTime endPeriod = history.Snapshots[history.Snapshots.Count - 1].TimeStamp.Date; - public static BarGraph Growth( SnapshotHistory history, string reportName, string valueName ) - { - BarGraph barGraph = new BarGraph( "Growth of " + valueName + " over time", "graphs_" + valueName.ToLower() + "_growth", 10, "Time", valueName, BarGraphRenderMode.Lines ); + ArrayList regions = new ArrayList(); - barGraph.FontSize = 6; - barGraph.Interval = 7; + DateTime curDate = DateTime.MinValue; + int curPeak = -1; + int curLow = 1000; + int curTotl = 0; + int curCont = 0; + int curValu = 0; - DateTime startPeriod = history.Snapshots[0].TimeStamp.Date + TimeSpan.FromDays( 1.0 ); - DateTime endPeriod = history.Snapshots[history.Snapshots.Count - 1].TimeStamp.Date; + for (int i = 0; i < history.Snapshots.Count; ++i) + { + Snapshot ss = history.Snapshots[i]; + DateTime timeStamp = ss.TimeStamp; - ArrayList regions = new ArrayList(); + if (timeStamp < startPeriod || timeStamp >= endPeriod) + continue; - DateTime curDate = DateTime.MinValue; - int curPeak = -1; - int curLow = 1000; - int curTotl = 0; - int curCont = 0; - int curValu = 0; + int val = LookupReportValue(ss, reportName, valueName); - for ( int i = 0; i < history.Snapshots.Count; ++i ) - { - Snapshot ss = history.Snapshots[i]; - DateTime timeStamp = ss.TimeStamp; + if (val == -1) + continue; - if ( timeStamp < startPeriod || timeStamp >= endPeriod ) - continue; + DateTime thisDate = timeStamp.Date; - int val = LookupReportValue( ss, reportName, valueName ); + if (curDate == DateTime.MinValue) + curDate = thisDate; - if ( val == -1 ) - continue; + curCont++; + curTotl += val; + curValu = curTotl / curCont; - DateTime thisDate = timeStamp.Date; + if (curDate != thisDate && curValu >= 0) + { + string mnthName = thisDate.ToString("MMMM"); - if ( curDate == DateTime.MinValue ) - curDate = thisDate; + if (regions.Count == 0) + { + regions.Add(new BarRegion(barGraph.Items.Count, barGraph.Items.Count, mnthName)); + } + else + { + BarRegion region = (BarRegion)regions[regions.Count - 1]; - curCont++; - curTotl += val; - curValu = curTotl / curCont; + if (region.m_Name == mnthName) + region.m_RangeTo = barGraph.Items.Count; + else + regions.Add(new BarRegion(barGraph.Items.Count, barGraph.Items.Count, mnthName)); + } - if ( curDate != thisDate && curValu >= 0 ) - { - string mnthName = thisDate.ToString( "MMMM" ); + barGraph.Items.Add(thisDate.Day.ToString(), curValu); - if ( regions.Count == 0 ) - { - regions.Add( new BarRegion( barGraph.Items.Count, barGraph.Items.Count, mnthName ) ); - } - else - { - BarRegion region = (BarRegion)regions[regions.Count - 1]; + curPeak = val; + curLow = val; + } + else + { + if (val > curPeak) + curPeak = val; - if ( region.m_Name == mnthName ) - region.m_RangeTo = barGraph.Items.Count; - else - regions.Add( new BarRegion( barGraph.Items.Count, barGraph.Items.Count, mnthName ) ); - } + if (val > 0 && val < curLow) + curLow = val; + } - barGraph.Items.Add( thisDate.Day.ToString(), curValu ); + curDate = thisDate; + } - curPeak = val; - curLow = val; - } - else - { - if ( val > curPeak ) - curPeak = val; + barGraph.Regions = (BarRegion[])regions.ToArray(typeof(BarRegion)); - if ( val > 0 && val < curLow ) - curLow = val; - } + return barGraph; + } - curDate = thisDate; - } + public static BarGraph OverTime(SnapshotHistory history, string reportName, string valueName, int step, int max, + int ival) + { + BarGraph barGraph = new BarGraph(valueName + " over time", "graphs_" + valueName.ToLower() + "_ot", 10, "Time", + valueName, BarGraphRenderMode.Lines); - barGraph.Regions = (BarRegion[])regions.ToArray( typeof( BarRegion ) ); + TimeSpan ts = TimeSpan.FromHours(max * step - 0.5); - return barGraph; - } + DateTime mostRecent = history.Snapshots[history.Snapshots.Count - 1].TimeStamp; + DateTime minTime = mostRecent - ts; - public static BarGraph OverTime( SnapshotHistory history, string reportName, string valueName, int step, int max, int ival ) - { - BarGraph barGraph = new BarGraph( valueName + " over time", "graphs_" + valueName.ToLower() + "_ot", 10, "Time", valueName, BarGraphRenderMode.Lines ); + barGraph.FontSize = 6; + barGraph.Interval = ival; - TimeSpan ts = TimeSpan.FromHours( (max*step)-0.5 ); + ArrayList regions = new ArrayList(); - DateTime mostRecent = history.Snapshots[history.Snapshots.Count - 1].TimeStamp; - DateTime minTime = mostRecent - ts; + for (int i = 0; i < history.Snapshots.Count; ++i) + { + Snapshot ss = history.Snapshots[i]; + DateTime timeStamp = ss.TimeStamp; - barGraph.FontSize = 6; - barGraph.Interval = ival; + if (timeStamp < minTime) + continue; - ArrayList regions = new ArrayList(); + if (i % step != 0) + continue; - for ( int i = 0; i < history.Snapshots.Count; ++i ) - { - Snapshot ss = history.Snapshots[i]; - DateTime timeStamp = ss.TimeStamp; + int val = LookupReportValue(ss, reportName, valueName); - if ( timeStamp < minTime ) - continue; + if (val == -1) + continue; - if ( (i % step) != 0 ) - continue; + int realHours = timeStamp.TimeOfDay.Hours; + int hours; - int val = LookupReportValue( ss, reportName, valueName ); + if (realHours == 0) + hours = 12; + else if (realHours > 12) + hours = realHours - 12; + else + hours = realHours; - if ( val == -1 ) - continue; + string dayName = timeStamp.DayOfWeek.ToString(); - int realHours = timeStamp.TimeOfDay.Hours; - int hours; + if (regions.Count == 0) + { + regions.Add(new BarRegion(barGraph.Items.Count, barGraph.Items.Count, dayName)); + } + else + { + BarRegion region = (BarRegion)regions[regions.Count - 1]; - if ( realHours == 0 ) - hours = 12; - else if ( realHours > 12 ) - hours = realHours - 12; - else - hours = realHours; + if (region.m_Name == dayName) + region.m_RangeTo = barGraph.Items.Count; + else + regions.Add(new BarRegion(barGraph.Items.Count, barGraph.Items.Count, dayName)); + } - string dayName = timeStamp.DayOfWeek.ToString(); + barGraph.Items.Add(hours + (realHours >= 12 ? " PM" : " AM"), val); + } - if ( regions.Count == 0 ) - { - regions.Add( new BarRegion( barGraph.Items.Count, barGraph.Items.Count, dayName ) ); - } - else - { - BarRegion region = (BarRegion) regions[regions.Count - 1]; + barGraph.Regions = (BarRegion[])regions.ToArray(typeof(BarRegion)); - if ( region.m_Name == dayName ) - region.m_RangeTo = barGraph.Items.Count; - else - regions.Add( new BarRegion( barGraph.Items.Count, barGraph.Items.Count, dayName ) ); - } + return barGraph; + } - barGraph.Items.Add( hours + (realHours >= 12 ? " PM" : " AM"), val ); - } + #region Type Identification - barGraph.Regions = (BarRegion[])regions.ToArray( typeof( BarRegion ) ); + public static readonly PersistableType ThisTypeID = new PersistableType("bg", Construct); - return barGraph; - } - } -} + private static PersistableObject Construct() + { + return new BarGraph(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Charts/Chart.cs b/Scripts/Engines/Reports/Objects/Charts/Chart.cs index d2ce667a4..9509e4e7e 100644 --- a/Scripts/Engines/Reports/Objects/Charts/Chart.cs +++ b/Scripts/Engines/Reports/Objects/Charts/Chart.cs @@ -1,46 +1,52 @@ namespace Server.Engines.Reports { - public abstract class Chart : PersistableObject - { - protected string m_Name; - protected string m_FileName; - protected ChartItemCollection m_Items; + public abstract class Chart : PersistableObject + { + protected string m_FileName; + protected ChartItemCollection m_Items; + protected string m_Name; - public string Name{ get => m_Name; - set => m_Name = value; - } - public string FileName{ get => m_FileName; - set => m_FileName = value; - } - public ChartItemCollection Items => m_Items; + public Chart() + { + m_Items = new ChartItemCollection(); + } - public Chart() - { - m_Items = new ChartItemCollection(); - } + public string Name + { + get => m_Name; + set => m_Name = value; + } - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetString( "n", m_Name ); - op.SetString( "f", m_FileName ); - } + public string FileName + { + get => m_FileName; + set => m_FileName = value; + } - public override void DeserializeAttributes( PersistanceReader ip ) - { - m_Name = Utility.Intern( ip.GetString( "n" ) ); - m_FileName = Utility.Intern( ip.GetString( "f" ) ); - } + public ChartItemCollection Items => m_Items; - public override void SerializeChildren( PersistanceWriter op ) - { - for ( int i = 0; i < m_Items.Count; ++i ) - m_Items[i].Serialize( op ); - } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetString("n", m_Name); + op.SetString("f", m_FileName); + } - public override void DeserializeChildren( PersistanceReader ip ) - { - while ( ip.HasChild ) - m_Items.Add( ip.GetChild() as ChartItem ); - } - } + public override void DeserializeAttributes(PersistanceReader ip) + { + m_Name = Utility.Intern(ip.GetString("n")); + m_FileName = Utility.Intern(ip.GetString("f")); + } + + public override void SerializeChildren(PersistanceWriter op) + { + for (int i = 0; i < m_Items.Count; ++i) + m_Items[i].Serialize(op); + } + + public override void DeserializeChildren(PersistanceReader ip) + { + while (ip.HasChild) + m_Items.Add(ip.GetChild() as ChartItem); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Charts/ChartItem.cs b/Scripts/Engines/Reports/Objects/Charts/ChartItem.cs index 0faed7bfd..a3ba24b00 100644 --- a/Scripts/Engines/Reports/Objects/Charts/ChartItem.cs +++ b/Scripts/Engines/Reports/Objects/Charts/ChartItem.cs @@ -1,42 +1,44 @@ namespace Server.Engines.Reports { - public class ChartItem : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "ci", Construct ); + public class ChartItem : PersistableObject + { + private ChartItem() + { + } - private static PersistableObject Construct() - { - return new ChartItem(); - } + public ChartItem(string name, int value) + { + Name = name; + Value = value; + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public string Name{ get; set; } - public string Name { get; set; } + public int Value{ get; set; } - public int Value { get; set; } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetString("n", Name); + op.SetInt32("v", Value); + } - private ChartItem() - { - } + public override void DeserializeAttributes(PersistanceReader ip) + { + Name = Utility.Intern(ip.GetString("n")); + Value = ip.GetInt32("v"); + } - public ChartItem( string name, int value ) - { - Name = name; - Value = value; - } + #region Type Identification - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetString( "n", Name ); - op.SetInt32( "v", Value ); - } + public static readonly PersistableType ThisTypeID = new PersistableType("ci", Construct); - public override void DeserializeAttributes( PersistanceReader ip ) - { - Name = Utility.Intern( ip.GetString( "n" ) ); - Value = ip.GetInt32( "v" ); - } - } -} + private static PersistableObject Construct() + { + return new ChartItem(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Charts/ChartItemCollection.cs b/Scripts/Engines/Reports/Objects/Charts/ChartItemCollection.cs index ee0121c4b..b87df7344 100644 --- a/Scripts/Engines/Reports/Objects/Charts/ChartItemCollection.cs +++ b/Scripts/Engines/Reports/Objects/Charts/ChartItemCollection.cs @@ -8,187 +8,180 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.ChartItem. + /// + public class ChartItemCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.ChartItem. + /// Gets or sets the value of the Server.Engines.Reports.ChartItem at a specific position in the ChartItemCollection. /// - public class ChartItemCollection : CollectionBase + public ChartItem this[int index] { - - /// - /// Default constructor. - /// - public ChartItemCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.ChartItem at a specific position in the ChartItemCollection. - /// - public ChartItem this[int index] - { - get => ((ChartItem)(List[index])); - set => List[index] = value; - } - - public int Add( string name, int value ) - { - return Add( new ChartItem( name, value ) ); - } - - /// - /// Append a Server.Engines.Reports.ChartItem entry to this collection. - /// - /// Server.Engines.Reports.ChartItem instance. - /// The position into which the new element was inserted. - public int Add(ChartItem value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.ChartItem instance is in this collection. - /// - /// Server.Engines.Reports.ChartItem instance to search for. - /// True if the Server.Engines.Reports.ChartItem instance is in the collection; otherwise false. - public bool Contains(ChartItem value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.ChartItem instance is in this collection. - /// - /// Server.Engines.Reports.ChartItem instance to find. - /// The zero-based index of the specified Server.Engines.Reports.ChartItem instance. If the object is not found, the return value is -1. - public int IndexOf(ChartItem value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.ChartItem instance from this collection. - /// - /// The Server.Engines.Reports.ChartItem instance to remove. - public void Remove(ChartItem value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.ChartItem instance. - /// - /// An Server.Engines.Reports.ChartItem's enumerator. - public new ChartItemCollectionEnumerator GetEnumerator() - { - return new ChartItemCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.ChartItem instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.ChartItem instance to insert. - public void Insert(int index, ChartItem value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.ChartItem. - /// - public class ChartItemCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private ChartItem _currentElement; - - /// - /// Collection to enumerate. - /// - private ChartItemCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal ChartItemCollectionEnumerator(ChartItemCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.ChartItem object in the enumerated ChartItemCollection currently indexed by this instance. - /// - public ChartItem Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (ChartItem)List[index]; + set => List[index] = value; } -} + + public int Add(string name, int value) + { + return Add(new ChartItem(name, value)); + } + + /// + /// Append a Server.Engines.Reports.ChartItem entry to this collection. + /// + /// Server.Engines.Reports.ChartItem instance. + /// The position into which the new element was inserted. + public int Add(ChartItem value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.ChartItem instance is in this collection. + /// + /// Server.Engines.Reports.ChartItem instance to search for. + /// True if the Server.Engines.Reports.ChartItem instance is in the collection; otherwise false. + public bool Contains(ChartItem value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.ChartItem instance is in this collection. + /// + /// Server.Engines.Reports.ChartItem instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.ChartItem instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(ChartItem value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.ChartItem instance from this collection. + /// + /// The Server.Engines.Reports.ChartItem instance to remove. + public void Remove(ChartItem value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.ChartItem instance. + /// + /// An Server.Engines.Reports.ChartItem's enumerator. + public new ChartItemCollectionEnumerator GetEnumerator() + { + return new ChartItemCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.ChartItem instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.ChartItem instance to insert. + public void Insert(int index, ChartItem value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.ChartItem. + /// + public class ChartItemCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private ChartItemCollection _collection; + + /// + /// Current element pointed to. + /// + private ChartItem _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal ChartItemCollectionEnumerator(ChartItemCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.ChartItem object in the enumerated ChartItemCollection currently indexed by this instance. + /// + public ChartItem Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Charts/PieChart.cs b/Scripts/Engines/Reports/Objects/Charts/PieChart.cs index d50814964..6bbc532cd 100644 --- a/Scripts/Engines/Reports/Objects/Charts/PieChart.cs +++ b/Scripts/Engines/Reports/Objects/Charts/PieChart.cs @@ -1,43 +1,45 @@ namespace Server.Engines.Reports { - public class PieChart : Chart - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "pc", Construct ); + public class PieChart : Chart + { + public PieChart(string name, string fileName, bool showPercents) + { + m_Name = name; + m_FileName = fileName; + ShowPercents = showPercents; + } - private static PersistableObject Construct() - { - return new PieChart(); - } + private PieChart() + { + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public bool ShowPercents{ get; set; } - public bool ShowPercents { get; set; } + public override void SerializeAttributes(PersistanceWriter op) + { + base.SerializeAttributes(op); - public PieChart( string name, string fileName, bool showPercents ) - { - m_Name = name; - m_FileName = fileName; - ShowPercents = showPercents; - } + op.SetBoolean("p", ShowPercents); + } - private PieChart() - { - } + public override void DeserializeAttributes(PersistanceReader ip) + { + base.DeserializeAttributes(ip); - public override void SerializeAttributes( PersistanceWriter op ) - { - base.SerializeAttributes( op ); + ShowPercents = ip.GetBoolean("p"); + } - op.SetBoolean( "p", ShowPercents ); - } + #region Type Identification - public override void DeserializeAttributes( PersistanceReader ip ) - { - base.DeserializeAttributes( ip ); + public static readonly PersistableType ThisTypeID = new PersistableType("pc", Construct); - ShowPercents = ip.GetBoolean( "p" ); - } - } -} + private static PersistableObject Construct() + { + return new PieChart(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/ItemValue.cs b/Scripts/Engines/Reports/Objects/Reports/ItemValue.cs index 09ae5c817..d2f045b48 100644 --- a/Scripts/Engines/Reports/Objects/Reports/ItemValue.cs +++ b/Scripts/Engines/Reports/Objects/Reports/ItemValue.cs @@ -1,52 +1,57 @@ namespace Server.Engines.Reports { - public class ItemValue : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "iv", Construct ); + public class ItemValue : PersistableObject + { + private string m_Value; - private static PersistableObject Construct() - { - return new ItemValue(); - } + private ItemValue() + { + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public ItemValue(string value) : this(value, null) + { + } - private string m_Value; + public ItemValue(string value, string format) + { + m_Value = value; + Format = format; + } - public string Value{ get => m_Value; - set => m_Value = value; - } - public string Format { get; set; } + public string Value + { + get => m_Value; + set => m_Value = value; + } - private ItemValue() - { - } + public string Format{ get; set; } - public ItemValue( string value ) : this( value, null ) - { - } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetString("v", m_Value); + op.SetString("f", Format); + } - public ItemValue( string value, string format ) - { - m_Value = value; - Format = format; - } + public override void DeserializeAttributes(PersistanceReader ip) + { + m_Value = ip.GetString("v"); + Format = Utility.Intern(ip.GetString("f")); - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetString( "v", m_Value ); - op.SetString( "f", Format ); - } + if (Format == null) + Utility.Intern(ref m_Value); + } - public override void DeserializeAttributes( PersistanceReader ip ) - { - m_Value = ip.GetString( "v" ); - Format = Utility.Intern( ip.GetString( "f" ) ); + #region Type Identification - if ( Format == null ) - Utility.Intern( ref m_Value ); - } - } -} + public static readonly PersistableType ThisTypeID = new PersistableType("iv", Construct); + + private static PersistableObject Construct() + { + return new ItemValue(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/ItemValueCollection.cs b/Scripts/Engines/Reports/Objects/Reports/ItemValueCollection.cs index f65fa958f..621d28b9d 100644 --- a/Scripts/Engines/Reports/Objects/Reports/ItemValueCollection.cs +++ b/Scripts/Engines/Reports/Objects/Reports/ItemValueCollection.cs @@ -8,192 +8,185 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.ItemValue. + /// + public class ItemValueCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.ItemValue. + /// Gets or sets the value of the Server.Engines.Reports.ItemValue at a specific position in the ItemValueCollection. /// - public class ItemValueCollection : CollectionBase + public ItemValue this[int index] { - - /// - /// Default constructor. - /// - public ItemValueCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.ItemValue at a specific position in the ItemValueCollection. - /// - public ItemValue this[int index] - { - get => ((ItemValue)(List[index])); - set => List[index] = value; - } - - public int Add( string value ) - { - return Add( new ItemValue( value ) ); - } - - public int Add( string value, string format ) - { - return Add( new ItemValue( value, format ) ); - } - - /// - /// Append a Server.Engines.Reports.ItemValue entry to this collection. - /// - /// Server.Engines.Reports.ItemValue instance. - /// The position into which the new element was inserted. - public int Add(ItemValue value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.ItemValue instance is in this collection. - /// - /// Server.Engines.Reports.ItemValue instance to search for. - /// True if the Server.Engines.Reports.ItemValue instance is in the collection; otherwise false. - public bool Contains(ItemValue value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.ItemValue instance is in this collection. - /// - /// Server.Engines.Reports.ItemValue instance to find. - /// The zero-based index of the specified Server.Engines.Reports.ItemValue instance. If the object is not found, the return value is -1. - public int IndexOf(ItemValue value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.ItemValue instance from this collection. - /// - /// The Server.Engines.Reports.ItemValue instance to remove. - public void Remove(ItemValue value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.ItemValue instance. - /// - /// An Server.Engines.Reports.ItemValue's enumerator. - public new ItemValueCollectionEnumerator GetEnumerator() - { - return new ItemValueCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.ItemValue instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.ItemValue instance to insert. - public void Insert(int index, ItemValue value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.ItemValue. - /// - public class ItemValueCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private ItemValue _currentElement; - - /// - /// Collection to enumerate. - /// - private ItemValueCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal ItemValueCollectionEnumerator(ItemValueCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.ItemValue object in the enumerated ItemValueCollection currently indexed by this instance. - /// - public ItemValue Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (ItemValue)List[index]; + set => List[index] = value; } -} + + public int Add(string value) + { + return Add(new ItemValue(value)); + } + + public int Add(string value, string format) + { + return Add(new ItemValue(value, format)); + } + + /// + /// Append a Server.Engines.Reports.ItemValue entry to this collection. + /// + /// Server.Engines.Reports.ItemValue instance. + /// The position into which the new element was inserted. + public int Add(ItemValue value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.ItemValue instance is in this collection. + /// + /// Server.Engines.Reports.ItemValue instance to search for. + /// True if the Server.Engines.Reports.ItemValue instance is in the collection; otherwise false. + public bool Contains(ItemValue value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.ItemValue instance is in this collection. + /// + /// Server.Engines.Reports.ItemValue instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.ItemValue instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(ItemValue value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.ItemValue instance from this collection. + /// + /// The Server.Engines.Reports.ItemValue instance to remove. + public void Remove(ItemValue value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.ItemValue instance. + /// + /// An Server.Engines.Reports.ItemValue's enumerator. + public new ItemValueCollectionEnumerator GetEnumerator() + { + return new ItemValueCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.ItemValue instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.ItemValue instance to insert. + public void Insert(int index, ItemValue value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.ItemValue. + /// + public class ItemValueCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private ItemValueCollection _collection; + + /// + /// Current element pointed to. + /// + private ItemValue _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal ItemValueCollectionEnumerator(ItemValueCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.ItemValue object in the enumerated ItemValueCollection currently indexed by this instance. + /// + public ItemValue Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/Report.cs b/Scripts/Engines/Reports/Objects/Reports/Report.cs index e63f915c8..3eb8475d9 100644 --- a/Scripts/Engines/Reports/Objects/Reports/Report.cs +++ b/Scripts/Engines/Reports/Objects/Reports/Report.cs @@ -1,70 +1,72 @@ namespace Server.Engines.Reports { - public class Report : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "rp", Construct ); + public class Report : PersistableObject + { + private Report() : this(null, null) + { + } - private static PersistableObject Construct() - { - return new Report(); - } + public Report(string name, string width) + { + Name = name; + Width = width; + Columns = new ReportColumnCollection(); + Items = new ReportItemCollection(); + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public string Name{ get; set; } - public string Name { get; set; } + public string Width{ get; set; } - public string Width { get; set; } + public ReportColumnCollection Columns{ get; } - public ReportColumnCollection Columns { get; } + public ReportItemCollection Items{ get; } - public ReportItemCollection Items { get; } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetString("n", Name); + op.SetString("w", Width); + } - private Report() : this( null, null ) - { - } + public override void DeserializeAttributes(PersistanceReader ip) + { + Name = Utility.Intern(ip.GetString("n")); + Width = Utility.Intern(ip.GetString("w")); + } - public Report( string name, string width ) - { - Name = name; - Width = width; - Columns = new ReportColumnCollection(); - Items = new ReportItemCollection(); - } + public override void SerializeChildren(PersistanceWriter op) + { + for (int i = 0; i < Columns.Count; ++i) + Columns[i].Serialize(op); - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetString( "n", Name ); - op.SetString( "w", Width ); - } + for (int i = 0; i < Items.Count; ++i) + Items[i].Serialize(op); + } - public override void DeserializeAttributes( PersistanceReader ip ) - { - Name = Utility.Intern( ip.GetString( "n" ) ); - Width = Utility.Intern( ip.GetString( "w" ) ); - } + public override void DeserializeChildren(PersistanceReader ip) + { + while (ip.HasChild) + { + PersistableObject child = ip.GetChild(); - public override void SerializeChildren( PersistanceWriter op ) - { - for ( int i = 0; i < Columns.Count; ++i ) - Columns[i].Serialize( op ); + if (child is ReportColumn column) + Columns.Add(column); + else if (child is ReportItem item) + Items.Add(item); + } + } - for ( int i = 0; i < Items.Count; ++i ) - Items[i].Serialize( op ); - } + #region Type Identification - public override void DeserializeChildren( PersistanceReader ip ) - { - while ( ip.HasChild ) - { - PersistableObject child = ip.GetChild(); + public static readonly PersistableType ThisTypeID = new PersistableType("rp", Construct); - if ( child is ReportColumn column ) - Columns.Add( column ); - else if ( child is ReportItem item ) - Items.Add( item ); - } - } - } -} + private static PersistableObject Construct() + { + return new Report(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/ReportColumn.cs b/Scripts/Engines/Reports/Objects/Reports/ReportColumn.cs index 76658635f..aae4f3121 100644 --- a/Scripts/Engines/Reports/Objects/Reports/ReportColumn.cs +++ b/Scripts/Engines/Reports/Objects/Reports/ReportColumn.cs @@ -1,51 +1,53 @@ namespace Server.Engines.Reports { - public class ReportColumn : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "rc", Construct ); + public class ReportColumn : PersistableObject + { + private ReportColumn() + { + } - private static PersistableObject Construct() - { - return new ReportColumn(); - } + public ReportColumn(string width, string align) : this(width, align, null) + { + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public ReportColumn(string width, string align, string name) + { + Width = width; + Align = align; + Name = name; + } - public string Width { get; set; } + public string Width{ get; set; } - public string Align { get; set; } + public string Align{ get; set; } - public string Name { get; set; } + public string Name{ get; set; } - private ReportColumn() - { - } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetString("w", Width); + op.SetString("a", Align); + op.SetString("n", Name); + } - public ReportColumn( string width, string align ) : this( width, align, null ) - { - } + public override void DeserializeAttributes(PersistanceReader ip) + { + Width = Utility.Intern(ip.GetString("w")); + Align = Utility.Intern(ip.GetString("a")); + Name = Utility.Intern(ip.GetString("n")); + } - public ReportColumn( string width, string align, string name ) - { - Width = width; - Align = align; - Name = name; - } + #region Type Identification - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetString( "w", Width ); - op.SetString( "a", Align ); - op.SetString( "n", Name ); - } + public static readonly PersistableType ThisTypeID = new PersistableType("rc", Construct); - public override void DeserializeAttributes( PersistanceReader ip ) - { - Width = Utility.Intern( ip.GetString( "w" ) ); - Align = Utility.Intern( ip.GetString( "a" ) ); - Name = Utility.Intern( ip.GetString( "n" ) ); - } - } -} + private static PersistableObject Construct() + { + return new ReportColumn(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/ReportColumnCollection.cs b/Scripts/Engines/Reports/Objects/Reports/ReportColumnCollection.cs index fcafa62cc..198534736 100644 --- a/Scripts/Engines/Reports/Objects/Reports/ReportColumnCollection.cs +++ b/Scripts/Engines/Reports/Objects/Reports/ReportColumnCollection.cs @@ -8,192 +8,186 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.ReportColumn. + /// + public class ReportColumnCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.ReportColumn. + /// Gets or sets the value of the Server.Engines.Reports.ReportColumn at a specific position in the ReportColumnCollection. /// - public class ReportColumnCollection : CollectionBase + public ReportColumn this[int index] { - - /// - /// Default constructor. - /// - public ReportColumnCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.ReportColumn at a specific position in the ReportColumnCollection. - /// - public ReportColumn this[int index] - { - get => ((ReportColumn)(List[index])); - set => List[index] = value; - } - - public int Add( string width, string align ) - { - return Add( new ReportColumn( width, align ) ); - } - - public int Add( string width, string align, string name ) - { - return Add( new ReportColumn( width, align, name ) ); - } - - /// - /// Append a Server.Engines.Reports.ReportColumn entry to this collection. - /// - /// Server.Engines.Reports.ReportColumn instance. - /// The position into which the new element was inserted. - public int Add(ReportColumn value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.ReportColumn instance is in this collection. - /// - /// Server.Engines.Reports.ReportColumn instance to search for. - /// True if the Server.Engines.Reports.ReportColumn instance is in the collection; otherwise false. - public bool Contains(ReportColumn value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.ReportColumn instance is in this collection. - /// - /// Server.Engines.Reports.ReportColumn instance to find. - /// The zero-based index of the specified Server.Engines.Reports.ReportColumn instance. If the object is not found, the return value is -1. - public int IndexOf(ReportColumn value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.ReportColumn instance from this collection. - /// - /// The Server.Engines.Reports.ReportColumn instance to remove. - public void Remove(ReportColumn value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.ReportColumn instance. - /// - /// An Server.Engines.Reports.ReportColumn's enumerator. - public new ReportColumnCollectionEnumerator GetEnumerator() - { - return new ReportColumnCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.ReportColumn instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.ReportColumn instance to insert. - public void Insert(int index, ReportColumn value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.ReportColumn. - /// - public class ReportColumnCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private ReportColumn _currentElement; - - /// - /// Collection to enumerate. - /// - private ReportColumnCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal ReportColumnCollectionEnumerator(ReportColumnCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.ReportColumn object in the enumerated ReportColumnCollection currently indexed by this instance. - /// - public ReportColumn Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (ReportColumn)List[index]; + set => List[index] = value; } -} + + public int Add(string width, string align) + { + return Add(new ReportColumn(width, align)); + } + + public int Add(string width, string align, string name) + { + return Add(new ReportColumn(width, align, name)); + } + + /// + /// Append a Server.Engines.Reports.ReportColumn entry to this collection. + /// + /// Server.Engines.Reports.ReportColumn instance. + /// The position into which the new element was inserted. + public int Add(ReportColumn value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.ReportColumn instance is in this collection. + /// + /// Server.Engines.Reports.ReportColumn instance to search for. + /// True if the Server.Engines.Reports.ReportColumn instance is in the collection; otherwise false. + public bool Contains(ReportColumn value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.ReportColumn instance is in this collection. + /// + /// Server.Engines.Reports.ReportColumn instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.ReportColumn instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(ReportColumn value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.ReportColumn instance from this collection. + /// + /// The Server.Engines.Reports.ReportColumn instance to remove. + public void Remove(ReportColumn value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.ReportColumn instance. + /// + /// An Server.Engines.Reports.ReportColumn's enumerator. + public new ReportColumnCollectionEnumerator GetEnumerator() + { + return new ReportColumnCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.ReportColumn instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.ReportColumn instance to insert. + public void Insert(int index, ReportColumn value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.ReportColumn. + /// + public class ReportColumnCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private ReportColumnCollection _collection; + + /// + /// Current element pointed to. + /// + private ReportColumn _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal ReportColumnCollectionEnumerator(ReportColumnCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.ReportColumn object in the enumerated ReportColumnCollection currently indexed by this + /// instance. + /// + public ReportColumn Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/ReportItem.cs b/Scripts/Engines/Reports/Objects/Reports/ReportItem.cs index dc03350da..336c6b2ea 100644 --- a/Scripts/Engines/Reports/Objects/Reports/ReportItem.cs +++ b/Scripts/Engines/Reports/Objects/Reports/ReportItem.cs @@ -1,35 +1,37 @@ namespace Server.Engines.Reports { - public class ReportItem : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "ri", Construct ); + public class ReportItem : PersistableObject + { + public ReportItem() + { + Values = new ItemValueCollection(); + } - private static PersistableObject Construct() - { - return new ReportItem(); - } + public ItemValueCollection Values{ get; } - public override PersistableType TypeID => ThisTypeID; - #endregion + public override void SerializeChildren(PersistanceWriter op) + { + for (int i = 0; i < Values.Count; ++i) + Values[i].Serialize(op); + } - public ItemValueCollection Values { get; } + public override void DeserializeChildren(PersistanceReader ip) + { + while (ip.HasChild) + Values.Add(ip.GetChild() as ItemValue); + } - public ReportItem() - { - Values = new ItemValueCollection(); - } + #region Type Identification - public override void SerializeChildren( PersistanceWriter op ) - { - for ( int i = 0; i < Values.Count; ++i ) - Values[i].Serialize( op ); - } + public static readonly PersistableType ThisTypeID = new PersistableType("ri", Construct); - public override void DeserializeChildren( PersistanceReader ip ) - { - while ( ip.HasChild ) - Values.Add( ip.GetChild() as ItemValue ); - } - } -} + private static PersistableObject Construct() + { + return new ReportItem(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Reports/ReportItemCollection.cs b/Scripts/Engines/Reports/Objects/Reports/ReportItemCollection.cs index e0aa9271c..1bdee17c2 100644 --- a/Scripts/Engines/Reports/Objects/Reports/ReportItemCollection.cs +++ b/Scripts/Engines/Reports/Objects/Reports/ReportItemCollection.cs @@ -8,197 +8,191 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.ReportItem. + /// + public class ReportItemCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.ReportItem. + /// Gets or sets the value of the Server.Engines.Reports.ReportItem at a specific position in the ReportItemCollection. /// - public class ReportItemCollection : CollectionBase + public ReportItem this[int index] { - - /// - /// Default constructor. - /// - public ReportItemCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.ReportItem at a specific position in the ReportItemCollection. - /// - public ReportItem this[int index] - { - get => ((ReportItem)(List[index])); - set => List[index] = value; - } - - public int Add( string name, object value ) - { - return Add( name, value, null ); - } - - public int Add( string name, object value, string format ) - { - ReportItem item = new ReportItem(); - - item.Values.Add( name ); - item.Values.Add( value == null ? "" : value.ToString(), format ); - - return Add( item ); - } - - /// - /// Append a Server.Engines.Reports.ReportItem entry to this collection. - /// - /// Server.Engines.Reports.ReportItem instance. - /// The position into which the new element was inserted. - public int Add(ReportItem value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.ReportItem instance is in this collection. - /// - /// Server.Engines.Reports.ReportItem instance to search for. - /// True if the Server.Engines.Reports.ReportItem instance is in the collection; otherwise false. - public bool Contains(ReportItem value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.ReportItem instance is in this collection. - /// - /// Server.Engines.Reports.ReportItem instance to find. - /// The zero-based index of the specified Server.Engines.Reports.ReportItem instance. If the object is not found, the return value is -1. - public int IndexOf(ReportItem value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.ReportItem instance from this collection. - /// - /// The Server.Engines.Reports.ReportItem instance to remove. - public void Remove(ReportItem value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.ReportItem instance. - /// - /// An Server.Engines.Reports.ReportItem's enumerator. - public new ReportItemCollectionEnumerator GetEnumerator() - { - return new ReportItemCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.ReportItem instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.ReportItem instance to insert. - public void Insert(int index, ReportItem value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.ReportItem. - /// - public class ReportItemCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private ReportItem _currentElement; - - /// - /// Collection to enumerate. - /// - private ReportItemCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal ReportItemCollectionEnumerator(ReportItemCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.ReportItem object in the enumerated ReportItemCollection currently indexed by this instance. - /// - public ReportItem Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (ReportItem)List[index]; + set => List[index] = value; } -} + + public int Add(string name, object value) + { + return Add(name, value, null); + } + + public int Add(string name, object value, string format) + { + ReportItem item = new ReportItem(); + + item.Values.Add(name); + item.Values.Add(value == null ? "" : value.ToString(), format); + + return Add(item); + } + + /// + /// Append a Server.Engines.Reports.ReportItem entry to this collection. + /// + /// Server.Engines.Reports.ReportItem instance. + /// The position into which the new element was inserted. + public int Add(ReportItem value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.ReportItem instance is in this collection. + /// + /// Server.Engines.Reports.ReportItem instance to search for. + /// True if the Server.Engines.Reports.ReportItem instance is in the collection; otherwise false. + public bool Contains(ReportItem value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.ReportItem instance is in this collection. + /// + /// Server.Engines.Reports.ReportItem instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.ReportItem instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(ReportItem value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.ReportItem instance from this collection. + /// + /// The Server.Engines.Reports.ReportItem instance to remove. + public void Remove(ReportItem value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.ReportItem instance. + /// + /// An Server.Engines.Reports.ReportItem's enumerator. + public new ReportItemCollectionEnumerator GetEnumerator() + { + return new ReportItemCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.ReportItem instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.ReportItem instance to insert. + public void Insert(int index, ReportItem value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.ReportItem. + /// + public class ReportItemCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private ReportItemCollection _collection; + + /// + /// Current element pointed to. + /// + private ReportItem _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal ReportItemCollectionEnumerator(ReportItemCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.ReportItem object in the enumerated ReportItemCollection currently indexed by this + /// instance. + /// + public ReportItem Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Snapshots/Snapshot.cs b/Scripts/Engines/Reports/Objects/Snapshots/Snapshot.cs index 380dbee0b..52f51d611 100644 --- a/Scripts/Engines/Reports/Objects/Snapshots/Snapshot.cs +++ b/Scripts/Engines/Reports/Objects/Snapshots/Snapshot.cs @@ -2,48 +2,50 @@ using System; namespace Server.Engines.Reports { - public class Snapshot : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "ss", Construct ); + public class Snapshot : PersistableObject + { + public Snapshot() + { + Children = new ObjectCollection(); + } - private static PersistableObject Construct() - { - return new Snapshot(); - } + public DateTime TimeStamp{ get; set; } - public override PersistableType TypeID => ThisTypeID; - #endregion + public ObjectCollection Children{ get; set; } - public DateTime TimeStamp { get; set; } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetDateTime("t", TimeStamp); + } - public ObjectCollection Children { get; set; } + public override void DeserializeAttributes(PersistanceReader ip) + { + TimeStamp = ip.GetDateTime("t"); + } - public Snapshot() - { - Children = new ObjectCollection(); - } + public override void SerializeChildren(PersistanceWriter op) + { + for (int i = 0; i < Children.Count; ++i) + Children[i].Serialize(op); + } - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetDateTime( "t", TimeStamp ); - } + public override void DeserializeChildren(PersistanceReader ip) + { + while (ip.HasChild) + Children.Add(ip.GetChild()); + } - public override void DeserializeAttributes( PersistanceReader ip ) - { - TimeStamp = ip.GetDateTime( "t" ); - } + #region Type Identification - public override void SerializeChildren( PersistanceWriter op ) - { - for ( int i = 0; i < Children.Count; ++i ) - Children[i].Serialize( op ); - } + public static readonly PersistableType ThisTypeID = new PersistableType("ss", Construct); - public override void DeserializeChildren( PersistanceReader ip ) - { - while ( ip.HasChild ) - Children.Add( ip.GetChild() ); - } - } -} + private static PersistableObject Construct() + { + return new Snapshot(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Snapshots/SnapshotCollection.cs b/Scripts/Engines/Reports/Objects/Snapshots/SnapshotCollection.cs index eba93a3b3..ce1b715b6 100644 --- a/Scripts/Engines/Reports/Objects/Snapshots/SnapshotCollection.cs +++ b/Scripts/Engines/Reports/Objects/Snapshots/SnapshotCollection.cs @@ -8,182 +8,175 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.Snapshot. + /// + public class SnapshotCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.Snapshot. + /// Gets or sets the value of the Server.Engines.Reports.Snapshot at a specific position in the SnapshotCollection. /// - public class SnapshotCollection : CollectionBase + public Snapshot this[int index] { - - /// - /// Default constructor. - /// - public SnapshotCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.Snapshot at a specific position in the SnapshotCollection. - /// - public Snapshot this[int index] - { - get => ((Snapshot)(List[index])); - set => List[index] = value; - } - - /// - /// Append a Server.Engines.Reports.Snapshot entry to this collection. - /// - /// Server.Engines.Reports.Snapshot instance. - /// The position into which the new element was inserted. - public int Add(Snapshot value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.Snapshot instance is in this collection. - /// - /// Server.Engines.Reports.Snapshot instance to search for. - /// True if the Server.Engines.Reports.Snapshot instance is in the collection; otherwise false. - public bool Contains(Snapshot value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.Snapshot instance is in this collection. - /// - /// Server.Engines.Reports.Snapshot instance to find. - /// The zero-based index of the specified Server.Engines.Reports.Snapshot instance. If the object is not found, the return value is -1. - public int IndexOf(Snapshot value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.Snapshot instance from this collection. - /// - /// The Server.Engines.Reports.Snapshot instance to remove. - public void Remove(Snapshot value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.Snapshot instance. - /// - /// An Server.Engines.Reports.Snapshot's enumerator. - public new SnapshotCollectionEnumerator GetEnumerator() - { - return new SnapshotCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.Snapshot instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.Snapshot instance to insert. - public void Insert(int index, Snapshot value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.Snapshot. - /// - public class SnapshotCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private Snapshot _currentElement; - - /// - /// Collection to enumerate. - /// - private SnapshotCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal SnapshotCollectionEnumerator(SnapshotCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.Snapshot object in the enumerated SnapshotCollection currently indexed by this instance. - /// - public Snapshot Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (Snapshot)List[index]; + set => List[index] = value; } -} + + /// + /// Append a Server.Engines.Reports.Snapshot entry to this collection. + /// + /// Server.Engines.Reports.Snapshot instance. + /// The position into which the new element was inserted. + public int Add(Snapshot value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.Snapshot instance is in this collection. + /// + /// Server.Engines.Reports.Snapshot instance to search for. + /// True if the Server.Engines.Reports.Snapshot instance is in the collection; otherwise false. + public bool Contains(Snapshot value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.Snapshot instance is in this collection. + /// + /// Server.Engines.Reports.Snapshot instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.Snapshot instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(Snapshot value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.Snapshot instance from this collection. + /// + /// The Server.Engines.Reports.Snapshot instance to remove. + public void Remove(Snapshot value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.Snapshot instance. + /// + /// An Server.Engines.Reports.Snapshot's enumerator. + public new SnapshotCollectionEnumerator GetEnumerator() + { + return new SnapshotCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.Snapshot instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.Snapshot instance to insert. + public void Insert(int index, Snapshot value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.Snapshot. + /// + public class SnapshotCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private SnapshotCollection _collection; + + /// + /// Current element pointed to. + /// + private Snapshot _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal SnapshotCollectionEnumerator(SnapshotCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.Snapshot object in the enumerated SnapshotCollection currently indexed by this instance. + /// + public Snapshot Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Snapshots/SnapshotHistory.cs b/Scripts/Engines/Reports/Objects/Snapshots/SnapshotHistory.cs index f8ba68b9f..f9d5f186d 100644 --- a/Scripts/Engines/Reports/Objects/Snapshots/SnapshotHistory.cs +++ b/Scripts/Engines/Reports/Objects/Snapshots/SnapshotHistory.cs @@ -2,60 +2,62 @@ using System.IO; namespace Server.Engines.Reports { - public class SnapshotHistory : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "sh", Construct ); + public class SnapshotHistory : PersistableObject + { + public SnapshotHistory() + { + Snapshots = new SnapshotCollection(); + } - private static PersistableObject Construct() - { - return new SnapshotHistory(); - } + public SnapshotCollection Snapshots{ get; set; } - public override PersistableType TypeID => ThisTypeID; - #endregion + public void Save() + { + string path = Path.Combine(Core.BaseDirectory, "reportHistory.xml"); + PersistanceWriter pw = new XmlPersistanceWriter(path, "Stats"); - public SnapshotCollection Snapshots { get; set; } + pw.WriteDocument(this); - public SnapshotHistory() - { - Snapshots = new SnapshotCollection(); - } + pw.Close(); + } - public void Save() - { - string path = Path.Combine( Core.BaseDirectory, "reportHistory.xml" ); - PersistanceWriter pw = new XmlPersistanceWriter( path, "Stats" ); + public void Load() + { + string path = Path.Combine(Core.BaseDirectory, "reportHistory.xml"); - pw.WriteDocument( this ); + if (!File.Exists(path)) + return; - pw.Close(); - } + PersistanceReader pr = new XmlPersistanceReader(path, "Stats"); - public void Load() - { - string path = Path.Combine( Core.BaseDirectory, "reportHistory.xml" ); + pr.ReadDocument(this); - if ( !File.Exists( path ) ) - return; + pr.Close(); + } - PersistanceReader pr = new XmlPersistanceReader( path, "Stats" ); + public override void SerializeChildren(PersistanceWriter op) + { + for (int i = 0; i < Snapshots.Count; ++i) + Snapshots[i].Serialize(op); + } - pr.ReadDocument( this ); + public override void DeserializeChildren(PersistanceReader ip) + { + while (ip.HasChild) + Snapshots.Add(ip.GetChild() as Snapshot); + } - pr.Close(); - } + #region Type Identification - public override void SerializeChildren( PersistanceWriter op ) - { - for ( int i = 0; i < Snapshots.Count; ++i ) - Snapshots[i].Serialize( op ); - } + public static readonly PersistableType ThisTypeID = new PersistableType("sh", Construct); - public override void DeserializeChildren( PersistanceReader ip ) - { - while ( ip.HasChild ) - Snapshots.Add( ip.GetChild() as Snapshot ); - } - } -} + private static PersistableObject Construct() + { + return new SnapshotHistory(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/Info.cs b/Scripts/Engines/Reports/Objects/Staffing/Info.cs index c90af00c3..9bcbd5813 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/Info.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/Info.cs @@ -3,94 +3,96 @@ using Server.Accounting; namespace Server.Engines.Reports { - public abstract class BaseInfo : IComparable - { - public static TimeSpan SortRange { get; set; } + public abstract class BaseInfo : IComparable + { + private string m_Display; - private string m_Display; + public BaseInfo(string account) + { + Account = account; + Pages = new PageInfoCollection(); + } - public string Account { get; set; } + public static TimeSpan SortRange{ get; set; } - public PageInfoCollection Pages { get; set; } + public string Account{ get; set; } - public string Display - { - get - { - if ( m_Display != null ) - return m_Display; + public PageInfoCollection Pages{ get; set; } - if ( Account != null ) - { - IAccount acct = Accounts.GetAccount( Account ); + public string Display + { + get + { + if (m_Display != null) + return m_Display; - if ( acct != null ) - { - Mobile mob = null; + if (Account != null) + { + IAccount acct = Accounts.GetAccount(Account); - for ( int i = 0; i < acct.Length; ++i ) - { - Mobile check = acct[i]; + if (acct != null) + { + Mobile mob = null; - if ( check != null && (mob == null || check.AccessLevel > mob.AccessLevel) ) - mob = check; - } + for (int i = 0; i < acct.Length; ++i) + { + Mobile check = acct[i]; - if ( mob?.Name != null && mob.Name.Length > 0 ) - return ( m_Display = mob.Name ); - } - } + if (check != null && (mob == null || check.AccessLevel > mob.AccessLevel)) + mob = check; + } - return ( m_Display = Account ); - } - } + if (mob?.Name != null && mob.Name.Length > 0) + return m_Display = mob.Name; + } + } - public int GetPageCount( PageResolution res, DateTime min, DateTime max ) - { - return StaffHistory.GetPageCount( Pages, res, min, max ); - } + return m_Display = Account; + } + } - public BaseInfo( string account ) - { - Account = account; - Pages = new PageInfoCollection(); - } + public int CompareTo(object obj) + { + BaseInfo cmp = obj as BaseInfo; - public void Register( PageInfo page ) - { - Pages.Add( page ); - } + int v = cmp.GetPageCount(cmp is StaffInfo ? PageResolution.Handled : PageResolution.None, + DateTime.UtcNow - SortRange, DateTime.UtcNow) + - GetPageCount(this is StaffInfo ? PageResolution.Handled : PageResolution.None, + DateTime.UtcNow - SortRange, DateTime.UtcNow); - public void Unregister( PageInfo page ) - { - Pages.Remove( page ); - } + if (v == 0) + v = string.Compare(Display, cmp.Display); - public int CompareTo( object obj ) - { - BaseInfo cmp = obj as BaseInfo; + return v; + } - int v = cmp.GetPageCount( cmp is StaffInfo ? PageResolution.Handled : PageResolution.None, DateTime.UtcNow - SortRange, DateTime.UtcNow ) - - GetPageCount( this is StaffInfo ? PageResolution.Handled : PageResolution.None, DateTime.UtcNow - SortRange, DateTime.UtcNow ); + public int GetPageCount(PageResolution res, DateTime min, DateTime max) + { + return StaffHistory.GetPageCount(Pages, res, min, max); + } - if ( v == 0 ) - v = string.Compare( Display, cmp.Display ); + public void Register(PageInfo page) + { + Pages.Add(page); + } - return v; - } - } + public void Unregister(PageInfo page) + { + Pages.Remove(page); + } + } - public class StaffInfo : BaseInfo - { - public StaffInfo( string account ) : base( account ) - { - } - } + public class StaffInfo : BaseInfo + { + public StaffInfo(string account) : base(account) + { + } + } - public class UserInfo : BaseInfo - { - public UserInfo( string account ) : base( account ) - { - } - } + public class UserInfo : BaseInfo + { + public UserInfo(string account) : base(account) + { + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/PageInfo.cs b/Scripts/Engines/Reports/Objects/Staffing/PageInfo.cs index 8c226ca6f..f76a1daa3 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/PageInfo.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/PageInfo.cs @@ -4,230 +4,232 @@ using Server.Engines.Help; namespace Server.Engines.Reports { - public enum PageResolution - { - None, - Handled, - Deleted, - Logged, - Canceled - } + public enum PageResolution + { + None, + Handled, + Deleted, + Logged, + Canceled + } - public class PageInfo : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "pi", Construct ); + public class PageInfo : PersistableObject + { + private StaffHistory m_History; + private StaffInfo m_Resolver; + private UserInfo m_Sender; - private static PersistableObject Construct() - { - return new PageInfo(); - } + private string m_SentBy; - public override PersistableType TypeID => ThisTypeID; - #endregion + public PageInfo() + { + Responses = new ResponseInfoCollection(); + } - private StaffHistory m_History; - private StaffInfo m_Resolver; - private UserInfo m_Sender; + public PageInfo(PageEntry entry) + { + PageType = entry.Type; - public StaffInfo Resolver - { - get => m_Resolver; - set - { - if ( m_Resolver == value ) - return; + TimeSent = entry.Sent; + m_SentBy = GetAccount(entry.Sender); - lock ( StaffHistory.RenderLock ) - { - m_Resolver?.Unregister( this ); + Message = entry.Message; + Responses = new ResponseInfoCollection(); + } - m_Resolver = value; + public StaffInfo Resolver + { + get => m_Resolver; + set + { + if (m_Resolver == value) + return; - m_Resolver?.Register( this ); - } - } - } + lock (StaffHistory.RenderLock) + { + m_Resolver?.Unregister(this); - public UserInfo Sender - { - get => m_Sender; - set - { - if ( m_Sender == value ) - return; + m_Resolver = value; - lock ( StaffHistory.RenderLock ) - { - m_Sender?.Unregister( this ); + m_Resolver?.Register(this); + } + } + } - m_Sender = value; + public UserInfo Sender + { + get => m_Sender; + set + { + if (m_Sender == value) + return; - m_Sender?.Register( this ); - } - } - } + lock (StaffHistory.RenderLock) + { + m_Sender?.Unregister(this); - private string m_SentBy; + m_Sender = value; - public StaffHistory History - { - get => m_History; - set - { - if ( m_History == value ) - return; + m_Sender?.Register(this); + } + } + } - if ( m_History != null ) - { - Sender = null; - Resolver = null; - } + public StaffHistory History + { + get => m_History; + set + { + if (m_History == value) + return; - m_History = value; + if (m_History != null) + { + Sender = null; + Resolver = null; + } - if ( m_History != null ) - { - Sender = m_History.GetUserInfo( m_SentBy ); - UpdateResolver(); - } - } - } + m_History = value; - public PageType PageType { get; set; } + if (m_History != null) + { + Sender = m_History.GetUserInfo(m_SentBy); + UpdateResolver(); + } + } + } - public PageResolution Resolution { get; private set; } + public PageType PageType{ get; set; } - public DateTime TimeSent { get; set; } + public PageResolution Resolution{ get; private set; } - public DateTime TimeResolved { get; private set; } + public DateTime TimeSent{ get; set; } - public string SentBy - { - get => m_SentBy; - set - { - m_SentBy = value; + public DateTime TimeResolved{ get; private set; } - if ( m_History != null ) - Sender = m_History.GetUserInfo( m_SentBy ); - } - } + public string SentBy + { + get => m_SentBy; + set + { + m_SentBy = value; - public string ResolvedBy { get; private set; } + if (m_History != null) + Sender = m_History.GetUserInfo(m_SentBy); + } + } - public string Message { get; set; } + public string ResolvedBy{ get; private set; } - public ResponseInfoCollection Responses { get; set; } + public string Message{ get; set; } - public void UpdateResolver() - { - string resolvedBy; - DateTime timeResolved; - PageResolution res = GetResolution( out resolvedBy, out timeResolved ); + public ResponseInfoCollection Responses{ get; set; } - if ( m_History != null && IsStaffResolution( res ) ) - Resolver = m_History.GetStaffInfo( resolvedBy ); - else - Resolver = null; + public void UpdateResolver() + { + string resolvedBy; + DateTime timeResolved; + PageResolution res = GetResolution(out resolvedBy, out timeResolved); - ResolvedBy = resolvedBy; - TimeResolved = timeResolved; - Resolution = res; - } + if (m_History != null && IsStaffResolution(res)) + Resolver = m_History.GetStaffInfo(resolvedBy); + else + Resolver = null; - public bool IsStaffResolution( PageResolution res ) - { - return ( res == PageResolution.Handled ); - } + ResolvedBy = resolvedBy; + TimeResolved = timeResolved; + Resolution = res; + } - public static PageResolution ResFromResp( string resp ) - { - switch ( resp ) - { - case "[Handled]": return PageResolution.Handled; - case "[Deleting]": return PageResolution.Deleted; - case "[Logout]": return PageResolution.Logged; - case "[Canceled]": return PageResolution.Canceled; - } + public bool IsStaffResolution(PageResolution res) + { + return res == PageResolution.Handled; + } - return PageResolution.None; - } + public static PageResolution ResFromResp(string resp) + { + switch (resp) + { + case "[Handled]": return PageResolution.Handled; + case "[Deleting]": return PageResolution.Deleted; + case "[Logout]": return PageResolution.Logged; + case "[Canceled]": return PageResolution.Canceled; + } - public PageResolution GetResolution( out string resolvedBy, out DateTime timeResolved ) - { - for ( int i = Responses.Count - 1; i >= 0; --i ) - { - ResponseInfo resp = Responses[i]; - PageResolution res = ResFromResp( resp.Message ); + return PageResolution.None; + } - if ( res != PageResolution.None ) - { - resolvedBy = resp.SentBy; - timeResolved = resp.TimeStamp; - return res; - } - } + public PageResolution GetResolution(out string resolvedBy, out DateTime timeResolved) + { + for (int i = Responses.Count - 1; i >= 0; --i) + { + ResponseInfo resp = Responses[i]; + PageResolution res = ResFromResp(resp.Message); - resolvedBy = m_SentBy; - timeResolved = TimeSent; - return PageResolution.None; - } + if (res != PageResolution.None) + { + resolvedBy = resp.SentBy; + timeResolved = resp.TimeStamp; + return res; + } + } - public static string GetAccount( Mobile mob ) - { - return mob?.Account is Account acct ? acct.Username : null; - } + resolvedBy = m_SentBy; + timeResolved = TimeSent; + return PageResolution.None; + } - public PageInfo() - { - Responses = new ResponseInfoCollection(); - } + public static string GetAccount(Mobile mob) + { + return mob?.Account is Account acct ? acct.Username : null; + } - public PageInfo( PageEntry entry ) - { - PageType = entry.Type; + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetInt32("p", (int)PageType); - TimeSent = entry.Sent; - m_SentBy = GetAccount( entry.Sender ); + op.SetDateTime("ts", TimeSent); + op.SetString("s", m_SentBy); - Message = entry.Message; - Responses = new ResponseInfoCollection(); - } + op.SetString("m", Message); + } - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetInt32( "p", (int)PageType ); + public override void DeserializeAttributes(PersistanceReader ip) + { + PageType = (PageType)ip.GetInt32("p"); - op.SetDateTime( "ts", TimeSent ); - op.SetString( "s", m_SentBy ); + TimeSent = ip.GetDateTime("ts"); + m_SentBy = ip.GetString("s"); - op.SetString( "m", Message ); - } + Message = ip.GetString("m"); + } - public override void DeserializeAttributes( PersistanceReader ip ) - { - PageType = (PageType) ip.GetInt32( "p" ); + public override void SerializeChildren(PersistanceWriter op) + { + lock (this) + { + for (int i = 0; i < Responses.Count; ++i) + Responses[i].Serialize(op); + } + } - TimeSent = ip.GetDateTime( "ts" ); - m_SentBy = ip.GetString( "s" ); + public override void DeserializeChildren(PersistanceReader ip) + { + while (ip.HasChild) + Responses.Add(ip.GetChild() as ResponseInfo); + } - Message = ip.GetString( "m" ); - } + #region Type Identification - public override void SerializeChildren( PersistanceWriter op ) - { - lock ( this ) - { - for ( int i = 0; i < Responses.Count; ++i ) - Responses[i].Serialize( op ); - } - } + public static readonly PersistableType ThisTypeID = new PersistableType("pi", Construct); - public override void DeserializeChildren( PersistanceReader ip ) - { - while ( ip.HasChild ) - Responses.Add( ip.GetChild() as ResponseInfo ); - } - } -} + private static PersistableObject Construct() + { + return new PageInfo(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/PageInfoCollection.cs b/Scripts/Engines/Reports/Objects/Staffing/PageInfoCollection.cs index 632b60f8a..96a76f9ba 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/PageInfoCollection.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/PageInfoCollection.cs @@ -8,182 +8,175 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.PageInfo. + /// + public class PageInfoCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.PageInfo. + /// Gets or sets the value of the Server.Engines.Reports.PageInfo at a specific position in the PageInfoCollection. /// - public class PageInfoCollection : CollectionBase + public PageInfo this[int index] { - - /// - /// Default constructor. - /// - public PageInfoCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.PageInfo at a specific position in the PageInfoCollection. - /// - public PageInfo this[int index] - { - get => ((PageInfo)(List[index])); - set => List[index] = value; - } - - /// - /// Append a Server.Engines.Reports.PageInfo entry to this collection. - /// - /// Server.Engines.Reports.PageInfo instance. - /// The position into which the new element was inserted. - public int Add(PageInfo value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.PageInfo instance is in this collection. - /// - /// Server.Engines.Reports.PageInfo instance to search for. - /// True if the Server.Engines.Reports.PageInfo instance is in the collection; otherwise false. - public bool Contains(PageInfo value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.PageInfo instance is in this collection. - /// - /// Server.Engines.Reports.PageInfo instance to find. - /// The zero-based index of the specified Server.Engines.Reports.PageInfo instance. If the object is not found, the return value is -1. - public int IndexOf(PageInfo value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.PageInfo instance from this collection. - /// - /// The Server.Engines.Reports.PageInfo instance to remove. - public void Remove(PageInfo value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.PageInfo instance. - /// - /// An Server.Engines.Reports.PageInfo's enumerator. - public new PageInfoCollectionEnumerator GetEnumerator() - { - return new PageInfoCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.PageInfo instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.PageInfo instance to insert. - public void Insert(int index, PageInfo value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.PageInfo. - /// - public class PageInfoCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private PageInfo _currentElement; - - /// - /// Collection to enumerate. - /// - private PageInfoCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal PageInfoCollectionEnumerator(PageInfoCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.PageInfo object in the enumerated PageInfoCollection currently indexed by this instance. - /// - public PageInfo Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (PageInfo)List[index]; + set => List[index] = value; } -} + + /// + /// Append a Server.Engines.Reports.PageInfo entry to this collection. + /// + /// Server.Engines.Reports.PageInfo instance. + /// The position into which the new element was inserted. + public int Add(PageInfo value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.PageInfo instance is in this collection. + /// + /// Server.Engines.Reports.PageInfo instance to search for. + /// True if the Server.Engines.Reports.PageInfo instance is in the collection; otherwise false. + public bool Contains(PageInfo value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.PageInfo instance is in this collection. + /// + /// Server.Engines.Reports.PageInfo instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.PageInfo instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(PageInfo value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.PageInfo instance from this collection. + /// + /// The Server.Engines.Reports.PageInfo instance to remove. + public void Remove(PageInfo value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.PageInfo instance. + /// + /// An Server.Engines.Reports.PageInfo's enumerator. + public new PageInfoCollectionEnumerator GetEnumerator() + { + return new PageInfoCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.PageInfo instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.PageInfo instance to insert. + public void Insert(int index, PageInfo value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.PageInfo. + /// + public class PageInfoCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private PageInfoCollection _collection; + + /// + /// Current element pointed to. + /// + private PageInfo _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal PageInfoCollectionEnumerator(PageInfoCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.PageInfo object in the enumerated PageInfoCollection currently indexed by this instance. + /// + public PageInfo Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/QueueStatus.cs b/Scripts/Engines/Reports/Objects/Staffing/QueueStatus.cs index 77909126b..eb68b29ab 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/QueueStatus.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/QueueStatus.cs @@ -2,43 +2,45 @@ using System; namespace Server.Engines.Reports { - public class QueueStatus : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "qs", Construct ); + public class QueueStatus : PersistableObject + { + public QueueStatus() + { + } - private static PersistableObject Construct() - { - return new QueueStatus(); - } + public QueueStatus(int count) + { + TimeStamp = DateTime.UtcNow; + Count = count; + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public DateTime TimeStamp{ get; set; } - public DateTime TimeStamp { get; set; } + public int Count{ get; set; } - public int Count { get; set; } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetDateTime("t", TimeStamp); + op.SetInt32("c", Count); + } - public QueueStatus() - { - } + public override void DeserializeAttributes(PersistanceReader ip) + { + TimeStamp = ip.GetDateTime("t"); + Count = ip.GetInt32("c"); + } - public QueueStatus( int count ) - { - TimeStamp = DateTime.UtcNow; - Count = count; - } + #region Type Identification - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetDateTime( "t", TimeStamp ); - op.SetInt32( "c", Count ); - } + public static readonly PersistableType ThisTypeID = new PersistableType("qs", Construct); - public override void DeserializeAttributes( PersistanceReader ip ) - { - TimeStamp = ip.GetDateTime( "t" ); - Count = ip.GetInt32( "c" ); - } - } -} + private static PersistableObject Construct() + { + return new QueueStatus(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/QueueStatusCollection.cs b/Scripts/Engines/Reports/Objects/Staffing/QueueStatusCollection.cs index 58e44b671..7efc7f6dc 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/QueueStatusCollection.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/QueueStatusCollection.cs @@ -8,182 +8,176 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.QueueStatus. + /// + public class QueueStatusCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.QueueStatus. + /// Gets or sets the value of the Server.Engines.Reports.QueueStatus at a specific position in the QueueStatusCollection. /// - public class QueueStatusCollection : CollectionBase + public QueueStatus this[int index] { - - /// - /// Default constructor. - /// - public QueueStatusCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.QueueStatus at a specific position in the QueueStatusCollection. - /// - public QueueStatus this[int index] - { - get => ((QueueStatus)(List[index])); - set => List[index] = value; - } - - /// - /// Append a Server.Engines.Reports.QueueStatus entry to this collection. - /// - /// Server.Engines.Reports.QueueStatus instance. - /// The position into which the new element was inserted. - public int Add(QueueStatus value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.QueueStatus instance is in this collection. - /// - /// Server.Engines.Reports.QueueStatus instance to search for. - /// True if the Server.Engines.Reports.QueueStatus instance is in the collection; otherwise false. - public bool Contains(QueueStatus value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.QueueStatus instance is in this collection. - /// - /// Server.Engines.Reports.QueueStatus instance to find. - /// The zero-based index of the specified Server.Engines.Reports.QueueStatus instance. If the object is not found, the return value is -1. - public int IndexOf(QueueStatus value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.QueueStatus instance from this collection. - /// - /// The Server.Engines.Reports.QueueStatus instance to remove. - public void Remove(QueueStatus value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.QueueStatus instance. - /// - /// An Server.Engines.Reports.QueueStatus's enumerator. - public new QueueStatusCollectionEnumerator GetEnumerator() - { - return new QueueStatusCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.QueueStatus instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.QueueStatus instance to insert. - public void Insert(int index, QueueStatus value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.QueueStatus. - /// - public class QueueStatusCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private QueueStatus _currentElement; - - /// - /// Collection to enumerate. - /// - private QueueStatusCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal QueueStatusCollectionEnumerator(QueueStatusCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.QueueStatus object in the enumerated QueueStatusCollection currently indexed by this instance. - /// - public QueueStatus Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (QueueStatus)List[index]; + set => List[index] = value; } -} + + /// + /// Append a Server.Engines.Reports.QueueStatus entry to this collection. + /// + /// Server.Engines.Reports.QueueStatus instance. + /// The position into which the new element was inserted. + public int Add(QueueStatus value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.QueueStatus instance is in this collection. + /// + /// Server.Engines.Reports.QueueStatus instance to search for. + /// True if the Server.Engines.Reports.QueueStatus instance is in the collection; otherwise false. + public bool Contains(QueueStatus value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.QueueStatus instance is in this collection. + /// + /// Server.Engines.Reports.QueueStatus instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.QueueStatus instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(QueueStatus value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.QueueStatus instance from this collection. + /// + /// The Server.Engines.Reports.QueueStatus instance to remove. + public void Remove(QueueStatus value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.QueueStatus instance. + /// + /// An Server.Engines.Reports.QueueStatus's enumerator. + public new QueueStatusCollectionEnumerator GetEnumerator() + { + return new QueueStatusCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.QueueStatus instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.QueueStatus instance to insert. + public void Insert(int index, QueueStatus value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.QueueStatus. + /// + public class QueueStatusCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private QueueStatusCollection _collection; + + /// + /// Current element pointed to. + /// + private QueueStatus _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal QueueStatusCollectionEnumerator(QueueStatusCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.QueueStatus object in the enumerated QueueStatusCollection currently indexed by this + /// instance. + /// + public QueueStatus Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/ResponseInfo.cs b/Scripts/Engines/Reports/Objects/Staffing/ResponseInfo.cs index 2485b5b14..7eafcc5e8 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/ResponseInfo.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/ResponseInfo.cs @@ -2,50 +2,52 @@ using System; namespace Server.Engines.Reports { - public class ResponseInfo : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "rs", Construct ); + public class ResponseInfo : PersistableObject + { + public ResponseInfo() + { + } - private static PersistableObject Construct() - { - return new ResponseInfo(); - } + public ResponseInfo(string sentBy, string message) + { + TimeStamp = DateTime.UtcNow; + SentBy = sentBy; + Message = message; + } - public override PersistableType TypeID => ThisTypeID; - #endregion + public DateTime TimeStamp{ get; set; } - public DateTime TimeStamp { get; set; } + public string SentBy{ get; set; } - public string SentBy { get; set; } + public string Message{ get; set; } - public string Message { get; set; } + public override void SerializeAttributes(PersistanceWriter op) + { + op.SetDateTime("t", TimeStamp); - public ResponseInfo() - { - } + op.SetString("s", SentBy); + op.SetString("m", Message); + } - public ResponseInfo( string sentBy, string message ) - { - TimeStamp = DateTime.UtcNow; - SentBy = sentBy; - Message = message; - } + public override void DeserializeAttributes(PersistanceReader ip) + { + TimeStamp = ip.GetDateTime("t"); - public override void SerializeAttributes( PersistanceWriter op ) - { - op.SetDateTime( "t", TimeStamp ); + SentBy = ip.GetString("s"); + Message = ip.GetString("m"); + } - op.SetString( "s", SentBy ); - op.SetString( "m", Message ); - } + #region Type Identification - public override void DeserializeAttributes( PersistanceReader ip ) - { - TimeStamp = ip.GetDateTime( "t" ); + public static readonly PersistableType ThisTypeID = new PersistableType("rs", Construct); - SentBy = ip.GetString( "s" ); - Message = ip.GetString( "m" ); - } - } -} + private static PersistableObject Construct() + { + return new ResponseInfo(); + } + + public override PersistableType TypeID => ThisTypeID; + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/ResponseInfoCollection.cs b/Scripts/Engines/Reports/Objects/Staffing/ResponseInfoCollection.cs index f9b7f0a9f..d3ab87e8b 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/ResponseInfoCollection.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/ResponseInfoCollection.cs @@ -8,187 +8,181 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.ResponseInfo. + /// + public class ResponseInfoCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.ResponseInfo. + /// Gets or sets the value of the Server.Engines.Reports.ResponseInfo at a specific position in the ResponseInfoCollection. /// - public class ResponseInfoCollection : CollectionBase + public ResponseInfo this[int index] { - - /// - /// Default constructor. - /// - public ResponseInfoCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.ResponseInfo at a specific position in the ResponseInfoCollection. - /// - public ResponseInfo this[int index] - { - get => ((ResponseInfo)(List[index])); - set => List[index] = value; - } - - public int Add( string sentBy, string message ) - { - return Add( new ResponseInfo( sentBy, message ) ); - } - - /// - /// Append a Server.Engines.Reports.ResponseInfo entry to this collection. - /// - /// Server.Engines.Reports.ResponseInfo instance. - /// The position into which the new element was inserted. - public int Add(ResponseInfo value) - { - return List.Add(value); - } - - /// - /// Determines whether a specified Server.Engines.Reports.ResponseInfo instance is in this collection. - /// - /// Server.Engines.Reports.ResponseInfo instance to search for. - /// True if the Server.Engines.Reports.ResponseInfo instance is in the collection; otherwise false. - public bool Contains(ResponseInfo value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.ResponseInfo instance is in this collection. - /// - /// Server.Engines.Reports.ResponseInfo instance to find. - /// The zero-based index of the specified Server.Engines.Reports.ResponseInfo instance. If the object is not found, the return value is -1. - public int IndexOf(ResponseInfo value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.ResponseInfo instance from this collection. - /// - /// The Server.Engines.Reports.ResponseInfo instance to remove. - public void Remove(ResponseInfo value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.ResponseInfo instance. - /// - /// An Server.Engines.Reports.ResponseInfo's enumerator. - public new ResponseInfoCollectionEnumerator GetEnumerator() - { - return new ResponseInfoCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.ResponseInfo instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.ResponseInfo instance to insert. - public void Insert(int index, ResponseInfo value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.ResponseInfo. - /// - public class ResponseInfoCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private ResponseInfo _currentElement; - - /// - /// Collection to enumerate. - /// - private ResponseInfoCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal ResponseInfoCollectionEnumerator(ResponseInfoCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.ResponseInfo object in the enumerated ResponseInfoCollection currently indexed by this instance. - /// - public ResponseInfo Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (ResponseInfo)List[index]; + set => List[index] = value; } -} + + public int Add(string sentBy, string message) + { + return Add(new ResponseInfo(sentBy, message)); + } + + /// + /// Append a Server.Engines.Reports.ResponseInfo entry to this collection. + /// + /// Server.Engines.Reports.ResponseInfo instance. + /// The position into which the new element was inserted. + public int Add(ResponseInfo value) + { + return List.Add(value); + } + + /// + /// Determines whether a specified Server.Engines.Reports.ResponseInfo instance is in this collection. + /// + /// Server.Engines.Reports.ResponseInfo instance to search for. + /// True if the Server.Engines.Reports.ResponseInfo instance is in the collection; otherwise false. + public bool Contains(ResponseInfo value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.ResponseInfo instance is in this collection. + /// + /// Server.Engines.Reports.ResponseInfo instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.ResponseInfo instance. If the object is not found, the + /// return value is -1. + /// + public int IndexOf(ResponseInfo value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.ResponseInfo instance from this collection. + /// + /// The Server.Engines.Reports.ResponseInfo instance to remove. + public void Remove(ResponseInfo value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.ResponseInfo instance. + /// + /// An Server.Engines.Reports.ResponseInfo's enumerator. + public new ResponseInfoCollectionEnumerator GetEnumerator() + { + return new ResponseInfoCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.ResponseInfo instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.ResponseInfo instance to insert. + public void Insert(int index, ResponseInfo value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.ResponseInfo. + /// + public class ResponseInfoCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private ResponseInfoCollection _collection; + + /// + /// Current element pointed to. + /// + private ResponseInfo _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal ResponseInfoCollectionEnumerator(ResponseInfoCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.ResponseInfo object in the enumerated ResponseInfoCollection currently indexed by this + /// instance. + /// + public ResponseInfo Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Objects/Staffing/StaffHistory.cs b/Scripts/Engines/Reports/Objects/Staffing/StaffHistory.cs index 77db0e770..78ea3be9d 100644 --- a/Scripts/Engines/Reports/Objects/Staffing/StaffHistory.cs +++ b/Scripts/Engines/Reports/Objects/Staffing/StaffHistory.cs @@ -1,393 +1,402 @@ using System; -using System.IO; using System.Collections; +using System.IO; namespace Server.Engines.Reports { - public class StaffHistory : PersistableObject - { - #region Type Identification - public static readonly PersistableType ThisTypeID = new PersistableType( "stfhst", Construct ); + public class StaffHistory : PersistableObject + { + public static readonly PersistableType ThisTypeID = new PersistableType("stfhst", Construct); + public static readonly object RenderLock = new object(); + public static readonly object SaveLock = new object(); - private static PersistableObject Construct() - { - return new StaffHistory(); - } + public StaffHistory() + { + Pages = new PageInfoCollection(); + QueueStats = new QueueStatusCollection(); - public override PersistableType TypeID => ThisTypeID; - #endregion + UserInfo = new Hashtable(StringComparer.OrdinalIgnoreCase); + StaffInfo = new Hashtable(StringComparer.OrdinalIgnoreCase); + } - public PageInfoCollection Pages { get; set; } + public PageInfoCollection Pages{ get; set; } + + public QueueStatusCollection QueueStats{ get; set; } + + public Hashtable UserInfo{ get; set; } + + public Hashtable StaffInfo{ get; set; } + + public void AddPage(PageInfo info) + { + lock (SaveLock) + { + Pages.Add(info); + } + + info.History = this; + } + + public StaffInfo GetStaffInfo(string account) + { + lock (RenderLock) + { + if (string.IsNullOrEmpty(account)) + return null; + + if (!(StaffInfo[account] is StaffInfo info)) + StaffInfo[account] = info = new StaffInfo(account); + + return info; + } + } + + public UserInfo GetUserInfo(string account) + { + if (string.IsNullOrEmpty(account)) + return null; + + if (!(UserInfo[account] is UserInfo info)) + UserInfo[account] = info = new UserInfo(account); + + return info; + } + + public void Save() + { + lock (SaveLock) + { + string path = Path.Combine(Core.BaseDirectory, "staffHistory.xml"); + PersistanceWriter pw = new XmlPersistanceWriter(path, "Staff"); + + pw.WriteDocument(this); + + pw.Close(); + } + } + + public void Load() + { + string path = Path.Combine(Core.BaseDirectory, "staffHistory.xml"); + + if (!File.Exists(path)) + return; + + PersistanceReader pr = new XmlPersistanceReader(path, "Staff"); + + pr.ReadDocument(this); + + pr.Close(); + } + + public override void SerializeChildren(PersistanceWriter op) + { + for (int i = 0; i < Pages.Count; ++i) + Pages[i].Serialize(op); + + for (int i = 0; i < QueueStats.Count; ++i) + QueueStats[i].Serialize(op); + } + + public override void DeserializeChildren(PersistanceReader ip) + { + DateTime min = DateTime.UtcNow - TimeSpan.FromDays(8.0); + + while (ip.HasChild) + { + PersistableObject obj = ip.GetChild(); + + if (obj is PageInfo pageInfo) + { + pageInfo.UpdateResolver(); + + if (pageInfo.TimeSent >= min || pageInfo.TimeResolved >= min) + { + Pages.Add(pageInfo); + pageInfo.History = this; + } + else + { + pageInfo.Sender = null; + pageInfo.Resolver = null; + } + } + else if (obj is QueueStatus queueStatus) + { + if (queueStatus.TimeStamp >= min) + QueueStats.Add(queueStatus); + } + } + } + + public StaffInfo[] GetStaff() + { + StaffInfo[] staff = new StaffInfo[StaffInfo.Count]; + int index = 0; + + foreach (StaffInfo staffInfo in StaffInfo.Values) + staff[index++] = staffInfo; + + return staff; + } + + public void Render(ObjectCollection objects) + { + lock (RenderLock) + { + objects.Add(GraphQueueStatus()); + + StaffInfo[] staff = GetStaff(); + + BaseInfo.SortRange = TimeSpan.FromDays(7.0); + Array.Sort(staff); + + objects.Add(GraphHourlyPages(Pages, PageResolution.None, "New pages by hour", "graph_new_pages_hr")); + objects.Add(GraphHourlyPages(Pages, PageResolution.Handled, "Handled pages by hour", + "graph_handled_pages_hr")); + objects.Add(GraphHourlyPages(Pages, PageResolution.Deleted, "Deleted pages by hour", + "graph_deleted_pages_hr")); + objects.Add(GraphHourlyPages(Pages, PageResolution.Canceled, "Canceled pages by hour", + "graph_canceled_pages_hr")); + objects.Add(GraphHourlyPages(Pages, PageResolution.Logged, "Logged-out pages by hour", + "graph_logged_pages_hr")); + + BaseInfo.SortRange = TimeSpan.FromDays(1.0); + Array.Sort(staff); + + objects.Add(ReportTotalPages(staff, TimeSpan.FromDays(1.0), "1 Day")); + objects.AddRange(ChartTotalPages(staff, TimeSpan.FromDays(1.0), "1 Day", "graph_daily_pages")); + + BaseInfo.SortRange = TimeSpan.FromDays(7.0); + Array.Sort(staff); + + objects.Add(ReportTotalPages(staff, TimeSpan.FromDays(7.0), "1 Week")); + objects.AddRange(ChartTotalPages(staff, TimeSpan.FromDays(7.0), "1 Week", "graph_weekly_pages")); + + BaseInfo.SortRange = TimeSpan.FromDays(30.0); + Array.Sort(staff); + + objects.Add(ReportTotalPages(staff, TimeSpan.FromDays(30.0), "1 Month")); + objects.AddRange(ChartTotalPages(staff, TimeSpan.FromDays(30.0), "1 Month", "graph_monthly_pages")); - public QueueStatusCollection QueueStats { get; set; } + for (int i = 0; i < staff.Length; ++i) + objects.Add(GraphHourlyPages(staff[i])); + } + } + + public static int GetPageCount(StaffInfo staff, DateTime min, DateTime max) + { + return GetPageCount(staff.Pages, PageResolution.Handled, min, max); + } + + public static int GetPageCount(PageInfoCollection pages, PageResolution res, DateTime min, DateTime max) + { + int count = 0; + + for (int i = 0; i < pages.Count; ++i) + { + if (res != PageResolution.None && pages[i].Resolution != res) + continue; + + DateTime ts = pages[i].TimeResolved; + + if (ts >= min && ts < max) + ++count; + } + + return count; + } + + private BarGraph GraphQueueStatus() + { + int[] totals = new int[24]; + int[] counts = new int[24]; + + DateTime max = DateTime.UtcNow; + DateTime min = max - TimeSpan.FromDays(7.0); + + for (int i = 0; i < QueueStats.Count; ++i) + { + DateTime ts = QueueStats[i].TimeStamp; - public Hashtable UserInfo { get; set; } + if (ts >= min && ts < max) + { + DateTime date = ts.Date; + TimeSpan time = ts.TimeOfDay; - public Hashtable StaffInfo { get; set; } + int hour = time.Hours; - public void AddPage( PageInfo info ) - { - lock ( SaveLock ) - Pages.Add( info ); + totals[hour] += QueueStats[i].Count; + counts[hour]++; + } + } - info.History = this; - } - - public StaffHistory() - { - Pages = new PageInfoCollection(); - QueueStats = new QueueStatusCollection(); - - UserInfo = new Hashtable( StringComparer.OrdinalIgnoreCase ); - StaffInfo = new Hashtable( StringComparer.OrdinalIgnoreCase ); - } - - public StaffInfo GetStaffInfo( string account ) - { - lock ( RenderLock ) - { - if ( string.IsNullOrEmpty(account) ) - return null; - - if ( !(StaffInfo[account] is StaffInfo info) ) - StaffInfo[account] = info = new StaffInfo( account ); - - return info; - } - } - - public UserInfo GetUserInfo( string account ) - { - if ( string.IsNullOrEmpty(account) ) - return null; - - if ( !(UserInfo[account] is UserInfo info) ) - UserInfo[account] = info = new UserInfo( account ); - - return info; - } - - public static readonly object RenderLock = new object(); - public static readonly object SaveLock = new object(); - - public void Save() - { - lock ( SaveLock ) - { - string path = Path.Combine( Core.BaseDirectory, "staffHistory.xml" ); - PersistanceWriter pw = new XmlPersistanceWriter( path, "Staff" ); + BarGraph barGraph = new BarGraph("Average pages in queue", "graph_pagequeue_avg", 10, "Time", "Pages", + BarGraphRenderMode.Lines); - pw.WriteDocument( this ); + barGraph.FontSize = 6; - pw.Close(); - } - } + for (int i = 7; i <= totals.Length + 7; ++i) + { + int val; - public void Load() - { - string path = Path.Combine( Core.BaseDirectory, "staffHistory.xml" ); + if (counts[i % totals.Length] == 0) + val = 0; + else + val = (totals[i % totals.Length] + counts[i % totals.Length] / 2) / counts[i % totals.Length]; - if ( !File.Exists( path ) ) - return; + int realHours = i % totals.Length; + int hours; - PersistanceReader pr = new XmlPersistanceReader( path, "Staff" ); - - pr.ReadDocument( this ); + if (realHours == 0) + hours = 12; + else if (realHours > 12) + hours = realHours - 12; + else + hours = realHours; - pr.Close(); - } + barGraph.Items.Add(hours + (realHours >= 12 ? " PM" : " AM"), val); + } - public override void SerializeChildren( PersistanceWriter op ) - { - for ( int i = 0; i < Pages.Count; ++i ) - Pages[i].Serialize( op ); + return barGraph; + } - for ( int i = 0; i < QueueStats.Count; ++i ) - QueueStats[i].Serialize( op ); - } + private BarGraph GraphHourlyPages(StaffInfo staff) + { + return GraphHourlyPages(staff.Pages, PageResolution.Handled, "Average pages handled by " + staff.Display, + "graphs_" + staff.Account.ToLower() + "_avg"); + } - public override void DeserializeChildren( PersistanceReader ip ) - { - DateTime min = DateTime.UtcNow - TimeSpan.FromDays( 8.0 ); + private BarGraph GraphHourlyPages(PageInfoCollection pages, PageResolution res, string title, string fname) + { + int[] totals = new int[24]; + int[] counts = new int[24]; - while ( ip.HasChild ) - { - PersistableObject obj = ip.GetChild(); + DateTime[] dates = new DateTime[24]; - if ( obj is PageInfo pageInfo ) - { - pageInfo.UpdateResolver(); + DateTime max = DateTime.UtcNow; + DateTime min = max - TimeSpan.FromDays(7.0); - if ( pageInfo.TimeSent >= min || pageInfo.TimeResolved >= min ) - { - Pages.Add( pageInfo ); - pageInfo.History = this; - } - else - { - pageInfo.Sender = null; - pageInfo.Resolver = null; - } - } - else if ( obj is QueueStatus queueStatus ) - { - if ( queueStatus.TimeStamp >= min ) - QueueStats.Add( queueStatus ); - } - } - } + bool sentStamp = res == PageResolution.None; - public StaffInfo[] GetStaff() - { - StaffInfo[] staff = new StaffInfo[StaffInfo.Count]; - int index = 0; + for (int i = 0; i < pages.Count; ++i) + { + if (res != PageResolution.None && pages[i].Resolution != res) + continue; - foreach ( StaffInfo staffInfo in StaffInfo.Values ) - staff[index++] = staffInfo; + DateTime ts = sentStamp ? pages[i].TimeSent : pages[i].TimeResolved; - return staff; - } + if (ts >= min && ts < max) + { + DateTime date = ts.Date; + TimeSpan time = ts.TimeOfDay; - public void Render( ObjectCollection objects ) - { - lock ( RenderLock ) - { - objects.Add( GraphQueueStatus() ); + int hour = time.Hours; - StaffInfo[] staff = GetStaff(); + totals[hour]++; - BaseInfo.SortRange = TimeSpan.FromDays( 7.0 ); - Array.Sort( staff ); + if (dates[hour] != date) + { + counts[hour]++; + dates[hour] = date; + } + } + } - objects.Add( GraphHourlyPages( Pages, PageResolution.None, "New pages by hour", "graph_new_pages_hr" ) ); - objects.Add( GraphHourlyPages( Pages, PageResolution.Handled, "Handled pages by hour", "graph_handled_pages_hr" ) ); - objects.Add( GraphHourlyPages( Pages, PageResolution.Deleted, "Deleted pages by hour", "graph_deleted_pages_hr" ) ); - objects.Add( GraphHourlyPages( Pages, PageResolution.Canceled, "Canceled pages by hour", "graph_canceled_pages_hr" ) ); - objects.Add( GraphHourlyPages( Pages, PageResolution.Logged, "Logged-out pages by hour", "graph_logged_pages_hr" ) ); + BarGraph barGraph = new BarGraph(title, fname, 10, "Time", "Pages", BarGraphRenderMode.Lines); - BaseInfo.SortRange = TimeSpan.FromDays( 1.0 ); - Array.Sort( staff ); - - objects.Add( ReportTotalPages( staff, TimeSpan.FromDays( 1.0 ), "1 Day" ) ); - objects.AddRange( (PersistableObject[])ChartTotalPages( staff, TimeSpan.FromDays( 1.0 ), "1 Day", "graph_daily_pages" ) ); - - BaseInfo.SortRange = TimeSpan.FromDays( 7.0 ); - Array.Sort( staff ); + barGraph.FontSize = 6; - objects.Add( ReportTotalPages( staff, TimeSpan.FromDays( 7.0 ), "1 Week" ) ); - objects.AddRange( (PersistableObject[])ChartTotalPages( staff, TimeSpan.FromDays( 7.0 ), "1 Week", "graph_weekly_pages" ) ); + for (int i = 7; i <= totals.Length + 7; ++i) + { + int val; - BaseInfo.SortRange = TimeSpan.FromDays( 30.0 ); - Array.Sort( staff ); + if (counts[i % totals.Length] == 0) + val = 0; + else + val = (totals[i % totals.Length] + counts[i % totals.Length] / 2) / counts[i % totals.Length]; - objects.Add( ReportTotalPages( staff, TimeSpan.FromDays( 30.0 ), "1 Month" ) ); - objects.AddRange( (PersistableObject[])ChartTotalPages( staff, TimeSpan.FromDays( 30.0 ), "1 Month", "graph_monthly_pages" ) ); + int realHours = i % totals.Length; + int hours; - for ( int i = 0; i < staff.Length; ++i ) - objects.Add( GraphHourlyPages( staff[i] ) ); - } - } + if (realHours == 0) + hours = 12; + else if (realHours > 12) + hours = realHours - 12; + else + hours = realHours; - public static int GetPageCount( StaffInfo staff, DateTime min, DateTime max ) - { - return GetPageCount( staff.Pages, PageResolution.Handled, min, max ); - } + barGraph.Items.Add(hours + (realHours >= 12 ? " PM" : " AM"), val); + } - public static int GetPageCount( PageInfoCollection pages, PageResolution res, DateTime min, DateTime max ) - { - int count = 0; + return barGraph; + } - for ( int i = 0; i < pages.Count; ++i ) - { - if ( res != PageResolution.None && pages[i].Resolution != res ) - continue; + private Report ReportTotalPages(StaffInfo[] staff, TimeSpan ts, string title) + { + DateTime max = DateTime.UtcNow; + DateTime min = max - ts; - DateTime ts = pages[i].TimeResolved; - - if ( ts >= min && ts < max ) - ++count; - } + Report report = new Report(title + " Staff Report", "400"); - return count; - } + report.Columns.Add("65%", "left", "Staff Name"); + report.Columns.Add("35%", "center", "Page Count"); - private BarGraph GraphQueueStatus() - { - int[] totals = new int[24]; - int[] counts = new int[24]; + for (int i = 0; i < staff.Length; ++i) + report.Items.Add(staff[i].Display, GetPageCount(staff[i], min, max)); - DateTime max = DateTime.UtcNow; - DateTime min = max - TimeSpan.FromDays( 7.0 ); + return report; + } - for ( int i = 0; i < QueueStats.Count; ++i ) - { - DateTime ts = QueueStats[i].TimeStamp; + private PieChart[] ChartTotalPages(StaffInfo[] staff, TimeSpan ts, string title, string fname) + { + DateTime max = DateTime.UtcNow; + DateTime min = max - ts; - if ( ts >= min && ts < max ) - { - DateTime date = ts.Date; - TimeSpan time = ts.TimeOfDay; + PieChart staffChart = new PieChart(title + " Staff Chart", fname + "_staff", true); - int hour = time.Hours; + int other = 0; - totals[hour] += QueueStats[i].Count; - counts[hour]++; - } - } + for (int i = 0; i < staff.Length; ++i) + { + int count = GetPageCount(staff[i], min, max); - BarGraph barGraph = new BarGraph( "Average pages in queue", "graph_pagequeue_avg", 10, "Time", "Pages", BarGraphRenderMode.Lines ); + if (i < 12 && count > 0) + staffChart.Items.Add(staff[i].Display, count); + else + other += count; + } - barGraph.FontSize = 6; + if (other > 0) + staffChart.Items.Add("Other", other); - for ( int i = 7; i <= totals.Length+7; ++i ) - { - int val; + PieChart resChart = new PieChart(title + " Resolutions", fname + "_resol", true); - if ( counts[i%totals.Length] == 0 ) - val = 0; - else - val = (totals[i%totals.Length] + (counts[i%totals.Length] / 2)) / counts[i%totals.Length]; + int countTotal = GetPageCount(Pages, PageResolution.None, min, max); + int countHandled = GetPageCount(Pages, PageResolution.Handled, min, max); + int countDeleted = GetPageCount(Pages, PageResolution.Deleted, min, max); + int countCanceled = GetPageCount(Pages, PageResolution.Canceled, min, max); + int countLogged = GetPageCount(Pages, PageResolution.Logged, min, max); + int countUnres = countTotal - (countHandled + countDeleted + countCanceled + countLogged); - int realHours = i%totals.Length; - int hours; + resChart.Items.Add("Handled", countHandled); + resChart.Items.Add("Deleted", countDeleted); + resChart.Items.Add("Canceled", countCanceled); + resChart.Items.Add("Logged Out", countLogged); + resChart.Items.Add("Unresolved", countUnres); - if ( realHours == 0 ) - hours = 12; - else if ( realHours > 12 ) - hours = realHours - 12; - else - hours = realHours; + return new[] { staffChart, resChart }; + } - barGraph.Items.Add( hours + (realHours >= 12 ? " PM" : " AM"), val ); - } + #region Type Identification - return barGraph; - } + private static PersistableObject Construct() + { + return new StaffHistory(); + } - private BarGraph GraphHourlyPages( StaffInfo staff ) - { - return GraphHourlyPages( staff.Pages, PageResolution.Handled, "Average pages handled by " + staff.Display, "graphs_" + staff.Account.ToLower() + "_avg" ); - } + public override PersistableType TypeID => ThisTypeID; - private BarGraph GraphHourlyPages( PageInfoCollection pages, PageResolution res, string title, string fname ) - { - int[] totals = new int[24]; - int[] counts = new int[24]; - - DateTime[] dates = new DateTime[24]; - - DateTime max = DateTime.UtcNow; - DateTime min = max - TimeSpan.FromDays( 7.0 ); - - bool sentStamp = ( res == PageResolution.None ); - - for ( int i = 0; i < pages.Count; ++i ) - { - if ( res != PageResolution.None && pages[i].Resolution != res ) - continue; - - DateTime ts = ( sentStamp ? pages[i].TimeSent : pages[i].TimeResolved ); - - if ( ts >= min && ts < max ) - { - DateTime date = ts.Date; - TimeSpan time = ts.TimeOfDay; - - int hour = time.Hours; - - totals[hour]++; - - if ( dates[hour] != date ) - { - counts[hour]++; - dates[hour] = date; - } - } - } - - BarGraph barGraph = new BarGraph( title, fname, 10, "Time", "Pages", BarGraphRenderMode.Lines ); - - barGraph.FontSize = 6; - - for ( int i = 7; i <= totals.Length+7; ++i ) - { - int val; - - if ( counts[i%totals.Length] == 0 ) - val = 0; - else - val = (totals[i%totals.Length] + (counts[i%totals.Length] / 2)) / counts[i%totals.Length]; - - int realHours = i%totals.Length; - int hours; - - if ( realHours == 0 ) - hours = 12; - else if ( realHours > 12 ) - hours = realHours - 12; - else - hours = realHours; - - barGraph.Items.Add( hours + (realHours >= 12 ? " PM" : " AM"), val ); - } - - return barGraph; - } - - private Report ReportTotalPages( StaffInfo[] staff, TimeSpan ts, string title ) - { - DateTime max = DateTime.UtcNow; - DateTime min = max - ts; - - Report report = new Report( title + " Staff Report", "400" ); - - report.Columns.Add( "65%", "left", "Staff Name" ); - report.Columns.Add( "35%", "center", "Page Count" ); - - for ( int i = 0; i < staff.Length; ++i ) - report.Items.Add( staff[i].Display, GetPageCount( staff[i], min, max ) ); - - return report; - } - - private PieChart[] ChartTotalPages( StaffInfo[] staff, TimeSpan ts, string title, string fname ) - { - DateTime max = DateTime.UtcNow; - DateTime min = max - ts; - - PieChart staffChart = new PieChart( title + " Staff Chart", fname + "_staff", true ); - - int other = 0; - - for ( int i = 0; i < staff.Length; ++i ) - { - int count = GetPageCount( staff[i], min, max ); - - if ( i < 12 && count > 0 ) - staffChart.Items.Add( staff[i].Display, count ); - else - other += count; - } - - if ( other > 0 ) - staffChart.Items.Add( "Other", other ); - - PieChart resChart = new PieChart( title + " Resolutions", fname + "_resol", true ); - - int countTotal = GetPageCount( Pages, PageResolution.None, min, max ); - int countHandled = GetPageCount( Pages, PageResolution.Handled, min, max ); - int countDeleted = GetPageCount( Pages, PageResolution.Deleted, min, max ); - int countCanceled = GetPageCount( Pages, PageResolution.Canceled, min, max ); - int countLogged = GetPageCount( Pages, PageResolution.Logged, min, max ); - int countUnres = countTotal - ( countHandled + countDeleted + countCanceled + countLogged ); - - resChart.Items.Add( "Handled", countHandled ); - resChart.Items.Add( "Deleted", countDeleted ); - resChart.Items.Add( "Canceled", countCanceled ); - resChart.Items.Add( "Logged Out", countLogged ); - resChart.Items.Add( "Unresolved", countUnres ); - - return new[]{ staffChart, resChart }; - } - } -} + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Persistance/PersistableObject.cs b/Scripts/Engines/Reports/Persistance/PersistableObject.cs index 0bb83aa1c..0d26608f0 100644 --- a/Scripts/Engines/Reports/Persistance/PersistableObject.cs +++ b/Scripts/Engines/Reports/Persistance/PersistableObject.cs @@ -1,48 +1,44 @@ namespace Server.Engines.Reports { - public abstract class PersistableObject - { - public abstract PersistableType TypeID{ get; } + public abstract class PersistableObject + { + public abstract PersistableType TypeID{ get; } - public virtual void SerializeAttributes( PersistanceWriter op ) - { - } + public virtual void SerializeAttributes(PersistanceWriter op) + { + } - public virtual void SerializeChildren( PersistanceWriter op ) - { - } + public virtual void SerializeChildren(PersistanceWriter op) + { + } - public void Serialize( PersistanceWriter op ) - { - op.BeginObject( TypeID ); - SerializeAttributes( op ); - op.BeginChildren(); - SerializeChildren( op ); - op.FinishChildren(); - op.FinishObject(); - } + public void Serialize(PersistanceWriter op) + { + op.BeginObject(TypeID); + SerializeAttributes(op); + op.BeginChildren(); + SerializeChildren(op); + op.FinishChildren(); + op.FinishObject(); + } - public virtual void DeserializeAttributes( PersistanceReader ip ) - { - } + public virtual void DeserializeAttributes(PersistanceReader ip) + { + } - public virtual void DeserializeChildren( PersistanceReader ip ) - { - } + public virtual void DeserializeChildren(PersistanceReader ip) + { + } - public void Deserialize( PersistanceReader ip ) - { - DeserializeAttributes( ip ); + public void Deserialize(PersistanceReader ip) + { + DeserializeAttributes(ip); - if ( ip.BeginChildren() ) - { - DeserializeChildren( ip ); - ip.FinishChildren(); - } - } - - public PersistableObject() - { - } - } + if (ip.BeginChildren()) + { + DeserializeChildren(ip); + ip.FinishChildren(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Persistance/PersistableObjectCollection.cs b/Scripts/Engines/Reports/Persistance/PersistableObjectCollection.cs index 8df497aa8..b0b77b560 100644 --- a/Scripts/Engines/Reports/Persistance/PersistableObjectCollection.cs +++ b/Scripts/Engines/Reports/Persistance/PersistableObjectCollection.cs @@ -8,187 +8,181 @@ // //------------------------------------------------------------------------------ +using System; +using System.Collections; + namespace Server.Engines.Reports { - using System.Collections; - - + /// + /// Strongly typed collection of Server.Engines.Reports.PersistableObject. + /// + public class ObjectCollection : CollectionBase + { /// - /// Strongly typed collection of Server.Engines.Reports.PersistableObject. + /// Gets or sets the value of the Server.Engines.Reports.PersistableObject at a specific position in the ObjectCollection. /// - public class ObjectCollection : CollectionBase + public PersistableObject this[int index] { - - /// - /// Default constructor. - /// - public ObjectCollection() : - base() - { - } - - /// - /// Gets or sets the value of the Server.Engines.Reports.PersistableObject at a specific position in the ObjectCollection. - /// - public PersistableObject this[int index] - { - get => ((PersistableObject)(List[index])); - set => List[index] = value; - } - - /// - /// Append a Server.Engines.Reports.PersistableObject entry to this collection. - /// - /// Server.Engines.Reports.PersistableObject instance. - /// The position into which the new element was inserted. - public int Add(PersistableObject value) - { - return List.Add(value); - } - - public void AddRange( PersistableObject[] col ) - { - InnerList.AddRange( col ); - } - - /// - /// Determines whether a specified Server.Engines.Reports.PersistableObject instance is in this collection. - /// - /// Server.Engines.Reports.PersistableObject instance to search for. - /// True if the Server.Engines.Reports.PersistableObject instance is in the collection; otherwise false. - public bool Contains(PersistableObject value) - { - return List.Contains(value); - } - - /// - /// Retrieve the index a specified Server.Engines.Reports.PersistableObject instance is in this collection. - /// - /// Server.Engines.Reports.PersistableObject instance to find. - /// The zero-based index of the specified Server.Engines.Reports.PersistableObject instance. If the object is not found, the return value is -1. - public int IndexOf(PersistableObject value) - { - return List.IndexOf(value); - } - - /// - /// Removes a specified Server.Engines.Reports.PersistableObject instance from this collection. - /// - /// The Server.Engines.Reports.PersistableObject instance to remove. - public void Remove(PersistableObject value) - { - List.Remove(value); - } - - /// - /// Returns an enumerator that can iterate through the Server.Engines.Reports.PersistableObject instance. - /// - /// An Server.Engines.Reports.PersistableObject's enumerator. - public new ObjectCollectionEnumerator GetEnumerator() - { - return new ObjectCollectionEnumerator(this); - } - - /// - /// Insert a Server.Engines.Reports.PersistableObject instance into this collection at a specified index. - /// - /// Zero-based index. - /// The Server.Engines.Reports.PersistableObject instance to insert. - public void Insert(int index, PersistableObject value) - { - List.Insert(index, value); - } - - /// - /// Strongly typed enumerator of Server.Engines.Reports.PersistableObject. - /// - public class ObjectCollectionEnumerator : IEnumerator - { - - /// - /// Current index - /// - private int _index; - - /// - /// Current element pointed to. - /// - private PersistableObject _currentElement; - - /// - /// Collection to enumerate. - /// - private ObjectCollection _collection; - - /// - /// Default constructor for enumerator. - /// - /// Instance of the collection to enumerate. - internal ObjectCollectionEnumerator(ObjectCollection collection) - { - _index = -1; - _collection = collection; - } - - /// - /// Gets the Server.Engines.Reports.PersistableObject object in the enumerated ObjectCollection currently indexed by this instance. - /// - public PersistableObject Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Gets the current element in the collection. - /// - object IEnumerator.Current - { - get - { - if (((_index == -1) - || (_index >= _collection.Count))) - { - throw new System.IndexOutOfRangeException("Enumerator not started."); - } - - return _currentElement; - } - } - - /// - /// Reset the cursor, so it points to the beginning of the enumerator. - /// - public void Reset() - { - _index = -1; - _currentElement = null; - } - - /// - /// Advances the enumerator to the next queue of the enumeration, if one is currently available. - /// - /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end of the enumeration. - public bool MoveNext() - { - if ((_index - < (_collection.Count - 1))) - { - _index = (_index + 1); - _currentElement = _collection[_index]; - return true; - } - _index = _collection.Count; - return false; - } - } + get => (PersistableObject)List[index]; + set => List[index] = value; } -} + + /// + /// Append a Server.Engines.Reports.PersistableObject entry to this collection. + /// + /// Server.Engines.Reports.PersistableObject instance. + /// The position into which the new element was inserted. + public int Add(PersistableObject value) + { + return List.Add(value); + } + + public void AddRange(PersistableObject[] col) + { + InnerList.AddRange(col); + } + + /// + /// Determines whether a specified Server.Engines.Reports.PersistableObject instance is in this collection. + /// + /// Server.Engines.Reports.PersistableObject instance to search for. + /// True if the Server.Engines.Reports.PersistableObject instance is in the collection; otherwise false. + public bool Contains(PersistableObject value) + { + return List.Contains(value); + } + + /// + /// Retrieve the index a specified Server.Engines.Reports.PersistableObject instance is in this collection. + /// + /// Server.Engines.Reports.PersistableObject instance to find. + /// + /// The zero-based index of the specified Server.Engines.Reports.PersistableObject instance. If the object is not + /// found, the return value is -1. + /// + public int IndexOf(PersistableObject value) + { + return List.IndexOf(value); + } + + /// + /// Removes a specified Server.Engines.Reports.PersistableObject instance from this collection. + /// + /// The Server.Engines.Reports.PersistableObject instance to remove. + public void Remove(PersistableObject value) + { + List.Remove(value); + } + + /// + /// Returns an enumerator that can iterate through the Server.Engines.Reports.PersistableObject instance. + /// + /// An Server.Engines.Reports.PersistableObject's enumerator. + public new ObjectCollectionEnumerator GetEnumerator() + { + return new ObjectCollectionEnumerator(this); + } + + /// + /// Insert a Server.Engines.Reports.PersistableObject instance into this collection at a specified index. + /// + /// Zero-based index. + /// The Server.Engines.Reports.PersistableObject instance to insert. + public void Insert(int index, PersistableObject value) + { + List.Insert(index, value); + } + + /// + /// Strongly typed enumerator of Server.Engines.Reports.PersistableObject. + /// + public class ObjectCollectionEnumerator : IEnumerator + { + /// + /// Collection to enumerate. + /// + private ObjectCollection _collection; + + /// + /// Current element pointed to. + /// + private PersistableObject _currentElement; + + /// + /// Current index + /// + private int _index; + + /// + /// Default constructor for enumerator. + /// + /// Instance of the collection to enumerate. + internal ObjectCollectionEnumerator(ObjectCollection collection) + { + _index = -1; + _collection = collection; + } + + /// + /// Gets the Server.Engines.Reports.PersistableObject object in the enumerated ObjectCollection currently indexed by this + /// instance. + /// + public PersistableObject Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Gets the current element in the collection. + /// + object IEnumerator.Current + { + get + { + if (_index == -1 + || _index >= _collection.Count) + throw new IndexOutOfRangeException("Enumerator not started."); + + return _currentElement; + } + } + + /// + /// Reset the cursor, so it points to the beginning of the enumerator. + /// + public void Reset() + { + _index = -1; + _currentElement = null; + } + + /// + /// Advances the enumerator to the next queue of the enumeration, if one is currently available. + /// + /// + /// true, if the enumerator was successfully advanced to the next queue; false, if the enumerator has reached the end + /// of the enumeration. + /// + public bool MoveNext() + { + if (_index + < _collection.Count - 1) + { + _index = _index + 1; + _currentElement = _collection[_index]; + return true; + } + + _index = _collection.Count; + return false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Persistance/PersistableType.cs b/Scripts/Engines/Reports/Persistance/PersistableType.cs index d1b17addb..9d1233d16 100644 --- a/Scripts/Engines/Reports/Persistance/PersistableType.cs +++ b/Scripts/Engines/Reports/Persistance/PersistableType.cs @@ -3,54 +3,54 @@ using System.Collections; namespace Server.Engines.Reports { - public delegate PersistableObject ConstructCallback(); + public delegate PersistableObject ConstructCallback(); - public sealed class PersistableTypeRegistry - { - private static Hashtable m_Table; + public sealed class PersistableTypeRegistry + { + private static Hashtable m_Table; - public static PersistableType Find( string name ) - { - return m_Table[name] as PersistableType; - } + static PersistableTypeRegistry() + { + m_Table = new Hashtable(StringComparer.OrdinalIgnoreCase); - public static void Register( PersistableType type ) - { - if ( type != null ) - m_Table[type.Name] = type; - } + Register(Report.ThisTypeID); + Register(BarGraph.ThisTypeID); + Register(PieChart.ThisTypeID); + Register(Snapshot.ThisTypeID); + Register(ItemValue.ThisTypeID); + Register(ChartItem.ThisTypeID); + Register(ReportItem.ThisTypeID); + Register(ReportColumn.ThisTypeID); + Register(SnapshotHistory.ThisTypeID); - static PersistableTypeRegistry() - { - m_Table = new Hashtable( StringComparer.OrdinalIgnoreCase ); + Register(PageInfo.ThisTypeID); + Register(QueueStatus.ThisTypeID); + Register(StaffHistory.ThisTypeID); + Register(ResponseInfo.ThisTypeID); + } - Register( Report.ThisTypeID ); - Register( BarGraph.ThisTypeID ); - Register( PieChart.ThisTypeID ); - Register( Snapshot.ThisTypeID ); - Register( ItemValue.ThisTypeID ); - Register( ChartItem.ThisTypeID ); - Register( ReportItem.ThisTypeID ); - Register( ReportColumn.ThisTypeID ); - Register( SnapshotHistory.ThisTypeID ); + public static PersistableType Find(string name) + { + return m_Table[name] as PersistableType; + } - Register( PageInfo.ThisTypeID ); - Register( QueueStatus.ThisTypeID ); - Register( StaffHistory.ThisTypeID ); - Register( ResponseInfo.ThisTypeID ); - } - } + public static void Register(PersistableType type) + { + if (type != null) + m_Table[type.Name] = type; + } + } - public sealed class PersistableType - { - public string Name { get; } + public sealed class PersistableType + { + public PersistableType(string name, ConstructCallback constructor) + { + Name = name; + Constructor = constructor; + } - public ConstructCallback Constructor { get; } + public string Name{ get; } - public PersistableType( string name, ConstructCallback constructor ) - { - Name = name; - Constructor = constructor; - } - } + public ConstructCallback Constructor{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Persistance/PersistanceReader.cs b/Scripts/Engines/Reports/Persistance/PersistanceReader.cs index 47f4c9fbe..46b1c77d6 100644 --- a/Scripts/Engines/Reports/Persistance/PersistanceReader.cs +++ b/Scripts/Engines/Reports/Persistance/PersistanceReader.cs @@ -4,113 +4,108 @@ using System.Xml; namespace Server.Engines.Reports { - public abstract class PersistanceReader - { - public abstract int GetInt32( string key ); - public abstract bool GetBoolean( string key ); - public abstract string GetString( string key ); - public abstract DateTime GetDateTime( string key ); + public abstract class PersistanceReader + { + public abstract bool HasChild{ get; } + public abstract int GetInt32(string key); + public abstract bool GetBoolean(string key); + public abstract string GetString(string key); + public abstract DateTime GetDateTime(string key); - public abstract bool BeginChildren(); - public abstract void FinishChildren(); - public abstract bool HasChild{ get; } - public abstract PersistableObject GetChild(); + public abstract bool BeginChildren(); + public abstract void FinishChildren(); + public abstract PersistableObject GetChild(); - public abstract void ReadDocument( PersistableObject root ); - public abstract void Close(); + public abstract void ReadDocument(PersistableObject root); + public abstract void Close(); + } - public PersistanceReader() - { - } - } + public class XmlPersistanceReader : PersistanceReader + { + private bool m_HasChild; + private StreamReader m_Reader; + private string m_Title; - public class XmlPersistanceReader : PersistanceReader - { - private StreamReader m_Reader; - private XmlTextReader m_Xml; - private string m_Title; + private bool m_WasEmptyElement; + private XmlTextReader m_Xml; - public XmlPersistanceReader( string filePath, string title ) - { - m_Reader = new StreamReader( filePath ); - m_Xml = new XmlTextReader( m_Reader ); - m_Xml.WhitespaceHandling=WhitespaceHandling.None; - m_Title = title; - } + public XmlPersistanceReader(string filePath, string title) + { + m_Reader = new StreamReader(filePath); + m_Xml = new XmlTextReader(m_Reader); + m_Xml.WhitespaceHandling = WhitespaceHandling.None; + m_Title = title; + } - public override int GetInt32( string key ) - { - return XmlConvert.ToInt32( m_Xml.GetAttribute( key ) ); - } + public override bool HasChild => m_HasChild; - public override bool GetBoolean( string key ) - { - return XmlConvert.ToBoolean( m_Xml.GetAttribute( key ) ); - } + public override int GetInt32(string key) + { + return XmlConvert.ToInt32(m_Xml.GetAttribute(key)); + } - public override string GetString( string key ) - { - return m_Xml.GetAttribute( key ); - } + public override bool GetBoolean(string key) + { + return XmlConvert.ToBoolean(m_Xml.GetAttribute(key)); + } - public override DateTime GetDateTime( string key ) - { - string val = m_Xml.GetAttribute( key ); + public override string GetString(string key) + { + return m_Xml.GetAttribute(key); + } - if ( val == null ) - return DateTime.MinValue; + public override DateTime GetDateTime(string key) + { + string val = m_Xml.GetAttribute(key); - return XmlConvert.ToDateTime( val, XmlDateTimeSerializationMode.Utc ); - } + if (val == null) + return DateTime.MinValue; - private bool m_HasChild; + return XmlConvert.ToDateTime(val, XmlDateTimeSerializationMode.Utc); + } - public override bool HasChild => m_HasChild; + public override bool BeginChildren() + { + m_HasChild = !m_WasEmptyElement; - private bool m_WasEmptyElement; + m_Xml.Read(); - public override bool BeginChildren() - { - m_HasChild = !m_WasEmptyElement; + return m_HasChild; + } - m_Xml.Read(); + public override void FinishChildren() + { + m_Xml.Read(); + } - return m_HasChild; - } + public override PersistableObject GetChild() + { + PersistableType type = PersistableTypeRegistry.Find(m_Xml.Name); + PersistableObject obj = type.Constructor(); - public override void FinishChildren() - { - m_Xml.Read(); - } + m_WasEmptyElement = m_Xml.IsEmptyElement; - public override PersistableObject GetChild() - { - PersistableType type = PersistableTypeRegistry.Find( m_Xml.Name ); - PersistableObject obj = type.Constructor(); + obj.Deserialize(this); - m_WasEmptyElement = m_Xml.IsEmptyElement; + m_HasChild = m_Xml.NodeType == XmlNodeType.Element; - obj.Deserialize( this ); + return obj; + } - m_HasChild = ( m_Xml.NodeType == XmlNodeType.Element ); + public override void ReadDocument(PersistableObject root) + { + Console.Write("Reports: {0}: Loading...", m_Title); + m_Xml.Read(); + m_Xml.Read(); + m_HasChild = !m_Xml.IsEmptyElement; + root.Deserialize(this); + Console.WriteLine("done"); + } - return obj; - } - - public override void ReadDocument( PersistableObject root ) - { - Console.Write( "Reports: {0}: Loading...", m_Title ); - m_Xml.Read(); - m_Xml.Read(); - m_HasChild = !m_Xml.IsEmptyElement; - root.Deserialize( this ); - Console.WriteLine( "done" ); - } - - public override void Close() - { - m_Xml.Close(); - m_Reader.Close(); - } - } + public override void Close() + { + m_Xml.Close(); + m_Reader.Close(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Persistance/PersistanceWriter.cs b/Scripts/Engines/Reports/Persistance/PersistanceWriter.cs index a3537c076..45f9be8c4 100644 --- a/Scripts/Engines/Reports/Persistance/PersistanceWriter.cs +++ b/Scripts/Engines/Reports/Persistance/PersistanceWriter.cs @@ -4,126 +4,122 @@ using System.Xml; namespace Server.Engines.Reports { - public abstract class PersistanceWriter - { - public abstract void SetInt32( string key, int value ); - public abstract void SetBoolean( string key, bool value ); - public abstract void SetString( string key, string value ); - public abstract void SetDateTime( string key, DateTime value ); + public abstract class PersistanceWriter + { + public abstract void SetInt32(string key, int value); + public abstract void SetBoolean(string key, bool value); + public abstract void SetString(string key, string value); + public abstract void SetDateTime(string key, DateTime value); - public abstract void BeginObject( PersistableType typeID ); - public abstract void BeginChildren(); - public abstract void FinishChildren(); - public abstract void FinishObject(); + public abstract void BeginObject(PersistableType typeID); + public abstract void BeginChildren(); + public abstract void FinishChildren(); + public abstract void FinishObject(); - public abstract void WriteDocument( PersistableObject root ); - public abstract void Close(); + public abstract void WriteDocument(PersistableObject root); + public abstract void Close(); + } - public PersistanceWriter() - { - } - } + public sealed class XmlPersistanceWriter : PersistanceWriter + { + private string m_RealFilePath; + private string m_TempFilePath; + private string m_Title; - public sealed class XmlPersistanceWriter : PersistanceWriter - { - private string m_RealFilePath; - private string m_TempFilePath; + private StreamWriter m_Writer; + private XmlTextWriter m_Xml; - private StreamWriter m_Writer; - private XmlTextWriter m_Xml; - private string m_Title; + public XmlPersistanceWriter(string filePath, string title) + { + m_RealFilePath = filePath; + m_TempFilePath = Path.ChangeExtension(filePath, ".tmp"); - public XmlPersistanceWriter( string filePath, string title ) - { - m_RealFilePath = filePath; - m_TempFilePath = Path.ChangeExtension( filePath, ".tmp" ); + m_Writer = new StreamWriter(m_TempFilePath); + m_Xml = new XmlTextWriter(m_Writer); - m_Writer = new StreamWriter( m_TempFilePath ); - m_Xml = new XmlTextWriter( m_Writer ); + m_Title = title; + } - m_Title = title; - } + public override void SetInt32(string key, int value) + { + m_Xml.WriteAttributeString(key, XmlConvert.ToString(value)); + } - public override void SetInt32( string key, int value ) - { - m_Xml.WriteAttributeString( key, XmlConvert.ToString( value ) ); - } + public override void SetBoolean(string key, bool value) + { + m_Xml.WriteAttributeString(key, XmlConvert.ToString(value)); + } - public override void SetBoolean( string key, bool value ) - { - m_Xml.WriteAttributeString( key, XmlConvert.ToString( value ) ); - } + public override void SetString(string key, string value) + { + if (value != null) + m_Xml.WriteAttributeString(key, value); + } - public override void SetString( string key, string value ) - { - if ( value != null ) - m_Xml.WriteAttributeString( key, value ); - } + public override void SetDateTime(string key, DateTime value) + { + if (value != DateTime.MinValue) + m_Xml.WriteAttributeString(key, XmlConvert.ToString(value, XmlDateTimeSerializationMode.Utc)); + } - public override void SetDateTime( string key, DateTime value ) - { - if ( value != DateTime.MinValue ) - m_Xml.WriteAttributeString( key, XmlConvert.ToString( value, XmlDateTimeSerializationMode.Utc ) ); - } + public override void BeginObject(PersistableType typeID) + { + m_Xml.WriteStartElement(typeID.Name); + } - public override void BeginObject( PersistableType typeID ) - { - m_Xml.WriteStartElement( typeID.Name ); - } + public override void BeginChildren() + { + } - public override void BeginChildren() - { - } + public override void FinishChildren() + { + } - public override void FinishChildren() - { - } + public override void FinishObject() + { + m_Xml.WriteEndElement(); + } - public override void FinishObject() - { - m_Xml.WriteEndElement(); - } + public override void WriteDocument(PersistableObject root) + { + Console.WriteLine("Reports: {0}: Save started", m_Title); - public override void WriteDocument( PersistableObject root ) - { - Console.WriteLine( "Reports: {0}: Save started", m_Title ); + m_Xml.Formatting = Formatting.Indented; + m_Xml.IndentChar = '\t'; + m_Xml.Indentation = 1; - m_Xml.Formatting = Formatting.Indented; - m_Xml.IndentChar = '\t'; - m_Xml.Indentation = 1; + m_Xml.WriteStartDocument(true); - m_Xml.WriteStartDocument( true ); + root.Serialize(this); - root.Serialize( this ); + Console.WriteLine("Reports: {0}: Save complete", m_Title); + } - Console.WriteLine( "Reports: {0}: Save complete", m_Title ); - } + public override void Close() + { + m_Xml.Close(); + m_Writer.Close(); - public override void Close() - { - m_Xml.Close(); - m_Writer.Close(); + try + { + string renamed = null; - try - { - string renamed = null; - - if ( File.Exists( m_RealFilePath ) ) - { - renamed = Path.ChangeExtension( m_RealFilePath, ".rem" ); - File.Move( m_RealFilePath, renamed ); - File.Move( m_TempFilePath, m_RealFilePath ); - File.Delete( renamed ); - } - else - { - File.Move( m_TempFilePath, m_RealFilePath ); - } - } - catch ( Exception ex ) - { - Console.WriteLine( ex ); - } - } - } + if (File.Exists(m_RealFilePath)) + { + renamed = Path.ChangeExtension(m_RealFilePath, ".rem"); + File.Move(m_RealFilePath, renamed); + File.Move(m_TempFilePath, m_RealFilePath); + File.Delete(renamed); + } + else + { + File.Move(m_TempFilePath, m_RealFilePath); + } + } + catch (Exception ex) + { + Console.WriteLine(ex); + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Rendering/BarGraphRenderer.cs b/Scripts/Engines/Reports/Rendering/BarGraphRenderer.cs index 10e3b924d..8abb67f31 100644 --- a/Scripts/Engines/Reports/Rendering/BarGraphRenderer.cs +++ b/Scripts/Engines/Reports/Rendering/BarGraphRenderer.cs @@ -1,891 +1,934 @@ using System; using System.Drawing; -using System.Drawing.Imaging; using System.Drawing.Drawing2D; +using System.Drawing.Imaging; +using System.Windows.Forms; namespace Server.Engines.Reports { - // Modified from MS sample - - //********************************************************************* - // - // BarGraph Class - // - // This class uses GDI+ to render Bar Chart. - // - //********************************************************************* - - public class BarRegion - { - public int m_RangeFrom, m_RangeTo; - public string m_Name; - - public BarRegion( int rangeFrom, int rangeTo, string name ) - { - m_RangeFrom = rangeFrom; - m_RangeTo = rangeTo; - m_Name = name; - } - } - - public class BarGraphRenderer : ChartRenderer - { - private const float _graphLegendSpacer = 15F; - private const float _labelFontSize = 7f; - private const int _legendFontSize = 9; - private const float _legendRectangleSize = 10F; - private const float _spacer = 5F; - - public BarRegion[] _regions; - - // Overall related members - private Color _backColor; - private string _longestTickValue = string.Empty; // Used to calculate max value width - private float _maxTickValueWidth; // Used to calculate left offset of bar graph - private float _totalHeight; - private float _totalWidth; - - // Graph related members - private float _barWidth; - private float _bottomBuffer; // Space from bottom to x axis - private Color _fontColor; - private float _graphHeight; - private float _graphWidth; - private float _maxValue; // = final tick value * tick count - private float _scaleFactor; // = _maxValue / _graphHeight - private float _spaceBtwBars; // For now same as _barWidth - private float _topBuffer; // Space from top to the top of y axis - private float _xOrigin; // x position where graph starts drawing - private float _yOrigin; // y position where graph starts drawing - private float _yTickValue; // Value for each tick = _maxValue/_yTickCount - - // Legend related members - private float _legendWidth; - private string _longestLabel = string.Empty; // Used to calculate legend width - private float _maxLabelWidth; - - public string FontFamily { get; set; } - - public BarGraphRenderMode RenderMode { get; set; } - - public Color BackgroundColor - { - set => _backColor = value; - } - - public int BottomBuffer - { - set => _bottomBuffer = Convert.ToSingle(value); - } - - public Color FontColor - { - set => _fontColor = value; - } - - public int Height - { - get => Convert.ToInt32(_totalHeight); - set => _totalHeight = Convert.ToSingle(value); - } - - public int Width - { - get => Convert.ToInt32(_totalWidth); - set => _totalWidth = Convert.ToSingle(value); - } - - public bool ShowLegend { get; set; } - - public bool ShowData { get; set; } - - public int TopBuffer - { - set => _topBuffer = Convert.ToSingle(value); - } - - public string VerticalLabel { get; set; } - - public int VerticalTickCount { get; set; } - - private string _xTitle, _yTitle; - - public void SetTitles( string xTitle, string yTitle ) - { - _xTitle = xTitle; - _yTitle = yTitle; - } - - public BarGraphRenderer() - { - AssignDefaultSettings(); - } - - public BarGraphRenderer(Color bgColor) - { - AssignDefaultSettings(); - BackgroundColor = bgColor; - } - - //********************************************************************* - // - // This method collects all data points and calculate all the necessary dimensions - // to draw the bar graph. It is the method called before invoking the Draw() method. - // labels is the x values. - // values is the y values. - // - //********************************************************************* - - public void CollectDataPoints(string[] labels, string[] values) - { - if (labels.Length == values.Length) - { - for(int i=0; i _xOrigin+_graphWidth ) - rc.Width = _xOrigin+_graphWidth-rc.X; - - using ( SolidBrush brsh = new SolidBrush( Color.FromArgb( 48, GetColor( i ) ) ) ) - gfx.FillRectangle( brsh, rc ); - - rc.Offset( (rc.Width - 200.0f) * 0.5f, -16.0f ); - rc.Width = 200.0f; - rc.Height = 20.0f; - - gfx.DrawString( reg.m_Name, font, textBrush, rc, textFormat ); - } - } - } - } - } - } - } - - //********************************************************************* - // - // This method returns a bar graph bitmap to the calling function. It is called after - // all dimensions and data points are calculated. - // - //********************************************************************* - - public override Bitmap Draw() - { - int height = Convert.ToInt32(_totalHeight); - int width = Convert.ToInt32(_totalWidth); - - Bitmap bmp = new Bitmap(width, height); - - using(Graphics graph = Graphics.FromImage(bmp)) - { - graph.CompositingQuality = CompositingQuality.HighQuality; - graph.SmoothingMode = SmoothingMode.AntiAlias; - - using ( SolidBrush brsh = new SolidBrush( _backColor ) ) - graph.FillRectangle(brsh, -1, -1, bmp.Width+1, bmp.Height+1); - - DrawRegions(graph); - DrawVerticalLabelArea(graph); - DrawXLabelBack(graph); - DrawBars(graph); - DrawXLabelArea(graph); - - if (ShowLegend) - DrawLegend(graph); - } - - return bmp; - } - - //********************************************************************* - // - // This method draws all the bars for the graph. - // - //********************************************************************* - - public int _interval; - - private void DrawBars(Graphics graph) - { - SolidBrush brsFont = null; - Font valFont = null; - StringFormat sfFormat = null; - - try - { - brsFont = new SolidBrush(_fontColor); - valFont = new Font(FontFamily, _labelFontSize); - sfFormat = new StringFormat(); - sfFormat.Alignment = StringAlignment.Center; - int i = 0; - - PointF[] linePoints = null; - - if ( RenderMode == BarGraphRenderMode.Lines ) - linePoints = new PointF[DataPoints.Count]; - - int pointIndex = 0; - - // Draw bars and the value above each bar - using ( Pen pen = new Pen(_fontColor,0.15f) ) - { - using ( SolidBrush whiteBrsh = new SolidBrush( Color.FromArgb( 128, Color.White ) ) ) - { - foreach(DataItem item in DataPoints) - { - using(SolidBrush barBrush = new SolidBrush(item.ItemColor)) - { - float itemY = _yOrigin + _graphHeight - item.SweepSize; - - if ( RenderMode == BarGraphRenderMode.Lines ) - { - linePoints[pointIndex++] = new PointF( _xOrigin + item.StartPos + (_barWidth / 2), itemY ); - } - else if ( RenderMode == BarGraphRenderMode.Bars ) - { - float ox = _xOrigin + item.StartPos; - float oy = itemY; - float ow = _barWidth; - float oh = item.SweepSize; - float of = 9.5f; - - PointF[] pts = { - new PointF( ox, oy ), - new PointF( ox + ow, oy ), - new PointF( ox + of, oy + of ), - new PointF( ox + of + ow, oy + of ), - new PointF( ox, oy + oh ), - new PointF( ox + of, oy + of + oh ), - new PointF( ox + of + ow, oy + of + oh ) - }; - - graph.FillPolygon( barBrush, new[]{ pts[2], pts[3], pts[6], pts[5] } ); - - using ( SolidBrush ltBrsh = new SolidBrush( System.Windows.Forms.ControlPaint.Light(item.ItemColor,0.1f) ) ) - graph.FillPolygon( ltBrsh, new[]{ pts[0], pts[2], pts[5], pts[4] } ); - - using ( SolidBrush drkBrush = new SolidBrush( System.Windows.Forms.ControlPaint.Dark(item.ItemColor,0.05f) ) ) - graph.FillPolygon( drkBrush, new[]{ pts[0], pts[1], pts[3], pts[2] } ); - - graph.DrawLine( pen, pts[0], pts[1] ); - graph.DrawLine( pen, pts[0], pts[2] ); - graph.DrawLine( pen, pts[1], pts[3] ); - graph.DrawLine( pen, pts[2], pts[3] ); - graph.DrawLine( pen, pts[2], pts[5] ); - graph.DrawLine( pen, pts[0], pts[4] ); - graph.DrawLine( pen, pts[4], pts[5] ); - graph.DrawLine( pen, pts[5], pts[6] ); - graph.DrawLine( pen, pts[3], pts[6] ); - - // Draw data value - if (ShowData&&(i%_interval)==0) - { - float sectionWidth = ( _barWidth + _spaceBtwBars ); - float startX = _xOrigin + (i * sectionWidth) + (sectionWidth / 2); // This draws the value on center of the bar - float startY = itemY - 2f - valFont.Height; // Positioned on top of each bar by 2 pixels - RectangleF recVal = new RectangleF(startX-((sectionWidth * _interval) / 2), startY, sectionWidth * _interval, valFont.Height); - SizeF sz = graph.MeasureString(item.Value.ToString("#,###.##"),valFont,recVal.Size,sfFormat); - //using ( SolidBrush brsh = new SolidBrush( Color.FromArgb( 180, 255, 255, 255 ) ) ) - // graph.FillRectangle( brsh, new RectangleF(recVal.X+((recVal.Width-sz.Width)/2),recVal.Y+((recVal.Height-sz.Height)/2),sz.Width+4,sz.Height) ); - - //graph.DrawString(item.Value.ToString("#,###.##"), valFont, brsFont, recVal, sfFormat); - - for ( int box = -1; box <= 1; ++box ) - { - for ( int boy = -1; boy <= 1; ++boy ) - { - if ( box == 0 && boy == 0 ) - continue; - - RectangleF rco = new RectangleF( recVal.X+box, recVal.Y+boy, recVal.Width, recVal.Height ); - graph.DrawString(item.Value.ToString("#,###.##"), valFont, whiteBrsh, rco, sfFormat); - } - } - - graph.DrawString(item.Value.ToString("#,###.##"), valFont, brsFont, recVal, sfFormat); - } - } - - i++; - } - } - - if ( RenderMode == BarGraphRenderMode.Lines ) - { - if ( linePoints.Length >= 2 ) - { - using ( Pen linePen = new Pen( Color.FromArgb(220,Color.Red), 2.5f ) ) - graph.DrawCurve( linePen, linePoints, 0.5f ); - } - - using ( Pen linePen = new Pen( Color.FromArgb(40,_fontColor), 0.8f ) ) - { - for ( int j = 0; j < linePoints.Length; ++j ) - { - graph.DrawLine( linePen, linePoints[j], new PointF( linePoints[j].X, _yOrigin + _graphHeight ) ); - - DataItem item = DataPoints[j]; - float itemY = _yOrigin + _graphHeight - item.SweepSize; - - // Draw data value - if (ShowData&&(j%_interval)==0) - { - graph.FillEllipse( brsFont, new RectangleF( linePoints[j].X-2.0f, linePoints[j].Y-2.0f, 4.0f, 4.0f ) ); - - float sectionWidth = ( _barWidth + _spaceBtwBars ); - float startX = _xOrigin + (j * sectionWidth) + (sectionWidth/2); // This draws the value on center of the bar - float startY = itemY - 2f - valFont.Height; // Positioned on top of each bar by 2 pixels - RectangleF recVal = new RectangleF(startX-((sectionWidth * _interval) / 2), startY, sectionWidth * _interval, valFont.Height); - SizeF sz = graph.MeasureString(item.Value.ToString("#,###.##"),valFont,recVal.Size,sfFormat); - //using ( SolidBrush brsh = new SolidBrush( Color.FromArgb( 48, 255, 255, 255 ) ) ) - // graph.FillRectangle( brsh, new RectangleF(recVal.X+((recVal.Width-sz.Width)/2),recVal.Y+((recVal.Height-sz.Height)/2),sz.Width+4,sz.Height) ); - - for ( int box = -1; box <= 1; ++box ) - { - for ( int boy = -1; boy <= 1; ++boy ) - { - if ( box == 0 && boy == 0 ) - continue; - - RectangleF rco = new RectangleF( recVal.X+box, recVal.Y+boy, recVal.Width, recVal.Height ); - graph.DrawString(item.Value.ToString("#,###.##"), valFont, whiteBrsh, rco, sfFormat); - } - } - - graph.DrawString(item.Value.ToString("#,###.##"), valFont, brsFont, recVal, sfFormat); - } - } - } - } - } - } - } - finally - { - brsFont?.Dispose(); - valFont?.Dispose(); - sfFormat?.Dispose(); - } - } - - //********************************************************************* - // - // This method draws the y label, tick marks, tick values, and the y axis. - // - //********************************************************************* - - private void DrawVerticalLabelArea(Graphics graph) - { - Font lblFont = null; - SolidBrush brs = null; - StringFormat lblFormat = null; - Pen pen = null; - StringFormat sfVLabel = null; - - float fo = (_yTitle==null?0.0f:20.0f); - - try - { - brs = new SolidBrush(_fontColor); - lblFormat = new StringFormat(); - pen = new Pen(_fontColor); - - if ( _yTitle != null ) - { - sfVLabel = new StringFormat(); - sfVLabel.Alignment = StringAlignment.Center; - sfVLabel.LineAlignment = StringAlignment.Center; - sfVLabel.FormatFlags=StringFormatFlags.DirectionVertical; - - lblFont = new Font(FontFamily, _labelFontSize+4.0f); - graph.DrawString(_yTitle,lblFont,brs,new RectangleF( 0.0f, _yOrigin, 20.0f, _graphHeight ), sfVLabel ); - lblFont.Dispose(); - } - - sfVLabel = new StringFormat(); - lblFormat.Alignment = StringAlignment.Far; - lblFormat.FormatFlags|=StringFormatFlags.NoClip; - - // Draw vertical label at the top of y-axis and place it in the middle top of y-axis - lblFont = new Font(FontFamily, _labelFontSize+2.0f,FontStyle.Bold); - RectangleF recVLabel = new RectangleF(0, _yOrigin-2*_spacer-lblFont.Height, _xOrigin*2, lblFont.Height); - sfVLabel.Alignment = StringAlignment.Center; - sfVLabel.FormatFlags|=StringFormatFlags.NoClip; - //graph.DrawRectangle(Pens.Black,Rectangle.Truncate(recVLabel)); - graph.DrawString(VerticalLabel, lblFont, brs, recVLabel, sfVLabel); - lblFont.Dispose(); - - lblFont = new Font(FontFamily, _labelFontSize); - // Draw all tick values and tick marks - using ( Pen smallPen = new Pen(Color.FromArgb(96,_fontColor),0.8f) ) - { - for (int i=0; i24?16.0f:0.0f), _graphWidth, 20.0f ), lblFormat ); - } - - lblFont = new Font(FontFamily, _labelFontSize); - lblFormat = new StringFormat(); - lblFormat.Alignment = StringAlignment.Center; - lblFormat.FormatFlags |= StringFormatFlags.NoClip; - lblFormat.Trimming = StringTrimming.None; - //lblFormat.FormatFlags |= StringFormatFlags.NoWrap; - - float of = 0.0f; - - if ( RenderMode == BarGraphRenderMode.Bars ) - { - of = 10.0f; - - // Draw x axis - graph.DrawLine( pen, _xOrigin + of, _yOrigin + _graphHeight + of, _xOrigin + _graphWidth + of, _yOrigin + _graphHeight + of ); - - graph.DrawLine( pen, _xOrigin, _yOrigin + _graphHeight, _xOrigin + of, _yOrigin + _graphHeight + of ); - graph.DrawLine( pen, _xOrigin + _graphWidth, _yOrigin + _graphHeight, _xOrigin + of + _graphWidth, _yOrigin + _graphHeight + of ); - } - - float currentX; - float currentY = _yOrigin + _graphHeight + 2.0f; // All x labels are drawn 2 pixels below x-axis - float labelWidth = _barWidth + _spaceBtwBars; // Fits exactly below the bar - int i = 0; - - // Draw x labels - foreach(DataItem item in DataPoints) - { - if ((i%_interval)==0) - { - currentX = _xOrigin + (i * labelWidth)+of+(labelWidth/2); - RectangleF recLbl = new RectangleF(currentX-((labelWidth*_interval)/2), currentY+of, labelWidth*_interval, lblFont.Height*2); - string lblString = ShowLegend ? item.Label : item.Description; // Decide what to show: short or long - - graph.DrawString(lblString, lblFont, brs, recLbl, lblFormat); - } - i++; - } - } - finally - { - lblFont?.Dispose(); - brs?.Dispose(); - lblFormat?.Dispose(); - pen?.Dispose(); - } - } - - //********************************************************************* - // - // This method determines where to place the legend box. - // It draws the legend border, legend description, and legend color code. - // - //********************************************************************* - - private void DrawLegend(Graphics graph) - { - Font lblFont = null; - SolidBrush brs = null; - StringFormat lblFormat = null; - Pen pen = null; - - try - { - lblFont = new Font(FontFamily, _legendFontSize); - brs = new SolidBrush(_fontColor); - lblFormat = new StringFormat(); - pen = new Pen(_fontColor); - lblFormat.Alignment = StringAlignment.Near; - - // Calculate Legend drawing start point - float startX = _xOrigin + _graphWidth + _graphLegendSpacer; - float startY = _yOrigin; - - float xColorCode = startX + _spacer; - float xLegendText = xColorCode + _legendRectangleSize + _spacer; - float legendHeight = 0.0f; - for(int i=0; i _maxTickValueWidth ) - _maxTickValueWidth = measured; - } - - float leftOffset = _spacer + _maxTickValueWidth + (_yTitle == null ? 0.0f : 20.0f); - float rtOffset = 0.0f; - - if (ShowLegend) - { - _legendWidth = _spacer + _legendRectangleSize + _spacer + _maxLabelWidth + _spacer; - rtOffset = _graphLegendSpacer + _legendWidth + _spacer; - } - else - rtOffset = _spacer; // Make graph in the middle - - if ( RenderMode == BarGraphRenderMode.Bars ) - rtOffset += 10.0f; - - rtOffset+=10.0f; - - _graphHeight = _totalHeight - _topBuffer - _bottomBuffer - (_xTitle == null ? 0.0f : 20.0f); // Buffer spaces are used to print labels - _graphWidth = _totalWidth - leftOffset - rtOffset; - _xOrigin = leftOffset; - _yOrigin = _topBuffer; - - // Once the correct _maxValue is determined, then calculate _scaleFactor - _scaleFactor = _maxValue / _graphHeight; - } - - //********************************************************************* - // - // This method determines the longest tick value from the given data points. - // The result is needed to calculate the correct graph dimension. - // - //********************************************************************* - - private void FindLongestTickValue() - { - float currentTick; - string tickString; - for (int i=0; i 2) - { - int midPostition = Convert.ToInt32(Math.Floor(text.Length/2.0)); - label = text.Substring(0,1) + text.Substring(midPostition, 1) + text.Substring(text.Length-1,1); - } - return label; - } - - //********************************************************************* - // - // This method calculates the max value and each tick mark value for the bar graph. - // - //********************************************************************* - - private void CalculateTickAndMax() - { - float tempMax = 0.0f; - - // Give graph some head room first about 10% of current max - _maxValue *= 1.1f; - - if (_maxValue != 0.0f) - { - // Find a rounded value nearest to the current max value - // Calculate this max first to give enough space to draw value on each bar - double exp = Convert.ToDouble(Math.Floor(Math.Log10(_maxValue))); - tempMax = Convert.ToSingle(Math.Ceiling(_maxValue / Math.Pow(10, exp)) * Math.Pow(10, exp)); - } - else - tempMax = 1.0f; - - // Once max value is calculated, tick value can be determined; tick value should be a whole number - _yTickValue = tempMax / VerticalTickCount; - double expTick = Convert.ToDouble(Math.Floor(Math.Log10(_yTickValue))); - _yTickValue = Convert.ToSingle(Math.Ceiling(_yTickValue / Math.Pow(10, expTick)) * Math.Pow(10, expTick)); - - // Re-calculate the max value with the new tick value - _maxValue = _yTickValue * VerticalTickCount; - } - - //********************************************************************* - // - // This method calculates the height for each bar in the graph - // - //********************************************************************* - - private void CalculateSweepValues() - { - // Called when all values and scale factor are known - // All values calculated here are relative from (_xOrigin, _yOrigin) - int i = 0; - foreach(DataItem item in DataPoints) - { - // This implementation does not support negative value - if (item.Value >= 0) item.SweepSize = item.Value/_scaleFactor; - - // (_spaceBtwBars/2) makes half white space for the first bar - item.StartPos = (_spaceBtwBars/2) + i * (_barWidth+_spaceBtwBars); - i++; - } - } - - //********************************************************************* - // - // This method calculates the width for each bar in the graph - // - //********************************************************************* - - private void CalculateBarWidth(int dataCount, float barGraphWidth) - { - // White space between each bar is the same as bar width itself - _barWidth = barGraphWidth / (dataCount * 2); // Each bar has 1 white space - //_barWidth =/* (float)Math.Floor(*/_barWidth/*)*/; - _spaceBtwBars = _barWidth; - } - - //********************************************************************* - // - // This method assigns default value to the bar graph properties and is only - // called from BarGraph constructors - // - //********************************************************************* - - private void AssignDefaultSettings() - { - // default values - _totalWidth = 680f; - _totalHeight = 450f; - FontFamily = "Verdana"; - _backColor = Color.White; - _fontColor = Color.Black; - _topBuffer = 30f; - _bottomBuffer = 30f; - VerticalTickCount = 2; - ShowLegend = false; - ShowData = false; - } - } -} + // Modified from MS sample + + //********************************************************************* + // + // BarGraph Class + // + // This class uses GDI+ to render Bar Chart. + // + //********************************************************************* + + public class BarRegion + { + public string m_Name; + public int m_RangeFrom, m_RangeTo; + + public BarRegion(int rangeFrom, int rangeTo, string name) + { + m_RangeFrom = rangeFrom; + m_RangeTo = rangeTo; + m_Name = name; + } + } + + public class BarGraphRenderer : ChartRenderer + { + private const float _graphLegendSpacer = 15F; + private const float _labelFontSize = 7f; + private const int _legendFontSize = 9; + private const float _legendRectangleSize = 10F; + private const float _spacer = 5F; + + // Overall related members + private Color _backColor; + + // Graph related members + private float _barWidth; + private float _bottomBuffer; // Space from bottom to x axis + private Color _fontColor; + private float _graphHeight; + private float _graphWidth; + + //********************************************************************* + // + // This method draws all the bars for the graph. + // + //********************************************************************* + + public int _interval; + + // Legend related members + private float _legendWidth; + private string _longestLabel = string.Empty; // Used to calculate legend width + private string _longestTickValue = string.Empty; // Used to calculate max value width + private float _maxLabelWidth; + private float _maxTickValueWidth; // Used to calculate left offset of bar graph + private float _maxValue; // = final tick value * tick count + + public BarRegion[] _regions; + private float _scaleFactor; // = _maxValue / _graphHeight + private float _spaceBtwBars; // For now same as _barWidth + private float _topBuffer; // Space from top to the top of y axis + private float _totalHeight; + private float _totalWidth; + private float _xOrigin; // x position where graph starts drawing + + private string _xTitle, _yTitle; + private float _yOrigin; // y position where graph starts drawing + private float _yTickValue; // Value for each tick = _maxValue/_yTickCount + + public BarGraphRenderer() + { + AssignDefaultSettings(); + } + + public BarGraphRenderer(Color bgColor) + { + AssignDefaultSettings(); + BackgroundColor = bgColor; + } + + public string FontFamily{ get; set; } + + public BarGraphRenderMode RenderMode{ get; set; } + + public Color BackgroundColor + { + set => _backColor = value; + } + + public int BottomBuffer + { + set => _bottomBuffer = Convert.ToSingle(value); + } + + public Color FontColor + { + set => _fontColor = value; + } + + public int Height + { + get => Convert.ToInt32(_totalHeight); + set => _totalHeight = Convert.ToSingle(value); + } + + public int Width + { + get => Convert.ToInt32(_totalWidth); + set => _totalWidth = Convert.ToSingle(value); + } + + public bool ShowLegend{ get; set; } + + public bool ShowData{ get; set; } + + public int TopBuffer + { + set => _topBuffer = Convert.ToSingle(value); + } + + public string VerticalLabel{ get; set; } + + public int VerticalTickCount{ get; set; } + + public void SetTitles(string xTitle, string yTitle) + { + _xTitle = xTitle; + _yTitle = yTitle; + } + + //********************************************************************* + // + // This method collects all data points and calculate all the necessary dimensions + // to draw the bar graph. It is the method called before invoking the Draw() method. + // labels is the x values. + // values is the y values. + // + //********************************************************************* + + public void CollectDataPoints(string[] labels, string[] values) + { + if (labels.Length == values.Length) + { + for (int i = 0; i < labels.Length; i++) + { + float temp = Convert.ToSingle(values[i]); + string shortLbl = MakeShortLabel(labels[i]); + + // For now put 0.0 for start position and sweep size + DataPoints.Add(new DataItem(shortLbl, labels[i], temp, 0.0f, 0.0f, GetColor(i))); + + // Find max value from data; this is only temporary _maxValue + if (_maxValue < temp) _maxValue = temp; + + // Find the longest description + if (ShowLegend) + { + string currentLbl = labels[i] + " (" + shortLbl + ")"; + float currentWidth = CalculateImgFontWidth(currentLbl, _legendFontSize, FontFamily); + if (_maxLabelWidth < currentWidth) + { + _longestLabel = currentLbl; + _maxLabelWidth = currentWidth; + } + } + } + + CalculateTickAndMax(); + CalculateGraphDimension(); + CalculateBarWidth(DataPoints.Count, _graphWidth); + CalculateSweepValues(); + } + else + { + throw new Exception("X data count is different from Y data count"); + } + } + + //********************************************************************* + // + // Same as above; called when user doesn't care about the x values + // + //********************************************************************* + + public void CollectDataPoints(string[] values) + { + string[] labels = values; + CollectDataPoints(labels, values); + } + + public void DrawRegions(Graphics gfx) + { + if (_regions == null) + return; + + using (StringFormat textFormat = new StringFormat()) + { + textFormat.Alignment = StringAlignment.Center; + textFormat.LineAlignment = StringAlignment.Center; + + using (Font font = new Font(FontFamily, _labelFontSize)) + { + using (Brush textBrush = new SolidBrush(_fontColor)) + { + using (Pen solidPen = new Pen(_fontColor)) + { + using (Pen lightPen = new Pen(Color.FromArgb(128, _fontColor))) + { + float labelWidth = _barWidth + _spaceBtwBars; + + for (int i = 0; i < _regions.Length; ++i) + { + BarRegion reg = _regions[i]; + + RectangleF rc = new RectangleF(_xOrigin + reg.m_RangeFrom * labelWidth, _yOrigin, + (reg.m_RangeTo - reg.m_RangeFrom + 1) * labelWidth, _graphHeight); + + if (rc.X + rc.Width > _xOrigin + _graphWidth) + rc.Width = _xOrigin + _graphWidth - rc.X; + + using (SolidBrush brsh = new SolidBrush(Color.FromArgb(48, GetColor(i)))) + { + gfx.FillRectangle(brsh, rc); + } + + rc.Offset((rc.Width - 200.0f) * 0.5f, -16.0f); + rc.Width = 200.0f; + rc.Height = 20.0f; + + gfx.DrawString(reg.m_Name, font, textBrush, rc, textFormat); + } + } + } + } + } + } + } + + //********************************************************************* + // + // This method returns a bar graph bitmap to the calling function. It is called after + // all dimensions and data points are calculated. + // + //********************************************************************* + + public override Bitmap Draw() + { + int height = Convert.ToInt32(_totalHeight); + int width = Convert.ToInt32(_totalWidth); + + Bitmap bmp = new Bitmap(width, height); + + using (Graphics graph = Graphics.FromImage(bmp)) + { + graph.CompositingQuality = CompositingQuality.HighQuality; + graph.SmoothingMode = SmoothingMode.AntiAlias; + + using (SolidBrush brsh = new SolidBrush(_backColor)) + { + graph.FillRectangle(brsh, -1, -1, bmp.Width + 1, bmp.Height + 1); + } + + DrawRegions(graph); + DrawVerticalLabelArea(graph); + DrawXLabelBack(graph); + DrawBars(graph); + DrawXLabelArea(graph); + + if (ShowLegend) + DrawLegend(graph); + } + + return bmp; + } + + private void DrawBars(Graphics graph) + { + SolidBrush brsFont = null; + Font valFont = null; + StringFormat sfFormat = null; + + try + { + brsFont = new SolidBrush(_fontColor); + valFont = new Font(FontFamily, _labelFontSize); + sfFormat = new StringFormat(); + sfFormat.Alignment = StringAlignment.Center; + int i = 0; + + PointF[] linePoints = null; + + if (RenderMode == BarGraphRenderMode.Lines) + linePoints = new PointF[DataPoints.Count]; + + int pointIndex = 0; + + // Draw bars and the value above each bar + using (Pen pen = new Pen(_fontColor, 0.15f)) + { + using (SolidBrush whiteBrsh = new SolidBrush(Color.FromArgb(128, Color.White))) + { + foreach (DataItem item in DataPoints) + using (SolidBrush barBrush = new SolidBrush(item.ItemColor)) + { + float itemY = _yOrigin + _graphHeight - item.SweepSize; + + if (RenderMode == BarGraphRenderMode.Lines) + { + linePoints[pointIndex++] = new PointF(_xOrigin + item.StartPos + _barWidth / 2, itemY); + } + else if (RenderMode == BarGraphRenderMode.Bars) + { + float ox = _xOrigin + item.StartPos; + float oy = itemY; + float ow = _barWidth; + float oh = item.SweepSize; + float of = 9.5f; + + PointF[] pts = + { + new PointF(ox, oy), + new PointF(ox + ow, oy), + new PointF(ox + of, oy + of), + new PointF(ox + of + ow, oy + of), + new PointF(ox, oy + oh), + new PointF(ox + of, oy + of + oh), + new PointF(ox + of + ow, oy + of + oh) + }; + + graph.FillPolygon(barBrush, new[] { pts[2], pts[3], pts[6], pts[5] }); + + using (SolidBrush ltBrsh = new SolidBrush(ControlPaint.Light(item.ItemColor, 0.1f))) + { + graph.FillPolygon(ltBrsh, new[] { pts[0], pts[2], pts[5], pts[4] }); + } + + using (SolidBrush drkBrush = new SolidBrush(ControlPaint.Dark(item.ItemColor, 0.05f))) + { + graph.FillPolygon(drkBrush, new[] { pts[0], pts[1], pts[3], pts[2] }); + } + + graph.DrawLine(pen, pts[0], pts[1]); + graph.DrawLine(pen, pts[0], pts[2]); + graph.DrawLine(pen, pts[1], pts[3]); + graph.DrawLine(pen, pts[2], pts[3]); + graph.DrawLine(pen, pts[2], pts[5]); + graph.DrawLine(pen, pts[0], pts[4]); + graph.DrawLine(pen, pts[4], pts[5]); + graph.DrawLine(pen, pts[5], pts[6]); + graph.DrawLine(pen, pts[3], pts[6]); + + // Draw data value + if (ShowData && i % _interval == 0) + { + float sectionWidth = _barWidth + _spaceBtwBars; + float startX = + _xOrigin + i * sectionWidth + + sectionWidth / 2; // This draws the value on center of the bar + float startY = + itemY - 2f - valFont.Height; // Positioned on top of each bar by 2 pixels + RectangleF recVal = new RectangleF(startX - sectionWidth * _interval / 2, startY, + sectionWidth * _interval, valFont.Height); + SizeF sz = graph.MeasureString(item.Value.ToString("#,###.##"), valFont, recVal.Size, + sfFormat); + //using ( SolidBrush brsh = new SolidBrush( Color.FromArgb( 180, 255, 255, 255 ) ) ) + // graph.FillRectangle( brsh, new RectangleF(recVal.X+((recVal.Width-sz.Width)/2),recVal.Y+((recVal.Height-sz.Height)/2),sz.Width+4,sz.Height) ); + + //graph.DrawString(item.Value.ToString("#,###.##"), valFont, brsFont, recVal, sfFormat); + + for (int box = -1; box <= 1; ++box) + for (int boy = -1; boy <= 1; ++boy) + { + if (box == 0 && boy == 0) + continue; + + RectangleF rco = new RectangleF(recVal.X + box, recVal.Y + boy, recVal.Width, + recVal.Height); + graph.DrawString(item.Value.ToString("#,###.##"), valFont, whiteBrsh, rco, + sfFormat); + } + + graph.DrawString(item.Value.ToString("#,###.##"), valFont, brsFont, recVal, + sfFormat); + } + } + + i++; + } + + if (RenderMode == BarGraphRenderMode.Lines) + { + if (linePoints.Length >= 2) + using (Pen linePen = new Pen(Color.FromArgb(220, Color.Red), 2.5f)) + { + graph.DrawCurve(linePen, linePoints, 0.5f); + } + + using (Pen linePen = new Pen(Color.FromArgb(40, _fontColor), 0.8f)) + { + for (int j = 0; j < linePoints.Length; ++j) + { + graph.DrawLine(linePen, linePoints[j], + new PointF(linePoints[j].X, _yOrigin + _graphHeight)); + + DataItem item = DataPoints[j]; + float itemY = _yOrigin + _graphHeight - item.SweepSize; + + // Draw data value + if (ShowData && j % _interval == 0) + { + graph.FillEllipse(brsFont, + new RectangleF(linePoints[j].X - 2.0f, linePoints[j].Y - 2.0f, 4.0f, 4.0f)); + + float sectionWidth = _barWidth + _spaceBtwBars; + float startX = + _xOrigin + j * sectionWidth + + sectionWidth / 2; // This draws the value on center of the bar + float startY = + itemY - 2f - valFont.Height; // Positioned on top of each bar by 2 pixels + RectangleF recVal = new RectangleF(startX - sectionWidth * _interval / 2, startY, + sectionWidth * _interval, valFont.Height); + SizeF sz = graph.MeasureString(item.Value.ToString("#,###.##"), valFont, recVal.Size, + sfFormat); + //using ( SolidBrush brsh = new SolidBrush( Color.FromArgb( 48, 255, 255, 255 ) ) ) + // graph.FillRectangle( brsh, new RectangleF(recVal.X+((recVal.Width-sz.Width)/2),recVal.Y+((recVal.Height-sz.Height)/2),sz.Width+4,sz.Height) ); + + for (int box = -1; box <= 1; ++box) + for (int boy = -1; boy <= 1; ++boy) + { + if (box == 0 && boy == 0) + continue; + + RectangleF rco = new RectangleF(recVal.X + box, recVal.Y + boy, recVal.Width, + recVal.Height); + graph.DrawString(item.Value.ToString("#,###.##"), valFont, whiteBrsh, rco, + sfFormat); + } + + graph.DrawString(item.Value.ToString("#,###.##"), valFont, brsFont, recVal, + sfFormat); + } + } + } + } + } + } + } + finally + { + brsFont?.Dispose(); + valFont?.Dispose(); + sfFormat?.Dispose(); + } + } + + //********************************************************************* + // + // This method draws the y label, tick marks, tick values, and the y axis. + // + //********************************************************************* + + private void DrawVerticalLabelArea(Graphics graph) + { + Font lblFont = null; + SolidBrush brs = null; + StringFormat lblFormat = null; + Pen pen = null; + StringFormat sfVLabel = null; + + float fo = _yTitle == null ? 0.0f : 20.0f; + + try + { + brs = new SolidBrush(_fontColor); + lblFormat = new StringFormat(); + pen = new Pen(_fontColor); + + if (_yTitle != null) + { + sfVLabel = new StringFormat(); + sfVLabel.Alignment = StringAlignment.Center; + sfVLabel.LineAlignment = StringAlignment.Center; + sfVLabel.FormatFlags = StringFormatFlags.DirectionVertical; + + lblFont = new Font(FontFamily, _labelFontSize + 4.0f); + graph.DrawString(_yTitle, lblFont, brs, new RectangleF(0.0f, _yOrigin, 20.0f, _graphHeight), sfVLabel); + lblFont.Dispose(); + } + + sfVLabel = new StringFormat(); + lblFormat.Alignment = StringAlignment.Far; + lblFormat.FormatFlags |= StringFormatFlags.NoClip; + + // Draw vertical label at the top of y-axis and place it in the middle top of y-axis + lblFont = new Font(FontFamily, _labelFontSize + 2.0f, FontStyle.Bold); + RectangleF recVLabel = + new RectangleF(0, _yOrigin - 2 * _spacer - lblFont.Height, _xOrigin * 2, lblFont.Height); + sfVLabel.Alignment = StringAlignment.Center; + sfVLabel.FormatFlags |= StringFormatFlags.NoClip; + //graph.DrawRectangle(Pens.Black,Rectangle.Truncate(recVLabel)); + graph.DrawString(VerticalLabel, lblFont, brs, recVLabel, sfVLabel); + lblFont.Dispose(); + + lblFont = new Font(FontFamily, _labelFontSize); + // Draw all tick values and tick marks + using (Pen smallPen = new Pen(Color.FromArgb(96, _fontColor), 0.8f)) + { + for (int i = 0; i < VerticalTickCount; i++) + { + float currentY = _topBuffer + i * _yTickValue / _scaleFactor; // Position for tick mark + float labelY = currentY - lblFont.Height / 2; // Place label in the middle of tick + RectangleF lblRec = new RectangleF(_spacer + fo - 6, labelY, _maxTickValueWidth, lblFont.Height); + + float currentTick = _maxValue - i * _yTickValue; // Calculate tick value from top to bottom + graph.DrawString(currentTick.ToString("#,###.##"), lblFont, brs, lblRec, + lblFormat); // Draw tick value + graph.DrawLine(pen, _xOrigin, currentY, _xOrigin - 4.0f, currentY); // Draw tick mark + + graph.DrawLine(smallPen, _xOrigin, currentY, _xOrigin + _graphWidth, currentY); + } + } + + // Draw y axis + graph.DrawLine(pen, _xOrigin, _yOrigin, _xOrigin, _yOrigin + _graphHeight); + } + finally + { + lblFont?.Dispose(); + brs?.Dispose(); + lblFormat?.Dispose(); + pen?.Dispose(); + sfVLabel?.Dispose(); + } + } + + //********************************************************************* + // + // This method draws x axis and all x labels + // + //********************************************************************* + + private void DrawXLabelBack(Graphics graph) + { + Font lblFont = null; + SolidBrush brs = null; + StringFormat lblFormat = null; + Pen pen = null; + + try + { + lblFont = new Font(FontFamily, _labelFontSize); + brs = new SolidBrush(_fontColor); + lblFormat = new StringFormat(); + pen = new Pen(_fontColor); + + lblFormat.Alignment = StringAlignment.Center; + + // Draw x axis + graph.DrawLine(pen, _xOrigin, _yOrigin + _graphHeight, _xOrigin + _graphWidth, _yOrigin + _graphHeight); + } + finally + { + lblFont?.Dispose(); + brs?.Dispose(); + lblFormat?.Dispose(); + pen?.Dispose(); + } + } + + private void DrawXLabelArea(Graphics graph) + { + Font lblFont = null; + SolidBrush brs = null; + StringFormat lblFormat = null; + Pen pen = null; + + try + { + brs = new SolidBrush(_fontColor); + pen = new Pen(_fontColor); + + if (_xTitle != null) + { + lblFormat = new StringFormat(); + lblFormat.Alignment = StringAlignment.Center; + lblFormat.LineAlignment = StringAlignment.Center; + // sfVLabel.FormatFlags=StringFormatFlags.DirectionVertical; + + lblFont = new Font(FontFamily, _labelFontSize + 2.0f, FontStyle.Bold); + graph.DrawString(_xTitle, lblFont, brs, + new RectangleF(_xOrigin, + _yOrigin + _graphHeight + 14.0f + (RenderMode == BarGraphRenderMode.Bars ? 10.0f : 0.0f) + + (DataPoints.Count / _interval > 24 ? 16.0f : 0.0f), _graphWidth, 20.0f), lblFormat); + } + + lblFont = new Font(FontFamily, _labelFontSize); + lblFormat = new StringFormat(); + lblFormat.Alignment = StringAlignment.Center; + lblFormat.FormatFlags |= StringFormatFlags.NoClip; + lblFormat.Trimming = StringTrimming.None; + //lblFormat.FormatFlags |= StringFormatFlags.NoWrap; + + float of = 0.0f; + + if (RenderMode == BarGraphRenderMode.Bars) + { + of = 10.0f; + + // Draw x axis + graph.DrawLine(pen, _xOrigin + of, _yOrigin + _graphHeight + of, _xOrigin + _graphWidth + of, + _yOrigin + _graphHeight + of); + + graph.DrawLine(pen, _xOrigin, _yOrigin + _graphHeight, _xOrigin + of, _yOrigin + _graphHeight + of); + graph.DrawLine(pen, _xOrigin + _graphWidth, _yOrigin + _graphHeight, _xOrigin + of + _graphWidth, + _yOrigin + _graphHeight + of); + } + + float currentX; + float currentY = _yOrigin + _graphHeight + 2.0f; // All x labels are drawn 2 pixels below x-axis + float labelWidth = _barWidth + _spaceBtwBars; // Fits exactly below the bar + int i = 0; + + // Draw x labels + foreach (DataItem item in DataPoints) + { + if (i % _interval == 0) + { + currentX = _xOrigin + i * labelWidth + of + labelWidth / 2; + RectangleF recLbl = new RectangleF(currentX - labelWidth * _interval / 2, currentY + of, + labelWidth * _interval, lblFont.Height * 2); + string lblString = ShowLegend ? item.Label : item.Description; // Decide what to show: short or long + + graph.DrawString(lblString, lblFont, brs, recLbl, lblFormat); + } + + i++; + } + } + finally + { + lblFont?.Dispose(); + brs?.Dispose(); + lblFormat?.Dispose(); + pen?.Dispose(); + } + } + + //********************************************************************* + // + // This method determines where to place the legend box. + // It draws the legend border, legend description, and legend color code. + // + //********************************************************************* + + private void DrawLegend(Graphics graph) + { + Font lblFont = null; + SolidBrush brs = null; + StringFormat lblFormat = null; + Pen pen = null; + + try + { + lblFont = new Font(FontFamily, _legendFontSize); + brs = new SolidBrush(_fontColor); + lblFormat = new StringFormat(); + pen = new Pen(_fontColor); + lblFormat.Alignment = StringAlignment.Near; + + // Calculate Legend drawing start point + float startX = _xOrigin + _graphWidth + _graphLegendSpacer; + float startY = _yOrigin; + + float xColorCode = startX + _spacer; + float xLegendText = xColorCode + _legendRectangleSize + _spacer; + float legendHeight = 0.0f; + for (int i = 0; i < DataPoints.Count; i++) + { + DataItem point = DataPoints[i]; + string text = point.Description + " (" + point.Label + ")"; + float currentY = startY + _spacer + i * (lblFont.Height + _spacer); + legendHeight += lblFont.Height + _spacer; + + // Draw legend description + graph.DrawString(text, lblFont, brs, xLegendText, currentY, lblFormat); + + // Draw color code + using (SolidBrush brsh = new SolidBrush(DataPoints[i].ItemColor)) + { + graph.FillRectangle(brsh, xColorCode, currentY + 3f, _legendRectangleSize, _legendRectangleSize); + } + } + + // Draw legend border + graph.DrawRectangle(pen, startX, startY, _legendWidth, legendHeight + _spacer); + } + finally + { + lblFont?.Dispose(); + brs?.Dispose(); + lblFormat?.Dispose(); + pen?.Dispose(); + } + } + + //********************************************************************* + // + // This method calculates all measurement aspects of the bar graph from the given data points + // + //********************************************************************* + + private void CalculateGraphDimension() + { + FindLongestTickValue(); + + // Need to add another character for spacing; this is not used for drawing, just for calculation + _longestTickValue += "0"; + //_maxTickValueWidth = CalculateImgFontWidth(_longestTickValue, _labelFontSize, FontFamily); + _maxTickValueWidth = 0.0f; + + + float currentTick; + string tickString; + for (int i = 0; i < VerticalTickCount; i++) + { + currentTick = _maxValue - i * _yTickValue; + tickString = currentTick.ToString("#,###.##"); + + float measured = CalculateImgFontWidth(tickString, _labelFontSize, FontFamily); + + if (measured > _maxTickValueWidth) + _maxTickValueWidth = measured; + } + + float leftOffset = _spacer + _maxTickValueWidth + (_yTitle == null ? 0.0f : 20.0f); + float rtOffset = 0.0f; + + if (ShowLegend) + { + _legendWidth = _spacer + _legendRectangleSize + _spacer + _maxLabelWidth + _spacer; + rtOffset = _graphLegendSpacer + _legendWidth + _spacer; + } + else + { + rtOffset = _spacer; // Make graph in the middle + } + + if (RenderMode == BarGraphRenderMode.Bars) + rtOffset += 10.0f; + + rtOffset += 10.0f; + + _graphHeight = + _totalHeight - _topBuffer - _bottomBuffer - + (_xTitle == null ? 0.0f : 20.0f); // Buffer spaces are used to print labels + _graphWidth = _totalWidth - leftOffset - rtOffset; + _xOrigin = leftOffset; + _yOrigin = _topBuffer; + + // Once the correct _maxValue is determined, then calculate _scaleFactor + _scaleFactor = _maxValue / _graphHeight; + } + + //********************************************************************* + // + // This method determines the longest tick value from the given data points. + // The result is needed to calculate the correct graph dimension. + // + //********************************************************************* + + private void FindLongestTickValue() + { + float currentTick; + string tickString; + for (int i = 0; i < VerticalTickCount; i++) + { + currentTick = _maxValue - i * _yTickValue; + tickString = currentTick.ToString("#,###.##"); + if (_longestTickValue.Length < tickString.Length) + _longestTickValue = tickString; + } + } + + //********************************************************************* + // + // This method calculates the image width in pixel for a given text + // + //********************************************************************* + + private float CalculateImgFontWidth(string text, float size, string family) + { + Bitmap bmp = null; + Graphics graph = null; + Font font = null; + + try + { + font = new Font(family, size); + + // Calculate the size of the string. + bmp = new Bitmap(1, 1, PixelFormat.Format32bppArgb); + graph = Graphics.FromImage(bmp); + SizeF oSize = graph.MeasureString(text, font); + oSize.Width = 4 + (float)Math.Ceiling(oSize.Width); + + return oSize.Width; + } + finally + { + graph?.Dispose(); + bmp?.Dispose(); + font?.Dispose(); + } + } + + //********************************************************************* + // + // This method creates abbreviation from long description; used for making legend + // + //********************************************************************* + + private string MakeShortLabel(string text) + { + string label = text; + if (text.Length > 2) + { + int midPostition = Convert.ToInt32(Math.Floor(text.Length / 2.0)); + label = text.Substring(0, 1) + text.Substring(midPostition, 1) + text.Substring(text.Length - 1, 1); + } + + return label; + } + + //********************************************************************* + // + // This method calculates the max value and each tick mark value for the bar graph. + // + //********************************************************************* + + private void CalculateTickAndMax() + { + float tempMax = 0.0f; + + // Give graph some head room first about 10% of current max + _maxValue *= 1.1f; + + if (_maxValue != 0.0f) + { + // Find a rounded value nearest to the current max value + // Calculate this max first to give enough space to draw value on each bar + double exp = Convert.ToDouble(Math.Floor(Math.Log10(_maxValue))); + tempMax = Convert.ToSingle(Math.Ceiling(_maxValue / Math.Pow(10, exp)) * Math.Pow(10, exp)); + } + else + { + tempMax = 1.0f; + } + + // Once max value is calculated, tick value can be determined; tick value should be a whole number + _yTickValue = tempMax / VerticalTickCount; + double expTick = Convert.ToDouble(Math.Floor(Math.Log10(_yTickValue))); + _yTickValue = Convert.ToSingle(Math.Ceiling(_yTickValue / Math.Pow(10, expTick)) * Math.Pow(10, expTick)); + + // Re-calculate the max value with the new tick value + _maxValue = _yTickValue * VerticalTickCount; + } + + //********************************************************************* + // + // This method calculates the height for each bar in the graph + // + //********************************************************************* + + private void CalculateSweepValues() + { + // Called when all values and scale factor are known + // All values calculated here are relative from (_xOrigin, _yOrigin) + int i = 0; + foreach (DataItem item in DataPoints) + { + // This implementation does not support negative value + if (item.Value >= 0) item.SweepSize = item.Value / _scaleFactor; + + // (_spaceBtwBars/2) makes half white space for the first bar + item.StartPos = _spaceBtwBars / 2 + i * (_barWidth + _spaceBtwBars); + i++; + } + } + + //********************************************************************* + // + // This method calculates the width for each bar in the graph + // + //********************************************************************* + + private void CalculateBarWidth(int dataCount, float barGraphWidth) + { + // White space between each bar is the same as bar width itself + _barWidth = barGraphWidth / (dataCount * 2); // Each bar has 1 white space + //_barWidth =/* (float)Math.Floor(*/_barWidth/*)*/; + _spaceBtwBars = _barWidth; + } + + //********************************************************************* + // + // This method assigns default value to the bar graph properties and is only + // called from BarGraph constructors + // + //********************************************************************* + + private void AssignDefaultSettings() + { + // default values + _totalWidth = 680f; + _totalHeight = 450f; + FontFamily = "Verdana"; + _backColor = Color.White; + _fontColor = Color.Black; + _topBuffer = 30f; + _bottomBuffer = 30f; + VerticalTickCount = 2; + ShowLegend = false; + ShowData = false; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Rendering/ChartRenderer.cs b/Scripts/Engines/Reports/Rendering/ChartRenderer.cs index 9fc408e13..5ae6b20a7 100644 --- a/Scripts/Engines/Reports/Rendering/ChartRenderer.cs +++ b/Scripts/Engines/Reports/Rendering/ChartRenderer.cs @@ -3,61 +3,54 @@ using System.Drawing; namespace Server.Engines.Reports { - //********************************************************************* - // - // Chart Class - // - // Base class implementation for BarChart and PieChart - // - //********************************************************************* + //********************************************************************* + // + // Chart Class + // + // Base class implementation for BarChart and PieChart + // + //********************************************************************* - public abstract class ChartRenderer - { - private const int _colorLimit = 9; + public abstract class ChartRenderer + { + private const int _colorLimit = 9; - private Color[] _color = - { - Color.Firebrick, - Color.SkyBlue, - Color.MediumSeaGreen, - Color.MediumOrchid, - Color.Chocolate, - Color.SlateBlue, - Color.LightPink, - Color.LightGreen, - Color.Khaki - }; + private Color[] _color = + { + Color.Firebrick, + Color.SkyBlue, + Color.MediumSeaGreen, + Color.MediumOrchid, + Color.Chocolate, + Color.SlateBlue, + Color.LightPink, + Color.LightGreen, + Color.Khaki + }; - // Represent collection of all data points for the chart + public ChartItemsCollection DataPoints{ get; set; } = new ChartItemsCollection(); - // The implementation of this method is provided by derived classes - public abstract Bitmap Draw(); + // Represent collection of all data points for the chart - public ChartItemsCollection DataPoints { get; set; } = new ChartItemsCollection(); + // The implementation of this method is provided by derived classes + public abstract Bitmap Draw(); - public void SetColor(int index, Color NewColor) - { - if (index < _colorLimit) - { - _color[index] = NewColor; - } - else - { - throw new Exception("Color Limit is " + _colorLimit); - } - } + public void SetColor(int index, Color NewColor) + { + if (index < _colorLimit) + _color[index] = NewColor; + else + throw new Exception("Color Limit is " + _colorLimit); + } - public Color GetColor(int index) - { - //return _color[index%_colorLimit]; + public Color GetColor(int index) + { + //return _color[index%_colorLimit]; - if (index < _colorLimit) - { - return _color[index]; - } + if (index < _colorLimit) return _color[index]; - return _color[(index+2)%_colorLimit]; - //throw new Exception("Color Limit is " + _colorLimit); - } - } + return _color[(index + 2) % _colorLimit]; + //throw new Exception("Color Limit is " + _colorLimit); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Rendering/DataItem.cs b/Scripts/Engines/Reports/Rendering/DataItem.cs index d07aeb32e..35e617564 100644 --- a/Scripts/Engines/Reports/Rendering/DataItem.cs +++ b/Scripts/Engines/Reports/Rendering/DataItem.cs @@ -3,75 +3,77 @@ using System.Drawing; namespace Server.Engines.Reports { - // Modified from MS sample + // Modified from MS sample - //********************************************************************* - // - // ChartItem Class - // - // This class represents a data point in a chart - // - //********************************************************************* + //********************************************************************* + // + // ChartItem Class + // + // This class represents a data point in a chart + // + //********************************************************************* - public class DataItem - { - private DataItem() {} - - public DataItem(string label, string desc, float data, float start, float sweep, Color clr) - { - Label = label; - Description = desc; - Value = data; - StartPos = start; - SweepSize = sweep; - ItemColor = clr; - } + public class DataItem + { + private DataItem() + { + } - public string Label { get; set; } + public DataItem(string label, string desc, float data, float start, float sweep, Color clr) + { + Label = label; + Description = desc; + Value = data; + StartPos = start; + SweepSize = sweep; + ItemColor = clr; + } - public string Description { get; set; } + public string Label{ get; set; } - public float Value { get; set; } + public string Description{ get; set; } - public Color ItemColor { get; set; } + public float Value{ get; set; } - public float StartPos { get; set; } + public Color ItemColor{ get; set; } - public float SweepSize { get; set; } - } + public float StartPos{ get; set; } - //********************************************************************* - // - // Custom Collection for ChartItems - // - //********************************************************************* + public float SweepSize{ get; set; } + } - public class ChartItemsCollection : CollectionBase - { - public DataItem this[int index] - { - get => (DataItem)(List[index]); - set => List[index] = value; - } - - public int Add(DataItem value) - { - return List.Add(value); - } - - public int IndexOf(DataItem value) - { - return List.IndexOf(value); - } - - public bool Contains(DataItem value) - { - return List.Contains(value); - } + //********************************************************************* + // + // Custom Collection for ChartItems + // + //********************************************************************* - public void Remove(DataItem value) - { - List.Remove(value); - } - } + public class ChartItemsCollection : CollectionBase + { + public DataItem this[int index] + { + get => (DataItem)List[index]; + set => List[index] = value; + } + + public int Add(DataItem value) + { + return List.Add(value); + } + + public int IndexOf(DataItem value) + { + return List.IndexOf(value); + } + + public bool Contains(DataItem value) + { + return List.Contains(value); + } + + public void Remove(DataItem value) + { + List.Remove(value); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Rendering/HtmlRenderer.cs b/Scripts/Engines/Reports/Rendering/HtmlRenderer.cs index adc615d64..98107e488 100644 --- a/Scripts/Engines/Reports/Rendering/HtmlRenderer.cs +++ b/Scripts/Engines/Reports/Rendering/HtmlRenderer.cs @@ -1,540 +1,548 @@ using System; -using System.IO; -using System.Web.UI; +using System.Diagnostics; using System.Drawing; using System.Drawing.Imaging; -using System.Diagnostics; +using System.IO; +using System.Web.UI; using HtmlTag = System.Web.UI.HtmlTextWriterTag; using HtmlAttr = System.Web.UI.HtmlTextWriterAttribute; namespace Server.Engines.Reports { - public class HtmlRenderer - { - private string m_Type; - private string m_Title; - private string m_OutputDirectory; + public class HtmlRenderer + { + private const string ShardTitle = "Shard"; - private DateTime m_TimeStamp; - private ObjectCollection m_Objects; + private static readonly string FtpHost = null; - private HtmlRenderer( string outputDirectory ) - { - m_Type = outputDirectory; - m_Title = ( m_Type == "staff" ? "Staff" : "Stats" ); - m_OutputDirectory = Path.Combine( Core.BaseDirectory, "output" ); + private static readonly string FtpUsername = null; + private static readonly string FtpPassword = null; - if ( !Directory.Exists( m_OutputDirectory ) ) - Directory.CreateDirectory( m_OutputDirectory ); + private static readonly string FtpStatsDirectory = null; + private static readonly string FtpStaffDirectory = null; + private ObjectCollection m_Objects; + private string m_OutputDirectory; - m_OutputDirectory = Path.Combine( m_OutputDirectory, outputDirectory ); + private DateTime m_TimeStamp; + private string m_Title; + private string m_Type; - if ( !Directory.Exists( m_OutputDirectory ) ) - Directory.CreateDirectory( m_OutputDirectory ); - } + private HtmlRenderer(string outputDirectory) + { + m_Type = outputDirectory; + m_Title = m_Type == "staff" ? "Staff" : "Stats"; + m_OutputDirectory = Path.Combine(Core.BaseDirectory, "output"); - public HtmlRenderer( string outputDirectory, Snapshot ss, SnapshotHistory history ) : this( outputDirectory ) - { - m_TimeStamp = ss.TimeStamp; + if (!Directory.Exists(m_OutputDirectory)) + Directory.CreateDirectory(m_OutputDirectory); - m_Objects = new ObjectCollection(); + m_OutputDirectory = Path.Combine(m_OutputDirectory, outputDirectory); - for ( int i = 0; i < ss.Children.Count; ++i ) - m_Objects.Add( ss.Children[i] ); + if (!Directory.Exists(m_OutputDirectory)) + Directory.CreateDirectory(m_OutputDirectory); + } + + public HtmlRenderer(string outputDirectory, Snapshot ss, SnapshotHistory history) : this(outputDirectory) + { + m_TimeStamp = ss.TimeStamp; + + m_Objects = new ObjectCollection(); - m_Objects.Add( BarGraph.OverTime( history, "General Stats", "Clients", 1, 100, 6 ) ); - m_Objects.Add( BarGraph.OverTime( history, "General Stats", "Items", 24, 9, 1 ) ); - m_Objects.Add( BarGraph.OverTime( history, "General Stats", "Players", 24, 9, 1 ) ); - m_Objects.Add( BarGraph.OverTime( history, "General Stats", "NPCs", 24, 9, 1 ) ); - m_Objects.Add( BarGraph.DailyAverage( history, "General Stats", "Clients" ) ); - m_Objects.Add( BarGraph.Growth( history, "General Stats", "Clients" ) ); - } + for (int i = 0; i < ss.Children.Count; ++i) + m_Objects.Add(ss.Children[i]); - public HtmlRenderer( string outputDirectory, StaffHistory history ) : this( outputDirectory ) - { - m_TimeStamp = DateTime.UtcNow; - - m_Objects = new ObjectCollection(); + m_Objects.Add(BarGraph.OverTime(history, "General Stats", "Clients", 1, 100, 6)); + m_Objects.Add(BarGraph.OverTime(history, "General Stats", "Items", 24, 9, 1)); + m_Objects.Add(BarGraph.OverTime(history, "General Stats", "Players", 24, 9, 1)); + m_Objects.Add(BarGraph.OverTime(history, "General Stats", "NPCs", 24, 9, 1)); + m_Objects.Add(BarGraph.DailyAverage(history, "General Stats", "Clients")); + m_Objects.Add(BarGraph.Growth(history, "General Stats", "Clients")); + } + + public HtmlRenderer(string outputDirectory, StaffHistory history) : this(outputDirectory) + { + m_TimeStamp = DateTime.UtcNow; + + m_Objects = new ObjectCollection(); + + history.Render(m_Objects); + } + + public void Render() + { + Console.WriteLine("Reports: {0}: Render started", m_Title); + + RenderFull(); + + for (int i = 0; i < m_Objects.Count; ++i) + RenderSingle(m_Objects[i]); + + Console.WriteLine("Reports: {0}: Render complete", m_Title); + } + + public void Upload() + { + if (FtpHost == null) + return; + + Console.WriteLine("Reports: {0}: Upload started", m_Title); + + string filePath = Path.Combine(m_OutputDirectory, "upload.ftp"); + + using (StreamWriter op = new StreamWriter(filePath)) + { + op.WriteLine("open \"{0}\"", FtpHost); + op.WriteLine(FtpUsername); + op.WriteLine(FtpPassword); + op.WriteLine("cd \"{0}\"", m_Type == "staff" ? FtpStaffDirectory : FtpStatsDirectory); + op.WriteLine("mput \"{0}\"", Path.Combine(m_OutputDirectory, "*.html")); + op.WriteLine("mput \"{0}\"", Path.Combine(m_OutputDirectory, "*.css")); + op.WriteLine("binary"); + op.WriteLine("mput \"{0}\"", Path.Combine(m_OutputDirectory, "*.png")); + op.WriteLine("disconnect"); + op.Write("quit"); + } + + ProcessStartInfo psi = new ProcessStartInfo(); + + psi.FileName = "ftp"; + psi.Arguments = $"-i -s:\"{filePath}\""; + + psi.CreateNoWindow = true; + psi.WindowStyle = ProcessWindowStyle.Hidden; + //psi.UseShellExecute = true; + + try + { + Process p = Process.Start(psi); + + p.WaitForExit(); + } + catch + { + } + + Console.WriteLine("Reports: {0}: Upload complete", m_Title); + + try + { + File.Delete(filePath); + } + catch + { + } + } + + public void RenderFull() + { + string filePath = Path.Combine(m_OutputDirectory, "reports.html"); + + using (StreamWriter op = new StreamWriter(filePath)) + { + using (HtmlTextWriter html = new HtmlTextWriter(op, "\t")) + { + RenderFull(html); + } + } + + string cssPath = Path.Combine(m_OutputDirectory, "styles.css"); + + if (File.Exists(cssPath)) + return; + + using (StreamWriter css = new StreamWriter(cssPath)) + { + css.WriteLine("body { background-color: #FFFFFF; font-family: verdana, arial; font-size: 11px; }"); + css.WriteLine("a { color: #28435E; }"); + css.WriteLine("a:hover { color: #4878A9; }"); + css.WriteLine("td.header { background-color: #9696AA; font-weight: bold; font-size: 12px; }"); + css.WriteLine("td.lentry { background-color: #D7D7EB; width: 10%; }"); + css.WriteLine("td.rentry { background-color: #FFFFFF; width: 90%; }"); + css.WriteLine("td.entry { background-color: #FFFFFF; }"); + css.WriteLine("td { font-size: 11px; }"); + css.Write(".tbl-border { background-color: #46465A; }"); + } + } + + public void RenderFull(HtmlTextWriter html) + { + html.RenderBeginTag(HtmlTag.Html); + + html.RenderBeginTag(HtmlTag.Head); + + html.RenderBeginTag(HtmlTag.Title); + html.Write("{0} Statistics", ShardTitle); + html.RenderEndTag(); + + html.AddAttribute("rel", "stylesheet"); + html.AddAttribute(HtmlAttr.Type, "text/css"); + html.AddAttribute(HtmlAttr.Href, "styles.css"); + html.RenderBeginTag(HtmlTag.Link); + html.RenderEndTag(); + + html.RenderEndTag(); + + html.RenderBeginTag(HtmlTag.Body); + + for (int i = 0; i < m_Objects.Count; ++i) + { + RenderDirect(m_Objects[i], html); + html.Write("

"); + } + + html.RenderBeginTag(HtmlTag.Center); + TimeZone tz = TimeZone.CurrentTimeZone; + bool isDaylight = tz.IsDaylightSavingTime(m_TimeStamp); + TimeSpan utcOffset = tz.GetUtcOffset(m_TimeStamp); + + html.Write("Snapshot taken at {0:d} {0:t}. All times are {1}.", m_TimeStamp, tz.StandardName); + html.RenderEndTag(); + + html.RenderEndTag(); - history.Render( m_Objects ); - } + html.RenderEndTag(); + } - public void Render() - { - Console.WriteLine( "Reports: {0}: Render started", m_Title ); + public static string SafeFileName(string name) + { + return name.ToLower().Replace(' ', '_'); + } - RenderFull(); + public void RenderSingle(PersistableObject obj) + { + string filePath = Path.Combine(m_OutputDirectory, SafeFileName(FindNameFrom(obj)) + ".html"); - for ( int i = 0; i < m_Objects.Count; ++i ) - RenderSingle( m_Objects[i] ); + using (StreamWriter op = new StreamWriter(filePath)) + { + using (HtmlTextWriter html = new HtmlTextWriter(op, "\t")) + { + RenderSingle(obj, html); + } + } + } - Console.WriteLine( "Reports: {0}: Render complete", m_Title ); - } + private string FindNameFrom(PersistableObject obj) + { + if (obj is Report report) + return report.Name; + if (obj is Chart chart) + return chart.Name; - private static readonly string FtpHost = null; - - private static readonly string FtpUsername = null; - private static readonly string FtpPassword = null; + return "Invalid"; + } - private static readonly string FtpStatsDirectory = null; - private static readonly string FtpStaffDirectory = null; + public void RenderSingle(PersistableObject obj, HtmlTextWriter html) + { + html.RenderBeginTag(HtmlTag.Html); - public void Upload() - { - if ( FtpHost == null ) - return; + html.RenderBeginTag(HtmlTag.Head); - Console.WriteLine( "Reports: {0}: Upload started", m_Title ); + html.RenderBeginTag(HtmlTag.Title); + html.Write("{0} Statistics - {1}", ShardTitle, FindNameFrom(obj)); + html.RenderEndTag(); - string filePath = Path.Combine( m_OutputDirectory, "upload.ftp" ); + html.AddAttribute("rel", "stylesheet"); + html.AddAttribute(HtmlAttr.Type, "text/css"); + html.AddAttribute(HtmlAttr.Href, "styles.css"); + html.RenderBeginTag(HtmlTag.Link); + html.RenderEndTag(); - using ( StreamWriter op = new StreamWriter( filePath ) ) - { - op.WriteLine( "open \"{0}\"", FtpHost ); - op.WriteLine( FtpUsername ); - op.WriteLine( FtpPassword ); - op.WriteLine( "cd \"{0}\"", ( m_Type == "staff" ? FtpStaffDirectory : FtpStatsDirectory ) ); - op.WriteLine( "mput \"{0}\"", Path.Combine( m_OutputDirectory, "*.html" ) ); - op.WriteLine( "mput \"{0}\"", Path.Combine( m_OutputDirectory, "*.css" ) ); - op.WriteLine( "binary" ); - op.WriteLine( "mput \"{0}\"", Path.Combine( m_OutputDirectory, "*.png" ) ); - op.WriteLine( "disconnect" ); - op.Write( "quit" ); - } + html.RenderEndTag(); - ProcessStartInfo psi = new ProcessStartInfo(); + html.RenderBeginTag(HtmlTag.Body); + + html.RenderBeginTag(HtmlTag.Center); - psi.FileName = "ftp"; - psi.Arguments = $"-i -s:\"{filePath}\""; + RenderDirect(obj, html); - psi.CreateNoWindow = true; - psi.WindowStyle = ProcessWindowStyle.Hidden; - //psi.UseShellExecute = true; + html.Write("
"); - try - { - Process p = Process.Start( psi ); + TimeZone tz = TimeZone.CurrentTimeZone; + bool isDaylight = tz.IsDaylightSavingTime(m_TimeStamp); + TimeSpan utcOffset = tz.GetUtcOffset(m_TimeStamp); - p.WaitForExit(); - } - catch - { - } + html.Write("Snapshot taken at {0:d} {0:t}. All times are {1}.", m_TimeStamp, tz.StandardName); + html.RenderEndTag(); - Console.WriteLine( "Reports: {0}: Upload complete", m_Title ); + html.RenderEndTag(); - try{ File.Delete( filePath ); } - catch{} - } + html.RenderEndTag(); + } - public void RenderFull() - { - string filePath = Path.Combine( m_OutputDirectory, "reports.html" ); + public void RenderDirect(PersistableObject obj, HtmlTextWriter html) + { + if (obj is Report report) + RenderReport(report, html); + else if (obj is BarGraph graph) + RenderBarGraph(graph, html); + else if (obj is PieChart chart) + RenderPieChart(chart, html); + } - using ( StreamWriter op = new StreamWriter( filePath ) ) - { - using ( HtmlTextWriter html = new HtmlTextWriter( op, "\t" ) ) - RenderFull( html ); - } + private void RenderPieChart(PieChart chart, HtmlTextWriter html) + { + PieChartRenderer pieChart = new PieChartRenderer(Color.White); - string cssPath = Path.Combine( m_OutputDirectory, "styles.css" ); + pieChart.ShowPercents = chart.ShowPercents; - if ( File.Exists( cssPath ) ) - return; + string[] labels = new string[chart.Items.Count]; + string[] values = new string[chart.Items.Count]; - using ( StreamWriter css = new StreamWriter( cssPath ) ) - { - css.WriteLine( "body { background-color: #FFFFFF; font-family: verdana, arial; font-size: 11px; }" ); - css.WriteLine( "a { color: #28435E; }" ); - css.WriteLine( "a:hover { color: #4878A9; }" ); - css.WriteLine( "td.header { background-color: #9696AA; font-weight: bold; font-size: 12px; }" ); - css.WriteLine( "td.lentry { background-color: #D7D7EB; width: 10%; }" ); - css.WriteLine( "td.rentry { background-color: #FFFFFF; width: 90%; }" ); - css.WriteLine( "td.entry { background-color: #FFFFFF; }" ); - css.WriteLine( "td { font-size: 11px; }" ); - css.Write ( ".tbl-border { background-color: #46465A; }" ); - } - } + for (int i = 0; i < chart.Items.Count; ++i) + { + ChartItem item = chart.Items[i]; - private const string ShardTitle = "Shard"; + labels[i] = item.Name; + values[i] = item.Value.ToString(); + } - public void RenderFull( HtmlTextWriter html ) - { - html.RenderBeginTag( HtmlTag.Html ); + pieChart.CollectDataPoints(labels, values); - html.RenderBeginTag( HtmlTag.Head ); + Bitmap bmp = pieChart.Draw(); - html.RenderBeginTag( HtmlTag.Title ); - html.Write( "{0} Statistics", ShardTitle ); - html.RenderEndTag(); + string fileName = chart.FileName + ".png"; + bmp.Save(Path.Combine(m_OutputDirectory, fileName), ImageFormat.Png); - html.AddAttribute( "rel", "stylesheet" ); - html.AddAttribute( HtmlAttr.Type, "text/css" ); - html.AddAttribute( HtmlAttr.Href, "styles.css" ); - html.RenderBeginTag( HtmlTag.Link ); - html.RenderEndTag(); - - html.RenderEndTag(); + html.Write(""); - html.RenderBeginTag( HtmlTag.Center ); - TimeZone tz = TimeZone.CurrentTimeZone; - bool isDaylight = tz.IsDaylightSavingTime( m_TimeStamp ); - TimeSpan utcOffset = tz.GetUtcOffset( m_TimeStamp ); - - html.Write( "Snapshot taken at {0:d} {0:t}. All times are {1}.", m_TimeStamp, tz.StandardName ); - html.RenderEndTag(); + html.AddAttribute(HtmlAttr.Cellpadding, "0"); + html.AddAttribute(HtmlAttr.Cellspacing, "0"); + html.AddAttribute(HtmlAttr.Border, "0"); + html.RenderBeginTag(HtmlTag.Table); - html.RenderEndTag(); + html.RenderBeginTag(HtmlTag.Tr); + html.AddAttribute(HtmlAttr.Class, "tbl-border"); + html.RenderBeginTag(HtmlTag.Td); - html.RenderEndTag(); - } + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Cellpadding, "4"); + html.AddAttribute(HtmlAttr.Cellspacing, "1"); + html.RenderBeginTag(HtmlTag.Table); - public static string SafeFileName( string name ) - { - return name.ToLower().Replace( ' ', '_' ); - } + html.RenderBeginTag(HtmlTag.Tr); - public void RenderSingle( PersistableObject obj ) - { - string filePath = Path.Combine( m_OutputDirectory, SafeFileName( FindNameFrom( obj ) ) + ".html" ); + html.AddAttribute(HtmlAttr.Colspan, "10"); + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Align, "center"); + html.AddAttribute(HtmlAttr.Class, "header"); + html.RenderBeginTag(HtmlTag.Td); + html.Write(chart.Name); + html.RenderEndTag(); + html.RenderEndTag(); - using ( StreamWriter op = new StreamWriter( filePath ) ) - { - using ( HtmlTextWriter html = new HtmlTextWriter( op, "\t" ) ) - RenderSingle( obj, html ); - } - } + html.RenderBeginTag(HtmlTag.Tr); - private string FindNameFrom( PersistableObject obj ) - { - if ( obj is Report report ) - return report.Name; - if ( obj is Chart chart ) - return chart.Name; + html.AddAttribute(HtmlAttr.Colspan, "10"); + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Align, "center"); + html.AddAttribute(HtmlAttr.Class, "entry"); + html.RenderBeginTag(HtmlTag.Td); - return "Invalid"; - } + html.AddAttribute(HtmlAttr.Width, bmp.Width.ToString()); + html.AddAttribute(HtmlAttr.Height, bmp.Height.ToString()); + html.AddAttribute(HtmlAttr.Src, fileName); + html.RenderBeginTag(HtmlTag.Img); + html.RenderEndTag(); - public void RenderSingle( PersistableObject obj, HtmlTextWriter html ) - { - html.RenderBeginTag( HtmlTag.Html ); + html.RenderEndTag(); + html.RenderEndTag(); - html.RenderBeginTag( HtmlTag.Head ); + html.RenderEndTag(); + html.RenderEndTag(); + html.RenderEndTag(); + html.RenderEndTag(); - html.RenderBeginTag( HtmlTag.Title ); - html.Write( "{0} Statistics - {1}", ShardTitle, FindNameFrom( obj ) ); - html.RenderEndTag(); + bmp.Dispose(); + } - html.AddAttribute( "rel", "stylesheet" ); - html.AddAttribute( HtmlAttr.Type, "text/css" ); - html.AddAttribute( HtmlAttr.Href, "styles.css" ); - html.RenderBeginTag( HtmlTag.Link ); - html.RenderEndTag(); + private void RenderBarGraph(BarGraph graph, HtmlTextWriter html) + { + BarGraphRenderer barGraph = new BarGraphRenderer(Color.White); - html.RenderEndTag(); + barGraph.RenderMode = graph.RenderMode; + + barGraph._regions = graph.Regions; + barGraph.SetTitles(graph.xTitle, null); - html.RenderBeginTag( HtmlTag.Body ); + if (graph.yTitle != null) + barGraph.VerticalLabel = graph.yTitle; - html.RenderBeginTag( HtmlTag.Center ); + barGraph.FontColor = Color.Black; + barGraph.ShowData = graph.Interval == 1; + barGraph.VerticalTickCount = graph.Ticks; - RenderDirect( obj, html ); + string[] labels = new string[graph.Items.Count]; + string[] values = new string[graph.Items.Count]; - html.Write( "
" ); + for (int i = 0; i < graph.Items.Count; ++i) + { + ChartItem item = graph.Items[i]; + + labels[i] = item.Name; + values[i] = item.Value.ToString(); + } + + barGraph._interval = graph.Interval; + barGraph.CollectDataPoints(labels, values); + + Bitmap bmp = barGraph.Draw(); - TimeZone tz = TimeZone.CurrentTimeZone; - bool isDaylight = tz.IsDaylightSavingTime( m_TimeStamp ); - TimeSpan utcOffset = tz.GetUtcOffset( m_TimeStamp ); + string fileName = graph.FileName + ".png"; + bmp.Save(Path.Combine(m_OutputDirectory, fileName), ImageFormat.Png); + + html.Write(""); + + html.AddAttribute(HtmlAttr.Cellpadding, "0"); + html.AddAttribute(HtmlAttr.Cellspacing, "0"); + html.AddAttribute(HtmlAttr.Border, "0"); + html.RenderBeginTag(HtmlTag.Table); + + html.RenderBeginTag(HtmlTag.Tr); + html.AddAttribute(HtmlAttr.Class, "tbl-border"); + html.RenderBeginTag(HtmlTag.Td); - html.Write( "Snapshot taken at {0:d} {0:t}. All times are {1}.", m_TimeStamp, tz.StandardName ); - html.RenderEndTag(); + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Cellpadding, "4"); + html.AddAttribute(HtmlAttr.Cellspacing, "1"); + html.RenderBeginTag(HtmlTag.Table); + + html.RenderBeginTag(HtmlTag.Tr); + + html.AddAttribute(HtmlAttr.Colspan, "10"); + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Align, "center"); + html.AddAttribute(HtmlAttr.Class, "header"); + html.RenderBeginTag(HtmlTag.Td); + html.Write(graph.Name); + html.RenderEndTag(); + html.RenderEndTag(); + + html.RenderBeginTag(HtmlTag.Tr); - html.RenderEndTag(); + html.AddAttribute(HtmlAttr.Colspan, "10"); + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Align, "center"); + html.AddAttribute(HtmlAttr.Class, "entry"); + html.RenderBeginTag(HtmlTag.Td); + + html.AddAttribute(HtmlAttr.Width, bmp.Width.ToString()); + html.AddAttribute(HtmlAttr.Height, bmp.Height.ToString()); + html.AddAttribute(HtmlAttr.Src, fileName); + html.RenderBeginTag(HtmlTag.Img); + html.RenderEndTag(); + + html.RenderEndTag(); + html.RenderEndTag(); - html.RenderEndTag(); - } + html.RenderEndTag(); + html.RenderEndTag(); + html.RenderEndTag(); + html.RenderEndTag(); + + bmp.Dispose(); + } - public void RenderDirect( PersistableObject obj, HtmlTextWriter html ) - { - if ( obj is Report report ) - RenderReport( report, html ); - else if ( obj is BarGraph graph ) - RenderBarGraph( graph, html ); - else if ( obj is PieChart chart ) - RenderPieChart( chart, html ); - } + private void RenderReport(Report report, HtmlTextWriter html) + { + html.AddAttribute(HtmlAttr.Width, report.Width); + html.AddAttribute(HtmlAttr.Cellpadding, "0"); + html.AddAttribute(HtmlAttr.Cellspacing, "0"); + html.AddAttribute(HtmlAttr.Border, "0"); + html.RenderBeginTag(HtmlTag.Table); - private void RenderPieChart( PieChart chart, HtmlTextWriter html ) - { - PieChartRenderer pieChart = new PieChartRenderer( Color.White ); - - pieChart.ShowPercents = chart.ShowPercents; - - string[] labels = new string[chart.Items.Count]; - string[] values = new string[chart.Items.Count]; - - for ( int i = 0; i < chart.Items.Count; ++i ) - { - ChartItem item = chart.Items[i]; - - labels[i] = item.Name; - values[i] = item.Value.ToString(); - } - - pieChart.CollectDataPoints( labels, values ); - - Bitmap bmp = pieChart.Draw(); - - string fileName = chart.FileName + ".png"; - bmp.Save( Path.Combine( m_OutputDirectory, fileName ), ImageFormat.Png ); - - html.Write( "" ); - - html.AddAttribute( HtmlAttr.Cellpadding, "0" ); - html.AddAttribute( HtmlAttr.Cellspacing, "0" ); - html.AddAttribute( HtmlAttr.Border, "0" ); - html.RenderBeginTag( HtmlTag.Table ); - - html.RenderBeginTag( HtmlTag.Tr ); - html.AddAttribute( HtmlAttr.Class, "tbl-border" ); - html.RenderBeginTag( HtmlTag.Td ); - - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Cellpadding, "4" ); - html.AddAttribute( HtmlAttr.Cellspacing, "1" ); - html.RenderBeginTag( HtmlTag.Table ); - - html.RenderBeginTag( HtmlTag.Tr ); - - html.AddAttribute( HtmlAttr.Colspan, "10" ); - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Align, "center" ); - html.AddAttribute( HtmlAttr.Class, "header" ); - html.RenderBeginTag( HtmlTag.Td ); - html.Write( chart.Name ); - html.RenderEndTag(); - html.RenderEndTag(); - - html.RenderBeginTag( HtmlTag.Tr ); - - html.AddAttribute( HtmlAttr.Colspan, "10" ); - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Align, "center" ); - html.AddAttribute( HtmlAttr.Class, "entry" ); - html.RenderBeginTag( HtmlTag.Td ); - - html.AddAttribute( HtmlAttr.Width, bmp.Width.ToString() ); - html.AddAttribute( HtmlAttr.Height, bmp.Height.ToString() ); - html.AddAttribute( HtmlAttr.Src, fileName ); - html.RenderBeginTag( HtmlTag.Img ); - html.RenderEndTag(); - - html.RenderEndTag(); - html.RenderEndTag(); - - html.RenderEndTag(); - html.RenderEndTag(); - html.RenderEndTag(); - html.RenderEndTag(); - - bmp.Dispose(); - } - - private void RenderBarGraph( BarGraph graph, HtmlTextWriter html ) - { - BarGraphRenderer barGraph = new BarGraphRenderer( Color.White ); - - barGraph.RenderMode = graph.RenderMode; - - barGraph._regions = graph.Regions; - barGraph.SetTitles( graph.xTitle, null ); - - if ( graph.yTitle != null ) - barGraph.VerticalLabel = graph.yTitle; - - barGraph.FontColor = Color.Black; - barGraph.ShowData = ( graph.Interval == 1 ); - barGraph.VerticalTickCount = graph.Ticks; - - string[] labels = new string[graph.Items.Count]; - string[] values = new string[graph.Items.Count]; - - for ( int i = 0; i < graph.Items.Count; ++i ) - { - ChartItem item = graph.Items[i]; - - labels[i] = item.Name; - values[i] = item.Value.ToString(); - } - - barGraph._interval = graph.Interval; - barGraph.CollectDataPoints( labels, values ); - - Bitmap bmp = barGraph.Draw(); - - string fileName = graph.FileName + ".png"; - bmp.Save( Path.Combine( m_OutputDirectory, fileName ), ImageFormat.Png ); - - html.Write( "" ); - - html.AddAttribute( HtmlAttr.Cellpadding, "0" ); - html.AddAttribute( HtmlAttr.Cellspacing, "0" ); - html.AddAttribute( HtmlAttr.Border, "0" ); - html.RenderBeginTag( HtmlTag.Table ); - - html.RenderBeginTag( HtmlTag.Tr ); - html.AddAttribute( HtmlAttr.Class, "tbl-border" ); - html.RenderBeginTag( HtmlTag.Td ); - - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Cellpadding, "4" ); - html.AddAttribute( HtmlAttr.Cellspacing, "1" ); - html.RenderBeginTag( HtmlTag.Table ); - - html.RenderBeginTag( HtmlTag.Tr ); - - html.AddAttribute( HtmlAttr.Colspan, "10" ); - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Align, "center" ); - html.AddAttribute( HtmlAttr.Class, "header" ); - html.RenderBeginTag( HtmlTag.Td ); - html.Write( graph.Name ); - html.RenderEndTag(); - html.RenderEndTag(); - - html.RenderBeginTag( HtmlTag.Tr ); - - html.AddAttribute( HtmlAttr.Colspan, "10" ); - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Align, "center" ); - html.AddAttribute( HtmlAttr.Class, "entry" ); - html.RenderBeginTag( HtmlTag.Td ); - - html.AddAttribute( HtmlAttr.Width, bmp.Width.ToString() ); - html.AddAttribute( HtmlAttr.Height, bmp.Height.ToString() ); - html.AddAttribute( HtmlAttr.Src, fileName ); - html.RenderBeginTag( HtmlTag.Img ); - html.RenderEndTag(); - - html.RenderEndTag(); - html.RenderEndTag(); - - html.RenderEndTag(); - html.RenderEndTag(); - html.RenderEndTag(); - html.RenderEndTag(); - - bmp.Dispose(); - } - - private void RenderReport( Report report, HtmlTextWriter html ) - { - html.AddAttribute( HtmlAttr.Width, report.Width ); - html.AddAttribute( HtmlAttr.Cellpadding, "0" ); - html.AddAttribute( HtmlAttr.Cellspacing, "0" ); - html.AddAttribute( HtmlAttr.Border, "0" ); - html.RenderBeginTag( HtmlTag.Table ); - - html.RenderBeginTag( HtmlTag.Tr ); - html.AddAttribute( HtmlAttr.Class, "tbl-border" ); - html.RenderBeginTag( HtmlTag.Td ); - - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Cellpadding, "4" ); - html.AddAttribute( HtmlAttr.Cellspacing, "1" ); - html.RenderBeginTag( HtmlTag.Table ); - - html.RenderBeginTag( HtmlTag.Tr ); - html.AddAttribute( HtmlAttr.Colspan, "10" ); - html.AddAttribute( HtmlAttr.Width, "100%" ); - html.AddAttribute( HtmlAttr.Align, "center" ); - html.AddAttribute( HtmlAttr.Class, "header" ); - html.RenderBeginTag( HtmlTag.Td ); - html.Write( report.Name ); - html.RenderEndTag(); - html.RenderEndTag(); - - bool isNamed = false; - - for ( int i = 0; i < report.Columns.Count && !isNamed; ++i ) - isNamed = ( report.Columns[i].Name != null ); - - if ( isNamed ) - { - html.RenderBeginTag( HtmlTag.Tr ); - - for ( int i = 0; i < report.Columns.Count; ++i ) - { - ReportColumn column = report.Columns[i]; - - html.AddAttribute( HtmlAttr.Class, "header" ); - html.AddAttribute( HtmlAttr.Width, column.Width ); - html.AddAttribute( HtmlAttr.Align, column.Align ); - html.RenderBeginTag( HtmlTag.Td ); - - html.Write( column.Name ); - - html.RenderEndTag(); - } - - html.RenderEndTag(); - } - - for ( int i = 0; i < report.Items.Count; ++i ) - { - ReportItem item = report.Items[i]; - - html.RenderBeginTag( HtmlTag.Tr ); - - for ( int j = 0; j < item.Values.Count; ++j ) - { - if ( !isNamed && j == 0 ) - html.AddAttribute( HtmlAttr.Width, report.Columns[j].Width ); - - html.AddAttribute( HtmlAttr.Align, report.Columns[j].Align ); - html.AddAttribute( HtmlAttr.Class, "entry" ); - html.RenderBeginTag( HtmlTag.Td ); - - if ( item.Values[j].Format == null ) - html.Write( item.Values[j].Value ); - else - html.Write( int.Parse( item.Values[j].Value ).ToString( item.Values[j].Format ) ); - - html.RenderEndTag(); - } - - html.RenderEndTag(); - } - - html.RenderEndTag(); - html.RenderEndTag(); - html.RenderEndTag(); - html.RenderEndTag(); - } - } -} + html.RenderBeginTag(HtmlTag.Tr); + html.AddAttribute(HtmlAttr.Class, "tbl-border"); + html.RenderBeginTag(HtmlTag.Td); + + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Cellpadding, "4"); + html.AddAttribute(HtmlAttr.Cellspacing, "1"); + html.RenderBeginTag(HtmlTag.Table); + + html.RenderBeginTag(HtmlTag.Tr); + html.AddAttribute(HtmlAttr.Colspan, "10"); + html.AddAttribute(HtmlAttr.Width, "100%"); + html.AddAttribute(HtmlAttr.Align, "center"); + html.AddAttribute(HtmlAttr.Class, "header"); + html.RenderBeginTag(HtmlTag.Td); + html.Write(report.Name); + html.RenderEndTag(); + html.RenderEndTag(); + + bool isNamed = false; + + for (int i = 0; i < report.Columns.Count && !isNamed; ++i) + isNamed = report.Columns[i].Name != null; + + if (isNamed) + { + html.RenderBeginTag(HtmlTag.Tr); + + for (int i = 0; i < report.Columns.Count; ++i) + { + ReportColumn column = report.Columns[i]; + + html.AddAttribute(HtmlAttr.Class, "header"); + html.AddAttribute(HtmlAttr.Width, column.Width); + html.AddAttribute(HtmlAttr.Align, column.Align); + html.RenderBeginTag(HtmlTag.Td); + + html.Write(column.Name); + + html.RenderEndTag(); + } + + html.RenderEndTag(); + } + + for (int i = 0; i < report.Items.Count; ++i) + { + ReportItem item = report.Items[i]; + + html.RenderBeginTag(HtmlTag.Tr); + + for (int j = 0; j < item.Values.Count; ++j) + { + if (!isNamed && j == 0) + html.AddAttribute(HtmlAttr.Width, report.Columns[j].Width); + + html.AddAttribute(HtmlAttr.Align, report.Columns[j].Align); + html.AddAttribute(HtmlAttr.Class, "entry"); + html.RenderBeginTag(HtmlTag.Td); + + if (item.Values[j].Format == null) + html.Write(item.Values[j].Value); + else + html.Write(int.Parse(item.Values[j].Value).ToString(item.Values[j].Format)); + + html.RenderEndTag(); + } + + html.RenderEndTag(); + } + + html.RenderEndTag(); + html.RenderEndTag(); + html.RenderEndTag(); + html.RenderEndTag(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Reports/Rendering/PieChartRenderer.cs b/Scripts/Engines/Reports/Rendering/PieChartRenderer.cs index 15197b4ca..1d70e2b0e 100644 --- a/Scripts/Engines/Reports/Rendering/PieChartRenderer.cs +++ b/Scripts/Engines/Reports/Rendering/PieChartRenderer.cs @@ -5,244 +5,252 @@ using System.Drawing.Drawing2D; namespace Server.Engines.Reports { - // Modified from MS sample + // Modified from MS sample - //********************************************************************* - // - // PieChart Class - // - // This class uses GDI+ to render Pie Chart. - // - //********************************************************************* + //********************************************************************* + // + // PieChart Class + // + // This class uses GDI+ to render Pie Chart. + // + //********************************************************************* - public class PieChartRenderer : ChartRenderer - { - private const int _bufferSpace = 125; - private ArrayList _chartItems; - private int _perimeter; - private Color _backgroundColor; - private Color _borderColor; - private float _total; - private int _legendWidth; - private int _legendHeight; - private int _legendFontHeight; - private string _legendFontStyle; - private float _legendFontSize; + public class PieChartRenderer : ChartRenderer + { + private const int _bufferSpace = 125; + private Color _backgroundColor; + private Color _borderColor; + private ArrayList _chartItems; + private int _legendFontHeight; + private float _legendFontSize; + private string _legendFontStyle; + private int _legendHeight; + private int _legendWidth; + private int _perimeter; + private float _total; - public bool ShowPercents { get; set; } + public PieChartRenderer() + { + _chartItems = new ArrayList(); + _perimeter = 250; + _backgroundColor = Color.White; + _borderColor = Color.FromArgb(63, 63, 63); + _legendFontSize = 8; + _legendFontStyle = "Verdana"; + } - public PieChartRenderer() - { - _chartItems = new ArrayList(); - _perimeter = 250; - _backgroundColor = Color.White; - _borderColor = Color.FromArgb(63,63,63); - _legendFontSize = 8; - _legendFontStyle = "Verdana"; - } + public PieChartRenderer(Color bgColor) + { + _chartItems = new ArrayList(); + _perimeter = 250; + _backgroundColor = bgColor; + _borderColor = Color.FromArgb(63, 63, 63); + _legendFontSize = 8; + _legendFontStyle = "Verdana"; + } - public PieChartRenderer(Color bgColor) - { - _chartItems = new ArrayList(); - _perimeter = 250; - _backgroundColor = bgColor; - _borderColor = Color.FromArgb(63,63,63); - _legendFontSize = 8; - _legendFontStyle = "Verdana"; - } + public bool ShowPercents{ get; set; } - //********************************************************************* - // - // This method collects all data points and calculate all the necessary dimensions - // to draw the chart. It is the first method called before invoking the Draw() method. - // - //********************************************************************* + //********************************************************************* + // + // This method collects all data points and calculate all the necessary dimensions + // to draw the chart. It is the first method called before invoking the Draw() method. + // + //********************************************************************* - public void CollectDataPoints(string[] xValues, string[] yValues) - { - _total = 0.0f; - - for (int i = 0;i < xValues.Length;i++) - { - float ftemp = Convert.ToSingle(yValues[i]); - _chartItems.Add(new DataItem(xValues[i], xValues.ToString(), ftemp, 0, 0, Color.AliceBlue)); - _total += ftemp; - } - - float nextStartPos = 0.0f; - int counter = 0; - foreach (DataItem item in _chartItems) - { - item.StartPos = nextStartPos; - item.SweepSize = item.Value / _total * 360; - nextStartPos = item.StartPos + item.SweepSize; - item.ItemColor = GetColor(counter++); - } + public void CollectDataPoints(string[] xValues, string[] yValues) + { + _total = 0.0f; - CalculateLegendWidthHeight(); - } + for (int i = 0; i < xValues.Length; i++) + { + float ftemp = Convert.ToSingle(yValues[i]); + _chartItems.Add(new DataItem(xValues[i], xValues.ToString(), ftemp, 0, 0, Color.AliceBlue)); + _total += ftemp; + } - //********************************************************************* - // - // This method returns a bitmap to the calling function. This is the method - // that actually draws the pie chart and the legend with it. - // - //********************************************************************* + float nextStartPos = 0.0f; + int counter = 0; + foreach (DataItem item in _chartItems) + { + item.StartPos = nextStartPos; + item.SweepSize = item.Value / _total * 360; + nextStartPos = item.StartPos + item.SweepSize; + item.ItemColor = GetColor(counter++); + } - public override Bitmap Draw() - { - int perimeter = _perimeter; - Rectangle pieRect = new Rectangle(0, 0, perimeter, perimeter-1); - Bitmap bmp = new Bitmap(perimeter + _legendWidth, perimeter); - Font fnt = null; - Pen pen = null; - Graphics grp = null; - StringFormat sf = null, sfp = null; - - try - { - grp = Graphics.FromImage(bmp); - grp.CompositingQuality = CompositingQuality.HighQuality; - grp.SmoothingMode = SmoothingMode.AntiAlias; - sf = new StringFormat(); + CalculateLegendWidthHeight(); + } - //Paint Back ground - using ( SolidBrush brsh = new SolidBrush( _backgroundColor ) ) - grp.FillRectangle(brsh, -1, -1, perimeter + _legendWidth+1, perimeter+1); + //********************************************************************* + // + // This method returns a bitmap to the calling function. This is the method + // that actually draws the pie chart and the legend with it. + // + //********************************************************************* - //Align text to the right - sf.Alignment = StringAlignment.Far; - - //Draw all wedges and legends - for(int i=0; i<_chartItems.Count; i++) - { - DataItem item = (DataItem) _chartItems[i]; - SolidBrush brs = null; - try - { - brs = new SolidBrush(item.ItemColor); - grp.FillPie(brs, pieRect, item.StartPos, item.SweepSize); + public override Bitmap Draw() + { + int perimeter = _perimeter; + Rectangle pieRect = new Rectangle(0, 0, perimeter, perimeter - 1); + Bitmap bmp = new Bitmap(perimeter + _legendWidth, perimeter); + Font fnt = null; + Pen pen = null; + Graphics grp = null; + StringFormat sf = null, sfp = null; - //grp.DrawPie(new Pen(_borderColor,1.2f),pieRect,item.StartPos,item.SweepSize); + try + { + grp = Graphics.FromImage(bmp); + grp.CompositingQuality = CompositingQuality.HighQuality; + grp.SmoothingMode = SmoothingMode.AntiAlias; + sf = new StringFormat(); - if ( fnt == null ) - fnt = new Font( _legendFontStyle, _legendFontSize ); + //Paint Back ground + using (SolidBrush brsh = new SolidBrush(_backgroundColor)) + { + grp.FillRectangle(brsh, -1, -1, perimeter + _legendWidth + 1, perimeter + 1); + } - if ( ShowPercents && item.SweepSize > 10 ) - { - if ( sfp == null ) - { - sfp = new StringFormat(); - sfp.Alignment = StringAlignment.Center; - sfp.LineAlignment = StringAlignment.Center; - } + //Align text to the right + sf.Alignment = StringAlignment.Far; - float perc = (item.SweepSize * 100.0f) / 360.0f; - string percString = $"{perc:F0}%"; + //Draw all wedges and legends + for (int i = 0; i < _chartItems.Count; i++) + { + DataItem item = (DataItem)_chartItems[i]; + SolidBrush brs = null; + try + { + brs = new SolidBrush(item.ItemColor); + grp.FillPie(brs, pieRect, item.StartPos, item.SweepSize); - float px = pieRect.X+(pieRect.Width/2); - float py = pieRect.Y+(pieRect.Height/2); + //grp.DrawPie(new Pen(_borderColor,1.2f),pieRect,item.StartPos,item.SweepSize); - double angle = item.StartPos + (item.SweepSize/2); - double rads = (angle/180.0)*Math.PI; + if (fnt == null) + fnt = new Font(_legendFontStyle, _legendFontSize); - px += (float)(Math.Cos( rads ) * perimeter / 3); - py += (float)(Math.Sin( rads ) * perimeter / 3); + if (ShowPercents && item.SweepSize > 10) + { + if (sfp == null) + { + sfp = new StringFormat(); + sfp.Alignment = StringAlignment.Center; + sfp.LineAlignment = StringAlignment.Center; + } - grp.DrawString( percString, fnt, Brushes.Gray, - new RectangleF( px - 30 - 1, py - 20, 60, 40 ), sfp ); + float perc = item.SweepSize * 100.0f / 360.0f; + string percString = $"{perc:F0}%"; - grp.DrawString( percString, fnt, Brushes.Gray, - new RectangleF( px - 30 + 1, py - 20, 60, 40 ), sfp ); + float px = pieRect.X + pieRect.Width / 2; + float py = pieRect.Y + pieRect.Height / 2; - grp.DrawString( percString, fnt, Brushes.Gray, - new RectangleF( px - 30, py - 20 - 1, 60, 40 ), sfp ); + double angle = item.StartPos + item.SweepSize / 2; + double rads = angle / 180.0 * Math.PI; - grp.DrawString( percString, fnt, Brushes.Gray, - new RectangleF( px - 30, py - 20 + 1, 60, 40 ), sfp ); + px += (float)(Math.Cos(rads) * perimeter / 3); + py += (float)(Math.Sin(rads) * perimeter / 3); + + grp.DrawString(percString, fnt, Brushes.Gray, + new RectangleF(px - 30 - 1, py - 20, 60, 40), sfp); + + grp.DrawString(percString, fnt, Brushes.Gray, + new RectangleF(px - 30 + 1, py - 20, 60, 40), sfp); + + grp.DrawString(percString, fnt, Brushes.Gray, + new RectangleF(px - 30, py - 20 - 1, 60, 40), sfp); + + grp.DrawString(percString, fnt, Brushes.Gray, + new RectangleF(px - 30, py - 20 + 1, 60, 40), sfp); - grp.DrawString( percString, fnt, Brushes.White, - new RectangleF( px - 30, py - 20, 60, 40 ), sfp ); - } + grp.DrawString(percString, fnt, Brushes.White, + new RectangleF(px - 30, py - 20, 60, 40), sfp); + } - if ( pen == null ) - pen = new Pen( _borderColor, 0.5f ); + if (pen == null) + pen = new Pen(_borderColor, 0.5f); - grp.FillRectangle(brs, perimeter + _bufferSpace, i * _legendFontHeight + 15, 10, 10); - grp.DrawRectangle(pen, perimeter + _bufferSpace, i * _legendFontHeight + 15, 10, 10); - - grp.DrawString(item.Label, fnt, - Brushes.Black, perimeter + _bufferSpace + 20, i * _legendFontHeight + 13); + grp.FillRectangle(brs, perimeter + _bufferSpace, i * _legendFontHeight + 15, 10, 10); + grp.DrawRectangle(pen, perimeter + _bufferSpace, i * _legendFontHeight + 15, 10, 10); - grp.DrawString(item.Value.ToString("#,###.##"), fnt, - Brushes.Black, perimeter + _bufferSpace + 200, i * _legendFontHeight + 13,sf); - } - finally - { - brs?.Dispose(); - } - } + grp.DrawString(item.Label, fnt, + Brushes.Black, perimeter + _bufferSpace + 20, i * _legendFontHeight + 13); - for(int i=0; i<_chartItems.Count; i++) - { - DataItem item = (DataItem) _chartItems[i]; - SolidBrush brs = null; - try - { - grp.DrawPie(new Pen(_borderColor,0.5f),pieRect,item.StartPos,item.SweepSize); - } - finally - { - brs?.Dispose(); - } - } - - //draws the border around Pie - using ( Pen pen2 = new Pen( _borderColor, 2 ) ) - grp.DrawEllipse(pen2, pieRect); + grp.DrawString(item.Value.ToString("#,###.##"), fnt, + Brushes.Black, perimeter + _bufferSpace + 200, i * _legendFontHeight + 13, sf); + } + finally + { + brs?.Dispose(); + } + } - //draw border around legend - using ( Pen pen1 = new Pen( _borderColor, 1 ) ) - grp.DrawRectangle(pen1, perimeter + _bufferSpace - 10, 10, 220, _chartItems.Count * _legendFontHeight + 25); + for (int i = 0; i < _chartItems.Count; i++) + { + DataItem item = (DataItem)_chartItems[i]; + SolidBrush brs = null; + try + { + grp.DrawPie(new Pen(_borderColor, 0.5f), pieRect, item.StartPos, item.SweepSize); + } + finally + { + brs?.Dispose(); + } + } - //Draw Total under legend - using ( Font fntb = new Font( _legendFontStyle, _legendFontSize, FontStyle.Bold ) ) - { - grp.DrawString("Total", fntb, - Brushes.Black, perimeter + _bufferSpace + 30, (_chartItems.Count+1) * _legendFontHeight,sf); - grp.DrawString(_total.ToString("#,###.##"), fntb, - Brushes.Black, perimeter + _bufferSpace + 200, (_chartItems.Count+1) * _legendFontHeight,sf); - } - - grp.SmoothingMode = SmoothingMode.AntiAlias; - } - finally - { - sf?.Dispose(); - grp?.Dispose(); - sfp?.Dispose(); - fnt?.Dispose(); - pen?.Dispose(); - } - return bmp; - } + //draws the border around Pie + using (Pen pen2 = new Pen(_borderColor, 2)) + { + grp.DrawEllipse(pen2, pieRect); + } - //********************************************************************* - // - // This method calculates the space required to draw the chart legend. - // - //********************************************************************* - - private void CalculateLegendWidthHeight() - { - Font fontLegend = new Font(_legendFontStyle, _legendFontSize); - _legendFontHeight = fontLegend.Height+3; - _legendHeight = fontLegend.Height * (_chartItems.Count + 1); - if (_legendHeight > _perimeter) _perimeter = _legendHeight; + //draw border around legend + using (Pen pen1 = new Pen(_borderColor, 1)) + { + grp.DrawRectangle(pen1, perimeter + _bufferSpace - 10, 10, 220, + _chartItems.Count * _legendFontHeight + 25); + } - _legendWidth = _perimeter + _bufferSpace; - fontLegend.Dispose(); - } - } + //Draw Total under legend + using (Font fntb = new Font(_legendFontStyle, _legendFontSize, FontStyle.Bold)) + { + grp.DrawString("Total", fntb, + Brushes.Black, perimeter + _bufferSpace + 30, (_chartItems.Count + 1) * _legendFontHeight, sf); + grp.DrawString(_total.ToString("#,###.##"), fntb, + Brushes.Black, perimeter + _bufferSpace + 200, (_chartItems.Count + 1) * _legendFontHeight, sf); + } + + grp.SmoothingMode = SmoothingMode.AntiAlias; + } + finally + { + sf?.Dispose(); + grp?.Dispose(); + sfp?.Dispose(); + fnt?.Dispose(); + pen?.Dispose(); + } + + return bmp; + } + + //********************************************************************* + // + // This method calculates the space required to draw the chart legend. + // + //********************************************************************* + + private void CalculateLegendWidthHeight() + { + Font fontLegend = new Font(_legendFontStyle, _legendFontSize); + _legendFontHeight = fontLegend.Height + 3; + _legendHeight = fontLegend.Height * (_chartItems.Count + 1); + if (_legendHeight > _perimeter) _perimeter = _legendHeight; + + _legendWidth = _perimeter + _bufferSpace; + fontLegend.Dispose(); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/Reports/Reports.cs b/Scripts/Engines/Reports/Reports.cs index 53d55d544..2350a3ba8 100644 --- a/Scripts/Engines/Reports/Reports.cs +++ b/Scripts/Engines/Reports/Reports.cs @@ -1,548 +1,548 @@ using System; -using System.Threading; using System.Collections; using System.Collections.Generic; -using Server.Mobiles; -using Server.Network; -using Server.Factions; +using System.Threading; using Server.Accounting; using Server.Engines.ConPVP; +using Server.Engines.Help; +using Server.Factions; +using Server.Mobiles; +using Server.Network; namespace Server.Engines.Reports { - public class Reports - { - public static bool Enabled = false; + public class Reports + { + public static bool Enabled = false; - public static void Initialize() - { - if ( !Enabled ) - return; + private static DateTime m_GenerateTime; - m_StatsHistory = new SnapshotHistory(); - m_StatsHistory.Load(); + private static SnapshotHistory m_StatsHistory; - StaffHistory = new StaffHistory(); - StaffHistory.Load(); + public static StaffHistory StaffHistory{ get; private set; } - DateTime now = DateTime.UtcNow; + public static void Initialize() + { + if (!Enabled) + return; - DateTime date = now.Date; - TimeSpan timeOfDay = now.TimeOfDay; + m_StatsHistory = new SnapshotHistory(); + m_StatsHistory.Load(); - m_GenerateTime = date + TimeSpan.FromHours( Math.Ceiling( timeOfDay.TotalHours ) ); + StaffHistory = new StaffHistory(); + StaffHistory.Load(); - Timer.DelayCall( TimeSpan.FromMinutes( 0.5 ), TimeSpan.FromMinutes( 0.5 ), CheckRegenerate ); - } + DateTime now = DateTime.UtcNow; - private static DateTime m_GenerateTime; + DateTime date = now.Date; + TimeSpan timeOfDay = now.TimeOfDay; - public static void CheckRegenerate() - { - if ( DateTime.UtcNow < m_GenerateTime ) - return; + m_GenerateTime = date + TimeSpan.FromHours(Math.Ceiling(timeOfDay.TotalHours)); - Generate(); - m_GenerateTime += TimeSpan.FromHours( 1.0 ); - } + Timer.DelayCall(TimeSpan.FromMinutes(0.5), TimeSpan.FromMinutes(0.5), CheckRegenerate); + } - private static SnapshotHistory m_StatsHistory; + public static void CheckRegenerate() + { + if (DateTime.UtcNow < m_GenerateTime) + return; - public static StaffHistory StaffHistory { get; private set; } + Generate(); + m_GenerateTime += TimeSpan.FromHours(1.0); + } - public static void Generate() - { - Snapshot ss = new Snapshot(); + public static void Generate() + { + Snapshot ss = new Snapshot(); - ss.TimeStamp = DateTime.UtcNow; + ss.TimeStamp = DateTime.UtcNow; - FillSnapshot( ss ); + FillSnapshot(ss); - m_StatsHistory.Snapshots.Add( ss ); - StaffHistory.QueueStats.Add( new QueueStatus( Help.PageQueue.List.Count ) ); + m_StatsHistory.Snapshots.Add(ss); + StaffHistory.QueueStats.Add(new QueueStatus(PageQueue.List.Count)); - ThreadPool.QueueUserWorkItem( UpdateOutput, ss ); - } + ThreadPool.QueueUserWorkItem(UpdateOutput, ss); + } - private static void UpdateOutput( object state ) - { - m_StatsHistory.Save(); - StaffHistory.Save(); + private static void UpdateOutput(object state) + { + m_StatsHistory.Save(); + StaffHistory.Save(); - HtmlRenderer renderer = new HtmlRenderer( "stats", (Snapshot) state, m_StatsHistory ); - renderer.Render(); - renderer.Upload(); + HtmlRenderer renderer = new HtmlRenderer("stats", (Snapshot)state, m_StatsHistory); + renderer.Render(); + renderer.Upload(); - renderer = new HtmlRenderer( "staff", StaffHistory ); - renderer.Render(); - renderer.Upload(); - } + renderer = new HtmlRenderer("staff", StaffHistory); + renderer.Render(); + renderer.Upload(); + } - public static void FillSnapshot( Snapshot ss ) - { - ss.Children.Add( CompileGeneralStats() ); - ss.Children.Add( CompilePCByDL() ); - ss.Children.Add( CompileTop15() ); - ss.Children.Add( CompileDislikedArenas() ); - ss.Children.Add( CompileStatChart() ); + public static void FillSnapshot(Snapshot ss) + { + ss.Children.Add(CompileGeneralStats()); + ss.Children.Add(CompilePCByDL()); + ss.Children.Add(CompileTop15()); + ss.Children.Add(CompileDislikedArenas()); + ss.Children.Add(CompileStatChart()); - PersistableObject[] obs = CompileSkillReports(); + PersistableObject[] obs = CompileSkillReports(); - for ( int i = 0; i < obs.Length; ++i ) - ss.Children.Add( obs[i] ); + for (int i = 0; i < obs.Length; ++i) + ss.Children.Add(obs[i]); - obs = CompileFactionReports(); + obs = CompileFactionReports(); - for ( int i = 0; i < obs.Length; ++i ) - ss.Children.Add( obs[i] ); - } + for (int i = 0; i < obs.Length; ++i) + ss.Children.Add(obs[i]); + } - public static Report CompileGeneralStats() - { - Report report = new Report( "General Stats", "200" ); + public static Report CompileGeneralStats() + { + Report report = new Report("General Stats", "200"); - report.Columns.Add( "50%", "left" ); - report.Columns.Add( "50%", "left" ); + report.Columns.Add("50%", "left"); + report.Columns.Add("50%", "left"); - int npcs = 0, players = 0; + int npcs = 0, players = 0; - foreach ( Mobile mob in World.Mobiles.Values ) - { - if ( mob.Player ) - ++players; - else - ++npcs; - } + foreach (Mobile mob in World.Mobiles.Values) + if (mob.Player) + ++players; + else + ++npcs; - report.Items.Add( "NPCs", npcs, "N0" ); - report.Items.Add( "Players", players, "N0" ); - report.Items.Add( "Clients", NetState.Instances.Count, "N0" ); - report.Items.Add( "Accounts", Accounts.Count, "N0" ); - report.Items.Add( "Items", World.Items.Count, "N0" ); + report.Items.Add("NPCs", npcs, "N0"); + report.Items.Add("Players", players, "N0"); + report.Items.Add("Clients", NetState.Instances.Count, "N0"); + report.Items.Add("Accounts", Accounts.Count, "N0"); + report.Items.Add("Items", World.Items.Count, "N0"); - return report; - } + return report; + } - private static Chart CompilePCByDL() - { - BarGraph chart = new BarGraph( "Player Count By Dueling Level", "graphs_pc_by_dl", 5, "Dueling Level", "Players", BarGraphRenderMode.Bars ); + private static Chart CompilePCByDL() + { + BarGraph chart = new BarGraph("Player Count By Dueling Level", "graphs_pc_by_dl", 5, "Dueling Level", "Players", + BarGraphRenderMode.Bars); - int lastLevel = -1; - ChartItem lastItem = null; + int lastLevel = -1; + ChartItem lastItem = null; - Ladder ladder = Ladder.Instance; + Ladder ladder = Ladder.Instance; - if ( ladder != null ) - { - ArrayList entries = ladder.ToArrayList(); + if (ladder != null) + { + ArrayList entries = ladder.ToArrayList(); - for ( int i = entries.Count - 1; i >= 0; --i ) - { - LadderEntry entry = (LadderEntry)entries[i]; - int level = Ladder.GetLevel( entry.Experience ); + for (int i = entries.Count - 1; i >= 0; --i) + { + LadderEntry entry = (LadderEntry)entries[i]; + int level = Ladder.GetLevel(entry.Experience); + + if (lastItem == null || level != lastLevel) + { + chart.Items.Add(lastItem = new ChartItem(level.ToString(), 1)); + lastLevel = level; + } + else + { + lastItem.Value++; + } + } + } + + return chart; + } + + private static Report CompileTop15() + { + Report report = new Report("Top 15 Duelists", "80%"); + + report.Columns.Add("6%", "center", "Rank"); + report.Columns.Add("6%", "center", "Level"); + report.Columns.Add("6%", "center", "Guild"); + report.Columns.Add("70%", "left", "Name"); + report.Columns.Add("6%", "center", "Wins"); + report.Columns.Add("6%", "center", "Losses"); + + Ladder ladder = Ladder.Instance; + + if (ladder != null) + { + ArrayList entries = ladder.ToArrayList(); + + for (int i = 0; i < entries.Count && i < 15; ++i) + { + LadderEntry entry = (LadderEntry)entries[i]; + int level = Ladder.GetLevel(entry.Experience); + string guild = ""; + + if (entry.Mobile.Guild != null) + guild = entry.Mobile.Guild.Abbreviation; + + ReportItem item = new ReportItem(); + + item.Values.Add(LadderGump.Rank(entry.Index + 1)); + item.Values.Add(level.ToString(), "N0"); + item.Values.Add(guild); + item.Values.Add(entry.Mobile.Name); + item.Values.Add(entry.Wins.ToString(), "N0"); + item.Values.Add(entry.Losses.ToString(), "N0"); + + report.Items.Add(item); + } + } + + return report; + } + + private static Chart CompileDislikedArenas() + { + PieChart chart = new PieChart("Most Disliked Arenas", "graphs_arenas_disliked", false); + + Preferences prefs = Preferences.Instance; + + if (prefs != null) + { + List arenas = Arena.Arenas; + + for (int i = 0; i < arenas.Count; ++i) + { + Arena arena = arenas[i]; + + string name = arena.Name; + + if (name != null) + chart.Items.Add(name, 0); + } - if ( lastItem == null || level != lastLevel ) - { - chart.Items.Add( lastItem = new ChartItem( level.ToString(), 1 ) ); - lastLevel = level; - } - else - { - lastItem.Value++; - } - } - } - - return chart; - } - - private static Report CompileTop15() - { - Report report = new Report( "Top 15 Duelists", "80%" ); - - report.Columns.Add( "6%", "center", "Rank" ); - report.Columns.Add( "6%", "center", "Level" ); - report.Columns.Add( "6%", "center", "Guild" ); - report.Columns.Add( "70%", "left", "Name" ); - report.Columns.Add( "6%", "center", "Wins" ); - report.Columns.Add( "6%", "center", "Losses" ); - - Ladder ladder = Ladder.Instance; - - if ( ladder != null ) - { - ArrayList entries = ladder.ToArrayList(); - - for ( int i = 0; i < entries.Count && i < 15; ++i ) - { - LadderEntry entry = (LadderEntry)entries[i]; - int level = Ladder.GetLevel( entry.Experience ); - string guild = ""; - - if ( entry.Mobile.Guild != null ) - guild = entry.Mobile.Guild.Abbreviation; - - ReportItem item = new ReportItem(); - - item.Values.Add( LadderGump.Rank( entry.Index + 1 ) ); - item.Values.Add( level.ToString(), "N0" ); - item.Values.Add( guild ); - item.Values.Add( entry.Mobile.Name ); - item.Values.Add( entry.Wins.ToString(), "N0" ); - item.Values.Add( entry.Losses.ToString(), "N0" ); - - report.Items.Add( item ); - } - } - - return report; - } - - private static Chart CompileDislikedArenas() - { - PieChart chart = new PieChart( "Most Disliked Arenas", "graphs_arenas_disliked", false ); - - Preferences prefs = Preferences.Instance; - - if ( prefs != null ) - { - List arenas = Arena.Arenas; - - for ( int i = 0; i < arenas.Count; ++i ) - { - Arena arena = arenas[i]; - - string name = arena.Name; - - if ( name != null ) - chart.Items.Add( name, 0 ); - } - - ArrayList entries = prefs.Entries; - - for ( int i = 0; i < entries.Count; ++i ) - { - PreferencesEntry entry = (PreferencesEntry)entries[i]; - ArrayList list = entry.Disliked; - - for ( int j = 0; j < list.Count; ++j ) - { - string disliked = (string)list[j]; - - for ( int k = 0; k < chart.Items.Count; ++k ) - { - ChartItem item = chart.Items[k]; - - if ( item.Name == disliked ) - { - ++item.Value; - break; - } - } - } - } - } - - return chart; - } - - public static Chart CompileStatChart() - { - PieChart chart = new PieChart( "Stat Distribution", "graphs_strdexint_distrib", true ); + ArrayList entries = prefs.Entries; + + for (int i = 0; i < entries.Count; ++i) + { + PreferencesEntry entry = (PreferencesEntry)entries[i]; + ArrayList list = entry.Disliked; - ChartItem strItem = new ChartItem( "Strength", 0 ); - ChartItem dexItem = new ChartItem( "Dexterity", 0 ); - ChartItem intItem = new ChartItem( "Intelligence", 0 ); + for (int j = 0; j < list.Count; ++j) + { + string disliked = (string)list[j]; - foreach ( Mobile mob in World.Mobiles.Values ) - { - if ( mob.RawStatTotal == mob.StatCap && mob is PlayerMobile ) - { - strItem.Value += mob.RawStr; - dexItem.Value += mob.RawDex; - intItem.Value += mob.RawInt; - } - } + for (int k = 0; k < chart.Items.Count; ++k) + { + ChartItem item = chart.Items[k]; - chart.Items.Add( strItem ); - chart.Items.Add( dexItem ); - chart.Items.Add( intItem ); + if (item.Name == disliked) + { + ++item.Value; + break; + } + } + } + } + } - return chart; - } + return chart; + } - public class SkillDistribution : IComparable - { - public SkillInfo m_Skill; - public int m_NumberOfGMs; + public static Chart CompileStatChart() + { + PieChart chart = new PieChart("Stat Distribution", "graphs_strdexint_distrib", true); - public SkillDistribution( SkillInfo skill ) - { - m_Skill = skill; - } + ChartItem strItem = new ChartItem("Strength", 0); + ChartItem dexItem = new ChartItem("Dexterity", 0); + ChartItem intItem = new ChartItem("Intelligence", 0); - public int CompareTo( object obj ) - { - return ( ((SkillDistribution)obj).m_NumberOfGMs - m_NumberOfGMs ); - } - } + foreach (Mobile mob in World.Mobiles.Values) + if (mob.RawStatTotal == mob.StatCap && mob is PlayerMobile) + { + strItem.Value += mob.RawStr; + dexItem.Value += mob.RawDex; + intItem.Value += mob.RawInt; + } - public static SkillDistribution[] GetSkillDistribution() - { - int skip = ( Core.ML ? 0 : Core.SE ? 1 : Core.AOS ? 3 : 6 ); + chart.Items.Add(strItem); + chart.Items.Add(dexItem); + chart.Items.Add(intItem); - SkillDistribution[] distribs = new SkillDistribution[SkillInfo.Table.Length - skip]; + return chart; + } - for ( int i = 0; i < distribs.Length; ++i ) - distribs[i] = new SkillDistribution( SkillInfo.Table[i] ); + public static SkillDistribution[] GetSkillDistribution() + { + int skip = Core.ML ? 0 : Core.SE ? 1 : Core.AOS ? 3 : 6; - foreach ( Mobile mob in World.Mobiles.Values ) - { - if ( mob.SkillsTotal >= 1500 && mob.SkillsTotal <= 7200 && mob is PlayerMobile ) - { - Skills skills = mob.Skills; + SkillDistribution[] distribs = new SkillDistribution[SkillInfo.Table.Length - skip]; - for ( int i = 0; i < skills.Length - skip; ++i ) - { - Skill skill = skills[i]; + for (int i = 0; i < distribs.Length; ++i) + distribs[i] = new SkillDistribution(SkillInfo.Table[i]); - if ( skill.BaseFixedPoint >= 1000 ) - distribs[i].m_NumberOfGMs++; - } - } - } + foreach (Mobile mob in World.Mobiles.Values) + if (mob.SkillsTotal >= 1500 && mob.SkillsTotal <= 7200 && mob is PlayerMobile) + { + Skills skills = mob.Skills; - return distribs; - } + for (int i = 0; i < skills.Length - skip; ++i) + { + Skill skill = skills[i]; - public static PersistableObject[] CompileSkillReports() - { - SkillDistribution[] distribs = GetSkillDistribution(); + if (skill.BaseFixedPoint >= 1000) + distribs[i].m_NumberOfGMs++; + } + } - Array.Sort( distribs ); + return distribs; + } - return new PersistableObject[]{ CompileSkillChart( distribs ), CompileSkillReport( distribs ) }; - } + public static PersistableObject[] CompileSkillReports() + { + SkillDistribution[] distribs = GetSkillDistribution(); - public static Report CompileSkillReport( SkillDistribution[] distribs ) - { - Report report = new Report( "Skill Report", "300" ); + Array.Sort(distribs); - report.Columns.Add( "70%", "left", "Name" ); - report.Columns.Add( "30%", "center", "GMs" ); + return new PersistableObject[] { CompileSkillChart(distribs), CompileSkillReport(distribs) }; + } - for ( int i = 0; i < distribs.Length; ++i ) - report.Items.Add( distribs[i].m_Skill.Name, distribs[i].m_NumberOfGMs, "N0" ); + public static Report CompileSkillReport(SkillDistribution[] distribs) + { + Report report = new Report("Skill Report", "300"); - return report; - } + report.Columns.Add("70%", "left", "Name"); + report.Columns.Add("30%", "center", "GMs"); - public static Chart CompileSkillChart( SkillDistribution[] distribs ) - { - PieChart chart = new PieChart( "GM Skill Distribution", "graphs_skill_distrib", true ); + for (int i = 0; i < distribs.Length; ++i) + report.Items.Add(distribs[i].m_Skill.Name, distribs[i].m_NumberOfGMs, "N0"); - for ( int i = 0; i < 12; ++i ) - chart.Items.Add( distribs[i].m_Skill.Name, distribs[i].m_NumberOfGMs ); + return report; + } - int rem = 0; + public static Chart CompileSkillChart(SkillDistribution[] distribs) + { + PieChart chart = new PieChart("GM Skill Distribution", "graphs_skill_distrib", true); - for ( int i = 12; i < distribs.Length; ++i ) - rem += distribs[i].m_NumberOfGMs; + for (int i = 0; i < 12; ++i) + chart.Items.Add(distribs[i].m_Skill.Name, distribs[i].m_NumberOfGMs); - chart.Items.Add( "Other", rem ); + int rem = 0; - return chart; - } + for (int i = 12; i < distribs.Length; ++i) + rem += distribs[i].m_NumberOfGMs; - public static PersistableObject[] CompileFactionReports() - { - return new PersistableObject[]{ CompileFactionMembershipChart(), CompileFactionReport(), CompileFactionTownReport(), CompileSigilReport(), CompileFactionLeaderboard() }; - } + chart.Items.Add("Other", rem); - public static Chart CompileFactionMembershipChart() - { - PieChart chart = new PieChart( "Faction Membership", "graphs_faction_membership", true ); + return chart; + } - List factions = Faction.Factions; + public static PersistableObject[] CompileFactionReports() + { + return new PersistableObject[] + { + CompileFactionMembershipChart(), CompileFactionReport(), CompileFactionTownReport(), CompileSigilReport(), + CompileFactionLeaderboard() + }; + } - for ( int i = 0; i < factions.Count; ++i ) - chart.Items.Add( factions[i].Definition.FriendlyName, factions[i].Members.Count ); + public static Chart CompileFactionMembershipChart() + { + PieChart chart = new PieChart("Faction Membership", "graphs_faction_membership", true); - return chart; - } + List factions = Faction.Factions; - public static Report CompileFactionLeaderboard() - { - Report report = new Report( "Faction Leaderboard", "60%" ); + for (int i = 0; i < factions.Count; ++i) + chart.Items.Add(factions[i].Definition.FriendlyName, factions[i].Members.Count); - report.Columns.Add( "28%", "center", "Name" ); - report.Columns.Add( "28%", "center", "Faction" ); - report.Columns.Add( "28%", "center", "Office" ); - report.Columns.Add( "16%", "center", "Kill Points" ); + return chart; + } - ArrayList list = new ArrayList(); + public static Report CompileFactionLeaderboard() + { + Report report = new Report("Faction Leaderboard", "60%"); - List factions = Faction.Factions; + report.Columns.Add("28%", "center", "Name"); + report.Columns.Add("28%", "center", "Faction"); + report.Columns.Add("28%", "center", "Office"); + report.Columns.Add("16%", "center", "Kill Points"); - for ( int i = 0; i < factions.Count; ++i ) - { - Faction faction = factions[i]; + ArrayList list = new ArrayList(); - list.AddRange( faction.Members ); - } + List factions = Faction.Factions; - list.Sort(); - list.Reverse(); + for (int i = 0; i < factions.Count; ++i) + { + Faction faction = factions[i]; - for ( int i = 0; i < list.Count && i < 15; ++i ) - { - PlayerState pl = (PlayerState)list[i]; + list.AddRange(faction.Members); + } - string office; + list.Sort(); + list.Reverse(); - if ( pl.Faction.Commander == pl.Mobile ) - office = "Commanding Lord"; - else if ( pl.Finance != null ) - office = $"{pl.Finance.Definition.FriendlyName} Finance Minister"; - else if ( pl.Sheriff != null ) - office = $"{pl.Sheriff.Definition.FriendlyName} Sheriff"; - else - office = ""; + for (int i = 0; i < list.Count && i < 15; ++i) + { + PlayerState pl = (PlayerState)list[i]; - ReportItem item = new ReportItem(); + string office; - item.Values.Add( pl.Mobile.Name ); - item.Values.Add( pl.Faction.Definition.FriendlyName ); - item.Values.Add( office ); - item.Values.Add( pl.KillPoints.ToString(), "N0" ); + if (pl.Faction.Commander == pl.Mobile) + office = "Commanding Lord"; + else if (pl.Finance != null) + office = $"{pl.Finance.Definition.FriendlyName} Finance Minister"; + else if (pl.Sheriff != null) + office = $"{pl.Sheriff.Definition.FriendlyName} Sheriff"; + else + office = ""; - report.Items.Add( item ); - } + ReportItem item = new ReportItem(); - return report; - } + item.Values.Add(pl.Mobile.Name); + item.Values.Add(pl.Faction.Definition.FriendlyName); + item.Values.Add(office); + item.Values.Add(pl.KillPoints.ToString(), "N0"); - public static Report CompileFactionReport() - { - Report report = new Report( "Faction Statistics", "80%" ); + report.Items.Add(item); + } - report.Columns.Add( "20%", "center", "Name" ); - report.Columns.Add( "20%", "center", "Commander" ); - report.Columns.Add( "15%", "center", "Members" ); - report.Columns.Add( "15%", "center", "Merchants" ); - report.Columns.Add( "15%", "center", "Kill Points" ); - report.Columns.Add( "15%", "center", "Silver" ); + return report; + } - List factions = Faction.Factions; + public static Report CompileFactionReport() + { + Report report = new Report("Faction Statistics", "80%"); - for ( int i = 0; i < factions.Count; ++i ) - { - Faction faction = factions[i]; - List members = faction.Members; + report.Columns.Add("20%", "center", "Name"); + report.Columns.Add("20%", "center", "Commander"); + report.Columns.Add("15%", "center", "Members"); + report.Columns.Add("15%", "center", "Merchants"); + report.Columns.Add("15%", "center", "Kill Points"); + report.Columns.Add("15%", "center", "Silver"); - int totalKillPoints = 0; - int totalMerchants = 0; + List factions = Faction.Factions; - for ( int j = 0; j < members.Count; ++j ) - { - totalKillPoints += members[j].KillPoints; + for (int i = 0; i < factions.Count; ++i) + { + Faction faction = factions[i]; + List members = faction.Members; - if ( members[j].MerchantTitle != MerchantTitle.None ) - ++totalMerchants; - } + int totalKillPoints = 0; + int totalMerchants = 0; - ReportItem item = new ReportItem(); + for (int j = 0; j < members.Count; ++j) + { + totalKillPoints += members[j].KillPoints; - item.Values.Add( faction.Definition.FriendlyName ); - item.Values.Add( faction.Commander == null ? "" : faction.Commander.Name ); - item.Values.Add( faction.Members.Count.ToString(), "N0" ); - item.Values.Add( totalMerchants.ToString(), "N0" ); - item.Values.Add( totalKillPoints.ToString(), "N0" ); - item.Values.Add( faction.Silver.ToString(), "N0" ); + if (members[j].MerchantTitle != MerchantTitle.None) + ++totalMerchants; + } - report.Items.Add( item ); - } + ReportItem item = new ReportItem(); - return report; - } + item.Values.Add(faction.Definition.FriendlyName); + item.Values.Add(faction.Commander == null ? "" : faction.Commander.Name); + item.Values.Add(faction.Members.Count.ToString(), "N0"); + item.Values.Add(totalMerchants.ToString(), "N0"); + item.Values.Add(totalKillPoints.ToString(), "N0"); + item.Values.Add(faction.Silver.ToString(), "N0"); - public static Report CompileSigilReport() - { - Report report = new Report( "Faction Town Sigils", "50%" ); + report.Items.Add(item); + } - report.Columns.Add( "35%", "center", "Town" ); - report.Columns.Add( "35%", "center", "Controller" ); - report.Columns.Add( "30%", "center", "Capturable" ); + return report; + } - List sigils = Sigil.Sigils; + public static Report CompileSigilReport() + { + Report report = new Report("Faction Town Sigils", "50%"); - for ( int i = 0; i < sigils.Count; ++i ) - { - Sigil sigil = sigils[i]; + report.Columns.Add("35%", "center", "Town"); + report.Columns.Add("35%", "center", "Controller"); + report.Columns.Add("30%", "center", "Capturable"); - string controller = "Unknown"; + List sigils = Sigil.Sigils; - if ( sigil.RootParent is Mobile mob ) - { - Faction faction = Faction.Find( mob ); + for (int i = 0; i < sigils.Count; ++i) + { + Sigil sigil = sigils[i]; - if ( faction != null ) - controller = faction.Definition.FriendlyName; - } - else if ( sigil.LastMonolith?.Faction != null ) - { - controller = sigil.LastMonolith.Faction.Definition.FriendlyName; - } + string controller = "Unknown"; - ReportItem item = new ReportItem(); + if (sigil.RootParent is Mobile mob) + { + Faction faction = Faction.Find(mob); - item.Values.Add( sigil.Town == null ? "" : sigil.Town.Definition.FriendlyName ); - item.Values.Add( controller ); - item.Values.Add( sigil.IsPurifying ? "No" : "Yes" ); + if (faction != null) + controller = faction.Definition.FriendlyName; + } + else if (sigil.LastMonolith?.Faction != null) + { + controller = sigil.LastMonolith.Faction.Definition.FriendlyName; + } - report.Items.Add( item ); - } + ReportItem item = new ReportItem(); - return report; - } + item.Values.Add(sigil.Town == null ? "" : sigil.Town.Definition.FriendlyName); + item.Values.Add(controller); + item.Values.Add(sigil.IsPurifying ? "No" : "Yes"); - public static Report CompileFactionTownReport() - { - Report report = new Report( "Faction Towns", "80%" ); + report.Items.Add(item); + } + + return report; + } - report.Columns.Add( "20%", "center", "Name" ); - report.Columns.Add( "20%", "center", "Owner" ); - report.Columns.Add( "17%", "center", "Sheriff" ); - report.Columns.Add( "17%", "center", "Finance Minister" ); - report.Columns.Add( "13%", "center", "Silver" ); - report.Columns.Add( "13%", "center", "Prices" ); + public static Report CompileFactionTownReport() + { + Report report = new Report("Faction Towns", "80%"); - List towns = Town.Towns; + report.Columns.Add("20%", "center", "Name"); + report.Columns.Add("20%", "center", "Owner"); + report.Columns.Add("17%", "center", "Sheriff"); + report.Columns.Add("17%", "center", "Finance Minister"); + report.Columns.Add("13%", "center", "Silver"); + report.Columns.Add("13%", "center", "Prices"); - for ( int i = 0; i < towns.Count; ++i ) - { - Town town = towns[i]; + List towns = Town.Towns; - string prices = "Normal"; + for (int i = 0; i < towns.Count; ++i) + { + Town town = towns[i]; + + string prices = "Normal"; - if ( town.Tax < 0 ) - prices = town.Tax.ToString() + "%"; - else if ( town.Tax > 0 ) - prices = "+" + town.Tax.ToString() + "%"; + if (town.Tax < 0) + prices = town.Tax + "%"; + else if (town.Tax > 0) + prices = "+" + town.Tax + "%"; - ReportItem item = new ReportItem(); + ReportItem item = new ReportItem(); - item.Values.Add( town.Definition.FriendlyName ); - item.Values.Add( town.Owner == null ? "Neutral" : town.Owner.Definition.FriendlyName ); - item.Values.Add( town.Sheriff == null ? "" : town.Sheriff.Name ); - item.Values.Add( town.Finance == null ? "" : town.Finance.Name ); - item.Values.Add( town.Silver.ToString(), "N0" ); - item.Values.Add( prices ); + item.Values.Add(town.Definition.FriendlyName); + item.Values.Add(town.Owner == null ? "Neutral" : town.Owner.Definition.FriendlyName); + item.Values.Add(town.Sheriff == null ? "" : town.Sheriff.Name); + item.Values.Add(town.Finance == null ? "" : town.Finance.Name); + item.Values.Add(town.Silver.ToString(), "N0"); + item.Values.Add(prices); - report.Items.Add( item ); - } + report.Items.Add(item); + } - return report; - } - } -} + return report; + } + + public class SkillDistribution : IComparable + { + public int m_NumberOfGMs; + public SkillInfo m_Skill; + + public SkillDistribution(SkillInfo skill) + { + m_Skill = skill; + } + + public int CompareTo(object obj) + { + return ((SkillDistribution)obj).m_NumberOfGMs - m_NumberOfGMs; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Spawner/ProximitySpawner.cs b/Scripts/Engines/Spawner/ProximitySpawner.cs index 4fb8e63a2..e8274df2e 100644 --- a/Scripts/Engines/Spawner/ProximitySpawner.cs +++ b/Scripts/Engines/Spawner/ProximitySpawner.cs @@ -2,129 +2,131 @@ using System; namespace Server.Mobiles { - public class ProximitySpawner : Spawner - { - [CommandProperty( AccessLevel.Developer )] - public int TriggerRange { get; set; } + public class ProximitySpawner : Spawner + { + [Constructible] + public ProximitySpawner() + { + } - [CommandProperty( AccessLevel.Developer )] - public TextDefinition SpawnMessage { get; set; } + [Constructible] + public ProximitySpawner(string spawnName) + : base(spawnName) + { + } - [CommandProperty( AccessLevel.Developer )] - public bool InstantFlag { get; set; } + [Constructible] + public ProximitySpawner(int amount, int minDelay, int maxDelay, int team, int homeRange, string spawnName) + : base(amount, minDelay, maxDelay, team, homeRange, spawnName) + { + } - [Constructible] - public ProximitySpawner() - { - } + [Constructible] + public ProximitySpawner(int amount, int minDelay, int maxDelay, int team, int homeRange, int triggerRange, + string spawnMessage, bool instantFlag, string spawnName) + : base(amount, minDelay, maxDelay, team, homeRange, spawnName) + { + TriggerRange = triggerRange; + SpawnMessage = TextDefinition.Parse(spawnMessage); + InstantFlag = instantFlag; + } - [Constructible] - public ProximitySpawner( string spawnName ) - : base( spawnName ) - { - } + public ProximitySpawner(int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange, + params string[] spawnedNames) + : base(amount, minDelay, maxDelay, team, homeRange, spawnedNames) + { + } - [Constructible] - public ProximitySpawner( int amount, int minDelay, int maxDelay, int team, int homeRange, string spawnName ) - : base( amount, minDelay, maxDelay, team, homeRange, spawnName ) - { - } + public ProximitySpawner(int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange, int triggerRange, + TextDefinition spawnMessage, bool instantFlag, params string[] spawnedNames) + : base(amount, minDelay, maxDelay, team, homeRange, spawnedNames) + { + TriggerRange = triggerRange; + SpawnMessage = spawnMessage; + InstantFlag = instantFlag; + } - [Constructible] - public ProximitySpawner( int amount, int minDelay, int maxDelay, int team, int homeRange, int triggerRange, string spawnMessage, bool instantFlag, string spawnName ) - : base( amount, minDelay, maxDelay, team, homeRange, spawnName ) - { - TriggerRange = triggerRange; - SpawnMessage = TextDefinition.Parse( spawnMessage ); - InstantFlag = instantFlag; - } + public ProximitySpawner(Serial serial) + : base(serial) + { + } - public ProximitySpawner( int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange, params string[] spawnedNames ) - : base( amount, minDelay, maxDelay, team, homeRange, spawnedNames ) - { - } + [CommandProperty(AccessLevel.Developer)] + public int TriggerRange{ get; set; } - public ProximitySpawner( int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange, int triggerRange, TextDefinition spawnMessage, bool instantFlag, params string[] spawnedNames ) - : base( amount, minDelay, maxDelay, team, homeRange, spawnedNames ) - { - TriggerRange = triggerRange; - SpawnMessage = spawnMessage; - InstantFlag = instantFlag; - } + [CommandProperty(AccessLevel.Developer)] + public TextDefinition SpawnMessage{ get; set; } - public override string DefaultName => "Proximity Spawner"; + [CommandProperty(AccessLevel.Developer)] + public bool InstantFlag{ get; set; } - public override void DoTimer( TimeSpan delay ) - { - if ( !Running ) - return; + public override string DefaultName => "Proximity Spawner"; - End = DateTime.UtcNow + delay; - } + public override bool HandlesOnMovement => true; - public override void Respawn() - { - RemoveSpawns(); + public override void DoTimer(TimeSpan delay) + { + if (!Running) + return; - End = DateTime.UtcNow; - } + End = DateTime.UtcNow + delay; + } - public override bool HandlesOnMovement => true; + public override void Respawn() + { + RemoveSpawns(); - public virtual bool ValidTrigger( Mobile m ) - { - if (m is BaseCreature bc && (bc.IsDeadBondedPet || !(bc.Controlled || bc.Summoned))) - return false; + End = DateTime.UtcNow; + } - return m.AccessLevel == AccessLevel.Player && ( m.Player || ( m.Alive && !m.Hidden && m.CanBeDamaged() ) ); - } + public virtual bool ValidTrigger(Mobile m) + { + if (m is BaseCreature bc && (bc.IsDeadBondedPet || !(bc.Controlled || bc.Summoned))) + return false; - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( !Running ) - return; + return m.AccessLevel == AccessLevel.Player && (m.Player || m.Alive && !m.Hidden && m.CanBeDamaged()); + } - if ( IsEmpty && End <= DateTime.UtcNow && m.InRange( GetWorldLocation(), TriggerRange ) && m.Location != oldLocation && ValidTrigger( m ) ) - { - TextDefinition.SendMessageTo( m, SpawnMessage ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (!Running) + return; - DoTimer(); - Spawn(); + if (IsEmpty && End <= DateTime.UtcNow && m.InRange(GetWorldLocation(), TriggerRange) && + m.Location != oldLocation && ValidTrigger(m)) + { + TextDefinition.SendMessageTo(m, SpawnMessage); - if ( InstantFlag ) - { - foreach ( ISpawnable spawned in Spawned.Keys ) - if ( spawned is Mobile mobile ) - mobile.Combatant = m; - } - } - } + DoTimer(); + Spawn(); - public ProximitySpawner( Serial serial ) - : base( serial ) - { - } + if (InstantFlag) + foreach (ISpawnable spawned in Spawned.Keys) + if (spawned is Mobile mobile) + mobile.Combatant = m; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( TriggerRange ); - TextDefinition.Serialize( writer, SpawnMessage ); - writer.Write( InstantFlag ); - } + writer.Write(TriggerRange); + TextDefinition.Serialize(writer, SpawnMessage); + writer.Write(InstantFlag); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - TriggerRange = reader.ReadInt(); - SpawnMessage = TextDefinition.Deserialize( reader ); - InstantFlag = reader.ReadBool(); - } - } -} + TriggerRange = reader.ReadInt(); + SpawnMessage = TextDefinition.Deserialize(reader); + InstantFlag = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Spawner/Spawner.cs b/Scripts/Engines/Spawner/Spawner.cs index 5a8c8545c..5c21ab036 100644 --- a/Scripts/Engines/Spawner/Spawner.cs +++ b/Scripts/Engines/Spawner/Spawner.cs @@ -1,275 +1,333 @@ using System; +using System.Collections.Generic; using System.IO; using System.Reflection; -using System.Collections.Generic; -using Server.Items; using Server.Commands; +using Server.Items; using CPA = Server.CommandPropertyAttribute; namespace Server.Mobiles { - public class Spawner : Item, ISpawner - { - private int m_Team; - private int m_HomeRange; - private int m_Count; - private int m_WalkingRange = -1; - private TimeSpan m_MinDelay; - private TimeSpan m_MaxDelay; + public class Spawner : Item, ISpawner + { + private static WarnTimer m_WarnTimer; + private int m_Count; + private bool m_Group; + private int m_HomeRange; + private TimeSpan m_MaxDelay; + private TimeSpan m_MinDelay; + private bool m_Running; + private int m_Team; - private InternalTimer m_Timer; - private bool m_Running; - private bool m_Group; - - public override string DefaultName => "Spawner"; - public bool IsFull => ( Spawned != null && Spawned.Count >= m_Count ); - public bool IsEmpty => ( Spawned != null && Spawned.Count == 0 ); - - public Point3D HomeLocation => Location; - public bool UnlinkOnTaming => true; - public DateTime End { get; set; } - - public List Entries { get; private set; } - - public Dictionary Spawned { get; private set; } - - public override void OnAfterDuped( Item newItem ) - { - if ( newItem is Spawner newSpawner ) - { - for ( int i = 0; i < Entries.Count; i++ ) - newSpawner.AddEntry( Entries[i].SpawnedName, Entries[i].SpawnedProbability, Entries[i].SpawnedMaxCount, false ); - } - } - - [CommandProperty( AccessLevel.Developer )] - public int Count - { - get => m_Count; - set - { - m_Count = value; - - if ( m_Timer != null ) - { - if ( ( !IsFull && !m_Timer.Running ) || IsFull && m_Timer.Running ) - DoTimer(); - } - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.Developer )] - public WayPoint WayPoint { get; set; } - - [CommandProperty( AccessLevel.Developer )] - public bool Running - { - get => m_Running; - set - { - if ( value ) - Start(); - else - Stop(); - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.Developer )] - public int HomeRange{ get => m_HomeRange; - set { m_HomeRange = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.Developer )] - public int WalkingRange{ get => m_WalkingRange; - set { m_WalkingRange = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.Developer )] - public int Team{ get => m_Team; - set { m_Team = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.Developer )] - public TimeSpan MinDelay{ get => m_MinDelay; - set { m_MinDelay = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.Developer )] - public TimeSpan MaxDelay{ get => m_MaxDelay; - set { m_MaxDelay = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.Developer )] - public TimeSpan NextSpawn - { - get - { - if ( m_Running && m_Timer != null && m_Timer.Running ) - return End - DateTime.UtcNow; - return TimeSpan.FromSeconds( 0 ); - } - set - { - Start(); - DoTimer( value ); - } - } - - [CommandProperty( AccessLevel.Developer )] - public bool Group - { - get => m_Group; - set { m_Group = value; InvalidateProperties(); } - } - - Region ISpawner.Region => Region.Find( Location, Map ); + private InternalTimer m_Timer; + private int m_WalkingRange = -1; // [Constructible] - public Spawner( int amount, int minDelay, int maxDelay, int team, int homeRange, string spawnedNames ) : base( 0x1f13 ) - { - InitSpawn( amount, TimeSpan.FromMinutes( minDelay ), TimeSpan.FromMinutes( maxDelay ), team, homeRange ); - AddEntry( spawnedNames, 100, amount, false ); - } + public Spawner(int amount, int minDelay, int maxDelay, int team, int homeRange, string spawnedNames) : base(0x1f13) + { + InitSpawn(amount, TimeSpan.FromMinutes(minDelay), TimeSpan.FromMinutes(maxDelay), team, homeRange); + AddEntry(spawnedNames, 100, amount, false); + } // [Constructible] - public Spawner( string spawnedName ) : base( 0x1f13 ) - { - InitSpawn( 1, TimeSpan.FromMinutes( 5 ), TimeSpan.FromMinutes( 10 ), 0, 4 ); - AddEntry( spawnedName, 100, 1, false ); - } + public Spawner(string spawnedName) : base(0x1f13) + { + InitSpawn(1, TimeSpan.FromMinutes(5), TimeSpan.FromMinutes(10), 0, 4); + AddEntry(spawnedName, 100, 1, false); + } - [Constructible( AccessLevel.Developer )] - public Spawner() : base( 0x1f13 ) - { - InitSpawn( 1, TimeSpan.FromMinutes( 5 ), TimeSpan.FromMinutes( 10 ), 0, 4 ); - } + [Constructible(AccessLevel.Developer)] + public Spawner() : base(0x1f13) + { + InitSpawn(1, TimeSpan.FromMinutes(5), TimeSpan.FromMinutes(10), 0, 4); + } - public Spawner( int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange, params string[] spawnedNames ) : base( 0x1f13 ) - { - InitSpawn( amount, minDelay, maxDelay, team, homeRange ); - for ( int i = 0;i < spawnedNames.Length; i++ ) - AddEntry( spawnedNames[i], 100, amount, false ); - } + public Spawner(int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange, + params string[] spawnedNames) : base(0x1f13) + { + InitSpawn(amount, minDelay, maxDelay, team, homeRange); + for (int i = 0; i < spawnedNames.Length; i++) + AddEntry(spawnedNames[i], 100, amount, false); + } - public SpawnerEntry AddEntry( string creaturename, int probability, int amount ) - { - return AddEntry( creaturename, probability, amount, true ); - } + public Spawner(Serial serial) : base(serial) + { + } - public SpawnerEntry AddEntry( string creaturename, int probability, int amount, bool dotimer ) - { - SpawnerEntry entry = new SpawnerEntry( creaturename, probability, amount ); - Entries.Add( entry ); - if ( dotimer ) - DoTimer( TimeSpan.FromSeconds( 1 ) ); + public override string DefaultName => "Spawner"; + public bool IsFull => Spawned != null && Spawned.Count >= m_Count; + public bool IsEmpty => Spawned != null && Spawned.Count == 0; + public DateTime End{ get; set; } - return entry; - } + public List Entries{ get; private set; } - public void InitSpawn( int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange ) - { - Visible = false; - Movable = false; - m_Running = true; - m_Group = false; - m_MinDelay = minDelay; - m_MaxDelay = maxDelay; - m_Count = amount; - m_Team = team; - m_HomeRange = homeRange; - Entries = new List(); - Spawned = new Dictionary(); + public Dictionary Spawned{ get; private set; } - DoTimer( TimeSpan.FromSeconds( 1 ) ); - } + [CommandProperty(AccessLevel.Developer)] + public int Count + { + get => m_Count; + set + { + m_Count = value; - public Spawner( Serial serial ) : base( serial ) - { - } + if (m_Timer != null) + if (!IsFull && !m_Timer.Running || IsFull && m_Timer.Running) + DoTimer(); - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.Developer ) - from.SendGump( new SpawnerGump( this ) ); - } + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.Developer)] + public WayPoint WayPoint{ get; set; } - if ( m_Running ) - { - list.Add( 1060742 ); // active + [CommandProperty(AccessLevel.Developer)] + public bool Running + { + get => m_Running; + set + { + if (value) + Start(); + else + Stop(); - list.Add( 1060656, m_Count.ToString() ); // amount to make: ~1_val~ - list.Add( 1061169, m_HomeRange.ToString() ); // range ~1_val~ - list.Add( 1060658, "walking range\t{0}", m_WalkingRange ); // ~1_val~: ~2_val~ + InvalidateProperties(); + } + } - list.Add( 1060658, "group\t{0}", m_Group ); // ~1_val~: ~2_val~ - list.Add( 1060659, "team\t{0}", m_Team ); // ~1_val~: ~2_val~ - list.Add( 1060660, "speed\t{0} to {1}", m_MinDelay, m_MaxDelay ); // ~1_val~: ~2_val~ + [CommandProperty(AccessLevel.Developer)] + public int WalkingRange + { + get => m_WalkingRange; + set + { + m_WalkingRange = value; + InvalidateProperties(); + } + } - for ( int i = 0; i < 3 && i < Entries.Count; ++i ) - list.Add( 1060661 + i, "{0}\t{1}", Entries[i].SpawnedName, CountSpawns( Entries[i] ) ); - } - else - list.Add( 1060743 ); // inactive - } + [CommandProperty(AccessLevel.Developer)] + public int Team + { + get => m_Team; + set + { + m_Team = value; + InvalidateProperties(); + } + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + [CommandProperty(AccessLevel.Developer)] + public TimeSpan MinDelay + { + get => m_MinDelay; + set + { + m_MinDelay = value; + InvalidateProperties(); + } + } - if ( m_Running ) - LabelTo( from, "[Running]" ); - else - LabelTo( from, "[Off]" ); - } + [CommandProperty(AccessLevel.Developer)] + public TimeSpan MaxDelay + { + get => m_MaxDelay; + set + { + m_MaxDelay = value; + InvalidateProperties(); + } + } - public void Start() - { - if ( !m_Running ) - { - if ( Entries.Count > 0 ) - { - m_Running = true; - DoTimer(); - } - } - } + [CommandProperty(AccessLevel.Developer)] + public TimeSpan NextSpawn + { + get + { + if (m_Running && m_Timer != null && m_Timer.Running) + return End - DateTime.UtcNow; + return TimeSpan.FromSeconds(0); + } + set + { + Start(); + DoTimer(value); + } + } - public void Stop() - { - if ( m_Running ) - { - m_Timer?.Stop(); - m_Running = false; - } - } + [CommandProperty(AccessLevel.Developer)] + public bool Group + { + get => m_Group; + set + { + m_Group = value; + InvalidateProperties(); + } + } - public void Defrag() - { - if ( Entries == null ) - Entries = new List(); + public Point3D HomeLocation => Location; + public bool UnlinkOnTaming => true; - for ( int i = 0; i < Entries.Count; ++i ) - Entries[i].Defrag( this ); - } + [CommandProperty(AccessLevel.Developer)] + public int HomeRange + { + get => m_HomeRange; + set + { + m_HomeRange = value; + InvalidateProperties(); + } + } - public void OnTick() - { + Region ISpawner.Region => Region.Find(Location, Map); + + public void Remove(ISpawnable spawn) + { + Defrag(); + + if (spawn != null) + { + Spawned.TryGetValue(spawn, out SpawnerEntry entry); + + entry?.Spawned.Remove(spawn); + + Spawned.Remove(spawn); + } + + if (m_Running && !IsFull && m_Timer != null && !m_Timer.Running) + DoTimer(); + } + + public override void OnAfterDuped(Item newItem) + { + if (newItem is Spawner newSpawner) + for (int i = 0; i < Entries.Count; i++) + newSpawner.AddEntry(Entries[i].SpawnedName, Entries[i].SpawnedProbability, Entries[i].SpawnedMaxCount, + false); + } + + public SpawnerEntry AddEntry(string creaturename, int probability, int amount) + { + return AddEntry(creaturename, probability, amount, true); + } + + public SpawnerEntry AddEntry(string creaturename, int probability, int amount, bool dotimer) + { + SpawnerEntry entry = new SpawnerEntry(creaturename, probability, amount); + Entries.Add(entry); + if (dotimer) + DoTimer(TimeSpan.FromSeconds(1)); + + return entry; + } + + public void InitSpawn(int amount, TimeSpan minDelay, TimeSpan maxDelay, int team, int homeRange) + { + Visible = false; + Movable = false; + m_Running = true; + m_Group = false; + m_MinDelay = minDelay; + m_MaxDelay = maxDelay; + m_Count = amount; + m_Team = team; + m_HomeRange = homeRange; + Entries = new List(); + Spawned = new Dictionary(); + + DoTimer(TimeSpan.FromSeconds(1)); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.Developer) + from.SendGump(new SpawnerGump(this)); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Running) + { + list.Add(1060742); // active + + list.Add(1060656, m_Count.ToString()); // amount to make: ~1_val~ + list.Add(1061169, m_HomeRange.ToString()); // range ~1_val~ + list.Add(1060658, "walking range\t{0}", m_WalkingRange); // ~1_val~: ~2_val~ + + list.Add(1060658, "group\t{0}", m_Group); // ~1_val~: ~2_val~ + list.Add(1060659, "team\t{0}", m_Team); // ~1_val~: ~2_val~ + list.Add(1060660, "speed\t{0} to {1}", m_MinDelay, m_MaxDelay); // ~1_val~: ~2_val~ + + for (int i = 0; i < 3 && i < Entries.Count; ++i) + list.Add(1060661 + i, "{0}\t{1}", Entries[i].SpawnedName, CountSpawns(Entries[i])); + } + else + { + list.Add(1060743); // inactive + } + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (m_Running) + LabelTo(from, "[Running]"); + else + LabelTo(from, "[Off]"); + } + + public void Start() + { + if (!m_Running) + if (Entries.Count > 0) + { + m_Running = true; + DoTimer(); + } + } + + public void Stop() + { + if (m_Running) + { + m_Timer?.Stop(); + m_Running = false; + } + } + + public void Defrag() + { + if (Entries == null) + Entries = new List(); + + for (int i = 0; i < Entries.Count; ++i) + Entries[i].Defrag(this); + } + + public void OnTick() + { // DoTimer( m_Spawned.Count >= m_Count ); - if ( m_Group ) - { - Defrag(); + if (m_Group) + { + Defrag(); - if ( Spawned.Count > 0 ) - return; + if (Spawned.Count > 0) + return; + + Respawn(); + } + else + { + Spawn(); + } - Respawn(); - } - else - Spawn(); /* if ( m_Running && m_Timer != null ) { @@ -279,885 +337,865 @@ namespace Server.Mobiles DoTimer( false ); } */ - DoTimer(); - } - - public virtual void Respawn() - { - RemoveSpawns(); - - for ( int i = 0; i < m_Count; i++ ) - Spawn(); - - DoTimer(); //Turn off the timer! - } - - public virtual void Spawn() - { - Defrag(); - - if ( Entries.Count > 0 && !IsFull ) - { - int probsum = 0; - - for ( int i = 0; i < Entries.Count; i++ ) - if ( !Entries[i].IsFull ) - probsum += Entries[i].SpawnedProbability; - - if ( probsum > 0 ) - { - int rand = Utility.RandomMinMax( 1, probsum ); - - for ( int i = 0; i < Entries.Count; i++ ) - { - SpawnerEntry entry = Entries[i]; - if ( !entry.IsFull ) - { - bool success = true; - - if ( rand <= entry.SpawnedProbability ) - { - EntryFlags flags; - success = Spawn( entry, out flags ); - entry.Valid = flags; - return; - } - - if ( success ) - rand -= entry.SpawnedProbability; - } - } - } - } - } - - private static string[,] FormatProperties( string[] args ) - { - string[,] props = null; - - int remains = args.Length; - - if ( remains >= 2 ) - { - props = new string[remains / 2, 2]; - - remains /= 2; - - for ( int j = 0; j < remains; ++j ) - { - props[j, 0] = args[j * 2]; - props[j, 1] = args[(j * 2) + 1]; - } - } - else - props = new string[0,0]; - - return props; - } - - private static PropertyInfo[] GetTypeProperties( Type type, string[,] props ) - { - PropertyInfo[] realProps = null; - - if ( props != null ) - { - realProps = new PropertyInfo[props.GetLength( 0 )]; - - PropertyInfo[] allProps = type.GetProperties( BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public ); - - for ( int i = 0; i < realProps.Length; ++i ) - { - PropertyInfo thisProp = null; - - string propName = props[i, 0]; - - for ( int j = 0; thisProp == null && j < allProps.Length; ++j ) - { - if ( Insensitive.Equals( propName, allProps[j].Name ) ) - thisProp = allProps[j]; - } - - if ( thisProp == null ) - return null; - CPA attr = Properties.GetCPA( thisProp ); - - if ( attr == null || AccessLevel.Developer < attr.WriteLevel || !thisProp.CanWrite || attr.ReadOnly ) - return null; - realProps[i] = thisProp; - } - } - - return realProps; - } - - public bool Spawn( int index, out EntryFlags flags ) - { - if ( index >= 0 && index < Entries.Count ) - return Spawn( Entries[index], out flags ); - flags = EntryFlags.InvalidEntry; - return false; - } - - public bool Spawn( SpawnerEntry entry, out EntryFlags flags ) - { - Map map = GetSpawnMap(); - flags = EntryFlags.None; - - if ( map == null || map == Map.Internal || Parent != null ) - return false; - - //Defrag taken care of in Spawn(), beforehand - //Count check taken care of in Spawn(), beforehand - - Type type = SpawnerType.GetType( entry.SpawnedName ); - - if ( type != null ) - { - try - { - object o = null; - string[] paramargs; - string[] propargs; - - if ( string.IsNullOrEmpty( entry.Properties ) ) - propargs = new string[0]; - else - propargs = CommandSystem.Split( entry.Properties.Trim() ); - - string[,] props = FormatProperties( propargs ); - - PropertyInfo[] realProps = GetTypeProperties( type, props ); - - if ( realProps == null ) - { - flags = EntryFlags.InvalidProps; - return false; - } - - if ( string.IsNullOrEmpty( entry.Parameters ) ) - paramargs = new string[0]; - else - paramargs = entry.Parameters.Trim().Split( ' ' ); - - ConstructorInfo[] ctors = type.GetConstructors(); - - for ( int i = 0; i < ctors.Length; ++i ) - { - ConstructorInfo ctor = ctors[i]; - - if ( Add.IsConstructible( ctor, AccessLevel.Developer ) ) - { - ParameterInfo[] paramList = ctor.GetParameters(); - - if ( paramargs.Length == paramList.Length ) - { - object[] paramValues = Add.ParseValues( paramList, paramargs ); - - if ( paramValues != null ) - { - o = ctor.Invoke( paramValues ); - for ( int j = 0; j < realProps.Length; j++ ) - { - if ( realProps[j] != null ) - { - object toSet = null; - string result = Properties.ConstructFromString( realProps[j].PropertyType, o, props[j, 1], ref toSet ); - if ( result == null ) - realProps[j].SetValue( o, toSet, null ); - else - { - flags = EntryFlags.InvalidProps; - - if ( o is ISpawnable spawnable ) - spawnable.Delete(); - - return false; - } - } - } - break; - } - } - } - } - - if ( o is Mobile m ) - { - Spawned.Add( m, entry ); - entry.Spawned.Add( m ); - - Point3D loc = ( m is BaseVendor ? Location : GetSpawnPosition( m, map ) ); - - m.OnBeforeSpawn( loc, map ); - InvalidateProperties(); - - m.MoveToWorld( loc, map ); - - if ( m is BaseCreature c ) - { - int walkrange = GetWalkingRange(); - - if ( walkrange >= 0 ) - c.RangeHome = walkrange; - else - c.RangeHome = m_HomeRange; - - c.CurrentWayPoint = GetWayPoint(); - - if ( m_Team > 0 ) - c.Team = m_Team; - - c.Home = Location; - c.HomeMap = Map; - } - - m.Spawner = this; - m.OnAfterSpawn(); - } - else if ( o is Item item ) - { - Spawned.Add( item, entry ); - entry.Spawned.Add( item ); - - Point3D loc = GetSpawnPosition( item, map ); - - item.OnBeforeSpawn( loc, map ); - - item.MoveToWorld( loc, map ); - - item.Spawner = this; - item.OnAfterSpawn(); - } - else - { - flags = EntryFlags.InvalidType | EntryFlags.InvalidParams; - return false; - } - } - catch ( Exception e ) - { - Console.WriteLine( "EXCEPTION CAUGHT: {0:X}", Serial ); - Console.WriteLine( e ); - return false; - } - - InvalidateProperties(); - return true; - } - - flags = EntryFlags.InvalidType; - return false; - } - - public virtual int GetWalkingRange() - { - return m_WalkingRange; - } - - public virtual WayPoint GetWayPoint() - { - return WayPoint; - } - - public virtual Point3D GetSpawnPosition( ISpawnable spawned, Map map ) - { - if ( map == null || map == Map.Internal ) - return Location; - - bool waterMob, waterOnlyMob; - - if ( spawned is Mobile mob ) - { - waterMob = mob.CanSwim; - waterOnlyMob = ( mob.CanSwim && mob.CantWalk ); - } - else - { - waterMob = false; - waterOnlyMob = false; - } - - // Try 10 times to find a Spawnable location. - for ( int i = 0; i < 10; i++ ) - { - int x = Location.X + (Utility.Random( (m_HomeRange * 2) + 1 ) - m_HomeRange); - int y = Location.Y + (Utility.Random( (m_HomeRange * 2) + 1 ) - m_HomeRange); - int z = Map.GetAverageZ( x, y ); - - int mapZ = map.GetAverageZ( x, y ); - - if ( waterMob ) - { - if ( IsValidWater( map, x, y, Z ) ) - return new Point3D( x, y, Z ); - if ( IsValidWater( map, x, y, mapZ ) ) - return new Point3D( x, y, mapZ ); - } - - if ( !waterOnlyMob ) - { - if ( map.CanSpawnMobile( x, y, Z ) ) - return new Point3D( x, y, Z ); - if ( map.CanSpawnMobile( x, y, mapZ ) ) - return new Point3D( x, y, mapZ ); - } - } - - return Location; - } - - public static bool IsValidWater( Map map, int x, int y, int z ) - { - if ( !Region.Find( new Point3D( x, y, z ), map ).AllowSpawn() || !map.CanFit( x, y, z, 16, false, true, false ) ) - return false; - - LandTile landTile = map.Tiles.GetLandTile( x, y ); - - if ( landTile.Z == z && ( TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet ) != 0 ) - return true; - - StaticTile[] staticTiles = map.Tiles.GetStaticTiles( x, y, true ); - - for ( int i = 0; i < staticTiles.Length; ++i ) - { - StaticTile staticTile = staticTiles[i]; - - if ( staticTile.Z == z && ( TileData.ItemTable[staticTile.ID & TileData.MaxItemValue].Flags & TileFlag.Wet ) != 0 ) - return true; - } - - return false; - } - - public virtual Map GetSpawnMap() - { - return Map; - } - - public void DoTimer() - { - if ( !m_Running ) - return; - - int minSeconds = (int)m_MinDelay.TotalSeconds; - int maxSeconds = (int)m_MaxDelay.TotalSeconds; - - TimeSpan delay = TimeSpan.FromSeconds( Utility.RandomMinMax( minSeconds, maxSeconds ) ); - DoTimer( delay ); - } - - public virtual void DoTimer( TimeSpan delay ) - { - if ( !m_Running ) - return; - - End = DateTime.UtcNow + delay; - - m_Timer?.Stop(); - - m_Timer = new InternalTimer( this, delay ); - if ( !IsFull ) - m_Timer.Start(); - } - - private class InternalTimer : Timer - { - private Spawner m_Spawner; - - public InternalTimer( Spawner spawner, TimeSpan delay ) : base( delay ) - { - if ( spawner.IsFull ) - Priority = TimerPriority.FiveSeconds; - else - Priority = TimerPriority.OneSecond; - - m_Spawner = spawner; - } - - protected override void OnTick() - { - if ( m_Spawner != null ) - if ( !m_Spawner.Deleted ) - m_Spawner.OnTick(); - } - } - - public int CountSpawns( SpawnerEntry entry ) - { - Defrag(); - - return entry.Spawned.Count; - } - - public void RemoveEntry( SpawnerEntry entry ) - { - Defrag(); - - for ( int i = entry.Spawned.Count-1; i >= 0; i-- ) - { - ISpawnable e = entry.Spawned[i]; - entry.Spawned.RemoveAt( i ); - e?.Delete(); - } + DoTimer(); + } + + public virtual void Respawn() + { + RemoveSpawns(); + + for (int i = 0; i < m_Count; i++) + Spawn(); + + DoTimer(); //Turn off the timer! + } + + public virtual void Spawn() + { + Defrag(); + + if (Entries.Count > 0 && !IsFull) + { + int probsum = 0; + + for (int i = 0; i < Entries.Count; i++) + if (!Entries[i].IsFull) + probsum += Entries[i].SpawnedProbability; + + if (probsum > 0) + { + int rand = Utility.RandomMinMax(1, probsum); + + for (int i = 0; i < Entries.Count; i++) + { + SpawnerEntry entry = Entries[i]; + if (!entry.IsFull) + { + bool success = true; + + if (rand <= entry.SpawnedProbability) + { + EntryFlags flags; + success = Spawn(entry, out flags); + entry.Valid = flags; + return; + } + + if (success) + rand -= entry.SpawnedProbability; + } + } + } + } + } + + private static string[,] FormatProperties(string[] args) + { + string[,] props = null; + + int remains = args.Length; + + if (remains >= 2) + { + props = new string[remains / 2, 2]; + + remains /= 2; + + for (int j = 0; j < remains; ++j) + { + props[j, 0] = args[j * 2]; + props[j, 1] = args[j * 2 + 1]; + } + } + else + { + props = new string[0, 0]; + } + + return props; + } + + private static PropertyInfo[] GetTypeProperties(Type type, string[,] props) + { + PropertyInfo[] realProps = null; + + if (props != null) + { + realProps = new PropertyInfo[props.GetLength(0)]; + + PropertyInfo[] allProps = + type.GetProperties(BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public); + + for (int i = 0; i < realProps.Length; ++i) + { + PropertyInfo thisProp = null; + + string propName = props[i, 0]; + + for (int j = 0; thisProp == null && j < allProps.Length; ++j) + if (Insensitive.Equals(propName, allProps[j].Name)) + thisProp = allProps[j]; + + if (thisProp == null) + return null; + CPA attr = Properties.GetCPA(thisProp); + + if (attr == null || AccessLevel.Developer < attr.WriteLevel || !thisProp.CanWrite || attr.ReadOnly) + return null; + realProps[i] = thisProp; + } + } + + return realProps; + } + + public bool Spawn(int index, out EntryFlags flags) + { + if (index >= 0 && index < Entries.Count) + return Spawn(Entries[index], out flags); + flags = EntryFlags.InvalidEntry; + return false; + } + + public bool Spawn(SpawnerEntry entry, out EntryFlags flags) + { + Map map = GetSpawnMap(); + flags = EntryFlags.None; + + if (map == null || map == Map.Internal || Parent != null) + return false; + + //Defrag taken care of in Spawn(), beforehand + //Count check taken care of in Spawn(), beforehand + + Type type = SpawnerType.GetType(entry.SpawnedName); + + if (type != null) + { + try + { + object o = null; + string[] paramargs; + string[] propargs; + + if (string.IsNullOrEmpty(entry.Properties)) + propargs = new string[0]; + else + propargs = CommandSystem.Split(entry.Properties.Trim()); + + string[,] props = FormatProperties(propargs); + + PropertyInfo[] realProps = GetTypeProperties(type, props); + + if (realProps == null) + { + flags = EntryFlags.InvalidProps; + return false; + } + + if (string.IsNullOrEmpty(entry.Parameters)) + paramargs = new string[0]; + else + paramargs = entry.Parameters.Trim().Split(' '); + + ConstructorInfo[] ctors = type.GetConstructors(); + + for (int i = 0; i < ctors.Length; ++i) + { + ConstructorInfo ctor = ctors[i]; + + if (Add.IsConstructible(ctor, AccessLevel.Developer)) + { + ParameterInfo[] paramList = ctor.GetParameters(); + + if (paramargs.Length == paramList.Length) + { + object[] paramValues = Add.ParseValues(paramList, paramargs); + + if (paramValues != null) + { + o = ctor.Invoke(paramValues); + for (int j = 0; j < realProps.Length; j++) + if (realProps[j] != null) + { + object toSet = null; + string result = Properties.ConstructFromString(realProps[j].PropertyType, o, + props[j, 1], ref toSet); + if (result == null) + { + realProps[j].SetValue(o, toSet, null); + } + else + { + flags = EntryFlags.InvalidProps; + + if (o is ISpawnable spawnable) + spawnable.Delete(); + + return false; + } + } + + break; + } + } + } + } + + if (o is Mobile m) + { + Spawned.Add(m, entry); + entry.Spawned.Add(m); + + Point3D loc = m is BaseVendor ? Location : GetSpawnPosition(m, map); + + m.OnBeforeSpawn(loc, map); + InvalidateProperties(); + + m.MoveToWorld(loc, map); + + if (m is BaseCreature c) + { + int walkrange = GetWalkingRange(); + + if (walkrange >= 0) + c.RangeHome = walkrange; + else + c.RangeHome = m_HomeRange; + + c.CurrentWayPoint = GetWayPoint(); + + if (m_Team > 0) + c.Team = m_Team; + + c.Home = Location; + c.HomeMap = Map; + } + + m.Spawner = this; + m.OnAfterSpawn(); + } + else if (o is Item item) + { + Spawned.Add(item, entry); + entry.Spawned.Add(item); + + Point3D loc = GetSpawnPosition(item, map); + + item.OnBeforeSpawn(loc, map); + + item.MoveToWorld(loc, map); + + item.Spawner = this; + item.OnAfterSpawn(); + } + else + { + flags = EntryFlags.InvalidType | EntryFlags.InvalidParams; + return false; + } + } + catch (Exception e) + { + Console.WriteLine("EXCEPTION CAUGHT: {0:X}", Serial); + Console.WriteLine(e); + return false; + } + + InvalidateProperties(); + return true; + } + + flags = EntryFlags.InvalidType; + return false; + } + + public virtual int GetWalkingRange() + { + return m_WalkingRange; + } + + public virtual WayPoint GetWayPoint() + { + return WayPoint; + } + + public virtual Point3D GetSpawnPosition(ISpawnable spawned, Map map) + { + if (map == null || map == Map.Internal) + return Location; + + bool waterMob, waterOnlyMob; + + if (spawned is Mobile mob) + { + waterMob = mob.CanSwim; + waterOnlyMob = mob.CanSwim && mob.CantWalk; + } + else + { + waterMob = false; + waterOnlyMob = false; + } + + // Try 10 times to find a Spawnable location. + for (int i = 0; i < 10; i++) + { + int x = Location.X + (Utility.Random(m_HomeRange * 2 + 1) - m_HomeRange); + int y = Location.Y + (Utility.Random(m_HomeRange * 2 + 1) - m_HomeRange); + int z = Map.GetAverageZ(x, y); + + int mapZ = map.GetAverageZ(x, y); + + if (waterMob) + { + if (IsValidWater(map, x, y, Z)) + return new Point3D(x, y, Z); + if (IsValidWater(map, x, y, mapZ)) + return new Point3D(x, y, mapZ); + } + + if (!waterOnlyMob) + { + if (map.CanSpawnMobile(x, y, Z)) + return new Point3D(x, y, Z); + if (map.CanSpawnMobile(x, y, mapZ)) + return new Point3D(x, y, mapZ); + } + } + + return Location; + } + + public static bool IsValidWater(Map map, int x, int y, int z) + { + if (!Region.Find(new Point3D(x, y, z), map).AllowSpawn() || !map.CanFit(x, y, z, 16, false, true, false)) + return false; + + LandTile landTile = map.Tiles.GetLandTile(x, y); + + if (landTile.Z == z && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Wet) != 0) + return true; + + StaticTile[] staticTiles = map.Tiles.GetStaticTiles(x, y, true); + + for (int i = 0; i < staticTiles.Length; ++i) + { + StaticTile staticTile = staticTiles[i]; + + if (staticTile.Z == z && + (TileData.ItemTable[staticTile.ID & TileData.MaxItemValue].Flags & TileFlag.Wet) != 0) + return true; + } + + return false; + } + + public virtual Map GetSpawnMap() + { + return Map; + } + + public void DoTimer() + { + if (!m_Running) + return; + + int minSeconds = (int)m_MinDelay.TotalSeconds; + int maxSeconds = (int)m_MaxDelay.TotalSeconds; + + TimeSpan delay = TimeSpan.FromSeconds(Utility.RandomMinMax(minSeconds, maxSeconds)); + DoTimer(delay); + } + + public virtual void DoTimer(TimeSpan delay) + { + if (!m_Running) + return; + + End = DateTime.UtcNow + delay; + + m_Timer?.Stop(); + + m_Timer = new InternalTimer(this, delay); + if (!IsFull) + m_Timer.Start(); + } + + public int CountSpawns(SpawnerEntry entry) + { + Defrag(); + + return entry.Spawned.Count; + } + + public void RemoveEntry(SpawnerEntry entry) + { + Defrag(); + + for (int i = entry.Spawned.Count - 1; i >= 0; i--) + { + ISpawnable e = entry.Spawned[i]; + entry.Spawned.RemoveAt(i); + e?.Delete(); + } - Entries.Remove( entry ); + Entries.Remove(entry); - if ( m_Running && !IsFull && m_Timer != null && !m_Timer.Running ) - DoTimer(); + if (m_Running && !IsFull && m_Timer != null && !m_Timer.Running) + DoTimer(); - InvalidateProperties(); - } + InvalidateProperties(); + } - public void Remove( ISpawnable spawn ) - { - Defrag(); + public void RemoveSpawn(int index) //Entry + { + if (index >= 0 && index < Entries.Count) + RemoveSpawn(Entries[index]); + } - if ( spawn != null ) - { - Spawned.TryGetValue( spawn, out SpawnerEntry entry ); + public void RemoveSpawn(SpawnerEntry entry) + { + for (int i = entry.Spawned.Count - 1; i >= 0; i--) + { + ISpawnable e = entry.Spawned[i]; - entry?.Spawned.Remove( spawn ); + if (e != null) + { + entry.Spawned.RemoveAt(i); + Spawned.Remove(e); - Spawned.Remove( spawn ); - } + e.Delete(); + } + } + } - if ( m_Running && !IsFull && m_Timer != null && !m_Timer.Running ) - DoTimer(); - } + public void RemoveSpawns() + { + Defrag(); - public void RemoveSpawn( int index ) //Entry - { - if ( index >= 0 && index < Entries.Count ) - RemoveSpawn( Entries[index] ); - } + for (int i = 0; i < Entries.Count; i++) + { + SpawnerEntry entry = Entries[i]; - public void RemoveSpawn( SpawnerEntry entry ) - { - for ( int i = entry.Spawned.Count-1; i >= 0; i-- ) - { - ISpawnable e = entry.Spawned[i]; + for (int j = entry.Spawned.Count - 1; j >= 0; j--) + { + ISpawnable e = entry.Spawned[j]; - if ( e != null ) - { - entry.Spawned.RemoveAt( i ); - Spawned.Remove( e ); + if (e != null) + { + Spawned.Remove(e); + entry.Spawned.RemoveAt(j); + e.Delete(); + } + } + } - e.Delete(); - } - } - } + if (m_Running && !IsFull && m_Timer != null && !m_Timer.Running) + DoTimer(); - public void RemoveSpawns() - { - Defrag(); + InvalidateProperties(); + } - for ( int i = 0;i < Entries.Count; i++ ) - { - SpawnerEntry entry = Entries[i]; + public void BringToHome() + { + Defrag(); - for ( int j = entry.Spawned.Count - 1; j >= 0; j-- ) - { - ISpawnable e = entry.Spawned[j]; + foreach (ISpawnable e in Spawned.Keys) e?.MoveToWorld(Location, Map); + } - if ( e != null ) - { - Spawned.Remove( e ); - entry.Spawned.RemoveAt( j ); - e.Delete(); - } - } - } + public override void OnDelete() + { + base.OnDelete(); - if ( m_Running && !IsFull && m_Timer != null && !m_Timer.Running ) - DoTimer(); + Stop(); + RemoveSpawns(); + } - InvalidateProperties(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void BringToHome() - { - Defrag(); + writer.Write(7); // version + + writer.Write(Entries.Count); + + for (int i = 0; i < Entries.Count; ++i) + Entries[i].Serialize(writer); + + writer.Write(m_WalkingRange); - foreach( ISpawnable e in Spawned.Keys ) - { - e?.MoveToWorld( Location, Map ); - } - } + writer.Write(WayPoint); - public override void OnDelete() - { - base.OnDelete(); + writer.Write(m_Group); - Stop(); - RemoveSpawns(); - } + writer.Write(m_MinDelay); + writer.Write(m_MaxDelay); + writer.Write(m_Count); + writer.Write(m_Team); + writer.Write(m_HomeRange); + writer.Write(m_Running); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (m_Running) + writer.WriteDeltaTime(End); + } - writer.Write( (int) 7 ); // version + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( Entries.Count ); + int version = reader.ReadInt(); + + Spawned = new Dictionary(); - for ( int i = 0; i < Entries.Count; ++i ) - Entries[i].Serialize( writer ); - - writer.Write( m_WalkingRange ); + if (version < 7) + Entries = new List(); - writer.Write( WayPoint ); + switch (version) + { + case 7: + { + int size = reader.ReadInt(); - writer.Write( m_Group ); + Entries = new List(size); - writer.Write( m_MinDelay ); - writer.Write( m_MaxDelay ); - writer.Write( m_Count ); - writer.Write( m_Team ); - writer.Write( m_HomeRange ); - writer.Write( m_Running ); + for (int i = 0; i < size; ++i) + Entries.Add(new SpawnerEntry(this, reader)); - if ( m_Running ) - writer.WriteDeltaTime( End ); - } + goto case 4; //Skip the other crap + } + case 6: + { + int size = reader.ReadInt(); - private static WarnTimer m_WarnTimer; - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Spawned = new Dictionary(); + bool addentries = Entries.Count == 0; - if ( version < 7 ) - Entries = new List(); + for (int i = 0; i < size; ++i) + if (addentries) + Entries.Add(new SpawnerEntry(string.Empty, 100, reader.ReadInt())); + else + Entries[i].SpawnedMaxCount = reader.ReadInt(); - switch ( version ) - { - case 7: - { - int size = reader.ReadInt(); + goto case 5; + } + case 5: + { + int size = reader.ReadInt(); - Entries = new List( size ); + bool addentries = Entries.Count == 0; - for ( int i = 0; i < size; ++i ) - Entries.Add( new SpawnerEntry( this, reader ) ); + for (int i = 0; i < size; ++i) + if (addentries) + Entries.Add(new SpawnerEntry(string.Empty, reader.ReadInt(), 1)); + else + Entries[i].SpawnedProbability = reader.ReadInt(); - goto case 4; //Skip the other crap - } - case 6: - { - int size = reader.ReadInt(); - - bool addentries = Entries.Count == 0; - - for ( int i = 0; i < size; ++i ) - if ( addentries ) - Entries.Add( new SpawnerEntry( string.Empty, 100, reader.ReadInt() ) ); - else - Entries[i].SpawnedMaxCount = reader.ReadInt(); - - goto case 5; - } - case 5: - { - int size = reader.ReadInt(); - - bool addentries = Entries.Count == 0; - - for ( int i = 0; i < size; ++i ) - if ( addentries ) - Entries.Add( new SpawnerEntry( string.Empty, reader.ReadInt(), 1 ) ); - else - Entries[i].SpawnedProbability = reader.ReadInt(); - - goto case 4; - } - case 4: - { - m_WalkingRange = reader.ReadInt(); - - goto case 3; - } - case 3: - case 2: - { - WayPoint = reader.ReadItem() as WayPoint; - - goto case 1; - } - - case 1: - { - m_Group = reader.ReadBool(); - - goto case 0; - } - - case 0: - { - m_MinDelay = reader.ReadTimeSpan(); - m_MaxDelay = reader.ReadTimeSpan(); - m_Count = reader.ReadInt(); - m_Team = reader.ReadInt(); - m_HomeRange = reader.ReadInt(); - m_Running = reader.ReadBool(); - - TimeSpan ts = TimeSpan.Zero; - - if ( m_Running ) - ts = reader.ReadDeltaTime() - DateTime.UtcNow; - - if ( version < 7 ) - { - int size = reader.ReadInt(); - - bool addentries = Entries.Count == 0; - - for ( int i = 0; i < size; ++i ) - { - string typeName = reader.ReadString(); - - if ( addentries ) - Entries.Add( new SpawnerEntry( typeName, 100, 1 ) ); - else - Entries[i].SpawnedName = typeName; - - if ( SpawnerType.GetType( typeName ) == null ) - { - if ( m_WarnTimer == null ) - m_WarnTimer = new WarnTimer(); - - m_WarnTimer.Add( Location, Map, typeName ); - } - } - - int count = reader.ReadInt(); - - for ( int i = 0; i < count; ++i ) - { - if ( reader.ReadEntity() is ISpawnable e ) - { - if ( e is BaseCreature creature ) - creature.RemoveIfUntamed = true; - - e.Spawner = this; - - for ( int j = 0;j < Entries.Count; j++ ) - { - if ( SpawnerType.GetType( Entries[j].SpawnedName ) == e.GetType() ) - { - Entries[j].Spawned.Add( e ); - Spawned.Add( e, Entries[j] ); - break; - } - } - } - } - } - - DoTimer( ts ); - - break; - } - } - - if ( version < 4 ) - m_WalkingRange = m_HomeRange; - } - - public static string ConvertTypes( string type ) - { - type = type.ToLower(); - switch ( type ) - { - case "wheat": return "WheatSheaf"; - case "noxxiousmage": return "NoxiousMage"; - case "noxxiousarcher": return "NoxiousArcher"; - case "noxxiouswarrior": return "NoxiousWarrior"; - case "noxxiouswarlord": return "NoxiousWarlord"; - case "obsidian": return "obsidianstatue"; - case "adeepwaterelemental": return "deepwaterelemental"; - case "noxskeleton": return "poisonskeleton"; - case "earthcaller": return "earthsummoner"; - case "bonedemon": return "bonedaemon"; - } - - return type; - } - - private class WarnTimer : Timer - { - private List m_List; - - private class WarnEntry - { - public Point3D m_Point; - public Map m_Map; - public string m_Name; - - public WarnEntry( Point3D p, Map map, string name ) - { - m_Point = p; - m_Map = map; - m_Name = name; - } - } - - public WarnTimer() : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_List = new List(); - Start(); - } - - public void Add( Point3D p, Map map, string name ) - { - m_List.Add( new WarnEntry( p, map, name ) ); - } - - protected override void OnTick() - { - try - { - Console.WriteLine( "Warning: {0} bad spawns detected, logged: 'badspawn.log'", m_List.Count ); - - using ( StreamWriter op = new StreamWriter( "badspawn.log", true ) ) - { - op.WriteLine( "# Bad spawns : {0}", DateTime.Now ); - op.WriteLine( "# Format: X Y Z F Name" ); - op.WriteLine(); - - foreach ( WarnEntry e in m_List ) - op.WriteLine( "{0}\t{1}\t{2}\t{3}\t{4}", e.m_Point.X, e.m_Point.Y, e.m_Point.Z, e.m_Map, e.m_Name ); - - op.WriteLine(); - op.WriteLine(); - } - } - catch - { - } - } - } - } - - [Flags] - public enum EntryFlags - { - None = 0x000, - InvalidType = 0x001, - InvalidParams = 0x002, - InvalidProps = 0x004, - InvalidEntry = 0x008 - } - - public class SpawnerEntry - { - public int SpawnedProbability { get; set; } - - public int SpawnedMaxCount { get; set; } - - public string SpawnedName { get; set; } - - public string Properties { get; set; } - - public string Parameters { get; set; } - - public EntryFlags Valid { get; set; } - - public List Spawned { get; } - - public bool IsFull => Spawned.Count >= SpawnedMaxCount; - - public SpawnerEntry( string name, int probability, int maxcount ) - { - SpawnedName = name; - SpawnedProbability = probability; - SpawnedMaxCount = maxcount; - Spawned = new List(); - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version - - writer.Write( SpawnedName ); - writer.Write( SpawnedProbability ); - writer.Write( SpawnedMaxCount ); - - writer.Write( Properties ); - writer.Write( Parameters ); - - writer.Write( Spawned.Count ); - - for ( int i = 0; i < Spawned.Count; ++i ) - { - object o = Spawned[i]; - - if ( o is Item item ) - writer.Write( item ); - else if ( o is Mobile mobile ) - writer.Write( mobile ); - else - writer.Write( Serial.MinusOne ); - } - } - - public SpawnerEntry( Spawner parent, GenericReader reader ) - { - int version = reader.ReadInt(); - - SpawnedName = reader.ReadString(); - SpawnedProbability = reader.ReadInt(); - SpawnedMaxCount = reader.ReadInt(); - - Properties = reader.ReadString(); - Parameters = reader.ReadString(); - - int count = reader.ReadInt(); - - Spawned = new List( count ); - - for ( int i = 0; i < count; ++i ) - { - //IEntity e = World.FindEntity( reader.ReadInt() ); - - if ( reader.ReadEntity() is ISpawnable e ) - { - e.Spawner = parent; - - if ( e is BaseCreature creature ) - creature.RemoveIfUntamed = true; - - Spawned.Add( e ); - - if ( !parent.Spawned.ContainsKey( e ) ) - parent.Spawned.Add( e, this ); - } - } - } - - public void Defrag( Spawner parent ) - { - for ( int i = 0; i < Spawned.Count; ++i ) - { - ISpawnable e = Spawned[i]; - bool remove = false; - - if ( e is Item item ) - { - if ( item.Deleted || item.RootParent is Mobile || item.IsLockedDown || item.IsSecure || item.Spawner == null ) - remove = true; - } - else if ( e is Mobile m ) - { - if ( m.Deleted ) - remove = true; - else if ( m is BaseCreature c ) - { - if ( c.Controlled || c.IsStabled ) - remove = true; + goto case 4; + } + case 4: + { + m_WalkingRange = reader.ReadInt(); + + goto case 3; + } + case 3: + case 2: + { + WayPoint = reader.ReadItem() as WayPoint; + + goto case 1; + } + + case 1: + { + m_Group = reader.ReadBool(); + + goto case 0; + } + + case 0: + { + m_MinDelay = reader.ReadTimeSpan(); + m_MaxDelay = reader.ReadTimeSpan(); + m_Count = reader.ReadInt(); + m_Team = reader.ReadInt(); + m_HomeRange = reader.ReadInt(); + m_Running = reader.ReadBool(); + + TimeSpan ts = TimeSpan.Zero; + + if (m_Running) + ts = reader.ReadDeltaTime() - DateTime.UtcNow; + + if (version < 7) + { + int size = reader.ReadInt(); + + bool addentries = Entries.Count == 0; + + for (int i = 0; i < size; ++i) + { + string typeName = reader.ReadString(); + + if (addentries) + Entries.Add(new SpawnerEntry(typeName, 100, 1)); + else + Entries[i].SpawnedName = typeName; + + if (SpawnerType.GetType(typeName) == null) + { + if (m_WarnTimer == null) + m_WarnTimer = new WarnTimer(); + + m_WarnTimer.Add(Location, Map, typeName); + } + } + + int count = reader.ReadInt(); + + for (int i = 0; i < count; ++i) + if (reader.ReadEntity() is ISpawnable e) + { + if (e is BaseCreature creature) + creature.RemoveIfUntamed = true; + + e.Spawner = this; + + for (int j = 0; j < Entries.Count; j++) + if (SpawnerType.GetType(Entries[j].SpawnedName) == e.GetType()) + { + Entries[j].Spawned.Add(e); + Spawned.Add(e, Entries[j]); + break; + } + } + } + + DoTimer(ts); + + break; + } + } + + if (version < 4) + m_WalkingRange = m_HomeRange; + } + + public static string ConvertTypes(string type) + { + type = type.ToLower(); + switch (type) + { + case "wheat": return "WheatSheaf"; + case "noxxiousmage": return "NoxiousMage"; + case "noxxiousarcher": return "NoxiousArcher"; + case "noxxiouswarrior": return "NoxiousWarrior"; + case "noxxiouswarlord": return "NoxiousWarlord"; + case "obsidian": return "obsidianstatue"; + case "adeepwaterelemental": return "deepwaterelemental"; + case "noxskeleton": return "poisonskeleton"; + case "earthcaller": return "earthsummoner"; + case "bonedemon": return "bonedaemon"; + } + + return type; + } + + private class InternalTimer : Timer + { + private Spawner m_Spawner; + + public InternalTimer(Spawner spawner, TimeSpan delay) : base(delay) + { + if (spawner.IsFull) + Priority = TimerPriority.FiveSeconds; + else + Priority = TimerPriority.OneSecond; + + m_Spawner = spawner; + } + + protected override void OnTick() + { + if (m_Spawner != null) + if (!m_Spawner.Deleted) + m_Spawner.OnTick(); + } + } + + private class WarnTimer : Timer + { + private List m_List; + + public WarnTimer() : base(TimeSpan.FromSeconds(1.0)) + { + m_List = new List(); + Start(); + } + + public void Add(Point3D p, Map map, string name) + { + m_List.Add(new WarnEntry(p, map, name)); + } + + protected override void OnTick() + { + try + { + Console.WriteLine("Warning: {0} bad spawns detected, logged: 'badspawn.log'", m_List.Count); + + using (StreamWriter op = new StreamWriter("badspawn.log", true)) + { + op.WriteLine("# Bad spawns : {0}", DateTime.Now); + op.WriteLine("# Format: X Y Z F Name"); + op.WriteLine(); + + foreach (WarnEntry e in m_List) + op.WriteLine("{0}\t{1}\t{2}\t{3}\t{4}", e.m_Point.X, e.m_Point.Y, e.m_Point.Z, e.m_Map, + e.m_Name); + + op.WriteLine(); + op.WriteLine(); + } + } + catch + { + } + } + + private class WarnEntry + { + public Map m_Map; + public string m_Name; + public Point3D m_Point; + + public WarnEntry(Point3D p, Map map, string name) + { + m_Point = p; + m_Map = map; + m_Name = name; + } + } + } + } + + [Flags] + public enum EntryFlags + { + None = 0x000, + InvalidType = 0x001, + InvalidParams = 0x002, + InvalidProps = 0x004, + InvalidEntry = 0x008 + } + + public class SpawnerEntry + { + public SpawnerEntry(string name, int probability, int maxcount) + { + SpawnedName = name; + SpawnedProbability = probability; + SpawnedMaxCount = maxcount; + Spawned = new List(); + } + + public SpawnerEntry(Spawner parent, GenericReader reader) + { + int version = reader.ReadInt(); + + SpawnedName = reader.ReadString(); + SpawnedProbability = reader.ReadInt(); + SpawnedMaxCount = reader.ReadInt(); + + Properties = reader.ReadString(); + Parameters = reader.ReadString(); + + int count = reader.ReadInt(); + + Spawned = new List(count); + + for (int i = 0; i < count; ++i) + //IEntity e = World.FindEntity( reader.ReadInt() ); + + if (reader.ReadEntity() is ISpawnable e) + { + e.Spawner = parent; + + if (e is BaseCreature creature) + creature.RemoveIfUntamed = true; + + Spawned.Add(e); + + if (!parent.Spawned.ContainsKey(e)) + parent.Spawned.Add(e, this); + } + } + + public int SpawnedProbability{ get; set; } + + public int SpawnedMaxCount{ get; set; } + + public string SpawnedName{ get; set; } + + public string Properties{ get; set; } + + public string Parameters{ get; set; } + + public EntryFlags Valid{ get; set; } + + public List Spawned{ get; } + + public bool IsFull => Spawned.Count >= SpawnedMaxCount; + + public void Serialize(GenericWriter writer) + { + writer.Write(0); // version + + writer.Write(SpawnedName); + writer.Write(SpawnedProbability); + writer.Write(SpawnedMaxCount); + + writer.Write(Properties); + writer.Write(Parameters); + + writer.Write(Spawned.Count); + + for (int i = 0; i < Spawned.Count; ++i) + { + object o = Spawned[i]; + + if (o is Item item) + writer.Write(item); + else if (o is Mobile mobile) + writer.Write(mobile); + else + writer.Write(Serial.MinusOne); + } + } + + public void Defrag(Spawner parent) + { + for (int i = 0; i < Spawned.Count; ++i) + { + ISpawnable e = Spawned[i]; + bool remove = false; + + if (e is Item item) + { + if (item.Deleted || item.RootParent is Mobile || item.IsLockedDown || item.IsSecure || + item.Spawner == null) + remove = true; + } + else if (e is Mobile m) + { + if (m.Deleted) + { + remove = true; + } + else if (m is BaseCreature c) + { + if (c.Controlled || c.IsStabled) + remove = true; /* else if ( c.Combatant == null && ( c.GetDistanceToSqrt( Location ) > (c.RangeHome * 4) ) ) { @@ -1168,20 +1206,24 @@ namespace Server.Mobiles remove = true; } */ - } - else if ( m.Spawner == null ) - remove = true; - } - else - remove = true; + } + else if (m.Spawner == null) + { + remove = true; + } + } + else + { + remove = true; + } - if ( remove ) - { - Spawned.RemoveAt( i-- ); - if ( parent.Spawned.ContainsKey( e ) ) - parent.Spawned.Remove( e ); - } - } - } - } -} + if (remove) + { + Spawned.RemoveAt(i--); + if (parent.Spawned.ContainsKey(e)) + parent.Spawned.Remove(e); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Spawner/SpawnerGump.cs b/Scripts/Engines/Spawner/SpawnerGump.cs index 19408d97b..6957171e8 100644 --- a/Scripts/Engines/Spawner/SpawnerGump.cs +++ b/Scripts/Engines/Spawner/SpawnerGump.cs @@ -1,303 +1,318 @@ using System; using System.Collections.Generic; -using Server.Network; using Server.Gumps; +using Server.Network; namespace Server.Mobiles { - public class SpawnerGump : Gump - { - private Spawner m_Spawner; - private int m_Page; - private SpawnerEntry m_Entry; + public class SpawnerGump : Gump + { + private SpawnerEntry m_Entry; + private int m_Page; + private Spawner m_Spawner; - public SpawnerGump( Spawner spawner ) : this( spawner, 0 ) - { - } + public SpawnerGump(Spawner spawner) : this(spawner, 0) + { + } - public SpawnerGump( Spawner spawner, int page ) : this( spawner, null, page ) - { - } + public SpawnerGump(Spawner spawner, int page) : this(spawner, null, page) + { + } - public SpawnerGump( Spawner spawner, SpawnerEntry focusentry, int page ) : base( 50, 50 ) - { - m_Spawner = spawner; - m_Entry = focusentry; - m_Page = page; + public SpawnerGump(Spawner spawner, SpawnerEntry focusentry, int page) : base(50, 50) + { + m_Spawner = spawner; + m_Entry = focusentry; + m_Page = page; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 343, 371 + ( m_Entry != null ? 44 : 0 ), 5054 ); + AddBackground(0, 0, 343, 371 + (m_Entry != null ? 44 : 0), 5054); - AddHtml( 95, 1, 250, 20, "Creatures List", false, false ); - AddHtml( 245, 1, 250, 20, "#", false, false ); - AddHtml( 282, 1, 250, 20, "Prb", false, false ); + AddHtml(95, 1, 250, 20, "Creatures List", false, false); + AddHtml(245, 1, 250, 20, "#", false, false); + AddHtml(282, 1, 250, 20, "Prb", false, false); - //AddLabel( 95, 1, 0, "Creatures List" ); + //AddLabel( 95, 1, 0, "Creatures List" ); - int offset = 0; + int offset = 0; - for ( int i = 0; i < 13; i++ ) - { - int textindex = i * 5; - int entryindex = ( m_Page * 13 ) + i; + for (int i = 0; i < 13; i++) + { + int textindex = i * 5; + int entryindex = m_Page * 13 + i; - SpawnerEntry entry = null; + SpawnerEntry entry = null; - if ( entryindex < spawner.Entries.Count ) - entry = m_Spawner.Entries[entryindex]; + if (entryindex < spawner.Entries.Count) + entry = m_Spawner.Entries[entryindex]; - if ( entry == null || m_Entry != entry ) - AddButton( 5, ( 22 * i ) + 21 + offset, entry != null ? 0xFBA : 0xFA5, entry != null ? 0xFBC : 0xFA7, GetButtonID( 2, (i * 2) ), GumpButtonType.Reply, 0 ); //Expand - else - AddButton( 5, ( 22 * i ) + 21 + offset, entry != null ? 0xFBB : 0xFA5, entry != null ? 0xFBC : 0xFA7, GetButtonID( 2, (i * 2) ), GumpButtonType.Reply, 0 ); //Unexpand + if (entry == null || m_Entry != entry) + AddButton(5, 22 * i + 21 + offset, entry != null ? 0xFBA : 0xFA5, entry != null ? 0xFBC : 0xFA7, + GetButtonID(2, i * 2), GumpButtonType.Reply, 0); //Expand + else + AddButton(5, 22 * i + 21 + offset, entry != null ? 0xFBB : 0xFA5, entry != null ? 0xFBC : 0xFA7, + GetButtonID(2, i * 2), GumpButtonType.Reply, 0); //Unexpand - AddButton( 38, ( 22 * i ) + 21 + offset, 0xFA2, 0xFA4, GetButtonID( 2, 1 + (i * 2) ), GumpButtonType.Reply, 0 ); //Delete + AddButton(38, 22 * i + 21 + offset, 0xFA2, 0xFA4, GetButtonID(2, 1 + i * 2), GumpButtonType.Reply, + 0); //Delete - AddImageTiled( 71, (22 * i) + 20 + offset, 161, 23, 0xA40 ); //creature text box - AddImageTiled( 72, (22 * i) + 21 + offset, 159, 21, 0xBBC ); //creature text box + AddImageTiled(71, 22 * i + 20 + offset, 161, 23, 0xA40); //creature text box + AddImageTiled(72, 22 * i + 21 + offset, 159, 21, 0xBBC); //creature text box - AddImageTiled( 235, (22 * i) + 20 + offset, 35, 23, 0xA40 ); //maxcount text box - AddImageTiled( 236, (22 * i) + 21 + offset, 33, 21, 0xBBC ); //maxcount text box + AddImageTiled(235, 22 * i + 20 + offset, 35, 23, 0xA40); //maxcount text box + AddImageTiled(236, 22 * i + 21 + offset, 33, 21, 0xBBC); //maxcount text box - AddImageTiled( 273, (22 * i) + 20 + offset, 35, 23, 0xA40 ); //probability text box - AddImageTiled( 274, (22 * i) + 21 + offset, 33, 21, 0xBBC ); //probability text box + AddImageTiled(273, 22 * i + 20 + offset, 35, 23, 0xA40); //probability text box + AddImageTiled(274, 22 * i + 21 + offset, 33, 21, 0xBBC); //probability text box - string name = ""; - string probability = ""; - string maxcount = ""; - EntryFlags flags = EntryFlags.None; + string name = ""; + string probability = ""; + string maxcount = ""; + EntryFlags flags = EntryFlags.None; - if ( entry != null ) - { - name = (string)entry.SpawnedName; - probability = entry.SpawnedProbability.ToString(); - maxcount = entry.SpawnedMaxCount.ToString(); - flags = entry.Valid; + if (entry != null) + { + name = entry.SpawnedName; + probability = entry.SpawnedProbability.ToString(); + maxcount = entry.SpawnedMaxCount.ToString(); + flags = entry.Valid; - AddLabel( 315, (22 * i) + 20 + offset, 0, spawner.CountSpawns( entry ).ToString() ); - } + AddLabel(315, 22 * i + 20 + offset, 0, spawner.CountSpawns(entry).ToString()); + } - AddTextEntry( 75, (22 * i) + 21 + offset, 156, 21, ( ( flags & EntryFlags.InvalidType ) != 0 ) ? 33 : 0, textindex, name ); //creature - AddTextEntry( 239, (22 * i) + 21 + offset, 30, 21, 0, textindex + 1, maxcount); //max count - AddTextEntry( 277, (22 * i) + 21 + offset, 30, 21, 0, textindex + 2, probability); //probability + AddTextEntry(75, 22 * i + 21 + offset, 156, 21, (flags & EntryFlags.InvalidType) != 0 ? 33 : 0, textindex, + name); //creature + AddTextEntry(239, 22 * i + 21 + offset, 30, 21, 0, textindex + 1, maxcount); //max count + AddTextEntry(277, 22 * i + 21 + offset, 30, 21, 0, textindex + 2, probability); //probability - if ( entry != null && m_Entry == entry ) - { - AddLabel( 5, (22 * i) + 42, 0x384, "Params" ); - AddImageTiled( 55, (22 * i) + 42, 253, 23, 0xA40 ); //Parameters - AddImageTiled( 56, (22 * i) + 43, 251, 21, 0xBBC ); //Parameters + if (entry != null && m_Entry == entry) + { + AddLabel(5, 22 * i + 42, 0x384, "Params"); + AddImageTiled(55, 22 * i + 42, 253, 23, 0xA40); //Parameters + AddImageTiled(56, 22 * i + 43, 251, 21, 0xBBC); //Parameters - AddLabel( 5, (22 * i) + 64, 0x384, "Props" ); - AddImageTiled( 55, (22 * i) + 64, 253, 23, 0xA40 ); //Properties - AddImageTiled( 56, (22 * i) + 65, 251, 21, 0xBBC ); //Properties + AddLabel(5, 22 * i + 64, 0x384, "Props"); + AddImageTiled(55, 22 * i + 64, 253, 23, 0xA40); //Properties + AddImageTiled(56, 22 * i + 65, 251, 21, 0xBBC); //Properties - AddTextEntry( 59, (22 * i) + 42, 248, 21, ( ( flags & EntryFlags.InvalidParams ) != 0 ) ? 33 : 0, textindex + 3, entry.Parameters ); //parameters - AddTextEntry( 59, (22 * i) + 62, 248, 21, ( ( flags & EntryFlags.InvalidProps ) != 0 ) ? 33 : 0, textindex + 4, entry.Properties ); //properties + AddTextEntry(59, 22 * i + 42, 248, 21, (flags & EntryFlags.InvalidParams) != 0 ? 33 : 0, textindex + 3, + entry.Parameters); //parameters + AddTextEntry(59, 22 * i + 62, 248, 21, (flags & EntryFlags.InvalidProps) != 0 ? 33 : 0, textindex + 4, + entry.Properties); //properties - offset += 44; - } - } + offset += 44; + } + } - AddButton( 5, 347 + offset, 0xFB1, 0xFB3, 0, GumpButtonType.Reply, 0 ); - AddLabel( 38, 347 + offset, 0x384, "Cancel" ); + AddButton(5, 347 + offset, 0xFB1, 0xFB3, 0, GumpButtonType.Reply, 0); + AddLabel(38, 347 + offset, 0x384, "Cancel"); - AddButton( 5, 325 + offset, 0xFB7, 0xFB9, GetButtonID( 1, 2 ), GumpButtonType.Reply, 0 ); - AddLabel( 38, 325 + offset, 0x384, "Okay" ); + AddButton(5, 325 + offset, 0xFB7, 0xFB9, GetButtonID(1, 2), GumpButtonType.Reply, 0); + AddLabel(38, 325 + offset, 0x384, "Okay"); - AddButton( 110, 325 + offset, 0xFB4, 0xFB6, GetButtonID( 1, 3 ), GumpButtonType.Reply, 0 ); - AddLabel( 143, 325 + offset, 0x384, "Bring to Home" ); + AddButton(110, 325 + offset, 0xFB4, 0xFB6, GetButtonID(1, 3), GumpButtonType.Reply, 0); + AddLabel(143, 325 + offset, 0x384, "Bring to Home"); - AddButton( 110, 347 + offset, 0xFA8, 0xFAA, GetButtonID( 1, 4 ), GumpButtonType.Reply, 0 ); - AddLabel( 143, 347 + offset, 0x384, "Total Respawn" ); + AddButton(110, 347 + offset, 0xFA8, 0xFAA, GetButtonID(1, 4), GumpButtonType.Reply, 0); + AddLabel(143, 347 + offset, 0x384, "Total Respawn"); - AddButton( 253, 325 + offset, 0xFB7, 0xFB9, GetButtonID( 1, 5 ), GumpButtonType.Reply, 0 ); - AddLabel( 286, 325 + offset, 0x384, "Apply" ); + AddButton(253, 325 + offset, 0xFB7, 0xFB9, GetButtonID(1, 5), GumpButtonType.Reply, 0); + AddLabel(286, 325 + offset, 0x384, "Apply"); - if ( m_Page > 0 ) - AddButton( 276, 308 + offset, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 276, 308 + offset, 0x25EA ); + if (m_Page > 0) + AddButton(276, 308 + offset, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(276, 308 + offset, 0x25EA); - if ( (m_Page + 1) * 13 <= m_Spawner.Entries.Count ) - AddButton( 293, 308 + offset, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 293, 308 + offset, 0x25E6 ); - } + if ((m_Page + 1) * 13 <= m_Spawner.Entries.Count) + AddButton(293, 308 + offset, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(293, 308 + offset, 0x25E6); + } - public int GetButtonID( int type, int index ) - { - return 1 + (index * 10) + type; - } + public int GetButtonID(int type, int index) + { + return 1 + index * 10 + type; + } - public void CreateArray( RelayInfo info, Mobile from, Spawner spawner ) - { - int ocount = spawner.Entries.Count; + public void CreateArray(RelayInfo info, Mobile from, Spawner spawner) + { + int ocount = spawner.Entries.Count; - List rementries = new List(); + List rementries = new List(); - for ( int i = 0;i < 13; i++ ) - { - int index = i * 5; - int entryindex = ( m_Page * 13 ) + i; + for (int i = 0; i < 13; i++) + { + int index = i * 5; + int entryindex = m_Page * 13 + i; - TextRelay cte = info.GetTextEntry( index ); - TextRelay mte = info.GetTextEntry( index + 1 ); - TextRelay poste = info.GetTextEntry( index + 2 ); - TextRelay parmte = info.GetTextEntry( index + 3 ); - TextRelay propte = info.GetTextEntry( index + 4 ); + TextRelay cte = info.GetTextEntry(index); + TextRelay mte = info.GetTextEntry(index + 1); + TextRelay poste = info.GetTextEntry(index + 2); + TextRelay parmte = info.GetTextEntry(index + 3); + TextRelay propte = info.GetTextEntry(index + 4); - if ( cte != null ) - { - string str = cte.Text.Trim().ToLower(); + if (cte != null) + { + string str = cte.Text.Trim().ToLower(); - if ( str.Length > 0 ) - { - Type type = SpawnerType.GetType( str ); + if (str.Length > 0) + { + Type type = SpawnerType.GetType(str); - if ( type != null ) - { - SpawnerEntry entry = null; + if (type != null) + { + SpawnerEntry entry = null; - if ( entryindex < ocount ) - { - entry = spawner.Entries[entryindex]; - entry.SpawnedName = str; + if (entryindex < ocount) + { + entry = spawner.Entries[entryindex]; + entry.SpawnedName = str; - if ( mte != null ) - entry.SpawnedMaxCount = Utility.ToInt32( mte.Text.Trim() ); + if (mte != null) + entry.SpawnedMaxCount = Utility.ToInt32(mte.Text.Trim()); - if ( poste != null ) - entry.SpawnedProbability = Utility.ToInt32( poste.Text.Trim() ); - } - else - { - int maxcount = 1; - int probcount = 100; + if (poste != null) + entry.SpawnedProbability = Utility.ToInt32(poste.Text.Trim()); + } + else + { + int maxcount = 1; + int probcount = 100; - if ( mte != null ) - maxcount = Utility.ToInt32( mte.Text.Trim() ); + if (mte != null) + maxcount = Utility.ToInt32(mte.Text.Trim()); - if ( poste != null ) - probcount = Utility.ToInt32( poste.Text.Trim() ); + if (poste != null) + probcount = Utility.ToInt32(poste.Text.Trim()); - entry = spawner.AddEntry( str, probcount, maxcount ); - } + entry = spawner.AddEntry(str, probcount, maxcount); + } - if ( parmte != null ) - entry.Parameters = parmte.Text.Trim(); + if (parmte != null) + entry.Parameters = parmte.Text.Trim(); - if ( propte != null ) - entry.Properties = propte.Text.Trim(); - } - else - from.SendMessage( "{0} is not a valid type name for entry #{1}.", str, i ); - } - else if ( entryindex < ocount && spawner.Entries[entryindex] != null ) - rementries.Add( spawner.Entries[entryindex] ); - } - } + if (propte != null) + entry.Properties = propte.Text.Trim(); + } + else + { + from.SendMessage("{0} is not a valid type name for entry #{1}.", str, i); + } + } + else if (entryindex < ocount && spawner.Entries[entryindex] != null) + { + rementries.Add(spawner.Entries[entryindex]); + } + } + } - if ( rementries.Count > 0 ) - for ( int i = 0; i < rementries.Count; i++ ) - spawner.RemoveEntry( rementries[i] ); + if (rementries.Count > 0) + for (int i = 0; i < rementries.Count; i++) + spawner.RemoveEntry(rementries[i]); - if ( ocount == 0 && spawner.Entries.Count > 0 ) - spawner.Start(); - } + if (ocount == 0 && spawner.Entries.Count > 0) + spawner.Start(); + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_Spawner.Deleted ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Spawner.Deleted) + return; - Mobile from = state.Mobile; + Mobile from = state.Mobile; - int val = info.ButtonID - 1; + int val = info.ButtonID - 1; - if ( val < 0 ) - return; + if (val < 0) + return; - int type = val % 10; - int index = val / 10; + int type = val % 10; + int index = val / 10; - switch ( type ) - { - case 0: //Cancel - return; - case 1: - { - switch ( index ) - { - case 0: - { - if ( m_Spawner.Entries != null && m_Page > 0 ) - { - m_Page--; - m_Entry = null; - } - break; - } - case 1: - { - if ( m_Spawner.Entries != null && (m_Page + 1) * 13 <= m_Spawner.Entries.Count ) - { - m_Page++; - m_Entry = null; - } - break; - } - case 2: //Okay - { - CreateArray(info, state.Mobile, m_Spawner); - return; - } - case 3: - { - m_Spawner.BringToHome(); - break; - } - case 4: // Complete respawn - { - m_Spawner.Respawn(); - break; - } - case 5: - { - CreateArray(info, state.Mobile, m_Spawner); - break; - } - } - break; - } - case 2: - { - int entryindex = ( index / 2 ) + ( m_Page * 13 ); - int buttontype = index % 2; + switch (type) + { + case 0: //Cancel + return; + case 1: + { + switch (index) + { + case 0: + { + if (m_Spawner.Entries != null && m_Page > 0) + { + m_Page--; + m_Entry = null; + } - if ( entryindex >= 0 && entryindex < m_Spawner.Entries.Count ) - { - SpawnerEntry entry = m_Spawner.Entries[entryindex]; - if ( buttontype == 0 ) // Spawn creature - { - if ( m_Entry != null && m_Entry == entry ) - m_Entry = null; - else - m_Entry = entry; - } - else // Remove creatures - m_Spawner.RemoveSpawn( entryindex ); - } + break; + } + case 1: + { + if (m_Spawner.Entries != null && (m_Page + 1) * 13 <= m_Spawner.Entries.Count) + { + m_Page++; + m_Entry = null; + } - CreateArray( info, state.Mobile, m_Spawner ); - break; - } - } + break; + } + case 2: //Okay + { + CreateArray(info, state.Mobile, m_Spawner); + return; + } + case 3: + { + m_Spawner.BringToHome(); + break; + } + case 4: // Complete respawn + { + m_Spawner.Respawn(); + break; + } + case 5: + { + CreateArray(info, state.Mobile, m_Spawner); + break; + } + } - if ( m_Entry != null && m_Spawner.Entries.Contains( m_Entry ) ) - state.Mobile.SendGump( new SpawnerGump( m_Spawner, m_Entry, m_Page ) ); - else - state.Mobile.SendGump( new SpawnerGump( m_Spawner, null, m_Page ) ); - } - } -} + break; + } + case 2: + { + int entryindex = index / 2 + m_Page * 13; + int buttontype = index % 2; + + if (entryindex >= 0 && entryindex < m_Spawner.Entries.Count) + { + SpawnerEntry entry = m_Spawner.Entries[entryindex]; + if (buttontype == 0) // Spawn creature + { + if (m_Entry != null && m_Entry == entry) + m_Entry = null; + else + m_Entry = entry; + } + else // Remove creatures + { + m_Spawner.RemoveSpawn(entryindex); + } + } + + CreateArray(info, state.Mobile, m_Spawner); + break; + } + } + + if (m_Entry != null && m_Spawner.Entries.Contains(m_Entry)) + state.Mobile.SendGump(new SpawnerGump(m_Spawner, m_Entry, m_Page)); + else + state.Mobile.SendGump(new SpawnerGump(m_Spawner, null, m_Page)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Spawner/SpawnerType.cs b/Scripts/Engines/Spawner/SpawnerType.cs index 08d6e1f07..dd6582ed2 100644 --- a/Scripts/Engines/Spawner/SpawnerType.cs +++ b/Scripts/Engines/Spawner/SpawnerType.cs @@ -2,11 +2,11 @@ using System; namespace Server.Mobiles { - public class SpawnerType - { - public static Type GetType( string name ) - { - return ScriptCompiler.FindTypeByName( name ); - } - } -} + public class SpawnerType + { + public static Type GetType(string name) + { + return ScriptCompiler.FindTypeByName(name); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Treasures of Tokuno/BasePigmentsOfTokuno.cs b/Scripts/Engines/Treasures of Tokuno/BasePigmentsOfTokuno.cs index 60b5de556..2730ab765 100644 --- a/Scripts/Engines/Treasures of Tokuno/BasePigmentsOfTokuno.cs +++ b/Scripts/Engines/Treasures of Tokuno/BasePigmentsOfTokuno.cs @@ -1,257 +1,289 @@ using System; using Server.Misc; using Server.Mobiles; +using Server.Targeting; namespace Server.Items { - public abstract class BasePigmentsOfTokuno : Item, IUsesRemaining - { - private static Type[] m_Glasses = { - typeof( MaritimeGlasses ), - typeof( WizardsGlasses ), - typeof( TradeGlasses ), - typeof( LyricalGlasses ), - typeof( NecromanticGlasses ), - typeof( LightOfWayGlasses ), - typeof( FoldedSteelGlasses ), - typeof( PoisonedGlasses ), - typeof( TreasureTrinketGlasses ), - typeof( MaceShieldGlasses ), - typeof( ArtsGlasses ), - typeof( AnthropomorphistGlasses ) - }; + public abstract class BasePigmentsOfTokuno : Item, IUsesRemaining + { + private static Type[] m_Glasses = + { + typeof(MaritimeGlasses), + typeof(WizardsGlasses), + typeof(TradeGlasses), + typeof(LyricalGlasses), + typeof(NecromanticGlasses), + typeof(LightOfWayGlasses), + typeof(FoldedSteelGlasses), + typeof(PoisonedGlasses), + typeof(TreasureTrinketGlasses), + typeof(MaceShieldGlasses), + typeof(ArtsGlasses), + typeof(AnthropomorphistGlasses) + }; - private static Type[] m_Replicas = { - typeof( ANecromancerShroud ), - typeof( BraveKnightOfTheBritannia ), - typeof( CaptainJohnsHat ), - typeof( DetectiveBoots ), - typeof( DjinnisRing ), - typeof( EmbroideredOakLeafCloak ), - typeof( GuantletsOfAnger ), - typeof( LieutenantOfTheBritannianRoyalGuard ), - typeof( OblivionsNeedle ), - typeof( RoyalGuardSurvivalKnife ), - typeof( SamaritanRobe ), - typeof( TheMostKnowledgePerson ), - typeof( TheRobeOfBritanniaAri ), - typeof( AcidProofRobe ), - typeof( Calm ), - typeof( CrownOfTalKeesh ), - typeof( FangOfRactus ), - typeof( GladiatorsCollar ), - typeof( OrcChieftainHelm ), - typeof( Pacify ), - typeof( Quell ), - typeof( ShroudOfDeciet ), - typeof( Subdue ) - }; + private static Type[] m_Replicas = + { + typeof(ANecromancerShroud), + typeof(BraveKnightOfTheBritannia), + typeof(CaptainJohnsHat), + typeof(DetectiveBoots), + typeof(DjinnisRing), + typeof(EmbroideredOakLeafCloak), + typeof(GuantletsOfAnger), + typeof(LieutenantOfTheBritannianRoyalGuard), + typeof(OblivionsNeedle), + typeof(RoyalGuardSurvivalKnife), + typeof(SamaritanRobe), + typeof(TheMostKnowledgePerson), + typeof(TheRobeOfBritanniaAri), + typeof(AcidProofRobe), + typeof(Calm), + typeof(CrownOfTalKeesh), + typeof(FangOfRactus), + typeof(GladiatorsCollar), + typeof(OrcChieftainHelm), + typeof(Pacify), + typeof(Quell), + typeof(ShroudOfDeciet), + typeof(Subdue) + }; - private static Type[] m_DyableHeritageItems = { - typeof( ChargerOfTheFallen ), - typeof( SamuraiHelm ), - typeof( HolySword ), - typeof( LeggingsOfEmbers ), - typeof( ShaminoCrossbow ) - }; + private static Type[] m_DyableHeritageItems = + { + typeof(ChargerOfTheFallen), + typeof(SamuraiHelm), + typeof(HolySword), + typeof(LeggingsOfEmbers), + typeof(ShaminoCrossbow) + }; - public override int LabelNumber => 1070933; // Pigments of Tokuno + private TextDefinition m_Label; - private int m_UsesRemaining; - private TextDefinition m_Label; + private int m_UsesRemaining; - protected TextDefinition Label - { - get => m_Label; - set { m_Label = value; InvalidateProperties(); } - } + public BasePigmentsOfTokuno() : base(0xEFF) + { + Weight = 1.0; + m_UsesRemaining = 1; + } - #region Old Item Serialization Vars - /* DO NOT USE! Only used in serialization of pigments that originally derived from Item */ + public BasePigmentsOfTokuno(int uses) : base(0xEFF) + { + Weight = 1.0; + m_UsesRemaining = uses; + } - protected bool InheritsItem { get; private set; } + public BasePigmentsOfTokuno(Serial serial) : base(serial) + { + } - #endregion + public override int LabelNumber => 1070933; // Pigments of Tokuno - public BasePigmentsOfTokuno() : base( 0xEFF ) - { - Weight = 1.0; - m_UsesRemaining = 1; - } + protected TextDefinition Label + { + get => m_Label; + set + { + m_Label = value; + InvalidateProperties(); + } + } - public BasePigmentsOfTokuno( int uses ) : base( 0xEFF ) - { - Weight = 1.0; - m_UsesRemaining = uses; - } + #region Old Item Serialization Vars - public BasePigmentsOfTokuno( Serial serial ) : base( serial ) - { - } + /* DO NOT USE! Only used in serialization of pigments that originally derived from Item */ - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + protected bool InheritsItem{ get; private set; } - if ( m_Label != null && m_Label > 0 ) - TextDefinition.AddTo( list, m_Label ); + #endregion - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnDoubleClick( Mobile from ) - { - if ( IsAccessibleTo( from ) && from.InRange( GetWorldLocation(), 3 ) ) - { - from.SendLocalizedMessage( 1070929 ); // Select the artifact or enhanced magic item to dye. - from.BeginTarget( 3, false, Targeting.TargetFlags.None, new TargetStateCallback( InternalCallback ), this ); - } - else - from.SendLocalizedMessage( 502436 ); // That is not accessible. - } + if (m_Label != null && m_Label > 0) + TextDefinition.AddTo(list, m_Label); - private void InternalCallback( Mobile from, object targeted, object state ) - { - BasePigmentsOfTokuno pigment = (BasePigmentsOfTokuno)state; + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ + } - if ( pigment.Deleted || pigment.UsesRemaining <= 0 || !from.InRange( pigment.GetWorldLocation(), 3 ) || !pigment.IsAccessibleTo( from )) - return; + public override void OnDoubleClick(Mobile from) + { + if (IsAccessibleTo(from) && from.InRange(GetWorldLocation(), 3)) + { + from.SendLocalizedMessage(1070929); // Select the artifact or enhanced magic item to dye. + from.BeginTarget(3, false, TargetFlags.None, new TargetStateCallback(InternalCallback), this); + } + else + { + from.SendLocalizedMessage(502436); // That is not accessible. + } + } - if ( !(targeted is Item i) ) - from.SendLocalizedMessage( 1070931 ); // You can only dye artifacts and enhanced magic items with this tub. - else if ( !from.InRange( i.GetWorldLocation(), 3 ) || !IsAccessibleTo( from ) ) - from.SendLocalizedMessage( 502436 ); // That is not accessible. - else if ( from.Items.Contains( i ) ) - from.SendLocalizedMessage( 1070930 ); // Can't dye artifacts or enhanced magic items that are being worn. - else if ( i.IsLockedDown ) - from.SendLocalizedMessage( 1070932 ); // You may not dye artifacts and enhanced magic items which are locked down. - else if ( i.QuestItem ) - from.SendLocalizedMessage( 1151836 ); // You may not dye toggled quest items. - else if ( i is MetalPigmentsOfTokuno ) - from.SendLocalizedMessage( 1042417 ); // You cannot dye that. - else if ( i is LesserPigmentsOfTokuno ) - from.SendLocalizedMessage( 1042417 ); // You cannot dye that. - else if ( i is PigmentsOfTokuno ) - from.SendLocalizedMessage( 1042417 ); // You cannot dye that. - else if ( !IsValidItem( i ) ) - from.SendLocalizedMessage( 1070931 ); // You can only dye artifacts and enhanced magic items with this tub. //Yes, it says tub on OSI. Don't ask me why ;p - else - { - //Notes: on OSI there IS no hue check to see if it's already hued. and no messages on successful hue either - i.Hue = Hue; + private void InternalCallback(Mobile from, object targeted, object state) + { + BasePigmentsOfTokuno pigment = (BasePigmentsOfTokuno)state; - if ( --pigment.UsesRemaining <= 0 ) - pigment.Delete(); + if (pigment.Deleted || pigment.UsesRemaining <= 0 || !from.InRange(pigment.GetWorldLocation(), 3) || + !pigment.IsAccessibleTo(from)) + return; - from.PlaySound(0x23E); // As per OSI TC1 - } - } + if (!(targeted is Item i)) + { + from.SendLocalizedMessage(1070931); // You can only dye artifacts and enhanced magic items with this tub. + } + else if (!from.InRange(i.GetWorldLocation(), 3) || !IsAccessibleTo(from)) + { + from.SendLocalizedMessage(502436); // That is not accessible. + } + else if (from.Items.Contains(i)) + { + from.SendLocalizedMessage(1070930); // Can't dye artifacts or enhanced magic items that are being worn. + } + else if (i.IsLockedDown) + { + from.SendLocalizedMessage( + 1070932); // You may not dye artifacts and enhanced magic items which are locked down. + } + else if (i.QuestItem) + { + from.SendLocalizedMessage(1151836); // You may not dye toggled quest items. + } + else if (i is MetalPigmentsOfTokuno) + { + from.SendLocalizedMessage(1042417); // You cannot dye that. + } + else if (i is LesserPigmentsOfTokuno) + { + from.SendLocalizedMessage(1042417); // You cannot dye that. + } + else if (i is PigmentsOfTokuno) + { + from.SendLocalizedMessage(1042417); // You cannot dye that. + } + else if (!IsValidItem(i)) + { + from.SendLocalizedMessage( + 1070931); // You can only dye artifacts and enhanced magic items with this tub. //Yes, it says tub on OSI. Don't ask me why ;p + } + else + { + //Notes: on OSI there IS no hue check to see if it's already hued. and no messages on successful hue either + i.Hue = Hue; - public static bool IsValidItem( Item i ) - { - if ( i is BasePigmentsOfTokuno ) - return false; + if (--pigment.UsesRemaining <= 0) + pigment.Delete(); - Type t = i.GetType(); + from.PlaySound(0x23E); // As per OSI TC1 + } + } - CraftResource resource = CraftResource.None; + public static bool IsValidItem(Item i) + { + if (i is BasePigmentsOfTokuno) + return false; - if ( i is BaseWeapon weapon ) - resource = weapon.Resource; - else if ( i is BaseArmor armor ) - resource = armor.Resource; - else if (i is BaseClothing clothing) - resource = clothing.Resource; + Type t = i.GetType(); - if ( !CraftResources.IsStandard( resource ) ) - return true; + CraftResource resource = CraftResource.None; - if ( i is ITokunoDyable ) - return true; + if (i is BaseWeapon weapon) + resource = weapon.Resource; + else if (i is BaseArmor armor) + resource = armor.Resource; + else if (i is BaseClothing clothing) + resource = clothing.Resource; - return( - IsInTypeList( t, TreasuresOfTokuno.LesserArtifactsTotal ) - || IsInTypeList( t, TreasuresOfTokuno.GreaterArtifacts ) - || IsInTypeList( t, DemonKnight.ArtifactRarity10 ) - || IsInTypeList( t, DemonKnight.ArtifactRarity11 ) - || IsInTypeList( t, MondainsLegacy.Artifacts ) - || IsInTypeList( t, StealableArtifactsSpawner.TypesOfEntires ) - || IsInTypeList( t, Paragon.Artifacts ) - || IsInTypeList( t, Leviathan.Artifacts ) - || IsInTypeList( t, TreasureMapChest.Artifacts ) - || IsInTypeList( t, m_Replicas ) - || IsInTypeList( t, m_DyableHeritageItems ) - || IsInTypeList( t, m_Glasses ) - ); - } + if (!CraftResources.IsStandard(resource)) + return true; - private static bool IsInTypeList( Type t, Type[] list ) - { - for( int i = 0; i < list.Length; i++ ) - { - if ( list[i] == t ) return true; - } + if (i is ITokunoDyable) + return true; - return false; - } + return IsInTypeList(t, TreasuresOfTokuno.LesserArtifactsTotal) + || IsInTypeList(t, TreasuresOfTokuno.GreaterArtifacts) + || IsInTypeList(t, DemonKnight.ArtifactRarity10) + || IsInTypeList(t, DemonKnight.ArtifactRarity11) + || IsInTypeList(t, MondainsLegacy.Artifacts) + || IsInTypeList(t, StealableArtifactsSpawner.TypesOfEntires) + || IsInTypeList(t, Paragon.Artifacts) + || IsInTypeList(t, Leviathan.Artifacts) + || IsInTypeList(t, TreasureMapChest.Artifacts) + || IsInTypeList(t, m_Replicas) + || IsInTypeList(t, m_DyableHeritageItems) + || IsInTypeList(t, m_Glasses); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private static bool IsInTypeList(Type t, Type[] list) + { + for (int i = 0; i < list.Length; i++) + if (list[i] == t) + return true; - writer.Write( (int)1 ); + return false; + } - writer.WriteEncodedInt( m_UsesRemaining ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(1); - int version = reader.ReadInt(); + writer.WriteEncodedInt(m_UsesRemaining); + } - switch ( version ) - { - case 1: - { - m_UsesRemaining = reader.ReadEncodedInt(); - break; - } - case 0: // Old pigments that inherited from item - { - InheritsItem = true; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( this is LesserPigmentsOfTokuno ) - ((LesserPigmentsOfTokuno)this).Type = (LesserPigmentType)reader.ReadEncodedInt(); - else if ( this is PigmentsOfTokuno ) - ((PigmentsOfTokuno)this).Type = (PigmentType)reader.ReadEncodedInt(); - else if ( this is MetalPigmentsOfTokuno ) - reader.ReadEncodedInt(); + int version = reader.ReadInt(); - m_UsesRemaining = reader.ReadEncodedInt(); + switch (version) + { + case 1: + { + m_UsesRemaining = reader.ReadEncodedInt(); + break; + } + case 0: // Old pigments that inherited from item + { + InheritsItem = true; - break; - } - } + if (this is LesserPigmentsOfTokuno) + ((LesserPigmentsOfTokuno)this).Type = (LesserPigmentType)reader.ReadEncodedInt(); + else if (this is PigmentsOfTokuno) + ((PigmentsOfTokuno)this).Type = (PigmentType)reader.ReadEncodedInt(); + else if (this is MetalPigmentsOfTokuno) + reader.ReadEncodedInt(); + m_UsesRemaining = reader.ReadEncodedInt(); - } + break; + } + } + } - #region IUsesRemaining Members + #region IUsesRemaining Members - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public bool ShowUsesRemaining - { - get => true; - set {} - } + public bool ShowUsesRemaining + { + get => true; + set { } + } - #endregion - } -} + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Engines/Treasures of Tokuno/GreaterArtifacts.cs b/Scripts/Engines/Treasures of Tokuno/GreaterArtifacts.cs index 9d70a1b3c..37e5fb6b5 100644 --- a/Scripts/Engines/Treasures of Tokuno/GreaterArtifacts.cs +++ b/Scripts/Engines/Treasures of Tokuno/GreaterArtifacts.cs @@ -1,500 +1,562 @@ namespace Server.Items { - public class DarkenedSky : Kama - { - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - public override int LabelNumber => 1070966; // Darkened Sky - - [Constructible] - public DarkenedSky() - { - WeaponAttributes.HitLightning = 60; - Attributes.WeaponSpeed = 25; - Attributes.WeaponDamage = 50; - } - - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = pois = chaos = direct = 0; - cold = nrgy = 50; - } - - public DarkenedSky( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - public class KasaOfTheRajin : Kasa - { - public override int LabelNumber => 1070969; // Kasa of the Raj-in - - public override int BasePhysicalResistance => 12; - public override int BaseFireResistance => 17; - public override int BaseColdResistance => 21; - public override int BasePoisonResistance => 17; - public override int BaseEnergyResistance => 17; - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - [Constructible] - public KasaOfTheRajin() - { - Attributes.SpellDamage = 12; - } - - public KasaOfTheRajin( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)2 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version <= 1 ) - { - MaxHitPoints = 255; - HitPoints = 255; - } - - if ( version == 0 ) - LootType = LootType.Regular; - } - - } - - public class RuneBeetleCarapace : PlateDo - { - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - public override int LabelNumber => 1070968; // Rune Beetle Carapace - - public override int BaseColdResistance => 14; - public override int BaseEnergyResistance => 14; - - [Constructible] - public RuneBeetleCarapace() - { - Attributes.BonusMana = 10; - Attributes.RegenMana = 3; - Attributes.LowerManaCost = 15; - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - } - - public RuneBeetleCarapace( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - public class Stormgrip : LeatherNinjaMitts - { - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - public override int LabelNumber => 1070970; // Stormgrip - - public override int BasePhysicalResistance => 10; - public override int BaseColdResistance => 18; - public override int BaseEnergyResistance => 18; - - [Constructible] - public Stormgrip() - { - Attributes.BonusInt = 8; - Attributes.Luck = 125; - Attributes.WeaponDamage = 25; - } - - public Stormgrip( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - public class SwordOfTheStampede : NoDachi - { - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - public override int LabelNumber => 1070964; // Sword of the Stampede - - [Constructible] - public SwordOfTheStampede() - { - WeaponAttributes.HitHarm = 100; - Attributes.AttackChance = 10; - Attributes.WeaponDamage = 60; - } - - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = pois = nrgy = chaos = direct = 0; - cold = 100; - } - - public SwordOfTheStampede( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - public class SwordsOfProsperity : Daisho - { - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - public override int LabelNumber => 1070963; // Swords of Prosperity - - [Constructible] - public SwordsOfProsperity() - { - WeaponAttributes.MageWeapon = 30; - Attributes.SpellChanneling = 1; - Attributes.CastSpeed = 1; - Attributes.Luck = 200; - } - - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = cold = pois = nrgy = chaos = direct = 0; - fire = 100; - } - - public SwordsOfProsperity( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - public class TheHorselord : Yumi - { - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - public override int LabelNumber => 1070967; // The Horselord - - [Constructible] - public TheHorselord() - { - Attributes.BonusDex = 5; - Attributes.RegenMana = 1; - Attributes.Luck = 125; - Attributes.WeaponDamage = 50; - - Slayer = SlayerName.ElementalBan; - Slayer2 = SlayerName.ReptilianDeath; - } - - public TheHorselord( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TomeOfLostKnowledge : Spellbook - { - public override int LabelNumber => 1070971; // Tome of Lost Knowledge - - [Constructible] - public TomeOfLostKnowledge() - { - LootType = LootType.Regular; - Hue = 0x530; - - SkillBonuses.SetValues( 0, SkillName.Magery, 15.0 ); - Attributes.BonusInt = 8; - Attributes.LowerManaCost = 15; - Attributes.SpellDamage = 15; - } - - public TomeOfLostKnowledge( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WindsEdge : Tessen - { - public override int LabelNumber => 1070965; // Wind's Edge - - [Constructible] - public WindsEdge() - { - WeaponAttributes.HitLeechMana = 40; - - Attributes.WeaponDamage = 50; - Attributes.WeaponSpeed = 50; - Attributes.DefendChance = 10; - } - - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = chaos = direct = 0; - nrgy = 100; - } - - - public WindsEdge( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public enum PigmentType - { - None, - ParagonGold, - VioletCouragePurple, - InvulnerabilityBlue, - LunaWhite, - DryadGreen, - ShadowDancerBlack, - BerserkerRed, - NoxGreen, - RumRed, - FireOrange, - FadedCoal, - Coal, - FadedGold, - StormBronze, - Rose, - MidnightCoal, - FadedBronze, - FadedRose, - DeepRose - } - - public class PigmentsOfTokuno : BasePigmentsOfTokuno - { - private static int[][] m_Table = { - // Hue, Label - new[]{ /*PigmentType.None,*/ 0, -1 }, - new[]{ /*PigmentType.ParagonGold,*/ 0x501, 1070987 }, - new[]{ /*PigmentType.VioletCouragePurple,*/ 0x486, 1070988 }, - new[]{ /*PigmentType.InvulnerabilityBlue,*/ 0x4F2, 1070989 }, - new[]{ /*PigmentType.LunaWhite,*/ 0x47E, 1070990 }, - new[]{ /*PigmentType.DryadGreen,*/ 0x48F, 1070991 }, - new[]{ /*PigmentType.ShadowDancerBlack,*/ 0x455, 1070992 }, - new[]{ /*PigmentType.BerserkerRed,*/ 0x21, 1070993 }, - new[]{ /*PigmentType.NoxGreen,*/ 0x58C, 1070994 }, - new[]{ /*PigmentType.RumRed,*/ 0x66C, 1070995 }, - new[]{ /*PigmentType.FireOrange,*/ 0x54F, 1070996 }, - new[]{ /*PigmentType.Fadedcoal,*/ 0x96A, 1079579 }, - new[]{ /*PigmentType.Coal,*/ 0x96B, 1079580 }, - new[]{ /*PigmentType.FadedGold,*/ 0x972, 1079581 }, - new[]{ /*PigmentType.StormBronze,*/ 0x977, 1079582 }, - new[]{ /*PigmentType.Rose,*/ 0x97C, 1079583 }, - new[]{ /*PigmentType.MidnightCoal,*/ 0x96C, 1079584 }, - new[]{ /*PigmentType.FadedBronze,*/ 0x975, 1079585 }, - new[]{ /*PigmentType.FadedRose,*/ 0x97B, 1079586 }, - new[]{ /*PigmentType.DeepRose,*/ 0x97E, 1079587 } - }; - - public static int[] GetInfo( PigmentType type ) - { - int v = (int)type; - - if ( v < 0 || v >= m_Table.Length ) - v = 0; - - return m_Table[v]; - } - - private PigmentType m_Type; - - [CommandProperty( AccessLevel.GameMaster )] - public PigmentType Type - { - get => m_Type; - set - { - m_Type = value; - - int v = (int)m_Type; - - if ( v >= 0 && v < m_Table.Length ) - { - Hue = m_Table[v][0]; - Label = m_Table[v][1]; - } - else - { - Hue = 0; - Label = -1; - } - } - } - - public override int LabelNumber => 1070933; // Pigments of Tokuno - - [Constructible] - public PigmentsOfTokuno() : this( PigmentType.None, 10 ) - { - } - - [Constructible] - public PigmentsOfTokuno( PigmentType type ) : this( type, (type == PigmentType.None||type >= PigmentType.FadedCoal)? 10 : 50 ) - { - } - - [Constructible] - public PigmentsOfTokuno( PigmentType type, int uses ) : base( uses ) - { - Weight = 1.0; - Type = type; - } - - public PigmentsOfTokuno( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); - - writer.WriteEncodedInt( (int)m_Type ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = ( InheritsItem ? 0 : reader.ReadInt() ); // Required for BasePigmentsOfTokuno insertion - - switch ( version ) - { - case 1: Type = (PigmentType)reader.ReadEncodedInt(); break; - case 0: break; - } - } - } -} + public class DarkenedSky : Kama + { + [Constructible] + public DarkenedSky() + { + WeaponAttributes.HitLightning = 60; + Attributes.WeaponSpeed = 25; + Attributes.WeaponDamage = 50; + } + + public DarkenedSky(Serial serial) : base(serial) + { + } + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override int LabelNumber => 1070966; // Darkened Sky + + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = pois = chaos = direct = 0; + cold = nrgy = 50; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class KasaOfTheRajin : Kasa + { + [Constructible] + public KasaOfTheRajin() + { + Attributes.SpellDamage = 12; + } + + public KasaOfTheRajin(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070969; // Kasa of the Raj-in + + public override int BasePhysicalResistance => 12; + public override int BaseFireResistance => 17; + public override int BaseColdResistance => 21; + public override int BasePoisonResistance => 17; + public override int BaseEnergyResistance => 17; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version <= 1) + { + MaxHitPoints = 255; + HitPoints = 255; + } + + if (version == 0) + LootType = LootType.Regular; + } + } + + public class RuneBeetleCarapace : PlateDo + { + [Constructible] + public RuneBeetleCarapace() + { + Attributes.BonusMana = 10; + Attributes.RegenMana = 3; + Attributes.LowerManaCost = 15; + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + } + + public RuneBeetleCarapace(Serial serial) : base(serial) + { + } + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override int LabelNumber => 1070968; // Rune Beetle Carapace + + public override int BaseColdResistance => 14; + public override int BaseEnergyResistance => 14; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Stormgrip : LeatherNinjaMitts + { + [Constructible] + public Stormgrip() + { + Attributes.BonusInt = 8; + Attributes.Luck = 125; + Attributes.WeaponDamage = 25; + } + + public Stormgrip(Serial serial) : base(serial) + { + } + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override int LabelNumber => 1070970; // Stormgrip + + public override int BasePhysicalResistance => 10; + public override int BaseColdResistance => 18; + public override int BaseEnergyResistance => 18; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SwordOfTheStampede : NoDachi + { + [Constructible] + public SwordOfTheStampede() + { + WeaponAttributes.HitHarm = 100; + Attributes.AttackChance = 10; + Attributes.WeaponDamage = 60; + } + + public SwordOfTheStampede(Serial serial) : base(serial) + { + } + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override int LabelNumber => 1070964; // Sword of the Stampede + + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = pois = nrgy = chaos = direct = 0; + cold = 100; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SwordsOfProsperity : Daisho + { + [Constructible] + public SwordsOfProsperity() + { + WeaponAttributes.MageWeapon = 30; + Attributes.SpellChanneling = 1; + Attributes.CastSpeed = 1; + Attributes.Luck = 200; + } + + public SwordsOfProsperity(Serial serial) : base(serial) + { + } + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override int LabelNumber => 1070963; // Swords of Prosperity + + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = cold = pois = nrgy = chaos = direct = 0; + fire = 100; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TheHorselord : Yumi + { + [Constructible] + public TheHorselord() + { + Attributes.BonusDex = 5; + Attributes.RegenMana = 1; + Attributes.Luck = 125; + Attributes.WeaponDamage = 50; + + Slayer = SlayerName.ElementalBan; + Slayer2 = SlayerName.ReptilianDeath; + } + + public TheHorselord(Serial serial) : base(serial) + { + } + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override int LabelNumber => 1070967; // The Horselord + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TomeOfLostKnowledge : Spellbook + { + [Constructible] + public TomeOfLostKnowledge() + { + LootType = LootType.Regular; + Hue = 0x530; + + SkillBonuses.SetValues(0, SkillName.Magery, 15.0); + Attributes.BonusInt = 8; + Attributes.LowerManaCost = 15; + Attributes.SpellDamage = 15; + } + + public TomeOfLostKnowledge(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070971; // Tome of Lost Knowledge + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WindsEdge : Tessen + { + [Constructible] + public WindsEdge() + { + WeaponAttributes.HitLeechMana = 40; + + Attributes.WeaponDamage = 50; + Attributes.WeaponSpeed = 50; + Attributes.DefendChance = 10; + } + + + public WindsEdge(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070965; // Wind's Edge + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = chaos = direct = 0; + nrgy = 100; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public enum PigmentType + { + None, + ParagonGold, + VioletCouragePurple, + InvulnerabilityBlue, + LunaWhite, + DryadGreen, + ShadowDancerBlack, + BerserkerRed, + NoxGreen, + RumRed, + FireOrange, + FadedCoal, + Coal, + FadedGold, + StormBronze, + Rose, + MidnightCoal, + FadedBronze, + FadedRose, + DeepRose + } + + public class PigmentsOfTokuno : BasePigmentsOfTokuno + { + private static int[][] m_Table = + { + // Hue, Label + new[] + { + /*PigmentType.None,*/ 0, -1 + }, + new[] + { + /*PigmentType.ParagonGold,*/ 0x501, 1070987 + }, + new[] + { + /*PigmentType.VioletCouragePurple,*/ 0x486, 1070988 + }, + new[] + { + /*PigmentType.InvulnerabilityBlue,*/ 0x4F2, 1070989 + }, + new[] + { + /*PigmentType.LunaWhite,*/ 0x47E, 1070990 + }, + new[] + { + /*PigmentType.DryadGreen,*/ 0x48F, 1070991 + }, + new[] + { + /*PigmentType.ShadowDancerBlack,*/ 0x455, 1070992 + }, + new[] + { + /*PigmentType.BerserkerRed,*/ 0x21, 1070993 + }, + new[] + { + /*PigmentType.NoxGreen,*/ 0x58C, 1070994 + }, + new[] + { + /*PigmentType.RumRed,*/ 0x66C, 1070995 + }, + new[] + { + /*PigmentType.FireOrange,*/ 0x54F, 1070996 + }, + new[] + { + /*PigmentType.Fadedcoal,*/ 0x96A, 1079579 + }, + new[] + { + /*PigmentType.Coal,*/ 0x96B, 1079580 + }, + new[] + { + /*PigmentType.FadedGold,*/ 0x972, 1079581 + }, + new[] + { + /*PigmentType.StormBronze,*/ 0x977, 1079582 + }, + new[] + { + /*PigmentType.Rose,*/ 0x97C, 1079583 + }, + new[] + { + /*PigmentType.MidnightCoal,*/ 0x96C, 1079584 + }, + new[] + { + /*PigmentType.FadedBronze,*/ 0x975, 1079585 + }, + new[] + { + /*PigmentType.FadedRose,*/ 0x97B, 1079586 + }, + new[] + { + /*PigmentType.DeepRose,*/ 0x97E, 1079587 + } + }; + + private PigmentType m_Type; + + [Constructible] + public PigmentsOfTokuno() : this(PigmentType.None, 10) + { + } + + [Constructible] + public PigmentsOfTokuno(PigmentType type) : this(type, + type == PigmentType.None || type >= PigmentType.FadedCoal ? 10 : 50) + { + } + + [Constructible] + public PigmentsOfTokuno(PigmentType type, int uses) : base(uses) + { + Weight = 1.0; + Type = type; + } + + public PigmentsOfTokuno(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public PigmentType Type + { + get => m_Type; + set + { + m_Type = value; + + int v = (int)m_Type; + + if (v >= 0 && v < m_Table.Length) + { + Hue = m_Table[v][0]; + Label = m_Table[v][1]; + } + else + { + Hue = 0; + Label = -1; + } + } + } + + public override int LabelNumber => 1070933; // Pigments of Tokuno + + public static int[] GetInfo(PigmentType type) + { + int v = (int)type; + + if (v < 0 || v >= m_Table.Length) + v = 0; + + return m_Table[v]; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + + writer.WriteEncodedInt((int)m_Type); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = InheritsItem ? 0 : reader.ReadInt(); // Required for BasePigmentsOfTokuno insertion + + switch (version) + { + case 1: + Type = (PigmentType)reader.ReadEncodedInt(); + break; + case 0: break; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Treasures of Tokuno/LesserArtifacts.cs b/Scripts/Engines/Treasures of Tokuno/LesserArtifacts.cs index 75e1382af..992033bb1 100644 --- a/Scripts/Engines/Treasures of Tokuno/LesserArtifacts.cs +++ b/Scripts/Engines/Treasures of Tokuno/LesserArtifacts.cs @@ -1,1043 +1,1083 @@ namespace Server.Items { - public class AncientFarmersKasa : Kasa - { - public override int LabelNumber => 1070922; // Ancient Farmer's Kasa - public override int BaseColdResistance => 19; - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - [Constructible] - public AncientFarmersKasa() - { - Attributes.BonusStr = 5; - Attributes.BonusStam = 5; - Attributes.RegenStam = 5; - - SkillBonuses.SetValues( 0, SkillName.AnimalLore, 5.0 ); - } - - public AncientFarmersKasa( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version <= 1 ) - { - MaxHitPoints = 255; - HitPoints = 255; - } - - if ( version == 0 ) - SkillBonuses.SetValues( 0, SkillName.AnimalLore, 5.0 ); - } - } - - public class AncientSamuraiDo : PlateDo - { - public override int LabelNumber => 1070926; // Ancient Samurai Do - - public override int BasePhysicalResistance => 15; - public override int BaseFireResistance => 12; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 11; - public override int BaseEnergyResistance => 8; - - [Constructible] - public AncientSamuraiDo() - { - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - SkillBonuses.SetValues( 0, SkillName.Parry, 10.0 ); - } - - public AncientSamuraiDo( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class ArmsOfTacticalExcellence : LeatherHiroSode - { - public override int LabelNumber => 1070921; // Arms of Tactical Excellence - - public override int BaseFireResistance => 9; - public override int BaseColdResistance => 13; - public override int BasePoisonResistance => 8; - - [Constructible] - public ArmsOfTacticalExcellence() - { - Attributes.BonusDex = 5; - SkillBonuses.SetValues( 0, SkillName.Tactics, 12.0 ); - } - - public ArmsOfTacticalExcellence( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class BlackLotusHood : ClothNinjaHood - { - public override int LabelNumber => 1070919; // Black Lotus Hood - - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 11; - public override int BaseColdResistance => 15; - public override int BasePoisonResistance => 11; - public override int BaseEnergyResistance => 11; - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - - [Constructible] - public BlackLotusHood() - { - Attributes.LowerManaCost = 6; - Attributes.AttackChance = 6; - ClothingAttributes.SelfRepair = 5; - } - - public BlackLotusHood( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 ) - { - MaxHitPoints = 255; - HitPoints = 255; - } - } - } - - public class DaimyosHelm : PlateBattleKabuto - { - public override int LabelNumber => 1070920; // Daimyo's Helm - - public override int BaseColdResistance => 10; - - [Constructible] - public DaimyosHelm() - { - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - ArmorAttributes.SelfRepair = 3; - Attributes.WeaponSpeed = 10; - } - - public DaimyosHelm( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class DemonForks : Sai - { - public override int LabelNumber => 1070917; // Demon Forks - - [Constructible] - public DemonForks() - { - WeaponAttributes.ResistFireBonus = 10; - WeaponAttributes.ResistPoisonBonus = 10; - - Attributes.ReflectPhysical = 10; - Attributes.WeaponDamage = 35; - Attributes.DefendChance = 10; - } - - public DemonForks( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } + public class AncientFarmersKasa : Kasa + { + [Constructible] + public AncientFarmersKasa() + { + Attributes.BonusStr = 5; + Attributes.BonusStam = 5; + Attributes.RegenStam = 5; + + SkillBonuses.SetValues(0, SkillName.AnimalLore, 5.0); + } + + public AncientFarmersKasa(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070922; // Ancient Farmer's Kasa + public override int BaseColdResistance => 19; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version <= 1) + { + MaxHitPoints = 255; + HitPoints = 255; + } + + if (version == 0) + SkillBonuses.SetValues(0, SkillName.AnimalLore, 5.0); + } + } + + public class AncientSamuraiDo : PlateDo + { + [Constructible] + public AncientSamuraiDo() + { + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + SkillBonuses.SetValues(0, SkillName.Parry, 10.0); + } + + public AncientSamuraiDo(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070926; // Ancient Samurai Do + + public override int BasePhysicalResistance => 15; + public override int BaseFireResistance => 12; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 11; + public override int BaseEnergyResistance => 8; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ArmsOfTacticalExcellence : LeatherHiroSode + { + [Constructible] + public ArmsOfTacticalExcellence() + { + Attributes.BonusDex = 5; + SkillBonuses.SetValues(0, SkillName.Tactics, 12.0); + } + + public ArmsOfTacticalExcellence(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070921; // Arms of Tactical Excellence + + public override int BaseFireResistance => 9; + public override int BaseColdResistance => 13; + public override int BasePoisonResistance => 8; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BlackLotusHood : ClothNinjaHood + { + [Constructible] + public BlackLotusHood() + { + Attributes.LowerManaCost = 6; + Attributes.AttackChance = 6; + ClothingAttributes.SelfRepair = 5; + } + + public BlackLotusHood(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070919; // Black Lotus Hood + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 11; + public override int BaseColdResistance => 15; + public override int BasePoisonResistance => 11; + public override int BaseEnergyResistance => 11; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0) + { + MaxHitPoints = 255; + HitPoints = 255; + } + } + } + + public class DaimyosHelm : PlateBattleKabuto + { + [Constructible] + public DaimyosHelm() + { + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + ArmorAttributes.SelfRepair = 3; + Attributes.WeaponSpeed = 10; + } + + public DaimyosHelm(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070920; // Daimyo's Helm + + public override int BaseColdResistance => 10; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DemonForks : Sai + { + [Constructible] + public DemonForks() + { + WeaponAttributes.ResistFireBonus = 10; + WeaponAttributes.ResistPoisonBonus = 10; + + Attributes.ReflectPhysical = 10; + Attributes.WeaponDamage = 35; + Attributes.DefendChance = 10; + } + + public DemonForks(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070917; // Demon Forks + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DragonNunchaku : Nunchaku + { + [Constructible] + public DragonNunchaku() + { + WeaponAttributes.ResistFireBonus = 5; + WeaponAttributes.SelfRepair = 3; + WeaponAttributes.HitFireball = 50; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } + Attributes.WeaponDamage = 40; + Attributes.WeaponSpeed = 20; + } + + public DragonNunchaku(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070914; // Dragon Nunchaku + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } - public class DragonNunchaku : Nunchaku - { - public override int LabelNumber => 1070914; // Dragon Nunchaku + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public DragonNunchaku() - { - WeaponAttributes.ResistFireBonus = 5; - WeaponAttributes.SelfRepair = 3; - WeaponAttributes.HitFireball = 50; + int version = reader.ReadInt(); + } + } - Attributes.WeaponDamage = 40; - Attributes.WeaponSpeed = 20; - } + public class Exiler : Tetsubo + { + [Constructible] + public Exiler() + { + WeaponAttributes.HitDispel = 33; + Slayer = SlayerName.Exorcism; - public DragonNunchaku( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Attributes.WeaponDamage = 40; + Attributes.WeaponSpeed = 20; + } - writer.Write( (int)0 ); - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public Exiler(Serial serial) : base(serial) + { + } - int version = reader.ReadInt(); - } + public override int LabelNumber => 1070913; // Exiler - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public class Exiler : Tetsubo - { - public override int LabelNumber => 1070913; // Exiler + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = chaos = direct = 0; - [Constructible] - public Exiler() - { - WeaponAttributes.HitDispel = 33; - Slayer = SlayerName.Exorcism; + nrgy = 100; + } - Attributes.WeaponDamage = 40; - Attributes.WeaponSpeed = 20; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = chaos = direct = 0; + writer.Write(0); + } - nrgy = 100; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public Exiler( Serial serial ) : base( serial ) - { - } + public class GlovesOfTheSun : LeatherNinjaMitts + { + [Constructible] + public GlovesOfTheSun() + { + Attributes.RegenHits = 2; + Attributes.NightSight = 1; + Attributes.LowerManaCost = 5; + Attributes.LowerRegCost = 18; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public GlovesOfTheSun(Serial serial) : base(serial) + { + } - writer.Write( (int)0 ); - } + public override int LabelNumber => 1070924; // Gloves of the Sun - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int BaseFireResistance => 24; - int version = reader.ReadInt(); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public class GlovesOfTheSun : LeatherNinjaMitts - { - public override int LabelNumber => 1070924; // Gloves of the Sun + writer.Write(0); + } - public override int BaseFireResistance => 24; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public GlovesOfTheSun() - { - Attributes.RegenHits = 2; - Attributes.NightSight = 1; - Attributes.LowerManaCost = 5; - Attributes.LowerRegCost = 18; - } + int version = reader.ReadInt(); + } + } - public GlovesOfTheSun( Serial serial ) : base( serial ) - { - } + public class HanzosBow : Yumi + { + [Constructible] + public HanzosBow() + { + WeaponAttributes.HitLeechHits = 40; + WeaponAttributes.SelfRepair = 3; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Attributes.WeaponDamage = 50; - writer.Write( (int)0 ); - } + SkillBonuses.SetValues(0, SkillName.Ninjitsu, 10); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public HanzosBow(Serial serial) : base(serial) + { + } - int version = reader.ReadInt(); - } + public override int LabelNumber => 1070918; // Hanzo's Bow - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public class HanzosBow : Yumi - { - public override int LabelNumber => 1070918; // Hanzo's Bow + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Constructible] - public HanzosBow() - { - WeaponAttributes.HitLeechHits = 40; - WeaponAttributes.SelfRepair = 3; + writer.Write(0); + } - Attributes.WeaponDamage = 50; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - SkillBonuses.SetValues( 0, SkillName.Ninjitsu, 10 ); - } + int version = reader.ReadInt(); + } + } - public HanzosBow( Serial serial ) : base( serial ) - { - } + public class LegsOfStability : PlateSuneate + { + [Constructible] + public LegsOfStability() + { + Attributes.BonusStam = 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + ArmorAttributes.SelfRepair = 3; + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + } - writer.Write( (int)0 ); - } + public LegsOfStability(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070925; // Legs of Stability + + public override int BasePhysicalResistance => 20; + public override int BasePoisonResistance => 18; + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } + public class PeasantsBokuto : Bokuto + { + [Constructible] + public PeasantsBokuto() + { + WeaponAttributes.SelfRepair = 3; + WeaponAttributes.HitLowerDefend = 30; - public class LegsOfStability : PlateSuneate - { - public override int LabelNumber => 1070925; // Legs of Stability + Attributes.WeaponDamage = 35; + Attributes.WeaponSpeed = 10; + Slayer = SlayerName.SnakesBane; + } - public override int BasePhysicalResistance => 20; - public override int BasePoisonResistance => 18; + public PeasantsBokuto(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070912; // Peasant's Bokuto + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } - [Constructible] - public LegsOfStability() - { - Attributes.BonusStam = 5; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - ArmorAttributes.SelfRepair = 3; - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - } + int version = reader.ReadInt(); + } + } - public LegsOfStability( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class PeasantsBokuto : Bokuto - { - public override int LabelNumber => 1070912; // Peasant's Bokuto - - [Constructible] - public PeasantsBokuto() - { - WeaponAttributes.SelfRepair = 3; - WeaponAttributes.HitLowerDefend = 30; - - Attributes.WeaponDamage = 35; - Attributes.WeaponSpeed = 10; - Slayer = SlayerName.SnakesBane; - } - - public PeasantsBokuto( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class PilferedDancerFans : Tessen - { - public override int LabelNumber => 1070916; // Pilfered Dancer Fans - - [Constructible] - public PilferedDancerFans() - { - Attributes.WeaponDamage = 20; - Attributes.WeaponSpeed = 20; - Attributes.CastRecovery = 2; - Attributes.DefendChance = 5; - Attributes.SpellChanneling = 1; - } - - public PilferedDancerFans( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class TheDestroyer : NoDachi - { - public override int LabelNumber => 1070915; // The Destroyer - - [Constructible] - public TheDestroyer() - { - WeaponAttributes.HitLeechStam = 40; - - Attributes.BonusStr = 6; - Attributes.AttackChance = 10; - Attributes.WeaponDamage = 50; - } - - public TheDestroyer( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - public class TomeOfEnlightenment : Spellbook - { - public override int LabelNumber => 1070934; // Tome of Enlightenment - - [Constructible] - public TomeOfEnlightenment() - { - LootType = LootType.Regular; - Hue = 0x455; - - Attributes.BonusInt = 5; - Attributes.SpellDamage = 10; - Attributes.CastSpeed = 1; - } - - public TomeOfEnlightenment( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LeurociansMempoOfFortune : LeatherMempo - { - public override int LabelNumber => 1071460; // Leurocian's mempo of fortune - - public override int BasePhysicalResistance => 15; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 15; - - [Constructible] - public LeurociansMempoOfFortune() - { - LootType = LootType.Regular; - Hue = 0x501; - - Attributes.Luck = 300; - Attributes.RegenMana = 1; - } - - public LeurociansMempoOfFortune( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; - } - - //Non weapon/armor ones: - - public class AncientUrn : Item - { - public static string[] Names { get; } = - { - "Akira", - "Avaniaga", - "Aya", - "Chie", - "Emiko", - "Fumiyo", - "Gennai", - "Gennosuke", - "Genjo", - "Hamato", - "Harumi", - "Ikuyo", - "Juri", - "Kaori", - "Kaoru", - "Kiyomori", - "Mayako", - "Motoki", - "Musashi", - "Nami", - "Nobukazu", - "Roku", - "Romi", - "Ryo", - "Sanzo", - "Sakamae", - "Satoshi", - "Takamori", - "Takuro", - "Teruyo", - "Toshiro", - "Yago", - "Yeijiro", - "Yoshi", - "Zeshin" - }; - - private string m_UrnName; - - [CommandProperty( AccessLevel.GameMaster )] - public string UrnName - { - get => m_UrnName; - set => m_UrnName = value; - } - - public override int LabelNumber => 1071014; // Ancient Urn - - [Constructible] - public AncientUrn( string urnName ) : base( 0x241D ) - { - m_UrnName = urnName; - Weight = 1.0; - } - - [Constructible] - public AncientUrn() : this( Names[Utility.Random( Names.Length )] ) - { - } - - public AncientUrn( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - writer.Write( m_UrnName ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - m_UrnName = reader.ReadString(); - - Utility.Intern( ref m_UrnName ); - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1070935, m_UrnName ); // Ancient Urn of ~1_name~ - } - - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, 1070935, m_UrnName ); // Ancient Urn of ~1_name~ - } - - } - - public class HonorableSwords : Item - { - private string m_SwordsName; - - [CommandProperty( AccessLevel.GameMaster )] - public string SwordsName - { - get => m_SwordsName; - set => m_SwordsName = value; - } - - public override int LabelNumber => 1071015; // Honorable Swords - - [Constructible] - public HonorableSwords( string swordsName ) : base( 0x2853 ) - { - m_SwordsName = swordsName; - - Weight = 5.0; - } - - [Constructible] - public HonorableSwords() : this( AncientUrn.Names[Utility.Random( AncientUrn.Names.Length )] ) - { - } - - public HonorableSwords( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - writer.Write( m_SwordsName ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - m_SwordsName = reader.ReadString(); - - Utility.Intern( ref m_SwordsName ); - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1070936, m_SwordsName ); // Honorable Swords of ~1_name~ - } - - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, 1070936, m_SwordsName ); // Honorable Swords of ~1_name~ - } - } - - [Furniture] - [Flippable( 0x2811, 0x2812 )] - public class ChestOfHeirlooms : LockableContainer - { - public override int LabelNumber => 1070937; // Chest of heirlooms - - [Constructible] - public ChestOfHeirlooms() : base( 0x2811 ) - { - Locked = true; - LockLevel = 95; - MaxLockLevel = 140; - RequiredSkill = 95; - - TrapType = TrapType.ExplosionTrap; - TrapLevel = 10; - TrapPower = 100; - - GumpID = 0x10B; - - for ( int i = 0; i < 10; ++i ) - { - Item item = Loot.ChestOfHeirloomsContains(); - - int attributeCount = Utility.RandomMinMax( 1, 5 ); - int min = 20; - int max = 80; - - if ( item is BaseWeapon weapon ) - { - if ( Core.AOS ) - BaseRunicTool.ApplyAttributesTo( weapon, attributeCount, min, max ); - else - { - weapon.DamageLevel = (WeaponDamageLevel)Utility.Random( 6 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random( 6 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random( 6 ); - } - } - else if ( item is BaseArmor armor ) - { - if ( Core.AOS ) - BaseRunicTool.ApplyAttributesTo( armor, attributeCount, min, max ); - else - { - armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random( 6 ); - armor.Durability = (ArmorDurabilityLevel)Utility.Random( 6 ); - } - } - else if (Core.AOS) - { - if ( item is BaseHat hat ) - BaseRunicTool.ApplyAttributesTo( hat, attributeCount, min, max ); - else if ( item is BaseJewel jewel ) - BaseRunicTool.ApplyAttributesTo( jewel, attributeCount, min, max ); - } - - DropItem( item ); - } - } - - public ChestOfHeirlooms( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FluteOfRenewal : BambooFlute - { - public override int LabelNumber => 1070927; // Flute of Renewal - - [Constructible] - public FluteOfRenewal() - { - Slayer = SlayerGroup.Groups[Utility.Random( SlayerGroup.Groups.Length - 1 )].Super.Name; //-1 to exclude Fey slayer. Try to confrim no fey slayer on this on OSI - - ReplenishesCharges = true; - } - - public override int InitMinUses => 300; - public override int InitMaxUses => 300; - - public FluteOfRenewal( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Slayer == SlayerName.Fey ) - Slayer = SlayerGroup.Groups[Utility.Random( SlayerGroup.Groups.Length - 1 )].Super.Name; - } - } - - public enum LesserPigmentType - { - None, - PaleOrange, - FreshRose, - ChaosBlue, - Silver, - NobleGold, - LightGreen, - PaleBlue, - FreshPlum, - DeepBrown, - BurntBrown - } - - public class LesserPigmentsOfTokuno : BasePigmentsOfTokuno - { - - private static int[][] m_Table = { - // Hue, Label - new[]{ /*PigmentType.None,*/ 0, -1 }, - new[]{ /*PigmentType.PaleOrange,*/ 0x02E, 1071458 }, - new[]{ /*PigmentType.FreshRose,*/ 0x4B9, 1071455 }, - new[]{ /*PigmentType.ChaosBlue,*/ 0x005, 1071459 }, - new[]{ /*PigmentType.Silver,*/ 0x3E9, 1071451 }, - new[]{ /*PigmentType.NobleGold,*/ 0x227, 1071457 }, - new[]{ /*PigmentType.LightGreen,*/ 0x1C8, 1071454 }, - new[]{ /*PigmentType.PaleBlue,*/ 0x24F, 1071456 }, - new[]{ /*PigmentType.FreshPlum,*/ 0x145, 1071450 }, - new[]{ /*PigmentType.DeepBrown,*/ 0x3F0, 1071452 }, - new[]{ /*PigmentType.BurntBrown,*/ 0x41A, 1071453 } - }; - - public static int[] GetInfo( LesserPigmentType type ) - { - int v = (int)type; - - if ( v < 0 || v >= m_Table.Length ) - v = 0; - - return m_Table[v]; - } - - private LesserPigmentType m_Type; - - [CommandProperty( AccessLevel.GameMaster )] - public LesserPigmentType Type - { - get => m_Type; - set - { - m_Type = value; - - int v = (int)m_Type; - - if ( v >= 0 && v < m_Table.Length ) - { - Hue = m_Table[v][0]; - Label = m_Table[v][1]; - } - else - { - Hue = 0; - Label = -1; - } - } - } - - [Constructible] - public LesserPigmentsOfTokuno() : this( (LesserPigmentType)Utility.Random(0,11) ) - { - } - - [Constructible] - public LesserPigmentsOfTokuno( LesserPigmentType type ) : base( 1 ) - { - Weight = 1.0; - Type = type; - } - - public LesserPigmentsOfTokuno( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); - - writer.WriteEncodedInt( (int)m_Type ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = ( InheritsItem ? 0 : reader.ReadInt() ); // Required for BasePigmentsOfTokuno insertion - - switch ( version ) - { - case 1: Type = (LesserPigmentType)reader.ReadEncodedInt(); break; - case 0: break; - } - } - } - - public class MetalPigmentsOfTokuno : BasePigmentsOfTokuno - { - [Constructible] - public MetalPigmentsOfTokuno() : base( 1 ) - { - RandomHue(); - Label = -1; - } - - public MetalPigmentsOfTokuno( Serial serial ) : base( serial ) - { - } - - public void RandomHue() - { - int a = Utility.Random(0,30); - if ( a != 0 ) - Hue = a + 0x960; - else - Hue = 0; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = ( InheritsItem ? 0 : reader.ReadInt() ); // Required for BasePigmentsOfTokuno insertion - } - } -} + public class PilferedDancerFans : Tessen + { + [Constructible] + public PilferedDancerFans() + { + Attributes.WeaponDamage = 20; + Attributes.WeaponSpeed = 20; + Attributes.CastRecovery = 2; + Attributes.DefendChance = 5; + Attributes.SpellChanneling = 1; + } + + public PilferedDancerFans(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070916; // Pilfered Dancer Fans + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TheDestroyer : NoDachi + { + [Constructible] + public TheDestroyer() + { + WeaponAttributes.HitLeechStam = 40; + + Attributes.BonusStr = 6; + Attributes.AttackChance = 10; + Attributes.WeaponDamage = 50; + } + + public TheDestroyer(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070915; // The Destroyer + + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TomeOfEnlightenment : Spellbook + { + [Constructible] + public TomeOfEnlightenment() + { + LootType = LootType.Regular; + Hue = 0x455; + + Attributes.BonusInt = 5; + Attributes.SpellDamage = 10; + Attributes.CastSpeed = 1; + } + + public TomeOfEnlightenment(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070934; // Tome of Enlightenment + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LeurociansMempoOfFortune : LeatherMempo + { + [Constructible] + public LeurociansMempoOfFortune() + { + LootType = LootType.Regular; + Hue = 0x501; + + Attributes.Luck = 300; + Attributes.RegenMana = 1; + } + + public LeurociansMempoOfFortune(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1071460; // Leurocian's mempo of fortune + + public override int BasePhysicalResistance => 15; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 15; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + //Non weapon/armor ones: + + public class AncientUrn : Item + { + private string m_UrnName; + + [Constructible] + public AncientUrn(string urnName) : base(0x241D) + { + m_UrnName = urnName; + Weight = 1.0; + } + + [Constructible] + public AncientUrn() : this(Names[Utility.Random(Names.Length)]) + { + } + + public AncientUrn(Serial serial) : base(serial) + { + } + + public static string[] Names{ get; } = + { + "Akira", + "Avaniaga", + "Aya", + "Chie", + "Emiko", + "Fumiyo", + "Gennai", + "Gennosuke", + "Genjo", + "Hamato", + "Harumi", + "Ikuyo", + "Juri", + "Kaori", + "Kaoru", + "Kiyomori", + "Mayako", + "Motoki", + "Musashi", + "Nami", + "Nobukazu", + "Roku", + "Romi", + "Ryo", + "Sanzo", + "Sakamae", + "Satoshi", + "Takamori", + "Takuro", + "Teruyo", + "Toshiro", + "Yago", + "Yeijiro", + "Yoshi", + "Zeshin" + }; + + [CommandProperty(AccessLevel.GameMaster)] + public string UrnName + { + get => m_UrnName; + set => m_UrnName = value; + } + + public override int LabelNumber => 1071014; // Ancient Urn + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + writer.Write(m_UrnName); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + m_UrnName = reader.ReadString(); + + Utility.Intern(ref m_UrnName); + } + + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1070935, m_UrnName); // Ancient Urn of ~1_name~ + } + + public override void OnSingleClick(Mobile from) + { + LabelTo(from, 1070935, m_UrnName); // Ancient Urn of ~1_name~ + } + } + + public class HonorableSwords : Item + { + private string m_SwordsName; + + [Constructible] + public HonorableSwords(string swordsName) : base(0x2853) + { + m_SwordsName = swordsName; + + Weight = 5.0; + } + + [Constructible] + public HonorableSwords() : this(AncientUrn.Names[Utility.Random(AncientUrn.Names.Length)]) + { + } + + public HonorableSwords(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string SwordsName + { + get => m_SwordsName; + set => m_SwordsName = value; + } + + public override int LabelNumber => 1071015; // Honorable Swords + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + writer.Write(m_SwordsName); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + m_SwordsName = reader.ReadString(); + + Utility.Intern(ref m_SwordsName); + } + + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1070936, m_SwordsName); // Honorable Swords of ~1_name~ + } + + public override void OnSingleClick(Mobile from) + { + LabelTo(from, 1070936, m_SwordsName); // Honorable Swords of ~1_name~ + } + } + + [Furniture] + [Flippable(0x2811, 0x2812)] + public class ChestOfHeirlooms : LockableContainer + { + [Constructible] + public ChestOfHeirlooms() : base(0x2811) + { + Locked = true; + LockLevel = 95; + MaxLockLevel = 140; + RequiredSkill = 95; + + TrapType = TrapType.ExplosionTrap; + TrapLevel = 10; + TrapPower = 100; + + GumpID = 0x10B; + + for (int i = 0; i < 10; ++i) + { + Item item = Loot.ChestOfHeirloomsContains(); + + int attributeCount = Utility.RandomMinMax(1, 5); + int min = 20; + int max = 80; + + if (item is BaseWeapon weapon) + { + if (Core.AOS) + { + BaseRunicTool.ApplyAttributesTo(weapon, attributeCount, min, max); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)Utility.Random(6); + weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random(6); + weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random(6); + } + } + else if (item is BaseArmor armor) + { + if (Core.AOS) + { + BaseRunicTool.ApplyAttributesTo(armor, attributeCount, min, max); + } + else + { + armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random(6); + armor.Durability = (ArmorDurabilityLevel)Utility.Random(6); + } + } + else if (Core.AOS) + { + if (item is BaseHat hat) + BaseRunicTool.ApplyAttributesTo(hat, attributeCount, min, max); + else if (item is BaseJewel jewel) + BaseRunicTool.ApplyAttributesTo(jewel, attributeCount, min, max); + } + + DropItem(item); + } + } + + public ChestOfHeirlooms(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070937; // Chest of heirlooms + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FluteOfRenewal : BambooFlute + { + [Constructible] + public FluteOfRenewal() + { + Slayer = SlayerGroup.Groups[Utility.Random(SlayerGroup.Groups.Length - 1)].Super + .Name; //-1 to exclude Fey slayer. Try to confrim no fey slayer on this on OSI + + ReplenishesCharges = true; + } + + public FluteOfRenewal(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1070927; // Flute of Renewal + + public override int InitMinUses => 300; + public override int InitMaxUses => 300; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Slayer == SlayerName.Fey) + Slayer = SlayerGroup.Groups[Utility.Random(SlayerGroup.Groups.Length - 1)].Super.Name; + } + } + + public enum LesserPigmentType + { + None, + PaleOrange, + FreshRose, + ChaosBlue, + Silver, + NobleGold, + LightGreen, + PaleBlue, + FreshPlum, + DeepBrown, + BurntBrown + } + + public class LesserPigmentsOfTokuno : BasePigmentsOfTokuno + { + private static int[][] m_Table = + { + // Hue, Label + new[] + { + /*PigmentType.None,*/ 0, -1 + }, + new[] + { + /*PigmentType.PaleOrange,*/ 0x02E, 1071458 + }, + new[] + { + /*PigmentType.FreshRose,*/ 0x4B9, 1071455 + }, + new[] + { + /*PigmentType.ChaosBlue,*/ 0x005, 1071459 + }, + new[] + { + /*PigmentType.Silver,*/ 0x3E9, 1071451 + }, + new[] + { + /*PigmentType.NobleGold,*/ 0x227, 1071457 + }, + new[] + { + /*PigmentType.LightGreen,*/ 0x1C8, 1071454 + }, + new[] + { + /*PigmentType.PaleBlue,*/ 0x24F, 1071456 + }, + new[] + { + /*PigmentType.FreshPlum,*/ 0x145, 1071450 + }, + new[] + { + /*PigmentType.DeepBrown,*/ 0x3F0, 1071452 + }, + new[] + { + /*PigmentType.BurntBrown,*/ 0x41A, 1071453 + } + }; + + private LesserPigmentType m_Type; + + [Constructible] + public LesserPigmentsOfTokuno() : this((LesserPigmentType)Utility.Random(0, 11)) + { + } + + [Constructible] + public LesserPigmentsOfTokuno(LesserPigmentType type) : base(1) + { + Weight = 1.0; + Type = type; + } + + public LesserPigmentsOfTokuno(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public LesserPigmentType Type + { + get => m_Type; + set + { + m_Type = value; + + int v = (int)m_Type; + + if (v >= 0 && v < m_Table.Length) + { + Hue = m_Table[v][0]; + Label = m_Table[v][1]; + } + else + { + Hue = 0; + Label = -1; + } + } + } + + public static int[] GetInfo(LesserPigmentType type) + { + int v = (int)type; + + if (v < 0 || v >= m_Table.Length) + v = 0; + + return m_Table[v]; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + + writer.WriteEncodedInt((int)m_Type); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = InheritsItem ? 0 : reader.ReadInt(); // Required for BasePigmentsOfTokuno insertion + + switch (version) + { + case 1: + Type = (LesserPigmentType)reader.ReadEncodedInt(); + break; + case 0: break; + } + } + } + + public class MetalPigmentsOfTokuno : BasePigmentsOfTokuno + { + [Constructible] + public MetalPigmentsOfTokuno() : base(1) + { + RandomHue(); + Label = -1; + } + + public MetalPigmentsOfTokuno(Serial serial) : base(serial) + { + } + + public void RandomHue() + { + int a = Utility.Random(0, 30); + if (a != 0) + Hue = a + 0x960; + else + Hue = 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = InheritsItem ? 0 : reader.ReadInt(); // Required for BasePigmentsOfTokuno insertion + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokuno.cs b/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokuno.cs index 72141e6e2..efc3a5c66 100644 --- a/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokuno.cs +++ b/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokuno.cs @@ -1,573 +1,630 @@ using System; -using Server.Network; using System.Collections; using System.Collections.Generic; -using Server.Items; using Server.Gumps; +using Server.Items; using Server.Misc; using Server.Mobiles; +using Server.Multis; +using Server.Network; +using Server.Regions; namespace Server.Misc { - public enum TreasuresOfTokunoEra - { - None, - ToTOne, - ToTTwo, - ToTThree - } + public enum TreasuresOfTokunoEra + { + None, + ToTOne, + ToTTwo, + ToTThree + } - public class TreasuresOfTokuno - { - public const int ItemsPerReward = 10; + public class TreasuresOfTokuno + { + public const int ItemsPerReward = 10; - public static Type[] LesserArtifactsTotal { get; } = - { - typeof( AncientFarmersKasa ), typeof( AncientSamuraiDo ), typeof( ArmsOfTacticalExcellence ), typeof( BlackLotusHood ), - typeof( DaimyosHelm ), typeof( DemonForks ), typeof( DragonNunchaku ), typeof( Exiler ), typeof( GlovesOfTheSun ), - typeof( HanzosBow ), typeof( LegsOfStability ), typeof( PeasantsBokuto ), typeof( PilferedDancerFans ), typeof( TheDestroyer ), - typeof( TomeOfEnlightenment ), typeof( AncientUrn ), typeof( HonorableSwords ), typeof( PigmentsOfTokuno ), typeof( FluteOfRenewal ), - typeof( LeurociansMempoOfFortune ), typeof( LesserPigmentsOfTokuno ), typeof( MetalPigmentsOfTokuno ), typeof( ChestOfHeirlooms ) - }; + private static Type[][] m_LesserArtifacts = + { + // ToT One Rewards + new[] + { + typeof(AncientFarmersKasa), typeof(AncientSamuraiDo), typeof(ArmsOfTacticalExcellence), + typeof(BlackLotusHood), + typeof(DaimyosHelm), typeof(DemonForks), typeof(DragonNunchaku), typeof(Exiler), typeof(GlovesOfTheSun), + typeof(HanzosBow), typeof(LegsOfStability), typeof(PeasantsBokuto), typeof(PilferedDancerFans), + typeof(TheDestroyer), + typeof(TomeOfEnlightenment), typeof(AncientUrn), typeof(HonorableSwords), typeof(PigmentsOfTokuno), + typeof(FluteOfRenewal), typeof(ChestOfHeirlooms) + }, + // ToT Two Rewards + new[] + { + typeof(MetalPigmentsOfTokuno), typeof(AncientFarmersKasa), typeof(AncientSamuraiDo), + typeof(ArmsOfTacticalExcellence), + typeof(MetalPigmentsOfTokuno), typeof(BlackLotusHood), typeof(DaimyosHelm), typeof(DemonForks), + typeof(MetalPigmentsOfTokuno), typeof(DragonNunchaku), typeof(Exiler), typeof(GlovesOfTheSun), + typeof(HanzosBow), + typeof(MetalPigmentsOfTokuno), typeof(LegsOfStability), typeof(PeasantsBokuto), typeof(PilferedDancerFans), + typeof(TheDestroyer), + typeof(MetalPigmentsOfTokuno), typeof(TomeOfEnlightenment), typeof(AncientUrn), typeof(HonorableSwords), + typeof(MetalPigmentsOfTokuno), typeof(FluteOfRenewal), typeof(ChestOfHeirlooms) + }, + // ToT Three Rewards + new[] + { + typeof(LesserPigmentsOfTokuno), typeof(AncientFarmersKasa), typeof(AncientSamuraiDo), + typeof(ArmsOfTacticalExcellence), + typeof(LesserPigmentsOfTokuno), typeof(BlackLotusHood), typeof(DaimyosHelm), typeof(HanzosBow), + typeof(LesserPigmentsOfTokuno), typeof(DemonForks), typeof(DragonNunchaku), typeof(Exiler), + typeof(GlovesOfTheSun), + typeof(LesserPigmentsOfTokuno), typeof(LegsOfStability), typeof(PeasantsBokuto), typeof(PilferedDancerFans), + typeof(TheDestroyer), + typeof(LesserPigmentsOfTokuno), typeof(TomeOfEnlightenment), typeof(AncientUrn), typeof(HonorableSwords), + typeof(FluteOfRenewal), + typeof(LesserPigmentsOfTokuno), typeof(LeurociansMempoOfFortune), typeof(ChestOfHeirlooms) + } + }; - public static TreasuresOfTokunoEra DropEra { get; set; } = TreasuresOfTokunoEra.None; + private static Type[][] m_GreaterArtifacts; - public static TreasuresOfTokunoEra RewardEra { get; set; } = TreasuresOfTokunoEra.ToTOne; + public static Type[] LesserArtifactsTotal{ get; } = + { + typeof(AncientFarmersKasa), typeof(AncientSamuraiDo), typeof(ArmsOfTacticalExcellence), typeof(BlackLotusHood), + typeof(DaimyosHelm), typeof(DemonForks), typeof(DragonNunchaku), typeof(Exiler), typeof(GlovesOfTheSun), + typeof(HanzosBow), typeof(LegsOfStability), typeof(PeasantsBokuto), typeof(PilferedDancerFans), + typeof(TheDestroyer), + typeof(TomeOfEnlightenment), typeof(AncientUrn), typeof(HonorableSwords), typeof(PigmentsOfTokuno), + typeof(FluteOfRenewal), + typeof(LeurociansMempoOfFortune), typeof(LesserPigmentsOfTokuno), typeof(MetalPigmentsOfTokuno), + typeof(ChestOfHeirlooms) + }; - private static Type[][] m_LesserArtifacts = { - // ToT One Rewards - new[] { - typeof( AncientFarmersKasa ), typeof( AncientSamuraiDo ), typeof( ArmsOfTacticalExcellence ), typeof( BlackLotusHood ), - typeof( DaimyosHelm ), typeof( DemonForks ), typeof( DragonNunchaku ), typeof( Exiler ), typeof( GlovesOfTheSun ), - typeof( HanzosBow ), typeof( LegsOfStability ), typeof( PeasantsBokuto ), typeof( PilferedDancerFans ), typeof( TheDestroyer ), - typeof( TomeOfEnlightenment ), typeof( AncientUrn ), typeof( HonorableSwords ), typeof( PigmentsOfTokuno ), - typeof( FluteOfRenewal ), typeof( ChestOfHeirlooms ) - }, - // ToT Two Rewards - new[] { - typeof( MetalPigmentsOfTokuno ), typeof( AncientFarmersKasa ), typeof( AncientSamuraiDo ), typeof( ArmsOfTacticalExcellence ), - typeof( MetalPigmentsOfTokuno ), typeof( BlackLotusHood ), typeof( DaimyosHelm ), typeof( DemonForks ), - typeof( MetalPigmentsOfTokuno ), typeof( DragonNunchaku ), typeof( Exiler ), typeof( GlovesOfTheSun ), typeof( HanzosBow ), - typeof( MetalPigmentsOfTokuno ), typeof( LegsOfStability ), typeof( PeasantsBokuto ), typeof( PilferedDancerFans ), typeof( TheDestroyer ), - typeof( MetalPigmentsOfTokuno ), typeof( TomeOfEnlightenment ), typeof( AncientUrn ), typeof( HonorableSwords ), - typeof( MetalPigmentsOfTokuno ), typeof( FluteOfRenewal ), typeof( ChestOfHeirlooms ) - }, - // ToT Three Rewards - new[] { - typeof( LesserPigmentsOfTokuno ), typeof( AncientFarmersKasa ), typeof( AncientSamuraiDo ), typeof( ArmsOfTacticalExcellence ), - typeof( LesserPigmentsOfTokuno ), typeof( BlackLotusHood ), typeof( DaimyosHelm ), typeof( HanzosBow ), - typeof( LesserPigmentsOfTokuno ), typeof( DemonForks ), typeof( DragonNunchaku ), typeof( Exiler ), typeof( GlovesOfTheSun ), - typeof( LesserPigmentsOfTokuno ), typeof( LegsOfStability ), typeof( PeasantsBokuto ), typeof( PilferedDancerFans ), typeof( TheDestroyer ), - typeof( LesserPigmentsOfTokuno ), typeof( TomeOfEnlightenment ), typeof( AncientUrn ), typeof( HonorableSwords ), typeof( FluteOfRenewal ), - typeof( LesserPigmentsOfTokuno ), typeof( LeurociansMempoOfFortune ), typeof( ChestOfHeirlooms ) - } - }; + public static TreasuresOfTokunoEra DropEra{ get; set; } = TreasuresOfTokunoEra.None; - public static Type[] LesserArtifacts => m_LesserArtifacts[(int)RewardEra-1]; + public static TreasuresOfTokunoEra RewardEra{ get; set; } = TreasuresOfTokunoEra.ToTOne; - private static Type[][] m_GreaterArtifacts; + public static Type[] LesserArtifacts => m_LesserArtifacts[(int)RewardEra - 1]; - public static Type[] GreaterArtifacts - { - get - { - if ( m_GreaterArtifacts == null ) - { - m_GreaterArtifacts = new Type[ToTRedeemGump.NormalRewards.Length][]; + public static Type[] GreaterArtifacts + { + get + { + if (m_GreaterArtifacts == null) + { + m_GreaterArtifacts = new Type[ToTRedeemGump.NormalRewards.Length][]; - for( int i = 0; i < m_GreaterArtifacts.Length; i++ ) - { - m_GreaterArtifacts[i] = new Type[ToTRedeemGump.NormalRewards[i].Length]; + for (int i = 0; i < m_GreaterArtifacts.Length; i++) + { + m_GreaterArtifacts[i] = new Type[ToTRedeemGump.NormalRewards[i].Length]; - for( int j = 0; j < m_GreaterArtifacts[i].Length; j++ ) - { - m_GreaterArtifacts[i][j] = ToTRedeemGump.NormalRewards[i][j].Type; - } - } - } + for (int j = 0; j < m_GreaterArtifacts[i].Length; j++) + m_GreaterArtifacts[i][j] = ToTRedeemGump.NormalRewards[i][j].Type; + } + } - return m_GreaterArtifacts[(int)RewardEra-1]; - } - } + return m_GreaterArtifacts[(int)RewardEra - 1]; + } + } - private static bool CheckLocation( Mobile m ) - { - Region r = m.Region; + private static bool CheckLocation(Mobile m) + { + Region r = m.Region; - if ( r.IsPartOf( typeof( Regions.HouseRegion ) ) || Multis.BaseBoat.FindBoatAt( m, m.Map ) != null ) - return false; - //TODO: a CanReach of something check as opposed to above? + if (r.IsPartOf(typeof(HouseRegion)) || BaseBoat.FindBoatAt(m, m.Map) != null) + return false; + //TODO: a CanReach of something check as opposed to above? - if ( r.IsPartOf( "Yomotsu Mines" ) || r.IsPartOf( "Fan Dancer's Dojo" ) ) - return true; + if (r.IsPartOf("Yomotsu Mines") || r.IsPartOf("Fan Dancer's Dojo")) + return true; - return (m.Map == Map.Tokuno); - } + return m.Map == Map.Tokuno; + } - public static void HandleKill( Mobile victim, Mobile killer ) - { - if ( DropEra == TreasuresOfTokunoEra.None || !(killer is PlayerMobile pm) || !(victim is BaseCreature bc) || !CheckLocation( bc ) || !CheckLocation( pm )|| !killer.InRange( victim, 18 )) - return; + public static void HandleKill(Mobile victim, Mobile killer) + { + if (DropEra == TreasuresOfTokunoEra.None || !(killer is PlayerMobile pm) || !(victim is BaseCreature bc) || + !CheckLocation(bc) || !CheckLocation(pm) || !killer.InRange(victim, 18)) + return; - if ( bc.Controlled || bc.Owners.Count > 0 || bc.Fame <= 0 ) - return; + if (bc.Controlled || bc.Owners.Count > 0 || bc.Fame <= 0) + return; - //25000 for 1/100 chance, 10 hyrus - //1500, 1/1000 chance, 20 lizard men for that chance. + //25000 for 1/100 chance, 10 hyrus + //1500, 1/1000 chance, 20 lizard men for that chance. - pm.ToTTotalMonsterFame += (int)(bc.Fame * (1 + Math.Sqrt( pm.Luck ) / 100)); + pm.ToTTotalMonsterFame += (int)(bc.Fame * (1 + Math.Sqrt(pm.Luck) / 100)); - //This is the Exponentional regression with only 2 datapoints. - //A log. func would also work, but it didn't make as much sense. - //This function isn't OSI exact beign that I don't know OSI's func they used ;p - int x = pm.ToTTotalMonsterFame; + //This is the Exponentional regression with only 2 datapoints. + //A log. func would also work, but it didn't make as much sense. + //This function isn't OSI exact beign that I don't know OSI's func they used ;p + int x = pm.ToTTotalMonsterFame; - //const double A = 8.63316841 * Math.Pow( 10, -4 ); - const double A = 0.000863316841; - //const double B = 4.25531915 * Math.Pow( 10, -6 ); - const double B = 0.00000425531915; + //const double A = 8.63316841 * Math.Pow( 10, -4 ); + const double A = 0.000863316841; + //const double B = 4.25531915 * Math.Pow( 10, -6 ); + const double B = 0.00000425531915; - double chance = A * Math.Pow( 10, B * x ); + double chance = A * Math.Pow(10, B * x); - if ( chance > Utility.RandomDouble() ) - { - Item i = null; + if (chance > Utility.RandomDouble()) + { + Item i = null; - try - { - i = Activator.CreateInstance( m_LesserArtifacts[(int)DropEra-1][Utility.Random( m_LesserArtifacts[(int)DropEra-1].Length )] ) as Item; - } - catch - { } + try + { + i = Activator.CreateInstance( + m_LesserArtifacts[(int)DropEra - 1][Utility.Random(m_LesserArtifacts[(int)DropEra - 1].Length)]) + as + Item; + } + catch + { + } - if ( i != null ) - { - pm.SendLocalizedMessage( 1062317 ); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. + if (i != null) + { + pm.SendLocalizedMessage( + 1062317); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. - if ( !pm.PlaceInBackpack( i ) ) - { - if ( pm.BankBox != null && pm.BankBox.TryDropItem( killer, i, false ) ) - pm.SendLocalizedMessage( 1079730 ); // The item has been placed into your bank box. - else - { - pm.SendLocalizedMessage( 1072523 ); // You find an artifact, but your backpack and bank are too full to hold it. - i.MoveToWorld( pm.Location, pm.Map ); - } - } + if (!pm.PlaceInBackpack(i)) + { + if (pm.BankBox != null && pm.BankBox.TryDropItem(killer, i, false)) + { + pm.SendLocalizedMessage(1079730); // The item has been placed into your bank box. + } + else + { + pm.SendLocalizedMessage( + 1072523); // You find an artifact, but your backpack and bank are too full to hold it. + i.MoveToWorld(pm.Location, pm.Map); + } + } - pm.ToTTotalMonsterFame = 0; - } - } - } - } + pm.ToTTotalMonsterFame = 0; + } + } + } + } } namespace Server.Mobiles { - public class IharaSoko : BaseVendor - { - public override bool IsActiveVendor => false; - public override bool IsInvulnerable => true; - public override bool DisallowAllMoves => true; - public override bool ClickTitle => true; - public override bool CanTeach => false; - public override string DefaultName => "Ihara Soko"; + public class IharaSoko : BaseVendor + { + protected List m_SBInfos = new List(); - protected List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + [Constructible] + public IharaSoko() : base("the Imperial Minister of Trade") + { + Female = false; + Body = 0x190; + Hue = 0x8403; + } - public override void InitSBInfo() - { - } + public IharaSoko(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - AddItem( new Waraji( 0x711 ) ); - AddItem( new Backpack() ); - AddItem( new Kamishimo( 0x483 ) ); + public override bool IsActiveVendor => false; + public override bool IsInvulnerable => true; + public override bool DisallowAllMoves => true; + public override bool ClickTitle => true; + public override bool CanTeach => false; + public override string DefaultName => "Ihara Soko"; + protected override List SBInfos => m_SBInfos; - Item item = new LightPlateJingasa(); - item.Hue = 0x711; + public override void InitSBInfo() + { + } - AddItem( item ); - } + public override void InitOutfit() + { + AddItem(new Waraji(0x711)); + AddItem(new Backpack()); + AddItem(new Kamishimo(0x483)); - [Constructible] - public IharaSoko() : base( "the Imperial Minister of Trade" ) - { - Female = false; - Body = 0x190; - Hue = 0x8403; - } + Item item = new LightPlateJingasa(); + item.Hue = 0x711; - public IharaSoko( Serial serial ) : base( serial ) - { - } + AddItem(item); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override bool CanBeDamaged() - { - return false; - } + public override bool CanBeDamaged() + { + return false; + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m.Alive && m is PlayerMobile pm ) - { - int range = 3; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m.Alive && m is PlayerMobile pm) + { + int range = 3; - if ( pm.Alive && Math.Abs( Z - pm.Z ) < 16 && InRange( m, range ) && !InRange( oldLocation, range ) ) - { - if ( pm.ToTItemsTurnedIn >= TreasuresOfTokuno.ItemsPerReward ) - { - SayTo( pm, 1070980 ); // Congratulations! You have turned in enough minor treasures to earn a greater reward. + if (pm.Alive && Math.Abs(Z - pm.Z) < 16 && InRange(m, range) && !InRange(oldLocation, range)) + { + if (pm.ToTItemsTurnedIn >= TreasuresOfTokuno.ItemsPerReward) + { + SayTo(pm, + 1070980); // Congratulations! You have turned in enough minor treasures to earn a greater reward. - pm.CloseGump( typeof( ToTTurnInGump ) ); //Sanity + pm.CloseGump(typeof(ToTTurnInGump)); //Sanity - if ( !pm.HasGump( typeof( ToTRedeemGump ) ) ) - pm.SendGump( new ToTRedeemGump( this, false ) ); - } - else - { - if ( pm.ToTItemsTurnedIn == 0 ) - SayTo( pm, 1071013 ); // Bring me 10 of the lost treasures of Tokuno and I will reward you with a valuable item. - else - SayTo( pm, 1070981, $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. + if (!pm.HasGump(typeof(ToTRedeemGump))) + pm.SendGump(new ToTRedeemGump(this, false)); + } + else + { + if (pm.ToTItemsTurnedIn == 0) + SayTo(pm, + 1071013); // Bring me 10 of the lost treasures of Tokuno and I will reward you with a valuable item. + else + SayTo(pm, 1070981, + $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. - ArrayList buttons = ToTTurnInGump.FindRedeemableItems( pm ); + ArrayList buttons = ToTTurnInGump.FindRedeemableItems(pm); - if ( buttons.Count > 0 && !pm.HasGump( typeof( ToTTurnInGump ) ) ) - pm.SendGump( new ToTTurnInGump( this, buttons ) ); - } - } + if (buttons.Count > 0 && !pm.HasGump(typeof(ToTTurnInGump))) + pm.SendGump(new ToTTurnInGump(this, buttons)); + } + } - int leaveRange = 7; + int leaveRange = 7; - if ( !InRange( m, leaveRange ) && InRange( oldLocation, leaveRange ) ) - { - pm.CloseGump( typeof( ToTRedeemGump ) ); - pm.CloseGump( typeof( ToTTurnInGump ) ); - } - } - } + if (!InRange(m, leaveRange) && InRange(oldLocation, leaveRange)) + { + pm.CloseGump(typeof(ToTRedeemGump)); + pm.CloseGump(typeof(ToTTurnInGump)); + } + } + } - public override void TurnToTokuno(){} - } + public override void TurnToTokuno() + { + } + } } namespace Server.Gumps { - public class ItemTileButtonInfo : ImageTileButtonInfo - { - public Item Item { get; set; } + public class ItemTileButtonInfo : ImageTileButtonInfo + { + public ItemTileButtonInfo(Item i) : base(i.ItemID, i.Hue, + i.Name == null || i.Name.Length <= 0 ? (TextDefinition)i.LabelNumber : (TextDefinition)i.Name) + { + Item = i; + } - public ItemTileButtonInfo( Item i ) : base( i.ItemID, i.Hue, ((i.Name == null || i.Name.Length <= 0)? (TextDefinition)i.LabelNumber : (TextDefinition)i.Name ) ) - { - Item = i; - } - } + public Item Item{ get; set; } + } - public class ToTTurnInGump : BaseImageTileButtonsGump - { - public static ArrayList FindRedeemableItems( Mobile m ) - { - Backpack pack = (Backpack)m.Backpack; - if ( pack == null ) - return new ArrayList(); + public class ToTTurnInGump : BaseImageTileButtonsGump + { + private Mobile m_Collector; - ArrayList items = new ArrayList( pack.FindItemsByType( TreasuresOfTokuno.LesserArtifactsTotal ) ); - ArrayList buttons = new ArrayList(); + public ToTTurnInGump(Mobile collector, ArrayList buttons) : + base(1071012, buttons) // Click a minor artifact to give it to Ihara Soko. + { + m_Collector = collector; + } - for( int i = 0; i < items.Count; i++ ) - { - Item item = (Item)items[i]; - if ( item is ChestOfHeirlooms heirlooms && !heirlooms.Locked ) - continue; + public ToTTurnInGump(Mobile collector, ItemTileButtonInfo[] buttons) : + base(1071012, buttons) // Click a minor artifact to give it to Ihara Soko. + { + m_Collector = collector; + } - if ( item is ChestOfHeirlooms ofHeirlooms && ofHeirlooms.TrapLevel != 10 ) - continue; + public static ArrayList FindRedeemableItems(Mobile m) + { + Backpack pack = (Backpack)m.Backpack; + if (pack == null) + return new ArrayList(); - if ( item is PigmentsOfTokuno tokuno && tokuno.Type != PigmentType.None ) - continue; + ArrayList items = new ArrayList(pack.FindItemsByType(TreasuresOfTokuno.LesserArtifactsTotal)); + ArrayList buttons = new ArrayList(); - buttons.Add( new ItemTileButtonInfo( item ) ); - } + for (int i = 0; i < items.Count; i++) + { + Item item = (Item)items[i]; + if (item is ChestOfHeirlooms heirlooms && !heirlooms.Locked) + continue; - return buttons; - } + if (item is ChestOfHeirlooms ofHeirlooms && ofHeirlooms.TrapLevel != 10) + continue; - Mobile m_Collector; + if (item is PigmentsOfTokuno tokuno && tokuno.Type != PigmentType.None) + continue; - public ToTTurnInGump( Mobile collector, ArrayList buttons ) : base( 1071012, buttons ) // Click a minor artifact to give it to Ihara Soko. - { - m_Collector = collector; - } + buttons.Add(new ItemTileButtonInfo(item)); + } - public ToTTurnInGump( Mobile collector, ItemTileButtonInfo[] buttons ) : base( 1071012, buttons ) // Click a minor artifact to give it to Ihara Soko. - { - m_Collector = collector; - } + return buttons; + } - public override void HandleButtonResponse( NetState sender, int adjustedButton, ImageTileButtonInfo buttonInfo ) - { - PlayerMobile pm = sender.Mobile as PlayerMobile; + public override void HandleButtonResponse(NetState sender, int adjustedButton, ImageTileButtonInfo buttonInfo) + { + PlayerMobile pm = sender.Mobile as PlayerMobile; - Item item = ((ItemTileButtonInfo)buttonInfo).Item; + Item item = ((ItemTileButtonInfo)buttonInfo).Item; - if ( !( pm != null && item.IsChildOf( pm.Backpack ) && pm.InRange( m_Collector.Location, 7 )) ) - return; + if (!(pm != null && item.IsChildOf(pm.Backpack) && pm.InRange(m_Collector.Location, 7))) + return; - item.Delete(); + item.Delete(); - if ( ++pm.ToTItemsTurnedIn >= TreasuresOfTokuno.ItemsPerReward ) - { - m_Collector.SayTo( pm, 1070980 ); // Congratulations! You have turned in enough minor treasures to earn a greater reward. + if (++pm.ToTItemsTurnedIn >= TreasuresOfTokuno.ItemsPerReward) + { + m_Collector.SayTo(pm, + 1070980); // Congratulations! You have turned in enough minor treasures to earn a greater reward. - pm.CloseGump( typeof( ToTTurnInGump ) ); //Sanity + pm.CloseGump(typeof(ToTTurnInGump)); //Sanity - if ( !pm.HasGump( typeof( ToTRedeemGump ) ) ) - pm.SendGump( new ToTRedeemGump( m_Collector, false ) ); - } - else - { - m_Collector.SayTo( pm, 1070981, $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. + if (!pm.HasGump(typeof(ToTRedeemGump))) + pm.SendGump(new ToTRedeemGump(m_Collector, false)); + } + else + { + m_Collector.SayTo(pm, 1070981, + $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. - ArrayList buttons = FindRedeemableItems( pm ); + ArrayList buttons = FindRedeemableItems(pm); - pm.CloseGump( typeof( ToTTurnInGump ) ); //Sanity + pm.CloseGump(typeof(ToTTurnInGump)); //Sanity - if ( buttons.Count > 0 ) - pm.SendGump( new ToTTurnInGump( m_Collector, buttons ) ); - } - } + if (buttons.Count > 0) + pm.SendGump(new ToTTurnInGump(m_Collector, buttons)); + } + } - public override void HandleCancel( NetState sender ) - { - if ( !(sender.Mobile is PlayerMobile pm) || !pm.InRange( m_Collector.Location, 7 ) ) - return; + public override void HandleCancel(NetState sender) + { + if (!(sender.Mobile is PlayerMobile pm) || !pm.InRange(m_Collector.Location, 7)) + return; - if ( pm.ToTItemsTurnedIn == 0 ) - m_Collector.SayTo( pm, 1071013 ); // Bring me 10 of the lost treasures of Tokuno and I will reward you with a valuable item. - else if ( pm.ToTItemsTurnedIn < TreasuresOfTokuno.ItemsPerReward ) //This case should ALWAYS be true with this gump, jsut a sanity check - m_Collector.SayTo( pm, 1070981, $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. - else - m_Collector.SayTo( pm, 1070982 ); // When you wish to choose your reward, you have but to approach me again. - } - - } + if (pm.ToTItemsTurnedIn == 0) + m_Collector.SayTo(pm, + 1071013); // Bring me 10 of the lost treasures of Tokuno and I will reward you with a valuable item. + else if (pm.ToTItemsTurnedIn < TreasuresOfTokuno.ItemsPerReward + ) //This case should ALWAYS be true with this gump, jsut a sanity check + m_Collector.SayTo(pm, 1070981, + $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. + else + m_Collector.SayTo(pm, 1070982); // When you wish to choose your reward, you have but to approach me again. + } + } } namespace Server.Gumps { - public class ToTRedeemGump : BaseImageTileButtonsGump - { - public class TypeTileButtonInfo : ImageTileButtonInfo - { - public Type Type { get; } + public class ToTRedeemGump : BaseImageTileButtonsGump + { + private Mobile m_Collector; - public TypeTileButtonInfo( Type type, int itemID, int hue, TextDefinition label, int localizedToolTip ) : base( itemID, hue, label, localizedToolTip ) - { - Type = type; - } + public ToTRedeemGump(Mobile collector, bool pigments) : base(pigments ? 1070986 : 1070985, + pigments + ? PigmentRewards[(int)TreasuresOfTokuno.RewardEra - 1] + : (ImageTileButtonInfo[])NormalRewards[(int)TreasuresOfTokuno.RewardEra - 1]) + { + m_Collector = collector; + } - public TypeTileButtonInfo( Type type, int itemID, TextDefinition label ) : this( type, itemID, 0, label, -1 ) - { - } + public static TypeTileButtonInfo[][] NormalRewards{ get; } = + { + // ToT One Rewards + new[] + { + new TypeTileButtonInfo(typeof(SwordsOfProsperity), 0x27A9, 1070963, 1071002), + new TypeTileButtonInfo(typeof(SwordOfTheStampede), 0x27A2, 1070964, 1070978), + new TypeTileButtonInfo(typeof(WindsEdge), 0x27A3, 1070965, 1071003), + new TypeTileButtonInfo(typeof(DarkenedSky), 0x27AD, 1070966, 1071004), + new TypeTileButtonInfo(typeof(TheHorselord), 0x27A5, 1070967, 1071005), + new TypeTileButtonInfo(typeof(RuneBeetleCarapace), 0x277D, 1070968, 1071006), + new TypeTileButtonInfo(typeof(KasaOfTheRajin), 0x2798, 1070969, 1071007), + new TypeTileButtonInfo(typeof(Stormgrip), 0x2792, 1070970, 1071008), + new TypeTileButtonInfo(typeof(TomeOfLostKnowledge), 0x0EFA, 0x530, 1070971, 1071009), + new TypeTileButtonInfo(typeof(PigmentsOfTokuno), 0x0EFF, 1070933, 1071011) + }, + // ToT Two Rewards + new[] + { + new TypeTileButtonInfo(typeof(SwordsOfProsperity), 0x27A9, 1070963, 1071002), + new TypeTileButtonInfo(typeof(SwordOfTheStampede), 0x27A2, 1070964, 1070978), + new TypeTileButtonInfo(typeof(WindsEdge), 0x27A3, 1070965, 1071003), + new TypeTileButtonInfo(typeof(DarkenedSky), 0x27AD, 1070966, 1071004), + new TypeTileButtonInfo(typeof(TheHorselord), 0x27A5, 1070967, 1071005), + new TypeTileButtonInfo(typeof(RuneBeetleCarapace), 0x277D, 1070968, 1071006), + new TypeTileButtonInfo(typeof(KasaOfTheRajin), 0x2798, 1070969, 1071007), + new TypeTileButtonInfo(typeof(Stormgrip), 0x2792, 1070970, 1071008), + new TypeTileButtonInfo(typeof(TomeOfLostKnowledge), 0x0EFA, 0x530, 1070971, 1071009), + new TypeTileButtonInfo(typeof(PigmentsOfTokuno), 0x0EFF, 1070933, 1071011) + }, + // ToT Three Rewards + new[] + { + new TypeTileButtonInfo(typeof(SwordsOfProsperity), 0x27A9, 1070963, 1071002), + new TypeTileButtonInfo(typeof(SwordOfTheStampede), 0x27A2, 1070964, 1070978), + new TypeTileButtonInfo(typeof(WindsEdge), 0x27A3, 1070965, 1071003), + new TypeTileButtonInfo(typeof(DarkenedSky), 0x27AD, 1070966, 1071004), + new TypeTileButtonInfo(typeof(TheHorselord), 0x27A5, 1070967, 1071005), + new TypeTileButtonInfo(typeof(RuneBeetleCarapace), 0x277D, 1070968, 1071006), + new TypeTileButtonInfo(typeof(KasaOfTheRajin), 0x2798, 1070969, 1071007), + new TypeTileButtonInfo(typeof(Stormgrip), 0x2792, 1070970, 1071008), + new TypeTileButtonInfo(typeof(TomeOfLostKnowledge), 0x0EFA, 0x530, 1070971, 1071009) + } + }; - public TypeTileButtonInfo( Type type, int itemID, TextDefinition label, int localizedToolTip ) : this( type, itemID, 0, label, localizedToolTip ) - { - } - } + public static PigmentsTileButtonInfo[][] PigmentRewards{ get; } = + { + // ToT One Pigment Rewards + new[] + { + new PigmentsTileButtonInfo(PigmentType.ParagonGold), + new PigmentsTileButtonInfo(PigmentType.VioletCouragePurple), + new PigmentsTileButtonInfo(PigmentType.InvulnerabilityBlue), + new PigmentsTileButtonInfo(PigmentType.LunaWhite), + new PigmentsTileButtonInfo(PigmentType.DryadGreen), + new PigmentsTileButtonInfo(PigmentType.ShadowDancerBlack), + new PigmentsTileButtonInfo(PigmentType.BerserkerRed), + new PigmentsTileButtonInfo(PigmentType.NoxGreen), + new PigmentsTileButtonInfo(PigmentType.RumRed), + new PigmentsTileButtonInfo(PigmentType.FireOrange) + }, + // ToT Two Pigment Rewards + new[] + { + new PigmentsTileButtonInfo(PigmentType.FadedCoal), + new PigmentsTileButtonInfo(PigmentType.Coal), + new PigmentsTileButtonInfo(PigmentType.FadedGold), + new PigmentsTileButtonInfo(PigmentType.StormBronze), + new PigmentsTileButtonInfo(PigmentType.Rose), + new PigmentsTileButtonInfo(PigmentType.MidnightCoal), + new PigmentsTileButtonInfo(PigmentType.FadedBronze), + new PigmentsTileButtonInfo(PigmentType.FadedRose), + new PigmentsTileButtonInfo(PigmentType.DeepRose) + }, + // ToT Three Pigment Rewards + new[] + { + new PigmentsTileButtonInfo(PigmentType.ParagonGold), + new PigmentsTileButtonInfo(PigmentType.VioletCouragePurple), + new PigmentsTileButtonInfo(PigmentType.InvulnerabilityBlue), + new PigmentsTileButtonInfo(PigmentType.LunaWhite), + new PigmentsTileButtonInfo(PigmentType.DryadGreen), + new PigmentsTileButtonInfo(PigmentType.ShadowDancerBlack), + new PigmentsTileButtonInfo(PigmentType.BerserkerRed), + new PigmentsTileButtonInfo(PigmentType.NoxGreen), + new PigmentsTileButtonInfo(PigmentType.RumRed), + new PigmentsTileButtonInfo(PigmentType.FireOrange) + } + }; - public class PigmentsTileButtonInfo : ImageTileButtonInfo - { - public PigmentType Pigment { get; set; } + public override void HandleButtonResponse(NetState sender, int adjustedButton, ImageTileButtonInfo buttonInfo) + { + if (!(sender.Mobile is PlayerMobile pm) || !pm.InRange(m_Collector.Location, 7) || + !(pm.ToTItemsTurnedIn >= TreasuresOfTokuno.ItemsPerReward)) + return; - public PigmentsTileButtonInfo( PigmentType p ) : base( 0xEFF, PigmentsOfTokuno.GetInfo( p )[0], PigmentsOfTokuno.GetInfo( p )[1] ) - { - Pigment = p; - } - } + bool pigments = buttonInfo is PigmentsTileButtonInfo; - #region ToT Normal Rewards Table + Item item = null; - #endregion + if (pigments) + { + PigmentsTileButtonInfo p = (PigmentsTileButtonInfo)buttonInfo; - public static TypeTileButtonInfo[][] NormalRewards { get; } = - { - // ToT One Rewards - new[] { - new TypeTileButtonInfo( typeof( SwordsOfProsperity ), 0x27A9, 1070963, 1071002 ), - new TypeTileButtonInfo( typeof( SwordOfTheStampede ), 0x27A2, 1070964, 1070978 ), - new TypeTileButtonInfo( typeof( WindsEdge ), 0x27A3, 1070965, 1071003 ), - new TypeTileButtonInfo( typeof( DarkenedSky ), 0x27AD, 1070966, 1071004 ), - new TypeTileButtonInfo( typeof( TheHorselord ), 0x27A5, 1070967, 1071005 ), - new TypeTileButtonInfo( typeof( RuneBeetleCarapace ), 0x277D, 1070968, 1071006 ), - new TypeTileButtonInfo( typeof( KasaOfTheRajin ), 0x2798, 1070969, 1071007 ), - new TypeTileButtonInfo( typeof( Stormgrip ), 0x2792, 1070970, 1071008 ), - new TypeTileButtonInfo( typeof( TomeOfLostKnowledge ), 0x0EFA, 0x530, 1070971, 1071009 ), - new TypeTileButtonInfo( typeof( PigmentsOfTokuno ), 0x0EFF, 1070933, 1071011 ) - }, - // ToT Two Rewards - new[] { - new TypeTileButtonInfo( typeof( SwordsOfProsperity ), 0x27A9, 1070963, 1071002 ), - new TypeTileButtonInfo( typeof( SwordOfTheStampede ), 0x27A2, 1070964, 1070978 ), - new TypeTileButtonInfo( typeof( WindsEdge ), 0x27A3, 1070965, 1071003 ), - new TypeTileButtonInfo( typeof( DarkenedSky ), 0x27AD, 1070966, 1071004 ), - new TypeTileButtonInfo( typeof( TheHorselord ), 0x27A5, 1070967, 1071005 ), - new TypeTileButtonInfo( typeof( RuneBeetleCarapace ), 0x277D, 1070968, 1071006 ), - new TypeTileButtonInfo( typeof( KasaOfTheRajin ), 0x2798, 1070969, 1071007 ), - new TypeTileButtonInfo( typeof( Stormgrip ), 0x2792, 1070970, 1071008 ), - new TypeTileButtonInfo( typeof( TomeOfLostKnowledge ), 0x0EFA, 0x530, 1070971, 1071009 ), - new TypeTileButtonInfo( typeof( PigmentsOfTokuno ), 0x0EFF, 1070933, 1071011 ) - }, - // ToT Three Rewards - new[] { - new TypeTileButtonInfo( typeof( SwordsOfProsperity ), 0x27A9, 1070963, 1071002 ), - new TypeTileButtonInfo( typeof( SwordOfTheStampede ), 0x27A2, 1070964, 1070978 ), - new TypeTileButtonInfo( typeof( WindsEdge ), 0x27A3, 1070965, 1071003 ), - new TypeTileButtonInfo( typeof( DarkenedSky ), 0x27AD, 1070966, 1071004 ), - new TypeTileButtonInfo( typeof( TheHorselord ), 0x27A5, 1070967, 1071005 ), - new TypeTileButtonInfo( typeof( RuneBeetleCarapace ), 0x277D, 1070968, 1071006 ), - new TypeTileButtonInfo( typeof( KasaOfTheRajin ), 0x2798, 1070969, 1071007 ), - new TypeTileButtonInfo( typeof( Stormgrip ), 0x2792, 1070970, 1071008 ), - new TypeTileButtonInfo( typeof( TomeOfLostKnowledge ), 0x0EFA, 0x530, 1070971, 1071009 ) - } - }; + item = new PigmentsOfTokuno(p.Pigment); + } + else + { + TypeTileButtonInfo t = buttonInfo as TypeTileButtonInfo; - #region ToT Pigment Rewards Table + if (t.Type == typeof(PigmentsOfTokuno)) //Special case of course. + { + pm.CloseGump(typeof(ToTTurnInGump)); //Sanity + pm.CloseGump(typeof(ToTRedeemGump)); - #endregion + pm.SendGump(new ToTRedeemGump(m_Collector, true)); - public static PigmentsTileButtonInfo[][] PigmentRewards { get; } = - { - // ToT One Pigment Rewards - new[] { - new PigmentsTileButtonInfo( PigmentType.ParagonGold ), - new PigmentsTileButtonInfo( PigmentType.VioletCouragePurple ), - new PigmentsTileButtonInfo( PigmentType.InvulnerabilityBlue ), - new PigmentsTileButtonInfo( PigmentType.LunaWhite ), - new PigmentsTileButtonInfo( PigmentType.DryadGreen ), - new PigmentsTileButtonInfo( PigmentType.ShadowDancerBlack ), - new PigmentsTileButtonInfo( PigmentType.BerserkerRed ), - new PigmentsTileButtonInfo( PigmentType.NoxGreen ), - new PigmentsTileButtonInfo( PigmentType.RumRed ), - new PigmentsTileButtonInfo( PigmentType.FireOrange ) - }, - // ToT Two Pigment Rewards - new[] { - new PigmentsTileButtonInfo( PigmentType.FadedCoal ), - new PigmentsTileButtonInfo( PigmentType.Coal ), - new PigmentsTileButtonInfo( PigmentType.FadedGold ), - new PigmentsTileButtonInfo( PigmentType.StormBronze ), - new PigmentsTileButtonInfo( PigmentType.Rose ), - new PigmentsTileButtonInfo( PigmentType.MidnightCoal ), - new PigmentsTileButtonInfo( PigmentType.FadedBronze ), - new PigmentsTileButtonInfo( PigmentType.FadedRose ), - new PigmentsTileButtonInfo( PigmentType.DeepRose ) - }, - // ToT Three Pigment Rewards - new[] { - new PigmentsTileButtonInfo( PigmentType.ParagonGold ), - new PigmentsTileButtonInfo( PigmentType.VioletCouragePurple ), - new PigmentsTileButtonInfo( PigmentType.InvulnerabilityBlue ), - new PigmentsTileButtonInfo( PigmentType.LunaWhite ), - new PigmentsTileButtonInfo( PigmentType.DryadGreen ), - new PigmentsTileButtonInfo( PigmentType.ShadowDancerBlack ), - new PigmentsTileButtonInfo( PigmentType.BerserkerRed ), - new PigmentsTileButtonInfo( PigmentType.NoxGreen ), - new PigmentsTileButtonInfo( PigmentType.RumRed ), - new PigmentsTileButtonInfo( PigmentType.FireOrange ) - } - }; + return; + } - private Mobile m_Collector; + try + { + item = (Item)Activator.CreateInstance(t.Type); + } + catch + { + } + } - public ToTRedeemGump( Mobile collector, bool pigments ) : base( pigments ? 1070986 : 1070985, pigments ? (ImageTileButtonInfo[])PigmentRewards[(int)TreasuresOfTokuno.RewardEra-1] : (ImageTileButtonInfo[])NormalRewards[(int)TreasuresOfTokuno.RewardEra-1] ) - { - m_Collector = collector; - } + if (item == null) + return; //Sanity - public override void HandleButtonResponse( NetState sender, int adjustedButton, ImageTileButtonInfo buttonInfo ) - { - if ( !(sender.Mobile is PlayerMobile pm) || !pm.InRange( m_Collector.Location, 7 ) || !(pm.ToTItemsTurnedIn >= TreasuresOfTokuno.ItemsPerReward) ) - return; - - bool pigments = (buttonInfo is PigmentsTileButtonInfo); - - Item item = null; - - if ( pigments ) - { - PigmentsTileButtonInfo p = (PigmentsTileButtonInfo) buttonInfo; - - item = new PigmentsOfTokuno( p.Pigment ); - } - else - { - TypeTileButtonInfo t = buttonInfo as TypeTileButtonInfo; - - if ( t.Type == typeof( PigmentsOfTokuno ) ) //Special case of course. - { - pm.CloseGump( typeof( ToTTurnInGump ) ); //Sanity - pm.CloseGump( typeof( ToTRedeemGump ) ); - - pm.SendGump( new ToTRedeemGump( m_Collector, true ) ); - - return; - } - - try - { - item = (Item)Activator.CreateInstance( t.Type ); - } - catch { } - } - - if ( item == null ) - return; //Sanity - - if ( pm.AddToBackpack( item ) ) - { - pm.ToTItemsTurnedIn -= TreasuresOfTokuno.ItemsPerReward; - m_Collector.SayTo( pm, 1070984, (item.Name == null || item.Name.Length <= 0)? $"#{item.LabelNumber}" : item.Name ); // You have earned the gratitude of the Empire. I have placed the ~1_OBJTYPE~ in your backpack. - } - else - { - item.Delete(); - m_Collector.SayTo( pm, 500722 ); // You don't have enough room in your backpack! - m_Collector.SayTo( pm, 1070982 ); // When you wish to choose your reward, you have but to approach me again. - } - } + if (pm.AddToBackpack(item)) + { + pm.ToTItemsTurnedIn -= TreasuresOfTokuno.ItemsPerReward; + m_Collector.SayTo(pm, 1070984, + item.Name == null || item.Name.Length <= 0 + ? $"#{item.LabelNumber}" + : item.Name); // You have earned the gratitude of the Empire. I have placed the ~1_OBJTYPE~ in your backpack. + } + else + { + item.Delete(); + m_Collector.SayTo(pm, 500722); // You don't have enough room in your backpack! + m_Collector.SayTo(pm, 1070982); // When you wish to choose your reward, you have but to approach me again. + } + } - public override void HandleCancel( NetState sender ) - { - if ( !(sender.Mobile is PlayerMobile pm) || !pm.InRange( m_Collector.Location, 7 ) ) - return; + public override void HandleCancel(NetState sender) + { + if (!(sender.Mobile is PlayerMobile pm) || !pm.InRange(m_Collector.Location, 7)) + return; - if ( pm.ToTItemsTurnedIn == 0 ) - m_Collector.SayTo( pm, 1071013 ); // Bring me 10 of the lost treasures of Tokuno and I will reward you with a valuable item. - else if ( pm.ToTItemsTurnedIn < TreasuresOfTokuno.ItemsPerReward ) //This and above case should ALWAYS be FALSE with this gump, jsut a sanity check - m_Collector.SayTo( pm, 1070981, $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. - else - m_Collector.SayTo( pm, 1070982 ); // When you wish to choose your reward, you have but to approach me again. + if (pm.ToTItemsTurnedIn == 0) + m_Collector.SayTo(pm, + 1071013); // Bring me 10 of the lost treasures of Tokuno and I will reward you with a valuable item. + else if (pm.ToTItemsTurnedIn < TreasuresOfTokuno.ItemsPerReward + ) //This and above case should ALWAYS be FALSE with this gump, jsut a sanity check + m_Collector.SayTo(pm, 1070981, + $"{pm.ToTItemsTurnedIn}\t{TreasuresOfTokuno.ItemsPerReward}"); // You have turned in ~1_COUNT~ minor artifacts. Turn in ~2_NUM~ to receive a reward. + else + m_Collector.SayTo(pm, 1070982); // When you wish to choose your reward, you have but to approach me again. + } - } - } + public class TypeTileButtonInfo : ImageTileButtonInfo + { + public TypeTileButtonInfo(Type type, int itemID, int hue, TextDefinition label, int localizedToolTip) : base( + itemID, hue, label, localizedToolTip) + { + Type = type; + } + + public TypeTileButtonInfo(Type type, int itemID, TextDefinition label) : this(type, itemID, 0, label, -1) + { + } + + public TypeTileButtonInfo(Type type, int itemID, TextDefinition label, int localizedToolTip) : this(type, itemID, + 0, label, localizedToolTip) + { + } + + public Type Type{ get; } + } + + public class PigmentsTileButtonInfo : ImageTileButtonInfo + { + public PigmentsTileButtonInfo(PigmentType p) : base(0xEFF, PigmentsOfTokuno.GetInfo(p)[0], + PigmentsOfTokuno.GetInfo(p)[1]) + { + Pigment = p; + } + + public PigmentType Pigment{ get; set; } + } + + #region ToT Normal Rewards Table + + #endregion + + #region ToT Pigment Rewards Table + + #endregion + } } /* Notes @@ -577,4 +634,4 @@ Pigments of tokuno do NOT check for if item is already hued 0; APPARENTLY he st Chest of Heirlooms don't show if unlocked. Chest of heirlooms, locked, HARD to pick at 100 lock picking but not impossible. had 95 health to 0, cause it's trapped >< (explosion i think) -*/ +*/ \ No newline at end of file diff --git a/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokunoPersistance.cs b/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokunoPersistance.cs index b41e213d1..74f50b64a 100644 --- a/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokunoPersistance.cs +++ b/Scripts/Engines/Treasures of Tokuno/TreasuresOfTokunoPersistance.cs @@ -1,62 +1,62 @@ namespace Server.Misc { - public class TreasuresOfTokunoPersistance : Item - { - public static TreasuresOfTokunoPersistance Instance { get; private set; } + public class TreasuresOfTokunoPersistance : Item + { + public TreasuresOfTokunoPersistance() : base(1) + { + Movable = false; - public override string DefaultName => "TreasuresOfTokuno Persistance - Internal"; + if (Instance == null || Instance.Deleted) + Instance = this; + else + base.Delete(); + } - public static void Initialize() - { - if ( Instance == null ) - new TreasuresOfTokunoPersistance(); - } + public TreasuresOfTokunoPersistance(Serial serial) : base(serial) + { + Instance = this; + } - public TreasuresOfTokunoPersistance() : base( 1 ) - { - Movable = false; + public static TreasuresOfTokunoPersistance Instance{ get; private set; } - if ( Instance == null || Instance.Deleted ) - Instance = this; - else - base.Delete(); - } + public override string DefaultName => "TreasuresOfTokuno Persistance - Internal"; - public TreasuresOfTokunoPersistance( Serial serial ) : base( serial ) - { - Instance = this; - } + public static void Initialize() + { + if (Instance == null) + new TreasuresOfTokunoPersistance(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.WriteEncodedInt( (int)TreasuresOfTokuno.RewardEra ); - writer.WriteEncodedInt( (int)TreasuresOfTokuno.DropEra ); - } + writer.WriteEncodedInt((int)TreasuresOfTokuno.RewardEra); + writer.WriteEncodedInt((int)TreasuresOfTokuno.DropEra); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - TreasuresOfTokuno.RewardEra = (TreasuresOfTokunoEra)reader.ReadEncodedInt(); - TreasuresOfTokuno.DropEra = (TreasuresOfTokunoEra)reader.ReadEncodedInt(); - - break; - } - } - } + switch (version) + { + case 0: + { + TreasuresOfTokuno.RewardEra = (TreasuresOfTokunoEra)reader.ReadEncodedInt(); + TreasuresOfTokuno.DropEra = (TreasuresOfTokunoEra)reader.ReadEncodedInt(); - public override void Delete() - { - } - } -} + break; + } + } + } + + public override void Delete() + { + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatue.cs b/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatue.cs index 73bb9c8fd..3909ec5e3 100644 --- a/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatue.cs +++ b/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatue.cs @@ -1,635 +1,670 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Gumps; -using Server.Items; -using Server.Spells; -using Server.Multis; -using Server.Network; -using Server.Targeting; using Server.Accounting; using Server.ContextMenus; using Server.Engines.VeteranRewards; +using Server.Gumps; +using Server.Items; +using Server.Multis; +using Server.Network; +using Server.Spells; +using Server.Targeting; namespace Server.Mobiles { - public enum StatueType - { - Marble, - Jade, - Bronze - } - - public enum StatuePose - { - Ready, - Casting, - Salute, - AllPraiseMe, - Fighting, - HandsOnHips - } - - public enum StatueMaterial - { - Antique, - Dark, - Medium, - Light - } - - public class CharacterStatue : Mobile, IRewardItem - { - private StatueType m_Type; - private StatuePose m_Pose; - private StatueMaterial m_Material; - - [CommandProperty( AccessLevel.GameMaster )] - public StatueType StatueType - { - get => m_Type; - set { m_Type = value; InvalidateHues(); InvalidatePose(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public StatuePose Pose - { - get => m_Pose; - set { m_Pose = value; InvalidatePose(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public StatueMaterial Material - { - get => m_Material; - set { m_Material = value; InvalidateHues(); InvalidatePose(); } - } - - private Mobile m_SculptedBy; - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile SculptedBy - { - get => m_SculptedBy; - set{ m_SculptedBy = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime SculptedOn { get; set; } - - public CharacterStatuePlinth Plinth { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } - - public CharacterStatue( Mobile from, StatueType type ) - { - m_Type = type; - m_Pose = StatuePose.Ready; - m_Material = StatueMaterial.Antique; - - Direction = Direction.South; - AccessLevel = AccessLevel.Counselor; - Hits = HitsMax; - Blessed = true; - Frozen = true; - - CloneBody( from ); - CloneClothes( from ); - InvalidateHues(); - } - - public CharacterStatue( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - DisplayPaperdollTo( from ); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_SculptedBy != null ) - { - if ( m_SculptedBy.ShowFameTitle && ( m_SculptedBy.Player || m_SculptedBy.Body.IsHuman ) && m_SculptedBy.Fame >= 10000 ) - list.Add( 1076202, $"{(m_SculptedBy.Female ? "Lady" : "Lord")} {m_SculptedBy.Name}"); // Sculpted by ~1_Name~ - else - list.Add( 1076202, m_SculptedBy.Name ); // Sculpted by ~1_Name~ - } - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.Alive && m_SculptedBy != null ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( ( house != null && house.IsCoOwner( from ) ) || (int) from.AccessLevel > (int) AccessLevel.Counselor ) - list.Add( new DemolishEntry( this ) ); - } - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - if ( Plinth != null && !Plinth.Deleted ) - Plinth.Delete(); - } - - protected override void OnMapChange( Map oldMap ) - { - InvalidatePose(); - - if ( Plinth != null ) - Plinth.Map = Map; - } - - protected override void OnLocationChange( Point3D oldLocation ) - { - InvalidatePose(); - - if ( Plinth != null ) - Plinth.Location = new Point3D( X, Y, Z - 5 ); - } + public enum StatueType + { + Marble, + Jade, + Bronze + } + + public enum StatuePose + { + Ready, + Casting, + Salute, + AllPraiseMe, + Fighting, + HandsOnHips + } + + public enum StatueMaterial + { + Antique, + Dark, + Medium, + Light + } + + public class CharacterStatue : Mobile, IRewardItem + { + private int m_Animation; + private int m_Frames; + private StatueMaterial m_Material; + private StatuePose m_Pose; + + private Mobile m_SculptedBy; + private StatueType m_Type; + + public CharacterStatue(Mobile from, StatueType type) + { + m_Type = type; + m_Pose = StatuePose.Ready; + m_Material = StatueMaterial.Antique; + + Direction = Direction.South; + AccessLevel = AccessLevel.Counselor; + Hits = HitsMax; + Blessed = true; + Frozen = true; + + CloneBody(from); + CloneClothes(from); + InvalidateHues(); + } + + public CharacterStatue(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public StatueType StatueType + { + get => m_Type; + set + { + m_Type = value; + InvalidateHues(); + InvalidatePose(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public StatuePose Pose + { + get => m_Pose; + set + { + m_Pose = value; + InvalidatePose(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public StatueMaterial Material + { + get => m_Material; + set + { + m_Material = value; + InvalidateHues(); + InvalidatePose(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile SculptedBy + { + get => m_SculptedBy; + set + { + m_SculptedBy = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime SculptedOn{ get; set; } + + public CharacterStatuePlinth Plinth{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } + + public override void OnDoubleClick(Mobile from) + { + DisplayPaperdollTo(from); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_SculptedBy != null) + { + if (m_SculptedBy.ShowFameTitle && (m_SculptedBy.Player || m_SculptedBy.Body.IsHuman) && + m_SculptedBy.Fame >= 10000) + list.Add(1076202, + $"{(m_SculptedBy.Female ? "Lady" : "Lord")} {m_SculptedBy.Name}"); // Sculpted by ~1_Name~ + else + list.Add(1076202, m_SculptedBy.Name); // Sculpted by ~1_Name~ + } + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.Alive && m_SculptedBy != null) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsCoOwner(from) || (int)from.AccessLevel > (int)AccessLevel.Counselor) + list.Add(new DemolishEntry(this)); + } + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + if (Plinth != null && !Plinth.Deleted) + Plinth.Delete(); + } + + protected override void OnMapChange(Map oldMap) + { + InvalidatePose(); + + if (Plinth != null) + Plinth.Map = Map; + } + + protected override void OnLocationChange(Point3D oldLocation) + { + InvalidatePose(); + + if (Plinth != null) + Plinth.Location = new Point3D(X, Y, Z - 5); + } + + public override bool CanBeRenamedBy(Mobile from) + { + return false; + } + + public override bool CanBeDamaged() + { + return false; + } + + public void OnRequestedAnimation(Mobile from) + { + from.Send(new UpdateStatueAnimation(this, 1, m_Animation, m_Frames)); + } + + public override void OnAosSingleClick(Mobile from) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override bool CanBeRenamedBy( Mobile from ) - { - return false; - } + writer.WriteEncodedInt(0); // version + + writer.Write((int)m_Type); + writer.Write((int)m_Pose); + writer.Write((int)m_Material); - public override bool CanBeDamaged() - { - return false; - } + writer.Write(m_SculptedBy); + writer.Write(SculptedOn); - public void OnRequestedAnimation( Mobile from ) - { - from.Send( new UpdateStatueAnimation( this, 1, m_Animation, m_Frames ) ); - } + writer.Write(Plinth); + writer.Write(IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnAosSingleClick( Mobile from ) - { - } + int version = reader.ReadEncodedInt(); + + m_Type = (StatueType)reader.ReadInt(); + m_Pose = (StatuePose)reader.ReadInt(); + m_Material = (StatueMaterial)reader.ReadInt(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - - writer.Write( (int) m_Type ); - writer.Write( (int) m_Pose ); - writer.Write( (int) m_Material ); - - writer.Write( (Mobile) m_SculptedBy ); - writer.Write( (DateTime) SculptedOn ); - - writer.Write( (Item) Plinth ); - writer.Write( (bool) IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Type = (StatueType) reader.ReadInt(); - m_Pose = (StatuePose) reader.ReadInt(); - m_Material = (StatueMaterial) reader.ReadInt(); - - m_SculptedBy = reader.ReadMobile(); - SculptedOn = reader.ReadDateTime(); + m_SculptedBy = reader.ReadMobile(); + SculptedOn = reader.ReadDateTime(); - Plinth = reader.ReadItem() as CharacterStatuePlinth; - IsRewardItem = reader.ReadBool(); + Plinth = reader.ReadItem() as CharacterStatuePlinth; + IsRewardItem = reader.ReadBool(); - InvalidatePose(); + InvalidatePose(); - Frozen = true; + Frozen = true; - if ( m_SculptedBy == null || Map == Map.Internal ) // Remove preview statues - { - Timer.DelayCall( TimeSpan.Zero, Delete ); - } - } + if (m_SculptedBy == null || Map == Map.Internal) // Remove preview statues + Timer.DelayCall(TimeSpan.Zero, Delete); + } - public void Sculpt( Mobile by ) - { - m_SculptedBy = by; - SculptedOn = DateTime.UtcNow; + public void Sculpt(Mobile by) + { + m_SculptedBy = by; + SculptedOn = DateTime.UtcNow; - InvalidateProperties(); - } - - public bool Demolish( Mobile by ) - { - CharacterStatueDeed deed = new CharacterStatueDeed( null ); - - if ( by.PlaceInBackpack( deed ) ) - { - Delete(); - - deed.Statue = this; - deed.StatueType = m_Type; - deed.IsRewardItem = IsRewardItem; - - Plinth?.Delete(); - - return true; - } - - @by.SendLocalizedMessage( 500720 ); // You don't have enough room in your backpack! - deed.Delete(); - - return false; - } - - public void Restore( CharacterStatue from ) - { - m_Material = from.Material; - m_Pose = from.Pose; - - Direction = from.Direction; - - CloneBody( from ); - CloneClothes( from ); - - InvalidateHues(); - InvalidatePose(); - } - - public void CloneBody( Mobile from ) - { - Name = from.Name; - BodyValue = from.BodyValue; - Female = from.Female; - HairItemID = from.HairItemID; - FacialHairItemID = from.FacialHairItemID; - } - - public void CloneClothes( Mobile from ) - { - for ( int i = Items.Count - 1; i >= 0; i -- ) - Items[ i ].Delete(); - - for ( int i = from.Items.Count - 1; i >= 0; i -- ) - { - Item item = from.Items[ i ]; - - if ( item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank ) - AddItem( CloneItem( item ) ); - } - } - - public Item CloneItem( Item item ) - { - Item cloned = new Item( item.ItemID ); - cloned.Layer = item.Layer; - cloned.Name = item.Name; - cloned.Hue = item.Hue; - cloned.Weight = item.Weight; - cloned.Movable = false; - - return cloned; - } - - public void InvalidateHues() - { - Hue = 0xB8F + (int) m_Type * 4 + (int) m_Material; - - HairHue = Hue; - - if ( FacialHairItemID > 0 ) - FacialHairHue = Hue; - - for ( int i = Items.Count - 1; i >= 0; i -- ) - Items[ i ].Hue = Hue; - - Plinth?.InvalidateHue(); - } - - private int m_Animation; - private int m_Frames; - - public void InvalidatePose() - { - switch ( m_Pose ) - { - case StatuePose.Ready: - m_Animation = 4; - m_Frames = 0; - break; - case StatuePose.Casting: - m_Animation = 16; - m_Frames = 2; - break; - case StatuePose.Salute: - m_Animation = 33; - m_Frames = 1; - break; - case StatuePose.AllPraiseMe: - m_Animation = 17; - m_Frames = 4; - break; - case StatuePose.Fighting: - m_Animation = 31; - m_Frames = 5; - break; - case StatuePose.HandsOnHips: - m_Animation = 6; - m_Frames = 1; - break; - } - - if ( Map != null ) - { - ProcessDelta(); - - Packet p = null; - - IPooledEnumerable eable = Map.GetClientsInRange( Location ); - - foreach( NetState state in eable ) - { - state.Mobile.ProcessDelta(); - - if ( p == null ) - p = Packet.Acquire( new UpdateStatueAnimation( this, 1, m_Animation, m_Frames ) ); - - state.Send( p ); - } - - Packet.Release( p ); - - eable.Free(); - } - } - - private class DemolishEntry : ContextMenuEntry - { - private CharacterStatue m_Statue; - - public DemolishEntry( CharacterStatue statue ) : base( 6275, 2 ) - { - m_Statue = statue; - } - - public override void OnClick() - { - if ( m_Statue.Deleted ) - return; - - m_Statue.Demolish( Owner.From ); - } - } - } - - public class CharacterStatueDeed : Item, IRewardItem - { - public override int LabelNumber - { - get - { - StatueType t = m_Type; - - if ( Statue != null ) - { - t = Statue.StatueType; - } - - switch ( t ) - { - case StatueType.Marble: return 1076189; - case StatueType.Jade: return 1076188; - case StatueType.Bronze: return 1076190; - default: return 1076173; - } - } - } - - private StatueType m_Type; - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public CharacterStatue Statue { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public StatueType StatueType - { - get - { - if ( Statue != null ) - return Statue.StatueType; - - return m_Type; - } - set => m_Type = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - public CharacterStatueDeed( CharacterStatue statue ) : base( 0x14F0 ) - { - Statue = statue; - - if ( statue != null ) - { - m_Type = statue.StatueType; - m_IsRewardItem = statue.IsRewardItem; - } - - LootType = LootType.Blessed; - Weight = 1.0; - } - - public CharacterStatueDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076222 ); // 6th Year Veteran Reward - - if ( Statue != null ) - list.Add( 1076231, Statue.Name ); // Statue of ~1_Name~ - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.Account is Account acct && from.AccessLevel == AccessLevel.Player ) - { - TimeSpan time = TimeSpan.FromDays( RewardSystem.RewardInterval.TotalDays * 6 ) - ( DateTime.UtcNow - acct.Created ); - - if ( time > TimeSpan.Zero ) - { - from.SendLocalizedMessage( 1008126, true, Math.Ceiling( time.TotalDays / RewardSystem.RewardInterval.TotalDays ).ToString() ); // Your account is not old enough to use this item. Months until you can use this item : - return; - } - } - - if ( IsChildOf( from.Backpack ) ) - { - if ( !from.IsBodyMod ) - { - from.SendLocalizedMessage( 1076194 ); // Select a place where you would like to put your statue. - from.Target = new CharacterStatueTarget( this, StatueType ); - } - else - from.SendLocalizedMessage( 1073648 ); // You may only proceed while in your original state... - } - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - - public override void OnDelete() - { - base.OnDelete(); - - Statue?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 1 ); // version - - writer.Write( (int) m_Type ); - - writer.Write( (Mobile) Statue ); - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - if ( version >= 1 ) { - m_Type = (StatueType) reader.ReadInt(); - } - - Statue = reader.ReadMobile() as CharacterStatue; - m_IsRewardItem = reader.ReadBool(); - } - } - - public class CharacterStatueTarget : Target - { - private Item m_Maker; - private StatueType m_Type; - - public CharacterStatueTarget( Item maker, StatueType type ) : base( -1, true, TargetFlags.None ) - { - m_Maker = maker; - m_Type = type; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; - - if ( p == null || map == null || m_Maker == null || m_Maker.Deleted ) - return; - - if ( m_Maker.IsChildOf( from.Backpack ) ) - { - SpellHelper.GetSurfaceTop( ref p ); - BaseHouse house = null; - Point3D loc = new Point3D( p ); - - if ( targeted is Item item && !item.IsLockedDown && !item.IsSecure && !(item is AddonComponent) ) - { - from.SendLocalizedMessage( 1076191 ); // Statues can only be placed in houses. - return; - } - if ( from.IsBodyMod ) - { - from.SendLocalizedMessage( 1073648 ); // You may only proceed while in your original state... - return; - } - - AddonFitResult result = CouldFit( loc, map, from, ref house ); - - if ( result == AddonFitResult.Valid ) - { - CharacterStatue statue = new CharacterStatue( from, m_Type ); - CharacterStatuePlinth plinth = new CharacterStatuePlinth( statue ); - - house.Addons.Add( plinth ); - - if ( m_Maker is IRewardItem rewardItem ) - statue.IsRewardItem = rewardItem.IsRewardItem; - - statue.Plinth = plinth; - plinth.MoveToWorld( loc, map ); - statue.InvalidatePose(); - - /* - * TODO: Previously the maker wasn't deleted until after statue - * customization, leading to redeeding issues. Exact OSI behavior - * needs looking into. - */ - m_Maker.Delete(); - statue.Sculpt( from ); - - from.CloseGump( typeof( CharacterStatueGump ) ); - from.SendGump( new CharacterStatueGump( m_Maker, statue, from ) ); - } - else if ( result == AddonFitResult.Blocked ) - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - else if ( result == AddonFitResult.NotInHouse ) - from.SendLocalizedMessage( 1076192 ); // Statues can only be placed in houses where you are the owner or co-owner. - else if ( result == AddonFitResult.DoorTooClose ) - from.SendLocalizedMessage( 500271 ); // You cannot build near the door. - } - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - - public static AddonFitResult CouldFit( Point3D p, Map map, Mobile from, ref BaseHouse house ) - { - if ( !map.CanFit( p.X, p.Y, p.Z, 20, true, true, true ) ) - return AddonFitResult.Blocked; - if ( !BaseAddon.CheckHouse( from, p, map, 20, ref house ) ) - return AddonFitResult.NotInHouse; - - return CheckDoors( p, 20, house ); - } - - public static AddonFitResult CheckDoors( Point3D p, int height, BaseHouse house ) - { - ArrayList doors = house.Doors; - - for ( int i = 0; i < doors.Count; i ++ ) - { - BaseDoor door = doors[ i ] as BaseDoor; - - Point3D doorLoc = door.GetWorldLocation(); - int doorHeight = door.ItemData.CalcHeight; - - if ( Utility.InRange( doorLoc, p, 1 ) && (p.Z == doorLoc.Z || ((p.Z + height) > doorLoc.Z && (doorLoc.Z + doorHeight) > p.Z)) ) - return AddonFitResult.DoorTooClose; - } - - return AddonFitResult.Valid; - } - } -} + InvalidateProperties(); + } + + public bool Demolish(Mobile by) + { + CharacterStatueDeed deed = new CharacterStatueDeed(null); + + if (by.PlaceInBackpack(deed)) + { + Delete(); + + deed.Statue = this; + deed.StatueType = m_Type; + deed.IsRewardItem = IsRewardItem; + + Plinth?.Delete(); + + return true; + } + + by.SendLocalizedMessage(500720); // You don't have enough room in your backpack! + deed.Delete(); + + return false; + } + + public void Restore(CharacterStatue from) + { + m_Material = from.Material; + m_Pose = from.Pose; + + Direction = from.Direction; + + CloneBody(from); + CloneClothes(from); + + InvalidateHues(); + InvalidatePose(); + } + + public void CloneBody(Mobile from) + { + Name = from.Name; + BodyValue = from.BodyValue; + Female = from.Female; + HairItemID = from.HairItemID; + FacialHairItemID = from.FacialHairItemID; + } + + public void CloneClothes(Mobile from) + { + for (int i = Items.Count - 1; i >= 0; i--) + Items[i].Delete(); + + for (int i = from.Items.Count - 1; i >= 0; i--) + { + Item item = from.Items[i]; + + if (item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank) + AddItem(CloneItem(item)); + } + } + + public Item CloneItem(Item item) + { + Item cloned = new Item(item.ItemID); + cloned.Layer = item.Layer; + cloned.Name = item.Name; + cloned.Hue = item.Hue; + cloned.Weight = item.Weight; + cloned.Movable = false; + + return cloned; + } + + public void InvalidateHues() + { + Hue = 0xB8F + (int)m_Type * 4 + (int)m_Material; + + HairHue = Hue; + + if (FacialHairItemID > 0) + FacialHairHue = Hue; + + for (int i = Items.Count - 1; i >= 0; i--) + Items[i].Hue = Hue; + + Plinth?.InvalidateHue(); + } + + public void InvalidatePose() + { + switch (m_Pose) + { + case StatuePose.Ready: + m_Animation = 4; + m_Frames = 0; + break; + case StatuePose.Casting: + m_Animation = 16; + m_Frames = 2; + break; + case StatuePose.Salute: + m_Animation = 33; + m_Frames = 1; + break; + case StatuePose.AllPraiseMe: + m_Animation = 17; + m_Frames = 4; + break; + case StatuePose.Fighting: + m_Animation = 31; + m_Frames = 5; + break; + case StatuePose.HandsOnHips: + m_Animation = 6; + m_Frames = 1; + break; + } + + if (Map != null) + { + ProcessDelta(); + + Packet p = null; + + IPooledEnumerable eable = Map.GetClientsInRange(Location); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + + if (p == null) + p = Packet.Acquire(new UpdateStatueAnimation(this, 1, m_Animation, m_Frames)); + + state.Send(p); + } + + Packet.Release(p); + + eable.Free(); + } + } + + private class DemolishEntry : ContextMenuEntry + { + private CharacterStatue m_Statue; + + public DemolishEntry(CharacterStatue statue) : base(6275, 2) + { + m_Statue = statue; + } + + public override void OnClick() + { + if (m_Statue.Deleted) + return; + + m_Statue.Demolish(Owner.From); + } + } + } + + public class CharacterStatueDeed : Item, IRewardItem + { + private bool m_IsRewardItem; + + private StatueType m_Type; + + public CharacterStatueDeed(CharacterStatue statue) : base(0x14F0) + { + Statue = statue; + + if (statue != null) + { + m_Type = statue.StatueType; + m_IsRewardItem = statue.IsRewardItem; + } + + LootType = LootType.Blessed; + Weight = 1.0; + } + + public CharacterStatueDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber + { + get + { + StatueType t = m_Type; + + if (Statue != null) t = Statue.StatueType; + + switch (t) + { + case StatueType.Marble: return 1076189; + case StatueType.Jade: return 1076188; + case StatueType.Bronze: return 1076190; + default: return 1076173; + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CharacterStatue Statue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public StatueType StatueType + { + get + { + if (Statue != null) + return Statue.StatueType; + + return m_Type; + } + set => m_Type = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076222); // 6th Year Veteran Reward + + if (Statue != null) + list.Add(1076231, Statue.Name); // Statue of ~1_Name~ + } + + public override void OnDoubleClick(Mobile from) + { + if (from.Account is Account acct && from.AccessLevel == AccessLevel.Player) + { + TimeSpan time = TimeSpan.FromDays(RewardSystem.RewardInterval.TotalDays * 6) - + (DateTime.UtcNow - acct.Created); + + if (time > TimeSpan.Zero) + { + from.SendLocalizedMessage(1008126, true, + Math.Ceiling(time.TotalDays / RewardSystem.RewardInterval.TotalDays) + .ToString()); // Your account is not old enough to use this item. Months until you can use this item : + return; + } + } + + if (IsChildOf(from.Backpack)) + { + if (!from.IsBodyMod) + { + from.SendLocalizedMessage(1076194); // Select a place where you would like to put your statue. + from.Target = new CharacterStatueTarget(this, StatueType); + } + else + { + from.SendLocalizedMessage(1073648); // You may only proceed while in your original state... + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + + public override void OnDelete() + { + base.OnDelete(); + + Statue?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + + writer.Write((int)m_Type); + + writer.Write(Statue); + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + if (version >= 1) m_Type = (StatueType)reader.ReadInt(); + + Statue = reader.ReadMobile() as CharacterStatue; + m_IsRewardItem = reader.ReadBool(); + } + } + + public class CharacterStatueTarget : Target + { + private Item m_Maker; + private StatueType m_Type; + + public CharacterStatueTarget(Item maker, StatueType type) : base(-1, true, TargetFlags.None) + { + m_Maker = maker; + m_Type = type; + } + + protected override void OnTarget(Mobile from, object targeted) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; + + if (p == null || map == null || m_Maker == null || m_Maker.Deleted) + return; + + if (m_Maker.IsChildOf(from.Backpack)) + { + SpellHelper.GetSurfaceTop(ref p); + BaseHouse house = null; + Point3D loc = new Point3D(p); + + if (targeted is Item item && !item.IsLockedDown && !item.IsSecure && !(item is AddonComponent)) + { + from.SendLocalizedMessage(1076191); // Statues can only be placed in houses. + return; + } + + if (from.IsBodyMod) + { + from.SendLocalizedMessage(1073648); // You may only proceed while in your original state... + return; + } + + AddonFitResult result = CouldFit(loc, map, from, ref house); + + if (result == AddonFitResult.Valid) + { + CharacterStatue statue = new CharacterStatue(from, m_Type); + CharacterStatuePlinth plinth = new CharacterStatuePlinth(statue); + + house.Addons.Add(plinth); + + if (m_Maker is IRewardItem rewardItem) + statue.IsRewardItem = rewardItem.IsRewardItem; + + statue.Plinth = plinth; + plinth.MoveToWorld(loc, map); + statue.InvalidatePose(); + + /* + * TODO: Previously the maker wasn't deleted until after statue + * customization, leading to redeeding issues. Exact OSI behavior + * needs looking into. + */ + m_Maker.Delete(); + statue.Sculpt(from); + + from.CloseGump(typeof(CharacterStatueGump)); + from.SendGump(new CharacterStatueGump(m_Maker, statue, from)); + } + else if (result == AddonFitResult.Blocked) + { + from.SendLocalizedMessage(500269); // You cannot build that there. + } + else if (result == AddonFitResult.NotInHouse) + { + from.SendLocalizedMessage( + 1076192); // Statues can only be placed in houses where you are the owner or co-owner. + } + else if (result == AddonFitResult.DoorTooClose) + { + from.SendLocalizedMessage(500271); // You cannot build near the door. + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + + public static AddonFitResult CouldFit(Point3D p, Map map, Mobile from, ref BaseHouse house) + { + if (!map.CanFit(p.X, p.Y, p.Z, 20, true, true, true)) + return AddonFitResult.Blocked; + if (!BaseAddon.CheckHouse(from, p, map, 20, ref house)) + return AddonFitResult.NotInHouse; + + return CheckDoors(p, 20, house); + } + + public static AddonFitResult CheckDoors(Point3D p, int height, BaseHouse house) + { + ArrayList doors = house.Doors; + + for (int i = 0; i < doors.Count; i++) + { + BaseDoor door = doors[i] as BaseDoor; + + Point3D doorLoc = door.GetWorldLocation(); + int doorHeight = door.ItemData.CalcHeight; + + if (Utility.InRange(doorLoc, p, 1) && + (p.Z == doorLoc.Z || p.Z + height > doorLoc.Z && doorLoc.Z + doorHeight > p.Z)) + return AddonFitResult.DoorTooClose; + } + + return AddonFitResult.Valid; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatueMaker.cs b/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatueMaker.cs index e0a0c26ef..e142fb54f 100644 --- a/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatueMaker.cs +++ b/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatueMaker.cs @@ -1,171 +1,183 @@ -using Server.Mobiles; using Server.Engines.VeteranRewards; +using Server.Mobiles; namespace Server.Items { - public class CharacterStatueMaker : Item, IRewardItem - { - public override int LabelNumber => 1076173; // Character Statue Maker + public class CharacterStatueMaker : Item, IRewardItem + { + private bool m_IsRewardItem; + private StatueType m_Type; - private bool m_IsRewardItem; - private StatueType m_Type; + public CharacterStatueMaker(StatueType type) : base(0x32F0) + { + m_Type = type; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + InvalidateHue(); - [CommandProperty( AccessLevel.GameMaster )] - public StatueType StatueType - { - get => m_Type; - set{ m_Type = value; InvalidateHue(); } - } + LootType = LootType.Blessed; + Weight = 5.0; + } - public CharacterStatueMaker( StatueType type ) : base( 0x32F0 ) - { - m_Type = type; + public CharacterStatueMaker(Serial serial) : base(serial) + { + } - InvalidateHue(); + public override int LabelNumber => 1076173; // Character Statue Maker - LootType = LootType.Blessed; - Weight = 5.0; - } + [CommandProperty(AccessLevel.GameMaster)] + public StatueType StatueType + { + get => m_Type; + set + { + m_Type = value; + InvalidateHue(); + } + } - public CharacterStatueMaker( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, new object[] { m_Type } ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, new object[] { m_Type })) + return; - if ( IsChildOf( from.Backpack ) ) - { - if ( !from.IsBodyMod ) - { - from.SendLocalizedMessage( 1076194 ); // Select a place where you would like to put your statue. - from.Target = new CharacterStatueTarget( this, m_Type ); - } - else - from.SendLocalizedMessage( 1073648 ); // You may only proceed while in your original state... - } - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + if (IsChildOf(from.Backpack)) + { + if (!from.IsBodyMod) + { + from.SendLocalizedMessage(1076194); // Select a place where you would like to put your statue. + from.Target = new CharacterStatueTarget(this, m_Type); + } + else + { + from.SendLocalizedMessage(1073648); // You may only proceed while in your original state... + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076222 ); // 6th Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076222); // 6th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - writer.Write( (int) m_Type ); - } + writer.Write(m_IsRewardItem); + writer.Write((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - m_Type = (StatueType) reader.ReadInt(); - } + m_IsRewardItem = reader.ReadBool(); + m_Type = (StatueType)reader.ReadInt(); + } - public void InvalidateHue() - { - Hue = 0xB8F + (int) m_Type * 4; - } - } + public void InvalidateHue() + { + Hue = 0xB8F + (int)m_Type * 4; + } + } - public class MarbleStatueMaker : CharacterStatueMaker - { - [Constructible] - public MarbleStatueMaker() : base( StatueType.Marble ) - { - } + public class MarbleStatueMaker : CharacterStatueMaker + { + [Constructible] + public MarbleStatueMaker() : base(StatueType.Marble) + { + } - public MarbleStatueMaker( Serial serial ) : base( serial ) - { - } + public MarbleStatueMaker(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class JadeStatueMaker : CharacterStatueMaker - { - [Constructible] - public JadeStatueMaker() : base( StatueType.Jade ) - { - } + public class JadeStatueMaker : CharacterStatueMaker + { + [Constructible] + public JadeStatueMaker() : base(StatueType.Jade) + { + } - public JadeStatueMaker( Serial serial ) : base( serial ) - { - } + public JadeStatueMaker(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BronzeStatueMaker : CharacterStatueMaker - { - [Constructible] - public BronzeStatueMaker() : base( StatueType.Bronze ) - { - } + public class BronzeStatueMaker : CharacterStatueMaker + { + [Constructible] + public BronzeStatueMaker() : base(StatueType.Bronze) + { + } - public BronzeStatueMaker( Serial serial ) : base( serial ) - { - } + public BronzeStatueMaker(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatuePlinth.cs b/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatuePlinth.cs index 9bd2860ea..225aa39e0 100644 --- a/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatuePlinth.cs +++ b/Scripts/Engines/VeteranRewards/Character Statue Maker/CharacterStatuePlinth.cs @@ -5,125 +5,122 @@ using Server.Multis; namespace Server.Items { - public class CharacterStatuePlinth : Static, IAddon - { - public Item Deed => new CharacterStatueDeed( m_Statue ); - public override int LabelNumber => 1076201; // Character Statue + public class CharacterStatuePlinth : Static, IAddon + { + private CharacterStatue m_Statue; - private CharacterStatue m_Statue; + public CharacterStatuePlinth(CharacterStatue statue) : base(0x32F2) + { + m_Statue = statue; - public CharacterStatuePlinth( CharacterStatue statue ) : base( 0x32F2 ) - { - m_Statue = statue; + InvalidateHue(); + } - InvalidateHue(); - } + public CharacterStatuePlinth(Serial serial) : base(serial) + { + } - public CharacterStatuePlinth( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076201; // Character Statue + public Item Deed => new CharacterStatueDeed(m_Statue); - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public virtual bool CouldFit(IPoint3D p, Map map) + { + Point3D point = new Point3D(p.X, p.Y, p.Z); - if ( m_Statue != null && !m_Statue.Deleted ) - m_Statue.Delete(); - } + if (map == null || !map.CanFit(point, 20)) + return false; - public override void OnMapChange() - { - if ( m_Statue != null ) - m_Statue.Map = Map; - } + BaseHouse house = BaseHouse.FindHouseAt(point, map, 20); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Statue != null ) - m_Statue.Location = new Point3D( X, Y, Z + 5 ); - } + if (house == null) + return false; - public override void OnDoubleClick( Mobile from ) - { - if ( m_Statue != null ) - from.SendGump( new CharacterPlinthGump( m_Statue ) ); - } + AddonFitResult result = CharacterStatueTarget.CheckDoors(point, 20, house); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (result == AddonFitResult.Valid) + return true; - writer.WriteEncodedInt( (int) 0 ); // version + return false; + } - writer.Write( (Mobile) m_Statue ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (m_Statue != null && !m_Statue.Deleted) + m_Statue.Delete(); + } - int version = reader.ReadEncodedInt(); + public override void OnMapChange() + { + if (m_Statue != null) + m_Statue.Map = Map; + } - m_Statue = reader.ReadMobile() as CharacterStatue; + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Statue != null) + m_Statue.Location = new Point3D(X, Y, Z + 5); + } - if ( m_Statue?.SculptedBy == null || Map == Map.Internal ) - { - Timer.DelayCall( TimeSpan.Zero, Delete ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (m_Statue != null) + from.SendGump(new CharacterPlinthGump(m_Statue)); + } - public void InvalidateHue() - { - if ( m_Statue != null ) - Hue = 0xB8F + (int) m_Statue.StatueType * 4 + (int) m_Statue.Material; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public virtual bool CouldFit( IPoint3D p, Map map ) - { - Point3D point = new Point3D( p.X, p.Y, p.Z ); + writer.WriteEncodedInt(0); // version - if ( map == null || !map.CanFit( point, 20 ) ) - return false; + writer.Write(m_Statue); + } - BaseHouse house = BaseHouse.FindHouseAt( point, map, 20 ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( house == null ) - return false; + int version = reader.ReadEncodedInt(); - AddonFitResult result = CharacterStatueTarget.CheckDoors( point, 20, house ); + m_Statue = reader.ReadMobile() as CharacterStatue; - if ( result == AddonFitResult.Valid ) - return true; + if (m_Statue?.SculptedBy == null || Map == Map.Internal) Timer.DelayCall(TimeSpan.Zero, Delete); + } - return false; - } + public void InvalidateHue() + { + if (m_Statue != null) + Hue = 0xB8F + (int)m_Statue.StatueType * 4 + (int)m_Statue.Material; + } - private class CharacterPlinthGump : Gump - { - public CharacterPlinthGump( CharacterStatue statue ) : base( 60, 30 ) - { - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + private class CharacterPlinthGump : Gump + { + public CharacterPlinthGump(CharacterStatue statue) : base(60, 30) + { + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); - AddImage( 0, 0, 0x24F4 ); - AddHtml( 55, 50, 150, 20, statue.Name, false, false ); - AddHtml( 55, 75, 150, 20, statue.SculptedOn.ToString(), false, false ); - AddHtmlLocalized( 55, 100, 150, 20, GetTypeNumber( statue.StatueType ), 0, false, false ); - } + AddPage(0); + AddImage(0, 0, 0x24F4); + AddHtml(55, 50, 150, 20, statue.Name, false, false); + AddHtml(55, 75, 150, 20, statue.SculptedOn.ToString(), false, false); + AddHtmlLocalized(55, 100, 150, 20, GetTypeNumber(statue.StatueType), 0, false, false); + } - public int GetTypeNumber( StatueType type ) - { - switch ( type ) - { - case StatueType.Marble: return 1076181; - case StatueType.Jade: return 1076180; - case StatueType.Bronze: return 1076230; - default: return 1076181; - } - } - } - } -} + public int GetTypeNumber(StatueType type) + { + switch (type) + { + case StatueType.Marble: return 1076181; + case StatueType.Jade: return 1076180; + case StatueType.Bronze: return 1076230; + default: return 1076181; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/Character Statue Maker/Gumps/CharacterStatueGump.cs b/Scripts/Engines/VeteranRewards/Character Statue Maker/Gumps/CharacterStatueGump.cs index 32eed5cde..2589661b2 100644 --- a/Scripts/Engines/VeteranRewards/Character Statue Maker/Gumps/CharacterStatueGump.cs +++ b/Scripts/Engines/VeteranRewards/Character Statue Maker/Gumps/CharacterStatueGump.cs @@ -3,195 +3,196 @@ using Server.Network; namespace Server.Gumps { - public class CharacterStatueGump : Gump - { - private Item m_Maker; - private CharacterStatue m_Statue; - private Mobile m_Owner; + public class CharacterStatueGump : Gump + { + private Item m_Maker; + private Mobile m_Owner; + private CharacterStatue m_Statue; - private enum Buttons - { - Close, - Sculpt, - PosePrev, - PoseNext, - DirPrev, - DirNext, - MatPrev, - MatNext, - Restore - } + public CharacterStatueGump(Item maker, CharacterStatue statue, Mobile owner) : base(60, 36) + { + m_Maker = maker; + m_Statue = statue; + m_Owner = owner; - public CharacterStatueGump( Item maker, CharacterStatue statue, Mobile owner ) : base( 60, 36 ) - { - m_Maker = maker; - m_Statue = statue; - m_Owner = owner; + if (m_Statue == null) + return; - if ( m_Statue == null ) - return; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 327, 324, 0x13BE); + AddImageTiled(10, 10, 307, 20, 0xA40); + AddImageTiled(10, 40, 307, 244, 0xA40); + AddImageTiled(10, 294, 307, 20, 0xA40); + AddAlphaRegion(10, 10, 307, 304); + AddHtmlLocalized(14, 12, 327, 20, 1076156, 0x7FFF, false, false); // Character Statue Maker - AddBackground( 0, 0, 327, 324, 0x13BE ); - AddImageTiled( 10, 10, 307, 20, 0xA40 ); - AddImageTiled( 10, 40, 307, 244, 0xA40 ); - AddImageTiled( 10, 294, 307, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 307, 304 ); - AddHtmlLocalized( 14, 12, 327, 20, 1076156, 0x7FFF, false, false ); // Character Statue Maker + // pose + AddHtmlLocalized(133, 41, 120, 20, 1076168, 0x7FFF, false, false); // Choose Pose + AddHtmlLocalized(133, 61, 120, 20, 1076208 + (int)m_Statue.Pose, 0x77E, false, false); + AddButton(163, 81, 0xFA5, 0xFA7, (int)Buttons.PoseNext, GumpButtonType.Reply, 0); + AddButton(133, 81, 0xFAE, 0xFB0, (int)Buttons.PosePrev, GumpButtonType.Reply, 0); - // pose - AddHtmlLocalized( 133, 41, 120, 20, 1076168, 0x7FFF, false, false ); // Choose Pose - AddHtmlLocalized( 133, 61, 120, 20, 1076208 + (int) m_Statue.Pose, 0x77E, false, false ); - AddButton( 163, 81, 0xFA5, 0xFA7, (int) Buttons.PoseNext, GumpButtonType.Reply, 0 ); - AddButton( 133, 81, 0xFAE, 0xFB0, (int) Buttons.PosePrev, GumpButtonType.Reply, 0 ); + // direction + AddHtmlLocalized(133, 126, 120, 20, 1076170, 0x7FFF, false, false); // Choose Direction + AddHtmlLocalized(133, 146, 120, 20, GetDirectionNumber(m_Statue.Direction), 0x77E, false, false); + AddButton(163, 167, 0xFA5, 0xFA7, (int)Buttons.DirNext, GumpButtonType.Reply, 0); + AddButton(133, 167, 0xFAE, 0xFB0, (int)Buttons.DirPrev, GumpButtonType.Reply, 0); - // direction - AddHtmlLocalized( 133, 126, 120, 20, 1076170, 0x7FFF, false, false ); // Choose Direction - AddHtmlLocalized( 133, 146, 120, 20, GetDirectionNumber( m_Statue.Direction ), 0x77E, false, false ); - AddButton( 163, 167, 0xFA5, 0xFA7, (int) Buttons.DirNext, GumpButtonType.Reply, 0 ); - AddButton( 133, 167, 0xFAE, 0xFB0, (int) Buttons.DirPrev, GumpButtonType.Reply, 0 ); + // material + AddHtmlLocalized(133, 211, 120, 20, 1076171, 0x7FFF, false, false); // Choose Material + AddHtmlLocalized(133, 231, 120, 20, GetMaterialNumber(m_Statue.StatueType, m_Statue.Material), 0x77E, false, + false); + AddButton(163, 253, 0xFA5, 0xFA7, (int)Buttons.MatNext, GumpButtonType.Reply, 0); + AddButton(133, 253, 0xFAE, 0xFB0, (int)Buttons.MatPrev, GumpButtonType.Reply, 0); - // material - AddHtmlLocalized( 133, 211, 120, 20, 1076171, 0x7FFF, false, false ); // Choose Material - AddHtmlLocalized( 133, 231, 120, 20, GetMaterialNumber( m_Statue.StatueType, m_Statue.Material ), 0x77E, false, false ); - AddButton( 163, 253, 0xFA5, 0xFA7, (int) Buttons.MatNext, GumpButtonType.Reply, 0 ); - AddButton( 133, 253, 0xFAE, 0xFB0, (int) Buttons.MatPrev, GumpButtonType.Reply, 0 ); + // cancel + AddButton(10, 294, 0xFB1, 0xFB2, (int)Buttons.Close, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 294, 80, 20, 1006045, 0x7FFF, false, false); // Cancel - // cancel - AddButton( 10, 294, 0xFB1, 0xFB2, (int) Buttons.Close, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 294, 80, 20, 1006045, 0x7FFF, false, false ); // Cancel + // sculpt + AddButton(234, 294, 0xFB7, 0xFB9, (int)Buttons.Sculpt, GumpButtonType.Reply, 0); + AddHtmlLocalized(269, 294, 80, 20, 1076174, 0x7FFF, false, false); // Sculpt - // sculpt - AddButton( 234, 294, 0xFB7, 0xFB9, (int) Buttons.Sculpt, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 269, 294, 80, 20, 1076174, 0x7FFF, false, false ); // Sculpt + // restore + if (m_Maker is CharacterStatueDeed) + { + AddButton(107, 294, 0xFAB, 0xFAD, (int)Buttons.Restore, GumpButtonType.Reply, 0); + AddHtmlLocalized(142, 294, 80, 20, 1076193, 0x7FFF, false, false); // Restore + } + } - // restore - if ( m_Maker is CharacterStatueDeed ) - { - AddButton( 107, 294, 0xFAB, 0xFAD, (int) Buttons.Restore, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 142, 294, 80, 20, 1076193, 0x7FFF, false, false ); // Restore - } - } + private int GetMaterialNumber(StatueType type, StatueMaterial material) + { + switch (material) + { + case StatueMaterial.Antique: - private int GetMaterialNumber( StatueType type, StatueMaterial material ) - { - switch ( material ) - { - case StatueMaterial.Antique: + switch (type) + { + case StatueType.Bronze: return 1076187; + case StatueType.Jade: return 1076186; + case StatueType.Marble: return 1076182; + } - switch ( type ) - { - case StatueType.Bronze: return 1076187; - case StatueType.Jade: return 1076186; - case StatueType.Marble: return 1076182; - } + return 1076187; + case StatueMaterial.Dark: - return 1076187; - case StatueMaterial.Dark: + if (type == StatueType.Marble) + return 1076183; - if ( type == StatueType.Marble ) - return 1076183; + return 1076182; + case StatueMaterial.Medium: return 1076184; + case StatueMaterial.Light: return 1076185; + default: return 1076187; + } + } - return 1076182; - case StatueMaterial.Medium: return 1076184; - case StatueMaterial.Light: return 1076185; - default: return 1076187; - } - } + private int GetDirectionNumber(Direction direction) + { + switch (direction) + { + case Direction.North: return 1075389; + case Direction.Right: return 1075388; + case Direction.East: return 1075387; + case Direction.Down: return 1076204; + case Direction.South: return 1075386; + case Direction.Left: return 1075391; + case Direction.West: return 1075390; + case Direction.Up: return 1076205; + default: return 1075386; + } + } - private int GetDirectionNumber( Direction direction ) - { - switch ( direction ) - { - case Direction.North: return 1075389; - case Direction.Right: return 1075388; - case Direction.East: return 1075387; - case Direction.Down: return 1076204; - case Direction.South: return 1075386; - case Direction.Left: return 1075391; - case Direction.West: return 1075390; - case Direction.Up: return 1076205; - default: return 1075386; - } - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Statue == null || m_Statue.Deleted) + return; - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_Statue == null || m_Statue.Deleted ) - return; + bool sendGump = false; - bool sendGump = false; + if (info.ButtonID == (int)Buttons.Sculpt) + { + if (m_Maker is CharacterStatueDeed deed) + { + CharacterStatue backup = deed.Statue; - if ( info.ButtonID == (int) Buttons.Sculpt ) - { - if ( m_Maker is CharacterStatueDeed deed ) - { - CharacterStatue backup = deed.Statue; + backup?.Delete(); + } - backup?.Delete(); - } + m_Maker?.Delete(); - m_Maker?.Delete(); + m_Statue.Sculpt(state.Mobile); + } + else if (info.ButtonID == (int)Buttons.PosePrev) + { + m_Statue.Pose = (StatuePose)(((int)m_Statue.Pose + 5) % 6); + sendGump = true; + } + else if (info.ButtonID == (int)Buttons.PoseNext) + { + m_Statue.Pose = (StatuePose)(((int)m_Statue.Pose + 1) % 6); + sendGump = true; + } + else if (info.ButtonID == (int)Buttons.DirPrev) + { + m_Statue.Direction = (Direction)(((int)m_Statue.Direction + 7) % 8); + m_Statue.InvalidatePose(); + sendGump = true; + } + else if (info.ButtonID == (int)Buttons.DirNext) + { + m_Statue.Direction = (Direction)(((int)m_Statue.Direction + 1) % 8); + m_Statue.InvalidatePose(); + sendGump = true; + } + else if (info.ButtonID == (int)Buttons.MatPrev) + { + m_Statue.Material = (StatueMaterial)(((int)m_Statue.Material + 3) % 4); + sendGump = true; + } + else if (info.ButtonID == (int)Buttons.MatNext) + { + m_Statue.Material = (StatueMaterial)(((int)m_Statue.Material + 1) % 4); + sendGump = true; + } + else if (info.ButtonID == (int)Buttons.Restore) + { + if (m_Maker is CharacterStatueDeed deed) + { + CharacterStatue backup = deed.Statue; - m_Statue.Sculpt( state.Mobile ); - } - else if ( info.ButtonID == (int) Buttons.PosePrev ) - { - m_Statue.Pose = (StatuePose) ( ( (int) m_Statue.Pose + 5 ) % 6 ); - sendGump = true; - } - else if ( info.ButtonID == (int) Buttons.PoseNext ) - { - m_Statue.Pose = (StatuePose) ( ( (int) m_Statue.Pose + 1 ) % 6 ); - sendGump = true; - } - else if ( info.ButtonID == (int) Buttons.DirPrev ) - { - m_Statue.Direction = (Direction) ( ( (int) m_Statue.Direction + 7 ) % 8 ); - m_Statue.InvalidatePose(); - sendGump = true; - } - else if ( info.ButtonID == (int) Buttons.DirNext ) - { - m_Statue.Direction = (Direction) ( ( (int) m_Statue.Direction + 1 ) % 8 ); - m_Statue.InvalidatePose(); - sendGump = true; - } - else if ( info.ButtonID == (int) Buttons.MatPrev ) - { - m_Statue.Material = (StatueMaterial) ( ( (int) m_Statue.Material + 3 ) % 4 ); - sendGump = true; - } - else if ( info.ButtonID == (int) Buttons.MatNext ) - { - m_Statue.Material = (StatueMaterial) ( ( (int) m_Statue.Material + 1 ) % 4 ); - sendGump = true; - } - else if ( info.ButtonID == (int) Buttons.Restore ) - { - if ( m_Maker is CharacterStatueDeed deed ) - { - CharacterStatue backup = deed.Statue; + if (backup != null) + m_Statue.Restore(backup); + } - if ( backup != null ) - m_Statue.Restore( backup ); - } + sendGump = true; + } + else // Close + { + sendGump = !m_Statue.Demolish(state.Mobile); + } - sendGump = true; - } - else // Close - { - sendGump = !m_Statue.Demolish( state.Mobile ); - } + if (sendGump) + state.Mobile.SendGump(new CharacterStatueGump(m_Maker, m_Statue, m_Owner)); + } - if ( sendGump ) - state.Mobile.SendGump( new CharacterStatueGump( m_Maker, m_Statue, m_Owner ) ); - } - } -} + private enum Buttons + { + Close, + Sculpt, + PosePrev, + PoseNext, + DirPrev, + DirNext, + MatPrev, + MatNext, + Restore + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/Character Statue Maker/Packets.cs b/Scripts/Engines/VeteranRewards/Character Statue Maker/Packets.cs index 4158ca2bd..b13fd47b9 100644 --- a/Scripts/Engines/VeteranRewards/Character Statue Maker/Packets.cs +++ b/Scripts/Engines/VeteranRewards/Character Statue Maker/Packets.cs @@ -1,20 +1,20 @@ namespace Server.Network { - public class UpdateStatueAnimation : Packet - { - public UpdateStatueAnimation( Mobile m, int status, int animation, int frame ) : base( 0xBF, 17 ) - { - m_Stream.Write( (short) 0x11 ); - m_Stream.Write( (short) 0x19 ); - m_Stream.Write( (byte) 0x5 ); - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0xFF ); - m_Stream.Write( (byte) status ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) animation ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) frame ); - } - } -} + public class UpdateStatueAnimation : Packet + { + public UpdateStatueAnimation(Mobile m, int status, int animation, int frame) : base(0xBF, 17) + { + m_Stream.Write((short)0x11); + m_Stream.Write((short)0x19); + m_Stream.Write((byte)0x5); + m_Stream.Write(m.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0xFF); + m_Stream.Write((byte)status); + m_Stream.Write((byte)0); + m_Stream.Write((byte)animation); + m_Stream.Write((byte)0); + m_Stream.Write((byte)frame); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardCategory.cs b/Scripts/Engines/VeteranRewards/RewardCategory.cs index 69d091e27..4ba977c9f 100644 --- a/Scripts/Engines/VeteranRewards/RewardCategory.cs +++ b/Scripts/Engines/VeteranRewards/RewardCategory.cs @@ -2,24 +2,24 @@ using System.Collections.Generic; namespace Server.Engines.VeteranRewards { - public class RewardCategory - { - public int Name { get; } + public class RewardCategory + { + public RewardCategory(int name) + { + Name = name; + Entries = new List(); + } - public string NameString { get; } + public RewardCategory(string name) + { + NameString = name; + Entries = new List(); + } - public List Entries { get; } + public int Name{ get; } - public RewardCategory( int name ) - { - Name = name; - Entries = new List(); - } + public string NameString{ get; } - public RewardCategory( string name ) - { - NameString = name; - Entries = new List(); - } - } -} + public List Entries{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardChoiceGump.cs b/Scripts/Engines/VeteranRewards/RewardChoiceGump.cs index 339b06806..6efec0e1d 100644 --- a/Scripts/Engines/VeteranRewards/RewardChoiceGump.cs +++ b/Scripts/Engines/VeteranRewards/RewardChoiceGump.cs @@ -5,193 +5,192 @@ using Server.Network; namespace Server.Engines.VeteranRewards { - public class RewardChoiceGump : Gump - { - private Mobile m_From; + public class RewardChoiceGump : Gump + { + private Mobile m_From; - private void RenderBackground() - { - AddPage( 0 ); + public RewardChoiceGump(Mobile from) : base(0, 0) + { + m_From = from; - AddBackground( 10, 10, 600, 450, 2600 ); + from.CloseGump(typeof(RewardChoiceGump)); - AddButton( 530, 415, 4017, 4019, 0, GumpButtonType.Reply, 0 ); + RenderBackground(); + RenderCategories(); + } - AddButton( 60, 415, 4014, 4016, 0, GumpButtonType.Page, 1 ); - AddHtmlLocalized( 95, 415, 200, 20, 1049755, false, false ); // Main Menu - } + private void RenderBackground() + { + AddPage(0); - private void RenderCategories() - { - TimeSpan rewardInterval = RewardSystem.RewardInterval; + AddBackground(10, 10, 600, 450, 2600); - string intervalAsString; + AddButton(530, 415, 4017, 4019, 0, GumpButtonType.Reply, 0); - if ( rewardInterval == TimeSpan.FromDays( 30.0 ) ) - intervalAsString = "month"; - else if ( rewardInterval == TimeSpan.FromDays( 60.0 ) ) - intervalAsString = "two months"; - else if ( rewardInterval == TimeSpan.FromDays( 90.0 ) ) - intervalAsString = "three months"; - else if ( rewardInterval == TimeSpan.FromDays( 365.0 ) ) - intervalAsString = "year"; - else - intervalAsString = $"{rewardInterval.TotalDays} day{(rewardInterval.TotalDays == 1 ? "" : "s")}"; + AddButton(60, 415, 4014, 4016, 0, GumpButtonType.Page, 1); + AddHtmlLocalized(95, 415, 200, 20, 1049755, false, false); // Main Menu + } - AddPage( 1 ); + private void RenderCategories() + { + TimeSpan rewardInterval = RewardSystem.RewardInterval; - AddHtml( 60, 35, 500, 70, "Ultima Online Rewards Program
" + - "Thank you for being a part of the Ultima Online community for a full " + intervalAsString + ". " + - "As a token of our appreciation, you may select from the following in-game reward items listed below. " + - "The gift items will be attributed to the character you have logged-in with on the shard you are on when you chose the item(s). " + - "The number of rewards you are entitled to are listed below and are for your entire account. " + - "To read more about these rewards before making a selection, feel free to visit the uo.com site at " + - "http://www.uo.com/rewards.", true, true ); + string intervalAsString; - int cur, max; + if (rewardInterval == TimeSpan.FromDays(30.0)) + intervalAsString = "month"; + else if (rewardInterval == TimeSpan.FromDays(60.0)) + intervalAsString = "two months"; + else if (rewardInterval == TimeSpan.FromDays(90.0)) + intervalAsString = "three months"; + else if (rewardInterval == TimeSpan.FromDays(365.0)) + intervalAsString = "year"; + else + intervalAsString = $"{rewardInterval.TotalDays} day{(rewardInterval.TotalDays == 1 ? "" : "s")}"; - RewardSystem.ComputeRewardInfo( m_From, out cur, out max ); + AddPage(1); - AddHtmlLocalized( 60, 105, 300, 35, 1006006, false, false ); // Your current total of rewards to choose: - AddLabel( 370, 107, 50, (max - cur).ToString() ); + AddHtml(60, 35, 500, 70, "Ultima Online Rewards Program
" + + "Thank you for being a part of the Ultima Online community for a full " + + intervalAsString + ". " + + "As a token of our appreciation, you may select from the following in-game reward items listed below. " + + "The gift items will be attributed to the character you have logged-in with on the shard you are on when you chose the item(s). " + + "The number of rewards you are entitled to are listed below and are for your entire account. " + + "To read more about these rewards before making a selection, feel free to visit the uo.com site at " + + "http://www.uo.com/rewards.", true, true); - AddHtmlLocalized( 60, 140, 300, 35, 1006007, false, false ); // You have already chosen: - AddLabel( 370, 142, 50, cur.ToString() ); + int cur, max; - RewardCategory[] categories = RewardSystem.Categories; + RewardSystem.ComputeRewardInfo(m_From, out cur, out max); - int page = 2; + AddHtmlLocalized(60, 105, 300, 35, 1006006, false, false); // Your current total of rewards to choose: + AddLabel(370, 107, 50, (max - cur).ToString()); - for ( int i = 0; i < categories.Length; ++i ) - { - if ( !RewardSystem.HasAccess( m_From, categories[i] ) ) - { - page += 1; - continue; - } + AddHtmlLocalized(60, 140, 300, 35, 1006007, false, false); // You have already chosen: + AddLabel(370, 142, 50, cur.ToString()); - AddButton( 100, 180 + (i * 40), 4005, 4005, 0, GumpButtonType.Page, page ); + RewardCategory[] categories = RewardSystem.Categories; - page += PagesPerCategory( categories[ i ] ); + int page = 2; - if ( categories[i].NameString != null ) - AddHtml( 135, 180 + (i * 40), 300, 20, categories[i].NameString, false, false ); - else - AddHtmlLocalized( 135, 180 + (i * 40), 300, 20, categories[i].Name, false, false ); - } + for (int i = 0; i < categories.Length; ++i) + { + if (!RewardSystem.HasAccess(m_From, categories[i])) + { + page += 1; + continue; + } - page = 2; + AddButton(100, 180 + i * 40, 4005, 4005, 0, GumpButtonType.Page, page); - for ( int i = 0; i < categories.Length; ++i ) - RenderCategory( categories[ i ], i, ref page ); - } + page += PagesPerCategory(categories[i]); - private int PagesPerCategory( RewardCategory category ) - { - List entries = category.Entries; - int j = 0, i = 0; + if (categories[i].NameString != null) + AddHtml(135, 180 + i * 40, 300, 20, categories[i].NameString, false, false); + else + AddHtmlLocalized(135, 180 + i * 40, 300, 20, categories[i].Name, false, false); + } - for ( j = 0; j < entries.Count; j++ ) - { - if ( RewardSystem.HasAccess( m_From, entries[ j ] ) ) - i++; - } - - return (int) Math.Ceiling( i / 24.0 ); - } + page = 2; - private int GetButtonID( int type, int index ) - { - return 2 + (index * 20) + type; - } + for (int i = 0; i < categories.Length; ++i) + RenderCategory(categories[i], i, ref page); + } - private void RenderCategory( RewardCategory category, int index, ref int page ) - { - AddPage( page ); + private int PagesPerCategory(RewardCategory category) + { + List entries = category.Entries; + int j = 0, i = 0; - List entries = category.Entries; + for (j = 0; j < entries.Count; j++) + if (RewardSystem.HasAccess(m_From, entries[j])) + i++; - int i = 0; - - for ( int j = 0; j < entries.Count; ++j ) - { - RewardEntry entry = entries[j]; + return (int)Math.Ceiling(i / 24.0); + } - if ( !RewardSystem.HasAccess( m_From, entry ) ) - continue; + private int GetButtonID(int type, int index) + { + return 2 + index * 20 + type; + } - if ( i == 24 ) - { - AddButton( 305, 415, 0xFA5, 0xFA7, 0, GumpButtonType.Page, ++page ); - AddHtmlLocalized( 340, 415, 200, 20, 1011066, false, false ); // Next page + private void RenderCategory(RewardCategory category, int index, ref int page) + { + AddPage(page); - AddPage( page ); + List entries = category.Entries; - AddButton( 270, 415, 0xFAE, 0xFB0, 0, GumpButtonType.Page, page - 1 ); - AddHtmlLocalized( 185, 415, 200, 20, 1011067, false, false ); // Previous page + int i = 0; - i = 0; - } + for (int j = 0; j < entries.Count; ++j) + { + RewardEntry entry = entries[j]; - AddButton( 55 + ((i / 12) * 250), 80 + ((i % 12) * 25), 5540, 5541, GetButtonID( index, j ), GumpButtonType.Reply, 0 ); + if (!RewardSystem.HasAccess(m_From, entry)) + continue; - if ( entry.NameString != null ) - AddHtml( 80 + ((i / 12) * 250), 80 + ((i % 12) * 25), 250, 20, entry.NameString, false, false ); - else - AddHtmlLocalized( 80 + ((i / 12) * 250), 80 + ((i % 12) * 25), 250, 20, entry.Name, false, false ); - ++i; - } + if (i == 24) + { + AddButton(305, 415, 0xFA5, 0xFA7, 0, GumpButtonType.Page, ++page); + AddHtmlLocalized(340, 415, 200, 20, 1011066, false, false); // Next page - page += 1; - } + AddPage(page); - public RewardChoiceGump( Mobile from ) : base( 0, 0 ) - { - m_From = from; + AddButton(270, 415, 0xFAE, 0xFB0, 0, GumpButtonType.Page, page - 1); + AddHtmlLocalized(185, 415, 200, 20, 1011067, false, false); // Previous page - from.CloseGump( typeof( RewardChoiceGump ) ); + i = 0; + } - RenderBackground(); - RenderCategories(); - } + AddButton(55 + i / 12 * 250, 80 + i % 12 * 25, 5540, 5541, GetButtonID(index, j), GumpButtonType.Reply, 0); - public override void OnResponse( NetState sender, RelayInfo info ) - { - int buttonID = info.ButtonID - 1; + if (entry.NameString != null) + AddHtml(80 + i / 12 * 250, 80 + i % 12 * 25, 250, 20, entry.NameString, false, false); + else + AddHtmlLocalized(80 + i / 12 * 250, 80 + i % 12 * 25, 250, 20, entry.Name, false, false); + ++i; + } - if ( buttonID == 0 ) - { - int cur, max; + page += 1; + } - RewardSystem.ComputeRewardInfo( m_From, out cur, out max ); + public override void OnResponse(NetState sender, RelayInfo info) + { + int buttonID = info.ButtonID - 1; - if ( cur < max ) - m_From.SendGump( new RewardNoticeGump( m_From ) ); - } - else - { - --buttonID; + if (buttonID == 0) + { + int cur, max; - int type = (buttonID % 20); - int index = (buttonID / 20); + RewardSystem.ComputeRewardInfo(m_From, out cur, out max); - RewardCategory[] categories = RewardSystem.Categories; + if (cur < max) + m_From.SendGump(new RewardNoticeGump(m_From)); + } + else + { + --buttonID; - if ( type >= 0 && type < categories.Length ) - { - RewardCategory category = categories[type]; + int type = buttonID % 20; + int index = buttonID / 20; - if ( index >= 0 && index < category.Entries.Count ) - { - RewardEntry entry = category.Entries[index]; + RewardCategory[] categories = RewardSystem.Categories; - if ( !RewardSystem.HasAccess( m_From, entry ) ) - return; + if (type >= 0 && type < categories.Length) + { + RewardCategory category = categories[type]; - m_From.SendGump( new RewardConfirmGump( m_From, entry ) ); - } - } - } - } - } + if (index >= 0 && index < category.Entries.Count) + { + RewardEntry entry = category.Entries[index]; + + if (!RewardSystem.HasAccess(m_From, entry)) + return; + + m_From.SendGump(new RewardConfirmGump(m_From, entry)); + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardConfirmGump.cs b/Scripts/Engines/VeteranRewards/RewardConfirmGump.cs index 079901287..2e7a8fa24 100644 --- a/Scripts/Engines/VeteranRewards/RewardConfirmGump.cs +++ b/Scripts/Engines/VeteranRewards/RewardConfirmGump.cs @@ -4,68 +4,69 @@ using Server.Network; namespace Server.Engines.VeteranRewards { - public class RewardConfirmGump : Gump - { - private Mobile m_From; - private RewardEntry m_Entry; + public class RewardConfirmGump : Gump + { + private RewardEntry m_Entry; + private Mobile m_From; - public RewardConfirmGump( Mobile from, RewardEntry entry ) : base( 0, 0 ) - { - m_From = from; - m_Entry = entry; + public RewardConfirmGump(Mobile from, RewardEntry entry) : base(0, 0) + { + m_From = from; + m_Entry = entry; - from.CloseGump( typeof( RewardConfirmGump ) ); + from.CloseGump(typeof(RewardConfirmGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 10, 10, 500, 300, 2600 ); + AddBackground(10, 10, 500, 300, 2600); - AddHtmlLocalized( 30, 55, 300, 35, 1006000, false, false ); // You have selected: + AddHtmlLocalized(30, 55, 300, 35, 1006000, false, false); // You have selected: - if ( entry.NameString != null ) - AddHtml( 335, 55, 150, 35, entry.NameString, false, false ); - else - AddHtmlLocalized( 335, 55, 150, 35, entry.Name, false, false ); + if (entry.NameString != null) + AddHtml(335, 55, 150, 35, entry.NameString, false, false); + else + AddHtmlLocalized(335, 55, 150, 35, entry.Name, false, false); - AddHtmlLocalized( 30, 95, 300, 35, 1006001, false, false ); // This will be assigned to this character: - AddLabel( 335, 95, 0, from.Name ); + AddHtmlLocalized(30, 95, 300, 35, 1006001, false, false); // This will be assigned to this character: + AddLabel(335, 95, 0, from.Name); - AddHtmlLocalized( 35, 160, 450, 90, 1006002, true, true ); // Are you sure you wish to select this reward for this character? You will not be able to transfer this reward to another character on another shard. Click 'ok' below to confirm your selection or 'cancel' to go back to the selection screen. + AddHtmlLocalized(35, 160, 450, 90, 1006002, true, + true); // Are you sure you wish to select this reward for this character? You will not be able to transfer this reward to another character on another shard. Click 'ok' below to confirm your selection or 'cancel' to go back to the selection screen. - AddButton( 60, 265, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 95, 266, 150, 35, 1006044, false, false ); // Ok + AddButton(60, 265, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(95, 266, 150, 35, 1006044, false, false); // Ok - AddButton( 295, 265, 4017, 4019, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 330, 266, 150, 35, 1006045, false, false ); // Cancel - } + AddButton(295, 265, 4017, 4019, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(330, 266, 150, 35, 1006045, false, false); // Cancel + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - { - if ( !RewardSystem.HasAccess( m_From, m_Entry ) ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + { + if (!RewardSystem.HasAccess(m_From, m_Entry)) + return; - Item item = m_Entry.Construct(); + Item item = m_Entry.Construct(); - if ( item != null ) - { - if ( item is RedSoulstone soulstone ) - soulstone.Account = m_From.Account.Username; + if (item != null) + { + if (item is RedSoulstone soulstone) + soulstone.Account = m_From.Account.Username; - if ( RewardSystem.ConsumeRewardPoint( m_From ) ) - m_From.AddToBackpack( item ); - else - item.Delete(); - } - } + if (RewardSystem.ConsumeRewardPoint(m_From)) + m_From.AddToBackpack(item); + else + item.Delete(); + } + } - int cur, max; + int cur, max; - RewardSystem.ComputeRewardInfo( m_From, out cur, out max ); + RewardSystem.ComputeRewardInfo(m_From, out cur, out max); - if ( cur < max ) - m_From.SendGump( new RewardNoticeGump( m_From ) ); - } - } -} + if (cur < max) + m_From.SendGump(new RewardNoticeGump(m_From)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardDemolitionGump.cs b/Scripts/Engines/VeteranRewards/RewardDemolitionGump.cs index eb79240cc..b3029325f 100644 --- a/Scripts/Engines/VeteranRewards/RewardDemolitionGump.cs +++ b/Scripts/Engines/VeteranRewards/RewardDemolitionGump.cs @@ -4,66 +4,71 @@ using Server.Network; namespace Server.Gumps { - public class RewardDemolitionGump : Gump - { - private IAddon m_Addon; + public class RewardDemolitionGump : Gump + { + private IAddon m_Addon; - private enum Buttons - { - Cancel, - Confirm, - } + public RewardDemolitionGump(IAddon addon, int question) : base(150, 50) + { + m_Addon = addon; - public RewardDemolitionGump( IAddon addon, int question ) : base( 150, 50 ) - { - m_Addon = addon; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + AddBackground(0, 0, 220, 170, 0x13BE); + AddBackground(10, 10, 200, 150, 0xBB8); - AddBackground( 0, 0, 220, 170, 0x13BE ); - AddBackground( 10, 10, 200, 150, 0xBB8 ); + AddHtmlLocalized(20, 30, 180, 60, question, false, false); // Do you wish to re-deed this decoration? - AddHtmlLocalized( 20, 30, 180, 60, question, false, false ); // Do you wish to re-deed this decoration? + AddHtmlLocalized(55, 100, 150, 25, 1011011, false, false); // CONTINUE + AddButton(20, 100, 0xFA5, 0xFA7, (int)Buttons.Confirm, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 100, 150, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 100, 0xFA5, 0xFA7, (int) Buttons.Confirm, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 125, 150, 25, 1011012, false, false); // CANCEL + AddButton(20, 125, 0xFA5, 0xFA7, (int)Buttons.Cancel, GumpButtonType.Reply, 0); + } - AddHtmlLocalized( 55, 125, 150, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 125, 0xFA5, 0xFA7, (int) Buttons.Cancel, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!(m_Addon is Item item) || item.Deleted) + return; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !(m_Addon is Item item) || item.Deleted ) - return; + if (info.ButtonID == (int)Buttons.Confirm) + { + Mobile m = sender.Mobile; + BaseHouse house = BaseHouse.FindHouseAt(m); - if ( info.ButtonID == (int) Buttons.Confirm ) - { - Mobile m = sender.Mobile; - BaseHouse house = BaseHouse.FindHouseAt( m ); + if (house?.IsOwner(m) == true) + { + if (m.InRange(item.Location, 2)) + { + Item deed = m_Addon.Deed; - if ( house?.IsOwner( m ) == true ) - { - if ( m.InRange( item.Location, 2 ) ) - { - Item deed = m_Addon.Deed; + if (deed != null) + { + m.AddToBackpack(deed); + house.Addons.Remove(item); + item.Delete(); + } + } + else + { + m.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + else + { + m.SendLocalizedMessage( + 1049784); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. + } + } + } - if ( deed != null ) - { - m.AddToBackpack( deed ); - house.Addons.Remove( item ); - item.Delete(); - } - } - else - m.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - else - m.SendLocalizedMessage( 1049784 ); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. - } - } - } -} + private enum Buttons + { + Cancel, + Confirm + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardEntry.cs b/Scripts/Engines/VeteranRewards/RewardEntry.cs index 1e9e9f585..61798575a 100644 --- a/Scripts/Engines/VeteranRewards/RewardEntry.cs +++ b/Scripts/Engines/VeteranRewards/RewardEntry.cs @@ -2,78 +2,80 @@ using System; namespace Server.Engines.VeteranRewards { - public class RewardEntry - { - public RewardList List { get; set; } + public class RewardEntry + { + public RewardEntry(RewardCategory category, int name, Type itemType, params object[] args) + { + Category = category; + ItemType = itemType; + RequiredExpansion = Expansion.None; + Name = name; + Args = args; + category.Entries.Add(this); + } - public RewardCategory Category { get; } + public RewardEntry(RewardCategory category, string name, Type itemType, params object[] args) + { + Category = category; + ItemType = itemType; + RequiredExpansion = Expansion.None; + NameString = name; + Args = args; + category.Entries.Add(this); + } - public Type ItemType { get; } + public RewardEntry(RewardCategory category, int name, Type itemType, Expansion requiredExpansion, + params object[] args) + { + Category = category; + ItemType = itemType; + RequiredExpansion = requiredExpansion; + Name = name; + Args = args; + category.Entries.Add(this); + } - public Expansion RequiredExpansion { get; } + public RewardEntry(RewardCategory category, string name, Type itemType, Expansion requiredExpansion, + params object[] args) + { + Category = category; + ItemType = itemType; + RequiredExpansion = requiredExpansion; + NameString = name; + Args = args; + category.Entries.Add(this); + } - public int Name { get; } + public RewardList List{ get; set; } - public string NameString { get; } + public RewardCategory Category{ get; } - public object[] Args { get; } + public Type ItemType{ get; } - public Item Construct() - { - try - { - Item item = Activator.CreateInstance( ItemType, Args ) as Item; + public Expansion RequiredExpansion{ get; } - if ( item is IRewardItem rewardItem ) - rewardItem.IsRewardItem = true; + public int Name{ get; } - return item; - } - catch - { - } + public string NameString{ get; } - return null; - } + public object[] Args{ get; } - public RewardEntry( RewardCategory category, int name, Type itemType, params object[] args ) - { - Category = category; - ItemType = itemType; - RequiredExpansion = Expansion.None; - Name = name; - Args = args; - category.Entries.Add( this ); - } + public Item Construct() + { + try + { + Item item = Activator.CreateInstance(ItemType, Args) as Item; - public RewardEntry( RewardCategory category, string name, Type itemType, params object[] args ) - { - Category = category; - ItemType = itemType; - RequiredExpansion = Expansion.None; - NameString = name; - Args = args; - category.Entries.Add( this ); - } + if (item is IRewardItem rewardItem) + rewardItem.IsRewardItem = true; - public RewardEntry( RewardCategory category, int name, Type itemType, Expansion requiredExpansion, params object[] args ) - { - Category = category; - ItemType = itemType; - RequiredExpansion = requiredExpansion; - Name = name; - Args = args; - category.Entries.Add( this ); - } + return item; + } + catch + { + } - public RewardEntry( RewardCategory category, string name, Type itemType, Expansion requiredExpansion, params object[] args ) - { - Category = category; - ItemType = itemType; - RequiredExpansion = requiredExpansion; - NameString = name; - Args = args; - category.Entries.Add( this ); - } - } -} + return null; + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardList.cs b/Scripts/Engines/VeteranRewards/RewardList.cs index 6323f9f38..4e8f85a94 100644 --- a/Scripts/Engines/VeteranRewards/RewardList.cs +++ b/Scripts/Engines/VeteranRewards/RewardList.cs @@ -2,19 +2,19 @@ using System; namespace Server.Engines.VeteranRewards { - public class RewardList - { - public TimeSpan Age { get; } + public class RewardList + { + public RewardList(TimeSpan interval, int index, RewardEntry[] entries) + { + Age = TimeSpan.FromDays(interval.TotalDays * index); + Entries = entries; - public RewardEntry[] Entries { get; } + for (int i = 0; i < entries.Length; ++i) + entries[i].List = this; + } - public RewardList( TimeSpan interval, int index, RewardEntry[] entries ) - { - Age = TimeSpan.FromDays( interval.TotalDays * index ); - Entries = entries; + public TimeSpan Age{ get; } - for ( int i = 0; i < entries.Length; ++i ) - entries[i].List = this; - } - } + public RewardEntry[] Entries{ get; } + } } \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardNoticeGump.cs b/Scripts/Engines/VeteranRewards/RewardNoticeGump.cs index 8d4d2672d..d2c72c640 100644 --- a/Scripts/Engines/VeteranRewards/RewardNoticeGump.cs +++ b/Scripts/Engines/VeteranRewards/RewardNoticeGump.cs @@ -3,36 +3,36 @@ using Server.Network; namespace Server.Engines.VeteranRewards { - public class RewardNoticeGump : Gump - { - private Mobile m_From; + public class RewardNoticeGump : Gump + { + private Mobile m_From; - public RewardNoticeGump( Mobile from ) : base( 0, 0 ) - { - m_From = from; + public RewardNoticeGump(Mobile from) : base(0, 0) + { + m_From = from; - from.CloseGump( typeof( RewardNoticeGump ) ); + from.CloseGump(typeof(RewardNoticeGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 10, 10, 500, 135, 2600 ); + AddBackground(10, 10, 500, 135, 2600); - /* You have reward items available. - * Click 'ok' below to get the selection menu or 'cancel' to be prompted upon your next login. - */ - AddHtmlLocalized( 52, 35, 420, 55, 1006046, true, true ); + /* You have reward items available. + * Click 'ok' below to get the selection menu or 'cancel' to be prompted upon your next login. + */ + AddHtmlLocalized(52, 35, 420, 55, 1006046, true, true); - AddButton( 60, 95, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 95, 96, 150, 35, 1006044, false, false ); // Ok + AddButton(60, 95, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(95, 96, 150, 35, 1006044, false, false); // Ok - AddButton( 285, 95, 4017, 4019, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 320, 96, 150, 35, 1006045, false, false ); // Cancel - } + AddButton(285, 95, 4017, 4019, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(320, 96, 150, 35, 1006045, false, false); // Cancel + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_From.SendGump( new RewardChoiceGump( m_From ) ); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_From.SendGump(new RewardChoiceGump(m_From)); + } + } } \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardOptionGump.cs b/Scripts/Engines/VeteranRewards/RewardOptionGump.cs index 9d7e9a900..14e7c12b1 100644 --- a/Scripts/Engines/VeteranRewards/RewardOptionGump.cs +++ b/Scripts/Engines/VeteranRewards/RewardOptionGump.cs @@ -3,95 +3,89 @@ using Server.Network; namespace Server.Gumps { - public interface IRewardOption - { - void GetOptions( RewardOptionList list ); - void OnOptionSelected( Mobile from, int choice ); - } + public interface IRewardOption + { + void GetOptions(RewardOptionList list); + void OnOptionSelected(Mobile from, int choice); + } - public class RewardOptionGump : Gump - { - private RewardOptionList m_Options = new RewardOptionList(); - private IRewardOption m_Option; + public class RewardOptionGump : Gump + { + private IRewardOption m_Option; + private RewardOptionList m_Options = new RewardOptionList(); - public RewardOptionGump( IRewardOption option ) : this( option, 0 ) - { - } + public RewardOptionGump(IRewardOption option) : this(option, 0) + { + } - public RewardOptionGump( IRewardOption option, int title ) : base( 60, 36 ) - { - m_Option = option; + public RewardOptionGump(IRewardOption option, int title) : base(60, 36) + { + m_Option = option; - m_Option?.GetOptions( m_Options ); + m_Option?.GetOptions(m_Options); - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL - if ( title > 0 ) - AddHtmlLocalized( 14, 12, 273, 20, title, 0x7FFF, false, false ); - else - AddHtmlLocalized( 14, 12, 273, 20, 1080392, 0x7FFF, false, false ); // Select your choice from the menu below. + if (title > 0) + AddHtmlLocalized(14, 12, 273, 20, title, 0x7FFF, false, false); + else + AddHtmlLocalized(14, 12, 273, 20, 1080392, 0x7FFF, false, false); // Select your choice from the menu below. - AddPage( 1 ); + AddPage(1); - for ( int i = 0; i < m_Options.Count; i++ ) - { - AddButton( 19, 49 + i * 24, 0x845, 0x846, m_Options[ i ].ID, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47 + i * 24, 213, 20, m_Options[ i ].Cliloc, 0x7FFF, false, false ); - } - } + for (int i = 0; i < m_Options.Count; i++) + { + AddButton(19, 49 + i * 24, 0x845, 0x846, m_Options[i].ID, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47 + i * 24, 213, 20, m_Options[i].Cliloc, 0x7FFF, false, false); + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Option != null && Contains( info.ButtonID ) ) - m_Option.OnOptionSelected( sender.Mobile, info.ButtonID ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Option != null && Contains(info.ButtonID)) + m_Option.OnOptionSelected(sender.Mobile, info.ButtonID); + } - private bool Contains( int chosen ) - { - if ( m_Options == null ) - return false; + private bool Contains(int chosen) + { + if (m_Options == null) + return false; - foreach ( RewardOption option in m_Options ) - { - if ( option.ID == chosen ) - return true; - } + foreach (RewardOption option in m_Options) + if (option.ID == chosen) + return true; - return false; - } - } + return false; + } + } - public class RewardOption - { - public int ID { get; } + public class RewardOption + { + public RewardOption(int id, int cliloc) + { + ID = id; + Cliloc = cliloc; + } - public int Cliloc { get; } + public int ID{ get; } - public RewardOption( int id, int cliloc ) - { - ID = id; - Cliloc = cliloc; - } - } + public int Cliloc{ get; } + } - public class RewardOptionList : List - { - public RewardOptionList() - { - } - - public void Add( int id, int cliloc ) - { - Add( new RewardOption( id, cliloc ) ); - } - } -} + public class RewardOptionList : List + { + public void Add(int id, int cliloc) + { + Add(new RewardOption(id, cliloc)); + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/VeteranRewards/RewardSystem.cs b/Scripts/Engines/VeteranRewards/RewardSystem.cs index aa865c436..0f07dd0c5 100644 --- a/Scripts/Engines/VeteranRewards/RewardSystem.cs +++ b/Scripts/Engines/VeteranRewards/RewardSystem.cs @@ -1,508 +1,510 @@ using System; +using System.Collections.Generic; +using Server.Accounting; using Server.Items; using Server.Mobiles; -using Server.Accounting; -using System.Collections.Generic; namespace Server.Engines.VeteranRewards { - public class RewardSystem - { - private static RewardCategory[] m_Categories; - private static RewardList[] m_Lists; - - public static RewardCategory[] Categories - { - get - { - if ( m_Categories == null ) - SetupRewardTables(); - - return m_Categories; - } - } - - public static RewardList[] Lists - { - get - { - if ( m_Lists == null ) - SetupRewardTables(); - - return m_Lists; - } - } - - public static bool Enabled = true; // change to true to enable vet rewards - public static bool SkillCapRewards = true; // assuming vet rewards are enabled, should total skill cap bonuses be awarded? (720 skills total at 4th level) - public static TimeSpan RewardInterval = TimeSpan.FromDays( 30.0 ); - - public static bool HasAccess( Mobile mob, RewardCategory category ) - { - List entries = category.Entries; - - for ( int j = 0; j < entries.Count; ++j ) - { - //RewardEntry entry = entries[j]; - if ( HasAccess( mob, entries[j] ) ) - { - return true; - } - } - return false; - } - - public static bool HasAccess( Mobile mob, RewardEntry entry ) - { - if ( Core.Expansion < entry.RequiredExpansion ) - { - return false; - } - - TimeSpan ts; - return HasAccess( mob, entry.List, out ts ); - } - - public static bool HasAccess( Mobile mob, RewardList list, out TimeSpan ts ) - { - if ( list == null ) - { - ts = TimeSpan.Zero; - return false; - } - - if ( !(mob.Account is Account acct) ) - { - ts = TimeSpan.Zero; - return false; - } - - TimeSpan totalTime = (DateTime.UtcNow - acct.Created); - - ts = ( list.Age - totalTime ); - - if ( ts <= TimeSpan.Zero ) - return true; - - return false; - } - - public static int GetRewardLevel( Mobile mob ) - { - if ( !(mob.Account is Account acct) ) - return 0; - - return GetRewardLevel( acct ); - } - - public static int GetRewardLevel( Account acct ) - { - TimeSpan totalTime = (DateTime.UtcNow - acct.Created); - - int level = (int)(totalTime.TotalDays / RewardInterval.TotalDays); - - if ( level < 0 ) - level = 0; - - return level; - } - - public static bool HasHalfLevel( Mobile mob ) - { - if ( !(mob.Account is Account acct) ) - return false; - - return HasHalfLevel( acct ); - } - - public static bool HasHalfLevel( Account acct ) - { - TimeSpan totalTime = (DateTime.UtcNow - acct.Created); - - double level = (totalTime.TotalDays / RewardInterval.TotalDays); - - return level >= 0.5; - } - - public static bool ConsumeRewardPoint( Mobile mob ) - { - ComputeRewardInfo( mob, out var cur, out var max ); - - if ( cur >= max ) - return false; - - if ( !(mob.Account is Account acct) ) - return false; - - //if ( mob.AccessLevel < AccessLevel.GameMaster ) - acct.SetTag( "numRewardsChosen", (cur + 1).ToString() ); - - return true; - } - - public static void ComputeRewardInfo( Mobile mob, out int cur, out int max ) - { - ComputeRewardInfo( mob, out cur, out max, out _ ); - } - - public static void ComputeRewardInfo( Mobile mob, out int cur, out int max, out int level ) - { - if ( !(mob.Account is Account acct) ) - { - cur = max = level = 0; - return; - } - - level = GetRewardLevel( acct ); - - if ( level == 0 ) - { - cur = max = 0; - return; - } - - string tag = acct.GetTag( "numRewardsChosen" ); - - if ( string.IsNullOrEmpty( tag ) ) - cur = 0; - else - cur = Utility.ToInt32( tag ); - - if ( level >= 6 ) - max = 9 + ((level - 6) * 2); - else - max = 2 + level; - } - - public static bool CheckIsUsableBy( Mobile from, Item item, object[] args ) - { - if ( m_Lists == null ) - SetupRewardTables(); - - bool isRelaxedRules = ( item is DyeTub || item is MonsterStatuette ); - - Type type = item.GetType(); - - for ( int i = 0; i < m_Lists.Length; ++i ) - { - RewardList list = m_Lists[i]; - RewardEntry[] entries = list.Entries; - TimeSpan ts; - - for ( int j = 0; j < entries.Length; ++j ) - { - if ( entries[j].ItemType == type ) - { - if ( args == null && entries[j].Args.Length == 0 ) - { - if ( (!isRelaxedRules || i > 0) && !HasAccess( from, list, out ts ) ) - { - from.SendLocalizedMessage( 1008126, true, Math.Ceiling( ts.TotalDays / 30.0 ).ToString() ); // Your account is not old enough to use this item. Months until you can use this item : - return false; - } - - return true; - } - - if ( args.Length == entries[j].Args.Length ) - { - bool match = true; - - for ( int k = 0; match && k < args.Length; ++k ) - match = ( args[k].Equals( entries[j].Args[k] ) ); - - if ( match ) - { - if ( (!isRelaxedRules || i > 0) && !HasAccess( from, list, out ts ) ) - { - from.SendLocalizedMessage( 1008126, true, Math.Ceiling( ts.TotalDays / 30.0 ).ToString() ); // Your account is not old enough to use this item. Months until you can use this item : - return false; - } - - return true; - } - } - } - } - } - - // no entry? - return true; - } - - public static int GetRewardYearLabel( Item item, object[] args ) - { - int level = GetRewardYear( item, args ); - - return 1076216 + ( ( level < 10 ) ? level : ( level < 12 ) ? (( level - 9 ) + 4240 ) : (( level - 11 ) + 37585 ) ); - } - - public static int GetRewardYear( Item item, object[] args ) - { - if ( m_Lists == null ) - SetupRewardTables(); - - Type type = item.GetType(); - - for ( int i = 0; i < m_Lists.Length; ++i ) - { - RewardList list = m_Lists[i]; - RewardEntry[] entries = list.Entries; - - for ( int j = 0; j < entries.Length; ++j ) - { - if ( entries[j].ItemType == type ) - { - if ( args == null && entries[j].Args.Length == 0 ) - return i + 1; - - if ( args.Length == entries[j].Args.Length ) - { - bool match = true; - - for ( int k = 0; match && k < args.Length; ++k ) - match = ( args[k].Equals( entries[j].Args[k] ) ); - - if ( match ) - return i + 1; - } - } - } - } - - // no entry? - return 0; - } - - public static void SetupRewardTables() - { - RewardCategory monsterStatues = new RewardCategory( 1049750 ); - RewardCategory cloaksAndRobes = new RewardCategory( 1049752 ); - RewardCategory etherealSteeds = new RewardCategory( 1049751 ); - RewardCategory specialDyeTubs = new RewardCategory( 1049753 ); - RewardCategory houseAddOns = new RewardCategory( 1049754 ); - RewardCategory miscellaneous = new RewardCategory( 1078596 ); - - m_Categories = new[] - { - monsterStatues, - cloaksAndRobes, - etherealSteeds, - specialDyeTubs, - houseAddOns, - miscellaneous - }; - - const int Bronze = 0x972; - const int Copper = 0x96D; - const int Golden = 0x8A5; - const int Agapite = 0x979; - const int Verite = 0x89F; - const int Valorite = 0x8AB; - const int IceGreen = 0x47F; - const int IceBlue = 0x482; - const int DarkGray = 0x497; - const int Fire = 0x489; - const int IceWhite = 0x47E; - const int JetBlack = 0x001; - const int Pink = 0x490; - const int Crimson = 0x485; - - m_Lists = new[] - { - new RewardList( RewardInterval, 1, new[] - { - new RewardEntry( specialDyeTubs, 1006008, typeof( RewardBlackDyeTub ) ), - new RewardEntry( specialDyeTubs, 1006013, typeof( FurnitureDyeTub ) ), - new RewardEntry( specialDyeTubs, 1006047, typeof( SpecialDyeTub ) ), - new RewardEntry( cloaksAndRobes, 1006009, typeof( RewardCloak ), Bronze, 1041286 ), - new RewardEntry( cloaksAndRobes, 1006010, typeof( RewardRobe ), Bronze, 1041287 ), - new RewardEntry( cloaksAndRobes, 1080366, typeof( RewardDress ), Expansion.ML, Bronze, 1080366 ), - new RewardEntry( cloaksAndRobes, 1006011, typeof( RewardCloak ), Copper, 1041288 ), - new RewardEntry( cloaksAndRobes, 1006012, typeof( RewardRobe ), Copper, 1041289 ), - new RewardEntry( cloaksAndRobes, 1080367, typeof( RewardDress ), Expansion.ML, Copper, 1080367 ), - new RewardEntry( monsterStatues, 1006024, typeof( MonsterStatuette ), MonsterStatuetteType.Crocodile ), - new RewardEntry( monsterStatues, 1006025, typeof( MonsterStatuette ), MonsterStatuetteType.Daemon ), - new RewardEntry( monsterStatues, 1006026, typeof( MonsterStatuette ), MonsterStatuetteType.Dragon ), - new RewardEntry( monsterStatues, 1006027, typeof( MonsterStatuette ), MonsterStatuetteType.EarthElemental ), - new RewardEntry( monsterStatues, 1006028, typeof( MonsterStatuette ), MonsterStatuetteType.Ettin ), - new RewardEntry( monsterStatues, 1006029, typeof( MonsterStatuette ), MonsterStatuetteType.Gargoyle ), - new RewardEntry( monsterStatues, 1006030, typeof( MonsterStatuette ), MonsterStatuetteType.Gorilla ), - new RewardEntry( monsterStatues, 1006031, typeof( MonsterStatuette ), MonsterStatuetteType.Lich ), - new RewardEntry( monsterStatues, 1006032, typeof( MonsterStatuette ), MonsterStatuetteType.Lizardman ), - new RewardEntry( monsterStatues, 1006033, typeof( MonsterStatuette ), MonsterStatuetteType.Ogre ), - new RewardEntry( monsterStatues, 1006034, typeof( MonsterStatuette ), MonsterStatuetteType.Orc ), - new RewardEntry( monsterStatues, 1006035, typeof( MonsterStatuette ), MonsterStatuetteType.Ratman ), - new RewardEntry( monsterStatues, 1006036, typeof( MonsterStatuette ), MonsterStatuetteType.Skeleton ), - new RewardEntry( monsterStatues, 1006037, typeof( MonsterStatuette ), MonsterStatuetteType.Troll ), - new RewardEntry( houseAddOns, 1062692, typeof( ContestMiniHouseDeed ), Expansion.AOS, MiniHouseType.MalasMountainPass ), - new RewardEntry( houseAddOns, 1072216, typeof( ContestMiniHouseDeed ), Expansion.SE, MiniHouseType.ChurchAtNight ), - new RewardEntry( miscellaneous, 1076155, typeof( RedSoulstone ), Expansion.ML ), - new RewardEntry( miscellaneous, 1080523, typeof( CommodityDeedBox ), Expansion.ML ), - } ), - new RewardList( RewardInterval, 2, new[] - { - new RewardEntry( specialDyeTubs, 1006052, typeof( LeatherDyeTub ) ), - new RewardEntry( cloaksAndRobes, 1006014, typeof( RewardCloak ), Agapite, 1041290 ), - new RewardEntry( cloaksAndRobes, 1006015, typeof( RewardRobe ), Agapite, 1041291 ), - new RewardEntry( cloaksAndRobes, 1080369, typeof( RewardDress ), Expansion.ML, Agapite, 1080369 ), - new RewardEntry( cloaksAndRobes, 1006016, typeof( RewardCloak ), Golden, 1041292 ), - new RewardEntry( cloaksAndRobes, 1006017, typeof( RewardRobe ), Golden, 1041293 ), - new RewardEntry( cloaksAndRobes, 1080368, typeof( RewardDress ), Expansion.ML, Golden, 1080368 ), - new RewardEntry( houseAddOns, 1006048, typeof( BannerDeed ) ), - new RewardEntry( houseAddOns, 1006049, typeof( FlamingHeadDeed ) ), - new RewardEntry( houseAddOns, 1080409, typeof( MinotaurStatueDeed ), Expansion.ML ) - } ), - new RewardList( RewardInterval, 3, new[] - { - new RewardEntry( cloaksAndRobes, 1006020, typeof( RewardCloak ), Verite, 1041294 ), - new RewardEntry( cloaksAndRobes, 1006021, typeof( RewardRobe ), Verite, 1041295 ), - new RewardEntry( cloaksAndRobes, 1080370, typeof( RewardDress ), Expansion.ML, Verite, 1080370 ), - new RewardEntry( cloaksAndRobes, 1006022, typeof( RewardCloak ), Valorite, 1041296 ), - new RewardEntry( cloaksAndRobes, 1006023, typeof( RewardRobe ), Valorite, 1041297 ), - new RewardEntry( cloaksAndRobes, 1080371, typeof( RewardDress ), Expansion.ML, Valorite, 1080371 ), - new RewardEntry( monsterStatues, 1006038, typeof( MonsterStatuette ), MonsterStatuetteType.Cow ), - new RewardEntry( monsterStatues, 1006039, typeof( MonsterStatuette ), MonsterStatuetteType.Zombie ), - new RewardEntry( monsterStatues, 1006040, typeof( MonsterStatuette ), MonsterStatuetteType.Llama ), - new RewardEntry( etherealSteeds, 1006019, typeof( EtherealHorse ) ), - new RewardEntry( etherealSteeds, 1006050, typeof( EtherealOstard ) ), - new RewardEntry( etherealSteeds, 1006051, typeof( EtherealLlama ) ), - new RewardEntry( houseAddOns, 1080407, typeof( PottedCactusDeed ), Expansion.ML ) - - } ), - new RewardList( RewardInterval, 4, new[] - { - new RewardEntry( specialDyeTubs, 1049740, typeof( RunebookDyeTub ) ), - new RewardEntry( cloaksAndRobes, 1049725, typeof( RewardCloak ), DarkGray, 1049757 ), - new RewardEntry( cloaksAndRobes, 1049726, typeof( RewardRobe ), DarkGray, 1049756 ), - new RewardEntry( cloaksAndRobes, 1080374, typeof( RewardDress ), Expansion.ML, DarkGray, 1080374 ), - new RewardEntry( cloaksAndRobes, 1049727, typeof( RewardCloak ), IceGreen, 1049759 ), - new RewardEntry( cloaksAndRobes, 1049728, typeof( RewardRobe ), IceGreen, 1049758 ), - new RewardEntry( cloaksAndRobes, 1080372, typeof( RewardDress ), Expansion.ML, IceGreen, 1080372 ), - - new RewardEntry( cloaksAndRobes, 1049729, typeof( RewardCloak ), IceBlue, 1049761 ), - new RewardEntry( cloaksAndRobes, 1049730, typeof( RewardRobe ), IceBlue, 1049760 ), - new RewardEntry( cloaksAndRobes, 1080373, typeof( RewardDress ), Expansion.ML, IceBlue, 1080373 ), - new RewardEntry( monsterStatues, 1049742, typeof( MonsterStatuette ), MonsterStatuetteType.Ophidian ), - new RewardEntry( monsterStatues, 1049743, typeof( MonsterStatuette ), MonsterStatuetteType.Reaper ), - new RewardEntry( monsterStatues, 1049744, typeof( MonsterStatuette ), MonsterStatuetteType.Mongbat ), - new RewardEntry( etherealSteeds, 1049746, typeof( EtherealKirin ) ), - new RewardEntry( etherealSteeds, 1049745, typeof( EtherealUnicorn ) ), - new RewardEntry( etherealSteeds, 1049747, typeof( EtherealRidgeback ) ), - new RewardEntry( houseAddOns, 1049737, typeof( DecorativeShieldDeed ) ), - new RewardEntry( houseAddOns, 1049738, typeof( HangingSkeletonDeed ) ) - } ), - new RewardList( RewardInterval, 5, new[] - { - new RewardEntry( specialDyeTubs, 1049741, typeof( StatuetteDyeTub ) ), - new RewardEntry( cloaksAndRobes, 1049731, typeof( RewardCloak ), JetBlack, 1049763 ), - new RewardEntry( cloaksAndRobes, 1049732, typeof( RewardRobe ), JetBlack, 1049762 ), - new RewardEntry( cloaksAndRobes, 1080377, typeof( RewardDress ), Expansion.ML, JetBlack, 1080377 ), - new RewardEntry( cloaksAndRobes, 1049733, typeof( RewardCloak ), IceWhite, 1049765 ), - new RewardEntry( cloaksAndRobes, 1049734, typeof( RewardRobe ), IceWhite, 1049764 ), - new RewardEntry( cloaksAndRobes, 1080376, typeof( RewardDress ), Expansion.ML, IceWhite, 1080376 ), - new RewardEntry( cloaksAndRobes, 1049735, typeof( RewardCloak ), Fire, 1049767 ), - new RewardEntry( cloaksAndRobes, 1049736, typeof( RewardRobe ), Fire, 1049766 ), - new RewardEntry( cloaksAndRobes, 1080375, typeof( RewardDress ), Expansion.ML, Fire, 1080375 ), - new RewardEntry( monsterStatues, 1049768, typeof( MonsterStatuette ), MonsterStatuetteType.Gazer ), - new RewardEntry( monsterStatues, 1049769, typeof( MonsterStatuette ), MonsterStatuetteType.FireElemental ), - new RewardEntry( monsterStatues, 1049770, typeof( MonsterStatuette ), MonsterStatuetteType.Wolf ), - new RewardEntry( etherealSteeds, 1049749, typeof( EtherealSwampDragon ) ), - new RewardEntry( etherealSteeds, 1049748, typeof( EtherealBeetle ) ), - new RewardEntry( houseAddOns, 1049739, typeof( StoneAnkhDeed ) ), - new RewardEntry( houseAddOns, 1080384, typeof( BloodyPentagramDeed ), Expansion.ML ) - } ), - new RewardList( RewardInterval, 6, new[] - { - new RewardEntry( houseAddOns, 1076188, typeof( CharacterStatueMaker ), Expansion.ML, StatueType.Jade ), - new RewardEntry( houseAddOns, 1076189, typeof( CharacterStatueMaker ), Expansion.ML, StatueType.Marble ), - new RewardEntry( houseAddOns, 1076190, typeof( CharacterStatueMaker ), Expansion.ML, StatueType.Bronze ), - new RewardEntry( houseAddOns, 1080527, typeof( RewardBrazierDeed ), Expansion.ML ) - } ), - new RewardList( RewardInterval, 7, new[] - { - new RewardEntry( houseAddOns, 1076157, typeof( CannonDeed ), Expansion.ML ), - new RewardEntry( houseAddOns, 1080550, typeof( TreeStumpDeed ), Expansion.ML ) - } ), - new RewardList( RewardInterval, 8, new[] - { - new RewardEntry( miscellaneous, 1076158, typeof( WeaponEngravingTool ), Expansion.ML ) - } ), - new RewardList( RewardInterval, 9, new[] - { - new RewardEntry( etherealSteeds, 1076159, typeof( RideablePolarBear ), Expansion.ML ), - new RewardEntry( houseAddOns, 1080549, typeof( WallBannerDeed ), Expansion.ML ) - } ), - new RewardList( RewardInterval, 10, new[] - { - new RewardEntry( monsterStatues, 1080520, typeof( MonsterStatuette ), Expansion.ML, MonsterStatuetteType.Harrower ), - new RewardEntry( monsterStatues, 1080521, typeof( MonsterStatuette ), Expansion.ML, MonsterStatuetteType.Efreet ), - - new RewardEntry( cloaksAndRobes, 1080382, typeof( RewardCloak ), Expansion.ML, Pink, 1080382 ), - new RewardEntry( cloaksAndRobes, 1080380, typeof( RewardRobe ), Expansion.ML, Pink, 1080380 ), - new RewardEntry( cloaksAndRobes, 1080378, typeof( RewardDress ), Expansion.ML, Pink, 1080378 ), - new RewardEntry( cloaksAndRobes, 1080383, typeof( RewardCloak ), Expansion.ML, Crimson, 1080383 ), - new RewardEntry( cloaksAndRobes, 1080381, typeof( RewardRobe ), Expansion.ML, Crimson, 1080381 ), - new RewardEntry( cloaksAndRobes, 1080379, typeof( RewardDress ), Expansion.ML, Crimson, 1080379 ), - - new RewardEntry( etherealSteeds, 1080386, typeof( EtherealCuSidhe ), Expansion.ML ), - - new RewardEntry( houseAddOns, 1080548, typeof( MiningCartDeed ), Expansion.ML ), - new RewardEntry( houseAddOns, 1080397, typeof( AnkhOfSacrificeDeed ), Expansion.ML ) - } ), - - new RewardList( RewardInterval, 11, new[] - { - new RewardEntry( etherealSteeds, 1113908, typeof( EtherealReptalon ), Expansion.ML ), - } ), - - new RewardList( RewardInterval, 12, new[] - { - new RewardEntry( etherealSteeds, 1113813, typeof( EtherealHiryu ), Expansion.ML ), - } ), - }; - } - public static void Initialize() - { - if ( Enabled ) - EventSink.Login += EventSink_Login; - } - - private static void EventSink_Login( LoginEventArgs e ) - { - if ( !e.Mobile.Alive ) - return; - - int cur, max, level; - - ComputeRewardInfo( e.Mobile, out cur, out max, out level ); - - if ( e.Mobile.SkillsCap == 7000 || e.Mobile.SkillsCap == 7050 || e.Mobile.SkillsCap == 7100 || e.Mobile.SkillsCap == 7150 || e.Mobile.SkillsCap == 7200 ) - { - if ( level > 4 ) - level = 4; - else if ( level < 0 ) - level = 0; - - if ( SkillCapRewards ) - e.Mobile.SkillsCap = 7000 + (level * 50); - else - e.Mobile.SkillsCap = 7000; - } - - if ( Core.ML && e.Mobile is PlayerMobile mobile && !mobile.HasStatReward && HasHalfLevel( mobile ) ) - { - mobile.HasStatReward = true; - mobile.StatCap += 5; - } - - if ( cur < max ) - e.Mobile.SendGump( new RewardNoticeGump( e.Mobile ) ); - } - } - - public interface IRewardItem - { - bool IsRewardItem{ get; set; } - } -} + public class RewardSystem + { + private static RewardCategory[] m_Categories; + private static RewardList[] m_Lists; + + public static bool Enabled = true; // change to true to enable vet rewards + + public static bool + SkillCapRewards = + true; // assuming vet rewards are enabled, should total skill cap bonuses be awarded? (720 skills total at 4th level) + + public static TimeSpan RewardInterval = TimeSpan.FromDays(30.0); + + public static RewardCategory[] Categories + { + get + { + if (m_Categories == null) + SetupRewardTables(); + + return m_Categories; + } + } + + public static RewardList[] Lists + { + get + { + if (m_Lists == null) + SetupRewardTables(); + + return m_Lists; + } + } + + public static bool HasAccess(Mobile mob, RewardCategory category) + { + List entries = category.Entries; + + for (int j = 0; j < entries.Count; ++j) + //RewardEntry entry = entries[j]; + if (HasAccess(mob, entries[j])) + return true; + return false; + } + + public static bool HasAccess(Mobile mob, RewardEntry entry) + { + if (Core.Expansion < entry.RequiredExpansion) return false; + + TimeSpan ts; + return HasAccess(mob, entry.List, out ts); + } + + public static bool HasAccess(Mobile mob, RewardList list, out TimeSpan ts) + { + if (list == null) + { + ts = TimeSpan.Zero; + return false; + } + + if (!(mob.Account is Account acct)) + { + ts = TimeSpan.Zero; + return false; + } + + TimeSpan totalTime = DateTime.UtcNow - acct.Created; + + ts = list.Age - totalTime; + + if (ts <= TimeSpan.Zero) + return true; + + return false; + } + + public static int GetRewardLevel(Mobile mob) + { + if (!(mob.Account is Account acct)) + return 0; + + return GetRewardLevel(acct); + } + + public static int GetRewardLevel(Account acct) + { + TimeSpan totalTime = DateTime.UtcNow - acct.Created; + + int level = (int)(totalTime.TotalDays / RewardInterval.TotalDays); + + if (level < 0) + level = 0; + + return level; + } + + public static bool HasHalfLevel(Mobile mob) + { + if (!(mob.Account is Account acct)) + return false; + + return HasHalfLevel(acct); + } + + public static bool HasHalfLevel(Account acct) + { + TimeSpan totalTime = DateTime.UtcNow - acct.Created; + + double level = totalTime.TotalDays / RewardInterval.TotalDays; + + return level >= 0.5; + } + + public static bool ConsumeRewardPoint(Mobile mob) + { + ComputeRewardInfo(mob, out int cur, out int max); + + if (cur >= max) + return false; + + if (!(mob.Account is Account acct)) + return false; + + //if ( mob.AccessLevel < AccessLevel.GameMaster ) + acct.SetTag("numRewardsChosen", (cur + 1).ToString()); + + return true; + } + + public static void ComputeRewardInfo(Mobile mob, out int cur, out int max) + { + ComputeRewardInfo(mob, out cur, out max, out _); + } + + public static void ComputeRewardInfo(Mobile mob, out int cur, out int max, out int level) + { + if (!(mob.Account is Account acct)) + { + cur = max = level = 0; + return; + } + + level = GetRewardLevel(acct); + + if (level == 0) + { + cur = max = 0; + return; + } + + string tag = acct.GetTag("numRewardsChosen"); + + if (string.IsNullOrEmpty(tag)) + cur = 0; + else + cur = Utility.ToInt32(tag); + + if (level >= 6) + max = 9 + (level - 6) * 2; + else + max = 2 + level; + } + + public static bool CheckIsUsableBy(Mobile from, Item item, object[] args) + { + if (m_Lists == null) + SetupRewardTables(); + + bool isRelaxedRules = item is DyeTub || item is MonsterStatuette; + + Type type = item.GetType(); + + for (int i = 0; i < m_Lists.Length; ++i) + { + RewardList list = m_Lists[i]; + RewardEntry[] entries = list.Entries; + TimeSpan ts; + + for (int j = 0; j < entries.Length; ++j) + if (entries[j].ItemType == type) + { + if (args == null && entries[j].Args.Length == 0) + { + if ((!isRelaxedRules || i > 0) && !HasAccess(from, list, out ts)) + { + from.SendLocalizedMessage(1008126, true, + Math.Ceiling(ts.TotalDays / 30.0) + .ToString()); // Your account is not old enough to use this item. Months until you can use this item : + return false; + } + + return true; + } + + if (args.Length == entries[j].Args.Length) + { + bool match = true; + + for (int k = 0; match && k < args.Length; ++k) + match = args[k].Equals(entries[j].Args[k]); + + if (match) + { + if ((!isRelaxedRules || i > 0) && !HasAccess(from, list, out ts)) + { + from.SendLocalizedMessage(1008126, true, + Math.Ceiling(ts.TotalDays / 30.0) + .ToString()); // Your account is not old enough to use this item. Months until you can use this item : + return false; + } + + return true; + } + } + } + } + + // no entry? + return true; + } + + public static int GetRewardYearLabel(Item item, object[] args) + { + int level = GetRewardYear(item, args); + + return 1076216 + (level < 10 ? level : level < 12 ? level - 9 + 4240 : level - 11 + 37585); + } + + public static int GetRewardYear(Item item, object[] args) + { + if (m_Lists == null) + SetupRewardTables(); + + Type type = item.GetType(); + + for (int i = 0; i < m_Lists.Length; ++i) + { + RewardList list = m_Lists[i]; + RewardEntry[] entries = list.Entries; + + for (int j = 0; j < entries.Length; ++j) + if (entries[j].ItemType == type) + { + if (args == null && entries[j].Args.Length == 0) + return i + 1; + + if (args.Length == entries[j].Args.Length) + { + bool match = true; + + for (int k = 0; match && k < args.Length; ++k) + match = args[k].Equals(entries[j].Args[k]); + + if (match) + return i + 1; + } + } + } + + // no entry? + return 0; + } + + public static void SetupRewardTables() + { + RewardCategory monsterStatues = new RewardCategory(1049750); + RewardCategory cloaksAndRobes = new RewardCategory(1049752); + RewardCategory etherealSteeds = new RewardCategory(1049751); + RewardCategory specialDyeTubs = new RewardCategory(1049753); + RewardCategory houseAddOns = new RewardCategory(1049754); + RewardCategory miscellaneous = new RewardCategory(1078596); + + m_Categories = new[] + { + monsterStatues, + cloaksAndRobes, + etherealSteeds, + specialDyeTubs, + houseAddOns, + miscellaneous + }; + + const int Bronze = 0x972; + const int Copper = 0x96D; + const int Golden = 0x8A5; + const int Agapite = 0x979; + const int Verite = 0x89F; + const int Valorite = 0x8AB; + const int IceGreen = 0x47F; + const int IceBlue = 0x482; + const int DarkGray = 0x497; + const int Fire = 0x489; + const int IceWhite = 0x47E; + const int JetBlack = 0x001; + const int Pink = 0x490; + const int Crimson = 0x485; + + m_Lists = new[] + { + new RewardList(RewardInterval, 1, new[] + { + new RewardEntry(specialDyeTubs, 1006008, typeof(RewardBlackDyeTub)), + new RewardEntry(specialDyeTubs, 1006013, typeof(FurnitureDyeTub)), + new RewardEntry(specialDyeTubs, 1006047, typeof(SpecialDyeTub)), + new RewardEntry(cloaksAndRobes, 1006009, typeof(RewardCloak), Bronze, 1041286), + new RewardEntry(cloaksAndRobes, 1006010, typeof(RewardRobe), Bronze, 1041287), + new RewardEntry(cloaksAndRobes, 1080366, typeof(RewardDress), Expansion.ML, Bronze, 1080366), + new RewardEntry(cloaksAndRobes, 1006011, typeof(RewardCloak), Copper, 1041288), + new RewardEntry(cloaksAndRobes, 1006012, typeof(RewardRobe), Copper, 1041289), + new RewardEntry(cloaksAndRobes, 1080367, typeof(RewardDress), Expansion.ML, Copper, 1080367), + new RewardEntry(monsterStatues, 1006024, typeof(MonsterStatuette), MonsterStatuetteType.Crocodile), + new RewardEntry(monsterStatues, 1006025, typeof(MonsterStatuette), MonsterStatuetteType.Daemon), + new RewardEntry(monsterStatues, 1006026, typeof(MonsterStatuette), MonsterStatuetteType.Dragon), + new RewardEntry(monsterStatues, 1006027, typeof(MonsterStatuette), MonsterStatuetteType.EarthElemental), + new RewardEntry(monsterStatues, 1006028, typeof(MonsterStatuette), MonsterStatuetteType.Ettin), + new RewardEntry(monsterStatues, 1006029, typeof(MonsterStatuette), MonsterStatuetteType.Gargoyle), + new RewardEntry(monsterStatues, 1006030, typeof(MonsterStatuette), MonsterStatuetteType.Gorilla), + new RewardEntry(monsterStatues, 1006031, typeof(MonsterStatuette), MonsterStatuetteType.Lich), + new RewardEntry(monsterStatues, 1006032, typeof(MonsterStatuette), MonsterStatuetteType.Lizardman), + new RewardEntry(monsterStatues, 1006033, typeof(MonsterStatuette), MonsterStatuetteType.Ogre), + new RewardEntry(monsterStatues, 1006034, typeof(MonsterStatuette), MonsterStatuetteType.Orc), + new RewardEntry(monsterStatues, 1006035, typeof(MonsterStatuette), MonsterStatuetteType.Ratman), + new RewardEntry(monsterStatues, 1006036, typeof(MonsterStatuette), MonsterStatuetteType.Skeleton), + new RewardEntry(monsterStatues, 1006037, typeof(MonsterStatuette), MonsterStatuetteType.Troll), + new RewardEntry(houseAddOns, 1062692, typeof(ContestMiniHouseDeed), Expansion.AOS, + MiniHouseType.MalasMountainPass), + new RewardEntry(houseAddOns, 1072216, typeof(ContestMiniHouseDeed), Expansion.SE, + MiniHouseType.ChurchAtNight), + new RewardEntry(miscellaneous, 1076155, typeof(RedSoulstone), Expansion.ML), + new RewardEntry(miscellaneous, 1080523, typeof(CommodityDeedBox), Expansion.ML) + }), + new RewardList(RewardInterval, 2, new[] + { + new RewardEntry(specialDyeTubs, 1006052, typeof(LeatherDyeTub)), + new RewardEntry(cloaksAndRobes, 1006014, typeof(RewardCloak), Agapite, 1041290), + new RewardEntry(cloaksAndRobes, 1006015, typeof(RewardRobe), Agapite, 1041291), + new RewardEntry(cloaksAndRobes, 1080369, typeof(RewardDress), Expansion.ML, Agapite, 1080369), + new RewardEntry(cloaksAndRobes, 1006016, typeof(RewardCloak), Golden, 1041292), + new RewardEntry(cloaksAndRobes, 1006017, typeof(RewardRobe), Golden, 1041293), + new RewardEntry(cloaksAndRobes, 1080368, typeof(RewardDress), Expansion.ML, Golden, 1080368), + new RewardEntry(houseAddOns, 1006048, typeof(BannerDeed)), + new RewardEntry(houseAddOns, 1006049, typeof(FlamingHeadDeed)), + new RewardEntry(houseAddOns, 1080409, typeof(MinotaurStatueDeed), Expansion.ML) + }), + new RewardList(RewardInterval, 3, new[] + { + new RewardEntry(cloaksAndRobes, 1006020, typeof(RewardCloak), Verite, 1041294), + new RewardEntry(cloaksAndRobes, 1006021, typeof(RewardRobe), Verite, 1041295), + new RewardEntry(cloaksAndRobes, 1080370, typeof(RewardDress), Expansion.ML, Verite, 1080370), + new RewardEntry(cloaksAndRobes, 1006022, typeof(RewardCloak), Valorite, 1041296), + new RewardEntry(cloaksAndRobes, 1006023, typeof(RewardRobe), Valorite, 1041297), + new RewardEntry(cloaksAndRobes, 1080371, typeof(RewardDress), Expansion.ML, Valorite, 1080371), + new RewardEntry(monsterStatues, 1006038, typeof(MonsterStatuette), MonsterStatuetteType.Cow), + new RewardEntry(monsterStatues, 1006039, typeof(MonsterStatuette), MonsterStatuetteType.Zombie), + new RewardEntry(monsterStatues, 1006040, typeof(MonsterStatuette), MonsterStatuetteType.Llama), + new RewardEntry(etherealSteeds, 1006019, typeof(EtherealHorse)), + new RewardEntry(etherealSteeds, 1006050, typeof(EtherealOstard)), + new RewardEntry(etherealSteeds, 1006051, typeof(EtherealLlama)), + new RewardEntry(houseAddOns, 1080407, typeof(PottedCactusDeed), Expansion.ML) + }), + new RewardList(RewardInterval, 4, new[] + { + new RewardEntry(specialDyeTubs, 1049740, typeof(RunebookDyeTub)), + new RewardEntry(cloaksAndRobes, 1049725, typeof(RewardCloak), DarkGray, 1049757), + new RewardEntry(cloaksAndRobes, 1049726, typeof(RewardRobe), DarkGray, 1049756), + new RewardEntry(cloaksAndRobes, 1080374, typeof(RewardDress), Expansion.ML, DarkGray, 1080374), + new RewardEntry(cloaksAndRobes, 1049727, typeof(RewardCloak), IceGreen, 1049759), + new RewardEntry(cloaksAndRobes, 1049728, typeof(RewardRobe), IceGreen, 1049758), + new RewardEntry(cloaksAndRobes, 1080372, typeof(RewardDress), Expansion.ML, IceGreen, 1080372), + + new RewardEntry(cloaksAndRobes, 1049729, typeof(RewardCloak), IceBlue, 1049761), + new RewardEntry(cloaksAndRobes, 1049730, typeof(RewardRobe), IceBlue, 1049760), + new RewardEntry(cloaksAndRobes, 1080373, typeof(RewardDress), Expansion.ML, IceBlue, 1080373), + new RewardEntry(monsterStatues, 1049742, typeof(MonsterStatuette), MonsterStatuetteType.Ophidian), + new RewardEntry(monsterStatues, 1049743, typeof(MonsterStatuette), MonsterStatuetteType.Reaper), + new RewardEntry(monsterStatues, 1049744, typeof(MonsterStatuette), MonsterStatuetteType.Mongbat), + new RewardEntry(etherealSteeds, 1049746, typeof(EtherealKirin)), + new RewardEntry(etherealSteeds, 1049745, typeof(EtherealUnicorn)), + new RewardEntry(etherealSteeds, 1049747, typeof(EtherealRidgeback)), + new RewardEntry(houseAddOns, 1049737, typeof(DecorativeShieldDeed)), + new RewardEntry(houseAddOns, 1049738, typeof(HangingSkeletonDeed)) + }), + new RewardList(RewardInterval, 5, new[] + { + new RewardEntry(specialDyeTubs, 1049741, typeof(StatuetteDyeTub)), + new RewardEntry(cloaksAndRobes, 1049731, typeof(RewardCloak), JetBlack, 1049763), + new RewardEntry(cloaksAndRobes, 1049732, typeof(RewardRobe), JetBlack, 1049762), + new RewardEntry(cloaksAndRobes, 1080377, typeof(RewardDress), Expansion.ML, JetBlack, 1080377), + new RewardEntry(cloaksAndRobes, 1049733, typeof(RewardCloak), IceWhite, 1049765), + new RewardEntry(cloaksAndRobes, 1049734, typeof(RewardRobe), IceWhite, 1049764), + new RewardEntry(cloaksAndRobes, 1080376, typeof(RewardDress), Expansion.ML, IceWhite, 1080376), + new RewardEntry(cloaksAndRobes, 1049735, typeof(RewardCloak), Fire, 1049767), + new RewardEntry(cloaksAndRobes, 1049736, typeof(RewardRobe), Fire, 1049766), + new RewardEntry(cloaksAndRobes, 1080375, typeof(RewardDress), Expansion.ML, Fire, 1080375), + new RewardEntry(monsterStatues, 1049768, typeof(MonsterStatuette), MonsterStatuetteType.Gazer), + new RewardEntry(monsterStatues, 1049769, typeof(MonsterStatuette), MonsterStatuetteType.FireElemental), + new RewardEntry(monsterStatues, 1049770, typeof(MonsterStatuette), MonsterStatuetteType.Wolf), + new RewardEntry(etherealSteeds, 1049749, typeof(EtherealSwampDragon)), + new RewardEntry(etherealSteeds, 1049748, typeof(EtherealBeetle)), + new RewardEntry(houseAddOns, 1049739, typeof(StoneAnkhDeed)), + new RewardEntry(houseAddOns, 1080384, typeof(BloodyPentagramDeed), Expansion.ML) + }), + new RewardList(RewardInterval, 6, new[] + { + new RewardEntry(houseAddOns, 1076188, typeof(CharacterStatueMaker), Expansion.ML, StatueType.Jade), + new RewardEntry(houseAddOns, 1076189, typeof(CharacterStatueMaker), Expansion.ML, StatueType.Marble), + new RewardEntry(houseAddOns, 1076190, typeof(CharacterStatueMaker), Expansion.ML, StatueType.Bronze), + new RewardEntry(houseAddOns, 1080527, typeof(RewardBrazierDeed), Expansion.ML) + }), + new RewardList(RewardInterval, 7, new[] + { + new RewardEntry(houseAddOns, 1076157, typeof(CannonDeed), Expansion.ML), + new RewardEntry(houseAddOns, 1080550, typeof(TreeStumpDeed), Expansion.ML) + }), + new RewardList(RewardInterval, 8, new[] + { + new RewardEntry(miscellaneous, 1076158, typeof(WeaponEngravingTool), Expansion.ML) + }), + new RewardList(RewardInterval, 9, new[] + { + new RewardEntry(etherealSteeds, 1076159, typeof(RideablePolarBear), Expansion.ML), + new RewardEntry(houseAddOns, 1080549, typeof(WallBannerDeed), Expansion.ML) + }), + new RewardList(RewardInterval, 10, new[] + { + new RewardEntry(monsterStatues, 1080520, typeof(MonsterStatuette), Expansion.ML, + MonsterStatuetteType.Harrower), + new RewardEntry(monsterStatues, 1080521, typeof(MonsterStatuette), Expansion.ML, + MonsterStatuetteType.Efreet), + + new RewardEntry(cloaksAndRobes, 1080382, typeof(RewardCloak), Expansion.ML, Pink, 1080382), + new RewardEntry(cloaksAndRobes, 1080380, typeof(RewardRobe), Expansion.ML, Pink, 1080380), + new RewardEntry(cloaksAndRobes, 1080378, typeof(RewardDress), Expansion.ML, Pink, 1080378), + new RewardEntry(cloaksAndRobes, 1080383, typeof(RewardCloak), Expansion.ML, Crimson, 1080383), + new RewardEntry(cloaksAndRobes, 1080381, typeof(RewardRobe), Expansion.ML, Crimson, 1080381), + new RewardEntry(cloaksAndRobes, 1080379, typeof(RewardDress), Expansion.ML, Crimson, 1080379), + + new RewardEntry(etherealSteeds, 1080386, typeof(EtherealCuSidhe), Expansion.ML), + + new RewardEntry(houseAddOns, 1080548, typeof(MiningCartDeed), Expansion.ML), + new RewardEntry(houseAddOns, 1080397, typeof(AnkhOfSacrificeDeed), Expansion.ML) + }), + + new RewardList(RewardInterval, 11, new[] + { + new RewardEntry(etherealSteeds, 1113908, typeof(EtherealReptalon), Expansion.ML) + }), + + new RewardList(RewardInterval, 12, new[] + { + new RewardEntry(etherealSteeds, 1113813, typeof(EtherealHiryu), Expansion.ML) + }) + }; + } + + public static void Initialize() + { + if (Enabled) + EventSink.Login += EventSink_Login; + } + + private static void EventSink_Login(LoginEventArgs e) + { + if (!e.Mobile.Alive) + return; + + int cur, max, level; + + ComputeRewardInfo(e.Mobile, out cur, out max, out level); + + if (e.Mobile.SkillsCap == 7000 || e.Mobile.SkillsCap == 7050 || e.Mobile.SkillsCap == 7100 || + e.Mobile.SkillsCap == 7150 || e.Mobile.SkillsCap == 7200) + { + if (level > 4) + level = 4; + else if (level < 0) + level = 0; + + if (SkillCapRewards) + e.Mobile.SkillsCap = 7000 + level * 50; + else + e.Mobile.SkillsCap = 7000; + } + + if (Core.ML && e.Mobile is PlayerMobile mobile && !mobile.HasStatReward && HasHalfLevel(mobile)) + { + mobile.HasStatReward = true; + mobile.StatCap += 5; + } + + if (cur < max) + e.Mobile.SendGump(new RewardNoticeGump(e.Mobile)); + } + } + + public interface IRewardItem + { + bool IsRewardItem{ get; set; } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/Compassion.cs b/Scripts/Engines/Virtues/Compassion.cs index 207df3efa..3d5d66efc 100644 --- a/Scripts/Engines/Virtues/Compassion.cs +++ b/Scripts/Engines/Virtues/Compassion.cs @@ -3,38 +3,38 @@ using Server.Mobiles; namespace Server { - public class CompassionVirtue - { - private static TimeSpan LossDelay = TimeSpan.FromDays( 7.0 ); - private const int LossAmount = 500; + public class CompassionVirtue + { + private const int LossAmount = 500; + private static TimeSpan LossDelay = TimeSpan.FromDays(7.0); - public static void Initialize() - { - VirtueGump.Register( 105, OnVirtueUsed ); - } + public static void Initialize() + { + VirtueGump.Register(105, OnVirtueUsed); + } - public static void OnVirtueUsed( Mobile from ) - { - from.SendLocalizedMessage( 1053001 ); // This virtue is not activated through the virtue menu. - } + public static void OnVirtueUsed(Mobile from) + { + from.SendLocalizedMessage(1053001); // This virtue is not activated through the virtue menu. + } - public static void CheckAtrophy( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return; + public static void CheckAtrophy(Mobile from) + { + if (!(from is PlayerMobile pm)) + return; - try - { - if ( (pm.LastCompassionLoss + LossDelay) < DateTime.UtcNow ) - { - VirtueHelper.Atrophy( from, VirtueName.Compassion, LossAmount ); - //OSI has no cliloc message for losing compassion. Weird. - pm.LastCompassionLoss = DateTime.UtcNow; - } - } - catch - { - } - } - } -} + try + { + if (pm.LastCompassionLoss + LossDelay < DateTime.UtcNow) + { + VirtueHelper.Atrophy(from, VirtueName.Compassion, LossAmount); + //OSI has no cliloc message for losing compassion. Weird. + pm.LastCompassionLoss = DateTime.UtcNow; + } + } + catch + { + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/Honor.cs b/Scripts/Engines/Virtues/Honor.cs index cdf67526c..91a792460 100644 --- a/Scripts/Engines/Virtues/Honor.cs +++ b/Scripts/Engines/Virtues/Honor.cs @@ -1,418 +1,409 @@ using System; -using Server.Mobiles; using Server.Gumps; -using Server.Targeting; +using Server.Mobiles; using Server.Regions; +using Server.Targeting; namespace Server { - public class HonorVirtue - { - - private static readonly TimeSpan UseDelay = TimeSpan.FromMinutes( 5.0 ); - - public static void Initialize() - { - VirtueGump.Register( 107, OnVirtueUsed ); - } - - private static void OnVirtueUsed( Mobile from ) - { - if ( from.Alive ) - { - from.SendLocalizedMessage( 1063160 ); // Target what you wish to honor. - from.Target = new InternalTarget(); - } - } - - private class InternalTarget : Target - { - public InternalTarget() : base( 12, false, TargetFlags.None ) - { - CheckLOS = true; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !(from is PlayerMobile pm) ) - return; - - if ( targeted == pm ) - { - EmbraceHonor( pm ); - } - else if ( targeted is Mobile mobile ) - Honor( pm, mobile ); - } - - protected override void OnTargetOutOfRange( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 1063232 ); // You are too far away to honor your opponent - } - } - - private static int GetHonorDuration( PlayerMobile from ) - { - switch ( VirtueHelper.GetLevel( from, VirtueName.Honor ) ) - { - case VirtueLevel.Seeker: return 30; - case VirtueLevel.Follower: return 90; - case VirtueLevel.Knight: return 300; - - default: return 0 ; - } - } - - private static void EmbraceHonor( PlayerMobile pm ) - { - if ( pm.HonorActive ) - { - pm.SendLocalizedMessage( 1063230 ); // You must wait awhile before you can embrace honor again. - return; - } - - if ( GetHonorDuration( pm ) == 0 ) - { - pm.SendLocalizedMessage( 1063234 ); // You do not have enough honor to do that - return; - } - - TimeSpan waitTime = DateTime.UtcNow - pm.LastHonorUse; - if ( waitTime < UseDelay ) - { - TimeSpan remainingTime = UseDelay - waitTime; - int remainingMinutes = (int) Math.Ceiling( remainingTime.TotalMinutes ); - - pm.SendLocalizedMessage( 1063240, remainingMinutes.ToString() ); // You must wait ~1_HONOR_WAIT~ minutes before embracing honor again - return; - } - - pm.SendGump( new HonorSelf( pm ) ); - - } - - public static void ActivateEmbrace( PlayerMobile pm ) - { - int duration = GetHonorDuration( pm ); - int usedPoints; - - if ( pm.Virtues.Honor < 4399) - usedPoints = 400; - else if ( pm.Virtues.Honor < 10599 ) - usedPoints = 600; - else - usedPoints = 1000; - - VirtueHelper.Atrophy( pm, VirtueName.Honor, usedPoints ); - - pm.HonorActive = true; - pm.SendLocalizedMessage( 1063235 ); // You embrace your honor - - Timer.DelayCall( TimeSpan.FromSeconds( duration ), - delegate { - pm.HonorActive = false; - pm.LastHonorUse = DateTime.UtcNow; - pm.SendLocalizedMessage( 1063236 ); // You no longer embrace your honor - } ); - } - - private static void Honor( PlayerMobile source, Mobile target ) - { - IHonorTarget honorTarget = target as IHonorTarget; - GuardedRegion reg = (GuardedRegion) source.Region.GetRegion( typeof( GuardedRegion ) ); - Map map = source.Map; - - if ( honorTarget == null ) - return; - - if ( honorTarget.ReceivedHonorContext != null ) - { - if ( honorTarget.ReceivedHonorContext.Source == source ) - return; - - if ( honorTarget.ReceivedHonorContext.CheckDistance() ) - { - source.SendLocalizedMessage( 1063233 ); // Somebody else is honoring this opponent - return; - } - } - - if ( target.Hits < target.HitsMax ) - { - source.SendLocalizedMessage( 1063166 ); // You cannot honor this monster because it is too damaged. - return; - } - - if ( target.Body.IsHuman && (!(target is BaseCreature cret) || (!cret.AlwaysAttackable && !cret.AlwaysMurderer)) ) - { - - if ( reg == null || reg.IsDisabled() ) - { - //Allow honor on blue if Out of guardzone - } - else if ( map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0 ) - { - //Allow honor on blue if in Fel - } - else - { - source.SendLocalizedMessage( 1001018 ); // You cannot perform negative acts - return; //cannot honor in trammel town on blue - } - } - - if ( Core.ML && target is PlayerMobile ) - { - source.SendLocalizedMessage( 1075614 ); // You cannot honor other players. - return; - } - - source.SentHonorContext?.Cancel(); - - new HonorContext( source, target ); - - source.Direction = source.GetDirectionTo( target ); - - if ( !source.Mounted ) - source.Animate( 32, 5, 1, true, true, 0 ); - - } - } - - public interface IHonorTarget - { - HonorContext ReceivedHonorContext{ get; set; } - } - - public class HonorContext - { - private double m_HonorDamage; - private int m_TotalDamage; - - private enum FirstHit - { - NotDelivered, - Delivered, - Granted - } - - private FirstHit m_FirstHit; - private bool m_Poisoned; - private Point3D m_InitialLocation; - private Map m_InitialMap; - - private InternalTimer m_Timer; - - public PlayerMobile Source { get; } - - public Mobile Target { get; } - - public HonorContext( PlayerMobile source, Mobile target ) - { - Source = source; - Target = target; - - m_FirstHit = FirstHit.NotDelivered; - m_Poisoned = false; - - m_InitialLocation = source.Location; - m_InitialMap = source.Map; - - source.SentHonorContext = this; - ((IHonorTarget)target).ReceivedHonorContext = this; - - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - source.m_hontime = (DateTime.UtcNow + TimeSpan.FromMinutes( 40 )); - - Timer.DelayCall( TimeSpan.FromMinutes( 40 ), - delegate { - if (source.m_hontime < DateTime.UtcNow && source.SentHonorContext != null) - { - Cancel(); - } - } ); - } - - public void OnSourceDamaged( Mobile from, int amount ) - { - if ( from != Target ) - return; - - if ( m_FirstHit == FirstHit.NotDelivered ) - m_FirstHit = FirstHit.Granted; - } - - public void OnTargetPoisoned() - { - m_Poisoned = true; // Set this flag for OnTargetDamaged which will be called next - } - - public void OnTargetDamaged( Mobile from, int amount ) - { - if ( m_FirstHit == FirstHit.NotDelivered ) - m_FirstHit = FirstHit.Delivered; - - if ( m_Poisoned ) - { - m_HonorDamage += amount * 0.8; - m_Poisoned = false; // Reset the flag - - return; - } - - m_TotalDamage += amount; - - if ( from == Source ) - { - if ( Target.CanSee( Source ) && Target.InLOS( Source ) && ( Source.InRange( Target, 1 ) - || ( Source.Location == m_InitialLocation && Source.Map == m_InitialMap ) ) ) - { - m_HonorDamage += amount; - } - else - { - m_HonorDamage += amount * 0.8; - } - } - else if ( from is BaseCreature creature && creature.GetMaster() == Source ) - { - m_HonorDamage += amount * 0.8; - } - } - - public void OnTargetHit( Mobile from ) - { - if ( from != Source || PerfectionDamageBonus == 100 ) - return; - - int bushido = (int) from.Skills.Bushido.Value; - if ( bushido < 50 ) - return; - - PerfectionDamageBonus += bushido / 10; - - if ( PerfectionDamageBonus >= 100 ) - { - PerfectionDamageBonus = 100; - Source.SendLocalizedMessage( 1063254 ); // You have Achieved Perfection in inflicting damage to this opponent! - } - else - { - Source.SendLocalizedMessage( 1063255 ); // You gain in Perfection as you precisely strike your opponent. - } - } - - public void OnTargetMissed( Mobile from ) - { - if ( from != Source || PerfectionDamageBonus == 0 ) - return; - - PerfectionDamageBonus -= 25; - - if ( PerfectionDamageBonus <= 0 ) - { - PerfectionDamageBonus = 0; - Source.SendLocalizedMessage( 1063256 ); // You have lost all Perfection in fighting this opponent. - } - else - { - Source.SendLocalizedMessage( 1063257 ); // You have lost some Perfection in fighting this opponent. - } - } - - public void OnSourceBeneficialAction( Mobile to ) - { - if ( to != Target ) - return; - - if ( PerfectionDamageBonus >= 0 ) - { - PerfectionDamageBonus = 0; - Source.SendLocalizedMessage( 1063256 ); // You have lost all Perfection in fighting this opponent. - } - } - - public void OnSourceKilled() - { - } - - public void OnTargetKilled() - { - Cancel(); - - int targetFame = Target.Fame; - - if ( PerfectionDamageBonus > 0 ) - { - int restore = Math.Min( PerfectionDamageBonus * ( targetFame + 5000 ) / 25000, 10 ); - - Source.Hits += restore; - Source.Stam += restore; - Source.Mana += restore; - } - - if ( Source.Virtues.Honor > targetFame ) - return; - - double dGain = ( targetFame / 100 ) * (m_HonorDamage / m_TotalDamage ); //Initial honor gain is 100th of the monsters honor - - if ( m_HonorDamage == m_TotalDamage && m_FirstHit == FirstHit.Granted) - dGain = dGain * 1.5; //honor gain is increased alot more if the combat was fully honorable - else - dGain = dGain * 0.9; - - int gain = Math.Min( (int)dGain, 200 ); - - if ( gain < 1 ) - gain=1; //Minimum gain of 1 honor when the honor is under the monsters fame - - if ( VirtueHelper.IsHighestPath( Source, VirtueName.Honor ) ) - { - Source.SendLocalizedMessage( 1063228 ); // You cannot gain more Honor. - return; - } - - bool gainedPath = false; - if ( VirtueHelper.Award( Source, VirtueName.Honor, (int) gain, ref gainedPath ) ) - { - if ( gainedPath ) - Source.SendLocalizedMessage( 1063226 ); // You have gained a path in Honor! - else - Source.SendLocalizedMessage( 1063225 ); // You have gained in Honor. - } - } - - public int PerfectionDamageBonus { get; private set; } - - public int PerfectionLuckBonus => (PerfectionDamageBonus * PerfectionDamageBonus) / 10; - - public bool CheckDistance() - { - return true; - } - - public void Cancel() - { - Source.SentHonorContext = null; - ((IHonorTarget)Target).ReceivedHonorContext = null; - - m_Timer.Stop(); - } - - private class InternalTimer : Timer - { - private HonorContext m_Context; - - public InternalTimer( HonorContext context ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Context = context; - } - - protected override void OnTick() - { - m_Context.CheckDistance(); - } - } - } -} + public class HonorVirtue + { + private static readonly TimeSpan UseDelay = TimeSpan.FromMinutes(5.0); + + public static void Initialize() + { + VirtueGump.Register(107, OnVirtueUsed); + } + + private static void OnVirtueUsed(Mobile from) + { + if (from.Alive) + { + from.SendLocalizedMessage(1063160); // Target what you wish to honor. + from.Target = new InternalTarget(); + } + } + + private static int GetHonorDuration(PlayerMobile from) + { + switch (VirtueHelper.GetLevel(from, VirtueName.Honor)) + { + case VirtueLevel.Seeker: return 30; + case VirtueLevel.Follower: return 90; + case VirtueLevel.Knight: return 300; + + default: return 0; + } + } + + private static void EmbraceHonor(PlayerMobile pm) + { + if (pm.HonorActive) + { + pm.SendLocalizedMessage(1063230); // You must wait awhile before you can embrace honor again. + return; + } + + if (GetHonorDuration(pm) == 0) + { + pm.SendLocalizedMessage(1063234); // You do not have enough honor to do that + return; + } + + TimeSpan waitTime = DateTime.UtcNow - pm.LastHonorUse; + if (waitTime < UseDelay) + { + TimeSpan remainingTime = UseDelay - waitTime; + int remainingMinutes = (int)Math.Ceiling(remainingTime.TotalMinutes); + + pm.SendLocalizedMessage(1063240, + remainingMinutes.ToString()); // You must wait ~1_HONOR_WAIT~ minutes before embracing honor again + return; + } + + pm.SendGump(new HonorSelf(pm)); + } + + public static void ActivateEmbrace(PlayerMobile pm) + { + int duration = GetHonorDuration(pm); + int usedPoints; + + if (pm.Virtues.Honor < 4399) + usedPoints = 400; + else if (pm.Virtues.Honor < 10599) + usedPoints = 600; + else + usedPoints = 1000; + + VirtueHelper.Atrophy(pm, VirtueName.Honor, usedPoints); + + pm.HonorActive = true; + pm.SendLocalizedMessage(1063235); // You embrace your honor + + Timer.DelayCall(TimeSpan.FromSeconds(duration), + delegate + { + pm.HonorActive = false; + pm.LastHonorUse = DateTime.UtcNow; + pm.SendLocalizedMessage(1063236); // You no longer embrace your honor + }); + } + + private static void Honor(PlayerMobile source, Mobile target) + { + IHonorTarget honorTarget = target as IHonorTarget; + GuardedRegion reg = (GuardedRegion)source.Region.GetRegion(typeof(GuardedRegion)); + Map map = source.Map; + + if (honorTarget == null) + return; + + if (honorTarget.ReceivedHonorContext != null) + { + if (honorTarget.ReceivedHonorContext.Source == source) + return; + + if (honorTarget.ReceivedHonorContext.CheckDistance()) + { + source.SendLocalizedMessage(1063233); // Somebody else is honoring this opponent + return; + } + } + + if (target.Hits < target.HitsMax) + { + source.SendLocalizedMessage(1063166); // You cannot honor this monster because it is too damaged. + return; + } + + if (target.Body.IsHuman && (!(target is BaseCreature cret) || !cret.AlwaysAttackable && !cret.AlwaysMurderer)) + { + if (reg == null || reg.IsDisabled()) + { + //Allow honor on blue if Out of guardzone + } + else if (map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0) + { + //Allow honor on blue if in Fel + } + else + { + source.SendLocalizedMessage(1001018); // You cannot perform negative acts + return; //cannot honor in trammel town on blue + } + } + + if (Core.ML && target is PlayerMobile) + { + source.SendLocalizedMessage(1075614); // You cannot honor other players. + return; + } + + source.SentHonorContext?.Cancel(); + + new HonorContext(source, target); + + source.Direction = source.GetDirectionTo(target); + + if (!source.Mounted) + source.Animate(32, 5, 1, true, true, 0); + } + + private class InternalTarget : Target + { + public InternalTarget() : base(12, false, TargetFlags.None) + { + CheckLOS = true; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!(from is PlayerMobile pm)) + return; + + if (targeted == pm) + EmbraceHonor(pm); + else if (targeted is Mobile mobile) + Honor(pm, mobile); + } + + protected override void OnTargetOutOfRange(Mobile from, object targeted) + { + from.SendLocalizedMessage(1063232); // You are too far away to honor your opponent + } + } + } + + public interface IHonorTarget + { + HonorContext ReceivedHonorContext{ get; set; } + } + + public class HonorContext + { + private FirstHit m_FirstHit; + private double m_HonorDamage; + private Point3D m_InitialLocation; + private Map m_InitialMap; + private bool m_Poisoned; + + private InternalTimer m_Timer; + private int m_TotalDamage; + + public HonorContext(PlayerMobile source, Mobile target) + { + Source = source; + Target = target; + + m_FirstHit = FirstHit.NotDelivered; + m_Poisoned = false; + + m_InitialLocation = source.Location; + m_InitialMap = source.Map; + + source.SentHonorContext = this; + ((IHonorTarget)target).ReceivedHonorContext = this; + + m_Timer = new InternalTimer(this); + m_Timer.Start(); + source.m_hontime = DateTime.UtcNow + TimeSpan.FromMinutes(40); + + Timer.DelayCall(TimeSpan.FromMinutes(40), + delegate + { + if (source.m_hontime < DateTime.UtcNow && source.SentHonorContext != null) Cancel(); + }); + } + + public PlayerMobile Source{ get; } + + public Mobile Target{ get; } + + public int PerfectionDamageBonus{ get; private set; } + + public int PerfectionLuckBonus => PerfectionDamageBonus * PerfectionDamageBonus / 10; + + public void OnSourceDamaged(Mobile from, int amount) + { + if (from != Target) + return; + + if (m_FirstHit == FirstHit.NotDelivered) + m_FirstHit = FirstHit.Granted; + } + + public void OnTargetPoisoned() + { + m_Poisoned = true; // Set this flag for OnTargetDamaged which will be called next + } + + public void OnTargetDamaged(Mobile from, int amount) + { + if (m_FirstHit == FirstHit.NotDelivered) + m_FirstHit = FirstHit.Delivered; + + if (m_Poisoned) + { + m_HonorDamage += amount * 0.8; + m_Poisoned = false; // Reset the flag + + return; + } + + m_TotalDamage += amount; + + if (from == Source) + { + if (Target.CanSee(Source) && Target.InLOS(Source) && (Source.InRange(Target, 1) + || Source.Location == m_InitialLocation && + Source.Map == m_InitialMap)) + m_HonorDamage += amount; + else + m_HonorDamage += amount * 0.8; + } + else if (from is BaseCreature creature && creature.GetMaster() == Source) + { + m_HonorDamage += amount * 0.8; + } + } + + public void OnTargetHit(Mobile from) + { + if (from != Source || PerfectionDamageBonus == 100) + return; + + int bushido = (int)from.Skills.Bushido.Value; + if (bushido < 50) + return; + + PerfectionDamageBonus += bushido / 10; + + if (PerfectionDamageBonus >= 100) + { + PerfectionDamageBonus = 100; + Source.SendLocalizedMessage(1063254); // You have Achieved Perfection in inflicting damage to this opponent! + } + else + { + Source.SendLocalizedMessage(1063255); // You gain in Perfection as you precisely strike your opponent. + } + } + + public void OnTargetMissed(Mobile from) + { + if (from != Source || PerfectionDamageBonus == 0) + return; + + PerfectionDamageBonus -= 25; + + if (PerfectionDamageBonus <= 0) + { + PerfectionDamageBonus = 0; + Source.SendLocalizedMessage(1063256); // You have lost all Perfection in fighting this opponent. + } + else + { + Source.SendLocalizedMessage(1063257); // You have lost some Perfection in fighting this opponent. + } + } + + public void OnSourceBeneficialAction(Mobile to) + { + if (to != Target) + return; + + if (PerfectionDamageBonus >= 0) + { + PerfectionDamageBonus = 0; + Source.SendLocalizedMessage(1063256); // You have lost all Perfection in fighting this opponent. + } + } + + public void OnSourceKilled() + { + } + + public void OnTargetKilled() + { + Cancel(); + + int targetFame = Target.Fame; + + if (PerfectionDamageBonus > 0) + { + int restore = Math.Min(PerfectionDamageBonus * (targetFame + 5000) / 25000, 10); + + Source.Hits += restore; + Source.Stam += restore; + Source.Mana += restore; + } + + if (Source.Virtues.Honor > targetFame) + return; + + double dGain = + targetFame / 100 * (m_HonorDamage / m_TotalDamage); //Initial honor gain is 100th of the monsters honor + + if (m_HonorDamage == m_TotalDamage && m_FirstHit == FirstHit.Granted) + dGain = dGain * 1.5; //honor gain is increased alot more if the combat was fully honorable + else + dGain = dGain * 0.9; + + int gain = Math.Min((int)dGain, 200); + + if (gain < 1) + gain = 1; //Minimum gain of 1 honor when the honor is under the monsters fame + + if (VirtueHelper.IsHighestPath(Source, VirtueName.Honor)) + { + Source.SendLocalizedMessage(1063228); // You cannot gain more Honor. + return; + } + + bool gainedPath = false; + if (VirtueHelper.Award(Source, VirtueName.Honor, gain, ref gainedPath)) + { + if (gainedPath) + Source.SendLocalizedMessage(1063226); // You have gained a path in Honor! + else + Source.SendLocalizedMessage(1063225); // You have gained in Honor. + } + } + + public bool CheckDistance() + { + return true; + } + + public void Cancel() + { + Source.SentHonorContext = null; + ((IHonorTarget)Target).ReceivedHonorContext = null; + + m_Timer.Stop(); + } + + private enum FirstHit + { + NotDelivered, + Delivered, + Granted + } + + private class InternalTimer : Timer + { + private HonorContext m_Context; + + public InternalTimer(HonorContext context) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Context = context; + } + + protected override void OnTick() + { + m_Context.CheckDistance(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/Justice.cs b/Scripts/Engines/Virtues/Justice.cs index cfebdbeb3..84d904a68 100644 --- a/Scripts/Engines/Virtues/Justice.cs +++ b/Scripts/Engines/Virtues/Justice.cs @@ -1,241 +1,243 @@ using System; using Server.Gumps; using Server.Mobiles; +using Server.Network; using Server.Targeting; namespace Server { - public class JusticeVirtue - { - private static TimeSpan LossDelay = TimeSpan.FromDays( 7.0 ); - private const int LossAmount = 950; + public class JusticeVirtue + { + private const int LossAmount = 950; + private static TimeSpan LossDelay = TimeSpan.FromDays(7.0); - public static void Initialize() - { - VirtueGump.Register( 109, OnVirtueUsed ); - } + public static void Initialize() + { + VirtueGump.Register(109, OnVirtueUsed); + } - public static bool CheckMapRegion( Mobile first, Mobile second ) - { - Map map = first.Map; + public static bool CheckMapRegion(Mobile first, Mobile second) + { + Map map = first.Map; - if ( second.Map != map ) - return false; + if (second.Map != map) + return false; - return GetMapRegion( map, first.Location ) == GetMapRegion( map, second.Location ); - } + return GetMapRegion(map, first.Location) == GetMapRegion(map, second.Location); + } - public static int GetMapRegion( Map map, Point3D loc ) - { - if ( map == null || map.MapID >= 2 ) - return 0; + public static int GetMapRegion(Map map, Point3D loc) + { + if (map == null || map.MapID >= 2) + return 0; - if ( loc.X < 5120 ) - return 0; + if (loc.X < 5120) + return 0; - if ( loc.Y < 2304 ) - return 1; + if (loc.Y < 2304) + return 1; - return 2; - } + return 2; + } - public static void OnVirtueUsed( Mobile from ) - { - if ( !from.CheckAlive() ) - return; + public static void OnVirtueUsed(Mobile from) + { + if (!from.CheckAlive()) + return; - if ( !(from is PlayerMobile protector) ) - return; + if (!(from is PlayerMobile protector)) + return; - if ( !VirtueHelper.IsSeeker( protector, VirtueName.Justice ) ) - { - protector.SendLocalizedMessage( 1049610 ); // You must reach the first path in this virtue to invoke it. - } - else if ( !protector.CanBeginAction( typeof( JusticeVirtue ) ) ) - { - protector.SendLocalizedMessage( 1049370 ); // You must wait a while before offering your protection again. - } - else if ( protector.JusticeProtectors.Count > 0 ) - { - protector.SendLocalizedMessage( 1049542 ); // You cannot protect someone while being protected. - } - else if ( protector.Map != Map.Felucca ) - { - protector.SendLocalizedMessage( 1049372 ); // You cannot use this ability here. - } - else - { - protector.BeginTarget( 14, false, TargetFlags.None, OnVirtueTargeted ); - protector.SendLocalizedMessage( 1049366 ); // Choose the player you wish to protect. - } - } + if (!VirtueHelper.IsSeeker(protector, VirtueName.Justice)) + { + protector.SendLocalizedMessage(1049610); // You must reach the first path in this virtue to invoke it. + } + else if (!protector.CanBeginAction(typeof(JusticeVirtue))) + { + protector.SendLocalizedMessage(1049370); // You must wait a while before offering your protection again. + } + else if (protector.JusticeProtectors.Count > 0) + { + protector.SendLocalizedMessage(1049542); // You cannot protect someone while being protected. + } + else if (protector.Map != Map.Felucca) + { + protector.SendLocalizedMessage(1049372); // You cannot use this ability here. + } + else + { + protector.BeginTarget(14, false, TargetFlags.None, OnVirtueTargeted); + protector.SendLocalizedMessage(1049366); // Choose the player you wish to protect. + } + } - public static void OnVirtueTargeted( Mobile from, object obj ) - { - PlayerMobile protector = from as PlayerMobile; - PlayerMobile pm = obj as PlayerMobile; + public static void OnVirtueTargeted(Mobile from, object obj) + { + PlayerMobile protector = from as PlayerMobile; + PlayerMobile pm = obj as PlayerMobile; - if ( protector == null ) - return; + if (protector == null) + return; - if ( !VirtueHelper.IsSeeker( protector, VirtueName.Justice ) ) - protector.SendLocalizedMessage( 1049610 ); // You must reach the first path in this virtue to invoke it. - else if ( !protector.CanBeginAction( typeof( JusticeVirtue ) ) ) - protector.SendLocalizedMessage( 1049370 ); // You must wait a while before offering your protection again. - else if ( protector.JusticeProtectors.Count > 0 ) - protector.SendLocalizedMessage( 1049542 ); // You cannot protect someone while being protected. - else if ( protector.Map != Map.Felucca ) - protector.SendLocalizedMessage( 1049372 ); // You cannot use this ability here. - else if ( pm == null ) - protector.SendLocalizedMessage( 1049678 ); // Only players can be protected. - else if ( pm.Map != Map.Felucca ) - protector.SendLocalizedMessage( 1049372 ); // You cannot use this ability here. - else if ( pm == protector || pm.Criminal || pm.Kills >= 5 ) - protector.SendLocalizedMessage( 1049436 ); // That player cannot be protected. - else if ( pm.JusticeProtectors.Count > 0 ) - protector.SendLocalizedMessage( 1049369 ); // You cannot protect that player right now. - else if ( pm.HasGump( typeof( AcceptProtectorGump ) ) ) - protector.SendLocalizedMessage( 1049369 ); // You cannot protect that player right now. - else - pm.SendGump( new AcceptProtectorGump( protector, pm ) ); - } + if (!VirtueHelper.IsSeeker(protector, VirtueName.Justice)) + protector.SendLocalizedMessage(1049610); // You must reach the first path in this virtue to invoke it. + else if (!protector.CanBeginAction(typeof(JusticeVirtue))) + protector.SendLocalizedMessage(1049370); // You must wait a while before offering your protection again. + else if (protector.JusticeProtectors.Count > 0) + protector.SendLocalizedMessage(1049542); // You cannot protect someone while being protected. + else if (protector.Map != Map.Felucca) + protector.SendLocalizedMessage(1049372); // You cannot use this ability here. + else if (pm == null) + protector.SendLocalizedMessage(1049678); // Only players can be protected. + else if (pm.Map != Map.Felucca) + protector.SendLocalizedMessage(1049372); // You cannot use this ability here. + else if (pm == protector || pm.Criminal || pm.Kills >= 5) + protector.SendLocalizedMessage(1049436); // That player cannot be protected. + else if (pm.JusticeProtectors.Count > 0) + protector.SendLocalizedMessage(1049369); // You cannot protect that player right now. + else if (pm.HasGump(typeof(AcceptProtectorGump))) + protector.SendLocalizedMessage(1049369); // You cannot protect that player right now. + else + pm.SendGump(new AcceptProtectorGump(protector, pm)); + } - public static void OnVirtueAccepted( PlayerMobile protector, PlayerMobile protectee ) - { - if ( !VirtueHelper.IsSeeker( protector, VirtueName.Justice ) ) - { - protector.SendLocalizedMessage( 1049610 ); // You must reach the first path in this virtue to invoke it. - } - else if ( !protector.CanBeginAction( typeof( JusticeVirtue ) ) ) - { - protector.SendLocalizedMessage( 1049370 ); // You must wait a while before offering your protection again. - } - else if ( protector.JusticeProtectors.Count > 0 ) - { - protector.SendLocalizedMessage( 1049542 ); // You cannot protect someone while being protected. - } - else if ( protector.Map != Map.Felucca ) - { - protector.SendLocalizedMessage( 1049372 ); // You cannot use this ability here. - } - else if ( protectee.Map != Map.Felucca ) - { - protector.SendLocalizedMessage( 1049372 ); // You cannot use this ability here. - } - else if ( protectee == protector || protectee.Criminal || protectee.Kills >= 5 ) - { - protector.SendLocalizedMessage( 1049436 ); // That player cannot be protected. - } - else if ( protectee.JusticeProtectors.Count > 0 ) - { - protector.SendLocalizedMessage( 1049369 ); // You cannot protect that player right now. - } - else - { - protectee.JusticeProtectors.Add( protector ); + public static void OnVirtueAccepted(PlayerMobile protector, PlayerMobile protectee) + { + if (!VirtueHelper.IsSeeker(protector, VirtueName.Justice)) + { + protector.SendLocalizedMessage(1049610); // You must reach the first path in this virtue to invoke it. + } + else if (!protector.CanBeginAction(typeof(JusticeVirtue))) + { + protector.SendLocalizedMessage(1049370); // You must wait a while before offering your protection again. + } + else if (protector.JusticeProtectors.Count > 0) + { + protector.SendLocalizedMessage(1049542); // You cannot protect someone while being protected. + } + else if (protector.Map != Map.Felucca) + { + protector.SendLocalizedMessage(1049372); // You cannot use this ability here. + } + else if (protectee.Map != Map.Felucca) + { + protector.SendLocalizedMessage(1049372); // You cannot use this ability here. + } + else if (protectee == protector || protectee.Criminal || protectee.Kills >= 5) + { + protector.SendLocalizedMessage(1049436); // That player cannot be protected. + } + else if (protectee.JusticeProtectors.Count > 0) + { + protector.SendLocalizedMessage(1049369); // You cannot protect that player right now. + } + else + { + protectee.JusticeProtectors.Add(protector); - string args = $"{protector.Name}\t{protectee.Name}"; + string args = $"{protector.Name}\t{protectee.Name}"; - protectee.SendLocalizedMessage( 1049451, args ); // You are now being protected by ~1_NAME~. - protector.SendLocalizedMessage( 1049452, args ); // You are now protecting ~2_NAME~. - } - } + protectee.SendLocalizedMessage(1049451, args); // You are now being protected by ~1_NAME~. + protector.SendLocalizedMessage(1049452, args); // You are now protecting ~2_NAME~. + } + } - public static void OnVirtueRejected( PlayerMobile protector, PlayerMobile protectee ) - { - string args = $"{protector.Name}\t{protectee.Name}"; + public static void OnVirtueRejected(PlayerMobile protector, PlayerMobile protectee) + { + string args = $"{protector.Name}\t{protectee.Name}"; - protectee.SendLocalizedMessage( 1049453, args ); // You have declined protection from ~1_NAME~. - protector.SendLocalizedMessage( 1049454, args ); // ~2_NAME~ has declined your protection. + protectee.SendLocalizedMessage(1049453, args); // You have declined protection from ~1_NAME~. + protector.SendLocalizedMessage(1049454, args); // ~2_NAME~ has declined your protection. - if ( protector.BeginAction( typeof( JusticeVirtue ) ) ) - Timer.DelayCall( TimeSpan.FromMinutes( 15.0 ), new TimerStateCallback( RejectDelay_Callback ), protector ); - } + if (protector.BeginAction(typeof(JusticeVirtue))) + Timer.DelayCall(TimeSpan.FromMinutes(15.0), new TimerStateCallback(RejectDelay_Callback), protector); + } - public static void RejectDelay_Callback( object state ) - { - if ( state is Mobile m ) - m.EndAction( typeof( JusticeVirtue ) ); - } + public static void RejectDelay_Callback(object state) + { + if (state is Mobile m) + m.EndAction(typeof(JusticeVirtue)); + } - public static void CheckAtrophy( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return; + public static void CheckAtrophy(Mobile from) + { + if (!(from is PlayerMobile pm)) + return; - try - { - if ( (pm.LastJusticeLoss + LossDelay) < DateTime.UtcNow ) - { - if ( VirtueHelper.Atrophy( from, VirtueName.Justice, LossAmount ) ) - from.SendLocalizedMessage( 1049373 ); // You have lost some Justice. + try + { + if (pm.LastJusticeLoss + LossDelay < DateTime.UtcNow) + { + if (VirtueHelper.Atrophy(from, VirtueName.Justice, LossAmount)) + from.SendLocalizedMessage(1049373); // You have lost some Justice. - pm.LastJusticeLoss = DateTime.UtcNow; - } - } - catch - { - } - } - } + pm.LastJusticeLoss = DateTime.UtcNow; + } + } + catch + { + } + } + } - public class AcceptProtectorGump : Gump - { - private PlayerMobile m_Protector; - private PlayerMobile m_Protectee; + public class AcceptProtectorGump : Gump + { + private PlayerMobile m_Protectee; + private PlayerMobile m_Protector; - public AcceptProtectorGump( PlayerMobile protector, PlayerMobile protectee ) : base( 150, 50 ) - { - m_Protector = protector; - m_Protectee = protectee; + public AcceptProtectorGump(PlayerMobile protector, PlayerMobile protectee) : base(150, 50) + { + m_Protector = protector; + m_Protectee = protectee; - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 396, 218, 3600 ); + AddBackground(0, 0, 396, 218, 3600); - AddImageTiled( 15, 15, 365, 190, 2624 ); - AddAlphaRegion( 15, 15, 365, 190 ); + AddImageTiled(15, 15, 365, 190, 2624); + AddAlphaRegion(15, 15, 365, 190); - AddHtmlLocalized( 30, 20, 360, 25, 1049365, 0x7FFF, false, false ); // Another player is offering you their protection: - AddLabel( 90, 55, 1153, protector.Name ); + AddHtmlLocalized(30, 20, 360, 25, 1049365, 0x7FFF, false, + false); // Another player is offering you their protection: + AddLabel(90, 55, 1153, protector.Name); - AddImage( 50, 45, 9005 ); - AddImageTiled( 80, 80, 200, 1, 9107 ); - AddImageTiled( 95, 82, 200, 1, 9157 ); + AddImage(50, 45, 9005); + AddImageTiled(80, 80, 200, 1, 9107); + AddImageTiled(95, 82, 200, 1, 9157); - AddRadio( 30, 110, 9727, 9730, true, 1 ); - AddHtmlLocalized( 65, 115, 300, 25, 1049444, 0x7FFF, false, false ); // Yes, I would like their protection. + AddRadio(30, 110, 9727, 9730, true, 1); + AddHtmlLocalized(65, 115, 300, 25, 1049444, 0x7FFF, false, false); // Yes, I would like their protection. - AddRadio( 30, 145, 9727, 9730, false, 0 ); - AddHtmlLocalized( 65, 148, 300, 25, 1049445, 0x7FFF, false, false ); // No thanks, I can take care of myself. + AddRadio(30, 145, 9727, 9730, false, 0); + AddHtmlLocalized(65, 148, 300, 25, 1049445, 0x7FFF, false, false); // No thanks, I can take care of myself. - AddButton( 160, 175, 247, 248, 2, GumpButtonType.Reply, 0 ); + AddButton(160, 175, 247, 248, 2, GumpButtonType.Reply, 0); - AddImage( 215, 0, 50581 ); + AddImage(215, 0, 50581); - AddImageTiled( 15, 14, 365, 1, 9107 ); - AddImageTiled( 380, 14, 1, 190, 9105 ); - AddImageTiled( 15, 205, 365, 1, 9107 ); - AddImageTiled( 15, 14, 1, 190, 9105 ); - AddImageTiled( 0, 0, 395, 1, 9157 ); - AddImageTiled( 394, 0, 1, 217, 9155 ); - AddImageTiled( 0, 216, 395, 1, 9157 ); - AddImageTiled( 0, 0, 1, 217, 9155 ); - } + AddImageTiled(15, 14, 365, 1, 9107); + AddImageTiled(380, 14, 1, 190, 9105); + AddImageTiled(15, 205, 365, 1, 9107); + AddImageTiled(15, 14, 1, 190, 9105); + AddImageTiled(0, 0, 395, 1, 9157); + AddImageTiled(394, 0, 1, 217, 9155); + AddImageTiled(0, 216, 395, 1, 9157); + AddImageTiled(0, 0, 1, 217, 9155); + } - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 2 ) - { - bool okay = info.IsSwitched( 1 ); + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 2) + { + bool okay = info.IsSwitched(1); - if ( okay ) - JusticeVirtue.OnVirtueAccepted( m_Protector, m_Protectee ); - else - JusticeVirtue.OnVirtueRejected( m_Protector, m_Protectee ); - } - } - } -} + if (okay) + JusticeVirtue.OnVirtueAccepted(m_Protector, m_Protectee); + else + JusticeVirtue.OnVirtueRejected(m_Protector, m_Protectee); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/Sacrifice.cs b/Scripts/Engines/Virtues/Sacrifice.cs index 8b298b142..d427105a5 100644 --- a/Scripts/Engines/Virtues/Sacrifice.cs +++ b/Scripts/Engines/Virtues/Sacrifice.cs @@ -1,185 +1,188 @@ using System; using Server.Gumps; using Server.Mobiles; -using Server.Targeting; using Server.Network; +using Server.Targeting; namespace Server { - public class SacrificeVirtue - { - private static TimeSpan GainDelay = TimeSpan.FromDays( 1.0 ); - private static TimeSpan LossDelay = TimeSpan.FromDays( 7.0 ); - private const int LossAmount = 500; + public class SacrificeVirtue + { + private const int LossAmount = 500; + private static TimeSpan GainDelay = TimeSpan.FromDays(1.0); + private static TimeSpan LossDelay = TimeSpan.FromDays(7.0); - public static void Initialize() - { - VirtueGump.Register( 110, OnVirtueUsed ); - } + public static void Initialize() + { + VirtueGump.Register(110, OnVirtueUsed); + } - public static void OnVirtueUsed( Mobile from ) - { - if ( !from.Hidden ) - { - if ( from.Alive ) - from.Target = new InternalTarget(); - else - Resurrect( from ); - } - else - from.SendLocalizedMessage( 1052015 ); // You cannot do that while hidden. - } + public static void OnVirtueUsed(Mobile from) + { + if (!from.Hidden) + { + if (from.Alive) + from.Target = new InternalTarget(); + else + Resurrect(from); + } + else + { + from.SendLocalizedMessage(1052015); // You cannot do that while hidden. + } + } - public static void CheckAtrophy( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return; + public static void CheckAtrophy(Mobile from) + { + if (!(from is PlayerMobile pm)) + return; - try - { - if ( (pm.LastSacrificeLoss + LossDelay) < DateTime.UtcNow ) - { - if ( VirtueHelper.Atrophy( from, VirtueName.Sacrifice, LossAmount ) ) - from.SendLocalizedMessage( 1052041 ); // You have lost some Sacrifice. + try + { + if (pm.LastSacrificeLoss + LossDelay < DateTime.UtcNow) + { + if (VirtueHelper.Atrophy(from, VirtueName.Sacrifice, LossAmount)) + from.SendLocalizedMessage(1052041); // You have lost some Sacrifice. - VirtueLevel level = VirtueHelper.GetLevel( from, VirtueName.Sacrifice ); + VirtueLevel level = VirtueHelper.GetLevel(from, VirtueName.Sacrifice); - pm.AvailableResurrects = (int)level; - pm.LastSacrificeLoss = DateTime.UtcNow; - } - } - catch - { - } - } + pm.AvailableResurrects = (int)level; + pm.LastSacrificeLoss = DateTime.UtcNow; + } + } + catch + { + } + } - public static void Resurrect( Mobile from ) - { - if ( from.Alive ) - return; + public static void Resurrect(Mobile from) + { + if (from.Alive) + return; - if ( !(from is PlayerMobile pm) ) - return; + if (!(from is PlayerMobile pm)) + return; - if ( from.Criminal ) - { - from.SendLocalizedMessage( 1052007 ); // You cannot use this ability while flagged as a criminal. - } - else if ( !VirtueHelper.IsSeeker( from, VirtueName.Sacrifice ) ) - { - from.SendLocalizedMessage( 1052004 ); // You cannot use this ability. - } - else if ( pm.AvailableResurrects <= 0 ) - { - from.SendLocalizedMessage( 1052005 ); // You do not have any resurrections left. - } - else - { - /* - * We need to wait for them to accept the gump or they can just use - * Sacrifice and cancel to have items in their backpack for free. - */ - from.CloseGump( typeof( ResurrectGump ) ); - from.SendGump( new ResurrectGump( from, true ) ); - } - } + if (from.Criminal) + { + from.SendLocalizedMessage(1052007); // You cannot use this ability while flagged as a criminal. + } + else if (!VirtueHelper.IsSeeker(from, VirtueName.Sacrifice)) + { + from.SendLocalizedMessage(1052004); // You cannot use this ability. + } + else if (pm.AvailableResurrects <= 0) + { + from.SendLocalizedMessage(1052005); // You do not have any resurrections left. + } + else + { + /* + * We need to wait for them to accept the gump or they can just use + * Sacrifice and cancel to have items in their backpack for free. + */ + from.CloseGump(typeof(ResurrectGump)); + from.SendGump(new ResurrectGump(from, true)); + } + } - public static void Sacrifice( Mobile from, object targeted ) - { - if ( !from.CheckAlive() ) - return; + public static void Sacrifice(Mobile from, object targeted) + { + if (!from.CheckAlive()) + return; - if ( !(from is PlayerMobile pm) ) - return; + if (!(from is PlayerMobile pm)) + return; - if ( !(targeted is Mobile targ) ) - return; + if (!(targeted is Mobile targ)) + return; - if ( !ValidateCreature( targ ) ) - { - from.SendLocalizedMessage( 1052014 ); // You cannot sacrifice your fame for that creature. - } - else if ( ((targ.Hits * 100) / Math.Max( targ.HitsMax, 1 )) < 90 ) - { - from.SendLocalizedMessage( 1052013 ); // You cannot sacrifice for this monster because it is too damaged. - } - else if ( from.Hidden ) - { - from.SendLocalizedMessage( 1052015 ); // You cannot do that while hidden. - } - else if ( VirtueHelper.IsHighestPath( from, VirtueName.Sacrifice ) ) - { - from.SendLocalizedMessage( 1052068 ); // You have already attained the highest path in this virtue. - } - else if ( from.Fame < 2500 ) - { - from.SendLocalizedMessage( 1052017 ); // You do not have enough fame to sacrifice. - } - else if ( DateTime.UtcNow < (pm.LastSacrificeGain + GainDelay) ) - { - from.SendLocalizedMessage( 1052016 ); // You must wait approximately one day before sacrificing again. - } - else - { - int toGain; + if (!ValidateCreature(targ)) + { + from.SendLocalizedMessage(1052014); // You cannot sacrifice your fame for that creature. + } + else if (targ.Hits * 100 / Math.Max(targ.HitsMax, 1) < 90) + { + from.SendLocalizedMessage(1052013); // You cannot sacrifice for this monster because it is too damaged. + } + else if (from.Hidden) + { + from.SendLocalizedMessage(1052015); // You cannot do that while hidden. + } + else if (VirtueHelper.IsHighestPath(from, VirtueName.Sacrifice)) + { + from.SendLocalizedMessage(1052068); // You have already attained the highest path in this virtue. + } + else if (from.Fame < 2500) + { + from.SendLocalizedMessage(1052017); // You do not have enough fame to sacrifice. + } + else if (DateTime.UtcNow < pm.LastSacrificeGain + GainDelay) + { + from.SendLocalizedMessage(1052016); // You must wait approximately one day before sacrificing again. + } + else + { + int toGain; - if ( from.Fame < 5000 ) - toGain = 500; - else if ( from.Fame < 10000 ) - toGain = 1000; - else - toGain = 2000; + if (from.Fame < 5000) + toGain = 500; + else if (from.Fame < 10000) + toGain = 1000; + else + toGain = 2000; - from.Fame = 0; + from.Fame = 0; - // I have seen the error of my ways! - targ.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1052009 ); + // I have seen the error of my ways! + targ.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1052009); - from.SendLocalizedMessage( 1052010 ); // You have set the creature free. + from.SendLocalizedMessage(1052010); // You have set the creature free. - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), targ.Delete ); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), targ.Delete); - pm.LastSacrificeGain = DateTime.UtcNow; + pm.LastSacrificeGain = DateTime.UtcNow; - bool gainedPath = false; + bool gainedPath = false; - if ( VirtueHelper.Award( from, VirtueName.Sacrifice, toGain, ref gainedPath ) ) - { - if ( gainedPath ) - { - from.SendLocalizedMessage( 1052008 ); // You have gained a path in Sacrifice! + if (VirtueHelper.Award(from, VirtueName.Sacrifice, toGain, ref gainedPath)) + { + if (gainedPath) + { + from.SendLocalizedMessage(1052008); // You have gained a path in Sacrifice! - if ( pm.AvailableResurrects < 3 ) - ++pm.AvailableResurrects; - } - else - { - from.SendLocalizedMessage( 1054160 ); // You have gained in sacrifice. - } - } + if (pm.AvailableResurrects < 3) + ++pm.AvailableResurrects; + } + else + { + from.SendLocalizedMessage(1054160); // You have gained in sacrifice. + } + } - from.SendLocalizedMessage( 1052016 ); // You must wait approximately one day before sacrificing again. - } - } + from.SendLocalizedMessage(1052016); // You must wait approximately one day before sacrificing again. + } + } - public static bool ValidateCreature( Mobile m ) - { - if ( m is BaseCreature creature && (creature.Controlled || creature.Summoned) ) - return false; + public static bool ValidateCreature(Mobile m) + { + if (m is BaseCreature creature && (creature.Controlled || creature.Summoned)) + return false; - return ( m is Lich || m is Succubus || m is Daemon || m is EvilMage || m is EnslavedGargoyle || m is GargoyleEnforcer ); - } + return m is Lich || m is Succubus || m is Daemon || m is EvilMage || m is EnslavedGargoyle || + m is GargoyleEnforcer; + } - private class InternalTarget : Target - { - public InternalTarget() : base( 8, false, TargetFlags.None ) - { - } + private class InternalTarget : Target + { + public InternalTarget() : base(8, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - Sacrifice( from, targeted ); - } - } - } -} + protected override void OnTarget(Mobile from, object targeted) + { + Sacrifice(from, targeted); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/Valor.cs b/Scripts/Engines/Virtues/Valor.cs index 635b5d6f2..6d3b92957 100644 --- a/Scripts/Engines/Virtues/Valor.cs +++ b/Scripts/Engines/Virtues/Valor.cs @@ -1,130 +1,141 @@ using System; +using Server.Engines.CannedEvil; using Server.Mobiles; using Server.Targeting; -using Server.Engines.CannedEvil; namespace Server { - public class ValorVirtue - { - private static TimeSpan LossDelay = TimeSpan.FromDays( 7.0 ); - private const int LossAmount = 250; + public class ValorVirtue + { + private const int LossAmount = 250; + private static TimeSpan LossDelay = TimeSpan.FromDays(7.0); - public static void Initialize() - { - VirtueGump.Register( 112, OnVirtueUsed ); - } + public static void Initialize() + { + VirtueGump.Register(112, OnVirtueUsed); + } - public static void OnVirtueUsed( Mobile from ) - { - if ( from.Alive ) - { - from.SendLocalizedMessage( 1054034 ); // Target the Champion Idol of the Champion you wish to challenge!. - from.Target = new InternalTarget(); - } - } + public static void OnVirtueUsed(Mobile from) + { + if (from.Alive) + { + from.SendLocalizedMessage(1054034); // Target the Champion Idol of the Champion you wish to challenge!. + from.Target = new InternalTarget(); + } + } - public static void CheckAtrophy( Mobile from ) - { - if ( !(from is PlayerMobile pm) ) - return; + public static void CheckAtrophy(Mobile from) + { + if (!(from is PlayerMobile pm)) + return; - try - { - if ( (pm.LastValorLoss + LossDelay) < DateTime.UtcNow ) - { - if ( VirtueHelper.Atrophy( from, VirtueName.Valor, LossAmount ) ) - from.SendLocalizedMessage( 1054040 ); // You have lost some Valor. + try + { + if (pm.LastValorLoss + LossDelay < DateTime.UtcNow) + { + if (VirtueHelper.Atrophy(from, VirtueName.Valor, LossAmount)) + from.SendLocalizedMessage(1054040); // You have lost some Valor. - pm.LastValorLoss = DateTime.UtcNow; - } - } - catch - { - } - } + pm.LastValorLoss = DateTime.UtcNow; + } + } + catch + { + } + } - public static void Valor( Mobile from, object targ ) - { - if ( !(targ is IdolOfTheChampion idol) || idol.Deleted || idol.Spawn == null || idol.Spawn.Deleted ) - from.SendLocalizedMessage( 1054035 ); // You must target a Champion Idol to challenge the Champion's spawn! - else if ( from.Hidden ) - from.SendLocalizedMessage( 1052015 ); // You cannot do that while hidden. - else if ( idol.Spawn.HasBeenAdvanced ) - from.SendLocalizedMessage( 1054038 ); // The Champion of this region has already been challenged! - else - { - VirtueLevel vl = VirtueHelper.GetLevel( from, VirtueName.Valor ); - if ( idol.Spawn.Active ) - { - if ( idol.Spawn.Champion != null ) //TODO: Message? - return; + public static void Valor(Mobile from, object targ) + { + if (!(targ is IdolOfTheChampion idol) || idol.Deleted || idol.Spawn == null || idol.Spawn.Deleted) + { + from.SendLocalizedMessage(1054035); // You must target a Champion Idol to challenge the Champion's spawn! + } + else if (from.Hidden) + { + from.SendLocalizedMessage(1052015); // You cannot do that while hidden. + } + else if (idol.Spawn.HasBeenAdvanced) + { + from.SendLocalizedMessage(1054038); // The Champion of this region has already been challenged! + } + else + { + VirtueLevel vl = VirtueHelper.GetLevel(from, VirtueName.Valor); + if (idol.Spawn.Active) + { + if (idol.Spawn.Champion != null) //TODO: Message? + return; - int needed, consumed; - switch( idol.Spawn.GetSubLevel() ) - { - case 0: - { - needed = consumed = 2500; - break; - } - case 1: - { - needed = consumed = 5000; - break; - } - case 2: - { - needed = 10000; - consumed = 7500; - break; - } - default: - { - needed = 20000; - consumed = 10000; - break; - } - } + int needed, consumed; + switch (idol.Spawn.GetSubLevel()) + { + case 0: + { + needed = consumed = 2500; + break; + } + case 1: + { + needed = consumed = 5000; + break; + } + case 2: + { + needed = 10000; + consumed = 7500; + break; + } + default: + { + needed = 20000; + consumed = 10000; + break; + } + } - if ( from.Virtues.GetValue( (int)VirtueName.Valor ) >= needed ) - { - VirtueHelper.Atrophy( from, VirtueName.Valor, consumed ); - from.SendLocalizedMessage( 1054037 ); // Your challenge is heard by the Champion of this region! Beware its wrath! - idol.Spawn.HasBeenAdvanced = true; - idol.Spawn.AdvanceLevel(); - } - else - from.SendLocalizedMessage( 1054039 ); // The Champion of this region ignores your challenge. You must further prove your valor. - } - else - { - if ( vl == VirtueLevel.Knight ) - { - VirtueHelper.Atrophy( from, VirtueName.Valor, 11000 ); - from.SendLocalizedMessage( 1054037 ); // Your challenge is heard by the Champion of this region! Beware its wrath! - idol.Spawn.EndRestart(); - idol.Spawn.HasBeenAdvanced = true; - } - else - { - from.SendLocalizedMessage( 1054036 ); // You must be a Knight of Valor to summon the champion's spawn in this manner! - } - } - } + if (from.Virtues.GetValue((int)VirtueName.Valor) >= needed) + { + VirtueHelper.Atrophy(from, VirtueName.Valor, consumed); + from.SendLocalizedMessage( + 1054037); // Your challenge is heard by the Champion of this region! Beware its wrath! + idol.Spawn.HasBeenAdvanced = true; + idol.Spawn.AdvanceLevel(); + } + else + { + from.SendLocalizedMessage( + 1054039); // The Champion of this region ignores your challenge. You must further prove your valor. + } + } + else + { + if (vl == VirtueLevel.Knight) + { + VirtueHelper.Atrophy(from, VirtueName.Valor, 11000); + from.SendLocalizedMessage( + 1054037); // Your challenge is heard by the Champion of this region! Beware its wrath! + idol.Spawn.EndRestart(); + idol.Spawn.HasBeenAdvanced = true; + } + else + { + from.SendLocalizedMessage( + 1054036); // You must be a Knight of Valor to summon the champion's spawn in this manner! + } + } + } + } - } + private class InternalTarget : Target + { + public InternalTarget() : base(14, false, TargetFlags.None) + { + } - private class InternalTarget : Target - { - public InternalTarget() : base( 14, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - Valor( from, targeted ); - } - } - } -} + protected override void OnTarget(Mobile from, object targeted) + { + Valor(from, targeted); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/VirtueGump.cs b/Scripts/Engines/Virtues/VirtueGump.cs index d5780fb6b..344dbeb44 100644 --- a/Scripts/Engines/Virtues/VirtueGump.cs +++ b/Scripts/Engines/Virtues/VirtueGump.cs @@ -1,182 +1,184 @@ -using System; using System.Collections.Generic; using Server.Gumps; using Server.Network; namespace Server { - public delegate void OnVirtueUsed( Mobile from ); + public delegate void OnVirtueUsed(Mobile from); - public class VirtueGump : Gump - { - private static Dictionary m_Callbacks = new Dictionary(); + public class VirtueGump : Gump + { + private static Dictionary m_Callbacks = new Dictionary(); - public static void Initialize() - { - EventSink.VirtueGumpRequest += EventSink_VirtueGumpRequest; - EventSink.VirtueItemRequest += EventSink_VirtueItemRequest; - EventSink.VirtueMacroRequest += EventSink_VirtueMacroRequest; - } + private static int[] m_Table = new int[24] + { + 0x0481, 0x0963, 0x0965, + 0x060A, 0x060F, 0x002A, + 0x08A4, 0x08A7, 0x0034, + 0x0965, 0x08FD, 0x0480, + 0x00EA, 0x0845, 0x0020, + 0x0011, 0x0269, 0x013D, + 0x08A1, 0x08A3, 0x0042, + 0x0543, 0x0547, 0x0061 + }; - public static void Register( int gumpID, OnVirtueUsed callback ) - { - m_Callbacks[gumpID] = callback; - } + private Mobile m_Beholder, m_Beheld; - private static void EventSink_VirtueItemRequest( VirtueItemRequestEventArgs e ) - { - if ( e.Beholder != e.Beheld ) - return; + public VirtueGump(Mobile beholder, Mobile beheld) : base(0, 0) + { + m_Beholder = beholder; + m_Beheld = beheld; - e.Beholder.CloseGump( typeof( VirtueGump ) ); + Serial = beheld.Serial; - if ( e.Beholder.Kills >= 5 ) - { - e.Beholder.SendLocalizedMessage( 1049609 ); // Murderers cannot invoke this virtue. - return; - } + AddPage(0); - m_Callbacks.TryGetValue(e.GumpID, out OnVirtueUsed callback); + AddImage(30, 40, 104); - if ( callback != null ) - callback( e.Beholder ); - else - e.Beholder.SendLocalizedMessage( 1052066 ); // That virtue is not active yet. - } + AddPage(1); + + Add(new InternalEntry(61, 71, 108, GetHueFor(0))); // Humility + Add(new InternalEntry(123, 46, 112, GetHueFor(4))); // Valor + Add(new InternalEntry(187, 70, 107, GetHueFor(5))); // Honor + Add(new InternalEntry(35, 135, 110, GetHueFor(1))); // Sacrifice + Add(new InternalEntry(211, 133, 105, GetHueFor(2))); // Compassion + Add(new InternalEntry(61, 195, 111, GetHueFor(3))); // Spiritulaity + Add(new InternalEntry(186, 195, 109, GetHueFor(6))); // Justice + Add(new InternalEntry(121, 221, 106, GetHueFor(7))); // Honesty + + if (m_Beholder == m_Beheld) + { + AddButton(57, 269, 2027, 2027, 1, GumpButtonType.Reply, 0); + AddButton(186, 269, 2071, 2071, 2, GumpButtonType.Reply, 0); + } + } + + public static void Initialize() + { + EventSink.VirtueGumpRequest += EventSink_VirtueGumpRequest; + EventSink.VirtueItemRequest += EventSink_VirtueItemRequest; + EventSink.VirtueMacroRequest += EventSink_VirtueMacroRequest; + } + + public static void Register(int gumpID, OnVirtueUsed callback) + { + m_Callbacks[gumpID] = callback; + } + + private static void EventSink_VirtueItemRequest(VirtueItemRequestEventArgs e) + { + if (e.Beholder != e.Beheld) + return; + + e.Beholder.CloseGump(typeof(VirtueGump)); + + if (e.Beholder.Kills >= 5) + { + e.Beholder.SendLocalizedMessage(1049609); // Murderers cannot invoke this virtue. + return; + } + + m_Callbacks.TryGetValue(e.GumpID, out OnVirtueUsed callback); + + if (callback != null) + callback(e.Beholder); + else + e.Beholder.SendLocalizedMessage(1052066); // That virtue is not active yet. + } - private static void EventSink_VirtueMacroRequest( VirtueMacroRequestEventArgs e ) - { - int virtueID = 0; + private static void EventSink_VirtueMacroRequest(VirtueMacroRequestEventArgs e) + { + int virtueID = 0; - switch ( e.VirtueID ) - { - case 0: // Honor - virtueID = 107; break; - case 1: // Sacrifice - virtueID = 110; break; - case 2: // Valor; - virtueID = 112; break; - } + switch (e.VirtueID) + { + case 0: // Honor + virtueID = 107; + break; + case 1: // Sacrifice + virtueID = 110; + break; + case 2: // Valor; + virtueID = 112; + break; + } - EventSink_VirtueItemRequest( new VirtueItemRequestEventArgs( e.Mobile, e.Mobile, virtueID ) ); - } + EventSink_VirtueItemRequest(new VirtueItemRequestEventArgs(e.Mobile, e.Mobile, virtueID)); + } - private static void EventSink_VirtueGumpRequest( VirtueGumpRequestEventArgs e ) - { - Mobile beholder = e.Beholder; - Mobile beheld = e.Beheld; + private static void EventSink_VirtueGumpRequest(VirtueGumpRequestEventArgs e) + { + Mobile beholder = e.Beholder; + Mobile beheld = e.Beheld; - if ( beholder == beheld && beholder.Kills >= 5 ) - { - beholder.SendLocalizedMessage( 1049609 ); // Murderers cannot invoke this virtue. - } - else if ( beholder.Map == beheld.Map && beholder.InRange( beheld, 12 ) ) - { - beholder.CloseGump( typeof( VirtueGump ) ); - beholder.SendGump( new VirtueGump( beholder, beheld ) ); - } - } + if (beholder == beheld && beholder.Kills >= 5) + { + beholder.SendLocalizedMessage(1049609); // Murderers cannot invoke this virtue. + } + else if (beholder.Map == beheld.Map && beholder.InRange(beheld, 12)) + { + beholder.CloseGump(typeof(VirtueGump)); + beholder.SendGump(new VirtueGump(beholder, beheld)); + } + } - private Mobile m_Beholder, m_Beheld; + private int GetHueFor(int index) + { + if (m_Beheld.Virtues.GetValue(index) == 0) + return 2402; - public VirtueGump( Mobile beholder, Mobile beheld ) : base( 0, 0 ) - { - m_Beholder = beholder; - m_Beheld = beheld; + int value = m_Beheld.Virtues.GetValue(index); - Serial = beheld.Serial; + if (value < 4000) + return 2402; - AddPage( 0 ); - - AddImage( 30, 40, 104 ); - - AddPage( 1 ); - - Add( new InternalEntry( 61, 71, 108, GetHueFor( 0 ) ) ); // Humility - Add( new InternalEntry( 123, 46, 112, GetHueFor( 4 ) ) ); // Valor - Add( new InternalEntry( 187, 70, 107, GetHueFor( 5 ) ) ); // Honor - Add( new InternalEntry( 35, 135, 110, GetHueFor( 1 ) ) ); // Sacrifice - Add( new InternalEntry( 211, 133, 105, GetHueFor( 2 ) ) ); // Compassion - Add( new InternalEntry( 61, 195, 111, GetHueFor( 3 ) ) ); // Spiritulaity - Add( new InternalEntry( 186, 195, 109, GetHueFor( 6 ) ) ); // Justice - Add( new InternalEntry( 121, 221, 106, GetHueFor( 7 ) ) ); // Honesty - - if ( m_Beholder == m_Beheld ) - { - AddButton( 57, 269, 2027, 2027, 1, GumpButtonType.Reply, 0 ); - AddButton( 186, 269, 2071, 2071, 2, GumpButtonType.Reply, 0 ); - } - } - - private static int[] m_Table = new int[24] - { - 0x0481, 0x0963, 0x0965, - 0x060A, 0x060F, 0x002A, - 0x08A4, 0x08A7, 0x0034, - 0x0965, 0x08FD, 0x0480, - 0x00EA, 0x0845, 0x0020, - 0x0011, 0x0269, 0x013D, - 0x08A1, 0x08A3, 0x0042, - 0x0543, 0x0547, 0x0061 - }; - - private int GetHueFor( int index ) - { - if ( m_Beheld.Virtues.GetValue( index ) == 0 ) - return 2402; - - int value = m_Beheld.Virtues.GetValue( index ); - - if ( value < 4000 ) - return 2402; - - if ( value >= 30000 ) - value = 20000; //Sanity + if (value >= 30000) + value = 20000; //Sanity - int vl; + int vl; - if ( value < 10000 ) - vl = 0; - else if ( value >= 20000 && index == 5) - vl = 2; - else if ( value >= 21000 && index != 1) - vl = 2; - else if ( value >= 22000 && index == 1) - vl = 2; - else - vl = 1; + if (value < 10000) + vl = 0; + else if (value >= 20000 && index == 5) + vl = 2; + else if (value >= 21000 && index != 1) + vl = 2; + else if (value >= 22000 && index == 1) + vl = 2; + else + vl = 1; - return m_Table[(index * 3) + (int) vl]; - } + return m_Table[index * 3 + vl]; + } - private class InternalEntry : GumpImage - { - public InternalEntry( int x, int y, int gumpID, int hue ) : base( x, y, gumpID, hue ) - { - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1 && m_Beholder == m_Beheld) + m_Beholder.SendGump(new VirtueStatusGump(m_Beholder)); + } - public override string Compile( NetState ns ) - { - return $"{{ gumppic {X} {Y} {GumpID} hue={Hue} class=VirtueGumpItem }}"; - } + private class InternalEntry : GumpImage + { + private static byte[] m_Class = StringToBuffer(" class=VirtueGumpItem"); - private static byte[] m_Class = StringToBuffer( " class=VirtueGumpItem" ); + public InternalEntry(int x, int y, int gumpID, int hue) : base(x, y, gumpID, hue) + { + } - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - base.AppendTo( ns, disp ); + public override string Compile(NetState ns) + { + return $"{{ gumppic {X} {Y} {GumpID} hue={Hue} class=VirtueGumpItem }}"; + } - disp.AppendLayout( m_Class ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + base.AppendTo(ns, disp); - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 1 && m_Beholder == m_Beheld ) - m_Beholder.SendGump( new VirtueStatusGump( m_Beholder ) ); - } - } -} + disp.AppendLayout(m_Class); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/VirtueHelper.cs b/Scripts/Engines/Virtues/VirtueHelper.cs index 9869824fc..be5452311 100644 --- a/Scripts/Engines/Virtues/VirtueHelper.cs +++ b/Scripts/Engines/Virtues/VirtueHelper.cs @@ -3,160 +3,161 @@ using Server.Mobiles; namespace Server { - public enum VirtueLevel - { - None, - Seeker, - Follower, - Knight - } + public enum VirtueLevel + { + None, + Seeker, + Follower, + Knight + } - public enum VirtueName - { - Humility, - Sacrifice, - Compassion, - Spirituality, - Valor, - Honor, - Justice, - Honesty - } + public enum VirtueName + { + Humility, + Sacrifice, + Compassion, + Spirituality, + Valor, + Honor, + Justice, + Honesty + } - public class VirtueHelper - { - public static bool HasAny( Mobile from, VirtueName virtue ) - { - return ( from.Virtues.GetValue( (int)virtue ) > 0 ); - } + public class VirtueHelper + { + public static bool HasAny(Mobile from, VirtueName virtue) + { + return from.Virtues.GetValue((int)virtue) > 0; + } - public static bool IsHighestPath( Mobile from, VirtueName virtue ) - { - return ( from.Virtues.GetValue( (int)virtue ) >= GetMaxAmount( virtue ) ); - } + public static bool IsHighestPath(Mobile from, VirtueName virtue) + { + return from.Virtues.GetValue((int)virtue) >= GetMaxAmount(virtue); + } - public static VirtueLevel GetLevel( Mobile from, VirtueName virtue ) - { - int v = from.Virtues.GetValue( (int)virtue ); - int vl; - int vmax = GetMaxAmount( virtue ); + public static VirtueLevel GetLevel(Mobile from, VirtueName virtue) + { + int v = from.Virtues.GetValue((int)virtue); + int vl; + int vmax = GetMaxAmount(virtue); - if ( v < 4000 ) - vl = 0; - else if ( v >= vmax) - vl = 3; - else - vl = ( v + 9999 ) / 10000; + if (v < 4000) + vl = 0; + else if (v >= vmax) + vl = 3; + else + vl = (v + 9999) / 10000; - return (VirtueLevel)vl; - } + return (VirtueLevel)vl; + } - public static int GetMaxAmount( VirtueName virtue ) - { - if ( virtue == VirtueName.Honor ) - return 20000; + public static int GetMaxAmount(VirtueName virtue) + { + if (virtue == VirtueName.Honor) + return 20000; - if ( virtue == VirtueName.Sacrifice ) - return 22000; + if (virtue == VirtueName.Sacrifice) + return 22000; - return 21000; - } + return 21000; + } - public static bool Award( Mobile from, VirtueName virtue, int amount, ref bool gainedPath ) - { - int current = from.Virtues.GetValue( (int)virtue ); + public static bool Award(Mobile from, VirtueName virtue, int amount, ref bool gainedPath) + { + int current = from.Virtues.GetValue((int)virtue); - int maxAmount = GetMaxAmount( virtue ); + int maxAmount = GetMaxAmount(virtue); - if ( current >= maxAmount ) - return false; + if (current >= maxAmount) + return false; - if ( (current + amount) >= maxAmount ) - amount = maxAmount - current; + if (current + amount >= maxAmount) + amount = maxAmount - current; - VirtueLevel oldLevel = GetLevel( from, virtue ); + VirtueLevel oldLevel = GetLevel(from, virtue); - from.Virtues.SetValue( (int)virtue, current + amount ); + from.Virtues.SetValue((int)virtue, current + amount); - gainedPath = ( GetLevel( from, virtue ) != oldLevel ); + gainedPath = GetLevel(from, virtue) != oldLevel; - return true; - } + return true; + } - public static bool Atrophy( Mobile from, VirtueName virtue ) - { - return Atrophy( from, virtue, 1 ); - } + public static bool Atrophy(Mobile from, VirtueName virtue) + { + return Atrophy(from, virtue, 1); + } - public static bool Atrophy( Mobile from, VirtueName virtue, int amount ) - { - int current = from.Virtues.GetValue( (int)virtue ); + public static bool Atrophy(Mobile from, VirtueName virtue, int amount) + { + int current = from.Virtues.GetValue((int)virtue); - if ( (current - amount) >= 0 ) - from.Virtues.SetValue( (int)virtue, current - amount ); - else - from.Virtues.SetValue( (int)virtue, 0 ); + if (current - amount >= 0) + from.Virtues.SetValue((int)virtue, current - amount); + else + from.Virtues.SetValue((int)virtue, 0); - return ( current > 0 ); - } + return current > 0; + } - public static bool IsSeeker( Mobile from, VirtueName virtue ) - { - return ( GetLevel( from, virtue ) >= VirtueLevel.Seeker ); - } + public static bool IsSeeker(Mobile from, VirtueName virtue) + { + return GetLevel(from, virtue) >= VirtueLevel.Seeker; + } - public static bool IsFollower( Mobile from, VirtueName virtue ) - { - return ( GetLevel( from, virtue ) >= VirtueLevel.Follower ); - } + public static bool IsFollower(Mobile from, VirtueName virtue) + { + return GetLevel(from, virtue) >= VirtueLevel.Follower; + } - public static bool IsKnight( Mobile from, VirtueName virtue ) - { - return ( GetLevel( from, virtue ) >= VirtueLevel.Knight ); - } + public static bool IsKnight(Mobile from, VirtueName virtue) + { + return GetLevel(from, virtue) >= VirtueLevel.Knight; + } - public static void AwardVirtue( PlayerMobile pm, VirtueName virtue, int amount ) - { - if ( virtue == VirtueName.Compassion ) - { - if ( pm.CompassionGains > 0 && DateTime.UtcNow > pm.NextCompassionDay ) - { - pm.NextCompassionDay = DateTime.MinValue; - pm.CompassionGains = 0; - } + public static void AwardVirtue(PlayerMobile pm, VirtueName virtue, int amount) + { + if (virtue == VirtueName.Compassion) + { + if (pm.CompassionGains > 0 && DateTime.UtcNow > pm.NextCompassionDay) + { + pm.NextCompassionDay = DateTime.MinValue; + pm.CompassionGains = 0; + } - if ( pm.CompassionGains >= 5 ) - { - pm.SendLocalizedMessage( 1053004 ); // You must wait about a day before you can gain in compassion again. - return; - } - } + if (pm.CompassionGains >= 5) + { + pm.SendLocalizedMessage(1053004); // You must wait about a day before you can gain in compassion again. + return; + } + } - bool gainedPath = false; - string virtueName = Enum.GetName( typeof( VirtueName ), virtue ); + bool gainedPath = false; + string virtueName = Enum.GetName(typeof(VirtueName), virtue); - if ( Award( pm, virtue, amount, ref gainedPath ) ) - { - // TODO: Localize? - if ( gainedPath ) - pm.SendMessage( "You have gained a path in {0}!", virtueName ); - else - pm.SendMessage( "You have gained in {0}.", virtueName ); + if (Award(pm, virtue, amount, ref gainedPath)) + { + // TODO: Localize? + if (gainedPath) + pm.SendMessage("You have gained a path in {0}!", virtueName); + else + pm.SendMessage("You have gained in {0}.", virtueName); - if ( virtue == VirtueName.Compassion ) - { - pm.NextCompassionDay = DateTime.UtcNow + TimeSpan.FromDays( 1.0 ); - ++pm.CompassionGains; + if (virtue == VirtueName.Compassion) + { + pm.NextCompassionDay = DateTime.UtcNow + TimeSpan.FromDays(1.0); + ++pm.CompassionGains; - if ( pm.CompassionGains >= 5 ) - pm.SendLocalizedMessage( 1053004 ); // You must wait about a day before you can gain in compassion again. - } - } - else - { - // TODO: Localize? - pm.SendMessage( "You have achieved the highest path of {0} and can no longer gain any further.", virtueName ); - } - } - } -} + if (pm.CompassionGains >= 5) + pm.SendLocalizedMessage( + 1053004); // You must wait about a day before you can gain in compassion again. + } + } + else + { + // TODO: Localize? + pm.SendMessage("You have achieved the highest path of {0} and can no longer gain any further.", virtueName); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/VirtueInfoGump.cs b/Scripts/Engines/Virtues/VirtueInfoGump.cs index b58d87f3a..e93041f2d 100644 --- a/Scripts/Engines/Virtues/VirtueInfoGump.cs +++ b/Scripts/Engines/Virtues/VirtueInfoGump.cs @@ -3,106 +3,106 @@ using Server.Network; namespace Server { - public class VirtueInfoGump : Gump - { - private Mobile m_Beholder; - private int m_Desc; - private string m_Page; - private VirtueName m_Virtue; + public class VirtueInfoGump : Gump + { + private Mobile m_Beholder; + private int m_Desc; + private string m_Page; + private VirtueName m_Virtue; - public VirtueInfoGump( Mobile beholder, VirtueName virtue, int description ) : this( beholder, virtue, description, null ) - { - } + public VirtueInfoGump(Mobile beholder, VirtueName virtue, int description) : this(beholder, virtue, description, + null) + { + } - public VirtueInfoGump( Mobile beholder, VirtueName virtue, int description, string webPage ) : base( 0, 0 ) - { - m_Beholder = beholder; - m_Virtue = virtue; - m_Desc = description; - m_Page = webPage; + public VirtueInfoGump(Mobile beholder, VirtueName virtue, int description, string webPage) : base(0, 0) + { + m_Beholder = beholder; + m_Virtue = virtue; + m_Desc = description; + m_Page = webPage; - int value = beholder.Virtues.GetValue( (int)virtue ); + int value = beholder.Virtues.GetValue((int)virtue); - AddPage( 0 ); + AddPage(0); - AddImage( 30, 40, 2080 ); - AddImage( 47, 77, 2081 ); - AddImage( 47, 147, 2081 ); - AddImage( 47, 217, 2081 ); - AddImage( 47, 267, 2083 ); - AddImage( 70, 213, 2091 ); + AddImage(30, 40, 2080); + AddImage(47, 77, 2081); + AddImage(47, 147, 2081); + AddImage(47, 217, 2081); + AddImage(47, 267, 2083); + AddImage(70, 213, 2091); - AddPage( 1 ); + AddPage(1); - int maxValue = VirtueHelper.GetMaxAmount( m_Virtue ); + int maxValue = VirtueHelper.GetMaxAmount(m_Virtue); - int valueDesc; - int dots; + int valueDesc; + int dots; - if ( value < 4000 ) - dots = value / 400; - else if ( value < 10000 ) - dots = (value - 4000) / 600; - else if ( value < maxValue ) - dots = (value - 10000) / ((maxValue-10000)/10); - else - dots = 10; + if (value < 4000) + dots = value / 400; + else if (value < 10000) + dots = (value - 4000) / 600; + else if (value < maxValue) + dots = (value - 10000) / ((maxValue - 10000) / 10); + else + dots = 10; - for ( int i = 0; i < 10; ++i ) - AddImage( 95 + (i * 17), 50, i < dots ? 2362 : 2360 ); + for (int i = 0; i < 10; ++i) + AddImage(95 + i * 17, 50, i < dots ? 2362 : 2360); - if ( value < 1 ) - valueDesc = 1052044; // You have not started on the path of this Virtue. - else if ( value < 400 ) - valueDesc = 1052045; // You have barely begun your journey through the path of this Virtue. - else if ( value < 2000 ) - valueDesc = 1052046; // You have progressed in this Virtue, but still have much to do. - else if ( value < 3600 ) - valueDesc = 1052047; // Your journey through the path of this Virtue is going well. - else if ( value < 4000 ) - valueDesc = 1052048; // You feel very close to achieving your next path in this Virtue. - else if ( dots < 1 ) - valueDesc = 1052049; // You have achieved a path in this Virtue. - else if ( dots < 9 ) - valueDesc = 1052047; // Your journey through the path of this Virtue is going well. - else if ( dots < 10 ) - valueDesc = 1052048; // You feel very close to achieving your next path in this Virtue. - else - valueDesc = 1052050; // You have achieved the highest path in this Virtue. + if (value < 1) + valueDesc = 1052044; // You have not started on the path of this Virtue. + else if (value < 400) + valueDesc = 1052045; // You have barely begun your journey through the path of this Virtue. + else if (value < 2000) + valueDesc = 1052046; // You have progressed in this Virtue, but still have much to do. + else if (value < 3600) + valueDesc = 1052047; // Your journey through the path of this Virtue is going well. + else if (value < 4000) + valueDesc = 1052048; // You feel very close to achieving your next path in this Virtue. + else if (dots < 1) + valueDesc = 1052049; // You have achieved a path in this Virtue. + else if (dots < 9) + valueDesc = 1052047; // Your journey through the path of this Virtue is going well. + else if (dots < 10) + valueDesc = 1052048; // You feel very close to achieving your next path in this Virtue. + else + valueDesc = 1052050; // You have achieved the highest path in this Virtue. - AddHtmlLocalized( 157, 73, 200, 40, 1051000 + (int)virtue, false, false ); - AddHtmlLocalized( 75, 95, 220, 140, description, false, false ); - AddHtmlLocalized( 70, 224, 229, 60, valueDesc, false, false ); + AddHtmlLocalized(157, 73, 200, 40, 1051000 + (int)virtue, false, false); + AddHtmlLocalized(75, 95, 220, 140, description, false, false); + AddHtmlLocalized(70, 224, 229, 60, valueDesc, false, false); - AddButton( 65, 277, 1209, 1209, 1, GumpButtonType.Reply, 0 ); + AddButton(65, 277, 1209, 1209, 1, GumpButtonType.Reply, 0); - AddButton( 280, 43, 4014, 4014, 2, GumpButtonType.Reply, 0 ); + AddButton(280, 43, 4014, 4014, 2, GumpButtonType.Reply, 0); - AddHtmlLocalized( 83, 275, 400, 40, (webPage == null) ? 1052055 : 1052052, false, false ); // This virtue is not yet defined. OR -click to learn more (opens webpage) + AddHtmlLocalized(83, 275, 400, 40, webPage == null ? 1052055 : 1052052, false, + false); // This virtue is not yet defined. OR -click to learn more (opens webpage) + } + public override void OnResponse(NetState state, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, m_Virtue, m_Desc, m_Page)); - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 1: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, m_Virtue, m_Desc, m_Page ) ); - - if ( m_Page != null ) - state.Send( new LaunchBrowser( m_Page ) ); //No message about web browser starting on OSI - break; - } - case 2: - { - m_Beholder.SendGump( new VirtueStatusGump( m_Beholder ) ); - break; - } - } - } - } -} + if (m_Page != null) + state.Send(new LaunchBrowser(m_Page)); //No message about web browser starting on OSI + break; + } + case 2: + { + m_Beholder.SendGump(new VirtueStatusGump(m_Beholder)); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Engines/Virtues/VirtueStatusGump.cs b/Scripts/Engines/Virtues/VirtueStatusGump.cs index 06a13f776..854c8271a 100644 --- a/Scripts/Engines/Virtues/VirtueStatusGump.cs +++ b/Scripts/Engines/Virtues/VirtueStatusGump.cs @@ -3,100 +3,106 @@ using Server.Network; namespace Server { - public class VirtueStatusGump : Gump - { - private Mobile m_Beholder; + public class VirtueStatusGump : Gump + { + private Mobile m_Beholder; - public VirtueStatusGump( Mobile beholder ) : base( 0, 0 ) - { - m_Beholder = beholder; + public VirtueStatusGump(Mobile beholder) : base(0, 0) + { + m_Beholder = beholder; - AddPage( 0 ); + AddPage(0); - AddImage( 30, 40, 2080 ); - AddImage( 47, 77, 2081 ); - AddImage( 47, 147, 2081 ); - AddImage( 47, 217, 2081 ); - AddImage( 47, 267, 2083 ); - AddImage( 70, 213, 2091 ); + AddImage(30, 40, 2080); + AddImage(47, 77, 2081); + AddImage(47, 147, 2081); + AddImage(47, 217, 2081); + AddImage(47, 267, 2083); + AddImage(70, 213, 2091); - AddPage( 1 ); + AddPage(1); - AddHtml( 140, 73, 200, 20, "The Virtues", false, false ); + AddHtml(140, 73, 200, 20, "The Virtues", false, false); - AddHtmlLocalized( 80, 100, 100, 40, 1051000, false, false ); // Humility - AddHtmlLocalized( 80, 129, 100, 40, 1051001, false, false ); // Sacrifice - AddHtmlLocalized( 80, 159, 100, 40, 1051002, false, false ); // Compassion - AddHtmlLocalized( 80, 189, 100, 40, 1051003, false, false ); // Spirituality - AddHtmlLocalized( 200, 100, 200, 40, 1051004, false, false ); // Valor - AddHtmlLocalized( 200, 129, 200, 40, 1051005, false, false ); // Honor - AddHtmlLocalized( 200, 159, 200, 40, 1051006, false, false ); // Justice - AddHtmlLocalized( 200, 189, 200, 40, 1051007, false, false ); // Honesty + AddHtmlLocalized(80, 100, 100, 40, 1051000, false, false); // Humility + AddHtmlLocalized(80, 129, 100, 40, 1051001, false, false); // Sacrifice + AddHtmlLocalized(80, 159, 100, 40, 1051002, false, false); // Compassion + AddHtmlLocalized(80, 189, 100, 40, 1051003, false, false); // Spirituality + AddHtmlLocalized(200, 100, 200, 40, 1051004, false, false); // Valor + AddHtmlLocalized(200, 129, 200, 40, 1051005, false, false); // Honor + AddHtmlLocalized(200, 159, 200, 40, 1051006, false, false); // Justice + AddHtmlLocalized(200, 189, 200, 40, 1051007, false, false); // Honesty - AddHtmlLocalized( 75, 224, 220, 60, 1052062, false, false ); // Click on a blue gem to view your status in that virtue. + AddHtmlLocalized(75, 224, 220, 60, 1052062, false, + false); // Click on a blue gem to view your status in that virtue. - AddButton( 60, 100, 1210, 1210, 1, GumpButtonType.Reply, 0 ); - AddButton( 60, 129, 1210, 1210, 2, GumpButtonType.Reply, 0 ); - AddButton( 60, 159, 1210, 1210, 3, GumpButtonType.Reply, 0 ); - AddButton( 60, 189, 1210, 1210, 4, GumpButtonType.Reply, 0 ); - AddButton( 180, 100, 1210, 1210, 5, GumpButtonType.Reply, 0 ); - AddButton( 180, 129, 1210, 1210, 6, GumpButtonType.Reply, 0 ); - AddButton( 180, 159, 1210, 1210, 7, GumpButtonType.Reply, 0 ); - AddButton( 180, 189, 1210, 1210, 8, GumpButtonType.Reply, 0 ); + AddButton(60, 100, 1210, 1210, 1, GumpButtonType.Reply, 0); + AddButton(60, 129, 1210, 1210, 2, GumpButtonType.Reply, 0); + AddButton(60, 159, 1210, 1210, 3, GumpButtonType.Reply, 0); + AddButton(60, 189, 1210, 1210, 4, GumpButtonType.Reply, 0); + AddButton(180, 100, 1210, 1210, 5, GumpButtonType.Reply, 0); + AddButton(180, 129, 1210, 1210, 6, GumpButtonType.Reply, 0); + AddButton(180, 159, 1210, 1210, 7, GumpButtonType.Reply, 0); + AddButton(180, 189, 1210, 1210, 8, GumpButtonType.Reply, 0); - AddButton( 280, 43, 4014, 4014, 9, GumpButtonType.Reply, 0 ); - } + AddButton(280, 43, 4014, 4014, 9, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState state, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 1: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Humility, 1052051 ) ); - break; - } - case 2: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Sacrifice, 1052053, @"http://update.uo.com/design_389.html" ) ); - break; - } - case 3: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Compassion, 1053000, @"http://update.uo.com/design_412.html" ) ); - break; - } - case 4: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Spirituality, 1052056 ) ); - break; - } - case 5: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Valor, 1054033, @"http://update.uo.com/design_427.html" ) ); - break; - } - case 6: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Honor, 1052058, @"http://guide.uo.com/virtues_2.html" ) ); - break; - } - case 7: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Justice, 1052059, @"http://update.uo.com/design_413.html" ) ); - break; - } - case 8: - { - m_Beholder.SendGump( new VirtueInfoGump( m_Beholder, VirtueName.Honesty, 1052060 ) ); - break; - } - case 9: - { - m_Beholder.SendGump( new VirtueGump( m_Beholder, m_Beholder ) ); - break; - } - } - } - } + public override void OnResponse(NetState state, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Humility, 1052051)); + break; + } + case 2: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Sacrifice, 1052053, + @"http://update.uo.com/design_389.html")); + break; + } + case 3: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Compassion, 1053000, + @"http://update.uo.com/design_412.html")); + break; + } + case 4: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Spirituality, 1052056)); + break; + } + case 5: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Valor, 1054033, + @"http://update.uo.com/design_427.html")); + break; + } + case 6: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Honor, 1052058, + @"http://guide.uo.com/virtues_2.html")); + break; + } + case 7: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Justice, 1052059, + @"http://update.uo.com/design_413.html")); + break; + } + case 8: + { + m_Beholder.SendGump(new VirtueInfoGump(m_Beholder, VirtueName.Honesty, 1052060)); + break; + } + case 9: + { + m_Beholder.SendGump(new VirtueGump(m_Beholder, m_Beholder)); + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/AddDoorGump.cs b/Scripts/Gumps/AddDoorGump.cs index 28092b03d..da1daa181 100644 --- a/Scripts/Gumps/AddDoorGump.cs +++ b/Scripts/Gumps/AddDoorGump.cs @@ -1,124 +1,125 @@ using System; +using Server.Commands; using Server.Items; using Server.Network; -using Server.Commands; namespace Server.Gumps { - public class AddDoorGump : Gump - { - private int m_Type; + public class AddDoorGump : Gump + { + public static DoorInfo[] m_Types = + { + new DoorInfo(typeof(MetalDoor), 0x675), + new DoorInfo(typeof(RattanDoor), 0x695), + new DoorInfo(typeof(DarkWoodDoor), 0x6A5), + new DoorInfo(typeof(LightWoodDoor), 0x6D5), + new DoorInfo(typeof(StrongWoodDoor), 0x6E5) + }; - public AddDoorGump() : this( -1 ) - { - } + private int m_Type; - public void AddBlueBack( int width, int height ) - { - AddBackground ( 0, 0, width-00, height-00, 0xE10 ); - AddBackground ( 8, 5, width-16, height-11, 0x053 ); - AddImageTiled ( 15, 14, width-29, height-29, 0xE14 ); - AddAlphaRegion( 15, 14, width-29, height-29 ); - } + public AddDoorGump() : this(-1) + { + } - public AddDoorGump( int type ) : base( 50, 40 ) - { - m_Type = type; + public AddDoorGump(int type) : base(50, 40) + { + m_Type = type; - AddPage( 0 ); + AddPage(0); - if ( m_Type >= 0 && m_Type < m_Types.Length ) - { - AddBlueBack( 155, 174 ); + if (m_Type >= 0 && m_Type < m_Types.Length) + { + AddBlueBack(155, 174); - int baseID = m_Types[m_Type].m_BaseID; + int baseID = m_Types[m_Type].m_BaseID; - AddItem( 25, 24, baseID ); - AddButton( 26, 37, 0x5782, 0x5782, 1, GumpButtonType.Reply, 0 ); + AddItem(25, 24, baseID); + AddButton(26, 37, 0x5782, 0x5782, 1, GumpButtonType.Reply, 0); - AddItem( 47, 45, baseID + 2 ); - AddButton( 43, 57, 0x5783, 0x5783, 2, GumpButtonType.Reply, 0 ); + AddItem(47, 45, baseID + 2); + AddButton(43, 57, 0x5783, 0x5783, 2, GumpButtonType.Reply, 0); - AddItem( 87, 22, baseID + 10 ); - AddButton( 116, 35, 0x5785, 0x5785, 6, GumpButtonType.Reply, 0 ); + AddItem(87, 22, baseID + 10); + AddButton(116, 35, 0x5785, 0x5785, 6, GumpButtonType.Reply, 0); - AddItem( 65, 45, baseID + 8 ); - AddButton( 96, 55, 0x5784, 0x5784, 5, GumpButtonType.Reply, 0 ); + AddItem(65, 45, baseID + 8); + AddButton(96, 55, 0x5784, 0x5784, 5, GumpButtonType.Reply, 0); - AddButton( 73, 36, 0x2716, 0x2716, 9, GumpButtonType.Reply, 0 ); - } - else - { - AddBlueBack( 265, 145 ); + AddButton(73, 36, 0x2716, 0x2716, 9, GumpButtonType.Reply, 0); + } + else + { + AddBlueBack(265, 145); - for ( int i = 0; i < m_Types.Length; ++i ) - { - AddButton( 30 + (i * 49), 13, 0x2624, 0x2625, i + 1, GumpButtonType.Reply, 0 ); - AddItem( 22 + (i * 49), 20, m_Types[i].m_BaseID ); - } - } - } + for (int i = 0; i < m_Types.Length; ++i) + { + AddButton(30 + i * 49, 13, 0x2624, 0x2625, i + 1, GumpButtonType.Reply, 0); + AddItem(22 + i * 49, 20, m_Types[i].m_BaseID); + } + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; - int button = info.ButtonID - 1; + public void AddBlueBack(int width, int height) + { + AddBackground(0, 0, width - 00, height - 00, 0xE10); + AddBackground(8, 5, width - 16, height - 11, 0x053); + AddImageTiled(15, 14, width - 29, height - 29, 0xE14); + AddAlphaRegion(15, 14, width - 29, height - 29); + } - if ( m_Type == -1 ) - { - if ( button >= 0 && button < m_Types.Length ) - from.SendGump( new AddDoorGump( button ) ); - } - else - { - if ( button >= 0 && button < 8 ) - { - from.SendGump( new AddDoorGump( m_Type ) ); - CommandSystem.Handle( from, - $"{CommandSystem.Prefix}Add {m_Types[m_Type].m_Type.Name} {(DoorFacing) button}"); - } - else if ( button == 8 ) - { - from.SendGump( new AddDoorGump( m_Type ) ); - CommandSystem.Handle( from, $"{CommandSystem.Prefix}Link"); - } - else - { - from.SendGump( new AddDoorGump() ); - } - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; + int button = info.ButtonID - 1; - public static void Initialize() - { - CommandSystem.Register( "AddDoor", AccessLevel.GameMaster, AddDoor_OnCommand ); - } + if (m_Type == -1) + { + if (button >= 0 && button < m_Types.Length) + from.SendGump(new AddDoorGump(button)); + } + else + { + if (button >= 0 && button < 8) + { + from.SendGump(new AddDoorGump(m_Type)); + CommandSystem.Handle(from, + $"{CommandSystem.Prefix}Add {m_Types[m_Type].m_Type.Name} {(DoorFacing)button}"); + } + else if (button == 8) + { + from.SendGump(new AddDoorGump(m_Type)); + CommandSystem.Handle(from, $"{CommandSystem.Prefix}Link"); + } + else + { + from.SendGump(new AddDoorGump()); + } + } + } - [Usage( "AddDoor" )] - [Description( "Displays a menu from which you can interactively add doors." )] - public static void AddDoor_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendGump( new AddDoorGump() ); - } + public static void Initialize() + { + CommandSystem.Register("AddDoor", AccessLevel.GameMaster, AddDoor_OnCommand); + } - public static DoorInfo[] m_Types = { - new DoorInfo( typeof( MetalDoor ), 0x675 ), - new DoorInfo( typeof( RattanDoor ), 0x695 ), - new DoorInfo( typeof( DarkWoodDoor ), 0x6A5 ), - new DoorInfo( typeof( LightWoodDoor ), 0x6D5 ), - new DoorInfo( typeof( StrongWoodDoor ), 0x6E5 ) - }; - } + [Usage("AddDoor")] + [Description("Displays a menu from which you can interactively add doors.")] + public static void AddDoor_OnCommand(CommandEventArgs e) + { + e.Mobile.SendGump(new AddDoorGump()); + } + } - public class DoorInfo - { - public Type m_Type; - public int m_BaseID; + public class DoorInfo + { + public int m_BaseID; + public Type m_Type; - public DoorInfo( Type type, int baseID ) - { - m_Type = type; - m_BaseID = baseID; - } - } + public DoorInfo(Type type, int baseID) + { + m_Type = type; + m_BaseID = baseID; + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/AddGump.cs b/Scripts/Gumps/AddGump.cs index cc746c5fe..9c87f5542 100644 --- a/Scripts/Gumps/AddGump.cs +++ b/Scripts/Gumps/AddGump.cs @@ -7,247 +7,245 @@ using Server.Targeting; namespace Server.Gumps { - public class AddGump : Gump - { - private string m_SearchString; - private Type[] m_SearchResults; - private int m_Page; + public class AddGump : Gump + { + private static Type typeofItem = typeof(Item), typeofMobile = typeof(Mobile); + private int m_Page; + private Type[] m_SearchResults; + private string m_SearchString; - public static void Initialize() - { - CommandSystem.Register( "AddMenu", AccessLevel.GameMaster, AddMenu_OnCommand ); - } + public AddGump(Mobile from, string searchString, int page, Type[] searchResults, bool explicitSearch) : base(50, 50) + { + m_SearchString = searchString; + m_SearchResults = searchResults; + m_Page = page; - [Usage( "AddMenu [searchString]" )] - [Description( "Opens an add menu, with an optional initial search string. This menu allows you to search for Items or Mobiles and add them interactively." )] - private static void AddMenu_OnCommand( CommandEventArgs e ) - { - string val = e.ArgString.Trim(); - Type[] types; - bool explicitSearch = false; + from.CloseGump(typeof(AddGump)); - if ( val.Length == 0 ) - { - types = Type.EmptyTypes; - } - else if ( val.Length < 3 ) - { - e.Mobile.SendMessage( "Invalid search string." ); - types = Type.EmptyTypes; - } - else - { - types = Match( val ).ToArray(); - explicitSearch = true; - } + AddPage(0); - e.Mobile.SendGump( new AddGump( e.Mobile, val, 0, types, explicitSearch ) ); - } + AddBackground(0, 0, 420, 280, 5054); - public AddGump( Mobile from, string searchString, int page, Type[] searchResults, bool explicitSearch ) : base( 50, 50 ) - { - m_SearchString = searchString; - m_SearchResults = searchResults; - m_Page = page; + AddImageTiled(10, 10, 400, 20, 2624); + AddAlphaRegion(10, 10, 400, 20); + AddImageTiled(41, 11, 184, 18, 0xBBC); + AddImageTiled(42, 12, 182, 16, 2624); + AddAlphaRegion(42, 12, 182, 16); - from.CloseGump( typeof( AddGump ) ); + AddButton(10, 9, 4011, 4013, 1, GumpButtonType.Reply, 0); + AddTextEntry(44, 10, 180, 20, 0x480, 0, searchString); - AddPage( 0 ); + AddHtmlLocalized(230, 10, 100, 20, 3010005, 0x7FFF, false, false); - AddBackground( 0, 0, 420, 280, 5054 ); + AddImageTiled(10, 40, 400, 200, 2624); + AddAlphaRegion(10, 40, 400, 200); - AddImageTiled( 10, 10, 400, 20, 2624 ); - AddAlphaRegion( 10, 10, 400, 20 ); - AddImageTiled( 41, 11, 184, 18, 0xBBC ); - AddImageTiled( 42, 12, 182, 16, 2624 ); - AddAlphaRegion( 42, 12, 182, 16 ); + if (searchResults.Length > 0) + for (int i = page * 10; i < (page + 1) * 10 && i < searchResults.Length; ++i) + { + int index = i % 10; - AddButton( 10, 9, 4011, 4013, 1, GumpButtonType.Reply, 0 ); - AddTextEntry( 44, 10, 180, 20, 0x480, 0, searchString ); + AddLabel(44, 39 + index * 20, 0x480, searchResults[i].Name); + AddButton(10, 39 + index * 20, 4023, 4025, 4 + i, GumpButtonType.Reply, 0); + } + else + AddLabel(15, 44, 0x480, explicitSearch ? "Nothing matched your search terms." : "No results to display."); - AddHtmlLocalized( 230, 10, 100, 20, 3010005, 0x7FFF, false, false ); + AddImageTiled(10, 250, 400, 20, 2624); + AddAlphaRegion(10, 250, 400, 20); - AddImageTiled( 10, 40, 400, 200, 2624 ); - AddAlphaRegion( 10, 40, 400, 200 ); + if (m_Page > 0) + AddButton(10, 249, 4014, 4016, 2, GumpButtonType.Reply, 0); + else + AddImage(10, 249, 4014); - if ( searchResults.Length > 0 ) - { - for ( int i = (page * 10); i < ((page + 1) * 10) && i < searchResults.Length; ++i ) - { - int index = i % 10; + AddHtmlLocalized(44, 250, 170, 20, 1061028, m_Page > 0 ? 0x7FFF : 0x5EF7, false, false); // Previous page - AddLabel( 44, 39 + (index * 20), 0x480, searchResults[i].Name ); - AddButton( 10, 39 + (index * 20), 4023, 4025, 4 + i, GumpButtonType.Reply, 0 ); - } - } - else - { - AddLabel( 15, 44, 0x480, explicitSearch ? "Nothing matched your search terms." : "No results to display." ); - } + if ((m_Page + 1) * 10 < searchResults.Length) + AddButton(210, 249, 4005, 4007, 3, GumpButtonType.Reply, 0); + else + AddImage(210, 249, 4005); - AddImageTiled( 10, 250, 400, 20, 2624 ); - AddAlphaRegion( 10, 250, 400, 20 ); + AddHtmlLocalized(244, 250, 170, 20, 1061027, (m_Page + 1) * 10 < searchResults.Length ? 0x7FFF : 0x5EF7, false, + false); // Next page + } - if ( m_Page > 0 ) - AddButton( 10, 249, 4014, 4016, 2, GumpButtonType.Reply, 0 ); - else - AddImage( 10, 249, 4014 ); + public static void Initialize() + { + CommandSystem.Register("AddMenu", AccessLevel.GameMaster, AddMenu_OnCommand); + } - AddHtmlLocalized( 44, 250, 170, 20, 1061028, m_Page > 0 ? 0x7FFF : 0x5EF7, false, false ); // Previous page + [Usage("AddMenu [searchString]")] + [Description( + "Opens an add menu, with an optional initial search string. This menu allows you to search for Items or Mobiles and add them interactively.")] + private static void AddMenu_OnCommand(CommandEventArgs e) + { + string val = e.ArgString.Trim(); + Type[] types; + bool explicitSearch = false; - if ( ((m_Page + 1) * 10) < searchResults.Length ) - AddButton( 210, 249, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - else - AddImage( 210, 249, 4005 ); + if (val.Length == 0) + { + types = Type.EmptyTypes; + } + else if (val.Length < 3) + { + e.Mobile.SendMessage("Invalid search string."); + types = Type.EmptyTypes; + } + else + { + types = Match(val).ToArray(); + explicitSearch = true; + } - AddHtmlLocalized( 244, 250, 170, 20, 1061027, ((m_Page + 1) * 10) < searchResults.Length ? 0x7FFF : 0x5EF7, false, false ); // Next page - } + e.Mobile.SendGump(new AddGump(e.Mobile, val, 0, types, explicitSearch)); + } - private static Type typeofItem = typeof( Item ), typeofMobile = typeof( Mobile ); + private static void Match(string match, Type[] types, List results) + { + if (match.Length == 0) + return; - private static void Match( string match, Type[] types, List results ) - { - if ( match.Length == 0 ) - return; + match = match.ToLower(); - match = match.ToLower(); + for (int i = 0; i < types.Length; ++i) + { + Type t = types[i]; - for ( int i = 0; i < types.Length; ++i ) - { - Type t = types[i]; + if ((typeofMobile.IsAssignableFrom(t) || typeofItem.IsAssignableFrom(t)) && + t.Name.ToLower().IndexOf(match) >= 0 && !results.Contains(t)) + { + ConstructorInfo[] ctors = t.GetConstructors(); - if ( (typeofMobile.IsAssignableFrom( t ) || typeofItem.IsAssignableFrom( t )) && t.Name.ToLower().IndexOf( match ) >= 0 && !results.Contains( t ) ) - { - ConstructorInfo[] ctors = t.GetConstructors(); + for (int j = 0; j < ctors.Length; ++j) + if (ctors[j].GetParameters().Length == 0 && + ctors[j].IsDefined(typeof(ConstructibleAttribute), false)) + { + results.Add(t); + break; + } + } + } + } - for ( int j = 0; j < ctors.Length; ++j ) - { - if ( ctors[j].GetParameters().Length == 0 && ctors[j].IsDefined( typeof( ConstructibleAttribute ), false ) ) - { - results.Add( t ); - break; - } - } - } - } - } + public static List Match(string match) + { + List results = new List(); + Type[] types; - public static List Match( string match ) - { - List results = new List(); - Type[] types; + Assembly[] asms = ScriptCompiler.Assemblies; - Assembly[] asms = ScriptCompiler.Assemblies; + for (int i = 0; i < asms.Length; ++i) + { + types = ScriptCompiler.GetTypeCache(asms[i]).Types; + Match(match, types, results); + } - for ( int i = 0; i < asms.Length; ++i ) - { - types = ScriptCompiler.GetTypeCache( asms[i] ).Types; - Match( match, types, results ); - } + types = ScriptCompiler.GetTypeCache(Core.Assembly).Types; + Match(match, types, results); - types = ScriptCompiler.GetTypeCache( Core.Assembly ).Types; - Match( match, types, results ); + results.Sort(new TypeNameComparer()); - results.Sort( new TypeNameComparer() ); + return results; + } - return results; - } + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - private class TypeNameComparer : IComparer - { - public int Compare( Type x, Type y ) - { - return x.Name.CompareTo( y.Name ); - } - } + switch (info.ButtonID) + { + case 1: // Search + { + TextRelay te = info.GetTextEntry(0); + string match = te == null ? "" : te.Text.Trim(); - public class InternalTarget : Target - { - private Type m_Type; - private Type[] m_SearchResults; - private string m_SearchString; - private int m_Page; + if (match.Length < 3) + { + from.SendMessage("Invalid search string."); + from.SendGump(new AddGump(from, match, m_Page, m_SearchResults, false)); + } + else + { + from.SendGump(new AddGump(from, match, 0, Match(match).ToArray(), true)); + } - public InternalTarget( Type type, Type[] searchResults, string searchString, int page ) : base( -1, true, TargetFlags.None ) - { - m_Type = type; - m_SearchResults = searchResults; - m_SearchString = searchString; - m_Page = page; - } + break; + } + case 2: // Previous page + { + if (m_Page > 0) + from.SendGump(new AddGump(from, m_SearchString, m_Page - 1, m_SearchResults, true)); - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D p ) - { - if ( p is Item item ) - p = item.GetWorldTop(); - else if ( p is Mobile m ) - p = m.Location; + break; + } + case 3: // Next page + { + if ((m_Page + 1) * 10 < m_SearchResults.Length) + from.SendGump(new AddGump(from, m_SearchString, m_Page + 1, m_SearchResults, true)); - Commands.Add.Invoke( from, new Point3D( p ), new Point3D( p ), new[]{ m_Type.Name } ); + break; + } + default: + { + int index = info.ButtonID - 4; - from.Target = new InternalTarget( m_Type, m_SearchResults, m_SearchString, m_Page ); - } - } + if (index >= 0 && index < m_SearchResults.Length) + { + from.SendMessage("Where do you wish to place this object? to cancel."); + from.Target = new InternalTarget(m_SearchResults[index], m_SearchResults, m_SearchString, m_Page); + } - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - if ( cancelType == TargetCancelType.Canceled ) - from.SendGump( new AddGump( from, m_SearchString, m_Page, m_SearchResults, true ) ); - } - } + break; + } + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + private class TypeNameComparer : IComparer + { + public int Compare(Type x, Type y) + { + return x.Name.CompareTo(y.Name); + } + } - switch ( info.ButtonID ) - { - case 1: // Search - { - TextRelay te = info.GetTextEntry( 0 ); - string match = ( te == null ? "" : te.Text.Trim() ); + public class InternalTarget : Target + { + private int m_Page; + private Type[] m_SearchResults; + private string m_SearchString; + private Type m_Type; - if ( match.Length < 3 ) - { - from.SendMessage( "Invalid search string." ); - from.SendGump( new AddGump( from, match, m_Page, m_SearchResults, false ) ); - } - else - { - from.SendGump( new AddGump( from, match, 0, Match( match ).ToArray(), true ) ); - } + public InternalTarget(Type type, Type[] searchResults, string searchString, int page) : base(-1, true, + TargetFlags.None) + { + m_Type = type; + m_SearchResults = searchResults; + m_SearchString = searchString; + m_Page = page; + } - break; - } - case 2: // Previous page - { - if ( m_Page > 0 ) - from.SendGump( new AddGump( from, m_SearchString, m_Page - 1, m_SearchResults, true ) ); + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D p) + { + if (p is Item item) + p = item.GetWorldTop(); + else if (p is Mobile m) + p = m.Location; - break; - } - case 3: // Next page - { - if ( (m_Page + 1) * 10 < m_SearchResults.Length ) - from.SendGump( new AddGump( from, m_SearchString, m_Page + 1, m_SearchResults, true ) ); + Commands.Add.Invoke(from, new Point3D(p), new Point3D(p), new[] { m_Type.Name }); - break; - } - default: - { - int index = info.ButtonID - 4; + from.Target = new InternalTarget(m_Type, m_SearchResults, m_SearchString, m_Page); + } + } - if ( index >= 0 && index < m_SearchResults.Length ) - { - from.SendMessage( "Where do you wish to place this object? to cancel." ); - from.Target = new InternalTarget( m_SearchResults[index], m_SearchResults, m_SearchString, m_Page ); - } - - break; - } - } - } - } -} + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + if (cancelType == TargetCancelType.Canceled) + from.SendGump(new AddGump(from, m_SearchString, m_Page, m_SearchResults, true)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/AdminGump.cs b/Scripts/Gumps/AdminGump.cs index e73184361..d067857f5 100644 --- a/Scripts/Gumps/AdminGump.cs +++ b/Scripts/Gumps/AdminGump.cs @@ -1,2976 +1,3226 @@ using System; -using System.Net; -using System.Text; using System.Collections; using System.Collections.Generic; -using Server.Items; -using Server.Prompts; -using Server.Network; +using System.Net; +using System.Text; +using System.Threading; using Server.Accounting; using Server.Commands; -using Server.Multis; +using Server.Items; using Server.Misc; +using Server.Multis; +using Server.Network; +using Server.Prompts; +using Server.RemoteAdmin; namespace Server.Gumps { - public enum AdminGumpPage - { - Information_General, - Information_Perf, - Administer, - Clients, - Accounts, - Accounts_Shared, - Firewall, - Administer_WorldBuilding, - Administer_Server, - Administer_Access, - Administer_Access_Lockdown, - Administer_Commands, - ClientInfo, - AccountDetails, - AccountDetails_Information, - AccountDetails_Characters, - AccountDetails_Access, - AccountDetails_Access_ClientIPs, - AccountDetails_Access_Restrictions, - AccountDetails_Comments, - AccountDetails_Tags, - AccountDetails_ChangePassword, - AccountDetails_ChangeAccess, - FirewallInfo - } - - public class AdminGump : Gump - { - private Mobile m_From; - private AdminGumpPage m_PageType; - private ArrayList m_List; - private int m_ListPage; - private object m_State; - - private const int LabelColor = 0x7FFF; - private const int SelectedColor = 0x421F; - private const int DisabledColor = 0x4210; - - private const int LabelColor32 = 0xFFFFFF; - private const int SelectedColor32 = 0x8080FF; - private const int DisabledColor32 = 0x808080; - - private const int LabelHue = 0x480; - private const int GreenHue = 0x40; - private const int RedHue = 0x20; - - public void AddPageButton( int x, int y, int buttonID, string text, AdminGumpPage page, params AdminGumpPage[] subPages ) - { - bool isSelection = ( m_PageType == page ); - - for ( int i = 0; !isSelection && i < subPages.Length; ++i ) - isSelection = ( m_PageType == subPages[i] ); - - AddSelectedButton( x, y, buttonID, text, isSelection ); - } - - public void AddSelectedButton( int x, int y, int buttonID, string text, bool isSelection ) - { - AddButton( x, y - 1, isSelection ? 4006 : 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - AddHtml( x + 35, y, 200, 20, Color( text, isSelection ? SelectedColor32 : LabelColor32 ), false, false ); - } - - public void AddButtonLabeled( int x, int y, int buttonID, string text ) - { - AddButton( x, y - 1, 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - AddHtml( x + 35, y, 240, 20, Color( text, LabelColor32 ), false, false ); - } - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - public void AddBlackAlpha( int x, int y, int width, int height ) - { - AddImageTiled( x, y, width, height, 2624 ); - AddAlphaRegion( x, y, width, height ); - } - - public int GetButtonID( int type, int index ) - { - return 1 + (index * 11) + type; - } - - public static string FormatTimeSpan( TimeSpan ts ) - { - return $"{ts.Days:D2}:{ts.Hours % 24:D2}:{ts.Minutes % 60:D2}:{ts.Seconds % 60:D2}"; - } - - public static string FormatByteAmount( long totalBytes ) - { - if ( totalBytes > 1000000000 ) - return $"{(double) totalBytes / 1073741824:F1} GB"; - - if ( totalBytes > 1000000 ) - return $"{(double) totalBytes / 1048576:F1} MB"; - - if ( totalBytes > 1000 ) - return $"{(double) totalBytes / 1024:F1} KB"; - - return $"{totalBytes} Bytes"; - } - - public static void Initialize() - { - CommandSystem.Register( "Admin", AccessLevel.Administrator, Admin_OnCommand ); - } - - [Usage( "Admin" )] - [Description( "Opens an interface providing server information and administration features including client, account, and firewall management." )] - public static void Admin_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendGump( new AdminGump( e.Mobile, AdminGumpPage.Clients, 0, null, null, null ) ); - } - - public static int GetHueFor( Mobile m ) - { - if ( m == null ) - return LabelHue; - - switch ( m.AccessLevel ) - { - case AccessLevel.Owner: - case AccessLevel.Developer: - case AccessLevel.Administrator: return 0x516; - case AccessLevel.Seer: return 0x144; - case AccessLevel.GameMaster: return 0x21; - case AccessLevel.Counselor: return 0x2; - case AccessLevel.Player: default: - { - if ( m.Kills >= 5 ) - return 0x21; - - return m.Criminal ? 0x3B1 : 0x58; - } - } - } - - private static string[] m_AccessLevelStrings = { - "Player", - "Counselor", - "Game Master", - "Seer", - "Administrator", - "Developer", - "Owner" - }; - - public static string FormatAccessLevel( AccessLevel level ) - { - int v = (int)level; - - if ( v >= 0 && v < m_AccessLevelStrings.Length ) - return m_AccessLevelStrings[v]; - - return "Unknown"; - } - - public AdminGump( Mobile from, AdminGumpPage pageType, int listPage, ArrayList list, string notice, object state ) : base( 50, 40 ) - { - from.CloseGump( typeof( AdminGump ) ); - - m_From = from; - m_PageType = pageType; - m_ListPage = listPage; - m_State = state; - m_List = list; - - AddPage( 0 ); - - AddBackground( 0, 0, 420, 440, 5054 ); - - AddBlackAlpha( 10, 10, 170, 100 ); - AddBlackAlpha( 190, 10, 220, 100 ); - AddBlackAlpha( 10, 120, 400, 260 ); - AddBlackAlpha( 10, 390, 400, 40 ); - - AddPageButton( 10, 10, GetButtonID( 0, 0 ), "INFORMATION", AdminGumpPage.Information_General, AdminGumpPage.Information_Perf ); - AddPageButton( 10, 30, GetButtonID( 0, 1 ), "ADMINISTER", AdminGumpPage.Administer, AdminGumpPage.Administer_Access, AdminGumpPage.Administer_Commands, AdminGumpPage.Administer_Server, AdminGumpPage.Administer_WorldBuilding, AdminGumpPage.Administer_Access_Lockdown ); - AddPageButton( 10, 50, GetButtonID( 0, 2 ), "CLIENT LIST", AdminGumpPage.Clients, AdminGumpPage.ClientInfo ); - AddPageButton( 10, 70, GetButtonID( 0, 3 ), "ACCOUNT LIST", AdminGumpPage.Accounts, AdminGumpPage.Accounts_Shared, AdminGumpPage.AccountDetails, AdminGumpPage.AccountDetails_Information, AdminGumpPage.AccountDetails_Characters, AdminGumpPage.AccountDetails_Access, AdminGumpPage.AccountDetails_Access_ClientIPs, AdminGumpPage.AccountDetails_Access_Restrictions, AdminGumpPage.AccountDetails_Comments, AdminGumpPage.AccountDetails_Tags, AdminGumpPage.AccountDetails_ChangeAccess, AdminGumpPage.AccountDetails_ChangePassword ); - AddPageButton( 10, 90, GetButtonID( 0, 4 ), "FIREWALL", AdminGumpPage.Firewall, AdminGumpPage.FirewallInfo ); - - if ( notice != null ) - AddHtml( 12, 392, 396, 36, Color( notice, LabelColor32 ), false, false ); - - switch ( pageType ) - { - case AdminGumpPage.Information_General: - { - int banned = 0; - int active = 0; - - foreach ( Account acct in Accounts.GetAccounts() ) - { - if ( acct.Banned ) - ++banned; - else - ++active; - } - - AddLabel( 20, 130, LabelHue, "Active Accounts:" ); - AddLabel( 150, 130, LabelHue, active.ToString() ); - - AddLabel( 20, 150, LabelHue, "Banned Accounts:" ); - AddLabel( 150, 150, LabelHue, banned.ToString() ); - - AddLabel( 20, 170, LabelHue, "Firewalled:" ); - AddLabel( 150, 170, LabelHue, Firewall.List.Count.ToString() ); - - AddLabel( 20, 190, LabelHue, "Clients:" ); - AddLabel( 150, 190, LabelHue, NetState.Instances.Count.ToString() ); - - AddLabel( 20, 210, LabelHue, "Mobiles:" ); - AddLabel( 150, 210, LabelHue, World.Mobiles.Count.ToString() ); - - AddLabel( 20, 230, LabelHue, "Mobile Scripts:" ); - AddLabel( 150, 230, LabelHue, Core.ScriptMobiles.ToString() ); - - AddLabel( 20, 250, LabelHue, "Items:" ); - AddLabel( 150, 250, LabelHue, World.Items.Count.ToString() ); - - AddLabel( 20, 270, LabelHue, "Item Scripts:" ); - AddLabel( 150, 270, LabelHue, Core.ScriptItems.ToString() ); - - AddLabel( 20, 290, LabelHue, "Uptime:" ); - AddLabel( 150, 290, LabelHue, FormatTimeSpan( DateTime.UtcNow - Clock.ServerStart ) ); - - AddLabel( 20, 310, LabelHue, "Memory:" ); - AddLabel( 150, 310, LabelHue, FormatByteAmount( GC.GetTotalMemory( false ) ) ); - - AddLabel( 20, 330, LabelHue, "Framework:" ); - AddLabel( 150, 330, LabelHue, Environment.Version.ToString() ); - - AddLabel( 20, 350, LabelHue, "Operating System: " ); - string os = Environment.OSVersion.ToString(); - - os = os.Replace( "Microsoft", "MSFT" ); - os = os.Replace( "Service Pack", "SP" ); - - AddLabel( 150, 350, LabelHue, os ); - - /*string str; + public enum AdminGumpPage + { + Information_General, + Information_Perf, + Administer, + Clients, + Accounts, + Accounts_Shared, + Firewall, + Administer_WorldBuilding, + Administer_Server, + Administer_Access, + Administer_Access_Lockdown, + Administer_Commands, + ClientInfo, + AccountDetails, + AccountDetails_Information, + AccountDetails_Characters, + AccountDetails_Access, + AccountDetails_Access_ClientIPs, + AccountDetails_Access_Restrictions, + AccountDetails_Comments, + AccountDetails_Tags, + AccountDetails_ChangePassword, + AccountDetails_ChangeAccess, + FirewallInfo + } + + public class AdminGump : Gump + { + private const int LabelColor = 0x7FFF; + private const int SelectedColor = 0x421F; + private const int DisabledColor = 0x4210; + + private const int LabelColor32 = 0xFFFFFF; + private const int SelectedColor32 = 0x8080FF; + private const int DisabledColor32 = 0x808080; + + private const int LabelHue = 0x480; + private const int GreenHue = 0x40; + private const int RedHue = 0x20; + + private static string[] m_AccessLevelStrings = + { + "Player", + "Counselor", + "Game Master", + "Seer", + "Administrator", + "Developer", + "Owner" + }; + + private Mobile m_From; + private ArrayList m_List; + private int m_ListPage; + private AdminGumpPage m_PageType; + private object m_State; + + public AdminGump(Mobile from, AdminGumpPage pageType, int listPage, ArrayList list, string notice, + object state) : base(50, 40) + { + from.CloseGump(typeof(AdminGump)); + + m_From = from; + m_PageType = pageType; + m_ListPage = listPage; + m_State = state; + m_List = list; + + AddPage(0); + + AddBackground(0, 0, 420, 440, 5054); + + AddBlackAlpha(10, 10, 170, 100); + AddBlackAlpha(190, 10, 220, 100); + AddBlackAlpha(10, 120, 400, 260); + AddBlackAlpha(10, 390, 400, 40); + + AddPageButton(10, 10, GetButtonID(0, 0), "INFORMATION", AdminGumpPage.Information_General, + AdminGumpPage.Information_Perf); + AddPageButton(10, 30, GetButtonID(0, 1), "ADMINISTER", AdminGumpPage.Administer, AdminGumpPage.Administer_Access, + AdminGumpPage.Administer_Commands, AdminGumpPage.Administer_Server, AdminGumpPage.Administer_WorldBuilding, + AdminGumpPage.Administer_Access_Lockdown); + AddPageButton(10, 50, GetButtonID(0, 2), "CLIENT LIST", AdminGumpPage.Clients, AdminGumpPage.ClientInfo); + AddPageButton(10, 70, GetButtonID(0, 3), "ACCOUNT LIST", AdminGumpPage.Accounts, AdminGumpPage.Accounts_Shared, + AdminGumpPage.AccountDetails, AdminGumpPage.AccountDetails_Information, + AdminGumpPage.AccountDetails_Characters, AdminGumpPage.AccountDetails_Access, + AdminGumpPage.AccountDetails_Access_ClientIPs, AdminGumpPage.AccountDetails_Access_Restrictions, + AdminGumpPage.AccountDetails_Comments, AdminGumpPage.AccountDetails_Tags, + AdminGumpPage.AccountDetails_ChangeAccess, AdminGumpPage.AccountDetails_ChangePassword); + AddPageButton(10, 90, GetButtonID(0, 4), "FIREWALL", AdminGumpPage.Firewall, AdminGumpPage.FirewallInfo); + + if (notice != null) + AddHtml(12, 392, 396, 36, Color(notice, LabelColor32), false, false); + + switch (pageType) + { + case AdminGumpPage.Information_General: + { + int banned = 0; + int active = 0; + + foreach (Account acct in Accounts.GetAccounts()) + if (acct.Banned) + ++banned; + else + ++active; + + AddLabel(20, 130, LabelHue, "Active Accounts:"); + AddLabel(150, 130, LabelHue, active.ToString()); + + AddLabel(20, 150, LabelHue, "Banned Accounts:"); + AddLabel(150, 150, LabelHue, banned.ToString()); + + AddLabel(20, 170, LabelHue, "Firewalled:"); + AddLabel(150, 170, LabelHue, Firewall.List.Count.ToString()); + + AddLabel(20, 190, LabelHue, "Clients:"); + AddLabel(150, 190, LabelHue, NetState.Instances.Count.ToString()); + + AddLabel(20, 210, LabelHue, "Mobiles:"); + AddLabel(150, 210, LabelHue, World.Mobiles.Count.ToString()); + + AddLabel(20, 230, LabelHue, "Mobile Scripts:"); + AddLabel(150, 230, LabelHue, Core.ScriptMobiles.ToString()); + + AddLabel(20, 250, LabelHue, "Items:"); + AddLabel(150, 250, LabelHue, World.Items.Count.ToString()); + + AddLabel(20, 270, LabelHue, "Item Scripts:"); + AddLabel(150, 270, LabelHue, Core.ScriptItems.ToString()); + + AddLabel(20, 290, LabelHue, "Uptime:"); + AddLabel(150, 290, LabelHue, FormatTimeSpan(DateTime.UtcNow - Clock.ServerStart)); + + AddLabel(20, 310, LabelHue, "Memory:"); + AddLabel(150, 310, LabelHue, FormatByteAmount(GC.GetTotalMemory(false))); + + AddLabel(20, 330, LabelHue, "Framework:"); + AddLabel(150, 330, LabelHue, Environment.Version.ToString()); + + AddLabel(20, 350, LabelHue, "Operating System: "); + string os = Environment.OSVersion.ToString(); + + os = os.Replace("Microsoft", "MSFT"); + os = os.Replace("Service Pack", "SP"); + + AddLabel(150, 350, LabelHue, os); + + /*string str; + + try{ str = FormatTimeSpan( Core.Process.TotalProcessorTime ); } + catch{ str = "(unable to retrieve)"; } + + AddLabel( 20, 330, LabelHue, "Process Time:" ); + AddLabel( 250, 330, LabelHue, str );*/ + + /*try{ str = Core.Process.PriorityClass.ToString(); } + catch{ str = "(unable to retrieve)"; } + + AddLabel( 20, 350, LabelHue, "Process Priority:" ); + AddLabel( 250, 350, LabelHue, str );*/ + + AddPageButton(200, 20, GetButtonID(0, 0), "General", AdminGumpPage.Information_General); + AddPageButton(200, 40, GetButtonID(0, 5), "Performance", AdminGumpPage.Information_Perf); + + break; + } + case AdminGumpPage.Information_Perf: + { + AddLabel(20, 130, LabelHue, "Cycles Per Second:"); + AddLabel(40, 150, LabelHue, "Current: " + Core.CyclesPerSecond.ToString("N2")); + AddLabel(40, 170, LabelHue, "Average: " + Core.AverageCPS.ToString("N2")); + + StringBuilder sb = new StringBuilder(); + + int curUser, maxUser; + int curIOCP, maxIOCP; + + ThreadPool.GetAvailableThreads(out curUser, out curIOCP); + ThreadPool.GetMaxThreads(out maxUser, out maxIOCP); + + sb.Append("Worker Threads:
Capacity: "); + sb.Append(maxUser); + sb.Append("
Available: "); + sb.Append(curUser); + sb.Append("
Usage: "); + sb.Append((maxUser - curUser) * 100 / maxUser); + sb.Append("%

IOCP Threads:
Capacity: "); + sb.Append(maxIOCP); + sb.Append("
Available: "); + sb.Append(curIOCP); + sb.Append("
Usage: "); + sb.Append((maxIOCP - curIOCP) * 100 / maxIOCP); + sb.Append("%"); + + List pools = BufferPool.Pools; + + lock (pools) + { + for (int i = 0; i < pools.Count; ++i) + { + BufferPool pool = pools[i]; + pool.GetInfo(out string name, out int freeCount, out int initialCapacity, + out int currentCapacity, out int bufferSize, out int misses); - try{ str = FormatTimeSpan( Core.Process.TotalProcessorTime ); } - catch{ str = "(unable to retrieve)"; } + if (sb.Length > 0) + sb.Append("

"); + + sb.Append(name); + sb.Append("
Size: "); + sb.Append(FormatByteAmount(bufferSize)); + sb.Append("
Capacity: "); + sb.Append(currentCapacity); + sb.Append(" ("); + sb.Append(misses); + sb.Append(" misses)
Available: "); + sb.Append(freeCount); + sb.Append("
Usage: "); + sb.Append((currentCapacity - freeCount) * 100 / currentCapacity); + sb.Append("% : "); + sb.Append(FormatByteAmount((currentCapacity - freeCount) * bufferSize)); + sb.Append(" of "); + sb.Append(FormatByteAmount(currentCapacity * bufferSize)); + } + } + + + AddLabel(20, 200, LabelHue, "Pooling:"); + AddHtml(20, 220, 380, 150, sb.ToString(), true, true); + + AddPageButton(200, 20, GetButtonID(0, 0), "General", AdminGumpPage.Information_General); + AddPageButton(200, 40, GetButtonID(0, 5), "Performance", AdminGumpPage.Information_Perf); + + break; + } + case AdminGumpPage.Administer_WorldBuilding: + { + AddHtml(10, 125, 400, 20, Color(Center("Generating"), LabelColor32), false, false); + + AddButtonLabeled(20, 150, GetButtonID(3, 100), "Documentation"); + AddButtonLabeled(220, 150, GetButtonID(3, 107), "Rebuild Categorization"); + + AddButtonLabeled(20, 175, GetButtonID(3, 101), "Teleporters"); + AddButtonLabeled(220, 175, GetButtonID(3, 102), "Moongates"); + + AddButtonLabeled(20, 200, GetButtonID(3, 103), "Vendors"); + AddButtonLabeled(220, 200, GetButtonID(3, 106), "Decoration"); + + AddButtonLabeled(20, 225, GetButtonID(3, 104), "Doors"); + AddButtonLabeled(220, 225, GetButtonID(3, 105), "Signs"); + + AddHtml(20, 275, 400, 30, Color(Center("Statics"), LabelColor32), false, false); + + AddButtonLabeled(20, 300, GetButtonID(3, 110), "Freeze (Target)"); + AddButtonLabeled(20, 325, GetButtonID(3, 111), "Freeze (World)"); + AddButtonLabeled(20, 350, GetButtonID(3, 112), "Freeze (Map)"); + + AddButtonLabeled(220, 300, GetButtonID(3, 120), "Unfreeze (Target)"); + AddButtonLabeled(220, 325, GetButtonID(3, 121), "Unfreeze (World)"); + AddButtonLabeled(220, 350, GetButtonID(3, 122), "Unfreeze (Map)"); + + goto case AdminGumpPage.Administer; + } + case AdminGumpPage.Administer_Server: + { + AddHtml(10, 125, 400, 20, Color(Center("Server"), LabelColor32), false, false); + + AddButtonLabeled(20, 150, GetButtonID(3, 200), "Save"); + + /*if ( !Core.Service ) + {*/ + AddButtonLabeled(20, 180, GetButtonID(3, 201), "Shutdown (With Save)"); + AddButtonLabeled(20, 200, GetButtonID(3, 202), "Shutdown (Without Save)"); + + AddButtonLabeled(20, 230, GetButtonID(3, 203), "Shutdown & Restart (With Save)"); + AddButtonLabeled(20, 250, GetButtonID(3, 204), "Shutdown & Restart (Without Save)"); + /*} + else + { + AddLabel( 20, 215, LabelHue, "Shutdown/Restart not available." ); + }*/ + + AddHtml(10, 295, 400, 20, Color(Center("Broadcast"), LabelColor32), false, false); + + AddTextField(20, 320, 380, 20, 0); + AddButtonLabeled(20, 350, GetButtonID(3, 210), "To Everyone"); + AddButtonLabeled(220, 350, GetButtonID(3, 211), "To Staff"); + + goto case AdminGumpPage.Administer; + } + case AdminGumpPage.Administer_Access_Lockdown: + { + AddHtml(10, 125, 400, 20, Color(Center("Server Lockdown"), LabelColor32), false, false); + + AddHtml(20, 150, 380, 80, + Color( + "When enabled, only clients with an access level equal to or greater than the specified lockdown level may access the server. After setting a lockdown level, use the Purge Invalid Clients button to disconnect those clients without access.", + LabelColor32), false, false); + + AccessLevel level = AccountHandler.LockdownLevel; + bool isLockedDown = level > AccessLevel.Player; + + AddSelectedButton(20, 230, GetButtonID(3, 500), "Not Locked Down", !isLockedDown); + AddSelectedButton(20, 260, GetButtonID(3, 504), "Administrators", + isLockedDown && level <= AccessLevel.Administrator); + AddSelectedButton(20, 280, GetButtonID(3, 503), "Seers", isLockedDown && level <= AccessLevel.Seer); + AddSelectedButton(20, 300, GetButtonID(3, 502), "Game Masters", + isLockedDown && level <= AccessLevel.GameMaster); + AddSelectedButton(20, 320, GetButtonID(3, 501), "Counselors", + isLockedDown && level <= AccessLevel.Counselor); + + AddButtonLabeled(20, 350, GetButtonID(3, 510), "Purge Invalid Clients"); + + goto case AdminGumpPage.Administer; + } + case AdminGumpPage.Administer_Access: + { + AddHtml(10, 125, 400, 20, Color(Center("Access"), LabelColor32), false, false); + + AddHtml(10, 155, 400, 20, Color(Center("Connectivity"), LabelColor32), false, false); + + AddButtonLabeled(20, 180, GetButtonID(3, 300), "Kick"); + AddButtonLabeled(220, 180, GetButtonID(3, 301), "Ban"); - AddLabel( 20, 330, LabelHue, "Process Time:" ); - AddLabel( 250, 330, LabelHue, str );*/ + AddButtonLabeled(20, 210, GetButtonID(3, 302), "Firewall"); + AddButtonLabeled(220, 210, GetButtonID(3, 303), "Lockdown"); + + AddHtml(10, 245, 400, 20, Color(Center("Staff"), LabelColor32), false, false); + + AddButtonLabeled(20, 270, GetButtonID(3, 310), "Make Player"); + AddButtonLabeled(20, 290, GetButtonID(3, 311), "Make Counselor"); + AddButtonLabeled(20, 310, GetButtonID(3, 312), "Make Game Master"); + AddButtonLabeled(20, 330, GetButtonID(3, 313), "Make Seer"); + + if (from.AccessLevel > AccessLevel.Administrator) + { + AddButtonLabeled(220, 270, GetButtonID(3, 314), "Make Administrator"); + + if (from.AccessLevel > AccessLevel.Developer) + { + AddButtonLabeled(220, 290, GetButtonID(3, 315), "Make Developer"); + + if (from.AccessLevel >= AccessLevel.Owner) + AddButtonLabeled(220, 310, GetButtonID(3, 316), "Make Owner"); + } + } + + goto case AdminGumpPage.Administer; + } + case AdminGumpPage.Administer_Commands: + { + AddHtml(10, 125, 400, 20, Color(Center("Commands"), LabelColor32), false, false); + + AddButtonLabeled(20, 150, GetButtonID(3, 400), "Add"); + AddButtonLabeled(220, 150, GetButtonID(3, 401), "Remove"); + + AddButtonLabeled(20, 170, GetButtonID(3, 402), "Dupe"); + AddButtonLabeled(220, 170, GetButtonID(3, 403), "Dupe in bag"); + + AddButtonLabeled(20, 200, GetButtonID(3, 404), "Properties"); + AddButtonLabeled(220, 200, GetButtonID(3, 405), "Skills"); + + AddButtonLabeled(20, 230, GetButtonID(3, 406), "Mortal"); + AddButtonLabeled(220, 230, GetButtonID(3, 407), "Immortal"); + + AddButtonLabeled(20, 250, GetButtonID(3, 408), "Squelch"); + AddButtonLabeled(220, 250, GetButtonID(3, 409), "Unsquelch"); + + AddButtonLabeled(20, 270, GetButtonID(3, 410), "Freeze"); + AddButtonLabeled(220, 270, GetButtonID(3, 411), "Unfreeze"); + + AddButtonLabeled(20, 290, GetButtonID(3, 412), "Hide"); + AddButtonLabeled(220, 290, GetButtonID(3, 413), "Unhide"); + + AddButtonLabeled(20, 310, GetButtonID(3, 414), "Kill"); + AddButtonLabeled(220, 310, GetButtonID(3, 415), "Resurrect"); + + AddButtonLabeled(20, 330, GetButtonID(3, 416), "Move"); + AddButtonLabeled(220, 330, GetButtonID(3, 417), "Wipe"); + + AddButtonLabeled(20, 350, GetButtonID(3, 418), "Teleport"); + AddButtonLabeled(220, 350, GetButtonID(3, 419), "Teleport (Multiple)"); + + goto case AdminGumpPage.Administer; + } + case AdminGumpPage.Administer: + { + AddPageButton(200, 20, GetButtonID(3, 0), "World Building", AdminGumpPage.Administer_WorldBuilding); + AddPageButton(200, 40, GetButtonID(3, 1), "Server", AdminGumpPage.Administer_Server); + AddPageButton(200, 60, GetButtonID(3, 2), "Access", AdminGumpPage.Administer_Access, + AdminGumpPage.Administer_Access_Lockdown); + AddPageButton(200, 80, GetButtonID(3, 3), "Commands", AdminGumpPage.Administer_Commands); + + break; + } + case AdminGumpPage.Clients: + { + if (m_List == null) + { + m_List = new ArrayList(NetState.Instances); + m_List.Sort(NetStateComparer.Instance); + } + + AddClientHeader(); + + AddLabelCropped(12, 120, 81, 20, LabelHue, "Name"); + AddLabelCropped(95, 120, 81, 20, LabelHue, "Account"); + AddLabelCropped(178, 120, 81, 20, LabelHue, "Access Level"); + AddLabelCropped(273, 120, 109, 20, LabelHue, "IP Address"); + + if (listPage > 0) + AddButton(375, 122, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(375, 122, 0x25EA); + + if ((listPage + 1) * 12 < m_List.Count) + AddButton(392, 122, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(392, 122, 0x25E6); + + if (m_List.Count == 0) + AddLabel(12, 140, LabelHue, "There are no clients to display."); + + for (int i = 0, index = listPage * 12; i < 12 && index >= 0 && index < m_List.Count; ++i, ++index) + { + if (!(m_List[index] is NetState ns)) + continue; + + Mobile m = ns.Mobile; + Account a = ns.Account as Account; + int offset = 140 + i * 20; + + if (m == null) + AddLabelCropped(12, offset, 81, 20, LabelHue, + AdminNetwork.IsAuth(ns) ? "(remote admin)" : "(logging in)"); + else + AddLabelCropped(12, offset, 81, 20, GetHueFor(m), m.Name); + AddLabelCropped(95, offset, 81, 20, LabelHue, a == null ? "(no account)" : a.Username); + AddLabelCropped(178, offset, 81, 20, LabelHue, + m == null + ? a != null ? FormatAccessLevel(a.AccessLevel) : "" + : FormatAccessLevel(m.AccessLevel)); + AddLabelCropped(273, offset, 109, 20, LabelHue, ns.ToString()); + + if (a != null || m != null) + AddButton(380, offset - 1, 0xFA5, 0xFA7, GetButtonID(4, index + 2), GumpButtonType.Reply, 0); + } + + break; + } + case AdminGumpPage.ClientInfo: + { + if (!(state is Mobile m)) + break; + + AddClientHeader(); + + AddHtml(10, 125, 400, 20, Color(Center("Information"), LabelColor32), false, false); + + int y = 146; + + AddLabel(20, y, LabelHue, "Name:"); + AddLabel(200, y, GetHueFor(m), m.Name); + y += 20; + + Account a = m.Account as Account; + + AddLabel(20, y, LabelHue, "Account:"); + AddLabel(200, y, a != null && a.Banned ? RedHue : LabelHue, a == null ? "(no account)" : a.Username); + AddButton(380, y, 0xFA5, 0xFA7, GetButtonID(7, 14), GumpButtonType.Reply, 0); + y += 20; + + NetState ns = m.NetState; + + if (ns == null) + { + AddLabel(20, y, LabelHue, "Address:"); + AddLabel(200, y, RedHue, "Offline"); + y += 20; + + AddLabel(20, y, LabelHue, "Location:"); + AddLabel(200, y, LabelHue, $"{m.Location} [{m.Map}]"); + y += 44; + } + else + { + AddLabel(20, y, LabelHue, "Address:"); + AddLabel(200, y, GreenHue, ns.ToString()); + y += 20; + + ClientVersion v = ns.Version; + + AddLabel(20, y, LabelHue, "Version:"); + AddLabel(200, y, LabelHue, v == null ? "(null)" : v.ToString()); + y += 20; + + AddLabel(20, y, LabelHue, "Location:"); + AddLabel(200, y, LabelHue, $"{m.Location} [{m.Map}]"); + y += 24; + } + + AddButtonLabeled(20, y, GetButtonID(7, 0), "Go to"); + AddButtonLabeled(200, y, GetButtonID(7, 1), "Get"); + y += 20; + + AddButtonLabeled(20, y, GetButtonID(7, 2), "Kick"); + AddButtonLabeled(200, y, GetButtonID(7, 3), "Ban"); + y += 20; + + AddButtonLabeled(20, y, GetButtonID(7, 4), "Properties"); + AddButtonLabeled(200, y, GetButtonID(7, 5), "Skills"); + y += 20; + + AddButtonLabeled(20, y, GetButtonID(7, 6), "Mortal"); + AddButtonLabeled(200, y, GetButtonID(7, 7), "Immortal"); + y += 20; + + AddButtonLabeled(20, y, GetButtonID(7, 8), "Squelch"); + AddButtonLabeled(200, y, GetButtonID(7, 9), "Unsquelch"); + y += 20; + + /*AddButtonLabeled( 20, y, GetButtonID( 7, 10 ), "Hide" ); + AddButtonLabeled( 200, y, GetButtonID( 7, 11 ), "Unhide" ); + y += 20;*/ + + AddButtonLabeled(20, y, GetButtonID(7, 12), "Kill"); + AddButtonLabeled(200, y, GetButtonID(7, 13), "Resurrect"); + y += 20; + + break; + } + case AdminGumpPage.Accounts_Shared: + { + if (m_List == null) + m_List = GetAllSharedAccounts(); + + AddLabelCropped(12, 120, 60, 20, LabelHue, "Count"); + AddLabelCropped(72, 120, 120, 20, LabelHue, "Address"); + AddLabelCropped(192, 120, 180, 20, LabelHue, "Accounts"); - /*try{ str = Core.Process.PriorityClass.ToString(); } - catch{ str = "(unable to retrieve)"; } + if (listPage > 0) + AddButton(375, 122, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(375, 122, 0x25EA); - AddLabel( 20, 350, LabelHue, "Process Priority:" ); - AddLabel( 250, 350, LabelHue, str );*/ + if ((listPage + 1) * 12 < m_List.Count) + AddButton(392, 122, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(392, 122, 0x25E6); + + if (m_List.Count == 0) + AddLabel(12, 140, LabelHue, "There are no accounts to display."); - AddPageButton( 200, 20, GetButtonID( 0, 0 ), "General", AdminGumpPage.Information_General ); - AddPageButton( 200, 40, GetButtonID( 0, 5 ), "Performance", AdminGumpPage.Information_Perf ); - - break; - } - case AdminGumpPage.Information_Perf: - { - AddLabel( 20, 130, LabelHue, "Cycles Per Second:" ); - AddLabel( 40, 150, LabelHue, "Current: " + Core.CyclesPerSecond.ToString( "N2" ) ); - AddLabel( 40, 170, LabelHue, "Average: " + Core.AverageCPS.ToString( "N2" ) ); + StringBuilder sb = new StringBuilder(); - StringBuilder sb = new StringBuilder(); + for (int i = 0, index = listPage * 12; i < 12 && index >= 0 && index < m_List.Count; ++i, ++index) + { + DictionaryEntry de = (DictionaryEntry)m_List[index]; + + IPAddress ipAddr = (IPAddress)de.Key; + ArrayList accts = (ArrayList)de.Value; + + int offset = 140 + i * 20; + + AddLabelCropped(12, offset, 60, 20, LabelHue, accts.Count.ToString()); + AddLabelCropped(72, offset, 120, 20, LabelHue, ipAddr.ToString()); + + if (sb.Length > 0) + sb.Length = 0; + + for (int j = 0; j < accts.Count; ++j) + { + if (j > 0) + sb.Append(", "); + + if (j < 4) + { + Account acct = (Account)accts[j]; + + sb.Append(acct.Username); + } + else + { + sb.Append("..."); + break; + } + } + + AddLabelCropped(192, offset, 180, 20, LabelHue, sb.ToString()); + + AddButton(380, offset - 1, 0xFA5, 0xFA7, GetButtonID(5, index + 56), GumpButtonType.Reply, 0); + } + + break; + } + case AdminGumpPage.Accounts: + { + if (m_List == null) m_List = new ArrayList(); // new ArrayList( (ICollection)Accounts.GetAccounts() ); + + ArrayList rads = state as ArrayList; + + AddAccountHeader(); + + if (rads == null) + AddLabelCropped(12, 120, 120, 20, LabelHue, "Name"); + else + AddLabelCropped(32, 120, 100, 20, LabelHue, "Name"); + + AddLabelCropped(132, 120, 120, 20, LabelHue, "Access Level"); + AddLabelCropped(252, 120, 120, 20, LabelHue, "Status"); + + if (listPage > 0) + AddButton(375, 122, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(375, 122, 0x25EA); + + if ((listPage + 1) * 12 < m_List.Count) + AddButton(392, 122, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(392, 122, 0x25E6); + + if (m_List.Count == 0) + AddLabel(12, 140, LabelHue, "There are no accounts to display."); + + if (rads != null && notice == null) + { + AddButtonLabeled(10, 390, GetButtonID(5, 27), "Ban marked"); + AddButtonLabeled(10, 410, GetButtonID(5, 28), "Delete marked"); + + AddButtonLabeled(210, 390, GetButtonID(5, 29), "Mark all"); + AddButtonLabeled(210, 410, GetButtonID(5, 35), "Unmark house owners"); + } + + for (int i = 0, index = listPage * 12; i < 12 && index >= 0 && index < m_List.Count; ++i, ++index) + { + if (!(m_List[index] is Account a)) + continue; + + int offset = 140 + i * 20; + + GetAccountInfo(a, out AccessLevel accessLevel, out bool online); + + if (rads == null) + { + AddLabelCropped(12, offset, 120, 20, LabelHue, a.Username); + } + else + { + AddCheck(10, offset, 0xD2, 0xD3, rads.Contains(a), index); + AddLabelCropped(32, offset, 100, 20, LabelHue, a.Username); + } - int curUser, maxUser; - int curIOCP, maxIOCP; - - System.Threading.ThreadPool.GetAvailableThreads( out curUser, out curIOCP ); - System.Threading.ThreadPool.GetMaxThreads( out maxUser, out maxIOCP ); - - sb.Append( "Worker Threads:
Capacity: " ); - sb.Append( maxUser ); - sb.Append( "
Available: " ); - sb.Append( curUser ); - sb.Append( "
Usage: " ); - sb.Append( ((maxUser - curUser) * 100) / maxUser ); - sb.Append( "%

IOCP Threads:
Capacity: " ); - sb.Append( maxIOCP ); - sb.Append( "
Available: " ); - sb.Append( curIOCP ); - sb.Append( "
Usage: " ); - sb.Append( ((maxIOCP - curIOCP) * 100) / maxIOCP ); - sb.Append( "%" ); + AddLabelCropped(132, offset, 120, 20, LabelHue, FormatAccessLevel(accessLevel)); + + if (online) + AddLabelCropped(252, offset, 120, 20, GreenHue, "Online"); + else if (a.Banned) + AddLabelCropped(252, offset, 120, 20, RedHue, "Banned"); + else + AddLabelCropped(252, offset, 120, 20, RedHue, "Offline"); + + AddButton(380, offset - 1, 0xFA5, 0xFA7, GetButtonID(5, index + 56), GumpButtonType.Reply, 0); + } + + break; + } + case AdminGumpPage.AccountDetails: + { + AddPageButton(190, 10, GetButtonID(5, 0), "Information", AdminGumpPage.AccountDetails_Information, + AdminGumpPage.AccountDetails_ChangeAccess, AdminGumpPage.AccountDetails_ChangePassword); + AddPageButton(190, 30, GetButtonID(5, 1), "Characters", AdminGumpPage.AccountDetails_Characters); + AddPageButton(190, 50, GetButtonID(5, 13), "Access", AdminGumpPage.AccountDetails_Access, + AdminGumpPage.AccountDetails_Access_ClientIPs, AdminGumpPage.AccountDetails_Access_Restrictions); + AddPageButton(190, 70, GetButtonID(5, 2), "Comments", AdminGumpPage.AccountDetails_Comments); + AddPageButton(190, 90, GetButtonID(5, 3), "Tags", AdminGumpPage.AccountDetails_Tags); + break; + } + case AdminGumpPage.AccountDetails_ChangePassword: + { + if (!(state is Account a)) + break; + + AddHtml(10, 125, 400, 20, Color(Center("Change Password"), LabelColor32), false, false); + + AddLabel(20, 150, LabelHue, "Username:"); + AddLabel(200, 150, LabelHue, a.Username); + + AddLabel(20, 180, LabelHue, "Password:"); + AddTextField(200, 180, 160, 20, 0); + + AddLabel(20, 210, LabelHue, "Confirm:"); + AddTextField(200, 210, 160, 20, 1); + + AddButtonLabeled(20, 240, GetButtonID(5, 12), "Submit Change"); + + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.AccountDetails_ChangeAccess: + { + if (!(state is Account a)) + break; + + AddHtml(10, 125, 400, 20, Color(Center("Change Access Level"), LabelColor32), false, false); + + AddLabel(20, 150, LabelHue, "Username:"); + AddLabel(200, 150, LabelHue, a.Username); + + AddLabel(20, 170, LabelHue, "Current Level:"); + AddLabel(200, 170, LabelHue, FormatAccessLevel(a.AccessLevel)); + + AddButtonLabeled(20, 200, GetButtonID(5, 20), "Player"); + AddButtonLabeled(20, 220, GetButtonID(5, 21), "Counselor"); + AddButtonLabeled(20, 240, GetButtonID(5, 22), "Game Master"); + AddButtonLabeled(20, 260, GetButtonID(5, 23), "Seer"); + + if (from.AccessLevel > AccessLevel.Administrator) + { + AddButtonLabeled(20, 280, GetButtonID(5, 24), "Administrator"); + + if (from.AccessLevel > AccessLevel.Developer) + { + AddButtonLabeled(20, 300, GetButtonID(5, 33), "Developer"); + + if (from.AccessLevel >= AccessLevel.Owner) + AddButtonLabeled(20, 320, GetButtonID(5, 34), "Owner"); + } + } + + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.AccountDetails_Information: + { + if (!(state is Account a)) + break; + + int charCount = 0; + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null) + ++charCount; + + AddHtml(10, 125, 400, 20, Color(Center("Information"), LabelColor32), false, false); + + AddLabel(20, 150, LabelHue, "Username:"); + AddLabel(200, 150, LabelHue, a.Username); + + AddLabel(20, 170, LabelHue, "Access Level:"); + AddLabel(200, 170, LabelHue, FormatAccessLevel(a.AccessLevel)); + + AddLabel(20, 190, LabelHue, "Status:"); + AddLabel(200, 190, a.Banned ? RedHue : GreenHue, a.Banned ? "Banned" : "Active"); + + if (a.Banned && a.GetBanTags(out DateTime banTime, out TimeSpan banDuration)) + { + if (banDuration == TimeSpan.MaxValue) + { + AddLabel(250, 190, LabelHue, "(Infinite)"); + } + else if (banDuration == TimeSpan.Zero) + { + AddLabel(250, 190, LabelHue, "(Zero)"); + } + else + { + TimeSpan remaining = DateTime.UtcNow - banTime; + + if (remaining < TimeSpan.Zero) + remaining = TimeSpan.Zero; + else if (remaining > banDuration) + remaining = banDuration; + + double remMinutes = remaining.TotalMinutes; + double totMinutes = banDuration.TotalMinutes; + + double perc = remMinutes / totMinutes; + + AddLabel(250, 190, LabelHue, $"{FormatTimeSpan(banDuration)} [{perc * 100:F0}%]"); + } + } + else if (a.Banned) + { + AddLabel(250, 190, LabelHue, "(Unspecified)"); + } - List pools = BufferPool.Pools; + AddLabel(20, 210, LabelHue, "Created:"); + AddLabel(200, 210, LabelHue, a.Created.ToString()); - lock ( pools ) - { - for ( int i = 0; i < pools.Count; ++i ) - { - BufferPool pool = pools[i]; - pool.GetInfo( out string name, out int freeCount, out int initialCapacity, out int currentCapacity, out int bufferSize, out int misses ); + AddLabel(20, 230, LabelHue, "Last Login:"); + AddLabel(200, 230, LabelHue, a.LastLogin.ToString()); - if ( sb.Length > 0 ) - sb.Append( "

" ); + AddLabel(20, 250, LabelHue, "Character Count:"); + AddLabel(200, 250, LabelHue, charCount.ToString()); - sb.Append( name ); - sb.Append( "
Size: " ); - sb.Append( FormatByteAmount( bufferSize ) ); - sb.Append( "
Capacity: " ); - sb.Append( currentCapacity ); - sb.Append( " (" ); - sb.Append( misses ); - sb.Append( " misses)
Available: " ); - sb.Append( freeCount ); - sb.Append( "
Usage: " ); - sb.Append( ((currentCapacity - freeCount) * 100) / currentCapacity ); - sb.Append( "% : " ); - sb.Append( FormatByteAmount( (currentCapacity - freeCount) * bufferSize ) ); - sb.Append( " of " ); - sb.Append( FormatByteAmount( currentCapacity * bufferSize ) ); - } - } + AddLabel(20, 270, LabelHue, "Comment Count:"); + AddLabel(200, 270, LabelHue, a.Comments.Count.ToString()); + AddLabel(20, 290, LabelHue, "Tag Count:"); + AddLabel(200, 290, LabelHue, a.Tags.Count.ToString()); - AddLabel( 20, 200, LabelHue, "Pooling:" ); - AddHtml( 20, 220, 380, 150, sb.ToString(), true, true ); + AddButtonLabeled(20, 320, GetButtonID(5, 8), "Change Password"); + AddButtonLabeled(200, 320, GetButtonID(5, 9), "Change Access Level"); - AddPageButton( 200, 20, GetButtonID( 0, 0 ), "General", AdminGumpPage.Information_General ); - AddPageButton( 200, 40, GetButtonID( 0, 5 ), "Performance", AdminGumpPage.Information_Perf ); + if (!a.Banned) + AddButtonLabeled(20, 350, GetButtonID(5, 10), "Ban Account"); + else + AddButtonLabeled(20, 350, GetButtonID(5, 11), "Unban Account"); - break; - } - case AdminGumpPage.Administer_WorldBuilding: - { - AddHtml( 10, 125, 400, 20, Color( Center( "Generating" ), LabelColor32 ), false, false ); - - AddButtonLabeled( 20, 150, GetButtonID( 3, 100 ), "Documentation" ); - AddButtonLabeled( 220, 150, GetButtonID( 3, 107 ), "Rebuild Categorization" ); - - AddButtonLabeled( 20, 175, GetButtonID( 3, 101 ), "Teleporters" ); - AddButtonLabeled( 220, 175, GetButtonID( 3, 102 ), "Moongates" ); - - AddButtonLabeled( 20, 200, GetButtonID( 3, 103 ), "Vendors" ); - AddButtonLabeled( 220, 200, GetButtonID( 3, 106 ), "Decoration" ); - - AddButtonLabeled( 20, 225, GetButtonID( 3, 104 ), "Doors" ); - AddButtonLabeled( 220, 225, GetButtonID( 3, 105 ), "Signs" ); - - AddHtml( 20, 275, 400, 30, Color( Center( "Statics" ), LabelColor32 ), false, false ); - - AddButtonLabeled( 20, 300, GetButtonID( 3, 110 ), "Freeze (Target)" ); - AddButtonLabeled( 20, 325, GetButtonID( 3, 111 ), "Freeze (World)" ); - AddButtonLabeled( 20, 350, GetButtonID( 3, 112 ), "Freeze (Map)" ); - - AddButtonLabeled( 220, 300, GetButtonID( 3, 120 ), "Unfreeze (Target)" ); - AddButtonLabeled( 220, 325, GetButtonID( 3, 121 ), "Unfreeze (World)" ); - AddButtonLabeled( 220, 350, GetButtonID( 3, 122 ), "Unfreeze (Map)" ); - - goto case AdminGumpPage.Administer; - } - case AdminGumpPage.Administer_Server: - { - AddHtml( 10, 125, 400, 20, Color( Center( "Server" ), LabelColor32 ), false, false ); - - AddButtonLabeled( 20, 150, GetButtonID( 3, 200 ), "Save" ); - - /*if ( !Core.Service ) - {*/ - AddButtonLabeled( 20, 180, GetButtonID( 3, 201 ), "Shutdown (With Save)" ); - AddButtonLabeled( 20, 200, GetButtonID( 3, 202 ), "Shutdown (Without Save)" ); + AddButtonLabeled(200, 350, GetButtonID(5, 25), "Delete Account"); - AddButtonLabeled( 20, 230, GetButtonID( 3, 203 ), "Shutdown & Restart (With Save)" ); - AddButtonLabeled( 20, 250, GetButtonID( 3, 204 ), "Shutdown & Restart (Without Save)" ); - /*} - else - { - AddLabel( 20, 215, LabelHue, "Shutdown/Restart not available." ); - }*/ - - AddHtml( 10, 295, 400, 20, Color( Center( "Broadcast" ), LabelColor32 ), false, false ); - - AddTextField( 20, 320, 380, 20, 0 ); - AddButtonLabeled( 20, 350, GetButtonID( 3, 210 ), "To Everyone" ); - AddButtonLabeled( 220, 350, GetButtonID( 3, 211 ), "To Staff" ); - - goto case AdminGumpPage.Administer; - } - case AdminGumpPage.Administer_Access_Lockdown: - { - AddHtml( 10, 125, 400, 20, Color( Center( "Server Lockdown" ), LabelColor32 ), false, false ); - - AddHtml( 20, 150, 380, 80, Color( "When enabled, only clients with an access level equal to or greater than the specified lockdown level may access the server. After setting a lockdown level, use the Purge Invalid Clients button to disconnect those clients without access.", LabelColor32 ), false, false ); - - AccessLevel level = AccountHandler.LockdownLevel; - bool isLockedDown = ( level > AccessLevel.Player ); - - AddSelectedButton( 20, 230, GetButtonID( 3, 500 ), "Not Locked Down", !isLockedDown ); - AddSelectedButton( 20, 260, GetButtonID( 3, 504 ), "Administrators", ( isLockedDown && level <= AccessLevel.Administrator ) ); - AddSelectedButton( 20, 280, GetButtonID( 3, 503 ), "Seers", ( isLockedDown && level <= AccessLevel.Seer ) ); - AddSelectedButton( 20, 300, GetButtonID( 3, 502 ), "Game Masters", ( isLockedDown && level <= AccessLevel.GameMaster ) ); - AddSelectedButton( 20, 320, GetButtonID( 3, 501 ), "Counselors", ( isLockedDown && level <= AccessLevel.Counselor ) ); - - AddButtonLabeled( 20, 350, GetButtonID( 3, 510 ), "Purge Invalid Clients" ); - - goto case AdminGumpPage.Administer; - } - case AdminGumpPage.Administer_Access: - { - AddHtml( 10, 125, 400, 20, Color( Center( "Access" ), LabelColor32 ), false, false ); - - AddHtml( 10, 155, 400, 20, Color( Center( "Connectivity" ), LabelColor32 ), false, false ); - - AddButtonLabeled( 20, 180, GetButtonID( 3, 300 ), "Kick" ); - AddButtonLabeled( 220, 180, GetButtonID( 3, 301 ), "Ban" ); + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.AccountDetails_Access: + { + if (!(state is Account a)) + break; + + AddHtml(10, 125, 400, 20, Color(Center("Access"), LabelColor32), false, false); + + AddPageButton(20, 150, GetButtonID(5, 14), "View client addresses", + AdminGumpPage.AccountDetails_Access_ClientIPs); + AddPageButton(20, 170, GetButtonID(5, 15), "Manage restrictions", + AdminGumpPage.AccountDetails_Access_Restrictions); + + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.AccountDetails_Access_ClientIPs: + { + if (!(state is Account a)) + break; - AddButtonLabeled( 20, 210, GetButtonID( 3, 302 ), "Firewall" ); - AddButtonLabeled( 220, 210, GetButtonID( 3, 303 ), "Lockdown" ); + if (m_List == null) + m_List = new ArrayList(a.LoginIPs); - AddHtml( 10, 245, 400, 20, Color( Center( "Staff" ), LabelColor32 ), false, false ); + AddHtml(10, 195, 400, 20, Color(Center("Client Addresses"), LabelColor32), false, false); - AddButtonLabeled( 20, 270, GetButtonID( 3, 310 ), "Make Player" ); - AddButtonLabeled( 20, 290, GetButtonID( 3, 311 ), "Make Counselor" ); - AddButtonLabeled( 20, 310, GetButtonID( 3, 312 ), "Make Game Master" ); - AddButtonLabeled( 20, 330, GetButtonID( 3, 313 ), "Make Seer" ); + AddButtonLabeled(227, 225, GetButtonID(5, 16), "View all shared accounts"); + AddButtonLabeled(227, 245, GetButtonID(5, 17), "Ban all shared accounts"); + AddButtonLabeled(227, 265, GetButtonID(5, 18), "Firewall all addresses"); + AddButtonLabeled(227, 285, GetButtonID(5, 36), "Clear all addresses"); - if ( from.AccessLevel > AccessLevel.Administrator ) - { - AddButtonLabeled( 220, 270, GetButtonID( 3, 314 ), "Make Administrator" ); - - if ( from.AccessLevel > AccessLevel.Developer ) - { - AddButtonLabeled( 220, 290, GetButtonID( 3, 315 ), "Make Developer" ); - - if ( from.AccessLevel >= AccessLevel.Owner ) - AddButtonLabeled( 220, 310, GetButtonID( 3, 316 ), "Make Owner" ); - } - } - - goto case AdminGumpPage.Administer; - } - case AdminGumpPage.Administer_Commands: - { - AddHtml( 10, 125, 400, 20, Color( Center( "Commands" ), LabelColor32 ), false, false ); - - AddButtonLabeled( 20, 150, GetButtonID( 3, 400 ), "Add" ); - AddButtonLabeled( 220, 150, GetButtonID( 3, 401 ), "Remove" ); - - AddButtonLabeled( 20, 170, GetButtonID( 3, 402 ), "Dupe" ); - AddButtonLabeled( 220, 170, GetButtonID( 3, 403 ), "Dupe in bag" ); - - AddButtonLabeled( 20, 200, GetButtonID( 3, 404 ), "Properties" ); - AddButtonLabeled( 220, 200, GetButtonID( 3, 405 ), "Skills" ); - - AddButtonLabeled( 20, 230, GetButtonID( 3, 406 ), "Mortal" ); - AddButtonLabeled( 220, 230, GetButtonID( 3, 407 ), "Immortal" ); - - AddButtonLabeled( 20, 250, GetButtonID( 3, 408 ), "Squelch" ); - AddButtonLabeled( 220, 250, GetButtonID( 3, 409 ), "Unsquelch" ); - - AddButtonLabeled( 20, 270, GetButtonID( 3, 410 ), "Freeze" ); - AddButtonLabeled( 220, 270, GetButtonID( 3, 411 ), "Unfreeze" ); - - AddButtonLabeled( 20, 290, GetButtonID( 3, 412 ), "Hide" ); - AddButtonLabeled( 220, 290, GetButtonID( 3, 413 ), "Unhide" ); - - AddButtonLabeled( 20, 310, GetButtonID( 3, 414 ), "Kill" ); - AddButtonLabeled( 220, 310, GetButtonID( 3, 415 ), "Resurrect" ); - - AddButtonLabeled( 20, 330, GetButtonID( 3, 416 ), "Move" ); - AddButtonLabeled( 220, 330, GetButtonID( 3, 417 ), "Wipe" ); - - AddButtonLabeled( 20, 350, GetButtonID( 3, 418 ), "Teleport" ); - AddButtonLabeled( 220, 350, GetButtonID( 3, 419 ), "Teleport (Multiple)" ); - - goto case AdminGumpPage.Administer; - } - case AdminGumpPage.Administer: - { - AddPageButton( 200, 20, GetButtonID( 3, 0 ), "World Building", AdminGumpPage.Administer_WorldBuilding ); - AddPageButton( 200, 40, GetButtonID( 3, 1 ), "Server", AdminGumpPage.Administer_Server ); - AddPageButton( 200, 60, GetButtonID( 3, 2 ), "Access", AdminGumpPage.Administer_Access, AdminGumpPage.Administer_Access_Lockdown ); - AddPageButton( 200, 80, GetButtonID( 3, 3 ), "Commands", AdminGumpPage.Administer_Commands ); - - break; - } - case AdminGumpPage.Clients: - { - if ( m_List == null ) - { - m_List = new ArrayList( NetState.Instances ); - m_List.Sort( NetStateComparer.Instance ); - } - - AddClientHeader(); - - AddLabelCropped( 12, 120, 81, 20, LabelHue, "Name" ); - AddLabelCropped( 95, 120, 81, 20, LabelHue, "Account" ); - AddLabelCropped( 178, 120, 81, 20, LabelHue, "Access Level" ); - AddLabelCropped( 273, 120,109, 20, LabelHue, "IP Address" ); - - if ( listPage > 0 ) - AddButton( 375, 122, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 375, 122, 0x25EA ); - - if ( (listPage + 1) * 12 < m_List.Count ) - AddButton( 392, 122, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 392, 122, 0x25E6 ); - - if ( m_List.Count == 0 ) - AddLabel( 12, 140, LabelHue, "There are no clients to display." ); - - for ( int i = 0, index = (listPage * 12); i < 12 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - if ( !(m_List[index] is NetState ns) ) - continue; - - Mobile m = ns.Mobile; - Account a = ns.Account as Account; - int offset = 140 + (i * 20); - - if ( m == null ) - { - AddLabelCropped(12, offset, 81, 20, LabelHue, - RemoteAdmin.AdminNetwork.IsAuth(ns) ? "(remote admin)" : "(logging in)"); - } - else - { - AddLabelCropped( 12, offset, 81, 20, GetHueFor( m ), m.Name ); - } - AddLabelCropped( 95, offset, 81, 20, LabelHue, a == null ? "(no account)" : a.Username ); - AddLabelCropped( 178, offset, 81, 20, LabelHue, m == null ? (a != null ? FormatAccessLevel( a.AccessLevel ) : "") : FormatAccessLevel( m.AccessLevel ) ); - AddLabelCropped( 273, offset,109, 20, LabelHue, ns.ToString() ); - - if ( a != null || m != null ) - AddButton( 380, offset - 1, 0xFA5, 0xFA7, GetButtonID( 4, index + 2 ), GumpButtonType.Reply, 0 ); - } - - break; - } - case AdminGumpPage.ClientInfo: - { - if ( !(state is Mobile m) ) - break; - - AddClientHeader(); - - AddHtml( 10, 125, 400, 20, Color( Center( "Information" ), LabelColor32 ), false, false ); - - int y = 146; - - AddLabel( 20, y, LabelHue, "Name:" ); - AddLabel( 200, y, GetHueFor( m ), m.Name ); - y += 20; - - Account a = m.Account as Account; - - AddLabel( 20, y, LabelHue, "Account:" ); - AddLabel( 200, y, (a != null && a.Banned) ? RedHue : LabelHue, a == null ? "(no account)" : a.Username ); - AddButton( 380, y, 0xFA5, 0xFA7, GetButtonID( 7, 14 ), GumpButtonType.Reply, 0 ); - y += 20; - - NetState ns = m.NetState; - - if ( ns == null ) - { - AddLabel( 20, y, LabelHue, "Address:" ); - AddLabel( 200, y, RedHue, "Offline" ); - y += 20; - - AddLabel( 20, y, LabelHue, "Location:" ); - AddLabel( 200, y, LabelHue, $"{m.Location} [{m.Map}]"); - y += 44; - } - else - { - AddLabel( 20, y, LabelHue, "Address:" ); - AddLabel( 200, y, GreenHue, ns.ToString() ); - y += 20; - - ClientVersion v = ns.Version; - - AddLabel( 20, y, LabelHue, "Version:" ); - AddLabel( 200, y, LabelHue, v == null ? "(null)" : v.ToString() ); - y += 20; - - AddLabel( 20, y, LabelHue, "Location:" ); - AddLabel( 200, y, LabelHue, $"{m.Location} [{m.Map}]"); - y += 24; - } - - AddButtonLabeled( 20, y, GetButtonID( 7, 0 ), "Go to" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 1 ), "Get" ); - y += 20; - - AddButtonLabeled( 20, y, GetButtonID( 7, 2 ), "Kick" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 3 ), "Ban" ); - y += 20; - - AddButtonLabeled( 20, y, GetButtonID( 7, 4 ), "Properties" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 5 ), "Skills" ); - y += 20; - - AddButtonLabeled( 20, y, GetButtonID( 7, 6 ), "Mortal" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 7 ), "Immortal" ); - y += 20; - - AddButtonLabeled( 20, y, GetButtonID( 7, 8 ), "Squelch" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 9 ), "Unsquelch" ); - y += 20; - - /*AddButtonLabeled( 20, y, GetButtonID( 7, 10 ), "Hide" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 11 ), "Unhide" ); - y += 20;*/ - - AddButtonLabeled( 20, y, GetButtonID( 7, 12 ), "Kill" ); - AddButtonLabeled( 200, y, GetButtonID( 7, 13 ), "Resurrect" ); - y += 20; - - break; - } - case AdminGumpPage.Accounts_Shared: - { - if ( m_List == null ) - m_List = GetAllSharedAccounts(); - - AddLabelCropped( 12, 120, 60, 20, LabelHue, "Count" ); - AddLabelCropped( 72, 120, 120, 20, LabelHue, "Address" ); - AddLabelCropped( 192, 120, 180, 20, LabelHue, "Accounts" ); - - if ( listPage > 0 ) - AddButton( 375, 122, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 375, 122, 0x25EA ); - - if ( (listPage + 1) * 12 < m_List.Count ) - AddButton( 392, 122, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 392, 122, 0x25E6 ); - - if ( m_List.Count == 0 ) - AddLabel( 12, 140, LabelHue, "There are no accounts to display." ); - - StringBuilder sb = new StringBuilder(); - - for ( int i = 0, index = (listPage * 12); i < 12 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - DictionaryEntry de = (DictionaryEntry)m_List[index]; - - IPAddress ipAddr = (IPAddress)de.Key; - ArrayList accts = (ArrayList)de.Value; - - int offset = 140 + (i * 20); - - AddLabelCropped( 12, offset, 60, 20, LabelHue, accts.Count.ToString() ); - AddLabelCropped( 72, offset, 120, 20, LabelHue, ipAddr.ToString() ); - - if ( sb.Length > 0 ) - sb.Length = 0; - - for ( int j = 0; j < accts.Count; ++j ) - { - if ( j > 0 ) - sb.Append( ", " ); - - if ( j < 4 ) - { - Account acct = (Account)accts[j]; - - sb.Append( acct.Username ); - } - else - { - sb.Append( "..." ); - break; - } - } - - AddLabelCropped( 192, offset, 180, 20, LabelHue, sb.ToString() ); - - AddButton( 380, offset - 1, 0xFA5, 0xFA7, GetButtonID( 5, index + 56 ), GumpButtonType.Reply, 0 ); - } - - break; - } - case AdminGumpPage.Accounts: - { - if ( m_List == null ) - { - m_List = new ArrayList(); // new ArrayList( (ICollection)Accounts.GetAccounts() ); - // m_List.Sort( AccountComparer.Instance ); - } - - ArrayList rads = ( state as ArrayList ); - - AddAccountHeader(); - - if ( rads == null ) - AddLabelCropped( 12, 120, 120, 20, LabelHue, "Name" ); - else - AddLabelCropped( 32, 120, 100, 20, LabelHue, "Name" ); - - AddLabelCropped( 132, 120, 120, 20, LabelHue, "Access Level" ); - AddLabelCropped( 252, 120, 120, 20, LabelHue, "Status" ); - - if ( listPage > 0 ) - AddButton( 375, 122, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 375, 122, 0x25EA ); - - if ( (listPage + 1) * 12 < m_List.Count ) - AddButton( 392, 122, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 392, 122, 0x25E6 ); - - if ( m_List.Count == 0 ) - AddLabel( 12, 140, LabelHue, "There are no accounts to display." ); - - if ( rads != null && notice == null ) - { - AddButtonLabeled( 10, 390, GetButtonID( 5, 27 ), "Ban marked" ); - AddButtonLabeled( 10, 410, GetButtonID( 5, 28 ), "Delete marked" ); - - AddButtonLabeled( 210, 390, GetButtonID( 5, 29 ), "Mark all" ); - AddButtonLabeled( 210, 410, GetButtonID( 5, 35 ), "Unmark house owners" ); - } - - for ( int i = 0, index = (listPage * 12); i < 12 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - if ( !(m_List[index] is Account a) ) - continue; - - int offset = 140 + (i * 20); - - GetAccountInfo( a, out var accessLevel, out var online ); - - if ( rads == null ) - { - AddLabelCropped( 12, offset, 120, 20, LabelHue, a.Username ); - } - else - { - AddCheck( 10, offset, 0xD2, 0xD3, rads.Contains( a ), index ); - AddLabelCropped( 32, offset, 100, 20, LabelHue, a.Username ); - } - - AddLabelCropped( 132, offset, 120, 20, LabelHue, FormatAccessLevel( accessLevel ) ); - - if ( online ) - AddLabelCropped( 252, offset, 120, 20, GreenHue, "Online" ); - else if ( a.Banned ) - AddLabelCropped( 252, offset, 120, 20, RedHue, "Banned" ); - else - AddLabelCropped( 252, offset, 120, 20, RedHue, "Offline" ); - - AddButton( 380, offset - 1, 0xFA5, 0xFA7, GetButtonID( 5, index + 56 ), GumpButtonType.Reply, 0 ); - } - - break; - } - case AdminGumpPage.AccountDetails: - { - AddPageButton( 190, 10, GetButtonID( 5, 0 ), "Information", AdminGumpPage.AccountDetails_Information, AdminGumpPage.AccountDetails_ChangeAccess, AdminGumpPage.AccountDetails_ChangePassword ); - AddPageButton( 190, 30, GetButtonID( 5, 1 ), "Characters", AdminGumpPage.AccountDetails_Characters ); - AddPageButton( 190, 50, GetButtonID( 5, 13 ), "Access", AdminGumpPage.AccountDetails_Access, AdminGumpPage.AccountDetails_Access_ClientIPs, AdminGumpPage.AccountDetails_Access_Restrictions ); - AddPageButton( 190, 70, GetButtonID( 5, 2 ), "Comments", AdminGumpPage.AccountDetails_Comments ); - AddPageButton( 190, 90, GetButtonID( 5, 3 ), "Tags", AdminGumpPage.AccountDetails_Tags ); - break; - } - case AdminGumpPage.AccountDetails_ChangePassword: - { - if ( !(state is Account a) ) - break; - - AddHtml( 10, 125, 400, 20, Color( Center( "Change Password" ), LabelColor32 ), false, false ); - - AddLabel( 20, 150, LabelHue, "Username:" ); - AddLabel( 200, 150, LabelHue, a.Username ); - - AddLabel( 20, 180, LabelHue, "Password:" ); - AddTextField( 200, 180, 160, 20, 0 ); - - AddLabel( 20, 210, LabelHue, "Confirm:" ); - AddTextField( 200, 210, 160, 20, 1 ); - - AddButtonLabeled( 20, 240, GetButtonID( 5, 12 ), "Submit Change" ); - - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.AccountDetails_ChangeAccess: - { - if ( !(state is Account a) ) - break; - - AddHtml( 10, 125, 400, 20, Color( Center( "Change Access Level" ), LabelColor32 ), false, false ); - - AddLabel( 20, 150, LabelHue, "Username:" ); - AddLabel( 200, 150, LabelHue, a.Username ); - - AddLabel( 20, 170, LabelHue, "Current Level:" ); - AddLabel( 200, 170, LabelHue, FormatAccessLevel( a.AccessLevel ) ); - - AddButtonLabeled( 20, 200, GetButtonID( 5, 20 ), "Player" ); - AddButtonLabeled( 20, 220, GetButtonID( 5, 21 ), "Counselor" ); - AddButtonLabeled( 20, 240, GetButtonID( 5, 22 ), "Game Master" ); - AddButtonLabeled( 20, 260, GetButtonID( 5, 23 ), "Seer" ); - - if ( from.AccessLevel > AccessLevel.Administrator ) - { - AddButtonLabeled( 20, 280, GetButtonID( 5, 24 ), "Administrator" ); - - if ( from.AccessLevel > AccessLevel.Developer ) - { - AddButtonLabeled( 20, 300, GetButtonID( 5, 33 ), "Developer" ); - - if ( from.AccessLevel >= AccessLevel.Owner ) - AddButtonLabeled( 20, 320, GetButtonID( 5, 34 ), "Owner" ); - } - } - - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.AccountDetails_Information: - { - if ( !(state is Account a) ) - break; - - int charCount = 0; - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] != null ) - ++charCount; - } - - AddHtml( 10, 125, 400, 20, Color( Center( "Information" ), LabelColor32 ), false, false ); - - AddLabel( 20, 150, LabelHue, "Username:" ); - AddLabel( 200, 150, LabelHue, a.Username ); - - AddLabel( 20, 170, LabelHue, "Access Level:" ); - AddLabel( 200, 170, LabelHue, FormatAccessLevel( a.AccessLevel ) ); - - AddLabel( 20, 190, LabelHue, "Status:" ); - AddLabel( 200, 190, a.Banned ? RedHue : GreenHue, a.Banned ? "Banned" : "Active" ); - - if ( a.Banned && a.GetBanTags( out var banTime, out var banDuration ) ) - { - if ( banDuration == TimeSpan.MaxValue ) - { - AddLabel( 250, 190, LabelHue, "(Infinite)" ); - } - else if ( banDuration == TimeSpan.Zero ) - { - AddLabel( 250, 190, LabelHue, "(Zero)" ); - } - else - { - TimeSpan remaining = (DateTime.UtcNow - banTime); - - if ( remaining < TimeSpan.Zero ) - remaining = TimeSpan.Zero; - else if ( remaining > banDuration ) - remaining = banDuration; - - double remMinutes = remaining.TotalMinutes; - double totMinutes = banDuration.TotalMinutes; - - double perc = remMinutes / totMinutes; + AddHtml(225, 315, 180, 80, Color("List of IP addresses which have accessed this account.", LabelColor32), + false, false); - AddLabel( 250, 190, LabelHue, $"{FormatTimeSpan(banDuration)} [{perc * 100:F0}%]"); - } - } - else if ( a.Banned ) - { - AddLabel( 250, 190, LabelHue, "(Unspecified)" ); - } + AddImageTiled(15, 219, 206, 156, 0xBBC); + AddBlackAlpha(16, 220, 204, 154); - AddLabel( 20, 210, LabelHue, "Created:" ); - AddLabel( 200, 210, LabelHue, a.Created.ToString() ); + AddHtml(18, 221, 114, 20, Color("IP Address", LabelColor32), false, false); - AddLabel( 20, 230, LabelHue, "Last Login:" ); - AddLabel( 200, 230, LabelHue, a.LastLogin.ToString() ); + if (listPage > 0) + AddButton(184, 223, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(184, 223, 0x25EA); - AddLabel( 20, 250, LabelHue, "Character Count:" ); - AddLabel( 200, 250, LabelHue, charCount.ToString() ); + if ((listPage + 1) * 6 < m_List.Count) + AddButton(201, 223, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(201, 223, 0x25E6); - AddLabel( 20, 270, LabelHue, "Comment Count:" ); - AddLabel( 200, 270, LabelHue, a.Comments.Count.ToString() ); + if (m_List.Count == 0) + AddHtml(18, 243, 200, 60, Color("This account has not yet been accessed.", LabelColor32), false, + false); - AddLabel( 20, 290, LabelHue, "Tag Count:" ); - AddLabel( 200, 290, LabelHue, a.Tags.Count.ToString() ); + for (int i = 0, index = listPage * 6; i < 6 && index >= 0 && index < m_List.Count; ++i, ++index) + { + AddHtml(18, 243 + i * 22, 114, 20, Color(m_List[index].ToString(), LabelColor32), false, false); + AddButton(130, 242 + i * 22, 0xFA2, 0xFA4, GetButtonID(8, index), GumpButtonType.Reply, 0); + AddButton(160, 242 + i * 22, 0xFA8, 0xFAA, GetButtonID(9, index), GumpButtonType.Reply, 0); + AddButton(190, 242 + i * 22, 0xFB1, 0xFB3, GetButtonID(10, index), GumpButtonType.Reply, 0); + } - AddButtonLabeled( 20, 320, GetButtonID( 5, 8 ), "Change Password" ); - AddButtonLabeled( 200, 320, GetButtonID( 5, 9 ), "Change Access Level" ); + goto case AdminGumpPage.AccountDetails_Access; + } + case AdminGumpPage.AccountDetails_Access_Restrictions: + { + if (!(state is Account a)) + break; - if ( !a.Banned ) - AddButtonLabeled( 20, 350, GetButtonID( 5, 10 ), "Ban Account" ); - else - AddButtonLabeled( 20, 350, GetButtonID( 5, 11 ), "Unban Account" ); + if (m_List == null) + m_List = new ArrayList(a.IPRestrictions); - AddButtonLabeled( 200, 350, GetButtonID( 5, 25 ), "Delete Account" ); + AddHtml(10, 195, 400, 20, Color(Center("Address Restrictions"), LabelColor32), false, false); - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.AccountDetails_Access: - { - if ( !(state is Account a) ) - break; + AddTextField(227, 225, 120, 20, 0); - AddHtml( 10, 125, 400, 20, Color( Center( "Access" ), LabelColor32 ), false, false ); + AddButtonLabeled(352, 225, GetButtonID(5, 19), "Add"); - AddPageButton( 20, 150, GetButtonID( 5, 14 ), "View client addresses", AdminGumpPage.AccountDetails_Access_ClientIPs ); - AddPageButton( 20, 170, GetButtonID( 5, 15 ), "Manage restrictions", AdminGumpPage.AccountDetails_Access_Restrictions ); + AddHtml(225, 255, 180, 120, + Color( + "Any clients connecting from an address not in this list will be rejected. Or, if the list is empty, any client may connect.", + LabelColor32), false, false); - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.AccountDetails_Access_ClientIPs: - { - if ( !(state is Account a) ) - break; + AddImageTiled(15, 219, 206, 156, 0xBBC); + AddBlackAlpha(16, 220, 204, 154); - if ( m_List == null ) - m_List = new ArrayList( a.LoginIPs ); + AddHtml(18, 221, 114, 20, Color("IP Address", LabelColor32), false, false); - AddHtml( 10, 195, 400, 20, Color( Center( "Client Addresses" ), LabelColor32 ), false, false ); + if (listPage > 0) + AddButton(184, 223, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(184, 223, 0x25EA); - AddButtonLabeled( 227, 225, GetButtonID( 5, 16 ), "View all shared accounts" ); - AddButtonLabeled( 227, 245, GetButtonID( 5, 17 ), "Ban all shared accounts" ); - AddButtonLabeled( 227, 265, GetButtonID( 5, 18 ), "Firewall all addresses" ); - AddButtonLabeled( 227, 285, GetButtonID( 5, 36 ), "Clear all addresses" ); + if ((listPage + 1) * 6 < m_List.Count) + AddButton(201, 223, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(201, 223, 0x25E6); - AddHtml( 225, 315, 180, 80, Color( "List of IP addresses which have accessed this account.", LabelColor32 ), false, false ); + if (m_List.Count == 0) + AddHtml(18, 243, 200, 60, Color("There are no addresses in this list.", LabelColor32), false, false); - AddImageTiled( 15, 219, 206, 156, 0xBBC ); - AddBlackAlpha( 16, 220, 204, 154 ); + for (int i = 0, index = listPage * 6; i < 6 && index >= 0 && index < m_List.Count; ++i, ++index) + { + AddHtml(18, 243 + i * 22, 114, 20, Color(m_List[index].ToString(), LabelColor32), false, false); + AddButton(190, 242 + i * 22, 0xFB1, 0xFB3, GetButtonID(8, index), GumpButtonType.Reply, 0); + } - AddHtml( 18, 221, 114, 20, Color( "IP Address", LabelColor32 ), false, false ); + goto case AdminGumpPage.AccountDetails_Access; + } + case AdminGumpPage.AccountDetails_Characters: + { + if (!(state is Account a)) + break; - if ( listPage > 0 ) - AddButton( 184, 223, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 184, 223, 0x25EA ); + AddHtml(10, 125, 400, 20, Color(Center("Characters"), LabelColor32), false, false); - if ( (listPage + 1) * 6 < m_List.Count ) - AddButton( 201, 223, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 201, 223, 0x25E6 ); + AddLabelCropped(12, 150, 120, 20, LabelHue, "Name"); + AddLabelCropped(132, 150, 120, 20, LabelHue, "Access Level"); + AddLabelCropped(252, 150, 120, 20, LabelHue, "Status"); - if ( m_List.Count == 0 ) - AddHtml( 18, 243, 200, 60, Color( "This account has not yet been accessed.", LabelColor32 ), false, false ); + int index = 0; - for ( int i = 0, index = (listPage * 6); i < 6 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - AddHtml( 18, 243 + (i * 22), 114, 20, Color( m_List[index].ToString(), LabelColor32 ), false, false ); - AddButton( 130, 242 + (i * 22), 0xFA2, 0xFA4, GetButtonID( 8, index ), GumpButtonType.Reply, 0 ); - AddButton( 160, 242 + (i * 22), 0xFA8, 0xFAA, GetButtonID( 9, index ), GumpButtonType.Reply, 0 ); - AddButton( 190, 242 + (i * 22), 0xFB1, 0xFB3, GetButtonID( 10, index ), GumpButtonType.Reply, 0 ); - } + for (int i = 0; i < a.Length; ++i) + { + Mobile m = a[i]; - goto case AdminGumpPage.AccountDetails_Access; - } - case AdminGumpPage.AccountDetails_Access_Restrictions: - { - if ( !(state is Account a) ) - break; + if (m == null) + continue; - if ( m_List == null ) - m_List = new ArrayList( a.IPRestrictions ); + int offset = 170 + index * 20; - AddHtml( 10, 195, 400, 20, Color( Center( "Address Restrictions" ), LabelColor32 ), false, false ); + AddLabelCropped(12, offset, 120, 20, GetHueFor(m), m.Name); + AddLabelCropped(132, offset, 120, 20, LabelHue, FormatAccessLevel(m.AccessLevel)); - AddTextField( 227, 225, 120, 20, 0 ); + if (m.NetState != null) + AddLabelCropped(252, offset, 120, 20, GreenHue, "Online"); + else + AddLabelCropped(252, offset, 120, 20, RedHue, "Offline"); - AddButtonLabeled( 352, 225, GetButtonID( 5, 19 ), "Add" ); + AddButton(380, offset - 1, 0xFA5, 0xFA7, GetButtonID(5, i + 50), GumpButtonType.Reply, 0); - AddHtml( 225, 255, 180, 120, Color( "Any clients connecting from an address not in this list will be rejected. Or, if the list is empty, any client may connect.", LabelColor32 ), false, false ); + ++index; + } - AddImageTiled( 15, 219, 206, 156, 0xBBC ); - AddBlackAlpha( 16, 220, 204, 154 ); + if (index == 0) + AddLabel(12, 170, LabelHue, "The character list is empty."); - AddHtml( 18, 221, 114, 20, Color( "IP Address", LabelColor32 ), false, false ); + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.AccountDetails_Comments: + { + if (!(state is Account a)) + break; - if ( listPage > 0 ) - AddButton( 184, 223, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 184, 223, 0x25EA ); + AddHtml(10, 125, 400, 20, Color(Center("Comments"), LabelColor32), false, false); - if ( (listPage + 1) * 6 < m_List.Count ) - AddButton( 201, 223, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 201, 223, 0x25E6 ); + AddButtonLabeled(20, 150, GetButtonID(5, 4), "Add Comment"); - if ( m_List.Count == 0 ) - AddHtml( 18, 243, 200, 60, Color( "There are no addresses in this list.", LabelColor32 ), false, false ); + StringBuilder sb = new StringBuilder(); - for ( int i = 0, index = (listPage * 6); i < 6 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - AddHtml( 18, 243 + (i * 22), 114, 20, Color( m_List[index].ToString(), LabelColor32 ), false, false ); - AddButton( 190, 242 + (i * 22), 0xFB1, 0xFB3, GetButtonID( 8, index ), GumpButtonType.Reply, 0 ); - } + if (a.Comments.Count == 0) + sb.Append("There are no comments for this account."); - goto case AdminGumpPage.AccountDetails_Access; - } - case AdminGumpPage.AccountDetails_Characters: - { - if ( !(state is Account a) ) - break; + for (int i = 0; i < a.Comments.Count; ++i) + { + if (i > 0) + sb.Append("

"); - AddHtml( 10, 125, 400, 20, Color( Center( "Characters" ), LabelColor32 ), false, false ); + AccountComment c = a.Comments[i]; - AddLabelCropped( 12, 150, 120, 20, LabelHue, "Name" ); - AddLabelCropped( 132, 150, 120, 20, LabelHue, "Access Level" ); - AddLabelCropped( 252, 150, 120, 20, LabelHue, "Status" ); + sb.AppendFormat("[{0} on {1}]
{2}", c.AddedBy, c.LastModified, c.Content); + } - int index = 0; + AddHtml(20, 180, 380, 190, sb.ToString(), true, true); - for ( int i = 0; i < a.Length; ++i ) - { - Mobile m = a[i]; + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.AccountDetails_Tags: + { + if (!(state is Account a)) + break; - if ( m == null ) - continue; + AddHtml(10, 125, 400, 20, Color(Center("Tags"), LabelColor32), false, false); - int offset = 170 + (index * 20); + AddButtonLabeled(20, 150, GetButtonID(5, 5), "Add Tag"); - AddLabelCropped( 12, offset, 120, 20, GetHueFor( m ), m.Name ); - AddLabelCropped( 132, offset, 120, 20, LabelHue, FormatAccessLevel( m.AccessLevel ) ); + StringBuilder sb = new StringBuilder(); - if ( m.NetState != null ) - AddLabelCropped( 252, offset, 120, 20, GreenHue, "Online" ); - else - AddLabelCropped( 252, offset, 120, 20, RedHue, "Offline" ); + if (a.Tags.Count == 0) + sb.Append("There are no tags for this account."); - AddButton( 380, offset - 1, 0xFA5, 0xFA7, GetButtonID( 5, i + 50 ), GumpButtonType.Reply, 0 ); + for (int i = 0; i < a.Tags.Count; ++i) + { + if (i > 0) + sb.Append("
"); - ++index; - } + AccountTag tag = a.Tags[i]; - if ( index == 0 ) - AddLabel( 12, 170, LabelHue, "The character list is empty." ); + sb.AppendFormat("{0} = {1}", tag.Name, tag.Value); + } - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.AccountDetails_Comments: - { - if ( !(state is Account a) ) - break; + AddHtml(20, 180, 380, 190, sb.ToString(), true, true); - AddHtml( 10, 125, 400, 20, Color( Center( "Comments" ), LabelColor32 ), false, false ); + goto case AdminGumpPage.AccountDetails; + } + case AdminGumpPage.Firewall: + { + AddFirewallHeader(); - AddButtonLabeled( 20, 150, GetButtonID( 5, 4 ), "Add Comment" ); + if (m_List == null) + m_List = new ArrayList(Firewall.List); - StringBuilder sb = new StringBuilder(); + AddLabelCropped(12, 120, 358, 20, LabelHue, "IP Address"); - if ( a.Comments.Count == 0 ) - sb.Append( "There are no comments for this account." ); + if (listPage > 0) + AddButton(375, 122, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(375, 122, 0x25EA); - for ( int i = 0; i < a.Comments.Count; ++i ) - { - if ( i > 0 ) - sb.Append( "

" ); + if ((listPage + 1) * 12 < m_List.Count) + AddButton(392, 122, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(392, 122, 0x25E6); - AccountComment c = a.Comments[i]; + if (m_List.Count == 0) + AddLabel(12, 140, LabelHue, "The firewall list is empty."); - sb.AppendFormat( "[{0} on {1}]
{2}", c.AddedBy, c.LastModified, c.Content ); - } + for (int i = 0, index = listPage * 12; i < 12 && index >= 0 && index < m_List.Count; ++i, ++index) + { + object obj = m_List[index]; - AddHtml( 20, 180, 380, 190, sb.ToString(), true, true ); + if (!(obj is Firewall.IFirewallEntry)) + break; - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.AccountDetails_Tags: - { - if ( !(state is Account a) ) - break; + int offset = 140 + i * 20; - AddHtml( 10, 125, 400, 20, Color( Center( "Tags" ), LabelColor32 ), false, false ); + AddLabelCropped(12, offset, 358, 20, LabelHue, obj.ToString()); + AddButton(380, offset - 1, 0xFA5, 0xFA7, GetButtonID(6, index + 4), GumpButtonType.Reply, 0); + } - AddButtonLabeled( 20, 150, GetButtonID( 5, 5 ), "Add Tag" ); + break; + } + case AdminGumpPage.FirewallInfo: + { + AddFirewallHeader(); - StringBuilder sb = new StringBuilder(); + if (!(state is Firewall.IFirewallEntry)) + break; - if ( a.Tags.Count == 0 ) - sb.Append( "There are no tags for this account." ); + AddHtml(10, 125, 400, 20, Color(Center(state.ToString()), LabelColor32), false, false); - for ( int i = 0; i < a.Tags.Count; ++i ) - { - if ( i > 0 ) - sb.Append( "
" ); + AddButtonLabeled(20, 150, GetButtonID(6, 3), "Remove"); - AccountTag tag = a.Tags[i]; + AddHtml(10, 175, 400, 20, Color(Center("Potentially Affected Accounts"), LabelColor32), false, false); - sb.AppendFormat( "{0} = {1}", tag.Name, tag.Value ); - } + if (m_List == null) + { + m_List = new ArrayList(); - AddHtml( 20, 180, 380, 190, sb.ToString(), true, true ); + foreach (IAccount ia in Accounts.GetAccounts()) + { + if (!(ia is Account acct)) + continue; - goto case AdminGumpPage.AccountDetails; - } - case AdminGumpPage.Firewall: - { - AddFirewallHeader(); + IPAddress[] loginList = acct.LoginIPs; - if ( m_List == null ) - m_List = new ArrayList( Firewall.List ); + bool contains = false; - AddLabelCropped( 12, 120, 358, 20, LabelHue, "IP Address" ); + for (int i = 0; !contains && i < loginList.Length; ++i) + if (((Firewall.IFirewallEntry)state).IsBlocked(loginList[i])) + { + m_List.Add(acct); + break; + } + } - if ( listPage > 0 ) - AddButton( 375, 122, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 375, 122, 0x25EA ); + m_List.Sort(AccountComparer.Instance); + } - if ( (listPage + 1) * 12 < m_List.Count ) - AddButton( 392, 122, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 392, 122, 0x25E6 ); + if (listPage > 0) + AddButton(375, 177, 0x15E3, 0x15E7, GetButtonID(1, 0), GumpButtonType.Reply, 0); + else + AddImage(375, 177, 0x25EA); - if ( m_List.Count == 0 ) - AddLabel( 12, 140, LabelHue, "The firewall list is empty." ); + if ((listPage + 1) * 12 < m_List.Count) + AddButton(392, 177, 0x15E1, 0x15E5, GetButtonID(1, 1), GumpButtonType.Reply, 0); + else + AddImage(392, 177, 0x25E6); - for ( int i = 0, index = (listPage * 12); i < 12 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - object obj = m_List[index]; + if (m_List.Count == 0) + AddLabelCropped(12, 200, 398, 20, LabelHue, "No accounts found."); - if ( !(obj is Firewall.IFirewallEntry ) ) - break; + for (int i = 0, index = listPage * 9; i < 9 && index >= 0 && index < m_List.Count; ++i, ++index) + { + Account a = m_List[index] as Account; - int offset = 140 + (i * 20); + if (a == null) + continue; - AddLabelCropped( 12, offset, 358, 20, LabelHue, obj.ToString() ); - AddButton( 380, offset - 1, 0xFA5, 0xFA7, GetButtonID( 6, index + 4 ), GumpButtonType.Reply, 0 ); - } + int offset = 200 + i * 20; - break; - } - case AdminGumpPage.FirewallInfo: - { - AddFirewallHeader(); + GetAccountInfo(a, out AccessLevel accessLevel, out bool online); - if ( !(state is Firewall.IFirewallEntry) ) - break; - - AddHtml( 10, 125, 400, 20, Color( Center( state.ToString() ), LabelColor32 ), false, false ); - - AddButtonLabeled( 20, 150, GetButtonID( 6, 3 ), "Remove" ); - - AddHtml( 10, 175, 400, 20, Color( Center( "Potentially Affected Accounts" ), LabelColor32 ), false, false ); - - if ( m_List == null ) - { - m_List = new ArrayList(); - - foreach ( IAccount ia in Accounts.GetAccounts() ) - { - if (!(ia is Account acct)) - continue; - - IPAddress[] loginList = acct.LoginIPs; - - bool contains = false; - - for( int i = 0; !contains && i < loginList.Length; ++i ) - { - if ( ((Firewall.IFirewallEntry)state).IsBlocked( loginList[i] ) ) - { - m_List.Add( acct ); - break; - } - } - } - - m_List.Sort( AccountComparer.Instance ); - } - - if ( listPage > 0 ) - AddButton( 375, 177, 0x15E3, 0x15E7, GetButtonID( 1, 0 ), GumpButtonType.Reply, 0 ); - else - AddImage( 375, 177, 0x25EA ); - - if ( (listPage + 1) * 12 < m_List.Count ) - AddButton( 392, 177, 0x15E1, 0x15E5, GetButtonID( 1, 1 ), GumpButtonType.Reply, 0 ); - else - AddImage( 392, 177, 0x25E6 ); - - if ( m_List.Count == 0 ) - AddLabelCropped( 12, 200, 398, 20, LabelHue, "No accounts found." ); - - for ( int i = 0, index = (listPage * 9); i < 9 && index >= 0 && index < m_List.Count; ++i, ++index ) - { - Account a = m_List[index] as Account; - - if ( a == null ) - continue; - - int offset = 200 + (i * 20); - - GetAccountInfo( a, out var accessLevel, out var online ); - - AddLabelCropped( 12, offset, 120, 20, LabelHue, a.Username ); - AddLabelCropped( 132, offset, 120, 20, LabelHue, FormatAccessLevel( accessLevel ) ); - - if ( online ) - AddLabelCropped( 252, offset, 120, 20, GreenHue, "Online" ); - else if ( a.Banned ) - AddLabelCropped( 252, offset, 120, 20, RedHue, "Banned" ); - else - AddLabelCropped( 252, offset, 120, 20, RedHue, "Offline" ); - - AddButton( 380, offset - 1, 0xFA5, 0xFA7, GetButtonID( 5, index + 56 ), GumpButtonType.Reply, 0 ); - } - - break; - } - } - } - - public void AddTextField( int x, int y, int width, int height, int index ) - { - AddBackground( x - 2, y - 2, width + 4, height + 4, 0x2486 ); - AddTextEntry( x + 2, y + 2, width - 4, height - 4, 0, index, "" ); - } - - public void AddClientHeader() - { - AddTextField( 200, 20, 200, 20, 0 ); - AddButtonLabeled( 200, 50, GetButtonID( 4, 0 ), "Search For Name" ); - AddButtonLabeled( 200, 80, GetButtonID( 4, 1 ), "Search For IP Address" ); - } - - public void AddAccountHeader() - { - AddPage( 1 ); - - AddLabel( 200, 20, LabelHue, "Name:" ); - AddTextField( 250, 20, 150, 20, 0 ); - - AddLabel( 200, 50, LabelHue, "Pass:" ); - AddTextField( 250, 50, 150, 20, 1 ); - - AddButtonLabeled( 200, 80, GetButtonID( 5, 6 ), "Add" ); - AddButtonLabeled( 290, 80, GetButtonID( 5, 7 ), "Search" ); - - AddButton( 384, 84, 0x15E1, 0x15E5, 0, GumpButtonType.Page, 2 ); - - AddPage( 2 ); - - AddButtonLabeled( 200, 20, GetButtonID( 5, 31 ), "View All: Inactive" ); - AddButtonLabeled( 200, 40, GetButtonID( 5, 32 ), "View All: Banned" ); - AddButtonLabeled( 200, 60, GetButtonID( 5, 26 ), "View All: Shared" ); - AddButtonLabeled( 200, 80, GetButtonID( 5, 30 ), "View All: Empty" ); - - AddButton( 384, 84, 0x15E1, 0x15E5, 0, GumpButtonType.Page, 1 ); - - AddPage( 0 ); - } - - public void AddFirewallHeader() - { - AddTextField( 200, 20, 200, 20, 0 ); - AddButtonLabeled( 320, 50, GetButtonID( 6, 0 ), "Search" ); - AddButtonLabeled( 200, 50, GetButtonID( 6, 1 ), "Add (Input)" ); - AddButtonLabeled( 200, 80, GetButtonID( 6, 2 ), "Add (Target)" ); - } - - private static ArrayList GetAllSharedAccounts() - { - Hashtable table = new Hashtable(); - ArrayList list; - - foreach ( Account acct in Accounts.GetAccounts() ) - { - IPAddress[] theirAddresses = acct.LoginIPs; - - for ( int i = 0; i < theirAddresses.Length; ++i ) - { - list = (ArrayList)table[theirAddresses[i]]; - - if ( list == null ) - table[theirAddresses[i]] = list = new ArrayList(); - - list.Add( acct ); - } - } - - list = new ArrayList( table ); - - for ( int i = 0; i < list.Count; ++i ) - { - DictionaryEntry de = (DictionaryEntry)list[i]; - ArrayList accts = (ArrayList)de.Value; - - if ( accts.Count == 1 ) - list.RemoveAt( i-- ); - else - accts.Sort( AccountComparer.Instance ); - } - - list.Sort( SharedAccountComparer.Instance ); - - return list; - } - - private class SharedAccountComparer : IComparer - { - public static readonly IComparer Instance = new SharedAccountComparer(); - - public SharedAccountComparer() - { - } - - public int Compare( object x, object y ) - { - DictionaryEntry a = (DictionaryEntry)x; - DictionaryEntry b = (DictionaryEntry)y; - - ArrayList aList = (ArrayList)a.Value; - ArrayList bList = (ArrayList)b.Value; - - return bList.Count - aList.Count; - } - } - - - private static ArrayList GetSharedAccounts( IPAddress ipAddress ) - { - ArrayList list = new ArrayList(); - - foreach ( Account acct in Accounts.GetAccounts() ) - { - IPAddress[] theirAddresses = acct.LoginIPs; - bool contains = false; - - for ( int i = 0; !contains && i < theirAddresses.Length; ++i ) - contains = ipAddress.Equals( theirAddresses[i] ); - - if ( contains ) - list.Add( acct ); - } - - list.Sort( AccountComparer.Instance ); - return list; - } - - private static ArrayList GetSharedAccounts( IPAddress[] ipAddresses ) - { - ArrayList list = new ArrayList(); - - foreach ( Account acct in Accounts.GetAccounts() ) - { - IPAddress[] theirAddresses = acct.LoginIPs; - bool contains = false; - - for ( int i = 0; !contains && i < theirAddresses.Length; ++i ) - { - IPAddress check = theirAddresses[i]; - - for ( int j = 0; !contains && j < ipAddresses.Length; ++j ) - contains = check.Equals( ipAddresses[j] ); - } - - if ( contains ) - list.Add( acct ); - } - - list.Sort( AccountComparer.Instance ); - return list; - } - - public static void BanShared_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - string notice; - ArrayList list = null; - - if ( okay ) - { - Account a = (Account)state; - list = GetSharedAccounts( a.LoginIPs ); - - for ( int i = 0; i < list.Count; ++i ) - { - ((Account)list[i]).SetUnspecifiedBan( from ); - ((Account)list[i]).Banned = true; - } - - notice = "All addresses in the list have been banned."; - } - else - { - notice = "You have chosen not to ban all shared accounts."; - } - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, state ) ); - - if ( okay ) - from.SendGump( new BanDurationGump( list ) ); - } - - public static void AccountDelete_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - if ( okay ) - { - Account a = (Account)state; - - CommandLogging.WriteLine( from, "{0} {1} deleting account {2}", from.AccessLevel, CommandLogging.Format( from ), a.Username ); - a.Delete(); - - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, null, - $"{a.Username} : The account has been deleted.", null ) ); - } - else - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "You have chosen not to delete the account.", state ) ); - } - } - - public static void ResendGump_Callback( Mobile from, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - object[] states = (object[])state; - ArrayList list = (ArrayList)states[0]; - ArrayList rads = (ArrayList)states[1]; - int page = (int)states[2]; - - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, page, list, null, rads ) ); - } - - public static void Marked_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - object[] states = (object[])state; - bool ban = (bool)states[0]; - ArrayList list = (ArrayList)states[1]; - ArrayList rads = (ArrayList)states[2]; - int page = (int)states[3]; - - if ( okay ) - { - if ( !ban ) - NetState.Pause(); - - for ( int i = 0; i < rads.Count; ++i ) - { - Account acct = (Account)rads[i]; - - if ( ban ) - { - CommandLogging.WriteLine( from, "{0} {1} banning account {2}", from.AccessLevel, CommandLogging.Format( from ), acct.Username ); - acct.SetUnspecifiedBan( from ); - acct.Banned = true; - } - else - { - CommandLogging.WriteLine( from, "{0} {1} deleting account {2}", from.AccessLevel, CommandLogging.Format( from ), acct.Username ); - acct.Delete(); - rads.RemoveAt( i-- ); - list.Remove( acct ); - } - } - - if ( !ban ) - NetState.Resume(); - - from.SendGump( new NoticeGump( 1060637, 30720, - $"You have {(ban ? "banned" : "deleted")} the account{(rads.Count == 1 ? "" : "s")}.", 0xFFC000, 420, 280, ResendGump_Callback, new object[]{ list, rads, ban ? page : 0 } ) ); - - if ( ban ) - from.SendGump( new BanDurationGump( rads ) ); - } - else - { - from.SendGump( new NoticeGump( 1060637, 30720, - $"You have chosen not to {(ban ? "ban" : "delete")} the account{(rads.Count == 1 ? "" : "s")}.", 0xFFC000, 420, 280, ResendGump_Callback, new object[]{ list, rads, page } ) ); - } - } - - public static void FirewallShared_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - string notice; - - if ( okay ) - { - Account a = (Account)state; - - for ( int i = 0; i < a.LoginIPs.Length; ++i ) - Firewall.Add( a.LoginIPs[i] ); - - notice = "All addresses in the list have been firewalled."; - } - else - { - notice = "You have chosen not to firewall all addresses."; - } - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, state ) ); - } - - public static void Firewall_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - object[] states = (object[])state; - - Account a = (Account)states[0]; - object toFirewall = states[1]; - - string notice; - - if ( okay ) - { - Firewall.Add( toFirewall ); - - notice = $"{toFirewall} : Added to firewall."; - } - else - { - notice = "You have chosen not to firewall the address."; - } - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, a ) ); - } - - public static void RemoveLoginIP_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - object[] states = (object[])state; - - Account a = (Account)states[0]; - IPAddress ip = (IPAddress)states[1]; - - string notice; - - if ( okay ) - { - IPAddress[] ips = a.LoginIPs; - - if ( ips.Length != 0 && ip == ips[0] && AccountHandler.IPTable.ContainsKey( ips[0] ) ) - --AccountHandler.IPTable[ip]; - - List newList = new List( ips ); - newList.Remove( ip ); - a.LoginIPs = newList.ToArray(); - - notice = $"{ip} : Removed address."; - } - else - { - notice = "You have chosen not to remove the address."; - } - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, a ) ); - } - - public static void RemoveLoginIPs_Callback( Mobile from, bool okay, object state ) - { - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - Account a = (Account)state; - - string notice; - - if ( okay ) - { - IPAddress[] ips = a.LoginIPs; - - if ( ips.Length != 0 && AccountHandler.IPTable.ContainsKey( ips[0] ) ) - --AccountHandler.IPTable[ips[0]]; - - a.LoginIPs = new IPAddress[0]; - - notice = "All addresses in the list have been removed."; - } - else - { - notice = "You have chosen not to clear all addresses."; - } - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, a ) ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int val = info.ButtonID - 1; - - if ( val < 0 ) - return; - - Mobile from = m_From; - - if ( from.AccessLevel < AccessLevel.Administrator ) - return; - - if ( m_PageType == AdminGumpPage.Accounts ) - { - ArrayList list = m_List; - - if ( list != null && m_State is ArrayList rads ) - { - for ( int i = 0, v = m_ListPage*12; i < 12 && v < list.Count; ++i, ++v ) - { - object obj = list[v]; - - if ( info.IsSwitched( v ) ) - { - if ( !rads.Contains( obj ) ) - rads.Add( obj ); - } - else if ( rads.Contains( obj ) ) - { - rads.Remove( obj ); - } - } - } - } - - int type = val % 11; - int index = val / 11; - - switch ( type ) - { - case 0: - { - AdminGumpPage page; - - switch ( index ) - { - case 0: page = AdminGumpPage.Information_General; break; - case 1: page = AdminGumpPage.Administer; break; - case 2: page = AdminGumpPage.Clients; break; - case 3: page = AdminGumpPage.Accounts; break; - case 4: page = AdminGumpPage.Firewall; break; - case 5: page = AdminGumpPage.Information_Perf; break; - default: return; - } - - from.SendGump( new AdminGump( from, page, 0, null, null, null ) ); - break; - } - case 1: - { - switch ( index ) - { - case 0: - { - if ( m_List != null && m_ListPage > 0 ) - from.SendGump( new AdminGump( from, m_PageType, m_ListPage - 1, m_List, null, m_State ) ); - - break; - } - case 1: - { - if ( m_List != null /*&& (m_ListPage + 1) * 12 < m_List.Count*/ ) - from.SendGump( new AdminGump( from, m_PageType, m_ListPage + 1, m_List, null, m_State ) ); - - break; - } - } - - break; - } - case 3: - { - string notice = null; - AdminGumpPage page = AdminGumpPage.Administer; - - if ( index >= 500 ) - page = AdminGumpPage.Administer_Access_Lockdown; - else if ( index >= 400 ) - page = AdminGumpPage.Administer_Commands; - else if ( index >= 300 ) - page = AdminGumpPage.Administer_Access; - else if ( index >= 200 ) - page = AdminGumpPage.Administer_Server; - else if ( index >= 100 ) - page = AdminGumpPage.Administer_WorldBuilding; - - switch ( index ) - { - case 0: page = AdminGumpPage.Administer_WorldBuilding; break; - case 1: page = AdminGumpPage.Administer_Server; break; - case 2: page = AdminGumpPage.Administer_Access; break; - case 3: page = AdminGumpPage.Administer_Commands; break; - - case 100: InvokeCommand( "DocGen" ); notice = "Documentation has been generated."; break; - case 101: InvokeCommand( "TelGen" ); notice = "Teleporters have been generated."; break; - case 102: InvokeCommand( "MoonGen" ); notice = "Moongates have been generated."; break; - case 103: InvokeCommand( "UOAMVendors" ); notice = "Vendor spawners have been generated."; break; - case 104: InvokeCommand( "DoorGen" ); notice = "Doors have been generated."; break; - case 105: InvokeCommand( "SignGen" ); notice = "Signs have been generated."; break; - case 106: InvokeCommand( "Decorate" ); notice = "Decoration has been generated."; break; - case 107: InvokeCommand( "RebuildCategorization" ); notice = "Categorization menu has been regenerated. The server should be restarted."; break; - - case 110: InvokeCommand( "Freeze" ); notice = "Target bounding points."; break; - case 120: InvokeCommand( "Unfreeze" ); notice = "Target bounding points."; break; - - case 200: InvokeCommand( "Save" ); notice = "The world has been saved."; break; - case 201: Shutdown( false, true ); break; - case 202: Shutdown( false, false ); break; - case 203: Shutdown( true, true ); break; - case 204: Shutdown( true, false ); break; - case 210: - case 211: - { - string text = info.GetTextEntry( 0 )?.Text.Trim(); - - if ( string.IsNullOrEmpty(text) ) - { - notice = "You must enter text to broadcast it."; - } - else - { - notice = "Your message has been broadcasted."; - InvokeCommand($"{(index == 210 ? "BC" : "SM")} {text}"); - } - - break; - } - - case 300: InvokeCommand( "Kick" ); notice = "Target the player to kick."; break; - case 301: InvokeCommand( "Ban" ); notice = "Target the player to ban."; break; - case 302: InvokeCommand( "Firewall" ); notice = "Target the player to firewall."; break; - - case 303: page = AdminGumpPage.Administer_Access_Lockdown; break; - - case 310: InvokeCommand( "Set AccessLevel Player" ); notice = "Target the player to change their access level. (Player)"; break; - case 311: InvokeCommand( "Set AccessLevel Counselor" ); notice = "Target the player to change their access level. (Counselor)"; break; - case 312: InvokeCommand( "Set AccessLevel GameMaster" ); notice = "Target the player to change their access level. (Game Master)"; break; - case 313: InvokeCommand( "Set AccessLevel Seer" ); notice = "Target the player to change their access level. (Seer)"; break; - - case 314: - { - if ( from.AccessLevel > AccessLevel.Administrator ) - { - InvokeCommand( "Set AccessLevel Administrator" ); - notice = "Target the player to change their access level. (Administrator)"; - } - - break; - } - - case 315: - { - if ( from.AccessLevel > AccessLevel.Developer ) - { - InvokeCommand( "Set AccessLevel Developer" ); - notice = "Target the player to change their access level. (Developer)"; - } - - break; - } - - case 316: - { - if ( from.AccessLevel >= AccessLevel.Owner ) - { - InvokeCommand( "Set AccessLevel Owner" ); - notice = "Target the player to change their access level. (Owner)"; - } - - break; - } - - case 400: notice = "Enter search terms to add objects."; break; - case 401: InvokeCommand( "Remove" ); notice = "Target the item or mobile to remove."; break; - case 402: InvokeCommand( "Dupe" ); notice = "Target the item to dupe."; break; - case 403: InvokeCommand( "DupeInBag" ); notice = "Target the item to dupe. The item will be duped at it's current location."; break; - case 404: InvokeCommand( "Props" ); notice = "Target the item or mobile to inspect."; break; - case 405: InvokeCommand( "Skills" ); notice = "Target a mobile to view their skills."; break; - case 406: InvokeCommand( "Set Blessed False" ); notice = "Target the mobile to make mortal."; break; - case 407: InvokeCommand( "Set Blessed True" ); notice = "Target the mobile to make immortal."; break; - case 408: InvokeCommand( "Set Squelched True" ); notice = "Target the mobile to squelch."; break; - case 409: InvokeCommand( "Set Squelched False" ); notice = "Target the mobile to unsquelch."; break; - case 410: InvokeCommand( "Set Frozen True" ); notice = "Target the mobile to freeze."; break; - case 411: InvokeCommand( "Set Frozen False" ); notice = "Target the mobile to unfreeze."; break; - case 412: InvokeCommand( "Set Hidden True" ); notice = "Target the mobile to hide."; break; - case 413: InvokeCommand( "Set Hidden False" ); notice = "Target the mobile to unhide."; break; - case 414: InvokeCommand( "Kill" ); notice = "Target the mobile to kill."; break; - case 415: InvokeCommand( "Resurrect" ); notice = "Target the mobile to resurrect."; break; - case 416: InvokeCommand( "Move" ); notice = "Target the item or mobile to move."; break; - case 417: InvokeCommand( "Wipe" ); notice = "Target bounding points."; break; - case 418: InvokeCommand( "Tele" ); notice = "Choose your destination."; break; - case 419: InvokeCommand( "Multi Tele" ); notice = "Choose your destination."; break; - - case 500: - case 501: - case 502: - case 503: - case 504: - { - AccountHandler.LockdownLevel = (AccessLevel)(index - 500); - - if ( AccountHandler.LockdownLevel > AccessLevel.Player ) - notice = "The lockdown level has been changed."; - else - notice = "The server is now accessible to everyone."; - - break; - } - - case 510: - { - AccessLevel level = AccountHandler.LockdownLevel; - - if ( level > AccessLevel.Player ) - { - List clients = NetState.Instances; - int count = 0; - - for ( int i = 0; i < clients.Count; ++i ) - { - NetState ns = clients[i]; - IAccount a = ns.Account; - - if ( a == null ) - continue; - - bool hasAccess = false; - - if ( a.AccessLevel >= level ) - { - hasAccess = true; - } - else - { - for ( int j = 0; !hasAccess && j < a.Length; ++j ) - { - Mobile m = a[j]; - - if ( m != null && m.AccessLevel >= level ) - hasAccess = true; - } - } - - if ( !hasAccess ) - { - ns.Dispose(); - ++count; - } - } - - if ( count == 0 ) - notice = "Nobody without access was found to disconnect."; - else - notice = $"Number of players disconnected: {count}"; - } - else - { - notice = "The server is not currently locked down."; - } - - break; - } - } - - from.SendGump( new AdminGump( from, page, 0, null, notice, null ) ); - - switch ( index ) - { - case 400: InvokeCommand( "Add" ); break; - case 111: InvokeCommand( "FreezeWorld" ); break; - case 112: InvokeCommand( "FreezeMap" ); break; - case 121: InvokeCommand( "UnfreezeWorld" ); break; - case 122: InvokeCommand( "UnfreezeMap" ); break; - } - - break; - } - case 4: - { - switch ( index ) - { - case 0: - case 1: - { - bool forName = ( index == 0 ); - - ArrayList results = new ArrayList(); - - string match = info.GetTextEntry( 0 )?.Text.Trim().ToLower(); - string notice = null; - - if ( string.IsNullOrEmpty(match) ) - { - notice = $"You must enter {(forName ? "a name" : "an ip address")} to search."; - } - else - { - List instances = NetState.Instances; - - for ( int i = 0; i < instances.Count; ++i ) - { - NetState ns = instances[i]; - - bool isMatch; - - if ( forName ) - { - Mobile m = ns.Mobile; - IAccount a = ns.Account; - - isMatch = ( m != null && m.Name.ToLower().IndexOf( match ) >= 0 ) - || ( a != null && a.Username.ToLower().IndexOf( match ) >= 0 ); - } - else - { - isMatch = ( ns.ToString().IndexOf( match ) >= 0 ); - } - - if ( isMatch ) - results.Add( ns ); - } - - results.Sort( NetStateComparer.Instance ); - } - - if ( results.Count == 1 ) - { - NetState ns = (NetState)results[0]; - object state = ns.Mobile; - - if ( state == null ) - state = ns.Account; - - if ( state is Mobile ) - from.SendGump( new AdminGump( from, AdminGumpPage.ClientInfo, 0, null, "One match found.", state ) ); - else if ( state is Account ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "One match found.", state ) ); - else - from.SendGump( new AdminGump( from, AdminGumpPage.Clients, 0, results, "One match found.", null ) ); - } - else - { - from.SendGump( new AdminGump( from, AdminGumpPage.Clients, 0, results, notice ?? (results.Count == 0 ? "Nothing matched your search terms." : null), null ) ); - } - - break; - } - default: - { - index -= 2; - - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - if ( !(m_List[index] is NetState ns) ) - break; - - Mobile m = ns.Mobile; - Account a = ns.Account as Account; - - if ( m != null ) - from.SendGump( new AdminGump( from, AdminGumpPage.ClientInfo, 0, null, null, m ) ); - else if ( a != null ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, null, a ) ); - } - - break; - } - } - - break; - } - case 5: - { - switch ( index ) - { - case 0: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, null, m_State ) ); break; - case 1: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Characters, 0, null, null, m_State ) ); break; - case 2: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Comments, 0, null, null, m_State ) ); break; - case 3: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Tags, 0, null, null, m_State ) ); break; - case 13: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access, 0, null, null, m_State ) ); break; - case 14: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, null, m_State ) ); break; - case 15: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_Restrictions, 0, null, null, m_State ) ); break; - case 4: from.Prompt = new AddCommentPrompt( m_State as Account ); from.SendMessage( "Enter the new account comment." ); break; - case 5: from.Prompt = new AddTagNamePrompt( m_State as Account ); from.SendMessage( "Enter the new tag name." ); break; - case 6: - { - string un = info.GetTextEntry( 0 )?.Text.Trim(); - string pw = info.GetTextEntry( 1 )?.Text.Trim(); - - Account dispAccount = null; - string notice; - - if ( string.IsNullOrEmpty(un) ) - { - notice = "You must enter a username to add an account."; - } - else if ( string.IsNullOrEmpty(pw) ) - { - notice = "You must enter a password to add an account."; - } - else - { - IAccount account = Accounts.GetAccount( un ); - - if ( account != null ) - { - notice = "There is already an account with that username."; - } - else - { - dispAccount = new Account( un, pw ); - notice = $"{un} : Account added."; - CommandLogging.WriteLine( from, "{0} {1} adding new account: {2}", from.AccessLevel, CommandLogging.Format( from ), un ); - } - } - - from.SendGump( new AdminGump( from, dispAccount != null ? AdminGumpPage.AccountDetails_Information : m_PageType, m_ListPage, m_List, notice, dispAccount ?? m_State ) ); - break; - } - case 7: - { - ArrayList results; - - TextRelay matchEntry = info.GetTextEntry( 0 ); - string match = matchEntry?.Text.Trim().ToLower(); - string notice = null; - - if ( string.IsNullOrEmpty(match) ) - { - results = new ArrayList( (ICollection)Accounts.GetAccounts() ); - results.Sort( AccountComparer.Instance ); - //notice = "You must enter a username to search."; - } - else - { - results = new ArrayList(); - foreach ( IAccount acct in Accounts.GetAccounts() ) - { - if ( acct.Username.ToLower().IndexOf( match ) >= 0 ) - results.Add( acct ); - } - - results.Sort( AccountComparer.Instance ); - } - - if ( results.Count == 1 ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "One match found.", results[0] ) ); - else - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, results, notice ?? (results.Count == 0 ? "Nothing matched your search terms." : null), new ArrayList() ) ); - - break; - } - case 8: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_ChangePassword, 0, null, null, m_State ) ); break; - case 9: from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_ChangeAccess, 0, null, null, m_State ) ); break; - case 10: case 11: - { - if ( !(m_State is Account a) ) - break; - - a.SetUnspecifiedBan( from ); - a.Banned = ( index == 10 ); - CommandLogging.WriteLine( from, "{0} {1} {3} account {2}", from.AccessLevel, CommandLogging.Format( from ), a.Username, a.Banned ? "banning" : "unbanning" ); - from.SendGump( new AdminGump( from, m_PageType, m_ListPage, m_List, - $"The account has been {(a.Banned ? "banned" : "unbanned")}.", m_State ) ); - - if ( index == 10 ) - from.SendGump( new BanDurationGump( a ) ); - - break; - } - case 12: - { - if ( !(m_State is Account a) ) - break; - - TextRelay passwordEntry = info.GetTextEntry( 0 ); - TextRelay confirmEntry = info.GetTextEntry( 1 ); - - string password = passwordEntry?.Text.Trim(); - string confirm = confirmEntry?.Text.Trim(); - - string notice; - AdminGumpPage page = AdminGumpPage.AccountDetails_ChangePassword; - - if ( string.IsNullOrEmpty(password) ) - { - notice = "You must enter the password."; - } - else if ( confirm != password ) - { - notice = "You must confirm the password. That field must precisely match the password field."; - } - else - { - notice = "The password has been changed."; - a.SetPassword( password ); - page = AdminGumpPage.AccountDetails_Information; - CommandLogging.WriteLine( from, "{0} {1} changing password of account {2}", from.AccessLevel, CommandLogging.Format( from ), a.Username ); - } - - from.SendGump( new AdminGump( from, page, 0, null, notice, m_State ) ); - - break; - } - case 16: // view shared - { - if ( !(m_State is Account a) ) - break; - - ArrayList list = GetSharedAccounts( a.LoginIPs ); - - if ( list.Count > 1 || (list.Count == 1 && !list.Contains( a )) ) - { - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, list, null, new ArrayList() ) ); - } - else if ( a.LoginIPs.Length > 0 ) - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "There are no other accounts which share an address with this one.", m_State ) ); - } - else - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "This account has not yet been accessed.", m_State ) ); - } - - break; - } - case 17: // ban shared - { - if ( !(m_State is Account a) ) - break; - - ArrayList list = GetSharedAccounts( a.LoginIPs ); - - if ( list.Count > 0 ) - { - StringBuilder sb = new StringBuilder(); - - sb.AppendFormat( "You are about to ban {0} account{1}. Do you wish to continue?", list.Count, list.Count != 1 ? "s" : "" ); - - for ( int i = 0; i < list.Count; ++i ) - sb.AppendFormat( "
- {0}", ((Account)list[i]).Username ); - - from.SendGump( new WarningGump( 1060635, 30720, sb.ToString(), 0xFFC000, 420, 400, BanShared_Callback, a ) ); - } - else if ( a.LoginIPs.Length > 0 ) - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "There are no accounts which share an address with this one.", m_State ) ); - } - else - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "This account has not yet been accessed.", m_State ) ); - } - - break; - } - case 18: // firewall all - { - if ( !(m_State is Account a) ) - break; - - if ( a.LoginIPs.Length > 0 ) - { - from.SendGump( new WarningGump( 1060635, 30720, - $"You are about to firewall {a.LoginIPs.Length} address{(a.LoginIPs.Length != 1 ? "s" : "")}. Do you wish to continue?", 0xFFC000, 420, 400, FirewallShared_Callback, a ) ); - } - else - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "This account has not yet been accessed.", m_State ) ); - } - - break; - } - case 19: // add - { - if ( !(m_State is Account a) ) - break; - - TextRelay entry = info.GetTextEntry( 0 ); - string ip = entry?.Text.Trim(); - - string notice; - - if ( string.IsNullOrEmpty(ip) ) - { - notice = "You must enter an address to add."; - } - else - { - string[] list = a.IPRestrictions; - - bool contains = false; - for ( int i = 0; !contains && i < list.Length; ++i ) - contains = ( list[i] == ip ); - - if ( contains ) - { - notice = "That address is already contained in the list."; - } - else - { - string[] newList = new string[list.Length + 1]; - - for ( int i = 0; i < list.Length; ++i ) - newList[i] = list[i]; - - newList[list.Length] = ip; - - a.IPRestrictions = newList; - - notice = $"{ip} : Added to restriction list."; - } - } - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_Restrictions, 0, null, notice, m_State ) ); - - break; - } - case 20: // Change access level - case 21: - case 22: - case 23: - case 24: - { - if ( !(m_State is Account a) ) - break; - - AccessLevel newLevel; - - switch ( index ) - { - default: - case 20: newLevel = AccessLevel.Player; break; - case 21: newLevel = AccessLevel.Counselor; break; - case 22: newLevel = AccessLevel.GameMaster; break; - case 23: newLevel = AccessLevel.Seer; break; - case 24: newLevel = AccessLevel.Administrator; break; - case 33: newLevel = AccessLevel.Developer; break; - case 34: newLevel = AccessLevel.Owner; break; - } - - if ( newLevel < from.AccessLevel || from.AccessLevel == AccessLevel.Owner ) - { - a.AccessLevel = newLevel; - - CommandLogging.WriteLine( from, "{0} {1} changing access level of account {2} to {3}", from.AccessLevel, CommandLogging.Format( from ), a.Username, a.AccessLevel ); - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "The access level has been changed.", m_State ) ); - } - - break; - } - case 25: - { - if ( !(m_State is Account a) ) - break; - - from.SendGump( new WarningGump( 1060635, 30720, - $"
Account of {a.Username}

You are about to permanently delete the account. Likewise, all characters on the account will be deleted, including equipped, inventory, and banked items. Any houses tied to the account will be demolished.

Do you wish to continue?", 0xFFC000, 420, 280, AccountDelete_Callback, m_State ) ); - break; - } - case 26: // View all shared accounts - { - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts_Shared, 0, null, null, null ) ); - break; - } - case 27: // Ban marked - { - ArrayList list = m_List; - - if ( list == null || !(m_State is ArrayList rads) ) - break; - - if ( rads.Count > 0 ) - from.SendGump( new WarningGump( 1060635, 30720, - $"You are about to ban {rads.Count} marked account{(rads.Count == 1 ? "" : "s")}. Be cautioned, the only way to reverse this is by hand--manually unbanning each account.

Do you wish to continue?", 0xFFC000, 420, 280, Marked_Callback, new object[]{ true, list, rads, m_ListPage } ) ); - else - from.SendGump( new NoticeGump( 1060637, 30720, "You have not yet marked any accounts. Place a check mark next to the accounts you wish to ban and then try again.", 0xFFC000, 420, 280, ResendGump_Callback, new object[]{ list, rads, m_ListPage } ) ); - - break; - } - case 28: // Delete marked - { - ArrayList list = m_List; - - if ( list == null || !(m_State is ArrayList rads) ) - break; - - if ( rads.Count > 0 ) - from.SendGump( new WarningGump( 1060635, 30720, string.Format( "You are about to permanently delete {0} marked account{1}. Likewise, all characters on the account{1} will be deleted, including equipped, inventory, and banked items. Any houses tied to the account{1} will be demolished.

Do you wish to continue?", rads.Count, rads.Count == 1 ? "" : "s" ), 0xFFC000, 420, 280, Marked_Callback, new object[]{ false, list, rads, m_ListPage } ) ); - else - from.SendGump( new NoticeGump( 1060637, 30720, "You have not yet marked any accounts. Place a check mark next to the accounts you wish to ban and then try again.", 0xFFC000, 420, 280, ResendGump_Callback, new object[]{ list, rads, m_ListPage } ) ); - - break; - } - case 29: // Mark all - { - ArrayList list = m_List; - - if ( list == null || !(m_State is ArrayList rads) ) - break; - - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, m_ListPage, m_List, null, new ArrayList( list ) ) ); - - break; - } - case 30: // View all empty accounts - { - ArrayList results = new ArrayList(); - - foreach ( IAccount acct in Accounts.GetAccounts() ) - { - bool empty = true; - - for ( int i = 0; empty && i < acct.Length; ++i ) - empty = ( acct[i] == null ); - - if ( empty ) - results.Add( acct ); - } - - if ( results.Count == 1 ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "One match found.", results[0] ) ); - else - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, results, (results.Count == 0 ? "Nothing matched your search terms." : null), new ArrayList() ) ); - - break; - } - case 31: // View all inactive accounts - { - ArrayList results = new ArrayList(); - - foreach ( IAccount acct in Accounts.GetAccounts() ) - { - if ((acct as Account)?.Inactive == true ) - results.Add( acct ); - } - - if ( results.Count == 1 ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "One match found.", results[0] ) ); - else - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, results, (results.Count == 0 ? "Nothing matched your search terms." : null), new ArrayList() ) ); - - break; - } - case 32: // View all banned accounts - { - ArrayList results = new ArrayList(); - - foreach ( IAccount acct in Accounts.GetAccounts() ) - { - if ((acct as Account)?.Banned == true ) - results.Add( acct ); - } - - if ( results.Count == 1 ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, "One match found.", results[0] ) ); - else - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, results, (results.Count == 0 ? "Nothing matched your search terms." : null), new ArrayList() ) ); - - break; - } - case 33: // Change access level (extended) - case 34: - { - goto case 20; - } - case 35: // Unmark house owners - { - ArrayList list = m_List; - ArrayList rads = m_State as ArrayList; - - if ( list == null || rads == null ) - break; - - ArrayList newRads = new ArrayList(); - - foreach ( Account acct in rads ) - { - bool hasHouse = false; - - for ( int i = 0; i < acct.Length && !hasHouse; ++i ) - if ( acct[i] != null && BaseHouse.HasHouse( acct[i] ) ) - hasHouse = true; - - if ( !hasHouse ) - newRads.Add( acct ); - } - - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, m_ListPage, m_List, null, newRads ) ); - - break; - } - case 36: // Clear login addresses - { - Account a = m_State as Account; - - if ( a == null ) - break; - - IPAddress[] ips = a.LoginIPs; - - if ( ips.Length == 0 ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "This account has not yet been accessed.", m_State ) ); - else - from.SendGump( new WarningGump( 1060635, 30720, - $"You are about to clear the address list for account {a} containing {ips.Length} {((ips.Length == 1) ? "entry" : "entries")}. Do you wish to continue?", 0xFFC000, 420, 280, RemoveLoginIPs_Callback, a ) ); - - break; - } - default: - { - index -= 50; - - if ( m_State is Account a && index >= 0 && index < a.Length ) - { - Mobile m = a[index]; - - if ( m != null ) - from.SendGump( new AdminGump( from, AdminGumpPage.ClientInfo, 0, null, null, m ) ); - } - else - { - index -= 6; - - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - if ( m_List[index] is Account ) - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, null, m_List[index] ) ); - else if ( m_List[index] is DictionaryEntry ) - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, (ArrayList)(((DictionaryEntry)m_List[index]).Value), null, new ArrayList() ) ); - } - } - - break; - } - } - - break; - } - case 6: - { - switch ( index ) - { - case 0: - { - TextRelay matchEntry = info.GetTextEntry( 0 ); - string match = matchEntry?.Text.Trim(); - - string notice = null; - ArrayList results = new ArrayList(); - - if ( string.IsNullOrEmpty(match) ) - { - notice = "You must enter a username to search."; - } - else - { - for ( int i = 0; i < Firewall.List.Count; ++i ) - { - string check = Firewall.List[i].ToString(); - - if ( check.IndexOf( match ) >= 0 ) - results.Add( Firewall.List[i] ); - } - } - - if ( results.Count == 1 ) - from.SendGump( new AdminGump( from, AdminGumpPage.FirewallInfo, 0, null, "One match found.", results[0] ) ); - else if ( results.Count > 1 ) - from.SendGump( new AdminGump( from, AdminGumpPage.Firewall, 0, results, - $"Search results for : {match}", m_State ) ); - else - from.SendGump( new AdminGump( from, m_PageType, m_ListPage, m_List, notice ?? "Nothing matched your search terms.", m_State ) ); - - break; - } - case 1: - { - TextRelay relay = info.GetTextEntry( 0 ); - string text = relay?.Text.Trim(); - - if ( text == null || text.Length == 0 ) - { - from.SendGump( new AdminGump( from, m_PageType, m_ListPage, m_List, "You must enter an address or pattern to add.", m_State ) ); - } - else if ( !Utility.IsValidIP( text ) ) - { - from.SendGump( new AdminGump( from, m_PageType, m_ListPage, m_List, "That is not a valid address or pattern.", m_State ) ); - } - else - { - object toAdd = Firewall.ToFirewallEntry( text ); - - CommandLogging.WriteLine( from, "{0} {1} firewalling {2}", from.AccessLevel, CommandLogging.Format( from ), toAdd ); - - Firewall.Add( toAdd ); - from.SendGump( new AdminGump( from, AdminGumpPage.FirewallInfo, 0, null, - $"{toAdd} : Added to firewall.", toAdd ) ); - } - - break; - } - case 2: - { - InvokeCommand( "Firewall" ); - from.SendGump( new AdminGump( from, m_PageType, m_ListPage, m_List, "Target the player to firewall.", m_State ) ); - break; - } - case 3: - { - if ( m_State is Firewall.IFirewallEntry ) - { - CommandLogging.WriteLine( from, "{0} {1} removing {2} from firewall list", from.AccessLevel, CommandLogging.Format( from ), m_State ); - - Firewall.Remove( m_State ); - from.SendGump( new AdminGump( from, AdminGumpPage.Firewall, 0, null, - $"{m_State} : Removed from firewall.", null ) ); - } - - break; - } - default: - { - index -= 4; - - if ( m_List != null && index >= 0 && index < m_List.Count ) - from.SendGump( new AdminGump( from, AdminGumpPage.FirewallInfo, 0, null, null, m_List[index] ) ); - - break; - } - } - - break; - } - case 7: - { - Mobile m = m_State as Mobile; - - if ( m == null ) - break; - - string notice = null; - bool sendGump = true; - - switch ( index ) - { - case 0: - { - Map map = m.Map; - Point3D loc = m.Location; - - if ( map == null || map == Map.Internal ) - { - map = m.LogoutMap; - loc = m.LogoutLocation; - } - - if ( map != null && map != Map.Internal ) - { - from.MoveToWorld( loc, map ); - notice = "You have been teleported to their location."; - } - - break; - } - case 1: - { - m.MoveToWorld( from.Location, from.Map ); - notice = "They have been teleported to your location."; - break; - } - case 2: - { - NetState ns = m.NetState; - - if ( ns != null ) - { - CommandLogging.WriteLine( from, "{0} {1} {2} {3}", from.AccessLevel, CommandLogging.Format( from ), "kicking", CommandLogging.Format( m ) ); - ns.Dispose(); - notice = "They have been kicked."; - } - else - { - notice = "They are already disconnected."; - } - - break; - } - case 3: - { - if ( m.Account is Account a ) - { - CommandLogging.WriteLine( from, "{0} {1} {2} {3}", from.AccessLevel, CommandLogging.Format( from ), "banning", CommandLogging.Format( m ) ); - a.Banned = true; - - NetState ns = m.NetState; - - ns?.Dispose(); - - notice = "They have been banned."; - } - - break; - } - case 6: - { - Properties.SetValue( from, m, "Blessed", "False" ); - notice = "They are now mortal."; - break; - } - case 7: - { - Properties.SetValue( from, m, "Blessed", "True" ); - notice = "They are now immortal."; - break; - } - case 8: - { - Properties.SetValue( from, m, "Squelched", "True" ); - notice = "They are now squelched."; - break; - } - case 9: - { - Properties.SetValue( from, m, "Squelched", "False" ); - notice = "They are now unsquelched."; - break; - } - case 10: - { - Properties.SetValue( from, m, "Hidden", "True" ); - notice = "They are now hidden."; - break; - } - case 11: - { - Properties.SetValue( from, m, "Hidden", "False" ); - notice = "They are now unhidden."; - break; - } - case 12: - { - CommandLogging.WriteLine( from, "{0} {1} killing {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( m ) ); - m.Kill(); - notice = "They have been killed."; - break; - } - case 13: - { - CommandLogging.WriteLine( from, "{0} {1} resurrecting {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( m ) ); - m.Resurrect(); - notice = "They have been resurrected."; - break; - } - case 14: - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Information, 0, null, null, m.Account ) ); - sendGump = false; - break; - } - } - - if ( sendGump ) - from.SendGump( new AdminGump( from, AdminGumpPage.ClientInfo, 0, null, notice, m_State ) ); - - switch ( index ) - { - case 3: - { - if ( m.Account is Account a ) - from.SendGump( new BanDurationGump( a ) ); - - break; - } - case 4: - { - from.SendGump( new PropertiesGump( from, m ) ); - break; - } - case 5: - { - from.SendGump( new SkillsGump( from, m ) ); - break; - } - } - - break; - } - case 8: - { - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - Account a = m_State as Account; - - if ( a == null ) - break; - - if ( m_PageType == AdminGumpPage.AccountDetails_Access_ClientIPs ) - { - from.SendGump( new WarningGump( 1060635, 30720, - $"You are about to firewall {m_List[index]}. All connection attempts from a matching IP will be refused. Are you sure?", 0xFFC000, 420, 280, Firewall_Callback, new[]{ a, m_List[index] } ) ); - } - else if ( m_PageType == AdminGumpPage.AccountDetails_Access_Restrictions ) - { - ArrayList list = new ArrayList( a.IPRestrictions ); - - list.Remove( m_List[index] ); - - a.IPRestrictions = (string[])list.ToArray( typeof( string ) ); - - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_Restrictions, 0, null, - $"{m_List[index]} : Removed from list.", a ) ); - } - } - - break; - } - case 9: - { - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - if ( m_PageType == AdminGumpPage.AccountDetails_Access_ClientIPs ) - { - object obj = m_List[index]; - - if ( !(obj is IPAddress) ) - break; - - Account a = m_State as Account; - - if ( a == null ) - break; - - ArrayList list = GetSharedAccounts( (IPAddress)obj ); - - if ( list.Count > 1 || (list.Count == 1 && !list.Contains( a )) ) - from.SendGump( new AdminGump( from, AdminGumpPage.Accounts, 0, list, null, new ArrayList() ) ); - else - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, "There are no other accounts which share that address.", m_State ) ); - } - } - - break; - } - case 10: - { - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - if ( m_PageType == AdminGumpPage.AccountDetails_Access_ClientIPs ) - { - IPAddress ip = m_List[index] as IPAddress; - - if ( ip == null ) - break; - - Account a = m_State as Account; - - if ( a == null ) - break; - - from.SendGump( new WarningGump( 1060635, 30720, - $"You are about to remove address {ip} from account {a}. Do you wish to continue?", 0xFFC000, 420, 280, RemoveLoginIP_Callback, new object[] { a, ip } ) ); - } - } - - break; - } - } - } - - private void Shutdown( bool restart, bool save ) - { - CommandLogging.WriteLine( m_From, "{0} {1} shutting down server (Restart: {2}) (Save: {3})", m_From.AccessLevel, CommandLogging.Format( m_From ), restart, save ); - - if ( save ) - InvokeCommand( "Save" ); - - Core.Kill( restart ); - } - - private void InvokeCommand( string c ) - { - CommandSystem.Handle( m_From, $"{CommandSystem.Prefix}{c}"); - } - - public static void GetAccountInfo( Account a, out AccessLevel accessLevel, out bool online ) - { - accessLevel = a.AccessLevel; - online = false; - - for ( int j = 0; j < a.Length; ++j ) - { - Mobile check = a[j]; - - if ( check == null ) - continue; - - if ( check.AccessLevel > accessLevel ) - accessLevel = check.AccessLevel; - - if ( check.NetState != null ) - online = true; - } - } - - private class AddCommentPrompt : Prompt - { - private Account m_Account; - - public AddCommentPrompt( Account acct ) - { - m_Account = acct; - } - - public override void OnCancel( Mobile from ) - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Comments, 0, null, "Request to add comment was canceled.", m_Account ) ); - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Account != null ) - { - m_Account.Comments.Add( new AccountComment( from.RawName, text ) ); - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Comments, 0, null, "Comment added.", m_Account ) ); - } - } - } - - private class AddTagNamePrompt : Prompt - { - private Account m_Account; - - public AddTagNamePrompt( Account acct ) - { - m_Account = acct; - } - - public override void OnCancel( Mobile from ) - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Tags, 0, null, "Request to add tag was canceled.", m_Account ) ); - } - - public override void OnResponse( Mobile from, string text ) - { - from.Prompt = new AddTagValuePrompt( m_Account, text ); - from.SendMessage( "Enter the new tag value." ); - } - } - - private class AddTagValuePrompt : Prompt - { - private Account m_Account; - private string m_Name; - - public AddTagValuePrompt( Account acct, string name ) - { - m_Account = acct; - m_Name = name; - } - - public override void OnCancel( Mobile from ) - { - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Tags, 0, null, "Request to add tag was canceled.", m_Account ) ); - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Account != null ) - { - m_Account.AddTag( m_Name, text ); - from.SendGump( new AdminGump( from, AdminGumpPage.AccountDetails_Tags, 0, null, "Tag added.", m_Account ) ); - } - } - } - - private class NetStateComparer : IComparer - { - public static readonly IComparer Instance = new NetStateComparer(); - - public NetStateComparer() - { - } - - public int Compare( object x, object y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; - - if ( !(x is NetState a) || !(y is NetState b) ) - throw new ArgumentException(); - - Mobile aMob = a.Mobile; - Mobile bMob = b.Mobile; - - if ( aMob == null && bMob == null ) - return 0; - if ( aMob == null ) - return 1; - if ( bMob == null ) - return -1; - - if ( aMob.AccessLevel > bMob.AccessLevel ) - return -1; - if ( aMob.AccessLevel < bMob.AccessLevel ) - return 1; - return Insensitive.Compare( aMob.Name, bMob.Name ); - } - } - - private class AccountComparer : IComparer - { - public static readonly IComparer Instance = new AccountComparer(); - - public AccountComparer() - { - } - - public int Compare( object x, object y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; - - if ( !(x is Account a) || !(y is Account b) ) - throw new ArgumentException(); - - GetAccountInfo( a, out var aLevel, out var aOnline ); - GetAccountInfo( b, out var bLevel, out var bOnline ); - - if ( aOnline && !bOnline ) - return -1; - if ( bOnline && !aOnline ) - return 1; - if ( aLevel > bLevel ) - return -1; - if ( aLevel < bLevel ) - return 1; - return Insensitive.Compare( a.Username, b.Username ); - } - } - } -} + AddLabelCropped(12, offset, 120, 20, LabelHue, a.Username); + AddLabelCropped(132, offset, 120, 20, LabelHue, FormatAccessLevel(accessLevel)); + + if (online) + AddLabelCropped(252, offset, 120, 20, GreenHue, "Online"); + else if (a.Banned) + AddLabelCropped(252, offset, 120, 20, RedHue, "Banned"); + else + AddLabelCropped(252, offset, 120, 20, RedHue, "Offline"); + + AddButton(380, offset - 1, 0xFA5, 0xFA7, GetButtonID(5, index + 56), GumpButtonType.Reply, 0); + } + + break; + } + } + } + + public void AddPageButton(int x, int y, int buttonID, string text, AdminGumpPage page, + params AdminGumpPage[] subPages) + { + bool isSelection = m_PageType == page; + + for (int i = 0; !isSelection && i < subPages.Length; ++i) + isSelection = m_PageType == subPages[i]; + + AddSelectedButton(x, y, buttonID, text, isSelection); + } + + public void AddSelectedButton(int x, int y, int buttonID, string text, bool isSelection) + { + AddButton(x, y - 1, isSelection ? 4006 : 4005, 4007, buttonID, GumpButtonType.Reply, 0); + AddHtml(x + 35, y, 200, 20, Color(text, isSelection ? SelectedColor32 : LabelColor32), false, false); + } + + public void AddButtonLabeled(int x, int y, int buttonID, string text) + { + AddButton(x, y - 1, 4005, 4007, buttonID, GumpButtonType.Reply, 0); + AddHtml(x + 35, y, 240, 20, Color(text, LabelColor32), false, false); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + public void AddBlackAlpha(int x, int y, int width, int height) + { + AddImageTiled(x, y, width, height, 2624); + AddAlphaRegion(x, y, width, height); + } + + public int GetButtonID(int type, int index) + { + return 1 + index * 11 + type; + } + + public static string FormatTimeSpan(TimeSpan ts) + { + return $"{ts.Days:D2}:{ts.Hours % 24:D2}:{ts.Minutes % 60:D2}:{ts.Seconds % 60:D2}"; + } + + public static string FormatByteAmount(long totalBytes) + { + if (totalBytes > 1000000000) + return $"{(double)totalBytes / 1073741824:F1} GB"; + + if (totalBytes > 1000000) + return $"{(double)totalBytes / 1048576:F1} MB"; + + if (totalBytes > 1000) + return $"{(double)totalBytes / 1024:F1} KB"; + + return $"{totalBytes} Bytes"; + } + + public static void Initialize() + { + CommandSystem.Register("Admin", AccessLevel.Administrator, Admin_OnCommand); + } + + [Usage("Admin")] + [Description( + "Opens an interface providing server information and administration features including client, account, and firewall management.")] + public static void Admin_OnCommand(CommandEventArgs e) + { + e.Mobile.SendGump(new AdminGump(e.Mobile, AdminGumpPage.Clients, 0, null, null, null)); + } + + public static int GetHueFor(Mobile m) + { + if (m == null) + return LabelHue; + + switch (m.AccessLevel) + { + case AccessLevel.Owner: + case AccessLevel.Developer: + case AccessLevel.Administrator: return 0x516; + case AccessLevel.Seer: return 0x144; + case AccessLevel.GameMaster: return 0x21; + case AccessLevel.Counselor: return 0x2; + case AccessLevel.Player: + default: + { + if (m.Kills >= 5) + return 0x21; + + return m.Criminal ? 0x3B1 : 0x58; + } + } + } + + public static string FormatAccessLevel(AccessLevel level) + { + int v = (int)level; + + if (v >= 0 && v < m_AccessLevelStrings.Length) + return m_AccessLevelStrings[v]; + + return "Unknown"; + } + + public void AddTextField(int x, int y, int width, int height, int index) + { + AddBackground(x - 2, y - 2, width + 4, height + 4, 0x2486); + AddTextEntry(x + 2, y + 2, width - 4, height - 4, 0, index, ""); + } + + public void AddClientHeader() + { + AddTextField(200, 20, 200, 20, 0); + AddButtonLabeled(200, 50, GetButtonID(4, 0), "Search For Name"); + AddButtonLabeled(200, 80, GetButtonID(4, 1), "Search For IP Address"); + } + + public void AddAccountHeader() + { + AddPage(1); + + AddLabel(200, 20, LabelHue, "Name:"); + AddTextField(250, 20, 150, 20, 0); + + AddLabel(200, 50, LabelHue, "Pass:"); + AddTextField(250, 50, 150, 20, 1); + + AddButtonLabeled(200, 80, GetButtonID(5, 6), "Add"); + AddButtonLabeled(290, 80, GetButtonID(5, 7), "Search"); + + AddButton(384, 84, 0x15E1, 0x15E5, 0, GumpButtonType.Page, 2); + + AddPage(2); + + AddButtonLabeled(200, 20, GetButtonID(5, 31), "View All: Inactive"); + AddButtonLabeled(200, 40, GetButtonID(5, 32), "View All: Banned"); + AddButtonLabeled(200, 60, GetButtonID(5, 26), "View All: Shared"); + AddButtonLabeled(200, 80, GetButtonID(5, 30), "View All: Empty"); + + AddButton(384, 84, 0x15E1, 0x15E5, 0, GumpButtonType.Page, 1); + + AddPage(0); + } + + public void AddFirewallHeader() + { + AddTextField(200, 20, 200, 20, 0); + AddButtonLabeled(320, 50, GetButtonID(6, 0), "Search"); + AddButtonLabeled(200, 50, GetButtonID(6, 1), "Add (Input)"); + AddButtonLabeled(200, 80, GetButtonID(6, 2), "Add (Target)"); + } + + private static ArrayList GetAllSharedAccounts() + { + Hashtable table = new Hashtable(); + ArrayList list; + + foreach (Account acct in Accounts.GetAccounts()) + { + IPAddress[] theirAddresses = acct.LoginIPs; + + for (int i = 0; i < theirAddresses.Length; ++i) + { + list = (ArrayList)table[theirAddresses[i]]; + + if (list == null) + table[theirAddresses[i]] = list = new ArrayList(); + + list.Add(acct); + } + } + + list = new ArrayList(table); + + for (int i = 0; i < list.Count; ++i) + { + DictionaryEntry de = (DictionaryEntry)list[i]; + ArrayList accts = (ArrayList)de.Value; + + if (accts.Count == 1) + list.RemoveAt(i--); + else + accts.Sort(AccountComparer.Instance); + } + + list.Sort(SharedAccountComparer.Instance); + + return list; + } + + + private static ArrayList GetSharedAccounts(IPAddress ipAddress) + { + ArrayList list = new ArrayList(); + + foreach (Account acct in Accounts.GetAccounts()) + { + IPAddress[] theirAddresses = acct.LoginIPs; + bool contains = false; + + for (int i = 0; !contains && i < theirAddresses.Length; ++i) + contains = ipAddress.Equals(theirAddresses[i]); + + if (contains) + list.Add(acct); + } + + list.Sort(AccountComparer.Instance); + return list; + } + + private static ArrayList GetSharedAccounts(IPAddress[] ipAddresses) + { + ArrayList list = new ArrayList(); + + foreach (Account acct in Accounts.GetAccounts()) + { + IPAddress[] theirAddresses = acct.LoginIPs; + bool contains = false; + + for (int i = 0; !contains && i < theirAddresses.Length; ++i) + { + IPAddress check = theirAddresses[i]; + + for (int j = 0; !contains && j < ipAddresses.Length; ++j) + contains = check.Equals(ipAddresses[j]); + } + + if (contains) + list.Add(acct); + } + + list.Sort(AccountComparer.Instance); + return list; + } + + public static void BanShared_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + string notice; + ArrayList list = null; + + if (okay) + { + Account a = (Account)state; + list = GetSharedAccounts(a.LoginIPs); + + for (int i = 0; i < list.Count; ++i) + { + ((Account)list[i]).SetUnspecifiedBan(from); + ((Account)list[i]).Banned = true; + } + + notice = "All addresses in the list have been banned."; + } + else + { + notice = "You have chosen not to ban all shared accounts."; + } + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, state)); + + if (okay) + from.SendGump(new BanDurationGump(list)); + } + + public static void AccountDelete_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + if (okay) + { + Account a = (Account)state; + + CommandLogging.WriteLine(from, "{0} {1} deleting account {2}", from.AccessLevel, CommandLogging.Format(from), + a.Username); + a.Delete(); + + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, null, + $"{a.Username} : The account has been deleted.", null)); + } + else + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "You have chosen not to delete the account.", state)); + } + } + + public static void ResendGump_Callback(Mobile from, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + object[] states = (object[])state; + ArrayList list = (ArrayList)states[0]; + ArrayList rads = (ArrayList)states[1]; + int page = (int)states[2]; + + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, page, list, null, rads)); + } + + public static void Marked_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + object[] states = (object[])state; + bool ban = (bool)states[0]; + ArrayList list = (ArrayList)states[1]; + ArrayList rads = (ArrayList)states[2]; + int page = (int)states[3]; + + if (okay) + { + if (!ban) + NetState.Pause(); + + for (int i = 0; i < rads.Count; ++i) + { + Account acct = (Account)rads[i]; + + if (ban) + { + CommandLogging.WriteLine(from, "{0} {1} banning account {2}", from.AccessLevel, + CommandLogging.Format(from), acct.Username); + acct.SetUnspecifiedBan(from); + acct.Banned = true; + } + else + { + CommandLogging.WriteLine(from, "{0} {1} deleting account {2}", from.AccessLevel, + CommandLogging.Format(from), acct.Username); + acct.Delete(); + rads.RemoveAt(i--); + list.Remove(acct); + } + } + + if (!ban) + NetState.Resume(); + + from.SendGump(new NoticeGump(1060637, 30720, + $"You have {(ban ? "banned" : "deleted")} the account{(rads.Count == 1 ? "" : "s")}.", 0xFFC000, 420, + 280, ResendGump_Callback, new object[] { list, rads, ban ? page : 0 })); + + if (ban) + from.SendGump(new BanDurationGump(rads)); + } + else + { + from.SendGump(new NoticeGump(1060637, 30720, + $"You have chosen not to {(ban ? "ban" : "delete")} the account{(rads.Count == 1 ? "" : "s")}.", + 0xFFC000, 420, 280, ResendGump_Callback, new object[] { list, rads, page })); + } + } + + public static void FirewallShared_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + string notice; + + if (okay) + { + Account a = (Account)state; + + for (int i = 0; i < a.LoginIPs.Length; ++i) + Firewall.Add(a.LoginIPs[i]); + + notice = "All addresses in the list have been firewalled."; + } + else + { + notice = "You have chosen not to firewall all addresses."; + } + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, state)); + } + + public static void Firewall_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + object[] states = (object[])state; + + Account a = (Account)states[0]; + object toFirewall = states[1]; + + string notice; + + if (okay) + { + Firewall.Add(toFirewall); + + notice = $"{toFirewall} : Added to firewall."; + } + else + { + notice = "You have chosen not to firewall the address."; + } + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, a)); + } + + public static void RemoveLoginIP_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + object[] states = (object[])state; + + Account a = (Account)states[0]; + IPAddress ip = (IPAddress)states[1]; + + string notice; + + if (okay) + { + IPAddress[] ips = a.LoginIPs; + + if (ips.Length != 0 && ip == ips[0] && AccountHandler.IPTable.ContainsKey(ips[0])) + --AccountHandler.IPTable[ip]; + + List newList = new List(ips); + newList.Remove(ip); + a.LoginIPs = newList.ToArray(); + + notice = $"{ip} : Removed address."; + } + else + { + notice = "You have chosen not to remove the address."; + } + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, a)); + } + + public static void RemoveLoginIPs_Callback(Mobile from, bool okay, object state) + { + if (from.AccessLevel < AccessLevel.Administrator) + return; + + Account a = (Account)state; + + string notice; + + if (okay) + { + IPAddress[] ips = a.LoginIPs; + + if (ips.Length != 0 && AccountHandler.IPTable.ContainsKey(ips[0])) + --AccountHandler.IPTable[ips[0]]; + + a.LoginIPs = new IPAddress[0]; + + notice = "All addresses in the list have been removed."; + } + else + { + notice = "You have chosen not to clear all addresses."; + } + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, notice, a)); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int val = info.ButtonID - 1; + + if (val < 0) + return; + + Mobile from = m_From; + + if (from.AccessLevel < AccessLevel.Administrator) + return; + + if (m_PageType == AdminGumpPage.Accounts) + { + ArrayList list = m_List; + + if (list != null && m_State is ArrayList rads) + for (int i = 0, v = m_ListPage * 12; i < 12 && v < list.Count; ++i, ++v) + { + object obj = list[v]; + + if (info.IsSwitched(v)) + { + if (!rads.Contains(obj)) + rads.Add(obj); + } + else if (rads.Contains(obj)) + { + rads.Remove(obj); + } + } + } + + int type = val % 11; + int index = val / 11; + + switch (type) + { + case 0: + { + AdminGumpPage page; + + switch (index) + { + case 0: + page = AdminGumpPage.Information_General; + break; + case 1: + page = AdminGumpPage.Administer; + break; + case 2: + page = AdminGumpPage.Clients; + break; + case 3: + page = AdminGumpPage.Accounts; + break; + case 4: + page = AdminGumpPage.Firewall; + break; + case 5: + page = AdminGumpPage.Information_Perf; + break; + default: return; + } + + from.SendGump(new AdminGump(from, page, 0, null, null, null)); + break; + } + case 1: + { + switch (index) + { + case 0: + { + if (m_List != null && m_ListPage > 0) + from.SendGump(new AdminGump(from, m_PageType, m_ListPage - 1, m_List, null, m_State)); + + break; + } + case 1: + { + if (m_List != null /*&& (m_ListPage + 1) * 12 < m_List.Count*/) + from.SendGump(new AdminGump(from, m_PageType, m_ListPage + 1, m_List, null, m_State)); + + break; + } + } + + break; + } + case 3: + { + string notice = null; + AdminGumpPage page = AdminGumpPage.Administer; + + if (index >= 500) + page = AdminGumpPage.Administer_Access_Lockdown; + else if (index >= 400) + page = AdminGumpPage.Administer_Commands; + else if (index >= 300) + page = AdminGumpPage.Administer_Access; + else if (index >= 200) + page = AdminGumpPage.Administer_Server; + else if (index >= 100) + page = AdminGumpPage.Administer_WorldBuilding; + + switch (index) + { + case 0: + page = AdminGumpPage.Administer_WorldBuilding; + break; + case 1: + page = AdminGumpPage.Administer_Server; + break; + case 2: + page = AdminGumpPage.Administer_Access; + break; + case 3: + page = AdminGumpPage.Administer_Commands; + break; + + case 100: + InvokeCommand("DocGen"); + notice = "Documentation has been generated."; + break; + case 101: + InvokeCommand("TelGen"); + notice = "Teleporters have been generated."; + break; + case 102: + InvokeCommand("MoonGen"); + notice = "Moongates have been generated."; + break; + case 103: + InvokeCommand("UOAMVendors"); + notice = "Vendor spawners have been generated."; + break; + case 104: + InvokeCommand("DoorGen"); + notice = "Doors have been generated."; + break; + case 105: + InvokeCommand("SignGen"); + notice = "Signs have been generated."; + break; + case 106: + InvokeCommand("Decorate"); + notice = "Decoration has been generated."; + break; + case 107: + InvokeCommand("RebuildCategorization"); + notice = "Categorization menu has been regenerated. The server should be restarted."; + break; + + case 110: + InvokeCommand("Freeze"); + notice = "Target bounding points."; + break; + case 120: + InvokeCommand("Unfreeze"); + notice = "Target bounding points."; + break; + + case 200: + InvokeCommand("Save"); + notice = "The world has been saved."; + break; + case 201: + Shutdown(false, true); + break; + case 202: + Shutdown(false, false); + break; + case 203: + Shutdown(true, true); + break; + case 204: + Shutdown(true, false); + break; + case 210: + case 211: + { + string text = info.GetTextEntry(0)?.Text.Trim(); + + if (string.IsNullOrEmpty(text)) + { + notice = "You must enter text to broadcast it."; + } + else + { + notice = "Your message has been broadcasted."; + InvokeCommand($"{(index == 210 ? "BC" : "SM")} {text}"); + } + + break; + } + + case 300: + InvokeCommand("Kick"); + notice = "Target the player to kick."; + break; + case 301: + InvokeCommand("Ban"); + notice = "Target the player to ban."; + break; + case 302: + InvokeCommand("Firewall"); + notice = "Target the player to firewall."; + break; + + case 303: + page = AdminGumpPage.Administer_Access_Lockdown; + break; + + case 310: + InvokeCommand("Set AccessLevel Player"); + notice = "Target the player to change their access level. (Player)"; + break; + case 311: + InvokeCommand("Set AccessLevel Counselor"); + notice = "Target the player to change their access level. (Counselor)"; + break; + case 312: + InvokeCommand("Set AccessLevel GameMaster"); + notice = "Target the player to change their access level. (Game Master)"; + break; + case 313: + InvokeCommand("Set AccessLevel Seer"); + notice = "Target the player to change their access level. (Seer)"; + break; + + case 314: + { + if (from.AccessLevel > AccessLevel.Administrator) + { + InvokeCommand("Set AccessLevel Administrator"); + notice = "Target the player to change their access level. (Administrator)"; + } + + break; + } + + case 315: + { + if (from.AccessLevel > AccessLevel.Developer) + { + InvokeCommand("Set AccessLevel Developer"); + notice = "Target the player to change their access level. (Developer)"; + } + + break; + } + + case 316: + { + if (from.AccessLevel >= AccessLevel.Owner) + { + InvokeCommand("Set AccessLevel Owner"); + notice = "Target the player to change their access level. (Owner)"; + } + + break; + } + + case 400: + notice = "Enter search terms to add objects."; + break; + case 401: + InvokeCommand("Remove"); + notice = "Target the item or mobile to remove."; + break; + case 402: + InvokeCommand("Dupe"); + notice = "Target the item to dupe."; + break; + case 403: + InvokeCommand("DupeInBag"); + notice = "Target the item to dupe. The item will be duped at it's current location."; + break; + case 404: + InvokeCommand("Props"); + notice = "Target the item or mobile to inspect."; + break; + case 405: + InvokeCommand("Skills"); + notice = "Target a mobile to view their skills."; + break; + case 406: + InvokeCommand("Set Blessed False"); + notice = "Target the mobile to make mortal."; + break; + case 407: + InvokeCommand("Set Blessed True"); + notice = "Target the mobile to make immortal."; + break; + case 408: + InvokeCommand("Set Squelched True"); + notice = "Target the mobile to squelch."; + break; + case 409: + InvokeCommand("Set Squelched False"); + notice = "Target the mobile to unsquelch."; + break; + case 410: + InvokeCommand("Set Frozen True"); + notice = "Target the mobile to freeze."; + break; + case 411: + InvokeCommand("Set Frozen False"); + notice = "Target the mobile to unfreeze."; + break; + case 412: + InvokeCommand("Set Hidden True"); + notice = "Target the mobile to hide."; + break; + case 413: + InvokeCommand("Set Hidden False"); + notice = "Target the mobile to unhide."; + break; + case 414: + InvokeCommand("Kill"); + notice = "Target the mobile to kill."; + break; + case 415: + InvokeCommand("Resurrect"); + notice = "Target the mobile to resurrect."; + break; + case 416: + InvokeCommand("Move"); + notice = "Target the item or mobile to move."; + break; + case 417: + InvokeCommand("Wipe"); + notice = "Target bounding points."; + break; + case 418: + InvokeCommand("Tele"); + notice = "Choose your destination."; + break; + case 419: + InvokeCommand("Multi Tele"); + notice = "Choose your destination."; + break; + + case 500: + case 501: + case 502: + case 503: + case 504: + { + AccountHandler.LockdownLevel = (AccessLevel)(index - 500); + + if (AccountHandler.LockdownLevel > AccessLevel.Player) + notice = "The lockdown level has been changed."; + else + notice = "The server is now accessible to everyone."; + + break; + } + + case 510: + { + AccessLevel level = AccountHandler.LockdownLevel; + + if (level > AccessLevel.Player) + { + List clients = NetState.Instances; + int count = 0; + + for (int i = 0; i < clients.Count; ++i) + { + NetState ns = clients[i]; + IAccount a = ns.Account; + + if (a == null) + continue; + + bool hasAccess = false; + + if (a.AccessLevel >= level) + hasAccess = true; + else + for (int j = 0; !hasAccess && j < a.Length; ++j) + { + Mobile m = a[j]; + + if (m != null && m.AccessLevel >= level) + hasAccess = true; + } + + if (!hasAccess) + { + ns.Dispose(); + ++count; + } + } + + if (count == 0) + notice = "Nobody without access was found to disconnect."; + else + notice = $"Number of players disconnected: {count}"; + } + else + { + notice = "The server is not currently locked down."; + } + + break; + } + } + + from.SendGump(new AdminGump(from, page, 0, null, notice, null)); + + switch (index) + { + case 400: + InvokeCommand("Add"); + break; + case 111: + InvokeCommand("FreezeWorld"); + break; + case 112: + InvokeCommand("FreezeMap"); + break; + case 121: + InvokeCommand("UnfreezeWorld"); + break; + case 122: + InvokeCommand("UnfreezeMap"); + break; + } + + break; + } + case 4: + { + switch (index) + { + case 0: + case 1: + { + bool forName = index == 0; + + ArrayList results = new ArrayList(); + + string match = info.GetTextEntry(0)?.Text.Trim().ToLower(); + string notice = null; + + if (string.IsNullOrEmpty(match)) + { + notice = $"You must enter {(forName ? "a name" : "an ip address")} to search."; + } + else + { + List instances = NetState.Instances; + + for (int i = 0; i < instances.Count; ++i) + { + NetState ns = instances[i]; + + bool isMatch; + + if (forName) + { + Mobile m = ns.Mobile; + IAccount a = ns.Account; + + isMatch = m != null && m.Name.ToLower().IndexOf(match) >= 0 + || a != null && a.Username.ToLower().IndexOf(match) >= 0; + } + else + { + isMatch = ns.ToString().IndexOf(match) >= 0; + } + + if (isMatch) + results.Add(ns); + } + + results.Sort(NetStateComparer.Instance); + } + + if (results.Count == 1) + { + NetState ns = (NetState)results[0]; + object state = ns.Mobile; + + if (state == null) + state = ns.Account; + + if (state is Mobile) + from.SendGump(new AdminGump(from, AdminGumpPage.ClientInfo, 0, null, "One match found.", + state)); + else if (state is Account) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "One match found.", state)); + else + from.SendGump(new AdminGump(from, AdminGumpPage.Clients, 0, results, "One match found.", + null)); + } + else + { + from.SendGump(new AdminGump(from, AdminGumpPage.Clients, 0, results, + notice ?? (results.Count == 0 ? "Nothing matched your search terms." : null), null)); + } + + break; + } + default: + { + index -= 2; + + if (m_List != null && index >= 0 && index < m_List.Count) + { + if (!(m_List[index] is NetState ns)) + break; + + Mobile m = ns.Mobile; + Account a = ns.Account as Account; + + if (m != null) + from.SendGump(new AdminGump(from, AdminGumpPage.ClientInfo, 0, null, null, m)); + else if (a != null) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + null, a)); + } + + break; + } + } + + break; + } + case 5: + { + switch (index) + { + case 0: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, null, + m_State)); + break; + case 1: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Characters, 0, null, null, + m_State)); + break; + case 2: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Comments, 0, null, null, + m_State)); + break; + case 3: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Tags, 0, null, null, m_State)); + break; + case 13: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access, 0, null, null, m_State)); + break; + case 14: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, null, + m_State)); + break; + case 15: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_Restrictions, 0, null, + null, m_State)); + break; + case 4: + from.Prompt = new AddCommentPrompt(m_State as Account); + from.SendMessage("Enter the new account comment."); + break; + case 5: + from.Prompt = new AddTagNamePrompt(m_State as Account); + from.SendMessage("Enter the new tag name."); + break; + case 6: + { + string un = info.GetTextEntry(0)?.Text.Trim(); + string pw = info.GetTextEntry(1)?.Text.Trim(); + + Account dispAccount = null; + string notice; + + if (string.IsNullOrEmpty(un)) + { + notice = "You must enter a username to add an account."; + } + else if (string.IsNullOrEmpty(pw)) + { + notice = "You must enter a password to add an account."; + } + else + { + IAccount account = Accounts.GetAccount(un); + + if (account != null) + { + notice = "There is already an account with that username."; + } + else + { + dispAccount = new Account(un, pw); + notice = $"{un} : Account added."; + CommandLogging.WriteLine(from, "{0} {1} adding new account: {2}", from.AccessLevel, + CommandLogging.Format(from), un); + } + } + + from.SendGump(new AdminGump(from, + dispAccount != null ? AdminGumpPage.AccountDetails_Information : m_PageType, m_ListPage, + m_List, notice, dispAccount ?? m_State)); + break; + } + case 7: + { + ArrayList results; + + TextRelay matchEntry = info.GetTextEntry(0); + string match = matchEntry?.Text.Trim().ToLower(); + string notice = null; + + if (string.IsNullOrEmpty(match)) + { + results = new ArrayList((ICollection)Accounts.GetAccounts()); + results.Sort(AccountComparer.Instance); + //notice = "You must enter a username to search."; + } + else + { + results = new ArrayList(); + foreach (IAccount acct in Accounts.GetAccounts()) + if (acct.Username.ToLower().IndexOf(match) >= 0) + results.Add(acct); + + results.Sort(AccountComparer.Instance); + } + + if (results.Count == 1) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "One match found.", results[0])); + else + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, results, + notice ?? (results.Count == 0 ? "Nothing matched your search terms." : null), + new ArrayList())); + + break; + } + case 8: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_ChangePassword, 0, null, null, + m_State)); + break; + case 9: + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_ChangeAccess, 0, null, null, + m_State)); + break; + case 10: + case 11: + { + if (!(m_State is Account a)) + break; + + a.SetUnspecifiedBan(from); + a.Banned = index == 10; + CommandLogging.WriteLine(from, "{0} {1} {3} account {2}", from.AccessLevel, + CommandLogging.Format(from), a.Username, a.Banned ? "banning" : "unbanning"); + from.SendGump(new AdminGump(from, m_PageType, m_ListPage, m_List, + $"The account has been {(a.Banned ? "banned" : "unbanned")}.", m_State)); + + if (index == 10) + from.SendGump(new BanDurationGump(a)); + + break; + } + case 12: + { + if (!(m_State is Account a)) + break; + + TextRelay passwordEntry = info.GetTextEntry(0); + TextRelay confirmEntry = info.GetTextEntry(1); + + string password = passwordEntry?.Text.Trim(); + string confirm = confirmEntry?.Text.Trim(); + + string notice; + AdminGumpPage page = AdminGumpPage.AccountDetails_ChangePassword; + + if (string.IsNullOrEmpty(password)) + { + notice = "You must enter the password."; + } + else if (confirm != password) + { + notice = + "You must confirm the password. That field must precisely match the password field."; + } + else + { + notice = "The password has been changed."; + a.SetPassword(password); + page = AdminGumpPage.AccountDetails_Information; + CommandLogging.WriteLine(from, "{0} {1} changing password of account {2}", from.AccessLevel, + CommandLogging.Format(from), a.Username); + } + + from.SendGump(new AdminGump(from, page, 0, null, notice, m_State)); + + break; + } + case 16: // view shared + { + if (!(m_State is Account a)) + break; + + ArrayList list = GetSharedAccounts(a.LoginIPs); + + if (list.Count > 1 || list.Count == 1 && !list.Contains(a)) + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, list, null, new ArrayList())); + else if (a.LoginIPs.Length > 0) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "There are no other accounts which share an address with this one.", m_State)); + else + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "This account has not yet been accessed.", m_State)); + + break; + } + case 17: // ban shared + { + if (!(m_State is Account a)) + break; + + ArrayList list = GetSharedAccounts(a.LoginIPs); + + if (list.Count > 0) + { + StringBuilder sb = new StringBuilder(); + + sb.AppendFormat("You are about to ban {0} account{1}. Do you wish to continue?", list.Count, + list.Count != 1 ? "s" : ""); + + for (int i = 0; i < list.Count; ++i) + sb.AppendFormat("
- {0}", ((Account)list[i]).Username); + + from.SendGump(new WarningGump(1060635, 30720, sb.ToString(), 0xFFC000, 420, 400, + BanShared_Callback, a)); + } + else if (a.LoginIPs.Length > 0) + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "There are no accounts which share an address with this one.", m_State)); + } + else + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "This account has not yet been accessed.", m_State)); + } + + break; + } + case 18: // firewall all + { + if (!(m_State is Account a)) + break; + + if (a.LoginIPs.Length > 0) + from.SendGump(new WarningGump(1060635, 30720, + $"You are about to firewall {a.LoginIPs.Length} address{(a.LoginIPs.Length != 1 ? "s" : "")}. Do you wish to continue?", + 0xFFC000, 420, 400, FirewallShared_Callback, a)); + else + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "This account has not yet been accessed.", m_State)); + + break; + } + case 19: // add + { + if (!(m_State is Account a)) + break; + + TextRelay entry = info.GetTextEntry(0); + string ip = entry?.Text.Trim(); + + string notice; + + if (string.IsNullOrEmpty(ip)) + { + notice = "You must enter an address to add."; + } + else + { + string[] list = a.IPRestrictions; + + bool contains = false; + for (int i = 0; !contains && i < list.Length; ++i) + contains = list[i] == ip; + + if (contains) + { + notice = "That address is already contained in the list."; + } + else + { + string[] newList = new string[list.Length + 1]; + + for (int i = 0; i < list.Length; ++i) + newList[i] = list[i]; + + newList[list.Length] = ip; + + a.IPRestrictions = newList; + + notice = $"{ip} : Added to restriction list."; + } + } + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_Restrictions, 0, null, + notice, m_State)); + + break; + } + case 20: // Change access level + case 21: + case 22: + case 23: + case 24: + { + if (!(m_State is Account a)) + break; + + AccessLevel newLevel; + + switch (index) + { + default: + case 20: + newLevel = AccessLevel.Player; + break; + case 21: + newLevel = AccessLevel.Counselor; + break; + case 22: + newLevel = AccessLevel.GameMaster; + break; + case 23: + newLevel = AccessLevel.Seer; + break; + case 24: + newLevel = AccessLevel.Administrator; + break; + case 33: + newLevel = AccessLevel.Developer; + break; + case 34: + newLevel = AccessLevel.Owner; + break; + } + + if (newLevel < from.AccessLevel || from.AccessLevel == AccessLevel.Owner) + { + a.AccessLevel = newLevel; + + CommandLogging.WriteLine(from, "{0} {1} changing access level of account {2} to {3}", + from.AccessLevel, CommandLogging.Format(from), a.Username, a.AccessLevel); + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "The access level has been changed.", m_State)); + } + + break; + } + case 25: + { + if (!(m_State is Account a)) + break; + + from.SendGump(new WarningGump(1060635, 30720, + $"
Account of {a.Username}

You are about to permanently delete the account. Likewise, all characters on the account will be deleted, including equipped, inventory, and banked items. Any houses tied to the account will be demolished.

Do you wish to continue?", + 0xFFC000, 420, 280, AccountDelete_Callback, m_State)); + break; + } + case 26: // View all shared accounts + { + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts_Shared, 0, null, null, null)); + break; + } + case 27: // Ban marked + { + ArrayList list = m_List; + + if (list == null || !(m_State is ArrayList rads)) + break; + + if (rads.Count > 0) + from.SendGump(new WarningGump(1060635, 30720, + $"You are about to ban {rads.Count} marked account{(rads.Count == 1 ? "" : "s")}. Be cautioned, the only way to reverse this is by hand--manually unbanning each account.

Do you wish to continue?", + 0xFFC000, 420, 280, Marked_Callback, new object[] { true, list, rads, m_ListPage })); + else + from.SendGump(new NoticeGump(1060637, 30720, + "You have not yet marked any accounts. Place a check mark next to the accounts you wish to ban and then try again.", + 0xFFC000, 420, 280, ResendGump_Callback, new object[] { list, rads, m_ListPage })); + + break; + } + case 28: // Delete marked + { + ArrayList list = m_List; + + if (list == null || !(m_State is ArrayList rads)) + break; + + if (rads.Count > 0) + from.SendGump(new WarningGump(1060635, 30720, + string.Format( + "You are about to permanently delete {0} marked account{1}. Likewise, all characters on the account{1} will be deleted, including equipped, inventory, and banked items. Any houses tied to the account{1} will be demolished.

Do you wish to continue?", + rads.Count, rads.Count == 1 ? "" : "s"), 0xFFC000, 420, 280, Marked_Callback, + new object[] { false, list, rads, m_ListPage })); + else + from.SendGump(new NoticeGump(1060637, 30720, + "You have not yet marked any accounts. Place a check mark next to the accounts you wish to ban and then try again.", + 0xFFC000, 420, 280, ResendGump_Callback, new object[] { list, rads, m_ListPage })); + + break; + } + case 29: // Mark all + { + ArrayList list = m_List; + + if (list == null || !(m_State is ArrayList rads)) + break; + + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, m_ListPage, m_List, null, + new ArrayList(list))); + + break; + } + case 30: // View all empty accounts + { + ArrayList results = new ArrayList(); + + foreach (IAccount acct in Accounts.GetAccounts()) + { + bool empty = true; + + for (int i = 0; empty && i < acct.Length; ++i) + empty = acct[i] == null; + + if (empty) + results.Add(acct); + } + + if (results.Count == 1) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "One match found.", results[0])); + else + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, results, + results.Count == 0 ? "Nothing matched your search terms." : null, new ArrayList())); + + break; + } + case 31: // View all inactive accounts + { + ArrayList results = new ArrayList(); + + foreach (IAccount acct in Accounts.GetAccounts()) + if ((acct as Account)?.Inactive == true) + results.Add(acct); + + if (results.Count == 1) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "One match found.", results[0])); + else + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, results, + results.Count == 0 ? "Nothing matched your search terms." : null, new ArrayList())); + + break; + } + case 32: // View all banned accounts + { + ArrayList results = new ArrayList(); + + foreach (IAccount acct in Accounts.GetAccounts()) + if ((acct as Account)?.Banned == true) + results.Add(acct); + + if (results.Count == 1) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + "One match found.", results[0])); + else + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, results, + results.Count == 0 ? "Nothing matched your search terms." : null, new ArrayList())); + + break; + } + case 33: // Change access level (extended) + case 34: + { + goto case 20; + } + case 35: // Unmark house owners + { + ArrayList list = m_List; + ArrayList rads = m_State as ArrayList; + + if (list == null || rads == null) + break; + + ArrayList newRads = new ArrayList(); + + foreach (Account acct in rads) + { + bool hasHouse = false; + + for (int i = 0; i < acct.Length && !hasHouse; ++i) + if (acct[i] != null && BaseHouse.HasHouse(acct[i])) + hasHouse = true; + + if (!hasHouse) + newRads.Add(acct); + } + + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, m_ListPage, m_List, null, newRads)); + + break; + } + case 36: // Clear login addresses + { + Account a = m_State as Account; + + if (a == null) + break; + + IPAddress[] ips = a.LoginIPs; + + if (ips.Length == 0) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "This account has not yet been accessed.", m_State)); + else + from.SendGump(new WarningGump(1060635, 30720, + $"You are about to clear the address list for account {a} containing {ips.Length} {(ips.Length == 1 ? "entry" : "entries")}. Do you wish to continue?", + 0xFFC000, 420, 280, RemoveLoginIPs_Callback, a)); + + break; + } + default: + { + index -= 50; + + if (m_State is Account a && index >= 0 && index < a.Length) + { + Mobile m = a[index]; + + if (m != null) + from.SendGump(new AdminGump(from, AdminGumpPage.ClientInfo, 0, null, null, m)); + } + else + { + index -= 6; + + if (m_List != null && index >= 0 && index < m_List.Count) + { + if (m_List[index] is Account) + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, + null, m_List[index])); + else if (m_List[index] is DictionaryEntry) + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, + (ArrayList)((DictionaryEntry)m_List[index]).Value, null, new ArrayList())); + } + } + + break; + } + } + + break; + } + case 6: + { + switch (index) + { + case 0: + { + TextRelay matchEntry = info.GetTextEntry(0); + string match = matchEntry?.Text.Trim(); + + string notice = null; + ArrayList results = new ArrayList(); + + if (string.IsNullOrEmpty(match)) + notice = "You must enter a username to search."; + else + for (int i = 0; i < Firewall.List.Count; ++i) + { + string check = Firewall.List[i].ToString(); + + if (check.IndexOf(match) >= 0) + results.Add(Firewall.List[i]); + } + + if (results.Count == 1) + from.SendGump(new AdminGump(from, AdminGumpPage.FirewallInfo, 0, null, "One match found.", + results[0])); + else if (results.Count > 1) + from.SendGump(new AdminGump(from, AdminGumpPage.Firewall, 0, results, + $"Search results for : {match}", m_State)); + else + from.SendGump(new AdminGump(from, m_PageType, m_ListPage, m_List, + notice ?? "Nothing matched your search terms.", m_State)); + + break; + } + case 1: + { + TextRelay relay = info.GetTextEntry(0); + string text = relay?.Text.Trim(); + + if (text == null || text.Length == 0) + { + from.SendGump(new AdminGump(from, m_PageType, m_ListPage, m_List, + "You must enter an address or pattern to add.", m_State)); + } + else if (!Utility.IsValidIP(text)) + { + from.SendGump(new AdminGump(from, m_PageType, m_ListPage, m_List, + "That is not a valid address or pattern.", m_State)); + } + else + { + object toAdd = Firewall.ToFirewallEntry(text); + + CommandLogging.WriteLine(from, "{0} {1} firewalling {2}", from.AccessLevel, + CommandLogging.Format(from), toAdd); + + Firewall.Add(toAdd); + from.SendGump(new AdminGump(from, AdminGumpPage.FirewallInfo, 0, null, + $"{toAdd} : Added to firewall.", toAdd)); + } + + break; + } + case 2: + { + InvokeCommand("Firewall"); + from.SendGump(new AdminGump(from, m_PageType, m_ListPage, m_List, + "Target the player to firewall.", m_State)); + break; + } + case 3: + { + if (m_State is Firewall.IFirewallEntry) + { + CommandLogging.WriteLine(from, "{0} {1} removing {2} from firewall list", from.AccessLevel, + CommandLogging.Format(from), m_State); + + Firewall.Remove(m_State); + from.SendGump(new AdminGump(from, AdminGumpPage.Firewall, 0, null, + $"{m_State} : Removed from firewall.", null)); + } + + break; + } + default: + { + index -= 4; + + if (m_List != null && index >= 0 && index < m_List.Count) + from.SendGump(new AdminGump(from, AdminGumpPage.FirewallInfo, 0, null, null, m_List[index])); + + break; + } + } + + break; + } + case 7: + { + Mobile m = m_State as Mobile; + + if (m == null) + break; + + string notice = null; + bool sendGump = true; + + switch (index) + { + case 0: + { + Map map = m.Map; + Point3D loc = m.Location; + + if (map == null || map == Map.Internal) + { + map = m.LogoutMap; + loc = m.LogoutLocation; + } + + if (map != null && map != Map.Internal) + { + from.MoveToWorld(loc, map); + notice = "You have been teleported to their location."; + } + + break; + } + case 1: + { + m.MoveToWorld(from.Location, from.Map); + notice = "They have been teleported to your location."; + break; + } + case 2: + { + NetState ns = m.NetState; + + if (ns != null) + { + CommandLogging.WriteLine(from, "{0} {1} {2} {3}", from.AccessLevel, + CommandLogging.Format(from), "kicking", CommandLogging.Format(m)); + ns.Dispose(); + notice = "They have been kicked."; + } + else + { + notice = "They are already disconnected."; + } + + break; + } + case 3: + { + if (m.Account is Account a) + { + CommandLogging.WriteLine(from, "{0} {1} {2} {3}", from.AccessLevel, + CommandLogging.Format(from), "banning", CommandLogging.Format(m)); + a.Banned = true; + + NetState ns = m.NetState; + + ns?.Dispose(); + + notice = "They have been banned."; + } + + break; + } + case 6: + { + Properties.SetValue(from, m, "Blessed", "False"); + notice = "They are now mortal."; + break; + } + case 7: + { + Properties.SetValue(from, m, "Blessed", "True"); + notice = "They are now immortal."; + break; + } + case 8: + { + Properties.SetValue(from, m, "Squelched", "True"); + notice = "They are now squelched."; + break; + } + case 9: + { + Properties.SetValue(from, m, "Squelched", "False"); + notice = "They are now unsquelched."; + break; + } + case 10: + { + Properties.SetValue(from, m, "Hidden", "True"); + notice = "They are now hidden."; + break; + } + case 11: + { + Properties.SetValue(from, m, "Hidden", "False"); + notice = "They are now unhidden."; + break; + } + case 12: + { + CommandLogging.WriteLine(from, "{0} {1} killing {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(m)); + m.Kill(); + notice = "They have been killed."; + break; + } + case 13: + { + CommandLogging.WriteLine(from, "{0} {1} resurrecting {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(m)); + m.Resurrect(); + notice = "They have been resurrected."; + break; + } + case 14: + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Information, 0, null, null, + m.Account)); + sendGump = false; + break; + } + } + + if (sendGump) + from.SendGump(new AdminGump(from, AdminGumpPage.ClientInfo, 0, null, notice, m_State)); + + switch (index) + { + case 3: + { + if (m.Account is Account a) + from.SendGump(new BanDurationGump(a)); + + break; + } + case 4: + { + from.SendGump(new PropertiesGump(from, m)); + break; + } + case 5: + { + from.SendGump(new SkillsGump(from, m)); + break; + } + } + + break; + } + case 8: + { + if (m_List != null && index >= 0 && index < m_List.Count) + { + Account a = m_State as Account; + + if (a == null) + break; + + if (m_PageType == AdminGumpPage.AccountDetails_Access_ClientIPs) + { + from.SendGump(new WarningGump(1060635, 30720, + $"You are about to firewall {m_List[index]}. All connection attempts from a matching IP will be refused. Are you sure?", + 0xFFC000, 420, 280, Firewall_Callback, new[] { a, m_List[index] })); + } + else if (m_PageType == AdminGumpPage.AccountDetails_Access_Restrictions) + { + ArrayList list = new ArrayList(a.IPRestrictions); + + list.Remove(m_List[index]); + + a.IPRestrictions = (string[])list.ToArray(typeof(string)); + + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_Restrictions, 0, null, + $"{m_List[index]} : Removed from list.", a)); + } + } + + break; + } + case 9: + { + if (m_List != null && index >= 0 && index < m_List.Count) + if (m_PageType == AdminGumpPage.AccountDetails_Access_ClientIPs) + { + object obj = m_List[index]; + + if (!(obj is IPAddress)) + break; + + Account a = m_State as Account; + + if (a == null) + break; + + ArrayList list = GetSharedAccounts((IPAddress)obj); + + if (list.Count > 1 || list.Count == 1 && !list.Contains(a)) + from.SendGump(new AdminGump(from, AdminGumpPage.Accounts, 0, list, null, new ArrayList())); + else + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Access_ClientIPs, 0, null, + "There are no other accounts which share that address.", m_State)); + } + + break; + } + case 10: + { + if (m_List != null && index >= 0 && index < m_List.Count) + if (m_PageType == AdminGumpPage.AccountDetails_Access_ClientIPs) + { + IPAddress ip = m_List[index] as IPAddress; + + if (ip == null) + break; + + Account a = m_State as Account; + + if (a == null) + break; + + from.SendGump(new WarningGump(1060635, 30720, + $"You are about to remove address {ip} from account {a}. Do you wish to continue?", 0xFFC000, + 420, 280, RemoveLoginIP_Callback, new object[] { a, ip })); + } + + break; + } + } + } + + private void Shutdown(bool restart, bool save) + { + CommandLogging.WriteLine(m_From, "{0} {1} shutting down server (Restart: {2}) (Save: {3})", m_From.AccessLevel, + CommandLogging.Format(m_From), restart, save); + + if (save) + InvokeCommand("Save"); + + Core.Kill(restart); + } + + private void InvokeCommand(string c) + { + CommandSystem.Handle(m_From, $"{CommandSystem.Prefix}{c}"); + } + + public static void GetAccountInfo(Account a, out AccessLevel accessLevel, out bool online) + { + accessLevel = a.AccessLevel; + online = false; + + for (int j = 0; j < a.Length; ++j) + { + Mobile check = a[j]; + + if (check == null) + continue; + + if (check.AccessLevel > accessLevel) + accessLevel = check.AccessLevel; + + if (check.NetState != null) + online = true; + } + } + + private class SharedAccountComparer : IComparer + { + public static readonly IComparer Instance = new SharedAccountComparer(); + + public int Compare(object x, object y) + { + DictionaryEntry a = (DictionaryEntry)x; + DictionaryEntry b = (DictionaryEntry)y; + + ArrayList aList = (ArrayList)a.Value; + ArrayList bList = (ArrayList)b.Value; + + return bList.Count - aList.Count; + } + } + + private class AddCommentPrompt : Prompt + { + private Account m_Account; + + public AddCommentPrompt(Account acct) + { + m_Account = acct; + } + + public override void OnCancel(Mobile from) + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Comments, 0, null, + "Request to add comment was canceled.", m_Account)); + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Account != null) + { + m_Account.Comments.Add(new AccountComment(from.RawName, text)); + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Comments, 0, null, "Comment added.", + m_Account)); + } + } + } + + private class AddTagNamePrompt : Prompt + { + private Account m_Account; + + public AddTagNamePrompt(Account acct) + { + m_Account = acct; + } + + public override void OnCancel(Mobile from) + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Tags, 0, null, + "Request to add tag was canceled.", m_Account)); + } + + public override void OnResponse(Mobile from, string text) + { + from.Prompt = new AddTagValuePrompt(m_Account, text); + from.SendMessage("Enter the new tag value."); + } + } + + private class AddTagValuePrompt : Prompt + { + private Account m_Account; + private string m_Name; + + public AddTagValuePrompt(Account acct, string name) + { + m_Account = acct; + m_Name = name; + } + + public override void OnCancel(Mobile from) + { + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Tags, 0, null, + "Request to add tag was canceled.", m_Account)); + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Account != null) + { + m_Account.AddTag(m_Name, text); + from.SendGump(new AdminGump(from, AdminGumpPage.AccountDetails_Tags, 0, null, "Tag added.", m_Account)); + } + } + } + + private class NetStateComparer : IComparer + { + public static readonly IComparer Instance = new NetStateComparer(); + + public int Compare(object x, object y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + if (!(x is NetState a) || !(y is NetState b)) + throw new ArgumentException(); + + Mobile aMob = a.Mobile; + Mobile bMob = b.Mobile; + + if (aMob == null && bMob == null) + return 0; + if (aMob == null) + return 1; + if (bMob == null) + return -1; + + if (aMob.AccessLevel > bMob.AccessLevel) + return -1; + if (aMob.AccessLevel < bMob.AccessLevel) + return 1; + return Insensitive.Compare(aMob.Name, bMob.Name); + } + } + + private class AccountComparer : IComparer + { + public static readonly IComparer Instance = new AccountComparer(); + + public int Compare(object x, object y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + if (!(x is Account a) || !(y is Account b)) + throw new ArgumentException(); + + GetAccountInfo(a, out AccessLevel aLevel, out bool aOnline); + GetAccountInfo(b, out AccessLevel bLevel, out bool bOnline); + + if (aOnline && !bOnline) + return -1; + if (bOnline && !aOnline) + return 1; + if (aLevel > bLevel) + return -1; + if (aLevel < bLevel) + return 1; + return Insensitive.Compare(a.Username, b.Username); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/BanDurationGump.cs b/Scripts/Gumps/BanDurationGump.cs index 8cfe907f3..e25e9a2c7 100644 --- a/Scripts/Gumps/BanDurationGump.cs +++ b/Scripts/Gumps/BanDurationGump.cs @@ -1,253 +1,247 @@ using System; using System.Collections; using Server.Accounting; +using Server.Network; namespace Server.Gumps { - public class BanDurationGump : Gump - { - private ArrayList m_List; + public class BanDurationGump : Gump + { + private ArrayList m_List; - public void AddButtonLabeled( int x, int y, int buttonID, string text ) - { - AddButton( x, y - 1, 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - AddHtml( x + 35, y, 240, 20, text, false, false ); - } + public BanDurationGump(Account a) : this(MakeList(a)) + { + } - public void AddTextField( int x, int y, int width, int height, int index ) - { - AddBackground( x - 2, y - 2, width + 4, height + 4, 0x2486 ); - AddTextEntry( x + 2, y + 2, width - 4, height - 4, 0, index, "" ); - } + public BanDurationGump(ArrayList list) : base((640 - 500) / 2, (480 - 305) / 2) + { + m_List = list; - public static ArrayList MakeList( object obj ) - { - ArrayList list = new ArrayList( 1 ); - list.Add( obj ); - return list; - } + int width = 500; + int height = 305; - public BanDurationGump( Account a ) : this( MakeList( a ) ) - { - } + AddPage(0); - public BanDurationGump( ArrayList list ) : base( (640 - 500) / 2, (480 - 305) / 2 ) - { - m_List = list; + AddBackground(0, 0, width, height, 5054); - int width = 500; - int height = 305; + //AddImageTiled( 10, 10, width - 20, 20, 2624 ); + //AddAlphaRegion( 10, 10, width - 20, 20 ); + AddHtml(10, 10, width - 20, 20, "
Ban Duration
", false, false); - AddPage( 0 ); + //AddImageTiled( 10, 40, width - 20, height - 50, 2624 ); + //AddAlphaRegion( 10, 40, width - 20, height - 50 ); - AddBackground( 0, 0, width, height, 5054 ); + AddButtonLabeled(15, 45, 1, "Infinite"); + AddButtonLabeled(15, 65, 2, "From D:H:M:S"); - //AddImageTiled( 10, 10, width - 20, 20, 2624 ); - //AddAlphaRegion( 10, 10, width - 20, 20 ); - AddHtml( 10, 10, width - 20, 20, "
Ban Duration
", false, false ); + AddInput(3, 0, "Days"); + AddInput(4, 1, "Hours"); + AddInput(5, 2, "Minutes"); + AddInput(6, 3, "Seconds"); - //AddImageTiled( 10, 40, width - 20, height - 50, 2624 ); - //AddAlphaRegion( 10, 40, width - 20, height - 50 ); + AddHtml(170, 45, 240, 20, "Comments:", false, false); + AddTextField(170, 65, 315, height - 80, 10); + } - AddButtonLabeled( 15, 45, 1, "Infinite" ); - AddButtonLabeled( 15, 65, 2, "From D:H:M:S" ); + public void AddButtonLabeled(int x, int y, int buttonID, string text) + { + AddButton(x, y - 1, 4005, 4007, buttonID, GumpButtonType.Reply, 0); + AddHtml(x + 35, y, 240, 20, text, false, false); + } - AddInput( 3, 0, "Days" ); - AddInput( 4, 1, "Hours" ); - AddInput( 5, 2, "Minutes" ); - AddInput( 6, 3, "Seconds" ); + public void AddTextField(int x, int y, int width, int height, int index) + { + AddBackground(x - 2, y - 2, width + 4, height + 4, 0x2486); + AddTextEntry(x + 2, y + 2, width - 4, height - 4, 0, index, ""); + } - AddHtml( 170, 45, 240, 20, "Comments:", false, false ); - AddTextField( 170, 65, 315, height - 80, 10 ); - } + public static ArrayList MakeList(object obj) + { + ArrayList list = new ArrayList(1); + list.Add(obj); + return list; + } - public void AddInput( int bid, int idx, string name ) - { - int x = 15; - int y = 95 + (idx * 50); + public void AddInput(int bid, int idx, string name) + { + int x = 15; + int y = 95 + idx * 50; - AddButtonLabeled( x, y, bid, name ); - AddTextField( x + 35, y + 20, 100, 20, idx ); - } + AddButtonLabeled(x, y, bid, name); + AddTextField(x + 35, y + 20, 100, 20, idx); + } - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - if ( from.AccessLevel < AccessLevel.Administrator ) - return; + if (from.AccessLevel < AccessLevel.Administrator) + return; - TextRelay d = info.GetTextEntry( 0 ); - TextRelay h = info.GetTextEntry( 1 ); - TextRelay m = info.GetTextEntry( 2 ); - TextRelay s = info.GetTextEntry( 3 ); + TextRelay d = info.GetTextEntry(0); + TextRelay h = info.GetTextEntry(1); + TextRelay m = info.GetTextEntry(2); + TextRelay s = info.GetTextEntry(3); - TextRelay c = info.GetTextEntry( 10 ); + TextRelay c = info.GetTextEntry(10); - TimeSpan duration; - bool shouldSet; + TimeSpan duration; + bool shouldSet; - string fromString = from.ToString(); + string fromString = from.ToString(); - switch ( info.ButtonID ) - { - case 0: - { - for ( int i = 0; i < m_List.Count; ++i ) - { - Account a = (Account)m_List[i]; + switch (info.ButtonID) + { + case 0: + { + for (int i = 0; i < m_List.Count; ++i) + { + Account a = (Account)m_List[i]; - a.SetUnspecifiedBan( from ); - } + a.SetUnspecifiedBan(from); + } - from.SendMessage( "Duration unspecified." ); - return; - } - case 1: // infinite - { - duration = TimeSpan.MaxValue; - shouldSet = true; - break; - } - case 2: // From D:H:M:S - { - if ( d != null && h != null && m != null && s != null ) - { - try - { - duration = new TimeSpan( Utility.ToInt32( d.Text ), Utility.ToInt32( h.Text ), Utility.ToInt32( m.Text ), Utility.ToInt32( s.Text ) ); - shouldSet = true; + from.SendMessage("Duration unspecified."); + return; + } + case 1: // infinite + { + duration = TimeSpan.MaxValue; + shouldSet = true; + break; + } + case 2: // From D:H:M:S + { + if (d != null && h != null && m != null && s != null) + try + { + duration = new TimeSpan(Utility.ToInt32(d.Text), Utility.ToInt32(h.Text), + Utility.ToInt32(m.Text), Utility.ToInt32(s.Text)); + shouldSet = true; - break; - } - catch - { - } - } + break; + } + catch + { + } - duration = TimeSpan.Zero; - shouldSet = false; + duration = TimeSpan.Zero; + shouldSet = false; - break; - } - case 3: // From D - { - if ( d != null ) - { - try - { - duration = TimeSpan.FromDays( Utility.ToDouble( d.Text ) ); - shouldSet = true; + break; + } + case 3: // From D + { + if (d != null) + try + { + duration = TimeSpan.FromDays(Utility.ToDouble(d.Text)); + shouldSet = true; - break; - } - catch - { - } - } + break; + } + catch + { + } - duration = TimeSpan.Zero; - shouldSet = false; + duration = TimeSpan.Zero; + shouldSet = false; - break; - } - case 4: // From H - { - if ( h != null ) - { - try - { - duration = TimeSpan.FromHours( Utility.ToDouble( h.Text ) ); - shouldSet = true; + break; + } + case 4: // From H + { + if (h != null) + try + { + duration = TimeSpan.FromHours(Utility.ToDouble(h.Text)); + shouldSet = true; - break; - } - catch - { - } - } + break; + } + catch + { + } - duration = TimeSpan.Zero; - shouldSet = false; + duration = TimeSpan.Zero; + shouldSet = false; - break; - } - case 5: // From M - { - if ( m != null ) - { - try - { - duration = TimeSpan.FromMinutes( Utility.ToDouble( m.Text ) ); - shouldSet = true; + break; + } + case 5: // From M + { + if (m != null) + try + { + duration = TimeSpan.FromMinutes(Utility.ToDouble(m.Text)); + shouldSet = true; - break; - } - catch - { - } - } + break; + } + catch + { + } - duration = TimeSpan.Zero; - shouldSet = false; + duration = TimeSpan.Zero; + shouldSet = false; - break; - } - case 6: // From S - { - if ( s != null ) - { - try - { - duration = TimeSpan.FromSeconds( Utility.ToDouble( s.Text ) ); - shouldSet = true; + break; + } + case 6: // From S + { + if (s != null) + try + { + duration = TimeSpan.FromSeconds(Utility.ToDouble(s.Text)); + shouldSet = true; - break; - } - catch - { - } - } + break; + } + catch + { + } - duration = TimeSpan.Zero; - shouldSet = false; + duration = TimeSpan.Zero; + shouldSet = false; - break; - } - default: return; - } + break; + } + default: return; + } - if ( shouldSet ) { - string comment = null; - - if ( c != null ) { - comment = c.Text.Trim(); + if (shouldSet) + { + string comment = null; - if ( comment.Length == 0 ) - comment = null; - } + if (c != null) + { + comment = c.Text.Trim(); - for ( int i = 0; i < m_List.Count; ++i ) - { - Account a = (Account)m_List[i]; + if (comment.Length == 0) + comment = null; + } - a.SetBanTags( from, DateTime.UtcNow, duration ); + for (int i = 0; i < m_List.Count; ++i) + { + Account a = (Account)m_List[i]; - if ( comment != null ) - a.Comments.Add( new AccountComment( from.RawName, - $"Duration: {((duration == TimeSpan.MaxValue) ? "Infinite" : duration.ToString())}, Comment: {comment}") ); - } + a.SetBanTags(from, DateTime.UtcNow, duration); - if ( duration == TimeSpan.MaxValue ) - from.SendMessage( "Ban Duration: Infinite" ); - else - from.SendMessage( "Ban Duration: {0}", duration ); - } - else - { - from.SendMessage( "Time values were improperly formatted." ); - from.SendGump( new BanDurationGump( m_List ) ); - } - } - } + if (comment != null) + a.Comments.Add(new AccountComment(from.RawName, + $"Duration: {(duration == TimeSpan.MaxValue ? "Infinite" : duration.ToString())}, Comment: {comment}")); + } + + if (duration == TimeSpan.MaxValue) + from.SendMessage("Ban Duration: Infinite"); + else + from.SendMessage("Ban Duration: {0}", duration); + } + else + { + from.SendMessage("Time values were improperly formatted."); + from.SendGump(new BanDurationGump(m_List)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/BaseConfirmGump.cs b/Scripts/Gumps/BaseConfirmGump.cs index 9b95900c1..b623f0c24 100644 --- a/Scripts/Gumps/BaseConfirmGump.cs +++ b/Scripts/Gumps/BaseConfirmGump.cs @@ -1,77 +1,79 @@ +using Server.Network; + namespace Server.Gumps { - public class BaseConfirmGump : Gump - { - public virtual int TitleNumber //
Warning!
- => 1075083; + public class BaseConfirmGump : Gump + { + public BaseConfirmGump() : base(120, 50) + { + Closable = false; + Disposable = true; + Dragable = true; + Resizable = false; - public virtual int LabelNumber // Are you sure you wish to select this? - => 1074975; + AddPage(0); - private enum Buttons - { - Close, - Break, - Confirm - } - - public BaseConfirmGump() : base( 120, 50 ) - { - Closable = false; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddImageTiled( 0, 0, 348, 262, 0xA8E ); - AddAlphaRegion( 0, 0, 348, 262 ); - AddImage( 0, 15, 0x27A8 ); - AddImageTiled( 0, 30, 17, 200, 0x27A7 ); - AddImage( 0, 230, 0x27AA ); - AddImage( 15, 230, 0x280C ); - AddImageTiled( 30, 0, 300, 17, 0x280A ); - AddImage( 315, 0, 0x280E ); - AddImage( 15, 244, 0x280C ); - AddImageTiled( 30, 244, 300, 17, 0x280A ); - AddImage( 315, 244, 0x280E ); - AddImage( 330, 15, 0x27A8 ); - AddImageTiled( 330, 30, 17, 200, 0x27A7 ); - AddImage( 330, 230, 0x27AA ); - AddImage( 333, 2, 0x2716 ); - AddImage( 315, 248, 0x2716 ); - AddImage( 2, 248, 0x2716 ); - AddImage( 2, 2, 0x2716 ); - AddHtmlLocalized( 25, 25, 200, 20, TitleNumber, 0x7D00, false, false ); - AddImage( 25, 40, 0xBBF ); - AddHtmlLocalized( 25, 55, 300, 120, LabelNumber, 0xFFFFFF, false, false ); - - AddRadio( 25, 175, 0x25F8, 0x25FB, true, (int) Buttons.Break ); - AddRadio( 25, 210, 0x25F8, 0x25FB, false, (int) Buttons.Close ); - - AddHtmlLocalized( 60, 180, 280, 20, 1074976, 0xFFFFFF, false, false ); - AddHtmlLocalized( 60, 215, 280, 20, 1074977, 0xFFFFFF, false, false ); - - AddButton( 265, 220, 0xF7, 0xF8, (int) Buttons.Confirm, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( Network.NetState state, RelayInfo info ) - { - if ( info.ButtonID == (int) Buttons.Confirm ) - { - if ( info.IsSwitched( (int) Buttons.Break ) ) - Confirm( state.Mobile ); - else - Refuse( state.Mobile ); - } - } - - public virtual void Confirm( Mobile from ) - { - } - - public virtual void Refuse( Mobile from ) - { - } - } -} + AddImageTiled(0, 0, 348, 262, 0xA8E); + AddAlphaRegion(0, 0, 348, 262); + AddImage(0, 15, 0x27A8); + AddImageTiled(0, 30, 17, 200, 0x27A7); + AddImage(0, 230, 0x27AA); + AddImage(15, 230, 0x280C); + AddImageTiled(30, 0, 300, 17, 0x280A); + AddImage(315, 0, 0x280E); + AddImage(15, 244, 0x280C); + AddImageTiled(30, 244, 300, 17, 0x280A); + AddImage(315, 244, 0x280E); + AddImage(330, 15, 0x27A8); + AddImageTiled(330, 30, 17, 200, 0x27A7); + AddImage(330, 230, 0x27AA); + AddImage(333, 2, 0x2716); + AddImage(315, 248, 0x2716); + AddImage(2, 248, 0x2716); + AddImage(2, 2, 0x2716); + AddHtmlLocalized(25, 25, 200, 20, TitleNumber, 0x7D00, false, false); + AddImage(25, 40, 0xBBF); + AddHtmlLocalized(25, 55, 300, 120, LabelNumber, 0xFFFFFF, false, false); + + AddRadio(25, 175, 0x25F8, 0x25FB, true, (int)Buttons.Break); + AddRadio(25, 210, 0x25F8, 0x25FB, false, (int)Buttons.Close); + + AddHtmlLocalized(60, 180, 280, 20, 1074976, 0xFFFFFF, false, false); + AddHtmlLocalized(60, 215, 280, 20, 1074977, 0xFFFFFF, false, false); + + AddButton(265, 220, 0xF7, 0xF8, (int)Buttons.Confirm, GumpButtonType.Reply, 0); + } + + public virtual int TitleNumber //
Warning!
+ => 1075083; + + public virtual int LabelNumber // Are you sure you wish to select this? + => 1074975; + + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == (int)Buttons.Confirm) + { + if (info.IsSwitched((int)Buttons.Break)) + Confirm(state.Mobile); + else + Refuse(state.Mobile); + } + } + + public virtual void Confirm(Mobile from) + { + } + + public virtual void Refuse(Mobile from) + { + } + + private enum Buttons + { + Close, + Break, + Confirm + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/BaseGridGump.cs b/Scripts/Gumps/BaseGridGump.cs index 61ceb7583..0c96b98b2 100644 --- a/Scripts/Gumps/BaseGridGump.cs +++ b/Scripts/Gumps/BaseGridGump.cs @@ -1,185 +1,188 @@ -using System; - namespace Server.Gumps { - public abstract class BaseGridGump : Gump - { - protected GumpBackground m_Background; - protected GumpImageTiled m_Offset; + public abstract class BaseGridGump : Gump + { + public const int ArrowLeftID1 = 0x15E3; + public const int ArrowLeftID2 = 0x15E7; + public const int ArrowLeftWidth = 16; + public const int ArrowLeftHeight = 16; - public int CurrentPage { get; private set; } + public const int ArrowRightID1 = 0x15E1; + public const int ArrowRightID2 = 0x15E5; + public const int ArrowRightWidth = 16; + public const int ArrowRightHeight = 16; + protected GumpBackground m_Background; + protected GumpImageTiled m_Offset; - public int CurrentX { get; private set; } + public BaseGridGump(int x, int y) : base(x, y) + { + } - public int CurrentY { get; private set; } + public int CurrentPage{ get; private set; } - public BaseGridGump( int x, int y ) : base( x, y ) - { - } + public int CurrentX{ get; private set; } - public virtual int BorderSize => 10; - public virtual int OffsetSize => 1; + public int CurrentY{ get; private set; } - public virtual int EntryHeight => 20; + public virtual int BorderSize => 10; + public virtual int OffsetSize => 1; - public virtual int OffsetGumpID => 0x0A40; - public virtual int HeaderGumpID => 0x0E14; - public virtual int EntryGumpID => 0x0BBC; - public virtual int BackGumpID => 0x13BE; + public virtual int EntryHeight => 20; - public virtual int TextHue => 0; - public virtual int TextOffsetX => 2; + public virtual int OffsetGumpID => 0x0A40; + public virtual int HeaderGumpID => 0x0E14; + public virtual int EntryGumpID => 0x0BBC; + public virtual int BackGumpID => 0x13BE; - public const int ArrowLeftID1 = 0x15E3; - public const int ArrowLeftID2 = 0x15E7; - public const int ArrowLeftWidth = 16; - public const int ArrowLeftHeight = 16; + public virtual int TextHue => 0; + public virtual int TextOffsetX => 2; - public const int ArrowRightID1 = 0x15E1; - public const int ArrowRightID2 = 0x15E5; - public const int ArrowRightWidth = 16; - public const int ArrowRightHeight = 16; + public string Center(string text) + { + return $"
{text}
"; + } - public string Center( string text ) - { - return $"
{text}
"; - } + public string Color(string text, int color) + { + return $"{text}"; + } - public string Color( string text, int color ) - { - return $"{text}"; - } + public int GetButtonID(int typeCount, int type, int index) + { + return 1 + index * typeCount + type; + } - public int GetButtonID( int typeCount, int type, int index ) - { - return 1 + (index * typeCount) + type; - } + public bool SplitButtonID(int buttonID, int typeCount, out int type, out int index) + { + if (buttonID < 1) + { + type = 0; + index = 0; + return false; + } - public bool SplitButtonID( int buttonID, int typeCount, out int type, out int index ) - { - if ( buttonID < 1 ) - { - type = 0; - index = 0; - return false; - } + buttonID -= 1; - buttonID -= 1; + type = buttonID % typeCount; + index = buttonID / typeCount; - type = buttonID % typeCount; - index = buttonID / typeCount; + return true; + } - return true; - } + public void FinishPage() + { + if (m_Background != null) + m_Background.Height = CurrentY + EntryHeight + OffsetSize + BorderSize; - public void FinishPage() - { - if ( m_Background != null ) - m_Background.Height = CurrentY + EntryHeight + OffsetSize + BorderSize; + if (m_Offset != null) + m_Offset.Height = CurrentY + EntryHeight + OffsetSize - BorderSize; + } - if ( m_Offset != null ) - m_Offset.Height = CurrentY + EntryHeight + OffsetSize - BorderSize; - } + public void AddNewPage() + { + FinishPage(); - public void AddNewPage() - { - FinishPage(); + CurrentX = BorderSize + OffsetSize; + CurrentY = BorderSize + OffsetSize; - CurrentX = BorderSize + OffsetSize; - CurrentY = BorderSize + OffsetSize; + AddPage(++CurrentPage); - AddPage( ++CurrentPage ); + m_Background = new GumpBackground(0, 0, 100, 100, BackGumpID); + Add(m_Background); - m_Background = new GumpBackground( 0, 0, 100, 100, BackGumpID ); - Add( m_Background ); + m_Offset = new GumpImageTiled(BorderSize, BorderSize, 100, 100, OffsetGumpID); + Add(m_Offset); + } - m_Offset = new GumpImageTiled( BorderSize, BorderSize, 100, 100, OffsetGumpID ); - Add( m_Offset ); - } + public void AddNewLine() + { + CurrentY += EntryHeight + OffsetSize; + CurrentX = BorderSize + OffsetSize; + } - public void AddNewLine() - { - CurrentY += EntryHeight + OffsetSize; - CurrentX = BorderSize + OffsetSize; - } + public void IncreaseX(int width) + { + CurrentX += width + OffsetSize; - public void IncreaseX( int width ) - { - CurrentX += width + OffsetSize; + width = CurrentX + BorderSize; - width = CurrentX + BorderSize; + if (m_Background != null && width > m_Background.Width) + m_Background.Width = width; - if ( m_Background != null && width > m_Background.Width ) - m_Background.Width = width; + width = CurrentX - BorderSize; - width = CurrentX - BorderSize; + if (m_Offset != null && width > m_Offset.Width) + m_Offset.Width = width; + } - if ( m_Offset != null && width > m_Offset.Width ) - m_Offset.Width = width; - } + public void AddEntryLabel(int width, string text) + { + AddImageTiled(CurrentX, CurrentY, width, EntryHeight, EntryGumpID); + AddLabelCropped(CurrentX + TextOffsetX, CurrentY, width - TextOffsetX, EntryHeight, TextHue, text); - public void AddEntryLabel( int width, string text ) - { - AddImageTiled( CurrentX, CurrentY, width, EntryHeight, EntryGumpID ); - AddLabelCropped( CurrentX + TextOffsetX, CurrentY, width - TextOffsetX, EntryHeight, TextHue, text ); + IncreaseX(width); + } - IncreaseX( width ); - } + public void AddEntryHtml(int width, string text) + { + AddImageTiled(CurrentX, CurrentY, width, EntryHeight, EntryGumpID); + AddHtml(CurrentX + TextOffsetX, CurrentY, width - TextOffsetX, EntryHeight, text, false, false); - public void AddEntryHtml( int width, string text ) - { - AddImageTiled( CurrentX, CurrentY, width, EntryHeight, EntryGumpID ); - AddHtml( CurrentX + TextOffsetX, CurrentY, width - TextOffsetX, EntryHeight, text, false, false ); + IncreaseX(width); + } - IncreaseX( width ); - } + public void AddEntryHeader(int width) + { + AddEntryHeader(width, 1); + } - public void AddEntryHeader( int width ) - { - AddEntryHeader( width, 1 ); - } + public void AddEntryHeader(int width, int spannedEntries) + { + AddImageTiled(CurrentX, CurrentY, width, EntryHeight * spannedEntries + OffsetSize * (spannedEntries - 1), + HeaderGumpID); + IncreaseX(width); + } - public void AddEntryHeader( int width, int spannedEntries ) - { - AddImageTiled( CurrentX, CurrentY, width, (EntryHeight * spannedEntries) + (OffsetSize * (spannedEntries - 1)), HeaderGumpID ); - IncreaseX( width ); - } + public void AddBlankLine() + { + if (m_Offset != null) + AddImageTiled(m_Offset.X, CurrentY, m_Offset.Width, EntryHeight, BackGumpID + 4); - public void AddBlankLine() - { - if ( m_Offset != null ) - AddImageTiled( m_Offset.X, CurrentY, m_Offset.Width, EntryHeight, BackGumpID + 4 ); + AddNewLine(); + } - AddNewLine(); - } + public void AddEntryButton(int width, int normalID, int pressedID, int buttonID, int buttonWidth, int buttonHeight) + { + AddEntryButton(width, normalID, pressedID, buttonID, buttonWidth, buttonHeight, 1); + } - public void AddEntryButton( int width, int normalID, int pressedID, int buttonID, int buttonWidth, int buttonHeight ) - { - AddEntryButton( width, normalID, pressedID, buttonID, buttonWidth, buttonHeight, 1 ); - } + public void AddEntryButton(int width, int normalID, int pressedID, int buttonID, int buttonWidth, int buttonHeight, + int spannedEntries) + { + AddImageTiled(CurrentX, CurrentY, width, EntryHeight * spannedEntries + OffsetSize * (spannedEntries - 1), + HeaderGumpID); + AddButton(CurrentX + (width - buttonWidth) / 2, + CurrentY + (EntryHeight * spannedEntries + OffsetSize * (spannedEntries - 1) - buttonHeight) / 2, normalID, + pressedID, buttonID, GumpButtonType.Reply, 0); - public void AddEntryButton( int width, int normalID, int pressedID, int buttonID, int buttonWidth, int buttonHeight, int spannedEntries ) - { - AddImageTiled( CurrentX, CurrentY, width, (EntryHeight * spannedEntries) + (OffsetSize * (spannedEntries - 1)), HeaderGumpID ); - AddButton( CurrentX + ((width - buttonWidth) / 2), CurrentY + (((EntryHeight * spannedEntries) + (OffsetSize * (spannedEntries - 1)) - buttonHeight) / 2), normalID, pressedID, buttonID, GumpButtonType.Reply, 0 ); + IncreaseX(width); + } - IncreaseX( width ); - } + public void AddEntryPageButton(int width, int normalID, int pressedID, int page, int buttonWidth, int buttonHeight) + { + AddImageTiled(CurrentX, CurrentY, width, EntryHeight, HeaderGumpID); + AddButton(CurrentX + (width - buttonWidth) / 2, CurrentY + (EntryHeight - buttonHeight) / 2, normalID, pressedID, + 0, GumpButtonType.Page, page); - public void AddEntryPageButton( int width, int normalID, int pressedID, int page, int buttonWidth, int buttonHeight ) - { - AddImageTiled( CurrentX, CurrentY, width, EntryHeight, HeaderGumpID ); - AddButton( CurrentX + ((width - buttonWidth) / 2), CurrentY + ((EntryHeight - buttonHeight) / 2), normalID, pressedID, 0, GumpButtonType.Page, page ); + IncreaseX(width); + } - IncreaseX( width ); - } + public void AddEntryText(int width, int entryID, string initialText) + { + AddImageTiled(CurrentX, CurrentY, width, EntryHeight, EntryGumpID); + AddTextEntry(CurrentX + TextOffsetX, CurrentY, width - TextOffsetX, EntryHeight, TextHue, entryID, initialText); - public void AddEntryText( int width, int entryID, string initialText ) - { - AddImageTiled( CurrentX, CurrentY, width, EntryHeight, EntryGumpID ); - AddTextEntry( CurrentX + TextOffsetX, CurrentY, width - TextOffsetX, EntryHeight, TextHue, entryID, initialText ); - - IncreaseX( width ); - } - } + IncreaseX(width); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/BaseImageTileButtonsGump.cs b/Scripts/Gumps/BaseImageTileButtonsGump.cs index ea3622b74..c0af72931 100644 --- a/Scripts/Gumps/BaseImageTileButtonsGump.cs +++ b/Scripts/Gumps/BaseImageTileButtonsGump.cs @@ -1,127 +1,132 @@ -using Server.Network; using System.Collections; +using Server.Network; namespace Server.Gumps { - public class ImageTileButtonInfo - { - private int m_ItemID; - private int m_Hue; - private int m_LocalizedTooltip; + public class ImageTileButtonInfo + { + private int m_Hue; + private int m_ItemID; - private TextDefinition m_Label; + private TextDefinition m_Label; + private int m_LocalizedTooltip; - public virtual int ItemID - { - get => m_ItemID; - set => m_ItemID = value; - } - public virtual int Hue - { - get => m_Hue; - set => m_Hue = value; - } - public virtual int LocalizedTooltip - { - get => m_LocalizedTooltip; - set => m_LocalizedTooltip = value; - } + public ImageTileButtonInfo(int itemID, int hue, TextDefinition label, int localizedTooltip) + { + m_Hue = hue; + m_ItemID = itemID; + m_Label = label; + m_LocalizedTooltip = localizedTooltip; + } - public virtual TextDefinition Label - { - get => m_Label; - set => m_Label = value; - } + public ImageTileButtonInfo(int itemID, int hue, TextDefinition label) : this(itemID, hue, label, -1) + { + } - public ImageTileButtonInfo( int itemID, int hue, TextDefinition label, int localizedTooltip ) - { - m_Hue = hue; - m_ItemID = itemID; - m_Label = label; - m_LocalizedTooltip = localizedTooltip; - } - public ImageTileButtonInfo( int itemID, int hue, TextDefinition label ) : this( itemID, hue, label, -1 ) - { - } - } + public virtual int ItemID + { + get => m_ItemID; + set => m_ItemID = value; + } - public class BaseImageTileButtonsGump : Gump - { - protected ImageTileButtonInfo[] Buttons { get; } + public virtual int Hue + { + get => m_Hue; + set => m_Hue = value; + } - protected virtual int XItems => 2; - protected virtual int YItems => 5; + public virtual int LocalizedTooltip + { + get => m_LocalizedTooltip; + set => m_LocalizedTooltip = value; + } - public BaseImageTileButtonsGump( TextDefinition header, ArrayList buttons ) : this( header, (ImageTileButtonInfo[])buttons.ToArray( typeof( ImageTileButtonInfo ) ) ) - { - } - public BaseImageTileButtonsGump( TextDefinition header, ImageTileButtonInfo[] buttons ) : base( 10, 10 ) //Coords are 0, o on OSI, intentional difference - { - Buttons = buttons; - AddPage( 0 ); + public virtual TextDefinition Label + { + get => m_Label; + set => m_Label = value; + } + } - int x = XItems * 250; - int y = YItems * 64; + public class BaseImageTileButtonsGump : Gump + { + public BaseImageTileButtonsGump(TextDefinition header, ArrayList buttons) : this(header, + (ImageTileButtonInfo[])buttons.ToArray(typeof(ImageTileButtonInfo))) + { + } - AddBackground( 0, 0, x+20, y+84, 0x13BE ); - AddImageTiled( 10, 10, x, 20, 0xA40 ); - AddImageTiled( 10, 40, x, y+4, 0xA40 ); - AddImageTiled( 10, y+54, x, 20, 0xA40 ); - AddAlphaRegion( 10, 10, x, y+64 ); + public BaseImageTileButtonsGump(TextDefinition header, ImageTileButtonInfo[] buttons) : + base(10, 10) //Coords are 0, o on OSI, intentional difference + { + Buttons = buttons; + AddPage(0); - AddButton( 10, y+54, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); //Cancel Button - AddHtmlLocalized( 45, y+56, x-50, 20, 1060051, 0x7FFF, false, false ); // CANCEL - TextDefinition.AddHtmlText( this, 14, 12, x, 20, header, false, false, 0x7FFF, 0xFFFFFF ); + int x = XItems * 250; + int y = YItems * 64; - AddPage( 1 ); + AddBackground(0, 0, x + 20, y + 84, 0x13BE); + AddImageTiled(10, 10, x, 20, 0xA40); + AddImageTiled(10, 40, x, y + 4, 0xA40); + AddImageTiled(10, y + 54, x, 20, 0xA40); + AddAlphaRegion(10, 10, x, y + 64); - int itemsPerPage = XItems * YItems; + AddButton(10, y + 54, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); //Cancel Button + AddHtmlLocalized(45, y + 56, x - 50, 20, 1060051, 0x7FFF, false, false); // CANCEL + TextDefinition.AddHtmlText(this, 14, 12, x, 20, header, false, false, 0x7FFF, 0xFFFFFF); - for( int i = 0; i < buttons.Length; i++ ) - { - int position = i % itemsPerPage; + AddPage(1); - int innerX = (position % XItems) * 250 + 14; - int innerY = (position / XItems) * 64 + 44; + int itemsPerPage = XItems * YItems; - int pageNum = i / itemsPerPage + 1; + for (int i = 0; i < buttons.Length; i++) + { + int position = i % itemsPerPage; - if ( position == 0 && i != 0 ) - { - AddButton( x-100, y+54, 0xFA5, 0xFA7, 0, GumpButtonType.Page, pageNum ); - AddHtmlLocalized( x-60, y+56, 60, 20, 1043353, 0x7FFF, false, false ); // Next + int innerX = position % XItems * 250 + 14; + int innerY = position / XItems * 64 + 44; - AddPage( pageNum ); + int pageNum = i / itemsPerPage + 1; - AddButton( x-200, y+54, 0xFAE, 0xFB0, 0, GumpButtonType.Page, pageNum - 1 ); - AddHtmlLocalized( x-160, y+56, 60, 20, 1011393, 0x7FFF, false, false ); // Back + if (position == 0 && i != 0) + { + AddButton(x - 100, y + 54, 0xFA5, 0xFA7, 0, GumpButtonType.Page, pageNum); + AddHtmlLocalized(x - 60, y + 56, 60, 20, 1043353, 0x7FFF, false, false); // Next - } + AddPage(pageNum); - ImageTileButtonInfo b = buttons[i]; + AddButton(x - 200, y + 54, 0xFAE, 0xFB0, 0, GumpButtonType.Page, pageNum - 1); + AddHtmlLocalized(x - 160, y + 56, 60, 20, 1011393, 0x7FFF, false, false); // Back + } - AddImageTiledButton( innerX, innerY, 0x918, 0x919, 100 + i, GumpButtonType.Reply, 0, b.ItemID, b.Hue, 15, 10, b.LocalizedTooltip ); - TextDefinition.AddHtmlText( this, innerX + 84, innerY, 250, 60, b.Label, false, false, 0x7FFF, 0xFFFFFF ); - } - } + ImageTileButtonInfo b = buttons[i]; - public override void OnResponse( NetState sender, RelayInfo info ) - { - int adjustedID = info.ButtonID - 100; + AddImageTiledButton(innerX, innerY, 0x918, 0x919, 100 + i, GumpButtonType.Reply, 0, b.ItemID, b.Hue, 15, 10, + b.LocalizedTooltip); + TextDefinition.AddHtmlText(this, innerX + 84, innerY, 250, 60, b.Label, false, false, 0x7FFF, 0xFFFFFF); + } + } - if ( adjustedID >= 0 && adjustedID < Buttons.Length ) - HandleButtonResponse( sender, adjustedID, Buttons[adjustedID] ); - else - HandleCancel( sender ); + protected ImageTileButtonInfo[] Buttons{ get; } - } + protected virtual int XItems => 2; + protected virtual int YItems => 5; - public virtual void HandleButtonResponse( NetState sender, int adjustedButton, ImageTileButtonInfo buttonInfo ) - { - } + public override void OnResponse(NetState sender, RelayInfo info) + { + int adjustedID = info.ButtonID - 100; - public virtual void HandleCancel( NetState sender ) - { - } - } -} + if (adjustedID >= 0 && adjustedID < Buttons.Length) + HandleButtonResponse(sender, adjustedID, Buttons[adjustedID]); + else + HandleCancel(sender); + } + + public virtual void HandleButtonResponse(NetState sender, int adjustedButton, ImageTileButtonInfo buttonInfo) + { + } + + public virtual void HandleCancel(NetState sender) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/CategorizedAddGump.cs b/Scripts/Gumps/CategorizedAddGump.cs index 7e84a7dd4..b9e5c528e 100644 --- a/Scripts/Gumps/CategorizedAddGump.cs +++ b/Scripts/Gumps/CategorizedAddGump.cs @@ -1,382 +1,397 @@ using System; +using System.Collections; using System.IO; using System.Xml; -using System.Collections; -using Server.Network; using Server.Commands; +using Server.Network; namespace Server.Gumps { - public abstract class CAGNode - { - public abstract string Caption{ get; } - public abstract void OnClick( Mobile from, int page ); - } - - public class CAGObject : CAGNode - { - public Type Type { get; } - - public int ItemID { get; } - - public int Hue { get; } - - public CAGCategory Parent { get; } - - public override string Caption => ( Type == null ? "bad type" : Type.Name ); - - public override void OnClick( Mobile from, int page ) - { - if ( Type == null ) - { - from.SendMessage( "That is an invalid type name." ); - } - else - { - CommandSystem.Handle( from, $"{CommandSystem.Prefix}Add {Type.Name}"); - - from.SendGump( new CategorizedAddGump( from, Parent, page ) ); - } - } - - public CAGObject( CAGCategory parent, XmlTextReader xml ) - { - Parent = parent; - - if ( xml.MoveToAttribute( "type" ) ) - Type = ScriptCompiler.FindTypeByFullName( xml.Value, false ); - - if ( xml.MoveToAttribute( "gfx" ) ) - ItemID = XmlConvert.ToInt32( xml.Value ); - - if ( xml.MoveToAttribute( "hue" ) ) - Hue = XmlConvert.ToInt32( xml.Value ); - } - } - - public class CAGCategory : CAGNode - { - public string Title { get; } - - public CAGNode[] Nodes { get; } - - public CAGCategory Parent { get; } - - public override string Caption => Title; - - public override void OnClick( Mobile from, int page ) - { - from.SendGump( new CategorizedAddGump( from, this, 0 ) ); - } - - private CAGCategory() - { - Title = "no data"; - Nodes = new CAGNode[0]; - } - - public CAGCategory( CAGCategory parent, XmlTextReader xml ) - { - Parent = parent; - - if ( xml.MoveToAttribute( "title" ) ) - Title = xml.Value; - else - Title = "empty"; - - if ( Title == "Docked" ) - Title = "Docked 2"; - - if ( xml.IsEmptyElement ) - { - Nodes = new CAGNode[0]; - } - else - { - ArrayList nodes = new ArrayList(); - - while ( xml.Read() && xml.NodeType != XmlNodeType.EndElement ) - { - if ( xml.NodeType == XmlNodeType.Element && xml.Name == "object" ) - nodes.Add( new CAGObject( this, xml ) ); - else if ( xml.NodeType == XmlNodeType.Element && xml.Name == "category" ) - { - if ( !xml.IsEmptyElement ) - nodes.Add( new CAGCategory( this, xml ) ); - } - else - xml.Skip(); - } - - Nodes = (CAGNode[])nodes.ToArray( typeof( CAGNode ) ); - } - } + public abstract class CAGNode + { + public abstract string Caption{ get; } + public abstract void OnClick(Mobile from, int page); + } + + public class CAGObject : CAGNode + { + public CAGObject(CAGCategory parent, XmlTextReader xml) + { + Parent = parent; + + if (xml.MoveToAttribute("type")) + Type = ScriptCompiler.FindTypeByFullName(xml.Value, false); + + if (xml.MoveToAttribute("gfx")) + ItemID = XmlConvert.ToInt32(xml.Value); + + if (xml.MoveToAttribute("hue")) + Hue = XmlConvert.ToInt32(xml.Value); + } + + public Type Type{ get; } + + public int ItemID{ get; } + + public int Hue{ get; } + + public CAGCategory Parent{ get; } + + public override string Caption => Type == null ? "bad type" : Type.Name; + + public override void OnClick(Mobile from, int page) + { + if (Type == null) + { + from.SendMessage("That is an invalid type name."); + } + else + { + CommandSystem.Handle(from, $"{CommandSystem.Prefix}Add {Type.Name}"); + + from.SendGump(new CategorizedAddGump(from, Parent, page)); + } + } + } + + public class CAGCategory : CAGNode + { + private static CAGCategory m_Root; + + private CAGCategory() + { + Title = "no data"; + Nodes = new CAGNode[0]; + } + + public CAGCategory(CAGCategory parent, XmlTextReader xml) + { + Parent = parent; + + if (xml.MoveToAttribute("title")) + Title = xml.Value; + else + Title = "empty"; + + if (Title == "Docked") + Title = "Docked 2"; + + if (xml.IsEmptyElement) + { + Nodes = new CAGNode[0]; + } + else + { + ArrayList nodes = new ArrayList(); - private static CAGCategory m_Root; - - public static CAGCategory Root - { - get - { - if ( m_Root == null ) - m_Root = Load( "Data/objects.xml" ); + while (xml.Read() && xml.NodeType != XmlNodeType.EndElement) + if (xml.NodeType == XmlNodeType.Element && xml.Name == "object") + { + nodes.Add(new CAGObject(this, xml)); + } + else if (xml.NodeType == XmlNodeType.Element && xml.Name == "category") + { + if (!xml.IsEmptyElement) + nodes.Add(new CAGCategory(this, xml)); + } + else + { + xml.Skip(); + } - return m_Root; - } - } - - public static CAGCategory Load( string path ) - { - if ( File.Exists( path ) ) - { - XmlTextReader xml = new XmlTextReader( path ); + Nodes = (CAGNode[])nodes.ToArray(typeof(CAGNode)); + } + } - xml.WhitespaceHandling = WhitespaceHandling.None; + public string Title{ get; } - while ( xml.Read() ) - { - if ( xml.Name == "category" && xml.NodeType == XmlNodeType.Element ) - { - CAGCategory cat = new CAGCategory( null, xml ); + public CAGNode[] Nodes{ get; } - xml.Close(); + public CAGCategory Parent{ get; } - return cat; - } - } - } + public override string Caption => Title; - return new CAGCategory(); - } - } + public static CAGCategory Root + { + get + { + if (m_Root == null) + m_Root = Load("Data/objects.xml"); - public class CategorizedAddGump : Gump - { - public static bool OldStyle = PropsConfig.OldStyle; + return m_Root; + } + } - public static readonly int EntryHeight = 24;//PropsConfig.EntryHeight; + public override void OnClick(Mobile from, int page) + { + from.SendGump(new CategorizedAddGump(from, this, 0)); + } - public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int BorderSize = PropsConfig.BorderSize; + public static CAGCategory Load(string path) + { + if (File.Exists(path)) + { + XmlTextReader xml = new XmlTextReader(path); - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + xml.WhitespaceHandling = WhitespaceHandling.None; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + while (xml.Read()) + if (xml.Name == "category" && xml.NodeType == XmlNodeType.Element) + { + CAGCategory cat = new CAGCategory(null, xml); - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + xml.Close(); - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY + (((EntryHeight - 20) / 2) / 2); - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + return cat; + } + } - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY + (((EntryHeight - 20) / 2) / 2); - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + return new CAGCategory(); + } + } - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY + (((EntryHeight - 20) / 2) / 2); - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public class CategorizedAddGump : Gump + { + public static bool OldStyle = PropsConfig.OldStyle; - private static bool PrevLabel = false, NextLabel = false; + public static readonly int EntryHeight = 24; //PropsConfig.EntryHeight; - private static readonly int PrevLabelOffsetX = PrevWidth + 1; - private static readonly int PrevLabelOffsetY = 0; + public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int BorderSize = PropsConfig.BorderSize; - private static readonly int NextLabelOffsetX = -29; - private static readonly int NextLabelOffsetY = 0; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - private static readonly int EntryWidth = 180; - private static readonly int EntryCount = 15; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (EntryCount + 1)); + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + public static readonly int SetWidth = PropsConfig.SetWidth; - private Mobile m_Owner; - private CAGCategory m_Category; - private int m_Page; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, + SetOffsetY = PropsConfig.SetOffsetY + (EntryHeight - 20) / 2 / 2; - public CategorizedAddGump( Mobile owner ) : this( owner, CAGCategory.Root, 0 ) - { - } + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public CategorizedAddGump( Mobile owner, CAGCategory category, int page ) : base( GumpOffsetX, GumpOffsetY ) - { - owner.CloseGump( typeof( WhoGump ) ); + public static readonly int PrevWidth = PropsConfig.PrevWidth; - m_Owner = owner; - m_Category = category; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, + PrevOffsetY = PropsConfig.PrevOffsetY + (EntryHeight - 20) / 2 / 2; - Initialize( page ); - } + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public void Initialize( int page ) - { - m_Page = page; + public static readonly int NextWidth = PropsConfig.NextWidth; - CAGNode[] nodes = m_Category.Nodes; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, + NextOffsetY = PropsConfig.NextOffsetY + (EntryHeight - 20) / 2 / 2; - int count = nodes.Length - (page * EntryCount); + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - if ( count < 0 ) - count = 0; - else if ( count > EntryCount ) - count = EntryCount; + private static bool PrevLabel = false, NextLabel = false; - int totalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (count + 1)); + private static readonly int PrevLabelOffsetX = PrevWidth + 1; + private static readonly int PrevLabelOffsetY = 0; - AddPage( 0 ); + private static readonly int NextLabelOffsetX = -29; + private static readonly int NextLabelOffsetY = 0; - AddBackground( 0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, OffsetGumpID ); + private static readonly int EntryWidth = 180; + private static readonly int EntryCount = 15; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + (EntryHeight + OffsetSize) * (EntryCount + 1); - if ( OldStyle ) - AddImageTiled( x, y, TotalWidth - (OffsetSize * 3) - SetWidth, EntryHeight, HeaderGumpID ); - else - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private CAGCategory m_Category; - if ( m_Category.Parent != null ) - { - AddButton( x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 1, GumpButtonType.Reply, 0 ); + private Mobile m_Owner; + private int m_Page; - if ( PrevLabel ) - AddLabel( x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous" ); - } + public CategorizedAddGump(Mobile owner) : this(owner, CAGCategory.Root, 0) + { + } - x += PrevWidth + OffsetSize; + public CategorizedAddGump(Mobile owner, CAGCategory category, int page) : base(GumpOffsetX, GumpOffsetY) + { + owner.CloseGump(typeof(WhoGump)); - int emptyWidth = TotalWidth - (PrevWidth * 2) - NextWidth - (OffsetSize * 5) - (OldStyle ? SetWidth + OffsetSize : 0); + m_Owner = owner; + m_Category = category; - if ( !OldStyle ) - AddImageTiled( x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, EntryGumpID ); + Initialize(page); + } - AddHtml( x + TextOffsetX, y + ((EntryHeight - 20) / 2), emptyWidth - TextOffsetX, EntryHeight, - $"
{m_Category.Caption}
", false, false ); + public void Initialize(int page) + { + m_Page = page; - x += emptyWidth + OffsetSize; + CAGNode[] nodes = m_Category.Nodes; - if ( OldStyle ) - AddImageTiled( x, y, TotalWidth - (OffsetSize * 3) - SetWidth, EntryHeight, HeaderGumpID ); - else - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + int count = nodes.Length - page * EntryCount; - if ( page > 0 ) - { - AddButton( x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 2, GumpButtonType.Reply, 0 ); + if (count < 0) + count = 0; + else if (count > EntryCount) + count = EntryCount; - if ( PrevLabel ) - AddLabel( x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous" ); - } + int totalHeight = OffsetSize + (EntryHeight + OffsetSize) * (count + 1); - x += PrevWidth + OffsetSize; + AddPage(0); - if ( !OldStyle ) - AddImageTiled( x, y, NextWidth, EntryHeight, HeaderGumpID ); + AddBackground(0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, + OffsetGumpID); - if ( (page + 1) * EntryCount < nodes.Length ) - { - AddButton( x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 3, GumpButtonType.Reply, 1 ); + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - if ( NextLabel ) - AddLabel( x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next" ); - } + if (OldStyle) + AddImageTiled(x, y, TotalWidth - OffsetSize * 3 - SetWidth, EntryHeight, HeaderGumpID); + else + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); - for ( int i = 0, index = page * EntryCount; i < EntryCount && index < nodes.Length; ++i, ++index ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + if (m_Category.Parent != null) + { + AddButton(x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 1, GumpButtonType.Reply, 0); - CAGNode node = nodes[index]; + if (PrevLabel) + AddLabel(x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous"); + } - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y + ((EntryHeight - 20) / 2), EntryWidth - TextOffsetX, EntryHeight, TextHue, node.Caption ); + x += PrevWidth + OffsetSize; - x += EntryWidth + OffsetSize; + int emptyWidth = TotalWidth - PrevWidth * 2 - NextWidth - OffsetSize * 5 - + (OldStyle ? SetWidth + OffsetSize : 0); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + if (!OldStyle) + AddImageTiled(x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, + EntryGumpID); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, i + 4, GumpButtonType.Reply, 0 ); + AddHtml(x + TextOffsetX, y + (EntryHeight - 20) / 2, emptyWidth - TextOffsetX, EntryHeight, + $"
{m_Category.Caption}
", false, false); - if ( node is CAGObject obj ) - { - int itemID = obj.ItemID; + x += emptyWidth + OffsetSize; - Rectangle2D bounds = ItemBounds.Table[itemID]; + if (OldStyle) + AddImageTiled(x, y, TotalWidth - OffsetSize * 3 - SetWidth, EntryHeight, HeaderGumpID); + else + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); - if ( itemID != 1 && bounds.Height < (EntryHeight * 2) ) - { - if ( bounds.Height < EntryHeight ) - AddItem( x - OffsetSize - 22 - ((i % 2) * 44) - (bounds.Width / 2) - bounds.X, y + (EntryHeight / 2) - (bounds.Height / 2) - bounds.Y, itemID ); - else - AddItem( x - OffsetSize - 22 - ((i % 2) * 44) - (bounds.Width / 2) - bounds.X, y + EntryHeight - 1 - bounds.Height - bounds.Y, itemID ); - } - } - } - } + if (page > 0) + { + AddButton(x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 2, GumpButtonType.Reply, 0); - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = m_Owner; + if (PrevLabel) + AddLabel(x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous"); + } - switch ( info.ButtonID ) - { - case 0: // Closed - { - return; - } - case 1: // Up - { - if ( m_Category.Parent != null ) - { - int index = Array.IndexOf( m_Category.Parent.Nodes, m_Category ) / EntryCount; - - if ( index < 0 ) - index = 0; - - from.SendGump( new CategorizedAddGump( from, m_Category.Parent, index ) ); - } - - break; - } - case 2: // Previous - { - if ( m_Page > 0 ) - from.SendGump( new CategorizedAddGump( from, m_Category, m_Page - 1 ) ); - - break; - } - case 3: // Next - { - if ( (m_Page + 1) * EntryCount < m_Category.Nodes.Length ) - from.SendGump( new CategorizedAddGump( from, m_Category, m_Page + 1 ) ); - - break; - } - default: - { - int index = (m_Page * EntryCount) + (info.ButtonID - 4); - - if ( index >= 0 && index < m_Category.Nodes.Length ) - m_Category.Nodes[index].OnClick( from, m_Page ); - - break; - } - } - } - } -} + x += PrevWidth + OffsetSize; + + if (!OldStyle) + AddImageTiled(x, y, NextWidth, EntryHeight, HeaderGumpID); + + if ((page + 1) * EntryCount < nodes.Length) + { + AddButton(x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 3, GumpButtonType.Reply, 1); + + if (NextLabel) + AddLabel(x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next"); + } + + for (int i = 0, index = page * EntryCount; i < EntryCount && index < nodes.Length; ++i, ++index) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; + + CAGNode node = nodes[index]; + + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y + (EntryHeight - 20) / 2, EntryWidth - TextOffsetX, EntryHeight, TextHue, + node.Caption); + + x += EntryWidth + OffsetSize; + + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, i + 4, GumpButtonType.Reply, 0); + + if (node is CAGObject obj) + { + int itemID = obj.ItemID; + + Rectangle2D bounds = ItemBounds.Table[itemID]; + + if (itemID != 1 && bounds.Height < EntryHeight * 2) + { + if (bounds.Height < EntryHeight) + AddItem(x - OffsetSize - 22 - i % 2 * 44 - bounds.Width / 2 - bounds.X, + y + EntryHeight / 2 - bounds.Height / 2 - bounds.Y, itemID); + else + AddItem(x - OffsetSize - 22 - i % 2 * 44 - bounds.Width / 2 - bounds.X, + y + EntryHeight - 1 - bounds.Height - bounds.Y, itemID); + } + } + } + } + + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = m_Owner; + + switch (info.ButtonID) + { + case 0: // Closed + { + return; + } + case 1: // Up + { + if (m_Category.Parent != null) + { + int index = Array.IndexOf(m_Category.Parent.Nodes, m_Category) / EntryCount; + + if (index < 0) + index = 0; + + from.SendGump(new CategorizedAddGump(from, m_Category.Parent, index)); + } + + break; + } + case 2: // Previous + { + if (m_Page > 0) + from.SendGump(new CategorizedAddGump(from, m_Category, m_Page - 1)); + + break; + } + case 3: // Next + { + if ((m_Page + 1) * EntryCount < m_Category.Nodes.Length) + from.SendGump(new CategorizedAddGump(from, m_Category, m_Page + 1)); + + break; + } + default: + { + int index = m_Page * EntryCount + (info.ButtonID - 4); + + if (index >= 0 && index < m_Category.Nodes.Length) + m_Category.Nodes[index].OnClick(from, m_Page); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/ClientGump.cs b/Scripts/Gumps/ClientGump.cs index 284cc94f2..48d1f2f56 100644 --- a/Scripts/Gumps/ClientGump.cs +++ b/Scripts/Gumps/ClientGump.cs @@ -1,298 +1,310 @@ -using System; using Server.Accounting; +using Server.Commands; +using Server.Commands.Generic; using Server.Mobiles; using Server.Network; using Server.Targets; -using Server.Commands; -using Server.Commands.Generic; namespace Server.Gumps { - public class ClientGump : Gump - { - private NetState m_State; + public class ClientGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private NetState m_State; - private void Resend( Mobile to, RelayInfo info ) - { - TextRelay te = info.GetTextEntry( 0 ); + public ClientGump(Mobile from, NetState state) : this(from, state, "") + { + } - to.SendGump( new ClientGump( to, m_State, te == null ? "" : te.Text ) ); - } + public ClientGump(Mobile from, NetState state, string initialText) : base(30, 20) + { + if (state == null) + return; - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_State == null ) - return; + m_State = state; - Mobile focus = m_State.Mobile; - Mobile from = state.Mobile; + AddPage(0); - if ( focus == null ) - { - from.SendMessage( "That character is no longer online." ); - return; - } + AddBackground(0, 0, 400, 274, 5054); - if ( focus.Deleted ) - { - from.SendMessage( "That character no longer exists." ); - return; - } - if ( from != focus && focus.Hidden && from.AccessLevel < focus.AccessLevel && ( !( focus is PlayerMobile ) || !((PlayerMobile)focus).VisibilityList.Contains( from ) ) ) - { - from.SendMessage( "That character is no longer visible." ); - return; - } + AddImageTiled(10, 10, 380, 19, 0xA40); + AddAlphaRegion(10, 10, 380, 19); - switch ( info.ButtonID ) - { - case 1: // Tell - { - TextRelay text = info.GetTextEntry( 0 ); + AddImageTiled(10, 32, 380, 232, 0xA40); + AddAlphaRegion(10, 32, 380, 232); - if ( text != null ) - { - focus.SendMessage( 0x482, "{0} tells you:", from.Name ); - focus.SendMessage( 0x482, text.Text ); + AddHtml(10, 10, 380, 20, Color(Center("User Information"), LabelColor32), false, false); - CommandLogging.WriteLine( from, "{0} {1} telling {2} \"{3}\" ", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ), text.Text ); - } + int line = 0; - from.SendGump( new ClientGump( from, m_State ) ); + AddHtml(14, 36 + line * 20, 200, 20, Color("Address:", LabelColor32), false, false); + AddHtml(70, 36 + line++ * 20, 200, 20, Color(state.ToString(), LabelColor32), false, false); - break; - } - case 4: // Props - { - Resend( from, info ); + AddHtml(14, 36 + line * 20, 200, 20, Color("Client:", LabelColor32), false, false); + AddHtml(70, 36 + line++ * 20, 200, 20, + Color(state.Version == null ? "(null)" : state.Version.ToString(), LabelColor32), false, false); - if ( !BaseCommand.IsAccessible( from, focus ) ) - from.SendMessage( "That is not accessible." ); - else - { - from.SendGump( new PropertiesGump( from, focus ) ); - CommandLogging.WriteLine( from, "{0} {1} opening properties gump of {2} ", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ) ); - } + AddHtml(14, 36 + line * 20, 200, 20, Color("Version:", LabelColor32), false, false); - break; - } - case 5: // Go to - { - if ( focus.Map == null || focus.Map == Map.Internal ) - { - from.SendMessage( "That character is not in the world." ); - } - else - { - from.MoveToWorld( focus.Location, focus.Map ); - Resend( from, info ); + ExpansionInfo info = state.ExpansionInfo; + string expansionName = info.Name; - CommandLogging.WriteLine( from, "{0} {1} going to {2}, Location {3}, Map {4}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ), focus.Location, focus.Map ); - } + AddHtml(70, 36 + line++ * 20, 200, 20, Color(expansionName, LabelColor32), false, false); - break; - } - case 6: // Get - { - if ( from.Map == null || from.Map == Map.Internal ) - { - from.SendMessage( "You cannot bring that person here." ); - } - else - { - focus.MoveToWorld( from.Location, from.Map ); - Resend( from, info ); + Account a = state.Account as Account; + Mobile m = state.Mobile; - CommandLogging.WriteLine( from, "{0} {1} bringing {2} to Location {3}, Map {4}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ), from.Location, from.Map ); - } + if (from.AccessLevel >= AccessLevel.GameMaster && a != null) + { + AddHtml(14, 36 + line * 20, 200, 20, Color("Account:", LabelColor32), false, false); + AddHtml(70, 36 + line++ * 20, 200, 20, Color(a.Username, LabelColor32), false, false); + } - break; - } - case 7: // Move - { - from.Target = new MoveTarget( focus ); - Resend( from, info ); + if (m != null) + { + AddHtml(14, 36 + line * 20, 200, 20, Color("Mobile:", LabelColor32), false, false); + AddHtml(70, 36 + line++ * 20, 200, 20, Color($"{m.Name} (0x{m.Serial.Value:X})", LabelColor32), false, + false); - break; - } - case 8: // Kick - { - if ( from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > focus.AccessLevel ) - { - focus.Say( "I've been kicked!" ); + AddHtml(14, 36 + line * 20, 200, 20, Color("Location:", LabelColor32), false, false); + AddHtml(70, 36 + line++ * 20, 200, 20, Color($"{m.Location} [{m.Map}]", LabelColor32), false, false); - m_State.Dispose(); + AddButton(13, 157, 0xFAB, 0xFAD, 1, GumpButtonType.Reply, 0); + AddHtml(48, 158, 200, 20, Color("Send Message", LabelColor32), false, false); - CommandLogging.WriteLine( from, "{0} {1} kicking {2} ", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ) ); - } + AddImageTiled(12, 182, 376, 80, 0xA40); + AddImageTiled(13, 183, 374, 78, 0xBBC); + AddTextEntry(15, 183, 372, 78, 0x480, 0, ""); - break; - } - case 9: // Kill - { - if ( from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > focus.AccessLevel ) - { - focus.Kill(); - CommandLogging.WriteLine( from, "{0} {1} killing {2} ", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ) ); - } + AddImageTiled(245, 35, 142, 144, 5058); - Resend( from, info ); + AddImageTiled(246, 36, 140, 142, 0xA40); + AddAlphaRegion(246, 36, 140, 142); - break; - } - case 10: //Res - { - if ( from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > focus.AccessLevel ) - { - focus.PlaySound( 0x214 ); - focus.FixedEffect( 0x376A, 10, 16 ); + line = 0; - focus.Resurrect(); + if (BaseCommand.IsAccessible(from, m)) + { + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Properties", LabelColor32), false, false); + } - CommandLogging.WriteLine( from, "{0} {1} resurrecting {2} ", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ) ); - } + if (from != m) + { + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Go to them", LabelColor32), false, false); - Resend( from, info ); + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 6, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Bring them here", LabelColor32), false, false); + } - break; - } - case 11: // Skills - { - Resend( from, info ); + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 7, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Move to target", LabelColor32), false, false); - if ( from.AccessLevel > focus.AccessLevel ) - { - from.SendGump( new SkillsGump( from, (Mobile)focus ) ); - CommandLogging.WriteLine( from, "{0} {1} Opening Skills gump of {2} ", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( focus ) ); - } + if (from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > m.AccessLevel) + { + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 8, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Disconnect", LabelColor32), false, false); - break; - } - } - } + if (m.Alive) + { + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 9, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Kill", LabelColor32), false, false); + } + else + { + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 10, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Resurrect", LabelColor32), false, false); + } + } - public ClientGump( Mobile from, NetState state ) : this( from, state, "" ) - { - } + if (from.AccessLevel >= AccessLevel.Counselor && from.AccessLevel > m.AccessLevel) + { + AddButton(246, 36 + line * 20, 0xFA5, 0xFA7, 11, GumpButtonType.Reply, 0); + AddHtml(280, 38 + line++ * 20, 100, 20, Color("Skills browser", LabelColor32), false, false); + } + } + } - private const int LabelColor32 = 0xFFFFFF; + private void Resend(Mobile to, RelayInfo info) + { + TextRelay te = info.GetTextEntry(0); - public string Center( string text ) - { - return $"
{text}
"; - } + to.SendGump(new ClientGump(to, m_State, te == null ? "" : te.Text)); + } - public string Color( string text, int color ) - { - return $"{text}"; - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_State == null) + return; - public ClientGump( Mobile from, NetState state, string initialText ) : base( 30, 20 ) - { - if ( state == null ) - return; + Mobile focus = m_State.Mobile; + Mobile from = state.Mobile; - m_State = state; + if (focus == null) + { + from.SendMessage("That character is no longer online."); + return; + } - AddPage( 0 ); + if (focus.Deleted) + { + from.SendMessage("That character no longer exists."); + return; + } - AddBackground( 0, 0, 400, 274, 5054 ); + if (from != focus && focus.Hidden && from.AccessLevel < focus.AccessLevel && + (!(focus is PlayerMobile) || !((PlayerMobile)focus).VisibilityList.Contains(from))) + { + from.SendMessage("That character is no longer visible."); + return; + } - AddImageTiled( 10, 10, 380, 19, 0xA40 ); - AddAlphaRegion( 10, 10, 380, 19 ); + switch (info.ButtonID) + { + case 1: // Tell + { + TextRelay text = info.GetTextEntry(0); - AddImageTiled( 10, 32, 380, 232, 0xA40 ); - AddAlphaRegion( 10, 32, 380, 232 ); + if (text != null) + { + focus.SendMessage(0x482, "{0} tells you:", from.Name); + focus.SendMessage(0x482, text.Text); - AddHtml( 10, 10, 380, 20, Color( Center( "User Information" ), LabelColor32 ), false, false ); + CommandLogging.WriteLine(from, "{0} {1} telling {2} \"{3}\" ", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(focus), text.Text); + } - int line = 0; + from.SendGump(new ClientGump(from, m_State)); - AddHtml( 14, 36 + (line * 20), 200, 20, Color( "Address:", LabelColor32 ), false, false ); - AddHtml( 70, 36 + (line++ * 20), 200, 20, Color( state.ToString(), LabelColor32 ), false, false ); + break; + } + case 4: // Props + { + Resend(from, info); - AddHtml( 14, 36 + (line * 20), 200, 20, Color( "Client:", LabelColor32 ), false, false ); - AddHtml( 70, 36 + (line++ * 20), 200, 20, Color( state.Version == null ? "(null)" : state.Version.ToString(), LabelColor32 ), false, false ); + if (!BaseCommand.IsAccessible(from, focus)) + { + from.SendMessage("That is not accessible."); + } + else + { + from.SendGump(new PropertiesGump(from, focus)); + CommandLogging.WriteLine(from, "{0} {1} opening properties gump of {2} ", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(focus)); + } - AddHtml( 14, 36 + (line * 20), 200, 20, Color( "Version:", LabelColor32 ), false, false ); + break; + } + case 5: // Go to + { + if (focus.Map == null || focus.Map == Map.Internal) + { + from.SendMessage("That character is not in the world."); + } + else + { + from.MoveToWorld(focus.Location, focus.Map); + Resend(from, info); - ExpansionInfo info = state.ExpansionInfo; - string expansionName = info.Name; + CommandLogging.WriteLine(from, "{0} {1} going to {2}, Location {3}, Map {4}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(focus), focus.Location, focus.Map); + } - AddHtml( 70, 36 + (line++ * 20), 200, 20, Color( expansionName, LabelColor32 ), false, false ); + break; + } + case 6: // Get + { + if (from.Map == null || from.Map == Map.Internal) + { + from.SendMessage("You cannot bring that person here."); + } + else + { + focus.MoveToWorld(from.Location, from.Map); + Resend(from, info); - Account a = state.Account as Account; - Mobile m = state.Mobile; + CommandLogging.WriteLine(from, "{0} {1} bringing {2} to Location {3}, Map {4}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(focus), from.Location, from.Map); + } - if ( from.AccessLevel >= AccessLevel.GameMaster && a != null ) - { - AddHtml( 14, 36 + (line * 20), 200, 20, Color( "Account:", LabelColor32 ), false, false ); - AddHtml( 70, 36 + (line++ * 20), 200, 20, Color( a.Username, LabelColor32 ), false, false ); - } + break; + } + case 7: // Move + { + from.Target = new MoveTarget(focus); + Resend(from, info); - if ( m != null ) - { - AddHtml( 14, 36 + (line * 20), 200, 20, Color( "Mobile:", LabelColor32 ), false, false ); - AddHtml( 70, 36 + (line++ * 20), 200, 20, Color($"{m.Name} (0x{m.Serial.Value:X})", LabelColor32 ), false, false ); + break; + } + case 8: // Kick + { + if (from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > focus.AccessLevel) + { + focus.Say("I've been kicked!"); - AddHtml( 14, 36 + (line * 20), 200, 20, Color( "Location:", LabelColor32 ), false, false ); - AddHtml( 70, 36 + (line++ * 20), 200, 20, Color($"{m.Location} [{m.Map}]", LabelColor32 ), false, false ); + m_State.Dispose(); - AddButton( 13, 157, 0xFAB, 0xFAD, 1, GumpButtonType.Reply, 0 ); - AddHtml( 48, 158, 200, 20, Color( "Send Message", LabelColor32 ), false, false ); + CommandLogging.WriteLine(from, "{0} {1} kicking {2} ", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(focus)); + } - AddImageTiled( 12, 182, 376, 80, 0xA40 ); - AddImageTiled( 13, 183, 374, 78, 0xBBC ); - AddTextEntry( 15, 183, 372, 78, 0x480, 0, "" ); + break; + } + case 9: // Kill + { + if (from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > focus.AccessLevel) + { + focus.Kill(); + CommandLogging.WriteLine(from, "{0} {1} killing {2} ", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(focus)); + } - AddImageTiled( 245, 35, 142, 144, 5058 ); + Resend(from, info); - AddImageTiled( 246, 36, 140, 142, 0xA40 ); - AddAlphaRegion( 246, 36, 140, 142 ); + break; + } + case 10: //Res + { + if (from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > focus.AccessLevel) + { + focus.PlaySound(0x214); + focus.FixedEffect(0x376A, 10, 16); - line = 0; + focus.Resurrect(); - if ( BaseCommand.IsAccessible( from, m ) ) - { - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Properties", LabelColor32 ), false, false ); - } + CommandLogging.WriteLine(from, "{0} {1} resurrecting {2} ", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(focus)); + } - if ( from != m ) - { - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Go to them", LabelColor32 ), false, false ); + Resend(from, info); - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 6, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Bring them here", LabelColor32 ), false, false ); - } + break; + } + case 11: // Skills + { + Resend(from, info); - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 7, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Move to target", LabelColor32 ), false, false ); + if (from.AccessLevel > focus.AccessLevel) + { + from.SendGump(new SkillsGump(from, focus)); + CommandLogging.WriteLine(from, "{0} {1} Opening Skills gump of {2} ", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(focus)); + } - if ( from.AccessLevel >= AccessLevel.GameMaster && from.AccessLevel > m.AccessLevel ) - { - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 8, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Disconnect", LabelColor32 ), false, false ); + break; + } + } + } - if ( m.Alive ) - { - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 9, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Kill", LabelColor32 ), false, false ); - } - else - { - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 10, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Resurrect", LabelColor32 ), false, false ); - } - } + public string Center(string text) + { + return $"
{text}
"; + } - if ( from.AccessLevel >= AccessLevel.Counselor && from.AccessLevel > m.AccessLevel ) - { - AddButton( 246, 36 + (line * 20), 0xFA5, 0xFA7, 11, GumpButtonType.Reply, 0 ); - AddHtml( 280, 38 + (line++ * 20), 100, 20, Color( "Skills browser", LabelColor32 ), false, false ); - } - } - } - } -} + public string Color(string text, int color) + { + return $"{text}"; + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/CommentsGump.cs b/Scripts/Gumps/CommentsGump.cs index 7e67c015e..e03f9f389 100644 --- a/Scripts/Gumps/CommentsGump.cs +++ b/Scripts/Gumps/CommentsGump.cs @@ -1,121 +1,118 @@ -using System; using System.Collections.Generic; using Server.Accounting; +using Server.Commands; using Server.Network; using Server.Prompts; using Server.Targeting; -using Server.Commands; namespace Server.Gumps { - public class CommentsGump : Gump - { - public static void Initialize() - { - CommandSystem.Register( "Comments", AccessLevel.Counselor, Comments_OnCommand ); - } + public class CommentsGump : Gump + { + private Account m_Acct; - [Usage( "Comments" )] - [Description( "View/Modify/Add account comments." )] - private static void Comments_OnCommand( CommandEventArgs args ) - { - args.Mobile.SendMessage( "Select the player to view account comments." ); - args.Mobile.BeginTarget( -1, false, TargetFlags.None, OnTarget ); - } + public CommentsGump(Account acct) : base(30, 30) + { + m_Acct = acct; - private static void OnTarget( Mobile from, object target ) - { - if ( !(target is Mobile m) || !m.Player ) - { - from.SendMessage( "You must target a player." ); - return; - } + AddPage(0); + AddImageTiled(0, 0, 410, 448, 0xA40); + AddAlphaRegion(1, 1, 408, 446); - if ( m.Account == null ) - from.SendMessage( "That player doesn't have an account loaded... weird." ); - else - from.SendGump( new CommentsGump( (Account)m.Account ) ); - } + string title = $"Comments for '{acct.Username}'"; + int x = 205 - title.Length / 2 * 7; + if (x < 120) + x = 120; + AddLabel(x, 12, 2100, title); - private Account m_Acct; - public CommentsGump( Account acct ) : base( 30, 30 ) - { - m_Acct = acct; + AddPage(1); + AddButton(12, 12, 0xFA8, 0xFAA, 0x7F, GumpButtonType.Reply, 0); + AddLabel(48, 12, 2100, "Add Comment"); - AddPage( 0 ); - AddImageTiled( 0, 0, 410, 448, 0xA40 ); - AddAlphaRegion( 1, 1, 408, 446 ); + List list = acct.Comments; + if (list.Count > 0) + for (int i = 0; i < list.Count; ++i) + { + AccountComment comment = list[i]; - string title = $"Comments for '{acct.Username}'"; - int x = 205 - ((title.Length / 2) * 7); - if ( x < 120 ) - x = 120; - AddLabel( x, 12, 2100, title ); + if (i >= 5 && i % 5 == 0) + { + AddButton(368, 12, 0xFA5, 0xFA7, 0, GumpButtonType.Page, i / 5 + 1); + AddLabel(298, 12, 2100, "Next Page"); + AddPage(i / 5 + 1); + AddButton(12, 12, 0xFAE, 0xFB0, 0, GumpButtonType.Page, i / 5); + AddLabel(48, 12, 2100, "Prev Page"); + } - AddPage( 1 ); - AddButton( 12, 12, 0xFA8, 0xFAA, 0x7F, GumpButtonType.Reply, 0 ); - AddLabel( 48, 12, 2100, "Add Comment" ); + string html = + $"[Added By: {comment.AddedBy} on {comment.LastModified.ToString("H:mm M/d/yy")}]
{comment.Content}"; + AddHtml(12, 44 + i % 5 * 80, 386, 70, html, true, true); + } + else + AddLabel(12, 44, 2100, "There are no comments for this account."); + } - List list = acct.Comments; - if ( list.Count > 0 ) - { - for ( int i = 0; i < list.Count; ++i ) - { - AccountComment comment = list[i]; + public static void Initialize() + { + CommandSystem.Register("Comments", AccessLevel.Counselor, Comments_OnCommand); + } - if ( i >= 5 && (i % 5) == 0 ) - { - AddButton( 368, 12, 0xFA5, 0xFA7, 0, GumpButtonType.Page, (i / 5) + 1 ); - AddLabel( 298, 12, 2100, "Next Page" ); - AddPage( (i / 5) + 1 ); - AddButton( 12, 12, 0xFAE, 0xFB0, 0, GumpButtonType.Page, (i / 5) ); - AddLabel( 48, 12, 2100, "Prev Page" ); - } + [Usage("Comments")] + [Description("View/Modify/Add account comments.")] + private static void Comments_OnCommand(CommandEventArgs args) + { + args.Mobile.SendMessage("Select the player to view account comments."); + args.Mobile.BeginTarget(-1, false, TargetFlags.None, OnTarget); + } - string html = - $"[Added By: {comment.AddedBy} on {comment.LastModified.ToString("H:mm M/d/yy")}]
{comment.Content}"; - AddHtml( 12, 44 + ((i % 5) * 80), 386, 70, html, true, true ); - } - } - else - { - AddLabel( 12, 44, 2100, "There are no comments for this account." ); - } - } + private static void OnTarget(Mobile from, object target) + { + if (!(target is Mobile m) || !m.Player) + { + from.SendMessage("You must target a player."); + return; + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 0x7F ) - { - state.Mobile.SendMessage( "Enter the text for the account comment (or press [Esc] to cancel):" ); - state.Mobile.Prompt = new CommentPrompt( m_Acct ); - } - } + if (m.Account == null) + from.SendMessage("That player doesn't have an account loaded... weird."); + else + from.SendGump(new CommentsGump((Account)m.Account)); + } - public class CommentPrompt : Prompt - { - private Account m_Acct; - public CommentPrompt( Account acct ) - { - m_Acct = acct; - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 0x7F) + { + state.Mobile.SendMessage("Enter the text for the account comment (or press [Esc] to cancel):"); + state.Mobile.Prompt = new CommentPrompt(m_Acct); + } + } - public override void OnCancel(Mobile from) - { - from.CloseGump( typeof( CommentsGump ) ); - from.SendGump( new CommentsGump( m_Acct ) ); - base.OnCancel (from); - } + public class CommentPrompt : Prompt + { + private Account m_Acct; - public override void OnResponse(Mobile from, string text) - { - base.OnResponse (from, text); - from.SendMessage( "Comment added." ); - //m_Acct.AddComment( from.Name, text ); - m_Acct.Comments.Add( new AccountComment( from.Name, text ) ); - from.CloseGump( typeof( CommentsGump ) ); - from.SendGump( new CommentsGump( m_Acct ) ); - } - } - } -} + public CommentPrompt(Account acct) + { + m_Acct = acct; + } + + public override void OnCancel(Mobile from) + { + from.CloseGump(typeof(CommentsGump)); + from.SendGump(new CommentsGump(m_Acct)); + base.OnCancel(from); + } + + public override void OnResponse(Mobile from, string text) + { + base.OnResponse(from, text); + from.SendMessage("Comment added."); + //m_Acct.AddComment( from.Name, text ); + m_Acct.Comments.Add(new AccountComment(from.Name, text)); + from.CloseGump(typeof(CommentsGump)); + from.SendGump(new CommentsGump(m_Acct)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/ConfirmBreakCrystalGump.cs b/Scripts/Gumps/ConfirmBreakCrystalGump.cs index 4cddec702..c7522b881 100644 --- a/Scripts/Gumps/ConfirmBreakCrystalGump.cs +++ b/Scripts/Gumps/ConfirmBreakCrystalGump.cs @@ -3,51 +3,51 @@ using Server.Mobiles; namespace Server.Gumps { - public class ConfirmBreakCrystalGump : BaseConfirmGump - { - public override int LabelNumber => 1075084; // This statuette will be destroyed when its trapped creature is summoned. The creature will be bonded to you but will disappear if released.

Do you wish to proceed? + public class ConfirmBreakCrystalGump : BaseConfirmGump + { + private BaseImprisonedMobile m_Item; - private BaseImprisonedMobile m_Item; + public ConfirmBreakCrystalGump(BaseImprisonedMobile item) + { + m_Item = item; + } - public ConfirmBreakCrystalGump( BaseImprisonedMobile item ) - { - m_Item = item; - } + public override int LabelNumber => + 1075084; // This statuette will be destroyed when its trapped creature is summoned. The creature will be bonded to you but will disappear if released.

Do you wish to proceed? - public override void Confirm( Mobile from ) - { - if ( m_Item == null || m_Item.Deleted ) - return; + public override void Confirm(Mobile from) + { + if (m_Item == null || m_Item.Deleted) + return; - BaseCreature summon = m_Item.Summon; + BaseCreature summon = m_Item.Summon; - if ( summon != null ) - { - if ( !summon.SetControlMaster( from ) ) - { - summon.Delete(); - } - else - { - from.SendLocalizedMessage( 1049666 ); // Your pet has bonded with you! + if (summon != null) + { + if (!summon.SetControlMaster(from)) + { + summon.Delete(); + } + else + { + from.SendLocalizedMessage(1049666); // Your pet has bonded with you! - summon.MoveToWorld( from.Location, from.Map ); - summon.IsBonded = true; + summon.MoveToWorld(from.Location, from.Map); + summon.IsBonded = true; - summon.Skills.Wrestling.Base = 100; - summon.Skills.Tactics.Base = 100; - summon.Skills.MagicResist.Base = 100; - summon.Skills.Anatomy.Base = 100; + summon.Skills.Wrestling.Base = 100; + summon.Skills.Tactics.Base = 100; + summon.Skills.MagicResist.Base = 100; + summon.Skills.Anatomy.Base = 100; - Effects.PlaySound( summon.Location, summon.Map, summon.BaseSoundID ); - Effects.SendLocationParticles( EffectItem.Create( summon.Location, summon.Map, EffectItem.DefaultDuration ), 0x3728, 1, 10, 0x26B6 ); + Effects.PlaySound(summon.Location, summon.Map, summon.BaseSoundID); + Effects.SendLocationParticles(EffectItem.Create(summon.Location, summon.Map, EffectItem.DefaultDuration), + 0x3728, 1, 10, 0x26B6); - m_Item.Release( from, summon ); - m_Item.Delete(); - } - } - } - } - - -} + m_Item.Release(from, summon); + m_Item.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/ConfirmHeritageGump.cs b/Scripts/Gumps/ConfirmHeritageGump.cs index e98b62241..c801aa941 100644 --- a/Scripts/Gumps/ConfirmHeritageGump.cs +++ b/Scripts/Gumps/ConfirmHeritageGump.cs @@ -4,70 +4,71 @@ using Server.Network; namespace Server.Gumps { - public class ConfirmHeritageGump : Gump - { - private HeritageToken m_Token; - private Type[] m_Selected; + public class ConfirmHeritageGump : Gump + { + private Type[] m_Selected; + private HeritageToken m_Token; - private enum Buttons - { - Cancel, - Okay - } + public ConfirmHeritageGump(HeritageToken token, Type[] selected, int cliloc) : base(60, 36) + { + m_Token = token; + m_Selected = selected; - public ConfirmHeritageGump( HeritageToken token, Type[] selected, int cliloc ) : base( 60, 36 ) - { - m_Token = token; - m_Selected = selected; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 291, 99, 0x13BE); + AddImageTiled(5, 6, 280, 20, 0xA40); + AddHtmlLocalized(9, 8, 280, 20, 1070972, 0x7FFF, false, + false); // Click "OKAY" to redeem the following promotional item: + AddImageTiled(5, 31, 280, 40, 0xA40); + AddHtmlLocalized(9, 35, 272, 40, cliloc, 0x7FFF, false, false); + AddButton(180, 73, 0xFB7, 0xFB8, (int)Buttons.Okay, GumpButtonType.Reply, 0); + AddHtmlLocalized(215, 75, 100, 20, 1011036, 0x7FFF, false, false); // OKAY + AddButton(5, 73, 0xFB1, 0xFB2, (int)Buttons.Cancel, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 75, 100, 20, 1060051, 0x7FFF, false, false); // CANCEL + } - AddBackground( 0, 0, 291, 99, 0x13BE ); - AddImageTiled( 5, 6, 280, 20, 0xA40 ); - AddHtmlLocalized( 9, 8, 280, 20, 1070972, 0x7FFF, false, false ); // Click "OKAY" to redeem the following promotional item: - AddImageTiled( 5, 31, 280, 40, 0xA40 ); - AddHtmlLocalized( 9, 35, 272, 40, cliloc, 0x7FFF, false, false ); - AddButton( 180, 73, 0xFB7, 0xFB8, (int) Buttons.Okay, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 215, 75, 100, 20, 1011036, 0x7FFF, false, false ); // OKAY - AddButton( 5, 73, 0xFB1, 0xFB2, (int) Buttons.Cancel, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 75, 100, 20, 1060051, 0x7FFF, false, false ); // CANCEL - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Token == null || m_Token.Deleted) + return; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Token == null || m_Token.Deleted ) - return; + switch (info.ButtonID) + { + case (int)Buttons.Okay: - switch ( info.ButtonID ) - { - case (int) Buttons.Okay: - - Item item = null; + Item item = null; - foreach ( Type type in m_Selected ) - { - try - { - item = Activator.CreateInstance( type ) as Item; - } - catch ( Exception ex ) - { - Console.WriteLine( ex.Message ); - Console.WriteLine( ex.StackTrace ); - } + foreach (Type type in m_Selected) + { + try + { + item = Activator.CreateInstance(type) as Item; + } + catch (Exception ex) + { + Console.WriteLine(ex.Message); + Console.WriteLine(ex.StackTrace); + } - if ( item != null ) - { - m_Token.Delete(); - sender.Mobile.AddToBackpack( item ); - } - } + if (item != null) + { + m_Token.Delete(); + sender.Mobile.AddToBackpack(item); + } + } - break; - case (int) Buttons.Cancel: - sender.Mobile.SendGump( new HeritageTokenGump( m_Token ) ); - break; - } - } - } -} + break; + case (int)Buttons.Cancel: + sender.Mobile.SendGump(new HeritageTokenGump(m_Token)); + break; + } + } + + private enum Buttons + { + Cancel, + Okay + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/ConfirmHouseResize.cs b/Scripts/Gumps/ConfirmHouseResize.cs index a61e2856a..0d5bbbeac 100644 --- a/Scripts/Gumps/ConfirmHouseResize.cs +++ b/Scripts/Gumps/ConfirmHouseResize.cs @@ -1,150 +1,158 @@ +using Server.Guilds; using Server.Items; using Server.Multis; using Server.Network; namespace Server.Gumps { - public class ConfirmHouseResize : Gump - { - private Mobile m_Mobile; - private BaseHouse m_House; + public class ConfirmHouseResize : Gump + { + private BaseHouse m_House; + private Mobile m_Mobile; - public ConfirmHouseResize( Mobile mobile, BaseHouse house ) : base( 110, 100 ) - { - m_Mobile = mobile; - m_House = house; + public ConfirmHouseResize(Mobile mobile, BaseHouse house) : base(110, 100) + { + m_Mobile = mobile; + m_House = house; - mobile.CloseGump( typeof( ConfirmHouseResize ) ); + mobile.CloseGump(typeof(ConfirmHouseResize)); - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 420, 280, 0x13BE ); - AddImageTiled( 10, 10, 400, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 400, 20 ); - AddHtmlLocalized( 10, 10, 400, 20, 1060635, 0x7800, false, false ); //
WARNING
- AddImageTiled( 10, 40, 400, 200, 0xA40 ); - AddAlphaRegion( 10, 40, 400, 200 ); + AddBackground(0, 0, 420, 280, 0x13BE); + AddImageTiled(10, 10, 400, 20, 0xA40); + AddAlphaRegion(10, 10, 400, 20); + AddHtmlLocalized(10, 10, 400, 20, 1060635, 0x7800, false, false); //
WARNING
+ AddImageTiled(10, 40, 400, 200, 0xA40); + AddAlphaRegion(10, 40, 400, 200); - /* You are attempting to resize your house. You will be refunded the house's - value directly to your bank box. All items in the house will *remain behind* - and can be *freely picked up by anyone*. Once the house is demolished, however, - only this account will be able to place on the land for one hour. This *will* - circumvent the normal 7-day waiting period (if it applies to you). This action - will not un-condemn any other houses on your account. If you have other, - grandfathered houses, this action *WILL* condemn them. Are you sure you wish - to continue?*/ - AddHtmlLocalized( 10, 40, 400, 200, 1080196, 0x7F00, false, true ); + /* You are attempting to resize your house. You will be refunded the house's + value directly to your bank box. All items in the house will *remain behind* + and can be *freely picked up by anyone*. Once the house is demolished, however, + only this account will be able to place on the land for one hour. This *will* + circumvent the normal 7-day waiting period (if it applies to you). This action + will not un-condemn any other houses on your account. If you have other, + grandfathered houses, this action *WILL* condemn them. Are you sure you wish + to continue?*/ + AddHtmlLocalized(10, 40, 400, 200, 1080196, 0x7F00, false, true); - AddImageTiled( 10, 250, 400, 20, 0xA40 ); - AddAlphaRegion( 10, 250, 400, 20 ); - AddButton( 10, 250, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddButton( 210, 250, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 250, 170, 20, 1011036, 0x7FFF, false, false ); // OKAY - AddHtmlLocalized( 240, 250, 170, 20, 1011012, 0x7FFF, false, false ); // CANCEL + AddImageTiled(10, 250, 400, 20, 0xA40); + AddAlphaRegion(10, 250, 400, 20); + AddButton(10, 250, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddButton(210, 250, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 250, 170, 20, 1011036, 0x7FFF, false, false); // OKAY + AddHtmlLocalized(240, 250, 170, 20, 1011012, 0x7FFF, false, false); // CANCEL + } - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1 && !m_House.Deleted) + { + if (m_House.IsOwner(m_Mobile)) + { + if (m_House.MovingCrate != null || m_House.InternalizedVendors.Count > 0) + { + m_Mobile.SendLocalizedMessage( + 1080455); // You can not resize your house at this time. Please remove all items fom the moving crate and try again. + return; + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 1 && !m_House.Deleted ) - { - if ( m_House.IsOwner( m_Mobile ) ) - { - if ( m_House.MovingCrate != null || m_House.InternalizedVendors.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 1080455 ); // You can not resize your house at this time. Please remove all items fom the moving crate and try again. - return; - } + if (!Guild.NewGuildSystem && m_House.FindGuildstone() != null) + { + m_Mobile.SendLocalizedMessage(501389); // You cannot redeed a house with a guildstone inside. + return; + } - if ( !Guilds.Guild.NewGuildSystem && m_House.FindGuildstone() != null ) - { - m_Mobile.SendLocalizedMessage( 501389 ); // You cannot redeed a house with a guildstone inside. - return; - } - /*else if ( m_House.PlayerVendors.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 503236 ); // You need to collect your vendor's belongings before moving. - return; - }*/ - if ( m_House.HasRentedVendors && m_House.VendorInventories.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 1062679 ); // You cannot do that that while you still have contract vendors or unclaimed contract vendor inventory in your house. - return; - } - if ( m_House.HasRentedVendors ) - { - m_Mobile.SendLocalizedMessage( 1062680 ); // You cannot do that that while you still have contract vendors in your house. - return; - } - if ( m_House.VendorInventories.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 1062681 ); // You cannot do that that while you still have unclaimed contract vendor inventory in your house. - return; - } + /*else if ( m_House.PlayerVendors.Count > 0 ) + { + m_Mobile.SendLocalizedMessage( 503236 ); // You need to collect your vendor's belongings before moving. + return; + }*/ + if (m_House.HasRentedVendors && m_House.VendorInventories.Count > 0) + { + m_Mobile.SendLocalizedMessage( + 1062679); // You cannot do that that while you still have contract vendors or unclaimed contract vendor inventory in your house. + return; + } - if ( m_Mobile.AccessLevel >= AccessLevel.GameMaster ) - { - m_Mobile.SendMessage( "You do not get a refund for your house as you are not a player" ); - m_House.RemoveKeys( m_Mobile ); - new TempNoHousingRegion( m_House, m_Mobile ); - m_House.Delete(); - } - else - { - Item toGive = null; + if (m_House.HasRentedVendors) + { + m_Mobile.SendLocalizedMessage( + 1062680); // You cannot do that that while you still have contract vendors in your house. + return; + } - if ( m_House.IsAosRules ) - { - if ( m_House.Price > 0 ) - toGive = new BankCheck( m_House.Price ); - else - toGive = m_House.GetDeed(); - } - else - { - toGive = m_House.GetDeed(); + if (m_House.VendorInventories.Count > 0) + { + m_Mobile.SendLocalizedMessage( + 1062681); // You cannot do that that while you still have unclaimed contract vendor inventory in your house. + return; + } - if ( toGive == null && m_House.Price > 0 ) - toGive = new BankCheck( m_House.Price ); - } + if (m_Mobile.AccessLevel >= AccessLevel.GameMaster) + { + m_Mobile.SendMessage("You do not get a refund for your house as you are not a player"); + m_House.RemoveKeys(m_Mobile); + new TempNoHousingRegion(m_House, m_Mobile); + m_House.Delete(); + } + else + { + Item toGive = null; - if ( toGive != null ) - { - BankBox box = m_Mobile.BankBox; + if (m_House.IsAosRules) + { + if (m_House.Price > 0) + toGive = new BankCheck(m_House.Price); + else + toGive = m_House.GetDeed(); + } + else + { + toGive = m_House.GetDeed(); - if ( box.TryDropItem( m_Mobile, toGive, false ) ) - { - if ( toGive is BankCheck check ) - m_Mobile.SendLocalizedMessage( 1060397, check.Worth.ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. + if (toGive == null && m_House.Price > 0) + toGive = new BankCheck(m_House.Price); + } - m_House.RemoveKeys( m_Mobile ); - new TempNoHousingRegion( m_House, m_Mobile ); - m_House.Delete(); - } - else - { - toGive.Delete(); - m_Mobile.SendLocalizedMessage( 500390 ); // Your bank box is full. - } - } - else - { - m_Mobile.SendMessage( "Unable to refund house." ); - } - } - } - else - { - m_Mobile.SendLocalizedMessage( 501320 ); // Only the house owner may do this. - } - } - else if ( info.ButtonID == 0 ) - { - m_Mobile.CloseGump( typeof( ConfirmHouseResize ) ); - m_Mobile.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Customize, m_Mobile, m_House ) ); - } - } - } -} + if (toGive != null) + { + BankBox box = m_Mobile.BankBox; + + if (box.TryDropItem(m_Mobile, toGive, false)) + { + if (toGive is BankCheck check) + m_Mobile.SendLocalizedMessage(1060397, + check.Worth.ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + + m_House.RemoveKeys(m_Mobile); + new TempNoHousingRegion(m_House, m_Mobile); + m_House.Delete(); + } + else + { + toGive.Delete(); + m_Mobile.SendLocalizedMessage(500390); // Your bank box is full. + } + } + else + { + m_Mobile.SendMessage("Unable to refund house."); + } + } + } + else + { + m_Mobile.SendLocalizedMessage(501320); // Only the house owner may do this. + } + } + else if (info.ButtonID == 0) + { + m_Mobile.CloseGump(typeof(ConfirmHouseResize)); + m_Mobile.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Customize, m_Mobile, m_House)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/ConfirmReleaseGump.cs b/Scripts/Gumps/ConfirmReleaseGump.cs index 80852b7e0..3457099fb 100644 --- a/Scripts/Gumps/ConfirmReleaseGump.cs +++ b/Scripts/Gumps/ConfirmReleaseGump.cs @@ -1,46 +1,44 @@ using Server.Mobiles; +using Server.Network; namespace Server.Gumps { - public class ConfirmReleaseGump : Gump - { - private Mobile m_From; - private BaseCreature m_Pet; + public class ConfirmReleaseGump : Gump + { + private Mobile m_From; + private BaseCreature m_Pet; - public ConfirmReleaseGump( Mobile from, BaseCreature pet ) : base( 50, 50 ) - { - m_From = from; - m_Pet = pet; + public ConfirmReleaseGump(Mobile from, BaseCreature pet) : base(50, 50) + { + m_From = from; + m_Pet = pet; - m_From.CloseGump( typeof( ConfirmReleaseGump ) ); + m_From.CloseGump(typeof(ConfirmReleaseGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 270, 120, 5054 ); - AddBackground( 10, 10, 250, 100, 3000 ); + AddBackground(0, 0, 270, 120, 5054); + AddBackground(10, 10, 250, 100, 3000); - AddHtmlLocalized( 20, 15, 230, 60, 1046257, true, true ); // Are you sure you want to release your pet? + AddHtmlLocalized(20, 15, 230, 60, 1046257, true, true); // Are you sure you want to release your pet? - AddButton( 20, 80, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 80, 75, 20, 1011011, false, false ); // CONTINUE + AddButton(20, 80, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 80, 75, 20, 1011011, false, false); // CONTINUE - AddButton( 135, 80, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 170, 80, 75, 20, 1011012, false, false ); // CANCEL - } + AddButton(135, 80, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(170, 80, 75, 20, 1011012, false, false); // CANCEL + } - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 2 ) - { - if ( !m_Pet.Deleted && m_Pet.Controlled && m_From == m_Pet.ControlMaster && m_From.CheckAlive() /*&& m_Pet.CheckControlChance( m_From )*/ ) - { - if ( m_Pet.Map == m_From.Map && m_Pet.InRange( m_From, 14 ) ) - { - m_Pet.ControlTarget = null; - m_Pet.ControlOrder = OrderType.Release; - } - } - } - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 2) + if (!m_Pet.Deleted && m_Pet.Controlled && m_From == m_Pet.ControlMaster && + m_From.CheckAlive() /*&& m_Pet.CheckControlChance( m_From )*/) + if (m_Pet.Map == m_From.Map && m_Pet.InRange(m_From, 14)) + { + m_Pet.ControlTarget = null; + m_Pet.ControlOrder = OrderType.Release; + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/DawnsMusicBoxGump.cs b/Scripts/Gumps/DawnsMusicBoxGump.cs index 3a20e68d0..dedc9c20d 100644 --- a/Scripts/Gumps/DawnsMusicBoxGump.cs +++ b/Scripts/Gumps/DawnsMusicBoxGump.cs @@ -1,85 +1,86 @@ -using Server.Network; -using Server.Items; +using Server.Items; +using Server.Network; namespace Server.Gumps { - public class DawnsMusicBoxGump : Gump - { - private DawnsMusicBox m_Box; + public class DawnsMusicBoxGump : Gump + { + private DawnsMusicBox m_Box; - public DawnsMusicBoxGump( DawnsMusicBox box ) - : base( 60, 36 ) - { - m_Box = box; + public DawnsMusicBoxGump(DawnsMusicBox box) + : base(60, 36) + { + m_Box = box; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1075130, 0x7FFF, false, false ); // Choose a track to play + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1075130, 0x7FFF, false, false); // Choose a track to play - int page = 1; - int i, y = 49; + int page = 1; + int i, y = 49; - AddPage( page ); + AddPage(page); - for ( i = 0; i < m_Box.Tracks.Count; i++, y += 24 ) - { - DawnsMusicInfo info = DawnsMusicBox.GetInfo( m_Box.Tracks[ i ] ); + for (i = 0; i < m_Box.Tracks.Count; i++, y += 24) + { + DawnsMusicInfo info = DawnsMusicBox.GetInfo(m_Box.Tracks[i]); - if ( i > 0 && i % 10 == 0 ) - { - AddButton( 228, 294, 0xFA5, 0xFA6, 0, GumpButtonType.Page, page + 1 ); + if (i > 0 && i % 10 == 0) + { + AddButton(228, 294, 0xFA5, 0xFA6, 0, GumpButtonType.Page, page + 1); - AddPage( page + 1 ); - y = 49; + AddPage(page + 1); + y = 49; - AddButton( 193, 294, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page ); + AddButton(193, 294, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page); - page++; - } + page++; + } - if (info == null) - continue; + if (info == null) + continue; - AddButton( 19, y, 0x845, 0x846, 100 + i, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, y - 2, 213, 20, info.Name, 0x7FFF, false, false ); - } + AddButton(19, y, 0x845, 0x846, 100 + i, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, y - 2, 213, 20, info.Name, 0x7FFF, false, false); + } - if ( i % 10 == 0 ) - { - AddButton( 228, 294, 0xFA5, 0xFA6, 0, GumpButtonType.Page, page + 1 ); + if (i % 10 == 0) + { + AddButton(228, 294, 0xFA5, 0xFA6, 0, GumpButtonType.Page, page + 1); - AddPage( page + 1 ); - y = 49; + AddPage(page + 1); + y = 49; - AddButton( 193, 294, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page ); - } + AddButton(193, 294, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page); + } - AddButton( 19, y, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, y - 2, 213, 20, 1075207, 0x7FFF, false, false ); // Stop Song - } + AddButton(19, y, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, y - 2, 213, 20, 1075207, 0x7FFF, false, false); // Stop Song + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Box == null || m_Box.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Box == null || m_Box.Deleted) + return; - Mobile m = sender.Mobile; + Mobile m = sender.Mobile; - if ( !m_Box.IsChildOf( m.Backpack ) && !m_Box.IsLockedDown ) - m.SendLocalizedMessage( 1061856 ); // You must have the item in your backpack or locked down in order to use it. - else if ( m_Box.IsLockedDown && !m_Box.HasAccces( m ) ) - m.SendLocalizedMessage( 502691 ); // You must be the owner to use this. - else if ( info.ButtonID == 1 ) - m_Box.EndMusic( m ); - else if ( info.ButtonID >= 100 && info.ButtonID - 100 < m_Box.Tracks.Count ) - m_Box.PlayMusic( m, m_Box.Tracks[ info.ButtonID - 100 ] ); - } - } -} + if (!m_Box.IsChildOf(m.Backpack) && !m_Box.IsLockedDown) + m.SendLocalizedMessage( + 1061856); // You must have the item in your backpack or locked down in order to use it. + else if (m_Box.IsLockedDown && !m_Box.HasAccces(m)) + m.SendLocalizedMessage(502691); // You must be the owner to use this. + else if (info.ButtonID == 1) + m_Box.EndMusic(m); + else if (info.ButtonID >= 100 && info.ButtonID - 100 < m_Box.Tracks.Count) + m_Box.PlayMusic(m, m_Box.Tracks[info.ButtonID - 100]); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Go/ChildNode.cs b/Scripts/Gumps/Go/ChildNode.cs index d20a90349..99e29f666 100644 --- a/Scripts/Gumps/Go/ChildNode.cs +++ b/Scripts/Gumps/Go/ChildNode.cs @@ -2,40 +2,40 @@ using System.Xml; namespace Server.Gumps { - public class ChildNode - { - public ChildNode( XmlTextReader xml, ParentNode parent ) - { - Parent = parent; + public class ChildNode + { + public ChildNode(XmlTextReader xml, ParentNode parent) + { + Parent = parent; - Parse( xml ); - } + Parse(xml); + } - private void Parse( XmlTextReader xml ) - { - if ( xml.MoveToAttribute( "name" ) ) - Name = xml.Value; - else - Name = "empty"; + public ParentNode Parent{ get; } - int x = 0, y = 0, z = 0; + public string Name{ get; private set; } - if ( xml.MoveToAttribute( "x" ) ) - x = Utility.ToInt32( xml.Value ); + public Point3D Location{ get; private set; } - if ( xml.MoveToAttribute( "y" ) ) - y = Utility.ToInt32( xml.Value ); + private void Parse(XmlTextReader xml) + { + if (xml.MoveToAttribute("name")) + Name = xml.Value; + else + Name = "empty"; - if ( xml.MoveToAttribute( "z" ) ) - z = Utility.ToInt32( xml.Value ); + int x = 0, y = 0, z = 0; - Location = new Point3D( x, y, z ); - } + if (xml.MoveToAttribute("x")) + x = Utility.ToInt32(xml.Value); - public ParentNode Parent { get; } + if (xml.MoveToAttribute("y")) + y = Utility.ToInt32(xml.Value); - public string Name { get; private set; } + if (xml.MoveToAttribute("z")) + z = Utility.ToInt32(xml.Value); - public Point3D Location { get; private set; } - } + Location = new Point3D(x, y, z); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Go/GoGump.cs b/Scripts/Gumps/Go/GoGump.cs index b988faf6b..ee200e8d1 100644 --- a/Scripts/Gumps/Go/GoGump.cs +++ b/Scripts/Gumps/Go/GoGump.cs @@ -1,241 +1,244 @@ -using System; using Server.Network; namespace Server.Gumps { - public class GoGump : Gump - { - public static readonly LocationTree Felucca = new LocationTree( "felucca.xml", Map.Felucca ); - public static readonly LocationTree Trammel = new LocationTree( "trammel.xml", Map.Trammel ); - public static readonly LocationTree Ilshenar = new LocationTree( "ilshenar.xml", Map.Ilshenar ); - public static readonly LocationTree Malas = new LocationTree( "malas.xml", Map.Malas ); - public static readonly LocationTree Tokuno = new LocationTree( "tokuno.xml", Map.Tokuno ); + public class GoGump : Gump + { + public static readonly LocationTree Felucca = new LocationTree("felucca.xml", Map.Felucca); + public static readonly LocationTree Trammel = new LocationTree("trammel.xml", Map.Trammel); + public static readonly LocationTree Ilshenar = new LocationTree("ilshenar.xml", Map.Ilshenar); + public static readonly LocationTree Malas = new LocationTree("malas.xml", Map.Malas); + public static readonly LocationTree Tokuno = new LocationTree("tokuno.xml", Map.Tokuno); - public static bool OldStyle = PropsConfig.OldStyle; + public static bool OldStyle = PropsConfig.OldStyle; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - private static bool PrevLabel = false, NextLabel = false; + private static bool PrevLabel = false, NextLabel = false; - private static readonly int PrevLabelOffsetX = PrevWidth + 1; - private static readonly int PrevLabelOffsetY = 0; + private static readonly int PrevLabelOffsetX = PrevWidth + 1; + private static readonly int PrevLabelOffsetY = 0; - private static readonly int NextLabelOffsetX = -29; - private static readonly int NextLabelOffsetY = 0; + private static readonly int NextLabelOffsetX = -29; + private static readonly int NextLabelOffsetY = 0; - private static readonly int EntryWidth = 180; - private static readonly int EntryCount = 15; + private static readonly int EntryWidth = 180; + private static readonly int EntryCount = 15; - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (EntryCount + 1)); + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + (EntryHeight + OffsetSize) * (EntryCount + 1); - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private ParentNode m_Node; + private int m_Page; - public static void DisplayTo( Mobile from ) - { - LocationTree tree; + private LocationTree m_Tree; - if ( from.Map == Map.Ilshenar ) - tree = Ilshenar; - else if ( from.Map == Map.Felucca ) - tree = Felucca; - else if ( from.Map == Map.Trammel ) - tree = Trammel; - else if ( from.Map == Map.Malas ) - tree = Malas; - else - tree = Tokuno; + private GoGump(int page, Mobile from, LocationTree tree, ParentNode node) : base(50, 50) + { + from.CloseGump(typeof(GoGump)); - tree.LastBranch.TryGetValue( from, out ParentNode branch ); + tree.LastBranch[from] = node; - if ( branch == null ) - branch = tree.Root; + m_Page = page; + m_Tree = tree; + m_Node = node; - if ( branch != null ) - from.SendGump( new GoGump( 0, from, tree, branch ) ); - } + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - private LocationTree m_Tree; - private ParentNode m_Node; - private int m_Page; + int count = node.Children.Length - page * EntryCount; - private GoGump( int page, Mobile from, LocationTree tree, ParentNode node ) : base( 50, 50 ) - { - from.CloseGump( typeof( GoGump ) ); + if (count < 0) + count = 0; + else if (count > EntryCount) + count = EntryCount; - tree.LastBranch[from] = node; + int totalHeight = OffsetSize + (EntryHeight + OffsetSize) * (count + 1); - m_Page = page; - m_Tree = tree; - m_Node = node; + AddPage(0); - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + AddBackground(0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, + OffsetGumpID); - int count = node.Children.Length - (page * EntryCount); + if (OldStyle) + AddImageTiled(x, y, TotalWidth - OffsetSize * 3 - SetWidth, EntryHeight, HeaderGumpID); + else + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); - if ( count < 0 ) - count = 0; - else if ( count > EntryCount ) - count = EntryCount; + if (node.Parent != null) + { + AddButton(x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 1, GumpButtonType.Reply, 0); - int totalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (count + 1)); + if (PrevLabel) + AddLabel(x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous"); + } - AddPage( 0 ); + x += PrevWidth + OffsetSize; - AddBackground( 0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, OffsetGumpID ); + int emptyWidth = TotalWidth - PrevWidth * 2 - NextWidth - OffsetSize * 5 - + (OldStyle ? SetWidth + OffsetSize : 0); - if ( OldStyle ) - AddImageTiled( x, y, TotalWidth - (OffsetSize * 3) - SetWidth, EntryHeight, HeaderGumpID ); - else - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + if (!OldStyle) + AddImageTiled(x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, + EntryGumpID); - if ( node.Parent != null ) - { - AddButton( x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 1, GumpButtonType.Reply, 0 ); + AddHtml(x + TextOffsetX, y, emptyWidth - TextOffsetX, EntryHeight, $"
{node.Name}
", false, + false); - if ( PrevLabel ) - AddLabel( x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous" ); - } + x += emptyWidth + OffsetSize; - x += PrevWidth + OffsetSize; + if (OldStyle) + AddImageTiled(x, y, TotalWidth - OffsetSize * 3 - SetWidth, EntryHeight, HeaderGumpID); + else + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); - int emptyWidth = TotalWidth - (PrevWidth * 2) - NextWidth - (OffsetSize * 5) - (OldStyle ? SetWidth + OffsetSize : 0); + if (page > 0) + { + AddButton(x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 2, GumpButtonType.Reply, 0); - if ( !OldStyle ) - AddImageTiled( x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, EntryGumpID ); + if (PrevLabel) + AddLabel(x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous"); + } - AddHtml( x + TextOffsetX, y, emptyWidth - TextOffsetX, EntryHeight, $"
{node.Name}
", false, false ); + x += PrevWidth + OffsetSize; - x += emptyWidth + OffsetSize; + if (!OldStyle) + AddImageTiled(x, y, NextWidth, EntryHeight, HeaderGumpID); - if ( OldStyle ) - AddImageTiled( x, y, TotalWidth - (OffsetSize * 3) - SetWidth, EntryHeight, HeaderGumpID ); - else - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + if ((page + 1) * EntryCount < node.Children.Length) + { + AddButton(x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 3, GumpButtonType.Reply, 1); - if ( page > 0 ) - { - AddButton( x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 2, GumpButtonType.Reply, 0 ); + if (NextLabel) + AddLabel(x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next"); + } - if ( PrevLabel ) - AddLabel( x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous" ); - } + for (int i = 0, index = page * EntryCount; i < EntryCount && index < node.Children.Length; ++i, ++index) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x += PrevWidth + OffsetSize; + object child = node.Children[index]; + string name = ""; - if ( !OldStyle ) - AddImageTiled( x, y, NextWidth, EntryHeight, HeaderGumpID ); + if (child is ParentNode parentNode) + name = parentNode.Name; + else if (child is ChildNode childNode) + name = childNode.Name; - if ( (page + 1) * EntryCount < node.Children.Length ) - { - AddButton( x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 3, GumpButtonType.Reply, 1 ); + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, name); - if ( NextLabel ) - AddLabel( x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next" ); - } + x += EntryWidth + OffsetSize; - for ( int i = 0, index = page * EntryCount; i < EntryCount && index < node.Children.Length; ++i, ++index ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - object child = node.Children[index]; - string name = ""; + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, index + 4, GumpButtonType.Reply, 0); + } + } - if ( child is ParentNode parentNode ) - name = parentNode.Name; - else if ( child is ChildNode childNode ) - name = childNode.Name; + public static void DisplayTo(Mobile from) + { + LocationTree tree; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, name ); + if (from.Map == Map.Ilshenar) + tree = Ilshenar; + else if (from.Map == Map.Felucca) + tree = Felucca; + else if (from.Map == Map.Trammel) + tree = Trammel; + else if (from.Map == Map.Malas) + tree = Malas; + else + tree = Tokuno; - x += EntryWidth + OffsetSize; + tree.LastBranch.TryGetValue(from, out ParentNode branch); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + if (branch == null) + branch = tree.Root; - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, index + 4, GumpButtonType.Reply, 0 ); - } - } + if (branch != null) + from.SendGump(new GoGump(0, from, tree, branch)); + } - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; - switch ( info.ButtonID ) - { - case 1: - { - if ( m_Node.Parent != null ) - from.SendGump( new GoGump( 0, from, m_Tree, m_Node.Parent ) ); + switch (info.ButtonID) + { + case 1: + { + if (m_Node.Parent != null) + from.SendGump(new GoGump(0, from, m_Tree, m_Node.Parent)); - break; - } - case 2: - { - if ( m_Page > 0 ) - from.SendGump( new GoGump( m_Page - 1, from, m_Tree, m_Node ) ); + break; + } + case 2: + { + if (m_Page > 0) + from.SendGump(new GoGump(m_Page - 1, from, m_Tree, m_Node)); - break; - } - case 3: - { - if ( (m_Page + 1) * EntryCount < m_Node.Children.Length ) - from.SendGump( new GoGump( m_Page + 1, from, m_Tree, m_Node ) ); + break; + } + case 3: + { + if ((m_Page + 1) * EntryCount < m_Node.Children.Length) + from.SendGump(new GoGump(m_Page + 1, from, m_Tree, m_Node)); - break; - } - default: - { - int index = info.ButtonID - 4; + break; + } + default: + { + int index = info.ButtonID - 4; - if ( index >= 0 && index < m_Node.Children.Length ) - { - object o = m_Node.Children[index]; + if (index >= 0 && index < m_Node.Children.Length) + { + object o = m_Node.Children[index]; - if ( o is ParentNode node ) - from.SendGump( new GoGump( 0, from, m_Tree, node ) ); - else - from.MoveToWorld(((ChildNode)o).Location, m_Tree.Map ); - } + if (o is ParentNode node) + from.SendGump(new GoGump(0, from, m_Tree, node)); + else + from.MoveToWorld(((ChildNode)o).Location, m_Tree.Map); + } - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Go/LocationTree.cs b/Scripts/Gumps/Go/LocationTree.cs index 0ffa6d584..618d51033 100644 --- a/Scripts/Gumps/Go/LocationTree.cs +++ b/Scripts/Gumps/Go/LocationTree.cs @@ -4,40 +4,40 @@ using System.Xml; namespace Server.Gumps { - public class LocationTree - { - public LocationTree( string fileName, Map map ) - { - LastBranch = new Dictionary(); - Map = map; + public class LocationTree + { + public LocationTree(string fileName, Map map) + { + LastBranch = new Dictionary(); + Map = map; - string path = Path.Combine( "Data/Locations/", fileName ); + string path = Path.Combine("Data/Locations/", fileName); - if ( File.Exists( path ) ) - { - XmlTextReader xml = new XmlTextReader( new StreamReader( path ) ); + if (File.Exists(path)) + { + XmlTextReader xml = new XmlTextReader(new StreamReader(path)); - xml.WhitespaceHandling = WhitespaceHandling.None; + xml.WhitespaceHandling = WhitespaceHandling.None; - Root = Parse( xml ); + Root = Parse(xml); - xml.Close(); - } - } + xml.Close(); + } + } - public Dictionary LastBranch { get; } + public Dictionary LastBranch{ get; } - public Map Map { get; } + public Map Map{ get; } - public ParentNode Root { get; } + public ParentNode Root{ get; } - private ParentNode Parse( XmlTextReader xml ) - { - xml.Read(); - xml.Read(); - xml.Read(); + private ParentNode Parse(XmlTextReader xml) + { + xml.Read(); + xml.Read(); + xml.Read(); - return new ParentNode( xml, null ); - } - } + return new ParentNode(xml, null); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Go/ParentNode.cs b/Scripts/Gumps/Go/ParentNode.cs index ae37244fe..1bda990ad 100644 --- a/Scripts/Gumps/Go/ParentNode.cs +++ b/Scripts/Gumps/Go/ParentNode.cs @@ -1,57 +1,57 @@ -using System.Xml; using System.Collections; +using System.Xml; namespace Server.Gumps { - public class ParentNode - { - public ParentNode( XmlTextReader xml, ParentNode parent ) - { - Parent = parent; + public class ParentNode + { + public ParentNode(XmlTextReader xml, ParentNode parent) + { + Parent = parent; - Parse( xml ); - } + Parse(xml); + } - private void Parse( XmlTextReader xml ) - { - if ( xml.MoveToAttribute( "name" ) ) - Name = xml.Value; - else - Name = "empty"; + public ParentNode Parent{ get; } - if ( xml.IsEmptyElement ) - { - Children = new object[0]; - } - else - { - ArrayList children = new ArrayList(); + public object[] Children{ get; private set; } - while ( xml.Read() && ( xml.NodeType == XmlNodeType.Element || xml.NodeType == XmlNodeType.Comment ) ) - { - if ( xml.NodeType == XmlNodeType.Comment ) - continue; + public string Name{ get; private set; } - if ( xml.Name == "child" ) - { - ChildNode n = new ChildNode( xml, this ); + private void Parse(XmlTextReader xml) + { + if (xml.MoveToAttribute("name")) + Name = xml.Value; + else + Name = "empty"; - children.Add( n ); - } - else - { - children.Add( new ParentNode( xml, this ) ); - } - } + if (xml.IsEmptyElement) + { + Children = new object[0]; + } + else + { + ArrayList children = new ArrayList(); - Children = children.ToArray(); - } - } + while (xml.Read() && (xml.NodeType == XmlNodeType.Element || xml.NodeType == XmlNodeType.Comment)) + { + if (xml.NodeType == XmlNodeType.Comment) + continue; - public ParentNode Parent { get; } + if (xml.Name == "child") + { + ChildNode n = new ChildNode(xml, this); - public object[] Children { get; private set; } + children.Add(n); + } + else + { + children.Add(new ParentNode(xml, this)); + } + } - public string Name { get; private set; } - } + Children = children.ToArray(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/DeclareFealtyGump.cs b/Scripts/Gumps/Guilds/DeclareFealtyGump.cs index bc1d16cad..b18b07efb 100644 --- a/Scripts/Gumps/Guilds/DeclareFealtyGump.cs +++ b/Scripts/Gumps/Guilds/DeclareFealtyGump.cs @@ -3,50 +3,47 @@ using Server.Network; namespace Server.Gumps { - public class DeclareFealtyGump : GuildMobileListGump - { - public DeclareFealtyGump( Mobile from, Guild guild ) : base( from, guild, true, guild.Members ) - { - } + public class DeclareFealtyGump : GuildMobileListGump + { + public DeclareFealtyGump(Mobile from, Guild guild) : base(from, guild, true, guild.Members) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011097, false, false ); // Declare your fealty + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011097, false, false); // Declare your fealty - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 250, 35, 1011098, false, false ); // I have selected my new lord. + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 250, 35, 1011098, false, false); // I have selected my new lord. - AddButton( 300, 400, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Mobile m = (Mobile)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Mobile m = m_List[index]; - if ( m != null && !m.Deleted ) - { - state.Mobile.GuildFealty = m; - } - } - } - } + if (m != null && !m.Deleted) state.Mobile.GuildFealty = m; + } + } + } - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); - } - } -} + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GrantGuildTitleGump.cs b/Scripts/Gumps/Guilds/GrantGuildTitleGump.cs index ab4618a11..8e6c50732 100644 --- a/Scripts/Gumps/Guilds/GrantGuildTitleGump.cs +++ b/Scripts/Gumps/Guilds/GrantGuildTitleGump.cs @@ -3,53 +3,53 @@ using Server.Network; namespace Server.Gumps { - public class GrantGuildTitleGump : GuildMobileListGump - { - public GrantGuildTitleGump( Mobile from, Guild guild ) : base( from, guild, true, guild.Members ) - { - } + public class GrantGuildTitleGump : GuildMobileListGump + { + public GrantGuildTitleGump(Mobile from, Guild guild) : base(from, guild, true, guild.Members) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011118, false, false ); // Grant a title to another member. + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011118, false, false); // Grant a title to another member. - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011127, false, false ); // I dub thee... + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011127, false, false); // I dub thee... - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Mobile m = (Mobile)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Mobile m = m_List[index]; - if ( m != null && !m.Deleted ) - { - m_Mobile.SendLocalizedMessage( 1013074 ); // New title (20 characters max): - m_Mobile.Prompt = new GuildTitlePrompt( m_Mobile, m, m_Guild ); - } - } - } - } - else if ( info.ButtonID == 2 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m != null && !m.Deleted) + { + m_Mobile.SendLocalizedMessage(1013074); // New title (20 characters max): + m_Mobile.Prompt = new GuildTitlePrompt(m_Mobile, m, m_Guild); + } + } + } + } + else if (info.ButtonID == 2) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildAbbrvPrompt.cs b/Scripts/Gumps/Guilds/GuildAbbrvPrompt.cs index 5ad261caf..f0f94a1c0 100644 --- a/Scripts/Gumps/Guilds/GuildAbbrvPrompt.cs +++ b/Scripts/Gumps/Guilds/GuildAbbrvPrompt.cs @@ -3,51 +3,51 @@ using Server.Prompts; namespace Server.Gumps { - public class GuildAbbrvPrompt : Prompt - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildAbbrvPrompt : Prompt + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildAbbrvPrompt( Mobile m, Guild g ) - { - m_Mobile = m; - m_Guild = g; - } + public GuildAbbrvPrompt(Mobile m, Guild g) + { + m_Mobile = m; + m_Guild = g; + } - public override void OnCancel( Mobile from ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnCancel(Mobile from) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } - public override void OnResponse( Mobile from, string text ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(Mobile from, string text) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - text = text.Trim(); + text = text.Trim(); - if ( text.Length > 3 ) - text = text.Substring( 0, 3 ); + if (text.Length > 3) + text = text.Substring(0, 3); - if ( text.Length > 0 ) - { - if ( BaseGuild.FindByAbbrev( text ) != null ) - { - m_Mobile.SendMessage( "{0} conflicts with the abbreviation of an existing guild.", text ); - } - else - { - m_Guild.Abbreviation = text; - m_Guild.GuildMessage( 1018025, true, text ); // Your guild abbreviation has changed: - } - } + if (text.Length > 0) + { + if (BaseGuild.FindByAbbrev(text) != null) + { + m_Mobile.SendMessage("{0} conflicts with the abbreviation of an existing guild.", text); + } + else + { + m_Guild.Abbreviation = text; + m_Guild.GuildMessage(1018025, true, text); // Your guild abbreviation has changed: + } + } - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildAcceptWarGump.cs b/Scripts/Gumps/Guilds/GuildAcceptWarGump.cs index e70dee566..aa3dfbadf 100644 --- a/Scripts/Gumps/Guilds/GuildAcceptWarGump.cs +++ b/Scripts/Gumps/Guilds/GuildAcceptWarGump.cs @@ -3,63 +3,63 @@ using Server.Network; namespace Server.Gumps { - public class GuildAcceptWarGump : GuildListGump - { - public GuildAcceptWarGump( Mobile from, Guild guild ) : base( from, guild, true, guild.WarInvitations ) - { - } + public class GuildAcceptWarGump : GuildListGump + { + public GuildAcceptWarGump(Mobile from, Guild guild) : base(from, guild, true, guild.WarInvitations) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011147, false, false ); // Select the guild to accept the invitations: + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011147, false, false); // Select the guild to accept the invitations: - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011100, false, false ); // Accept war invitations. + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011100, false, false); // Accept war invitations. - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Guild g = (Guild)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Guild g = m_List[index]; - if ( g != null ) - { - m_Guild.WarInvitations.Remove( g ); - g.WarDeclarations.Remove( m_Guild ); + if (g != null) + { + m_Guild.WarInvitations.Remove(g); + g.WarDeclarations.Remove(m_Guild); - m_Guild.AddEnemy( g ); - m_Guild.GuildMessage( 1018020, true, "{0} ({1})", g.Name, g.Abbreviation ); + m_Guild.AddEnemy(g); + m_Guild.GuildMessage(1018020, true, "{0} ({1})", g.Name, g.Abbreviation); - GuildGump.EnsureClosed( m_Mobile ); + GuildGump.EnsureClosed(m_Mobile); - if ( m_Guild.WarInvitations.Count > 0 ) - m_Mobile.SendGump( new GuildAcceptWarGump( m_Mobile, m_Guild ) ); - else - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } - } - else if ( info.ButtonID == 2 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m_Guild.WarInvitations.Count > 0) + m_Mobile.SendGump(new GuildAcceptWarGump(m_Mobile, m_Guild)); + else + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } + } + else if (info.ButtonID == 2) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildAdminCandidatesGump.cs b/Scripts/Gumps/Guilds/GuildAdminCandidatesGump.cs index ace292939..ec1218527 100644 --- a/Scripts/Gumps/Guilds/GuildAdminCandidatesGump.cs +++ b/Scripts/Gumps/Guilds/GuildAdminCandidatesGump.cs @@ -1,125 +1,131 @@ +using Server.Factions; using Server.Guilds; using Server.Network; -using Server.Factions; namespace Server.Gumps { - public class GuildAdminCandidatesGump : GuildMobileListGump - { - public GuildAdminCandidatesGump( Mobile from, Guild guild ) : base( from, guild, true, guild.Candidates ) - { - } + public class GuildAdminCandidatesGump : GuildMobileListGump + { + public GuildAdminCandidatesGump(Mobile from, Guild guild) : base(from, guild, true, guild.Candidates) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1013075, false, false ); // Accept or Refuse candidates for membership + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1013075, false, false); // Accept or Refuse candidates for membership - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1013076, false, false ); // Accept + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1013076, false, false); // Accept - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1013077, false, false ); // Refuse - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1013077, false, false); // Refuse + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - switch ( info.ButtonID ) - { - case 0: - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); + switch (info.ButtonID) + { + case 0: + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); - break; - } - case 1: // Accept - { - int[] switches = info.Switches; + break; + } + case 1: // Accept + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Mobile m = (Mobile)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Mobile m = m_List[index]; - if ( m != null && !m.Deleted ) - { - #region Factions - PlayerState guildState = PlayerState.Find( m_Guild.Leader ); - PlayerState targetState = PlayerState.Find( m ); + if (m != null && !m.Deleted) + { + #region Factions - Faction guildFaction = guildState?.Faction; - Faction targetFaction = targetState?.Faction; + PlayerState guildState = PlayerState.Find(m_Guild.Leader); + PlayerState targetState = PlayerState.Find(m); - if ( guildFaction != targetFaction ) - { - if ( guildFaction == null ) - m_Mobile.SendLocalizedMessage( 1013027 ); // That player cannot join a non-faction guild. - else if ( targetFaction == null ) - m_Mobile.SendLocalizedMessage( 1013026 ); // That player must be in a faction before joining this guild. - else - m_Mobile.SendLocalizedMessage( 1013028 ); // That person has a different faction affiliation. + Faction guildFaction = guildState?.Faction; + Faction targetFaction = targetState?.Faction; - break; - } + if (guildFaction != targetFaction) + { + if (guildFaction == null) + m_Mobile.SendLocalizedMessage( + 1013027); // That player cannot join a non-faction guild. + else if (targetFaction == null) + m_Mobile.SendLocalizedMessage( + 1013026); // That player must be in a faction before joining this guild. + else + m_Mobile.SendLocalizedMessage( + 1013028); // That person has a different faction affiliation. - if ( targetState != null && targetState.IsLeaving ) - { - // OSI does this quite strangely, so we'll just do it this way - m_Mobile.SendMessage( "That person is quitting their faction and so you may not recruit them." ); - break; - } - #endregion + break; + } - m_Guild.Candidates.Remove( m ); - m_Guild.Accepted.Add( m ); + if (targetState != null && targetState.IsLeaving) + { + // OSI does this quite strangely, so we'll just do it this way + m_Mobile.SendMessage( + "That person is quitting their faction and so you may not recruit them."); + break; + } - GuildGump.EnsureClosed( m_Mobile ); + #endregion - if ( m_Guild.Candidates.Count > 0 ) - m_Mobile.SendGump( new GuildAdminCandidatesGump( m_Mobile, m_Guild ) ); - else - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + m_Guild.Candidates.Remove(m); + m_Guild.Accepted.Add(m); - break; - } - case 2: // Refuse - { - int[] switches = info.Switches; + GuildGump.EnsureClosed(m_Mobile); - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (m_Guild.Candidates.Count > 0) + m_Mobile.SendGump(new GuildAdminCandidatesGump(m_Mobile, m_Guild)); + else + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } - if ( index >= 0 && index < m_List.Count ) - { - Mobile m = (Mobile)m_List[index]; + break; + } + case 2: // Refuse + { + int[] switches = info.Switches; - if ( m != null && !m.Deleted ) - { - m_Guild.Candidates.Remove( m ); + if (switches.Length > 0) + { + int index = switches[0]; - GuildGump.EnsureClosed( m_Mobile ); + if (index >= 0 && index < m_List.Count) + { + Mobile m = m_List[index]; - if ( m_Guild.Candidates.Count > 0 ) - m_Mobile.SendGump( new GuildAdminCandidatesGump( m_Mobile, m_Guild ) ); - else - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m != null && !m.Deleted) + { + m_Guild.Candidates.Remove(m); - break; - } - } - } - } + GuildGump.EnsureClosed(m_Mobile); + + if (m_Guild.Candidates.Count > 0) + m_Mobile.SendGump(new GuildAdminCandidatesGump(m_Mobile, m_Guild)); + else + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } + + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildCandidatesGump.cs b/Scripts/Gumps/Guilds/GuildCandidatesGump.cs index 5f7cfa65e..92103b735 100644 --- a/Scripts/Gumps/Guilds/GuildCandidatesGump.cs +++ b/Scripts/Gumps/Guilds/GuildCandidatesGump.cs @@ -3,30 +3,30 @@ using Server.Network; namespace Server.Gumps { - public class GuildCandidatesGump : GuildMobileListGump - { - public GuildCandidatesGump( Mobile from, Guild guild ) : base( from, guild, false, guild.Candidates ) - { - } + public class GuildCandidatesGump : GuildMobileListGump + { + public GuildCandidatesGump(Mobile from, Guild guild) : base(from, guild, false, guild.Candidates) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 500, 35, 1013030, false, false ); //
Candidates
+ protected override void Design() + { + AddHtmlLocalized(20, 10, 500, 35, 1013030, false, false); //
Candidates
- AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 300, 35, 1011120, false, false ); // Return to the main menu. - } + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 300, 35, 1011120, false, false); // Return to the main menu. + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); - } - } - } + if (info.ButtonID == 1) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildChangeTypeGump.cs b/Scripts/Gumps/Guilds/GuildChangeTypeGump.cs index ad4e839e2..5c0533337 100644 --- a/Scripts/Gumps/Guilds/GuildChangeTypeGump.cs +++ b/Scripts/Gumps/Guilds/GuildChangeTypeGump.cs @@ -1,91 +1,101 @@ using System; +using Server.Factions; using Server.Guilds; using Server.Mobiles; using Server.Network; -using Server.Factions; namespace Server.Gumps { - public class GuildChangeTypeGump : Gump - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildChangeTypeGump : Gump + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildChangeTypeGump( Mobile from, Guild guild ) : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + public GuildChangeTypeGump(Mobile from, Guild guild) : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 400, 5054 ); - AddBackground( 10, 10, 530, 380, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 400, 5054); + AddBackground(10, 10, 530, 380, 3000); - AddHtmlLocalized( 20, 15, 510, 30, 1013062, false, false ); //
Change Guild Type Menu
+ AddHtmlLocalized(20, 15, 510, 30, 1013062, false, false); //
Change Guild Type Menu
- AddHtmlLocalized( 50, 50, 450, 30, 1013066, false, false ); // Please select the type of guild you would like to change to + AddHtmlLocalized(50, 50, 450, 30, 1013066, false, + false); // Please select the type of guild you would like to change to - AddButton( 20, 100, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 85, 100, 300, 30, 1013063, false, false ); // Standard guild + AddButton(20, 100, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(85, 100, 300, 30, 1013063, false, false); // Standard guild - AddButton( 20, 150, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddItem( 50, 143, 7109 ); - AddHtmlLocalized( 85, 150, 300, 300, 1013064, false, false ); // Order guild + AddButton(20, 150, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddItem(50, 143, 7109); + AddHtmlLocalized(85, 150, 300, 300, 1013064, false, false); // Order guild - AddButton( 20, 200, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddItem( 45, 200, 7107 ); - AddHtmlLocalized( 85, 200, 300, 300, 1013065, false, false ); // Chaos guild + AddButton(20, 200, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddItem(45, 200, 7107); + AddHtmlLocalized(85, 200, 300, 300, 1013065, false, false); // Chaos guild - AddButton( 300, 360, 4005, 4007, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 360, 150, 30, 1011012, false, false ); // CANCEL - } + AddButton(300, 360, 4005, 4007, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 360, 150, 30, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( ( Guild.NewGuildSystem && !BaseGuildGump.IsLeader( m_Mobile, m_Guild ) ) || ( !Guild.NewGuildSystem && GuildGump.BadLeader( m_Mobile, m_Guild ) ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (Guild.NewGuildSystem && !BaseGuildGump.IsLeader(m_Mobile, m_Guild) || + !Guild.NewGuildSystem && GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - GuildType newType; + GuildType newType; - switch ( info.ButtonID ) - { - default: newType = m_Guild.Type; break; - case 1: newType = GuildType.Regular; break; - case 2: newType = GuildType.Order; break; - case 3: newType = GuildType.Chaos; break; - } + switch (info.ButtonID) + { + default: + newType = m_Guild.Type; + break; + case 1: + newType = GuildType.Regular; + break; + case 2: + newType = GuildType.Order; + break; + case 3: + newType = GuildType.Chaos; + break; + } - if ( m_Guild.Type != newType ) - { - PlayerState pl = PlayerState.Find( m_Mobile ); + if (m_Guild.Type != newType) + { + PlayerState pl = PlayerState.Find(m_Mobile); - if ( pl != null ) - { - m_Mobile.SendLocalizedMessage( 1010405 ); // You cannot change guild types while in a Faction! - } - else if ( m_Guild.TypeLastChange.AddDays( 7 ) > DateTime.UtcNow ) - { - m_Mobile.SendLocalizedMessage( 1011142 ); // You have already changed your guild type recently. - // TODO: Clilocs 1011142-1011145 suggest a timer for pending changes - } - else - { - m_Guild.Type = newType; - m_Guild.GuildMessage( 1018022, true, newType.ToString() ); // Guild Message: Your guild type has changed: - } - } + if (pl != null) + { + m_Mobile.SendLocalizedMessage(1010405); // You cannot change guild types while in a Faction! + } + else if (m_Guild.TypeLastChange.AddDays(7) > DateTime.UtcNow) + { + m_Mobile.SendLocalizedMessage(1011142); // You have already changed your guild type recently. + // TODO: Clilocs 1011142-1011145 suggest a timer for pending changes + } + else + { + m_Guild.Type = newType; + m_Guild.GuildMessage(1018022, true, newType.ToString()); // Guild Message: Your guild type has changed: + } + } - if ( Guild.NewGuildSystem ) - { - if ( m_Mobile is PlayerMobile mobile ) - mobile.SendGump( new GuildInfoGump( mobile, m_Guild ) ); + if (Guild.NewGuildSystem) + { + if (m_Mobile is PlayerMobile mobile) + mobile.SendGump(new GuildInfoGump(mobile, m_Guild)); - return; - } + return; + } - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } -} + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildCharterGump.cs b/Scripts/Gumps/Guilds/GuildCharterGump.cs index f665237ae..bc4c884bd 100644 --- a/Scripts/Gumps/Guilds/GuildCharterGump.cs +++ b/Scripts/Gumps/Guilds/GuildCharterGump.cs @@ -3,68 +3,67 @@ using Server.Network; namespace Server.Gumps { - public class GuildCharterGump : Gump - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildCharterGump : Gump + { + private const string DefaultWebsite = "https://github.com/runuo/"; + private Guild m_Guild; + private Mobile m_Mobile; - private const string DefaultWebsite = "https://github.com/runuo/"; + public GuildCharterGump(Mobile from, Guild guild) : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - public GuildCharterGump( Mobile from, Guild guild ) : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + Dragable = false; - Dragable = false; + AddPage(0); + AddBackground(0, 0, 550, 400, 5054); + AddBackground(10, 10, 530, 380, 3000); - AddPage( 0 ); - AddBackground( 0, 0, 550, 400, 5054 ); - AddBackground( 10, 10, 530, 380, 3000 ); + AddButton(20, 360, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 360, 300, 35, 1011120, false, false); // Return to the main menu. - AddButton( 20, 360, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 360, 300, 35, 1011120, false, false ); // Return to the main menu. + string charter; - string charter; + if ((charter = guild.Charter) == null || (charter = charter.Trim()).Length <= 0) + AddHtmlLocalized(20, 20, 400, 35, 1013032, false, false); // No charter has been defined. + else + AddHtml(20, 20, 510, 75, charter, true, true); - if ( (charter = guild.Charter) == null || (charter = charter.Trim()).Length <= 0 ) - AddHtmlLocalized( 20, 20, 400, 35, 1013032, false, false ); // No charter has been defined. - else - AddHtml( 20, 20, 510, 75, charter, true, true ); + AddButton(20, 200, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 200, 300, 20, 1011122, false, false); // Visit the guild website : - AddButton( 20, 200, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 200, 300, 20, 1011122, false, false ); // Visit the guild website : + string website; - string website; + if ((website = guild.Website) == null || (website = website.Trim()).Length <= 0) + website = DefaultWebsite; - if ( (website = guild.Website) == null || (website = website.Trim()).Length <= 0 ) - website = DefaultWebsite; + AddHtml(55, 220, 300, 20, website, false, false); + } - AddHtml( 55, 220, 300, 20, website, false, false ); - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + switch (info.ButtonID) + { + case 0: return; // Close + case 1: break; // Return to main menu + case 2: + { + string website; - switch ( info.ButtonID ) - { - case 0: return; // Close - case 1: break; // Return to main menu - case 2: - { - string website; + if ((website = m_Guild.Website) == null || (website = website.Trim()).Length <= 0) + website = DefaultWebsite; - if ( (website = m_Guild.Website) == null || (website = website.Trim()).Length <= 0 ) - website = DefaultWebsite; + m_Mobile.LaunchBrowser(website); + break; + } + } - m_Mobile.LaunchBrowser( website ); - break; - } - } - - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); - } - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildCharterPrompt.cs b/Scripts/Gumps/Guilds/GuildCharterPrompt.cs index cc0491347..e3f265ba1 100644 --- a/Scripts/Gumps/Guilds/GuildCharterPrompt.cs +++ b/Scripts/Gumps/Guilds/GuildCharterPrompt.cs @@ -3,44 +3,44 @@ using Server.Prompts; namespace Server.Gumps { - public class GuildCharterPrompt : Prompt - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildCharterPrompt : Prompt + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildCharterPrompt( Mobile m, Guild g ) - { - m_Mobile = m; - m_Guild = g; - } + public GuildCharterPrompt(Mobile m, Guild g) + { + m_Mobile = m; + m_Guild = g; + } - public override void OnCancel( Mobile from ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnCancel(Mobile from) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } - public override void OnResponse( Mobile from, string text ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(Mobile from, string text) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - text = text.Trim(); + text = text.Trim(); - if ( text.Length > 50 ) - text = text.Substring( 0, 50 ); + if (text.Length > 50) + text = text.Substring(0, 50); - if ( text.Length > 0 ) - m_Guild.Charter = text; + if (text.Length > 0) + m_Guild.Charter = text; - m_Mobile.SendLocalizedMessage( 1013072 ); // Enter the new website for the guild (50 characters max): - m_Mobile.Prompt = new GuildWebsitePrompt( m_Mobile, m_Guild ); + m_Mobile.SendLocalizedMessage(1013072); // Enter the new website for the guild (50 characters max): + m_Mobile.Prompt = new GuildWebsitePrompt(m_Mobile, m_Guild); - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildDeclarePeaceGump.cs b/Scripts/Gumps/Guilds/GuildDeclarePeaceGump.cs index da5198852..ffc0b12ab 100644 --- a/Scripts/Gumps/Guilds/GuildDeclarePeaceGump.cs +++ b/Scripts/Gumps/Guilds/GuildDeclarePeaceGump.cs @@ -3,60 +3,61 @@ using Server.Network; namespace Server.Gumps { - public class GuildDeclarePeaceGump : GuildListGump - { - public GuildDeclarePeaceGump( Mobile from, Guild guild ) : base( from, guild, true, guild.Enemies ) - { - } + public class GuildDeclarePeaceGump : GuildListGump + { + public GuildDeclarePeaceGump(Mobile from, Guild guild) : base(from, guild, true, guild.Enemies) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011137, false, false ); // Select the guild you wish to declare peace with. + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011137, false, false); // Select the guild you wish to declare peace with. - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011138, false, false ); // Send the olive branch. + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011138, false, false); // Send the olive branch. - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Guild g = (Guild)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Guild g = m_List[index]; - if ( g != null ) - { - m_Guild.RemoveEnemy( g ); - m_Guild.GuildMessage( 1018018, true, "{0} ({1})", g.Name, g.Abbreviation ); // Guild Message: You are now at peace with this guild: + if (g != null) + { + m_Guild.RemoveEnemy(g); + m_Guild.GuildMessage(1018018, true, "{0} ({1})", g.Name, + g.Abbreviation); // Guild Message: You are now at peace with this guild: - GuildGump.EnsureClosed( m_Mobile ); + GuildGump.EnsureClosed(m_Mobile); - if ( m_Guild.Enemies.Count > 0 ) - m_Mobile.SendGump( new GuildDeclarePeaceGump( m_Mobile, m_Guild ) ); - else - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } - } - else if ( info.ButtonID == 2 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m_Guild.Enemies.Count > 0) + m_Mobile.SendGump(new GuildDeclarePeaceGump(m_Mobile, m_Guild)); + else + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } + } + else if (info.ButtonID == 2) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildDeclareWarGump.cs b/Scripts/Gumps/Guilds/GuildDeclareWarGump.cs index 742d77bd0..079299d99 100644 --- a/Scripts/Gumps/Guilds/GuildDeclareWarGump.cs +++ b/Scripts/Gumps/Guilds/GuildDeclareWarGump.cs @@ -1,85 +1,89 @@ +using System.Collections.Generic; +using Server.Factions; using Server.Guilds; using Server.Network; -using Server.Factions; -using System.Collections.Generic; namespace Server.Gumps { - public class GuildDeclareWarGump : GuildListGump - { - public GuildDeclareWarGump( Mobile from, Guild guild, List list ) - : base( from, guild, true, list ) - { - } + public class GuildDeclareWarGump : GuildListGump + { + public GuildDeclareWarGump(Mobile from, Guild guild, List list) + : base(from, guild, true, list) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011065, false, false ); // Select the guild you wish to declare war on. + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011065, false, false); // Select the guild you wish to declare war on. - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011068, false, false ); // Send the challenge! + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011068, false, false); // Send the challenge! - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Guild g = m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Guild g = m_List[index]; - if ( g != null ) - { - if ( g == m_Guild ) - { - m_Mobile.SendLocalizedMessage( 501184 ); // You cannot declare war against yourself! - } - else if ( (g.WarInvitations.Contains( m_Guild ) && m_Guild.WarDeclarations.Contains( g )) || m_Guild.IsWar( g ) ) - { - m_Mobile.SendLocalizedMessage( 501183 ); // You are already at war with that guild. - } - else if ( Faction.Find( m_Guild.Leader ) != null ) - { - m_Mobile.SendLocalizedMessage( 1005288 ); // You cannot declare war while you are in a faction - } - else - { - if ( !m_Guild.WarDeclarations.Contains( g ) ) - { - m_Guild.WarDeclarations.Add( g ); - m_Guild.GuildMessage( 1018019, true, "{0} ({1})", g.Name, g.Abbreviation ); // Guild Message: Your guild has sent an invitation for war: - } + if (g != null) + { + if (g == m_Guild) + { + m_Mobile.SendLocalizedMessage(501184); // You cannot declare war against yourself! + } + else if (g.WarInvitations.Contains(m_Guild) && m_Guild.WarDeclarations.Contains(g) || + m_Guild.IsWar(g)) + { + m_Mobile.SendLocalizedMessage(501183); // You are already at war with that guild. + } + else if (Faction.Find(m_Guild.Leader) != null) + { + m_Mobile.SendLocalizedMessage(1005288); // You cannot declare war while you are in a faction + } + else + { + if (!m_Guild.WarDeclarations.Contains(g)) + { + m_Guild.WarDeclarations.Add(g); + m_Guild.GuildMessage(1018019, true, "{0} ({1})", g.Name, + g.Abbreviation); // Guild Message: Your guild has sent an invitation for war: + } - if ( !g.WarInvitations.Contains( m_Guild ) ) - { - g.WarInvitations.Add( m_Guild ); - g.GuildMessage( 1018021, true, "{0} ({1})", m_Guild.Name, m_Guild.Abbreviation ); // Guild Message: Your guild has received an invitation to war: - } - } + if (!g.WarInvitations.Contains(m_Guild)) + { + g.WarInvitations.Add(m_Guild); + g.GuildMessage(1018021, true, "{0} ({1})", m_Guild.Name, + m_Guild + .Abbreviation); // Guild Message: Your guild has received an invitation to war: + } + } - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildWarAdminGump( m_Mobile, m_Guild ) ); - } - } - } - } - else if ( info.ButtonID == 2 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } -} + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildWarAdminGump(m_Mobile, m_Guild)); + } + } + } + } + else if (info.ButtonID == 2) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildDeclareWarPrompt.cs b/Scripts/Gumps/Guilds/GuildDeclareWarPrompt.cs index 1f3f1d5aa..fbd03c56a 100644 --- a/Scripts/Gumps/Guilds/GuildDeclareWarPrompt.cs +++ b/Scripts/Gumps/Guilds/GuildDeclareWarPrompt.cs @@ -1,56 +1,56 @@ +using System.Collections.Generic; using Server.Guilds; using Server.Prompts; -using System.Collections.Generic; namespace Server.Gumps { - public class GuildDeclareWarPrompt : Prompt - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildDeclareWarPrompt : Prompt + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildDeclareWarPrompt( Mobile m, Guild g ) - { - m_Mobile = m; - m_Guild = g; - } + public GuildDeclareWarPrompt(Mobile m, Guild g) + { + m_Mobile = m; + m_Guild = g; + } - public override void OnCancel( Mobile from ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnCancel(Mobile from) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildWarAdminGump( m_Mobile, m_Guild ) ); - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildWarAdminGump(m_Mobile, m_Guild)); + } - public override void OnResponse( Mobile from, string text ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(Mobile from, string text) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - text = text.Trim(); + text = text.Trim(); - if ( text.Length >= 3 ) - { - List guilds = Utility.CastConvertList( BaseGuild.Search( text ) ); + if (text.Length >= 3) + { + List guilds = Utility.CastConvertList(BaseGuild.Search(text)); - GuildGump.EnsureClosed( m_Mobile ); + GuildGump.EnsureClosed(m_Mobile); - if ( guilds.Count > 0 ) - { - m_Mobile.SendGump( new GuildDeclareWarGump( m_Mobile, m_Guild, guilds ) ); - } - else - { - m_Mobile.SendGump( new GuildWarAdminGump( m_Mobile, m_Guild ) ); - m_Mobile.SendLocalizedMessage( 1018003 ); // No guilds found matching - try another name in the search - } - } - else - { - m_Mobile.SendMessage( "Search string must be at least three letters in length." ); - } - } - } + if (guilds.Count > 0) + { + m_Mobile.SendGump(new GuildDeclareWarGump(m_Mobile, m_Guild, guilds)); + } + else + { + m_Mobile.SendGump(new GuildWarAdminGump(m_Mobile, m_Guild)); + m_Mobile.SendLocalizedMessage(1018003); // No guilds found matching - try another name in the search + } + } + else + { + m_Mobile.SendMessage("Search string must be at least three letters in length."); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildDismissGump.cs b/Scripts/Gumps/Guilds/GuildDismissGump.cs index ac59a86bb..23e79990b 100644 --- a/Scripts/Gumps/Guilds/GuildDismissGump.cs +++ b/Scripts/Gumps/Guilds/GuildDismissGump.cs @@ -3,58 +3,58 @@ using Server.Network; namespace Server.Gumps { - public class GuildDismissGump : GuildMobileListGump - { - public GuildDismissGump ( Mobile from, Guild guild ) : base( from, guild, true, guild.Members ) - { - } + public class GuildDismissGump : GuildMobileListGump + { + public GuildDismissGump(Mobile from, Guild guild) : base(from, guild, true, guild.Members) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011124, false, false ); // Whom do you wish to dismiss? + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011124, false, false); // Whom do you wish to dismiss? - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011125, false, false ); // Kick them out! + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011125, false, false); // Kick them out! - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Mobile m = (Mobile)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Mobile m = m_List[index]; - if ( m != null && !m.Deleted ) - { - m_Guild.RemoveMember( m ); + if (m != null && !m.Deleted) + { + m_Guild.RemoveMember(m); - if ( m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Mobile == m_Guild.Leader ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } - } - } - else if ( info.ButtonID == 2 && (m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Mobile == m_Guild.Leader) ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Mobile == m_Guild.Leader) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } + } + } + else if (info.ButtonID == 2 && (m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Mobile == m_Guild.Leader)) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildGump.cs b/Scripts/Gumps/Guilds/GuildGump.cs index 4aa292a68..28ce5215f 100644 --- a/Scripts/Gumps/Guilds/GuildGump.cs +++ b/Scripts/Gumps/Guilds/GuildGump.cs @@ -3,218 +3,220 @@ using Server.Network; namespace Server.Gumps { - public class GuildGump : Gump - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildGump : Gump + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildGump( Mobile beholder, Guild guild ) : base( 20, 30 ) - { - m_Mobile = beholder; - m_Guild = guild; + public GuildGump(Mobile beholder, Guild guild) : base(20, 30) + { + m_Mobile = beholder; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 400, 5054 ); - AddBackground( 10, 10, 530, 380, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 400, 5054); + AddBackground(10, 10, 530, 380, 3000); - AddHtml( 20, 15, 200, 35, guild.Name, false, false ); + AddHtml(20, 15, 200, 35, guild.Name, false, false); - Mobile leader = guild.Leader; + Mobile leader = guild.Leader; - if ( leader != null ) - { - string leadTitle; + if (leader != null) + { + string leadTitle; - if ( (leadTitle = leader.GuildTitle) != null && (leadTitle = leadTitle.Trim()).Length > 0 ) - leadTitle += ": "; - else - leadTitle = ""; + if ((leadTitle = leader.GuildTitle) != null && (leadTitle = leadTitle.Trim()).Length > 0) + leadTitle += ": "; + else + leadTitle = ""; - string leadName; + string leadName; - if ( (leadName = leader.Name) == null || (leadName = leadName.Trim()).Length <= 0 ) - leadName = "(empty)"; + if ((leadName = leader.Name) == null || (leadName = leadName.Trim()).Length <= 0) + leadName = "(empty)"; - AddHtml( 220, 15, 250, 35, leadTitle + leadName, false, false ); - } + AddHtml(220, 15, 250, 35, leadTitle + leadName, false, false); + } - AddButton( 20, 50, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 50, 100, 20, 1013022, false, false ); // Loyal to + AddButton(20, 50, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 50, 100, 20, 1013022, false, false); // Loyal to - Mobile fealty = beholder.GuildFealty; + Mobile fealty = beholder.GuildFealty; - if ( fealty == null || !guild.IsMember( fealty ) ) - fealty = leader; + if (fealty == null || !guild.IsMember(fealty)) + fealty = leader; - if ( fealty == null ) - fealty = beholder; + if (fealty == null) + fealty = beholder; - string fealtyName; + string fealtyName; - if ( fealty == null || (fealtyName = fealty.Name) == null || (fealtyName = fealtyName.Trim()).Length <= 0 ) - fealtyName = "(empty)"; + if (fealty == null || (fealtyName = fealty.Name) == null || (fealtyName = fealtyName.Trim()).Length <= 0) + fealtyName = "(empty)"; - if ( beholder == fealty ) - AddHtmlLocalized( 55, 70, 470, 20, 1018002, false, false ); // yourself - else - AddHtml( 55, 70, 470, 20, fealtyName, false, false ); + if (beholder == fealty) + AddHtmlLocalized(55, 70, 470, 20, 1018002, false, false); // yourself + else + AddHtml(55, 70, 470, 20, fealtyName, false, false); - AddButton( 215, 50, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 250, 50, 170, 20, 1013023, false, false ); // Display guild abbreviation - AddHtmlLocalized( 250, 70, 50, 20, beholder.DisplayGuildTitle ? 1011262 : 1011263, false, false ); // on/off + AddButton(215, 50, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(250, 50, 170, 20, 1013023, false, false); // Display guild abbreviation + AddHtmlLocalized(250, 70, 50, 20, beholder.DisplayGuildTitle ? 1011262 : 1011263, false, false); // on/off - AddButton( 20, 100, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 100, 470, 30, 1011086, false, false ); // View the current roster. + AddButton(20, 100, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 100, 470, 30, 1011086, false, false); // View the current roster. - AddButton( 20, 130, 4005, 4007, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 130, 470, 30, 1011085, false, false ); // Recruit someone into the guild. + AddButton(20, 130, 4005, 4007, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 130, 470, 30, 1011085, false, false); // Recruit someone into the guild. - if ( guild.Candidates.Count > 0 ) - { - AddButton( 20, 160, 4005, 4007, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 160, 470, 30, 1011093, false, false ); // View list of candidates who have been sponsored to the guild. - } - else - { - AddImage( 20, 160, 4020 ); - AddHtmlLocalized( 55, 160, 470, 30, 1013031, false, false ); // There are currently no candidates for membership. - } + if (guild.Candidates.Count > 0) + { + AddButton(20, 160, 4005, 4007, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 160, 470, 30, 1011093, false, + false); // View list of candidates who have been sponsored to the guild. + } + else + { + AddImage(20, 160, 4020); + AddHtmlLocalized(55, 160, 470, 30, 1013031, false, + false); // There are currently no candidates for membership. + } - AddButton( 20, 220, 4005, 4007, 6, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 220, 470, 30, 1011087, false, false ); // View the guild's charter. + AddButton(20, 220, 4005, 4007, 6, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 220, 470, 30, 1011087, false, false); // View the guild's charter. - AddButton( 20, 250, 4005, 4007, 7, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 250, 470, 30, 1011092, false, false ); // Resign from the guild. + AddButton(20, 250, 4005, 4007, 7, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 250, 470, 30, 1011092, false, false); // Resign from the guild. - AddButton( 20, 280, 4005, 4007, 8, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 280, 470, 30, 1011095, false, false ); // View list of guilds you are at war with. + AddButton(20, 280, 4005, 4007, 8, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 280, 470, 30, 1011095, false, false); // View list of guilds you are at war with. - if ( beholder.AccessLevel >= AccessLevel.GameMaster || beholder == leader ) - { - AddButton( 20, 310, 4005, 4007, 9, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 310, 470, 30, 1011094, false, false ); // Access guildmaster functions. - } - else - { - AddImage( 20, 310, 4020 ); - AddHtmlLocalized( 55, 310, 470, 30, 1018013, false, false ); // Reserved for guildmaster - } + if (beholder.AccessLevel >= AccessLevel.GameMaster || beholder == leader) + { + AddButton(20, 310, 4005, 4007, 9, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 310, 470, 30, 1011094, false, false); // Access guildmaster functions. + } + else + { + AddImage(20, 310, 4020); + AddHtmlLocalized(55, 310, 470, 30, 1018013, false, false); // Reserved for guildmaster + } - AddButton( 20, 360, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 360, 470, 30, 1011441, false, false ); // EXIT - } + AddButton(20, 360, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 360, 470, 30, 1011441, false, false); // EXIT + } - public static void EnsureClosed( Mobile m ) - { - m.CloseGump( typeof( DeclareFealtyGump ) ); - m.CloseGump( typeof( GrantGuildTitleGump ) ); - m.CloseGump( typeof( GuildAdminCandidatesGump ) ); - m.CloseGump( typeof( GuildCandidatesGump ) ); - m.CloseGump( typeof( GuildChangeTypeGump ) ); - m.CloseGump( typeof( GuildCharterGump ) ); - m.CloseGump( typeof( GuildDismissGump ) ); - m.CloseGump( typeof( GuildGump ) ); - m.CloseGump( typeof( GuildmasterGump ) ); - m.CloseGump( typeof( GuildRosterGump ) ); - m.CloseGump( typeof( GuildWarGump ) ); - } + public static void EnsureClosed(Mobile m) + { + m.CloseGump(typeof(DeclareFealtyGump)); + m.CloseGump(typeof(GrantGuildTitleGump)); + m.CloseGump(typeof(GuildAdminCandidatesGump)); + m.CloseGump(typeof(GuildCandidatesGump)); + m.CloseGump(typeof(GuildChangeTypeGump)); + m.CloseGump(typeof(GuildCharterGump)); + m.CloseGump(typeof(GuildDismissGump)); + m.CloseGump(typeof(GuildGump)); + m.CloseGump(typeof(GuildmasterGump)); + m.CloseGump(typeof(GuildRosterGump)); + m.CloseGump(typeof(GuildWarGump)); + } - public static bool BadLeader( Mobile m, Guild g ) - { - if ( m.Deleted || g.Disbanded || (m.AccessLevel < AccessLevel.GameMaster && g.Leader != m) ) - return true; + public static bool BadLeader(Mobile m, Guild g) + { + if (m.Deleted || g.Disbanded || m.AccessLevel < AccessLevel.GameMaster && g.Leader != m) + return true; - Item stone = g.Guildstone; + Item stone = g.Guildstone; - return ( stone == null || stone.Deleted || !m.InRange( stone.GetWorldLocation(), 2 ) ); - } + return stone == null || stone.Deleted || !m.InRange(stone.GetWorldLocation(), 2); + } - public static bool BadMember( Mobile m, Guild g ) - { - if ( m.Deleted || g.Disbanded || (m.AccessLevel < AccessLevel.GameMaster && !g.IsMember( m )) ) - return true; + public static bool BadMember(Mobile m, Guild g) + { + if (m.Deleted || g.Disbanded || m.AccessLevel < AccessLevel.GameMaster && !g.IsMember(m)) + return true; - Item stone = g.Guildstone; + Item stone = g.Guildstone; - return ( stone == null || stone.Deleted || !m.InRange( stone.GetWorldLocation(), 2 ) ); - } + return stone == null || stone.Deleted || !m.InRange(stone.GetWorldLocation(), 2); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( BadMember( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (BadMember(m_Mobile, m_Guild)) + return; - switch ( info.ButtonID ) - { - case 1: // Loyalty - { - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new DeclareFealtyGump( m_Mobile, m_Guild ) ); + switch (info.ButtonID) + { + case 1: // Loyalty + { + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new DeclareFealtyGump(m_Mobile, m_Guild)); - break; - } - case 2: // Toggle display abbreviation - { - m_Mobile.DisplayGuildTitle = !m_Mobile.DisplayGuildTitle; + break; + } + case 2: // Toggle display abbreviation + { + m_Mobile.DisplayGuildTitle = !m_Mobile.DisplayGuildTitle; - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); - break; - } - case 3: // View the current roster - { - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildRosterGump( m_Mobile, m_Guild ) ); + break; + } + case 3: // View the current roster + { + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildRosterGump(m_Mobile, m_Guild)); - break; - } - case 4: // Recruit - { - m_Mobile.Target = new GuildRecruitTarget( m_Mobile, m_Guild ); + break; + } + case 4: // Recruit + { + m_Mobile.Target = new GuildRecruitTarget(m_Mobile, m_Guild); - break; - } - case 5: // Membership candidates - { - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildCandidatesGump( m_Mobile, m_Guild ) ); + break; + } + case 5: // Membership candidates + { + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildCandidatesGump(m_Mobile, m_Guild)); - break; - } - case 6: // View charter - { - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildCharterGump( m_Mobile, m_Guild ) ); + break; + } + case 6: // View charter + { + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildCharterGump(m_Mobile, m_Guild)); - break; - } - case 7: // Resign - { - m_Guild.RemoveMember( m_Mobile ); + break; + } + case 7: // Resign + { + m_Guild.RemoveMember(m_Mobile); - break; - } - case 8: // View wars - { - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildWarGump( m_Mobile, m_Guild ) ); + break; + } + case 8: // View wars + { + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildWarGump(m_Mobile, m_Guild)); - break; - } - case 9: // Guildmaster functions - { - if ( m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Guild.Leader == m_Mobile ) - { - EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } + break; + } + case 9: // Guildmaster functions + { + if (m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Guild.Leader == m_Mobile) + { + EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildListGump.cs b/Scripts/Gumps/Guilds/GuildListGump.cs index 5d0e94714..7b9b4e4d6 100644 --- a/Scripts/Gumps/Guilds/GuildListGump.cs +++ b/Scripts/Gumps/Guilds/GuildListGump.cs @@ -1,64 +1,64 @@ -using Server.Guilds; using System.Collections.Generic; +using Server.Guilds; namespace Server.Gumps { - public abstract class GuildListGump : Gump - { - protected Mobile m_Mobile; - protected Guild m_Guild; - protected List m_List; + public abstract class GuildListGump : Gump + { + protected Guild m_Guild; + protected List m_List; + protected Mobile m_Mobile; - public GuildListGump( Mobile from, Guild guild, bool radio, List list ) : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + public GuildListGump(Mobile from, Guild guild, bool radio, List list) : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 440, 5054 ); - AddBackground( 10, 10, 530, 420, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 440, 5054); + AddBackground(10, 10, 530, 420, 3000); - Design(); + Design(); - m_List = new List( list ); + m_List = new List(list); - for ( int i = 0; i < m_List.Count; ++i ) - { - if ( (i % 11) == 0 ) - { - if ( i != 0 ) - { - AddButton( 300, 370, 4005, 4007, 0, GumpButtonType.Page, (i / 11) + 1 ); - AddHtmlLocalized( 335, 370, 300, 35, 1011066, false, false ); // Next page - } + for (int i = 0; i < m_List.Count; ++i) + { + if (i % 11 == 0) + { + if (i != 0) + { + AddButton(300, 370, 4005, 4007, 0, GumpButtonType.Page, i / 11 + 1); + AddHtmlLocalized(335, 370, 300, 35, 1011066, false, false); // Next page + } - AddPage( (i / 11) + 1 ); + AddPage(i / 11 + 1); - if ( i != 0 ) - { - AddButton( 20, 370, 4014, 4016, 0, GumpButtonType.Page, (i / 11) ); - AddHtmlLocalized( 55, 370, 300, 35, 1011067, false, false ); // Previous page - } - } + if (i != 0) + { + AddButton(20, 370, 4014, 4016, 0, GumpButtonType.Page, i / 11); + AddHtmlLocalized(55, 370, 300, 35, 1011067, false, false); // Previous page + } + } - if ( radio ) - AddRadio( 20, 35 + ((i % 11) * 30), 208, 209, false, i ); + if (radio) + AddRadio(20, 35 + i % 11 * 30, 208, 209, false, i); - Guild g = m_List[i]; + Guild g = m_List[i]; - string name; + string name; - if ( (name = g.Name) != null && (name = name.Trim()).Length <= 0 ) - name = "(empty)"; + if ((name = g.Name) != null && (name = name.Trim()).Length <= 0) + name = "(empty)"; - AddLabel( (radio ? 55 : 20), 35 + ((i % 11) * 30), 0, name ); - } - } + AddLabel(radio ? 55 : 20, 35 + i % 11 * 30, 0, name); + } + } - protected virtual void Design() - { - } - } + protected virtual void Design() + { + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildMobileListGump.cs b/Scripts/Gumps/Guilds/GuildMobileListGump.cs index f847105d1..62c57aa72 100644 --- a/Scripts/Gumps/Guilds/GuildMobileListGump.cs +++ b/Scripts/Gumps/Guilds/GuildMobileListGump.cs @@ -1,65 +1,65 @@ -using Server.Guilds; using System.Collections.Generic; +using Server.Guilds; namespace Server.Gumps { - public abstract class GuildMobileListGump : Gump - { - protected Mobile m_Mobile; - protected Guild m_Guild; - protected List m_List; + public abstract class GuildMobileListGump : Gump + { + protected Guild m_Guild; + protected List m_List; + protected Mobile m_Mobile; - public GuildMobileListGump( Mobile from, Guild guild, bool radio, List list ) - : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + public GuildMobileListGump(Mobile from, Guild guild, bool radio, List list) + : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 440, 5054 ); - AddBackground( 10, 10, 530, 420, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 440, 5054); + AddBackground(10, 10, 530, 420, 3000); - Design(); + Design(); - m_List = new List( list ); + m_List = new List(list); - for ( int i = 0; i < m_List.Count; ++i ) - { - if ( (i % 11) == 0 ) - { - if ( i != 0 ) - { - AddButton( 300, 370, 4005, 4007, 0, GumpButtonType.Page, (i / 11) + 1 ); - AddHtmlLocalized( 335, 370, 300, 35, 1011066, false, false ); // Next page - } + for (int i = 0; i < m_List.Count; ++i) + { + if (i % 11 == 0) + { + if (i != 0) + { + AddButton(300, 370, 4005, 4007, 0, GumpButtonType.Page, i / 11 + 1); + AddHtmlLocalized(335, 370, 300, 35, 1011066, false, false); // Next page + } - AddPage( (i / 11) + 1 ); + AddPage(i / 11 + 1); - if ( i != 0 ) - { - AddButton( 20, 370, 4014, 4016, 0, GumpButtonType.Page, (i / 11) ); - AddHtmlLocalized( 55, 370, 300, 35, 1011067, false, false ); // Previous page - } - } + if (i != 0) + { + AddButton(20, 370, 4014, 4016, 0, GumpButtonType.Page, i / 11); + AddHtmlLocalized(55, 370, 300, 35, 1011067, false, false); // Previous page + } + } - if ( radio ) - AddRadio( 20, 35 + ((i % 11) * 30), 208, 209, false, i ); + if (radio) + AddRadio(20, 35 + i % 11 * 30, 208, 209, false, i); - Mobile m = m_List[i]; + Mobile m = m_List[i]; - string name; + string name; - if ( (name = m.Name) != null && (name = name.Trim()).Length <= 0 ) - name = "(empty)"; + if ((name = m.Name) != null && (name = name.Trim()).Length <= 0) + name = "(empty)"; - AddLabel( (radio ? 55 : 20), 35 + ((i % 11) * 30), 0, name ); - } - } + AddLabel(radio ? 55 : 20, 35 + i % 11 * 30, 0, name); + } + } - protected virtual void Design() - { - } - } + protected virtual void Design() + { + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildNamePrompt.cs b/Scripts/Gumps/Guilds/GuildNamePrompt.cs index 7e21a9740..292a23b72 100644 --- a/Scripts/Gumps/Guilds/GuildNamePrompt.cs +++ b/Scripts/Gumps/Guilds/GuildNamePrompt.cs @@ -3,51 +3,51 @@ using Server.Prompts; namespace Server.Gumps { - public class GuildNamePrompt : Prompt - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildNamePrompt : Prompt + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildNamePrompt( Mobile m, Guild g ) - { - m_Mobile = m; - m_Guild = g; - } + public GuildNamePrompt(Mobile m, Guild g) + { + m_Mobile = m; + m_Guild = g; + } - public override void OnCancel( Mobile from ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnCancel(Mobile from) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } - public override void OnResponse( Mobile from, string text ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(Mobile from, string text) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - text = text.Trim(); + text = text.Trim(); - if ( text.Length > 40 ) - text = text.Substring( 0, 40 ); + if (text.Length > 40) + text = text.Substring(0, 40); - if ( text.Length > 0 ) - { - if ( BaseGuild.FindByName( text ) != null ) - { - m_Mobile.SendMessage( "{0} conflicts with the name of an existing guild.", text ); - } - else - { - m_Guild.Name = text; - m_Guild.GuildMessage( 1018024, true, text ); // The name of your guild has changed: - } - } + if (text.Length > 0) + { + if (BaseGuild.FindByName(text) != null) + { + m_Mobile.SendMessage("{0} conflicts with the name of an existing guild.", text); + } + else + { + m_Guild.Name = text; + m_Guild.GuildMessage(1018024, true, text); // The name of your guild has changed: + } + } - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildRejectWarGump.cs b/Scripts/Gumps/Guilds/GuildRejectWarGump.cs index 55ee941d1..2a1f36bcd 100644 --- a/Scripts/Gumps/Guilds/GuildRejectWarGump.cs +++ b/Scripts/Gumps/Guilds/GuildRejectWarGump.cs @@ -3,60 +3,60 @@ using Server.Network; namespace Server.Gumps { - public class GuildRejectWarGump : GuildListGump - { - public GuildRejectWarGump( Mobile from, Guild guild ) : base( from, guild, true, guild.WarInvitations ) - { - } + public class GuildRejectWarGump : GuildListGump + { + public GuildRejectWarGump(Mobile from, Guild guild) : base(from, guild, true, guild.WarInvitations) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011148, false, false ); // Select the guild to reject their invitations: + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011148, false, false); // Select the guild to reject their invitations: - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011101, false, false ); // Reject war invitations. + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011101, false, false); // Reject war invitations. - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Guild g = (Guild)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Guild g = m_List[index]; - if ( g != null ) - { - m_Guild.WarInvitations.Remove( g ); - g.WarDeclarations.Remove( m_Guild ); + if (g != null) + { + m_Guild.WarInvitations.Remove(g); + g.WarDeclarations.Remove(m_Guild); - GuildGump.EnsureClosed( m_Mobile ); + GuildGump.EnsureClosed(m_Mobile); - if ( m_Guild.WarInvitations.Count > 0 ) - m_Mobile.SendGump( new GuildRejectWarGump( m_Mobile, m_Guild ) ); - else - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } - } - else if ( info.ButtonID == 2 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m_Guild.WarInvitations.Count > 0) + m_Mobile.SendGump(new GuildRejectWarGump(m_Mobile, m_Guild)); + else + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } + } + else if (info.ButtonID == 2) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildRescindDeclarationGump.cs b/Scripts/Gumps/Guilds/GuildRescindDeclarationGump.cs index 23c02ccf9..8a55ef7bc 100644 --- a/Scripts/Gumps/Guilds/GuildRescindDeclarationGump.cs +++ b/Scripts/Gumps/Guilds/GuildRescindDeclarationGump.cs @@ -3,60 +3,60 @@ using Server.Network; namespace Server.Gumps { - public class GuildRescindDeclarationGump : GuildListGump - { - public GuildRescindDeclarationGump( Mobile from, Guild guild ) : base( from, guild, true, guild.WarDeclarations ) - { - } + public class GuildRescindDeclarationGump : GuildListGump + { + public GuildRescindDeclarationGump(Mobile from, Guild guild) : base(from, guild, true, guild.WarDeclarations) + { + } - protected override void Design() - { - AddHtmlLocalized( 20, 10, 400, 35, 1011150, false, false ); // Select the guild to rescind our invitations: + protected override void Design() + { + AddHtmlLocalized(20, 10, 400, 35, 1011150, false, false); // Select the guild to rescind our invitations: - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 245, 30, 1011102, false, false ); // Rescind your war declarations. + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 245, 30, 1011102, false, false); // Rescind your war declarations. - AddButton( 300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 400, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(300, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 400, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; + if (info.ButtonID == 1) + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - if ( index >= 0 && index < m_List.Count ) - { - Guild g = (Guild)m_List[index]; + if (index >= 0 && index < m_List.Count) + { + Guild g = m_List[index]; - if ( g != null ) - { - m_Guild.WarDeclarations.Remove( g ); - g.WarInvitations.Remove( m_Guild ); + if (g != null) + { + m_Guild.WarDeclarations.Remove(g); + g.WarInvitations.Remove(m_Guild); - GuildGump.EnsureClosed( m_Mobile ); + GuildGump.EnsureClosed(m_Mobile); - if ( m_Guild.WarDeclarations.Count > 0 ) - m_Mobile.SendGump( new GuildRescindDeclarationGump( m_Mobile, m_Guild ) ); - else - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } - } - else if ( info.ButtonID == 2 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } - } + if (m_Guild.WarDeclarations.Count > 0) + m_Mobile.SendGump(new GuildRescindDeclarationGump(m_Mobile, m_Guild)); + else + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } + } + else if (info.ButtonID == 2) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildRosterGump.cs b/Scripts/Gumps/Guilds/GuildRosterGump.cs index 535e802d6..e363fa33e 100644 --- a/Scripts/Gumps/Guilds/GuildRosterGump.cs +++ b/Scripts/Gumps/Guilds/GuildRosterGump.cs @@ -1,33 +1,32 @@ -using System; using Server.Guilds; using Server.Network; namespace Server.Gumps { - public class GuildRosterGump : GuildMobileListGump - { - public GuildRosterGump( Mobile from, Guild guild ) : base( from, guild, false, guild.Members ) - { - } + public class GuildRosterGump : GuildMobileListGump + { + public GuildRosterGump(Mobile from, Guild guild) : base(from, guild, false, guild.Members) + { + } - protected override void Design() - { - AddHtml( 20, 10, 500, 35, $"
{m_Guild.Name}
", false, false ); + protected override void Design() + { + AddHtml(20, 10, 500, 35, $"
{m_Guild.Name}
", false, false); - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 300, 35, 1011120, false, false ); // Return to the main menu. - } + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 300, 35, 1011120, false, false); // Return to the main menu. + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); - } - } - } + if (info.ButtonID == 1) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildTitlePrompt.cs b/Scripts/Gumps/Guilds/GuildTitlePrompt.cs index a9ba1e9d9..35e4655d0 100644 --- a/Scripts/Gumps/Guilds/GuildTitlePrompt.cs +++ b/Scripts/Gumps/Guilds/GuildTitlePrompt.cs @@ -3,46 +3,46 @@ using Server.Prompts; namespace Server.Gumps { - public class GuildTitlePrompt : Prompt - { - private Mobile m_Leader, m_Target; - private Guild m_Guild; + public class GuildTitlePrompt : Prompt + { + private Guild m_Guild; + private Mobile m_Leader, m_Target; - public GuildTitlePrompt( Mobile leader, Mobile target, Guild g ) - { - m_Leader = leader; - m_Target = target; - m_Guild = g; - } + public GuildTitlePrompt(Mobile leader, Mobile target, Guild g) + { + m_Leader = leader; + m_Target = target; + m_Guild = g; + } - public override void OnCancel( Mobile from ) - { - if ( GuildGump.BadLeader( m_Leader, m_Guild ) ) - return; - if ( m_Target.Deleted || !m_Guild.IsMember( m_Target ) ) - return; + public override void OnCancel(Mobile from) + { + if (GuildGump.BadLeader(m_Leader, m_Guild)) + return; + if (m_Target.Deleted || !m_Guild.IsMember(m_Target)) + return; - GuildGump.EnsureClosed( m_Leader ); - m_Leader.SendGump( new GuildmasterGump( m_Leader, m_Guild ) ); - } + GuildGump.EnsureClosed(m_Leader); + m_Leader.SendGump(new GuildmasterGump(m_Leader, m_Guild)); + } - public override void OnResponse( Mobile from, string text ) - { - if ( GuildGump.BadLeader( m_Leader, m_Guild ) ) - return; - if ( m_Target.Deleted || !m_Guild.IsMember( m_Target ) ) - return; + public override void OnResponse(Mobile from, string text) + { + if (GuildGump.BadLeader(m_Leader, m_Guild)) + return; + if (m_Target.Deleted || !m_Guild.IsMember(m_Target)) + return; - text = text.Trim(); + text = text.Trim(); - if ( text.Length > 20 ) - text = text.Substring( 0, 20 ); + if (text.Length > 20) + text = text.Substring(0, 20); - if ( text.Length > 0 ) - m_Target.GuildTitle = text; + if (text.Length > 0) + m_Target.GuildTitle = text; - GuildGump.EnsureClosed( m_Leader ); - m_Leader.SendGump( new GuildmasterGump( m_Leader, m_Guild ) ); - } - } + GuildGump.EnsureClosed(m_Leader); + m_Leader.SendGump(new GuildmasterGump(m_Leader, m_Guild)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildWarAdminGump.cs b/Scripts/Gumps/Guilds/GuildWarAdminGump.cs index d191332ad..636841ea3 100644 --- a/Scripts/Gumps/Guilds/GuildWarAdminGump.cs +++ b/Scripts/Gumps/Guilds/GuildWarAdminGump.cs @@ -3,116 +3,117 @@ using Server.Network; namespace Server.Gumps { - public class GuildWarAdminGump : Gump - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildWarAdminGump : Gump + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildWarAdminGump( Mobile from, Guild guild ) : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + public GuildWarAdminGump(Mobile from, Guild guild) : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 440, 5054 ); - AddBackground( 10, 10, 530, 420, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 440, 5054); + AddBackground(10, 10, 530, 420, 3000); - AddHtmlLocalized( 20, 10, 510, 35, 1011105, false, false ); //
WAR FUNCTIONS
+ AddHtmlLocalized(20, 10, 510, 35, 1011105, false, false); //
WAR FUNCTIONS
- AddButton( 20, 40, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 40, 400, 30, 1011099, false, false ); // Declare war through guild name search. + AddButton(20, 40, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 40, 400, 30, 1011099, false, false); // Declare war through guild name search. - int count = 0; + int count = 0; - if ( guild.Enemies.Count > 0 ) - { - AddButton( 20, 160 + (count * 30), 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 160 + (count++ * 30), 400, 30, 1011103, false, false ); // Declare peace. - } - else - { - AddHtmlLocalized( 20, 160 + (count++ * 30), 400, 30, 1013033, false, false ); // No current wars - } + if (guild.Enemies.Count > 0) + { + AddButton(20, 160 + count * 30, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 160 + count++ * 30, 400, 30, 1011103, false, false); // Declare peace. + } + else + { + AddHtmlLocalized(20, 160 + count++ * 30, 400, 30, 1013033, false, false); // No current wars + } - if ( guild.WarInvitations.Count > 0 ) - { - AddButton( 20, 160 + (count * 30), 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 160 + (count++ * 30), 400, 30, 1011100, false, false ); // Accept war invitations. + if (guild.WarInvitations.Count > 0) + { + AddButton(20, 160 + count * 30, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 160 + count++ * 30, 400, 30, 1011100, false, false); // Accept war invitations. - AddButton( 20, 160 + (count * 30), 4005, 4007, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 160 + (count++ * 30), 400, 30, 1011101, false, false ); // Reject war invitations. - } - else - { - AddHtmlLocalized( 20, 160 + (count++ * 30), 400, 30, 1018012, false, false ); // No current invitations received for war. - } + AddButton(20, 160 + count * 30, 4005, 4007, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 160 + count++ * 30, 400, 30, 1011101, false, false); // Reject war invitations. + } + else + { + AddHtmlLocalized(20, 160 + count++ * 30, 400, 30, 1018012, false, + false); // No current invitations received for war. + } - if ( guild.WarDeclarations.Count > 0 ) - { - AddButton( 20, 160 + (count * 30), 4005, 4007, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 160 + (count++ * 30), 400, 30, 1011102, false, false ); // Rescind your war declarations. - } - else - { - AddHtmlLocalized( 20, 160 + (count++ * 30), 400, 30, 1013055, false, false ); // No current war declarations - } + if (guild.WarDeclarations.Count > 0) + { + AddButton(20, 160 + count * 30, 4005, 4007, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 160 + count++ * 30, 400, 30, 1011102, false, false); // Rescind your war declarations. + } + else + { + AddHtmlLocalized(20, 160 + count++ * 30, 400, 30, 1013055, false, false); // No current war declarations + } - AddButton( 20, 400, 4005, 4007, 6, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 400, 35, 1011104, false, false ); // Return to the previous menu. - } + AddButton(20, 400, 4005, 4007, 6, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 400, 35, 1011104, false, false); // Return to the previous menu. + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - switch ( info.ButtonID ) - { - case 1: // Declare war - { - m_Mobile.SendLocalizedMessage( 1018001 ); // Declare war through search - Enter Guild Name: - m_Mobile.Prompt = new GuildDeclareWarPrompt( m_Mobile, m_Guild ); + switch (info.ButtonID) + { + case 1: // Declare war + { + m_Mobile.SendLocalizedMessage(1018001); // Declare war through search - Enter Guild Name: + m_Mobile.Prompt = new GuildDeclareWarPrompt(m_Mobile, m_Guild); - break; - } - case 2: // Declare peace - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildDeclarePeaceGump( m_Mobile, m_Guild ) ); + break; + } + case 2: // Declare peace + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildDeclarePeaceGump(m_Mobile, m_Guild)); - break; - } - case 3: // Accept war - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildAcceptWarGump( m_Mobile, m_Guild ) ); + break; + } + case 3: // Accept war + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildAcceptWarGump(m_Mobile, m_Guild)); - break; - } - case 4: // Reject war - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildRejectWarGump( m_Mobile, m_Guild ) ); + break; + } + case 4: // Reject war + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildRejectWarGump(m_Mobile, m_Guild)); - break; - } - case 5: // Rescind declarations - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildRescindDeclarationGump( m_Mobile, m_Guild ) ); + break; + } + case 5: // Rescind declarations + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildRescindDeclarationGump(m_Mobile, m_Guild)); - break; - } - case 6: // Return - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); + break; + } + case 6: // Return + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildWarGump.cs b/Scripts/Gumps/Guilds/GuildWarGump.cs index 983cf1f9c..37884f348 100644 --- a/Scripts/Gumps/Guilds/GuildWarGump.cs +++ b/Scripts/Gumps/Guilds/GuildWarGump.cs @@ -1,113 +1,101 @@ +using System.Collections.Generic; using Server.Guilds; using Server.Network; -using System.Collections.Generic; namespace Server.Gumps { - public class GuildWarGump : Gump - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildWarGump : Gump + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildWarGump( Mobile from, Guild guild ) : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + public GuildWarGump(Mobile from, Guild guild) : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 440, 5054 ); - AddBackground( 10, 10, 530, 420, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 440, 5054); + AddBackground(10, 10, 530, 420, 3000); - AddHtmlLocalized( 20, 10, 500, 35, 1011133, false, false ); //
WARFARE STATUS
+ AddHtmlLocalized(20, 10, 500, 35, 1011133, false, false); //
WARFARE STATUS
- AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 300, 35, 1011120, false, false ); // Return to the main menu. + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 300, 35, 1011120, false, false); // Return to the main menu. - AddPage( 1 ); + AddPage(1); - AddButton( 375, 375, 5224, 5224, 0, GumpButtonType.Page, 2 ); - AddHtmlLocalized( 410, 373, 100, 25, 1011066, false, false ); // Next page + AddButton(375, 375, 5224, 5224, 0, GumpButtonType.Page, 2); + AddHtmlLocalized(410, 373, 100, 25, 1011066, false, false); // Next page - AddHtmlLocalized( 20, 45, 400, 20, 1011134, false, false ); // We are at war with: + AddHtmlLocalized(20, 45, 400, 20, 1011134, false, false); // We are at war with: - List enemies = guild.Enemies; + List enemies = guild.Enemies; - if ( enemies.Count == 0 ) - { - AddHtmlLocalized( 20, 65, 400, 20, 1013033, false, false ); // No current wars - } - else - { - for ( int i = 0; i < enemies.Count; ++i ) - { - Guild g = enemies[i]; + if (enemies.Count == 0) + AddHtmlLocalized(20, 65, 400, 20, 1013033, false, false); // No current wars + else + for (int i = 0; i < enemies.Count; ++i) + { + Guild g = enemies[i]; - AddHtml( 20, 65 + (i * 20), 300, 20, g.Name, false, false ); - } - } + AddHtml(20, 65 + i * 20, 300, 20, g.Name, false, false); + } - AddPage( 2 ); + AddPage(2); - AddButton( 375, 375, 5224, 5224, 0, GumpButtonType.Page, 3 ); - AddHtmlLocalized( 410, 373, 100, 25, 1011066, false, false ); // Next page + AddButton(375, 375, 5224, 5224, 0, GumpButtonType.Page, 3); + AddHtmlLocalized(410, 373, 100, 25, 1011066, false, false); // Next page - AddButton( 30, 375, 5223, 5223, 0, GumpButtonType.Page, 1 ); - AddHtmlLocalized( 65, 373, 150, 25, 1011067, false, false ); // Previous page + AddButton(30, 375, 5223, 5223, 0, GumpButtonType.Page, 1); + AddHtmlLocalized(65, 373, 150, 25, 1011067, false, false); // Previous page - AddHtmlLocalized( 20, 45, 400, 20, 1011136, false, false ); // Guilds that we have declared war on: + AddHtmlLocalized(20, 45, 400, 20, 1011136, false, false); // Guilds that we have declared war on: - List declared = guild.WarDeclarations; + List declared = guild.WarDeclarations; - if ( declared.Count == 0 ) - { - AddHtmlLocalized( 20, 65, 400, 20, 1018012, false, false ); // No current invitations received for war. - } - else - { - for ( int i = 0; i < declared.Count; ++i ) - { - Guild g = (Guild)declared[i]; + if (declared.Count == 0) + AddHtmlLocalized(20, 65, 400, 20, 1018012, false, false); // No current invitations received for war. + else + for (int i = 0; i < declared.Count; ++i) + { + Guild g = declared[i]; - AddHtml( 20, 65 + (i * 20), 300, 20, g.Name, false, false ); - } - } + AddHtml(20, 65 + i * 20, 300, 20, g.Name, false, false); + } - AddPage( 3 ); + AddPage(3); - AddButton( 30, 375, 5223, 5223, 0, GumpButtonType.Page, 2 ); - AddHtmlLocalized( 65, 373, 150, 25, 1011067, false, false ); // Previous page + AddButton(30, 375, 5223, 5223, 0, GumpButtonType.Page, 2); + AddHtmlLocalized(65, 373, 150, 25, 1011067, false, false); // Previous page - AddHtmlLocalized( 20, 45, 400, 20, 1011135, false, false ); // Guilds that have declared war on us: + AddHtmlLocalized(20, 45, 400, 20, 1011135, false, false); // Guilds that have declared war on us: - List invites = guild.WarInvitations; + List invites = guild.WarInvitations; - if ( invites.Count == 0 ) - { - AddHtmlLocalized( 20, 65, 400, 20, 1013055, false, false ); // No current war declarations - } - else - { - for ( int i = 0; i < invites.Count; ++i ) - { - Guild g = invites[i]; + if (invites.Count == 0) + AddHtmlLocalized(20, 65, 400, 20, 1013055, false, false); // No current war declarations + else + for (int i = 0; i < invites.Count; ++i) + { + Guild g = invites[i]; - AddHtml( 20, 65 + (i * 20), 300, 20, g.Name, false, false ); - } - } - } + AddHtml(20, 65 + i * 20, 300, 20, g.Name, false, false); + } + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; - if ( info.ButtonID == 1 ) - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); - } - } - } + if (info.ButtonID == 1) + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildWebsitePrompt.cs b/Scripts/Gumps/Guilds/GuildWebsitePrompt.cs index 2de8f7454..16aae7a12 100644 --- a/Scripts/Gumps/Guilds/GuildWebsitePrompt.cs +++ b/Scripts/Gumps/Guilds/GuildWebsitePrompt.cs @@ -3,41 +3,41 @@ using Server.Prompts; namespace Server.Gumps { - public class GuildWebsitePrompt : Prompt - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildWebsitePrompt : Prompt + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildWebsitePrompt( Mobile m, Guild g ) - { - m_Mobile = m; - m_Guild = g; - } + public GuildWebsitePrompt(Mobile m, Guild g) + { + m_Mobile = m; + m_Guild = g; + } - public override void OnCancel( Mobile from ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnCancel(Mobile from) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } - public override void OnResponse( Mobile from, string text ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(Mobile from, string text) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - text = text.Trim(); + text = text.Trim(); - if ( text.Length > 50 ) - text = text.Substring( 0, 50 ); + if (text.Length > 50) + text = text.Substring(0, 50); - if ( text.Length > 0 ) - m_Guild.Website = text; + if (text.Length > 0) + m_Guild.Website = text; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); - } - } + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/GuildmasterGump.cs b/Scripts/Gumps/Guilds/GuildmasterGump.cs index d75f1ea04..0554c09b4 100644 --- a/Scripts/Gumps/Guilds/GuildmasterGump.cs +++ b/Scripts/Gumps/Guilds/GuildmasterGump.cs @@ -1,187 +1,189 @@ -using Server.Items; using Server.Guilds; +using Server.Items; using Server.Network; namespace Server.Gumps { - public class GuildmasterGump : Gump - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildmasterGump : Gump + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildmasterGump( Mobile from, Guild guild ) : base( 20, 30 ) - { - m_Mobile = from; - m_Guild = guild; + public GuildmasterGump(Mobile from, Guild guild) : base(20, 30) + { + m_Mobile = from; + m_Guild = guild; - Dragable = false; + Dragable = false; - AddPage( 0 ); - AddBackground( 0, 0, 550, 400, 5054 ); - AddBackground( 10, 10, 530, 380, 3000 ); + AddPage(0); + AddBackground(0, 0, 550, 400, 5054); + AddBackground(10, 10, 530, 380, 3000); - AddHtmlLocalized( 20, 15, 510, 35, 1011121, false, false ); //
GUILDMASTER FUNCTIONS
+ AddHtmlLocalized(20, 15, 510, 35, 1011121, false, false); //
GUILDMASTER FUNCTIONS
- AddButton( 20, 40, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 40, 470, 30, 1011107, false, false ); // Set the guild name. + AddButton(20, 40, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 40, 470, 30, 1011107, false, false); // Set the guild name. - AddButton( 20, 70, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 70, 470, 30, 1011109, false, false ); // Set the guild's abbreviation. + AddButton(20, 70, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 70, 470, 30, 1011109, false, false); // Set the guild's abbreviation. - if ( Guild.OrderChaos ) - { - AddButton( 20, 100, 4005, 4007, 4, GumpButtonType.Reply, 0 ); + if (Guild.OrderChaos) + { + AddButton(20, 100, 4005, 4007, 4, GumpButtonType.Reply, 0); - switch ( m_Guild.Type ) - { - case GuildType.Regular: - AddHtmlLocalized( 55, 100, 470, 30, 1013059, false, false ); // Change guild type: Currently Standard - break; - case GuildType.Order: - AddHtmlLocalized( 55, 100, 470, 30, 1013057, false, false ); // Change guild type: Currently Order - break; - case GuildType.Chaos: - AddHtmlLocalized( 55, 100, 470, 30, 1013058, false, false ); // Change guild type: Currently Chaos - break; - } - } + switch (m_Guild.Type) + { + case GuildType.Regular: + AddHtmlLocalized(55, 100, 470, 30, 1013059, false, false); // Change guild type: Currently Standard + break; + case GuildType.Order: + AddHtmlLocalized(55, 100, 470, 30, 1013057, false, false); // Change guild type: Currently Order + break; + case GuildType.Chaos: + AddHtmlLocalized(55, 100, 470, 30, 1013058, false, false); // Change guild type: Currently Chaos + break; + } + } - AddButton( 20, 130, 4005, 4007, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 130, 470, 30, 1011112, false, false ); // Set the guild's charter. + AddButton(20, 130, 4005, 4007, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 130, 470, 30, 1011112, false, false); // Set the guild's charter. - AddButton( 20, 160, 4005, 4007, 6, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 160, 470, 30, 1011113, false, false ); // Dismiss a member. + AddButton(20, 160, 4005, 4007, 6, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 160, 470, 30, 1011113, false, false); // Dismiss a member. - AddButton( 20, 190, 4005, 4007, 7, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 190, 470, 30, 1011114, false, false ); // Go to the WAR menu. + AddButton(20, 190, 4005, 4007, 7, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 190, 470, 30, 1011114, false, false); // Go to the WAR menu. - if ( m_Guild.Candidates.Count > 0 ) - { - AddButton( 20, 220, 4005, 4007, 8, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 220, 470, 30, 1013056, false, false ); // Administer the list of candidates - } - else - { - AddImage( 20, 220, 4020 ); - AddHtmlLocalized( 55, 220, 470, 30, 1013031, false, false ); // There are currently no candidates for membership. - } + if (m_Guild.Candidates.Count > 0) + { + AddButton(20, 220, 4005, 4007, 8, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 220, 470, 30, 1013056, false, false); // Administer the list of candidates + } + else + { + AddImage(20, 220, 4020); + AddHtmlLocalized(55, 220, 470, 30, 1013031, false, + false); // There are currently no candidates for membership. + } - AddButton( 20, 250, 4005, 4007, 9, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 250, 470, 30, 1011117, false, false ); // Set the guildmaster's title. + AddButton(20, 250, 4005, 4007, 9, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 250, 470, 30, 1011117, false, false); // Set the guildmaster's title. - AddButton( 20, 280, 4005, 4007, 10, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 280, 470, 30, 1011118, false, false ); // Grant a title to another member. + AddButton(20, 280, 4005, 4007, 10, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 280, 470, 30, 1011118, false, false); // Grant a title to another member. - AddButton( 20, 310, 4005, 4007, 11, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 310, 470, 30, 1011119, false, false ); // Move this guildstone. + AddButton(20, 310, 4005, 4007, 11, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 310, 470, 30, 1011119, false, false); // Move this guildstone. - AddButton( 20, 360, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 360, 245, 30, 1011120, false, false ); // Return to the main menu. + AddButton(20, 360, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 360, 245, 30, 1011120, false, false); // Return to the main menu. - AddButton( 300, 360, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 335, 360, 100, 30, 1011441, false, false ); // EXIT - } + AddButton(300, 360, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(335, 360, 100, 30, 1011441, false, false); // EXIT + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( GuildGump.BadLeader( m_Mobile, m_Guild ) ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (GuildGump.BadLeader(m_Mobile, m_Guild)) + return; - switch ( info.ButtonID ) - { - case 1: // Main menu - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); + switch (info.ButtonID) + { + case 1: // Main menu + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); - break; - } - case 2: // Set guild name - { - m_Mobile.SendLocalizedMessage( 1013060 ); // Enter new guild name (40 characters max): - m_Mobile.Prompt = new GuildNamePrompt( m_Mobile, m_Guild ); + break; + } + case 2: // Set guild name + { + m_Mobile.SendLocalizedMessage(1013060); // Enter new guild name (40 characters max): + m_Mobile.Prompt = new GuildNamePrompt(m_Mobile, m_Guild); - break; - } - case 3: // Set guild abbreviation - { - m_Mobile.SendLocalizedMessage( 1013061 ); // Enter new guild abbreviation (3 characters max): - m_Mobile.Prompt = new GuildAbbrvPrompt( m_Mobile, m_Guild ); + break; + } + case 3: // Set guild abbreviation + { + m_Mobile.SendLocalizedMessage(1013061); // Enter new guild abbreviation (3 characters max): + m_Mobile.Prompt = new GuildAbbrvPrompt(m_Mobile, m_Guild); - break; - } - case 4: // Change guild type - { - if ( !Guild.OrderChaos ) - return; + break; + } + case 4: // Change guild type + { + if (!Guild.OrderChaos) + return; - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildChangeTypeGump( m_Mobile, m_Guild ) ); + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildChangeTypeGump(m_Mobile, m_Guild)); - break; - } - case 5: // Set charter - { - m_Mobile.SendLocalizedMessage( 1013071 ); // Enter the new guild charter (50 characters max): - m_Mobile.Prompt = new GuildCharterPrompt( m_Mobile, m_Guild ); + break; + } + case 5: // Set charter + { + m_Mobile.SendLocalizedMessage(1013071); // Enter the new guild charter (50 characters max): + m_Mobile.Prompt = new GuildCharterPrompt(m_Mobile, m_Guild); - break; - } - case 6: // Dismiss member - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildDismissGump( m_Mobile, m_Guild ) ); + break; + } + case 6: // Dismiss member + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildDismissGump(m_Mobile, m_Guild)); - break; - } - case 7: // War menu - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildWarAdminGump( m_Mobile, m_Guild ) ); + break; + } + case 7: // War menu + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildWarAdminGump(m_Mobile, m_Guild)); - break; - } - case 8: // Administer candidates - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildAdminCandidatesGump( m_Mobile, m_Guild ) ); + break; + } + case 8: // Administer candidates + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildAdminCandidatesGump(m_Mobile, m_Guild)); - break; - } - case 9: // Set guildmaster's title - { - m_Mobile.SendLocalizedMessage( 1013073 ); // Enter new guildmaster title (20 characters max): - m_Mobile.Prompt = new GuildTitlePrompt( m_Mobile, m_Mobile, m_Guild ); + break; + } + case 9: // Set guildmaster's title + { + m_Mobile.SendLocalizedMessage(1013073); // Enter new guildmaster title (20 characters max): + m_Mobile.Prompt = new GuildTitlePrompt(m_Mobile, m_Mobile, m_Guild); - break; - } - case 10: // Grant title - { - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GrantGuildTitleGump( m_Mobile, m_Guild ) ); + break; + } + case 10: // Grant title + { + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GrantGuildTitleGump(m_Mobile, m_Guild)); - break; - } - case 11: // Move guildstone - { - if ( m_Guild.Guildstone != null ) - { - GuildTeleporter item = new GuildTeleporter( m_Guild.Guildstone ); + break; + } + case 11: // Move guildstone + { + if (m_Guild.Guildstone != null) + { + GuildTeleporter item = new GuildTeleporter(m_Guild.Guildstone); - m_Guild.Teleporter?.Delete(); + m_Guild.Teleporter?.Delete(); - m_Mobile.SendLocalizedMessage( 501133 ); // Use the teleporting object placed in your backpack to move this guildstone. + m_Mobile.SendLocalizedMessage( + 501133); // Use the teleporting object placed in your backpack to move this guildstone. - m_Mobile.AddToBackpack( item ); - m_Guild.Teleporter = item; - } + m_Mobile.AddToBackpack(item); + m_Guild.Teleporter = item; + } - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildmasterGump( m_Mobile, m_Guild ) ); + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildmasterGump(m_Mobile, m_Guild)); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/AdvancedSearch.cs b/Scripts/Gumps/Guilds/New Guild System/AdvancedSearch.cs index 2a352289c..afc068a7d 100644 --- a/Scripts/Gumps/Guilds/New Guild System/AdvancedSearch.cs +++ b/Scripts/Gumps/Guilds/New Guild System/AdvancedSearch.cs @@ -1,71 +1,69 @@ using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public delegate void SearchSelectionCallback( GuildDisplayType display ); + public delegate void SearchSelectionCallback(GuildDisplayType display); - public class GuildAdvancedSearchGump : BaseGuildGump - { - private GuildDisplayType m_Display; - private SearchSelectionCallback m_Callback; + public class GuildAdvancedSearchGump : BaseGuildGump + { + private SearchSelectionCallback m_Callback; + private GuildDisplayType m_Display; - public GuildAdvancedSearchGump( PlayerMobile pm, Guild g, GuildDisplayType display, SearchSelectionCallback callback ) : base( pm, g ) - { - m_Callback = callback; - m_Display = display; - PopulateGump(); - } + public GuildAdvancedSearchGump(PlayerMobile pm, Guild g, GuildDisplayType display, SearchSelectionCallback callback) + : base(pm, g) + { + m_Callback = callback; + m_Display = display; + PopulateGump(); + } - public override void PopulateGump() - { - base.PopulateGump(); + public override void PopulateGump() + { + base.PopulateGump(); - AddHtmlLocalized( 431, 43, 110, 26, 1062978, 0xF, false, false ); // Diplomacy + AddHtmlLocalized(431, 43, 110, 26, 1062978, 0xF, false, false); // Diplomacy - AddHtmlLocalized( 65, 80, 480, 26, 1063124, 0xF, true, false ); // Advanced Search Options + AddHtmlLocalized(65, 80, 480, 26, 1063124, 0xF, true, false); // Advanced Search Options - AddHtmlLocalized( 65, 110, 480, 26, 1063136 + (int)m_Display, 0xF, false, false ); // Showing All Guilds/w/Relation/Waiting Relation + AddHtmlLocalized(65, 110, 480, 26, 1063136 + (int)m_Display, 0xF, false, + false); // Showing All Guilds/w/Relation/Waiting Relation - AddGroup( 1 ); - AddRadio( 75, 140, 0xD2, 0xD3, false, 2 ); - AddHtmlLocalized( 105, 140, 200, 26, 1063006, 0x0, false, false ); // Show Guilds with Relationship - AddRadio( 75, 170, 0xD2, 0xD3, false, 1 ); - AddHtmlLocalized( 105, 170, 200, 26, 1063005, 0x0, false, false ); // Show Guilds Awaiting Action - AddRadio( 75, 200, 0xD2, 0xD3, false, 0 ); - AddHtmlLocalized( 105, 200, 200, 26, 1063007, 0x0, false, false ); // Show All Guilds + AddGroup(1); + AddRadio(75, 140, 0xD2, 0xD3, false, 2); + AddHtmlLocalized(105, 140, 200, 26, 1063006, 0x0, false, false); // Show Guilds with Relationship + AddRadio(75, 170, 0xD2, 0xD3, false, 1); + AddHtmlLocalized(105, 170, 200, 26, 1063005, 0x0, false, false); // Show Guilds Awaiting Action + AddRadio(75, 200, 0xD2, 0xD3, false, 0); + AddHtmlLocalized(105, 200, 200, 26, 1063007, 0x0, false, false); // Show All Guilds - AddBackground( 450, 370, 100, 26, 0x2486 ); - AddButton( 455, 375, 0x845, 0x846, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 480, 373, 60, 26, 1006044, 0x0, false, false ); // OK - AddBackground( 340, 370, 100, 26, 0x2486 ); - AddButton( 345, 375, 0x845, 0x846, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 370, 373, 60, 26, 1006045, 0x0, false, false ); // Cancel - } + AddBackground(450, 370, 100, 26, 0x2486); + AddButton(455, 375, 0x845, 0x846, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(480, 373, 60, 26, 1006044, 0x0, false, false); // OK + AddBackground(340, 370, 100, 26, 0x2486); + AddButton(345, 375, 0x845, 0x846, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(370, 373, 60, 26, 1006045, 0x0, false, false); // Cancel + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - base.OnResponse( sender, info ); + public override void OnResponse(NetState sender, RelayInfo info) + { + base.OnResponse(sender, info); - if ( !(sender.Mobile is PlayerMobile pm) || !IsMember( pm, guild ) ) - return; + if (!(sender.Mobile is PlayerMobile pm) || !IsMember(pm, guild)) + return; - GuildDisplayType display = m_Display; + GuildDisplayType display = m_Display; - if ( info.ButtonID == 5 ) - { - for( int i = 0; i < 3; i++ ) - { - if ( info.IsSwitched( i ) ) - { - display = (GuildDisplayType)i; - m_Callback( display ); - break; - } - } - } - } - } -} + if (info.ButtonID == 5) + for (int i = 0; i < 3; i++) + if (info.IsSwitched(i)) + { + display = (GuildDisplayType)i; + m_Callback(display); + break; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/BaseGuildGump.cs b/Scripts/Gumps/Guilds/New Guild System/BaseGuildGump.cs index 43c5dc4e2..739658001 100644 --- a/Scripts/Gumps/Guilds/New Guild System/BaseGuildGump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/BaseGuildGump.cs @@ -1,140 +1,140 @@ -using System; -using Server.Mobiles; using Server.Gumps; -using Server.Network; using Server.Misc; +using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public abstract class BaseGuildGump : Gump - { - protected Guild guild { get; } + public abstract class BaseGuildGump : Gump + { + public BaseGuildGump(PlayerMobile pm, Guild g) : this(pm, g, 10, 10) + { + } - protected PlayerMobile player { get; } + public BaseGuildGump(PlayerMobile pm, Guild g, int x, int y) : base(x, y) + { + guild = g; + player = pm; - public BaseGuildGump( PlayerMobile pm, Guild g ) : this( pm, g, 10, 10 ) - { - } + pm.CloseGump(typeof(BaseGuildGump)); + } - public BaseGuildGump( PlayerMobile pm, Guild g, int x, int y ) : base( x, y ) - { - guild = g; - player = pm; + protected Guild guild{ get; } - pm.CloseGump( typeof( BaseGuildGump ) ); - } + protected PlayerMobile player{ get; } - //There's prolly a way to have all the vars set of inherited classes before something is called in the Ctor... but... I can't think of it right now, and I can't use Timer.DelayCall here :< + //There's prolly a way to have all the vars set of inherited classes before something is called in the Ctor... but... I can't think of it right now, and I can't use Timer.DelayCall here :< - public virtual void PopulateGump() - { - AddPage( 0 ); + public virtual void PopulateGump() + { + AddPage(0); - AddBackground( 0, 0, 600, 440, 0x24AE ); - AddBackground( 66, 40, 150, 26, 0x2486 ); - AddButton( 71, 45, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 96, 43, 110, 26, 1063014, 0x0, false, false ); // My Guild - AddBackground( 236, 40, 150, 26, 0x2486 ); - AddButton( 241, 45, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 266, 43, 110, 26, 1062974, 0x0, false, false ); // Guild Roster - AddBackground( 401, 40, 150, 26, 0x2486 ); - AddButton( 406, 45, 0x845, 0x846, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 431, 43, 110, 26, 1062978, 0x0, false, false ); // Diplomacy - AddPage( 1 ); - } + AddBackground(0, 0, 600, 440, 0x24AE); + AddBackground(66, 40, 150, 26, 0x2486); + AddButton(71, 45, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(96, 43, 110, 26, 1063014, 0x0, false, false); // My Guild + AddBackground(236, 40, 150, 26, 0x2486); + AddButton(241, 45, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(266, 43, 110, 26, 1062974, 0x0, false, false); // Guild Roster + AddBackground(401, 40, 150, 26, 0x2486); + AddButton(406, 45, 0x845, 0x846, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(431, 43, 110, 26, 1062978, 0x0, false, false); // Diplomacy + AddPage(1); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - PlayerMobile pm = sender.Mobile as PlayerMobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + PlayerMobile pm = sender.Mobile as PlayerMobile; - if ( !IsMember( pm, guild ) ) - return; + if (!IsMember(pm, guild)) + return; - switch( info.ButtonID ) - { - case 1: - { - pm.SendGump( new GuildInfoGump( pm, guild ) ); - break; - } - case 2: - { - pm.SendGump( new GuildRosterGump( pm, guild ) ); - break; - } - case 3: - { - pm.SendGump( new GuildDiplomacyGump( pm, guild ) ); - break; - } - } - } + switch (info.ButtonID) + { + case 1: + { + pm.SendGump(new GuildInfoGump(pm, guild)); + break; + } + case 2: + { + pm.SendGump(new GuildRosterGump(pm, guild)); + break; + } + case 3: + { + pm.SendGump(new GuildDiplomacyGump(pm, guild)); + break; + } + } + } - public static bool IsLeader( Mobile m, Guild g ) - { - return !( m.Deleted || g.Disbanded || !( m is PlayerMobile ) || (m.AccessLevel < AccessLevel.GameMaster && g.Leader != m) ); - } + public static bool IsLeader(Mobile m, Guild g) + { + return !(m.Deleted || g.Disbanded || !(m is PlayerMobile) || + m.AccessLevel < AccessLevel.GameMaster && g.Leader != m); + } - public static bool IsMember( Mobile m, Guild g ) - { - return !( m.Deleted || g.Disbanded || !( m is PlayerMobile ) || (m.AccessLevel < AccessLevel.GameMaster && !g.IsMember( m )) ); - } + public static bool IsMember(Mobile m, Guild g) + { + return !(m.Deleted || g.Disbanded || !(m is PlayerMobile) || + m.AccessLevel < AccessLevel.GameMaster && !g.IsMember(m)); + } - public static bool CheckProfanity( string s ) - { - return CheckProfanity( s, 50 ); - } - public static bool CheckProfanity( string s, int maxLength ) - { - //return NameVerification.Validate( s, 1, 50, true, true, false, int.MaxValue, ProfanityProtection.Exceptions, ProfanityProtection.Disallowed, ProfanityProtection.StartDisallowed ); //What am I doing wrong, this still allows chars like the <3 symbol... 3 AM. someone change this to use this + public static bool CheckProfanity(string s) + { + return CheckProfanity(s, 50); + } - //With testing on OSI, Guild stuff seems to follow a 'simpler' method of profanity protection - if ( s.Length < 1 || s.Length > maxLength ) - return false; + public static bool CheckProfanity(string s, int maxLength) + { + //return NameVerification.Validate( s, 1, 50, true, true, false, int.MaxValue, ProfanityProtection.Exceptions, ProfanityProtection.Disallowed, ProfanityProtection.StartDisallowed ); //What am I doing wrong, this still allows chars like the <3 symbol... 3 AM. someone change this to use this - char[] exceptions = ProfanityProtection.Exceptions; + //With testing on OSI, Guild stuff seems to follow a 'simpler' method of profanity protection + if (s.Length < 1 || s.Length > maxLength) + return false; - s = s.ToLower(); + char[] exceptions = ProfanityProtection.Exceptions; - for ( int i = 0; i < s.Length; ++i ) - { - char c = s[i]; + s = s.ToLower(); - if ( (c < 'a' || c > 'z') && (c < '0' || c > '9')) - { - bool except = false; + for (int i = 0; i < s.Length; ++i) + { + char c = s[i]; - for( int j = 0; !except && j < exceptions.Length; j++ ) - if ( c == exceptions[j] ) - except = true; + if ((c < 'a' || c > 'z') && (c < '0' || c > '9')) + { + bool except = false; - if ( !except ) - return false; - } - } + for (int j = 0; !except && j < exceptions.Length; j++) + if (c == exceptions[j]) + except = true; - string[] disallowed = ProfanityProtection.Disallowed; + if (!except) + return false; + } + } - for( int i = 0; i < disallowed.Length; i++ ) - { - if ( s.IndexOf( disallowed[i] ) != -1 ) - return false; - } + string[] disallowed = ProfanityProtection.Disallowed; - return true; - } + for (int i = 0; i < disallowed.Length; i++) + if (s.IndexOf(disallowed[i]) != -1) + return false; - public void AddHtmlText( int x, int y, int width, int height, TextDefinition text, bool back, bool scroll ) - { - if ( text != null && text.Number > 0 ) - AddHtmlLocalized( x, y, width, height, text.Number, back, scroll ); - else if ( text?.String != null ) - AddHtml( x, y, width, height, text.String, back, scroll ); - } + return true; + } - public static string Color( string text, int color ) - { - return $"{text}"; - } - } -} + public void AddHtmlText(int x, int y, int width, int height, TextDefinition text, bool back, bool scroll) + { + if (text != null && text.Number > 0) + AddHtmlLocalized(x, y, width, height, text.Number, back, scroll); + else if (text?.String != null) + AddHtml(x, y, width, height, text.String, back, scroll); + } + + public static string Color(string text, int color) + { + return $"{text}"; + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/BaseGuildListGump.cs b/Scripts/Gumps/Guilds/New Guild System/BaseGuildListGump.cs index db81f28cd..e0f9a3c9c 100644 --- a/Scripts/Gumps/Guilds/New Guild System/BaseGuildListGump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/BaseGuildListGump.cs @@ -1,204 +1,209 @@ using System; -using Server.Gumps; -using Server.Network; -using Server.Mobiles; using System.Collections.Generic; +using Server.Gumps; +using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public abstract class BaseGuildListGump : BaseGuildGump - { - List m_List; - IComparer m_Comparer; - InfoField[] m_Fields; - bool m_Ascending; - string m_Filter; - int m_StartNumber; + public abstract class BaseGuildListGump : BaseGuildGump + { + private const int itemsPerPage = 8; + private bool m_Ascending; + private IComparer m_Comparer; + private InfoField[] m_Fields; + private string m_Filter; + private List m_List; + private int m_StartNumber; - private const int itemsPerPage = 8; + public BaseGuildListGump(PlayerMobile pm, Guild g, List list, IComparer currentComparer, bool ascending, + string filter, int startNumber, InfoField[] fields) + : base(pm, g) + { + m_Filter = filter.Trim(); - public BaseGuildListGump( PlayerMobile pm, Guild g, List list, IComparer currentComparer, bool ascending, string filter, int startNumber, InfoField[] fields ) - : base( pm, g ) - { - m_Filter = filter.Trim(); + m_Comparer = currentComparer; + m_Fields = fields; + m_Ascending = ascending; + m_StartNumber = startNumber; + m_List = list; + } - m_Comparer = currentComparer; - m_Fields = fields; - m_Ascending = ascending; - m_StartNumber = startNumber; - m_List = list; - } + public virtual bool WillFilter => m_Filter.Length >= 0; - public virtual bool WillFilter => (m_Filter.Length >= 0); + public override void PopulateGump() + { + base.PopulateGump(); - public override void PopulateGump() - { - base.PopulateGump(); + List list = m_List; + if (WillFilter) + { + m_List = new List(); + for (int i = 0; i < list.Count; i++) + if (!IsFiltered(list[i], m_Filter)) + m_List.Add(list[i]); + } + else + { + m_List = new List(list); + } - List list = m_List; - if ( WillFilter ) - { - m_List = new List(); - for( int i = 0; i < list.Count; i++ ) - { - if ( !IsFiltered( list[i], m_Filter ) ) - m_List.Add( list[i] ); - } - } - else - { - m_List = new List( list ); - } - - m_List.Sort( m_Comparer ); - m_StartNumber = Math.Max( Math.Min( m_StartNumber, m_List.Count - 1 ), 0 ); + m_List.Sort(m_Comparer); + m_StartNumber = Math.Max(Math.Min(m_StartNumber, m_List.Count - 1), 0); + AddBackground(130, 75, 385, 30, 0xBB8); + AddTextEntry(135, 80, 375, 30, 0x481, 1, m_Filter); + AddButton(520, 75, 0x867, 0x868, 5, GumpButtonType.Reply, 0); //Filter Button - AddBackground( 130, 75, 385, 30, 0xBB8 ); - AddTextEntry( 135, 80, 375, 30, 0x481, 1, m_Filter ); - AddButton( 520, 75, 0x867, 0x868, 5, GumpButtonType.Reply, 0 ); //Filter Button + int width = 0; + for (int i = 0; i < m_Fields.Length; i++) + { + InfoField f = m_Fields[i]; - int width = 0; - for( int i = 0; i < m_Fields.Length; i++ ) - { - InfoField f = m_Fields[i]; + AddImageTiled(65 + width, 110, f.Width + 10, 26, 0xA40); + AddImageTiled(67 + width, 112, f.Width + 6, 22, 0xBBC); + AddHtmlText(70 + width, 113, f.Width, 20, f.Name, false, false); - AddImageTiled( 65 + width, 110, f.Width + 10, 26, 0xA40 ); - AddImageTiled( 67 + width, 112, f.Width + 6, 22, 0xBBC ); - AddHtmlText( 70 + width, 113, f.Width, 20, f.Name, false, false ); + bool isComparer = m_Fields[i].Comparer.GetType() == m_Comparer.GetType(); - bool isComparer = ( m_Fields[i].Comparer.GetType() == m_Comparer.GetType() ); + int ButtonID = isComparer ? m_Ascending ? 0x983 : 0x985 : 0x2716; - int ButtonID = ( isComparer ) ? ( m_Ascending ? 0x983 : 0x985 ) : 0x2716; + AddButton(59 + width + f.Width, 117, ButtonID, ButtonID + (isComparer ? 1 : 0), 100 + i, + GumpButtonType.Reply, 0); - AddButton( 59 + width + f.Width, 117, ButtonID, ButtonID + (isComparer ? 1 : 0) , 100 + i, GumpButtonType.Reply, 0 ); + width += f.Width + 12; + } - width += (f.Width + 12); - } + if (m_StartNumber <= 0) + AddButton(65, 80, 0x15E3, 0x15E7, 0, GumpButtonType.Page, 0); + else + AddButton(65, 80, 0x15E3, 0x15E7, 6, GumpButtonType.Reply, 0); // Back - if ( m_StartNumber <= 0 ) - AddButton( 65, 80, 0x15E3, 0x15E7, 0, GumpButtonType.Page, 0 ); - else - AddButton( 65, 80, 0x15E3, 0x15E7, 6, GumpButtonType.Reply, 0 ); // Back - - if ( m_StartNumber + itemsPerPage > m_List.Count ) - AddButton( 95, 80, 0x15E1, 0x15E5, 0, GumpButtonType.Page, 0 ); - else - AddButton( 95, 80, 0x15E1, 0x15E5, 7, GumpButtonType.Reply, 0 ); // Forward + if (m_StartNumber + itemsPerPage > m_List.Count) + AddButton(95, 80, 0x15E1, 0x15E5, 0, GumpButtonType.Page, 0); + else + AddButton(95, 80, 0x15E1, 0x15E5, 7, GumpButtonType.Reply, 0); // Forward + int itemNumber = 0; - int itemNumber = 0; + if (m_Ascending) + for (int i = m_StartNumber; i < m_StartNumber + itemsPerPage && i < m_List.Count; i++) + DrawEntry(m_List[i], i, itemNumber++); + else //descending, go from bottom of list to the top + for (int i = m_List.Count - 1 - m_StartNumber; + i >= 0 && i >= m_List.Count - itemsPerPage - m_StartNumber; + i--) + DrawEntry(m_List[i], i, itemNumber++); - if ( m_Ascending ) - for( int i = m_StartNumber; i < m_StartNumber + itemsPerPage && i < m_List.Count; i++ ) - DrawEntry( m_List[i], i, itemNumber++ ); - else //descending, go from bottom of list to the top - for( int i = m_List.Count - 1 - m_StartNumber; i >= 0 && i >= (m_List.Count - itemsPerPage - m_StartNumber); i-- ) - DrawEntry( m_List[i], i, itemNumber++ ); + DrawEndingEntry(itemNumber); + } - DrawEndingEntry( itemNumber ); - } + public virtual void DrawEndingEntry(int itemNumber) + { + } - public virtual void DrawEndingEntry( int itemNumber ) - { - } + public virtual bool HasRelationship(T o) + { + return false; + } - public virtual bool HasRelationship( T o ) - { - return false; - } + public virtual void DrawEntry(T o, int index, int itemNumber) + { + int width = 0; + for (int j = 0; j < m_Fields.Length; j++) + { + InfoField f = m_Fields[j]; - public virtual void DrawEntry( T o, int index, int itemNumber ) - { - int width = 0; - for( int j = 0; j < m_Fields.Length; j++ ) - { - InfoField f = m_Fields[j]; + AddImageTiled(65 + width, 138 + itemNumber * 28, f.Width + 10, 26, 0xA40); + AddImageTiled(67 + width, 140 + itemNumber * 28, f.Width + 6, 22, 0xBBC); + AddHtmlText(70 + width, 141 + itemNumber * 28, f.Width, 20, GetValuesFor(o, m_Fields.Length)[j], false, + false); - AddImageTiled( 65 + width, 138 + itemNumber * 28, f.Width + 10, 26, 0xA40 ); - AddImageTiled( 67 + width, 140 + itemNumber * 28, f.Width + 6, 22, 0xBBC ); - AddHtmlText( 70 + width, 141 + itemNumber * 28, f.Width, 20, GetValuesFor( o, m_Fields.Length )[j], false, false ); + width += f.Width + 12; + } - width += (f.Width + 12); - } + if (HasRelationship(o)) + AddButton(40, 143 + itemNumber * 28, 0x8AF, 0x8AF, 200 + index, GumpButtonType.Reply, 0); //Info Button + else + AddButton(40, 143 + itemNumber * 28, 0x4B9, 0x4BA, 200 + index, GumpButtonType.Reply, 0); //Info Button + } - if ( HasRelationship( o ) ) - AddButton( 40, 143 + itemNumber * 28, 0x8AF, 0x8AF, 200 + index, GumpButtonType.Reply, 0 ); //Info Button - else - AddButton( 40, 143 + itemNumber * 28, 0x4B9, 0x4BA, 200 + index, GumpButtonType.Reply, 0 ); //Info Button - } + protected abstract TextDefinition[] GetValuesFor(T o, int aryLength); + protected abstract bool IsFiltered(T o, string filter); - protected abstract TextDefinition[] GetValuesFor( T o, int aryLength ); - protected abstract bool IsFiltered( T o, string filter ); + public override void OnResponse(NetState sender, RelayInfo info) + { + base.OnResponse(sender, info); - public override void OnResponse( NetState sender, RelayInfo info ) - { - base.OnResponse( sender, info ); + if (!(sender.Mobile is PlayerMobile pm) || !IsMember(pm, guild)) + return; - if ( !(sender.Mobile is PlayerMobile pm) || !IsMember( pm, guild ) ) - return; + int id = info.ButtonID; - int id = info.ButtonID; + switch (id) + { + case 5: //Filter + { + TextRelay t = info.GetTextEntry(1); + pm.SendGump(GetResentGump(player, guild, m_Comparer, m_Ascending, t == null ? "" : t.Text, 0)); + break; + } + case 6: //Back + { + pm.SendGump( + GetResentGump(player, guild, m_Comparer, m_Ascending, m_Filter, m_StartNumber - itemsPerPage)); + break; + } + case 7: //Forward + { + pm.SendGump( + GetResentGump(player, guild, m_Comparer, m_Ascending, m_Filter, m_StartNumber + itemsPerPage)); + break; + } + } - switch( id ) - { - case 5: //Filter - { - TextRelay t = info.GetTextEntry( 1 ); - pm.SendGump( GetResentGump( player, guild, m_Comparer, m_Ascending, ( t == null ) ? "" : t.Text, 0 ) ); - break; - } - case 6: //Back - { - pm.SendGump( GetResentGump( player, guild, m_Comparer, m_Ascending, m_Filter, m_StartNumber - itemsPerPage ) ); - break; - } - case 7: //Forward - { - pm.SendGump( GetResentGump( player, guild, m_Comparer, m_Ascending, m_Filter, m_StartNumber + itemsPerPage ) ); - break; - } - } + if (id >= 100 && id < 100 + m_Fields.Length) + { + IComparer comparer = m_Fields[id - 100].Comparer; - if ( id >= 100 && id < (100 + m_Fields.Length) ) - { - IComparer comparer = m_Fields[id-100].Comparer; + if (m_Comparer.GetType() == comparer.GetType()) + m_Ascending = !m_Ascending; - if ( m_Comparer.GetType() == comparer.GetType() ) - m_Ascending = !m_Ascending; - - pm.SendGump( GetResentGump( player, guild, comparer, m_Ascending, m_Filter, 0 ) ); - } - else if ( id >= 200 && id < ( 200 + m_List.Count ) ) - { - pm.SendGump( GetObjectInfoGump( player, guild, m_List[id - 200] ) ); - } - } + pm.SendGump(GetResentGump(player, guild, comparer, m_Ascending, m_Filter, 0)); + } + else if (id >= 200 && id < 200 + m_List.Count) + { + pm.SendGump(GetObjectInfoGump(player, guild, m_List[id - 200])); + } + } - public abstract Gump GetResentGump( PlayerMobile pm, Guild g, IComparer comparer, bool ascending, string filter, int startNumber ); - public abstract Gump GetObjectInfoGump( PlayerMobile pm, Guild g, T o ); + public abstract Gump GetResentGump(PlayerMobile pm, Guild g, IComparer comparer, bool ascending, string filter, + int startNumber); - public void ResendGump() - { - player.SendGump( GetResentGump( player, guild, m_Comparer, m_Ascending, m_Filter, m_StartNumber ) ); - } - } - public struct InfoField - { - public TextDefinition Name { get; } + public abstract Gump GetObjectInfoGump(PlayerMobile pm, Guild g, T o); - public int Width { get; } + public void ResendGump() + { + player.SendGump(GetResentGump(player, guild, m_Comparer, m_Ascending, m_Filter, m_StartNumber)); + } + } - public IComparer Comparer { get; } + public struct InfoField + { + public TextDefinition Name{ get; } - public InfoField( TextDefinition name, int width, IComparer comparer ) - { - Name = name; - Width = width; - Comparer = comparer; - } - } -} + public int Width{ get; } + + public IComparer Comparer{ get; } + + public InfoField(TextDefinition name, int width, IComparer comparer) + { + Name = name; + Width = width; + Comparer = comparer; + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/Create Guild Gump.cs b/Scripts/Gumps/Guilds/New Guild System/Create Guild Gump.cs index 3750df7f0..f021c3d6e 100644 --- a/Scripts/Gumps/Guilds/New Guild System/Create Guild Gump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/Create Guild Gump.cs @@ -1,93 +1,113 @@ using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public class CreateGuildGump : Gump - { - public CreateGuildGump( PlayerMobile pm, string guildName = "Guild Name", string guildAbbrev = "") : base ( 10, 10 ) - { - pm.CloseGump( typeof( CreateGuildGump ) ); - pm.CloseGump( typeof( BaseGuildGump ) ); + public class CreateGuildGump : Gump + { + public CreateGuildGump(PlayerMobile pm, string guildName = "Guild Name", string guildAbbrev = "") : base(10, 10) + { + pm.CloseGump(typeof(CreateGuildGump)); + pm.CloseGump(typeof(BaseGuildGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 500, 300, 0x2422 ); - AddHtmlLocalized( 25, 20, 450, 25, 1062939, 0x0, true, false ); //
GUILD MENU
- AddHtmlLocalized( 25, 60, 450, 60, 1062940, 0x0, false, false ); // As you are not a member of any guild, you can create your own by providing a unique guild name and paying the standard guild registration fee. - AddHtmlLocalized( 25, 135, 120, 25, 1062941, 0x0, false, false ); // Registration Fee: - AddLabel( 155, 135, 0x481, Guild.RegistrationFee.ToString() ); - AddHtmlLocalized( 25, 165, 120, 25, 1011140, 0x0, false, false ); // Enter Guild Name: - AddBackground( 155, 160, 320, 26, 0xBB8 ); - AddTextEntry( 160, 163, 315, 21, 0x481, 5, guildName ); - AddHtmlLocalized( 25, 191, 120, 26, 1063035, 0x0, false, false ); // Abbreviation: - AddBackground( 155, 186, 320, 26, 0xBB8 ); - AddTextEntry( 160, 189, 315, 21, 0x481, 6, guildAbbrev ); - AddButton( 415, 217, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0 ); - AddButton( 345, 217, 0xF2, 0xF1, 0, GumpButtonType.Reply, 0 ); + AddBackground(0, 0, 500, 300, 0x2422); + AddHtmlLocalized(25, 20, 450, 25, 1062939, 0x0, true, false); //
GUILD MENU
+ AddHtmlLocalized(25, 60, 450, 60, 1062940, 0x0, false, + false); // As you are not a member of any guild, you can create your own by providing a unique guild name and paying the standard guild registration fee. + AddHtmlLocalized(25, 135, 120, 25, 1062941, 0x0, false, false); // Registration Fee: + AddLabel(155, 135, 0x481, Guild.RegistrationFee.ToString()); + AddHtmlLocalized(25, 165, 120, 25, 1011140, 0x0, false, false); // Enter Guild Name: + AddBackground(155, 160, 320, 26, 0xBB8); + AddTextEntry(160, 163, 315, 21, 0x481, 5, guildName); + AddHtmlLocalized(25, 191, 120, 26, 1063035, 0x0, false, false); // Abbreviation: + AddBackground(155, 186, 320, 26, 0xBB8); + AddTextEntry(160, 189, 315, 21, 0x481, 6, guildAbbrev); + AddButton(415, 217, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0); + AddButton(345, 217, 0xF2, 0xF1, 0, GumpButtonType.Reply, 0); - if ( pm.AcceptGuildInvites ) - AddButton( 20, 260, 0xD2, 0xD3, 2, GumpButtonType.Reply, 0 ); - else - AddButton( 20, 260, 0xD3, 0xD2, 2, GumpButtonType.Reply, 0 ); + if (pm.AcceptGuildInvites) + AddButton(20, 260, 0xD2, 0xD3, 2, GumpButtonType.Reply, 0); + else + AddButton(20, 260, 0xD3, 0xD2, 2, GumpButtonType.Reply, 0); - AddHtmlLocalized( 45, 260, 200, 30, 1062943, 0x0, false, false ); // Ignore Guild Invites - } + AddHtmlLocalized(45, 260, 200, 30, 1062943, 0x0, false, false); // Ignore Guild Invites + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !(sender.Mobile is PlayerMobile pm) || pm.Guild != null ) - return; //Sanity + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!(sender.Mobile is PlayerMobile pm) || pm.Guild != null) + return; //Sanity - switch( info.ButtonID ) - { - case 1: - { - TextRelay tName = info.GetTextEntry( 5 ); - TextRelay tAbbrev = info.GetTextEntry( 6 ); + switch (info.ButtonID) + { + case 1: + { + TextRelay tName = info.GetTextEntry(5); + TextRelay tAbbrev = info.GetTextEntry(6); - string guildName = (tName == null) ? "" : tName.Text; - string guildAbbrev = (tAbbrev == null) ? "" : tAbbrev.Text; + string guildName = tName == null ? "" : tName.Text; + string guildAbbrev = tAbbrev == null ? "" : tAbbrev.Text; - guildName = Utility.FixHtml( guildName.Trim() ); - guildAbbrev = Utility.FixHtml( guildAbbrev.Trim() ); + guildName = Utility.FixHtml(guildName.Trim()); + guildAbbrev = Utility.FixHtml(guildAbbrev.Trim()); - if ( guildName.Length <= 0 ) - pm.SendLocalizedMessage( 1070884 ); // Guild name cannot be blank. - else if ( guildAbbrev.Length <= 0 ) - pm.SendLocalizedMessage( 1070885 ); // You must provide a guild abbreviation. - else if ( guildName.Length > Guild.NameLimit ) - pm.SendLocalizedMessage( 1063036, Guild.NameLimit.ToString() ); // A guild name cannot be more than ~1_val~ characters in length. - else if ( guildAbbrev.Length > Guild.AbbrevLimit ) - pm.SendLocalizedMessage( 1063037, Guild.AbbrevLimit.ToString() ); // An abbreviation cannot exceed ~1_val~ characters in length. - else if ( BaseGuild.FindByAbbrev( guildAbbrev ) != null || !BaseGuildGump.CheckProfanity( guildAbbrev ) ) - pm.SendLocalizedMessage( 501153 ); // That abbreviation is not available. - else if ( BaseGuild.FindByName( guildName ) != null || !BaseGuildGump.CheckProfanity( guildName ) ) - pm.SendLocalizedMessage( 1063000 ); // That guild name is not available. - else if ( !Banker.Withdraw( pm, Guild.RegistrationFee ) ) - pm.SendLocalizedMessage( 1063001, Guild.RegistrationFee.ToString() ); // You do not possess the ~1_val~ gold piece fee required to create a guild. - else - { - pm.SendLocalizedMessage( 1060398, Guild.RegistrationFee.ToString() ); // ~1_AMOUNT~ gold has been withdrawn from your bank box. - pm.SendLocalizedMessage( 1063238 ); // Your new guild has been founded. - pm.Guild = new Guild( pm, guildName, guildAbbrev ); - } + if (guildName.Length <= 0) + { + pm.SendLocalizedMessage(1070884); // Guild name cannot be blank. + } + else if (guildAbbrev.Length <= 0) + { + pm.SendLocalizedMessage(1070885); // You must provide a guild abbreviation. + } + else if (guildName.Length > Guild.NameLimit) + { + pm.SendLocalizedMessage(1063036, + Guild.NameLimit.ToString()); // A guild name cannot be more than ~1_val~ characters in length. + } + else if (guildAbbrev.Length > Guild.AbbrevLimit) + { + pm.SendLocalizedMessage(1063037, + Guild.AbbrevLimit.ToString()); // An abbreviation cannot exceed ~1_val~ characters in length. + } + else if (BaseGuild.FindByAbbrev(guildAbbrev) != null || !BaseGuildGump.CheckProfanity(guildAbbrev)) + { + pm.SendLocalizedMessage(501153); // That abbreviation is not available. + } + else if (BaseGuild.FindByName(guildName) != null || !BaseGuildGump.CheckProfanity(guildName)) + { + pm.SendLocalizedMessage(1063000); // That guild name is not available. + } + else if (!Banker.Withdraw(pm, Guild.RegistrationFee)) + { + pm.SendLocalizedMessage(1063001, + Guild.RegistrationFee + .ToString()); // You do not possess the ~1_val~ gold piece fee required to create a guild. + } + else + { + pm.SendLocalizedMessage(1060398, + Guild.RegistrationFee.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. + pm.SendLocalizedMessage(1063238); // Your new guild has been founded. + pm.Guild = new Guild(pm, guildName, guildAbbrev); + } - break; - } - case 2: - { - pm.AcceptGuildInvites = !pm.AcceptGuildInvites; + break; + } + case 2: + { + pm.AcceptGuildInvites = !pm.AcceptGuildInvites; - if ( pm.AcceptGuildInvites ) - pm.SendLocalizedMessage( 1070699 ); // You are now accepting guild invitations. - else - pm.SendLocalizedMessage( 1070698 ); // You are now ignoring guild invitations. + if (pm.AcceptGuildInvites) + pm.SendLocalizedMessage(1070699); // You are now accepting guild invitations. + else + pm.SendLocalizedMessage(1070698); // You are now ignoring guild invitations. - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/DiplomacyGump.cs b/Scripts/Gumps/Guilds/New Guild System/DiplomacyGump.cs index 21bd42ba4..c711a90cb 100644 --- a/Scripts/Gumps/Guilds/New Guild System/DiplomacyGump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/DiplomacyGump.cs @@ -1,287 +1,293 @@ -using Server.Gumps; -using Server.Network; -using Server.Mobiles; using System.Collections.Generic; +using Server.Gumps; +using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public enum GuildDisplayType - { - All, - AwaitingAction, - Relations - } + public enum GuildDisplayType + { + All, + AwaitingAction, + Relations + } - public class GuildDiplomacyGump : BaseGuildListGump - { - protected virtual bool AllowAdvancedSearch => true; + public class GuildDiplomacyGump : BaseGuildListGump + { + private GuildDisplayType m_Display; + private TextDefinition m_LowerText; - #region Comparers - private class NameComparer : IComparer - { - public static readonly IComparer Instance = new NameComparer(); + public GuildDiplomacyGump(PlayerMobile pm, Guild g) + : this(pm, g, NameComparer.Instance, true, "", 0, GuildDisplayType.All, + Utility.CastConvertList(new List(BaseGuild.List.Values)), + 1063136 + (int)GuildDisplayType.All) + { + } - public NameComparer() - { - } + public GuildDiplomacyGump(PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, + int startNumber, GuildDisplayType display) + : this(pm, g, currentComparer, ascending, filter, startNumber, display, + Utility.CastConvertList(new List(BaseGuild.List.Values)), + 1063136 + (int)display) + { + } - public int Compare( Guild x, Guild y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + public GuildDiplomacyGump(PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, + int startNumber, List list, TextDefinition lowerText) + : this(pm, g, currentComparer, ascending, filter, startNumber, GuildDisplayType.All, list, lowerText) + { + } - return Insensitive.Compare( x.Name, y.Name ); - } - } + public GuildDiplomacyGump(PlayerMobile pm, Guild g, bool ascending, string filter, int startNumber, List list, + TextDefinition lowerText) + : this(pm, g, NameComparer.Instance, ascending, filter, startNumber, GuildDisplayType.All, list, lowerText) + { + } - private class StatusComparer : IComparer - { - private enum GuildCompareStatus - { - Peace, - Ally, - War - } - private Guild m_Guild; - public StatusComparer( Guild g ) - { - m_Guild = g; - } + public GuildDiplomacyGump(PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, + int startNumber, GuildDisplayType display, List list, TextDefinition lowerText) + : base(pm, g, list, currentComparer, ascending, filter, startNumber, + new[] + { + new InfoField(1062954, 280, NameComparer.Instance), //Guild Name + new InfoField(1062957, 50, AbbrevComparer.Instance), //Abbrev + new InfoField(1062958, 120, new StatusComparer(g)) //Guild Title + }) + { + m_Display = display; + m_LowerText = lowerText; + PopulateGump(); + } - public int Compare( Guild x, Guild y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + protected virtual bool AllowAdvancedSearch => true; - GuildCompareStatus aStatus = GuildCompareStatus.Peace; - GuildCompareStatus bStatus = GuildCompareStatus.Peace; + public override bool WillFilter + { + get + { + if (m_Display == GuildDisplayType.All) + return base.WillFilter; - if ( m_Guild.IsAlly( x ) ) - aStatus = GuildCompareStatus.Ally; - else if ( m_Guild.IsWar( x ) ) - aStatus = GuildCompareStatus.War; + return true; + } + } + + public override void PopulateGump() + { + base.PopulateGump(); + + AddHtmlLocalized(431, 43, 110, 26, 1062978, 0xF, false, false); // Diplomacy + } + + protected override TextDefinition[] GetValuesFor(Guild g, int aryLength) + { + TextDefinition[] defs = new TextDefinition[aryLength]; + + defs[0] = g == guild ? Color(g.Name, 0x006600) : g.Name; + defs[1] = g.Abbreviation; + + defs[2] = 3000085; //Peace - if ( m_Guild.IsAlly( y ) ) - bStatus = GuildCompareStatus.Ally; - else if ( m_Guild.IsWar( y ) ) - bStatus = GuildCompareStatus.War; + if (guild.IsAlly(g)) + { + if (guild.Alliance.Leader == g) + defs[2] = 1063237; // Alliance Leader + else + defs[2] = 1062964; // Ally + } + else if (guild.IsWar(g)) + { + defs[2] = 3000086; // War + } - return ((int)aStatus).CompareTo( (int)bStatus ); - } - } - private class AbbrevComparer : IComparer - { - public static readonly IComparer Instance = new AbbrevComparer(); + return defs; + } - public AbbrevComparer() - { - } + public override bool HasRelationship(Guild g) + { + if (g == guild) + return false; - public int Compare( Guild x, Guild y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + if (guild.FindPendingWar(g) != null) + return true; - return Insensitive.Compare( x.Abbreviation, y.Abbreviation ); - } - } + AllianceInfo alliance = guild.Alliance; - #endregion + if (alliance != null) + { + Guild leader = alliance.Leader; - GuildDisplayType m_Display; - TextDefinition m_LowerText; + if (leader != null) + { + if (guild == leader && alliance.IsPendingMember(g) || g == leader && alliance.IsPendingMember(guild)) + return true; + } + else if (alliance.IsPendingMember(g)) + { + return true; + } + } - public GuildDiplomacyGump( PlayerMobile pm, Guild g ) - : this( pm, g, NameComparer.Instance, true, "", 0, GuildDisplayType.All, Utility.CastConvertList( new List( BaseGuild.List.Values ) ), (1063136 + (int)GuildDisplayType.All) ) - { - } + return false; + } - public GuildDiplomacyGump( PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, int startNumber, GuildDisplayType display ) - : this( pm, g, currentComparer, ascending, filter, startNumber, display, Utility.CastConvertList( new List( BaseGuild.List.Values ) ), (1063136 + (int)display) ) - { - } + public override void DrawEndingEntry(int itemNumber) + { + //AddHtmlLocalized( 66, 153 + itemNumber * 28, 280, 26, 1063136 + (int)m_Display, 0xF, false, false ); // Showing All Guilds/Awaiting Action/ w/Relation Ship + //AddHtmlText( 66, 153 + itemNumber * 28, 280, 26, m_LowerText, false, false ); - public GuildDiplomacyGump( PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, int startNumber, List list, TextDefinition lowerText ) - : this( pm, g, currentComparer, ascending, filter, startNumber, GuildDisplayType.All, list, lowerText ) - { - } + if (m_LowerText != null && m_LowerText.Number > 0) + AddHtmlLocalized(66, 153 + itemNumber * 28, 280, 26, m_LowerText.Number, 0xF, false, false); + else if (m_LowerText?.String != null) + AddHtml(66, 153 + itemNumber * 28, 280, 26, Color(m_LowerText.String, 0x99), false, false); - public GuildDiplomacyGump( PlayerMobile pm, Guild g, bool ascending, string filter, int startNumber, List list, TextDefinition lowerText ) - : this( pm, g, NameComparer.Instance, ascending, filter, startNumber, GuildDisplayType.All, list, lowerText ) - { - } - - public GuildDiplomacyGump( PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, int startNumber, GuildDisplayType display, List list, TextDefinition lowerText ) - : base( pm, g, list, currentComparer, ascending, filter, startNumber, - new[] - { - new InfoField( 1062954, 280, NameComparer.Instance ), //Guild Name - new InfoField( 1062957, 50, AbbrevComparer.Instance ), //Abbrev - new InfoField( 1062958, 120, new StatusComparer( g ) ) //Guild Title - }) - { - - m_Display = display; - m_LowerText = lowerText; - PopulateGump(); - } - - public override void PopulateGump() - { - base.PopulateGump(); - - AddHtmlLocalized( 431, 43, 110, 26, 1062978, 0xF, false, false ); // Diplomacy - } - - protected override TextDefinition[] GetValuesFor( Guild g, int aryLength ) - { - TextDefinition[] defs = new TextDefinition[aryLength]; - - defs[0] = ( g == guild ) ? Color( g.Name, 0x006600 ) : g.Name; - defs[1] = g.Abbreviation; - - defs[2] = 3000085; //Peace + if (AllowAdvancedSearch) + { + AddBackground(350, 148 + itemNumber * 28, 200, 26, 0x2486); + AddButton(355, 153 + itemNumber * 28, 0x845, 0x846, 8, GumpButtonType.Reply, 0); + AddHtmlLocalized(380, 151 + itemNumber * 28, 160, 26, 1063083, 0x0, false, false); // Advanced Search + } + } - if ( guild.IsAlly( g ) ) - { - if ( guild.Alliance.Leader == g ) - defs[2] = 1063237; // Alliance Leader - else - defs[2] = 1062964; // Ally - } - else if ( guild.IsWar( g ) ) - { - defs[2] = 3000086; // War - } + protected override bool IsFiltered(Guild g, string filter) + { + if (g == null) + return true; - return defs; - } + switch (m_Display) + { + case GuildDisplayType.Relations: + { + //if ( !( guild.IsWar( g ) || guild.IsAlly( g ) ) ) - public override bool HasRelationship( Guild g ) - { - if ( g == guild ) - return false; + if (!(guild.FindActiveWar(g) != null || guild.IsAlly(g)) + ) //As per OSI, only the guild leader wars show up under the sorting by relation + return true; - if ( guild.FindPendingWar( g ) != null ) - return true; + return false; + } + case GuildDisplayType.AwaitingAction: + { + return !HasRelationship(g); + } + } - AllianceInfo alliance = guild.Alliance; - - if ( alliance != null ) - { - Guild leader = alliance.Leader; - - if ( leader != null ) - { - if ( guild == leader && alliance.IsPendingMember( g ) || g == leader && alliance.IsPendingMember( guild ) ) - return true; - } - else if ( alliance.IsPendingMember( g ) ) - return true; - } - - return false; - } - - public override void DrawEndingEntry( int itemNumber ) - { - //AddHtmlLocalized( 66, 153 + itemNumber * 28, 280, 26, 1063136 + (int)m_Display, 0xF, false, false ); // Showing All Guilds/Awaiting Action/ w/Relation Ship - //AddHtmlText( 66, 153 + itemNumber * 28, 280, 26, m_LowerText, false, false ); - - if ( m_LowerText != null && m_LowerText.Number > 0 ) - AddHtmlLocalized( 66, 153 + itemNumber * 28, 280, 26, m_LowerText.Number, 0xF, false, false ); - else if ( m_LowerText?.String != null ) - AddHtml( 66, 153 + itemNumber * 28, 280, 26, Color( m_LowerText.String, 0x99 ), false, false ); - - if ( AllowAdvancedSearch ) - { - AddBackground( 350, 148 + itemNumber * 28, 200, 26, 0x2486 ); - AddButton( 355, 153 + itemNumber * 28, 0x845, 0x846, 8, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 380, 151 + itemNumber * 28, 160, 26, 1063083, 0x0, false, false ); // Advanced Search - } - } + return !(Insensitive.Contains(g.Name, filter) || Insensitive.Contains(g.Abbreviation, filter)); + } - protected override bool IsFiltered( Guild g, string filter ) - { - if ( g == null ) - return true; + public override Gump GetResentGump(PlayerMobile pm, Guild g, IComparer comparer, bool ascending, + string filter, int startNumber) + { + return new GuildDiplomacyGump(pm, g, comparer, ascending, filter, startNumber, m_Display); + } - switch( m_Display ) - { - case GuildDisplayType.Relations: - { - //if ( !( guild.IsWar( g ) || guild.IsAlly( g ) ) ) + public override Gump GetObjectInfoGump(PlayerMobile pm, Guild g, Guild o) + { + if (guild == o) + return new GuildInfoGump(pm, g); - if ( !( guild.FindActiveWar( g ) != null || guild.IsAlly( g ) ) ) //As per OSI, only the guild leader wars show up under the sorting by relation - return true; + return new OtherGuildInfo(pm, g, o); + } - return false; - } - case GuildDisplayType.AwaitingAction: - { - return !HasRelationship( g ); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + base.OnResponse(sender, info); - return !( Insensitive.Contains( g.Name, filter ) || Insensitive.Contains( g.Abbreviation, filter ) ); - } + if (!(sender.Mobile is PlayerMobile pm) || !IsMember(pm, guild)) + return; - public override bool WillFilter - { - get - { - if ( m_Display == GuildDisplayType.All ) - return base.WillFilter; + if (AllowAdvancedSearch && info.ButtonID == 8) + pm.SendGump(new GuildAdvancedSearchGump(pm, guild, m_Display, AdvancedSearch_Callback)); + } - return true; - } - } + public void AdvancedSearch_Callback(GuildDisplayType display) + { + m_Display = display; + ResendGump(); + } + + #region Comparers + + private class NameComparer : IComparer + { + public static readonly IComparer Instance = new NameComparer(); + + public int Compare(Guild x, Guild y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + return Insensitive.Compare(x.Name, y.Name); + } + } + + private class StatusComparer : IComparer + { + private Guild m_Guild; + + public StatusComparer(Guild g) + { + m_Guild = g; + } + + public int Compare(Guild x, Guild y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + GuildCompareStatus aStatus = GuildCompareStatus.Peace; + GuildCompareStatus bStatus = GuildCompareStatus.Peace; + + if (m_Guild.IsAlly(x)) + aStatus = GuildCompareStatus.Ally; + else if (m_Guild.IsWar(x)) + aStatus = GuildCompareStatus.War; - public override Gump GetResentGump( PlayerMobile pm, Guild g, IComparer comparer, bool ascending, string filter, int startNumber ) - { - return new GuildDiplomacyGump( pm, g, comparer, ascending, filter, startNumber, m_Display ); - } + if (m_Guild.IsAlly(y)) + bStatus = GuildCompareStatus.Ally; + else if (m_Guild.IsWar(y)) + bStatus = GuildCompareStatus.War; - public override Gump GetObjectInfoGump( PlayerMobile pm, Guild g, Guild o ) - { - if ( guild == o ) - return new GuildInfoGump( pm, g ); + return ((int)aStatus).CompareTo((int)bStatus); + } - return new OtherGuildInfo( pm, g, (Guild)o ) ; - } + private enum GuildCompareStatus + { + Peace, + Ally, + War + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - base.OnResponse( sender, info ); + private class AbbrevComparer : IComparer + { + public static readonly IComparer Instance = new AbbrevComparer(); - if ( !(sender.Mobile is PlayerMobile pm) || !IsMember( pm, guild ) ) - return; + public int Compare(Guild x, Guild y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; - if ( AllowAdvancedSearch && info.ButtonID == 8 ) - pm.SendGump( new GuildAdvancedSearchGump( pm, guild, m_Display, AdvancedSearch_Callback )); + return Insensitive.Compare(x.Abbreviation, y.Abbreviation); + } + } - } - - public void AdvancedSearch_Callback( GuildDisplayType display ) - { - m_Display = display; - ResendGump(); - } - } -} + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/GuildInfoGump.cs b/Scripts/Gumps/Guilds/New Guild System/GuildInfoGump.cs index 2f28fb257..5792612f3 100644 --- a/Scripts/Gumps/Guilds/New Guild System/GuildInfoGump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/GuildInfoGump.cs @@ -1,188 +1,196 @@ -using System; -using Server.Mobiles; -using Server.Gumps; -using Server.Network; using Server.Factions; +using Server.Gumps; +using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public class GuildInfoGump : BaseGuildGump - { - private bool m_IsResigning; + public class GuildInfoGump : BaseGuildGump + { + private bool m_IsResigning; - public GuildInfoGump( PlayerMobile pm, Guild g ) : this( pm, g, false ) - { - } - public GuildInfoGump( PlayerMobile pm, Guild g, bool isResigning ) : base( pm, g ) - { - m_IsResigning = isResigning; - PopulateGump(); - } + public GuildInfoGump(PlayerMobile pm, Guild g) : this(pm, g, false) + { + } - public override void PopulateGump() - { - bool isLeader = IsLeader( player, guild ); - base.PopulateGump(); + public GuildInfoGump(PlayerMobile pm, Guild g, bool isResigning) : base(pm, g) + { + m_IsResigning = isResigning; + PopulateGump(); + } - AddHtmlLocalized( 96, 43, 110, 26, 1063014, 0xF, false, false ); // My Guild + public override void PopulateGump() + { + bool isLeader = IsLeader(player, guild); + base.PopulateGump(); - AddImageTiled( 65, 80, 160, 26, 0xA40 ); - AddImageTiled( 67, 82, 156, 22, 0xBBC ); - AddHtmlLocalized( 70, 83, 150, 20, 1062954, 0x0, false, false ); // Guild Name - AddHtml( 233, 84, 320, 26, guild.Name, false, false ); + AddHtmlLocalized(96, 43, 110, 26, 1063014, 0xF, false, false); // My Guild - AddImageTiled( 65, 114, 160, 26, 0xA40 ); - AddImageTiled( 67, 116, 156, 22, 0xBBC ); - AddHtmlLocalized( 70, 117, 150, 20, 1063025, 0x0, false, false ); // Alliance + AddImageTiled(65, 80, 160, 26, 0xA40); + AddImageTiled(67, 82, 156, 22, 0xBBC); + AddHtmlLocalized(70, 83, 150, 20, 1062954, 0x0, false, false); // Guild Name + AddHtml(233, 84, 320, 26, guild.Name, false, false); - if ( guild.Alliance != null && guild.Alliance.IsMember( guild ) ) - { - AddHtml( 233, 118, 320, 26, guild.Alliance.Name, false, false ); - AddButton( 40, 120, 0x4B9, 0x4BA, 6, GumpButtonType.Reply, 0 ); //Alliance Roster - } + AddImageTiled(65, 114, 160, 26, 0xA40); + AddImageTiled(67, 116, 156, 22, 0xBBC); + AddHtmlLocalized(70, 117, 150, 20, 1063025, 0x0, false, false); // Alliance - if ( Guild.OrderChaos && isLeader ) - AddButton( 40, 154, 0x4B9, 0x4BA, 100, GumpButtonType.Reply, 0 ); // Guild Faction + if (guild.Alliance != null && guild.Alliance.IsMember(guild)) + { + AddHtml(233, 118, 320, 26, guild.Alliance.Name, false, false); + AddButton(40, 120, 0x4B9, 0x4BA, 6, GumpButtonType.Reply, 0); //Alliance Roster + } - AddImageTiled( 65, 148, 160, 26, 0xA40 ); - AddImageTiled( 67, 150, 156, 22, 0xBBC ); - AddHtmlLocalized( 70, 151, 150, 20, 1063084, 0x0, false, false ); // Guild Faction + if (Guild.OrderChaos && isLeader) + AddButton(40, 154, 0x4B9, 0x4BA, 100, GumpButtonType.Reply, 0); // Guild Faction - GuildType gt; - Faction f; + AddImageTiled(65, 148, 160, 26, 0xA40); + AddImageTiled(67, 150, 156, 22, 0xBBC); + AddHtmlLocalized(70, 151, 150, 20, 1063084, 0x0, false, false); // Guild Faction - if ( ( gt = guild.Type ) != GuildType.Regular ) - AddHtml( 233, 152, 320, 26, gt.ToString(), false, false ); - else if ( ( f = Faction.Find( guild.Leader ) ) != null ) - AddHtml( 233, 152, 320, 26, f.ToString(), false, false ); + GuildType gt; + Faction f; - AddImageTiled( 65, 196, 480, 4, 0x238D ); + if ((gt = guild.Type) != GuildType.Regular) + AddHtml(233, 152, 320, 26, gt.ToString(), false, false); + else if ((f = Faction.Find(guild.Leader)) != null) + AddHtml(233, 152, 320, 26, f.ToString(), false, false); + + AddImageTiled(65, 196, 480, 4, 0x238D); - string s = guild.Charter; - if ( string.IsNullOrEmpty( s ) ) - s = "The guild leader has not yet set the guild charter."; + string s = guild.Charter; + if (string.IsNullOrEmpty(s)) + s = "The guild leader has not yet set the guild charter."; - AddHtml( 65, 216, 480, 80, s, true, true ); - if ( isLeader ) - AddButton( 40, 251, 0x4B9, 0x4BA, 4, GumpButtonType.Reply, 0 ); //Charter Edit button + AddHtml(65, 216, 480, 80, s, true, true); + if (isLeader) + AddButton(40, 251, 0x4B9, 0x4BA, 4, GumpButtonType.Reply, 0); //Charter Edit button - s = guild.Website; - if ( string.IsNullOrEmpty( s ) ) - s = "Guild website not yet set."; - AddHtml( 65, 306, 480, 30, s, true, false ); - if ( isLeader ) - AddButton( 40, 313, 0x4B9, 0x4BA, 5, GumpButtonType.Reply, 0 ); //Website Edit button + s = guild.Website; + if (string.IsNullOrEmpty(s)) + s = "Guild website not yet set."; + AddHtml(65, 306, 480, 30, s, true, false); + if (isLeader) + AddButton(40, 313, 0x4B9, 0x4BA, 5, GumpButtonType.Reply, 0); //Website Edit button - AddCheck( 65, 370, 0xD2, 0xD3, player.DisplayGuildTitle, 0 ); - AddHtmlLocalized( 95, 370, 150, 26, 1063085, 0x0, false, false ); // Show Guild Title - AddBackground( 450, 370, 100, 26, 0x2486 ); + AddCheck(65, 370, 0xD2, 0xD3, player.DisplayGuildTitle, 0); + AddHtmlLocalized(95, 370, 150, 26, 1063085, 0x0, false, false); // Show Guild Title + AddBackground(450, 370, 100, 26, 0x2486); - AddButton( 455, 375, 0x845, 0x846, 7, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 480, 373, 60, 26, 3006115, (m_IsResigning) ? 0x5000 : 0, false, false ); // Resign - } + AddButton(455, 375, 0x845, 0x846, 7, GumpButtonType.Reply, 0); + AddHtmlLocalized(480, 373, 60, 26, 3006115, m_IsResigning ? 0x5000 : 0, false, false); // Resign + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - base.OnResponse( sender, info ); + public override void OnResponse(NetState sender, RelayInfo info) + { + base.OnResponse(sender, info); - PlayerMobile pm = sender.Mobile as PlayerMobile; + PlayerMobile pm = sender.Mobile as PlayerMobile; - if ( !IsMember( pm, guild ) ) - return; + if (!IsMember(pm, guild)) + return; - pm.DisplayGuildTitle = info.IsSwitched( 0 ); + pm.DisplayGuildTitle = info.IsSwitched(0); - switch( info.ButtonID ) - { - //1-3 handled by base.OnResponse - case 4: - { - if ( IsLeader( pm, guild ) ) - { - pm.SendLocalizedMessage( 1013071 ); // Enter the new guild charter (50 characters max): + switch (info.ButtonID) + { + //1-3 handled by base.OnResponse + case 4: + { + if (IsLeader(pm, guild)) + { + pm.SendLocalizedMessage(1013071); // Enter the new guild charter (50 characters max): - pm.BeginPrompt( SetCharter_Callback, true ); //Have the same callback handle both canceling and deletion cause the 2nd callback would just get a text of "" - } - break; - } - case 5: - { - if ( IsLeader( pm, guild ) ) - { - pm.SendLocalizedMessage( 1013072 ); // Enter the new website for the guild (50 characters max): - pm.BeginPrompt( SetWebsite_Callback, true ); //Have the same callback handle both canceling and deletion cause the 2nd callback would just get a text of "" - } - break; - } - case 6: - { - //Alliance Roster - if ( guild.Alliance != null && guild.Alliance.IsMember( guild ) ) - pm.SendGump( new AllianceInfo.AllianceRosterGump( pm, guild, guild.Alliance ) ); + pm.BeginPrompt(SetCharter_Callback, + true); //Have the same callback handle both canceling and deletion cause the 2nd callback would just get a text of "" + } - break; - } - case 7: - { - //Resign - if ( !m_IsResigning ) - { - pm.SendLocalizedMessage( 1063332 ); // Are you sure you wish to resign from your guild? - pm.SendGump( new GuildInfoGump( pm, guild, true ) ); - } - else - { - guild.RemoveMember( pm, 1063411 ); // You resign from your guild. - } - break; - } - case 100: // Custom code to support Order/Chaos in the new guild system - { - // Guild Faction - if ( Guild.OrderChaos && IsLeader( pm, guild ) ) - { - pm.CloseGump( typeof( GuildChangeTypeGump ) ); - pm.SendGump( new GuildChangeTypeGump( pm, guild ) ); - } - break; - } - } - } + break; + } + case 5: + { + if (IsLeader(pm, guild)) + { + pm.SendLocalizedMessage(1013072); // Enter the new website for the guild (50 characters max): + pm.BeginPrompt(SetWebsite_Callback, + true); //Have the same callback handle both canceling and deletion cause the 2nd callback would just get a text of "" + } - public void SetCharter_Callback( Mobile from, string text ) - { - if ( !IsLeader( from, guild ) ) - return; + break; + } + case 6: + { + //Alliance Roster + if (guild.Alliance != null && guild.Alliance.IsMember(guild)) + pm.SendGump(new AllianceInfo.AllianceRosterGump(pm, guild, guild.Alliance)); - string charter = Utility.FixHtml( text.Trim() ); + break; + } + case 7: + { + //Resign + if (!m_IsResigning) + { + pm.SendLocalizedMessage(1063332); // Are you sure you wish to resign from your guild? + pm.SendGump(new GuildInfoGump(pm, guild, true)); + } + else + { + guild.RemoveMember(pm, 1063411); // You resign from your guild. + } - if ( charter.Length > 50 ) - { - from.SendLocalizedMessage( 1070774, "50" ); // Your guild charter cannot exceed ~1_val~ characters. - } - else - { - guild.Charter = charter; - from.SendLocalizedMessage( 1070775 ); // You submit a new guild charter. - } - } + break; + } + case 100: // Custom code to support Order/Chaos in the new guild system + { + // Guild Faction + if (Guild.OrderChaos && IsLeader(pm, guild)) + { + pm.CloseGump(typeof(GuildChangeTypeGump)); + pm.SendGump(new GuildChangeTypeGump(pm, guild)); + } - public void SetWebsite_Callback( Mobile from, string text ) - { - if ( !IsLeader( from, guild ) ) - return; + break; + } + } + } - string site = Utility.FixHtml( text.Trim() ); + public void SetCharter_Callback(Mobile from, string text) + { + if (!IsLeader(from, guild)) + return; - if ( site.Length > 50 ) - from.SendLocalizedMessage( 1070777, "50" ); // Your guild website cannot exceed ~1_val~ characters. - else - { - guild.Website = site; - from.SendLocalizedMessage( 1070778 ); // You submit a new guild website. - } - } - } -} + string charter = Utility.FixHtml(text.Trim()); + + if (charter.Length > 50) + { + from.SendLocalizedMessage(1070774, "50"); // Your guild charter cannot exceed ~1_val~ characters. + } + else + { + guild.Charter = charter; + from.SendLocalizedMessage(1070775); // You submit a new guild charter. + } + } + + public void SetWebsite_Callback(Mobile from, string text) + { + if (!IsLeader(from, guild)) + return; + + string site = Utility.FixHtml(text.Trim()); + + if (site.Length > 50) + { + from.SendLocalizedMessage(1070777, "50"); // Your guild website cannot exceed ~1_val~ characters. + } + else + { + guild.Website = site; + from.SendLocalizedMessage(1070778); // You submit a new guild website. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/GuildInvitationRequest.cs b/Scripts/Gumps/Guilds/New Guild System/GuildInvitationRequest.cs index a6c2cd040..5d113f7ba 100644 --- a/Scripts/Gumps/Guilds/New Guild System/GuildInvitationRequest.cs +++ b/Scripts/Gumps/Guilds/New Guild System/GuildInvitationRequest.cs @@ -1,62 +1,65 @@ -using System; using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public class GuildInvitationRequest : BaseGuildGump - { - PlayerMobile m_Inviter; - public GuildInvitationRequest( PlayerMobile pm, Guild g, PlayerMobile inviter ) : base( pm, g ) - { - m_Inviter = inviter; + public class GuildInvitationRequest : BaseGuildGump + { + private PlayerMobile m_Inviter; - PopulateGump(); - } + public GuildInvitationRequest(PlayerMobile pm, Guild g, PlayerMobile inviter) : base(pm, g) + { + m_Inviter = inviter; - public override void PopulateGump() - { - AddPage( 0 ); + PopulateGump(); + } - AddBackground( 0, 0, 350, 170, 0x2422 ); - AddHtmlLocalized( 25, 20, 300, 45, 1062946, 0x0, true, false ); //
You have been invited to join a guild! (Warning: Accepting will make you attackable!)
- AddHtml( 25, 75, 300, 25, $"
{guild.Name}
", true, false ); - AddButton( 265, 130, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0 ); - AddButton( 195, 130, 0xF2, 0xF1, 0, GumpButtonType.Reply, 0 ); - AddButton( 20, 130, 0xD2, 0xD3, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 130, 150, 30, 1062943, 0x0, false, false ); // Ignore Guild Invites - } + public override void PopulateGump() + { + AddPage(0); + + AddBackground(0, 0, 350, 170, 0x2422); + AddHtmlLocalized(25, 20, 300, 45, 1062946, 0x0, true, + false); //
You have been invited to join a guild! (Warning: Accepting will make you attackable!)
+ AddHtml(25, 75, 300, 25, $"
{guild.Name}
", true, false); + AddButton(265, 130, 0xF7, 0xF8, 1, GumpButtonType.Reply, 0); + AddButton(195, 130, 0xF2, 0xF1, 0, GumpButtonType.Reply, 0); + AddButton(20, 130, 0xD2, 0xD3, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 130, 150, 30, 1062943, 0x0, false, false); // Ignore Guild Invites + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( guild.Disbanded || player.Guild != null ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (guild.Disbanded || player.Guild != null) + return; - switch( info.ButtonID ) - { - case 0: - { - m_Inviter.SendLocalizedMessage( 1063250, $"{player.Name}\t{guild.Name}"); // ~1_val~ has declined your invitation to join ~2_val~. - break; - } - case 1: - { - guild.AddMember( player ); - player.SendLocalizedMessage( 1063056, guild.Name ); // You have joined ~1_val~. - m_Inviter.SendLocalizedMessage( 1063249, $"{player.Name}\t{guild.Name}"); // ~1_val~ has accepted your invitation to join ~2_val~. + switch (info.ButtonID) + { + case 0: + { + m_Inviter.SendLocalizedMessage(1063250, + $"{player.Name}\t{guild.Name}"); // ~1_val~ has declined your invitation to join ~2_val~. + break; + } + case 1: + { + guild.AddMember(player); + player.SendLocalizedMessage(1063056, guild.Name); // You have joined ~1_val~. + m_Inviter.SendLocalizedMessage(1063249, + $"{player.Name}\t{guild.Name}"); // ~1_val~ has accepted your invitation to join ~2_val~. - break; - } - case 2: - { - player.AcceptGuildInvites = false; - player.SendLocalizedMessage( 1070698 ); // You are now ignoring guild invitations. + break; + } + case 2: + { + player.AcceptGuildInvites = false; + player.SendLocalizedMessage(1070698); // You are now ignoring guild invitations. - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/GuildMemberInfoGump.cs b/Scripts/Gumps/Guilds/New Guild System/GuildMemberInfoGump.cs index 475450ea0..abac3b2f4 100644 --- a/Scripts/Gumps/Guilds/New Guild System/GuildMemberInfoGump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/GuildMemberInfoGump.cs @@ -1,220 +1,255 @@ using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public class GuildMemberInfoGump : BaseGuildGump - { - PlayerMobile m_Member; - bool m_ToLeader, m_toKick; + public class GuildMemberInfoGump : BaseGuildGump + { + private PlayerMobile m_Member; + private bool m_ToLeader, m_toKick; - public GuildMemberInfoGump( PlayerMobile pm, Guild g, PlayerMobile member, bool toKick, bool toPromoteToLeader ) : base( pm, g, 10, 40 ) - { - m_ToLeader = toPromoteToLeader; - m_toKick = toKick; - m_Member = member; - PopulateGump(); - } + public GuildMemberInfoGump(PlayerMobile pm, Guild g, PlayerMobile member, bool toKick, bool toPromoteToLeader) : + base(pm, g, 10, 40) + { + m_ToLeader = toPromoteToLeader; + m_toKick = toKick; + m_Member = member; + PopulateGump(); + } - public override void PopulateGump() - { - AddPage( 0 ); + public override void PopulateGump() + { + AddPage(0); - AddBackground( 0, 0, 350, 255, 0x242C ); - AddHtmlLocalized( 20, 15, 310, 26, 1063018, 0x0, false, false ); //
Guild Member Information
- AddImageTiled( 20, 40, 310, 2, 0x2711 ); + AddBackground(0, 0, 350, 255, 0x242C); + AddHtmlLocalized(20, 15, 310, 26, 1063018, 0x0, false, + false); //
Guild Member Information
+ AddImageTiled(20, 40, 310, 2, 0x2711); - AddHtmlLocalized( 20, 50, 150, 26, 1062955, 0x0, true, false ); // Name - AddHtml( 180, 53, 150, 26, m_Member.Name, false, false ); + AddHtmlLocalized(20, 50, 150, 26, 1062955, 0x0, true, false); // Name + AddHtml(180, 53, 150, 26, m_Member.Name, false, false); - AddHtmlLocalized( 20, 80, 150, 26, 1062956, 0x0, true, false ); // Rank - AddHtmlLocalized( 180, 83, 150, 26, m_Member.GuildRank.Name, 0x0, false, false ); + AddHtmlLocalized(20, 80, 150, 26, 1062956, 0x0, true, false); // Rank + AddHtmlLocalized(180, 83, 150, 26, m_Member.GuildRank.Name, 0x0, false, false); - AddHtmlLocalized( 20, 110, 150, 26, 1062953, 0x0, true, false ); // Guild Title - AddHtml( 180, 113, 150, 26, m_Member.GuildTitle, false, false ); - AddImageTiled( 20, 142, 310, 2, 0x2711 ); + AddHtmlLocalized(20, 110, 150, 26, 1062953, 0x0, true, false); // Guild Title + AddHtml(180, 113, 150, 26, m_Member.GuildTitle, false, false); + AddImageTiled(20, 142, 310, 2, 0x2711); - AddBackground( 20, 150, 310, 26, 0x2486 ); - AddButton( 25, 155, 0x845, 0x846, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 153, 270, 26, (m_Member == player.GuildFealty && guild.Leader != m_Member) ? 1063082 : 1062996, 0x0, false, false ); // Clear/Cast Vote For This Member + AddBackground(20, 150, 310, 26, 0x2486); + AddButton(25, 155, 0x845, 0x846, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 153, 270, 26, + m_Member == player.GuildFealty && guild.Leader != m_Member ? 1063082 : 1062996, 0x0, false, + false); // Clear/Cast Vote For This Member - AddBackground( 20, 180, 150, 26, 0x2486 ); - AddButton( 25, 185, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 183, 110, 26, 1062993, (m_ToLeader)? 0x990000 : 0, false, false ); // Promote + AddBackground(20, 180, 150, 26, 0x2486); + AddButton(25, 185, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 183, 110, 26, 1062993, m_ToLeader ? 0x990000 : 0, false, false); // Promote - AddBackground( 180, 180, 150, 26, 0x2486 ); - AddButton( 185, 185, 0x845, 0x846, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 210, 183, 110, 26, 1062995, 0x0, false, false ); // Set Guild Title + AddBackground(180, 180, 150, 26, 0x2486); + AddButton(185, 185, 0x845, 0x846, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(210, 183, 110, 26, 1062995, 0x0, false, false); // Set Guild Title - AddBackground( 20, 210, 150, 26, 0x2486 ); - AddButton( 25, 215, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 213, 110, 26, 1062994, 0x0, false, false ); // Demote + AddBackground(20, 210, 150, 26, 0x2486); + AddButton(25, 215, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 213, 110, 26, 1062994, 0x0, false, false); // Demote - AddBackground( 180, 210, 150, 26, 0x2486 ); - AddButton( 185, 215, 0x845, 0x846, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 210, 213, 110, 26, 1062997, (m_toKick)? 0x5000 : 0, false, false ); // Kick - } + AddBackground(180, 210, 150, 26, 0x2486); + AddButton(185, 215, 0x845, 0x846, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(210, 213, 110, 26, 1062997, m_toKick ? 0x5000 : 0, false, false); // Kick + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !(sender.Mobile is PlayerMobile pm) || !IsMember( pm, guild ) || !IsMember( m_Member, guild ) ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!(sender.Mobile is PlayerMobile pm) || !IsMember(pm, guild) || !IsMember(m_Member, guild)) + return; - RankDefinition playerRank = pm.GuildRank; - RankDefinition targetRank = m_Member.GuildRank; + RankDefinition playerRank = pm.GuildRank; + RankDefinition targetRank = m_Member.GuildRank; - switch( info.ButtonID ) - { - case 1: //Promote - { - if ( playerRank.GetFlag( RankFlags.CanPromoteDemote ) && ((playerRank.Rank -1 ) > targetRank.Rank || ( playerRank == RankDefinition.Leader && playerRank.Rank > targetRank.Rank )) ) - { - targetRank = RankDefinition.Ranks[targetRank.Rank + 1]; + switch (info.ButtonID) + { + case 1: //Promote + { + if (playerRank.GetFlag(RankFlags.CanPromoteDemote) && + (playerRank.Rank - 1 > targetRank.Rank || + playerRank == RankDefinition.Leader && playerRank.Rank > targetRank.Rank)) + { + targetRank = RankDefinition.Ranks[targetRank.Rank + 1]; - if ( targetRank == RankDefinition.Leader ) - { - if ( m_ToLeader ) - { - m_Member.GuildRank = targetRank; - pm.SendLocalizedMessage( 1063156, m_Member.Name ); // The guild information for ~1_val~ has been updated. - pm.SendLocalizedMessage( 1063156, pm.Name ); // The guild information for ~1_val~ has been updated. - guild.Leader = m_Member; - } - else - { - pm.SendLocalizedMessage( 1063144 ); // Are you sure you wish to make this member the new guild leader? - pm.SendGump( new GuildMemberInfoGump( player, guild, m_Member, false, true ) ); - } - } - else - { - m_Member.GuildRank = targetRank; - pm.SendLocalizedMessage( 1063156, m_Member.Name ); // The guild information for ~1_val~ has been updated. - } - } - else - pm.SendLocalizedMessage( 1063143 ); // You don't have permission to promote this member. + if (targetRank == RankDefinition.Leader) + { + if (m_ToLeader) + { + m_Member.GuildRank = targetRank; + pm.SendLocalizedMessage(1063156, + m_Member.Name); // The guild information for ~1_val~ has been updated. + pm.SendLocalizedMessage(1063156, + pm.Name); // The guild information for ~1_val~ has been updated. + guild.Leader = m_Member; + } + else + { + pm.SendLocalizedMessage( + 1063144); // Are you sure you wish to make this member the new guild leader? + pm.SendGump(new GuildMemberInfoGump(player, guild, m_Member, false, true)); + } + } + else + { + m_Member.GuildRank = targetRank; + pm.SendLocalizedMessage(1063156, + m_Member.Name); // The guild information for ~1_val~ has been updated. + } + } + else + { + pm.SendLocalizedMessage(1063143); // You don't have permission to promote this member. + } - break; - } - case 2: //Demote - { - if ( playerRank.GetFlag( RankFlags.CanPromoteDemote ) && playerRank.Rank > targetRank.Rank ) - { - if ( targetRank == RankDefinition.Lowest ) - { - if ( RankDefinition.Lowest.Name.Number == 1062963 ) - pm.SendLocalizedMessage( 1063333 ); // You can't demote a ronin. - else - pm.SendMessage( "You can't demote a {0}.", RankDefinition.Lowest.Name ); - } - else - { - m_Member.GuildRank = RankDefinition.Ranks[targetRank.Rank - 1]; - pm.SendLocalizedMessage( 1063156, m_Member.Name ); // The guild information for ~1_val~ has been updated. - } - } - else - pm.SendLocalizedMessage( 1063146 ); // You don't have permission to demote this member. + break; + } + case 2: //Demote + { + if (playerRank.GetFlag(RankFlags.CanPromoteDemote) && playerRank.Rank > targetRank.Rank) + { + if (targetRank == RankDefinition.Lowest) + { + if (RankDefinition.Lowest.Name.Number == 1062963) + pm.SendLocalizedMessage(1063333); // You can't demote a ronin. + else + pm.SendMessage("You can't demote a {0}.", RankDefinition.Lowest.Name); + } + else + { + m_Member.GuildRank = RankDefinition.Ranks[targetRank.Rank - 1]; + pm.SendLocalizedMessage(1063156, + m_Member.Name); // The guild information for ~1_val~ has been updated. + } + } + else + { + pm.SendLocalizedMessage(1063146); // You don't have permission to demote this member. + } - break; - } - case 3: //Set Guild title - { - if ( playerRank.GetFlag( RankFlags.CanSetGuildTitle ) && ( playerRank.Rank > targetRank.Rank || m_Member == player)) - { - pm.SendLocalizedMessage( 1011128 ); // Enter the new title for this guild member or 'none' to remove a title: + break; + } + case 3: //Set Guild title + { + if (playerRank.GetFlag(RankFlags.CanSetGuildTitle) && + (playerRank.Rank > targetRank.Rank || m_Member == player)) + { + pm.SendLocalizedMessage( + 1011128); // Enter the new title for this guild member or 'none' to remove a title: - pm.BeginPrompt( SetTitle_Callback ); - } - else if ( m_Member.GuildTitle == null || m_Member.GuildTitle.Length <= 0 ) - { - pm.SendLocalizedMessage( 1070746 ); // You don't have the permission to set that member's guild title. - } - else - { - pm.SendLocalizedMessage( 1063148 ); // You don't have permission to change this member's guild title. - } + pm.BeginPrompt(SetTitle_Callback); + } + else if (m_Member.GuildTitle == null || m_Member.GuildTitle.Length <= 0) + { + pm.SendLocalizedMessage(1070746); // You don't have the permission to set that member's guild title. + } + else + { + pm.SendLocalizedMessage(1063148); // You don't have permission to change this member's guild title. + } - break; - } - case 4: //Vote - { - if ( m_Member == pm.GuildFealty && guild.Leader != m_Member ) - pm.SendLocalizedMessage( 1063158 ); // You have cleared your vote for guild leader. - else if ( guild.CanVote( m_Member ) )//( playerRank.GetFlag( RankFlags.CanVote ) ) - { - if ( m_Member == guild.Leader ) - pm.SendLocalizedMessage( 1063424 ); // You can't vote for the current guild leader. - else if ( !guild.CanBeVotedFor( m_Member ) ) - pm.SendLocalizedMessage( 1063425 ); // You can't vote for an inactive guild member. - else - { - pm.GuildFealty = m_Member; - pm.SendLocalizedMessage( 1063159, m_Member.Name ); // You cast your vote for ~1_val~ for guild leader. - } - } - else - pm.SendLocalizedMessage( 1063149 ); // You don't have permission to vote. + break; + } + case 4: //Vote + { + if (m_Member == pm.GuildFealty && guild.Leader != m_Member) + { + pm.SendLocalizedMessage(1063158); // You have cleared your vote for guild leader. + } + else if (guild.CanVote(m_Member)) //( playerRank.GetFlag( RankFlags.CanVote ) ) + { + if (m_Member == guild.Leader) + { + pm.SendLocalizedMessage(1063424); // You can't vote for the current guild leader. + } + else if (!guild.CanBeVotedFor(m_Member)) + { + pm.SendLocalizedMessage(1063425); // You can't vote for an inactive guild member. + } + else + { + pm.GuildFealty = m_Member; + pm.SendLocalizedMessage(1063159, + m_Member.Name); // You cast your vote for ~1_val~ for guild leader. + } + } + else + { + pm.SendLocalizedMessage(1063149); // You don't have permission to vote. + } - break; - } - case 5: //Kick - { - if ( ( playerRank.GetFlag( RankFlags.RemovePlayers ) && playerRank.Rank > targetRank.Rank ) || ( playerRank.GetFlag( RankFlags.RemoveLowestRank ) && targetRank == RankDefinition.Lowest ) ) - { - if ( m_toKick ) - { - guild.RemoveMember( m_Member ); - pm.SendLocalizedMessage( 1063157 ); // The member has been removed from your guild. - } - else - { - pm.SendLocalizedMessage( 1063152 ); // Are you sure you wish to kick this member from the guild? - pm.SendGump( new GuildMemberInfoGump( player, guild, m_Member, true, false ) ); - } - } - else - pm.SendLocalizedMessage( 1063151 ); // You don't have permission to remove this member. + break; + } + case 5: //Kick + { + if (playerRank.GetFlag(RankFlags.RemovePlayers) && playerRank.Rank > targetRank.Rank || + playerRank.GetFlag(RankFlags.RemoveLowestRank) && targetRank == RankDefinition.Lowest) + { + if (m_toKick) + { + guild.RemoveMember(m_Member); + pm.SendLocalizedMessage(1063157); // The member has been removed from your guild. + } + else + { + pm.SendLocalizedMessage(1063152); // Are you sure you wish to kick this member from the guild? + pm.SendGump(new GuildMemberInfoGump(player, guild, m_Member, true, false)); + } + } + else + { + pm.SendLocalizedMessage(1063151); // You don't have permission to remove this member. + } - break; - } - } - } + break; + } + } + } - public void SetTitle_Callback( Mobile from, string text ) - { - if (!(from is PlayerMobile pm) || m_Member == null ) - return; + public void SetTitle_Callback(Mobile from, string text) + { + if (!(from is PlayerMobile pm) || m_Member == null) + return; - if ( !(m_Member.Guild is Guild g) || !IsMember( pm, g ) || !(pm.GuildRank.GetFlag( RankFlags.CanSetGuildTitle ) && (pm.GuildRank.Rank > m_Member.GuildRank.Rank || pm == m_Member)) ) - { - if ( m_Member.GuildTitle == null || m_Member.GuildTitle.Length <= 0 ) - pm.SendLocalizedMessage( 1070746 ); // You don't have the permission to set that member's guild title. - else - pm.SendLocalizedMessage( 1063148 ); // You don't have permission to change this member's guild title. + if (!(m_Member.Guild is Guild g) || !IsMember(pm, g) || + !(pm.GuildRank.GetFlag(RankFlags.CanSetGuildTitle) && + (pm.GuildRank.Rank > m_Member.GuildRank.Rank || pm == m_Member))) + { + if (m_Member.GuildTitle == null || m_Member.GuildTitle.Length <= 0) + pm.SendLocalizedMessage(1070746); // You don't have the permission to set that member's guild title. + else + pm.SendLocalizedMessage(1063148); // You don't have permission to change this member's guild title. - return; - } + return; + } - string title = Utility.FixHtml( text.Trim() ); + string title = Utility.FixHtml(text.Trim()); - if ( title.Length > 20 ) - from.SendLocalizedMessage( 501178 ); // That title is too long. - else if ( !CheckProfanity( title ) ) - from.SendLocalizedMessage( 501179 ); // That title is disallowed. - else - { - if ( Insensitive.Equals( title, "none" ) ) - m_Member.GuildTitle = null; - else - m_Member.GuildTitle = title; + if (title.Length > 20) + { + from.SendLocalizedMessage(501178); // That title is too long. + } + else if (!CheckProfanity(title)) + { + from.SendLocalizedMessage(501179); // That title is disallowed. + } + else + { + if (Insensitive.Equals(title, "none")) + m_Member.GuildTitle = null; + else + m_Member.GuildTitle = title; - pm.SendLocalizedMessage( 1063156, m_Member.Name ); // The guild information for ~1_val~ has been updated. - } - } - } -} + pm.SendLocalizedMessage(1063156, m_Member.Name); // The guild information for ~1_val~ has been updated. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/GuildRosterGump.cs b/Scripts/Gumps/Guilds/New Guild System/GuildRosterGump.cs index c3ce2bdcf..97df6a2a0 100644 --- a/Scripts/Gumps/Guilds/New Guild System/GuildRosterGump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/GuildRosterGump.cs @@ -1,259 +1,257 @@ -using System; -using Server.Gumps; -using Server.Network; -using Server.Mobiles; -using Server.Factions; using System.Collections.Generic; +using Server.Factions; +using Server.Gumps; +using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Guilds { - public class GuildRosterGump : BaseGuildListGump - { - #region Comparers - private class NameComparer : IComparer - { - public static readonly IComparer Instance = new NameComparer(); + public class GuildRosterGump : BaseGuildListGump + { + private static InfoField[] m_Fields = + { + new InfoField(1062955, 130, NameComparer.Instance), //Name + new InfoField(1062956, 80, RankComparer.Instance), //Rank + new InfoField(1062952, 80, LastOnComparer.Instance), //Last On + new InfoField(1062953, 150, TitleComparer.Instance) //Guild Title + }; - public NameComparer() - { - } + public GuildRosterGump(PlayerMobile pm, Guild g) : this(pm, g, LastOnComparer.Instance, false, "", 0) + { + } - public int Compare( PlayerMobile x, PlayerMobile y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + public GuildRosterGump(PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, + string filter, int startNumber) + : base(pm, g, Utility.SafeConvertList(g.Members), currentComparer, ascending, filter, + startNumber, m_Fields) + { + PopulateGump(); + } - return Insensitive.Compare( x.Name, y.Name ); - } - } + public override void PopulateGump() + { + base.PopulateGump(); - private class LastOnComparer : IComparer - { - public static readonly IComparer Instance = new LastOnComparer(); + AddHtmlLocalized(266, 43, 110, 26, 1062974, 0xF, false, false); // Guild Roster + } - public LastOnComparer() - { - } + public override void DrawEndingEntry(int itemNumber) + { + AddBackground(225, 148 + itemNumber * 28, 150, 26, 0x2486); + AddButton(230, 153 + itemNumber * 28, 0x845, 0x846, 8, GumpButtonType.Reply, 0); + AddHtmlLocalized(255, 151 + itemNumber * 28, 110, 26, 1062992, 0x0, false, false); // Invite Player + } - public int Compare( PlayerMobile x, PlayerMobile y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + protected override TextDefinition[] GetValuesFor(PlayerMobile pm, int aryLength) + { + TextDefinition[] defs = new TextDefinition[aryLength]; - NetState aState = x.NetState; - NetState bState = y.NetState; + string name = $"{pm.Name}{(player.GuildFealty == pm && player.GuildFealty != guild.Leader ? " *" : "")}"; - if ( aState == null && bState == null ) - return x.LastOnline.CompareTo( y.LastOnline ); - if ( aState == null ) - return -1; - if ( bState == null ) - return 1; - return 0; - } - } - private class TitleComparer : IComparer - { - public static readonly IComparer Instance = new TitleComparer(); + if (pm == player) + name = Color(name, 0x006600); + else if (pm.NetState != null) + name = Color(name, 0x000066); - public TitleComparer() - { - } + defs[0] = name; + defs[1] = pm.GuildRank.Name; + defs[2] = pm.NetState != null + ? new TextDefinition(1063015) + : new TextDefinition(pm.LastOnline.ToString("yyyy-MM-dd")); + defs[3] = pm.GuildTitle ?? ""; - public int Compare( PlayerMobile x, PlayerMobile y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + return defs; + } - return Insensitive.Compare( x.GuildTitle, y.GuildTitle ); - } - } + protected override bool IsFiltered(PlayerMobile pm, string filter) + { + if (pm == null) + return true; - private class RankComparer : IComparer - { - public static readonly IComparer Instance = new RankComparer(); + return !Insensitive.Contains(pm.Name, filter); + } - public RankComparer() - { - } + public override Gump GetResentGump(PlayerMobile pm, Guild g, IComparer comparer, bool ascending, + string filter, int startNumber) + { + return new GuildRosterGump(pm, g, comparer, ascending, filter, startNumber); + } - public int Compare( PlayerMobile x, PlayerMobile y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; + public override Gump GetObjectInfoGump(PlayerMobile pm, Guild g, PlayerMobile o) + { + return new GuildMemberInfoGump(pm, g, o, false, false); + } - return x.GuildRank.Rank.CompareTo( y.GuildRank.Rank ); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + base.OnResponse(sender, info); - #endregion + if (!(sender.Mobile is PlayerMobile pm) || !IsMember(pm, guild)) + return; - private static InfoField[] m_Fields = - { - new InfoField( 1062955, 130, NameComparer.Instance ), //Name - new InfoField( 1062956, 80, RankComparer.Instance ), //Rank - new InfoField( 1062952, 80, LastOnComparer.Instance), //Last On - new InfoField( 1062953, 150, TitleComparer.Instance ) //Guild Title - }; + if (info.ButtonID == 8) + { + if (pm.GuildRank.GetFlag(RankFlags.CanInvitePlayer)) + { + pm.SendLocalizedMessage(1063048); // Whom do you wish to invite into your guild? + pm.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(InvitePlayer_Callback), guild); + } + else + { + pm.SendLocalizedMessage(503301); // You don't have permission to do that. + } + } + } - public GuildRosterGump( PlayerMobile pm, Guild g ) : this( pm, g, LastOnComparer.Instance, false, "", 0 ) - { - } + public void InvitePlayer_Callback(Mobile from, object targeted, object state) + { + PlayerMobile pm = from as PlayerMobile; + PlayerMobile targ = targeted as PlayerMobile; - public GuildRosterGump( PlayerMobile pm, Guild g, IComparer currentComparer, bool ascending, string filter, int startNumber ) - : base( pm, g, Utility.SafeConvertList( g.Members ), currentComparer, ascending, filter, startNumber, m_Fields ) - { - PopulateGump(); - } + Guild g = state as Guild; - public override void PopulateGump() - { - base.PopulateGump(); + PlayerState guildState = PlayerState.Find(g.Leader); + PlayerState targetState = PlayerState.Find(targ); - AddHtmlLocalized( 266, 43, 110, 26, 1062974, 0xF, false, false ); // Guild Roster - } + Faction guildFaction = guildState?.Faction; + Faction targetFaction = targetState?.Faction; - public override void DrawEndingEntry( int itemNumber ) - { - AddBackground( 225, 148 + itemNumber * 28, 150, 26, 0x2486 ); - AddButton( 230, 153 + itemNumber * 28, 0x845, 0x846, 8, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 255, 151 + itemNumber * 28, 110, 26, 1062992, 0x0, false, false ); // Invite Player - } + if (pm == null || !IsMember(pm, guild) || !pm.GuildRank.GetFlag(RankFlags.CanInvitePlayer)) + { + pm.SendLocalizedMessage(503301); // You don't have permission to do that. + } + else if (targ == null) + { + pm.SendLocalizedMessage(1063334); // That isn't a valid player. + } + else if (!targ.AcceptGuildInvites) + { + pm.SendLocalizedMessage(1063049, targ.Name); // ~1_val~ is not accepting guild invitations. + } + else if (g.IsMember(targ)) + { + pm.SendLocalizedMessage(1063050, targ.Name); // ~1_val~ is already a member of your guild! + } + else if (targ.Guild != null) + { + pm.SendLocalizedMessage(1063051, targ.Name); // ~1_val~ is already a member of a guild. + } + else if (targ.HasGump(typeof(BaseGuildGump)) || targ.HasGump(typeof(CreateGuildGump)) + ) //TODO: Check message if CreateGuildGump Open + { + pm.SendLocalizedMessage(1063052, targ.Name); // ~1_val~ is currently considering another guild invitation. + } - protected override TextDefinition[] GetValuesFor( PlayerMobile pm, int aryLength ) - { - TextDefinition[] defs = new TextDefinition[aryLength]; + #region Factions - string name = $"{pm.Name}{((player.GuildFealty == pm && player.GuildFealty != guild.Leader) ? " *" : "")}"; + else if (targ.Young && guildFaction != null) + { + pm.SendLocalizedMessage(1070766); // You cannot invite a young player to your faction-aligned guild. + } + else if (guildFaction != targetFaction) + { + if (guildFaction == null) + pm.SendLocalizedMessage(1013027); // That player cannot join a non-faction guild. + else if (targetFaction == null) + pm.SendLocalizedMessage(1013026); // That player must be in a faction before joining this guild. + else + pm.SendLocalizedMessage(1013028); // That person has a different faction affiliation. + } + else if (targetState != null && targetState.IsLeaving) + { + // OSI does this quite strangely, so we'll just do it this way + pm.SendMessage("That person is quitting their faction and so you may not recruit them."); + } - if ( pm == player ) - name = Color( name, 0x006600 ); - else if ( pm.NetState != null ) - name = Color( name, 0x000066 ); + #endregion - defs[0] = name; - defs[1] = pm.GuildRank.Name; - defs[2] = (pm.NetState != null) ? new TextDefinition( 1063015 ): new TextDefinition( pm.LastOnline.ToString( "yyyy-MM-dd" ) ); - defs[3] = pm.GuildTitle ?? ""; + else + { + pm.SendLocalizedMessage(1063053, targ.Name); // You invite ~1_val~ to join your guild. + targ.SendGump(new GuildInvitationRequest(targ, guild, pm)); + } + } - return defs; - } + #region Comparers - protected override bool IsFiltered( PlayerMobile pm, string filter ) - { - if ( pm == null ) - return true; + private class NameComparer : IComparer + { + public static readonly IComparer Instance = new NameComparer(); - return !Insensitive.Contains( pm.Name, filter ); - } + public int Compare(PlayerMobile x, PlayerMobile y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; - public override Gump GetResentGump( PlayerMobile pm, Guild g, IComparer comparer, bool ascending, string filter, int startNumber ) - { - return new GuildRosterGump( pm, g, comparer, ascending, filter, startNumber ); - } + return Insensitive.Compare(x.Name, y.Name); + } + } - public override Gump GetObjectInfoGump( PlayerMobile pm, Guild g, PlayerMobile o ) - { - return new GuildMemberInfoGump( pm, g, o, false, false ) ; - } + private class LastOnComparer : IComparer + { + public static readonly IComparer Instance = new LastOnComparer(); - public override void OnResponse( NetState sender, RelayInfo info ) - { - base.OnResponse( sender, info ); + public int Compare(PlayerMobile x, PlayerMobile y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; - if ( !(sender.Mobile is PlayerMobile pm) || !IsMember( pm, guild ) ) - return; + NetState aState = x.NetState; + NetState bState = y.NetState; - if ( info.ButtonID == 8 ) - { - if ( pm.GuildRank.GetFlag( RankFlags.CanInvitePlayer ) ) - { - pm.SendLocalizedMessage( 1063048 ); // Whom do you wish to invite into your guild? - pm.BeginTarget( -1, false, Targeting.TargetFlags.None, new TargetStateCallback( InvitePlayer_Callback ), guild ); - } - else - pm.SendLocalizedMessage( 503301 ); // You don't have permission to do that. - } - } + if (aState == null && bState == null) + return x.LastOnline.CompareTo(y.LastOnline); + if (aState == null) + return -1; + if (bState == null) + return 1; + return 0; + } + } - public void InvitePlayer_Callback( Mobile from, object targeted, object state ) - { - PlayerMobile pm = from as PlayerMobile; - PlayerMobile targ = targeted as PlayerMobile; + private class TitleComparer : IComparer + { + public static readonly IComparer Instance = new TitleComparer(); - Guild g = state as Guild; + public int Compare(PlayerMobile x, PlayerMobile y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; - PlayerState guildState = PlayerState.Find( g.Leader ); - PlayerState targetState = PlayerState.Find( targ ); + return Insensitive.Compare(x.GuildTitle, y.GuildTitle); + } + } - Faction guildFaction = guildState?.Faction; - Faction targetFaction = targetState?.Faction; + private class RankComparer : IComparer + { + public static readonly IComparer Instance = new RankComparer(); - if ( pm == null || !IsMember( pm, guild ) || !pm.GuildRank.GetFlag( RankFlags.CanInvitePlayer ) ) - { - pm.SendLocalizedMessage( 503301 ); // You don't have permission to do that. - } - else if ( targ == null ) - { - pm.SendLocalizedMessage( 1063334 ); // That isn't a valid player. - } - else if ( !targ.AcceptGuildInvites ) - { - pm.SendLocalizedMessage( 1063049, targ.Name ); // ~1_val~ is not accepting guild invitations. - } - else if ( g.IsMember( targ ) ) - { - pm.SendLocalizedMessage( 1063050, targ.Name ); // ~1_val~ is already a member of your guild! - } - else if ( targ.Guild != null ) - { - pm.SendLocalizedMessage( 1063051, targ.Name ); // ~1_val~ is already a member of a guild. - } - else if ( targ.HasGump( typeof( BaseGuildGump ) ) || targ.HasGump( typeof( CreateGuildGump ) )) //TODO: Check message if CreateGuildGump Open - { - pm.SendLocalizedMessage( 1063052, targ.Name ); // ~1_val~ is currently considering another guild invitation. - } - #region Factions - else if ( targ.Young && guildFaction != null ) - { - pm.SendLocalizedMessage( 1070766 ); // You cannot invite a young player to your faction-aligned guild. - } - else if ( guildFaction != targetFaction ) - { - if ( guildFaction == null ) - pm.SendLocalizedMessage( 1013027 ); // That player cannot join a non-faction guild. - else if ( targetFaction == null ) - pm.SendLocalizedMessage( 1013026 ); // That player must be in a faction before joining this guild. - else - pm.SendLocalizedMessage( 1013028 ); // That person has a different faction affiliation. - } - else if ( targetState != null && targetState.IsLeaving ) - { - // OSI does this quite strangely, so we'll just do it this way - pm.SendMessage( "That person is quitting their faction and so you may not recruit them." ); - } - #endregion - else - { - pm.SendLocalizedMessage( 1063053, targ.Name ); // You invite ~1_val~ to join your guild. - targ.SendGump( new GuildInvitationRequest( targ, guild, pm ) ); - } - } - } -} + public int Compare(PlayerMobile x, PlayerMobile y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + return x.GuildRank.Rank.CompareTo(y.GuildRank.Rank); + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/OtherGuildInfo.cs b/Scripts/Gumps/Guilds/New Guild System/OtherGuildInfo.cs index 7b408e018..953010c66 100644 --- a/Scripts/Gumps/Guilds/New Guild System/OtherGuildInfo.cs +++ b/Scripts/Gumps/Guilds/New Guild System/OtherGuildInfo.cs @@ -1,634 +1,703 @@ using System; -using Server.Mobiles; -using Server.Gumps; -using Server.Network; using Server.Factions; +using Server.Gumps; +using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public class OtherGuildInfo : BaseGuildGump - { - private Guild m_Other; - public OtherGuildInfo( PlayerMobile pm, Guild g, Guild otherGuild ) : base( pm, g, 10, 40 ) - { - m_Other = otherGuild; + public class OtherGuildInfo : BaseGuildGump + { + private Guild m_Other; - g.CheckExpiredWars(); + public OtherGuildInfo(PlayerMobile pm, Guild g, Guild otherGuild) : base(pm, g, 10, 40) + { + m_Other = otherGuild; - PopulateGump(); - } + g.CheckExpiredWars(); - public void AddButtonAndBackground( int x, int y, int buttonID, int locNum ) - { - AddBackground( x, y, 225, 26, 0x2486 ); - AddButton( x+5, y+5, 0x845, 0x846, buttonID, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( x+30, y+3, 185, 26, locNum, 0x0, false, false ); - } + PopulateGump(); + } - public override void PopulateGump() - { - Guild g = Guild.GetAllianceLeader( guild ); - Guild other = Guild.GetAllianceLeader( m_Other ); + public void AddButtonAndBackground(int x, int y, int buttonID, int locNum) + { + AddBackground(x, y, 225, 26, 0x2486); + AddButton(x + 5, y + 5, 0x845, 0x846, buttonID, GumpButtonType.Reply, 0); + AddHtmlLocalized(x + 30, y + 3, 185, 26, locNum, 0x0, false, false); + } - WarDeclaration war = g.FindPendingWar( other ); - WarDeclaration activeWar = g.FindActiveWar( other ); + public override void PopulateGump() + { + Guild g = Guild.GetAllianceLeader(guild); + Guild other = Guild.GetAllianceLeader(m_Other); - AllianceInfo alliance = guild.Alliance; - AllianceInfo otherAlliance = m_Other.Alliance; - //NOTE TO SELF: Only only alliance leader can see pending guild alliance statuses + WarDeclaration war = g.FindPendingWar(other); + WarDeclaration activeWar = g.FindActiveWar(other); - bool PendingWar = (war != null); - bool ActiveWar = (activeWar != null); - AddPage( 0 ); + AllianceInfo alliance = guild.Alliance; + AllianceInfo otherAlliance = m_Other.Alliance; + //NOTE TO SELF: Only only alliance leader can see pending guild alliance statuses - AddBackground( 0, 0, 520, 335, 0x242C ); - AddHtmlLocalized( 20, 15, 480, 26, 1062975, 0x0, false, false ); //
Guild Relationship
- AddImageTiled( 20, 40, 480, 2, 0x2711 ); - AddHtmlLocalized( 20, 50, 120, 26, 1062954, 0x0, true, false ); // Guild Name - AddHtml( 150, 53, 360, 26, m_Other.Name, false, false ); + bool PendingWar = war != null; + bool ActiveWar = activeWar != null; + AddPage(0); - AddHtmlLocalized( 20, 80, 120, 26, 1063025, 0x0, true, false ); // Alliance + AddBackground(0, 0, 520, 335, 0x242C); + AddHtmlLocalized(20, 15, 480, 26, 1062975, 0x0, false, + false); //
Guild Relationship
+ AddImageTiled(20, 40, 480, 2, 0x2711); + AddHtmlLocalized(20, 50, 120, 26, 1062954, 0x0, true, false); // Guild Name + AddHtml(150, 53, 360, 26, m_Other.Name, false, false); - if ( otherAlliance != null ) - { - if ( otherAlliance.IsMember( m_Other )) - { - AddHtml( 150, 83, 360, 26, otherAlliance.Name, false, false ); - } - //else if ( otherAlliance.Leader == guild && ( otherAlliance.IsPendingMember( m_Other ) || otherAlliance.IsPendingMember( guild ) ) ) - /* else if ( (otherAlliance.Leader == guild && otherAlliance.IsPendingMember( m_Other ) ) || ( otherAlliance.Leader == m_Other && otherAlliance.IsPendingMember( guild ) ) ) - { - AddHtml( 150, 83, 360, 26, Color( alliance.Name, 0xF), false, false ); - } - //AddHtml( 150, 83, 360, 26, ( alliance.PendingMembers.Contains( guild ) || alliance.PendingMembers.Contains( m_Other ) ) ? String.Format( "{0}", alliance.Name ) : alliance.Name, false, false ); - //AddHtml( 150, 83, 360, 26, ( otherAlliance == alliance && otherAlliance.PendingMembers.Contains( guild ) || otherAlliance.PendingMembers.Contains( m_Other ) ) ? String.Format( "{0}", otherAlliance.Name ) : otherAlliance.Name, false, false ); - */ - } + AddHtmlLocalized(20, 80, 120, 26, 1063025, 0x0, true, false); // Alliance - AddHtmlLocalized( 20, 110, 120, 26, 1063139, 0x0, true, false ); // Abbreviation - AddHtml( 150, 113, 120, 26, m_Other.Abbreviation, false, false ); + if (otherAlliance != null) + if (otherAlliance.IsMember(m_Other)) + AddHtml(150, 83, 360, 26, otherAlliance.Name, false, false); + + AddHtmlLocalized(20, 110, 120, 26, 1063139, 0x0, true, false); // Abbreviation + AddHtml(150, 113, 120, 26, m_Other.Abbreviation, false, false); - string kills = "0/0"; - string time = "00:00"; - string otherKills = "0/0"; + string kills = "0/0"; + string time = "00:00"; + string otherKills = "0/0"; - WarDeclaration otherWar; + WarDeclaration otherWar; - if ( ActiveWar ) - { - kills = $"{activeWar.Kills}/{activeWar.MaxKills}"; + if (ActiveWar) + { + kills = $"{activeWar.Kills}/{activeWar.MaxKills}"; - TimeSpan timeRemaining = TimeSpan.Zero; + TimeSpan timeRemaining = TimeSpan.Zero; - if ( activeWar.WarLength != TimeSpan.Zero && (activeWar.WarBeginning + activeWar.WarLength) > DateTime.UtcNow ) - timeRemaining = (activeWar.WarBeginning + activeWar.WarLength) - DateTime.UtcNow; + if (activeWar.WarLength != TimeSpan.Zero && activeWar.WarBeginning + activeWar.WarLength > DateTime.UtcNow) + timeRemaining = activeWar.WarBeginning + activeWar.WarLength - DateTime.UtcNow; - //time = String.Format( "{0:D2}:{1:D2}", timeRemaining.Hours.ToString(), timeRemaining.Subtract( TimeSpan.FromHours( timeRemaining.Hours ) ).Minutes ); //Is there a formatter for htis? it's 2AM and I'm tired and can't find it - time = $"{timeRemaining.Hours:D2}:{DateTime.MinValue + timeRemaining:mm}"; + //time = String.Format( "{0:D2}:{1:D2}", timeRemaining.Hours.ToString(), timeRemaining.Subtract( TimeSpan.FromHours( timeRemaining.Hours ) ).Minutes ); //Is there a formatter for htis? it's 2AM and I'm tired and can't find it + time = $"{timeRemaining.Hours:D2}:{DateTime.MinValue + timeRemaining:mm}"; - otherWar = m_Other.FindActiveWar( guild ); - if ( otherWar != null ) - otherKills = $"{otherWar.Kills}/{otherWar.MaxKills}"; - } - else if ( PendingWar ) - { - kills = Color($"{war.Kills}/{war.MaxKills}", 0x990000 ); - //time = Color( String.Format( "{0}:{1}", war.WarLength.Hours, ((TimeSpan)(war.WarLength - TimeSpan.FromHours( war.WarLength.Hours ))).Minutes ), 0xFF0000 ); - time = Color($"{war.WarLength.Hours:D2}:{DateTime.MinValue + war.WarLength:mm}", 0x990000 ); + otherWar = m_Other.FindActiveWar(guild); + if (otherWar != null) + otherKills = $"{otherWar.Kills}/{otherWar.MaxKills}"; + } + else if (PendingWar) + { + kills = Color($"{war.Kills}/{war.MaxKills}", 0x990000); + //time = Color( String.Format( "{0}:{1}", war.WarLength.Hours, ((TimeSpan)(war.WarLength - TimeSpan.FromHours( war.WarLength.Hours ))).Minutes ), 0xFF0000 ); + time = Color($"{war.WarLength.Hours:D2}:{DateTime.MinValue + war.WarLength:mm}", 0x990000); - otherWar = m_Other.FindPendingWar( guild ); - if ( otherWar != null ) - otherKills = Color($"{otherWar.Kills}/{otherWar.MaxKills}", 0x990000 ); - } + otherWar = m_Other.FindPendingWar(guild); + if (otherWar != null) + otherKills = Color($"{otherWar.Kills}/{otherWar.MaxKills}", 0x990000); + } - AddHtmlLocalized( 280, 110, 120, 26, 1062966, 0x0, true, false ); // Your Kills - AddHtml( 410, 113, 120, 26, kills , false, false ); + AddHtmlLocalized(280, 110, 120, 26, 1062966, 0x0, true, false); // Your Kills + AddHtml(410, 113, 120, 26, kills, false, false); - AddHtmlLocalized( 20, 140, 120, 26, 1062968, 0x0, true, false ); // Time Remaining - AddHtml( 150, 143, 120, 26, time, false, false ); + AddHtmlLocalized(20, 140, 120, 26, 1062968, 0x0, true, false); // Time Remaining + AddHtml(150, 143, 120, 26, time, false, false); - AddHtmlLocalized( 280, 140, 120, 26, 1062967, 0x0, true, false ); // Their Kills - AddHtml( 410, 143, 120, 26, otherKills, false, false ); + AddHtmlLocalized(280, 140, 120, 26, 1062967, 0x0, true, false); // Their Kills + AddHtml(410, 143, 120, 26, otherKills, false, false); - AddImageTiled( 20, 172, 480, 2, 0x2711 ); + AddImageTiled(20, 172, 480, 2, 0x2711); - int number = 1062973;//
You are at peace with this guild.
+ int number = 1062973; //
You are at peace with this guild.
- if ( PendingWar ) - { - if ( war.WarRequester ) - { - number = 1063027; //
You have challenged this guild to war!
- } - else - { - number = 1062969; //
This guild has challenged you to war!
+ if (PendingWar) + { + if (war.WarRequester) + { + number = 1063027; //
You have challenged this guild to war!
+ } + else + { + number = 1062969; //
This guild has challenged you to war!
- AddButtonAndBackground( 20, 260, 5, 1062981 ); // Accept Challenge - AddButtonAndBackground( 275, 260, 6, 1062983 ); //Modify Terms - } + AddButtonAndBackground(20, 260, 5, 1062981); // Accept Challenge + AddButtonAndBackground(275, 260, 6, 1062983); //Modify Terms + } - AddButtonAndBackground( 20, 290, 7, 1062982 ); // Dismiss Challenge - } - else if ( ActiveWar ) - { - number = 1062965; //
You are at war with this guild!
- AddButtonAndBackground( 20, 290, 8, 1062980 ); // Surrender - } - else if ( alliance != null && alliance == otherAlliance ) //alliance, Same Alliance - { - if ( alliance.IsMember( guild ) && alliance.IsMember( m_Other ) ) //Both in Same alliance, full members - { - number = 1062970; //
You are allied with this guild.
+ AddButtonAndBackground(20, 290, 7, 1062982); // Dismiss Challenge + } + else if (ActiveWar) + { + number = 1062965; //
You are at war with this guild!
+ AddButtonAndBackground(20, 290, 8, 1062980); // Surrender + } + else if (alliance != null && alliance == otherAlliance) //alliance, Same Alliance + { + if (alliance.IsMember(guild) && alliance.IsMember(m_Other)) //Both in Same alliance, full members + { + number = 1062970; //
You are allied with this guild.
- if ( alliance.Leader == guild ) - { - AddButtonAndBackground( 20, 260, 12, 1062984 ); // Remove Guild from Alliance - AddButtonAndBackground( 275, 260, 13, 1063433 ); // Promote to Alliance Leader //Note: No 'confirmation' like the other leader guild promotion things - //Remove guild from alliance //Promote to Alliance Leader - } + if (alliance.Leader == guild) + { + AddButtonAndBackground(20, 260, 12, 1062984); // Remove Guild from Alliance + AddButtonAndBackground(275, 260, 13, + 1063433); // Promote to Alliance Leader //Note: No 'confirmation' like the other leader guild promotion things + //Remove guild from alliance //Promote to Alliance Leader + } - //Show roster, Centered, up - AddButtonAndBackground( 148, 215, 10, 1063164 ); //Show Alliance Roster - //Leave Alliance - AddButtonAndBackground( 20, 290, 11, 1062985 ); // Leave Alliance - } - else if ( alliance.Leader == guild && alliance.IsPendingMember( m_Other ) ) - { - number = 1062971; //
You have requested an alliance with this guild.
+ //Show roster, Centered, up + AddButtonAndBackground(148, 215, 10, 1063164); //Show Alliance Roster + //Leave Alliance + AddButtonAndBackground(20, 290, 11, 1062985); // Leave Alliance + } + else if (alliance.Leader == guild && alliance.IsPendingMember(m_Other)) + { + number = 1062971; //
You have requested an alliance with this guild.
- //Show Alliance Roster, Centered, down. - AddButtonAndBackground( 148, 245, 10, 1063164 ); //Show Alliance Roster - //Withdraw Request - AddButtonAndBackground( 20, 290, 14, 1062986 ); // Withdraw Request + //Show Alliance Roster, Centered, down. + AddButtonAndBackground(148, 245, 10, 1063164); //Show Alliance Roster + //Withdraw Request + AddButtonAndBackground(20, 290, 14, 1062986); // Withdraw Request - AddHtml( 150, 83, 360, 26, Color( alliance.Name, 0x99 ), false, false ); - } - else if ( alliance.Leader == m_Other && alliance.IsPendingMember( guild ) ) - { - number = 1062972; //
This guild has requested an alliance.
+ AddHtml(150, 83, 360, 26, Color(alliance.Name, 0x99), false, false); + } + else if (alliance.Leader == m_Other && alliance.IsPendingMember(guild)) + { + number = 1062972; //
This guild has requested an alliance.
- //Show alliance Roster, top - AddButtonAndBackground( 148, 215, 10, 1063164 ); //Show Alliance Roster - //Deny Request - //Accept Request - AddButtonAndBackground( 20, 260, 15, 1062988 ); // Deny Request - AddButtonAndBackground( 20, 290, 16, 1062987 ); // Accept Request + //Show alliance Roster, top + AddButtonAndBackground(148, 215, 10, 1063164); //Show Alliance Roster + //Deny Request + //Accept Request + AddButtonAndBackground(20, 260, 15, 1062988); // Deny Request + AddButtonAndBackground(20, 290, 16, 1062987); // Accept Request - AddHtml( 150, 83, 360, 26, Color( alliance.Name, 0x99 ), false, false ); - } - } - else - { - AddButtonAndBackground( 20, 260, 2, 1062990 ); // Request Alliance - AddButtonAndBackground( 20, 290, 1, 1062989 ); // Declare War! - } + AddHtml(150, 83, 360, 26, Color(alliance.Name, 0x99), false, false); + } + } + else + { + AddButtonAndBackground(20, 260, 2, 1062990); // Request Alliance + AddButtonAndBackground(20, 290, 1, 1062989); // Declare War! + } - AddButtonAndBackground( 275, 290, 0, 3000091 ); //Cancel + AddButtonAndBackground(275, 290, 0, 3000091); //Cancel - AddHtmlLocalized( 20, 180, 480, 30, number, 0x0, true, false ); - AddImageTiled( 20, 245, 480, 2, 0x2711 ); - } + AddHtmlLocalized(20, 180, 480, 30, number, 0x0, true, false); + AddImageTiled(20, 245, 480, 2, 0x2711); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - PlayerMobile pm = sender.Mobile as PlayerMobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + PlayerMobile pm = sender.Mobile as PlayerMobile; - if ( !IsMember( pm, guild ) ) - return; + if (!IsMember(pm, guild)) + return; - RankDefinition playerRank = pm.GuildRank; + RankDefinition playerRank = pm.GuildRank; - Guild guildLeader = Guild.GetAllianceLeader( guild ); - Guild otherGuild = Guild.GetAllianceLeader( m_Other ); + Guild guildLeader = Guild.GetAllianceLeader(guild); + Guild otherGuild = Guild.GetAllianceLeader(m_Other); - WarDeclaration war = guildLeader.FindPendingWar( otherGuild ); - WarDeclaration activeWar = guildLeader.FindActiveWar( otherGuild ); - WarDeclaration otherWar = otherGuild.FindPendingWar( guildLeader ); + WarDeclaration war = guildLeader.FindPendingWar(otherGuild); + WarDeclaration activeWar = guildLeader.FindActiveWar(otherGuild); + WarDeclaration otherWar = otherGuild.FindPendingWar(guildLeader); - AllianceInfo alliance = guild.Alliance; - AllianceInfo otherAlliance = otherGuild.Alliance; + AllianceInfo alliance = guild.Alliance; + AllianceInfo otherAlliance = otherGuild.Alliance; - switch( info.ButtonID ) - { - #region War - case 5: //Accept the war - { - if ( war != null && !war.WarRequester && activeWar == null ) - { - if ( !playerRank.GetFlag( RankFlags.ControlWarStatus ) ) - { - pm.SendLocalizedMessage( 1063440 ); // You don't have permission to negotiate wars. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, alliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else - { - //Accept the war - guild.PendingWars.Remove( war ); - war.WarBeginning = DateTime.UtcNow; - guild.AcceptedWars.Add( war ); + switch (info.ButtonID) + { + #region War - if ( alliance != null && alliance.IsMember( guild ) ) - { - alliance.AllianceMessage( 1070769, ((otherAlliance != null) ? otherAlliance.Name : otherGuild.Name) ); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ - alliance.InvalidateMemberProperties(); - } - else - { - guild.GuildMessage( 1070769, ((otherAlliance != null) ? otherAlliance.Name : otherGuild.Name) ); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ - guild.InvalidateMemberProperties(); - } - //Technically SHOULD say Your guild is now at war w/out any info, intentional diff. + case 5: //Accept the war + { + if (war != null && !war.WarRequester && activeWar == null) + { + if (!playerRank.GetFlag(RankFlags.ControlWarStatus)) + { + pm.SendLocalizedMessage(1063440); // You don't have permission to negotiate wars. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, + alliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else + { + //Accept the war + guild.PendingWars.Remove(war); + war.WarBeginning = DateTime.UtcNow; + guild.AcceptedWars.Add(war); - otherGuild.PendingWars.Remove( otherWar ); - otherWar.WarBeginning = DateTime.UtcNow; - otherGuild.AcceptedWars.Add( otherWar ); + if (alliance != null && alliance.IsMember(guild)) + { + alliance.AllianceMessage(1070769, + otherAlliance != null + ? otherAlliance.Name + : otherGuild.Name); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ + alliance.InvalidateMemberProperties(); + } + else + { + guild.GuildMessage(1070769, + otherAlliance != null + ? otherAlliance.Name + : otherGuild.Name); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ + guild.InvalidateMemberProperties(); + } + //Technically SHOULD say Your guild is now at war w/out any info, intentional diff. - if ( otherAlliance != null && m_Other.Alliance.IsMember( m_Other ) ) - { - otherAlliance.AllianceMessage( 1070769, ((alliance != null) ? alliance.Name : guild.Name) ); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ - otherAlliance.InvalidateMemberProperties(); - } - else - { - otherGuild.GuildMessage( 1070769, ((alliance != null) ? alliance.Name : guild.Name) ); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ - otherGuild.InvalidateMemberProperties(); - } - } - } + otherGuild.PendingWars.Remove(otherWar); + otherWar.WarBeginning = DateTime.UtcNow; + otherGuild.AcceptedWars.Add(otherWar); - break; - } - case 6: //Modify war terms - { - if ( war != null && !war.WarRequester && activeWar == null ) - { - if ( !playerRank.GetFlag( RankFlags.ControlWarStatus ) ) - { - pm.SendLocalizedMessage( 1063440 ); // You don't have permission to negotiate wars. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, alliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else - { - pm.SendGump( new WarDeclarationGump( pm, guild, otherGuild ) ); - } - } - break; - } - case 7: //Dismiss war - { - if ( war != null ) - { - if ( !playerRank.GetFlag( RankFlags.ControlWarStatus ) ) - { - pm.SendLocalizedMessage( 1063440 ); // You don't have permission to negotiate wars. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, alliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else - { - //Dismiss the war - guild.PendingWars.Remove( war ); - otherGuild.PendingWars.Remove( otherWar ); - pm.SendLocalizedMessage( 1070752 ); // The proposal has been updated. - //Messages to opposing guild? (Testing on OSI says no) - } - } - break; - } - case 8: //Surrender - { - if ( !playerRank.GetFlag( RankFlags.ControlWarStatus ) ) - { - pm.SendLocalizedMessage( 1063440 ); // You don't have permission to negotiate wars. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, alliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else - { - if ( activeWar != null ) - { - if ( alliance != null && alliance.IsMember( guild ) ) - { - alliance.AllianceMessage( 1070740, ((otherAlliance != null) ? otherAlliance.Name : otherGuild.Name) );// You have lost the war with ~1_val~. - alliance.InvalidateMemberProperties(); - } - else - { - guild.GuildMessage( 1070740, ((otherAlliance != null) ? otherAlliance.Name : otherGuild.Name) );// You have lost the war with ~1_val~. - guild.InvalidateMemberProperties(); - } + if (otherAlliance != null && m_Other.Alliance.IsMember(m_Other)) + { + otherAlliance.AllianceMessage(1070769, + alliance != null + ? alliance.Name + : guild.Name); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ + otherAlliance.InvalidateMemberProperties(); + } + else + { + otherGuild.GuildMessage(1070769, + alliance != null + ? alliance.Name + : guild.Name); // Guild Message: Your guild is now at war with ~1_GUILDNAME~ + otherGuild.InvalidateMemberProperties(); + } + } + } - guild.AcceptedWars.Remove( activeWar ); + break; + } + case 6: //Modify war terms + { + if (war != null && !war.WarRequester && activeWar == null) + { + if (!playerRank.GetFlag(RankFlags.ControlWarStatus)) + { + pm.SendLocalizedMessage(1063440); // You don't have permission to negotiate wars. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, + alliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else + { + pm.SendGump(new WarDeclarationGump(pm, guild, otherGuild)); + } + } - if ( otherAlliance != null && otherAlliance.IsMember( otherGuild ) ) - { - otherAlliance.AllianceMessage( 1070739, ((guild.Alliance != null) ? guild.Alliance.Name : guild.Name) );// You have won the war against ~1_val~! - otherAlliance.InvalidateMemberProperties(); - } - else - { - otherGuild.GuildMessage( 1070739, ((guild.Alliance != null) ? guild.Alliance.Name : guild.Name) );// You have won the war against ~1_val~! - otherGuild.InvalidateMemberProperties(); - } + break; + } + case 7: //Dismiss war + { + if (war != null) + { + if (!playerRank.GetFlag(RankFlags.ControlWarStatus)) + { + pm.SendLocalizedMessage(1063440); // You don't have permission to negotiate wars. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, + alliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else + { + //Dismiss the war + guild.PendingWars.Remove(war); + otherGuild.PendingWars.Remove(otherWar); + pm.SendLocalizedMessage(1070752); // The proposal has been updated. + //Messages to opposing guild? (Testing on OSI says no) + } + } - otherGuild.AcceptedWars.Remove( otherGuild.FindActiveWar( guild ) ); - } - } - break; - } - case 1: //Declare War - { - if ( war == null && activeWar == null ) - { - if ( !playerRank.GetFlag( RankFlags.ControlWarStatus ) ) - { - pm.SendLocalizedMessage( 1063440 ); // You don't have permission to negotiate wars. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, alliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else if ( otherAlliance != null && otherAlliance.Leader != m_Other ) - { - pm.SendLocalizedMessage( 1063239, $"{m_Other.Name}\t{otherAlliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, otherAlliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else - { - pm.SendGump( new WarDeclarationGump( pm, guild, m_Other ) ); - } - } - break; - } - #endregion - case 2: //Request Alliance - { - #region New alliance - if ( alliance == null ) - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1070747 ); // You don't have permission to create an alliance. - } - else if ( Faction.Find( guild.Leader ) != Faction.Find( m_Other.Leader ) ) - { - pm.SendLocalizedMessage( 1070758 ); // You cannot propose an alliance to a guild with a different faction allegiance. - } - else if ( otherAlliance != null ) - { - if ( otherAlliance.IsPendingMember( m_Other ) ) - pm.SendLocalizedMessage( 1063416, m_Other.Name ); // ~1_val~ is currently considering another alliance proposal. - else - pm.SendLocalizedMessage( 1063426, m_Other.Name ); // ~1_val~ already belongs to an alliance. - } - else if ( m_Other.AcceptedWars.Count > 0 || m_Other.PendingWars.Count > 0 ) - { - pm.SendLocalizedMessage( 1063427, m_Other.Name ); // ~1_val~ is currently involved in a guild war. - } - else if ( guild.AcceptedWars.Count > 0 || guild.PendingWars.Count > 0 ) - { - pm.SendLocalizedMessage( 1063427, guild.Name ); // ~1_val~ is currently involved in a guild war. - } - else - { - pm.SendLocalizedMessage( 1063439 ); // Enter a name for the new alliance: - pm.BeginPrompt( CreateAlliance_Callback ); - } - } - #endregion - #region Existing Alliance - else - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - } - else if ( otherAlliance != null ) - { - if ( otherAlliance.IsPendingMember( m_Other ) ) - pm.SendLocalizedMessage( 1063416, m_Other.Name ); // ~1_val~ is currently considering another alliance proposal. - else - pm.SendLocalizedMessage( 1063426, m_Other.Name ); // ~1_val~ already belongs to an alliance. - } - else if ( alliance.IsPendingMember( guild ) ) - { - pm.SendLocalizedMessage( 1063416, guild.Name ); // ~1_val~ is currently considering another alliance proposal. - } - else if ( m_Other.AcceptedWars.Count > 0 || m_Other.PendingWars.Count > 0 ) - { - pm.SendLocalizedMessage( 1063427, m_Other.Name ); // ~1_val~ is currently involved in a guild war. - } - else if ( guild.AcceptedWars.Count > 0 || guild.PendingWars.Count > 0 ) - { - pm.SendLocalizedMessage( 1063427, guild.Name ); // ~1_val~ is currently involved in a guild war. - } - else if ( Faction.Find( guild.Leader ) != Faction.Find( m_Other.Leader ) ) - { - pm.SendLocalizedMessage( 1070758 ); // You cannot propose an alliance to a guild with a different faction allegiance. - } - else - { - pm.SendLocalizedMessage( 1070750, m_Other.Name ); // An invitation to join your alliance has been sent to ~1_val~. + break; + } + case 8: //Surrender + { + if (!playerRank.GetFlag(RankFlags.ControlWarStatus)) + { + pm.SendLocalizedMessage(1063440); // You don't have permission to negotiate wars. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, alliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else + { + if (activeWar != null) + { + if (alliance != null && alliance.IsMember(guild)) + { + alliance.AllianceMessage(1070740, + otherAlliance != null + ? otherAlliance.Name + : otherGuild.Name); // You have lost the war with ~1_val~. + alliance.InvalidateMemberProperties(); + } + else + { + guild.GuildMessage(1070740, + otherAlliance != null + ? otherAlliance.Name + : otherGuild.Name); // You have lost the war with ~1_val~. + guild.InvalidateMemberProperties(); + } - m_Other.GuildMessage( 1070780, guild.Name ); // ~1_val~ has proposed an alliance. + guild.AcceptedWars.Remove(activeWar); - m_Other.Alliance = alliance; //Calls addPendingGuild - //alliance.AddPendingGuild( m_Other ); - } - } - #endregion - break; - } - case 10: //Show Alliance Roster - { - if ( alliance != null && alliance == otherAlliance ) - pm.SendGump( new AllianceInfo.AllianceRosterGump( pm, guild, alliance ) ); + if (otherAlliance != null && otherAlliance.IsMember(otherGuild)) + { + otherAlliance.AllianceMessage(1070739, + guild.Alliance != null + ? guild.Alliance.Name + : guild.Name); // You have won the war against ~1_val~! + otherAlliance.InvalidateMemberProperties(); + } + else + { + otherGuild.GuildMessage(1070739, + guild.Alliance != null + ? guild.Alliance.Name + : guild.Name); // You have won the war against ~1_val~! + otherGuild.InvalidateMemberProperties(); + } - break; - } - case 11: //Leave Alliance - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( alliance != null && alliance.IsMember( guild ) ) - { - guild.Alliance = null; //Calls alliance.Removeguild + otherGuild.AcceptedWars.Remove(otherGuild.FindActiveWar(guild)); + } + } + + break; + } + case 1: //Declare War + { + if (war == null && activeWar == null) + { + if (!playerRank.GetFlag(RankFlags.ControlWarStatus)) + { + pm.SendLocalizedMessage(1063440); // You don't have permission to negotiate wars. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, + alliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else if (otherAlliance != null && otherAlliance.Leader != m_Other) + { + pm.SendLocalizedMessage(1063239, + $"{m_Other.Name}\t{otherAlliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, + otherAlliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else + { + pm.SendGump(new WarDeclarationGump(pm, guild, m_Other)); + } + } + + break; + } + + #endregion + + case 2: //Request Alliance + { + #region New alliance + + if (alliance == null) + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1070747); // You don't have permission to create an alliance. + } + else if (Faction.Find(guild.Leader) != Faction.Find(m_Other.Leader)) + { + pm.SendLocalizedMessage( + 1070758); // You cannot propose an alliance to a guild with a different faction allegiance. + } + else if (otherAlliance != null) + { + if (otherAlliance.IsPendingMember(m_Other)) + pm.SendLocalizedMessage(1063416, + m_Other.Name); // ~1_val~ is currently considering another alliance proposal. + else + pm.SendLocalizedMessage(1063426, m_Other.Name); // ~1_val~ already belongs to an alliance. + } + else if (m_Other.AcceptedWars.Count > 0 || m_Other.PendingWars.Count > 0) + { + pm.SendLocalizedMessage(1063427, m_Other.Name); // ~1_val~ is currently involved in a guild war. + } + else if (guild.AcceptedWars.Count > 0 || guild.PendingWars.Count > 0) + { + pm.SendLocalizedMessage(1063427, guild.Name); // ~1_val~ is currently involved in a guild war. + } + else + { + pm.SendLocalizedMessage(1063439); // Enter a name for the new alliance: + pm.BeginPrompt(CreateAlliance_Callback); + } + } + + #endregion + + #region Existing Alliance + + else + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + } + else if (otherAlliance != null) + { + if (otherAlliance.IsPendingMember(m_Other)) + pm.SendLocalizedMessage(1063416, + m_Other.Name); // ~1_val~ is currently considering another alliance proposal. + else + pm.SendLocalizedMessage(1063426, m_Other.Name); // ~1_val~ already belongs to an alliance. + } + else if (alliance.IsPendingMember(guild)) + { + pm.SendLocalizedMessage(1063416, + guild.Name); // ~1_val~ is currently considering another alliance proposal. + } + else if (m_Other.AcceptedWars.Count > 0 || m_Other.PendingWars.Count > 0) + { + pm.SendLocalizedMessage(1063427, m_Other.Name); // ~1_val~ is currently involved in a guild war. + } + else if (guild.AcceptedWars.Count > 0 || guild.PendingWars.Count > 0) + { + pm.SendLocalizedMessage(1063427, guild.Name); // ~1_val~ is currently involved in a guild war. + } + else if (Faction.Find(guild.Leader) != Faction.Find(m_Other.Leader)) + { + pm.SendLocalizedMessage( + 1070758); // You cannot propose an alliance to a guild with a different faction allegiance. + } + else + { + pm.SendLocalizedMessage(1070750, + m_Other.Name); // An invitation to join your alliance has been sent to ~1_val~. + + m_Other.GuildMessage(1070780, guild.Name); // ~1_val~ has proposed an alliance. + + m_Other.Alliance = alliance; //Calls addPendingGuild + //alliance.AddPendingGuild( m_Other ); + } + } + + #endregion + + break; + } + case 10: //Show Alliance Roster + { + if (alliance != null && alliance == otherAlliance) + pm.SendGump(new AllianceInfo.AllianceRosterGump(pm, guild, alliance)); + + break; + } + case 11: //Leave Alliance + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (alliance != null && alliance.IsMember(guild)) + { + guild.Alliance = null; //Calls alliance.Removeguild // alliance.RemoveGuild( guild ); - m_Other.InvalidateWarNotoriety(); + m_Other.InvalidateWarNotoriety(); - guild.InvalidateMemberNotoriety(); - } - break; - } - case 12: //Remove Guild from alliance - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - } - else if ( alliance != null && alliance.IsMember( guild ) && alliance.IsMember( m_Other ) ) - { - m_Other.Alliance = null; + guild.InvalidateMemberNotoriety(); + } - m_Other.InvalidateMemberNotoriety(); + break; + } + case 12: //Remove Guild from alliance + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + } + else if (alliance != null && alliance.IsMember(guild) && alliance.IsMember(m_Other)) + { + m_Other.Alliance = null; - guild.InvalidateWarNotoriety(); - } - break; - } - case 13: //Promote to Alliance leader - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - } - else if ( alliance != null && alliance.IsMember( guild ) && alliance.IsMember( m_Other ) ) - { - pm.SendLocalizedMessage( 1063434, $"{m_Other.Name}\t{alliance.Name}"); // ~1_val~ is now the leader of ~2_val~. + m_Other.InvalidateMemberNotoriety(); - alliance.Leader = m_Other; - } - break; - } - case 14: //Withdraw Request - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( alliance != null && alliance.Leader == guild && alliance.IsPendingMember( m_Other ) ) - { - m_Other.Alliance = null; - pm.SendLocalizedMessage( 1070752 ); // The proposal has been updated. - } - break; - } - case 15: //Deny Alliance Request - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( alliance != null && otherAlliance != null && alliance.Leader == m_Other && otherAlliance.IsPendingMember( guild ) ) - { - pm.SendLocalizedMessage( 1070752 ); // The proposal has been updated. - //m_Other.GuildMessage( 1070782 ); // ~1_val~ has responded to your proposal. //Per OSI commented out. + guild.InvalidateWarNotoriety(); + } - guild.Alliance = null; - } - break; - } - case 16: //Accept Alliance Request - { - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1063436 ); // You don't have permission to negotiate an alliance. - } - else if ( otherAlliance != null && otherAlliance.Leader == m_Other && otherAlliance.IsPendingMember( guild ) ) - { - pm.SendLocalizedMessage( 1070752 ); // The proposal has been updated. + break; + } + case 13: //Promote to Alliance leader + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + } + else if (alliance != null && alliance.IsMember(guild) && alliance.IsMember(m_Other)) + { + pm.SendLocalizedMessage(1063434, + $"{m_Other.Name}\t{alliance.Name}"); // ~1_val~ is now the leader of ~2_val~. - otherAlliance.TurnToMember( m_Other ); //No need to verify it's in the guild or already a member, the function does this + alliance.Leader = m_Other; + } - otherAlliance.TurnToMember( guild ); - } - break; - } - } - } + break; + } + case 14: //Withdraw Request + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (alliance != null && alliance.Leader == guild && alliance.IsPendingMember(m_Other)) + { + m_Other.Alliance = null; + pm.SendLocalizedMessage(1070752); // The proposal has been updated. + } - public void CreateAlliance_Callback( Mobile from, string text ) - { - PlayerMobile pm = from as PlayerMobile; + break; + } + case 15: //Deny Alliance Request + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (alliance != null && otherAlliance != null && alliance.Leader == m_Other && + otherAlliance.IsPendingMember(guild)) + { + pm.SendLocalizedMessage(1070752); // The proposal has been updated. + //m_Other.GuildMessage( 1070782 ); // ~1_val~ has responded to your proposal. //Per OSI commented out. + + guild.Alliance = null; + } + + break; + } + case 16: //Accept Alliance Request + { + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1063436); // You don't have permission to negotiate an alliance. + } + else if (otherAlliance != null && otherAlliance.Leader == m_Other && + otherAlliance.IsPendingMember(guild)) + { + pm.SendLocalizedMessage(1070752); // The proposal has been updated. + + otherAlliance + .TurnToMember( + m_Other); //No need to verify it's in the guild or already a member, the function does this + + otherAlliance.TurnToMember(guild); + } + + break; + } + } + } + + public void CreateAlliance_Callback(Mobile from, string text) + { + PlayerMobile pm = from as PlayerMobile; - AllianceInfo alliance = guild.Alliance; - AllianceInfo otherAlliance = m_Other.Alliance; + AllianceInfo alliance = guild.Alliance; + AllianceInfo otherAlliance = m_Other.Alliance; - if ( !IsMember( from, guild ) || alliance != null ) - return; + if (!IsMember(from, guild) || alliance != null) + return; - RankDefinition playerRank = pm.GuildRank; + RankDefinition playerRank = pm.GuildRank; - if ( !playerRank.GetFlag( RankFlags.AllianceControl ) ) - { - pm.SendLocalizedMessage( 1070747 ); // You don't have permission to create an alliance. - } - else if ( Faction.Find( guild.Leader ) != Faction.Find( m_Other.Leader ) ) - { - //Notes about this: OSI only cares/checks when proposing, you can change your faction all you want later. - pm.SendLocalizedMessage( 1070758 ); // You cannot propose an alliance to a guild with a different faction allegiance. - } - else if ( otherAlliance != null ) - { - if ( otherAlliance.IsPendingMember( m_Other ) ) - pm.SendLocalizedMessage( 1063416, m_Other.Name ); // ~1_val~ is currently considering another alliance proposal. - else - pm.SendLocalizedMessage( 1063426, m_Other.Name ); // ~1_val~ already belongs to an alliance. - } - else if ( m_Other.AcceptedWars.Count > 0 || m_Other.PendingWars.Count > 0 ) - { - pm.SendLocalizedMessage( 1063427, m_Other.Name ); // ~1_val~ is currently involved in a guild war. - } - else if ( guild.AcceptedWars.Count > 0 || guild.PendingWars.Count > 0 ) - { - pm.SendLocalizedMessage( 1063427, guild.Name ); // ~1_val~ is currently involved in a guild war. - } - else - { - string name = Utility.FixHtml( text.Trim() ); + if (!playerRank.GetFlag(RankFlags.AllianceControl)) + { + pm.SendLocalizedMessage(1070747); // You don't have permission to create an alliance. + } + else if (Faction.Find(guild.Leader) != Faction.Find(m_Other.Leader)) + { + //Notes about this: OSI only cares/checks when proposing, you can change your faction all you want later. + pm.SendLocalizedMessage( + 1070758); // You cannot propose an alliance to a guild with a different faction allegiance. + } + else if (otherAlliance != null) + { + if (otherAlliance.IsPendingMember(m_Other)) + pm.SendLocalizedMessage(1063416, + m_Other.Name); // ~1_val~ is currently considering another alliance proposal. + else + pm.SendLocalizedMessage(1063426, m_Other.Name); // ~1_val~ already belongs to an alliance. + } + else if (m_Other.AcceptedWars.Count > 0 || m_Other.PendingWars.Count > 0) + { + pm.SendLocalizedMessage(1063427, m_Other.Name); // ~1_val~ is currently involved in a guild war. + } + else if (guild.AcceptedWars.Count > 0 || guild.PendingWars.Count > 0) + { + pm.SendLocalizedMessage(1063427, guild.Name); // ~1_val~ is currently involved in a guild war. + } + else + { + string name = Utility.FixHtml(text.Trim()); - if ( !CheckProfanity( name ) ) - pm.SendLocalizedMessage( 1070886 ); // That alliance name is not allowed. - else if ( name.Length > Guild.NameLimit ) - pm.SendLocalizedMessage( 1070887, Guild.NameLimit.ToString() ); // An alliance name cannot exceed ~1_val~ characters in length. - else if ( AllianceInfo.Alliances.ContainsKey( name.ToLower() ) ) - pm.SendLocalizedMessage( 1063428 ); // That alliance name is not available. - else - { - pm.SendLocalizedMessage( 1070750, m_Other.Name ); // An invitation to join your alliance has been sent to ~1_val~. + if (!CheckProfanity(name)) + { + pm.SendLocalizedMessage(1070886); // That alliance name is not allowed. + } + else if (name.Length > Guild.NameLimit) + { + pm.SendLocalizedMessage(1070887, + Guild.NameLimit.ToString()); // An alliance name cannot exceed ~1_val~ characters in length. + } + else if (AllianceInfo.Alliances.ContainsKey(name.ToLower())) + { + pm.SendLocalizedMessage(1063428); // That alliance name is not available. + } + else + { + pm.SendLocalizedMessage(1070750, + m_Other.Name); // An invitation to join your alliance has been sent to ~1_val~. - m_Other.GuildMessage( 1070780, guild.Name ); // ~1_val~ has proposed an alliance. + m_Other.GuildMessage(1070780, guild.Name); // ~1_val~ has proposed an alliance. - new AllianceInfo( guild, name, m_Other ); - } - } - } - } -} + new AllianceInfo(guild, name, m_Other); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/New Guild System/War Declaration gump.cs b/Scripts/Gumps/Guilds/New Guild System/War Declaration gump.cs index e7f3df781..7ed859a53 100644 --- a/Scripts/Gumps/Guilds/New Guild System/War Declaration gump.cs +++ b/Scripts/Gumps/Guilds/New Guild System/War Declaration gump.cs @@ -1,129 +1,140 @@ using System; using Server.Gumps; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Guilds { - public class WarDeclarationGump : BaseGuildGump - { - private Guild m_Other; + public class WarDeclarationGump : BaseGuildGump + { + private Guild m_Other; - public WarDeclarationGump( PlayerMobile pm, Guild g, Guild otherGuild ) : base( pm, g ) - { - m_Other = otherGuild; - WarDeclaration war = g.FindPendingWar( otherGuild ); + public WarDeclarationGump(PlayerMobile pm, Guild g, Guild otherGuild) : base(pm, g) + { + m_Other = otherGuild; + WarDeclaration war = g.FindPendingWar(otherGuild); - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 500, 340, 0x24AE ); - AddBackground( 65, 50, 370, 30, 0x2486 ); - AddHtmlLocalized( 75, 55, 370, 26, 1062979, 0x3C00, false, false ); //
Declaration of War
- AddImage( 410, 45, 0x232C ); - AddHtmlLocalized( 65, 95, 200, 20, 1063009, 0x14AF, false, false ); // Duration of War - AddHtmlLocalized( 65, 120, 400, 20, 1063010, 0x0, false, false ); // Enter the number of hours the war will last. - AddBackground( 65, 150, 40, 30, 0x2486 ); - AddTextEntry( 70, 154, 50, 30, 0x481, 10, (war != null) ? war.WarLength.Hours.ToString() : "0" ); - AddHtmlLocalized( 65, 195, 200, 20, 1063011, 0x14AF, false, false ); // Victory Condition - AddHtmlLocalized( 65, 220, 400, 20, 1063012, 0x0, false, false ); // Enter the winning number of kills. - AddBackground( 65, 250, 40, 30, 0x2486 ); - AddTextEntry( 70, 254, 50, 30, 0x481, 11, (war != null) ? war.MaxKills.ToString() : "0" ); - AddBackground( 190, 270, 130, 26, 0x2486 ); - AddButton( 195, 275, 0x845, 0x846, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 220, 273, 90, 26, 1006045, 0x0, false, false ); // Cancel - AddBackground( 330, 270, 130, 26, 0x2486 ); - AddButton( 335, 275, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 360, 273, 90, 26, 1062989, 0x5000, false, false ); // Declare War! - } + AddBackground(0, 0, 500, 340, 0x24AE); + AddBackground(65, 50, 370, 30, 0x2486); + AddHtmlLocalized(75, 55, 370, 26, 1062979, 0x3C00, false, + false); //
Declaration of War
+ AddImage(410, 45, 0x232C); + AddHtmlLocalized(65, 95, 200, 20, 1063009, 0x14AF, false, false); // Duration of War + AddHtmlLocalized(65, 120, 400, 20, 1063010, 0x0, false, false); // Enter the number of hours the war will last. + AddBackground(65, 150, 40, 30, 0x2486); + AddTextEntry(70, 154, 50, 30, 0x481, 10, war != null ? war.WarLength.Hours.ToString() : "0"); + AddHtmlLocalized(65, 195, 200, 20, 1063011, 0x14AF, false, false); // Victory Condition + AddHtmlLocalized(65, 220, 400, 20, 1063012, 0x0, false, false); // Enter the winning number of kills. + AddBackground(65, 250, 40, 30, 0x2486); + AddTextEntry(70, 254, 50, 30, 0x481, 11, war != null ? war.MaxKills.ToString() : "0"); + AddBackground(190, 270, 130, 26, 0x2486); + AddButton(195, 275, 0x845, 0x846, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(220, 273, 90, 26, 1006045, 0x0, false, false); // Cancel + AddBackground(330, 270, 130, 26, 0x2486); + AddButton(335, 275, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(360, 273, 90, 26, 1062989, 0x5000, false, false); // Declare War! + } - public override void OnResponse( NetState sender, RelayInfo info ) - { + public override void OnResponse(NetState sender, RelayInfo info) + { + PlayerMobile pm = sender.Mobile as PlayerMobile; - PlayerMobile pm = sender.Mobile as PlayerMobile; + if (!IsMember(pm, guild)) + return; - if ( !IsMember( pm, guild ) ) - return; + RankDefinition playerRank = pm.GuildRank; - RankDefinition playerRank = pm.GuildRank; + switch (info.ButtonID) + { + case 1: + { + AllianceInfo alliance = guild.Alliance; + AllianceInfo otherAlliance = m_Other.Alliance; - switch( info.ButtonID ) - { - case 1: - { - AllianceInfo alliance = guild.Alliance; - AllianceInfo otherAlliance = m_Other.Alliance; + if (!playerRank.GetFlag(RankFlags.ControlWarStatus)) + { + pm.SendLocalizedMessage(1063440); // You don't have permission to negotiate wars. + } + else if (alliance != null && alliance.Leader != guild) + { + pm.SendLocalizedMessage(1063239, + $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, alliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else if (otherAlliance != null && otherAlliance.Leader != m_Other) + { + pm.SendLocalizedMessage(1063239, + $"{m_Other.Name}\t{otherAlliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. + pm.SendLocalizedMessage(1070707, + otherAlliance.Leader.Name); // You need to negotiate via ~1_val~ instead. + } + else + { + WarDeclaration activeWar = guild.FindActiveWar(m_Other); - if ( !playerRank.GetFlag( RankFlags.ControlWarStatus ) ) - { - pm.SendLocalizedMessage( 1063440 ); // You don't have permission to negotiate wars. - } - else if ( alliance != null && alliance.Leader != guild ) - { - pm.SendLocalizedMessage( 1063239, $"{guild.Name}\t{alliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, alliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else if ( otherAlliance != null && otherAlliance.Leader != m_Other ) - { - pm.SendLocalizedMessage( 1063239, $"{m_Other.Name}\t{otherAlliance.Name}"); // ~1_val~ is not the leader of the ~2_val~ alliance. - pm.SendLocalizedMessage( 1070707, otherAlliance.Leader.Name ); // You need to negotiate via ~1_val~ instead. - } - else - { - WarDeclaration activeWar = guild.FindActiveWar( m_Other ); + if (activeWar == null) + { + WarDeclaration war = guild.FindPendingWar(m_Other); + WarDeclaration otherWar = m_Other.FindPendingWar(guild); - if ( activeWar == null ) - { - WarDeclaration war = guild.FindPendingWar( m_Other ); - WarDeclaration otherWar = m_Other.FindPendingWar( guild ); + //Note: OSI differs from what it says on website. unlimited war = 0 kills/ 0 hrs. Not > 999. (sidenote: they both cap at 65535, 7.5 years, but, still.) + TextRelay tKills = info.GetTextEntry(11); + TextRelay tWarLength = info.GetTextEntry(10); - //Note: OSI differs from what it says on website. unlimited war = 0 kills/ 0 hrs. Not > 999. (sidenote: they both cap at 65535, 7.5 years, but, still.) - TextRelay tKills = info.GetTextEntry( 11 ); - TextRelay tWarLength = info.GetTextEntry( 10 ); + int maxKills = tKills == null + ? 0 + : Math.Max(Math.Min(Utility.ToInt32(info.GetTextEntry(11).Text), 0xFFFF), 0); + TimeSpan warLength = TimeSpan.FromHours(tWarLength == null + ? 0 + : Math.Max(Math.Min(Utility.ToInt32(info.GetTextEntry(10).Text), 0xFFFF), 0)); - int maxKills = (tKills == null)? 0 : Math.Max( Math.Min( Utility.ToInt32( info.GetTextEntry( 11 ).Text ), 0xFFFF ), 0 ); - TimeSpan warLength = TimeSpan.FromHours( (tWarLength == null) ? 0 : Math.Max( Math.Min( Utility.ToInt32( info.GetTextEntry( 10 ).Text ), 0xFFFF ), 0 ) ); + if (war != null) + { + war.MaxKills = maxKills; + war.WarLength = warLength; + war.WarRequester = true; + } + else + { + guild.PendingWars.Add(new WarDeclaration(guild, m_Other, maxKills, warLength, true)); + } - if ( war != null ) - { - war.MaxKills = maxKills; - war.WarLength = warLength; - war.WarRequester = true; - } - else - { - guild.PendingWars.Add( new WarDeclaration( guild, m_Other, maxKills, warLength, true ) ); - } + if (otherWar != null) + { + otherWar.MaxKills = maxKills; + otherWar.WarLength = warLength; + otherWar.WarRequester = false; + } + else + { + m_Other.PendingWars.Add(new WarDeclaration(m_Other, guild, maxKills, warLength, false)); + } - if ( otherWar != null ) - { - otherWar.MaxKills = maxKills; - otherWar.WarLength = warLength; - otherWar.WarRequester = false; - } - else - { - m_Other.PendingWars.Add( new WarDeclaration( m_Other, guild, maxKills, warLength, false ) ); - } + if (war != null) + pm.SendLocalizedMessage(1070752); // The proposal has been updated. + else + m_Other.GuildMessage(1070781, + guild.Alliance != null + ? guild.Alliance.Name + : guild.Name); // ~1_val~ has proposed a war. - if ( war != null ) - { - pm.SendLocalizedMessage( 1070752 ); // The proposal has been updated. - //m_Other.GuildMessage( 1070782 ); // ~1_val~ has responded to your proposal. - } - else - m_Other.GuildMessage( 1070781, ((guild.Alliance != null ) ? guild.Alliance.Name : guild.Name ) ); // ~1_val~ has proposed a war. + pm.SendLocalizedMessage(1070751, + m_Other.Alliance != null + ? m_Other.Alliance.Name + : m_Other.Name); // War proposal has been sent to ~1_val~. + } + } - pm.SendLocalizedMessage( 1070751, ((m_Other.Alliance != null ) ? m_Other.Alliance.Name : m_Other.Name ) ); // War proposal has been sent to ~1_val~. - } - } - break; - } - default: - { - pm.SendGump( new OtherGuildInfo( pm, guild, m_Other ) ); - break; - } - } - } - } -} + break; + } + default: + { + pm.SendGump(new OtherGuildInfo(pm, guild, m_Other)); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Guilds/RecruitTarget.cs b/Scripts/Gumps/Guilds/RecruitTarget.cs index 5cb3ded63..be878c9e7 100644 --- a/Scripts/Gumps/Guilds/RecruitTarget.cs +++ b/Scripts/Gumps/Guilds/RecruitTarget.cs @@ -1,91 +1,97 @@ +using Server.Factions; using Server.Guilds; using Server.Targeting; -using Server.Factions; namespace Server.Gumps { - public class GuildRecruitTarget : Target - { - private Mobile m_Mobile; - private Guild m_Guild; + public class GuildRecruitTarget : Target + { + private Guild m_Guild; + private Mobile m_Mobile; - public GuildRecruitTarget( Mobile m, Guild guild ) : base( 10, false, TargetFlags.None ) - { - m_Mobile = m; - m_Guild = guild; - } + public GuildRecruitTarget(Mobile m, Guild guild) : base(10, false, TargetFlags.None) + { + m_Mobile = m; + m_Guild = guild; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; - if ( targeted is Mobile m ) - { - PlayerState guildState = PlayerState.Find( m_Guild.Leader ); - PlayerState targetState = PlayerState.Find( m ); + if (targeted is Mobile m) + { + PlayerState guildState = PlayerState.Find(m_Guild.Leader); + PlayerState targetState = PlayerState.Find(m); - Faction guildFaction = guildState?.Faction; - Faction targetFaction = targetState?.Faction; + Faction guildFaction = guildState?.Faction; + Faction targetFaction = targetState?.Faction; - if ( !m.Player ) - { - m_Mobile.SendLocalizedMessage( 501161 ); // You may only recruit players into the guild. - } - else if ( !m.Alive ) - { - m_Mobile.SendLocalizedMessage( 501162 ); // Only the living may be recruited. - } - else if ( m_Guild.IsMember( m ) ) - { - m_Mobile.SendLocalizedMessage( 501163 ); // They are already a guildmember! - } - else if ( m_Guild.Candidates.Contains( m ) ) - { - m_Mobile.SendLocalizedMessage( 501164 ); // They are already a candidate. - } - else if ( m_Guild.Accepted.Contains( m ) ) - { - m_Mobile.SendLocalizedMessage( 501165 ); // They have already been accepted for membership, and merely need to use the Guildstone to gain full membership. - } - else if ( m.Guild != null ) - { - m_Mobile.SendLocalizedMessage( 501166 ); // You can only recruit candidates who are not already in a guild. - } - #region Factions - else if ( guildFaction != targetFaction ) - { - if ( guildFaction == null ) - m_Mobile.SendLocalizedMessage( 1013027 ); // That player cannot join a non-faction guild. - else if ( targetFaction == null ) - m_Mobile.SendLocalizedMessage( 1013026 ); // That player must be in a faction before joining this guild. - else - m_Mobile.SendLocalizedMessage( 1013028 ); // That person has a different faction affiliation. - } - else if ( targetState != null && targetState.IsLeaving ) - { - // OSI does this quite strangely, so we'll just do it this way - m_Mobile.SendMessage( "That person is quitting their faction and so you may not recruit them." ); - } - #endregion - else if ( m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Guild.Leader == m_Mobile ) - { - m_Guild.Accepted.Add( m ); - } - else - { - m_Guild.Candidates.Add( m ); - } - } - } + if (!m.Player) + { + m_Mobile.SendLocalizedMessage(501161); // You may only recruit players into the guild. + } + else if (!m.Alive) + { + m_Mobile.SendLocalizedMessage(501162); // Only the living may be recruited. + } + else if (m_Guild.IsMember(m)) + { + m_Mobile.SendLocalizedMessage(501163); // They are already a guildmember! + } + else if (m_Guild.Candidates.Contains(m)) + { + m_Mobile.SendLocalizedMessage(501164); // They are already a candidate. + } + else if (m_Guild.Accepted.Contains(m)) + { + m_Mobile.SendLocalizedMessage( + 501165); // They have already been accepted for membership, and merely need to use the Guildstone to gain full membership. + } + else if (m.Guild != null) + { + m_Mobile.SendLocalizedMessage(501166); // You can only recruit candidates who are not already in a guild. + } - protected override void OnTargetFinish( Mobile from ) - { - if ( GuildGump.BadMember( m_Mobile, m_Guild ) ) - return; + #region Factions - GuildGump.EnsureClosed( m_Mobile ); - m_Mobile.SendGump( new GuildGump( m_Mobile, m_Guild ) ); - } - } -} + else if (guildFaction != targetFaction) + { + if (guildFaction == null) + m_Mobile.SendLocalizedMessage(1013027); // That player cannot join a non-faction guild. + else if (targetFaction == null) + m_Mobile.SendLocalizedMessage( + 1013026); // That player must be in a faction before joining this guild. + else + m_Mobile.SendLocalizedMessage(1013028); // That person has a different faction affiliation. + } + else if (targetState != null && targetState.IsLeaving) + { + // OSI does this quite strangely, so we'll just do it this way + m_Mobile.SendMessage("That person is quitting their faction and so you may not recruit them."); + } + + #endregion + + else if (m_Mobile.AccessLevel >= AccessLevel.GameMaster || m_Guild.Leader == m_Mobile) + { + m_Guild.Accepted.Add(m); + } + else + { + m_Guild.Candidates.Add(m); + } + } + } + + protected override void OnTargetFinish(Mobile from) + { + if (GuildGump.BadMember(m_Mobile, m_Guild)) + return; + + GuildGump.EnsureClosed(m_Mobile); + m_Mobile.SendGump(new GuildGump(m_Mobile, m_Guild)); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/HeritageTokenGump.cs b/Scripts/Gumps/HeritageTokenGump.cs index 73a1f9ab4..5f731b4d9 100644 --- a/Scripts/Gumps/HeritageTokenGump.cs +++ b/Scripts/Gumps/HeritageTokenGump.cs @@ -5,384 +5,574 @@ using Server.Network; namespace Server.Gumps { - public class HeritageTokenGump : Gump - { - private HeritageToken m_Token; + public class HeritageTokenGump : Gump + { + private HeritageToken m_Token; - public HeritageTokenGump( HeritageToken token ) : base( 60, 36 ) - { - m_Token = token; + public HeritageTokenGump(HeritageToken token) : base(60, 36) + { + m_Token = token; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 520, 404, 0x13BE ); - AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 324, 0xA40 ); - AddImageTiled( 10, 374, 500, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 500, 384 ); - AddButton( 10, 374, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 376, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 500, 20, 1075576, 0x7FFF, false, false ); // Choose your item from the following pages + AddBackground(0, 0, 520, 404, 0x13BE); + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 324, 0xA40); + AddImageTiled(10, 374, 500, 20, 0xA40); + AddAlphaRegion(10, 10, 500, 384); + AddButton(10, 374, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 376, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 500, 20, 1075576, 0x7FFF, false, false); // Choose your item from the following pages - AddPage( 1 ); + AddPage(1); - AddImageTiledButton( 14, 44, 0x918, 0x919, 0x64, GumpButtonType.Reply, 0, 0x1411, 0x2C, 18, 8 ); - AddTooltip( 1062912 ); - AddHtmlLocalized( 98, 44, 250, 60, 1078147, 0x7FFF, false, false ); // Royal Leggings of Embers - AddImageTiledButton( 264, 44, 0x918, 0x919, 0x65, GumpButtonType.Reply, 0, 0x234D, 0x0, 18, 12 ); - AddTooltip( 1062914 ); - AddHtmlLocalized( 348, 44, 250, 60, 1062913, 0x7FFF, false, false ); // Rose of Trinsic - AddImageTiledButton( 14, 108, 0x918, 0x919, 0x66, GumpButtonType.Reply, 0, 0x26C3, 0x504, 18, 8 ); - AddTooltip( 1062916 ); - AddHtmlLocalized( 98, 108, 250, 60, 1062915, 0x7FFF, false, false ); // Shamino’s Best Crossbow - AddImageTiledButton( 264, 108, 0x918, 0x919, 0x67, GumpButtonType.Reply, 0, 0x3F1D, 0x0, 18, 8 ); - AddTooltip( 1062918 ); - AddHtmlLocalized( 348, 108, 250, 60, 1062917, 0x7FFF, false, false ); // The Tapestry of Sosaria - AddImageTiledButton( 14, 172, 0x918, 0x919, 0x68, GumpButtonType.Reply, 0, 0x3F14, 0x0, 18, 8 ); - AddTooltip( 1062920 ); - AddHtmlLocalized( 98, 172, 250, 60, 1062919, 0x7FFF, false, false ); // Hearth of the Home Fire - AddImageTiledButton( 264, 172, 0x918, 0x919, 0x69, GumpButtonType.Reply, 0, 0xF60, 0x482, -1, 10 ); - AddTooltip( 1062922 ); - AddHtmlLocalized( 348, 172, 250, 60, 1062921, 0x7FFF, false, false ); // The Holy Sword - AddImageTiledButton( 14, 236, 0x918, 0x919, 0x6A, GumpButtonType.Reply, 0, 0x236C, 0x0, 18, 6 ); - AddTooltip( 1062924 ); - AddHtmlLocalized( 98, 236, 250, 60, 1062923, 0x7FFF, false, false ); // Ancient Samurai Helm - AddImageTiledButton( 264, 236, 0x918, 0x919, 0x6B, GumpButtonType.Reply, 0, 0x2B10, 0x226, 18, 11 ); - AddTooltip( 1075223 ); - AddHtmlLocalized( 348, 236, 250, 60, 1075188, 0x7FFF, false, false ); // Helm of Spirituality - AddImageTiledButton( 14, 300, 0x918, 0x919, 0x6C, GumpButtonType.Reply, 0, 0x2B0C, 0x226, 18, 15 ); - AddTooltip( 1075224 ); - AddHtmlLocalized( 98, 300, 250, 60, 1075192, 0x7FFF, false, false ); // Gauntlets of Valor - AddImageTiledButton( 264, 300, 0x918, 0x919, 0x6D, GumpButtonType.Reply, 0, 0x2B01, 0x0, 18, 9 ); - AddTooltip( 1075225 ); - AddHtmlLocalized( 348, 300, 250, 60, 1075196, 0x7FFF, false, false ); // Dupre’s Shield - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 2 ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next + AddImageTiledButton(14, 44, 0x918, 0x919, 0x64, GumpButtonType.Reply, 0, 0x1411, 0x2C, 18, 8); + AddTooltip(1062912); + AddHtmlLocalized(98, 44, 250, 60, 1078147, 0x7FFF, false, false); // Royal Leggings of Embers + AddImageTiledButton(264, 44, 0x918, 0x919, 0x65, GumpButtonType.Reply, 0, 0x234D, 0x0, 18, 12); + AddTooltip(1062914); + AddHtmlLocalized(348, 44, 250, 60, 1062913, 0x7FFF, false, false); // Rose of Trinsic + AddImageTiledButton(14, 108, 0x918, 0x919, 0x66, GumpButtonType.Reply, 0, 0x26C3, 0x504, 18, 8); + AddTooltip(1062916); + AddHtmlLocalized(98, 108, 250, 60, 1062915, 0x7FFF, false, false); // Shamino’s Best Crossbow + AddImageTiledButton(264, 108, 0x918, 0x919, 0x67, GumpButtonType.Reply, 0, 0x3F1D, 0x0, 18, 8); + AddTooltip(1062918); + AddHtmlLocalized(348, 108, 250, 60, 1062917, 0x7FFF, false, false); // The Tapestry of Sosaria + AddImageTiledButton(14, 172, 0x918, 0x919, 0x68, GumpButtonType.Reply, 0, 0x3F14, 0x0, 18, 8); + AddTooltip(1062920); + AddHtmlLocalized(98, 172, 250, 60, 1062919, 0x7FFF, false, false); // Hearth of the Home Fire + AddImageTiledButton(264, 172, 0x918, 0x919, 0x69, GumpButtonType.Reply, 0, 0xF60, 0x482, -1, 10); + AddTooltip(1062922); + AddHtmlLocalized(348, 172, 250, 60, 1062921, 0x7FFF, false, false); // The Holy Sword + AddImageTiledButton(14, 236, 0x918, 0x919, 0x6A, GumpButtonType.Reply, 0, 0x236C, 0x0, 18, 6); + AddTooltip(1062924); + AddHtmlLocalized(98, 236, 250, 60, 1062923, 0x7FFF, false, false); // Ancient Samurai Helm + AddImageTiledButton(264, 236, 0x918, 0x919, 0x6B, GumpButtonType.Reply, 0, 0x2B10, 0x226, 18, 11); + AddTooltip(1075223); + AddHtmlLocalized(348, 236, 250, 60, 1075188, 0x7FFF, false, false); // Helm of Spirituality + AddImageTiledButton(14, 300, 0x918, 0x919, 0x6C, GumpButtonType.Reply, 0, 0x2B0C, 0x226, 18, 15); + AddTooltip(1075224); + AddHtmlLocalized(98, 300, 250, 60, 1075192, 0x7FFF, false, false); // Gauntlets of Valor + AddImageTiledButton(264, 300, 0x918, 0x919, 0x6D, GumpButtonType.Reply, 0, 0x2B01, 0x0, 18, 9); + AddTooltip(1075225); + AddHtmlLocalized(348, 300, 250, 60, 1075196, 0x7FFF, false, false); // Dupre’s Shield + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 2); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - AddPage( 2 ); + AddPage(2); - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - AddImageTiledButton( 14, 44, 0x918, 0x919, 0x6E, GumpButtonType.Reply, 0, 0x2AC6, 0x0, 29, 0 ); - AddTooltip( 1075226 ); - AddHtmlLocalized( 98, 44, 250, 60, 1075197, 0x7FFF, false, false ); // Fountain of Life - AddImageTiledButton( 264, 44, 0x918, 0x919, 0x6F, GumpButtonType.Reply, 0, 0x2AF9, 0x0, -4, -5 ); - AddTooltip( 1075227 ); - AddHtmlLocalized( 348, 44, 250, 60, 1075198, 0x7FFF, false, false ); // Dawn’s Music Box - AddImageTiledButton( 14, 108, 0x918, 0x919, 0x70, GumpButtonType.Reply, 0, 0x2253, 0x0, 18, 12 ); - AddTooltip( 1075228 ); - AddHtmlLocalized( 98, 108, 250, 60, 1078148, 0x7FFF, false, false ); // Ossian Grimoire - AddImageTiledButton( 264, 108, 0x918, 0x919, 0x71, GumpButtonType.Reply, 0, 0x2D98, 0x0, 19, 13 ); - AddTooltip( 1078527 ); - AddHtmlLocalized( 348, 108, 250, 60, 1078142, 0x7FFF, false, false ); // Talisman of the Fey:
Ferret - AddImageTiledButton( 14, 172, 0x918, 0x919, 0x72, GumpButtonType.Reply, 0, 0x2D97, 0x0, 19, 13 ); - AddTooltip( 1078528 ); - AddHtmlLocalized( 98, 172, 250, 60, 1078143, 0x7FFF, false, false ); // Talisman of the Fey:
Squirrel - AddImageTiledButton( 264, 172, 0x918, 0x919, 0x73, GumpButtonType.Reply, 0, 0x2D96, 0x0, 19, 8 ); - AddTooltip( 1078529 ); - AddHtmlLocalized( 348, 172, 250, 60, 1078144, 0x7FFF, false, false ); // Talisman of the Fey:
Cu Sidhe - AddImageTiledButton( 14, 236, 0x918, 0x919, 0x74, GumpButtonType.Reply, 0, 0x2D95, 0x0, -4, 2 ); - AddTooltip( 1078530 ); - AddHtmlLocalized( 98, 236, 250, 60, 1078145, 0x7FFF, false, false ); // Talisman of the Fey:
Reptalon - AddImageTiledButton( 264, 236, 0x918, 0x919, 0x75, GumpButtonType.Reply, 0, 0x2B02, 0x0, -2, 9 ); - AddTooltip( 1078526 ); - AddHtmlLocalized( 348, 236, 250, 60, 1075201, 0x7FFF, false, false ); // Quiver of Infinity - AddImageTiledButton( 14, 300, 0x918, 0x919, 0x76, GumpButtonType.Reply, 0, 0x2A91, 0x0, 25, 5 ); - AddTooltip( 1075986 ); - AddHtmlLocalized( 98, 300, 250, 60, 1074797, 0x7FFF, false, false ); // Bone Throne, Bone Couch
and Bone Table - AddImageTiledButton( 264, 300, 0x918, 0x919, 0x77, GumpButtonType.Reply, 0, 0x2A99, 0x0, 18, 1 ); - AddTooltip( 1075987 ); - AddHtmlLocalized( 348, 300, 250, 60, 1078146, 0x7FFF, false, false ); // Creepy Portraits - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 3 ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + AddImageTiledButton(14, 44, 0x918, 0x919, 0x6E, GumpButtonType.Reply, 0, 0x2AC6, 0x0, 29, 0); + AddTooltip(1075226); + AddHtmlLocalized(98, 44, 250, 60, 1075197, 0x7FFF, false, false); // Fountain of Life + AddImageTiledButton(264, 44, 0x918, 0x919, 0x6F, GumpButtonType.Reply, 0, 0x2AF9, 0x0, -4, -5); + AddTooltip(1075227); + AddHtmlLocalized(348, 44, 250, 60, 1075198, 0x7FFF, false, false); // Dawn’s Music Box + AddImageTiledButton(14, 108, 0x918, 0x919, 0x70, GumpButtonType.Reply, 0, 0x2253, 0x0, 18, 12); + AddTooltip(1075228); + AddHtmlLocalized(98, 108, 250, 60, 1078148, 0x7FFF, false, false); // Ossian Grimoire + AddImageTiledButton(264, 108, 0x918, 0x919, 0x71, GumpButtonType.Reply, 0, 0x2D98, 0x0, 19, 13); + AddTooltip(1078527); + AddHtmlLocalized(348, 108, 250, 60, 1078142, 0x7FFF, false, false); // Talisman of the Fey:
Ferret + AddImageTiledButton(14, 172, 0x918, 0x919, 0x72, GumpButtonType.Reply, 0, 0x2D97, 0x0, 19, 13); + AddTooltip(1078528); + AddHtmlLocalized(98, 172, 250, 60, 1078143, 0x7FFF, false, false); // Talisman of the Fey:
Squirrel + AddImageTiledButton(264, 172, 0x918, 0x919, 0x73, GumpButtonType.Reply, 0, 0x2D96, 0x0, 19, 8); + AddTooltip(1078529); + AddHtmlLocalized(348, 172, 250, 60, 1078144, 0x7FFF, false, false); // Talisman of the Fey:
Cu Sidhe + AddImageTiledButton(14, 236, 0x918, 0x919, 0x74, GumpButtonType.Reply, 0, 0x2D95, 0x0, -4, 2); + AddTooltip(1078530); + AddHtmlLocalized(98, 236, 250, 60, 1078145, 0x7FFF, false, false); // Talisman of the Fey:
Reptalon + AddImageTiledButton(264, 236, 0x918, 0x919, 0x75, GumpButtonType.Reply, 0, 0x2B02, 0x0, -2, 9); + AddTooltip(1078526); + AddHtmlLocalized(348, 236, 250, 60, 1075201, 0x7FFF, false, false); // Quiver of Infinity + AddImageTiledButton(14, 300, 0x918, 0x919, 0x76, GumpButtonType.Reply, 0, 0x2A91, 0x0, 25, 5); + AddTooltip(1075986); + AddHtmlLocalized(98, 300, 250, 60, 1074797, 0x7FFF, false, false); // Bone Throne, Bone Couch
and Bone Table + AddImageTiledButton(264, 300, 0x918, 0x919, 0x77, GumpButtonType.Reply, 0, 0x2A99, 0x0, 18, 1); + AddTooltip(1075987); + AddHtmlLocalized(348, 300, 250, 60, 1078146, 0x7FFF, false, false); // Creepy Portraits + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 3); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - AddPage( 3 ); + AddPage(3); - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 2 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - AddImageTiledButton( 14, 44, 0x918, 0x919, 0x78, GumpButtonType.Reply, 0, 0x2A71, 0x0, 13, 5 ); - AddTooltip( 1075988 ); - AddHtmlLocalized( 98, 44, 250, 60, 1074799, 0x7FFF, false, false ); // Mounted Pixies (5) - AddImageTiledButton( 264, 44, 0x918, 0x919, 0x79, GumpButtonType.Reply, 0, 0x2A98, 0x0, 26, 1 ); - AddTooltip( 1075990 ); - AddHtmlLocalized( 348, 44, 250, 60, 1074800, 0x7FFF, false, false ); // Haunted Mirror - AddImageTiledButton( 14, 108, 0x918, 0x919, 0x7A, GumpButtonType.Reply, 0, 0x2A92, 0x0, 18, 1 ); - AddTooltip( 1075989 ); - AddHtmlLocalized( 98, 108, 250, 60, 1074801, 0x7FFF, false, false ); // Bed of Nails - AddImageTiledButton( 264, 108, 0x918, 0x919, 0x7B, GumpButtonType.Reply, 0, 0x2AB8, 0x0, 18, 1 ); - AddTooltip( 1075991 ); - AddHtmlLocalized( 348, 108, 250, 60, 1074818, 0x7FFF, false, false ); // Sacrificial Altar - AddImageTiledButton( 14, 172, 0x918, 0x919, 0x7C, GumpButtonType.Reply, 0, 0x3F26, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 98, 172, 250, 60, 1076257, 0x7FFF, false, false ); // Broken Covered Chair - AddImageTiledButton( 264, 172, 0x918, 0x919, 0x7D, GumpButtonType.Reply, 0, 0x3F22, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 348, 172, 250, 60, 1076258, 0x7FFF, false, false ); // Broken Bookcase - AddImageTiledButton( 14, 236, 0x918, 0x919, 0x7E, GumpButtonType.Reply, 0, 0x3F24, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 98, 236, 250, 60, 1076259, 0x7FFF, false, false ); // Standing Broken Chair - AddImageTiledButton( 264, 236, 0x918, 0x919, 0x7F, GumpButtonType.Reply, 0, 0x3F25, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 348, 236, 250, 60, 1076260, 0x7FFF, false, false ); // Broken Vanity - AddImageTiledButton( 14, 300, 0x918, 0x919, 0x80, GumpButtonType.Reply, 0, 0x3F23, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 98, 300, 250, 60, 1076261, 0x7FFF, false, false ); // Broken Chest of Drawers - AddImageTiledButton( 264, 300, 0x918, 0x919, 0x81, GumpButtonType.Reply, 0, 0x3F21, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 348, 300, 250, 60, 1076262, 0x7FFF, false, false ); // Broken Armoire - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 4 ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 2); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + AddImageTiledButton(14, 44, 0x918, 0x919, 0x78, GumpButtonType.Reply, 0, 0x2A71, 0x0, 13, 5); + AddTooltip(1075988); + AddHtmlLocalized(98, 44, 250, 60, 1074799, 0x7FFF, false, false); // Mounted Pixies (5) + AddImageTiledButton(264, 44, 0x918, 0x919, 0x79, GumpButtonType.Reply, 0, 0x2A98, 0x0, 26, 1); + AddTooltip(1075990); + AddHtmlLocalized(348, 44, 250, 60, 1074800, 0x7FFF, false, false); // Haunted Mirror + AddImageTiledButton(14, 108, 0x918, 0x919, 0x7A, GumpButtonType.Reply, 0, 0x2A92, 0x0, 18, 1); + AddTooltip(1075989); + AddHtmlLocalized(98, 108, 250, 60, 1074801, 0x7FFF, false, false); // Bed of Nails + AddImageTiledButton(264, 108, 0x918, 0x919, 0x7B, GumpButtonType.Reply, 0, 0x2AB8, 0x0, 18, 1); + AddTooltip(1075991); + AddHtmlLocalized(348, 108, 250, 60, 1074818, 0x7FFF, false, false); // Sacrificial Altar + AddImageTiledButton(14, 172, 0x918, 0x919, 0x7C, GumpButtonType.Reply, 0, 0x3F26, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(98, 172, 250, 60, 1076257, 0x7FFF, false, false); // Broken Covered Chair + AddImageTiledButton(264, 172, 0x918, 0x919, 0x7D, GumpButtonType.Reply, 0, 0x3F22, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(348, 172, 250, 60, 1076258, 0x7FFF, false, false); // Broken Bookcase + AddImageTiledButton(14, 236, 0x918, 0x919, 0x7E, GumpButtonType.Reply, 0, 0x3F24, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(98, 236, 250, 60, 1076259, 0x7FFF, false, false); // Standing Broken Chair + AddImageTiledButton(264, 236, 0x918, 0x919, 0x7F, GumpButtonType.Reply, 0, 0x3F25, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(348, 236, 250, 60, 1076260, 0x7FFF, false, false); // Broken Vanity + AddImageTiledButton(14, 300, 0x918, 0x919, 0x80, GumpButtonType.Reply, 0, 0x3F23, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(98, 300, 250, 60, 1076261, 0x7FFF, false, false); // Broken Chest of Drawers + AddImageTiledButton(264, 300, 0x918, 0x919, 0x81, GumpButtonType.Reply, 0, 0x3F21, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(348, 300, 250, 60, 1076262, 0x7FFF, false, false); // Broken Armoire + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 4); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - AddPage( 4 ); + AddPage(4); - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 3 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - AddImageTiledButton( 14, 44, 0x918, 0x919, 0x82, GumpButtonType.Reply, 0, 0x3F0B, 0x0, 18, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 98, 44, 250, 60, 1076263, 0x7FFF, false, false ); // Broken Bed - AddImageTiledButton( 264, 44, 0x918, 0x919, 0x83, GumpButtonType.Reply, 0, 0xC19, 0x0, 13, 8 ); - AddTooltip( 1076610 ); - AddHtmlLocalized( 348, 44, 250, 60, 1076264, 0x7FFF, false, false ); // Broken Fallen Chair - AddImageTiledButton( 14, 108, 0x918, 0x919, 0x84, GumpButtonType.Reply, 0, 0x3DAA, 0x0, 20, -3 ); - AddTooltip( 1076611 ); - AddHtmlLocalized( 98, 108, 250, 60, 1076265, 0x7FFF, false, false ); // Suit of Gold Armor - AddImageTiledButton( 264, 108, 0x918, 0x919, 0x85, GumpButtonType.Reply, 0, 0x151C, 0x0, -20, -3 ); - AddTooltip( 1076612 ); - AddHtmlLocalized( 348, 108, 250, 60, 1076266, 0x7FFF, false, false ); // Suit of Silver Armor - AddImageTiledButton( 14, 172, 0x918, 0x919, 0x86, GumpButtonType.Reply, 0, 0x3DB1, 0x0, 18, 8 ); - AddTooltip( 1076613 ); - AddHtmlLocalized( 98, 172, 250, 60, 1076267, 0x7FFF, false, false ); // Boiling Cauldron - AddImageTiledButton( 264, 172, 0x918, 0x919, 0x87, GumpButtonType.Reply, 0, 0x3F27, 0x0, 18, 8 ); - AddTooltip( 1076614 ); - AddHtmlLocalized( 348, 172, 250, 60, 1024656, 0x7FFF, false, false ); // Guillotine - AddImageTiledButton( 14, 236, 0x918, 0x919, 0x88, GumpButtonType.Reply, 0, 0x3F0C, 0x0, 18, 8 ); - AddTooltip( 1076615 ); - AddHtmlLocalized( 98, 236, 250, 60, 1076268, 0x7FFF, false, false ); // Cherry Blossom Tree - AddImageTiledButton( 264, 236, 0x918, 0x919, 0x89, GumpButtonType.Reply, 0, 0x3F07, 0x0, 18, 8 ); - AddTooltip( 1076616 ); - AddHtmlLocalized( 348, 236, 250, 60, 1076269, 0x7FFF, false, false ); // Apple Tree - AddImageTiledButton( 14, 300, 0x918, 0x919, 0x8A, GumpButtonType.Reply, 0, 0x3F16, 0x0, 18, 8 ); - AddTooltip( 1076617 ); - AddHtmlLocalized( 98, 300, 250, 60, 1076270, 0x7FFF, false, false ); // Peach Tree - AddImageTiledButton( 264, 300, 0x918, 0x919, 0x8B, GumpButtonType.Reply, 0, 0x3F12, 0x0, 18, 8 ); - AddTooltip( 1076618 ); - AddHtmlLocalized( 348, 300, 250, 60, 1076271, 0x7FFF, false, false ); // Hanging Axes - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 5 ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 3); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + AddImageTiledButton(14, 44, 0x918, 0x919, 0x82, GumpButtonType.Reply, 0, 0x3F0B, 0x0, 18, 8); + AddTooltip(1076610); + AddHtmlLocalized(98, 44, 250, 60, 1076263, 0x7FFF, false, false); // Broken Bed + AddImageTiledButton(264, 44, 0x918, 0x919, 0x83, GumpButtonType.Reply, 0, 0xC19, 0x0, 13, 8); + AddTooltip(1076610); + AddHtmlLocalized(348, 44, 250, 60, 1076264, 0x7FFF, false, false); // Broken Fallen Chair + AddImageTiledButton(14, 108, 0x918, 0x919, 0x84, GumpButtonType.Reply, 0, 0x3DAA, 0x0, 20, -3); + AddTooltip(1076611); + AddHtmlLocalized(98, 108, 250, 60, 1076265, 0x7FFF, false, false); // Suit of Gold Armor + AddImageTiledButton(264, 108, 0x918, 0x919, 0x85, GumpButtonType.Reply, 0, 0x151C, 0x0, -20, -3); + AddTooltip(1076612); + AddHtmlLocalized(348, 108, 250, 60, 1076266, 0x7FFF, false, false); // Suit of Silver Armor + AddImageTiledButton(14, 172, 0x918, 0x919, 0x86, GumpButtonType.Reply, 0, 0x3DB1, 0x0, 18, 8); + AddTooltip(1076613); + AddHtmlLocalized(98, 172, 250, 60, 1076267, 0x7FFF, false, false); // Boiling Cauldron + AddImageTiledButton(264, 172, 0x918, 0x919, 0x87, GumpButtonType.Reply, 0, 0x3F27, 0x0, 18, 8); + AddTooltip(1076614); + AddHtmlLocalized(348, 172, 250, 60, 1024656, 0x7FFF, false, false); // Guillotine + AddImageTiledButton(14, 236, 0x918, 0x919, 0x88, GumpButtonType.Reply, 0, 0x3F0C, 0x0, 18, 8); + AddTooltip(1076615); + AddHtmlLocalized(98, 236, 250, 60, 1076268, 0x7FFF, false, false); // Cherry Blossom Tree + AddImageTiledButton(264, 236, 0x918, 0x919, 0x89, GumpButtonType.Reply, 0, 0x3F07, 0x0, 18, 8); + AddTooltip(1076616); + AddHtmlLocalized(348, 236, 250, 60, 1076269, 0x7FFF, false, false); // Apple Tree + AddImageTiledButton(14, 300, 0x918, 0x919, 0x8A, GumpButtonType.Reply, 0, 0x3F16, 0x0, 18, 8); + AddTooltip(1076617); + AddHtmlLocalized(98, 300, 250, 60, 1076270, 0x7FFF, false, false); // Peach Tree + AddImageTiledButton(264, 300, 0x918, 0x919, 0x8B, GumpButtonType.Reply, 0, 0x3F12, 0x0, 18, 8); + AddTooltip(1076618); + AddHtmlLocalized(348, 300, 250, 60, 1076271, 0x7FFF, false, false); // Hanging Axes + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 5); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - AddPage( 5 ); + AddPage(5); - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 4 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - AddImageTiledButton( 14, 44, 0x918, 0x919, 0x8C, GumpButtonType.Reply, 0, 0x3F13, 0x0, 18, 8 ); - AddTooltip( 1076619 ); - AddHtmlLocalized( 98, 44, 250, 60, 1076272, 0x7FFF, false, false ); // Hanging Swords - AddImageTiledButton( 264, 44, 0x918, 0x919, 0x8D, GumpButtonType.Reply, 0, 0x3F09, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 348, 44, 250, 60, 1076273, 0x7FFF, false, false ); // Blue fancy rug - AddImageTiledButton( 14, 108, 0x918, 0x919, 0x8E, GumpButtonType.Reply, 0, 0x3F0E, 0x0, 18, 8 ); - AddTooltip( 1076621 ); - AddHtmlLocalized( 98, 108, 250, 60, 1076274, 0x7FFF, false, false ); // Coffin - AddImageTiledButton( 264, 108, 0x918, 0x919, 0x8F, GumpButtonType.Reply, 0, 0x3F1F, 0x0, 18, 8 ); - AddTooltip( 1076623 ); - AddHtmlLocalized( 348, 108, 250, 60, 1074027, 0x7FFF, false, false ); // Vanity - AddImageTiledButton( 14, 172, 0x918, 0x919, 0x90, GumpButtonType.Reply, 0, 0x118B, 0x0, -4, -9 ); - AddTooltip( 1076624 ); - AddHtmlLocalized( 98, 172, 250, 60, 1076635, 0x7FFF, false, false ); // Table With A Purple
Tablecloth - AddImageTiledButton( 264, 172, 0x918, 0x919, 0x91, GumpButtonType.Reply, 0, 0x118C, 0x0, -4, -9 ); - AddTooltip( 1076624 ); - AddHtmlLocalized( 348, 172, 250, 60, 1076636, 0x7FFF, false, false ); // Table With A Blue
Tablecloth - AddImageTiledButton( 14, 236, 0x918, 0x919, 0x92, GumpButtonType.Reply, 0, 0x118D, 0x0, -4, -9 ); - AddTooltip( 1076624 ); - AddHtmlLocalized( 98, 236, 250, 60, 1076637, 0x7FFF, false, false ); // Table With A Red
Tablecloth - AddImageTiledButton( 264, 236, 0x918, 0x919, 0x93, GumpButtonType.Reply, 0, 0x118E, 0x0, -4, -9 ); - AddTooltip( 1076624 ); - AddHtmlLocalized( 348, 236, 250, 60, 1076638, 0x7FFF, false, false ); // Table With An Orange
Tablecloth - AddImageTiledButton( 14, 300, 0x918, 0x919, 0x94, GumpButtonType.Reply, 0, 0x3F1E, 0x0, 18, 8 ); - AddTooltip( 1076625 ); - AddHtmlLocalized( 98, 300, 250, 60, 1076279, 0x7FFF, false, false ); // Unmade Bed - AddImageTiledButton( 264, 300, 0x918, 0x919, 0x95, GumpButtonType.Reply, 0, 0x3F0F, 0x0, 18, 8 ); - AddTooltip( 1076626 ); - AddHtmlLocalized( 348, 300, 250, 60, 1076280, 0x7FFF, false, false ); // Curtains - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 6 ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 4); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + AddImageTiledButton(14, 44, 0x918, 0x919, 0x8C, GumpButtonType.Reply, 0, 0x3F13, 0x0, 18, 8); + AddTooltip(1076619); + AddHtmlLocalized(98, 44, 250, 60, 1076272, 0x7FFF, false, false); // Hanging Swords + AddImageTiledButton(264, 44, 0x918, 0x919, 0x8D, GumpButtonType.Reply, 0, 0x3F09, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(348, 44, 250, 60, 1076273, 0x7FFF, false, false); // Blue fancy rug + AddImageTiledButton(14, 108, 0x918, 0x919, 0x8E, GumpButtonType.Reply, 0, 0x3F0E, 0x0, 18, 8); + AddTooltip(1076621); + AddHtmlLocalized(98, 108, 250, 60, 1076274, 0x7FFF, false, false); // Coffin + AddImageTiledButton(264, 108, 0x918, 0x919, 0x8F, GumpButtonType.Reply, 0, 0x3F1F, 0x0, 18, 8); + AddTooltip(1076623); + AddHtmlLocalized(348, 108, 250, 60, 1074027, 0x7FFF, false, false); // Vanity + AddImageTiledButton(14, 172, 0x918, 0x919, 0x90, GumpButtonType.Reply, 0, 0x118B, 0x0, -4, -9); + AddTooltip(1076624); + AddHtmlLocalized(98, 172, 250, 60, 1076635, 0x7FFF, false, false); // Table With A Purple
Tablecloth + AddImageTiledButton(264, 172, 0x918, 0x919, 0x91, GumpButtonType.Reply, 0, 0x118C, 0x0, -4, -9); + AddTooltip(1076624); + AddHtmlLocalized(348, 172, 250, 60, 1076636, 0x7FFF, false, false); // Table With A Blue
Tablecloth + AddImageTiledButton(14, 236, 0x918, 0x919, 0x92, GumpButtonType.Reply, 0, 0x118D, 0x0, -4, -9); + AddTooltip(1076624); + AddHtmlLocalized(98, 236, 250, 60, 1076637, 0x7FFF, false, false); // Table With A Red
Tablecloth + AddImageTiledButton(264, 236, 0x918, 0x919, 0x93, GumpButtonType.Reply, 0, 0x118E, 0x0, -4, -9); + AddTooltip(1076624); + AddHtmlLocalized(348, 236, 250, 60, 1076638, 0x7FFF, false, false); // Table With An Orange
Tablecloth + AddImageTiledButton(14, 300, 0x918, 0x919, 0x94, GumpButtonType.Reply, 0, 0x3F1E, 0x0, 18, 8); + AddTooltip(1076625); + AddHtmlLocalized(98, 300, 250, 60, 1076279, 0x7FFF, false, false); // Unmade Bed + AddImageTiledButton(264, 300, 0x918, 0x919, 0x95, GumpButtonType.Reply, 0, 0x3F0F, 0x0, 18, 8); + AddTooltip(1076626); + AddHtmlLocalized(348, 300, 250, 60, 1076280, 0x7FFF, false, false); // Curtains + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 6); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - AddPage( 6 ); + AddPage(6); - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 5 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - AddImageTiledButton( 14, 44, 0x918, 0x919, 0x96, GumpButtonType.Reply, 0, 0x1E34, 0x0, 18, -17 ); - AddTooltip( 1076627 ); - AddHtmlLocalized( 98, 44, 250, 60, 1076281, 0x7FFF, false, false ); // Scarecrow - AddImageTiledButton( 264, 44, 0x918, 0x919, 0x97, GumpButtonType.Reply, 0, 0xA0C, 0x0, 18, 8 ); - AddTooltip( 1076628 ); - AddHtmlLocalized( 348, 44, 250, 60, 1076282, 0x7FFF, false, false ); // Wall Torch - AddImageTiledButton( 14, 108, 0x918, 0x919, 0x98, GumpButtonType.Reply, 0, 0x3F10, 0x0, 18, 9 ); - AddTooltip( 1076629 ); - AddHtmlLocalized( 98, 108, 250, 60, 1076283, 0x7FFF, false, false ); // Fountain - AddImageTiledButton( 264, 108, 0x918, 0x919, 0x99, GumpButtonType.Reply, 0, 0x3F19, 0x0, 18, 8 ); - AddTooltip( 1076630 ); - AddHtmlLocalized( 348, 108, 250, 60, 1076284, 0x7FFF, false, false ); // Statue - AddImageTiledButton( 14, 172, 0x918, 0x919, 0x9A, GumpButtonType.Reply, 0, 0x1EA5, 0x0, 5, -25 ); - AddTooltip( 1076631 ); - AddHtmlLocalized( 98, 172, 250, 60, 1076285, 0x7FFF, false, false ); // Large Fish Net - AddImageTiledButton( 264, 172, 0x918, 0x919, 0x9B, GumpButtonType.Reply, 0, 0x1EA3, 0x0, 18, -27 ); - AddTooltip( 1076632 ); - AddHtmlLocalized( 348, 172, 250, 60, 1076286, 0x7FFF, false, false ); // Small Fish Net - AddImageTiledButton( 14, 236, 0x918, 0x919, 0x9C, GumpButtonType.Reply, 0, 0x2FDF, 0x0, 18, -36 ); - AddTooltip( 1076633 ); - AddHtmlLocalized( 98, 236, 250, 60, 1076287, 0x7FFF, false, false ); // Ladder - AddImageTiledButton( 264, 236, 0x918, 0x919, 0x9D, GumpButtonType.Reply, 0, 0x3F15, 0x0, 18, 8 ); - AddTooltip( 1076622 ); - AddHtmlLocalized( 348, 236, 250, 60, 1076288, 0x7FFF, false, false ); // Iron Maiden - AddImageTiledButton( 14, 300, 0x918, 0x919, 0x9E, GumpButtonType.Reply, 0, 0x3F0A, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 98, 300, 250, 60, 1076585, 0x7FFF, false, false ); // Blue plain rug - AddImageTiledButton( 264, 300, 0x918, 0x919, 0x9F, GumpButtonType.Reply, 0, 0x3F11, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 348, 300, 250, 60, 1076586, 0x7FFF, false, false ); // Golden decorative rug - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 7 ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 5); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + AddImageTiledButton(14, 44, 0x918, 0x919, 0x96, GumpButtonType.Reply, 0, 0x1E34, 0x0, 18, -17); + AddTooltip(1076627); + AddHtmlLocalized(98, 44, 250, 60, 1076281, 0x7FFF, false, false); // Scarecrow + AddImageTiledButton(264, 44, 0x918, 0x919, 0x97, GumpButtonType.Reply, 0, 0xA0C, 0x0, 18, 8); + AddTooltip(1076628); + AddHtmlLocalized(348, 44, 250, 60, 1076282, 0x7FFF, false, false); // Wall Torch + AddImageTiledButton(14, 108, 0x918, 0x919, 0x98, GumpButtonType.Reply, 0, 0x3F10, 0x0, 18, 9); + AddTooltip(1076629); + AddHtmlLocalized(98, 108, 250, 60, 1076283, 0x7FFF, false, false); // Fountain + AddImageTiledButton(264, 108, 0x918, 0x919, 0x99, GumpButtonType.Reply, 0, 0x3F19, 0x0, 18, 8); + AddTooltip(1076630); + AddHtmlLocalized(348, 108, 250, 60, 1076284, 0x7FFF, false, false); // Statue + AddImageTiledButton(14, 172, 0x918, 0x919, 0x9A, GumpButtonType.Reply, 0, 0x1EA5, 0x0, 5, -25); + AddTooltip(1076631); + AddHtmlLocalized(98, 172, 250, 60, 1076285, 0x7FFF, false, false); // Large Fish Net + AddImageTiledButton(264, 172, 0x918, 0x919, 0x9B, GumpButtonType.Reply, 0, 0x1EA3, 0x0, 18, -27); + AddTooltip(1076632); + AddHtmlLocalized(348, 172, 250, 60, 1076286, 0x7FFF, false, false); // Small Fish Net + AddImageTiledButton(14, 236, 0x918, 0x919, 0x9C, GumpButtonType.Reply, 0, 0x2FDF, 0x0, 18, -36); + AddTooltip(1076633); + AddHtmlLocalized(98, 236, 250, 60, 1076287, 0x7FFF, false, false); // Ladder + AddImageTiledButton(264, 236, 0x918, 0x919, 0x9D, GumpButtonType.Reply, 0, 0x3F15, 0x0, 18, 8); + AddTooltip(1076622); + AddHtmlLocalized(348, 236, 250, 60, 1076288, 0x7FFF, false, false); // Iron Maiden + AddImageTiledButton(14, 300, 0x918, 0x919, 0x9E, GumpButtonType.Reply, 0, 0x3F0A, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(98, 300, 250, 60, 1076585, 0x7FFF, false, false); // Blue plain rug + AddImageTiledButton(264, 300, 0x918, 0x919, 0x9F, GumpButtonType.Reply, 0, 0x3F11, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(348, 300, 250, 60, 1076586, 0x7FFF, false, false); // Golden decorative rug + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, 7); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - AddPage( 7 ); + AddPage(7); - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 6 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - AddImageTiledButton( 14, 44, 0x918, 0x919, 0xA0, GumpButtonType.Reply, 0, 0x3F0D, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 98, 44, 250, 60, 1076587, 0x7FFF, false, false ); // Cinnamon fancy rug - AddImageTiledButton( 264, 44, 0x918, 0x919, 0xA1, GumpButtonType.Reply, 0, 0x3F18, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 348, 44, 250, 60, 1076588, 0x7FFF, false, false ); // Red plain rug - AddImageTiledButton( 14, 108, 0x918, 0x919, 0xA2, GumpButtonType.Reply, 0, 0x3F08, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 98, 108, 250, 60, 1076589, 0x7FFF, false, false ); // Blue decorative rug - AddImageTiledButton( 264, 108, 0x918, 0x919, 0xA3, GumpButtonType.Reply, 0, 0x3F17, 0x0, 18, 8 ); - AddTooltip( 1076620 ); - AddHtmlLocalized( 348, 108, 250, 60, 1076590, 0x7FFF, false, false ); // Pink fancy rug - AddImageTiledButton( 14, 172, 0x918, 0x919, 0xA4, GumpButtonType.Reply, 0, 0x312A, 0x0, 18, 8 ); - AddTooltip( 1076615 ); - AddHtmlLocalized( 98, 172, 250, 60, 1076784, 0x7FFF, false, false ); // Cherry Blossom Trunk - AddImageTiledButton( 264, 172, 0x918, 0x919, 0xA5, GumpButtonType.Reply, 0, 0x3128, 0x0, 18, 8 ); - AddTooltip( 1076616 ); - AddHtmlLocalized( 348, 172, 250, 60, 1076785, 0x7FFF, false, false ); // Apple Trunk - AddImageTiledButton( 14, 236, 0x918, 0x919, 0xA6, GumpButtonType.Reply, 0, 0x3129, 0x0, 18, 8 ); - AddTooltip( 1076617 ); - AddHtmlLocalized( 98, 236, 250, 60, 1076786, 0x7FFF, false, false ); // Peach Trunk - } + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 6); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + AddImageTiledButton(14, 44, 0x918, 0x919, 0xA0, GumpButtonType.Reply, 0, 0x3F0D, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(98, 44, 250, 60, 1076587, 0x7FFF, false, false); // Cinnamon fancy rug + AddImageTiledButton(264, 44, 0x918, 0x919, 0xA1, GumpButtonType.Reply, 0, 0x3F18, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(348, 44, 250, 60, 1076588, 0x7FFF, false, false); // Red plain rug + AddImageTiledButton(14, 108, 0x918, 0x919, 0xA2, GumpButtonType.Reply, 0, 0x3F08, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(98, 108, 250, 60, 1076589, 0x7FFF, false, false); // Blue decorative rug + AddImageTiledButton(264, 108, 0x918, 0x919, 0xA3, GumpButtonType.Reply, 0, 0x3F17, 0x0, 18, 8); + AddTooltip(1076620); + AddHtmlLocalized(348, 108, 250, 60, 1076590, 0x7FFF, false, false); // Pink fancy rug + AddImageTiledButton(14, 172, 0x918, 0x919, 0xA4, GumpButtonType.Reply, 0, 0x312A, 0x0, 18, 8); + AddTooltip(1076615); + AddHtmlLocalized(98, 172, 250, 60, 1076784, 0x7FFF, false, false); // Cherry Blossom Trunk + AddImageTiledButton(264, 172, 0x918, 0x919, 0xA5, GumpButtonType.Reply, 0, 0x3128, 0x0, 18, 8); + AddTooltip(1076616); + AddHtmlLocalized(348, 172, 250, 60, 1076785, 0x7FFF, false, false); // Apple Trunk + AddImageTiledButton(14, 236, 0x918, 0x919, 0xA6, GumpButtonType.Reply, 0, 0x3129, 0x0, 18, 8); + AddTooltip(1076617); + AddHtmlLocalized(98, 236, 250, 60, 1076786, 0x7FFF, false, false); // Peach Trunk + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Token == null || m_Token.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Token == null || m_Token.Deleted || info.ButtonID == 0) + return; - List types = new List(); - int cliloc = 0; + List types = new List(); + int cliloc = 0; - switch ( info.ButtonID ) - { - // 7th anniversary - case 0x64: types.Add( typeof( LeggingsOfEmbers ) ); cliloc = 1078147; break; - case 0x65: types.Add( typeof( RoseOfTrinsic ) ); cliloc = 1062913; break; - case 0x66: types.Add( typeof( ShaminoCrossbow ) ); cliloc = 1062915; break; - case 0x67: types.Add( typeof( TapestryOfSosaria ) ); cliloc = 1062917; break; - case 0x68: types.Add( typeof( HearthOfHomeFireDeed ) ); cliloc = 1062919; break; - case 0x69: types.Add( typeof( HolySword ) ); cliloc = 1062921; break; - case 0x6A: types.Add( typeof( SamuraiHelm ) ); cliloc = 1062923; break; + switch (info.ButtonID) + { + // 7th anniversary + case 0x64: + types.Add(typeof(LeggingsOfEmbers)); + cliloc = 1078147; + break; + case 0x65: + types.Add(typeof(RoseOfTrinsic)); + cliloc = 1062913; + break; + case 0x66: + types.Add(typeof(ShaminoCrossbow)); + cliloc = 1062915; + break; + case 0x67: + types.Add(typeof(TapestryOfSosaria)); + cliloc = 1062917; + break; + case 0x68: + types.Add(typeof(HearthOfHomeFireDeed)); + cliloc = 1062919; + break; + case 0x69: + types.Add(typeof(HolySword)); + cliloc = 1062921; + break; + case 0x6A: + types.Add(typeof(SamuraiHelm)); + cliloc = 1062923; + break; - // 8th anniversary - /*case 0x6B: types.Add( typeof( SpiritualityHelm ) ); cliloc = 1075188; break; - case 0x6C: types.Add( typeof( ValorGauntlets ) ); cliloc = 1075192; break;*/ - case 0x6D: types.Add( typeof( DupresShield ) ); cliloc = 1075196; break; - case 0x6E: types.Add( typeof( FountainOfLifeDeed ) ); cliloc = 1075197; break; - case 0x6F: types.Add( typeof( DawnsMusicBox ) ); cliloc = 1075198; break; - case 0x70: types.Add( typeof( OssianGrimoire ) ); cliloc = 1078148; break; - case 0x71: types.Add( typeof( FerretFormTalisman ) ); cliloc = 1078142; break; - case 0x72: types.Add( typeof( SquirrelFormTalisman ) ); cliloc = 1078143; break; - case 0x73: types.Add( typeof( CuSidheFormTalisman ) ); cliloc = 1078144; break; - case 0x74: types.Add( typeof( ReptalonFormTalisman ) ); cliloc = 1078145; break; - case 0x75: types.Add( typeof( QuiverOfInfinity ) ); cliloc = 1075201; break; + // 8th anniversary + /*case 0x6B: types.Add( typeof( SpiritualityHelm ) ); cliloc = 1075188; break; + case 0x6C: types.Add( typeof( ValorGauntlets ) ); cliloc = 1075192; break;*/ + case 0x6D: + types.Add(typeof(DupresShield)); + cliloc = 1075196; + break; + case 0x6E: + types.Add(typeof(FountainOfLifeDeed)); + cliloc = 1075197; + break; + case 0x6F: + types.Add(typeof(DawnsMusicBox)); + cliloc = 1075198; + break; + case 0x70: + types.Add(typeof(OssianGrimoire)); + cliloc = 1078148; + break; + case 0x71: + types.Add(typeof(FerretFormTalisman)); + cliloc = 1078142; + break; + case 0x72: + types.Add(typeof(SquirrelFormTalisman)); + cliloc = 1078143; + break; + case 0x73: + types.Add(typeof(CuSidheFormTalisman)); + cliloc = 1078144; + break; + case 0x74: + types.Add(typeof(ReptalonFormTalisman)); + cliloc = 1078145; + break; + case 0x75: + types.Add(typeof(QuiverOfInfinity)); + cliloc = 1075201; + break; - // evil home decor - case 0x76: - types.Add( typeof( BoneThroneDeed ) ); - types.Add( typeof( BoneCouchDeed ) ); - types.Add( typeof( BoneTableDeed ) ); - cliloc = 1074797; - break; - case 0x77: - types.Add( typeof( CreepyPortraitDeed ) ); - types.Add( typeof( DisturbingPortraitDeed ) ); - types.Add( typeof( UnsettlingPortraitDeed ) ); - cliloc = 1078146; - break; - case 0x78: - types.Add( typeof( MountedPixieBlueDeed ) ); - types.Add( typeof( MountedPixieGreenDeed ) ); - types.Add( typeof( MountedPixieLimeDeed ) ); - types.Add( typeof( MountedPixieOrangeDeed ) ); - types.Add( typeof( MountedPixieWhiteDeed ) ); - cliloc = 1074799; - break; - case 0x79: types.Add( typeof( HaunterMirrorDeed ) ); cliloc = 1074800; break; - case 0x7A: types.Add( typeof( BedOfNailsDeed ) ); cliloc = 1074801; break; - case 0x7B: types.Add( typeof( SacrificialAltarDeed ) ); cliloc = 1074818; break; + // evil home decor + case 0x76: + types.Add(typeof(BoneThroneDeed)); + types.Add(typeof(BoneCouchDeed)); + types.Add(typeof(BoneTableDeed)); + cliloc = 1074797; + break; + case 0x77: + types.Add(typeof(CreepyPortraitDeed)); + types.Add(typeof(DisturbingPortraitDeed)); + types.Add(typeof(UnsettlingPortraitDeed)); + cliloc = 1078146; + break; + case 0x78: + types.Add(typeof(MountedPixieBlueDeed)); + types.Add(typeof(MountedPixieGreenDeed)); + types.Add(typeof(MountedPixieLimeDeed)); + types.Add(typeof(MountedPixieOrangeDeed)); + types.Add(typeof(MountedPixieWhiteDeed)); + cliloc = 1074799; + break; + case 0x79: + types.Add(typeof(HaunterMirrorDeed)); + cliloc = 1074800; + break; + case 0x7A: + types.Add(typeof(BedOfNailsDeed)); + cliloc = 1074801; + break; + case 0x7B: + types.Add(typeof(SacrificialAltarDeed)); + cliloc = 1074818; + break; - // broken furniture - case 0x7C: types.Add( typeof( BrokenCoveredChairDeed ) ); cliloc = 1076257; break; - case 0x7D: types.Add( typeof( BrokenBookcaseDeed ) ); cliloc = 1076258; break; - case 0x7E: types.Add( typeof( StandingBrokenChairDeed ) ); cliloc = 1076259; break; - case 0x7F: types.Add( typeof( BrokenVanityDeed ) ); cliloc = 1076260; break; - case 0x80: types.Add( typeof( BrokenChestOfDrawersDeed ) ); cliloc = 1076261; break; - case 0x81: types.Add( typeof( BrokenArmoireDeed ) ); cliloc = 1076262; break; - case 0x82: types.Add( typeof( BrokenBedDeed ) ); cliloc = 1076263; break; - case 0x83: types.Add( typeof( BrokenFallenChairDeed ) ); cliloc = 1076264; break; + // broken furniture + case 0x7C: + types.Add(typeof(BrokenCoveredChairDeed)); + cliloc = 1076257; + break; + case 0x7D: + types.Add(typeof(BrokenBookcaseDeed)); + cliloc = 1076258; + break; + case 0x7E: + types.Add(typeof(StandingBrokenChairDeed)); + cliloc = 1076259; + break; + case 0x7F: + types.Add(typeof(BrokenVanityDeed)); + cliloc = 1076260; + break; + case 0x80: + types.Add(typeof(BrokenChestOfDrawersDeed)); + cliloc = 1076261; + break; + case 0x81: + types.Add(typeof(BrokenArmoireDeed)); + cliloc = 1076262; + break; + case 0x82: + types.Add(typeof(BrokenBedDeed)); + cliloc = 1076263; + break; + case 0x83: + types.Add(typeof(BrokenFallenChairDeed)); + cliloc = 1076264; + break; - // other - case 0x84: types.Add( typeof( SuitOfGoldArmorDeed ) ); cliloc = 1076265; break; - case 0x85: types.Add( typeof( SuitOfSilverArmorDeed ) ); cliloc = 1076266; break; - case 0x86: types.Add( typeof( BoilingCauldronDeed ) ); cliloc = 1076267; break; - case 0x87: types.Add( typeof( GuillotineDeed ) ); cliloc = 1024656; break; - case 0x88: types.Add( typeof( CherryBlossomTreeDeed ) ); cliloc = 1076268; break; - case 0x89: types.Add( typeof( AppleTreeDeed ) ); cliloc = 1076269; break; - case 0x8A: types.Add( typeof( PeachTreeDeed ) ); cliloc = 1076270; break; - case 0x8B: types.Add( typeof( HangingAxesDeed ) ); cliloc = 1076271; break; - case 0x8C: types.Add( typeof( HangingSwordsDeed ) ); cliloc = 1076272; break; - case 0x8D: types.Add( typeof( BlueFancyRugDeed ) ); cliloc = 1076273; break; - case 0x8E: types.Add( typeof( WoodenCoffinDeed ) ); cliloc = 1076274; break; - case 0x8F: types.Add( typeof( VanityDeed ) ); cliloc = 1074027; break; - case 0x90: types.Add( typeof( TableWithPurpleClothDeed ) ); cliloc = 1076635; break; - case 0x91: types.Add( typeof( TableWithBlueClothDeed ) ); cliloc = 1076636; break; - case 0x92: types.Add( typeof( TableWithRedClothDeed ) ); cliloc = 1076637; break; - case 0x93: types.Add( typeof( TableWithOrangeClothDeed ) ); cliloc = 1076638; break; - case 0x94: types.Add( typeof( UnmadeBedDeed ) ); cliloc = 1076279; break; - case 0x95: types.Add( typeof( CurtainsDeed ) ); cliloc = 1076280; break; - case 0x96: types.Add( typeof( ScarecrowDeed ) ); cliloc = 1076281; break; - case 0x97: types.Add( typeof( WallTorchDeed ) ); cliloc = 1076282; break; - case 0x98: types.Add( typeof( FountainDeed ) ); cliloc = 1076283; break; - case 0x99: types.Add( typeof( StoneStatueDeed ) ); cliloc = 1076284; break; - case 0x9A: types.Add( typeof( LargeFishingNetDeed ) ); cliloc = 1076285; break; - case 0x9B: types.Add( typeof( SmallFishingNetDeed ) ); cliloc = 1076286; break; - case 0x9C: types.Add( typeof( HouseLadderDeed ) ); cliloc = 1076287; break; - case 0x9D: types.Add( typeof( IronMaidenDeed ) ); cliloc = 1076288; break; - case 0x9E: types.Add( typeof( BluePlainRugDeed ) ); cliloc = 1076585; break; - case 0x9F: types.Add( typeof( GoldenDecorativeRugDeed ) ); cliloc = 1076586; break; - case 0xA0: types.Add( typeof( CinnamonFancyRugDeed ) ); cliloc = 1076587; break; - case 0xA1: types.Add( typeof( RedPlainRugDeed ) ); cliloc = 1076588; break; - case 0xA2: types.Add( typeof( BlueDecorativeRugDeed ) ); cliloc = 1076589; break; - case 0xA3: types.Add( typeof( PinkFancyRugDeed ) ); cliloc = 1076590; break; - case 0xA4: types.Add( typeof( CherryBlossomTrunkDeed ) ); cliloc = 1076784; break; - case 0xA5: types.Add( typeof( AppleTrunkDeed ) ); cliloc = 1076785; break; - case 0xA6: types.Add( typeof( PeachTrunkDeed ) ); cliloc = 1076786; break; - } + // other + case 0x84: + types.Add(typeof(SuitOfGoldArmorDeed)); + cliloc = 1076265; + break; + case 0x85: + types.Add(typeof(SuitOfSilverArmorDeed)); + cliloc = 1076266; + break; + case 0x86: + types.Add(typeof(BoilingCauldronDeed)); + cliloc = 1076267; + break; + case 0x87: + types.Add(typeof(GuillotineDeed)); + cliloc = 1024656; + break; + case 0x88: + types.Add(typeof(CherryBlossomTreeDeed)); + cliloc = 1076268; + break; + case 0x89: + types.Add(typeof(AppleTreeDeed)); + cliloc = 1076269; + break; + case 0x8A: + types.Add(typeof(PeachTreeDeed)); + cliloc = 1076270; + break; + case 0x8B: + types.Add(typeof(HangingAxesDeed)); + cliloc = 1076271; + break; + case 0x8C: + types.Add(typeof(HangingSwordsDeed)); + cliloc = 1076272; + break; + case 0x8D: + types.Add(typeof(BlueFancyRugDeed)); + cliloc = 1076273; + break; + case 0x8E: + types.Add(typeof(WoodenCoffinDeed)); + cliloc = 1076274; + break; + case 0x8F: + types.Add(typeof(VanityDeed)); + cliloc = 1074027; + break; + case 0x90: + types.Add(typeof(TableWithPurpleClothDeed)); + cliloc = 1076635; + break; + case 0x91: + types.Add(typeof(TableWithBlueClothDeed)); + cliloc = 1076636; + break; + case 0x92: + types.Add(typeof(TableWithRedClothDeed)); + cliloc = 1076637; + break; + case 0x93: + types.Add(typeof(TableWithOrangeClothDeed)); + cliloc = 1076638; + break; + case 0x94: + types.Add(typeof(UnmadeBedDeed)); + cliloc = 1076279; + break; + case 0x95: + types.Add(typeof(CurtainsDeed)); + cliloc = 1076280; + break; + case 0x96: + types.Add(typeof(ScarecrowDeed)); + cliloc = 1076281; + break; + case 0x97: + types.Add(typeof(WallTorchDeed)); + cliloc = 1076282; + break; + case 0x98: + types.Add(typeof(FountainDeed)); + cliloc = 1076283; + break; + case 0x99: + types.Add(typeof(StoneStatueDeed)); + cliloc = 1076284; + break; + case 0x9A: + types.Add(typeof(LargeFishingNetDeed)); + cliloc = 1076285; + break; + case 0x9B: + types.Add(typeof(SmallFishingNetDeed)); + cliloc = 1076286; + break; + case 0x9C: + types.Add(typeof(HouseLadderDeed)); + cliloc = 1076287; + break; + case 0x9D: + types.Add(typeof(IronMaidenDeed)); + cliloc = 1076288; + break; + case 0x9E: + types.Add(typeof(BluePlainRugDeed)); + cliloc = 1076585; + break; + case 0x9F: + types.Add(typeof(GoldenDecorativeRugDeed)); + cliloc = 1076586; + break; + case 0xA0: + types.Add(typeof(CinnamonFancyRugDeed)); + cliloc = 1076587; + break; + case 0xA1: + types.Add(typeof(RedPlainRugDeed)); + cliloc = 1076588; + break; + case 0xA2: + types.Add(typeof(BlueDecorativeRugDeed)); + cliloc = 1076589; + break; + case 0xA3: + types.Add(typeof(PinkFancyRugDeed)); + cliloc = 1076590; + break; + case 0xA4: + types.Add(typeof(CherryBlossomTrunkDeed)); + cliloc = 1076784; + break; + case 0xA5: + types.Add(typeof(AppleTrunkDeed)); + cliloc = 1076785; + break; + case 0xA6: + types.Add(typeof(PeachTrunkDeed)); + cliloc = 1076786; + break; + } - if ( types.Count > 0 && cliloc > 0 ) - { - sender.Mobile.CloseGump( typeof( ConfirmHeritageGump ) ); - sender.Mobile.SendGump( new ConfirmHeritageGump( m_Token, types.ToArray(), cliloc ) ); - } - else - sender.Mobile.SendLocalizedMessage( 501311 ); // This option is currently disabled, while we evaluate it for game balance. - } - } -} + if (types.Count > 0 && cliloc > 0) + { + sender.Mobile.CloseGump(typeof(ConfirmHeritageGump)); + sender.Mobile.SendGump(new ConfirmHeritageGump(m_Token, types.ToArray(), cliloc)); + } + else + { + sender.Mobile + .SendLocalizedMessage( + 501311); // This option is currently disabled, while we evaluate it for game balance. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/HonorSelf.cs b/Scripts/Gumps/HonorSelf.cs index 2c5cc6365..44f7b5f3f 100644 --- a/Scripts/Gumps/HonorSelf.cs +++ b/Scripts/Gumps/HonorSelf.cs @@ -1,31 +1,25 @@ -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Gumps { - public class HonorSelf: Gump - { - PlayerMobile m_from; - public HonorSelf( PlayerMobile from ) : base( 150, 50 ) - { - m_from = from; - AddBackground(0, 0, 245, 145, 9250); - AddButton(157, 101, 247, 248, 1, GumpButtonType.Reply, 0); - AddButton(81, 100, 241, 248, 0, GumpButtonType.Reply, 0); - AddHtml( 21, 20, 203, 70, @"Are you sure you want to use -honor points on yourself?", true, false); - } + public class HonorSelf : Gump + { + private PlayerMobile m_from; - public override void OnResponse( NetState sender, RelayInfo info ) - { - - if ( info.ButtonID == 1 ) - { - HonorVirtue.ActivateEmbrace(m_from); - } - else - { - } - } - } -} + public HonorSelf(PlayerMobile from) : base(150, 50) + { + m_from = from; + AddBackground(0, 0, 245, 145, 9250); + AddButton(157, 101, 247, 248, 1, GumpButtonType.Reply, 0); + AddButton(81, 100, 241, 248, 0, GumpButtonType.Reply, 0); + AddHtml(21, 20, 203, 70, @"Are you sure you want to use +honor points on yourself?", true, false); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) HonorVirtue.ActivateEmbrace(m_from); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/HouseDemolishGump.cs b/Scripts/Gumps/HouseDemolishGump.cs index 9f02b2b4e..18e376e01 100644 --- a/Scripts/Gumps/HouseDemolishGump.cs +++ b/Scripts/Gumps/HouseDemolishGump.cs @@ -1,37 +1,38 @@ using Server.Accounting; +using Server.Guilds; using Server.Items; using Server.Multis; using Server.Network; namespace Server.Gumps { - public class HouseDemolishGump : Gump - { - private Mobile m_Mobile; - private BaseHouse m_House; + public class HouseDemolishGump : Gump + { + private BaseHouse m_House; + private Mobile m_Mobile; - public HouseDemolishGump( Mobile mobile, BaseHouse house ) : base( 110, 100 ) - { - m_Mobile = mobile; - m_House = house; + public HouseDemolishGump(Mobile mobile, BaseHouse house) : base(110, 100) + { + m_Mobile = mobile; + m_House = house; - mobile.CloseGump( typeof( HouseDemolishGump ) ); + mobile.CloseGump(typeof(HouseDemolishGump)); - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 420, 280, 5054 ); + AddBackground(0, 0, 420, 280, 5054); - AddImageTiled( 10, 10, 400, 20, 2624 ); - AddAlphaRegion( 10, 10, 400, 20 ); + AddImageTiled(10, 10, 400, 20, 2624); + AddAlphaRegion(10, 10, 400, 20); - AddHtmlLocalized( 10, 10, 400, 20, 1060635, 30720, false, false ); //
WARNING
+ AddHtmlLocalized(10, 10, 400, 20, 1060635, 30720, false, false); //
WARNING
- AddImageTiled( 10, 40, 400, 200, 2624 ); - AddAlphaRegion( 10, 40, 400, 200 ); + AddImageTiled(10, 40, 400, 200, 2624); + AddAlphaRegion(10, 40, 400, 200); - AddHtmlLocalized( 10, 40, 400, 200, 1061795, 32512, false, true ); /* You are about to demolish your house. + AddHtmlLocalized(10, 40, 400, 200, 1061795, 32512, false, true); /* You are about to demolish your house. * You will be refunded the house's value directly to your bank box. * All items in the house will remain behind and can be freely picked up by anyone. * Once the house is demolished, anyone can attempt to place a new house on the vacant land. @@ -39,127 +40,131 @@ namespace Server.Gumps * Are you sure you wish to continue? */ - AddImageTiled( 10, 250, 400, 20, 2624 ); - AddAlphaRegion( 10, 250, 400, 20 ); + AddImageTiled(10, 250, 400, 20, 2624); + AddAlphaRegion(10, 250, 400, 20); - AddButton( 10, 250, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 250, 170, 20, 1011036, 32767, false, false ); // OKAY + AddButton(10, 250, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 250, 170, 20, 1011036, 32767, false, false); // OKAY - AddButton( 210, 250, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 240, 250, 170, 20, 1011012, 32767, false, false ); // CANCEL - } + AddButton(210, 250, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(240, 250, 170, 20, 1011012, 32767, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 1 && !m_House.Deleted ) - { - if ( m_House.IsOwner( m_Mobile ) ) - { - if ( m_House.MovingCrate != null || m_House.InternalizedVendors.Count > 0 ) - { - return; - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1 && !m_House.Deleted) + { + if (m_House.IsOwner(m_Mobile)) + { + if (m_House.MovingCrate != null || m_House.InternalizedVendors.Count > 0) return; - if ( !Guilds.Guild.NewGuildSystem && m_House.FindGuildstone() != null ) - { - m_Mobile.SendLocalizedMessage( 501389 ); // You cannot redeed a house with a guildstone inside. - return; - } - /*else if ( m_House.PlayerVendors.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 503236 ); // You need to collect your vendor's belongings before moving. - return; - }*/ - if ( m_House.HasRentedVendors && m_House.VendorInventories.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 1062679 ); // You cannot do that that while you still have contract vendors or unclaimed contract vendor inventory in your house. - return; - } - if ( m_House.HasRentedVendors ) - { - m_Mobile.SendLocalizedMessage( 1062680 ); // You cannot do that that while you still have contract vendors in your house. - return; - } - if ( m_House.VendorInventories.Count > 0 ) - { - m_Mobile.SendLocalizedMessage( 1062681 ); // You cannot do that that while you still have unclaimed contract vendor inventory in your house. - return; - } + if (!Guild.NewGuildSystem && m_House.FindGuildstone() != null) + { + m_Mobile.SendLocalizedMessage(501389); // You cannot redeed a house with a guildstone inside. + return; + } + + /*else if ( m_House.PlayerVendors.Count > 0 ) + { + m_Mobile.SendLocalizedMessage( 503236 ); // You need to collect your vendor's belongings before moving. + return; + }*/ + if (m_House.HasRentedVendors && m_House.VendorInventories.Count > 0) + { + m_Mobile.SendLocalizedMessage( + 1062679); // You cannot do that that while you still have contract vendors or unclaimed contract vendor inventory in your house. + return; + } + + if (m_House.HasRentedVendors) + { + m_Mobile.SendLocalizedMessage( + 1062680); // You cannot do that that while you still have contract vendors in your house. + return; + } + + if (m_House.VendorInventories.Count > 0) + { + m_Mobile.SendLocalizedMessage( + 1062681); // You cannot do that that while you still have unclaimed contract vendor inventory in your house. + return; + } - if ( m_Mobile.AccessLevel >= AccessLevel.GameMaster ) - { - m_Mobile.SendMessage( "You do not get a refund for your house as you are not a player" ); - m_House.RemoveKeys(m_Mobile); - m_House.Delete(); - } - else - { - Item toGive = null; + if (m_Mobile.AccessLevel >= AccessLevel.GameMaster) + { + m_Mobile.SendMessage("You do not get a refund for your house as you are not a player"); + m_House.RemoveKeys(m_Mobile); + m_House.Delete(); + } + else + { + Item toGive = null; - if ( m_House.IsAosRules ) - { - if ( m_House.Price > 0 ) - toGive = new BankCheck( m_House.Price ); - else - toGive = m_House.GetDeed(); - } - else - { - toGive = m_House.GetDeed(); + if (m_House.IsAosRules) + { + if (m_House.Price > 0) + toGive = new BankCheck(m_House.Price); + else + toGive = m_House.GetDeed(); + } + else + { + toGive = m_House.GetDeed(); - if ( toGive == null && m_House.Price > 0 ) - toGive = new BankCheck( m_House.Price ); - } + if (toGive == null && m_House.Price > 0) + toGive = new BankCheck(m_House.Price); + } - BankCheck check = toGive as BankCheck; + BankCheck check = toGive as BankCheck; - if (AccountGold.Enabled && check != null) - { - var worth = check.Worth; + if (AccountGold.Enabled && check != null) + { + int worth = check.Worth; - if (m_Mobile.Account != null && m_Mobile.Account.DepositGold(worth)) - { - check.Delete(); + if (m_Mobile.Account != null && m_Mobile.Account.DepositGold(worth)) + { + check.Delete(); - m_Mobile.SendLocalizedMessage(1060397, worth.ToString("#,0")); - // ~1_AMOUNT~ gold has been deposited into your bank box. + m_Mobile.SendLocalizedMessage(1060397, worth.ToString("#,0")); + // ~1_AMOUNT~ gold has been deposited into your bank box. - m_House.RemoveKeys(m_Mobile); - m_House.Delete(); - return; - } - } + m_House.RemoveKeys(m_Mobile); + m_House.Delete(); + return; + } + } - if ( toGive != null ) - { - BankBox box = m_Mobile.BankBox; + if (toGive != null) + { + BankBox box = m_Mobile.BankBox; - if ( box.TryDropItem( m_Mobile, toGive, false ) ) - { - if ( check != null ) - m_Mobile.SendLocalizedMessage( 1060397, check.Worth.ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. + if (box.TryDropItem(m_Mobile, toGive, false)) + { + if (check != null) + m_Mobile.SendLocalizedMessage(1060397, + check.Worth.ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. - m_House.RemoveKeys( m_Mobile ); - m_House.Delete(); - } - else - { - toGive.Delete(); - m_Mobile.SendLocalizedMessage( 500390 ); // Your bank box is full. - } - } - else - { - m_Mobile.SendMessage( "Unable to refund house." ); - } - } - } - else - { - m_Mobile.SendLocalizedMessage( 501320 ); // Only the house owner may do this. - } - } - } - } -} + m_House.RemoveKeys(m_Mobile); + m_House.Delete(); + } + else + { + toGive.Delete(); + m_Mobile.SendLocalizedMessage(500390); // Your bank box is full. + } + } + else + { + m_Mobile.SendMessage("Unable to refund house."); + } + } + } + else + { + m_Mobile.SendLocalizedMessage(501320); // Only the house owner may do this. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/HouseGump.cs b/Scripts/Gumps/HouseGump.cs index 13a48f01a..2bdbc83b8 100644 --- a/Scripts/Gumps/HouseGump.cs +++ b/Scripts/Gumps/HouseGump.cs @@ -1,752 +1,740 @@ -using System; using System.Collections; +using Server.Guilds; +using Server.Multis; using Server.Network; using Server.Prompts; -using Server.Multis; namespace Server.Gumps { - public class HouseListGump : Gump - { - private BaseHouse m_House; + public class HouseListGump : Gump + { + private BaseHouse m_House; - public HouseListGump( int number, ArrayList list, BaseHouse house, bool accountOf ) : base( 20, 30 ) - { - if ( house.Deleted ) - return; - - m_House = house; + public HouseListGump(int number, ArrayList list, BaseHouse house, bool accountOf) : base(20, 30) + { + if (house.Deleted) + return; - AddPage( 0 ); + m_House = house; - AddBackground( 0, 0, 420, 430, 5054 ); - AddBackground( 10, 10, 400, 410, 3000 ); - - AddButton( 20, 388, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 388, 300, 20, 1011104, false, false ); // Return to previous menu + AddPage(0); - AddHtmlLocalized( 20, 20, 350, 20, number, false, false ); + AddBackground(0, 0, 420, 430, 5054); + AddBackground(10, 10, 400, 410, 3000); - if ( list != null ) - { - for ( int i = 0; i < list.Count; ++i ) - { - if ( (i % 16) == 0 ) - { - if ( i != 0 ) - { - // Next button - AddButton( 370, 20, 4005, 4007, 0, GumpButtonType.Page, (i / 16) + 1 ); - } + AddButton(20, 388, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 388, 300, 20, 1011104, false, false); // Return to previous menu - AddPage( (i / 16) + 1 ); + AddHtmlLocalized(20, 20, 350, 20, number, false, false); - if ( i != 0 ) - { - // Previous button - AddButton( 340, 20, 4014, 4016, 0, GumpButtonType.Page, i / 16 ); - } - } + if (list != null) + for (int i = 0; i < list.Count; ++i) + { + if (i % 16 == 0) + { + if (i != 0) AddButton(370, 20, 4005, 4007, 0, GumpButtonType.Page, i / 16 + 1); - Mobile m = (Mobile)list[i]; + AddPage(i / 16 + 1); - string name; + if (i != 0) AddButton(340, 20, 4014, 4016, 0, GumpButtonType.Page, i / 16); + } - if ( m == null || (name = m.Name) == null || (name = name.Trim()).Length <= 0 ) - continue; - - AddLabel( 55, 55 + ((i % 16) * 20), 0, accountOf && m.Player && m.Account != null ? $"Account of {name}" - : name ); - } - } - } + Mobile m = (Mobile)list[i]; - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_House.Deleted ) - return; - - Mobile from = state.Mobile; - - from.SendGump( new HouseGump( from, m_House ) ); - } - } - - public class HouseRemoveGump : Gump - { - private BaseHouse m_House; - private ArrayList m_List, m_Copy; - private int m_Number; - private bool m_AccountOf; - - public HouseRemoveGump( int number, ArrayList list, BaseHouse house, bool accountOf ) : base( 20, 30 ) - { - if ( house.Deleted ) - return; - - m_House = house; - m_List = list; - m_Number = number; - m_AccountOf = accountOf; - - AddPage( 0 ); - - AddBackground( 0, 0, 420, 430, 5054 ); - AddBackground( 10, 10, 400, 410, 3000 ); - - AddButton( 20, 388, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 388, 300, 20, 1011104, false, false ); // Return to previous menu - - AddButton( 20, 365, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 365, 300, 20, 1011270, false, false ); // Remove now! - - AddHtmlLocalized( 20, 20, 350, 20, number, false, false ); - - if ( list != null ) - { - m_Copy = new ArrayList( list ); - - for ( int i = 0; i < list.Count; ++i ) - { - if ( (i % 15) == 0 ) - { - if ( i != 0 ) - { - // Next button - AddButton( 370, 20, 4005, 4007, 0, GumpButtonType.Page, (i / 15) + 1 ); - } - - AddPage( (i / 15) + 1 ); - - if ( i != 0 ) - { - // Previous button - AddButton( 340, 20, 4014, 4016, 0, GumpButtonType.Page, i / 15 ); - } - } - - Mobile m = (Mobile)list[i]; - - string name; - - if ( m == null || (name = m.Name) == null || (name = name.Trim()).Length <= 0 ) - continue; - - AddCheck( 34, 52 + ((i % 15) * 20), 0xD2, 0xD3, false, i ); - AddLabel( 55, 52 + ((i % 15) * 20), 0, accountOf && m.Player && m.Account != null ? $"Account of {name}" - : name ); - } - } - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_House.Deleted ) - return; - - Mobile from = state.Mobile; - - if ( m_List != null && info.ButtonID == 1 ) // Remove now - { - int[] switches = info.Switches; - - if ( switches.Length > 0 ) - { - for ( int i = 0; i < switches.Length; ++i ) - { - int index = switches[i]; - - if ( index >= 0 && index < m_Copy.Count ) - m_List.Remove( m_Copy[index] ); - } - - if ( m_List.Count > 0 ) - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseRemoveGump( m_Number, m_List, m_House, m_AccountOf ) ); - return; - } - } - } - - from.SendGump( new HouseGump( from, m_House ) ); - } - } - - public class HouseGump : Gump - { - private BaseHouse m_House; - - private ArrayList Wrap( string value ) - { - if ( value == null || (value = value.Trim()).Length <= 0 ) - return null; - - string[] values = value.Split( ' ' ); - ArrayList list = new ArrayList(); - string current = ""; - - for ( int i = 0; i < values.Length; ++i ) - { - string val = values[i]; - - string v = current.Length == 0 ? val : current + ' ' + val; - - if ( v.Length < 10 ) - { - current = v; - } - else if ( v.Length == 10 ) - { - list.Add( v ); - - if ( list.Count == 6 ) - return list; - - current = ""; - } - else if ( val.Length <= 10 ) - { - list.Add( current ); + string name; - if ( list.Count == 6 ) - return list; + if (m == null || (name = m.Name) == null || (name = name.Trim()).Length <= 0) + continue; - current = val; - } - else - { - while ( v.Length >= 10 ) - { - list.Add( v.Substring( 0, 10 ) ); + AddLabel(55, 55 + i % 16 * 20, 0, accountOf && m.Player && m.Account != null + ? $"Account of {name}" + : name); + } + } - if ( list.Count == 6 ) - return list; + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_House.Deleted) + return; - v = v.Substring( 10 ); - } + Mobile from = state.Mobile; - current = v; - } - } + from.SendGump(new HouseGump(from, m_House)); + } + } - if ( current.Length > 0 ) - list.Add( current ); + public class HouseRemoveGump : Gump + { + private bool m_AccountOf; + private BaseHouse m_House; + private ArrayList m_List, m_Copy; + private int m_Number; - return list; - } + public HouseRemoveGump(int number, ArrayList list, BaseHouse house, bool accountOf) : base(20, 30) + { + if (house.Deleted) + return; - public HouseGump( Mobile from, BaseHouse house ) : base( 20, 30 ) - { - if ( house.Deleted ) - return; + m_House = house; + m_List = list; + m_Number = number; + m_AccountOf = accountOf; - m_House = house; + AddPage(0); - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); + AddBackground(0, 0, 420, 430, 5054); + AddBackground(10, 10, 400, 410, 3000); - bool isCombatRestricted = house.IsCombatRestricted( from ); + AddButton(20, 388, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 388, 300, 20, 1011104, false, false); // Return to previous menu - bool isOwner = m_House.IsOwner( from ); - bool isCoOwner = isOwner || m_House.IsCoOwner( from ); - bool isFriend = isCoOwner || m_House.IsFriend( from ); + AddButton(20, 365, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 365, 300, 20, 1011270, false, false); // Remove now! - if ( isCombatRestricted ) - isFriend = isCoOwner = isOwner = false; + AddHtmlLocalized(20, 20, 350, 20, number, false, false); - AddPage( 0 ); + if (list != null) + { + m_Copy = new ArrayList(list); - if ( isFriend ) - { - AddBackground( 0, 0, 420, 430, 5054 ); - AddBackground( 10, 10, 400,410, 3000 ); - } + for (int i = 0; i < list.Count; ++i) + { + if (i % 15 == 0) + { + if (i != 0) AddButton(370, 20, 4005, 4007, 0, GumpButtonType.Page, i / 15 + 1); - AddImage( 130, 0, 100 ); + AddPage(i / 15 + 1); - if ( m_House.Sign != null ) - { - ArrayList lines = Wrap( m_House.Sign.GetName() ); + if (i != 0) AddButton(340, 20, 4014, 4016, 0, GumpButtonType.Page, i / 15); + } - if ( lines != null ) - { - for ( int i = 0, y = (101 - (lines.Count * 14)) / 2; i < lines.Count; ++i, y += 14 ) - { - string s = (string)lines[i]; + Mobile m = (Mobile)list[i]; - AddLabel( 130 + ((143 - (s.Length * 8)) / 2), y, 0, s ); - } - } - } + string name; - if ( !isFriend ) - return; + if (m == null || (name = m.Name) == null || (name = name.Trim()).Length <= 0) + continue; - AddHtmlLocalized( 55, 103, 75, 20, 1011233, false, false ); // INFO - AddButton( 20, 103, 4005, 4007, 0, GumpButtonType.Page, 1 ); + AddCheck(34, 52 + i % 15 * 20, 0xD2, 0xD3, false, i); + AddLabel(55, 52 + i % 15 * 20, 0, accountOf && m.Player && m.Account != null + ? $"Account of {name}" + : name); + } + } + } - AddHtmlLocalized( 170, 103, 75, 20, 1011234, false, false ); // FRIENDS - AddButton( 135, 103, 4005, 4007, 0, GumpButtonType.Page, 2 ); + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_House.Deleted) + return; - AddHtmlLocalized( 295, 103, 75, 20, 1011235, false, false ); // OPTIONS - AddButton( 260, 103, 4005, 4007, 0, GumpButtonType.Page, 3 ); + Mobile from = state.Mobile; - AddHtmlLocalized( 295, 390, 75, 20, 1011441, false, false ); // EXIT - AddButton( 260, 390, 4005, 4007, 0, GumpButtonType.Reply, 0 ); + if (m_List != null && info.ButtonID == 1) // Remove now + { + int[] switches = info.Switches; - AddHtmlLocalized( 55, 390, 200, 20, 1011236, false, false ); // Change this house's name! - AddButton( 20, 390, 4005, 4007, 1, GumpButtonType.Reply, 0 ); + if (switches.Length > 0) + { + for (int i = 0; i < switches.Length; ++i) + { + int index = switches[i]; - // Info page - AddPage( 1 ); + if (index >= 0 && index < m_Copy.Count) + m_List.Remove(m_Copy[index]); + } - AddHtmlLocalized( 20, 135, 100, 20, 1011242, false, false ); // Owned by: - AddHtml( 120, 135, 100, 20, GetOwnerName(), false, false ); + if (m_List.Count > 0) + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseRemoveGump(m_Number, m_List, m_House, m_AccountOf)); + return; + } + } + } - AddHtmlLocalized( 20, 170, 275, 20, 1011237, false, false ); // Number of locked down items: - AddHtml( 320, 170, 50, 20, m_House.LockDownCount.ToString(), false, false ); + from.SendGump(new HouseGump(from, m_House)); + } + } - AddHtmlLocalized( 20, 190, 275, 20, 1011238, false, false ); // Maximum locked down items: - AddHtml( 320, 190, 50, 20, m_House.MaxLockDowns.ToString(), false, false ); + public class HouseGump : Gump + { + private BaseHouse m_House; - AddHtmlLocalized( 20, 210, 275, 20, 1011239, false, false ); // Number of secure containers: - AddHtml( 320, 210, 50, 20, m_House.SecureCount.ToString(), false, false ); + public HouseGump(Mobile from, BaseHouse house) : base(20, 30) + { + if (house.Deleted) + return; - AddHtmlLocalized( 20, 230, 275, 20, 1011240, false, false ); // Maximum number of secure containers: - AddHtml( 320, 230, 50, 20, m_House.MaxSecures.ToString(), false, false ); + m_House = house; - AddHtmlLocalized( 20, 260, 400, 20, 1018032, false, false ); // This house is properly placed. - AddHtmlLocalized( 20, 280, 400, 20, 1018035, false, false ); // This house is of modern design. + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); - if ( m_House.Public ) - { - // TODO: Validate exact placement - AddHtmlLocalized( 20, 305, 275, 20, 1011241, false, false ); // Number of visits this building has had - AddHtml( 320, 305, 50, 20, m_House.Visits.ToString(), false, false ); - } + bool isCombatRestricted = house.IsCombatRestricted(from); - // Friends page - AddPage( 2 ); + bool isOwner = m_House.IsOwner(from); + bool isCoOwner = isOwner || m_House.IsCoOwner(from); + bool isFriend = isCoOwner || m_House.IsFriend(from); - AddHtmlLocalized( 45, 130, 150, 20, 1011266, false, false ); // List of co-owners - AddButton( 20, 130, 2714, 2715, 2, GumpButtonType.Reply, 0 ); + if (isCombatRestricted) + isFriend = isCoOwner = isOwner = false; - AddHtmlLocalized( 45, 150, 150, 20, 1011267, false, false ); // Add a co-owner - AddButton( 20, 150, 2714, 2715, 3, GumpButtonType.Reply, 0 ); + AddPage(0); - AddHtmlLocalized( 45, 170, 150, 20, 1018036, false, false ); // Remove a co-owner - AddButton( 20, 170, 2714, 2715, 4, GumpButtonType.Reply, 0 ); + if (isFriend) + { + AddBackground(0, 0, 420, 430, 5054); + AddBackground(10, 10, 400, 410, 3000); + } - AddHtmlLocalized( 45, 190, 150, 20, 1011268, false, false ); // Clear co-owner list - AddButton( 20, 190, 2714, 2715, 5, GumpButtonType.Reply, 0 ); + AddImage(130, 0, 100); - AddHtmlLocalized( 225, 130, 155, 20, 1011243, false, false ); // List of Friends - AddButton( 200, 130, 2714, 2715, 6, GumpButtonType.Reply, 0 ); + if (m_House.Sign != null) + { + ArrayList lines = Wrap(m_House.Sign.GetName()); - AddHtmlLocalized( 225, 150, 155, 20, 1011244, false, false ); // Add a Friend - AddButton( 200, 150, 2714, 2715, 7, GumpButtonType.Reply, 0 ); + if (lines != null) + for (int i = 0, y = (101 - lines.Count * 14) / 2; i < lines.Count; ++i, y += 14) + { + string s = (string)lines[i]; - AddHtmlLocalized( 225, 170, 155, 20, 1018037, false, false ); // Remove a Friend - AddButton( 200, 170, 2714, 2715, 8, GumpButtonType.Reply, 0 ); + AddLabel(130 + (143 - s.Length * 8) / 2, y, 0, s); + } + } - AddHtmlLocalized( 225, 190, 155, 20, 1011245, false, false ); // Clear Friends list - AddButton( 200, 190, 2714, 2715, 9, GumpButtonType.Reply, 0 ); + if (!isFriend) + return; - AddHtmlLocalized( 120, 215, 280, 20, 1011258, false, false ); // Ban someone from the house - AddButton( 95, 215, 2714, 2715, 10, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 103, 75, 20, 1011233, false, false); // INFO + AddButton(20, 103, 4005, 4007, 0, GumpButtonType.Page, 1); - AddHtmlLocalized( 120, 235, 280, 20, 1011259, false, false ); // Eject someone from the house - AddButton( 95, 235, 2714, 2715, 11, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(170, 103, 75, 20, 1011234, false, false); // FRIENDS + AddButton(135, 103, 4005, 4007, 0, GumpButtonType.Page, 2); - AddHtmlLocalized( 120, 255, 280, 20, 1011260, false, false ); // View a list of banned people - AddButton( 95, 255, 2714, 2715, 12, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(295, 103, 75, 20, 1011235, false, false); // OPTIONS + AddButton(260, 103, 4005, 4007, 0, GumpButtonType.Page, 3); - AddHtmlLocalized( 120, 275, 280, 20, 1011261, false, false ); // Lift a ban - AddButton( 95, 275, 2714, 2715, 13, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(295, 390, 75, 20, 1011441, false, false); // EXIT + AddButton(260, 390, 4005, 4007, 0, GumpButtonType.Reply, 0); - // Options page - AddPage( 3 ); + AddHtmlLocalized(55, 390, 200, 20, 1011236, false, false); // Change this house's name! + AddButton(20, 390, 4005, 4007, 1, GumpButtonType.Reply, 0); - AddHtmlLocalized( 45, 150, 355, 30, 1011248, false, false ); // Transfer ownership of the house - AddButton( 20, 150, 2714, 2715, 14, GumpButtonType.Reply, 0 ); + // Info page + AddPage(1); - AddHtmlLocalized( 45, 180, 355, 30, 1011249, false, false ); // Demolish house and get deed back - AddButton( 20, 180, 2714, 2715, 15, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(20, 135, 100, 20, 1011242, false, false); // Owned by: + AddHtml(120, 135, 100, 20, GetOwnerName(), false, false); - if ( !m_House.Public ) - { - AddHtmlLocalized( 45, 210, 355, 30, 1011247, false, false ); // Change the house locks - AddButton( 20, 210, 2714, 2715, 16, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(20, 170, 275, 20, 1011237, false, false); // Number of locked down items: + AddHtml(320, 170, 50, 20, m_House.LockDownCount.ToString(), false, false); - AddHtmlLocalized( 45, 240, 350, 90, 1011253, false, false ); // Declare this building to be public. This will make your front door unlockable. - AddButton( 20, 240, 2714, 2715, 17, GumpButtonType.Reply, 0 ); - } - else - { - //AddHtmlLocalized( 45, 280, 350, 30, 1011250, false, false ); // Change the sign type - AddHtmlLocalized( 45, 210, 350, 30, 1011250, false, false ); // Change the sign type - AddButton( 20, 210, 2714, 2715, 0, GumpButtonType.Page, 4 ); + AddHtmlLocalized(20, 190, 275, 20, 1011238, false, false); // Maximum locked down items: + AddHtml(320, 190, 50, 20, m_House.MaxLockDowns.ToString(), false, false); - AddHtmlLocalized( 45, 240, 350, 30, 1011252, false, false ); // Declare this building to be private. - AddButton( 20, 240, 2714, 2715, 17, GumpButtonType.Reply, 0 ); - - // Change the sign type - AddPage( 4 ); + AddHtmlLocalized(20, 210, 275, 20, 1011239, false, false); // Number of secure containers: + AddHtml(320, 210, 50, 20, m_House.SecureCount.ToString(), false, false); - for ( int i = 0; i < 24; ++i ) - { - AddRadio( 53 + ((i / 4) * 50), 137 + ((i % 4) * 35), 210, 211, false, i + 1 ); - AddItem( 60 + ((i / 4) * 50), 130 + ((i % 4) * 35), 2980 + (i * 2) ); - } + AddHtmlLocalized(20, 230, 275, 20, 1011240, false, false); // Maximum number of secure containers: + AddHtml(320, 230, 50, 20, m_House.MaxSecures.ToString(), false, false); - AddHtmlLocalized( 200, 305, 129, 20, 1011254, false, false ); // Guild sign choices - AddButton( 350, 305, 252, 253, 0, GumpButtonType.Page, 5 ); - - AddHtmlLocalized( 200, 340, 355, 30, 1011277, false, false ); // Okay that is fine. - AddButton( 350, 340, 4005, 4007, 18, GumpButtonType.Reply, 0 ); - - AddPage( 5 ); - - for ( int i = 0; i < 29; ++i ) - { - AddRadio( 53 + ((i / 5) * 50), 137 + ((i % 5) * 35), 210, 211, false, i + 25 ); - AddItem( 60 + ((i / 5) * 50), 130 + ((i % 5) * 35), 3028 + (i * 2) ); - } - - AddHtmlLocalized( 200, 305, 129, 20, 1011255, false, false ); // Shop sign choices - AddButton( 350, 305, 250, 251, 0, GumpButtonType.Page, 4 ); - - AddHtmlLocalized( 200, 340, 355, 30, 1011277, false, false ); // Okay that is fine. - AddButton( 350, 340, 4005, 4007, 18, GumpButtonType.Reply, 0 ); - } - } - - private string GetOwnerName() - { - Mobile m = m_House.Owner; - - if ( m == null ) - return "(unowned)"; - - string name; - - if ( (name = m.Name) == null || (name = name.Trim()).Length <= 0 ) - name = "(no name)"; - - return name; - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_House.Deleted ) - return; - - Mobile from = sender.Mobile; - - bool isCombatRestricted = m_House.IsCombatRestricted( from ); - - bool isOwner = m_House.IsOwner( from ); - bool isCoOwner = isOwner || m_House.IsCoOwner( from ); - bool isFriend = isCoOwner || m_House.IsFriend( from ); - - if ( isCombatRestricted ) - isFriend = isCoOwner = isOwner = false; - - if ( !isFriend || !from.Alive ) - return; - - Item sign = m_House.Sign; - - if ( sign == null || from.Map != sign.Map || !from.InRange( sign.GetWorldLocation(), 18 ) ) - return; - - switch ( info.ButtonID ) - { - case 1: // Rename sign - { - from.Prompt = new RenamePrompt( m_House ); - from.SendLocalizedMessage( 501302 ); // What dost thou wish the sign to say? - - break; - } - case 2: // List of co-owners - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseListGump( 1011275, m_House.CoOwners, m_House, false ) ); - - break; - } - case 3: // Add co-owner - { - if ( isOwner ) - { - from.SendLocalizedMessage( 501328 ); // Target the person you wish to name a co-owner of your household. - from.Target = new CoOwnerTarget( true, m_House ); - } - else - { - from.SendLocalizedMessage( 501327 ); // Only the house owner may add Co-owners. - } - - break; - } - case 4: // Remove co-owner - { - if ( isOwner ) - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseRemoveGump( 1011274, m_House.CoOwners, m_House, false ) ); - } - else - { - from.SendLocalizedMessage( 501329 ); // Only the house owner may remove co-owners. - } - - break; - } - case 5: // Clear co-owners - { - if ( isOwner ) - { - m_House.CoOwners?.Clear(); - - from.SendLocalizedMessage( 501333 ); // All co-owners have been removed from this house. - } - else - { - from.SendLocalizedMessage( 501330 ); // Only the house owner may remove co-owners. - } - - break; - } - case 6: // List friends - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseListGump( 1011273, m_House.Friends, m_House, false ) ); - - break; - } - case 7: // Add friend - { - if ( isCoOwner ) - { - from.SendLocalizedMessage( 501317 ); // Target the person you wish to name a friend of your household. - from.Target = new HouseFriendTarget( true, m_House ); - } - else - { - from.SendLocalizedMessage( 501316 ); // Only the house owner may add friends. - } - - break; - } - case 8: // Remove friend - { - if ( isCoOwner ) - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseRemoveGump( 1011272, m_House.Friends, m_House, false ) ); - } - else - { - from.SendLocalizedMessage( 501318 ); // Only the house owner may remove friends. - } - - break; - } - case 9: // Clear friends - { - if ( isCoOwner ) - { - m_House.Friends?.Clear(); - - from.SendLocalizedMessage( 501332 ); // All friends have been removed from this house. - } - else - { - from.SendLocalizedMessage( 501319 ); // Only the house owner may remove friends. - } - - break; - } - case 10: // Ban - { - from.SendLocalizedMessage( 501325 ); // Target the individual to ban from this house. - from.Target = new HouseBanTarget( true, m_House ); - - break; - } - case 11: // Eject - { - from.SendLocalizedMessage( 501326 ); // Target the individual to eject from this house. - from.Target = new HouseKickTarget( m_House ); - - break; - } - case 12: // List bans - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseListGump( 1011271, m_House.Bans, m_House, true ) ); - - break; - } - case 13: // Remove ban - { - from.CloseGump( typeof( HouseGump ) ); - from.CloseGump( typeof( HouseListGump ) ); - from.CloseGump( typeof( HouseRemoveGump ) ); - from.SendGump( new HouseRemoveGump( 1011269, m_House.Bans, m_House, true ) ); - - break; - } - case 14: // Transfer ownership - { - if ( isOwner ) - { - from.SendLocalizedMessage( 501309 ); // Target the person to whom you wish to give this house. - from.Target = new HouseOwnerTarget( m_House ); - } - else - { - from.SendLocalizedMessage( 501310 ); // Only the house owner may do this. - } - - break; - } - case 15: // Demolish house - { - if ( isOwner ) - { - if ( !Guilds.Guild.NewGuildSystem && m_House.FindGuildstone() != null ) - { - from.SendLocalizedMessage( 501389 ); // You cannot redeed a house with a guildstone inside. - } - else - { - from.CloseGump( typeof( HouseDemolishGump ) ); - from.SendGump( new HouseDemolishGump( from, m_House ) ); - } - } - else - { - from.SendLocalizedMessage( 501320 ); // Only the house owner may do this. - } - - break; - } - case 16: // Change locks - { - if ( m_House.Public ) - { - from.SendLocalizedMessage( 501669 );// Public houses are always unlocked. - } - else - { - if ( isOwner ) - { - m_House.RemoveKeys( from ); - m_House.ChangeLocks( from ); - - from.SendLocalizedMessage( 501306 ); // The locks on your front door have been changed, and new master keys have been placed in your bank and your backpack. - } - else - { - from.SendLocalizedMessage( 501303 ); // Only the house owner may change the house locks. - } - } - - break; - } - case 17: // Declare public/private - { - if ( isOwner ) - { - if ( m_House.Public && m_House.PlayerVendors.Count > 0 ) - { - from.SendLocalizedMessage( 501887 ); // You have vendors working out of this building. It cannot be declared private until there are no vendors in place. - break; - } - - m_House.Public = !m_House.Public; - if ( !m_House.Public ) - { - m_House.ChangeLocks( from ); - - from.SendLocalizedMessage( 501888 ); // This house is now private. - from.SendLocalizedMessage( 501306 ); // The locks on your front door have been changed, and new master keys have been placed in your bank and your backpack. - } - else - { - m_House.RemoveKeys( from ); - m_House.RemoveLocks(); - from.SendLocalizedMessage( 501886 );//This house is now public. Friends of the house my now have vendors working out of this building. - } - } - else - { - from.SendLocalizedMessage( 501307 ); // Only the house owner may do this. - } - - break; - } - case 18: // Change type - { - if ( isOwner ) - { - if ( m_House.Public && info.Switches.Length > 0 ) - { - int index = info.Switches[0] - 1; - - if ( index >= 0 && index < 53 ) - m_House.ChangeSignType( 2980 + (index * 2) ); - } - } - else - { - from.SendLocalizedMessage( 501307 ); // Only the house owner may do this. - } - - break; - } - } - } - } + AddHtmlLocalized(20, 260, 400, 20, 1018032, false, false); // This house is properly placed. + AddHtmlLocalized(20, 280, 400, 20, 1018035, false, false); // This house is of modern design. + + if (m_House.Public) + { + // TODO: Validate exact placement + AddHtmlLocalized(20, 305, 275, 20, 1011241, false, false); // Number of visits this building has had + AddHtml(320, 305, 50, 20, m_House.Visits.ToString(), false, false); + } + + // Friends page + AddPage(2); + + AddHtmlLocalized(45, 130, 150, 20, 1011266, false, false); // List of co-owners + AddButton(20, 130, 2714, 2715, 2, GumpButtonType.Reply, 0); + + AddHtmlLocalized(45, 150, 150, 20, 1011267, false, false); // Add a co-owner + AddButton(20, 150, 2714, 2715, 3, GumpButtonType.Reply, 0); + + AddHtmlLocalized(45, 170, 150, 20, 1018036, false, false); // Remove a co-owner + AddButton(20, 170, 2714, 2715, 4, GumpButtonType.Reply, 0); + + AddHtmlLocalized(45, 190, 150, 20, 1011268, false, false); // Clear co-owner list + AddButton(20, 190, 2714, 2715, 5, GumpButtonType.Reply, 0); + + AddHtmlLocalized(225, 130, 155, 20, 1011243, false, false); // List of Friends + AddButton(200, 130, 2714, 2715, 6, GumpButtonType.Reply, 0); + + AddHtmlLocalized(225, 150, 155, 20, 1011244, false, false); // Add a Friend + AddButton(200, 150, 2714, 2715, 7, GumpButtonType.Reply, 0); + + AddHtmlLocalized(225, 170, 155, 20, 1018037, false, false); // Remove a Friend + AddButton(200, 170, 2714, 2715, 8, GumpButtonType.Reply, 0); + + AddHtmlLocalized(225, 190, 155, 20, 1011245, false, false); // Clear Friends list + AddButton(200, 190, 2714, 2715, 9, GumpButtonType.Reply, 0); + + AddHtmlLocalized(120, 215, 280, 20, 1011258, false, false); // Ban someone from the house + AddButton(95, 215, 2714, 2715, 10, GumpButtonType.Reply, 0); + + AddHtmlLocalized(120, 235, 280, 20, 1011259, false, false); // Eject someone from the house + AddButton(95, 235, 2714, 2715, 11, GumpButtonType.Reply, 0); + + AddHtmlLocalized(120, 255, 280, 20, 1011260, false, false); // View a list of banned people + AddButton(95, 255, 2714, 2715, 12, GumpButtonType.Reply, 0); + + AddHtmlLocalized(120, 275, 280, 20, 1011261, false, false); // Lift a ban + AddButton(95, 275, 2714, 2715, 13, GumpButtonType.Reply, 0); + + // Options page + AddPage(3); + + AddHtmlLocalized(45, 150, 355, 30, 1011248, false, false); // Transfer ownership of the house + AddButton(20, 150, 2714, 2715, 14, GumpButtonType.Reply, 0); + + AddHtmlLocalized(45, 180, 355, 30, 1011249, false, false); // Demolish house and get deed back + AddButton(20, 180, 2714, 2715, 15, GumpButtonType.Reply, 0); + + if (!m_House.Public) + { + AddHtmlLocalized(45, 210, 355, 30, 1011247, false, false); // Change the house locks + AddButton(20, 210, 2714, 2715, 16, GumpButtonType.Reply, 0); + + AddHtmlLocalized(45, 240, 350, 90, 1011253, false, + false); // Declare this building to be public. This will make your front door unlockable. + AddButton(20, 240, 2714, 2715, 17, GumpButtonType.Reply, 0); + } + else + { + //AddHtmlLocalized( 45, 280, 350, 30, 1011250, false, false ); // Change the sign type + AddHtmlLocalized(45, 210, 350, 30, 1011250, false, false); // Change the sign type + AddButton(20, 210, 2714, 2715, 0, GumpButtonType.Page, 4); + + AddHtmlLocalized(45, 240, 350, 30, 1011252, false, false); // Declare this building to be private. + AddButton(20, 240, 2714, 2715, 17, GumpButtonType.Reply, 0); + + // Change the sign type + AddPage(4); + + for (int i = 0; i < 24; ++i) + { + AddRadio(53 + i / 4 * 50, 137 + i % 4 * 35, 210, 211, false, i + 1); + AddItem(60 + i / 4 * 50, 130 + i % 4 * 35, 2980 + i * 2); + } + + AddHtmlLocalized(200, 305, 129, 20, 1011254, false, false); // Guild sign choices + AddButton(350, 305, 252, 253, 0, GumpButtonType.Page, 5); + + AddHtmlLocalized(200, 340, 355, 30, 1011277, false, false); // Okay that is fine. + AddButton(350, 340, 4005, 4007, 18, GumpButtonType.Reply, 0); + + AddPage(5); + + for (int i = 0; i < 29; ++i) + { + AddRadio(53 + i / 5 * 50, 137 + i % 5 * 35, 210, 211, false, i + 25); + AddItem(60 + i / 5 * 50, 130 + i % 5 * 35, 3028 + i * 2); + } + + AddHtmlLocalized(200, 305, 129, 20, 1011255, false, false); // Shop sign choices + AddButton(350, 305, 250, 251, 0, GumpButtonType.Page, 4); + + AddHtmlLocalized(200, 340, 355, 30, 1011277, false, false); // Okay that is fine. + AddButton(350, 340, 4005, 4007, 18, GumpButtonType.Reply, 0); + } + } + + private ArrayList Wrap(string value) + { + if (value == null || (value = value.Trim()).Length <= 0) + return null; + + string[] values = value.Split(' '); + ArrayList list = new ArrayList(); + string current = ""; + + for (int i = 0; i < values.Length; ++i) + { + string val = values[i]; + + string v = current.Length == 0 ? val : current + ' ' + val; + + if (v.Length < 10) + { + current = v; + } + else if (v.Length == 10) + { + list.Add(v); + + if (list.Count == 6) + return list; + + current = ""; + } + else if (val.Length <= 10) + { + list.Add(current); + + if (list.Count == 6) + return list; + + current = val; + } + else + { + while (v.Length >= 10) + { + list.Add(v.Substring(0, 10)); + + if (list.Count == 6) + return list; + + v = v.Substring(10); + } + + current = v; + } + } + + if (current.Length > 0) + list.Add(current); + + return list; + } + + private string GetOwnerName() + { + Mobile m = m_House.Owner; + + if (m == null) + return "(unowned)"; + + string name; + + if ((name = m.Name) == null || (name = name.Trim()).Length <= 0) + name = "(no name)"; + + return name; + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_House.Deleted) + return; + + Mobile from = sender.Mobile; + + bool isCombatRestricted = m_House.IsCombatRestricted(from); + + bool isOwner = m_House.IsOwner(from); + bool isCoOwner = isOwner || m_House.IsCoOwner(from); + bool isFriend = isCoOwner || m_House.IsFriend(from); + + if (isCombatRestricted) + isFriend = isCoOwner = isOwner = false; + + if (!isFriend || !from.Alive) + return; + + Item sign = m_House.Sign; + + if (sign == null || from.Map != sign.Map || !from.InRange(sign.GetWorldLocation(), 18)) + return; + + switch (info.ButtonID) + { + case 1: // Rename sign + { + from.Prompt = new RenamePrompt(m_House); + from.SendLocalizedMessage(501302); // What dost thou wish the sign to say? + + break; + } + case 2: // List of co-owners + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseListGump(1011275, m_House.CoOwners, m_House, false)); + + break; + } + case 3: // Add co-owner + { + if (isOwner) + { + from.SendLocalizedMessage( + 501328); // Target the person you wish to name a co-owner of your household. + from.Target = new CoOwnerTarget(true, m_House); + } + else + { + from.SendLocalizedMessage(501327); // Only the house owner may add Co-owners. + } + + break; + } + case 4: // Remove co-owner + { + if (isOwner) + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseRemoveGump(1011274, m_House.CoOwners, m_House, false)); + } + else + { + from.SendLocalizedMessage(501329); // Only the house owner may remove co-owners. + } + + break; + } + case 5: // Clear co-owners + { + if (isOwner) + { + m_House.CoOwners?.Clear(); + + from.SendLocalizedMessage(501333); // All co-owners have been removed from this house. + } + else + { + from.SendLocalizedMessage(501330); // Only the house owner may remove co-owners. + } + + break; + } + case 6: // List friends + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseListGump(1011273, m_House.Friends, m_House, false)); + + break; + } + case 7: // Add friend + { + if (isCoOwner) + { + from.SendLocalizedMessage(501317); // Target the person you wish to name a friend of your household. + from.Target = new HouseFriendTarget(true, m_House); + } + else + { + from.SendLocalizedMessage(501316); // Only the house owner may add friends. + } + + break; + } + case 8: // Remove friend + { + if (isCoOwner) + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseRemoveGump(1011272, m_House.Friends, m_House, false)); + } + else + { + from.SendLocalizedMessage(501318); // Only the house owner may remove friends. + } + + break; + } + case 9: // Clear friends + { + if (isCoOwner) + { + m_House.Friends?.Clear(); + + from.SendLocalizedMessage(501332); // All friends have been removed from this house. + } + else + { + from.SendLocalizedMessage(501319); // Only the house owner may remove friends. + } + + break; + } + case 10: // Ban + { + from.SendLocalizedMessage(501325); // Target the individual to ban from this house. + from.Target = new HouseBanTarget(true, m_House); + + break; + } + case 11: // Eject + { + from.SendLocalizedMessage(501326); // Target the individual to eject from this house. + from.Target = new HouseKickTarget(m_House); + + break; + } + case 12: // List bans + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseListGump(1011271, m_House.Bans, m_House, true)); + + break; + } + case 13: // Remove ban + { + from.CloseGump(typeof(HouseGump)); + from.CloseGump(typeof(HouseListGump)); + from.CloseGump(typeof(HouseRemoveGump)); + from.SendGump(new HouseRemoveGump(1011269, m_House.Bans, m_House, true)); + + break; + } + case 14: // Transfer ownership + { + if (isOwner) + { + from.SendLocalizedMessage(501309); // Target the person to whom you wish to give this house. + from.Target = new HouseOwnerTarget(m_House); + } + else + { + from.SendLocalizedMessage(501310); // Only the house owner may do this. + } + + break; + } + case 15: // Demolish house + { + if (isOwner) + { + if (!Guild.NewGuildSystem && m_House.FindGuildstone() != null) + { + from.SendLocalizedMessage(501389); // You cannot redeed a house with a guildstone inside. + } + else + { + from.CloseGump(typeof(HouseDemolishGump)); + from.SendGump(new HouseDemolishGump(from, m_House)); + } + } + else + { + from.SendLocalizedMessage(501320); // Only the house owner may do this. + } + + break; + } + case 16: // Change locks + { + if (m_House.Public) + { + from.SendLocalizedMessage(501669); // Public houses are always unlocked. + } + else + { + if (isOwner) + { + m_House.RemoveKeys(from); + m_House.ChangeLocks(from); + + from.SendLocalizedMessage( + 501306); // The locks on your front door have been changed, and new master keys have been placed in your bank and your backpack. + } + else + { + from.SendLocalizedMessage(501303); // Only the house owner may change the house locks. + } + } + + break; + } + case 17: // Declare public/private + { + if (isOwner) + { + if (m_House.Public && m_House.PlayerVendors.Count > 0) + { + from.SendLocalizedMessage( + 501887); // You have vendors working out of this building. It cannot be declared private until there are no vendors in place. + break; + } + + m_House.Public = !m_House.Public; + if (!m_House.Public) + { + m_House.ChangeLocks(from); + + from.SendLocalizedMessage(501888); // This house is now private. + from.SendLocalizedMessage( + 501306); // The locks on your front door have been changed, and new master keys have been placed in your bank and your backpack. + } + else + { + m_House.RemoveKeys(from); + m_House.RemoveLocks(); + from.SendLocalizedMessage( + 501886); //This house is now public. Friends of the house my now have vendors working out of this building. + } + } + else + { + from.SendLocalizedMessage(501307); // Only the house owner may do this. + } + + break; + } + case 18: // Change type + { + if (isOwner) + { + if (m_House.Public && info.Switches.Length > 0) + { + int index = info.Switches[0] - 1; + + if (index >= 0 && index < 53) + m_House.ChangeSignType(2980 + index * 2); + } + } + else + { + from.SendLocalizedMessage(501307); // Only the house owner may do this. + } + + break; + } + } + } + } } namespace Server.Prompts { - public class RenamePrompt : Prompt - { - private BaseHouse m_House; + public class RenamePrompt : Prompt + { + private BaseHouse m_House; - public RenamePrompt( BaseHouse house ) - { - m_House = house; - } + public RenamePrompt(BaseHouse house) + { + m_House = house; + } - public override void OnResponse( Mobile from, string text ) - { - if ( m_House.IsFriend( from ) ) - { - if ( m_House.Sign != null ) - m_House.Sign.Name = text; + public override void OnResponse(Mobile from, string text) + { + if (m_House.IsFriend(from)) + { + if (m_House.Sign != null) + m_House.Sign.Name = text; - from.SendMessage( "Sign changed." ); - } - } - } + from.SendMessage("Sign changed."); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/HouseGumpAOS.cs b/Scripts/Gumps/HouseGumpAOS.cs index e428668cd..af244b7ca 100644 --- a/Scripts/Gumps/HouseGumpAOS.cs +++ b/Scripts/Gumps/HouseGumpAOS.cs @@ -1,1470 +1,1498 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Network; -using Server.Prompts; +using Server.Guilds; +using Server.Items; using Server.Mobiles; using Server.Multis; -using Server.Items; +using Server.Network; +using Server.Prompts; namespace Server.Gumps { - public enum HouseGumpPageAOS - { - Information, - Security, - Storage, - Customize, - Ownership, - ChangeHanger, - ChangeFoundation, - ChangeSign, - RemoveCoOwner, - ListCoOwner, - RemoveFriend, - ListFriend, - RemoveBan, - ListBan, - RemoveAccess, - ListAccess, - ChangePost, - Vendors - } - - public class HouseGumpAOS : Gump - { - private BaseHouse m_House; - private HouseGumpPageAOS m_Page; - - private const int LabelColor = 0x7FFF; - private const int SelectedColor = 0x421F; - private const int DisabledColor = 0x4210; - private const int WarningColor = 0x7E10; - - private const int LabelHue = 0x481; - private const int HighlightedLabelHue = 0x64; - - private ArrayList m_List; - - private string GetOwnerName() - { - Mobile m = m_House.Owner; - - if ( m == null || m.Deleted ) - return "(unowned)"; - - string name; - - if ( (name = m.Name) == null || (name = name.Trim()).Length <= 0 ) - name = "(no name)"; - - return name; - } - - private string GetDateTime( DateTime val ) - { - if ( val == DateTime.MinValue ) - return ""; - - return val.ToString( "yyyy'-'MM'-'dd HH':'mm':'ss" ); - } - - public void AddPageButton( int x, int y, int buttonID, int number, HouseGumpPageAOS page ) - { - bool isSelection = ( m_Page == page ); - - AddButton( x, y, isSelection ? 4006 : 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( x + 45, y, 200, 20, number, isSelection ? SelectedColor : LabelColor, false, false ); - } - - public void AddButtonLabeled( int x, int y, int buttonID, int number ) - { - AddButtonLabeled( x, y, buttonID, number, true ); - } - - public void AddButtonLabeled( int x, int y, int buttonID, int number, bool enabled ) - { - if ( enabled ) - AddButton( x, y, 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - - AddHtmlLocalized( x + 35, y, 240, 20, number, enabled ? LabelColor : DisabledColor, false, false ); - } - - public void AddList( ArrayList list, int button, bool accountOf, bool leadingStar, Mobile from ) - { - if ( list == null ) - return; - - m_List = new ArrayList( list ); - - int lastPage = 0; - int index = 0; - - for ( int i = 0; i < list.Count; ++i ) - { - int xoffset = ((index % 20) / 10) * 200; - int yoffset = (index % 10) * 20; - int page = 1 + (index / 20); - - if ( page != lastPage ) - { - if ( lastPage != 0 ) - AddButton( 40, 360, 4005, 4007, 0, GumpButtonType.Page, page ); - - AddPage( page ); - - if ( lastPage != 0 ) - AddButton( 10, 360, 4014, 4016, 0, GumpButtonType.Page, lastPage ); - - lastPage = page; - } - - - Mobile m = (Mobile)list[i]; + public enum HouseGumpPageAOS + { + Information, + Security, + Storage, + Customize, + Ownership, + ChangeHanger, + ChangeFoundation, + ChangeSign, + RemoveCoOwner, + ListCoOwner, + RemoveFriend, + ListFriend, + RemoveBan, + ListBan, + RemoveAccess, + ListAccess, + ChangePost, + Vendors + } + + public class HouseGumpAOS : Gump + { + private const int LabelColor = 0x7FFF; + private const int SelectedColor = 0x421F; + private const int DisabledColor = 0x4210; + private const int WarningColor = 0x7E10; + + private const int LabelHue = 0x481; + private const int HighlightedLabelHue = 0x64; + + private static int[] m_HangerNumbers = + { + 2968, 2970, 2972, + 2974, 2976, 2978 + }; + + private static int[] m_FoundationNumbers = Core.ML + ? new[] + { + 20, 189, 765, 65, 101, 0x2DF7, 0x2DFB, 0x3672, 0x3676 + } + : new[] + { + 20, 189, 765, 65, 101 + }; + + private static int[] m_PostNumbers = + { + 9, 29, 54, 90, 147, 169, + 177, 204, 251, 257, 263, + 298, 347, 424, 441, 466, + 514, 600, 601, 602, 603, + 660, 666, 672, 898, 970, + 974, 982 + }; + + private static List _HouseSigns = new List(); + private BaseHouse m_House; + + private ArrayList m_List; + private HouseGumpPageAOS m_Page; + + public HouseGumpAOS(HouseGumpPageAOS page, Mobile from, BaseHouse house) : base(50, 40) + { + m_House = house; + m_Page = page; + + from.CloseGump(typeof(HouseGumpAOS)); + //from.CloseGump( typeof( HouseListGump ) ); + //from.CloseGump( typeof( HouseRemoveGump ) ); + + bool isCombatRestricted = house.IsCombatRestricted(from); + + bool isOwner = house.IsOwner(from); + bool isCoOwner = isOwner || house.IsCoOwner(from); + bool isFriend = isCoOwner || house.IsFriend(from); + + if (isCombatRestricted) + isFriend = isCoOwner = isOwner = false; + + AddPage(0); + + if (isFriend || page == HouseGumpPageAOS.Vendors) + { + AddBackground(0, 0, 420, page != HouseGumpPageAOS.Vendors ? 440 : 420, 5054); + + AddImageTiled(10, 10, 400, 100, 2624); + AddAlphaRegion(10, 10, 400, 100); + + AddImageTiled(10, 120, 400, 260, 2624); + AddAlphaRegion(10, 120, 400, 260); + + AddImageTiled(10, 390, 400, page != HouseGumpPageAOS.Vendors ? 40 : 20, 2624); + AddAlphaRegion(10, 390, 400, page != HouseGumpPageAOS.Vendors ? 40 : 20); + + AddButtonLabeled(250, page != HouseGumpPageAOS.Vendors ? 410 : 390, 0, 1060675); // CLOSE + } + + AddImage(10, 10, 100); + + if (m_House.Sign != null) + { + ArrayList lines = Wrap(m_House.Sign.GetName()); + + if (lines != null) + for (int i = 0, y = (114 - lines.Count * 14) / 2; i < lines.Count; ++i, y += 14) + { + string s = (string)lines[i]; + + AddLabel(10 + (160 - s.Length * 8) / 2, y, 0, s); + } + } + + if (page == HouseGumpPageAOS.Vendors) + { + AddHtmlLocalized(10, 120, 400, 20, 1062428, LabelColor, false, false); //
SHOPS
+ + AddList(house.AvailableVendorsFor(from), 1, false, false, from); + return; + } + + if (!isFriend) + return; + + if (house.Public) + { + AddButtonLabeled(10, 390, GetButtonID(0, 0), 1060674); // Banish + AddButtonLabeled(10, 410, GetButtonID(0, 1), 1011261); // Lift a Ban + } + else + { + AddButtonLabeled(10, 390, GetButtonID(0, 2), 1060676); // Grant Access + AddButtonLabeled(10, 410, GetButtonID(0, 3), 1060677); // Revoke Access + } + + AddPageButton(150, 10, GetButtonID(1, 0), 1060668, HouseGumpPageAOS.Information); + AddPageButton(150, 30, GetButtonID(1, 1), 1060669, HouseGumpPageAOS.Security); + AddPageButton(150, 50, GetButtonID(1, 2), 1060670, HouseGumpPageAOS.Storage); + AddPageButton(150, 70, GetButtonID(1, 3), 1060671, HouseGumpPageAOS.Customize); + AddPageButton(150, 90, GetButtonID(1, 4), 1060672, HouseGumpPageAOS.Ownership); + + switch (page) + { + case HouseGumpPageAOS.Information: + { + AddHtmlLocalized(20, 130, 200, 20, 1011242, LabelColor, false, false); // Owned By: + AddLabel(210, 130, LabelHue, GetOwnerName()); + + AddHtmlLocalized(20, 170, 380, 20, 1018032, SelectedColor, false, + false); // This house is properly placed. + AddHtmlLocalized(20, 190, 380, 20, 1018035, SelectedColor, false, + false); // This house is of modern design. + AddHtmlLocalized(20, 210, 380, 20, house is HouseFoundation ? 1060681 : 1060680, SelectedColor, false, + false); // This is a (pre | custom)-built house. + AddHtmlLocalized(20, 230, 380, 20, house.Public ? 1060678 : 1060679, SelectedColor, false, + false); // This house is (private | open to the public). + + switch (house.DecayType) + { + case DecayType.Ageless: + case DecayType.AutoRefresh: + { + AddHtmlLocalized(20, 250, 380, 20, 1062209, SelectedColor, false, + false); // This house is Automatically refreshed. + break; + } + case DecayType.ManualRefresh: + { + AddHtmlLocalized(20, 250, 380, 20, 1062208, SelectedColor, false, + false); // This house is Grandfathered. + break; + } + case DecayType.Condemned: + { + AddHtmlLocalized(20, 250, 380, 20, 1062207, WarningColor, false, + false); // This house is Condemned. + break; + } + } + + AddHtmlLocalized(20, 290, 200, 20, 1060692, SelectedColor, false, false); // Built On: + AddLabel(250, 290, LabelHue, GetDateTime(house.BuiltOn)); + + AddHtmlLocalized(20, 310, 200, 20, 1060693, SelectedColor, false, false); // Last Traded: + AddLabel(250, 310, LabelHue, GetDateTime(house.LastTraded)); + + AddHtmlLocalized(20, 330, 200, 20, 1061793, SelectedColor, false, false); // House Value + AddLabel(250, 330, LabelHue, house.Price.ToString()); + + AddHtmlLocalized(20, 360, 300, 20, 1011241, SelectedColor, false, + false); // Number of visits this building has had: + AddLabel(350, 360, LabelHue, house.Visits.ToString()); + + break; + } + case HouseGumpPageAOS.Security: + { + AddButtonLabeled(10, 130, GetButtonID(3, 0), 1011266, isCoOwner); // View Co-Owner List + AddButtonLabeled(10, 150, GetButtonID(3, 1), 1011267, isOwner); // Add a Co-Owner + AddButtonLabeled(10, 170, GetButtonID(3, 2), 1018036, isOwner); // Remove a Co-Owner + AddButtonLabeled(10, 190, GetButtonID(3, 3), 1011268, isOwner); // Clear Co-Owner List + + AddButtonLabeled(10, 220, GetButtonID(3, 4), 1011243); // View Friends List + AddButtonLabeled(10, 240, GetButtonID(3, 5), 1011244, isCoOwner); // Add a Friend + AddButtonLabeled(10, 260, GetButtonID(3, 6), 1018037, isCoOwner); // Remove a Friend + AddButtonLabeled(10, 280, GetButtonID(3, 7), 1011245, isCoOwner); // Clear Friend List + + if (house.Public) + { + AddButtonLabeled(10, 310, GetButtonID(3, 8), 1011260); // View Ban List + AddButtonLabeled(10, 330, GetButtonID(3, 9), 1060698); // Clear Ban List + + AddButtonLabeled(210, 130, GetButtonID(3, 12), 1060695, isOwner); // Change to Private + + AddHtmlLocalized(245, 150, 240, 20, 1060694, SelectedColor, false, false); // Change to Public + } + else + { + AddButtonLabeled(10, 310, GetButtonID(3, 10), 1060699); // View Access List + AddButtonLabeled(10, 330, GetButtonID(3, 11), 1060700); // Clear Access List + + AddHtmlLocalized(245, 130, 240, 20, 1060695, SelectedColor, false, false); // Change to Private + + AddButtonLabeled(210, 150, GetButtonID(3, 13), 1060694, isOwner); // Change to Public + } + + break; + } + case HouseGumpPageAOS.Storage: + { + AddHtmlLocalized(10, 130, 400, 20, 1060682, LabelColor, false, + false); //
HOUSE STORAGE SUMMARY
+ + // This is not as OSI; storage changes not yet implemented + + /*AddHtmlLocalized( 10, 170, 275, 20, 1011237, LabelColor, false, false ); // Number of locked down items: + AddLabel( 310, 170, LabelHue, m_House.LockDownCount.ToString() ); + + AddHtmlLocalized( 10, 190, 275, 20, 1011238, LabelColor, false, false ); // Maximum locked down items: + AddLabel( 310, 190, LabelHue, m_House.MaxLockDowns.ToString() ); + + AddHtmlLocalized( 10, 210, 275, 20, 1011239, LabelColor, false, false ); // Number of secure containers: + AddLabel( 310, 210, LabelHue, m_House.SecureCount.ToString() ); + + AddHtmlLocalized( 10, 230, 275, 20, 1011240, LabelColor, false, false ); // Maximum number of secure containers: + AddLabel( 310, 230, LabelHue, m_House.MaxSecures.ToString() );*/ + + int fromSecures, fromVendors, fromLockdowns, fromMovingCrate; + + int maxSecures = house.GetAosMaxSecures(); + int curSecures = house.GetAosCurSecures(out fromSecures, out fromVendors, out fromLockdowns, + out fromMovingCrate); + + int maxLockdowns = house.GetAosMaxLockdowns(); + int curLockdowns = house.GetAosCurLockdowns(); + + int bonusStorage = (int)(house.BonusStorageScalar * 100 - 100); + + if (bonusStorage > 0) + { + AddHtmlLocalized(10, 150, 300, 20, 1072519, LabelColor, false, false); // Increased Storage + AddLabel(310, 150, LabelHue, $"{bonusStorage}%"); + } + + AddHtmlLocalized(10, 170, 300, 20, 1060683, LabelColor, false, false); // Maximum Secure Storage + AddLabel(310, 170, LabelHue, maxSecures.ToString()); + + AddHtmlLocalized(10, 190, 300, 20, 1060685, LabelColor, false, false); // Used by Moving Crate + AddLabel(310, 190, LabelHue, fromMovingCrate.ToString()); + + AddHtmlLocalized(10, 210, 300, 20, 1060686, LabelColor, false, false); // Used by Lockdowns + AddLabel(310, 210, LabelHue, fromLockdowns.ToString()); + + if (BaseHouse.NewVendorSystem) + { + AddHtmlLocalized(10, 230, 300, 20, 1060688, LabelColor, false, false); // Used by Secure Containers + AddLabel(310, 230, LabelHue, fromSecures.ToString()); + + AddHtmlLocalized(10, 250, 300, 20, 1060689, LabelColor, false, false); // Available Storage + AddLabel(310, 250, LabelHue, Math.Max(maxSecures - curSecures, 0).ToString()); + + AddHtmlLocalized(10, 290, 300, 20, 1060690, LabelColor, false, false); // Maximum Lockdowns + AddLabel(310, 290, LabelHue, maxLockdowns.ToString()); + + AddHtmlLocalized(10, 310, 300, 20, 1060691, LabelColor, false, false); // Available Lockdowns + AddLabel(310, 310, LabelHue, Math.Max(maxLockdowns - curLockdowns, 0).ToString()); + + int maxVendors = house.GetNewVendorSystemMaxVendors(); + int vendors = house.PlayerVendors.Count + house.VendorRentalContracts.Count; + + AddHtmlLocalized(10, 350, 300, 20, 1062391, LabelColor, false, false); // Vendor Count + AddLabel(310, 350, LabelHue, vendors + " / " + maxVendors); + } + else + { + AddHtmlLocalized(10, 230, 300, 20, 1060687, LabelColor, false, false); // Used by Vendors + AddLabel(310, 230, LabelHue, fromVendors.ToString()); + + AddHtmlLocalized(10, 250, 300, 20, 1060688, LabelColor, false, false); // Used by Secure Containers + AddLabel(310, 250, LabelHue, fromSecures.ToString()); + + AddHtmlLocalized(10, 270, 300, 20, 1060689, LabelColor, false, false); // Available Storage + AddLabel(310, 270, LabelHue, Math.Max(maxSecures - curSecures, 0).ToString()); + + AddHtmlLocalized(10, 330, 300, 20, 1060690, LabelColor, false, false); // Maximum Lockdowns + AddLabel(310, 330, LabelHue, maxLockdowns.ToString()); + + AddHtmlLocalized(10, 350, 300, 20, 1060691, LabelColor, false, false); // Available Lockdowns + AddLabel(310, 350, LabelHue, Math.Max(maxLockdowns - curLockdowns, 0).ToString()); + } + + break; + } + case HouseGumpPageAOS.Customize: + { + bool isCustomizable = isOwner && house is HouseFoundation; + + AddButtonLabeled(10, 120, GetButtonID(5, 0), 1060759, + isOwner && !isCustomizable && house.ConvertEntry != null); // Convert Into Customizable House + AddButtonLabeled(10, 160, GetButtonID(5, 1), 1060765, isOwner && isCustomizable); // Customize This House + AddButtonLabeled(10, 180, GetButtonID(5, 2), 1060760, + isOwner && house.MovingCrate != null); // Relocate Moving Crate + AddButtonLabeled(10, 210, GetButtonID(5, 3), 1060761, isOwner && house.Public); // Change House Sign + AddButtonLabeled(10, 230, GetButtonID(5, 4), 1060762, + isOwner && isCustomizable); // Change House Sign Hanger + AddButtonLabeled(10, 250, GetButtonID(5, 5), 1060763, + isOwner && isCustomizable && ((HouseFoundation)house).Signpost != null); // Change Signpost + AddButtonLabeled(10, 280, GetButtonID(5, 6), 1062004, + isOwner && isCustomizable); // Change Foundation Style + AddButtonLabeled(10, 310, GetButtonID(5, 7), 1060764, isCoOwner); // Rename House + + break; + } + case HouseGumpPageAOS.Ownership: + { + AddButtonLabeled(10, 130, GetButtonID(6, 0), 1061794, + isOwner && house.MovingCrate == null && house.InternalizedVendors.Count == 0); // Demolish House + AddButtonLabeled(10, 150, GetButtonID(6, 1), 1061797, isOwner); // Trade House + AddButtonLabeled(10, 190, GetButtonID(6, 2), 1061798, false); // Make Primary + + break; + } + case HouseGumpPageAOS.ChangeHanger: + { + for (int i = 0; i < m_HangerNumbers.Length; ++i) + { + int x = 50 + i % 3 * 100; + int y = 180 + i / 3 * 80; + + AddButton(x, y, 4005, 4007, GetButtonID(7, i), GumpButtonType.Reply, 0); + AddItem(x + 20, y, m_HangerNumbers[i]); + } + + break; + } + case HouseGumpPageAOS.ChangeFoundation: + { + for (int i = 0; i < m_FoundationNumbers.Length; ++i) + { + int x = 15 + i % 5 * 80; + int y = 180 + i / 5 * 100; + + AddButton(x, y, 4005, 4007, GetButtonID(8, i), GumpButtonType.Reply, 0); + AddItem(x + 25, y, m_FoundationNumbers[i]); + } + + break; + } + case HouseGumpPageAOS.ChangeSign: + { + int index = 0; + + if (_HouseSigns.Count == 0) + { + // Add standard signs + for (int i = 0; i < 54; ++i) _HouseSigns.Add(2980 + i * 2); + + // Add library and beekeeper signs ( ML ) + _HouseSigns.Add(2966); + _HouseSigns.Add(3140); + } + + int signsPerPage = Core.ML ? 24 : 18; + int totalSigns = Core.ML ? 56 : 54; + int pages = (int)Math.Ceiling((double)totalSigns / signsPerPage); + + for (int i = 0; i < pages; ++i) + { + AddPage(i + 1); + + AddButton(10, 360, 4005, 4007, 0, GumpButtonType.Page, (i + 1) % pages + 1); + + for (int j = 0; j < signsPerPage && totalSigns - signsPerPage * i - j > 0; ++j) + { + int x = 30 + j % 6 * 60; + int y = 130 + j / 6 * 60; + + AddButton(x, y, 4005, 4007, GetButtonID(9, index), GumpButtonType.Reply, 0); + AddItem(x + 20, y, _HouseSigns[index++]); + } + } + + break; + } + case HouseGumpPageAOS.RemoveCoOwner: + { + AddHtmlLocalized(10, 120, 400, 20, 1060730, LabelColor, false, false); //
CO-OWNER LIST
+ AddList(house.CoOwners, 10, false, true, from); + break; + } + case HouseGumpPageAOS.ListCoOwner: + { + AddHtmlLocalized(10, 120, 400, 20, 1060730, LabelColor, false, false); //
CO-OWNER LIST
+ AddList(house.CoOwners, -1, false, true, from); + break; + } + case HouseGumpPageAOS.RemoveFriend: + { + AddHtmlLocalized(10, 120, 400, 20, 1060731, LabelColor, false, false); //
FRIENDS LIST
+ AddList(house.Friends, 11, false, true, from); + break; + } + case HouseGumpPageAOS.ListFriend: + { + AddHtmlLocalized(10, 120, 400, 20, 1060731, LabelColor, false, false); //
FRIENDS LIST
+ AddList(house.Friends, -1, false, true, from); + break; + } + case HouseGumpPageAOS.RemoveBan: + { + AddHtmlLocalized(10, 120, 400, 20, 1060733, LabelColor, false, false); //
BAN LIST
+ AddList(house.Bans, 12, true, true, from); + break; + } + case HouseGumpPageAOS.ListBan: + { + AddHtmlLocalized(10, 120, 400, 20, 1060733, LabelColor, false, false); //
BAN LIST
+ AddList(house.Bans, -1, true, true, from); + break; + } + case HouseGumpPageAOS.RemoveAccess: + { + AddHtmlLocalized(10, 120, 400, 20, 1060732, LabelColor, false, false); //
ACCESS LIST
+ AddList(house.Access, 13, false, true, from); + break; + } + case HouseGumpPageAOS.ListAccess: + { + AddHtmlLocalized(10, 120, 400, 20, 1060732, LabelColor, false, false); //
ACCESS LIST
+ AddList(house.Access, -1, false, true, from); + break; + } + case HouseGumpPageAOS.ChangePost: + { + int index = 0; + + for (int i = 0; i < 2; ++i) + { + AddPage(i + 1); + + AddButton(10, 360, 4005, 4007, 0, GumpButtonType.Page, (i + 1) % 2 + 1); + + for (int j = 0; j < 16 && index < m_PostNumbers.Length; ++j) + { + int x = 15 + j % 8 * 50; + int y = 130 + j / 8 * 110; + + AddButton(x, y, 4005, 4007, GetButtonID(14, index), GumpButtonType.Reply, 0); + AddItem(x + 10, y, m_PostNumbers[index++]); + } + } + + break; + } + } + } + + private string GetOwnerName() + { + Mobile m = m_House.Owner; + + if (m == null || m.Deleted) + return "(unowned)"; + + string name; + + if ((name = m.Name) == null || (name = name.Trim()).Length <= 0) + name = "(no name)"; + + return name; + } + + private string GetDateTime(DateTime val) + { + if (val == DateTime.MinValue) + return ""; + + return val.ToString("yyyy'-'MM'-'dd HH':'mm':'ss"); + } + + public void AddPageButton(int x, int y, int buttonID, int number, HouseGumpPageAOS page) + { + bool isSelection = m_Page == page; + + AddButton(x, y, isSelection ? 4006 : 4005, 4007, buttonID, GumpButtonType.Reply, 0); + AddHtmlLocalized(x + 45, y, 200, 20, number, isSelection ? SelectedColor : LabelColor, false, false); + } + + public void AddButtonLabeled(int x, int y, int buttonID, int number) + { + AddButtonLabeled(x, y, buttonID, number, true); + } + + public void AddButtonLabeled(int x, int y, int buttonID, int number, bool enabled) + { + if (enabled) + AddButton(x, y, 4005, 4007, buttonID, GumpButtonType.Reply, 0); + + AddHtmlLocalized(x + 35, y, 240, 20, number, enabled ? LabelColor : DisabledColor, false, false); + } + + public void AddList(ArrayList list, int button, bool accountOf, bool leadingStar, Mobile from) + { + if (list == null) + return; + + m_List = new ArrayList(list); + + int lastPage = 0; + int index = 0; + + for (int i = 0; i < list.Count; ++i) + { + int xoffset = index % 20 / 10 * 200; + int yoffset = index % 10 * 20; + int page = 1 + index / 20; + + if (page != lastPage) + { + if (lastPage != 0) + AddButton(40, 360, 4005, 4007, 0, GumpButtonType.Page, page); - string name; - int labelHue = LabelHue; + AddPage(page); - if ( m is PlayerVendor vendor ) - { - name = vendor.ShopName; + if (lastPage != 0) + AddButton(10, 360, 4014, 4016, 0, GumpButtonType.Page, lastPage); - if ( vendor.IsOwner( from ) ) - labelHue = HighlightedLabelHue; - } - else if ( m != null ) - { - name = m.Name; - } - else - { - continue; - } + lastPage = page; + } - if ( (name = name.Trim()).Length <= 0 ) - continue; - if ( button != -1 ) - AddButton( 10 + xoffset, 150 + yoffset, 4005, 4007, GetButtonID( button, i ), GumpButtonType.Reply, 0 ); + Mobile m = (Mobile)list[i]; - if ( accountOf && m.Player && m.Account != null ) - name = "Account of " + name; + string name; + int labelHue = LabelHue; - if ( leadingStar ) - name = "* " + name; + if (m is PlayerVendor vendor) + { + name = vendor.ShopName; - AddLabel( button > 0 ? 45 + xoffset : 10 + xoffset, 150 + yoffset, labelHue, name ); - ++index; - } - } + if (vendor.IsOwner(from)) + labelHue = HighlightedLabelHue; + } + else if (m != null) + { + name = m.Name; + } + else + { + continue; + } - public int GetButtonID( int type, int index ) - { - return 1 + (index * 15) + type; - } - - private static int[] m_HangerNumbers = { - 2968, 2970, 2972, - 2974, 2976, 2978 - }; - - private static int[] m_FoundationNumbers = (Core.ML ? new[] - { - 20, 189, 765, 65, 101, 0x2DF7, 0x2DFB, 0x3672, 0x3676 - }: - new[] - { - 20, 189, 765, 65, 101 - }); - - private static int[] m_PostNumbers = { - 9, 29, 54, 90, 147, 169, - 177, 204, 251, 257, 263, - 298, 347, 424, 441, 466, - 514, 600, 601, 602, 603, - 660, 666, 672, 898, 970, - 974, 982 - }; - - private static List _HouseSigns = new List(); - - public HouseGumpAOS( HouseGumpPageAOS page, Mobile from, BaseHouse house ) : base( 50, 40 ) - { - m_House = house; - m_Page = page; - - from.CloseGump( typeof( HouseGumpAOS ) ); - //from.CloseGump( typeof( HouseListGump ) ); - //from.CloseGump( typeof( HouseRemoveGump ) ); - - bool isCombatRestricted = house.IsCombatRestricted( from ); - - bool isOwner = house.IsOwner( from ); - bool isCoOwner = isOwner || house.IsCoOwner( from ); - bool isFriend = isCoOwner || house.IsFriend( from ); - - if ( isCombatRestricted ) - isFriend = isCoOwner = isOwner = false; - - AddPage( 0 ); - - if ( isFriend || page == HouseGumpPageAOS.Vendors ) - { - AddBackground( 0, 0, 420, page != HouseGumpPageAOS.Vendors ? 440 : 420, 5054 ); - - AddImageTiled( 10, 10, 400, 100, 2624 ); - AddAlphaRegion( 10, 10, 400, 100 ); - - AddImageTiled( 10, 120, 400, 260, 2624 ); - AddAlphaRegion( 10, 120, 400, 260 ); - - AddImageTiled( 10, 390, 400, page != HouseGumpPageAOS.Vendors ? 40 : 20, 2624 ); - AddAlphaRegion( 10, 390, 400, page != HouseGumpPageAOS.Vendors ? 40 : 20 ); - - AddButtonLabeled( 250, page != HouseGumpPageAOS.Vendors ? 410 : 390, 0, 1060675 ); // CLOSE - } - - AddImage( 10, 10, 100 ); - - if ( m_House.Sign != null ) - { - ArrayList lines = Wrap( m_House.Sign.GetName() ); - - if ( lines != null ) - { - for ( int i = 0, y = (114 - (lines.Count * 14)) / 2; i < lines.Count; ++i, y += 14 ) - { - string s = (string)lines[i]; - - AddLabel( 10 + ((160 - (s.Length * 8)) / 2), y, 0, s ); - } - } - } - - if ( page == HouseGumpPageAOS.Vendors ) - { - AddHtmlLocalized( 10, 120, 400, 20, 1062428, LabelColor, false, false ); //
SHOPS
- - AddList( house.AvailableVendorsFor( from ), 1, false, false, from ); - return; - } - - if ( !isFriend ) - return; - - if ( house.Public ) - { - AddButtonLabeled( 10, 390, GetButtonID( 0, 0 ), 1060674 ); // Banish - AddButtonLabeled( 10, 410, GetButtonID( 0, 1 ), 1011261 ); // Lift a Ban - } - else - { - AddButtonLabeled( 10, 390, GetButtonID( 0, 2 ), 1060676 ); // Grant Access - AddButtonLabeled( 10, 410, GetButtonID( 0, 3 ), 1060677 ); // Revoke Access - } - - AddPageButton( 150, 10, GetButtonID( 1, 0 ), 1060668, HouseGumpPageAOS.Information ); - AddPageButton( 150, 30, GetButtonID( 1, 1 ), 1060669, HouseGumpPageAOS.Security ); - AddPageButton( 150, 50, GetButtonID( 1, 2 ), 1060670, HouseGumpPageAOS.Storage ); - AddPageButton( 150, 70, GetButtonID( 1, 3 ), 1060671, HouseGumpPageAOS.Customize ); - AddPageButton( 150, 90, GetButtonID( 1, 4 ), 1060672, HouseGumpPageAOS.Ownership ); - - switch ( page ) - { - case HouseGumpPageAOS.Information: - { - AddHtmlLocalized( 20, 130, 200, 20, 1011242, LabelColor, false, false ); // Owned By: - AddLabel( 210, 130, LabelHue, GetOwnerName() ); - - AddHtmlLocalized( 20, 170, 380, 20, 1018032, SelectedColor, false, false ); // This house is properly placed. - AddHtmlLocalized( 20, 190, 380, 20, 1018035, SelectedColor, false, false ); // This house is of modern design. - AddHtmlLocalized( 20, 210, 380, 20, (house is HouseFoundation) ? 1060681 : 1060680, SelectedColor, false, false ); // This is a (pre | custom)-built house. - AddHtmlLocalized( 20, 230, 380, 20, house.Public ? 1060678 : 1060679, SelectedColor, false, false ); // This house is (private | open to the public). - - switch ( house.DecayType ) - { - case DecayType.Ageless: - case DecayType.AutoRefresh: - { - AddHtmlLocalized( 20, 250, 380, 20, 1062209, SelectedColor, false, false ); // This house is Automatically refreshed. - break; - } - case DecayType.ManualRefresh: - { - AddHtmlLocalized( 20, 250, 380, 20, 1062208, SelectedColor, false, false ); // This house is Grandfathered. - break; - } - case DecayType.Condemned: - { - AddHtmlLocalized( 20, 250, 380, 20, 1062207, WarningColor, false, false ); // This house is Condemned. - break; - } - } - - AddHtmlLocalized( 20, 290, 200, 20, 1060692, SelectedColor, false, false ); // Built On: - AddLabel( 250, 290, LabelHue, GetDateTime( house.BuiltOn ) ); - - AddHtmlLocalized( 20, 310, 200, 20, 1060693, SelectedColor, false, false ); // Last Traded: - AddLabel( 250, 310, LabelHue, GetDateTime( house.LastTraded ) ); - - AddHtmlLocalized( 20, 330, 200, 20, 1061793, SelectedColor, false, false ); // House Value - AddLabel( 250, 330, LabelHue, house.Price.ToString() ); - - AddHtmlLocalized( 20, 360, 300, 20, 1011241, SelectedColor, false, false ); // Number of visits this building has had: - AddLabel( 350, 360, LabelHue, house.Visits.ToString() ); - - break; - } - case HouseGumpPageAOS.Security: - { - AddButtonLabeled( 10, 130, GetButtonID( 3, 0 ), 1011266, isCoOwner ); // View Co-Owner List - AddButtonLabeled( 10, 150, GetButtonID( 3, 1 ), 1011267, isOwner ); // Add a Co-Owner - AddButtonLabeled( 10, 170, GetButtonID( 3, 2 ), 1018036, isOwner ); // Remove a Co-Owner - AddButtonLabeled( 10, 190, GetButtonID( 3, 3 ), 1011268, isOwner ); // Clear Co-Owner List - - AddButtonLabeled( 10, 220, GetButtonID( 3, 4 ), 1011243 ); // View Friends List - AddButtonLabeled( 10, 240, GetButtonID( 3, 5 ), 1011244, isCoOwner ); // Add a Friend - AddButtonLabeled( 10, 260, GetButtonID( 3, 6 ), 1018037, isCoOwner ); // Remove a Friend - AddButtonLabeled( 10, 280, GetButtonID( 3, 7 ), 1011245, isCoOwner ); // Clear Friend List - - if ( house.Public ) - { - AddButtonLabeled( 10, 310, GetButtonID( 3, 8 ), 1011260 ); // View Ban List - AddButtonLabeled( 10, 330, GetButtonID( 3, 9 ), 1060698 ); // Clear Ban List - - AddButtonLabeled( 210, 130, GetButtonID( 3, 12 ), 1060695, isOwner ); // Change to Private - - AddHtmlLocalized( 245, 150, 240, 20, 1060694, SelectedColor, false, false ); // Change to Public - } - else - { - AddButtonLabeled( 10, 310, GetButtonID( 3, 10 ), 1060699 ); // View Access List - AddButtonLabeled( 10, 330, GetButtonID( 3, 11 ), 1060700 ); // Clear Access List - - AddHtmlLocalized( 245, 130, 240, 20, 1060695, SelectedColor, false, false ); // Change to Private - - AddButtonLabeled( 210, 150, GetButtonID( 3, 13 ), 1060694, isOwner ); // Change to Public - } - - break; - } - case HouseGumpPageAOS.Storage: - { - AddHtmlLocalized( 10, 130, 400, 20, 1060682, LabelColor, false, false ); //
HOUSE STORAGE SUMMARY
- - // This is not as OSI; storage changes not yet implemented - - /*AddHtmlLocalized( 10, 170, 275, 20, 1011237, LabelColor, false, false ); // Number of locked down items: - AddLabel( 310, 170, LabelHue, m_House.LockDownCount.ToString() ); - - AddHtmlLocalized( 10, 190, 275, 20, 1011238, LabelColor, false, false ); // Maximum locked down items: - AddLabel( 310, 190, LabelHue, m_House.MaxLockDowns.ToString() ); - - AddHtmlLocalized( 10, 210, 275, 20, 1011239, LabelColor, false, false ); // Number of secure containers: - AddLabel( 310, 210, LabelHue, m_House.SecureCount.ToString() ); - - AddHtmlLocalized( 10, 230, 275, 20, 1011240, LabelColor, false, false ); // Maximum number of secure containers: - AddLabel( 310, 230, LabelHue, m_House.MaxSecures.ToString() );*/ - - int fromSecures, fromVendors, fromLockdowns, fromMovingCrate; - - int maxSecures = house.GetAosMaxSecures(); - int curSecures = house.GetAosCurSecures( out fromSecures, out fromVendors, out fromLockdowns, out fromMovingCrate ); - - int maxLockdowns = house.GetAosMaxLockdowns(); - int curLockdowns = house.GetAosCurLockdowns(); - - int bonusStorage = (int)((house.BonusStorageScalar * 100)-100); - - if ( bonusStorage > 0 ) - { - AddHtmlLocalized( 10, 150, 300, 20, 1072519, LabelColor, false, false ); // Increased Storage - AddLabel( 310, 150, LabelHue, $"{bonusStorage}%"); - } - - AddHtmlLocalized( 10, 170, 300, 20, 1060683, LabelColor, false, false ); // Maximum Secure Storage - AddLabel( 310, 170, LabelHue, maxSecures.ToString() ); - - AddHtmlLocalized( 10, 190, 300, 20, 1060685, LabelColor, false, false ); // Used by Moving Crate - AddLabel( 310, 190, LabelHue, fromMovingCrate.ToString() ); - - AddHtmlLocalized( 10, 210, 300, 20, 1060686, LabelColor, false, false ); // Used by Lockdowns - AddLabel( 310, 210, LabelHue, fromLockdowns.ToString() ); - - if ( BaseHouse.NewVendorSystem ) - { - AddHtmlLocalized( 10, 230, 300, 20, 1060688, LabelColor, false, false ); // Used by Secure Containers - AddLabel( 310, 230, LabelHue, fromSecures.ToString() ); - - AddHtmlLocalized( 10, 250, 300, 20, 1060689, LabelColor, false, false ); // Available Storage - AddLabel( 310, 250, LabelHue, Math.Max( maxSecures - curSecures, 0 ).ToString() ); - - AddHtmlLocalized( 10, 290, 300, 20, 1060690, LabelColor, false, false ); // Maximum Lockdowns - AddLabel( 310, 290, LabelHue, maxLockdowns.ToString() ); - - AddHtmlLocalized( 10, 310, 300, 20, 1060691, LabelColor, false, false ); // Available Lockdowns - AddLabel( 310, 310, LabelHue, Math.Max( maxLockdowns - curLockdowns, 0 ).ToString() ); - - int maxVendors = house.GetNewVendorSystemMaxVendors(); - int vendors = house.PlayerVendors.Count + house.VendorRentalContracts.Count; - - AddHtmlLocalized( 10, 350, 300, 20, 1062391, LabelColor, false, false ); // Vendor Count - AddLabel( 310, 350, LabelHue, vendors.ToString() + " / " + maxVendors.ToString() ); - } - else - { - AddHtmlLocalized( 10, 230, 300, 20, 1060687, LabelColor, false, false ); // Used by Vendors - AddLabel( 310, 230, LabelHue, fromVendors.ToString() ); - - AddHtmlLocalized( 10, 250, 300, 20, 1060688, LabelColor, false, false ); // Used by Secure Containers - AddLabel( 310, 250, LabelHue, fromSecures.ToString() ); - - AddHtmlLocalized( 10, 270, 300, 20, 1060689, LabelColor, false, false ); // Available Storage - AddLabel( 310, 270, LabelHue, Math.Max( maxSecures - curSecures, 0 ).ToString() ); - - AddHtmlLocalized( 10, 330, 300, 20, 1060690, LabelColor, false, false ); // Maximum Lockdowns - AddLabel( 310, 330, LabelHue, maxLockdowns.ToString() ); - - AddHtmlLocalized( 10, 350, 300, 20, 1060691, LabelColor, false, false ); // Available Lockdowns - AddLabel( 310, 350, LabelHue, Math.Max( maxLockdowns - curLockdowns, 0 ).ToString() ); - } - - break; - } - case HouseGumpPageAOS.Customize: - { - bool isCustomizable = isOwner && ( house is HouseFoundation ); - - AddButtonLabeled( 10, 120, GetButtonID( 5, 0 ), 1060759, isOwner && !isCustomizable && ( house.ConvertEntry != null ) ); // Convert Into Customizable House - AddButtonLabeled( 10, 160, GetButtonID( 5, 1 ), 1060765, isOwner && isCustomizable ); // Customize This House - AddButtonLabeled( 10, 180, GetButtonID( 5, 2 ), 1060760, isOwner && house.MovingCrate != null ); // Relocate Moving Crate - AddButtonLabeled( 10, 210, GetButtonID( 5, 3 ), 1060761, isOwner && house.Public ); // Change House Sign - AddButtonLabeled( 10, 230, GetButtonID( 5, 4 ), 1060762, isOwner && isCustomizable ); // Change House Sign Hanger - AddButtonLabeled( 10, 250, GetButtonID( 5, 5 ), 1060763, isOwner && isCustomizable && ( ((HouseFoundation)house).Signpost != null ) ); // Change Signpost - AddButtonLabeled( 10, 280, GetButtonID( 5, 6 ), 1062004, isOwner && isCustomizable ); // Change Foundation Style - AddButtonLabeled( 10, 310, GetButtonID( 5, 7 ), 1060764, isCoOwner ); // Rename House - - break; - } - case HouseGumpPageAOS.Ownership: - { - AddButtonLabeled( 10, 130, GetButtonID( 6, 0 ), 1061794, isOwner && house.MovingCrate == null && house.InternalizedVendors.Count == 0 ); // Demolish House - AddButtonLabeled( 10, 150, GetButtonID( 6, 1 ), 1061797, isOwner ); // Trade House - AddButtonLabeled( 10, 190, GetButtonID( 6, 2 ), 1061798, false ); // Make Primary - - break; - } - case HouseGumpPageAOS.ChangeHanger: - { - for ( int i = 0; i < m_HangerNumbers.Length; ++i ) - { - int x = 50 + ((i % 3) * 100); - int y = 180 + ((i / 3) * 80); - - AddButton( x, y, 4005, 4007, GetButtonID( 7, i ), GumpButtonType.Reply, 0 ); - AddItem( x + 20, y, m_HangerNumbers[i] ); - } - - break; - } - case HouseGumpPageAOS.ChangeFoundation: - { - for ( int i = 0; i < m_FoundationNumbers.Length; ++i ) - { - int x = 15 + ((i % 5) * 80); - int y = 180 + ((i / 5) * 100); - - AddButton( x, y, 4005, 4007, GetButtonID( 8, i ), GumpButtonType.Reply, 0 ); - AddItem( x + 25, y, m_FoundationNumbers[i] ); - } - - break; - } - case HouseGumpPageAOS.ChangeSign: - { - int index = 0; - - if ( _HouseSigns.Count == 0 ) - { - // Add standard signs - for ( int i = 0; i < 54; ++i ) - { - _HouseSigns.Add( 2980 + ( i * 2 ) ); - } - - // Add library and beekeeper signs ( ML ) - _HouseSigns.Add( 2966 ); - _HouseSigns.Add( 3140 ); - } - - int signsPerPage = Core.ML ? 24 : 18; - int totalSigns = Core.ML ? 56 : 54; - int pages = (int) Math.Ceiling( (double) totalSigns / signsPerPage ); - - for ( int i = 0; i < pages; ++i ) - { - AddPage( i + 1 ); - - AddButton( 10, 360, 4005, 4007, 0, GumpButtonType.Page, ((i + 1) % pages ) + 1 ); - - for ( int j = 0; j < signsPerPage && totalSigns - ( signsPerPage * i ) - j > 0; ++j ) - { - int x = 30 + ((j % 6) * 60); - int y = 130 + ((j / 6) * 60); - - AddButton( x, y, 4005, 4007, GetButtonID( 9, index ), GumpButtonType.Reply, 0 ); - AddItem( x + 20, y, _HouseSigns[index++] ); - } - } - - break; - } - case HouseGumpPageAOS.RemoveCoOwner: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060730, LabelColor, false, false ); //
CO-OWNER LIST
- AddList( house.CoOwners, 10, false, true, from ); - break; - } - case HouseGumpPageAOS.ListCoOwner: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060730, LabelColor, false, false ); //
CO-OWNER LIST
- AddList( house.CoOwners, -1, false, true, from ); - break; - } - case HouseGumpPageAOS.RemoveFriend: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060731, LabelColor, false, false ); //
FRIENDS LIST
- AddList( house.Friends, 11, false, true, from ); - break; - } - case HouseGumpPageAOS.ListFriend: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060731, LabelColor, false, false ); //
FRIENDS LIST
- AddList( house.Friends, -1, false, true, from ); - break; - } - case HouseGumpPageAOS.RemoveBan: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060733, LabelColor, false, false ); //
BAN LIST
- AddList( house.Bans, 12, true, true, from ); - break; - } - case HouseGumpPageAOS.ListBan: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060733, LabelColor, false, false ); //
BAN LIST
- AddList( house.Bans, -1, true, true, from ); - break; - } - case HouseGumpPageAOS.RemoveAccess: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060732, LabelColor, false, false ); //
ACCESS LIST
- AddList( house.Access, 13, false, true, from ); - break; - } - case HouseGumpPageAOS.ListAccess: - { - AddHtmlLocalized( 10, 120, 400, 20, 1060732, LabelColor, false, false ); //
ACCESS LIST
- AddList( house.Access, -1, false, true, from ); - break; - } - case HouseGumpPageAOS.ChangePost: - { - int index = 0; - - for ( int i = 0; i < 2; ++i ) - { - AddPage( i + 1 ); - - AddButton( 10, 360, 4005, 4007, 0, GumpButtonType.Page, ((i + 1) % 2) + 1 ); - - for ( int j = 0; j < 16 && index < m_PostNumbers.Length; ++j ) - { - int x = 15 + ((j % 8) * 50); - int y = 130 + ((j / 8) * 110); - - AddButton( x, y, 4005, 4007, GetButtonID( 14, index ), GumpButtonType.Reply, 0 ); - AddItem( x + 10, y, m_PostNumbers[index++] ); - } - } - - break; - } - } - } - - public static void PublicPrivateNotice_Callback( Mobile from, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( !house.Deleted ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, house ) ); - } - - public static void CustomizeNotice_Callback( Mobile from, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( !house.Deleted ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Customize, from, house ) ); - } - - public static void ClearCoOwners_Callback( Mobile from, bool okay, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( house.Deleted ) - return; - - if ( okay && house.IsOwner( from ) ) - { - house.CoOwners?.Clear(); - - from.SendLocalizedMessage( 501333 ); // All co-owners have been removed from this house. - } - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, house ) ); - } - - public static void ClearFriends_Callback( Mobile from, bool okay, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( house.Deleted ) - return; - - if ( okay && house.IsCoOwner( from ) ) - { - house.Friends?.Clear(); - - from.SendLocalizedMessage( 501332 ); // All friends have been removed from this house. - } - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, house ) ); - } - - public static void ClearBans_Callback( Mobile from, bool okay, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( house.Deleted ) - return; - - if ( okay && house.IsFriend( from ) ) - { - house.Bans?.Clear(); - - from.SendLocalizedMessage( 1060754 ); // All bans for this house have been lifted. - } - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, house ) ); - } - - public static void ClearAccess_Callback( Mobile from, bool okay, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( house.Deleted ) - return; - - if ( okay && house.IsFriend( from ) ) - { - ArrayList list = new ArrayList( house.Access ); - - house.Access?.Clear(); - - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; - - if ( !house.HasAccess( m ) && house.IsInside( m ) ) - { - m.Location = house.BanLocation; - m.SendLocalizedMessage( 1060734 ); // Your access to this house has been revoked. - } - } - - from.SendLocalizedMessage( 1061843 ); // This house's Access List has been cleared. - } - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, house ) ); - } - - public static void ConvertHouse_Callback( Mobile from, bool okay, object state ) - { - BaseHouse house = (BaseHouse) state; - - if ( house.Deleted ) - return; - - if ( okay && house.IsOwner( from ) && !house.HasRentedVendors ) - { - HousePlacementEntry e = house.ConvertEntry; - - if ( e != null ) - { - int cost = e.Cost - house.Price; - - if ( cost > 0 ) - { - if ( Banker.Withdraw( from, cost ) ) - { - from.SendLocalizedMessage( 1060398, cost.ToString() ); // ~1_AMOUNT~ gold has been withdrawn from your bank box. - } - else - { - from.SendLocalizedMessage( 1061624 ); // You do not have enough funds in your bank to cover the difference between your old house and your new one. - return; - } - } - else if ( cost < 0 ) - { - if ( Banker.Deposit( from, -cost ) ) - from.SendLocalizedMessage( 1060397, (-cost).ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. - else - return; - } - - BaseHouse newHouse = e.ConstructHouse( from ); - - if ( newHouse != null ) - { - newHouse.Price = e.Cost; - - house.MoveAllToCrate(); - - newHouse.Friends = new ArrayList( house.Friends ); - newHouse.CoOwners = new ArrayList( house.CoOwners ); - newHouse.Bans = new ArrayList( house.Bans ); - newHouse.Access = new ArrayList( house.Access ); - newHouse.BuiltOn = house.BuiltOn; - newHouse.LastTraded = house.LastTraded; - newHouse.Public = house.Public; - - newHouse.VendorInventories.AddRange( house.VendorInventories ); - house.VendorInventories.Clear(); - - foreach ( VendorInventory inventory in newHouse.VendorInventories ) - { - inventory.House = newHouse; - } - - newHouse.InternalizedVendors.AddRange( house.InternalizedVendors ); - house.InternalizedVendors.Clear(); - - foreach ( Mobile mobile in newHouse.InternalizedVendors ) - { - if ( mobile is PlayerVendor vendor ) - vendor.House = newHouse; - else if ( mobile is PlayerBarkeeper barkeeper ) - barkeeper.House = newHouse; - } - - if ( house.MovingCrate != null ) - { - newHouse.MovingCrate = house.MovingCrate; - newHouse.MovingCrate.House = newHouse; - house.MovingCrate = null; - } - - List items = house.GetItems(); - List mobiles = house.GetMobiles(); - - newHouse.MoveToWorld( new Point3D( house.X + house.ConvertOffsetX, house.Y + house.ConvertOffsetY, house.Z + house.ConvertOffsetZ ), house.Map ); - house.Delete(); - - foreach ( Item item in items ) - { - item.Location = newHouse.BanLocation; - } - - foreach ( Mobile mobile in mobiles ) - { - mobile.Location = newHouse.BanLocation; - } - - /* You have successfully replaced your original house with a new house. - * The value of the replaced house has been deposited into your bank box. - * All of the items in your original house have been relocated to a Moving Crate in the new house. - * Any deed-based house add-ons have been converted back into deeds. - * Vendors and barkeeps in the house, if any, have been stored in the Moving Crate as well. - * Use the Get Vendor context-sensitive menu option on your character to retrieve them. - * These containers can be used to re-create the vendor in a new location. - * Any barkeepers have been converted into deeds. - */ - from.SendGump( new NoticeGump( 1060637, 30720, 1060012, 32512, 420, 280, null, null ) ); - return; - } - } - } - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, house ) ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_House.Deleted ) - return; - - Mobile from = sender.Mobile; - - bool isCombatRestricted = m_House.IsCombatRestricted( from ); - - bool isOwner = m_House.IsOwner( from ); - bool isCoOwner = isOwner || m_House.IsCoOwner( from ); - bool isFriend = isCoOwner || m_House.IsFriend( from ); - - if ( isCombatRestricted ) - isCoOwner = isFriend = false; - - if ( !from.CheckAlive() ) - return; - - Item sign = m_House.Sign; - - if ( sign == null || from.Map != sign.Map || !from.InRange( sign.GetWorldLocation(), 18 ) ) - return; - - HouseFoundation foundation = m_House as HouseFoundation; - bool isCustomizable = ( foundation != null ); - - int val = info.ButtonID - 1; - - if ( val < 0 ) - return; - - int type = val % 15; - int index = val / 15; - - if ( m_Page == HouseGumpPageAOS.Vendors ) - { - if ( index >= 0 && index < m_List.Count ) - { - PlayerVendor vendor = (PlayerVendor) m_List[index]; - - if ( !vendor.CanInteractWith( from, false ) ) - return; - - if ( from.Map != sign.Map || !from.InRange( sign, 5 ) ) - { - from.SendLocalizedMessage( 1062429 ); // You must be within five paces of the house sign to use this option. - } - else if ( vendor.IsOwner( from ) ) - { - vendor.SendOwnerGump( from ); - } - else - { - vendor.OpenBackpack( from ); - } - } - - return; - } - - if ( !isFriend ) - return; - - switch ( type ) - { - case 0: - { - switch ( index ) - { - case 0: // Banish - { - if ( m_House.Public ) - { - from.SendLocalizedMessage( 501325 ); // Target the individual to ban from this house. - from.Target = new HouseBanTarget( true, m_House ); - } - - break; - } - case 1: // Lift Ban - { - if ( m_House.Public ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveBan, from, m_House ) ); - - break; - } - case 2: // Grant Access - { - if ( !m_House.Public ) - { - from.SendLocalizedMessage( 1060711 ); // Target the person you would like to grant access to. - from.Target = new HouseAccessTarget( m_House ); - } - - break; - } - case 3: // Revoke Access - { - if ( !m_House.Public ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveAccess, from, m_House ) ); - - break; - } - } - - break; - } - case 1: - { - HouseGumpPageAOS page; - - switch ( index ) - { - case 0: page = HouseGumpPageAOS.Information; break; - case 1: page = HouseGumpPageAOS.Security; break; - case 2: page = HouseGumpPageAOS.Storage; break; - case 3: page = HouseGumpPageAOS.Customize; break; - case 4: page = HouseGumpPageAOS.Ownership; break; - default: return; - } - - from.SendGump( new HouseGumpAOS( page, from, m_House ) ); - break; - } - case 3: - { - switch ( index ) - { - case 0: // View Co-Owner List - { - if ( isCoOwner ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ListCoOwner, from, m_House ) ); - - break; - } - case 1: // Add a Co-Owner - { - if ( isOwner ) - { - from.SendLocalizedMessage( 501328 ); // Target the person you wish to name a co-owner of your household. - from.Target = new CoOwnerTarget( true, m_House ); - } - - break; - } - case 2: // Remove a Co-Owner - { - if ( isOwner ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveCoOwner, from, m_House ) ); - - break; - } - case 3: // Clear Co-Owner List - { - if ( isOwner ) - from.SendGump( new WarningGump( 1060635, 30720, 1060736, 32512, 420, 280, ClearCoOwners_Callback, m_House ) ); - - break; - } - case 4: // View Friends List - { - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ListFriend, from, m_House ) ); - - break; - } - case 5: // Add a Friend - { - if ( isCoOwner ) - { - from.SendLocalizedMessage( 501317 ); // Target the person you wish to name a friend of your household. - from.Target = new HouseFriendTarget( true, m_House ); - } - - break; - } - case 6: // Remove a Friend - { - if ( isCoOwner ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveFriend, from, m_House ) ); - - break; - } - case 7: // Clear Friend List - { - if ( isCoOwner ) - from.SendGump( new WarningGump( 1060635, 30720, 1018039, 32512, 420, 280, ClearFriends_Callback, m_House ) ); - - break; - } - case 8: // View Ban List - { - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ListBan, from, m_House ) ); - - break; - } - case 9: // Clear Ban List - { - from.SendGump( new WarningGump( 1060635, 30720, 1060753, 32512, 420, 280, ClearBans_Callback, m_House ) ); - - break; - } - case 10: // View Access List - { - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ListAccess, from, m_House ) ); - - break; - } - case 11: // Clear Access List - { - from.SendGump( new WarningGump( 1060635, 30720, 1061842, 32512, 420, 280, ClearAccess_Callback, m_House ) ); - - break; - } - case 12: // Make Private - { - if ( isOwner ) - { - if ( m_House.PlayerVendors.Count > 0 ) - { - // You have vendors working out of this building. It cannot be declared private until there are no vendors in place. - from.SendGump( new NoticeGump( 1060637, 30720, 501887, 32512, 320, 180, PublicPrivateNotice_Callback, m_House ) ); - break; - } - - if ( m_House.VendorRentalContracts.Count > 0 ) - { - // You cannot currently take this action because you have vendor contracts locked down in your home. You must remove them first. - from.SendGump( new NoticeGump( 1060637, 30720, 1062351, 32512, 320, 180, PublicPrivateNotice_Callback, m_House ) ); - break; - } - - m_House.Public = false; - - m_House.ChangeLocks( from ); - - // This house is now private. - from.SendGump( new NoticeGump( 1060637, 30720, 501888, 32512, 320, 180, PublicPrivateNotice_Callback, m_House ) ); - - Region r = m_House.Region; - List list = r.GetMobiles(); - - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; - - if ( !m_House.HasAccess( m ) && m_House.IsInside( m ) ) - m.Location = m_House.BanLocation; - } - } - - break; - } - case 13: // Make Public - { - if ( isOwner ) - { - m_House.Public = true; - - m_House.RemoveKeys( from ); - m_House.RemoveLocks(); - - if ( BaseHouse.NewVendorSystem ) - { - // This house is now public. The owner may now place vendors and vendor rental contracts. - from.SendGump( new NoticeGump( 1060637, 30720, 501886, 32512, 320, 180, PublicPrivateNotice_Callback, m_House ) ); - } - else - { - from.SendGump( new NoticeGump( 1060637, 30720, "This house is now public. Friends of the house may now have vendors working out of this building.", 0xF8C000, 320, 180, PublicPrivateNotice_Callback, m_House ) ); - } - - Region r = m_House.Region; - List list = r.GetMobiles(); - - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; - - if ( m_House.IsBanned( m ) && m_House.IsInside( m ) ) - m.Location = m_House.BanLocation; - } - } - - break; - } - } - - break; - } - case 5: - { - switch ( index ) - { - case 0: // Convert Into Customizable House - { - if ( isOwner && !isCustomizable ) - { - if ( m_House.HasRentedVendors ) - { - // You cannot perform this action while you still have vendors rented out in this house. - from.SendGump( new NoticeGump( 1060637, 30720, 1062395, 32512, 320, 180, CustomizeNotice_Callback, m_House ) ); - } - else - { - HousePlacementEntry e = m_House.ConvertEntry; - - if ( e != null ) - { - /* You are about to turn your house into a customizable house. - * You will be refunded the value of this house, and then be charged the cost of the equivalent customizable dirt lot. - * All of your possessions in the house will be transported to a Moving Crate. - * Deed-based house add-ons will be converted back into deeds. - * Vendors and barkeeps will also be stored in the Moving Crate. - * Your house will be leveled to its foundation, and you will be able to build new walls, windows, doors, and stairs. - * Are you sure you wish to continue? - */ - from.SendGump( new WarningGump( 1060635, 30720, 1060013, 32512, 420, 280, ConvertHouse_Callback, m_House ) ); - } - } - } - - break; - } - case 1: // Customize This House - { - if ( isOwner && isCustomizable ) - { - if ( m_House.HasRentedVendors ) - { - // You cannot perform this action while you still have vendors rented out in this house. - from.SendGump( new NoticeGump( 1060637, 30720, 1062395, 32512, 320, 180, CustomizeNotice_Callback, m_House ) ); - } - #region Mondain's Legacy - else if ( m_House.HasAddonContainers ) - { - // The house can not be customized when add-on containers such as aquariums, elven furniture containers, vanities, and boiling cauldrons - // are present in the house. Please re-deed the add-on containers before customizing the house. - from.SendGump( new NoticeGump( 1060637, 30720, 1074863, 32512, 320, 180, CustomizeNotice_Callback, m_House ) ); - } - #endregion - else - { - foundation.BeginCustomize( from ); - } - } - - break; - } - case 2: // Relocate Moving Crate - { - MovingCrate crate = m_House.MovingCrate; - - if ( isOwner && crate != null ) - { - if ( !m_House.IsInside( from ) ) - { - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - { - crate.MoveToWorld( from.Location, from.Map ); - crate.RestartTimer(); - } - } - - break; - } - case 3: // Change House Sign - { - if ( isOwner && m_House.Public ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ChangeSign, from, m_House ) ); - - break; - } - case 4: // Change House Sign Hanger - { - if ( isOwner && isCustomizable ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ChangeHanger, from, m_House ) ); - - break; - } - case 5: // Change Signpost - { - if ( isOwner && isCustomizable && foundation.Signpost != null ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ChangePost, from, m_House ) ); - - break; - } - case 6: // Change Foundation Style - { - if ( isOwner && isCustomizable ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.ChangeFoundation, from, m_House ) ); - - break; - } - case 7: // Rename House - { - if ( isCoOwner ) - { - from.Prompt = new RenamePrompt( m_House ); - from.SendLocalizedMessage( 501302 ); // What dost thou wish the sign to say? - } - - break; - } - } - - break; - } - case 6: - { - switch ( index ) - { - case 0: // Demolish - { - if ( isOwner && m_House.MovingCrate == null && m_House.InternalizedVendors.Count == 0 ) - { - if ( !Guilds.Guild.NewGuildSystem && m_House.FindGuildstone() != null ) - { - from.SendLocalizedMessage( 501389 ); // You cannot redeed a house with a guildstone inside. - } - else if ( Core.ML && from.AccessLevel < AccessLevel.GameMaster && DateTime.UtcNow <= m_House.BuiltOn.AddHours ( 1 ) ) - { - from.SendLocalizedMessage( 1080178 ); // You must wait one hour between each house demolition. - } - else - { - from.CloseGump( typeof( HouseDemolishGump ) ); - from.SendGump( new HouseDemolishGump( from, m_House ) ); - } - } - - break; - } - case 1: // Trade House - { - if ( isOwner ) - { - if ( BaseHouse.NewVendorSystem && m_House.HasPersonalVendors ) - { - from.SendLocalizedMessage( 1062467 ); // You cannot trade this house while you still have personal vendors inside. - } - else if ( m_House.DecayLevel == DecayLevel.DemolitionPending ) - { - from.SendLocalizedMessage( 1005321 ); // This house has been marked for demolition, and it cannot be transferred. - } - else - { - from.SendLocalizedMessage( 501309 ); // Target the person to whom you wish to give this house. - from.Target = new HouseOwnerTarget( m_House ); - } - } - - break; - } - case 2: // Make Primary - break; - } - - break; - } - case 7: - { - if ( isOwner && isCustomizable && index >= 0 && index < m_HangerNumbers.Length ) - { - Item hanger = foundation.SignHanger; - - if ( hanger != null ) - hanger.ItemID = m_HangerNumbers[index]; - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Customize, from, m_House ) ); - } - - break; - } - case 8: - { - if ( isOwner && isCustomizable ) - { - FoundationType newType; - - if ( Core.ML && index >= 5 ) - { - switch( index ) - { - case 5: newType = FoundationType.ElvenGrey; break; - case 6: newType = FoundationType.ElvenNatural; break; - case 7: newType = FoundationType.Crystal; break; - case 8: newType = FoundationType.Shadow; break; - default: return; - } - } - else - { - switch( index ) - { - case 0: newType = FoundationType.DarkWood; break; - case 1: newType = FoundationType.LightWood; break; - case 2: newType = FoundationType.Dungeon; break; - case 3: newType = FoundationType.Brick; break; - case 4: newType = FoundationType.Stone; break; - default: return; - } - } - - foundation.Type = newType; - - DesignState state = foundation.BackupState; - HouseFoundation.ApplyFoundation( newType, state.Components ); - state.OnRevised(); - - state = foundation.DesignState; - HouseFoundation.ApplyFoundation( newType, state.Components ); - state.OnRevised(); - - state = foundation.CurrentState; - HouseFoundation.ApplyFoundation( newType, state.Components ); - state.OnRevised(); - - foundation.Delta( ItemDelta.Update ); - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Customize, from, m_House ) ); - } - - break; - } - case 9: - { - if ( isOwner && m_House.Public && index >= 0 && index < _HouseSigns.Count ) - { - m_House.ChangeSignType( _HouseSigns[index] ); - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Customize, from, m_House ) ); - } - - break; - } - case 10: - { - if ( isOwner && m_List != null && index >= 0 && index < m_List.Count ) - { - m_House.RemoveCoOwner( from, (Mobile)m_List[index] ); - - if ( m_House.CoOwners.Count > 0 ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveCoOwner, from, m_House ) ); - else - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, m_House ) ); - } - - break; - } - case 11: - { - if ( isCoOwner && m_List != null && index >= 0 && index < m_List.Count ) - { - m_House.RemoveFriend( from, (Mobile)m_List[index] ); - - if ( m_House.Friends.Count > 0 ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveFriend, from, m_House ) ); - else - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, m_House ) ); - } - - break; - } - case 12: - { - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - m_House.RemoveBan( from, (Mobile)m_List[index] ); - - if ( m_House.Bans.Count > 0 ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveBan, from, m_House ) ); - else - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, m_House ) ); - } - - break; - } - case 13: - { - if ( m_List != null && index >= 0 && index < m_List.Count ) - { - m_House.RemoveAccess( from, (Mobile)m_List[index] ); - - if ( m_House.Access.Count > 0 ) - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.RemoveAccess, from, m_House ) ); - else - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Security, from, m_House ) ); - } - - break; - } - case 14: - { - if ( isOwner && isCustomizable && index >= 0 && index < m_PostNumbers.Length ) - { - foundation.SignpostGraphic = m_PostNumbers[index]; - foundation.CheckSignpost(); - - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Customize, from, m_House ) ); - } - - break; - } - } - } - - private ArrayList Wrap( string value ) - { - if ( value == null || (value = value.Trim()).Length <= 0 ) - return null; - - string[] values = value.Split( ' ' ); - ArrayList list = new ArrayList(); - string current = ""; - - for ( int i = 0; i < values.Length; ++i ) - { - string val = values[i]; - - string v = current.Length == 0 ? val : current + ' ' + val; - - if ( v.Length < 10 ) - { - current = v; - } - else if ( v.Length == 10 ) - { - list.Add( v ); - - if ( list.Count == 6 ) - return list; - - current = ""; - } - else if ( val.Length <= 10 ) - { - list.Add( current ); - - if ( list.Count == 6 ) - return list; - - current = val; - } - else - { - while ( v.Length >= 10 ) - { - list.Add( v.Substring( 0, 10 ) ); - - if ( list.Count == 6 ) - return list; - - v = v.Substring( 10 ); - } - - current = v; - } - } - - if ( current.Length > 0 ) - list.Add( current ); - - return list; - } - } -} + if ((name = name.Trim()).Length <= 0) + continue; + + if (button != -1) + AddButton(10 + xoffset, 150 + yoffset, 4005, 4007, GetButtonID(button, i), GumpButtonType.Reply, 0); + + if (accountOf && m.Player && m.Account != null) + name = "Account of " + name; + + if (leadingStar) + name = "* " + name; + + AddLabel(button > 0 ? 45 + xoffset : 10 + xoffset, 150 + yoffset, labelHue, name); + ++index; + } + } + + public int GetButtonID(int type, int index) + { + return 1 + index * 15 + type; + } + + public static void PublicPrivateNotice_Callback(Mobile from, object state) + { + BaseHouse house = (BaseHouse)state; + + if (!house.Deleted) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, house)); + } + + public static void CustomizeNotice_Callback(Mobile from, object state) + { + BaseHouse house = (BaseHouse)state; + + if (!house.Deleted) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Customize, from, house)); + } + + public static void ClearCoOwners_Callback(Mobile from, bool okay, object state) + { + BaseHouse house = (BaseHouse)state; + + if (house.Deleted) + return; + + if (okay && house.IsOwner(from)) + { + house.CoOwners?.Clear(); + + from.SendLocalizedMessage(501333); // All co-owners have been removed from this house. + } + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, house)); + } + + public static void ClearFriends_Callback(Mobile from, bool okay, object state) + { + BaseHouse house = (BaseHouse)state; + + if (house.Deleted) + return; + + if (okay && house.IsCoOwner(from)) + { + house.Friends?.Clear(); + + from.SendLocalizedMessage(501332); // All friends have been removed from this house. + } + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, house)); + } + + public static void ClearBans_Callback(Mobile from, bool okay, object state) + { + BaseHouse house = (BaseHouse)state; + + if (house.Deleted) + return; + + if (okay && house.IsFriend(from)) + { + house.Bans?.Clear(); + + from.SendLocalizedMessage(1060754); // All bans for this house have been lifted. + } + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, house)); + } + + public static void ClearAccess_Callback(Mobile from, bool okay, object state) + { + BaseHouse house = (BaseHouse)state; + + if (house.Deleted) + return; + + if (okay && house.IsFriend(from)) + { + ArrayList list = new ArrayList(house.Access); + + house.Access?.Clear(); + + for (int i = 0; i < list.Count; ++i) + { + Mobile m = (Mobile)list[i]; + + if (!house.HasAccess(m) && house.IsInside(m)) + { + m.Location = house.BanLocation; + m.SendLocalizedMessage(1060734); // Your access to this house has been revoked. + } + } + + from.SendLocalizedMessage(1061843); // This house's Access List has been cleared. + } + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, house)); + } + + public static void ConvertHouse_Callback(Mobile from, bool okay, object state) + { + BaseHouse house = (BaseHouse)state; + + if (house.Deleted) + return; + + if (okay && house.IsOwner(from) && !house.HasRentedVendors) + { + HousePlacementEntry e = house.ConvertEntry; + + if (e != null) + { + int cost = e.Cost - house.Price; + + if (cost > 0) + { + if (Banker.Withdraw(from, cost)) + { + from.SendLocalizedMessage(1060398, + cost.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. + } + else + { + from.SendLocalizedMessage( + 1061624); // You do not have enough funds in your bank to cover the difference between your old house and your new one. + return; + } + } + else if (cost < 0) + { + if (Banker.Deposit(from, -cost)) + from.SendLocalizedMessage(1060397, + (-cost).ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + else + return; + } + + BaseHouse newHouse = e.ConstructHouse(from); + + if (newHouse != null) + { + newHouse.Price = e.Cost; + + house.MoveAllToCrate(); + + newHouse.Friends = new ArrayList(house.Friends); + newHouse.CoOwners = new ArrayList(house.CoOwners); + newHouse.Bans = new ArrayList(house.Bans); + newHouse.Access = new ArrayList(house.Access); + newHouse.BuiltOn = house.BuiltOn; + newHouse.LastTraded = house.LastTraded; + newHouse.Public = house.Public; + + newHouse.VendorInventories.AddRange(house.VendorInventories); + house.VendorInventories.Clear(); + + foreach (VendorInventory inventory in newHouse.VendorInventories) inventory.House = newHouse; + + newHouse.InternalizedVendors.AddRange(house.InternalizedVendors); + house.InternalizedVendors.Clear(); + + foreach (Mobile mobile in newHouse.InternalizedVendors) + if (mobile is PlayerVendor vendor) + vendor.House = newHouse; + else if (mobile is PlayerBarkeeper barkeeper) + barkeeper.House = newHouse; + + if (house.MovingCrate != null) + { + newHouse.MovingCrate = house.MovingCrate; + newHouse.MovingCrate.House = newHouse; + house.MovingCrate = null; + } + + List items = house.GetItems(); + List mobiles = house.GetMobiles(); + + newHouse.MoveToWorld( + new Point3D(house.X + house.ConvertOffsetX, house.Y + house.ConvertOffsetY, + house.Z + house.ConvertOffsetZ), house.Map); + house.Delete(); + + foreach (Item item in items) item.Location = newHouse.BanLocation; + + foreach (Mobile mobile in mobiles) mobile.Location = newHouse.BanLocation; + + /* You have successfully replaced your original house with a new house. + * The value of the replaced house has been deposited into your bank box. + * All of the items in your original house have been relocated to a Moving Crate in the new house. + * Any deed-based house add-ons have been converted back into deeds. + * Vendors and barkeeps in the house, if any, have been stored in the Moving Crate as well. + * Use the Get Vendor context-sensitive menu option on your character to retrieve them. + * These containers can be used to re-create the vendor in a new location. + * Any barkeepers have been converted into deeds. + */ + from.SendGump(new NoticeGump(1060637, 30720, 1060012, 32512, 420, 280, null, null)); + return; + } + } + } + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, house)); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_House.Deleted) + return; + + Mobile from = sender.Mobile; + + bool isCombatRestricted = m_House.IsCombatRestricted(from); + + bool isOwner = m_House.IsOwner(from); + bool isCoOwner = isOwner || m_House.IsCoOwner(from); + bool isFriend = isCoOwner || m_House.IsFriend(from); + + if (isCombatRestricted) + isCoOwner = isFriend = false; + + if (!from.CheckAlive()) + return; + + Item sign = m_House.Sign; + + if (sign == null || from.Map != sign.Map || !from.InRange(sign.GetWorldLocation(), 18)) + return; + + HouseFoundation foundation = m_House as HouseFoundation; + bool isCustomizable = foundation != null; + + int val = info.ButtonID - 1; + + if (val < 0) + return; + + int type = val % 15; + int index = val / 15; + + if (m_Page == HouseGumpPageAOS.Vendors) + { + if (index >= 0 && index < m_List.Count) + { + PlayerVendor vendor = (PlayerVendor)m_List[index]; + + if (!vendor.CanInteractWith(from, false)) + return; + + if (from.Map != sign.Map || !from.InRange(sign, 5)) + from.SendLocalizedMessage( + 1062429); // You must be within five paces of the house sign to use this option. + else if (vendor.IsOwner(from)) + vendor.SendOwnerGump(from); + else + vendor.OpenBackpack(from); + } + + return; + } + + if (!isFriend) + return; + + switch (type) + { + case 0: + { + switch (index) + { + case 0: // Banish + { + if (m_House.Public) + { + from.SendLocalizedMessage(501325); // Target the individual to ban from this house. + from.Target = new HouseBanTarget(true, m_House); + } + + break; + } + case 1: // Lift Ban + { + if (m_House.Public) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveBan, from, m_House)); + + break; + } + case 2: // Grant Access + { + if (!m_House.Public) + { + from.SendLocalizedMessage(1060711); // Target the person you would like to grant access to. + from.Target = new HouseAccessTarget(m_House); + } + + break; + } + case 3: // Revoke Access + { + if (!m_House.Public) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveAccess, from, m_House)); + + break; + } + } + + break; + } + case 1: + { + HouseGumpPageAOS page; + + switch (index) + { + case 0: + page = HouseGumpPageAOS.Information; + break; + case 1: + page = HouseGumpPageAOS.Security; + break; + case 2: + page = HouseGumpPageAOS.Storage; + break; + case 3: + page = HouseGumpPageAOS.Customize; + break; + case 4: + page = HouseGumpPageAOS.Ownership; + break; + default: return; + } + + from.SendGump(new HouseGumpAOS(page, from, m_House)); + break; + } + case 3: + { + switch (index) + { + case 0: // View Co-Owner List + { + if (isCoOwner) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ListCoOwner, from, m_House)); + + break; + } + case 1: // Add a Co-Owner + { + if (isOwner) + { + from.SendLocalizedMessage( + 501328); // Target the person you wish to name a co-owner of your household. + from.Target = new CoOwnerTarget(true, m_House); + } + + break; + } + case 2: // Remove a Co-Owner + { + if (isOwner) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveCoOwner, from, m_House)); + + break; + } + case 3: // Clear Co-Owner List + { + if (isOwner) + from.SendGump(new WarningGump(1060635, 30720, 1060736, 32512, 420, 280, + ClearCoOwners_Callback, m_House)); + + break; + } + case 4: // View Friends List + { + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ListFriend, from, m_House)); + + break; + } + case 5: // Add a Friend + { + if (isCoOwner) + { + from.SendLocalizedMessage( + 501317); // Target the person you wish to name a friend of your household. + from.Target = new HouseFriendTarget(true, m_House); + } + + break; + } + case 6: // Remove a Friend + { + if (isCoOwner) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveFriend, from, m_House)); + + break; + } + case 7: // Clear Friend List + { + if (isCoOwner) + from.SendGump(new WarningGump(1060635, 30720, 1018039, 32512, 420, 280, + ClearFriends_Callback, m_House)); + + break; + } + case 8: // View Ban List + { + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ListBan, from, m_House)); + + break; + } + case 9: // Clear Ban List + { + from.SendGump(new WarningGump(1060635, 30720, 1060753, 32512, 420, 280, ClearBans_Callback, + m_House)); + + break; + } + case 10: // View Access List + { + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ListAccess, from, m_House)); + + break; + } + case 11: // Clear Access List + { + from.SendGump(new WarningGump(1060635, 30720, 1061842, 32512, 420, 280, ClearAccess_Callback, + m_House)); + + break; + } + case 12: // Make Private + { + if (isOwner) + { + if (m_House.PlayerVendors.Count > 0) + { + // You have vendors working out of this building. It cannot be declared private until there are no vendors in place. + from.SendGump(new NoticeGump(1060637, 30720, 501887, 32512, 320, 180, + PublicPrivateNotice_Callback, m_House)); + break; + } + + if (m_House.VendorRentalContracts.Count > 0) + { + // You cannot currently take this action because you have vendor contracts locked down in your home. You must remove them first. + from.SendGump(new NoticeGump(1060637, 30720, 1062351, 32512, 320, 180, + PublicPrivateNotice_Callback, m_House)); + break; + } + + m_House.Public = false; + + m_House.ChangeLocks(from); + + // This house is now private. + from.SendGump(new NoticeGump(1060637, 30720, 501888, 32512, 320, 180, + PublicPrivateNotice_Callback, m_House)); + + Region r = m_House.Region; + List list = r.GetMobiles(); + + for (int i = 0; i < list.Count; ++i) + { + Mobile m = list[i]; + + if (!m_House.HasAccess(m) && m_House.IsInside(m)) + m.Location = m_House.BanLocation; + } + } + + break; + } + case 13: // Make Public + { + if (isOwner) + { + m_House.Public = true; + + m_House.RemoveKeys(from); + m_House.RemoveLocks(); + + if (BaseHouse.NewVendorSystem) + from.SendGump(new NoticeGump(1060637, 30720, 501886, 32512, 320, 180, + PublicPrivateNotice_Callback, m_House)); + else + from.SendGump(new NoticeGump(1060637, 30720, + "This house is now public. Friends of the house may now have vendors working out of this building.", + 0xF8C000, 320, 180, PublicPrivateNotice_Callback, m_House)); + + Region r = m_House.Region; + List list = r.GetMobiles(); + + for (int i = 0; i < list.Count; ++i) + { + Mobile m = list[i]; + + if (m_House.IsBanned(m) && m_House.IsInside(m)) + m.Location = m_House.BanLocation; + } + } + + break; + } + } + + break; + } + case 5: + { + switch (index) + { + case 0: // Convert Into Customizable House + { + if (isOwner && !isCustomizable) + { + if (m_House.HasRentedVendors) + { + // You cannot perform this action while you still have vendors rented out in this house. + from.SendGump(new NoticeGump(1060637, 30720, 1062395, 32512, 320, 180, + CustomizeNotice_Callback, m_House)); + } + else + { + HousePlacementEntry e = m_House.ConvertEntry; + + if (e != null) + from.SendGump(new WarningGump(1060635, 30720, 1060013, 32512, 420, 280, + ConvertHouse_Callback, m_House)); + } + } + + break; + } + case 1: // Customize This House + { + if (isOwner && isCustomizable) + { + if (m_House.HasRentedVendors) + from.SendGump(new NoticeGump(1060637, 30720, 1062395, 32512, 320, 180, + CustomizeNotice_Callback, m_House)); + + #region Mondain's Legacy + + else if (m_House.HasAddonContainers) + from.SendGump(new NoticeGump(1060637, 30720, 1074863, 32512, 320, 180, + CustomizeNotice_Callback, m_House)); + + #endregion + + else + foundation.BeginCustomize(from); + } + + break; + } + case 2: // Relocate Moving Crate + { + MovingCrate crate = m_House.MovingCrate; + + if (isOwner && crate != null) + { + if (!m_House.IsInside(from)) + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + else + { + crate.MoveToWorld(from.Location, from.Map); + crate.RestartTimer(); + } + } + + break; + } + case 3: // Change House Sign + { + if (isOwner && m_House.Public) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ChangeSign, from, m_House)); + + break; + } + case 4: // Change House Sign Hanger + { + if (isOwner && isCustomizable) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ChangeHanger, from, m_House)); + + break; + } + case 5: // Change Signpost + { + if (isOwner && isCustomizable && foundation.Signpost != null) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ChangePost, from, m_House)); + + break; + } + case 6: // Change Foundation Style + { + if (isOwner && isCustomizable) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.ChangeFoundation, from, m_House)); + + break; + } + case 7: // Rename House + { + if (isCoOwner) + { + from.Prompt = new RenamePrompt(m_House); + from.SendLocalizedMessage(501302); // What dost thou wish the sign to say? + } + + break; + } + } + + break; + } + case 6: + { + switch (index) + { + case 0: // Demolish + { + if (isOwner && m_House.MovingCrate == null && m_House.InternalizedVendors.Count == 0) + { + if (!Guild.NewGuildSystem && m_House.FindGuildstone() != null) + { + from.SendLocalizedMessage(501389); // You cannot redeed a house with a guildstone inside. + } + else if (Core.ML && from.AccessLevel < AccessLevel.GameMaster && + DateTime.UtcNow <= m_House.BuiltOn.AddHours(1)) + { + from.SendLocalizedMessage( + 1080178); // You must wait one hour between each house demolition. + } + else + { + from.CloseGump(typeof(HouseDemolishGump)); + from.SendGump(new HouseDemolishGump(from, m_House)); + } + } + + break; + } + case 1: // Trade House + { + if (isOwner) + { + if (BaseHouse.NewVendorSystem && m_House.HasPersonalVendors) + { + from.SendLocalizedMessage( + 1062467); // You cannot trade this house while you still have personal vendors inside. + } + else if (m_House.DecayLevel == DecayLevel.DemolitionPending) + { + from.SendLocalizedMessage( + 1005321); // This house has been marked for demolition, and it cannot be transferred. + } + else + { + from.SendLocalizedMessage( + 501309); // Target the person to whom you wish to give this house. + from.Target = new HouseOwnerTarget(m_House); + } + } + + break; + } + case 2: // Make Primary + break; + } + + break; + } + case 7: + { + if (isOwner && isCustomizable && index >= 0 && index < m_HangerNumbers.Length) + { + Item hanger = foundation.SignHanger; + + if (hanger != null) + hanger.ItemID = m_HangerNumbers[index]; + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Customize, from, m_House)); + } + + break; + } + case 8: + { + if (isOwner && isCustomizable) + { + FoundationType newType; + + if (Core.ML && index >= 5) + switch (index) + { + case 5: + newType = FoundationType.ElvenGrey; + break; + case 6: + newType = FoundationType.ElvenNatural; + break; + case 7: + newType = FoundationType.Crystal; + break; + case 8: + newType = FoundationType.Shadow; + break; + default: return; + } + else + switch (index) + { + case 0: + newType = FoundationType.DarkWood; + break; + case 1: + newType = FoundationType.LightWood; + break; + case 2: + newType = FoundationType.Dungeon; + break; + case 3: + newType = FoundationType.Brick; + break; + case 4: + newType = FoundationType.Stone; + break; + default: return; + } + + foundation.Type = newType; + + DesignState state = foundation.BackupState; + HouseFoundation.ApplyFoundation(newType, state.Components); + state.OnRevised(); + + state = foundation.DesignState; + HouseFoundation.ApplyFoundation(newType, state.Components); + state.OnRevised(); + + state = foundation.CurrentState; + HouseFoundation.ApplyFoundation(newType, state.Components); + state.OnRevised(); + + foundation.Delta(ItemDelta.Update); + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Customize, from, m_House)); + } + + break; + } + case 9: + { + if (isOwner && m_House.Public && index >= 0 && index < _HouseSigns.Count) + { + m_House.ChangeSignType(_HouseSigns[index]); + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Customize, from, m_House)); + } + + break; + } + case 10: + { + if (isOwner && m_List != null && index >= 0 && index < m_List.Count) + { + m_House.RemoveCoOwner(from, (Mobile)m_List[index]); + + if (m_House.CoOwners.Count > 0) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveCoOwner, from, m_House)); + else + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, m_House)); + } + + break; + } + case 11: + { + if (isCoOwner && m_List != null && index >= 0 && index < m_List.Count) + { + m_House.RemoveFriend(from, (Mobile)m_List[index]); + + if (m_House.Friends.Count > 0) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveFriend, from, m_House)); + else + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, m_House)); + } + + break; + } + case 12: + { + if (m_List != null && index >= 0 && index < m_List.Count) + { + m_House.RemoveBan(from, (Mobile)m_List[index]); + + if (m_House.Bans.Count > 0) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveBan, from, m_House)); + else + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, m_House)); + } + + break; + } + case 13: + { + if (m_List != null && index >= 0 && index < m_List.Count) + { + m_House.RemoveAccess(from, (Mobile)m_List[index]); + + if (m_House.Access.Count > 0) + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.RemoveAccess, from, m_House)); + else + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Security, from, m_House)); + } + + break; + } + case 14: + { + if (isOwner && isCustomizable && index >= 0 && index < m_PostNumbers.Length) + { + foundation.SignpostGraphic = m_PostNumbers[index]; + foundation.CheckSignpost(); + + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Customize, from, m_House)); + } + + break; + } + } + } + + private ArrayList Wrap(string value) + { + if (value == null || (value = value.Trim()).Length <= 0) + return null; + + string[] values = value.Split(' '); + ArrayList list = new ArrayList(); + string current = ""; + + for (int i = 0; i < values.Length; ++i) + { + string val = values[i]; + + string v = current.Length == 0 ? val : current + ' ' + val; + + if (v.Length < 10) + { + current = v; + } + else if (v.Length == 10) + { + list.Add(v); + + if (list.Count == 6) + return list; + + current = ""; + } + else if (val.Length <= 10) + { + list.Add(current); + + if (list.Count == 6) + return list; + + current = val; + } + else + { + while (v.Length >= 10) + { + list.Add(v.Substring(0, 10)); + + if (list.Count == 6) + return list; + + v = v.Substring(10); + } + + current = v; + } + } + + if (current.Length > 0) + list.Add(current); + + return list; + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/HouseTransferGump.cs b/Scripts/Gumps/HouseTransferGump.cs index 6b8c26b80..7729d4f68 100644 --- a/Scripts/Gumps/HouseTransferGump.cs +++ b/Scripts/Gumps/HouseTransferGump.cs @@ -3,60 +3,60 @@ using Server.Network; namespace Server.Gumps { - public class HouseTransferGump : Gump - { - private Mobile m_From, m_To; - private BaseHouse m_House; + public class HouseTransferGump : Gump + { + private Mobile m_From, m_To; + private BaseHouse m_House; - public HouseTransferGump( Mobile from, Mobile to, BaseHouse house ) : base( 110, 100 ) - { - m_From = from; - m_To = to; - m_House = house; + public HouseTransferGump(Mobile from, Mobile to, BaseHouse house) : base(110, 100) + { + m_From = from; + m_To = to; + m_House = house; - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 420, 280, 5054 ); + AddBackground(0, 0, 420, 280, 5054); - AddImageTiled( 10, 10, 400, 20, 2624 ); - AddAlphaRegion( 10, 10, 400, 20 ); + AddImageTiled(10, 10, 400, 20, 2624); + AddAlphaRegion(10, 10, 400, 20); - AddHtmlLocalized( 10, 10, 400, 20, 1060635, 30720, false, false ); //
WARNING
+ AddHtmlLocalized(10, 10, 400, 20, 1060635, 30720, false, false); //
WARNING
- AddImageTiled( 10, 40, 400, 200, 2624 ); - AddAlphaRegion( 10, 40, 400, 200 ); + AddImageTiled(10, 40, 400, 200, 2624); + AddAlphaRegion(10, 40, 400, 200); - /* Another player is attempting to initiate a house trade with you. - * In order for you to see this window, both you and the other person are standing within two paces of the house to be traded. - * If you click OKAY below, a house trade scroll will appear in your trade window and you can complete the transaction. - * This scroll is a distinctive blue color and will show the name of the house, the name of the owner of that house, and the sextant coordinates of the center of the house when you hover your mouse over it. - * In order for the transaction to be successful, you both must accept the trade and you both must remain within two paces of the house sign. - *

Accepting this house in trade will condemn any and all of your other houses that you may have. - * All of your houses on all shards will be affected. - *

In addition, you will not be able to place another house or have one transferred to you for one (1) real-life week.

- * Once you accept these terms, these effects cannot be reversed. - * Re-deeding or transferring your new house will not uncondemn your other house(s) nor will the one week timer be removed.

- * If you are absolutely certain you wish to proceed, click the button next to OKAY below. - * If you do not wish to trade for this house, click CANCEL. - */ - AddHtmlLocalized( 10, 40, 400, 200, 1062086, 32512, false, true ); + /* Another player is attempting to initiate a house trade with you. + * In order for you to see this window, both you and the other person are standing within two paces of the house to be traded. + * If you click OKAY below, a house trade scroll will appear in your trade window and you can complete the transaction. + * This scroll is a distinctive blue color and will show the name of the house, the name of the owner of that house, and the sextant coordinates of the center of the house when you hover your mouse over it. + * In order for the transaction to be successful, you both must accept the trade and you both must remain within two paces of the house sign. + *

Accepting this house in trade will condemn any and all of your other houses that you may have. + * All of your houses on all shards will be affected. + *

In addition, you will not be able to place another house or have one transferred to you for one (1) real-life week.

+ * Once you accept these terms, these effects cannot be reversed. + * Re-deeding or transferring your new house will not uncondemn your other house(s) nor will the one week timer be removed.

+ * If you are absolutely certain you wish to proceed, click the button next to OKAY below. + * If you do not wish to trade for this house, click CANCEL. + */ + AddHtmlLocalized(10, 40, 400, 200, 1062086, 32512, false, true); - AddImageTiled( 10, 250, 400, 20, 2624 ); - AddAlphaRegion( 10, 250, 400, 20 ); + AddImageTiled(10, 250, 400, 20, 2624); + AddAlphaRegion(10, 250, 400, 20); - AddButton( 10, 250, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 250, 170, 20, 1011036, 32767, false, false ); // OKAY + AddButton(10, 250, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 250, 170, 20, 1011036, 32767, false, false); // OKAY - AddButton( 210, 250, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 240, 250, 170, 20, 1011012, 32767, false, false ); // CANCEL - } + AddButton(210, 250, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(240, 250, 170, 20, 1011012, 32767, false, false); // CANCEL + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 1 && !m_House.Deleted ) - m_House.EndConfirmTransfer( m_From, m_To ); - } - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1 && !m_House.Deleted) + m_House.EndConfirmTransfer(m_From, m_To); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/NoticeGump.cs b/Scripts/Gumps/NoticeGump.cs index 27052580f..024b08c14 100644 --- a/Scripts/Gumps/NoticeGump.cs +++ b/Scripts/Gumps/NoticeGump.cs @@ -1,47 +1,49 @@ -using System; +using Server.Network; namespace Server.Gumps { - public delegate void NoticeGumpCallback( Mobile from, object state ); + public delegate void NoticeGumpCallback(Mobile from, object state); - public class NoticeGump : Gump - { - private NoticeGumpCallback m_Callback; - private object m_State; + public class NoticeGump : Gump + { + private NoticeGumpCallback m_Callback; + private object m_State; - public NoticeGump( int header, int headerColor, object content, int contentColor, int width, int height, NoticeGumpCallback callback, object state ) : base( (640 - width) / 2, (480 - height) / 2 ) - { - m_Callback = callback; - m_State = state; + public NoticeGump(int header, int headerColor, object content, int contentColor, int width, int height, + NoticeGumpCallback callback, object state) : base((640 - width) / 2, (480 - height) / 2) + { + m_Callback = callback; + m_State = state; - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, width, height, 5054 ); + AddBackground(0, 0, width, height, 5054); - AddImageTiled( 10, 10, width - 20, 20, 2624 ); - AddAlphaRegion( 10, 10, width - 20, 20 ); - AddHtmlLocalized( 10, 10, width - 20, 20, header, headerColor, false, false ); + AddImageTiled(10, 10, width - 20, 20, 2624); + AddAlphaRegion(10, 10, width - 20, 20); + AddHtmlLocalized(10, 10, width - 20, 20, header, headerColor, false, false); - AddImageTiled( 10, 40, width - 20, height - 80, 2624 ); - AddAlphaRegion( 10, 40, width - 20, height - 80 ); + AddImageTiled(10, 40, width - 20, height - 80, 2624); + AddAlphaRegion(10, 40, width - 20, height - 80); - if ( content is int i ) - AddHtmlLocalized( 10, 40, width - 20, height - 80, i, contentColor, false, true ); - else if ( content is string ) - AddHtml( 10, 40, width - 20, height - 80, $"{content}", false, true ); + if (content is int i) + AddHtmlLocalized(10, 40, width - 20, height - 80, i, contentColor, false, true); + else if (content is string) + AddHtml(10, 40, width - 20, height - 80, $"{content}", false, + true); - AddImageTiled( 10, height - 30, width - 20, 20, 2624 ); - AddAlphaRegion( 10, height - 30, width - 20, 20 ); - AddButton( 10, height - 30, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, height - 30, 120, 20, 1011036, 32767, false, false ); // OKAY - } + AddImageTiled(10, height - 30, width - 20, 20, 2624); + AddAlphaRegion(10, height - 30, width - 20, 20); + AddButton(10, height - 30, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, height - 30, 120, 20, 1011036, 32767, false, false); // OKAY + } - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Callback?.Invoke( sender.Mobile, m_State ); - } - } -} + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_Callback?.Invoke(sender.Mobile, m_State); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/PetResurrectGump.cs b/Scripts/Gumps/PetResurrectGump.cs index 8be59baad..84540a9f1 100644 --- a/Scripts/Gumps/PetResurrectGump.cs +++ b/Scripts/Gumps/PetResurrectGump.cs @@ -1,83 +1,84 @@ -using System; using Server.Mobiles; using Server.Network; namespace Server.Gumps { - public class PetResurrectGump : Gump - { - private BaseCreature m_Pet; - private double m_HitsScalar; + public class PetResurrectGump : Gump + { + private double m_HitsScalar; + private BaseCreature m_Pet; - public PetResurrectGump( Mobile from, BaseCreature pet ) - : this( from, pet, 0.0 ) - { - } + public PetResurrectGump(Mobile from, BaseCreature pet) + : this(from, pet, 0.0) + { + } - public PetResurrectGump( Mobile from, BaseCreature pet, double hitsScalar ) : base( 50, 50 ) - { - from.CloseGump( typeof( PetResurrectGump ) ); + public PetResurrectGump(Mobile from, BaseCreature pet, double hitsScalar) : base(50, 50) + { + from.CloseGump(typeof(PetResurrectGump)); - m_Pet = pet; - m_HitsScalar = hitsScalar; + m_Pet = pet; + m_HitsScalar = hitsScalar; - AddPage( 0 ); + AddPage(0); - AddBackground( 10, 10, 265, 140, 0x242C ); + AddBackground(10, 10, 265, 140, 0x242C); - AddItem( 205, 40, 0x4 ); - AddItem( 227, 40, 0x5 ); + AddItem(205, 40, 0x4); + AddItem(227, 40, 0x5); - AddItem( 180, 78, 0xCAE ); - AddItem( 195, 90, 0xCAD ); - AddItem( 218, 95, 0xCB0 ); + AddItem(180, 78, 0xCAE); + AddItem(195, 90, 0xCAD); + AddItem(218, 95, 0xCB0); - AddHtmlLocalized( 30, 30, 150, 75, 1049665, false, false ); //
Wilt thou sanctify the resurrection of:
- AddHtml( 30, 70, 150, 25, $"
{pet.Name}
", true, false ); + AddHtmlLocalized(30, 30, 150, 75, 1049665, false, + false); //
Wilt thou sanctify the resurrection of:
+ AddHtml(30, 70, 150, 25, $"
{pet.Name}
", true, false); - AddButton( 40, 105, 0x81A, 0x81B, 0x1, GumpButtonType.Reply, 0 ); // Okay - AddButton( 110, 105, 0x819, 0x818, 0x2, GumpButtonType.Reply, 0 ); // Cancel - } + AddButton(40, 105, 0x81A, 0x81B, 0x1, GumpButtonType.Reply, 0); // Okay + AddButton(110, 105, 0x819, 0x818, 0x2, GumpButtonType.Reply, 0); // Cancel + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_Pet.Deleted || !m_Pet.IsBonded || !m_Pet.IsDeadPet ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Pet.Deleted || !m_Pet.IsBonded || !m_Pet.IsDeadPet) + return; - Mobile from = state.Mobile; + Mobile from = state.Mobile; - if ( info.ButtonID == 1 ) - { - if ( m_Pet.Map == null || !m_Pet.Map.CanFit( m_Pet.Location, 16, false, false ) ) - { - from.SendLocalizedMessage( 503256 ); // You fail to resurrect the creature. - return; - } + if (info.ButtonID == 1) + { + if (m_Pet.Map == null || !m_Pet.Map.CanFit(m_Pet.Location, 16, false, false)) + { + from.SendLocalizedMessage(503256); // You fail to resurrect the creature. + return; + } - if ( m_Pet.Region != null && m_Pet.Region.IsPartOf( "Khaldun" ) ) //TODO: Confirm for pets, as per Bandage's script. - { - from.SendLocalizedMessage( 1010395 ); // The veil of death in this area is too strong and resists thy efforts to restore life. - return; - } + if (m_Pet.Region != null && m_Pet.Region.IsPartOf("Khaldun") + ) //TODO: Confirm for pets, as per Bandage's script. + { + from.SendLocalizedMessage( + 1010395); // The veil of death in this area is too strong and resists thy efforts to restore life. + return; + } - m_Pet.PlaySound( 0x214 ); - m_Pet.FixedEffect( 0x376A, 10, 16 ); - m_Pet.ResurrectPet(); + m_Pet.PlaySound(0x214); + m_Pet.FixedEffect(0x376A, 10, 16); + m_Pet.ResurrectPet(); - double decreaseAmount; + double decreaseAmount; - if ( from == m_Pet.ControlMaster ) - decreaseAmount = 0.1; - else - decreaseAmount = 0.2; + if (from == m_Pet.ControlMaster) + decreaseAmount = 0.1; + else + decreaseAmount = 0.2; - for ( int i = 0; i < m_Pet.Skills.Length; ++i ) //Decrease all skills on pet. - m_Pet.Skills[i].Base -= decreaseAmount; + for (int i = 0; i < m_Pet.Skills.Length; ++i) //Decrease all skills on pet. + m_Pet.Skills[i].Base -= decreaseAmount; - if ( !m_Pet.IsDeadPet && m_HitsScalar > 0 ) - m_Pet.Hits = (int)(m_Pet.HitsMax * m_HitsScalar); - } - - } - } -} + if (!m_Pet.IsDeadPet && m_HitsScalar > 0) + m_Pet.Hits = (int)(m_Pet.HitsMax * m_HitsScalar); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/PlayerVendorGumps.cs b/Scripts/Gumps/PlayerVendorGumps.cs index 273c51456..543c9b086 100644 --- a/Scripts/Gumps/PlayerVendorGumps.cs +++ b/Scripts/Gumps/PlayerVendorGumps.cs @@ -1,1039 +1,1050 @@ using System; using System.Collections.Generic; using System.Reflection; -using Server.Mobiles; -using Server.Items; -using Server.Network; using Server.HuePickers; +using Server.Items; +using Server.Mobiles; +using Server.Network; namespace Server.Gumps { - public class PlayerVendorBuyGump : Gump - { - private PlayerVendor m_Vendor; - private VendorItem m_VI; - - public PlayerVendorBuyGump( PlayerVendor vendor, VendorItem vi ) : base( 100, 200 ) - { - m_Vendor = vendor; - m_VI = vi; - - AddBackground( 100, 10, 300, 150, 5054 ); - - AddHtmlLocalized( 125, 20, 250, 24, 1019070, false, false ); // You have agreed to purchase: - - if ( !string.IsNullOrEmpty( vi.Description ) ) - AddLabel( 125, 45, 0, vi.Description ); - else - AddHtmlLocalized( 125, 45, 250, 24, 1019072, false, false ); // an item without a description - - AddHtmlLocalized( 125, 70, 250, 24, 1019071, false, false ); // for the amount of: - AddLabel( 125, 95, 0, vi.Price.ToString() ); - - AddButton( 250, 130, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 282, 130, 100, 24, 1011012, false, false ); // CANCEL - - AddButton( 120, 130, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 152, 130, 100, 24, 1011036, false, false ); // OKAY - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; - - if ( !m_Vendor.CanInteractWith( from, false ) ) - return; - - if ( m_Vendor.IsOwner( from ) ) - { - m_Vendor.SayTo( from, 503212 ); // You own this shop, just take what you want. - return; - } - - if ( info.ButtonID == 1 ) - { - m_Vendor.Say( from.Name ); - - if ( !m_VI.Valid || !m_VI.Item.IsChildOf( m_Vendor.Backpack ) ) - { - m_Vendor.SayTo( from, 503216 ); // You can't buy that. - return; - } - - int totalGold = 0; - - if ( from.Backpack != null ) - totalGold += from.Backpack.GetAmount( typeof( Gold ) ); - - totalGold += Banker.GetBalance( from ); - - if ( totalGold < m_VI.Price ) - { - m_Vendor.SayTo( from, 503205 ); // You cannot afford this item. - } - else if ( !from.PlaceInBackpack( m_VI.Item ) ) - { - m_Vendor.SayTo( from, 503204 ); // You do not have room in your backpack for this. - } - else - { - int leftPrice = m_VI.Price; - - if ( from.Backpack != null ) - leftPrice -= from.Backpack.ConsumeUpTo( typeof( Gold ), leftPrice ); - - if ( leftPrice > 0 ) - Banker.Withdraw( from, leftPrice ); - - m_Vendor.HoldGold += m_VI.Price; - - from.SendLocalizedMessage( 503201 ); // You take the item. - } - } - else - { - from.SendLocalizedMessage( 503207 ); // Cancelled purchase. - } - } - } - - public class PlayerVendorOwnerGump : Gump - { - private PlayerVendor m_Vendor; - - public PlayerVendorOwnerGump( PlayerVendor vendor ) : base( 50, 200 ) - { - m_Vendor = vendor; - - int perDay = m_Vendor.ChargePerDay; - - AddPage( 0 ); - AddBackground( 25, 10, 530, 140, 5054 ); - - AddHtmlLocalized( 425, 25, 120, 20, 1019068, false, false ); // See goods - AddButton( 390, 25, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 425, 48, 120, 20, 1019069, false, false ); // Customize - AddButton( 390, 48, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 425, 72, 120, 20, 1011012, false, false ); // CANCEL - AddButton( 390, 71, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - - AddHtmlLocalized( 40, 72, 260, 20, 1038321, false, false ); // Gold held for you: - AddLabel( 300, 72, 0, m_Vendor.HoldGold.ToString() ); - AddHtmlLocalized( 40, 96, 260, 20, 1038322, false, false ); // Gold held in my account: - AddLabel( 300, 96, 0, m_Vendor.BankAccount.ToString() ); - - //AddHtmlLocalized( 40, 120, 260, 20, 1038324, false, false ); // My charge per day is: - // Localization has changed, we must use a string here - AddHtml( 40, 120, 260, 20, "My charge per day is:", false, false ); - AddLabel( 300, 120, 0, perDay.ToString() ); - - double days = (m_Vendor.HoldGold + m_Vendor.BankAccount) / ((double)perDay); - - AddHtmlLocalized( 40, 25, 260, 20, 1038318, false, false ); // Amount of days I can work: - AddLabel( 300, 25, 0, ((int)days).ToString() ); - AddHtmlLocalized( 40, 48, 260, 20, 1038319, false, false ); // Earth days: - AddLabel( 300, 48, 0, ((int)(days / 12.0)).ToString() ); - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; - - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - switch ( info.ButtonID ) - { - case 1: - { - m_Vendor.OpenBackpack( from ); + public class PlayerVendorBuyGump : Gump + { + private PlayerVendor m_Vendor; + private VendorItem m_VI; + + public PlayerVendorBuyGump(PlayerVendor vendor, VendorItem vi) : base(100, 200) + { + m_Vendor = vendor; + m_VI = vi; + + AddBackground(100, 10, 300, 150, 5054); + + AddHtmlLocalized(125, 20, 250, 24, 1019070, false, false); // You have agreed to purchase: + + if (!string.IsNullOrEmpty(vi.Description)) + AddLabel(125, 45, 0, vi.Description); + else + AddHtmlLocalized(125, 45, 250, 24, 1019072, false, false); // an item without a description + + AddHtmlLocalized(125, 70, 250, 24, 1019071, false, false); // for the amount of: + AddLabel(125, 95, 0, vi.Price.ToString()); + + AddButton(250, 130, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(282, 130, 100, 24, 1011012, false, false); // CANCEL + + AddButton(120, 130, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(152, 130, 100, 24, 1011036, false, false); // OKAY + } + + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; + + if (!m_Vendor.CanInteractWith(from, false)) + return; + + if (m_Vendor.IsOwner(from)) + { + m_Vendor.SayTo(from, 503212); // You own this shop, just take what you want. + return; + } + + if (info.ButtonID == 1) + { + m_Vendor.Say(from.Name); + + if (!m_VI.Valid || !m_VI.Item.IsChildOf(m_Vendor.Backpack)) + { + m_Vendor.SayTo(from, 503216); // You can't buy that. + return; + } + + int totalGold = 0; + + if (from.Backpack != null) + totalGold += from.Backpack.GetAmount(typeof(Gold)); + + totalGold += Banker.GetBalance(from); + + if (totalGold < m_VI.Price) + { + m_Vendor.SayTo(from, 503205); // You cannot afford this item. + } + else if (!from.PlaceInBackpack(m_VI.Item)) + { + m_Vendor.SayTo(from, 503204); // You do not have room in your backpack for this. + } + else + { + int leftPrice = m_VI.Price; + + if (from.Backpack != null) + leftPrice -= from.Backpack.ConsumeUpTo(typeof(Gold), leftPrice); + + if (leftPrice > 0) + Banker.Withdraw(from, leftPrice); + + m_Vendor.HoldGold += m_VI.Price; + + from.SendLocalizedMessage(503201); // You take the item. + } + } + else + { + from.SendLocalizedMessage(503207); // Cancelled purchase. + } + } + } + + public class PlayerVendorOwnerGump : Gump + { + private PlayerVendor m_Vendor; + + public PlayerVendorOwnerGump(PlayerVendor vendor) : base(50, 200) + { + m_Vendor = vendor; + + int perDay = m_Vendor.ChargePerDay; + + AddPage(0); + AddBackground(25, 10, 530, 140, 5054); + + AddHtmlLocalized(425, 25, 120, 20, 1019068, false, false); // See goods + AddButton(390, 25, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(425, 48, 120, 20, 1019069, false, false); // Customize + AddButton(390, 48, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(425, 72, 120, 20, 1011012, false, false); // CANCEL + AddButton(390, 71, 4005, 4007, 0, GumpButtonType.Reply, 0); + + AddHtmlLocalized(40, 72, 260, 20, 1038321, false, false); // Gold held for you: + AddLabel(300, 72, 0, m_Vendor.HoldGold.ToString()); + AddHtmlLocalized(40, 96, 260, 20, 1038322, false, false); // Gold held in my account: + AddLabel(300, 96, 0, m_Vendor.BankAccount.ToString()); + + //AddHtmlLocalized( 40, 120, 260, 20, 1038324, false, false ); // My charge per day is: + // Localization has changed, we must use a string here + AddHtml(40, 120, 260, 20, "My charge per day is:", false, false); + AddLabel(300, 120, 0, perDay.ToString()); + + double days = (m_Vendor.HoldGold + m_Vendor.BankAccount) / (double)perDay; + + AddHtmlLocalized(40, 25, 260, 20, 1038318, false, false); // Amount of days I can work: + AddLabel(300, 25, 0, ((int)days).ToString()); + AddHtmlLocalized(40, 48, 260, 20, 1038319, false, false); // Earth days: + AddLabel(300, 48, 0, ((int)(days / 12.0)).ToString()); + } + + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; + + if (!m_Vendor.CanInteractWith(from, true)) + return; + + switch (info.ButtonID) + { + case 1: + { + m_Vendor.OpenBackpack(from); - break; - } - case 2: - { - from.SendGump( new PlayerVendorCustomizeGump( m_Vendor, from ) ); + break; + } + case 2: + { + from.SendGump(new PlayerVendorCustomizeGump(m_Vendor, from)); - break; - } - } - } - } + break; + } + } + } + } - public class NewPlayerVendorOwnerGump : Gump - { - private PlayerVendor m_Vendor; - - public NewPlayerVendorOwnerGump( PlayerVendor vendor ) : base( 50, 200 ) - { - m_Vendor = vendor; - - int perRealWorldDay = vendor.ChargePerRealWorldDay; - int goldHeld = vendor.HoldGold; - - AddBackground( 25, 10, 530, 180, 0x13BE ); - - AddImageTiled( 35, 20, 510, 160, 0xA40 ); - AddAlphaRegion( 35, 20, 510, 160 ); - - AddImage( 10, 0, 0x28DC ); - AddImage( 537, 175, 0x28DC ); - AddImage( 10, 175, 0x28DC ); - AddImage( 537, 0, 0x28DC ); - - if ( goldHeld < perRealWorldDay ) - { - int goldNeeded = perRealWorldDay - goldHeld; - - AddHtmlLocalized( 40, 35, 260, 20, 1038320, 0x7FFF, false, false ); // Gold needed for 1 day of vendor salary: - AddLabel( 300, 35, 0x1F, goldNeeded.ToString() ); - } - else - { - int days = goldHeld / perRealWorldDay; - - AddHtmlLocalized( 40, 35, 260, 20, 1038318, 0x7FFF, false, false ); // # of days Vendor salary is paid for: - AddLabel( 300, 35, 0x480, days.ToString() ); - } - - AddHtmlLocalized( 40, 58, 260, 20, 1038324, 0x7FFF, false, false ); // My charge per real world day is: - AddLabel( 300, 58, 0x480, perRealWorldDay.ToString() ); - - AddHtmlLocalized( 40, 82, 260, 20, 1038322, 0x7FFF, false, false ); // Gold held in my account: - AddLabel( 300, 82, 0x480, goldHeld.ToString() ); - - AddHtmlLocalized( 40, 108, 260, 20, 1062509, 0x7FFF, false, false ); // Shop Name: - AddLabel( 140, 106, 0x66D, vendor.ShopName ); - - if ( vendor is RentedVendor rentedVendor ) - { - rentedVendor.ComputeRentalExpireDelay( out var days, out var hours ); - - AddLabel( 38, 132, 0x480, - $"Location rental will expire in {days} day{(days != 1 ? "s" : "")} and {hours} hour{(hours != 1 ? "s" : "")}."); - } - - AddButton( 390, 24, 0x15E1, 0x15E5, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 408, 21, 120, 20, 1019068, 0x7FFF, false, false ); // See goods - - AddButton( 390, 44, 0x15E1, 0x15E5, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 408, 41, 120, 20, 1019069, 0x7FFF, false, false ); // Customize - - AddButton( 390, 64, 0x15E1, 0x15E5, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 408, 61, 120, 20, 1062434, 0x7FFF, false, false ); // Rename Shop - - AddButton( 390, 84, 0x15E1, 0x15E5, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 408, 81, 120, 20, 3006217, 0x7FFF, false, false ); // Rename Vendor - - AddButton( 390, 104, 0x15E1, 0x15E5, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 408, 101, 120, 20, 3006123, 0x7FFF, false, false ); // Open Paperdoll - - AddButton( 390, 124, 0x15E1, 0x15E5, 6, GumpButtonType.Reply, 0 ); - AddLabel( 408, 121, 0x480, "Collect Gold" ); - - AddButton( 390, 144, 0x15E1, 0x15E5, 7, GumpButtonType.Reply, 0 ); - AddLabel( 408, 141, 0x480, "Dismiss Vendor" ); - - AddButton( 390, 162, 0x15E1, 0x15E5, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 408, 161, 120, 20, 1011012, 0x7FFF, false, false ); // CANCEL - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; - - if ( info.ButtonID == 1 || info.ButtonID == 2 ) // See goods or Customize - m_Vendor.CheckTeleport( from ); - - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - switch ( info.ButtonID ) - { - case 1: // See goods - { - m_Vendor.OpenBackpack( from ); - - break; - } - case 2: // Customize - { - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - - break; - } - case 3: // Rename Shop - { - m_Vendor.RenameShop( from ); - - break; - } - case 4: // Rename Vendor - { - m_Vendor.Rename( from ); - - break; - } - case 5: // Open Paperdoll - { - m_Vendor.DisplayPaperdollTo( from ); - - break; - } - case 6: // Collect Gold - { - m_Vendor.CollectGold( from ); - - break; - } - case 7: // Dismiss Vendor - { - m_Vendor.Dismiss( from ); - - break; - } - } - } - } - - public class PlayerVendorCustomizeGump : Gump - { - private Mobile m_Vendor; - - private class CustomItem - { - public CustomItem( int itemID, int loc ) : this( null, itemID, loc, 0, false ) - { - } - - public CustomItem( int itemID, int loc, bool longText ) : this( null, itemID, loc, 0, longText ) - { - } - - public CustomItem( Type type, int loc ) : this( type, loc, 0 ) - { - } - - public CustomItem( Type type, int loc, int art ) : this( type, 0, loc, art, false ) - { - } - - public CustomItem( Type type, int itemID, int loc, int art, bool longText ) - { - Type = type; - ItemID = itemID; - LocNumber = loc; - ArtNumber = art; - LongText = longText; - } - - public Item Create() - { - if ( Type == null ) - return null; - - Item i = null; - - try - { - ConstructorInfo ctor = Type.GetConstructor( new Type[0] ); - if ( ctor != null ) - i = ctor.Invoke( null ) as Item; - } - catch - { - } - - return i; - } - - public Type Type { get; } - - public int ItemID { get; } - - public int LocNumber { get; } - - public int ArtNumber { get; } - - public bool LongText { get; } - } - - private class CustomCategory - { - public CustomCategory( Layer layer, int loc, bool canDye, CustomItem[] items ) - { - Entries = items; - CanDye = canDye; - Layer = layer; - LocNumber = loc; - } - - public bool CanDye { get; } - - public CustomItem[] Entries { get; } - - public Layer Layer { get; } - - public int LocNumber { get; } - } - - private static CustomCategory[] Categories = { - new CustomCategory( Layer.InnerTorso, 1011357, true, new[]{// Upper Torso - new CustomItem( typeof( Shirt ), 1011359, 5399 ), - new CustomItem( typeof( FancyShirt ), 1011360, 7933 ), - new CustomItem( typeof( PlainDress ), 1011363, 7937 ), - new CustomItem( typeof( FancyDress ), 1011364, 7935 ), - new CustomItem( typeof( Robe ), 1011365, 7939 ) - } ), - - new CustomCategory( Layer.MiddleTorso, 1011371, true, new[]{//Over chest - new CustomItem( typeof( Doublet ), 1011358, 8059 ), - new CustomItem( typeof( Tunic ), 1011361, 8097 ), - new CustomItem( typeof( JesterSuit ), 1011366, 8095 ), - new CustomItem( typeof( BodySash ), 1011372, 5441 ), - new CustomItem( typeof( Surcoat ), 1011362, 8189 ), - new CustomItem( typeof( HalfApron ), 1011373, 5435 ), - new CustomItem( typeof( FullApron ), 1011374, 5437 ), - } ), - - new CustomCategory( Layer.Shoes, 1011388, true, new[]{//Footwear - new CustomItem( typeof( Sandals ), 1011389, 5901 ), - new CustomItem( typeof( Shoes ), 1011390, 5904 ), - new CustomItem( typeof( Boots ), 1011391, 5899 ), - new CustomItem( typeof( ThighBoots ), 1011392, 5906 ), - } ), - - new CustomCategory( Layer.Helm, 1011375, true, new[]{//Hats - new CustomItem( typeof( SkullCap ), 1011376, 5444 ), - new CustomItem( typeof( Bandana ), 1011377, 5440 ), - new CustomItem( typeof( FloppyHat ), 1011378, 5907 ), - new CustomItem( typeof( WideBrimHat ), 1011379, 5908 ), - new CustomItem( typeof( Cap ), 1011380, 5909 ), - new CustomItem( typeof( TallStrawHat ), 1011382, 5910 ) - } ), - - new CustomCategory( Layer.Helm, 1015319, true, new[]{//More Hats - new CustomItem( typeof( StrawHat ), 1011382, 5911 ), - new CustomItem( typeof( WizardsHat ), 1011383, 5912 ), - new CustomItem( typeof( Bonnet ), 1011384, 5913 ), - new CustomItem( typeof( FeatheredHat ), 1011385, 5914 ), - new CustomItem( typeof( TricorneHat ), 1011386, 5915 ), - new CustomItem( typeof( JesterHat ), 1011387, 5916 ) - } ), - - new CustomCategory( Layer.Pants, 1011367, true, new[]{ //Lower Torso - new CustomItem( typeof( LongPants ), 1011368, 5433 ), - new CustomItem( typeof( Kilt ), 1011369, 5431 ), - new CustomItem( typeof( Skirt ), 1011370, 5398 ), - } ), - - new CustomCategory( Layer.Cloak, 1011393, true, new[]{ // Back - new CustomItem( typeof( Cloak ), 1011394, 5397 ) - } ), - - new CustomCategory( Layer.Hair, 1011395, true, new[]{ // Hair - new CustomItem( 0x203B, 1011052 ), - new CustomItem( 0x203C, 1011053 ), - new CustomItem( 0x203D, 1011054 ), - new CustomItem( 0x2044, 1011055 ), - new CustomItem( 0x2045, 1011047 ), - new CustomItem( 0x204A, 1011050 ), - new CustomItem( 0x2047, 1011396 ), - new CustomItem( 0x2048, 1011048 ), - new CustomItem( 0x2049, 1011049 ), - } ), - - new CustomCategory( Layer.FacialHair, 1015320, true, new[]{//Facial Hair - new CustomItem( 0x2041, 1011062 ), - new CustomItem( 0x203F, 1011060 ), - new CustomItem( 0x204B, 1015321, true ), - new CustomItem( 0x203E, 1011061 ), - new CustomItem( 0x204C, 1015322, true ), - new CustomItem( 0x2040, 1015323 ), - new CustomItem( 0x204D, 1011401 ), - } ), - - new CustomCategory( Layer.FirstValid, 1011397, false, new[]{//Held items - new CustomItem( typeof( FishingPole ), 1011406, 3520 ), - new CustomItem( typeof( Pickaxe ), 1011407, 3717 ), - new CustomItem( typeof( Pitchfork ), 1011408, 3720 ), - new CustomItem( typeof( Cleaver ), 1015324, 3778 ), - new CustomItem( typeof( Mace ), 1011409, 3933 ), - new CustomItem( typeof( Torch ), 1011410, 3940 ), - new CustomItem( typeof( Hammer ), 1011411, 4020 ), - new CustomItem( typeof( Longsword ), 1011412, 3936 ), - new CustomItem( typeof( GnarledStaff ), 1011413, 5113 ) - } ), - - new CustomCategory( Layer.FirstValid, 1015325, false, new[]{//More held items - new CustomItem( typeof( Crossbow ), 1011414, 3920 ), - new CustomItem( typeof( WarMace ), 1011415, 5126 ), - new CustomItem( typeof( TwoHandedAxe ), 1011416, 5186 ), - new CustomItem( typeof( Spear ), 1011417, 3939 ), - new CustomItem( typeof( Katana ), 1011418, 5118 ), - new CustomItem( typeof( Spellbook ), 1011419, 3834 ) - } ) - }; - - public PlayerVendorCustomizeGump( Mobile v, Mobile from ) : base( 30, 40 ) - { - m_Vendor = v; - int x,y; - - from.CloseGump( typeof( PlayerVendorCustomizeGump ) ); - - AddPage( 0 ); - AddBackground( 0, 0, 585, 393, 5054 ); - AddBackground( 195, 36, 387, 275, 3000 ); - AddHtmlLocalized( 10, 10, 565, 18, 1011356, false, false ); //
VENDOR CUSTOMIZATION MENU
- AddHtmlLocalized( 60, 355, 150, 18, 1011036, false, false ); // OKAY - AddButton( 25, 355, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 320, 355, 150, 18, 1011012, false, false ); // CANCEL - AddButton( 285, 355, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - - y = 35; - for ( int i=0;i 0 ) - { - int cnum = info.Switches[0]; - int cat = cnum%256; - int ent = cnum>>8; - - if ( cat < Categories.Length && cat >= 0 ) - { - if ( ent < Categories[cat].Entries.Length && ent >= 0 ) - { - Item item = m_Vendor.FindItemOnLayer( Categories[cat].Layer ); - - item?.Delete(); - - List items = m_Vendor.Items; - - for ( int i = 0; item == null && i < items.Count; ++i ) - { - Item checkitem = items[i]; - Type type = checkitem.GetType(); - - for ( int j = 0; item == null && j < Categories[cat].Entries.Length; ++j ) - { - if ( type == Categories[cat].Entries[j].Type ) - item = checkitem; - } - } - - item?.Delete(); - - if ( Categories[cat].Layer == Layer.FacialHair ) - { - if ( m_Vendor.Female ) - { - from.SendLocalizedMessage( 1010639 ); // You cannot place facial hair on a woman! - } - else - { - int hue = m_Vendor.FacialHairHue; - - m_Vendor.FacialHairItemID = 0; - m_Vendor.ProcessDelta(); // invalidate item ID for clients - - m_Vendor.FacialHairItemID = Categories[cat].Entries[ent].ItemID; - m_Vendor.FacialHairHue = hue; - } - } - else if ( Categories[cat].Layer == Layer.Hair ) - { - int hue = m_Vendor.HairHue; - - m_Vendor.HairItemID = 0; - m_Vendor.ProcessDelta(); // invalidate item ID for clients - - m_Vendor.HairItemID = Categories[cat].Entries[ent].ItemID; - m_Vendor.HairHue = hue; - } - else - { - item = Categories[cat].Entries[ent].Create(); - - if ( item != null ) - { - item.Layer = Categories[cat].Layer; - - if ( !m_Vendor.EquipItem( item ) ) - item.Delete(); - } - } - - from.SendGump( new PlayerVendorCustomizeGump( m_Vendor, from ) ); - } - } - else - { - cat -= 100; - - if ( cat < 100 ) - { - if ( cat < Categories.Length && cat >= 0 ) - { - CustomCategory category = Categories[cat]; - - if ( category.Layer == Layer.Hair ) - { - new PVHairHuePicker( false, m_Vendor, from ).SendTo( state ); - } - else if ( category.Layer == Layer.FacialHair ) - { - new PVHairHuePicker( true, m_Vendor, from ).SendTo( state ); - } - else - { - Item item = null; - - List items = m_Vendor.Items; - - for ( int i = 0; item == null && i < items.Count; ++i ) - { - Item checkitem = items[i]; - Type type = checkitem.GetType(); - - for ( int j = 0; item == null && j < category.Entries.Length; ++j ) - { - if ( type == category.Entries[j].Type ) - item = checkitem; - } - } - - if ( item != null ) - new PVHuePicker( item, m_Vendor, from ).SendTo( state ); - } - } - } - else - { - cat -= 100; - - if ( cat < Categories.Length && cat >= 0 ) - { - CustomCategory category = Categories[cat]; - - if ( category.Layer == Layer.Hair ) - { - m_Vendor.HairItemID = 0; - } - else if ( category.Layer == Layer.FacialHair ) - { - m_Vendor.FacialHairItemID = 0; - } - else - { - Item item = null; - - List items = m_Vendor.Items; - - for ( int i = 0; item == null && i < items.Count; ++i ) - { - Item checkitem = items[i]; - Type type = checkitem.GetType(); - - for ( int j = 0; item == null && j < category.Entries.Length; ++j ) - { - if ( type == category.Entries[j].Type ) - item = checkitem; - } - } - - item?.Delete(); - } - - from.SendGump( new PlayerVendorCustomizeGump( m_Vendor, from ) ); - } - } - } - } - } - - private class PVHuePicker : HuePicker - { - private Item m_Item; - private Mobile m_Vendor; - private Mobile m_Mob; - - public PVHuePicker( Item item, Mobile v, Mobile from ) : base( item.ItemID ) - { - m_Item = item; - m_Vendor = v; - m_Mob = from; - } - - public override void OnResponse( int hue ) - { - if ( m_Item.Deleted ) - return; - - if ( m_Vendor is PlayerVendor vendor && !vendor.CanInteractWith( m_Mob, true ) ) - return; - - if ( m_Vendor is PlayerBarkeeper barkeeper && !barkeeper.IsOwner( m_Mob ) ) - return; - - m_Item.Hue = hue; - m_Mob.SendGump( new PlayerVendorCustomizeGump( m_Vendor, m_Mob ) ); - } - } - - private class PVHairHuePicker : HuePicker - { - private bool m_FacialHair; - private Mobile m_Vendor; - private Mobile m_Mob; - - public PVHairHuePicker( bool facialHair, Mobile v, Mobile from ) : base( 0xFAB ) - { - m_FacialHair = facialHair; - m_Vendor = v; - m_Mob = from; - } - - public override void OnResponse( int hue ) - { - if ( m_Vendor.Deleted ) - return; - - if ( m_Vendor is PlayerVendor vendor && !vendor.CanInteractWith( m_Mob, true ) ) - return; - - if ( m_Vendor is PlayerBarkeeper barkeeper && !barkeeper.IsOwner( m_Mob ) ) - return; - - if ( m_FacialHair ) - m_Vendor.FacialHairHue = hue; - else - m_Vendor.HairHue = hue; - - m_Mob.SendGump( new PlayerVendorCustomizeGump( m_Vendor, m_Mob ) ); - } - } - } - - public class NewPlayerVendorCustomizeGump : Gump - { - private PlayerVendor m_Vendor; - - private class HairOrBeard - { - public int ItemID { get; } - - public int Name { get; } - - public HairOrBeard( int itemID, int name ) - { - ItemID = itemID; - Name = name; - } - } - - private static HairOrBeard[] m_HairStyles = { - new HairOrBeard( 0x203B, 1011052 ), // Short - new HairOrBeard( 0x203C, 1011053 ), // Long - new HairOrBeard( 0x203D, 1011054 ), // Ponytail - new HairOrBeard( 0x2044, 1011055 ), // Mohawk - new HairOrBeard( 0x2045, 1011047 ), // Pageboy - new HairOrBeard( 0x204A, 1011050 ), // Topknot - new HairOrBeard( 0x2047, 1011396 ), // Curly - new HairOrBeard( 0x2048, 1011048 ), // Receding - new HairOrBeard( 0x2049, 1011049 ) // 2-tails - }; - - private static HairOrBeard[] m_BeardStyles = { - new HairOrBeard( 0x2041, 1011062 ), // Mustache - new HairOrBeard( 0x203F, 1011060 ), // Short beard - new HairOrBeard( 0x204B, 1015321 ), // Short Beard & Moustache - new HairOrBeard( 0x203E, 1011061 ), // Long beard - new HairOrBeard( 0x204C, 1015322 ), // Long Beard & Moustache - new HairOrBeard( 0x2040, 1015323 ), // Goatee - new HairOrBeard( 0x204D, 1011401 ) // Vandyke - }; - - public NewPlayerVendorCustomizeGump( PlayerVendor vendor ) : base( 50, 50 ) - { - m_Vendor = vendor; - - AddBackground( 0, 0, 370, 370, 0x13BE ); - - AddImageTiled( 10, 10, 350, 20, 0xA40 ); - AddImageTiled( 10, 40, 350, 20, 0xA40 ); - AddImageTiled( 10, 70, 350, 260, 0xA40 ); - AddImageTiled( 10, 340, 350, 20, 0xA40 ); - - AddAlphaRegion( 10, 10, 350, 350 ); - - AddHtmlLocalized( 10, 12, 350, 18, 1011356, 0x7FFF, false, false ); //
VENDOR CUSTOMIZATION MENU
- - AddHtmlLocalized( 10, 42, 150, 18, 1062459, 0x421F, false, false ); //
HAIR
- - for ( int i = 0; i < m_HairStyles.Length; i++ ) - { - HairOrBeard hair = m_HairStyles[i]; - - AddButton( 10, 70 + i * 20, 0xFA5, 0xFA7, 0x100 | i, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 72 + i * 20, 110, 18, hair.Name, 0x7FFF, false, false ); - } - - AddButton( 10, 70 + m_HairStyles.Length * 20, 0xFB1, 0xFB3, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 72 + m_HairStyles.Length * 20, 110, 18, 1011403, 0x7FFF, false, false ); // Remove - - AddButton( 10, 70 + (m_HairStyles.Length + 1) * 20, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 72 + (m_HairStyles.Length + 1) * 20, 110, 18, 1011402, 0x7FFF, false, false ); // Color - - if ( vendor.Female ) - { - AddButton( 160, 290, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 292, 160, 18, 1015327, 0x7FFF, false, false ); // Male - - AddHtmlLocalized( 195, 312, 160, 18, 1015328, 0x421F, false, false ); // Female - } - else - { - AddHtmlLocalized( 160, 42, 210, 18, 1062460, 0x421F, false, false ); //
BEARD
- - for ( int i = 0; i < m_BeardStyles.Length; i++ ) - { - HairOrBeard beard = m_BeardStyles[i]; - - AddButton( 160, 70 + i * 20, 0xFA5, 0xFA7, 0x200 | i, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 72 + i * 20, 160, 18, beard.Name, 0x7FFF, false, false ); - } - - AddButton( 160, 70 + m_BeardStyles.Length * 20, 0xFB1, 0xFB3, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 72 + m_BeardStyles.Length * 20, 160, 18, 1011403, 0x7FFF, false, false ); // Remove - - AddButton( 160, 70 + (m_BeardStyles.Length + 1) * 20, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 72 + (m_BeardStyles.Length + 1) * 20, 160, 18, 1011402, 0x7FFF, false, false ); // Color - - AddHtmlLocalized( 195, 292, 160, 18, 1015327, 0x421F, false, false ); // Male - - AddButton( 160, 310, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 312, 160, 18, 1015328, 0x7FFF, false, false ); // Female - } - - AddButton( 10, 340, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 342, 305, 18, 1060675, 0x7FFF, false, false ); // CLOSE - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; - - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - switch ( info.ButtonID ) - { - case 0: // CLOSE - { - m_Vendor.Direction = m_Vendor.GetDirectionTo( from ); - m_Vendor.Animate( 32, 5, 1, true, false, 0 ); // bow - m_Vendor.SayTo( from, 1043310 + Utility.Random( 12 ) ); // a little random speech - - break; - } - case 1: // Female/Male - { - if ( m_Vendor.Female ) - { - m_Vendor.BodyValue = 400; - m_Vendor.Female = false; - } - else - { - m_Vendor.BodyValue = 401; - m_Vendor.Female = true; - - m_Vendor.FacialHairItemID = 0; - } + public class NewPlayerVendorOwnerGump : Gump + { + private PlayerVendor m_Vendor; + + public NewPlayerVendorOwnerGump(PlayerVendor vendor) : base(50, 200) + { + m_Vendor = vendor; + + int perRealWorldDay = vendor.ChargePerRealWorldDay; + int goldHeld = vendor.HoldGold; + + AddBackground(25, 10, 530, 180, 0x13BE); + + AddImageTiled(35, 20, 510, 160, 0xA40); + AddAlphaRegion(35, 20, 510, 160); + + AddImage(10, 0, 0x28DC); + AddImage(537, 175, 0x28DC); + AddImage(10, 175, 0x28DC); + AddImage(537, 0, 0x28DC); + + if (goldHeld < perRealWorldDay) + { + int goldNeeded = perRealWorldDay - goldHeld; + + AddHtmlLocalized(40, 35, 260, 20, 1038320, 0x7FFF, false, false); // Gold needed for 1 day of vendor salary: + AddLabel(300, 35, 0x1F, goldNeeded.ToString()); + } + else + { + int days = goldHeld / perRealWorldDay; + + AddHtmlLocalized(40, 35, 260, 20, 1038318, 0x7FFF, false, false); // # of days Vendor salary is paid for: + AddLabel(300, 35, 0x480, days.ToString()); + } + + AddHtmlLocalized(40, 58, 260, 20, 1038324, 0x7FFF, false, false); // My charge per real world day is: + AddLabel(300, 58, 0x480, perRealWorldDay.ToString()); + + AddHtmlLocalized(40, 82, 260, 20, 1038322, 0x7FFF, false, false); // Gold held in my account: + AddLabel(300, 82, 0x480, goldHeld.ToString()); + + AddHtmlLocalized(40, 108, 260, 20, 1062509, 0x7FFF, false, false); // Shop Name: + AddLabel(140, 106, 0x66D, vendor.ShopName); + + if (vendor is RentedVendor rentedVendor) + { + rentedVendor.ComputeRentalExpireDelay(out int days, out int hours); + + AddLabel(38, 132, 0x480, + $"Location rental will expire in {days} day{(days != 1 ? "s" : "")} and {hours} hour{(hours != 1 ? "s" : "")}."); + } + + AddButton(390, 24, 0x15E1, 0x15E5, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(408, 21, 120, 20, 1019068, 0x7FFF, false, false); // See goods + + AddButton(390, 44, 0x15E1, 0x15E5, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(408, 41, 120, 20, 1019069, 0x7FFF, false, false); // Customize + + AddButton(390, 64, 0x15E1, 0x15E5, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(408, 61, 120, 20, 1062434, 0x7FFF, false, false); // Rename Shop + + AddButton(390, 84, 0x15E1, 0x15E5, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(408, 81, 120, 20, 3006217, 0x7FFF, false, false); // Rename Vendor + + AddButton(390, 104, 0x15E1, 0x15E5, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(408, 101, 120, 20, 3006123, 0x7FFF, false, false); // Open Paperdoll + + AddButton(390, 124, 0x15E1, 0x15E5, 6, GumpButtonType.Reply, 0); + AddLabel(408, 121, 0x480, "Collect Gold"); + + AddButton(390, 144, 0x15E1, 0x15E5, 7, GumpButtonType.Reply, 0); + AddLabel(408, 141, 0x480, "Dismiss Vendor"); + + AddButton(390, 162, 0x15E1, 0x15E5, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(408, 161, 120, 20, 1011012, 0x7FFF, false, false); // CANCEL + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; + + if (info.ButtonID == 1 || info.ButtonID == 2) // See goods or Customize + m_Vendor.CheckTeleport(from); + + if (!m_Vendor.CanInteractWith(from, true)) + return; + + switch (info.ButtonID) + { + case 1: // See goods + { + m_Vendor.OpenBackpack(from); + + break; + } + case 2: // Customize + { + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + + break; + } + case 3: // Rename Shop + { + m_Vendor.RenameShop(from); + + break; + } + case 4: // Rename Vendor + { + m_Vendor.Rename(from); + + break; + } + case 5: // Open Paperdoll + { + m_Vendor.DisplayPaperdollTo(from); + + break; + } + case 6: // Collect Gold + { + m_Vendor.CollectGold(from); + + break; + } + case 7: // Dismiss Vendor + { + m_Vendor.Dismiss(from); + + break; + } + } + } + } + + public class PlayerVendorCustomizeGump : Gump + { + private static CustomCategory[] Categories = + { + new CustomCategory(Layer.InnerTorso, 1011357, true, new[] + { + // Upper Torso + new CustomItem(typeof(Shirt), 1011359, 5399), + new CustomItem(typeof(FancyShirt), 1011360, 7933), + new CustomItem(typeof(PlainDress), 1011363, 7937), + new CustomItem(typeof(FancyDress), 1011364, 7935), + new CustomItem(typeof(Robe), 1011365, 7939) + }), + + new CustomCategory(Layer.MiddleTorso, 1011371, true, new[] + { + //Over chest + new CustomItem(typeof(Doublet), 1011358, 8059), + new CustomItem(typeof(Tunic), 1011361, 8097), + new CustomItem(typeof(JesterSuit), 1011366, 8095), + new CustomItem(typeof(BodySash), 1011372, 5441), + new CustomItem(typeof(Surcoat), 1011362, 8189), + new CustomItem(typeof(HalfApron), 1011373, 5435), + new CustomItem(typeof(FullApron), 1011374, 5437) + }), + + new CustomCategory(Layer.Shoes, 1011388, true, new[] + { + //Footwear + new CustomItem(typeof(Sandals), 1011389, 5901), + new CustomItem(typeof(Shoes), 1011390, 5904), + new CustomItem(typeof(Boots), 1011391, 5899), + new CustomItem(typeof(ThighBoots), 1011392, 5906) + }), + + new CustomCategory(Layer.Helm, 1011375, true, new[] + { + //Hats + new CustomItem(typeof(SkullCap), 1011376, 5444), + new CustomItem(typeof(Bandana), 1011377, 5440), + new CustomItem(typeof(FloppyHat), 1011378, 5907), + new CustomItem(typeof(WideBrimHat), 1011379, 5908), + new CustomItem(typeof(Cap), 1011380, 5909), + new CustomItem(typeof(TallStrawHat), 1011382, 5910) + }), + + new CustomCategory(Layer.Helm, 1015319, true, new[] + { + //More Hats + new CustomItem(typeof(StrawHat), 1011382, 5911), + new CustomItem(typeof(WizardsHat), 1011383, 5912), + new CustomItem(typeof(Bonnet), 1011384, 5913), + new CustomItem(typeof(FeatheredHat), 1011385, 5914), + new CustomItem(typeof(TricorneHat), 1011386, 5915), + new CustomItem(typeof(JesterHat), 1011387, 5916) + }), + + new CustomCategory(Layer.Pants, 1011367, true, new[] + { + //Lower Torso + new CustomItem(typeof(LongPants), 1011368, 5433), + new CustomItem(typeof(Kilt), 1011369, 5431), + new CustomItem(typeof(Skirt), 1011370, 5398) + }), + + new CustomCategory(Layer.Cloak, 1011393, true, new[] + { + // Back + new CustomItem(typeof(Cloak), 1011394, 5397) + }), + + new CustomCategory(Layer.Hair, 1011395, true, new[] + { + // Hair + new CustomItem(0x203B, 1011052), + new CustomItem(0x203C, 1011053), + new CustomItem(0x203D, 1011054), + new CustomItem(0x2044, 1011055), + new CustomItem(0x2045, 1011047), + new CustomItem(0x204A, 1011050), + new CustomItem(0x2047, 1011396), + new CustomItem(0x2048, 1011048), + new CustomItem(0x2049, 1011049) + }), + + new CustomCategory(Layer.FacialHair, 1015320, true, new[] + { + //Facial Hair + new CustomItem(0x2041, 1011062), + new CustomItem(0x203F, 1011060), + new CustomItem(0x204B, 1015321, true), + new CustomItem(0x203E, 1011061), + new CustomItem(0x204C, 1015322, true), + new CustomItem(0x2040, 1015323), + new CustomItem(0x204D, 1011401) + }), + + new CustomCategory(Layer.FirstValid, 1011397, false, new[] + { + //Held items + new CustomItem(typeof(FishingPole), 1011406, 3520), + new CustomItem(typeof(Pickaxe), 1011407, 3717), + new CustomItem(typeof(Pitchfork), 1011408, 3720), + new CustomItem(typeof(Cleaver), 1015324, 3778), + new CustomItem(typeof(Mace), 1011409, 3933), + new CustomItem(typeof(Torch), 1011410, 3940), + new CustomItem(typeof(Hammer), 1011411, 4020), + new CustomItem(typeof(Longsword), 1011412, 3936), + new CustomItem(typeof(GnarledStaff), 1011413, 5113) + }), + + new CustomCategory(Layer.FirstValid, 1015325, false, new[] + { + //More held items + new CustomItem(typeof(Crossbow), 1011414, 3920), + new CustomItem(typeof(WarMace), 1011415, 5126), + new CustomItem(typeof(TwoHandedAxe), 1011416, 5186), + new CustomItem(typeof(Spear), 1011417, 3939), + new CustomItem(typeof(Katana), 1011418, 5118), + new CustomItem(typeof(Spellbook), 1011419, 3834) + }) + }; + + private Mobile m_Vendor; + + public PlayerVendorCustomizeGump(Mobile v, Mobile from) : base(30, 40) + { + m_Vendor = v; + int x, y; + + from.CloseGump(typeof(PlayerVendorCustomizeGump)); + + AddPage(0); + AddBackground(0, 0, 585, 393, 5054); + AddBackground(195, 36, 387, 275, 3000); + AddHtmlLocalized(10, 10, 565, 18, 1011356, false, false); //
VENDOR CUSTOMIZATION MENU
+ AddHtmlLocalized(60, 355, 150, 18, 1011036, false, false); // OKAY + AddButton(25, 355, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(320, 355, 150, 18, 1011012, false, false); // CANCEL + AddButton(285, 355, 4005, 4007, 0, GumpButtonType.Reply, 0); + + y = 35; + for (int i = 0; i < Categories.Length; i++) + { + CustomCategory cat = Categories[i]; + AddHtmlLocalized(5, y, 150, 25, cat.LocNumber, true, false); + AddButton(155, y, 4005, 4007, 0, GumpButtonType.Page, i + 1); + y += 25; + } + + for (int i = 0; i < Categories.Length; i++) + { + CustomCategory cat = Categories[i]; + AddPage(i + 1); + + for (int c = 0; c < cat.Entries.Length; c++) + { + CustomItem entry = cat.Entries[c]; + x = 198 + c % 3 * 129; + y = 38 + c / 3 * 67; + + AddHtmlLocalized(x, y, 100, entry.LongText ? 36 : 18, entry.LocNumber, false, false); + + if (entry.ArtNumber != 0) + AddItem(x + 20, y + 25, entry.ArtNumber); + + AddRadio(x, y + (entry.LongText ? 40 : 20), 210, 211, false, (c << 8) + i); + } + + if (cat.CanDye) + { + AddHtmlLocalized(327, 239, 100, 18, 1011402, false, false); // Color + AddRadio(327, 259, 210, 211, false, 100 + i); + } + + AddHtmlLocalized(456, 239, 100, 18, 1011403, false, false); // Remove + AddRadio(456, 259, 210, 211, false, 200 + i); + } + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Vendor.Deleted) + return; + + Mobile from = state.Mobile; + + if (m_Vendor is PlayerVendor vendor && !vendor.CanInteractWith(from, true)) + return; + + if (m_Vendor is PlayerBarkeeper barkeeper && !barkeeper.IsOwner(from)) + return; + + if (info.ButtonID == 0) + { + if (m_Vendor is PlayerVendor) // do nothing for barkeeps + { + m_Vendor.Direction = m_Vendor.GetDirectionTo(from); + m_Vendor.Animate(32, 5, 1, true, false, 0); //bow + m_Vendor.SayTo(from, 1043310 + Utility.Random(12)); // a little random speech + } + } + else if (info.ButtonID == 1 && info.Switches.Length > 0) + { + int cnum = info.Switches[0]; + int cat = cnum % 256; + int ent = cnum >> 8; + + if (cat < Categories.Length && cat >= 0) + { + if (ent < Categories[cat].Entries.Length && ent >= 0) + { + Item item = m_Vendor.FindItemOnLayer(Categories[cat].Layer); + + item?.Delete(); + + List items = m_Vendor.Items; + + for (int i = 0; item == null && i < items.Count; ++i) + { + Item checkitem = items[i]; + Type type = checkitem.GetType(); + + for (int j = 0; item == null && j < Categories[cat].Entries.Length; ++j) + if (type == Categories[cat].Entries[j].Type) + item = checkitem; + } + + item?.Delete(); + + if (Categories[cat].Layer == Layer.FacialHair) + { + if (m_Vendor.Female) + { + from.SendLocalizedMessage(1010639); // You cannot place facial hair on a woman! + } + else + { + int hue = m_Vendor.FacialHairHue; + + m_Vendor.FacialHairItemID = 0; + m_Vendor.ProcessDelta(); // invalidate item ID for clients + + m_Vendor.FacialHairItemID = Categories[cat].Entries[ent].ItemID; + m_Vendor.FacialHairHue = hue; + } + } + else if (Categories[cat].Layer == Layer.Hair) + { + int hue = m_Vendor.HairHue; + + m_Vendor.HairItemID = 0; + m_Vendor.ProcessDelta(); // invalidate item ID for clients + + m_Vendor.HairItemID = Categories[cat].Entries[ent].ItemID; + m_Vendor.HairHue = hue; + } + else + { + item = Categories[cat].Entries[ent].Create(); + + if (item != null) + { + item.Layer = Categories[cat].Layer; + + if (!m_Vendor.EquipItem(item)) + item.Delete(); + } + } + + from.SendGump(new PlayerVendorCustomizeGump(m_Vendor, from)); + } + } + else + { + cat -= 100; + + if (cat < 100) + { + if (cat < Categories.Length && cat >= 0) + { + CustomCategory category = Categories[cat]; + + if (category.Layer == Layer.Hair) + { + new PVHairHuePicker(false, m_Vendor, from).SendTo(state); + } + else if (category.Layer == Layer.FacialHair) + { + new PVHairHuePicker(true, m_Vendor, from).SendTo(state); + } + else + { + Item item = null; + + List items = m_Vendor.Items; + + for (int i = 0; item == null && i < items.Count; ++i) + { + Item checkitem = items[i]; + Type type = checkitem.GetType(); + + for (int j = 0; item == null && j < category.Entries.Length; ++j) + if (type == category.Entries[j].Type) + item = checkitem; + } + + if (item != null) + new PVHuePicker(item, m_Vendor, from).SendTo(state); + } + } + } + else + { + cat -= 100; + + if (cat < Categories.Length && cat >= 0) + { + CustomCategory category = Categories[cat]; + + if (category.Layer == Layer.Hair) + { + m_Vendor.HairItemID = 0; + } + else if (category.Layer == Layer.FacialHair) + { + m_Vendor.FacialHairItemID = 0; + } + else + { + Item item = null; + + List items = m_Vendor.Items; + + for (int i = 0; item == null && i < items.Count; ++i) + { + Item checkitem = items[i]; + Type type = checkitem.GetType(); + + for (int j = 0; item == null && j < category.Entries.Length; ++j) + if (type == category.Entries[j].Type) + item = checkitem; + } + + item?.Delete(); + } + + from.SendGump(new PlayerVendorCustomizeGump(m_Vendor, from)); + } + } + } + } + } + + private class CustomItem + { + public CustomItem(int itemID, int loc) : this(null, itemID, loc, 0, false) + { + } + + public CustomItem(int itemID, int loc, bool longText) : this(null, itemID, loc, 0, longText) + { + } + + public CustomItem(Type type, int loc) : this(type, loc, 0) + { + } + + public CustomItem(Type type, int loc, int art) : this(type, 0, loc, art, false) + { + } + + public CustomItem(Type type, int itemID, int loc, int art, bool longText) + { + Type = type; + ItemID = itemID; + LocNumber = loc; + ArtNumber = art; + LongText = longText; + } + + public Type Type{ get; } + + public int ItemID{ get; } + + public int LocNumber{ get; } + + public int ArtNumber{ get; } + + public bool LongText{ get; } + + public Item Create() + { + if (Type == null) + return null; + + Item i = null; + + try + { + ConstructorInfo ctor = Type.GetConstructor(new Type[0]); + if (ctor != null) + i = ctor.Invoke(null) as Item; + } + catch + { + } + + return i; + } + } + + private class CustomCategory + { + public CustomCategory(Layer layer, int loc, bool canDye, CustomItem[] items) + { + Entries = items; + CanDye = canDye; + Layer = layer; + LocNumber = loc; + } + + public bool CanDye{ get; } + + public CustomItem[] Entries{ get; } + + public Layer Layer{ get; } + + public int LocNumber{ get; } + } + + private class PVHuePicker : HuePicker + { + private Item m_Item; + private Mobile m_Mob; + private Mobile m_Vendor; + + public PVHuePicker(Item item, Mobile v, Mobile from) : base(item.ItemID) + { + m_Item = item; + m_Vendor = v; + m_Mob = from; + } + + public override void OnResponse(int hue) + { + if (m_Item.Deleted) + return; + + if (m_Vendor is PlayerVendor vendor && !vendor.CanInteractWith(m_Mob, true)) + return; + + if (m_Vendor is PlayerBarkeeper barkeeper && !barkeeper.IsOwner(m_Mob)) + return; + + m_Item.Hue = hue; + m_Mob.SendGump(new PlayerVendorCustomizeGump(m_Vendor, m_Mob)); + } + } + + private class PVHairHuePicker : HuePicker + { + private bool m_FacialHair; + private Mobile m_Mob; + private Mobile m_Vendor; + + public PVHairHuePicker(bool facialHair, Mobile v, Mobile from) : base(0xFAB) + { + m_FacialHair = facialHair; + m_Vendor = v; + m_Mob = from; + } + + public override void OnResponse(int hue) + { + if (m_Vendor.Deleted) + return; + + if (m_Vendor is PlayerVendor vendor && !vendor.CanInteractWith(m_Mob, true)) + return; + + if (m_Vendor is PlayerBarkeeper barkeeper && !barkeeper.IsOwner(m_Mob)) + return; + + if (m_FacialHair) + m_Vendor.FacialHairHue = hue; + else + m_Vendor.HairHue = hue; + + m_Mob.SendGump(new PlayerVendorCustomizeGump(m_Vendor, m_Mob)); + } + } + } + + public class NewPlayerVendorCustomizeGump : Gump + { + private static HairOrBeard[] m_HairStyles = + { + new HairOrBeard(0x203B, 1011052), // Short + new HairOrBeard(0x203C, 1011053), // Long + new HairOrBeard(0x203D, 1011054), // Ponytail + new HairOrBeard(0x2044, 1011055), // Mohawk + new HairOrBeard(0x2045, 1011047), // Pageboy + new HairOrBeard(0x204A, 1011050), // Topknot + new HairOrBeard(0x2047, 1011396), // Curly + new HairOrBeard(0x2048, 1011048), // Receding + new HairOrBeard(0x2049, 1011049) // 2-tails + }; + + private static HairOrBeard[] m_BeardStyles = + { + new HairOrBeard(0x2041, 1011062), // Mustache + new HairOrBeard(0x203F, 1011060), // Short beard + new HairOrBeard(0x204B, 1015321), // Short Beard & Moustache + new HairOrBeard(0x203E, 1011061), // Long beard + new HairOrBeard(0x204C, 1015322), // Long Beard & Moustache + new HairOrBeard(0x2040, 1015323), // Goatee + new HairOrBeard(0x204D, 1011401) // Vandyke + }; + + private PlayerVendor m_Vendor; + + public NewPlayerVendorCustomizeGump(PlayerVendor vendor) : base(50, 50) + { + m_Vendor = vendor; + + AddBackground(0, 0, 370, 370, 0x13BE); + + AddImageTiled(10, 10, 350, 20, 0xA40); + AddImageTiled(10, 40, 350, 20, 0xA40); + AddImageTiled(10, 70, 350, 260, 0xA40); + AddImageTiled(10, 340, 350, 20, 0xA40); + + AddAlphaRegion(10, 10, 350, 350); + + AddHtmlLocalized(10, 12, 350, 18, 1011356, 0x7FFF, false, false); //
VENDOR CUSTOMIZATION MENU
+ + AddHtmlLocalized(10, 42, 150, 18, 1062459, 0x421F, false, false); //
HAIR
+ + for (int i = 0; i < m_HairStyles.Length; i++) + { + HairOrBeard hair = m_HairStyles[i]; + + AddButton(10, 70 + i * 20, 0xFA5, 0xFA7, 0x100 | i, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 72 + i * 20, 110, 18, hair.Name, 0x7FFF, false, false); + } + + AddButton(10, 70 + m_HairStyles.Length * 20, 0xFB1, 0xFB3, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 72 + m_HairStyles.Length * 20, 110, 18, 1011403, 0x7FFF, false, false); // Remove + + AddButton(10, 70 + (m_HairStyles.Length + 1) * 20, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 72 + (m_HairStyles.Length + 1) * 20, 110, 18, 1011402, 0x7FFF, false, false); // Color + + if (vendor.Female) + { + AddButton(160, 290, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 292, 160, 18, 1015327, 0x7FFF, false, false); // Male + + AddHtmlLocalized(195, 312, 160, 18, 1015328, 0x421F, false, false); // Female + } + else + { + AddHtmlLocalized(160, 42, 210, 18, 1062460, 0x421F, false, false); //
BEARD
+ + for (int i = 0; i < m_BeardStyles.Length; i++) + { + HairOrBeard beard = m_BeardStyles[i]; + + AddButton(160, 70 + i * 20, 0xFA5, 0xFA7, 0x200 | i, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 72 + i * 20, 160, 18, beard.Name, 0x7FFF, false, false); + } + + AddButton(160, 70 + m_BeardStyles.Length * 20, 0xFB1, 0xFB3, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 72 + m_BeardStyles.Length * 20, 160, 18, 1011403, 0x7FFF, false, false); // Remove + + AddButton(160, 70 + (m_BeardStyles.Length + 1) * 20, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 72 + (m_BeardStyles.Length + 1) * 20, 160, 18, 1011402, 0x7FFF, false, false); // Color + + AddHtmlLocalized(195, 292, 160, 18, 1015327, 0x421F, false, false); // Male + + AddButton(160, 310, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 312, 160, 18, 1015328, 0x7FFF, false, false); // Female + } + + AddButton(10, 340, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 342, 305, 18, 1060675, 0x7FFF, false, false); // CLOSE + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; + + if (!m_Vendor.CanInteractWith(from, true)) + return; + + switch (info.ButtonID) + { + case 0: // CLOSE + { + m_Vendor.Direction = m_Vendor.GetDirectionTo(from); + m_Vendor.Animate(32, 5, 1, true, false, 0); // bow + m_Vendor.SayTo(from, 1043310 + Utility.Random(12)); // a little random speech - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); + break; + } + case 1: // Female/Male + { + if (m_Vendor.Female) + { + m_Vendor.BodyValue = 400; + m_Vendor.Female = false; + } + else + { + m_Vendor.BodyValue = 401; + m_Vendor.Female = true; - break; - } - case 2: // Remove hair - { - m_Vendor.HairItemID = 0; - - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - - break; - } - case 3: // Color hair - { - if ( m_Vendor.HairItemID > 0 ) - { - new PVHuePicker( m_Vendor, false, from ).SendTo( from.NetState ); - } - else - { - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - } - - break; - } - case 4: // Remove beard - { - m_Vendor.FacialHairItemID = 0; - - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - - break; - } - case 5: // Color beard - { - if ( m_Vendor.FacialHairItemID > 0 ) - { - new PVHuePicker( m_Vendor, true, from ).SendTo( from.NetState ); - } - else - { - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - } - - break; - } - default: - { - int hairhue = 0; - - if ( (info.ButtonID & 0x100) != 0 ) // Hair style selected - { - int index = info.ButtonID & 0xFF; - - if ( index >= m_HairStyles.Length ) - return; - - HairOrBeard hairStyle = m_HairStyles[index]; - - hairhue = m_Vendor.HairHue; - - m_Vendor.HairItemID = 0; - m_Vendor.ProcessDelta(); - - m_Vendor.HairItemID = hairStyle.ItemID; - - m_Vendor.HairHue = hairhue; - - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - } - else if ( (info.ButtonID & 0x200) != 0 ) // Beard style selected - { - if ( m_Vendor.Female ) - return; - - int index = info.ButtonID & 0xFF; - - if ( index >= m_BeardStyles.Length ) - return; - - HairOrBeard beardStyle = m_BeardStyles[index]; - - hairhue = m_Vendor.FacialHairHue; - - m_Vendor.FacialHairItemID = 0; - m_Vendor.ProcessDelta(); - - m_Vendor.FacialHairItemID = beardStyle.ItemID; - - m_Vendor.FacialHairHue = hairhue; - - from.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - } - - break; - } - } - } - - private class PVHuePicker : HuePicker - { - private PlayerVendor m_Vendor; - private bool m_FacialHair; - private Mobile m_From; - - public PVHuePicker( PlayerVendor vendor, bool facialHair, Mobile from ) : base( 0xFAB ) - { - m_Vendor = vendor; - m_FacialHair = facialHair; - m_From = from; - } - - public override void OnResponse( int hue ) - { - if ( !m_Vendor.CanInteractWith( m_From, true ) ) - return; - - if ( m_FacialHair ) - m_Vendor.FacialHairHue = hue; - else - m_Vendor.HairHue = hue; + m_Vendor.FacialHairItemID = 0; + } - m_From.SendGump( new NewPlayerVendorCustomizeGump( m_Vendor ) ); - } - } - } -} + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + + break; + } + case 2: // Remove hair + { + m_Vendor.HairItemID = 0; + + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + + break; + } + case 3: // Color hair + { + if (m_Vendor.HairItemID > 0) + new PVHuePicker(m_Vendor, false, from).SendTo(from.NetState); + else + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + + break; + } + case 4: // Remove beard + { + m_Vendor.FacialHairItemID = 0; + + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + + break; + } + case 5: // Color beard + { + if (m_Vendor.FacialHairItemID > 0) + new PVHuePicker(m_Vendor, true, from).SendTo(from.NetState); + else + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + + break; + } + default: + { + int hairhue = 0; + + if ((info.ButtonID & 0x100) != 0) // Hair style selected + { + int index = info.ButtonID & 0xFF; + + if (index >= m_HairStyles.Length) + return; + + HairOrBeard hairStyle = m_HairStyles[index]; + + hairhue = m_Vendor.HairHue; + + m_Vendor.HairItemID = 0; + m_Vendor.ProcessDelta(); + + m_Vendor.HairItemID = hairStyle.ItemID; + + m_Vendor.HairHue = hairhue; + + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + } + else if ((info.ButtonID & 0x200) != 0) // Beard style selected + { + if (m_Vendor.Female) + return; + + int index = info.ButtonID & 0xFF; + + if (index >= m_BeardStyles.Length) + return; + + HairOrBeard beardStyle = m_BeardStyles[index]; + + hairhue = m_Vendor.FacialHairHue; + + m_Vendor.FacialHairItemID = 0; + m_Vendor.ProcessDelta(); + + m_Vendor.FacialHairItemID = beardStyle.ItemID; + + m_Vendor.FacialHairHue = hairhue; + + from.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + } + + break; + } + } + } + + private class HairOrBeard + { + public HairOrBeard(int itemID, int name) + { + ItemID = itemID; + Name = name; + } + + public int ItemID{ get; } + + public int Name{ get; } + } + + private class PVHuePicker : HuePicker + { + private bool m_FacialHair; + private Mobile m_From; + private PlayerVendor m_Vendor; + + public PVHuePicker(PlayerVendor vendor, bool facialHair, Mobile from) : base(0xFAB) + { + m_Vendor = vendor; + m_FacialHair = facialHair; + m_From = from; + } + + public override void OnResponse(int hue) + { + if (!m_Vendor.CanInteractWith(m_From, true)) + return; + + if (m_FacialHair) + m_Vendor.FacialHairHue = hue; + else + m_Vendor.HairHue = hue; + + m_From.SendGump(new NewPlayerVendorCustomizeGump(m_Vendor)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/PolymorphGump.cs b/Scripts/Gumps/PolymorphGump.cs index 0a10ab8b3..188c8718b 100644 --- a/Scripts/Gumps/PolymorphGump.cs +++ b/Scripts/Gumps/PolymorphGump.cs @@ -4,239 +4,239 @@ using Server.Spells.Seventh; namespace Server.Gumps { - public class PolymorphEntry - { - public static readonly PolymorphEntry Chicken = new PolymorphEntry( 8401, 0xD0, 1015236, 15, 10 ); - public static readonly PolymorphEntry Dog = new PolymorphEntry( 8405, 0xD9, 1015237, 17, 10 ); - public static readonly PolymorphEntry Wolf = new PolymorphEntry( 8426, 0xE1, 1015238, 18, 10 ); - public static readonly PolymorphEntry Panther = new PolymorphEntry( 8473, 0xD6, 1015239, 20, 14 ); - public static readonly PolymorphEntry Gorilla = new PolymorphEntry( 8437, 0x1D, 1015240, 23, 10 ); - public static readonly PolymorphEntry BlackBear = new PolymorphEntry( 8399, 0xD3, 1015241, 22, 10 ); - public static readonly PolymorphEntry GrizzlyBear = new PolymorphEntry( 8411, 0xD4, 1015242, 22, 12 ); - public static readonly PolymorphEntry PolarBear = new PolymorphEntry( 8417, 0xD5, 1015243, 26, 10 ); - public static readonly PolymorphEntry HumanMale = new PolymorphEntry( 8397, 0x190, 1015244, 29, 8 ); - public static readonly PolymorphEntry HumanFemale = new PolymorphEntry( 8398, 0x191, 1015254, 29, 10 ); - public static readonly PolymorphEntry Slime = new PolymorphEntry( 8424, 0x33, 1015246, 5, 10 ); - public static readonly PolymorphEntry Orc = new PolymorphEntry( 8416, 0x11, 1015247, 29, 10 ); - public static readonly PolymorphEntry LizardMan = new PolymorphEntry( 8414, 0x21, 1015248, 26, 10 ); - public static readonly PolymorphEntry Gargoyle = new PolymorphEntry( 8409, 0x04, 1015249, 22, 10 ); - public static readonly PolymorphEntry Ogre = new PolymorphEntry( 8415, 0x01, 1015250, 24, 9 ); - public static readonly PolymorphEntry Troll = new PolymorphEntry( 8425, 0x36, 1015251, 25, 9 ); - public static readonly PolymorphEntry Ettin = new PolymorphEntry( 8408, 0x02, 1015252, 25, 8 ); - public static readonly PolymorphEntry Daemon = new PolymorphEntry( 8403, 0x09, 1015253, 25, 8 ); + public class PolymorphEntry + { + public static readonly PolymorphEntry Chicken = new PolymorphEntry(8401, 0xD0, 1015236, 15, 10); + public static readonly PolymorphEntry Dog = new PolymorphEntry(8405, 0xD9, 1015237, 17, 10); + public static readonly PolymorphEntry Wolf = new PolymorphEntry(8426, 0xE1, 1015238, 18, 10); + public static readonly PolymorphEntry Panther = new PolymorphEntry(8473, 0xD6, 1015239, 20, 14); + public static readonly PolymorphEntry Gorilla = new PolymorphEntry(8437, 0x1D, 1015240, 23, 10); + public static readonly PolymorphEntry BlackBear = new PolymorphEntry(8399, 0xD3, 1015241, 22, 10); + public static readonly PolymorphEntry GrizzlyBear = new PolymorphEntry(8411, 0xD4, 1015242, 22, 12); + public static readonly PolymorphEntry PolarBear = new PolymorphEntry(8417, 0xD5, 1015243, 26, 10); + public static readonly PolymorphEntry HumanMale = new PolymorphEntry(8397, 0x190, 1015244, 29, 8); + public static readonly PolymorphEntry HumanFemale = new PolymorphEntry(8398, 0x191, 1015254, 29, 10); + public static readonly PolymorphEntry Slime = new PolymorphEntry(8424, 0x33, 1015246, 5, 10); + public static readonly PolymorphEntry Orc = new PolymorphEntry(8416, 0x11, 1015247, 29, 10); + public static readonly PolymorphEntry LizardMan = new PolymorphEntry(8414, 0x21, 1015248, 26, 10); + public static readonly PolymorphEntry Gargoyle = new PolymorphEntry(8409, 0x04, 1015249, 22, 10); + public static readonly PolymorphEntry Ogre = new PolymorphEntry(8415, 0x01, 1015250, 24, 9); + public static readonly PolymorphEntry Troll = new PolymorphEntry(8425, 0x36, 1015251, 25, 9); + public static readonly PolymorphEntry Ettin = new PolymorphEntry(8408, 0x02, 1015252, 25, 8); + public static readonly PolymorphEntry Daemon = new PolymorphEntry(8403, 0x09, 1015253, 25, 8); - private PolymorphEntry( int Art, int Body, int LocNum, int X, int Y ) - { - ArtID = Art; - BodyID = Body; - LocNumber = LocNum; - this.X = X; - this.Y = Y; - } + private PolymorphEntry(int Art, int Body, int LocNum, int X, int Y) + { + ArtID = Art; + BodyID = Body; + LocNumber = LocNum; + this.X = X; + this.Y = Y; + } - public int ArtID { get; } + public int ArtID{ get; } - public int BodyID { get; } + public int BodyID{ get; } - public int LocNumber { get; } + public int LocNumber{ get; } - public int X { get; } + public int X{ get; } - public int Y { get; } - } + public int Y{ get; } + } - public class PolymorphGump : Gump - { - private class PolymorphCategory - { - public PolymorphCategory( int num, params PolymorphEntry[] entries ) - { - LocNumber = num; - Entries = entries; - } + public class PolymorphGump : Gump + { + private static PolymorphCategory[] Categories = + { + new PolymorphCategory(1015235, // Animals + PolymorphEntry.Chicken, + PolymorphEntry.Dog, + PolymorphEntry.Wolf, + PolymorphEntry.Panther, + PolymorphEntry.Gorilla, + PolymorphEntry.BlackBear, + PolymorphEntry.GrizzlyBear, + PolymorphEntry.PolarBear, + PolymorphEntry.HumanMale), - public PolymorphEntry[] Entries { get; } - - public int LocNumber { get; } - } - - private static PolymorphCategory[] Categories = { - new PolymorphCategory( 1015235, // Animals - PolymorphEntry.Chicken, - PolymorphEntry.Dog, - PolymorphEntry.Wolf, - PolymorphEntry.Panther, - PolymorphEntry.Gorilla, - PolymorphEntry.BlackBear, - PolymorphEntry.GrizzlyBear, - PolymorphEntry.PolarBear, - PolymorphEntry.HumanMale ), - - new PolymorphCategory( 1015245, // Monsters - PolymorphEntry.Slime, - PolymorphEntry.Orc, - PolymorphEntry.LizardMan, - PolymorphEntry.Gargoyle, - PolymorphEntry.Ogre, - PolymorphEntry.Troll, - PolymorphEntry.Ettin, - PolymorphEntry.Daemon, - PolymorphEntry.HumanFemale ) - }; + new PolymorphCategory(1015245, // Monsters + PolymorphEntry.Slime, + PolymorphEntry.Orc, + PolymorphEntry.LizardMan, + PolymorphEntry.Gargoyle, + PolymorphEntry.Ogre, + PolymorphEntry.Troll, + PolymorphEntry.Ettin, + PolymorphEntry.Daemon, + PolymorphEntry.HumanFemale) + }; - private Mobile m_Caster; - private Item m_Scroll; + private Mobile m_Caster; + private Item m_Scroll; - public PolymorphGump( Mobile caster, Item scroll ) : base( 50, 50 ) - { - m_Caster = caster; - m_Scroll = scroll; + public PolymorphGump(Mobile caster, Item scroll) : base(50, 50) + { + m_Caster = caster; + m_Scroll = scroll; - int x,y; - AddPage( 0 ); - AddBackground( 0, 0, 585, 393, 5054 ); - AddBackground( 195, 36, 387, 275, 3000 ); - AddHtmlLocalized( 0, 0, 510, 18, 1015234, false, false ); //
Polymorph Selection Menu
- AddHtmlLocalized( 60, 355, 150, 18, 1011036, false, false ); // OKAY - AddButton( 25, 355, 4005, 4007, 1, GumpButtonType.Reply, 1 ); - AddHtmlLocalized( 320, 355, 150, 18, 1011012, false, false ); // CANCEL - AddButton( 285, 355, 4005, 4007, 0, GumpButtonType.Reply, 2 ); + int x, y; + AddPage(0); + AddBackground(0, 0, 585, 393, 5054); + AddBackground(195, 36, 387, 275, 3000); + AddHtmlLocalized(0, 0, 510, 18, 1015234, false, false); //
Polymorph Selection Menu
+ AddHtmlLocalized(60, 355, 150, 18, 1011036, false, false); // OKAY + AddButton(25, 355, 4005, 4007, 1, GumpButtonType.Reply, 1); + AddHtmlLocalized(320, 355, 150, 18, 1011012, false, false); // CANCEL + AddButton(285, 355, 4005, 4007, 0, GumpButtonType.Reply, 2); - y = 35; - for ( int i=0;i 0 ) - { - int cnum = info.Switches[0]; - int cat = cnum%256; - int ent = cnum>>8; + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1 && info.Switches.Length > 0) + { + int cnum = info.Switches[0]; + int cat = cnum % 256; + int ent = cnum >> 8; - if ( cat >= 0 && cat < Categories.Length ) - { - if ( ent >= 0 && ent < Categories[cat].Entries.Length ) - { - Spell spell = new PolymorphSpell( m_Caster, m_Scroll, Categories[cat].Entries[ent].BodyID ); - spell.Cast(); - } - } - } - } - } + if (cat >= 0 && cat < Categories.Length) + if (ent >= 0 && ent < Categories[cat].Entries.Length) + { + Spell spell = new PolymorphSpell(m_Caster, m_Scroll, Categories[cat].Entries[ent].BodyID); + spell.Cast(); + } + } + } - public class NewPolymorphGump : Gump - { - private static readonly PolymorphEntry[] m_Entries = { - PolymorphEntry.Chicken, - PolymorphEntry.Dog, - PolymorphEntry.Wolf, - PolymorphEntry.Panther, - PolymorphEntry.Gorilla, - PolymorphEntry.BlackBear, - PolymorphEntry.GrizzlyBear, - PolymorphEntry.PolarBear, - PolymorphEntry.HumanMale, - PolymorphEntry.HumanFemale, - PolymorphEntry.Slime, - PolymorphEntry.Orc, - PolymorphEntry.LizardMan, - PolymorphEntry.Gargoyle, - PolymorphEntry.Ogre, - PolymorphEntry.Troll, - PolymorphEntry.Ettin, - PolymorphEntry.Daemon - }; + private class PolymorphCategory + { + public PolymorphCategory(int num, params PolymorphEntry[] entries) + { + LocNumber = num; + Entries = entries; + } - private Mobile m_Caster; - private Item m_Scroll; + public PolymorphEntry[] Entries{ get; } - public NewPolymorphGump( Mobile caster, Item scroll ) : base( 0, 0 ) - { - m_Caster = caster; - m_Scroll = scroll; + public int LocNumber{ get; } + } + } - AddPage( 0 ); + public class NewPolymorphGump : Gump + { + private static readonly PolymorphEntry[] m_Entries = + { + PolymorphEntry.Chicken, + PolymorphEntry.Dog, + PolymorphEntry.Wolf, + PolymorphEntry.Panther, + PolymorphEntry.Gorilla, + PolymorphEntry.BlackBear, + PolymorphEntry.GrizzlyBear, + PolymorphEntry.PolarBear, + PolymorphEntry.HumanMale, + PolymorphEntry.HumanFemale, + PolymorphEntry.Slime, + PolymorphEntry.Orc, + PolymorphEntry.LizardMan, + PolymorphEntry.Gargoyle, + PolymorphEntry.Ogre, + PolymorphEntry.Troll, + PolymorphEntry.Ettin, + PolymorphEntry.Daemon + }; - AddBackground( 0, 0, 520, 404, 0x13BE ); - AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 324, 0xA40 ); - AddImageTiled( 10, 374, 500, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 500, 384 ); + private Mobile m_Caster; + private Item m_Scroll; - AddHtmlLocalized( 14, 12, 500, 20, 1015234, 0x7FFF, false, false ); //
Polymorph Selection Menu
+ public NewPolymorphGump(Mobile caster, Item scroll) : base(0, 0) + { + m_Caster = caster; + m_Scroll = scroll; - AddButton( 10, 374, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 376, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL + AddPage(0); - for ( int i = 0; i < m_Entries.Length; i++ ) - { - PolymorphEntry entry = m_Entries[i]; + AddBackground(0, 0, 520, 404, 0x13BE); + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 324, 0xA40); + AddImageTiled(10, 374, 500, 20, 0xA40); + AddAlphaRegion(10, 10, 500, 384); - int page = i / 10 + 1; - int pos = i % 10; + AddHtmlLocalized(14, 12, 500, 20, 1015234, 0x7FFF, false, false); //
Polymorph Selection Menu
- if ( pos == 0 ) - { - if ( page > 1 ) - { - AddButton( 400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, page ); - AddHtmlLocalized( 440, 376, 60, 20, 1043353, 0x7FFF, false, false ); // Next - } + AddButton(10, 374, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 376, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL - AddPage( page ); + for (int i = 0; i < m_Entries.Length; i++) + { + PolymorphEntry entry = m_Entries[i]; - if ( page > 1 ) - { - AddButton( 300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1 ); - AddHtmlLocalized( 340, 376, 60, 20, 1011393, 0x7FFF, false, false ); // Back - } - } + int page = i / 10 + 1; + int pos = i % 10; - int x = ( pos % 2 == 0 ) ? 14 : 264; - int y = ( pos / 2 ) * 64 + 44; + if (pos == 0) + { + if (page > 1) + { + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, page); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next + } - AddImageTiledButton( x, y, 0x918, 0x919, i + 1, GumpButtonType.Reply, 0, entry.ArtID, 0x0, entry.X, entry.Y ); - AddHtmlLocalized( x + 84, y, 250, 60, entry.LocNumber, 0x7FFF, false, false ); - } - } + AddPage(page); - public override void OnResponse( NetState sender, RelayInfo info ) - { - int idx = info.ButtonID - 1; + if (page > 1) + { + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + } + } - if ( idx < 0 || idx >= m_Entries.Length ) - return; + int x = pos % 2 == 0 ? 14 : 264; + int y = pos / 2 * 64 + 44; - Spell spell = new PolymorphSpell( m_Caster, m_Scroll, m_Entries[idx].BodyID ); - spell.Cast(); - } - } -} + AddImageTiledButton(x, y, 0x918, 0x919, i + 1, GumpButtonType.Reply, 0, entry.ArtID, 0x0, entry.X, entry.Y); + AddHtmlLocalized(x + 84, y, 250, 60, entry.LocNumber, 0x7FFF, false, false); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int idx = info.ButtonID - 1; + + if (idx < 0 || idx >= m_Entries.Length) + return; + + Spell spell = new PolymorphSpell(m_Caster, m_Scroll, m_Entries[idx].BodyID); + spell.Cast(); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Props/PropsConfig.cs b/Scripts/Gumps/Props/PropsConfig.cs index e206b0f6d..1b0f23f8c 100644 --- a/Scripts/Gumps/Props/PropsConfig.cs +++ b/Scripts/Gumps/Props/PropsConfig.cs @@ -1,39 +1,42 @@ namespace Server.Gumps { - public class PropsConfig - { - public static readonly bool OldStyle = false; + public class PropsConfig + { + public static readonly bool OldStyle = false; - public static readonly int GumpOffsetX = 30; - public static readonly int GumpOffsetY = 30; + public static readonly int GumpOffsetX = 30; + public static readonly int GumpOffsetY = 30; - public static readonly int TextHue = 0; - public static readonly int TextOffsetX = 2; + public static readonly int TextHue = 0; + public static readonly int TextOffsetX = 2; - public static readonly int OffsetGumpID = 0x0A40; // Pure black - public static readonly int HeaderGumpID = OldStyle ? 0x0BBC : 0x0E14; // Light offwhite, textured : Dark navy blue, textured - public static readonly int EntryGumpID = 0x0BBC; // Light offwhite, textured - public static readonly int BackGumpID = 0x13BE; // Gray slate/stoney - public static readonly int SetGumpID = OldStyle ? 0x0000 : 0x0E14; // Empty : Dark navy blue, textured + public static readonly int OffsetGumpID = 0x0A40; // Pure black - public static readonly int SetWidth = 20; - public static readonly int SetOffsetX = OldStyle ? 4 : 2, SetOffsetY = 2; - public static readonly int SetButtonID1 = 0x15E1; // Arrow pointing right - public static readonly int SetButtonID2 = 0x15E5; // " pressed + public static readonly int + HeaderGumpID = OldStyle ? 0x0BBC : 0x0E14; // Light offwhite, textured : Dark navy blue, textured - public static readonly int PrevWidth = 20; - public static readonly int PrevOffsetX = 2, PrevOffsetY = 2; - public static readonly int PrevButtonID1 = 0x15E3; // Arrow pointing left - public static readonly int PrevButtonID2 = 0x15E7; // " pressed + public static readonly int EntryGumpID = 0x0BBC; // Light offwhite, textured + public static readonly int BackGumpID = 0x13BE; // Gray slate/stoney + public static readonly int SetGumpID = OldStyle ? 0x0000 : 0x0E14; // Empty : Dark navy blue, textured - public static readonly int NextWidth = 20; - public static readonly int NextOffsetX = 2, NextOffsetY = 2; - public static readonly int NextButtonID1 = 0x15E1; // Arrow pointing right - public static readonly int NextButtonID2 = 0x15E5; // " pressed + public static readonly int SetWidth = 20; + public static readonly int SetOffsetX = OldStyle ? 4 : 2, SetOffsetY = 2; + public static readonly int SetButtonID1 = 0x15E1; // Arrow pointing right + public static readonly int SetButtonID2 = 0x15E5; // " pressed - public static readonly int OffsetSize = 1; + public static readonly int PrevWidth = 20; + public static readonly int PrevOffsetX = 2, PrevOffsetY = 2; + public static readonly int PrevButtonID1 = 0x15E3; // Arrow pointing left + public static readonly int PrevButtonID2 = 0x15E7; // " pressed - public static readonly int EntryHeight = 20; - public static readonly int BorderSize = 10; - } + public static readonly int NextWidth = 20; + public static readonly int NextOffsetX = 2, NextOffsetY = 2; + public static readonly int NextButtonID1 = 0x15E1; // Arrow pointing right + public static readonly int NextButtonID2 = 0x15E5; // " pressed + + public static readonly int OffsetSize = 1; + + public static readonly int EntryHeight = 20; + public static readonly int BorderSize = 10; + } } \ No newline at end of file diff --git a/Scripts/Gumps/Props/PropsGump.cs b/Scripts/Gumps/Props/PropsGump.cs index 2e43b9394..4851c3965 100644 --- a/Scripts/Gumps/Props/PropsGump.cs +++ b/Scripts/Gumps/Props/PropsGump.cs @@ -8,747 +8,718 @@ using CPA = Server.CommandPropertyAttribute; namespace Server.Gumps { - public class StackEntry - { - public object m_Object; - public PropertyInfo m_Property; - - public StackEntry(object obj, PropertyInfo prop) - { - m_Object = obj; - m_Property = prop; - } - } - - public class PropertiesGump : Gump - { - private ArrayList m_List; - private int m_Page; - private Mobile m_Mobile; - private object m_Object; - private Type m_Type; - private Stack m_Stack; + public class StackEntry + { + public object m_Object; + public PropertyInfo m_Property; + + public StackEntry(object obj, PropertyInfo prop) + { + m_Object = obj; + m_Property = prop; + } + } + + public class PropertiesGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; + + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; + + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + + public static readonly int OffsetSize = PropsConfig.OffsetSize; + + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; + + private static bool PrevLabel = OldStyle, NextLabel = OldStyle; + private static bool TypeLabel = !OldStyle; + + private static readonly int PrevLabelOffsetX = PrevWidth + 1; + private static readonly int PrevLabelOffsetY = 0; + + private static readonly int NextLabelOffsetX = -29; + private static readonly int NextLabelOffsetY = 0; + + private static readonly int NameWidth = 107; + private static readonly int ValueWidth = 128; + + private static readonly int EntryCount = 15; + + private static readonly int TypeWidth = NameWidth + OffsetSize + ValueWidth; + + private static readonly int TotalWidth = + OffsetSize + NameWidth + OffsetSize + ValueWidth + OffsetSize + SetWidth + OffsetSize; + + private static readonly int TotalHeight = OffsetSize + (EntryHeight + OffsetSize) * (EntryCount + 1); + + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + + public static string[] m_BoolNames = { "True", "False" }; + public static object[] m_BoolValues = { true, false }; + + public static string[] m_PoisonNames = { "None", "Lesser", "Regular", "Greater", "Deadly", "Lethal" }; + + public static object[] m_PoisonValues = + { null, Poison.Lesser, Poison.Regular, Poison.Greater, Poison.Deadly, Poison.Lethal }; + + private static Type typeofMobile = typeof(Mobile); + private static Type typeofItem = typeof(Item); + private static Type typeofType = typeof(Type); + private static Type typeofPoint3D = typeof(Point3D); + private static Type typeofPoint2D = typeof(Point2D); + private static Type typeofTimeSpan = typeof(TimeSpan); + private static Type typeofCustomEnum = typeof(CustomEnumAttribute); + private static Type typeofEnum = typeof(Enum); + private static Type typeofBool = typeof(bool); + private static Type typeofString = typeof(string); + private static Type typeofText = typeof(TextDefinition); + private static Type typeofPoison = typeof(Poison); + private static Type typeofMap = typeof(Map); + private static Type typeofSkills = typeof(Skills); + private static Type typeofPropertyObject = typeof(PropertyObjectAttribute); + private static Type typeofNoSort = typeof(NoSortAttribute); + + private static Type[] typeofReal = + { + typeof(float), + typeof(double) + }; + + private static Type[] typeofNumeric = + { + typeof(byte), + typeof(short), + typeof(int), + typeof(long), + typeof(sbyte), + typeof(ushort), + typeof(uint), + typeof(ulong) + }; + + private static Type typeofCPA = typeof(CPA); + private static Type typeofObject = typeof(object); + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private Stack m_Stack; + private Type m_Type; + + public PropertiesGump(Mobile mobile, object o) : base(GumpOffsetX, GumpOffsetY) + { + m_Mobile = mobile; + m_Object = o; + m_Type = o.GetType(); + m_List = BuildList(); - public static readonly bool OldStyle = PropsConfig.OldStyle; + Initialize(0); + } - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public PropertiesGump(Mobile mobile, object o, Stack stack, StackEntry parent) : base(GumpOffsetX, + GumpOffsetY) + { + m_Mobile = mobile; + m_Object = o; + m_Type = o.GetType(); + m_Stack = stack; + m_List = BuildList(); - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; - - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - - public static readonly int OffsetSize = PropsConfig.OffsetSize; - - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; - - private static bool PrevLabel = OldStyle, NextLabel = OldStyle; - private static bool TypeLabel = !OldStyle; - - private static readonly int PrevLabelOffsetX = PrevWidth + 1; - private static readonly int PrevLabelOffsetY = 0; - - private static readonly int NextLabelOffsetX = -29; - private static readonly int NextLabelOffsetY = 0; - - private static readonly int NameWidth = 107; - private static readonly int ValueWidth = 128; - - private static readonly int EntryCount = 15; - - private static readonly int TypeWidth = NameWidth + OffsetSize + ValueWidth; - - private static readonly int TotalWidth = OffsetSize + NameWidth + OffsetSize + ValueWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (EntryCount + 1)); - - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; - - public PropertiesGump( Mobile mobile, object o ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Mobile = mobile; - m_Object = o; - m_Type = o.GetType(); - m_List = BuildList(); - - Initialize( 0 ); - } - - public PropertiesGump( Mobile mobile, object o, Stack stack, StackEntry parent ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Mobile = mobile; - m_Object = o; - m_Type = o.GetType(); - m_Stack = stack; - m_List = BuildList(); - - if ( parent != null ) - { - if ( m_Stack == null ) - m_Stack = new Stack(); - - m_Stack.Push( parent ); - } - - Initialize( 0 ); - } - - public PropertiesGump( Mobile mobile, object o, Stack stack, ArrayList list, int page ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Mobile = mobile; - m_Object = o; - - if ( o != null ) - m_Type = o.GetType(); - - m_List = list; - m_Stack = stack; - - Initialize( page ); - } - - private void Initialize( int page ) - { - m_Page = page; - - int count = m_List.Count - (page * EntryCount); - - if ( count < 0 ) - count = 0; - else if ( count > EntryCount ) - count = EntryCount; - - int lastIndex = (page * EntryCount) + count - 1; - - if ( lastIndex >= 0 && lastIndex < m_List.Count && m_List[lastIndex] == null ) - --count; - - int totalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (count + 1)); - - AddPage( 0 ); - - AddBackground( 0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, OffsetGumpID ); - - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; - - int emptyWidth = TotalWidth - PrevWidth - NextWidth - (OffsetSize * 4) - (OldStyle ? SetWidth + OffsetSize : 0); - - if ( OldStyle ) - AddImageTiled( x, y, TotalWidth - (OffsetSize * 3) - SetWidth, EntryHeight, HeaderGumpID ); - else - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); - - if ( page > 0 ) - { - AddButton( x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 1, GumpButtonType.Reply, 0 ); - - if ( PrevLabel ) - AddLabel( x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous" ); - } - - x += PrevWidth + OffsetSize; - - if ( !OldStyle ) - AddImageTiled( x, y, emptyWidth, EntryHeight, HeaderGumpID ); - - if ( TypeLabel && m_Type != null ) - AddHtml( x, y, emptyWidth, EntryHeight, - $"
{m_Type.Name}
", false, false ); - - x += emptyWidth + OffsetSize; - - if ( !OldStyle ) - AddImageTiled( x, y, NextWidth, EntryHeight, HeaderGumpID ); - - if ( (page + 1) * EntryCount < m_List.Count ) - { - AddButton( x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 2, GumpButtonType.Reply, 1 ); - - if ( NextLabel ) - AddLabel( x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next" ); - } - - for ( int i = 0, index = page * EntryCount; i < count && index < m_List.Count; ++i, ++index ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; - - object o = m_List[index]; - - if ( o == null ) - { - AddImageTiled( x - OffsetSize, y, TotalWidth, EntryHeight, BackGumpID + 4 ); - } - else if ( o is Type type ) - { - AddImageTiled( x, y, TypeWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, TypeWidth - TextOffsetX, EntryHeight, TextHue, type.Name ); - x += TypeWidth + OffsetSize; - - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - } - else if ( o is PropertyInfo prop ) - { - AddImageTiled( x, y, NameWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, NameWidth - TextOffsetX, EntryHeight, TextHue, prop.Name ); - x += NameWidth + OffsetSize; - AddImageTiled( x, y, ValueWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, ValueWidth - TextOffsetX, EntryHeight, TextHue, ValueToString( prop ) ); - x += ValueWidth + OffsetSize; - - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - - CPA cpa = GetCPA( prop ); - - if ( prop.CanWrite && cpa != null && m_Mobile.AccessLevel >= cpa.WriteLevel && !cpa.ReadOnly ) - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, i + 3, GumpButtonType.Reply, 0 ); - } - } - } - - public static string[] m_BoolNames = { "True", "False" }; - public static object[] m_BoolValues = { true, false }; - - public static string[] m_PoisonNames = { "None", "Lesser", "Regular", "Greater", "Deadly", "Lethal" }; - public static object[] m_PoisonValues = { null, Poison.Lesser, Poison.Regular, Poison.Greater, Poison.Deadly, Poison.Lethal }; - - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; - - if ( !BaseCommand.IsAccessible( from, m_Object ) ) - { - from.SendMessage( "You may no longer access their properties." ); - return; - } - - switch ( info.ButtonID ) - { - case 0: // Closed - { - if ( m_Stack != null && m_Stack.Count > 0 ) - { - StackEntry entry = m_Stack.Pop(); - - from.SendGump( new PropertiesGump( from, entry.m_Object, m_Stack, null ) ); - } - - break; - } - case 1: // Previous - { - if ( m_Page > 0 ) - from.SendGump( new PropertiesGump( from, m_Object, m_Stack, m_List, m_Page - 1 ) ); - - break; - } - case 2: // Next - { - if ( (m_Page + 1) * EntryCount < m_List.Count ) - from.SendGump( new PropertiesGump( from, m_Object, m_Stack, m_List, m_Page + 1 ) ); - - break; - } - default: - { - int index = (m_Page * EntryCount) + (info.ButtonID - 3); - - if ( index >= 0 && index < m_List.Count ) - { - PropertyInfo prop = m_List[index] as PropertyInfo; - - if ( prop == null ) - return; - - CPA attr = GetCPA( prop ); - - if ( !prop.CanWrite || attr == null || from.AccessLevel < attr.WriteLevel || attr.ReadOnly ) - return; - - Type type = prop.PropertyType; - - if ( IsType( type, typeofMobile ) || IsType( type, typeofItem ) ) - from.SendGump( new SetObjectGump( prop, from, m_Object, m_Stack, type, m_Page, m_List ) ); - else if ( IsType( type, typeofType ) ) - from.Target = new SetObjectTarget( prop, from, m_Object, m_Stack, type, m_Page, m_List ); - else if ( IsType( type, typeofPoint3D ) ) - from.SendGump( new SetPoint3DGump( prop, from, m_Object, m_Stack, m_Page, m_List ) ); - else if ( IsType( type, typeofPoint2D ) ) - from.SendGump( new SetPoint2DGump( prop, from, m_Object, m_Stack, m_Page, m_List ) ); - else if ( IsType( type, typeofTimeSpan ) ) - from.SendGump( new SetTimeSpanGump( prop, from, m_Object, m_Stack, m_Page, m_List ) ); - else if ( IsCustomEnum( type ) ) - from.SendGump( new SetCustomEnumGump( prop, from, m_Object, m_Stack, m_Page, m_List, GetCustomEnumNames( type ) ) ); - else if ( IsType( type, typeofEnum ) ) - from.SendGump( new SetListOptionGump( prop, from, m_Object, m_Stack, m_Page, m_List, Enum.GetNames( type ), GetObjects( Enum.GetValues( type ) ) ) ); - else if ( IsType( type, typeofBool ) ) - from.SendGump( new SetListOptionGump( prop, from, m_Object, m_Stack, m_Page, m_List, m_BoolNames, m_BoolValues ) ); - else if ( IsType( type, typeofString ) || IsType( type, typeofReal ) || IsType( type, typeofNumeric ) || IsType( type, typeofText ) ) - from.SendGump( new SetGump( prop, from, m_Object, m_Stack, m_Page, m_List ) ); - else if ( IsType( type, typeofPoison ) ) - from.SendGump( new SetListOptionGump( prop, from, m_Object, m_Stack, m_Page, m_List, m_PoisonNames, m_PoisonValues ) ); - else if ( IsType( type, typeofMap ) ) - from.SendGump( new SetListOptionGump( prop, from, m_Object, m_Stack, m_Page, m_List, Map.GetMapNames(), Map.GetMapValues() ) ); - else if ( IsType( type, typeofSkills ) && m_Object is Mobile mobile ) - { - from.SendGump( new PropertiesGump( from, mobile, m_Stack, m_List, m_Page ) ); - from.SendGump( new SkillsGump( from, mobile ) ); - } - else if ( HasAttribute( type, typeofPropertyObject, true ) ) - { - object obj = prop.GetValue( m_Object, null ); - - if ( obj != null ) - from.SendGump( new PropertiesGump( from, obj, m_Stack, new StackEntry( m_Object, prop ) ) ); - else - from.SendGump( new PropertiesGump( from, m_Object, m_Stack, m_List, m_Page ) ); - } - } - - break; - } - } - } - - private static object[] GetObjects( Array a ) - { - object[] list = new object[a.Length]; - - for ( int i = 0; i < list.Length; ++i ) - list[i] = a.GetValue( i ); - - return list; - } - - private static bool IsCustomEnum( Type type ) - { - return type.IsDefined( typeofCustomEnum, false ); - } - - public static void OnValueChanged( object obj, PropertyInfo prop, Stack stack ) - { - if ( stack == null || stack.Count == 0 ) - return; - - if ( !prop.PropertyType.IsValueType ) - return; - - StackEntry peek = stack.Peek(); - - if ( peek.m_Property.CanWrite ) - peek.m_Property.SetValue( peek.m_Object, obj, null ); - } - - private static string[] GetCustomEnumNames( Type type ) - { - object[] attrs = type.GetCustomAttributes( typeofCustomEnum, false ); - - if ( attrs.Length == 0 ) - return new string[0]; - - if ( !(attrs[0] is CustomEnumAttribute ce) ) - return new string[0]; - - return ce.Names; - } - - private static bool HasAttribute( Type type, Type check, bool inherit ) - { - object[] objs = type.GetCustomAttributes( check, inherit ); - - return ( objs != null && objs.Length > 0 ); - } - - private static bool IsType( Type type, Type check ) - { - return type == check || type.IsSubclassOf( check ); - } - - private static bool IsType( Type type, Type[] check ) - { - for ( int i = 0; i < check.Length; ++i ) - if ( IsType( type, check[i] ) ) - return true; - - return false; - } - - private static Type typeofMobile = typeof( Mobile ); - private static Type typeofItem = typeof( Item ); - private static Type typeofType = typeof( Type ); - private static Type typeofPoint3D = typeof( Point3D ); - private static Type typeofPoint2D = typeof( Point2D ); - private static Type typeofTimeSpan = typeof( TimeSpan ); - private static Type typeofCustomEnum = typeof( CustomEnumAttribute ); - private static Type typeofEnum = typeof( Enum ); - private static Type typeofBool = typeof( bool ); - private static Type typeofString = typeof( string ); - private static Type typeofText = typeof( TextDefinition ); - private static Type typeofPoison = typeof( Poison ); - private static Type typeofMap = typeof( Map ); - private static Type typeofSkills = typeof( Skills ); - private static Type typeofPropertyObject = typeof( PropertyObjectAttribute ); - private static Type typeofNoSort = typeof( NoSortAttribute ); - - private static Type[] typeofReal = { - typeof( float ), - typeof( double ) - }; - - private static Type[] typeofNumeric = { - typeof( byte ), - typeof( short ), - typeof( int ), - typeof( long ), - typeof( sbyte ), - typeof( ushort ), - typeof( uint ), - typeof( ulong ) - }; - - private string ValueToString( PropertyInfo prop ) - { - return ValueToString( m_Object, prop ); - } - - public static string ValueToString( object obj, PropertyInfo prop ) - { - try - { - return ValueToString( prop.GetValue( obj, null ) ); - } - catch ( Exception e ) - { - return $"!{e.GetType()}!"; - } - } - - public static string ValueToString( object o ) - { - if ( o == null ) - { - return "-null-"; - } - if ( o is string s ) - { - return $"\"{s}\""; - } - if ( o is bool ) - { - return o.ToString(); - } - if ( o is char c ) - { - return $"0x{(int) c:X} '{c}'"; - } - if ( o is Serial serial ) - { - if ( serial.IsValid ) - { - if ( serial.IsItem ) - { - return $"(I) 0x{serial.Value:X}"; - } - if ( serial.IsMobile ) - { - return $"(M) 0x{serial.Value:X}"; - } - } - - return $"(?) 0x{serial.Value:X}"; - } - if ( o is byte || o is sbyte || o is short || o is ushort || o is int || o is uint || o is long || o is ulong ) - { - return string.Format( "{0} (0x{0:X})", o ); - } - if ( o is Mobile mobile ) - { - return $"(M) 0x{mobile.Serial.Value:X} \"{mobile.Name}\""; - } - if ( o is Item item ) - { - return $"(I) 0x{item.Serial.Value:X}"; - } - if ( o is Type type ) - { - return type.Name; - } - if ( o is TextDefinition definition ) - { - return definition.Format( true ); - } - - return o.ToString(); - } - - private ArrayList BuildList() - { - ArrayList list = new ArrayList(); - - if ( m_Type == null ) - return list; - - PropertyInfo[] props = m_Type.GetProperties( BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public ); - - ArrayList groups = GetGroups( m_Type, props ); - - for ( int i = 0; i < groups.Count; ++i ) - { - DictionaryEntry de = (DictionaryEntry)groups[i]; - ArrayList groupList = (ArrayList)de.Value; - - if ( !HasAttribute( (Type)de.Key, typeofNoSort, false ) ) - groupList.Sort( PropertySorter.Instance ); - - if ( i != 0 ) - list.Add( null ); - - list.Add( de.Key ); - list.AddRange( groupList ); - } - - return list; - } - - private static Type typeofCPA = typeof( CPA ); - private static Type typeofObject = typeof( object ); - - private static CPA GetCPA( PropertyInfo prop ) - { - object[] attrs = prop.GetCustomAttributes( typeofCPA, false ); - - if ( attrs.Length > 0 ) - return attrs[0] as CPA; - return null; - } - - private ArrayList GetGroups( Type objectType, PropertyInfo[] props ) - { - Hashtable groups = new Hashtable(); - - for ( int i = 0; i < props.Length; ++i ) - { - PropertyInfo prop = props[i]; - - if ( prop.CanRead ) - { - CPA attr = GetCPA( prop ); - - if ( attr != null && m_Mobile.AccessLevel >= attr.ReadLevel ) - { - Type type = prop.DeclaringType; - - while ( true ) - { - Type baseType = type.BaseType; - - if ( baseType == null || baseType == typeofObject ) - break; - - if ( baseType.GetProperty( prop.Name, prop.PropertyType ) != null ) - type = baseType; - else - break; - } - - ArrayList list = (ArrayList)groups[type]; - - if ( list == null ) - groups[type] = list = new ArrayList(); - - list.Add( prop ); - } - } - } - - ArrayList sorted = new ArrayList( groups ); - - sorted.Sort( new GroupComparer( objectType ) ); - - return sorted; - } - - public static object GetObjectFromString( Type t, string s ) - { - if ( t == typeof( string ) ) - { - return s; - } - - if ( t == typeof( byte ) || t == typeof( sbyte ) || t == typeof( short ) || t == typeof( ushort ) || t == typeof( int ) || t == typeof( uint ) || t == typeof( long ) || t == typeof( ulong ) ) - { - if ( s.StartsWith( "0x" ) ) - { - if ( t == typeof( ulong ) || t == typeof( uint ) || t == typeof( ushort ) || t == typeof( byte ) ) - { - return Convert.ChangeType( Convert.ToUInt64( s.Substring( 2 ), 16 ), t ); - } - - return Convert.ChangeType( Convert.ToInt64( s.Substring( 2 ), 16 ), t ); - } - - return Convert.ChangeType( s, t ); - } - if ( t == typeof( double ) || t == typeof( float ) ) - { - return Convert.ChangeType( s, t ); - } - if ( t.IsDefined( typeof( ParsableAttribute ), false ) ) - { - MethodInfo parseMethod = t.GetMethod( "Parse", new[]{ typeof( string ) } ); - - return parseMethod.Invoke( null, new object[]{ s } ); - } - - throw new Exception( "bad" ); - } - - private static string GetStringFromObject( object o ) - { - if ( o == null ) - { - return "-null-"; - } - if ( o is string s ) - { - return $"\"{s}\""; - } - if ( o is bool ) - { - return o.ToString(); - } - if ( o is char c ) - { - return $"0x{(int) c:X} '{c}'"; - } - if ( o is Serial serial ) - { - if ( serial.IsValid ) - { - if ( serial.IsItem ) - { - return $"(I) 0x{serial.Value:X}"; - } - if ( serial.IsMobile ) - { - return $"(M) 0x{serial.Value:X}"; - } - } - - return $"(?) 0x{serial.Value:X}"; - } - if ( o is byte || o is sbyte || o is short || o is ushort || o is int || o is uint || o is long || o is ulong ) - { - return string.Format( "{0} (0x{0:X})", o ); - } - if ( o is Mobile mobile ) - { - return $"(M) 0x{mobile.Serial.Value:X} \"{mobile.Name}\""; - } - if ( o is Item item ) - { - return $"(I) 0x{item.Serial.Value:X}"; - } - if ( o is Type type ) - { - return type.Name; - } - - return o.ToString(); - } - - private class PropertySorter : IComparer - { - public static readonly PropertySorter Instance = new PropertySorter(); - - private PropertySorter() - { - } - - public int Compare( object x, object y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; - - PropertyInfo a = x as PropertyInfo; - PropertyInfo b = y as PropertyInfo; - - if ( a == null || b == null ) - throw new ArgumentException(); - - return a.Name.CompareTo( b.Name ); - } - } - - private class GroupComparer : IComparer - { - private Type m_Start; - - public GroupComparer( Type start ) - { - m_Start = start; - } - - private static Type typeofObject = typeof( object ); - - private int GetDistance( Type type ) - { - Type current = m_Start; - - int dist; - - for ( dist = 0; current != null && current != typeofObject && current != type; ++dist ) - current = current.BaseType; - - return dist; - } - - public int Compare( object x, object y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; - - if ( !(x is DictionaryEntry) || !(y is DictionaryEntry) ) - throw new ArgumentException(); - - DictionaryEntry de1 = (DictionaryEntry)x; - DictionaryEntry de2 = (DictionaryEntry)y; - - return GetDistance( (Type)de1.Key ).CompareTo( GetDistance( (Type)de2.Key ) ); - } - } - } -} + if (parent != null) + { + if (m_Stack == null) + m_Stack = new Stack(); + + m_Stack.Push(parent); + } + + Initialize(0); + } + + public PropertiesGump(Mobile mobile, object o, Stack stack, ArrayList list, int page) : base(GumpOffsetX, + GumpOffsetY) + { + m_Mobile = mobile; + m_Object = o; + + if (o != null) + m_Type = o.GetType(); + + m_List = list; + m_Stack = stack; + + Initialize(page); + } + + private void Initialize(int page) + { + m_Page = page; + + int count = m_List.Count - page * EntryCount; + + if (count < 0) + count = 0; + else if (count > EntryCount) + count = EntryCount; + + int lastIndex = page * EntryCount + count - 1; + + if (lastIndex >= 0 && lastIndex < m_List.Count && m_List[lastIndex] == null) + --count; + + int totalHeight = OffsetSize + (EntryHeight + OffsetSize) * (count + 1); + + AddPage(0); + + AddBackground(0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, + OffsetGumpID); + + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; + + int emptyWidth = TotalWidth - PrevWidth - NextWidth - OffsetSize * 4 - (OldStyle ? SetWidth + OffsetSize : 0); + + if (OldStyle) + AddImageTiled(x, y, TotalWidth - OffsetSize * 3 - SetWidth, EntryHeight, HeaderGumpID); + else + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); + + if (page > 0) + { + AddButton(x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 1, GumpButtonType.Reply, 0); + + if (PrevLabel) + AddLabel(x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous"); + } + + x += PrevWidth + OffsetSize; + + if (!OldStyle) + AddImageTiled(x, y, emptyWidth, EntryHeight, HeaderGumpID); + + if (TypeLabel && m_Type != null) + AddHtml(x, y, emptyWidth, EntryHeight, + $"
{m_Type.Name}
", false, false); + + x += emptyWidth + OffsetSize; + + if (!OldStyle) + AddImageTiled(x, y, NextWidth, EntryHeight, HeaderGumpID); + + if ((page + 1) * EntryCount < m_List.Count) + { + AddButton(x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 2, GumpButtonType.Reply, 1); + + if (NextLabel) + AddLabel(x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next"); + } + + for (int i = 0, index = page * EntryCount; i < count && index < m_List.Count; ++i, ++index) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; + + object o = m_List[index]; + + if (o == null) + { + AddImageTiled(x - OffsetSize, y, TotalWidth, EntryHeight, BackGumpID + 4); + } + else if (o is Type type) + { + AddImageTiled(x, y, TypeWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, TypeWidth - TextOffsetX, EntryHeight, TextHue, type.Name); + x += TypeWidth + OffsetSize; + + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + } + else if (o is PropertyInfo prop) + { + AddImageTiled(x, y, NameWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, NameWidth - TextOffsetX, EntryHeight, TextHue, prop.Name); + x += NameWidth + OffsetSize; + AddImageTiled(x, y, ValueWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, ValueWidth - TextOffsetX, EntryHeight, TextHue, ValueToString(prop)); + x += ValueWidth + OffsetSize; + + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + + CPA cpa = GetCPA(prop); + + if (prop.CanWrite && cpa != null && m_Mobile.AccessLevel >= cpa.WriteLevel && !cpa.ReadOnly) + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, i + 3, GumpButtonType.Reply, + 0); + } + } + } + + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; + + if (!BaseCommand.IsAccessible(from, m_Object)) + { + from.SendMessage("You may no longer access their properties."); + return; + } + + switch (info.ButtonID) + { + case 0: // Closed + { + if (m_Stack != null && m_Stack.Count > 0) + { + StackEntry entry = m_Stack.Pop(); + + from.SendGump(new PropertiesGump(from, entry.m_Object, m_Stack, null)); + } + + break; + } + case 1: // Previous + { + if (m_Page > 0) + from.SendGump(new PropertiesGump(from, m_Object, m_Stack, m_List, m_Page - 1)); + + break; + } + case 2: // Next + { + if ((m_Page + 1) * EntryCount < m_List.Count) + from.SendGump(new PropertiesGump(from, m_Object, m_Stack, m_List, m_Page + 1)); + + break; + } + default: + { + int index = m_Page * EntryCount + (info.ButtonID - 3); + + if (index >= 0 && index < m_List.Count) + { + PropertyInfo prop = m_List[index] as PropertyInfo; + + if (prop == null) + return; + + CPA attr = GetCPA(prop); + + if (!prop.CanWrite || attr == null || from.AccessLevel < attr.WriteLevel || attr.ReadOnly) + return; + + Type type = prop.PropertyType; + + if (IsType(type, typeofMobile) || IsType(type, typeofItem)) + { + from.SendGump(new SetObjectGump(prop, from, m_Object, m_Stack, type, m_Page, m_List)); + } + else if (IsType(type, typeofType)) + { + from.Target = new SetObjectTarget(prop, from, m_Object, m_Stack, type, m_Page, m_List); + } + else if (IsType(type, typeofPoint3D)) + { + from.SendGump(new SetPoint3DGump(prop, from, m_Object, m_Stack, m_Page, m_List)); + } + else if (IsType(type, typeofPoint2D)) + { + from.SendGump(new SetPoint2DGump(prop, from, m_Object, m_Stack, m_Page, m_List)); + } + else if (IsType(type, typeofTimeSpan)) + { + from.SendGump(new SetTimeSpanGump(prop, from, m_Object, m_Stack, m_Page, m_List)); + } + else if (IsCustomEnum(type)) + { + from.SendGump(new SetCustomEnumGump(prop, from, m_Object, m_Stack, m_Page, m_List, + GetCustomEnumNames(type))); + } + else if (IsType(type, typeofEnum)) + { + from.SendGump(new SetListOptionGump(prop, from, m_Object, m_Stack, m_Page, m_List, + Enum.GetNames(type), GetObjects(Enum.GetValues(type)))); + } + else if (IsType(type, typeofBool)) + { + from.SendGump(new SetListOptionGump(prop, from, m_Object, m_Stack, m_Page, m_List, m_BoolNames, + m_BoolValues)); + } + else if (IsType(type, typeofString) || IsType(type, typeofReal) || IsType(type, typeofNumeric) || + IsType(type, typeofText)) + { + from.SendGump(new SetGump(prop, from, m_Object, m_Stack, m_Page, m_List)); + } + else if (IsType(type, typeofPoison)) + { + from.SendGump(new SetListOptionGump(prop, from, m_Object, m_Stack, m_Page, m_List, m_PoisonNames, + m_PoisonValues)); + } + else if (IsType(type, typeofMap)) + { + from.SendGump(new SetListOptionGump(prop, from, m_Object, m_Stack, m_Page, m_List, + Map.GetMapNames(), Map.GetMapValues())); + } + else if (IsType(type, typeofSkills) && m_Object is Mobile mobile) + { + from.SendGump(new PropertiesGump(from, mobile, m_Stack, m_List, m_Page)); + from.SendGump(new SkillsGump(from, mobile)); + } + else if (HasAttribute(type, typeofPropertyObject, true)) + { + object obj = prop.GetValue(m_Object, null); + + if (obj != null) + from.SendGump(new PropertiesGump(from, obj, m_Stack, new StackEntry(m_Object, prop))); + else + from.SendGump(new PropertiesGump(from, m_Object, m_Stack, m_List, m_Page)); + } + } + + break; + } + } + } + + private static object[] GetObjects(Array a) + { + object[] list = new object[a.Length]; + + for (int i = 0; i < list.Length; ++i) + list[i] = a.GetValue(i); + + return list; + } + + private static bool IsCustomEnum(Type type) + { + return type.IsDefined(typeofCustomEnum, false); + } + + public static void OnValueChanged(object obj, PropertyInfo prop, Stack stack) + { + if (stack == null || stack.Count == 0) + return; + + if (!prop.PropertyType.IsValueType) + return; + + StackEntry peek = stack.Peek(); + + if (peek.m_Property.CanWrite) + peek.m_Property.SetValue(peek.m_Object, obj, null); + } + + private static string[] GetCustomEnumNames(Type type) + { + object[] attrs = type.GetCustomAttributes(typeofCustomEnum, false); + + if (attrs.Length == 0) + return new string[0]; + + if (!(attrs[0] is CustomEnumAttribute ce)) + return new string[0]; + + return ce.Names; + } + + private static bool HasAttribute(Type type, Type check, bool inherit) + { + object[] objs = type.GetCustomAttributes(check, inherit); + + return objs != null && objs.Length > 0; + } + + private static bool IsType(Type type, Type check) + { + return type == check || type.IsSubclassOf(check); + } + + private static bool IsType(Type type, Type[] check) + { + for (int i = 0; i < check.Length; ++i) + if (IsType(type, check[i])) + return true; + + return false; + } + + private string ValueToString(PropertyInfo prop) + { + return ValueToString(m_Object, prop); + } + + public static string ValueToString(object obj, PropertyInfo prop) + { + try + { + return ValueToString(prop.GetValue(obj, null)); + } + catch (Exception e) + { + return $"!{e.GetType()}!"; + } + } + + public static string ValueToString(object o) + { + if (o == null) return "-null-"; + if (o is string s) return $"\"{s}\""; + if (o is bool) return o.ToString(); + if (o is char c) return $"0x{(int)c:X} '{c}'"; + if (o is Serial serial) + { + if (serial.IsValid) + { + if (serial.IsItem) return $"(I) 0x{serial.Value:X}"; + if (serial.IsMobile) return $"(M) 0x{serial.Value:X}"; + } + + return $"(?) 0x{serial.Value:X}"; + } + + if (o is byte || o is sbyte || o is short || o is ushort || o is int || o is uint || o is long || o is ulong) + return string.Format("{0} (0x{0:X})", o); + if (o is Mobile mobile) return $"(M) 0x{mobile.Serial.Value:X} \"{mobile.Name}\""; + if (o is Item item) return $"(I) 0x{item.Serial.Value:X}"; + if (o is Type type) return type.Name; + if (o is TextDefinition definition) return definition.Format(true); + + return o.ToString(); + } + + private ArrayList BuildList() + { + ArrayList list = new ArrayList(); + + if (m_Type == null) + return list; + + PropertyInfo[] props = m_Type.GetProperties(BindingFlags.Static | BindingFlags.Instance | BindingFlags.Public); + + ArrayList groups = GetGroups(m_Type, props); + + for (int i = 0; i < groups.Count; ++i) + { + DictionaryEntry de = (DictionaryEntry)groups[i]; + ArrayList groupList = (ArrayList)de.Value; + + if (!HasAttribute((Type)de.Key, typeofNoSort, false)) + groupList.Sort(PropertySorter.Instance); + + if (i != 0) + list.Add(null); + + list.Add(de.Key); + list.AddRange(groupList); + } + + return list; + } + + private static CPA GetCPA(PropertyInfo prop) + { + object[] attrs = prop.GetCustomAttributes(typeofCPA, false); + + if (attrs.Length > 0) + return attrs[0] as CPA; + return null; + } + + private ArrayList GetGroups(Type objectType, PropertyInfo[] props) + { + Hashtable groups = new Hashtable(); + + for (int i = 0; i < props.Length; ++i) + { + PropertyInfo prop = props[i]; + + if (prop.CanRead) + { + CPA attr = GetCPA(prop); + + if (attr != null && m_Mobile.AccessLevel >= attr.ReadLevel) + { + Type type = prop.DeclaringType; + + while (true) + { + Type baseType = type.BaseType; + + if (baseType == null || baseType == typeofObject) + break; + + if (baseType.GetProperty(prop.Name, prop.PropertyType) != null) + type = baseType; + else + break; + } + + ArrayList list = (ArrayList)groups[type]; + + if (list == null) + groups[type] = list = new ArrayList(); + + list.Add(prop); + } + } + } + + ArrayList sorted = new ArrayList(groups); + + sorted.Sort(new GroupComparer(objectType)); + + return sorted; + } + + public static object GetObjectFromString(Type t, string s) + { + if (t == typeof(string)) return s; + + if (t == typeof(byte) || t == typeof(sbyte) || t == typeof(short) || t == typeof(ushort) || t == typeof(int) || + t == typeof(uint) || t == typeof(long) || t == typeof(ulong)) + { + if (s.StartsWith("0x")) + { + if (t == typeof(ulong) || t == typeof(uint) || t == typeof(ushort) || t == typeof(byte)) + return Convert.ChangeType(Convert.ToUInt64(s.Substring(2), 16), t); + + return Convert.ChangeType(Convert.ToInt64(s.Substring(2), 16), t); + } + + return Convert.ChangeType(s, t); + } + + if (t == typeof(double) || t == typeof(float)) return Convert.ChangeType(s, t); + if (t.IsDefined(typeof(ParsableAttribute), false)) + { + MethodInfo parseMethod = t.GetMethod("Parse", new[] { typeof(string) }); + + return parseMethod.Invoke(null, new object[] { s }); + } + + throw new Exception("bad"); + } + + private static string GetStringFromObject(object o) + { + if (o == null) return "-null-"; + if (o is string s) return $"\"{s}\""; + if (o is bool) return o.ToString(); + if (o is char c) return $"0x{(int)c:X} '{c}'"; + if (o is Serial serial) + { + if (serial.IsValid) + { + if (serial.IsItem) return $"(I) 0x{serial.Value:X}"; + if (serial.IsMobile) return $"(M) 0x{serial.Value:X}"; + } + + return $"(?) 0x{serial.Value:X}"; + } + + if (o is byte || o is sbyte || o is short || o is ushort || o is int || o is uint || o is long || o is ulong) + return string.Format("{0} (0x{0:X})", o); + if (o is Mobile mobile) return $"(M) 0x{mobile.Serial.Value:X} \"{mobile.Name}\""; + if (o is Item item) return $"(I) 0x{item.Serial.Value:X}"; + if (o is Type type) return type.Name; + + return o.ToString(); + } + + private class PropertySorter : IComparer + { + public static readonly PropertySorter Instance = new PropertySorter(); + + private PropertySorter() + { + } + + public int Compare(object x, object y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + PropertyInfo a = x as PropertyInfo; + PropertyInfo b = y as PropertyInfo; + + if (a == null || b == null) + throw new ArgumentException(); + + return a.Name.CompareTo(b.Name); + } + } + + private class GroupComparer : IComparer + { + private static Type typeofObject = typeof(object); + private Type m_Start; + + public GroupComparer(Type start) + { + m_Start = start; + } + + public int Compare(object x, object y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + if (!(x is DictionaryEntry) || !(y is DictionaryEntry)) + throw new ArgumentException(); + + DictionaryEntry de1 = (DictionaryEntry)x; + DictionaryEntry de2 = (DictionaryEntry)y; + + return GetDistance((Type)de1.Key).CompareTo(GetDistance((Type)de2.Key)); + } + + private int GetDistance(Type type) + { + Type current = m_Start; + + int dist; + + for (dist = 0; current != null && current != typeofObject && current != type; ++dist) + current = current.BaseType; + + return dist; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetBodyGump.cs b/Scripts/Gumps/Props/SetBodyGump.cs index 2cba657b0..75f0ade06 100644 --- a/Scripts/Gumps/Props/SetBodyGump.cs +++ b/Scripts/Gumps/Props/SetBodyGump.cs @@ -2,289 +2,311 @@ using System; using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Network; using Server.Commands; +using Server.Network; namespace Server.Gumps { - public class SetBodyGump : Gump - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; - private int m_OurPage; - private ArrayList m_OurList; - private ModelBodyType m_OurType; + public class SetBodyGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private const int SelectedColor32 = 0x8080FF; + private const int TextColor32 = 0xFFFFFF; - private const int LabelColor32 = 0xFFFFFF; - private const int SelectedColor32 = 0x8080FF; - private const int TextColor32 = 0xFFFFFF; + private static ArrayList m_Monster, m_Animal, m_Sea, m_Human; + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private ArrayList m_OurList; + private int m_OurPage; + private ModelBodyType m_OurType; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - public SetBodyGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) - : this( prop, mobile, o, stack, page, list, 0, null, ModelBodyType.Invalid ) - { - } + public SetBodyGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list) + : this(prop, mobile, o, stack, page, list, 0, null, ModelBodyType.Invalid) + { + } - public string Center( string text ) - { - return $"
{text}
"; - } + public SetBodyGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list, + int ourPage, ArrayList ourList, ModelBodyType ourType) + : base(20, 30) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; + m_OurPage = ourPage; + m_OurList = ourList; + m_OurType = ourType; - public string Color( string text, int color ) - { - return $"{text}"; - } + AddPage(0); - public void AddTypeButton( int x, int y, int buttonID, string text, ModelBodyType type ) - { - bool isSelection = (m_OurType == type); + AddBackground(0, 0, 525, 328, 5054); - AddButton( x, y - 1, isSelection ? 4006 : 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - AddHtml( x + 35, y, 200, 20, Color( text, isSelection ? SelectedColor32 : LabelColor32 ), false, false ); - } + AddImageTiled(10, 10, 505, 20, 0xA40); + AddAlphaRegion(10, 10, 505, 20); - public SetBodyGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list, int ourPage, ArrayList ourList, ModelBodyType ourType) - : base( 20, 30 ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; - m_OurPage = ourPage; - m_OurList = ourList; - m_OurType = ourType; + AddImageTiled(10, 35, 505, 283, 0xA40); + AddAlphaRegion(10, 35, 505, 283); - AddPage( 0 ); + AddTypeButton(10, 10, 1, "Monster", ModelBodyType.Monsters); + AddTypeButton(130, 10, 2, "Animal", ModelBodyType.Animals); + AddTypeButton(250, 10, 3, "Marine", ModelBodyType.Sea); + AddTypeButton(370, 10, 4, "Human", ModelBodyType.Human); - AddBackground( 0, 0, 525, 328, 5054 ); + AddImage(480, 12, 0x25EA); + AddImage(497, 12, 0x25E6); - AddImageTiled( 10, 10, 505, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 505, 20 ); + if (ourList == null) + { + AddLabel(15, 40, 0x480, "Choose a body type above."); + } + else if (ourList.Count == 0) + { + AddLabel(15, 40, 0x480, "The server must have UO:3D installed to use this feature."); + } + else + { + for (int i = 0, index = ourPage * 12; i < 12 && index >= 0 && index < ourList.Count; ++i, ++index) + { + InternalEntry entry = (InternalEntry)ourList[index]; + int itemID = entry.ItemID; - AddImageTiled( 10, 35, 505, 283, 0xA40 ); - AddAlphaRegion( 10, 35, 505, 283 ); + Rectangle2D bounds = ItemBounds.Table[itemID & 0x3FFF]; - AddTypeButton( 10, 10, 1, "Monster", ModelBodyType.Monsters ); - AddTypeButton( 130, 10, 2, "Animal", ModelBodyType.Animals ); - AddTypeButton( 250, 10, 3, "Marine", ModelBodyType.Sea ); - AddTypeButton( 370, 10, 4, "Human", ModelBodyType.Human ); + int x = 15 + i % 4 * 125; + int y = 40 + i / 4 * 93; - AddImage( 480, 12, 0x25EA ); - AddImage( 497, 12, 0x25E6 ); + AddItem(x + (120 - bounds.Width) / 2 - bounds.X, y + (69 - bounds.Height) / 2 - bounds.Y, itemID); + AddButton(x + 6, y + 66, 0x98D, 0x98D, 7 + index, GumpButtonType.Reply, 0); - if ( ourList == null ) - { - AddLabel( 15, 40, 0x480, "Choose a body type above." ); - } - else if ( ourList.Count == 0 ) - { - AddLabel( 15, 40, 0x480, "The server must have UO:3D installed to use this feature." ); - } - else - { - for( int i = 0, index = (ourPage * 12); i < 12 && index >= 0 && index < ourList.Count; ++i, ++index ) - { - InternalEntry entry = (InternalEntry)ourList[index]; - int itemID = entry.ItemID; + x += 6; + y += 67; - Rectangle2D bounds = ItemBounds.Table[itemID & 0x3FFF]; + AddHtml(x + 0, y - 1, 108, 21, Center(entry.DisplayName), false, false); + AddHtml(x + 0, y + 1, 108, 21, Center(entry.DisplayName), false, false); + AddHtml(x - 1, y + 0, 108, 21, Center(entry.DisplayName), false, false); + AddHtml(x + 1, y + 0, 108, 21, Center(entry.DisplayName), false, false); + AddHtml(x + 0, y + 0, 108, 21, Color(Center(entry.DisplayName), TextColor32), false, false); + } - int x = 15 + ((i % 4) * 125); - int y = 40 + ((i / 4) * 93); + if (ourPage > 0) + AddButton(480, 12, 0x15E3, 0x15E7, 5, GumpButtonType.Reply, 0); - AddItem( x + ((120 - bounds.Width) / 2) - bounds.X, y + ((69 - bounds.Height) / 2) - bounds.Y, itemID ); - AddButton( x + 6, y + 66, 0x98D, 0x98D, 7 + index, GumpButtonType.Reply, 0 ); + if ((ourPage + 1) * 12 < ourList.Count) + AddButton(497, 12, 0x15E1, 0x15E5, 6, GumpButtonType.Reply, 0); + } + } - x += 6; - y += 67; + public string Center(string text) + { + return $"
{text}
"; + } - AddHtml( x + 0, y - 1, 108, 21, Center( entry.DisplayName ), false, false ); - AddHtml( x + 0, y + 1, 108, 21, Center( entry.DisplayName ), false, false ); - AddHtml( x - 1, y + 0, 108, 21, Center( entry.DisplayName ), false, false ); - AddHtml( x + 1, y + 0, 108, 21, Center( entry.DisplayName ), false, false ); - AddHtml( x + 0, y + 0, 108, 21, Color( Center( entry.DisplayName ), TextColor32 ), false, false ); - } + public string Color(string text, int color) + { + return $"{text}"; + } - if ( ourPage > 0 ) - AddButton( 480, 12, 0x15E3, 0x15E7, 5, GumpButtonType.Reply, 0 ); + public void AddTypeButton(int x, int y, int buttonID, string text, ModelBodyType type) + { + bool isSelection = m_OurType == type; - if ( (ourPage + 1) * 12 < ourList.Count ) - AddButton( 497, 12, 0x15E1, 0x15E5, 6, GumpButtonType.Reply, 0 ); - } - } + AddButton(x, y - 1, isSelection ? 4006 : 4005, 4007, buttonID, GumpButtonType.Reply, 0); + AddHtml(x + 35, y, 200, 20, Color(text, isSelection ? SelectedColor32 : LabelColor32), false, false); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - int index = info.ButtonID - 1; + public override void OnResponse(NetState sender, RelayInfo info) + { + int index = info.ButtonID - 1; - if ( index == -1 ) - { - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - else if ( index >= 0 && index < 4 ) - { - if ( m_Monster == null ) - LoadLists(); + if (index == -1) + { + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + else if (index >= 0 && index < 4) + { + if (m_Monster == null) + LoadLists(); - ModelBodyType type; - ArrayList list; + ModelBodyType type; + ArrayList list; - switch( index ) - { - default: - case 0: type = ModelBodyType.Monsters; list = m_Monster; break; - case 1: type = ModelBodyType.Animals; list = m_Animal; break; - case 2: type = ModelBodyType.Sea; list = m_Sea; break; - case 3: type = ModelBodyType.Human; list = m_Human; break; - } + switch (index) + { + default: + case 0: + type = ModelBodyType.Monsters; + list = m_Monster; + break; + case 1: + type = ModelBodyType.Animals; + list = m_Animal; + break; + case 2: + type = ModelBodyType.Sea; + list = m_Sea; + break; + case 3: + type = ModelBodyType.Human; + list = m_Human; + break; + } - m_Mobile.SendGump( new SetBodyGump( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, 0, list, type ) ); - } - else if ( m_OurList != null ) - { - index -= 4; + m_Mobile.SendGump(new SetBodyGump(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, 0, list, type)); + } + else if (m_OurList != null) + { + index -= 4; - if ( index == 0 && m_OurPage > 0 ) - { - m_Mobile.SendGump( new SetBodyGump( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, m_OurPage - 1, m_OurList, m_OurType ) ); - } - else if ( index == 1 && ((m_OurPage + 1) * 12) < m_OurList.Count ) - { - m_Mobile.SendGump( new SetBodyGump( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, m_OurPage + 1, m_OurList, m_OurType ) ); - } - else - { - index -= 2; + if (index == 0 && m_OurPage > 0) + { + m_Mobile.SendGump(new SetBodyGump(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, m_OurPage - 1, + m_OurList, m_OurType)); + } + else if (index == 1 && (m_OurPage + 1) * 12 < m_OurList.Count) + { + m_Mobile.SendGump(new SetBodyGump(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, m_OurPage + 1, + m_OurList, m_OurType)); + } + else + { + index -= 2; - if ( index >= 0 && index < m_OurList.Count ) - { - try - { - InternalEntry entry = (InternalEntry)m_OurList[index]; + if (index >= 0 && index < m_OurList.Count) + { + try + { + InternalEntry entry = (InternalEntry)m_OurList[index]; - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, entry.Body.ToString() ); - m_Property.SetValue( m_Object, entry.Body, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, entry.Body.ToString()); + m_Property.SetValue(m_Object, entry.Body, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - m_Mobile.SendGump( new SetBodyGump( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, m_OurPage, m_OurList, m_OurType ) ); - } - } - } - } + m_Mobile.SendGump(new SetBodyGump(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List, m_OurPage, + m_OurList, m_OurType)); + } + } + } + } - private static ArrayList m_Monster, m_Animal, m_Sea, m_Human; + private static void LoadLists() + { + m_Monster = new ArrayList(); + m_Animal = new ArrayList(); + m_Sea = new ArrayList(); + m_Human = new ArrayList(); - private static void LoadLists() - { - m_Monster = new ArrayList(); - m_Animal = new ArrayList(); - m_Sea = new ArrayList(); - m_Human = new ArrayList(); + List entries = Docs.LoadBodies(); - List entries = Docs.LoadBodies(); + for (int i = 0; i < entries.Count; ++i) + { + BodyEntry oldEntry = entries[i]; + int bodyID = oldEntry.Body.BodyID; - for( int i = 0; i < entries.Count; ++i ) - { - BodyEntry oldEntry = (BodyEntry)entries[i]; - int bodyID = oldEntry.Body.BodyID; + if (((Body)bodyID).IsEmpty) + continue; - if ( ((Body)bodyID).IsEmpty ) - continue; + ArrayList list = null; - ArrayList list = null; + switch (oldEntry.BodyType) + { + case ModelBodyType.Monsters: + list = m_Monster; + break; + case ModelBodyType.Animals: + list = m_Animal; + break; + case ModelBodyType.Sea: + list = m_Sea; + break; + case ModelBodyType.Human: + list = m_Human; + break; + } - switch( oldEntry.BodyType ) - { - case ModelBodyType.Monsters: list = m_Monster; break; - case ModelBodyType.Animals: list = m_Animal; break; - case ModelBodyType.Sea: list = m_Sea; break; - case ModelBodyType.Human: list = m_Human; break; - } + if (list == null) + continue; - if ( list == null ) - continue; + int itemID = ShrinkTable.Lookup(bodyID, -1); - int itemID = ShrinkTable.Lookup( bodyID, -1 ); + if (itemID != -1) + list.Add(new InternalEntry(bodyID, itemID, oldEntry.Name)); + } - if ( itemID != -1 ) - list.Add( new InternalEntry( bodyID, itemID, oldEntry.Name ) ); - } + m_Monster.Sort(); + m_Animal.Sort(); + m_Sea.Sort(); + m_Human.Sort(); + } - m_Monster.Sort(); - m_Animal.Sort(); - m_Sea.Sort(); - m_Human.Sort(); - } + private class InternalEntry : IComparable + { + private static string[] m_GroupNames = + { + "ogres_", "ettins_", "walking_dead_", "gargoyles_", + "orcs_", "flails_", "daemons_", "arachnids_", + "dragons_", "elementals_", "serpents_", "gazers_", + "liche_", "spirits_", "harpies_", "headless_", + "lizard_race_", "mongbat_", "rat_race_", "scorpions_", + "trolls_", "slimes_", "skeletons_", "ethereals_", + "terathan_", "imps_", "cyclops_", "krakens_", + "frogs_", "ophidians_", "centaurs_", "mages_", + "fey_race_", "genies_", "paladins_", "shadowlords_", + "succubi_", "lizards_", "rodents_", "birds_", + "bovines_", "bruins_", "canines_", "deer_", + "equines_", "felines_", "fowl_", "gorillas_", + "kirin_", "llamas_", "ostards_", "porcines_", + "ruminants_", "walrus_", "dolphins_", "sea_horse_", + "sea_serpents_", "character_", "h_", "titans_" + }; - private class InternalEntry : IComparable - { - public int Body { get; } + public InternalEntry(int body, int itemID, string name) + { + Body = body; + ItemID = itemID; + Name = name; - public int ItemID { get; } + DisplayName = name.ToLower(); - public string Name { get; } + for (int i = 0; i < m_GroupNames.Length; ++i) + if (DisplayName.StartsWith(m_GroupNames[i])) + { + DisplayName = DisplayName.Substring(m_GroupNames[i].Length); + break; + } - public string DisplayName { get; } + DisplayName = DisplayName.Replace('_', ' '); + } - private static string[] m_GroupNames = { - "ogres_", "ettins_", "walking_dead_", "gargoyles_", - "orcs_", "flails_", "daemons_", "arachnids_", - "dragons_", "elementals_", "serpents_", "gazers_", - "liche_", "spirits_", "harpies_", "headless_", - "lizard_race_", "mongbat_", "rat_race_", "scorpions_", - "trolls_", "slimes_", "skeletons_", "ethereals_", - "terathan_", "imps_", "cyclops_", "krakens_", - "frogs_", "ophidians_", "centaurs_", "mages_", - "fey_race_", "genies_", "paladins_", "shadowlords_", - "succubi_", "lizards_", "rodents_", "birds_", - "bovines_", "bruins_", "canines_", "deer_", - "equines_", "felines_", "fowl_", "gorillas_", - "kirin_", "llamas_", "ostards_", "porcines_", - "ruminants_", "walrus_", "dolphins_", "sea_horse_", - "sea_serpents_", "character_", "h_", "titans_" - }; + public int Body{ get; } - public InternalEntry( int body, int itemID, string name ) - { - Body = body; - ItemID = itemID; - Name = name; + public int ItemID{ get; } - DisplayName = name.ToLower(); + public string Name{ get; } - for( int i = 0; i < m_GroupNames.Length; ++i ) - { - if ( DisplayName.StartsWith( m_GroupNames[i] ) ) - { - DisplayName = DisplayName.Substring( m_GroupNames[i].Length ); - break; - } - } + public string DisplayName{ get; } - DisplayName = DisplayName.Replace( '_', ' ' ); - } + public int CompareTo(object obj) + { + InternalEntry comp = (InternalEntry)obj; - public int CompareTo( object obj ) - { - InternalEntry comp = (InternalEntry)obj; + int v = Name.CompareTo(comp.Name); - int v = Name.CompareTo( comp.Name ); + if (v == 0) + Body.CompareTo(comp.Body); - if ( v == 0 ) - Body.CompareTo( comp.Body ); - - return v; - } - } - } -} + return v; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetCustomEnumGump.cs b/Scripts/Gumps/Props/SetCustomEnumGump.cs index 7b1ef928d..3813c33aa 100644 --- a/Scripts/Gumps/Props/SetCustomEnumGump.cs +++ b/Scripts/Gumps/Props/SetCustomEnumGump.cs @@ -2,49 +2,50 @@ using System; using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Network; using Server.Commands; +using Server.Network; namespace Server.Gumps { - public class SetCustomEnumGump : SetListOptionGump - { - private string[] m_Names; + public class SetCustomEnumGump : SetListOptionGump + { + private string[] m_Names; - public SetCustomEnumGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int propspage, ArrayList list, string[] names ) : base( prop, mobile, o, stack, propspage, list, names, null ) - { - m_Names = names; - } + public SetCustomEnumGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int propspage, + ArrayList list, string[] names) : base(prop, mobile, o, stack, propspage, list, names, null) + { + m_Names = names; + } - public override void OnResponse( NetState sender, RelayInfo relayInfo ) - { - int index = relayInfo.ButtonID - 1; + public override void OnResponse(NetState sender, RelayInfo relayInfo) + { + int index = relayInfo.ButtonID - 1; - if ( index >= 0 && index < m_Names.Length ) - { - try - { - MethodInfo info = m_Property.PropertyType.GetMethod( "Parse", new[]{ typeof( string ) } ); + if (index >= 0 && index < m_Names.Length) + try + { + MethodInfo info = m_Property.PropertyType.GetMethod("Parse", new[] { typeof(string) }); - string result = ""; + string result = ""; - if ( info != null ) - result = Properties.SetDirect( m_Mobile, m_Object, m_Object, m_Property, m_Property.Name, info.Invoke( null, new object[] { m_Names[index] } ), true ); - else if ( m_Property.PropertyType == typeof( Enum ) || m_Property.PropertyType.IsSubclassOf( typeof( Enum ) ) ) - result = Properties.SetDirect( m_Mobile, m_Object, m_Object, m_Property, m_Property.Name, Enum.Parse( m_Property.PropertyType, m_Names[index], false ), true ); + if (info != null) + result = Properties.SetDirect(m_Mobile, m_Object, m_Object, m_Property, m_Property.Name, + info.Invoke(null, new object[] { m_Names[index] }), true); + else if (m_Property.PropertyType == typeof(Enum) || m_Property.PropertyType.IsSubclassOf(typeof(Enum))) + result = Properties.SetDirect(m_Mobile, m_Object, m_Object, m_Property, m_Property.Name, + Enum.Parse(m_Property.PropertyType, m_Names[index], false), true); - m_Mobile.SendMessage( result ); + m_Mobile.SendMessage(result); - if ( result == "Property has been set." ) - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } + if (result == "Property has been set.") + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetGump.cs b/Scripts/Gumps/Props/SetGump.cs index dd32580b4..7019b2ab3 100644 --- a/Scripts/Gumps/Props/SetGump.cs +++ b/Scripts/Gumps/Props/SetGump.cs @@ -1,280 +1,284 @@ using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Network; -using Server.HuePickers; using Server.Commands; +using Server.HuePickers; +using Server.Network; namespace Server.Gumps { - public class SetGump : Gump - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + public class SetGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public static readonly bool OldStyle = PropsConfig.OldStyle; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + private static readonly int EntryWidth = 212; - private static readonly int EntryWidth = 212; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + 2 * (EntryHeight + OffsetSize); - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + (2 * (EntryHeight + OffsetSize)); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + public SetGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list) : base( + GumpOffsetX, GumpOffsetY) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; - public SetGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; + bool canNull = !prop.PropertyType.IsValueType; + bool canDye = prop.IsDefined(typeof(HueAttribute), false); + bool isBody = prop.IsDefined(typeof(BodyAttribute), false); - bool canNull = !prop.PropertyType.IsValueType; - bool canDye = prop.IsDefined( typeof( HueAttribute ), false ); - bool isBody = prop.IsDefined( typeof( BodyAttribute ), false ); + object val = prop.GetValue(m_Object, null); + string initialText; - object val = prop.GetValue( m_Object, null ); - string initialText; + if (val == null) + initialText = ""; + else if (val is TextDefinition definition) + initialText = definition.GetValue(); + else + initialText = val.ToString(); - if ( val == null ) - initialText = ""; - else if ( val is TextDefinition definition ) - initialText = definition.GetValue(); - else - initialText = val.ToString(); + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, BackWidth, + BackHeight + (canNull ? EntryHeight + OffsetSize : 0) + (canDye ? EntryHeight + OffsetSize : 0) + + (isBody ? EntryHeight + OffsetSize : 0), BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), + TotalHeight + (canNull ? EntryHeight + OffsetSize : 0) + (canDye ? EntryHeight + OffsetSize : 0) + + (isBody ? EntryHeight + OffsetSize : 0), OffsetGumpID); - AddBackground( 0, 0, BackWidth, BackHeight + (canNull ? (EntryHeight + OffsetSize) : 0) + (canDye ? (EntryHeight + OffsetSize) : 0) + (isBody ? (EntryHeight + OffsetSize) : 0), BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight + (canNull ? (EntryHeight + OffsetSize) : 0) + (canDye ? (EntryHeight + OffsetSize) : 0) + (isBody ? (EntryHeight + OffsetSize) : 0), OffsetGumpID ); + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddTextEntry(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, 0, initialText); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddTextEntry( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, 0, initialText ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0 ); + if (canNull) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - if ( canNull ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Null"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Null" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0); + } - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0 ); - } + if (canDye) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - if ( canDye ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Hue Picker"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Hue Picker" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0); + } - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0 ); - } + if (isBody) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - if ( isBody ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Body Picker"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Body Picker" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 4, GumpButtonType.Reply, 0); + } + } - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 4, GumpButtonType.Reply, 0 ); - } - } + public override void OnResponse(NetState sender, RelayInfo info) + { + object toSet; + bool shouldSet, shouldSend = true; - private class InternalPicker : HuePicker - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + switch (info.ButtonID) + { + case 1: + { + TextRelay text = info.GetTextEntry(0); - public InternalPicker( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( ((IHued)o).HuedItemID ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; - } + if (text != null) + { + try + { + toSet = PropertiesGump.GetObjectFromString(m_Property.PropertyType, text.Text); + shouldSet = true; + } + catch + { + toSet = null; + shouldSet = false; + m_Mobile.SendMessage("Bad format"); + } + } + else + { + toSet = null; + shouldSet = false; + } - public override void OnResponse( int hue ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, hue.ToString() ); - m_Property.SetValue( m_Object, hue, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } + break; + } + case 2: // Null + { + toSet = null; + shouldSet = true; - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } + break; + } + case 3: // Hue Picker + { + toSet = null; + shouldSet = false; + shouldSend = false; - public override void OnResponse( NetState sender, RelayInfo info ) - { - object toSet; - bool shouldSet, shouldSend = true; + m_Mobile.SendHuePicker(new InternalPicker(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List)); - switch ( info.ButtonID ) - { - case 1: - { - TextRelay text = info.GetTextEntry( 0 ); + break; + } + case 4: // Body Picker + { + toSet = null; + shouldSet = false; + shouldSend = false; - if ( text != null ) - { - try - { - toSet = PropertiesGump.GetObjectFromString( m_Property.PropertyType, text.Text ); - shouldSet = true; - } - catch - { - toSet = null; - shouldSet = false; - m_Mobile.SendMessage( "Bad format" ); - } - } - else - { - toSet = null; - shouldSet = false; - } + m_Mobile.SendGump(new SetBodyGump(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List)); - break; - } - case 2: // Null - { - toSet = null; - shouldSet = true; + break; + } + default: + { + toSet = null; + shouldSet = false; - break; - } - case 3: // Hue Picker - { - toSet = null; - shouldSet = false; - shouldSend = false; + break; + } + } - m_Mobile.SendHuePicker( new InternalPicker( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List ) ); + if (shouldSet) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, + toSet == null ? "(null)" : toSet.ToString()); + m_Property.SetValue(m_Object, toSet, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - break; - } - case 4: // Body Picker - { - toSet = null; - shouldSet = false; - shouldSend = false; + if (shouldSend) + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } - m_Mobile.SendGump( new SetBodyGump( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List ) ); + private class InternalPicker : HuePicker + { + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - break; - } - default: - { - toSet = null; - shouldSet = false; + public InternalPicker(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, + ArrayList list) : base(((IHued)o).HuedItemID) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; + } - break; - } - } + public override void OnResponse(int hue) + { + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, hue.ToString()); + m_Property.SetValue(m_Object, hue, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - if ( shouldSet ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, toSet==null?"(null)":toSet.ToString() ); - m_Property.SetValue( m_Object, toSet, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - - if ( shouldSend ) - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } -} + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetListOptionGump.cs b/Scripts/Gumps/Props/SetListOptionGump.cs index cd67d26c8..a541cbaf1 100644 --- a/Scripts/Gumps/Props/SetListOptionGump.cs +++ b/Scripts/Gumps/Props/SetListOptionGump.cs @@ -1,186 +1,188 @@ using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Network; using Server.Commands; +using Server.Network; namespace Server.Gumps { - public class SetListOptionGump : Gump - { - protected PropertyInfo m_Property; - protected Mobile m_Mobile; - protected object m_Object; - protected Stack m_Stack; - protected int m_Page; - protected ArrayList m_List; + public class SetListOptionGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public static readonly bool OldStyle = PropsConfig.OldStyle; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + private static readonly int EntryWidth = 212; + private static readonly int EntryCount = 13; - private static readonly int EntryWidth = 212; - private static readonly int EntryCount = 13; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static bool PrevLabel = OldStyle, NextLabel = OldStyle; - private static bool PrevLabel = OldStyle, NextLabel = OldStyle; + private static readonly int PrevLabelOffsetX = PrevWidth + 1; + private static readonly int PrevLabelOffsetY = 0; - private static readonly int PrevLabelOffsetX = PrevWidth + 1; - private static readonly int PrevLabelOffsetY = 0; + private static readonly int NextLabelOffsetX = -29; + private static readonly int NextLabelOffsetY = 0; + protected ArrayList m_List; + protected Mobile m_Mobile; + protected object m_Object; + protected int m_Page; + protected PropertyInfo m_Property; + protected Stack m_Stack; - private static readonly int NextLabelOffsetX = -29; - private static readonly int NextLabelOffsetY = 0; + protected object[] m_Values; - protected object[] m_Values; + public SetListOptionGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int propspage, + ArrayList list, string[] names, object[] values) : base(GumpOffsetX, GumpOffsetY) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = propspage; + m_List = list; - public SetListOptionGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int propspage, ArrayList list, string[] names, object[] values ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = propspage; - m_List = list; + m_Values = values; - m_Values = values; + int pages = (names.Length + EntryCount - 1) / EntryCount; + int index = 0; - int pages = (names.Length + EntryCount - 1) / EntryCount; - int index = 0; + for (int page = 1; page <= pages; ++page) + { + AddPage(page); - for ( int page = 1; page <= pages; ++page ) - { - AddPage( page ); + int start = (page - 1) * EntryCount; + int count = names.Length - start; - int start = (page - 1) * EntryCount; - int count = names.Length - start; + if (count > EntryCount) + count = EntryCount; - if ( count > EntryCount ) - count = EntryCount; + int totalHeight = OffsetSize + (count + 2) * (EntryHeight + OffsetSize); + int backHeight = BorderSize + totalHeight + BorderSize; - int totalHeight = OffsetSize + ((count + 2) * (EntryHeight + OffsetSize)); - int backHeight = BorderSize + totalHeight + BorderSize; - - AddBackground( 0, 0, BackWidth, backHeight, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, OffsetGumpID ); + AddBackground(0, 0, BackWidth, backHeight, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, + OffsetGumpID); + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + int emptyWidth = TotalWidth - PrevWidth - NextWidth - OffsetSize * 4 - + (OldStyle ? SetWidth + OffsetSize : 0); - int emptyWidth = TotalWidth - PrevWidth - NextWidth - (OffsetSize * 4) - (OldStyle ? SetWidth + OffsetSize : 0); + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + if (page > 1) + { + AddButton(x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 0, GumpButtonType.Page, + page - 1); - if ( page > 1 ) - { - AddButton( x + PrevOffsetX, y + PrevOffsetY, PrevButtonID1, PrevButtonID2, 0, GumpButtonType.Page, page - 1 ); + if (PrevLabel) + AddLabel(x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous"); + } - if ( PrevLabel ) - AddLabel( x + PrevLabelOffsetX, y + PrevLabelOffsetY, TextHue, "Previous" ); - } + x += PrevWidth + OffsetSize; - x += PrevWidth + OffsetSize; + if (!OldStyle) + AddImageTiled(x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), + EntryHeight, HeaderGumpID); - if ( !OldStyle ) - AddImageTiled( x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, HeaderGumpID ); + x += emptyWidth + OffsetSize; - x += emptyWidth + OffsetSize; + if (!OldStyle) + AddImageTiled(x, y, NextWidth, EntryHeight, HeaderGumpID); - if ( !OldStyle ) - AddImageTiled( x, y, NextWidth, EntryHeight, HeaderGumpID ); + if (page < pages) + { + AddButton(x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 0, GumpButtonType.Page, + page + 1); - if ( page < pages ) - { - AddButton( x + NextOffsetX, y + NextOffsetY, NextButtonID1, NextButtonID2, 0, GumpButtonType.Page, page + 1 ); - - if ( NextLabel ) - AddLabel( x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next" ); - } + if (NextLabel) + AddLabel(x + NextLabelOffsetX, y + NextLabelOffsetY, TextHue, "Next"); + } + AddRect(0, prop.Name, 0); - AddRect( 0, prop.Name, 0 ); + for (int i = 0; i < count; ++i) + AddRect(i + 1, names[index], ++index); + } + } - for ( int i = 0; i < count; ++i ) - AddRect( i + 1, names[index], ++index ); - } - } + private void AddRect(int index, string str, int button) + { + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize + (index + 1) * (EntryHeight + OffsetSize); - private void AddRect( int index, string str, int button ) - { - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize + ((index + 1) * (EntryHeight + OffsetSize)); + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, str); - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, str ); + x += EntryWidth + OffsetSize; - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + if (button != 0) + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, button, GumpButtonType.Reply, 0); + } - if ( button != 0 ) - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, button, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + int index = info.ButtonID - 1; - public override void OnResponse( NetState sender, RelayInfo info ) - { - int index = info.ButtonID - 1; + if (index >= 0 && index < m_Values.Length) + try + { + object toSet = m_Values[index]; - if ( index >= 0 && index < m_Values.Length ) - { - try - { - object toSet = m_Values[index]; + string result = Properties.SetDirect(m_Mobile, m_Object, m_Object, m_Property, m_Property.Name, toSet, + true); - string result = Properties.SetDirect( m_Mobile, m_Object, m_Object, m_Property, m_Property.Name, toSet, true ); + m_Mobile.SendMessage(result); - m_Mobile.SendMessage( result ); + if (result == "Property has been set.") + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - if ( result == "Property has been set." ) - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetObjectGump.cs b/Scripts/Gumps/Props/SetObjectGump.cs index f3d671b43..67c75c9f2 100644 --- a/Scripts/Gumps/Props/SetObjectGump.cs +++ b/Scripts/Gumps/Props/SetObjectGump.cs @@ -2,307 +2,308 @@ using System; using System.Collections; using System.Collections.Generic; using System.Reflection; +using Server.Commands; using Server.Commands.Generic; using Server.Network; using Server.Prompts; -using Server.Commands; namespace Server.Gumps { - public class SetObjectGump : Gump - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private Type m_Type; - private int m_Page; - private ArrayList m_List; + public class SetObjectGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public static readonly bool OldStyle = PropsConfig.OldStyle; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + private static readonly int EntryWidth = 212; - private static readonly int EntryWidth = 212; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + 5 * (EntryHeight + OffsetSize); - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + (5 * (EntryHeight + OffsetSize)); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; + private Type m_Type; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + public SetObjectGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, Type type, int page, + ArrayList list) : base(GumpOffsetX, GumpOffsetY) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Type = type; + m_Page = page; + m_List = list; - public SetObjectGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, Type type, int page, ArrayList list ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Type = type; - m_Page = page; - m_List = list; + string initialText = PropertiesGump.ValueToString(o, prop); - string initialText = PropertiesGump.ValueToString( o, prop ); + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, BackWidth, BackHeight, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, + OffsetGumpID); - AddBackground( 0, 0, BackWidth, BackHeight, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, OffsetGumpID ); + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, initialText); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, initialText ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Change by Serial"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Change by Serial" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Nullify"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Nullify" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "View Properties"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "View Properties" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 4, GumpButtonType.Reply, 0); + } - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 4, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + object toSet; + bool shouldSet, shouldSend = true; + object viewProps = null; - private class InternalPrompt : Prompt - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private Type m_Type; - private int m_Page; - private ArrayList m_List; + switch (info.ButtonID) + { + case 0: // closed + { + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); - public InternalPrompt( PropertyInfo prop, Mobile mobile, object o, Stack stack, Type type, int page, ArrayList list ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Type = type; - m_Page = page; - m_List = list; - } + toSet = null; + shouldSet = false; + shouldSend = false; - public override void OnCancel( Mobile from ) - { - m_Mobile.SendGump( new SetObjectGump( m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List ) ); - } + break; + } + case 1: // Change by Target + { + m_Mobile.Target = new SetObjectTarget(m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List); + toSet = null; + shouldSet = false; + shouldSend = false; + break; + } + case 2: // Change by Serial + { + toSet = null; + shouldSet = false; + shouldSend = false; - public override void OnResponse( Mobile from, string text ) - { - object toSet; - bool shouldSet; + m_Mobile.SendMessage("Enter the serial you wish to find:"); + m_Mobile.Prompt = new InternalPrompt(m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List); - try - { - int serial = Utility.ToInt32( text ); + break; + } + case 3: // Nullify + { + toSet = null; + shouldSet = true; - toSet = World.FindEntity( serial ); + break; + } + case 4: // View Properties + { + toSet = null; + shouldSet = false; - if ( toSet == null ) - { - shouldSet = false; - m_Mobile.SendMessage( "No object with that serial was found." ); - } - else if ( !m_Type.IsAssignableFrom( toSet.GetType() ) ) - { - toSet = null; - shouldSet = false; - m_Mobile.SendMessage( "The object with that serial could not be assigned to a property of type : {0}", m_Type.Name ); - } - else - { - shouldSet = true; - } - } - catch - { - toSet = null; - shouldSet = false; - m_Mobile.SendMessage( "Bad format" ); - } + object obj = m_Property.GetValue(m_Object, null); - if ( shouldSet ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, toSet==null?"(null)":toSet.ToString() ); - m_Property.SetValue( m_Object, toSet, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } + if (obj == null) + m_Mobile.SendMessage("The property is null and so you cannot view its properties."); + else if (!BaseCommand.IsAccessible(m_Mobile, obj)) + m_Mobile.SendMessage("You may not view their properties."); + else + viewProps = obj; - m_Mobile.SendGump( new SetObjectGump( m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List ) ); - } - } + break; + } + default: + { + toSet = null; + shouldSet = false; - public override void OnResponse( NetState sender, RelayInfo info ) - { - object toSet; - bool shouldSet, shouldSend = true; - object viewProps = null; + break; + } + } - switch ( info.ButtonID ) - { - case 0: // closed - { - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); + if (shouldSet) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, + toSet == null ? "(null)" : toSet.ToString()); + m_Property.SetValue(m_Object, toSet, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - toSet = null; - shouldSet = false; - shouldSend = false; + if (shouldSend) + m_Mobile.SendGump(new SetObjectGump(m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List)); - break; - } - case 1: // Change by Target - { - m_Mobile.Target = new SetObjectTarget( m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List ); - toSet = null; - shouldSet = false; - shouldSend = false; - break; - } - case 2: // Change by Serial - { - toSet = null; - shouldSet = false; - shouldSend = false; + if (viewProps != null) + m_Mobile.SendGump(new PropertiesGump(m_Mobile, viewProps)); + } - m_Mobile.SendMessage( "Enter the serial you wish to find:" ); - m_Mobile.Prompt = new InternalPrompt( m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List ); + private class InternalPrompt : Prompt + { + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; + private Type m_Type; - break; - } - case 3: // Nullify - { - toSet = null; - shouldSet = true; + public InternalPrompt(PropertyInfo prop, Mobile mobile, object o, Stack stack, Type type, int page, + ArrayList list) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Type = type; + m_Page = page; + m_List = list; + } - break; - } - case 4: // View Properties - { - toSet = null; - shouldSet = false; + public override void OnCancel(Mobile from) + { + m_Mobile.SendGump(new SetObjectGump(m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List)); + } - object obj = m_Property.GetValue( m_Object, null ); + public override void OnResponse(Mobile from, string text) + { + object toSet; + bool shouldSet; - if ( obj == null ) - m_Mobile.SendMessage( "The property is null and so you cannot view its properties." ); - else if ( !BaseCommand.IsAccessible( m_Mobile, obj ) ) - m_Mobile.SendMessage( "You may not view their properties." ); - else - viewProps = obj; + try + { + int serial = Utility.ToInt32(text); - break; - } - default: - { - toSet = null; - shouldSet = false; + toSet = World.FindEntity(serial); - break; - } - } + if (toSet == null) + { + shouldSet = false; + m_Mobile.SendMessage("No object with that serial was found."); + } + else if (!m_Type.IsAssignableFrom(toSet.GetType())) + { + toSet = null; + shouldSet = false; + m_Mobile.SendMessage("The object with that serial could not be assigned to a property of type : {0}", + m_Type.Name); + } + else + { + shouldSet = true; + } + } + catch + { + toSet = null; + shouldSet = false; + m_Mobile.SendMessage("Bad format"); + } - if ( shouldSet ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, toSet==null?"(null)":toSet.ToString() ); - m_Property.SetValue( m_Object, toSet, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } + if (shouldSet) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, + toSet == null ? "(null)" : toSet.ToString()); + m_Property.SetValue(m_Object, toSet, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - if ( shouldSend ) - m_Mobile.SendGump( new SetObjectGump( m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List ) ); - - if ( viewProps != null ) - m_Mobile.SendGump( new PropertiesGump( m_Mobile, viewProps ) ); - } - } + m_Mobile.SendGump(new SetObjectGump(m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetObjectTarget.cs b/Scripts/Gumps/Props/SetObjectTarget.cs index 8637dc2c7..2ec03c1f8 100644 --- a/Scripts/Gumps/Props/SetObjectTarget.cs +++ b/Scripts/Gumps/Props/SetObjectTarget.cs @@ -2,65 +2,67 @@ using System; using System.Collections; using System.Collections.Generic; using System.Reflection; +using Server.Commands; using Server.Items; using Server.Targeting; -using Server.Commands; namespace Server.Gumps { - public class SetObjectTarget : Target - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private Type m_Type; - private int m_Page; - private ArrayList m_List; + public class SetObjectTarget : Target + { + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; + private Type m_Type; - public SetObjectTarget( PropertyInfo prop, Mobile mobile, object o, Stack stack, Type type, int page, ArrayList list ) : base( -1, false, TargetFlags.None ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Type = type; - m_Page = page; - m_List = list; - } + public SetObjectTarget(PropertyInfo prop, Mobile mobile, object o, Stack stack, Type type, int page, + ArrayList list) : base(-1, false, TargetFlags.None) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Type = type; + m_Page = page; + m_List = list; + } - protected override void OnTarget( Mobile from, object targeted ) - { - try - { - if ( m_Type == typeof( Type ) ) - targeted = targeted.GetType(); - else if ( (m_Type == typeof( BaseAddon ) || m_Type.IsAssignableFrom( typeof( BaseAddon ) )) && targeted is AddonComponent ) - targeted = ((AddonComponent)targeted).Addon; + protected override void OnTarget(Mobile from, object targeted) + { + try + { + if (m_Type == typeof(Type)) + targeted = targeted.GetType(); + else if ((m_Type == typeof(BaseAddon) || m_Type.IsAssignableFrom(typeof(BaseAddon))) && + targeted is AddonComponent) + targeted = ((AddonComponent)targeted).Addon; - if ( m_Type.IsAssignableFrom( targeted.GetType() ) ) - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, targeted.ToString() ); - m_Property.SetValue( m_Object, targeted, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - else - { - m_Mobile.SendMessage( "That cannot be assigned to a property of type : {0}", m_Type.Name ); - } - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } + if (m_Type.IsAssignableFrom(targeted.GetType())) + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, targeted.ToString()); + m_Property.SetValue(m_Object, targeted, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + else + { + m_Mobile.SendMessage("That cannot be assigned to a property of type : {0}", m_Type.Name); + } + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } + } - protected override void OnTargetFinish( Mobile from ) - { - if ( m_Type == typeof( Type ) ) - from.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - else - from.SendGump( new SetObjectGump( m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List ) ); - } - } + protected override void OnTargetFinish(Mobile from) + { + if (m_Type == typeof(Type)) + from.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + else + from.SendGump(new SetObjectGump(m_Property, m_Mobile, m_Object, m_Stack, m_Type, m_Page, m_List)); + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetPoint2DGump.cs b/Scripts/Gumps/Props/SetPoint2DGump.cs index 1e0bd7bc5..94b860e36 100644 --- a/Scripts/Gumps/Props/SetPoint2DGump.cs +++ b/Scripts/Gumps/Props/SetPoint2DGump.cs @@ -1,234 +1,232 @@ using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Targeting; -using Server.Network; using Server.Commands; +using Server.Network; +using Server.Targeting; namespace Server.Gumps { - public class SetPoint2DGump : Gump - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + public class SetPoint2DGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public static readonly bool OldStyle = PropsConfig.OldStyle; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + private static readonly int CoordWidth = 105; + private static readonly int EntryWidth = CoordWidth + OffsetSize + CoordWidth; - private static readonly int CoordWidth = 105; - private static readonly int EntryWidth = CoordWidth + OffsetSize + CoordWidth; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + 4 * (EntryHeight + OffsetSize); - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + (4 * (EntryHeight + OffsetSize)); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + public SetPoint2DGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list) + : base(GumpOffsetX, GumpOffsetY) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; - public SetPoint2DGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; + Point2D p = (Point2D)prop.GetValue(o, null); - Point2D p = (Point2D)prop.GetValue( o, null ); + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, BackWidth, BackHeight, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, + OffsetGumpID); - AddBackground( 0, 0, BackWidth, BackHeight, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, OffsetGumpID ); + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Use your location"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Use your location" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Target a location"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Target a location" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, CoordWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "X:"); + AddTextEntry(x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 0, p.X.ToString()); + x += CoordWidth + OffsetSize; - AddImageTiled( x, y, CoordWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "X:" ); - AddTextEntry( x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 0, p.X.ToString() ); - x += CoordWidth + OffsetSize; + AddImageTiled(x, y, CoordWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "Y:"); + AddTextEntry(x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 1, p.Y.ToString()); + x += CoordWidth + OffsetSize; - AddImageTiled( x, y, CoordWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "Y:" ); - AddTextEntry( x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 1, p.Y.ToString() ); - x += CoordWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0); + } - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + Point2D toSet; + bool shouldSet, shouldSend; - private class InternalTarget : Target - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + switch (info.ButtonID) + { + case 1: // Current location + { + toSet = new Point2D(m_Mobile.Location); + shouldSet = true; + shouldSend = true; - public InternalTarget( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( -1, true, TargetFlags.None ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; - } + break; + } + case 2: // Pick location + { + m_Mobile.Target = new InternalTarget(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is IPoint3D p ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, new Point2D( p ).ToString() ); - m_Property.SetValue( m_Object, new Point2D( p ), null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - } + toSet = Point2D.Zero; + shouldSet = false; + shouldSend = false; - protected override void OnTargetFinish( Mobile from ) - { - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } + break; + } + case 3: // Use values + { + TextRelay x = info.GetTextEntry(0); + TextRelay y = info.GetTextEntry(1); - public override void OnResponse( NetState sender, RelayInfo info ) - { - Point2D toSet; - bool shouldSet, shouldSend; + toSet = new Point2D(x == null ? 0 : Utility.ToInt32(x.Text), y == null ? 0 : Utility.ToInt32(y.Text)); + shouldSet = true; + shouldSend = true; - switch ( info.ButtonID ) - { - case 1: // Current location - { - toSet = new Point2D( m_Mobile.Location ); - shouldSet = true; - shouldSend = true; + break; + } + default: + { + toSet = Point2D.Zero; + shouldSet = false; + shouldSend = true; - break; - } - case 2: // Pick location - { - m_Mobile.Target = new InternalTarget( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List ); + break; + } + } - toSet = Point2D.Zero; - shouldSet = false; - shouldSend = false; + if (shouldSet) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, toSet.ToString()); + m_Property.SetValue(m_Object, toSet, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - break; - } - case 3: // Use values - { - TextRelay x = info.GetTextEntry( 0 ); - TextRelay y = info.GetTextEntry( 1 ); + if (shouldSend) + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } - toSet = new Point2D( x == null ? 0 : Utility.ToInt32( x.Text ), y == null ? 0 : Utility.ToInt32( y.Text ) ); - shouldSet = true; - shouldSend = true; + private class InternalTarget : Target + { + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - break; - } - default: - { - toSet = Point2D.Zero; - shouldSet = false; - shouldSend = true; + public InternalTarget(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, + ArrayList list) : base(-1, true, TargetFlags.None) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; + } - break; - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is IPoint3D p) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, new Point2D(p).ToString()); + m_Property.SetValue(m_Object, new Point2D(p), null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } + } - if ( shouldSet ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, toSet.ToString() ); - m_Property.SetValue( m_Object, toSet, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - - if ( shouldSend ) - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetPoint3DGump.cs b/Scripts/Gumps/Props/SetPoint3DGump.cs index 3fa7f07b9..ec8e07e7e 100644 --- a/Scripts/Gumps/Props/SetPoint3DGump.cs +++ b/Scripts/Gumps/Props/SetPoint3DGump.cs @@ -1,240 +1,239 @@ using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Targeting; -using Server.Network; using Server.Commands; +using Server.Network; +using Server.Targeting; namespace Server.Gumps { - public class SetPoint3DGump : Gump - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + public class SetPoint3DGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public static readonly bool OldStyle = PropsConfig.OldStyle; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + private static readonly int CoordWidth = 70; + private static readonly int EntryWidth = CoordWidth + OffsetSize + CoordWidth + OffsetSize + CoordWidth; - private static readonly int CoordWidth = 70; - private static readonly int EntryWidth = CoordWidth + OffsetSize + CoordWidth + OffsetSize + CoordWidth; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + 4 * (EntryHeight + OffsetSize); - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + (4 * (EntryHeight + OffsetSize)); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + public SetPoint3DGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list) + : base(GumpOffsetX, GumpOffsetY) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; - public SetPoint3DGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; + Point3D p = (Point3D)prop.GetValue(o, null); - Point3D p = (Point3D)prop.GetValue( o, null ); + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, BackWidth, BackHeight, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, + OffsetGumpID); - AddBackground( 0, 0, BackWidth, BackHeight, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, OffsetGumpID ); + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, prop.Name ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Use your location"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Use your location" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Target a location"); + x += EntryWidth + OffsetSize; - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, "Target a location" ); - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 2, GumpButtonType.Reply, 0 ); + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + AddImageTiled(x, y, CoordWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "X:"); + AddTextEntry(x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 0, p.X.ToString()); + x += CoordWidth + OffsetSize; - AddImageTiled( x, y, CoordWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "X:" ); - AddTextEntry( x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 0, p.X.ToString() ); - x += CoordWidth + OffsetSize; + AddImageTiled(x, y, CoordWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "Y:"); + AddTextEntry(x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 1, p.Y.ToString()); + x += CoordWidth + OffsetSize; - AddImageTiled( x, y, CoordWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "Y:" ); - AddTextEntry( x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 1, p.Y.ToString() ); - x += CoordWidth + OffsetSize; + AddImageTiled(x, y, CoordWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "Z:"); + AddTextEntry(x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 2, p.Z.ToString()); + x += CoordWidth + OffsetSize; - AddImageTiled( x, y, CoordWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, CoordWidth - TextOffsetX, EntryHeight, TextHue, "Z:" ); - AddTextEntry( x + 16, y, CoordWidth - 16, EntryHeight, TextHue, 2, p.Z.ToString() ); - x += CoordWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0); + } - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 3, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + Point3D toSet; + bool shouldSet, shouldSend; - private class InternalTarget : Target - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + switch (info.ButtonID) + { + case 1: // Current location + { + toSet = m_Mobile.Location; + shouldSet = true; + shouldSend = true; - public InternalTarget( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( -1, true, TargetFlags.None ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; - } + break; + } + case 2: // Pick location + { + m_Mobile.Target = new InternalTarget(m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is IPoint3D p ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, new Point3D( p ).ToString() ); - m_Property.SetValue( m_Object, new Point3D( p ), null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - } + toSet = Point3D.Zero; + shouldSet = false; + shouldSend = false; - protected override void OnTargetFinish( Mobile from ) - { - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } + break; + } + case 3: // Use values + { + TextRelay x = info.GetTextEntry(0); + TextRelay y = info.GetTextEntry(1); + TextRelay z = info.GetTextEntry(2); - public override void OnResponse( NetState sender, RelayInfo info ) - { - Point3D toSet; - bool shouldSet, shouldSend; + toSet = new Point3D(x == null ? 0 : Utility.ToInt32(x.Text), y == null ? 0 : Utility.ToInt32(y.Text), + z == null ? 0 : Utility.ToInt32(z.Text)); + shouldSet = true; + shouldSend = true; - switch ( info.ButtonID ) - { - case 1: // Current location - { - toSet = m_Mobile.Location; - shouldSet = true; - shouldSend = true; + break; + } + default: + { + toSet = Point3D.Zero; + shouldSet = false; + shouldSend = true; - break; - } - case 2: // Pick location - { - m_Mobile.Target = new InternalTarget( m_Property, m_Mobile, m_Object, m_Stack, m_Page, m_List ); + break; + } + } - toSet = Point3D.Zero; - shouldSet = false; - shouldSend = false; + if (shouldSet) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, toSet.ToString()); + m_Property.SetValue(m_Object, toSet, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - break; - } - case 3: // Use values - { - TextRelay x = info.GetTextEntry( 0 ); - TextRelay y = info.GetTextEntry( 1 ); - TextRelay z = info.GetTextEntry( 2 ); + if (shouldSend) + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } - toSet = new Point3D( x == null ? 0 : Utility.ToInt32( x.Text ), y == null ? 0 : Utility.ToInt32( y.Text ), z == null ? 0 : Utility.ToInt32( z.Text ) ); - shouldSet = true; - shouldSend = true; + private class InternalTarget : Target + { + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - break; - } - default: - { - toSet = Point3D.Zero; - shouldSet = false; - shouldSend = true; + public InternalTarget(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, + ArrayList list) : base(-1, true, TargetFlags.None) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; + } - break; - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is IPoint3D p) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, new Point3D(p).ToString()); + m_Property.SetValue(m_Object, new Point3D(p), null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } + } - if ( shouldSet ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, toSet.ToString() ); - m_Property.SetValue( m_Object, toSet, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - - if ( shouldSend ) - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/Props/SetTimeSpanGump.cs b/Scripts/Gumps/Props/SetTimeSpanGump.cs index 764025d15..5abf216cb 100644 --- a/Scripts/Gumps/Props/SetTimeSpanGump.cs +++ b/Scripts/Gumps/Props/SetTimeSpanGump.cs @@ -2,237 +2,226 @@ using System; using System.Collections; using System.Collections.Generic; using System.Reflection; -using Server.Network; using Server.Commands; +using Server.Network; namespace Server.Gumps { - public class SetTimeSpanGump : Gump - { - private PropertyInfo m_Property; - private Mobile m_Mobile; - private object m_Object; - private Stack m_Stack; - private int m_Page; - private ArrayList m_List; + public class SetTimeSpanGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public static readonly bool OldStyle = PropsConfig.OldStyle; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - public static readonly int OffsetSize = PropsConfig.OffsetSize; + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; + private static readonly int EntryWidth = 212; - private static readonly int EntryWidth = 212; + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + 7 * (EntryHeight + OffsetSize); - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + (7 * (EntryHeight + OffsetSize)); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + private ArrayList m_List; + private Mobile m_Mobile; + private object m_Object; + private int m_Page; + private PropertyInfo m_Property; + private Stack m_Stack; - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + public SetTimeSpanGump(PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list) + : base(GumpOffsetX, GumpOffsetY) + { + m_Property = prop; + m_Mobile = mobile; + m_Object = o; + m_Stack = stack; + m_Page = page; + m_List = list; - public SetTimeSpanGump( PropertyInfo prop, Mobile mobile, object o, Stack stack, int page, ArrayList list ) : base( GumpOffsetX, GumpOffsetY ) - { - m_Property = prop; - m_Mobile = mobile; - m_Object = o; - m_Stack = stack; - m_Page = page; - m_List = list; + TimeSpan ts = (TimeSpan)prop.GetValue(o, null); - TimeSpan ts = (TimeSpan)prop.GetValue( o, null ); + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, BackWidth, BackHeight, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, + OffsetGumpID); - AddBackground( 0, 0, BackWidth, BackHeight, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, OffsetGumpID ); + AddRect(0, prop.Name, 0, -1); + AddRect(1, ts.ToString(), 0, -1); + AddRect(2, "Zero", 1, -1); + AddRect(3, "From H:M:S", 2, -1); + AddRect(4, "H:", 3, 0); + AddRect(5, "M:", 4, 1); + AddRect(6, "S:", 5, 2); + } - AddRect( 0, prop.Name, 0, -1 ); - AddRect( 1, ts.ToString(), 0, -1 ); - AddRect( 2, "Zero", 1, -1 ); - AddRect( 3, "From H:M:S", 2, -1 ); - AddRect( 4, "H:", 3, 0 ); - AddRect( 5, "M:", 4, 1 ); - AddRect( 6, "S:", 5, 2 ); - } + private void AddRect(int index, string str, int button, int text) + { + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize + index * (EntryHeight + OffsetSize); - private void AddRect( int index, string str, int button, int text ) - { - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize + (index * (EntryHeight + OffsetSize)); + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, str); - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, str ); + if (text != -1) + AddTextEntry(x + 16 + TextOffsetX, y, EntryWidth - TextOffsetX - 16, EntryHeight, TextHue, text, ""); - if ( text != -1 ) - AddTextEntry( x + 16 + TextOffsetX, y, EntryWidth - TextOffsetX - 16, EntryHeight, TextHue, text, "" ); + x += EntryWidth + OffsetSize; - x += EntryWidth + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + if (button != 0) + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, button, GumpButtonType.Reply, 0); + } - if ( button != 0 ) - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, button, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + TimeSpan toSet; + bool shouldSet, shouldSend; - public override void OnResponse( NetState sender, RelayInfo info ) - { - TimeSpan toSet; - bool shouldSet, shouldSend; + TextRelay h = info.GetTextEntry(0); + TextRelay m = info.GetTextEntry(1); + TextRelay s = info.GetTextEntry(2); - TextRelay h = info.GetTextEntry( 0 ); - TextRelay m = info.GetTextEntry( 1 ); - TextRelay s = info.GetTextEntry( 2 ); + switch (info.ButtonID) + { + case 1: // Zero + { + toSet = TimeSpan.Zero; + shouldSet = true; + shouldSend = true; - switch ( info.ButtonID ) - { - case 1: // Zero - { - toSet = TimeSpan.Zero; - shouldSet = true; - shouldSend = true; + break; + } + case 2: // From H:M:S + { + bool successfulParse = false; + if (h != null && m != null && s != null) + successfulParse = TimeSpan.TryParse(h.Text + ":" + m.Text + ":" + s.Text, out toSet); + else + toSet = TimeSpan.Zero; - break; - } - case 2: // From H:M:S - { - bool successfulParse = false; - if ( h != null && m != null && s != null ) - { - successfulParse = TimeSpan.TryParse( h.Text + ":" + m.Text + ":" + s.Text, out toSet ); - } - else - { - toSet = TimeSpan.Zero; - } + shouldSet = shouldSend = successfulParse; - shouldSet = shouldSend = successfulParse; + break; + } + case 3: // From H + { + if (h != null) + try + { + toSet = TimeSpan.FromHours(Utility.ToDouble(h.Text)); + shouldSet = true; + shouldSend = true; - break; - } - case 3: // From H - { - if ( h != null ) - { - try - { - toSet = TimeSpan.FromHours( Utility.ToDouble( h.Text ) ); - shouldSet = true; - shouldSend = true; + break; + } + catch + { + } - break; - } - catch - { - } - } + toSet = TimeSpan.Zero; + shouldSet = false; + shouldSend = false; - toSet = TimeSpan.Zero; - shouldSet = false; - shouldSend = false; + break; + } + case 4: // From M + { + if (m != null) + try + { + toSet = TimeSpan.FromMinutes(Utility.ToDouble(m.Text)); + shouldSet = true; + shouldSend = true; - break; - } - case 4: // From M - { - if ( m != null ) - { - try - { - toSet = TimeSpan.FromMinutes( Utility.ToDouble( m.Text ) ); - shouldSet = true; - shouldSend = true; + break; + } + catch + { + } - break; - } - catch - { - } - } + toSet = TimeSpan.Zero; + shouldSet = false; + shouldSend = false; - toSet = TimeSpan.Zero; - shouldSet = false; - shouldSend = false; + break; + } + case 5: // From S + { + if (s != null) + try + { + toSet = TimeSpan.FromSeconds(Utility.ToDouble(s.Text)); + shouldSet = true; + shouldSend = true; - break; - } - case 5: // From S - { - if ( s != null ) - { - try - { - toSet = TimeSpan.FromSeconds( Utility.ToDouble( s.Text ) ); - shouldSet = true; - shouldSend = true; + break; + } + catch + { + } - break; - } - catch - { - } - } + toSet = TimeSpan.Zero; + shouldSet = false; + shouldSend = false; - toSet = TimeSpan.Zero; - shouldSet = false; - shouldSend = false; + break; + } + default: + { + toSet = TimeSpan.Zero; + shouldSet = false; + shouldSend = true; - break; - } - default: - { - toSet = TimeSpan.Zero; - shouldSet = false; - shouldSend = true; + break; + } + } - break; - } - } + if (shouldSet) + try + { + CommandLogging.LogChangeProperty(m_Mobile, m_Object, m_Property.Name, toSet.ToString()); + m_Property.SetValue(m_Object, toSet, null); + PropertiesGump.OnValueChanged(m_Object, m_Property, m_Stack); + } + catch + { + m_Mobile.SendMessage("An exception was caught. The property may not have changed."); + } - if ( shouldSet ) - { - try - { - CommandLogging.LogChangeProperty( m_Mobile, m_Object, m_Property.Name, toSet.ToString() ); - m_Property.SetValue( m_Object, toSet, null ); - PropertiesGump.OnValueChanged( m_Object, m_Property, m_Stack ); - } - catch - { - m_Mobile.SendMessage( "An exception was caught. The property may not have changed." ); - } - } - - if ( shouldSend ) - m_Mobile.SendGump( new PropertiesGump( m_Mobile, m_Object, m_Stack, m_List, m_Page ) ); - } - } -} + if (shouldSend) + m_Mobile.SendGump(new PropertiesGump(m_Mobile, m_Object, m_Stack, m_List, m_Page)); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/ReclaimVendorGump.cs b/Scripts/Gumps/ReclaimVendorGump.cs index ecab35248..acbd837e3 100644 --- a/Scripts/Gumps/ReclaimVendorGump.cs +++ b/Scripts/Gumps/ReclaimVendorGump.cs @@ -1,77 +1,78 @@ using System.Collections; -using Server.Network; using Server.Multis; +using Server.Network; namespace Server.Gumps { - public class ReclaimVendorGump : Gump - { - private BaseHouse m_House; - private ArrayList m_Vendors; + public class ReclaimVendorGump : Gump + { + private BaseHouse m_House; + private ArrayList m_Vendors; - public ReclaimVendorGump( BaseHouse house ) : base( 50, 50 ) - { - m_House = house; - m_Vendors = new ArrayList( house.InternalizedVendors ); + public ReclaimVendorGump(BaseHouse house) : base(50, 50) + { + m_House = house; + m_Vendors = new ArrayList(house.InternalizedVendors); - AddBackground( 0, 0, 170, 50 + m_Vendors.Count * 20, 0x13BE ); + AddBackground(0, 0, 170, 50 + m_Vendors.Count * 20, 0x13BE); - AddImageTiled( 10, 10, 150, 20, 0xA40 ); - AddHtmlLocalized( 10, 10, 150, 20, 1061827, 0x7FFF, false, false ); //
Reclaim Vendor
+ AddImageTiled(10, 10, 150, 20, 0xA40); + AddHtmlLocalized(10, 10, 150, 20, 1061827, 0x7FFF, false, false); //
Reclaim Vendor
- AddImageTiled( 10, 40, 150, m_Vendors.Count * 20, 0xA40 ); + AddImageTiled(10, 40, 150, m_Vendors.Count * 20, 0xA40); - for ( int i = 0; i < m_Vendors.Count; i++ ) - { - Mobile m = (Mobile) m_Vendors[i]; + for (int i = 0; i < m_Vendors.Count; i++) + { + Mobile m = (Mobile)m_Vendors[i]; - int y = 40 + i * 20; + int y = 40 + i * 20; - AddButton( 10, y, 0xFA5, 0xFA7, i + 1, GumpButtonType.Reply, 0 ); - AddLabel( 45, y, 0x481, m.Name ); - } - } + AddButton(10, y, 0xFA5, 0xFA7, i + 1, GumpButtonType.Reply, 0); + AddLabel(45, y, 0x481, m.Name); + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - if ( info.ButtonID == 0 || !m_House.IsActive || !m_House.IsInside( from ) || !m_House.IsOwner( from ) || !from.CheckAlive() ) - return; + if (info.ButtonID == 0 || !m_House.IsActive || !m_House.IsInside(from) || !m_House.IsOwner(from) || + !from.CheckAlive()) + return; - int index = info.ButtonID - 1; + int index = info.ButtonID - 1; - if ( index < 0 || index >= m_Vendors.Count ) - return; + if (index < 0 || index >= m_Vendors.Count) + return; - Mobile mob = (Mobile) m_Vendors[index]; + Mobile mob = (Mobile)m_Vendors[index]; - if ( !m_House.InternalizedVendors.Contains( mob ) ) - return; + if (!m_House.InternalizedVendors.Contains(mob)) + return; - if ( mob.Deleted ) - { - m_House.InternalizedVendors.Remove( mob ); - } - else - { - bool vendor, contract; - BaseHouse.IsThereVendor( from.Location, from.Map, out vendor, out contract ); + if (mob.Deleted) + { + m_House.InternalizedVendors.Remove(mob); + } + else + { + bool vendor, contract; + BaseHouse.IsThereVendor(from.Location, from.Map, out vendor, out contract); - if ( vendor ) - { - from.SendLocalizedMessage( 1062677 ); // You cannot place a vendor or barkeep at this location. - } - else if ( contract ) - { - from.SendLocalizedMessage( 1062678 ); // You cannot place a vendor or barkeep on top of a rental contract! - } - else - { - m_House.InternalizedVendors.Remove( mob ); - mob.MoveToWorld( from.Location, from.Map ); - } - } - } - } + if (vendor) + { + from.SendLocalizedMessage(1062677); // You cannot place a vendor or barkeep at this location. + } + else if (contract) + { + from.SendLocalizedMessage(1062678); // You cannot place a vendor or barkeep on top of a rental contract! + } + else + { + m_House.InternalizedVendors.Remove(mob); + mob.MoveToWorld(from.Location, from.Map); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/RewardGump.cs b/Scripts/Gumps/RewardGump.cs index ca3e56647..438eae254 100644 --- a/Scripts/Gumps/RewardGump.cs +++ b/Scripts/Gumps/RewardGump.cs @@ -3,184 +3,185 @@ using Server.Network; namespace Server.Gumps { - /* - * A generic version of the EA Clean Up Britannia reward gump. - */ + /* + * A generic version of the EA Clean Up Britannia reward gump. + */ - public interface IRewardEntry - { - int Price { get; } - int ItemID { get; } - int Hue { get; } - int Tooltip { get; } - TextDefinition Description { get; } - } + public interface IRewardEntry + { + int Price{ get; } + int ItemID{ get; } + int Hue{ get; } + int Tooltip{ get; } + TextDefinition Description{ get; } + } - public delegate void RewardPickedHandler( Mobile from, int index ); + public delegate void RewardPickedHandler(Mobile from, int index); - public class RewardGump : Gump - { - public TextDefinition Title { get; } + public class RewardGump : Gump + { + public RewardGump(TextDefinition title, IRewardEntry[] rewards, int points, RewardPickedHandler onPicked) + : base(250, 50) + { + Title = title; + Rewards = rewards; + Points = points; + OnPicked = onPicked; - public IRewardEntry[] Rewards { get; } + AddPage(0); - public int Points { get; } + AddImage(0, 0, 0x1F40); + AddImageTiled(20, 37, 300, 308, 0x1F42); + AddImage(20, 325, 0x1F43); + AddImage(35, 8, 0x39); + AddImageTiled(65, 8, 257, 10, 0x3A); + AddImage(290, 8, 0x3B); + AddImage(32, 33, 0x2635); + AddImageTiled(70, 55, 230, 2, 0x23C5); - public RewardPickedHandler OnPicked { get; } + if (Title.String != null) + AddHtml(70, 35, 270, 20, Title.String, false, false); + else if (Title.Number != 0) + AddHtmlLocalized(70, 35, 270, 20, Title.Number, 1, false, false); - public RewardGump( TextDefinition title, IRewardEntry[] rewards, int points, RewardPickedHandler onPicked ) - : base( 250, 50 ) - { - Title = title; - Rewards = rewards; - Points = points; - OnPicked = onPicked; + AddHtmlLocalized(50, 65, 150, 20, 1072843, 1, false, false); // Your Reward Points: + AddLabel(230, 65, 0x64, Points.ToString()); + AddImageTiled(35, 85, 270, 2, 0x23C5); + AddHtmlLocalized(35, 90, 270, 20, 1072844, 1, false, false); // Please Choose a Reward: - AddPage( 0 ); + AddPage(1); - AddImage( 0, 0, 0x1F40 ); - AddImageTiled( 20, 37, 300, 308, 0x1F42 ); - AddImage( 20, 325, 0x1F43 ); - AddImage( 35, 8, 0x39 ); - AddImageTiled( 65, 8, 257, 10, 0x3A ); - AddImage( 290, 8, 0x3B ); - AddImage( 32, 33, 0x2635 ); - AddImageTiled( 70, 55, 230, 2, 0x23C5 ); + int offset = 110; + int page = 1; - if ( Title.String != null ) - AddHtml( 70, 35, 270, 20, Title.String, false, false ); - else if ( Title.Number != 0 ) - AddHtmlLocalized( 70, 35, 270, 20, Title.Number, 1, false, false ); + for (int i = 0; i < Rewards.Length; ++i) + { + IRewardEntry entry = Rewards[i]; - AddHtmlLocalized( 50, 65, 150, 20, 1072843, 1, false, false ); // Your Reward Points: - AddLabel( 230, 65, 0x64, Points.ToString() ); - AddImageTiled( 35, 85, 270, 2, 0x23C5 ); - AddHtmlLocalized( 35, 90, 270, 20, 1072844, 1, false, false ); // Please Choose a Reward: + Rectangle2D bounds = ItemBounds.Table[entry.ItemID]; + int height = Math.Max(36, bounds.Height); - AddPage( 1 ); + if (offset + height > 320) + { + AddHtmlLocalized(240, 335, 60, 20, 1072854, 1, false, false); //
Next
+ AddButton(300, 335, 0x15E1, 0x15E5, 51, GumpButtonType.Page, page + 1); - int offset = 110; - int page = 1; + AddPage(++page); - for ( int i = 0; i < Rewards.Length; ++i ) - { - IRewardEntry entry = Rewards[i]; + AddButton(150, 335, 0x15E3, 0x15E7, 52, GumpButtonType.Page, page - 1); + AddHtmlLocalized(170, 335, 60, 20, 1074880, 1, false, false); // Previous - Rectangle2D bounds = ItemBounds.Table[entry.ItemID]; - int height = Math.Max( 36, bounds.Height ); + offset = 110; + } - if ( offset + height > 320 ) - { - AddHtmlLocalized( 240, 335, 60, 20, 1072854, 1, false, false ); //
Next
- AddButton( 300, 335, 0x15E1, 0x15E5, 51, GumpButtonType.Page, page + 1 ); + bool available = entry.Price <= Points; + int half = offset + height / 2; - AddPage( ++page ); + if (available) + AddButton(35, half - 6, 0x837, 0x838, 100 + i, GumpButtonType.Reply, 0); - AddButton( 150, 335, 0x15E3, 0x15E7, 52, GumpButtonType.Page, page - 1 ); - AddHtmlLocalized( 170, 335, 60, 20, 1074880, 1, false, false ); // Previous + AddItem(83 - bounds.Width / 2 - bounds.X, half - bounds.Height / 2 - bounds.Y, entry.ItemID, + available ? entry.Hue : 995); - offset = 110; - } + if (entry.Tooltip != 0) + AddTooltip(entry.Tooltip); - bool available = ( entry.Price <= Points ); - int half = offset + ( height / 2 ); + AddLabel(133, half - 10, available ? 0x64 : 0x21, entry.Price.ToString()); - if ( available ) - AddButton( 35, half - 6, 0x837, 0x838, 100 + i, GumpButtonType.Reply, 0 ); + if (entry.Description != null) + { + if (entry.Description.String != null) + AddHtml(190, offset, 114, height, entry.Description.String, false, false); + else if (entry.Description.Number != 0) + AddHtmlLocalized(190, offset, 114, height, entry.Description.Number, 1, false, false); + } - AddItem( 83 - ( bounds.Width / 2 ) - bounds.X, half - ( bounds.Height / 2 ) - bounds.Y, entry.ItemID, available ? entry.Hue : 995 ); + offset += height + 10; + } + } - if ( entry.Tooltip != 0 ) - AddTooltip( entry.Tooltip ); + public TextDefinition Title{ get; } - AddLabel( 133, half - 10, available ? 0x64 : 0x21, entry.Price.ToString() ); + public IRewardEntry[] Rewards{ get; } - if ( entry.Description != null ) - { - if ( entry.Description.String != null ) - AddHtml( 190, offset, 114, height, entry.Description.String, false, false ); - else if ( entry.Description.Number != 0 ) - AddHtmlLocalized( 190, offset, 114, height, entry.Description.Number, 1, false, false ); - } + public int Points{ get; } - offset += height + 10; - } - } + public RewardPickedHandler OnPicked{ get; } - public override void OnResponse( NetState sender, RelayInfo info ) - { - int choice = info.ButtonID; + public override void OnResponse(NetState sender, RelayInfo info) + { + int choice = info.ButtonID; - if ( choice == 0 ) - return; // Close + if (choice == 0) + return; // Close - choice -= 100; + choice -= 100; - if ( choice >= 0 && choice < Rewards.Length ) - { - IRewardEntry entry = Rewards[choice]; + if (choice >= 0 && choice < Rewards.Length) + { + IRewardEntry entry = Rewards[choice]; - if ( entry.Price <= Points ) - sender.Mobile.SendGump( new RewardConfirmGump( this, choice, entry ) ); - } - } - } + if (entry.Price <= Points) + sender.Mobile.SendGump(new RewardConfirmGump(this, choice, entry)); + } + } + } - public class RewardConfirmGump : Gump - { - private RewardGump m_Parent; - private int m_Index; + public class RewardConfirmGump : Gump + { + private int m_Index; + private RewardGump m_Parent; - public RewardConfirmGump( RewardGump parent, int index, IRewardEntry entry ) - : base( 120, 50 ) - { - m_Parent = parent; - m_Index = index; + public RewardConfirmGump(RewardGump parent, int index, IRewardEntry entry) + : base(120, 50) + { + m_Parent = parent; + m_Index = index; - Closable = false; + Closable = false; - AddPage( 0 ); + AddPage(0); - AddImageTiled( 0, 0, 348, 262, 0xA8E ); - AddAlphaRegion( 0, 0, 348, 262 ); - AddImage( 0, 15, 0x27A8 ); - AddImageTiled( 0, 30, 17, 200, 0x27A7 ); - AddImage( 0, 230, 0x27AA ); - AddImage( 15, 0, 0x280C ); - AddImageTiled( 30, 0, 300, 17, 0x280A ); - AddImage( 315, 0, 0x280E ); - AddImage( 15, 244, 0x280C ); - AddImageTiled( 30, 244, 300, 17, 0x280A ); - AddImage( 315, 244, 0x280E ); - AddImage( 330, 15, 0x27A8 ); - AddImageTiled( 330, 30, 17, 200, 0x27A7 ); - AddImage( 330, 230, 0x27AA ); - AddImage( 333, 2, 0x2716 ); - AddImage( 333, 248, 0x2716 ); - AddImage( 2, 248, 0x2716 ); - AddImage( 2, 2, 0x2716 ); + AddImageTiled(0, 0, 348, 262, 0xA8E); + AddAlphaRegion(0, 0, 348, 262); + AddImage(0, 15, 0x27A8); + AddImageTiled(0, 30, 17, 200, 0x27A7); + AddImage(0, 230, 0x27AA); + AddImage(15, 0, 0x280C); + AddImageTiled(30, 0, 300, 17, 0x280A); + AddImage(315, 0, 0x280E); + AddImage(15, 244, 0x280C); + AddImageTiled(30, 244, 300, 17, 0x280A); + AddImage(315, 244, 0x280E); + AddImage(330, 15, 0x27A8); + AddImageTiled(330, 30, 17, 200, 0x27A7); + AddImage(330, 230, 0x27AA); + AddImage(333, 2, 0x2716); + AddImage(333, 248, 0x2716); + AddImage(2, 248, 0x2716); + AddImage(2, 2, 0x2716); - AddItem( 140, 120, entry.ItemID, entry.Hue ); + AddItem(140, 120, entry.ItemID, entry.Hue); - if ( entry.Tooltip != 0 ) - AddTooltip( entry.Tooltip ); + if (entry.Tooltip != 0) + AddTooltip(entry.Tooltip); - AddHtmlLocalized( 25, 22, 200, 20, 1074974, 0x7D00, false, false ); // Confirm Selection - AddImage( 25, 40, 0xBBF ); - AddHtmlLocalized( 25, 55, 300, 120, 1074975, 0xFFFFFF, false, false ); // Are you sure you wish to select this? - AddRadio( 25, 175, 0x25F8, 0x25FB, true, 1 ); - AddRadio( 25, 210, 0x25F8, 0x25FB, false, 0 ); - AddHtmlLocalized( 60, 180, 280, 20, 1074976, 0xFFFFFF, false, false ); // Yes - AddHtmlLocalized( 60, 215, 280, 20, 1074977, 0xFFFFFF, false, false ); // No - AddButton( 265, 220, 0xF7, 0xF8, 7, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(25, 22, 200, 20, 1074974, 0x7D00, false, false); // Confirm Selection + AddImage(25, 40, 0xBBF); + AddHtmlLocalized(25, 55, 300, 120, 1074975, 0xFFFFFF, false, false); // Are you sure you wish to select this? + AddRadio(25, 175, 0x25F8, 0x25FB, true, 1); + AddRadio(25, 210, 0x25F8, 0x25FB, false, 0); + AddHtmlLocalized(60, 180, 280, 20, 1074976, 0xFFFFFF, false, false); // Yes + AddHtmlLocalized(60, 215, 280, 20, 1074977, 0xFFFFFF, false, false); // No + AddButton(265, 220, 0xF7, 0xF8, 7, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 7 && info.IsSwitched( 1 ) ) - m_Parent.OnPicked( sender.Mobile, m_Index ); - else - sender.Mobile.SendGump( new RewardGump( m_Parent.Title, m_Parent.Rewards, m_Parent.Points, m_Parent.OnPicked ) ); - } - } -} + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 7 && info.IsSwitched(1)) + m_Parent.OnPicked(sender.Mobile, m_Index); + else + sender.Mobile.SendGump(new RewardGump(m_Parent.Title, m_Parent.Rewards, m_Parent.Points, m_Parent.OnPicked)); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/RunebookGump.cs b/Scripts/Gumps/RunebookGump.cs index e5485ea90..54df01b19 100644 --- a/Scripts/Gumps/RunebookGump.cs +++ b/Scripts/Gumps/RunebookGump.cs @@ -1,447 +1,454 @@ -using System; using System.Collections.Generic; using Server.Items; +using Server.Multis; using Server.Network; +using Server.Prompts; +using Server.Spells.Chivalry; using Server.Spells.Fourth; using Server.Spells.Seventh; -using Server.Spells.Chivalry; -using Server.Prompts; namespace Server.Gumps { - public class RunebookGump : Gump - { - public Runebook Book { get; } - - public int GetMapHue( Map map ) - { - if ( map == Map.Trammel ) - return 10; - if ( map == Map.Felucca ) - return 81; - if ( map == Map.Ilshenar ) - return 1102; - if ( map == Map.Malas ) - return 1102; - if ( map == Map.Tokuno ) - return 1154; - - return 0; - } - - public string GetName( string name ) - { - if ( name == null || (name = name.Trim()).Length <= 0 ) - return "(indescript)"; - - return name; - } - - private void AddBackground() - { - AddPage( 0 ); - - // Background image - AddImage( 100, 10, 2200 ); - - // Two separators - for ( int i = 0; i < 2; ++i ) - { - int xOffset = 125 + (i * 165); - - AddImage( xOffset, 50, 57 ); - xOffset += 20; - - for ( int j = 0; j < 6; ++j, xOffset += 15 ) - AddImage( xOffset, 50, 58 ); - - AddImage( xOffset - 5, 50, 59 ); - } - - // First four page buttons - for ( int i = 0, xOffset = 130, gumpID = 2225; i < 4; ++i, xOffset += 35, ++gumpID ) - AddButton( xOffset, 187, gumpID, gumpID, 0, GumpButtonType.Page, 2 + i ); - - // Next four page buttons - for ( int i = 0, xOffset = 300, gumpID = 2229; i < 4; ++i, xOffset += 35, ++gumpID ) - AddButton( xOffset, 187, gumpID, gumpID, 0, GumpButtonType.Page, 6 + i ); - - // Charges - AddHtmlLocalized( 140, 40, 80, 18, 1011296, false, false ); // Charges: - AddHtml( 220, 40, 30, 18, Book.CurCharges.ToString(), false, false ); - - // Max charges - AddHtmlLocalized( 300, 40, 100, 18, 1011297, false, false ); // Max Charges: - AddHtml( 400, 40, 30, 18, Book.MaxCharges.ToString(), false, false ); - } - - private void AddIndex() - { - // Index - AddPage( 1 ); - - // Rename button - AddButton( 125, 15, 2472, 2473, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 158, 22, 100, 18, 1011299, false, false ); // Rename book - - // List of entries - List entries = Book.Entries; - - for ( int i = 0; i < 16; ++i ) - { - string desc; - int hue; - - if ( i < entries.Count ) - { - desc = GetName( entries[i].Description ); - hue = GetMapHue( entries[i].Map ); - } - else - { - desc = "Empty"; - hue = 0; - } - - // Use charge button - AddButton( 130 + ((i / 8) * 160), 65 + ((i % 8) * 15), 2103, 2104, 2 + (i * 6) + 0, GumpButtonType.Reply, 0 ); - - // Description label - AddLabelCropped( 145 + ((i / 8) * 160), 60 + ((i % 8) * 15), 115, 17, hue, desc ); - } - - // Turn page button - AddButton( 393, 14, 2206, 2206, 0, GumpButtonType.Page, 2 ); - } - - private void AddDetails( int index, int half ) - { - // Use charge button - AddButton( 130 + (half * 160), 65, 2103, 2104, 2 + (index * 6) + 0, GumpButtonType.Reply, 0 ); - - string desc; - int hue; - - if ( index < Book.Entries.Count ) - { - RunebookEntry e = (RunebookEntry)Book.Entries[index]; - - desc = GetName( e.Description ); - hue = GetMapHue( e.Map ); - - // Location labels - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - - if ( Sextant.Format( e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - { - AddLabel( 135 + (half * 160), 80, 0, $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}"); - AddLabel( 135 + (half * 160), 95, 0, $"{xLong}� {xMins}'{(xEast ? "E" : "W")}"); - } - - // Drop rune button - AddButton( 135 + (half * 160), 115, 2437, 2438, 2 + (index * 6) + 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 150 + (half * 160), 115, 100, 18, 1011298, false, false ); // Drop rune - - // Set as default button - int defButtonID = e != Book.Default ? 2361 : 2360; - - AddButton( 160 + (half * 140), 20, defButtonID, defButtonID, 2 + (index * 6) + 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 175 + (half * 140), 15, 100, 18, 1011300, false, false ); // Set default - - if ( Core.AOS ) - { - AddButton( 135 + (half * 160), 140, 2103, 2104, 2 + (index * 6) + 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 150 + (half * 160), 136, 110, 20, 1062722, false, false ); // Recall - - AddButton( 135 + (half * 160), 158, 2103, 2104, 2 + (index * 6) + 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 150 + (half * 160), 154, 110, 20, 1062723, false, false ); // Gate Travel - - AddButton( 135 + (half * 160), 176, 2103, 2104, 2 + (index * 6) + 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 150 + (half * 160), 172, 110, 20, 1062724, false, false ); // Sacred Journey - } - else - { - // Recall button - AddButton( 135 + (half * 160), 140, 2271, 2271, 2 + (index * 6) + 3, GumpButtonType.Reply, 0 ); - - // Gate button - AddButton( 205 + (half * 160), 140, 2291, 2291, 2 + (index * 6) + 4, GumpButtonType.Reply, 0 ); - } - } - else - { - desc = "Empty"; - hue = 0; - } - - // Description label - AddLabelCropped( 145 + (half * 160), 60, 115, 17, hue, desc ); - } - - public RunebookGump( Mobile from, Runebook book ) : base( 150, 200 ) - { - Book = book; - - AddBackground(); - AddIndex(); - - for ( int page = 0; page < 8; ++page ) - { - AddPage( 2 + page ); - - AddButton( 125, 14, 2205, 2205, 0, GumpButtonType.Page, 1 + page ); - - if ( page < 7 ) - AddButton( 393, 14, 2206, 2206, 0, GumpButtonType.Page, 3 + page ); - - for ( int half = 0; half < 2; ++half ) - AddDetails( (page * 2) + half, half ); - } - } - - public static bool HasSpell( Mobile from, int spellID ) - { - Spellbook book = Spellbook.Find( from, spellID ); - - return ( book != null && book.HasSpell( spellID ) ); - } - - private class InternalPrompt : Prompt - { - private Runebook m_Book; - - public InternalPrompt( Runebook book ) - { - m_Book = book; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Book.Deleted || !from.InRange( m_Book.GetWorldLocation(), (Core.ML ? 3 : 1) ) ) - return; - - if ( m_Book.CheckAccess( from ) ) - { - m_Book.Description = Utility.FixHtml( text.Trim() ); - - from.CloseGump( typeof( RunebookGump ) ); - from.SendGump( new RunebookGump( from, m_Book ) ); - - from.SendMessage( "The book's title has been changed." ); - } - else - { - m_Book.Openers.Remove( from ); - - from.SendLocalizedMessage( 502416 ); // That cannot be done while the book is locked down. - } - } - - public override void OnCancel( Mobile from ) - { - from.SendLocalizedMessage( 502415 ); // Request cancelled. - - if ( !m_Book.Deleted && from.InRange( m_Book.GetWorldLocation(), (Core.ML ? 3 : 1) ) ) - { - from.CloseGump( typeof( RunebookGump ) ); - from.SendGump( new RunebookGump( from, m_Book ) ); - } - } - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; - - if ( Book.Deleted || !from.InRange( Book.GetWorldLocation(), (Core.ML ? 3 : 1) ) || !Multis.DesignContext.Check( from ) ) - { - Book.Openers.Remove( from ); - return; - } - - int buttonID = info.ButtonID; - - if ( buttonID == 1 ) // Rename book - { - if ( !Book.IsLockedDown || from.AccessLevel >= AccessLevel.GameMaster ) - { - from.SendLocalizedMessage( 502414 ); // Please enter a title for the runebook: - from.Prompt = new InternalPrompt( Book ); - } - else - { - Book.Openers.Remove( from ); - - from.SendLocalizedMessage( 502413, null, 0x35 ); // That cannot be done while the book is locked down. - } - } - else - { - buttonID -= 2; - - int index = buttonID / 6; - int type = buttonID % 6; - - if ( index >= 0 && index < Book.Entries.Count ) - { - RunebookEntry e = (RunebookEntry)Book.Entries[index]; - - switch ( type ) - { - case 0: // Use charges - { - if ( Book.CurCharges <= 0 ) - { - from.CloseGump( typeof( RunebookGump ) ); - from.SendGump( new RunebookGump( from, Book ) ); - - from.SendLocalizedMessage( 502412 ); // There are no charges left on that item. - } - else - { - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - - if ( Sextant.Format( e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - { - string location = - $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; - from.SendMessage( location ); - } - - Book.OnTravel(); - new RecallSpell( from, Book, e, Book ).Cast(); - - Book.Openers.Remove( from ); - } - - break; - } - case 1: // Drop rune - { - if ( !Book.IsLockedDown || from.AccessLevel >= AccessLevel.GameMaster ) - { - Book.DropRune( from, e, index ); - - from.CloseGump( typeof( RunebookGump ) ); - if ( !Core.ML ) - from.SendGump( new RunebookGump( from, Book ) ); - } - else - { - Book.Openers.Remove( from ); - - from.SendLocalizedMessage( 502413, null, 0x35 ); // That cannot be done while the book is locked down. - } - - break; - } - case 2: // Set default - { - if ( Book.CheckAccess( from ) ) - { - Book.Default = e; - - from.CloseGump( typeof( RunebookGump ) ); - from.SendGump( new RunebookGump( from, Book ) ); - - from.SendLocalizedMessage( 502417 ); // New default location set. - } - - break; - } - case 3: // Recall - { - if ( HasSpell( from, 31 ) ) - { - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - - if ( Sextant.Format( e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - { - string location = - $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; - from.SendMessage( location ); - } - - Book.OnTravel(); - new RecallSpell( from, null, e, null ).Cast(); - } - else - { - from.SendLocalizedMessage( 500015 ); // You do not have that spell! - } - - Book.Openers.Remove( from ); - - break; - } - case 4: // Gate - { - if ( HasSpell( from, 51 ) ) - { - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - - if ( Sextant.Format( e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - { - string location = - $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; - from.SendMessage( location ); - } - - Book.OnTravel(); - new GateTravelSpell( from, null, e ).Cast(); - } - else - { - from.SendLocalizedMessage( 500015 ); // You do not have that spell! - } - - Book.Openers.Remove( from ); - - break; - } - case 5: // Sacred Journey - { - if ( Core.AOS ) - { - if ( HasSpell( from, 209 ) ) - { - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - - if ( Sextant.Format( e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - { - string location = - $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; - from.SendMessage( location ); - } - - Book.OnTravel(); - new SacredJourneySpell( from, null, e, null ).Cast(); - } - else - { - from.SendLocalizedMessage( 500015 ); // You do not have that spell! - } - } - - Book.Openers.Remove( from ); - - break; - } - } - } - else - Book.Openers.Remove( from ); - } - } - } + public class RunebookGump : Gump + { + public RunebookGump(Mobile from, Runebook book) : base(150, 200) + { + Book = book; + + AddBackground(); + AddIndex(); + + for (int page = 0; page < 8; ++page) + { + AddPage(2 + page); + + AddButton(125, 14, 2205, 2205, 0, GumpButtonType.Page, 1 + page); + + if (page < 7) + AddButton(393, 14, 2206, 2206, 0, GumpButtonType.Page, 3 + page); + + for (int half = 0; half < 2; ++half) + AddDetails(page * 2 + half, half); + } + } + + public Runebook Book{ get; } + + public int GetMapHue(Map map) + { + if (map == Map.Trammel) + return 10; + if (map == Map.Felucca) + return 81; + if (map == Map.Ilshenar) + return 1102; + if (map == Map.Malas) + return 1102; + if (map == Map.Tokuno) + return 1154; + + return 0; + } + + public string GetName(string name) + { + if (name == null || (name = name.Trim()).Length <= 0) + return "(indescript)"; + + return name; + } + + private void AddBackground() + { + AddPage(0); + + // Background image + AddImage(100, 10, 2200); + + // Two separators + for (int i = 0; i < 2; ++i) + { + int xOffset = 125 + i * 165; + + AddImage(xOffset, 50, 57); + xOffset += 20; + + for (int j = 0; j < 6; ++j, xOffset += 15) + AddImage(xOffset, 50, 58); + + AddImage(xOffset - 5, 50, 59); + } + + // First four page buttons + for (int i = 0, xOffset = 130, gumpID = 2225; i < 4; ++i, xOffset += 35, ++gumpID) + AddButton(xOffset, 187, gumpID, gumpID, 0, GumpButtonType.Page, 2 + i); + + // Next four page buttons + for (int i = 0, xOffset = 300, gumpID = 2229; i < 4; ++i, xOffset += 35, ++gumpID) + AddButton(xOffset, 187, gumpID, gumpID, 0, GumpButtonType.Page, 6 + i); + + // Charges + AddHtmlLocalized(140, 40, 80, 18, 1011296, false, false); // Charges: + AddHtml(220, 40, 30, 18, Book.CurCharges.ToString(), false, false); + + // Max charges + AddHtmlLocalized(300, 40, 100, 18, 1011297, false, false); // Max Charges: + AddHtml(400, 40, 30, 18, Book.MaxCharges.ToString(), false, false); + } + + private void AddIndex() + { + // Index + AddPage(1); + + // Rename button + AddButton(125, 15, 2472, 2473, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(158, 22, 100, 18, 1011299, false, false); // Rename book + + // List of entries + List entries = Book.Entries; + + for (int i = 0; i < 16; ++i) + { + string desc; + int hue; + + if (i < entries.Count) + { + desc = GetName(entries[i].Description); + hue = GetMapHue(entries[i].Map); + } + else + { + desc = "Empty"; + hue = 0; + } + + // Use charge button + AddButton(130 + i / 8 * 160, 65 + i % 8 * 15, 2103, 2104, 2 + i * 6 + 0, GumpButtonType.Reply, 0); + + // Description label + AddLabelCropped(145 + i / 8 * 160, 60 + i % 8 * 15, 115, 17, hue, desc); + } + + // Turn page button + AddButton(393, 14, 2206, 2206, 0, GumpButtonType.Page, 2); + } + + private void AddDetails(int index, int half) + { + // Use charge button + AddButton(130 + half * 160, 65, 2103, 2104, 2 + index * 6 + 0, GumpButtonType.Reply, 0); + + string desc; + int hue; + + if (index < Book.Entries.Count) + { + RunebookEntry e = Book.Entries[index]; + + desc = GetName(e.Description); + hue = GetMapHue(e.Map); + + // Location labels + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + if (Sextant.Format(e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth)) + { + AddLabel(135 + half * 160, 80, 0, $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}"); + AddLabel(135 + half * 160, 95, 0, $"{xLong}� {xMins}'{(xEast ? "E" : "W")}"); + } + + // Drop rune button + AddButton(135 + half * 160, 115, 2437, 2438, 2 + index * 6 + 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(150 + half * 160, 115, 100, 18, 1011298, false, false); // Drop rune + + // Set as default button + int defButtonID = e != Book.Default ? 2361 : 2360; + + AddButton(160 + half * 140, 20, defButtonID, defButtonID, 2 + index * 6 + 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(175 + half * 140, 15, 100, 18, 1011300, false, false); // Set default + + if (Core.AOS) + { + AddButton(135 + half * 160, 140, 2103, 2104, 2 + index * 6 + 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(150 + half * 160, 136, 110, 20, 1062722, false, false); // Recall + + AddButton(135 + half * 160, 158, 2103, 2104, 2 + index * 6 + 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(150 + half * 160, 154, 110, 20, 1062723, false, false); // Gate Travel + + AddButton(135 + half * 160, 176, 2103, 2104, 2 + index * 6 + 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(150 + half * 160, 172, 110, 20, 1062724, false, false); // Sacred Journey + } + else + { + // Recall button + AddButton(135 + half * 160, 140, 2271, 2271, 2 + index * 6 + 3, GumpButtonType.Reply, 0); + + // Gate button + AddButton(205 + half * 160, 140, 2291, 2291, 2 + index * 6 + 4, GumpButtonType.Reply, 0); + } + } + else + { + desc = "Empty"; + hue = 0; + } + + // Description label + AddLabelCropped(145 + half * 160, 60, 115, 17, hue, desc); + } + + public static bool HasSpell(Mobile from, int spellID) + { + Spellbook book = Spellbook.Find(from, spellID); + + return book != null && book.HasSpell(spellID); + } + + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; + + if (Book.Deleted || !from.InRange(Book.GetWorldLocation(), Core.ML ? 3 : 1) || !DesignContext.Check(from)) + { + Book.Openers.Remove(from); + return; + } + + int buttonID = info.ButtonID; + + if (buttonID == 1) // Rename book + { + if (!Book.IsLockedDown || from.AccessLevel >= AccessLevel.GameMaster) + { + from.SendLocalizedMessage(502414); // Please enter a title for the runebook: + from.Prompt = new InternalPrompt(Book); + } + else + { + Book.Openers.Remove(from); + + from.SendLocalizedMessage(502413, null, 0x35); // That cannot be done while the book is locked down. + } + } + else + { + buttonID -= 2; + + int index = buttonID / 6; + int type = buttonID % 6; + + if (index >= 0 && index < Book.Entries.Count) + { + RunebookEntry e = Book.Entries[index]; + + switch (type) + { + case 0: // Use charges + { + if (Book.CurCharges <= 0) + { + from.CloseGump(typeof(RunebookGump)); + from.SendGump(new RunebookGump(from, Book)); + + from.SendLocalizedMessage(502412); // There are no charges left on that item. + } + else + { + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + if (Sextant.Format(e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, + ref ySouth)) + { + string location = + $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; + from.SendMessage(location); + } + + Book.OnTravel(); + new RecallSpell(from, Book, e, Book).Cast(); + + Book.Openers.Remove(from); + } + + break; + } + case 1: // Drop rune + { + if (!Book.IsLockedDown || from.AccessLevel >= AccessLevel.GameMaster) + { + Book.DropRune(from, e, index); + + from.CloseGump(typeof(RunebookGump)); + if (!Core.ML) + from.SendGump(new RunebookGump(from, Book)); + } + else + { + Book.Openers.Remove(from); + + from.SendLocalizedMessage(502413, null, + 0x35); // That cannot be done while the book is locked down. + } + + break; + } + case 2: // Set default + { + if (Book.CheckAccess(from)) + { + Book.Default = e; + + from.CloseGump(typeof(RunebookGump)); + from.SendGump(new RunebookGump(from, Book)); + + from.SendLocalizedMessage(502417); // New default location set. + } + + break; + } + case 3: // Recall + { + if (HasSpell(from, 31)) + { + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + if (Sextant.Format(e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, + ref ySouth)) + { + string location = + $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; + from.SendMessage(location); + } + + Book.OnTravel(); + new RecallSpell(from, null, e, null).Cast(); + } + else + { + from.SendLocalizedMessage(500015); // You do not have that spell! + } + + Book.Openers.Remove(from); + + break; + } + case 4: // Gate + { + if (HasSpell(from, 51)) + { + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + if (Sextant.Format(e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, + ref ySouth)) + { + string location = + $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; + from.SendMessage(location); + } + + Book.OnTravel(); + new GateTravelSpell(from, null, e).Cast(); + } + else + { + from.SendLocalizedMessage(500015); // You do not have that spell! + } + + Book.Openers.Remove(from); + + break; + } + case 5: // Sacred Journey + { + if (Core.AOS) + { + if (HasSpell(from, 209)) + { + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + if (Sextant.Format(e.Location, e.Map, ref xLong, ref yLat, ref xMins, ref yMins, + ref xEast, ref ySouth)) + { + string location = + $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; + from.SendMessage(location); + } + + Book.OnTravel(); + new SacredJourneySpell(from, null, e, null).Cast(); + } + else + { + from.SendLocalizedMessage(500015); // You do not have that spell! + } + } + + Book.Openers.Remove(from); + + break; + } + } + } + else + { + Book.Openers.Remove(from); + } + } + } + + private class InternalPrompt : Prompt + { + private Runebook m_Book; + + public InternalPrompt(Runebook book) + { + m_Book = book; + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Book.Deleted || !from.InRange(m_Book.GetWorldLocation(), Core.ML ? 3 : 1)) + return; + + if (m_Book.CheckAccess(from)) + { + m_Book.Description = Utility.FixHtml(text.Trim()); + + from.CloseGump(typeof(RunebookGump)); + from.SendGump(new RunebookGump(from, m_Book)); + + from.SendMessage("The book's title has been changed."); + } + else + { + m_Book.Openers.Remove(from); + + from.SendLocalizedMessage(502416); // That cannot be done while the book is locked down. + } + } + + public override void OnCancel(Mobile from) + { + from.SendLocalizedMessage(502415); // Request cancelled. + + if (!m_Book.Deleted && from.InRange(m_Book.GetWorldLocation(), Core.ML ? 3 : 1)) + { + from.CloseGump(typeof(RunebookGump)); + from.SendGump(new RunebookGump(from, m_Book)); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/SetSecureLevelGump.cs b/Scripts/Gumps/SetSecureLevelGump.cs index c24513dd3..f422d17d4 100644 --- a/Scripts/Gumps/SetSecureLevelGump.cs +++ b/Scripts/Gumps/SetSecureLevelGump.cs @@ -1,91 +1,103 @@ +using Server.Guilds; using Server.Multis; using Server.Network; -using Server.Guilds; namespace Server.Gumps { - public interface ISecurable - { - SecureLevel Level{ get; set; } - } + public interface ISecurable + { + SecureLevel Level{ get; set; } + } - public class SetSecureLevelGump : Gump - { - private ISecurable m_Info; + public class SetSecureLevelGump : Gump + { + private ISecurable m_Info; - public SetSecureLevelGump( Mobile owner, ISecurable info, BaseHouse house ) : base( 50, 50 ) - { - m_Info = info; + public SetSecureLevelGump(Mobile owner, ISecurable info, BaseHouse house) : base(50, 50) + { + m_Info = info; - AddPage( 0 ); + AddPage(0); - int offset = ( Guild.NewGuildSystem )? 20 : 0; + int offset = Guild.NewGuildSystem ? 20 : 0; - AddBackground( 0, 0, 220, 160 + offset, 5054 ); + AddBackground(0, 0, 220, 160 + offset, 5054); - AddImageTiled( 10, 10, 200, 20, 5124 ); - AddImageTiled( 10, 40, 200, 20, 5124 ); - AddImageTiled( 10, 70, 200, 80 + offset, 5124 ); + AddImageTiled(10, 10, 200, 20, 5124); + AddImageTiled(10, 40, 200, 20, 5124); + AddImageTiled(10, 70, 200, 80 + offset, 5124); - AddAlphaRegion( 10, 10, 200, 140 ); + AddAlphaRegion(10, 10, 200, 140); - AddHtmlLocalized( 10, 10, 200, 20, 1061276, 32767, false, false ); //
SET ACCESS
- AddHtmlLocalized( 10, 40, 100, 20, 1041474, 32767, false, false ); // Owner: + AddHtmlLocalized(10, 10, 200, 20, 1061276, 32767, false, false); //
SET ACCESS
+ AddHtmlLocalized(10, 40, 100, 20, 1041474, 32767, false, false); // Owner: - AddLabel( 110, 40, 1152, owner == null ? "" : owner.Name ); + AddLabel(110, 40, 1152, owner == null ? "" : owner.Name); - AddButton( 10, 70, GetFirstID( SecureLevel.Owner ), 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 70, 150, 20, 1061277, GetColor( SecureLevel.Owner ), false, false ); // Owner Only + AddButton(10, 70, GetFirstID(SecureLevel.Owner), 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 70, 150, 20, 1061277, GetColor(SecureLevel.Owner), false, false); // Owner Only - AddButton( 10, 90, GetFirstID( SecureLevel.CoOwners ), 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 90, 150, 20, 1061278, GetColor( SecureLevel.CoOwners ), false, false ); // Co-Owners + AddButton(10, 90, GetFirstID(SecureLevel.CoOwners), 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 90, 150, 20, 1061278, GetColor(SecureLevel.CoOwners), false, false); // Co-Owners - AddButton( 10, 110, GetFirstID( SecureLevel.Friends ), 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 110, 150, 20, 1061279, GetColor( SecureLevel.Friends ), false, false ); // Friends + AddButton(10, 110, GetFirstID(SecureLevel.Friends), 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 110, 150, 20, 1061279, GetColor(SecureLevel.Friends), false, false); // Friends - Mobile houseOwner = house.Owner; - if ( Guild.NewGuildSystem && house != null && houseOwner?.Guild != null && ((Guild)houseOwner.Guild).Leader == houseOwner ) //Only the actual House owner AND guild master can set guild secures - { - AddButton( 10, 130, GetFirstID( SecureLevel.Guild ), 4007, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 130, 150, 20, 1063455, GetColor( SecureLevel.Guild ), false, false ); // Guild Members - } + Mobile houseOwner = house.Owner; + if (Guild.NewGuildSystem && house != null && houseOwner?.Guild != null && + ((Guild)houseOwner.Guild).Leader == houseOwner + ) //Only the actual House owner AND guild master can set guild secures + { + AddButton(10, 130, GetFirstID(SecureLevel.Guild), 4007, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 130, 150, 20, 1063455, GetColor(SecureLevel.Guild), false, false); // Guild Members + } - AddButton( 10, 130 + offset, GetFirstID( SecureLevel.Anyone ), 4007, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 130 + offset, 150, 20, 1061626, GetColor( SecureLevel.Anyone ), false, false ); // Anyone - } + AddButton(10, 130 + offset, GetFirstID(SecureLevel.Anyone), 4007, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 130 + offset, 150, 20, 1061626, GetColor(SecureLevel.Anyone), false, false); // Anyone + } - public int GetColor( SecureLevel level ) - { - return ( m_Info.Level == level ) ? 0x7F18 : 0x7FFF; - } + public int GetColor(SecureLevel level) + { + return m_Info.Level == level ? 0x7F18 : 0x7FFF; + } - public int GetFirstID( SecureLevel level ) - { - return ( m_Info.Level == level ) ? 4006 : 4005; - } + public int GetFirstID(SecureLevel level) + { + return m_Info.Level == level ? 4006 : 4005; + } - public override void OnResponse( NetState state, RelayInfo info ) - { - SecureLevel level = m_Info.Level; + public override void OnResponse(NetState state, RelayInfo info) + { + SecureLevel level = m_Info.Level; - switch ( info.ButtonID ) - { - case 1: level = SecureLevel.Owner; break; - case 2: level = SecureLevel.CoOwners; break; - case 3: level = SecureLevel.Friends; break; - case 4: level = SecureLevel.Anyone; break; - case 5: level = SecureLevel.Guild; break; - } + switch (info.ButtonID) + { + case 1: + level = SecureLevel.Owner; + break; + case 2: + level = SecureLevel.CoOwners; + break; + case 3: + level = SecureLevel.Friends; + break; + case 4: + level = SecureLevel.Anyone; + break; + case 5: + level = SecureLevel.Guild; + break; + } - if ( m_Info.Level == level ) - { - state.Mobile.SendLocalizedMessage( 1061281 ); // Access level unchanged. - } - else - { - m_Info.Level = level; - state.Mobile.SendLocalizedMessage( 1061280 ); // New access level set. - } - } - } -} + if (m_Info.Level == level) + { + state.Mobile.SendLocalizedMessage(1061281); // Access level unchanged. + } + else + { + m_Info.Level = level; + state.Mobile.SendLocalizedMessage(1061280); // New access level set. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/SkillsGump.cs b/Scripts/Gumps/SkillsGump.cs index d290d2f7f..3578bef25 100644 --- a/Scripts/Gumps/SkillsGump.cs +++ b/Scripts/Gumps/SkillsGump.cs @@ -1,541 +1,565 @@ using System; using System.Collections; -using Server.Network; using Server.Commands; +using Server.Network; namespace Server.Gumps { - public class EditSkillGump : Gump - { - public static readonly bool OldStyle = PropsConfig.OldStyle; - - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; - - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - - public static readonly int OffsetSize = PropsConfig.OffsetSize; - - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; - - private static readonly int EntryWidth = 160; - - private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + (2 * (EntryHeight + OffsetSize)); - - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; - - private Mobile m_From; - private Mobile m_Target; - private Skill m_Skill; - - private SkillsGumpGroup m_Selected; - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - { - try - { - if ( m_From.AccessLevel >= AccessLevel.GameMaster ) - { - TextRelay text = info.GetTextEntry( 0 ); - - if ( text != null ) - { - m_Skill.Base = Convert.ToDouble( text.Text ); - CommandLogging.LogChangeProperty( m_From, m_Target, $"{m_Skill}.Base", m_Skill.Base.ToString() ); - } - } - else - { - m_From.SendMessage( "You may not change that." ); - } - - m_From.SendGump( new SkillsGump( m_From, m_Target, m_Selected ) ); - } - catch - { - m_From.SendMessage( "Bad format. ###.# expected." ); - m_From.SendGump( new EditSkillGump( m_From, m_Target, m_Skill, m_Selected ) ); - } - } - else - { - m_From.SendGump( new SkillsGump( m_From, m_Target, m_Selected ) ); - } - } + public class EditSkillGump : Gump + { + public static readonly bool OldStyle = PropsConfig.OldStyle; - public EditSkillGump( Mobile from, Mobile target, Skill skill, SkillsGumpGroup selected ) : base( GumpOffsetX, GumpOffsetY ) - { - m_From = from; - m_Target = target; - m_Skill = skill; - m_Selected = selected; + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - string initialText = m_Skill.Base.ToString( "F1" ); + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - AddPage( 0 ); + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; + + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; + + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; + + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; + + public static readonly int OffsetSize = PropsConfig.OffsetSize; + + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; + + private static readonly int EntryWidth = 160; + + private static readonly int TotalWidth = OffsetSize + EntryWidth + OffsetSize + SetWidth + OffsetSize; + private static readonly int TotalHeight = OffsetSize + 2 * (EntryHeight + OffsetSize); + + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; + + private Mobile m_From; + + private SkillsGumpGroup m_Selected; + private Skill m_Skill; + private Mobile m_Target; + + public EditSkillGump(Mobile from, Mobile target, Skill skill, SkillsGumpGroup selected) : base(GumpOffsetX, + GumpOffsetY) + { + m_From = from; + m_Target = target; + m_Skill = skill; + m_Selected = selected; + + string initialText = m_Skill.Base.ToString("F1"); + + AddPage(0); + + AddBackground(0, 0, BackWidth, BackHeight, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, + OffsetGumpID); + + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; + + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddLabelCropped(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, skill.Name); + x += EntryWidth + OffsetSize; + + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; - AddBackground( 0, 0, BackWidth, BackHeight, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), TotalHeight, OffsetGumpID ); + AddImageTiled(x, y, EntryWidth, EntryHeight, EntryGumpID); + AddTextEntry(x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, 0, initialText); + x += EntryWidth + OffsetSize; - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddLabelCropped( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, skill.Name ); - x += EntryWidth + OffsetSize; + AddButton(x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0); + } - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; - - AddImageTiled( x, y, EntryWidth, EntryHeight, EntryGumpID ); - AddTextEntry( x + TextOffsetX, y, EntryWidth - TextOffsetX, EntryHeight, TextHue, 0, initialText ); - x += EntryWidth + OffsetSize; - - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); - - AddButton( x + SetOffsetX, y + SetOffsetY, SetButtonID1, SetButtonID2, 1, GumpButtonType.Reply, 0 ); - } - } - - public class SkillsGump : Gump - { - public static bool OldStyle = PropsConfig.OldStyle; - - public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; - public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - - public static readonly int TextHue = PropsConfig.TextHue; - public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - - public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; - public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; - public static readonly int EntryGumpID = PropsConfig.EntryGumpID; - public static readonly int BackGumpID = PropsConfig.BackGumpID; - public static readonly int SetGumpID = PropsConfig.SetGumpID; - - public static readonly int SetWidth = PropsConfig.SetWidth; - public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; - public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; - public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - - public static readonly int PrevWidth = PropsConfig.PrevWidth; - public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; - public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; - public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - - public static readonly int NextWidth = PropsConfig.NextWidth; - public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; - public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; - public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - - public static readonly int OffsetSize = PropsConfig.OffsetSize; - - public static readonly int EntryHeight = PropsConfig.EntryHeight; - public static readonly int BorderSize = PropsConfig.BorderSize; - - /* - private static bool PrevLabel = OldStyle, NextLabel = OldStyle; - - private static readonly int PrevLabelOffsetX = PrevWidth + 1; - - private static readonly int PrevLabelOffsetY = 0; - - private static readonly int NextLabelOffsetX = -29; - private static readonly int NextLabelOffsetY = 0; - * */ - - private static readonly int NameWidth = 107; - private static readonly int ValueWidth = 128; - - private static readonly int EntryCount = 15; - - private static readonly int TypeWidth = NameWidth + OffsetSize + ValueWidth; - - private static readonly int TotalWidth = OffsetSize + NameWidth + OffsetSize + ValueWidth + OffsetSize + SetWidth + OffsetSize; - private static readonly int TotalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (EntryCount + 1)); - - private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; - private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; - - private static readonly int IndentWidth = 12; - - private Mobile m_From; - private Mobile m_Target; - - private SkillsGumpGroup[] m_Groups; - private SkillsGumpGroup m_Selected; - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int buttonID = info.ButtonID - 1; - - int index = buttonID / 3; - int type = buttonID % 3; - - switch ( type ) - { - case 0: - { - if ( index >= 0 && index < m_Groups.Length ) - { - SkillsGumpGroup newSelection = m_Groups[index]; - - if ( m_Selected != newSelection ) - m_From.SendGump( new SkillsGump( m_From, m_Target, newSelection ) ); - else - m_From.SendGump( new SkillsGump( m_From, m_Target, null ) ); - } - - break; - } - case 1: - { - if ( m_Selected != null && index >= 0 && index < m_Selected.Skills.Length ) - { - Skill sk = m_Target.Skills[m_Selected.Skills[index]]; - - if ( sk != null ) - { - if ( m_From.AccessLevel >= AccessLevel.GameMaster ) - { - m_From.SendGump( new EditSkillGump( m_From, m_Target, sk, m_Selected ) ); - } - else - { - m_From.SendMessage( "You may not change that." ); - m_From.SendGump( new SkillsGump( m_From, m_Target, m_Selected ) ); - } - } - else - { - m_From.SendGump( new SkillsGump( m_From, m_Target, m_Selected ) ); - } - } - - break; - } - case 2: - { - if ( m_Selected != null && index >= 0 && index < m_Selected.Skills.Length ) - { - Skill sk = m_Target.Skills[m_Selected.Skills[index]]; - - if ( sk != null ) - { - if ( m_From.AccessLevel >= AccessLevel.GameMaster ) - { - switch ( sk.Lock ) - { - case SkillLock.Up: sk.SetLockNoRelay( SkillLock.Down ); sk.Update(); break; - case SkillLock.Down: sk.SetLockNoRelay( SkillLock.Locked ); sk.Update(); break; - case SkillLock.Locked: sk.SetLockNoRelay( SkillLock.Up ); sk.Update(); break; - } - } - else - { - m_From.SendMessage( "You may not change that." ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + try + { + if (m_From.AccessLevel >= AccessLevel.GameMaster) + { + TextRelay text = info.GetTextEntry(0); - m_From.SendGump( new SkillsGump( m_From, m_Target, m_Selected ) ); - } - } + if (text != null) + { + m_Skill.Base = Convert.ToDouble(text.Text); + CommandLogging.LogChangeProperty(m_From, m_Target, $"{m_Skill}.Base", m_Skill.Base.ToString()); + } + } + else + { + m_From.SendMessage("You may not change that."); + } - break; - } - } - } + m_From.SendGump(new SkillsGump(m_From, m_Target, m_Selected)); + } + catch + { + m_From.SendMessage("Bad format. ###.# expected."); + m_From.SendGump(new EditSkillGump(m_From, m_Target, m_Skill, m_Selected)); + } + else + m_From.SendGump(new SkillsGump(m_From, m_Target, m_Selected)); + } + } - public int GetButtonID( int type, int index ) - { - return 1 + (index * 3) + type; - } + public class SkillsGump : Gump + { + public static bool OldStyle = PropsConfig.OldStyle; - public SkillsGump( Mobile from, Mobile target ) : this( from, target, null ) - { - } + public static readonly int GumpOffsetX = PropsConfig.GumpOffsetX; + public static readonly int GumpOffsetY = PropsConfig.GumpOffsetY; - public SkillsGump( Mobile from, Mobile target, SkillsGumpGroup selected ) : base( GumpOffsetX, GumpOffsetY ) - { - m_From = from; - m_Target = target; + public static readonly int TextHue = PropsConfig.TextHue; + public static readonly int TextOffsetX = PropsConfig.TextOffsetX; - m_Groups = SkillsGumpGroup.Groups; - m_Selected = selected; - - int count = m_Groups.Length; - - if ( selected != null ) - count += selected.Skills.Length; - - int totalHeight = OffsetSize + ((EntryHeight + OffsetSize) * (count + 1)); - - AddPage( 0 ); - - AddBackground( 0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID ); - AddImageTiled( BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, OffsetGumpID ); - - int x = BorderSize + OffsetSize; - int y = BorderSize + OffsetSize; - - int emptyWidth = TotalWidth - PrevWidth - NextWidth - (OffsetSize * 4) - (OldStyle ? SetWidth + OffsetSize : 0); + public static readonly int OffsetGumpID = PropsConfig.OffsetGumpID; + public static readonly int HeaderGumpID = PropsConfig.HeaderGumpID; + public static readonly int EntryGumpID = PropsConfig.EntryGumpID; + public static readonly int BackGumpID = PropsConfig.BackGumpID; + public static readonly int SetGumpID = PropsConfig.SetGumpID; - if ( OldStyle ) - AddImageTiled( x, y, TotalWidth - (OffsetSize * 3) - SetWidth, EntryHeight, HeaderGumpID ); - else - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + public static readonly int SetWidth = PropsConfig.SetWidth; + public static readonly int SetOffsetX = PropsConfig.SetOffsetX, SetOffsetY = PropsConfig.SetOffsetY; + public static readonly int SetButtonID1 = PropsConfig.SetButtonID1; + public static readonly int SetButtonID2 = PropsConfig.SetButtonID2; - x += PrevWidth + OffsetSize; + public static readonly int PrevWidth = PropsConfig.PrevWidth; + public static readonly int PrevOffsetX = PropsConfig.PrevOffsetX, PrevOffsetY = PropsConfig.PrevOffsetY; + public static readonly int PrevButtonID1 = PropsConfig.PrevButtonID1; + public static readonly int PrevButtonID2 = PropsConfig.PrevButtonID2; - if ( !OldStyle ) - AddImageTiled( x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, HeaderGumpID ); + public static readonly int NextWidth = PropsConfig.NextWidth; + public static readonly int NextOffsetX = PropsConfig.NextOffsetX, NextOffsetY = PropsConfig.NextOffsetY; + public static readonly int NextButtonID1 = PropsConfig.NextButtonID1; + public static readonly int NextButtonID2 = PropsConfig.NextButtonID2; - x += emptyWidth + OffsetSize; + public static readonly int OffsetSize = PropsConfig.OffsetSize; - if ( !OldStyle ) - AddImageTiled( x, y, NextWidth, EntryHeight, HeaderGumpID ); + public static readonly int EntryHeight = PropsConfig.EntryHeight; + public static readonly int BorderSize = PropsConfig.BorderSize; - for ( int i = 0; i < m_Groups.Length; ++i ) - { - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + /* + private static bool PrevLabel = OldStyle, NextLabel = OldStyle; - SkillsGumpGroup group = m_Groups[i]; + private static readonly int PrevLabelOffsetX = PrevWidth + 1; + + private static readonly int PrevLabelOffsetY = 0; - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + private static readonly int NextLabelOffsetX = -29; + private static readonly int NextLabelOffsetY = 0; + * */ - if ( group == selected ) - AddButton( x + PrevOffsetX, y + PrevOffsetY, 0x15E2, 0x15E6, GetButtonID( 0, i ), GumpButtonType.Reply, 0 ); - else - AddButton( x + PrevOffsetX, y + PrevOffsetY, 0x15E1, 0x15E5, GetButtonID( 0, i ), GumpButtonType.Reply, 0 ); + private static readonly int NameWidth = 107; + private static readonly int ValueWidth = 128; - x += PrevWidth + OffsetSize; + private static readonly int EntryCount = 15; - x -= (OldStyle ? OffsetSize : 0); + private static readonly int TypeWidth = NameWidth + OffsetSize + ValueWidth; - AddImageTiled( x, y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, EntryGumpID ); - AddLabel( x + TextOffsetX, y, TextHue, group.Name ); + private static readonly int TotalWidth = + OffsetSize + NameWidth + OffsetSize + ValueWidth + OffsetSize + SetWidth + OffsetSize; - x += emptyWidth + (OldStyle ? OffsetSize * 2 : 0); - x += OffsetSize; + private static readonly int TotalHeight = OffsetSize + (EntryHeight + OffsetSize) * (EntryCount + 1); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + private static readonly int BackWidth = BorderSize + TotalWidth + BorderSize; + private static readonly int BackHeight = BorderSize + TotalHeight + BorderSize; - if ( group == selected ) - { - int indentMaskX = BorderSize; - int indentMaskY = y + EntryHeight + OffsetSize; + private static readonly int IndentWidth = 12; - for ( int j = 0; j < group.Skills.Length; ++j ) - { - Skill sk = target.Skills[group.Skills[j]]; + private Mobile m_From; - x = BorderSize + OffsetSize; - y += EntryHeight + OffsetSize; + private SkillsGumpGroup[] m_Groups; + private SkillsGumpGroup m_Selected; + private Mobile m_Target; - x += OffsetSize; - x += IndentWidth; + public SkillsGump(Mobile from, Mobile target) : this(from, target, null) + { + } - AddImageTiled( x, y, PrevWidth, EntryHeight, HeaderGumpID ); + public SkillsGump(Mobile from, Mobile target, SkillsGumpGroup selected) : base(GumpOffsetX, GumpOffsetY) + { + m_From = from; + m_Target = target; - AddButton( x + PrevOffsetX, y + PrevOffsetY, 0x15E1, 0x15E5, GetButtonID( 1, j ), GumpButtonType.Reply, 0 ); + m_Groups = SkillsGumpGroup.Groups; + m_Selected = selected; - x += PrevWidth + OffsetSize; + int count = m_Groups.Length; - x -= (OldStyle ? OffsetSize : 0); + if (selected != null) + count += selected.Skills.Length; - AddImageTiled( x, y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0) - OffsetSize - IndentWidth, EntryHeight, EntryGumpID ); - AddLabel( x + TextOffsetX, y, TextHue, sk == null ? "(null)" : sk.Name ); + int totalHeight = OffsetSize + (EntryHeight + OffsetSize) * (count + 1); - x += emptyWidth + (OldStyle ? OffsetSize * 2 : 0) - OffsetSize - IndentWidth; - x += OffsetSize; + AddPage(0); - if ( SetGumpID != 0 ) - AddImageTiled( x, y, SetWidth, EntryHeight, SetGumpID ); + AddBackground(0, 0, BackWidth, BorderSize + totalHeight + BorderSize, BackGumpID); + AddImageTiled(BorderSize, BorderSize, TotalWidth - (OldStyle ? SetWidth + OffsetSize : 0), totalHeight, + OffsetGumpID); - if ( sk != null ) - { - int buttonID1, buttonID2; - int xOffset, yOffset; + int x = BorderSize + OffsetSize; + int y = BorderSize + OffsetSize; - switch ( sk.Lock ) - { - default: - case SkillLock.Up: buttonID1 = 0x983; buttonID2 = 0x983; xOffset = 6; yOffset = 4; break; - case SkillLock.Down: buttonID1 = 0x985; buttonID2 = 0x985; xOffset = 6; yOffset = 4; break; - case SkillLock.Locked: buttonID1 = 0x82C; buttonID2 = 0x82C; xOffset = 5; yOffset = 2; break; - } - - AddButton( x + xOffset, y + yOffset, buttonID1, buttonID2, GetButtonID( 2, j ), GumpButtonType.Reply, 0 ); - - y += 1; - x -= OffsetSize; - x -= 1; - x -= 50; - - AddImageTiled( x, y, 50, EntryHeight - 2, OffsetGumpID ); - - x += 1; - y += 1; - - AddImageTiled( x, y, 48, EntryHeight - 4, EntryGumpID ); - - AddLabelCropped( x + TextOffsetX, y - 1, 48 - TextOffsetX, EntryHeight - 3, TextHue, sk.Base.ToString( "F1" ) ); - - y -= 2; - } - } - - AddImageTiled( indentMaskX, indentMaskY, IndentWidth + OffsetSize, (group.Skills.Length * (EntryHeight + OffsetSize)) - (i < (m_Groups.Length - 1) ? OffsetSize : 0), BackGumpID + 4 ); - } - } - } - } - - public class SkillsGumpGroup - { - public string Name { get; } - - public SkillName[] Skills { get; } - - public SkillsGumpGroup( string name, SkillName[] skills ) - { - Name = name; - Skills = skills; - - Array.Sort( Skills, new SkillNameComparer() ); - } - - private class SkillNameComparer : IComparer - { - public SkillNameComparer() - { - } - - public int Compare( object x, object y ) - { - SkillName a = (SkillName)x; - SkillName b = (SkillName)y; - - string aName = SkillInfo.Table[(int)a].Name; - string bName = SkillInfo.Table[(int)b].Name; - - return aName.CompareTo( bName ); - } - } - - public static SkillsGumpGroup[] Groups { get; } = - { - new SkillsGumpGroup( "Crafting", new[] - { - SkillName.Alchemy, - SkillName.Blacksmith, - SkillName.Cartography, - SkillName.Carpentry, - SkillName.Cooking, - SkillName.Fletching, - SkillName.Inscribe, - SkillName.Tailoring, - SkillName.Tinkering, - SkillName.Imbuing - } ), - new SkillsGumpGroup( "Bardic", new[] - { - SkillName.Discordance, - SkillName.Musicianship, - SkillName.Peacemaking, - SkillName.Provocation - } ), - new SkillsGumpGroup( "Magical", new[] - { - SkillName.Chivalry, - SkillName.EvalInt, - SkillName.Magery, - SkillName.MagicResist, - SkillName.Meditation, - SkillName.Necromancy, - SkillName.SpiritSpeak, - SkillName.Ninjitsu, - SkillName.Bushido, - SkillName.Spellweaving, - SkillName.Mysticism - } ), - new SkillsGumpGroup( "Miscellaneous", new[] - { - SkillName.Camping, - SkillName.Fishing, - SkillName.Focus, - SkillName.Healing, - SkillName.Herding, - SkillName.Lockpicking, - SkillName.Lumberjacking, - SkillName.Mining, - SkillName.Snooping, - SkillName.Veterinary - } ), - new SkillsGumpGroup( "Combat Ratings", new[] - { - SkillName.Archery, - SkillName.Fencing, - SkillName.Macing, - SkillName.Parry, - SkillName.Swords, - SkillName.Tactics, - SkillName.Wrestling, - SkillName.Throwing - } ), - new SkillsGumpGroup( "Actions", new[] - { - SkillName.AnimalTaming, - SkillName.Begging, - SkillName.DetectHidden, - SkillName.Hiding, - SkillName.RemoveTrap, - SkillName.Poisoning, - SkillName.Stealing, - SkillName.Stealth, - SkillName.Tracking - } ), - new SkillsGumpGroup( "Lore & Knowledge", new[] - { - SkillName.Anatomy, - SkillName.AnimalLore, - SkillName.ArmsLore, - SkillName.Forensics, - SkillName.ItemID, - SkillName.TasteID - } ) - }; - } + int emptyWidth = TotalWidth - PrevWidth - NextWidth - OffsetSize * 4 - (OldStyle ? SetWidth + OffsetSize : 0); + + if (OldStyle) + AddImageTiled(x, y, TotalWidth - OffsetSize * 3 - SetWidth, EntryHeight, HeaderGumpID); + else + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); + + x += PrevWidth + OffsetSize; + + if (!OldStyle) + AddImageTiled(x - (OldStyle ? OffsetSize : 0), y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, + HeaderGumpID); + + x += emptyWidth + OffsetSize; + + if (!OldStyle) + AddImageTiled(x, y, NextWidth, EntryHeight, HeaderGumpID); + + for (int i = 0; i < m_Groups.Length; ++i) + { + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; + + SkillsGumpGroup group = m_Groups[i]; + + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); + + if (group == selected) + AddButton(x + PrevOffsetX, y + PrevOffsetY, 0x15E2, 0x15E6, GetButtonID(0, i), GumpButtonType.Reply, 0); + else + AddButton(x + PrevOffsetX, y + PrevOffsetY, 0x15E1, 0x15E5, GetButtonID(0, i), GumpButtonType.Reply, 0); + + x += PrevWidth + OffsetSize; + + x -= OldStyle ? OffsetSize : 0; + + AddImageTiled(x, y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0), EntryHeight, EntryGumpID); + AddLabel(x + TextOffsetX, y, TextHue, group.Name); + + x += emptyWidth + (OldStyle ? OffsetSize * 2 : 0); + x += OffsetSize; + + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + + if (group == selected) + { + int indentMaskX = BorderSize; + int indentMaskY = y + EntryHeight + OffsetSize; + + for (int j = 0; j < group.Skills.Length; ++j) + { + Skill sk = target.Skills[group.Skills[j]]; + + x = BorderSize + OffsetSize; + y += EntryHeight + OffsetSize; + + x += OffsetSize; + x += IndentWidth; + + AddImageTiled(x, y, PrevWidth, EntryHeight, HeaderGumpID); + + AddButton(x + PrevOffsetX, y + PrevOffsetY, 0x15E1, 0x15E5, GetButtonID(1, j), GumpButtonType.Reply, + 0); + + x += PrevWidth + OffsetSize; + + x -= OldStyle ? OffsetSize : 0; + + AddImageTiled(x, y, emptyWidth + (OldStyle ? OffsetSize * 2 : 0) - OffsetSize - IndentWidth, + EntryHeight, EntryGumpID); + AddLabel(x + TextOffsetX, y, TextHue, sk == null ? "(null)" : sk.Name); + + x += emptyWidth + (OldStyle ? OffsetSize * 2 : 0) - OffsetSize - IndentWidth; + x += OffsetSize; + + if (SetGumpID != 0) + AddImageTiled(x, y, SetWidth, EntryHeight, SetGumpID); + + if (sk != null) + { + int buttonID1, buttonID2; + int xOffset, yOffset; + + switch (sk.Lock) + { + default: + case SkillLock.Up: + buttonID1 = 0x983; + buttonID2 = 0x983; + xOffset = 6; + yOffset = 4; + break; + case SkillLock.Down: + buttonID1 = 0x985; + buttonID2 = 0x985; + xOffset = 6; + yOffset = 4; + break; + case SkillLock.Locked: + buttonID1 = 0x82C; + buttonID2 = 0x82C; + xOffset = 5; + yOffset = 2; + break; + } + + AddButton(x + xOffset, y + yOffset, buttonID1, buttonID2, GetButtonID(2, j), + GumpButtonType.Reply, 0); + + y += 1; + x -= OffsetSize; + x -= 1; + x -= 50; + + AddImageTiled(x, y, 50, EntryHeight - 2, OffsetGumpID); + + x += 1; + y += 1; + + AddImageTiled(x, y, 48, EntryHeight - 4, EntryGumpID); + + AddLabelCropped(x + TextOffsetX, y - 1, 48 - TextOffsetX, EntryHeight - 3, TextHue, + sk.Base.ToString("F1")); + + y -= 2; + } + } + + AddImageTiled(indentMaskX, indentMaskY, IndentWidth + OffsetSize, + group.Skills.Length * (EntryHeight + OffsetSize) - (i < m_Groups.Length - 1 ? OffsetSize : 0), + BackGumpID + 4); + } + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int buttonID = info.ButtonID - 1; + + int index = buttonID / 3; + int type = buttonID % 3; + + switch (type) + { + case 0: + { + if (index >= 0 && index < m_Groups.Length) + { + SkillsGumpGroup newSelection = m_Groups[index]; + + if (m_Selected != newSelection) + m_From.SendGump(new SkillsGump(m_From, m_Target, newSelection)); + else + m_From.SendGump(new SkillsGump(m_From, m_Target, null)); + } + + break; + } + case 1: + { + if (m_Selected != null && index >= 0 && index < m_Selected.Skills.Length) + { + Skill sk = m_Target.Skills[m_Selected.Skills[index]]; + + if (sk != null) + { + if (m_From.AccessLevel >= AccessLevel.GameMaster) + { + m_From.SendGump(new EditSkillGump(m_From, m_Target, sk, m_Selected)); + } + else + { + m_From.SendMessage("You may not change that."); + m_From.SendGump(new SkillsGump(m_From, m_Target, m_Selected)); + } + } + else + { + m_From.SendGump(new SkillsGump(m_From, m_Target, m_Selected)); + } + } + + break; + } + case 2: + { + if (m_Selected != null && index >= 0 && index < m_Selected.Skills.Length) + { + Skill sk = m_Target.Skills[m_Selected.Skills[index]]; + + if (sk != null) + { + if (m_From.AccessLevel >= AccessLevel.GameMaster) + switch (sk.Lock) + { + case SkillLock.Up: + sk.SetLockNoRelay(SkillLock.Down); + sk.Update(); + break; + case SkillLock.Down: + sk.SetLockNoRelay(SkillLock.Locked); + sk.Update(); + break; + case SkillLock.Locked: + sk.SetLockNoRelay(SkillLock.Up); + sk.Update(); + break; + } + else + m_From.SendMessage("You may not change that."); + + m_From.SendGump(new SkillsGump(m_From, m_Target, m_Selected)); + } + } + + break; + } + } + } + + public int GetButtonID(int type, int index) + { + return 1 + index * 3 + type; + } + } + + public class SkillsGumpGroup + { + public SkillsGumpGroup(string name, SkillName[] skills) + { + Name = name; + Skills = skills; + + Array.Sort(Skills, new SkillNameComparer()); + } + + public string Name{ get; } + + public SkillName[] Skills{ get; } + + public static SkillsGumpGroup[] Groups{ get; } = + { + new SkillsGumpGroup("Crafting", new[] + { + SkillName.Alchemy, + SkillName.Blacksmith, + SkillName.Cartography, + SkillName.Carpentry, + SkillName.Cooking, + SkillName.Fletching, + SkillName.Inscribe, + SkillName.Tailoring, + SkillName.Tinkering, + SkillName.Imbuing + }), + new SkillsGumpGroup("Bardic", new[] + { + SkillName.Discordance, + SkillName.Musicianship, + SkillName.Peacemaking, + SkillName.Provocation + }), + new SkillsGumpGroup("Magical", new[] + { + SkillName.Chivalry, + SkillName.EvalInt, + SkillName.Magery, + SkillName.MagicResist, + SkillName.Meditation, + SkillName.Necromancy, + SkillName.SpiritSpeak, + SkillName.Ninjitsu, + SkillName.Bushido, + SkillName.Spellweaving, + SkillName.Mysticism + }), + new SkillsGumpGroup("Miscellaneous", new[] + { + SkillName.Camping, + SkillName.Fishing, + SkillName.Focus, + SkillName.Healing, + SkillName.Herding, + SkillName.Lockpicking, + SkillName.Lumberjacking, + SkillName.Mining, + SkillName.Snooping, + SkillName.Veterinary + }), + new SkillsGumpGroup("Combat Ratings", new[] + { + SkillName.Archery, + SkillName.Fencing, + SkillName.Macing, + SkillName.Parry, + SkillName.Swords, + SkillName.Tactics, + SkillName.Wrestling, + SkillName.Throwing + }), + new SkillsGumpGroup("Actions", new[] + { + SkillName.AnimalTaming, + SkillName.Begging, + SkillName.DetectHidden, + SkillName.Hiding, + SkillName.RemoveTrap, + SkillName.Poisoning, + SkillName.Stealing, + SkillName.Stealth, + SkillName.Tracking + }), + new SkillsGumpGroup("Lore & Knowledge", new[] + { + SkillName.Anatomy, + SkillName.AnimalLore, + SkillName.ArmsLore, + SkillName.Forensics, + SkillName.ItemID, + SkillName.TasteID + }) + }; + + private class SkillNameComparer : IComparer + { + public int Compare(object x, object y) + { + SkillName a = (SkillName)x; + SkillName b = (SkillName)y; + + string aName = SkillInfo.Table[(int)a].Name; + string bName = SkillInfo.Table[(int)b].Name; + + return aName.CompareTo(bName); + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/TithingGump.cs b/Scripts/Gumps/TithingGump.cs index 3332f7d13..5ae978886 100644 --- a/Scripts/Gumps/TithingGump.cs +++ b/Scripts/Gumps/TithingGump.cs @@ -3,121 +3,130 @@ using Server.Network; namespace Server.Gumps { - public class TithingGump : Gump - { - private Mobile m_From; - private int m_Offer; + public class TithingGump : Gump + { + private Mobile m_From; + private int m_Offer; - public TithingGump( Mobile from, int offer ) : base( 160, 40 ) - { - int totalGold = from.TotalGold; + public TithingGump(Mobile from, int offer) : base(160, 40) + { + int totalGold = from.TotalGold; - if ( offer > totalGold ) - offer = totalGold; - else if ( offer < 0 ) - offer = 0; + if (offer > totalGold) + offer = totalGold; + else if (offer < 0) + offer = 0; - m_From = from; - m_Offer = offer; + m_From = from; + m_Offer = offer; - AddPage( 0 ); + AddPage(0); - AddImage( 30, 30, 102 ); + AddImage(30, 30, 102); - AddHtmlLocalized( 95, 100, 120, 100, 1060198, 0, false, false ); // May your wealth bring blessings to those in need, if tithed upon this most sacred site. + AddHtmlLocalized(95, 100, 120, 100, 1060198, 0, false, + false); // May your wealth bring blessings to those in need, if tithed upon this most sacred site. - AddLabel( 57, 274, 0, "Gold:" ); - AddLabel( 87, 274, 53, (totalGold - offer).ToString() ); + AddLabel(57, 274, 0, "Gold:"); + AddLabel(87, 274, 53, (totalGold - offer).ToString()); - AddLabel( 137, 274, 0, "Tithe:" ); - AddLabel( 172, 274, 53, offer.ToString() ); + AddLabel(137, 274, 0, "Tithe:"); + AddLabel(172, 274, 53, offer.ToString()); - AddButton( 105, 230, 5220, 5220, 2, GumpButtonType.Reply, 0 ); - AddButton( 113, 230, 5222, 5222, 2, GumpButtonType.Reply, 0 ); - AddLabel( 108, 228, 0, "<" ); - AddLabel( 112, 228, 0, "<" ); + AddButton(105, 230, 5220, 5220, 2, GumpButtonType.Reply, 0); + AddButton(113, 230, 5222, 5222, 2, GumpButtonType.Reply, 0); + AddLabel(108, 228, 0, "<"); + AddLabel(112, 228, 0, "<"); - AddButton( 127, 230, 5223, 5223, 1, GumpButtonType.Reply, 0 ); - AddLabel( 131, 228, 0, "<" ); + AddButton(127, 230, 5223, 5223, 1, GumpButtonType.Reply, 0); + AddLabel(131, 228, 0, "<"); - AddButton( 147, 230, 5224, 5224, 3, GumpButtonType.Reply, 0 ); - AddLabel( 153, 228, 0, ">" ); + AddButton(147, 230, 5224, 5224, 3, GumpButtonType.Reply, 0); + AddLabel(153, 228, 0, ">"); - AddButton( 168, 230, 5220, 5220, 4, GumpButtonType.Reply, 0 ); - AddButton( 176, 230, 5222, 5222, 4, GumpButtonType.Reply, 0 ); - AddLabel( 172, 228, 0, ">" ); - AddLabel( 176, 228, 0, ">" ); + AddButton(168, 230, 5220, 5220, 4, GumpButtonType.Reply, 0); + AddButton(176, 230, 5222, 5222, 4, GumpButtonType.Reply, 0); + AddLabel(172, 228, 0, ">"); + AddLabel(176, 228, 0, ">"); - AddButton( 217, 272, 4023, 4024, 5, GumpButtonType.Reply, 0 ); - } + AddButton(217, 272, 4023, 4024, 5, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 0: - { - // You have decided to tithe no gold to the shrine. - m_From.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1060193 ); - break; - } - case 1: - case 2: - case 3: - case 4: - { - int offer = 0; + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 0: + { + // You have decided to tithe no gold to the shrine. + m_From.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1060193); + break; + } + case 1: + case 2: + case 3: + case 4: + { + int offer = 0; - switch ( info.ButtonID ) - { - case 1: offer = m_Offer - 100; break; - case 2: offer = 0; break; - case 3: offer = m_Offer + 100; break; - case 4: offer = m_From.TotalGold; break; - } + switch (info.ButtonID) + { + case 1: + offer = m_Offer - 100; + break; + case 2: + offer = 0; + break; + case 3: + offer = m_Offer + 100; + break; + case 4: + offer = m_From.TotalGold; + break; + } - m_From.SendGump( new TithingGump( m_From, offer ) ); - break; - } - case 5: - { - int totalGold = m_From.TotalGold; + m_From.SendGump(new TithingGump(m_From, offer)); + break; + } + case 5: + { + int totalGold = m_From.TotalGold; - if ( m_Offer > totalGold ) - m_Offer = totalGold; - else if ( m_Offer < 0 ) - m_Offer = 0; + if (m_Offer > totalGold) + m_Offer = totalGold; + else if (m_Offer < 0) + m_Offer = 0; - if ( (m_From.TithingPoints + m_Offer) > 100000 ) // TODO: What's the maximum? - m_Offer = (100000 - m_From.TithingPoints); + if (m_From.TithingPoints + m_Offer > 100000) // TODO: What's the maximum? + m_Offer = 100000 - m_From.TithingPoints; - if ( m_Offer <= 0 ) - { - // You have decided to tithe no gold to the shrine. - m_From.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1060193 ); - break; - } + if (m_Offer <= 0) + { + // You have decided to tithe no gold to the shrine. + m_From.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1060193); + break; + } - Container pack = m_From.Backpack; + Container pack = m_From.Backpack; - if ( pack != null && pack.ConsumeTotal( typeof( Gold ), m_Offer ) ) - { - // You tithe gold to the shrine as a sign of devotion. - m_From.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1060195 ); - m_From.TithingPoints += m_Offer; + if (pack != null && pack.ConsumeTotal(typeof(Gold), m_Offer)) + { + // You tithe gold to the shrine as a sign of devotion. + m_From.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1060195); + m_From.TithingPoints += m_Offer; - m_From.PlaySound( 0x243 ); - m_From.PlaySound( 0x2E6 ); - } - else - { - // You do not have enough gold to tithe that amount! - m_From.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1060194 ); - } + m_From.PlaySound(0x243); + m_From.PlaySound(0x2E6); + } + else + { + // You do not have enough gold to tithe that amount! + m_From.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1060194); + } - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/ToTAdminGump.cs b/Scripts/Gumps/ToTAdminGump.cs index a5150aa4e..7ffb8bd5d 100644 --- a/Scripts/Gumps/ToTAdminGump.cs +++ b/Scripts/Gumps/ToTAdminGump.cs @@ -1,134 +1,135 @@ using System; +using Server.Commands; using Server.Misc; using Server.Network; -using Server.Commands; namespace Server.Gumps { - public class ToTAdminGump : Gump - { - private int m_ToTEras; - private static string[] m_ToTInfo = - { - //Opening Message - "
Treasures of Tokuno Admin

" + - "-Use the gems to switch eras
" + - "-Drop era and Reward era can be changed seperately
" + - "-Drop era can be deactivated, Reward era is always activated", - //Treasures of Tokuno 1 message - "
Treasures of Tokuno 1

" + - "-10 charge Bleach Pigment can drop as a Lesser Artifact
" + - "-50 charge Neon Pigments available as a reward
", - //Treasures of Tokuno 2 message - "
Treasures of Tokuno 2

" + - "-30 types of 1 charge Metallic Pigments drop as Lesser Artifacts
" + - "-1 charge Bleach Pigment can drop as a Lesser Artifact
" + - "-10 charge Greater Metallic Pigments available as a reward", - //Treasures of Tokuno 3 message - "
Treasures of Tokuno 3

" + - "-10 types of 1 charge Fresh Pigments drop as Lesser Artifacts
" + - "-1 charge Bleach Pigment can drop as a Lesser Artifact
" + - "-Leurocian's Mempo Of Fortune can drop as a Lesser Artifact" - }; - - public ToTAdminGump() : base( 30, 50 ) - { - Closable=true; - Disposable=true; - Dragable=true; - Resizable=false; - - m_ToTEras = Enum.GetValues( typeof( TreasuresOfTokunoEra ) ).Length - 1; - - AddPage( 0 ); - AddBackground( 0, 0, 320, 75 + (m_ToTEras * 25), 9200 ); - AddImageTiled( 25, 18, 270, 10, 9267 ); - AddLabel( 75, 5, 54, "Treasures of Tokuno Admin" ); - AddLabel( 10, 25, 54, "ToT Era" ); - AddLabel( 90, 25, 54, "Drop Era" ); - AddLabel( 195, 25, 54, "Reward Era" ); - AddLabel( 287, 25, 54, "Info" ); - - AddBackground( 320, 0, 200, 150, 9200 ); - AddImageTiled( 325, 5, 190, 140, 2624 ); - AddAlphaRegion( 325, 5, 190, 140 ); - - SetupToTEras(); - } - - public void SetupToTEras() - { - bool isActivated = TreasuresOfTokuno.DropEra != TreasuresOfTokunoEra.None; - AddButton( 75, 50, isActivated ? 2361 : 2360, isActivated ? 2361 : 2360, 1, GumpButtonType.Reply, 0 ); - AddLabel( 90, 45, isActivated ? 167 : 137, isActivated ? "Activated" : "Deactivated" ); - - for ( int i = 0; i < m_ToTEras; i++ ) - { - int yoffset = (i * 25); - - bool isThisDropEra = ((int)TreasuresOfTokuno.DropEra - 1) == i; - bool isThisRewardEra = ((int)TreasuresOfTokuno.RewardEra - 1) == i; - int dropButtonID = isThisDropEra ? 2361 : 2360; - int rewardButtonID = isThisRewardEra ? 2361 : 2360; - - AddLabel( 10, 70 + yoffset, 2100, "ToT " + ( i + 1 ) ); - AddButton( 75, 75 + yoffset, dropButtonID, dropButtonID, 2 + ( i * 2 ), GumpButtonType.Reply, 0); - AddLabel( 90, 70 + yoffset, isThisDropEra ? 167 : 137, isThisDropEra ? "Active" : "Inactive" ); - AddButton( 180, 75 + yoffset, rewardButtonID, rewardButtonID, 2 + ( i * 2 ) + 1, GumpButtonType.Reply, 0); - AddLabel( 195, 70 + yoffset, isThisRewardEra ? 167 : 137, isThisRewardEra ? "Active" : "Inactive" ); - - AddButton( 285, 70 + yoffset, 4005, 4006, i, GumpButtonType.Page, 2 + i); - } - - for ( int i = 0; i < m_ToTInfo.Length; i++ ) - { - AddPage( 1 + i ); - AddHtml( 330, 10, 180, 130, m_ToTInfo[i], false, true ); - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int button = info.ButtonID; - Mobile from = sender.Mobile; + public class ToTAdminGump : Gump + { + private static string[] m_ToTInfo = + { + //Opening Message + "
Treasures of Tokuno Admin

" + + "-Use the gems to switch eras
" + + "-Drop era and Reward era can be changed seperately
" + + "-Drop era can be deactivated, Reward era is always activated", + //Treasures of Tokuno 1 message + "
Treasures of Tokuno 1

" + + "-10 charge Bleach Pigment can drop as a Lesser Artifact
" + + "-50 charge Neon Pigments available as a reward
", + //Treasures of Tokuno 2 message + "
Treasures of Tokuno 2

" + + "-30 types of 1 charge Metallic Pigments drop as Lesser Artifacts
" + + "-1 charge Bleach Pigment can drop as a Lesser Artifact
" + + "-10 charge Greater Metallic Pigments available as a reward", + //Treasures of Tokuno 3 message + "
Treasures of Tokuno 3

" + + "-10 types of 1 charge Fresh Pigments drop as Lesser Artifacts
" + + "-1 charge Bleach Pigment can drop as a Lesser Artifact
" + + "-Leurocian's Mempo Of Fortune can drop as a Lesser Artifact" + }; - if ( button == 1 ) - { - TreasuresOfTokuno.DropEra = TreasuresOfTokunoEra.None; - from.SendMessage( "Treasures of Tokuno Drops have been deactivated" ); - } - else if ( button >= 2 ) - { - int selectedToT; - if ( button % 2 == 0 ) - { - selectedToT = button / 2; - TreasuresOfTokuno.DropEra = (TreasuresOfTokunoEra)( selectedToT ); - from.SendMessage( "Treasures of Tokuno " + selectedToT + " Drops have been enabled" ); - } - else - { - selectedToT = (button - 1) / 2; - TreasuresOfTokuno.RewardEra = (TreasuresOfTokunoEra)( selectedToT ); - from.SendMessage( "Treasures of Tokuno " + selectedToT + " Rewards have been enabled" ); - } - } - } - - public static void Initialize() - { - CommandSystem.Register( "ToTAdmin", AccessLevel.Administrator, ToTAdmin_OnCommand ); - } + private int m_ToTEras; - [Usage( "ToTAdmin" )] - [Description( "Displays a menu to configure Treasures of Tokuno." )] - public static void ToTAdmin_OnCommand( CommandEventArgs e ) - { - ToTAdminGump tg; - - tg = new ToTAdminGump(); - e.Mobile.CloseGump( typeof( ToTAdminGump ) ); - e.Mobile.SendGump( tg ); - } - } -} + public ToTAdminGump() : base(30, 50) + { + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + m_ToTEras = Enum.GetValues(typeof(TreasuresOfTokunoEra)).Length - 1; + + AddPage(0); + AddBackground(0, 0, 320, 75 + m_ToTEras * 25, 9200); + AddImageTiled(25, 18, 270, 10, 9267); + AddLabel(75, 5, 54, "Treasures of Tokuno Admin"); + AddLabel(10, 25, 54, "ToT Era"); + AddLabel(90, 25, 54, "Drop Era"); + AddLabel(195, 25, 54, "Reward Era"); + AddLabel(287, 25, 54, "Info"); + + AddBackground(320, 0, 200, 150, 9200); + AddImageTiled(325, 5, 190, 140, 2624); + AddAlphaRegion(325, 5, 190, 140); + + SetupToTEras(); + } + + public void SetupToTEras() + { + bool isActivated = TreasuresOfTokuno.DropEra != TreasuresOfTokunoEra.None; + AddButton(75, 50, isActivated ? 2361 : 2360, isActivated ? 2361 : 2360, 1, GumpButtonType.Reply, 0); + AddLabel(90, 45, isActivated ? 167 : 137, isActivated ? "Activated" : "Deactivated"); + + for (int i = 0; i < m_ToTEras; i++) + { + int yoffset = i * 25; + + bool isThisDropEra = (int)TreasuresOfTokuno.DropEra - 1 == i; + bool isThisRewardEra = (int)TreasuresOfTokuno.RewardEra - 1 == i; + int dropButtonID = isThisDropEra ? 2361 : 2360; + int rewardButtonID = isThisRewardEra ? 2361 : 2360; + + AddLabel(10, 70 + yoffset, 2100, "ToT " + (i + 1)); + AddButton(75, 75 + yoffset, dropButtonID, dropButtonID, 2 + i * 2, GumpButtonType.Reply, 0); + AddLabel(90, 70 + yoffset, isThisDropEra ? 167 : 137, isThisDropEra ? "Active" : "Inactive"); + AddButton(180, 75 + yoffset, rewardButtonID, rewardButtonID, 2 + i * 2 + 1, GumpButtonType.Reply, 0); + AddLabel(195, 70 + yoffset, isThisRewardEra ? 167 : 137, isThisRewardEra ? "Active" : "Inactive"); + + AddButton(285, 70 + yoffset, 4005, 4006, i, GumpButtonType.Page, 2 + i); + } + + for (int i = 0; i < m_ToTInfo.Length; i++) + { + AddPage(1 + i); + AddHtml(330, 10, 180, 130, m_ToTInfo[i], false, true); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int button = info.ButtonID; + Mobile from = sender.Mobile; + + if (button == 1) + { + TreasuresOfTokuno.DropEra = TreasuresOfTokunoEra.None; + from.SendMessage("Treasures of Tokuno Drops have been deactivated"); + } + else if (button >= 2) + { + int selectedToT; + if (button % 2 == 0) + { + selectedToT = button / 2; + TreasuresOfTokuno.DropEra = (TreasuresOfTokunoEra)selectedToT; + from.SendMessage("Treasures of Tokuno " + selectedToT + " Drops have been enabled"); + } + else + { + selectedToT = (button - 1) / 2; + TreasuresOfTokuno.RewardEra = (TreasuresOfTokunoEra)selectedToT; + from.SendMessage("Treasures of Tokuno " + selectedToT + " Rewards have been enabled"); + } + } + } + + public static void Initialize() + { + CommandSystem.Register("ToTAdmin", AccessLevel.Administrator, ToTAdmin_OnCommand); + } + + [Usage("ToTAdmin")] + [Description("Displays a menu to configure Treasures of Tokuno.")] + public static void ToTAdmin_OnCommand(CommandEventArgs e) + { + ToTAdminGump tg; + + tg = new ToTAdminGump(); + e.Mobile.CloseGump(typeof(ToTAdminGump)); + e.Mobile.SendGump(tg); + } + } +} \ No newline at end of file diff --git a/Scripts/Gumps/VendorInventoryGump.cs b/Scripts/Gumps/VendorInventoryGump.cs index 2e99d947a..8d700600a 100644 --- a/Scripts/Gumps/VendorInventoryGump.cs +++ b/Scripts/Gumps/VendorInventoryGump.cs @@ -1,118 +1,124 @@ using System; using System.Collections; -using Server.Network; -using Server.Multis; using Server.Mobiles; +using Server.Multis; +using Server.Network; namespace Server.Gumps { - public class VendorInventoryGump : Gump - { - private BaseHouse m_House; - private ArrayList m_Inventories; + public class VendorInventoryGump : Gump + { + private BaseHouse m_House; + private ArrayList m_Inventories; - public VendorInventoryGump( BaseHouse house, Mobile from ) : base( 50, 50 ) - { - m_House = house; - m_Inventories = new ArrayList( house.VendorInventories ); + public VendorInventoryGump(BaseHouse house, Mobile from) : base(50, 50) + { + m_House = house; + m_Inventories = new ArrayList(house.VendorInventories); - AddBackground( 0, 0, 420, 50 + 20 * m_Inventories.Count, 0x13BE ); + AddBackground(0, 0, 420, 50 + 20 * m_Inventories.Count, 0x13BE); - AddImageTiled( 10, 10, 400, 20, 0xA40 ); - AddHtmlLocalized( 15, 10, 200, 20, 1062435, 0x7FFF, false, false ); // Reclaim Vendor Inventory - AddHtmlLocalized( 330, 10, 50, 20, 1062465, 0x7FFF, false, false ); // Expires + AddImageTiled(10, 10, 400, 20, 0xA40); + AddHtmlLocalized(15, 10, 200, 20, 1062435, 0x7FFF, false, false); // Reclaim Vendor Inventory + AddHtmlLocalized(330, 10, 50, 20, 1062465, 0x7FFF, false, false); // Expires - AddImageTiled( 10, 40, 400, 20 * m_Inventories.Count, 0xA40 ); + AddImageTiled(10, 40, 400, 20 * m_Inventories.Count, 0xA40); - for ( int i = 0; i < m_Inventories.Count; i++ ) - { - VendorInventory inventory = (VendorInventory) m_Inventories[i]; + for (int i = 0; i < m_Inventories.Count; i++) + { + VendorInventory inventory = (VendorInventory)m_Inventories[i]; - int y = 40 + 20 * i; + int y = 40 + 20 * i; - if ( inventory.Owner == from ) - AddButton( 10, y, 0xFA5, 0xFA7, i + 1, GumpButtonType.Reply, 0 ); + if (inventory.Owner == from) + AddButton(10, y, 0xFA5, 0xFA7, i + 1, GumpButtonType.Reply, 0); - AddLabel( 45, y, 0x481, $"{inventory.ShopName} ({inventory.VendorName})"); + AddLabel(45, y, 0x481, $"{inventory.ShopName} ({inventory.VendorName})"); - TimeSpan expire = inventory.ExpireTime - DateTime.UtcNow; - int hours = (int) expire.TotalHours; + TimeSpan expire = inventory.ExpireTime - DateTime.UtcNow; + int hours = (int)expire.TotalHours; - AddLabel( 320, y, 0x481, hours.ToString() ); - AddHtmlLocalized( 350, y, 50, 20, 1062466, 0x7FFF, false, false ); // hour(s) - } - } + AddLabel(320, y, 0x481, hours.ToString()); + AddHtmlLocalized(350, y, 50, 20, 1062466, 0x7FFF, false, false); // hour(s) + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0) + return; - Mobile from = sender.Mobile; - HouseSign sign = m_House.Sign; + Mobile from = sender.Mobile; + HouseSign sign = m_House.Sign; - if ( m_House.Deleted || sign == null || sign.Deleted || !from.CheckAlive() ) - return; + if (m_House.Deleted || sign == null || sign.Deleted || !from.CheckAlive()) + return; - if ( from.Map != sign.Map || !from.InRange( sign, 5 ) ) - { - from.SendLocalizedMessage( 1062429 ); // You must be within five paces of the house sign to use this option. - return; - } + if (from.Map != sign.Map || !from.InRange(sign, 5)) + { + from.SendLocalizedMessage(1062429); // You must be within five paces of the house sign to use this option. + return; + } - int index = info.ButtonID - 1; - if ( index < 0 || index >= m_Inventories.Count ) - return; + int index = info.ButtonID - 1; + if (index < 0 || index >= m_Inventories.Count) + return; - VendorInventory inventory = (VendorInventory) m_Inventories[index]; + VendorInventory inventory = (VendorInventory)m_Inventories[index]; - if ( inventory.Owner != from || !m_House.VendorInventories.Contains( inventory ) ) - return; + if (inventory.Owner != from || !m_House.VendorInventories.Contains(inventory)) + return; - int totalItems = 0; - int givenToBackpack = 0; - int givenToBankBox = 0; - for ( int i = inventory.Items.Count - 1; i >= 0; i-- ) - { - Item item = inventory.Items[i]; + int totalItems = 0; + int givenToBackpack = 0; + int givenToBankBox = 0; + for (int i = inventory.Items.Count - 1; i >= 0; i--) + { + Item item = inventory.Items[i]; - if ( item.Deleted ) - { - inventory.Items.RemoveAt( i ); - continue; - } + if (item.Deleted) + { + inventory.Items.RemoveAt(i); + continue; + } - totalItems += 1 + item.TotalItems; + totalItems += 1 + item.TotalItems; - if ( from.PlaceInBackpack( item ) ) - { - inventory.Items.RemoveAt( i ); - givenToBackpack += 1 + item.TotalItems; - } - else if ( from.BankBox.TryDropItem( from, item, false ) ) - { - inventory.Items.RemoveAt( i ); - givenToBankBox += 1 + item.TotalItems; - } - } + if (from.PlaceInBackpack(item)) + { + inventory.Items.RemoveAt(i); + givenToBackpack += 1 + item.TotalItems; + } + else if (from.BankBox.TryDropItem(from, item, false)) + { + inventory.Items.RemoveAt(i); + givenToBankBox += 1 + item.TotalItems; + } + } - from.SendLocalizedMessage( 1062436, totalItems.ToString() + "\t" + inventory.Gold.ToString() ); // The vendor you selected had ~1_COUNT~ items in its inventory, and ~2_AMOUNT~ gold in its account. + from.SendLocalizedMessage(1062436, + totalItems + "\t" + + inventory.Gold); // The vendor you selected had ~1_COUNT~ items in its inventory, and ~2_AMOUNT~ gold in its account. - int givenGold = Banker.DepositUpTo( from, inventory.Gold ); - inventory.Gold -= givenGold; + int givenGold = Banker.DepositUpTo(from, inventory.Gold); + inventory.Gold -= givenGold; - from.SendLocalizedMessage( 1060397, givenGold.ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. - from.SendLocalizedMessage( 1062437, givenToBackpack.ToString() + "\t" + givenToBankBox.ToString() ); // ~1_COUNT~ items have been removed from the shop inventory and placed in your backpack. ~2_BANKCOUNT~ items were removed from the shop inventory and placed in your bank box. + from.SendLocalizedMessage(1060397, + givenGold.ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + from.SendLocalizedMessage(1062437, + givenToBackpack + "\t" + + givenToBankBox); // ~1_COUNT~ items have been removed from the shop inventory and placed in your backpack. ~2_BANKCOUNT~ items were removed from the shop inventory and placed in your bank box. - if ( inventory.Gold > 0 || inventory.Items.Count > 0 ) - { - from.SendLocalizedMessage( 1062440 ); // Some of the shop inventory would not fit in your backpack or bank box. Please free up some room and try again. - } - else - { - inventory.Delete(); - from.SendLocalizedMessage( 1062438 ); // The shop is now empty of inventory and funds, so it has been deleted. - } - } - } + if (inventory.Gold > 0 || inventory.Items.Count > 0) + { + from.SendLocalizedMessage( + 1062440); // Some of the shop inventory would not fit in your backpack or bank box. Please free up some room and try again. + } + else + { + inventory.Delete(); + from.SendLocalizedMessage(1062438); // The shop is now empty of inventory and funds, so it has been deleted. + } + } + } } \ No newline at end of file diff --git a/Scripts/Gumps/ViewHousesGump.cs b/Scripts/Gumps/ViewHousesGump.cs index c7eef73f2..678343a6e 100644 --- a/Scripts/Gumps/ViewHousesGump.cs +++ b/Scripts/Gumps/ViewHousesGump.cs @@ -1,299 +1,291 @@ -using System; using System.Collections.Generic; -using Server.Items; -using Server.Multis; -using Server.Targeting; using Server.Accounting; using Server.Commands; +using Server.Items; +using Server.Multis; +using Server.Network; +using Server.Targeting; namespace Server.Gumps { - public class ViewHousesGump : Gump - { - public static void Initialize() - { - CommandSystem.Register( "ViewHouses", AccessLevel.GameMaster, ViewHouses_OnCommand ); - } + public class ViewHousesGump : Gump + { + private const int White16 = 0x7FFF; + private const int White = 0xFFFFFF; - [Usage( "ViewHouses" )] - [Description( "Displays a menu listing all houses of a targeted player. The menu also contains specific house details, and options to: go to house, open house menu, and demolish house." )] - public static void ViewHouses_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, ViewHouses_OnTarget ); - } - - public static void ViewHouses_OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile mobile ) - from.SendGump( new ViewHousesGump( from, GetHouses( mobile ), null ) ); - } - - private class HouseComparer : IComparer - { - public static readonly IComparer Instance = new HouseComparer(); - - public int Compare( BaseHouse x, BaseHouse y ) - { - return x.BuiltOn.CompareTo( y.BuiltOn ); - } - } + private Mobile m_From; + private List m_List; + private BaseHouse m_Selection; - public static List GetHouses( Mobile owner ) - { - List list = new List(); + public ViewHousesGump(Mobile from, List list, BaseHouse sel) : base(50, 40) + { + m_From = from; + m_List = list; + m_Selection = sel; - if ( !(owner.Account is Account acct) ) - { - list.AddRange( BaseHouse.GetHouses( owner ) ); - } - else - { - for ( int i = 0; i < acct.Length; ++i ) - { - Mobile mob = acct[i]; + from.CloseGump(typeof(ViewHousesGump)); - if ( mob != null ) - list.AddRange( BaseHouse.GetHouses( mob ) ); - } - } + AddPage(0); - list.Sort( HouseComparer.Instance ); + AddBackground(0, 0, 240, 360, 5054); + AddBlackAlpha(10, 10, 220, 340); - return list; - } + if (sel == null || sel.Deleted) + { + m_Selection = null; - private Mobile m_From; - private List m_List; - private BaseHouse m_Selection; + AddHtml(35, 15, 120, 20, Color("House Type", White), false, false); - public ViewHousesGump( Mobile from, List list, BaseHouse sel ) : base( 50, 40 ) - { - m_From = from; - m_List = list; - m_Selection = sel; + if (list.Count == 0) + AddHtml(35, 40, 160, 40, Color("There were no houses found for that player.", White), false, false); - from.CloseGump( typeof( ViewHousesGump ) ); + AddImage(190, 17, 0x25EA); + AddImage(207, 17, 0x25E6); - AddPage( 0 ); + int page = 0; - AddBackground( 0, 0, 240, 360, 5054 ); - AddBlackAlpha( 10, 10, 220, 340 ); + for (int i = 0; i < list.Count; ++i) + { + if (i % 15 == 0) + { + if (page > 0) + AddButton(207, 17, 0x15E1, 0x15E5, 0, GumpButtonType.Page, page + 1); - if ( sel == null || sel.Deleted ) - { - m_Selection = null; + AddPage(++page); - AddHtml( 35, 15, 120, 20, Color( "House Type", White ), false, false ); + if (page > 1) + AddButton(190, 17, 0x15E3, 0x15E7, 0, GumpButtonType.Page, page - 1); + } - if ( list.Count == 0 ) - AddHtml( 35, 40, 160, 40, Color( "There were no houses found for that player.", White ), false, false ); + object name = FindHouseName(list[i]); - AddImage( 190, 17, 0x25EA ); - AddImage( 207, 17, 0x25E6 ); + AddHtml(15, 40 + i % 15 * 20, 20, 20, Color($"{i + 1}.", White), false, false); - int page = 0; + if (name is int nameInt) + AddHtmlLocalized(35, 40 + i % 15 * 20, 160, 20, nameInt, White16, false, false); + else + AddHtml(35, 40 + i % 15 * 20, 160, 20, Color(name.ToString(), White), false, false); - for ( int i = 0; i < list.Count; ++i ) - { - if ( (i % 15) == 0 ) - { - if ( page > 0 ) - AddButton( 207, 17, 0x15E1, 0x15E5, 0, GumpButtonType.Page, page+1 ); - - AddPage( ++page ); - - if ( page > 1 ) - AddButton( 190, 17, 0x15E3, 0x15E7, 0, GumpButtonType.Page, page-1 ); - } - - object name = FindHouseName( list[i] ); - - AddHtml( 15, 40 + ((i % 15) * 20), 20, 20, Color($"{i + 1}.", White ), false, false ); + AddButton(198, 39 + i % 15 * 20, 4005, 4007, i + 1, GumpButtonType.Reply, 0); + } + } + else + { + string location; + Map map = sel.Map; - if ( name is int nameInt ) - AddHtmlLocalized( 35, 40 + ((i % 15) * 20), 160, 20, nameInt, White16, false, false ); - else - AddHtml( 35, 40 + ((i % 15) * 20), 160, 20, Color( name.ToString(), White ), false, false ); + string houseName = sel.Sign == null ? "An Unnamed House" : sel.Sign.GetName(); + string owner = sel.Owner == null ? "nobody" : sel.Owner.Name; - AddButton( 198, 39 + ((i % 15) * 20), 4005, 4007, i+1, GumpButtonType.Reply, 0 ); - } - } - else - { - string location; - Map map = sel.Map; + int xLong = 0, yLat = 0, xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; - var houseName = (sel.Sign == null) ? "An Unnamed House" : sel.Sign.GetName(); - var owner = (sel.Owner == null) ? "nobody" : sel.Owner.Name; + bool valid = Sextant.Format(sel.Location, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, + ref ySouth); - int xLong = 0, yLat = 0, xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; + if (valid) + location = $"{yLat}° {yMins}'{(ySouth ? "S" : "N")}, {xLong}° {xMins}'{(xEast ? "E" : "W")}"; + else + location = "unknown"; - bool valid = Sextant.Format( sel.Location, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ); + AddHtml(10, 15, 220, 20, Color(Center("House Properties"), White), false, false); - if ( valid ) - location = $"{yLat}° {yMins}'{(ySouth ? "S" : "N")}, {xLong}° {xMins}'{(xEast ? "E" : "W")}"; - else - location = "unknown"; + AddHtml(15, 40, 210, 20, Color("Facet:", White), false, false); + AddHtml(15, 40, 210, 20, Color(Right(map == null ? "(null)" : map.Name), White), false, false); - AddHtml( 10, 15, 220, 20, Color( Center( "House Properties" ), White ), false, false ); + AddHtml(15, 60, 210, 20, Color("Location:", White), false, false); + AddHtml(15, 60, 210, 20, Color(Right(sel.Location.ToString()), White), false, false); - AddHtml( 15, 40, 210, 20, Color( "Facet:", White ), false, false ); - AddHtml( 15, 40, 210, 20, Color( Right( map == null ? "(null)" : map.Name ), White ), false, false ); + AddHtml(15, 80, 210, 20, Color("Sextant:", White), false, false); + AddHtml(15, 80, 210, 20, Color(Right(location), White), false, false); - AddHtml( 15, 60, 210, 20, Color( "Location:", White ), false, false ); - AddHtml( 15, 60, 210, 20, Color( Right( sel.Location.ToString() ), White ), false, false ); + AddHtml(15, 100, 210, 20, Color("Owner:", White), false, false); + AddHtml(15, 100, 210, 20, Color(Right(owner), White), false, false); - AddHtml( 15, 80, 210, 20, Color( "Sextant:", White ), false, false ); - AddHtml( 15, 80, 210, 20, Color( Right( location ), White ), false, false ); + AddHtml(15, 120, 210, 20, Color("Name:", White), false, false); + AddHtml(15, 120, 210, 20, Color(Right(houseName), White), false, false); - AddHtml( 15, 100, 210, 20, Color( "Owner:", White ), false, false ); - AddHtml( 15, 100, 210, 20, Color( Right( owner ), White ), false, false ); + AddHtml(15, 140, 210, 20, Color("Friends:", White), false, false); + AddHtml(15, 140, 210, 20, Color(Right(sel.Friends.Count.ToString()), White), false, false); - AddHtml( 15, 120, 210, 20, Color( "Name:", White ), false, false ); - AddHtml( 15, 120, 210, 20, Color( Right( houseName ), White ), false, false ); + AddHtml(15, 160, 210, 20, Color("Co-Owners:", White), false, false); + AddHtml(15, 160, 210, 20, Color(Right(sel.CoOwners.Count.ToString()), White), false, false); - AddHtml( 15, 140, 210, 20, Color( "Friends:", White ), false, false ); - AddHtml( 15, 140, 210, 20, Color( Right( sel.Friends.Count.ToString() ), White ), false, false ); + AddHtml(15, 180, 210, 20, Color("Bans:", White), false, false); + AddHtml(15, 180, 210, 20, Color(Right(sel.Bans.Count.ToString()), White), false, false); - AddHtml( 15, 160, 210, 20, Color( "Co-Owners:", White ), false, false ); - AddHtml( 15, 160, 210, 20, Color( Right( sel.CoOwners.Count.ToString() ), White ), false, false ); + AddHtml(15, 200, 210, 20, Color("Decays:", White), false, false); + AddHtml(15, 200, 210, 20, Color(Right(sel.CanDecay ? "Yes" : "No"), White), false, false); - AddHtml( 15, 180, 210, 20, Color( "Bans:", White ), false, false ); - AddHtml( 15, 180, 210, 20, Color( Right( sel.Bans.Count.ToString() ), White ), false, false ); + AddHtml(15, 220, 210, 20, Color("Decay Level:", White), false, false); + AddHtml(15, 220, 210, 20, Color(Right(sel.DecayLevel.ToString()), White), false, false); - AddHtml( 15, 200, 210, 20, Color( "Decays:", White ), false, false ); - AddHtml( 15, 200, 210, 20, Color( Right( sel.CanDecay ? "Yes" : "No" ), White ), false, false ); + AddButton(15, 245, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtml(50, 245, 120, 20, Color("Go to house", White), false, false); - AddHtml( 15, 220, 210, 20, Color( "Decay Level:", White ), false, false ); - AddHtml( 15, 220, 210, 20, Color( Right( sel.DecayLevel.ToString() ), White ), false, false ); + AddButton(15, 265, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtml(50, 265, 120, 20, Color("Open house menu", White), false, false); - AddButton( 15, 245, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtml( 50, 245, 120, 20, Color( "Go to house", White ), false, false ); + AddButton(15, 285, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtml(50, 285, 120, 20, Color("Demolish house", White), false, false); + + AddButton(15, 305, 4005, 4007, 4, GumpButtonType.Reply, 0); + AddHtml(50, 305, 120, 20, Color("Refresh house", White), false, false); + } + } + + public static void Initialize() + { + CommandSystem.Register("ViewHouses", AccessLevel.GameMaster, ViewHouses_OnCommand); + } + + [Usage("ViewHouses")] + [Description( + "Displays a menu listing all houses of a targeted player. The menu also contains specific house details, and options to: go to house, open house menu, and demolish house.")] + public static void ViewHouses_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, ViewHouses_OnTarget); + } + + public static void ViewHouses_OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile mobile) + from.SendGump(new ViewHousesGump(from, GetHouses(mobile), null)); + } + + public static List GetHouses(Mobile owner) + { + List list = new List(); - AddButton( 15, 265, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtml( 50, 265, 120, 20, Color( "Open house menu", White ), false, false ); - - AddButton( 15, 285, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtml( 50, 285, 120, 20, Color( "Demolish house", White ), false, false ); - - AddButton( 15, 305, 4005, 4007, 4, GumpButtonType.Reply, 0 ); - AddHtml( 50, 305, 120, 20, Color( "Refresh house", White ), false, false ); - } - } - - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( m_Selection == null ) - { - int v = info.ButtonID - 1; - - if ( v >= 0 && v < m_List.Count ) - m_From.SendGump( new ViewHousesGump( m_From, m_List, m_List[v] ) ); - } - else if ( !m_Selection.Deleted ) - { - switch ( info.ButtonID ) - { - case 0: - { - m_From.SendGump( new ViewHousesGump( m_From, m_List, null ) ); - break; - } - case 1: - { - Map map = m_Selection.Map; - - if ( map != null && map != Map.Internal ) - m_From.MoveToWorld( m_Selection.BanLocation, map ); - - m_From.SendGump( new ViewHousesGump( m_From, m_List, m_Selection ) ); - - break; - } - case 2: - { - m_From.SendGump( new ViewHousesGump( m_From, m_List, m_Selection ) ); - - HouseSign sign = m_Selection.Sign; - - if ( sign != null && !sign.Deleted ) - sign.OnDoubleClick( m_From ); - - break; - } - case 3: - { - m_From.SendGump( new ViewHousesGump( m_From, m_List, m_Selection ) ); - m_From.SendGump( new HouseDemolishGump( m_From, m_Selection ) ); - - break; - } - case 4: - { - m_Selection.RefreshDecay(); - m_From.SendGump( new ViewHousesGump( m_From, m_List, m_Selection ) ); - - break; - } - } - } - } - - public object FindHouseName( BaseHouse house ) - { - int multiID = house.ItemID; - HousePlacementEntry[] entries; - - entries = HousePlacementEntry.ClassicHouses; - - for ( int i = 0; i < entries.Length; ++i ) - { - if ( entries[i].MultiID == multiID ) - return entries[i].Description; - } - - entries = HousePlacementEntry.TwoStoryFoundations; - - for ( int i = 0; i < entries.Length; ++i ) - { - if ( entries[i].MultiID == multiID ) - return entries[i].Description; - } - - entries = HousePlacementEntry.ThreeStoryFoundations; - - for ( int i = 0; i < entries.Length; ++i ) - { - if ( entries[i].MultiID == multiID ) - return entries[i].Description; - } - - return house.GetType().Name; - } - - private const int White16 = 0x7FFF; - private const int White = 0xFFFFFF; - - public string Right( string text ) - { - return $"
{text}
"; - } - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - public void AddBlackAlpha( int x, int y, int width, int height ) - { - AddImageTiled( x, y, width, height, 2624 ); - AddAlphaRegion( x, y, width, height ); - } - } -} + if (!(owner.Account is Account acct)) + list.AddRange(BaseHouse.GetHouses(owner)); + else + for (int i = 0; i < acct.Length; ++i) + { + Mobile mob = acct[i]; + + if (mob != null) + list.AddRange(BaseHouse.GetHouses(mob)); + } + + list.Sort(HouseComparer.Instance); + + return list; + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Selection == null) + { + int v = info.ButtonID - 1; + + if (v >= 0 && v < m_List.Count) + m_From.SendGump(new ViewHousesGump(m_From, m_List, m_List[v])); + } + else if (!m_Selection.Deleted) + { + switch (info.ButtonID) + { + case 0: + { + m_From.SendGump(new ViewHousesGump(m_From, m_List, null)); + break; + } + case 1: + { + Map map = m_Selection.Map; + + if (map != null && map != Map.Internal) + m_From.MoveToWorld(m_Selection.BanLocation, map); + + m_From.SendGump(new ViewHousesGump(m_From, m_List, m_Selection)); + + break; + } + case 2: + { + m_From.SendGump(new ViewHousesGump(m_From, m_List, m_Selection)); + + HouseSign sign = m_Selection.Sign; + + if (sign != null && !sign.Deleted) + sign.OnDoubleClick(m_From); + + break; + } + case 3: + { + m_From.SendGump(new ViewHousesGump(m_From, m_List, m_Selection)); + m_From.SendGump(new HouseDemolishGump(m_From, m_Selection)); + + break; + } + case 4: + { + m_Selection.RefreshDecay(); + m_From.SendGump(new ViewHousesGump(m_From, m_List, m_Selection)); + + break; + } + } + } + } + + public object FindHouseName(BaseHouse house) + { + int multiID = house.ItemID; + HousePlacementEntry[] entries; + + entries = HousePlacementEntry.ClassicHouses; + + for (int i = 0; i < entries.Length; ++i) + if (entries[i].MultiID == multiID) + return entries[i].Description; + + entries = HousePlacementEntry.TwoStoryFoundations; + + for (int i = 0; i < entries.Length; ++i) + if (entries[i].MultiID == multiID) + return entries[i].Description; + + entries = HousePlacementEntry.ThreeStoryFoundations; + + for (int i = 0; i < entries.Length; ++i) + if (entries[i].MultiID == multiID) + return entries[i].Description; + + return house.GetType().Name; + } + + public string Right(string text) + { + return $"
{text}
"; + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + public void AddBlackAlpha(int x, int y, int width, int height) + { + AddImageTiled(x, y, width, height, 2624); + AddAlphaRegion(x, y, width, height); + } + + private class HouseComparer : IComparer + { + public static readonly IComparer Instance = new HouseComparer(); + + public int Compare(BaseHouse x, BaseHouse y) + { + return x.BuiltOn.CompareTo(y.BuiltOn); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Christmas/2010/Addons/FireFliesDeed.cs b/Scripts/Holiday Stuff/Christmas/2010/Addons/FireFliesDeed.cs index 862bacebd..7c3cdd94d 100644 --- a/Scripts/Holiday Stuff/Christmas/2010/Addons/FireFliesDeed.cs +++ b/Scripts/Holiday Stuff/Christmas/2010/Addons/FireFliesDeed.cs @@ -5,273 +5,289 @@ using Server.Targeting; namespace Server.Items { - public class Fireflies : Item, IAddon - { - public override int LabelNumber => 1150061; + public class Fireflies : Item, IAddon + { + [Constructible] + public Fireflies() + : this(0x1596) + { + } - public Item Deed - { - get - { - FirefliesDeed deed = new FirefliesDeed(); + [Constructible] + public Fireflies(int itemID) + : base(itemID) + { + LootType = LootType.Blessed; + Movable = false; + } - return deed; - } - } + public Fireflies(Serial serial) + : base(serial) + { + } - public bool FacingSouth - { - get - { - if ( ItemID == 0x2336 ) - return true; + public override int LabelNumber => 1150061; - return false; - } - } + public bool FacingSouth + { + get + { + if (ItemID == 0x2336) + return true; - [Constructible] - public Fireflies() - : this( 0x1596 ) - { - } + return false; + } + } - [Constructible] - public Fireflies( int itemID ) - : base( itemID ) - { - LootType = LootType.Blessed; - Movable = false; - } + public Item Deed + { + get + { + FirefliesDeed deed = new FirefliesDeed(); - public Fireflies( Serial serial ) - : base( serial ) - { - } + return deed; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( Location, 3 ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public bool CouldFit(IPoint3D p, Map map) + { + if (map == null || !map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( RewardDemolitionGump ) ); - from.SendGump( new RewardDemolitionGump( this, 1049783 ) ); // Do you wish to re-deed this decoration? - } - else - from.SendLocalizedMessage( 1049784 ); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + if (FacingSouth) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // north wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // west wall + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(Location, 3)) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - writer.WriteEncodedInt( 0 ); // version - } + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(RewardDemolitionGump)); + from.SendGump(new RewardDemolitionGump(this, 1049783)); // Do you wish to re-deed this decoration? + } + else + { + from.SendLocalizedMessage( + 1049784); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadEncodedInt(); - } + writer.WriteEncodedInt(0); // version + } - public bool CouldFit( IPoint3D p, Map map ) - { - if ( map == null || !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( FacingSouth ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // north wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // west wall - } - } + int version = reader.ReadEncodedInt(); + } + } - public class FirefliesDeed : Item - { - public override int LabelNumber => 1150061; + public class FirefliesDeed : Item + { + [Constructible] + public FirefliesDeed() + : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } - [Constructible] - public FirefliesDeed() - : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } + public FirefliesDeed(Serial serial) + : base(serial) + { + } - public FirefliesDeed( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1150061; - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( FacingGump ) ); + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(FacingGump)); - if ( !from.SendGump( new FacingGump( this, from ) ) ) - { - from.SendLocalizedMessage( 1150062 ); // You fail to re-deed the holiday fireflies. - } - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } + if (!from.SendGump(new FacingGump(this, from))) + from.SendLocalizedMessage(1150062); // You fail to re-deed the holiday fireflies. + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class FacingGump : Gump - { - private FirefliesDeed m_Deed; - private Mobile m_Placer; + private class FacingGump : Gump + { + private FirefliesDeed m_Deed; + private Mobile m_Placer; - private enum Buttons - { - Cancel, - South, - East - } + public FacingGump(FirefliesDeed deed, Mobile player) + : base(150, 50) + { + m_Deed = deed; + m_Placer = player; - public FacingGump( FirefliesDeed deed, Mobile player ) - : base( 150, 50 ) - { - m_Deed = deed; - m_Placer = player; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 300, 150, 0xA28); - AddBackground( 0, 0, 300, 150, 0xA28 ); + AddItem(90, 30, 0x2332); + AddItem(180, 30, 0x2336); - AddItem( 90, 30, 0x2332 ); - AddItem( 180, 30, 0x2336 ); + AddButton(50, 35, 0x868, 0x869, (int)Buttons.East, GumpButtonType.Reply, 0); + AddButton(145, 35, 0x868, 0x869, (int)Buttons.South, GumpButtonType.Reply, 0); + } - AddButton( 50, 35, 0x868, 0x869, ( int )Buttons.East, GumpButtonType.Reply, 0 ); - AddButton( 145, 35, 0x868, 0x869, ( int )Buttons.South, GumpButtonType.Reply, 0 ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + int m_ItemID; - public override void OnResponse( NetState sender, RelayInfo info ) - { - int m_ItemID; + switch (info.ButtonID) + { + case (int)Buttons.East: + m_ItemID = 0x2332; + break; + case (int)Buttons.South: + m_ItemID = 0x2336; + break; + default: return; + } - switch( (int)info.ButtonID ) - { - case ( int )Buttons.East: m_ItemID = 0x2332; break; - case ( int )Buttons.South: m_ItemID = 0x2336; break; - default: return; - } + m_Placer.Target = new InternalTarget(m_Deed, m_ItemID); + } - m_Placer.Target = new InternalTarget( m_Deed, m_ItemID ); + private enum Buttons + { + Cancel, + South, + East + } + } - } - } + private class InternalTarget : Target + { + private FirefliesDeed m_FirefliesDeed; + private int m_ItemID; - private class InternalTarget : Target - { - private FirefliesDeed m_FirefliesDeed; - private int m_ItemID; + public InternalTarget(FirefliesDeed m_Deed, int itemid) + : base(-1, true, TargetFlags.None) + { + m_FirefliesDeed = m_Deed; + m_ItemID = itemid; + } - public InternalTarget( FirefliesDeed m_Deed, int itemid ) - : base( -1, true, TargetFlags.None ) - { - m_FirefliesDeed = m_Deed; - m_ItemID = itemid; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_FirefliesDeed == null || m_FirefliesDeed.Deleted) + return; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_FirefliesDeed == null || m_FirefliesDeed.Deleted ) - return; + if (m_FirefliesDeed.IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( m_FirefliesDeed.IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (house != null && house.IsOwner(from)) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; - if ( house != null && house.IsOwner( from ) ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; + if (p == null || map == null || map == Map.Internal) + return; - if ( p == null || map == null || map == Map.Internal ) - return; + Point3D p3d = new Point3D(p); + ItemData id = TileData.ItemTable[m_ItemID & TileData.MaxItemValue]; - Point3D p3d = new Point3D( p ); - ItemData id = TileData.ItemTable[ m_ItemID & TileData.MaxItemValue ]; + if (map.CanFit(p3d, id.Height)) + { + house = BaseHouse.FindHouseAt(p3d, map, id.Height); - if ( map.CanFit( p3d, id.Height ) ) - { - house = BaseHouse.FindHouseAt( p3d, map, id.Height ); + if (house != null && house.IsOwner(from)) + { + bool north = BaseAddon.IsWall(p3d.X, p3d.Y - 1, p3d.Z, map); + bool west = BaseAddon.IsWall(p3d.X - 1, p3d.Y, p3d.Z, map); - if ( house != null && house.IsOwner( from ) ) - { - bool north = BaseAddon.IsWall( p3d.X, p3d.Y - 1, p3d.Z, map ); - bool west = BaseAddon.IsWall( p3d.X - 1, p3d.Y, p3d.Z, map ); + bool isclear = true; - bool isclear = true; + foreach (Item item in Map.Malas.GetItemsInRange(p3d, 0)) + if (item is Fireflies) + isclear = false; - foreach( Item item in Map.Malas.GetItemsInRange( p3d, 0 ) ) - { - if ( item is Fireflies ) - { - isclear = false; - } - } + if ((m_ItemID == 0x2336 && north || m_ItemID == 0x2332 && west) && isclear) + { + Fireflies flies = new Fireflies(m_ItemID); - if ( ( ( m_ItemID == 0x2336 && north ) || ( m_ItemID == 0x2332 && west ) ) && isclear ) - { - Fireflies flies = new Fireflies( m_ItemID ); + house.Addons.Add(flies); - house.Addons.Add( flies ); + flies.MoveToWorld(p3d, from.Map); - flies.MoveToWorld( p3d, from.Map ); + m_FirefliesDeed.Delete(); + } - m_FirefliesDeed.Delete(); - } - - else - from.SendLocalizedMessage( 1150065 ); // Holiday fireflies must be placed next to a wall. - } - else - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - else - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - } - } -} + else + { + from.SendLocalizedMessage(1150065); // Holiday fireflies must be placed next to a wall. + } + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } + else + { + from.SendLocalizedMessage(500269); // You cannot build that there. + } + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Christmas/2010/Items/AngelDecoration.cs b/Scripts/Holiday Stuff/Christmas/2010/Items/AngelDecoration.cs index c8f5c230b..2ad8499a9 100644 --- a/Scripts/Holiday Stuff/Christmas/2010/Items/AngelDecoration.cs +++ b/Scripts/Holiday Stuff/Christmas/2010/Items/AngelDecoration.cs @@ -1,33 +1,33 @@ namespace Server.Items.Holiday { - [TypeAlias( "Server.Items.AngelDecoration" )] - [Flippable( 0x46FA, 0x46FB )] - public class AngelDecoration : Item - { - public AngelDecoration() : base ( 0x46FA ) - { - LootType = LootType.Blessed; + [TypeAlias("Server.Items.AngelDecoration")] + [Flippable(0x46FA, 0x46FB)] + public class AngelDecoration : Item + { + public AngelDecoration() : base(0x46FA) + { + LootType = LootType.Blessed; - Weight = 30; - } + Weight = 30; + } - public AngelDecoration( Serial serial ) - : base( serial ) - { - } + public AngelDecoration(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Christmas/2010/Items/RockingHorse.cs b/Scripts/Holiday Stuff/Christmas/2010/Items/RockingHorse.cs index 20bd4bf07..2538d3d2d 100644 --- a/Scripts/Holiday Stuff/Christmas/2010/Items/RockingHorse.cs +++ b/Scripts/Holiday Stuff/Christmas/2010/Items/RockingHorse.cs @@ -1,33 +1,33 @@ namespace Server.Items.Holiday { - [TypeAlias( "Server.Items.RockingHorse" )] - [Flippable( 0x4214, 0x4215 )] - public class RockingHorse : Item - { - public RockingHorse() : base ( 0x4214 ) - { - LootType = LootType.Blessed; + [TypeAlias("Server.Items.RockingHorse")] + [Flippable(0x4214, 0x4215)] + public class RockingHorse : Item + { + public RockingHorse() : base(0x4214) + { + LootType = LootType.Blessed; - Weight = 30; - } + Weight = 30; + } - public RockingHorse( Serial serial ) - : base( serial ) - { - } + public RockingHorse(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Easter/2011/Items/DragonEasterEgg.cs b/Scripts/Holiday Stuff/Easter/2011/Items/DragonEasterEgg.cs index 6a59395ba..027906d6d 100644 --- a/Scripts/Holiday Stuff/Easter/2011/Items/DragonEasterEgg.cs +++ b/Scripts/Holiday Stuff/Easter/2011/Items/DragonEasterEgg.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class DragonEasterEgg : Item, IDyable - { - public override int LabelNumber => 1097278; + public class DragonEasterEgg : Item, IDyable + { + [Constructible] + public DragonEasterEgg() + : base(0x47E6) + { + } - [Constructible] - public DragonEasterEgg() - : base( 0x47E6 ) - { - } + public DragonEasterEgg(Serial serial) + : base(serial) + { + } - public DragonEasterEgg( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1097278; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted || !sender.AllowDyables) + return false; - writer.Write( ( int ) 0 ); - } + Hue = sender.DyedHue; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return true; + } - int version = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted || !sender.AllowDyables ) - return false; + writer.Write(0); + } - Hue = sender.DyedHue; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return true; - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2006/Engines/TrickOrTreat.cs b/Scripts/Holiday Stuff/Halloween/2006/Engines/TrickOrTreat.cs index 68d19334f..6c3e7ee87 100644 --- a/Scripts/Holiday Stuff/Halloween/2006/Engines/TrickOrTreat.cs +++ b/Scripts/Holiday Stuff/Halloween/2006/Engines/TrickOrTreat.cs @@ -1,363 +1,333 @@ using System; -using Server.Items; -using Server.Targeting; -using Server.Events.Halloween; -using Server.Mobiles; using System.Collections.Generic; +using Server.Events.Halloween; +using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.Engines.Events { - public class TrickOrTreat - { - public static TimeSpan OneSecond = TimeSpan.FromSeconds( 1 ); + public class TrickOrTreat + { + public static TimeSpan OneSecond = TimeSpan.FromSeconds(1); - public static void Initialize() - { - DateTime now = DateTime.UtcNow; + public static void Initialize() + { + DateTime now = DateTime.UtcNow; - if ( DateTime.UtcNow >= HolidaySettings.StartHalloween && DateTime.UtcNow <= HolidaySettings.FinishHalloween ) - { - EventSink.Speech += EventSink_Speech; - } - } + if (DateTime.UtcNow >= HolidaySettings.StartHalloween && DateTime.UtcNow <= HolidaySettings.FinishHalloween) + EventSink.Speech += EventSink_Speech; + } - private static void EventSink_Speech( SpeechEventArgs e ) - { + private static void EventSink_Speech(SpeechEventArgs e) + { + if (Insensitive.Contains(e.Speech, "trick or treat")) + { + e.Mobile.Target = new TrickOrTreatTarget(); - if ( Insensitive.Contains( e.Speech, "trick or treat" ) ) - { - e.Mobile.Target = new TrickOrTreatTarget(); + e.Mobile.SendLocalizedMessage(1076764); /* Pick someone to Trick or Treat. */ + } + } - e.Mobile.SendLocalizedMessage( 1076764 ); /* Pick someone to Trick or Treat. */ - } - } + public static void Bleeding(Mobile m_From) + { + if (CheckMobile(m_From)) + if (m_From.Location != Point3D.Zero) + { + int amount = Utility.RandomMinMax(3, 7); - private class TrickOrTreatTarget : Target - { - public TrickOrTreatTarget() - : base( 15, false, TargetFlags.None ) - { - } + for (int i = 0; i < amount; i++) + new Blood(Utility.RandomMinMax(0x122C, 0x122F)).MoveToWorld( + RandomPointOneAway(m_From.X, m_From.Y, m_From.Z, m_From.Map), m_From.Map); + } + } - protected override void OnTarget( Mobile from, object targ ) - { - if ( targ != null && CheckMobile( from ) ) - { - if ( !( targ is Mobile ) ) - { - from.SendLocalizedMessage( 1076781 ); /* There is little chance of getting candy from that! */ - return; - } - if ( !( targ is BaseVendor ) || ( ( BaseVendor )targ ).Deleted ) - { - from.SendLocalizedMessage( 1076765 ); /* That doesn't look friendly. */ - return; - } + public static void RemoveHueMod(Mobile target) + { + if (target != null && !target.Deleted) target.SolidHueOverride = -1; + } - DateTime now = DateTime.UtcNow; + public static void SolidHueMobile(Mobile target) + { + if (CheckMobile(target)) + { + target.SolidHueOverride = Utility.RandomMinMax(2501, 2644); - BaseVendor m_Begged = targ as BaseVendor; + Timer.DelayCall(TimeSpan.FromSeconds(10), RemoveHueMod, target); + } + } - if ( CheckMobile( m_Begged ) ) - { - if ( m_Begged.NextTrickOrTreat > now ) - { - from.SendLocalizedMessage( 1076767 ); /* That doesn't appear to have any more candy. */ - return; - } + public static void MakeTwin(Mobile m_From) + { + List m_Items = new List(); - m_Begged.NextTrickOrTreat = now + TimeSpan.FromMinutes( Utility.RandomMinMax( 5, 10 ) ); + if (CheckMobile(m_From)) + { + Mobile twin = new NaughtyTwin(m_From); - if ( from.Backpack != null && !from.Backpack.Deleted ) - { - if ( Utility.RandomDouble() > .10 ) - { - switch( Utility.Random( 3 ) ) - { - case 0: m_Begged.Say( 1076768 ); break; /* Oooooh, aren't you cute! */ - case 1: m_Begged.Say( 1076779 ); break; /* All right...This better not spoil your dinner! */ - case 2: m_Begged.Say( 1076778 ); break; /* Here you go! Enjoy! */ - default: break; - } + if (twin != null && !twin.Deleted) + { + foreach (Item item in m_From.Items) + if (item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank) + m_Items.Add(item); - if ( Utility.RandomDouble() <= .01 && from.Skills.Begging.Value >= 100 ) - { - from.AddToBackpack( HolidaySettings.RandomGMBeggerItem ); + if (m_Items.Count > 0) + { + for (int i = 0; i < m_Items.Count; i++) /* dupe exploits start out like this ... */ + twin.AddItem(Mobile.LiftItemDupe(m_Items[i], 1)); - from.SendLocalizedMessage( 1076777 ); /* You receive a special treat! */ - } - else - { - from.AddToBackpack( HolidaySettings.RandomTreat ); + foreach (Item item in twin.Items) /* ... and end like this */ + if (item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank) + item.Movable = false; + } - from.SendLocalizedMessage( 1076769 ); /* You receive some candy. */ - } - } - else - { - m_Begged.Say( 1076770 ); /* TRICK! */ + twin.Hue = m_From.Hue; + twin.BodyValue = m_From.BodyValue; + twin.Kills = m_From.Kills; - int m_Action = Utility.Random( 4 ); + Point3D point = RandomPointOneAway(m_From.X, m_From.Y, m_From.Z, m_From.Map); - if ( m_Action == 0 ) - { - Timer.DelayCall( OneSecond, OneSecond, 10, Bleeding, from ); - } - else if ( m_Action == 1 ) - { - Timer.DelayCall( TimeSpan.FromSeconds( 2 ), SolidHueMobile, from ); - } - else - { - Timer.DelayCall( TimeSpan.FromSeconds( 2 ), MakeTwin, from ); - } - } - } - } - } - } - } + twin.MoveToWorld(m_From.Map.CanSpawnMobile(point) ? point : m_From.Location, m_From.Map); - public static void Bleeding( Mobile m_From ) - { - if ( CheckMobile( m_From ) ) - { - if ( m_From.Location != Point3D.Zero ) - { - int amount = Utility.RandomMinMax( 3, 7 ); + Timer.DelayCall(TimeSpan.FromSeconds(5), DeleteTwin, twin); + } + } + } - for( int i = 0; i < amount; i++ ) - { - new Blood( Utility.RandomMinMax( 0x122C, 0x122F ) ).MoveToWorld( RandomPointOneAway( m_From.X, m_From.Y, m_From.Z, m_From.Map ), m_From.Map ); - } - } - } - } + public static void DeleteTwin(Mobile m_Twin) + { + if (CheckMobile(m_Twin)) m_Twin.Delete(); + } - public static void RemoveHueMod( Mobile target ) - { - if ( target != null && !target.Deleted ) - { - target.SolidHueOverride = -1; - } - } + public static Point3D RandomPointOneAway(int x, int y, int z, Map map) + { + Point3D loc = new Point3D(x + Utility.Random(-1, 3), y + Utility.Random(-1, 3), 0); - public static void SolidHueMobile( Mobile target ) - { - if ( CheckMobile( target ) ) - { - target.SolidHueOverride = Utility.RandomMinMax( 2501, 2644 ); + loc.Z = map.CanFit(loc, 0) ? map.GetAverageZ(loc.X, loc.Y) : z; - Timer.DelayCall( TimeSpan.FromSeconds( 10 ), RemoveHueMod, target ); - } - } + return loc; + } - public static void MakeTwin( Mobile m_From ) - { - List m_Items = new List(); + public static bool CheckMobile(Mobile mobile) + { + return mobile?.Map != null && !mobile.Deleted && mobile.Alive && mobile.Map != Map.Internal; + } - if ( CheckMobile( m_From ) ) - { - Mobile twin = new NaughtyTwin( m_From ); + private class TrickOrTreatTarget : Target + { + public TrickOrTreatTarget() + : base(15, false, TargetFlags.None) + { + } - if ( twin != null && !twin.Deleted ) - { - foreach( Item item in m_From.Items ) - { - if ( item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank ) - { - m_Items.Add( item ); - } - } + protected override void OnTarget(Mobile from, object targ) + { + if (targ != null && CheckMobile(from)) + { + if (!(targ is Mobile)) + { + from.SendLocalizedMessage(1076781); /* There is little chance of getting candy from that! */ + return; + } - if ( m_Items.Count > 0 ) - { - for( int i = 0; i < m_Items.Count; i++ ) /* dupe exploits start out like this ... */ - { - twin.AddItem( Mobile.LiftItemDupe( m_Items[ i ], 1 ) ); - } + if (!(targ is BaseVendor) || ((BaseVendor)targ).Deleted) + { + from.SendLocalizedMessage(1076765); /* That doesn't look friendly. */ + return; + } - foreach( Item item in twin.Items ) /* ... and end like this */ - { - if ( item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank ) - { - item.Movable = false; - } - } - } + DateTime now = DateTime.UtcNow; - twin.Hue = m_From.Hue; - twin.BodyValue = m_From.BodyValue; - twin.Kills = m_From.Kills; + BaseVendor m_Begged = targ as BaseVendor; - Point3D point = RandomPointOneAway( m_From.X, m_From.Y, m_From.Z, m_From.Map ); + if (CheckMobile(m_Begged)) + { + if (m_Begged.NextTrickOrTreat > now) + { + from.SendLocalizedMessage(1076767); /* That doesn't appear to have any more candy. */ + return; + } - twin.MoveToWorld( m_From.Map.CanSpawnMobile( point ) ? point : m_From.Location, m_From.Map ); + m_Begged.NextTrickOrTreat = now + TimeSpan.FromMinutes(Utility.RandomMinMax(5, 10)); - Timer.DelayCall( TimeSpan.FromSeconds( 5 ), DeleteTwin, twin ); - } - } - } + if (from.Backpack != null && !from.Backpack.Deleted) + { + if (Utility.RandomDouble() > .10) + { + switch (Utility.Random(3)) + { + case 0: + m_Begged.Say(1076768); + break; /* Oooooh, aren't you cute! */ + case 1: + m_Begged.Say(1076779); + break; /* All right...This better not spoil your dinner! */ + case 2: + m_Begged.Say(1076778); + break; /* Here you go! Enjoy! */ + } - public static void DeleteTwin( Mobile m_Twin ) - { - if ( CheckMobile( m_Twin ) ) - { - m_Twin.Delete(); - } - } + if (Utility.RandomDouble() <= .01 && from.Skills.Begging.Value >= 100) + { + from.AddToBackpack(HolidaySettings.RandomGMBeggerItem); - public static Point3D RandomPointOneAway( int x, int y, int z, Map map ) - { - Point3D loc = new Point3D( x + Utility.Random( -1, 3 ), y + Utility.Random( -1, 3 ), 0 ); + from.SendLocalizedMessage(1076777); /* You receive a special treat! */ + } + else + { + from.AddToBackpack(HolidaySettings.RandomTreat); - loc.Z = ( map.CanFit( loc, 0 )) ? map.GetAverageZ( loc.X, loc.Y ) : z; + from.SendLocalizedMessage(1076769); /* You receive some candy. */ + } + } + else + { + m_Begged.Say(1076770); /* TRICK! */ - return loc; - } + int m_Action = Utility.Random(4); - public static bool CheckMobile( Mobile mobile ) - { - return ( mobile?.Map != null && !mobile.Deleted && mobile.Alive && mobile.Map != Map.Internal ); - } - } + if (m_Action == 0) + Timer.DelayCall(OneSecond, OneSecond, 10, Bleeding, from); + else if (m_Action == 1) + Timer.DelayCall(TimeSpan.FromSeconds(2), SolidHueMobile, from); + else + Timer.DelayCall(TimeSpan.FromSeconds(2), MakeTwin, from); + } + } + } + } + } + } + } - public class NaughtyTwin : BaseCreature - { - private Mobile m_From; + public class NaughtyTwin : BaseCreature + { + private static Point3D[] Felucca_Locations = + { + new Point3D(4467, 1283, 5), // Moonglow + new Point3D(1336, 1997, 5), // Britain + new Point3D(1499, 3771, 5), // Jhelom + new Point3D(771, 752, 5), // Yew + new Point3D(2701, 692, 5), // Minoc + new Point3D(1828, 2948, -20), // Trinsic + new Point3D(643, 2067, 5), // Skara Brae + new Point3D(3563, 2139, Map.Trammel.GetAverageZ(3563, 2139)) // (New) Magincia + }; - private static Point3D[] Felucca_Locations = - { - new Point3D( 4467, 1283, 5 ), // Moonglow - new Point3D( 1336, 1997, 5 ), // Britain - new Point3D( 1499, 3771, 5 ), // Jhelom - new Point3D( 771, 752, 5 ), // Yew - new Point3D( 2701, 692, 5 ), // Minoc - new Point3D( 1828, 2948,-20), // Trinsic - new Point3D( 643, 2067, 5 ), // Skara Brae - new Point3D( 3563, 2139, Map.Trammel.GetAverageZ( 3563, 2139 ) ), // (New) Magincia - }; + private static Point3D[] Malas_Locations = + { + new Point3D(1015, 527, -65), // Luna + new Point3D(1997, 1386, -85) // Umbra + }; - private static Point3D[] Malas_Locations = - { - new Point3D(1015, 527, -65), // Luna - new Point3D(1997, 1386, -85) // Umbra - }; + private static Point3D[] Ilshenar_Locations = + { + new Point3D(1215, 467, -13), // Compassion + new Point3D(722, 1366, -60), // Honesty + new Point3D(744, 724, -28), // Honor + new Point3D(281, 1016, 0), // Humility + new Point3D(987, 1011, -32), // Justice + new Point3D(1174, 1286, -30), // Sacrifice + new Point3D(1532, 1340, -3), // Spirituality + new Point3D(528, 216, -45), // Valor + new Point3D(1721, 218, 96) // Chaos + }; - private static Point3D[] Ilshenar_Locations = - { - new Point3D( 1215, 467, -13 ), // Compassion - new Point3D( 722, 1366, -60 ), // Honesty - new Point3D( 744, 724, -28 ), // Honor - new Point3D( 281, 1016, 0 ), // Humility - new Point3D( 987, 1011, -32 ), // Justice - new Point3D( 1174, 1286, -30 ), // Sacrifice - new Point3D( 1532, 1340, - 3 ), // Spirituality - new Point3D( 528, 216, -45 ), // Valor - new Point3D( 1721, 218, 96 ) // Chaos - }; + private static Point3D[] Tokuno_Locations = + { + new Point3D(1169, 998, 41), // Isamu-Jima + new Point3D(802, 1204, 25), // Makoto-Jima + new Point3D(270, 628, 15) // Homare-Jima + }; - private static Point3D[] Tokuno_Locations = - { - new Point3D( 1169, 998, 41 ), // Isamu-Jima - new Point3D( 802, 1204, 25 ), // Makoto-Jima - new Point3D( 270, 628, 15 ) // Homare-Jima - }; + private Mobile m_From; - public NaughtyTwin( Mobile from ) - : base( AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4 ) - { - if ( TrickOrTreat.CheckMobile( from ) ) - { - Body = from.Body; + public NaughtyTwin(Mobile from) + : base(AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4) + { + if (TrickOrTreat.CheckMobile(from)) + { + Body = from.Body; - m_From = from; - Name = $"{from.Name}\'s Naughty Twin"; + m_From = from; + Name = $"{from.Name}\'s Naughty Twin"; - Timer.DelayCall( TrickOrTreat.OneSecond, Utility.RandomBool() ? StealCandy : new TimerStateCallback( ToGate ), m_From ); - } - } + Timer.DelayCall(TrickOrTreat.OneSecond, + Utility.RandomBool() ? StealCandy : new TimerStateCallback(ToGate), m_From); + } + } - public override void OnThink() - { - if ( m_From == null || m_From.Deleted ) - { - Delete(); - } - } + public NaughtyTwin(Serial serial) + : base(serial) + { + } - public static Item FindCandyTypes( Mobile target ) - { - Type[] types = { typeof( WrappedCandy ), typeof( Lollipops ), typeof( NougatSwirl ), typeof( Taffy ), typeof( JellyBeans ) }; + public override void OnThink() + { + if (m_From == null || m_From.Deleted) Delete(); + } - if ( TrickOrTreat.CheckMobile( target ) ) - { - for( int i = 0; i < types.Length; i++ ) - { - Item item = target.Backpack.FindItemByType( types[ i ] ); + public static Item FindCandyTypes(Mobile target) + { + Type[] types = + { typeof(WrappedCandy), typeof(Lollipops), typeof(NougatSwirl), typeof(Taffy), typeof(JellyBeans) }; - if ( item != null ) - { - return item; - } - } - } - return null; - } + if (TrickOrTreat.CheckMobile(target)) + for (int i = 0; i < types.Length; i++) + { + Item item = target.Backpack.FindItemByType(types[i]); - public static void StealCandy( Mobile target ) - { - if ( TrickOrTreat.CheckMobile( target ) ) - { - Item item = FindCandyTypes( target ); + if (item != null) return item; + } - target.SendLocalizedMessage( 1113967 ); /* Your naughty twin steals some of your candy. */ + return null; + } - if ( item != null && !item.Deleted ) - { - item.Delete(); - } - } - } + public static void StealCandy(Mobile target) + { + if (TrickOrTreat.CheckMobile(target)) + { + Item item = FindCandyTypes(target); - public static void ToGate( Mobile target ) - { - if ( TrickOrTreat.CheckMobile( target ) ) - { - target.SendLocalizedMessage( 1113972 ); /* Your naughty twin teleports you away with a naughty laugh! */ + target.SendLocalizedMessage(1113967); /* Your naughty twin steals some of your candy. */ - target.MoveToWorld( RandomMoongate( target ), target.Map ); - } - } + if (item != null && !item.Deleted) item.Delete(); + } + } - public static Point3D RandomMoongate( Mobile target ) - { - Map map = target.Map; + public static void ToGate(Mobile target) + { + if (TrickOrTreat.CheckMobile(target)) + { + target.SendLocalizedMessage(1113972); /* Your naughty twin teleports you away with a naughty laugh! */ - switch( target.Map.MapID ) - { - case 2: return Ilshenar_Locations[ Utility.Random( Ilshenar_Locations.Length ) ]; - case 3: return Malas_Locations[ Utility.Random( Malas_Locations.Length ) ]; - case 4: return Tokuno_Locations[ Utility.Random( Tokuno_Locations.Length ) ]; - default: return Felucca_Locations[ Utility.Random( Felucca_Locations.Length ) ]; - } - } + target.MoveToWorld(RandomMoongate(target), target.Map); + } + } - public NaughtyTwin( Serial serial ) - : base( serial ) - { - } + public static Point3D RandomMoongate(Mobile target) + { + Map map = target.Map; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( ( int )0 ); - } + switch (target.Map.MapID) + { + case 2: return Ilshenar_Locations[Utility.Random(Ilshenar_Locations.Length)]; + case 3: return Malas_Locations[Utility.Random(Malas_Locations.Length)]; + case 4: return Tokuno_Locations[Utility.Random(Tokuno_Locations.Length)]; + default: return Felucca_Locations[Utility.Random(Felucca_Locations.Length)]; + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2006/Items/HalloweenPumpkin.cs b/Scripts/Holiday Stuff/Halloween/2006/Items/HalloweenPumpkin.cs index 6ce2d4377..aeb171895 100644 --- a/Scripts/Holiday Stuff/Halloween/2006/Items/HalloweenPumpkin.cs +++ b/Scripts/Holiday Stuff/Halloween/2006/Items/HalloweenPumpkin.cs @@ -1,85 +1,96 @@ -using System; -using Server.Mobiles; +using Server.Mobiles; namespace Server.Items { - public class HalloweenPumpkin : Item - { - private static readonly string[] m_Staff = - { - "Ryan", "Mark", "Eos", "Athena", "Xavier", "Krrios", "Zippy" - }; + public class HalloweenPumpkin : Item + { + private static readonly string[] m_Staff = + { + "Ryan", "Mark", "Eos", "Athena", "Xavier", "Krrios", "Zippy" + }; - [Constructible] - public HalloweenPumpkin() - { - Weight = Utility.RandomMinMax( 3, 20 ); - ItemID = ( Utility.RandomDouble() <= .02 ) ? Utility.RandomList( 0x4694, 0x4698 ) : Utility.RandomList( 0xc6a, 0xc6b, 0xc6c ); - } + [Constructible] + public HalloweenPumpkin() + { + Weight = Utility.RandomMinMax(3, 20); + ItemID = Utility.RandomDouble() <= .02 + ? Utility.RandomList(0x4694, 0x4698) + : Utility.RandomList(0xc6a, 0xc6b, 0xc6c); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - return; + public HalloweenPumpkin(Serial serial) + : base(serial) + { + } - bool douse = false; + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + return; - switch ( ItemID ) - { - case 0x4694: ItemID = 0x4691; break; - case 0x4691: ItemID = 0x4694; douse = true; break; - case 0x4698: ItemID = 0x4695; break; - case 0x4695: ItemID = 0x4698; douse = true; break; - default: return; - } + bool douse = false; - from.SendLocalizedMessage( douse ? 1113988 : 1113987 ); // You extinguish/light the Jack-O-Lantern - Effects.PlaySound( GetWorldLocation(), Map, douse ? 0x3be : 0x47 ); - } + switch (ItemID) + { + case 0x4694: + ItemID = 0x4691; + break; + case 0x4691: + ItemID = 0x4694; + douse = true; + break; + case 0x4698: + ItemID = 0x4695; + break; + case 0x4695: + ItemID = 0x4698; + douse = true; + break; + default: return; + } - private void AssignRandomName() - { - Name = $"{m_Staff[Utility.Random(m_Staff.Length)]}'s Jack-O-Lantern"; - } + from.SendLocalizedMessage(douse ? 1113988 : 1113987); // You extinguish/light the Jack-O-Lantern + Effects.PlaySound(GetWorldLocation(), Map, douse ? 0x3be : 0x47); + } - public override bool OnDragLift( Mobile from ) - { - if ( Name == null && ( ItemID == 0x4694 || ItemID == 0x4691 || ItemID == 0x4698 || ItemID == 0x4695 ) ) - { - if ( Utility.RandomBool() ) - { - new PumpkinHead().MoveToWorld( GetWorldLocation(), Map ); + private void AssignRandomName() + { + Name = $"{m_Staff[Utility.Random(m_Staff.Length)]}'s Jack-O-Lantern"; + } - Delete(); - return false; - } + public override bool OnDragLift(Mobile from) + { + if (Name == null && (ItemID == 0x4694 || ItemID == 0x4691 || ItemID == 0x4698 || ItemID == 0x4695)) + { + if (Utility.RandomBool()) + { + new PumpkinHead().MoveToWorld(GetWorldLocation(), Map); - AssignRandomName(); - } + Delete(); + return false; + } - return true; - } + AssignRandomName(); + } - public HalloweenPumpkin( Serial serial ) - : base( serial ) - { - } + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && Name == null && ItemID == 0x4698 ) - AssignRandomName(); - } - } -} + if (version == 0 && Name == null && ItemID == 0x4698) + AssignRandomName(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2006/Items/PumpkinScarecrow.cs b/Scripts/Holiday Stuff/Halloween/2006/Items/PumpkinScarecrow.cs index 493cc9543..83aedb403 100644 --- a/Scripts/Holiday Stuff/Halloween/2006/Items/PumpkinScarecrow.cs +++ b/Scripts/Holiday Stuff/Halloween/2006/Items/PumpkinScarecrow.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class PumpkinScarecrow : Item - { - public override int LabelNumber => 1096947; + public class PumpkinScarecrow : Item + { + [Constructible] + public PumpkinScarecrow() + : base(Utility.RandomBool() ? 0x469B : 0x469C) + { + } - [Constructible] - public PumpkinScarecrow() - : base( Utility.RandomBool() ? 0x469B : 0x469C ) - { - } + public PumpkinScarecrow(Serial serial) + : base(serial) + { + } - public PumpkinScarecrow( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1096947; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2006/Items/RuinedTapestry.cs b/Scripts/Holiday Stuff/Halloween/2006/Items/RuinedTapestry.cs index ad635fad5..1e51337a8 100644 --- a/Scripts/Holiday Stuff/Halloween/2006/Items/RuinedTapestry.cs +++ b/Scripts/Holiday Stuff/Halloween/2006/Items/RuinedTapestry.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class RuinedTapestry : Item - { - public override string DefaultName => "Ruined Tapestry "; + public class RuinedTapestry : Item + { + [Constructible] + public RuinedTapestry() + : base(Utility.RandomBool() ? 0x4699 : 0x469A) + { + } - [Constructible] - public RuinedTapestry() - : base( Utility.RandomBool() ? 0x4699 : 0x469A ) - { - } + public RuinedTapestry(Serial serial) + : base(serial) + { + } - public RuinedTapestry( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "Ruined Tapestry "; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2006/Items/TwilightLantern.cs b/Scripts/Holiday Stuff/Halloween/2006/Items/TwilightLantern.cs index 856e01f5d..945230d3c 100644 --- a/Scripts/Holiday Stuff/Halloween/2006/Items/TwilightLantern.cs +++ b/Scripts/Holiday Stuff/Halloween/2006/Items/TwilightLantern.cs @@ -1,45 +1,44 @@ namespace Server.Items { + public class TwilightLantern : Lantern + { + [Constructible] + public TwilightLantern() + { + Hue = Utility.RandomBool() ? 244 : 997; + } - public class TwilightLantern : Lantern - { - public override string DefaultName => "Twilight Lantern"; + public TwilightLantern(Serial serial) + : base(serial) + { + } - [Constructible] - public TwilightLantern() - { - Hue = Utility.RandomBool() ? 244 : 997; - } + public override string DefaultName => "Twilight Lantern"; - public override bool AllowEquippedCast( Mobile from ) - { - return true; - } + public override bool AllowEquippedCast(Mobile from) + { + return true; + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1060482 ); // Spell Channeling - } + list.Add(1060482); // Spell Channeling + } - public TwilightLantern( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( ( int )0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Engines/PumpkinPatch.cs b/Scripts/Holiday Stuff/Halloween/2009/Engines/PumpkinPatch.cs index a648c7757..e281b1ecb 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Engines/PumpkinPatch.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Engines/PumpkinPatch.cs @@ -1,74 +1,68 @@ using System; -using Server.Items; using Server.Events.Halloween; +using Server.Items; namespace Server.Engines.Events { - public class PumpkinPatchSpawner - { - private static Timer m_Timer; + public class PumpkinPatchSpawner + { + private static Timer m_Timer; - private static Rectangle2D[] m_PumpkinFields = - { - new Rectangle2D( 4557, 1471, 20, 10 ), - new Rectangle2D( 796, 2152, 36, 24 ), - new Rectangle2D( 816, 2251, 16, 8 ), - new Rectangle2D( 816, 2261, 16, 8 ), - new Rectangle2D( 816, 2271, 16, 8 ), - new Rectangle2D( 816, 2281, 16, 8 ), - new Rectangle2D( 835, 2344, 16, 16 ), - new Rectangle2D( 816, 2344, 16, 24 ) - }; + private static Rectangle2D[] m_PumpkinFields = + { + new Rectangle2D(4557, 1471, 20, 10), + new Rectangle2D(796, 2152, 36, 24), + new Rectangle2D(816, 2251, 16, 8), + new Rectangle2D(816, 2261, 16, 8), + new Rectangle2D(816, 2271, 16, 8), + new Rectangle2D(816, 2281, 16, 8), + new Rectangle2D(835, 2344, 16, 16), + new Rectangle2D(816, 2344, 16, 24) + }; - public static void Initialize() - { - DateTime now = DateTime.UtcNow; + public static void Initialize() + { + DateTime now = DateTime.UtcNow; - if ( DateTime.UtcNow >= HolidaySettings.StartHalloween && DateTime.UtcNow <= HolidaySettings.FinishHalloween ) - { - m_Timer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromMinutes( .50 ), 0, PumpkinPatchSpawnerCallback); - } - } + if (DateTime.UtcNow >= HolidaySettings.StartHalloween && DateTime.UtcNow <= HolidaySettings.FinishHalloween) + m_Timer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromMinutes(.50), 0, PumpkinPatchSpawnerCallback); + } - protected static void PumpkinPatchSpawnerCallback() - { - AddPumpkin( Map.Felucca ); - AddPumpkin( Map.Trammel ); - } + protected static void PumpkinPatchSpawnerCallback() + { + AddPumpkin(Map.Felucca); + AddPumpkin(Map.Trammel); + } - private static void AddPumpkin( Map map ) - { - for( int i = 0; i < m_PumpkinFields.Length; i++ ) - { - Rectangle2D rect = m_PumpkinFields[ i ]; + private static void AddPumpkin(Map map) + { + for (int i = 0; i < m_PumpkinFields.Length; i++) + { + Rectangle2D rect = m_PumpkinFields[i]; - int spawncount = ( ( rect.Height * rect.Width ) / 20 ); - int pumpkins = 0; + int spawncount = rect.Height * rect.Width / 20; + int pumpkins = 0; - foreach( Item item in map.GetItemsInBounds( rect ) ) - { - if ( item is HalloweenPumpkin ) - { - pumpkins++; - } - } + foreach (Item item in map.GetItemsInBounds(rect)) + if (item is HalloweenPumpkin) + pumpkins++; - if ( spawncount > pumpkins ) - { - Item item = new HalloweenPumpkin(); + if (spawncount > pumpkins) + { + Item item = new HalloweenPumpkin(); - item.MoveToWorld( RandomPointIn( rect, map ), map ); - } - } - } + item.MoveToWorld(RandomPointIn(rect, map), map); + } + } + } - private static Point3D RandomPointIn( Rectangle2D rect, Map map ) - { - int x = Utility.Random( rect.X, rect.Width ); - int y = Utility.Random( rect.Y, rect.Height ); - int z = map.GetAverageZ( x, y ); + private static Point3D RandomPointIn(Rectangle2D rect, Map map) + { + int x = Utility.Random(rect.X, rect.Width); + int y = Utility.Random(rect.Y, rect.Height); + int z = map.GetAverageZ(x, y); - return new Point3D( x, y, z ); - } - } -} + return new Point3D(x, y, z); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Foods/CreepyCake.cs b/Scripts/Holiday Stuff/Halloween/2009/Foods/CreepyCake.cs index d2ec2f7b5..3b10ec857 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Foods/CreepyCake.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Foods/CreepyCake.cs @@ -1,38 +1,38 @@ namespace Server.Items { - /* - first seen halloween 2009. subsequently in 2010, - 2011 and 2012. GM Beggar-only Semi-Rare Treats - */ + /* + first seen halloween 2009. subsequently in 2010, + 2011 and 2012. GM Beggar-only Semi-Rare Treats + */ - public class CreepyCake : Food - { - public override string DefaultName => "Creepy Cake"; + public class CreepyCake : Food + { + [Constructible] + public CreepyCake() + : base(0x9e9) + { + Hue = 0x3E4; + } - [Constructible] - public CreepyCake() - : base( 0x9e9 ) - { - Hue = 0x3E4; - } + public CreepyCake(Serial serial) + : base(serial) + { + } - public CreepyCake( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "Creepy Cake"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Foods/HarvestWine.cs b/Scripts/Holiday Stuff/Halloween/2009/Foods/HarvestWine.cs index d56b47a83..9f9830ddb 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Foods/HarvestWine.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Foods/HarvestWine.cs @@ -1,39 +1,39 @@ namespace Server.Items { - /* - first seen halloween 2009. subsequently in 2010, - 2011 and 2012. GM Beggar-only Semi-Rare Treats - */ + /* + first seen halloween 2009. subsequently in 2010, + 2011 and 2012. GM Beggar-only Semi-Rare Treats + */ - public class HarvestWine : BeverageBottle - { - public override string DefaultName => "Harvest Wine"; - public override double DefaultWeight => 1; + public class HarvestWine : BeverageBottle + { + [Constructible] + public HarvestWine() + : base(BeverageType.Wine) + { + Hue = 0xe0; + } - [Constructible] - public HarvestWine() - : base( BeverageType.Wine ) - { - Hue = 0xe0; - } + public HarvestWine(Serial serial) + : base(serial) + { + } - public HarvestWine( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "Harvest Wine"; + public override double DefaultWeight => 1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Foods/MrPlainsCookies.cs b/Scripts/Holiday Stuff/Halloween/2009/Foods/MrPlainsCookies.cs index a004104f2..615ee0f98 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Foods/MrPlainsCookies.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Foods/MrPlainsCookies.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class MrPlainsCookies : Food - { - public override string DefaultName => "Mr Plain's Cookies"; + public class MrPlainsCookies : Food + { + [Constructible] + public MrPlainsCookies() + : base(0x160C) + { + Weight = 1.0; + FillFactor = 4; + Hue = 0xF4; + } - [Constructible] - public MrPlainsCookies( ) - : base( 0x160C ) - { - Weight = 1.0; - FillFactor = 4; - Hue = 0xF4; - } + public MrPlainsCookies(Serial serial) + : base(serial) + { + } - public MrPlainsCookies( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "Mr Plain's Cookies"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Foods/MurkyMilk.cs b/Scripts/Holiday Stuff/Halloween/2009/Foods/MurkyMilk.cs index 5e8e70575..31670993d 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Foods/MurkyMilk.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Foods/MurkyMilk.cs @@ -1,42 +1,42 @@ namespace Server.Items { - /* - first seen halloween 2009. subsequently in 2010, - 2011 and 2012. GM Beggar-only Semi-Rare Treats - */ + /* + first seen halloween 2009. subsequently in 2010, + 2011 and 2012. GM Beggar-only Semi-Rare Treats + */ - public class MurkyMilk : Pitcher - { - public override string DefaultName => "Murky Milk"; - public override int MaxQuantity => 5; - public override double DefaultWeight => 1; + public class MurkyMilk : Pitcher + { + [Constructible] + public MurkyMilk() + : base(BeverageType.Milk) + { + Hue = 0x3e5; + Quantity = MaxQuantity; + ItemID = Utility.RandomBool() ? 0x09F0 : 0x09AD; + } - [Constructible] - public MurkyMilk( ) - : base( BeverageType.Milk ) - { - Hue = 0x3e5; - Quantity = MaxQuantity; - ItemID = ( Utility.RandomBool() ) ? 0x09F0 : 0x09AD; - } + public MurkyMilk(Serial serial) + : base(serial) + { + } - public MurkyMilk( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "Murky Milk"; + public override int MaxQuantity => 5; + public override double DefaultWeight => 1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Foods/PumpkinPizza.cs b/Scripts/Holiday Stuff/Halloween/2009/Foods/PumpkinPizza.cs index f97f1f46c..30f4b357d 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Foods/PumpkinPizza.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Foods/PumpkinPizza.cs @@ -1,37 +1,37 @@ namespace Server.Items { - /* - first seen halloween 2009. subsequently in 2010, - 2011 and 2012. GM Beggar-only Semi-Rare Treats - */ + /* + first seen halloween 2009. subsequently in 2010, + 2011 and 2012. GM Beggar-only Semi-Rare Treats + */ - public class PumpkinPizza : CheesePizza - { - public override string DefaultName => "Pumpkin Pizza"; + public class PumpkinPizza : CheesePizza + { + [Constructible] + public PumpkinPizza() + { + Hue = 0xF3; + } - [Constructible] - public PumpkinPizza( ) - { - Hue = 0xF3; - } + public PumpkinPizza(Serial serial) + : base(serial) + { + } - public PumpkinPizza( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "Pumpkin Pizza"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Items/GrimWarning.cs b/Scripts/Holiday Stuff/Halloween/2009/Items/GrimWarning.cs index 2ec057c43..246afc0a0 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Items/GrimWarning.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Items/GrimWarning.cs @@ -1,37 +1,37 @@ namespace Server.Items { - /* - first seen halloween 2009. subsequently in 2010, - 2011 and 2012. GM Beggar-only Semi-Rare Treats - */ + /* + first seen halloween 2009. subsequently in 2010, + 2011 and 2012. GM Beggar-only Semi-Rare Treats + */ - public class GrimWarning : Item - { - public override double DefaultWeight => 1; + public class GrimWarning : Item + { + [Constructible] + public GrimWarning() + : base(0x42BD) + { + } - [Constructible] - public GrimWarning () - : base( 0x42BD ) - { - } + public GrimWarning(Serial serial) + : base(serial) + { + } - public GrimWarning( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2009/Items/SkullsOnPike.cs b/Scripts/Holiday Stuff/Halloween/2009/Items/SkullsOnPike.cs index d34b0fa2a..dce85b870 100644 --- a/Scripts/Holiday Stuff/Halloween/2009/Items/SkullsOnPike.cs +++ b/Scripts/Holiday Stuff/Halloween/2009/Items/SkullsOnPike.cs @@ -1,37 +1,37 @@ namespace Server.Items { - /* - first seen halloween 2009. subsequently in 2010, - 2011 and 2012. GM Beggar-only Semi-Rare Treats - */ + /* + first seen halloween 2009. subsequently in 2010, + 2011 and 2012. GM Beggar-only Semi-Rare Treats + */ - public class SkullsOnPike : Item - { - public override double DefaultWeight => 1; + public class SkullsOnPike : Item + { + [Constructible] + public SkullsOnPike() + : base(0x42B5) + { + } - [Constructible] - public SkullsOnPike() - : base( 0x42B5 ) - { - } + public SkullsOnPike(Serial serial) + : base(serial) + { + } - public SkullsOnPike( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2010/Items/ChairInAGhostCostume.cs b/Scripts/Holiday Stuff/Halloween/2010/Items/ChairInAGhostCostume.cs index 1c402e3dc..1da684b90 100644 --- a/Scripts/Holiday Stuff/Halloween/2010/Items/ChairInAGhostCostume.cs +++ b/Scripts/Holiday Stuff/Halloween/2010/Items/ChairInAGhostCostume.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class ChairInAGhostCostume : Item - { - public override double DefaultWeight => 5; + public class ChairInAGhostCostume : Item + { + [Constructible] + public ChairInAGhostCostume() + : base(0x3F26) + { + } - [Constructible] - public ChairInAGhostCostume() - : base( 0x3F26 ) - { - } + public ChairInAGhostCostume(Serial serial) + : base(serial) + { + } - public ChairInAGhostCostume( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2010/Items/ColoredSmallWebs.cs b/Scripts/Holiday Stuff/Halloween/2010/Items/ColoredSmallWebs.cs index c607aa0e7..b6843ad89 100644 --- a/Scripts/Holiday Stuff/Halloween/2010/Items/ColoredSmallWebs.cs +++ b/Scripts/Holiday Stuff/Halloween/2010/Items/ColoredSmallWebs.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class ColoredSmallWebs : Item - { - public override double DefaultWeight => 5; + public class ColoredSmallWebs : Item + { + [Constructible] + public ColoredSmallWebs() + : base(Utility.RandomBool() ? 0x10d6 : 0x10d7) + { + Hue = Utility.RandomBool() ? 0x455 : 0x4E9; + } - [Constructible] - public ColoredSmallWebs() - : base( Utility.RandomBool() ? 0x10d6 : 0x10d7 ) - { - Hue = Utility.RandomBool() ? 0x455 : 0x4E9; - } + public ColoredSmallWebs(Serial serial) + : base(serial) + { + } - public ColoredSmallWebs( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2010/Items/ExcellentIronMaiden.cs b/Scripts/Holiday Stuff/Halloween/2010/Items/ExcellentIronMaiden.cs index 0796a5b71..56806963a 100644 --- a/Scripts/Holiday Stuff/Halloween/2010/Items/ExcellentIronMaiden.cs +++ b/Scripts/Holiday Stuff/Halloween/2010/Items/ExcellentIronMaiden.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class ExcellentIronMaiden : Item - { - public override double DefaultWeight => 5; + public class ExcellentIronMaiden : Item + { + [Constructible] + public ExcellentIronMaiden() + : base(0x3f15) + { + } - [Constructible] - public ExcellentIronMaiden() - : base( 0x3f15 ) - { - } + public ExcellentIronMaiden(Serial serial) + : base(serial) + { + } - public ExcellentIronMaiden( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2010/Items/HalloweenGuillotine.cs b/Scripts/Holiday Stuff/Halloween/2010/Items/HalloweenGuillotine.cs index b4b4c0d1c..c1861c748 100644 --- a/Scripts/Holiday Stuff/Halloween/2010/Items/HalloweenGuillotine.cs +++ b/Scripts/Holiday Stuff/Halloween/2010/Items/HalloweenGuillotine.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class HalloweenGuillotine : Item - { - public override double DefaultWeight => 5; + public class HalloweenGuillotine : Item + { + [Constructible] + public HalloweenGuillotine() : base(0x3F27) + { + } - [Constructible] - public HalloweenGuillotine() : base( 0x3F27 ) - { - } + public HalloweenGuillotine(Serial serial) + : base(serial) + { + } - public HalloweenGuillotine( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2011/Items/BasePaintedMask.cs b/Scripts/Holiday Stuff/Halloween/2011/Items/BasePaintedMask.cs index 9a4f98c65..bc0cc2622 100644 --- a/Scripts/Holiday Stuff/Halloween/2011/Items/BasePaintedMask.cs +++ b/Scripts/Holiday Stuff/Halloween/2011/Items/BasePaintedMask.cs @@ -1,76 +1,67 @@ -using System; -//using System.Collections.Generic; +//using System.Collections.Generic; namespace Server.Items.Holiday { - [TypeAlias( "Server.Items.ClownMask", "Server.Items.DaemonMask", "Server.Items.PlagueMask" )] - public class BasePaintedMask : Item - { - public override string DefaultName - { - get - { - if ( m_Staffer != null ) - { - return $"{MaskName} hand painted by {m_Staffer}"; - } + [TypeAlias("Server.Items.ClownMask", "Server.Items.DaemonMask", "Server.Items.PlagueMask")] + public class BasePaintedMask : Item + { + private static string[] m_Staffers = + { + "Ryan", + "Mark", + "Krrios", + "Zippy", + "Athena", + "Eos", + "Xavier" + }; - return MaskName; - } - } + private string m_Staffer; - public virtual string MaskName => "A Mask"; + public BasePaintedMask(int itemid) + : this(m_Staffers[Utility.Random(m_Staffers.Length)], itemid) + { + } - private string m_Staffer; + public BasePaintedMask(string staffer, int itemid) + : base(itemid + Utility.Random(2)) + { + m_Staffer = staffer; - private static string[] m_Staffers = - { - "Ryan", - "Mark", - "Krrios", - "Zippy", - "Athena", - "Eos", - "Xavier" - }; + Utility.Intern(m_Staffer); + } - public BasePaintedMask( int itemid ) - : this( m_Staffers[ Utility.Random( m_Staffers.Length ) ], itemid ) - { + public BasePaintedMask(Serial serial) : base(serial) + { + } - } + public override string DefaultName + { + get + { + if (m_Staffer != null) return $"{MaskName} hand painted by {m_Staffer}"; - public BasePaintedMask( string staffer, int itemid ) - : base( itemid + Utility.Random( 2 ) ) - { - m_Staffer = staffer; + return MaskName; + } + } - Utility.Intern( m_Staffer ); - } + public virtual string MaskName => "A Mask"; - public BasePaintedMask( Serial serial ) : base( serial ) - { + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - } + writer.Write(1); // version + writer.Write(m_Staffer); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( ( int )1 ); // version - writer.Write( ( string )m_Staffer ); - } + int version = reader.ReadInt(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 1 ) - { - m_Staffer = Utility.Intern( reader.ReadString() ); - } - } - } -} + if (version == 1) m_Staffer = Utility.Intern(reader.ReadString()); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2011/Items/ClownMask.cs b/Scripts/Holiday Stuff/Halloween/2011/Items/ClownMask.cs index 37e0a9a4d..2be536035 100644 --- a/Scripts/Holiday Stuff/Halloween/2011/Items/ClownMask.cs +++ b/Scripts/Holiday Stuff/Halloween/2011/Items/ClownMask.cs @@ -1,32 +1,32 @@ namespace Server.Items.Holiday { - public class PaintedEvilClownMask : BasePaintedMask - { - public override string MaskName => "Evil Clown Mask"; + public class PaintedEvilClownMask : BasePaintedMask + { + [Constructible] + public PaintedEvilClownMask() + : base(0x4a90) + { + } - [Constructible] - public PaintedEvilClownMask( ) - : base( 0x4a90 ) - { - } + public PaintedEvilClownMask(Serial serial) + : base(serial) + { + } - public PaintedEvilClownMask( Serial serial ) - : base( serial ) - { - } + public override string MaskName => "Evil Clown Mask"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2011/Items/DaemonMask.cs b/Scripts/Holiday Stuff/Halloween/2011/Items/DaemonMask.cs index 786c0f2e5..3cafb5fa5 100644 --- a/Scripts/Holiday Stuff/Halloween/2011/Items/DaemonMask.cs +++ b/Scripts/Holiday Stuff/Halloween/2011/Items/DaemonMask.cs @@ -1,33 +1,32 @@ namespace Server.Items.Holiday { - public class PaintedDaemonMask : BasePaintedMask - { - public override string MaskName => "Daemon Mask"; + public class PaintedDaemonMask : BasePaintedMask + { + [Constructible] + public PaintedDaemonMask() + : base(0x4a92) + { + } - [Constructible] - public PaintedDaemonMask() - : base( 0x4a92 ) - { - } + public PaintedDaemonMask(Serial serial) + : base(serial) + { + } - public PaintedDaemonMask( Serial serial ) - : base( serial ) - { - } + public override string MaskName => "Daemon Mask"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2011/Items/PlagueMask.cs b/Scripts/Holiday Stuff/Halloween/2011/Items/PlagueMask.cs index c9c38da30..3b3375027 100644 --- a/Scripts/Holiday Stuff/Halloween/2011/Items/PlagueMask.cs +++ b/Scripts/Holiday Stuff/Halloween/2011/Items/PlagueMask.cs @@ -1,32 +1,32 @@ namespace Server.Items.Holiday { - public class PaintedPlagueMask : BasePaintedMask - { - public override string MaskName => "Plague Mask"; + public class PaintedPlagueMask : BasePaintedMask + { + [Constructible] + public PaintedPlagueMask() + : base(0x4A8E) + { + } - [Constructible] - public PaintedPlagueMask() - : base( 0x4A8E ) - { - } + public PaintedPlagueMask(Serial serial) + : base(serial) + { + } - public PaintedPlagueMask( Serial serial ) - : base( serial ) - { - } + public override string MaskName => "Plague Mask"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2011/Mobiles/PumpkinHead.cs b/Scripts/Holiday Stuff/Halloween/2011/Mobiles/PumpkinHead.cs index 5d010ba7f..2d946172a 100644 --- a/Scripts/Holiday Stuff/Halloween/2011/Mobiles/PumpkinHead.cs +++ b/Scripts/Holiday Stuff/Halloween/2011/Mobiles/PumpkinHead.cs @@ -4,126 +4,127 @@ using Server.Items.Holiday; namespace Server.Mobiles { - public class PumpkinHead : BaseCreature - { - public override string CorpseName => "a killer pumpkin corpse"; - public override bool AutoDispel => true; - public override bool BardImmune => true; - public override bool Unprovokable => true; - public override bool AreaPeaceImmune => true; - public override string DefaultName => "a killer pumpkin"; + public class PumpkinHead : BaseCreature + { + [Constructible] + public PumpkinHead() + : base(Utility.RandomBool() ? AIType.AI_Melee : AIType.AI_Mage, FightMode.Closest, 10, 1, 0.05, 0.1) + { + Body = 1246 + Utility.Random(2); - [Constructible] - public PumpkinHead() - : base( Utility.RandomBool() ? AIType.AI_Melee : AIType.AI_Mage, FightMode.Closest, 10, 1, 0.05, 0.1 ) - { - Body = 1246 + Utility.Random( 2 ); + BaseSoundID = 268; - BaseSoundID = 268; + SetStr(350); + SetDex(125); + SetInt(250); - SetStr( 350 ); - SetDex( 125 ); - SetInt( 250 ); + SetHits(500); + SetMana(1000); - SetHits( 500 ); - SetMana( 1000 ); + SetDamage(10, 15); - SetDamage( 10, 15 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 55); + SetResistance(ResistanceType.Fire, 50); + SetResistance(ResistanceType.Cold, 50); + SetResistance(ResistanceType.Poison, 65); + SetResistance(ResistanceType.Energy, 80); - SetResistance( ResistanceType.Physical, 55 ); - SetResistance( ResistanceType.Fire, 50 ); - SetResistance( ResistanceType.Cold, 50 ); - SetResistance( ResistanceType.Poison, 65 ); - SetResistance( ResistanceType.Energy, 80 ); + SetSkill(SkillName.DetectHidden, 100.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.Necromancy, 100.0); + SetSkill(SkillName.SpiritSpeak, 120.0); + SetSkill(SkillName.Magery, 160.0); + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.MagicResist, 100.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 80.0); - SetSkill( SkillName.DetectHidden, 100.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.Necromancy, 100.0 ); - SetSkill( SkillName.SpiritSpeak, 120.0 ); - SetSkill( SkillName.Magery, 160.0 ); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.MagicResist, 100.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + VirtualArmor = 49; + } - VirtualArmor = 49; - } + public PumpkinHead(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - if ( Utility.RandomDouble() < .05 ) - { - //PackItem( new TwilightLantern() ); OLD Halloween + public override string CorpseName => "a killer pumpkin corpse"; + public override bool AutoDispel => true; + public override bool BardImmune => true; + public override bool Unprovokable => true; + public override bool AreaPeaceImmune => true; + public override string DefaultName => "a killer pumpkin"; - switch( Utility.Random( 5 ) ) - { - case 0: PackItem( new PaintedEvilClownMask() ); break; - case 1: PackItem( new PaintedDaemonMask() ); break; - case 2: PackItem( new PaintedPlagueMask() ); break; - case 3: PackItem( new PaintedEvilJesterMask() ); break; - case 4: PackItem( new PaintedPorcelainMask() ); break; - default: break; - } - } + public override void GenerateLoot() + { + if (Utility.RandomDouble() < .05) + switch (Utility.Random(5)) + { + case 0: + PackItem(new PaintedEvilClownMask()); + break; + case 1: + PackItem(new PaintedDaemonMask()); + break; + case 2: + PackItem(new PaintedPlagueMask()); + break; + case 3: + PackItem(new PaintedEvilJesterMask()); + break; + case 4: + PackItem(new PaintedPorcelainMask()); + break; + } - PackItem( new WrappedCandy() ); - AddLoot( LootPack.UltraRich, 2 ); - } + PackItem(new WrappedCandy()); + AddLoot(LootPack.UltraRich, 2); + } - public virtual void Lifted_Callback( Mobile from ) - { - if ( from != null && !from.Deleted && from is PlayerMobile ) - { - Combatant = from; + public virtual void Lifted_Callback(Mobile from) + { + if (from != null && !from.Deleted && from is PlayerMobile) + { + Combatant = from; - Warmode = true; - } - } + Warmode = true; + } + } - public override Item NewHarmfulItem() - { - Item bad = new AcidSlime( TimeSpan.FromSeconds( 10 ), 25, 30 ); + public override Item NewHarmfulItem() + { + Item bad = new AcidSlime(TimeSpan.FromSeconds(10), 25, 30); - bad.Name = "gooey nasty pumpkin hummus"; + bad.Name = "gooey nasty pumpkin hummus"; - bad.Hue = 144; + bad.Hue = 144; - return bad; - } + return bad; + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( Utility.RandomBool() ) - { - if ( from?.Map != null && Map != Map.Internal && Map == from.Map && from.InRange( this, 12 ) ) - { - SpillAcid( ( willKill ) ? this : from, ( willKill ) ? 3 : 1 ); - } - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (Utility.RandomBool()) + if (from?.Map != null && Map != Map.Internal && Map == from.Map && from.InRange(this, 12)) + SpillAcid(willKill ? this : from, willKill ? 3 : 1); - base.OnDamage( amount, from, willKill ); - } + base.OnDamage(amount, from, willKill); + } - public PumpkinHead( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( ( int )0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2012/Items/EvilJesterMask.cs b/Scripts/Holiday Stuff/Halloween/2012/Items/EvilJesterMask.cs index 96e0f8be7..b30eea959 100644 --- a/Scripts/Holiday Stuff/Halloween/2012/Items/EvilJesterMask.cs +++ b/Scripts/Holiday Stuff/Halloween/2012/Items/EvilJesterMask.cs @@ -1,32 +1,32 @@ namespace Server.Items.Holiday { - public class PaintedEvilJesterMask : BasePaintedMask - { - public override string MaskName => "Evil Jester Mask"; + public class PaintedEvilJesterMask : BasePaintedMask + { + [Constructible] + public PaintedEvilJesterMask() + : base(0x4BA5) + { + } - [Constructible] - public PaintedEvilJesterMask() - : base( 0x4BA5 ) - { - } + public PaintedEvilJesterMask(Serial serial) + : base(serial) + { + } - public PaintedEvilJesterMask( Serial serial ) - : base( serial ) - { - } + public override string MaskName => "Evil Jester Mask"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/2012/Items/PorcelainMask.cs b/Scripts/Holiday Stuff/Halloween/2012/Items/PorcelainMask.cs index de01d50f9..7235be359 100644 --- a/Scripts/Holiday Stuff/Halloween/2012/Items/PorcelainMask.cs +++ b/Scripts/Holiday Stuff/Halloween/2012/Items/PorcelainMask.cs @@ -1,32 +1,32 @@ namespace Server.Items.Holiday { - public class PaintedPorcelainMask : BasePaintedMask - { - public override string MaskName => "Porcelain Mask"; + public class PaintedPorcelainMask : BasePaintedMask + { + [Constructible] + public PaintedPorcelainMask() + : base(0x4BA7) + { + } - [Constructible] - public PaintedPorcelainMask() - : base( 0x4BA7 ) - { - } + public PaintedPorcelainMask(Serial serial) + : base(serial) + { + } - public PaintedPorcelainMask( Serial serial ) - : base( serial ) - { - } + public override string MaskName => "Porcelain Mask"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/HolidaySettings.cs b/Scripts/Holiday Stuff/Halloween/HolidaySettings.cs index 6e72f5a18..25ead51a3 100644 --- a/Scripts/Holiday Stuff/Halloween/HolidaySettings.cs +++ b/Scripts/Holiday Stuff/Halloween/HolidaySettings.cs @@ -3,38 +3,40 @@ using Server.Items; namespace Server.Events.Halloween { - class HolidaySettings - { - public static DateTime StartHalloween // YY MM DD - => new DateTime( 2012, 10, 24 ); + internal class HolidaySettings + { + private static Type[] m_GMBeggarTreats = + { + typeof(CreepyCake), + typeof(PumpkinPizza), + typeof(GrimWarning), + typeof(HarvestWine), + typeof(MurkyMilk), + typeof(MrPlainsCookies), + typeof(SkullsOnPike), + typeof(ChairInAGhostCostume), + typeof(ExcellentIronMaiden), + typeof(HalloweenGuillotine), + typeof(ColoredSmallWebs) + }; - public static DateTime FinishHalloween => new DateTime( 2012, 11, 15 ); + private static Type[] m_Treats = + { + typeof(Lollipops), + typeof(WrappedCandy), + typeof(JellyBeans), + typeof(Taffy), + typeof(NougatSwirl) + }; - public static Item RandomGMBeggerItem => ( Item )Activator.CreateInstance( m_GMBeggarTreats[ Utility.Random( m_GMBeggarTreats.Length ) ] ); - public static Item RandomTreat => (Item)Activator.CreateInstance ( m_Treats[ Utility.Random( m_Treats.Length ) ]); + public static DateTime StartHalloween // YY MM DD + => new DateTime(2012, 10, 24); - private static Type[] m_GMBeggarTreats = - { - typeof( CreepyCake ), - typeof( PumpkinPizza ), - typeof( GrimWarning ), - typeof( HarvestWine ), - typeof( MurkyMilk ), - typeof( MrPlainsCookies ), - typeof( SkullsOnPike ), - typeof( ChairInAGhostCostume ), - typeof( ExcellentIronMaiden ), - typeof( HalloweenGuillotine ), - typeof( ColoredSmallWebs ) - }; + public static DateTime FinishHalloween => new DateTime(2012, 11, 15); - private static Type[] m_Treats = - { - typeof( Lollipops ), - typeof( WrappedCandy ), - typeof( JellyBeans ), - typeof( Taffy ), - typeof( NougatSwirl ) - }; - } -} + public static Item RandomGMBeggerItem => + (Item)Activator.CreateInstance(m_GMBeggarTreats[Utility.Random(m_GMBeggarTreats.Length)]); + + public static Item RandomTreat => (Item)Activator.CreateInstance(m_Treats[Utility.Random(m_Treats.Length)]); + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/Treats/Jellybeans.cs b/Scripts/Holiday Stuff/Halloween/Treats/Jellybeans.cs index 63107a8ff..b3d01c553 100644 --- a/Scripts/Holiday Stuff/Halloween/Treats/Jellybeans.cs +++ b/Scripts/Holiday Stuff/Halloween/Treats/Jellybeans.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class JellyBeans : CandyCane - { - public override int LabelNumber => 1096932; /* jellybeans */ + public class JellyBeans : CandyCane + { + [Constructible] + public JellyBeans() + : this(1) + { + } - [Constructible] - public JellyBeans() - : this( 1 ) - { - } + public JellyBeans(int amount) + : base(0x468C) + { + Stackable = true; + } - public JellyBeans( int amount ) - : base( 0x468C ) - { - Stackable = true; - } + public JellyBeans(Serial serial) + : base(serial) + { + } - public JellyBeans( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1096932; /* jellybeans */ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/Treats/Lollipops.cs b/Scripts/Holiday Stuff/Halloween/Treats/Lollipops.cs index 27e7b092d..8691295f2 100644 --- a/Scripts/Holiday Stuff/Halloween/Treats/Lollipops.cs +++ b/Scripts/Holiday Stuff/Halloween/Treats/Lollipops.cs @@ -1,38 +1,38 @@ namespace Server.Items { - [TypeAlias( "Server.Items.Lollipop" )] - public class Lollipops : CandyCane - { - [Constructible] - public Lollipops() - : this( 1 ) - { - } + [TypeAlias("Server.Items.Lollipop")] + public class Lollipops : CandyCane + { + [Constructible] + public Lollipops() + : this(1) + { + } - [Constructible] - public Lollipops( int amount ) - : base( 0x468D + Utility.Random( 3 )) - { - Stackable = true; - } + [Constructible] + public Lollipops(int amount) + : base(0x468D + Utility.Random(3)) + { + Stackable = true; + } - public Lollipops( Serial serial ) - : base( serial ) - { - } + public Lollipops(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/Treats/NougatSwirl.cs b/Scripts/Holiday Stuff/Halloween/Treats/NougatSwirl.cs index ff6154925..3b00afb5a 100644 --- a/Scripts/Holiday Stuff/Halloween/Treats/NougatSwirl.cs +++ b/Scripts/Holiday Stuff/Halloween/Treats/NougatSwirl.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class NougatSwirl : CandyCane - { - public override int LabelNumber => 1096936; /* nougat swirl */ + public class NougatSwirl : CandyCane + { + [Constructible] + public NougatSwirl() : this(1) + { + } - [Constructible] - public NougatSwirl() : this(1) - { + [Constructible] + public NougatSwirl(int amount) + : base(0x4690) + { + Stackable = true; + } - } + public NougatSwirl(Serial serial) + : base(serial) + { + } - [Constructible] - public NougatSwirl( int amount ) - : base( 0x4690 ) - { - Stackable = true; - } + public override int LabelNumber => 1096936; /* nougat swirl */ - public NougatSwirl( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( ( int )0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/Treats/Taffy.cs b/Scripts/Holiday Stuff/Halloween/Treats/Taffy.cs index 68bfcd059..cec62e912 100644 --- a/Scripts/Holiday Stuff/Halloween/Treats/Taffy.cs +++ b/Scripts/Holiday Stuff/Halloween/Treats/Taffy.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class Taffy : CandyCane - { - public override int LabelNumber => 1096949; /* taffy */ + public class Taffy : CandyCane + { + [Constructible] + public Taffy() + : this(1) + { + } - [Constructible] - public Taffy() - : this( 1 ) - { - } + public Taffy(int amount) + : base(0x469D) + { + Stackable = true; + } - public Taffy( int amount ) - : base( 0x469D ) - { - Stackable = true; - } + public Taffy(Serial serial) + : base(serial) + { + } - public Taffy( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1096949; /* taffy */ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Halloween/Treats/WrappedCandy.cs b/Scripts/Holiday Stuff/Halloween/Treats/WrappedCandy.cs index e058ea0de..085081968 100644 --- a/Scripts/Holiday Stuff/Halloween/Treats/WrappedCandy.cs +++ b/Scripts/Holiday Stuff/Halloween/Treats/WrappedCandy.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class WrappedCandy : CandyCane - { - public override int LabelNumber => 1096950; /* wrapped candy */ + public class WrappedCandy : CandyCane + { + [Constructible] + public WrappedCandy() + : this(1) + { + } - [Constructible] - public WrappedCandy() - : this( 1 ) - { - } + public WrappedCandy(int amount) + : base(0x469e) + { + Stackable = true; + } - public WrappedCandy( int amount ) - : base( 0x469e ) - { - Stackable = true; - } + public WrappedCandy(Serial serial) + : base(serial) + { + } - public WrappedCandy( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1096950; /* wrapped candy */ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Valentine/2010/Items/AnimatedHeartShapedBox.cs b/Scripts/Holiday Stuff/Valentine/2010/Items/AnimatedHeartShapedBox.cs index f9212454b..6981ac610 100644 --- a/Scripts/Holiday Stuff/Valentine/2010/Items/AnimatedHeartShapedBox.cs +++ b/Scripts/Holiday Stuff/Valentine/2010/Items/AnimatedHeartShapedBox.cs @@ -1,31 +1,31 @@ namespace Server.Items { - [FlippableAttribute( 0x49CC, 0x49D0 )] - public class AnimatedHeartShapedBox : HeartShapedBox - { - [Constructible] - public AnimatedHeartShapedBox() - { - ItemID = 0x49CC; - } + [Flippable(0x49CC, 0x49D0)] + public class AnimatedHeartShapedBox : HeartShapedBox + { + [Constructible] + public AnimatedHeartShapedBox() + { + ItemID = 0x49CC; + } - public AnimatedHeartShapedBox( Serial serial ) - : base( serial ) - { - } + public AnimatedHeartShapedBox(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Valentine/2011/Items/StValentinesBears.cs b/Scripts/Holiday Stuff/Valentine/2011/Items/StValentinesBears.cs index 8d2697567..40ebc91f8 100644 --- a/Scripts/Holiday Stuff/Valentine/2011/Items/StValentinesBears.cs +++ b/Scripts/Holiday Stuff/Valentine/2011/Items/StValentinesBears.cs @@ -4,284 +4,302 @@ using Server.Network; namespace Server.Items { - public abstract class StValentinesBear : Item - { - public override string DefaultName - { - get - { - if ( m_Owner != null ) - return $"{m_Owner}'s St. Valentine Bear"; - return "St. Valentine Bear"; - } - } + public abstract class StValentinesBear : Item + { + private string m_Line1; + private string m_Line2; + private string m_Line3; - private string m_Owner; - private string m_Line1; - private string m_Line2; - private string m_Line3; + private string m_Owner; - [CommandProperty( AccessLevel.GameMaster )] - public string Owner - { - get => m_Owner; - set { m_Owner = value; InvalidateProperties(); } - } + public StValentinesBear(int itemid, string name) + : base(itemid) + { + m_Owner = name; + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public string Line1 - { - get => m_Line1; - set { m_Line1 = value; InvalidateProperties(); } - } + public StValentinesBear(Serial serial) + : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public string Line2 - { - get => m_Line2; - set { m_Line2 = value; InvalidateProperties(); } - } + public override string DefaultName + { + get + { + if (m_Owner != null) + return $"{m_Owner}'s St. Valentine Bear"; + return "St. Valentine Bear"; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public string Line3 - { - get => m_Line3; - set { m_Line3 = value; InvalidateProperties(); } - } + [CommandProperty(AccessLevel.GameMaster)] + public string Owner + { + get => m_Owner; + set + { + m_Owner = value; + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime EditLimit { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public string Line1 + { + get => m_Line1; + set + { + m_Line1 = value; + InvalidateProperties(); + } + } - public bool IsSigned => ( m_Line1 != null || m_Line2 != null || m_Line3 != null ); + [CommandProperty(AccessLevel.GameMaster)] + public string Line2 + { + get => m_Line2; + set + { + m_Line2 = value; + InvalidateProperties(); + } + } - public bool CanSign => ( !IsSigned || DateTime.UtcNow <= EditLimit ); + [CommandProperty(AccessLevel.GameMaster)] + public string Line3 + { + get => m_Line3; + set + { + m_Line3 = value; + InvalidateProperties(); + } + } - public StValentinesBear( int itemid, string name ) - : base( itemid ) - { - m_Owner = name; - LootType = LootType.Blessed; - } + [CommandProperty(AccessLevel.GameMaster)] + public DateTime EditLimit{ get; set; } - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_Owner != null ) - list.Add( 1150295, m_Owner ); // ~1_NAME~'s St. Valentine Bear - else - list.Add( 1150294 ); // St. Valentine Bear + public bool IsSigned => m_Line1 != null || m_Line2 != null || m_Line3 != null; - AddLine( list, 1150301, m_Line1 ); // [ ~1_LINE0~ ] - AddLine( list, 1150302, m_Line2 ); // [ ~1_LINE1~ ] - AddLine( list, 1150303, m_Line3 ); // [ ~1_LINE2~ ] - } + public bool CanSign => !IsSigned || DateTime.UtcNow <= EditLimit; - private static void AddLine( ObjectPropertyList list, int cliloc, string line ) - { - if ( line != null ) - list.Add( cliloc, line ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_Owner != null) + list.Add(1150295, m_Owner); // ~1_NAME~'s St. Valentine Bear + else + list.Add(1150294); // St. Valentine Bear - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + AddLine(list, 1150301, m_Line1); // [ ~1_LINE0~ ] + AddLine(list, 1150302, m_Line2); // [ ~1_LINE1~ ] + AddLine(list, 1150303, m_Line3); // [ ~1_LINE2~ ] + } - ShowLine( from, 1150301, m_Line1 ); // [ ~1_LINE0~ ] - ShowLine( from, 1150302, m_Line2 ); // [ ~1_LINE1~ ] - ShowLine( from, 1150303, m_Line3 ); // [ ~1_LINE2~ ] - } + private static void AddLine(ObjectPropertyList list, int cliloc, string line) + { + if (line != null) + list.Add(cliloc, line); + } - private void ShowLine( Mobile from, int cliloc, string line ) - { - if ( line != null ) - LabelTo( from, cliloc, line ); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - public override void OnDoubleClick( Mobile from ) - { - if ( !CupidsArrow.CheckSeason( from ) || !CanSign ) - return; + ShowLine(from, 1150301, m_Line1); // [ ~1_LINE0~ ] + ShowLine(from, 1150302, m_Line2); // [ ~1_LINE1~ ] + ShowLine(from, 1150303, m_Line3); // [ ~1_LINE2~ ] + } - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1080063 ); // This must be in your backpack to use it. - return; - } + private void ShowLine(Mobile from, int cliloc, string line) + { + if (line != null) + LabelTo(from, cliloc, line); + } - from.SendGump( new InternalGump( this ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (!CupidsArrow.CheckSeason(from) || !CanSign) + return; - public StValentinesBear( Serial serial ) - : base( serial ) - { - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1080063); // This must be in your backpack to use it. + return; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + from.SendGump(new InternalGump(this)); + } - writer.Write( (int)0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( m_Owner ); - writer.Write( m_Line1 ); - writer.Write( m_Line2 ); - writer.Write( m_Line3 ); - } + writer.Write(0); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Owner); + writer.Write(m_Line1); + writer.Write(m_Line2); + writer.Write(m_Line3); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Owner = Utility.Intern( reader.ReadString() ); - m_Line1 = Utility.Intern( reader.ReadString() ); - m_Line2 = Utility.Intern( reader.ReadString() ); - m_Line3 = Utility.Intern( reader.ReadString() ); - } + int version = reader.ReadInt(); - private class InternalGump : Gump - { - private StValentinesBear m_Bear; + m_Owner = Utility.Intern(reader.ReadString()); + m_Line1 = Utility.Intern(reader.ReadString()); + m_Line2 = Utility.Intern(reader.ReadString()); + m_Line3 = Utility.Intern(reader.ReadString()); + } - public InternalGump( StValentinesBear bear ) - : base( 50, 50 ) - { - m_Bear = bear; + private class InternalGump : Gump + { + private StValentinesBear m_Bear; - AddPage( 0 ); - AddBackground( 0, 0, 420, 320, 9300 ); - AddHtml( 10, 10, 400, 21, "
St. Valentine Bear
", false, false ); - AddHtmlLocalized( 10, 40, 400, 75, 1150293, 0, false, false ); // Enter up to three lines of personalized greeting for your St. Valentine Bear. You many enter up to 25 characters per line. Once you enter text, you will only be able to correct mistakes for 10 minutes. + public InternalGump(StValentinesBear bear) + : base(50, 50) + { + m_Bear = bear; - AddHtmlLocalized( 10, 129, 400, 21, 1150296, 0, false, false ); // Line 1: - AddBackground( 10, 150, 400, 24, 9350 ); - AddTextEntry( 15, 152, 390, 20, 0, 0, "", 25 ); + AddPage(0); + AddBackground(0, 0, 420, 320, 9300); + AddHtml(10, 10, 400, 21, "
St. Valentine Bear
", false, false); + AddHtmlLocalized(10, 40, 400, 75, 1150293, 0, false, + false); // Enter up to three lines of personalized greeting for your St. Valentine Bear. You many enter up to 25 characters per line. Once you enter text, you will only be able to correct mistakes for 10 minutes. - AddHtmlLocalized( 10, 179, 400, 21, 1150297, 0, false, false ); // Line 2: - AddBackground( 10, 200, 400, 24, 9350 ); - AddTextEntry( 15, 202, 390, 20, 0, 1, "", 25 ); + AddHtmlLocalized(10, 129, 400, 21, 1150296, 0, false, false); // Line 1: + AddBackground(10, 150, 400, 24, 9350); + AddTextEntry(15, 152, 390, 20, 0, 0, "", 25); - AddHtmlLocalized( 10, 229, 400, 21, 1150298, 0, false, false ); // Line 3: - AddBackground( 10, 250, 400, 24, 9350 ); - AddTextEntry( 15, 252, 390, 20, 0, 2, "", 25 ); + AddHtmlLocalized(10, 179, 400, 21, 1150297, 0, false, false); // Line 2: + AddBackground(10, 200, 400, 24, 9350); + AddTextEntry(15, 202, 390, 20, 0, 1, "", 25); - AddButton( 15, 285, 242, 241, 0, GumpButtonType.Reply, 0 ); - AddButton( 335, 285, 247, 248, 1, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(10, 229, 400, 21, 1150298, 0, false, false); // Line 3: + AddBackground(10, 250, 400, 24, 9350); + AddTextEntry(15, 252, 390, 20, 0, 2, "", 25); - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + AddButton(15, 285, 242, 241, 0, GumpButtonType.Reply, 0); + AddButton(335, 285, 247, 248, 1, GumpButtonType.Reply, 0); + } - if ( m_Bear.Deleted || !m_Bear.IsChildOf( from.Backpack ) || !m_Bear.CanSign || info.ButtonID != 1 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - string line1 = GetLine( info, 0 ); - string line2 = GetLine( info, 1 ); - string line3 = GetLine( info, 2 ); + if (m_Bear.Deleted || !m_Bear.IsChildOf(from.Backpack) || !m_Bear.CanSign || info.ButtonID != 1) + return; - if ( string.IsNullOrEmpty( line1 ) - || string.IsNullOrEmpty( line2 ) - || string.IsNullOrEmpty( line3 ) ) - { - from.SendMessage( "Lines cannot be left blank." ); - return; - } + string line1 = GetLine(info, 0); + string line2 = GetLine(info, 1); + string line3 = GetLine(info, 2); - if ( line1.Length > 25 - || line2.Length > 25 - || line3.Length > 25 ) - { - from.SendMessage( "Lines may not exceed 25 characters." ); - return; - } + if (string.IsNullOrEmpty(line1) + || string.IsNullOrEmpty(line2) + || string.IsNullOrEmpty(line3)) + { + from.SendMessage("Lines cannot be left blank."); + return; + } - if ( !m_Bear.IsSigned ) - m_Bear.EditLimit = DateTime.UtcNow + TimeSpan.FromMinutes( 10 ); + if (line1.Length > 25 + || line2.Length > 25 + || line3.Length > 25) + { + from.SendMessage("Lines may not exceed 25 characters."); + return; + } - m_Bear.Line1 = Utility.FixHtml( line1 ); - m_Bear.Line2 = Utility.FixHtml( line2 ); - m_Bear.Line3 = Utility.FixHtml( line3 ); + if (!m_Bear.IsSigned) + m_Bear.EditLimit = DateTime.UtcNow + TimeSpan.FromMinutes(10); - from.SendMessage( "You add the personalized greeting to your St. Valentine Bear." ); - } + m_Bear.Line1 = Utility.FixHtml(line1); + m_Bear.Line2 = Utility.FixHtml(line2); + m_Bear.Line3 = Utility.FixHtml(line3); - private static string GetLine( RelayInfo info, int idx ) - { - TextRelay tr = info.GetTextEntry( idx ); + from.SendMessage("You add the personalized greeting to your St. Valentine Bear."); + } - return tr?.Text; - } - } - } + private static string GetLine(RelayInfo info, int idx) + { + TextRelay tr = info.GetTextEntry(idx); - [FlippableAttribute( 0x48E0, 0x48E1 )] - public class StValentinesPanda : StValentinesBear - { - [Constructible] - public StValentinesPanda() - : this( null ) - { - } + return tr?.Text; + } + } + } - [Constructible] - public StValentinesPanda( string name ) - : base( 0x48E0, name ) - { - } + [Flippable(0x48E0, 0x48E1)] + public class StValentinesPanda : StValentinesBear + { + [Constructible] + public StValentinesPanda() + : this(null) + { + } - public StValentinesPanda( Serial serial ) - : base( serial ) - { - } + [Constructible] + public StValentinesPanda(string name) + : base(0x48E0, name) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public StValentinesPanda(Serial serial) + : base(serial) + { + } - writer.Write( (int)0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [FlippableAttribute( 0x48E2, 0x48E3 )] - public class StValentinesPolarBear : StValentinesBear - { - [Constructible] - public StValentinesPolarBear() - : this( null ) - { - } + int version = reader.ReadInt(); + } + } - [Constructible] - public StValentinesPolarBear( string name ) - : base( 0x48E2, name ) - { - } + [Flippable(0x48E2, 0x48E3)] + public class StValentinesPolarBear : StValentinesBear + { + [Constructible] + public StValentinesPolarBear() + : this(null) + { + } - public StValentinesPolarBear( Serial serial ) - : base( serial ) - { - } + [Constructible] + public StValentinesPolarBear(string name) + : base(0x48E2, name) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public StValentinesPolarBear(Serial serial) + : base(serial) + { + } - writer.Write( (int)0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Valentine/2012/Items/CupidStatue.cs b/Scripts/Holiday Stuff/Valentine/2012/Items/CupidStatue.cs index 9f0893ed1..580d81a64 100644 --- a/Scripts/Holiday Stuff/Valentine/2012/Items/CupidStatue.cs +++ b/Scripts/Holiday Stuff/Valentine/2012/Items/CupidStatue.cs @@ -1,34 +1,34 @@ namespace Server.Items { - [FlippableAttribute( 0x4F7C, 0x4F7D )] - public class CupidStatue : Item - { - public override int LabelNumber => 1099220; // cupid statue + [Flippable(0x4F7C, 0x4F7D)] + public class CupidStatue : Item + { + [Constructible] + public CupidStatue() + : base(0x4F7D) + { + LootType = LootType.Blessed; + } - [Constructible] - public CupidStatue() - : base( 0x4F7D ) - { - LootType = LootType.Blessed; - } + public CupidStatue(Serial serial) + : base(serial) + { + } - public CupidStatue( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1099220; // cupid statue - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Holiday Stuff/Valentine/2012/Items/HeartShapedBox.cs b/Scripts/Holiday Stuff/Valentine/2012/Items/HeartShapedBox.cs index a20436820..49fbdc9b0 100644 --- a/Scripts/Holiday Stuff/Valentine/2012/Items/HeartShapedBox.cs +++ b/Scripts/Holiday Stuff/Valentine/2012/Items/HeartShapedBox.cs @@ -1,52 +1,52 @@ namespace Server.Items { - [FlippableAttribute( 0x49CA, 0x49CB )] - public class HeartShapedBox : BaseContainer - { - public override int DefaultDropSound => m_DropSound; + [Flippable(0x49CA, 0x49CB)] + public class HeartShapedBox : BaseContainer + { + private static int m_DropSound; - [Constructible] - public HeartShapedBox() - : base( 0x49CA ) - { - } + [Constructible] + public HeartShapedBox() + : base(0x49CA) + { + } - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - PrepareSound( from ); - return base.OnDragDropInto( from, item, p ); - } + public HeartShapedBox(Serial serial) + : base(serial) + { + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - PrepareSound( from ); - return base.OnDragDrop( from, dropped ); - } + public override int DefaultDropSound => m_DropSound; - private static int m_DropSound; + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + PrepareSound(from); + return base.OnDragDropInto(from, item, p); + } - private static void PrepareSound( Mobile from ) - { - m_DropSound = from.Female ? 0x430 : 0x320; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + PrepareSound(from); + return base.OnDragDrop(from, dropped); + } - public HeartShapedBox( Serial serial ) - : base( serial ) - { - } + private static void PrepareSound(Mobile from) + { + m_DropSound = from.Female ? 0x430 : 0x320; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AbbatoirAddon.cs b/Scripts/Items/Addons/AbbatoirAddon.cs index acec87e14..2d10e4360 100644 --- a/Scripts/Items/Addons/AbbatoirAddon.cs +++ b/Scripts/Items/Addons/AbbatoirAddon.cs @@ -1,68 +1,68 @@ namespace Server.Items { - public class AbbatoirAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AbbatoirDeed(); + public class AbbatoirAddon : BaseAddon + { + [Constructible] + public AbbatoirAddon() + { + AddComponent(new AddonComponent(0x120E), -1, -1, 0); + AddComponent(new AddonComponent(0x120F), 0, -1, 0); + AddComponent(new AddonComponent(0x1210), 1, -1, 0); + AddComponent(new AddonComponent(0x1215), -1, 0, 0); + AddComponent(new AddonComponent(0x1216), 0, 0, 0); + AddComponent(new AddonComponent(0x1211), 1, 0, 0); + AddComponent(new AddonComponent(0x1214), -1, 1, 0); + AddComponent(new AddonComponent(0x1213), 0, 1, 0); + AddComponent(new AddonComponent(0x1212), 1, 1, 0); + } - [Constructible] - public AbbatoirAddon() - { - AddComponent( new AddonComponent( 0x120E ), -1, -1, 0 ); - AddComponent( new AddonComponent( 0x120F ), 0, -1, 0 ); - AddComponent( new AddonComponent( 0x1210 ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0x1215 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x1216 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1211 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1214 ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0x1213 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1212 ), 1, 1, 0 ); - } + public AbbatoirAddon(Serial serial) : base(serial) + { + } - public AbbatoirAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AbbatoirDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class AbbatoirDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AbbatoirAddon(); - public override int LabelNumber => 1044329; // abbatoir + public class AbbatoirDeed : BaseAddonDeed + { + [Constructible] + public AbbatoirDeed() + { + } - [Constructible] - public AbbatoirDeed() - { - } + public AbbatoirDeed(Serial serial) : base(serial) + { + } - public AbbatoirDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AbbatoirAddon(); + public override int LabelNumber => 1044329; // abbatoir - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AddonComponent.cs b/Scripts/Items/Addons/AddonComponent.cs index d2700dd10..3d69fc204 100644 --- a/Scripts/Items/Addons/AddonComponent.cs +++ b/Scripts/Items/Addons/AddonComponent.cs @@ -1,252 +1,262 @@ +using Server.Engines.Craft; + namespace Server.Items { - [Engines.Craft.Anvil] - public class AnvilComponent : AddonComponent - { - [Constructible] - public AnvilComponent( int itemID ) : base( itemID ) - { - } + [Anvil] + public class AnvilComponent : AddonComponent + { + [Constructible] + public AnvilComponent(int itemID) : base(itemID) + { + } - public AnvilComponent( Serial serial ) : base( serial ) - { - } + public AnvilComponent(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Engines.Craft.Forge] - public class ForgeComponent : AddonComponent - { - [Constructible] - public ForgeComponent( int itemID ) : base( itemID ) - { - } + [Forge] + public class ForgeComponent : AddonComponent + { + [Constructible] + public ForgeComponent(int itemID) : base(itemID) + { + } - public ForgeComponent( Serial serial ) : base( serial ) - { - } + public ForgeComponent(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LocalizedAddonComponent : AddonComponent - { - private int m_LabelNumber; + public class LocalizedAddonComponent : AddonComponent + { + private int m_LabelNumber; - [CommandProperty( AccessLevel.GameMaster )] - public int Number - { - get => m_LabelNumber; - set{ m_LabelNumber = value; InvalidateProperties(); } - } + [Constructible] + public LocalizedAddonComponent(int itemID, int labelNumber) : base(itemID) + { + m_LabelNumber = labelNumber; + } - public override int LabelNumber => m_LabelNumber; + public LocalizedAddonComponent(Serial serial) : base(serial) + { + } - [Constructible] - public LocalizedAddonComponent( int itemID, int labelNumber ) : base( itemID ) - { - m_LabelNumber = labelNumber; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_LabelNumber; + set + { + m_LabelNumber = value; + InvalidateProperties(); + } + } - public LocalizedAddonComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => m_LabelNumber; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_LabelNumber ); - } + writer.Write(m_LabelNumber); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadInt(); - break; - } - } - } - } + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadInt(); + break; + } + } + } + } - public class AddonComponent : Item, IChopable - { - [CommandProperty( AccessLevel.GameMaster )] - public BaseAddon Addon { get; set; } + public class AddonComponent : Item, IChopable + { + private static LightEntry[] m_Entries = + { + new LightEntry(LightType.WestSmall, 1122, 1123, 1124, 1141, 1142, 1143, 1144, 1145, 1146, 2347, 2359, 2360, 2361, + 2362, 2363, 2364, 2387, 2388, 2389, 2390, 2391, 2392), + new LightEntry(LightType.NorthSmall, 1131, 1133, 1134, 1147, 1148, 1149, 1150, 1151, 1152, 2352, 2373, 2374, + 2375, 2376, 2377, 2378, 2401, 2402, 2403, 2404, 2405, 2406), + new LightEntry(LightType.Circle300, 6526, 6538, 6571), + new LightEntry(LightType.Circle150, 5703, 6587) + }; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Offset { get; set; } + [Constructible] + public AddonComponent(int itemID) : base(itemID) + { + Movable = false; + ApplyLightTo(this); + } - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set - { - base.Hue = value; + public AddonComponent(Serial serial) : base(serial) + { + } - if ( Addon != null && Addon.ShareHue ) - Addon.Hue = value; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public BaseAddon Addon{ get; set; } - public virtual bool NeedsWall => false; - public virtual Point3D WallPosition => Point3D.Zero; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Offset{ get; set; } - [Constructible] - public AddonComponent( int itemID ) : base( itemID ) - { - Movable = false; - ApplyLightTo( this ); - } + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; - public AddonComponent( Serial serial ) : base( serial ) - { - } + if (Addon != null && Addon.ShareHue) + Addon.Hue = value; + } + } - public override void OnDoubleClick( Mobile from ) - { - Addon?.OnComponentUsed( this, from ); - } + public virtual bool NeedsWall => false; + public virtual Point3D WallPosition => Point3D.Zero; - public void OnChop( Mobile from ) - { - if ( Addon != null && from.InRange( GetWorldLocation(), 3 ) ) - Addon.OnChop( from ); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } + public void OnChop(Mobile from) + { + if (Addon != null && from.InRange(GetWorldLocation(), 3)) + Addon.OnChop(from); + else + from.SendLocalizedMessage(500446); // That is too far away. + } - public override void OnLocationChange( Point3D old ) - { - if ( Addon != null ) - Addon.Location = new Point3D( X - Offset.X, Y - Offset.Y, Z - Offset.Z ); - } + public override void OnDoubleClick(Mobile from) + { + Addon?.OnComponentUsed(this, from); + } - public override void OnMapChange() - { - if ( Addon != null ) - Addon.Map = Map; - } + public override void OnLocationChange(Point3D old) + { + if (Addon != null) + Addon.Location = new Point3D(X - Offset.X, Y - Offset.Y, Z - Offset.Z); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnMapChange() + { + if (Addon != null) + Addon.Map = Map; + } - Addon?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Addon?.Delete(); + } - writer.Write( (int) 1 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( Addon ); - writer.Write( Offset ); - } + writer.Write(1); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(Addon); + writer.Write(Offset); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - case 0: - { - Addon = reader.ReadItem() as BaseAddon; - Offset = reader.ReadPoint3D(); + int version = reader.ReadInt(); - Addon?.OnComponentLoaded( this ); + switch (version) + { + case 1: + case 0: + { + Addon = reader.ReadItem() as BaseAddon; + Offset = reader.ReadPoint3D(); - ApplyLightTo( this ); + Addon?.OnComponentLoaded(this); - break; - } - } + ApplyLightTo(this); - if ( version < 1 && Weight == 0 ) - Weight = -1; - } + break; + } + } - public static void ApplyLightTo( Item item ) - { - if ( (item.ItemData.Flags & TileFlag.LightSource) == 0 ) - return; // not a light source + if (version < 1 && Weight == 0) + Weight = -1; + } - int itemID = item.ItemID; + public static void ApplyLightTo(Item item) + { + if ((item.ItemData.Flags & TileFlag.LightSource) == 0) + return; // not a light source - for ( int i = 0; i < m_Entries.Length; ++i ) - { - LightEntry entry = m_Entries[i]; - int[] toMatch = entry.m_ItemIDs; - bool contains = false; + int itemID = item.ItemID; - for ( int j = 0; !contains && j < toMatch.Length; ++j ) - contains = ( itemID == toMatch[j] ); + for (int i = 0; i < m_Entries.Length; ++i) + { + LightEntry entry = m_Entries[i]; + int[] toMatch = entry.m_ItemIDs; + bool contains = false; - if ( contains ) - { - item.Light = entry.m_Light; - return; - } - } - } + for (int j = 0; !contains && j < toMatch.Length; ++j) + contains = itemID == toMatch[j]; - private static LightEntry[] m_Entries = { - new LightEntry( LightType.WestSmall, 1122, 1123, 1124, 1141, 1142, 1143, 1144, 1145, 1146, 2347, 2359, 2360, 2361, 2362, 2363, 2364, 2387, 2388, 2389, 2390, 2391, 2392 ), - new LightEntry( LightType.NorthSmall, 1131, 1133, 1134, 1147, 1148, 1149, 1150, 1151, 1152, 2352, 2373, 2374, 2375, 2376, 2377, 2378, 2401, 2402, 2403, 2404, 2405, 2406 ), - new LightEntry( LightType.Circle300, 6526, 6538, 6571 ), - new LightEntry( LightType.Circle150, 5703, 6587 ) - }; + if (contains) + { + item.Light = entry.m_Light; + return; + } + } + } - private class LightEntry - { - public LightType m_Light; - public int[] m_ItemIDs; + private class LightEntry + { + public int[] m_ItemIDs; + public LightType m_Light; - public LightEntry( LightType light, params int[] itemIDs ) - { - m_Light = light; - m_ItemIDs = itemIDs; - } - } - } -} + public LightEntry(LightType light, params int[] itemIDs) + { + m_Light = light; + m_ItemIDs = itemIDs; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AddonContainerComponent.cs b/Scripts/Items/Addons/AddonContainerComponent.cs index e28a706eb..6ebb94840 100644 --- a/Scripts/Items/Addons/AddonContainerComponent.cs +++ b/Scripts/Items/Addons/AddonContainerComponent.cs @@ -3,152 +3,153 @@ using Server.ContextMenus; namespace Server.Items { - public class AddonContainerComponent : Item, IChopable - { - public virtual bool NeedsWall => false; - public virtual Point3D WallPosition => Point3D.Zero; + public class AddonContainerComponent : Item, IChopable + { + [Constructible] + public AddonContainerComponent(int itemID) : base(itemID) + { + Movable = false; - [CommandProperty( AccessLevel.GameMaster )] - public BaseAddonContainer Addon { get; set; } + AddonComponent.ApplyLightTo(this); + } - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Offset { get; set; } + public AddonContainerComponent(Serial serial) : base(serial) + { + } - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set - { - base.Hue = value; + public virtual bool NeedsWall => false; + public virtual Point3D WallPosition => Point3D.Zero; - if ( Addon != null && Addon.ShareHue ) - Addon.Hue = value; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public BaseAddonContainer Addon{ get; set; } - [Constructible] - public AddonContainerComponent( int itemID ) : base( itemID ) - { - Movable = false; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Offset{ get; set; } - AddonComponent.ApplyLightTo( this ); - } + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; - public AddonContainerComponent( Serial serial ) : base( serial ) - { - } + if (Addon != null && Addon.ShareHue) + Addon.Hue = value; + } + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( Addon != null ) - return Addon.OnDragDrop( from, dropped ); + public virtual void OnChop(Mobile from) + { + if (Addon != null && from.InRange(GetWorldLocation(), 3)) + Addon.OnChop(from); + else + from.SendLocalizedMessage(500446); // That is too far away. + } - return false; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (Addon != null) + return Addon.OnDragDrop(from, dropped); - public override void OnDoubleClick( Mobile from ) - { - Addon?.OnComponentUsed( this, from ); - } + return false; + } - public override void OnLocationChange( Point3D old ) - { - if ( Addon != null ) - Addon.Location = new Point3D( X - Offset.X, Y - Offset.Y, Z - Offset.Z ); - } + public override void OnDoubleClick(Mobile from) + { + Addon?.OnComponentUsed(this, from); + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - Addon?.GetContextMenuEntries( from, list ); - } + public override void OnLocationChange(Point3D old) + { + if (Addon != null) + Addon.Location = new Point3D(X - Offset.X, Y - Offset.Y, Z - Offset.Z); + } - public override void OnMapChange() - { - if ( Addon != null ) - Addon.Map = Map; - } + public override void GetContextMenuEntries(Mobile from, List list) + { + Addon?.GetContextMenuEntries(from, list); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnMapChange() + { + if (Addon != null) + Addon.Map = Map; + } - Addon?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Addon?.Delete(); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( Addon ); - writer.Write( Offset ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(Addon); + writer.Write(Offset); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Addon = reader.ReadItem() as BaseAddonContainer; - Offset = reader.ReadPoint3D(); + int version = reader.ReadInt(); - Addon?.OnComponentLoaded( this ); + Addon = reader.ReadItem() as BaseAddonContainer; + Offset = reader.ReadPoint3D(); - AddonComponent.ApplyLightTo( this ); - } + Addon?.OnComponentLoaded(this); - public virtual void OnChop( Mobile from ) - { - if ( Addon != null && from.InRange( GetWorldLocation(), 3 ) ) - Addon.OnChop( from ); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } + AddonComponent.ApplyLightTo(this); + } + } - public class LocalizedContainerComponent : AddonContainerComponent - { - private int m_LabelNumber; + public class LocalizedContainerComponent : AddonContainerComponent + { + private int m_LabelNumber; - public override int LabelNumber - { - get - { - if ( m_LabelNumber > 0 ) - return m_LabelNumber; + public LocalizedContainerComponent(int itemID, int labelNumber) : base(itemID) + { + m_LabelNumber = labelNumber; + } - return base.LabelNumber; - } - } + public LocalizedContainerComponent(Serial serial) : base(serial) + { + } - public LocalizedContainerComponent( int itemID, int labelNumber ) : base( itemID ) - { - m_LabelNumber = labelNumber; - } + public override int LabelNumber + { + get + { + if (m_LabelNumber > 0) + return m_LabelNumber; - public LocalizedContainerComponent( Serial serial ) : base( serial ) - { - } + return base.LabelNumber; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_LabelNumber ); - } + writer.Write(m_LabelNumber); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_LabelNumber = reader.ReadInt(); - } - } -} + m_LabelNumber = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AlchemistTableEastAddon.cs b/Scripts/Items/Addons/AlchemistTableEastAddon.cs index a838b18e4..5ec45facc 100644 --- a/Scripts/Items/Addons/AlchemistTableEastAddon.cs +++ b/Scripts/Items/Addons/AlchemistTableEastAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class AlchemistTableEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AlchemistTableEastDeed(); + public class AlchemistTableEastAddon : BaseAddon + { + [Constructible] + public AlchemistTableEastAddon() + { + AddComponent(new AddonComponent(0x2DD3), 0, 0, 0); + } - [Constructible] - public AlchemistTableEastAddon() - { - AddComponent( new AddonComponent( 0x2DD3 ), 0, 0, 0 ); - } + public AlchemistTableEastAddon(Serial serial) : base(serial) + { + } - public AlchemistTableEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AlchemistTableEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version - } + writer.WriteEncodedInt(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class AlchemistTableEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AlchemistTableEastAddon(); - public override int LabelNumber => 1073397; // alchemist table (east) + public class AlchemistTableEastDeed : BaseAddonDeed + { + [Constructible] + public AlchemistTableEastDeed() + { + } - [Constructible] - public AlchemistTableEastDeed() - { - } + public AlchemistTableEastDeed(Serial serial) : base(serial) + { + } - public AlchemistTableEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AlchemistTableEastAddon(); + public override int LabelNumber => 1073397; // alchemist table (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AlchemistTableSouthAddon.cs b/Scripts/Items/Addons/AlchemistTableSouthAddon.cs index a8d7e4783..555e6761f 100644 --- a/Scripts/Items/Addons/AlchemistTableSouthAddon.cs +++ b/Scripts/Items/Addons/AlchemistTableSouthAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class AlchemistTableSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AlchemistTableSouthDeed(); + public class AlchemistTableSouthAddon : BaseAddon + { + [Constructible] + public AlchemistTableSouthAddon() + { + AddComponent(new AddonComponent(0x2DD4), 0, 0, 0); + } - [Constructible] - public AlchemistTableSouthAddon() - { - AddComponent( new AddonComponent( 0x2DD4 ), 0, 0, 0 ); - } + public AlchemistTableSouthAddon(Serial serial) : base(serial) + { + } - public AlchemistTableSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AlchemistTableSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version - } + writer.WriteEncodedInt(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class AlchemistTableSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AlchemistTableSouthAddon(); - public override int LabelNumber => 1073396; // alchemist table (south) + public class AlchemistTableSouthDeed : BaseAddonDeed + { + [Constructible] + public AlchemistTableSouthDeed() + { + } - [Constructible] - public AlchemistTableSouthDeed() - { - } + public AlchemistTableSouthDeed(Serial serial) : base(serial) + { + } - public AlchemistTableSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AlchemistTableSouthAddon(); + public override int LabelNumber => 1073396; // alchemist table (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AnvilEastAddon.cs b/Scripts/Items/Addons/AnvilEastAddon.cs index bc64722cb..6de830117 100644 --- a/Scripts/Items/Addons/AnvilEastAddon.cs +++ b/Scripts/Items/Addons/AnvilEastAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class AnvilEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AnvilEastDeed(); + public class AnvilEastAddon : BaseAddon + { + [Constructible] + public AnvilEastAddon() + { + AddComponent(new AnvilComponent(0xFAF), 0, 0, 0); + } - [Constructible] - public AnvilEastAddon() - { - AddComponent( new AnvilComponent( 0xFAF ), 0, 0, 0 ); - } + public AnvilEastAddon(Serial serial) : base(serial) + { + } - public AnvilEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AnvilEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class AnvilEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AnvilEastAddon(); - public override int LabelNumber => 1044333; // anvil (east) + public class AnvilEastDeed : BaseAddonDeed + { + [Constructible] + public AnvilEastDeed() + { + } - [Constructible] - public AnvilEastDeed() - { - } + public AnvilEastDeed(Serial serial) : base(serial) + { + } - public AnvilEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AnvilEastAddon(); + public override int LabelNumber => 1044333; // anvil (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/AnvilSouthAddon.cs b/Scripts/Items/Addons/AnvilSouthAddon.cs index cd8ad9321..a8f9d6e05 100644 --- a/Scripts/Items/Addons/AnvilSouthAddon.cs +++ b/Scripts/Items/Addons/AnvilSouthAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class AnvilSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AnvilSouthDeed(); + public class AnvilSouthAddon : BaseAddon + { + [Constructible] + public AnvilSouthAddon() + { + AddComponent(new AnvilComponent(0xFB0), 0, 0, 0); + } - [Constructible] - public AnvilSouthAddon() - { - AddComponent( new AnvilComponent( 0xFB0 ), 0, 0, 0 ); - } + public AnvilSouthAddon(Serial serial) : base(serial) + { + } - public AnvilSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AnvilSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class AnvilSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AnvilSouthAddon(); - public override int LabelNumber => 1044334; // anvil (south) + public class AnvilSouthDeed : BaseAddonDeed + { + [Constructible] + public AnvilSouthDeed() + { + } - [Constructible] - public AnvilSouthDeed() - { - } + public AnvilSouthDeed(Serial serial) : base(serial) + { + } - public AnvilSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AnvilSouthAddon(); + public override int LabelNumber => 1044334; // anvil (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ArcaneBookshelfEastAddon.cs b/Scripts/Items/Addons/ArcaneBookshelfEastAddon.cs index 16de1de09..24e07b41e 100644 --- a/Scripts/Items/Addons/ArcaneBookshelfEastAddon.cs +++ b/Scripts/Items/Addons/ArcaneBookshelfEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ArcaneBookshelfEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ArcaneBookshelfEastDeed(); + public class ArcaneBookshelfEastAddon : BaseAddon + { + [Constructible] + public ArcaneBookshelfEastAddon() + { + AddComponent(new AddonComponent(0x3084), 0, 0, 0); + AddComponent(new AddonComponent(0x3085), -1, 0, 0); + } - [Constructible] - public ArcaneBookshelfEastAddon() - { - AddComponent( new AddonComponent( 0x3084 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3085 ), -1, 0, 0 ); - } + public ArcaneBookshelfEastAddon(Serial serial) : base(serial) + { + } - public ArcaneBookshelfEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ArcaneBookshelfEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ArcaneBookshelfEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ArcaneBookshelfEastAddon(); - public override int LabelNumber => 1073371; // arcane bookshelf (east) + public class ArcaneBookshelfEastDeed : BaseAddonDeed + { + [Constructible] + public ArcaneBookshelfEastDeed() + { + } - [Constructible] - public ArcaneBookshelfEastDeed() - { - } + public ArcaneBookshelfEastDeed(Serial serial) : base(serial) + { + } - public ArcaneBookshelfEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ArcaneBookshelfEastAddon(); + public override int LabelNumber => 1073371; // arcane bookshelf (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ArcaneBookshelfSouthAddon.cs b/Scripts/Items/Addons/ArcaneBookshelfSouthAddon.cs index db4d0ff2d..ca6b394c0 100644 --- a/Scripts/Items/Addons/ArcaneBookshelfSouthAddon.cs +++ b/Scripts/Items/Addons/ArcaneBookshelfSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ArcaneBookshelfSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ArcaneBookshelfSouthDeed(); + public class ArcaneBookshelfSouthAddon : BaseAddon + { + [Constructible] + public ArcaneBookshelfSouthAddon() + { + AddComponent(new AddonComponent(0x3087), 0, 0, 0); + AddComponent(new AddonComponent(0x3086), 0, 1, 0); + } - [Constructible] - public ArcaneBookshelfSouthAddon() - { - AddComponent( new AddonComponent( 0x3087 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3086 ), 0, 1, 0 ); - } + public ArcaneBookshelfSouthAddon(Serial serial) : base(serial) + { + } - public ArcaneBookshelfSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ArcaneBookshelfSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ArcaneBookshelfSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ArcaneBookshelfSouthAddon(); - public override int LabelNumber => 1072871; // arcane bookshelf (south) + public class ArcaneBookshelfSouthDeed : BaseAddonDeed + { + [Constructible] + public ArcaneBookshelfSouthDeed() + { + } - [Constructible] - public ArcaneBookshelfSouthDeed() - { - } + public ArcaneBookshelfSouthDeed(Serial serial) : base(serial) + { + } - public ArcaneBookshelfSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ArcaneBookshelfSouthAddon(); + public override int LabelNumber => 1072871; // arcane bookshelf (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ArcaneCircleAddon.cs b/Scripts/Items/Addons/ArcaneCircleAddon.cs index ae79bceba..41ad4cfd9 100644 --- a/Scripts/Items/Addons/ArcaneCircleAddon.cs +++ b/Scripts/Items/Addons/ArcaneCircleAddon.cs @@ -1,83 +1,81 @@ namespace Server.Items { - public class ArcaneCircleAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ArcaneCircleDeed(); + public class ArcaneCircleAddon : BaseAddon + { + [Constructible] + public ArcaneCircleAddon() + { + AddComponent(new AddonComponent(0x3083), -1, -1, 0); + AddComponent(new AddonComponent(0x3080), -1, 0, 0); + AddComponent(new AddonComponent(0x3082), 0, -1, 0); + AddComponent(new AddonComponent(0x3081), 1, -1, 0); + AddComponent(new AddonComponent(0x307D), -1, 1, 0); + AddComponent(new AddonComponent(0x307F), 0, 0, 0); + AddComponent(new AddonComponent(0x307E), 1, 0, 0); + AddComponent(new AddonComponent(0x307C), 0, 1, 0); + AddComponent(new AddonComponent(0x307B), 1, 1, 0); + } - [Constructible] - public ArcaneCircleAddon() - { - AddComponent( new AddonComponent( 0x3083 ), -1, -1, 0 ); - AddComponent( new AddonComponent( 0x3080 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x3082 ), 0, -1, 0 ); - AddComponent( new AddonComponent( 0x3081 ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0x307D ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0x307F ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x307E ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x307C ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x307B ), 1, 1, 0 ); - } + public ArcaneCircleAddon(Serial serial) : base(serial) + { + } - public ArcaneCircleAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ArcaneCircleDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version - } + writer.WriteEncodedInt(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if ( version == 0 ) - ValidationQueue.Add( this ); - } + if (version == 0) + ValidationQueue.Add(this); + } - public void Validate() - { - foreach ( AddonComponent c in Components ) - { - if ( c.ItemID == 0x3083 ) - { - c.Offset = new Point3D( -1, -1, 0 ); - c.MoveToWorld( new Point3D( X + c.Offset.X, Y + c.Offset.Y, Z + c.Offset.Z ), Map ); - } - } - } - } + public void Validate() + { + foreach (AddonComponent c in Components) + if (c.ItemID == 0x3083) + { + c.Offset = new Point3D(-1, -1, 0); + c.MoveToWorld(new Point3D(X + c.Offset.X, Y + c.Offset.Y, Z + c.Offset.Z), Map); + } + } + } - public class ArcaneCircleDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ArcaneCircleAddon(); - public override int LabelNumber => 1072703; // arcane circle + public class ArcaneCircleDeed : BaseAddonDeed + { + [Constructible] + public ArcaneCircleDeed() + { + } - [Constructible] - public ArcaneCircleDeed() - { - } + public ArcaneCircleDeed(Serial serial) : base(serial) + { + } - public ArcaneCircleDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ArcaneCircleAddon(); + public override int LabelNumber => 1072703; // arcane circle - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ArcanistStatueEastAddon.cs b/Scripts/Items/Addons/ArcanistStatueEastAddon.cs index 68b1c1ad7..c8de0013c 100644 --- a/Scripts/Items/Addons/ArcanistStatueEastAddon.cs +++ b/Scripts/Items/Addons/ArcanistStatueEastAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class ArcanistStatueEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ArcanistStatueEastDeed(); + public class ArcanistStatueEastAddon : BaseAddon + { + [Constructible] + public ArcanistStatueEastAddon() + { + AddComponent(new AddonComponent(0x2D0E), 0, 0, 0); + } - [Constructible] - public ArcanistStatueEastAddon() - { - AddComponent( new AddonComponent( 0x2D0E ), 0, 0, 0 ); - } + public ArcanistStatueEastAddon(Serial serial) : base(serial) + { + } - public ArcanistStatueEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ArcanistStatueEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ArcanistStatueEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ArcanistStatueEastAddon(); - public override int LabelNumber => 1072886; // arcanist statue (east) + public class ArcanistStatueEastDeed : BaseAddonDeed + { + [Constructible] + public ArcanistStatueEastDeed() + { + } - [Constructible] - public ArcanistStatueEastDeed() - { - } + public ArcanistStatueEastDeed(Serial serial) : base(serial) + { + } - public ArcanistStatueEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ArcanistStatueEastAddon(); + public override int LabelNumber => 1072886; // arcanist statue (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ArcanistStatueSouthAddon.cs b/Scripts/Items/Addons/ArcanistStatueSouthAddon.cs index 22e2eec50..a9869c18e 100644 --- a/Scripts/Items/Addons/ArcanistStatueSouthAddon.cs +++ b/Scripts/Items/Addons/ArcanistStatueSouthAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class ArcanistStatueSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ArcanistStatueSouthDeed(); + public class ArcanistStatueSouthAddon : BaseAddon + { + [Constructible] + public ArcanistStatueSouthAddon() + { + AddComponent(new AddonComponent(0x2D0F), 0, 0, 0); + } - [Constructible] - public ArcanistStatueSouthAddon() - { - AddComponent( new AddonComponent( 0x2D0F ), 0, 0, 0 ); - } + public ArcanistStatueSouthAddon(Serial serial) : base(serial) + { + } - public ArcanistStatueSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ArcanistStatueSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ArcanistStatueSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ArcanistStatueSouthAddon(); - public override int LabelNumber => 1072885; // arcanist statue (south) + public class ArcanistStatueSouthDeed : BaseAddonDeed + { + [Constructible] + public ArcanistStatueSouthDeed() + { + } - [Constructible] - public ArcanistStatueSouthDeed() - { - } + public ArcanistStatueSouthDeed(Serial serial) : base(serial) + { + } - public ArcanistStatueSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ArcanistStatueSouthAddon(); + public override int LabelNumber => 1072885; // arcanist statue (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/BallotBox.cs b/Scripts/Items/Addons/BallotBox.cs index 763c60318..bd39cd5cf 100644 --- a/Scripts/Items/Addons/BallotBox.cs +++ b/Scripts/Items/Addons/BallotBox.cs @@ -1,377 +1,378 @@ using System; -using Server.Multis; +using System.Collections.Generic; using Server.Gumps; +using Server.Multis; using Server.Network; using Server.Prompts; -using System.Collections.Generic; namespace Server.Items { - public class BallotBox : AddonComponent - { - public static readonly int MaxTopicLines = 6; - - public override int LabelNumber => 1041006; // a ballot box - - public string[] Topic { get; private set; } - - public List Yes { get; private set; } - - public List No { get; private set; } - - [Constructible] - public BallotBox() : base( 0x9A8 ) - { - Topic = new string[0]; - Yes = new List(); - No = new List(); - } - - public BallotBox( Serial serial ) : base( serial ) - { - } - - public void ClearTopic() - { - Topic = new string[0]; - - ClearVotes(); - } - - public void AddLineToTopic( string line ) - { - if ( Topic.Length >= MaxTopicLines ) - return; - - string[] newTopic = new string[Topic.Length + 1]; - Topic.CopyTo( newTopic, 0 ); - newTopic[Topic.Length] = line; - - Topic = newTopic; - - ClearVotes(); - } - - public void ClearVotes() - { - Yes.Clear(); - No.Clear(); - } - - public bool IsOwner( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - - BaseHouse house = BaseHouse.FindHouseAt( this ); - return ( house != null && house.IsOwner( from ) ); - } - - public bool HasVoted( Mobile from ) - { - return ( Yes.Contains( from ) || No.Contains( from ) ); - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - SendLocalizedMessageTo( from, 500369 ); // I'm a ballot box, not a container! - return false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - else - { - bool isOwner = IsOwner( from ); - from.SendGump( new InternalGump( this, isOwner ) ); - } - } - - private class InternalGump : Gump - { - private BallotBox m_Box; - - public InternalGump( BallotBox box, bool isOwner ) : base( 110, 70 ) - { - m_Box = box; - - AddBackground( 0, 0, 400, 350, 0xA28 ); - - if ( isOwner ) - AddHtmlLocalized( 0, 15, 400, 35, 1011000, false, false ); //
Ballot Box Owner's Menu
- else - AddHtmlLocalized( 0, 15, 400, 35, 1011001, false, false ); //
Ballot Box -- Vote Here!
- - AddHtmlLocalized( 0, 50, 400, 35, 1011002, false, false ); //
Topic
- - int lineCount = box.Topic.Length; - AddBackground( 25, 90, 350, Math.Max( 20 * lineCount, 20 ), 0x1400 ); - - for ( int i = 0; i < lineCount; i++ ) - { - string line = box.Topic[i]; - - if ( !string.IsNullOrEmpty( line ) ) - AddLabelCropped( 30, 90 + i * 20, 340, 20, 0x3E3, line ); - } - - int yesCount = box.Yes.Count; - int noCount = box.No.Count; - int totalVotes = yesCount + noCount; - - AddHtmlLocalized( 0, 215, 400, 35, 1011003, false, false ); //
votes
- - if ( !isOwner ) - AddButton( 20, 240, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 242, 25, 35, 1011004, false, false ); // aye: - AddLabel( 78, 242, 0x0, $"[{yesCount}]"); - - if ( !isOwner ) - AddButton( 20, 275, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 277, 25, 35, 1011005, false, false ); // nay: - AddLabel( 78, 277, 0x0, $"[{noCount}]"); - - if ( totalVotes > 0 ) - { - AddImageTiled( 130, 242, ( yesCount * 225 ) / totalVotes, 10, 0xD6 ); - AddImageTiled( 130, 277, ( noCount * 225 ) / totalVotes, 10, 0xD6 ); - } - - AddButton( 45, 305, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 308, 40, 35, 1011008, false, false ); // done - - if ( isOwner ) - { - AddButton( 120, 305, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 155, 308, 100, 35, 1011006, false, false ); // change topic - - AddButton( 240, 305, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 275, 308, 300, 100, 1011007, false, false ); // reset votes - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Box.Deleted || info.ButtonID == 0 ) - return; - - Mobile from = sender.Mobile; - - if ( from.Map != m_Box.Map || !from.InRange( m_Box.GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - bool isOwner = m_Box.IsOwner( from ); - - switch ( info.ButtonID ) - { - case 1: // change topic - { - if ( isOwner ) - { - m_Box.ClearTopic(); - - from.SendLocalizedMessage( 500370, "", 0x35 ); // Enter a line of text for your ballot, and hit ENTER. Hit ESC after the last line is entered. - from.Prompt = new TopicPrompt( m_Box ); - } - - break; - } - case 2: // reset votes - { - if ( isOwner ) - { - m_Box.ClearVotes(); - from.SendLocalizedMessage( 500371 ); // Votes zeroed out. - } - - goto default; - } - case 3: // aye - { - if ( !isOwner ) - { - if ( m_Box.HasVoted( from ) ) - { - from.SendLocalizedMessage( 500374 ); // You have already voted on this ballot. - } - else - { - m_Box.Yes.Add( from ); - from.SendLocalizedMessage( 500373 ); // Your vote has been registered. - } - } - - goto default; - } - case 4: // nay - { - if ( !isOwner ) - { - if ( m_Box.HasVoted( from ) ) - { - from.SendLocalizedMessage( 500374 ); // You have already voted on this ballot. - } - else - { - m_Box.No.Add( from ); - from.SendLocalizedMessage( 500373 ); // Your vote has been registered. - } - } - - goto default; - } - default: - { - from.SendGump( new InternalGump( m_Box, isOwner ) ); - break; - } - } - } - } - - private class TopicPrompt : Prompt - { - private BallotBox m_Box; - - public TopicPrompt( BallotBox box ) - { - m_Box = box; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Box.Deleted || !m_Box.IsOwner( from ) ) - return; - - if ( from.Map != m_Box.Map || !from.InRange( m_Box.GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - m_Box.AddLineToTopic( text.TrimEnd() ); - - if ( m_Box.Topic.Length < MaxTopicLines ) - { - from.SendLocalizedMessage( 500377, "", 0x35 ); // Next line or ESC to finish: - from.Prompt = new TopicPrompt( m_Box ); - } - else - { - from.SendLocalizedMessage( 500376, "", 0x35 ); // Ballot entry complete. - from.SendGump( new InternalGump( m_Box, true ) ); - } - } - - public override void OnCancel( Mobile from ) - { - if ( m_Box.Deleted || !m_Box.IsOwner( from ) ) - return; - - if ( from.Map != m_Box.Map || !from.InRange( m_Box.GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - from.SendLocalizedMessage( 500376, "", 0x35 ); // Ballot entry complete. - from.SendGump( new InternalGump( m_Box, true ) ); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.WriteEncodedInt( Topic.Length ); - - for ( int i = 0; i < Topic.Length; i++ ) - writer.Write( (string) Topic[i] ); - - writer.Write( Yes, true ); - writer.Write( No, true ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - Topic = new string[reader.ReadEncodedInt()]; - - for ( int i = 0; i < Topic.Length; i++ ) - Topic[i] = reader.ReadString(); - - Yes = reader.ReadStrongMobileList(); - No = reader.ReadStrongMobileList(); - } - } - - public class BallotBoxAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BallotBoxDeed(); - - public BallotBoxAddon() - { - AddComponent( new BallotBox(), 0, 0, 0 ); - } - - public BallotBoxAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } + public class BallotBox : AddonComponent + { + public static readonly int MaxTopicLines = 6; + + [Constructible] + public BallotBox() : base(0x9A8) + { + Topic = new string[0]; + Yes = new List(); + No = new List(); + } - public class BallotBoxDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BallotBoxAddon(); + public BallotBox(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1044327; // ballot box - - [Constructible] - public BallotBoxDeed() - { - } + public override int LabelNumber => 1041006; // a ballot box - public BallotBoxDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public string[] Topic{ get; private set; } - writer.WriteEncodedInt( 0 ); // version - } + public List Yes{ get; private set; } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public List No{ get; private set; } - int version = reader.ReadEncodedInt(); - } - } -} + public void ClearTopic() + { + Topic = new string[0]; + + ClearVotes(); + } + + public void AddLineToTopic(string line) + { + if (Topic.Length >= MaxTopicLines) + return; + + string[] newTopic = new string[Topic.Length + 1]; + Topic.CopyTo(newTopic, 0); + newTopic[Topic.Length] = line; + + Topic = newTopic; + + ClearVotes(); + } + + public void ClearVotes() + { + Yes.Clear(); + No.Clear(); + } + + public bool IsOwner(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + + BaseHouse house = BaseHouse.FindHouseAt(this); + return house != null && house.IsOwner(from); + } + + public bool HasVoted(Mobile from) + { + return Yes.Contains(from) || No.Contains(from); + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + SendLocalizedMessageTo(from, 500369); // I'm a ballot box, not a container! + return false; + } + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + else + { + bool isOwner = IsOwner(from); + from.SendGump(new InternalGump(this, isOwner)); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(Topic.Length); + + for (int i = 0; i < Topic.Length; i++) + writer.Write(Topic[i]); + + writer.Write(Yes, true); + writer.Write(No, true); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + Topic = new string[reader.ReadEncodedInt()]; + + for (int i = 0; i < Topic.Length; i++) + Topic[i] = reader.ReadString(); + + Yes = reader.ReadStrongMobileList(); + No = reader.ReadStrongMobileList(); + } + + private class InternalGump : Gump + { + private BallotBox m_Box; + + public InternalGump(BallotBox box, bool isOwner) : base(110, 70) + { + m_Box = box; + + AddBackground(0, 0, 400, 350, 0xA28); + + if (isOwner) + AddHtmlLocalized(0, 15, 400, 35, 1011000, false, false); //
Ballot Box Owner's Menu
+ else + AddHtmlLocalized(0, 15, 400, 35, 1011001, false, false); //
Ballot Box -- Vote Here!
+ + AddHtmlLocalized(0, 50, 400, 35, 1011002, false, false); //
Topic
+ + int lineCount = box.Topic.Length; + AddBackground(25, 90, 350, Math.Max(20 * lineCount, 20), 0x1400); + + for (int i = 0; i < lineCount; i++) + { + string line = box.Topic[i]; + + if (!string.IsNullOrEmpty(line)) + AddLabelCropped(30, 90 + i * 20, 340, 20, 0x3E3, line); + } + + int yesCount = box.Yes.Count; + int noCount = box.No.Count; + int totalVotes = yesCount + noCount; + + AddHtmlLocalized(0, 215, 400, 35, 1011003, false, false); //
votes
+ + if (!isOwner) + AddButton(20, 240, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 242, 25, 35, 1011004, false, false); // aye: + AddLabel(78, 242, 0x0, $"[{yesCount}]"); + + if (!isOwner) + AddButton(20, 275, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 277, 25, 35, 1011005, false, false); // nay: + AddLabel(78, 277, 0x0, $"[{noCount}]"); + + if (totalVotes > 0) + { + AddImageTiled(130, 242, yesCount * 225 / totalVotes, 10, 0xD6); + AddImageTiled(130, 277, noCount * 225 / totalVotes, 10, 0xD6); + } + + AddButton(45, 305, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 308, 40, 35, 1011008, false, false); // done + + if (isOwner) + { + AddButton(120, 305, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(155, 308, 100, 35, 1011006, false, false); // change topic + + AddButton(240, 305, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(275, 308, 300, 100, 1011007, false, false); // reset votes + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Box.Deleted || info.ButtonID == 0) + return; + + Mobile from = sender.Mobile; + + if (from.Map != m_Box.Map || !from.InRange(m_Box.GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + bool isOwner = m_Box.IsOwner(from); + + switch (info.ButtonID) + { + case 1: // change topic + { + if (isOwner) + { + m_Box.ClearTopic(); + + from.SendLocalizedMessage(500370, "", + 0x35); // Enter a line of text for your ballot, and hit ENTER. Hit ESC after the last line is entered. + from.Prompt = new TopicPrompt(m_Box); + } + + break; + } + case 2: // reset votes + { + if (isOwner) + { + m_Box.ClearVotes(); + from.SendLocalizedMessage(500371); // Votes zeroed out. + } + + goto default; + } + case 3: // aye + { + if (!isOwner) + { + if (m_Box.HasVoted(from)) + { + from.SendLocalizedMessage(500374); // You have already voted on this ballot. + } + else + { + m_Box.Yes.Add(from); + from.SendLocalizedMessage(500373); // Your vote has been registered. + } + } + + goto default; + } + case 4: // nay + { + if (!isOwner) + { + if (m_Box.HasVoted(from)) + { + from.SendLocalizedMessage(500374); // You have already voted on this ballot. + } + else + { + m_Box.No.Add(from); + from.SendLocalizedMessage(500373); // Your vote has been registered. + } + } + + goto default; + } + default: + { + from.SendGump(new InternalGump(m_Box, isOwner)); + break; + } + } + } + } + + private class TopicPrompt : Prompt + { + private BallotBox m_Box; + + public TopicPrompt(BallotBox box) + { + m_Box = box; + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Box.Deleted || !m_Box.IsOwner(from)) + return; + + if (from.Map != m_Box.Map || !from.InRange(m_Box.GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + m_Box.AddLineToTopic(text.TrimEnd()); + + if (m_Box.Topic.Length < MaxTopicLines) + { + from.SendLocalizedMessage(500377, "", 0x35); // Next line or ESC to finish: + from.Prompt = new TopicPrompt(m_Box); + } + else + { + from.SendLocalizedMessage(500376, "", 0x35); // Ballot entry complete. + from.SendGump(new InternalGump(m_Box, true)); + } + } + + public override void OnCancel(Mobile from) + { + if (m_Box.Deleted || !m_Box.IsOwner(from)) + return; + + if (from.Map != m_Box.Map || !from.InRange(m_Box.GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + from.SendLocalizedMessage(500376, "", 0x35); // Ballot entry complete. + from.SendGump(new InternalGump(m_Box, true)); + } + } + } + + public class BallotBoxAddon : BaseAddon + { + public BallotBoxAddon() + { + AddComponent(new BallotBox(), 0, 0, 0); + } + + public BallotBoxAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new BallotBoxDeed(); + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class BallotBoxDeed : BaseAddonDeed + { + [Constructible] + public BallotBoxDeed() + { + } + + public BallotBoxDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new BallotBoxAddon(); + + public override int LabelNumber => 1044327; // ballot box + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/BaseAddon.cs b/Scripts/Items/Addons/BaseAddon.cs index 580d6aa02..893c33ff5 100644 --- a/Scripts/Items/Addons/BaseAddon.cs +++ b/Scripts/Items/Addons/BaseAddon.cs @@ -4,277 +4,278 @@ using Server.Multis; namespace Server.Items { - public enum AddonFitResult - { - Valid, - Blocked, - NotInHouse, - DoorTooClose, - NoWall, - DoorsNotClosed - } + public enum AddonFitResult + { + Valid, + Blocked, + NotInHouse, + DoorTooClose, + NoWall, + DoorsNotClosed + } - public interface IAddon - { - Item Deed{ get; } + public interface IAddon + { + Item Deed{ get; } - bool CouldFit( IPoint3D p, Map map ); - } + bool CouldFit(IPoint3D p, Map map); + } - public abstract class BaseAddon : Item, IChopable, IAddon - { - #region Mondain's Legacy - private CraftResource m_Resource; + public abstract class BaseAddon : Item, IChopable, IAddon + { + public BaseAddon() : base(1) + { + Movable = false; + Visible = false; - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set - { - if ( m_Resource != value ) - { - m_Resource = value; - Hue = CraftResources.GetHue( m_Resource ); + Components = new List(); + } - InvalidateProperties(); - } - } - } - #endregion + public BaseAddon(Serial serial) : base(serial) + { + } - public void AddComponent( AddonComponent c, int x, int y, int z ) - { - if ( Deleted ) - return; + public virtual bool RetainDeedHue => false; - Components.Add( c ); + public virtual BaseAddonDeed Deed => null; - c.Addon = this; - c.Offset = new Point3D( x, y, z ); - c.MoveToWorld( new Point3D( X + x, Y + y, Z + z ), Map ); - } + public List Components{ get; private set; } - public BaseAddon() : base( 1 ) - { - Movable = false; - Visible = false; + public virtual bool ShareHue => true; - Components = new List(); - } + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + if (base.Hue != value) + { + base.Hue = value; - public virtual bool RetainDeedHue => false; + if (!Deleted && ShareHue && Components != null) + foreach (AddonComponent c in Components) + c.Hue = value; + } + } + } - public virtual void OnChop( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + Item IAddon.Deed => Deed; - if ( house != null && house.IsOwner( from ) && house.Addons.Contains( this ) ) - { - Effects.PlaySound( GetWorldLocation(), Map, 0x3B3 ); - from.SendLocalizedMessage( 500461 ); // You destroy the item. + public bool CouldFit(IPoint3D p, Map map) + { + BaseHouse h = null; + return CouldFit(p, map, null, ref h) == AddonFitResult.Valid; + } - int hue = 0; + public virtual void OnChop(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - if ( RetainDeedHue ) - { - for ( int i = 0; hue == 0 && i < Components.Count; ++i ) - { - AddonComponent c = Components[i]; + if (house != null && house.IsOwner(from) && house.Addons.Contains(this)) + { + Effects.PlaySound(GetWorldLocation(), Map, 0x3B3); + from.SendLocalizedMessage(500461); // You destroy the item. - if ( c.Hue != 0 ) - hue = c.Hue; - } - } + int hue = 0; - Delete(); + if (RetainDeedHue) + for (int i = 0; hue == 0 && i < Components.Count; ++i) + { + AddonComponent c = Components[i]; - house.Addons.Remove( this ); + if (c.Hue != 0) + hue = c.Hue; + } - BaseAddonDeed deed = Deed; + Delete(); - if ( deed != null ) - { - if ( RetainDeedHue ) - deed.Hue = hue; + house.Addons.Remove(this); - from.AddToBackpack( deed ); - } - } - } + BaseAddonDeed deed = Deed; - public virtual BaseAddonDeed Deed => null; + if (deed != null) + { + if (RetainDeedHue) + deed.Hue = hue; - Item IAddon.Deed => Deed; + from.AddToBackpack(deed); + } + } + } - public List Components { get; private set; } + public void AddComponent(AddonComponent c, int x, int y, int z) + { + if (Deleted) + return; - public BaseAddon( Serial serial ) : base( serial ) - { - } + Components.Add(c); - public bool CouldFit( IPoint3D p, Map map ) - { - BaseHouse h = null; - return ( CouldFit( p, map, null, ref h ) == AddonFitResult.Valid ); - } + c.Addon = this; + c.Offset = new Point3D(x, y, z); + c.MoveToWorld(new Point3D(X + x, Y + y, Z + z), Map); + } - public virtual AddonFitResult CouldFit( IPoint3D p, Map map, Mobile from, ref BaseHouse house ) - { - if ( Deleted ) - return AddonFitResult.Blocked; + public virtual AddonFitResult CouldFit(IPoint3D p, Map map, Mobile from, ref BaseHouse house) + { + if (Deleted) + return AddonFitResult.Blocked; - foreach ( AddonComponent c in Components ) - { - Point3D p3D = new Point3D( p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z ); + foreach (AddonComponent c in Components) + { + Point3D p3D = new Point3D(p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z); - if ( !map.CanFit( p3D.X, p3D.Y, p3D.Z, c.ItemData.Height, false, true, ( c.Z == 0 ) ) ) - return AddonFitResult.Blocked; - if ( !CheckHouse( from, p3D, map, c.ItemData.Height, ref house ) ) - return AddonFitResult.NotInHouse; + if (!map.CanFit(p3D.X, p3D.Y, p3D.Z, c.ItemData.Height, false, true, c.Z == 0)) + return AddonFitResult.Blocked; + if (!CheckHouse(from, p3D, map, c.ItemData.Height, ref house)) + return AddonFitResult.NotInHouse; - if ( c.NeedsWall ) - { - Point3D wall = c.WallPosition; + if (c.NeedsWall) + { + Point3D wall = c.WallPosition; - if ( !IsWall( p3D.X + wall.X, p3D.Y + wall.Y, p3D.Z + wall.Z, map ) ) - return AddonFitResult.NoWall; - } - } + if (!IsWall(p3D.X + wall.X, p3D.Y + wall.Y, p3D.Z + wall.Z, map)) + return AddonFitResult.NoWall; + } + } - ArrayList doors = house.Doors; + ArrayList doors = house.Doors; - for ( int i = 0; i < doors.Count; ++i ) - { - BaseDoor door = doors[i] as BaseDoor; + for (int i = 0; i < doors.Count; ++i) + { + BaseDoor door = doors[i] as BaseDoor; - Point3D doorLoc = door.GetWorldLocation(); - int doorHeight = door.ItemData.CalcHeight; + Point3D doorLoc = door.GetWorldLocation(); + int doorHeight = door.ItemData.CalcHeight; - foreach ( AddonComponent c in Components ) - { - Point3D addonLoc = new Point3D( p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z ); - int addonHeight = c.ItemData.CalcHeight; + foreach (AddonComponent c in Components) + { + Point3D addonLoc = new Point3D(p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z); + int addonHeight = c.ItemData.CalcHeight; - if ( Utility.InRange( doorLoc, addonLoc, 1 ) && (addonLoc.Z == doorLoc.Z || ((addonLoc.Z + addonHeight) > doorLoc.Z && (doorLoc.Z + doorHeight) > addonLoc.Z)) ) - return AddonFitResult.DoorTooClose; - } - } + if (Utility.InRange(doorLoc, addonLoc, 1) && + (addonLoc.Z == doorLoc.Z || + addonLoc.Z + addonHeight > doorLoc.Z && doorLoc.Z + doorHeight > addonLoc.Z)) + return AddonFitResult.DoorTooClose; + } + } - return AddonFitResult.Valid; - } + return AddonFitResult.Valid; + } - public static bool CheckHouse( Mobile from, Point3D p, Map map, int height, ref BaseHouse house ) - { - house = BaseHouse.FindHouseAt( p, map, height ); + public static bool CheckHouse(Mobile from, Point3D p, Map map, int height, ref BaseHouse house) + { + house = BaseHouse.FindHouseAt(p, map, height); - if ( house == null || ( from != null && !house.IsOwner( from ) ) ) - return false; + if (house == null || from != null && !house.IsOwner(from)) + return false; - return true; - } + return true; + } - public static bool IsWall( int x, int y, int z, Map map ) - { - if ( map == null ) - return false; + public static bool IsWall(int x, int y, int z, Map map) + { + if (map == null) + return false; - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y, true ); + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y, true); - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile t = tiles[i]; - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile t = tiles[i]; + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - if ( (id.Flags & TileFlag.Wall) != 0 && (z + 16) > t.Z && (t.Z + t.Height) > z ) - return true; - } + if ((id.Flags & TileFlag.Wall) != 0 && z + 16 > t.Z && t.Z + t.Height > z) + return true; + } - return false; - } + return false; + } - public virtual void OnComponentLoaded( AddonComponent c ) - { - } + public virtual void OnComponentLoaded(AddonComponent c) + { + } - public virtual void OnComponentUsed( AddonComponent c, Mobile from ) - { - } + public virtual void OnComponentUsed(AddonComponent c, Mobile from) + { + } - public override void OnLocationChange( Point3D oldLoc ) - { - if ( Deleted ) - return; + public override void OnLocationChange(Point3D oldLoc) + { + if (Deleted) + return; - foreach ( AddonComponent c in Components ) - c.Location = new Point3D( X + c.Offset.X, Y + c.Offset.Y, Z + c.Offset.Z ); - } + foreach (AddonComponent c in Components) + c.Location = new Point3D(X + c.Offset.X, Y + c.Offset.Y, Z + c.Offset.Z); + } - public override void OnMapChange() - { - if ( Deleted ) - return; + public override void OnMapChange() + { + if (Deleted) + return; - foreach ( AddonComponent c in Components ) - c.Map = Map; - } + foreach (AddonComponent c in Components) + c.Map = Map; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - foreach ( AddonComponent c in Components ) - c.Delete(); - } + foreach (AddonComponent c in Components) + c.Delete(); + } - public virtual bool ShareHue => true; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set - { - if ( base.Hue != value ) - { - base.Hue = value; + writer.Write(1); // version - if ( !Deleted && ShareHue && Components != null ) - { - foreach ( AddonComponent c in Components ) - c.Hue = value; - } - } - } - } + writer.WriteItemList(Components); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 1 ); // version + int version = reader.ReadInt(); - writer.WriteItemList( Components ); - } + switch (version) + { + case 1: + case 0: + { + Components = reader.ReadStrongItemList(); + break; + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (version < 1 && Weight == 0) + Weight = -1; + } - int version = reader.ReadInt(); + #region Mondain's Legacy - switch ( version ) - { - case 1: - case 0: - { - Components = reader.ReadStrongItemList(); - break; - } - } + private CraftResource m_Resource; - if ( version < 1 && Weight == 0 ) - Weight = -1; - } - } -} + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + if (m_Resource != value) + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + + InvalidateProperties(); + } + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/BaseAddonContainer.cs b/Scripts/Items/Addons/BaseAddonContainer.cs index 470d7e401..50439fc96 100644 --- a/Scripts/Items/Addons/BaseAddonContainer.cs +++ b/Scripts/Items/Addons/BaseAddonContainer.cs @@ -4,289 +4,293 @@ using Server.Multis; namespace Server.Items { - public abstract class BaseAddonContainer : BaseContainer, IChopable, IAddon - { - public override bool DisplayWeight => false; - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set - { - if ( base.Hue != value ) - { - base.Hue = value; - - if ( !Deleted && ShareHue && Components != null ) - { - Hue = value; - - foreach ( AddonContainerComponent c in Components ) - c.Hue = value; - } - } - } - } - - private CraftResource m_Resource; + public abstract class BaseAddonContainer : BaseContainer, IChopable, IAddon + { + private CraftResource m_Resource; + + public BaseAddonContainer(int itemID) : base(itemID) + { + AddonComponent.ApplyLightTo(this); + + Components = new List(); + } + + public BaseAddonContainer(Serial serial) : base(serial) + { + } + + public override bool DisplayWeight => false; + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + if (base.Hue != value) + { + base.Hue = value; + + if (!Deleted && ShareHue && Components != null) + { + Hue = value; + + foreach (AddonContainerComponent c in Components) + c.Hue = value; + } + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + if (m_Resource != value) + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + + InvalidateProperties(); + } + } + } + + public virtual bool RetainDeedHue => false; + public virtual bool NeedsWall => false; + public virtual bool ShareHue => true; + public virtual Point3D WallPosition => Point3D.Zero; + public virtual BaseAddonContainerDeed Deed => null; + + public List Components{ get; private set; } + + Item IAddon.Deed => Deed; + + public bool CouldFit(IPoint3D p, Map map) + { + BaseHouse house = null; + + return CouldFit(p, map, null, ref house) == AddonFitResult.Valid; + } + + public virtual void OnChop(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsOwner(from)) + { + if (!IsSecure) + { + Effects.PlaySound(GetWorldLocation(), Map, 0x3B3); + from.SendLocalizedMessage(500461); // You destroy the item. - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set - { - if ( m_Resource != value ) - { - m_Resource = value; - Hue = CraftResources.GetHue( m_Resource ); - - InvalidateProperties(); - } - } - } - - Item IAddon.Deed => Deed; - - public virtual bool RetainDeedHue => false; - public virtual bool NeedsWall => false; - public virtual bool ShareHue => true; - public virtual Point3D WallPosition => Point3D.Zero; - public virtual BaseAddonContainerDeed Deed => null; + int hue = 0; - public List Components { get; private set; } - - public BaseAddonContainer( int itemID ) : base( itemID ) - { - AddonComponent.ApplyLightTo( this ); - - Components = new List(); - } - - public BaseAddonContainer( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLoc ) - { - base.OnLocationChange( oldLoc ); - - if ( Deleted ) - return; - - foreach ( AddonContainerComponent c in Components ) - c.Location = new Point3D( X + c.Offset.X, Y + c.Offset.Y, Z + c.Offset.Z ); - } - - public override void OnMapChange() - { - base.OnMapChange(); - - if ( Deleted ) - return; - - foreach ( AddonContainerComponent c in Components ) - c.Map = Map; - } - - public override void OnDelete() - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - house?.Addons.Remove( this ); - - base.OnDelete(); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( !CraftResources.IsStandard( m_Resource ) ) - list.Add( CraftResources.GetLocalizationNumber( m_Resource ) ); - } + if (RetainDeedHue) + for (int i = 0; hue == 0 && i < Components.Count; ++i) + { + AddonContainerComponent c = Components[i]; - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - foreach ( AddonContainerComponent c in Components ) - c.Delete(); - } + if (c.Hue != 0) + hue = c.Hue; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + DropItemsToGround(); + + Delete(); + + house.Addons.Remove(this); + + BaseAddonContainerDeed deed = Deed; - writer.Write( (int) 0 ); // version + if (deed != null) + { + deed.Resource = Resource; - writer.WriteItemList( Components ); - writer.Write( (int) m_Resource ); - } + if (RetainDeedHue) + deed.Hue = hue; + + from.AddToBackpack(deed); + } + } + else + { + from.SendLocalizedMessage(1074870); // This item must be unlocked/unsecured before re-deeding it. + } + } + } + + public override void OnLocationChange(Point3D oldLoc) + { + base.OnLocationChange(oldLoc); + + if (Deleted) + return; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + foreach (AddonContainerComponent c in Components) + c.Location = new Point3D(X + c.Offset.X, Y + c.Offset.Y, Z + c.Offset.Z); + } - int version = reader.ReadInt(); + public override void OnMapChange() + { + base.OnMapChange(); - Components = reader.ReadStrongItemList(); - m_Resource = (CraftResource) reader.ReadInt(); + if (Deleted) + return; - AddonComponent.ApplyLightTo( this ); - } + foreach (AddonContainerComponent c in Components) + c.Map = Map; + } - public virtual void DropItemsToGround() - { - for ( int i = Items.Count - 1; i >= 0; i-- ) - Items[ i ].MoveToWorld( Location ); - } + public override void OnDelete() + { + BaseHouse house = BaseHouse.FindHouseAt(this); - public void AddComponent( AddonContainerComponent c, int x, int y, int z ) - { - if ( Deleted ) - return; + house?.Addons.Remove(this); - Components.Add( c ); + base.OnDelete(); + } - c.Addon = this; - c.Offset = new Point3D( x, y, z ); - c.MoveToWorld( new Point3D( X + x, Y + y, Z + z ), Map ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public AddonFitResult CouldFit( IPoint3D p, Map map, Mobile from, ref BaseHouse house ) - { - if ( Deleted ) - return AddonFitResult.Blocked; + if (!CraftResources.IsStandard(m_Resource)) + list.Add(CraftResources.GetLocalizationNumber(m_Resource)); + } - foreach ( AddonContainerComponent c in Components ) - { - Point3D p3D = new Point3D( p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z ); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - if ( !map.CanFit( p3D.X, p3D.Y, p3D.Z, c.ItemData.Height, false, true, ( c.Z == 0 ) ) ) - return AddonFitResult.Blocked; - if ( !BaseAddon.CheckHouse( from, p3D, map, c.ItemData.Height, ref house ) ) - return AddonFitResult.NotInHouse; + foreach (AddonContainerComponent c in Components) + c.Delete(); + } - if ( c.NeedsWall ) - { - Point3D wall = c.WallPosition; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( !BaseAddon.IsWall( p3D.X + wall.X, p3D.Y + wall.Y, p3D.Z + wall.Z, map ) ) - return AddonFitResult.NoWall; - } - } + writer.Write(0); // version - Point3D p3 = new Point3D( p.X, p.Y, p.Z ); + writer.WriteItemList(Components); + writer.Write((int)m_Resource); + } - if ( !map.CanFit( p3.X, p3.Y, p3.Z, ItemData.Height, false, true, ( Z == 0 ) ) ) - return AddonFitResult.Blocked; - if ( !BaseAddon.CheckHouse( from, p3, map, ItemData.Height, ref house ) ) - return AddonFitResult.NotInHouse; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( NeedsWall ) - { - Point3D wall = WallPosition; + int version = reader.ReadInt(); - if ( !BaseAddon.IsWall( p3.X + wall.X, p3.Y + wall.Y, p3.Z + wall.Z, map ) ) - return AddonFitResult.NoWall; - } + Components = reader.ReadStrongItemList(); + m_Resource = (CraftResource)reader.ReadInt(); - if ( house != null ) - { - ArrayList doors = house.Doors; + AddonComponent.ApplyLightTo(this); + } - for ( int i = 0; i < doors.Count; ++i ) - { - BaseDoor door = doors[ i ] as BaseDoor; + public virtual void DropItemsToGround() + { + for (int i = Items.Count - 1; i >= 0; i--) + Items[i].MoveToWorld(Location); + } - if ( door != null && door.Open ) - return AddonFitResult.DoorsNotClosed; + public void AddComponent(AddonContainerComponent c, int x, int y, int z) + { + if (Deleted) + return; - Point3D doorLoc = door.GetWorldLocation(); - int doorHeight = door.ItemData.CalcHeight; + Components.Add(c); - foreach ( AddonContainerComponent c in Components ) - { - Point3D addonLoc = new Point3D( p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z ); - int addonHeight = c.ItemData.CalcHeight; + c.Addon = this; + c.Offset = new Point3D(x, y, z); + c.MoveToWorld(new Point3D(X + x, Y + y, Z + z), Map); + } - if ( Utility.InRange( doorLoc, addonLoc, 1 ) && ( addonLoc.Z == doorLoc.Z || ( ( addonLoc.Z + addonHeight ) > doorLoc.Z && ( doorLoc.Z + doorHeight ) > addonLoc.Z ) ) ) - return AddonFitResult.DoorTooClose; - } + public AddonFitResult CouldFit(IPoint3D p, Map map, Mobile from, ref BaseHouse house) + { + if (Deleted) + return AddonFitResult.Blocked; + + foreach (AddonContainerComponent c in Components) + { + Point3D p3D = new Point3D(p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z); - Point3D addonLo = new Point3D( p.X, p.Y, p.Z ); - int addonHeigh = ItemData.CalcHeight; + if (!map.CanFit(p3D.X, p3D.Y, p3D.Z, c.ItemData.Height, false, true, c.Z == 0)) + return AddonFitResult.Blocked; + if (!BaseAddon.CheckHouse(from, p3D, map, c.ItemData.Height, ref house)) + return AddonFitResult.NotInHouse; - if ( Utility.InRange( doorLoc, addonLo, 1 ) && ( addonLo.Z == doorLoc.Z || ( ( addonLo.Z + addonHeigh ) > doorLoc.Z && ( doorLoc.Z + doorHeight ) > addonLo.Z ) ) ) - return AddonFitResult.DoorTooClose; - } - } + if (c.NeedsWall) + { + Point3D wall = c.WallPosition; - return AddonFitResult.Valid; - } + if (!BaseAddon.IsWall(p3D.X + wall.X, p3D.Y + wall.Y, p3D.Z + wall.Z, map)) + return AddonFitResult.NoWall; + } + } - public bool CouldFit( IPoint3D p, Map map ) - { - BaseHouse house = null; + Point3D p3 = new Point3D(p.X, p.Y, p.Z); - return ( CouldFit( p, map, null, ref house ) == AddonFitResult.Valid ); - } + if (!map.CanFit(p3.X, p3.Y, p3.Z, ItemData.Height, false, true, Z == 0)) + return AddonFitResult.Blocked; + if (!BaseAddon.CheckHouse(from, p3, map, ItemData.Height, ref house)) + return AddonFitResult.NotInHouse; - public virtual void OnChop( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null && house.IsOwner( from ) ) - { - if ( !IsSecure ) - { - Effects.PlaySound( GetWorldLocation(), Map, 0x3B3 ); - from.SendLocalizedMessage( 500461 ); // You destroy the item. + if (NeedsWall) + { + Point3D wall = WallPosition; - int hue = 0; + if (!BaseAddon.IsWall(p3.X + wall.X, p3.Y + wall.Y, p3.Z + wall.Z, map)) + return AddonFitResult.NoWall; + } - if ( RetainDeedHue ) - { - for ( int i = 0; hue == 0 && i < Components.Count; ++i ) - { - AddonContainerComponent c = Components[ i ]; + if (house != null) + { + ArrayList doors = house.Doors; - if ( c.Hue != 0 ) - hue = c.Hue; - } - } + for (int i = 0; i < doors.Count; ++i) + { + BaseDoor door = doors[i] as BaseDoor; - DropItemsToGround(); + if (door != null && door.Open) + return AddonFitResult.DoorsNotClosed; + + Point3D doorLoc = door.GetWorldLocation(); + int doorHeight = door.ItemData.CalcHeight; - Delete(); + foreach (AddonContainerComponent c in Components) + { + Point3D addonLoc = new Point3D(p.X + c.Offset.X, p.Y + c.Offset.Y, p.Z + c.Offset.Z); + int addonHeight = c.ItemData.CalcHeight; + + if (Utility.InRange(doorLoc, addonLoc, 1) && + (addonLoc.Z == doorLoc.Z || + addonLoc.Z + addonHeight > doorLoc.Z && doorLoc.Z + doorHeight > addonLoc.Z)) + return AddonFitResult.DoorTooClose; + } - house.Addons.Remove( this ); + Point3D addonLo = new Point3D(p.X, p.Y, p.Z); + int addonHeigh = ItemData.CalcHeight; - BaseAddonContainerDeed deed = Deed; - - if ( deed != null ) - { - deed.Resource = Resource; - - if ( RetainDeedHue ) - deed.Hue = hue; - - from.AddToBackpack( deed ); - } - } - else - from.SendLocalizedMessage( 1074870 ); // This item must be unlocked/unsecured before re-deeding it. - } - } - - public virtual void OnComponentLoaded( AddonContainerComponent c ) - { - } - - public virtual void OnComponentUsed( AddonContainerComponent c, Mobile from ) - { - } - } -} + if (Utility.InRange(doorLoc, addonLo, 1) && + (addonLo.Z == doorLoc.Z || addonLo.Z + addonHeigh > doorLoc.Z && doorLoc.Z + doorHeight > addonLo.Z)) + return AddonFitResult.DoorTooClose; + } + } + + return AddonFitResult.Valid; + } + + public virtual void OnComponentLoaded(AddonContainerComponent c) + { + } + + public virtual void OnComponentUsed(AddonContainerComponent c, Mobile from) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/BaseAddonContainerDeed.cs b/Scripts/Items/Addons/BaseAddonContainerDeed.cs index 8b2ecd283..ab86868c1 100644 --- a/Scripts/Items/Addons/BaseAddonContainerDeed.cs +++ b/Scripts/Items/Addons/BaseAddonContainerDeed.cs @@ -1,163 +1,167 @@ using System; -using Server.Multis; -using Server.Targeting; using Server.Engines.Craft; +using Server.Multis; +using Server.Spells; +using Server.Targeting; namespace Server.Items { - [Flippable( 0x14F0, 0x14EF )] - public abstract class BaseAddonContainerDeed : Item, ICraftable - { - public abstract BaseAddonContainer Addon{ get; } - - private CraftResource m_Resource; + [Flippable(0x14F0, 0x14EF)] + public abstract class BaseAddonContainerDeed : Item, ICraftable + { + private CraftResource m_Resource; - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set - { - if ( m_Resource != value ) - { - m_Resource = value; - Hue = CraftResources.GetHue( m_Resource ); - - InvalidateProperties(); - } - } - } + public BaseAddonContainerDeed() : base(0x14F0) + { + Weight = 1.0; - public BaseAddonContainerDeed() : base( 0x14F0 ) - { - Weight = 1.0; + if (!Core.AOS) + LootType = LootType.Newbied; + } - if ( !Core.AOS ) - LootType = LootType.Newbied; - } + public BaseAddonContainerDeed(Serial serial) : base(serial) + { + } - public BaseAddonContainerDeed( Serial serial ) : base( serial ) - { - } + public abstract BaseAddonContainer Addon{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + if (m_Resource != value) + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); - writer.Write( (int) 1 ); // version + InvalidateProperties(); + } + } + } - // version 1 - writer.Write( (int) m_Resource ); - } + #region ICraftable - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public virtual int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, + BaseTool tool, CraftItem craftItem, int resHue) + { + Type resourceType = typeRes; - int version = reader.ReadInt(); + if (resourceType == null) + resourceType = craftItem.Resources.GetAt(0).ItemType; - switch ( version ) - { - case 1: - m_Resource = (CraftResource) reader.ReadInt(); - break; - } - } + Resource = CraftResources.GetFromType(resourceType); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - from.Target = new InternalTarget( this ); - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + CraftContext context = craftSystem.GetContext(from); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (context != null && context.DoNotColor) + Hue = 0; - if ( !CraftResources.IsStandard( m_Resource ) ) - list.Add( CraftResources.GetLocalizationNumber( m_Resource ) ); - } + return quality; + } - #region ICraftable - public virtual int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Type resourceType = typeRes; + #endregion - if ( resourceType == null ) - resourceType = craftItem.Resources.GetAt( 0 ).ItemType; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Resource = CraftResources.GetFromType( resourceType ); + writer.Write(1); // version - CraftContext context = craftSystem.GetContext( from ); + // version 1 + writer.Write((int)m_Resource); + } - if ( context != null && context.DoNotColor ) - Hue = 0; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return quality; - } - #endregion + int version = reader.ReadInt(); - private class InternalTarget : Target - { - private BaseAddonContainerDeed m_Deed; + switch (version) + { + case 1: + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } - public InternalTarget( BaseAddonContainerDeed deed ) : base( -1, true, TargetFlags.None ) - { - m_Deed = deed; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + from.Target = new InternalTarget(this); + else + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } - CheckLOS = false; - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - protected override void OnTarget( Mobile from, object targeted ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; + if (!CraftResources.IsStandard(m_Resource)) + list.Add(CraftResources.GetLocalizationNumber(m_Resource)); + } - if ( p == null || map == null || m_Deed.Deleted ) - return; + private class InternalTarget : Target + { + private BaseAddonContainerDeed m_Deed; - if ( m_Deed.IsChildOf( from.Backpack ) ) - { - BaseAddonContainer addon = m_Deed.Addon; - addon.Resource = m_Deed.Resource; + public InternalTarget(BaseAddonContainerDeed deed) : base(-1, true, TargetFlags.None) + { + m_Deed = deed; - Spells.SpellHelper.GetSurfaceTop( ref p ); + CheckLOS = false; + } - BaseHouse house = null; + protected override void OnTarget(Mobile from, object targeted) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; - AddonFitResult res = addon.CouldFit( p, map, from, ref house ); + if (p == null || map == null || m_Deed.Deleted) + return; - if ( res == AddonFitResult.Valid ) - addon.MoveToWorld( new Point3D( p ), map ); - else if ( res == AddonFitResult.Blocked ) - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - else if ( res == AddonFitResult.NotInHouse ) - from.SendLocalizedMessage( 500274 ); // You can only place this in a house that you own! - else if ( res == AddonFitResult.DoorsNotClosed ) - from.SendMessage( "You must close all house doors before placing this." ); - else if ( res == AddonFitResult.DoorTooClose ) - from.SendLocalizedMessage( 500271 ); // You cannot build near the door. - else if ( res == AddonFitResult.NoWall ) - from.SendLocalizedMessage( 500268 ); // This object needs to be mounted on something. - - if ( res == AddonFitResult.Valid ) - { - m_Deed.Delete(); - house.Addons.Add( addon ); - house.AddSecure( from, addon ); - } - else - { - addon.Delete(); - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - } - } -} + if (m_Deed.IsChildOf(from.Backpack)) + { + BaseAddonContainer addon = m_Deed.Addon; + addon.Resource = m_Deed.Resource; + + SpellHelper.GetSurfaceTop(ref p); + + BaseHouse house = null; + + AddonFitResult res = addon.CouldFit(p, map, from, ref house); + + if (res == AddonFitResult.Valid) + addon.MoveToWorld(new Point3D(p), map); + else if (res == AddonFitResult.Blocked) + from.SendLocalizedMessage(500269); // You cannot build that there. + else if (res == AddonFitResult.NotInHouse) + from.SendLocalizedMessage(500274); // You can only place this in a house that you own! + else if (res == AddonFitResult.DoorsNotClosed) + from.SendMessage("You must close all house doors before placing this."); + else if (res == AddonFitResult.DoorTooClose) + from.SendLocalizedMessage(500271); // You cannot build near the door. + else if (res == AddonFitResult.NoWall) + from.SendLocalizedMessage(500268); // This object needs to be mounted on something. + + if (res == AddonFitResult.Valid) + { + m_Deed.Delete(); + house.Addons.Add(addon); + house.AddSecure(from, addon); + } + else + { + addon.Delete(); + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/BaseAddonDeed.cs b/Scripts/Items/Addons/BaseAddonDeed.cs index 712bc7d55..4a068bc53 100644 --- a/Scripts/Items/Addons/BaseAddonDeed.cs +++ b/Scripts/Items/Addons/BaseAddonDeed.cs @@ -1,126 +1,128 @@ using Server.Multis; +using Server.Spells; using Server.Targeting; namespace Server.Items { - [Flippable( 0x14F0, 0x14EF )] - public abstract class BaseAddonDeed : Item - { - public abstract BaseAddon Addon{ get; - } + [Flippable(0x14F0, 0x14EF)] + public abstract class BaseAddonDeed : Item + { + public BaseAddonDeed() : base(0x14F0) + { + Weight = 1.0; - #region Mondain's Legacy - private CraftResource m_Resource; + if (!Core.AOS) + LootType = LootType.Newbied; + } - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set - { - if ( m_Resource != value ) - { - m_Resource = value; - Hue = CraftResources.GetHue( m_Resource ); + public BaseAddonDeed(Serial serial) : base(serial) + { + } - InvalidateProperties(); - } - } - } - #endregion + public abstract BaseAddon Addon{ get; } - public BaseAddonDeed() : base( 0x14F0 ) - { - Weight = 1.0; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( !Core.AOS ) - LootType = LootType.Newbied; - } + writer.Write(0); // version + } - public BaseAddonDeed( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); - writer.Write( (int) 0 ); // version - } + if (Weight == 0.0) + Weight = 1.0; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + from.Target = new InternalTarget(this); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } - int version = reader.ReadInt(); + private class InternalTarget : Target + { + private BaseAddonDeed m_Deed; - if ( Weight == 0.0 ) - Weight = 1.0; - } + public InternalTarget(BaseAddonDeed deed) : base(-1, true, TargetFlags.None) + { + m_Deed = deed; - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - from.Target = new InternalTarget( this ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + CheckLOS = false; + } - private class InternalTarget : Target - { - private BaseAddonDeed m_Deed; + protected override void OnTarget(Mobile from, object targeted) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; - public InternalTarget( BaseAddonDeed deed ) : base( -1, true, TargetFlags.None ) - { - m_Deed = deed; + if (p == null || map == null || m_Deed.Deleted) + return; - CheckLOS = false; - } + if (m_Deed.IsChildOf(from.Backpack)) + { + BaseAddon addon = m_Deed.Addon; - protected override void OnTarget( Mobile from, object targeted ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; + SpellHelper.GetSurfaceTop(ref p); - if ( p == null || map == null || m_Deed.Deleted ) - return; + BaseHouse house = null; - if ( m_Deed.IsChildOf( from.Backpack ) ) - { - BaseAddon addon = m_Deed.Addon; + AddonFitResult res = addon.CouldFit(p, map, from, ref house); - Spells.SpellHelper.GetSurfaceTop( ref p ); + if (res == AddonFitResult.Valid) + addon.MoveToWorld(new Point3D(p), map); + else if (res == AddonFitResult.Blocked) + from.SendLocalizedMessage(500269); // You cannot build that there. + else if (res == AddonFitResult.NotInHouse) + from.SendLocalizedMessage(500274); // You can only place this in a house that you own! + else if (res == AddonFitResult.DoorTooClose) + from.SendLocalizedMessage(500271); // You cannot build near the door. + else if (res == AddonFitResult.NoWall) + from.SendLocalizedMessage(500268); // This object needs to be mounted on something. - BaseHouse house = null; + if (res == AddonFitResult.Valid) + { + m_Deed.Delete(); + house.Addons.Add(addon); + } + else + { + addon.Delete(); + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } - AddonFitResult res = addon.CouldFit( p, map, from, ref house ); + #region Mondain's Legacy - if ( res == AddonFitResult.Valid ) - addon.MoveToWorld( new Point3D( p ), map ); - else if ( res == AddonFitResult.Blocked ) - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - else if ( res == AddonFitResult.NotInHouse ) - from.SendLocalizedMessage( 500274 ); // You can only place this in a house that you own! - else if ( res == AddonFitResult.DoorTooClose ) - from.SendLocalizedMessage( 500271 ); // You cannot build near the door. - else if ( res == AddonFitResult.NoWall ) - from.SendLocalizedMessage( 500268 ); // This object needs to be mounted on something. - - if ( res == AddonFitResult.Valid ) - { - m_Deed.Delete(); - house.Addons.Add( addon ); - } - else - { - addon.Delete(); - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - } - } + private CraftResource m_Resource; + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + if (m_Resource != value) + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + + InvalidateProperties(); + } + } + } + + #endregion + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/BearRugs.cs b/Scripts/Items/Addons/BearRugs.cs index 84c1cd1a7..b561329f3 100644 --- a/Scripts/Items/Addons/BearRugs.cs +++ b/Scripts/Items/Addons/BearRugs.cs @@ -1,266 +1,266 @@ namespace Server.Items { - public class BrownBearRugEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrownBearRugEastDeed(); + public class BrownBearRugEastAddon : BaseAddon + { + [Constructible] + public BrownBearRugEastAddon() + { + AddComponent(new AddonComponent(0x1E40), 1, 1, 0); + AddComponent(new AddonComponent(0x1E41), 1, 0, 0); + AddComponent(new AddonComponent(0x1E42), 1, -1, 0); + AddComponent(new AddonComponent(0x1E43), 0, -1, 0); + AddComponent(new AddonComponent(0x1E44), 0, 0, 0); + AddComponent(new AddonComponent(0x1E45), 0, 1, 0); + AddComponent(new AddonComponent(0x1E46), -1, 1, 0); + AddComponent(new AddonComponent(0x1E47), -1, 0, 0); + AddComponent(new AddonComponent(0x1E48), -1, -1, 0); + } - [Constructible] - public BrownBearRugEastAddon() - { - AddComponent( new AddonComponent( 0x1E40 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E41 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E42 ), 1,-1, 0 ); - AddComponent( new AddonComponent( 0x1E43 ), 0,-1, 0 ); - AddComponent( new AddonComponent( 0x1E44 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1E45 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1E46 ),-1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E47 ),-1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E48 ),-1,-1, 0 ); - } + public BrownBearRugEastAddon(Serial serial) : base(serial) + { + } - public BrownBearRugEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrownBearRugEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BrownBearRugEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrownBearRugEastAddon(); - public override int LabelNumber => 1049397; // a brown bear rug deed facing east + public class BrownBearRugEastDeed : BaseAddonDeed + { + [Constructible] + public BrownBearRugEastDeed() + { + } - [Constructible] - public BrownBearRugEastDeed() - { - } + public BrownBearRugEastDeed(Serial serial) : base(serial) + { + } - public BrownBearRugEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrownBearRugEastAddon(); + public override int LabelNumber => 1049397; // a brown bear rug deed facing east - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BrownBearRugSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrownBearRugSouthDeed(); + public class BrownBearRugSouthAddon : BaseAddon + { + [Constructible] + public BrownBearRugSouthAddon() + { + AddComponent(new AddonComponent(0x1E36), 1, 1, 0); + AddComponent(new AddonComponent(0x1E37), 0, 1, 0); + AddComponent(new AddonComponent(0x1E38), -1, 1, 0); + AddComponent(new AddonComponent(0x1E39), -1, 0, 0); + AddComponent(new AddonComponent(0x1E3A), 0, 0, 0); + AddComponent(new AddonComponent(0x1E3B), 1, 0, 0); + AddComponent(new AddonComponent(0x1E3C), 1, -1, 0); + AddComponent(new AddonComponent(0x1E3D), 0, -1, 0); + AddComponent(new AddonComponent(0x1E3E), -1, -1, 0); + } - [Constructible] - public BrownBearRugSouthAddon() - { - AddComponent( new AddonComponent( 0x1E36 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E37 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1E38 ),-1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E39 ),-1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E3A ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1E3B ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E3C ), 1,-1, 0 ); - AddComponent( new AddonComponent( 0x1E3D ), 0,-1, 0 ); - AddComponent( new AddonComponent( 0x1E3E ),-1,-1, 0 ); - } + public BrownBearRugSouthAddon(Serial serial) : base(serial) + { + } - public BrownBearRugSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrownBearRugSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BrownBearRugSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrownBearRugSouthAddon(); - public override int LabelNumber => 1049398; // a brown bear rug deed facing south + public class BrownBearRugSouthDeed : BaseAddonDeed + { + [Constructible] + public BrownBearRugSouthDeed() + { + } - [Constructible] - public BrownBearRugSouthDeed() - { - } + public BrownBearRugSouthDeed(Serial serial) : base(serial) + { + } - public BrownBearRugSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrownBearRugSouthAddon(); + public override int LabelNumber => 1049398; // a brown bear rug deed facing south - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PolarBearRugEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PolarBearRugEastDeed(); + public class PolarBearRugEastAddon : BaseAddon + { + [Constructible] + public PolarBearRugEastAddon() + { + AddComponent(new AddonComponent(0x1E53), 1, 1, 0); + AddComponent(new AddonComponent(0x1E54), 1, 0, 0); + AddComponent(new AddonComponent(0x1E55), 1, -1, 0); + AddComponent(new AddonComponent(0x1E56), 0, -1, 0); + AddComponent(new AddonComponent(0x1E57), 0, 0, 0); + AddComponent(new AddonComponent(0x1E58), 0, 1, 0); + AddComponent(new AddonComponent(0x1E59), -1, 1, 0); + AddComponent(new AddonComponent(0x1E5A), -1, 0, 0); + AddComponent(new AddonComponent(0x1E5B), -1, -1, 0); + } - [Constructible] - public PolarBearRugEastAddon() - { - AddComponent( new AddonComponent( 0x1E53 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E54 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E55 ), 1,-1, 0 ); - AddComponent( new AddonComponent( 0x1E56 ), 0,-1, 0 ); - AddComponent( new AddonComponent( 0x1E57 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1E58 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1E59 ),-1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E5A ),-1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E5B ),-1,-1, 0 ); - } + public PolarBearRugEastAddon(Serial serial) : base(serial) + { + } - public PolarBearRugEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PolarBearRugEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PolarBearRugEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PolarBearRugEastAddon(); - public override int LabelNumber => 1049399; // a polar bear rug deed facing east + public class PolarBearRugEastDeed : BaseAddonDeed + { + [Constructible] + public PolarBearRugEastDeed() + { + } - [Constructible] - public PolarBearRugEastDeed() - { - } + public PolarBearRugEastDeed(Serial serial) : base(serial) + { + } - public PolarBearRugEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PolarBearRugEastAddon(); + public override int LabelNumber => 1049399; // a polar bear rug deed facing east - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PolarBearRugSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PolarBearRugSouthDeed(); + public class PolarBearRugSouthAddon : BaseAddon + { + [Constructible] + public PolarBearRugSouthAddon() + { + AddComponent(new AddonComponent(0x1E49), 1, 1, 0); + AddComponent(new AddonComponent(0x1E4A), 0, 1, 0); + AddComponent(new AddonComponent(0x1E4B), -1, 1, 0); + AddComponent(new AddonComponent(0x1E4C), -1, 0, 0); + AddComponent(new AddonComponent(0x1E4D), 0, 0, 0); + AddComponent(new AddonComponent(0x1E4E), 1, 0, 0); + AddComponent(new AddonComponent(0x1E4F), 1, -1, 0); + AddComponent(new AddonComponent(0x1E50), 0, -1, 0); + AddComponent(new AddonComponent(0x1E51), -1, -1, 0); + } - [Constructible] - public PolarBearRugSouthAddon() - { - AddComponent( new AddonComponent( 0x1E49 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E4A ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1E4B ),-1, 1, 0 ); - AddComponent( new AddonComponent( 0x1E4C ),-1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E4D ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1E4E ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1E4F ), 1,-1, 0 ); - AddComponent( new AddonComponent( 0x1E50 ), 0,-1, 0 ); - AddComponent( new AddonComponent( 0x1E51 ),-1,-1, 0 ); - } + public PolarBearRugSouthAddon(Serial serial) : base(serial) + { + } - public PolarBearRugSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PolarBearRugSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PolarBearRugSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PolarBearRugSouthAddon(); - public override int LabelNumber => 1049400; // a polar bear rug deed facing south + public class PolarBearRugSouthDeed : BaseAddonDeed + { + [Constructible] + public PolarBearRugSouthDeed() + { + } - [Constructible] - public PolarBearRugSouthDeed() - { - } + public PolarBearRugSouthDeed(Serial serial) : base(serial) + { + } - public PolarBearRugSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PolarBearRugSouthAddon(); + public override int LabelNumber => 1049400; // a polar bear rug deed facing south - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/BloodPentagram.cs b/Scripts/Items/Addons/BloodPentagram.cs index edd11f866..5b0270758 100644 --- a/Scripts/Items/Addons/BloodPentagram.cs +++ b/Scripts/Items/Addons/BloodPentagram.cs @@ -1,67 +1,67 @@ namespace Server.Items { - public class BloodPentagram : BaseAddon - { - [Constructible] - public BloodPentagram () - { - AddComponent( new AddonComponent( 0x1CF9 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1CF8 ), 0, 2, 0 ); - AddComponent( new AddonComponent( 0x1CF7 ), 0, 3, 0 ); - AddComponent( new AddonComponent( 0x1CF6 ), 0, 4, 0 ); - AddComponent( new AddonComponent( 0x1CF5 ), 0, 5, 0 ); + public class BloodPentagram : BaseAddon + { + [Constructible] + public BloodPentagram() + { + AddComponent(new AddonComponent(0x1CF9), 0, 1, 0); + AddComponent(new AddonComponent(0x1CF8), 0, 2, 0); + AddComponent(new AddonComponent(0x1CF7), 0, 3, 0); + AddComponent(new AddonComponent(0x1CF6), 0, 4, 0); + AddComponent(new AddonComponent(0x1CF5), 0, 5, 0); - AddComponent( new AddonComponent( 0x1CFB ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1CFA ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1D09 ), 1, 2, 0 ); - AddComponent( new AddonComponent( 0x1D08 ), 1, 3, 0 ); - AddComponent( new AddonComponent( 0x1D07 ), 1, 4, 0 ); - AddComponent( new AddonComponent( 0x1CF4 ), 1, 5, 0 ); + AddComponent(new AddonComponent(0x1CFB), 1, 0, 0); + AddComponent(new AddonComponent(0x1CFA), 1, 1, 0); + AddComponent(new AddonComponent(0x1D09), 1, 2, 0); + AddComponent(new AddonComponent(0x1D08), 1, 3, 0); + AddComponent(new AddonComponent(0x1D07), 1, 4, 0); + AddComponent(new AddonComponent(0x1CF4), 1, 5, 0); - AddComponent( new AddonComponent( 0x1CFC ), 2, 0, 0 ); - AddComponent( new AddonComponent( 0x1D0A ), 2, 1, 0 ); - AddComponent( new AddonComponent( 0x1D11 ), 2, 2, 0 ); - AddComponent( new AddonComponent( 0x1D10 ), 2, 3, 0 ); - AddComponent( new AddonComponent( 0x1D06 ), 2, 4, 0 ); - AddComponent( new AddonComponent( 0x1CF3 ), 2, 5, 0 ); + AddComponent(new AddonComponent(0x1CFC), 2, 0, 0); + AddComponent(new AddonComponent(0x1D0A), 2, 1, 0); + AddComponent(new AddonComponent(0x1D11), 2, 2, 0); + AddComponent(new AddonComponent(0x1D10), 2, 3, 0); + AddComponent(new AddonComponent(0x1D06), 2, 4, 0); + AddComponent(new AddonComponent(0x1CF3), 2, 5, 0); - AddComponent( new AddonComponent( 0x1CFD ), 3, 0, 0 ); - AddComponent( new AddonComponent( 0x1D0B ), 3, 1, 0 ); - AddComponent( new AddonComponent( 0x1D12 ), 3, 2, 0 ); - AddComponent( new AddonComponent( 0x1D0F ), 3, 3, 0 ); - AddComponent( new AddonComponent( 0x1D05 ), 3, 4, 0 ); - AddComponent( new AddonComponent( 0x1CF2 ), 3, 5, 0 ); + AddComponent(new AddonComponent(0x1CFD), 3, 0, 0); + AddComponent(new AddonComponent(0x1D0B), 3, 1, 0); + AddComponent(new AddonComponent(0x1D12), 3, 2, 0); + AddComponent(new AddonComponent(0x1D0F), 3, 3, 0); + AddComponent(new AddonComponent(0x1D05), 3, 4, 0); + AddComponent(new AddonComponent(0x1CF2), 3, 5, 0); - AddComponent( new AddonComponent( 0x1CFE ), 4, 0, 0 ); - AddComponent( new AddonComponent( 0x1D0C ), 4, 1, 0 ); - AddComponent( new AddonComponent( 0x1D0D ), 4, 2, 0 ); - AddComponent( new AddonComponent( 0x1D0E ), 4, 3, 0 ); - AddComponent( new AddonComponent( 0x1D04 ), 4, 4, 0 ); - AddComponent( new AddonComponent( 0x1CF1 ), 4, 5, 0 ); + AddComponent(new AddonComponent(0x1CFE), 4, 0, 0); + AddComponent(new AddonComponent(0x1D0C), 4, 1, 0); + AddComponent(new AddonComponent(0x1D0D), 4, 2, 0); + AddComponent(new AddonComponent(0x1D0E), 4, 3, 0); + AddComponent(new AddonComponent(0x1D04), 4, 4, 0); + AddComponent(new AddonComponent(0x1CF1), 4, 5, 0); - AddComponent( new AddonComponent( 0x1CFF ), 5, 0, 0 ); - AddComponent( new AddonComponent( 0x1D00 ), 5, 1, 0 ); - AddComponent( new AddonComponent( 0x1D01 ), 5, 2, 0 ); - AddComponent( new AddonComponent( 0x1D02 ), 5, 3, 0 ); - AddComponent( new AddonComponent( 0x1D03 ), 5, 4, 0 ); - } + AddComponent(new AddonComponent(0x1CFF), 5, 0, 0); + AddComponent(new AddonComponent(0x1D00), 5, 1, 0); + AddComponent(new AddonComponent(0x1D01), 5, 2, 0); + AddComponent(new AddonComponent(0x1D02), 5, 3, 0); + AddComponent(new AddonComponent(0x1D03), 5, 4, 0); + } - public BloodPentagram( Serial serial ) : base( serial ) - { - } + public BloodPentagram(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/DartBoard.cs b/Scripts/Items/Addons/DartBoard.cs index fc0b739e5..98b051cf6 100644 --- a/Scripts/Items/Addons/DartBoard.cs +++ b/Scripts/Items/Addons/DartBoard.cs @@ -2,213 +2,213 @@ using Server.Network; namespace Server.Items { - public class DartBoard : AddonComponent - { - public override bool NeedsWall => true; - public override Point3D WallPosition => East ? new Point3D( -1, 0, 0 ) : new Point3D( 0, -1, 0 ); + public class DartBoard : AddonComponent + { + [Constructible] + public DartBoard() : this(true) + { + } - public bool East => ItemID == 0x1E2F; + [Constructible] + public DartBoard(bool east) : base(east ? 0x1E2F : 0x1E2E) + { + } - [Constructible] - public DartBoard() : this( true ) - { - } + public DartBoard(Serial serial) : base(serial) + { + } - [Constructible] - public DartBoard( bool east ) : base( east ? 0x1E2F : 0x1E2E ) - { - } + public override bool NeedsWall => true; + public override Point3D WallPosition => East ? new Point3D(-1, 0, 0) : new Point3D(0, -1, 0); - public DartBoard( Serial serial ) : base( serial ) - { - } + public bool East => ItemID == 0x1E2F; - public override void OnDoubleClick( Mobile from ) - { - Direction dir; - if ( from.Location != Location ) - dir = from.GetDirectionTo( this ); - else if ( East ) - dir = Direction.West; - else - dir = Direction.North; + public override void OnDoubleClick(Mobile from) + { + Direction dir; + if (from.Location != Location) + dir = from.GetDirectionTo(this); + else if (East) + dir = Direction.West; + else + dir = Direction.North; - from.Direction = dir; + from.Direction = dir; - bool canThrow; + bool canThrow; - if ( !from.InRange( this, 4 ) || !from.InLOS( this ) ) - canThrow = false; - else if ( East ) - canThrow = ( dir == Direction.Left || dir == Direction.West || dir == Direction.Up ); - else - canThrow = ( dir == Direction.Up || dir == Direction.North || dir == Direction.Right ); + if (!from.InRange(this, 4) || !from.InLOS(this)) + canThrow = false; + else if (East) + canThrow = dir == Direction.Left || dir == Direction.West || dir == Direction.Up; + else + canThrow = dir == Direction.Up || dir == Direction.North || dir == Direction.Right; - if ( canThrow ) - Throw( from ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + if (canThrow) + Throw(from); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public void Throw( Mobile from ) - { - if ( !(from.Weapon is BaseKnife knife) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500751 ); // Try holding a knife... - return; - } + public void Throw(Mobile from) + { + if (!(from.Weapon is BaseKnife knife)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 500751); // Try holding a knife... + return; + } - from.Animate( from.Mounted ? 26 : 9, 7, 1, true, false, 0 ); - from.MovingEffect( this, knife.ItemID, 7, 1, false, false ); - from.PlaySound( 0x238 ); + from.Animate(from.Mounted ? 26 : 9, 7, 1, true, false, 0); + from.MovingEffect(this, knife.ItemID, 7, 1, false, false); + from.PlaySound(0x238); - double rand = Utility.RandomDouble(); + double rand = Utility.RandomDouble(); - int message; - if ( rand < 0.05 ) - message = 500752; // BULLSEYE! 50 Points! - else if ( rand < 0.20 ) - message = 500753; // Just missed the center! 20 points. - else if ( rand < 0.45 ) - message = 500754; // 10 point shot. - else if ( rand < 0.70 ) - message = 500755; // 5 pointer. - else if ( rand < 0.85 ) - message = 500756; // 1 point. Bad throw. - else - message = 500757; // Missed. + int message; + if (rand < 0.05) + message = 500752; // BULLSEYE! 50 Points! + else if (rand < 0.20) + message = 500753; // Just missed the center! 20 points. + else if (rand < 0.45) + message = 500754; // 10 point shot. + else if (rand < 0.70) + message = 500755; // 5 pointer. + else if (rand < 0.85) + message = 500756; // 1 point. Bad throw. + else + message = 500757; // Missed. - PublicOverheadMessage( MessageType.Regular, 0x3B2, message ); - } + PublicOverheadMessage(MessageType.Regular, 0x3B2, message); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class DartBoardEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new DartBoardEastDeed(); + public class DartBoardEastAddon : BaseAddon + { + public DartBoardEastAddon() + { + AddComponent(new DartBoard(true), 0, 0, 0); + } - public DartBoardEastAddon() - { - AddComponent( new DartBoard( true ), 0, 0, 0 ); - } + public DartBoardEastAddon(Serial serial) : base(serial) + { + } - public DartBoardEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new DartBoardEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class DartBoardEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new DartBoardEastAddon(); + public class DartBoardEastDeed : BaseAddonDeed + { + [Constructible] + public DartBoardEastDeed() + { + } - public override int LabelNumber => 1044326; // dartboard (east) + public DartBoardEastDeed(Serial serial) : base(serial) + { + } - [Constructible] - public DartBoardEastDeed() - { - } + public override BaseAddon Addon => new DartBoardEastAddon(); - public DartBoardEastDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1044326; // dartboard (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class DartBoardSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new DartBoardSouthDeed(); + public class DartBoardSouthAddon : BaseAddon + { + public DartBoardSouthAddon() + { + AddComponent(new DartBoard(false), 0, 0, 0); + } - public DartBoardSouthAddon() - { - AddComponent( new DartBoard( false ), 0, 0, 0 ); - } + public DartBoardSouthAddon(Serial serial) : base(serial) + { + } - public DartBoardSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new DartBoardSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class DartBoardSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new DartBoardSouthAddon(); + public class DartBoardSouthDeed : BaseAddonDeed + { + [Constructible] + public DartBoardSouthDeed() + { + } - public override int LabelNumber => 1044325; // dartboard (south) + public DartBoardSouthDeed(Serial serial) : base(serial) + { + } - [Constructible] - public DartBoardSouthDeed() - { - } + public override BaseAddon Addon => new DartBoardSouthAddon(); - public DartBoardSouthDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1044325; // dartboard (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenBedEastAddon.cs b/Scripts/Items/Addons/ElvenBedEastAddon.cs index 77718a087..2843267de 100644 --- a/Scripts/Items/Addons/ElvenBedEastAddon.cs +++ b/Scripts/Items/Addons/ElvenBedEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenBedEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenBedEastDeed(); + public class ElvenBedEastAddon : BaseAddon + { + [Constructible] + public ElvenBedEastAddon() + { + AddComponent(new AddonComponent(0x304D), 0, 0, 0); + AddComponent(new AddonComponent(0x304C), 1, 0, 0); + } - [Constructible] - public ElvenBedEastAddon() - { - AddComponent( new AddonComponent( 0x304D ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x304C ), 1, 0, 0 ); - } + public ElvenBedEastAddon(Serial serial) : base(serial) + { + } - public ElvenBedEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenBedEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenBedEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenBedEastAddon(); - public override int LabelNumber => 1072861; // elven bed (east) + public class ElvenBedEastDeed : BaseAddonDeed + { + [Constructible] + public ElvenBedEastDeed() + { + } - [Constructible] - public ElvenBedEastDeed() - { - } + public ElvenBedEastDeed(Serial serial) : base(serial) + { + } - public ElvenBedEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenBedEastAddon(); + public override int LabelNumber => 1072861; // elven bed (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenBedSouthAddon.cs b/Scripts/Items/Addons/ElvenBedSouthAddon.cs index 855a52b11..cf2cfa302 100644 --- a/Scripts/Items/Addons/ElvenBedSouthAddon.cs +++ b/Scripts/Items/Addons/ElvenBedSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenBedSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenBedSouthDeed(); + public class ElvenBedSouthAddon : BaseAddon + { + [Constructible] + public ElvenBedSouthAddon() + { + AddComponent(new AddonComponent(0x3050), 0, 0, 0); + AddComponent(new AddonComponent(0x3051), 0, -1, 0); + } - [Constructible] - public ElvenBedSouthAddon() - { - AddComponent( new AddonComponent( 0x3050 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3051 ), 0, -1, 0 ); - } + public ElvenBedSouthAddon(Serial serial) : base(serial) + { + } - public ElvenBedSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenBedSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenBedSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenBedSouthAddon(); - public override int LabelNumber => 1072860; // elven bed (south) + public class ElvenBedSouthDeed : BaseAddonDeed + { + [Constructible] + public ElvenBedSouthDeed() + { + } - [Constructible] - public ElvenBedSouthDeed() - { - } + public ElvenBedSouthDeed(Serial serial) : base(serial) + { + } - public ElvenBedSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenBedSouthAddon(); + public override int LabelNumber => 1072860; // elven bed (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenDresserEastAddon.cs b/Scripts/Items/Addons/ElvenDresserEastAddon.cs index dc6171063..3c6dc7cf4 100644 --- a/Scripts/Items/Addons/ElvenDresserEastAddon.cs +++ b/Scripts/Items/Addons/ElvenDresserEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenDresserEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenDresserEastDeed(); + public class ElvenDresserEastAddon : BaseAddon + { + [Constructible] + public ElvenDresserEastAddon() + { + AddComponent(new AddonComponent(0x30E4), 0, 0, 0); + AddComponent(new AddonComponent(0x30E3), 0, -1, 0); + } - [Constructible] - public ElvenDresserEastAddon() - { - AddComponent( new AddonComponent( 0x30E4 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x30E3 ), 0, -1, 0 ); - } + public ElvenDresserEastAddon(Serial serial) : base(serial) + { + } - public ElvenDresserEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenDresserEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenDresserEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenDresserEastAddon(); - public override int LabelNumber => 1073388; // elven dresser (east) + public class ElvenDresserEastDeed : BaseAddonDeed + { + [Constructible] + public ElvenDresserEastDeed() + { + } - [Constructible] - public ElvenDresserEastDeed() - { - } + public ElvenDresserEastDeed(Serial serial) : base(serial) + { + } - public ElvenDresserEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenDresserEastAddon(); + public override int LabelNumber => 1073388; // elven dresser (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenDresserSouthAddon.cs b/Scripts/Items/Addons/ElvenDresserSouthAddon.cs index 992e869ca..bfaf23664 100644 --- a/Scripts/Items/Addons/ElvenDresserSouthAddon.cs +++ b/Scripts/Items/Addons/ElvenDresserSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenDresserSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenDresserSouthDeed(); + public class ElvenDresserSouthAddon : BaseAddon + { + [Constructible] + public ElvenDresserSouthAddon() + { + AddComponent(new AddonComponent(0x30E5), 0, 0, 0); + AddComponent(new AddonComponent(0x30E6), 1, 0, 0); + } - [Constructible] - public ElvenDresserSouthAddon() - { - AddComponent( new AddonComponent( 0x30E5 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x30E6 ), 1, 0, 0 ); - } + public ElvenDresserSouthAddon(Serial serial) : base(serial) + { + } - public ElvenDresserSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenDresserSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenDresserSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenDresserSouthAddon(); - public override int LabelNumber => 1072864; // elven dresser (south) + public class ElvenDresserSouthDeed : BaseAddonDeed + { + [Constructible] + public ElvenDresserSouthDeed() + { + } - [Constructible] - public ElvenDresserSouthDeed() - { - } + public ElvenDresserSouthDeed(Serial serial) : base(serial) + { + } - public ElvenDresserSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenDresserSouthAddon(); + public override int LabelNumber => 1072864; // elven dresser (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenForgeAddon.cs b/Scripts/Items/Addons/ElvenForgeAddon.cs index 7f3e092d6..fcf124189 100644 --- a/Scripts/Items/Addons/ElvenForgeAddon.cs +++ b/Scripts/Items/Addons/ElvenForgeAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class ElvenForgeAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenForgeDeed(); + public class ElvenForgeAddon : BaseAddon + { + [Constructible] + public ElvenForgeAddon() + { + AddComponent(new AddonComponent(0x2DD8), 0, 0, 0); + } - [Constructible] - public ElvenForgeAddon() - { - AddComponent( new AddonComponent( 0x2DD8 ), 0, 0, 0 ); - } + public ElvenForgeAddon(Serial serial) : base(serial) + { + } - public ElvenForgeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenForgeDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenForgeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenForgeAddon(); - public override int LabelNumber => 1072875; // squirrel statue (east) + public class ElvenForgeDeed : BaseAddonDeed + { + [Constructible] + public ElvenForgeDeed() + { + } - [Constructible] - public ElvenForgeDeed() - { - } + public ElvenForgeDeed(Serial serial) : base(serial) + { + } - public ElvenForgeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenForgeAddon(); + public override int LabelNumber => 1072875; // squirrel statue (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenLoveseatEastAddon.cs b/Scripts/Items/Addons/ElvenLoveseatEastAddon.cs index 9d3911261..09189012b 100644 --- a/Scripts/Items/Addons/ElvenLoveseatEastAddon.cs +++ b/Scripts/Items/Addons/ElvenLoveseatEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenLoveseatEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenLoveseatEastDeed(); + public class ElvenLoveseatEastAddon : BaseAddon + { + [Constructible] + public ElvenLoveseatEastAddon() + { + AddComponent(new AddonComponent(0x3089), 0, 0, 0); + AddComponent(new AddonComponent(0x3088), 1, 0, 0); + } - [Constructible] - public ElvenLoveseatEastAddon() - { - AddComponent( new AddonComponent( 0x3089 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3088 ), 1, 0, 0 ); - } + public ElvenLoveseatEastAddon(Serial serial) : base(serial) + { + } - public ElvenLoveseatEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenLoveseatEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenLoveseatEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenLoveseatEastAddon(); - public override int LabelNumber => 1073372; // elven loveseat (east) + public class ElvenLoveseatEastDeed : BaseAddonDeed + { + [Constructible] + public ElvenLoveseatEastDeed() + { + } - [Constructible] - public ElvenLoveseatEastDeed() - { - } + public ElvenLoveseatEastDeed(Serial serial) : base(serial) + { + } - public ElvenLoveseatEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenLoveseatEastAddon(); + public override int LabelNumber => 1073372; // elven loveseat (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenLoveseatSouthAddon.cs b/Scripts/Items/Addons/ElvenLoveseatSouthAddon.cs index 06da1b577..c8e8dadd7 100644 --- a/Scripts/Items/Addons/ElvenLoveseatSouthAddon.cs +++ b/Scripts/Items/Addons/ElvenLoveseatSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenLoveseatSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenLoveseatSouthDeed(); + public class ElvenLoveseatSouthAddon : BaseAddon + { + [Constructible] + public ElvenLoveseatSouthAddon() + { + AddComponent(new AddonComponent(0x308A), 0, 0, 0); + AddComponent(new AddonComponent(0x308B), 0, -1, 0); + } - [Constructible] - public ElvenLoveseatSouthAddon() - { - AddComponent( new AddonComponent( 0x308A ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x308B ), 0, -1, 0 ); - } + public ElvenLoveseatSouthAddon(Serial serial) : base(serial) + { + } - public ElvenLoveseatSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenLoveseatSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenLoveseatSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenLoveseatSouthAddon(); - public override int LabelNumber => 1072867; // elven loveseat (south) + public class ElvenLoveseatSouthDeed : BaseAddonDeed + { + [Constructible] + public ElvenLoveseatSouthDeed() + { + } - [Constructible] - public ElvenLoveseatSouthDeed() - { - } + public ElvenLoveseatSouthDeed(Serial serial) : base(serial) + { + } - public ElvenLoveseatSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenLoveseatSouthAddon(); + public override int LabelNumber => 1072867; // elven loveseat (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenSpinningwheelEastAddon.cs b/Scripts/Items/Addons/ElvenSpinningwheelEastAddon.cs index 74570950f..69945e6d2 100644 --- a/Scripts/Items/Addons/ElvenSpinningwheelEastAddon.cs +++ b/Scripts/Items/Addons/ElvenSpinningwheelEastAddon.cs @@ -2,133 +2,136 @@ using System; namespace Server.Items { - public class ElvenSpinningwheelEastAddon : BaseAddon, ISpinningWheel - { - public override BaseAddonDeed Deed => new ElvenSpinningwheelEastDeed(); + public class ElvenSpinningwheelEastAddon : BaseAddon, ISpinningWheel + { + private Timer m_Timer; - [Constructible] - public ElvenSpinningwheelEastAddon() - { - AddComponent( new AddonComponent( 0x2DD9 ), 0, 0, 0 ); - } + [Constructible] + public ElvenSpinningwheelEastAddon() + { + AddComponent(new AddonComponent(0x2DD9), 0, 0, 0); + } - public ElvenSpinningwheelEastAddon( Serial serial ) : base( serial ) - { - } + public ElvenSpinningwheelEastAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override BaseAddonDeed Deed => new ElvenSpinningwheelEastDeed(); - writer.WriteEncodedInt( 0 ); // version - } + public bool Spinning => m_Timer != null; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void BeginSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer = new SpinTimer(this, callback, from, hue); + m_Timer.Start(); - int version = reader.ReadEncodedInt(); - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x2DD9: + case 0x101C: + case 0x10A4: + ++c.ItemID; + break; + } + } - private Timer m_Timer; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnComponentLoaded( AddonComponent c ) - { - switch ( c.ItemID ) - { - case 0x2E3D: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + writer.WriteEncodedInt(0); // version + } - public bool Spinning => m_Timer != null; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public void BeginSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer = new SpinTimer( this, callback, from, hue ); - m_Timer.Start(); + int version = reader.ReadEncodedInt(); + } - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x2DD9: - case 0x101C: - case 0x10A4: ++c.ItemID; break; - } - } - } + public override void OnComponentLoaded(AddonComponent c) + { + switch (c.ItemID) + { + case 0x2E3D: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } + } - public void EndSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer?.Stop(); + public void EndSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } - callback?.Invoke( this, from, hue ); - } + callback?.Invoke(this, from, hue); + } - private class SpinTimer : Timer - { - private ElvenSpinningwheelEastAddon m_Wheel; - private SpinCallback m_Callback; - private Mobile m_From; - private int m_Hue; + private class SpinTimer : Timer + { + private SpinCallback m_Callback; + private Mobile m_From; + private int m_Hue; + private ElvenSpinningwheelEastAddon m_Wheel; - public SpinTimer( ElvenSpinningwheelEastAddon wheel, SpinCallback callback, Mobile from, int hue ) : base( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Wheel = wheel; - m_Callback = callback; - m_From = from; - m_Hue = hue; - Priority = TimerPriority.TwoFiftyMS; - } + public SpinTimer(ElvenSpinningwheelEastAddon wheel, SpinCallback callback, Mobile from, int hue) : base( + TimeSpan.FromSeconds(3.0)) + { + m_Wheel = wheel; + m_Callback = callback; + m_From = from; + m_Hue = hue; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - m_Wheel.EndSpin( m_Callback, m_From, m_Hue ); - } - } - } + protected override void OnTick() + { + m_Wheel.EndSpin(m_Callback, m_From, m_Hue); + } + } + } - public class ElvenSpinningwheelEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenSpinningwheelEastAddon(); - public override int LabelNumber => 1073393; // elven spinning wheel (east) + public class ElvenSpinningwheelEastDeed : BaseAddonDeed + { + [Constructible] + public ElvenSpinningwheelEastDeed() + { + } - [Constructible] - public ElvenSpinningwheelEastDeed() - { - } + public ElvenSpinningwheelEastDeed(Serial serial) : base(serial) + { + } - public ElvenSpinningwheelEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenSpinningwheelEastAddon(); + public override int LabelNumber => 1073393; // elven spinning wheel (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenSpinningwheelSouthAddon.cs b/Scripts/Items/Addons/ElvenSpinningwheelSouthAddon.cs index f1eec9a81..39bd60ec8 100644 --- a/Scripts/Items/Addons/ElvenSpinningwheelSouthAddon.cs +++ b/Scripts/Items/Addons/ElvenSpinningwheelSouthAddon.cs @@ -2,135 +2,138 @@ using System; namespace Server.Items { - public class ElvenSpinningwheelSouthAddon : BaseAddon, ISpinningWheel - { - public override BaseAddonDeed Deed => new ElvenSpinningwheelSouthDeed(); + public class ElvenSpinningwheelSouthAddon : BaseAddon, ISpinningWheel + { + private Timer m_Timer; - [Constructible] - public ElvenSpinningwheelSouthAddon() - { - AddComponent( new AddonComponent( 0x2DDA ), 0, 0, 0 ); - } + [Constructible] + public ElvenSpinningwheelSouthAddon() + { + AddComponent(new AddonComponent(0x2DDA), 0, 0, 0); + } - public ElvenSpinningwheelSouthAddon( Serial serial ) : base( serial ) - { - } + public ElvenSpinningwheelSouthAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override BaseAddonDeed Deed => new ElvenSpinningwheelSouthDeed(); - writer.WriteEncodedInt( 0 ); // version - } + public bool Spinning => m_Timer != null; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void BeginSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer = new SpinTimer(this, callback, from, hue); + m_Timer.Start(); - int version = reader.ReadEncodedInt(); - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1015: + case 0x1019: + case 0x101C: + case 0x10A4: + ++c.ItemID; + break; + } + } - private Timer m_Timer; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnComponentLoaded( AddonComponent c ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + writer.WriteEncodedInt(0); // version + } - public bool Spinning => m_Timer != null; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public void BeginSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer = new SpinTimer( this, callback, from, hue ); - m_Timer.Start(); + int version = reader.ReadEncodedInt(); + } - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1015: - case 0x1019: - case 0x101C: - case 0x10A4: ++c.ItemID; break; - } - } - } + public override void OnComponentLoaded(AddonComponent c) + { + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } + } - public void EndSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer?.Stop(); + public void EndSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } - callback?.Invoke( this, from, hue ); - } + callback?.Invoke(this, from, hue); + } - private class SpinTimer : Timer - { - private ElvenSpinningwheelSouthAddon m_Wheel; - private SpinCallback m_Callback; - private Mobile m_From; - private int m_Hue; + private class SpinTimer : Timer + { + private SpinCallback m_Callback; + private Mobile m_From; + private int m_Hue; + private ElvenSpinningwheelSouthAddon m_Wheel; - public SpinTimer( ElvenSpinningwheelSouthAddon wheel, SpinCallback callback, Mobile from, int hue ) : base( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Wheel = wheel; - m_Callback = callback; - m_From = from; - m_Hue = hue; - Priority = TimerPriority.TwoFiftyMS; - } + public SpinTimer(ElvenSpinningwheelSouthAddon wheel, SpinCallback callback, Mobile from, int hue) : base( + TimeSpan.FromSeconds(3.0)) + { + m_Wheel = wheel; + m_Callback = callback; + m_From = from; + m_Hue = hue; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - m_Wheel.EndSpin( m_Callback, m_From, m_Hue ); - } - } - } + protected override void OnTick() + { + m_Wheel.EndSpin(m_Callback, m_From, m_Hue); + } + } + } - public class ElvenSpinningwheelSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenSpinningwheelSouthAddon(); - public override int LabelNumber => 1072878; // spinning wheel (south) + public class ElvenSpinningwheelSouthDeed : BaseAddonDeed + { + [Constructible] + public ElvenSpinningwheelSouthDeed() + { + } - [Constructible] - public ElvenSpinningwheelSouthDeed() - { - } + public ElvenSpinningwheelSouthDeed(Serial serial) : base(serial) + { + } - public ElvenSpinningwheelSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenSpinningwheelSouthAddon(); + public override int LabelNumber => 1072878; // spinning wheel (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenStoveEastAddon.cs b/Scripts/Items/Addons/ElvenStoveEastAddon.cs index df39a1a4c..3273e2aa1 100644 --- a/Scripts/Items/Addons/ElvenStoveEastAddon.cs +++ b/Scripts/Items/Addons/ElvenStoveEastAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class ElvenStoveEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenStoveEastDeed(); + public class ElvenStoveEastAddon : BaseAddon + { + [Constructible] + public ElvenStoveEastAddon() + { + AddComponent(new AddonComponent(0x2DDB), 0, 0, 0); + } - [Constructible] - public ElvenStoveEastAddon() - { - AddComponent( new AddonComponent( 0x2DDB ), 0, 0, 0 ); - } + public ElvenStoveEastAddon(Serial serial) : base(serial) + { + } - public ElvenStoveEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenStoveEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenStoveEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenStoveEastAddon(); - public override int LabelNumber => 1073395; // elven oven (east) + public class ElvenStoveEastDeed : BaseAddonDeed + { + [Constructible] + public ElvenStoveEastDeed() + { + } - [Constructible] - public ElvenStoveEastDeed() - { - } + public ElvenStoveEastDeed(Serial serial) : base(serial) + { + } - public ElvenStoveEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenStoveEastAddon(); + public override int LabelNumber => 1073395; // elven oven (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenStoveSouthAddon.cs b/Scripts/Items/Addons/ElvenStoveSouthAddon.cs index 331ea998c..1c8c2b07f 100644 --- a/Scripts/Items/Addons/ElvenStoveSouthAddon.cs +++ b/Scripts/Items/Addons/ElvenStoveSouthAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class ElvenStoveSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenStoveSouthDeed(); + public class ElvenStoveSouthAddon : BaseAddon + { + [Constructible] + public ElvenStoveSouthAddon() + { + AddComponent(new AddonComponent(0x2DDC), 0, 0, 0); + } - [Constructible] - public ElvenStoveSouthAddon() - { - AddComponent( new AddonComponent( 0x2DDC ), 0, 0, 0 ); - } + public ElvenStoveSouthAddon(Serial serial) : base(serial) + { + } - public ElvenStoveSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenStoveSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenStoveSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenStoveSouthAddon(); - public override int LabelNumber => 1073394; // elven oven (south) + public class ElvenStoveSouthDeed : BaseAddonDeed + { + [Constructible] + public ElvenStoveSouthDeed() + { + } - [Constructible] - public ElvenStoveSouthDeed() - { - } + public ElvenStoveSouthDeed(Serial serial) : base(serial) + { + } - public ElvenStoveSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenStoveSouthAddon(); + public override int LabelNumber => 1073394; // elven oven (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenWashbasinEastAddon.cs b/Scripts/Items/Addons/ElvenWashbasinEastAddon.cs index fd7df57f2..535c23659 100644 --- a/Scripts/Items/Addons/ElvenWashbasinEastAddon.cs +++ b/Scripts/Items/Addons/ElvenWashbasinEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenWashBasinEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenWashBasinEastDeed(); + public class ElvenWashBasinEastAddon : BaseAddon + { + [Constructible] + public ElvenWashBasinEastAddon() + { + AddComponent(new AddonComponent(0x30DF), 0, 0, 0); + AddComponent(new AddonComponent(0x30E0), 0, 1, 0); + } - [Constructible] - public ElvenWashBasinEastAddon() - { - AddComponent( new AddonComponent( 0x30DF ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x30E0 ), 0, 1, 0 ); - } + public ElvenWashBasinEastAddon(Serial serial) : base(serial) + { + } - public ElvenWashBasinEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenWashBasinEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenWashBasinEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenWashBasinEastAddon(); - public override int LabelNumber => 1073387; // elven wash basin (east) + public class ElvenWashBasinEastDeed : BaseAddonDeed + { + [Constructible] + public ElvenWashBasinEastDeed() + { + } - [Constructible] - public ElvenWashBasinEastDeed() - { - } + public ElvenWashBasinEastDeed(Serial serial) : base(serial) + { + } - public ElvenWashBasinEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenWashBasinEastAddon(); + public override int LabelNumber => 1073387; // elven wash basin (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ElvenWashbasinSouthAddon.cs b/Scripts/Items/Addons/ElvenWashbasinSouthAddon.cs index 02b287ad6..14e65f073 100644 --- a/Scripts/Items/Addons/ElvenWashbasinSouthAddon.cs +++ b/Scripts/Items/Addons/ElvenWashbasinSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class ElvenWashBasinSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ElvenWashBasinSouthDeed(); + public class ElvenWashBasinSouthAddon : BaseAddon + { + [Constructible] + public ElvenWashBasinSouthAddon() + { + AddComponent(new AddonComponent(0x30E1), 0, 0, 0); + AddComponent(new AddonComponent(0x30E2), 1, 0, 0); + } - [Constructible] - public ElvenWashBasinSouthAddon() - { - AddComponent( new AddonComponent( 0x30E1 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x30E2 ), 1, 0, 0 ); - } + public ElvenWashBasinSouthAddon(Serial serial) : base(serial) + { + } - public ElvenWashBasinSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ElvenWashBasinSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenWashBasinSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ElvenWashBasinSouthAddon(); - public override int LabelNumber => 1072865; // elven wash basin (south) + public class ElvenWashBasinSouthDeed : BaseAddonDeed + { + [Constructible] + public ElvenWashBasinSouthDeed() + { + } - [Constructible] - public ElvenWashBasinSouthDeed() - { - } + public ElvenWashBasinSouthDeed(Serial serial) : base(serial) + { + } - public ElvenWashBasinSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ElvenWashBasinSouthAddon(); + public override int LabelNumber => 1072865; // elven wash basin (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/FancyElvenTableEastAddon.cs b/Scripts/Items/Addons/FancyElvenTableEastAddon.cs index 4450b9491..3edb1ab21 100644 --- a/Scripts/Items/Addons/FancyElvenTableEastAddon.cs +++ b/Scripts/Items/Addons/FancyElvenTableEastAddon.cs @@ -1,62 +1,62 @@ namespace Server.Items { - public class FancyElvenTableEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new FancyElvenTableEastDeed(); + public class FancyElvenTableEastAddon : BaseAddon + { + [Constructible] + public FancyElvenTableEastAddon() + { + AddComponent(new AddonComponent(0x3094), -1, 0, 0); + AddComponent(new AddonComponent(0x3093), 0, 0, 0); + AddComponent(new AddonComponent(0x3092), 1, 0, 0); + } - [Constructible] - public FancyElvenTableEastAddon() - { - AddComponent( new AddonComponent( 0x3094 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x3093 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3092 ), 1, 0, 0 ); - } + public FancyElvenTableEastAddon(Serial serial) : base(serial) + { + } - public FancyElvenTableEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new FancyElvenTableEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class FancyElvenTableEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new FancyElvenTableEastAddon(); - public override int LabelNumber => 1073386; // hardwood table (east) + public class FancyElvenTableEastDeed : BaseAddonDeed + { + [Constructible] + public FancyElvenTableEastDeed() + { + } - [Constructible] - public FancyElvenTableEastDeed() - { - } + public FancyElvenTableEastDeed(Serial serial) : base(serial) + { + } - public FancyElvenTableEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new FancyElvenTableEastAddon(); + public override int LabelNumber => 1073386; // hardwood table (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/FancyElvenTableSouthAddon.cs b/Scripts/Items/Addons/FancyElvenTableSouthAddon.cs index fdc5265f6..4dbfd7fd0 100644 --- a/Scripts/Items/Addons/FancyElvenTableSouthAddon.cs +++ b/Scripts/Items/Addons/FancyElvenTableSouthAddon.cs @@ -1,62 +1,62 @@ namespace Server.Items { - public class FancyElvenTableSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new FancyElvenTableSouthDeed(); + public class FancyElvenTableSouthAddon : BaseAddon + { + [Constructible] + public FancyElvenTableSouthAddon() + { + AddComponent(new AddonComponent(0x3095), 0, 1, 0); + AddComponent(new AddonComponent(0x3096), 0, 0, 0); + AddComponent(new AddonComponent(0x3097), 0, -1, 0); + } - [Constructible] - public FancyElvenTableSouthAddon() - { - AddComponent( new AddonComponent( 0x3095 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x3096 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3097 ), 0, -1, 0 ); - } + public FancyElvenTableSouthAddon(Serial serial) : base(serial) + { + } - public FancyElvenTableSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new FancyElvenTableSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class FancyElvenTableSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new FancyElvenTableSouthAddon(); - public override int LabelNumber => 1073385; // hardwood table (south) + public class FancyElvenTableSouthDeed : BaseAddonDeed + { + [Constructible] + public FancyElvenTableSouthDeed() + { + } - [Constructible] - public FancyElvenTableSouthDeed() - { - } + public FancyElvenTableSouthDeed(Serial serial) : base(serial) + { + } - public FancyElvenTableSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new FancyElvenTableSouthAddon(); + public override int LabelNumber => 1073385; // hardwood table (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/FireColumnAddon.cs b/Scripts/Items/Addons/FireColumnAddon.cs index 7ae634688..6ec1ae4cc 100644 --- a/Scripts/Items/Addons/FireColumnAddon.cs +++ b/Scripts/Items/Addons/FireColumnAddon.cs @@ -1,57 +1,57 @@ namespace Server.Items { - public class FireColumnAddon : BaseAddon - { - public override bool ShareHue => false; + public class FireColumnAddon : BaseAddon + { + [Constructible] + public FireColumnAddon() + : this(false) + { + } - [Constructible] - public FireColumnAddon() - : this( false ) - { - } + [Constructible] + public FireColumnAddon(bool bloody) + { + AddComponent(new AddonComponent(0x3A5), 0, 0, 0); + AddComponent(new AddonComponent(0x3A5), 0, 0, 5); + AddComponent(new AddonComponent(0x3A5), 0, 0, 10); + AddComponent(new AddonComponent(0x3A5), 0, 0, 15); - [Constructible] - public FireColumnAddon( bool bloody ) - { - AddComponent( new AddonComponent( 0x3A5 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3A5 ), 0, 0, 5 ); - AddComponent( new AddonComponent( 0x3A5 ), 0, 0, 10 ); - AddComponent( new AddonComponent( 0x3A5 ), 0, 0, 15 ); + AddComponent(new AddonComponent(0x19BB), 0, 0, 21); + AddComponent(new AddonComponent(0x19AB), 0, 0, 23); - AddComponent( new AddonComponent( 0x19BB ), 0, 0, 21 ); - AddComponent( new AddonComponent( 0x19AB ), 0, 0, 23 ); + if (bloody) + { + AddComponent(new AddonComponent(0x122B), -2, 0, 0); + AddComponent(new AddonComponent(0x122E), 0, -2, 0); + AddComponent(new AddonComponent(0x122D), -1, 1, 0); + AddComponent(new AddonComponent(0x122F), 1, -1, 0); + AddComponent(new AddonComponent(0x122D), 0, 1, 0); + AddComponent(new AddonComponent(0x122A), 1, 0, 0); + AddComponent(new AddonComponent(0x122B), 2, -1, 0); + AddComponent(new AddonComponent(0x122B), 0, 2, 0); + AddComponent(new AddonComponent(0x122E), 1, 1, 0); + } + } - if ( bloody ) - { - AddComponent( new AddonComponent( 0x122B ), -2, 0, 0 ); - AddComponent( new AddonComponent( 0x122E ), 0, -2, 0 ); - AddComponent( new AddonComponent( 0x122D ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0x122F ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0x122D ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x122A ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x122B ), 2, -1, 0 ); - AddComponent( new AddonComponent( 0x122B ), 0, 2, 0 ); - AddComponent( new AddonComponent( 0x122E ), 1, 1, 0 ); - } - } + public FireColumnAddon(Serial serial) + : base(serial) + { + } - public FireColumnAddon( Serial serial ) - : base( serial ) - { - } + public override bool ShareHue => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/FlourMillEastAddon.cs b/Scripts/Items/Addons/FlourMillEastAddon.cs index 96a32bec2..85c895f65 100644 --- a/Scripts/Items/Addons/FlourMillEastAddon.cs +++ b/Scripts/Items/Addons/FlourMillEastAddon.cs @@ -1,211 +1,214 @@ using System; -using Server.Network; using System.Collections.Generic; +using Server.Network; namespace Server.Items { - public interface IFlourMill - { - int MaxFlour{ get; } - int CurFlour{ get; set; } - } + public interface IFlourMill + { + int MaxFlour{ get; } + int CurFlour{ get; set; } + } - public enum FlourMillStage - { - Empty, - Filled, - Working - } + public enum FlourMillStage + { + Empty, + Filled, + Working + } - public class FlourMillEastAddon : BaseAddon, IFlourMill - { - public override BaseAddonDeed Deed => new FlourMillEastDeed(); + public class FlourMillEastAddon : BaseAddon, IFlourMill + { + private static int[][] m_StageTable = + { + new[] { 0x1920, 0x1921, 0x1925 }, + new[] { 0x1922, 0x1923, 0x1926 }, + new[] { 0x1924, 0x1924, 0x1928 } + }; - private int m_Flour; - private Timer m_Timer; + private int m_Flour; + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public int MaxFlour => 2; + [Constructible] + public FlourMillEastAddon() + { + AddComponent(new AddonComponent(0x1920), -1, 0, 0); + AddComponent(new AddonComponent(0x1922), 0, 0, 0); + AddComponent(new AddonComponent(0x1924), 1, 0, 0); + } - [CommandProperty( AccessLevel.GameMaster )] - public int CurFlour - { - get => m_Flour; - set{ m_Flour = Math.Max( 0, Math.Min( value, MaxFlour ) ); UpdateStage(); } - } + public FlourMillEastAddon(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool HasFlour => ( m_Flour > 0 ); + public override BaseAddonDeed Deed => new FlourMillEastDeed(); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsFull => ( m_Flour >= MaxFlour ); + [CommandProperty(AccessLevel.GameMaster)] + public bool HasFlour => m_Flour > 0; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsWorking => ( m_Timer != null ); + [CommandProperty(AccessLevel.GameMaster)] + public bool IsFull => m_Flour >= MaxFlour; - public void StartWorking( Mobile from ) - { - if ( IsWorking ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsWorking => m_Timer != null; - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( FinishWorking_Callback ), from ); - UpdateStage(); - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxFlour => 2; - private void FinishWorking_Callback( object state ) - { - if ( m_Timer != null ) - { - m_Timer.Stop(); - m_Timer = null; - } + [CommandProperty(AccessLevel.GameMaster)] + public int CurFlour + { + get => m_Flour; + set + { + m_Flour = Math.Max(0, Math.Min(value, MaxFlour)); + UpdateStage(); + } + } - if ( state is Mobile from && !from.Deleted && !Deleted && IsFull ) - { - SackFlour flour = new SackFlour(); + public void StartWorking(Mobile from) + { + if (IsWorking) + return; - flour.ItemID = ( Utility.RandomBool() ? 4153 : 4165 ); + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(FinishWorking_Callback), from); + UpdateStage(); + } - if ( from.PlaceInBackpack( flour ) ) - { - m_Flour = 0; - } - else - { - flour.Delete(); - from.SendLocalizedMessage( 500998 ); // There is not enough room in your backpack! You stop grinding. - } - } + private void FinishWorking_Callback(object state) + { + if (m_Timer != null) + { + m_Timer.Stop(); + m_Timer = null; + } - UpdateStage(); - } + if (state is Mobile from && !from.Deleted && !Deleted && IsFull) + { + SackFlour flour = new SackFlour(); - private static int[][] m_StageTable = { - new[]{ 0x1920, 0x1921, 0x1925 }, - new[]{ 0x1922, 0x1923, 0x1926 }, - new[]{ 0x1924, 0x1924, 0x1928 } - }; + flour.ItemID = Utility.RandomBool() ? 4153 : 4165; - private int[] FindItemTable( int itemID ) - { - for ( int i = 0; i < m_StageTable.Length; ++i ) - { - int[] itemTable = m_StageTable[i]; + if (from.PlaceInBackpack(flour)) + { + m_Flour = 0; + } + else + { + flour.Delete(); + from.SendLocalizedMessage(500998); // There is not enough room in your backpack! You stop grinding. + } + } - for ( int j = 0; j < itemTable.Length; ++j ) - { - if ( itemTable[j] == itemID ) - return itemTable; - } - } + UpdateStage(); + } - return null; - } + private int[] FindItemTable(int itemID) + { + for (int i = 0; i < m_StageTable.Length; ++i) + { + int[] itemTable = m_StageTable[i]; - public void UpdateStage() - { - if ( IsWorking ) - UpdateStage( FlourMillStage.Working ); - else if ( HasFlour ) - UpdateStage( FlourMillStage.Filled ); - else - UpdateStage( FlourMillStage.Empty ); - } + for (int j = 0; j < itemTable.Length; ++j) + if (itemTable[j] == itemID) + return itemTable; + } - public void UpdateStage( FlourMillStage stage ) - { - List components = Components; + return null; + } - int[][] stageTable = m_StageTable; + public void UpdateStage() + { + if (IsWorking) + UpdateStage(FlourMillStage.Working); + else if (HasFlour) + UpdateStage(FlourMillStage.Filled); + else + UpdateStage(FlourMillStage.Empty); + } - for ( int i = 0; i < components.Count; ++i ) - { - if ( !(components[i] is AddonComponent component) ) - continue; + public void UpdateStage(FlourMillStage stage) + { + List components = Components; - int[] itemTable = FindItemTable( component.ItemID ); + int[][] stageTable = m_StageTable; - if ( itemTable != null ) - component.ItemID = itemTable[(int)stage]; - } - } + for (int i = 0; i < components.Count; ++i) + { + if (!(components[i] is AddonComponent component)) + continue; - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 4 ) || !from.InLOS( this ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else if ( !IsFull ) - from.SendLocalizedMessage( 500997 ); // You need more wheat to make a sack of flour. - else - StartWorking( from ); - } + int[] itemTable = FindItemTable(component.ItemID); - [Constructible] - public FlourMillEastAddon() - { - AddComponent( new AddonComponent( 0x1920 ),-1, 0, 0 ); - AddComponent( new AddonComponent( 0x1922 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1924 ), 1, 0, 0 ); - } + if (itemTable != null) + component.ItemID = itemTable[(int)stage]; + } + } - public FlourMillEastAddon( Serial serial ) : base( serial ) - { - } + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (!from.InRange(GetWorldLocation(), 4) || !from.InLOS(this)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (!IsFull) + from.SendLocalizedMessage(500997); // You need more wheat to make a sack of flour. + else + StartWorking(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) m_Flour ); - } + writer.Write(m_Flour); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_Flour = reader.ReadInt(); - break; - } - } + switch (version) + { + case 1: + { + m_Flour = reader.ReadInt(); + break; + } + } - UpdateStage(); - } - } + UpdateStage(); + } + } - public class FlourMillEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new FlourMillEastAddon(); - public override int LabelNumber => 1044347; // flour mill (east) + public class FlourMillEastDeed : BaseAddonDeed + { + [Constructible] + public FlourMillEastDeed() + { + } - [Constructible] - public FlourMillEastDeed() - { - } + public FlourMillEastDeed(Serial serial) : base(serial) + { + } - public FlourMillEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new FlourMillEastAddon(); + public override int LabelNumber => 1044347; // flour mill (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/FlourMillSouthAddon.cs b/Scripts/Items/Addons/FlourMillSouthAddon.cs index df95daa27..31917916d 100644 --- a/Scripts/Items/Addons/FlourMillSouthAddon.cs +++ b/Scripts/Items/Addons/FlourMillSouthAddon.cs @@ -1,197 +1,201 @@ using System; -using Server.Network; using System.Collections.Generic; +using Server.Network; namespace Server.Items { - public class FlourMillSouthAddon : BaseAddon, IFlourMill - { - public override BaseAddonDeed Deed => new FlourMillSouthDeed(); - private int m_Flour; - private Timer m_Timer; + public class FlourMillSouthAddon : BaseAddon, IFlourMill + { + private static int[][] m_StageTable = + { + new[] { 0x192C, 0x192D, 0x1931 }, + new[] { 0x192E, 0x192F, 0x1932 }, + new[] { 0x1930, 0x1930, 0x1934 } + }; - [CommandProperty( AccessLevel.GameMaster )] - public int MaxFlour => 2; + private int m_Flour; + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public int CurFlour - { - get => m_Flour; - set{ m_Flour = Math.Max( 0, Math.Min( value, MaxFlour ) ); UpdateStage(); } - } + [Constructible] + public FlourMillSouthAddon() + { + AddComponent(new AddonComponent(0x192C), 0, -1, 0); + AddComponent(new AddonComponent(0x192E), 0, 0, 0); + AddComponent(new AddonComponent(0x1930), 0, 1, 0); + } - [CommandProperty( AccessLevel.GameMaster )] - public bool HasFlour => ( m_Flour > 0 ); + public FlourMillSouthAddon(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsFull => ( m_Flour >= MaxFlour ); + public override BaseAddonDeed Deed => new FlourMillSouthDeed(); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsWorking => ( m_Timer != null ); + [CommandProperty(AccessLevel.GameMaster)] + public bool HasFlour => m_Flour > 0; - public void StartWorking( Mobile from ) - { - if ( IsWorking ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsFull => m_Flour >= MaxFlour; - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( FinishWorking_Callback ), from ); - UpdateStage(); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsWorking => m_Timer != null; - private void FinishWorking_Callback( object state ) - { - if ( m_Timer != null ) - { - m_Timer.Stop(); - m_Timer = null; - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxFlour => 2; - if ( state is Mobile from && !from.Deleted && !Deleted && IsFull ) - { - SackFlour flour = new SackFlour(); + [CommandProperty(AccessLevel.GameMaster)] + public int CurFlour + { + get => m_Flour; + set + { + m_Flour = Math.Max(0, Math.Min(value, MaxFlour)); + UpdateStage(); + } + } - flour.ItemID = ( Utility.RandomBool() ? 4153 : 4165 ); + public void StartWorking(Mobile from) + { + if (IsWorking) + return; - if ( from.PlaceInBackpack( flour ) ) - { - m_Flour = 0; - } - else - { - flour.Delete(); - from.SendLocalizedMessage( 500998 ); // There is not enough room in your backpack! You stop grinding. - } - } + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(FinishWorking_Callback), from); + UpdateStage(); + } - UpdateStage(); - } + private void FinishWorking_Callback(object state) + { + if (m_Timer != null) + { + m_Timer.Stop(); + m_Timer = null; + } - private static int[][] m_StageTable = { - new[]{ 0x192C, 0x192D, 0x1931 }, - new[]{ 0x192E, 0x192F, 0x1932 }, - new[]{ 0x1930, 0x1930, 0x1934 } - }; + if (state is Mobile from && !from.Deleted && !Deleted && IsFull) + { + SackFlour flour = new SackFlour(); - private int[] FindItemTable( int itemID ) - { - for ( int i = 0; i < m_StageTable.Length; ++i ) - { - int[] itemTable = m_StageTable[i]; + flour.ItemID = Utility.RandomBool() ? 4153 : 4165; - for ( int j = 0; j < itemTable.Length; ++j ) - { - if ( itemTable[j] == itemID ) - return itemTable; - } - } + if (from.PlaceInBackpack(flour)) + { + m_Flour = 0; + } + else + { + flour.Delete(); + from.SendLocalizedMessage(500998); // There is not enough room in your backpack! You stop grinding. + } + } - return null; - } + UpdateStage(); + } - public void UpdateStage() - { - if ( IsWorking ) - UpdateStage( FlourMillStage.Working ); - else if ( HasFlour ) - UpdateStage( FlourMillStage.Filled ); - else - UpdateStage( FlourMillStage.Empty ); - } + private int[] FindItemTable(int itemID) + { + for (int i = 0; i < m_StageTable.Length; ++i) + { + int[] itemTable = m_StageTable[i]; - public void UpdateStage( FlourMillStage stage ) - { - List components = Components; + for (int j = 0; j < itemTable.Length; ++j) + if (itemTable[j] == itemID) + return itemTable; + } - int[][] stageTable = m_StageTable; + return null; + } - for ( int i = 0; i < components.Count; ++i ) - { - if ( !(components[i] is AddonComponent component) ) - continue; + public void UpdateStage() + { + if (IsWorking) + UpdateStage(FlourMillStage.Working); + else if (HasFlour) + UpdateStage(FlourMillStage.Filled); + else + UpdateStage(FlourMillStage.Empty); + } - int[] itemTable = FindItemTable( component.ItemID ); + public void UpdateStage(FlourMillStage stage) + { + List components = Components; - if ( itemTable != null ) - component.ItemID = itemTable[(int)stage]; - } - } + int[][] stageTable = m_StageTable; - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 4 ) || !from.InLOS( this ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else if ( !IsFull ) - from.SendLocalizedMessage( 500997 ); // You need more wheat to make a sack of flour. - else - StartWorking( from ); - } + for (int i = 0; i < components.Count; ++i) + { + if (!(components[i] is AddonComponent component)) + continue; - [Constructible] - public FlourMillSouthAddon() - { - AddComponent( new AddonComponent( 0x192C ), 0,-1, 0 ); - AddComponent( new AddonComponent( 0x192E ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1930 ), 0, 1, 0 ); - } + int[] itemTable = FindItemTable(component.ItemID); - public FlourMillSouthAddon( Serial serial ) : base( serial ) - { - } + if (itemTable != null) + component.ItemID = itemTable[(int)stage]; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (!from.InRange(GetWorldLocation(), 4) || !from.InLOS(this)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (!IsFull) + from.SendLocalizedMessage(500997); // You need more wheat to make a sack of flour. + else + StartWorking(from); + } - writer.Write( (int) 1 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) m_Flour ); - } + writer.Write(1); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Flour); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - { - m_Flour = reader.ReadInt(); - break; - } - } + int version = reader.ReadInt(); - UpdateStage(); - } - } + switch (version) + { + case 1: + { + m_Flour = reader.ReadInt(); + break; + } + } - public class FlourMillSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new FlourMillSouthAddon(); - public override int LabelNumber => 1044348; // flour mill (south) + UpdateStage(); + } + } - [Constructible] - public FlourMillSouthDeed() - { - } + public class FlourMillSouthDeed : BaseAddonDeed + { + [Constructible] + public FlourMillSouthDeed() + { + } - public FlourMillSouthDeed( Serial serial ) : base( serial ) - { - } + public FlourMillSouthDeed(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override BaseAddon Addon => new FlourMillSouthAddon(); + public override int LabelNumber => 1044348; // flour mill (south) - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/FlowerTapestries.cs b/Scripts/Items/Addons/FlowerTapestries.cs index 0d770aa19..cfadac83a 100644 --- a/Scripts/Items/Addons/FlowerTapestries.cs +++ b/Scripts/Items/Addons/FlowerTapestries.cs @@ -1,238 +1,238 @@ namespace Server.Items { - public class LightFlowerTapestryEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LightFlowerTapestryEastDeed(); + public class LightFlowerTapestryEastAddon : BaseAddon + { + [Constructible] + public LightFlowerTapestryEastAddon() + { + AddComponent(new AddonComponent(0xFDC), 0, 0, 0); + AddComponent(new AddonComponent(0xFDB), 0, 1, 0); + } - [Constructible] - public LightFlowerTapestryEastAddon() - { - AddComponent( new AddonComponent( 0xFDC ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xFDB ), 0, 1, 0 ); - } + public LightFlowerTapestryEastAddon(Serial serial) : base(serial) + { + } - public LightFlowerTapestryEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LightFlowerTapestryEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LightFlowerTapestryEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LightFlowerTapestryEastAddon(); - public override int LabelNumber => 1049393; // a flower tapestry deed facing east + public class LightFlowerTapestryEastDeed : BaseAddonDeed + { + [Constructible] + public LightFlowerTapestryEastDeed() + { + } - [Constructible] - public LightFlowerTapestryEastDeed() - { - } + public LightFlowerTapestryEastDeed(Serial serial) : base(serial) + { + } - public LightFlowerTapestryEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LightFlowerTapestryEastAddon(); + public override int LabelNumber => 1049393; // a flower tapestry deed facing east - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LightFlowerTapestrySouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LightFlowerTapestrySouthDeed(); + public class LightFlowerTapestrySouthAddon : BaseAddon + { + [Constructible] + public LightFlowerTapestrySouthAddon() + { + AddComponent(new AddonComponent(0xFD9), 0, 0, 0); + AddComponent(new AddonComponent(0xFDA), 1, 0, 0); + } - [Constructible] - public LightFlowerTapestrySouthAddon() - { - AddComponent( new AddonComponent( 0xFD9 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xFDA ), 1, 0, 0 ); - } + public LightFlowerTapestrySouthAddon(Serial serial) : base(serial) + { + } - public LightFlowerTapestrySouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LightFlowerTapestrySouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LightFlowerTapestrySouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LightFlowerTapestrySouthAddon(); - public override int LabelNumber => 1049394; // a flower tapestry deed facing south + public class LightFlowerTapestrySouthDeed : BaseAddonDeed + { + [Constructible] + public LightFlowerTapestrySouthDeed() + { + } - [Constructible] - public LightFlowerTapestrySouthDeed() - { - } + public LightFlowerTapestrySouthDeed(Serial serial) : base(serial) + { + } - public LightFlowerTapestrySouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LightFlowerTapestrySouthAddon(); + public override int LabelNumber => 1049394; // a flower tapestry deed facing south - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DarkFlowerTapestryEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new DarkFlowerTapestryEastDeed(); + public class DarkFlowerTapestryEastAddon : BaseAddon + { + [Constructible] + public DarkFlowerTapestryEastAddon() + { + AddComponent(new AddonComponent(0xFE0), 0, 0, 0); + AddComponent(new AddonComponent(0xFDF), 0, 1, 0); + } - [Constructible] - public DarkFlowerTapestryEastAddon() - { - AddComponent( new AddonComponent( 0xFE0 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xFDF ), 0, 1, 0 ); - } + public DarkFlowerTapestryEastAddon(Serial serial) : base(serial) + { + } - public DarkFlowerTapestryEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new DarkFlowerTapestryEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DarkFlowerTapestryEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new DarkFlowerTapestryEastAddon(); - public override int LabelNumber => 1049395; // a dark flower tapestry deed facing east + public class DarkFlowerTapestryEastDeed : BaseAddonDeed + { + [Constructible] + public DarkFlowerTapestryEastDeed() + { + } - [Constructible] - public DarkFlowerTapestryEastDeed() - { - } + public DarkFlowerTapestryEastDeed(Serial serial) : base(serial) + { + } - public DarkFlowerTapestryEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new DarkFlowerTapestryEastAddon(); + public override int LabelNumber => 1049395; // a dark flower tapestry deed facing east - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DarkFlowerTapestrySouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new DarkFlowerTapestrySouthDeed(); + public class DarkFlowerTapestrySouthAddon : BaseAddon + { + [Constructible] + public DarkFlowerTapestrySouthAddon() + { + AddComponent(new AddonComponent(0xFDD), 0, 0, 0); + AddComponent(new AddonComponent(0xFDE), 1, 0, 0); + } - [Constructible] - public DarkFlowerTapestrySouthAddon() - { - AddComponent( new AddonComponent( 0xFDD ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xFDE ), 1, 0, 0 ); - } + public DarkFlowerTapestrySouthAddon(Serial serial) : base(serial) + { + } - public DarkFlowerTapestrySouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new DarkFlowerTapestrySouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DarkFlowerTapestrySouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new DarkFlowerTapestrySouthAddon(); - public override int LabelNumber => 1049396; // a dark flower tapestry deed facing south + public class DarkFlowerTapestrySouthDeed : BaseAddonDeed + { + [Constructible] + public DarkFlowerTapestrySouthDeed() + { + } - [Constructible] - public DarkFlowerTapestrySouthDeed() - { - } + public DarkFlowerTapestrySouthDeed(Serial serial) : base(serial) + { + } - public DarkFlowerTapestrySouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new DarkFlowerTapestrySouthAddon(); + public override int LabelNumber => 1049396; // a dark flower tapestry deed facing south - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/GiantWebs.cs b/Scripts/Items/Addons/GiantWebs.cs index 4a978d58b..d715e2364 100644 --- a/Scripts/Items/Addons/GiantWebs.cs +++ b/Scripts/Items/Addons/GiantWebs.cs @@ -1,200 +1,206 @@ namespace Server.Items { - public class GiantWeb1 : BaseAddon - { - [Constructible] - public GiantWeb1() - { - int itemID = 4280; - int count = 5; - bool leftToRight = false; + public class GiantWeb1 : BaseAddon + { + [Constructible] + public GiantWeb1() + { + int itemID = 4280; + int count = 5; + bool leftToRight = false; - for ( int i = 0; i < count; ++i ) - AddComponent( new AddonComponent( itemID++ ), leftToRight ? i : count - 1 - i, -( leftToRight ? i : count - 1 - i ), 0 ); - } + for (int i = 0; i < count; ++i) + AddComponent(new AddonComponent(itemID++), leftToRight ? i : count - 1 - i, + -(leftToRight ? i : count - 1 - i), 0); + } - public GiantWeb1( Serial serial ) - : base( serial ) - { - } + public GiantWeb1(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } - public class GiantWeb2 : BaseAddon - { - [Constructible] - public GiantWeb2() - { - int itemID = 4285; - int count = 5; - bool leftToRight = true; + public class GiantWeb2 : BaseAddon + { + [Constructible] + public GiantWeb2() + { + int itemID = 4285; + int count = 5; + bool leftToRight = true; - for ( int i = 0; i < count; ++i ) - AddComponent( new AddonComponent( itemID++ ), leftToRight ? i : count - 1 - i, -( leftToRight ? i : count - 1 - i ), 0 ); - } + for (int i = 0; i < count; ++i) + AddComponent(new AddonComponent(itemID++), leftToRight ? i : count - 1 - i, + -(leftToRight ? i : count - 1 - i), 0); + } - public GiantWeb2( Serial serial ) - : base( serial ) - { - } + public GiantWeb2(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } - public class GiantWeb3 : BaseAddon - { - [Constructible] - public GiantWeb3() - { - int itemID = 4290; - int count = 4; - bool leftToRight = true; + public class GiantWeb3 : BaseAddon + { + [Constructible] + public GiantWeb3() + { + int itemID = 4290; + int count = 4; + bool leftToRight = true; - for ( int i = 0; i < count; ++i ) - AddComponent( new AddonComponent( itemID++ ), leftToRight ? i : count - 1 - i, -( leftToRight ? i : count - 1 - i ), 0 ); - } + for (int i = 0; i < count; ++i) + AddComponent(new AddonComponent(itemID++), leftToRight ? i : count - 1 - i, + -(leftToRight ? i : count - 1 - i), 0); + } - public GiantWeb3( Serial serial ) - : base( serial ) - { - } + public GiantWeb3(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } - public class GiantWeb4 : BaseAddon - { - [Constructible] - public GiantWeb4() - { - int itemID = 4294; - int count = 4; - bool leftToRight = false; + public class GiantWeb4 : BaseAddon + { + [Constructible] + public GiantWeb4() + { + int itemID = 4294; + int count = 4; + bool leftToRight = false; - for ( int i = 0; i < count; ++i ) - AddComponent( new AddonComponent( itemID++ ), leftToRight ? i : count - 1 - i, -( leftToRight ? i : count - 1 - i ), 0 ); - } + for (int i = 0; i < count; ++i) + AddComponent(new AddonComponent(itemID++), leftToRight ? i : count - 1 - i, + -(leftToRight ? i : count - 1 - i), 0); + } - public GiantWeb4( Serial serial ) - : base( serial ) - { - } + public GiantWeb4(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } - public class GiantWeb5 : BaseAddon - { - [Constructible] - public GiantWeb5() - { - int itemID = 4298; - int count = 4; - bool leftToRight = true; + public class GiantWeb5 : BaseAddon + { + [Constructible] + public GiantWeb5() + { + int itemID = 4298; + int count = 4; + bool leftToRight = true; - for ( int i = 0; i < count; ++i ) - AddComponent( new AddonComponent( itemID++ ), leftToRight ? i : count - 1 - i, -( leftToRight ? i : count - 1 - i ), 0 ); - } + for (int i = 0; i < count; ++i) + AddComponent(new AddonComponent(itemID++), leftToRight ? i : count - 1 - i, + -(leftToRight ? i : count - 1 - i), 0); + } - public GiantWeb5( Serial serial ) - : base( serial ) - { - } + public GiantWeb5(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } - public class GiantWeb6 : BaseAddon - { - [Constructible] - public GiantWeb6() - { - int itemID = 4302; - int count = 4; - bool leftToRight = false; + public class GiantWeb6 : BaseAddon + { + [Constructible] + public GiantWeb6() + { + int itemID = 4302; + int count = 4; + bool leftToRight = false; - for ( int i = 0; i < count; ++i ) - AddComponent( new AddonComponent( itemID++ ), leftToRight ? i : count - 1 - i, -( leftToRight ? i : count - 1 - i ), 0 ); - } + for (int i = 0; i < count; ++i) + AddComponent(new AddonComponent(itemID++), leftToRight ? i : count - 1 - i, + -(leftToRight ? i : count - 1 - i), 0); + } - public GiantWeb6( Serial serial ) - : base( serial ) - { - } + public GiantWeb6(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/GozaMats.cs b/Scripts/Items/Addons/GozaMats.cs index 51140b16d..53942e991 100644 --- a/Scripts/Items/Addons/GozaMats.cs +++ b/Scripts/Items/Addons/GozaMats.cs @@ -1,535 +1,535 @@ namespace Server.Items { - public class GozaMatEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GozaMatEastDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public GozaMatEastAddon() : this( 0 ) - { - } - - [Constructible] - public GozaMatEastAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28a4, 1030688 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x28a5, 1030688 ), 0, 0, 0 ); - Hue = hue; - } - - public GozaMatEastAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GozaMatEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new GozaMatEastAddon( Hue ); - public override int LabelNumber => 1030404; // goza (east) - - [Constructible] - public GozaMatEastDeed() - { - } - - public GozaMatEastDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GozaMatSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GozaMatSouthDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public GozaMatSouthAddon() : this( 0 ) - { - } - - [Constructible] - public GozaMatSouthAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28a6, 1030688 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0x28a7, 1030688 ), 0, 0, 0 ); - Hue = hue; - } - - public GozaMatSouthAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GozaMatSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new GozaMatSouthAddon( Hue ); - public override int LabelNumber => 1030405; // goza (south) - - [Constructible] - public GozaMatSouthDeed() - { - } - - public GozaMatSouthDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SquareGozaMatEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SquareGozaMatEastDeed(); - public override int LabelNumber => 1030688; // goza mat - - public override bool RetainDeedHue => true; - - [Constructible] - public SquareGozaMatEastAddon() : this( 0 ) - { - } - - [Constructible] - public SquareGozaMatEastAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28a8, 1030688 ), 0, 0, 0 ); - Hue = hue; - } - - public SquareGozaMatEastAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SquareGozaMatEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SquareGozaMatEastAddon( Hue ); - public override int LabelNumber => 1030407; // square goza (east) - - [Constructible] - public SquareGozaMatEastDeed() - { - } - - public SquareGozaMatEastDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SquareGozaMatSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SquareGozaMatSouthDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public SquareGozaMatSouthAddon() : this( 0 ) - { - } - - [Constructible] - public SquareGozaMatSouthAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28a9, 1030688 ), 0, 0, 0 ); - Hue = hue; - } - - public SquareGozaMatSouthAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SquareGozaMatSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SquareGozaMatSouthAddon( Hue ); - public override int LabelNumber => 1030406; // square goza (south) - - - [Constructible] - public SquareGozaMatSouthDeed() - { - } - - public SquareGozaMatSouthDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BrocadeGozaMatEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrocadeGozaMatEastDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public BrocadeGozaMatEastAddon() : this( 0 ) - { - } - - [Constructible] - public BrocadeGozaMatEastAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28AB, 1030688 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x28AA, 1030688 ), 1, 0, 0 ); - Hue = hue; - } - - public BrocadeGozaMatEastAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BrocadeGozaMatEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrocadeGozaMatEastAddon( Hue ); - public override int LabelNumber => 1030408; // brocade goza (east) - - [Constructible] - public BrocadeGozaMatEastDeed() - { - } - - public BrocadeGozaMatEastDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - public class BrocadeGozaMatSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrocadeGozaMatSouthDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public BrocadeGozaMatSouthAddon() : this( 0 ) - { - } - - [Constructible] - public BrocadeGozaMatSouthAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28AD, 1030688 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x28AC, 1030688 ), 0, 1, 0 ); - Hue = hue; - } - - public BrocadeGozaMatSouthAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BrocadeGozaMatSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrocadeGozaMatSouthAddon( Hue ); - public override int LabelNumber => 1030409; // brocade goza (south) - - [Constructible] - public BrocadeGozaMatSouthDeed() - { - } - - public BrocadeGozaMatSouthDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - public class BrocadeSquareGozaMatEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrocadeSquareGozaMatEastDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public BrocadeSquareGozaMatEastAddon() : this( 0 ) - { - } - - [Constructible] - public BrocadeSquareGozaMatEastAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28AE, 1030688 ), 0, 0, 0 ); - Hue = hue; - } - - public BrocadeSquareGozaMatEastAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BrocadeSquareGozaMatEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrocadeSquareGozaMatEastAddon( Hue ); - public override int LabelNumber => 1030411; // brocade square goza (east) - - [Constructible] - public BrocadeSquareGozaMatEastDeed() - { - } - - public BrocadeSquareGozaMatEastDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BrocadeSquareGozaMatSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrocadeSquareGozaMatSouthDeed(); - - public override bool RetainDeedHue => true; - - [Constructible] - public BrocadeSquareGozaMatSouthAddon() : this( 0 ) - { - } - - [Constructible] - public BrocadeSquareGozaMatSouthAddon( int hue ) - { - AddComponent( new LocalizedAddonComponent( 0x28AF, 1030688 ), 0, 0, 0 ); - Hue = hue; - } - - public BrocadeSquareGozaMatSouthAddon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public class GozaMatEastAddon : BaseAddon + { + [Constructible] + public GozaMatEastAddon() : this(0) + { + } + + [Constructible] + public GozaMatEastAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28a4, 1030688), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0x28a5, 1030688), 0, 0, 0); + Hue = hue; + } + + public GozaMatEastAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new GozaMatEastDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GozaMatEastDeed : BaseAddonDeed + { + [Constructible] + public GozaMatEastDeed() + { + } + + public GozaMatEastDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new GozaMatEastAddon(Hue); + public override int LabelNumber => 1030404; // goza (east) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GozaMatSouthAddon : BaseAddon + { + [Constructible] + public GozaMatSouthAddon() : this(0) + { + } + + [Constructible] + public GozaMatSouthAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28a6, 1030688), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0x28a7, 1030688), 0, 0, 0); + Hue = hue; + } + + public GozaMatSouthAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new GozaMatSouthDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GozaMatSouthDeed : BaseAddonDeed + { + [Constructible] + public GozaMatSouthDeed() + { + } + + public GozaMatSouthDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new GozaMatSouthAddon(Hue); + public override int LabelNumber => 1030405; // goza (south) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SquareGozaMatEastAddon : BaseAddon + { + [Constructible] + public SquareGozaMatEastAddon() : this(0) + { + } + + [Constructible] + public SquareGozaMatEastAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28a8, 1030688), 0, 0, 0); + Hue = hue; + } + + public SquareGozaMatEastAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new SquareGozaMatEastDeed(); + public override int LabelNumber => 1030688; // goza mat + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SquareGozaMatEastDeed : BaseAddonDeed + { + [Constructible] + public SquareGozaMatEastDeed() + { + } + + public SquareGozaMatEastDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new SquareGozaMatEastAddon(Hue); + public override int LabelNumber => 1030407; // square goza (east) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SquareGozaMatSouthAddon : BaseAddon + { + [Constructible] + public SquareGozaMatSouthAddon() : this(0) + { + } + + [Constructible] + public SquareGozaMatSouthAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28a9, 1030688), 0, 0, 0); + Hue = hue; + } + + public SquareGozaMatSouthAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new SquareGozaMatSouthDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SquareGozaMatSouthDeed : BaseAddonDeed + { + [Constructible] + public SquareGozaMatSouthDeed() + { + } + + public SquareGozaMatSouthDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new SquareGozaMatSouthAddon(Hue); + public override int LabelNumber => 1030406; // square goza (south) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeGozaMatEastAddon : BaseAddon + { + [Constructible] + public BrocadeGozaMatEastAddon() : this(0) + { + } + + [Constructible] + public BrocadeGozaMatEastAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28AB, 1030688), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x28AA, 1030688), 1, 0, 0); + Hue = hue; + } + + public BrocadeGozaMatEastAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new BrocadeGozaMatEastDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeGozaMatEastDeed : BaseAddonDeed + { + [Constructible] + public BrocadeGozaMatEastDeed() + { + } + + public BrocadeGozaMatEastDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new BrocadeGozaMatEastAddon(Hue); + public override int LabelNumber => 1030408; // brocade goza (east) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeGozaMatSouthAddon : BaseAddon + { + [Constructible] + public BrocadeGozaMatSouthAddon() : this(0) + { + } + + [Constructible] + public BrocadeGozaMatSouthAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28AD, 1030688), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x28AC, 1030688), 0, 1, 0); + Hue = hue; + } + + public BrocadeGozaMatSouthAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new BrocadeGozaMatSouthDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeGozaMatSouthDeed : BaseAddonDeed + { + [Constructible] + public BrocadeGozaMatSouthDeed() + { + } + + public BrocadeGozaMatSouthDeed(Serial serial) : base(serial) + { + } + + public override BaseAddon Addon => new BrocadeGozaMatSouthAddon(Hue); + public override int LabelNumber => 1030409; // brocade goza (south) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeSquareGozaMatEastAddon : BaseAddon + { + [Constructible] + public BrocadeSquareGozaMatEastAddon() : this(0) + { + } + + [Constructible] + public BrocadeSquareGozaMatEastAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28AE, 1030688), 0, 0, 0); + Hue = hue; + } + + public BrocadeSquareGozaMatEastAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new BrocadeSquareGozaMatEastDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeSquareGozaMatEastDeed : BaseAddonDeed + { + [Constructible] + public BrocadeSquareGozaMatEastDeed() + { + } + + public BrocadeSquareGozaMatEastDeed(Serial serial) : base(serial) + { + } - public class BrocadeSquareGozaMatSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrocadeSquareGozaMatSouthAddon( Hue ); - public override int LabelNumber => 1030410; // brocade square goza (south) - - - [Constructible] - public BrocadeSquareGozaMatSouthDeed() - { - } - - public BrocadeSquareGozaMatSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrocadeSquareGozaMatEastAddon(Hue); + public override int LabelNumber => 1030411; // brocade square goza (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeSquareGozaMatSouthAddon : BaseAddon + { + [Constructible] + public BrocadeSquareGozaMatSouthAddon() : this(0) + { + } + + [Constructible] + public BrocadeSquareGozaMatSouthAddon(int hue) + { + AddComponent(new LocalizedAddonComponent(0x28AF, 1030688), 0, 0, 0); + Hue = hue; + } + + public BrocadeSquareGozaMatSouthAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed => new BrocadeSquareGozaMatSouthDeed(); + + public override bool RetainDeedHue => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrocadeSquareGozaMatSouthDeed : BaseAddonDeed + { + [Constructible] + public BrocadeSquareGozaMatSouthDeed() + { + } - writer.Write( (int) 0 ); // version - } + public BrocadeSquareGozaMatSouthDeed(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override BaseAddon Addon => new BrocadeSquareGozaMatSouthAddon(Hue); + public override int LabelNumber => 1030410; // brocade square goza (south) - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/GrayBrickFireplaceEastAddon.cs b/Scripts/Items/Addons/GrayBrickFireplaceEastAddon.cs index 9ec66975a..c04eea03c 100644 --- a/Scripts/Items/Addons/GrayBrickFireplaceEastAddon.cs +++ b/Scripts/Items/Addons/GrayBrickFireplaceEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class GrayBrickFireplaceEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GrayBrickFireplaceEastDeed(); + public class GrayBrickFireplaceEastAddon : BaseAddon + { + [Constructible] + public GrayBrickFireplaceEastAddon() + { + AddComponent(new AddonComponent(0x93D), 0, 0, 0); + AddComponent(new AddonComponent(0x937), 0, 1, 0); + } - [Constructible] - public GrayBrickFireplaceEastAddon() - { - AddComponent( new AddonComponent( 0x93D ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x937 ), 0, 1, 0 ); - } + public GrayBrickFireplaceEastAddon(Serial serial) : base(serial) + { + } - public GrayBrickFireplaceEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new GrayBrickFireplaceEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GrayBrickFireplaceEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new GrayBrickFireplaceEastAddon(); - public override int LabelNumber => 1061846; // grey brick fireplace (east) + public class GrayBrickFireplaceEastDeed : BaseAddonDeed + { + [Constructible] + public GrayBrickFireplaceEastDeed() + { + } - [Constructible] - public GrayBrickFireplaceEastDeed() - { - } + public GrayBrickFireplaceEastDeed(Serial serial) : base(serial) + { + } - public GrayBrickFireplaceEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new GrayBrickFireplaceEastAddon(); + public override int LabelNumber => 1061846; // grey brick fireplace (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/GrayBrickFireplaceSouthAddon.cs b/Scripts/Items/Addons/GrayBrickFireplaceSouthAddon.cs index e0344cc3f..453306adb 100644 --- a/Scripts/Items/Addons/GrayBrickFireplaceSouthAddon.cs +++ b/Scripts/Items/Addons/GrayBrickFireplaceSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class GrayBrickFireplaceSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GrayBrickFireplaceSouthDeed(); + public class GrayBrickFireplaceSouthAddon : BaseAddon + { + [Constructible] + public GrayBrickFireplaceSouthAddon() + { + AddComponent(new AddonComponent(0x94B), -1, 0, 0); + AddComponent(new AddonComponent(0x945), 0, 0, 0); + } - [Constructible] - public GrayBrickFireplaceSouthAddon() - { - AddComponent( new AddonComponent( 0x94B ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x945 ), 0, 0, 0 ); - } + public GrayBrickFireplaceSouthAddon(Serial serial) : base(serial) + { + } - public GrayBrickFireplaceSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new GrayBrickFireplaceSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GrayBrickFireplaceSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new GrayBrickFireplaceSouthAddon(); - public override int LabelNumber => 1061847; // grey brick fireplace (south) + public class GrayBrickFireplaceSouthDeed : BaseAddonDeed + { + [Constructible] + public GrayBrickFireplaceSouthDeed() + { + } - [Constructible] - public GrayBrickFireplaceSouthDeed() - { - } + public GrayBrickFireplaceSouthDeed(Serial serial) : base(serial) + { + } - public GrayBrickFireplaceSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new GrayBrickFireplaceSouthAddon(); + public override int LabelNumber => 1061847; // grey brick fireplace (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/JackOLantern.cs b/Scripts/Items/Addons/JackOLantern.cs index 74814eb21..d72b6383e 100644 --- a/Scripts/Items/Addons/JackOLantern.cs +++ b/Scripts/Items/Addons/JackOLantern.cs @@ -2,89 +2,81 @@ using System; namespace Server.Items { - public class JackOLantern : BaseAddon - { - public override bool ShareHue => false; + public class JackOLantern : BaseAddon + { + [Constructible] + public JackOLantern() + : this(1 > Utility.Random(2)) + { + } - private AddonComponent GetComponent( int itemID, int hue ) - { - AddonComponent ac = new AddonComponent( itemID ); + [Constructible] + public JackOLantern(bool south) + { + AddComponent(new AddonComponent(5703), 0, 0, +0); - ac.Hue = hue; - ac.Name = "jack-o-lantern"; + int hue = 1161; + //( 1 > Utility.Random( 5 ) ? 2118 : 1161 ); - return ac; - } + if (!south) + { + AddComponent(GetComponent(3178, 0000), 0, 0, -1); + AddComponent(GetComponent(3883, hue), 0, 0, +1); + AddComponent(GetComponent(3862, hue), 0, 0, +0); + } + else + { + AddComponent(GetComponent(3179, 0000), 0, 0, +0); + AddComponent(GetComponent(3885, hue), 0, 0, -1); + AddComponent(GetComponent(3871, hue), 0, 0, +0); + } + } - [Constructible] - public JackOLantern() - : this( 1 > Utility.Random( 2 ) ) - { - } + public JackOLantern(Serial serial) + : base(serial) + { + } - [Constructible] - public JackOLantern( bool south ) - { - AddComponent( new AddonComponent( 5703 ), 0, 0, +0 ); + public override bool ShareHue => false; - int hue = 1161; - //( 1 > Utility.Random( 5 ) ? 2118 : 1161 ); + private AddonComponent GetComponent(int itemID, int hue) + { + AddonComponent ac = new AddonComponent(itemID); - if ( !south ) - { - AddComponent( GetComponent( 3178, 0000 ), 0, 0, -1 ); - AddComponent( GetComponent( 3883, hue ), 0, 0, +1 ); - AddComponent( GetComponent( 3862, hue ), 0, 0, +0 ); - } - else - { - AddComponent( GetComponent( 3179, 0000 ), 0, 0, +0 ); - AddComponent( GetComponent( 3885, hue ), 0, 0, -1 ); - AddComponent( GetComponent( 3871, hue ), 0, 0, +0 ); - } - } + ac.Hue = hue; + ac.Name = "jack-o-lantern"; - public JackOLantern( Serial serial ) - : base( serial ) - { - } + return ac; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 2 ); // version - } + writer.Write((byte)2); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); + int version = reader.ReadByte(); - if ( version == 0 ) - { - Timer.DelayCall( TimeSpan.Zero, delegate - { - for ( int i = 0; i < Components.Count; ++i ) - { - if ( Components[i] is AddonComponent ac && ac.Hue == 2118 ) - ac.Hue = 1161; - } - } ); - } + if (version == 0) + Timer.DelayCall(TimeSpan.Zero, delegate + { + for (int i = 0; i < Components.Count; ++i) + if (Components[i] is AddonComponent ac && ac.Hue == 2118) + ac.Hue = 1161; + }); - if ( version <= 1 ) - { - Timer.DelayCall( TimeSpan.Zero, delegate - { - for ( int i = 0; i < Components.Count; ++i ) - { - if ( Components[i] is AddonComponent ac ) - ac.Name = "jack-o-lantern"; - } - } ); - } - } - } -} + if (version <= 1) + Timer.DelayCall(TimeSpan.Zero, delegate + { + for (int i = 0; i < Components.Count; ++i) + if (Components[i] is AddonComponent ac) + ac.Name = "jack-o-lantern"; + }); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LargeBedEastAddon.cs b/Scripts/Items/Addons/LargeBedEastAddon.cs index d924e2a30..d3e9994ae 100644 --- a/Scripts/Items/Addons/LargeBedEastAddon.cs +++ b/Scripts/Items/Addons/LargeBedEastAddon.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class LargeBedEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeBedEastDeed(); + public class LargeBedEastAddon : BaseAddon + { + [Constructible] + public LargeBedEastAddon() + { + AddComponent(new AddonComponent(0xA7D), 0, 0, 0); + AddComponent(new AddonComponent(0xA7C), 0, 1, 0); + AddComponent(new AddonComponent(0xA79), 1, 0, 0); + AddComponent(new AddonComponent(0xA78), 1, 1, 0); + } - [Constructible] - public LargeBedEastAddon() - { - AddComponent( new AddonComponent( 0xA7D ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xA7C ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0xA79 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0xA78 ), 1, 1, 0 ); - } + public LargeBedEastAddon(Serial serial) : base(serial) + { + } - public LargeBedEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LargeBedEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeBedEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeBedEastAddon(); - public override int LabelNumber => 1044324; // large bed (east) + public class LargeBedEastDeed : BaseAddonDeed + { + [Constructible] + public LargeBedEastDeed() + { + } - [Constructible] - public LargeBedEastDeed() - { - } + public LargeBedEastDeed(Serial serial) : base(serial) + { + } - public LargeBedEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeBedEastAddon(); + public override int LabelNumber => 1044324; // large bed (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LargeBedSouthAddon.cs b/Scripts/Items/Addons/LargeBedSouthAddon.cs index e5e94a3fd..397cc7a5b 100644 --- a/Scripts/Items/Addons/LargeBedSouthAddon.cs +++ b/Scripts/Items/Addons/LargeBedSouthAddon.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class LargeBedSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeBedSouthDeed(); + public class LargeBedSouthAddon : BaseAddon + { + [Constructible] + public LargeBedSouthAddon() + { + AddComponent(new AddonComponent(0xA83), 0, 0, 0); + AddComponent(new AddonComponent(0xA7F), 0, 1, 0); + AddComponent(new AddonComponent(0xA82), 1, 0, 0); + AddComponent(new AddonComponent(0xA7E), 1, 1, 0); + } - [Constructible] - public LargeBedSouthAddon() - { - AddComponent( new AddonComponent( 0xA83 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xA7F ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0xA82 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0xA7E ), 1, 1, 0 ); - } + public LargeBedSouthAddon(Serial serial) : base(serial) + { + } - public LargeBedSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LargeBedSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeBedSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeBedSouthAddon(); - public override int LabelNumber => 1044323; // large bed (south) + public class LargeBedSouthDeed : BaseAddonDeed + { + [Constructible] + public LargeBedSouthDeed() + { + } - [Constructible] - public LargeBedSouthDeed() - { - } + public LargeBedSouthDeed(Serial serial) : base(serial) + { + } - public LargeBedSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeBedSouthAddon(); + public override int LabelNumber => 1044323; // large bed (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LargeForgeEastAddon.cs b/Scripts/Items/Addons/LargeForgeEastAddon.cs index aac007cc0..cc9d9fee4 100644 --- a/Scripts/Items/Addons/LargeForgeEastAddon.cs +++ b/Scripts/Items/Addons/LargeForgeEastAddon.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class LargeForgeEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeForgeEastDeed(); + public class LargeForgeEastAddon : BaseAddon + { + [Constructible] + public LargeForgeEastAddon() + { + AddComponent(new ForgeComponent(0x1986), 0, 0, 0); + AddComponent(new ForgeComponent(0x198A), 0, 1, 0); + AddComponent(new ForgeComponent(0x1996), 0, 2, 0); + AddComponent(new ForgeComponent(0x1992), 0, 3, 0); + } - [Constructible] - public LargeForgeEastAddon() - { - AddComponent( new ForgeComponent( 0x1986 ), 0, 0, 0 ); - AddComponent( new ForgeComponent( 0x198A ), 0, 1, 0 ); - AddComponent( new ForgeComponent( 0x1996 ), 0, 2, 0 ); - AddComponent( new ForgeComponent( 0x1992 ), 0, 3, 0 ); - } + public LargeForgeEastAddon(Serial serial) : base(serial) + { + } - public LargeForgeEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LargeForgeEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeForgeEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeForgeEastAddon(); - public override int LabelNumber => 1044331; // large forge (east) + public class LargeForgeEastDeed : BaseAddonDeed + { + [Constructible] + public LargeForgeEastDeed() + { + } - [Constructible] - public LargeForgeEastDeed() - { - } + public LargeForgeEastDeed(Serial serial) : base(serial) + { + } - public LargeForgeEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeForgeEastAddon(); + public override int LabelNumber => 1044331; // large forge (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LargeForgeSouthAddon.cs b/Scripts/Items/Addons/LargeForgeSouthAddon.cs index b66037061..d92ac89ee 100644 --- a/Scripts/Items/Addons/LargeForgeSouthAddon.cs +++ b/Scripts/Items/Addons/LargeForgeSouthAddon.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class LargeForgeSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeForgeSouthDeed(); + public class LargeForgeSouthAddon : BaseAddon + { + [Constructible] + public LargeForgeSouthAddon() + { + AddComponent(new ForgeComponent(0x197A), 0, 0, 0); + AddComponent(new ForgeComponent(0x197E), 1, 0, 0); + AddComponent(new ForgeComponent(0x19A2), 2, 0, 0); + AddComponent(new ForgeComponent(0x199E), 3, 0, 0); + } - [Constructible] - public LargeForgeSouthAddon() - { - AddComponent( new ForgeComponent( 0x197A ), 0, 0, 0 ); - AddComponent( new ForgeComponent( 0x197E ), 1, 0, 0 ); - AddComponent( new ForgeComponent( 0x19A2 ), 2, 0, 0 ); - AddComponent( new ForgeComponent( 0x199E ), 3, 0, 0 ); - } + public LargeForgeSouthAddon(Serial serial) : base(serial) + { + } - public LargeForgeSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LargeForgeSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeForgeSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeForgeSouthAddon(); - public override int LabelNumber => 1044332; // large forge (south) + public class LargeForgeSouthDeed : BaseAddonDeed + { + [Constructible] + public LargeForgeSouthDeed() + { + } - [Constructible] - public LargeForgeSouthDeed() - { - } + public LargeForgeSouthDeed(Serial serial) : base(serial) + { + } - public LargeForgeSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeForgeSouthAddon(); + public override int LabelNumber => 1044332; // large forge (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LargeStoneTableEastAddon.cs b/Scripts/Items/Addons/LargeStoneTableEastAddon.cs index 00265d756..10585f4aa 100644 --- a/Scripts/Items/Addons/LargeStoneTableEastAddon.cs +++ b/Scripts/Items/Addons/LargeStoneTableEastAddon.cs @@ -1,70 +1,70 @@ namespace Server.Items { - public class LargeStoneTableEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeStoneTableEastDeed(); + public class LargeStoneTableEastAddon : BaseAddon + { + [Constructible] + public LargeStoneTableEastAddon() : this(0) + { + } - public override bool RetainDeedHue => true; + [Constructible] + public LargeStoneTableEastAddon(int hue) + { + AddComponent(new AddonComponent(0x1202), 0, 0, 0); + AddComponent(new AddonComponent(0x1203), 0, 1, 0); + AddComponent(new AddonComponent(0x1201), 0, 2, 0); + Hue = hue; + } - [Constructible] - public LargeStoneTableEastAddon() : this( 0 ) - { - } + public LargeStoneTableEastAddon(Serial serial) : base(serial) + { + } - [Constructible] - public LargeStoneTableEastAddon( int hue ) - { - AddComponent( new AddonComponent( 0x1202 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1203 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1201 ), 0, 2, 0 ); - Hue = hue; - } + public override BaseAddonDeed Deed => new LargeStoneTableEastDeed(); - public LargeStoneTableEastAddon( Serial serial ) : base( serial ) - { - } + public override bool RetainDeedHue => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeStoneTableEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeStoneTableEastAddon( Hue ); - public override int LabelNumber => 1044511; // large stone table (east) + public class LargeStoneTableEastDeed : BaseAddonDeed + { + [Constructible] + public LargeStoneTableEastDeed() + { + } - [Constructible] - public LargeStoneTableEastDeed() - { - } + public LargeStoneTableEastDeed(Serial serial) : base(serial) + { + } - public LargeStoneTableEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeStoneTableEastAddon(Hue); + public override int LabelNumber => 1044511; // large stone table (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LargeStoneTableSouthAddon.cs b/Scripts/Items/Addons/LargeStoneTableSouthAddon.cs index a29ab7c79..20b657453 100644 --- a/Scripts/Items/Addons/LargeStoneTableSouthAddon.cs +++ b/Scripts/Items/Addons/LargeStoneTableSouthAddon.cs @@ -1,70 +1,70 @@ namespace Server.Items { - public class LargeStoneTableSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeStoneTableSouthDeed(); + public class LargeStoneTableSouthAddon : BaseAddon + { + [Constructible] + public LargeStoneTableSouthAddon() : this(0) + { + } - public override bool RetainDeedHue => true; + [Constructible] + public LargeStoneTableSouthAddon(int hue) + { + AddComponent(new AddonComponent(0x1205), 0, 0, 0); + AddComponent(new AddonComponent(0x1206), 1, 0, 0); + AddComponent(new AddonComponent(0x1204), 2, 0, 0); + Hue = hue; + } - [Constructible] - public LargeStoneTableSouthAddon() : this( 0 ) - { - } + public LargeStoneTableSouthAddon(Serial serial) : base(serial) + { + } - [Constructible] - public LargeStoneTableSouthAddon( int hue ) - { - AddComponent( new AddonComponent( 0x1205 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1206 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1204 ), 2, 0, 0 ); - Hue = hue; - } + public override BaseAddonDeed Deed => new LargeStoneTableSouthDeed(); - public LargeStoneTableSouthAddon( Serial serial ) : base( serial ) - { - } + public override bool RetainDeedHue => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeStoneTableSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeStoneTableSouthAddon( Hue ); - public override int LabelNumber => 1044512; // large stone table (South) + public class LargeStoneTableSouthDeed : BaseAddonDeed + { + [Constructible] + public LargeStoneTableSouthDeed() + { + } - [Constructible] - public LargeStoneTableSouthDeed() - { - } + public LargeStoneTableSouthDeed(Serial serial) : base(serial) + { + } - public LargeStoneTableSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeStoneTableSouthAddon(Hue); + public override int LabelNumber => 1044512; // large stone table (South) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LoomEastAddon.cs b/Scripts/Items/Addons/LoomEastAddon.cs index 671c8fc8b..525514db7 100644 --- a/Scripts/Items/Addons/LoomEastAddon.cs +++ b/Scripts/Items/Addons/LoomEastAddon.cs @@ -1,79 +1,79 @@ namespace Server.Items { - public interface ILoom - { - int Phase{ get; set; } - } + public interface ILoom + { + int Phase{ get; set; } + } - public class LoomEastAddon : BaseAddon, ILoom - { - public override BaseAddonDeed Deed => new LoomEastDeed(); + public class LoomEastAddon : BaseAddon, ILoom + { + [Constructible] + public LoomEastAddon() + { + AddComponent(new AddonComponent(0x1060), 0, 0, 0); + AddComponent(new AddonComponent(0x105F), 0, 1, 0); + } - public int Phase { get; set; } + public LoomEastAddon(Serial serial) : base(serial) + { + } - [Constructible] - public LoomEastAddon() - { - AddComponent( new AddonComponent( 0x1060 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x105F ), 0, 1, 0 ); - } + public override BaseAddonDeed Deed => new LoomEastDeed(); - public LoomEastAddon( Serial serial ) : base( serial ) - { - } + public int Phase{ get; set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) Phase ); - } + writer.Write(Phase); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Phase = reader.ReadInt(); - break; - } - } - } - } + switch (version) + { + case 1: + { + Phase = reader.ReadInt(); + break; + } + } + } + } - public class LoomEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LoomEastAddon(); - public override int LabelNumber => 1044343; // loom (east) + public class LoomEastDeed : BaseAddonDeed + { + [Constructible] + public LoomEastDeed() + { + } - [Constructible] - public LoomEastDeed() - { - } + public LoomEastDeed(Serial serial) : base(serial) + { + } - public LoomEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LoomEastAddon(); + public override int LabelNumber => 1044343; // loom (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/LoomSouthAddon.cs b/Scripts/Items/Addons/LoomSouthAddon.cs index ca002b7d0..62a15683d 100644 --- a/Scripts/Items/Addons/LoomSouthAddon.cs +++ b/Scripts/Items/Addons/LoomSouthAddon.cs @@ -1,74 +1,74 @@ namespace Server.Items { - public class LoomSouthAddon : BaseAddon, ILoom - { - public override BaseAddonDeed Deed => new LoomSouthDeed(); + public class LoomSouthAddon : BaseAddon, ILoom + { + [Constructible] + public LoomSouthAddon() + { + AddComponent(new AddonComponent(0x1061), 0, 0, 0); + AddComponent(new AddonComponent(0x1062), 1, 0, 0); + } - public int Phase { get; set; } + public LoomSouthAddon(Serial serial) : base(serial) + { + } - [Constructible] - public LoomSouthAddon() - { - AddComponent( new AddonComponent( 0x1061 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1062 ), 1, 0, 0 ); - } + public override BaseAddonDeed Deed => new LoomSouthDeed(); - public LoomSouthAddon( Serial serial ) : base( serial ) - { - } + public int Phase{ get; set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) Phase ); - } + writer.Write(Phase); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Phase = reader.ReadInt(); - break; - } - } - } - } + switch (version) + { + case 1: + { + Phase = reader.ReadInt(); + break; + } + } + } + } - public class LoomSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LoomSouthAddon(); - public override int LabelNumber => 1044344; // loom (south) + public class LoomSouthDeed : BaseAddonDeed + { + [Constructible] + public LoomSouthDeed() + { + } - [Constructible] - public LoomSouthDeed() - { - } + public LoomSouthDeed(Serial serial) : base(serial) + { + } - public LoomSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LoomSouthAddon(); + public override int LabelNumber => 1044344; // loom (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/MediumStoneTableEastAddon.cs b/Scripts/Items/Addons/MediumStoneTableEastAddon.cs index 7fa53201a..18da0efa7 100644 --- a/Scripts/Items/Addons/MediumStoneTableEastAddon.cs +++ b/Scripts/Items/Addons/MediumStoneTableEastAddon.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class MediumStoneTableEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MediumStoneTableEastDeed(); + public class MediumStoneTableEastAddon : BaseAddon + { + [Constructible] + public MediumStoneTableEastAddon() : this(0) + { + } - public override bool RetainDeedHue => true; + [Constructible] + public MediumStoneTableEastAddon(int hue) + { + AddComponent(new AddonComponent(0x1202), 0, 0, 0); + AddComponent(new AddonComponent(0x1201), 0, 1, 0); + Hue = hue; + } - [Constructible] - public MediumStoneTableEastAddon() : this( 0 ) - { - } + public MediumStoneTableEastAddon(Serial serial) : base(serial) + { + } - [Constructible] - public MediumStoneTableEastAddon( int hue ) - { - AddComponent( new AddonComponent( 0x1202 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1201 ), 0, 1, 0 ); - Hue = hue; - } + public override BaseAddonDeed Deed => new MediumStoneTableEastDeed(); - public MediumStoneTableEastAddon( Serial serial ) : base( serial ) - { - } + public override bool RetainDeedHue => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MediumStoneTableEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MediumStoneTableEastAddon( Hue ); - public override int LabelNumber => 1044508; // stone table (east) + public class MediumStoneTableEastDeed : BaseAddonDeed + { + [Constructible] + public MediumStoneTableEastDeed() + { + } - [Constructible] - public MediumStoneTableEastDeed() - { - } + public MediumStoneTableEastDeed(Serial serial) : base(serial) + { + } - public MediumStoneTableEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MediumStoneTableEastAddon(Hue); + public override int LabelNumber => 1044508; // stone table (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/MediumStoneTableSouthAddon.cs b/Scripts/Items/Addons/MediumStoneTableSouthAddon.cs index cb336f8a8..2697185db 100644 --- a/Scripts/Items/Addons/MediumStoneTableSouthAddon.cs +++ b/Scripts/Items/Addons/MediumStoneTableSouthAddon.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class MediumStoneTableSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MediumStoneTableSouthDeed(); + public class MediumStoneTableSouthAddon : BaseAddon + { + [Constructible] + public MediumStoneTableSouthAddon() : this(0) + { + } - public override bool RetainDeedHue => true; + [Constructible] + public MediumStoneTableSouthAddon(int hue) + { + AddComponent(new AddonComponent(0x1205), 0, 0, 0); + AddComponent(new AddonComponent(0x1204), 1, 0, 0); + Hue = hue; + } - [Constructible] - public MediumStoneTableSouthAddon() : this( 0 ) - { - } + public MediumStoneTableSouthAddon(Serial serial) : base(serial) + { + } - [Constructible] - public MediumStoneTableSouthAddon( int hue ) - { - AddComponent( new AddonComponent( 0x1205 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1204 ), 1, 0, 0 ); - Hue = hue; - } + public override BaseAddonDeed Deed => new MediumStoneTableSouthDeed(); - public MediumStoneTableSouthAddon( Serial serial ) : base( serial ) - { - } + public override bool RetainDeedHue => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MediumStoneTableSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MediumStoneTableSouthAddon( Hue ); - public override int LabelNumber => 1044509; // stone table (South) + public class MediumStoneTableSouthDeed : BaseAddonDeed + { + [Constructible] + public MediumStoneTableSouthDeed() + { + } - [Constructible] - public MediumStoneTableSouthDeed() - { - } + public MediumStoneTableSouthDeed(Serial serial) : base(serial) + { + } - public MediumStoneTableSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MediumStoneTableSouthAddon(Hue); + public override int LabelNumber => 1044509; // stone table (South) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/OrnateElvenTableEastAddon.cs b/Scripts/Items/Addons/OrnateElvenTableEastAddon.cs index b69a438a3..e547f2c71 100644 --- a/Scripts/Items/Addons/OrnateElvenTableEastAddon.cs +++ b/Scripts/Items/Addons/OrnateElvenTableEastAddon.cs @@ -1,62 +1,62 @@ namespace Server.Items { - public class OrnateElvenTableEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new OrnateElvenTableEastDeed(); + public class OrnateElvenTableEastAddon : BaseAddon + { + [Constructible] + public OrnateElvenTableEastAddon() + { + AddComponent(new AddonComponent(0x308E), -1, 0, 0); + AddComponent(new AddonComponent(0x308D), 0, 0, 0); + AddComponent(new AddonComponent(0x308C), 1, 0, 0); + } - [Constructible] - public OrnateElvenTableEastAddon() - { - AddComponent( new AddonComponent( 0x308E ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x308D ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x308C ), 1, 0, 0 ); - } + public OrnateElvenTableEastAddon(Serial serial) : base(serial) + { + } - public OrnateElvenTableEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new OrnateElvenTableEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class OrnateElvenTableEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new OrnateElvenTableEastAddon(); - public override int LabelNumber => 1073384; // ornate table (east) + public class OrnateElvenTableEastDeed : BaseAddonDeed + { + [Constructible] + public OrnateElvenTableEastDeed() + { + } - [Constructible] - public OrnateElvenTableEastDeed() - { - } + public OrnateElvenTableEastDeed(Serial serial) : base(serial) + { + } - public OrnateElvenTableEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new OrnateElvenTableEastAddon(); + public override int LabelNumber => 1073384; // ornate table (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/OrnateElvenTableSouthAddon.cs b/Scripts/Items/Addons/OrnateElvenTableSouthAddon.cs index 41bc87b02..295f68a35 100644 --- a/Scripts/Items/Addons/OrnateElvenTableSouthAddon.cs +++ b/Scripts/Items/Addons/OrnateElvenTableSouthAddon.cs @@ -1,62 +1,62 @@ namespace Server.Items { - public class OrnateElvenTableSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new OrnateElvenTableSouthDeed(); + public class OrnateElvenTableSouthAddon : BaseAddon + { + [Constructible] + public OrnateElvenTableSouthAddon() + { + AddComponent(new AddonComponent(0x308F), 0, 1, 0); + AddComponent(new AddonComponent(0x3090), 0, 0, 0); + AddComponent(new AddonComponent(0x3091), 0, -1, 0); + } - [Constructible] - public OrnateElvenTableSouthAddon() - { - AddComponent( new AddonComponent( 0x308F ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x3090 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3091 ), 0, -1, 0 ); - } + public OrnateElvenTableSouthAddon(Serial serial) : base(serial) + { + } - public OrnateElvenTableSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new OrnateElvenTableSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class OrnateElvenTableSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new OrnateElvenTableSouthAddon(); - public override int LabelNumber => 1072869; // ornate table (south) + public class OrnateElvenTableSouthDeed : BaseAddonDeed + { + [Constructible] + public OrnateElvenTableSouthDeed() + { + } - [Constructible] - public OrnateElvenTableSouthDeed() - { - } + public OrnateElvenTableSouthDeed(Serial serial) : base(serial) + { + } - public OrnateElvenTableSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new OrnateElvenTableSouthAddon(); + public override int LabelNumber => 1072869; // ornate table (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/ParrotPerchAddon.cs b/Scripts/Items/Addons/ParrotPerchAddon.cs index 6e90c0359..6fd56fd04 100644 --- a/Scripts/Items/Addons/ParrotPerchAddon.cs +++ b/Scripts/Items/Addons/ParrotPerchAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class ParrotPerchAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ParrotPerchDeed(); + public class ParrotPerchAddon : BaseAddon + { + [Constructible] + public ParrotPerchAddon() + { + AddComponent(new AddonComponent(0x2FF4), 0, 0, 0); + } - [Constructible] - public ParrotPerchAddon() - { - AddComponent( new AddonComponent( 0x2FF4 ), 0, 0, 0 ); - } + public ParrotPerchAddon(Serial serial) : base(serial) + { + } - public ParrotPerchAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ParrotPerchDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ParrotPerchDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ParrotPerchAddon(); - public override int LabelNumber => 1072617; // parrot perch + public class ParrotPerchDeed : BaseAddonDeed + { + [Constructible] + public ParrotPerchDeed() + { + } - [Constructible] - public ParrotPerchDeed() - { - } + public ParrotPerchDeed(Serial serial) : base(serial) + { + } - public ParrotPerchDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ParrotPerchAddon(); + public override int LabelNumber => 1072617; // parrot perch - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/PentagramAddon.cs b/Scripts/Items/Addons/PentagramAddon.cs index 28af8b36e..c43a44e94 100644 --- a/Scripts/Items/Addons/PentagramAddon.cs +++ b/Scripts/Items/Addons/PentagramAddon.cs @@ -1,68 +1,68 @@ namespace Server.Items { - public class PentagramAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PentagramDeed(); + public class PentagramAddon : BaseAddon + { + [Constructible] + public PentagramAddon() + { + AddComponent(new AddonComponent(0xFE7), -1, -1, 0); + AddComponent(new AddonComponent(0xFE8), 0, -1, 0); + AddComponent(new AddonComponent(0xFEB), 1, -1, 0); + AddComponent(new AddonComponent(0xFE6), -1, 0, 0); + AddComponent(new AddonComponent(0xFEA), 0, 0, 0); + AddComponent(new AddonComponent(0xFEE), 1, 0, 0); + AddComponent(new AddonComponent(0xFE9), -1, 1, 0); + AddComponent(new AddonComponent(0xFEC), 0, 1, 0); + AddComponent(new AddonComponent(0xFED), 1, 1, 0); + } - [Constructible] - public PentagramAddon() - { - AddComponent( new AddonComponent( 0xFE7 ), -1, -1, 0 ); - AddComponent( new AddonComponent( 0xFE8 ), 0, -1, 0 ); - AddComponent( new AddonComponent( 0xFEB ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0xFE6 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0xFEA ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xFEE ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0xFE9 ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0xFEC ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0xFED ), 1, 1, 0 ); - } + public PentagramAddon(Serial serial) : base(serial) + { + } - public PentagramAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PentagramDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PentagramDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PentagramAddon(); - public override int LabelNumber => 1044328; // pentagram + public class PentagramDeed : BaseAddonDeed + { + [Constructible] + public PentagramDeed() + { + } - [Constructible] - public PentagramDeed() - { - } + public PentagramDeed(Serial serial) : base(serial) + { + } - public PentagramDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PentagramAddon(); + public override int LabelNumber => 1044328; // pentagram - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/PickpocketDips.cs b/Scripts/Items/Addons/PickpocketDips.cs index 9e3ef07a9..c548fc90e 100644 --- a/Scripts/Items/Addons/PickpocketDips.cs +++ b/Scripts/Items/Addons/PickpocketDips.cs @@ -2,256 +2,257 @@ using System; namespace Server.Items { - [Flippable( 0x1EC0, 0x1EC3 )] - public class PickpocketDip : AddonComponent - { - private Timer m_Timer; + [Flippable(0x1EC0, 0x1EC3)] + public class PickpocketDip : AddonComponent + { + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public double MinSkill { get; set; } + public PickpocketDip(int itemID) : base(itemID) + { + MinSkill = -25.0; + MaxSkill = +25.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public double MaxSkill { get; set; } + public PickpocketDip(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool Swinging => ( m_Timer != null ); + [CommandProperty(AccessLevel.GameMaster)] + public double MinSkill{ get; set; } - public PickpocketDip( int itemID ) : base( itemID ) - { - MinSkill = -25.0; - MaxSkill = +25.0; - } + [CommandProperty(AccessLevel.GameMaster)] + public double MaxSkill{ get; set; } - public void UpdateItemID() - { - int baseItemID = 0x1EC0 + (((ItemID - 0x1EC0) / 3) * 3); + [CommandProperty(AccessLevel.GameMaster)] + public bool Swinging => m_Timer != null; - ItemID = baseItemID + (Swinging ? 1 : 0); - } + public void UpdateItemID() + { + int baseItemID = 0x1EC0 + (ItemID - 0x1EC0) / 3 * 3; - public void BeginSwing() - { - m_Timer?.Stop(); + ItemID = baseItemID + (Swinging ? 1 : 0); + } - m_Timer = new InternalTimer( this ); - m_Timer.Start(); + public void BeginSwing() + { + m_Timer?.Stop(); - UpdateItemID(); - } + m_Timer = new InternalTimer(this); + m_Timer.Start(); - public void EndSwing() - { - m_Timer?.Stop(); + UpdateItemID(); + } - m_Timer = null; + public void EndSwing() + { + m_Timer?.Stop(); - UpdateItemID(); - } + m_Timer = null; - public void Use( Mobile from ) - { - from.Direction = from.GetDirectionTo( GetWorldLocation() ); + UpdateItemID(); + } - Effects.PlaySound( GetWorldLocation(), Map, 0x4F ); + public void Use(Mobile from) + { + from.Direction = from.GetDirectionTo(GetWorldLocation()); - if ( from.CheckSkill( SkillName.Stealing, MinSkill, MaxSkill ) ) - { - SendLocalizedMessageTo( from, 501834 ); // You successfully avoid disturbing the dip while searching it. - } - else - { - Effects.PlaySound( GetWorldLocation(), Map, 0x390 ); + Effects.PlaySound(GetWorldLocation(), Map, 0x4F); - BeginSwing(); - ProcessDelta(); - SendLocalizedMessageTo( from, 501831 ); // You carelessly bump the dip and start it swinging. - } - } + if (from.CheckSkill(SkillName.Stealing, MinSkill, MaxSkill)) + { + SendLocalizedMessageTo(from, 501834); // You successfully avoid disturbing the dip while searching it. + } + else + { + Effects.PlaySound(GetWorldLocation(), Map, 0x390); - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 1 ) ) - SendLocalizedMessageTo( from, 501816 ); // You are too far away to do that. - else if ( Swinging ) - SendLocalizedMessageTo( from, 501815 ); // You have to wait until it stops swinging. - else if ( from.Skills[SkillName.Stealing].Base >= MaxSkill ) - SendLocalizedMessageTo( from, 501830 ); // Your ability to steal cannot improve any further by simply practicing on a dummy. - else if ( from.Mounted ) - SendLocalizedMessageTo( from, 501829 ); // You can't practice on this while on a mount. - else - Use( from ); - } + BeginSwing(); + ProcessDelta(); + SendLocalizedMessageTo(from, 501831); // You carelessly bump the dip and start it swinging. + } + } - public PickpocketDip( Serial serial ) : base( serial ) - { - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 1)) + SendLocalizedMessageTo(from, 501816); // You are too far away to do that. + else if (Swinging) + SendLocalizedMessageTo(from, 501815); // You have to wait until it stops swinging. + else if (from.Skills[SkillName.Stealing].Base >= MaxSkill) + SendLocalizedMessageTo(from, + 501830); // Your ability to steal cannot improve any further by simply practicing on a dummy. + else if (from.Mounted) + SendLocalizedMessageTo(from, 501829); // You can't practice on this while on a mount. + else + Use(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( MinSkill ); - writer.Write( MaxSkill ); - } + writer.Write(MinSkill); + writer.Write(MaxSkill); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - MinSkill = reader.ReadDouble(); - MaxSkill = reader.ReadDouble(); + switch (version) + { + case 0: + { + MinSkill = reader.ReadDouble(); + MaxSkill = reader.ReadDouble(); - if ( MinSkill == 0.0 && MaxSkill == 30.0 ) - { - MinSkill = -25.0; - MaxSkill = +25.0; - } + if (MinSkill == 0.0 && MaxSkill == 30.0) + { + MinSkill = -25.0; + MaxSkill = +25.0; + } - break; - } - } + break; + } + } - UpdateItemID(); - } + UpdateItemID(); + } - private class InternalTimer : Timer - { - private PickpocketDip m_Dip; + private class InternalTimer : Timer + { + private PickpocketDip m_Dip; - public InternalTimer( PickpocketDip dip ) : base( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Dip = dip; - Priority = TimerPriority.FiftyMS; - } + public InternalTimer(PickpocketDip dip) : base(TimeSpan.FromSeconds(3.0)) + { + m_Dip = dip; + Priority = TimerPriority.FiftyMS; + } - protected override void OnTick() - { - m_Dip.EndSwing(); - } - } - } + protected override void OnTick() + { + m_Dip.EndSwing(); + } + } + } - public class PickpocketDipEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PickpocketDipEastDeed(); + public class PickpocketDipEastAddon : BaseAddon + { + [Constructible] + public PickpocketDipEastAddon() + { + AddComponent(new PickpocketDip(0x1EC3), 0, 0, 0); + } - [Constructible] - public PickpocketDipEastAddon() - { - AddComponent( new PickpocketDip( 0x1EC3 ), 0, 0, 0 ); - } + public PickpocketDipEastAddon(Serial serial) : base(serial) + { + } - public PickpocketDipEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PickpocketDipEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PickpocketDipEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PickpocketDipEastAddon(); - public override int LabelNumber => 1044337; // pickpocket dip (east) + public class PickpocketDipEastDeed : BaseAddonDeed + { + [Constructible] + public PickpocketDipEastDeed() + { + } - [Constructible] - public PickpocketDipEastDeed() - { - } + public PickpocketDipEastDeed(Serial serial) : base(serial) + { + } - public PickpocketDipEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PickpocketDipEastAddon(); + public override int LabelNumber => 1044337; // pickpocket dip (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PickpocketDipSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PickpocketDipSouthDeed(); + public class PickpocketDipSouthAddon : BaseAddon + { + [Constructible] + public PickpocketDipSouthAddon() + { + AddComponent(new PickpocketDip(0x1EC0), 0, 0, 0); + } - [Constructible] - public PickpocketDipSouthAddon() - { - AddComponent( new PickpocketDip( 0x1EC0 ), 0, 0, 0 ); - } + public PickpocketDipSouthAddon(Serial serial) : base(serial) + { + } - public PickpocketDipSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PickpocketDipSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PickpocketDipSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PickpocketDipSouthAddon(); - public override int LabelNumber => 1044338; // pickpocket dip (south) + public class PickpocketDipSouthDeed : BaseAddonDeed + { + [Constructible] + public PickpocketDipSouthDeed() + { + } - [Constructible] - public PickpocketDipSouthDeed() - { - } + public PickpocketDipSouthDeed(Serial serial) : base(serial) + { + } - public PickpocketDipSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PickpocketDipSouthAddon(); + public override int LabelNumber => 1044338; // pickpocket dip (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/PyramidAddon.cs b/Scripts/Items/Addons/PyramidAddon.cs index dfbc148b8..e992df070 100644 --- a/Scripts/Items/Addons/PyramidAddon.cs +++ b/Scripts/Items/Addons/PyramidAddon.cs @@ -1,53 +1,53 @@ namespace Server.Items { - public class PyramidAddon : BaseAddon - { - public override bool ShareHue => false; + public class PyramidAddon : BaseAddon + { + [Constructible] + public PyramidAddon() + { + AddComponent(new AddonComponent(1006), 0, 0, 5); - [Constructible] - public PyramidAddon() - { - AddComponent( new AddonComponent( 1006 ), 0, 0, 5 ); + for (int o = 1; o <= 2; ++o) + { + AddComponent(new AddonComponent(1011), -o, -o, (2 - o) * 5); + AddComponent(new AddonComponent(1012), +o, +o, (2 - o) * 5); + AddComponent(new AddonComponent(1013), +o, -o, (2 - o) * 5); + AddComponent(new AddonComponent(1014), -o, +o, (2 - o) * 5); + } - for ( int o = 1; o <= 2; ++o ) - { - AddComponent( new AddonComponent( 1011 ), -o, -o, ( 2 - o ) * 5 ); - AddComponent( new AddonComponent( 1012 ), +o, +o, ( 2 - o ) * 5 ); - AddComponent( new AddonComponent( 1013 ), +o, -o, ( 2 - o ) * 5 ); - AddComponent( new AddonComponent( 1014 ), -o, +o, ( 2 - o ) * 5 ); - } + for (int o = -1; o <= 1; ++o) + { + AddComponent(new AddonComponent(1007), o, 2, 0); + AddComponent(new AddonComponent(1008), 2, o, 0); + AddComponent(new AddonComponent(1009), o, -2, 0); + AddComponent(new AddonComponent(1010), -2, o, 0); + } - for ( int o = -1; o <= 1; ++o ) - { - AddComponent( new AddonComponent( 1007 ), o, 2, 0 ); - AddComponent( new AddonComponent( 1008 ), 2, o, 0 ); - AddComponent( new AddonComponent( 1009 ), o, -2, 0 ); - AddComponent( new AddonComponent( 1010 ), -2, o, 0 ); - } + AddComponent(new AddonComponent(1007), 0, 1, 5); + AddComponent(new AddonComponent(1008), 1, 0, 5); + AddComponent(new AddonComponent(1009), 0, -1, 5); + AddComponent(new AddonComponent(1010), -1, 0, 5); + } - AddComponent( new AddonComponent( 1007 ), 0, 1, 5 ); - AddComponent( new AddonComponent( 1008 ), 1, 0, 5 ); - AddComponent( new AddonComponent( 1009 ), 0, -1, 5 ); - AddComponent( new AddonComponent( 1010 ), -1, 0, 5 ); - } + public PyramidAddon(Serial serial) + : base(serial) + { + } - public PyramidAddon( Serial serial ) - : base( serial ) - { - } + public override bool ShareHue => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/RejuvinationAnkhs.cs b/Scripts/Items/Addons/RejuvinationAnkhs.cs index 8df358d84..46975eb2d 100644 --- a/Scripts/Items/Addons/RejuvinationAnkhs.cs +++ b/Scripts/Items/Addons/RejuvinationAnkhs.cs @@ -2,177 +2,176 @@ using System; namespace Server.Items { - public class RejuvinationAddonComponent : AddonComponent - { - public RejuvinationAddonComponent( int itemID ) : base( itemID ) - { - } + public class RejuvinationAddonComponent : AddonComponent + { + public RejuvinationAddonComponent(int itemID) : base(itemID) + { + } - public RejuvinationAddonComponent( Serial serial ) : base( serial ) - { - } + public RejuvinationAddonComponent(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.BeginAction( typeof( RejuvinationAddonComponent ) ) ) - { - from.FixedEffect( 0x373A, 1, 16 ); + public override void OnDoubleClick(Mobile from) + { + if (from.BeginAction(typeof(RejuvinationAddonComponent))) + { + from.FixedEffect(0x373A, 1, 16); - int random = Utility.Random( 1, 4 ); + int random = Utility.Random(1, 4); - if ( random == 1 || random == 4 ) - { - from.Hits = from.HitsMax; - SendLocalizedMessageTo( from, 500801 ); // A sense of warmth fills your body! - } + if (random == 1 || random == 4) + { + from.Hits = from.HitsMax; + SendLocalizedMessageTo(from, 500801); // A sense of warmth fills your body! + } - if ( random == 2 || random == 4 ) - { - from.Mana = from.ManaMax; - SendLocalizedMessageTo( from, 500802 ); // A feeling of power surges through your veins! - } + if (random == 2 || random == 4) + { + from.Mana = from.ManaMax; + SendLocalizedMessageTo(from, 500802); // A feeling of power surges through your veins! + } - if ( random == 3 || random == 4 ) - { - from.Stam = from.StamMax; - SendLocalizedMessageTo( from, 500803 ); // You feel as though you've slept for days! - } + if (random == 3 || random == 4) + { + from.Stam = from.StamMax; + SendLocalizedMessageTo(from, 500803); // You feel as though you've slept for days! + } - Timer.DelayCall( TimeSpan.FromHours( 2.0 ), new TimerStateCallback( ReleaseUseLock_Callback ), new object[]{ from, random } ); - } - } + Timer.DelayCall(TimeSpan.FromHours(2.0), new TimerStateCallback(ReleaseUseLock_Callback), + new object[] { from, random }); + } + } - public virtual void ReleaseUseLock_Callback( object state ) - { - object[] states = (object[])state; + public virtual void ReleaseUseLock_Callback(object state) + { + object[] states = (object[])state; - Mobile from = (Mobile)states[0]; - int random = (int)states[1]; + Mobile from = (Mobile)states[0]; + int random = (int)states[1]; - from.EndAction( typeof( RejuvinationAddonComponent ) ); + from.EndAction(typeof(RejuvinationAddonComponent)); - if ( random == 4 ) - { - from.Hits = from.HitsMax; - from.Mana = from.ManaMax; - from.Stam = from.StamMax; - SendLocalizedMessageTo( from, 500807 ); // You feel completely rejuvinated! - } - } + if (random == 4) + { + from.Hits = from.HitsMax; + from.Mana = from.ManaMax; + from.Stam = from.StamMax; + SendLocalizedMessageTo(from, 500807); // You feel completely rejuvinated! + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public abstract class BaseRejuvinationAnkh : BaseAddon - { - public BaseRejuvinationAnkh() - { - } + public abstract class BaseRejuvinationAnkh : BaseAddon + { + private DateTime m_NextMessage; - public override bool HandlesOnMovement => true; + public BaseRejuvinationAnkh() + { + } - private DateTime m_NextMessage; + public BaseRejuvinationAnkh(Serial serial) : base(serial) + { + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + public override bool HandlesOnMovement => true; - if ( m.Player && Utility.InRange( Location, m.Location, 3 ) && !Utility.InRange( Location, oldLocation, 3 ) ) - { - if ( DateTime.UtcNow >= m_NextMessage ) - { - if ( Components.Count > 0 ) - ((AddonComponent)Components[0]).SendLocalizedMessageTo( m, 1010061 ); // An overwhelming sense of peace fills you. + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - m_NextMessage = DateTime.UtcNow + TimeSpan.FromSeconds( 25.0 ); - } - } - } + if (m.Player && Utility.InRange(Location, m.Location, 3) && !Utility.InRange(Location, oldLocation, 3)) + if (DateTime.UtcNow >= m_NextMessage) + { + if (Components.Count > 0) + Components[0].SendLocalizedMessageTo(m, 1010061); // An overwhelming sense of peace fills you. - public BaseRejuvinationAnkh( Serial serial ) : base( serial ) - { - } + m_NextMessage = DateTime.UtcNow + TimeSpan.FromSeconds(25.0); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class RejuvinationAnkhWest : BaseRejuvinationAnkh - { - [Constructible] - public RejuvinationAnkhWest() - { - AddComponent( new RejuvinationAddonComponent( 0x3 ), 0, 0, 0 ); - AddComponent( new RejuvinationAddonComponent( 0x2 ), 0, 1, 0 ); - } + public class RejuvinationAnkhWest : BaseRejuvinationAnkh + { + [Constructible] + public RejuvinationAnkhWest() + { + AddComponent(new RejuvinationAddonComponent(0x3), 0, 0, 0); + AddComponent(new RejuvinationAddonComponent(0x2), 0, 1, 0); + } - public RejuvinationAnkhWest( Serial serial ) : base( serial ) - { - } + public RejuvinationAnkhWest(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class RejuvinationAnkhNorth : BaseRejuvinationAnkh - { - [Constructible] - public RejuvinationAnkhNorth() - { - AddComponent( new RejuvinationAddonComponent( 0x4 ), 0, 0, 0 ); - AddComponent( new RejuvinationAddonComponent( 0x5 ), 1, 0, 0 ); - } + public class RejuvinationAnkhNorth : BaseRejuvinationAnkh + { + [Constructible] + public RejuvinationAnkhNorth() + { + AddComponent(new RejuvinationAddonComponent(0x4), 0, 0, 0); + AddComponent(new RejuvinationAddonComponent(0x5), 1, 0, 0); + } - public RejuvinationAnkhNorth( Serial serial ) : base( serial ) - { - } + public RejuvinationAnkhNorth(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SHTeleporter.cs b/Scripts/Items/Addons/SHTeleporter.cs index 3eb62c7b7..f028f2744 100644 --- a/Scripts/Items/Addons/SHTeleporter.cs +++ b/Scripts/Items/Addons/SHTeleporter.cs @@ -1,437 +1,438 @@ using System; using Server.Commands; +using Server.Mobiles; namespace Server.Items { - public class SHTeleComponent : AddonComponent - { - private bool m_Active; - private SHTeleComponent m_TeleDest; - - [CommandProperty( AccessLevel.GameMaster )] - public bool Active - { - get => m_Active; - set - { - m_Active = value; - - if ( Addon is SHTeleporter sourceAddon ) - sourceAddon.ChangeActive( value ); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D TeleOffset { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public Point3D TelePoint - { - get => new Point3D( Location.X + TeleOffset.X, Location.Y + TeleOffset.Y, Location.Z + TeleOffset.Z ); - set => TeleOffset = new Point3D( value.X - Location.X, value.Y - Location.Y, value.Z - Location.Z ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public SHTeleComponent TeleDest - { - get => m_TeleDest; - set - { - m_TeleDest = value; - - if ( Addon is SHTeleporter sourceAddon ) - sourceAddon.ChangeDest( value ); - } - } - - public override string DefaultName => "a hole"; - - [Constructible] - public SHTeleComponent() : this( 0x1775 ) - { - } - - [Constructible] - public SHTeleComponent( int itemID ) : this( itemID, new Point3D( 0, 0, 0 ) ) - { - } - - [Constructible] - public SHTeleComponent( int itemID, Point3D offset ) : base( itemID ) - { - Movable = false; - Hue = 1; - - m_Active = true; - TeleOffset = offset; - } - - public SHTeleComponent( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile m ) - { - if ( !m_Active || m_TeleDest == null || m_TeleDest.Deleted || m_TeleDest.Map == Map.Internal ) - return; - - if ( m.InRange( this, 3 ) ) - { - Map map = m_TeleDest.Map; - Point3D p = m_TeleDest.TelePoint; - - Mobiles.BaseCreature.TeleportPets( m, p, map ); - - m.MoveToWorld( p, map ); - } - else - { - m.SendLocalizedMessage( 1019045 ); // I can't reach that. - } - } - - public override void OnDoubleClickDead( Mobile m ) - { - OnDoubleClick( m ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - - writer.Write( m_Active ); - writer.Write( m_TeleDest ); - writer.Write( TeleOffset ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Active = reader.ReadBool(); - m_TeleDest = reader.ReadItem() as SHTeleComponent; - TeleOffset = reader.ReadPoint3D(); - } - } - - public class SHTeleporter : BaseAddon - { - public static void Initialize() - { - CommandSystem.Register( "SHTelGen", AccessLevel.Administrator, SHTelGen_OnCommand ); - } - - [Usage( "SHTelGen" )] - [Description( "Generates solen hives teleporters." )] - public static void SHTelGen_OnCommand( CommandEventArgs e ) - { - World.Broadcast( 0x35, true, "Solen hives teleporters are being generated, please wait." ); - - DateTime startTime = DateTime.UtcNow; - - int count = new SHTeleporterCreator().CreateSHTeleporters(); - - DateTime endTime = DateTime.UtcNow; - - World.Broadcast( 0x35, true, "{0} solen hives teleporters have been created. The entire process took {1:F1} seconds.", count, (endTime - startTime).TotalSeconds ); - } - - public class SHTeleporterCreator - { - private int m_Count; - - public SHTeleporterCreator() - { - m_Count = 0; - } - - public static SHTeleporter FindSHTeleporter( Map map, Point3D p ) - { - IPooledEnumerable eable = map.GetItemsInRange( p, 0 ); - - foreach (SHTeleporter item in eable ) - { - if ( item.Z == p.Z ) - { - eable.Free(); - return item; - } - } - - eable.Free(); - return null; - } - - public SHTeleporter AddSHT( Map map, bool ext, int x, int y, int z ) - { - Point3D p = new Point3D( x, y, z ); - SHTeleporter tele = FindSHTeleporter( map, p ); - - if ( tele == null ) - { - tele = new SHTeleporter( ext ); - tele.MoveToWorld( p, map ); - - m_Count++; - } - - return tele; - } - - public static void Link( SHTeleporter tele1, SHTeleporter tele2 ) - { - tele1.ChangeDest( tele2 ); - tele2.ChangeDest( tele1 ); - } - - public void AddSHTCouple( Map map, bool ext1, int x1, int y1, int z1, bool ext2, int x2, int y2, int z2 ) - { - SHTeleporter tele1 = AddSHT( map, ext1, x1, y1, z1 ); - SHTeleporter tele2 = AddSHT( map, ext2, x2, y2, z2 ); - - Link( tele1, tele2 ); - } - - public void AddSHTCouple( bool ext1, int x1, int y1, int z1, bool ext2, int x2, int y2, int z2 ) - { - AddSHTCouple( Map.Trammel, ext1, x1, y1, z1, ext2, x2, y2, z2 ); - AddSHTCouple( Map.Felucca, ext1, x1, y1, z1, ext2, x2, y2, z2 ); - } - - public int CreateSHTeleporters() - { - SHTeleporter tele1, tele2; - - AddSHTCouple( true, 2608, 763, 0, false, 5918, 1794, 0 ); - AddSHTCouple( false, 5897, 1877, 0, false, 5871, 1867, 0 ); - AddSHTCouple( false, 5852, 1848, 0, false, 5771, 1867, 0 ); - - tele1 = AddSHT( Map.Trammel, false, 5747, 1895, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Trammel, false, 5658, 1898, 0 ); - Link( tele1, tele2 ); - - tele1 = AddSHT( Map.Felucca, false, 5747, 1895, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Felucca, false, 5658, 1898, 0 ); - Link( tele1, tele2 ); - - AddSHTCouple( false, 5727, 1894, 0, false, 5756, 1794, 0 ); - AddSHTCouple( false, 5784, 1929, 0, false, 5700, 1929, 0 ); - - tele1 = AddSHT( Map.Trammel, false, 5711, 1952, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Trammel, false, 5657, 1954, 0 ); - Link( tele1, tele2 ); - - tele1 = AddSHT( Map.Felucca, false, 5711, 1952, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Felucca, false, 5657, 1954, 0 ); - Link( tele1, tele2 ); - - tele1 = AddSHT( Map.Trammel, false, 5655, 2018, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Trammel, true, 1690, 2789, 0 ); - Link( tele1, tele2 ); - - tele1 = AddSHT( Map.Felucca, false, 5655, 2018, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Felucca, true, 1690, 2789, 0 ); - Link( tele1, tele2 ); - - AddSHTCouple( false, 5809, 1905, 0, false, 5876, 1891, 0 ); - - tele1 = AddSHT( Map.Trammel, false, 5814, 2015, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Trammel, false, 5913, 1893, 0 ); - Link( tele1, tele2 ); - - tele1 = AddSHT( Map.Felucca, false, 5814, 2015, 0 ); - tele1.LeftTele.TeleOffset = new Point3D( -1, 3, 0 ); - tele2 = AddSHT( Map.Felucca, false, 5913, 1893, 0 ); - Link( tele1, tele2 ); - - AddSHTCouple( false, 5919, 2021, 0, true, 1724, 814, 0 ); - - tele1 = AddSHT( Map.Trammel, false, 5654, 1791, 0 ); - tele2 = AddSHT( Map.Trammel, true, 730, 1451, 0 ); - Link( tele1, tele2 ); - AddSHT( Map.Trammel, false, 5734, 1859, 0 ).ChangeDest( tele2 ); - - tele1 = AddSHT( Map.Felucca, false, 5654, 1791, 0 ); - tele2 = AddSHT( Map.Felucca, true, 730, 1451, 0 ); - Link( tele1, tele2 ); - AddSHT( Map.Felucca, false, 5734, 1859, 0 ).ChangeDest( tele2 ); - - return m_Count; - } - } - - private bool m_Changing; - - [CommandProperty( AccessLevel.GameMaster )] - public bool External { get; private set; } - - public SHTeleComponent UpTele { get; private set; } - - public SHTeleComponent RightTele { get; private set; } - - public SHTeleComponent DownTele { get; private set; } - - public SHTeleComponent LeftTele { get; private set; } - - [Constructible] - public SHTeleporter() : this( true ) - { - } - - [Constructible] - public SHTeleporter( bool external ) - { - m_Changing = false; - External = external; - - if ( external ) - { - AddComponent( new AddonComponent( 0x549 ), -1, -1, 0 ); - AddComponent( new AddonComponent( 0x54D ), 0, -1, 0 ); - AddComponent( new AddonComponent( 0x54E ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0x548 ), 2, -1, 0 ); - AddComponent( new AddonComponent( 0x54B ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x53B ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x53B ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x544 ), 2, 0, 0 ); - AddComponent( new AddonComponent( 0x54C ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0x53B ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x53B ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x545 ), 2, 1, 0 ); - AddComponent( new AddonComponent( 0x547 ), -1, 2, 0 ); - AddComponent( new AddonComponent( 0x541 ), 0, 2, 0 ); - AddComponent( new AddonComponent( 0x543 ), 1, 2, 0 ); - AddComponent( new AddonComponent( 0x540 ), 2, 2, 0 ); - } - - Point3D upOS = external ? new Point3D( -1, 0, 0 ) : new Point3D( -2, -1, 0 ); - UpTele = new SHTeleComponent( external ? 0x1775 : 0x495, upOS ); - AddComponent( UpTele, 0, 0, 0 ); - - Point3D rightOS = external ? new Point3D( -2, 0, 0 ) : new Point3D( 2, -1, 0 ); - RightTele = new SHTeleComponent( external ? 0x1775 : 0x495, rightOS ); - AddComponent( RightTele, 1, 0, 0 ); - - Point3D downOS = external ? new Point3D( -2, -1, 0 ) : new Point3D( 2, 2, 0 ); - DownTele = new SHTeleComponent( external ? 0x1776 : 0x495, downOS ); - AddComponent( DownTele, 1, 1, 0 ); - - Point3D leftOS = external ? new Point3D( -1, -1, 0 ) : new Point3D( -1, 2, 0 ); - LeftTele = new SHTeleComponent( external ? 0x1775 : 0x495, leftOS ); - AddComponent( LeftTele, 0, 1, 0 ); - } - - public SHTeleporter( Serial serial ) : base( serial ) - { - m_Changing = false; - } - - public override bool ShareHue => false; - - public void ChangeActive( bool active ) - { - if ( m_Changing ) - return; - - m_Changing = true; - - UpTele.Active = active; - RightTele.Active = active; - DownTele.Active = active; - LeftTele.Active = active; - - m_Changing = false; - } - - public void ChangeDest( SHTeleComponent dest ) - { - if ( m_Changing ) - return; - - m_Changing = true; - - if ( !(dest?.Addon is SHTeleporter) ) - { - UpTele.TeleDest = dest; - RightTele.TeleDest = dest; - DownTele.TeleDest = dest; - LeftTele.TeleDest = dest; - } - else - { - SHTeleporter destAddon = (SHTeleporter)dest.Addon; - - UpTele.TeleDest = destAddon.UpTele; - RightTele.TeleDest = destAddon.RightTele; - DownTele.TeleDest = destAddon.DownTele; - LeftTele.TeleDest = destAddon.LeftTele; - } - - m_Changing = false; - } - - public void ChangeDest( SHTeleporter destAddon ) - { - if ( m_Changing ) - return; - - m_Changing = true; - - if ( destAddon != null ) - { - UpTele.TeleDest = destAddon.UpTele; - RightTele.TeleDest = destAddon.RightTele; - DownTele.TeleDest = destAddon.DownTele; - LeftTele.TeleDest = destAddon.LeftTele; - } - else - { - UpTele.TeleDest = null; - RightTele.TeleDest = null; - DownTele.TeleDest = null; - LeftTele.TeleDest = null; - } - - m_Changing = false; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - - writer.Write( External ); - - writer.Write( UpTele ); - writer.Write( RightTele ); - writer.Write( DownTele ); - writer.Write( LeftTele ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - External = reader.ReadBool(); - - UpTele = (SHTeleComponent)reader.ReadItem(); - RightTele = (SHTeleComponent)reader.ReadItem(); - DownTele = (SHTeleComponent)reader.ReadItem(); - LeftTele = (SHTeleComponent)reader.ReadItem(); - } - } -} + public class SHTeleComponent : AddonComponent + { + private bool m_Active; + private SHTeleComponent m_TeleDest; + + [Constructible] + public SHTeleComponent() : this(0x1775) + { + } + + [Constructible] + public SHTeleComponent(int itemID) : this(itemID, new Point3D(0, 0, 0)) + { + } + + [Constructible] + public SHTeleComponent(int itemID, Point3D offset) : base(itemID) + { + Movable = false; + Hue = 1; + + m_Active = true; + TeleOffset = offset; + } + + public SHTeleComponent(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Active + { + get => m_Active; + set + { + m_Active = value; + + if (Addon is SHTeleporter sourceAddon) + sourceAddon.ChangeActive(value); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D TeleOffset{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D TelePoint + { + get => new Point3D(Location.X + TeleOffset.X, Location.Y + TeleOffset.Y, Location.Z + TeleOffset.Z); + set => TeleOffset = new Point3D(value.X - Location.X, value.Y - Location.Y, value.Z - Location.Z); + } + + [CommandProperty(AccessLevel.GameMaster)] + public SHTeleComponent TeleDest + { + get => m_TeleDest; + set + { + m_TeleDest = value; + + if (Addon is SHTeleporter sourceAddon) + sourceAddon.ChangeDest(value); + } + } + + public override string DefaultName => "a hole"; + + public override void OnDoubleClick(Mobile m) + { + if (!m_Active || m_TeleDest == null || m_TeleDest.Deleted || m_TeleDest.Map == Map.Internal) + return; + + if (m.InRange(this, 3)) + { + Map map = m_TeleDest.Map; + Point3D p = m_TeleDest.TelePoint; + + BaseCreature.TeleportPets(m, p, map); + + m.MoveToWorld(p, map); + } + else + { + m.SendLocalizedMessage(1019045); // I can't reach that. + } + } + + public override void OnDoubleClickDead(Mobile m) + { + OnDoubleClick(m); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Active); + writer.Write(m_TeleDest); + writer.Write(TeleOffset); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Active = reader.ReadBool(); + m_TeleDest = reader.ReadItem() as SHTeleComponent; + TeleOffset = reader.ReadPoint3D(); + } + } + + public class SHTeleporter : BaseAddon + { + private bool m_Changing; + + [Constructible] + public SHTeleporter() : this(true) + { + } + + [Constructible] + public SHTeleporter(bool external) + { + m_Changing = false; + External = external; + + if (external) + { + AddComponent(new AddonComponent(0x549), -1, -1, 0); + AddComponent(new AddonComponent(0x54D), 0, -1, 0); + AddComponent(new AddonComponent(0x54E), 1, -1, 0); + AddComponent(new AddonComponent(0x548), 2, -1, 0); + AddComponent(new AddonComponent(0x54B), -1, 0, 0); + AddComponent(new AddonComponent(0x53B), 0, 0, 0); + AddComponent(new AddonComponent(0x53B), 1, 0, 0); + AddComponent(new AddonComponent(0x544), 2, 0, 0); + AddComponent(new AddonComponent(0x54C), -1, 1, 0); + AddComponent(new AddonComponent(0x53B), 0, 1, 0); + AddComponent(new AddonComponent(0x53B), 1, 1, 0); + AddComponent(new AddonComponent(0x545), 2, 1, 0); + AddComponent(new AddonComponent(0x547), -1, 2, 0); + AddComponent(new AddonComponent(0x541), 0, 2, 0); + AddComponent(new AddonComponent(0x543), 1, 2, 0); + AddComponent(new AddonComponent(0x540), 2, 2, 0); + } + + Point3D upOS = external ? new Point3D(-1, 0, 0) : new Point3D(-2, -1, 0); + UpTele = new SHTeleComponent(external ? 0x1775 : 0x495, upOS); + AddComponent(UpTele, 0, 0, 0); + + Point3D rightOS = external ? new Point3D(-2, 0, 0) : new Point3D(2, -1, 0); + RightTele = new SHTeleComponent(external ? 0x1775 : 0x495, rightOS); + AddComponent(RightTele, 1, 0, 0); + + Point3D downOS = external ? new Point3D(-2, -1, 0) : new Point3D(2, 2, 0); + DownTele = new SHTeleComponent(external ? 0x1776 : 0x495, downOS); + AddComponent(DownTele, 1, 1, 0); + + Point3D leftOS = external ? new Point3D(-1, -1, 0) : new Point3D(-1, 2, 0); + LeftTele = new SHTeleComponent(external ? 0x1775 : 0x495, leftOS); + AddComponent(LeftTele, 0, 1, 0); + } + + public SHTeleporter(Serial serial) : base(serial) + { + m_Changing = false; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool External{ get; private set; } + + public SHTeleComponent UpTele{ get; private set; } + + public SHTeleComponent RightTele{ get; private set; } + + public SHTeleComponent DownTele{ get; private set; } + + public SHTeleComponent LeftTele{ get; private set; } + + public override bool ShareHue => false; + + public static void Initialize() + { + CommandSystem.Register("SHTelGen", AccessLevel.Administrator, SHTelGen_OnCommand); + } + + [Usage("SHTelGen")] + [Description("Generates solen hives teleporters.")] + public static void SHTelGen_OnCommand(CommandEventArgs e) + { + World.Broadcast(0x35, true, "Solen hives teleporters are being generated, please wait."); + + DateTime startTime = DateTime.UtcNow; + + int count = new SHTeleporterCreator().CreateSHTeleporters(); + + DateTime endTime = DateTime.UtcNow; + + World.Broadcast(0x35, true, + "{0} solen hives teleporters have been created. The entire process took {1:F1} seconds.", count, + (endTime - startTime).TotalSeconds); + } + + public void ChangeActive(bool active) + { + if (m_Changing) + return; + + m_Changing = true; + + UpTele.Active = active; + RightTele.Active = active; + DownTele.Active = active; + LeftTele.Active = active; + + m_Changing = false; + } + + public void ChangeDest(SHTeleComponent dest) + { + if (m_Changing) + return; + + m_Changing = true; + + if (!(dest?.Addon is SHTeleporter)) + { + UpTele.TeleDest = dest; + RightTele.TeleDest = dest; + DownTele.TeleDest = dest; + LeftTele.TeleDest = dest; + } + else + { + SHTeleporter destAddon = (SHTeleporter)dest.Addon; + + UpTele.TeleDest = destAddon.UpTele; + RightTele.TeleDest = destAddon.RightTele; + DownTele.TeleDest = destAddon.DownTele; + LeftTele.TeleDest = destAddon.LeftTele; + } + + m_Changing = false; + } + + public void ChangeDest(SHTeleporter destAddon) + { + if (m_Changing) + return; + + m_Changing = true; + + if (destAddon != null) + { + UpTele.TeleDest = destAddon.UpTele; + RightTele.TeleDest = destAddon.RightTele; + DownTele.TeleDest = destAddon.DownTele; + LeftTele.TeleDest = destAddon.LeftTele; + } + else + { + UpTele.TeleDest = null; + RightTele.TeleDest = null; + DownTele.TeleDest = null; + LeftTele.TeleDest = null; + } + + m_Changing = false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(External); + + writer.Write(UpTele); + writer.Write(RightTele); + writer.Write(DownTele); + writer.Write(LeftTele); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + External = reader.ReadBool(); + + UpTele = (SHTeleComponent)reader.ReadItem(); + RightTele = (SHTeleComponent)reader.ReadItem(); + DownTele = (SHTeleComponent)reader.ReadItem(); + LeftTele = (SHTeleComponent)reader.ReadItem(); + } + + public class SHTeleporterCreator + { + private int m_Count; + + public SHTeleporterCreator() + { + m_Count = 0; + } + + public static SHTeleporter FindSHTeleporter(Map map, Point3D p) + { + IPooledEnumerable eable = map.GetItemsInRange(p, 0); + + foreach (SHTeleporter item in eable) + if (item.Z == p.Z) + { + eable.Free(); + return item; + } + + eable.Free(); + return null; + } + + public SHTeleporter AddSHT(Map map, bool ext, int x, int y, int z) + { + Point3D p = new Point3D(x, y, z); + SHTeleporter tele = FindSHTeleporter(map, p); + + if (tele == null) + { + tele = new SHTeleporter(ext); + tele.MoveToWorld(p, map); + + m_Count++; + } + + return tele; + } + + public static void Link(SHTeleporter tele1, SHTeleporter tele2) + { + tele1.ChangeDest(tele2); + tele2.ChangeDest(tele1); + } + + public void AddSHTCouple(Map map, bool ext1, int x1, int y1, int z1, bool ext2, int x2, int y2, int z2) + { + SHTeleporter tele1 = AddSHT(map, ext1, x1, y1, z1); + SHTeleporter tele2 = AddSHT(map, ext2, x2, y2, z2); + + Link(tele1, tele2); + } + + public void AddSHTCouple(bool ext1, int x1, int y1, int z1, bool ext2, int x2, int y2, int z2) + { + AddSHTCouple(Map.Trammel, ext1, x1, y1, z1, ext2, x2, y2, z2); + AddSHTCouple(Map.Felucca, ext1, x1, y1, z1, ext2, x2, y2, z2); + } + + public int CreateSHTeleporters() + { + SHTeleporter tele1, tele2; + + AddSHTCouple(true, 2608, 763, 0, false, 5918, 1794, 0); + AddSHTCouple(false, 5897, 1877, 0, false, 5871, 1867, 0); + AddSHTCouple(false, 5852, 1848, 0, false, 5771, 1867, 0); + + tele1 = AddSHT(Map.Trammel, false, 5747, 1895, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Trammel, false, 5658, 1898, 0); + Link(tele1, tele2); + + tele1 = AddSHT(Map.Felucca, false, 5747, 1895, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Felucca, false, 5658, 1898, 0); + Link(tele1, tele2); + + AddSHTCouple(false, 5727, 1894, 0, false, 5756, 1794, 0); + AddSHTCouple(false, 5784, 1929, 0, false, 5700, 1929, 0); + + tele1 = AddSHT(Map.Trammel, false, 5711, 1952, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Trammel, false, 5657, 1954, 0); + Link(tele1, tele2); + + tele1 = AddSHT(Map.Felucca, false, 5711, 1952, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Felucca, false, 5657, 1954, 0); + Link(tele1, tele2); + + tele1 = AddSHT(Map.Trammel, false, 5655, 2018, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Trammel, true, 1690, 2789, 0); + Link(tele1, tele2); + + tele1 = AddSHT(Map.Felucca, false, 5655, 2018, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Felucca, true, 1690, 2789, 0); + Link(tele1, tele2); + + AddSHTCouple(false, 5809, 1905, 0, false, 5876, 1891, 0); + + tele1 = AddSHT(Map.Trammel, false, 5814, 2015, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Trammel, false, 5913, 1893, 0); + Link(tele1, tele2); + + tele1 = AddSHT(Map.Felucca, false, 5814, 2015, 0); + tele1.LeftTele.TeleOffset = new Point3D(-1, 3, 0); + tele2 = AddSHT(Map.Felucca, false, 5913, 1893, 0); + Link(tele1, tele2); + + AddSHTCouple(false, 5919, 2021, 0, true, 1724, 814, 0); + + tele1 = AddSHT(Map.Trammel, false, 5654, 1791, 0); + tele2 = AddSHT(Map.Trammel, true, 730, 1451, 0); + Link(tele1, tele2); + AddSHT(Map.Trammel, false, 5734, 1859, 0).ChangeDest(tele2); + + tele1 = AddSHT(Map.Felucca, false, 5654, 1791, 0); + tele2 = AddSHT(Map.Felucca, true, 730, 1451, 0); + Link(tele1, tele2); + AddSHT(Map.Felucca, false, 5734, 1859, 0).ChangeDest(tele2); + + return m_Count; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SandstoneFireplaceEastAddon.cs b/Scripts/Items/Addons/SandstoneFireplaceEastAddon.cs index 50cd97168..030674523 100644 --- a/Scripts/Items/Addons/SandstoneFireplaceEastAddon.cs +++ b/Scripts/Items/Addons/SandstoneFireplaceEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class SandstoneFireplaceEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SandstoneFireplaceEastDeed(); + public class SandstoneFireplaceEastAddon : BaseAddon + { + [Constructible] + public SandstoneFireplaceEastAddon() + { + AddComponent(new AddonComponent(0x489), 0, 0, 0); + AddComponent(new AddonComponent(0x475), 0, 1, 0); + } - [Constructible] - public SandstoneFireplaceEastAddon() - { - AddComponent( new AddonComponent( 0x489 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x475 ), 0, 1, 0 ); - } + public SandstoneFireplaceEastAddon(Serial serial) : base(serial) + { + } - public SandstoneFireplaceEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SandstoneFireplaceEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SandstoneFireplaceEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SandstoneFireplaceEastAddon(); - public override int LabelNumber => 1061844; // sandstone fireplace (east) + public class SandstoneFireplaceEastDeed : BaseAddonDeed + { + [Constructible] + public SandstoneFireplaceEastDeed() + { + } - [Constructible] - public SandstoneFireplaceEastDeed() - { - } + public SandstoneFireplaceEastDeed(Serial serial) : base(serial) + { + } - public SandstoneFireplaceEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SandstoneFireplaceEastAddon(); + public override int LabelNumber => 1061844; // sandstone fireplace (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SandstoneFireplaceSouthAddon.cs b/Scripts/Items/Addons/SandstoneFireplaceSouthAddon.cs index bb5d7f21f..ac8180275 100644 --- a/Scripts/Items/Addons/SandstoneFireplaceSouthAddon.cs +++ b/Scripts/Items/Addons/SandstoneFireplaceSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class SandstoneFireplaceSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SandstoneFireplaceSouthDeed(); + public class SandstoneFireplaceSouthAddon : BaseAddon + { + [Constructible] + public SandstoneFireplaceSouthAddon() + { + AddComponent(new AddonComponent(0x482), -1, 0, 0); + AddComponent(new AddonComponent(0x47B), 0, 0, 0); + } - [Constructible] - public SandstoneFireplaceSouthAddon() - { - AddComponent( new AddonComponent( 0x482 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x47B ), 0, 0, 0 ); - } + public SandstoneFireplaceSouthAddon(Serial serial) : base(serial) + { + } - public SandstoneFireplaceSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SandstoneFireplaceSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SandstoneFireplaceSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SandstoneFireplaceSouthAddon(); - public override int LabelNumber => 1061845; // sandstone fireplace (south) + public class SandstoneFireplaceSouthDeed : BaseAddonDeed + { + [Constructible] + public SandstoneFireplaceSouthDeed() + { + } - [Constructible] - public SandstoneFireplaceSouthDeed() - { - } + public SandstoneFireplaceSouthDeed(Serial serial) : base(serial) + { + } - public SandstoneFireplaceSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SandstoneFireplaceSouthAddon(); + public override int LabelNumber => 1061845; // sandstone fireplace (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SandstoneFountainAddon.cs b/Scripts/Items/Addons/SandstoneFountainAddon.cs index bfe9db965..d6c91219e 100644 --- a/Scripts/Items/Addons/SandstoneFountainAddon.cs +++ b/Scripts/Items/Addons/SandstoneFountainAddon.cs @@ -1,51 +1,51 @@ namespace Server.Items { - public class SandstoneFountainAddon : BaseAddon - { - [Constructible] - public SandstoneFountainAddon() - { - int itemID = 0x19C3; + public class SandstoneFountainAddon : BaseAddon + { + [Constructible] + public SandstoneFountainAddon() + { + int itemID = 0x19C3; - AddComponent( new AddonComponent( itemID++ ), -2, +1, 0 ); - AddComponent( new AddonComponent( itemID++ ), -1, +1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +0, +1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +1, +1, 0 ); + AddComponent(new AddonComponent(itemID++), -2, +1, 0); + AddComponent(new AddonComponent(itemID++), -1, +1, 0); + AddComponent(new AddonComponent(itemID++), +0, +1, 0); + AddComponent(new AddonComponent(itemID++), +1, +1, 0); - AddComponent( new AddonComponent( itemID++ ), +1, +0, 0 ); - AddComponent( new AddonComponent( itemID++ ), +1, -1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +1, -2, 0 ); + AddComponent(new AddonComponent(itemID++), +1, +0, 0); + AddComponent(new AddonComponent(itemID++), +1, -1, 0); + AddComponent(new AddonComponent(itemID++), +1, -2, 0); - AddComponent( new AddonComponent( itemID++ ), +0, -2, 0 ); - AddComponent( new AddonComponent( itemID++ ), +0, -1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +0, +0, 0 ); + AddComponent(new AddonComponent(itemID++), +0, -2, 0); + AddComponent(new AddonComponent(itemID++), +0, -1, 0); + AddComponent(new AddonComponent(itemID++), +0, +0, 0); - AddComponent( new AddonComponent( itemID++ ), -1, +0, 0 ); - AddComponent( new AddonComponent( itemID++ ), -2, +0, 0 ); + AddComponent(new AddonComponent(itemID++), -1, +0, 0); + AddComponent(new AddonComponent(itemID++), -2, +0, 0); - AddComponent( new AddonComponent( itemID++ ), -2, -1, 0 ); - AddComponent( new AddonComponent( itemID++ ), -1, -1, 0 ); + AddComponent(new AddonComponent(itemID++), -2, -1, 0); + AddComponent(new AddonComponent(itemID++), -1, -1, 0); - AddComponent( new AddonComponent( itemID++ ), -1, -2, 0 ); - AddComponent( new AddonComponent( ++itemID ), -2, -2, 0 ); - } + AddComponent(new AddonComponent(itemID++), -1, -2, 0); + AddComponent(new AddonComponent(++itemID), -2, -2, 0); + } - public SandstoneFountainAddon( Serial serial ) : base( serial ) - { - } + public SandstoneFountainAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/SerpentPillarAddon.cs b/Scripts/Items/Addons/SerpentPillarAddon.cs index fcce10816..64f1186f4 100644 --- a/Scripts/Items/Addons/SerpentPillarAddon.cs +++ b/Scripts/Items/Addons/SerpentPillarAddon.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class SerpentPillarAddon : BaseAddon - { - [Constructible] - public SerpentPillarAddon() - { - AddComponent( new AddonComponent( 9020 ), -2, +1, 0 ); - AddComponent( new AddonComponent( 9021 ), -2, +0, 0 ); - AddComponent( new AddonComponent( 9022 ), -2, -1, 0 ); - AddComponent( new AddonComponent( 9023 ), -2, -2, 0 ); - AddComponent( new AddonComponent( 9024 ), -1, -2, 0 ); - AddComponent( new AddonComponent( 9025 ), +0, -2, 0 ); - AddComponent( new AddonComponent( 9026 ), +1, -2, 0 ); + public class SerpentPillarAddon : BaseAddon + { + [Constructible] + public SerpentPillarAddon() + { + AddComponent(new AddonComponent(9020), -2, +1, 0); + AddComponent(new AddonComponent(9021), -2, +0, 0); + AddComponent(new AddonComponent(9022), -2, -1, 0); + AddComponent(new AddonComponent(9023), -2, -2, 0); + AddComponent(new AddonComponent(9024), -1, -2, 0); + AddComponent(new AddonComponent(9025), +0, -2, 0); + AddComponent(new AddonComponent(9026), +1, -2, 0); - AddComponent( new AddonComponent( 9027 ), -1, +1, 0 ); - AddComponent( new AddonComponent( 9028 ), -1, +0, 0 ); - AddComponent( new AddonComponent( 9029 ), -1, -1, 0 ); + AddComponent(new AddonComponent(9027), -1, +1, 0); + AddComponent(new AddonComponent(9028), -1, +0, 0); + AddComponent(new AddonComponent(9029), -1, -1, 0); - AddComponent( new AddonComponent( 9030 ), +0, +1, 0 ); - AddComponent( new AddonComponent( 9031 ), +0, +0, 0 ); - AddComponent( new AddonComponent( 9032 ), +0, -1, 0 ); + AddComponent(new AddonComponent(9030), +0, +1, 0); + AddComponent(new AddonComponent(9031), +0, +0, 0); + AddComponent(new AddonComponent(9032), +0, -1, 0); - AddComponent( new AddonComponent( 9033 ), +1, +0, 0 ); - AddComponent( new AddonComponent( 9034 ), +1, -1, 0 ); - } + AddComponent(new AddonComponent(9033), +1, +0, 0); + AddComponent(new AddonComponent(9034), +1, -1, 0); + } - public SerpentPillarAddon( Serial serial ) - : base( serial ) - { - } + public SerpentPillarAddon(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/ShrineOfWisdomAddon.cs b/Scripts/Items/Addons/ShrineOfWisdomAddon.cs index 8b5185062..32b6fd67e 100644 --- a/Scripts/Items/Addons/ShrineOfWisdomAddon.cs +++ b/Scripts/Items/Addons/ShrineOfWisdomAddon.cs @@ -1,62 +1,64 @@ +using Server.Engines.Craft; + namespace Server.Items { - public class ShrineOfWisdomAddon : BaseAddon - { - [Constructible] - public ShrineOfWisdomAddon() - { - AddComponent( new ShrineOfWisdomComponent( 0x14C3 ), 0, 0, 0 ); - AddComponent( new ShrineOfWisdomComponent( 0x14C6 ), 1, 0, 0 ); - AddComponent( new ShrineOfWisdomComponent( 0x14D4 ), 0, 1, 0 ); - AddComponent( new ShrineOfWisdomComponent( 0x14D5 ), 1, 1, 0 ); - Hue = 0x47E; - } + public class ShrineOfWisdomAddon : BaseAddon + { + [Constructible] + public ShrineOfWisdomAddon() + { + AddComponent(new ShrineOfWisdomComponent(0x14C3), 0, 0, 0); + AddComponent(new ShrineOfWisdomComponent(0x14C6), 1, 0, 0); + AddComponent(new ShrineOfWisdomComponent(0x14D4), 0, 1, 0); + AddComponent(new ShrineOfWisdomComponent(0x14D5), 1, 1, 0); + Hue = 0x47E; + } - public ShrineOfWisdomAddon( Serial serial ) : base( serial ) - { - } + public ShrineOfWisdomAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Engines.Craft.Forge] - public class ShrineOfWisdomComponent : AddonComponent - { - public override int LabelNumber => 1062046; // Shrine of Wisdom + [Forge] + public class ShrineOfWisdomComponent : AddonComponent + { + [Constructible] + public ShrineOfWisdomComponent(int itemID) : base(itemID) + { + } - [Constructible] - public ShrineOfWisdomComponent( int itemID ) : base( itemID ) - { - } + public ShrineOfWisdomComponent(Serial serial) : base(serial) + { + } - public ShrineOfWisdomComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1062046; // Shrine of Wisdom - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SkullPileAddon.cs b/Scripts/Items/Addons/SkullPileAddon.cs index bfa5daf35..aa3dbf5a1 100644 --- a/Scripts/Items/Addons/SkullPileAddon.cs +++ b/Scripts/Items/Addons/SkullPileAddon.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class SkullPileAddon : BaseAddon - { - [Constructible] - public SkullPileAddon() - { - AddComponent( new AddonComponent( 6872 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 6873 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 6874 ), -1, 1, 0 ); - AddComponent( new AddonComponent( 6875 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 6876 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 6877 ), 1, -1, 0 ); - AddComponent( new AddonComponent( 6878 ), 2, -1, 0 ); - AddComponent( new AddonComponent( 6879 ), 2, 0, 0 ); - } + public class SkullPileAddon : BaseAddon + { + [Constructible] + public SkullPileAddon() + { + AddComponent(new AddonComponent(6872), 1, 1, 0); + AddComponent(new AddonComponent(6873), 0, 1, 0); + AddComponent(new AddonComponent(6874), -1, 1, 0); + AddComponent(new AddonComponent(6875), 0, 0, 0); + AddComponent(new AddonComponent(6876), 1, 0, 0); + AddComponent(new AddonComponent(6877), 1, -1, 0); + AddComponent(new AddonComponent(6878), 2, -1, 0); + AddComponent(new AddonComponent(6879), 2, 0, 0); + } - public SkullPileAddon( Serial serial ) - : base( serial ) - { - } + public SkullPileAddon(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); - } - } + int version = reader.ReadByte(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/SmallBedEastAddon.cs b/Scripts/Items/Addons/SmallBedEastAddon.cs index 230fa7e23..e4a74b1fd 100644 --- a/Scripts/Items/Addons/SmallBedEastAddon.cs +++ b/Scripts/Items/Addons/SmallBedEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class SmallBedEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SmallBedEastDeed(); + public class SmallBedEastAddon : BaseAddon + { + [Constructible] + public SmallBedEastAddon() + { + AddComponent(new AddonComponent(0xA5D), 0, 0, 0); + AddComponent(new AddonComponent(0xA62), 1, 0, 0); + } - [Constructible] - public SmallBedEastAddon() - { - AddComponent( new AddonComponent( 0xA5D ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xA62 ), 1, 0, 0 ); - } + public SmallBedEastAddon(Serial serial) : base(serial) + { + } - public SmallBedEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SmallBedEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallBedEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SmallBedEastAddon(); - public override int LabelNumber => 1044322; // small bed (east) + public class SmallBedEastDeed : BaseAddonDeed + { + [Constructible] + public SmallBedEastDeed() + { + } - [Constructible] - public SmallBedEastDeed() - { - } + public SmallBedEastDeed(Serial serial) : base(serial) + { + } - public SmallBedEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SmallBedEastAddon(); + public override int LabelNumber => 1044322; // small bed (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SmallBedSouthAddon.cs b/Scripts/Items/Addons/SmallBedSouthAddon.cs index 08461b2ce..8c983effc 100644 --- a/Scripts/Items/Addons/SmallBedSouthAddon.cs +++ b/Scripts/Items/Addons/SmallBedSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class SmallBedSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SmallBedSouthDeed(); + public class SmallBedSouthAddon : BaseAddon + { + [Constructible] + public SmallBedSouthAddon() + { + AddComponent(new AddonComponent(0xA63), 0, 0, 0); + AddComponent(new AddonComponent(0xA5C), 0, 1, 0); + } - [Constructible] - public SmallBedSouthAddon() - { - AddComponent( new AddonComponent( 0xA63 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xA5C ), 0, 1, 0 ); - } + public SmallBedSouthAddon(Serial serial) : base(serial) + { + } - public SmallBedSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SmallBedSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallBedSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SmallBedSouthAddon(); - public override int LabelNumber => 1044321; // small bed (south) + public class SmallBedSouthDeed : BaseAddonDeed + { + [Constructible] + public SmallBedSouthDeed() + { + } - [Constructible] - public SmallBedSouthDeed() - { - } + public SmallBedSouthDeed(Serial serial) : base(serial) + { + } - public SmallBedSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SmallBedSouthAddon(); + public override int LabelNumber => 1044321; // small bed (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SmallForgeAddon.cs b/Scripts/Items/Addons/SmallForgeAddon.cs index 1dee86002..a47835e96 100644 --- a/Scripts/Items/Addons/SmallForgeAddon.cs +++ b/Scripts/Items/Addons/SmallForgeAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class SmallForgeAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SmallForgeDeed(); + public class SmallForgeAddon : BaseAddon + { + [Constructible] + public SmallForgeAddon() + { + AddComponent(new ForgeComponent(0xFB1), 0, 0, 0); + } - [Constructible] - public SmallForgeAddon() - { - AddComponent( new ForgeComponent( 0xFB1 ), 0, 0, 0 ); - } + public SmallForgeAddon(Serial serial) : base(serial) + { + } - public SmallForgeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SmallForgeDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallForgeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SmallForgeAddon(); - public override int LabelNumber => 1044330; // small forge + public class SmallForgeDeed : BaseAddonDeed + { + [Constructible] + public SmallForgeDeed() + { + } - [Constructible] - public SmallForgeDeed() - { - } + public SmallForgeDeed(Serial serial) : base(serial) + { + } - public SmallForgeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SmallForgeAddon(); + public override int LabelNumber => 1044330; // small forge - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SolenAntHole.cs b/Scripts/Items/Addons/SolenAntHole.cs index 87479e53f..c5d216186 100644 --- a/Scripts/Items/Addons/SolenAntHole.cs +++ b/Scripts/Items/Addons/SolenAntHole.cs @@ -1,170 +1,169 @@ -using System; using System.Collections.Generic; -using Server.Network; using Server.Mobiles; +using Server.Network; using Server.Spells; namespace Server.Items { - public class SolenAntHoleComponent : AddonComponent - { - public SolenAntHoleComponent( int itemID ) : base( itemID ) - { - } + public class SolenAntHoleComponent : AddonComponent + { + public SolenAntHoleComponent(int itemID) : base(itemID) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( this, 2 ) ) - { - Map map = Map; + public SolenAntHoleComponent(Serial serial) : base(serial) + { + } - if ( map == Map.Trammel || map == Map.Felucca ) - { - from.MoveToWorld( new Point3D( 5922, 2024, 0 ), map ); - PublicOverheadMessage( MessageType.Regular, 0x3B2, true, - $"* {from.Name} dives into the hole and disappears!*"); - } - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(this, 2)) + { + Map map = Map; - public SolenAntHoleComponent( Serial serial ) : base( serial ) - { - } + if (map == Map.Trammel || map == Map.Felucca) + { + from.MoveToWorld(new Point3D(5922, 2024, 0), map); + PublicOverheadMessage(MessageType.Regular, 0x3B2, true, + $"* {from.Name} dives into the hole and disappears!*"); + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SolenAntHole : BaseAddon - { - public override bool ShareHue => false; - public override bool HandlesOnMovement => true; + public class SolenAntHole : BaseAddon + { + private List m_Spawned; - private List m_Spawned; + [Constructible] + public SolenAntHole() + { + m_Spawned = new List(); - [Constructible] - public SolenAntHole() - { - m_Spawned = new List(); + AddComponent(new AddonComponent(0x914), "dirt", 0, 0, 0, 0); + AddComponent(new SolenAntHoleComponent(0x122A), "a hole", 0x1, 0, 0, 0); + AddComponent(new AddonComponent(0x1B23), "dirt", 0x970, 1, 1, 0); + AddComponent(new AddonComponent(0xEE0), "dirt", 0, 1, 0, 0); + AddComponent(new AddonComponent(0x1B24), "dirt", 0x970, 1, -1, 0); + AddComponent(new AddonComponent(0xEE1), "dirt", 0, 0, -1, 0); + AddComponent(new AddonComponent(0x1B25), "dirt", 0x970, -1, -1, 0); + AddComponent(new AddonComponent(0xEE2), "dirt", 0, -1, 0, 0); + AddComponent(new AddonComponent(0x1B26), "dirt", 0x970, -1, 1, 0); + AddComponent(new AddonComponent(0xED3), "dirt", 0, 0, 1, 0); + } - AddComponent( new AddonComponent( 0x914 ), "dirt", 0, 0, 0, 0 ); - AddComponent( new SolenAntHoleComponent( 0x122A ), "a hole", 0x1, 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1B23 ), "dirt", 0x970, 1, 1, 0 ); - AddComponent( new AddonComponent( 0xEE0 ), "dirt", 0, 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1B24 ), "dirt", 0x970, 1, -1, 0 ); - AddComponent( new AddonComponent( 0xEE1 ), "dirt", 0, 0, -1, 0 ); - AddComponent( new AddonComponent( 0x1B25 ), "dirt", 0x970, -1, -1, 0 ); - AddComponent( new AddonComponent( 0xEE2 ), "dirt", 0, -1, 0, 0 ); - AddComponent( new AddonComponent( 0x1B26 ), "dirt", 0x970, -1, 1, 0 ); - AddComponent( new AddonComponent( 0xED3 ), "dirt", 0, 0, 1, 0 ); - } + public SolenAntHole(Serial serial) : base(serial) + { + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( !m.Player || !m.Alive || m.Hidden || !SpawnKilled() ) - return; + public override bool ShareHue => false; + public override bool HandlesOnMovement => true; - if ( Utility.InRange( Location, m.Location, 3 ) && !Utility.InRange( Location, oldLocation, 3 ) ) - { - int count = 1 + Utility.Random( 4 ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (!m.Player || !m.Alive || m.Hidden || !SpawnKilled()) + return; - for ( int i = 0; i < count; i++ ) - SpawnAnt(); + if (Utility.InRange(Location, m.Location, 3) && !Utility.InRange(Location, oldLocation, 3)) + { + int count = 1 + Utility.Random(4); - if ( 0.05 > Utility.RandomDouble() ) - SpawnAnt( new Beetle() ); - } - } + for (int i = 0; i < count; i++) + SpawnAnt(); - public void AddComponent( AddonComponent c, string name, int hue, int x, int y, int z ) - { - c.Hue = hue; - c.Name = name; - AddComponent( c, x, y, z ); - } + if (0.05 > Utility.RandomDouble()) + SpawnAnt(new Beetle()); + } + } - public void SpawnAnt() - { - int random = Utility.Random( 3 ); - Map map = Map; + public void AddComponent(AddonComponent c, string name, int hue, int x, int y, int z) + { + c.Hue = hue; + c.Name = name; + AddComponent(c, x, y, z); + } - if ( map == Map.Trammel ) - { - if ( random < 2 ) - SpawnAnt( new RedSolenWorker() ); - else - SpawnAnt( new RedSolenWarrior() ); - } - else if ( map == Map.Felucca ) - { - if ( random < 2 ) - SpawnAnt( new BlackSolenWorker() ); - else - SpawnAnt( new BlackSolenWarrior() ); - } - } + public void SpawnAnt() + { + int random = Utility.Random(3); + Map map = Map; - public void SpawnAnt( BaseCreature ant ) - { - m_Spawned.Add( ant ); + if (map == Map.Trammel) + { + if (random < 2) + SpawnAnt(new RedSolenWorker()); + else + SpawnAnt(new RedSolenWarrior()); + } + else if (map == Map.Felucca) + { + if (random < 2) + SpawnAnt(new BlackSolenWorker()); + else + SpawnAnt(new BlackSolenWarrior()); + } + } - Map map = Map; - Point3D p = Location; + public void SpawnAnt(BaseCreature ant) + { + m_Spawned.Add(ant); - for ( int i = 0; i < 5; i++ ) - if ( SpellHelper.FindValidSpawnLocation( map, ref p, false ) ) - break; + Map map = Map; + Point3D p = Location; - ant.MoveToWorld( p, map ); - ant.Home = Location; - ant.RangeHome = 10; - } + for (int i = 0; i < 5; i++) + if (SpellHelper.FindValidSpawnLocation(map, ref p, false)) + break; - public bool SpawnKilled() - { - for ( int i = m_Spawned.Count - 1; i >= 0; i-- ) - { - if ( !m_Spawned[ i ].Alive || m_Spawned[ i ].Deleted ) - m_Spawned.RemoveAt( i ); - } + ant.MoveToWorld(p, map); + ant.Home = Location; + ant.RangeHome = 10; + } - return m_Spawned.Count < 2; - } + public bool SpawnKilled() + { + for (int i = m_Spawned.Count - 1; i >= 0; i--) + if (!m_Spawned[i].Alive || m_Spawned[i].Deleted) + m_Spawned.RemoveAt(i); - public SolenAntHole( Serial serial ) : base( serial ) - { - } + return m_Spawned.Count < 2; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.WriteMobileList( m_Spawned ); - } + writer.WriteMobileList(m_Spawned); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Spawned = reader.ReadStrongMobileList(); - } - } -} + m_Spawned = reader.ReadStrongMobileList(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SpinningwheelEastAddon.cs b/Scripts/Items/Addons/SpinningwheelEastAddon.cs index 015d2bd73..d85c4fd9b 100644 --- a/Scripts/Items/Addons/SpinningwheelEastAddon.cs +++ b/Scripts/Items/Addons/SpinningwheelEastAddon.cs @@ -2,143 +2,146 @@ using System; namespace Server.Items { - public delegate void SpinCallback( ISpinningWheel sender, Mobile from, int hue ); + public delegate void SpinCallback(ISpinningWheel sender, Mobile from, int hue); - public interface ISpinningWheel - { - bool Spinning{ get; } - void BeginSpin( SpinCallback callback, Mobile from, int hue ); - } + public interface ISpinningWheel + { + bool Spinning{ get; } + void BeginSpin(SpinCallback callback, Mobile from, int hue); + } - public class SpinningwheelEastAddon : BaseAddon, ISpinningWheel - { - public override BaseAddonDeed Deed => new SpinningwheelEastDeed(); + public class SpinningwheelEastAddon : BaseAddon, ISpinningWheel + { + private Timer m_Timer; - [Constructible] - public SpinningwheelEastAddon() - { - AddComponent( new AddonComponent( 0x1019 ), 0, 0, 0 ); - } + [Constructible] + public SpinningwheelEastAddon() + { + AddComponent(new AddonComponent(0x1019), 0, 0, 0); + } - public SpinningwheelEastAddon( Serial serial ) : base( serial ) - { - } + public SpinningwheelEastAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override BaseAddonDeed Deed => new SpinningwheelEastDeed(); - writer.Write( (int) 0 ); // version - } + public bool Spinning => m_Timer != null; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void BeginSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer = new SpinTimer(this, callback, from, hue); + m_Timer.Start(); - int version = reader.ReadInt(); - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1015: + case 0x1019: + case 0x101C: + case 0x10A4: + ++c.ItemID; + break; + } + } - private Timer m_Timer; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnComponentLoaded( AddonComponent c ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + writer.Write(0); // version + } - public bool Spinning => m_Timer != null; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public void BeginSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer = new SpinTimer( this, callback, from, hue ); - m_Timer.Start(); + int version = reader.ReadInt(); + } - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1015: - case 0x1019: - case 0x101C: - case 0x10A4: ++c.ItemID; break; - } - } - } + public override void OnComponentLoaded(AddonComponent c) + { + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } + } - public void EndSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer?.Stop(); + public void EndSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } - callback?.Invoke( this, from, hue ); - } + callback?.Invoke(this, from, hue); + } - private class SpinTimer : Timer - { - private SpinningwheelEastAddon m_Wheel; - private SpinCallback m_Callback; - private Mobile m_From; - private int m_Hue; + private class SpinTimer : Timer + { + private SpinCallback m_Callback; + private Mobile m_From; + private int m_Hue; + private SpinningwheelEastAddon m_Wheel; - public SpinTimer( SpinningwheelEastAddon wheel, SpinCallback callback, Mobile from, int hue ) : base( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Wheel = wheel; - m_Callback = callback; - m_From = from; - m_Hue = hue; - Priority = TimerPriority.TwoFiftyMS; - } + public SpinTimer(SpinningwheelEastAddon wheel, SpinCallback callback, Mobile from, int hue) : base( + TimeSpan.FromSeconds(3.0)) + { + m_Wheel = wheel; + m_Callback = callback; + m_From = from; + m_Hue = hue; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - m_Wheel.EndSpin( m_Callback, m_From, m_Hue ); - } - } - } + protected override void OnTick() + { + m_Wheel.EndSpin(m_Callback, m_From, m_Hue); + } + } + } - public class SpinningwheelEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SpinningwheelEastAddon(); - public override int LabelNumber => 1044341; // spining wheel (east) + public class SpinningwheelEastDeed : BaseAddonDeed + { + [Constructible] + public SpinningwheelEastDeed() + { + } - [Constructible] - public SpinningwheelEastDeed() - { - } + public SpinningwheelEastDeed(Serial serial) : base(serial) + { + } - public SpinningwheelEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SpinningwheelEastAddon(); + public override int LabelNumber => 1044341; // spining wheel (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SpinningwheelSouthAddon.cs b/Scripts/Items/Addons/SpinningwheelSouthAddon.cs index 9eefd93bd..a79769d39 100644 --- a/Scripts/Items/Addons/SpinningwheelSouthAddon.cs +++ b/Scripts/Items/Addons/SpinningwheelSouthAddon.cs @@ -2,135 +2,138 @@ using System; namespace Server.Items { - public class SpinningwheelSouthAddon : BaseAddon, ISpinningWheel - { - public override BaseAddonDeed Deed => new SpinningwheelSouthDeed(); + public class SpinningwheelSouthAddon : BaseAddon, ISpinningWheel + { + private Timer m_Timer; - [Constructible] - public SpinningwheelSouthAddon() - { - AddComponent( new AddonComponent( 0x1015 ), 0, 0, 0 ); - } + [Constructible] + public SpinningwheelSouthAddon() + { + AddComponent(new AddonComponent(0x1015), 0, 0, 0); + } - public SpinningwheelSouthAddon( Serial serial ) : base( serial ) - { - } + public SpinningwheelSouthAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override BaseAddonDeed Deed => new SpinningwheelSouthDeed(); - writer.Write( (int) 0 ); // version - } + public bool Spinning => m_Timer != null; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void BeginSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer = new SpinTimer(this, callback, from, hue); + m_Timer.Start(); - int version = reader.ReadInt(); - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1015: + case 0x1019: + case 0x101C: + case 0x10A4: + ++c.ItemID; + break; + } + } - private Timer m_Timer; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnComponentLoaded( AddonComponent c ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + writer.Write(0); // version + } - public bool Spinning => m_Timer != null; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public void BeginSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer = new SpinTimer( this, callback, from, hue ); - m_Timer.Start(); + int version = reader.ReadInt(); + } - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1015: - case 0x1019: - case 0x101C: - case 0x10A4: ++c.ItemID; break; - } - } - } + public override void OnComponentLoaded(AddonComponent c) + { + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } + } - public void EndSpin( SpinCallback callback, Mobile from, int hue ) - { - m_Timer?.Stop(); + public void EndSpin(SpinCallback callback, Mobile from, int hue) + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - foreach ( AddonComponent c in Components ) - { - switch ( c.ItemID ) - { - case 0x1016: - case 0x101A: - case 0x101D: - case 0x10A5: --c.ItemID; break; - } - } + foreach (AddonComponent c in Components) + switch (c.ItemID) + { + case 0x1016: + case 0x101A: + case 0x101D: + case 0x10A5: + --c.ItemID; + break; + } - callback?.Invoke( this, from, hue ); - } + callback?.Invoke(this, from, hue); + } - private class SpinTimer : Timer - { - private SpinningwheelSouthAddon m_Wheel; - private SpinCallback m_Callback; - private Mobile m_From; - private int m_Hue; + private class SpinTimer : Timer + { + private SpinCallback m_Callback; + private Mobile m_From; + private int m_Hue; + private SpinningwheelSouthAddon m_Wheel; - public SpinTimer( SpinningwheelSouthAddon wheel, SpinCallback callback, Mobile from, int hue ) : base( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Wheel = wheel; - m_Callback = callback; - m_From = from; - m_Hue = hue; - Priority = TimerPriority.TwoFiftyMS; - } + public SpinTimer(SpinningwheelSouthAddon wheel, SpinCallback callback, Mobile from, int hue) : base( + TimeSpan.FromSeconds(3.0)) + { + m_Wheel = wheel; + m_Callback = callback; + m_From = from; + m_Hue = hue; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - m_Wheel.EndSpin( m_Callback, m_From, m_Hue ); - } - } - } + protected override void OnTick() + { + m_Wheel.EndSpin(m_Callback, m_From, m_Hue); + } + } + } - public class SpinningwheelSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SpinningwheelSouthAddon(); - public override int LabelNumber => 1044342; // spining wheel (south) + public class SpinningwheelSouthDeed : BaseAddonDeed + { + [Constructible] + public SpinningwheelSouthDeed() + { + } - [Constructible] - public SpinningwheelSouthDeed() - { - } + public SpinningwheelSouthDeed(Serial serial) : base(serial) + { + } - public SpinningwheelSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SpinningwheelSouthAddon(); + public override int LabelNumber => 1044342; // spining wheel (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SquirrelStatueEastAddon.cs b/Scripts/Items/Addons/SquirrelStatueEastAddon.cs index 5f45f41a1..d19d50154 100644 --- a/Scripts/Items/Addons/SquirrelStatueEastAddon.cs +++ b/Scripts/Items/Addons/SquirrelStatueEastAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class SquirrelStatueEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SquirrelStatueEastDeed(); + public class SquirrelStatueEastAddon : BaseAddon + { + [Constructible] + public SquirrelStatueEastAddon() + { + AddComponent(new AddonComponent(0x2D10), 0, 0, 0); + } - [Constructible] - public SquirrelStatueEastAddon() - { - AddComponent( new AddonComponent( 0x2D10 ), 0, 0, 0 ); - } + public SquirrelStatueEastAddon(Serial serial) : base(serial) + { + } - public SquirrelStatueEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SquirrelStatueEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SquirrelStatueEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SquirrelStatueEastAddon(); - public override int LabelNumber => 1073398; // squirrel statue (east) + public class SquirrelStatueEastDeed : BaseAddonDeed + { + [Constructible] + public SquirrelStatueEastDeed() + { + } - [Constructible] - public SquirrelStatueEastDeed() - { - } + public SquirrelStatueEastDeed(Serial serial) : base(serial) + { + } - public SquirrelStatueEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SquirrelStatueEastAddon(); + public override int LabelNumber => 1073398; // squirrel statue (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/SquirrelStatueSouthAddon.cs b/Scripts/Items/Addons/SquirrelStatueSouthAddon.cs index c00e9c724..2eeda5384 100644 --- a/Scripts/Items/Addons/SquirrelStatueSouthAddon.cs +++ b/Scripts/Items/Addons/SquirrelStatueSouthAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class SquirrelStatueSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SquirrelStatueSouthDeed(); + public class SquirrelStatueSouthAddon : BaseAddon + { + [Constructible] + public SquirrelStatueSouthAddon() + { + AddComponent(new AddonComponent(0x2D11), 0, 0, 0); + } - [Constructible] - public SquirrelStatueSouthAddon() - { - AddComponent( new AddonComponent( 0x2D11 ), 0, 0, 0 ); - } + public SquirrelStatueSouthAddon(Serial serial) : base(serial) + { + } - public SquirrelStatueSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SquirrelStatueSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SquirrelStatueSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SquirrelStatueSouthAddon(); - public override int LabelNumber => 1072884; // squirrel statue (south) + public class SquirrelStatueSouthDeed : BaseAddonDeed + { + [Constructible] + public SquirrelStatueSouthDeed() + { + } - [Constructible] - public SquirrelStatueSouthDeed() - { - } + public SquirrelStatueSouthDeed(Serial serial) : base(serial) + { + } - public SquirrelStatueSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SquirrelStatueSouthAddon(); + public override int LabelNumber => 1072884; // squirrel statue (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/StoneFireplaceEastAddon.cs b/Scripts/Items/Addons/StoneFireplaceEastAddon.cs index ce47d8b0a..d1ea2db3d 100644 --- a/Scripts/Items/Addons/StoneFireplaceEastAddon.cs +++ b/Scripts/Items/Addons/StoneFireplaceEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class StoneFireplaceEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new StoneFireplaceEastDeed(); + public class StoneFireplaceEastAddon : BaseAddon + { + [Constructible] + public StoneFireplaceEastAddon() + { + AddComponent(new AddonComponent(0x959), 0, 0, 0); + AddComponent(new AddonComponent(0x953), 0, 1, 0); + } - [Constructible] - public StoneFireplaceEastAddon() - { - AddComponent( new AddonComponent( 0x959 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x953 ), 0, 1, 0 ); - } + public StoneFireplaceEastAddon(Serial serial) : base(serial) + { + } - public StoneFireplaceEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new StoneFireplaceEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class StoneFireplaceEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new StoneFireplaceEastAddon(); - public override int LabelNumber => 1061848; // stone fireplace (east) + public class StoneFireplaceEastDeed : BaseAddonDeed + { + [Constructible] + public StoneFireplaceEastDeed() + { + } - [Constructible] - public StoneFireplaceEastDeed() - { - } + public StoneFireplaceEastDeed(Serial serial) : base(serial) + { + } - public StoneFireplaceEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new StoneFireplaceEastAddon(); + public override int LabelNumber => 1061848; // stone fireplace (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/StoneFireplaceSouthAddon.cs b/Scripts/Items/Addons/StoneFireplaceSouthAddon.cs index 087b0fc48..ab47ec485 100644 --- a/Scripts/Items/Addons/StoneFireplaceSouthAddon.cs +++ b/Scripts/Items/Addons/StoneFireplaceSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class StoneFireplaceSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new StoneFireplaceSouthDeed(); + public class StoneFireplaceSouthAddon : BaseAddon + { + [Constructible] + public StoneFireplaceSouthAddon() + { + AddComponent(new AddonComponent(0x967), -1, 0, 0); + AddComponent(new AddonComponent(0x961), 0, 0, 0); + } - [Constructible] - public StoneFireplaceSouthAddon() - { - AddComponent( new AddonComponent( 0x967 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x961 ), 0, 0, 0 ); - } + public StoneFireplaceSouthAddon(Serial serial) : base(serial) + { + } - public StoneFireplaceSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new StoneFireplaceSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class StoneFireplaceSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new StoneFireplaceSouthAddon(); - public override int LabelNumber => 1061849; // stone fireplace (south) + public class StoneFireplaceSouthDeed : BaseAddonDeed + { + [Constructible] + public StoneFireplaceSouthDeed() + { + } - [Constructible] - public StoneFireplaceSouthDeed() - { - } + public StoneFireplaceSouthDeed(Serial serial) : base(serial) + { + } - public StoneFireplaceSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new StoneFireplaceSouthAddon(); + public override int LabelNumber => 1061849; // stone fireplace (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/StoneFountainAddon.cs b/Scripts/Items/Addons/StoneFountainAddon.cs index 13c9da00c..fca70cb01 100644 --- a/Scripts/Items/Addons/StoneFountainAddon.cs +++ b/Scripts/Items/Addons/StoneFountainAddon.cs @@ -1,51 +1,51 @@ namespace Server.Items { - public class StoneFountainAddon : BaseAddon - { - [Constructible] - public StoneFountainAddon() - { - int itemID = 0x1731; + public class StoneFountainAddon : BaseAddon + { + [Constructible] + public StoneFountainAddon() + { + int itemID = 0x1731; - AddComponent( new AddonComponent( itemID++ ), -2, +1, 0 ); - AddComponent( new AddonComponent( itemID++ ), -1, +1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +0, +1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +1, +1, 0 ); + AddComponent(new AddonComponent(itemID++), -2, +1, 0); + AddComponent(new AddonComponent(itemID++), -1, +1, 0); + AddComponent(new AddonComponent(itemID++), +0, +1, 0); + AddComponent(new AddonComponent(itemID++), +1, +1, 0); - AddComponent( new AddonComponent( itemID++ ), +1, +0, 0 ); - AddComponent( new AddonComponent( itemID++ ), +1, -1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +1, -2, 0 ); + AddComponent(new AddonComponent(itemID++), +1, +0, 0); + AddComponent(new AddonComponent(itemID++), +1, -1, 0); + AddComponent(new AddonComponent(itemID++), +1, -2, 0); - AddComponent( new AddonComponent( itemID++ ), +0, -2, 0 ); - AddComponent( new AddonComponent( itemID++ ), +0, -1, 0 ); - AddComponent( new AddonComponent( itemID++ ), +0, +0, 0 ); + AddComponent(new AddonComponent(itemID++), +0, -2, 0); + AddComponent(new AddonComponent(itemID++), +0, -1, 0); + AddComponent(new AddonComponent(itemID++), +0, +0, 0); - AddComponent( new AddonComponent( itemID++ ), -1, +0, 0 ); - AddComponent( new AddonComponent( itemID++ ), -2, +0, 0 ); + AddComponent(new AddonComponent(itemID++), -1, +0, 0); + AddComponent(new AddonComponent(itemID++), -2, +0, 0); - AddComponent( new AddonComponent( itemID++ ), -2, -1, 0 ); - AddComponent( new AddonComponent( itemID++ ), -1, -1, 0 ); + AddComponent(new AddonComponent(itemID++), -2, -1, 0); + AddComponent(new AddonComponent(itemID++), -1, -1, 0); - AddComponent( new AddonComponent( itemID++ ), -1, -2, 0 ); - AddComponent( new AddonComponent( ++itemID ), -2, -2, 0 ); - } + AddComponent(new AddonComponent(itemID++), -1, -2, 0); + AddComponent(new AddonComponent(++itemID), -2, -2, 0); + } - public StoneFountainAddon( Serial serial ) : base( serial ) - { - } + public StoneFountainAddon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/StoneOvenEastAddon.cs b/Scripts/Items/Addons/StoneOvenEastAddon.cs index 65bb60860..5f6a943c7 100644 --- a/Scripts/Items/Addons/StoneOvenEastAddon.cs +++ b/Scripts/Items/Addons/StoneOvenEastAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class StoneOvenEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new StoneOvenEastDeed(); + public class StoneOvenEastAddon : BaseAddon + { + [Constructible] + public StoneOvenEastAddon() + { + AddComponent(new AddonComponent(0x92C), 0, 0, 0); + AddComponent(new AddonComponent(0x92B), 0, 1, 0); + } - [Constructible] - public StoneOvenEastAddon() - { - AddComponent( new AddonComponent( 0x92C ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x92B ), 0, 1, 0 ); - } + public StoneOvenEastAddon(Serial serial) : base(serial) + { + } - public StoneOvenEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new StoneOvenEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class StoneOvenEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new StoneOvenEastAddon(); - public override int LabelNumber => 1044345; // stone oven (east) + public class StoneOvenEastDeed : BaseAddonDeed + { + [Constructible] + public StoneOvenEastDeed() + { + } - [Constructible] - public StoneOvenEastDeed() - { - } + public StoneOvenEastDeed(Serial serial) : base(serial) + { + } - public StoneOvenEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new StoneOvenEastAddon(); + public override int LabelNumber => 1044345; // stone oven (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/StoneOvenSouthAddon.cs b/Scripts/Items/Addons/StoneOvenSouthAddon.cs index aab2daf94..55d58d0bc 100644 --- a/Scripts/Items/Addons/StoneOvenSouthAddon.cs +++ b/Scripts/Items/Addons/StoneOvenSouthAddon.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class StoneOvenSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new StoneOvenSouthDeed(); + public class StoneOvenSouthAddon : BaseAddon + { + [Constructible] + public StoneOvenSouthAddon() + { + AddComponent(new AddonComponent(0x931), -1, 0, 0); + AddComponent(new AddonComponent(0x930), 0, 0, 0); + } - [Constructible] - public StoneOvenSouthAddon() - { - AddComponent( new AddonComponent( 0x931 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x930 ), 0, 0, 0 ); - } + public StoneOvenSouthAddon(Serial serial) : base(serial) + { + } - public StoneOvenSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new StoneOvenSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class StoneOvenSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new StoneOvenSouthAddon(); - public override int LabelNumber => 1044346; // stone oven (south) + public class StoneOvenSouthDeed : BaseAddonDeed + { + [Constructible] + public StoneOvenSouthDeed() + { + } - [Constructible] - public StoneOvenSouthDeed() - { - } + public StoneOvenSouthDeed(Serial serial) : base(serial) + { + } - public StoneOvenSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new StoneOvenSouthAddon(); + public override int LabelNumber => 1044346; // stone oven (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/StretchedHides.cs b/Scripts/Items/Addons/StretchedHides.cs index af053b64f..d25a73e76 100644 --- a/Scripts/Items/Addons/StretchedHides.cs +++ b/Scripts/Items/Addons/StretchedHides.cs @@ -1,234 +1,234 @@ namespace Server.Items { - public class SmallStretchedHideEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SmallStretchedHideEastDeed(); + public class SmallStretchedHideEastAddon : BaseAddon + { + [Constructible] + public SmallStretchedHideEastAddon() + { + AddComponent(new AddonComponent(0x1069), 0, 0, 0); + } - [Constructible] - public SmallStretchedHideEastAddon() - { - AddComponent( new AddonComponent( 0x1069 ), 0, 0, 0 ); - } + public SmallStretchedHideEastAddon(Serial serial) : base(serial) + { + } - public SmallStretchedHideEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SmallStretchedHideEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallStretchedHideEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SmallStretchedHideEastAddon(); - public override int LabelNumber => 1049401; // a small stretched hide deed facing east + public class SmallStretchedHideEastDeed : BaseAddonDeed + { + [Constructible] + public SmallStretchedHideEastDeed() + { + } - [Constructible] - public SmallStretchedHideEastDeed() - { - } + public SmallStretchedHideEastDeed(Serial serial) : base(serial) + { + } - public SmallStretchedHideEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SmallStretchedHideEastAddon(); + public override int LabelNumber => 1049401; // a small stretched hide deed facing east - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallStretchedHideSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SmallStretchedHideSouthDeed(); + public class SmallStretchedHideSouthAddon : BaseAddon + { + [Constructible] + public SmallStretchedHideSouthAddon() + { + AddComponent(new AddonComponent(0x107A), 0, 0, 0); + } - [Constructible] - public SmallStretchedHideSouthAddon() - { - AddComponent( new AddonComponent( 0x107A ), 0, 0, 0 ); - } + public SmallStretchedHideSouthAddon(Serial serial) : base(serial) + { + } - public SmallStretchedHideSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SmallStretchedHideSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallStretchedHideSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SmallStretchedHideSouthAddon(); - public override int LabelNumber => 1049402; // a small stretched hide deed facing south + public class SmallStretchedHideSouthDeed : BaseAddonDeed + { + [Constructible] + public SmallStretchedHideSouthDeed() + { + } - [Constructible] - public SmallStretchedHideSouthDeed() - { - } + public SmallStretchedHideSouthDeed(Serial serial) : base(serial) + { + } - public SmallStretchedHideSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SmallStretchedHideSouthAddon(); + public override int LabelNumber => 1049402; // a small stretched hide deed facing south - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MediumStretchedHideEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MediumStretchedHideEastDeed(); + public class MediumStretchedHideEastAddon : BaseAddon + { + [Constructible] + public MediumStretchedHideEastAddon() + { + AddComponent(new AddonComponent(0x106B), 0, 0, 0); + } - [Constructible] - public MediumStretchedHideEastAddon() - { - AddComponent( new AddonComponent( 0x106B ), 0, 0, 0 ); - } + public MediumStretchedHideEastAddon(Serial serial) : base(serial) + { + } - public MediumStretchedHideEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MediumStretchedHideEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MediumStretchedHideEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MediumStretchedHideEastAddon(); - public override int LabelNumber => 1049403; // a medium stretched hide deed facing east + public class MediumStretchedHideEastDeed : BaseAddonDeed + { + [Constructible] + public MediumStretchedHideEastDeed() + { + } - [Constructible] - public MediumStretchedHideEastDeed() - { - } + public MediumStretchedHideEastDeed(Serial serial) : base(serial) + { + } - public MediumStretchedHideEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MediumStretchedHideEastAddon(); + public override int LabelNumber => 1049403; // a medium stretched hide deed facing east - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MediumStretchedHideSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MediumStretchedHideSouthDeed(); + public class MediumStretchedHideSouthAddon : BaseAddon + { + [Constructible] + public MediumStretchedHideSouthAddon() + { + AddComponent(new AddonComponent(0x107C), 0, 0, 0); + } - [Constructible] - public MediumStretchedHideSouthAddon() - { - AddComponent( new AddonComponent( 0x107C ), 0, 0, 0 ); - } + public MediumStretchedHideSouthAddon(Serial serial) : base(serial) + { + } - public MediumStretchedHideSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MediumStretchedHideSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MediumStretchedHideSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MediumStretchedHideSouthAddon(); - public override int LabelNumber => 1049404; // a medium stretched hide deed facing south + public class MediumStretchedHideSouthDeed : BaseAddonDeed + { + [Constructible] + public MediumStretchedHideSouthDeed() + { + } - [Constructible] - public MediumStretchedHideSouthDeed() - { - } + public MediumStretchedHideSouthDeed(Serial serial) : base(serial) + { + } - public MediumStretchedHideSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MediumStretchedHideSouthAddon(); + public override int LabelNumber => 1049404; // a medium stretched hide deed facing south - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/TallElvenBedEastAddon.cs b/Scripts/Items/Addons/TallElvenBedEastAddon.cs index a4220bff9..a11ce3089 100644 --- a/Scripts/Items/Addons/TallElvenBedEastAddon.cs +++ b/Scripts/Items/Addons/TallElvenBedEastAddon.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class TallElvenBedEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TallElvenBedEastDeed(); + public class TallElvenBedEastAddon : BaseAddon + { + [Constructible] + public TallElvenBedEastAddon() + { + AddComponent(new AddonComponent(0x3054), 0, 0, 0); + AddComponent(new AddonComponent(0x3053), 1, 0, 0); + AddComponent(new AddonComponent(0x3055), 2, -1, 0); + AddComponent(new AddonComponent(0x3052), 2, 0, 0); + } - [Constructible] - public TallElvenBedEastAddon() - { - AddComponent( new AddonComponent( 0x3054 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3053 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x3055 ), 2, -1, 0 ); - AddComponent( new AddonComponent( 0x3052 ), 2, 0, 0 ); - } + public TallElvenBedEastAddon(Serial serial) : base(serial) + { + } - public TallElvenBedEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TallElvenBedEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class TallElvenBedEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TallElvenBedEastAddon(); - public override int LabelNumber => 1072859; // tall elven bed (east) + public class TallElvenBedEastDeed : BaseAddonDeed + { + [Constructible] + public TallElvenBedEastDeed() + { + } - [Constructible] - public TallElvenBedEastDeed() - { - } + public TallElvenBedEastDeed(Serial serial) : base(serial) + { + } - public TallElvenBedEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TallElvenBedEastAddon(); + public override int LabelNumber => 1072859; // tall elven bed (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/TallElvenBedSouthAddon.cs b/Scripts/Items/Addons/TallElvenBedSouthAddon.cs index 0d94080a5..a135ba4f2 100644 --- a/Scripts/Items/Addons/TallElvenBedSouthAddon.cs +++ b/Scripts/Items/Addons/TallElvenBedSouthAddon.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class TallElvenBedSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TallElvenBedSouthDeed(); + public class TallElvenBedSouthAddon : BaseAddon + { + [Constructible] + public TallElvenBedSouthAddon() + { + AddComponent(new AddonComponent(0x3058), 0, 0, 0); // angolo alto sx + AddComponent(new AddonComponent(0x3057), -1, 1, 0); // angolo basso sx + AddComponent(new AddonComponent(0x3059), 0, -1, 0); // angolo alto dx + AddComponent(new AddonComponent(0x3056), 0, 1, 0); // angolo basso dx + } - [Constructible] - public TallElvenBedSouthAddon() - { - AddComponent( new AddonComponent( 0x3058 ), 0, 0, 0 ); // angolo alto sx - AddComponent( new AddonComponent( 0x3057 ), -1, 1, 0 ); // angolo basso sx - AddComponent( new AddonComponent( 0x3059 ), 0, -1, 0 ); // angolo alto dx - AddComponent( new AddonComponent( 0x3056 ), 0, 1, 0 ); // angolo basso dx - } + public TallElvenBedSouthAddon(Serial serial) : base(serial) + { + } - public TallElvenBedSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TallElvenBedSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class TallElvenBedSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TallElvenBedSouthAddon(); - public override int LabelNumber => 1072858; // tall elven bed (south) + public class TallElvenBedSouthDeed : BaseAddonDeed + { + [Constructible] + public TallElvenBedSouthDeed() + { + } - [Constructible] - public TallElvenBedSouthDeed() - { - } + public TallElvenBedSouthDeed(Serial serial) : base(serial) + { + } - public TallElvenBedSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TallElvenBedSouthAddon(); + public override int LabelNumber => 1072858; // tall elven bed (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/Telescope.cs b/Scripts/Items/Addons/Telescope.cs index 952f67aa9..ede150aa2 100644 --- a/Scripts/Items/Addons/Telescope.cs +++ b/Scripts/Items/Addons/Telescope.cs @@ -1,103 +1,103 @@ namespace Server.Items { - public class Telescope : BaseAddon - { - [Constructible] - public Telescope() - { - AddComponent( new AddonComponent( 0x1494 ), 0, 5, 0 ); - AddComponent( new AddonComponent( 0x145B ), 0, 6, 0 ); - AddComponent( new AddonComponent( 0x145A ), 0, 7, 0 ); + public class Telescope : BaseAddon + { + [Constructible] + public Telescope() + { + AddComponent(new AddonComponent(0x1494), 0, 5, 0); + AddComponent(new AddonComponent(0x145B), 0, 6, 0); + AddComponent(new AddonComponent(0x145A), 0, 7, 0); - AddComponent( new AddonComponent( 0x1495 ), 1, 4, 0 ); - AddComponent( new AddonComponent( 0x145C ), 1, 7, 0 ); - AddComponent( new AddonComponent( 0x145D ), 1, 8, 0 ); + AddComponent(new AddonComponent(0x1495), 1, 4, 0); + AddComponent(new AddonComponent(0x145C), 1, 7, 0); + AddComponent(new AddonComponent(0x145D), 1, 8, 0); - AddComponent( new AddonComponent( 0x1496 ), 2, 3, 0 ); - AddComponent( new AddonComponent( 0x1499 ), 2, 4, 0 ); - AddComponent( new AddonComponent( 0x148E ), 2, 6, 0 ); - AddComponent( new AddonComponent( 0x1493 ), 2, 7, 0 ); - AddComponent( new AddonComponent( 0x1492 ), 2, 8, 0 ); - AddComponent( new AddonComponent( 0x145E ), 2, 9, 0 ); - AddComponent( new AddonComponent( 0x1459 ), 2,10, 0 ); + AddComponent(new AddonComponent(0x1496), 2, 3, 0); + AddComponent(new AddonComponent(0x1499), 2, 4, 0); + AddComponent(new AddonComponent(0x148E), 2, 6, 0); + AddComponent(new AddonComponent(0x1493), 2, 7, 0); + AddComponent(new AddonComponent(0x1492), 2, 8, 0); + AddComponent(new AddonComponent(0x145E), 2, 9, 0); + AddComponent(new AddonComponent(0x1459), 2, 10, 0); - AddComponent( new AddonComponent( 0x1497 ), 3, 2, 0 ); - AddComponent( new AddonComponent( 0x145F ), 3, 9, 0 ); - AddComponent( new AddonComponent( 0x1461 ), 3,10, 0 ); + AddComponent(new AddonComponent(0x1497), 3, 2, 0); + AddComponent(new AddonComponent(0x145F), 3, 9, 0); + AddComponent(new AddonComponent(0x1461), 3, 10, 0); - AddComponent( new AddonComponent( 0x149A ), 4, 1, 0 ); - AddComponent( new AddonComponent( 0x1498 ), 4, 2, 0 ); - AddComponent( new AddonComponent( 0x148F ), 4, 4, 0 ); - AddComponent( new AddonComponent( 0x148D ), 4, 6, 0 ); - AddComponent( new AddonComponent( 0x1488 ), 4, 8, 0 ); - AddComponent( new AddonComponent( 0x1460 ), 4, 9, 0 ); - AddComponent( new AddonComponent( 0x1462 ), 4,10, 0 ); + AddComponent(new AddonComponent(0x149A), 4, 1, 0); + AddComponent(new AddonComponent(0x1498), 4, 2, 0); + AddComponent(new AddonComponent(0x148F), 4, 4, 0); + AddComponent(new AddonComponent(0x148D), 4, 6, 0); + AddComponent(new AddonComponent(0x1488), 4, 8, 0); + AddComponent(new AddonComponent(0x1460), 4, 9, 0); + AddComponent(new AddonComponent(0x1462), 4, 10, 0); - AddComponent( new AddonComponent( 0x147D ), 5, 0, 0 ); - AddComponent( new AddonComponent( 0x1490 ), 5, 4, 0 ); - AddComponent( new AddonComponent( 0x148B ), 5, 5, 0 ); - AddComponent( new AddonComponent( 0x148A ), 5, 6, 0 ); - AddComponent( new AddonComponent( 0x1486 ), 5, 7, 0 ); - AddComponent( new AddonComponent( 0x1485 ), 5, 8, 0 ); + AddComponent(new AddonComponent(0x147D), 5, 0, 0); + AddComponent(new AddonComponent(0x1490), 5, 4, 0); + AddComponent(new AddonComponent(0x148B), 5, 5, 0); + AddComponent(new AddonComponent(0x148A), 5, 6, 0); + AddComponent(new AddonComponent(0x1486), 5, 7, 0); + AddComponent(new AddonComponent(0x1485), 5, 8, 0); - AddComponent( new AddonComponent( 0x147C ), 6, 0, 0 ); - AddComponent( new AddonComponent( 0x1491 ), 6, 4, 0 ); - AddComponent( new AddonComponent( 0x148C ), 6, 5, 0 ); - AddComponent( new AddonComponent( 0x1489 ), 6, 6, 0 ); - AddComponent( new AddonComponent( 0x1487 ), 6, 7, 0 ); - AddComponent( new AddonComponent( 0x1484 ), 6, 8, 0 ); - AddComponent( new AddonComponent( 0x1463 ), 6,10, 0 ); + AddComponent(new AddonComponent(0x147C), 6, 0, 0); + AddComponent(new AddonComponent(0x1491), 6, 4, 0); + AddComponent(new AddonComponent(0x148C), 6, 5, 0); + AddComponent(new AddonComponent(0x1489), 6, 6, 0); + AddComponent(new AddonComponent(0x1487), 6, 7, 0); + AddComponent(new AddonComponent(0x1484), 6, 8, 0); + AddComponent(new AddonComponent(0x1463), 6, 10, 0); - AddComponent( new AddonComponent( 0x147B ), 7, 0, 0 ); - AddComponent( new AddonComponent( 0x147F ), 7, 3, 0 ); - AddComponent( new AddonComponent( 0x1480 ), 7, 4, 0 ); - AddComponent( new AddonComponent( 0x1482 ), 7, 5, 0 ); - AddComponent( new AddonComponent( 0x1469 ), 7, 6, 0 ); - AddComponent( new AddonComponent( 0x1468 ), 7, 7, 0 ); - AddComponent( new AddonComponent( 0x1465 ), 7, 8, 0 ); - AddComponent( new AddonComponent( 0x1464 ), 7, 9, 0 ); + AddComponent(new AddonComponent(0x147B), 7, 0, 0); + AddComponent(new AddonComponent(0x147F), 7, 3, 0); + AddComponent(new AddonComponent(0x1480), 7, 4, 0); + AddComponent(new AddonComponent(0x1482), 7, 5, 0); + AddComponent(new AddonComponent(0x1469), 7, 6, 0); + AddComponent(new AddonComponent(0x1468), 7, 7, 0); + AddComponent(new AddonComponent(0x1465), 7, 8, 0); + AddComponent(new AddonComponent(0x1464), 7, 9, 0); - AddComponent( new AddonComponent( 0x147A ), 8, 0, 0 ); - AddComponent( new AddonComponent( 0x1479 ), 8, 1, 0 ); - AddComponent( new AddonComponent( 0x1477 ), 8, 2, 0 ); - AddComponent( new AddonComponent( 0x147E ), 8, 3, 0 ); - AddComponent( new AddonComponent( 0x1481 ), 8, 4, 0 ); - AddComponent( new AddonComponent( 0x1483 ), 8, 5, 0 ); - AddComponent( new AddonComponent( 0x146A ), 8, 6, 0 ); - AddComponent( new AddonComponent( 0x1467 ), 8, 7, 0 ); - AddComponent( new AddonComponent( 0x1466 ), 8, 8, 0 ); + AddComponent(new AddonComponent(0x147A), 8, 0, 0); + AddComponent(new AddonComponent(0x1479), 8, 1, 0); + AddComponent(new AddonComponent(0x1477), 8, 2, 0); + AddComponent(new AddonComponent(0x147E), 8, 3, 0); + AddComponent(new AddonComponent(0x1481), 8, 4, 0); + AddComponent(new AddonComponent(0x1483), 8, 5, 0); + AddComponent(new AddonComponent(0x146A), 8, 6, 0); + AddComponent(new AddonComponent(0x1467), 8, 7, 0); + AddComponent(new AddonComponent(0x1466), 8, 8, 0); - AddComponent( new AddonComponent( 0x1478 ), 9, 1, 0 ); - AddComponent( new AddonComponent( 0x1475 ), 9, 2, 0 ); - AddComponent( new AddonComponent( 0x1474 ), 9, 3, 0 ); - AddComponent( new AddonComponent( 0x146F ), 9, 4, 0 ); - AddComponent( new AddonComponent( 0x146E ), 9, 5, 0 ); - AddComponent( new AddonComponent( 0x146D ), 9, 6, 0 ); - AddComponent( new AddonComponent( 0x146B ), 9, 7, 0 ); + AddComponent(new AddonComponent(0x1478), 9, 1, 0); + AddComponent(new AddonComponent(0x1475), 9, 2, 0); + AddComponent(new AddonComponent(0x1474), 9, 3, 0); + AddComponent(new AddonComponent(0x146F), 9, 4, 0); + AddComponent(new AddonComponent(0x146E), 9, 5, 0); + AddComponent(new AddonComponent(0x146D), 9, 6, 0); + AddComponent(new AddonComponent(0x146B), 9, 7, 0); - AddComponent( new AddonComponent( 0x1476 ),10, 2, 0 ); - AddComponent( new AddonComponent( 0x1473 ),10, 3, 0 ); - AddComponent( new AddonComponent( 0x1470 ),10, 4, 0 ); - AddComponent( new AddonComponent( 0x1471 ),10, 5, 0 ); - AddComponent( new AddonComponent( 0x1472 ),10, 6, 0 ); - } + AddComponent(new AddonComponent(0x1476), 10, 2, 0); + AddComponent(new AddonComponent(0x1473), 10, 3, 0); + AddComponent(new AddonComponent(0x1470), 10, 4, 0); + AddComponent(new AddonComponent(0x1471), 10, 5, 0); + AddComponent(new AddonComponent(0x1472), 10, 6, 0); + } - public Telescope( Serial serial ) : base( serial ) - { - } + public Telescope(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Addons/TrainingDummies.cs b/Scripts/Items/Addons/TrainingDummies.cs index 5030e8947..ce7a20690 100644 --- a/Scripts/Items/Addons/TrainingDummies.cs +++ b/Scripts/Items/Addons/TrainingDummies.cs @@ -2,266 +2,267 @@ using System; namespace Server.Items { - [Flippable( 0x1070, 0x1074 )] - public class TrainingDummy : AddonComponent - { - private Timer m_Timer; + [Flippable(0x1070, 0x1074)] + public class TrainingDummy : AddonComponent + { + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public double MinSkill { get; set; } + [Constructible] + public TrainingDummy() : this(0x1074) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public double MaxSkill { get; set; } + [Constructible] + public TrainingDummy(int itemID) : base(itemID) + { + MinSkill = -25.0; + MaxSkill = +25.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool Swinging => ( m_Timer != null ); + public TrainingDummy(Serial serial) : base(serial) + { + } - [Constructible] - public TrainingDummy() : this( 0x1074 ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public double MinSkill{ get; set; } - [Constructible] - public TrainingDummy( int itemID ) : base( itemID ) - { - MinSkill = -25.0; - MaxSkill = +25.0; - } + [CommandProperty(AccessLevel.GameMaster)] + public double MaxSkill{ get; set; } - public void UpdateItemID() - { - int baseItemID = (ItemID / 2) * 2; + [CommandProperty(AccessLevel.GameMaster)] + public bool Swinging => m_Timer != null; - ItemID = baseItemID + (Swinging ? 1 : 0); - } + public void UpdateItemID() + { + int baseItemID = ItemID / 2 * 2; - public void BeginSwing() - { - m_Timer?.Stop(); + ItemID = baseItemID + (Swinging ? 1 : 0); + } - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - } + public void BeginSwing() + { + m_Timer?.Stop(); - public void EndSwing() - { - m_Timer?.Stop(); + m_Timer = new InternalTimer(this); + m_Timer.Start(); + } - m_Timer = null; + public void EndSwing() + { + m_Timer?.Stop(); - UpdateItemID(); - } + m_Timer = null; - public void OnHit() - { - UpdateItemID(); - Effects.PlaySound( GetWorldLocation(), Map, Utility.RandomList( 0x3A4, 0x3A6, 0x3A9, 0x3AE, 0x3B4, 0x3B6 ) ); - } + UpdateItemID(); + } - public void Use( Mobile from, BaseWeapon weapon ) - { - BeginSwing(); + public void OnHit() + { + UpdateItemID(); + Effects.PlaySound(GetWorldLocation(), Map, Utility.RandomList(0x3A4, 0x3A6, 0x3A9, 0x3AE, 0x3B4, 0x3B6)); + } - from.Direction = from.GetDirectionTo( GetWorldLocation() ); - weapon.PlaySwingAnimation( from ); + public void Use(Mobile from, BaseWeapon weapon) + { + BeginSwing(); - from.CheckSkill( weapon.Skill, MinSkill, MaxSkill ); - } + from.Direction = from.GetDirectionTo(GetWorldLocation()); + weapon.PlaySwingAnimation(from); - public override void OnDoubleClick( Mobile from ) - { - BaseWeapon weapon = from.Weapon as BaseWeapon; + from.CheckSkill(weapon.Skill, MinSkill, MaxSkill); + } - if ( weapon is BaseRanged ) - SendLocalizedMessageTo( from, 501822 ); // You can't practice ranged weapons on this. - else if ( weapon == null || !from.InRange( GetWorldLocation(), weapon.MaxRange ) ) - SendLocalizedMessageTo( from, 501816 ); // You are too far away to do that. - else if ( Swinging ) - SendLocalizedMessageTo( from, 501815 ); // You have to wait until it stops swinging. - else if ( from.Skills[weapon.Skill].Base >= MaxSkill ) - SendLocalizedMessageTo( from, 501828 ); // Your skill cannot improve any further by simply practicing with a dummy. - else if ( from.Mounted ) - SendLocalizedMessageTo( from, 501829 ); // You can't practice on this while on a mount. - else - Use( from, weapon ); - } + public override void OnDoubleClick(Mobile from) + { + BaseWeapon weapon = from.Weapon as BaseWeapon; - public TrainingDummy( Serial serial ) : base( serial ) - { - } + if (weapon is BaseRanged) + SendLocalizedMessageTo(from, 501822); // You can't practice ranged weapons on this. + else if (weapon == null || !from.InRange(GetWorldLocation(), weapon.MaxRange)) + SendLocalizedMessageTo(from, 501816); // You are too far away to do that. + else if (Swinging) + SendLocalizedMessageTo(from, 501815); // You have to wait until it stops swinging. + else if (from.Skills[weapon.Skill].Base >= MaxSkill) + SendLocalizedMessageTo(from, + 501828); // Your skill cannot improve any further by simply practicing with a dummy. + else if (from.Mounted) + SendLocalizedMessageTo(from, 501829); // You can't practice on this while on a mount. + else + Use(from, weapon); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( MinSkill ); - writer.Write( MaxSkill ); - } + writer.Write(MinSkill); + writer.Write(MaxSkill); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - MinSkill = reader.ReadDouble(); - MaxSkill = reader.ReadDouble(); + switch (version) + { + case 0: + { + MinSkill = reader.ReadDouble(); + MaxSkill = reader.ReadDouble(); - if ( MinSkill == 0.0 && MaxSkill == 30.0 ) - { - MinSkill = -25.0; - MaxSkill = +25.0; - } + if (MinSkill == 0.0 && MaxSkill == 30.0) + { + MinSkill = -25.0; + MaxSkill = +25.0; + } - break; - } - } + break; + } + } - UpdateItemID(); - } + UpdateItemID(); + } - private class InternalTimer : Timer - { - private TrainingDummy m_Dummy; - private bool m_Delay = true; + private class InternalTimer : Timer + { + private bool m_Delay = true; + private TrainingDummy m_Dummy; - public InternalTimer( TrainingDummy dummy ) : base( TimeSpan.FromSeconds( 0.25 ), TimeSpan.FromSeconds( 2.75 ) ) - { - m_Dummy = dummy; - Priority = TimerPriority.FiftyMS; - } + public InternalTimer(TrainingDummy dummy) : base(TimeSpan.FromSeconds(0.25), TimeSpan.FromSeconds(2.75)) + { + m_Dummy = dummy; + Priority = TimerPriority.FiftyMS; + } - protected override void OnTick() - { - if ( m_Delay ) - m_Dummy.OnHit(); - else - m_Dummy.EndSwing(); + protected override void OnTick() + { + if (m_Delay) + m_Dummy.OnHit(); + else + m_Dummy.EndSwing(); - m_Delay = !m_Delay; - } - } - } + m_Delay = !m_Delay; + } + } + } - public class TrainingDummyEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TrainingDummyEastDeed(); + public class TrainingDummyEastAddon : BaseAddon + { + [Constructible] + public TrainingDummyEastAddon() + { + AddComponent(new TrainingDummy(0x1074), 0, 0, 0); + } - [Constructible] - public TrainingDummyEastAddon() - { - AddComponent( new TrainingDummy( 0x1074 ), 0, 0, 0 ); - } + public TrainingDummyEastAddon(Serial serial) : base(serial) + { + } - public TrainingDummyEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TrainingDummyEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class TrainingDummyEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TrainingDummyEastAddon(); - public override int LabelNumber => 1044335; // training dummy (east) + public class TrainingDummyEastDeed : BaseAddonDeed + { + [Constructible] + public TrainingDummyEastDeed() + { + } - [Constructible] - public TrainingDummyEastDeed() - { - } + public TrainingDummyEastDeed(Serial serial) : base(serial) + { + } - public TrainingDummyEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TrainingDummyEastAddon(); + public override int LabelNumber => 1044335; // training dummy (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class TrainingDummySouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TrainingDummySouthDeed(); + public class TrainingDummySouthAddon : BaseAddon + { + [Constructible] + public TrainingDummySouthAddon() + { + AddComponent(new TrainingDummy(0x1070), 0, 0, 0); + } - [Constructible] - public TrainingDummySouthAddon() - { - AddComponent( new TrainingDummy( 0x1070 ), 0, 0, 0 ); - } + public TrainingDummySouthAddon(Serial serial) : base(serial) + { + } - public TrainingDummySouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TrainingDummySouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class TrainingDummySouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TrainingDummySouthAddon(); - public override int LabelNumber => 1044336; // training dummy (south) + public class TrainingDummySouthDeed : BaseAddonDeed + { + [Constructible] + public TrainingDummySouthDeed() + { + } - [Constructible] - public TrainingDummySouthDeed() - { - } + public TrainingDummySouthDeed(Serial serial) : base(serial) + { + } - public TrainingDummySouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TrainingDummySouthAddon(); + public override int LabelNumber => 1044336; // training dummy (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/WarriorStatueEastAddon.cs b/Scripts/Items/Addons/WarriorStatueEastAddon.cs index 41beb145e..89fba8a54 100644 --- a/Scripts/Items/Addons/WarriorStatueEastAddon.cs +++ b/Scripts/Items/Addons/WarriorStatueEastAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class WarriorStatueEastAddon : BaseAddon - { - public override BaseAddonDeed Deed => new WarriorStatueEastDeed(); + public class WarriorStatueEastAddon : BaseAddon + { + [Constructible] + public WarriorStatueEastAddon() + { + AddComponent(new AddonComponent(0x2D12), 0, 0, 0); + } - [Constructible] - public WarriorStatueEastAddon() - { - AddComponent( new AddonComponent( 0x2D12 ), 0, 0, 0 ); - } + public WarriorStatueEastAddon(Serial serial) : base(serial) + { + } - public WarriorStatueEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new WarriorStatueEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WarriorStatueEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new WarriorStatueEastAddon(); - public override int LabelNumber => 1072888; // warrior statue (east) + public class WarriorStatueEastDeed : BaseAddonDeed + { + [Constructible] + public WarriorStatueEastDeed() + { + } - [Constructible] - public WarriorStatueEastDeed() - { - } + public WarriorStatueEastDeed(Serial serial) : base(serial) + { + } - public WarriorStatueEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new WarriorStatueEastAddon(); + public override int LabelNumber => 1072888; // warrior statue (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/WarriorStatueSouthAddon.cs b/Scripts/Items/Addons/WarriorStatueSouthAddon.cs index 1cae0dafd..823f3eb22 100644 --- a/Scripts/Items/Addons/WarriorStatueSouthAddon.cs +++ b/Scripts/Items/Addons/WarriorStatueSouthAddon.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class WarriorStatueSouthAddon : BaseAddon - { - public override BaseAddonDeed Deed => new WarriorStatueSouthDeed(); + public class WarriorStatueSouthAddon : BaseAddon + { + [Constructible] + public WarriorStatueSouthAddon() + { + AddComponent(new AddonComponent(0x2D13), 0, 0, 0); + } - [Constructible] - public WarriorStatueSouthAddon() - { - AddComponent( new AddonComponent( 0x2D13 ), 0, 0, 0 ); - } + public WarriorStatueSouthAddon(Serial serial) : base(serial) + { + } - public WarriorStatueSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new WarriorStatueSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WarriorStatueSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new WarriorStatueSouthAddon(); - public override int LabelNumber => 1072887; // warrior statue (south) + public class WarriorStatueSouthDeed : BaseAddonDeed + { + [Constructible] + public WarriorStatueSouthDeed() + { + } - [Constructible] - public WarriorStatueSouthDeed() - { - } + public WarriorStatueSouthDeed(Serial serial) : base(serial) + { + } - public WarriorStatueSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new WarriorStatueSouthAddon(); + public override int LabelNumber => 1072887; // warrior statue (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/WaterTroughEastAddon.cs b/Scripts/Items/Addons/WaterTroughEastAddon.cs index c8cd87808..e8b071550 100644 --- a/Scripts/Items/Addons/WaterTroughEastAddon.cs +++ b/Scripts/Items/Addons/WaterTroughEastAddon.cs @@ -1,67 +1,67 @@ namespace Server.Items { - public class WaterTroughEastAddon : BaseAddon, IWaterSource - { - public override BaseAddonDeed Deed => new WaterTroughEastDeed(); + public class WaterTroughEastAddon : BaseAddon, IWaterSource + { + [Constructible] + public WaterTroughEastAddon() + { + AddComponent(new AddonComponent(0xB41), 0, 0, 0); + AddComponent(new AddonComponent(0xB42), 0, 1, 0); + } - [Constructible] - public WaterTroughEastAddon() - { - AddComponent( new AddonComponent( 0xB41 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xB42 ), 0, 1, 0 ); - } + public WaterTroughEastAddon(Serial serial) : base(serial) + { + } - public WaterTroughEastAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new WaterTroughEastDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public int Quantity + { + get => 500; + set { } + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public int Quantity - { - get => 500; - set{} - } - } + int version = reader.ReadInt(); + } + } - public class WaterTroughEastDeed : BaseAddonDeed - { - public override BaseAddon Addon => new WaterTroughEastAddon(); - public override int LabelNumber => 1044349; // water trough (east) + public class WaterTroughEastDeed : BaseAddonDeed + { + [Constructible] + public WaterTroughEastDeed() + { + } - [Constructible] - public WaterTroughEastDeed() - { - } + public WaterTroughEastDeed(Serial serial) : base(serial) + { + } - public WaterTroughEastDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new WaterTroughEastAddon(); + public override int LabelNumber => 1044349; // water trough (east) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/WaterTroughSouthAddon.cs b/Scripts/Items/Addons/WaterTroughSouthAddon.cs index 75c6a62bc..7a51e85eb 100644 --- a/Scripts/Items/Addons/WaterTroughSouthAddon.cs +++ b/Scripts/Items/Addons/WaterTroughSouthAddon.cs @@ -1,67 +1,67 @@ namespace Server.Items { - public class WaterTroughSouthAddon : BaseAddon, IWaterSource - { - public override BaseAddonDeed Deed => new WaterTroughSouthDeed(); + public class WaterTroughSouthAddon : BaseAddon, IWaterSource + { + [Constructible] + public WaterTroughSouthAddon() + { + AddComponent(new AddonComponent(0xB43), 0, 0, 0); + AddComponent(new AddonComponent(0xB44), 1, 0, 0); + } - [Constructible] - public WaterTroughSouthAddon() - { - AddComponent( new AddonComponent( 0xB43 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0xB44 ), 1, 0, 0 ); - } + public WaterTroughSouthAddon(Serial serial) : base(serial) + { + } - public WaterTroughSouthAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new WaterTroughSouthDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public int Quantity + { + get => 500; + set { } + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public int Quantity - { - get => 500; - set{} - } - } + int version = reader.ReadInt(); + } + } - public class WaterTroughSouthDeed : BaseAddonDeed - { - public override BaseAddon Addon => new WaterTroughSouthAddon(); - public override int LabelNumber => 1044350; // water trough (south) + public class WaterTroughSouthDeed : BaseAddonDeed + { + [Constructible] + public WaterTroughSouthDeed() + { + } - [Constructible] - public WaterTroughSouthDeed() - { - } + public WaterTroughSouthDeed(Serial serial) : base(serial) + { + } - public WaterTroughSouthDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new WaterTroughSouthAddon(); + public override int LabelNumber => 1044350; // water trough (south) - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Addons/WaterVat.cs b/Scripts/Items/Addons/WaterVat.cs index 781b669b9..0d442862b 100644 --- a/Scripts/Items/Addons/WaterVat.cs +++ b/Scripts/Items/Addons/WaterVat.cs @@ -1,84 +1,84 @@ namespace Server.Items { - public class WaterVatEast : BaseAddon - { - [Constructible] - public WaterVatEast() - { - AddComponent( new AddonComponent( 0x1558 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x14DE ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0x1552 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x14DF ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0x1554 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1559 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1550 ), 1, 3, 0 ); - AddComponent( new AddonComponent( 0x1555 ), 3, 1, 0 ); - AddComponent( new AddonComponent( 0x14D7 ), 2, 2, 0 ); + public class WaterVatEast : BaseAddon + { + [Constructible] + public WaterVatEast() + { + AddComponent(new AddonComponent(0x1558), 0, 0, 0); + AddComponent(new AddonComponent(0x14DE), -1, 1, 0); + AddComponent(new AddonComponent(0x1552), 0, 1, 0); + AddComponent(new AddonComponent(0x14DF), 1, -1, 0); + AddComponent(new AddonComponent(0x1554), 1, 0, 0); + AddComponent(new AddonComponent(0x1559), 1, 1, 0); + AddComponent(new AddonComponent(0x1550), 1, 3, 0); + AddComponent(new AddonComponent(0x1555), 3, 1, 0); + AddComponent(new AddonComponent(0x14D7), 2, 2, 0); - // Blockers - AddComponent( new AddonComponent( 0x21A4 ), 2, -1, 0 ); - AddComponent( new AddonComponent( 0x21A4 ), 3, 0, 0 ); - AddComponent( new AddonComponent( 0x21A4 ), -1, 2, 0 ); - AddComponent( new AddonComponent( 0x21A4 ), 0, 3, 0 ); - } + // Blockers + AddComponent(new AddonComponent(0x21A4), 2, -1, 0); + AddComponent(new AddonComponent(0x21A4), 3, 0, 0); + AddComponent(new AddonComponent(0x21A4), -1, 2, 0); + AddComponent(new AddonComponent(0x21A4), 0, 3, 0); + } - public WaterVatEast( Serial serial ) : base( serial ) - { - } + public WaterVatEast(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WaterVatSouth : BaseAddon - { - [Constructible] - public WaterVatSouth() - { - AddComponent( new AddonComponent( 0x1558 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x14DE ), -1, 1, 0 ); - AddComponent( new AddonComponent( 0x1552 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x14DF ), 1, -1, 0 ); - AddComponent( new AddonComponent( 0x1554 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1559 ), 1, 1, 0 ); - AddComponent( new AddonComponent( 0x1551 ), 1, 3, 0 ); - AddComponent( new AddonComponent( 0x1556 ), 3, 1, 0 ); - AddComponent( new AddonComponent( 0x14D7 ), 2, 2, 0 ); + public class WaterVatSouth : BaseAddon + { + [Constructible] + public WaterVatSouth() + { + AddComponent(new AddonComponent(0x1558), 0, 0, 0); + AddComponent(new AddonComponent(0x14DE), -1, 1, 0); + AddComponent(new AddonComponent(0x1552), 0, 1, 0); + AddComponent(new AddonComponent(0x14DF), 1, -1, 0); + AddComponent(new AddonComponent(0x1554), 1, 0, 0); + AddComponent(new AddonComponent(0x1559), 1, 1, 0); + AddComponent(new AddonComponent(0x1551), 1, 3, 0); + AddComponent(new AddonComponent(0x1556), 3, 1, 0); + AddComponent(new AddonComponent(0x14D7), 2, 2, 0); - // Blockers - AddComponent( new AddonComponent( 0x21A4 ), 2, -1, 0 ); - AddComponent( new AddonComponent( 0x21A4 ), 3, 0, 0 ); - AddComponent( new AddonComponent( 0x21A4 ), -1, 2, 0 ); - AddComponent( new AddonComponent( 0x21A4 ), 0, 3, 0 ); - } + // Blockers + AddComponent(new AddonComponent(0x21A4), 2, -1, 0); + AddComponent(new AddonComponent(0x21A4), 3, 0, 0); + AddComponent(new AddonComponent(0x21A4), -1, 2, 0); + AddComponent(new AddonComponent(0x21A4), 0, 3, 0); + } - public WaterVatSouth( Serial serial ) : base( serial ) - { - } + public WaterVatSouth(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Aquarium.cs b/Scripts/Items/Aquarium/Aquarium.cs index 1a34979cb..7cc5b6895 100644 --- a/Scripts/Items/Aquarium/Aquarium.cs +++ b/Scripts/Items/Aquarium/Aquarium.cs @@ -1,1163 +1,1186 @@ using System; using System.Collections.Generic; +using Server.ContextMenus; using Server.Multis; using Server.Network; -using Server.ContextMenus; namespace Server.Items { - public class Aquarium : BaseAddonContainer - { - public static readonly TimeSpan EvaluationInterval = TimeSpan.FromDays( 1 ); - - // items info - - [CommandProperty( AccessLevel.GameMaster )] - public int LiveCreatures { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int DeadCreatures - { - get - { - int dead = 0; - - for ( int i = 0; i < Items.Count; i ++ ) - { - if ( Items[ i ] is BaseFish ) - { - BaseFish fish = (BaseFish) Items[ i ]; - - if ( fish.Dead ) - dead += 1; - } - } - - return dead; - } - } + public class Aquarium : BaseAddonContainer + { + public static readonly TimeSpan EvaluationInterval = TimeSpan.FromDays(1); + private bool m_EvaluateDay; - [CommandProperty( AccessLevel.GameMaster )] - public int MaxLiveCreatures - { - get - { - int state = ( m_Food.State == (int) FoodState.Overfed ) ? 1 : (int) FoodState.Full - m_Food.State; + // aquarium state + private AquariumState m_Food; - state += (int) WaterState.Strong - m_Water.State; + // events + private bool m_RewardAvailable; - state = (int) Math.Pow( state, 1.75 ); + // evaluate timer + private Timer m_Timer; - return MaxItems - state; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsFull => ( Items.Count >= MaxItems ); - - // vacation info - private int m_VacationLeft; - - [CommandProperty( AccessLevel.GameMaster )] - public int VacationLeft - { - get => m_VacationLeft; - set{ m_VacationLeft = value; InvalidateProperties(); } - } - - // aquarium state - private AquariumState m_Food; - private AquariumState m_Water; - - [CommandProperty( AccessLevel.GameMaster )] - public AquariumState Food - { - get => m_Food; - set{ m_Food = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public AquariumState Water - { - get => m_Water; - set{ m_Water = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool OptimalState => ( m_Food.State == (int) FoodState.Full && m_Water.State == (int) WaterState.Strong ); - - // events - private bool m_RewardAvailable; - private bool m_EvaluateDay; - - public List Events { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool RewardAvailable - { - get => m_RewardAvailable; - set{ m_RewardAvailable = value; InvalidateProperties(); } - } - - // evaluate timer - private Timer m_Timer; - - public override BaseAddonContainerDeed Deed - { - get - { - if ( ItemID == 0x3062 ) - return new AquariumEastDeed(); - return new AquariumNorthDeed(); - } - } - - public override double DefaultWeight => 10.0; - - public Aquarium( int itemID ) : base( itemID ) - { - Movable = false; - - if ( itemID == 0x3060 ) - AddComponent( new AddonContainerComponent( 0x3061 ), -1, 0, 0 ); - - if ( itemID == 0x3062 ) - AddComponent( new AddonContainerComponent( 0x3063 ), 0, -1, 0 ); - - MaxItems = 30; - - m_Food = new AquariumState(); - m_Water = new AquariumState(); - - m_Food.State = (int) FoodState.Full; - m_Water.State = (int) WaterState.Strong; - - m_Food.Maintain = Utility.RandomMinMax( 1, 2 ); - m_Food.Improve = m_Food.Maintain + Utility.RandomMinMax( 1, 2 ); - - m_Water.Maintain = Utility.RandomMinMax( 1, 3 ); - - Events = new List(); - - m_Timer = Timer.DelayCall( EvaluationInterval, EvaluationInterval, Evaluate ); - } - - public Aquarium( Serial serial ) : base( serial ) - { - } - - public override void OnDelete() - { - if ( m_Timer != null ) - { - m_Timer.Stop(); - m_Timer = null; - } - } - - public override void OnDoubleClick( Mobile from ) - { - ExamineAquarium( from ); - } - - public virtual bool HasAccess( Mobile from ) - { - if ( from == null || from.Deleted ) - return false; - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - - BaseHouse house = BaseHouse.FindHouseAt( this ); - - return ( house != null && house.IsCoOwner( from ) ); - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( !HasAccess( from ) ) - { - from.SendLocalizedMessage( 1073821 ); // You do not have access to that item for use with the aquarium. - return false; - } - - if ( m_VacationLeft > 0 ) - { - from.SendLocalizedMessage( 1074427 ); // The aquarium is in vacation mode. - return false; - } - - bool takeItem = true; - - if ( dropped is FishBowl bowl ) - { - if ( bowl.Empty || !AddFish( from, bowl.Fish ) ) - return false; - - bowl.InvalidateProperties(); - - takeItem = false; - } - else if ( dropped is BaseFish fish ) - { - if ( !AddFish( from, fish ) ) - return false; - } - else if ( dropped is VacationWafer ) - { - m_VacationLeft = VacationWafer.VacationDays; - dropped.Delete(); + // vacation info + private int m_VacationLeft; + private AquariumState m_Water; - from.SendLocalizedMessage( 1074428, m_VacationLeft.ToString() ); // The aquarium will be in vacation mode for ~1_DAYS~ days - } - else if ( dropped is AquariumFood ) - { - m_Food.Added += 1; - dropped.Delete(); + public Aquarium(int itemID) : base(itemID) + { + Movable = false; + + if (itemID == 0x3060) + AddComponent(new AddonContainerComponent(0x3061), -1, 0, 0); + + if (itemID == 0x3062) + AddComponent(new AddonContainerComponent(0x3063), 0, -1, 0); + + MaxItems = 30; + + m_Food = new AquariumState(); + m_Water = new AquariumState(); + + m_Food.State = (int)FoodState.Full; + m_Water.State = (int)WaterState.Strong; + + m_Food.Maintain = Utility.RandomMinMax(1, 2); + m_Food.Improve = m_Food.Maintain + Utility.RandomMinMax(1, 2); + + m_Water.Maintain = Utility.RandomMinMax(1, 3); + + Events = new List(); + + m_Timer = Timer.DelayCall(EvaluationInterval, EvaluationInterval, Evaluate); + } + + public Aquarium(Serial serial) : base(serial) + { + } + + // items info + + [CommandProperty(AccessLevel.GameMaster)] + public int LiveCreatures{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int DeadCreatures + { + get + { + int dead = 0; + + for (int i = 0; i < Items.Count; i++) + if (Items[i] is BaseFish) + { + BaseFish fish = (BaseFish)Items[i]; + + if (fish.Dead) + dead += 1; + } + + return dead; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxLiveCreatures + { + get + { + int state = m_Food.State == (int)FoodState.Overfed ? 1 : (int)FoodState.Full - m_Food.State; + + state += (int)WaterState.Strong - m_Water.State; + + state = (int)Math.Pow(state, 1.75); + + return MaxItems - state; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsFull => Items.Count >= MaxItems; + + [CommandProperty(AccessLevel.GameMaster)] + public int VacationLeft + { + get => m_VacationLeft; + set + { + m_VacationLeft = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AquariumState Food + { + get => m_Food; + set + { + m_Food = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AquariumState Water + { + get => m_Water; + set + { + m_Water = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool OptimalState => m_Food.State == (int)FoodState.Full && m_Water.State == (int)WaterState.Strong; + + public List Events{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool RewardAvailable + { + get => m_RewardAvailable; + set + { + m_RewardAvailable = value; + InvalidateProperties(); + } + } + + public override BaseAddonContainerDeed Deed + { + get + { + if (ItemID == 0x3062) + return new AquariumEastDeed(); + return new AquariumNorthDeed(); + } + } + + public override double DefaultWeight => 10.0; + + public override void OnDelete() + { + if (m_Timer != null) + { + m_Timer.Stop(); + m_Timer = null; + } + } + + public override void OnDoubleClick(Mobile from) + { + ExamineAquarium(from); + } + + public virtual bool HasAccess(Mobile from) + { + if (from == null || from.Deleted) + return false; + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + + BaseHouse house = BaseHouse.FindHouseAt(this); + + return house != null && house.IsCoOwner(from); + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (!HasAccess(from)) + { + from.SendLocalizedMessage(1073821); // You do not have access to that item for use with the aquarium. + return false; + } + + if (m_VacationLeft > 0) + { + from.SendLocalizedMessage(1074427); // The aquarium is in vacation mode. + return false; + } + + bool takeItem = true; + + if (dropped is FishBowl bowl) + { + if (bowl.Empty || !AddFish(from, bowl.Fish)) + return false; + + bowl.InvalidateProperties(); + + takeItem = false; + } + else if (dropped is BaseFish fish) + { + if (!AddFish(from, fish)) + return false; + } + else if (dropped is VacationWafer) + { + m_VacationLeft = VacationWafer.VacationDays; + dropped.Delete(); + + from.SendLocalizedMessage(1074428, + m_VacationLeft.ToString()); // The aquarium will be in vacation mode for ~1_DAYS~ days + } + else if (dropped is AquariumFood) + { + m_Food.Added += 1; + dropped.Delete(); + + from.SendLocalizedMessage(1074259, "1"); // ~1_NUM~ unit(s) of food have been added to the aquarium. + } + else if (dropped is BaseBeverage beverage) + { + if (beverage.IsEmpty || !beverage.Pourable || beverage.Content != BeverageType.Water) + { + from.SendLocalizedMessage(500840); // Can't pour that in there. + return false; + } + + m_Water.Added += 1; + beverage.Quantity -= 1; + + from.PlaySound(0x4E); + from.SendLocalizedMessage(1074260, "1"); // ~1_NUM~ unit(s) of water have been added to the aquarium. + + takeItem = false; + } + else if (!AddDecoration(from, dropped)) + { + takeItem = false; + } + + from.CloseGump(typeof(AquariumGump)); + + InvalidateProperties(); + + if (takeItem) + from.PlaySound(0x42); + + return takeItem; + } + + public override void DropItemsToGround() + { + Point3D loc = GetWorldLocation(); + + for (int i = Items.Count - 1; i >= 0; i--) + { + Item item = Items[i]; + + item.MoveToWorld(loc, Map); + + if (item is BaseFish fish && !fish.Dead) + fish.StartTimer(); + } + } + + public override bool CheckItemUse(Mobile from, Item item) + { + if (item != this) + return false; + + return base.CheckItemUse(from, item); + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (item != this) + { + reject = LRReason.CannotLift; + return false; + } + + return base.CheckLift(from, item, ref reject); + } + + public override void OnSingleClick(Mobile from) + { + if (Deleted || !from.CanSee(this)) + return; + + base.OnSingleClick(from); + + if (m_VacationLeft > 0) + LabelTo(from, 1074430, m_VacationLeft.ToString()); // Vacation days left: ~1_DAYS + + if (Events.Count > 0) + LabelTo(from, 1074426, Events.Count.ToString()); // ~1_NUM~ event(s) to view! + + if (m_RewardAvailable) + LabelTo(from, 1074362); // A reward is available! + + LabelTo(from, 1074247, $"{LiveCreatures}\t{MaxLiveCreatures}"); // Live Creatures: ~1_NUM~ / ~2_MAX~ + + if (DeadCreatures > 0) + LabelTo(from, 1074248, DeadCreatures.ToString()); // Dead Creatures: ~1_NUM~ + + int decorations = Items.Count - LiveCreatures - DeadCreatures; + + if (decorations > 0) + LabelTo(from, 1074249, (Items.Count - LiveCreatures - DeadCreatures).ToString()); // Decorations: ~1_NUM~ + + LabelTo(from, 1074250, "#" + FoodNumber()); // Food state: ~1_STATE~ + LabelTo(from, 1074251, "#" + WaterNumber()); // Water state: ~1_STATE~ + + if (m_Food.State == (int)FoodState.Dead) + LabelTo(from, 1074577, $"{m_Food.Added}\t{m_Food.Improve}"); // Food Added: ~1_CUR~ Needed: ~2_NEED~ + else if (m_Food.State == (int)FoodState.Overfed) + LabelTo(from, 1074577, $"{m_Food.Added}\t{m_Food.Maintain}"); // Food Added: ~1_CUR~ Needed: ~2_NEED~ + else + LabelTo(from, 1074253, + $"{m_Food.Added}\t{m_Food.Maintain}\t{m_Food.Improve}"); // Food Added: ~1_CUR~ Feed: ~2_NEED~ Improve: ~3_GROW~ + + if (m_Water.State == (int)WaterState.Dead) + LabelTo(from, 1074578, $"{m_Water.Added}\t{m_Water.Improve}"); // Water Added: ~1_CUR~ Needed: ~2_NEED~ + else if (m_Water.State == (int)WaterState.Strong) + LabelTo(from, 1074578, $"{m_Water.Added}\t{m_Water.Maintain}"); // Water Added: ~1_CUR~ Needed: ~2_NEED~ + else + LabelTo(from, 1074254, + $"{m_Water.Added}\t{m_Water.Maintain}\t{m_Water.Improve}"); // Water Added: ~1_CUR~ Maintain: ~2_NEED~ Improve: ~3_GROW~ + } - from.SendLocalizedMessage( 1074259, "1" ); // ~1_NUM~ unit(s) of food have been added to the aquarium. - } - else if ( dropped is BaseBeverage beverage ) - { - if ( beverage.IsEmpty || !beverage.Pourable || beverage.Content != BeverageType.Water ) - { - from.SendLocalizedMessage( 500840 ); // Can't pour that in there. - return false; - } - - m_Water.Added += 1; - beverage.Quantity -= 1; - - from.PlaySound( 0x4E ); - from.SendLocalizedMessage( 1074260, "1" ); // ~1_NUM~ unit(s) of water have been added to the aquarium. - - takeItem = false; - } - else if ( !AddDecoration( from, dropped ) ) - { - takeItem = false; - } - - from.CloseGump( typeof( AquariumGump ) ); - - InvalidateProperties(); - - if ( takeItem ) - from.PlaySound( 0x42 ); - - return takeItem; - } - - public override void DropItemsToGround() - { - Point3D loc = GetWorldLocation(); - - for ( int i = Items.Count - 1; i >= 0; i-- ) - { - Item item = Items[ i ]; + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - item.MoveToWorld( loc, Map ); - - if ( item is BaseFish fish && !fish.Dead ) - fish.StartTimer(); - } - } - - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( item != this ) - return false; - - return base.CheckItemUse( from, item ); - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( item != this ) - { - reject = LRReason.CannotLift; - return false; - } - - return base.CheckLift( from, item, ref reject ); - } - - public override void OnSingleClick( Mobile from ) - { - if ( Deleted || !from.CanSee( this ) ) - return; + if (m_VacationLeft > 0) + list.Add(1074430, m_VacationLeft.ToString()); // Vacation days left: ~1_DAYS - base.OnSingleClick( from ); - - if ( m_VacationLeft > 0 ) - LabelTo( from, 1074430, m_VacationLeft.ToString() ); // Vacation days left: ~1_DAYS - - if ( Events.Count > 0 ) - LabelTo( from, 1074426, Events.Count.ToString() ); // ~1_NUM~ event(s) to view! - - if ( m_RewardAvailable ) - LabelTo( from, 1074362 ); // A reward is available! - - LabelTo( from, 1074247, $"{LiveCreatures}\t{MaxLiveCreatures}"); // Live Creatures: ~1_NUM~ / ~2_MAX~ - - if ( DeadCreatures > 0 ) - LabelTo( from, 1074248, DeadCreatures.ToString() ); // Dead Creatures: ~1_NUM~ - - int decorations = Items.Count - LiveCreatures - DeadCreatures; - - if ( decorations > 0 ) - LabelTo( from, 1074249, (Items.Count - LiveCreatures - DeadCreatures).ToString() ); // Decorations: ~1_NUM~ + if (Events.Count > 0) + list.Add(1074426, Events.Count.ToString()); // ~1_NUM~ event(s) to view! - LabelTo( from, 1074250, "#" + FoodNumber() ); // Food state: ~1_STATE~ - LabelTo( from, 1074251, "#" + WaterNumber() ); // Water state: ~1_STATE~ - - if ( m_Food.State == (int) FoodState.Dead ) - LabelTo( from, 1074577, $"{m_Food.Added}\t{m_Food.Improve}"); // Food Added: ~1_CUR~ Needed: ~2_NEED~ - else if ( m_Food.State == (int) FoodState.Overfed ) - LabelTo( from, 1074577, $"{m_Food.Added}\t{m_Food.Maintain}"); // Food Added: ~1_CUR~ Needed: ~2_NEED~ - else - LabelTo( from, 1074253, $"{m_Food.Added}\t{m_Food.Maintain}\t{m_Food.Improve}"); // Food Added: ~1_CUR~ Feed: ~2_NEED~ Improve: ~3_GROW~ + if (m_RewardAvailable) + list.Add(1074362); // A reward is available! - if ( m_Water.State == (int) WaterState.Dead ) - LabelTo( from, 1074578, $"{m_Water.Added}\t{m_Water.Improve}"); // Water Added: ~1_CUR~ Needed: ~2_NEED~ - else if ( m_Water.State == (int) WaterState.Strong ) - LabelTo( from, 1074578, $"{m_Water.Added}\t{m_Water.Maintain}"); // Water Added: ~1_CUR~ Needed: ~2_NEED~ - else - LabelTo( from, 1074254, $"{m_Water.Added}\t{m_Water.Maintain}\t{m_Water.Improve}"); // Water Added: ~1_CUR~ Maintain: ~2_NEED~ Improve: ~3_GROW~ - } + list.Add(1074247, "{0}\t{1}", LiveCreatures, MaxLiveCreatures); // Live Creatures: ~1_NUM~ / ~2_MAX~ - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + int dead = DeadCreatures; - if ( m_VacationLeft > 0 ) - list.Add( 1074430, m_VacationLeft.ToString() ); // Vacation days left: ~1_DAYS + if (dead > 0) + list.Add(1074248, dead.ToString()); // Dead Creatures: ~1_NUM~ - if ( Events.Count > 0 ) - list.Add( 1074426, Events.Count.ToString() ); // ~1_NUM~ event(s) to view! + int decorations = Items.Count - LiveCreatures - dead; - if ( m_RewardAvailable ) - list.Add( 1074362 ); // A reward is available! + if (decorations > 0) + list.Add(1074249, decorations.ToString()); // Decorations: ~1_NUM~ - list.Add( 1074247, "{0}\t{1}", LiveCreatures, MaxLiveCreatures ); // Live Creatures: ~1_NUM~ / ~2_MAX~ + list.Add(1074250, "#{0}", FoodNumber()); // Food state: ~1_STATE~ + list.Add(1074251, "#{0}", WaterNumber()); // Water state: ~1_STATE~ - int dead = DeadCreatures; + if (m_Food.State == (int)FoodState.Dead) + list.Add(1074577, "{0}\t{1}", m_Food.Added, m_Food.Improve); // Food Added: ~1_CUR~ Needed: ~2_NEED~ + else if (m_Food.State == (int)FoodState.Overfed) + list.Add(1074577, "{0}\t{1}", m_Food.Added, m_Food.Maintain); // Food Added: ~1_CUR~ Needed: ~2_NEED~ + else + list.Add(1074253, "{0}\t{1}\t{2}", m_Food.Added, m_Food.Maintain, + m_Food.Improve); // Food Added: ~1_CUR~ Feed: ~2_NEED~ Improve: ~3_GROW~ - if ( dead > 0 ) - list.Add( 1074248, dead.ToString() ); // Dead Creatures: ~1_NUM~ + if (m_Water.State == (int)WaterState.Dead) + list.Add(1074578, "{0}\t{1}", m_Water.Added, m_Water.Improve); // Water Added: ~1_CUR~ Needed: ~2_NEED~ + else if (m_Water.State == (int)WaterState.Strong) + list.Add(1074578, "{0}\t{1}", m_Water.Added, m_Water.Maintain); // Water Added: ~1_CUR~ Needed: ~2_NEED~ + else + list.Add(1074254, "{0}\t{1}\t{2}", m_Water.Added, m_Water.Maintain, + m_Water.Improve); // Water Added: ~1_CUR~ Maintain: ~2_NEED~ Improve: ~3_GROW~ + } - int decorations = Items.Count - LiveCreatures - dead; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( decorations > 0 ) - list.Add( 1074249, decorations.ToString() ); // Decorations: ~1_NUM~ + if (from.Alive) + { + list.Add(new ExamineEntry(this)); - list.Add( 1074250, "#{0}", FoodNumber() ); // Food state: ~1_STATE~ - list.Add( 1074251, "#{0}", WaterNumber() ); // Water state: ~1_STATE~ + if (HasAccess(from)) + { + if (m_RewardAvailable) + list.Add(new CollectRewardEntry(this)); - if ( m_Food.State == (int) FoodState.Dead ) - list.Add( 1074577, "{0}\t{1}", m_Food.Added, m_Food.Improve ); // Food Added: ~1_CUR~ Needed: ~2_NEED~ - else if ( m_Food.State == (int) FoodState.Overfed ) - list.Add( 1074577, "{0}\t{1}", m_Food.Added, m_Food.Maintain ); // Food Added: ~1_CUR~ Needed: ~2_NEED~ - else - list.Add( 1074253, "{0}\t{1}\t{2}", m_Food.Added, m_Food.Maintain, m_Food.Improve ); // Food Added: ~1_CUR~ Feed: ~2_NEED~ Improve: ~3_GROW~ + if (Events.Count > 0) + list.Add(new ViewEventEntry(this)); - if ( m_Water.State == (int) WaterState.Dead ) - list.Add( 1074578, "{0}\t{1}", m_Water.Added, m_Water.Improve ); // Water Added: ~1_CUR~ Needed: ~2_NEED~ - else if ( m_Water.State == (int) WaterState.Strong ) - list.Add( 1074578, "{0}\t{1}", m_Water.Added, m_Water.Maintain ); // Water Added: ~1_CUR~ Needed: ~2_NEED~ - else - list.Add( 1074254, "{0}\t{1}\t{2}", m_Water.Added, m_Water.Maintain, m_Water.Improve ); // Water Added: ~1_CUR~ Maintain: ~2_NEED~ Improve: ~3_GROW~ - } + if (m_VacationLeft > 0) + list.Add(new CancelVacationMode(this)); + } + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (from.AccessLevel >= AccessLevel.GameMaster) + { + list.Add(new GMAddFood(this)); + list.Add(new GMAddWater(this)); + list.Add(new GMForceEvaluate(this)); + list.Add(new GMOpen(this)); + list.Add(new GMFill(this)); + } + } - if ( from.Alive ) - { - list.Add( new ExamineEntry( this ) ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( HasAccess( from ) ) - { - if ( m_RewardAvailable ) - list.Add( new CollectRewardEntry( this ) ); + writer.Write(3); // Version + + // version 1 + if (m_Timer != null) + writer.Write(m_Timer.Next); + else + writer.Write(DateTime.UtcNow + EvaluationInterval); - if ( Events.Count > 0 ) - list.Add( new ViewEventEntry( this ) ); + // version 0 + writer.Write(LiveCreatures); + writer.Write(m_VacationLeft); - if ( m_VacationLeft > 0 ) - list.Add( new CancelVacationMode( this ) ); - } - } + m_Food.Serialize(writer); + m_Water.Serialize(writer); - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - list.Add( new GMAddFood( this ) ); - list.Add( new GMAddWater( this ) ); - list.Add( new GMForceEvaluate( this ) ); - list.Add( new GMOpen( this ) ); - list.Add( new GMFill( this ) ); - } - } + writer.Write(Events.Count); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( 3 ); // Version - - // version 1 - if ( m_Timer != null ) - writer.Write( m_Timer.Next ); - else - writer.Write( DateTime.UtcNow + EvaluationInterval ); - - // version 0 - writer.Write( (int) LiveCreatures ); - writer.Write( (int) m_VacationLeft ); - - m_Food.Serialize( writer ); - m_Water.Serialize( writer ); - - writer.Write( (int) Events.Count ); - - for ( int i = 0; i < Events.Count; i ++ ) - writer.Write( (int) Events[ i ] ); + for (int i = 0; i < Events.Count; i++) + writer.Write(Events[i]); - writer.Write( (bool) m_RewardAvailable ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); + writer.Write(m_RewardAvailable); + } - switch ( version ) - { - case 3: - case 2: - case 1: - { - DateTime next = reader.ReadDateTime(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( next < DateTime.UtcNow ) - next = DateTime.UtcNow; - - m_Timer = Timer.DelayCall( next - DateTime.UtcNow, EvaluationInterval, Evaluate ); - - goto case 0; - } - case 0: - { - LiveCreatures = reader.ReadInt(); - m_VacationLeft = reader.ReadInt(); - - m_Food = new AquariumState(); - m_Water = new AquariumState(); - - m_Food.Deserialize( reader ); - m_Water.Deserialize( reader ); - - Events = new List(); - - int count = reader.ReadInt(); - - for ( int i = 0; i < count; i ++ ) - Events.Add( reader.ReadInt() ); - - m_RewardAvailable = reader.ReadBool(); - - break; - } - } - - if ( version < 2 ) - { - Weight = DefaultWeight; - Movable = false; - } - - if ( version < 3 ) - ValidationQueue.Add( this ); - } - - private void RecountLiveCreatures() - { - LiveCreatures = 0; - List fish = FindItemsByType(); - - foreach ( BaseFish f in fish ) - { - if ( !f.Dead ) - ++LiveCreatures; - } - } - - public void Validate() - { - RecountLiveCreatures(); - } - - #region Members - public int FoodNumber() - { - if ( m_Food.State == (int) FoodState.Full ) - return 1074240; - - if ( m_Food.State == (int) FoodState.Overfed ) - return 1074239; - - return 1074236 + m_Food.State; - } - - public int WaterNumber() - { - return 1074242 + m_Water.State; - } - #endregion - - #region Virtual members - public virtual void KillFish( int amount ) - { - List toKill = new List(); - - for ( int i = 0; i < Items.Count; i ++ ) - { - if ( Items[ i ] is BaseFish ) - { - BaseFish fish = (BaseFish) Items[ i ]; - - if ( !fish.Dead ) - toKill.Add( fish ); - } - } - - while ( amount > 0 && toKill.Count > 0 ) - { - int kill = Utility.Random( toKill.Count ); - - toKill[ kill ].Kill(); - - toKill.RemoveAt( kill ); - - amount -= 1; - LiveCreatures -= 1; - - if ( LiveCreatures < 0 ) - LiveCreatures = 0; - - Events.Add( 1074366 ); // An unfortunate accident has left a creature floating upside-down. It is starting to smell. - } - } - - public virtual void Evaluate() - { - if ( m_VacationLeft > 0 ) - { - m_VacationLeft -= 1; - } - else if ( m_EvaluateDay ) - { - // reset events - Events = new List(); - - // food events - if ( - ( m_Food.Added < m_Food.Maintain && m_Food.State != (int) FoodState.Overfed && m_Food.State != (int) FoodState.Dead ) || - ( m_Food.Added >= m_Food.Improve && m_Food.State == (int) FoodState.Full ) - ) - Events.Add( 1074368 ); // The tank looks worse than it did yesterday. - - if ( - ( m_Food.Added >= m_Food.Improve && m_Food.State != (int) FoodState.Full && m_Food.State != (int) FoodState.Overfed ) || - ( m_Food.Added < m_Food.Maintain && m_Food.State == (int) FoodState.Overfed ) - ) - Events.Add( 1074367 ); // The tank looks healthier today. - - // water events - if ( m_Water.Added < m_Water.Maintain && m_Water.State != (int) WaterState.Dead ) - Events.Add( 1074370 ); // This tank can use more water. - - if ( m_Water.Added >= m_Water.Improve && m_Water.State != (int) WaterState.Strong ) - Events.Add( 1074369 ); // The water looks clearer today. - - UpdateFoodState(); - UpdateWaterState(); - - // reward - if ( LiveCreatures > 0 ) - m_RewardAvailable = true; - } - else - { - // new fish - if ( OptimalState && LiveCreatures < MaxLiveCreatures ) - { - if ( Utility.RandomDouble() < 0.005 * LiveCreatures ) - { - BaseFish fish = null; - int message = 0; - - switch ( Utility.Random( 6 ) ) - { - case 0: - { - message = 1074371; // Brine shrimp have hatched overnight in the tank. - fish = new BrineShrimp(); - break; - } - case 1: - { - message = 1074365; // A new creature has hatched overnight in the tank. - fish = new Coral(); - break; - } - case 2: - { - message = 1074365; // A new creature has hatched overnight in the tank. - fish = new FullMoonFish(); - break; - } - case 3: - { - message = 1074373; // A sea horse has hatched overnight in the tank. - fish = new SeaHorseFish(); - break; - } - case 4: - { - message = 1074365; // A new creature has hatched overnight in the tank. - fish = new StrippedFlakeFish(); - break; - } - case 5: - { - message = 1074365; // A new creature has hatched overnight in the tank. - fish = new StrippedSosarianSwill(); - break; - } - } - - if ( Utility.RandomDouble() < 0.05 ) - fish.Hue = FishHues[ Utility.Random( FishHues.Length ) ]; - else if ( Utility.RandomDouble() < 0.5 ) - fish.Hue = Utility.RandomMinMax( 0x100, 0x3E5 ); - - if ( AddFish( fish ) ) - Events.Add( message ); - else - fish.Delete(); - } - } - - // kill fish *grins* - if ( LiveCreatures < MaxLiveCreatures ) - { - if ( Utility.RandomDouble() < 0.01 ) - KillFish( 1 ); - } - else - { - KillFish( LiveCreatures - MaxLiveCreatures ); - } - } - - m_EvaluateDay = !m_EvaluateDay; - InvalidateProperties(); - } - - public virtual void GiveReward( Mobile to ) - { - if ( !m_RewardAvailable ) - return; - - int max = (int) ( ( (double) LiveCreatures / 30 ) * m_Decorations.Length ); - - int random = ( max <= 0 ) ? 0 : Utility.Random( max ); - - if ( random >= m_Decorations.Length ) - random = m_Decorations.Length - 1; - - Item item; - - try - { - item = Activator.CreateInstance( m_Decorations[ random ] ) as Item; - } - catch - { - return; - } - - if ( item == null ) - return; - - if ( !to.PlaceInBackpack( item ) ) - { - item.Delete(); - to.SendLocalizedMessage( 1074361 ); // The reward could not be given. Make sure you have room in your pack. - return; - } - - to.SendLocalizedMessage( 1074360, $"#{item.LabelNumber}"); // You receive a reward: ~1_REWARD~ - to.PlaySound( 0x5A3 ); - - m_RewardAvailable = false; - - InvalidateProperties(); - } - - public virtual void UpdateFoodState() - { - if ( m_Food.Added < m_Food.Maintain ) - m_Food.State = ( m_Food.State <= 0 ) ? 0 : m_Food.State - 1; - else if ( m_Food.Added >= m_Food.Improve ) - m_Food.State = ( m_Food.State >= (int) FoodState.Overfed ) ? (int) FoodState.Overfed : m_Food.State + 1; - - m_Food.Maintain = Utility.Random( (int) FoodState.Overfed + 1 - m_Food.State, 2 ); - - if ( m_Food.State == (int) FoodState.Overfed ) - m_Food.Improve = 0; - else - m_Food.Improve = m_Food.Maintain + 2; - - m_Food.Added = 0; - } - - public virtual void UpdateWaterState() - { - if ( m_Water.Added < m_Water.Maintain ) - m_Water.State = ( m_Water.State <= 0 ) ? 0 : m_Water.State - 1; - else if ( m_Water.Added >= m_Water.Improve ) - m_Water.State = ( m_Water.State >= (int) WaterState.Strong ) ? (int) WaterState.Strong : m_Water.State + 1; - - m_Water.Maintain = Utility.Random( (int) WaterState.Strong + 2 - m_Water.State, 2 ); - - if ( m_Water.State == (int) WaterState.Strong ) - m_Water.Improve = 0; - else - m_Water.Improve = m_Water.Maintain + 2; - - m_Water.Added = 0; - } - - public virtual bool RemoveItem( Mobile from, int at ) - { - if ( at < 0 && at >= Items.Count ) - return false; - - Item item = Items[ at ]; - - if ( item.IsLockedDown ) // for legacy aquariums - { - from.SendLocalizedMessage( 1010449 ); // You may not use this object while it is locked down. - return false; - } - - if ( item is BaseFish fish ) - { - FishBowl bowl; - - if ( (bowl = GetEmptyBowl( from )) != null ) - { - bowl.AddItem( fish ); - - from.SendLocalizedMessage( 1074511 ); // You put the creature into a fish bowl. - } - else - { - if ( !from.PlaceInBackpack( fish ) ) - { - from.SendLocalizedMessage( 1074514 ); // You have no place to put it. - return false; - } - - from.SendLocalizedMessage( 1074512 ); // You put the gasping creature into your pack. - } - - if ( !fish.Dead ) - LiveCreatures -= 1; - } - else - { - if ( !from.PlaceInBackpack( item ) ) - { - from.SendLocalizedMessage( 1074514 ); // You have no place to put it. - return false; - } - - from.SendLocalizedMessage( 1074513 ); // You put the item into your pack. - } - - InvalidateProperties(); - return true; - } - - public virtual void ExamineAquarium( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - from.CloseGump( typeof( AquariumGump ) ); - from.SendGump( new AquariumGump( this, HasAccess( from ) ) ); - - from.PlaySound( 0x5A4 ); - } - - public virtual bool AddFish( BaseFish fish ) - { - return AddFish( null, fish ); - } - - public virtual bool AddFish( Mobile from, BaseFish fish ) - { - if ( fish == null ) - return false; - - if ( IsFull || LiveCreatures >= MaxLiveCreatures || fish.Dead ) - { - from?.SendLocalizedMessage( 1073633 ); // The aquarium can not hold the creature. - - return false; - } - - AddItem( fish ); - fish.StopTimer(); - - LiveCreatures += 1; - - from?.SendLocalizedMessage( 1073632, $"#{fish.LabelNumber}"); // You add the following creature to your aquarium: ~1_FISH~ - - InvalidateProperties(); - return true; - } - - public virtual bool AddDecoration( Item item ) - { - return AddDecoration( null, item ); - } - - public virtual bool AddDecoration( Mobile from, Item item ) - { - if ( item == null ) - return false; - - if ( IsFull ) - { - from?.SendLocalizedMessage( 1073636 ); // The decoration will not fit in the aquarium. - - return false; - } - - if ( !Accepts( item ) ) - { - from?.SendLocalizedMessage( 1073822 ); // The aquarium can not hold that item. - - return false; - } - - AddItem( item ); - - from?.SendLocalizedMessage( 1073635, ( item.LabelNumber != 0 ) ? $"#{item.LabelNumber}" : item.Name ); // You add the following decoration to your aquarium: ~1_NAME~ - - InvalidateProperties(); - return true; - } - #endregion - - #region Static members - public static FishBowl GetEmptyBowl( Mobile from ) - { - if ( from?.Backpack == null ) - return null; - - Item[] items = from.Backpack.FindItemsByType( typeof( FishBowl ) ); - - for ( int i = 0; i < items.Length; i ++ ) - { - if ( items[ i ] is FishBowl ) - { - FishBowl bowl = (FishBowl) items[ i ]; - - if ( bowl.Empty ) - return bowl; - } - } - - return null; - } - - private static Type[] m_Decorations = { - typeof( FishBones ), - typeof( WaterloggedBoots ), - typeof( CaptainBlackheartsFishingPole ), - typeof( CraftysFishingHat ), - typeof( AquariumFishNet ), - typeof( AquariumMessage ), - typeof( IslandStatue ), - typeof( Shell ), - typeof( ToyBoat ) - }; - - public static bool Accepts( Item item ) - { - if ( item == null ) - return false; - - Type type = item.GetType(); - - for ( int i = 0; i < m_Decorations.Length; i ++ ) - { - if ( type == m_Decorations[ i ] ) - return true; - } - - return false; - } - - public static int[] FishHues { get; } = - { - 0x1C2, 0x1C3, 0x2A3, 0x47E, 0x51D - }; - - #endregion - - #region Context entries - private class ExamineEntry : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public ExamineEntry( Aquarium aquarium ) : base( 6235, 2 ) // Examine Aquarium - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted ) - return; - - m_Aquarium.ExamineAquarium( Owner.From ); - } - } - - private class CollectRewardEntry : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public CollectRewardEntry( Aquarium aquarium ) : base( 6237, 2 ) // Collect Reward - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted || !m_Aquarium.HasAccess( Owner.From ) ) - return; - - m_Aquarium.GiveReward( Owner.From ); - } - } - - private class ViewEventEntry : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public ViewEventEntry( Aquarium aquarium ) : base( 6239, 2 ) // View events - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted || !m_Aquarium.HasAccess( Owner.From ) || m_Aquarium.Events.Count == 0 ) - return; - - Owner.From.SendLocalizedMessage( m_Aquarium.Events[ 0 ] ); - - if ( m_Aquarium.Events[ 0 ] == 1074366 ) - Owner.From.PlaySound( 0x5A2 ); - - m_Aquarium.Events.RemoveAt( 0 ); - m_Aquarium.InvalidateProperties(); - } - } - - private class CancelVacationMode : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public CancelVacationMode( Aquarium aquarium ) : base( 6240, 2 ) // Cancel vacation mode - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted || !m_Aquarium.HasAccess( Owner.From ) ) - return; - - Owner.From.SendLocalizedMessage( 1074429 ); // Vacation mode has been cancelled. - m_Aquarium.VacationLeft = 0; - m_Aquarium.InvalidateProperties(); - } - } - - // GM context entries - private class GMAddFood : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public GMAddFood( Aquarium aquarium ) : base( 6231, -1 ) // GM Add Food - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted ) - return; - - m_Aquarium.Food.Added += 1; - m_Aquarium.InvalidateProperties(); - } - } - - private class GMAddWater : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public GMAddWater( Aquarium aquarium ) : base( 6232, -1 ) // GM Add Water - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted ) - return; - - m_Aquarium.Water.Added += 1; - m_Aquarium.InvalidateProperties(); - } - } - - private class GMForceEvaluate : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public GMForceEvaluate( Aquarium aquarium ) : base( 6233, -1 ) // GM Force Evaluate - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted ) - return; - - m_Aquarium.Evaluate(); - } - } - - private class GMOpen : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public GMOpen( Aquarium aquarium ) : base( 6234, -1 ) // GM Open Container - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted ) - return; - - Owner.From.SendGump( new AquariumGump( m_Aquarium, true ) ); - } - } - - private class GMFill : ContextMenuEntry - { - private Aquarium m_Aquarium; - - public GMFill( Aquarium aquarium ) : base( 6236, -1 ) // GM Fill Food and Water - { - m_Aquarium = aquarium; - } - - public override void OnClick() - { - if ( m_Aquarium.Deleted ) - return; - - m_Aquarium.Food.Added = m_Aquarium.Food.Maintain; - m_Aquarium.Water.Added = m_Aquarium.Water.Maintain; - m_Aquarium.InvalidateProperties(); - } - } - #endregion - } - - public class AquariumEastDeed : BaseAddonContainerDeed - { - public override BaseAddonContainer Addon => new Aquarium( 0x3062 ); - public override int LabelNumber => 1074501; // Large Aquarium (east) - - [Constructible] - public AquariumEastDeed() - { - } - - public AquariumEastDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( 0 ); // Version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AquariumNorthDeed : BaseAddonContainerDeed - { - public override BaseAddonContainer Addon => new Aquarium( 0x3060 ); - public override int LabelNumber => 1074497; // Large Aquarium (north) - - [Constructible] - public AquariumNorthDeed() - { - } - - public AquariumNorthDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( 0 ); // Version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + + switch (version) + { + case 3: + case 2: + case 1: + { + DateTime next = reader.ReadDateTime(); + + if (next < DateTime.UtcNow) + next = DateTime.UtcNow; + + m_Timer = Timer.DelayCall(next - DateTime.UtcNow, EvaluationInterval, Evaluate); + + goto case 0; + } + case 0: + { + LiveCreatures = reader.ReadInt(); + m_VacationLeft = reader.ReadInt(); + + m_Food = new AquariumState(); + m_Water = new AquariumState(); + + m_Food.Deserialize(reader); + m_Water.Deserialize(reader); + + Events = new List(); + + int count = reader.ReadInt(); + + for (int i = 0; i < count; i++) + Events.Add(reader.ReadInt()); + + m_RewardAvailable = reader.ReadBool(); + + break; + } + } + + if (version < 2) + { + Weight = DefaultWeight; + Movable = false; + } + + if (version < 3) + ValidationQueue.Add(this); + } + + private void RecountLiveCreatures() + { + LiveCreatures = 0; + List fish = FindItemsByType(); + + foreach (BaseFish f in fish) + if (!f.Dead) + ++LiveCreatures; + } + + public void Validate() + { + RecountLiveCreatures(); + } + + #region Members + + public int FoodNumber() + { + if (m_Food.State == (int)FoodState.Full) + return 1074240; + + if (m_Food.State == (int)FoodState.Overfed) + return 1074239; + + return 1074236 + m_Food.State; + } + + public int WaterNumber() + { + return 1074242 + m_Water.State; + } + + #endregion + + #region Virtual members + + public virtual void KillFish(int amount) + { + List toKill = new List(); + + for (int i = 0; i < Items.Count; i++) + if (Items[i] is BaseFish) + { + BaseFish fish = (BaseFish)Items[i]; + + if (!fish.Dead) + toKill.Add(fish); + } + + while (amount > 0 && toKill.Count > 0) + { + int kill = Utility.Random(toKill.Count); + + toKill[kill].Kill(); + + toKill.RemoveAt(kill); + + amount -= 1; + LiveCreatures -= 1; + + if (LiveCreatures < 0) + LiveCreatures = 0; + + Events.Add(1074366); // An unfortunate accident has left a creature floating upside-down. It is starting to smell. + } + } + + public virtual void Evaluate() + { + if (m_VacationLeft > 0) + { + m_VacationLeft -= 1; + } + else if (m_EvaluateDay) + { + // reset events + Events = new List(); + + // food events + if ( + m_Food.Added < m_Food.Maintain && m_Food.State != (int)FoodState.Overfed && + m_Food.State != (int)FoodState.Dead || + m_Food.Added >= m_Food.Improve && m_Food.State == (int)FoodState.Full + ) + Events.Add(1074368); // The tank looks worse than it did yesterday. + + if ( + m_Food.Added >= m_Food.Improve && m_Food.State != (int)FoodState.Full && + m_Food.State != (int)FoodState.Overfed || + m_Food.Added < m_Food.Maintain && m_Food.State == (int)FoodState.Overfed + ) + Events.Add(1074367); // The tank looks healthier today. + + // water events + if (m_Water.Added < m_Water.Maintain && m_Water.State != (int)WaterState.Dead) + Events.Add(1074370); // This tank can use more water. + + if (m_Water.Added >= m_Water.Improve && m_Water.State != (int)WaterState.Strong) + Events.Add(1074369); // The water looks clearer today. + + UpdateFoodState(); + UpdateWaterState(); + + // reward + if (LiveCreatures > 0) + m_RewardAvailable = true; + } + else + { + // new fish + if (OptimalState && LiveCreatures < MaxLiveCreatures) + if (Utility.RandomDouble() < 0.005 * LiveCreatures) + { + BaseFish fish = null; + int message = 0; + + switch (Utility.Random(6)) + { + case 0: + { + message = 1074371; // Brine shrimp have hatched overnight in the tank. + fish = new BrineShrimp(); + break; + } + case 1: + { + message = 1074365; // A new creature has hatched overnight in the tank. + fish = new Coral(); + break; + } + case 2: + { + message = 1074365; // A new creature has hatched overnight in the tank. + fish = new FullMoonFish(); + break; + } + case 3: + { + message = 1074373; // A sea horse has hatched overnight in the tank. + fish = new SeaHorseFish(); + break; + } + case 4: + { + message = 1074365; // A new creature has hatched overnight in the tank. + fish = new StrippedFlakeFish(); + break; + } + case 5: + { + message = 1074365; // A new creature has hatched overnight in the tank. + fish = new StrippedSosarianSwill(); + break; + } + } + + if (Utility.RandomDouble() < 0.05) + fish.Hue = FishHues[Utility.Random(FishHues.Length)]; + else if (Utility.RandomDouble() < 0.5) + fish.Hue = Utility.RandomMinMax(0x100, 0x3E5); + + if (AddFish(fish)) + Events.Add(message); + else + fish.Delete(); + } + + // kill fish *grins* + if (LiveCreatures < MaxLiveCreatures) + { + if (Utility.RandomDouble() < 0.01) + KillFish(1); + } + else + { + KillFish(LiveCreatures - MaxLiveCreatures); + } + } + + m_EvaluateDay = !m_EvaluateDay; + InvalidateProperties(); + } + + public virtual void GiveReward(Mobile to) + { + if (!m_RewardAvailable) + return; + + int max = (int)((double)LiveCreatures / 30 * m_Decorations.Length); + + int random = max <= 0 ? 0 : Utility.Random(max); + + if (random >= m_Decorations.Length) + random = m_Decorations.Length - 1; + + Item item; + + try + { + item = Activator.CreateInstance(m_Decorations[random]) as Item; + } + catch + { + return; + } + + if (item == null) + return; + + if (!to.PlaceInBackpack(item)) + { + item.Delete(); + to.SendLocalizedMessage(1074361); // The reward could not be given. Make sure you have room in your pack. + return; + } + + to.SendLocalizedMessage(1074360, $"#{item.LabelNumber}"); // You receive a reward: ~1_REWARD~ + to.PlaySound(0x5A3); + + m_RewardAvailable = false; + + InvalidateProperties(); + } + + public virtual void UpdateFoodState() + { + if (m_Food.Added < m_Food.Maintain) + m_Food.State = m_Food.State <= 0 ? 0 : m_Food.State - 1; + else if (m_Food.Added >= m_Food.Improve) + m_Food.State = m_Food.State >= (int)FoodState.Overfed ? (int)FoodState.Overfed : m_Food.State + 1; + + m_Food.Maintain = Utility.Random((int)FoodState.Overfed + 1 - m_Food.State, 2); + + if (m_Food.State == (int)FoodState.Overfed) + m_Food.Improve = 0; + else + m_Food.Improve = m_Food.Maintain + 2; + + m_Food.Added = 0; + } + + public virtual void UpdateWaterState() + { + if (m_Water.Added < m_Water.Maintain) + m_Water.State = m_Water.State <= 0 ? 0 : m_Water.State - 1; + else if (m_Water.Added >= m_Water.Improve) + m_Water.State = m_Water.State >= (int)WaterState.Strong ? (int)WaterState.Strong : m_Water.State + 1; + + m_Water.Maintain = Utility.Random((int)WaterState.Strong + 2 - m_Water.State, 2); + + if (m_Water.State == (int)WaterState.Strong) + m_Water.Improve = 0; + else + m_Water.Improve = m_Water.Maintain + 2; + + m_Water.Added = 0; + } + + public virtual bool RemoveItem(Mobile from, int at) + { + if (at < 0 && at >= Items.Count) + return false; + + Item item = Items[at]; + + if (item.IsLockedDown) // for legacy aquariums + { + from.SendLocalizedMessage(1010449); // You may not use this object while it is locked down. + return false; + } + + if (item is BaseFish fish) + { + FishBowl bowl; + + if ((bowl = GetEmptyBowl(from)) != null) + { + bowl.AddItem(fish); + + from.SendLocalizedMessage(1074511); // You put the creature into a fish bowl. + } + else + { + if (!from.PlaceInBackpack(fish)) + { + from.SendLocalizedMessage(1074514); // You have no place to put it. + return false; + } + + from.SendLocalizedMessage(1074512); // You put the gasping creature into your pack. + } + + if (!fish.Dead) + LiveCreatures -= 1; + } + else + { + if (!from.PlaceInBackpack(item)) + { + from.SendLocalizedMessage(1074514); // You have no place to put it. + return false; + } + + from.SendLocalizedMessage(1074513); // You put the item into your pack. + } + + InvalidateProperties(); + return true; + } + + public virtual void ExamineAquarium(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + from.CloseGump(typeof(AquariumGump)); + from.SendGump(new AquariumGump(this, HasAccess(from))); + + from.PlaySound(0x5A4); + } + + public virtual bool AddFish(BaseFish fish) + { + return AddFish(null, fish); + } + + public virtual bool AddFish(Mobile from, BaseFish fish) + { + if (fish == null) + return false; + + if (IsFull || LiveCreatures >= MaxLiveCreatures || fish.Dead) + { + from?.SendLocalizedMessage(1073633); // The aquarium can not hold the creature. + + return false; + } + + AddItem(fish); + fish.StopTimer(); + + LiveCreatures += 1; + + from?.SendLocalizedMessage(1073632, + $"#{fish.LabelNumber}"); // You add the following creature to your aquarium: ~1_FISH~ + + InvalidateProperties(); + return true; + } + + public virtual bool AddDecoration(Item item) + { + return AddDecoration(null, item); + } + + public virtual bool AddDecoration(Mobile from, Item item) + { + if (item == null) + return false; + + if (IsFull) + { + from?.SendLocalizedMessage(1073636); // The decoration will not fit in the aquarium. + + return false; + } + + if (!Accepts(item)) + { + from?.SendLocalizedMessage(1073822); // The aquarium can not hold that item. + + return false; + } + + AddItem(item); + + from?.SendLocalizedMessage(1073635, + item.LabelNumber != 0 + ? $"#{item.LabelNumber}" + : item.Name); // You add the following decoration to your aquarium: ~1_NAME~ + + InvalidateProperties(); + return true; + } + + #endregion + + #region Static members + + public static FishBowl GetEmptyBowl(Mobile from) + { + if (from?.Backpack == null) + return null; + + Item[] items = from.Backpack.FindItemsByType(typeof(FishBowl)); + + for (int i = 0; i < items.Length; i++) + if (items[i] is FishBowl) + { + FishBowl bowl = (FishBowl)items[i]; + + if (bowl.Empty) + return bowl; + } + + return null; + } + + private static Type[] m_Decorations = + { + typeof(FishBones), + typeof(WaterloggedBoots), + typeof(CaptainBlackheartsFishingPole), + typeof(CraftysFishingHat), + typeof(AquariumFishNet), + typeof(AquariumMessage), + typeof(IslandStatue), + typeof(Shell), + typeof(ToyBoat) + }; + + public static bool Accepts(Item item) + { + if (item == null) + return false; + + Type type = item.GetType(); + + for (int i = 0; i < m_Decorations.Length; i++) + if (type == m_Decorations[i]) + return true; + + return false; + } + + public static int[] FishHues{ get; } = + { + 0x1C2, 0x1C3, 0x2A3, 0x47E, 0x51D + }; + + #endregion + + #region Context entries + + private class ExamineEntry : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public ExamineEntry(Aquarium aquarium) : base(6235, 2) // Examine Aquarium + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted) + return; + + m_Aquarium.ExamineAquarium(Owner.From); + } + } + + private class CollectRewardEntry : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public CollectRewardEntry(Aquarium aquarium) : base(6237, 2) // Collect Reward + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted || !m_Aquarium.HasAccess(Owner.From)) + return; + + m_Aquarium.GiveReward(Owner.From); + } + } + + private class ViewEventEntry : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public ViewEventEntry(Aquarium aquarium) : base(6239, 2) // View events + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted || !m_Aquarium.HasAccess(Owner.From) || m_Aquarium.Events.Count == 0) + return; + + Owner.From.SendLocalizedMessage(m_Aquarium.Events[0]); + + if (m_Aquarium.Events[0] == 1074366) + Owner.From.PlaySound(0x5A2); + + m_Aquarium.Events.RemoveAt(0); + m_Aquarium.InvalidateProperties(); + } + } + + private class CancelVacationMode : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public CancelVacationMode(Aquarium aquarium) : base(6240, 2) // Cancel vacation mode + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted || !m_Aquarium.HasAccess(Owner.From)) + return; + + Owner.From.SendLocalizedMessage(1074429); // Vacation mode has been cancelled. + m_Aquarium.VacationLeft = 0; + m_Aquarium.InvalidateProperties(); + } + } + + // GM context entries + private class GMAddFood : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public GMAddFood(Aquarium aquarium) : base(6231, -1) // GM Add Food + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted) + return; + + m_Aquarium.Food.Added += 1; + m_Aquarium.InvalidateProperties(); + } + } + + private class GMAddWater : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public GMAddWater(Aquarium aquarium) : base(6232, -1) // GM Add Water + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted) + return; + + m_Aquarium.Water.Added += 1; + m_Aquarium.InvalidateProperties(); + } + } + + private class GMForceEvaluate : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public GMForceEvaluate(Aquarium aquarium) : base(6233, -1) // GM Force Evaluate + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted) + return; + + m_Aquarium.Evaluate(); + } + } + + private class GMOpen : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public GMOpen(Aquarium aquarium) : base(6234, -1) // GM Open Container + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted) + return; + + Owner.From.SendGump(new AquariumGump(m_Aquarium, true)); + } + } + + private class GMFill : ContextMenuEntry + { + private Aquarium m_Aquarium; + + public GMFill(Aquarium aquarium) : base(6236, -1) // GM Fill Food and Water + { + m_Aquarium = aquarium; + } + + public override void OnClick() + { + if (m_Aquarium.Deleted) + return; + + m_Aquarium.Food.Added = m_Aquarium.Food.Maintain; + m_Aquarium.Water.Added = m_Aquarium.Water.Maintain; + m_Aquarium.InvalidateProperties(); + } + } + + #endregion + } + + public class AquariumEastDeed : BaseAddonContainerDeed + { + [Constructible] + public AquariumEastDeed() + { + } + + public AquariumEastDeed(Serial serial) : base(serial) + { + } + + public override BaseAddonContainer Addon => new Aquarium(0x3062); + public override int LabelNumber => 1074501; // Large Aquarium (east) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // Version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AquariumNorthDeed : BaseAddonContainerDeed + { + [Constructible] + public AquariumNorthDeed() + { + } + + public AquariumNorthDeed(Serial serial) : base(serial) + { + } + + public override BaseAddonContainer Addon => new Aquarium(0x3060); + public override int LabelNumber => 1074497; // Large Aquarium (north) + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // Version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/AquariumFishingNet.cs b/Scripts/Items/Aquarium/AquariumFishingNet.cs index 99f0ecc92..c617d1507 100644 --- a/Scripts/Items/Aquarium/AquariumFishingNet.cs +++ b/Scripts/Items/Aquarium/AquariumFishingNet.cs @@ -1,189 +1,190 @@ namespace Server.Items { - public class AquariumFishNet : SpecialFishingNet - { - public override int LabelNumber => 1074463; // An aquarium fishing net + public class AquariumFishNet : SpecialFishingNet + { + [Constructible] + public AquariumFishNet() + { + ItemID = 0xDC8; - [Constructible] - public AquariumFishNet() - { - ItemID = 0xDC8; + if (Hue == 0x8A0) + Hue = 0x240; + } - if ( Hue == 0x8A0 ) - Hue = 0x240; - } + public AquariumFishNet(Serial serial) : base(serial) + { + } - protected override void AddNetProperties( ObjectPropertyList list ) - { - } + public override int LabelNumber => 1074463; // An aquarium fishing net - public override bool RequireDeepWater => false; + public override bool RequireDeepWater => false; - protected override void FinishEffect( Point3D p, Map map, Mobile from ) - { - if ( from.Skills.Fishing.Value < 10 ) - { - from.SendLocalizedMessage( 1074487 ); // The creatures are too quick for you! - } - else - { - BaseFish fish = GiveFish( from ); - FishBowl bowl = Aquarium.GetEmptyBowl( from ); + protected override void AddNetProperties(ObjectPropertyList list) + { + } - if ( bowl != null ) - { - fish.StopTimer(); - bowl.AddItem( fish ); - from.SendLocalizedMessage( 1074489 ); // A live creature jumps into the fish bowl in your pack! - Delete(); - return; - } + protected override void FinishEffect(Point3D p, Map map, Mobile from) + { + if (from.Skills.Fishing.Value < 10) + { + from.SendLocalizedMessage(1074487); // The creatures are too quick for you! + } + else + { + BaseFish fish = GiveFish(from); + FishBowl bowl = Aquarium.GetEmptyBowl(from); - if ( from.PlaceInBackpack( fish ) ) - { - from.PlaySound( 0x5A2 ); - from.SendLocalizedMessage( 1074490 ); // A live creature flops around in your pack before running out of air. + if (bowl != null) + { + fish.StopTimer(); + bowl.AddItem(fish); + from.SendLocalizedMessage(1074489); // A live creature jumps into the fish bowl in your pack! + Delete(); + return; + } - fish.Kill(); - Delete(); - return; - } + if (from.PlaceInBackpack(fish)) + { + from.PlaySound(0x5A2); + from.SendLocalizedMessage( + 1074490); // A live creature flops around in your pack before running out of air. - fish.Delete(); + fish.Kill(); + Delete(); + return; + } - from.SendLocalizedMessage( 1074488 ); // You could not hold the creature. - } + fish.Delete(); - InUse = false; - Movable = true; + from.SendLocalizedMessage(1074488); // You could not hold the creature. + } - if ( !from.PlaceInBackpack( this ) ) - { - if ( from.Map == null || from.Map == Map.Internal ) - Delete(); - else - MoveToWorld( from.Location, from.Map ); - } - } + InUse = false; + Movable = true; - private BaseFish GiveFish( Mobile from ) - { - double skill = from.Skills.Fishing.Value; + if (!from.PlaceInBackpack(this)) + { + if (from.Map == null || from.Map == Map.Internal) + Delete(); + else + MoveToWorld(from.Location, from.Map); + } + } - if ( ( skill / 100.0 ) >= Utility.RandomDouble() ) - { - int max = (int) skill / 5; + private BaseFish GiveFish(Mobile from) + { + double skill = from.Skills.Fishing.Value; - if ( max > 20 ) - max = 20; + if (skill / 100.0 >= Utility.RandomDouble()) + { + int max = (int)skill / 5; - switch ( Utility.Random( max ) ) - { - case 0: return new MinocBlueFish(); - case 1: return new Shrimp(); - case 2: return new FandancerFish(); - case 3: return new GoldenBroadtail(); - case 4: return new RedDartFish(); - case 5: return new AlbinoCourtesanFish(); - case 6: return new MakotoCourtesanFish(); - case 7: return new NujelmHoneyFish(); - case 8: return new Jellyfish(); - case 9: return new SpeckledCrab(); - case 10: return new LongClawCrab(); - case 11: return new AlbinoFrog(); - case 12: return new KillerFrog(); - case 13: return new VesperReefTiger(); - case 14: return new PurpleFrog(); - case 15: return new BritainCrownFish(); - case 16: return new YellowFinBluebelly(); - case 17: return new SpottedBuccaneer(); - case 18: return new SpinedScratcherFish(); - default: return new SmallMouthSuckerFin(); - } - } + if (max > 20) + max = 20; - return new MinocBlueFish(); - } + switch (Utility.Random(max)) + { + case 0: return new MinocBlueFish(); + case 1: return new Shrimp(); + case 2: return new FandancerFish(); + case 3: return new GoldenBroadtail(); + case 4: return new RedDartFish(); + case 5: return new AlbinoCourtesanFish(); + case 6: return new MakotoCourtesanFish(); + case 7: return new NujelmHoneyFish(); + case 8: return new Jellyfish(); + case 9: return new SpeckledCrab(); + case 10: return new LongClawCrab(); + case 11: return new AlbinoFrog(); + case 12: return new KillerFrog(); + case 13: return new VesperReefTiger(); + case 14: return new PurpleFrog(); + case 15: return new BritainCrownFish(); + case 16: return new YellowFinBluebelly(); + case 17: return new SpottedBuccaneer(); + case 18: return new SpinedScratcherFish(); + default: return new SmallMouthSuckerFin(); + } + } - public AquariumFishNet( Serial serial ) : base( serial ) - { - } + return new MinocBlueFish(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - // Legacy code - public class AquariumFishingNet : Item - { - public override int LabelNumber => 1074463; // An aquarium fishing net + // Legacy code + public class AquariumFishingNet : Item + { + public AquariumFishingNet() + { + } - public AquariumFishingNet() - { - } + public AquariumFishingNet(Serial serial) : base(serial) + { + } - public AquariumFishingNet( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074463; // An aquarium fishing net - private Item CreateReplacement() - { - Item result = new AquariumFishNet(); - result.Hue = Hue; - result.LootType = LootType; - result.Movable = Movable; - result.Name = Name; - result.QuestItem = QuestItem; - result.Visible = Visible; + private Item CreateReplacement() + { + Item result = new AquariumFishNet(); + result.Hue = Hue; + result.LootType = LootType; + result.Movable = Movable; + result.Name = Name; + result.QuestItem = QuestItem; + result.Visible = Visible; - return result; - } + return result; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - Item replacement = CreateReplacement(); + Item replacement = CreateReplacement(); - if ( !from.PlaceInBackpack( replacement ) ) - { - replacement.Delete(); - from.SendLocalizedMessage( 500720 ); // You don't have enough room in your backpack! - } - else - { - Delete(); - from.Use( replacement ); - } - } + if (!from.PlaceInBackpack(replacement)) + { + replacement.Delete(); + from.SendLocalizedMessage(500720); // You don't have enough room in your backpack! + } + else + { + Delete(); + from.Use(replacement); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/AquariumFood.cs b/Scripts/Items/Aquarium/AquariumFood.cs index 1e0321852..21dcf359e 100644 --- a/Scripts/Items/Aquarium/AquariumFood.cs +++ b/Scripts/Items/Aquarium/AquariumFood.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class AquariumFood : Item - { - public override int LabelNumber => 1074819; // Aquarium food + public class AquariumFood : Item + { + [Constructible] + public AquariumFood() : base(0xEFC) + { + } - [Constructible] - public AquariumFood() : base( 0xEFC ) - { - } + public AquariumFood(Serial serial) : base(serial) + { + } - public AquariumFood( Serial serial ) : base( serial ) - { + public override int LabelNumber => 1074819; // Aquarium food - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/AquariumGump.cs b/Scripts/Items/Aquarium/AquariumGump.cs index dc23a62ba..acb3a91e1 100644 --- a/Scripts/Items/Aquarium/AquariumGump.cs +++ b/Scripts/Items/Aquarium/AquariumGump.cs @@ -1,90 +1,89 @@ -using System; using Server.Gumps; using Server.Network; namespace Server.Items { - public class AquariumGump : Gump - { - private Aquarium m_Aquarium; + public class AquariumGump : Gump + { + private Aquarium m_Aquarium; - public AquariumGump( Aquarium aquarium, bool edit ) : base( 100, 100 ) - { - m_Aquarium = aquarium; + public AquariumGump(Aquarium aquarium, bool edit) : base(100, 100) + { + m_Aquarium = aquarium; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); - AddBackground( 0, 0, 350, 323, 0xE10 ); - AddImage( 0, 0, 0x2C96 ); + AddPage(0); + AddBackground(0, 0, 350, 323, 0xE10); + AddImage(0, 0, 0x2C96); - if ( m_Aquarium.Items.Count == 0 ) - return; + if (m_Aquarium.Items.Count == 0) + return; - for ( int i = 1; i <= m_Aquarium.Items.Count; i ++ ) - DisplayPage( i, edit ); - } + for (int i = 1; i <= m_Aquarium.Items.Count; i++) + DisplayPage(i, edit); + } - public void DisplayPage( int page, bool edit ) - { - AddPage( page ); + public void DisplayPage(int page, bool edit) + { + AddPage(page); - Item item = m_Aquarium.Items[ page - 1 ]; + Item item = m_Aquarium.Items[page - 1]; - // item name - if ( item.LabelNumber != 0 ) - AddHtmlLocalized( 20, 217, 250, 20, item.LabelNumber, 0xFFFFFF, false, false ); // Name + // item name + if (item.LabelNumber != 0) + AddHtmlLocalized(20, 217, 250, 20, item.LabelNumber, 0xFFFFFF, false, false); // Name - // item details - if ( item is BaseFish fish ) - AddHtmlLocalized( 20, 239, 315, 20, fish.GetDescription(), 0xFFFFFF, false, false ); - else - AddHtmlLocalized( 20, 239, 315, 20, 1073634, 0xFFFFFF, false, false ); // An aquarium decoration + // item details + if (item is BaseFish fish) + AddHtmlLocalized(20, 239, 315, 20, fish.GetDescription(), 0xFFFFFF, false, false); + else + AddHtmlLocalized(20, 239, 315, 20, 1073634, 0xFFFFFF, false, false); // An aquarium decoration - // item image - AddItem( 150, 80, item.ItemID, item.Hue ); + // item image + AddItem(150, 80, item.ItemID, item.Hue); - // item number / all items - AddHtml( 20, 195, 250, 20, $"{page}/{m_Aquarium.Items.Count}", false, false ); + // item number / all items + AddHtml(20, 195, 250, 20, $"{page}/{m_Aquarium.Items.Count}", false, false); - // remove item - if ( edit ) - { - AddBackground( 230, 195, 100, 26, 0x13BE ); - AddButton( 235, 200, 0x845, 0x846, page, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 260, 198, 60, 26, 1073838, 0x0, false, false ); // Remove - } + // remove item + if (edit) + { + AddBackground(230, 195, 100, 26, 0x13BE); + AddButton(235, 200, 0x845, 0x846, page, GumpButtonType.Reply, 0); + AddHtmlLocalized(260, 198, 60, 26, 1073838, 0x0, false, false); // Remove + } - // next page - if ( page < m_Aquarium.Items.Count ) - { - AddButton( 195, 280, 0xFA5, 0xFA7, 0, GumpButtonType.Page, page + 1 ); - AddHtmlLocalized( 230, 283, 100, 18, 1044045, 0xFFFFFF, false, false ); // NEXT PAGE - } + // next page + if (page < m_Aquarium.Items.Count) + { + AddButton(195, 280, 0xFA5, 0xFA7, 0, GumpButtonType.Page, page + 1); + AddHtmlLocalized(230, 283, 100, 18, 1044045, 0xFFFFFF, false, false); // NEXT PAGE + } - // previous page - if ( page > 1 ) - { - AddButton( 45, 280, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page - 1 ); - AddHtmlLocalized( 80, 283, 100, 18, 1044044, 0xFFFFFF, false, false ); // PREV PAGE - } - } + // previous page + if (page > 1) + { + AddButton(45, 280, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page - 1); + AddHtmlLocalized(80, 283, 100, 18, 1044044, 0xFFFFFF, false, false); // PREV PAGE + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Aquarium == null || m_Aquarium.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Aquarium == null || m_Aquarium.Deleted) + return; - bool edit = m_Aquarium.HasAccess( sender.Mobile ); + bool edit = m_Aquarium.HasAccess(sender.Mobile); - if ( info.ButtonID > 0 && info.ButtonID <= m_Aquarium.Items.Count && edit ) - m_Aquarium.RemoveItem( sender.Mobile, info.ButtonID - 1 ); + if (info.ButtonID > 0 && info.ButtonID <= m_Aquarium.Items.Count && edit) + m_Aquarium.RemoveItem(sender.Mobile, info.ButtonID - 1); - if ( info.ButtonID > 0 ) - sender.Mobile.SendGump( new AquariumGump( m_Aquarium, edit ) ); - } - } -} + if (info.ButtonID > 0) + sender.Mobile.SendGump(new AquariumGump(m_Aquarium, edit)); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/AquariumState.cs b/Scripts/Items/Aquarium/AquariumState.cs index 990de2421..52ff6ad82 100644 --- a/Scripts/Items/Aquarium/AquariumState.cs +++ b/Scripts/Items/Aquarium/AquariumState.cs @@ -1,80 +1,76 @@ namespace Server.Items { - public enum WaterState - { - Dead, - Dying, - Unhealthy, - Healthy, - Strong - } + public enum WaterState + { + Dead, + Dying, + Unhealthy, + Healthy, + Strong + } - public enum FoodState - { - Dead, - Starving, - Hungry, - Full, - Overfed - } + public enum FoodState + { + Dead, + Starving, + Hungry, + Full, + Overfed + } - [PropertyObject] - public class AquariumState - { - private int m_State; + [PropertyObject] + public class AquariumState + { + private int m_State; - [CommandProperty( AccessLevel.GameMaster )] - public int State - { - get => m_State; - set - { - m_State = value; + [CommandProperty(AccessLevel.GameMaster)] + public int State + { + get => m_State; + set + { + m_State = value; - if ( m_State < 0 ) - m_State = 0; + if (m_State < 0) + m_State = 0; - if ( m_State > 4 ) - m_State = 4; - } - } + if (m_State > 4) + m_State = 4; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public int Maintain { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int Maintain{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int Improve { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int Improve{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int Added { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int Added{ get; set; } - public AquariumState() - { - } + public override string ToString() + { + return "..."; + } - public override string ToString() - { - return "..."; - } + public virtual void Serialize(GenericWriter writer) + { + writer.Write(0); // version - public virtual void Serialize( GenericWriter writer ) - { - writer.Write( 0 ); // version + writer.Write(m_State); + writer.Write(Maintain); + writer.Write(Improve); + writer.Write(Added); + } - writer.Write( m_State ); - writer.Write( Maintain ); - writer.Write( Improve ); - writer.Write( Added ); - } + public virtual void Deserialize(GenericReader reader) + { + int version = reader.ReadInt(); - public virtual void Deserialize( GenericReader reader ) - { - int version = reader.ReadInt(); - - m_State = reader.ReadInt(); - Maintain = reader.ReadInt(); - Improve = reader.ReadInt(); - Added = reader.ReadInt(); - } - } -} + m_State = reader.ReadInt(); + Maintain = reader.ReadInt(); + Improve = reader.ReadInt(); + Added = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/BaseFish.cs b/Scripts/Items/Aquarium/BaseFish.cs index b6c220a36..b1f4479cb 100644 --- a/Scripts/Items/Aquarium/BaseFish.cs +++ b/Scripts/Items/Aquarium/BaseFish.cs @@ -2,92 +2,92 @@ using System; namespace Server.Items { - public class BaseFish : Item - { - private static readonly TimeSpan DeathDelay = TimeSpan.FromMinutes( 5 ); + public class BaseFish : Item + { + private static readonly TimeSpan DeathDelay = TimeSpan.FromMinutes(5); - private Timer m_Timer; + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public bool Dead => ( ItemID == 0x3B0C ); + [Constructible] + public BaseFish(int itemID) : base(itemID) + { + StartTimer(); + } - [Constructible] - public BaseFish( int itemID ) : base( itemID ) - { - StartTimer(); - } + public BaseFish(Serial serial) : base(serial) + { + } - public BaseFish( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Dead => ItemID == 0x3B0C; - public virtual void StartTimer() - { - m_Timer?.Stop(); + public virtual void StartTimer() + { + m_Timer?.Stop(); - m_Timer = Timer.DelayCall( DeathDelay, Kill ); + m_Timer = Timer.DelayCall(DeathDelay, Kill); - InvalidateProperties(); - } + InvalidateProperties(); + } - public virtual void StopTimer() - { - m_Timer?.Stop(); + public virtual void StopTimer() + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - InvalidateProperties(); - } + InvalidateProperties(); + } - public override void OnDelete() - { - StopTimer(); - } + public override void OnDelete() + { + StopTimer(); + } - public virtual void Kill() - { - ItemID = 0x3B0C; - StopTimer(); + public virtual void Kill() + { + ItemID = 0x3B0C; + StopTimer(); - InvalidateProperties(); - } + InvalidateProperties(); + } - public int GetDescription() - { - // TODO: This will never return "very unusual dead aquarium creature" due to the way it is killed - if ( ItemID > 0x3B0F ) - return Dead ? 1074424 : 1074422; // A very unusual [dead/live] aquarium creature - if ( Hue != 0 ) - return Dead ? 1074425 : 1074423; // A [dead/live] aquarium creature of unusual color + public int GetDescription() + { + // TODO: This will never return "very unusual dead aquarium creature" due to the way it is killed + if (ItemID > 0x3B0F) + return Dead ? 1074424 : 1074422; // A very unusual [dead/live] aquarium creature + if (Hue != 0) + return Dead ? 1074425 : 1074423; // A [dead/live] aquarium creature of unusual color - return Dead ? 1073623 : 1073622; // A [dead/live] aquarium creature - } + return Dead ? 1073623 : 1073622; // A [dead/live] aquarium creature + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( GetDescription() ); + list.Add(GetDescription()); - if ( !Dead && m_Timer != null ) - list.Add( 1074507 ); // Gasping for air - } + if (!Dead && m_Timer != null) + list.Add(1074507); // Gasping for air + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( !( Parent is Aquarium ) && !( Parent is FishBowl ) ) - StartTimer(); - } - } -} + if (!(Parent is Aquarium) && !(Parent is FishBowl)) + StartTimer(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/AlbinoCourtesanFish.cs b/Scripts/Items/Aquarium/Fish/AlbinoCourtesanFish.cs index 1b7fd1da6..e04780fad 100644 --- a/Scripts/Items/Aquarium/Fish/AlbinoCourtesanFish.cs +++ b/Scripts/Items/Aquarium/Fish/AlbinoCourtesanFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class AlbinoCourtesanFish : BaseFish - { - public override int LabelNumber => 1074592; // Albino Courtesan Fish + public class AlbinoCourtesanFish : BaseFish + { + [Constructible] + public AlbinoCourtesanFish() : base(0x3B04) + { + } - [Constructible] - public AlbinoCourtesanFish() : base( 0x3B04 ) - { - } + public AlbinoCourtesanFish(Serial serial) : base(serial) + { + } - public AlbinoCourtesanFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074592; // Albino Courtesan Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/AlbinoFrog.cs b/Scripts/Items/Aquarium/Fish/AlbinoFrog.cs index c3215cc17..93028fa68 100644 --- a/Scripts/Items/Aquarium/Fish/AlbinoFrog.cs +++ b/Scripts/Items/Aquarium/Fish/AlbinoFrog.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AlbinoFrog : BaseFish - { - public override int LabelNumber => 1073824; // An Albino Frog + public class AlbinoFrog : BaseFish + { + [Constructible] + public AlbinoFrog() : base(0x3B0D) + { + Hue = 0x47E; + } - [Constructible] - public AlbinoFrog() : base( 0x3B0D ) - { - Hue = 0x47E; - } + public AlbinoFrog(Serial serial) : base(serial) + { + } - public AlbinoFrog( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073824; // An Albino Frog - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/BritainCrownFish.cs b/Scripts/Items/Aquarium/Fish/BritainCrownFish.cs index 2485ccbe4..f046e42b1 100644 --- a/Scripts/Items/Aquarium/Fish/BritainCrownFish.cs +++ b/Scripts/Items/Aquarium/Fish/BritainCrownFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class BritainCrownFish : BaseFish - { - public override int LabelNumber => 1074589; // Britain Crown Fish + public class BritainCrownFish : BaseFish + { + [Constructible] + public BritainCrownFish() : base(0x3AFF) + { + } - [Constructible] - public BritainCrownFish() : base( 0x3AFF ) - { - } + public BritainCrownFish(Serial serial) : base(serial) + { + } - public BritainCrownFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074589; // Britain Crown Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/FandancerFish.cs b/Scripts/Items/Aquarium/Fish/FandancerFish.cs index 46bb49f7b..f4bb81578 100644 --- a/Scripts/Items/Aquarium/Fish/FandancerFish.cs +++ b/Scripts/Items/Aquarium/Fish/FandancerFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class FandancerFish : BaseFish - { - public override int LabelNumber => 1074591; // Fandancer Fish + public class FandancerFish : BaseFish + { + [Constructible] + public FandancerFish() : base(0x3B02) + { + } - [Constructible] - public FandancerFish() : base( 0x3B02 ) - { - } + public FandancerFish(Serial serial) : base(serial) + { + } - public FandancerFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074591; // Fandancer Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/GoldenBroadtail.cs b/Scripts/Items/Aquarium/Fish/GoldenBroadtail.cs index 0c60d1dbb..af057c23a 100644 --- a/Scripts/Items/Aquarium/Fish/GoldenBroadtail.cs +++ b/Scripts/Items/Aquarium/Fish/GoldenBroadtail.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class GoldenBroadtail : BaseFish - { - public override int LabelNumber => 1073828; // A Golden Broadtail + public class GoldenBroadtail : BaseFish + { + [Constructible] + public GoldenBroadtail() : base(0x3B03) + { + } - [Constructible] - public GoldenBroadtail() : base( 0x3B03 ) - { - } + public GoldenBroadtail(Serial serial) : base(serial) + { + } - public GoldenBroadtail( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073828; // A Golden Broadtail - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/Jellyfish.cs b/Scripts/Items/Aquarium/Fish/Jellyfish.cs index a4c9fa57f..28e289ded 100644 --- a/Scripts/Items/Aquarium/Fish/Jellyfish.cs +++ b/Scripts/Items/Aquarium/Fish/Jellyfish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class Jellyfish : BaseFish - { - public override int LabelNumber => 1074593; // Jellyfish + public class Jellyfish : BaseFish + { + [Constructible] + public Jellyfish() : base(0x3B0E) + { + } - [Constructible] - public Jellyfish() : base( 0x3B0E ) - { - } + public Jellyfish(Serial serial) : base(serial) + { + } - public Jellyfish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074593; // Jellyfish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/KillerFrog.cs b/Scripts/Items/Aquarium/Fish/KillerFrog.cs index 1799a6cfe..44debc977 100644 --- a/Scripts/Items/Aquarium/Fish/KillerFrog.cs +++ b/Scripts/Items/Aquarium/Fish/KillerFrog.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class KillerFrog : BaseFish - { - public override int LabelNumber => 1073825; // A Killer Frog + public class KillerFrog : BaseFish + { + [Constructible] + public KillerFrog() : base(0x3B0D) + { + } - [Constructible] - public KillerFrog() : base( 0x3B0D ) - { - } + public KillerFrog(Serial serial) : base(serial) + { + } - public KillerFrog( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073825; // A Killer Frog - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/LongClawCrab.cs b/Scripts/Items/Aquarium/Fish/LongClawCrab.cs index 23c7119e2..f6d0d0cde 100644 --- a/Scripts/Items/Aquarium/Fish/LongClawCrab.cs +++ b/Scripts/Items/Aquarium/Fish/LongClawCrab.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class LongClawCrab : BaseFish - { - public override int LabelNumber => 1073827; // A Long Claw Crab + public class LongClawCrab : BaseFish + { + [Constructible] + public LongClawCrab() : base(0x3AFC) + { + Hue = 0x527; + } - [Constructible] - public LongClawCrab() : base( 0x3AFC ) - { - Hue = 0x527; - } + public LongClawCrab(Serial serial) : base(serial) + { + } - public LongClawCrab( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073827; // A Long Claw Crab - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/MakotoCourtesanFish.cs b/Scripts/Items/Aquarium/Fish/MakotoCourtesanFish.cs index dbb232260..4bfbc080f 100644 --- a/Scripts/Items/Aquarium/Fish/MakotoCourtesanFish.cs +++ b/Scripts/Items/Aquarium/Fish/MakotoCourtesanFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class MakotoCourtesanFish : BaseFish - { - public override int LabelNumber => 1073835; // A Makoto Courtesan Fish + public class MakotoCourtesanFish : BaseFish + { + [Constructible] + public MakotoCourtesanFish() : base(0x3AFD) + { + } - [Constructible] - public MakotoCourtesanFish() : base( 0x3AFD ) - { - } + public MakotoCourtesanFish(Serial serial) : base(serial) + { + } - public MakotoCourtesanFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073835; // A Makoto Courtesan Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/MinocBlueFish.cs b/Scripts/Items/Aquarium/Fish/MinocBlueFish.cs index fca62ecfb..189e15219 100644 --- a/Scripts/Items/Aquarium/Fish/MinocBlueFish.cs +++ b/Scripts/Items/Aquarium/Fish/MinocBlueFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class MinocBlueFish : BaseFish - { - public override int LabelNumber => 1073829; // A Minoc Blue Fish + public class MinocBlueFish : BaseFish + { + [Constructible] + public MinocBlueFish() : base(0x3AFE) + { + } - [Constructible] - public MinocBlueFish() : base( 0x3AFE ) - { - } + public MinocBlueFish(Serial serial) : base(serial) + { + } - public MinocBlueFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073829; // A Minoc Blue Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/NujelmHoneyFish.cs b/Scripts/Items/Aquarium/Fish/NujelmHoneyFish.cs index e7f4e6f9a..3d78ddda9 100644 --- a/Scripts/Items/Aquarium/Fish/NujelmHoneyFish.cs +++ b/Scripts/Items/Aquarium/Fish/NujelmHoneyFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class NujelmHoneyFish : BaseFish - { - public override int LabelNumber => 1073830; // A Nujel'm Honey Fish + public class NujelmHoneyFish : BaseFish + { + [Constructible] + public NujelmHoneyFish() : base(0x3B06) + { + } - [Constructible] - public NujelmHoneyFish() : base( 0x3B06 ) - { - } + public NujelmHoneyFish(Serial serial) : base(serial) + { + } - public NujelmHoneyFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073830; // A Nujel'm Honey Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/PurpleFrog.cs b/Scripts/Items/Aquarium/Fish/PurpleFrog.cs index b4b217c4f..2ad0748d9 100644 --- a/Scripts/Items/Aquarium/Fish/PurpleFrog.cs +++ b/Scripts/Items/Aquarium/Fish/PurpleFrog.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class PurpleFrog : BaseFish - { - public override int LabelNumber => 1073823; // A Purple Frog + public class PurpleFrog : BaseFish + { + [Constructible] + public PurpleFrog() : base(0x3B0D) + { + Hue = 0x4FA; + } - [Constructible] - public PurpleFrog() : base( 0x3B0D ) - { - Hue = 0x4FA; - } + public PurpleFrog(Serial serial) : base(serial) + { + } - public PurpleFrog( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073823; // A Purple Frog - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/RedDartFish.cs b/Scripts/Items/Aquarium/Fish/RedDartFish.cs index ff8a5b299..82057b12c 100644 --- a/Scripts/Items/Aquarium/Fish/RedDartFish.cs +++ b/Scripts/Items/Aquarium/Fish/RedDartFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class RedDartFish : BaseFish - { - public override int LabelNumber => 1073834; // A Red Dart Fish + public class RedDartFish : BaseFish + { + [Constructible] + public RedDartFish() : base(0x3B00) + { + } - [Constructible] - public RedDartFish() : base( 0x3B00 ) - { - } + public RedDartFish(Serial serial) : base(serial) + { + } - public RedDartFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073834; // A Red Dart Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/Shrimp.cs b/Scripts/Items/Aquarium/Fish/Shrimp.cs index 14b6fb9d8..59eb7adca 100644 --- a/Scripts/Items/Aquarium/Fish/Shrimp.cs +++ b/Scripts/Items/Aquarium/Fish/Shrimp.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class Shrimp : BaseFish - { - public override int LabelNumber => 1074596; // Shrimp + public class Shrimp : BaseFish + { + [Constructible] + public Shrimp() : base(0x3B14) + { + } - [Constructible] - public Shrimp() : base( 0x3B14 ) - { - } + public Shrimp(Serial serial) : base(serial) + { + } - public Shrimp( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074596; // Shrimp - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/SmallMouthSuckerFin.cs b/Scripts/Items/Aquarium/Fish/SmallMouthSuckerFin.cs index c5d7cf14f..3183ac81b 100644 --- a/Scripts/Items/Aquarium/Fish/SmallMouthSuckerFin.cs +++ b/Scripts/Items/Aquarium/Fish/SmallMouthSuckerFin.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class SmallMouthSuckerFin : BaseFish - { - public override int LabelNumber => 1074590; // Small Mouth Sucker Fin + public class SmallMouthSuckerFin : BaseFish + { + [Constructible] + public SmallMouthSuckerFin() : base(0x3B01) + { + } - [Constructible] - public SmallMouthSuckerFin() : base( 0x3B01 ) - { - } + public SmallMouthSuckerFin(Serial serial) : base(serial) + { + } - public SmallMouthSuckerFin( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074590; // Small Mouth Sucker Fin - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/SpeckledCrab.cs b/Scripts/Items/Aquarium/Fish/SpeckledCrab.cs index e9bc5125d..3667a2069 100644 --- a/Scripts/Items/Aquarium/Fish/SpeckledCrab.cs +++ b/Scripts/Items/Aquarium/Fish/SpeckledCrab.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class SpeckledCrab : BaseFish - { - public override int LabelNumber => 1073826; // A Speckled Crab + public class SpeckledCrab : BaseFish + { + [Constructible] + public SpeckledCrab() : base(0x3AFC) + { + } - [Constructible] - public SpeckledCrab() : base( 0x3AFC ) - { - } + public SpeckledCrab(Serial serial) : base(serial) + { + } - public SpeckledCrab( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073826; // A Speckled Crab - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/SpinedScratcherFish.cs b/Scripts/Items/Aquarium/Fish/SpinedScratcherFish.cs index 2d82e8ddb..89a1e52d9 100644 --- a/Scripts/Items/Aquarium/Fish/SpinedScratcherFish.cs +++ b/Scripts/Items/Aquarium/Fish/SpinedScratcherFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class SpinedScratcherFish : BaseFish - { - public override int LabelNumber => 1073832; // A Spined Scratcher Fish + public class SpinedScratcherFish : BaseFish + { + [Constructible] + public SpinedScratcherFish() : base(0x3B05) + { + } - [Constructible] - public SpinedScratcherFish() : base( 0x3B05 ) - { - } + public SpinedScratcherFish(Serial serial) : base(serial) + { + } - public SpinedScratcherFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073832; // A Spined Scratcher Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/SpottedBuccaneer.cs b/Scripts/Items/Aquarium/Fish/SpottedBuccaneer.cs index bcc795347..baeccc5e6 100644 --- a/Scripts/Items/Aquarium/Fish/SpottedBuccaneer.cs +++ b/Scripts/Items/Aquarium/Fish/SpottedBuccaneer.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class SpottedBuccaneer : BaseFish - { - public override int LabelNumber => 1073833; // A Spotted Buccaneer + public class SpottedBuccaneer : BaseFish + { + [Constructible] + public SpottedBuccaneer() : base(0x3B09) + { + } - [Constructible] - public SpottedBuccaneer() : base( 0x3B09 ) - { - } + public SpottedBuccaneer(Serial serial) : base(serial) + { + } - public SpottedBuccaneer( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073833; // A Spotted Buccaneer - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/VesperReefTiger.cs b/Scripts/Items/Aquarium/Fish/VesperReefTiger.cs index f8caf9cb7..ebfdc5098 100644 --- a/Scripts/Items/Aquarium/Fish/VesperReefTiger.cs +++ b/Scripts/Items/Aquarium/Fish/VesperReefTiger.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class VesperReefTiger : BaseFish - { - public override int LabelNumber => 1073836; // A Vesper Reef Tiger + public class VesperReefTiger : BaseFish + { + [Constructible] + public VesperReefTiger() : base(0x3B08) + { + } - [Constructible] - public VesperReefTiger() : base( 0x3B08 ) - { - } + public VesperReefTiger(Serial serial) : base(serial) + { + } - public VesperReefTiger( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073836; // A Vesper Reef Tiger - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Fish/YellowFinBluebelly.cs b/Scripts/Items/Aquarium/Fish/YellowFinBluebelly.cs index 4c0d728e8..22f6f5c14 100644 --- a/Scripts/Items/Aquarium/Fish/YellowFinBluebelly.cs +++ b/Scripts/Items/Aquarium/Fish/YellowFinBluebelly.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class YellowFinBluebelly : BaseFish - { - public override int LabelNumber => 1073831; // A Yellow Fin Bluebelly + public class YellowFinBluebelly : BaseFish + { + [Constructible] + public YellowFinBluebelly() : base(0x3B07) + { + } - [Constructible] - public YellowFinBluebelly() : base( 0x3B07 ) - { - } + public YellowFinBluebelly(Serial serial) : base(serial) + { + } - public YellowFinBluebelly( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073831; // A Yellow Fin Bluebelly - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/FishBowl.cs b/Scripts/Items/Aquarium/FishBowl.cs index c983c3edc..fe8666470 100644 --- a/Scripts/Items/Aquarium/FishBowl.cs +++ b/Scripts/Items/Aquarium/FishBowl.cs @@ -4,167 +4,167 @@ using Server.Network; namespace Server.Items { - public class FishBowl : BaseContainer - { - public override int LabelNumber => 1074499; // A fish bowl + public class FishBowl : BaseContainer + { + [Constructible] + public FishBowl() : base(0x241C) + { + Hue = 0x47E; + MaxItems = 1; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool Empty => ( Items.Count == 0 ); + public FishBowl(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public BaseFish Fish - { - get - { - if ( Empty ) - return null; + public override int LabelNumber => 1074499; // A fish bowl - return Items[0] as BaseFish; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Empty => Items.Count == 0; - public override double DefaultWeight => 2.0; + [CommandProperty(AccessLevel.GameMaster)] + public BaseFish Fish + { + get + { + if (Empty) + return null; - [Constructible] - public FishBowl() : base( 0x241C ) - { - Hue = 0x47E; - MaxItems = 1; - } + return Items[0] as BaseFish; + } + } - public FishBowl( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 2.0; - public override void OnDoubleClick( Mobile from ) - { - } + public override void OnDoubleClick(Mobile from) + { + } - public override bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage ) - { - if ( !CheckHold( from, dropped, sendFullMessage, true ) ) - return false; + public override bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage) + { + if (!CheckHold(from, dropped, sendFullMessage, true)) + return false; - DropItem( dropped ); - return true; - } + DropItem(dropped); + return true; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( !IsAccessibleTo( from ) ) - { - from.SendLocalizedMessage( 502436 ); // That is not accessible. - return false; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (!IsAccessibleTo(from)) + { + from.SendLocalizedMessage(502436); // That is not accessible. + return false; + } - if ( !( dropped is BaseFish ) ) - { - from.SendLocalizedMessage( 1074836 ); // The container can not hold that type of object. - return false; - } + if (!(dropped is BaseFish)) + { + from.SendLocalizedMessage(1074836); // The container can not hold that type of object. + return false; + } - if ( base.OnDragDrop( from, dropped ) ) - { - ((BaseFish) dropped).StopTimer(); - InvalidateProperties(); + if (base.OnDragDrop(from, dropped)) + { + ((BaseFish)dropped).StopTimer(); + InvalidateProperties(); - return true; - } + return true; + } - return false; - } + return false; + } - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( item != this ) - return false; + public override bool CheckItemUse(Mobile from, Item item) + { + if (item != this) + return false; - return base.CheckItemUse( from, item ); - } + return base.CheckItemUse(from, item); + } - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( item != this ) - { - reject = LRReason.CannotLift; - return false; - } + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (item != this) + { + reject = LRReason.CannotLift; + return false; + } - return base.CheckLift( from, item, ref reject ); - } + return base.CheckLift(from, item, ref reject); + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - if ( !Empty ) - { - BaseFish fish = Fish; + if (!Empty) + { + BaseFish fish = Fish; - if ( fish != null ) - list.Add( 1074494, "#{0}", fish.LabelNumber ); // Contains: ~1_CREATURE~ - } - } + if (fish != null) + list.Add(1074494, "#{0}", fish.LabelNumber); // Contains: ~1_CREATURE~ + } + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( !Empty && IsAccessibleTo( from ) ) - list.Add( new RemoveCreature( this ) ); - } + if (!Empty && IsAccessibleTo(from)) + list.Add(new RemoveCreature(this)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 ) - Weight = DefaultWeight; - } + if (version == 0) + Weight = DefaultWeight; + } - private class RemoveCreature : ContextMenuEntry - { - private FishBowl m_Bowl; + private class RemoveCreature : ContextMenuEntry + { + private FishBowl m_Bowl; - public RemoveCreature( FishBowl bowl ) : base( 6242, 3 ) // Remove creature - { - m_Bowl = bowl; - } + public RemoveCreature(FishBowl bowl) : base(6242, 3) // Remove creature + { + m_Bowl = bowl; + } - public override void OnClick() - { - if ( m_Bowl == null || m_Bowl.Deleted || !m_Bowl.IsAccessibleTo( Owner.From ) ) - return; + public override void OnClick() + { + if (m_Bowl == null || m_Bowl.Deleted || !m_Bowl.IsAccessibleTo(Owner.From)) + return; - BaseFish fish = m_Bowl.Fish; + BaseFish fish = m_Bowl.Fish; - if ( fish != null ) - { - if ( fish.IsLockedDown ) // for legacy fish bowls - { - Owner.From.SendLocalizedMessage( 1010449 ); // You may not use this object while it is locked down. - } - else if ( !Owner.From.PlaceInBackpack( fish ) ) - { - Owner.From.SendLocalizedMessage( 1074496 ); // There is no room in your pack for the creature. - } - else - { - Owner.From.SendLocalizedMessage( 1074495 ); // The creature has been removed from the fish bowl. - fish.StartTimer(); - m_Bowl.InvalidateProperties(); - } - } - } - } - } -} + if (fish != null) + { + if (fish.IsLockedDown) // for legacy fish bowls + { + Owner.From.SendLocalizedMessage(1010449); // You may not use this object while it is locked down. + } + else if (!Owner.From.PlaceInBackpack(fish)) + { + Owner.From.SendLocalizedMessage(1074496); // There is no room in your pack for the creature. + } + else + { + Owner.From.SendLocalizedMessage(1074495); // The creature has been removed from the fish bowl. + fish.StartTimer(); + m_Bowl.InvalidateProperties(); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Reward Fish/BrineShrimp.cs b/Scripts/Items/Aquarium/Reward Fish/BrineShrimp.cs index 80c0162ce..7200fa416 100644 --- a/Scripts/Items/Aquarium/Reward Fish/BrineShrimp.cs +++ b/Scripts/Items/Aquarium/Reward Fish/BrineShrimp.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class BrineShrimp : BaseFish - { - public override int LabelNumber => 1074415; // Brine shrimp + public class BrineShrimp : BaseFish + { + [Constructible] + public BrineShrimp() : base(0x3B11) + { + } - [Constructible] - public BrineShrimp() : base( 0x3B11 ) - { - } + public BrineShrimp(Serial serial) : base(serial) + { + } - public BrineShrimp( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074415; // Brine shrimp - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Reward Fish/Coral.cs b/Scripts/Items/Aquarium/Reward Fish/Coral.cs index d992964cc..2812c6f70 100644 --- a/Scripts/Items/Aquarium/Reward Fish/Coral.cs +++ b/Scripts/Items/Aquarium/Reward Fish/Coral.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class Coral : BaseFish - { - public override int LabelNumber => 1074588; // Coral + public class Coral : BaseFish + { + [Constructible] + public Coral() : base(Utility.RandomList(0x3AF9, 0x3AFA, 0x3AFB)) + { + } - [Constructible] - public Coral() : base( Utility.RandomList( 0x3AF9, 0x3AFA, 0x3AFB ) ) - { - } + public Coral(Serial serial) : base(serial) + { + } - public Coral( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074588; // Coral - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Reward Fish/FullMoonFish.cs b/Scripts/Items/Aquarium/Reward Fish/FullMoonFish.cs index 83b6de156..c9dd15c4c 100644 --- a/Scripts/Items/Aquarium/Reward Fish/FullMoonFish.cs +++ b/Scripts/Items/Aquarium/Reward Fish/FullMoonFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class FullMoonFish : BaseFish - { - public override int LabelNumber => 1074597; // A Full Moon Fish + public class FullMoonFish : BaseFish + { + [Constructible] + public FullMoonFish() : base(0x3B15) + { + } - [Constructible] - public FullMoonFish() : base( 0x3B15 ) - { - } + public FullMoonFish(Serial serial) : base(serial) + { + } - public FullMoonFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074597; // A Full Moon Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Reward Fish/SeaHorse.cs b/Scripts/Items/Aquarium/Reward Fish/SeaHorse.cs index 597f761f3..292abd06f 100644 --- a/Scripts/Items/Aquarium/Reward Fish/SeaHorse.cs +++ b/Scripts/Items/Aquarium/Reward Fish/SeaHorse.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class SeaHorseFish : BaseFish - { - public override int LabelNumber => 1074414; // A sea horse + public class SeaHorseFish : BaseFish + { + [Constructible] + public SeaHorseFish() : base(0x3B10) + { + } - [Constructible] - public SeaHorseFish() : base( 0x3B10 ) - { - } + public SeaHorseFish(Serial serial) : base(serial) + { + } - public SeaHorseFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074414; // A sea horse - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Reward Fish/StrippedFlakeFish.cs b/Scripts/Items/Aquarium/Reward Fish/StrippedFlakeFish.cs index 6509b13c8..3863407c0 100644 --- a/Scripts/Items/Aquarium/Reward Fish/StrippedFlakeFish.cs +++ b/Scripts/Items/Aquarium/Reward Fish/StrippedFlakeFish.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class StrippedFlakeFish : BaseFish - { - public override int LabelNumber => 1074595; // Stripped Flake Fish + public class StrippedFlakeFish : BaseFish + { + [Constructible] + public StrippedFlakeFish() : base(0x3B0A) + { + } - [Constructible] - public StrippedFlakeFish() : base( 0x3B0A ) - { - } + public StrippedFlakeFish(Serial serial) : base(serial) + { + } - public StrippedFlakeFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074595; // Stripped Flake Fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Reward Fish/StrippedSosarianSwill.cs b/Scripts/Items/Aquarium/Reward Fish/StrippedSosarianSwill.cs index 083b5bbc8..ef3199d9a 100644 --- a/Scripts/Items/Aquarium/Reward Fish/StrippedSosarianSwill.cs +++ b/Scripts/Items/Aquarium/Reward Fish/StrippedSosarianSwill.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class StrippedSosarianSwill : BaseFish - { - public override int LabelNumber => 1074594; // Stripped Sosarian Swill + public class StrippedSosarianSwill : BaseFish + { + [Constructible] + public StrippedSosarianSwill() : base(0x3B0A) + { + } - [Constructible] - public StrippedSosarianSwill() : base( 0x3B0A ) - { - } + public StrippedSosarianSwill(Serial serial) : base(serial) + { + } - public StrippedSosarianSwill( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074594; // Stripped Sosarian Swill - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/AquariumMessage.cs b/Scripts/Items/Aquarium/Rewards/AquariumMessage.cs index a08d54a06..8785750bc 100644 --- a/Scripts/Items/Aquarium/Rewards/AquariumMessage.cs +++ b/Scripts/Items/Aquarium/Rewards/AquariumMessage.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class AquariumMessage : MessageInABottle - { - public override int LabelNumber => 1073894; // Message in a Bottle + public class AquariumMessage : MessageInABottle + { + [Constructible] + public AquariumMessage() + { + } - [Constructible] - public AquariumMessage() - { - } + public AquariumMessage(Serial serial) : base(serial) + { + } - public AquariumMessage( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073894; // Message in a Bottle - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/CaptainBlackheartsFishingPole.cs b/Scripts/Items/Aquarium/Rewards/CaptainBlackheartsFishingPole.cs index b406c9a80..1cd828ff5 100644 --- a/Scripts/Items/Aquarium/Rewards/CaptainBlackheartsFishingPole.cs +++ b/Scripts/Items/Aquarium/Rewards/CaptainBlackheartsFishingPole.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class CaptainBlackheartsFishingPole : FishingPole - { - public override int LabelNumber => 1074571; // Captain Blackheart's Fishing Pole + public class CaptainBlackheartsFishingPole : FishingPole + { + [Constructible] + public CaptainBlackheartsFishingPole() + { + } - [Constructible] - public CaptainBlackheartsFishingPole() - { - } + public CaptainBlackheartsFishingPole(Serial serial) : base(serial) + { + } - public CaptainBlackheartsFishingPole( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074571; // Captain Blackheart's Fishing Pole - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/CraftysFishingHat.cs b/Scripts/Items/Aquarium/Rewards/CraftysFishingHat.cs index 9aaa3b9a4..f841c17ee 100644 --- a/Scripts/Items/Aquarium/Rewards/CraftysFishingHat.cs +++ b/Scripts/Items/Aquarium/Rewards/CraftysFishingHat.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class CraftysFishingHat : BaseHat - { - public override int LabelNumber => 1074572; // Crafty's Fishing Hat + public class CraftysFishingHat : BaseHat + { + [Constructible] + public CraftysFishingHat() : base(0x1713) + { + } - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + public CraftysFishingHat(Serial serial) : base(serial) + { + } - public override int InitMinHits => 20; - public override int InitMaxHits => 30; + public override int LabelNumber => 1074572; // Crafty's Fishing Hat - [Constructible] - public CraftysFishingHat() : base( 0x1713 ) - { - } + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public CraftysFishingHat( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 20; + public override int InitMaxHits => 30; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/FishBones.cs b/Scripts/Items/Aquarium/Rewards/FishBones.cs index b18403ef6..56c1509f9 100644 --- a/Scripts/Items/Aquarium/Rewards/FishBones.cs +++ b/Scripts/Items/Aquarium/Rewards/FishBones.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class FishBones : Item - { - public override int LabelNumber => 1074601; // Fish bones - public override double DefaultWeight => 1.0; + public class FishBones : Item + { + [Constructible] + public FishBones() : base(0x3B0C) + { + } - [Constructible] - public FishBones() : base( 0x3B0C ) - { - } + public FishBones(Serial serial) : base(serial) + { + } - public FishBones( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074601; // Fish bones + public override double DefaultWeight => 1.0; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/IslandStatue.cs b/Scripts/Items/Aquarium/Rewards/IslandStatue.cs index 8c8a021c7..ad7158fca 100644 --- a/Scripts/Items/Aquarium/Rewards/IslandStatue.cs +++ b/Scripts/Items/Aquarium/Rewards/IslandStatue.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class IslandStatue : Item - { - public override int LabelNumber => 1074600; // An island statue - public override double DefaultWeight => 1.0; + public class IslandStatue : Item + { + [Constructible] + public IslandStatue() : base(0x3B0F) + { + } - [Constructible] - public IslandStatue() : base( 0x3B0F ) - { - } + public IslandStatue(Serial serial) : base(serial) + { + } - public IslandStatue( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074600; // An island statue + public override double DefaultWeight => 1.0; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/Shell.cs b/Scripts/Items/Aquarium/Rewards/Shell.cs index 523464f46..4b21bfefd 100644 --- a/Scripts/Items/Aquarium/Rewards/Shell.cs +++ b/Scripts/Items/Aquarium/Rewards/Shell.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class Shell : Item - { - public override int LabelNumber => 1074598; // A shell - public override double DefaultWeight => 1.0; + public class Shell : Item + { + [Constructible] + public Shell() : base(Utility.RandomList(0x3B12, 0x3B13)) + { + } - [Constructible] - public Shell() : base( Utility.RandomList( 0x3B12, 0x3B13 ) ) - { - } + public Shell(Serial serial) : base(serial) + { + } - public Shell( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074598; // A shell + public override double DefaultWeight => 1.0; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/ToyBoat.cs b/Scripts/Items/Aquarium/Rewards/ToyBoat.cs index 1c33466b9..fcd509914 100644 --- a/Scripts/Items/Aquarium/Rewards/ToyBoat.cs +++ b/Scripts/Items/Aquarium/Rewards/ToyBoat.cs @@ -1,39 +1,39 @@ namespace Server.Items { - [FlippableAttribute( 0x14F3, 0x14F4 )] - public class ToyBoat : Item - { - public override int LabelNumber => 1074363; // A toy boat - public override double DefaultWeight => 1.0; + [Flippable(0x14F3, 0x14F4)] + public class ToyBoat : Item + { + [Constructible] + public ToyBoat() : base(0x14F4) + { + } - [Constructible] - public ToyBoat() : base( 0x14F4 ) - { - } + public ToyBoat(Serial serial) : base(serial) + { + } - public ToyBoat( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074363; // A toy boat + public override double DefaultWeight => 1.0; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/Rewards/WaterloggedBoots.cs b/Scripts/Items/Aquarium/Rewards/WaterloggedBoots.cs index 6911d2577..1a1732253 100644 --- a/Scripts/Items/Aquarium/Rewards/WaterloggedBoots.cs +++ b/Scripts/Items/Aquarium/Rewards/WaterloggedBoots.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class WaterloggedBoots : BaseShoes - { - public override int LabelNumber => 1074364; // Waterlogged boots + public class WaterloggedBoots : BaseShoes + { + [Constructible] + public WaterloggedBoots() : base(0x1711) + { + if (Utility.RandomBool()) + { + // thigh boots + ItemID = 0x1711; + Weight = 4.0; + } + else + { + // boots + ItemID = 0x170B; + Weight = 3.0; + } + } - [Constructible] - public WaterloggedBoots() : base( 0x1711 ) - { - if ( Utility.RandomBool() ) - { - // thigh boots - ItemID = 0x1711; - Weight = 4.0; - } - else - { - // boots - ItemID = 0x170B; - Weight = 3.0; - } - } + public WaterloggedBoots(Serial serial) : base(serial) + { + } - public WaterloggedBoots( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074364; // Waterlogged boots - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1073634 ); // An aquarium decoration - } + list.Add(1073634); // An aquarium decoration + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Aquarium/VacationWafer.cs b/Scripts/Items/Aquarium/VacationWafer.cs index d95187b70..9b5d0768c 100644 --- a/Scripts/Items/Aquarium/VacationWafer.cs +++ b/Scripts/Items/Aquarium/VacationWafer.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class VacationWafer : Item - { - public const int VacationDays = 7; + public class VacationWafer : Item + { + public const int VacationDays = 7; - public override int LabelNumber => 1074431; // An aquarium flake sphere + [Constructible] + public VacationWafer() : base(0x973) + { + } - [Constructible] - public VacationWafer() : base( 0x973 ) - { - } + public VacationWafer(Serial serial) : base(serial) + { + } - public VacationWafer( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074431; // An aquarium flake sphere - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1074432, VacationDays.ToString() ); // Vacation days: ~1_DAYS~ - } + list.Add(1074432, VacationDays.ToString()); // Vacation days: ~1_DAYS~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 && ItemID == 0x971 ) - ItemID = 0x973; - } - } -} + if (version < 1 && ItemID == 0x971) + ItemID = 0x973; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/ArmorEnums.cs b/Scripts/Items/Armor/ArmorEnums.cs index 7f907eda6..b51a89c8b 100644 --- a/Scripts/Items/Armor/ArmorEnums.cs +++ b/Scripts/Items/Armor/ArmorEnums.cs @@ -1,62 +1,62 @@ namespace Server.Items { - public enum ArmorQuality - { - Low, - Regular, - Exceptional - } + public enum ArmorQuality + { + Low, + Regular, + Exceptional + } - public enum ArmorDurabilityLevel - { - Regular, - Durable, - Substantial, - Massive, - Fortified, - Indestructible - } + public enum ArmorDurabilityLevel + { + Regular, + Durable, + Substantial, + Massive, + Fortified, + Indestructible + } - public enum ArmorProtectionLevel - { - Regular, - Defense, - Guarding, - Hardening, - Fortification, - Invulnerability, - } + public enum ArmorProtectionLevel + { + Regular, + Defense, + Guarding, + Hardening, + Fortification, + Invulnerability + } - public enum ArmorBodyType - { - Gorget, - Gloves, - Helmet, - Arms, - Legs, - Chest, - Shield - } + public enum ArmorBodyType + { + Gorget, + Gloves, + Helmet, + Arms, + Legs, + Chest, + Shield + } - public enum ArmorMaterialType - { - Cloth, - Leather, - Studded, - Bone, - Spined, - Horned, - Barbed, - Ringmail, - Chainmail, - Plate, - Dragon // On OSI, Dragon is seen and considered its own type. - } + public enum ArmorMaterialType + { + Cloth, + Leather, + Studded, + Bone, + Spined, + Horned, + Barbed, + Ringmail, + Chainmail, + Plate, + Dragon // On OSI, Dragon is seen and considered its own type. + } - public enum ArmorMeditationAllowance - { - All, - Half, - None - } + public enum ArmorMeditationAllowance + { + All, + Half, + None + } } \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/ArmorOfFortune.cs b/Scripts/Items/Armor/Artifacts/ArmorOfFortune.cs index 9c1a2a52a..aa0081d55 100644 --- a/Scripts/Items/Armor/Artifacts/ArmorOfFortune.cs +++ b/Scripts/Items/Armor/Artifacts/ArmorOfFortune.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ArmorOfFortune : StuddedChest - { - public override int LabelNumber => 1061098; // Armor of Fortune - public override int ArtifactRarity => 11; + public class ArmorOfFortune : StuddedChest + { + [Constructible] + public ArmorOfFortune() + { + Hue = 0x501; + Attributes.Luck = 200; + Attributes.DefendChance = 15; + Attributes.LowerRegCost = 40; + ArmorAttributes.MageArmor = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public ArmorOfFortune(Serial serial) : base(serial) + { + } - [Constructible] - public ArmorOfFortune() - { - Hue = 0x501; - Attributes.Luck = 200; - Attributes.DefendChance = 15; - Attributes.LowerRegCost = 40; - ArmorAttributes.MageArmor = 1; - } + public override int LabelNumber => 1061098; // Armor of Fortune + public override int ArtifactRarity => 11; - public ArmorOfFortune( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/Craftable/BrambleCoat.cs b/Scripts/Items/Armor/Artifacts/Craftable/BrambleCoat.cs index 8b1fe1eef..f921b3fb2 100644 --- a/Scripts/Items/Armor/Artifacts/Craftable/BrambleCoat.cs +++ b/Scripts/Items/Armor/Artifacts/Craftable/BrambleCoat.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class BrambleCoat : WoodlandChest - { - public override int LabelNumber => 1072925; // Bramble Coat + public class BrambleCoat : WoodlandChest + { + [Constructible] + public BrambleCoat() + { + Hue = 0x1; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 8; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 8; - public override int BaseEnergyResistance => 7; + ArmorAttributes.SelfRepair = 3; + Attributes.BonusHits = 4; + Attributes.Luck = 150; + Attributes.ReflectPhysical = 25; + Attributes.DefendChance = 15; + } - [Constructible] - public BrambleCoat() - { - Hue = 0x1; + public BrambleCoat(Serial serial) : base(serial) + { + } - ArmorAttributes.SelfRepair = 3; - Attributes.BonusHits = 4; - Attributes.Luck = 150; - Attributes.ReflectPhysical = 25; - Attributes.DefendChance = 15; - } + public override int LabelNumber => 1072925; // Bramble Coat - public BrambleCoat( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 8; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 8; + public override int BaseEnergyResistance => 7; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/Craftable/IronwoodCrown.cs b/Scripts/Items/Armor/Artifacts/Craftable/IronwoodCrown.cs index 680446b3a..37353a9f2 100644 --- a/Scripts/Items/Armor/Artifacts/Craftable/IronwoodCrown.cs +++ b/Scripts/Items/Armor/Artifacts/Craftable/IronwoodCrown.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class IronwoodCrown : RavenHelm - { - public override int LabelNumber => 1072924; // Ironwood Crown + public class IronwoodCrown : RavenHelm + { + [Constructible] + public IronwoodCrown() + { + Hue = 0x1; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 7; - public override int BaseEnergyResistance => 10; + ArmorAttributes.SelfRepair = 3; - [Constructible] - public IronwoodCrown() - { - Hue = 0x1; + Attributes.BonusStr = 5; + Attributes.BonusDex = 5; + Attributes.BonusInt = 5; + } - ArmorAttributes.SelfRepair = 3; + public IronwoodCrown(Serial serial) : base(serial) + { + } - Attributes.BonusStr = 5; - Attributes.BonusDex = 5; - Attributes.BonusInt = 5; - } + public override int LabelNumber => 1072924; // Ironwood Crown - public IronwoodCrown( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 7; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/Craftable/SongWovenMantle.cs b/Scripts/Items/Armor/Artifacts/Craftable/SongWovenMantle.cs index 58749c884..e2fea3186 100644 --- a/Scripts/Items/Armor/Artifacts/Craftable/SongWovenMantle.cs +++ b/Scripts/Items/Armor/Artifacts/Craftable/SongWovenMantle.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class SongWovenMantle : LeafArms - { - public override int LabelNumber => 1072931; // Song Woven Mantle + public class SongWovenMantle : LeafArms + { + [Constructible] + public SongWovenMantle() + { + Hue = 0x493; - public override int BasePhysicalResistance => 14; - public override int BaseColdResistance => 14; - public override int BaseEnergyResistance => 16; + SkillBonuses.SetValues(0, SkillName.Musicianship, 10.0); - [Constructible] - public SongWovenMantle() - { - Hue = 0x493; + Attributes.Luck = 100; + Attributes.DefendChance = 5; + } - SkillBonuses.SetValues( 0, SkillName.Musicianship, 10.0 ); + public SongWovenMantle(Serial serial) : base(serial) + { + } - Attributes.Luck = 100; - Attributes.DefendChance = 5; - } + public override int LabelNumber => 1072931; // Song Woven Mantle - public SongWovenMantle( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 14; + public override int BaseColdResistance => 14; + public override int BaseEnergyResistance => 16; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/Craftable/SpellWovenBritches.cs b/Scripts/Items/Armor/Artifacts/Craftable/SpellWovenBritches.cs index 60eecd1bb..e18a60ef4 100644 --- a/Scripts/Items/Armor/Artifacts/Craftable/SpellWovenBritches.cs +++ b/Scripts/Items/Armor/Artifacts/Craftable/SpellWovenBritches.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class SpellWovenBritches : LeafLegs - { - public override int LabelNumber => 1072929; // Spell Woven Britches + public class SpellWovenBritches : LeafLegs + { + [Constructible] + public SpellWovenBritches() + { + Hue = 0x487; - public override int BaseFireResistance => 15; - public override int BasePoisonResistance => 16; + SkillBonuses.SetValues(0, SkillName.Meditation, 10.0); - [Constructible] - public SpellWovenBritches() - { - Hue = 0x487; + Attributes.BonusInt = 8; + Attributes.SpellDamage = 10; + Attributes.LowerManaCost = 10; + } - SkillBonuses.SetValues( 0, SkillName.Meditation, 10.0 ); + public SpellWovenBritches(Serial serial) : base(serial) + { + } - Attributes.BonusInt = 8; - Attributes.SpellDamage = 10; - Attributes.LowerManaCost = 10; - } + public override int LabelNumber => 1072929; // Spell Woven Britches - public SpellWovenBritches( Serial serial ) : base( serial ) - { - } + public override int BaseFireResistance => 15; + public override int BasePoisonResistance => 16; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/Craftable/StitchersMittens.cs b/Scripts/Items/Armor/Artifacts/Craftable/StitchersMittens.cs index ca661943b..40fa2d39e 100644 --- a/Scripts/Items/Armor/Artifacts/Craftable/StitchersMittens.cs +++ b/Scripts/Items/Armor/Artifacts/Craftable/StitchersMittens.cs @@ -1,40 +1,39 @@ namespace Server.Items { - public class StitchersMittens : LeafGloves - { - public override int LabelNumber => 1072932; // Stitcher's Mittens + public class StitchersMittens : LeafGloves + { + [Constructible] + public StitchersMittens() + { + Hue = 0x481; - public override int BasePhysicalResistance => 20; - public override int BaseColdResistance => 20; + SkillBonuses.SetValues(0, SkillName.Healing, 10.0); - [Constructible] - public StitchersMittens() - { - Hue = 0x481; + Attributes.BonusDex = 5; + Attributes.LowerRegCost = 30; + } - SkillBonuses.SetValues( 0, SkillName.Healing, 10.0 ); + public StitchersMittens(Serial serial) : base(serial) + { + } - Attributes.BonusDex = 5; - Attributes.LowerRegCost = 30; - } + public override int LabelNumber => 1072932; // Stitcher's Mittens - public StitchersMittens( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 20; + public override int BaseColdResistance => 20; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/GauntletsOfNobility.cs b/Scripts/Items/Armor/Artifacts/GauntletsOfNobility.cs index ece078714..e377080ba 100644 --- a/Scripts/Items/Armor/Artifacts/GauntletsOfNobility.cs +++ b/Scripts/Items/Armor/Artifacts/GauntletsOfNobility.cs @@ -1,50 +1,50 @@ namespace Server.Items { - public class GauntletsOfNobility : RingmailGloves - { - public override int LabelNumber => 1061092; // Gauntlets of Nobility - public override int ArtifactRarity => 11; + public class GauntletsOfNobility : RingmailGloves + { + [Constructible] + public GauntletsOfNobility() + { + Hue = 0x4FE; + Attributes.BonusStr = 8; + Attributes.Luck = 100; + Attributes.WeaponDamage = 20; + } - public override int BasePhysicalResistance => 18; - public override int BasePoisonResistance => 20; + public GauntletsOfNobility(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061092; // Gauntlets of Nobility + public override int ArtifactRarity => 11; - [Constructible] - public GauntletsOfNobility() - { - Hue = 0x4FE; - Attributes.BonusStr = 8; - Attributes.Luck = 100; - Attributes.WeaponDamage = 20; - } + public override int BasePhysicalResistance => 18; + public override int BasePoisonResistance => 20; - public GauntletsOfNobility( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - if ( Hue == 0x562 ) - Hue = 0x4FE; + if (version < 1) + { + if (Hue == 0x562) + Hue = 0x4FE; - PhysicalBonus = 0; - PoisonBonus = 0; - } - } - } -} + PhysicalBonus = 0; + PoisonBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/HelmOfInsight.cs b/Scripts/Items/Armor/Artifacts/HelmOfInsight.cs index 10b90b5fd..9f5b7a886 100644 --- a/Scripts/Items/Armor/Artifacts/HelmOfInsight.cs +++ b/Scripts/Items/Armor/Artifacts/HelmOfInsight.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class HelmOfInsight : PlateHelm - { - public override int LabelNumber => 1061096; // Helm of Insight - public override int ArtifactRarity => 11; + public class HelmOfInsight : PlateHelm + { + [Constructible] + public HelmOfInsight() + { + Hue = 0x554; + Attributes.BonusInt = 8; + Attributes.BonusMana = 15; + Attributes.RegenMana = 2; + Attributes.LowerManaCost = 8; + } - public override int BaseEnergyResistance => 17; + public HelmOfInsight(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061096; // Helm of Insight + public override int ArtifactRarity => 11; - [Constructible] - public HelmOfInsight() - { - Hue = 0x554; - Attributes.BonusInt = 8; - Attributes.BonusMana = 15; - Attributes.RegenMana = 2; - Attributes.LowerManaCost = 8; - } + public override int BaseEnergyResistance => 17; - public HelmOfInsight( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - EnergyBonus = 0; - } - } -} + if (version < 1) + EnergyBonus = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/HolyKnightsBreastplate.cs b/Scripts/Items/Armor/Artifacts/HolyKnightsBreastplate.cs index ec0fa000a..802a594e9 100644 --- a/Scripts/Items/Armor/Artifacts/HolyKnightsBreastplate.cs +++ b/Scripts/Items/Armor/Artifacts/HolyKnightsBreastplate.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class HolyKnightsBreastplate : PlateChest - { - public override int LabelNumber => 1061097; // Holy Knight's Breastplate - public override int ArtifactRarity => 11; + public class HolyKnightsBreastplate : PlateChest + { + [Constructible] + public HolyKnightsBreastplate() + { + Hue = 0x47E; + Attributes.BonusHits = 10; + Attributes.ReflectPhysical = 15; + } - public override int BasePhysicalResistance => 35; + public HolyKnightsBreastplate(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061097; // Holy Knight's Breastplate + public override int ArtifactRarity => 11; - [Constructible] - public HolyKnightsBreastplate() - { - Hue = 0x47E; - Attributes.BonusHits = 10; - Attributes.ReflectPhysical = 15; - } + public override int BasePhysicalResistance => 35; - public HolyKnightsBreastplate( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - PhysicalBonus = 0; - } - } -} + if (version < 1) + PhysicalBonus = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/InquisitorsResolution.cs b/Scripts/Items/Armor/Artifacts/InquisitorsResolution.cs index 5d08db757..8e7147904 100644 --- a/Scripts/Items/Armor/Artifacts/InquisitorsResolution.cs +++ b/Scripts/Items/Armor/Artifacts/InquisitorsResolution.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class InquisitorsResolution : PlateGloves - { - public override int LabelNumber => 1060206; // The Inquisitor's Resolution - public override int ArtifactRarity => 10; + public class InquisitorsResolution : PlateGloves + { + [Constructible] + public InquisitorsResolution() + { + Hue = 0x4F2; + Attributes.CastRecovery = 3; + Attributes.LowerManaCost = 8; + ArmorAttributes.MageArmor = 1; + } - public override int BaseColdResistance => 22; - public override int BaseEnergyResistance => 17; + public InquisitorsResolution(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1060206; // The Inquisitor's Resolution + public override int ArtifactRarity => 10; - [Constructible] - public InquisitorsResolution() - { - Hue = 0x4F2; - Attributes.CastRecovery = 3; - Attributes.LowerManaCost = 8; - ArmorAttributes.MageArmor = 1; - } + public override int BaseColdResistance => 22; + public override int BaseEnergyResistance => 17; - public InquisitorsResolution( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - ColdBonus = 0; - EnergyBonus = 0; - } - } - } -} + if (version < 1) + { + ColdBonus = 0; + EnergyBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/JackalsCollar.cs b/Scripts/Items/Armor/Artifacts/JackalsCollar.cs index be457132b..01543895a 100644 --- a/Scripts/Items/Armor/Artifacts/JackalsCollar.cs +++ b/Scripts/Items/Armor/Artifacts/JackalsCollar.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class JackalsCollar : PlateGorget - { - public override int LabelNumber => 1061594; // Jackal's Collar - public override int ArtifactRarity => 11; + public class JackalsCollar : PlateGorget + { + [Constructible] + public JackalsCollar() + { + Hue = 0x6D1; + Attributes.BonusDex = 15; + Attributes.RegenHits = 2; + } - public override int BaseFireResistance => 23; - public override int BaseColdResistance => 17; + public JackalsCollar(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061594; // Jackal's Collar + public override int ArtifactRarity => 11; - [Constructible] - public JackalsCollar() - { - Hue = 0x6D1; - Attributes.BonusDex = 15; - Attributes.RegenHits = 2; - } + public override int BaseFireResistance => 23; + public override int BaseColdResistance => 17; - public JackalsCollar( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - if ( Hue == 0x54B ) - Hue = 0x6D1; + if (version < 1) + { + if (Hue == 0x54B) + Hue = 0x6D1; - FireBonus = 0; - ColdBonus = 0; - } - } - } -} + FireBonus = 0; + ColdBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/LeggingsOfBane.cs b/Scripts/Items/Armor/Artifacts/LeggingsOfBane.cs index b9016ff8c..23e96d691 100644 --- a/Scripts/Items/Armor/Artifacts/LeggingsOfBane.cs +++ b/Scripts/Items/Armor/Artifacts/LeggingsOfBane.cs @@ -1,58 +1,57 @@ namespace Server.Items { - public class LeggingsOfBane : ChainLegs - { - public override int LabelNumber => 1061100; // Leggings of Bane - public override int ArtifactRarity => 11; + public class LeggingsOfBane : ChainLegs + { + [Constructible] + public LeggingsOfBane() + { + Hue = 0x4F5; + ArmorAttributes.DurabilityBonus = 100; + HitPoints = MaxHitPoints = + 255; //Cause the Durability bonus and such and the min/max hits as well as all other hits being whole #'s... + Attributes.BonusStam = 8; + Attributes.AttackChance = 20; + } - public override int BasePoisonResistance => 36; + public LeggingsOfBane(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061100; // Leggings of Bane + public override int ArtifactRarity => 11; - [Constructible] - public LeggingsOfBane() - { - Hue = 0x4F5; - ArmorAttributes.DurabilityBonus = 100; - HitPoints = MaxHitPoints = 255; //Cause the Durability bonus and such and the min/max hits as well as all other hits being whole #'s... - Attributes.BonusStam = 8; - Attributes.AttackChance = 20; - } + public override int BasePoisonResistance => 36; - public LeggingsOfBane( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 2 ); - } + writer.Write(2); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version <= 1 ) - { - if ( HitPoints > 255 || MaxHitPoints > 255 ) - HitPoints = MaxHitPoints = 255; - } + if (version <= 1) + if (HitPoints > 255 || MaxHitPoints > 255) + HitPoints = MaxHitPoints = 255; - if ( version < 1 ) - { - if ( Hue == 0x559 ) - Hue = 0x4F5; + if (version < 1) + { + if (Hue == 0x559) + Hue = 0x4F5; - if ( ArmorAttributes.DurabilityBonus == 0 ) - ArmorAttributes.DurabilityBonus = 100; + if (ArmorAttributes.DurabilityBonus == 0) + ArmorAttributes.DurabilityBonus = 100; - PoisonBonus = 0; - } - } - } -} + PoisonBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/MidnightBracers.cs b/Scripts/Items/Armor/Artifacts/MidnightBracers.cs index 21d2349d5..21d966368 100644 --- a/Scripts/Items/Armor/Artifacts/MidnightBracers.cs +++ b/Scripts/Items/Armor/Artifacts/MidnightBracers.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class MidnightBracers : BoneArms - { - public override int LabelNumber => 1061093; // Midnight Bracers - public override int ArtifactRarity => 11; + public class MidnightBracers : BoneArms + { + [Constructible] + public MidnightBracers() + { + Hue = 0x455; + SkillBonuses.SetValues(0, SkillName.Necromancy, 20.0); + Attributes.SpellDamage = 10; + ArmorAttributes.MageArmor = 1; + } - public override int BasePhysicalResistance => 23; + public MidnightBracers(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061093; // Midnight Bracers + public override int ArtifactRarity => 11; - [Constructible] - public MidnightBracers() - { - Hue = 0x455; - SkillBonuses.SetValues( 0, SkillName.Necromancy, 20.0 ); - Attributes.SpellDamage = 10; - ArmorAttributes.MageArmor = 1; - } + public override int BasePhysicalResistance => 23; - public MidnightBracers( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - PhysicalBonus = 0; - } - } -} + if (version < 1) + PhysicalBonus = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/OrnateCrownOfTheHarrower.cs b/Scripts/Items/Armor/Artifacts/OrnateCrownOfTheHarrower.cs index 2b7e67344..fe9801e2d 100644 --- a/Scripts/Items/Armor/Artifacts/OrnateCrownOfTheHarrower.cs +++ b/Scripts/Items/Armor/Artifacts/OrnateCrownOfTheHarrower.cs @@ -1,48 +1,48 @@ namespace Server.Items { - public class OrnateCrownOfTheHarrower : BoneHelm - { - public override int LabelNumber => 1061095; // Ornate Crown of the Harrower - public override int ArtifactRarity => 11; + public class OrnateCrownOfTheHarrower : BoneHelm + { + [Constructible] + public OrnateCrownOfTheHarrower() + { + Hue = 0x4F6; + Attributes.RegenHits = 2; + Attributes.RegenStam = 3; + Attributes.WeaponDamage = 25; + } - public override int BasePoisonResistance => 17; + public OrnateCrownOfTheHarrower(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061095; // Ornate Crown of the Harrower + public override int ArtifactRarity => 11; - [Constructible] - public OrnateCrownOfTheHarrower() - { - Hue = 0x4F6; - Attributes.RegenHits = 2; - Attributes.RegenStam = 3; - Attributes.WeaponDamage = 25; - } + public override int BasePoisonResistance => 17; - public OrnateCrownOfTheHarrower( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - if ( Hue == 0x55A ) - Hue = 0x4F6; + if (version < 1) + { + if (Hue == 0x55A) + Hue = 0x4F6; - PoisonBonus = 0; - } - } - } -} + PoisonBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/ShadowDancerLeggings.cs b/Scripts/Items/Armor/Artifacts/ShadowDancerLeggings.cs index fde5ada37..c1596e0e8 100644 --- a/Scripts/Items/Armor/Artifacts/ShadowDancerLeggings.cs +++ b/Scripts/Items/Armor/Artifacts/ShadowDancerLeggings.cs @@ -1,52 +1,52 @@ namespace Server.Items { - public class ShadowDancerLeggings : LeatherLegs - { - public override int LabelNumber => 1061598; // Shadow Dancer Leggings - public override int ArtifactRarity => 11; + public class ShadowDancerLeggings : LeatherLegs + { + [Constructible] + public ShadowDancerLeggings() + { + ItemID = 0x13D2; + Hue = 0x455; + SkillBonuses.SetValues(0, SkillName.Stealth, 20.0); + SkillBonuses.SetValues(1, SkillName.Stealing, 20.0); + } - public override int BasePhysicalResistance => 17; - public override int BasePoisonResistance => 18; - public override int BaseEnergyResistance => 18; + public ShadowDancerLeggings(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061598; // Shadow Dancer Leggings + public override int ArtifactRarity => 11; - [Constructible] - public ShadowDancerLeggings() - { - ItemID = 0x13D2; - Hue = 0x455; - SkillBonuses.SetValues( 0, SkillName.Stealth, 20.0 ); - SkillBonuses.SetValues( 1, SkillName.Stealing, 20.0 ); - } + public override int BasePhysicalResistance => 17; + public override int BasePoisonResistance => 18; + public override int BaseEnergyResistance => 18; - public ShadowDancerLeggings( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - if ( ItemID == 0x13CB ) - ItemID = 0x13D2; + if (version < 1) + { + if (ItemID == 0x13CB) + ItemID = 0x13D2; - PhysicalBonus = 0; - PoisonBonus = 0; - EnergyBonus = 0; - } - } - } -} + PhysicalBonus = 0; + PoisonBonus = 0; + EnergyBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/TunicOfFire.cs b/Scripts/Items/Armor/Artifacts/TunicOfFire.cs index 7d7127a0d..4fae4a1ea 100644 --- a/Scripts/Items/Armor/Artifacts/TunicOfFire.cs +++ b/Scripts/Items/Armor/Artifacts/TunicOfFire.cs @@ -1,53 +1,53 @@ namespace Server.Items { - public class TunicOfFire : ChainChest - { - public override int LabelNumber => 1061099; // Tunic of Fire - public override int ArtifactRarity => 11; + public class TunicOfFire : ChainChest + { + [Constructible] + public TunicOfFire() + { + Hue = 0x54F; + ArmorAttributes.SelfRepair = 5; + Attributes.NightSight = 1; + Attributes.ReflectPhysical = 15; + } - public override int BasePhysicalResistance => 24; - public override int BaseFireResistance => 34; + public TunicOfFire(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061099; // Tunic of Fire + public override int ArtifactRarity => 11; - [Constructible] - public TunicOfFire() - { - Hue = 0x54F; - ArmorAttributes.SelfRepair = 5; - Attributes.NightSight = 1; - Attributes.ReflectPhysical = 15; - } + public override int BasePhysicalResistance => 24; + public override int BaseFireResistance => 34; - public TunicOfFire( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - if ( Hue == 0x54E ) - Hue = 0x54F; + if (version < 1) + { + if (Hue == 0x54E) + Hue = 0x54F; - if ( Attributes.NightSight == 0 ) - Attributes.NightSight = 1; + if (Attributes.NightSight == 0) + Attributes.NightSight = 1; - PhysicalBonus = 0; - FireBonus = 0; - } - } - } -} + PhysicalBonus = 0; + FireBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Artifacts/VoiceOfTheFallenKing.cs b/Scripts/Items/Armor/Artifacts/VoiceOfTheFallenKing.cs index 770ff8618..3ba6bad1a 100644 --- a/Scripts/Items/Armor/Artifacts/VoiceOfTheFallenKing.cs +++ b/Scripts/Items/Armor/Artifacts/VoiceOfTheFallenKing.cs @@ -1,50 +1,50 @@ namespace Server.Items { - public class VoiceOfTheFallenKing : LeatherGorget - { - public override int LabelNumber => 1061094; // Voice of the Fallen King - public override int ArtifactRarity => 11; + public class VoiceOfTheFallenKing : LeatherGorget + { + [Constructible] + public VoiceOfTheFallenKing() + { + Hue = 0x76D; + Attributes.BonusStr = 8; + Attributes.RegenHits = 5; + Attributes.RegenStam = 3; + } - public override int BaseColdResistance => 18; - public override int BaseEnergyResistance => 18; + public VoiceOfTheFallenKing(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061094; // Voice of the Fallen King + public override int ArtifactRarity => 11; - [Constructible] - public VoiceOfTheFallenKing() - { - Hue = 0x76D; - Attributes.BonusStr = 8; - Attributes.RegenHits = 5; - Attributes.RegenStam = 3; - } + public override int BaseColdResistance => 18; + public override int BaseEnergyResistance => 18; - public VoiceOfTheFallenKing( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - if ( Hue == 0x551 ) - Hue = 0x76D; + if (version < 1) + { + if (Hue == 0x551) + Hue = 0x76D; - ColdBonus = 0; - EnergyBonus = 0; - } - } - } -} + ColdBonus = 0; + EnergyBonus = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/BaseArmor.cs b/Scripts/Items/Armor/BaseArmor.cs index 746588f9a..bf6c3785d 100644 --- a/Scripts/Items/Armor/BaseArmor.cs +++ b/Scripts/Items/Armor/BaseArmor.cs @@ -1,1599 +1,1813 @@ using System; using System.Collections.Generic; -using Server.Network; using Server.Engines.Craft; +using Server.Ethics; using Server.Factions; +using Server.Network; using AMA = Server.Items.ArmorMeditationAllowance; using AMT = Server.Items.ArmorMaterialType; using ABT = Server.Items.ArmorBodyType; namespace Server.Items { - public abstract class BaseArmor : Item, IScissorable, IFactionItem, ICraftable, IWearableDurability - { - #region Factions - private FactionItem m_FactionState; - - public FactionItem FactionItemState - { - get => m_FactionState; - set - { - m_FactionState = value; - - if ( m_FactionState == null ) - Hue = CraftResources.GetHue( Resource ); - - LootType = ( m_FactionState == null ? LootType.Regular : LootType.Blessed ); - } - } - #endregion - - - - /* Armor internals work differently now (Jun 19 2003) - * - * The attributes defined below default to -1. - * If the value is -1, the corresponding virtual 'Aos/Old' property is used. - * If not, the attribute value itself is used. Here's the list: - * - ArmorBase - * - StrBonus - * - DexBonus - * - IntBonus - * - StrReq - * - DexReq - * - IntReq - * - MeditationAllowance - */ - - // Instance values. These values must are unique to each armor piece. - private int m_MaxHitPoints; - private int m_HitPoints; - private Mobile m_Crafter; - private ArmorQuality m_Quality; - private ArmorDurabilityLevel m_Durability; - private ArmorProtectionLevel m_Protection; - private CraftResource m_Resource; - private bool m_Identified; - private int m_PhysicalBonus, m_FireBonus, m_ColdBonus, m_PoisonBonus, m_EnergyBonus; - - private AosAttributes m_AosAttributes; - private AosArmorAttributes m_AosArmorAttributes; - private AosSkillBonuses m_AosSkillBonuses; - - // Overridable values. These values are provided to override the defaults which get defined in the individual armor scripts. - private int m_ArmorBase = -1; - private int m_StrBonus = -1, m_DexBonus = -1, m_IntBonus = -1; - private int m_StrReq = -1, m_DexReq = -1, m_IntReq = -1; - private AMA m_Meditate = (AMA)(-1); - - - public virtual bool AllowMaleWearer => true; - public virtual bool AllowFemaleWearer => true; - - public abstract AMT MaterialType{ get; } - - public virtual int RevertArmorBase => ArmorBase; - public virtual int ArmorBase => 0; - - public virtual AMA DefMedAllowance => AMA.None; - public virtual AMA AosMedAllowance => DefMedAllowance; - public virtual AMA OldMedAllowance => DefMedAllowance; - - - public virtual int AosStrBonus => 0; - public virtual int AosDexBonus => 0; - public virtual int AosIntBonus => 0; - public virtual int AosStrReq => 0; - public virtual int AosDexReq => 0; - public virtual int AosIntReq => 0; - - - public virtual int OldStrBonus => 0; - public virtual int OldDexBonus => 0; - public virtual int OldIntBonus => 0; - public virtual int OldStrReq => 0; - public virtual int OldDexReq => 0; - public virtual int OldIntReq => 0; - - public virtual bool CanFortify => true; - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is BaseArmor armor) ) - return; - - armor.m_AosAttributes = new AosAttributes( newItem, m_AosAttributes ); - armor.m_AosArmorAttributes = new AosArmorAttributes( newItem, m_AosArmorAttributes ); - armor.m_AosSkillBonuses = new AosSkillBonuses( newItem, m_AosSkillBonuses ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public AMA MeditationAllowance - { - get => ( m_Meditate == (AMA)(-1) ? Core.AOS ? AosMedAllowance : OldMedAllowance : m_Meditate ); - set => m_Meditate = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BaseArmorRating - { - get - { - if ( m_ArmorBase == -1 ) - return ArmorBase; - return m_ArmorBase; - } - set - { - m_ArmorBase = value; Invalidate(); - } - } - - public double BaseArmorRatingScaled => ( BaseArmorRating * ArmorScalar ); - - public virtual double ArmorRating - { - get - { - int ar = BaseArmorRating; - - if ( m_Protection != ArmorProtectionLevel.Regular ) - ar += 10 + (5 * (int)m_Protection); - - switch ( m_Resource ) - { - case CraftResource.DullCopper: ar += 2; break; - case CraftResource.ShadowIron: ar += 4; break; - case CraftResource.Copper: ar += 6; break; - case CraftResource.Bronze: ar += 8; break; - case CraftResource.Gold: ar += 10; break; - case CraftResource.Agapite: ar += 12; break; - case CraftResource.Verite: ar += 14; break; - case CraftResource.Valorite: ar += 16; break; - case CraftResource.SpinedLeather: ar += 10; break; - case CraftResource.HornedLeather: ar += 13; break; - case CraftResource.BarbedLeather: ar += 16; break; - } - - ar += -8 + (8 * (int)m_Quality); - return ScaleArmorByDurability( ar ); - } - } - - public double ArmorRatingScaled => ( ArmorRating * ArmorScalar ); - - [CommandProperty( AccessLevel.GameMaster )] - public int StrBonus - { - get => ( m_StrBonus == -1 ? Core.AOS ? AosStrBonus : OldStrBonus : m_StrBonus ); - set{ m_StrBonus = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DexBonus - { - get => ( m_DexBonus == -1 ? Core.AOS ? AosDexBonus : OldDexBonus : m_DexBonus ); - set{ m_DexBonus = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int IntBonus - { - get => ( m_IntBonus == -1 ? Core.AOS ? AosIntBonus : OldIntBonus : m_IntBonus ); - set{ m_IntBonus = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int StrRequirement - { - get => ( m_StrReq == -1 ? Core.AOS ? AosStrReq : OldStrReq : m_StrReq ); - set{ m_StrReq = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DexRequirement - { - get => ( m_DexReq == -1 ? Core.AOS ? AosDexReq : OldDexReq : m_DexReq ); - set{ m_DexReq = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int IntRequirement - { - get => ( m_IntReq == -1 ? Core.AOS ? AosIntReq : OldIntReq : m_IntReq ); - set{ m_IntReq = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Identified - { - get => m_Identified; - set{ m_Identified = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool PlayerConstructed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set - { - if ( m_Resource != value ) - { - UnscaleDurability(); - - m_Resource = value; - - if ( CraftItem.RetainsColor( GetType() ) ) - { - Hue = CraftResources.GetHue(m_Resource); - } - - Invalidate(); - InvalidateProperties(); - - (Parent as Mobile)?.UpdateResistances(); - - ScaleDurability(); - } - } - } - - public virtual double ArmorScalar - { - get - { - int pos = (int)BodyPosition; - - if ( pos >= 0 && pos < ArmorScalars.Length ) - return ArmorScalars[pos]; - - return 1.0; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxHitPoints - { - get => m_MaxHitPoints; - set{ m_MaxHitPoints = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitPoints - { - get => m_HitPoints; - set - { - if ( value != m_HitPoints && MaxHitPoints > 0 ) - { - m_HitPoints = value; - - if ( m_HitPoints < 0 ) - Delete(); - else if ( m_HitPoints > MaxHitPoints ) - m_HitPoints = MaxHitPoints; - - InvalidateProperties(); - } - } - } - - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } - - - [CommandProperty( AccessLevel.GameMaster )] - public ArmorQuality Quality - { - get => m_Quality; - set{ UnscaleDurability(); m_Quality = value; Invalidate(); InvalidateProperties(); ScaleDurability(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public ArmorDurabilityLevel Durability - { - get => m_Durability; - set{ UnscaleDurability(); m_Durability = value; ScaleDurability(); InvalidateProperties(); } - } - - public virtual int ArtifactRarity => 0; - - [CommandProperty( AccessLevel.GameMaster )] - public ArmorProtectionLevel ProtectionLevel - { - get => m_Protection; - set - { - if ( m_Protection != value ) - { - m_Protection = value; - - Invalidate(); - InvalidateProperties(); - - (Parent as Mobile)?.UpdateResistances(); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosAttributes Attributes - { - get => m_AosAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosArmorAttributes ArmorAttributes - { - get => m_AosArmorAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosSkillBonuses SkillBonuses - { - get => m_AosSkillBonuses; - set{} - } - - public int ComputeStatReq( StatType type ) - { - int v; - - if ( type == StatType.Str ) - v = StrRequirement; - else if ( type == StatType.Dex ) - v = DexRequirement; - else - v = IntRequirement; - - return AOS.Scale( v, 100 - GetLowerStatReq() ); - } - - public int ComputeStatBonus( StatType type ) - { - if ( type == StatType.Str ) - return StrBonus + Attributes.BonusStr; - if ( type == StatType.Dex ) - return DexBonus + Attributes.BonusDex; - return IntBonus + Attributes.BonusInt; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int PhysicalBonus{ get => m_PhysicalBonus; - set{ m_PhysicalBonus = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int FireBonus{ get => m_FireBonus; - set{ m_FireBonus = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int ColdBonus{ get => m_ColdBonus; - set{ m_ColdBonus = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonBonus{ get => m_PoisonBonus; - set{ m_PoisonBonus = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int EnergyBonus{ get => m_EnergyBonus; - set{ m_EnergyBonus = value; InvalidateProperties(); } } - - public virtual int BasePhysicalResistance => 0; - public virtual int BaseFireResistance => 0; - public virtual int BaseColdResistance => 0; - public virtual int BasePoisonResistance => 0; - public virtual int BaseEnergyResistance => 0; - - public override int PhysicalResistance => BasePhysicalResistance + GetProtOffset() + GetResourceAttrs().ArmorPhysicalResist + m_PhysicalBonus; - public override int FireResistance => BaseFireResistance + GetProtOffset() + GetResourceAttrs().ArmorFireResist + m_FireBonus; - public override int ColdResistance => BaseColdResistance + GetProtOffset() + GetResourceAttrs().ArmorColdResist + m_ColdBonus; - public override int PoisonResistance => BasePoisonResistance + GetProtOffset() + GetResourceAttrs().ArmorPoisonResist + m_PoisonBonus; - public override int EnergyResistance => BaseEnergyResistance + GetProtOffset() + GetResourceAttrs().ArmorEnergyResist + m_EnergyBonus; - - public virtual int InitMinHits => 0; - public virtual int InitMaxHits => 0; - - [CommandProperty( AccessLevel.GameMaster )] - public ArmorBodyType BodyPosition - { - get - { - switch ( Layer ) - { - default: - case Layer.Neck: return ArmorBodyType.Gorget; - case Layer.TwoHanded: return ArmorBodyType.Shield; - case Layer.Gloves: return ArmorBodyType.Gloves; - case Layer.Helm: return ArmorBodyType.Helmet; - case Layer.Arms: return ArmorBodyType.Arms; - - case Layer.InnerLegs: - case Layer.OuterLegs: - case Layer.Pants: return ArmorBodyType.Legs; - - case Layer.InnerTorso: - case Layer.OuterTorso: - case Layer.Shirt: return ArmorBodyType.Chest; - } - } - } - - public void DistributeBonuses( int amount ) - { - for ( int i = 0; i < amount; ++i ) - { - switch ( Utility.Random( 5 ) ) - { - case 0: ++m_PhysicalBonus; break; - case 1: ++m_FireBonus; break; - case 2: ++m_ColdBonus; break; - case 3: ++m_PoisonBonus; break; - case 4: ++m_EnergyBonus; break; - } - } - - InvalidateProperties(); - } - - public CraftAttributeInfo GetResourceAttrs() - { - CraftResourceInfo info = CraftResources.GetInfo( m_Resource ); - - if ( info == null ) - return CraftAttributeInfo.Blank; - - return info.AttributeInfo; - } - - public int GetProtOffset() - { - switch ( m_Protection ) - { - case ArmorProtectionLevel.Guarding: return 1; - case ArmorProtectionLevel.Hardening: return 2; - case ArmorProtectionLevel.Fortification: return 3; - case ArmorProtectionLevel.Invulnerability: return 4; - } - - return 0; - } - - public void UnscaleDurability() - { - int scale = 100 + GetDurabilityBonus(); - - m_HitPoints = ((m_HitPoints * 100) + (scale - 1)) / scale; - m_MaxHitPoints = ((m_MaxHitPoints * 100) + (scale - 1)) / scale; - InvalidateProperties(); - } - - public void ScaleDurability() - { - int scale = 100 + GetDurabilityBonus(); - - m_HitPoints = ((m_HitPoints * scale) + 99) / 100; - m_MaxHitPoints = ((m_MaxHitPoints * scale) + 99) / 100; - InvalidateProperties(); - } - - public int GetDurabilityBonus() - { - int bonus = 0; - - if ( m_Quality == ArmorQuality.Exceptional ) - bonus += 20; - - switch ( m_Durability ) - { - case ArmorDurabilityLevel.Durable: bonus += 20; break; - case ArmorDurabilityLevel.Substantial: bonus += 50; break; - case ArmorDurabilityLevel.Massive: bonus += 70; break; - case ArmorDurabilityLevel.Fortified: bonus += 100; break; - case ArmorDurabilityLevel.Indestructible: bonus += 120; break; - } - - if ( Core.AOS ) - { - bonus += m_AosArmorAttributes.DurabilityBonus; - - CraftResourceInfo resInfo = CraftResources.GetInfo( m_Resource ); - CraftAttributeInfo attrInfo = null; - - if ( resInfo != null ) - attrInfo = resInfo.AttributeInfo; - - if ( attrInfo != null ) - bonus += attrInfo.ArmorDurability; - } - - return bonus; - } - - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 502437 ); // Items you wish to cut must be in your backpack. - return false; - } - - if ( Ethics.Ethic.IsImbued( this ) ) - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } - - CraftSystem system = DefTailoring.CraftSystem; - - CraftItem item = system.CraftItems.SearchFor( GetType() ); - - if ( item != null && item.Resources.Count == 1 && item.Resources.GetAt( 0 ).Amount >= 2 ) - { - try - { - Item res = (Item)Activator.CreateInstance( CraftResources.GetInfo( m_Resource ).ResourceTypes[0] ); - - ScissorHelper( from, res, PlayerConstructed ? (item.Resources.GetAt( 0 ).Amount / 2) : 1 ); - return true; - } - catch - { - } - } - - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } - - public static double[] ArmorScalars { get; set; } = { 0.07, 0.07, 0.14, 0.15, 0.22, 0.35 }; - - public static void ValidateMobile( Mobile m ) - { - for ( int i = m.Items.Count - 1; i >= 0; --i ) - { - if ( i >= m.Items.Count ) - continue; - - Item item = m.Items[i]; - - if ( item is BaseArmor armor ) - { - if ( armor.RequiredRace != null && m.Race != armor.RequiredRace ) - { - if ( armor.RequiredRace == Race.Elf ) - m.SendLocalizedMessage( 1072203 ); // Only Elves may use this. - else - m.SendMessage( "Only {0} may use this.", armor.RequiredRace.PluralName ); - - m.AddToBackpack( armor ); - } - else if ( !armor.AllowMaleWearer && !m.Female && m.AccessLevel < AccessLevel.GameMaster ) - { - if ( armor.AllowFemaleWearer ) - m.SendLocalizedMessage( 1010388 ); // Only females can wear this. - else - m.SendMessage( "You may not wear this." ); - - m.AddToBackpack( armor ); - } - else if ( !armor.AllowFemaleWearer && m.Female && m.AccessLevel < AccessLevel.GameMaster ) - { - if ( armor.AllowMaleWearer ) - m.SendLocalizedMessage( 1063343 ); // Only males can wear this. - else - m.SendMessage( "You may not wear this." ); - - m.AddToBackpack( armor ); - } - } - } - } - - public int GetLowerStatReq() - { - if ( !Core.AOS ) - return 0; - - int v = m_AosArmorAttributes.LowerStatReq; - - CraftResourceInfo info = CraftResources.GetInfo( m_Resource ); - - CraftAttributeInfo attrInfo = info?.AttributeInfo; - - if ( attrInfo != null ) - v += attrInfo.ArmorLowerRequirements; - - if ( v > 100 ) - v = 100; - - return v; - } - - public override void OnAdded(IEntity parent) - { - if ( parent is Mobile from ) - { - if ( Core.AOS ) - m_AosSkillBonuses.AddTo( from ); - - from.Delta( MobileDelta.Armor ); // Tell them armor rating has changed - } - } - - public virtual double ScaleArmorByDurability( double armor ) - { - int scale = 100; - - if ( m_MaxHitPoints > 0 && m_HitPoints < m_MaxHitPoints ) - scale = 50 + ((50 * m_HitPoints) / m_MaxHitPoints); - - return ( armor * scale ) / 100; - } - - protected void Invalidate() - { - (Parent as Mobile)?.Delta( MobileDelta.Armor ); // Tell them armor rating has changed - } - - public BaseArmor( Serial serial ) : base( serial ) - { - } - - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } - - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } - - [Flags] - private enum SaveFlag - { - None = 0x00000000, - Attributes = 0x00000001, - ArmorAttributes = 0x00000002, - PhysicalBonus = 0x00000004, - FireBonus = 0x00000008, - ColdBonus = 0x00000010, - PoisonBonus = 0x00000020, - EnergyBonus = 0x00000040, - Identified = 0x00000080, - MaxHitPoints = 0x00000100, - HitPoints = 0x00000200, - Crafter = 0x00000400, - Quality = 0x00000800, - Durability = 0x00001000, - Protection = 0x00002000, - Resource = 0x00004000, - BaseArmor = 0x00008000, - StrBonus = 0x00010000, - DexBonus = 0x00020000, - IntBonus = 0x00040000, - StrReq = 0x00080000, - DexReq = 0x00100000, - IntReq = 0x00200000, - MedAllowance = 0x00400000, - SkillBonuses = 0x00800000, - PlayerConstructed = 0x01000000 - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 7 ); // version - - SaveFlag flags = SaveFlag.None; - - SetSaveFlag( ref flags, SaveFlag.Attributes, !m_AosAttributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.ArmorAttributes, !m_AosArmorAttributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.PhysicalBonus, m_PhysicalBonus != 0 ); - SetSaveFlag( ref flags, SaveFlag.FireBonus, m_FireBonus != 0 ); - SetSaveFlag( ref flags, SaveFlag.ColdBonus, m_ColdBonus != 0 ); - SetSaveFlag( ref flags, SaveFlag.PoisonBonus, m_PoisonBonus != 0 ); - SetSaveFlag( ref flags, SaveFlag.EnergyBonus, m_EnergyBonus != 0 ); - SetSaveFlag( ref flags, SaveFlag.Identified, m_Identified != false ); - SetSaveFlag( ref flags, SaveFlag.MaxHitPoints, m_MaxHitPoints != 0 ); - SetSaveFlag( ref flags, SaveFlag.HitPoints, m_HitPoints != 0 ); - SetSaveFlag( ref flags, SaveFlag.Crafter, m_Crafter != null ); - SetSaveFlag( ref flags, SaveFlag.Quality, m_Quality != ArmorQuality.Regular ); - SetSaveFlag( ref flags, SaveFlag.Durability, m_Durability != ArmorDurabilityLevel.Regular ); - SetSaveFlag( ref flags, SaveFlag.Protection, m_Protection != ArmorProtectionLevel.Regular ); - SetSaveFlag( ref flags, SaveFlag.Resource, m_Resource != DefaultResource ); - SetSaveFlag( ref flags, SaveFlag.BaseArmor, m_ArmorBase != -1 ); - SetSaveFlag( ref flags, SaveFlag.StrBonus, m_StrBonus != -1 ); - SetSaveFlag( ref flags, SaveFlag.DexBonus, m_DexBonus != -1 ); - SetSaveFlag( ref flags, SaveFlag.IntBonus, m_IntBonus != -1 ); - SetSaveFlag( ref flags, SaveFlag.StrReq, m_StrReq != -1 ); - SetSaveFlag( ref flags, SaveFlag.DexReq, m_DexReq != -1 ); - SetSaveFlag( ref flags, SaveFlag.IntReq, m_IntReq != -1 ); - SetSaveFlag( ref flags, SaveFlag.MedAllowance, m_Meditate != (AMA)(-1) ); - SetSaveFlag( ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.PlayerConstructed, PlayerConstructed != false ); - - writer.WriteEncodedInt( (int) flags ); - - if ( GetSaveFlag( flags, SaveFlag.Attributes ) ) - m_AosAttributes.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.ArmorAttributes ) ) - m_AosArmorAttributes.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.PhysicalBonus ) ) - writer.WriteEncodedInt( (int) m_PhysicalBonus ); - - if ( GetSaveFlag( flags, SaveFlag.FireBonus ) ) - writer.WriteEncodedInt( (int) m_FireBonus ); - - if ( GetSaveFlag( flags, SaveFlag.ColdBonus ) ) - writer.WriteEncodedInt( (int) m_ColdBonus ); - - if ( GetSaveFlag( flags, SaveFlag.PoisonBonus ) ) - writer.WriteEncodedInt( (int) m_PoisonBonus ); - - if ( GetSaveFlag( flags, SaveFlag.EnergyBonus ) ) - writer.WriteEncodedInt( (int) m_EnergyBonus ); - - if ( GetSaveFlag( flags, SaveFlag.MaxHitPoints ) ) - writer.WriteEncodedInt( (int) m_MaxHitPoints ); - - if ( GetSaveFlag( flags, SaveFlag.HitPoints ) ) - writer.WriteEncodedInt( (int) m_HitPoints ); - - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - writer.Write( (Mobile) m_Crafter ); - - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - writer.WriteEncodedInt( (int) m_Quality ); - - if ( GetSaveFlag( flags, SaveFlag.Durability ) ) - writer.WriteEncodedInt( (int) m_Durability ); - - if ( GetSaveFlag( flags, SaveFlag.Protection ) ) - writer.WriteEncodedInt( (int) m_Protection ); - - if ( GetSaveFlag( flags, SaveFlag.Resource ) ) - writer.WriteEncodedInt( (int) m_Resource ); - - if ( GetSaveFlag( flags, SaveFlag.BaseArmor ) ) - writer.WriteEncodedInt( (int) m_ArmorBase ); - - if ( GetSaveFlag( flags, SaveFlag.StrBonus ) ) - writer.WriteEncodedInt( (int) m_StrBonus ); - - if ( GetSaveFlag( flags, SaveFlag.DexBonus ) ) - writer.WriteEncodedInt( (int) m_DexBonus ); + public abstract class BaseArmor : Item, IScissorable, IFactionItem, ICraftable, IWearableDurability + { + private AosArmorAttributes m_AosArmorAttributes; + + private AosAttributes m_AosAttributes; + private AosSkillBonuses m_AosSkillBonuses; + + // Overridable values. These values are provided to override the defaults which get defined in the individual armor scripts. + private int m_ArmorBase = -1; + private Mobile m_Crafter; + private ArmorDurabilityLevel m_Durability; + private int m_HitPoints; + private bool m_Identified; + + + /* Armor internals work differently now (Jun 19 2003) + * + * The attributes defined below default to -1. + * If the value is -1, the corresponding virtual 'Aos/Old' property is used. + * If not, the attribute value itself is used. Here's the list: + * - ArmorBase + * - StrBonus + * - DexBonus + * - IntBonus + * - StrReq + * - DexReq + * - IntReq + * - MeditationAllowance + */ + + // Instance values. These values must are unique to each armor piece. + private int m_MaxHitPoints; + private AMA m_Meditate = (AMA)(-1); + private int m_PhysicalBonus, m_FireBonus, m_ColdBonus, m_PoisonBonus, m_EnergyBonus; + private ArmorProtectionLevel m_Protection; + private ArmorQuality m_Quality; + private CraftResource m_Resource; + private int m_StrBonus = -1, m_DexBonus = -1, m_IntBonus = -1; + private int m_StrReq = -1, m_DexReq = -1, m_IntReq = -1; + + public BaseArmor(Serial serial) : base(serial) + { + } + + public BaseArmor(int itemID) : base(itemID) + { + m_Quality = ArmorQuality.Regular; + m_Durability = ArmorDurabilityLevel.Regular; + m_Crafter = null; + + m_Resource = DefaultResource; + Hue = CraftResources.GetHue(m_Resource); + + m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax(InitMinHits, InitMaxHits); + + Layer = (Layer)ItemData.Quality; + + m_AosAttributes = new AosAttributes(this); + m_AosArmorAttributes = new AosArmorAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + } + + + public virtual bool AllowMaleWearer => true; + public virtual bool AllowFemaleWearer => true; + + public abstract AMT MaterialType{ get; } + + public virtual int RevertArmorBase => ArmorBase; + public virtual int ArmorBase => 0; + + public virtual AMA DefMedAllowance => AMA.None; + public virtual AMA AosMedAllowance => DefMedAllowance; + public virtual AMA OldMedAllowance => DefMedAllowance; + + + public virtual int AosStrBonus => 0; + public virtual int AosDexBonus => 0; + public virtual int AosIntBonus => 0; + public virtual int AosStrReq => 0; + public virtual int AosDexReq => 0; + public virtual int AosIntReq => 0; + + + public virtual int OldStrBonus => 0; + public virtual int OldDexBonus => 0; + public virtual int OldIntBonus => 0; + public virtual int OldStrReq => 0; + public virtual int OldDexReq => 0; + public virtual int OldIntReq => 0; + + [CommandProperty(AccessLevel.GameMaster)] + public AMA MeditationAllowance + { + get => m_Meditate == (AMA)(-1) ? Core.AOS ? AosMedAllowance : OldMedAllowance : m_Meditate; + set => m_Meditate = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BaseArmorRating + { + get + { + if (m_ArmorBase == -1) + return ArmorBase; + return m_ArmorBase; + } + set + { + m_ArmorBase = value; + Invalidate(); + } + } + + public double BaseArmorRatingScaled => BaseArmorRating * ArmorScalar; + + public virtual double ArmorRating + { + get + { + int ar = BaseArmorRating; + + if (m_Protection != ArmorProtectionLevel.Regular) + ar += 10 + 5 * (int)m_Protection; + + switch (m_Resource) + { + case CraftResource.DullCopper: + ar += 2; + break; + case CraftResource.ShadowIron: + ar += 4; + break; + case CraftResource.Copper: + ar += 6; + break; + case CraftResource.Bronze: + ar += 8; + break; + case CraftResource.Gold: + ar += 10; + break; + case CraftResource.Agapite: + ar += 12; + break; + case CraftResource.Verite: + ar += 14; + break; + case CraftResource.Valorite: + ar += 16; + break; + case CraftResource.SpinedLeather: + ar += 10; + break; + case CraftResource.HornedLeather: + ar += 13; + break; + case CraftResource.BarbedLeather: + ar += 16; + break; + } + + ar += -8 + 8 * (int)m_Quality; + return ScaleArmorByDurability(ar); + } + } + + public double ArmorRatingScaled => ArmorRating * ArmorScalar; + + [CommandProperty(AccessLevel.GameMaster)] + public int StrBonus + { + get => m_StrBonus == -1 ? Core.AOS ? AosStrBonus : OldStrBonus : m_StrBonus; + set + { + m_StrBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DexBonus + { + get => m_DexBonus == -1 ? Core.AOS ? AosDexBonus : OldDexBonus : m_DexBonus; + set + { + m_DexBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int IntBonus + { + get => m_IntBonus == -1 ? Core.AOS ? AosIntBonus : OldIntBonus : m_IntBonus; + set + { + m_IntBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int StrRequirement + { + get => m_StrReq == -1 ? Core.AOS ? AosStrReq : OldStrReq : m_StrReq; + set + { + m_StrReq = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DexRequirement + { + get => m_DexReq == -1 ? Core.AOS ? AosDexReq : OldDexReq : m_DexReq; + set + { + m_DexReq = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int IntRequirement + { + get => m_IntReq == -1 ? Core.AOS ? AosIntReq : OldIntReq : m_IntReq; + set + { + m_IntReq = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Identified + { + get => m_Identified; + set + { + m_Identified = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool PlayerConstructed{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + if (m_Resource != value) + { + UnscaleDurability(); + + m_Resource = value; + + if (CraftItem.RetainsColor(GetType())) Hue = CraftResources.GetHue(m_Resource); + + Invalidate(); + InvalidateProperties(); + + (Parent as Mobile)?.UpdateResistances(); + + ScaleDurability(); + } + } + } + + public virtual double ArmorScalar + { + get + { + int pos = (int)BodyPosition; + + if (pos >= 0 && pos < ArmorScalars.Length) + return ArmorScalars[pos]; + + return 1.0; + } + } + + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + + [CommandProperty(AccessLevel.GameMaster)] + public ArmorQuality Quality + { + get => m_Quality; + set + { + UnscaleDurability(); + m_Quality = value; + Invalidate(); + InvalidateProperties(); + ScaleDurability(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public ArmorDurabilityLevel Durability + { + get => m_Durability; + set + { + UnscaleDurability(); + m_Durability = value; + ScaleDurability(); + InvalidateProperties(); + } + } + + public virtual int ArtifactRarity => 0; + + [CommandProperty(AccessLevel.GameMaster)] + public ArmorProtectionLevel ProtectionLevel + { + get => m_Protection; + set + { + if (m_Protection != value) + { + m_Protection = value; + + Invalidate(); + InvalidateProperties(); + + (Parent as Mobile)?.UpdateResistances(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosAttributes Attributes + { + get => m_AosAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosArmorAttributes ArmorAttributes + { + get => m_AosArmorAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosSkillBonuses SkillBonuses + { + get => m_AosSkillBonuses; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int PhysicalBonus + { + get => m_PhysicalBonus; + set + { + m_PhysicalBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int FireBonus + { + get => m_FireBonus; + set + { + m_FireBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ColdBonus + { + get => m_ColdBonus; + set + { + m_ColdBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonBonus + { + get => m_PoisonBonus; + set + { + m_PoisonBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int EnergyBonus + { + get => m_EnergyBonus; + set + { + m_EnergyBonus = value; + InvalidateProperties(); + } + } + + public virtual int BasePhysicalResistance => 0; + public virtual int BaseFireResistance => 0; + public virtual int BaseColdResistance => 0; + public virtual int BasePoisonResistance => 0; + public virtual int BaseEnergyResistance => 0; + + public override int PhysicalResistance => BasePhysicalResistance + GetProtOffset() + + GetResourceAttrs().ArmorPhysicalResist + m_PhysicalBonus; + + public override int FireResistance => + BaseFireResistance + GetProtOffset() + GetResourceAttrs().ArmorFireResist + m_FireBonus; + + public override int ColdResistance => + BaseColdResistance + GetProtOffset() + GetResourceAttrs().ArmorColdResist + m_ColdBonus; + + public override int PoisonResistance => + BasePoisonResistance + GetProtOffset() + GetResourceAttrs().ArmorPoisonResist + m_PoisonBonus; + + public override int EnergyResistance => + BaseEnergyResistance + GetProtOffset() + GetResourceAttrs().ArmorEnergyResist + m_EnergyBonus; + + [CommandProperty(AccessLevel.GameMaster)] + public ArmorBodyType BodyPosition + { + get + { + switch (Layer) + { + default: + case Layer.Neck: return ArmorBodyType.Gorget; + case Layer.TwoHanded: return ArmorBodyType.Shield; + case Layer.Gloves: return ArmorBodyType.Gloves; + case Layer.Helm: return ArmorBodyType.Helmet; + case Layer.Arms: return ArmorBodyType.Arms; + + case Layer.InnerLegs: + case Layer.OuterLegs: + case Layer.Pants: return ArmorBodyType.Legs; + + case Layer.InnerTorso: + case Layer.OuterTorso: + case Layer.Shirt: return ArmorBodyType.Chest; + } + } + } + + public static double[] ArmorScalars{ get; set; } = { 0.07, 0.07, 0.14, 0.15, 0.22, 0.35 }; + + public virtual CraftResource DefaultResource => CraftResource.Iron; + + public virtual Race RequiredRace => null; + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + InvalidateProperties(); + } + } + + #region ICraftable Members + + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Quality = (ArmorQuality)quality; + + if (makersMark) + Crafter = from; + + Type resourceType = typeRes; + + if (resourceType == null) + resourceType = craftItem.Resources.GetAt(0).ItemType; + + Resource = CraftResources.GetFromType(resourceType); + PlayerConstructed = true; + + CraftContext context = craftSystem.GetContext(from); + + if (context != null && context.DoNotColor) + Hue = 0; + + if (Quality == ArmorQuality.Exceptional) + { + if (!(Core.ML && this is BaseShield) + ) // Guessed Core.ML removed exceptional resist bonuses from crafted shields + DistributeBonuses(tool is BaseRunicTool ? 6 : + Core.SE ? 15 : 14); // Not sure since when, but right now 15 points are added, not 14. + + if (Core.ML && !(this is BaseShield)) + { + int bonus = (int)(from.Skills.ArmsLore.Value / 20); + + for (int i = 0; i < bonus; i++) + switch (Utility.Random(5)) + { + case 0: + m_PhysicalBonus++; + break; + case 1: + m_FireBonus++; + break; + case 2: + m_ColdBonus++; + break; + case 3: + m_EnergyBonus++; + break; + case 4: + m_PoisonBonus++; + break; + } + + from.CheckSkill(SkillName.ArmsLore, 0, 100); + } + } + + if (Core.AOS) + (tool as BaseRunicTool)?.ApplyAttributesTo(this); + + return quality; + } + + #endregion + + public bool Scissor(Mobile from, Scissors scissors) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502437); // Items you wish to cut must be in your backpack. + return false; + } + + if (Ethic.IsImbued(this)) + { + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } + + CraftSystem system = DefTailoring.CraftSystem; + + CraftItem item = system.CraftItems.SearchFor(GetType()); + + if (item != null && item.Resources.Count == 1 && item.Resources.GetAt(0).Amount >= 2) + try + { + Item res = (Item)Activator.CreateInstance(CraftResources.GetInfo(m_Resource).ResourceTypes[0]); + + ScissorHelper(from, res, PlayerConstructed ? item.Resources.GetAt(0).Amount / 2 : 1); + return true; + } + catch + { + } + + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } + + public virtual bool CanFortify => true; + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxHitPoints + { + get => m_MaxHitPoints; + set + { + m_MaxHitPoints = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitPoints + { + get => m_HitPoints; + set + { + if (value != m_HitPoints && MaxHitPoints > 0) + { + m_HitPoints = value; + + if (m_HitPoints < 0) + Delete(); + else if (m_HitPoints > MaxHitPoints) + m_HitPoints = MaxHitPoints; + + InvalidateProperties(); + } + } + } + + public virtual int InitMinHits => 0; + public virtual int InitMaxHits => 0; + + public void UnscaleDurability() + { + int scale = 100 + GetDurabilityBonus(); + + m_HitPoints = (m_HitPoints * 100 + (scale - 1)) / scale; + m_MaxHitPoints = (m_MaxHitPoints * 100 + (scale - 1)) / scale; + InvalidateProperties(); + } + + public void ScaleDurability() + { + int scale = 100 + GetDurabilityBonus(); + + m_HitPoints = (m_HitPoints * scale + 99) / 100; + m_MaxHitPoints = (m_MaxHitPoints * scale + 99) / 100; + InvalidateProperties(); + } + + public virtual int OnHit(BaseWeapon weapon, int damageTaken) + { + double halfar = ArmorRating / 2.0; + int absorbed = (int)(halfar + halfar * Utility.RandomDouble()); + + damageTaken -= absorbed; + if (damageTaken < 0) + damageTaken = 0; + + if (absorbed < 2) + absorbed = 2; + + if (25 > Utility.Random(100)) // 25% chance to lower durability + { + if (Core.AOS && m_AosArmorAttributes.SelfRepair > Utility.Random(10)) + { + HitPoints += 2; + } + else + { + int wear; + + if (weapon.Type == WeaponType.Bashing) + wear = absorbed / 2; + else + wear = Utility.Random(2); + + if (wear > 0 && m_MaxHitPoints > 0) + { + if (m_HitPoints >= wear) + { + HitPoints -= wear; + wear = 0; + } + else + { + wear -= HitPoints; + HitPoints = 0; + } + + if (wear > 0) + { + if (m_MaxHitPoints > wear) + { + MaxHitPoints -= wear; + + if (Parent is Mobile mobile) + mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061121); // Your equipment is severely damaged. + } + else + { + Delete(); + } + } + } + } + } + + return damageTaken; + } + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is BaseArmor armor)) + return; + + armor.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); + armor.m_AosArmorAttributes = new AosArmorAttributes(newItem, m_AosArmorAttributes); + armor.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); + } + + public int ComputeStatReq(StatType type) + { + int v; + + if (type == StatType.Str) + v = StrRequirement; + else if (type == StatType.Dex) + v = DexRequirement; + else + v = IntRequirement; + + return AOS.Scale(v, 100 - GetLowerStatReq()); + } + + public int ComputeStatBonus(StatType type) + { + if (type == StatType.Str) + return StrBonus + Attributes.BonusStr; + if (type == StatType.Dex) + return DexBonus + Attributes.BonusDex; + return IntBonus + Attributes.BonusInt; + } + + public void DistributeBonuses(int amount) + { + for (int i = 0; i < amount; ++i) + switch (Utility.Random(5)) + { + case 0: + ++m_PhysicalBonus; + break; + case 1: + ++m_FireBonus; + break; + case 2: + ++m_ColdBonus; + break; + case 3: + ++m_PoisonBonus; + break; + case 4: + ++m_EnergyBonus; + break; + } + + InvalidateProperties(); + } + + public CraftAttributeInfo GetResourceAttrs() + { + CraftResourceInfo info = CraftResources.GetInfo(m_Resource); + + if (info == null) + return CraftAttributeInfo.Blank; + + return info.AttributeInfo; + } + + public int GetProtOffset() + { + switch (m_Protection) + { + case ArmorProtectionLevel.Guarding: return 1; + case ArmorProtectionLevel.Hardening: return 2; + case ArmorProtectionLevel.Fortification: return 3; + case ArmorProtectionLevel.Invulnerability: return 4; + } + + return 0; + } + + public int GetDurabilityBonus() + { + int bonus = 0; + + if (m_Quality == ArmorQuality.Exceptional) + bonus += 20; + + switch (m_Durability) + { + case ArmorDurabilityLevel.Durable: + bonus += 20; + break; + case ArmorDurabilityLevel.Substantial: + bonus += 50; + break; + case ArmorDurabilityLevel.Massive: + bonus += 70; + break; + case ArmorDurabilityLevel.Fortified: + bonus += 100; + break; + case ArmorDurabilityLevel.Indestructible: + bonus += 120; + break; + } + + if (Core.AOS) + { + bonus += m_AosArmorAttributes.DurabilityBonus; + + CraftResourceInfo resInfo = CraftResources.GetInfo(m_Resource); + CraftAttributeInfo attrInfo = null; + + if (resInfo != null) + attrInfo = resInfo.AttributeInfo; + + if (attrInfo != null) + bonus += attrInfo.ArmorDurability; + } + + return bonus; + } + + public static void ValidateMobile(Mobile m) + { + for (int i = m.Items.Count - 1; i >= 0; --i) + { + if (i >= m.Items.Count) + continue; + + Item item = m.Items[i]; + + if (item is BaseArmor armor) + { + if (armor.RequiredRace != null && m.Race != armor.RequiredRace) + { + if (armor.RequiredRace == Race.Elf) + m.SendLocalizedMessage(1072203); // Only Elves may use this. + else + m.SendMessage("Only {0} may use this.", armor.RequiredRace.PluralName); + + m.AddToBackpack(armor); + } + else if (!armor.AllowMaleWearer && !m.Female && m.AccessLevel < AccessLevel.GameMaster) + { + if (armor.AllowFemaleWearer) + m.SendLocalizedMessage(1010388); // Only females can wear this. + else + m.SendMessage("You may not wear this."); + + m.AddToBackpack(armor); + } + else if (!armor.AllowFemaleWearer && m.Female && m.AccessLevel < AccessLevel.GameMaster) + { + if (armor.AllowMaleWearer) + m.SendLocalizedMessage(1063343); // Only males can wear this. + else + m.SendMessage("You may not wear this."); + + m.AddToBackpack(armor); + } + } + } + } + + public int GetLowerStatReq() + { + if (!Core.AOS) + return 0; + + int v = m_AosArmorAttributes.LowerStatReq; + + CraftResourceInfo info = CraftResources.GetInfo(m_Resource); + + CraftAttributeInfo attrInfo = info?.AttributeInfo; + + if (attrInfo != null) + v += attrInfo.ArmorLowerRequirements; + + if (v > 100) + v = 100; + + return v; + } + + public override void OnAdded(IEntity parent) + { + if (parent is Mobile from) + { + if (Core.AOS) + m_AosSkillBonuses.AddTo(from); + + from.Delta(MobileDelta.Armor); // Tell them armor rating has changed + } + } + + public virtual double ScaleArmorByDurability(double armor) + { + int scale = 100; + + if (m_MaxHitPoints > 0 && m_HitPoints < m_MaxHitPoints) + scale = 50 + 50 * m_HitPoints / m_MaxHitPoints; + + return armor * scale / 100; + } + + protected void Invalidate() + { + (Parent as Mobile)?.Delta(MobileDelta.Armor); // Tell them armor rating has changed + } + + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } + + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(7); // version + + SaveFlag flags = SaveFlag.None; + + SetSaveFlag(ref flags, SaveFlag.Attributes, !m_AosAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.ArmorAttributes, !m_AosArmorAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.PhysicalBonus, m_PhysicalBonus != 0); + SetSaveFlag(ref flags, SaveFlag.FireBonus, m_FireBonus != 0); + SetSaveFlag(ref flags, SaveFlag.ColdBonus, m_ColdBonus != 0); + SetSaveFlag(ref flags, SaveFlag.PoisonBonus, m_PoisonBonus != 0); + SetSaveFlag(ref flags, SaveFlag.EnergyBonus, m_EnergyBonus != 0); + SetSaveFlag(ref flags, SaveFlag.Identified, m_Identified); + SetSaveFlag(ref flags, SaveFlag.MaxHitPoints, m_MaxHitPoints != 0); + SetSaveFlag(ref flags, SaveFlag.HitPoints, m_HitPoints != 0); + SetSaveFlag(ref flags, SaveFlag.Crafter, m_Crafter != null); + SetSaveFlag(ref flags, SaveFlag.Quality, m_Quality != ArmorQuality.Regular); + SetSaveFlag(ref flags, SaveFlag.Durability, m_Durability != ArmorDurabilityLevel.Regular); + SetSaveFlag(ref flags, SaveFlag.Protection, m_Protection != ArmorProtectionLevel.Regular); + SetSaveFlag(ref flags, SaveFlag.Resource, m_Resource != DefaultResource); + SetSaveFlag(ref flags, SaveFlag.BaseArmor, m_ArmorBase != -1); + SetSaveFlag(ref flags, SaveFlag.StrBonus, m_StrBonus != -1); + SetSaveFlag(ref flags, SaveFlag.DexBonus, m_DexBonus != -1); + SetSaveFlag(ref flags, SaveFlag.IntBonus, m_IntBonus != -1); + SetSaveFlag(ref flags, SaveFlag.StrReq, m_StrReq != -1); + SetSaveFlag(ref flags, SaveFlag.DexReq, m_DexReq != -1); + SetSaveFlag(ref flags, SaveFlag.IntReq, m_IntReq != -1); + SetSaveFlag(ref flags, SaveFlag.MedAllowance, m_Meditate != (AMA)(-1)); + SetSaveFlag(ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.PlayerConstructed, PlayerConstructed); - if ( GetSaveFlag( flags, SaveFlag.IntBonus ) ) - writer.WriteEncodedInt( (int) m_IntBonus ); + writer.WriteEncodedInt((int)flags); - if ( GetSaveFlag( flags, SaveFlag.StrReq ) ) - writer.WriteEncodedInt( (int) m_StrReq ); + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_AosAttributes.Serialize(writer); - if ( GetSaveFlag( flags, SaveFlag.DexReq ) ) - writer.WriteEncodedInt( (int) m_DexReq ); + if (GetSaveFlag(flags, SaveFlag.ArmorAttributes)) + m_AosArmorAttributes.Serialize(writer); - if ( GetSaveFlag( flags, SaveFlag.IntReq ) ) - writer.WriteEncodedInt( (int) m_IntReq ); + if (GetSaveFlag(flags, SaveFlag.PhysicalBonus)) + writer.WriteEncodedInt(m_PhysicalBonus); - if ( GetSaveFlag( flags, SaveFlag.MedAllowance ) ) - writer.WriteEncodedInt( (int) m_Meditate ); + if (GetSaveFlag(flags, SaveFlag.FireBonus)) + writer.WriteEncodedInt(m_FireBonus); - if ( GetSaveFlag( flags, SaveFlag.SkillBonuses ) ) - m_AosSkillBonuses.Serialize( writer ); - } + if (GetSaveFlag(flags, SaveFlag.ColdBonus)) + writer.WriteEncodedInt(m_ColdBonus); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (GetSaveFlag(flags, SaveFlag.PoisonBonus)) + writer.WriteEncodedInt(m_PoisonBonus); - int version = reader.ReadInt(); + if (GetSaveFlag(flags, SaveFlag.EnergyBonus)) + writer.WriteEncodedInt(m_EnergyBonus); - switch ( version ) - { - case 7: - case 6: - case 5: - { - SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.MaxHitPoints)) + writer.WriteEncodedInt(m_MaxHitPoints); - if ( GetSaveFlag( flags, SaveFlag.Attributes ) ) - m_AosAttributes = new AosAttributes( this, reader ); - else - m_AosAttributes = new AosAttributes( this ); + if (GetSaveFlag(flags, SaveFlag.HitPoints)) + writer.WriteEncodedInt(m_HitPoints); - if ( GetSaveFlag( flags, SaveFlag.ArmorAttributes ) ) - m_AosArmorAttributes = new AosArmorAttributes( this, reader ); - else - m_AosArmorAttributes = new AosArmorAttributes( this ); + if (GetSaveFlag(flags, SaveFlag.Crafter)) + writer.Write(m_Crafter); - if ( GetSaveFlag( flags, SaveFlag.PhysicalBonus ) ) - m_PhysicalBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Quality)) + writer.WriteEncodedInt((int)m_Quality); - if ( GetSaveFlag( flags, SaveFlag.FireBonus ) ) - m_FireBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Durability)) + writer.WriteEncodedInt((int)m_Durability); - if ( GetSaveFlag( flags, SaveFlag.ColdBonus ) ) - m_ColdBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Protection)) + writer.WriteEncodedInt((int)m_Protection); - if ( GetSaveFlag( flags, SaveFlag.PoisonBonus ) ) - m_PoisonBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Resource)) + writer.WriteEncodedInt((int)m_Resource); - if ( GetSaveFlag( flags, SaveFlag.EnergyBonus ) ) - m_EnergyBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.BaseArmor)) + writer.WriteEncodedInt(m_ArmorBase); - if ( GetSaveFlag( flags, SaveFlag.Identified ) ) - m_Identified = ( version >= 7 || reader.ReadBool() ); + if (GetSaveFlag(flags, SaveFlag.StrBonus)) + writer.WriteEncodedInt(m_StrBonus); - if ( GetSaveFlag( flags, SaveFlag.MaxHitPoints ) ) - m_MaxHitPoints = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.DexBonus)) + writer.WriteEncodedInt(m_DexBonus); - if ( GetSaveFlag( flags, SaveFlag.HitPoints ) ) - m_HitPoints = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.IntBonus)) + writer.WriteEncodedInt(m_IntBonus); - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - m_Crafter = reader.ReadMobile(); - - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - m_Quality = (ArmorQuality)reader.ReadEncodedInt(); - else - m_Quality = ArmorQuality.Regular; - - if ( version == 5 && m_Quality == ArmorQuality.Low ) - m_Quality = ArmorQuality.Regular; - - if ( GetSaveFlag( flags, SaveFlag.Durability ) ) - { - m_Durability = (ArmorDurabilityLevel)reader.ReadEncodedInt(); - - if ( m_Durability > ArmorDurabilityLevel.Indestructible ) - m_Durability = ArmorDurabilityLevel.Durable; - } - - if ( GetSaveFlag( flags, SaveFlag.Protection ) ) - { - m_Protection = (ArmorProtectionLevel)reader.ReadEncodedInt(); - - if ( m_Protection > ArmorProtectionLevel.Invulnerability ) - m_Protection = ArmorProtectionLevel.Defense; - } - - if ( GetSaveFlag( flags, SaveFlag.Resource ) ) - m_Resource = (CraftResource)reader.ReadEncodedInt(); - else - m_Resource = DefaultResource; - - if ( m_Resource == CraftResource.None ) - m_Resource = DefaultResource; - - if ( GetSaveFlag( flags, SaveFlag.BaseArmor ) ) - m_ArmorBase = reader.ReadEncodedInt(); - else - m_ArmorBase = -1; - - if ( GetSaveFlag( flags, SaveFlag.StrBonus ) ) - m_StrBonus = reader.ReadEncodedInt(); - else - m_StrBonus = -1; - - if ( GetSaveFlag( flags, SaveFlag.DexBonus ) ) - m_DexBonus = reader.ReadEncodedInt(); - else - m_DexBonus = -1; - - if ( GetSaveFlag( flags, SaveFlag.IntBonus ) ) - m_IntBonus = reader.ReadEncodedInt(); - else - m_IntBonus = -1; - - if ( GetSaveFlag( flags, SaveFlag.StrReq ) ) - m_StrReq = reader.ReadEncodedInt(); - else - m_StrReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.DexReq ) ) - m_DexReq = reader.ReadEncodedInt(); - else - m_DexReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.IntReq ) ) - m_IntReq = reader.ReadEncodedInt(); - else - m_IntReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.MedAllowance ) ) - m_Meditate = (AMA)reader.ReadEncodedInt(); - else - m_Meditate = (AMA)(-1); - - if ( GetSaveFlag( flags, SaveFlag.SkillBonuses ) ) - m_AosSkillBonuses = new AosSkillBonuses( this, reader ); - - if ( GetSaveFlag( flags, SaveFlag.PlayerConstructed ) ) - PlayerConstructed = true; - - break; - } - case 4: - { - m_AosAttributes = new AosAttributes( this, reader ); - m_AosArmorAttributes = new AosArmorAttributes( this, reader ); - goto case 3; - } - case 3: - { - m_PhysicalBonus = reader.ReadInt(); - m_FireBonus = reader.ReadInt(); - m_ColdBonus = reader.ReadInt(); - m_PoisonBonus = reader.ReadInt(); - m_EnergyBonus = reader.ReadInt(); - goto case 2; - } - case 2: - case 1: - { - m_Identified = reader.ReadBool(); - goto case 0; - } - case 0: - { - m_ArmorBase = reader.ReadInt(); - m_MaxHitPoints = reader.ReadInt(); - m_HitPoints = reader.ReadInt(); - m_Crafter = reader.ReadMobile(); - m_Quality = (ArmorQuality)reader.ReadInt(); - m_Durability = (ArmorDurabilityLevel)reader.ReadInt(); - m_Protection = (ArmorProtectionLevel)reader.ReadInt(); - - AMT mat = (AMT)reader.ReadInt(); - - if ( m_ArmorBase == RevertArmorBase ) - m_ArmorBase = -1; - - /*m_BodyPos = (ArmorBodyType)*/reader.ReadInt(); - - if ( version < 4 ) - { - m_AosAttributes = new AosAttributes( this ); - m_AosArmorAttributes = new AosArmorAttributes( this ); - } - - if ( version < 3 && m_Quality == ArmorQuality.Exceptional ) - DistributeBonuses( 6 ); - - if ( version >= 2 ) - { - m_Resource = (CraftResource)reader.ReadInt(); - } - else - { - OreInfo info; - - switch ( reader.ReadInt() ) - { - default: - case 0: info = OreInfo.Iron; break; - case 1: info = OreInfo.DullCopper; break; - case 2: info = OreInfo.ShadowIron; break; - case 3: info = OreInfo.Copper; break; - case 4: info = OreInfo.Bronze; break; - case 5: info = OreInfo.Gold; break; - case 6: info = OreInfo.Agapite; break; - case 7: info = OreInfo.Verite; break; - case 8: info = OreInfo.Valorite; break; - } - - m_Resource = CraftResources.GetFromOreInfo( info, mat ); - } - - m_StrBonus = reader.ReadInt(); - m_DexBonus = reader.ReadInt(); - m_IntBonus = reader.ReadInt(); - m_StrReq = reader.ReadInt(); - m_DexReq = reader.ReadInt(); - m_IntReq = reader.ReadInt(); - - if ( m_StrBonus == OldStrBonus ) - m_StrBonus = -1; - - if ( m_DexBonus == OldDexBonus ) - m_DexBonus = -1; - - if ( m_IntBonus == OldIntBonus ) - m_IntBonus = -1; - - if ( m_StrReq == OldStrReq ) - m_StrReq = -1; - - if ( m_DexReq == OldDexReq ) - m_DexReq = -1; - - if ( m_IntReq == OldIntReq ) - m_IntReq = -1; - - m_Meditate = (AMA)reader.ReadInt(); - - if ( m_Meditate == OldMedAllowance ) - m_Meditate = (AMA)(-1); - - if ( m_Resource == CraftResource.None ) - { - if ( mat == ArmorMaterialType.Studded || mat == ArmorMaterialType.Leather ) - m_Resource = CraftResource.RegularLeather; - else if ( mat == ArmorMaterialType.Spined ) - m_Resource = CraftResource.SpinedLeather; - else if ( mat == ArmorMaterialType.Horned ) - m_Resource = CraftResource.HornedLeather; - else if ( mat == ArmorMaterialType.Barbed ) - m_Resource = CraftResource.BarbedLeather; - else - m_Resource = CraftResource.Iron; - } - - if ( m_MaxHitPoints == 0 && m_HitPoints == 0 ) - m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - - break; - } - } - - if ( m_AosSkillBonuses == null ) - m_AosSkillBonuses = new AosSkillBonuses( this ); - - Mobile m = Parent as Mobile; - - if ( Core.AOS && m != null ) - m_AosSkillBonuses.AddTo( m ); - - int strBonus = ComputeStatBonus( StatType.Str ); - int dexBonus = ComputeStatBonus( StatType.Dex ); - int intBonus = ComputeStatBonus( StatType.Int ); - - if ( m != null && (strBonus != 0 || dexBonus != 0 || intBonus != 0) ) - { - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - m?.CheckStatTimers(); - - if ( version < 7 ) - PlayerConstructed = true; // we don't know, so, assume it's crafted - } - - public virtual CraftResource DefaultResource => CraftResource.Iron; - - public BaseArmor( int itemID ) : base( itemID ) - { - m_Quality = ArmorQuality.Regular; - m_Durability = ArmorDurabilityLevel.Regular; - m_Crafter = null; - - m_Resource = DefaultResource; - Hue = CraftResources.GetHue( m_Resource ); - - m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - - Layer = (Layer)ItemData.Quality; - - m_AosAttributes = new AosAttributes( this ); - m_AosArmorAttributes = new AosArmorAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - } - - public override bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - if ( !Ethics.Ethic.CheckTrade( from, to, newOwner, this ) ) - return false; - - return base.AllowSecureTrade( from, to, newOwner, accepted ); - } - - public virtual Race RequiredRace => null; - - public override bool CanEquip( Mobile from ) - { - if ( !Ethics.Ethic.CheckEquip( from, this ) ) - return false; - - if ( from.AccessLevel < AccessLevel.GameMaster ) - { - if ( RequiredRace != null && from.Race != RequiredRace ) - { - if ( RequiredRace == Race.Elf ) - from.SendLocalizedMessage( 1072203 ); // Only Elves may use this. - else - from.SendMessage( "Only {0} may use this.", RequiredRace.PluralName ); - - return false; - } - - if ( !AllowMaleWearer && !from.Female ) - { - if ( AllowFemaleWearer ) - from.SendLocalizedMessage( 1010388 ); // Only females can wear this. - else - from.SendMessage( "You may not wear this." ); - - return false; - } - if ( !AllowFemaleWearer && from.Female ) - { - if ( AllowMaleWearer ) - from.SendLocalizedMessage( 1063343 ); // Only males can wear this. - else - from.SendMessage( "You may not wear this." ); - - return false; - } - int strBonus = ComputeStatBonus( StatType.Str ), strReq = ComputeStatReq( StatType.Str ); - int dexBonus = ComputeStatBonus( StatType.Dex ), dexReq = ComputeStatReq( StatType.Dex ); - int intBonus = ComputeStatBonus( StatType.Int ), intReq = ComputeStatReq( StatType.Int ); - - if ( from.Dex < dexReq || (from.Dex + dexBonus) < 1 ) - { - from.SendLocalizedMessage( 502077 ); // You do not have enough dexterity to equip this item. - return false; - } - - if ( from.Str < strReq || (from.Str + strBonus) < 1 ) - { - from.SendLocalizedMessage( 500213 ); // You are not strong enough to equip that. - return false; - } - if ( from.Int < intReq || (from.Int + intBonus) < 1 ) - { - from.SendMessage( "You are not smart enough to equip that." ); - return false; - } - } - - return base.CanEquip( from ); - } - - public override bool CheckPropertyConfliction( Mobile m ) - { - if ( base.CheckPropertyConfliction( m ) ) - return true; - - if ( Layer == Layer.Pants ) - return ( m.FindItemOnLayer( Layer.InnerLegs ) != null ); - - if ( Layer == Layer.Shirt ) - return ( m.FindItemOnLayer( Layer.InnerTorso ) != null ); - - return false; - } - - public override bool OnEquip( Mobile from ) - { - from.CheckStatTimers(); - - int strBonus = ComputeStatBonus( StatType.Str ); - int dexBonus = ComputeStatBonus( StatType.Dex ); - int intBonus = ComputeStatBonus( StatType.Int ); - - if ( strBonus != 0 || dexBonus != 0 || intBonus != 0 ) - { - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - return base.OnEquip( from ); - } - - public override void OnRemoved(IEntity parent) - { - if ( parent is Mobile m ) - { - string modName = Serial.ToString(); - - m.RemoveStatMod( modName + "Str" ); - m.RemoveStatMod( modName + "Dex" ); - m.RemoveStatMod( modName + "Int" ); - - if ( Core.AOS ) - m_AosSkillBonuses.Remove(); - - m.Delta( MobileDelta.Armor ); // Tell them armor rating has changed - m.CheckStatTimers(); - } - - base.OnRemoved( parent ); - } - - public virtual int OnHit( BaseWeapon weapon, int damageTaken ) - { - double halfar = ArmorRating / 2.0; - int absorbed = (int)(halfar + halfar*Utility.RandomDouble()); - - damageTaken -= absorbed; - if ( damageTaken < 0 ) - damageTaken = 0; - - if ( absorbed < 2 ) - absorbed = 2; - - if ( 25 > Utility.Random( 100 ) ) // 25% chance to lower durability - { - if ( Core.AOS && m_AosArmorAttributes.SelfRepair > Utility.Random( 10 ) ) - { - HitPoints += 2; - } - else - { - int wear; - - if ( weapon.Type == WeaponType.Bashing ) - wear = absorbed / 2; - else - wear = Utility.Random( 2 ); - - if ( wear > 0 && m_MaxHitPoints > 0 ) - { - if ( m_HitPoints >= wear ) - { - HitPoints -= wear; - wear = 0; - } - else - { - wear -= HitPoints; - HitPoints = 0; - } - - if ( wear > 0 ) - { - if ( m_MaxHitPoints > wear ) - { - MaxHitPoints -= wear; - - if ( Parent is Mobile mobile ) - mobile.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061121 ); // Your equipment is severely damaged. - } - else - { - Delete(); - } - } - } - } - } - - return damageTaken; - } - - private string GetNameString() - { - string name = Name; - - if ( name == null ) - name = $"#{LabelNumber}"; - - return name; - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set{ base.Hue = value; InvalidateProperties(); } - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - int oreType; - - switch ( m_Resource ) - { - case CraftResource.DullCopper: oreType = 1053108; break; // dull copper - case CraftResource.ShadowIron: oreType = 1053107; break; // shadow iron - case CraftResource.Copper: oreType = 1053106; break; // copper - case CraftResource.Bronze: oreType = 1053105; break; // bronze - case CraftResource.Gold: oreType = 1053104; break; // golden - case CraftResource.Agapite: oreType = 1053103; break; // agapite - case CraftResource.Verite: oreType = 1053102; break; // verite - case CraftResource.Valorite: oreType = 1053101; break; // valorite - case CraftResource.SpinedLeather: oreType = 1061118; break; // spined - case CraftResource.HornedLeather: oreType = 1061117; break; // horned - case CraftResource.BarbedLeather: oreType = 1061116; break; // barbed - case CraftResource.RedScales: oreType = 1060814; break; // red - case CraftResource.YellowScales: oreType = 1060818; break; // yellow - case CraftResource.BlackScales: oreType = 1060820; break; // black - case CraftResource.GreenScales: oreType = 1060819; break; // green - case CraftResource.WhiteScales: oreType = 1060821; break; // white - case CraftResource.BlueScales: oreType = 1060815; break; // blue - default: oreType = 0; break; - } - - if ( m_Quality == ArmorQuality.Exceptional ) - { - if ( oreType != 0 ) - list.Add( 1053100, "#{0}\t{1}", oreType, GetNameString() ); // exceptional ~1_oretype~ ~2_armortype~ - else - list.Add( 1050040, GetNameString() ); // exceptional ~1_ITEMNAME~ - } - else - { - if ( oreType != 0 ) - list.Add( 1053099, "#{0}\t{1}", oreType, GetNameString() ); // ~1_oretype~ ~2_armortype~ - else if ( Name == null ) - list.Add( LabelNumber ); - else - list.Add( Name ); - } - } - - public override bool AllowEquippedCast( Mobile from ) - { - if ( base.AllowEquippedCast( from ) ) - return true; - - return ( m_AosAttributes.SpellChanneling != 0 ); - } - - public virtual int GetLuckBonus() - { - CraftResourceInfo resInfo = CraftResources.GetInfo( m_Resource ); - - CraftAttributeInfo attrInfo = resInfo?.AttributeInfo; - - if ( attrInfo == null ) - return 0; - - return attrInfo.ArmorLuck; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (GetSaveFlag(flags, SaveFlag.StrReq)) + writer.WriteEncodedInt(m_StrReq); - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if (GetSaveFlag(flags, SaveFlag.DexReq)) + writer.WriteEncodedInt(m_DexReq); - #region Factions - if ( m_FactionState != null ) - list.Add( 1041350 ); // faction item - #endregion + if (GetSaveFlag(flags, SaveFlag.IntReq)) + writer.WriteEncodedInt(m_IntReq); - if ( RequiredRace == Race.Elf ) - list.Add( 1075086 ); // Elves Only + if (GetSaveFlag(flags, SaveFlag.MedAllowance)) + writer.WriteEncodedInt((int)m_Meditate); - m_AosSkillBonuses.GetProperties( list ); + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses.Serialize(writer); + } - int prop; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( (prop = ArtifactRarity) > 0 ) - list.Add( 1061078, prop.ToString() ); // artifact rarity ~1_val~ + int version = reader.ReadInt(); - if ( (prop = m_AosAttributes.WeaponDamage) != 0 ) - list.Add( 1060401, prop.ToString() ); // damage increase ~1_val~% + switch (version) + { + case 7: + case 6: + case 5: + { + SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.DefendChance) != 0 ) - list.Add( 1060408, prop.ToString() ); // defense chance increase ~1_val~% + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_AosAttributes = new AosAttributes(this, reader); + else + m_AosAttributes = new AosAttributes(this); - if ( (prop = m_AosAttributes.BonusDex) != 0 ) - list.Add( 1060409, prop.ToString() ); // dexterity bonus ~1_val~ + if (GetSaveFlag(flags, SaveFlag.ArmorAttributes)) + m_AosArmorAttributes = new AosArmorAttributes(this, reader); + else + m_AosArmorAttributes = new AosArmorAttributes(this); - if ( (prop = m_AosAttributes.EnhancePotions) != 0 ) - list.Add( 1060411, prop.ToString() ); // enhance potions ~1_val~% + if (GetSaveFlag(flags, SaveFlag.PhysicalBonus)) + m_PhysicalBonus = reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.CastRecovery) != 0 ) - list.Add( 1060412, prop.ToString() ); // faster cast recovery ~1_val~ + if (GetSaveFlag(flags, SaveFlag.FireBonus)) + m_FireBonus = reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.CastSpeed) != 0 ) - list.Add( 1060413, prop.ToString() ); // faster casting ~1_val~ + if (GetSaveFlag(flags, SaveFlag.ColdBonus)) + m_ColdBonus = reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.AttackChance) != 0 ) - list.Add( 1060415, prop.ToString() ); // hit chance increase ~1_val~% + if (GetSaveFlag(flags, SaveFlag.PoisonBonus)) + m_PoisonBonus = reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.BonusHits) != 0 ) - list.Add( 1060431, prop.ToString() ); // hit point increase ~1_val~ + if (GetSaveFlag(flags, SaveFlag.EnergyBonus)) + m_EnergyBonus = reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.BonusInt) != 0 ) - list.Add( 1060432, prop.ToString() ); // intelligence bonus ~1_val~ + if (GetSaveFlag(flags, SaveFlag.Identified)) + m_Identified = version >= 7 || reader.ReadBool(); - if ( (prop = m_AosAttributes.LowerManaCost) != 0 ) - list.Add( 1060433, prop.ToString() ); // lower mana cost ~1_val~% + if (GetSaveFlag(flags, SaveFlag.MaxHitPoints)) + m_MaxHitPoints = reader.ReadEncodedInt(); - if ( (prop = m_AosAttributes.LowerRegCost) != 0 ) - list.Add( 1060434, prop.ToString() ); // lower reagent cost ~1_val~% + if (GetSaveFlag(flags, SaveFlag.HitPoints)) + m_HitPoints = reader.ReadEncodedInt(); - if ( (prop = GetLowerStatReq()) != 0 ) - list.Add( 1060435, prop.ToString() ); // lower requirements ~1_val~% + if (GetSaveFlag(flags, SaveFlag.Crafter)) + m_Crafter = reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.Quality)) + m_Quality = (ArmorQuality)reader.ReadEncodedInt(); + else + m_Quality = ArmorQuality.Regular; + + if (version == 5 && m_Quality == ArmorQuality.Low) + m_Quality = ArmorQuality.Regular; + + if (GetSaveFlag(flags, SaveFlag.Durability)) + { + m_Durability = (ArmorDurabilityLevel)reader.ReadEncodedInt(); + + if (m_Durability > ArmorDurabilityLevel.Indestructible) + m_Durability = ArmorDurabilityLevel.Durable; + } + + if (GetSaveFlag(flags, SaveFlag.Protection)) + { + m_Protection = (ArmorProtectionLevel)reader.ReadEncodedInt(); + + if (m_Protection > ArmorProtectionLevel.Invulnerability) + m_Protection = ArmorProtectionLevel.Defense; + } + + if (GetSaveFlag(flags, SaveFlag.Resource)) + m_Resource = (CraftResource)reader.ReadEncodedInt(); + else + m_Resource = DefaultResource; + + if (m_Resource == CraftResource.None) + m_Resource = DefaultResource; + + if (GetSaveFlag(flags, SaveFlag.BaseArmor)) + m_ArmorBase = reader.ReadEncodedInt(); + else + m_ArmorBase = -1; + + if (GetSaveFlag(flags, SaveFlag.StrBonus)) + m_StrBonus = reader.ReadEncodedInt(); + else + m_StrBonus = -1; + + if (GetSaveFlag(flags, SaveFlag.DexBonus)) + m_DexBonus = reader.ReadEncodedInt(); + else + m_DexBonus = -1; + + if (GetSaveFlag(flags, SaveFlag.IntBonus)) + m_IntBonus = reader.ReadEncodedInt(); + else + m_IntBonus = -1; + + if (GetSaveFlag(flags, SaveFlag.StrReq)) + m_StrReq = reader.ReadEncodedInt(); + else + m_StrReq = -1; + + if (GetSaveFlag(flags, SaveFlag.DexReq)) + m_DexReq = reader.ReadEncodedInt(); + else + m_DexReq = -1; + + if (GetSaveFlag(flags, SaveFlag.IntReq)) + m_IntReq = reader.ReadEncodedInt(); + else + m_IntReq = -1; + + if (GetSaveFlag(flags, SaveFlag.MedAllowance)) + m_Meditate = (AMA)reader.ReadEncodedInt(); + else + m_Meditate = (AMA)(-1); + + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses = new AosSkillBonuses(this, reader); + + if (GetSaveFlag(flags, SaveFlag.PlayerConstructed)) + PlayerConstructed = true; + + break; + } + case 4: + { + m_AosAttributes = new AosAttributes(this, reader); + m_AosArmorAttributes = new AosArmorAttributes(this, reader); + goto case 3; + } + case 3: + { + m_PhysicalBonus = reader.ReadInt(); + m_FireBonus = reader.ReadInt(); + m_ColdBonus = reader.ReadInt(); + m_PoisonBonus = reader.ReadInt(); + m_EnergyBonus = reader.ReadInt(); + goto case 2; + } + case 2: + case 1: + { + m_Identified = reader.ReadBool(); + goto case 0; + } + case 0: + { + m_ArmorBase = reader.ReadInt(); + m_MaxHitPoints = reader.ReadInt(); + m_HitPoints = reader.ReadInt(); + m_Crafter = reader.ReadMobile(); + m_Quality = (ArmorQuality)reader.ReadInt(); + m_Durability = (ArmorDurabilityLevel)reader.ReadInt(); + m_Protection = (ArmorProtectionLevel)reader.ReadInt(); + + AMT mat = (AMT)reader.ReadInt(); + + if (m_ArmorBase == RevertArmorBase) + m_ArmorBase = -1; + + /*m_BodyPos = (ArmorBodyType)*/ + reader.ReadInt(); + + if (version < 4) + { + m_AosAttributes = new AosAttributes(this); + m_AosArmorAttributes = new AosArmorAttributes(this); + } + + if (version < 3 && m_Quality == ArmorQuality.Exceptional) + DistributeBonuses(6); + + if (version >= 2) + { + m_Resource = (CraftResource)reader.ReadInt(); + } + else + { + OreInfo info; + + switch (reader.ReadInt()) + { + default: + case 0: + info = OreInfo.Iron; + break; + case 1: + info = OreInfo.DullCopper; + break; + case 2: + info = OreInfo.ShadowIron; + break; + case 3: + info = OreInfo.Copper; + break; + case 4: + info = OreInfo.Bronze; + break; + case 5: + info = OreInfo.Gold; + break; + case 6: + info = OreInfo.Agapite; + break; + case 7: + info = OreInfo.Verite; + break; + case 8: + info = OreInfo.Valorite; + break; + } + + m_Resource = CraftResources.GetFromOreInfo(info, mat); + } + + m_StrBonus = reader.ReadInt(); + m_DexBonus = reader.ReadInt(); + m_IntBonus = reader.ReadInt(); + m_StrReq = reader.ReadInt(); + m_DexReq = reader.ReadInt(); + m_IntReq = reader.ReadInt(); + + if (m_StrBonus == OldStrBonus) + m_StrBonus = -1; + + if (m_DexBonus == OldDexBonus) + m_DexBonus = -1; + + if (m_IntBonus == OldIntBonus) + m_IntBonus = -1; + + if (m_StrReq == OldStrReq) + m_StrReq = -1; + + if (m_DexReq == OldDexReq) + m_DexReq = -1; + + if (m_IntReq == OldIntReq) + m_IntReq = -1; + + m_Meditate = (AMA)reader.ReadInt(); + + if (m_Meditate == OldMedAllowance) + m_Meditate = (AMA)(-1); + + if (m_Resource == CraftResource.None) + { + if (mat == ArmorMaterialType.Studded || mat == ArmorMaterialType.Leather) + m_Resource = CraftResource.RegularLeather; + else if (mat == ArmorMaterialType.Spined) + m_Resource = CraftResource.SpinedLeather; + else if (mat == ArmorMaterialType.Horned) + m_Resource = CraftResource.HornedLeather; + else if (mat == ArmorMaterialType.Barbed) + m_Resource = CraftResource.BarbedLeather; + else + m_Resource = CraftResource.Iron; + } + + if (m_MaxHitPoints == 0 && m_HitPoints == 0) + m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax(InitMinHits, InitMaxHits); + + break; + } + } + + if (m_AosSkillBonuses == null) + m_AosSkillBonuses = new AosSkillBonuses(this); + + Mobile m = Parent as Mobile; + + if (Core.AOS && m != null) + m_AosSkillBonuses.AddTo(m); + + int strBonus = ComputeStatBonus(StatType.Str); + int dexBonus = ComputeStatBonus(StatType.Dex); + int intBonus = ComputeStatBonus(StatType.Int); + + if (m != null && (strBonus != 0 || dexBonus != 0 || intBonus != 0)) + { + string modName = Serial.ToString(); + + if (strBonus != 0) + m.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + m.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + m.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + m?.CheckStatTimers(); + + if (version < 7) + PlayerConstructed = true; // we don't know, so, assume it's crafted + } + + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (!Ethic.CheckTrade(from, to, newOwner, this)) + return false; + + return base.AllowSecureTrade(from, to, newOwner, accepted); + } + + public override bool CanEquip(Mobile from) + { + if (!Ethic.CheckEquip(from, this)) + return false; + + if (from.AccessLevel < AccessLevel.GameMaster) + { + if (RequiredRace != null && from.Race != RequiredRace) + { + if (RequiredRace == Race.Elf) + from.SendLocalizedMessage(1072203); // Only Elves may use this. + else + from.SendMessage("Only {0} may use this.", RequiredRace.PluralName); + + return false; + } + + if (!AllowMaleWearer && !from.Female) + { + if (AllowFemaleWearer) + from.SendLocalizedMessage(1010388); // Only females can wear this. + else + from.SendMessage("You may not wear this."); + + return false; + } + + if (!AllowFemaleWearer && from.Female) + { + if (AllowMaleWearer) + from.SendLocalizedMessage(1063343); // Only males can wear this. + else + from.SendMessage("You may not wear this."); + + return false; + } + + int strBonus = ComputeStatBonus(StatType.Str), strReq = ComputeStatReq(StatType.Str); + int dexBonus = ComputeStatBonus(StatType.Dex), dexReq = ComputeStatReq(StatType.Dex); + int intBonus = ComputeStatBonus(StatType.Int), intReq = ComputeStatReq(StatType.Int); + + if (from.Dex < dexReq || from.Dex + dexBonus < 1) + { + from.SendLocalizedMessage(502077); // You do not have enough dexterity to equip this item. + return false; + } + + if (from.Str < strReq || from.Str + strBonus < 1) + { + from.SendLocalizedMessage(500213); // You are not strong enough to equip that. + return false; + } + + if (from.Int < intReq || from.Int + intBonus < 1) + { + from.SendMessage("You are not smart enough to equip that."); + return false; + } + } + + return base.CanEquip(from); + } + + public override bool CheckPropertyConfliction(Mobile m) + { + if (base.CheckPropertyConfliction(m)) + return true; + + if (Layer == Layer.Pants) + return m.FindItemOnLayer(Layer.InnerLegs) != null; + + if (Layer == Layer.Shirt) + return m.FindItemOnLayer(Layer.InnerTorso) != null; + + return false; + } + + public override bool OnEquip(Mobile from) + { + from.CheckStatTimers(); + + int strBonus = ComputeStatBonus(StatType.Str); + int dexBonus = ComputeStatBonus(StatType.Dex); + int intBonus = ComputeStatBonus(StatType.Int); + + if (strBonus != 0 || dexBonus != 0 || intBonus != 0) + { + string modName = Serial.ToString(); + + if (strBonus != 0) + from.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + from.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + from.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + return base.OnEquip(from); + } + + public override void OnRemoved(IEntity parent) + { + if (parent is Mobile m) + { + string modName = Serial.ToString(); + + m.RemoveStatMod(modName + "Str"); + m.RemoveStatMod(modName + "Dex"); + m.RemoveStatMod(modName + "Int"); + + if (Core.AOS) + m_AosSkillBonuses.Remove(); + + m.Delta(MobileDelta.Armor); // Tell them armor rating has changed + m.CheckStatTimers(); + } + + base.OnRemoved(parent); + } + + private string GetNameString() + { + string name = Name; + + if (name == null) + name = $"#{LabelNumber}"; + + return name; + } + + public override void AddNameProperty(ObjectPropertyList list) + { + int oreType; + + switch (m_Resource) + { + case CraftResource.DullCopper: + oreType = 1053108; + break; // dull copper + case CraftResource.ShadowIron: + oreType = 1053107; + break; // shadow iron + case CraftResource.Copper: + oreType = 1053106; + break; // copper + case CraftResource.Bronze: + oreType = 1053105; + break; // bronze + case CraftResource.Gold: + oreType = 1053104; + break; // golden + case CraftResource.Agapite: + oreType = 1053103; + break; // agapite + case CraftResource.Verite: + oreType = 1053102; + break; // verite + case CraftResource.Valorite: + oreType = 1053101; + break; // valorite + case CraftResource.SpinedLeather: + oreType = 1061118; + break; // spined + case CraftResource.HornedLeather: + oreType = 1061117; + break; // horned + case CraftResource.BarbedLeather: + oreType = 1061116; + break; // barbed + case CraftResource.RedScales: + oreType = 1060814; + break; // red + case CraftResource.YellowScales: + oreType = 1060818; + break; // yellow + case CraftResource.BlackScales: + oreType = 1060820; + break; // black + case CraftResource.GreenScales: + oreType = 1060819; + break; // green + case CraftResource.WhiteScales: + oreType = 1060821; + break; // white + case CraftResource.BlueScales: + oreType = 1060815; + break; // blue + default: + oreType = 0; + break; + } + + if (m_Quality == ArmorQuality.Exceptional) + { + if (oreType != 0) + list.Add(1053100, "#{0}\t{1}", oreType, GetNameString()); // exceptional ~1_oretype~ ~2_armortype~ + else + list.Add(1050040, GetNameString()); // exceptional ~1_ITEMNAME~ + } + else + { + if (oreType != 0) + list.Add(1053099, "#{0}\t{1}", oreType, GetNameString()); // ~1_oretype~ ~2_armortype~ + else if (Name == null) + list.Add(LabelNumber); + else + list.Add(Name); + } + } + + public override bool AllowEquippedCast(Mobile from) + { + if (base.AllowEquippedCast(from)) + return true; + + return m_AosAttributes.SpellChanneling != 0; + } + + public virtual int GetLuckBonus() + { + CraftResourceInfo resInfo = CraftResources.GetInfo(m_Resource); + + CraftAttributeInfo attrInfo = resInfo?.AttributeInfo; + + if (attrInfo == null) + return 0; + + return attrInfo.ArmorLuck; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ + + #region Factions + + if (m_FactionState != null) + list.Add(1041350); // faction item + + #endregion + + if (RequiredRace == Race.Elf) + list.Add(1075086); // Elves Only + + m_AosSkillBonuses.GetProperties(list); + + int prop; + + if ((prop = ArtifactRarity) > 0) + list.Add(1061078, prop.ToString()); // artifact rarity ~1_val~ + + if ((prop = m_AosAttributes.WeaponDamage) != 0) + list.Add(1060401, prop.ToString()); // damage increase ~1_val~% + + if ((prop = m_AosAttributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% - if ( (prop = (GetLuckBonus() + m_AosAttributes.Luck)) != 0 ) - list.Add( 1060436, prop.ToString() ); // luck ~1_val~ + if ((prop = m_AosAttributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ - if ( (prop = m_AosArmorAttributes.MageArmor) != 0 ) - list.Add( 1060437 ); // mage armor + if ((prop = m_AosAttributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% - if ( (prop = m_AosAttributes.BonusMana) != 0 ) - list.Add( 1060439, prop.ToString() ); // mana increase ~1_val~ + if ((prop = m_AosAttributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ - if ( (prop = m_AosAttributes.RegenMana) != 0 ) - list.Add( 1060440, prop.ToString() ); // mana regeneration ~1_val~ + if ((prop = m_AosAttributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - if ( (prop = m_AosAttributes.NightSight) != 0 ) - list.Add( 1060441 ); // night sight + if ((prop = m_AosAttributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - if ( (prop = m_AosAttributes.ReflectPhysical) != 0 ) - list.Add( 1060442, prop.ToString() ); // reflect physical damage ~1_val~% + if ((prop = m_AosAttributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if ( (prop = m_AosAttributes.RegenStam) != 0 ) - list.Add( 1060443, prop.ToString() ); // stamina regeneration ~1_val~ + if ((prop = m_AosAttributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - if ( (prop = m_AosAttributes.RegenHits) != 0 ) - list.Add( 1060444, prop.ToString() ); // hit point regeneration ~1_val~ + if ((prop = m_AosAttributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if ( (prop = m_AosArmorAttributes.SelfRepair) != 0 ) - list.Add( 1060450, prop.ToString() ); // self repair ~1_val~ + if ((prop = m_AosAttributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - if ( (prop = m_AosAttributes.SpellChanneling) != 0 ) - list.Add( 1060482 ); // spell channeling + if ((prop = GetLowerStatReq()) != 0) + list.Add(1060435, prop.ToString()); // lower requirements ~1_val~% - if ( (prop = m_AosAttributes.SpellDamage) != 0 ) - list.Add( 1060483, prop.ToString() ); // spell damage increase ~1_val~% + if ((prop = GetLuckBonus() + m_AosAttributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - if ( (prop = m_AosAttributes.BonusStam) != 0 ) - list.Add( 1060484, prop.ToString() ); // stamina increase ~1_val~ + if ((prop = m_AosArmorAttributes.MageArmor) != 0) + list.Add(1060437); // mage armor - if ( (prop = m_AosAttributes.BonusStr) != 0 ) - list.Add( 1060485, prop.ToString() ); // strength bonus ~1_val~ + if ((prop = m_AosAttributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - if ( (prop = m_AosAttributes.WeaponSpeed) != 0 ) - list.Add( 1060486, prop.ToString() ); // swing speed increase ~1_val~% + if ((prop = m_AosAttributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - if ( Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0 ) - list.Add( 1075210, prop.ToString() ); // Increased Karma Loss ~1val~% + if ((prop = m_AosAttributes.NightSight) != 0) + list.Add(1060441); // night sight - base.AddResistanceProperties( list ); + if ((prop = m_AosAttributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - if ( (prop = GetDurabilityBonus()) > 0 ) - list.Add( 1060410, prop.ToString() ); // durability ~1_val~% + if ((prop = m_AosAttributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - if ( (prop = ComputeStatReq( StatType.Str )) > 0 ) - list.Add( 1061170, prop.ToString() ); // strength requirement ~1_val~ + if ((prop = m_AosAttributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if ( m_HitPoints >= 0 && m_MaxHitPoints > 0 ) - list.Add( 1060639, "{0}\t{1}", m_HitPoints, m_MaxHitPoints ); // durability ~1_val~ / ~2_val~ - } + if ((prop = m_AosArmorAttributes.SelfRepair) != 0) + list.Add(1060450, prop.ToString()); // self repair ~1_val~ - public override void OnSingleClick( Mobile from ) - { - List attrs = new List(); + if ((prop = m_AosAttributes.SpellChanneling) != 0) + list.Add(1060482); // spell channeling - if ( DisplayLootType ) - { - if ( LootType == LootType.Blessed ) - attrs.Add( new EquipInfoAttribute( 1038021 ) ); // blessed - else if ( LootType == LootType.Cursed ) - attrs.Add( new EquipInfoAttribute( 1049643 ) ); // cursed - } + if ((prop = m_AosAttributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - #region Factions - if ( m_FactionState != null ) - attrs.Add( new EquipInfoAttribute( 1041350 ) ); // faction item - #endregion + if ((prop = m_AosAttributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - if ( m_Quality == ArmorQuality.Exceptional ) - attrs.Add( new EquipInfoAttribute( 1018305 - (int)m_Quality ) ); + if ((prop = m_AosAttributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - if ( m_Identified || from.AccessLevel >= AccessLevel.GameMaster) - { - if ( m_Durability != ArmorDurabilityLevel.Regular ) - attrs.Add( new EquipInfoAttribute( 1038000 + (int)m_Durability ) ); + if ((prop = m_AosAttributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - if ( m_Protection > ArmorProtectionLevel.Regular && m_Protection <= ArmorProtectionLevel.Invulnerability ) - attrs.Add( new EquipInfoAttribute( 1038005 + (int)m_Protection ) ); - } - else if ( m_Durability != ArmorDurabilityLevel.Regular || (m_Protection > ArmorProtectionLevel.Regular && m_Protection <= ArmorProtectionLevel.Invulnerability) ) - attrs.Add( new EquipInfoAttribute( 1038000 ) ); // Unidentified + if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) + list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% - int number; + base.AddResistanceProperties(list); - if ( Name == null ) - { - number = LabelNumber; - } - else - { - LabelTo( from, Name ); - number = 1041000; - } + if ((prop = GetDurabilityBonus()) > 0) + list.Add(1060410, prop.ToString()); // durability ~1_val~% - if ( attrs.Count == 0 && Crafter == null && Name != null ) - return; + if ((prop = ComputeStatReq(StatType.Str)) > 0) + list.Add(1061170, prop.ToString()); // strength requirement ~1_val~ - EquipmentInfo eqInfo = new EquipmentInfo( number, m_Crafter, false, attrs.ToArray() ); + if (m_HitPoints >= 0 && m_MaxHitPoints > 0) + list.Add(1060639, "{0}\t{1}", m_HitPoints, m_MaxHitPoints); // durability ~1_val~ / ~2_val~ + } - from.Send( new DisplayEquipmentInfo( this, eqInfo ) ); - } + public override void OnSingleClick(Mobile from) + { + List attrs = new List(); - #region ICraftable Members + if (DisplayLootType) + { + if (LootType == LootType.Blessed) + attrs.Add(new EquipInfoAttribute(1038021)); // blessed + else if (LootType == LootType.Cursed) + attrs.Add(new EquipInfoAttribute(1049643)); // cursed + } - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (ArmorQuality)quality; + #region Factions - if ( makersMark ) - Crafter = from; + if (m_FactionState != null) + attrs.Add(new EquipInfoAttribute(1041350)); // faction item + + #endregion - Type resourceType = typeRes; + if (m_Quality == ArmorQuality.Exceptional) + attrs.Add(new EquipInfoAttribute(1018305 - (int)m_Quality)); - if ( resourceType == null ) - resourceType = craftItem.Resources.GetAt( 0 ).ItemType; - - Resource = CraftResources.GetFromType( resourceType ); - PlayerConstructed = true; - - CraftContext context = craftSystem.GetContext( from ); - - if ( context != null && context.DoNotColor ) - Hue = 0; - - if ( Quality == ArmorQuality.Exceptional ) - { - if ( !( Core.ML && this is BaseShield )) // Guessed Core.ML removed exceptional resist bonuses from crafted shields - DistributeBonuses( (tool is BaseRunicTool ? 6 : Core.SE ? 15 : 14) ); // Not sure since when, but right now 15 points are added, not 14. - - if ( Core.ML && !(this is BaseShield) ) - { - int bonus = (int)(from.Skills.ArmsLore.Value / 20); - - for( int i = 0; i < bonus; i++ ) - { - switch( Utility.Random( 5 ) ) - { - case 0: m_PhysicalBonus++; break; - case 1: m_FireBonus++; break; - case 2: m_ColdBonus++; break; - case 3: m_EnergyBonus++; break; - case 4: m_PoisonBonus++; break; - } - } - - from.CheckSkill( SkillName.ArmsLore, 0, 100 ); - } - } - - if ( Core.AOS ) - (tool as BaseRunicTool)?.ApplyAttributesTo( this ); - - return quality; - } - - #endregion - } -} + if (m_Identified || from.AccessLevel >= AccessLevel.GameMaster) + { + if (m_Durability != ArmorDurabilityLevel.Regular) + attrs.Add(new EquipInfoAttribute(1038000 + (int)m_Durability)); + + if (m_Protection > ArmorProtectionLevel.Regular && m_Protection <= ArmorProtectionLevel.Invulnerability) + attrs.Add(new EquipInfoAttribute(1038005 + (int)m_Protection)); + } + else if (m_Durability != ArmorDurabilityLevel.Regular || m_Protection > ArmorProtectionLevel.Regular && + m_Protection <= ArmorProtectionLevel.Invulnerability) + { + attrs.Add(new EquipInfoAttribute(1038000)); // Unidentified + } + + int number; + + if (Name == null) + { + number = LabelNumber; + } + else + { + LabelTo(from, Name); + number = 1041000; + } + + if (attrs.Count == 0 && Crafter == null && Name != null) + return; + + EquipmentInfo eqInfo = new EquipmentInfo(number, m_Crafter, false, attrs.ToArray()); + + from.Send(new DisplayEquipmentInfo(this, eqInfo)); + } + + [Flags] + private enum SaveFlag + { + None = 0x00000000, + Attributes = 0x00000001, + ArmorAttributes = 0x00000002, + PhysicalBonus = 0x00000004, + FireBonus = 0x00000008, + ColdBonus = 0x00000010, + PoisonBonus = 0x00000020, + EnergyBonus = 0x00000040, + Identified = 0x00000080, + MaxHitPoints = 0x00000100, + HitPoints = 0x00000200, + Crafter = 0x00000400, + Quality = 0x00000800, + Durability = 0x00001000, + Protection = 0x00002000, + Resource = 0x00004000, + BaseArmor = 0x00008000, + StrBonus = 0x00010000, + DexBonus = 0x00020000, + IntBonus = 0x00040000, + StrReq = 0x00080000, + DexReq = 0x00100000, + IntReq = 0x00200000, + MedAllowance = 0x00400000, + SkillBonuses = 0x00800000, + PlayerConstructed = 0x01000000 + } + + #region Factions + + private FactionItem m_FactionState; + + public FactionItem FactionItemState + { + get => m_FactionState; + set + { + m_FactionState = value; + + if (m_FactionState == null) + Hue = CraftResources.GetHue(Resource); + + LootType = m_FactionState == null ? LootType.Regular : LootType.Blessed; + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Bone/BoneArms.cs b/Scripts/Items/Armor/Bone/BoneArms.cs index 0f2a0db29..094b7be0d 100644 --- a/Scripts/Items/Armor/Bone/BoneArms.cs +++ b/Scripts/Items/Armor/Bone/BoneArms.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x144e, 0x1453 )] - public class BoneArms : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 4; + [Flippable(0x144e, 0x1453)] + public class BoneArms : BaseArmor + { + [Constructible] + public BoneArms() : base(0x144E) + { + Weight = 2.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 30; + public BoneArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 4; - public override int OldDexBonus => -2; + public override int InitMinHits => 25; + public override int InitMaxHits => 30; - public override int ArmorBase => 30; - public override int RevertArmorBase => 4; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int OldDexBonus => -2; - [Constructible] - public BoneArms() : base( 0x144E ) - { - Weight = 2.0; - } + public override int ArmorBase => 30; + public override int RevertArmorBase => 4; - public BoneArms( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - if ( Weight == 1.0 ) - Weight = 2.0; - } + if (Weight == 1.0) + Weight = 2.0; + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Bone/BoneChest.cs b/Scripts/Items/Armor/Bone/BoneChest.cs index 0b7038557..e5b29489a 100644 --- a/Scripts/Items/Armor/Bone/BoneChest.cs +++ b/Scripts/Items/Armor/Bone/BoneChest.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x144f, 0x1454 )] - public class BoneChest : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 4; + [Flippable(0x144f, 0x1454)] + public class BoneChest : BaseArmor + { + [Constructible] + public BoneChest() : base(0x144F) + { + Weight = 6.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 30; + public BoneChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 60; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 4; - public override int OldDexBonus => -6; + public override int InitMinHits => 25; + public override int InitMaxHits => 30; - public override int ArmorBase => 30; - public override int RevertArmorBase => 11; + public override int AosStrReq => 60; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int OldDexBonus => -6; - [Constructible] - public BoneChest() : base( 0x144F ) - { - Weight = 6.0; - } + public override int ArmorBase => 30; + public override int RevertArmorBase => 11; - public BoneChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - if ( Weight == 1.0 ) - Weight = 6.0; - } + if (Weight == 1.0) + Weight = 6.0; + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Bone/BoneGloves.cs b/Scripts/Items/Armor/Bone/BoneGloves.cs index c222adc4d..d8b829cef 100644 --- a/Scripts/Items/Armor/Bone/BoneGloves.cs +++ b/Scripts/Items/Armor/Bone/BoneGloves.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x1450, 0x1455 )] - public class BoneGloves : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 4; + [Flippable(0x1450, 0x1455)] + public class BoneGloves : BaseArmor + { + [Constructible] + public BoneGloves() : base(0x1450) + { + Weight = 2.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 30; + public BoneGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 4; - public override int OldDexBonus => -1; + public override int InitMinHits => 25; + public override int InitMaxHits => 30; - public override int ArmorBase => 30; - public override int RevertArmorBase => 2; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int OldDexBonus => -1; - [Constructible] - public BoneGloves() : base( 0x1450 ) - { - Weight = 2.0; - } + public override int ArmorBase => 30; + public override int RevertArmorBase => 2; - public BoneGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - if ( Weight == 1.0 ) - Weight = 2.0; - } + if (Weight == 1.0) + Weight = 2.0; + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Bone/BoneLegs.cs b/Scripts/Items/Armor/Bone/BoneLegs.cs index b03044837..30da8fd19 100644 --- a/Scripts/Items/Armor/Bone/BoneLegs.cs +++ b/Scripts/Items/Armor/Bone/BoneLegs.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0x1452, 0x1457 )] - public class BoneLegs : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 4; + [Flippable(0x1452, 0x1457)] + public class BoneLegs : BaseArmor + { + [Constructible] + public BoneLegs() : base(0x1452) + { + Weight = 3.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 30; + public BoneLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 4; - public override int OldDexBonus => -4; + public override int InitMinHits => 25; + public override int InitMaxHits => 30; - public override int ArmorBase => 30; - public override int RevertArmorBase => 7; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int OldDexBonus => -4; - [Constructible] - public BoneLegs() : base( 0x1452 ) - { - Weight = 3.0; - } + public override int ArmorBase => 30; + public override int RevertArmorBase => 7; - public BoneLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Chain/ChainChest.cs b/Scripts/Items/Armor/Chain/ChainChest.cs index d957c7912..d572b5731 100644 --- a/Scripts/Items/Armor/Chain/ChainChest.cs +++ b/Scripts/Items/Armor/Chain/ChainChest.cs @@ -1,46 +1,46 @@ namespace Server.Items { - [FlippableAttribute( 0x13bf, 0x13c4 )] - public class ChainChest : BaseArmor - { - public override int BasePhysicalResistance => 4; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 1; - public override int BaseEnergyResistance => 2; + [Flippable(0x13bf, 0x13c4)] + public class ChainChest : BaseArmor + { + [Constructible] + public ChainChest() : base(0x13BF) + { + Weight = 7.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 60; + public ChainChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 60; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 4; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 1; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -5; + public override int InitMinHits => 45; + public override int InitMaxHits => 60; - public override int ArmorBase => 28; + public override int AosStrReq => 60; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; + public override int OldDexBonus => -5; - [Constructible] - public ChainChest() : base( 0x13BF ) - { - Weight = 7.0; - } + public override int ArmorBase => 28; - public ChainChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Chain/ChainHatsuburi.cs b/Scripts/Items/Armor/Chain/ChainHatsuburi.cs index a8a2727a6..f47e71394 100644 --- a/Scripts/Items/Armor/Chain/ChainHatsuburi.cs +++ b/Scripts/Items/Armor/Chain/ChainHatsuburi.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class ChainHatsuburi : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 4; + public class ChainHatsuburi : BaseArmor + { + [Constructible] + public ChainHatsuburi() : base(0x2774) + { + Weight = 7.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public ChainHatsuburi(Serial serial) : base(serial) + { + } - public override int AosStrReq => 50; - public override int OldStrReq => 50; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 3; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; + public override int AosStrReq => 50; + public override int OldStrReq => 50; - [Constructible] - public ChainHatsuburi() : base( 0x2774 ) - { - Weight = 7.0; - } + public override int ArmorBase => 3; - public ChainHatsuburi( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Chain/ChainLegs.cs b/Scripts/Items/Armor/Chain/ChainLegs.cs index 3151dd28a..72732061f 100644 --- a/Scripts/Items/Armor/Chain/ChainLegs.cs +++ b/Scripts/Items/Armor/Chain/ChainLegs.cs @@ -1,46 +1,46 @@ namespace Server.Items { - [FlippableAttribute( 0x13be, 0x13c3 )] - public class ChainLegs : BaseArmor - { - public override int BasePhysicalResistance => 4; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 1; - public override int BaseEnergyResistance => 2; + [Flippable(0x13be, 0x13c3)] + public class ChainLegs : BaseArmor + { + [Constructible] + public ChainLegs() : base(0x13BE) + { + Weight = 7.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 60; + public ChainLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 60; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 4; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 1; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -3; + public override int InitMinHits => 45; + public override int InitMaxHits => 60; - public override int ArmorBase => 28; + public override int AosStrReq => 60; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; + public override int OldDexBonus => -3; - [Constructible] - public ChainLegs() : base( 0x13BE ) - { - Weight = 7.0; - } + public override int ArmorBase => 28; - public ChainLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/DaemonBone/DaemonArms.cs b/Scripts/Items/Armor/DaemonBone/DaemonArms.cs index 005a6b667..85a36899a 100644 --- a/Scripts/Items/Armor/DaemonBone/DaemonArms.cs +++ b/Scripts/Items/Armor/DaemonBone/DaemonArms.cs @@ -1,60 +1,60 @@ namespace Server.Items { - [FlippableAttribute( 0x144e, 0x1453 )] - public class DaemonArms : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 7; + [Flippable(0x144e, 0x1453)] + public class DaemonArms : BaseArmor + { + [Constructible] + public DaemonArms() : base(0x144E) + { + Weight = 2.0; + Hue = 0x648; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + ArmorAttributes.SelfRepair = 1; + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public DaemonArms(Serial serial) : base(serial) + { + } - public override int OldDexBonus => -2; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 7; - public override int ArmorBase => 46; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - public override int LabelNumber => 1041371; // daemon bone arms + public override int OldDexBonus => -2; - [Constructible] - public DaemonArms() : base( 0x144E ) - { - Weight = 2.0; - Hue = 0x648; + public override int ArmorBase => 46; - ArmorAttributes.SelfRepair = 1; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public DaemonArms( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041371; // daemon bone arms - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - if ( Weight == 1.0 ) - Weight = 2.0; - } + if (Weight == 1.0) + Weight = 2.0; + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( ArmorAttributes.SelfRepair == 0 ) - ArmorAttributes.SelfRepair = 1; - } - } -} + if (ArmorAttributes.SelfRepair == 0) + ArmorAttributes.SelfRepair = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/DaemonBone/DaemonChest.cs b/Scripts/Items/Armor/DaemonBone/DaemonChest.cs index 559c422b2..1f44b9055 100644 --- a/Scripts/Items/Armor/DaemonBone/DaemonChest.cs +++ b/Scripts/Items/Armor/DaemonBone/DaemonChest.cs @@ -1,60 +1,60 @@ namespace Server.Items { - [FlippableAttribute( 0x144f, 0x1454 )] - public class DaemonChest : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 7; + [Flippable(0x144f, 0x1454)] + public class DaemonChest : BaseArmor + { + [Constructible] + public DaemonChest() : base(0x144F) + { + Weight = 6.0; + Hue = 0x648; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + ArmorAttributes.SelfRepair = 1; + } - public override int AosStrReq => 60; - public override int OldStrReq => 40; + public DaemonChest(Serial serial) : base(serial) + { + } - public override int OldDexBonus => -6; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 7; - public override int ArmorBase => 46; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 60; + public override int OldStrReq => 40; - public override int LabelNumber => 1041372; // daemon bone armor + public override int OldDexBonus => -6; - [Constructible] - public DaemonChest() : base( 0x144F ) - { - Weight = 6.0; - Hue = 0x648; + public override int ArmorBase => 46; - ArmorAttributes.SelfRepair = 1; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public DaemonChest( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041372; // daemon bone armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 6.0; + if (Weight == 1.0) + Weight = 6.0; - if ( ArmorAttributes.SelfRepair == 0 ) - ArmorAttributes.SelfRepair = 1; - } - } -} + if (ArmorAttributes.SelfRepair == 0) + ArmorAttributes.SelfRepair = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/DaemonBone/DaemonGloves.cs b/Scripts/Items/Armor/DaemonBone/DaemonGloves.cs index 980fe8d44..92b5d1aae 100644 --- a/Scripts/Items/Armor/DaemonBone/DaemonGloves.cs +++ b/Scripts/Items/Armor/DaemonBone/DaemonGloves.cs @@ -1,60 +1,60 @@ namespace Server.Items { - [FlippableAttribute( 0x1450, 0x1455 )] - public class DaemonGloves : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 7; + [Flippable(0x1450, 0x1455)] + public class DaemonGloves : BaseArmor + { + [Constructible] + public DaemonGloves() : base(0x1450) + { + Weight = 2.0; + Hue = 0x648; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + ArmorAttributes.SelfRepair = 1; + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public DaemonGloves(Serial serial) : base(serial) + { + } - public override int OldDexBonus => -1; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 7; - public override int ArmorBase => 46; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - public override int LabelNumber => 1041373; // daemon bone gloves + public override int OldDexBonus => -1; - [Constructible] - public DaemonGloves() : base( 0x1450 ) - { - Weight = 2.0; - Hue = 0x648; + public override int ArmorBase => 46; - ArmorAttributes.SelfRepair = 1; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public DaemonGloves( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041373; // daemon bone gloves - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; + if (Weight == 1.0) + Weight = 2.0; - if ( ArmorAttributes.SelfRepair == 0 ) - ArmorAttributes.SelfRepair = 1; - } - } -} + if (ArmorAttributes.SelfRepair == 0) + ArmorAttributes.SelfRepair = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/DaemonBone/DaemonLegs.cs b/Scripts/Items/Armor/DaemonBone/DaemonLegs.cs index be0dabe91..a45f1a903 100644 --- a/Scripts/Items/Armor/DaemonBone/DaemonLegs.cs +++ b/Scripts/Items/Armor/DaemonBone/DaemonLegs.cs @@ -1,55 +1,55 @@ namespace Server.Items { - [FlippableAttribute( 0x1452, 0x1457 )] - public class DaemonLegs : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 7; + [Flippable(0x1452, 0x1457)] + public class DaemonLegs : BaseArmor + { + [Constructible] + public DaemonLegs() : base(0x1452) + { + Weight = 3.0; + Hue = 0x648; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + ArmorAttributes.SelfRepair = 1; + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public DaemonLegs(Serial serial) : base(serial) + { + } - public override int OldDexBonus => -4; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 7; - public override int ArmorBase => 46; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - public override int LabelNumber => 1041375; // daemon bone leggings + public override int OldDexBonus => -4; - [Constructible] - public DaemonLegs() : base( 0x1452 ) - { - Weight = 3.0; - Hue = 0x648; + public override int ArmorBase => 46; - ArmorAttributes.SelfRepair = 1; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public DaemonLegs( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041375; // daemon bone leggings - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( ArmorAttributes.SelfRepair == 0 ) - ArmorAttributes.SelfRepair = 1; - } - } -} + if (ArmorAttributes.SelfRepair == 0) + ArmorAttributes.SelfRepair = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Dragon/DragonArms.cs b/Scripts/Items/Armor/Dragon/DragonArms.cs index f3da43232..4df01ee1c 100644 --- a/Scripts/Items/Armor/Dragon/DragonArms.cs +++ b/Scripts/Items/Armor/Dragon/DragonArms.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2657, 0x2658 )] - public class DragonArms : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x2657, 0x2658)] + public class DragonArms : BaseArmor + { + [Constructible] + public DragonArms() : base(0x2657) + { + Weight = 5.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public DragonArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 75; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -2; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override int ArmorBase => 40; + public override int AosStrReq => 75; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; - public override CraftResource DefaultResource => CraftResource.RedScales; + public override int OldDexBonus => -2; - [Constructible] - public DragonArms() : base( 0x2657 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public DragonArms( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; + public override CraftResource DefaultResource => CraftResource.RedScales; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 15.0; - } - } -} + if (Weight == 1.0) + Weight = 15.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Dragon/DragonChest.cs b/Scripts/Items/Armor/Dragon/DragonChest.cs index dc50f833d..e17f4afb7 100644 --- a/Scripts/Items/Armor/Dragon/DragonChest.cs +++ b/Scripts/Items/Armor/Dragon/DragonChest.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2641, 0x2642 )] - public class DragonChest : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x2641, 0x2642)] + public class DragonChest : BaseArmor + { + [Constructible] + public DragonChest() : base(0x2641) + { + Weight = 10.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public DragonChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 75; - public override int OldStrReq => 60; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -8; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override int ArmorBase => 40; + public override int AosStrReq => 75; + public override int OldStrReq => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; - public override CraftResource DefaultResource => CraftResource.RedScales; + public override int OldDexBonus => -8; - [Constructible] - public DragonChest() : base( 0x2641 ) - { - Weight = 10.0; - } + public override int ArmorBase => 40; - public DragonChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; + public override CraftResource DefaultResource => CraftResource.RedScales; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 15.0; - } - } -} + if (Weight == 1.0) + Weight = 15.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Dragon/DragonGloves.cs b/Scripts/Items/Armor/Dragon/DragonGloves.cs index 0098453df..a4c04a460 100644 --- a/Scripts/Items/Armor/Dragon/DragonGloves.cs +++ b/Scripts/Items/Armor/Dragon/DragonGloves.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2643, 0x2644 )] - public class DragonGloves : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x2643, 0x2644)] + public class DragonGloves : BaseArmor + { + [Constructible] + public DragonGloves() : base(0x2643) + { + Weight = 2.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public DragonGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 75; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -2; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override int ArmorBase => 40; + public override int AosStrReq => 75; + public override int OldStrReq => 30; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; - public override CraftResource DefaultResource => CraftResource.RedScales; + public override int OldDexBonus => -2; - [Constructible] - public DragonGloves() : base( 0x2643 ) - { - Weight = 2.0; - } + public override int ArmorBase => 40; - public DragonGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; + public override CraftResource DefaultResource => CraftResource.RedScales; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Dragon/DragonHelm.cs b/Scripts/Items/Armor/Dragon/DragonHelm.cs index 33c927019..8955ca0c2 100644 --- a/Scripts/Items/Armor/Dragon/DragonHelm.cs +++ b/Scripts/Items/Armor/Dragon/DragonHelm.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [Flippable( 0x2645, 0x2646 )] - public class DragonHelm : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x2645, 0x2646)] + public class DragonHelm : BaseArmor + { + [Constructible] + public DragonHelm() : base(0x2645) + { + Weight = 5.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public DragonHelm(Serial serial) : base(serial) + { + } - public override int AosStrReq => 75; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -1; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override int ArmorBase => 40; + public override int AosStrReq => 75; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; - public override CraftResource DefaultResource => CraftResource.RedScales; + public override int OldDexBonus => -1; - [Constructible] - public DragonHelm() : base( 0x2645 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public DragonHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; + public override CraftResource DefaultResource => CraftResource.RedScales; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Dragon/DragonLegs.cs b/Scripts/Items/Armor/Dragon/DragonLegs.cs index 948a76612..2b9f9c64e 100644 --- a/Scripts/Items/Armor/Dragon/DragonLegs.cs +++ b/Scripts/Items/Armor/Dragon/DragonLegs.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2647, 0x2648 )] - public class DragonLegs : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x2647, 0x2648)] + public class DragonLegs : BaseArmor + { + [Constructible] + public DragonLegs() : base(0x2647) + { + Weight = 6.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public DragonLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 75; - public override int OldStrReq => 60; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -6; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override int ArmorBase => 40; + public override int AosStrReq => 75; + public override int OldStrReq => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; - public override CraftResource DefaultResource => CraftResource.RedScales; + public override int OldDexBonus => -6; - [Constructible] - public DragonLegs() : base( 0x2647 ) - { - Weight = 6.0; - } + public override int ArmorBase => 40; - public DragonLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; + public override CraftResource DefaultResource => CraftResource.RedScales; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/AnthropomorphistGlasses.cs b/Scripts/Items/Armor/Glasses/AnthropomorphistGlasses.cs index 46fa599ee..0d2840803 100644 --- a/Scripts/Items/Armor/Glasses/AnthropomorphistGlasses.cs +++ b/Scripts/Items/Armor/Glasses/AnthropomorphistGlasses.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class AnthropomorphistGlasses : ElvenGlasses - { - public override int LabelNumber => 1073379; //Anthropomorphist Reading Glasses + public class AnthropomorphistGlasses : ElvenGlasses + { + [Constructible] + public AnthropomorphistGlasses() + { + Attributes.BonusHits = 5; + Attributes.RegenMana = 3; + Attributes.ReflectPhysical = 20; - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 20; - public override int BaseEnergyResistance => 20; + Hue = 0x80; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public AnthropomorphistGlasses(Serial serial) : base(serial) + { + } + public override int LabelNumber => 1073379; //Anthropomorphist Reading Glasses - [Constructible] - public AnthropomorphistGlasses() - { - Attributes.BonusHits = 5; - Attributes.RegenMana = 3; - Attributes.ReflectPhysical = 20; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 20; + public override int BaseEnergyResistance => 20; - Hue = 0x80; - } - public AnthropomorphistGlasses( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( version == 0 && Hue == 0 ) - Hue = 0x80; - } - } -} + if (version == 0 && Hue == 0) + Hue = 0x80; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/ArtsGlasses.cs b/Scripts/Items/Armor/Glasses/ArtsGlasses.cs index fc3ff993d..f1260a2e7 100644 --- a/Scripts/Items/Armor/Glasses/ArtsGlasses.cs +++ b/Scripts/Items/Armor/Glasses/ArtsGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class ArtsGlasses : ElvenGlasses - { - public override int LabelNumber => 1073363; //Reading Glasses of the Arts + public class ArtsGlasses : ElvenGlasses + { + [Constructible] + public ArtsGlasses() + { + Attributes.BonusStr = 5; + Attributes.BonusInt = 5; + Attributes.BonusHits = 15; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 8; - public override int BaseColdResistance => 8; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 10; + Hue = 0x73; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public ArtsGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public ArtsGlasses() - { - Attributes.BonusStr = 5; - Attributes.BonusInt = 5; - Attributes.BonusHits = 15; + public override int LabelNumber => 1073363; //Reading Glasses of the Arts - Hue = 0x73; - } - public ArtsGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 8; + public override int BaseColdResistance => 8; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x73; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x73; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/ElvenGlasses.cs b/Scripts/Items/Armor/Glasses/ElvenGlasses.cs index a446c226f..80a321fb7 100644 --- a/Scripts/Items/Armor/Glasses/ElvenGlasses.cs +++ b/Scripts/Items/Armor/Glasses/ElvenGlasses.cs @@ -1,144 +1,144 @@ namespace Server.Items { - public class ElvenGlasses : BaseArmor - { - public override int LabelNumber => 1032216; // elven glasses + public class ElvenGlasses : BaseArmor + { + private AosWeaponAttributes m_AosWeaponAttributes; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Constructible] + public ElvenGlasses() : base(0x2FB8) + { + Weight = 2; + m_AosWeaponAttributes = new AosWeaponAttributes(this); + } - public override int InitMinHits => 36; - public override int InitMaxHits => 48; + public ElvenGlasses(Serial serial) : base(serial) + { + } - public override int AosStrReq => 45; - public override int OldStrReq => 40; + public override int LabelNumber => 1032216; // elven glasses - public override int ArmorBase => 30; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int InitMinHits => 36; + public override int InitMaxHits => 48; - private AosWeaponAttributes m_AosWeaponAttributes; + public override int AosStrReq => 45; + public override int OldStrReq => 40; - [CommandProperty( AccessLevel.GameMaster )] - public AosWeaponAttributes WeaponAttributes - { - get => m_AosWeaponAttributes; - set{} - } + public override int ArmorBase => 30; - [Constructible] - public ElvenGlasses() : base( 0x2FB8 ) - { - Weight = 2; - m_AosWeaponAttributes = new AosWeaponAttributes( this ); - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public ElvenGlasses( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public AosWeaponAttributes WeaponAttributes + { + get => m_AosWeaponAttributes; + set { } + } - public override void AppendChildNameProperties( ObjectPropertyList list ) - { - base.AppendChildNameProperties( list ); + public override void AppendChildNameProperties(ObjectPropertyList list) + { + base.AppendChildNameProperties(list); - int prop; + int prop; - if ( (prop = m_AosWeaponAttributes.HitColdArea) != 0 ) - list.Add( 1060416, prop.ToString() ); // hit cold area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitColdArea) != 0) + list.Add(1060416, prop.ToString()); // hit cold area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitDispel) != 0 ) - list.Add( 1060417, prop.ToString() ); // hit dispel ~1_val~% + if ((prop = m_AosWeaponAttributes.HitDispel) != 0) + list.Add(1060417, prop.ToString()); // hit dispel ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitEnergyArea) != 0 ) - list.Add( 1060418, prop.ToString() ); // hit energy area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitEnergyArea) != 0) + list.Add(1060418, prop.ToString()); // hit energy area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitFireArea) != 0 ) - list.Add( 1060419, prop.ToString() ); // hit fire area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitFireArea) != 0) + list.Add(1060419, prop.ToString()); // hit fire area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitFireball) != 0 ) - list.Add( 1060420, prop.ToString() ); // hit fireball ~1_val~% + if ((prop = m_AosWeaponAttributes.HitFireball) != 0) + list.Add(1060420, prop.ToString()); // hit fireball ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitHarm) != 0 ) - list.Add( 1060421, prop.ToString() ); // hit harm ~1_val~% + if ((prop = m_AosWeaponAttributes.HitHarm) != 0) + list.Add(1060421, prop.ToString()); // hit harm ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLeechHits) != 0 ) - list.Add( 1060422, prop.ToString() ); // hit life leech ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLeechHits) != 0) + list.Add(1060422, prop.ToString()); // hit life leech ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLightning) != 0 ) - list.Add( 1060423, prop.ToString() ); // hit lightning ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLightning) != 0) + list.Add(1060423, prop.ToString()); // hit lightning ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLowerAttack) != 0 ) - list.Add( 1060424, prop.ToString() ); // hit lower attack ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLowerAttack) != 0) + list.Add(1060424, prop.ToString()); // hit lower attack ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLowerDefend) != 0 ) - list.Add( 1060425, prop.ToString() ); // hit lower defense ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLowerDefend) != 0) + list.Add(1060425, prop.ToString()); // hit lower defense ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitMagicArrow) != 0 ) - list.Add( 1060426, prop.ToString() ); // hit magic arrow ~1_val~% + if ((prop = m_AosWeaponAttributes.HitMagicArrow) != 0) + list.Add(1060426, prop.ToString()); // hit magic arrow ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLeechMana) != 0 ) - list.Add( 1060427, prop.ToString() ); // hit mana leech ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLeechMana) != 0) + list.Add(1060427, prop.ToString()); // hit mana leech ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitPhysicalArea) != 0 ) - list.Add( 1060428, prop.ToString() ); // hit physical area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitPhysicalArea) != 0) + list.Add(1060428, prop.ToString()); // hit physical area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitPoisonArea) != 0 ) - list.Add( 1060429, prop.ToString() ); // hit poison area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitPoisonArea) != 0) + list.Add(1060429, prop.ToString()); // hit poison area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLeechStam) != 0 ) - list.Add( 1060430, prop.ToString() ); // hit stamina leech ~1_val~% - } + if ((prop = m_AosWeaponAttributes.HitLeechStam) != 0) + list.Add(1060430, prop.ToString()); // hit stamina leech ~1_val~% + } - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } - private enum SaveFlag - { - None = 0x00000000, - WeaponAttributes = 0x00000001, - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version - writer.Write( (int) 0 ); // version + SaveFlag flags = SaveFlag.None; - SaveFlag flags = SaveFlag.None; + SetSaveFlag(ref flags, SaveFlag.WeaponAttributes, !m_AosWeaponAttributes.IsEmpty); - SetSaveFlag( ref flags, SaveFlag.WeaponAttributes, !m_AosWeaponAttributes.IsEmpty ); + writer.Write((int)flags); - writer.Write( (int) flags ); + if (GetSaveFlag(flags, SaveFlag.WeaponAttributes)) + m_AosWeaponAttributes.Serialize(writer); + } - if ( GetSaveFlag( flags, SaveFlag.WeaponAttributes ) ) - m_AosWeaponAttributes.Serialize( writer ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + SaveFlag flags = (SaveFlag)reader.ReadInt(); - SaveFlag flags = (SaveFlag) reader.ReadInt(); + if (GetSaveFlag(flags, SaveFlag.WeaponAttributes)) + m_AosWeaponAttributes = new AosWeaponAttributes(this, reader); + else + m_AosWeaponAttributes = new AosWeaponAttributes(this); + } - if ( GetSaveFlag( flags, SaveFlag.WeaponAttributes ) ) - m_AosWeaponAttributes = new AosWeaponAttributes( this, reader ); - else - m_AosWeaponAttributes = new AosWeaponAttributes( this ); - } - } -} + private enum SaveFlag + { + None = 0x00000000, + WeaponAttributes = 0x00000001 + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/FoldedSteelGlasses.cs b/Scripts/Items/Armor/Glasses/FoldedSteelGlasses.cs index d9f897d68..78a3d4e14 100644 --- a/Scripts/Items/Armor/Glasses/FoldedSteelGlasses.cs +++ b/Scripts/Items/Armor/Glasses/FoldedSteelGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class FoldedSteelGlasses : ElvenGlasses - { - public override int LabelNumber => 1073380; //Folded Steel Reading Glasses + public class FoldedSteelGlasses : ElvenGlasses + { + [Constructible] + public FoldedSteelGlasses() + { + Attributes.BonusStr = 8; + Attributes.NightSight = 1; + Attributes.DefendChance = 15; - public override int BasePhysicalResistance => 20; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + Hue = 0x47E; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public FoldedSteelGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public FoldedSteelGlasses() - { - Attributes.BonusStr = 8; - Attributes.NightSight = 1; - Attributes.DefendChance = 15; + public override int LabelNumber => 1073380; //Folded Steel Reading Glasses - Hue = 0x47E; - } - public FoldedSteelGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 20; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x47E; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x47E; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/LightOfWayGlasses.cs b/Scripts/Items/Armor/Glasses/LightOfWayGlasses.cs index a9fbe9a6b..77ae21277 100644 --- a/Scripts/Items/Armor/Glasses/LightOfWayGlasses.cs +++ b/Scripts/Items/Armor/Glasses/LightOfWayGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class LightOfWayGlasses : ElvenGlasses - { - public override int LabelNumber => 1073378; //Light Of Way Reading Glasses + public class LightOfWayGlasses : ElvenGlasses + { + [Constructible] + public LightOfWayGlasses() + { + Attributes.BonusStr = 7; + Attributes.BonusInt = 5; + Attributes.WeaponDamage = 30; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + Hue = 0x256; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public LightOfWayGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public LightOfWayGlasses() - { - Attributes.BonusStr = 7; - Attributes.BonusInt = 5; - Attributes.WeaponDamage = 30; + public override int LabelNumber => 1073378; //Light Of Way Reading Glasses - Hue = 0x256; - } - public LightOfWayGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x256; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x256; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/LyricalGlasses.cs b/Scripts/Items/Armor/Glasses/LyricalGlasses.cs index b035939f9..7d1680f02 100644 --- a/Scripts/Items/Armor/Glasses/LyricalGlasses.cs +++ b/Scripts/Items/Armor/Glasses/LyricalGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class LyricalGlasses : ElvenGlasses - { - public override int LabelNumber => 1073382; //Lyrical Reading Glasses + public class LyricalGlasses : ElvenGlasses + { + [Constructible] + public LyricalGlasses() + { + WeaponAttributes.HitLowerDefend = 20; + Attributes.NightSight = 1; + Attributes.ReflectPhysical = 15; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + Hue = 0x47F; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public LyricalGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public LyricalGlasses() - { - WeaponAttributes.HitLowerDefend = 20; - Attributes.NightSight = 1; - Attributes.ReflectPhysical = 15; + public override int LabelNumber => 1073382; //Lyrical Reading Glasses - Hue = 0x47F; - } - public LyricalGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x47F; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x47F; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/MaceShieldGlasses.cs b/Scripts/Items/Armor/Glasses/MaceShieldGlasses.cs index b62cfe5f1..2f988fc4e 100644 --- a/Scripts/Items/Armor/Glasses/MaceShieldGlasses.cs +++ b/Scripts/Items/Armor/Glasses/MaceShieldGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class MaceShieldGlasses : ElvenGlasses - { - public override int LabelNumber => 1073381; //Mace And Shield Reading Glasses + public class MaceShieldGlasses : ElvenGlasses + { + [Constructible] + public MaceShieldGlasses() + { + WeaponAttributes.HitLowerDefend = 30; + Attributes.BonusStr = 10; + Attributes.BonusDex = 5; - public override int BasePhysicalResistance => 25; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + Hue = 0x1DD; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public MaceShieldGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public MaceShieldGlasses() - { - WeaponAttributes.HitLowerDefend = 30; - Attributes.BonusStr = 10; - Attributes.BonusDex = 5; + public override int LabelNumber => 1073381; //Mace And Shield Reading Glasses - Hue = 0x1DD; - } - public MaceShieldGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 25; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x1DD; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x1DD; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/MaritimeGlasses.cs b/Scripts/Items/Armor/Glasses/MaritimeGlasses.cs index 7254db1b0..8a7fbde93 100644 --- a/Scripts/Items/Armor/Glasses/MaritimeGlasses.cs +++ b/Scripts/Items/Armor/Glasses/MaritimeGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class MaritimeGlasses : ElvenGlasses - { - public override int LabelNumber => 1073364; //Maritime Reading Glasses + public class MaritimeGlasses : ElvenGlasses + { + [Constructible] + public MaritimeGlasses() + { + Attributes.Luck = 150; + Attributes.NightSight = 1; + Attributes.ReflectPhysical = 20; - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 30; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + Hue = 0x581; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public MaritimeGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public MaritimeGlasses() - { - Attributes.Luck = 150; - Attributes.NightSight = 1; - Attributes.ReflectPhysical = 20; + public override int LabelNumber => 1073364; //Maritime Reading Glasses - Hue = 0x581; - } - public MaritimeGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 30; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x581; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x581; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/NecromanticGlasses.cs b/Scripts/Items/Armor/Glasses/NecromanticGlasses.cs index ac759e2a6..3b1db4e43 100644 --- a/Scripts/Items/Armor/Glasses/NecromanticGlasses.cs +++ b/Scripts/Items/Armor/Glasses/NecromanticGlasses.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class NecromanticGlasses : ElvenGlasses - { - public override int LabelNumber => 1073377; //Necromantic Reading Glasses + public class NecromanticGlasses : ElvenGlasses + { + [Constructible] + public NecromanticGlasses() + { + Attributes.LowerManaCost = 15; + Attributes.LowerRegCost = 30; - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + Hue = 0x22D; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public NecromanticGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public NecromanticGlasses() - { - Attributes.LowerManaCost = 15; - Attributes.LowerRegCost = 30; + public override int LabelNumber => 1073377; //Necromantic Reading Glasses - Hue = 0x22D; - } - public NecromanticGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x22D; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x22D; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/PoisonedGlasses.cs b/Scripts/Items/Armor/Glasses/PoisonedGlasses.cs index 9bd2534db..3c19c9f2f 100644 --- a/Scripts/Items/Armor/Glasses/PoisonedGlasses.cs +++ b/Scripts/Items/Armor/Glasses/PoisonedGlasses.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class PoisonedGlasses : ElvenGlasses - { - public override int LabelNumber => 1073376; //Poisoned Reading Glasses + public class PoisonedGlasses : ElvenGlasses + { + [Constructible] + public PoisonedGlasses() + { + Attributes.BonusStam = 3; + Attributes.RegenStam = 4; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 30; - public override int BaseEnergyResistance => 10; + Hue = 0x113; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public PoisonedGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public PoisonedGlasses() - { - Attributes.BonusStam = 3; - Attributes.RegenStam = 4; + public override int LabelNumber => 1073376; //Poisoned Reading Glasses - Hue = 0x113; - } - public PoisonedGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 30; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x113; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x113; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/TradeGlasses.cs b/Scripts/Items/Armor/Glasses/TradeGlasses.cs index 88e23b4ea..72d9c0613 100644 --- a/Scripts/Items/Armor/Glasses/TradeGlasses.cs +++ b/Scripts/Items/Armor/Glasses/TradeGlasses.cs @@ -1,38 +1,39 @@ namespace Server.Items { - public class TradeGlasses : ElvenGlasses - { - public override int LabelNumber => 1073362; //Reading Glasses of the Trades + public class TradeGlasses : ElvenGlasses + { + [Constructible] + public TradeGlasses() + { + Attributes.BonusStr = 10; + Attributes.BonusInt = 10; + } - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + public TradeGlasses(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1073362; //Reading Glasses of the Trades - [Constructible] - public TradeGlasses() - { - Attributes.BonusStr = 10; - Attributes.BonusInt = 10; - } - public TradeGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/TreasureTrinketGlasses.cs b/Scripts/Items/Armor/Glasses/TreasureTrinketGlasses.cs index 88bb5943a..2d597f788 100644 --- a/Scripts/Items/Armor/Glasses/TreasureTrinketGlasses.cs +++ b/Scripts/Items/Armor/Glasses/TreasureTrinketGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class TreasureTrinketGlasses : ElvenGlasses - { - public override int LabelNumber => 1073373; //Treasures and Trinkets Reading Glasses + public class TreasureTrinketGlasses : ElvenGlasses + { + [Constructible] + public TreasureTrinketGlasses() + { + Attributes.BonusInt = 10; + Attributes.BonusHits = 5; + Attributes.SpellDamage = 10; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + Hue = 0x1C2; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public TreasureTrinketGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public TreasureTrinketGlasses() - { - Attributes.BonusInt = 10; - Attributes.BonusHits = 5; - Attributes.SpellDamage = 10; + public override int LabelNumber => 1073373; //Treasures and Trinkets Reading Glasses - Hue = 0x1C2; - } - public TreasureTrinketGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x1C2; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x1C2; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Glasses/WizardsGlasses.cs b/Scripts/Items/Armor/Glasses/WizardsGlasses.cs index f4ef6d422..5c6a1ad5a 100644 --- a/Scripts/Items/Armor/Glasses/WizardsGlasses.cs +++ b/Scripts/Items/Armor/Glasses/WizardsGlasses.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class WizardsGlasses : ElvenGlasses - { - public override int LabelNumber => 1073374; //Wizard's Crystal Reading Glasses + public class WizardsGlasses : ElvenGlasses + { + [Constructible] + public WizardsGlasses() + { + Attributes.BonusMana = 10; + Attributes.RegenMana = 3; + Attributes.SpellDamage = 15; - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + Hue = 0x2B0; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public WizardsGlasses(Serial serial) : base(serial) + { + } - [Constructible] - public WizardsGlasses() - { - Attributes.BonusMana = 10; - Attributes.RegenMana = 3; - Attributes.SpellDamage = 15; + public override int LabelNumber => 1073374; //Wizard's Crystal Reading Glasses - Hue = 0x2B0; - } - public WizardsGlasses( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - if ( version == 0 && Hue == 0 ) - Hue = 0x2B0; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Hue == 0) + Hue = 0x2B0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/Bascinet.cs b/Scripts/Items/Armor/Helmets/Bascinet.cs index 143b07803..3bef2c1e7 100644 --- a/Scripts/Items/Armor/Helmets/Bascinet.cs +++ b/Scripts/Items/Armor/Helmets/Bascinet.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class Bascinet : BaseArmor - { - public override int BasePhysicalResistance => 7; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 2; + public class Bascinet : BaseArmor + { + [Constructible] + public Bascinet() : base(0x140C) + { + Weight = 5.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public Bascinet(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 7; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 18; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 40; + public override int OldStrReq => 10; - [Constructible] - public Bascinet() : base( 0x140C ) - { - Weight = 5.0; - } + public override int ArmorBase => 18; - public Bascinet( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/BoneHelm.cs b/Scripts/Items/Armor/Helmets/BoneHelm.cs index 75caa9870..982a00010 100644 --- a/Scripts/Items/Armor/Helmets/BoneHelm.cs +++ b/Scripts/Items/Armor/Helmets/BoneHelm.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x1451, 0x1456 )] - public class BoneHelm : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 4; + [Flippable(0x1451, 0x1456)] + public class BoneHelm : BaseArmor + { + [Constructible] + public BoneHelm() : base(0x1451) + { + Weight = 3.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 30; + public BoneHelm(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 30; + public override int InitMinHits => 25; + public override int InitMaxHits => 30; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 20; + public override int OldStrReq => 40; - [Constructible] - public BoneHelm() : base( 0x1451 ) - { - Weight = 3.0; - } + public override int ArmorBase => 30; - public BoneHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - if ( Weight == 1.0 ) - Weight = 3.0; - } + if (Weight == 1.0) + Weight = 3.0; + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/ChainCoif.cs b/Scripts/Items/Armor/Helmets/ChainCoif.cs index b787028e6..3839b26fc 100644 --- a/Scripts/Items/Armor/Helmets/ChainCoif.cs +++ b/Scripts/Items/Armor/Helmets/ChainCoif.cs @@ -1,44 +1,44 @@ namespace Server.Items { - [FlippableAttribute( 0x13BB, 0x13C0 )] - public class ChainCoif : BaseArmor - { - public override int BasePhysicalResistance => 4; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 1; - public override int BaseEnergyResistance => 2; + [Flippable(0x13BB, 0x13C0)] + public class ChainCoif : BaseArmor + { + [Constructible] + public ChainCoif() : base(0x13BB) + { + Weight = 1.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 60; + public ChainCoif(Serial serial) : base(serial) + { + } - public override int AosStrReq => 60; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 4; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 1; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 28; + public override int InitMinHits => 35; + public override int InitMaxHits => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; + public override int AosStrReq => 60; + public override int OldStrReq => 20; - [Constructible] - public ChainCoif () : base( 0x13BB ) - { - Weight = 1.0; - } + public override int ArmorBase => 28; - public ChainCoif ( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Chainmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/Circlet.cs b/Scripts/Items/Armor/Helmets/Circlet.cs index 3e710a23a..8ab4b7df1 100644 --- a/Scripts/Items/Armor/Helmets/Circlet.cs +++ b/Scripts/Items/Armor/Helmets/Circlet.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2B6E, 0x3165 )] - public class Circlet : BaseArmor - { - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 5; + [Flippable(0x2B6E, 0x3165)] + public class Circlet : BaseArmor + { + [Constructible] + public Circlet() : base(0x2B6E) + { + Weight = 2.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public Circlet(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 30; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 30; - public override Race RequiredRace => Race.Elf; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - [Constructible] - public Circlet() : base( 0x2B6E ) - { - Weight = 2.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public Circlet( Serial serial ) : base( serial ) - { - } + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/CloseHelm.cs b/Scripts/Items/Armor/Helmets/CloseHelm.cs index 0b932e80e..a8b0739c8 100644 --- a/Scripts/Items/Armor/Helmets/CloseHelm.cs +++ b/Scripts/Items/Armor/Helmets/CloseHelm.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class CloseHelm : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class CloseHelm : BaseArmor + { + [Constructible] + public CloseHelm() : base(0x1408) + { + Weight = 5.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 60; + public CloseHelm(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 30; + public override int InitMinHits => 45; + public override int InitMaxHits => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - [Constructible] - public CloseHelm() : base( 0x1408 ) - { - Weight = 5.0; - } + public override int ArmorBase => 30; - public CloseHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/DaemonHelm.cs b/Scripts/Items/Armor/Helmets/DaemonHelm.cs index 032ddce0f..be46277fa 100644 --- a/Scripts/Items/Armor/Helmets/DaemonHelm.cs +++ b/Scripts/Items/Armor/Helmets/DaemonHelm.cs @@ -1,58 +1,58 @@ namespace Server.Items { - [FlippableAttribute( 0x1451, 0x1456 )] - public class DaemonHelm : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 7; + [Flippable(0x1451, 0x1456)] + public class DaemonHelm : BaseArmor + { + [Constructible] + public DaemonHelm() : base(0x1451) + { + Hue = 0x648; + Weight = 3.0; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + ArmorAttributes.SelfRepair = 1; + } - public override int AosStrReq => 20; - public override int OldStrReq => 40; + public DaemonHelm(Serial serial) : base(serial) + { + } - public override int ArmorBase => 46; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 7; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override int LabelNumber => 1041374; // daemon bone helmet + public override int AosStrReq => 20; + public override int OldStrReq => 40; - [Constructible] - public DaemonHelm() : base( 0x1451 ) - { - Hue = 0x648; - Weight = 3.0; + public override int ArmorBase => 46; - ArmorAttributes.SelfRepair = 1; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Bone; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public DaemonHelm( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041374; // daemon bone helmet - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 3.0; + if (Weight == 1.0) + Weight = 3.0; - if ( ArmorAttributes.SelfRepair == 0 ) - ArmorAttributes.SelfRepair = 1; - } - } -} + if (ArmorAttributes.SelfRepair == 0) + ArmorAttributes.SelfRepair = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/GemmedCirclet.cs b/Scripts/Items/Armor/Helmets/GemmedCirclet.cs index 545826be9..6259e1a9a 100644 --- a/Scripts/Items/Armor/Helmets/GemmedCirclet.cs +++ b/Scripts/Items/Armor/Helmets/GemmedCirclet.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2B70, 0x3167 )] - public class GemmedCirclet : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B70, 0x3167)] + public class GemmedCirclet : BaseArmor + { + [Constructible] + public GemmedCirclet() : base(0x2B70) + { + Weight = 2.0; + } - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 5; + public GemmedCirclet(Serial serial) : base(serial) + { + } - public override int InitMinHits => 20; - public override int InitMaxHits => 35; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 30; + public override int InitMinHits => 20; + public override int InitMaxHits => 35; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 30; - [Constructible] - public GemmedCirclet() : base( 0x2B70 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public GemmedCirclet( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/Helmet.cs b/Scripts/Items/Armor/Helmets/Helmet.cs index 7d60b8a4c..ec2802f18 100644 --- a/Scripts/Items/Armor/Helmets/Helmet.cs +++ b/Scripts/Items/Armor/Helmets/Helmet.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class Helmet : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class Helmet : BaseArmor + { + [Constructible] + public Helmet() : base(0x140A) + { + Weight = 5.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 60; + public Helmet(Serial serial) : base(serial) + { + } - public override int AosStrReq => 45; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 30; + public override int InitMinHits => 45; + public override int InitMaxHits => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 45; + public override int OldStrReq => 40; - [Constructible] - public Helmet() : base( 0x140A ) - { - Weight = 5.0; - } + public override int ArmorBase => 30; - public Helmet( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/LeatherCap.cs b/Scripts/Items/Armor/Helmets/LeatherCap.cs index 3111a371a..67110387e 100644 --- a/Scripts/Items/Armor/Helmets/LeatherCap.cs +++ b/Scripts/Items/Armor/Helmets/LeatherCap.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x1db9, 0x1dba )] - public class LeatherCap : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x1db9, 0x1dba)] + public class LeatherCap : BaseArmor + { + [Constructible] + public LeatherCap() : base(0x1DB9) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherCap(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeatherCap() : base( 0x1DB9 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherCap( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/NorseHelm.cs b/Scripts/Items/Armor/Helmets/NorseHelm.cs index 023ad28ea..359e40288 100644 --- a/Scripts/Items/Armor/Helmets/NorseHelm.cs +++ b/Scripts/Items/Armor/Helmets/NorseHelm.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class NorseHelm : BaseArmor - { - public override int BasePhysicalResistance => 4; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 2; + public class NorseHelm : BaseArmor + { + [Constructible] + public NorseHelm() : base(0x140E) + { + Weight = 5.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 60; + public NorseHelm(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 4; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 30; + public override int InitMinHits => 45; + public override int InitMaxHits => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 55; + public override int OldStrReq => 40; - [Constructible] - public NorseHelm() : base( 0x140E ) - { - Weight = 5.0; - } + public override int ArmorBase => 30; - public NorseHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/OrcHelm.cs b/Scripts/Items/Armor/Helmets/OrcHelm.cs index a78467289..17affa02a 100644 --- a/Scripts/Items/Armor/Helmets/OrcHelm.cs +++ b/Scripts/Items/Armor/Helmets/OrcHelm.cs @@ -1,52 +1,49 @@ namespace Server.Items { - public class OrcHelm : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 5; + public class OrcHelm : BaseArmor + { + [Constructible] + public OrcHelm() : base(0x1F0B) + { + } - public override int InitMinHits => 30; - public override int InitMaxHits => 50; + public OrcHelm(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 20; + public override int InitMinHits => 30; + public override int InitMaxHits => 50; - public override double DefaultWeight => 5; + public override int AosStrReq => 30; + public override int OldStrReq => 10; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int ArmorBase => 20; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.None; + public override double DefaultWeight => 5; - [Constructible] - public OrcHelm() : base( 0x1F0B ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public OrcHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.None; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( version == 0 && ( Weight == 1 || Weight == 5 ) ) - { - Weight = -1; - } - } - } -} + if (version == 0 && (Weight == 1 || Weight == 5)) Weight = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/PlateHelm.cs b/Scripts/Items/Armor/Helmets/PlateHelm.cs index c131bf41d..2698f40ab 100644 --- a/Scripts/Items/Armor/Helmets/PlateHelm.cs +++ b/Scripts/Items/Armor/Helmets/PlateHelm.cs @@ -1,48 +1,48 @@ namespace Server.Items { - public class PlateHelm : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateHelm : BaseArmor + { + [Constructible] + public PlateHelm() : base(0x1412) + { + Weight = 5.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public PlateHelm(Serial serial) : base(serial) + { + } - public override int AosStrReq => 80; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -1; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 40; + public override int AosStrReq => 80; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int OldDexBonus => -1; - [Constructible] - public PlateHelm() : base( 0x1412 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public PlateHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/RavenHelm.cs b/Scripts/Items/Armor/Helmets/RavenHelm.cs index 1916f5027..699ca6d35 100644 --- a/Scripts/Items/Armor/Helmets/RavenHelm.cs +++ b/Scripts/Items/Armor/Helmets/RavenHelm.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0x2B71, 0x3168 )] - public class RavenHelm : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B71, 0x3168)] + public class RavenHelm : BaseArmor + { + [Constructible] + public RavenHelm() : base(0x2B71) + { + Weight = 5.0; + } - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 5; + public RavenHelm(Serial serial) : base(serial) + { + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - [Constructible] - public RavenHelm() : base( 0x2B71 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public RavenHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/RoyalCirclet.cs b/Scripts/Items/Armor/Helmets/RoyalCirclet.cs index e62a8962d..f7621dae6 100644 --- a/Scripts/Items/Armor/Helmets/RoyalCirclet.cs +++ b/Scripts/Items/Armor/Helmets/RoyalCirclet.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2B6F, 0x3166 )] - public class RoyalCirclet : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B6F, 0x3166)] + public class RoyalCirclet : BaseArmor + { + [Constructible] + public RoyalCirclet() : base(0x2B6F) + { + Weight = 2.0; + } - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 5; + public RoyalCirclet(Serial serial) : base(serial) + { + } - public override int InitMinHits => 20; - public override int InitMaxHits => 35; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 30; + public override int InitMinHits => 20; + public override int InitMaxHits => 35; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 30; - [Constructible] - public RoyalCirclet() : base( 0x2B6F ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public RoyalCirclet( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/VultureHelm.cs b/Scripts/Items/Armor/Helmets/VultureHelm.cs index 02333abfa..ad855a0f1 100644 --- a/Scripts/Items/Armor/Helmets/VultureHelm.cs +++ b/Scripts/Items/Armor/Helmets/VultureHelm.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0x2B72, 0x3169 )] - public class VultureHelm : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B72, 0x3169)] + public class VultureHelm : BaseArmor + { + [Constructible] + public VultureHelm() : base(0x2B72) + { + Weight = 5.0; + } - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 5; + public VultureHelm(Serial serial) : base(serial) + { + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - [Constructible] - public VultureHelm() : base( 0x2B72 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public VultureHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Helmets/WingedHelm.cs b/Scripts/Items/Armor/Helmets/WingedHelm.cs index 01544abb6..bbfd3ed7b 100644 --- a/Scripts/Items/Armor/Helmets/WingedHelm.cs +++ b/Scripts/Items/Armor/Helmets/WingedHelm.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0x2B73, 0x316A )] - public class WingedHelm : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B73, 0x316A)] + public class WingedHelm : BaseArmor + { + [Constructible] + public WingedHelm() : base(0x2B73) + { + Weight = 5.0; + } - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 5; + public WingedHelm(Serial serial) : base(serial) + { + } - public override int InitMinHits => 45; - public override int InitMaxHits => 55; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 5; - public override int ArmorBase => 40; + public override int InitMinHits => 45; + public override int InitMaxHits => 55; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - [Constructible] - public WingedHelm() : base( 0x2B73 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public WingedHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/FemaleLeafChest.cs b/Scripts/Items/Armor/Leather/FemaleLeafChest.cs index bf10f1c12..95aab53e4 100644 --- a/Scripts/Items/Armor/Leather/FemaleLeafChest.cs +++ b/Scripts/Items/Armor/Leather/FemaleLeafChest.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2FCB, 0x3181 )] - public class FemaleLeafChest : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + [Flippable(0x2FCB, 0x3181)] + public class FemaleLeafChest : BaseArmor + { + [Constructible] + public FemaleLeafChest() : base(0x2FCB) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public FemaleLeafChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 20; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public FemaleLeafChest() : base( 0x2FCB ) - { - Weight = 2.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public FemaleLeafChest( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/FemaleLeatherChest.cs b/Scripts/Items/Armor/Leather/FemaleLeatherChest.cs index 1ec48eb2d..127c59701 100644 --- a/Scripts/Items/Armor/Leather/FemaleLeatherChest.cs +++ b/Scripts/Items/Armor/Leather/FemaleLeatherChest.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1c06, 0x1c07 )] - public class FemaleLeatherChest : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x1c06, 0x1c07)] + public class FemaleLeatherChest : BaseArmor + { + [Constructible] + public FemaleLeatherChest() : base(0x1C06) + { + Weight = 1.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public FemaleLeatherChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public FemaleLeatherChest() : base( 0x1C06 ) - { - Weight = 1.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public FemaleLeatherChest( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeafArms.cs b/Scripts/Items/Armor/Leather/LeafArms.cs index 4ced26819..1ce97de34 100644 --- a/Scripts/Items/Armor/Leather/LeafArms.cs +++ b/Scripts/Items/Armor/Leather/LeafArms.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2FC8, 0x317E )] - public class LeafArms : BaseArmor - { - public override Race RequiredRace => Race.Elf; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + [Flippable(0x2FC8, 0x317E)] + public class LeafArms : BaseArmor + { + [Constructible] + public LeafArms() : base(0x2FC8) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeafArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 15; - public override int OldStrReq => 15; + public override Race RequiredRace => Race.Elf; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 15; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeafArms() : base( 0x2FC8 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeafArms( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeafChest.cs b/Scripts/Items/Armor/Leather/LeafChest.cs index eb1b4698d..be19d01ce 100644 --- a/Scripts/Items/Armor/Leather/LeafChest.cs +++ b/Scripts/Items/Armor/Leather/LeafChest.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2FC5, 0x317B )] - public class LeafChest : BaseArmor - { - public override Race RequiredRace => Race.Elf; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + [Flippable(0x2FC5, 0x317B)] + public class LeafChest : BaseArmor + { + [Constructible] + public LeafChest() : base(0x2FC5) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeafChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 20; + public override Race RequiredRace => Race.Elf; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 20; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeafChest() : base( 0x2FC5 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeafChest( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeafGloves.cs b/Scripts/Items/Armor/Leather/LeafGloves.cs index ea130b780..e7754388c 100644 --- a/Scripts/Items/Armor/Leather/LeafGloves.cs +++ b/Scripts/Items/Armor/Leather/LeafGloves.cs @@ -1,136 +1,146 @@ -using System; - namespace Server.Items { - [Flippable] - public class LeafGloves : BaseArmor, IArcaneEquip - { - public override Race RequiredRace => Race.Elf; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + [Flippable] + public class LeafGloves : BaseArmor, IArcaneEquip + { + [Constructible] + public LeafGloves() : base(0x2FC6) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeafGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override Race RequiredRace => Race.Elf; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeafGloves() : base( 0x2FC6 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeafGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - if ( IsArcane ) - { - writer.Write( true ); - writer.Write( (int) m_CurArcaneCharges ); - writer.Write( (int) m_MaxArcaneCharges ); - } - else - { - writer.Write( false ); - } - } + if (IsArcane) + { + writer.Write(true); + writer.Write(m_CurArcaneCharges); + writer.Write(m_MaxArcaneCharges); + } + else + { + writer.Write(false); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - switch ( version ) - { - case 0: - { - if ( reader.ReadBool() ) - { - m_CurArcaneCharges = reader.ReadInt(); - m_MaxArcaneCharges = reader.ReadInt(); + switch (version) + { + case 0: + { + if (reader.ReadBool()) + { + m_CurArcaneCharges = reader.ReadInt(); + m_MaxArcaneCharges = reader.ReadInt(); - if ( Hue == 2118 ) - Hue = ArcaneGem.DefaultArcaneHue; - } + if (Hue == 2118) + Hue = ArcaneGem.DefaultArcaneHue; + } - break; - } - } - } + break; + } + } + } - #region Arcane Impl - private int m_MaxArcaneCharges, m_CurArcaneCharges; + #region Arcane Impl - [CommandProperty( AccessLevel.GameMaster )] - public int MaxArcaneCharges - { - get => m_MaxArcaneCharges; - set{ m_MaxArcaneCharges = value; InvalidateProperties(); Update(); } - } + private int m_MaxArcaneCharges, m_CurArcaneCharges; - [CommandProperty( AccessLevel.GameMaster )] - public int CurArcaneCharges - { - get => m_CurArcaneCharges; - set{ m_CurArcaneCharges = value; InvalidateProperties(); Update(); } - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxArcaneCharges + { + get => m_MaxArcaneCharges; + set + { + m_MaxArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsArcane => ( m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0 ); + [CommandProperty(AccessLevel.GameMaster)] + public int CurArcaneCharges + { + get => m_CurArcaneCharges; + set + { + m_CurArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } - public void Update() - { - if ( IsArcane ) - ItemID = 0x26B0; // TODO: Check - else if ( ItemID == 0x26B0 ) - ItemID = 0x2FC6; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsArcane => m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0; - if ( IsArcane && CurArcaneCharges == 0 ) - Hue = 0; - } + public void Update() + { + if (IsArcane) + ItemID = 0x26B0; // TODO: Check + else if (ItemID == 0x26B0) + ItemID = 0x2FC6; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (IsArcane && CurArcaneCharges == 0) + Hue = 0; + } - if ( IsArcane ) - list.Add( 1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges ); // arcane charges: ~1_val~ / ~2_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + if (IsArcane) + list.Add(1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges); // arcane charges: ~1_val~ / ~2_val~ + } - if ( IsArcane ) - LabelTo( from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - public void Flip() - { - if ( ItemID == 0x2FC6 ) - ItemID = 0x317C; - else if ( ItemID == 0x317C ) - ItemID = 0x2FC6; - } - #endregion - } -} + if (IsArcane) + LabelTo(from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); + } + + public void Flip() + { + if (ItemID == 0x2FC6) + ItemID = 0x317C; + else if (ItemID == 0x317C) + ItemID = 0x2FC6; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeafGorget.cs b/Scripts/Items/Armor/Leather/LeafGorget.cs index 76b248bde..2fba6e1d5 100644 --- a/Scripts/Items/Armor/Leather/LeafGorget.cs +++ b/Scripts/Items/Armor/Leather/LeafGorget.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class LeafGorget : BaseArmor - { - public override Race RequiredRace => Race.Elf; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + public class LeafGorget : BaseArmor + { + [Constructible] + public LeafGorget() : base(0x2FC7) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeafGorget(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override Race RequiredRace => Race.Elf; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeafGorget() : base( 0x2FC7 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeafGorget( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeafLegs.cs b/Scripts/Items/Armor/Leather/LeafLegs.cs index ae2992e35..41bd65a8e 100644 --- a/Scripts/Items/Armor/Leather/LeafLegs.cs +++ b/Scripts/Items/Armor/Leather/LeafLegs.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2FC9, 0x317F )] - public class LeafLegs : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2FC9, 0x317F)] + public class LeafLegs : BaseArmor + { + [Constructible] + public LeafLegs() : base(0x2FC9) + { + Weight = 2.0; + } - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + public LeafLegs(Serial serial) : base(serial) + { + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 20; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 20; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeafLegs() : base( 0x2FC9 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeafLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeafTonlet.cs b/Scripts/Items/Armor/Leather/LeafTonlet.cs index d0a09b16f..e10efd467 100644 --- a/Scripts/Items/Armor/Leather/LeafTonlet.cs +++ b/Scripts/Items/Armor/Leather/LeafTonlet.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2FCA, 0x3180 )] - public class LeafTonlet : BaseArmor - { - public override Race RequiredRace => Race.Elf; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; + [Flippable(0x2FCA, 0x3180)] + public class LeafTonlet : BaseArmor + { + [Constructible] + public LeafTonlet() : base(0x2FCA) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeafTonlet(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override Race RequiredRace => Race.Elf; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeafTonlet() : base( 0x2FCA ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeafTonlet( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherArms.cs b/Scripts/Items/Armor/Leather/LeatherArms.cs index 97b2ba440..a9c4c4ba3 100644 --- a/Scripts/Items/Armor/Leather/LeatherArms.cs +++ b/Scripts/Items/Armor/Leather/LeatherArms.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13cd, 0x13c5 )] - public class LeatherArms : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x13cd, 0x13c5)] + public class LeatherArms : BaseArmor + { + [Constructible] + public LeatherArms() : base(0x13CD) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeatherArms() : base( 0x13CD ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherArms( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherBustierArms.cs b/Scripts/Items/Armor/Leather/LeatherBustierArms.cs index ea8eebe9c..b0e12b36e 100644 --- a/Scripts/Items/Armor/Leather/LeatherBustierArms.cs +++ b/Scripts/Items/Armor/Leather/LeatherBustierArms.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1c0a, 0x1c0b )] - public class LeatherBustierArms : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x1c0a, 0x1c0b)] + public class LeatherBustierArms : BaseArmor + { + [Constructible] + public LeatherBustierArms() : base(0x1C0A) + { + Weight = 1.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherBustierArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public LeatherBustierArms() : base( 0x1C0A ) - { - Weight = 1.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public LeatherBustierArms( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherChest.cs b/Scripts/Items/Armor/Leather/LeatherChest.cs index 19fdce15e..d1902db6b 100644 --- a/Scripts/Items/Armor/Leather/LeatherChest.cs +++ b/Scripts/Items/Armor/Leather/LeatherChest.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13cc, 0x13d3 )] - public class LeatherChest : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x13cc, 0x13d3)] + public class LeatherChest : BaseArmor + { + [Constructible] + public LeatherChest() : base(0x13CC) + { + Weight = 6.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeatherChest() : base( 0x13CC ) - { - Weight = 6.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherChest( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 6.0; - } - } -} + if (Weight == 1.0) + Weight = 6.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherDo.cs b/Scripts/Items/Armor/Leather/LeatherDo.cs index 0a0f8ff7e..f879ae5d0 100644 --- a/Scripts/Items/Armor/Leather/LeatherDo.cs +++ b/Scripts/Items/Armor/Leather/LeatherDo.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherDo : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherDo : BaseArmor + { + [Constructible] + public LeatherDo() : base(0x27C6) + { + Weight = 6.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public LeatherDo(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 40; + public override int OldStrReq => 40; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherDo() : base( 0x27C6 ) - { - Weight = 6.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherDo( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherGloves.cs b/Scripts/Items/Armor/Leather/LeatherGloves.cs index 0566300e3..da6742375 100644 --- a/Scripts/Items/Armor/Leather/LeatherGloves.cs +++ b/Scripts/Items/Armor/Leather/LeatherGloves.cs @@ -1,135 +1,145 @@ -using System; - namespace Server.Items { - [Flippable] - public class LeatherGloves : BaseArmor, IArcaneEquip - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable] + public class LeatherGloves : BaseArmor, IArcaneEquip + { + [Constructible] + public LeatherGloves() : base(0x13C6) + { + Weight = 1.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeatherGloves() : base( 0x13C6 ) - { - Weight = 1.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - if ( IsArcane ) - { - writer.Write( true ); - writer.Write( (int) m_CurArcaneCharges ); - writer.Write( (int) m_MaxArcaneCharges ); - } - else - { - writer.Write( false ); - } - } + if (IsArcane) + { + writer.Write(true); + writer.Write(m_CurArcaneCharges); + writer.Write(m_MaxArcaneCharges); + } + else + { + writer.Write(false); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - if ( reader.ReadBool() ) - { - m_CurArcaneCharges = reader.ReadInt(); - m_MaxArcaneCharges = reader.ReadInt(); + switch (version) + { + case 1: + { + if (reader.ReadBool()) + { + m_CurArcaneCharges = reader.ReadInt(); + m_MaxArcaneCharges = reader.ReadInt(); - if ( Hue == 2118 ) - Hue = ArcaneGem.DefaultArcaneHue; - } + if (Hue == 2118) + Hue = ArcaneGem.DefaultArcaneHue; + } - break; - } - } - } + break; + } + } + } - #region Arcane Impl - private int m_MaxArcaneCharges, m_CurArcaneCharges; + #region Arcane Impl - [CommandProperty( AccessLevel.GameMaster )] - public int MaxArcaneCharges - { - get => m_MaxArcaneCharges; - set{ m_MaxArcaneCharges = value; InvalidateProperties(); Update(); } - } + private int m_MaxArcaneCharges, m_CurArcaneCharges; - [CommandProperty( AccessLevel.GameMaster )] - public int CurArcaneCharges - { - get => m_CurArcaneCharges; - set{ m_CurArcaneCharges = value; InvalidateProperties(); Update(); } - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxArcaneCharges + { + get => m_MaxArcaneCharges; + set + { + m_MaxArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsArcane => ( m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0 ); + [CommandProperty(AccessLevel.GameMaster)] + public int CurArcaneCharges + { + get => m_CurArcaneCharges; + set + { + m_CurArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } - public void Update() - { - if ( IsArcane ) - ItemID = 0x26B0; - else if ( ItemID == 0x26B0 ) - ItemID = 0x13C6; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsArcane => m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0; - if ( IsArcane && CurArcaneCharges == 0 ) - Hue = 0; - } + public void Update() + { + if (IsArcane) + ItemID = 0x26B0; + else if (ItemID == 0x26B0) + ItemID = 0x13C6; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (IsArcane && CurArcaneCharges == 0) + Hue = 0; + } - if ( IsArcane ) - list.Add( 1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges ); // arcane charges: ~1_val~ / ~2_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + if (IsArcane) + list.Add(1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges); // arcane charges: ~1_val~ / ~2_val~ + } - if ( IsArcane ) - LabelTo( from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - public void Flip() - { - if ( ItemID == 0x13C6 ) - ItemID = 0x13CE; - else if ( ItemID == 0x13CE ) - ItemID = 0x13C6; - } - #endregion - } -} + if (IsArcane) + LabelTo(from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); + } + + public void Flip() + { + if (ItemID == 0x13C6) + ItemID = 0x13CE; + else if (ItemID == 0x13CE) + ItemID = 0x13C6; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherGorget.cs b/Scripts/Items/Armor/Leather/LeatherGorget.cs index c41158503..c0e83717c 100644 --- a/Scripts/Items/Armor/Leather/LeatherGorget.cs +++ b/Scripts/Items/Armor/Leather/LeatherGorget.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherGorget : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherGorget : BaseArmor + { + [Constructible] + public LeatherGorget() : base(0x13C7) + { + Weight = 1.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherGorget(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeatherGorget() : base( 0x13C7 ) - { - Weight = 1.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherGorget( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherHaidate.cs b/Scripts/Items/Armor/Leather/LeatherHaidate.cs index ab5e1178e..81e3df748 100644 --- a/Scripts/Items/Armor/Leather/LeatherHaidate.cs +++ b/Scripts/Items/Armor/Leather/LeatherHaidate.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class LeatherHaidate : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherHaidate : BaseArmor + { + [Constructible] + public LeatherHaidate() : base(0x278A) + { + Weight = 4.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherHaidate(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 20; + + public override int ArmorBase => 3; + + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - [Constructible] - public LeatherHaidate() : base( 0x278A ) - { - Weight = 4.0; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public LeatherHaidate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherHiroSode.cs b/Scripts/Items/Armor/Leather/LeatherHiroSode.cs index 537fe2342..848c563b7 100644 --- a/Scripts/Items/Armor/Leather/LeatherHiroSode.cs +++ b/Scripts/Items/Armor/Leather/LeatherHiroSode.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherHiroSode : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherHiroSode : BaseArmor + { + [Constructible] + public LeatherHiroSode() : base(0x277E) + { + Weight = 1.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public LeatherHiroSode(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherHiroSode() : base( 0x277E ) - { - Weight = 1.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherHiroSode( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherJingasa.cs b/Scripts/Items/Armor/Leather/LeatherJingasa.cs index 2923d724d..a1e677dda 100644 --- a/Scripts/Items/Armor/Leather/LeatherJingasa.cs +++ b/Scripts/Items/Armor/Leather/LeatherJingasa.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherJingasa : BaseArmor - { - public override int BasePhysicalResistance => 4; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 3; + public class LeatherJingasa : BaseArmor + { + [Constructible] + public LeatherJingasa() : base(0x2776) + { + Weight = 3.0; + } - public override int InitMinHits => 20; - public override int InitMaxHits => 30; + public LeatherJingasa(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 4; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 20; + public override int InitMaxHits => 30; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherJingasa() : base( 0x2776 ) - { - Weight = 3.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherJingasa( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherLegs.cs b/Scripts/Items/Armor/Leather/LeatherLegs.cs index 9f8515712..a8a067426 100644 --- a/Scripts/Items/Armor/Leather/LeatherLegs.cs +++ b/Scripts/Items/Armor/Leather/LeatherLegs.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x13cb, 0x13d2 )] - public class LeatherLegs : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x13cb, 0x13d2)] + public class LeatherLegs : BaseArmor + { + [Constructible] + public LeatherLegs() : base(0x13CB) + { + Weight = 4.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - [Constructible] - public LeatherLegs() : base( 0x13CB ) - { - Weight = 4.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherMempo.cs b/Scripts/Items/Armor/Leather/LeatherMempo.cs index a389cbe16..af1a29984 100644 --- a/Scripts/Items/Armor/Leather/LeatherMempo.cs +++ b/Scripts/Items/Armor/Leather/LeatherMempo.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherMempo : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherMempo : BaseArmor + { + [Constructible] + public LeatherMempo() : base(0x277A) + { + Weight = 2.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 40; + public LeatherMempo(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 35; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 30; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherMempo() : base( 0x277A ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherMempo( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherNinjaHood.cs b/Scripts/Items/Armor/Leather/LeatherNinjaHood.cs index 4681e11d6..d5eb533a8 100644 --- a/Scripts/Items/Armor/Leather/LeatherNinjaHood.cs +++ b/Scripts/Items/Armor/Leather/LeatherNinjaHood.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherNinjaHood : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class LeatherNinjaHood : BaseArmor + { + [Constructible] + public LeatherNinjaHood() : base(0x278E) + { + Weight = 2.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 45; + public LeatherNinjaHood(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 3; + public override int InitMinHits => 25; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherNinjaHood() : base( 0x278E ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherNinjaHood( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherNinjaJacket.cs b/Scripts/Items/Armor/Leather/LeatherNinjaJacket.cs index a8020c311..8651a48df 100644 --- a/Scripts/Items/Armor/Leather/LeatherNinjaJacket.cs +++ b/Scripts/Items/Armor/Leather/LeatherNinjaJacket.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherNinjaJacket : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherNinjaJacket : BaseArmor + { + [Constructible] + public LeatherNinjaJacket() : base(0x2793) + { + Weight = 5.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 65; + public LeatherNinjaJacket(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 55; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherNinjaJacket() : base( 0x2793 ) - { - Weight = 5.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherNinjaJacket( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherNinjaMitts.cs b/Scripts/Items/Armor/Leather/LeatherNinjaMitts.cs index 1e7416a50..cf34bca41 100644 --- a/Scripts/Items/Armor/Leather/LeatherNinjaMitts.cs +++ b/Scripts/Items/Armor/Leather/LeatherNinjaMitts.cs @@ -1,63 +1,63 @@ namespace Server.Items { - public class LeatherNinjaMitts : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherNinjaMitts : BaseArmor + { + [Constructible] + public LeatherNinjaMitts() : base(0x2792) + { + Weight = 2.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 25; + public LeatherNinjaMitts(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 25; + public override int InitMaxHits => 25; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherNinjaMitts() : base( 0x2792 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherNinjaMitts( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 2 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - if ( reader.ReadBool() ) - { - reader.ReadInt(); - reader.ReadInt(); - } + switch (version) + { + case 1: + { + if (reader.ReadBool()) + { + reader.ReadInt(); + reader.ReadInt(); + } - Weight = 2.0; - ItemID = 0x2792; + Weight = 2.0; + ItemID = 0x2792; - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherNinjaPants.cs b/Scripts/Items/Armor/Leather/LeatherNinjaPants.cs index 58b3c6acc..41dc965bb 100644 --- a/Scripts/Items/Armor/Leather/LeatherNinjaPants.cs +++ b/Scripts/Items/Armor/Leather/LeatherNinjaPants.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherNinjaPants : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherNinjaPants : BaseArmor + { + [Constructible] + public LeatherNinjaPants() : base(0x2791) + { + Weight = 3.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public LeatherNinjaPants(Serial serial) : base(serial) + { + } - public override int AosStrReq => 10; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 10; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherNinjaPants() : base( 0x2791 ) - { - Weight = 3.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherNinjaPants( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherShorts.cs b/Scripts/Items/Armor/Leather/LeatherShorts.cs index 606373c4e..8ab4d66f5 100644 --- a/Scripts/Items/Armor/Leather/LeatherShorts.cs +++ b/Scripts/Items/Armor/Leather/LeatherShorts.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1c00, 0x1c01 )] - public class LeatherShorts : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x1c00, 0x1c01)] + public class LeatherShorts : BaseArmor + { + [Constructible] + public LeatherShorts() : base(0x1C00) + { + Weight = 3.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherShorts(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public LeatherShorts() : base( 0x1C00 ) - { - Weight = 3.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public LeatherShorts( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherSkirt.cs b/Scripts/Items/Armor/Leather/LeatherSkirt.cs index 741028fc9..4572cf7e1 100644 --- a/Scripts/Items/Armor/Leather/LeatherSkirt.cs +++ b/Scripts/Items/Armor/Leather/LeatherSkirt.cs @@ -1,52 +1,52 @@ namespace Server.Items { - [FlippableAttribute( 0x1c08, 0x1c09 )] - public class LeatherSkirt : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x1c08, 0x1c09)] + public class LeatherSkirt : BaseArmor + { + [Constructible] + public LeatherSkirt() : base(0x1C08) + { + Weight = 1.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherSkirt(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public LeatherSkirt() : base( 0x1C08 ) - { - Weight = 1.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public LeatherSkirt( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - if ( Weight == 3.0 ) - Weight = 1.0; - } + if (Weight == 3.0) + Weight = 1.0; + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Leather/LeatherSuneate.cs b/Scripts/Items/Armor/Leather/LeatherSuneate.cs index 31ff324b5..c531f1abe 100644 --- a/Scripts/Items/Armor/Leather/LeatherSuneate.cs +++ b/Scripts/Items/Armor/Leather/LeatherSuneate.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class LeatherSuneate : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class LeatherSuneate : BaseArmor + { + [Constructible] + public LeatherSuneate() : base(0x2786) + { + Weight = 4.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 40; + public LeatherSuneate(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 25; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 20; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 3; - [Constructible] - public LeatherSuneate() : base( 0x2786 ) - { - Weight = 4.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public LeatherSuneate( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/DecorativePlateKabuto.cs b/Scripts/Items/Armor/Plate/DecorativePlateKabuto.cs index 3f0a053bd..c70f92c5d 100644 --- a/Scripts/Items/Armor/Plate/DecorativePlateKabuto.cs +++ b/Scripts/Items/Armor/Plate/DecorativePlateKabuto.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class DecorativePlateKabuto : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 3; + public class DecorativePlateKabuto : BaseArmor + { + [Constructible] + public DecorativePlateKabuto() : base(0x2778) + { + Weight = 6.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public DecorativePlateKabuto(Serial serial) : base(serial) + { + } - public override int AosStrReq => 70; - public override int OldStrReq => 70; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 70; + public override int OldStrReq => 70; - [Constructible] - public DecorativePlateKabuto() : base( 0x2778 ) - { - Weight = 6.0; - } + public override int ArmorBase => 3; - public DecorativePlateKabuto( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/FemalePlateChest.cs b/Scripts/Items/Armor/Plate/FemalePlateChest.cs index 7cbcdcd6f..7329eb9ef 100644 --- a/Scripts/Items/Armor/Plate/FemalePlateChest.cs +++ b/Scripts/Items/Armor/Plate/FemalePlateChest.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x1c04, 0x1c05 )] - public class FemalePlateChest : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x1c04, 0x1c05)] + public class FemalePlateChest : BaseArmor + { + [Constructible] + public FemalePlateChest() : base(0x1C04) + { + Weight = 4.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public FemalePlateChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 95; - public override int OldStrReq => 45; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -5; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override bool AllowMaleWearer => false; + public override int AosStrReq => 95; + public override int OldStrReq => 45; - public override int ArmorBase => 30; + public override int OldDexBonus => -5; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override bool AllowMaleWearer => false; - [Constructible] - public FemalePlateChest() : base( 0x1C04 ) - { - Weight = 4.0; - } + public override int ArmorBase => 30; - public FemalePlateChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 4.0; - } - } -} + if (Weight == 1.0) + Weight = 4.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/FemaleWoodlandChest.cs b/Scripts/Items/Armor/Plate/FemaleWoodlandChest.cs index f53a82c1a..3a11d1543 100644 --- a/Scripts/Items/Armor/Plate/FemaleWoodlandChest.cs +++ b/Scripts/Items/Armor/Plate/FemaleWoodlandChest.cs @@ -1,49 +1,49 @@ namespace Server.Items { - //Is this a filler-type item? the clilocs don't match up and at a glacnce I can't find direct reference of it - [FlippableAttribute( 0x2B6D, 0x3164 )] - public class FemaleElvenPlateChest : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + //Is this a filler-type item? the clilocs don't match up and at a glacnce I can't find direct reference of it + [Flippable(0x2B6D, 0x3164)] + public class FemaleElvenPlateChest : BaseArmor + { + [Constructible] + public FemaleElvenPlateChest() : base(0x2B6D) + { + Weight = 8.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public FemaleElvenPlateChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 95; - public override int OldStrReq => 95; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override bool AllowMaleWearer => false; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 30; + public override int AosStrReq => 95; + public override int OldStrReq => 95; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override bool AllowMaleWearer => false; - [Constructible] - public FemaleElvenPlateChest() : base( 0x2B6D ) - { - Weight = 8.0; - } + public override int ArmorBase => 30; - public FemaleElvenPlateChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/HeavyPlateJingasa.cs b/Scripts/Items/Armor/Plate/HeavyPlateJingasa.cs index b9e2436b6..8b6f09282 100644 --- a/Scripts/Items/Armor/Plate/HeavyPlateJingasa.cs +++ b/Scripts/Items/Armor/Plate/HeavyPlateJingasa.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class HeavyPlateJingasa : BaseArmor - { - public override int BasePhysicalResistance => 7; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 2; + public class HeavyPlateJingasa : BaseArmor + { + [Constructible] + public HeavyPlateJingasa() : base(0x2777) + { + Weight = 5.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 70; + public HeavyPlateJingasa(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 55; + public override int BasePhysicalResistance => 7; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 4; + public override int InitMinHits => 50; + public override int InitMaxHits => 70; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 55; + public override int OldStrReq => 55; - [Constructible] - public HeavyPlateJingasa() : base( 0x2777 ) - { - Weight = 5.0; - } + public override int ArmorBase => 4; - public HeavyPlateJingasa( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/LightPlateJingasa.cs b/Scripts/Items/Armor/Plate/LightPlateJingasa.cs index e36b47f9e..343b9cc3e 100644 --- a/Scripts/Items/Armor/Plate/LightPlateJingasa.cs +++ b/Scripts/Items/Armor/Plate/LightPlateJingasa.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class LightPlateJingasa : BaseArmor - { - public override int BasePhysicalResistance => 7; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 2; + public class LightPlateJingasa : BaseArmor + { + [Constructible] + public LightPlateJingasa() : base(0x2781) + { + Weight = 5.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 60; + public LightPlateJingasa(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 55; + public override int BasePhysicalResistance => 7; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 4; + public override int InitMinHits => 55; + public override int InitMaxHits => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 55; + public override int OldStrReq => 55; - [Constructible] - public LightPlateJingasa() : base( 0x2781 ) - { - Weight = 5.0; - } + public override int ArmorBase => 4; - public LightPlateJingasa( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateArms.cs b/Scripts/Items/Armor/Plate/PlateArms.cs index 036dc6bc9..f97581ef1 100644 --- a/Scripts/Items/Armor/Plate/PlateArms.cs +++ b/Scripts/Items/Armor/Plate/PlateArms.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1410, 0x1417 )] - public class PlateArms : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x1410, 0x1417)] + public class PlateArms : BaseArmor + { + [Constructible] + public PlateArms() : base(0x1410) + { + Weight = 5.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public PlateArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 80; - public override int OldStrReq => 40; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -2; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 40; + public override int AosStrReq => 80; + public override int OldStrReq => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int OldDexBonus => -2; - [Constructible] - public PlateArms() : base( 0x1410 ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public PlateArms( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } - } -} + if (Weight == 1.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateBattleKabuto.cs b/Scripts/Items/Armor/Plate/PlateBattleKabuto.cs index ff8f95c89..e70e79fa8 100644 --- a/Scripts/Items/Armor/Plate/PlateBattleKabuto.cs +++ b/Scripts/Items/Armor/Plate/PlateBattleKabuto.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateBattleKabuto : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 3; + public class PlateBattleKabuto : BaseArmor + { + [Constructible] + public PlateBattleKabuto() : base(0x2785) + { + Weight = 6.0; + } - public override int InitMinHits => 60; - public override int InitMaxHits => 65; + public PlateBattleKabuto(Serial serial) : base(serial) + { + } - public override int AosStrReq => 70; - public override int OldStrReq => 70; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 60; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 70; + public override int OldStrReq => 70; - [Constructible] - public PlateBattleKabuto() : base( 0x2785 ) - { - Weight = 6.0; - } + public override int ArmorBase => 3; - public PlateBattleKabuto( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateChest.cs b/Scripts/Items/Armor/Plate/PlateChest.cs index d1a8b20e4..956d1925d 100644 --- a/Scripts/Items/Armor/Plate/PlateChest.cs +++ b/Scripts/Items/Armor/Plate/PlateChest.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1415, 0x1416 )] - public class PlateChest : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x1415, 0x1416)] + public class PlateChest : BaseArmor + { + [Constructible] + public PlateChest() : base(0x1415) + { + Weight = 10.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public PlateChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 95; - public override int OldStrReq => 60; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -8; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 40; + public override int AosStrReq => 95; + public override int OldStrReq => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int OldDexBonus => -8; - [Constructible] - public PlateChest() : base( 0x1415 ) - { - Weight = 10.0; - } + public override int ArmorBase => 40; - public PlateChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 10.0; - } - } -} + if (Weight == 1.0) + Weight = 10.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateDo.cs b/Scripts/Items/Armor/Plate/PlateDo.cs index 13cac17b9..cf6030751 100644 --- a/Scripts/Items/Armor/Plate/PlateDo.cs +++ b/Scripts/Items/Armor/Plate/PlateDo.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateDo : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateDo : BaseArmor + { + [Constructible] + public PlateDo() : base(0x277D) + { + Weight = 10.0; + } - public override int InitMinHits => 60; - public override int InitMaxHits => 70; + public PlateDo(Serial serial) : base(serial) + { + } - public override int AosStrReq => 85; - public override int OldStrReq => 85; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 3; + public override int InitMinHits => 60; + public override int InitMaxHits => 70; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 85; + public override int OldStrReq => 85; - [Constructible] - public PlateDo() : base( 0x277D ) - { - Weight = 10.0; - } + public override int ArmorBase => 3; - public PlateDo( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateGloves.cs b/Scripts/Items/Armor/Plate/PlateGloves.cs index 246184404..a362ca46c 100644 --- a/Scripts/Items/Armor/Plate/PlateGloves.cs +++ b/Scripts/Items/Armor/Plate/PlateGloves.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1414, 0x1418 )] - public class PlateGloves : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x1414, 0x1418)] + public class PlateGloves : BaseArmor + { + [Constructible] + public PlateGloves() : base(0x1414) + { + Weight = 2.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public PlateGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 70; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -2; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 40; + public override int AosStrReq => 70; + public override int OldStrReq => 30; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int OldDexBonus => -2; - [Constructible] - public PlateGloves() : base( 0x1414 ) - { - Weight = 2.0; - } + public override int ArmorBase => 40; - public PlateGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateGorget.cs b/Scripts/Items/Armor/Plate/PlateGorget.cs index 55879aaec..810848e02 100644 --- a/Scripts/Items/Armor/Plate/PlateGorget.cs +++ b/Scripts/Items/Armor/Plate/PlateGorget.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class PlateGorget : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateGorget : BaseArmor + { + [Constructible] + public PlateGorget() : base(0x1413) + { + Weight = 2.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public PlateGorget(Serial serial) : base(serial) + { + } - public override int AosStrReq => 45; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldDexBonus => -1; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 40; + public override int AosStrReq => 45; + public override int OldStrReq => 30; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int OldDexBonus => -1; - [Constructible] - public PlateGorget() : base( 0x1413 ) - { - Weight = 2.0; - } + public override int ArmorBase => 40; - public PlateGorget( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateHaidate.cs b/Scripts/Items/Armor/Plate/PlateHaidate.cs index bef6418ee..c3af21a8b 100644 --- a/Scripts/Items/Armor/Plate/PlateHaidate.cs +++ b/Scripts/Items/Armor/Plate/PlateHaidate.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateHaidate : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateHaidate : BaseArmor + { + [Constructible] + public PlateHaidate() : base(0x278D) + { + Weight = 7.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 65; + public PlateHaidate(Serial serial) : base(serial) + { + } - public override int AosStrReq => 80; - public override int OldStrReq => 80; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 3; + public override int InitMinHits => 55; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 80; + public override int OldStrReq => 80; - [Constructible] - public PlateHaidate() : base( 0x278D ) - { - Weight = 7.0; - } + public override int ArmorBase => 3; - public PlateHaidate( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateHatsuburi.cs b/Scripts/Items/Armor/Plate/PlateHatsuburi.cs index f3ec91cef..d3294a082 100644 --- a/Scripts/Items/Armor/Plate/PlateHatsuburi.cs +++ b/Scripts/Items/Armor/Plate/PlateHatsuburi.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateHatsuburi : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 3; + public class PlateHatsuburi : BaseArmor + { + [Constructible] + public PlateHatsuburi() : base(0x2775) + { + Weight = 5.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public PlateHatsuburi(Serial serial) : base(serial) + { + } - public override int AosStrReq => 65; - public override int OldStrReq => 65; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 4; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 65; + public override int OldStrReq => 65; - [Constructible] - public PlateHatsuburi() : base( 0x2775 ) - { - Weight = 5.0; - } + public override int ArmorBase => 4; - public PlateHatsuburi( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateHiroSode.cs b/Scripts/Items/Armor/Plate/PlateHiroSode.cs index 99417503a..4c63030d0 100644 --- a/Scripts/Items/Armor/Plate/PlateHiroSode.cs +++ b/Scripts/Items/Armor/Plate/PlateHiroSode.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateHiroSode : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateHiroSode : BaseArmor + { + [Constructible] + public PlateHiroSode() : base(0x2780) + { + Weight = 3.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 75; + public PlateHiroSode(Serial serial) : base(serial) + { + } - public override int AosStrReq => 75; - public override int OldStrReq => 75; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 3; + public override int InitMinHits => 55; + public override int InitMaxHits => 75; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 75; + public override int OldStrReq => 75; - [Constructible] - public PlateHiroSode() : base( 0x2780 ) - { - Weight = 3.0; - } + public override int ArmorBase => 3; - public PlateHiroSode( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateLegs.cs b/Scripts/Items/Armor/Plate/PlateLegs.cs index 71a31f5cf..9a32f3748 100644 --- a/Scripts/Items/Armor/Plate/PlateLegs.cs +++ b/Scripts/Items/Armor/Plate/PlateLegs.cs @@ -1,46 +1,46 @@ namespace Server.Items { - [FlippableAttribute( 0x1411, 0x141a )] - public class PlateLegs : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x1411, 0x141a)] + public class PlateLegs : BaseArmor + { + [Constructible] + public PlateLegs() : base(0x1411) + { + Weight = 7.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public PlateLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 90; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int OldStrReq => 60; - public override int OldDexBonus => -6; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override int ArmorBase => 40; + public override int AosStrReq => 90; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int OldStrReq => 60; + public override int OldDexBonus => -6; - [Constructible] - public PlateLegs() : base( 0x1411 ) - { - Weight = 7.0; - } + public override int ArmorBase => 40; - public PlateLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateMempo.cs b/Scripts/Items/Armor/Plate/PlateMempo.cs index e3c0ac184..597106af3 100644 --- a/Scripts/Items/Armor/Plate/PlateMempo.cs +++ b/Scripts/Items/Armor/Plate/PlateMempo.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateMempo : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateMempo : BaseArmor + { + [Constructible] + public PlateMempo() : base(0x2779) + { + Weight = 3.0; + } - public override int InitMinHits => 60; - public override int InitMaxHits => 70; + public PlateMempo(Serial serial) : base(serial) + { + } - public override int AosStrReq => 50; - public override int OldStrReq => 50; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 4; + public override int InitMinHits => 60; + public override int InitMaxHits => 70; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 50; + public override int OldStrReq => 50; - [Constructible] - public PlateMempo() : base( 0x2779 ) - { - Weight = 3.0; - } + public override int ArmorBase => 4; - public PlateMempo( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/PlateSuneate.cs b/Scripts/Items/Armor/Plate/PlateSuneate.cs index d6db250d6..d882fd254 100644 --- a/Scripts/Items/Armor/Plate/PlateSuneate.cs +++ b/Scripts/Items/Armor/Plate/PlateSuneate.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class PlateSuneate : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public class PlateSuneate : BaseArmor + { + [Constructible] + public PlateSuneate() : base(0x2788) + { + Weight = 7.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 65; + public PlateSuneate(Serial serial) : base(serial) + { + } - public override int AosStrReq => 80; - public override int OldStrReq => 80; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 3; + public override int InitMinHits => 55; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 80; + public override int OldStrReq => 80; - [Constructible] - public PlateSuneate() : base( 0x2788 ) - { - Weight = 7.0; - } + public override int ArmorBase => 3; - public PlateSuneate( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/SmallPlateJingasa.cs b/Scripts/Items/Armor/Plate/SmallPlateJingasa.cs index 9cef94b00..e813e9f6c 100644 --- a/Scripts/Items/Armor/Plate/SmallPlateJingasa.cs +++ b/Scripts/Items/Armor/Plate/SmallPlateJingasa.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class SmallPlateJingasa : BaseArmor - { - public override int BasePhysicalResistance => 7; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 2; + public class SmallPlateJingasa : BaseArmor + { + [Constructible] + public SmallPlateJingasa() : base(0x2784) + { + Weight = 5.0; + } - public override int InitMinHits => 55; - public override int InitMaxHits => 60; + public SmallPlateJingasa(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 55; + public override int BasePhysicalResistance => 7; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 4; + public override int InitMinHits => 55; + public override int InitMaxHits => 60; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 55; + public override int OldStrReq => 55; - [Constructible] - public SmallPlateJingasa() : base( 0x2784 ) - { - Weight = 5.0; - } + public override int ArmorBase => 4; - public SmallPlateJingasa( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/StandardPlateKabuto.cs b/Scripts/Items/Armor/Plate/StandardPlateKabuto.cs index 6828fed91..270082b38 100644 --- a/Scripts/Items/Armor/Plate/StandardPlateKabuto.cs +++ b/Scripts/Items/Armor/Plate/StandardPlateKabuto.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class StandardPlateKabuto : BaseArmor - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 2; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 2; - public override int BaseEnergyResistance => 3; + public class StandardPlateKabuto : BaseArmor + { + [Constructible] + public StandardPlateKabuto() : base(0x2789) + { + Weight = 6.0; + } - public override int InitMinHits => 60; - public override int InitMaxHits => 65; + public StandardPlateKabuto(Serial serial) : base(serial) + { + } - public override int AosStrReq => 70; - public override int OldStrReq => 70; + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 2; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 2; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 60; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int AosStrReq => 70; + public override int OldStrReq => 70; - [Constructible] - public StandardPlateKabuto() : base( 0x2789 ) - { - Weight = 6.0; - } + public override int ArmorBase => 3; - public StandardPlateKabuto( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/WoodlandArms.cs b/Scripts/Items/Armor/Plate/WoodlandArms.cs index 97f3930bb..da6dbdf4c 100644 --- a/Scripts/Items/Armor/Plate/WoodlandArms.cs +++ b/Scripts/Items/Armor/Plate/WoodlandArms.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2B6C, 0x3163 )] - public class WoodlandArms : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x2B6C, 0x3163)] + public class WoodlandArms : BaseArmor + { + [Constructible] + public WoodlandArms() : base(0x2B6C) + { + Weight = 5.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public WoodlandArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 80; - public override int OldStrReq => 80; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override Race RequiredRace => Race.Elf; + public override int AosStrReq => 80; + public override int OldStrReq => 80; - [Constructible] - public WoodlandArms() : base( 0x2B6C ) - { - Weight = 5.0; - } + public override int ArmorBase => 40; - public WoodlandArms( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/WoodlandChest.cs b/Scripts/Items/Armor/Plate/WoodlandChest.cs index 04a8d1546..7cda187e9 100644 --- a/Scripts/Items/Armor/Plate/WoodlandChest.cs +++ b/Scripts/Items/Armor/Plate/WoodlandChest.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2B67, 0x315E )] - public class WoodlandChest : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x2B67, 0x315E)] + public class WoodlandChest : BaseArmor + { + [Constructible] + public WoodlandChest() : base(0x2B67) + { + Weight = 8.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public WoodlandChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 95; - public override int OldStrReq => 95; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override Race RequiredRace => Race.Elf; + public override int AosStrReq => 95; + public override int OldStrReq => 95; - [Constructible] - public WoodlandChest() : base( 0x2B67 ) - { - Weight = 8.0; - } + public override int ArmorBase => 40; - public WoodlandChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/WoodlandGloves.cs b/Scripts/Items/Armor/Plate/WoodlandGloves.cs index 26216de11..87d538a84 100644 --- a/Scripts/Items/Armor/Plate/WoodlandGloves.cs +++ b/Scripts/Items/Armor/Plate/WoodlandGloves.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2B6A, 0x3161 )] - public class WoodlandGloves : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x2B6A, 0x3161)] + public class WoodlandGloves : BaseArmor + { + [Constructible] + public WoodlandGloves() : base(0x2B6A) + { + Weight = 2.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public WoodlandGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 70; - public override int OldStrReq => 70; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override Race RequiredRace => Race.Elf; + public override int AosStrReq => 70; + public override int OldStrReq => 70; - [Constructible] - public WoodlandGloves() : base( 0x2B6A ) - { - Weight = 2.0; - } + public override int ArmorBase => 40; - public WoodlandGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/WoodlandGorget.cs b/Scripts/Items/Armor/Plate/WoodlandGorget.cs index 2999b59d1..fd19eaf50 100644 --- a/Scripts/Items/Armor/Plate/WoodlandGorget.cs +++ b/Scripts/Items/Armor/Plate/WoodlandGorget.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x2B69, 0x3160 )] - public class WoodlandGorget : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x2B69, 0x3160)] + public class WoodlandGorget : BaseArmor + { + [Constructible] + public WoodlandGorget() : base(0x2B69) + { + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public WoodlandGorget(Serial serial) : base(serial) + { + } - public override int AosStrReq => 45; - public override int OldStrReq => 45; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override Race RequiredRace => Race.Elf; + public override int AosStrReq => 45; + public override int OldStrReq => 45; - [Constructible] - public WoodlandGorget() : base( 0x2B69 ) - { - } + public override int ArmorBase => 40; - public WoodlandGorget( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version - } + writer.WriteEncodedInt(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if ( version == 0 ) - Weight = -1; - } - } -} + if (version == 0) + Weight = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Plate/WoodlandLegs.cs b/Scripts/Items/Armor/Plate/WoodlandLegs.cs index eff3de723..716dff990 100644 --- a/Scripts/Items/Armor/Plate/WoodlandLegs.cs +++ b/Scripts/Items/Armor/Plate/WoodlandLegs.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2B6B, 0x3162 )] - public class WoodlandLegs : BaseArmor - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 2; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + [Flippable(0x2B6B, 0x3162)] + public class WoodlandLegs : BaseArmor + { + [Constructible] + public WoodlandLegs() : base(0x2B6B) + { + Weight = 8.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public WoodlandLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 90; - public override int OldStrReq => 90; + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 2; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 40; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override Race RequiredRace => Race.Elf; + public override int AosStrReq => 90; + public override int OldStrReq => 90; - [Constructible] - public WoodlandLegs() : base( 0x2B6B ) - { - Weight = 8.0; - } + public override int ArmorBase => 40; - public WoodlandLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ranger/RangerArms.cs b/Scripts/Items/Armor/Ranger/RangerArms.cs index 1c4acd97d..e86048a0e 100644 --- a/Scripts/Items/Armor/Ranger/RangerArms.cs +++ b/Scripts/Items/Armor/Ranger/RangerArms.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x13dc, 0x13d4 )] - public class RangerArms : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13dc, 0x13d4)] + public class RangerArms : BaseArmor + { + [Constructible] + public RangerArms() : base(0x13DC) + { + Weight = 4.0; + Hue = 0x59C; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public RangerArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override int LabelNumber => 1041493; // studded sleeves, ranger armor + public override int ArmorBase => 16; - [Constructible] - public RangerArms() : base( 0x13DC ) - { - Weight = 4.0; - Hue = 0x59C; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public RangerArms( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041493; // studded sleeves, ranger armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 4.0; - } - } -} + if (Weight == 1.0) + Weight = 4.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ranger/RangerChest.cs b/Scripts/Items/Armor/Ranger/RangerChest.cs index 9bdec33a8..6b524fbc0 100644 --- a/Scripts/Items/Armor/Ranger/RangerChest.cs +++ b/Scripts/Items/Armor/Ranger/RangerChest.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x13db, 0x13e2 )] - public class RangerChest : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13db, 0x13e2)] + public class RangerChest : BaseArmor + { + [Constructible] + public RangerChest() : base(0x13DB) + { + Weight = 8.0; + Hue = 0x59C; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public RangerChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 35; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 35; + public override int OldStrReq => 35; - public override int LabelNumber => 1041497; // studded tunic, ranger armor + public override int ArmorBase => 16; - [Constructible] - public RangerChest() : base( 0x13DB ) - { - Weight = 8.0; - Hue = 0x59C; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public RangerChest( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041497; // studded tunic, ranger armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 8.0; - } - } -} + if (Weight == 1.0) + Weight = 8.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ranger/RangerGloves.cs b/Scripts/Items/Armor/Ranger/RangerGloves.cs index 968b08eec..abf349dac 100644 --- a/Scripts/Items/Armor/Ranger/RangerGloves.cs +++ b/Scripts/Items/Armor/Ranger/RangerGloves.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0x13d5, 0x13dd )] - public class RangerGloves : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13d5, 0x13dd)] + public class RangerGloves : BaseArmor + { + [Constructible] + public RangerGloves() : base(0x13D5) + { + Weight = 1.0; + Hue = 0x59C; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public RangerGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override int LabelNumber => 1041494; // studded gloves, ranger armor + public override int ArmorBase => 16; - [Constructible] - public RangerGloves() : base( 0x13D5 ) - { - Weight = 1.0; - Hue = 0x59C; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public RangerGloves( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041494; // studded gloves, ranger armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ranger/RangerGorget.cs b/Scripts/Items/Armor/Ranger/RangerGorget.cs index 61df06829..9bb1e3c87 100644 --- a/Scripts/Items/Armor/Ranger/RangerGorget.cs +++ b/Scripts/Items/Armor/Ranger/RangerGorget.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class RangerGorget : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class RangerGorget : BaseArmor + { + [Constructible] + public RangerGorget() : base(0x13D6) + { + Weight = 1.0; + Hue = 0x59C; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public RangerGorget(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override int LabelNumber => 1041495; // studded gorget, ranger armor + public override int ArmorBase => 16; - [Constructible] - public RangerGorget() : base( 0x13D6 ) - { - Weight = 1.0; - Hue = 0x59C; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public RangerGorget( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041495; // studded gorget, ranger armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ranger/RangerLegs.cs b/Scripts/Items/Armor/Ranger/RangerLegs.cs index 19c37c8fd..5f9b03d90 100644 --- a/Scripts/Items/Armor/Ranger/RangerLegs.cs +++ b/Scripts/Items/Armor/Ranger/RangerLegs.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x13da, 0x13e1 )] - public class RangerLegs : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13da, 0x13e1)] + public class RangerLegs : BaseArmor + { + [Constructible] + public RangerLegs() : base(0x13DA) + { + Weight = 3.0; + Hue = 0x59C; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public RangerLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 35; - public override int LabelNumber => 1041496; // studded leggings, ranger armor + public override int ArmorBase => 16; - [Constructible] - public RangerLegs() : base( 0x13DA ) - { - Weight = 3.0; - Hue = 0x59C; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public RangerLegs( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041496; // studded leggings, ranger armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 5.0; - } - } -} + if (Weight == 3.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ring/RingmailArms.cs b/Scripts/Items/Armor/Ring/RingmailArms.cs index 002265f60..96735d944 100644 --- a/Scripts/Items/Armor/Ring/RingmailArms.cs +++ b/Scripts/Items/Armor/Ring/RingmailArms.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x13ee, 0x13ef )] - public class RingmailArms : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 1; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + [Flippable(0x13ee, 0x13ef)] + public class RingmailArms : BaseArmor + { + [Constructible] + public RingmailArms() : base(0x13EE) + { + Weight = 15.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public RingmailArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 1; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -1; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override int ArmorBase => 22; + public override int AosStrReq => 40; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; + public override int OldDexBonus => -1; - [Constructible] - public RingmailArms() : base( 0x13EE ) - { - Weight = 15.0; - } + public override int ArmorBase => 22; - public RingmailArms( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 15.0; - } - } -} + if (Weight == 1.0) + Weight = 15.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ring/RingmailChest.cs b/Scripts/Items/Armor/Ring/RingmailChest.cs index d68eb37c6..02211a66e 100644 --- a/Scripts/Items/Armor/Ring/RingmailChest.cs +++ b/Scripts/Items/Armor/Ring/RingmailChest.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x13ec, 0x13ed )] - public class RingmailChest : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 1; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + [Flippable(0x13ec, 0x13ed)] + public class RingmailChest : BaseArmor + { + [Constructible] + public RingmailChest() : base(0x13EC) + { + Weight = 15.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public RingmailChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 1; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -2; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override int ArmorBase => 22; + public override int AosStrReq => 40; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; + public override int OldDexBonus => -2; - [Constructible] - public RingmailChest() : base( 0x13EC ) - { - Weight = 15.0; - } + public override int ArmorBase => 22; - public RingmailChest( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 15.0; - } - } -} + if (Weight == 1.0) + Weight = 15.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ring/RingmailGloves.cs b/Scripts/Items/Armor/Ring/RingmailGloves.cs index 2fa50a319..bd89b7034 100644 --- a/Scripts/Items/Armor/Ring/RingmailGloves.cs +++ b/Scripts/Items/Armor/Ring/RingmailGloves.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x13eb, 0x13f2 )] - public class RingmailGloves : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 1; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + [Flippable(0x13eb, 0x13f2)] + public class RingmailGloves : BaseArmor + { + [Constructible] + public RingmailGloves() : base(0x13EB) + { + Weight = 2.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public RingmailGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 1; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -1; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override int ArmorBase => 22; + public override int AosStrReq => 40; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; + public override int OldDexBonus => -1; - [Constructible] - public RingmailGloves() : base( 0x13EB ) - { - Weight = 2.0; - } + public override int ArmorBase => 22; - public RingmailGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Ring/RingmailLegs.cs b/Scripts/Items/Armor/Ring/RingmailLegs.cs index 5e53c7467..75856e2c3 100644 --- a/Scripts/Items/Armor/Ring/RingmailLegs.cs +++ b/Scripts/Items/Armor/Ring/RingmailLegs.cs @@ -1,46 +1,46 @@ namespace Server.Items { - [FlippableAttribute( 0x13f0, 0x13f1 )] - public class RingmailLegs : BaseArmor - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 1; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + [Flippable(0x13f0, 0x13f1)] + public class RingmailLegs : BaseArmor + { + [Constructible] + public RingmailLegs() : base(0x13F0) + { + Weight = 15.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public RingmailLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 1; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -1; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override int ArmorBase => 22; + public override int AosStrReq => 40; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; + public override int OldDexBonus => -1; - [Constructible] - public RingmailLegs() : base( 0x13F0 ) - { - Weight = 15.0; - } + public override int ArmorBase => 22; - public RingmailLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/FemaleStuddedChest.cs b/Scripts/Items/Armor/Studded/FemaleStuddedChest.cs index f61662a94..1aeb75537 100644 --- a/Scripts/Items/Armor/Studded/FemaleStuddedChest.cs +++ b/Scripts/Items/Armor/Studded/FemaleStuddedChest.cs @@ -1,52 +1,52 @@ namespace Server.Items { - [FlippableAttribute( 0x1c02, 0x1c03 )] - public class FemaleStuddedChest : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x1c02, 0x1c03)] + public class FemaleStuddedChest : BaseArmor + { + [Constructible] + public FemaleStuddedChest() : base(0x1C02) + { + Weight = 6.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public FemaleStuddedChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 35; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 35; + public override int OldStrReq => 35; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public FemaleStuddedChest() : base( 0x1C02 ) - { - Weight = 6.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public FemaleStuddedChest( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 6.0; - } - } -} + if (Weight == 1.0) + Weight = 6.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/HideChest.cs b/Scripts/Items/Armor/Studded/HideChest.cs index 7856f8a88..f7466f88d 100644 --- a/Scripts/Items/Armor/Studded/HideChest.cs +++ b/Scripts/Items/Armor/Studded/HideChest.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2B74, 0x316B )] - public class HideChest : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B74, 0x316B)] + public class HideChest : BaseArmor + { + [Constructible] + public HideChest() : base(0x2B74) + { + Weight = 6.0; + } - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public HideChest(Serial serial) : base(serial) + { + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 15; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 15; - [Constructible] - public HideChest() : base( 0x2B74 ) - { - Weight = 6.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public HideChest( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/HideFemaleChest.cs b/Scripts/Items/Armor/Studded/HideFemaleChest.cs index 4afaa1100..e80c76c04 100644 --- a/Scripts/Items/Armor/Studded/HideFemaleChest.cs +++ b/Scripts/Items/Armor/Studded/HideFemaleChest.cs @@ -1,53 +1,53 @@ namespace Server.Items { - [FlippableAttribute( 0x2B79, 0x3170 )] - public class HideFemaleChest : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B79, 0x3170)] + public class HideFemaleChest : BaseArmor + { + [Constructible] + public HideFemaleChest() : base(0x2B79) + { + Weight = 6.0; + } - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public HideFemaleChest(Serial serial) : base(serial) + { + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 35; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 15; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 35; + public override int OldStrReq => 35; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 15; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public HideFemaleChest() : base( 0x2B79 ) - { - Weight = 6.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public HideFemaleChest( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/HideGloves.cs b/Scripts/Items/Armor/Studded/HideGloves.cs index 64472840f..6a6bfa0aa 100644 --- a/Scripts/Items/Armor/Studded/HideGloves.cs +++ b/Scripts/Items/Armor/Studded/HideGloves.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2B75, 0x316C )] - public class HideGloves : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B75, 0x316C)] + public class HideGloves : BaseArmor + { + [Constructible] + public HideGloves() : base(0x2B75) + { + Weight = 2.0; + } - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public HideGloves(Serial serial) : base(serial) + { + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 15; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 15; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 15; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 15; - [Constructible] - public HideGloves() : base( 0x2B75 ) - { - Weight = 2.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public HideGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/HideGorget.cs b/Scripts/Items/Armor/Studded/HideGorget.cs index a92a0aff8..ebd4ba8d1 100644 --- a/Scripts/Items/Armor/Studded/HideGorget.cs +++ b/Scripts/Items/Armor/Studded/HideGorget.cs @@ -1,52 +1,52 @@ namespace Server.Items { - [FlippableAttribute( 0x2B76, 0x316D )] - public class HideGorget : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B76, 0x316D)] + public class HideGorget : BaseArmor + { + [Constructible] + public HideGorget() : base(0x2B76) + { + Weight = 3.0; + } - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public HideGorget(Serial serial) : base(serial) + { + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 15; - public override int OldStrReq => 15; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 15; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 15; + public override int OldStrReq => 15; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 15; - [Constructible] - public HideGorget() : base( 0x2B76 ) - { - Weight = 3.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public HideGorget( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } -} + if (Weight == 2.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/HidePants.cs b/Scripts/Items/Armor/Studded/HidePants.cs index e9d5d898d..e2dbf171d 100644 --- a/Scripts/Items/Armor/Studded/HidePants.cs +++ b/Scripts/Items/Armor/Studded/HidePants.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2B78, 0x316F )] - public class HidePants : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B78, 0x316F)] + public class HidePants : BaseArmor + { + [Constructible] + public HidePants() : base(0x2B78) + { + Weight = 5.0; + } - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public HidePants(Serial serial) : base(serial) + { + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 15; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 15; - [Constructible] - public HidePants() : base( 0x2B78 ) - { - Weight = 5.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public HidePants( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/HidePauldrons.cs b/Scripts/Items/Armor/Studded/HidePauldrons.cs index a121f69cd..567a12e9f 100644 --- a/Scripts/Items/Armor/Studded/HidePauldrons.cs +++ b/Scripts/Items/Armor/Studded/HidePauldrons.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2B77, 0x316E )] - public class HidePauldrons : BaseArmor - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2B77, 0x316E)] + public class HidePauldrons : BaseArmor + { + [Constructible] + public HidePauldrons() : base(0x2B77) + { + Weight = 4.0; + } - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 4; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 2; + public HidePauldrons(Serial serial) : base(serial) + { + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public override Race RequiredRace => Race.Elf; - public override int AosStrReq => 20; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 4; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 2; - public override int ArmorBase => 15; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 20; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 15; - [Constructible] - public HidePauldrons() : base( 0x2B77 ) - { - Weight = 4.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public HidePauldrons( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedArms.cs b/Scripts/Items/Armor/Studded/StuddedArms.cs index 3ef384867..bf9c93fc7 100644 --- a/Scripts/Items/Armor/Studded/StuddedArms.cs +++ b/Scripts/Items/Armor/Studded/StuddedArms.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13dc, 0x13d4 )] - public class StuddedArms : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13dc, 0x13d4)] + public class StuddedArms : BaseArmor + { + [Constructible] + public StuddedArms() : base(0x13DC) + { + Weight = 4.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - [Constructible] - public StuddedArms() : base( 0x13DC ) - { - Weight = 4.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public StuddedArms( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 4.0; - } - } -} + if (Weight == 1.0) + Weight = 4.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedBustierArms.cs b/Scripts/Items/Armor/Studded/StuddedBustierArms.cs index 24f3ddf0f..eee9bb458 100644 --- a/Scripts/Items/Armor/Studded/StuddedBustierArms.cs +++ b/Scripts/Items/Armor/Studded/StuddedBustierArms.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1c0c, 0x1c0d )] - public class StuddedBustierArms : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x1c0c, 0x1c0d)] + public class StuddedBustierArms : BaseArmor + { + [Constructible] + public StuddedBustierArms() : base(0x1C0C) + { + Weight = 1.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedBustierArms(Serial serial) : base(serial) + { + } - public override int AosStrReq => 35; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 35; + public override int OldStrReq => 35; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - public override bool AllowMaleWearer => false; + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public StuddedBustierArms() : base( 0x1C0C ) - { - Weight = 1.0; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public StuddedBustierArms( Serial serial ) : base( serial ) - { - } + public override bool AllowMaleWearer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedChest.cs b/Scripts/Items/Armor/Studded/StuddedChest.cs index 3d4dc33ba..e4b612aa7 100644 --- a/Scripts/Items/Armor/Studded/StuddedChest.cs +++ b/Scripts/Items/Armor/Studded/StuddedChest.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13db, 0x13e2 )] - public class StuddedChest : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13db, 0x13e2)] + public class StuddedChest : BaseArmor + { + [Constructible] + public StuddedChest() : base(0x13DB) + { + Weight = 8.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedChest(Serial serial) : base(serial) + { + } - public override int AosStrReq => 35; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 35; + public override int OldStrReq => 35; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - [Constructible] - public StuddedChest() : base( 0x13DB ) - { - Weight = 8.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public StuddedChest( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 8.0; - } - } -} + if (Weight == 1.0) + Weight = 8.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedDo.cs b/Scripts/Items/Armor/Studded/StuddedDo.cs index b2635321c..5e63952ea 100644 --- a/Scripts/Items/Armor/Studded/StuddedDo.cs +++ b/Scripts/Items/Armor/Studded/StuddedDo.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class StuddedDo : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class StuddedDo : BaseArmor + { + [Constructible] + public StuddedDo() : base(0x27C7) + { + Weight = 8.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public StuddedDo(Serial serial) : base(serial) + { + } - public override int AosStrReq => 55; - public override int OldStrReq => 55; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 3; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 55; + public override int OldStrReq => 55; - [Constructible] - public StuddedDo() : base( 0x27C7 ) - { - Weight = 8.0; - } + public override int ArmorBase => 3; - public StuddedDo( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedGloves.cs b/Scripts/Items/Armor/Studded/StuddedGloves.cs index 9a45a2600..a3fcd8f41 100644 --- a/Scripts/Items/Armor/Studded/StuddedGloves.cs +++ b/Scripts/Items/Armor/Studded/StuddedGloves.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13d5, 0x13dd )] - public class StuddedGloves : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13d5, 0x13dd)] + public class StuddedGloves : BaseArmor + { + [Constructible] + public StuddedGloves() : base(0x13D5) + { + Weight = 1.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedGloves(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - [Constructible] - public StuddedGloves() : base( 0x13D5 ) - { - Weight = 1.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public StuddedGloves( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } -} + if (Weight == 2.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedGorget.cs b/Scripts/Items/Armor/Studded/StuddedGorget.cs index a24391ce7..fbb1fd7be 100644 --- a/Scripts/Items/Armor/Studded/StuddedGorget.cs +++ b/Scripts/Items/Armor/Studded/StuddedGorget.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class StuddedGorget : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class StuddedGorget : BaseArmor + { + [Constructible] + public StuddedGorget() : base(0x13D6) + { + Weight = 1.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedGorget(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - [Constructible] - public StuddedGorget() : base( 0x13D6 ) - { - Weight = 1.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public StuddedGorget( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } -} + if (Weight == 2.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedHaidate.cs b/Scripts/Items/Armor/Studded/StuddedHaidate.cs index 9c35d909d..a9950fb65 100644 --- a/Scripts/Items/Armor/Studded/StuddedHaidate.cs +++ b/Scripts/Items/Armor/Studded/StuddedHaidate.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class StuddedHaidate : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class StuddedHaidate : BaseArmor + { + [Constructible] + public StuddedHaidate() : base(0x278B) + { + Weight = 5.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedHaidate(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 3; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 30; - [Constructible] - public StuddedHaidate() : base( 0x278B ) - { - Weight = 5.0; - } + public override int ArmorBase => 3; - public StuddedHaidate( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedHiroSode.cs b/Scripts/Items/Armor/Studded/StuddedHiroSode.cs index 7de94d4cf..960f8ff0b 100644 --- a/Scripts/Items/Armor/Studded/StuddedHiroSode.cs +++ b/Scripts/Items/Armor/Studded/StuddedHiroSode.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class StuddedHiroSode : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class StuddedHiroSode : BaseArmor + { + [Constructible] + public StuddedHiroSode() : base(0x277F) + { + Weight = 1.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 55; + public StuddedHiroSode(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 3; + public override int InitMinHits => 45; + public override int InitMaxHits => 55; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 30; - [Constructible] - public StuddedHiroSode() : base( 0x277F ) - { - Weight = 1.0; - } + public override int ArmorBase => 3; - public StuddedHiroSode( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedLegs.cs b/Scripts/Items/Armor/Studded/StuddedLegs.cs index c914178ec..fad053907 100644 --- a/Scripts/Items/Armor/Studded/StuddedLegs.cs +++ b/Scripts/Items/Armor/Studded/StuddedLegs.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13da, 0x13e1 )] - public class StuddedLegs : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13da, 0x13e1)] + public class StuddedLegs : BaseArmor + { + [Constructible] + public StuddedLegs() : base(0x13DA) + { + Weight = 5.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedLegs(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 35; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 35; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; + public override int ArmorBase => 16; - [Constructible] - public StuddedLegs() : base( 0x13DA ) - { - Weight = 5.0; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public StuddedLegs( Serial serial ) : base( serial ) - { - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.Half; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 5.0; - } - } -} + if (Weight == 3.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedMempo.cs b/Scripts/Items/Armor/Studded/StuddedMempo.cs index 8e3654861..d30c6d7e4 100644 --- a/Scripts/Items/Armor/Studded/StuddedMempo.cs +++ b/Scripts/Items/Armor/Studded/StuddedMempo.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class StuddedMempo : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public class StuddedMempo : BaseArmor + { + [Constructible] + public StuddedMempo() : base(0x279D) + { + Weight = 2.0; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public StuddedMempo(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 3; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 30; - [Constructible] - public StuddedMempo() : base( 0x279D ) - { - Weight = 2.0; - } + public override int ArmorBase => 3; - public StuddedMempo( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Armor/Studded/StuddedSuneate.cs b/Scripts/Items/Armor/Studded/StuddedSuneate.cs index 0d2dcef2c..cbca5ac9e 100644 --- a/Scripts/Items/Armor/Studded/StuddedSuneate.cs +++ b/Scripts/Items/Armor/Studded/StuddedSuneate.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class StuddedSuneate : BaseArmor - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + public class StuddedSuneate : BaseArmor + { + [Constructible] + public StuddedSuneate() : base(0x27D2) + { + Weight = 5.0; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 50; + public StuddedSuneate(Serial serial) : base(serial) + { + } - public override int AosStrReq => 30; - public override int OldStrReq => 30; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 3; + public override int InitMinHits => 35; + public override int InitMaxHits => 50; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 30; + public override int OldStrReq => 30; - [Constructible] - public StuddedSuneate() : base( 0x27D2 ) - { - Weight = 5.0; - } + public override int ArmorBase => 3; - public StuddedSuneate( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Body Parts/BonePile.cs b/Scripts/Items/Body Parts/BonePile.cs index 4326f8594..4c55ce2b8 100644 --- a/Scripts/Items/Body Parts/BonePile.cs +++ b/Scripts/Items/Body Parts/BonePile.cs @@ -1,41 +1,41 @@ namespace Server.Items { - [FlippableAttribute( 0x1B09, 0x1B10 )] - public class BonePile : Item, IScissorable - { - [Constructible] - public BonePile( ) : base( 0x1B09 + Utility.Random( 8 ) ) - { - Stackable = false; - Weight = 10.0; - } + [Flippable(0x1B09, 0x1B10)] + public class BonePile : Item, IScissorable + { + [Constructible] + public BonePile() : base(0x1B09 + Utility.Random(8)) + { + Stackable = false; + Weight = 10.0; + } - public BonePile( Serial serial ) : base( serial ) - { - } + public BonePile(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) + return false; - writer.Write( (int) 0 ); // version - } + base.ScissorHelper(from, new Bone(), Utility.RandomMinMax(10, 15)); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return true; + } - int version = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) - return false; + writer.Write(0); // version + } - base.ScissorHelper( from, new Bone(), Utility.RandomMinMax( 10, 15 ) ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return true; - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/Head.cs b/Scripts/Items/Body Parts/Head.cs index 1b9262db5..a72994324 100644 --- a/Scripts/Items/Body Parts/Head.cs +++ b/Scripts/Items/Body Parts/Head.cs @@ -1,116 +1,114 @@ -using System; - namespace Server.Items { - public enum HeadType - { - Regular, - Duel, - Tournament - } + public enum HeadType + { + Regular, + Duel, + Tournament + } - public class Head : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public string PlayerName { get; set; } + public class Head : Item + { + [Constructible] + public Head() + : this(null) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public HeadType HeadType { get; set; } + [Constructible] + public Head(string playerName) + : this(HeadType.Regular, playerName) + { + } - public override string DefaultName - { - get - { - if ( PlayerName == null ) - return base.DefaultName; + [Constructible] + public Head(HeadType headType, string playerName) + : base(0x1DA0) + { + HeadType = headType; + PlayerName = playerName; + } - switch ( HeadType ) - { - default: - return $"the head of {PlayerName}"; + public Head(Serial serial) + : base(serial) + { + } - case HeadType.Duel: - return $"the head of {PlayerName}, taken in a duel"; + [CommandProperty(AccessLevel.GameMaster)] + public string PlayerName{ get; set; } - case HeadType.Tournament: - return $"the head of {PlayerName}, taken in a tournament"; - } - } - } + [CommandProperty(AccessLevel.GameMaster)] + public HeadType HeadType{ get; set; } - [Constructible] - public Head() - : this( null ) - { - } + public override string DefaultName + { + get + { + if (PlayerName == null) + return base.DefaultName; - [Constructible] - public Head( string playerName ) - : this( HeadType.Regular, playerName ) - { - } + switch (HeadType) + { + default: + return $"the head of {PlayerName}"; - [Constructible] - public Head( HeadType headType, string playerName ) - : base( 0x1DA0 ) - { - HeadType = headType; - PlayerName = playerName; - } + case HeadType.Duel: + return $"the head of {PlayerName}, taken in a duel"; - public Head( Serial serial ) - : base( serial ) - { - } + case HeadType.Tournament: + return $"the head of {PlayerName}, taken in a tournament"; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (string) PlayerName ); - writer.WriteEncodedInt( (int) HeadType ); - } + writer.Write(PlayerName); + writer.WriteEncodedInt((int)HeadType); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - PlayerName = reader.ReadString(); - HeadType = (HeadType) reader.ReadEncodedInt(); - break; + switch (version) + { + case 1: + PlayerName = reader.ReadString(); + HeadType = (HeadType)reader.ReadEncodedInt(); + break; - case 0: - string format = Name; + case 0: + string format = Name; - if ( format != null ) - { - if ( format.StartsWith( "the head of " ) ) - format = format.Substring( "the head of ".Length ); + if (format != null) + { + if (format.StartsWith("the head of ")) + format = format.Substring("the head of ".Length); - if ( format.EndsWith( ", taken in a duel" ) ) - { - format = format.Substring( 0, format.Length - ", taken in a duel".Length ); - HeadType = HeadType.Duel; - } - else if ( format.EndsWith( ", taken in a tournament" ) ) - { - format = format.Substring( 0, format.Length - ", taken in a tournament".Length ); - HeadType = HeadType.Tournament; - } - } + if (format.EndsWith(", taken in a duel")) + { + format = format.Substring(0, format.Length - ", taken in a duel".Length); + HeadType = HeadType.Duel; + } + else if (format.EndsWith(", taken in a tournament")) + { + format = format.Substring(0, format.Length - ", taken in a tournament".Length); + HeadType = HeadType.Tournament; + } + } - PlayerName = format; - Name = null; + PlayerName = format; + Name = null; - break; - } - } - } + break; + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/LeftArm.cs b/Scripts/Items/Body Parts/LeftArm.cs index 75beb146b..47e4bb29c 100644 --- a/Scripts/Items/Body Parts/LeftArm.cs +++ b/Scripts/Items/Body Parts/LeftArm.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class LeftArm : Item - { - [Constructible] - public LeftArm() : base( 0x1DA1 ) - { - } + public class LeftArm : Item + { + [Constructible] + public LeftArm() : base(0x1DA1) + { + } - public LeftArm( Serial serial ) : base( serial ) - { - } + public LeftArm(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/LeftLeg.cs b/Scripts/Items/Body Parts/LeftLeg.cs index 070c21490..676ecaf6f 100644 --- a/Scripts/Items/Body Parts/LeftLeg.cs +++ b/Scripts/Items/Body Parts/LeftLeg.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class LeftLeg : Item - { - [Constructible] - public LeftLeg() : base( 0x1DA3 ) - { - } + public class LeftLeg : Item + { + [Constructible] + public LeftLeg() : base(0x1DA3) + { + } - public LeftLeg( Serial serial ) : base( serial ) - { - } + public LeftLeg(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/RibCage.cs b/Scripts/Items/Body Parts/RibCage.cs index 4aaf01b44..49000c127 100644 --- a/Scripts/Items/Body Parts/RibCage.cs +++ b/Scripts/Items/Body Parts/RibCage.cs @@ -1,41 +1,41 @@ namespace Server.Items { - [FlippableAttribute( 0x1B17, 0x1B18 )] - public class RibCage : Item, IScissorable - { - [Constructible] - public RibCage() : base( 0x1B17 + Utility.Random( 2 ) ) - { - Stackable = false; - Weight = 5.0; - } + [Flippable(0x1B17, 0x1B18)] + public class RibCage : Item, IScissorable + { + [Constructible] + public RibCage() : base(0x1B17 + Utility.Random(2)) + { + Stackable = false; + Weight = 5.0; + } - public RibCage( Serial serial ) : base( serial ) - { - } + public RibCage(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) + return false; - writer.Write( (int) 0 ); // version - } + base.ScissorHelper(from, new Bone(), Utility.RandomMinMax(3, 5)); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return true; + } - int version = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) - return false; + writer.Write(0); // version + } - base.ScissorHelper( from, new Bone(), Utility.RandomMinMax( 3, 5 ) ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return true; - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/RightArm.cs b/Scripts/Items/Body Parts/RightArm.cs index 7438a28ff..ab2f62bd6 100644 --- a/Scripts/Items/Body Parts/RightArm.cs +++ b/Scripts/Items/Body Parts/RightArm.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class RightArm : Item - { - [Constructible] - public RightArm() : base( 0x1DA2 ) - { - } + public class RightArm : Item + { + [Constructible] + public RightArm() : base(0x1DA2) + { + } - public RightArm( Serial serial ) : base( serial ) - { - } + public RightArm(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/RightLeg.cs b/Scripts/Items/Body Parts/RightLeg.cs index d2cc118ab..f31dd54b3 100644 --- a/Scripts/Items/Body Parts/RightLeg.cs +++ b/Scripts/Items/Body Parts/RightLeg.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class RightLeg : Item - { - [Constructible] - public RightLeg() : base( 0x1DA4 ) - { - } + public class RightLeg : Item + { + [Constructible] + public RightLeg() : base(0x1DA4) + { + } - public RightLeg( Serial serial ) : base( serial ) - { - } + public RightLeg(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Body Parts/Torso.cs b/Scripts/Items/Body Parts/Torso.cs index fb0a8d11d..f9541aac4 100644 --- a/Scripts/Items/Body Parts/Torso.cs +++ b/Scripts/Items/Body Parts/Torso.cs @@ -1,29 +1,29 @@ namespace Server.Items { - public class Torso : Item - { - [Constructible] - public Torso() : base( 0x1D9F ) - { - Weight = 2.0; - } + public class Torso : Item + { + [Constructible] + public Torso() : base(0x1D9F) + { + Weight = 2.0; + } - public Torso( Serial serial ) : base( serial ) - { - } + public Torso(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Books/BaseBook.cs b/Scripts/Items/Books/BaseBook.cs index a6706c67a..2bc618875 100644 --- a/Scripts/Items/Books/BaseBook.cs +++ b/Scripts/Items/Books/BaseBook.cs @@ -3,495 +3,498 @@ using System.Collections.Generic; using System.IO; using System.Text; using Server.ContextMenus; -using Server.Network; using Server.Gumps; using Server.Multis; +using Server.Network; namespace Server.Items { - public class BookPageInfo - { - public string[] Lines { get; set; } - - public BookPageInfo() - { - Lines = new string[0]; - } - - public BookPageInfo( params string[] lines ) - { - Lines = lines; - } - - public BookPageInfo( GenericReader reader ) - { - int length = reader.ReadInt(); - - Lines = new string[length]; - - for ( int i = 0; i < Lines.Length; ++i ) - Lines[i] = Utility.Intern( reader.ReadString() ); - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( Lines.Length ); - - for ( int i = 0; i < Lines.Length; ++i ) - writer.Write( Lines[i] ); - } - } - - public class BaseBook : Item, ISecurable - { - private string m_Title; - private string m_Author; - - [CommandProperty( AccessLevel.GameMaster )] - public string Title - { - get => m_Title; - set { m_Title = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string Author - { - get => m_Author; - set { m_Author = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Writable { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public int PagesCount => Pages.Length; - - public BookPageInfo[] Pages { get; private set; } - - [Constructible] - public BaseBook( int itemID ) : this( itemID, 20, true ) - { - } - - [Constructible] - public BaseBook( int itemID, int pageCount, bool writable ) : this( itemID, null, null, pageCount, writable ) - { - } - - [Constructible] - public BaseBook( int itemID, string title, string author, int pageCount, bool writable ) : base( itemID ) - { - m_Title = title; - m_Author = author; - Writable = writable; - - BookContent content = DefaultContent; - - if ( content == null ) - { - Pages = new BookPageInfo[pageCount]; + public class BookPageInfo + { + public BookPageInfo() + { + Lines = new string[0]; + } + + public BookPageInfo(params string[] lines) + { + Lines = lines; + } + + public BookPageInfo(GenericReader reader) + { + int length = reader.ReadInt(); + + Lines = new string[length]; + + for (int i = 0; i < Lines.Length; ++i) + Lines[i] = Utility.Intern(reader.ReadString()); + } + + public string[] Lines{ get; set; } + + public void Serialize(GenericWriter writer) + { + writer.Write(Lines.Length); + + for (int i = 0; i < Lines.Length; ++i) + writer.Write(Lines[i]); + } + } + + public class BaseBook : Item, ISecurable + { + private string m_Author; + private string m_Title; + + [Constructible] + public BaseBook(int itemID) : this(itemID, 20, true) + { + } + + [Constructible] + public BaseBook(int itemID, int pageCount, bool writable) : this(itemID, null, null, pageCount, writable) + { + } + + [Constructible] + public BaseBook(int itemID, string title, string author, int pageCount, bool writable) : base(itemID) + { + m_Title = title; + m_Author = author; + Writable = writable; + + BookContent content = DefaultContent; + + if (content == null) + { + Pages = new BookPageInfo[pageCount]; + + for (int i = 0; i < Pages.Length; ++i) + Pages[i] = new BookPageInfo(); + } + else + { + Pages = content.Copy(); + } + } + + // Intended for defined books only + public BaseBook(int itemID, bool writable) : base(itemID) + { + Writable = writable; + + BookContent content = DefaultContent; + + if (content == null) + { + Pages = new BookPageInfo[0]; + } + else + { + m_Title = content.Title; + m_Author = content.Author; + Pages = content.Copy(); + } + } + + public BaseBook(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Title + { + get => m_Title; + set + { + m_Title = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Author + { + get => m_Author; + set + { + m_Author = value; + InvalidateProperties(); + } + } - for ( int i = 0; i < Pages.Length; ++i ) - Pages[i] = new BookPageInfo(); - } - else - { - Pages = content.Copy(); - } - } - - // Intended for defined books only - public BaseBook( int itemID, bool writable ) : base( itemID ) - { - Writable = writable; - - BookContent content = DefaultContent; - - if ( content == null ) - { - Pages = new BookPageInfo[0]; - } - else - { - m_Title = content.Title; - m_Author = content.Author; - Pages = content.Copy(); - } - } - - public virtual BookContent DefaultContent => null; - - public BaseBook( Serial serial ) : base( serial ) - { - } - - [Flags] - private enum SaveFlags - { - None = 0x00, - Title = 0x01, - Author = 0x02, - Writable = 0x04, - Content = 0x08 - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - BookContent content = DefaultContent; - - SaveFlags flags = SaveFlags.None; - - if ( m_Title != content?.Title ) - flags |= SaveFlags.Title; - - if ( m_Author != content?.Author ) - flags |= SaveFlags.Author; - - if ( Writable ) - flags |= SaveFlags.Writable; - - if ( content == null || !content.IsMatch( Pages ) ) - flags |= SaveFlags.Content; - - - - writer.Write( (int) 4 ); // version - - writer.Write( (int)Level ); - - writer.Write( (byte) flags ); - - if ( (flags & SaveFlags.Title) != 0 ) - writer.Write( m_Title ); - - if ( (flags & SaveFlags.Author) != 0 ) - writer.Write( m_Author ); - - if ( (flags & SaveFlags.Content) != 0 ) - { - writer.WriteEncodedInt( Pages.Length ); - - for ( int i = 0; i < Pages.Length; ++i ) - Pages[i].Serialize( writer ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 4: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 3; - } - case 3: - case 2: - { - BookContent content = DefaultContent; - - SaveFlags flags = (SaveFlags) reader.ReadByte(); - - if ( (flags & SaveFlags.Title) != 0 ) - m_Title = Utility.Intern( reader.ReadString() ); - else if ( content != null ) - m_Title = content.Title; - - if ( (flags & SaveFlags.Author) != 0 ) - m_Author = reader.ReadString(); - else if ( content != null ) - m_Author = content.Author; - - Writable = ( flags & SaveFlags.Writable ) != 0; - - if ( (flags & SaveFlags.Content) != 0 ) - { - Pages = new BookPageInfo[reader.ReadEncodedInt()]; - - for ( int i = 0; i < Pages.Length; ++i ) - Pages[i] = new BookPageInfo( reader ); - } - else - { - if ( content != null ) - Pages = content.Copy(); - else - Pages = new BookPageInfo[0]; - } - - break; - } - case 1: - case 0: - { - m_Title = reader.ReadString(); - m_Author = reader.ReadString(); - Writable = reader.ReadBool(); - - if ( version == 0 || reader.ReadBool() ) - { - Pages = new BookPageInfo[reader.ReadInt()]; - - for ( int i = 0; i < Pages.Length; ++i ) - Pages[i] = new BookPageInfo( reader ); - } - else - { - BookContent content = DefaultContent; - - if ( content != null ) - Pages = content.Copy(); - else - Pages = new BookPageInfo[0]; - } - - break; - } - } - - if ( version < 3 && ( Weight == 1 || Weight == 2 ) ) - Weight = -1; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_Title != null && m_Title.Length > 0 ) - list.Add( m_Title ); - else - base.AddNameProperty( list ); - } - - /*public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_Title != null && m_Title.Length > 0 ) - list.Add( 1060658, "Title\t{0}", m_Title ); // ~1_val~: ~2_val~ - - if ( m_Author != null && m_Author.Length > 0 ) - list.Add( 1060659, "Author\t{0}", m_Author ); // ~1_val~: ~2_val~ - - if ( m_Pages != null && m_Pages.Length > 0 ) - list.Add( 1060660, "Pages\t{0}", m_Pages.Length ); // ~1_val~: ~2_val~ - }*/ - - public override void OnSingleClick ( Mobile from ) - { - LabelTo( from, "{0} by {1}", m_Title, m_Author ); - LabelTo( from, "[{0} pages]", Pages.Length ); - } - - public override void OnDoubleClick ( Mobile from ) - { - if ( m_Title == null && m_Author == null && Writable == true ) - { - Title = "a book"; - Author = from.Name; - } - - from.Send( new BookHeader( from, this ) ); - from.Send( new BookPageDetails( this ) ); - } - - public string ContentAsString - { - get - { - StringBuilder sb = new StringBuilder(); - - foreach( BookPageInfo bpi in Pages ) - { - foreach( string line in bpi.Lines ) - { - sb.AppendLine( line ); - } - } - - return sb.ToString(); - } - } - - public string[] ContentAsStringArray - { - get - { - List lines = new List(); - - foreach( BookPageInfo bpi in Pages ) - { - lines.AddRange( bpi.Lines ); - } - - return lines.ToArray(); - } - } - - public static void Initialize() - { - PacketHandlers.Register( 0xD4, 0, true, HeaderChange ); - PacketHandlers.Register( 0x66, 0, true, ContentChange ); - PacketHandlers.Register( 0x93, 99, true, OldHeaderChange ); - } - - public static void OldHeaderChange( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BaseBook book) || !book.Writable || !from.InRange( book.GetWorldLocation(), 1 ) || !book.IsAccessibleTo( from ) ) - return; - - pvSrc.Seek( 4, SeekOrigin.Current ); // Skip flags and page count - - string title = pvSrc.ReadStringSafe( 60 ); - string author = pvSrc.ReadStringSafe( 30 ); + [CommandProperty(AccessLevel.GameMaster)] + public bool Writable{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int PagesCount => Pages.Length; + + public BookPageInfo[] Pages{ get; private set; } + + public virtual BookContent DefaultContent => null; + + public string ContentAsString + { + get + { + StringBuilder sb = new StringBuilder(); + + foreach (BookPageInfo bpi in Pages) + foreach (string line in bpi.Lines) + sb.AppendLine(line); + + return sb.ToString(); + } + } + + public string[] ContentAsStringArray + { + get + { + List lines = new List(); + + foreach (BookPageInfo bpi in Pages) lines.AddRange(bpi.Lines); + + return lines.ToArray(); + } + } + + #region ISecurable Members + + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } + + #endregion + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + BookContent content = DefaultContent; + + SaveFlags flags = SaveFlags.None; + + if (m_Title != content?.Title) + flags |= SaveFlags.Title; + + if (m_Author != content?.Author) + flags |= SaveFlags.Author; + + if (Writable) + flags |= SaveFlags.Writable; + + if (content == null || !content.IsMatch(Pages)) + flags |= SaveFlags.Content; + + + writer.Write(4); // version + + writer.Write((int)Level); + + writer.Write((byte)flags); + + if ((flags & SaveFlags.Title) != 0) + writer.Write(m_Title); + + if ((flags & SaveFlags.Author) != 0) + writer.Write(m_Author); + + if ((flags & SaveFlags.Content) != 0) + { + writer.WriteEncodedInt(Pages.Length); + + for (int i = 0; i < Pages.Length; ++i) + Pages[i].Serialize(writer); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - book.Title = Utility.FixHtml( title ); - book.Author = Utility.FixHtml( author ); - } + int version = reader.ReadInt(); - public static void HeaderChange( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BaseBook book) || !book.Writable || !from.InRange( book.GetWorldLocation(), 1 ) || !book.IsAccessibleTo( from ) ) - return; - - pvSrc.Seek( 4, SeekOrigin.Current ); // Skip flags and page count - - int titleLength = pvSrc.ReadUInt16(); - - if ( titleLength > 60 ) - return; - - string title = pvSrc.ReadUTF8StringSafe( titleLength ); - - int authorLength = pvSrc.ReadUInt16(); - - if ( authorLength > 30 ) - return; - - string author = pvSrc.ReadUTF8StringSafe( authorLength ); - - book.Title = Utility.FixHtml( title ); - book.Author = Utility.FixHtml( author ); - } - - public static void ContentChange( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BaseBook book) || !book.Writable || !from.InRange( book.GetWorldLocation(), 1 ) || !book.IsAccessibleTo( from ) ) - return; - - int pageCount = pvSrc.ReadUInt16(); - - if ( pageCount > book.PagesCount ) - return; - - for ( int i = 0; i < pageCount; ++i ) - { - int index = pvSrc.ReadUInt16(); - - if ( index >= 1 && index <= book.PagesCount ) - { - --index; - - int lineCount = pvSrc.ReadUInt16(); - - if ( lineCount <= 8 ) - { - string[] lines = new string[lineCount]; - - for ( int j = 0; j < lineCount; ++j ) - if ( (lines[j] = pvSrc.ReadUTF8StringSafe()).Length >= 80 ) - return; - - book.Pages[index].Lines = lines; - } - else - { - return; - } - } - else - { - return; - } - } - } - - #region ISecurable Members - - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } - - #endregion - } - - public sealed class BookPageDetails : Packet - { - public BookPageDetails( BaseBook book ) : base( 0x66 ) - { - EnsureCapacity( 256 ); - - m_Stream.Write( (int) book.Serial ); - m_Stream.Write( (ushort) book.PagesCount ); - - for ( int i = 0; i < book.PagesCount; ++i ) - { - BookPageInfo page = book.Pages[i]; - - m_Stream.Write( (ushort) (i + 1) ); - m_Stream.Write( (ushort) page.Lines.Length ); - - for ( int j = 0; j < page.Lines.Length; ++j ) - { - byte[] buffer = Utility.UTF8.GetBytes( page.Lines[j] ); - - m_Stream.Write( buffer, 0, buffer.Length ); - m_Stream.Write( (byte) 0 ); - } - } - } - } - - public sealed class BookHeader : Packet - { - public BookHeader( Mobile from, BaseBook book ) : base ( 0xD4 ) - { - string title = book.Title ?? ""; - string author = book.Author ?? ""; - - byte[] titleBuffer = Utility.UTF8.GetBytes( title ); - byte[] authorBuffer = Utility.UTF8.GetBytes( author ); - - EnsureCapacity( 15 + titleBuffer.Length + authorBuffer.Length ); - - m_Stream.Write( (int) book.Serial ); - m_Stream.Write( (bool) true ); - m_Stream.Write( (bool) book.Writable && from.InRange( book.GetWorldLocation(), 1 ) ); - m_Stream.Write( (ushort) book.PagesCount ); - - m_Stream.Write( (ushort) (titleBuffer.Length + 1) ); - m_Stream.Write( titleBuffer, 0, titleBuffer.Length ); - m_Stream.Write( (byte) 0 ); // terminate - - m_Stream.Write( (ushort) (authorBuffer.Length + 1) ); - m_Stream.Write( authorBuffer, 0, authorBuffer.Length ); - m_Stream.Write( (byte) 0 ); // terminate - } - } -} + switch (version) + { + case 4: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 3; + } + case 3: + case 2: + { + BookContent content = DefaultContent; + + SaveFlags flags = (SaveFlags)reader.ReadByte(); + + if ((flags & SaveFlags.Title) != 0) + m_Title = Utility.Intern(reader.ReadString()); + else if (content != null) + m_Title = content.Title; + + if ((flags & SaveFlags.Author) != 0) + m_Author = reader.ReadString(); + else if (content != null) + m_Author = content.Author; + + Writable = (flags & SaveFlags.Writable) != 0; + + if ((flags & SaveFlags.Content) != 0) + { + Pages = new BookPageInfo[reader.ReadEncodedInt()]; + + for (int i = 0; i < Pages.Length; ++i) + Pages[i] = new BookPageInfo(reader); + } + else + { + if (content != null) + Pages = content.Copy(); + else + Pages = new BookPageInfo[0]; + } + + break; + } + case 1: + case 0: + { + m_Title = reader.ReadString(); + m_Author = reader.ReadString(); + Writable = reader.ReadBool(); + + if (version == 0 || reader.ReadBool()) + { + Pages = new BookPageInfo[reader.ReadInt()]; + + for (int i = 0; i < Pages.Length; ++i) + Pages[i] = new BookPageInfo(reader); + } + else + { + BookContent content = DefaultContent; + + if (content != null) + Pages = content.Copy(); + else + Pages = new BookPageInfo[0]; + } + + break; + } + } + + if (version < 3 && (Weight == 1 || Weight == 2)) + Weight = -1; + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_Title != null && m_Title.Length > 0) + list.Add(m_Title); + else + base.AddNameProperty(list); + } + + /*public override void GetProperties( ObjectPropertyList list ) + { + base.GetProperties( list ); + + if ( m_Title != null && m_Title.Length > 0 ) + list.Add( 1060658, "Title\t{0}", m_Title ); // ~1_val~: ~2_val~ + + if ( m_Author != null && m_Author.Length > 0 ) + list.Add( 1060659, "Author\t{0}", m_Author ); // ~1_val~: ~2_val~ + + if ( m_Pages != null && m_Pages.Length > 0 ) + list.Add( 1060660, "Pages\t{0}", m_Pages.Length ); // ~1_val~: ~2_val~ + }*/ + + public override void OnSingleClick(Mobile from) + { + LabelTo(from, "{0} by {1}", m_Title, m_Author); + LabelTo(from, "[{0} pages]", Pages.Length); + } + + public override void OnDoubleClick(Mobile from) + { + if (m_Title == null && m_Author == null && Writable) + { + Title = "a book"; + Author = from.Name; + } + + from.Send(new BookHeader(from, this)); + from.Send(new BookPageDetails(this)); + } + + public static void Initialize() + { + PacketHandlers.Register(0xD4, 0, true, HeaderChange); + PacketHandlers.Register(0x66, 0, true, ContentChange); + PacketHandlers.Register(0x93, 99, true, OldHeaderChange); + } + + public static void OldHeaderChange(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (!(World.FindItem(pvSrc.ReadInt32()) is BaseBook book) || !book.Writable || + !from.InRange(book.GetWorldLocation(), 1) || !book.IsAccessibleTo(from)) + return; + + pvSrc.Seek(4, SeekOrigin.Current); // Skip flags and page count + + string title = pvSrc.ReadStringSafe(60); + string author = pvSrc.ReadStringSafe(30); + + book.Title = Utility.FixHtml(title); + book.Author = Utility.FixHtml(author); + } + + public static void HeaderChange(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (!(World.FindItem(pvSrc.ReadInt32()) is BaseBook book) || !book.Writable || + !from.InRange(book.GetWorldLocation(), 1) || !book.IsAccessibleTo(from)) + return; + + pvSrc.Seek(4, SeekOrigin.Current); // Skip flags and page count + + int titleLength = pvSrc.ReadUInt16(); + + if (titleLength > 60) + return; + + string title = pvSrc.ReadUTF8StringSafe(titleLength); + + int authorLength = pvSrc.ReadUInt16(); + + if (authorLength > 30) + return; + + string author = pvSrc.ReadUTF8StringSafe(authorLength); + + book.Title = Utility.FixHtml(title); + book.Author = Utility.FixHtml(author); + } + + public static void ContentChange(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (!(World.FindItem(pvSrc.ReadInt32()) is BaseBook book) || !book.Writable || + !from.InRange(book.GetWorldLocation(), 1) || !book.IsAccessibleTo(from)) + return; + + int pageCount = pvSrc.ReadUInt16(); + + if (pageCount > book.PagesCount) + return; + + for (int i = 0; i < pageCount; ++i) + { + int index = pvSrc.ReadUInt16(); + + if (index >= 1 && index <= book.PagesCount) + { + --index; + + int lineCount = pvSrc.ReadUInt16(); + + if (lineCount <= 8) + { + string[] lines = new string[lineCount]; + + for (int j = 0; j < lineCount; ++j) + if ((lines[j] = pvSrc.ReadUTF8StringSafe()).Length >= 80) + return; + + book.Pages[index].Lines = lines; + } + else + { + return; + } + } + else + { + return; + } + } + } + + [Flags] + private enum SaveFlags + { + None = 0x00, + Title = 0x01, + Author = 0x02, + Writable = 0x04, + Content = 0x08 + } + } + + public sealed class BookPageDetails : Packet + { + public BookPageDetails(BaseBook book) : base(0x66) + { + EnsureCapacity(256); + + m_Stream.Write(book.Serial); + m_Stream.Write((ushort)book.PagesCount); + + for (int i = 0; i < book.PagesCount; ++i) + { + BookPageInfo page = book.Pages[i]; + + m_Stream.Write((ushort)(i + 1)); + m_Stream.Write((ushort)page.Lines.Length); + + for (int j = 0; j < page.Lines.Length; ++j) + { + byte[] buffer = Utility.UTF8.GetBytes(page.Lines[j]); + + m_Stream.Write(buffer, 0, buffer.Length); + m_Stream.Write((byte)0); + } + } + } + } + + public sealed class BookHeader : Packet + { + public BookHeader(Mobile from, BaseBook book) : base(0xD4) + { + string title = book.Title ?? ""; + string author = book.Author ?? ""; + + byte[] titleBuffer = Utility.UTF8.GetBytes(title); + byte[] authorBuffer = Utility.UTF8.GetBytes(author); + + EnsureCapacity(15 + titleBuffer.Length + authorBuffer.Length); + + m_Stream.Write(book.Serial); + m_Stream.Write(true); + m_Stream.Write(book.Writable && from.InRange(book.GetWorldLocation(), 1)); + m_Stream.Write((ushort)book.PagesCount); + + m_Stream.Write((ushort)(titleBuffer.Length + 1)); + m_Stream.Write(titleBuffer, 0, titleBuffer.Length); + m_Stream.Write((byte)0); // terminate + + m_Stream.Write((ushort)(authorBuffer.Length + 1)); + m_Stream.Write(authorBuffer, 0, authorBuffer.Length); + m_Stream.Write((byte)0); // terminate + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/BlueBook.cs b/Scripts/Items/Books/BlueBook.cs index 1bf2325c2..7e464f088 100644 --- a/Scripts/Items/Books/BlueBook.cs +++ b/Scripts/Items/Books/BlueBook.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class BlueBook : BaseBook - { + public class BlueBook : BaseBook + { + [Constructible] + public BlueBook() : base(0xFF2, 40, true) + { + } - [Constructible] - public BlueBook() : base( 0xFF2, 40, true ) - { - } + [Constructible] + public BlueBook(int pageCount, bool writable) : base(0xFF2, pageCount, writable) + { + } - [Constructible] - public BlueBook( int pageCount, bool writable ) : base( 0xFF2, pageCount, writable ) - { - } + [Constructible] + public BlueBook(string title, string author, int pageCount, bool writable) : base(0xFF2, title, author, pageCount, + writable) + { + } - [Constructible] - public BlueBook( string title, string author, int pageCount, bool writable ) : base( 0xFF2, title, author, pageCount, writable ) - { - } + // Intended for defined books only + public BlueBook(bool writable) : base(0xFF2, writable) + { + } - // Intended for defined books only - public BlueBook( bool writable ) : base( 0xFF2, writable ) - { - } + public BlueBook(Serial serial) : base(serial) + { + } - public BlueBook( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } - int version = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - } -} + writer.Write(0); // version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/BrownBook.cs b/Scripts/Items/Books/BrownBook.cs index 1e370e15d..f6900edf3 100644 --- a/Scripts/Items/Books/BrownBook.cs +++ b/Scripts/Items/Books/BrownBook.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class BrownBook : BaseBook - { - [Constructible] - public BrownBook() : base( 0xFEF ) - { - } + public class BrownBook : BaseBook + { + [Constructible] + public BrownBook() : base(0xFEF) + { + } - [Constructible] - public BrownBook( int pageCount, bool writable ) : base( 0xFEF, pageCount, writable ) - { - } + [Constructible] + public BrownBook(int pageCount, bool writable) : base(0xFEF, pageCount, writable) + { + } - [Constructible] - public BrownBook( string title, string author, int pageCount, bool writable ) : base( 0xFEF, title, author, pageCount, writable ) - { - } + [Constructible] + public BrownBook(string title, string author, int pageCount, bool writable) : base(0xFEF, title, author, pageCount, + writable) + { + } - // Intended for defined books only - public BrownBook( bool writable ) : base( 0xFEF, writable ) - { - } + // Intended for defined books only + public BrownBook(bool writable) : base(0xFEF, writable) + { + } - public BrownBook( Serial serial ) : base( serial ) - { - } + public BrownBook(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } - } + writer.Write(0); // version + } + } } \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/BlackthornWelcomeBook.cs b/Scripts/Items/Books/Defined/BlackthornWelcomeBook.cs index ba6b73c87..cfc163d41 100644 --- a/Scripts/Items/Books/Defined/BlackthornWelcomeBook.cs +++ b/Scripts/Items/Books/Defined/BlackthornWelcomeBook.cs @@ -1,294 +1,294 @@ namespace Server.Items { - public class BlackthornWelcomeBook : RedBook - { - public static readonly BookContent Content = new BookContent - ( - "A Welcome", "Lord Blackthorn", - new BookPageInfo - ( - " Greetings to you,", - "new member of the", - "Trusted.", - " You now read these", - "words because you", - "have been deemed", - "worthy to join the", - "ranks of" - ), - new BookPageInfo - ( - "Britannia's defenders.", - "Some will call you a", - "betrayer of mankind, I", - "say they are", - "misguided. I call you", - "a defender for Sosaria", - "needs saving from", - "itself." - ), - new BookPageInfo - ( - " The forces of order", - "once ruled our world.", - "Like a great", - "darkness over our", - "lives we lived under", - "the oppressive watch", - "of a king who", - "dictated our actions" - ), - new BookPageInfo - ( - "and passed judgment", - "on our character. He", - "suppressed our way of", - "life by denying our", - "freedom and the", - "ability to determine", - "who we are and what", - "we stand for. Even" - ), - new BookPageInfo - ( - "today in the absence", - "of this man we still", - "see the symbol of his", - "tyranny, we watch his", - "personal guards patrol", - "the cities to", - "intimidate us, and we", - "feel his laws like a" - ), - new BookPageInfo - ( - "vice on our lives.", - " You are here", - "because you choose to", - "be free. Like many", - "Britannians you have", - "felt the oppression of", - "one man's ideas", - "weighing down upon" - ), - new BookPageInfo - ( - "you like chains. You", - "have felt the embrace", - "of fear, wondering if", - "you face consequence", - "for simply having", - "ideas not in harmony", - "with those forced upon", - "you. You have seen" - ), - new BookPageInfo - ( - "men fight and die for", - "the principles of a", - "zealot and wondered,", - "'Who will fight for", - "my principles should", - "they be opposed?'", - "You tire of living", - "under the shadow of" - ), - new BookPageInfo - ( - "dreams that do not", - "belong to you. And", - "most of all, you have", - "wondered what you", - "can do to live free.", - " Your journey to", - "freedom begins here.", - " I, like you, once" - ), - new BookPageInfo - ( - "desired my freedom", - "from the limits placed", - "on me. I watched in", - "disgust as this world", - "became engrossed with", - "the preaching of", - "virtue and none of the", - "practice. I held my" - ), - new BookPageInfo - ( - "convictions in check,", - "fearful of the reaction", - "of men blinded by", - "belief. I forced", - "myself to bury the", - "very ideology that", - "made me an individual.", - "I was fortunate that" - ), - new BookPageInfo - ( - "a being of unique", - "power and", - "unimaginable", - "intelligence saw", - "through to the true", - "person I was, the", - "person I was meant to", - "be. Exodus found" - ), - new BookPageInfo - ( - "within me a man of", - "free will,", - "determination, and", - "incomprehension for", - "the plight of", - "oppression forced on so", - "many Britannians.", - " Exodus has also" - ), - new BookPageInfo - ( - "chosen you because of", - "the strength of your", - "character.", - " Many of the men", - "who were once my", - "peers look upon me", - "and see a betrayer of", - "humanity. They" - ), - new BookPageInfo - ( - "claim my newfound", - "form is unnatural and", - "wrong. Because they", - "see the unknown in", - "me, they show fear.", - "They disapprove of", - "my choices and in", - "their ignorance see" - ), - new BookPageInfo - ( - "evil. Yet I hide my", - "true self no longer", - "from these men. My", - "thoughts and my", - "personal morality have", - "been liberated in the", - "face of the oppression", - "that once consumed me." - ), - new BookPageInfo - ( - "Where they see a", - "man no longer human.", - "I see a man that has", - "not betrayed his", - "humanity but has been", - "freed from it. This", - "is the power that has", - "been granted to me by" - ), - new BookPageInfo - ( - "Exodus. I have been", - "given my freedom. I", - "have been released", - "from my fears.", - " Exodus will give", - "you the power to", - "conquer your fears as", - "well." - ), - new BookPageInfo - ( - " When your fear", - "of this world is gone,", - "then the world truly", - "belongs to you in a", - "way it never has", - "before. You, trusted", - "one, will soon be given", - "a gift. Your body," - ), - new BookPageInfo - ( - "like mine, will be", - "enlightened and raised", - "to a level no mortal", - "can know. The power", - "to control your own", - "destiny will belong to", - "you for the first time", - "in your life." - ), - new BookPageInfo - ( - " You will, at long", - "last, be cleansed of", - "fear.", - " Together, with the", - "power of Exodus", - "behind us, we shall", - "finally wage war on", - "the oppression that" - ), - new BookPageInfo - ( - "once held us back", - "from our full", - "potential. We shall", - "claim this world, and", - "reshape it in an image", - "of freedom for all of", - "us. Those who once", - "told you who you are" - ), - new BookPageInfo - ( - "and how you should", - "live will no longer be", - "able to stand in the", - "way of your free will.", - "Many say you will", - "be abandoning your", - "humanity but in truth,", - "you will be more than" - ), - new BookPageInfo - ( - "human.", - " You will be freed." - ) - ); + public class BlackthornWelcomeBook : RedBook + { + public static readonly BookContent Content = new BookContent + ( + "A Welcome", "Lord Blackthorn", + new BookPageInfo + ( + " Greetings to you,", + "new member of the", + "Trusted.", + " You now read these", + "words because you", + "have been deemed", + "worthy to join the", + "ranks of" + ), + new BookPageInfo + ( + "Britannia's defenders.", + "Some will call you a", + "betrayer of mankind, I", + "say they are", + "misguided. I call you", + "a defender for Sosaria", + "needs saving from", + "itself." + ), + new BookPageInfo + ( + " The forces of order", + "once ruled our world.", + "Like a great", + "darkness over our", + "lives we lived under", + "the oppressive watch", + "of a king who", + "dictated our actions" + ), + new BookPageInfo + ( + "and passed judgment", + "on our character. He", + "suppressed our way of", + "life by denying our", + "freedom and the", + "ability to determine", + "who we are and what", + "we stand for. Even" + ), + new BookPageInfo + ( + "today in the absence", + "of this man we still", + "see the symbol of his", + "tyranny, we watch his", + "personal guards patrol", + "the cities to", + "intimidate us, and we", + "feel his laws like a" + ), + new BookPageInfo + ( + "vice on our lives.", + " You are here", + "because you choose to", + "be free. Like many", + "Britannians you have", + "felt the oppression of", + "one man's ideas", + "weighing down upon" + ), + new BookPageInfo + ( + "you like chains. You", + "have felt the embrace", + "of fear, wondering if", + "you face consequence", + "for simply having", + "ideas not in harmony", + "with those forced upon", + "you. You have seen" + ), + new BookPageInfo + ( + "men fight and die for", + "the principles of a", + "zealot and wondered,", + "'Who will fight for", + "my principles should", + "they be opposed?'", + "You tire of living", + "under the shadow of" + ), + new BookPageInfo + ( + "dreams that do not", + "belong to you. And", + "most of all, you have", + "wondered what you", + "can do to live free.", + " Your journey to", + "freedom begins here.", + " I, like you, once" + ), + new BookPageInfo + ( + "desired my freedom", + "from the limits placed", + "on me. I watched in", + "disgust as this world", + "became engrossed with", + "the preaching of", + "virtue and none of the", + "practice. I held my" + ), + new BookPageInfo + ( + "convictions in check,", + "fearful of the reaction", + "of men blinded by", + "belief. I forced", + "myself to bury the", + "very ideology that", + "made me an individual.", + "I was fortunate that" + ), + new BookPageInfo + ( + "a being of unique", + "power and", + "unimaginable", + "intelligence saw", + "through to the true", + "person I was, the", + "person I was meant to", + "be. Exodus found" + ), + new BookPageInfo + ( + "within me a man of", + "free will,", + "determination, and", + "incomprehension for", + "the plight of", + "oppression forced on so", + "many Britannians.", + " Exodus has also" + ), + new BookPageInfo + ( + "chosen you because of", + "the strength of your", + "character.", + " Many of the men", + "who were once my", + "peers look upon me", + "and see a betrayer of", + "humanity. They" + ), + new BookPageInfo + ( + "claim my newfound", + "form is unnatural and", + "wrong. Because they", + "see the unknown in", + "me, they show fear.", + "They disapprove of", + "my choices and in", + "their ignorance see" + ), + new BookPageInfo + ( + "evil. Yet I hide my", + "true self no longer", + "from these men. My", + "thoughts and my", + "personal morality have", + "been liberated in the", + "face of the oppression", + "that once consumed me." + ), + new BookPageInfo + ( + "Where they see a", + "man no longer human.", + "I see a man that has", + "not betrayed his", + "humanity but has been", + "freed from it. This", + "is the power that has", + "been granted to me by" + ), + new BookPageInfo + ( + "Exodus. I have been", + "given my freedom. I", + "have been released", + "from my fears.", + " Exodus will give", + "you the power to", + "conquer your fears as", + "well." + ), + new BookPageInfo + ( + " When your fear", + "of this world is gone,", + "then the world truly", + "belongs to you in a", + "way it never has", + "before. You, trusted", + "one, will soon be given", + "a gift. Your body," + ), + new BookPageInfo + ( + "like mine, will be", + "enlightened and raised", + "to a level no mortal", + "can know. The power", + "to control your own", + "destiny will belong to", + "you for the first time", + "in your life." + ), + new BookPageInfo + ( + " You will, at long", + "last, be cleansed of", + "fear.", + " Together, with the", + "power of Exodus", + "behind us, we shall", + "finally wage war on", + "the oppression that" + ), + new BookPageInfo + ( + "once held us back", + "from our full", + "potential. We shall", + "claim this world, and", + "reshape it in an image", + "of freedom for all of", + "us. Those who once", + "told you who you are" + ), + new BookPageInfo + ( + "and how you should", + "live will no longer be", + "able to stand in the", + "way of your free will.", + "Many say you will", + "be abandoning your", + "humanity but in truth,", + "you will be more than" + ), + new BookPageInfo + ( + "human.", + " You will be freed." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public BlackthornWelcomeBook() : base(false) + { + Hue = 0x89B; + } - [Constructible] - public BlackthornWelcomeBook() : base( false ) - { - Hue = 0x89B; - } + public BlackthornWelcomeBook(Serial serial) : base(serial) + { + } - public BlackthornWelcomeBook( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/BookContent.cs b/Scripts/Items/Books/Defined/BookContent.cs index 4e5d33da8..7f5e865e6 100644 --- a/Scripts/Items/Books/Defined/BookContent.cs +++ b/Scripts/Items/Books/Defined/BookContent.cs @@ -1,56 +1,49 @@ namespace Server.Items { - public class BookContent - { - public string Title { get; } + public class BookContent + { + public BookContent(string title, string author, params BookPageInfo[] pages) + { + Title = title; + Author = author; + Pages = pages; + } - public string Author { get; } + public string Title{ get; } - public BookPageInfo[] Pages { get; } + public string Author{ get; } - public BookContent( string title, string author, params BookPageInfo[] pages ) - { - Title = title; - Author = author; - Pages = pages; - } + public BookPageInfo[] Pages{ get; } - public BookPageInfo[] Copy() - { - BookPageInfo[] copy = new BookPageInfo[Pages.Length]; + public BookPageInfo[] Copy() + { + BookPageInfo[] copy = new BookPageInfo[Pages.Length]; - for ( int i = 0; i < copy.Length; ++i ) - copy[i] = new BookPageInfo( Pages[i].Lines ); + for (int i = 0; i < copy.Length; ++i) + copy[i] = new BookPageInfo(Pages[i].Lines); - return copy; - } + return copy; + } - public bool IsMatch( BookPageInfo[] cmp ) - { - if ( cmp.Length != Pages.Length ) - return false; + public bool IsMatch(BookPageInfo[] cmp) + { + if (cmp.Length != Pages.Length) + return false; - for ( int i = 0; i < cmp.Length; ++i ) - { - string[] a = Pages[i].Lines; - string[] b = cmp[i].Lines; + for (int i = 0; i < cmp.Length; ++i) + { + string[] a = Pages[i].Lines; + string[] b = cmp[i].Lines; - if ( a.Length != b.Length ) - { - return false; - } + if (a.Length != b.Length) return false; - if ( a != b ) - { - for ( int j = 0; j < a.Length; ++j ) - { - if ( a[j] != b[j] ) - return false; - } - } - } + if (a != b) + for (int j = 0; j < a.Length; ++j) + if (a[j] != b[j]) + return false; + } - return true; - } - } + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/DrakovsJournal.cs b/Scripts/Items/Books/Defined/DrakovsJournal.cs index 7742509a0..f7b2177d5 100644 --- a/Scripts/Items/Books/Defined/DrakovsJournal.cs +++ b/Scripts/Items/Books/Defined/DrakovsJournal.cs @@ -1,126 +1,126 @@ namespace Server.Items { - public class DrakovsJournal : BlueBook - { - public static readonly BookContent Content = new BookContent - ( - "Drakov's Journal", "Drakov", - new BookPageInfo - ( - "My Master", - "", - "This journal was", - "found on one of", - "our controllers. It", - "seems he has lost", - "faith in you. Know", - "that he has been" - ), - new BookPageInfo - ( - "dealth with and will", - "never again speak", - "ill of you or our", - "cause.", - " -Galzon" - ), - new BookPageInfo - ( - "We have completted", - "construction of the", - "devices needed to", - "build the clockwork", - "overseers and minions", - "as per the request of", - "the Master. The", - "gargoyles have been" - ), - new BookPageInfo - ( - "most useful and their", - "knowledge of the", - "techniques for the", - "construction of these", - "creatures will serve", - "us well.", - " -----", - "I am not one to" - ), - new BookPageInfo - ( - "criticize the Master,", - "but I believe he may", - "have erred in his", - "decision to destroy", - "the wingless ones.", - "Already our forces", - "are weakened by the", - "constant attacks of" - ), - new BookPageInfo - ( - "the humans Their", - "strength and", - "unquestioning", - "compliance would", - "have made them very", - "useful in the fight", - "against the humans.", - "But the Master felt" - ), - new BookPageInfo - ( - "their presence to be", - "an annoyance and", - "a distraction to the", - "winged ones. It was", - "not difficult at all", - "to remove them from", - "this world. But now", - "I fear without more" - ), - new BookPageInfo - ( - "allies, willing or", - "not, we stand", - "little chance of", - "defeating the foul", - "humans from our", - "lands. Perhaps if", - "the Master had", - "shown a little" - ), - new BookPageInfo - ( - "mercy and forsight", - "we would not be", - "in such dire peril." - ) - ); + public class DrakovsJournal : BlueBook + { + public static readonly BookContent Content = new BookContent + ( + "Drakov's Journal", "Drakov", + new BookPageInfo + ( + "My Master", + "", + "This journal was", + "found on one of", + "our controllers. It", + "seems he has lost", + "faith in you. Know", + "that he has been" + ), + new BookPageInfo + ( + "dealth with and will", + "never again speak", + "ill of you or our", + "cause.", + " -Galzon" + ), + new BookPageInfo + ( + "We have completted", + "construction of the", + "devices needed to", + "build the clockwork", + "overseers and minions", + "as per the request of", + "the Master. The", + "gargoyles have been" + ), + new BookPageInfo + ( + "most useful and their", + "knowledge of the", + "techniques for the", + "construction of these", + "creatures will serve", + "us well.", + " -----", + "I am not one to" + ), + new BookPageInfo + ( + "criticize the Master,", + "but I believe he may", + "have erred in his", + "decision to destroy", + "the wingless ones.", + "Already our forces", + "are weakened by the", + "constant attacks of" + ), + new BookPageInfo + ( + "the humans Their", + "strength and", + "unquestioning", + "compliance would", + "have made them very", + "useful in the fight", + "against the humans.", + "But the Master felt" + ), + new BookPageInfo + ( + "their presence to be", + "an annoyance and", + "a distraction to the", + "winged ones. It was", + "not difficult at all", + "to remove them from", + "this world. But now", + "I fear without more" + ), + new BookPageInfo + ( + "allies, willing or", + "not, we stand", + "little chance of", + "defeating the foul", + "humans from our", + "lands. Perhaps if", + "the Master had", + "shown a little" + ), + new BookPageInfo + ( + "mercy and forsight", + "we would not be", + "in such dire peril." + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public DrakovsJournal() : base(false) + { + } - [Constructible] - public DrakovsJournal() : base( false ) - { - } + public DrakovsJournal(Serial serial) : base(serial) + { + } - public DrakovsJournal( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/FropozJournal.cs b/Scripts/Items/Books/Defined/FropozJournal.cs index 88b2a5dec..1c6f6e05b 100644 --- a/Scripts/Items/Books/Defined/FropozJournal.cs +++ b/Scripts/Items/Books/Defined/FropozJournal.cs @@ -1,179 +1,179 @@ namespace Server.Items { - public class FropozJournal : RedBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal", "Fropoz", - new BookPageInfo - ( - "I have done as my", - "Master has", - "instructed me.", - "", - "The painted humans", - "have been driven into", - "Britannia and are even", - "now wreaking havoc" - ), - new BookPageInfo - ( - "across the land,", - "providing us with the", - "distraction my Master", - "requested. We", - "have provided them", - "with the masks", - "necessary to defeat", - "the orcs, thus" - ), - new BookPageInfo - ( - "causing even more", - "distress for the people", - "of Britannia. The", - "unsuspecting fools", - "are too busy dealing", - "with the orc hordes to", - "continue their", - "exploration of our" - ), - new BookPageInfo - ( - "lands. We are", - "safe...for now.", - " ----", - "The attacks", - "continue exactly as", - "planned. My Master", - "is pleased with my", - "work and we are" - ), - new BookPageInfo - ( - "closer to our goals than", - "ever before. The", - "gargoyles have proven", - "to be more troublesome", - "than we first", - "anticipated, but I", - "believe we can", - "subjugate them fully" - ), - new BookPageInfo - ( - "given enough time. It's", - "unfortunate that we", - "did not discover their", - "knowledge sooner.", - "Even now they", - "prepare our armies", - "for battle, but not", - "without resistance." - ), - new BookPageInfo - ( - "Now that some of", - "them know of the", - "other lands and of", - "humans, they will", - "double their efforts to", - "seek help. This", - "cannot be allowed.", - " -----" - ), - new BookPageInfo - ( - "Damn them!! The", - "humans proved", - "more resourcefull than", - "we thought them", - "capable of. Already", - "their homes are free", - "of orcs and savages", - "and they once again" - ), - new BookPageInfo - ( - "are treading in our", - "lands. We may have to", - "move sooner than we", - "thought. I will", - "prepar my brethern", - "and our golems.", - "Hopefully, we can", - "buy our Master some" - ), - new BookPageInfo - ( - "more time before the", - "humans discover us.", - " -----", - "It's too late. The", - "gargoyles whom have", - "evaded our capture", - "have opened the doors", - "to our land." - ), - new BookPageInfo - ( - "They pray the", - "humans will help", - "them, despite the", - "actions of their", - "cousins in Britannia. I", - "fear they are right.", - "I must go to warn", - "the MastKai Hohiro," - ), - new BookPageInfo - ( - ), - new BookPageInfo - ( - "10.11.2001", - "first one to be here", - "", - "Congrats. I didn't really", - "care to log on earlier,", - "nor did I come straight", - "here. 2pm, Magus" - ) - ); + public class FropozJournal : RedBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal", "Fropoz", + new BookPageInfo + ( + "I have done as my", + "Master has", + "instructed me.", + "", + "The painted humans", + "have been driven into", + "Britannia and are even", + "now wreaking havoc" + ), + new BookPageInfo + ( + "across the land,", + "providing us with the", + "distraction my Master", + "requested. We", + "have provided them", + "with the masks", + "necessary to defeat", + "the orcs, thus" + ), + new BookPageInfo + ( + "causing even more", + "distress for the people", + "of Britannia. The", + "unsuspecting fools", + "are too busy dealing", + "with the orc hordes to", + "continue their", + "exploration of our" + ), + new BookPageInfo + ( + "lands. We are", + "safe...for now.", + " ----", + "The attacks", + "continue exactly as", + "planned. My Master", + "is pleased with my", + "work and we are" + ), + new BookPageInfo + ( + "closer to our goals than", + "ever before. The", + "gargoyles have proven", + "to be more troublesome", + "than we first", + "anticipated, but I", + "believe we can", + "subjugate them fully" + ), + new BookPageInfo + ( + "given enough time. It's", + "unfortunate that we", + "did not discover their", + "knowledge sooner.", + "Even now they", + "prepare our armies", + "for battle, but not", + "without resistance." + ), + new BookPageInfo + ( + "Now that some of", + "them know of the", + "other lands and of", + "humans, they will", + "double their efforts to", + "seek help. This", + "cannot be allowed.", + " -----" + ), + new BookPageInfo + ( + "Damn them!! The", + "humans proved", + "more resourcefull than", + "we thought them", + "capable of. Already", + "their homes are free", + "of orcs and savages", + "and they once again" + ), + new BookPageInfo + ( + "are treading in our", + "lands. We may have to", + "move sooner than we", + "thought. I will", + "prepar my brethern", + "and our golems.", + "Hopefully, we can", + "buy our Master some" + ), + new BookPageInfo + ( + "more time before the", + "humans discover us.", + " -----", + "It's too late. The", + "gargoyles whom have", + "evaded our capture", + "have opened the doors", + "to our land." + ), + new BookPageInfo + ( + "They pray the", + "humans will help", + "them, despite the", + "actions of their", + "cousins in Britannia. I", + "fear they are right.", + "I must go to warn", + "the MastKai Hohiro," + ), + new BookPageInfo + ( + ), + new BookPageInfo + ( + "10.11.2001", + "first one to be here", + "", + "Congrats. I didn't really", + "care to log on earlier,", + "nor did I come straight", + "here. 2pm, Magus" + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public FropozJournal() : base(false) + { + } - [Constructible] - public FropozJournal() : base( false ) - { - } + public FropozJournal(Serial serial) : base(serial) + { + } - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( "Fropoz's Journal" ); - } + public override BookContent DefaultContent => Content; - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, "Fropoz's Journal" ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add("Fropoz's Journal"); + } - public FropozJournal( Serial serial ) : base( serial ) - { - } + public override void OnSingleClick(Mobile from) + { + LabelTo(from, "Fropoz's Journal"); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/KaburJournal.cs b/Scripts/Items/Books/Defined/KaburJournal.cs index 125ffc340..1eba97ead 100644 --- a/Scripts/Items/Books/Defined/KaburJournal.cs +++ b/Scripts/Items/Books/Defined/KaburJournal.cs @@ -1,264 +1,264 @@ namespace Server.Items { - public class KaburJournal : RedBook - { - public static readonly BookContent Content = new BookContent - ( - "Journal", "Kabur", - new BookPageInfo - ( - "The campaign to slaughter", - "the Meer goes well.", - "Although they seem to", - "oppose the forces of", - "ours at every turn, we", - "still defeat them in", - "combat. Spies of the", - "Meer have been found and" - ), - new BookPageInfo - ( - "slain outside of the", - "fortress of ours. The", - "fools underestimate us.", - "We have the power of", - "Lord Exodus behind us.", - "Soon they will learn to", - "serve the Juka and I", - "shall carry the head of" - ), - new BookPageInfo - ( - "the wench, Dasha, on a", - "spike for all the warriors", - "of ours to share triumph", - "under.", - "", - "One of the warriors of", - "the Juka died today.", - "During the training" - ), - new BookPageInfo - ( - "exercises of ours he", - "spoke out in favor of", - "the warriors of the", - "Meer, saying that they", - "were indeed powerful and", - "would provide a challenge", - "to the Juka. A Juka in", - "fear is no Juka. I gave" - ), - new BookPageInfo - ( - "him the death of a", - "coward, outside of battle.", - "", - "More spies of the Meer", - "have been found around", - "the fortress of ours.", - "Many have been seen and", - "escaped the wrath of the" - ), - new BookPageInfo - ( - "warriors of ours. Those", - "who have been captured", - "and tortured have", - "revealed nothing to us,", - "even when subjected to", - "the spells of the females.", - " I know the Meer must", - "have plans against us if" - ), - new BookPageInfo - ( - "they send so many spies.", - " I may send the troops", - "of the Juka to invade", - "the camps of theirs as a", - "warning.", - "", - "I have met Dasha in", - "battle this day. The" - ), - new BookPageInfo - ( - "efforts of hers to draw", - "me into a Black Duel", - "were foolish. Had we", - "not been interrupted in", - "the cave I would have", - "ended the life of hers", - "but I will have to wait", - "for another battle. Lord" - ), - new BookPageInfo - ( - "Exodus has ordered more", - "patrols around the", - "fortress of ours. If", - "Dasha is any indication,", - "the Meer will strike soon.", - "", - "More Meer stand outside", - "of the fortress of ours" - ), - new BookPageInfo - ( - "than I have ever seen at", - "once. They must seek", - "vengeance for the", - "destruction of their", - "forest. Many Juka stand", - "ready at the base of the", - "mountain to face the", - "forces of theirs but" - ), - new BookPageInfo - ( - "today may be the final", - "battle. Exodus has", - "summoned me, I must", - "prepare.", - "", - "Dusk has passed and the", - "Juka now live in a new", - "age, a later time. I have" - ), - new BookPageInfo - ( - "just returned from", - "exploring the new world", - "that surrounds the", - "fortress of the Juka.", - "During the attack of the", - "Meer the madman", - "Adranath tried to destroy", - "the fortress of ours" - ), - new BookPageInfo - ( - "with great magic. At", - "once he was still and", - "light surrounded the", - "fortress. Everything", - "faded from view. When I", - "regained the senses of", - "mine I saw no sign of", - "the Meer but Dasha." - ), - new BookPageInfo - ( - "She has not been found", - "since this new being,", - "Blackthorn, blasted her", - "from the top of the", - "fortress.", - "The forest was gone, now", - "replaced by grasslands.", - "In the far distance I" - ), - new BookPageInfo - ( - "could see humans that", - "had covered the bodies of", - "theirs in marks. Even", - "Gargoyles populate this", - "place. Exodus has", - "explained to me that the", - "Juka and the fortress of", - "ours have been pulled" - ), - new BookPageInfo - ( - "forward in time. The", - "world we knew is now", - "thousands of years in the", - "past. Lord Exodus say", - "he has has saved the", - "Juka from extinction. I", - "do not want to believe", - "him. I asked this" - ), - new BookPageInfo - ( - "stranger about the Meer,", - "but he tells me a new", - "enemy remains to be", - "destroyed. It seems the", - "enemies of ours have", - "passed away to dust like", - "the forest." - ), - new BookPageInfo - ( - "I have spoken with other", - "Juka and I suspect I have", - "been told the truth. All", - "the Juka had powerful", - "dreams. In the dreams", - "of ours the Meer invaded", - "the fortress of ours and", - "a great battle took place." - ), - new BookPageInfo - ( - " All the Juka and all the", - "Meer perished and the", - "fortress was destroyed", - "from Adranath's spells. I", - "would not like to believe", - "that the Meer could ever", - "destroy us, but now it", - "seems we have seen a" - ), - new BookPageInfo - ( - "vision of the fate of", - "ours now lost in time. I", - "must now wonder if the", - "Meer did not die in the", - "battle with the Juka, how", - "did they die? And more", - "importantly, where is", - "Dasha?" - ) - ); + public class KaburJournal : RedBook + { + public static readonly BookContent Content = new BookContent + ( + "Journal", "Kabur", + new BookPageInfo + ( + "The campaign to slaughter", + "the Meer goes well.", + "Although they seem to", + "oppose the forces of", + "ours at every turn, we", + "still defeat them in", + "combat. Spies of the", + "Meer have been found and" + ), + new BookPageInfo + ( + "slain outside of the", + "fortress of ours. The", + "fools underestimate us.", + "We have the power of", + "Lord Exodus behind us.", + "Soon they will learn to", + "serve the Juka and I", + "shall carry the head of" + ), + new BookPageInfo + ( + "the wench, Dasha, on a", + "spike for all the warriors", + "of ours to share triumph", + "under.", + "", + "One of the warriors of", + "the Juka died today.", + "During the training" + ), + new BookPageInfo + ( + "exercises of ours he", + "spoke out in favor of", + "the warriors of the", + "Meer, saying that they", + "were indeed powerful and", + "would provide a challenge", + "to the Juka. A Juka in", + "fear is no Juka. I gave" + ), + new BookPageInfo + ( + "him the death of a", + "coward, outside of battle.", + "", + "More spies of the Meer", + "have been found around", + "the fortress of ours.", + "Many have been seen and", + "escaped the wrath of the" + ), + new BookPageInfo + ( + "warriors of ours. Those", + "who have been captured", + "and tortured have", + "revealed nothing to us,", + "even when subjected to", + "the spells of the females.", + " I know the Meer must", + "have plans against us if" + ), + new BookPageInfo + ( + "they send so many spies.", + " I may send the troops", + "of the Juka to invade", + "the camps of theirs as a", + "warning.", + "", + "I have met Dasha in", + "battle this day. The" + ), + new BookPageInfo + ( + "efforts of hers to draw", + "me into a Black Duel", + "were foolish. Had we", + "not been interrupted in", + "the cave I would have", + "ended the life of hers", + "but I will have to wait", + "for another battle. Lord" + ), + new BookPageInfo + ( + "Exodus has ordered more", + "patrols around the", + "fortress of ours. If", + "Dasha is any indication,", + "the Meer will strike soon.", + "", + "More Meer stand outside", + "of the fortress of ours" + ), + new BookPageInfo + ( + "than I have ever seen at", + "once. They must seek", + "vengeance for the", + "destruction of their", + "forest. Many Juka stand", + "ready at the base of the", + "mountain to face the", + "forces of theirs but" + ), + new BookPageInfo + ( + "today may be the final", + "battle. Exodus has", + "summoned me, I must", + "prepare.", + "", + "Dusk has passed and the", + "Juka now live in a new", + "age, a later time. I have" + ), + new BookPageInfo + ( + "just returned from", + "exploring the new world", + "that surrounds the", + "fortress of the Juka.", + "During the attack of the", + "Meer the madman", + "Adranath tried to destroy", + "the fortress of ours" + ), + new BookPageInfo + ( + "with great magic. At", + "once he was still and", + "light surrounded the", + "fortress. Everything", + "faded from view. When I", + "regained the senses of", + "mine I saw no sign of", + "the Meer but Dasha." + ), + new BookPageInfo + ( + "She has not been found", + "since this new being,", + "Blackthorn, blasted her", + "from the top of the", + "fortress.", + "The forest was gone, now", + "replaced by grasslands.", + "In the far distance I" + ), + new BookPageInfo + ( + "could see humans that", + "had covered the bodies of", + "theirs in marks. Even", + "Gargoyles populate this", + "place. Exodus has", + "explained to me that the", + "Juka and the fortress of", + "ours have been pulled" + ), + new BookPageInfo + ( + "forward in time. The", + "world we knew is now", + "thousands of years in the", + "past. Lord Exodus say", + "he has has saved the", + "Juka from extinction. I", + "do not want to believe", + "him. I asked this" + ), + new BookPageInfo + ( + "stranger about the Meer,", + "but he tells me a new", + "enemy remains to be", + "destroyed. It seems the", + "enemies of ours have", + "passed away to dust like", + "the forest." + ), + new BookPageInfo + ( + "I have spoken with other", + "Juka and I suspect I have", + "been told the truth. All", + "the Juka had powerful", + "dreams. In the dreams", + "of ours the Meer invaded", + "the fortress of ours and", + "a great battle took place." + ), + new BookPageInfo + ( + " All the Juka and all the", + "Meer perished and the", + "fortress was destroyed", + "from Adranath's spells. I", + "would not like to believe", + "that the Meer could ever", + "destroy us, but now it", + "seems we have seen a" + ), + new BookPageInfo + ( + "vision of the fate of", + "ours now lost in time. I", + "must now wonder if the", + "Meer did not die in the", + "battle with the Juka, how", + "did they die? And more", + "importantly, where is", + "Dasha?" + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public KaburJournal() : base(false) + { + } - [Constructible] - public KaburJournal() : base( false ) - { - } + public KaburJournal(Serial serial) : base(serial) + { + } - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( "Khabur's Journal" ); - } + public override BookContent DefaultContent => Content; - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, "Khabur's Journal" ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add("Khabur's Journal"); + } - public KaburJournal( Serial serial ) : base( serial ) - { - } + public override void OnSingleClick(Mobile from) + { + LabelTo(from, "Khabur's Journal"); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/LibraryBooks.cs b/Scripts/Items/Books/Defined/LibraryBooks.cs index 8dbf0e795..c1888c6a4 100644 --- a/Scripts/Items/Books/Defined/LibraryBooks.cs +++ b/Scripts/Items/Books/Defined/LibraryBooks.cs @@ -1,6208 +1,6264 @@ namespace Server.Items { - #region A Grammar of Orcish - public class GrammarOfOrcish : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "A Grammar of Orcish", "Yorick of Yew", - new BookPageInfo - ( - "This volume, and", - "others in the series,", - "are sponsored by", - "donations from Lord", - "Blackthorn, ever a", - "supporter of", - "understanding the", - "other sentient races" - ), - new BookPageInfo - ( - "of Britannia.", - "-", - "", - " The Orcish tongue", - "may fall unpleasingly", - "'pon the ear, yet it", - "has within it a", - "complex grammar oft" - ), - new BookPageInfo - ( - "misunderstood by", - "those who merely", - "hear the few broken", - "words of English our", - "orcish brothers", - "manage without", - "education.", - " These are the basic" - ), - new BookPageInfo - ( - "rules of orcish:", - " Orcish has five", - "tenses: present, past,", - "future imperfect,", - "present interjectional,", - "and prehensile.", - " Examples: gugroflu,", - "gugrofloog, gugrobo," - ), - new BookPageInfo - ( - "gugroglu!, gugrogug.", - " All transitive verbs", - "in the prehensile", - "tense end in \"ug.\"", - " Examples:", - "urgleighug,", - "biggugdaghgug,", - "curdakalmug." - ), - new BookPageInfo - ( - " All present", - "interjectional", - "conjugations start", - "with the letter G", - "unless the contain the", - "third declensive", - "accent of the letter U.", - " Examples:" - ), - new BookPageInfo - ( - "ghothudunglug, but not", - "azhbuugub.", - " The past tense can", - "only refer to events", - "since the last meal,", - "but the prehensile", - "tense can refer to", - "any event within" - ), - new BookPageInfo - ( - "reach.", - " The present tense", - "is conjugated like the", - "future imperfect", - "tense, when the", - "interrogative mode is", - "used by pitching the", - "sound a quarter-tone" - ), - new BookPageInfo - ( - "higher.", - "Orcish hath no", - "concept of person, as", - "in first person, third", - "person, I, we, etc.", - " Orcish grammar", - "relies upon the three", - "cardinal rules of" - ), - new BookPageInfo - ( - "accretion, prefixing,", - "and agglutination, in", - "addition to pitch. In", - "the former, phonemes", - "combine into larger", - "words which may", - "contain full phrasal", - "significance. In the" - ), - new BookPageInfo - ( - "second, prefixing", - "specific phonetic", - "sounds changes the", - "subject of the", - "sentence into object,", - "interrogative,", - "addressed individual,", - "or dinner." - ), - new BookPageInfo - ( - " Agglutination occurs", - "whenever four of the", - "same letter are", - "present in a word, in", - "which case, any two", - "of them may be", - "removed or slurred.", - " Pitch changes the" - ), - new BookPageInfo - ( - "phoneme value of", - "individual syllables,", - "thus completely", - "altering what a word", - "may mean. The", - "classic example is", - "\"Aktgluthugrot", - "bigglogubuu" - ), - new BookPageInfo - ( - "dargilgaglug lublublub\"", - "which can mean \"You", - "are such a pretty", - "girl,\" \"My mother ate", - "your primroses,\" or", - "\"Jellyfish nose paints", - "alms potato,\"", - "depending on pitch." - ), - new BookPageInfo - ( - " Orcish poetry often", - "relies upon repeating", - "the same phrase in", - "multiple pitches, even", - "changing pitch", - "midword. None of", - "this great art is", - "translatable." - ), - new BookPageInfo - ( - " The orcish language", - "uses the following", - "vowels: ab, ad, ag, akt,", - "at, augh, auh, azh, e,", - "i, o, oo, u, uu. The", - "vowel sound a is not", - "recognized as a vowel", - "and does not exist in" - ), - new BookPageInfo - ( - "their alphabet.", - "The orcish alphabet is", - "best learned using the", - "classic rhyme", - "repeated at 23", - "different pitches:", - " Lugnog ghu blat", - "suggaroglug," - ), - new BookPageInfo - ( - "Gaghbuu dakdar ab", - "highugbo,", - " Gothnogbuim ad", - "gilgubbugbuilug", - "Bilgeaugh thurggulg", - "stuiggro!", - "", - "A translation of the" - ), - new BookPageInfo - ( - "first pitch:", - "Eat food, the first", - "letter is ab,", - "Kill people, next letter", - "is ad,", - "I forget the rest", - "But augh is in there", - "somewhere!" - ), - new BookPageInfo - ( - "", - " What follows is a", - "complete phonetic", - "library of the orcish", - "language:", - "ab, ad, ag, akt, alm,", - "at, augh, auh, azh,", - "ba, ba, bag, bar, baz," - ), - new BookPageInfo - ( - "bid, bilge, bo, bog, bog,", - "brui, bu, buad, bug,", - "bug, buil, buim, bum,", - "buo, buor, buu, ca,", - "car, clog, cro, cuk,", - "cur, da, dagh, dagh,", - "dak, dar, deak, der,", - "dil, dit, dor, dre, dri," - ), - new BookPageInfo - ( - "dru, du, dud, duf,", - "dug, dug, duh, dun,", - "eag, eg, egg, eichel,", - "ek, ep, ewk, faugh,", - "fid, flu, fog, foo,", - "foz, fruk, fu, fub,", - "fud, fun, fup, fur,", - "gaa, gag, gagh, gan," - ), - new BookPageInfo - ( - "gar, gh, gha, ghat,", - "ghed, ghig, gho, ghu,", - "gig, gil, gka, glu, glu,", - "glug, gna, gno, gnu,", - "gol, gom, goth, grunt,", - "grut, gu, gub, gub,", - "gug, gug, gugh, guk,", - "guk," - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GrammarOfOrcish() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public GrammarOfOrcish( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region A Politic Call to Anarchy - public class CallToAnarchy : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "A Politic Call to Anarchy", "Lord Blackthorn", - new BookPageInfo - ( - " Let it never be said", - "that I have aught as", - "quarrel with my liege", - "Lord British, for", - "indeed we be of the", - "best of friends,", - "sharing amicable", - "games of chess 'pon a" - ), - new BookPageInfo - ( - "winter's night, and", - "talking at length into", - "the wee hours of the", - "issues that affect the", - "realm of Britannia.", - " Yet true friendship", - "doth not prevent true", - "philosophical" - ), - new BookPageInfo - ( - "disagreement either.", - "While I view with", - "approval my lord's", - "affection for his", - "carefully crafted", - "philosophy of the", - "Eight Virtues,", - "wherein moral" - ), - new BookPageInfo - ( - "behavior is", - "encouraged in the", - "populace, I view with", - "less approval the", - "expenditure of public", - "funds upon the", - "construction of", - "\"shrines\" to said" - ), - new BookPageInfo - ( - "ideals.", - " The issue is not one", - "of funds, however,", - "but a disagreement", - "most intellectual over", - "the proper way of", - "humankind in an", - "ethical sense. Surely" - ), - new BookPageInfo - ( - "freedom of decision", - "must be regarded as", - "paramount in any", - "such moral decision?", - "Though none fail to", - "censure the", - "murderer, a subtler", - "question arises when" - ), - new BookPageInfo - ( - "we ask if his", - "behavior would be", - "ethical if he were", - "forced to it.", - " I say to thee, the", - "reader, quite flatly,", - "that no ethical system", - "shall have sway over" - ), - new BookPageInfo - ( - "me unless it", - "convinceth me, for", - "that freely made", - "choice is to me the", - "sign that the system", - "hath validity.", - " Whereas the system", - "of \"Virtues\" that my" - ), - new BookPageInfo - ( - "liege espouses is", - "indeed a compilation", - "of commonly approved", - "virtues, I approve of", - "it. Where it seeks to", - "control the populace", - "and restrict their", - "diversity and their" - ), - new BookPageInfo - ( - "range of behaviors, I", - "quarrel with it. And", - "thus do I issue this", - "politic call to anarchy,", - "whilst humbly", - "begging forgiveness", - "of Lord British for", - "my impertinence:" - ), - new BookPageInfo - ( - " Celebrate thy", - "differences. Take", - "thy actions according", - "to thy own lights.", - "Question from what", - "source a law, a rule,", - "a judge, and a virtue", - "may arise. 'Twere" - ), - new BookPageInfo - ( - "possible (though I", - "suggest it not", - "seriously) that a", - "daemon planted the", - "seed of these", - "\"Virtues\" in my Lord", - "British's mind; 'twere", - "possible that the" - ), - new BookPageInfo - ( - "Shrines were but a", - "plan to destroy this", - "world. Thou canst not", - "know unless thou", - "questioneth, doubteth,", - "and in the end,", - "unless thou relyest", - "upon THYSELF and" - ), - new BookPageInfo - ( - "thy judgement.", - " I offer these words", - "as mere philosophical", - "musings for those", - "who seek", - "enlightenment, for", - "'tis the issue that", - "hath occupied mine" - ), - new BookPageInfo - ( - "interest and that of", - "Lord British for", - "some time now." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public CallToAnarchy() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public CallToAnarchy( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region A Primer on Arms and Weapons - public class ArmsAndWeaponsPrimer : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "A Primer on Arms and Weapons", "Martin", - new BookPageInfo - ( - " These are the", - "basic elements to", - "consider in assessing", - "a weapon, of which", - "all warriors who", - "regard themselves as", - "more than mere", - "mercenaries should be" - ), - new BookPageInfo - ( - "aware.", - " First and most", - "obvious is the amount", - "of damage that the", - "weapon may do", - "against unprotected", - "flesh. While 'tis this", - "which first attracts" - ), - new BookPageInfo - ( - "the attention of the", - "novice, 'tis a deadly", - "mistake to regard it", - "as the sole value of a", - "weapon. While it may", - "prove devastating", - "indeed as a means of", - "causing damage, a" - ), - new BookPageInfo - ( - "weapon must also", - "serve as stout shield", - "when engaged in", - "combat.", - " Hence the second", - "issue to which to pay", - "attention is the", - "amount of protection" - ), - new BookPageInfo - ( - "that a weapon may", - "offer. Pay close", - "attention to the guard", - "on it, if it be a blade,", - "or the stoutness of", - "its wood if it is a pole", - "arm.", - " Oft related to this" - ), - new BookPageInfo - ( - "is the weight of the", - "weapon, for a heavy", - "weapon is more", - "difficult to maneuver", - "to block with, though", - "it may do more", - "damage to thy", - "opponent." - ), - new BookPageInfo - ( - " If a weapon is too", - "heavy for the wielder", - "to move it freely,", - "they should choose", - "another and not", - "attempt to prove their", - "prowess by the size", - "of their sword." - ), - new BookPageInfo - ( - " The reach of a", - "weapon both increases", - "its defensive ability,", - "and renders it more", - "useful in open spaces", - "as it allows attack", - "against the opponent", - "without the need to" - ), - new BookPageInfo - ( - "close. But be aware of", - "the limitations of thy", - "weapon! For a", - "weapon with great", - "reach may be useless", - "in close quarters, for", - "lack of space to", - "maneuver it. Should" - ), - new BookPageInfo - ( - "that dagger-wielding", - "enemy close on thee", - "and thy halberd, 'tis", - "best to flee.", - " Lastly, a factor", - "that must always be", - "considered is the", - "condition of the" - ), - new BookPageInfo - ( - "weapon. It might be a", - "wondrous magical", - "blade of surpassing", - "sharpness and it may", - "leap to block blows", - "with a mind of its", - "own. It also might be", - "of such flimsy" - ), - new BookPageInfo - ( - "construction, or", - "damaged to such an", - "extent, that the first", - "time it clangs against", - "steel, 'twill shatter", - "into useless shards.", - " Seek ye a good", - "blacksmith should thy" - ), - new BookPageInfo - ( - "weapon become", - "damaged, but be", - "aware that their", - "ministrations may", - "simply make the", - "matter worse.", - " While mages of", - "some ability oft create" - ), - new BookPageInfo - ( - "magical weapons", - "which enhance skill,", - "are preternaturally", - "sharp, or incinerate", - "the enemy as they", - "fall, to my mind the", - "greatest gift that they", - "can grant a stout" - ), - new BookPageInfo - ( - "sword is to make it", - "resistant to damage,", - "for thy own skill can", - "make up the", - "difference. Except", - "for the fireball, but", - "if the corpse is", - "charred, then so will" - ), - new BookPageInfo - ( - "be the possessions,", - "which maketh looting", - "difficult!" - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public ArmsAndWeaponsPrimer() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public ArmsAndWeaponsPrimer( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region A Song of Samlethe - public class SongOfSamlethe : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "A Song of Samlethe", "Sandra", - new BookPageInfo - ( - "The first bear did", - "swim by day,", - "And it did sleep by", - "night.", - "It kept itself within", - "its cave", - "and ate by starry", - "light." - ), - new BookPageInfo - ( - "", - "The second bear it did", - "cavort", - "'Neath canopies of", - "trees,", - "And danced its", - "strange bearish sort", - "Of joy for all to see." - ), - new BookPageInfo - ( - "", - "The first bear, well,", - "'twas hunted,", - "And today adorns a", - "floor.", - "Its ruggish face has", - "been dented", - "By footfalls and the" - ), - new BookPageInfo - ( - "door.", - "", - "The second bear did", - "step once", - "Into a mushroom ring,", - "And now does dance", - "the dunce", - "For wisps and" - ), - new BookPageInfo - ( - "unseen things.", - "", - "So do not dance, and", - "do not sleep,", - "Or else be led astray!", - "For bears all end up", - "six feet deep", - "At the end of" - ), - new BookPageInfo - ( - "Samlethe's day." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public SongOfSamlethe() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public SongOfSamlethe( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region A Tale of Three Tribes - public class TaleOfThreeTribes : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "A Tale of Three Tribes", "Janet, Scribe", - new BookPageInfo - ( - " The dungeon known", - "as Despise is in fact", - "not a dungeon as", - "such, but rather a", - "large natural cave.", - "Inhospitable and", - "unfriendly to", - "visitors, it is filled" - ), - new BookPageInfo - ( - "with damp spots", - "where the deadly", - "Exploding Red Spotted", - "Toadstool grows in", - "abundance.", - " According to the", - "oldest of historical", - "texts, in days gone" - ), - new BookPageInfo - ( - "by the cave was once", - "the home of three", - "separate tribes who", - "had come to an", - "accommodation with", - "each other. Oddly", - "enough, the three", - "tribes were of" - ), - new BookPageInfo - ( - "dragons, lizard men,", - "and rat men. While", - "today few except", - "extremists associated", - "with Lord Blackthorn", - "regard these latter", - "two as being", - "intelligent beings," - ), - new BookPageInfo - ( - "apparently they have", - "indeed fallen from a", - "more evolved state", - "over the years.", - " 'Tis said that these", - "three races did dwell", - "in relative harmony", - "within the vast cave," - ), - new BookPageInfo - ( - "building when they", - "required it, and", - "trading amongst", - "themselves if needed.", - " But over time,", - "something happened,", - "and they were forced", - "to withdraw from" - ), - new BookPageInfo - ( - "their society, until", - "today thou mayst", - "find individuals of", - "each species within", - "the dungeon, but", - "never again as a", - "civilization.", - " 'Tis also said that" - ), - new BookPageInfo - ( - "someday the three", - "tribes may return to", - "Despise, to once again", - "inhabit it together.", - " Until then, nothing", - "remains as token of", - "this save an oddly", - "intelligent skeleton," - ), - new BookPageInfo - ( - "magically enchanted,", - "that doth speak when", - "questions are asked,", - "and from whom I", - "obtained these tales", - "one day, when I was", - "pursued by evil", - "monsters and fled" - ), - new BookPageInfo - ( - "into his skeletal arms.", - " Fortunately, I", - "escaped and lived to", - "write it all down!" - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TaleOfThreeTribes() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public TaleOfThreeTribes( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Beltran's Guide to Guilds - public class GuideToGuilds : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Beltran's Guide to Guilds", "Beltran", - new BookPageInfo - ( - " This reference", - "work is intended", - "merely to serve as", - "resource for those", - "curious as to the full", - "range of trades and", - "societies extant in", - "Britannia and nearby" - ), - new BookPageInfo - ( - "nations. For each", - "trade or guild, their", - "blazon is given.", - "", - " Armourer's Guild.", - "Gold bar above black", - "bar." - ), - new BookPageInfo - ( - " Association of", - "Warriors. Blue cross", - "on a red field.", - "", - " Barters' Guild.", - "Green and white", - "stripes, diagonal." - ), - new BookPageInfo - ( - " Blacksmith's Guild.", - "Gold alongside black.", - "", - " Federation of", - "Rogues and Beggars.", - "Red above black.", - "", - " Fighters and" - ), - new BookPageInfo - ( - "Footmen. Blue", - "horzontal bar on red", - "field.", - "", - " Guild of Archers.", - "A gold swath parting", - "red and blue." - ), - new BookPageInfo - ( - " Guild of", - "Armaments. Swath of", - "gold on black field,", - "gold accents.", - "", - " Guild of Assassins.", - "Black and red", - "quartered." - ), - new BookPageInfo - ( - "", - " Guild of Barbers.", - "Red and white", - "stripes.", - "", - " Guild of Cavalry and", - "Horse. Vertical blue", - "on a red field." - ), - new BookPageInfo - ( - "", - " Guild of", - "Fishermen. Blue and", - "white, quartered.", - "", - " Guild of Mages.", - "Purple and blue, in a", - "crossed pennant" - ), - new BookPageInfo - ( - "pattern.", - "", - " Guild of", - "Provisioners. White", - "bar above green bar.", - "", - " Guild of Sorcery. A", - "field divided" - ), - new BookPageInfo - ( - "diagonally in blue and", - "purple.", - "", - " Healers Guild. Gold", - "swath dividing green", - "from purple, gold", - "accents." - ), - new BookPageInfo - ( - " Lord British's", - "Healers of Virtue.", - "Golden ankh on dark", - "green.", - "", - " Masters of Illusion.", - "Blue and purple", - "checkers." - ), - new BookPageInfo - ( - "", - " Merchants' Guild.", - "Gold coins on green", - "field.", - "", - " Mining Cooperative.", - "A gold cross,", - "quartering blue and" - ), - new BookPageInfo - ( - "black.", - "", - " Order of Engineers.", - "Purple, gold, and blue", - "vertical.", - "", - " Sailors' Maritime", - "Association. A white" - ), - new BookPageInfo - ( - "bar centered on a blue", - "field.", - "", - " Seamen's Chapter.", - "Blue and white in a", - "crossed pennant", - "pattern." - ), - new BookPageInfo - ( - " Society of Cooks and", - "Chefs. White and red", - "diagonal fields", - "checker on green", - "field.", - "", - " Society of", - "Shipwrights. White" - ), - new BookPageInfo - ( - "diagonal above blue.", - "", - " Society of Thieves.", - "Black and red diagonal", - "stripes.", - "", - " Society of", - "Weaponsmakers. Gold" - ), - new BookPageInfo - ( - "diagonal above black.", - "", - " Tailor's Hall. Purple", - "above gold above red.", - "", - " The Bardic", - "Collegium. Purple and", - "red checkers on gold" - ), - new BookPageInfo - ( - "field.", - "", - " Traders' Guild.", - "White bar centered", - "down green field." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public GuideToGuilds() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public GuideToGuilds( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Birds of Britannia - public class BirdsOfBritannia : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Birds of Britannia", "Thom the Heathen", - new BookPageInfo - ( - " The WREN is a", - "tiny insect-eating", - "bird with a loud voice.", - " The cheerful trills", - "of Wrens are", - "extraordinarily", - "varied and melodious.", - " The SWALLOW" - ), - new BookPageInfo - ( - "is easily recognized", - "by its forked tail.", - "Swallows catch", - "insects in flight, and", - "have squeaky,", - "twittering songs.", - " The WARBLER is", - "an exceptional singer," - ), - new BookPageInfo - ( - "whose extensive", - "songs combine the", - "best qualities of", - "Wrens and Swallows.", - " The NUTHATCH", - "climbs down trees", - "head first, searching", - "for insects in the" - ), - new BookPageInfo - ( - "bark. It sings a", - "repetitive series of", - "notes with a nasal", - "tone quality.", - " The agile", - "CHICKADEE has a", - "buzzy", - "\"chick-a-dee-dee\"" - ), - new BookPageInfo - ( - "call, from which its", - "name is derived. Its", - "song is a series of", - "whistled notes.", - " The THRUSH is a", - "brown bird with a", - "spotted breast, which", - "eats worms and" - ), - new BookPageInfo - ( - "snails, and has a", - "beautiful singing", - "voice. Thrushes use", - "a stone as an anvil to", - "smash the shells of", - "snails.", - " The little", - "NIGHTINGALE is" - ), - new BookPageInfo - ( - "also known for its", - "beautiful song, which", - "it sings even at night.", - " The STARLING", - "is a small dark bird", - "with a yellow bill and", - "a squeaky,", - "high-pitched song." - ), - new BookPageInfo - ( - "Starlings can mimic", - "the sounds of other", - "birds.", - " The SKYLARK", - "sings a series of", - "high-pitched", - "melodious trills in", - "flight." - ), - new BookPageInfo - ( - " The FINCH is a", - "small seed-eating bird", - "with a conical beak", - "and a musical,", - "warbling song.", - " The CROSSBILL", - "is a kind of Finch", - "with a strange" - ), - new BookPageInfo - ( - "crossed bill, which it", - "uses to extract seeds", - "from pine cones.", - " The CANARY is a", - "kind of Finch that is", - "often kept as a pet.", - "Miners would often", - "take Canaries" - ), - new BookPageInfo - ( - "underground with", - "them, to warn them", - "of the presence of", - "hazardous vapors in", - "the air.", - " The SPARROW", - "weaves a nest of", - "grass, and has an" - ), - new BookPageInfo - ( - "unmusical chirp for a", - "voice.", - " The TOWHEE is a", - "kind of Sparrow that", - "continually reminds", - "listeners to drink", - "their tea.", - " The SHRIKE is a" - ), - new BookPageInfo - ( - "gray bird with a", - "hooked bill. Shrikes", - "have the habit of", - "impaling their prey", - "on thorns.", - " The", - "WOODPECKER has a", - "pointed beak that is" - ), - new BookPageInfo - ( - "suitable for pecking at", - "wood to get at the", - "insects inside.", - " The", - "KINGFISHER dives", - "for fish, which it", - "catches with its long,", - "pointed beak." - ), - new BookPageInfo - ( - " The TERN", - "migrates over great", - "distances, from one", - "end of Britannia to", - "the other each year.", - "Terns dive from the", - "air to catch fish.", - " The PLOVER is a" - ), - new BookPageInfo - ( - "bird that distracts", - "predators by", - "pretending to have a", - "broken wing.", - " The LAPWING is", - "a kind of Plover that", - "has a long black crest.", - " The HAWK is a" - ), - new BookPageInfo - ( - "predator that feeds on", - "small birds, mice,", - "squirrels, and other", - "small animals. Small", - "hawks are known as", - "Kites.", - " The DOVE is a", - "seed-eating bird with" - ), - new BookPageInfo - ( - "a peaceful reputation.", - " Doves have a", - "low-pitched cooing", - "song.", - " The PARROT is a", - "brightly colored bird", - "with a hooked bill,", - "favored as a" - ), - new BookPageInfo - ( - "companion by pirates.", - " Parrots can be", - "taught to imitate the", - "human voice.", - " The CUCKOO is a", - "devious bird that lays", - "eggs in the nests of", - "Warblers and other" - ), - new BookPageInfo - ( - "small birds. Cuckoos", - "have the uncanny", - "ability to keep track", - "of time, singing once", - "at the beginning of", - "each hour.", - " The", - "ROADRUNNER is" - ), - new BookPageInfo - ( - "an unusual bird with", - "a long tail, which", - "runs swiftly along", - "the ground hunting", - "for lizards and", - "snakes.", - " The SWIFT is a", - "very agile bird that" - ), - new BookPageInfo - ( - "spends nearly its", - "entire life in the air.", - "With their mouths", - "wide open, Swifts", - "capture insects in", - "mid-flight.", - " The", - "HUMMINGBIRD is a" - ), - new BookPageInfo - ( - "cross between a", - "Swift and a Fairy.", - "These tiny, brightly", - "colored birds hover", - "magically near", - "flowers, and live on", - "the nectar they", - "provide." - ), - new BookPageInfo - ( - " The OWL is a", - "reputedly wise bird", - "that is active at night,", - "unlike most birds.", - "Owls have excellent", - "night vision and", - "low-pitched hooting", - "calls. Their wings" - ), - new BookPageInfo - ( - "are silent in flight.", - " The", - "GOATSUCKER is a", - "strange owl-like bird", - "that is thought to live", - "on the milk of goats.", - "These mysterious", - "birds make jarring" - ), - new BookPageInfo - ( - "sounds at night, for", - "which reason they", - "are also called", - "Nightjars.", - " The DUCK is a", - "bird that swims more", - "often than it flies,", - "and has a nasal voice" - ), - new BookPageInfo - ( - "that is described as a", - "\"quack\".", - " The SWAN is a", - "kind of long-necked", - "Duck that is all white.", - " Swans are usually", - "voiceless, but they", - "are said to have an" - ), - new BookPageInfo - ( - "extraordinarily", - "beautiful song." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public BirdsOfBritannia() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public BirdsOfBritannia( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Britannian Flora: A Casual Guide - public class BritannianFlora : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Britannian Flora: A Casual Guide", "Herbert the Lost", - new BookPageInfo - ( - " Oft 'pon rambling", - "through the woods", - "avoiding bears have I", - "spotted some plant", - "whose like I have", - "never seen before,", - "and concluded that I", - "was a blithering idiot" - ), - new BookPageInfo - ( - "for failing to notice it", - "in the past. Equally", - "as oft have I", - "concluded that I was a", - "worse idiot for not", - "running faster from", - "the bear.", - " While not all my" - ), - new BookPageInfo - ( - "readers may share", - "my proclivities for", - "tree-climbing, it", - "occurred to me that", - "mayhap mine", - "information might", - "serve some humble", - "purpose." - ), - new BookPageInfo - ( - " The two most", - "unique flowering", - "plants in the", - "Britannian", - "countryside are the", - "orfleur and the", - "whiteflower, also", - "called white horns." - ), - new BookPageInfo - ( - " The orfleur is", - "notable for its", - "massive orange-red", - "blossoms, which", - "dwarf marigolds like", - "the sun dwarfs your", - "common fireball spell.", - "The odor of said" - ), - new BookPageInfo - ( - "blooms is best", - "described as", - "peppermint-apple,", - "with a dash of garlic.", - "'Tis a popular potted", - "plant despite, or", - "perhaps because of,", - "its exotic nature." - ), - new BookPageInfo - ( - " Whiteflowers exude", - "a subtle fragrance not", - "unlike that of freshly", - "shaven wood mixed", - "with cool lemon ice.", - "Their tall stands", - "always droop with the", - "heavy weight of the" - ), - new BookPageInfo - ( - "massive blooms, oft", - "as large as a child's", - "head.", - " The flowers are so", - "large that one may", - "scoop out the pollen in", - "handfuls, and during", - "the spring season" - ), - new BookPageInfo - ( - "many a prank hath", - "been played by idle", - "boys 'pon their", - "sisters by dumping", - "said pollen into their", - "clothing drawers,", - "causing sneezes for", - "days." - ), - new BookPageInfo - ( - " The most", - "interesting native tree", - "to Britannia is the", - "spider tree. The", - "reason for its naming", - "is obscure, but may", - "have to do with the", - "twisted gray stalks" - ), - new BookPageInfo - ( - "from which the", - "spherical canopy", - "sprouts. 'Tis", - "something of a", - "misnomer to term", - "these \"trunks\" as", - "they are spindly and", - "flexible. Spider trees" - ), - new BookPageInfo - ( - "provide a fresh,", - "piney smell to a room", - "and are therefore", - "often potted.", - " In jungle climes,", - "one finds the blade", - "plant, whose sharp", - "leaves oft collect" - ), - new BookPageInfo - ( - "water for the thirsty", - "traveler, yet can", - "draw blood easily.", - " The deadliest plant,", - "if you can call a", - "fungus such, is the", - "Exploding Red Spotted", - "Toadstool. No pattern" - ), - new BookPageInfo - ( - "can be discerned to", - "its habitats save", - "malice, for merely", - "approaching results in", - "the cap exploding", - "with powder, noxious", - "gas, and tiny painful", - "pellets flying in all" - ), - new BookPageInfo - ( - "directions.", - "Unfortunately, 'tis", - "impossible to tell it", - "apart from the", - "Ordinary Red Spotted", - "Toadstool save through", - "experimentation.", - " Truly odd among the" - ), - new BookPageInfo - ( - "varied flora of", - "Britannia, however,", - "are those which bear", - "names clearly alien to", - "our tongue. Among", - "these I name the", - "Tuscany pine (for I", - "have never seen a" - ), - new BookPageInfo - ( - "region of this world", - "named Tuscany), the", - "o'hii tree, whose very", - "name sounds like", - "some tropical isle, and", - "the welsh poppy,", - "which while", - "different from the" - ), - new BookPageInfo - ( - "ordinary poppy in", - "color and appearance,", - "is prefaced with the", - "odd word \"welsh,\"", - "which as far as I", - "know means to forgo", - "paying a debt." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public BritannianFlora() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public BritannianFlora( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Classic Children's Tales, Volume 2 - public class ChildrenTalesVol2 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Classic Children's Tales, Volume 2", "Guilhem, Editor", - new BookPageInfo - ( - "Clarke's Printery", - "is Honored to", - "Present Tales from", - "Ages Past!", - " Guilhem the", - "Scholar Shall End", - "EachVolume with", - "Staid Commentary." - ), - new BookPageInfo - ( - "", - "THE RHYME", - "Dance in the Star", - "Chamber", - "And Dance in the Pit", - "And Eat of your", - "Entrees", - "In the Glass House" - ), - new BookPageInfo - ( - "you Sit", - "", - "COMMENTARY", - " A common feeding", - "rhyme for little", - "babies, 'tis thought", - "that this little ditty is", - "part of the corpus of" - ), - new BookPageInfo - ( - "legendary tales", - "regarding the world", - "before Sosaria (see", - "the wonderful fables", - "of Fabio the Poor for", - "fictionalized versions", - "of these stories, also", - "available from this" - ), - new BookPageInfo - ( - "same publisher).", - " According to these", - "old tales, which", - "survive mostly in the", - "hills and remote", - "villages where Lord", - "British is as yet a", - "distant and mythical" - ), - new BookPageInfo - ( - "ruler, the gods of old", - "(a fanciful notion!)", - "met to discuss the", - "progress of creating", - "the world in mystical", - "rooms. A simple", - "analysis reveals these", - "rooms to be mere" - ), - new BookPageInfo - ( - "mythological", - "generalizations.", - " \"The Star", - "Chamber\" is clearly a", - "reference to the sky.", - "\"The Pit\" is certainly", - "an Underworld", - "analogous to the" - ), - new BookPageInfo - ( - "Snakehills of other", - "tales, and \"the Glass", - "House\" is no doubt the", - "vantage point from", - "which the gods", - "observed their", - "creation. All is simple", - "when seen from this" - ), - new BookPageInfo - ( - "perspective, leaving", - "only the mysterious", - "reference to dinners.", - "Oddly enough, the", - "rhyme is universally", - "used only for", - "midnight feedings,", - "never during the day." - ), - new BookPageInfo - ( - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public ChildrenTalesVol2() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public ChildrenTalesVol2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Classic Tales of Vesper, Volume 1 - public class TalesOfVesperVol1 : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Classic Tales of Vesper, Volume 1", "Clarke's Printery", - new BookPageInfo - ( - "'Tis an Honor to", - "present to Thee these", - "Tales collected from", - "Ages Past. In this", - "Inaugural Volume, we", - "present this Verse", - "oft Recited as a", - "Lullabye for sleepy" - ), - new BookPageInfo - ( - "Children.", - "", - "Preface", - "by Guilhem the", - "Scholar", - "", - " The meaning of this", - "verse has oft been" - ), - new BookPageInfo - ( - "discussed in halls of", - "scholarly sorts, for", - "its mysterious", - "singsongy melody is", - "oddly disturbing to", - "adult ears, though", - "children seem to find", - "it restful as they" - ), - new BookPageInfo - ( - "sleep. Perhaps it is", - "but the remnant of a", - "longer ballad once", - "extant, for there are", - "internal indications", - "that it once told a", - "longer story about", - "ill-fated lovers, and a" - ), - new BookPageInfo - ( - "magical experiment", - "gone awry. However,", - "poetic license and the", - "folk process has", - "distorted the words", - "until now the locale of", - "the tale is no more", - "than \"in the wind,\"" - ), - new BookPageInfo - ( - "which while it serves", - "a pleasingly", - "metaphorical purpose,", - "fails to inform the", - "listener as to any real", - "locale!", - " Another possibility", - "is that this is some" - ), - new BookPageInfo - ( - "form of creation", - "myth explaining the", - "genesis of the various", - "humanoid creatures", - "that roam the lands of", - "Britannia. It does not", - "take a stretch of the", - "imagination to name" - ), - new BookPageInfo - ( - "the middle verse's", - "\"girl becomes tree\" as", - "a possible explanation", - "for the reaper, for in", - "the area surrounding", - "Minoc, reapers are", - "oft referred to among", - "the lumberjacking" - ), - new BookPageInfo - ( - "community as", - "\"widowmakers.\" That", - "these creatures are", - "of arcane origin is", - "assumed, but the", - "verse seems to imply", - "a long ago creator, and", - "uses the antique" - ), - new BookPageInfo - ( - "magickal terminology", - "of \"plaiting strands", - "of ether\" that is so", - "often found in", - "ancient texts. In", - "addition, the", - "reference to", - "\"snakehills\" may" - ), - new BookPageInfo - ( - "profitably be regarded", - "as a reference to an", - "actual location, such", - "as perhaps a local", - "term for the", - "Serpent's Spine.", - " A commoner", - "interpretation is that" - ), - new BookPageInfo - ( - "like many nursery", - "rhymes, it is a", - "simple explanation", - "for death, wherein", - "the wind snatches up", - "boys and girls and", - "when they sleep in", - "order to keep the" - ), - new BookPageInfo - ( - "balance of the world.", - "Notable tales have", - "been written for", - "children of", - "adventures in \"the", - "Snakehills,\" which", - "are presumed to be an", - "Afterworld whence" - ), - new BookPageInfo - ( - "the spirit lives on. A", - "grim lullabye, to be", - "sure, but no worse", - "than \"lest I die before", - "I wake\" surely.", - " In either case, 'tis", - "an old favorite,", - "herein printed for" - ), - new BookPageInfo - ( - "the first time for", - "thy enjoyment and", - "perusal!", - "", - "In the Wind where", - "the Balance", - "Is Whispered in", - "Hallways" - ), - new BookPageInfo - ( - "In the Wind where", - "the Magic", - "Flows All through the", - "Night", - "There live Mages and", - "Mages", - "With Robes made of", - "Whole Days" - ), - new BookPageInfo - ( - "Reading Books full of", - "Doings", - "Printed on Light", - "", - "In the Wind where", - "the Lovers", - "Are Crossed under", - "Shadows" - ), - new BookPageInfo - ( - "Where they Meet and", - "are Parted", - "By the Orders of", - "Fate", - "The Girl becomes", - "Tree,", - "And thus becomes", - "Widow" - ), - new BookPageInfo - ( - "The Boy becomes", - "Earth", - "And Wanders Till", - "Late", - "", - "In the Wind are the", - "Monsters", - "First Born First" - ), - new BookPageInfo - ( - "Created", - "When Chanting and", - "Ether", - "Mix Meddling and", - "Nigh", - "Fear going to Wind,", - "Fear Finding its", - "Plaitings," - ), - new BookPageInfo - ( - "Go Not to the", - "Snakehills", - "Lest You Care to Die" - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TalesOfVesperVol1() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public TalesOfVesperVol1( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Deceit: A Dungeon of Horrors - public class DeceitDungeonOfHorror : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Deceit: A Dungeon of Horrors", "Mercenary Justin", - new BookPageInfo - ( - " My employers have", - "oft taken me into this", - "den of hideous", - "creatures, and I", - "thought that it", - "behooved me to write", - "down what I know of", - "it, now that I am" - ), - new BookPageInfo - ( - "retired from the life", - "of an adventurer for", - "hire.", - " Deceit was once a", - "temple to forgotten", - "powers of old. It was", - "taken over by mages", - "who eventually were" - ), - new BookPageInfo - ( - "driven out by the", - "depredations of their", - "own evil lackeys.", - "However, many of", - "the magical traps and", - "devices that they", - "placed for their", - "defenses remain," - ), - new BookPageInfo - ( - "particularly those the", - "wizards used to", - "protect their", - "treasures.", - " The dungeon is", - "mystically linked by", - "crystal balls placed in", - "different locations." - ), - new BookPageInfo - ( - "These magical orbs do", - "transmit speech, and", - "even have memory of", - "things that have been", - "said near them. No", - "doubt they once", - "served as a warning", - "system" - ), - new BookPageInfo - ( - " Be wary of a", - "brazier that giveth", - "warning when", - "approached; thou canst", - "use it to summon", - "deadly creatures.", - " There be a", - "tantalizing chest," - ), - new BookPageInfo - ( - "undoubtedly full of", - "treasure, that cannot", - "be reached save past a", - "complex set of", - "pressure plates that", - "trigger deadly spikes.", - "As I never had", - "sufficient folk with" - ), - new BookPageInfo - ( - "me to unlock the", - "puzzle, I never", - "obtained the riches", - "that awaited there.", - " Do not investigate", - "iron maidens too", - "closely, for they may", - "suck you within" - ), - new BookPageInfo - ( - "them!", - " There is one place", - "where a deadly trap", - "can only be disarmed", - "by making use of a", - "statue that cleverly", - "conceals a lever.", - " Oft one encounters" - ), - new BookPageInfo - ( - "the deadly exploding", - "toadstool; the ones in", - "Deceit are deadlier", - "than most, as they", - "explode continually.", - "Likewise, the very", - "pools of water and", - "slime on the floor" - ), - new BookPageInfo - ( - "may poison thee.", - " The most magical", - "device in the dungeon", - "is a mystical bridge", - "that can only be", - "triggered by a level", - "embedded in the floor.", - "Be wary however," - ), - new BookPageInfo - ( - "for the bridge thus", - "created doth burst", - "into flame when one", - "passeth across it!" - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public DeceitDungeonOfHorror() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public DeceitDungeonOfHorror( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Dimensional Travel, a Monograph - public class DimensionalTravel : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Dimensional Travel, a Monograph", "Dryus Doost, Mage", - new BookPageInfo - ( - " 'Tis beyond the", - "scope of this small", - "monograph to discuss", - "the details of", - "moongates, and the", - "manners in which", - "they distort the", - "fabric of reality in" - ), - new BookPageInfo - ( - "such a manner as to", - "permit the passage of", - "living flesh from", - "place to place, world to", - "world, or indeed from", - "dimension to", - "dimension.", - " Instead, allow me to" - ), - new BookPageInfo - ( - "bring thy attention,", - "Gentle Reader, to the", - "curious", - "characteristics that", - "are shared by certain", - "individuals within", - "our realm.", - " Long has it been" - ), - new BookPageInfo - ( - "known that the blue", - "moongate permits", - "travel from place to", - "place, and none have", - "trouble in taking this", - "path. Yet 'tis also", - "known, albeit only to a", - "few, that certain" - ), - new BookPageInfo - ( - "individuals are unable", - "to traverse the black", - "moongates that permit", - "travel from one", - "dimension to another.", - " The noted mage and", - "peer of our realm,", - "Lord Blackthorn, once" - ), - new BookPageInfo - ( - "told me in", - "conversation that his", - "arcane research had", - "indicated that the", - "issue was one of", - "conversation of ether.", - "To wit, given the", - "postulate that matter" - ), - new BookPageInfo - ( - "within a given", - "dimension may be but", - "a cross-section of", - "ethereal matter that", - "exists in multiple", - "dimensions, it", - "becomes obvious that", - "said ethereal" - ), - new BookPageInfo - ( - "structure cannot", - "enter dimensions in", - "which it is already", - "present.", - " Imagine an", - "individual (and the", - "Lord Blackthorn", - "hinted that he was" - ), - new BookPageInfo - ( - "one such) who exists", - "already in some form", - "in multiple", - "dimensions; said", - "individual would not", - "be able to cross into", - "another dimension", - "because HE IS" - ), - new BookPageInfo - ( - "ALREADY THERE.", - " The implications of", - "this are staggering,", - "and merit further", - "study. 'Tis well", - "known by theorists in", - "the field that", - "divisions in the" - ), - new BookPageInfo - ( - "ethereal structure of", - "an individual are", - "already implicit at the", - "temporal level, as", - "causality forces", - "divisions upon the", - "ether. This is the", - "basic operating" - ), - new BookPageInfo - ( - "mechanism by which", - "white moongates", - "function, permitting", - "time travel.", - " As time travel is", - "not barred by the", - "presence of an earlier", - "self (though" - ), - new BookPageInfo - ( - "encountering said", - "earlier self can prove", - "arcanely perilous),", - "there must be some", - "rigidity to the", - "ethereal structure", - "that bars multiple", - "instantiations of" - ), - new BookPageInfo - ( - "structures from", - "manifesting within", - "the same context.", - " If one regards time", - "and causal bifurcation", - "as a web, perhaps the", - "appropriate analogy", - "for dimensional" - ), - new BookPageInfo - ( - "matrices is that of a", - "crystalline structure,", - "with rigid linkages.", - "The only way in", - "which an individual", - "such as Lord", - "Blackthorn, who", - "exists in multiple" - ), - new BookPageInfo - ( - "dimensional matrices,", - "can cross worlds via", - "a black moongate,", - "would be for the", - "entire crystalline", - "structure of the", - "dimension to", - "perfectly match the" - ), - new BookPageInfo - ( - "ethereal resonance of", - "the destination", - "dimension.", - " The problem of why", - "certain individuals", - "are already replicated", - "in multiple crystalline", - "matrices is one that I" - ), - new BookPageInfo - ( - "fail to provide any", - "schema for in these", - "poor theories. It is", - "my fondest hope that", - "someday someone", - "shall conquer that", - "thorny problem and", - "enlighten the world." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public DimensionalTravel() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public DimensionalTravel( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Ethical Hedonism: An Introduction - public class EthicalHedonism : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Ethical Hedonism: An Introduction", "Richard Garriott", - new BookPageInfo - ( - " Societies oft have", - "common codes of", - "conduct which it", - "expects all its people", - "to abide by. Now,", - "while 'tis true that", - "this can offer some", - "advantages, most of" - ), - new BookPageInfo - ( - "the codes I see today", - "around Britannia have", - "fatal flaws. Let us", - "examine them.", - " First, there is", - "Blackthorn's code of", - "Chaos or basically", - "Anarchy. Whereas" - ), - new BookPageInfo - ( - "this affords the", - "individual maximum", - "opportunity for", - "individuality and even", - "pursuit of personal", - "happiness, it does not", - "offer even basic", - "interpersonal conduct" - ), - new BookPageInfo - ( - "codes to prevent", - "people from killing", - "each other.", - " Without such basic", - "tenets, all the people", - "will need to spend a", - "significant portion of", - "their time and effort" - ), - new BookPageInfo - ( - "towards personal", - "protection and thus", - "less time towards", - "other more beneficial", - "pursuits.", - " Then there are the", - "moral codes that are", - "so popular today." - ), - new BookPageInfo - ( - "These codes are built", - "largely on historical", - "tradition rather than", - "current logic and thus", - "are also antiquated.", - "For example many", - "moral codes we see", - "today include" - ), - new BookPageInfo - ( - "statements about not", - "eating certain foods", - "that once were often", - "poisonous, but today", - "can be prepared", - "safely.", - " Many forbid contact", - "between young people" - ), - new BookPageInfo - ( - "of the opposite", - "gender, which can in", - "fact be hazardous; but", - "the codes often have", - "lost the context as to", - "why this is done,", - "instead merely calling", - "it amoral. In this day" - ), - new BookPageInfo - ( - "and age to call that a", - "necessary moral", - "would need a new", - "reasoning. I put forth", - "that tradition is not", - "enough", - " Then there are", - "Lord British's" - ), - new BookPageInfo - ( - "Virtues. It strikes me", - "that while a system", - "of virtues is", - "wonderful as a", - "touchstone to guide a", - "society to good", - "behavior, these are", - "but shades of the" - ), - new BookPageInfo - ( - "underlying truth as to", - "why one may wish to", - "live a life according to", - "certain rules of", - "conduct.", - " On the other hand,", - "clearly the Virtues", - "that I have heard" - ), - new BookPageInfo - ( - "Lord British speak of", - "are clearly positive", - "codes of conduct, far", - "better than the world", - "of anarchy that Lord", - "Blackthorn suggests.", - "Yet, are not these", - "Virtues still derived" - ), - new BookPageInfo - ( - "from a set of", - "principles which", - "though they sound", - "good, are difficult to", - "pin down as actual,", - "undeniable, rational", - "truths?", - " Worse yet though" - ), - new BookPageInfo - ( - "imagine a society", - "who's code of", - "conduct was based on", - "pure survival of the", - "strongest. While this", - "society may function", - "and even accomplish", - "much, it can be" - ), - new BookPageInfo - ( - "fairly argued that", - "personal happiness", - "would suffer greatly,", - "except for those at", - "the top. To rule that", - "out, however, we", - "must first believe", - "that people have a" - ), - new BookPageInfo - ( - "right to pursue", - "happiness.", - " I hope is a safe", - "assumption that all", - "beings wish to be", - "happy; I will broadly", - "describe this as", - "Hedonism. Yet, if all" - ), - new BookPageInfo - ( - "people did is live a", - "life of hedonism,", - "their hedonism might", - "be in conflict with", - "those near them, so I", - "will use the term", - "Ethics to describe", - "limits one might put" - ), - new BookPageInfo - ( - "on one's hedonistic", - "tendencies to allow", - "others to pursue their", - "happiness as well.", - " Allow me to give", - "this example: If one", - "were to live alone on a", - "desert isle, one could" - ), - new BookPageInfo - ( - "live a life of pure", - "hedonism, for no", - "action one might take", - "could interfere with", - "another's right to", - "pursue their", - "happiness. Poison the", - "lake if you like, there" - ), - new BookPageInfo - ( - "is no one to blame but", - "yourself!", - " Now suppose two", - "of you live on that", - "island. Thou dost not", - "want thy neighbor to", - "feel free to poison the", - "lake. Would it not be" - ), - new BookPageInfo - ( - "better to consider it", - "unethical to poison the", - "lake without first", - "thinking of those", - "whose pursuit of", - "happiness might be", - "affected by this", - "action?" - ), - new BookPageInfo - ( - " I put forth that it is", - "the fact that we as a", - "people choose to live in", - "groups known as a", - "society that causes us", - "to compromise our", - "pure hedonism with", - "logical ethics." - ), - new BookPageInfo - ( - "Likewise we accept", - "not being able to kill", - "others without", - "reason, because our", - "own pursuit of", - "happiness would be", - "greatly interfered", - "with if we feared" - ), - new BookPageInfo - ( - "others would do the", - "same to us. From", - "this basis of logic can", - "be formed the Tenets", - "of Ethical Hedonism.", - " For more on this", - "subject, see The", - "Tenants of Ethical" - ), - new BookPageInfo - ( - "Hedonism, by", - "Richard Garriott and", - "Herman Miller." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public EthicalHedonism() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public EthicalHedonism( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region My Story - public class MyStory : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "My Story", "Sherry the Mouse", - new BookPageInfo - ( - " 'Twas on a chill", - "night, when the moon", - "shone pasty-faced", - "above the horizon,", - "balanced on the", - "towers of Lord", - "British's castle, that", - "the events I am about" - ), - new BookPageInfo - ( - "to relate took place,", - "some years ago now. I", - "witnessed them all", - "from my tiny", - "mousehole.", - " Milords British and", - "Blackthorn are", - "accustomed to a game" - ), - new BookPageInfo - ( - "of chess 'pon an", - "evening, over which", - "they argue the issues", - "that affect the course", - "of the realm. Lord", - "Blackthorn was on his", - "way to Lord British's", - "chambers, and Lord" - ), - new BookPageInfo - ( - "British stood by a", - "window casement,", - "just having finished", - "setting the pieces", - "upon the board.", - " Suddenly the", - "shutters blew open,", - "and Lord British fell" - ), - new BookPageInfo - ( - "to the ground, one", - "hand shielding his", - "eyes. A chill wind", - "entered the room, and", - "it seemed a gash was", - "torn in the very air.", - "Through the gash I", - "could see stars and" - ), - new BookPageInfo - ( - "swirling clouds of", - "stellar dust, and a", - "coldness sucked all", - "the warmth from the", - "air. A terrible wind", - "tossed books and", - "blankets across the", - "room, and furniture" - ), - new BookPageInfo - ( - "toppled.", - " From within this", - "gash issued a great", - "voice, unlike any I", - "have ever heard. And", - "these are the words it", - "spoke (for I", - "memorized them most" - ), - new BookPageInfo - ( - "carefully):", - " \"Greetings, Lord", - "British. I am the", - "Time Lord, a being", - "from beyond your", - "dimension, as thou", - "art from a world", - "other than Sosaria. I" - ), - new BookPageInfo - ( - "am here to bring thee", - "warning. Dost thou", - "recall how long ago a", - "mysterious Stranger", - "came to Sosaria and", - "saved the world from", - "the evil wizard", - "Mondain? He" - ), - new BookPageInfo - ( - "shattered the Gem of", - "Immortality, within", - "which dwelled a", - "perfect likeness of", - "this world.\"", - " Lord British slowly", - "stood and faced the", - "hole in the air. \"I" - ), - new BookPageInfo - ( - "remember,\" he said.", - "\"Oft have I wished", - "that stranger would", - "return.\"", - " \"He hath returned,\"", - "spoke the voice. \"But", - "not to here. When the", - "Gem was shattered, a" - ), - new BookPageInfo - ( - "thousand shards were", - "scattered across the", - "dimensions, and in", - "each shard there is a", - "perfect likeness of", - "this world. And thou", - "dost live upon one", - "such shard, for thou" - ), - new BookPageInfo - ( - "art not of the true", - "world-thou art", - "merely a reflection.\"", - " Lord British looked", - "shaken by this, and I", - "did not know what to", - "think! Was I merely a", - "shadow of the real" - ), - new BookPageInfo - ( - "me, which lives still", - "somewhere else", - "across uncounted", - "universes?", - " \"My task is to heal", - "this shattered world,", - "Lord British,\" said", - "the voice. \"And I seek" - ), - new BookPageInfo - ( - "to enlist thee in my", - "cause. Be warned that", - "in this case, healing", - "carries with it a", - "terrible price.\"", - " Concern warred", - "with curiosity on my", - "liege's face, but ever" - ), - new BookPageInfo - ( - "one to shoulder a", - "burden, he", - "straightened and", - "faced the gash in the", - "air bravely. \"Name", - "thy price.\"", - " \"A shard of a", - "universe is a" - ), - new BookPageInfo - ( - "powerful thing, and a", - "universe shattered is", - "always in danger", - "from the powers of", - "darkness. Already", - "three shards were", - "turned to evil, and", - "sent to plague the" - ), - new BookPageInfo - ( - "original universe in", - "the form of", - "Shadowlords. Many", - "times have I brought", - "the Stranger back to", - "Britannia, to preserve", - "it from its own folly", - "or from outside" - ), - new BookPageInfo - ( - "dangers. Yet as long", - "as the world", - "remaineth in pieces,", - "it remaineth", - "vulnerable. We must", - "bring the shards into", - "harmony, so that they", - "resonate in such a" - ), - new BookPageInfo - ( - "manner that matches", - "the original universe.", - "Then the two", - "universes shall", - "merge, and be again", - "as one.\"", - " \"But if we are only", - "shadows...\" Lord" - ), - new BookPageInfo - ( - "British said", - "wonderingly.", - " The light from the", - "stars within the hole", - "seemed to dim.", - "\"Indeed, the", - "reflections shall", - "become one with the" - ), - new BookPageInfo - ( - "original. Thou wouldst", - "cease to be as thou", - "art, and become part", - "of the larger you.", - "Thou shalt not die;", - "however, uncounted", - "generations have", - "passed and borne" - ), - new BookPageInfo - ( - "children since that", - "day, and they have no", - "counterparts. They", - "would perish utterly.\"", - " Lord British sagged", - "in shock, realizing", - "the terrible price that", - "would be paid to heal" - ), - new BookPageInfo - ( - "the universe. \"All of", - "my people,\" he", - "breathed.", - " \"'Tis for the greater", - "good.\"", - " Lord British bowed", - "his head.", - " 'Twas then I saw" - ), - new BookPageInfo - ( - "the movement by the", - "door, half-hid by the", - "heavy red curtains.", - "Lord Blackthorn stood", - "there, concealed from", - "the rest of the room,", - "his face white. How", - "long had he been" - ), - new BookPageInfo - ( - "listening? I cannot", - "say, yet I suspect", - "that he had heard all", - "that the mysterious", - "voice had to say.", - " \"How then, shall I", - "aid thee?\" Lord", - "British said," - ), - new BookPageInfo - ( - "weariness in his", - "voice.", - " \"Aid the nobilty that", - "resideth in the", - "human heart. Protect", - "the Virtues that so", - "recently came to thee", - "in thought late at" - ), - new BookPageInfo - ( - "night. They are the", - "Virtues of life, as", - "your counterpart", - "understands them to", - "be. For when thy", - "populace doth live and", - "breathe these Virtues,", - "shall it match the" - ), - new BookPageInfo - ( - "true Britannia, and", - "thy shard shall", - "rejoin with it.\"", - " The gash in the air", - "began to close, and", - "with it warmth stole", - "back into the room.", - " \"I was going to" - ), - new BookPageInfo - ( - "discuss my idea with", - "Blackthorn tonight,\"", - "Lord British", - "breathed. \"Have I no", - "thoughts that are my", - "own? Is my life but", - "a reflection of", - "another me?\"" - ), - new BookPageInfo - ( - " \"Nay,\" said the", - "voice, smaller through", - "the diminished", - "opening. \"Say, rather,", - "that you are parallel,", - "for there is no", - "guarantee that thou", - "shalt accomplish what" - ), - new BookPageInfo - ( - "I have set thee to. I", - "speak tonight to a", - "thousand of thee, and", - "ask the same of all.", - "Perhaps not all shall", - "seek to aid me.\" And", - "with that, the gash", - "closed, and the voice" - ), - new BookPageInfo - ( - "was gone, leaving a", - "room that appeare", - "tossed by a mighty", - "storm.", - " \"Destroy the world", - "to save the universe,\"", - "Lord British said", - "bitterly. \"I do not" - ), - new BookPageInfo - ( - "wonder that some", - "may balk.\"", - " Lord Blackthorn", - "collected himself, and", - "strode into the room,", - "a decent mimicry of", - "surprise on his face.", - "\"My liege! What has" - ), - new BookPageInfo - ( - "happened here?\" he", - "exclaimed, feigning", - "dismay well. But not", - "well enough to fool", - "his old friend, whose", - "eyes narrowed at", - "seeing him there.", - " \"How much didst" - ), - new BookPageInfo - ( - "thou hear?\" demanded", - "Lord British.", - " \"Why, nothing,\"", - "managed Blackthorn,", - "his head ducked away", - "from his friend, as", - "he bent to retrieve the", - "fallen chess pieces. \"I" - ), - new BookPageInfo - ( - "merely came for our", - "game of chess.\"", - " Together they", - "righted the pedestal", - "table, and set the", - "pieces upon the black", - "and white squares.", - "\"Such simplicity to" - ), - new BookPageInfo - ( - "the game, Blackthorn,\"", - "mused Lord British,", - "idly brushing one", - "finger against the", - "board. \"Black and", - "white, each to its own", - "color, as if life were", - "so simple. What think" - ), - new BookPageInfo - ( - "you?\"", - " Blackthorn sat", - "heavily on a hassock", - "beside the chess table.", - "\"I think that matters", - "are never so simple,", - "my liege. And that I", - "would regret it deeply" - ), - new BookPageInfo - ( - "if someone, such as a", - "friend, saw it thus.\"", - " Lord British's eyes", - "met his. \"Yet", - "sometimes one must", - "sacrifice a pawn to", - "save a king.\"", - " Lord Blackthorn met" - ), - new BookPageInfo - ( - "his gaze squarely.", - "\"Even pawns have", - "lives and loves at", - "home, my lord.\" Then", - "he reached out for a", - "pawn, and firmly", - "moved it forward two", - "squares. \"Shall we" - ), - new BookPageInfo - ( - "play a game?\" he", - "asked.", - " The chess game that", - "night was a draw,", - "and they played", - "grimly.", - " And the next day,", - "Lord British gathered" - ), - new BookPageInfo - ( - "the nobles to proclaim", - "the idea of a new", - "system of Virtues,", - "and declared that", - "shrines should be", - "built across the land.", - " Lord Blackthorn", - "opposed it bitterly," - ), - new BookPageInfo - ( - "and many thought", - "him strange for doing", - "so, for ever had he", - "been a noble and", - "upright man, and", - "ever had he and Lord", - "British been in", - "accord. Declaring that" - ), - new BookPageInfo - ( - "he should start his", - "own shrine, he", - "departed the castle", - "that day to live in a", - "tower in a lake on the", - "north side of the", - "city.", - " They are still the" - ), - new BookPageInfo - ( - "best of friends, yet a", - "sadness hangs", - "between them, as if", - "they were forced into", - "making choices that", - "appealed not to them.", - "And at night, when I", - "creep softly from one" - ), - new BookPageInfo - ( - "corner of my liege's", - "bedchamber to", - "another, I sometimes", - "see him take a pawn", - "from his night table,", - "and hold it in his", - "hand, and quietly", - "weep." - ), - new BookPageInfo - ( - " But I am but a", - "mouse, and none hear", - "me. This tale goes", - "unknown, save for", - "my writing these", - "enormous letters with", - "mine ink-stained tiny", - "paws for thee to" - ), - new BookPageInfo - ( - "read, for I fear", - "indeed for our world", - "and for our people in", - "these perilous times." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public MyStory() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public MyStory( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region On the Diversity of Our Land - public class DiversityOfOurLand : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "On the Diversity of Our Land", "Lord Blackthorn", - new BookPageInfo - ( - " While I deplore the", - "depredations of the", - "misguided and", - "belligerent races with", - "which we share our", - "fair Britannia, and", - "alongside the populace,", - "do mourn the needless" - ), - new BookPageInfo - ( - "deaths that their", - "raids cause, I cannot", - "countenance the policy", - "of wholesale slaughter", - "of these races that", - "seems to be the habit", - "of our soldierly", - "element." - ), - new BookPageInfo - ( - " Can we not regard", - "the ratmen, lizard", - "men, and orcs are", - "fellow intelligent", - "beings with whom we", - "share a planet? Why", - "must we slay them", - "on sight, rather than" - ), - new BookPageInfo - ( - "attempt to engage", - "them in dialogue?", - "There is no policy of", - "shooting at wisps", - "when they grace us", - "with their presence", - "(not that an arrow", - "could do much to" - ), - new BookPageInfo - ( - "pierce them!).", - " To view these", - "creatures as vermin", - "denies their obvious", - "intelligence, and we", - "cannot underestimate", - "the repercussions", - "that their slaughter" - ), - new BookPageInfo - ( - "may have. If we", - "regard the slaying of", - "fellow humans as a", - "crime, so must we", - "regard the killing of", - "an orc.", - " At the same time,", - "should a lizardman" - ), - new BookPageInfo - ( - "slay a human, should", - "we not forgive their", - "ignorance and", - "foolishness? Let us", - "not surrender the", - "high moral ground by", - "descending to", - "bestiality." - ), - new BookPageInfo - ( - " Now, I say not that", - "we should fail to", - "defend ourselves in", - "case of attack, for", - "even amongst humans", - "we see war, we see", - "famine, and we see", - "assault (though we" - ), - new BookPageInfo - ( - "owe a debt of", - "gratitude to our Lord", - "British for", - "preserving us from", - "the worst of these!).", - "However, incursions", - "such as the recent", - "tragedy which cost us" - ), - new BookPageInfo - ( - "the life of Japheth,", - "Guildmaster of", - "Trinsic's Paladins,", - "are folly.", - " I had met Japheth,", - "and like all paladins,", - "he burned with an", - "inner fire. Yet" - ), - new BookPageInfo - ( - "though I had the", - "utmost respect for", - "him, none could deny", - "the hatred that", - "flashed in his eyes at", - "the mere mention of", - "orcs. And thus he", - "carried his battle to" - ), - new BookPageInfo - ( - "the orc camps, and", - "died there, unable to", - "rise above his own", - "childhood experiences", - "depicted in his book,", - "\"The Burning of", - "Trinsic.\" 'Tis a", - "shame that even our" - ), - new BookPageInfo - ( - "mightiest men fall", - "prey to this", - "ignorance!", - " Are there not", - "legends of orcs", - "adopting human", - "children to raise as", - "their own? Tales of" - ), - new BookPageInfo - ( - "complex societies built", - "underground by races", - "we regard as bestial?", - " Let us not repeat", - "the mistake of", - "Japheth of the", - "Paladins, and let us", - "cease to persecute the" - ), - new BookPageInfo - ( - "nonhuman races,", - "before we discover", - "that we are harming", - "ourselves in the", - "process." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public DiversityOfOurLand() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public DiversityOfOurLand( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Quest of the Virtues - public class QuestOfVirtues : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Quest of the Virtues", "Autenil", - new BookPageInfo - ( - "Volume 1", - "Chapter 1: Starting out", - "I begin my Quest in the", - "fine bank of Skara Brae.", - "My Quest is to travel by", - "foot to the eight shrines", - "of Britannia. Although", - "this may sound easy, it" - ), - new BookPageInfo - ( - "is hampered because I", - "have forsaken my abilities", - "and worldly possessions.", - "Instead, all that I have", - "to live by are a set of", - "plain clothes, a ship to", - "sail the seas and my", - "diary in which to record" - ), - new BookPageInfo - ( - "my adventures. Onward", - "Ho towards the Shrine of", - "Spirituality!", - "", - "Chapter 2: The Road to", - "Spirituality", - "", - "Since I have forsaken" - ), - new BookPageInfo - ( - "magic as a form of", - "travel, I must find a way", - "to the mainland from this", - "island town. Fortunately,", - "I was able to barter a", - "ride from the ferryman.", - "Upon reaching the", - "mainland, I followed the" - ), - new BookPageInfo - ( - "road until it turned", - "North, yet I must", - "continue Eastward. I", - "paused to listen to the", - "pleasant sounds of the", - "birds chirping and enjoyed", - "the peace away from the", - "busy life. Upon reaching" - ), - new BookPageInfo - ( - "the Hedge Maze I recalled", - "a story about the mage", - "Relvinian in the days of", - "old and turned South to", - "go around it. Possessing", - "no weapons and having", - "forsaken my training, I", - "heeded the sign that said," - ), - new BookPageInfo - ( - "\"Enter and Become One", - "Among Ghosts.\" The River", - "forced me to turn South", - "and then continue East.", - "", - "Chapter 3: Spirituality", - "", - "Spirituality is the leader" - ), - new BookPageInfo - ( - "of the Virtues. It is the", - "meditation and", - "understanding of all other", - "Virtues. Without", - "Spirituality, one cannot", - "completely follow the", - "Virtues, for It is the", - "dedication and adherance" - ), - new BookPageInfo - ( - "to them.", - "", - "Chapter 4: Finding Honor", - "", - "My next visit will be to", - "the Shrine of Honor,", - "which lies a fair distance", - "to the South. There is a" - ), - new BookPageInfo - ( - "road to my East that I", - "will follow to the town", - "of Trinsic. I found a", - "warm room at the", - "Traveller's Inn, and woke", - "refreshed in the morning", - "to hear the sounds of", - "nature as I prepared to" - ), - new BookPageInfo - ( - "continue my journeys. I", - "thanked the kind innkeeper", - "and headed out of Trinsic", - "and South. I conversed", - "briefly with one lucky", - "enough to own a house in", - "the beautiful country and", - "he bade me good fortune" - ), - new BookPageInfo - ( - "on my travels. I used my", - "rusty blade to cut", - "through dense jungles", - "past ruins of a forgotten", - "realm, now inhabited only", - "by the Undead. Many a", - "mongbat did hamper my", - "journey, but finally I" - ), - new BookPageInfo - ( - "arrived at the Shrine of", - "Honor.", - "", - "Chapter 5: Honor", - "", - "Many link Honor and", - "battle, but it can be", - "used with any aspect of" - ), - new BookPageInfo - ( - "Life. Honor is to abide", - "by the rules, dishonor is", - "to cheat; to seek the", - "unfair advantage. I vowed", - "to always live life with", - "Honor.", - "", - "Chapter 6: Seeking Valor" - ), - new BookPageInfo - ( - "I must now embark on my", - "trusty small ship, the", - "Hollandia, to the South", - "and East, to a small", - "island where few have", - "travelled. I know not yet", - "what I will encounter at", - "sea, so I bid the Virtues" - ), - new BookPageInfo - ( - "grant me safety. So", - "begins my voyage. I", - "managed to sail unnoticed", - "past some water", - "elementals which took a", - "fair bit of navigation", - "from my tillerman.", - "However, I arrived without" - ), - new BookPageInfo - ( - "incident.", - "", - "Chapter 7: Valor", - "", - "The Shrine of Valor is", - "protected by many a", - "beast far too poisonous", - "and foul for myself to" - ), - new BookPageInfo - ( - "vanquish. One mush show", - "Valor to approach the", - "Shrine! Valor is often", - "shown in one's willingness", - "to fight what maybe a", - "losing battle upon which", - "he believes. It takes", - "Valor to stand your" - ), - new BookPageInfo - ( - "ground against the many", - "murderers and lawbreakers", - "in our lands. You may", - "lose, but you show Valor", - "in that you fight that", - "which must be opposed.", - "Fight the fights you", - "believe in, not just the" - ), - new BookPageInfo - ( - "fights you think you can", - "win.", - "", - "Chapter 8: The Voyage to", - "Humility", - "", - "My journey will continue", - "to the East towards the" - ), - new BookPageInfo - ( - "Shrine of Humility. I", - "launch my boat from the", - "West side of the Island", - "of Valor, where I made", - "my daring escape from", - "the many Giant Serpents", - "chasing me with their", - "poisonous venom and" - ), - new BookPageInfo - ( - "hissing tongues. Beautiful", - "blue waves washed over", - "the bow of the boat as", - "dolphins played, merrily", - "leading me on. The voyage", - "is long and the water", - "turbulent but finally land", - "was struck. Quickly I ran," - ), - new BookPageInfo - ( - "eager to find my final", - "destination for the day.", - "", - "Chapter 9: Humility", - "", - "The Shrine of Humility is", - "surprisingly spartan; it is", - "merely a grove of stone" - ), - new BookPageInfo - ( - "pillars with an ankh and", - "the Humility stone at its", - "center. I would", - "characterize Humility as", - "this Quest; returning to", - "my roots in this world. I", - "have rejected my", - "possessions and my wealth" - ), - new BookPageInfo - ( - "in order to rely only", - "upon my cunning and", - "instincts. No longer have", - "I that which makes me", - "Glorious to others, but I", - "have only that which I", - "need to survive. I may no", - "longer rely upon myself, I" - ), - new BookPageInfo - ( - "must rely upon others", - "for my survival. My", - "journey to Humility has", - "only made me realize even", - "more how Blessed I have", - "been." - ), - new BookPageInfo - ( - "Chapter 10: Onward to", - "Honesty", - "", - "Now the journey will turn", - "South towards the Island", - "of Ice. However, my", - "voyages and excursions", - "into the jungle have made" - ), - new BookPageInfo - ( - "me quite tired, so I will", - "camp here beside a river", - "near the Shrine of", - "Humility for the night. I", - "awake the next morning", - "refreshed and invigorated,", - "but also under attack! A", - "Headless One has noticed" - ), - new BookPageInfo - ( - "my rise from slumber and", - "attacks viciously. My", - "trusty cleaver was in my", - "hand instantly, but my", - "lack of skill with the", - "weapon delayed the death", - "of the creature. I", - "launched the Hollandia and" - ), - new BookPageInfo - ( - "set sail for the Island of", - "Ice, seeking the Shrine of", - "Honesty. As I sail the", - "vast oceans, I find myself", - "desiring the company of", - "my fellow man. Hopefully I", - "shall meet some kind of", - "traveller with whom I may" - ), - new BookPageInfo - ( - "exchange a few words.", - "Shortly I was landing my", - "boat on the North end of", - "the Island of Ice. I", - "quickly made my way", - "through snow across the", - "frigid tundra while trying", - "to keep warm. The Shrine" - ), - new BookPageInfo - ( - "of Honesty bid me", - "welcome as I felth the", - "warmth radiate throughout", - "me.", - "", - "Chapter 11: Honesty", - "", - "Honesty is to uphold and" - ), - new BookPageInfo - ( - "defend the truth at all", - "times. Furthermore,", - "Honesty requires us to", - "be fair and true to our", - "fellow man; not taking", - "undue advantage. Honesty", - "is a Virtue often lacking", - "in today's world. It seems" - ), - new BookPageInfo - ( - "as though people are out", - "to gain wealth with no", - "regard to Honesty", - "towards other people.", - "Honesty is the foundation", - "upon which trust is built.", - "If the foundation", - "crumbles, everything built" - ), - new BookPageInfo - ( - "upon it must fall. The", - "cold environment which", - "houses the Shrine of", - "Honesty is a testament", - "to its value in today's", - "society. The symbolic cold", - "and secluded location", - "shows us that only the" - ), - new BookPageInfo - ( - "most dedicated to", - "pursuing Honesty will", - "achieve it. May we all be", - "Honest with our fellow", - "man and remember to", - "treat them how we would", - "like to be treated." - ), - new BookPageInfo - ( - "Chapter 12: The Path to", - "Sacrifice.", - "", - "I made my way to the", - "West side of the Island", - "of Ice. From there I", - "launch the Hollandia and", - "sail slightly to the North" - ), - new BookPageInfo - ( - "and West. I land my boat", - "just East of the Shrine", - "of Sacrifice, so my road", - "is West. Although I enjoy", - "the sea, I am happy to", - "be back on the mainland", - "for the final three", - "Shrines." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public QuestOfVirtues() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public QuestOfVirtues( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Regarding Llamas - public class RegardingLlamas : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Regarding Llamas", "Simon", - new BookPageInfo - ( - " Llamas are curious", - "beasts, shaggy and", - "sought after for their", - "wool, yet of a", - "curiously arrogant", - "disposition reflected", - "in their eyes. They", - "live in mountainous" - ), - new BookPageInfo - ( - "areas, though who", - "may have first tamed", - "them is lost in the", - "mists of history.", - " 'Tis a well-known", - "fact that llamas can", - "indeed be tamed, and", - "used as grazing" - ), - new BookPageInfo - ( - "animals, for their", - "meat, and of course", - "for their wool. Yet", - "'tis lesser known that", - "their ornery", - "disposition and", - "tendency to spit at", - "those they dislike" - ), - new BookPageInfo - ( - "makes them appealing", - "guard creatures as", - "well, though they", - "have little sound with", - "which to sound an", - "alarum." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public RegardingLlamas() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public RegardingLlamas( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Talking to Wisps - public class TalkingToWisps : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Talking to Wisps", "Yorick ofMoonglow", - new BookPageInfo - ( - "This volume was", - "sponsored by", - "donations from Lord", - "Blackthorn, ever a", - "supporter of", - "understanding the", - "other sentient races", - "of Britannia." - ), - new BookPageInfo - ( - "-", - " Wisps are the most", - "intelligent of the", - "nonhuman races", - "inhabiting Britannia.", - "'Tis claimed by the", - "great sages that", - "someday we shall be" - ), - new BookPageInfo - ( - "able to converse with", - "them openly in our", - "native", - "tongue--indeed, we", - "must hope that wisps", - "learn our language,", - "for it is not possible", - "for humans to" - ), - new BookPageInfo - ( - "pronounce wispish!", - " The wispish", - "language seems to", - "only contain one", - "vowel, the letter Y.", - "However, the letters", - "W, C, M, and L seem", - "to be treated" - ), - new BookPageInfo - ( - "grammatically as", - "vowels, and in", - "addition every letter", - "is followed by what", - "sounds to the human", - "ear like a glottal stop.", - "It is possible that the", - "glottal stop is" - ), - new BookPageInfo - ( - "considered a vowel as", - "well.", - " Wisps do make use", - "of what sound to us", - "like pitch and", - "emphasis shifts", - "similar to", - "exclamations and" - ), - new BookPageInfo - ( - "questions.", - " The average word is", - "wispish seems to", - "consist of three", - "phonemes and three", - "glottal stops, plus", - "possibly a pitch shift.", - "It often sounds like a" - ), - new BookPageInfo - ( - "fire burning or", - "crackling. Some have", - "speculated that what", - "we are analyzing is", - "in fact nothing more", - "than the very air", - "crackling near the", - "wisp's glow, and not" - ), - new BookPageInfo - ( - "language, but this is", - "of course unlikely." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TalkingToWisps() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public TalkingToWisps( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Taming Dragons - public class TamingDragons : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Taming Dragons", "Wyrd Beastmaster", - new BookPageInfo - ( - " I have not much to", - "tell about dragons. The", - "sole time I approached", - "one with an eye", - "towards taming it,", - "my initial attempts at", - "calming it met with", - "failure. It fixed a" - ), - new BookPageInfo - ( - "massive beady eye", - "upon me, and began", - "its slithering", - "approach, intending no", - "doubt to insert me", - "into its maw and bear", - "down with its teeth.", - " However, as I was" - ), - new BookPageInfo - ( - "engaged in what", - "remains to this day", - "the most terrifying", - "combat of my life,", - "the dragon suddenly", - "whirled as if in a", - "panic, ran a short", - "distance, took off into" - ), - new BookPageInfo - ( - "the air, then", - "transformed into a", - "whirlwind. Lastly, it", - "exploded, showering", - "gouts of black blood", - "and heaving, stinking", - "flesh upon miles of", - "countryside. The" - ), - new BookPageInfo - ( - "fireball was massive,", - "enough to light a city,", - "I should surmise.", - " I never did discover", - "the exact cause of", - "this strange behavior,", - "except to assume that", - "it was not typical for" - ), - new BookPageInfo - ( - "this reptilian species.", - "My best guesses", - "revolve around a", - "magical fracture in", - "the nature of reality,", - "which is far too", - "esoteric a territory", - "for one of my limited" - ), - new BookPageInfo - ( - "scholarship.", - " Hence my basic", - "advice to those who", - "seek to tame a", - "dragon-be sure that", - "thou hast mastered", - "the twin skills of", - "taming animals, and" - ), - new BookPageInfo - ( - "running away very", - "very fast." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TamingDragons() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public TamingDragons( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Bold Stranger - public class BoldStranger : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Bold Stranger", "Old Fabio the Poor", - new BookPageInfo - ( - " In a time before", - "time, the Gods that Be", - "assembled a group of", - "artisans, craftsmen", - "and lore masters", - "(for, yes, even in", - "those days, art", - "existed) to create the" - ), - new BookPageInfo - ( - "world of Sosaria. To", - "this group, the gods", - "gave a tiny world,", - "Rytabul, in which to", - "test their works, to", - "see if they were of", - "the quality desired", - "for the true world in" - ), - new BookPageInfo - ( - "which they would be", - "placed. And though", - "the gods were tight", - "fisted with their gold,", - "this small crew", - "worked hard and long,", - "and were happy in", - "their tasks." - ), - new BookPageInfo - ( - " A small corner of", - "Rytabul had been", - "claimed by the artisan", - "Selrahc the Slow.", - "Though he was not", - "the fastest of the", - "assembled workers,", - "the gods smiled upon" - ), - new BookPageInfo - ( - "his work, even", - "presenting him with", - "a mystic talisman", - "proclaiming his work", - "the best among the", - "newer artisans. And", - "so Selrahc went about", - "his business, creating" - ), - new BookPageInfo - ( - "hundreds of designs", - "which would one day", - "add color and variety", - "to Sosaria.", - " One day a", - "stranger appeared to", - "Selrahc. His chest", - "was bare and he wore" - ), - new BookPageInfo - ( - "trousers of the", - "brightest green, and", - "wherever he went,", - "plants grew in his", - "footsteps. This", - "caused Selrahc no end", - "of trouble, the", - "stranger always" - ), - new BookPageInfo - ( - "looking over his", - "shoulder, and the", - "plants sprouting in", - "places Selrahc", - "required to ply his", - "art. And so Selrahc", - "approached the", - "stranger and bade" - ), - new BookPageInfo - ( - "him speak. But this", - "man in green", - "remained silent.", - "Selrahc pleaded with", - "the stranger to give", - "his name, and would", - "he please leave", - "Selrahc to his work." - ), - new BookPageInfo - ( - "But this mysterious", - "stranger remained", - "mute.", - " This angered", - "Selrahc mightily. Who", - "was this silent man,", - "interfering with", - "tasks the gods" - ), - new BookPageInfo - ( - "themselves had", - "entrusted to Selrahc?", - "In an attempt to", - "embarrass this", - "interloper, Selrahc", - "stole his green", - "trousers, leaving him", - "naked and open to" - ), - new BookPageInfo - ( - "comments about his", - "very manhood, and", - "still the stranger", - "would not speak,", - "would not leave this", - "tiny corner of", - "Rytabul.", - " Vexed to his very" - ), - new BookPageInfo - ( - "limits, Selrahc took", - "his war axe and", - "smote the silent one", - "mightily, again and", - "again, until the silent", - "stranger ran away,", - "having never said a", - "word, and never" - ), - new BookPageInfo - ( - "showed himself in", - "Rytabul again.", - " Thus endeth the", - "tale of the bold", - "stranger." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public BoldStranger() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public BoldStranger( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Burning of Trinsic - public class BurningOfTrinsic : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Burning of Trinsic", "Japheth of Trinsic", - new BookPageInfo - ( - " 'Twas a sight to", - "see, the sunlight", - "falling lightly on the", - "sandstone walls of", - "Trinsic 'pon a", - "morning in spring.", - " Children ran along", - "the parapets and" - ), - new BookPageInfo - ( - "walkways, their", - "laughter and running", - "providing music to the", - "daybreak, despite", - "their oft-ragged", - "clothing.", - " And I was one of", - "those young ones," - ), - new BookPageInfo - ( - "letting my joy rise", - "up to the skies.", - " Little did we all", - "know of the darker", - "days that would lie", - "ahead, for we were", - "too young.", - " Had we but gained" - ), - new BookPageInfo - ( - "access to the quiet", - "councils held in the", - "Paladin tower as it", - "faced the sea,", - "councils lit by", - "candlelight and", - "worry, we would", - "have learned more of" - ), - new BookPageInfo - ( - "the fears of", - "imminent attack from", - "the forest, where", - "foul creatures born", - "of dank caves and", - "darkness were", - "marauding ever more", - "often into the lands" - ), - new BookPageInfo - ( - "around Trinsic's", - "moat.", - " But we were", - "children! The", - "parapets and the moat", - "were places to play,", - "not stout defenses,", - "and we gave no" - ), - new BookPageInfo - ( - "thought to the", - "necessities that must", - "have required their", - "construction.", - " We used to reach", - "the sheltered", - "orchards on the lee", - "side of the parapet" - ), - new BookPageInfo - ( - "walls, where the", - "southern river cut", - "through the city, by", - "swimming across the", - "water.", - " The rich folk who", - "lived in the great", - "manses there would" - ), - new BookPageInfo - ( - "shout from their", - "windows and shake", - "their fists, for we", - "would run through", - "their gardens and", - "tear up the delicate", - "foxgloves and", - "orfleurs with our" - ), - new BookPageInfo - ( - "unshod dirty feet.", - "Then we would dive", - "into the water and", - "splash merrily to the", - "fruit trees.", - " The southern", - "river lazily slid", - "under the an ungated" - ), - new BookPageInfo - ( - "arch in the mighty", - "wall, and we would", - "lay on the grassy", - "bank and watch it", - "gurgle by the lily", - "pads.", - " That spring that", - "pleasant spot became" - ), - new BookPageInfo - ( - "the doorway through", - "which our city of", - "Trinsic let in the", - "monstrous deformed", - "humanoids that", - "savaged us. I lay upon", - "that grassy bank and", - "watched them wade" - ), - new BookPageInfo - ( - "in, their coarse hair", - "wet and matted, algae", - "and muck festooning", - "their wild brows.", - " They caught sight", - "of a quicksilver girl", - "with bright blond hair", - "and lively eyes. Her" - ), - new BookPageInfo - ( - "name was Leyla, and", - "that spring I had held", - "fond dreams of", - "holding her hand and", - "sharing flavored ice", - "while dangling our", - "feet off the small", - "bridge by Smugglers" - ), - new BookPageInfo - ( - "Gate.", - " And I said nothing", - "when they caught", - "her, and did not cry", - "out when they", - "dragged her off", - "through that breach in", - "our wall, and did not" - ), - new BookPageInfo - ( - "warn the city when I", - "saw the helmeted orc", - "captains call the", - "charge upon the", - "mansions.", - " Blame me not, for", - "I was but a child, and", - "one who hid in the" - ), - new BookPageInfo - ( - "branches of the peach", - "trees, all a-tremble", - "whilst I watched the", - "smoke rise from Sean", - "the tailor's, and fire", - "lash out at the roof of", - "witchy Eleanor's", - "tavern." - ), - new BookPageInfo - ( - " To this day I have", - "had no word of", - "Leyla, and to this", - "day the smell of", - "burning wood can", - "conjure terrible", - "dreams. Yet with the", - "eyes of adulthood, 'tis" - ), - new BookPageInfo - ( - "possible to examine", - "the flaws in the", - "defense of Trinsic on", - "that fateful day, and", - "the reasons why our", - "walls are now", - "double-thick, and", - "why our buildings" - ), - new BookPageInfo - ( - "are now built as", - "fortresses within a", - "somber fortified city.", - " While I can look", - "out from the top of", - "the new Paladin", - "tower, and spy the", - "mighty white sails" - ), - new BookPageInfo - ( - "across the barrier", - "island, and can", - "descry the small", - "hollow south of the", - "city where gypsies", - "are wont to camp, I", - "can also envision the", - "city as it might be" - ), - new BookPageInfo - ( - "burning, and I bless", - "the bargain we made:", - "space for safety,", - "grace for sturdiness,", - "and wood for stone.", - " Whilst I live, I", - "shall not see Trinsic", - "burn, and no more" - ), - new BookPageInfo - ( - "cries of little girls", - "will haunt the sleep", - "of our fair citizens.", - " - Japheth, Paladin", - "Guildmaster of the", - "City of Trinsic" - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public BurningOfTrinsic() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public BurningOfTrinsic( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Fight - public class TheFight : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Fight", "M. de la Garza", - new BookPageInfo - ( - " A cold autumn's", - "morning with misty", - "fog secures a dozen", - "brave knights,", - "supplying hidden", - "shelter from prying", - "eyes deep in the", - "foothills of the" - ), - new BookPageInfo - ( - "vibrant valley.", - "Dragons soar like", - "fierce warriors,", - "circling around and", - "around, then roaring", - "like thunder, rallying", - "all that listen. The", - "dragons land swiftly" - ), - new BookPageInfo - ( - "beside the proud", - "warriors, bending", - "necks and extending", - "wings, lifting black", - "claws and allowing", - "valiant fighters to", - "ride forth and win an", - "arisen battle. The" - ), - new BookPageInfo - ( - "increasing winds", - "silence the sounds of", - "combat, and they", - "fight, standing their", - "ground like mothers", - "protecting their", - "childern, bright", - "armor flashing as" - ), - new BookPageInfo - ( - "each one falls.", - " A cold autumn's", - "evening with misty", - "fog cradles a dozen", - "battered corpses of", - "knights, creasing", - "them in currents of", - "winds that run deep" - ), - new BookPageInfo - ( - "in the foothills of the", - "desolate valley.", - "Dragons glide like", - "silent angels, circling", - "around and around,", - "then calling like", - "banshees; keening", - "cries of mourning." - ), - new BookPageInfo - ( - "The dragons land", - "heavily beside the", - "peaceful bodies,", - "bending necks and", - "extending wings,", - "lifting black claws", - "and allowing valiant", - "fighters to ride forth" - ), - new BookPageInfo - ( - "and win an arisen", - "battle. The increasing", - "winds silence the", - "sounds of combat, and", - "they fight, standing", - "their ground like", - "mothers protecting", - "their childern, bright" - ), - new BookPageInfo - ( - "armor flashing as", - "each one falls.", - " A cold autumn's", - "evening with misty", - "fog cradles a dozen", - "battered corpses of", - "knights, creasing", - "them in currents of" - ), - new BookPageInfo - ( - "winds that run deep", - "in the foothills of the", - "desolate valley.", - "Dragons glide like", - "silent angels, circling", - "around and around,", - "then calling like", - "banshees; keening" - ), - new BookPageInfo - ( - "cries of mourning.", - "The dragons land", - "heavily beside the", - "peaceful bodies,", - "bending necks and", - "extending wings,", - "lifting black claws", - "and pinching the" - ), - new BookPageInfo - ( - "sacred ground and", - "new eternal home.", - "The dying winds", - "whistle among the", - "dead in somber", - "procession, and they", - "lie, grasping weapons", - "to protect themselves" - ), - new BookPageInfo - ( - "like knights still in", - "battle, shattered", - "armor shining like", - "newly born stars." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TheFight() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public TheFight( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Life of a Travelling Minstrel - public class LifeOfATravellingMinstrel : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Life of a Travelling Minstrel", "Sarah of Yew", - new BookPageInfo - ( - " While 'tis true that", - "the musician who", - "seeketh only to make", - "sweet music for", - "herself and for", - "others needs little", - "more than some", - "talent, and stern" - ), - new BookPageInfo - ( - "practice at the chosen", - "instrument, those of", - "us who seek the open", - "road shall find indeed", - "that a greater skill is", - "required. Herein", - "discover those secrets", - "which I have learned" - ), - new BookPageInfo - ( - "over the years as an", - "itinerant performer...", - " Once I was in", - "Jhelom, and", - "accidentally angered a", - "bravo of some local", - "repute, whose blade", - "flickered all too" - ), - new BookPageInfo - ( - "eagerly near my", - "slender neck (for I", - "was young then).", - "After various threats", - "to \"ruin my pretty", - "face\" this bravo", - "grabbed my arm in a", - "most unseemly" - ), - new BookPageInfo - ( - "fashion and tossed", - "me into a barbaric", - "enclosure locally", - "entitled a dueling pit.", - "My plaintive cries", - "for help went", - "unheeded by the", - "guards, for the" - ), - new BookPageInfo - ( - "inhabitants of Jhelom", - "are eager indeed to", - "measure fighting", - "prowess at any time!", - " What saved me was", - "the ability to", - "improvise a melody", - "and tune that" - ), - new BookPageInfo - ( - "satirized the", - "proceedings, and", - "sufficiently angered", - "an onlooker to prod", - "him to coming to my", - "defense. Once that", - "fight was underway,", - "I was able to make" - ), - new BookPageInfo - ( - "good my escape.", - "Hence, I regard the", - "ability to incite fights", - "as indispensable to", - "the prudent bard.", - " Upon another", - "occasion, 'twas the", - "obverse side of that" - ), - new BookPageInfo - ( - "coin which saved me,", - "for I was being held", - "prisoner by a", - "particularly nasty", - "band of ruffians who", - "had seized me", - "unawares from the", - "road to Vesper." - ), - new BookPageInfo - ( - " They had worked", - "themselves into a", - "frenzy and were", - "ready to attack and I", - "fear, tear me limb", - "from limb, when I", - "began to sing", - "frantically, tapping" - ), - new BookPageInfo - ( - "my falled drum with", - "my tied up feet. The", - "melody developed into", - "a soothing one, and", - "the brigands slowly", - "calmed down to the", - "extent of apologizing,", - "and they let me go!" - ), - new BookPageInfo - ( - " A final example I", - "would pray you grant", - "your attention: once I", - "was lost upon a large", - "isle far to the east of", - "the mainland, well", - "beyond Serpent's", - "Hold, where lava" - ), - new BookPageInfo - ( - "made its sluggish", - "way across the", - "surface landscape.", - "And this accursed", - "land was filled with", - "vile beasts and", - "cunning dragons.", - " I was being pursued" - ), - new BookPageInfo - ( - "by one of said fell", - "dragons when I found", - "myself trapped. I", - "quickly skirted a", - "bubbling pool of molten", - "rock and attempted to", - "hide.", - " The dragon scented" - ), - new BookPageInfo - ( - "me and was", - "preparing to skirt the", - "pool, when I began to", - "play a lusty tune", - "upon my lute that", - "attracted its attention.", - "Mesmerized and", - "enticed by the" - ), - new BookPageInfo - ( - "melody, it stepped", - "directly toward sme,", - "and into the", - "lava-where its foot", - "was so burned that it", - "quickly hopped away,", - "undignified and", - "annoyed." - ), - new BookPageInfo - ( - " 'Tis my fond hope", - "that other travelling", - "minstrels shall learn", - "from my experiences", - "and apply themselves", - "to practicing these", - "skills in order to", - "preserve life and" - ), - new BookPageInfo - ( - "limb." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public LifeOfATravellingMinstrel() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public LifeOfATravellingMinstrel( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Major Trade Associations - public class MajorTradeAssociation : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Major Trade Associations", "Pieter of Vesper", - new BookPageInfo - ( - " There are ten major", - "trade associations that", - "operate legitimately in", - "the lands of Britannia", - "and among its trading", - "partners. Many of", - "these guilds are", - "divided into local or" - ), - new BookPageInfo - ( - "specialty subguilds,", - "who use the same", - "colors but vary the", - "heraldic pattern.", - " There are many", - "lesser trade", - "associations that have", - "closed membership," - ), - new BookPageInfo - ( - "and one can join them", - "only by invitation.", - "Beltran's Guide to", - "Guilds is the", - "definitive text on the", - "full range of guilds", - "and other associations", - "in Britannia, and I" - ), - new BookPageInfo - ( - "heartily recommend", - "it.", - " In what follows I", - "have attempted to", - "bring together the", - "known information", - "regarding these", - "guilds. I offer thee" - ), - new BookPageInfo - ( - "the name, typical", - "membership, heraldic", - "colors, known", - "specialty", - "organizations within", - "the larger guild, and", - "any known", - "affiliations to other" - ), - new BookPageInfo - ( - "guilds, which often", - "occur because of", - "trade reasons.", - "", - "The Guild of Arcane", - "Arts", - "Members: alchemists", - "and wizards" - ), - new BookPageInfo - ( - "Colors: blue and purple", - "Subguilds: Illusionists,", - "Mages, Wizards", - "Affiliations: Healer's", - "Guild", - "", - "The Warrior's Guild", - "Members:" - ), - new BookPageInfo - ( - "mercenaries,", - "soldiery, guardsmen,", - "weapons masters,", - "paladins.", - "Colors: Blue and red", - "Subguilds: Cavalry,", - "Fighters, Warriors", - "Affiliations: League" - ), - new BookPageInfo - ( - "of Rangers", - "", - "League of Rangers", - "Members: rangers,", - "bowyers, animal", - "trainers", - "Colors: Red, gold and", - "blue" - ), - new BookPageInfo - ( - "", - "Guild of Healers", - "Members: healers", - "Colors: Green, gold,", - "and purple", - "Affiliations: Guild of", - "Arcane Arts" - ), - new BookPageInfo - ( - "Mining Cooperative", - "Members: miners", - "Colors: blue and black", - "checkers, with a gold", - "cross", - "Affiliations: Order of", - "Engineers" - ), - new BookPageInfo - ( - "Merchants'", - "Association", - "Members:", - "innkeepers,", - "tavernkeepers,", - "jewelers,", - "provisioners", - "Colors: gold coins on a" - ), - new BookPageInfo - ( - "green field for", - "Merchants. White", - "and green for the", - "others.", - "Subguilds: Barters,", - "Provisioners,", - "Traders, Merchants" - ), - new BookPageInfo - ( - "Order of Engineers", - "Members: tinkers and", - "engineers", - "Colors: Blue, gold, and", - "purple vertical bars", - "Affiliations: Mining", - "Cooperative" - ), - new BookPageInfo - ( - "Society of Clothiers", - "Members: tailors and", - "weavers", - "Colors: Purple, gold,", - "and red horizontal", - "bars", - "", - "Maritime Guild" - ), - new BookPageInfo - ( - "Members: fishermen,", - "sailors, mapmakers,", - "shipwrights", - "Colors: blue and white", - "Subguilds:", - "Fishermen, Sailors,", - "Shipwrights" - ), - new BookPageInfo - ( - "Bardic Collegium", - "Members: bards,", - "musicians,", - "storytellers, and other", - "performers", - "Colors: Purple, red", - "and gold checkerboard" - ), - new BookPageInfo - ( - "Society of Thieves", - "Members: beggars,", - "cutpurses, assassins,", - "and brigands", - "Colors: red and black", - "Subguilds: Rogues", - "(beggars), Assassins,", - "Thieves" - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public MajorTradeAssociation() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public MajorTradeAssociation( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Rankings of Trades - public class RankingsOfTrades : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Rankings of Trades", "Lord Higginbotham", - new BookPageInfo - ( - " Whilst 'tis true that", - "within each trade, one", - "finds differing titles", - "and accolades granted", - "to the members of a", - "given guild,", - "nonetheless for the", - "betterment of trade" - ), - new BookPageInfo - ( - "and understanding,", - "we must have a", - "commonality of", - "titling.", - " For those who may", - "find themselves", - "ignorant of the finer", - "distinctions between a" - ), - new BookPageInfo - ( - "three-knot member of", - "the Sailors' Maritime", - "Association and a", - "second thaumaturge,", - "this book shall serve", - "as a simple", - "introduction to the", - "common cant used" - ), - new BookPageInfo - ( - "when members of", - "differing guilds and", - "trade organizations", - "must trade with each", - "other and must", - "establish relative", - "credentials.", - " Neophyte" - ), - new BookPageInfo - ( - "Has shown interest", - "in learning the craft", - "and some meager", - "talent.", - " Novice", - "Is practicing basic", - "skills but has not been", - "admitted to full" - ), - new BookPageInfo - ( - "standing.", - " Apprentice", - "A student of the", - "discipline.", - " Journeyman", - "Warranted to practice", - "the discipline under", - "the eyes of a tutor." - ), - new BookPageInfo - ( - " Expert", - "A full member of the", - "guild.", - " Adept", - "A member of the", - "guild qualified to", - "teach others.", - " Master" - ), - new BookPageInfo - ( - "Acknowledged as", - "qualified to lead a hall", - "or business.", - " Grandmaster", - "Rarely a permanent", - "title, granted in", - "common parlance to", - "those who have" - ), - new BookPageInfo - ( - "shown extreme", - "mastery of their", - "craft recently." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public RankingsOfTrades() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public RankingsOfTrades( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region The Wild Girl of the Forest - public class WildGirlOfTheForest : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "The Wild Girl of the Forest", "Horace the Trader", - new BookPageInfo - ( - " Her name was", - "Leyla, she said, and", - "her hair was braided", - "wild with creepers", - "and thorns. I", - "marveled that they", - "did not hurt her, but", - "when I asked, she but" - ), - new BookPageInfo - ( - "shrugged and let her", - "eyes roam once more", - "across the woods.", - "Though I had my", - "hands securely", - "fastened by her", - "ropes, I itched to", - "reach out and comb" - ), - new BookPageInfo - ( - "that unruly golden", - "mane, dirtied and", - "leaf-ridden.", - " Her provenance,", - "she told me over", - "nights illumined by", - "campfires, was once", - "the city of Trinsic." - ), - new BookPageInfo - ( - "She claimed to have", - "been kidnapped and", - "raised by orcs, which", - "I judged an unlikely", - "tale, for all know orcs", - "delight in eating the", - "meat of honest folk.", - "When I told her this," - ), - new BookPageInfo - ( - "she laughed a fey", - "laugh, and gaily", - "admitted that honest", - "she was not, for oft", - "had she stolen folk", - "away from caravans", - "to loot their", - "possessions from an" - ), - new BookPageInfo - ( - "unconscious body!", - " At this, I began to", - "fear for my life, and", - "her smile seemed full", - "of teeth sharper than", - "a human ought to", - "have, for the tale of", - "orcish raising had" - ), - new BookPageInfo - ( - "struck fear into the", - "marrow of my bones.", - "\"Wilt thou eat me?\" I", - "asked, a-tremble,", - "fearing the answer.", - " And she cocked", - "her head at me, like a", - "wild animal facing a" - ), - new BookPageInfo - ( - "word that it dost not", - "understand, and the", - "fixity in her eyes", - "was a glimpse into", - "the deeper reaches of", - "the Abyss. But she", - "finally grunted, and", - "said, \"Nay,\" in a" - ), - new BookPageInfo - ( - "voice that recalled to", - "me a child. \"Nay,\"", - "she said, \"for thou", - "dost remind me of a", - "boy I knew once,", - "when I was a girl", - "who played in a city", - "of great sandstone" - ), - new BookPageInfo - ( - "walls, before I was", - "taken. He had sandy", - "hair like thee, and I", - "dreamt as a child of", - "holding his hand and", - "sharing flavored ice.", - "His name was", - "Japheth.\"" - ), - new BookPageInfo - ( - " The next morning", - "she let me go,", - "stripped of my pouch", - "and clothes, and bade", - "me run through the", - "woods, and to fear", - "recapture, for surely", - "her heart would not" - ), - new BookPageInfo - ( - "soften again. 'Twas a", - "fearful run, and I", - "came to the road to", - "Yew with welts and", - "scratches run", - "rampant crost my", - "skin, but I did not see", - "her again." - ), - new BookPageInfo - ( - " Oft have I", - "wondered of the boy", - "named Japheth, and", - "whether he", - "remembers a girl who", - "lived in sandstone", - "walls. The only", - "Japheth I know is the" - ), - new BookPageInfo - ( - "Guildmaster of", - "Paladins who died", - "last year warring", - "amidst the orcs, and", - "though he had indeed", - "sandy hair, I cannot", - "picture him side by", - "side with a feral girl" - ), - new BookPageInfo - ( - "whose tongue has", - "tasted of human", - "flesh.", - " Yet the paths of", - "fate are strange", - "indeed, and I suppose", - "'tis possible that this", - "paladin died" - ), - new BookPageInfo - ( - "defending his", - "remembered lady's", - "honor, unknowingly", - "struck down by the", - "orc that she called", - "father." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public WildGirlOfTheForest() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public WildGirlOfTheForest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Treatise on Alchemy - public class TreatiseOnAlchemy : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Treatise on Alchemy", "Felicia Hierophant", - new BookPageInfo - ( - " The alchemical", - "arts are notable for", - "their deceptive", - "simplicity. 'Tis true", - "that to our best", - "knowledge currently,", - "there are but eight", - "valid potions that can" - ), - new BookPageInfo - ( - "be made (though I", - "emphasize that new", - "discoveries may", - "always await).", - "However, the delicate", - "balance of confecting", - "the potions is", - "difficult indeed, and" - ), - new BookPageInfo - ( - "requires great skill.", - " To give thee an", - "example of the", - "simpler potions that", - "can be created by", - "those well-versed in", - "the subtleties of", - "alchemy:" - ), - new BookPageInfo - ( - " Black pearl, that", - "rare substance that is", - "oft found lying", - "unannounced upon the", - "surface of the", - "ground, when", - "properly crushed", - "with mortar and" - ), - new BookPageInfo - ( - "pestle, can yield a", - "fine powder. Said", - "powder in the proper", - "proportions when", - "mixed via the", - "alchemical arts can", - "yield a wonderfully", - "refreshing drink." - ), - new BookPageInfo - ( - " The revolting blood", - "moss so gingerly", - "scraped off of", - "windowsills by", - "fastidious housewives", - "is but a tiny cousin to", - "the wilder version,", - "which when properly" - ), - new BookPageInfo - ( - "prepared yields a", - "magical liquid that for", - "a time can make the", - "imbiber a more agile", - "and dextrous", - "individual.", - " However, beware", - "of the deadly" - ), - new BookPageInfo - ( - "nightshade, for it", - "yields a deceptively", - "sweet-tasting poison", - "that can prove highly", - "fatal to the drinker,", - "and in fact is also", - "used by assassins to", - "coat their blades." - ), - new BookPageInfo - ( - "Fortunately, this", - "latter art of poisoning", - "is little known!", - " There is much to", - "reward the student of", - "alchemy, indeed. The", - "rumours of longtime", - "alchemists losing" - ), - new BookPageInfo - ( - "their hair and", - "acquiring an", - "unhealthy pallor, not", - "to mention unsightly", - "blotches upon their", - "once-fair skin, are", - "unhappily, true. Yet", - "the joys of the mind" - ), - new BookPageInfo - ( - "make up for the", - "complete loss of", - "interest that others", - "may have in thee as", - "an object of", - "courtship, and I have", - "never regretted that", - "choice. Honestly," - ), - new BookPageInfo - ( - "truly. Not once." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public TreatiseOnAlchemy() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public TreatiseOnAlchemy( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Virtue - public class VirtueBook : BaseBook - { - public static readonly BookContent Content = new BookContent - ( - "Virtue", "Lord British", - new BookPageInfo - ( - " Within this world", - "live people with many", - "different ideals, and", - "this is good. Yet what", - "is it within the people", - "of our land that sorts", - "out the good from the", - "evil, the cherished" - ), - new BookPageInfo - ( - "form the disdained?", - "Virtue, I say it is,", - "and virtue is the", - "logical outcome of a", - "people who wish to", - "live together in a", - "bonded society.", - " For without Virtues" - ), - new BookPageInfo - ( - "as a code of conduct", - "which people maintain", - "in their relations", - "with each other, the", - "fabric of that society", - "will become weakened.", - "For a society to grow", - "and prosper for all," - ), - new BookPageInfo - ( - "each must grant the", - "others a common base", - "of consideration.", - " I call this base the", - "Virtues. For though", - "one person might gain", - "personal advantage by", - "breaching such a" - ), - new BookPageInfo - ( - "code, the society as a", - "whole would suffer.", - " There are three", - "Principle Virtues that", - "should guide people to", - "enlightenment. These", - "are: Truth, Love and", - "Courage. From all the" - ), - new BookPageInfo - ( - "infinite reasons one", - "may have to found an", - "action, such as greed", - "or charity, envy or", - "pity, the three", - "Principle Virtues", - "stand out.", - " In fact all other" - ), - new BookPageInfo - ( - "virtues and vices can", - "be show to be built", - "from these principles", - "and their opposite", - "corruption's of", - "Falsehood, Hatred and", - "Cowardice. These", - "three Principles can" - ), - new BookPageInfo - ( - "be combined in eight", - "ways, which I will", - "call the eight virtues.", - "The eight virtues", - "which we should", - "build our society upon", - "follow.", - " Truth alone becomes" - ), - new BookPageInfo - ( - "Honesty, for without", - "honesty between our", - "people, how can we", - "build the trust which", - "is needed to", - "maximize our", - "successes.", - " Love alone becomes" - ), - new BookPageInfo - ( - "compassion, for at", - "some time or another", - "all of us will need the", - "compassion of others,", - "and most likely", - "compassion will be", - "shown to those who", - "have shown it." - ), - new BookPageInfo - ( - " Courage alone", - "becomes Valor,", - "without valor our", - "people will never", - "reach into the", - "unknown or to the", - "risky and will never", - "achieve." - ), - new BookPageInfo - ( - " Truth tempered by", - "Love give us Justice,", - "for only in a loving", - "search for the truth", - "can one dispense fair", - "Justice, rather than", - "create a cold and", - "callous people." - ), - new BookPageInfo - ( - " Love and Courage", - "give us Sacrifice, for", - "a people who love each", - "other will be willing", - "to make personal", - "sacrifices to help", - "other in need, which", - "one day, may be" - ), - new BookPageInfo - ( - "needed in return.", - " Courage and Truth", - "give us Honor, great", - "knights know this", - "well, that chivalric", - "honor can be found", - "by adhering to this", - "code of conduct." - ), - new BookPageInfo - ( - " Combining Truth,", - "Love and Courage", - "suggest the virtue of", - "Spirituality the virtue", - "that causes one to be", - "introspective, to", - "wonder about ones", - "place in this world" - ), - new BookPageInfo - ( - "and whether one's", - "deeds will be recorded", - "as a gift to the world", - "or a plague.", - " The final Virtue is", - "more complicated. For", - "the eighth combination", - "is that devoid of" - ), - new BookPageInfo - ( - "Truth, Love or", - "Courage which can", - "only exist in a state", - "of great Pride, which", - "of course is not a", - "virtue at all. Perhaps", - "this trick of fate is a", - "test to see if one can" - ), - new BookPageInfo - ( - "realize that the true", - "virtue is that of", - "Humility. I feel that", - "the people of", - "Magincia fail to see", - "this to such a degree", - "that I would not be", - "surprised if some ill" - ), - new BookPageInfo - ( - "fate awaited their", - "future.", - " Thus from the", - "infinite possibilities", - "which spawned the", - "Three Principles of", - "Truth, Love and", - "Courage, come the" - ), - new BookPageInfo - ( - "Eight Virtues of", - "Honesty, Compassion,", - "Valor, Justice,", - "Sacrifice, Honor,", - "Spirituality, and", - "Humility." - ) - ); - - public override BookContent DefaultContent => Content; - - [Constructible] - public VirtueBook() : base( Utility.Random( 0xFEF, 2 ), false ) - { - } - - public VirtueBook( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion -} + #region A Grammar of Orcish + + public class GrammarOfOrcish : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "A Grammar of Orcish", "Yorick of Yew", + new BookPageInfo + ( + "This volume, and", + "others in the series,", + "are sponsored by", + "donations from Lord", + "Blackthorn, ever a", + "supporter of", + "understanding the", + "other sentient races" + ), + new BookPageInfo + ( + "of Britannia.", + "-", + "", + " The Orcish tongue", + "may fall unpleasingly", + "'pon the ear, yet it", + "has within it a", + "complex grammar oft" + ), + new BookPageInfo + ( + "misunderstood by", + "those who merely", + "hear the few broken", + "words of English our", + "orcish brothers", + "manage without", + "education.", + " These are the basic" + ), + new BookPageInfo + ( + "rules of orcish:", + " Orcish has five", + "tenses: present, past,", + "future imperfect,", + "present interjectional,", + "and prehensile.", + " Examples: gugroflu,", + "gugrofloog, gugrobo," + ), + new BookPageInfo + ( + "gugroglu!, gugrogug.", + " All transitive verbs", + "in the prehensile", + "tense end in \"ug.\"", + " Examples:", + "urgleighug,", + "biggugdaghgug,", + "curdakalmug." + ), + new BookPageInfo + ( + " All present", + "interjectional", + "conjugations start", + "with the letter G", + "unless the contain the", + "third declensive", + "accent of the letter U.", + " Examples:" + ), + new BookPageInfo + ( + "ghothudunglug, but not", + "azhbuugub.", + " The past tense can", + "only refer to events", + "since the last meal,", + "but the prehensile", + "tense can refer to", + "any event within" + ), + new BookPageInfo + ( + "reach.", + " The present tense", + "is conjugated like the", + "future imperfect", + "tense, when the", + "interrogative mode is", + "used by pitching the", + "sound a quarter-tone" + ), + new BookPageInfo + ( + "higher.", + "Orcish hath no", + "concept of person, as", + "in first person, third", + "person, I, we, etc.", + " Orcish grammar", + "relies upon the three", + "cardinal rules of" + ), + new BookPageInfo + ( + "accretion, prefixing,", + "and agglutination, in", + "addition to pitch. In", + "the former, phonemes", + "combine into larger", + "words which may", + "contain full phrasal", + "significance. In the" + ), + new BookPageInfo + ( + "second, prefixing", + "specific phonetic", + "sounds changes the", + "subject of the", + "sentence into object,", + "interrogative,", + "addressed individual,", + "or dinner." + ), + new BookPageInfo + ( + " Agglutination occurs", + "whenever four of the", + "same letter are", + "present in a word, in", + "which case, any two", + "of them may be", + "removed or slurred.", + " Pitch changes the" + ), + new BookPageInfo + ( + "phoneme value of", + "individual syllables,", + "thus completely", + "altering what a word", + "may mean. The", + "classic example is", + "\"Aktgluthugrot", + "bigglogubuu" + ), + new BookPageInfo + ( + "dargilgaglug lublublub\"", + "which can mean \"You", + "are such a pretty", + "girl,\" \"My mother ate", + "your primroses,\" or", + "\"Jellyfish nose paints", + "alms potato,\"", + "depending on pitch." + ), + new BookPageInfo + ( + " Orcish poetry often", + "relies upon repeating", + "the same phrase in", + "multiple pitches, even", + "changing pitch", + "midword. None of", + "this great art is", + "translatable." + ), + new BookPageInfo + ( + " The orcish language", + "uses the following", + "vowels: ab, ad, ag, akt,", + "at, augh, auh, azh, e,", + "i, o, oo, u, uu. The", + "vowel sound a is not", + "recognized as a vowel", + "and does not exist in" + ), + new BookPageInfo + ( + "their alphabet.", + "The orcish alphabet is", + "best learned using the", + "classic rhyme", + "repeated at 23", + "different pitches:", + " Lugnog ghu blat", + "suggaroglug," + ), + new BookPageInfo + ( + "Gaghbuu dakdar ab", + "highugbo,", + " Gothnogbuim ad", + "gilgubbugbuilug", + "Bilgeaugh thurggulg", + "stuiggro!", + "", + "A translation of the" + ), + new BookPageInfo + ( + "first pitch:", + "Eat food, the first", + "letter is ab,", + "Kill people, next letter", + "is ad,", + "I forget the rest", + "But augh is in there", + "somewhere!" + ), + new BookPageInfo + ( + "", + " What follows is a", + "complete phonetic", + "library of the orcish", + "language:", + "ab, ad, ag, akt, alm,", + "at, augh, auh, azh,", + "ba, ba, bag, bar, baz," + ), + new BookPageInfo + ( + "bid, bilge, bo, bog, bog,", + "brui, bu, buad, bug,", + "bug, buil, buim, bum,", + "buo, buor, buu, ca,", + "car, clog, cro, cuk,", + "cur, da, dagh, dagh,", + "dak, dar, deak, der,", + "dil, dit, dor, dre, dri," + ), + new BookPageInfo + ( + "dru, du, dud, duf,", + "dug, dug, duh, dun,", + "eag, eg, egg, eichel,", + "ek, ep, ewk, faugh,", + "fid, flu, fog, foo,", + "foz, fruk, fu, fub,", + "fud, fun, fup, fur,", + "gaa, gag, gagh, gan," + ), + new BookPageInfo + ( + "gar, gh, gha, ghat,", + "ghed, ghig, gho, ghu,", + "gig, gil, gka, glu, glu,", + "glug, gna, gno, gnu,", + "gol, gom, goth, grunt,", + "grut, gu, gub, gub,", + "gug, gug, gugh, guk,", + "guk," + ) + ); + + [Constructible] + public GrammarOfOrcish() : base(Utility.Random(0xFEF, 2), false) + { + } + + public GrammarOfOrcish(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region A Politic Call to Anarchy + + public class CallToAnarchy : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "A Politic Call to Anarchy", "Lord Blackthorn", + new BookPageInfo + ( + " Let it never be said", + "that I have aught as", + "quarrel with my liege", + "Lord British, for", + "indeed we be of the", + "best of friends,", + "sharing amicable", + "games of chess 'pon a" + ), + new BookPageInfo + ( + "winter's night, and", + "talking at length into", + "the wee hours of the", + "issues that affect the", + "realm of Britannia.", + " Yet true friendship", + "doth not prevent true", + "philosophical" + ), + new BookPageInfo + ( + "disagreement either.", + "While I view with", + "approval my lord's", + "affection for his", + "carefully crafted", + "philosophy of the", + "Eight Virtues,", + "wherein moral" + ), + new BookPageInfo + ( + "behavior is", + "encouraged in the", + "populace, I view with", + "less approval the", + "expenditure of public", + "funds upon the", + "construction of", + "\"shrines\" to said" + ), + new BookPageInfo + ( + "ideals.", + " The issue is not one", + "of funds, however,", + "but a disagreement", + "most intellectual over", + "the proper way of", + "humankind in an", + "ethical sense. Surely" + ), + new BookPageInfo + ( + "freedom of decision", + "must be regarded as", + "paramount in any", + "such moral decision?", + "Though none fail to", + "censure the", + "murderer, a subtler", + "question arises when" + ), + new BookPageInfo + ( + "we ask if his", + "behavior would be", + "ethical if he were", + "forced to it.", + " I say to thee, the", + "reader, quite flatly,", + "that no ethical system", + "shall have sway over" + ), + new BookPageInfo + ( + "me unless it", + "convinceth me, for", + "that freely made", + "choice is to me the", + "sign that the system", + "hath validity.", + " Whereas the system", + "of \"Virtues\" that my" + ), + new BookPageInfo + ( + "liege espouses is", + "indeed a compilation", + "of commonly approved", + "virtues, I approve of", + "it. Where it seeks to", + "control the populace", + "and restrict their", + "diversity and their" + ), + new BookPageInfo + ( + "range of behaviors, I", + "quarrel with it. And", + "thus do I issue this", + "politic call to anarchy,", + "whilst humbly", + "begging forgiveness", + "of Lord British for", + "my impertinence:" + ), + new BookPageInfo + ( + " Celebrate thy", + "differences. Take", + "thy actions according", + "to thy own lights.", + "Question from what", + "source a law, a rule,", + "a judge, and a virtue", + "may arise. 'Twere" + ), + new BookPageInfo + ( + "possible (though I", + "suggest it not", + "seriously) that a", + "daemon planted the", + "seed of these", + "\"Virtues\" in my Lord", + "British's mind; 'twere", + "possible that the" + ), + new BookPageInfo + ( + "Shrines were but a", + "plan to destroy this", + "world. Thou canst not", + "know unless thou", + "questioneth, doubteth,", + "and in the end,", + "unless thou relyest", + "upon THYSELF and" + ), + new BookPageInfo + ( + "thy judgement.", + " I offer these words", + "as mere philosophical", + "musings for those", + "who seek", + "enlightenment, for", + "'tis the issue that", + "hath occupied mine" + ), + new BookPageInfo + ( + "interest and that of", + "Lord British for", + "some time now." + ) + ); + + [Constructible] + public CallToAnarchy() : base(Utility.Random(0xFEF, 2), false) + { + } + + public CallToAnarchy(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region A Primer on Arms and Weapons + + public class ArmsAndWeaponsPrimer : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "A Primer on Arms and Weapons", "Martin", + new BookPageInfo + ( + " These are the", + "basic elements to", + "consider in assessing", + "a weapon, of which", + "all warriors who", + "regard themselves as", + "more than mere", + "mercenaries should be" + ), + new BookPageInfo + ( + "aware.", + " First and most", + "obvious is the amount", + "of damage that the", + "weapon may do", + "against unprotected", + "flesh. While 'tis this", + "which first attracts" + ), + new BookPageInfo + ( + "the attention of the", + "novice, 'tis a deadly", + "mistake to regard it", + "as the sole value of a", + "weapon. While it may", + "prove devastating", + "indeed as a means of", + "causing damage, a" + ), + new BookPageInfo + ( + "weapon must also", + "serve as stout shield", + "when engaged in", + "combat.", + " Hence the second", + "issue to which to pay", + "attention is the", + "amount of protection" + ), + new BookPageInfo + ( + "that a weapon may", + "offer. Pay close", + "attention to the guard", + "on it, if it be a blade,", + "or the stoutness of", + "its wood if it is a pole", + "arm.", + " Oft related to this" + ), + new BookPageInfo + ( + "is the weight of the", + "weapon, for a heavy", + "weapon is more", + "difficult to maneuver", + "to block with, though", + "it may do more", + "damage to thy", + "opponent." + ), + new BookPageInfo + ( + " If a weapon is too", + "heavy for the wielder", + "to move it freely,", + "they should choose", + "another and not", + "attempt to prove their", + "prowess by the size", + "of their sword." + ), + new BookPageInfo + ( + " The reach of a", + "weapon both increases", + "its defensive ability,", + "and renders it more", + "useful in open spaces", + "as it allows attack", + "against the opponent", + "without the need to" + ), + new BookPageInfo + ( + "close. But be aware of", + "the limitations of thy", + "weapon! For a", + "weapon with great", + "reach may be useless", + "in close quarters, for", + "lack of space to", + "maneuver it. Should" + ), + new BookPageInfo + ( + "that dagger-wielding", + "enemy close on thee", + "and thy halberd, 'tis", + "best to flee.", + " Lastly, a factor", + "that must always be", + "considered is the", + "condition of the" + ), + new BookPageInfo + ( + "weapon. It might be a", + "wondrous magical", + "blade of surpassing", + "sharpness and it may", + "leap to block blows", + "with a mind of its", + "own. It also might be", + "of such flimsy" + ), + new BookPageInfo + ( + "construction, or", + "damaged to such an", + "extent, that the first", + "time it clangs against", + "steel, 'twill shatter", + "into useless shards.", + " Seek ye a good", + "blacksmith should thy" + ), + new BookPageInfo + ( + "weapon become", + "damaged, but be", + "aware that their", + "ministrations may", + "simply make the", + "matter worse.", + " While mages of", + "some ability oft create" + ), + new BookPageInfo + ( + "magical weapons", + "which enhance skill,", + "are preternaturally", + "sharp, or incinerate", + "the enemy as they", + "fall, to my mind the", + "greatest gift that they", + "can grant a stout" + ), + new BookPageInfo + ( + "sword is to make it", + "resistant to damage,", + "for thy own skill can", + "make up the", + "difference. Except", + "for the fireball, but", + "if the corpse is", + "charred, then so will" + ), + new BookPageInfo + ( + "be the possessions,", + "which maketh looting", + "difficult!" + ) + ); + + [Constructible] + public ArmsAndWeaponsPrimer() : base(Utility.Random(0xFEF, 2), false) + { + } + + public ArmsAndWeaponsPrimer(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region A Song of Samlethe + + public class SongOfSamlethe : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "A Song of Samlethe", "Sandra", + new BookPageInfo + ( + "The first bear did", + "swim by day,", + "And it did sleep by", + "night.", + "It kept itself within", + "its cave", + "and ate by starry", + "light." + ), + new BookPageInfo + ( + "", + "The second bear it did", + "cavort", + "'Neath canopies of", + "trees,", + "And danced its", + "strange bearish sort", + "Of joy for all to see." + ), + new BookPageInfo + ( + "", + "The first bear, well,", + "'twas hunted,", + "And today adorns a", + "floor.", + "Its ruggish face has", + "been dented", + "By footfalls and the" + ), + new BookPageInfo + ( + "door.", + "", + "The second bear did", + "step once", + "Into a mushroom ring,", + "And now does dance", + "the dunce", + "For wisps and" + ), + new BookPageInfo + ( + "unseen things.", + "", + "So do not dance, and", + "do not sleep,", + "Or else be led astray!", + "For bears all end up", + "six feet deep", + "At the end of" + ), + new BookPageInfo + ( + "Samlethe's day." + ) + ); + + [Constructible] + public SongOfSamlethe() : base(Utility.Random(0xFEF, 2), false) + { + } + + public SongOfSamlethe(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region A Tale of Three Tribes + + public class TaleOfThreeTribes : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "A Tale of Three Tribes", "Janet, Scribe", + new BookPageInfo + ( + " The dungeon known", + "as Despise is in fact", + "not a dungeon as", + "such, but rather a", + "large natural cave.", + "Inhospitable and", + "unfriendly to", + "visitors, it is filled" + ), + new BookPageInfo + ( + "with damp spots", + "where the deadly", + "Exploding Red Spotted", + "Toadstool grows in", + "abundance.", + " According to the", + "oldest of historical", + "texts, in days gone" + ), + new BookPageInfo + ( + "by the cave was once", + "the home of three", + "separate tribes who", + "had come to an", + "accommodation with", + "each other. Oddly", + "enough, the three", + "tribes were of" + ), + new BookPageInfo + ( + "dragons, lizard men,", + "and rat men. While", + "today few except", + "extremists associated", + "with Lord Blackthorn", + "regard these latter", + "two as being", + "intelligent beings," + ), + new BookPageInfo + ( + "apparently they have", + "indeed fallen from a", + "more evolved state", + "over the years.", + " 'Tis said that these", + "three races did dwell", + "in relative harmony", + "within the vast cave," + ), + new BookPageInfo + ( + "building when they", + "required it, and", + "trading amongst", + "themselves if needed.", + " But over time,", + "something happened,", + "and they were forced", + "to withdraw from" + ), + new BookPageInfo + ( + "their society, until", + "today thou mayst", + "find individuals of", + "each species within", + "the dungeon, but", + "never again as a", + "civilization.", + " 'Tis also said that" + ), + new BookPageInfo + ( + "someday the three", + "tribes may return to", + "Despise, to once again", + "inhabit it together.", + " Until then, nothing", + "remains as token of", + "this save an oddly", + "intelligent skeleton," + ), + new BookPageInfo + ( + "magically enchanted,", + "that doth speak when", + "questions are asked,", + "and from whom I", + "obtained these tales", + "one day, when I was", + "pursued by evil", + "monsters and fled" + ), + new BookPageInfo + ( + "into his skeletal arms.", + " Fortunately, I", + "escaped and lived to", + "write it all down!" + ) + ); + + [Constructible] + public TaleOfThreeTribes() : base(Utility.Random(0xFEF, 2), false) + { + } + + public TaleOfThreeTribes(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Beltran's Guide to Guilds + + public class GuideToGuilds : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Beltran's Guide to Guilds", "Beltran", + new BookPageInfo + ( + " This reference", + "work is intended", + "merely to serve as", + "resource for those", + "curious as to the full", + "range of trades and", + "societies extant in", + "Britannia and nearby" + ), + new BookPageInfo + ( + "nations. For each", + "trade or guild, their", + "blazon is given.", + "", + " Armourer's Guild.", + "Gold bar above black", + "bar." + ), + new BookPageInfo + ( + " Association of", + "Warriors. Blue cross", + "on a red field.", + "", + " Barters' Guild.", + "Green and white", + "stripes, diagonal." + ), + new BookPageInfo + ( + " Blacksmith's Guild.", + "Gold alongside black.", + "", + " Federation of", + "Rogues and Beggars.", + "Red above black.", + "", + " Fighters and" + ), + new BookPageInfo + ( + "Footmen. Blue", + "horzontal bar on red", + "field.", + "", + " Guild of Archers.", + "A gold swath parting", + "red and blue." + ), + new BookPageInfo + ( + " Guild of", + "Armaments. Swath of", + "gold on black field,", + "gold accents.", + "", + " Guild of Assassins.", + "Black and red", + "quartered." + ), + new BookPageInfo + ( + "", + " Guild of Barbers.", + "Red and white", + "stripes.", + "", + " Guild of Cavalry and", + "Horse. Vertical blue", + "on a red field." + ), + new BookPageInfo + ( + "", + " Guild of", + "Fishermen. Blue and", + "white, quartered.", + "", + " Guild of Mages.", + "Purple and blue, in a", + "crossed pennant" + ), + new BookPageInfo + ( + "pattern.", + "", + " Guild of", + "Provisioners. White", + "bar above green bar.", + "", + " Guild of Sorcery. A", + "field divided" + ), + new BookPageInfo + ( + "diagonally in blue and", + "purple.", + "", + " Healers Guild. Gold", + "swath dividing green", + "from purple, gold", + "accents." + ), + new BookPageInfo + ( + " Lord British's", + "Healers of Virtue.", + "Golden ankh on dark", + "green.", + "", + " Masters of Illusion.", + "Blue and purple", + "checkers." + ), + new BookPageInfo + ( + "", + " Merchants' Guild.", + "Gold coins on green", + "field.", + "", + " Mining Cooperative.", + "A gold cross,", + "quartering blue and" + ), + new BookPageInfo + ( + "black.", + "", + " Order of Engineers.", + "Purple, gold, and blue", + "vertical.", + "", + " Sailors' Maritime", + "Association. A white" + ), + new BookPageInfo + ( + "bar centered on a blue", + "field.", + "", + " Seamen's Chapter.", + "Blue and white in a", + "crossed pennant", + "pattern." + ), + new BookPageInfo + ( + " Society of Cooks and", + "Chefs. White and red", + "diagonal fields", + "checker on green", + "field.", + "", + " Society of", + "Shipwrights. White" + ), + new BookPageInfo + ( + "diagonal above blue.", + "", + " Society of Thieves.", + "Black and red diagonal", + "stripes.", + "", + " Society of", + "Weaponsmakers. Gold" + ), + new BookPageInfo + ( + "diagonal above black.", + "", + " Tailor's Hall. Purple", + "above gold above red.", + "", + " The Bardic", + "Collegium. Purple and", + "red checkers on gold" + ), + new BookPageInfo + ( + "field.", + "", + " Traders' Guild.", + "White bar centered", + "down green field." + ) + ); + + [Constructible] + public GuideToGuilds() : base(Utility.Random(0xFEF, 2), false) + { + } + + public GuideToGuilds(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Birds of Britannia + + public class BirdsOfBritannia : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Birds of Britannia", "Thom the Heathen", + new BookPageInfo + ( + " The WREN is a", + "tiny insect-eating", + "bird with a loud voice.", + " The cheerful trills", + "of Wrens are", + "extraordinarily", + "varied and melodious.", + " The SWALLOW" + ), + new BookPageInfo + ( + "is easily recognized", + "by its forked tail.", + "Swallows catch", + "insects in flight, and", + "have squeaky,", + "twittering songs.", + " The WARBLER is", + "an exceptional singer," + ), + new BookPageInfo + ( + "whose extensive", + "songs combine the", + "best qualities of", + "Wrens and Swallows.", + " The NUTHATCH", + "climbs down trees", + "head first, searching", + "for insects in the" + ), + new BookPageInfo + ( + "bark. It sings a", + "repetitive series of", + "notes with a nasal", + "tone quality.", + " The agile", + "CHICKADEE has a", + "buzzy", + "\"chick-a-dee-dee\"" + ), + new BookPageInfo + ( + "call, from which its", + "name is derived. Its", + "song is a series of", + "whistled notes.", + " The THRUSH is a", + "brown bird with a", + "spotted breast, which", + "eats worms and" + ), + new BookPageInfo + ( + "snails, and has a", + "beautiful singing", + "voice. Thrushes use", + "a stone as an anvil to", + "smash the shells of", + "snails.", + " The little", + "NIGHTINGALE is" + ), + new BookPageInfo + ( + "also known for its", + "beautiful song, which", + "it sings even at night.", + " The STARLING", + "is a small dark bird", + "with a yellow bill and", + "a squeaky,", + "high-pitched song." + ), + new BookPageInfo + ( + "Starlings can mimic", + "the sounds of other", + "birds.", + " The SKYLARK", + "sings a series of", + "high-pitched", + "melodious trills in", + "flight." + ), + new BookPageInfo + ( + " The FINCH is a", + "small seed-eating bird", + "with a conical beak", + "and a musical,", + "warbling song.", + " The CROSSBILL", + "is a kind of Finch", + "with a strange" + ), + new BookPageInfo + ( + "crossed bill, which it", + "uses to extract seeds", + "from pine cones.", + " The CANARY is a", + "kind of Finch that is", + "often kept as a pet.", + "Miners would often", + "take Canaries" + ), + new BookPageInfo + ( + "underground with", + "them, to warn them", + "of the presence of", + "hazardous vapors in", + "the air.", + " The SPARROW", + "weaves a nest of", + "grass, and has an" + ), + new BookPageInfo + ( + "unmusical chirp for a", + "voice.", + " The TOWHEE is a", + "kind of Sparrow that", + "continually reminds", + "listeners to drink", + "their tea.", + " The SHRIKE is a" + ), + new BookPageInfo + ( + "gray bird with a", + "hooked bill. Shrikes", + "have the habit of", + "impaling their prey", + "on thorns.", + " The", + "WOODPECKER has a", + "pointed beak that is" + ), + new BookPageInfo + ( + "suitable for pecking at", + "wood to get at the", + "insects inside.", + " The", + "KINGFISHER dives", + "for fish, which it", + "catches with its long,", + "pointed beak." + ), + new BookPageInfo + ( + " The TERN", + "migrates over great", + "distances, from one", + "end of Britannia to", + "the other each year.", + "Terns dive from the", + "air to catch fish.", + " The PLOVER is a" + ), + new BookPageInfo + ( + "bird that distracts", + "predators by", + "pretending to have a", + "broken wing.", + " The LAPWING is", + "a kind of Plover that", + "has a long black crest.", + " The HAWK is a" + ), + new BookPageInfo + ( + "predator that feeds on", + "small birds, mice,", + "squirrels, and other", + "small animals. Small", + "hawks are known as", + "Kites.", + " The DOVE is a", + "seed-eating bird with" + ), + new BookPageInfo + ( + "a peaceful reputation.", + " Doves have a", + "low-pitched cooing", + "song.", + " The PARROT is a", + "brightly colored bird", + "with a hooked bill,", + "favored as a" + ), + new BookPageInfo + ( + "companion by pirates.", + " Parrots can be", + "taught to imitate the", + "human voice.", + " The CUCKOO is a", + "devious bird that lays", + "eggs in the nests of", + "Warblers and other" + ), + new BookPageInfo + ( + "small birds. Cuckoos", + "have the uncanny", + "ability to keep track", + "of time, singing once", + "at the beginning of", + "each hour.", + " The", + "ROADRUNNER is" + ), + new BookPageInfo + ( + "an unusual bird with", + "a long tail, which", + "runs swiftly along", + "the ground hunting", + "for lizards and", + "snakes.", + " The SWIFT is a", + "very agile bird that" + ), + new BookPageInfo + ( + "spends nearly its", + "entire life in the air.", + "With their mouths", + "wide open, Swifts", + "capture insects in", + "mid-flight.", + " The", + "HUMMINGBIRD is a" + ), + new BookPageInfo + ( + "cross between a", + "Swift and a Fairy.", + "These tiny, brightly", + "colored birds hover", + "magically near", + "flowers, and live on", + "the nectar they", + "provide." + ), + new BookPageInfo + ( + " The OWL is a", + "reputedly wise bird", + "that is active at night,", + "unlike most birds.", + "Owls have excellent", + "night vision and", + "low-pitched hooting", + "calls. Their wings" + ), + new BookPageInfo + ( + "are silent in flight.", + " The", + "GOATSUCKER is a", + "strange owl-like bird", + "that is thought to live", + "on the milk of goats.", + "These mysterious", + "birds make jarring" + ), + new BookPageInfo + ( + "sounds at night, for", + "which reason they", + "are also called", + "Nightjars.", + " The DUCK is a", + "bird that swims more", + "often than it flies,", + "and has a nasal voice" + ), + new BookPageInfo + ( + "that is described as a", + "\"quack\".", + " The SWAN is a", + "kind of long-necked", + "Duck that is all white.", + " Swans are usually", + "voiceless, but they", + "are said to have an" + ), + new BookPageInfo + ( + "extraordinarily", + "beautiful song." + ) + ); + + [Constructible] + public BirdsOfBritannia() : base(Utility.Random(0xFEF, 2), false) + { + } + + public BirdsOfBritannia(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Britannian Flora: A Casual Guide + + public class BritannianFlora : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Britannian Flora: A Casual Guide", "Herbert the Lost", + new BookPageInfo + ( + " Oft 'pon rambling", + "through the woods", + "avoiding bears have I", + "spotted some plant", + "whose like I have", + "never seen before,", + "and concluded that I", + "was a blithering idiot" + ), + new BookPageInfo + ( + "for failing to notice it", + "in the past. Equally", + "as oft have I", + "concluded that I was a", + "worse idiot for not", + "running faster from", + "the bear.", + " While not all my" + ), + new BookPageInfo + ( + "readers may share", + "my proclivities for", + "tree-climbing, it", + "occurred to me that", + "mayhap mine", + "information might", + "serve some humble", + "purpose." + ), + new BookPageInfo + ( + " The two most", + "unique flowering", + "plants in the", + "Britannian", + "countryside are the", + "orfleur and the", + "whiteflower, also", + "called white horns." + ), + new BookPageInfo + ( + " The orfleur is", + "notable for its", + "massive orange-red", + "blossoms, which", + "dwarf marigolds like", + "the sun dwarfs your", + "common fireball spell.", + "The odor of said" + ), + new BookPageInfo + ( + "blooms is best", + "described as", + "peppermint-apple,", + "with a dash of garlic.", + "'Tis a popular potted", + "plant despite, or", + "perhaps because of,", + "its exotic nature." + ), + new BookPageInfo + ( + " Whiteflowers exude", + "a subtle fragrance not", + "unlike that of freshly", + "shaven wood mixed", + "with cool lemon ice.", + "Their tall stands", + "always droop with the", + "heavy weight of the" + ), + new BookPageInfo + ( + "massive blooms, oft", + "as large as a child's", + "head.", + " The flowers are so", + "large that one may", + "scoop out the pollen in", + "handfuls, and during", + "the spring season" + ), + new BookPageInfo + ( + "many a prank hath", + "been played by idle", + "boys 'pon their", + "sisters by dumping", + "said pollen into their", + "clothing drawers,", + "causing sneezes for", + "days." + ), + new BookPageInfo + ( + " The most", + "interesting native tree", + "to Britannia is the", + "spider tree. The", + "reason for its naming", + "is obscure, but may", + "have to do with the", + "twisted gray stalks" + ), + new BookPageInfo + ( + "from which the", + "spherical canopy", + "sprouts. 'Tis", + "something of a", + "misnomer to term", + "these \"trunks\" as", + "they are spindly and", + "flexible. Spider trees" + ), + new BookPageInfo + ( + "provide a fresh,", + "piney smell to a room", + "and are therefore", + "often potted.", + " In jungle climes,", + "one finds the blade", + "plant, whose sharp", + "leaves oft collect" + ), + new BookPageInfo + ( + "water for the thirsty", + "traveler, yet can", + "draw blood easily.", + " The deadliest plant,", + "if you can call a", + "fungus such, is the", + "Exploding Red Spotted", + "Toadstool. No pattern" + ), + new BookPageInfo + ( + "can be discerned to", + "its habitats save", + "malice, for merely", + "approaching results in", + "the cap exploding", + "with powder, noxious", + "gas, and tiny painful", + "pellets flying in all" + ), + new BookPageInfo + ( + "directions.", + "Unfortunately, 'tis", + "impossible to tell it", + "apart from the", + "Ordinary Red Spotted", + "Toadstool save through", + "experimentation.", + " Truly odd among the" + ), + new BookPageInfo + ( + "varied flora of", + "Britannia, however,", + "are those which bear", + "names clearly alien to", + "our tongue. Among", + "these I name the", + "Tuscany pine (for I", + "have never seen a" + ), + new BookPageInfo + ( + "region of this world", + "named Tuscany), the", + "o'hii tree, whose very", + "name sounds like", + "some tropical isle, and", + "the welsh poppy,", + "which while", + "different from the" + ), + new BookPageInfo + ( + "ordinary poppy in", + "color and appearance,", + "is prefaced with the", + "odd word \"welsh,\"", + "which as far as I", + "know means to forgo", + "paying a debt." + ) + ); + + [Constructible] + public BritannianFlora() : base(Utility.Random(0xFEF, 2), false) + { + } + + public BritannianFlora(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Classic Children's Tales, Volume 2 + + public class ChildrenTalesVol2 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Classic Children's Tales, Volume 2", "Guilhem, Editor", + new BookPageInfo + ( + "Clarke's Printery", + "is Honored to", + "Present Tales from", + "Ages Past!", + " Guilhem the", + "Scholar Shall End", + "EachVolume with", + "Staid Commentary." + ), + new BookPageInfo + ( + "", + "THE RHYME", + "Dance in the Star", + "Chamber", + "And Dance in the Pit", + "And Eat of your", + "Entrees", + "In the Glass House" + ), + new BookPageInfo + ( + "you Sit", + "", + "COMMENTARY", + " A common feeding", + "rhyme for little", + "babies, 'tis thought", + "that this little ditty is", + "part of the corpus of" + ), + new BookPageInfo + ( + "legendary tales", + "regarding the world", + "before Sosaria (see", + "the wonderful fables", + "of Fabio the Poor for", + "fictionalized versions", + "of these stories, also", + "available from this" + ), + new BookPageInfo + ( + "same publisher).", + " According to these", + "old tales, which", + "survive mostly in the", + "hills and remote", + "villages where Lord", + "British is as yet a", + "distant and mythical" + ), + new BookPageInfo + ( + "ruler, the gods of old", + "(a fanciful notion!)", + "met to discuss the", + "progress of creating", + "the world in mystical", + "rooms. A simple", + "analysis reveals these", + "rooms to be mere" + ), + new BookPageInfo + ( + "mythological", + "generalizations.", + " \"The Star", + "Chamber\" is clearly a", + "reference to the sky.", + "\"The Pit\" is certainly", + "an Underworld", + "analogous to the" + ), + new BookPageInfo + ( + "Snakehills of other", + "tales, and \"the Glass", + "House\" is no doubt the", + "vantage point from", + "which the gods", + "observed their", + "creation. All is simple", + "when seen from this" + ), + new BookPageInfo + ( + "perspective, leaving", + "only the mysterious", + "reference to dinners.", + "Oddly enough, the", + "rhyme is universally", + "used only for", + "midnight feedings,", + "never during the day." + ), + new BookPageInfo + ( + ) + ); + + [Constructible] + public ChildrenTalesVol2() : base(Utility.Random(0xFEF, 2), false) + { + } + + public ChildrenTalesVol2(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Classic Tales of Vesper, Volume 1 + + public class TalesOfVesperVol1 : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Classic Tales of Vesper, Volume 1", "Clarke's Printery", + new BookPageInfo + ( + "'Tis an Honor to", + "present to Thee these", + "Tales collected from", + "Ages Past. In this", + "Inaugural Volume, we", + "present this Verse", + "oft Recited as a", + "Lullabye for sleepy" + ), + new BookPageInfo + ( + "Children.", + "", + "Preface", + "by Guilhem the", + "Scholar", + "", + " The meaning of this", + "verse has oft been" + ), + new BookPageInfo + ( + "discussed in halls of", + "scholarly sorts, for", + "its mysterious", + "singsongy melody is", + "oddly disturbing to", + "adult ears, though", + "children seem to find", + "it restful as they" + ), + new BookPageInfo + ( + "sleep. Perhaps it is", + "but the remnant of a", + "longer ballad once", + "extant, for there are", + "internal indications", + "that it once told a", + "longer story about", + "ill-fated lovers, and a" + ), + new BookPageInfo + ( + "magical experiment", + "gone awry. However,", + "poetic license and the", + "folk process has", + "distorted the words", + "until now the locale of", + "the tale is no more", + "than \"in the wind,\"" + ), + new BookPageInfo + ( + "which while it serves", + "a pleasingly", + "metaphorical purpose,", + "fails to inform the", + "listener as to any real", + "locale!", + " Another possibility", + "is that this is some" + ), + new BookPageInfo + ( + "form of creation", + "myth explaining the", + "genesis of the various", + "humanoid creatures", + "that roam the lands of", + "Britannia. It does not", + "take a stretch of the", + "imagination to name" + ), + new BookPageInfo + ( + "the middle verse's", + "\"girl becomes tree\" as", + "a possible explanation", + "for the reaper, for in", + "the area surrounding", + "Minoc, reapers are", + "oft referred to among", + "the lumberjacking" + ), + new BookPageInfo + ( + "community as", + "\"widowmakers.\" That", + "these creatures are", + "of arcane origin is", + "assumed, but the", + "verse seems to imply", + "a long ago creator, and", + "uses the antique" + ), + new BookPageInfo + ( + "magickal terminology", + "of \"plaiting strands", + "of ether\" that is so", + "often found in", + "ancient texts. In", + "addition, the", + "reference to", + "\"snakehills\" may" + ), + new BookPageInfo + ( + "profitably be regarded", + "as a reference to an", + "actual location, such", + "as perhaps a local", + "term for the", + "Serpent's Spine.", + " A commoner", + "interpretation is that" + ), + new BookPageInfo + ( + "like many nursery", + "rhymes, it is a", + "simple explanation", + "for death, wherein", + "the wind snatches up", + "boys and girls and", + "when they sleep in", + "order to keep the" + ), + new BookPageInfo + ( + "balance of the world.", + "Notable tales have", + "been written for", + "children of", + "adventures in \"the", + "Snakehills,\" which", + "are presumed to be an", + "Afterworld whence" + ), + new BookPageInfo + ( + "the spirit lives on. A", + "grim lullabye, to be", + "sure, but no worse", + "than \"lest I die before", + "I wake\" surely.", + " In either case, 'tis", + "an old favorite,", + "herein printed for" + ), + new BookPageInfo + ( + "the first time for", + "thy enjoyment and", + "perusal!", + "", + "In the Wind where", + "the Balance", + "Is Whispered in", + "Hallways" + ), + new BookPageInfo + ( + "In the Wind where", + "the Magic", + "Flows All through the", + "Night", + "There live Mages and", + "Mages", + "With Robes made of", + "Whole Days" + ), + new BookPageInfo + ( + "Reading Books full of", + "Doings", + "Printed on Light", + "", + "In the Wind where", + "the Lovers", + "Are Crossed under", + "Shadows" + ), + new BookPageInfo + ( + "Where they Meet and", + "are Parted", + "By the Orders of", + "Fate", + "The Girl becomes", + "Tree,", + "And thus becomes", + "Widow" + ), + new BookPageInfo + ( + "The Boy becomes", + "Earth", + "And Wanders Till", + "Late", + "", + "In the Wind are the", + "Monsters", + "First Born First" + ), + new BookPageInfo + ( + "Created", + "When Chanting and", + "Ether", + "Mix Meddling and", + "Nigh", + "Fear going to Wind,", + "Fear Finding its", + "Plaitings," + ), + new BookPageInfo + ( + "Go Not to the", + "Snakehills", + "Lest You Care to Die" + ) + ); + + [Constructible] + public TalesOfVesperVol1() : base(Utility.Random(0xFEF, 2), false) + { + } + + public TalesOfVesperVol1(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Deceit: A Dungeon of Horrors + + public class DeceitDungeonOfHorror : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Deceit: A Dungeon of Horrors", "Mercenary Justin", + new BookPageInfo + ( + " My employers have", + "oft taken me into this", + "den of hideous", + "creatures, and I", + "thought that it", + "behooved me to write", + "down what I know of", + "it, now that I am" + ), + new BookPageInfo + ( + "retired from the life", + "of an adventurer for", + "hire.", + " Deceit was once a", + "temple to forgotten", + "powers of old. It was", + "taken over by mages", + "who eventually were" + ), + new BookPageInfo + ( + "driven out by the", + "depredations of their", + "own evil lackeys.", + "However, many of", + "the magical traps and", + "devices that they", + "placed for their", + "defenses remain," + ), + new BookPageInfo + ( + "particularly those the", + "wizards used to", + "protect their", + "treasures.", + " The dungeon is", + "mystically linked by", + "crystal balls placed in", + "different locations." + ), + new BookPageInfo + ( + "These magical orbs do", + "transmit speech, and", + "even have memory of", + "things that have been", + "said near them. No", + "doubt they once", + "served as a warning", + "system" + ), + new BookPageInfo + ( + " Be wary of a", + "brazier that giveth", + "warning when", + "approached; thou canst", + "use it to summon", + "deadly creatures.", + " There be a", + "tantalizing chest," + ), + new BookPageInfo + ( + "undoubtedly full of", + "treasure, that cannot", + "be reached save past a", + "complex set of", + "pressure plates that", + "trigger deadly spikes.", + "As I never had", + "sufficient folk with" + ), + new BookPageInfo + ( + "me to unlock the", + "puzzle, I never", + "obtained the riches", + "that awaited there.", + " Do not investigate", + "iron maidens too", + "closely, for they may", + "suck you within" + ), + new BookPageInfo + ( + "them!", + " There is one place", + "where a deadly trap", + "can only be disarmed", + "by making use of a", + "statue that cleverly", + "conceals a lever.", + " Oft one encounters" + ), + new BookPageInfo + ( + "the deadly exploding", + "toadstool; the ones in", + "Deceit are deadlier", + "than most, as they", + "explode continually.", + "Likewise, the very", + "pools of water and", + "slime on the floor" + ), + new BookPageInfo + ( + "may poison thee.", + " The most magical", + "device in the dungeon", + "is a mystical bridge", + "that can only be", + "triggered by a level", + "embedded in the floor.", + "Be wary however," + ), + new BookPageInfo + ( + "for the bridge thus", + "created doth burst", + "into flame when one", + "passeth across it!" + ) + ); + + [Constructible] + public DeceitDungeonOfHorror() : base(Utility.Random(0xFEF, 2), false) + { + } + + public DeceitDungeonOfHorror(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Dimensional Travel, a Monograph + + public class DimensionalTravel : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Dimensional Travel, a Monograph", "Dryus Doost, Mage", + new BookPageInfo + ( + " 'Tis beyond the", + "scope of this small", + "monograph to discuss", + "the details of", + "moongates, and the", + "manners in which", + "they distort the", + "fabric of reality in" + ), + new BookPageInfo + ( + "such a manner as to", + "permit the passage of", + "living flesh from", + "place to place, world to", + "world, or indeed from", + "dimension to", + "dimension.", + " Instead, allow me to" + ), + new BookPageInfo + ( + "bring thy attention,", + "Gentle Reader, to the", + "curious", + "characteristics that", + "are shared by certain", + "individuals within", + "our realm.", + " Long has it been" + ), + new BookPageInfo + ( + "known that the blue", + "moongate permits", + "travel from place to", + "place, and none have", + "trouble in taking this", + "path. Yet 'tis also", + "known, albeit only to a", + "few, that certain" + ), + new BookPageInfo + ( + "individuals are unable", + "to traverse the black", + "moongates that permit", + "travel from one", + "dimension to another.", + " The noted mage and", + "peer of our realm,", + "Lord Blackthorn, once" + ), + new BookPageInfo + ( + "told me in", + "conversation that his", + "arcane research had", + "indicated that the", + "issue was one of", + "conversation of ether.", + "To wit, given the", + "postulate that matter" + ), + new BookPageInfo + ( + "within a given", + "dimension may be but", + "a cross-section of", + "ethereal matter that", + "exists in multiple", + "dimensions, it", + "becomes obvious that", + "said ethereal" + ), + new BookPageInfo + ( + "structure cannot", + "enter dimensions in", + "which it is already", + "present.", + " Imagine an", + "individual (and the", + "Lord Blackthorn", + "hinted that he was" + ), + new BookPageInfo + ( + "one such) who exists", + "already in some form", + "in multiple", + "dimensions; said", + "individual would not", + "be able to cross into", + "another dimension", + "because HE IS" + ), + new BookPageInfo + ( + "ALREADY THERE.", + " The implications of", + "this are staggering,", + "and merit further", + "study. 'Tis well", + "known by theorists in", + "the field that", + "divisions in the" + ), + new BookPageInfo + ( + "ethereal structure of", + "an individual are", + "already implicit at the", + "temporal level, as", + "causality forces", + "divisions upon the", + "ether. This is the", + "basic operating" + ), + new BookPageInfo + ( + "mechanism by which", + "white moongates", + "function, permitting", + "time travel.", + " As time travel is", + "not barred by the", + "presence of an earlier", + "self (though" + ), + new BookPageInfo + ( + "encountering said", + "earlier self can prove", + "arcanely perilous),", + "there must be some", + "rigidity to the", + "ethereal structure", + "that bars multiple", + "instantiations of" + ), + new BookPageInfo + ( + "structures from", + "manifesting within", + "the same context.", + " If one regards time", + "and causal bifurcation", + "as a web, perhaps the", + "appropriate analogy", + "for dimensional" + ), + new BookPageInfo + ( + "matrices is that of a", + "crystalline structure,", + "with rigid linkages.", + "The only way in", + "which an individual", + "such as Lord", + "Blackthorn, who", + "exists in multiple" + ), + new BookPageInfo + ( + "dimensional matrices,", + "can cross worlds via", + "a black moongate,", + "would be for the", + "entire crystalline", + "structure of the", + "dimension to", + "perfectly match the" + ), + new BookPageInfo + ( + "ethereal resonance of", + "the destination", + "dimension.", + " The problem of why", + "certain individuals", + "are already replicated", + "in multiple crystalline", + "matrices is one that I" + ), + new BookPageInfo + ( + "fail to provide any", + "schema for in these", + "poor theories. It is", + "my fondest hope that", + "someday someone", + "shall conquer that", + "thorny problem and", + "enlighten the world." + ) + ); + + [Constructible] + public DimensionalTravel() : base(Utility.Random(0xFEF, 2), false) + { + } + + public DimensionalTravel(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Ethical Hedonism: An Introduction + + public class EthicalHedonism : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Ethical Hedonism: An Introduction", "Richard Garriott", + new BookPageInfo + ( + " Societies oft have", + "common codes of", + "conduct which it", + "expects all its people", + "to abide by. Now,", + "while 'tis true that", + "this can offer some", + "advantages, most of" + ), + new BookPageInfo + ( + "the codes I see today", + "around Britannia have", + "fatal flaws. Let us", + "examine them.", + " First, there is", + "Blackthorn's code of", + "Chaos or basically", + "Anarchy. Whereas" + ), + new BookPageInfo + ( + "this affords the", + "individual maximum", + "opportunity for", + "individuality and even", + "pursuit of personal", + "happiness, it does not", + "offer even basic", + "interpersonal conduct" + ), + new BookPageInfo + ( + "codes to prevent", + "people from killing", + "each other.", + " Without such basic", + "tenets, all the people", + "will need to spend a", + "significant portion of", + "their time and effort" + ), + new BookPageInfo + ( + "towards personal", + "protection and thus", + "less time towards", + "other more beneficial", + "pursuits.", + " Then there are the", + "moral codes that are", + "so popular today." + ), + new BookPageInfo + ( + "These codes are built", + "largely on historical", + "tradition rather than", + "current logic and thus", + "are also antiquated.", + "For example many", + "moral codes we see", + "today include" + ), + new BookPageInfo + ( + "statements about not", + "eating certain foods", + "that once were often", + "poisonous, but today", + "can be prepared", + "safely.", + " Many forbid contact", + "between young people" + ), + new BookPageInfo + ( + "of the opposite", + "gender, which can in", + "fact be hazardous; but", + "the codes often have", + "lost the context as to", + "why this is done,", + "instead merely calling", + "it amoral. In this day" + ), + new BookPageInfo + ( + "and age to call that a", + "necessary moral", + "would need a new", + "reasoning. I put forth", + "that tradition is not", + "enough", + " Then there are", + "Lord British's" + ), + new BookPageInfo + ( + "Virtues. It strikes me", + "that while a system", + "of virtues is", + "wonderful as a", + "touchstone to guide a", + "society to good", + "behavior, these are", + "but shades of the" + ), + new BookPageInfo + ( + "underlying truth as to", + "why one may wish to", + "live a life according to", + "certain rules of", + "conduct.", + " On the other hand,", + "clearly the Virtues", + "that I have heard" + ), + new BookPageInfo + ( + "Lord British speak of", + "are clearly positive", + "codes of conduct, far", + "better than the world", + "of anarchy that Lord", + "Blackthorn suggests.", + "Yet, are not these", + "Virtues still derived" + ), + new BookPageInfo + ( + "from a set of", + "principles which", + "though they sound", + "good, are difficult to", + "pin down as actual,", + "undeniable, rational", + "truths?", + " Worse yet though" + ), + new BookPageInfo + ( + "imagine a society", + "who's code of", + "conduct was based on", + "pure survival of the", + "strongest. While this", + "society may function", + "and even accomplish", + "much, it can be" + ), + new BookPageInfo + ( + "fairly argued that", + "personal happiness", + "would suffer greatly,", + "except for those at", + "the top. To rule that", + "out, however, we", + "must first believe", + "that people have a" + ), + new BookPageInfo + ( + "right to pursue", + "happiness.", + " I hope is a safe", + "assumption that all", + "beings wish to be", + "happy; I will broadly", + "describe this as", + "Hedonism. Yet, if all" + ), + new BookPageInfo + ( + "people did is live a", + "life of hedonism,", + "their hedonism might", + "be in conflict with", + "those near them, so I", + "will use the term", + "Ethics to describe", + "limits one might put" + ), + new BookPageInfo + ( + "on one's hedonistic", + "tendencies to allow", + "others to pursue their", + "happiness as well.", + " Allow me to give", + "this example: If one", + "were to live alone on a", + "desert isle, one could" + ), + new BookPageInfo + ( + "live a life of pure", + "hedonism, for no", + "action one might take", + "could interfere with", + "another's right to", + "pursue their", + "happiness. Poison the", + "lake if you like, there" + ), + new BookPageInfo + ( + "is no one to blame but", + "yourself!", + " Now suppose two", + "of you live on that", + "island. Thou dost not", + "want thy neighbor to", + "feel free to poison the", + "lake. Would it not be" + ), + new BookPageInfo + ( + "better to consider it", + "unethical to poison the", + "lake without first", + "thinking of those", + "whose pursuit of", + "happiness might be", + "affected by this", + "action?" + ), + new BookPageInfo + ( + " I put forth that it is", + "the fact that we as a", + "people choose to live in", + "groups known as a", + "society that causes us", + "to compromise our", + "pure hedonism with", + "logical ethics." + ), + new BookPageInfo + ( + "Likewise we accept", + "not being able to kill", + "others without", + "reason, because our", + "own pursuit of", + "happiness would be", + "greatly interfered", + "with if we feared" + ), + new BookPageInfo + ( + "others would do the", + "same to us. From", + "this basis of logic can", + "be formed the Tenets", + "of Ethical Hedonism.", + " For more on this", + "subject, see The", + "Tenants of Ethical" + ), + new BookPageInfo + ( + "Hedonism, by", + "Richard Garriott and", + "Herman Miller." + ) + ); + + [Constructible] + public EthicalHedonism() : base(Utility.Random(0xFEF, 2), false) + { + } + + public EthicalHedonism(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region My Story + + public class MyStory : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "My Story", "Sherry the Mouse", + new BookPageInfo + ( + " 'Twas on a chill", + "night, when the moon", + "shone pasty-faced", + "above the horizon,", + "balanced on the", + "towers of Lord", + "British's castle, that", + "the events I am about" + ), + new BookPageInfo + ( + "to relate took place,", + "some years ago now. I", + "witnessed them all", + "from my tiny", + "mousehole.", + " Milords British and", + "Blackthorn are", + "accustomed to a game" + ), + new BookPageInfo + ( + "of chess 'pon an", + "evening, over which", + "they argue the issues", + "that affect the course", + "of the realm. Lord", + "Blackthorn was on his", + "way to Lord British's", + "chambers, and Lord" + ), + new BookPageInfo + ( + "British stood by a", + "window casement,", + "just having finished", + "setting the pieces", + "upon the board.", + " Suddenly the", + "shutters blew open,", + "and Lord British fell" + ), + new BookPageInfo + ( + "to the ground, one", + "hand shielding his", + "eyes. A chill wind", + "entered the room, and", + "it seemed a gash was", + "torn in the very air.", + "Through the gash I", + "could see stars and" + ), + new BookPageInfo + ( + "swirling clouds of", + "stellar dust, and a", + "coldness sucked all", + "the warmth from the", + "air. A terrible wind", + "tossed books and", + "blankets across the", + "room, and furniture" + ), + new BookPageInfo + ( + "toppled.", + " From within this", + "gash issued a great", + "voice, unlike any I", + "have ever heard. And", + "these are the words it", + "spoke (for I", + "memorized them most" + ), + new BookPageInfo + ( + "carefully):", + " \"Greetings, Lord", + "British. I am the", + "Time Lord, a being", + "from beyond your", + "dimension, as thou", + "art from a world", + "other than Sosaria. I" + ), + new BookPageInfo + ( + "am here to bring thee", + "warning. Dost thou", + "recall how long ago a", + "mysterious Stranger", + "came to Sosaria and", + "saved the world from", + "the evil wizard", + "Mondain? He" + ), + new BookPageInfo + ( + "shattered the Gem of", + "Immortality, within", + "which dwelled a", + "perfect likeness of", + "this world.\"", + " Lord British slowly", + "stood and faced the", + "hole in the air. \"I" + ), + new BookPageInfo + ( + "remember,\" he said.", + "\"Oft have I wished", + "that stranger would", + "return.\"", + " \"He hath returned,\"", + "spoke the voice. \"But", + "not to here. When the", + "Gem was shattered, a" + ), + new BookPageInfo + ( + "thousand shards were", + "scattered across the", + "dimensions, and in", + "each shard there is a", + "perfect likeness of", + "this world. And thou", + "dost live upon one", + "such shard, for thou" + ), + new BookPageInfo + ( + "art not of the true", + "world-thou art", + "merely a reflection.\"", + " Lord British looked", + "shaken by this, and I", + "did not know what to", + "think! Was I merely a", + "shadow of the real" + ), + new BookPageInfo + ( + "me, which lives still", + "somewhere else", + "across uncounted", + "universes?", + " \"My task is to heal", + "this shattered world,", + "Lord British,\" said", + "the voice. \"And I seek" + ), + new BookPageInfo + ( + "to enlist thee in my", + "cause. Be warned that", + "in this case, healing", + "carries with it a", + "terrible price.\"", + " Concern warred", + "with curiosity on my", + "liege's face, but ever" + ), + new BookPageInfo + ( + "one to shoulder a", + "burden, he", + "straightened and", + "faced the gash in the", + "air bravely. \"Name", + "thy price.\"", + " \"A shard of a", + "universe is a" + ), + new BookPageInfo + ( + "powerful thing, and a", + "universe shattered is", + "always in danger", + "from the powers of", + "darkness. Already", + "three shards were", + "turned to evil, and", + "sent to plague the" + ), + new BookPageInfo + ( + "original universe in", + "the form of", + "Shadowlords. Many", + "times have I brought", + "the Stranger back to", + "Britannia, to preserve", + "it from its own folly", + "or from outside" + ), + new BookPageInfo + ( + "dangers. Yet as long", + "as the world", + "remaineth in pieces,", + "it remaineth", + "vulnerable. We must", + "bring the shards into", + "harmony, so that they", + "resonate in such a" + ), + new BookPageInfo + ( + "manner that matches", + "the original universe.", + "Then the two", + "universes shall", + "merge, and be again", + "as one.\"", + " \"But if we are only", + "shadows...\" Lord" + ), + new BookPageInfo + ( + "British said", + "wonderingly.", + " The light from the", + "stars within the hole", + "seemed to dim.", + "\"Indeed, the", + "reflections shall", + "become one with the" + ), + new BookPageInfo + ( + "original. Thou wouldst", + "cease to be as thou", + "art, and become part", + "of the larger you.", + "Thou shalt not die;", + "however, uncounted", + "generations have", + "passed and borne" + ), + new BookPageInfo + ( + "children since that", + "day, and they have no", + "counterparts. They", + "would perish utterly.\"", + " Lord British sagged", + "in shock, realizing", + "the terrible price that", + "would be paid to heal" + ), + new BookPageInfo + ( + "the universe. \"All of", + "my people,\" he", + "breathed.", + " \"'Tis for the greater", + "good.\"", + " Lord British bowed", + "his head.", + " 'Twas then I saw" + ), + new BookPageInfo + ( + "the movement by the", + "door, half-hid by the", + "heavy red curtains.", + "Lord Blackthorn stood", + "there, concealed from", + "the rest of the room,", + "his face white. How", + "long had he been" + ), + new BookPageInfo + ( + "listening? I cannot", + "say, yet I suspect", + "that he had heard all", + "that the mysterious", + "voice had to say.", + " \"How then, shall I", + "aid thee?\" Lord", + "British said," + ), + new BookPageInfo + ( + "weariness in his", + "voice.", + " \"Aid the nobilty that", + "resideth in the", + "human heart. Protect", + "the Virtues that so", + "recently came to thee", + "in thought late at" + ), + new BookPageInfo + ( + "night. They are the", + "Virtues of life, as", + "your counterpart", + "understands them to", + "be. For when thy", + "populace doth live and", + "breathe these Virtues,", + "shall it match the" + ), + new BookPageInfo + ( + "true Britannia, and", + "thy shard shall", + "rejoin with it.\"", + " The gash in the air", + "began to close, and", + "with it warmth stole", + "back into the room.", + " \"I was going to" + ), + new BookPageInfo + ( + "discuss my idea with", + "Blackthorn tonight,\"", + "Lord British", + "breathed. \"Have I no", + "thoughts that are my", + "own? Is my life but", + "a reflection of", + "another me?\"" + ), + new BookPageInfo + ( + " \"Nay,\" said the", + "voice, smaller through", + "the diminished", + "opening. \"Say, rather,", + "that you are parallel,", + "for there is no", + "guarantee that thou", + "shalt accomplish what" + ), + new BookPageInfo + ( + "I have set thee to. I", + "speak tonight to a", + "thousand of thee, and", + "ask the same of all.", + "Perhaps not all shall", + "seek to aid me.\" And", + "with that, the gash", + "closed, and the voice" + ), + new BookPageInfo + ( + "was gone, leaving a", + "room that appeare", + "tossed by a mighty", + "storm.", + " \"Destroy the world", + "to save the universe,\"", + "Lord British said", + "bitterly. \"I do not" + ), + new BookPageInfo + ( + "wonder that some", + "may balk.\"", + " Lord Blackthorn", + "collected himself, and", + "strode into the room,", + "a decent mimicry of", + "surprise on his face.", + "\"My liege! What has" + ), + new BookPageInfo + ( + "happened here?\" he", + "exclaimed, feigning", + "dismay well. But not", + "well enough to fool", + "his old friend, whose", + "eyes narrowed at", + "seeing him there.", + " \"How much didst" + ), + new BookPageInfo + ( + "thou hear?\" demanded", + "Lord British.", + " \"Why, nothing,\"", + "managed Blackthorn,", + "his head ducked away", + "from his friend, as", + "he bent to retrieve the", + "fallen chess pieces. \"I" + ), + new BookPageInfo + ( + "merely came for our", + "game of chess.\"", + " Together they", + "righted the pedestal", + "table, and set the", + "pieces upon the black", + "and white squares.", + "\"Such simplicity to" + ), + new BookPageInfo + ( + "the game, Blackthorn,\"", + "mused Lord British,", + "idly brushing one", + "finger against the", + "board. \"Black and", + "white, each to its own", + "color, as if life were", + "so simple. What think" + ), + new BookPageInfo + ( + "you?\"", + " Blackthorn sat", + "heavily on a hassock", + "beside the chess table.", + "\"I think that matters", + "are never so simple,", + "my liege. And that I", + "would regret it deeply" + ), + new BookPageInfo + ( + "if someone, such as a", + "friend, saw it thus.\"", + " Lord British's eyes", + "met his. \"Yet", + "sometimes one must", + "sacrifice a pawn to", + "save a king.\"", + " Lord Blackthorn met" + ), + new BookPageInfo + ( + "his gaze squarely.", + "\"Even pawns have", + "lives and loves at", + "home, my lord.\" Then", + "he reached out for a", + "pawn, and firmly", + "moved it forward two", + "squares. \"Shall we" + ), + new BookPageInfo + ( + "play a game?\" he", + "asked.", + " The chess game that", + "night was a draw,", + "and they played", + "grimly.", + " And the next day,", + "Lord British gathered" + ), + new BookPageInfo + ( + "the nobles to proclaim", + "the idea of a new", + "system of Virtues,", + "and declared that", + "shrines should be", + "built across the land.", + " Lord Blackthorn", + "opposed it bitterly," + ), + new BookPageInfo + ( + "and many thought", + "him strange for doing", + "so, for ever had he", + "been a noble and", + "upright man, and", + "ever had he and Lord", + "British been in", + "accord. Declaring that" + ), + new BookPageInfo + ( + "he should start his", + "own shrine, he", + "departed the castle", + "that day to live in a", + "tower in a lake on the", + "north side of the", + "city.", + " They are still the" + ), + new BookPageInfo + ( + "best of friends, yet a", + "sadness hangs", + "between them, as if", + "they were forced into", + "making choices that", + "appealed not to them.", + "And at night, when I", + "creep softly from one" + ), + new BookPageInfo + ( + "corner of my liege's", + "bedchamber to", + "another, I sometimes", + "see him take a pawn", + "from his night table,", + "and hold it in his", + "hand, and quietly", + "weep." + ), + new BookPageInfo + ( + " But I am but a", + "mouse, and none hear", + "me. This tale goes", + "unknown, save for", + "my writing these", + "enormous letters with", + "mine ink-stained tiny", + "paws for thee to" + ), + new BookPageInfo + ( + "read, for I fear", + "indeed for our world", + "and for our people in", + "these perilous times." + ) + ); + + [Constructible] + public MyStory() : base(Utility.Random(0xFEF, 2), false) + { + } + + public MyStory(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region On the Diversity of Our Land + + public class DiversityOfOurLand : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "On the Diversity of Our Land", "Lord Blackthorn", + new BookPageInfo + ( + " While I deplore the", + "depredations of the", + "misguided and", + "belligerent races with", + "which we share our", + "fair Britannia, and", + "alongside the populace,", + "do mourn the needless" + ), + new BookPageInfo + ( + "deaths that their", + "raids cause, I cannot", + "countenance the policy", + "of wholesale slaughter", + "of these races that", + "seems to be the habit", + "of our soldierly", + "element." + ), + new BookPageInfo + ( + " Can we not regard", + "the ratmen, lizard", + "men, and orcs are", + "fellow intelligent", + "beings with whom we", + "share a planet? Why", + "must we slay them", + "on sight, rather than" + ), + new BookPageInfo + ( + "attempt to engage", + "them in dialogue?", + "There is no policy of", + "shooting at wisps", + "when they grace us", + "with their presence", + "(not that an arrow", + "could do much to" + ), + new BookPageInfo + ( + "pierce them!).", + " To view these", + "creatures as vermin", + "denies their obvious", + "intelligence, and we", + "cannot underestimate", + "the repercussions", + "that their slaughter" + ), + new BookPageInfo + ( + "may have. If we", + "regard the slaying of", + "fellow humans as a", + "crime, so must we", + "regard the killing of", + "an orc.", + " At the same time,", + "should a lizardman" + ), + new BookPageInfo + ( + "slay a human, should", + "we not forgive their", + "ignorance and", + "foolishness? Let us", + "not surrender the", + "high moral ground by", + "descending to", + "bestiality." + ), + new BookPageInfo + ( + " Now, I say not that", + "we should fail to", + "defend ourselves in", + "case of attack, for", + "even amongst humans", + "we see war, we see", + "famine, and we see", + "assault (though we" + ), + new BookPageInfo + ( + "owe a debt of", + "gratitude to our Lord", + "British for", + "preserving us from", + "the worst of these!).", + "However, incursions", + "such as the recent", + "tragedy which cost us" + ), + new BookPageInfo + ( + "the life of Japheth,", + "Guildmaster of", + "Trinsic's Paladins,", + "are folly.", + " I had met Japheth,", + "and like all paladins,", + "he burned with an", + "inner fire. Yet" + ), + new BookPageInfo + ( + "though I had the", + "utmost respect for", + "him, none could deny", + "the hatred that", + "flashed in his eyes at", + "the mere mention of", + "orcs. And thus he", + "carried his battle to" + ), + new BookPageInfo + ( + "the orc camps, and", + "died there, unable to", + "rise above his own", + "childhood experiences", + "depicted in his book,", + "\"The Burning of", + "Trinsic.\" 'Tis a", + "shame that even our" + ), + new BookPageInfo + ( + "mightiest men fall", + "prey to this", + "ignorance!", + " Are there not", + "legends of orcs", + "adopting human", + "children to raise as", + "their own? Tales of" + ), + new BookPageInfo + ( + "complex societies built", + "underground by races", + "we regard as bestial?", + " Let us not repeat", + "the mistake of", + "Japheth of the", + "Paladins, and let us", + "cease to persecute the" + ), + new BookPageInfo + ( + "nonhuman races,", + "before we discover", + "that we are harming", + "ourselves in the", + "process." + ) + ); + + [Constructible] + public DiversityOfOurLand() : base(Utility.Random(0xFEF, 2), false) + { + } + + public DiversityOfOurLand(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Quest of the Virtues + + public class QuestOfVirtues : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Quest of the Virtues", "Autenil", + new BookPageInfo + ( + "Volume 1", + "Chapter 1: Starting out", + "I begin my Quest in the", + "fine bank of Skara Brae.", + "My Quest is to travel by", + "foot to the eight shrines", + "of Britannia. Although", + "this may sound easy, it" + ), + new BookPageInfo + ( + "is hampered because I", + "have forsaken my abilities", + "and worldly possessions.", + "Instead, all that I have", + "to live by are a set of", + "plain clothes, a ship to", + "sail the seas and my", + "diary in which to record" + ), + new BookPageInfo + ( + "my adventures. Onward", + "Ho towards the Shrine of", + "Spirituality!", + "", + "Chapter 2: The Road to", + "Spirituality", + "", + "Since I have forsaken" + ), + new BookPageInfo + ( + "magic as a form of", + "travel, I must find a way", + "to the mainland from this", + "island town. Fortunately,", + "I was able to barter a", + "ride from the ferryman.", + "Upon reaching the", + "mainland, I followed the" + ), + new BookPageInfo + ( + "road until it turned", + "North, yet I must", + "continue Eastward. I", + "paused to listen to the", + "pleasant sounds of the", + "birds chirping and enjoyed", + "the peace away from the", + "busy life. Upon reaching" + ), + new BookPageInfo + ( + "the Hedge Maze I recalled", + "a story about the mage", + "Relvinian in the days of", + "old and turned South to", + "go around it. Possessing", + "no weapons and having", + "forsaken my training, I", + "heeded the sign that said," + ), + new BookPageInfo + ( + "\"Enter and Become One", + "Among Ghosts.\" The River", + "forced me to turn South", + "and then continue East.", + "", + "Chapter 3: Spirituality", + "", + "Spirituality is the leader" + ), + new BookPageInfo + ( + "of the Virtues. It is the", + "meditation and", + "understanding of all other", + "Virtues. Without", + "Spirituality, one cannot", + "completely follow the", + "Virtues, for It is the", + "dedication and adherance" + ), + new BookPageInfo + ( + "to them.", + "", + "Chapter 4: Finding Honor", + "", + "My next visit will be to", + "the Shrine of Honor,", + "which lies a fair distance", + "to the South. There is a" + ), + new BookPageInfo + ( + "road to my East that I", + "will follow to the town", + "of Trinsic. I found a", + "warm room at the", + "Traveller's Inn, and woke", + "refreshed in the morning", + "to hear the sounds of", + "nature as I prepared to" + ), + new BookPageInfo + ( + "continue my journeys. I", + "thanked the kind innkeeper", + "and headed out of Trinsic", + "and South. I conversed", + "briefly with one lucky", + "enough to own a house in", + "the beautiful country and", + "he bade me good fortune" + ), + new BookPageInfo + ( + "on my travels. I used my", + "rusty blade to cut", + "through dense jungles", + "past ruins of a forgotten", + "realm, now inhabited only", + "by the Undead. Many a", + "mongbat did hamper my", + "journey, but finally I" + ), + new BookPageInfo + ( + "arrived at the Shrine of", + "Honor.", + "", + "Chapter 5: Honor", + "", + "Many link Honor and", + "battle, but it can be", + "used with any aspect of" + ), + new BookPageInfo + ( + "Life. Honor is to abide", + "by the rules, dishonor is", + "to cheat; to seek the", + "unfair advantage. I vowed", + "to always live life with", + "Honor.", + "", + "Chapter 6: Seeking Valor" + ), + new BookPageInfo + ( + "I must now embark on my", + "trusty small ship, the", + "Hollandia, to the South", + "and East, to a small", + "island where few have", + "travelled. I know not yet", + "what I will encounter at", + "sea, so I bid the Virtues" + ), + new BookPageInfo + ( + "grant me safety. So", + "begins my voyage. I", + "managed to sail unnoticed", + "past some water", + "elementals which took a", + "fair bit of navigation", + "from my tillerman.", + "However, I arrived without" + ), + new BookPageInfo + ( + "incident.", + "", + "Chapter 7: Valor", + "", + "The Shrine of Valor is", + "protected by many a", + "beast far too poisonous", + "and foul for myself to" + ), + new BookPageInfo + ( + "vanquish. One mush show", + "Valor to approach the", + "Shrine! Valor is often", + "shown in one's willingness", + "to fight what maybe a", + "losing battle upon which", + "he believes. It takes", + "Valor to stand your" + ), + new BookPageInfo + ( + "ground against the many", + "murderers and lawbreakers", + "in our lands. You may", + "lose, but you show Valor", + "in that you fight that", + "which must be opposed.", + "Fight the fights you", + "believe in, not just the" + ), + new BookPageInfo + ( + "fights you think you can", + "win.", + "", + "Chapter 8: The Voyage to", + "Humility", + "", + "My journey will continue", + "to the East towards the" + ), + new BookPageInfo + ( + "Shrine of Humility. I", + "launch my boat from the", + "West side of the Island", + "of Valor, where I made", + "my daring escape from", + "the many Giant Serpents", + "chasing me with their", + "poisonous venom and" + ), + new BookPageInfo + ( + "hissing tongues. Beautiful", + "blue waves washed over", + "the bow of the boat as", + "dolphins played, merrily", + "leading me on. The voyage", + "is long and the water", + "turbulent but finally land", + "was struck. Quickly I ran," + ), + new BookPageInfo + ( + "eager to find my final", + "destination for the day.", + "", + "Chapter 9: Humility", + "", + "The Shrine of Humility is", + "surprisingly spartan; it is", + "merely a grove of stone" + ), + new BookPageInfo + ( + "pillars with an ankh and", + "the Humility stone at its", + "center. I would", + "characterize Humility as", + "this Quest; returning to", + "my roots in this world. I", + "have rejected my", + "possessions and my wealth" + ), + new BookPageInfo + ( + "in order to rely only", + "upon my cunning and", + "instincts. No longer have", + "I that which makes me", + "Glorious to others, but I", + "have only that which I", + "need to survive. I may no", + "longer rely upon myself, I" + ), + new BookPageInfo + ( + "must rely upon others", + "for my survival. My", + "journey to Humility has", + "only made me realize even", + "more how Blessed I have", + "been." + ), + new BookPageInfo + ( + "Chapter 10: Onward to", + "Honesty", + "", + "Now the journey will turn", + "South towards the Island", + "of Ice. However, my", + "voyages and excursions", + "into the jungle have made" + ), + new BookPageInfo + ( + "me quite tired, so I will", + "camp here beside a river", + "near the Shrine of", + "Humility for the night. I", + "awake the next morning", + "refreshed and invigorated,", + "but also under attack! A", + "Headless One has noticed" + ), + new BookPageInfo + ( + "my rise from slumber and", + "attacks viciously. My", + "trusty cleaver was in my", + "hand instantly, but my", + "lack of skill with the", + "weapon delayed the death", + "of the creature. I", + "launched the Hollandia and" + ), + new BookPageInfo + ( + "set sail for the Island of", + "Ice, seeking the Shrine of", + "Honesty. As I sail the", + "vast oceans, I find myself", + "desiring the company of", + "my fellow man. Hopefully I", + "shall meet some kind of", + "traveller with whom I may" + ), + new BookPageInfo + ( + "exchange a few words.", + "Shortly I was landing my", + "boat on the North end of", + "the Island of Ice. I", + "quickly made my way", + "through snow across the", + "frigid tundra while trying", + "to keep warm. The Shrine" + ), + new BookPageInfo + ( + "of Honesty bid me", + "welcome as I felth the", + "warmth radiate throughout", + "me.", + "", + "Chapter 11: Honesty", + "", + "Honesty is to uphold and" + ), + new BookPageInfo + ( + "defend the truth at all", + "times. Furthermore,", + "Honesty requires us to", + "be fair and true to our", + "fellow man; not taking", + "undue advantage. Honesty", + "is a Virtue often lacking", + "in today's world. It seems" + ), + new BookPageInfo + ( + "as though people are out", + "to gain wealth with no", + "regard to Honesty", + "towards other people.", + "Honesty is the foundation", + "upon which trust is built.", + "If the foundation", + "crumbles, everything built" + ), + new BookPageInfo + ( + "upon it must fall. The", + "cold environment which", + "houses the Shrine of", + "Honesty is a testament", + "to its value in today's", + "society. The symbolic cold", + "and secluded location", + "shows us that only the" + ), + new BookPageInfo + ( + "most dedicated to", + "pursuing Honesty will", + "achieve it. May we all be", + "Honest with our fellow", + "man and remember to", + "treat them how we would", + "like to be treated." + ), + new BookPageInfo + ( + "Chapter 12: The Path to", + "Sacrifice.", + "", + "I made my way to the", + "West side of the Island", + "of Ice. From there I", + "launch the Hollandia and", + "sail slightly to the North" + ), + new BookPageInfo + ( + "and West. I land my boat", + "just East of the Shrine", + "of Sacrifice, so my road", + "is West. Although I enjoy", + "the sea, I am happy to", + "be back on the mainland", + "for the final three", + "Shrines." + ) + ); + + [Constructible] + public QuestOfVirtues() : base(Utility.Random(0xFEF, 2), false) + { + } + + public QuestOfVirtues(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Regarding Llamas + + public class RegardingLlamas : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Regarding Llamas", "Simon", + new BookPageInfo + ( + " Llamas are curious", + "beasts, shaggy and", + "sought after for their", + "wool, yet of a", + "curiously arrogant", + "disposition reflected", + "in their eyes. They", + "live in mountainous" + ), + new BookPageInfo + ( + "areas, though who", + "may have first tamed", + "them is lost in the", + "mists of history.", + " 'Tis a well-known", + "fact that llamas can", + "indeed be tamed, and", + "used as grazing" + ), + new BookPageInfo + ( + "animals, for their", + "meat, and of course", + "for their wool. Yet", + "'tis lesser known that", + "their ornery", + "disposition and", + "tendency to spit at", + "those they dislike" + ), + new BookPageInfo + ( + "makes them appealing", + "guard creatures as", + "well, though they", + "have little sound with", + "which to sound an", + "alarum." + ) + ); + + [Constructible] + public RegardingLlamas() : base(Utility.Random(0xFEF, 2), false) + { + } + + public RegardingLlamas(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Talking to Wisps + + public class TalkingToWisps : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Talking to Wisps", "Yorick ofMoonglow", + new BookPageInfo + ( + "This volume was", + "sponsored by", + "donations from Lord", + "Blackthorn, ever a", + "supporter of", + "understanding the", + "other sentient races", + "of Britannia." + ), + new BookPageInfo + ( + "-", + " Wisps are the most", + "intelligent of the", + "nonhuman races", + "inhabiting Britannia.", + "'Tis claimed by the", + "great sages that", + "someday we shall be" + ), + new BookPageInfo + ( + "able to converse with", + "them openly in our", + "native", + "tongue--indeed, we", + "must hope that wisps", + "learn our language,", + "for it is not possible", + "for humans to" + ), + new BookPageInfo + ( + "pronounce wispish!", + " The wispish", + "language seems to", + "only contain one", + "vowel, the letter Y.", + "However, the letters", + "W, C, M, and L seem", + "to be treated" + ), + new BookPageInfo + ( + "grammatically as", + "vowels, and in", + "addition every letter", + "is followed by what", + "sounds to the human", + "ear like a glottal stop.", + "It is possible that the", + "glottal stop is" + ), + new BookPageInfo + ( + "considered a vowel as", + "well.", + " Wisps do make use", + "of what sound to us", + "like pitch and", + "emphasis shifts", + "similar to", + "exclamations and" + ), + new BookPageInfo + ( + "questions.", + " The average word is", + "wispish seems to", + "consist of three", + "phonemes and three", + "glottal stops, plus", + "possibly a pitch shift.", + "It often sounds like a" + ), + new BookPageInfo + ( + "fire burning or", + "crackling. Some have", + "speculated that what", + "we are analyzing is", + "in fact nothing more", + "than the very air", + "crackling near the", + "wisp's glow, and not" + ), + new BookPageInfo + ( + "language, but this is", + "of course unlikely." + ) + ); + + [Constructible] + public TalkingToWisps() : base(Utility.Random(0xFEF, 2), false) + { + } + + public TalkingToWisps(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Taming Dragons + + public class TamingDragons : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Taming Dragons", "Wyrd Beastmaster", + new BookPageInfo + ( + " I have not much to", + "tell about dragons. The", + "sole time I approached", + "one with an eye", + "towards taming it,", + "my initial attempts at", + "calming it met with", + "failure. It fixed a" + ), + new BookPageInfo + ( + "massive beady eye", + "upon me, and began", + "its slithering", + "approach, intending no", + "doubt to insert me", + "into its maw and bear", + "down with its teeth.", + " However, as I was" + ), + new BookPageInfo + ( + "engaged in what", + "remains to this day", + "the most terrifying", + "combat of my life,", + "the dragon suddenly", + "whirled as if in a", + "panic, ran a short", + "distance, took off into" + ), + new BookPageInfo + ( + "the air, then", + "transformed into a", + "whirlwind. Lastly, it", + "exploded, showering", + "gouts of black blood", + "and heaving, stinking", + "flesh upon miles of", + "countryside. The" + ), + new BookPageInfo + ( + "fireball was massive,", + "enough to light a city,", + "I should surmise.", + " I never did discover", + "the exact cause of", + "this strange behavior,", + "except to assume that", + "it was not typical for" + ), + new BookPageInfo + ( + "this reptilian species.", + "My best guesses", + "revolve around a", + "magical fracture in", + "the nature of reality,", + "which is far too", + "esoteric a territory", + "for one of my limited" + ), + new BookPageInfo + ( + "scholarship.", + " Hence my basic", + "advice to those who", + "seek to tame a", + "dragon-be sure that", + "thou hast mastered", + "the twin skills of", + "taming animals, and" + ), + new BookPageInfo + ( + "running away very", + "very fast." + ) + ); + + [Constructible] + public TamingDragons() : base(Utility.Random(0xFEF, 2), false) + { + } + + public TamingDragons(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Bold Stranger + + public class BoldStranger : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Bold Stranger", "Old Fabio the Poor", + new BookPageInfo + ( + " In a time before", + "time, the Gods that Be", + "assembled a group of", + "artisans, craftsmen", + "and lore masters", + "(for, yes, even in", + "those days, art", + "existed) to create the" + ), + new BookPageInfo + ( + "world of Sosaria. To", + "this group, the gods", + "gave a tiny world,", + "Rytabul, in which to", + "test their works, to", + "see if they were of", + "the quality desired", + "for the true world in" + ), + new BookPageInfo + ( + "which they would be", + "placed. And though", + "the gods were tight", + "fisted with their gold,", + "this small crew", + "worked hard and long,", + "and were happy in", + "their tasks." + ), + new BookPageInfo + ( + " A small corner of", + "Rytabul had been", + "claimed by the artisan", + "Selrahc the Slow.", + "Though he was not", + "the fastest of the", + "assembled workers,", + "the gods smiled upon" + ), + new BookPageInfo + ( + "his work, even", + "presenting him with", + "a mystic talisman", + "proclaiming his work", + "the best among the", + "newer artisans. And", + "so Selrahc went about", + "his business, creating" + ), + new BookPageInfo + ( + "hundreds of designs", + "which would one day", + "add color and variety", + "to Sosaria.", + " One day a", + "stranger appeared to", + "Selrahc. His chest", + "was bare and he wore" + ), + new BookPageInfo + ( + "trousers of the", + "brightest green, and", + "wherever he went,", + "plants grew in his", + "footsteps. This", + "caused Selrahc no end", + "of trouble, the", + "stranger always" + ), + new BookPageInfo + ( + "looking over his", + "shoulder, and the", + "plants sprouting in", + "places Selrahc", + "required to ply his", + "art. And so Selrahc", + "approached the", + "stranger and bade" + ), + new BookPageInfo + ( + "him speak. But this", + "man in green", + "remained silent.", + "Selrahc pleaded with", + "the stranger to give", + "his name, and would", + "he please leave", + "Selrahc to his work." + ), + new BookPageInfo + ( + "But this mysterious", + "stranger remained", + "mute.", + " This angered", + "Selrahc mightily. Who", + "was this silent man,", + "interfering with", + "tasks the gods" + ), + new BookPageInfo + ( + "themselves had", + "entrusted to Selrahc?", + "In an attempt to", + "embarrass this", + "interloper, Selrahc", + "stole his green", + "trousers, leaving him", + "naked and open to" + ), + new BookPageInfo + ( + "comments about his", + "very manhood, and", + "still the stranger", + "would not speak,", + "would not leave this", + "tiny corner of", + "Rytabul.", + " Vexed to his very" + ), + new BookPageInfo + ( + "limits, Selrahc took", + "his war axe and", + "smote the silent one", + "mightily, again and", + "again, until the silent", + "stranger ran away,", + "having never said a", + "word, and never" + ), + new BookPageInfo + ( + "showed himself in", + "Rytabul again.", + " Thus endeth the", + "tale of the bold", + "stranger." + ) + ); + + [Constructible] + public BoldStranger() : base(Utility.Random(0xFEF, 2), false) + { + } + + public BoldStranger(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Burning of Trinsic + + public class BurningOfTrinsic : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Burning of Trinsic", "Japheth of Trinsic", + new BookPageInfo + ( + " 'Twas a sight to", + "see, the sunlight", + "falling lightly on the", + "sandstone walls of", + "Trinsic 'pon a", + "morning in spring.", + " Children ran along", + "the parapets and" + ), + new BookPageInfo + ( + "walkways, their", + "laughter and running", + "providing music to the", + "daybreak, despite", + "their oft-ragged", + "clothing.", + " And I was one of", + "those young ones," + ), + new BookPageInfo + ( + "letting my joy rise", + "up to the skies.", + " Little did we all", + "know of the darker", + "days that would lie", + "ahead, for we were", + "too young.", + " Had we but gained" + ), + new BookPageInfo + ( + "access to the quiet", + "councils held in the", + "Paladin tower as it", + "faced the sea,", + "councils lit by", + "candlelight and", + "worry, we would", + "have learned more of" + ), + new BookPageInfo + ( + "the fears of", + "imminent attack from", + "the forest, where", + "foul creatures born", + "of dank caves and", + "darkness were", + "marauding ever more", + "often into the lands" + ), + new BookPageInfo + ( + "around Trinsic's", + "moat.", + " But we were", + "children! The", + "parapets and the moat", + "were places to play,", + "not stout defenses,", + "and we gave no" + ), + new BookPageInfo + ( + "thought to the", + "necessities that must", + "have required their", + "construction.", + " We used to reach", + "the sheltered", + "orchards on the lee", + "side of the parapet" + ), + new BookPageInfo + ( + "walls, where the", + "southern river cut", + "through the city, by", + "swimming across the", + "water.", + " The rich folk who", + "lived in the great", + "manses there would" + ), + new BookPageInfo + ( + "shout from their", + "windows and shake", + "their fists, for we", + "would run through", + "their gardens and", + "tear up the delicate", + "foxgloves and", + "orfleurs with our" + ), + new BookPageInfo + ( + "unshod dirty feet.", + "Then we would dive", + "into the water and", + "splash merrily to the", + "fruit trees.", + " The southern", + "river lazily slid", + "under the an ungated" + ), + new BookPageInfo + ( + "arch in the mighty", + "wall, and we would", + "lay on the grassy", + "bank and watch it", + "gurgle by the lily", + "pads.", + " That spring that", + "pleasant spot became" + ), + new BookPageInfo + ( + "the doorway through", + "which our city of", + "Trinsic let in the", + "monstrous deformed", + "humanoids that", + "savaged us. I lay upon", + "that grassy bank and", + "watched them wade" + ), + new BookPageInfo + ( + "in, their coarse hair", + "wet and matted, algae", + "and muck festooning", + "their wild brows.", + " They caught sight", + "of a quicksilver girl", + "with bright blond hair", + "and lively eyes. Her" + ), + new BookPageInfo + ( + "name was Leyla, and", + "that spring I had held", + "fond dreams of", + "holding her hand and", + "sharing flavored ice", + "while dangling our", + "feet off the small", + "bridge by Smugglers" + ), + new BookPageInfo + ( + "Gate.", + " And I said nothing", + "when they caught", + "her, and did not cry", + "out when they", + "dragged her off", + "through that breach in", + "our wall, and did not" + ), + new BookPageInfo + ( + "warn the city when I", + "saw the helmeted orc", + "captains call the", + "charge upon the", + "mansions.", + " Blame me not, for", + "I was but a child, and", + "one who hid in the" + ), + new BookPageInfo + ( + "branches of the peach", + "trees, all a-tremble", + "whilst I watched the", + "smoke rise from Sean", + "the tailor's, and fire", + "lash out at the roof of", + "witchy Eleanor's", + "tavern." + ), + new BookPageInfo + ( + " To this day I have", + "had no word of", + "Leyla, and to this", + "day the smell of", + "burning wood can", + "conjure terrible", + "dreams. Yet with the", + "eyes of adulthood, 'tis" + ), + new BookPageInfo + ( + "possible to examine", + "the flaws in the", + "defense of Trinsic on", + "that fateful day, and", + "the reasons why our", + "walls are now", + "double-thick, and", + "why our buildings" + ), + new BookPageInfo + ( + "are now built as", + "fortresses within a", + "somber fortified city.", + " While I can look", + "out from the top of", + "the new Paladin", + "tower, and spy the", + "mighty white sails" + ), + new BookPageInfo + ( + "across the barrier", + "island, and can", + "descry the small", + "hollow south of the", + "city where gypsies", + "are wont to camp, I", + "can also envision the", + "city as it might be" + ), + new BookPageInfo + ( + "burning, and I bless", + "the bargain we made:", + "space for safety,", + "grace for sturdiness,", + "and wood for stone.", + " Whilst I live, I", + "shall not see Trinsic", + "burn, and no more" + ), + new BookPageInfo + ( + "cries of little girls", + "will haunt the sleep", + "of our fair citizens.", + " - Japheth, Paladin", + "Guildmaster of the", + "City of Trinsic" + ) + ); + + [Constructible] + public BurningOfTrinsic() : base(Utility.Random(0xFEF, 2), false) + { + } + + public BurningOfTrinsic(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Fight + + public class TheFight : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Fight", "M. de la Garza", + new BookPageInfo + ( + " A cold autumn's", + "morning with misty", + "fog secures a dozen", + "brave knights,", + "supplying hidden", + "shelter from prying", + "eyes deep in the", + "foothills of the" + ), + new BookPageInfo + ( + "vibrant valley.", + "Dragons soar like", + "fierce warriors,", + "circling around and", + "around, then roaring", + "like thunder, rallying", + "all that listen. The", + "dragons land swiftly" + ), + new BookPageInfo + ( + "beside the proud", + "warriors, bending", + "necks and extending", + "wings, lifting black", + "claws and allowing", + "valiant fighters to", + "ride forth and win an", + "arisen battle. The" + ), + new BookPageInfo + ( + "increasing winds", + "silence the sounds of", + "combat, and they", + "fight, standing their", + "ground like mothers", + "protecting their", + "childern, bright", + "armor flashing as" + ), + new BookPageInfo + ( + "each one falls.", + " A cold autumn's", + "evening with misty", + "fog cradles a dozen", + "battered corpses of", + "knights, creasing", + "them in currents of", + "winds that run deep" + ), + new BookPageInfo + ( + "in the foothills of the", + "desolate valley.", + "Dragons glide like", + "silent angels, circling", + "around and around,", + "then calling like", + "banshees; keening", + "cries of mourning." + ), + new BookPageInfo + ( + "The dragons land", + "heavily beside the", + "peaceful bodies,", + "bending necks and", + "extending wings,", + "lifting black claws", + "and allowing valiant", + "fighters to ride forth" + ), + new BookPageInfo + ( + "and win an arisen", + "battle. The increasing", + "winds silence the", + "sounds of combat, and", + "they fight, standing", + "their ground like", + "mothers protecting", + "their childern, bright" + ), + new BookPageInfo + ( + "armor flashing as", + "each one falls.", + " A cold autumn's", + "evening with misty", + "fog cradles a dozen", + "battered corpses of", + "knights, creasing", + "them in currents of" + ), + new BookPageInfo + ( + "winds that run deep", + "in the foothills of the", + "desolate valley.", + "Dragons glide like", + "silent angels, circling", + "around and around,", + "then calling like", + "banshees; keening" + ), + new BookPageInfo + ( + "cries of mourning.", + "The dragons land", + "heavily beside the", + "peaceful bodies,", + "bending necks and", + "extending wings,", + "lifting black claws", + "and pinching the" + ), + new BookPageInfo + ( + "sacred ground and", + "new eternal home.", + "The dying winds", + "whistle among the", + "dead in somber", + "procession, and they", + "lie, grasping weapons", + "to protect themselves" + ), + new BookPageInfo + ( + "like knights still in", + "battle, shattered", + "armor shining like", + "newly born stars." + ) + ); + + [Constructible] + public TheFight() : base(Utility.Random(0xFEF, 2), false) + { + } + + public TheFight(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Life of a Travelling Minstrel + + public class LifeOfATravellingMinstrel : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Life of a Travelling Minstrel", "Sarah of Yew", + new BookPageInfo + ( + " While 'tis true that", + "the musician who", + "seeketh only to make", + "sweet music for", + "herself and for", + "others needs little", + "more than some", + "talent, and stern" + ), + new BookPageInfo + ( + "practice at the chosen", + "instrument, those of", + "us who seek the open", + "road shall find indeed", + "that a greater skill is", + "required. Herein", + "discover those secrets", + "which I have learned" + ), + new BookPageInfo + ( + "over the years as an", + "itinerant performer...", + " Once I was in", + "Jhelom, and", + "accidentally angered a", + "bravo of some local", + "repute, whose blade", + "flickered all too" + ), + new BookPageInfo + ( + "eagerly near my", + "slender neck (for I", + "was young then).", + "After various threats", + "to \"ruin my pretty", + "face\" this bravo", + "grabbed my arm in a", + "most unseemly" + ), + new BookPageInfo + ( + "fashion and tossed", + "me into a barbaric", + "enclosure locally", + "entitled a dueling pit.", + "My plaintive cries", + "for help went", + "unheeded by the", + "guards, for the" + ), + new BookPageInfo + ( + "inhabitants of Jhelom", + "are eager indeed to", + "measure fighting", + "prowess at any time!", + " What saved me was", + "the ability to", + "improvise a melody", + "and tune that" + ), + new BookPageInfo + ( + "satirized the", + "proceedings, and", + "sufficiently angered", + "an onlooker to prod", + "him to coming to my", + "defense. Once that", + "fight was underway,", + "I was able to make" + ), + new BookPageInfo + ( + "good my escape.", + "Hence, I regard the", + "ability to incite fights", + "as indispensable to", + "the prudent bard.", + " Upon another", + "occasion, 'twas the", + "obverse side of that" + ), + new BookPageInfo + ( + "coin which saved me,", + "for I was being held", + "prisoner by a", + "particularly nasty", + "band of ruffians who", + "had seized me", + "unawares from the", + "road to Vesper." + ), + new BookPageInfo + ( + " They had worked", + "themselves into a", + "frenzy and were", + "ready to attack and I", + "fear, tear me limb", + "from limb, when I", + "began to sing", + "frantically, tapping" + ), + new BookPageInfo + ( + "my falled drum with", + "my tied up feet. The", + "melody developed into", + "a soothing one, and", + "the brigands slowly", + "calmed down to the", + "extent of apologizing,", + "and they let me go!" + ), + new BookPageInfo + ( + " A final example I", + "would pray you grant", + "your attention: once I", + "was lost upon a large", + "isle far to the east of", + "the mainland, well", + "beyond Serpent's", + "Hold, where lava" + ), + new BookPageInfo + ( + "made its sluggish", + "way across the", + "surface landscape.", + "And this accursed", + "land was filled with", + "vile beasts and", + "cunning dragons.", + " I was being pursued" + ), + new BookPageInfo + ( + "by one of said fell", + "dragons when I found", + "myself trapped. I", + "quickly skirted a", + "bubbling pool of molten", + "rock and attempted to", + "hide.", + " The dragon scented" + ), + new BookPageInfo + ( + "me and was", + "preparing to skirt the", + "pool, when I began to", + "play a lusty tune", + "upon my lute that", + "attracted its attention.", + "Mesmerized and", + "enticed by the" + ), + new BookPageInfo + ( + "melody, it stepped", + "directly toward sme,", + "and into the", + "lava-where its foot", + "was so burned that it", + "quickly hopped away,", + "undignified and", + "annoyed." + ), + new BookPageInfo + ( + " 'Tis my fond hope", + "that other travelling", + "minstrels shall learn", + "from my experiences", + "and apply themselves", + "to practicing these", + "skills in order to", + "preserve life and" + ), + new BookPageInfo + ( + "limb." + ) + ); + + [Constructible] + public LifeOfATravellingMinstrel() : base(Utility.Random(0xFEF, 2), false) + { + } + + public LifeOfATravellingMinstrel(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Major Trade Associations + + public class MajorTradeAssociation : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Major Trade Associations", "Pieter of Vesper", + new BookPageInfo + ( + " There are ten major", + "trade associations that", + "operate legitimately in", + "the lands of Britannia", + "and among its trading", + "partners. Many of", + "these guilds are", + "divided into local or" + ), + new BookPageInfo + ( + "specialty subguilds,", + "who use the same", + "colors but vary the", + "heraldic pattern.", + " There are many", + "lesser trade", + "associations that have", + "closed membership," + ), + new BookPageInfo + ( + "and one can join them", + "only by invitation.", + "Beltran's Guide to", + "Guilds is the", + "definitive text on the", + "full range of guilds", + "and other associations", + "in Britannia, and I" + ), + new BookPageInfo + ( + "heartily recommend", + "it.", + " In what follows I", + "have attempted to", + "bring together the", + "known information", + "regarding these", + "guilds. I offer thee" + ), + new BookPageInfo + ( + "the name, typical", + "membership, heraldic", + "colors, known", + "specialty", + "organizations within", + "the larger guild, and", + "any known", + "affiliations to other" + ), + new BookPageInfo + ( + "guilds, which often", + "occur because of", + "trade reasons.", + "", + "The Guild of Arcane", + "Arts", + "Members: alchemists", + "and wizards" + ), + new BookPageInfo + ( + "Colors: blue and purple", + "Subguilds: Illusionists,", + "Mages, Wizards", + "Affiliations: Healer's", + "Guild", + "", + "The Warrior's Guild", + "Members:" + ), + new BookPageInfo + ( + "mercenaries,", + "soldiery, guardsmen,", + "weapons masters,", + "paladins.", + "Colors: Blue and red", + "Subguilds: Cavalry,", + "Fighters, Warriors", + "Affiliations: League" + ), + new BookPageInfo + ( + "of Rangers", + "", + "League of Rangers", + "Members: rangers,", + "bowyers, animal", + "trainers", + "Colors: Red, gold and", + "blue" + ), + new BookPageInfo + ( + "", + "Guild of Healers", + "Members: healers", + "Colors: Green, gold,", + "and purple", + "Affiliations: Guild of", + "Arcane Arts" + ), + new BookPageInfo + ( + "Mining Cooperative", + "Members: miners", + "Colors: blue and black", + "checkers, with a gold", + "cross", + "Affiliations: Order of", + "Engineers" + ), + new BookPageInfo + ( + "Merchants'", + "Association", + "Members:", + "innkeepers,", + "tavernkeepers,", + "jewelers,", + "provisioners", + "Colors: gold coins on a" + ), + new BookPageInfo + ( + "green field for", + "Merchants. White", + "and green for the", + "others.", + "Subguilds: Barters,", + "Provisioners,", + "Traders, Merchants" + ), + new BookPageInfo + ( + "Order of Engineers", + "Members: tinkers and", + "engineers", + "Colors: Blue, gold, and", + "purple vertical bars", + "Affiliations: Mining", + "Cooperative" + ), + new BookPageInfo + ( + "Society of Clothiers", + "Members: tailors and", + "weavers", + "Colors: Purple, gold,", + "and red horizontal", + "bars", + "", + "Maritime Guild" + ), + new BookPageInfo + ( + "Members: fishermen,", + "sailors, mapmakers,", + "shipwrights", + "Colors: blue and white", + "Subguilds:", + "Fishermen, Sailors,", + "Shipwrights" + ), + new BookPageInfo + ( + "Bardic Collegium", + "Members: bards,", + "musicians,", + "storytellers, and other", + "performers", + "Colors: Purple, red", + "and gold checkerboard" + ), + new BookPageInfo + ( + "Society of Thieves", + "Members: beggars,", + "cutpurses, assassins,", + "and brigands", + "Colors: red and black", + "Subguilds: Rogues", + "(beggars), Assassins,", + "Thieves" + ) + ); + + [Constructible] + public MajorTradeAssociation() : base(Utility.Random(0xFEF, 2), false) + { + } + + public MajorTradeAssociation(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Rankings of Trades + + public class RankingsOfTrades : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Rankings of Trades", "Lord Higginbotham", + new BookPageInfo + ( + " Whilst 'tis true that", + "within each trade, one", + "finds differing titles", + "and accolades granted", + "to the members of a", + "given guild,", + "nonetheless for the", + "betterment of trade" + ), + new BookPageInfo + ( + "and understanding,", + "we must have a", + "commonality of", + "titling.", + " For those who may", + "find themselves", + "ignorant of the finer", + "distinctions between a" + ), + new BookPageInfo + ( + "three-knot member of", + "the Sailors' Maritime", + "Association and a", + "second thaumaturge,", + "this book shall serve", + "as a simple", + "introduction to the", + "common cant used" + ), + new BookPageInfo + ( + "when members of", + "differing guilds and", + "trade organizations", + "must trade with each", + "other and must", + "establish relative", + "credentials.", + " Neophyte" + ), + new BookPageInfo + ( + "Has shown interest", + "in learning the craft", + "and some meager", + "talent.", + " Novice", + "Is practicing basic", + "skills but has not been", + "admitted to full" + ), + new BookPageInfo + ( + "standing.", + " Apprentice", + "A student of the", + "discipline.", + " Journeyman", + "Warranted to practice", + "the discipline under", + "the eyes of a tutor." + ), + new BookPageInfo + ( + " Expert", + "A full member of the", + "guild.", + " Adept", + "A member of the", + "guild qualified to", + "teach others.", + " Master" + ), + new BookPageInfo + ( + "Acknowledged as", + "qualified to lead a hall", + "or business.", + " Grandmaster", + "Rarely a permanent", + "title, granted in", + "common parlance to", + "those who have" + ), + new BookPageInfo + ( + "shown extreme", + "mastery of their", + "craft recently." + ) + ); + + [Constructible] + public RankingsOfTrades() : base(Utility.Random(0xFEF, 2), false) + { + } + + public RankingsOfTrades(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region The Wild Girl of the Forest + + public class WildGirlOfTheForest : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "The Wild Girl of the Forest", "Horace the Trader", + new BookPageInfo + ( + " Her name was", + "Leyla, she said, and", + "her hair was braided", + "wild with creepers", + "and thorns. I", + "marveled that they", + "did not hurt her, but", + "when I asked, she but" + ), + new BookPageInfo + ( + "shrugged and let her", + "eyes roam once more", + "across the woods.", + "Though I had my", + "hands securely", + "fastened by her", + "ropes, I itched to", + "reach out and comb" + ), + new BookPageInfo + ( + "that unruly golden", + "mane, dirtied and", + "leaf-ridden.", + " Her provenance,", + "she told me over", + "nights illumined by", + "campfires, was once", + "the city of Trinsic." + ), + new BookPageInfo + ( + "She claimed to have", + "been kidnapped and", + "raised by orcs, which", + "I judged an unlikely", + "tale, for all know orcs", + "delight in eating the", + "meat of honest folk.", + "When I told her this," + ), + new BookPageInfo + ( + "she laughed a fey", + "laugh, and gaily", + "admitted that honest", + "she was not, for oft", + "had she stolen folk", + "away from caravans", + "to loot their", + "possessions from an" + ), + new BookPageInfo + ( + "unconscious body!", + " At this, I began to", + "fear for my life, and", + "her smile seemed full", + "of teeth sharper than", + "a human ought to", + "have, for the tale of", + "orcish raising had" + ), + new BookPageInfo + ( + "struck fear into the", + "marrow of my bones.", + "\"Wilt thou eat me?\" I", + "asked, a-tremble,", + "fearing the answer.", + " And she cocked", + "her head at me, like a", + "wild animal facing a" + ), + new BookPageInfo + ( + "word that it dost not", + "understand, and the", + "fixity in her eyes", + "was a glimpse into", + "the deeper reaches of", + "the Abyss. But she", + "finally grunted, and", + "said, \"Nay,\" in a" + ), + new BookPageInfo + ( + "voice that recalled to", + "me a child. \"Nay,\"", + "she said, \"for thou", + "dost remind me of a", + "boy I knew once,", + "when I was a girl", + "who played in a city", + "of great sandstone" + ), + new BookPageInfo + ( + "walls, before I was", + "taken. He had sandy", + "hair like thee, and I", + "dreamt as a child of", + "holding his hand and", + "sharing flavored ice.", + "His name was", + "Japheth.\"" + ), + new BookPageInfo + ( + " The next morning", + "she let me go,", + "stripped of my pouch", + "and clothes, and bade", + "me run through the", + "woods, and to fear", + "recapture, for surely", + "her heart would not" + ), + new BookPageInfo + ( + "soften again. 'Twas a", + "fearful run, and I", + "came to the road to", + "Yew with welts and", + "scratches run", + "rampant crost my", + "skin, but I did not see", + "her again." + ), + new BookPageInfo + ( + " Oft have I", + "wondered of the boy", + "named Japheth, and", + "whether he", + "remembers a girl who", + "lived in sandstone", + "walls. The only", + "Japheth I know is the" + ), + new BookPageInfo + ( + "Guildmaster of", + "Paladins who died", + "last year warring", + "amidst the orcs, and", + "though he had indeed", + "sandy hair, I cannot", + "picture him side by", + "side with a feral girl" + ), + new BookPageInfo + ( + "whose tongue has", + "tasted of human", + "flesh.", + " Yet the paths of", + "fate are strange", + "indeed, and I suppose", + "'tis possible that this", + "paladin died" + ), + new BookPageInfo + ( + "defending his", + "remembered lady's", + "honor, unknowingly", + "struck down by the", + "orc that she called", + "father." + ) + ); + + [Constructible] + public WildGirlOfTheForest() : base(Utility.Random(0xFEF, 2), false) + { + } + + public WildGirlOfTheForest(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Treatise on Alchemy + + public class TreatiseOnAlchemy : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Treatise on Alchemy", "Felicia Hierophant", + new BookPageInfo + ( + " The alchemical", + "arts are notable for", + "their deceptive", + "simplicity. 'Tis true", + "that to our best", + "knowledge currently,", + "there are but eight", + "valid potions that can" + ), + new BookPageInfo + ( + "be made (though I", + "emphasize that new", + "discoveries may", + "always await).", + "However, the delicate", + "balance of confecting", + "the potions is", + "difficult indeed, and" + ), + new BookPageInfo + ( + "requires great skill.", + " To give thee an", + "example of the", + "simpler potions that", + "can be created by", + "those well-versed in", + "the subtleties of", + "alchemy:" + ), + new BookPageInfo + ( + " Black pearl, that", + "rare substance that is", + "oft found lying", + "unannounced upon the", + "surface of the", + "ground, when", + "properly crushed", + "with mortar and" + ), + new BookPageInfo + ( + "pestle, can yield a", + "fine powder. Said", + "powder in the proper", + "proportions when", + "mixed via the", + "alchemical arts can", + "yield a wonderfully", + "refreshing drink." + ), + new BookPageInfo + ( + " The revolting blood", + "moss so gingerly", + "scraped off of", + "windowsills by", + "fastidious housewives", + "is but a tiny cousin to", + "the wilder version,", + "which when properly" + ), + new BookPageInfo + ( + "prepared yields a", + "magical liquid that for", + "a time can make the", + "imbiber a more agile", + "and dextrous", + "individual.", + " However, beware", + "of the deadly" + ), + new BookPageInfo + ( + "nightshade, for it", + "yields a deceptively", + "sweet-tasting poison", + "that can prove highly", + "fatal to the drinker,", + "and in fact is also", + "used by assassins to", + "coat their blades." + ), + new BookPageInfo + ( + "Fortunately, this", + "latter art of poisoning", + "is little known!", + " There is much to", + "reward the student of", + "alchemy, indeed. The", + "rumours of longtime", + "alchemists losing" + ), + new BookPageInfo + ( + "their hair and", + "acquiring an", + "unhealthy pallor, not", + "to mention unsightly", + "blotches upon their", + "once-fair skin, are", + "unhappily, true. Yet", + "the joys of the mind" + ), + new BookPageInfo + ( + "make up for the", + "complete loss of", + "interest that others", + "may have in thee as", + "an object of", + "courtship, and I have", + "never regretted that", + "choice. Honestly," + ), + new BookPageInfo + ( + "truly. Not once." + ) + ); + + [Constructible] + public TreatiseOnAlchemy() : base(Utility.Random(0xFEF, 2), false) + { + } + + public TreatiseOnAlchemy(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Virtue + + public class VirtueBook : BaseBook + { + public static readonly BookContent Content = new BookContent + ( + "Virtue", "Lord British", + new BookPageInfo + ( + " Within this world", + "live people with many", + "different ideals, and", + "this is good. Yet what", + "is it within the people", + "of our land that sorts", + "out the good from the", + "evil, the cherished" + ), + new BookPageInfo + ( + "form the disdained?", + "Virtue, I say it is,", + "and virtue is the", + "logical outcome of a", + "people who wish to", + "live together in a", + "bonded society.", + " For without Virtues" + ), + new BookPageInfo + ( + "as a code of conduct", + "which people maintain", + "in their relations", + "with each other, the", + "fabric of that society", + "will become weakened.", + "For a society to grow", + "and prosper for all," + ), + new BookPageInfo + ( + "each must grant the", + "others a common base", + "of consideration.", + " I call this base the", + "Virtues. For though", + "one person might gain", + "personal advantage by", + "breaching such a" + ), + new BookPageInfo + ( + "code, the society as a", + "whole would suffer.", + " There are three", + "Principle Virtues that", + "should guide people to", + "enlightenment. These", + "are: Truth, Love and", + "Courage. From all the" + ), + new BookPageInfo + ( + "infinite reasons one", + "may have to found an", + "action, such as greed", + "or charity, envy or", + "pity, the three", + "Principle Virtues", + "stand out.", + " In fact all other" + ), + new BookPageInfo + ( + "virtues and vices can", + "be show to be built", + "from these principles", + "and their opposite", + "corruption's of", + "Falsehood, Hatred and", + "Cowardice. These", + "three Principles can" + ), + new BookPageInfo + ( + "be combined in eight", + "ways, which I will", + "call the eight virtues.", + "The eight virtues", + "which we should", + "build our society upon", + "follow.", + " Truth alone becomes" + ), + new BookPageInfo + ( + "Honesty, for without", + "honesty between our", + "people, how can we", + "build the trust which", + "is needed to", + "maximize our", + "successes.", + " Love alone becomes" + ), + new BookPageInfo + ( + "compassion, for at", + "some time or another", + "all of us will need the", + "compassion of others,", + "and most likely", + "compassion will be", + "shown to those who", + "have shown it." + ), + new BookPageInfo + ( + " Courage alone", + "becomes Valor,", + "without valor our", + "people will never", + "reach into the", + "unknown or to the", + "risky and will never", + "achieve." + ), + new BookPageInfo + ( + " Truth tempered by", + "Love give us Justice,", + "for only in a loving", + "search for the truth", + "can one dispense fair", + "Justice, rather than", + "create a cold and", + "callous people." + ), + new BookPageInfo + ( + " Love and Courage", + "give us Sacrifice, for", + "a people who love each", + "other will be willing", + "to make personal", + "sacrifices to help", + "other in need, which", + "one day, may be" + ), + new BookPageInfo + ( + "needed in return.", + " Courage and Truth", + "give us Honor, great", + "knights know this", + "well, that chivalric", + "honor can be found", + "by adhering to this", + "code of conduct." + ), + new BookPageInfo + ( + " Combining Truth,", + "Love and Courage", + "suggest the virtue of", + "Spirituality the virtue", + "that causes one to be", + "introspective, to", + "wonder about ones", + "place in this world" + ), + new BookPageInfo + ( + "and whether one's", + "deeds will be recorded", + "as a gift to the world", + "or a plague.", + " The final Virtue is", + "more complicated. For", + "the eighth combination", + "is that devoid of" + ), + new BookPageInfo + ( + "Truth, Love or", + "Courage which can", + "only exist in a state", + "of great Pride, which", + "of course is not a", + "virtue at all. Perhaps", + "this trick of fate is a", + "test to see if one can" + ), + new BookPageInfo + ( + "realize that the true", + "virtue is that of", + "Humility. I feel that", + "the people of", + "Magincia fail to see", + "this to such a degree", + "that I would not be", + "surprised if some ill" + ), + new BookPageInfo + ( + "fate awaited their", + "future.", + " Thus from the", + "infinite possibilities", + "which spawned the", + "Three Principles of", + "Truth, Love and", + "Courage, come the" + ), + new BookPageInfo + ( + "Eight Virtues of", + "Honesty, Compassion,", + "Valor, Justice,", + "Sacrifice, Honor,", + "Spirituality, and", + "Humility." + ) + ); + + [Constructible] + public VirtueBook() : base(Utility.Random(0xFEF, 2), false) + { + } + + public VirtueBook(Serial serial) : base(serial) + { + } + + public override BookContent DefaultContent => Content; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/NewAquariumBook.cs b/Scripts/Items/Books/Defined/NewAquariumBook.cs index 262ee9b59..2778db166 100644 --- a/Scripts/Items/Books/Defined/NewAquariumBook.cs +++ b/Scripts/Items/Books/Defined/NewAquariumBook.cs @@ -1,129 +1,129 @@ namespace Server.Items { - public class NewAquariumBook : BlueBook - { - public static readonly BookContent Content = new BookContent - ( - "Your New Aquarium", "Les Bilgewater", - new BookPageInfo - ( - "Welcome to the", - "wonderful world", - "of aquarium ownership.", - "With a little time and", - "skill your aquarium can", - "become a work of art!" - ), - new BookPageInfo - ( - "Catching Fish:", - "You will need to", - "aquire a fishing net,", - "and a number of fish", - "bowls, from your local", - "fisherman.", - "To use the net,", - "select it from your" - ), - new BookPageInfo - ( - "backpack, and cast it", - "into shallow water.", - "Then we wait.", - " The fish will be so", - "happy to be in your", - "aquarium, they will", - "jump right into your", - "fish bowl when caught!" - ), - new BookPageInfo - ( - "Just take them home", - "and pour them into", - "your aquarium, and", - "BING! You have a happy", - "new addition to your", - "collection!" - ), - new BookPageInfo - ( - "Caring for our", - "Underwater Allies:", - "", - " Fish need clean", - "water and food to", - "survive.", - " Our aquarium comes", - "with a status monitoring" - ), - new BookPageInfo - ( - "aid. Must be Magic!", - " Just look at the", - "front of your aquarium", - "(mouse over). See the", - "helpful and friendly", - "guide? It tells how much", - "food and water is", - "needed to maintain," - ), - new BookPageInfo - ( - "and improve the quality", - "of your tank.", - " You dont want to", - "overfeed your fish", - "very often. In fact,", - "you only want to feed", - "them every other day.", - "But, remember to keep" - ), - new BookPageInfo - ( - "the water strong and", - "healthy, and add more", - "on a regular basis", - "to keep your aquarium", - "a pretty, sparkely blue.", - "", - " Well, I hope you", - "get as much enjoyment," - ), - new BookPageInfo - ( - "collecting a beautiful", - "array of our fine, finned,", - "friends from the sea,", - "as I do!", - "", - "Happy Fishing!" - ) - ); + public class NewAquariumBook : BlueBook + { + public static readonly BookContent Content = new BookContent + ( + "Your New Aquarium", "Les Bilgewater", + new BookPageInfo + ( + "Welcome to the", + "wonderful world", + "of aquarium ownership.", + "With a little time and", + "skill your aquarium can", + "become a work of art!" + ), + new BookPageInfo + ( + "Catching Fish:", + "You will need to", + "aquire a fishing net,", + "and a number of fish", + "bowls, from your local", + "fisherman.", + "To use the net,", + "select it from your" + ), + new BookPageInfo + ( + "backpack, and cast it", + "into shallow water.", + "Then we wait.", + " The fish will be so", + "happy to be in your", + "aquarium, they will", + "jump right into your", + "fish bowl when caught!" + ), + new BookPageInfo + ( + "Just take them home", + "and pour them into", + "your aquarium, and", + "BING! You have a happy", + "new addition to your", + "collection!" + ), + new BookPageInfo + ( + "Caring for our", + "Underwater Allies:", + "", + " Fish need clean", + "water and food to", + "survive.", + " Our aquarium comes", + "with a status monitoring" + ), + new BookPageInfo + ( + "aid. Must be Magic!", + " Just look at the", + "front of your aquarium", + "(mouse over). See the", + "helpful and friendly", + "guide? It tells how much", + "food and water is", + "needed to maintain," + ), + new BookPageInfo + ( + "and improve the quality", + "of your tank.", + " You dont want to", + "overfeed your fish", + "very often. In fact,", + "you only want to feed", + "them every other day.", + "But, remember to keep" + ), + new BookPageInfo + ( + "the water strong and", + "healthy, and add more", + "on a regular basis", + "to keep your aquarium", + "a pretty, sparkely blue.", + "", + " Well, I hope you", + "get as much enjoyment," + ), + new BookPageInfo + ( + "collecting a beautiful", + "array of our fine, finned,", + "friends from the sea,", + "as I do!", + "", + "Happy Fishing!" + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public NewAquariumBook() : base(false) + { + Hue = 0; + } - [Constructible] - public NewAquariumBook() : base( false ) - { - Hue = 0; - } + public NewAquariumBook(Serial serial) : base(serial) + { + } - public NewAquariumBook( Serial serial ) : base( serial ) - { - } + public override BookContent DefaultContent => Content; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/Defined/TranslatedGargoyleJournal.cs b/Scripts/Items/Books/Defined/TranslatedGargoyleJournal.cs index 75455080c..982b4b9f5 100644 --- a/Scripts/Items/Books/Defined/TranslatedGargoyleJournal.cs +++ b/Scripts/Items/Books/Defined/TranslatedGargoyleJournal.cs @@ -1,161 +1,161 @@ namespace Server.Items { - public class TranslatedGargoyleJournal : BlueBook - { - public static readonly BookContent Content = new BookContent - ( - "Translated Journal", "Velis", - new BookPageInfo - ( - "This text has been", - "translated from a", - "gargoyle's journal", - "following his capture", - "and subsequent", - "reeducation.", - "", - " -Velis" - ), - new BookPageInfo - ( - "I write this in the", - "hopes that someday a", - "soul of pure heart and", - "mind will read it. We", - "are not the evil beings", - "that our cousin", - "gargoyles have made", - "us out to be. We" - ), - new BookPageInfo - ( - "consider them", - "uncivilized and they", - "have no concept of the", - "Principles. To you", - "who reads this, I beg", - "for your help in", - "saving my brethern", - "and preserving my" - ), - new BookPageInfo - ( - "race. We stand at the", - "edge of destruction as", - "does the rest of the", - "world. Once it was", - "written law that we", - "would not allow the", - "knowledge of our", - "civilization to spread" - ), - new BookPageInfo - ( - "into the world, no we", - "are left with little", - "choice...contact the", - "outside world in the hopes", - "of finding help to save", - "it or becoming the", - "unwilling bringers of", - "its damnation." - ), - new BookPageInfo - ( - " I fear my capture is", - "certain, the", - "controllers grow ever", - "closer to my hiding", - "place and I know if", - "they discover me, my", - "fate will be as that of", - "my brothers." - ), - new BookPageInfo - ( - "Although we resisted", - "with all our strength", - "it is now clear that we", - "must have assistance", - "or our people will be", - "gone. And if our", - "oppressor achieves", - "his goals our race will" - ), - new BookPageInfo - ( - "surely be joined buy", - "others.", - " Those of us who", - "have not yet been", - "taken hope to open a", - "path from the outside", - "world into the city.", - "We believe we have" - ), - new BookPageInfo - ( - "found weak areas in", - "the mountains that we", - "can successfully", - "knock through with", - "our limited supplies.", - "We will have to work", - "quickly and the risk", - "of being discovered is" - ), - new BookPageInfo - ( - "great, but no choice", - "remains..." - ), - new BookPageInfo - ( - ), - new BookPageInfo - ( - ), - new BookPageInfo - ( - "Kai Hohiro, 12pm.", - "10.11.2001", - "first one to be here" - ) - ); + public class TranslatedGargoyleJournal : BlueBook + { + public static readonly BookContent Content = new BookContent + ( + "Translated Journal", "Velis", + new BookPageInfo + ( + "This text has been", + "translated from a", + "gargoyle's journal", + "following his capture", + "and subsequent", + "reeducation.", + "", + " -Velis" + ), + new BookPageInfo + ( + "I write this in the", + "hopes that someday a", + "soul of pure heart and", + "mind will read it. We", + "are not the evil beings", + "that our cousin", + "gargoyles have made", + "us out to be. We" + ), + new BookPageInfo + ( + "consider them", + "uncivilized and they", + "have no concept of the", + "Principles. To you", + "who reads this, I beg", + "for your help in", + "saving my brethern", + "and preserving my" + ), + new BookPageInfo + ( + "race. We stand at the", + "edge of destruction as", + "does the rest of the", + "world. Once it was", + "written law that we", + "would not allow the", + "knowledge of our", + "civilization to spread" + ), + new BookPageInfo + ( + "into the world, no we", + "are left with little", + "choice...contact the", + "outside world in the hopes", + "of finding help to save", + "it or becoming the", + "unwilling bringers of", + "its damnation." + ), + new BookPageInfo + ( + " I fear my capture is", + "certain, the", + "controllers grow ever", + "closer to my hiding", + "place and I know if", + "they discover me, my", + "fate will be as that of", + "my brothers." + ), + new BookPageInfo + ( + "Although we resisted", + "with all our strength", + "it is now clear that we", + "must have assistance", + "or our people will be", + "gone. And if our", + "oppressor achieves", + "his goals our race will" + ), + new BookPageInfo + ( + "surely be joined buy", + "others.", + " Those of us who", + "have not yet been", + "taken hope to open a", + "path from the outside", + "world into the city.", + "We believe we have" + ), + new BookPageInfo + ( + "found weak areas in", + "the mountains that we", + "can successfully", + "knock through with", + "our limited supplies.", + "We will have to work", + "quickly and the risk", + "of being discovered is" + ), + new BookPageInfo + ( + "great, but no choice", + "remains..." + ), + new BookPageInfo + ( + ), + new BookPageInfo + ( + ), + new BookPageInfo + ( + "Kai Hohiro, 12pm.", + "10.11.2001", + "first one to be here" + ) + ); - public override BookContent DefaultContent => Content; + [Constructible] + public TranslatedGargoyleJournal() : base(false) + { + } - [Constructible] - public TranslatedGargoyleJournal() : base( false ) - { - } + public TranslatedGargoyleJournal(Serial serial) : base(serial) + { + } - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( "Translated Gargoyle Journal" ); - } + public override BookContent DefaultContent => Content; - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, "Translated Gargoyle Journal" ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add("Translated Gargoyle Journal"); + } - public TranslatedGargoyleJournal( Serial serial ) : base( serial ) - { - } + public override void OnSingleClick(Mobile from) + { + LabelTo(from, "Translated Gargoyle Journal"); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int)0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Books/RedBook.cs b/Scripts/Items/Books/RedBook.cs index 1a1b6acd5..2ee8b7d15 100644 --- a/Scripts/Items/Books/RedBook.cs +++ b/Scripts/Items/Books/RedBook.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class RedBook : BaseBook - { - [Constructible] - public RedBook() : base( 0xFF1 ) - { - } + public class RedBook : BaseBook + { + [Constructible] + public RedBook() : base(0xFF1) + { + } - [Constructible] - public RedBook( int pageCount, bool writable ) : base( 0xFF1, pageCount, writable ) - { - } + [Constructible] + public RedBook(int pageCount, bool writable) : base(0xFF1, pageCount, writable) + { + } - [Constructible] - public RedBook( string title, string author, int pageCount, bool writable ) : base( 0xFF1, title, author, pageCount, writable ) - { - } + [Constructible] + public RedBook(string title, string author, int pageCount, bool writable) : base(0xFF1, title, author, pageCount, + writable) + { + } - // Intended for defined books only - public RedBook( bool writable ) : base( 0xFF1, writable ) - { - } + // Intended for defined books only + public RedBook(bool writable) : base(0xFF1, writable) + { + } - public RedBook( Serial serial ) : base( serial ) - { - } + public RedBook(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } - } + writer.Write(0); // version + } + } } \ No newline at end of file diff --git a/Scripts/Items/Books/TanBook.cs b/Scripts/Items/Books/TanBook.cs index f323a0832..5be5297b0 100644 --- a/Scripts/Items/Books/TanBook.cs +++ b/Scripts/Items/Books/TanBook.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class TanBook : BaseBook - { - [Constructible] - public TanBook() : base( 0xFF0 ) - { - } + public class TanBook : BaseBook + { + [Constructible] + public TanBook() : base(0xFF0) + { + } - [Constructible] - public TanBook( int pageCount, bool writable ) : base( 0xFF0, pageCount, writable ) - { - } + [Constructible] + public TanBook(int pageCount, bool writable) : base(0xFF0, pageCount, writable) + { + } - [Constructible] - public TanBook( string title, string author, int pageCount, bool writable ) : base( 0xFF0, title, author, pageCount, writable ) - { - } + [Constructible] + public TanBook(string title, string author, int pageCount, bool writable) : base(0xFF0, title, author, pageCount, + writable) + { + } - // Intended for defined books only - public TanBook( bool writable ) : base( 0xFF0, writable ) - { - } + // Intended for defined books only + public TanBook(bool writable) : base(0xFF0, writable) + { + } - public TanBook( Serial serial ) : base( serial ) - { - } + public TanBook(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } - } + writer.Write(0); // version + } + } } \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/ArtifactLargeVase.cs b/Scripts/Items/Champion Artifacts/Decorative/ArtifactLargeVase.cs index 41e058439..2db3ad588 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/ArtifactLargeVase.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/ArtifactLargeVase.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class ArtifactLargeVase : Item - { - [Constructible] - public ArtifactLargeVase() : base( 0x0B47 ) - { - } + public class ArtifactLargeVase : Item + { + [Constructible] + public ArtifactLargeVase() : base(0x0B47) + { + } - public ArtifactLargeVase( Serial serial ) : base( serial ) - { - } + public ArtifactLargeVase(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/ArtifactVase.cs b/Scripts/Items/Champion Artifacts/Decorative/ArtifactVase.cs index 6249b4c43..205df4ea6 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/ArtifactVase.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/ArtifactVase.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class ArtifactVase : Item - { - [Constructible] - public ArtifactVase() : base( 0x0B48 ) - { - } + public class ArtifactVase : Item + { + [Constructible] + public ArtifactVase() : base(0x0B48) + { + } - public ArtifactVase( Serial serial ) : base( serial ) - { - } + public ArtifactVase(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/DemonSkull.cs b/Scripts/Items/Champion Artifacts/Decorative/DemonSkull.cs index 274f313e2..5ed3e0a6f 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/DemonSkull.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/DemonSkull.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class DemonSkull : Item - { - [Constructible] - public DemonSkull() : base( 0x224e + Utility.Random(4) ) - { - } + public class DemonSkull : Item + { + [Constructible] + public DemonSkull() : base(0x224e + Utility.Random(4)) + { + } - public DemonSkull( Serial serial ) : base( serial ) - { - } + public DemonSkull(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/DirtPatch.cs b/Scripts/Items/Champion Artifacts/Decorative/DirtPatch.cs index 1d73d62e1..2b7a98c24 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/DirtPatch.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/DirtPatch.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class DirtPatch : Item - { - [Constructible] - public DirtPatch(): base(0x0913) - { - } + public class DirtPatch : Item + { + [Constructible] + public DirtPatch() : base(0x0913) + { + } - public DirtPatch(Serial serial): base(serial) - { - } + public DirtPatch(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/EvilIdolSkull.cs b/Scripts/Items/Champion Artifacts/Decorative/EvilIdolSkull.cs index 8551900b9..64036567f 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/EvilIdolSkull.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/EvilIdolSkull.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class EvilIdolSkull : Item - { - public override int LabelNumber => 1095237; // Evil Idol + public class EvilIdolSkull : Item + { + [Constructible] + public EvilIdolSkull() : base(0x1F18) + { + } - [Constructible] - public EvilIdolSkull() : base( 0x1F18 ) - { - } + public EvilIdolSkull(Serial serial) : base(serial) + { + } - public EvilIdolSkull( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1095237; // Evil Idol - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/Futon.cs b/Scripts/Items/Champion Artifacts/Decorative/Futon.cs index 6636fdb9f..538095e6f 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/Futon.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/Futon.cs @@ -1,39 +1,47 @@ namespace Server.Items { - [Flippable] - public class Futon : Item - { - [Constructible] - public Futon() : base( Utility.RandomDouble() > 0.5 ? 0x295C : 0x295E ) - { - } + [Flippable] + public class Futon : Item + { + [Constructible] + public Futon() : base(Utility.RandomDouble() > 0.5 ? 0x295C : 0x295E) + { + } - public Futon( Serial serial ) : base( serial ) - { - } + public Futon(Serial serial) : base(serial) + { + } - public void Flip() - { - switch ( ItemID ) - { - case 0x295C: ItemID = 0x295D; break; - case 0x295E: ItemID = 0x295F; break; + public void Flip() + { + switch (ItemID) + { + case 0x295C: + ItemID = 0x295D; + break; + case 0x295E: + ItemID = 0x295F; + break; - case 0x295D: ItemID = 0x295C; break; - case 0x295F: ItemID = 0x295E; break; - } - } + case 0x295D: + ItemID = 0x295C; + break; + case 0x295F: + ItemID = 0x295E; + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/LavaTile.cs b/Scripts/Items/Champion Artifacts/Decorative/LavaTile.cs index 00010d954..8df74ed9d 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/LavaTile.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/LavaTile.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class LavaTile : Item - { - [Constructible] - public LavaTile() : base( 0x12EE ) - { - } + public class LavaTile : Item + { + [Constructible] + public LavaTile() : base(0x12EE) + { + } - public LavaTile( Serial serial ) : base( serial ) - { - } + public LavaTile(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/Pier.cs b/Scripts/Items/Champion Artifacts/Decorative/Pier.cs index 8e78aefe1..0fb9f2639 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/Pier.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/Pier.cs @@ -1,52 +1,53 @@ namespace Server.Items { - public class Pier : Item - { - /* - * This does not make a lot of sense, being a "Pier" - * and having possible itemids that have nothing - * to do with piers. The three items here are basically - * permutations of the same "drop", or item that - * will be randomly selected when the item drops. - * - * It was either this, or make 2 - * new classes named to reflect that they are rocks - * in water, or put them all in one class. Either - * is kind of senseless, so it is what it is. - * - */ + public class Pier : Item + { + /* + * This does not make a lot of sense, being a "Pier" + * and having possible itemids that have nothing + * to do with piers. The three items here are basically + * permutations of the same "drop", or item that + * will be randomly selected when the item drops. + * + * It was either this, or make 2 + * new classes named to reflect that they are rocks + * in water, or put them all in one class. Either + * is kind of senseless, so it is what it is. + * + */ - private static int[] m_itemids = { - 0x3486, 0x348b, 0x3ae - }; + private static int[] m_itemids = + { + 0x3486, 0x348b, 0x3ae + }; - [Constructible] - public Pier() - : base(m_itemids[Utility.Random(3)]) - { - } + [Constructible] + public Pier() + : base(m_itemids[Utility.Random(3)]) + { + } - public Pier(int itemid) - : base(itemid) - { - } + public Pier(int itemid) + : base(itemid) + { + } - public Pier( Serial serial ) : base( serial ) - { - } + public Pier(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/SkullPole.cs b/Scripts/Items/Champion Artifacts/Decorative/SkullPole.cs index 9306ef5f4..f9bd3db44 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/SkullPole.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/SkullPole.cs @@ -1,29 +1,29 @@ namespace Server.Items { - public class SkullPole : Item - { - [Constructible] - public SkullPole() : base( 0x2204 ) - { - Weight = 5; - } + public class SkullPole : Item + { + [Constructible] + public SkullPole() : base(0x2204) + { + Weight = 5; + } - public SkullPole( Serial serial ) : base( serial ) - { - } + public SkullPole(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/SwampTile.cs b/Scripts/Items/Champion Artifacts/Decorative/SwampTile.cs index 08f20395f..3ec93e8dd 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/SwampTile.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/SwampTile.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class SwampTile : Item - { - [Constructible] - public SwampTile() : base( 0x320D ) - { - } + public class SwampTile : Item + { + [Constructible] + public SwampTile() : base(0x320D) + { + } - public SwampTile( Serial serial ) : base( serial ) - { - } + public SwampTile(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/TatteredAncientMummyWrapping.cs b/Scripts/Items/Champion Artifacts/Decorative/TatteredAncientMummyWrapping.cs index 1764924ad..3b2fe9ae6 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/TatteredAncientMummyWrapping.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/TatteredAncientMummyWrapping.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class TatteredAncientMummyWrapping : Item - { - public override int LabelNumber => 1094912; // Tattered Ancient Mummy Wrapping [Replica] + public class TatteredAncientMummyWrapping : Item + { + [Constructible] + public TatteredAncientMummyWrapping() : base(0xE21) + { + Hue = 0x909; + } - [Constructible] - public TatteredAncientMummyWrapping() : base( 0xE21 ) - { - Hue = 0x909; - } + public TatteredAncientMummyWrapping(Serial serial) : base(serial) + { + } - public TatteredAncientMummyWrapping( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1094912; // Tattered Ancient Mummy Wrapping [Replica] - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/WallBlood.cs b/Scripts/Items/Champion Artifacts/Decorative/WallBlood.cs index def4b0d6c..e2d92b015 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/WallBlood.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/WallBlood.cs @@ -1,29 +1,29 @@ namespace Server.Items { - public class WallBlood : Item - { - [Constructible] - public WallBlood() - : base(Utility.RandomBool() ? 0x1D95 : 0x1D94) - { - } + public class WallBlood : Item + { + [Constructible] + public WallBlood() + : base(Utility.RandomBool() ? 0x1D95 : 0x1D94) + { + } - public WallBlood( Serial serial ) : base( serial ) - { - } + public WallBlood(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/WaterTile.cs b/Scripts/Items/Champion Artifacts/Decorative/WaterTile.cs index b21d21133..1c2546477 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/WaterTile.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/WaterTile.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class WaterTile : Item - { - [Constructible] - public WaterTile() : base( 0x346E ) - { - } + public class WaterTile : Item + { + [Constructible] + public WaterTile() : base(0x346E) + { + } - public WaterTile( Serial serial ) : base( serial ) - { - } + public WaterTile(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/Web.cs b/Scripts/Items/Champion Artifacts/Decorative/Web.cs index 5aff8e2c9..341c3c892 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/Web.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/Web.cs @@ -1,36 +1,37 @@ namespace Server.Items { - public class Web : Item - { - private static int[] m_itemids = { - 0x10d7, 0x10d8, 0x10dd - }; + public class Web : Item + { + private static int[] m_itemids = + { + 0x10d7, 0x10d8, 0x10dd + }; - [Constructible] - public Web() - : base(m_itemids[Utility.Random(3)]) - { - } + [Constructible] + public Web() + : base(m_itemids[Utility.Random(3)]) + { + } - [Constructible] - public Web( int itemid ) : base( itemid ) - { - } + [Constructible] + public Web(int itemid) : base(itemid) + { + } - public Web( Serial serial ) : base( serial ) - { - } + public Web(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Decorative/WindSpirit.cs b/Scripts/Items/Champion Artifacts/Decorative/WindSpirit.cs index 49a0f3b9e..691440b8e 100644 --- a/Scripts/Items/Champion Artifacts/Decorative/WindSpirit.cs +++ b/Scripts/Items/Champion Artifacts/Decorative/WindSpirit.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class WindSpirit : Item - { - public override int LabelNumber => 1094925; // Wind Spirit [Replica] + public class WindSpirit : Item + { + [Constructible] + public WindSpirit() : base(0x1F1F) + { + } - [Constructible] - public WindSpirit() : base( 0x1F1F ) - { - } + public WindSpirit(Serial serial) : base(serial) + { + } - public WindSpirit( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1094925; // Wind Spirit [Replica] - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/ANecromancerShroud.cs b/Scripts/Items/Champion Artifacts/Shared/ANecromancerShroud.cs index 756011f89..6547f0cf9 100644 --- a/Scripts/Items/Champion Artifacts/Shared/ANecromancerShroud.cs +++ b/Scripts/Items/Champion Artifacts/Shared/ANecromancerShroud.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class ANecromancerShroud : Robe - { - public override int LabelNumber => 1094913; // A Necromancer Shroud [Replica] + public class ANecromancerShroud : Robe + { + [Constructible] + public ANecromancerShroud() + { + Hue = 0x455; + } - public override int BaseColdResistance => 5; + public ANecromancerShroud(Serial serial) : base(serial) + { + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public override int LabelNumber => 1094913; // A Necromancer Shroud [Replica] - public override bool CanFortify => false; + public override int BaseColdResistance => 5; - [Constructible] - public ANecromancerShroud() - { - Hue = 0x455; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public ANecromancerShroud( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/BraveKnightOfTheBritannia.cs b/Scripts/Items/Champion Artifacts/Shared/BraveKnightOfTheBritannia.cs index 1c9dac06b..69eb3a311 100644 --- a/Scripts/Items/Champion Artifacts/Shared/BraveKnightOfTheBritannia.cs +++ b/Scripts/Items/Champion Artifacts/Shared/BraveKnightOfTheBritannia.cs @@ -1,52 +1,53 @@ namespace Server.Items { - public class BraveKnightOfTheBritannia : Katana - { - public override int LabelNumber => 1094909; // Brave Knight of The Britannia [Replica] + public class BraveKnightOfTheBritannia : Katana + { + [Constructible] + public BraveKnightOfTheBritannia() + { + Hue = 0x47e; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.WeaponSpeed = 30; + Attributes.WeaponDamage = 35; - public override bool CanFortify => false; + WeaponAttributes.HitLeechStam = 48; + WeaponAttributes.HitHarm = 26; + WeaponAttributes.HitLeechHits = 22; + } - [Constructible] - public BraveKnightOfTheBritannia() - { - Hue = 0x47e; + public BraveKnightOfTheBritannia(Serial serial) : base(serial) + { + } - Attributes.WeaponSpeed = 30; - Attributes.WeaponDamage = 35; + public override int LabelNumber => 1094909; // Brave Knight of The Britannia [Replica] - WeaponAttributes.HitLeechStam = 48; - WeaponAttributes.HitHarm = 26; - WeaponAttributes.HitLeechHits = 22; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = chaos = direct = 0; - fire = 40; - cold = 30; - pois = 10; - nrgy = 20; - } + public override bool CanFortify => false; - public BraveKnightOfTheBritannia( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = chaos = direct = 0; + fire = 40; + cold = 30; + pois = 10; + nrgy = 20; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/CaptainJohnsHat.cs b/Scripts/Items/Champion Artifacts/Shared/CaptainJohnsHat.cs index 1bb0ae286..8e017b6f9 100644 --- a/Scripts/Items/Champion Artifacts/Shared/CaptainJohnsHat.cs +++ b/Scripts/Items/Champion Artifacts/Shared/CaptainJohnsHat.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class CaptainJohnsHat : TricorneHat - { - public override int LabelNumber => 1094911; // Captain John's Hat [Replica] + public class CaptainJohnsHat : TricorneHat + { + [Constructible] + public CaptainJohnsHat() + { + Hue = 0x455; - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 7; - public override int BaseEnergyResistance => 23; + Attributes.BonusDex = 8; + Attributes.NightSight = 1; + Attributes.AttackChance = 15; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + SkillBonuses.Skill_1_Name = SkillName.Swords; + SkillBonuses.Skill_1_Value = 20; + } - public override bool CanFortify => false; + public CaptainJohnsHat(Serial serial) : base(serial) + { + } - [Constructible] - public CaptainJohnsHat() - { - Hue = 0x455; + public override int LabelNumber => 1094911; // Captain John's Hat [Replica] - Attributes.BonusDex = 8; - Attributes.NightSight = 1; - Attributes.AttackChance = 15; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 7; + public override int BaseEnergyResistance => 23; - SkillBonuses.Skill_1_Name = SkillName.Swords; - SkillBonuses.Skill_1_Value = 20; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public CaptainJohnsHat( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/DetectiveBoots.cs b/Scripts/Items/Champion Artifacts/Shared/DetectiveBoots.cs index ba9835e78..180f03ec0 100644 --- a/Scripts/Items/Champion Artifacts/Shared/DetectiveBoots.cs +++ b/Scripts/Items/Champion Artifacts/Shared/DetectiveBoots.cs @@ -2,49 +2,54 @@ using System; namespace Server.Items { - public class DetectiveBoots : Boots - { - public override int LabelNumber => 1094894 + m_Level; // [Quality] Detective of the Royal Guard [Replica] + public class DetectiveBoots : Boots + { + private int m_Level; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + [Constructible] + public DetectiveBoots() + { + Hue = 0x455; + Level = Utility.RandomMinMax(0, 2); + } - public override bool CanFortify => false; + public DetectiveBoots(Serial serial) : base(serial) + { + } - private int m_Level; + public override int LabelNumber => 1094894 + m_Level; // [Quality] Detective of the Royal Guard [Replica] - [CommandProperty( AccessLevel.GameMaster )] - public int Level - { - get => m_Level; - set{ m_Level = Math.Max( Math.Min( 2, value), 0 ); Attributes.BonusInt = 2 + m_Level; InvalidateProperties(); } - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - [Constructible] - public DetectiveBoots() - { - Hue = 0x455; - Level = Utility.RandomMinMax( 0, 2 ); - } + public override bool CanFortify => false; - public DetectiveBoots( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Level + { + get => m_Level; + set + { + m_Level = Math.Max(Math.Min(2, value), 0); + Attributes.BonusInt = 2 + m_Level; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Level = Attributes.BonusInt - 2; - } - } -} + Level = Attributes.BonusInt - 2; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/DjinnisRing.cs b/Scripts/Items/Champion Artifacts/Shared/DjinnisRing.cs index 8fbe28a63..8b6758674 100644 --- a/Scripts/Items/Champion Artifacts/Shared/DjinnisRing.cs +++ b/Scripts/Items/Champion Artifacts/Shared/DjinnisRing.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class DjinnisRing : SilverRing - { - public override int LabelNumber => 1094927; // Djinni's Ring [Replica] + public class DjinnisRing : SilverRing + { + [Constructible] + public DjinnisRing() + { + Attributes.BonusInt = 5; + Attributes.SpellDamage = 10; + Attributes.CastSpeed = 2; + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public DjinnisRing(Serial serial) : base(serial) + { + } - [Constructible] - public DjinnisRing() - { - Attributes.BonusInt = 5; - Attributes.SpellDamage = 10; - Attributes.CastSpeed = 2; - } + public override int LabelNumber => 1094927; // Djinni's Ring [Replica] - public DjinnisRing( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/EmbroideredOakLeafCloak.cs b/Scripts/Items/Champion Artifacts/Shared/EmbroideredOakLeafCloak.cs index e66d6f880..c4d2365a3 100644 --- a/Scripts/Items/Champion Artifacts/Shared/EmbroideredOakLeafCloak.cs +++ b/Scripts/Items/Champion Artifacts/Shared/EmbroideredOakLeafCloak.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class EmbroideredOakLeafCloak : BaseOuterTorso - { - public override int LabelNumber => 1094901; // Embroidered Oak Leaf Cloak [Replica] + public class EmbroideredOakLeafCloak : BaseOuterTorso + { + [Constructible] + public EmbroideredOakLeafCloak() : base(0x2684) + { + Hue = 0x483; + StrRequirement = 0; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + SkillBonuses.Skill_1_Name = SkillName.Stealth; + SkillBonuses.Skill_1_Value = 5; + } - public override bool CanFortify => false; + public EmbroideredOakLeafCloak(Serial serial) : base(serial) + { + } - [Constructible] - public EmbroideredOakLeafCloak() : base( 0x2684 ) - { - Hue = 0x483; - StrRequirement = 0; + public override int LabelNumber => 1094901; // Embroidered Oak Leaf Cloak [Replica] - SkillBonuses.Skill_1_Name = SkillName.Stealth; - SkillBonuses.Skill_1_Value = 5; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public EmbroideredOakLeafCloak( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/GauntletsOfAnger.cs b/Scripts/Items/Champion Artifacts/Shared/GauntletsOfAnger.cs index 8414a9c5d..29be190ef 100644 --- a/Scripts/Items/Champion Artifacts/Shared/GauntletsOfAnger.cs +++ b/Scripts/Items/Champion Artifacts/Shared/GauntletsOfAnger.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class GuantletsOfAnger : PlateGloves - { - public override int LabelNumber => 1094902; // Gauntlets of Anger [Replica] + public class GuantletsOfAnger : PlateGloves + { + [Constructible] + public GuantletsOfAnger() + { + Hue = 0x29b; - public override int BasePhysicalResistance => 4; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 6; - public override int BaseEnergyResistance => 5; + Attributes.BonusHits = 8; + Attributes.RegenHits = 2; + Attributes.DefendChance = 10; + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public GuantletsOfAnger(Serial serial) : base(serial) + { + } - public override bool CanFortify => false; + public override int LabelNumber => 1094902; // Gauntlets of Anger [Replica] - [Constructible] - public GuantletsOfAnger() - { - Hue = 0x29b; + public override int BasePhysicalResistance => 4; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 6; + public override int BaseEnergyResistance => 5; - Attributes.BonusHits = 8; - Attributes.RegenHits = 2; - Attributes.DefendChance = 10; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public GuantletsOfAnger( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/LieutenantOfTheBritannianRoyalGuard.cs b/Scripts/Items/Champion Artifacts/Shared/LieutenantOfTheBritannianRoyalGuard.cs index 9eefd59fb..52b7db9cd 100644 --- a/Scripts/Items/Champion Artifacts/Shared/LieutenantOfTheBritannianRoyalGuard.cs +++ b/Scripts/Items/Champion Artifacts/Shared/LieutenantOfTheBritannianRoyalGuard.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class LieutenantOfTheBritannianRoyalGuard : BodySash - { - public override int LabelNumber => 1094910; // Lieutenant of the Britannian Royal Guard [Replica] + public class LieutenantOfTheBritannianRoyalGuard : BodySash + { + [Constructible] + public LieutenantOfTheBritannianRoyalGuard() + { + Hue = 0xe8; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.BonusInt = 5; + Attributes.RegenMana = 2; + Attributes.LowerRegCost = 10; + } - public override bool CanFortify => false; + public LieutenantOfTheBritannianRoyalGuard(Serial serial) : base(serial) + { + } - [Constructible] - public LieutenantOfTheBritannianRoyalGuard() - { - Hue = 0xe8; + public override int LabelNumber => 1094910; // Lieutenant of the Britannian Royal Guard [Replica] - Attributes.BonusInt = 5; - Attributes.RegenMana = 2; - Attributes.LowerRegCost = 10; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public LieutenantOfTheBritannianRoyalGuard( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/OblivionsNeedle.cs b/Scripts/Items/Champion Artifacts/Shared/OblivionsNeedle.cs index e31adf47a..53360c44e 100644 --- a/Scripts/Items/Champion Artifacts/Shared/OblivionsNeedle.cs +++ b/Scripts/Items/Champion Artifacts/Shared/OblivionsNeedle.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class OblivionsNeedle : Dagger - { - public override int LabelNumber => 1094916; // Oblivion's Needle [Replica] + public class OblivionsNeedle : Dagger + { + [Constructible] + public OblivionsNeedle() + { + Attributes.BonusStam = 20; + Attributes.AttackChance = 20; + Attributes.DefendChance = -20; + Attributes.WeaponDamage = 40; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + WeaponAttributes.HitLeechStam = 50; + } - public override bool CanFortify => false; + public OblivionsNeedle(Serial serial) : base(serial) + { + } - [Constructible] - public OblivionsNeedle() - { - Attributes.BonusStam = 20; - Attributes.AttackChance = 20; - Attributes.DefendChance = -20; - Attributes.WeaponDamage = 40; + public override int LabelNumber => 1094916; // Oblivion's Needle [Replica] - WeaponAttributes.HitLeechStam = 50; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public OblivionsNeedle( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/RoyalGuardSurvivalKnife.cs b/Scripts/Items/Champion Artifacts/Shared/RoyalGuardSurvivalKnife.cs index ae7663738..a41ca56d3 100644 --- a/Scripts/Items/Champion Artifacts/Shared/RoyalGuardSurvivalKnife.cs +++ b/Scripts/Items/Champion Artifacts/Shared/RoyalGuardSurvivalKnife.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class RoyalGuardSurvivalKnife : SkinningKnife - { - public override int LabelNumber => 1094918; // Royal Guard Survival Knife [Replica] + public class RoyalGuardSurvivalKnife : SkinningKnife + { + [Constructible] + public RoyalGuardSurvivalKnife() + { + Attributes.SpellChanneling = 1; + Attributes.Luck = 140; + Attributes.EnhancePotions = 25; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + WeaponAttributes.UseBestSkill = 1; + WeaponAttributes.LowerStatReq = 50; + } - public override bool CanFortify => false; + public RoyalGuardSurvivalKnife(Serial serial) : base(serial) + { + } - [Constructible] - public RoyalGuardSurvivalKnife() - { - Attributes.SpellChanneling = 1; - Attributes.Luck = 140; - Attributes.EnhancePotions = 25; + public override int LabelNumber => 1094918; // Royal Guard Survival Knife [Replica] - WeaponAttributes.UseBestSkill = 1; - WeaponAttributes.LowerStatReq = 50; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public RoyalGuardSurvivalKnife( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/SamaritanRobe.cs b/Scripts/Items/Champion Artifacts/Shared/SamaritanRobe.cs index 06ab8e1e3..8a44bdc52 100644 --- a/Scripts/Items/Champion Artifacts/Shared/SamaritanRobe.cs +++ b/Scripts/Items/Champion Artifacts/Shared/SamaritanRobe.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class SamaritanRobe : Robe - { - public override int LabelNumber => 1094926; // Good Samaritan of Britannia [Replica] + public class SamaritanRobe : Robe + { + [Constructible] + public SamaritanRobe() + { + Hue = 0x2a3; + } - public override int BasePhysicalResistance => 5; + public SamaritanRobe(Serial serial) : base(serial) + { + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public override int LabelNumber => 1094926; // Good Samaritan of Britannia [Replica] - public override bool CanFortify => false; + public override int BasePhysicalResistance => 5; - [Constructible] - public SamaritanRobe() - { - Hue = 0x2a3; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public SamaritanRobe( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/TheMostKnowledgePerson.cs b/Scripts/Items/Champion Artifacts/Shared/TheMostKnowledgePerson.cs index af98522c0..9cc18650f 100644 --- a/Scripts/Items/Champion Artifacts/Shared/TheMostKnowledgePerson.cs +++ b/Scripts/Items/Champion Artifacts/Shared/TheMostKnowledgePerson.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class TheMostKnowledgePerson : BaseOuterTorso - { - public override int LabelNumber => 1094893; // The Most Knowledge Person [Replica] + public class TheMostKnowledgePerson : BaseOuterTorso + { + [Constructible] + public TheMostKnowledgePerson() : base(0x2684) + { + Hue = 0x117; + StrRequirement = 0; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.BonusHits = 3 + Utility.RandomMinMax(0, 2); + } - public override bool CanFortify => false; + public TheMostKnowledgePerson(Serial serial) : base(serial) + { + } - public override bool CanBeBlessed => false; + public override int LabelNumber => 1094893; // The Most Knowledge Person [Replica] - [Constructible] - public TheMostKnowledgePerson() : base( 0x2684 ) - { - Hue = 0x117; - StrRequirement = 0; + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - Attributes.BonusHits = 3 + Utility.RandomMinMax( 0, 2 ); - } + public override bool CanFortify => false; - public TheMostKnowledgePerson( Serial serial ) : base( serial ) - { - } + public override bool CanBeBlessed => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Shared/TheRobeOfBritanniaAri.cs b/Scripts/Items/Champion Artifacts/Shared/TheRobeOfBritanniaAri.cs index 4ef4f94c6..1b8c222bc 100644 --- a/Scripts/Items/Champion Artifacts/Shared/TheRobeOfBritanniaAri.cs +++ b/Scripts/Items/Champion Artifacts/Shared/TheRobeOfBritanniaAri.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class TheRobeOfBritanniaAri : BaseOuterTorso - { - public override int LabelNumber => 1094931; // The Robe of Britannia "Ari" [Replica] + public class TheRobeOfBritanniaAri : BaseOuterTorso + { + [Constructible] + public TheRobeOfBritanniaAri() : base(0x2684) + { + Hue = 0x48b; + StrRequirement = 0; + } - public override int BasePhysicalResistance => 10; + public TheRobeOfBritanniaAri(Serial serial) : base(serial) + { + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public override int LabelNumber => 1094931; // The Robe of Britannia "Ari" [Replica] - public override bool CanFortify => false; + public override int BasePhysicalResistance => 10; - [Constructible] - public TheRobeOfBritanniaAri() : base( 0x2684 ) - { - Hue = 0x48b; - StrRequirement = 0; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public TheRobeOfBritanniaAri( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/AcidProofRobe.cs b/Scripts/Items/Champion Artifacts/Unique/AcidProofRobe.cs index f2ca7b101..43ebb52d5 100644 --- a/Scripts/Items/Champion Artifacts/Unique/AcidProofRobe.cs +++ b/Scripts/Items/Champion Artifacts/Unique/AcidProofRobe.cs @@ -1,44 +1,41 @@ namespace Server.Items { - public class AcidProofRobe : Robe - { - public override int LabelNumber => 1095236; // Acid-Proof Robe [Replica] + public class AcidProofRobe : Robe + { + [Constructible] + public AcidProofRobe() + { + Hue = 0x455; + LootType = LootType.Blessed; + } - public override int BaseFireResistance => 4; + public AcidProofRobe(Serial serial) : base(serial) + { + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public override int LabelNumber => 1095236; // Acid-Proof Robe [Replica] - public override bool CanFortify => false; + public override int BaseFireResistance => 4; - [Constructible] - public AcidProofRobe() - { - Hue = 0x455; - LootType = LootType.Blessed; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public AcidProofRobe( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if (version < 1 && Hue == 1) - { - Hue = 0x455; - } - } - } -} + if (version < 1 && Hue == 1) Hue = 0x455; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/Calm.cs b/Scripts/Items/Champion Artifacts/Unique/Calm.cs index 3d84487a6..023166785 100644 --- a/Scripts/Items/Champion Artifacts/Unique/Calm.cs +++ b/Scripts/Items/Champion Artifacts/Unique/Calm.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class Calm : Halberd - { - public override int LabelNumber => 1094915; // Calm [Replica] + public class Calm : Halberd + { + [Constructible] + public Calm() + { + Hue = 0x2cb; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.SpellChanneling = 1; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 50; - public override bool CanFortify => false; + WeaponAttributes.HitLeechMana = 100; + WeaponAttributes.UseBestSkill = 1; + } - [Constructible] - public Calm() - { - Hue = 0x2cb; + public Calm(Serial serial) : base(serial) + { + } - Attributes.SpellChanneling = 1; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 50; + public override int LabelNumber => 1094915; // Calm [Replica] - WeaponAttributes.HitLeechMana = 100; - WeaponAttributes.UseBestSkill = 1; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public Calm( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/CrownOfTalKeesh.cs b/Scripts/Items/Champion Artifacts/Unique/CrownOfTalKeesh.cs index e213909ed..f3a4231b8 100644 --- a/Scripts/Items/Champion Artifacts/Unique/CrownOfTalKeesh.cs +++ b/Scripts/Items/Champion Artifacts/Unique/CrownOfTalKeesh.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class CrownOfTalKeesh : Bandana - { - public override int LabelNumber => 1094903; // Crown of Tal'Keesh [Replica] + public class CrownOfTalKeesh : Bandana + { + [Constructible] + public CrownOfTalKeesh() + { + Hue = 0x4F2; - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 20; - public override int BaseEnergyResistance => 20; + Attributes.BonusInt = 8; + Attributes.RegenMana = 4; + Attributes.SpellDamage = 10; + } - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + public CrownOfTalKeesh(Serial serial) : base(serial) + { + } - public override bool CanFortify => false; + public override int LabelNumber => 1094903; // Crown of Tal'Keesh [Replica] - [Constructible] - public CrownOfTalKeesh() - { - Hue = 0x4F2; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 20; + public override int BaseEnergyResistance => 20; - Attributes.BonusInt = 8; - Attributes.RegenMana = 4; - Attributes.SpellDamage = 10; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public CrownOfTalKeesh( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/FangOfRactus.cs b/Scripts/Items/Champion Artifacts/Unique/FangOfRactus.cs index 719afd6fa..cdc67940a 100644 --- a/Scripts/Items/Champion Artifacts/Unique/FangOfRactus.cs +++ b/Scripts/Items/Champion Artifacts/Unique/FangOfRactus.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class FangOfRactus : Kryss - { - public override int LabelNumber => 1094892; // Fang of Ractus [Replica] + public class FangOfRactus : Kryss + { + [Constructible] + public FangOfRactus() + { + Hue = 0x117; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.SpellChanneling = 1; + Attributes.AttackChance = 5; + Attributes.DefendChance = 5; + Attributes.WeaponDamage = 35; - public override bool CanFortify => false; + WeaponAttributes.HitPoisonArea = 20; + WeaponAttributes.ResistPoisonBonus = 15; + } - [Constructible] - public FangOfRactus() - { - Hue = 0x117; + public FangOfRactus(Serial serial) : base(serial) + { + } - Attributes.SpellChanneling = 1; - Attributes.AttackChance = 5; - Attributes.DefendChance = 5; - Attributes.WeaponDamage = 35; + public override int LabelNumber => 1094892; // Fang of Ractus [Replica] - WeaponAttributes.HitPoisonArea = 20; - WeaponAttributes.ResistPoisonBonus = 15; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public FangOfRactus( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/GladiatorsCollar.cs b/Scripts/Items/Champion Artifacts/Unique/GladiatorsCollar.cs index 036b2e6bc..4997743f9 100644 --- a/Scripts/Items/Champion Artifacts/Unique/GladiatorsCollar.cs +++ b/Scripts/Items/Champion Artifacts/Unique/GladiatorsCollar.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class GladiatorsCollar : PlateGorget - { - public override int LabelNumber => 1094917; // Gladiator's Collar [Replica] + public class GladiatorsCollar : PlateGorget + { + [Constructible] + public GladiatorsCollar() + { + Hue = 0x26d; - public override int BasePhysicalResistance => 18; - public override int BaseFireResistance => 18; - public override int BaseColdResistance => 17; - public override int BasePoisonResistance => 18; - public override int BaseEnergyResistance => 16; + Attributes.BonusHits = 10; + Attributes.AttackChance = 10; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + ArmorAttributes.MageArmor = 1; + } - public override bool CanFortify => false; + public GladiatorsCollar(Serial serial) : base(serial) + { + } - [Constructible] - public GladiatorsCollar() - { - Hue = 0x26d; + public override int LabelNumber => 1094917; // Gladiator's Collar [Replica] - Attributes.BonusHits = 10; - Attributes.AttackChance = 10; + public override int BasePhysicalResistance => 18; + public override int BaseFireResistance => 18; + public override int BaseColdResistance => 17; + public override int BasePoisonResistance => 18; + public override int BaseEnergyResistance => 16; - ArmorAttributes.MageArmor = 1; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public GladiatorsCollar( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/OrcChieftainHelm.cs b/Scripts/Items/Champion Artifacts/Unique/OrcChieftainHelm.cs index 0ac774d15..8569ca58f 100644 --- a/Scripts/Items/Champion Artifacts/Unique/OrcChieftainHelm.cs +++ b/Scripts/Items/Champion Artifacts/Unique/OrcChieftainHelm.cs @@ -1,55 +1,52 @@ namespace Server.Items { - public class OrcChieftainHelm : OrcHelm - { - public override int LabelNumber => 1094924; // Orc Chieftain Helm [Replica] + public class OrcChieftainHelm : OrcHelm + { + [Constructible] + public OrcChieftainHelm() + { + Hue = 0x2a3; - public override int BasePhysicalResistance => 23; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 23; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 5; + Attributes.Luck = 100; + Attributes.RegenHits = 3; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + if (Utility.RandomBool()) + Attributes.BonusHits = 30; + else + Attributes.AttackChance = 30; + } - public override bool CanFortify => false; + public OrcChieftainHelm(Serial serial) : base(serial) + { + } - [Constructible] - public OrcChieftainHelm() - { - Hue = 0x2a3; + public override int LabelNumber => 1094924; // Orc Chieftain Helm [Replica] - Attributes.Luck = 100; - Attributes.RegenHits = 3; + public override int BasePhysicalResistance => 23; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 23; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 5; - if ( Utility.RandomBool() ) - Attributes.BonusHits = 30; - else - Attributes.AttackChance = 30; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public OrcChieftainHelm( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if (version < 1 && Hue == 0x3f) /* Pigmented? */ - { - Hue = 0x2a3; - } - } - } -} + if (version < 1 && Hue == 0x3f) /* Pigmented? */ Hue = 0x2a3; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/Pacify.cs b/Scripts/Items/Champion Artifacts/Unique/Pacify.cs index 45a777bb3..c48d9927a 100644 --- a/Scripts/Items/Champion Artifacts/Unique/Pacify.cs +++ b/Scripts/Items/Champion Artifacts/Unique/Pacify.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class Pacify : Pike - { - public override int LabelNumber => 1094929; // Pacify [Replica] + public class Pacify : Pike + { + [Constructible] + public Pacify() + { + Hue = 0x835; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.SpellChanneling = 1; + Attributes.AttackChance = 10; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 50; - public override bool CanFortify => false; + WeaponAttributes.HitLeechMana = 100; + WeaponAttributes.UseBestSkill = 1; + } - [Constructible] - public Pacify() - { - Hue = 0x835; + public Pacify(Serial serial) : base(serial) + { + } - Attributes.SpellChanneling = 1; - Attributes.AttackChance = 10; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 50; + public override int LabelNumber => 1094929; // Pacify [Replica] - WeaponAttributes.HitLeechMana = 100; - WeaponAttributes.UseBestSkill = 1; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public Pacify( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/Quell.cs b/Scripts/Items/Champion Artifacts/Unique/Quell.cs index 6c644b61a..0fa3a7fe3 100644 --- a/Scripts/Items/Champion Artifacts/Unique/Quell.cs +++ b/Scripts/Items/Champion Artifacts/Unique/Quell.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class Quell : Bardiche - { - public override int LabelNumber => 1094928; // Quell [Replica] + public class Quell : Bardiche + { + [Constructible] + public Quell() + { + Hue = 0x225; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.SpellChanneling = 1; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 50; + Attributes.AttackChance = 10; - public override bool CanFortify => false; + WeaponAttributes.HitLeechMana = 100; + WeaponAttributes.UseBestSkill = 1; + } - [Constructible] - public Quell() - { - Hue = 0x225; + public Quell(Serial serial) : base(serial) + { + } - Attributes.SpellChanneling = 1; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 50; - Attributes.AttackChance = 10; + public override int LabelNumber => 1094928; // Quell [Replica] - WeaponAttributes.HitLeechMana = 100; - WeaponAttributes.UseBestSkill = 1; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public Quell( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/ShroudOfDeceit.cs b/Scripts/Items/Champion Artifacts/Unique/ShroudOfDeceit.cs index ee5d753d8..e884adda2 100644 --- a/Scripts/Items/Champion Artifacts/Unique/ShroudOfDeceit.cs +++ b/Scripts/Items/Champion Artifacts/Unique/ShroudOfDeceit.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class ShroudOfDeciet : BoneChest - { - public override int LabelNumber => 1094914; // Shroud of Deceit [Replica] + public class ShroudOfDeciet : BoneChest + { + [Constructible] + public ShroudOfDeciet() + { + Hue = 0x38F; - public override int BasePhysicalResistance => 11; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 18; - public override int BasePoisonResistance => 15; - public override int BaseEnergyResistance => 13; + Attributes.RegenHits = 3; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + ArmorAttributes.MageArmor = 1; - public override bool CanFortify => false; + SkillBonuses.Skill_1_Name = SkillName.MagicResist; + SkillBonuses.Skill_1_Value = 10; + } - [Constructible] - public ShroudOfDeciet() - { - Hue = 0x38F; + public ShroudOfDeciet(Serial serial) : base(serial) + { + } - Attributes.RegenHits = 3; + public override int LabelNumber => 1094914; // Shroud of Deceit [Replica] - ArmorAttributes.MageArmor = 1; + public override int BasePhysicalResistance => 11; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 18; + public override int BasePoisonResistance => 15; + public override int BaseEnergyResistance => 13; - SkillBonuses.Skill_1_Name = SkillName.MagicResist; - SkillBonuses.Skill_1_Value = 10; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public ShroudOfDeciet( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Champion Artifacts/Unique/Subdue.cs b/Scripts/Items/Champion Artifacts/Unique/Subdue.cs index 827835bf1..74ad4fc94 100644 --- a/Scripts/Items/Champion Artifacts/Unique/Subdue.cs +++ b/Scripts/Items/Champion Artifacts/Unique/Subdue.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class Subdue : Scythe - { - public override int LabelNumber => 1094930; // Subdue [Replica] + public class Subdue : Scythe + { + [Constructible] + public Subdue() + { + Hue = 0x2cb; - public override int InitMinHits => 150; - public override int InitMaxHits => 150; + Attributes.SpellChanneling = 1; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 50; + Attributes.AttackChance = 10; - public override bool CanFortify => false; + WeaponAttributes.HitLeechMana = 100; + WeaponAttributes.UseBestSkill = 1; + } - [Constructible] - public Subdue() - { - Hue = 0x2cb; + public Subdue(Serial serial) : base(serial) + { + } - Attributes.SpellChanneling = 1; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 50; - Attributes.AttackChance = 10; + public override int LabelNumber => 1094930; // Subdue [Replica] - WeaponAttributes.HitLeechMana = 100; - WeaponAttributes.UseBestSkill = 1; - } + public override int InitMinHits => 150; + public override int InitMaxHits => 150; - public Subdue( Serial serial ) : base( serial ) - { - } + public override bool CanFortify => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Artifacts/CrimsonCincture.cs b/Scripts/Items/Clothing/Artifacts/CrimsonCincture.cs index c1bf310a8..4f2aabe3b 100644 --- a/Scripts/Items/Clothing/Artifacts/CrimsonCincture.cs +++ b/Scripts/Items/Clothing/Artifacts/CrimsonCincture.cs @@ -1,36 +1,35 @@ namespace Server.Items { - public class CrimsonCincture : HalfApron, ITokunoDyable - { - public override int LabelNumber => 1075043; // Crimson Cincture + public class CrimsonCincture : HalfApron, ITokunoDyable + { + [Constructible] + public CrimsonCincture() + { + Hue = 0x485; - [Constructible] - public CrimsonCincture() - { - Hue = 0x485; + Attributes.BonusDex = 5; + Attributes.BonusHits = 10; + Attributes.RegenHits = 2; + } - Attributes.BonusDex = 5; - Attributes.BonusHits = 10; - Attributes.RegenHits = 2; - } + public CrimsonCincture(Serial serial) : base(serial) + { + } - public CrimsonCincture( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075043; // Crimson Cincture - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Artifacts/DivineCountenance.cs b/Scripts/Items/Clothing/Artifacts/DivineCountenance.cs index 30e3fd7e8..4629b475b 100644 --- a/Scripts/Items/Clothing/Artifacts/DivineCountenance.cs +++ b/Scripts/Items/Clothing/Artifacts/DivineCountenance.cs @@ -1,58 +1,58 @@ namespace Server.Items { - public class DivineCountenance : HornedTribalMask - { - public override int LabelNumber => 1061289; // Divine Countenance + public class DivineCountenance : HornedTribalMask + { + [Constructible] + public DivineCountenance() + { + Hue = 0x482; - public override int ArtifactRarity => 11; + Attributes.BonusInt = 8; + Attributes.RegenMana = 2; + Attributes.ReflectPhysical = 15; + Attributes.LowerManaCost = 8; + } - public override int BasePhysicalResistance => 8; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 9; - public override int BaseEnergyResistance => 25; + public DivineCountenance(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061289; // Divine Countenance - [Constructible] - public DivineCountenance() - { - Hue = 0x482; + public override int ArtifactRarity => 11; - Attributes.BonusInt = 8; - Attributes.RegenMana = 2; - Attributes.ReflectPhysical = 15; - Attributes.LowerManaCost = 8; - } + public override int BasePhysicalResistance => 8; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 9; + public override int BaseEnergyResistance => 25; - public DivineCountenance( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Resistances.Physical = 0; - Resistances.Fire = 0; - Resistances.Cold = 0; - Resistances.Energy = 0; - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Resistances.Physical = 0; + Resistances.Fire = 0; + Resistances.Cold = 0; + Resistances.Energy = 0; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Artifacts/HatOfTheMagi.cs b/Scripts/Items/Clothing/Artifacts/HatOfTheMagi.cs index 4f2f5209f..d32ecc2f4 100644 --- a/Scripts/Items/Clothing/Artifacts/HatOfTheMagi.cs +++ b/Scripts/Items/Clothing/Artifacts/HatOfTheMagi.cs @@ -1,53 +1,53 @@ namespace Server.Items { - public class HatOfTheMagi : WizardsHat - { - public override int LabelNumber => 1061597; // Hat of the Magi + public class HatOfTheMagi : WizardsHat + { + [Constructible] + public HatOfTheMagi() + { + Hue = 0x481; - public override int ArtifactRarity => 11; + Attributes.BonusInt = 8; + Attributes.RegenMana = 4; + Attributes.SpellDamage = 10; + } - public override int BasePoisonResistance => 20; - public override int BaseEnergyResistance => 20; + public HatOfTheMagi(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061597; // Hat of the Magi - [Constructible] - public HatOfTheMagi() - { - Hue = 0x481; + public override int ArtifactRarity => 11; - Attributes.BonusInt = 8; - Attributes.RegenMana = 4; - Attributes.SpellDamage = 10; - } + public override int BasePoisonResistance => 20; + public override int BaseEnergyResistance => 20; - public HatOfTheMagi( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Resistances.Poison = 0; - Resistances.Energy = 0; - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Resistances.Poison = 0; + Resistances.Energy = 0; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Artifacts/HuntersHeaddress.cs b/Scripts/Items/Clothing/Artifacts/HuntersHeaddress.cs index a1fea15eb..925233e77 100644 --- a/Scripts/Items/Clothing/Artifacts/HuntersHeaddress.cs +++ b/Scripts/Items/Clothing/Artifacts/HuntersHeaddress.cs @@ -1,53 +1,52 @@ namespace Server.Items { - public class HuntersHeaddress : DeerMask - { - public override int LabelNumber => 1061595; // Hunter's Headdress + public class HuntersHeaddress : DeerMask + { + [Constructible] + public HuntersHeaddress() + { + Hue = 0x594; - public override int ArtifactRarity => 11; + SkillBonuses.SetValues(0, SkillName.Archery, 20); - public override int BaseColdResistance => 23; + Attributes.BonusDex = 8; + Attributes.NightSight = 1; + Attributes.AttackChance = 15; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public HuntersHeaddress(Serial serial) : base(serial) + { + } - [Constructible] - public HuntersHeaddress() - { - Hue = 0x594; + public override int LabelNumber => 1061595; // Hunter's Headdress - SkillBonuses.SetValues( 0, SkillName.Archery, 20 ); + public override int ArtifactRarity => 11; - Attributes.BonusDex = 8; - Attributes.NightSight = 1; - Attributes.AttackChance = 15; + public override int BaseColdResistance => 23; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public HuntersHeaddress( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(1); + } - writer.Write( (int) 1 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Resistances.Cold = 0; - break; - } - } - } - } -} + int version = reader.ReadInt(); + switch (version) + { + case 0: + { + Resistances.Cold = 0; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Artifacts/SpiritOfTheTotem.cs b/Scripts/Items/Clothing/Artifacts/SpiritOfTheTotem.cs index 88d79c571..54b3a6763 100644 --- a/Scripts/Items/Clothing/Artifacts/SpiritOfTheTotem.cs +++ b/Scripts/Items/Clothing/Artifacts/SpiritOfTheTotem.cs @@ -1,51 +1,51 @@ namespace Server.Items { - public class SpiritOfTheTotem : BearMask - { - public override int LabelNumber => 1061599; // Spirit of the Totem + public class SpiritOfTheTotem : BearMask + { + [Constructible] + public SpiritOfTheTotem() + { + Hue = 0x455; - public override int ArtifactRarity => 11; + Attributes.BonusStr = 20; + Attributes.ReflectPhysical = 15; + Attributes.AttackChance = 15; + } - public override int BasePhysicalResistance => 20; + public SpiritOfTheTotem(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061599; // Spirit of the Totem - [Constructible] - public SpiritOfTheTotem() - { - Hue = 0x455; + public override int ArtifactRarity => 11; - Attributes.BonusStr = 20; - Attributes.ReflectPhysical = 15; - Attributes.AttackChance = 15; - } + public override int BasePhysicalResistance => 20; - public SpiritOfTheTotem( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Resistances.Physical = 0; - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Resistances.Physical = 0; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/BaseClothing.cs b/Scripts/Items/Clothing/BaseClothing.cs index dc411d68e..eecc9df01 100644 --- a/Scripts/Items/Clothing/BaseClothing.cs +++ b/Scripts/Items/Clothing/BaseClothing.cs @@ -1,1016 +1,1092 @@ using System; using System.Collections.Generic; using Server.Engines.Craft; +using Server.Ethics; using Server.Factions; using Server.Network; namespace Server.Items { - public enum ClothingQuality - { - Low, - Regular, - Exceptional - } - - public interface IArcaneEquip - { - bool IsArcane{ get; } - int CurArcaneCharges{ get; set; } - int MaxArcaneCharges{ get; set; } - } - - public abstract class BaseClothing : Item, IDyable, IScissorable, IFactionItem, ICraftable, IWearableDurability - { - #region Factions - private FactionItem m_FactionState; - - public FactionItem FactionItemState - { - get => m_FactionState; - set - { - m_FactionState = value; - - if ( m_FactionState == null ) - Hue = 0; - - LootType = ( m_FactionState == null ? LootType.Regular : LootType.Blessed ); - } - } - #endregion - - public virtual bool CanFortify => true; - - private int m_MaxHitPoints; - private int m_HitPoints; - private Mobile m_Crafter; - private ClothingQuality m_Quality; - protected CraftResource m_Resource; - private int m_StrReq = -1; - - private AosAttributes m_AosAttributes; - private AosArmorAttributes m_AosClothingAttributes; - private AosSkillBonuses m_AosSkillBonuses; - private AosElementAttributes m_AosResistances; - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxHitPoints - { - get => m_MaxHitPoints; - set{ m_MaxHitPoints = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitPoints - { - get => m_HitPoints; - set - { - if ( value != m_HitPoints && MaxHitPoints > 0 ) - { - m_HitPoints = value; - - if ( m_HitPoints < 0 ) - Delete(); - else if ( m_HitPoints > MaxHitPoints ) - m_HitPoints = MaxHitPoints; - - InvalidateProperties(); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int StrRequirement - { - get => ( m_StrReq == -1 ? (Core.AOS ? AosStrReq : OldStrReq) : m_StrReq ); - set{ m_StrReq = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public ClothingQuality Quality - { - get => m_Quality; - set{ m_Quality = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool PlayerConstructed { get; set; } - - public virtual CraftResource DefaultResource => CraftResource.None; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; Hue = CraftResources.GetHue( m_Resource ); InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosAttributes Attributes - { - get => m_AosAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosArmorAttributes ClothingAttributes - { - get => m_AosClothingAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosSkillBonuses SkillBonuses - { - get => m_AosSkillBonuses; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosElementAttributes Resistances - { - get => m_AosResistances; - set{} - } - - public virtual int BasePhysicalResistance => 0; - public virtual int BaseFireResistance => 0; - public virtual int BaseColdResistance => 0; - public virtual int BasePoisonResistance => 0; - public virtual int BaseEnergyResistance => 0; - - public override int PhysicalResistance => BasePhysicalResistance + m_AosResistances.Physical; - public override int FireResistance => BaseFireResistance + m_AosResistances.Fire; - public override int ColdResistance => BaseColdResistance + m_AosResistances.Cold; - public override int PoisonResistance => BasePoisonResistance + m_AosResistances.Poison; - public override int EnergyResistance => BaseEnergyResistance + m_AosResistances.Energy; - - public virtual int ArtifactRarity => 0; - - public virtual int BaseStrBonus => 0; - public virtual int BaseDexBonus => 0; - public virtual int BaseIntBonus => 0; - - public override bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - if ( !Ethics.Ethic.CheckTrade( from, to, newOwner, this ) ) - return false; - - return base.AllowSecureTrade( from, to, newOwner, accepted ); - } - - public virtual Race RequiredRace => null; - - public override bool CanEquip( Mobile from ) - { - if ( !Ethics.Ethic.CheckEquip( from, this ) ) - return false; - - if ( from.AccessLevel < AccessLevel.GameMaster ) - { - if ( RequiredRace != null && from.Race != RequiredRace ) - { - if ( RequiredRace == Race.Elf ) - from.SendLocalizedMessage( 1072203 ); // Only Elves may use this. - else - from.SendMessage( "Only {0} may use this.", RequiredRace.PluralName ); - - return false; - } - - if ( !AllowMaleWearer && !from.Female ) - { - if ( AllowFemaleWearer ) - from.SendLocalizedMessage( 1010388 ); // Only females can wear this. - else - from.SendMessage( "You may not wear this." ); - - return false; - } - if ( !AllowFemaleWearer && from.Female ) - { - if ( AllowMaleWearer ) - from.SendLocalizedMessage( 1063343 ); // Only males can wear this. - else - from.SendMessage( "You may not wear this." ); - - return false; - } - int strBonus = ComputeStatBonus( StatType.Str ); - int strReq = ComputeStatReq( StatType.Str ); - - if ( from.Str < strReq || (from.Str + strBonus) < 1 ) - { - from.SendLocalizedMessage( 500213 ); // You are not strong enough to equip that. - return false; - } - } - - return base.CanEquip( from ); - } - - public virtual int AosStrReq => 10; - public virtual int OldStrReq => 0; - - public virtual int InitMinHits => 0; - public virtual int InitMaxHits => 0; - - public virtual bool AllowMaleWearer => true; - public virtual bool AllowFemaleWearer => true; - public virtual bool CanBeBlessed => true; - - public int ComputeStatReq( StatType type ) - { - int v; - - //if ( type == StatType.Str ) - v = StrRequirement; - - return AOS.Scale( v, 100 - GetLowerStatReq() ); - } - - public int ComputeStatBonus( StatType type ) - { - if ( type == StatType.Str ) - return BaseStrBonus + Attributes.BonusStr; - if ( type == StatType.Dex ) - return BaseDexBonus + Attributes.BonusDex; - return BaseIntBonus + Attributes.BonusInt; - } - - public virtual void AddStatBonuses( Mobile parent ) - { - if ( parent == null ) - return; - - int strBonus = ComputeStatBonus( StatType.Str ); - int dexBonus = ComputeStatBonus( StatType.Dex ); - int intBonus = ComputeStatBonus( StatType.Int ); - - if ( strBonus == 0 && dexBonus == 0 && intBonus == 0 ) - return; - - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - parent.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - parent.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - parent.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - public static void ValidateMobile( Mobile m ) - { - for ( int i = m.Items.Count - 1; i >= 0; --i ) - { - if ( i >= m.Items.Count ) - continue; - - Item item = m.Items[i]; - - if ( item is BaseClothing clothing ) - { - if ( clothing.RequiredRace != null && m.Race != clothing.RequiredRace ) - { - if ( clothing.RequiredRace == Race.Elf ) - m.SendLocalizedMessage( 1072203 ); // Only Elves may use this. - else - m.SendMessage( "Only {0} may use this.", clothing.RequiredRace.PluralName ); - - m.AddToBackpack( clothing ); - } - else if ( !clothing.AllowMaleWearer && !m.Female && m.AccessLevel < AccessLevel.GameMaster ) - { - if ( clothing.AllowFemaleWearer ) - m.SendLocalizedMessage( 1010388 ); // Only females can wear this. - else - m.SendMessage( "You may not wear this." ); - - m.AddToBackpack( clothing ); - } - else if ( !clothing.AllowFemaleWearer && m.Female && m.AccessLevel < AccessLevel.GameMaster ) - { - if ( clothing.AllowMaleWearer ) - m.SendLocalizedMessage( 1063343 ); // Only males can wear this. - else - m.SendMessage( "You may not wear this." ); - - m.AddToBackpack( clothing ); - } - } - } - } - - public int GetLowerStatReq() - { - if ( !Core.AOS ) - return 0; - - return m_AosClothingAttributes.LowerStatReq; - } - - public override void OnAdded(IEntity parent) - { - if ( parent is Mobile mob ) - { - if ( Core.AOS ) - m_AosSkillBonuses.AddTo( mob ); - - AddStatBonuses( mob ); - mob.CheckStatTimers(); - } - - base.OnAdded( parent ); - } - - public override void OnRemoved(IEntity parent) - { - if ( parent is Mobile mob ) - { - if ( Core.AOS ) - m_AosSkillBonuses.Remove(); - - string modName = Serial.ToString(); - - mob.RemoveStatMod( modName + "Str" ); - mob.RemoveStatMod( modName + "Dex" ); - mob.RemoveStatMod( modName + "Int" ); - - mob.CheckStatTimers(); - } - - base.OnRemoved( parent ); - } - - public virtual int OnHit( BaseWeapon weapon, int damageTaken ) - { - int Absorbed = Utility.RandomMinMax( 1, 4 ); - - damageTaken -= Absorbed; - - if ( damageTaken < 0 ) - damageTaken = 0; - - if ( 25 > Utility.Random( 100 ) ) // 25% chance to lower durability - { - if ( Core.AOS && m_AosClothingAttributes.SelfRepair > Utility.Random( 10 ) ) - { - HitPoints += 2; - } - else - { - int wear; - - if ( weapon.Type == WeaponType.Bashing ) - wear = Absorbed / 2; - else - wear = Utility.Random( 2 ); - - if ( wear > 0 && m_MaxHitPoints > 0 ) - { - if ( m_HitPoints >= wear ) - { - HitPoints -= wear; - wear = 0; - } - else - { - wear -= HitPoints; - HitPoints = 0; - } - - if ( wear > 0 ) - { - if ( m_MaxHitPoints > wear ) - { - MaxHitPoints -= wear; - - (Parent as Mobile)?.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061121 ); // Your equipment is severely damaged. - } - else - { - Delete(); - } - } - } - } - } - - return damageTaken; - } - - public BaseClothing( int itemID, Layer layer ) : this( itemID, layer, 0 ) - { - } - - public BaseClothing( int itemID, Layer layer, int hue ) : base( itemID ) - { - Layer = layer; - Hue = hue; - - m_Resource = DefaultResource; - m_Quality = ClothingQuality.Regular; - - m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - - m_AosAttributes = new AosAttributes( this ); - m_AosClothingAttributes = new AosArmorAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - m_AosResistances = new AosElementAttributes( this ); - } - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is BaseClothing clothing) ) - return; - - clothing.m_AosAttributes = new AosAttributes( newItem, m_AosAttributes ); - clothing.m_AosResistances = new AosElementAttributes( newItem, m_AosResistances ); - clothing.m_AosSkillBonuses = new AosSkillBonuses( newItem, m_AosSkillBonuses ); - clothing.m_AosClothingAttributes = new AosArmorAttributes( newItem, m_AosClothingAttributes ); - } - - public BaseClothing( Serial serial ) : base( serial ) - { - } - - public override bool AllowEquippedCast( Mobile from ) - { - if ( base.AllowEquippedCast( from ) ) - return true; - - return ( m_AosAttributes.SpellChanneling != 0 ); - } - - public void UnscaleDurability() - { - int scale = 100 + m_AosClothingAttributes.DurabilityBonus; - - m_HitPoints = ( ( m_HitPoints * 100 ) + ( scale - 1 ) ) / scale; - m_MaxHitPoints = ( ( m_MaxHitPoints * 100 ) + ( scale - 1 ) ) / scale; - - InvalidateProperties(); - } - - public void ScaleDurability() - { - int scale = 100 + m_AosClothingAttributes.DurabilityBonus; - - m_HitPoints = ( ( m_HitPoints * scale ) + 99 ) / 100; - m_MaxHitPoints = ( ( m_MaxHitPoints * scale ) + 99 ) / 100; - - InvalidateProperties(); - } - - public override bool CheckPropertyConfliction( Mobile m ) - { - if ( base.CheckPropertyConfliction( m ) ) - return true; - - if ( Layer == Layer.Pants ) - return ( m.FindItemOnLayer( Layer.InnerLegs ) != null ); - - if ( Layer == Layer.Shirt ) - return ( m.FindItemOnLayer( Layer.InnerTorso ) != null ); - - return false; - } - - private string GetNameString() - { - string name = Name; - - if ( name == null ) - name = $"#{LabelNumber}"; - - return name; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - int oreType; + public enum ClothingQuality + { + Low, + Regular, + Exceptional + } + + public interface IArcaneEquip + { + bool IsArcane{ get; } + int CurArcaneCharges{ get; set; } + int MaxArcaneCharges{ get; set; } + } + + public abstract class BaseClothing : Item, IDyable, IScissorable, IFactionItem, ICraftable, IWearableDurability + { + private AosAttributes m_AosAttributes; + private AosArmorAttributes m_AosClothingAttributes; + private AosElementAttributes m_AosResistances; + private AosSkillBonuses m_AosSkillBonuses; + private Mobile m_Crafter; + private int m_HitPoints; + + private int m_MaxHitPoints; + private ClothingQuality m_Quality; + protected CraftResource m_Resource; + private int m_StrReq = -1; + + public BaseClothing(int itemID, Layer layer) : this(itemID, layer, 0) + { + } + + public BaseClothing(int itemID, Layer layer, int hue) : base(itemID) + { + Layer = layer; + Hue = hue; + + m_Resource = DefaultResource; + m_Quality = ClothingQuality.Regular; + + m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax(InitMinHits, InitMaxHits); + + m_AosAttributes = new AosAttributes(this); + m_AosClothingAttributes = new AosArmorAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + m_AosResistances = new AosElementAttributes(this); + } + + public BaseClothing(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int StrRequirement + { + get => m_StrReq == -1 ? Core.AOS ? AosStrReq : OldStrReq : m_StrReq; + set + { + m_StrReq = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public ClothingQuality Quality + { + get => m_Quality; + set + { + m_Quality = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool PlayerConstructed{ get; set; } + + public virtual CraftResource DefaultResource => CraftResource.None; + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosAttributes Attributes + { + get => m_AosAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosArmorAttributes ClothingAttributes + { + get => m_AosClothingAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosSkillBonuses SkillBonuses + { + get => m_AosSkillBonuses; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosElementAttributes Resistances + { + get => m_AosResistances; + set { } + } + + public virtual int BasePhysicalResistance => 0; + public virtual int BaseFireResistance => 0; + public virtual int BaseColdResistance => 0; + public virtual int BasePoisonResistance => 0; + public virtual int BaseEnergyResistance => 0; + + public override int PhysicalResistance => BasePhysicalResistance + m_AosResistances.Physical; + public override int FireResistance => BaseFireResistance + m_AosResistances.Fire; + public override int ColdResistance => BaseColdResistance + m_AosResistances.Cold; + public override int PoisonResistance => BasePoisonResistance + m_AosResistances.Poison; + public override int EnergyResistance => BaseEnergyResistance + m_AosResistances.Energy; + + public virtual int ArtifactRarity => 0; + + public virtual int BaseStrBonus => 0; + public virtual int BaseDexBonus => 0; + public virtual int BaseIntBonus => 0; + + public virtual Race RequiredRace => null; + + public virtual int AosStrReq => 10; + public virtual int OldStrReq => 0; + + public virtual bool AllowMaleWearer => true; + public virtual bool AllowFemaleWearer => true; + public virtual bool CanBeBlessed => true; + + #region ICraftable Members + + public virtual int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, + BaseTool tool, CraftItem craftItem, int resHue) + { + Quality = (ClothingQuality)quality; + + if (makersMark) + Crafter = from; + + if (DefaultResource != CraftResource.None) + { + Type resourceType = typeRes; + + if (resourceType == null) + resourceType = craftItem.Resources.GetAt(0).ItemType; + + Resource = CraftResources.GetFromType(resourceType); + } + else + { + Hue = resHue; + } + + PlayerConstructed = true; + + CraftContext context = craftSystem.GetContext(from); + + if (context != null && context.DoNotColor) + Hue = 0; + + return quality; + } + + #endregion + + public virtual bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; + if (RootParent is Mobile && from != RootParent) + return false; + + Hue = sender.DyedHue; + + return true; + } + + public virtual bool Scissor(Mobile from, Scissors scissors) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502437); // Items you wish to cut must be in your backpack. + return false; + } + + if (Ethic.IsImbued(this)) + { + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } + + CraftSystem system = DefTailoring.CraftSystem; + + CraftItem item = system.CraftItems.SearchFor(GetType()); + + if (item != null && item.Resources.Count == 1 && item.Resources.GetAt(0).Amount >= 2) + try + { + Type resourceType = null; + + CraftResourceInfo info = CraftResources.GetInfo(m_Resource); + + if (info != null && info.ResourceTypes.Length > 0) + resourceType = info.ResourceTypes[0]; + + if (resourceType == null) + resourceType = item.Resources.GetAt(0).ItemType; + + Item res = (Item)Activator.CreateInstance(resourceType); + + ScissorHelper(from, res, PlayerConstructed ? item.Resources.GetAt(0).Amount / 2 : 1); + + res.LootType = LootType.Regular; + + return true; + } + catch + { + } + + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } + + public virtual bool CanFortify => true; + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxHitPoints + { + get => m_MaxHitPoints; + set + { + m_MaxHitPoints = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitPoints + { + get => m_HitPoints; + set + { + if (value != m_HitPoints && MaxHitPoints > 0) + { + m_HitPoints = value; + + if (m_HitPoints < 0) + Delete(); + else if (m_HitPoints > MaxHitPoints) + m_HitPoints = MaxHitPoints; + + InvalidateProperties(); + } + } + } + + public virtual int InitMinHits => 0; + public virtual int InitMaxHits => 0; + + public virtual int OnHit(BaseWeapon weapon, int damageTaken) + { + int Absorbed = Utility.RandomMinMax(1, 4); + + damageTaken -= Absorbed; + + if (damageTaken < 0) + damageTaken = 0; + + if (25 > Utility.Random(100)) // 25% chance to lower durability + { + if (Core.AOS && m_AosClothingAttributes.SelfRepair > Utility.Random(10)) + { + HitPoints += 2; + } + else + { + int wear; + + if (weapon.Type == WeaponType.Bashing) + wear = Absorbed / 2; + else + wear = Utility.Random(2); + + if (wear > 0 && m_MaxHitPoints > 0) + { + if (m_HitPoints >= wear) + { + HitPoints -= wear; + wear = 0; + } + else + { + wear -= HitPoints; + HitPoints = 0; + } + + if (wear > 0) + { + if (m_MaxHitPoints > wear) + { + MaxHitPoints -= wear; + + (Parent as Mobile)?.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061121); // Your equipment is severely damaged. + } + else + { + Delete(); + } + } + } + } + } + + return damageTaken; + } + + public void UnscaleDurability() + { + int scale = 100 + m_AosClothingAttributes.DurabilityBonus; + + m_HitPoints = (m_HitPoints * 100 + (scale - 1)) / scale; + m_MaxHitPoints = (m_MaxHitPoints * 100 + (scale - 1)) / scale; + + InvalidateProperties(); + } + + public void ScaleDurability() + { + int scale = 100 + m_AosClothingAttributes.DurabilityBonus; + + m_HitPoints = (m_HitPoints * scale + 99) / 100; + m_MaxHitPoints = (m_MaxHitPoints * scale + 99) / 100; + + InvalidateProperties(); + } + + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (!Ethic.CheckTrade(from, to, newOwner, this)) + return false; + + return base.AllowSecureTrade(from, to, newOwner, accepted); + } + + public override bool CanEquip(Mobile from) + { + if (!Ethic.CheckEquip(from, this)) + return false; + + if (from.AccessLevel < AccessLevel.GameMaster) + { + if (RequiredRace != null && from.Race != RequiredRace) + { + if (RequiredRace == Race.Elf) + from.SendLocalizedMessage(1072203); // Only Elves may use this. + else + from.SendMessage("Only {0} may use this.", RequiredRace.PluralName); + + return false; + } + + if (!AllowMaleWearer && !from.Female) + { + if (AllowFemaleWearer) + from.SendLocalizedMessage(1010388); // Only females can wear this. + else + from.SendMessage("You may not wear this."); + + return false; + } + + if (!AllowFemaleWearer && from.Female) + { + if (AllowMaleWearer) + from.SendLocalizedMessage(1063343); // Only males can wear this. + else + from.SendMessage("You may not wear this."); + + return false; + } + + int strBonus = ComputeStatBonus(StatType.Str); + int strReq = ComputeStatReq(StatType.Str); + + if (from.Str < strReq || from.Str + strBonus < 1) + { + from.SendLocalizedMessage(500213); // You are not strong enough to equip that. + return false; + } + } + + return base.CanEquip(from); + } + + public int ComputeStatReq(StatType type) + { + int v; + + //if ( type == StatType.Str ) + v = StrRequirement; + + return AOS.Scale(v, 100 - GetLowerStatReq()); + } + + public int ComputeStatBonus(StatType type) + { + if (type == StatType.Str) + return BaseStrBonus + Attributes.BonusStr; + if (type == StatType.Dex) + return BaseDexBonus + Attributes.BonusDex; + return BaseIntBonus + Attributes.BonusInt; + } + + public virtual void AddStatBonuses(Mobile parent) + { + if (parent == null) + return; + + int strBonus = ComputeStatBonus(StatType.Str); + int dexBonus = ComputeStatBonus(StatType.Dex); + int intBonus = ComputeStatBonus(StatType.Int); + + if (strBonus == 0 && dexBonus == 0 && intBonus == 0) + return; + + string modName = Serial.ToString(); + + if (strBonus != 0) + parent.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + parent.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + parent.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + public static void ValidateMobile(Mobile m) + { + for (int i = m.Items.Count - 1; i >= 0; --i) + { + if (i >= m.Items.Count) + continue; + + Item item = m.Items[i]; + + if (item is BaseClothing clothing) + { + if (clothing.RequiredRace != null && m.Race != clothing.RequiredRace) + { + if (clothing.RequiredRace == Race.Elf) + m.SendLocalizedMessage(1072203); // Only Elves may use this. + else + m.SendMessage("Only {0} may use this.", clothing.RequiredRace.PluralName); + + m.AddToBackpack(clothing); + } + else if (!clothing.AllowMaleWearer && !m.Female && m.AccessLevel < AccessLevel.GameMaster) + { + if (clothing.AllowFemaleWearer) + m.SendLocalizedMessage(1010388); // Only females can wear this. + else + m.SendMessage("You may not wear this."); + + m.AddToBackpack(clothing); + } + else if (!clothing.AllowFemaleWearer && m.Female && m.AccessLevel < AccessLevel.GameMaster) + { + if (clothing.AllowMaleWearer) + m.SendLocalizedMessage(1063343); // Only males can wear this. + else + m.SendMessage("You may not wear this."); + + m.AddToBackpack(clothing); + } + } + } + } + + public int GetLowerStatReq() + { + if (!Core.AOS) + return 0; + + return m_AosClothingAttributes.LowerStatReq; + } + + public override void OnAdded(IEntity parent) + { + if (parent is Mobile mob) + { + if (Core.AOS) + m_AosSkillBonuses.AddTo(mob); + + AddStatBonuses(mob); + mob.CheckStatTimers(); + } + + base.OnAdded(parent); + } + + public override void OnRemoved(IEntity parent) + { + if (parent is Mobile mob) + { + if (Core.AOS) + m_AosSkillBonuses.Remove(); + + string modName = Serial.ToString(); + + mob.RemoveStatMod(modName + "Str"); + mob.RemoveStatMod(modName + "Dex"); + mob.RemoveStatMod(modName + "Int"); + + mob.CheckStatTimers(); + } + + base.OnRemoved(parent); + } + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is BaseClothing clothing)) + return; + + clothing.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); + clothing.m_AosResistances = new AosElementAttributes(newItem, m_AosResistances); + clothing.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); + clothing.m_AosClothingAttributes = new AosArmorAttributes(newItem, m_AosClothingAttributes); + } + + public override bool AllowEquippedCast(Mobile from) + { + if (base.AllowEquippedCast(from)) + return true; + + return m_AosAttributes.SpellChanneling != 0; + } + + public override bool CheckPropertyConfliction(Mobile m) + { + if (base.CheckPropertyConfliction(m)) + return true; + + if (Layer == Layer.Pants) + return m.FindItemOnLayer(Layer.InnerLegs) != null; + + if (Layer == Layer.Shirt) + return m.FindItemOnLayer(Layer.InnerTorso) != null; + + return false; + } + + private string GetNameString() + { + string name = Name; + + if (name == null) + name = $"#{LabelNumber}"; + + return name; + } + + public override void AddNameProperty(ObjectPropertyList list) + { + int oreType; + + switch (m_Resource) + { + case CraftResource.DullCopper: + oreType = 1053108; + break; // dull copper + case CraftResource.ShadowIron: + oreType = 1053107; + break; // shadow iron + case CraftResource.Copper: + oreType = 1053106; + break; // copper + case CraftResource.Bronze: + oreType = 1053105; + break; // bronze + case CraftResource.Gold: + oreType = 1053104; + break; // golden + case CraftResource.Agapite: + oreType = 1053103; + break; // agapite + case CraftResource.Verite: + oreType = 1053102; + break; // verite + case CraftResource.Valorite: + oreType = 1053101; + break; // valorite + case CraftResource.SpinedLeather: + oreType = 1061118; + break; // spined + case CraftResource.HornedLeather: + oreType = 1061117; + break; // horned + case CraftResource.BarbedLeather: + oreType = 1061116; + break; // barbed + case CraftResource.RedScales: + oreType = 1060814; + break; // red + case CraftResource.YellowScales: + oreType = 1060818; + break; // yellow + case CraftResource.BlackScales: + oreType = 1060820; + break; // black + case CraftResource.GreenScales: + oreType = 1060819; + break; // green + case CraftResource.WhiteScales: + oreType = 1060821; + break; // white + case CraftResource.BlueScales: + oreType = 1060815; + break; // blue + default: + oreType = 0; + break; + } + + if (oreType != 0) + list.Add(1053099, "#{0}\t{1}", oreType, GetNameString()); // ~1_oretype~ ~2_armortype~ + else if (Name == null) + list.Add(LabelNumber); + else + list.Add(Name); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ + + #region Factions + + if (m_FactionState != null) + list.Add(1041350); // faction item + + #endregion + + if (m_Quality == ClothingQuality.Exceptional) + list.Add(1060636); // exceptional + + if (RequiredRace == Race.Elf) + list.Add(1075086); // Elves Only + + m_AosSkillBonuses?.GetProperties(list); + + int prop; + + if ((prop = ArtifactRarity) > 0) + list.Add(1061078, prop.ToString()); // artifact rarity ~1_val~ + + if ((prop = m_AosAttributes.WeaponDamage) != 0) + list.Add(1060401, prop.ToString()); // damage increase ~1_val~% + + if ((prop = m_AosAttributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% + + if ((prop = m_AosAttributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ + + if ((prop = m_AosAttributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% + + if ((prop = m_AosAttributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ + + if ((prop = m_AosAttributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ + + if ((prop = m_AosAttributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - switch ( m_Resource ) - { - case CraftResource.DullCopper: oreType = 1053108; break; // dull copper - case CraftResource.ShadowIron: oreType = 1053107; break; // shadow iron - case CraftResource.Copper: oreType = 1053106; break; // copper - case CraftResource.Bronze: oreType = 1053105; break; // bronze - case CraftResource.Gold: oreType = 1053104; break; // golden - case CraftResource.Agapite: oreType = 1053103; break; // agapite - case CraftResource.Verite: oreType = 1053102; break; // verite - case CraftResource.Valorite: oreType = 1053101; break; // valorite - case CraftResource.SpinedLeather: oreType = 1061118; break; // spined - case CraftResource.HornedLeather: oreType = 1061117; break; // horned - case CraftResource.BarbedLeather: oreType = 1061116; break; // barbed - case CraftResource.RedScales: oreType = 1060814; break; // red - case CraftResource.YellowScales: oreType = 1060818; break; // yellow - case CraftResource.BlackScales: oreType = 1060820; break; // black - case CraftResource.GreenScales: oreType = 1060819; break; // green - case CraftResource.WhiteScales: oreType = 1060821; break; // white - case CraftResource.BlueScales: oreType = 1060815; break; // blue - default: oreType = 0; break; - } + if ((prop = m_AosAttributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if ( oreType != 0 ) - list.Add( 1053099, "#{0}\t{1}", oreType, GetNameString() ); // ~1_oretype~ ~2_armortype~ - else if ( Name == null ) - list.Add( LabelNumber ); - else - list.Add( Name ); - } + if ((prop = m_AosAttributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if ((prop = m_AosAttributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if ((prop = m_AosAttributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - #region Factions - if ( m_FactionState != null ) - list.Add( 1041350 ); // faction item - #endregion + if ((prop = m_AosClothingAttributes.LowerStatReq) != 0) + list.Add(1060435, prop.ToString()); // lower requirements ~1_val~% - if ( m_Quality == ClothingQuality.Exceptional ) - list.Add( 1060636 ); // exceptional + if ((prop = m_AosAttributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - if ( RequiredRace == Race.Elf ) - list.Add( 1075086 ); // Elves Only + if ((prop = m_AosClothingAttributes.MageArmor) != 0) + list.Add(1060437); // mage armor - m_AosSkillBonuses?.GetProperties( list ); + if ((prop = m_AosAttributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - int prop; + if ((prop = m_AosAttributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - if ( (prop = ArtifactRarity) > 0 ) - list.Add( 1061078, prop.ToString() ); // artifact rarity ~1_val~ + if ((prop = m_AosAttributes.NightSight) != 0) + list.Add(1060441); // night sight - if ( (prop = m_AosAttributes.WeaponDamage) != 0 ) - list.Add( 1060401, prop.ToString() ); // damage increase ~1_val~% + if ((prop = m_AosAttributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - if ( (prop = m_AosAttributes.DefendChance) != 0 ) - list.Add( 1060408, prop.ToString() ); // defense chance increase ~1_val~% + if ((prop = m_AosAttributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - if ( (prop = m_AosAttributes.BonusDex) != 0 ) - list.Add( 1060409, prop.ToString() ); // dexterity bonus ~1_val~ + if ((prop = m_AosAttributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if ( (prop = m_AosAttributes.EnhancePotions) != 0 ) - list.Add( 1060411, prop.ToString() ); // enhance potions ~1_val~% + if ((prop = m_AosClothingAttributes.SelfRepair) != 0) + list.Add(1060450, prop.ToString()); // self repair ~1_val~ - if ( (prop = m_AosAttributes.CastRecovery) != 0 ) - list.Add( 1060412, prop.ToString() ); // faster cast recovery ~1_val~ + if ((prop = m_AosAttributes.SpellChanneling) != 0) + list.Add(1060482); // spell channeling - if ( (prop = m_AosAttributes.CastSpeed) != 0 ) - list.Add( 1060413, prop.ToString() ); // faster casting ~1_val~ + if ((prop = m_AosAttributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - if ( (prop = m_AosAttributes.AttackChance) != 0 ) - list.Add( 1060415, prop.ToString() ); // hit chance increase ~1_val~% + if ((prop = m_AosAttributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - if ( (prop = m_AosAttributes.BonusHits) != 0 ) - list.Add( 1060431, prop.ToString() ); // hit point increase ~1_val~ + if ((prop = m_AosAttributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - if ( (prop = m_AosAttributes.BonusInt) != 0 ) - list.Add( 1060432, prop.ToString() ); // intelligence bonus ~1_val~ + if ((prop = m_AosAttributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - if ( (prop = m_AosAttributes.LowerManaCost) != 0 ) - list.Add( 1060433, prop.ToString() ); // lower mana cost ~1_val~% + if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) + list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% - if ( (prop = m_AosAttributes.LowerRegCost) != 0 ) - list.Add( 1060434, prop.ToString() ); // lower reagent cost ~1_val~% + base.AddResistanceProperties(list); - if ( (prop = m_AosClothingAttributes.LowerStatReq) != 0 ) - list.Add( 1060435, prop.ToString() ); // lower requirements ~1_val~% + if ((prop = m_AosClothingAttributes.DurabilityBonus) > 0) + list.Add(1060410, prop.ToString()); // durability ~1_val~% - if ( (prop = m_AosAttributes.Luck) != 0 ) - list.Add( 1060436, prop.ToString() ); // luck ~1_val~ + if ((prop = ComputeStatReq(StatType.Str)) > 0) + list.Add(1061170, prop.ToString()); // strength requirement ~1_val~ - if ( (prop = m_AosClothingAttributes.MageArmor) != 0 ) - list.Add( 1060437 ); // mage armor + if (m_HitPoints >= 0 && m_MaxHitPoints > 0) + list.Add(1060639, "{0}\t{1}", m_HitPoints, m_MaxHitPoints); // durability ~1_val~ / ~2_val~ + } - if ( (prop = m_AosAttributes.BonusMana) != 0 ) - list.Add( 1060439, prop.ToString() ); // mana increase ~1_val~ + public override void OnSingleClick(Mobile from) + { + List attrs = new List(); - if ( (prop = m_AosAttributes.RegenMana) != 0 ) - list.Add( 1060440, prop.ToString() ); // mana regeneration ~1_val~ + AddEquipInfoAttributes(from, attrs); - if ( (prop = m_AosAttributes.NightSight) != 0 ) - list.Add( 1060441 ); // night sight + int number; - if ( (prop = m_AosAttributes.ReflectPhysical) != 0 ) - list.Add( 1060442, prop.ToString() ); // reflect physical damage ~1_val~% + if (Name == null) + { + number = LabelNumber; + } + else + { + LabelTo(from, Name); + number = 1041000; + } - if ( (prop = m_AosAttributes.RegenStam) != 0 ) - list.Add( 1060443, prop.ToString() ); // stamina regeneration ~1_val~ + if (attrs.Count == 0 && Crafter == null && Name != null) + return; - if ( (prop = m_AosAttributes.RegenHits) != 0 ) - list.Add( 1060444, prop.ToString() ); // hit point regeneration ~1_val~ + EquipmentInfo eqInfo = new EquipmentInfo(number, m_Crafter, false, attrs.ToArray()); - if ( (prop = m_AosClothingAttributes.SelfRepair) != 0 ) - list.Add( 1060450, prop.ToString() ); // self repair ~1_val~ + from.Send(new DisplayEquipmentInfo(this, eqInfo)); + } - if ( (prop = m_AosAttributes.SpellChanneling) != 0 ) - list.Add( 1060482 ); // spell channeling - - if ( (prop = m_AosAttributes.SpellDamage) != 0 ) - list.Add( 1060483, prop.ToString() ); // spell damage increase ~1_val~% - - if ( (prop = m_AosAttributes.BonusStam) != 0 ) - list.Add( 1060484, prop.ToString() ); // stamina increase ~1_val~ - - if ( (prop = m_AosAttributes.BonusStr) != 0 ) - list.Add( 1060485, prop.ToString() ); // strength bonus ~1_val~ - - if ( (prop = m_AosAttributes.WeaponSpeed) != 0 ) - list.Add( 1060486, prop.ToString() ); // swing speed increase ~1_val~% - - if ( Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0 ) - list.Add( 1075210, prop.ToString() ); // Increased Karma Loss ~1val~% - - base.AddResistanceProperties( list ); - - if ( (prop = m_AosClothingAttributes.DurabilityBonus) > 0 ) - list.Add( 1060410, prop.ToString() ); // durability ~1_val~% - - if ( (prop = ComputeStatReq( StatType.Str )) > 0 ) - list.Add( 1061170, prop.ToString() ); // strength requirement ~1_val~ - - if ( m_HitPoints >= 0 && m_MaxHitPoints > 0 ) - list.Add( 1060639, "{0}\t{1}", m_HitPoints, m_MaxHitPoints ); // durability ~1_val~ / ~2_val~ - } - - public override void OnSingleClick( Mobile from ) - { - List attrs = new List(); - - AddEquipInfoAttributes( from, attrs ); - - int number; - - if ( Name == null ) - { - number = LabelNumber; - } - else - { - LabelTo( from, Name ); - number = 1041000; - } - - if ( attrs.Count == 0 && Crafter == null && Name != null ) - return; - - EquipmentInfo eqInfo = new EquipmentInfo( number, m_Crafter, false, attrs.ToArray() ); - - from.Send( new DisplayEquipmentInfo( this, eqInfo ) ); - } - - public virtual void AddEquipInfoAttributes( Mobile from, List attrs ) - { - if ( DisplayLootType ) - { - if ( LootType == LootType.Blessed ) - attrs.Add( new EquipInfoAttribute( 1038021 ) ); // blessed - else if ( LootType == LootType.Cursed ) - attrs.Add( new EquipInfoAttribute( 1049643 ) ); // cursed - } - - #region Factions - if ( m_FactionState != null ) - attrs.Add( new EquipInfoAttribute( 1041350 ) ); // faction item - #endregion - - if ( m_Quality == ClothingQuality.Exceptional ) - attrs.Add( new EquipInfoAttribute( 1018305 - (int)m_Quality ) ); - } - - #region Serialization - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } - - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } - - [Flags] - private enum SaveFlag - { - None = 0x00000000, - Resource = 0x00000001, - Attributes = 0x00000002, - ClothingAttributes = 0x00000004, - SkillBonuses = 0x00000008, - Resistances = 0x00000010, - MaxHitPoints = 0x00000020, - HitPoints = 0x00000040, - PlayerConstructed = 0x00000080, - Crafter = 0x00000100, - Quality = 0x00000200, - StrReq = 0x00000400 - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 5 ); // version - - SaveFlag flags = SaveFlag.None; - - SetSaveFlag( ref flags, SaveFlag.Resource, m_Resource != DefaultResource ); - SetSaveFlag( ref flags, SaveFlag.Attributes, !m_AosAttributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.ClothingAttributes,!m_AosClothingAttributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.Resistances, !m_AosResistances.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.MaxHitPoints, m_MaxHitPoints != 0 ); - SetSaveFlag( ref flags, SaveFlag.HitPoints, m_HitPoints != 0 ); - SetSaveFlag( ref flags, SaveFlag.PlayerConstructed, PlayerConstructed != false ); - SetSaveFlag( ref flags, SaveFlag.Crafter, m_Crafter != null ); - SetSaveFlag( ref flags, SaveFlag.Quality, m_Quality != ClothingQuality.Regular ); - SetSaveFlag( ref flags, SaveFlag.StrReq, m_StrReq != -1 ); - - writer.WriteEncodedInt( (int) flags ); - - if ( GetSaveFlag( flags, SaveFlag.Resource ) ) - writer.WriteEncodedInt( (int) m_Resource ); - - if ( GetSaveFlag( flags, SaveFlag.Attributes ) ) - m_AosAttributes.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.ClothingAttributes ) ) - m_AosClothingAttributes.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.SkillBonuses ) ) - m_AosSkillBonuses.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.Resistances ) ) - m_AosResistances.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.MaxHitPoints ) ) - writer.WriteEncodedInt( (int) m_MaxHitPoints ); - - if ( GetSaveFlag( flags, SaveFlag.HitPoints ) ) - writer.WriteEncodedInt( (int) m_HitPoints ); - - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - writer.Write( (Mobile) m_Crafter ); - - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - writer.WriteEncodedInt( (int) m_Quality ); - - if ( GetSaveFlag( flags, SaveFlag.StrReq ) ) - writer.WriteEncodedInt( (int) m_StrReq ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 5: - { - SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); - - if ( GetSaveFlag( flags, SaveFlag.Resource ) ) - m_Resource = (CraftResource)reader.ReadEncodedInt(); - else - m_Resource = DefaultResource; - - if ( GetSaveFlag( flags, SaveFlag.Attributes ) ) - m_AosAttributes = new AosAttributes( this, reader ); - else - m_AosAttributes = new AosAttributes( this ); - - if ( GetSaveFlag( flags, SaveFlag.ClothingAttributes ) ) - m_AosClothingAttributes = new AosArmorAttributes( this, reader ); - else - m_AosClothingAttributes = new AosArmorAttributes( this ); - - if ( GetSaveFlag( flags, SaveFlag.SkillBonuses ) ) - m_AosSkillBonuses = new AosSkillBonuses( this, reader ); - else - m_AosSkillBonuses = new AosSkillBonuses( this ); - - if ( GetSaveFlag( flags, SaveFlag.Resistances ) ) - m_AosResistances = new AosElementAttributes( this, reader ); - else - m_AosResistances = new AosElementAttributes( this ); - - if ( GetSaveFlag( flags, SaveFlag.MaxHitPoints ) ) - m_MaxHitPoints = reader.ReadEncodedInt(); - - if ( GetSaveFlag( flags, SaveFlag.HitPoints ) ) - m_HitPoints = reader.ReadEncodedInt(); - - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - m_Crafter = reader.ReadMobile(); - - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - m_Quality = (ClothingQuality)reader.ReadEncodedInt(); - else - m_Quality = ClothingQuality.Regular; - - if ( GetSaveFlag( flags, SaveFlag.StrReq ) ) - m_StrReq = reader.ReadEncodedInt(); - else - m_StrReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.PlayerConstructed ) ) - PlayerConstructed = true; - - break; - } - case 4: - { - m_Resource = (CraftResource)reader.ReadInt(); - - goto case 3; - } - case 3: - { - m_AosAttributes = new AosAttributes( this, reader ); - m_AosClothingAttributes = new AosArmorAttributes( this, reader ); - m_AosSkillBonuses = new AosSkillBonuses( this, reader ); - m_AosResistances = new AosElementAttributes( this, reader ); - - goto case 2; - } - case 2: - { - PlayerConstructed = reader.ReadBool(); - goto case 1; - } - case 1: - { - m_Crafter = reader.ReadMobile(); - m_Quality = (ClothingQuality)reader.ReadInt(); - break; - } - case 0: - { - m_Crafter = null; - m_Quality = ClothingQuality.Regular; - break; - } - } - - if ( version < 2 ) - PlayerConstructed = true; // we don't know, so, assume it's crafted - - if ( version < 3 ) - { - m_AosAttributes = new AosAttributes( this ); - m_AosClothingAttributes = new AosArmorAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - m_AosResistances = new AosElementAttributes( this ); - } - - if ( version < 4 ) - m_Resource = DefaultResource; - - if ( m_MaxHitPoints == 0 && m_HitPoints == 0 ) - m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - - if ( Parent is Mobile parent ) - { - if ( Core.AOS ) - m_AosSkillBonuses.AddTo( parent ); - - AddStatBonuses( parent ); - parent.CheckStatTimers(); - } - } - #endregion - - public virtual bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; - if ( RootParent is Mobile && from != RootParent ) - return false; - - Hue = sender.DyedHue; - - return true; - } - - public virtual bool Scissor( Mobile from, Scissors scissors ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 502437 ); // Items you wish to cut must be in your backpack. - return false; - } - - if ( Ethics.Ethic.IsImbued( this ) ) - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } - - CraftSystem system = DefTailoring.CraftSystem; - - CraftItem item = system.CraftItems.SearchFor( GetType() ); - - if ( item != null && item.Resources.Count == 1 && item.Resources.GetAt( 0 ).Amount >= 2 ) - { - try - { - Type resourceType = null; - - CraftResourceInfo info = CraftResources.GetInfo( m_Resource ); - - if ( info != null && info.ResourceTypes.Length > 0 ) - resourceType = info.ResourceTypes[0]; - - if ( resourceType == null ) - resourceType = item.Resources.GetAt( 0 ).ItemType; - - Item res = (Item)Activator.CreateInstance( resourceType ); - - ScissorHelper( from, res, PlayerConstructed ? (item.Resources.GetAt( 0 ).Amount / 2) : 1 ); - - res.LootType = LootType.Regular; - - return true; - } - catch - { - } - } - - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } - - public void DistributeBonuses( int amount ) - { - for ( int i = 0; i < amount; ++i ) - { - switch ( Utility.Random( 5 ) ) - { - case 0: ++m_AosResistances.Physical; break; - case 1: ++m_AosResistances.Fire; break; - case 2: ++m_AosResistances.Cold; break; - case 3: ++m_AosResistances.Poison; break; - case 4: ++m_AosResistances.Energy; break; - } - } - - InvalidateProperties(); - } - - #region ICraftable Members - - public virtual int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (ClothingQuality)quality; - - if ( makersMark ) - Crafter = from; - - if ( DefaultResource != CraftResource.None ) - { - Type resourceType = typeRes; - - if ( resourceType == null ) - resourceType = craftItem.Resources.GetAt( 0 ).ItemType; - - Resource = CraftResources.GetFromType( resourceType ); - } - else - { - Hue = resHue; - } - - PlayerConstructed = true; - - CraftContext context = craftSystem.GetContext( from ); - - if ( context != null && context.DoNotColor ) - Hue = 0; - - return quality; - } - - #endregion - } -} + public virtual void AddEquipInfoAttributes(Mobile from, List attrs) + { + if (DisplayLootType) + { + if (LootType == LootType.Blessed) + attrs.Add(new EquipInfoAttribute(1038021)); // blessed + else if (LootType == LootType.Cursed) + attrs.Add(new EquipInfoAttribute(1049643)); // cursed + } + + #region Factions + + if (m_FactionState != null) + attrs.Add(new EquipInfoAttribute(1041350)); // faction item + + #endregion + + if (m_Quality == ClothingQuality.Exceptional) + attrs.Add(new EquipInfoAttribute(1018305 - (int)m_Quality)); + } + + public void DistributeBonuses(int amount) + { + for (int i = 0; i < amount; ++i) + switch (Utility.Random(5)) + { + case 0: + ++m_AosResistances.Physical; + break; + case 1: + ++m_AosResistances.Fire; + break; + case 2: + ++m_AosResistances.Cold; + break; + case 3: + ++m_AosResistances.Poison; + break; + case 4: + ++m_AosResistances.Energy; + break; + } + + InvalidateProperties(); + } + + #region Factions + + private FactionItem m_FactionState; + + public FactionItem FactionItemState + { + get => m_FactionState; + set + { + m_FactionState = value; + + if (m_FactionState == null) + Hue = 0; + + LootType = m_FactionState == null ? LootType.Regular : LootType.Blessed; + } + } + + #endregion + + #region Serialization + + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } + + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } + + [Flags] + private enum SaveFlag + { + None = 0x00000000, + Resource = 0x00000001, + Attributes = 0x00000002, + ClothingAttributes = 0x00000004, + SkillBonuses = 0x00000008, + Resistances = 0x00000010, + MaxHitPoints = 0x00000020, + HitPoints = 0x00000040, + PlayerConstructed = 0x00000080, + Crafter = 0x00000100, + Quality = 0x00000200, + StrReq = 0x00000400 + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(5); // version + + SaveFlag flags = SaveFlag.None; + + SetSaveFlag(ref flags, SaveFlag.Resource, m_Resource != DefaultResource); + SetSaveFlag(ref flags, SaveFlag.Attributes, !m_AosAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.ClothingAttributes, !m_AosClothingAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.Resistances, !m_AosResistances.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.MaxHitPoints, m_MaxHitPoints != 0); + SetSaveFlag(ref flags, SaveFlag.HitPoints, m_HitPoints != 0); + SetSaveFlag(ref flags, SaveFlag.PlayerConstructed, PlayerConstructed); + SetSaveFlag(ref flags, SaveFlag.Crafter, m_Crafter != null); + SetSaveFlag(ref flags, SaveFlag.Quality, m_Quality != ClothingQuality.Regular); + SetSaveFlag(ref flags, SaveFlag.StrReq, m_StrReq != -1); + + writer.WriteEncodedInt((int)flags); + + if (GetSaveFlag(flags, SaveFlag.Resource)) + writer.WriteEncodedInt((int)m_Resource); + + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_AosAttributes.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.ClothingAttributes)) + m_AosClothingAttributes.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.Resistances)) + m_AosResistances.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.MaxHitPoints)) + writer.WriteEncodedInt(m_MaxHitPoints); + + if (GetSaveFlag(flags, SaveFlag.HitPoints)) + writer.WriteEncodedInt(m_HitPoints); + + if (GetSaveFlag(flags, SaveFlag.Crafter)) + writer.Write(m_Crafter); + + if (GetSaveFlag(flags, SaveFlag.Quality)) + writer.WriteEncodedInt((int)m_Quality); + + if (GetSaveFlag(flags, SaveFlag.StrReq)) + writer.WriteEncodedInt(m_StrReq); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 5: + { + SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Resource)) + m_Resource = (CraftResource)reader.ReadEncodedInt(); + else + m_Resource = DefaultResource; + + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_AosAttributes = new AosAttributes(this, reader); + else + m_AosAttributes = new AosAttributes(this); + + if (GetSaveFlag(flags, SaveFlag.ClothingAttributes)) + m_AosClothingAttributes = new AosArmorAttributes(this, reader); + else + m_AosClothingAttributes = new AosArmorAttributes(this); + + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses = new AosSkillBonuses(this, reader); + else + m_AosSkillBonuses = new AosSkillBonuses(this); + + if (GetSaveFlag(flags, SaveFlag.Resistances)) + m_AosResistances = new AosElementAttributes(this, reader); + else + m_AosResistances = new AosElementAttributes(this); + + if (GetSaveFlag(flags, SaveFlag.MaxHitPoints)) + m_MaxHitPoints = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.HitPoints)) + m_HitPoints = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Crafter)) + m_Crafter = reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.Quality)) + m_Quality = (ClothingQuality)reader.ReadEncodedInt(); + else + m_Quality = ClothingQuality.Regular; + + if (GetSaveFlag(flags, SaveFlag.StrReq)) + m_StrReq = reader.ReadEncodedInt(); + else + m_StrReq = -1; + + if (GetSaveFlag(flags, SaveFlag.PlayerConstructed)) + PlayerConstructed = true; + + break; + } + case 4: + { + m_Resource = (CraftResource)reader.ReadInt(); + + goto case 3; + } + case 3: + { + m_AosAttributes = new AosAttributes(this, reader); + m_AosClothingAttributes = new AosArmorAttributes(this, reader); + m_AosSkillBonuses = new AosSkillBonuses(this, reader); + m_AosResistances = new AosElementAttributes(this, reader); + + goto case 2; + } + case 2: + { + PlayerConstructed = reader.ReadBool(); + goto case 1; + } + case 1: + { + m_Crafter = reader.ReadMobile(); + m_Quality = (ClothingQuality)reader.ReadInt(); + break; + } + case 0: + { + m_Crafter = null; + m_Quality = ClothingQuality.Regular; + break; + } + } + + if (version < 2) + PlayerConstructed = true; // we don't know, so, assume it's crafted + + if (version < 3) + { + m_AosAttributes = new AosAttributes(this); + m_AosClothingAttributes = new AosArmorAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + m_AosResistances = new AosElementAttributes(this); + } + + if (version < 4) + m_Resource = DefaultResource; + + if (m_MaxHitPoints == 0 && m_HitPoints == 0) + m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax(InitMinHits, InitMaxHits); + + if (Parent is Mobile parent) + { + if (Core.AOS) + m_AosSkillBonuses.AddTo(parent); + + AddStatBonuses(parent); + parent.CheckStatTimers(); + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Cloaks.cs b/Scripts/Items/Clothing/Cloaks.cs index 67563cfa9..6ad58251a 100644 --- a/Scripts/Items/Clothing/Cloaks.cs +++ b/Scripts/Items/Clothing/Cloaks.cs @@ -1,307 +1,323 @@ -using System; using Server.Engines.VeteranRewards; namespace Server.Items { - public abstract class BaseCloak : BaseClothing - { - public BaseCloak( int itemID ) : this( itemID, 0 ) - { - } + public abstract class BaseCloak : BaseClothing + { + public BaseCloak(int itemID) : this(itemID, 0) + { + } - public BaseCloak( int itemID, int hue ) : base( itemID, Layer.Cloak, hue ) - { - } + public BaseCloak(int itemID, int hue) : base(itemID, Layer.Cloak, hue) + { + } - public BaseCloak( Serial serial ) : base( serial ) - { - } + public BaseCloak(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable] - public class Cloak : BaseCloak, IArcaneEquip - { - #region Arcane Impl - private int m_MaxArcaneCharges, m_CurArcaneCharges; + [Flippable] + public class Cloak : BaseCloak, IArcaneEquip + { + [Constructible] + public Cloak() : this(0) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int MaxArcaneCharges - { - get => m_MaxArcaneCharges; - set{ m_MaxArcaneCharges = value; InvalidateProperties(); Update(); } - } + [Constructible] + public Cloak(int hue) : base(0x1515, hue) + { + Weight = 5.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public int CurArcaneCharges - { - get => m_CurArcaneCharges; - set{ m_CurArcaneCharges = value; InvalidateProperties(); Update(); } - } + public Cloak(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsArcane => ( m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void Update() - { - if ( IsArcane ) - ItemID = 0x26AD; - else if ( ItemID == 0x26AD ) - ItemID = 0x1515; + writer.Write(1); // version - if ( IsArcane && CurArcaneCharges == 0 ) - Hue = 0; - } + if (IsArcane) + { + writer.Write(true); + writer.Write(m_CurArcaneCharges); + writer.Write(m_MaxArcaneCharges); + } + else + { + writer.Write(false); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( IsArcane ) - list.Add( 1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges ); // arcane charges: ~1_val~ / ~2_val~ - } + int version = reader.ReadInt(); - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + switch (version) + { + case 1: + { + if (reader.ReadBool()) + { + m_CurArcaneCharges = reader.ReadInt(); + m_MaxArcaneCharges = reader.ReadInt(); - if ( IsArcane ) - LabelTo( from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); - } + if (Hue == 2118) + Hue = ArcaneGem.DefaultArcaneHue; + } - public void Flip() - { - if ( ItemID == 0x1515 ) - ItemID = 0x1530; - else if ( ItemID == 0x1530 ) - ItemID = 0x1515; - } - #endregion + break; + } + } - [Constructible] - public Cloak() : this( 0 ) - { - } + if (Weight == 4.0) + Weight = 5.0; + } - [Constructible] - public Cloak( int hue ) : base( 0x1515, hue ) - { - Weight = 5.0; - } + #region Arcane Impl - public Cloak( Serial serial ) : base( serial ) - { - } + private int m_MaxArcaneCharges, m_CurArcaneCharges; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [CommandProperty(AccessLevel.GameMaster)] + public int MaxArcaneCharges + { + get => m_MaxArcaneCharges; + set + { + m_MaxArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } - writer.Write( (int) 1 ); // version + [CommandProperty(AccessLevel.GameMaster)] + public int CurArcaneCharges + { + get => m_CurArcaneCharges; + set + { + m_CurArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } - if ( IsArcane ) - { - writer.Write( true ); - writer.Write( (int) m_CurArcaneCharges ); - writer.Write( (int) m_MaxArcaneCharges ); - } - else - { - writer.Write( false ); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsArcane => m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void Update() + { + if (IsArcane) + ItemID = 0x26AD; + else if (ItemID == 0x26AD) + ItemID = 0x1515; - int version = reader.ReadInt(); + if (IsArcane && CurArcaneCharges == 0) + Hue = 0; + } - switch ( version ) - { - case 1: - { - if ( reader.ReadBool() ) - { - m_CurArcaneCharges = reader.ReadInt(); - m_MaxArcaneCharges = reader.ReadInt(); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Hue == 2118 ) - Hue = ArcaneGem.DefaultArcaneHue; - } + if (IsArcane) + list.Add(1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges); // arcane charges: ~1_val~ / ~2_val~ + } - break; - } - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - if ( Weight == 4.0 ) - Weight = 5.0; - } - } + if (IsArcane) + LabelTo(from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); + } - [Flippable] - public class RewardCloak : BaseCloak, IRewardItem - { - private int m_LabelNumber; + public void Flip() + { + if (ItemID == 0x1515) + ItemID = 0x1530; + else if (ItemID == 0x1530) + ItemID = 0x1515; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + #endregion + } - [CommandProperty( AccessLevel.GameMaster )] - public int Number - { - get => m_LabelNumber; - set{ m_LabelNumber = value; InvalidateProperties(); } - } + [Flippable] + public class RewardCloak : BaseCloak, IRewardItem + { + private int m_LabelNumber; - public override int LabelNumber - { - get - { - if ( m_LabelNumber > 0 ) - return m_LabelNumber; + [Constructible] + public RewardCloak() : this(0) + { + } - return base.LabelNumber; - } - } + [Constructible] + public RewardCloak(int hue) : this(hue, 0) + { + } - public override int BasePhysicalResistance => 3; + [Constructible] + public RewardCloak(int hue, int labelNumber) : base(0x1515, hue) + { + Weight = 5.0; + LootType = LootType.Blessed; - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); + m_LabelNumber = labelNumber; + } - if ( parent is Mobile mobile ) - mobile.VirtualArmorMod += 2; - } + public RewardCloak(Serial serial) : base(serial) + { + } - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_LabelNumber; + set + { + m_LabelNumber = value; + InvalidateProperties(); + } + } - if ( parent is Mobile mobile ) - mobile.VirtualArmorMod -= 2; - } + public override int LabelNumber + { + get + { + if (m_LabelNumber > 0) + return m_LabelNumber; - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } + return base.LabelNumber; + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override int BasePhysicalResistance => 3; - if ( Core.ML && IsRewardItem ) - list.Add( RewardSystem.GetRewardYearLabel( this, new object[]{ Hue, m_LabelNumber } ) ); // X Year Veteran Reward - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - public override bool CanEquip( Mobile m ) - { - if ( !base.CanEquip( m ) ) - return false; + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - return !IsRewardItem || RewardSystem.CheckIsUsableBy( m, this, new object[]{ Hue, m_LabelNumber } ); - } + if (parent is Mobile mobile) + mobile.VirtualArmorMod += 2; + } - [Constructible] - public RewardCloak() : this( 0 ) - { - } + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); - [Constructible] - public RewardCloak( int hue ) : this( hue, 0 ) - { - } + if (parent is Mobile mobile) + mobile.VirtualArmorMod -= 2; + } - [Constructible] - public RewardCloak( int hue, int labelNumber ) : base( 0x1515, hue ) - { - Weight = 5.0; - LootType = LootType.Blessed; + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } - m_LabelNumber = labelNumber; - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public RewardCloak( Serial serial ) : base( serial ) - { - } + if (Core.ML && IsRewardItem) + list.Add(RewardSystem.GetRewardYearLabel(this, + new object[] { Hue, m_LabelNumber })); // X Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CanEquip(Mobile m) + { + if (!base.CanEquip(m)) + return false; - writer.Write( (int) 0 ); // version + return !IsRewardItem || RewardSystem.CheckIsUsableBy(m, this, new object[] { Hue, m_LabelNumber }); + } - writer.Write( (int) m_LabelNumber ); - writer.Write( (bool) IsRewardItem ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version - int version = reader.ReadInt(); + writer.Write(m_LabelNumber); + writer.Write(IsRewardItem); + } - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadInt(); - IsRewardItem = reader.ReadBool(); - break; - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Parent is Mobile mobile ) - mobile.VirtualArmorMod += 2; - } - } + int version = reader.ReadInt(); - [Flippable( 0x230A, 0x2309 )] - public class FurCape : BaseCloak - { - [Constructible] - public FurCape() : this( 0 ) - { - } + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadInt(); + IsRewardItem = reader.ReadBool(); + break; + } + } - [Constructible] - public FurCape( int hue ) : base( 0x230A, hue ) - { - Weight = 4.0; - } + if (Parent is Mobile mobile) + mobile.VirtualArmorMod += 2; + } + } - public FurCape( Serial serial ) : base( serial ) - { - } + [Flippable(0x230A, 0x2309)] + public class FurCape : BaseCloak + { + [Constructible] + public FurCape() : this(0) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public FurCape(int hue) : base(0x230A, hue) + { + Weight = 4.0; + } - writer.Write( (int) 0 ); // version - } + public FurCape(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Hats.cs b/Scripts/Items/Clothing/Hats.cs index ab83cd35b..d24c60a4f 100644 --- a/Scripts/Items/Clothing/Hats.cs +++ b/Scripts/Items/Clothing/Hats.cs @@ -1,1063 +1,1066 @@ using System; -using Server.Engines.Craft; -using Server.Network; using System.Collections.Generic; +using Server.Engines.Craft; +using Server.Misc; +using Server.Network; namespace Server.Items { - public abstract class BaseHat : BaseClothing, IShipwreckedItem - { - [CommandProperty( AccessLevel.GameMaster )] - public bool IsShipwreckedItem { get; set; } - - public BaseHat( int itemID ) : this( itemID, 0 ) - { - } - - public BaseHat( int itemID, int hue ) : base( itemID, Layer.Helm, hue ) - { - } - - public BaseHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( IsShipwreckedItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - IsShipwreckedItem = reader.ReadBool(); - break; - } - } - } - - public override void AddEquipInfoAttributes( Mobile from, List attrs ) - { - base.AddEquipInfoAttributes( from, attrs ); - - if ( IsShipwreckedItem ) - attrs.Add( new EquipInfoAttribute( 1041645 ) ); // recovered from a shipwreck - } - - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - - if ( IsShipwreckedItem ) - list.Add( 1041645 ); // recovered from a shipwreck - } - - public override int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (ClothingQuality)quality; - - if ( Quality == ClothingQuality.Exceptional ) - DistributeBonuses( (tool is BaseRunicTool ? 6 : (Core.SE ? 15 : 14)) ); //BLAME OSI. (We can't confirm it's an OSI bug yet.) - - return base.OnCraft( quality, makersMark, from, craftSystem, typeRes, tool, craftItem, resHue ); - } - - } - [Flippable( 0x2798, 0x27E3 )] - public class Kasa : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public Kasa() : this( 0 ) - { - } - - [Constructible] - public Kasa( int hue ) : base( 0x2798, hue ) - { - Weight = 3.0; - } - - public Kasa( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x278F, 0x27DA )] - public class ClothNinjaHood : BaseHat - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 6; - public override int BasePoisonResistance => 9; - public override int BaseEnergyResistance => 9; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public ClothNinjaHood() : this( 0 ) - { - } - - [Constructible] - public ClothNinjaHood( int hue ) : base( 0x278F, hue ) - { - Weight = 2.0; - } - - public ClothNinjaHood( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2306, 0x2305 )] - public class FlowerGarland : BaseHat - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 6; - public override int BasePoisonResistance => 9; - public override int BaseEnergyResistance => 9; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public FlowerGarland() : this( 0 ) - { - } - - [Constructible] - public FlowerGarland( int hue ) : base( 0x2306, hue ) - { - Weight = 1.0; - } - - public FlowerGarland( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FloppyHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public FloppyHat() : this( 0 ) - { - } - - [Constructible] - public FloppyHat( int hue ) : base( 0x1713, hue ) - { - Weight = 1.0; - } - - public FloppyHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WideBrimHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public WideBrimHat() : this( 0 ) - { - } - - [Constructible] - public WideBrimHat( int hue ) : base( 0x1714, hue ) - { - Weight = 1.0; - } - - public WideBrimHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Cap : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public Cap() : this( 0 ) - { - } - - [Constructible] - public Cap( int hue ) : base( 0x1715, hue ) - { - Weight = 1.0; - } - - public Cap( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SkullCap : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 8; - public override int BaseEnergyResistance => 8; - - public override int InitMinHits => ( Core.ML ? 14 : 7 ); - public override int InitMaxHits => ( Core.ML ? 28 : 12 ); - - [Constructible] - public SkullCap() : this( 0 ) - { - } - - [Constructible] - public SkullCap( int hue ) : base( 0x1544, hue ) - { - Weight = 1.0; - } - - public SkullCap( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Bandana : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 8; - public override int BaseEnergyResistance => 8; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public Bandana() : this( 0 ) - { - } - - [Constructible] - public Bandana( int hue ) : base( 0x1540, hue ) - { - Weight = 1.0; - } - - public Bandana( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BearMask : BaseHat - { - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 8; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 4; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public BearMask() : this( 0 ) - { - } - - [Constructible] - public BearMask( int hue ) : base( 0x1545, hue ) - { - Weight = 5.0; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public BearMask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DeerMask : BaseHat - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 8; - public override int BasePoisonResistance => 1; - public override int BaseEnergyResistance => 7; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public DeerMask() : this( 0 ) - { - } - - [Constructible] - public DeerMask( int hue ) : base( 0x1547, hue ) - { - Weight = 4.0; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public DeerMask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class HornedTribalMask : BaseHat - { - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 9; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public HornedTribalMask() : this( 0 ) - { - } - - [Constructible] - public HornedTribalMask( int hue ) : base( 0x1549, hue ) - { - Weight = 2.0; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public HornedTribalMask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TribalMask : BaseHat - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 6; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public TribalMask() : this( 0 ) - { - } - - [Constructible] - public TribalMask( int hue ) : base( 0x154B, hue ) - { - Weight = 2.0; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public TribalMask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TallStrawHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public TallStrawHat() : this( 0 ) - { - } - - [Constructible] - public TallStrawHat( int hue ) : base( 0x1716, hue ) - { - Weight = 1.0; - } - - public TallStrawHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class StrawHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public StrawHat() : this( 0 ) - { - } - - [Constructible] - public StrawHat( int hue ) : base( 0x1717, hue ) - { - Weight = 1.0; - } - - public StrawHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class OrcishKinMask : BaseHat - { - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 7; - public override int BaseEnergyResistance => 8; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public override string DefaultName => "a mask of orcish kin"; - - [Constructible] - public OrcishKinMask() : this( 0x8A4 ) - { - } - - [Constructible] - public OrcishKinMask( int hue ) : base( 0x141B, hue ) - { - Weight = 2.0; - } - - public override bool CanEquip( Mobile m ) - { - if ( !base.CanEquip( m ) ) - return false; - - if ( m.BodyMod == 183 || m.BodyMod == 184 ) - { - m.SendLocalizedMessage( 1061629 ); // You can't do that while wearing savage kin paint. - return false; - } - - return true; - } - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - if ( parent is Mobile mobile ) - Misc.Titles.AwardKarma( mobile, -20, true ); - } - - public OrcishKinMask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - /*if ( Hue != 0x8A4 ) - Hue = 0x8A4;*/ - } - } - - public class SavageMask : BaseHat - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 6; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - public static int GetRandomHue() - { - int v = Utility.RandomBirdHue(); - - if ( v == 2101 ) - v = 0; - - return v; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - [Constructible] - public SavageMask() : this( GetRandomHue() ) - { - } - - [Constructible] - public SavageMask( int hue ) : base( 0x154B, hue ) - { - Weight = 2.0; - } - - public SavageMask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - /*if ( Hue != 0 && (Hue < 2101 || Hue > 2130) ) - Hue = GetRandomHue();*/ - } - } - - public class WizardsHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public WizardsHat() : this( 0 ) - { - } - - [Constructible] - public WizardsHat( int hue ) : base( 0x1718, hue ) - { - Weight = 1.0; - } - - public WizardsHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MagicWizardsHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - public override int LabelNumber => 1041072; // a magical wizard's hat - - public override int BaseStrBonus => -5; - public override int BaseDexBonus => -5; - public override int BaseIntBonus => +5; - - [Constructible] - public MagicWizardsHat() : this( 0 ) - { - } - - [Constructible] - public MagicWizardsHat( int hue ) : base( 0x1718, hue ) - { - Weight = 1.0; - } - - public MagicWizardsHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Bonnet : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public Bonnet() : this( 0 ) - { - } - - [Constructible] - public Bonnet( int hue ) : base( 0x1719, hue ) - { - Weight = 1.0; - } - - public Bonnet( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FeatheredHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public FeatheredHat() : this( 0 ) - { - } - - [Constructible] - public FeatheredHat( int hue ) : base( 0x171A, hue ) - { - Weight = 1.0; - } - - public FeatheredHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TricorneHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public TricorneHat() : this( 0 ) - { - } - - [Constructible] - public TricorneHat( int hue ) : base( 0x171B, hue ) - { - Weight = 1.0; - } - - public TricorneHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class JesterHat : BaseHat - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; - - public override int InitMinHits => 20; - public override int InitMaxHits => 30; - - [Constructible] - public JesterHat() : this( 0 ) - { - } - - [Constructible] - public JesterHat( int hue ) : base( 0x171C, hue ) - { - Weight = 1.0; - } - - public JesterHat( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public abstract class BaseHat : BaseClothing, IShipwreckedItem + { + public BaseHat(int itemID) : this(itemID, 0) + { + } + + public BaseHat(int itemID, int hue) : base(itemID, Layer.Helm, hue) + { + } + + public BaseHat(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsShipwreckedItem{ get; set; } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(IsShipwreckedItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + IsShipwreckedItem = reader.ReadBool(); + break; + } + } + } + + public override void AddEquipInfoAttributes(Mobile from, List attrs) + { + base.AddEquipInfoAttributes(from, attrs); + + if (IsShipwreckedItem) + attrs.Add(new EquipInfoAttribute(1041645)); // recovered from a shipwreck + } + + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + + if (IsShipwreckedItem) + list.Add(1041645); // recovered from a shipwreck + } + + public override int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, + BaseTool tool, CraftItem craftItem, int resHue) + { + Quality = (ClothingQuality)quality; + + if (Quality == ClothingQuality.Exceptional) + DistributeBonuses(tool is BaseRunicTool ? 6 : + Core.SE ? 15 : 14); //BLAME OSI. (We can't confirm it's an OSI bug yet.) + + return base.OnCraft(quality, makersMark, from, craftSystem, typeRes, tool, craftItem, resHue); + } + } + + [Flippable(0x2798, 0x27E3)] + public class Kasa : BaseHat + { + [Constructible] + public Kasa() : this(0) + { + } + + [Constructible] + public Kasa(int hue) : base(0x2798, hue) + { + Weight = 3.0; + } + + public Kasa(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x278F, 0x27DA)] + public class ClothNinjaHood : BaseHat + { + [Constructible] + public ClothNinjaHood() : this(0) + { + } + + [Constructible] + public ClothNinjaHood(int hue) : base(0x278F, hue) + { + Weight = 2.0; + } + + public ClothNinjaHood(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 6; + public override int BasePoisonResistance => 9; + public override int BaseEnergyResistance => 9; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2306, 0x2305)] + public class FlowerGarland : BaseHat + { + [Constructible] + public FlowerGarland() : this(0) + { + } + + [Constructible] + public FlowerGarland(int hue) : base(0x2306, hue) + { + Weight = 1.0; + } + + public FlowerGarland(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 6; + public override int BasePoisonResistance => 9; + public override int BaseEnergyResistance => 9; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FloppyHat : BaseHat + { + [Constructible] + public FloppyHat() : this(0) + { + } + + [Constructible] + public FloppyHat(int hue) : base(0x1713, hue) + { + Weight = 1.0; + } + + public FloppyHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WideBrimHat : BaseHat + { + [Constructible] + public WideBrimHat() : this(0) + { + } + + [Constructible] + public WideBrimHat(int hue) : base(0x1714, hue) + { + Weight = 1.0; + } + + public WideBrimHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Cap : BaseHat + { + [Constructible] + public Cap() : this(0) + { + } + + [Constructible] + public Cap(int hue) : base(0x1715, hue) + { + Weight = 1.0; + } + + public Cap(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SkullCap : BaseHat + { + [Constructible] + public SkullCap() : this(0) + { + } + + [Constructible] + public SkullCap(int hue) : base(0x1544, hue) + { + Weight = 1.0; + } + + public SkullCap(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 8; + public override int BaseEnergyResistance => 8; + + public override int InitMinHits => Core.ML ? 14 : 7; + public override int InitMaxHits => Core.ML ? 28 : 12; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Bandana : BaseHat + { + [Constructible] + public Bandana() : this(0) + { + } + + [Constructible] + public Bandana(int hue) : base(0x1540, hue) + { + Weight = 1.0; + } + + public Bandana(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 8; + public override int BaseEnergyResistance => 8; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BearMask : BaseHat + { + [Constructible] + public BearMask() : this(0) + { + } + + [Constructible] + public BearMask(int hue) : base(0x1545, hue) + { + Weight = 5.0; + } + + public BearMask(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 8; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 4; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DeerMask : BaseHat + { + [Constructible] + public DeerMask() : this(0) + { + } + + [Constructible] + public DeerMask(int hue) : base(0x1547, hue) + { + Weight = 4.0; + } + + public DeerMask(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 8; + public override int BasePoisonResistance => 1; + public override int BaseEnergyResistance => 7; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class HornedTribalMask : BaseHat + { + [Constructible] + public HornedTribalMask() : this(0) + { + } + + [Constructible] + public HornedTribalMask(int hue) : base(0x1549, hue) + { + Weight = 2.0; + } + + public HornedTribalMask(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 9; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TribalMask : BaseHat + { + [Constructible] + public TribalMask() : this(0) + { + } + + [Constructible] + public TribalMask(int hue) : base(0x154B, hue) + { + Weight = 2.0; + } + + public TribalMask(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 6; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TallStrawHat : BaseHat + { + [Constructible] + public TallStrawHat() : this(0) + { + } + + [Constructible] + public TallStrawHat(int hue) : base(0x1716, hue) + { + Weight = 1.0; + } + + public TallStrawHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StrawHat : BaseHat + { + [Constructible] + public StrawHat() : this(0) + { + } + + [Constructible] + public StrawHat(int hue) : base(0x1717, hue) + { + Weight = 1.0; + } + + public StrawHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class OrcishKinMask : BaseHat + { + [Constructible] + public OrcishKinMask() : this(0x8A4) + { + } + + [Constructible] + public OrcishKinMask(int hue) : base(0x141B, hue) + { + Weight = 2.0; + } + + public OrcishKinMask(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 7; + public override int BaseEnergyResistance => 8; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override string DefaultName => "a mask of orcish kin"; + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override bool CanEquip(Mobile m) + { + if (!base.CanEquip(m)) + return false; + + if (m.BodyMod == 183 || m.BodyMod == 184) + { + m.SendLocalizedMessage(1061629); // You can't do that while wearing savage kin paint. + return false; + } + + return true; + } + + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); + + if (parent is Mobile mobile) + Titles.AwardKarma(mobile, -20, true); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + /*if ( Hue != 0x8A4 ) + Hue = 0x8A4;*/ + } + } + + public class SavageMask : BaseHat + { + [Constructible] + public SavageMask() : this(GetRandomHue()) + { + } + + [Constructible] + public SavageMask(int hue) : base(0x154B, hue) + { + Weight = 2.0; + } + + public SavageMask(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 6; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public static int GetRandomHue() + { + int v = Utility.RandomBirdHue(); + + if (v == 2101) + v = 0; + + return v; + } + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + /*if ( Hue != 0 && (Hue < 2101 || Hue > 2130) ) + Hue = GetRandomHue();*/ + } + } + + public class WizardsHat : BaseHat + { + [Constructible] + public WizardsHat() : this(0) + { + } + + [Constructible] + public WizardsHat(int hue) : base(0x1718, hue) + { + Weight = 1.0; + } + + public WizardsHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MagicWizardsHat : BaseHat + { + [Constructible] + public MagicWizardsHat() : this(0) + { + } + + [Constructible] + public MagicWizardsHat(int hue) : base(0x1718, hue) + { + Weight = 1.0; + } + + public MagicWizardsHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override int LabelNumber => 1041072; // a magical wizard's hat + + public override int BaseStrBonus => -5; + public override int BaseDexBonus => -5; + public override int BaseIntBonus => +5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Bonnet : BaseHat + { + [Constructible] + public Bonnet() : this(0) + { + } + + [Constructible] + public Bonnet(int hue) : base(0x1719, hue) + { + Weight = 1.0; + } + + public Bonnet(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FeatheredHat : BaseHat + { + [Constructible] + public FeatheredHat() : this(0) + { + } + + [Constructible] + public FeatheredHat(int hue) : base(0x171A, hue) + { + Weight = 1.0; + } + + public FeatheredHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TricorneHat : BaseHat + { + [Constructible] + public TricorneHat() : this(0) + { + } + + [Constructible] + public TricorneHat(int hue) : base(0x171B, hue) + { + Weight = 1.0; + } + + public TricorneHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class JesterHat : BaseHat + { + [Constructible] + public JesterHat() : this(0) + { + } + + [Constructible] + public JesterHat(int hue) : base(0x171C, hue) + { + Weight = 1.0; + } + + public JesterHat(Serial serial) : base(serial) + { + } + + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; + + public override int InitMinHits => 20; + public override int InitMaxHits => 30; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/MiddleTorso.cs b/Scripts/Items/Clothing/MiddleTorso.cs index 531673f3a..f1ca6698f 100644 --- a/Scripts/Items/Clothing/MiddleTorso.cs +++ b/Scripts/Items/Clothing/MiddleTorso.cs @@ -1,301 +1,301 @@ namespace Server.Items { - public abstract class BaseMiddleTorso : BaseClothing - { - public BaseMiddleTorso( int itemID ) : this( itemID, 0 ) - { - } + public abstract class BaseMiddleTorso : BaseClothing + { + public BaseMiddleTorso(int itemID) : this(itemID, 0) + { + } - public BaseMiddleTorso( int itemID, int hue ) : base( itemID, Layer.MiddleTorso, hue ) - { - } + public BaseMiddleTorso(int itemID, int hue) : base(itemID, Layer.MiddleTorso, hue) + { + } - public BaseMiddleTorso( Serial serial ) : base( serial ) - { - } + public BaseMiddleTorso(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x1541, 0x1542 )] - public class BodySash : BaseMiddleTorso - { - [Constructible] - public BodySash() : this( 0 ) - { - } + [Flippable(0x1541, 0x1542)] + public class BodySash : BaseMiddleTorso + { + [Constructible] + public BodySash() : this(0) + { + } - [Constructible] - public BodySash( int hue ) : base( 0x1541, hue ) - { - Weight = 1.0; - } + [Constructible] + public BodySash(int hue) : base(0x1541, hue) + { + Weight = 1.0; + } - public BodySash( Serial serial ) : base( serial ) - { - } + public BodySash(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x153d, 0x153e )] - public class FullApron : BaseMiddleTorso - { - [Constructible] - public FullApron() : this( 0 ) - { - } + [Flippable(0x153d, 0x153e)] + public class FullApron : BaseMiddleTorso + { + [Constructible] + public FullApron() : this(0) + { + } - [Constructible] - public FullApron( int hue ) : base( 0x153d, hue ) - { - Weight = 4.0; - } + [Constructible] + public FullApron(int hue) : base(0x153d, hue) + { + Weight = 4.0; + } - public FullApron( Serial serial ) : base( serial ) - { - } + public FullApron(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x1f7b, 0x1f7c )] - public class Doublet : BaseMiddleTorso - { - [Constructible] - public Doublet() : this( 0 ) - { - } + [Flippable(0x1f7b, 0x1f7c)] + public class Doublet : BaseMiddleTorso + { + [Constructible] + public Doublet() : this(0) + { + } - [Constructible] - public Doublet( int hue ) : base( 0x1F7B, hue ) - { - Weight = 2.0; - } + [Constructible] + public Doublet(int hue) : base(0x1F7B, hue) + { + Weight = 2.0; + } - public Doublet( Serial serial ) : base( serial ) - { - } + public Doublet(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x1ffd, 0x1ffe )] - public class Surcoat : BaseMiddleTorso - { - [Constructible] - public Surcoat() : this( 0 ) - { - } + [Flippable(0x1ffd, 0x1ffe)] + public class Surcoat : BaseMiddleTorso + { + [Constructible] + public Surcoat() : this(0) + { + } - [Constructible] - public Surcoat( int hue ) : base( 0x1FFD, hue ) - { - Weight = 6.0; - } + [Constructible] + public Surcoat(int hue) : base(0x1FFD, hue) + { + Weight = 6.0; + } - public Surcoat( Serial serial ) : base( serial ) - { - } + public Surcoat(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 6.0; - } - } + if (Weight == 3.0) + Weight = 6.0; + } + } - [Flippable( 0x1fa1, 0x1fa2 )] - public class Tunic : BaseMiddleTorso - { - [Constructible] - public Tunic() : this( 0 ) - { - } + [Flippable(0x1fa1, 0x1fa2)] + public class Tunic : BaseMiddleTorso + { + [Constructible] + public Tunic() : this(0) + { + } - [Constructible] - public Tunic( int hue ) : base( 0x1FA1, hue ) - { - Weight = 5.0; - } + [Constructible] + public Tunic(int hue) : base(0x1FA1, hue) + { + Weight = 5.0; + } - public Tunic( Serial serial ) : base( serial ) - { - } + public Tunic(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x2310, 0x230F )] - public class FormalShirt : BaseMiddleTorso - { - [Constructible] - public FormalShirt() : this( 0 ) - { - } + [Flippable(0x2310, 0x230F)] + public class FormalShirt : BaseMiddleTorso + { + [Constructible] + public FormalShirt() : this(0) + { + } - [Constructible] - public FormalShirt( int hue ) : base( 0x2310, hue ) - { - Weight = 1.0; - } + [Constructible] + public FormalShirt(int hue) : base(0x2310, hue) + { + Weight = 1.0; + } - public FormalShirt( Serial serial ) : base( serial ) - { - } + public FormalShirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - if ( Weight == 2.0 ) - Weight = 1.0; - } + if (Weight == 2.0) + Weight = 1.0; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x1f9f, 0x1fa0 )] - public class JesterSuit : BaseMiddleTorso - { - [Constructible] - public JesterSuit() : this( 0 ) - { - } + [Flippable(0x1f9f, 0x1fa0)] + public class JesterSuit : BaseMiddleTorso + { + [Constructible] + public JesterSuit() : this(0) + { + } - [Constructible] - public JesterSuit( int hue ) : base( 0x1F9F, hue ) - { - Weight = 4.0; - } + [Constructible] + public JesterSuit(int hue) : base(0x1F9F, hue) + { + Weight = 4.0; + } - public JesterSuit( Serial serial ) : base( serial ) - { - } + public JesterSuit(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x27A1, 0x27EC )] - public class JinBaori : BaseMiddleTorso - { - [Constructible] - public JinBaori() : this( 0 ) - { - } + [Flippable(0x27A1, 0x27EC)] + public class JinBaori : BaseMiddleTorso + { + [Constructible] + public JinBaori() : this(0) + { + } - [Constructible] - public JinBaori( int hue ) : base( 0x27A1, hue ) - { - Weight = 3.0; - } + [Constructible] + public JinBaori(int hue) : base(0x27A1, hue) + { + Weight = 3.0; + } - public JinBaori( Serial serial ) : base( serial ) - { - } + public JinBaori(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Clothing/OuterLegs.cs b/Scripts/Items/Clothing/OuterLegs.cs index ec07ea93a..e36437de0 100644 --- a/Scripts/Items/Clothing/OuterLegs.cs +++ b/Scripts/Items/Clothing/OuterLegs.cs @@ -1,166 +1,166 @@ namespace Server.Items { - public abstract class BaseOuterLegs : BaseClothing - { - public BaseOuterLegs( int itemID ) : this( itemID, 0 ) - { - } + public abstract class BaseOuterLegs : BaseClothing + { + public BaseOuterLegs(int itemID) : this(itemID, 0) + { + } - public BaseOuterLegs( int itemID, int hue ) : base( itemID, Layer.OuterLegs, hue ) - { - } + public BaseOuterLegs(int itemID, int hue) : base(itemID, Layer.OuterLegs, hue) + { + } - public BaseOuterLegs( Serial serial ) : base( serial ) - { - } + public BaseOuterLegs(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x230C, 0x230B )] - public class FurSarong : BaseOuterLegs - { - [Constructible] - public FurSarong() : this( 0 ) - { - } + [Flippable(0x230C, 0x230B)] + public class FurSarong : BaseOuterLegs + { + [Constructible] + public FurSarong() : this(0) + { + } - [Constructible] - public FurSarong( int hue ) : base( 0x230C, hue ) - { - Weight = 3.0; - } + [Constructible] + public FurSarong(int hue) : base(0x230C, hue) + { + Weight = 3.0; + } - public FurSarong( Serial serial ) : base( serial ) - { - } + public FurSarong(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 4.0 ) - Weight = 3.0; - } - } + if (Weight == 4.0) + Weight = 3.0; + } + } - [Flippable( 0x1516, 0x1531 )] - public class Skirt : BaseOuterLegs - { - [Constructible] - public Skirt() : this( 0 ) - { - } + [Flippable(0x1516, 0x1531)] + public class Skirt : BaseOuterLegs + { + [Constructible] + public Skirt() : this(0) + { + } - [Constructible] - public Skirt( int hue ) : base( 0x1516, hue ) - { - Weight = 4.0; - } + [Constructible] + public Skirt(int hue) : base(0x1516, hue) + { + Weight = 4.0; + } - public Skirt( Serial serial ) : base( serial ) - { - } + public Skirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x1537, 0x1538 )] - public class Kilt : BaseOuterLegs - { - [Constructible] - public Kilt() : this( 0 ) - { - } + [Flippable(0x1537, 0x1538)] + public class Kilt : BaseOuterLegs + { + [Constructible] + public Kilt() : this(0) + { + } - [Constructible] - public Kilt( int hue ) : base( 0x1537, hue ) - { - Weight = 2.0; - } + [Constructible] + public Kilt(int hue) : base(0x1537, hue) + { + Weight = 2.0; + } - public Kilt( Serial serial ) : base( serial ) - { - } + public Kilt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x279A, 0x27E5 )] - public class Hakama : BaseOuterLegs - { - [Constructible] - public Hakama() : this( 0 ) - { - } + [Flippable(0x279A, 0x27E5)] + public class Hakama : BaseOuterLegs + { + [Constructible] + public Hakama() : this(0) + { + } - [Constructible] - public Hakama( int hue ) : base( 0x279A, hue ) - { - Weight = 2.0; - } + [Constructible] + public Hakama(int hue) : base(0x279A, hue) + { + Weight = 2.0; + } - public Hakama( Serial serial ) : base( serial ) - { - } + public Hakama(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Clothing/OuterTorso.cs b/Scripts/Items/Clothing/OuterTorso.cs index 1b7a61eb3..2db3c5797 100644 --- a/Scripts/Items/Clothing/OuterTorso.cs +++ b/Scripts/Items/Clothing/OuterTorso.cs @@ -3,865 +3,892 @@ using Server.Engines.VeteranRewards; namespace Server.Items { - public abstract class BaseOuterTorso : BaseClothing - { - public BaseOuterTorso( int itemID ) : this( itemID, 0 ) - { - } - - public BaseOuterTorso( int itemID, int hue ) : base( itemID, Layer.OuterTorso, hue ) - { - } - - public BaseOuterTorso( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x230E, 0x230D )] - public class GildedDress : BaseOuterTorso - { - [Constructible] - public GildedDress() : this( 0 ) - { - } - - [Constructible] - public GildedDress( int hue ) : base( 0x230E, hue ) - { - Weight = 3.0; - } - - public GildedDress( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x1F00, 0x1EFF )] - public class FancyDress : BaseOuterTorso - { - [Constructible] - public FancyDress() : this( 0 ) - { - } - - [Constructible] - public FancyDress( int hue ) : base( 0x1F00, hue ) - { - Weight = 3.0; - } - - public FancyDress( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DeathRobe : Robe - { - private Timer m_DecayTimer; - private DateTime m_DecayTime; - - private static TimeSpan m_DefaultDecayTime = TimeSpan.FromMinutes(1.0); - - public override bool DisplayLootType => false; - - [Constructible] - public DeathRobe() - { - LootType = LootType.Newbied; - Hue = 2301; - BeginDecay( m_DefaultDecayTime ); - } - - public new bool Scissor( Mobile from, Scissors scissors ) - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } - - public void BeginDecay() - { - BeginDecay( m_DefaultDecayTime ); - } - - private void BeginDecay( TimeSpan delay ) - { - m_DecayTimer?.Stop(); - - m_DecayTime = DateTime.UtcNow + delay; - - m_DecayTimer = new InternalTimer( this, delay ); - m_DecayTimer.Start(); - } - - public override bool OnDroppedToWorld( Mobile from, Point3D p ) - { - BeginDecay( m_DefaultDecayTime ); - - return true; - } - - public override bool OnDroppedToMobile( Mobile from, Mobile target ) - { - if (m_DecayTimer != null ) - { - m_DecayTimer.Stop(); - m_DecayTimer = null; - } - - return true; - } - - public override void OnAfterDelete() - { - m_DecayTimer?.Stop(); - - m_DecayTimer = null; - } - - private class InternalTimer : Timer - { - private DeathRobe m_Robe; - - public InternalTimer( DeathRobe c, TimeSpan delay ) : base( delay ) - { - m_Robe = c; - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - if ( m_Robe.Parent != null || m_Robe.IsLockedDown ) - Stop(); - else - m_Robe.Delete(); - } - } - - public DeathRobe( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - - writer.Write( m_DecayTimer != null ); - - if ( m_DecayTimer != null ) - writer.WriteDeltaTime( m_DecayTime ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - { - if ( reader.ReadBool() ) - { - m_DecayTime = reader.ReadDeltaTime(); - BeginDecay( m_DecayTime - DateTime.UtcNow ); - } - break; - } - case 1: - case 0: - { - if ( Parent == null ) - BeginDecay( m_DefaultDecayTime ); - break; - } - } - - if ( version < 1 && Hue == 0 ) - Hue = 2301; - } - } - - [Flippable] - public class RewardRobe : BaseOuterTorso, IRewardItem - { - private int m_LabelNumber; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Number - { - get => m_LabelNumber; - set{ m_LabelNumber = value; InvalidateProperties(); } - } - - public override int LabelNumber - { - get - { - if ( m_LabelNumber > 0 ) - return m_LabelNumber; - - return base.LabelNumber; - } - } - - public override int BasePhysicalResistance => 3; - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - if ( parent is Mobile mobile ) - mobile.VirtualArmorMod += 2; - } - - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); - - if ( parent is Mobile mobile ) - mobile.VirtualArmorMod -= 2; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Core.ML && IsRewardItem ) - list.Add( RewardSystem.GetRewardYearLabel( this, new object[]{ Hue, m_LabelNumber } ) ); // X Year Veteran Reward - } - - public override bool CanEquip( Mobile m ) - { - if ( !base.CanEquip( m ) ) - return false; - - return !IsRewardItem || RewardSystem.CheckIsUsableBy( m, this, new object[]{ Hue, m_LabelNumber } ); - } - - [Constructible] - public RewardRobe() : this( 0 ) - { - } - - [Constructible] - public RewardRobe( int hue ) : this( hue, 0 ) - { - } - - [Constructible] - public RewardRobe( int hue, int labelNumber ) : base( 0x1F03, hue ) - { - Weight = 3.0; - LootType = LootType.Blessed; - - m_LabelNumber = labelNumber; - } - - public RewardRobe( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( (int) m_LabelNumber ); - writer.Write( (bool) IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadInt(); - IsRewardItem = reader.ReadBool(); - break; - } - } - - if ( Parent is Mobile mobile ) - mobile.VirtualArmorMod += 2; - } - } - - [Flippable] - public class RewardDress : BaseOuterTorso, IRewardItem - { - private int m_LabelNumber; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Number - { - get => m_LabelNumber; - set{ m_LabelNumber = value; InvalidateProperties(); } - } - - public override int LabelNumber - { - get - { - if ( m_LabelNumber > 0 ) - return m_LabelNumber; - - return base.LabelNumber; - } - } - - public override int BasePhysicalResistance => 3; - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - if ( parent is Mobile mobile ) - mobile.VirtualArmorMod += 2; - } - - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); - - if ( parent is Mobile mobile ) - mobile.VirtualArmorMod -= 2; - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( IsRewardItem ) - list.Add( RewardSystem.GetRewardYearLabel( this, new object[]{ Hue, m_LabelNumber } ) ); // X Year Veteran Reward - } - - public override bool CanEquip( Mobile m ) - { - if ( !base.CanEquip( m ) ) - return false; - - return !IsRewardItem || RewardSystem.CheckIsUsableBy( m, this, new object[]{ Hue, m_LabelNumber } ); - } - - [Constructible] - public RewardDress() : this( 0 ) - { - } - - [Constructible] - public RewardDress( int hue ) : this( hue, 0 ) - { - } - - [Constructible] - public RewardDress( int hue, int labelNumber ) : base( 0x1F01, hue ) - { - Weight = 2.0; - LootType = LootType.Blessed; - - m_LabelNumber = labelNumber; - } - - public RewardDress( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( (int) m_LabelNumber ); - writer.Write( (bool) IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadInt(); - IsRewardItem = reader.ReadBool(); - break; - } - } - - if ( Parent is Mobile mobile ) - mobile.VirtualArmorMod += 2; - } - } - - [Flippable] - public class Robe : BaseOuterTorso, IArcaneEquip - { - #region Arcane Impl - private int m_MaxArcaneCharges, m_CurArcaneCharges; - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxArcaneCharges - { - get => m_MaxArcaneCharges; - set{ m_MaxArcaneCharges = value; InvalidateProperties(); Update(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int CurArcaneCharges - { - get => m_CurArcaneCharges; - set{ m_CurArcaneCharges = value; InvalidateProperties(); Update(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsArcane => ( m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0 ); - - public void Update() - { - if ( IsArcane ) - ItemID = 0x26AE; - else if ( ItemID == 0x26AE ) - ItemID = 0x1F04; - - if ( IsArcane && CurArcaneCharges == 0 ) - Hue = 0; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( IsArcane ) - list.Add( 1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges ); // arcane charges: ~1_val~ / ~2_val~ - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( IsArcane ) - LabelTo( from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); - } - - public void Flip() - { - if ( ItemID == 0x1F03 ) - ItemID = 0x1F04; - else if ( ItemID == 0x1F04 ) - ItemID = 0x1F03; - } - #endregion - - [Constructible] - public Robe() : this( 0 ) - { - } - - [Constructible] - public Robe( int hue ) : base( 0x1F03, hue ) - { - Weight = 3.0; - } - - public Robe( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - if ( IsArcane ) - { - writer.Write( true ); - writer.Write( (int) m_CurArcaneCharges ); - writer.Write( (int) m_MaxArcaneCharges ); - } - else - { - writer.Write( false ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - if ( reader.ReadBool() ) - { - m_CurArcaneCharges = reader.ReadInt(); - m_MaxArcaneCharges = reader.ReadInt(); - - if ( Hue == 2118 ) - Hue = ArcaneGem.DefaultArcaneHue; - } - - break; - } - } - } - } - - public class MonkRobe : BaseOuterTorso - { - [Constructible] - public MonkRobe() : this( 0x21E ) - { - } - - [Constructible] - public MonkRobe( int hue ) : base( 0x2687, hue ) - { - Weight = 1.0; - StrRequirement = 0; - } - public override int LabelNumber => 1076584; // A monk's robe - public override bool CanBeBlessed => false; - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } - public MonkRobe( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x1f01, 0x1f02 )] - public class PlainDress : BaseOuterTorso - { - [Constructible] - public PlainDress() : this( 0 ) - { - } - - [Constructible] - public PlainDress( int hue ) : base( 0x1F01, hue ) - { - Weight = 2.0; - } - - public PlainDress( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 3.0 ) - Weight = 2.0; - } - } - - [Flippable( 0x2799, 0x27E4 )] - public class Kamishimo : BaseOuterTorso - { - [Constructible] - public Kamishimo() : this( 0 ) - { - } - - [Constructible] - public Kamishimo( int hue ) : base( 0x2799, hue ) - { - Weight = 3.0; - } - - public Kamishimo( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x279C, 0x27E7 )] - public class HakamaShita : BaseOuterTorso - { - [Constructible] - public HakamaShita() : this( 0 ) - { - } - - [Constructible] - public HakamaShita( int hue ) : base( 0x279C, hue ) - { - Weight = 3.0; - } - - public HakamaShita( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2782, 0x27CD )] - public class MaleKimono : BaseOuterTorso - { - [Constructible] - public MaleKimono() : this( 0 ) - { - } - - [Constructible] - public MaleKimono( int hue ) : base( 0x2782, hue ) - { - Weight = 3.0; - } - - public override bool AllowFemaleWearer => false; - - public MaleKimono( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2783, 0x27CE )] - public class FemaleKimono : BaseOuterTorso - { - [Constructible] - public FemaleKimono() : this( 0 ) - { - } - - [Constructible] - public FemaleKimono( int hue ) : base( 0x2783, hue ) - { - Weight = 3.0; - } - - public override bool AllowMaleWearer => false; - - public FemaleKimono( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2FB9, 0x3173 )] - public class MaleElvenRobe : BaseOuterTorso - { - public override Race RequiredRace => Race.Elf; - - [Constructible] - public MaleElvenRobe() : this( 0 ) - { - } - - [Constructible] - public MaleElvenRobe( int hue ) : base( 0x2FB9, hue ) - { - Weight = 2.0; - } - - public MaleElvenRobe( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - [Flippable( 0x2FBA, 0x3174 )] - public class FemaleElvenRobe : BaseOuterTorso - { - public override Race RequiredRace => Race.Elf; - [Constructible] - public FemaleElvenRobe() : this( 0 ) - { - } - - [Constructible] - public FemaleElvenRobe( int hue ) : base( 0x2FBA, hue ) - { - Weight = 2.0; - } - - public override bool AllowMaleWearer => false; - - public FemaleElvenRobe( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + public abstract class BaseOuterTorso : BaseClothing + { + public BaseOuterTorso(int itemID) : this(itemID, 0) + { + } + + public BaseOuterTorso(int itemID, int hue) : base(itemID, Layer.OuterTorso, hue) + { + } + + public BaseOuterTorso(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x230E, 0x230D)] + public class GildedDress : BaseOuterTorso + { + [Constructible] + public GildedDress() : this(0) + { + } + + [Constructible] + public GildedDress(int hue) : base(0x230E, hue) + { + Weight = 3.0; + } + + public GildedDress(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1F00, 0x1EFF)] + public class FancyDress : BaseOuterTorso + { + [Constructible] + public FancyDress() : this(0) + { + } + + [Constructible] + public FancyDress(int hue) : base(0x1F00, hue) + { + Weight = 3.0; + } + + public FancyDress(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DeathRobe : Robe + { + private static TimeSpan m_DefaultDecayTime = TimeSpan.FromMinutes(1.0); + private DateTime m_DecayTime; + private Timer m_DecayTimer; + + [Constructible] + public DeathRobe() + { + LootType = LootType.Newbied; + Hue = 2301; + BeginDecay(m_DefaultDecayTime); + } + + public DeathRobe(Serial serial) : base(serial) + { + } + + public override bool DisplayLootType => false; + + public new bool Scissor(Mobile from, Scissors scissors) + { + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } + + public void BeginDecay() + { + BeginDecay(m_DefaultDecayTime); + } + + private void BeginDecay(TimeSpan delay) + { + m_DecayTimer?.Stop(); + + m_DecayTime = DateTime.UtcNow + delay; + + m_DecayTimer = new InternalTimer(this, delay); + m_DecayTimer.Start(); + } + + public override bool OnDroppedToWorld(Mobile from, Point3D p) + { + BeginDecay(m_DefaultDecayTime); + + return true; + } + + public override bool OnDroppedToMobile(Mobile from, Mobile target) + { + if (m_DecayTimer != null) + { + m_DecayTimer.Stop(); + m_DecayTimer = null; + } + + return true; + } + + public override void OnAfterDelete() + { + m_DecayTimer?.Stop(); + + m_DecayTimer = null; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + + writer.Write(m_DecayTimer != null); + + if (m_DecayTimer != null) + writer.WriteDeltaTime(m_DecayTime); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: + { + if (reader.ReadBool()) + { + m_DecayTime = reader.ReadDeltaTime(); + BeginDecay(m_DecayTime - DateTime.UtcNow); + } + + break; + } + case 1: + case 0: + { + if (Parent == null) + BeginDecay(m_DefaultDecayTime); + break; + } + } + + if (version < 1 && Hue == 0) + Hue = 2301; + } + + private class InternalTimer : Timer + { + private DeathRobe m_Robe; + + public InternalTimer(DeathRobe c, TimeSpan delay) : base(delay) + { + m_Robe = c; + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + if (m_Robe.Parent != null || m_Robe.IsLockedDown) + Stop(); + else + m_Robe.Delete(); + } + } + } + + [Flippable] + public class RewardRobe : BaseOuterTorso, IRewardItem + { + private int m_LabelNumber; + + [Constructible] + public RewardRobe() : this(0) + { + } + + [Constructible] + public RewardRobe(int hue) : this(hue, 0) + { + } + + [Constructible] + public RewardRobe(int hue, int labelNumber) : base(0x1F03, hue) + { + Weight = 3.0; + LootType = LootType.Blessed; + + m_LabelNumber = labelNumber; + } + + public RewardRobe(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_LabelNumber; + set + { + m_LabelNumber = value; + InvalidateProperties(); + } + } + + public override int LabelNumber + { + get + { + if (m_LabelNumber > 0) + return m_LabelNumber; + + return base.LabelNumber; + } + } + + public override int BasePhysicalResistance => 3; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } + + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); + + if (parent is Mobile mobile) + mobile.VirtualArmorMod += 2; + } + + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); + + if (parent is Mobile mobile) + mobile.VirtualArmorMod -= 2; + } + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Core.ML && IsRewardItem) + list.Add(RewardSystem.GetRewardYearLabel(this, + new object[] { Hue, m_LabelNumber })); // X Year Veteran Reward + } + + public override bool CanEquip(Mobile m) + { + if (!base.CanEquip(m)) + return false; + + return !IsRewardItem || RewardSystem.CheckIsUsableBy(m, this, new object[] { Hue, m_LabelNumber }); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_LabelNumber); + writer.Write(IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadInt(); + IsRewardItem = reader.ReadBool(); + break; + } + } + + if (Parent is Mobile mobile) + mobile.VirtualArmorMod += 2; + } + } + + [Flippable] + public class RewardDress : BaseOuterTorso, IRewardItem + { + private int m_LabelNumber; + + [Constructible] + public RewardDress() : this(0) + { + } + + [Constructible] + public RewardDress(int hue) : this(hue, 0) + { + } + + [Constructible] + public RewardDress(int hue, int labelNumber) : base(0x1F01, hue) + { + Weight = 2.0; + LootType = LootType.Blessed; + + m_LabelNumber = labelNumber; + } + + public RewardDress(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_LabelNumber; + set + { + m_LabelNumber = value; + InvalidateProperties(); + } + } + + public override int LabelNumber + { + get + { + if (m_LabelNumber > 0) + return m_LabelNumber; + + return base.LabelNumber; + } + } + + public override int BasePhysicalResistance => 3; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } + + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); + + if (parent is Mobile mobile) + mobile.VirtualArmorMod += 2; + } + + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); + + if (parent is Mobile mobile) + mobile.VirtualArmorMod -= 2; + } + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (IsRewardItem) + list.Add(RewardSystem.GetRewardYearLabel(this, + new object[] { Hue, m_LabelNumber })); // X Year Veteran Reward + } + + public override bool CanEquip(Mobile m) + { + if (!base.CanEquip(m)) + return false; + + return !IsRewardItem || RewardSystem.CheckIsUsableBy(m, this, new object[] { Hue, m_LabelNumber }); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_LabelNumber); + writer.Write(IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadInt(); + IsRewardItem = reader.ReadBool(); + break; + } + } + + if (Parent is Mobile mobile) + mobile.VirtualArmorMod += 2; + } + } + + [Flippable] + public class Robe : BaseOuterTorso, IArcaneEquip + { + [Constructible] + public Robe() : this(0) + { + } + + [Constructible] + public Robe(int hue) : base(0x1F03, hue) + { + Weight = 3.0; + } + + public Robe(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + if (IsArcane) + { + writer.Write(true); + writer.Write(m_CurArcaneCharges); + writer.Write(m_MaxArcaneCharges); + } + else + { + writer.Write(false); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + if (reader.ReadBool()) + { + m_CurArcaneCharges = reader.ReadInt(); + m_MaxArcaneCharges = reader.ReadInt(); + + if (Hue == 2118) + Hue = ArcaneGem.DefaultArcaneHue; + } + + break; + } + } + } + + #region Arcane Impl + + private int m_MaxArcaneCharges, m_CurArcaneCharges; + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxArcaneCharges + { + get => m_MaxArcaneCharges; + set + { + m_MaxArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int CurArcaneCharges + { + get => m_CurArcaneCharges; + set + { + m_CurArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsArcane => m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0; + + public void Update() + { + if (IsArcane) + ItemID = 0x26AE; + else if (ItemID == 0x26AE) + ItemID = 0x1F04; + + if (IsArcane && CurArcaneCharges == 0) + Hue = 0; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (IsArcane) + list.Add(1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges); // arcane charges: ~1_val~ / ~2_val~ + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (IsArcane) + LabelTo(from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); + } + + public void Flip() + { + if (ItemID == 0x1F03) + ItemID = 0x1F04; + else if (ItemID == 0x1F04) + ItemID = 0x1F03; + } + + #endregion + } + + public class MonkRobe : BaseOuterTorso + { + [Constructible] + public MonkRobe() : this(0x21E) + { + } + + [Constructible] + public MonkRobe(int hue) : base(0x2687, hue) + { + Weight = 1.0; + StrRequirement = 0; + } + + public MonkRobe(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1076584; // A monk's robe + public override bool CanBeBlessed => false; + + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1f01, 0x1f02)] + public class PlainDress : BaseOuterTorso + { + [Constructible] + public PlainDress() : this(0) + { + } + + [Constructible] + public PlainDress(int hue) : base(0x1F01, hue) + { + Weight = 2.0; + } + + public PlainDress(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 3.0) + Weight = 2.0; + } + } + + [Flippable(0x2799, 0x27E4)] + public class Kamishimo : BaseOuterTorso + { + [Constructible] + public Kamishimo() : this(0) + { + } + + [Constructible] + public Kamishimo(int hue) : base(0x2799, hue) + { + Weight = 3.0; + } + + public Kamishimo(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x279C, 0x27E7)] + public class HakamaShita : BaseOuterTorso + { + [Constructible] + public HakamaShita() : this(0) + { + } + + [Constructible] + public HakamaShita(int hue) : base(0x279C, hue) + { + Weight = 3.0; + } + + public HakamaShita(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2782, 0x27CD)] + public class MaleKimono : BaseOuterTorso + { + [Constructible] + public MaleKimono() : this(0) + { + } + + [Constructible] + public MaleKimono(int hue) : base(0x2782, hue) + { + Weight = 3.0; + } + + public MaleKimono(Serial serial) : base(serial) + { + } + + public override bool AllowFemaleWearer => false; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2783, 0x27CE)] + public class FemaleKimono : BaseOuterTorso + { + [Constructible] + public FemaleKimono() : this(0) + { + } + + [Constructible] + public FemaleKimono(int hue) : base(0x2783, hue) + { + Weight = 3.0; + } + + public FemaleKimono(Serial serial) : base(serial) + { + } + + public override bool AllowMaleWearer => false; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2FB9, 0x3173)] + public class MaleElvenRobe : BaseOuterTorso + { + [Constructible] + public MaleElvenRobe() : this(0) + { + } + + [Constructible] + public MaleElvenRobe(int hue) : base(0x2FB9, hue) + { + Weight = 2.0; + } + + public MaleElvenRobe(Serial serial) : base(serial) + { + } + + public override Race RequiredRace => Race.Elf; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + [Flippable(0x2FBA, 0x3174)] + public class FemaleElvenRobe : BaseOuterTorso + { + [Constructible] + public FemaleElvenRobe() : this(0) + { + } + + [Constructible] + public FemaleElvenRobe(int hue) : base(0x2FBA, hue) + { + Weight = 2.0; + } + + public FemaleElvenRobe(Serial serial) : base(serial) + { + } + + public override Race RequiredRace => Race.Elf; + + public override bool AllowMaleWearer => false; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Pants.cs b/Scripts/Items/Clothing/Pants.cs index 7aa8c469d..001e0ef46 100644 --- a/Scripts/Items/Clothing/Pants.cs +++ b/Scripts/Items/Clothing/Pants.cs @@ -1,165 +1,165 @@ namespace Server.Items { - public abstract class BasePants : BaseClothing - { - public BasePants( int itemID ) : this( itemID, 0 ) - { - } + public abstract class BasePants : BaseClothing + { + public BasePants(int itemID) : this(itemID, 0) + { + } - public BasePants( int itemID, int hue ) : base( itemID, Layer.Pants, hue ) - { - } + public BasePants(int itemID, int hue) : base(itemID, Layer.Pants, hue) + { + } - public BasePants( Serial serial ) : base( serial ) - { - } + public BasePants(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x152e, 0x152f )] - public class ShortPants : BasePants - { - [Constructible] - public ShortPants() : this( 0 ) - { - } + [Flippable(0x152e, 0x152f)] + public class ShortPants : BasePants + { + [Constructible] + public ShortPants() : this(0) + { + } - [Constructible] - public ShortPants( int hue ) : base( 0x152E, hue ) - { - Weight = 2.0; - } + [Constructible] + public ShortPants(int hue) : base(0x152E, hue) + { + Weight = 2.0; + } - public ShortPants( Serial serial ) : base( serial ) - { - } + public ShortPants(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x1539, 0x153a )] - public class LongPants : BasePants - { - [Constructible] - public LongPants() : this( 0 ) - { - } + [Flippable(0x1539, 0x153a)] + public class LongPants : BasePants + { + [Constructible] + public LongPants() : this(0) + { + } - [Constructible] - public LongPants( int hue ) : base( 0x1539, hue ) - { - Weight = 2.0; - } + [Constructible] + public LongPants(int hue) : base(0x1539, hue) + { + Weight = 2.0; + } - public LongPants( Serial serial ) : base( serial ) - { - } + public LongPants(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x279B, 0x27E6 )] - public class TattsukeHakama : BasePants - { - [Constructible] - public TattsukeHakama() : this( 0 ) - { - } + [Flippable(0x279B, 0x27E6)] + public class TattsukeHakama : BasePants + { + [Constructible] + public TattsukeHakama() : this(0) + { + } - [Constructible] - public TattsukeHakama( int hue ) : base( 0x279B, hue ) - { - Weight = 2.0; - } + [Constructible] + public TattsukeHakama(int hue) : base(0x279B, hue) + { + Weight = 2.0; + } - public TattsukeHakama( Serial serial ) : base( serial ) - { - } + public TattsukeHakama(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x2FC3, 0x3179 )] - public class ElvenPants : BasePants - { - public override Race RequiredRace => Race.Elf; + [Flippable(0x2FC3, 0x3179)] + public class ElvenPants : BasePants + { + [Constructible] + public ElvenPants() : this(0) + { + } - [Constructible] - public ElvenPants() : this( 0 ) - { - } + [Constructible] + public ElvenPants(int hue) : base(0x2FC3, hue) + { + Weight = 2.0; + } - [Constructible] - public ElvenPants( int hue ) : base( 0x2FC3, hue ) - { - Weight = 2.0; - } + public ElvenPants(Serial serial) : base(serial) + { + } - public ElvenPants( Serial serial ) : base( serial ) - { - } + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Shirts.cs b/Scripts/Items/Clothing/Shirts.cs index 87a90fb02..5e85cf4d5 100644 --- a/Scripts/Items/Clothing/Shirts.cs +++ b/Scripts/Items/Clothing/Shirts.cs @@ -1,202 +1,203 @@ namespace Server.Items { - public abstract class BaseShirt : BaseClothing - { - public BaseShirt( int itemID ) : this( itemID, 0 ) - { - } + public abstract class BaseShirt : BaseClothing + { + public BaseShirt(int itemID) : this(itemID, 0) + { + } - public BaseShirt( int itemID, int hue ) : base( itemID, Layer.Shirt, hue ) - { - } + public BaseShirt(int itemID, int hue) : base(itemID, Layer.Shirt, hue) + { + } - public BaseShirt( Serial serial ) : base( serial ) - { - } + public BaseShirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x1efd, 0x1efe )] - public class FancyShirt : BaseShirt - { - [Constructible] - public FancyShirt() : this( 0 ) - { - } + [Flippable(0x1efd, 0x1efe)] + public class FancyShirt : BaseShirt + { + [Constructible] + public FancyShirt() : this(0) + { + } - [Constructible] - public FancyShirt( int hue ) : base( 0x1EFD, hue ) - { - Weight = 2.0; - } + [Constructible] + public FancyShirt(int hue) : base(0x1EFD, hue) + { + Weight = 2.0; + } - public FancyShirt( Serial serial ) : base( serial ) - { - } + public FancyShirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x1517, 0x1518 )] - public class Shirt : BaseShirt - { - [Constructible] - public Shirt() : this( 0 ) - { - } + [Flippable(0x1517, 0x1518)] + public class Shirt : BaseShirt + { + [Constructible] + public Shirt() : this(0) + { + } - [Constructible] - public Shirt( int hue ) : base( 0x1517, hue ) - { - Weight = 1.0; - } + [Constructible] + public Shirt(int hue) : base(0x1517, hue) + { + Weight = 1.0; + } - public Shirt( Serial serial ) : base( serial ) - { - } + public Shirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } + if (Weight == 2.0) + Weight = 1.0; + } + } - [Flippable( 0x2794, 0x27DF )] - public class ClothNinjaJacket : BaseShirt - { - [Constructible] - public ClothNinjaJacket() : this( 0 ) - { - } + [Flippable(0x2794, 0x27DF)] + public class ClothNinjaJacket : BaseShirt + { + [Constructible] + public ClothNinjaJacket() : this(0) + { + } - [Constructible] - public ClothNinjaJacket( int hue ) : base( 0x2794, hue ) - { - Weight = 5.0; - Layer = Layer.InnerTorso; - } + [Constructible] + public ClothNinjaJacket(int hue) : base(0x2794, hue) + { + Weight = 5.0; + Layer = Layer.InnerTorso; + } - public ClothNinjaJacket( Serial serial ) : base( serial ) - { - } + public ClothNinjaJacket(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class ElvenShirt : BaseShirt - { - public override Race RequiredRace => Race.Elf; + public class ElvenShirt : BaseShirt + { + [Constructible] + public ElvenShirt() : this(0) + { + } - [Constructible] - public ElvenShirt() : this( 0 ) - { - } + [Constructible] + public ElvenShirt(int hue) : base(0x3175, hue) + { + Weight = 2.0; + } - [Constructible] - public ElvenShirt( int hue ) : base( 0x3175, hue ) - { - Weight = 2.0; - } + public ElvenShirt(Serial serial) + : base(serial) + { + } - public ElvenShirt(Serial serial) - : base( serial ) - { - } + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ElvenDarkShirt : BaseShirt - { - public override Race RequiredRace => Race.Elf; - [Constructible] - public ElvenDarkShirt() : this( 0 ) - { - } + public class ElvenDarkShirt : BaseShirt + { + [Constructible] + public ElvenDarkShirt() : this(0) + { + } - [Constructible] - public ElvenDarkShirt( int hue ) : base( 0x3176, hue ) - { - Weight = 2.0; - } + [Constructible] + public ElvenDarkShirt(int hue) : base(0x3176, hue) + { + Weight = 2.0; + } - public ElvenDarkShirt( Serial serial ) : base( serial ) - { - } + public ElvenDarkShirt(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override Race RequiredRace => Race.Elf; - writer.WriteEncodedInt( 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Shoes.cs b/Scripts/Items/Clothing/Shoes.cs index 910b4ad62..9f0fa954e 100644 --- a/Scripts/Items/Clothing/Shoes.cs +++ b/Scripts/Items/Clothing/Shoes.cs @@ -1,460 +1,470 @@ -using System; - namespace Server.Items { - public abstract class BaseShoes : BaseClothing - { - public BaseShoes( int itemID ) : this( itemID, 0 ) - { - } - - public BaseShoes( int itemID, int hue ) : base( itemID, Layer.Shoes, hue ) - { - } - - public BaseShoes( Serial serial ) : base( serial ) - { - } - - public override bool Scissor( Mobile from, Scissors scissors ) - { - if ( DefaultResource == CraftResource.None ) - return base.Scissor( from, scissors ); - - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: break; // empty, resource removed - case 1: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - case 0: - { - m_Resource = DefaultResource; - break; - } - } - } - } - - [Flippable( 0x2307, 0x2308 )] - public class FurBoots : BaseShoes - { - [Constructible] - public FurBoots() : this( 0 ) - { - } - - [Constructible] - public FurBoots( int hue ) : base( 0x2307, hue ) - { - Weight = 3.0; - } - - public FurBoots( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x170b, 0x170c )] - public class Boots : BaseShoes - { - public override CraftResource DefaultResource => CraftResource.RegularLeather; - - [Constructible] - public Boots() : this( 0 ) - { - } - - [Constructible] - public Boots( int hue ) : base( 0x170B, hue ) - { - Weight = 3.0; - } - - public Boots( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable] - public class ThighBoots : BaseShoes, IArcaneEquip - { - #region Arcane Impl - private int m_MaxArcaneCharges, m_CurArcaneCharges; - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxArcaneCharges - { - get => m_MaxArcaneCharges; - set{ m_MaxArcaneCharges = value; InvalidateProperties(); Update(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int CurArcaneCharges - { - get => m_CurArcaneCharges; - set{ m_CurArcaneCharges = value; InvalidateProperties(); Update(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsArcane => ( m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0 ); - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( IsArcane ) - LabelTo( from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); - } - - public void Update() - { - if ( IsArcane ) - ItemID = 0x26AF; - else if ( ItemID == 0x26AF ) - ItemID = 0x1711; - - if ( IsArcane && CurArcaneCharges == 0 ) - Hue = 0; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( IsArcane ) - list.Add( 1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges ); // arcane charges: ~1_val~ / ~2_val~ - } - - public void Flip() - { - if ( ItemID == 0x1711 ) - ItemID = 0x1712; - else if ( ItemID == 0x1712 ) - ItemID = 0x1711; - } - #endregion - - public override CraftResource DefaultResource => CraftResource.RegularLeather; - - [Constructible] - public ThighBoots() : this( 0 ) - { - } - - [Constructible] - public ThighBoots( int hue ) : base( 0x1711, hue ) - { - Weight = 4.0; - } - - public ThighBoots( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - if ( IsArcane ) - { - writer.Write( true ); - writer.Write( (int) m_CurArcaneCharges ); - writer.Write( (int) m_MaxArcaneCharges ); - } - else - { - writer.Write( false ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - if ( reader.ReadBool() ) - { - m_CurArcaneCharges = reader.ReadInt(); - m_MaxArcaneCharges = reader.ReadInt(); - - if ( Hue == 2118 ) - Hue = ArcaneGem.DefaultArcaneHue; - } - - break; - } - } - } - } - - [FlippableAttribute( 0x170f, 0x1710 )] - public class Shoes : BaseShoes - { - public override CraftResource DefaultResource => CraftResource.RegularLeather; - - [Constructible] - public Shoes() : this( 0 ) - { - } - - [Constructible] - public Shoes( int hue ) : base( 0x170F, hue ) - { - Weight = 2.0; - } - - public Shoes( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x170d, 0x170e )] - public class Sandals : BaseShoes - { - public override CraftResource DefaultResource => CraftResource.RegularLeather; - - [Constructible] - public Sandals() : this( 0 ) - { - } - - [Constructible] - public Sandals( int hue ) : base( 0x170D, hue ) - { - Weight = 1.0; - } - - public Sandals( Serial serial ) : base( serial ) - { - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - return false; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2797, 0x27E2 )] - public class NinjaTabi : BaseShoes - { - [Constructible] - public NinjaTabi() : this( 0 ) - { - } - - [Constructible] - public NinjaTabi( int hue ) : base( 0x2797, hue ) - { - Weight = 2.0; - } - - public NinjaTabi( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2796, 0x27E1 )] - public class SamuraiTabi : BaseShoes - { - [Constructible] - public SamuraiTabi() : this( 0 ) - { - } - - [Constructible] - public SamuraiTabi( int hue ) : base( 0x2796, hue ) - { - Weight = 2.0; - } - - public SamuraiTabi( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x2796, 0x27E1 )] - public class Waraji : BaseShoes - { - [Constructible] - public Waraji() : this( 0 ) - { - } - - [Constructible] - public Waraji( int hue ) : base( 0x2796, hue ) - { - Weight = 2.0; - } - - public Waraji( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x2FC4, 0x317A )] - public class ElvenBoots : BaseShoes - { - public override CraftResource DefaultResource => CraftResource.RegularLeather; - - public override Race RequiredRace => Race.Elf; - - [Constructible] - public ElvenBoots() : this( 0 ) - { - } - - [Constructible] - public ElvenBoots( int hue ) : base( 0x2FC4, hue ) - { - Weight = 2.0; - } - - public ElvenBoots( Serial serial ) : base( serial ) - { - } - - public override bool Dye( Mobile from, DyeTub sender ) - { - return false; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + public abstract class BaseShoes : BaseClothing + { + public BaseShoes(int itemID) : this(itemID, 0) + { + } + + public BaseShoes(int itemID, int hue) : base(itemID, Layer.Shoes, hue) + { + } + + public BaseShoes(Serial serial) : base(serial) + { + } + + public override bool Scissor(Mobile from, Scissors scissors) + { + if (DefaultResource == CraftResource.None) + return base.Scissor(from, scissors); + + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: break; // empty, resource removed + case 1: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + case 0: + { + m_Resource = DefaultResource; + break; + } + } + } + } + + [Flippable(0x2307, 0x2308)] + public class FurBoots : BaseShoes + { + [Constructible] + public FurBoots() : this(0) + { + } + + [Constructible] + public FurBoots(int hue) : base(0x2307, hue) + { + Weight = 3.0; + } + + public FurBoots(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x170b, 0x170c)] + public class Boots : BaseShoes + { + [Constructible] + public Boots() : this(0) + { + } + + [Constructible] + public Boots(int hue) : base(0x170B, hue) + { + Weight = 3.0; + } + + public Boots(Serial serial) : base(serial) + { + } + + public override CraftResource DefaultResource => CraftResource.RegularLeather; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable] + public class ThighBoots : BaseShoes, IArcaneEquip + { + [Constructible] + public ThighBoots() : this(0) + { + } + + [Constructible] + public ThighBoots(int hue) : base(0x1711, hue) + { + Weight = 4.0; + } + + public ThighBoots(Serial serial) : base(serial) + { + } + + public override CraftResource DefaultResource => CraftResource.RegularLeather; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + if (IsArcane) + { + writer.Write(true); + writer.Write(m_CurArcaneCharges); + writer.Write(m_MaxArcaneCharges); + } + else + { + writer.Write(false); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + if (reader.ReadBool()) + { + m_CurArcaneCharges = reader.ReadInt(); + m_MaxArcaneCharges = reader.ReadInt(); + + if (Hue == 2118) + Hue = ArcaneGem.DefaultArcaneHue; + } + + break; + } + } + } + + #region Arcane Impl + + private int m_MaxArcaneCharges, m_CurArcaneCharges; + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxArcaneCharges + { + get => m_MaxArcaneCharges; + set + { + m_MaxArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int CurArcaneCharges + { + get => m_CurArcaneCharges; + set + { + m_CurArcaneCharges = value; + InvalidateProperties(); + Update(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsArcane => m_MaxArcaneCharges > 0 && m_CurArcaneCharges >= 0; + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (IsArcane) + LabelTo(from, 1061837, $"{m_CurArcaneCharges}\t{m_MaxArcaneCharges}"); + } + + public void Update() + { + if (IsArcane) + ItemID = 0x26AF; + else if (ItemID == 0x26AF) + ItemID = 0x1711; + + if (IsArcane && CurArcaneCharges == 0) + Hue = 0; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (IsArcane) + list.Add(1061837, "{0}\t{1}", m_CurArcaneCharges, m_MaxArcaneCharges); // arcane charges: ~1_val~ / ~2_val~ + } + + public void Flip() + { + if (ItemID == 0x1711) + ItemID = 0x1712; + else if (ItemID == 0x1712) + ItemID = 0x1711; + } + + #endregion + } + + [Flippable(0x170f, 0x1710)] + public class Shoes : BaseShoes + { + [Constructible] + public Shoes() : this(0) + { + } + + [Constructible] + public Shoes(int hue) : base(0x170F, hue) + { + Weight = 2.0; + } + + public Shoes(Serial serial) : base(serial) + { + } + + public override CraftResource DefaultResource => CraftResource.RegularLeather; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x170d, 0x170e)] + public class Sandals : BaseShoes + { + [Constructible] + public Sandals() : this(0) + { + } + + [Constructible] + public Sandals(int hue) : base(0x170D, hue) + { + Weight = 1.0; + } + + public Sandals(Serial serial) : base(serial) + { + } + + public override CraftResource DefaultResource => CraftResource.RegularLeather; + + public override bool Dye(Mobile from, DyeTub sender) + { + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2797, 0x27E2)] + public class NinjaTabi : BaseShoes + { + [Constructible] + public NinjaTabi() : this(0) + { + } + + [Constructible] + public NinjaTabi(int hue) : base(0x2797, hue) + { + Weight = 2.0; + } + + public NinjaTabi(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2796, 0x27E1)] + public class SamuraiTabi : BaseShoes + { + [Constructible] + public SamuraiTabi() : this(0) + { + } + + [Constructible] + public SamuraiTabi(int hue) : base(0x2796, hue) + { + Weight = 2.0; + } + + public SamuraiTabi(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2796, 0x27E1)] + public class Waraji : BaseShoes + { + [Constructible] + public Waraji() : this(0) + { + } + + [Constructible] + public Waraji(int hue) : base(0x2796, hue) + { + Weight = 2.0; + } + + public Waraji(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x2FC4, 0x317A)] + public class ElvenBoots : BaseShoes + { + [Constructible] + public ElvenBoots() : this(0) + { + } + + [Constructible] + public ElvenBoots(int hue) : base(0x2FC4, hue) + { + Weight = 2.0; + } + + public ElvenBoots(Serial serial) : base(serial) + { + } + + public override CraftResource DefaultResource => CraftResource.RegularLeather; + + public override Race RequiredRace => Race.Elf; + + public override bool Dye(Mobile from, DyeTub sender) + { + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Clothing/Waist.cs b/Scripts/Items/Clothing/Waist.cs index 6fec67c83..d611bfc5a 100644 --- a/Scripts/Items/Clothing/Waist.cs +++ b/Scripts/Items/Clothing/Waist.cs @@ -1,145 +1,144 @@ namespace Server.Items { + public abstract class BaseWaist : BaseClothing + { + public BaseWaist(int itemID) : this(itemID, 0) + { + } - public abstract class BaseWaist : BaseClothing - { - public BaseWaist( int itemID ) : this( itemID, 0 ) - { - } + public BaseWaist(int itemID, int hue) : base(itemID, Layer.Waist, hue) + { + } - public BaseWaist( int itemID, int hue ) : base( itemID, Layer.Waist, hue ) - { - } + public BaseWaist(Serial serial) : base(serial) + { + } - public BaseWaist( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + [Flippable(0x153b, 0x153c)] + public class HalfApron : BaseWaist + { + [Constructible] + public HalfApron() : this(0) + { + } - [FlippableAttribute( 0x153b, 0x153c )] - public class HalfApron : BaseWaist - { - [Constructible] - public HalfApron() : this( 0 ) - { - } + [Constructible] + public HalfApron(int hue) : base(0x153b, hue) + { + Weight = 2.0; + } - [Constructible] - public HalfApron( int hue ) : base( 0x153b, hue ) - { - Weight = 2.0; - } + public HalfApron(Serial serial) : base(serial) + { + } - public HalfApron( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + [Flippable(0x27A0, 0x27EB)] + public class Obi : BaseWaist + { + [Constructible] + public Obi() : this(0) + { + } - [Flippable( 0x27A0, 0x27EB )] - public class Obi : BaseWaist - { - [Constructible] - public Obi() : this( 0 ) - { - } + [Constructible] + public Obi(int hue) : base(0x27A0, hue) + { + Weight = 1.0; + } - [Constructible] - public Obi( int hue ) : base( 0x27A0, hue ) - { - Weight = 1.0; - } + public Obi(Serial serial) : base(serial) + { + } - public Obi( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + [Flippable(0x2B68, 0x315F)] + public class WoodlandBelt : BaseWaist + { + [Constructible] + public WoodlandBelt() : this(0) + { + } - [FlippableAttribute( 0x2B68, 0x315F )] - public class WoodlandBelt : BaseWaist - { - public override Race RequiredRace => Race.Elf; + [Constructible] + public WoodlandBelt(int hue) : base(0x2B68, hue) + { + Weight = 4.0; + } - [Constructible] - public WoodlandBelt() : this( 0 ) - { - } + public WoodlandBelt(Serial serial) : base(serial) + { + } - [Constructible] - public WoodlandBelt( int hue ) : base( 0x2B68, hue ) - { - Weight = 4.0; - } + public override Race RequiredRace => Race.Elf; - public WoodlandBelt( Serial serial ) : base( serial ) - { - } + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } + public override bool Scissor(Mobile from, Scissors scissors) + { + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } - public override bool Scissor( Mobile from, Scissors scissors ) - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); // version + } - writer.WriteEncodedInt( 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Ankhs.cs b/Scripts/Items/Construction/Ankhs.cs index c36a2d89e..11593d4bc 100644 --- a/Scripts/Items/Construction/Ankhs.cs +++ b/Scripts/Items/Construction/Ankhs.cs @@ -1,430 +1,455 @@ using System.Collections.Generic; +using Server.ContextMenus; using Server.Gumps; using Server.Mobiles; -using Server.ContextMenus; namespace Server.Items { - public class Ankhs - { - public const int ResurrectRange = 2; - public const int TitheRange = 2; - public const int LockRange = 2; - - public static void GetContextMenuEntries( Mobile from, Item item, List list ) - { - if ( from is PlayerMobile mobile ) - list.Add( new LockKarmaEntry( mobile ) ); - - list.Add( new ResurrectEntry( from, item ) ); - - if ( Core.AOS ) - list.Add( new TitheEntry( from ) ); - } - - public static void Resurrect( Mobile m, Item item ) - { - if ( m.Alive ) - return; - - if ( !m.InRange( item.GetWorldLocation(), ResurrectRange ) ) - m.SendLocalizedMessage( 500446 ); // That is too far away. - else if ( m.Map != null && m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.VirtueShrine ) ); - } - else - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - - private class ResurrectEntry : ContextMenuEntry - { - private Mobile m_Mobile; - private Item m_Item; - - public ResurrectEntry( Mobile mobile, Item item ) : base( 6195, ResurrectRange ) - { - m_Mobile = mobile; - m_Item = item; - - Enabled = !m_Mobile.Alive; - } - - public override void OnClick() - { - Resurrect( m_Mobile, m_Item ); - } - } - - private class LockKarmaEntry : ContextMenuEntry - { - private PlayerMobile m_Mobile; - - public LockKarmaEntry( PlayerMobile mobile ) : base( mobile.KarmaLocked ? 6197 : 6196, LockRange ) - { - m_Mobile = mobile; - } - - public override void OnClick() - { - m_Mobile.KarmaLocked = !m_Mobile.KarmaLocked; - - if ( m_Mobile.KarmaLocked ) - m_Mobile.SendLocalizedMessage( 1060192 ); // Your karma has been locked. Your karma can no longer be raised. - else - m_Mobile.SendLocalizedMessage( 1060191 ); // Your karma has been unlocked. Your karma can be raised again. - } - } - - private class TitheEntry : ContextMenuEntry - { - private Mobile m_Mobile; - - public TitheEntry( Mobile mobile ) : base( 6198, TitheRange ) - { - m_Mobile = mobile; - - Enabled = m_Mobile.Alive; - } - - public override void OnClick() - { - if ( m_Mobile.CheckAlive() ) - m_Mobile.SendGump( new TithingGump( m_Mobile, 0 ) ); - } - } - } - - public class AnkhWest : Item - { - private InternalItem m_Item; - - [Constructible] - public AnkhWest() : this( false ) - { - } - - [Constructible] - public AnkhWest( bool bloodied ) : base( bloodied ? 0x1D98 : 0x3 ) - { - Movable = false; - - m_Item = new InternalItem( bloodied, this ); - } - - public AnkhWest( Serial serial ) : base( serial ) - { - } - - public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Parent == null && Utility.InRange( Location, m.Location, 1 ) && !Utility.InRange( Location, oldLocation, 1 ) ) - Ankhs.Resurrect( m, this ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - Ankhs.GetContextMenuEntries( from, this, list ); - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set{ base.Hue = value; if ( m_Item.Hue != value ) m_Item.Hue = value; } - } - - public override void OnDoubleClickDead( Mobile m ) - { - Ankhs.Resurrect( m, this ); - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X, Y + 1, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as InternalItem; - } - - private class InternalItem : Item - { - private AnkhWest m_Item; - - public InternalItem( bool bloodied, AnkhWest item ) : base( bloodied ? 0x1D97 : 0x2 ) - { - Movable = false; - - m_Item = item; - } - - public InternalItem( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X, Y - 1, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Parent == null && Utility.InRange( Location, m.Location, 1 ) && !Utility.InRange( Location, oldLocation, 1 ) ) - Ankhs.Resurrect( m, this ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - Ankhs.GetContextMenuEntries( from, this, list ); - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set{ base.Hue = value; if ( m_Item.Hue != value ) m_Item.Hue = value; } - } - - public override void OnDoubleClickDead( Mobile m ) - { - Ankhs.Resurrect( m, this ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as AnkhWest; - } - } - } - - [TypeAlias( "Server.Items.AnkhEast" )] - public class AnkhNorth : Item - { - private InternalItem m_Item; - - [Constructible] - public AnkhNorth() : this( false ) - { - } - - [Constructible] - public AnkhNorth( bool bloodied ) : base( bloodied ? 0x1E5D : 0x4 ) - { - Movable = false; - - m_Item = new InternalItem( bloodied, this ); - } - - public AnkhNorth( Serial serial ) - : base( serial ) - { - } - - public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Parent == null && Utility.InRange( Location, m.Location, 1 ) && !Utility.InRange( Location, oldLocation, 1 ) ) - Ankhs.Resurrect( m, this ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - Ankhs.GetContextMenuEntries( from, this, list ); - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set{ base.Hue = value; if ( m_Item.Hue != value ) m_Item.Hue = value; } - } - - public override void OnDoubleClickDead( Mobile m ) - { - Ankhs.Resurrect( m, this ); - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as InternalItem; - } - - [TypeAlias( "Server.Items.AnkhEast+InternalItem" )] - private class InternalItem : Item - { - private AnkhNorth m_Item; - - public InternalItem( bool bloodied, AnkhNorth item ) - : base( bloodied ? 0x1E5C : 0x5 ) - { - Movable = false; - - m_Item = item; - } - - public InternalItem( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Parent == null && Utility.InRange( Location, m.Location, 1 ) && !Utility.InRange( Location, oldLocation, 1 ) ) - Ankhs.Resurrect( m, this ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - Ankhs.GetContextMenuEntries( from, this, list ); - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set{ base.Hue = value; if ( m_Item.Hue != value ) m_Item.Hue = value; } - } - - public override void OnDoubleClickDead( Mobile m ) - { - Ankhs.Resurrect( m, this ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as AnkhNorth; - } - } - } -} + public class Ankhs + { + public const int ResurrectRange = 2; + public const int TitheRange = 2; + public const int LockRange = 2; + + public static void GetContextMenuEntries(Mobile from, Item item, List list) + { + if (from is PlayerMobile mobile) + list.Add(new LockKarmaEntry(mobile)); + + list.Add(new ResurrectEntry(from, item)); + + if (Core.AOS) + list.Add(new TitheEntry(from)); + } + + public static void Resurrect(Mobile m, Item item) + { + if (m.Alive) + return; + + if (!m.InRange(item.GetWorldLocation(), ResurrectRange)) + { + m.SendLocalizedMessage(500446); // That is too far away. + } + else if (m.Map != null && m.Map.CanFit(m.Location, 16, false, false)) + { + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.VirtueShrine)); + } + else + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + } + + private class ResurrectEntry : ContextMenuEntry + { + private Item m_Item; + private Mobile m_Mobile; + + public ResurrectEntry(Mobile mobile, Item item) : base(6195, ResurrectRange) + { + m_Mobile = mobile; + m_Item = item; + + Enabled = !m_Mobile.Alive; + } + + public override void OnClick() + { + Resurrect(m_Mobile, m_Item); + } + } + + private class LockKarmaEntry : ContextMenuEntry + { + private PlayerMobile m_Mobile; + + public LockKarmaEntry(PlayerMobile mobile) : base(mobile.KarmaLocked ? 6197 : 6196, LockRange) + { + m_Mobile = mobile; + } + + public override void OnClick() + { + m_Mobile.KarmaLocked = !m_Mobile.KarmaLocked; + + if (m_Mobile.KarmaLocked) + m_Mobile.SendLocalizedMessage( + 1060192); // Your karma has been locked. Your karma can no longer be raised. + else + m_Mobile.SendLocalizedMessage(1060191); // Your karma has been unlocked. Your karma can be raised again. + } + } + + private class TitheEntry : ContextMenuEntry + { + private Mobile m_Mobile; + + public TitheEntry(Mobile mobile) : base(6198, TitheRange) + { + m_Mobile = mobile; + + Enabled = m_Mobile.Alive; + } + + public override void OnClick() + { + if (m_Mobile.CheckAlive()) + m_Mobile.SendGump(new TithingGump(m_Mobile, 0)); + } + } + } + + public class AnkhWest : Item + { + private InternalItem m_Item; + + [Constructible] + public AnkhWest() : this(false) + { + } + + [Constructible] + public AnkhWest(bool bloodied) : base(bloodied ? 0x1D98 : 0x3) + { + Movable = false; + + m_Item = new InternalItem(bloodied, this); + } + + public AnkhWest(Serial serial) : base(serial) + { + } + + public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + if (m_Item.Hue != value) m_Item.Hue = value; + } + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Parent == null && Utility.InRange(Location, m.Location, 1) && !Utility.InRange(Location, oldLocation, 1)) + Ankhs.Resurrect(m, this); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + Ankhs.GetContextMenuEntries(from, this, list); + } + + public override void OnDoubleClickDead(Mobile m) + { + Ankhs.Resurrect(m, this); + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + } + + private class InternalItem : Item + { + private AnkhWest m_Item; + + public InternalItem(bool bloodied, AnkhWest item) : base(bloodied ? 0x1D97 : 0x2) + { + Movable = false; + + m_Item = item; + } + + public InternalItem(Serial serial) : base(serial) + { + } + + public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + if (m_Item.Hue != value) m_Item.Hue = value; + } + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Parent == null && Utility.InRange(Location, m.Location, 1) && !Utility.InRange(Location, oldLocation, 1)) + Ankhs.Resurrect(m, this); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + Ankhs.GetContextMenuEntries(from, this, list); + } + + public override void OnDoubleClickDead(Mobile m) + { + Ankhs.Resurrect(m, this); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as AnkhWest; + } + } + } + + [TypeAlias("Server.Items.AnkhEast")] + public class AnkhNorth : Item + { + private InternalItem m_Item; + + [Constructible] + public AnkhNorth() : this(false) + { + } + + [Constructible] + public AnkhNorth(bool bloodied) : base(bloodied ? 0x1E5D : 0x4) + { + Movable = false; + + m_Item = new InternalItem(bloodied, this); + } + + public AnkhNorth(Serial serial) + : base(serial) + { + } + + public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + if (m_Item.Hue != value) m_Item.Hue = value; + } + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Parent == null && Utility.InRange(Location, m.Location, 1) && !Utility.InRange(Location, oldLocation, 1)) + Ankhs.Resurrect(m, this); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + Ankhs.GetContextMenuEntries(from, this, list); + } + + public override void OnDoubleClickDead(Mobile m) + { + Ankhs.Resurrect(m, this); + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + } + + [TypeAlias("Server.Items.AnkhEast+InternalItem")] + private class InternalItem : Item + { + private AnkhNorth m_Item; + + public InternalItem(bool bloodied, AnkhNorth item) + : base(bloodied ? 0x1E5C : 0x5) + { + Movable = false; + + m_Item = item; + } + + public InternalItem(Serial serial) : base(serial) + { + } + + public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + if (m_Item.Hue != value) m_Item.Hue = value; + } + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Parent == null && Utility.InRange(Location, m.Location, 1) && !Utility.InRange(Location, oldLocation, 1)) + Ankhs.Resurrect(m, this); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + Ankhs.GetContextMenuEntries(from, this, list); + } + + public override void OnDoubleClickDead(Mobile m) + { + Ankhs.Resurrect(m, this); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as AnkhNorth; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Chairs/Benchs.cs b/Scripts/Items/Construction/Chairs/Benchs.cs index 218c82907..26e3e5fb7 100644 --- a/Scripts/Items/Construction/Chairs/Benchs.cs +++ b/Scripts/Items/Construction/Chairs/Benchs.cs @@ -1,31 +1,31 @@ namespace Server.Items { - [Furniture] - [Flippable( 0xB2D, 0xB2C )] - public class WoodenBench : Item - { - [Constructible] - public WoodenBench() : base( 0xB2D ) - { - Weight = 6; - } + [Furniture] + [Flippable(0xB2D, 0xB2C)] + public class WoodenBench : Item + { + [Constructible] + public WoodenBench() : base(0xB2D) + { + Weight = 6; + } - public WoodenBench(Serial serial) : base(serial) - { - } + public WoodenBench(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Chairs/Chairs.cs b/Scripts/Items/Construction/Chairs/Chairs.cs index 97d58a9b7..85d185d73 100644 --- a/Scripts/Items/Construction/Chairs/Chairs.cs +++ b/Scripts/Items/Construction/Chairs/Chairs.cs @@ -1,244 +1,244 @@ namespace Server.Items { - [Furniture] - [Flippable( 0xB4F, 0xB4E, 0xB50, 0xB51 )] - public class FancyWoodenChairCushion : Item - { - [Constructible] - public FancyWoodenChairCushion() : base(0xB4F) - { - Weight = 20.0; - } + [Furniture] + [Flippable(0xB4F, 0xB4E, 0xB50, 0xB51)] + public class FancyWoodenChairCushion : Item + { + [Constructible] + public FancyWoodenChairCushion() : base(0xB4F) + { + Weight = 20.0; + } - public FancyWoodenChairCushion(Serial serial) : base(serial) - { - } + public FancyWoodenChairCushion(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 20.0; - } - } + if (Weight == 6.0) + Weight = 20.0; + } + } - [Furniture] - [Flippable( 0xB53, 0xB52, 0xB54, 0xB55 )] - public class WoodenChairCushion : Item - { - [Constructible] - public WoodenChairCushion() : base(0xB53) - { - Weight = 20.0; - } + [Furniture] + [Flippable(0xB53, 0xB52, 0xB54, 0xB55)] + public class WoodenChairCushion : Item + { + [Constructible] + public WoodenChairCushion() : base(0xB53) + { + Weight = 20.0; + } - public WoodenChairCushion(Serial serial) : base(serial) - { - } + public WoodenChairCushion(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 20.0; - } - } + if (Weight == 6.0) + Weight = 20.0; + } + } - [Furniture] - [Flippable( 0xB57, 0xB56, 0xB59, 0xB58 )] - public class WoodenChair : Item - { - [Constructible] - public WoodenChair() : base(0xB57) - { - Weight = 20.0; - } + [Furniture] + [Flippable(0xB57, 0xB56, 0xB59, 0xB58)] + public class WoodenChair : Item + { + [Constructible] + public WoodenChair() : base(0xB57) + { + Weight = 20.0; + } - public WoodenChair(Serial serial) : base(serial) - { - } + public WoodenChair(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 20.0; - } - } + if (Weight == 6.0) + Weight = 20.0; + } + } - [Furniture] - [Flippable( 0xB5B, 0xB5A, 0xB5C, 0xB5D )] - public class BambooChair : Item - { - [Constructible] - public BambooChair() : base(0xB5B) - { - Weight = 20.0; - } + [Furniture] + [Flippable(0xB5B, 0xB5A, 0xB5C, 0xB5D)] + public class BambooChair : Item + { + [Constructible] + public BambooChair() : base(0xB5B) + { + Weight = 20.0; + } - public BambooChair(Serial serial) : base(serial) - { - } + public BambooChair(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 20.0; - } - } + if (Weight == 6.0) + Weight = 20.0; + } + } - [DynamicFliping] - [Flippable(0x1218, 0x1219, 0x121A, 0x121B)] - public class StoneChair : Item - { - [Constructible] - public StoneChair() : base(0x1218) - { - Weight = 20; - } + [DynamicFliping] + [Flippable(0x1218, 0x1219, 0x121A, 0x121B)] + public class StoneChair : Item + { + [Constructible] + public StoneChair() : base(0x1218) + { + Weight = 20; + } - public StoneChair(Serial serial) : base(serial) - { - } + public StoneChair(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [DynamicFliping] - [Flippable( 0x2DE3, 0x2DE4, 0x2DE5, 0x2DE6 )] - public class OrnateElvenChair : Item - { - [Constructible] - public OrnateElvenChair() : base( 0x2DE3 ) - { - Weight = 1.0; - } + [DynamicFliping] + [Flippable(0x2DE3, 0x2DE4, 0x2DE5, 0x2DE6)] + public class OrnateElvenChair : Item + { + [Constructible] + public OrnateElvenChair() : base(0x2DE3) + { + Weight = 1.0; + } - public OrnateElvenChair( Serial serial ) : base( serial ) - { - } + public OrnateElvenChair(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [DynamicFliping] - [Flippable( 0x2DEB, 0x2DEC, 0x2DED, 0x2DEE )] - public class BigElvenChair : Item - { - [Constructible] - public BigElvenChair() : base( 0x2DEB ) - { - } + [DynamicFliping] + [Flippable(0x2DEB, 0x2DEC, 0x2DED, 0x2DEE)] + public class BigElvenChair : Item + { + [Constructible] + public BigElvenChair() : base(0x2DEB) + { + } - public BigElvenChair( Serial serial ) : base( serial ) - { - } + public BigElvenChair(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [DynamicFliping] - [Flippable( 0x2DF5, 0x2DF6 )] - public class ElvenReadingChair : Item - { - [Constructible] - public ElvenReadingChair() : base( 0x2DF5 ) - { - } + [DynamicFliping] + [Flippable(0x2DF5, 0x2DF6)] + public class ElvenReadingChair : Item + { + [Constructible] + public ElvenReadingChair() : base(0x2DF5) + { + } - public ElvenReadingChair( Serial serial ) : base( serial ) - { - } + public ElvenReadingChair(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Chairs/Stools.cs b/Scripts/Items/Construction/Chairs/Stools.cs index 6d38f3aa0..d6d2af532 100644 --- a/Scripts/Items/Construction/Chairs/Stools.cs +++ b/Scripts/Items/Construction/Chairs/Stools.cs @@ -1,64 +1,64 @@ namespace Server.Items { - [Furniture] - public class Stool : Item - { - [Constructible] - public Stool() : base( 0xA2A ) - { - Weight = 10.0; - } + [Furniture] + public class Stool : Item + { + [Constructible] + public Stool() : base(0xA2A) + { + Weight = 10.0; + } - public Stool(Serial serial) : base(serial) - { - } + public Stool(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 10.0; - } - } + if (Weight == 6.0) + Weight = 10.0; + } + } - [Furniture] - public class FootStool : Item - { - [Constructible] - public FootStool() : base( 0xB5E ) - { - Weight = 6.0; - } + [Furniture] + public class FootStool : Item + { + [Constructible] + public FootStool() : base(0xB5E) + { + Weight = 6.0; + } - public FootStool(Serial serial) : base(serial) - { - } + public FootStool(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 10.0; - } - } + if (Weight == 6.0) + Weight = 10.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Chairs/Thrones.cs b/Scripts/Items/Construction/Chairs/Thrones.cs index 0a783982d..5258ce788 100644 --- a/Scripts/Items/Construction/Chairs/Thrones.cs +++ b/Scripts/Items/Construction/Chairs/Thrones.cs @@ -1,66 +1,66 @@ namespace Server.Items { - [Furniture] - [Flippable(0xB32, 0xB33)] - public class Throne : Item - { - [Constructible] - public Throne() : base(0xB33) - { - Weight = 1.0; - } + [Furniture] + [Flippable(0xB32, 0xB33)] + public class Throne : Item + { + [Constructible] + public Throne() : base(0xB33) + { + Weight = 1.0; + } - public Throne(Serial serial) : base(serial) - { - } + public Throne(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 1.0; - } - } + if (Weight == 6.0) + Weight = 1.0; + } + } - [Furniture] - [Flippable( 0xB2E, 0xB2F, 0xB31, 0xB30 )] - public class WoodenThrone : Item - { - [Constructible] - public WoodenThrone() : base(0xB2E) - { - Weight = 15.0; - } + [Furniture] + [Flippable(0xB2E, 0xB2F, 0xB31, 0xB30)] + public class WoodenThrone : Item + { + [Constructible] + public WoodenThrone() : base(0xB2E) + { + Weight = 15.0; + } - public WoodenThrone(Serial serial) : base(serial) - { - } + public WoodenThrone(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 15.0; - } - } + if (Weight == 6.0) + Weight = 15.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Decorative/DecorativeShield.cs b/Scripts/Items/Construction/Decorative/DecorativeShield.cs index 96c2f7e7e..ec21931e6 100644 --- a/Scripts/Items/Construction/Decorative/DecorativeShield.cs +++ b/Scripts/Items/Construction/Decorative/DecorativeShield.cs @@ -1,423 +1,422 @@ namespace Server.Items { - - [FlippableAttribute( 0x156C, 0x156D )] - public class DecorativeShield1 : Item - { - [Constructible] - public DecorativeShield1() : base( 0x156C ) - { - Movable = false; - } - - public DecorativeShield1( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - [FlippableAttribute( 0x156E, 0x156F )] - public class DecorativeShield2 : Item - { - [Constructible] - public DecorativeShield2() : base( 0x156E ) - { - Movable = false; - } - - public DecorativeShield2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1570, 0x1571 )] - public class DecorativeShield3 : Item - { - [Constructible] - public DecorativeShield3() : base( 0x1570 ) - { - Movable = false; - } - - public DecorativeShield3( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1572, 0x1573 )] - public class DecorativeShield4 : Item - { - [Constructible] - public DecorativeShield4() : base( 0x1572 ) - { - Movable = false; - } - - public DecorativeShield4( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1574, 0x1575 )] - public class DecorativeShield5 : Item - { - [Constructible] - public DecorativeShield5() : base( 0x1574 ) - { - Movable = false; - } - - public DecorativeShield5( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1576, 0x1577 )] - public class DecorativeShield6 : Item - { - [Constructible] - public DecorativeShield6() : base( 0x1576 ) - { - Movable = false; - } - - public DecorativeShield6( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1578, 0x1579 )] - public class DecorativeShield7 : Item - { - [Constructible] - public DecorativeShield7() : base( 0x1578 ) - { - Movable = false; - } - - public DecorativeShield7( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x157A, 0x157B )] - public class DecorativeShield8 : Item - { - [Constructible] - public DecorativeShield8() : base( 0x157A ) - { - Movable = false; - } - - public DecorativeShield8( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x157C, 0x157D )] - public class DecorativeShield9 : Item - { - [Constructible] - public DecorativeShield9() : base( 0x157C ) - { - Movable = false; - } - - public DecorativeShield9( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x157E, 0x157F )] - public class DecorativeShield10 : Item - { - [Constructible] - public DecorativeShield10() : base( 0x157E ) - { - Movable = false; - } - - public DecorativeShield10( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1580, 0x1581 )] - public class DecorativeShield11 : Item - { - [Constructible] - public DecorativeShield11() : base( 0x1580 ) - { - Movable = false; - } - - public DecorativeShield11( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1582, 0x1583, 0x1634, 0x1635 )] - public class DecorativeShieldSword1North : Item - { - [Constructible] - public DecorativeShieldSword1North() : base( Utility.Random( 0x1582, 2 ) ) - { - Movable = false; - } - - public DecorativeShieldSword1North( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1634, 0x1635, 0x1582, 0x1583 )] - public class DecorativeShieldSword1West : Item - { - [Constructible] - public DecorativeShieldSword1West() : base( Utility.Random( 0x1634, 2 ) ) - { - Movable = false; - } - - public DecorativeShieldSword1West( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1584, 0x1585, 0x1636, 0x1637 )] - public class DecorativeShieldSword2North : Item - { - [Constructible] - public DecorativeShieldSword2North() : base( Utility.Random( 0x1584, 2 ) ) - { - Movable = false; - } - - public DecorativeShieldSword2North( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1636, 0x1637, 0x1584, 0x1585 )] - public class DecorativeShieldSword2West : Item - { - [Constructible] - public DecorativeShieldSword2West() : base( Utility.Random( 0x1636, 2 ) ) - { - Movable = false; - } - - public DecorativeShieldSword2West( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - + [Flippable(0x156C, 0x156D)] + public class DecorativeShield1 : Item + { + [Constructible] + public DecorativeShield1() : base(0x156C) + { + Movable = false; + } + + public DecorativeShield1(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x156E, 0x156F)] + public class DecorativeShield2 : Item + { + [Constructible] + public DecorativeShield2() : base(0x156E) + { + Movable = false; + } + + public DecorativeShield2(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1570, 0x1571)] + public class DecorativeShield3 : Item + { + [Constructible] + public DecorativeShield3() : base(0x1570) + { + Movable = false; + } + + public DecorativeShield3(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1572, 0x1573)] + public class DecorativeShield4 : Item + { + [Constructible] + public DecorativeShield4() : base(0x1572) + { + Movable = false; + } + + public DecorativeShield4(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1574, 0x1575)] + public class DecorativeShield5 : Item + { + [Constructible] + public DecorativeShield5() : base(0x1574) + { + Movable = false; + } + + public DecorativeShield5(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1576, 0x1577)] + public class DecorativeShield6 : Item + { + [Constructible] + public DecorativeShield6() : base(0x1576) + { + Movable = false; + } + + public DecorativeShield6(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1578, 0x1579)] + public class DecorativeShield7 : Item + { + [Constructible] + public DecorativeShield7() : base(0x1578) + { + Movable = false; + } + + public DecorativeShield7(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x157A, 0x157B)] + public class DecorativeShield8 : Item + { + [Constructible] + public DecorativeShield8() : base(0x157A) + { + Movable = false; + } + + public DecorativeShield8(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x157C, 0x157D)] + public class DecorativeShield9 : Item + { + [Constructible] + public DecorativeShield9() : base(0x157C) + { + Movable = false; + } + + public DecorativeShield9(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x157E, 0x157F)] + public class DecorativeShield10 : Item + { + [Constructible] + public DecorativeShield10() : base(0x157E) + { + Movable = false; + } + + public DecorativeShield10(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1580, 0x1581)] + public class DecorativeShield11 : Item + { + [Constructible] + public DecorativeShield11() : base(0x1580) + { + Movable = false; + } + + public DecorativeShield11(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1582, 0x1583, 0x1634, 0x1635)] + public class DecorativeShieldSword1North : Item + { + [Constructible] + public DecorativeShieldSword1North() : base(Utility.Random(0x1582, 2)) + { + Movable = false; + } + + public DecorativeShieldSword1North(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1634, 0x1635, 0x1582, 0x1583)] + public class DecorativeShieldSword1West : Item + { + [Constructible] + public DecorativeShieldSword1West() : base(Utility.Random(0x1634, 2)) + { + Movable = false; + } + + public DecorativeShieldSword1West(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1584, 0x1585, 0x1636, 0x1637)] + public class DecorativeShieldSword2North : Item + { + [Constructible] + public DecorativeShieldSword2North() : base(Utility.Random(0x1584, 2)) + { + Movable = false; + } + + public DecorativeShieldSword2North(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1636, 0x1637, 0x1584, 0x1585)] + public class DecorativeShieldSword2West : Item + { + [Constructible] + public DecorativeShieldSword2West() : base(Utility.Random(0x1636, 2)) + { + Movable = false; + } + + public DecorativeShieldSword2West(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Decorative/DecorativeWeapon.cs b/Scripts/Items/Construction/Decorative/DecorativeWeapon.cs index 4d2c9973f..c60acdffc 100644 --- a/Scripts/Items/Construction/Decorative/DecorativeWeapon.cs +++ b/Scripts/Items/Construction/Decorative/DecorativeWeapon.cs @@ -1,535 +1,542 @@ namespace Server.Items { - [FlippableAttribute( 0x155E, 0x155F, 0x155C, 0x155D )] - public class DecorativeBowWest : Item - { - [Constructible] - public DecorativeBowWest() : base( Utility.Random( 0x155E, 2 ) ) - { - Movable = false; - } - - public DecorativeBowWest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x155C, 0x155D, 0x155E, 0x155F )] - public class DecorativeBowNorth : Item - { - [Constructible] - public DecorativeBowNorth() : base( Utility.Random( 0x155C, 2 ) ) - { - Movable = false; - } - - public DecorativeBowNorth( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1560, 0x1561, 0x1562, 0x1563 )] - public class DecorativeAxeNorth : Item - { - [Constructible] - public DecorativeAxeNorth() : base( Utility.Random( 0x1560, 2 ) ) - { - Movable = false; - } - - public DecorativeAxeNorth( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1562, 0x1563, 0x1560, 0x1561 )] - public class DecorativeAxeWest : Item - { - [Constructible] - public DecorativeAxeWest() : base( Utility.Random( 0x1562, 2 ) ) - { - Movable = false; - } - - public DecorativeAxeWest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DecorativeSwordNorth : Item - { - private InternalItem m_Item; - - [Constructible] - public DecorativeSwordNorth() : base( 0x1565 ) - { - Movable = false; - - m_Item = new InternalItem( this ); - } - - public DecorativeSwordNorth( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private DecorativeSwordNorth m_Item; + [Flippable(0x155E, 0x155F, 0x155C, 0x155D)] + public class DecorativeBowWest : Item + { + [Constructible] + public DecorativeBowWest() : base(Utility.Random(0x155E, 2)) + { + Movable = false; + } + + public DecorativeBowWest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x155C, 0x155D, 0x155E, 0x155F)] + public class DecorativeBowNorth : Item + { + [Constructible] + public DecorativeBowNorth() : base(Utility.Random(0x155C, 2)) + { + Movable = false; + } + + public DecorativeBowNorth(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1560, 0x1561, 0x1562, 0x1563)] + public class DecorativeAxeNorth : Item + { + [Constructible] + public DecorativeAxeNorth() : base(Utility.Random(0x1560, 2)) + { + Movable = false; + } + + public DecorativeAxeNorth(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1562, 0x1563, 0x1560, 0x1561)] + public class DecorativeAxeWest : Item + { + [Constructible] + public DecorativeAxeWest() : base(Utility.Random(0x1562, 2)) + { + Movable = false; + } + + public DecorativeAxeWest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DecorativeSwordNorth : Item + { + private InternalItem m_Item; + + [Constructible] + public DecorativeSwordNorth() : base(0x1565) + { + Movable = false; + + m_Item = new InternalItem(this); + } + + public DecorativeSwordNorth(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalItem( DecorativeSwordNorth item ) : base( 0x1564 ) - { - Movable = true; - - m_Item = item; - } - - public InternalItem( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + int version = reader.ReadInt(); - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version + m_Item = reader.ReadItem() as InternalItem; + } - writer.Write( m_Item ); - } + private class InternalItem : Item + { + private DecorativeSwordNorth m_Item; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public InternalItem(DecorativeSwordNorth item) : base(0x1564) + { + Movable = true; - int version = reader.ReadInt(); + m_Item = item; + } - m_Item = reader.ReadItem() as DecorativeSwordNorth; - } - } - } - public class DecorativeSwordWest : Item - { - private InternalItem m_Item; + public InternalItem(Serial serial) : base(serial) + { + } - [Constructible] - public DecorativeSwordWest() : base( 0x1566 ) - { - Movable = false; + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } - m_Item = new InternalItem( this ); - } - - public DecorativeSwordWest( Serial serial ) : base( serial ) - { - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 1 , Z ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item?.Delete(); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private DecorativeSwordWest m_Item; + writer.Write(0); // version - public InternalItem( DecorativeSwordWest item ) : base( 0x1567 ) - { - Movable = true; - - m_Item = item; - } - - public InternalItem( Serial serial ) : base( serial ) - { - } + writer.Write(m_Item); + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 1, Z ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + int version = reader.ReadInt(); - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); + m_Item = reader.ReadItem() as DecorativeSwordNorth; + } + } + } - m_Item = reader.ReadItem() as DecorativeSwordWest; - } - } - } - public class DecorativeDAxeNorth : Item - { - private InternalItem m_Item; + public class DecorativeSwordWest : Item + { + private InternalItem m_Item; - [Constructible] - public DecorativeDAxeNorth() : base( 0x1569 ) - { - Movable = false; + [Constructible] + public DecorativeSwordWest() : base(0x1566) + { + Movable = false; - m_Item = new InternalItem( this ); - } - - public DecorativeDAxeNorth( Serial serial ) : base( serial ) - { - } + m_Item = new InternalItem(this); + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y, Z ); - } + public DecorativeSwordWest(Serial serial) : base(serial) + { + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private DecorativeDAxeNorth m_Item; + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public InternalItem( DecorativeDAxeNorth item ) : base( 0x1568 ) - { - Movable = true; - - m_Item = item; - } - - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Item?.Delete(); + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y, Z ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + writer.Write(0); // version - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); + writer.Write(m_Item); + } - m_Item = reader.ReadItem() as DecorativeDAxeNorth; - } - } - } - public class DecorativeDAxeWest : Item - { - private InternalItem m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public DecorativeDAxeWest() : base( 0x156A ) - { - Movable = false; + int version = reader.ReadInt(); - m_Item = new InternalItem( this ); - } + m_Item = reader.ReadItem() as InternalItem; + } - public DecorativeDAxeWest( Serial serial ) : base( serial ) - { - } + private class InternalItem : Item + { + private DecorativeSwordWest m_Item; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 1 , Z ); - } + public InternalItem(DecorativeSwordWest item) : base(0x1567) + { + Movable = true; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item = item; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public InternalItem(Serial serial) : base(serial) + { + } - m_Item?.Delete(); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( (int) 0 ); // version + public override void OnAfterDelete() + { + base.OnAfterDelete(); - writer.Write( m_Item ); - } + m_Item?.Delete(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(0); // version - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private DecorativeDAxeWest m_Item; + writer.Write(m_Item); + } - public InternalItem( DecorativeDAxeWest item ) : base( 0x156B ) - { - Movable = true; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Item = item; - } + int version = reader.ReadInt(); - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Item = reader.ReadItem() as DecorativeSwordWest; + } + } + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 1, Z ); - } + public class DecorativeDAxeNorth : Item + { + private InternalItem m_Item; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + [Constructible] + public DecorativeDAxeNorth() : base(0x1569) + { + Movable = false; - public override void OnAfterDelete() - { - base.OnAfterDelete(); + m_Item = new InternalItem(this); + } - m_Item?.Delete(); - } + public DecorativeDAxeNorth(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - writer.Write( (int) 0 ); // version + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( m_Item ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + m_Item?.Delete(); + } - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item = reader.ReadItem() as DecorativeDAxeWest; - } - } - } + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + } + + private class InternalItem : Item + { + private DecorativeDAxeNorth m_Item; + + public InternalItem(DecorativeDAxeNorth item) : base(0x1568) + { + Movable = true; + + m_Item = item; + } + + public InternalItem(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as DecorativeDAxeNorth; + } + } + } + + public class DecorativeDAxeWest : Item + { + private InternalItem m_Item; + + [Constructible] + public DecorativeDAxeWest() : base(0x156A) + { + Movable = false; + + m_Item = new InternalItem(this); + } + + public DecorativeDAxeWest(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + } + + private class InternalItem : Item + { + private DecorativeDAxeWest m_Item; + + public InternalItem(DecorativeDAxeWest item) : base(0x156B) + { + Movable = true; + + m_Item = item; + } + + public InternalItem(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as DecorativeDAxeWest; + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Decorative/PaintingPortraits.cs b/Scripts/Items/Construction/Decorative/PaintingPortraits.cs index a7dc1af61..6940d0632 100644 --- a/Scripts/Items/Construction/Decorative/PaintingPortraits.cs +++ b/Scripts/Items/Construction/Decorative/PaintingPortraits.cs @@ -1,197 +1,197 @@ namespace Server.Items { - public class LargePainting : Item - { - [Constructible] - public LargePainting() : base( 0x0EA0 ) - { - Movable = false; - } + public class LargePainting : Item + { + [Constructible] + public LargePainting() : base(0x0EA0) + { + Movable = false; + } - public LargePainting( Serial serial ) : base( serial ) - { - } + public LargePainting(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x0E9F, 0x0EC8 )] - public class WomanPortrait1 : Item - { - [Constructible] - public WomanPortrait1() : base( 0x0E9F ) - { - Movable = false; - } + [Flippable(0x0E9F, 0x0EC8)] + public class WomanPortrait1 : Item + { + [Constructible] + public WomanPortrait1() : base(0x0E9F) + { + Movable = false; + } - public WomanPortrait1( Serial serial ) : base( serial ) - { - } + public WomanPortrait1(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x0EE7, 0x0EC9 )] - public class WomanPortrait2 : Item - { - [Constructible] - public WomanPortrait2() : base( 0x0EE7 ) - { - Movable = false; - } + [Flippable(0x0EE7, 0x0EC9)] + public class WomanPortrait2 : Item + { + [Constructible] + public WomanPortrait2() : base(0x0EE7) + { + Movable = false; + } - public WomanPortrait2( Serial serial ) : base( serial ) - { - } + public WomanPortrait2(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x0EA2, 0x0EA1 )] - public class ManPortrait1 : Item - { - [Constructible] - public ManPortrait1() : base( 0x0EA2 ) - { - Movable = false; - } + [Flippable(0x0EA2, 0x0EA1)] + public class ManPortrait1 : Item + { + [Constructible] + public ManPortrait1() : base(0x0EA2) + { + Movable = false; + } - public ManPortrait1( Serial serial ) : base( serial ) - { - } + public ManPortrait1(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x0EA3, 0x0EA4 )] - public class ManPortrait2 : Item - { - [Constructible] - public ManPortrait2() : base( 0x0EA3 ) - { - Movable = false; - } + [Flippable(0x0EA3, 0x0EA4)] + public class ManPortrait2 : Item + { + [Constructible] + public ManPortrait2() : base(0x0EA3) + { + Movable = false; + } - public ManPortrait2( Serial serial ) : base( serial ) - { - } + public ManPortrait2(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x0EA6, 0x0EA5 )] - public class LadyPortrait1 : Item - { - [Constructible] - public LadyPortrait1() : base( 0x0EA6 ) - { - Movable = false; - } + [Flippable(0x0EA6, 0x0EA5)] + public class LadyPortrait1 : Item + { + [Constructible] + public LadyPortrait1() : base(0x0EA6) + { + Movable = false; + } - public LadyPortrait1( Serial serial ) : base( serial ) - { - } + public LadyPortrait1(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x0EA7, 0x0EA8 )] - public class LadyPortrait2 : Item - { - [Constructible] - public LadyPortrait2() : base( 0x0EA7 ) - { - Movable = false; - } + [Flippable(0x0EA7, 0x0EA8)] + public class LadyPortrait2 : Item + { + [Constructible] + public LadyPortrait2() : base(0x0EA7) + { + Movable = false; + } - public LadyPortrait2( Serial serial ) : base( serial ) - { - } + public LadyPortrait2(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Decorative/Tapestry.cs b/Scripts/Items/Construction/Decorative/Tapestry.cs index 8cc25f18b..948cf6144 100644 --- a/Scripts/Items/Construction/Decorative/Tapestry.cs +++ b/Scripts/Items/Construction/Decorative/Tapestry.cs @@ -1,1167 +1,1179 @@ namespace Server.Items { - public class Tapestry1N : Item - { - private InternalItem m_Item; + public class Tapestry1N : Item + { + private InternalItem m_Item; - [Constructible] - public Tapestry1N() : base( 0xEAA ) - { - Movable = false; + [Constructible] + public Tapestry1N() : base(0xEAA) + { + Movable = false; - m_Item = new InternalItem( this ); - } + m_Item = new InternalItem(this); + } - public Tapestry1N( Serial serial ) : base( serial ) - { - } + public Tapestry1N(Serial serial) : base(serial) + { + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y , Z ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Item?.Delete(); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version - int version = reader.ReadInt(); + writer.Write(m_Item); + } - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry1N m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalItem( Tapestry1N item ) : base( 0xEAB ) - { - Movable = true; + int version = reader.ReadInt(); - m_Item = item; - } + m_Item = reader.ReadItem() as InternalItem; + } - public InternalItem( Serial serial ) : base( serial ) - { - } + private class InternalItem : Item + { + private Tapestry1N m_Item; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y , Z ); - } + public InternalItem(Tapestry1N item) : base(0xEAB) + { + Movable = true; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item = item; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public InternalItem(Serial serial) : base(serial) + { + } - m_Item?.Delete(); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( (int) 0 ); // version + public override void OnAfterDelete() + { + base.OnAfterDelete(); - writer.Write( m_Item ); - } + m_Item?.Delete(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(0); // version - m_Item = reader.ReadItem() as Tapestry1N; - } - } - } + writer.Write(m_Item); + } - public class Tapestry2N : Item - { - private InternalItem m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public Tapestry2N() : base( 0xEAC ) - { - Movable = false; + int version = reader.ReadInt(); - m_Item = new InternalItem( this ); - } + m_Item = reader.ReadItem() as Tapestry1N; + } + } + } - public Tapestry2N( Serial serial ) : base( serial ) - { - } + public class Tapestry2N : Item + { + private InternalItem m_Item; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y , Z ); - } + [Constructible] + public Tapestry2N() : base(0xEAC) + { + Movable = false; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item = new InternalItem(this); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public Tapestry2N(Serial serial) : base(serial) + { + } - m_Item?.Delete(); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( m_Item ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + m_Item?.Delete(); + } - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry2N m_Item; + writer.Write(0); // version - public InternalItem( Tapestry2N item ) : base( 0xEAD ) - { - Movable = true; + writer.Write(m_Item); + } - m_Item = item; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalItem( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y , Z ); - } + m_Item = reader.ReadItem() as InternalItem; + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + private class InternalItem : Item + { + private Tapestry2N m_Item; - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public InternalItem(Tapestry2N item) : base(0xEAD) + { + Movable = true; - m_Item?.Delete(); - } + m_Item = item; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version + public InternalItem(Serial serial) : base(serial) + { + } - writer.Write( m_Item ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - int version = reader.ReadInt(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Item = reader.ReadItem() as Tapestry2N; - } - } - } - public class Tapestry2W : Item - { - private InternalItem m_Item; + m_Item?.Delete(); + } - [Constructible] - public Tapestry2W() : base( 0xEAE ) - { - Movable = false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item = new InternalItem( this ); - } + writer.Write(0); // version - public Tapestry2W( Serial serial ) : base( serial ) - { - } + writer.Write(m_Item); + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 1 , Z ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + int version = reader.ReadInt(); - public override void OnAfterDelete() - { - base.OnAfterDelete(); + m_Item = reader.ReadItem() as Tapestry2N; + } + } + } - m_Item?.Delete(); - } + public class Tapestry2W : Item + { + private InternalItem m_Item; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public Tapestry2W() : base(0xEAE) + { + Movable = false; - writer.Write( (int) 0 ); // version + m_Item = new InternalItem(this); + } - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public Tapestry2W(Serial serial) : base(serial) + { + } - int version = reader.ReadInt(); + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry2W m_Item; + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public InternalItem( Tapestry2W item ) : base( 0xEAF ) - { - Movable = true; + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Item = item; - } + m_Item?.Delete(); + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 1 , Z ); - } + writer.Write(0); // version - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + writer.Write(m_Item); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Item?.Delete(); - } + int version = reader.ReadInt(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Item = reader.ReadItem() as InternalItem; + } - writer.Write( (int) 0 ); // version + private class InternalItem : Item + { + private Tapestry2W m_Item; - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public InternalItem(Tapestry2W item) : base(0xEAF) + { + Movable = true; - int version = reader.ReadInt(); + m_Item = item; + } - m_Item = reader.ReadItem() as Tapestry2W; - } - } - } + public InternalItem(Serial serial) : base(serial) + { + } - public class Tapestry3N : Item - { - private InternalItem m_Item; + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } - [Constructible] - public Tapestry3N() : base( 0xFD6 ) - { - Movable = false; + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - m_Item = new InternalItem( this ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public Tapestry3N( Serial serial ) : base( serial ) - { - } + m_Item?.Delete(); + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 2, Y , Z ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + writer.Write(0); // version - public override void OnAfterDelete() - { - base.OnAfterDelete(); + writer.Write(m_Item); + } - m_Item?.Delete(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); - writer.Write( (int) 0 ); // version + m_Item = reader.ReadItem() as Tapestry2W; + } + } + } - writer.Write( m_Item ); - } + public class Tapestry3N : Item + { + private InternalItem m_Item; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public Tapestry3N() : base(0xFD6) + { + Movable = false; - int version = reader.ReadInt(); + m_Item = new InternalItem(this); + } - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry3N m_Item; + public Tapestry3N(Serial serial) : base(serial) + { + } - public InternalItem( Tapestry3N item ) : base( 0xFD5 ) - { - Movable = true; + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 2, Y, Z); + } - m_Item = item; - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 2, Y , Z ); - } + m_Item?.Delete(); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnAfterDelete() - { - base.OnAfterDelete(); + writer.Write(0); // version - m_Item?.Delete(); - } + writer.Write(m_Item); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version + int version = reader.ReadInt(); - writer.Write( m_Item ); - } + m_Item = reader.ReadItem() as InternalItem; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + private class InternalItem : Item + { + private Tapestry3N m_Item; - int version = reader.ReadInt(); + public InternalItem(Tapestry3N item) : base(0xFD5) + { + Movable = true; - m_Item = reader.ReadItem() as Tapestry3N; - } - } - } + m_Item = item; + } - public class Tapestry3W : Item - { - private InternalItem m_Item; + public InternalItem(Serial serial) : base(serial) + { + } - [Constructible] - public Tapestry3W() : base( 0xFD7 ) - { - Movable = false; + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 2, Y, Z); + } - m_Item = new InternalItem( this ); - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public Tapestry3W( Serial serial ) : base( serial ) - { - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 2 , Z ); - } + m_Item?.Delete(); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnAfterDelete() - { - base.OnAfterDelete(); + writer.Write(0); // version - m_Item?.Delete(); - } + writer.Write(m_Item); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version + int version = reader.ReadInt(); - writer.Write( m_Item ); - } + m_Item = reader.ReadItem() as Tapestry3N; + } + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public class Tapestry3W : Item + { + private InternalItem m_Item; - int version = reader.ReadInt(); + [Constructible] + public Tapestry3W() : base(0xFD7) + { + Movable = false; - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry3W m_Item; + m_Item = new InternalItem(this); + } - public InternalItem( Tapestry3W item ) : base( 0xFD8 ) - { - Movable = true; + public Tapestry3W(Serial serial) : base(serial) + { + } - m_Item = item; - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 2, Z); + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 2 , Z ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item?.Delete(); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item?.Delete(); - } + writer.Write(0); // version - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(m_Item); + } - writer.Write( (int) 0 ); // version + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( m_Item ); - } + int version = reader.ReadInt(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + m_Item = reader.ReadItem() as InternalItem; + } - int version = reader.ReadInt(); + private class InternalItem : Item + { + private Tapestry3W m_Item; - m_Item = reader.ReadItem() as Tapestry3W; - } - } - } + public InternalItem(Tapestry3W item) : base(0xFD8) + { + Movable = true; - public class Tapestry4N : Item - { - private InternalItem m_Item; + m_Item = item; + } - [Constructible] - public Tapestry4N() : base( 0xFDA ) - { - Movable = false; + public InternalItem(Serial serial) : base(serial) + { + } - m_Item = new InternalItem( this ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 2, Z); + } - public Tapestry4N( Serial serial ) : base( serial ) - { - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y , Z ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item?.Delete(); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item?.Delete(); - } + writer.Write(0); // version - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version + writer.Write(m_Item); + } - writer.Write( m_Item ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + m_Item = reader.ReadItem() as Tapestry3W; + } + } + } - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry4N m_Item; + public class Tapestry4N : Item + { + private InternalItem m_Item; - public InternalItem( Tapestry4N item ) : base( 0xFD9 ) - { - Movable = true; + [Constructible] + public Tapestry4N() : base(0xFDA) + { + Movable = false; - m_Item = item; - } + m_Item = new InternalItem(this); + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public Tapestry4N(Serial serial) : base(serial) + { + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y , Z ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Item?.Delete(); - } + m_Item?.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Item ); - } + writer.Write(m_Item); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Item = reader.ReadItem() as Tapestry4N; - } - } - } - public class Tapestry4W : Item - { - private InternalItem m_Item; + m_Item = reader.ReadItem() as InternalItem; + } - [Constructible] - public Tapestry4W() : base( 0xFDB ) - { - Movable = false; + private class InternalItem : Item + { + private Tapestry4N m_Item; - m_Item = new InternalItem( this ); - } + public InternalItem(Tapestry4N item) : base(0xFD9) + { + Movable = true; - public Tapestry4W( Serial serial ) : base( serial ) - { - } + m_Item = item; + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 1, Z ); - } + public InternalItem(Serial serial) : base(serial) + { + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - m_Item?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Item?.Delete(); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( m_Item ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Item); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Item = reader.ReadItem() as InternalItem; - } + int version = reader.ReadInt(); - private class InternalItem : Item - { - private Tapestry4W m_Item; + m_Item = reader.ReadItem() as Tapestry4N; + } + } + } - public InternalItem( Tapestry4W item ) : base( 0xFDC ) - { - Movable = true; + public class Tapestry4W : Item + { + private InternalItem m_Item; - m_Item = item; - } + [Constructible] + public Tapestry4W() : base(0xFDB) + { + Movable = false; - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Item = new InternalItem(this); + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 1, Z ); - } + public Tapestry4W(Serial serial) : base(serial) + { + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - m_Item?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Item?.Delete(); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( m_Item ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Item); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Item = reader.ReadItem() as Tapestry4W; - } - } - } + int version = reader.ReadInt(); - public class Tapestry5N : Item - { - private InternalItem m_Item; + m_Item = reader.ReadItem() as InternalItem; + } - [Constructible] - public Tapestry5N() : base( 0xFDE ) - { - Movable = false; + private class InternalItem : Item + { + private Tapestry4W m_Item; - m_Item = new InternalItem( this ); - } + public InternalItem(Tapestry4W item) : base(0xFDC) + { + Movable = true; - public Tapestry5N( Serial serial ) : base( serial ) - { - } + m_Item = item; + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y , Z ); - } + public InternalItem(Serial serial) : base(serial) + { + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - m_Item?.Delete(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Item?.Delete(); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( m_Item ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Item); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry5N m_Item; + int version = reader.ReadInt(); - public InternalItem( Tapestry5N item ) : base( 0xFDD ) - { - Movable = true; + m_Item = reader.ReadItem() as Tapestry4W; + } + } + } - m_Item = item; - } + public class Tapestry5N : Item + { + private InternalItem m_Item; - public InternalItem( Serial serial ) : base( serial ) - { - } + [Constructible] + public Tapestry5N() : base(0xFDE) + { + Movable = false; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y , Z ); - } + m_Item = new InternalItem(this); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public Tapestry5N(Serial serial) : base(serial) + { + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - m_Item?.Delete(); - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - writer.Write( (int) 0 ); // version + m_Item?.Delete(); + } - writer.Write( m_Item ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version - int version = reader.ReadInt(); + writer.Write(m_Item); + } - m_Item = reader.ReadItem() as Tapestry5N; - } - } - } - public class Tapestry5W : Item - { - private InternalItem m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public Tapestry5W() : base( 0xFDF ) - { - Movable = false; + int version = reader.ReadInt(); - m_Item = new InternalItem( this ); - } + m_Item = reader.ReadItem() as InternalItem; + } - public Tapestry5W( Serial serial ) : base( serial ) - { - } + private class InternalItem : Item + { + private Tapestry5N m_Item; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 1, Z ); - } + public InternalItem(Tapestry5N item) : base(0xFDD) + { + Movable = true; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item = item; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public InternalItem(Serial serial) : base(serial) + { + } - m_Item?.Delete(); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( (int) 0 ); // version + public override void OnAfterDelete() + { + base.OnAfterDelete(); - writer.Write( m_Item ); - } + m_Item?.Delete(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(0); // version - m_Item = reader.ReadItem() as InternalItem; - } + writer.Write(m_Item); + } - private class InternalItem : Item - { - private Tapestry5W m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalItem( Tapestry5W item ) : base( 0xFE0 ) - { - Movable = true; + int version = reader.ReadInt(); - m_Item = item; - } + m_Item = reader.ReadItem() as Tapestry5N; + } + } + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public class Tapestry5W : Item + { + private InternalItem m_Item; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 1, Z ); - } + [Constructible] + public Tapestry5W() : base(0xFDF) + { + Movable = false; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item = new InternalItem(this); + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public Tapestry5W(Serial serial) : base(serial) + { + } - m_Item?.Delete(); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( (int) 0 ); // version + public override void OnAfterDelete() + { + base.OnAfterDelete(); - writer.Write( m_Item ); - } + m_Item?.Delete(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(0); // version - m_Item = reader.ReadItem() as Tapestry5W; - } - } - } + writer.Write(m_Item); + } - public class Tapestry6N : Item - { - private InternalItem m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public Tapestry6N() : base( 0xFE2 ) - { - Movable = false; + int version = reader.ReadInt(); - m_Item = new InternalItem( this ); - } + m_Item = reader.ReadItem() as InternalItem; + } - public Tapestry6N( Serial serial ) : base( serial ) - { - } + private class InternalItem : Item + { + private Tapestry5W m_Item; - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y , Z ); - } + public InternalItem(Tapestry5W item) : base(0xFE0) + { + Movable = true; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + m_Item = item; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public InternalItem(Serial serial) : base(serial) + { + } - m_Item?.Delete(); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( (int) 0 ); // version + public override void OnAfterDelete() + { + base.OnAfterDelete(); - writer.Write( m_Item ); - } + m_Item?.Delete(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(0); // version - m_Item = reader.ReadItem() as InternalItem; - } - private class InternalItem : Item - { - private Tapestry6N m_Item; + writer.Write(m_Item); + } - public InternalItem( Tapestry6N item ) : base( 0xFE1 ) - { - Movable = true; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Item = item; - } + int version = reader.ReadInt(); - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Item = reader.ReadItem() as Tapestry5W; + } + } + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y , Z ); - } + public class Tapestry6N : Item + { + private InternalItem m_Item; - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + [Constructible] + public Tapestry6N() : base(0xFE2) + { + Movable = false; - public override void OnAfterDelete() - { - base.OnAfterDelete(); + m_Item = new InternalItem(this); + } - m_Item?.Delete(); - } + public Tapestry6N(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - writer.Write( (int) 0 ); // version + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - writer.Write( m_Item ); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + m_Item?.Delete(); + } - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Item = reader.ReadItem() as Tapestry6N; - } - } - } - public class Tapestry6W : Item - { - private InternalItem m_Item; + writer.Write(0); // version - [Constructible] - public Tapestry6W() : base( 0xFE3 ) - { - Movable = false; + writer.Write(m_Item); + } - m_Item = new InternalItem( this ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public Tapestry6W( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y - 1, Z ); - } + m_Item = reader.ReadItem() as InternalItem; + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + private class InternalItem : Item + { + private Tapestry6N m_Item; - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public InternalItem(Tapestry6N item) : base(0xFE1) + { + Movable = true; - m_Item?.Delete(); - } + m_Item = item; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public InternalItem(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + } - writer.Write( m_Item ); - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - int version = reader.ReadInt(); + m_Item?.Delete(); + } - m_Item = reader.ReadItem() as InternalItem; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private class InternalItem : Item - { - private Tapestry6W m_Item; + writer.Write(0); // version - public InternalItem( Tapestry6W item ) : base( 0xFE4 ) - { - Movable = true; + writer.Write(m_Item); + } - m_Item = item; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalItem( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X , Y + 1, Z ); - } + m_Item = reader.ReadItem() as Tapestry6N; + } + } + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public class Tapestry6W : Item + { + private InternalItem m_Item; - public override void OnAfterDelete() - { - base.OnAfterDelete(); + [Constructible] + public Tapestry6W() : base(0xFE3) + { + Movable = false; - m_Item?.Delete(); - } + m_Item = new InternalItem(this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Tapestry6W(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } - writer.Write( m_Item ); - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - int version = reader.ReadInt(); + m_Item?.Delete(); + } - m_Item = reader.ReadItem() as Tapestry6W; - } - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + } + + private class InternalItem : Item + { + private Tapestry6W m_Item; + + public InternalItem(Tapestry6W item) : base(0xFE4) + { + Movable = true; + + m_Item = item; + } + + public InternalItem(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as Tapestry6W; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Doors/BaseDoor.cs b/Scripts/Items/Construction/Doors/BaseDoor.cs index 5cdb93479..5781c1c80 100644 --- a/Scripts/Items/Construction/Doors/BaseDoor.cs +++ b/Scripts/Items/Construction/Doors/BaseDoor.cs @@ -6,498 +6,524 @@ using Server.Targeting; namespace Server.Items { - public abstract class BaseDoor : Item, ILockable, ITelekinesisable - { - private bool m_Open; - private BaseDoor m_Link; - - private Timer m_Timer; - - private static Point3D[] m_Offsets = { - new Point3D(-1, 1, 0 ), - new Point3D( 1, 1, 0 ), - new Point3D(-1, 0, 0 ), - new Point3D( 1,-1, 0 ), - new Point3D( 1, 1, 0 ), - new Point3D( 1,-1, 0 ), - new Point3D( 0, 0, 0 ), - new Point3D( 0,-1, 0 ), - - new Point3D( 0, 0, 0 ), - new Point3D( 0, 0, 0 ), - new Point3D( 0, 0, 0 ), - new Point3D( 0, 0, 0 ) - }; - - // Called by RunUO - public static void Initialize() - { - EventSink.OpenDoorMacroUsed += EventSink_OpenDoorMacroUsed; - - CommandSystem.Register( "Link", AccessLevel.GameMaster, Link_OnCommand ); - CommandSystem.Register( "ChainLink", AccessLevel.GameMaster, ChainLink_OnCommand ); - } - - [Usage( "Link" )] - [Description( "Links two targeted doors together." )] - private static void Link_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, Link_OnFirstTarget ); - e.Mobile.SendMessage( "Target the first door to link." ); - } - - private static void Link_OnFirstTarget( Mobile from, object targeted ) - { - if ( !(targeted is BaseDoor door) ) - { - from.BeginTarget( -1, false, TargetFlags.None, Link_OnFirstTarget ); - from.SendMessage( "That is not a door. Try again." ); - } - else - { - from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( Link_OnSecondTarget ), door ); - from.SendMessage( "Target the second door to link." ); - } - } - - private static void Link_OnSecondTarget( Mobile from, object targeted, object state ) - { - BaseDoor first = (BaseDoor)state; - - if ( !(targeted is BaseDoor second) ) - { - from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( Link_OnSecondTarget ), first ); - from.SendMessage( "That is not a door. Try again." ); - } - else - { - first.Link = second; - second.Link = first; - from.SendMessage( "The doors have been linked." ); - } - } - - [Usage( "ChainLink" )] - [Description( "Chain-links two or more targeted doors together." )] - private static void ChainLink_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( ChainLink_OnTarget ), new List() ); - e.Mobile.SendMessage( "Target the first of a sequence of doors to link." ); - } - - private static void ChainLink_OnTarget( Mobile from, object targeted, object state ) - { - if ( !(targeted is BaseDoor door) ) - { - from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( ChainLink_OnTarget ), state ); - from.SendMessage( "That is not a door. Try again." ); - } - else - { - List list = (List)state; - - if ( list.Count > 0 && list[0] == door ) - { - if ( list.Count >= 2 ) - { - for ( int i = 0; i < list.Count; ++i ) - list[i].Link = list[(i + 1) % list.Count]; - - from.SendMessage( "The chain of doors have been linked." ); - } - else - { - from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( ChainLink_OnTarget ), state ); - from.SendMessage( "You have not yet targeted two unique doors. Target the second door to link." ); - } - } - else if ( list.Contains( door ) ) - { - from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( ChainLink_OnTarget ), state ); - from.SendMessage( "You have already targeted that door. Target another door, or retarget the first door to complete the chain." ); - } - else - { - list.Add( door ); - - from.BeginTarget( -1, false, TargetFlags.None, new TargetStateCallback( ChainLink_OnTarget ), state ); - - if ( list.Count == 1 ) - from.SendMessage( "Target the second door to link." ); - else - from.SendMessage( "Target another door to link. To complete the chain, retarget the first door." ); - } - } - } - - private static void EventSink_OpenDoorMacroUsed( OpenDoorMacroEventArgs args ) - { - Mobile m = args.Mobile; - - if ( m.Map != null ) - { - int x = m.X, y = m.Y; - - switch ( m.Direction & Direction.Mask ) - { - case Direction.North: --y; break; - case Direction.Right: ++x; --y; break; - case Direction.East: ++x; break; - case Direction.Down: ++x; ++y; break; - case Direction.South: ++y; break; - case Direction.Left: --x; ++y; break; - case Direction.West: --x; break; - case Direction.Up: --x; --y; break; - } - - Sector sector = m.Map.GetSector( x, y ); - - foreach ( Item item in sector.Items ) - { - if ( item.Location.X == x && item.Location.Y == y && (item.Z + item.ItemData.Height) > m.Z && (m.Z + 16) > item.Z && item is BaseDoor && m.CanSee( item ) && m.InLOS( item ) ) - { - if ( m.CheckAlive() ) - { - m.SendLocalizedMessage( 500024 ); // Opening door... - item.OnDoubleClick( m ); - } - - break; - } - } - } - } - - public static Point3D GetOffset( DoorFacing facing ) - { - return m_Offsets[(int)facing]; - } - - private class InternalTimer : Timer - { - private BaseDoor m_Door; - - public InternalTimer( BaseDoor door ) : base( TimeSpan.FromSeconds( 20.0 ), TimeSpan.FromSeconds( 10.0 ) ) - { - Priority = TimerPriority.OneSecond; - m_Door = door; - } - - protected override void OnTick() - { - if ( m_Door.Open && m_Door.IsFreeToClose() ) - m_Door.Open = false; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Locked { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public uint KeyValue { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Open - { - get => m_Open; - set - { - if ( m_Open != value ) - { - m_Open = value; - - ItemID = m_Open ? OpenedID : ClosedID; - - if ( m_Open ) - Location = new Point3D( X + Offset.X, Y + Offset.Y, Z + Offset.Z ); - else - Location = new Point3D( X - Offset.X, Y - Offset.Y, Z - Offset.Z ); - - Effects.PlaySound( this, Map, m_Open ? OpenedSound : ClosedSound ); - - if ( m_Open ) - m_Timer.Start(); - else - m_Timer.Stop(); - } - } - } - - public bool CanClose() - { - if ( !m_Open ) - return true; - - Map map = Map; - - if ( map == null ) - return false; - - Point3D p = new Point3D( X - Offset.X, Y - Offset.Y, Z - Offset.Z ); - - return CheckFit( map, p, 16 ); - } - - private bool CheckFit( Map map, Point3D p, int height ) - { - if ( map == Map.Internal ) - return false; - - int x = p.X; - int y = p.Y; - int z = p.Z; - - Sector sector = map.GetSector( x, y ); - List items = sector.Items; - List mobs = sector.Mobiles; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint( x, y ) && !(item is BaseDoor) ) - { - ItemData id = item.ItemData; - bool surface = id.Surface; - bool impassable = id.Impassable; - - if ( (surface || impassable) && (item.Z + id.CalcHeight) > z && (z + height) > item.Z ) - return false; - } - } - - for ( int i = 0; i < mobs.Count; ++i ) - { - Mobile m = mobs[i]; - - if ( m.Location.X == x && m.Location.Y == y ) - { - if ( m.Hidden && m.AccessLevel > AccessLevel.Player ) - continue; - - if ( !m.Alive ) - continue; - - if ( (m.Z + 16) > z && (z + height) > m.Z ) - return false; - } - } - - return true; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int OpenedID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ClosedID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int OpenedSound { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ClosedSound { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Offset { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public BaseDoor Link - { - get - { - if ( m_Link != null && m_Link.Deleted ) - m_Link = null; - - return m_Link; - } - set => m_Link = value; - } - - public virtual bool UseChainedFunctionality => false; - - public List GetChain() - { - List list = new List(); - BaseDoor c = this; - - do - { - list.Add( c ); - c = c.Link; - } while ( c != null && !list.Contains( c ) ); - - return list; - } - - public bool IsFreeToClose() - { - if ( !UseChainedFunctionality ) - return CanClose(); - - List list = GetChain(); - - bool freeToClose = true; - - for ( int i = 0; freeToClose && i < list.Count; ++i ) - freeToClose = list[i].CanClose(); - - return freeToClose; - } - - public void OnTelekinesis( Mobile from ) - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5022 ); - Effects.PlaySound( Location, Map, 0x1F5 ); - - Use( from ); - } - - public virtual bool IsInside( Mobile from ) - { - return false; - } - - public virtual bool UseLocks() - { - return true; - } - - public virtual void Use( Mobile from ) - { - if ( Locked && !m_Open && UseLocks() ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502502 ); // That is locked, but you open it with your godly powers. - //from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, 502502, "", "" ) ); // That is locked, but you open it with your godly powers. - } - else if ( Key.ContainsKey( from.Backpack, KeyValue ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501282 ); // You quickly unlock, open, and relock the door - } - else if ( IsInside( from ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501280 ); // That is locked, but is usable from the inside. - } - else - { - if ( Hue == 0x44E && Map == Map.Malas ) // doom door into healer room in doom - SendLocalizedMessageTo( from, 1060014 ); // Only the dead may pass. - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502503 ); // That is locked. - - return; - } - } - - if ( m_Open && !IsFreeToClose() ) - return; - - if ( m_Open ) - OnClosed( from ); - else - OnOpened( from ); - - if ( UseChainedFunctionality ) - { - bool open = !m_Open; - - List list = GetChain(); - - for ( int i = 0; i < list.Count; ++i ) - list[i].Open = open; - } - else - { - Open = !m_Open; - - BaseDoor link = Link; - - if ( m_Open && link != null && !link.Open ) - link.Open = true; - } - } - - public virtual void OnOpened( Mobile from ) - { - } - - public virtual void OnClosed( Mobile from ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel == AccessLevel.Player && (/*!from.InLOS( this ) || */!from.InRange( GetWorldLocation(), 2 )) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else - Use( from ); - } - - public BaseDoor( int closedID, int openedID, int openedSound, int closedSound, Point3D offset ) : base( closedID ) - { - OpenedID = openedID; - ClosedID = closedID; - OpenedSound = openedSound; - ClosedSound = closedSound; - Offset = offset; - - m_Timer = new InternalTimer( this ); - - Movable = false; - } - - public BaseDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( KeyValue ); - - writer.Write( m_Open ); - writer.Write( Locked ); - writer.Write( OpenedID ); - writer.Write( ClosedID ); - writer.Write( OpenedSound ); - writer.Write( ClosedSound ); - writer.Write( Offset ); - writer.Write( m_Link ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - KeyValue = reader.ReadUInt(); - m_Open = reader.ReadBool(); - Locked = reader.ReadBool(); - OpenedID = reader.ReadInt(); - ClosedID = reader.ReadInt(); - OpenedSound = reader.ReadInt(); - ClosedSound = reader.ReadInt(); - Offset = reader.ReadPoint3D(); - m_Link = reader.ReadItem() as BaseDoor; - - m_Timer = new InternalTimer( this ); - - if ( m_Open ) - m_Timer.Start(); - - break; - } - } - } - } -} + public abstract class BaseDoor : Item, ILockable, ITelekinesisable + { + private static Point3D[] m_Offsets = + { + new Point3D(-1, 1, 0), + new Point3D(1, 1, 0), + new Point3D(-1, 0, 0), + new Point3D(1, -1, 0), + new Point3D(1, 1, 0), + new Point3D(1, -1, 0), + new Point3D(0, 0, 0), + new Point3D(0, -1, 0), + + new Point3D(0, 0, 0), + new Point3D(0, 0, 0), + new Point3D(0, 0, 0), + new Point3D(0, 0, 0) + }; + + private BaseDoor m_Link; + private bool m_Open; + + private Timer m_Timer; + + public BaseDoor(int closedID, int openedID, int openedSound, int closedSound, Point3D offset) : base(closedID) + { + OpenedID = openedID; + ClosedID = closedID; + OpenedSound = openedSound; + ClosedSound = closedSound; + Offset = offset; + + m_Timer = new InternalTimer(this); + + Movable = false; + } + + public BaseDoor(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Open + { + get => m_Open; + set + { + if (m_Open != value) + { + m_Open = value; + + ItemID = m_Open ? OpenedID : ClosedID; + + if (m_Open) + Location = new Point3D(X + Offset.X, Y + Offset.Y, Z + Offset.Z); + else + Location = new Point3D(X - Offset.X, Y - Offset.Y, Z - Offset.Z); + + Effects.PlaySound(this, Map, m_Open ? OpenedSound : ClosedSound); + + if (m_Open) + m_Timer.Start(); + else + m_Timer.Stop(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int OpenedID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ClosedID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int OpenedSound{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ClosedSound{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Offset{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public BaseDoor Link + { + get + { + if (m_Link != null && m_Link.Deleted) + m_Link = null; + + return m_Link; + } + set => m_Link = value; + } + + public virtual bool UseChainedFunctionality => false; + + [CommandProperty(AccessLevel.GameMaster)] + public bool Locked{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public uint KeyValue{ get; set; } + + public void OnTelekinesis(Mobile from) + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x376A, 9, 32, 5022); + Effects.PlaySound(Location, Map, 0x1F5); + + Use(from); + } + + // Called by RunUO + public static void Initialize() + { + EventSink.OpenDoorMacroUsed += EventSink_OpenDoorMacroUsed; + + CommandSystem.Register("Link", AccessLevel.GameMaster, Link_OnCommand); + CommandSystem.Register("ChainLink", AccessLevel.GameMaster, ChainLink_OnCommand); + } + + [Usage("Link")] + [Description("Links two targeted doors together.")] + private static void Link_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, Link_OnFirstTarget); + e.Mobile.SendMessage("Target the first door to link."); + } + + private static void Link_OnFirstTarget(Mobile from, object targeted) + { + if (!(targeted is BaseDoor door)) + { + from.BeginTarget(-1, false, TargetFlags.None, Link_OnFirstTarget); + from.SendMessage("That is not a door. Try again."); + } + else + { + from.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(Link_OnSecondTarget), door); + from.SendMessage("Target the second door to link."); + } + } + + private static void Link_OnSecondTarget(Mobile from, object targeted, object state) + { + BaseDoor first = (BaseDoor)state; + + if (!(targeted is BaseDoor second)) + { + from.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(Link_OnSecondTarget), first); + from.SendMessage("That is not a door. Try again."); + } + else + { + first.Link = second; + second.Link = first; + from.SendMessage("The doors have been linked."); + } + } + + [Usage("ChainLink")] + [Description("Chain-links two or more targeted doors together.")] + private static void ChainLink_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(ChainLink_OnTarget), + new List()); + e.Mobile.SendMessage("Target the first of a sequence of doors to link."); + } + + private static void ChainLink_OnTarget(Mobile from, object targeted, object state) + { + if (!(targeted is BaseDoor door)) + { + from.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(ChainLink_OnTarget), state); + from.SendMessage("That is not a door. Try again."); + } + else + { + List list = (List)state; + + if (list.Count > 0 && list[0] == door) + { + if (list.Count >= 2) + { + for (int i = 0; i < list.Count; ++i) + list[i].Link = list[(i + 1) % list.Count]; + + from.SendMessage("The chain of doors have been linked."); + } + else + { + from.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(ChainLink_OnTarget), state); + from.SendMessage("You have not yet targeted two unique doors. Target the second door to link."); + } + } + else if (list.Contains(door)) + { + from.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(ChainLink_OnTarget), state); + from.SendMessage( + "You have already targeted that door. Target another door, or retarget the first door to complete the chain."); + } + else + { + list.Add(door); + + from.BeginTarget(-1, false, TargetFlags.None, new TargetStateCallback(ChainLink_OnTarget), state); + + if (list.Count == 1) + from.SendMessage("Target the second door to link."); + else + from.SendMessage("Target another door to link. To complete the chain, retarget the first door."); + } + } + } + + private static void EventSink_OpenDoorMacroUsed(OpenDoorMacroEventArgs args) + { + Mobile m = args.Mobile; + + if (m.Map != null) + { + int x = m.X, y = m.Y; + + switch (m.Direction & Direction.Mask) + { + case Direction.North: + --y; + break; + case Direction.Right: + ++x; + --y; + break; + case Direction.East: + ++x; + break; + case Direction.Down: + ++x; + ++y; + break; + case Direction.South: + ++y; + break; + case Direction.Left: + --x; + ++y; + break; + case Direction.West: + --x; + break; + case Direction.Up: + --x; + --y; + break; + } + + Sector sector = m.Map.GetSector(x, y); + + foreach (Item item in sector.Items) + if (item.Location.X == x && item.Location.Y == y && item.Z + item.ItemData.Height > m.Z && + m.Z + 16 > item.Z && item is BaseDoor && m.CanSee(item) && m.InLOS(item)) + { + if (m.CheckAlive()) + { + m.SendLocalizedMessage(500024); // Opening door... + item.OnDoubleClick(m); + } + + break; + } + } + } + + public static Point3D GetOffset(DoorFacing facing) + { + return m_Offsets[(int)facing]; + } + + public bool CanClose() + { + if (!m_Open) + return true; + + Map map = Map; + + if (map == null) + return false; + + Point3D p = new Point3D(X - Offset.X, Y - Offset.Y, Z - Offset.Z); + + return CheckFit(map, p, 16); + } + + private bool CheckFit(Map map, Point3D p, int height) + { + if (map == Map.Internal) + return false; + + int x = p.X; + int y = p.Y; + int z = p.Z; + + Sector sector = map.GetSector(x, y); + List items = sector.Items; + List mobs = sector.Mobiles; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (!(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint(x, y) && + !(item is BaseDoor)) + { + ItemData id = item.ItemData; + bool surface = id.Surface; + bool impassable = id.Impassable; + + if ((surface || impassable) && item.Z + id.CalcHeight > z && z + height > item.Z) + return false; + } + } + + for (int i = 0; i < mobs.Count; ++i) + { + Mobile m = mobs[i]; + + if (m.Location.X == x && m.Location.Y == y) + { + if (m.Hidden && m.AccessLevel > AccessLevel.Player) + continue; + + if (!m.Alive) + continue; + + if (m.Z + 16 > z && z + height > m.Z) + return false; + } + } + + return true; + } + + public List GetChain() + { + List list = new List(); + BaseDoor c = this; + + do + { + list.Add(c); + c = c.Link; + } while (c != null && !list.Contains(c)); + + return list; + } + + public bool IsFreeToClose() + { + if (!UseChainedFunctionality) + return CanClose(); + + List list = GetChain(); + + bool freeToClose = true; + + for (int i = 0; freeToClose && i < list.Count; ++i) + freeToClose = list[i].CanClose(); + + return freeToClose; + } + + public virtual bool IsInside(Mobile from) + { + return false; + } + + public virtual bool UseLocks() + { + return true; + } + + public virtual void Use(Mobile from) + { + if (Locked && !m_Open && UseLocks()) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 502502); // That is locked, but you open it with your godly powers. + //from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, 502502, "", "" ) ); // That is locked, but you open it with your godly powers. + } + else if (Key.ContainsKey(from.Backpack, KeyValue)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 501282); // You quickly unlock, open, and relock the door + } + else if (IsInside(from)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 501280); // That is locked, but is usable from the inside. + } + else + { + if (Hue == 0x44E && Map == Map.Malas) // doom door into healer room in doom + SendLocalizedMessageTo(from, 1060014); // Only the dead may pass. + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502503); // That is locked. + + return; + } + } + + if (m_Open && !IsFreeToClose()) + return; + + if (m_Open) + OnClosed(from); + else + OnOpened(from); + + if (UseChainedFunctionality) + { + bool open = !m_Open; + + List list = GetChain(); + + for (int i = 0; i < list.Count; ++i) + list[i].Open = open; + } + else + { + Open = !m_Open; + + BaseDoor link = Link; + + if (m_Open && link != null && !link.Open) + link.Open = true; + } + } + + public virtual void OnOpened(Mobile from) + { + } + + public virtual void OnClosed(Mobile from) + { + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel == AccessLevel.Player && !from.InRange(GetWorldLocation(), 2)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else + Use(from); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(KeyValue); + + writer.Write(m_Open); + writer.Write(Locked); + writer.Write(OpenedID); + writer.Write(ClosedID); + writer.Write(OpenedSound); + writer.Write(ClosedSound); + writer.Write(Offset); + writer.Write(m_Link); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + KeyValue = reader.ReadUInt(); + m_Open = reader.ReadBool(); + Locked = reader.ReadBool(); + OpenedID = reader.ReadInt(); + ClosedID = reader.ReadInt(); + OpenedSound = reader.ReadInt(); + ClosedSound = reader.ReadInt(); + Offset = reader.ReadPoint3D(); + m_Link = reader.ReadItem() as BaseDoor; + + m_Timer = new InternalTimer(this); + + if (m_Open) + m_Timer.Start(); + + break; + } + } + } + + private class InternalTimer : Timer + { + private BaseDoor m_Door; + + public InternalTimer(BaseDoor door) : base(TimeSpan.FromSeconds(20.0), TimeSpan.FromSeconds(10.0)) + { + Priority = TimerPriority.OneSecond; + m_Door = door; + } + + protected override void OnTick() + { + if (m_Door.Open && m_Door.IsFreeToClose()) + m_Door.Open = false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Doors/Doors.cs b/Scripts/Items/Construction/Doors/Doors.cs index 27680ac44..3471e1269 100644 --- a/Scripts/Items/Construction/Doors/Doors.cs +++ b/Scripts/Items/Construction/Doors/Doors.cs @@ -1,357 +1,371 @@ namespace Server.Items { - public enum DoorFacing - { - WestCW, - EastCCW, - WestCCW, - EastCW, - SouthCW, - NorthCCW, - SouthCCW, - NorthCW, - //Sliding Doors - SouthSW, - SouthSE, - WestSS, - WestSN - } - - public class IronGateShort : BaseDoor - { - [Constructible] - public IronGateShort( DoorFacing facing ) : base( 0x84c + (2 * (int)facing), 0x84d + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } - - public IronGateShort( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class IronGate : BaseDoor - { - [Constructible] - public IronGate( DoorFacing facing ) : base( 0x824 + (2 * (int)facing), 0x825 + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } - - public IronGate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LightWoodGate : BaseDoor - { - [Constructible] - public LightWoodGate( DoorFacing facing ) : base( 0x839 + (2 * (int)facing), 0x83A + (2 * (int)facing), 0xEB, 0xF2, GetOffset( facing ) ) - { - } - - public LightWoodGate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DarkWoodGate : BaseDoor - { - [Constructible] - public DarkWoodGate( DoorFacing facing ) : base( 0x866 + (2 * (int)facing), 0x867 + (2 * (int)facing), 0xEB, 0xF2, GetOffset( facing ) ) - { - } - - public DarkWoodGate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MetalDoor : BaseDoor - { - [Constructible] - public MetalDoor( DoorFacing facing ) : base( 0x675 + (2 * (int)facing), 0x676 + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } - - public MetalDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BarredMetalDoor : BaseDoor - { - [Constructible] - public BarredMetalDoor( DoorFacing facing ) : base( 0x685 + (2 * (int)facing), 0x686 + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } - - public BarredMetalDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BarredMetalDoor2 : BaseDoor - { - [Constructible] - public BarredMetalDoor2( DoorFacing facing ) : base( 0x1FED + (2 * (int)facing), 0x1FEE + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } - - public BarredMetalDoor2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RattanDoor : BaseDoor - { - [Constructible] - public RattanDoor( DoorFacing facing ) : base( 0x695 + (2 * (int)facing), 0x696 + (2 * (int)facing), 0xEB, 0xF2, GetOffset( facing ) ) - { - } - - public RattanDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DarkWoodDoor : BaseDoor - { - [Constructible] - public DarkWoodDoor( DoorFacing facing ) : base( 0x6A5 + (2 * (int)facing), 0x6A6 + (2 * (int)facing), 0xEA, 0xF1, GetOffset( facing ) ) - { - } - - public DarkWoodDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MediumWoodDoor : BaseDoor - { - [Constructible] - public MediumWoodDoor( DoorFacing facing ) : base( 0x6B5 + (2 * (int)facing), 0x6B6 + (2 * (int)facing), 0xEA, 0xF1, GetOffset( facing ) ) - { - } - - public MediumWoodDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MetalDoor2 : BaseDoor - { - [Constructible] - public MetalDoor2( DoorFacing facing ) : base( 0x6C5 + (2 * (int)facing), 0x6C6 + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } - - public MetalDoor2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LightWoodDoor : BaseDoor - { - [Constructible] - public LightWoodDoor( DoorFacing facing ) : base( 0x6D5 + (2 * (int)facing), 0x6D6 + (2 * (int)facing), 0xEA, 0xF1, GetOffset( facing ) ) - { - } - - public LightWoodDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class StrongWoodDoor : BaseDoor - { - [Constructible] - public StrongWoodDoor( DoorFacing facing ) : base( 0x6E5 + (2 * (int)facing), 0x6E6 + (2 * (int)facing), 0xEA, 0xF1, GetOffset( facing ) ) - { - } - - public StrongWoodDoor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public enum DoorFacing + { + WestCW, + EastCCW, + WestCCW, + EastCW, + SouthCW, + NorthCCW, + SouthCCW, + NorthCW, + + //Sliding Doors + SouthSW, + SouthSE, + WestSS, + WestSN + } + + public class IronGateShort : BaseDoor + { + [Constructible] + public IronGateShort(DoorFacing facing) : base(0x84c + 2 * (int)facing, 0x84d + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } + + public IronGateShort(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class IronGate : BaseDoor + { + [Constructible] + public IronGate(DoorFacing facing) : base(0x824 + 2 * (int)facing, 0x825 + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } + + public IronGate(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LightWoodGate : BaseDoor + { + [Constructible] + public LightWoodGate(DoorFacing facing) : base(0x839 + 2 * (int)facing, 0x83A + 2 * (int)facing, 0xEB, 0xF2, + GetOffset(facing)) + { + } + + public LightWoodGate(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DarkWoodGate : BaseDoor + { + [Constructible] + public DarkWoodGate(DoorFacing facing) : base(0x866 + 2 * (int)facing, 0x867 + 2 * (int)facing, 0xEB, 0xF2, + GetOffset(facing)) + { + } + + public DarkWoodGate(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MetalDoor : BaseDoor + { + [Constructible] + public MetalDoor(DoorFacing facing) : base(0x675 + 2 * (int)facing, 0x676 + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } + + public MetalDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BarredMetalDoor : BaseDoor + { + [Constructible] + public BarredMetalDoor(DoorFacing facing) : base(0x685 + 2 * (int)facing, 0x686 + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } + + public BarredMetalDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BarredMetalDoor2 : BaseDoor + { + [Constructible] + public BarredMetalDoor2(DoorFacing facing) : base(0x1FED + 2 * (int)facing, 0x1FEE + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } + + public BarredMetalDoor2(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RattanDoor : BaseDoor + { + [Constructible] + public RattanDoor(DoorFacing facing) : base(0x695 + 2 * (int)facing, 0x696 + 2 * (int)facing, 0xEB, 0xF2, + GetOffset(facing)) + { + } + + public RattanDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DarkWoodDoor : BaseDoor + { + [Constructible] + public DarkWoodDoor(DoorFacing facing) : base(0x6A5 + 2 * (int)facing, 0x6A6 + 2 * (int)facing, 0xEA, 0xF1, + GetOffset(facing)) + { + } + + public DarkWoodDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MediumWoodDoor : BaseDoor + { + [Constructible] + public MediumWoodDoor(DoorFacing facing) : base(0x6B5 + 2 * (int)facing, 0x6B6 + 2 * (int)facing, 0xEA, 0xF1, + GetOffset(facing)) + { + } + + public MediumWoodDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MetalDoor2 : BaseDoor + { + [Constructible] + public MetalDoor2(DoorFacing facing) : base(0x6C5 + 2 * (int)facing, 0x6C6 + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } + + public MetalDoor2(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LightWoodDoor : BaseDoor + { + [Constructible] + public LightWoodDoor(DoorFacing facing) : base(0x6D5 + 2 * (int)facing, 0x6D6 + 2 * (int)facing, 0xEA, 0xF1, + GetOffset(facing)) + { + } + + public LightWoodDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StrongWoodDoor : BaseDoor + { + [Constructible] + public StrongWoodDoor(DoorFacing facing) : base(0x6E5 + 2 * (int)facing, 0x6E6 + 2 * (int)facing, 0xEA, 0xF1, + GetOffset(facing)) + { + } + + public StrongWoodDoor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Doors/HouseDoors.cs b/Scripts/Items/Construction/Doors/HouseDoors.cs index 588a61711..694804130 100644 --- a/Scripts/Items/Construction/Doors/HouseDoors.cs +++ b/Scripts/Items/Construction/Doors/HouseDoors.cs @@ -1,240 +1,265 @@ using System; -using Server.Multis; -using Server.Gumps; using System.Collections.Generic; using Server.ContextMenus; +using Server.Gumps; +using Server.Multis; namespace Server.Items { - public class MetalHouseDoor : BaseHouseDoor - { - [Constructible] - public MetalHouseDoor( DoorFacing facing ) : base( facing, 0x675 + (2 * (int)facing), 0x676 + (2 * (int)facing), 0xEC, 0xF3, GetOffset( facing ) ) - { - } + public class MetalHouseDoor : BaseHouseDoor + { + [Constructible] + public MetalHouseDoor(DoorFacing facing) : base(facing, 0x675 + 2 * (int)facing, 0x676 + 2 * (int)facing, 0xEC, 0xF3, + GetOffset(facing)) + { + } - public MetalHouseDoor( Serial serial ) : base( serial ) - { - } + public MetalHouseDoor(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DarkWoodHouseDoor : BaseHouseDoor - { - [Constructible] - public DarkWoodHouseDoor( DoorFacing facing ) : base( facing, 0x6A5 + (2 * (int)facing), 0x6A6 + (2 * (int)facing), 0xEA, 0xF1, GetOffset( facing ) ) - { - } + public class DarkWoodHouseDoor : BaseHouseDoor + { + [Constructible] + public DarkWoodHouseDoor(DoorFacing facing) : base(facing, 0x6A5 + 2 * (int)facing, 0x6A6 + 2 * (int)facing, 0xEA, + 0xF1, GetOffset(facing)) + { + } - public DarkWoodHouseDoor( Serial serial ) : base( serial ) - { - } + public DarkWoodHouseDoor(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GenericHouseDoor : BaseHouseDoor - { - [Constructible] - public GenericHouseDoor( DoorFacing facing, int baseItemID, int openedSound, int closedSound ) : this( facing, baseItemID, openedSound, closedSound, true ) - { - } + public class GenericHouseDoor : BaseHouseDoor + { + [Constructible] + public GenericHouseDoor(DoorFacing facing, int baseItemID, int openedSound, int closedSound) : this(facing, + baseItemID, openedSound, closedSound, true) + { + } - [Constructible] - public GenericHouseDoor( DoorFacing facing, int baseItemID, int openedSound, int closedSound, bool autoAdjust ) - : base( facing, baseItemID + (autoAdjust ? (2 * (int)facing) : 0), baseItemID + 1 + (autoAdjust ? (2 * (int)facing) : 0), openedSound, closedSound, GetOffset( facing ) ) - { - } + [Constructible] + public GenericHouseDoor(DoorFacing facing, int baseItemID, int openedSound, int closedSound, bool autoAdjust) + : base(facing, baseItemID + (autoAdjust ? 2 * (int)facing : 0), + baseItemID + 1 + (autoAdjust ? 2 * (int)facing : 0), openedSound, closedSound, GetOffset(facing)) + { + } - public GenericHouseDoor( Serial serial ) : base( serial ) - { - } + public GenericHouseDoor(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public abstract class BaseHouseDoor : BaseDoor, ISecurable - { - [CommandProperty( AccessLevel.GameMaster )] - public DoorFacing Facing { get; set; } + public abstract class BaseHouseDoor : BaseDoor, ISecurable + { + public BaseHouseDoor(DoorFacing facing, int closedID, int openedID, int openedSound, int closedSound, Point3D offset) + : base(closedID, openedID, openedSound, closedSound, offset) + { + Facing = facing; + Level = SecureLevel.Anyone; + } - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + public BaseHouseDoor(Serial serial) : base(serial) + { + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } + [CommandProperty(AccessLevel.GameMaster)] + public DoorFacing Facing{ get; set; } - public BaseHouseDoor( DoorFacing facing, int closedID, int openedID, int openedSound, int closedSound, Point3D offset ) : base( closedID, openedID, openedSound, closedSound, offset ) - { - Facing = facing; - Level = SecureLevel.Anyone; - } + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - public BaseHouse FindHouse() - { - Point3D loc; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } - if ( Open ) - loc = new Point3D( X - Offset.X, Y - Offset.Y, Z - Offset.Z ); - else - loc = Location; + public BaseHouse FindHouse() + { + Point3D loc; - return BaseHouse.FindHouseAt( loc, Map, 20 ); - } + if (Open) + loc = new Point3D(X - Offset.X, Y - Offset.Y, Z - Offset.Z); + else + loc = Location; - public bool CheckAccess( Mobile m ) - { - BaseHouse house = FindHouse(); + return BaseHouse.FindHouseAt(loc, Map, 20); + } - if ( house == null ) - return false; + public bool CheckAccess(Mobile m) + { + BaseHouse house = FindHouse(); - if ( !house.IsAosRules ) - return true; + if (house == null) + return false; - if ( house.Public ? house.IsBanned( m ) : !house.HasAccess( m ) ) - return false; + if (!house.IsAosRules) + return true; - return house.HasSecureAccess( m, Level ); - } + if (house.Public ? house.IsBanned(m) : !house.HasAccess(m)) + return false; - public override void OnOpened( Mobile from ) - { - BaseHouse house = FindHouse(); + return house.HasSecureAccess(m, Level); + } - if ( house != null && house.IsFriend( from ) && from.AccessLevel == AccessLevel.Player && house.RefreshDecay() ) - from.SendLocalizedMessage( 1043293 ); // Your house's age and contents have been refreshed. + public override void OnOpened(Mobile from) + { + BaseHouse house = FindHouse(); - if ( house != null && house.Public && !house.IsFriend( from ) ) - house.Visits++; - } + if (house != null && house.IsFriend(from) && from.AccessLevel == AccessLevel.Player && house.RefreshDecay()) + from.SendLocalizedMessage(1043293); // Your house's age and contents have been refreshed. - public override bool UseLocks() - { - BaseHouse house = FindHouse(); + if (house != null && house.Public && !house.IsFriend(from)) + house.Visits++; + } - return ( house == null || !house.IsAosRules ); - } + public override bool UseLocks() + { + BaseHouse house = FindHouse(); - public override void Use( Mobile from ) - { - if ( !CheckAccess( from ) ) - from.SendLocalizedMessage( 1061637 ); // You are not allowed to access this. - else - base.Use( from ); - } + return house == null || !house.IsAosRules; + } - public BaseHouseDoor( Serial serial ) : base( serial ) - { - } + public override void Use(Mobile from) + { + if (!CheckAccess(from)) + from.SendLocalizedMessage(1061637); // You are not allowed to access this. + else + base.Use(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) Level ); + writer.Write((int)Level); - writer.Write( (int) Facing ); - } + writer.Write((int)Facing); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 0; - } - case 0: - { - if ( version < 1 ) - Level = SecureLevel.Anyone; + switch (version) + { + case 1: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 0; + } + case 0: + { + if (version < 1) + Level = SecureLevel.Anyone; - Facing = (DoorFacing)reader.ReadInt(); - break; - } - } - } + Facing = (DoorFacing)reader.ReadInt(); + break; + } + } + } - public override bool IsInside( Mobile from ) - { - int x,y,w,h; + public override bool IsInside(Mobile from) + { + int x, y, w, h; - const int r = 2; - const int bs = r*2+1; - const int ss = r+1; + const int r = 2; + const int bs = r * 2 + 1; + const int ss = r + 1; - switch ( Facing ) - { - case DoorFacing.WestCW: - case DoorFacing.EastCCW: x = -r; y = -r; w = bs; h = ss; break; + switch (Facing) + { + case DoorFacing.WestCW: + case DoorFacing.EastCCW: + x = -r; + y = -r; + w = bs; + h = ss; + break; - case DoorFacing.EastCW: - case DoorFacing.WestCCW: x = -r; y = 0; w = bs; h = ss; break; + case DoorFacing.EastCW: + case DoorFacing.WestCCW: + x = -r; + y = 0; + w = bs; + h = ss; + break; - case DoorFacing.SouthCW: - case DoorFacing.NorthCCW: x = -r; y = -r; w = ss; h = bs; break; + case DoorFacing.SouthCW: + case DoorFacing.NorthCCW: + x = -r; + y = -r; + w = ss; + h = bs; + break; - case DoorFacing.NorthCW: - case DoorFacing.SouthCCW: x = 0; y = -r; w = ss; h = bs; break; + case DoorFacing.NorthCW: + case DoorFacing.SouthCCW: + x = 0; + y = -r; + w = ss; + h = bs; + break; - //No way to test the 'insideness' of SE Sliding doors on OSI, so leaving them default to false until furthur information gained + //No way to test the 'insideness' of SE Sliding doors on OSI, so leaving them default to false until furthur information gained - default: return false; - } + default: return false; + } - int rx = from.X - X; - int ry = from.Y - Y; - int az = Math.Abs( from.Z - Z ); + int rx = from.X - X; + int ry = from.Y - Y; + int az = Math.Abs(from.Z - Z); - return ( rx >= x && rx < (x+w) && ry >= y && ry < (y+h) && az <= 4 ); - } - } + return rx >= x && rx < x + w && ry >= y && ry < y + h && az <= 4; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Doors/Portcullis.cs b/Scripts/Items/Construction/Doors/Portcullis.cs index b72e52659..c6faa6186 100644 --- a/Scripts/Items/Construction/Doors/Portcullis.cs +++ b/Scripts/Items/Construction/Doors/Portcullis.cs @@ -1,58 +1,58 @@ namespace Server.Items { - public class PortcullisNS : BaseDoor - { - public override bool UseChainedFunctionality => true; + public class PortcullisNS : BaseDoor + { + [Constructible] + public PortcullisNS() : base(0x6F5, 0x6F5, 0xF0, 0xEF, new Point3D(0, 0, 20)) + { + } - [Constructible] - public PortcullisNS() : base( 0x6F5, 0x6F5, 0xF0, 0xEF, new Point3D( 0, 0, 20 ) ) - { - } + public PortcullisNS(Serial serial) : base(serial) + { + } - public PortcullisNS( Serial serial ) : base( serial ) - { - } + public override bool UseChainedFunctionality => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PortcullisEW : BaseDoor - { - public override bool UseChainedFunctionality => true; + public class PortcullisEW : BaseDoor + { + [Constructible] + public PortcullisEW() : base(0x6F6, 0x6F6, 0xF0, 0xEF, new Point3D(0, 0, 20)) + { + } - [Constructible] - public PortcullisEW() : base( 0x6F6, 0x6F6, 0xF0, 0xEF, new Point3D( 0, 0, 20 ) ) - { - } + public PortcullisEW(Serial serial) : base(serial) + { + } - public PortcullisEW( Serial serial ) : base( serial ) - { - } + public override bool UseChainedFunctionality => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Doors/SecretDoors.cs b/Scripts/Items/Construction/Doors/SecretDoors.cs index c4515e36a..4fe529760 100644 --- a/Scripts/Items/Construction/Doors/SecretDoors.cs +++ b/Scripts/Items/Construction/Doors/SecretDoors.cs @@ -1,158 +1,164 @@ namespace Server.Items { - public class SecretStoneDoor1 : BaseDoor - { - [Constructible] - public SecretStoneDoor1( DoorFacing facing ) : base( 0xE8 + (2 * (int)facing), 0xE9 + (2 * (int)facing), 0xED, 0xF4, GetOffset( facing ) ) - { - } + public class SecretStoneDoor1 : BaseDoor + { + [Constructible] + public SecretStoneDoor1(DoorFacing facing) : base(0xE8 + 2 * (int)facing, 0xE9 + 2 * (int)facing, 0xED, 0xF4, + GetOffset(facing)) + { + } - public SecretStoneDoor1( Serial serial ) : base( serial ) - { - } + public SecretStoneDoor1(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SecretDungeonDoor : BaseDoor - { - [Constructible] - public SecretDungeonDoor( DoorFacing facing ) : base( 0x314 + (2 * (int)facing), 0x315 + (2 * (int)facing), 0xED, 0xF4, GetOffset( facing ) ) - { - } + public class SecretDungeonDoor : BaseDoor + { + [Constructible] + public SecretDungeonDoor(DoorFacing facing) : base(0x314 + 2 * (int)facing, 0x315 + 2 * (int)facing, 0xED, 0xF4, + GetOffset(facing)) + { + } - public SecretDungeonDoor( Serial serial ) : base( serial ) - { - } + public SecretDungeonDoor(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SecretStoneDoor2 : BaseDoor - { - [Constructible] - public SecretStoneDoor2( DoorFacing facing ) : base( 0x324 + (2 * (int)facing), 0x325 + (2 * (int)facing), 0xED, 0xF4, GetOffset( facing ) ) - { - } + public class SecretStoneDoor2 : BaseDoor + { + [Constructible] + public SecretStoneDoor2(DoorFacing facing) : base(0x324 + 2 * (int)facing, 0x325 + 2 * (int)facing, 0xED, 0xF4, + GetOffset(facing)) + { + } - public SecretStoneDoor2( Serial serial ) : base( serial ) - { - } + public SecretStoneDoor2(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SecretWoodenDoor : BaseDoor - { - [Constructible] - public SecretWoodenDoor( DoorFacing facing ) : base( 0x334 + (2 * (int)facing), 0x335 + (2 * (int)facing), 0xED, 0xF4, GetOffset( facing ) ) - { - } + public class SecretWoodenDoor : BaseDoor + { + [Constructible] + public SecretWoodenDoor(DoorFacing facing) : base(0x334 + 2 * (int)facing, 0x335 + 2 * (int)facing, 0xED, 0xF4, + GetOffset(facing)) + { + } - public SecretWoodenDoor( Serial serial ) : base( serial ) - { - } + public SecretWoodenDoor(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SecretLightWoodDoor : BaseDoor - { - [Constructible] - public SecretLightWoodDoor( DoorFacing facing ) : base( 0x344 + (2 * (int)facing), 0x345 + (2 * (int)facing), 0xED, 0xF4, GetOffset( facing ) ) - { - } + public class SecretLightWoodDoor : BaseDoor + { + [Constructible] + public SecretLightWoodDoor(DoorFacing facing) : base(0x344 + 2 * (int)facing, 0x345 + 2 * (int)facing, 0xED, 0xF4, + GetOffset(facing)) + { + } - public SecretLightWoodDoor( Serial serial ) : base( serial ) - { - } + public SecretLightWoodDoor(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SecretStoneDoor3 : BaseDoor - { - [Constructible] - public SecretStoneDoor3( DoorFacing facing ) : base( 0x354 + (2 * (int)facing), 0x355 + (2 * (int)facing), 0xED, 0xF4, GetOffset( facing ) ) - { - } + public class SecretStoneDoor3 : BaseDoor + { + [Constructible] + public SecretStoneDoor3(DoorFacing facing) : base(0x354 + 2 * (int)facing, 0x355 + 2 * (int)facing, 0xED, 0xF4, + GetOffset(facing)) + { + } - public SecretStoneDoor3( Serial serial ) : base( serial ) - { - } + public SecretStoneDoor3(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) // Default Serialize method - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) // Default Serialize method + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) // Default Deserialize method - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) // Default Deserialize method + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Floors/Floors.cs b/Scripts/Items/Construction/Floors/Floors.cs index 97e4fe437..a50951236 100644 --- a/Scripts/Items/Construction/Floors/Floors.cs +++ b/Scripts/Items/Construction/Floors/Floors.cs @@ -1,626 +1,626 @@ namespace Server.Items { - public abstract class BaseFloor : Item - { - public BaseFloor( int itemID, int count ) : base( Utility.Random( itemID, count ) ) - { - Movable = false; - } - - public BaseFloor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class StonePaversLight : BaseFloor - { - [Constructible] - public StonePaversLight() : base( 0x519, 4 ) - { - } - - public StonePaversLight( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class StonePaversMedium : BaseFloor - { - [Constructible] - public StonePaversMedium() : base( 0x51D, 4 ) - { - } - - public StonePaversMedium( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class StonePaversDark : BaseFloor - { - [Constructible] - public StonePaversDark() : base( 0x521, 4 ) - { - } - - public StonePaversDark( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreyFlagstones : BaseFloor - { - [Constructible] - public GreyFlagstones() : base( 0x4FC, 4 ) - { - } - - public GreyFlagstones( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SandFlagstones : BaseFloor - { - [Constructible] - public SandFlagstones() : base( 0x500, 4 ) - { - } - - public SandFlagstones( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MarbleFloor : BaseFloor - { - [Constructible] - public MarbleFloor() : base( 0x50D, 2 ) - { - } - - public MarbleFloor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenMarbleFloor : BaseFloor - { - [Constructible] - public GreenMarbleFloor() : base( 0x50F, 2 ) - { - } - - public GreenMarbleFloor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreyMarbleFloor : BaseFloor - { - [Constructible] - public GreyMarbleFloor() : base( 0x511, 4 ) - { - } - - public GreyMarbleFloor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CobblestonesFloor : BaseFloor - { - [Constructible] - public CobblestonesFloor() : base( 0x515, 4 ) - { - } - - public CobblestonesFloor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SandstoneFloorN : BaseFloor - { - [Constructible] - public SandstoneFloorN() : base( 0x525, 4 ) - { - } - - public SandstoneFloorN( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SandstoneFloorW : BaseFloor - { - [Constructible] - public SandstoneFloorW() : base( 0x529, 4 ) - { - } - - public SandstoneFloorW( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DarkSandstoneFloorN : BaseFloor - { - [Constructible] - public DarkSandstoneFloorN() : base( 0x52F, 4 ) - { - } - - public DarkSandstoneFloorN( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DarkSandstoneFloorW : BaseFloor - { - [Constructible] - public DarkSandstoneFloorW() : base( 0x533, 4 ) - { - } - - public DarkSandstoneFloorW( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BricksFloor1 : BaseFloor - { - [Constructible] - public BricksFloor1() : base( 0x4E2, 8 ) - { - } - - public BricksFloor1( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BricksFloor2 : BaseFloor - { - [Constructible] - public BricksFloor2() : base( 0x537, 4 ) - { - } - - public BricksFloor2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CaveFloorCenter : BaseFloor - { - [Constructible] - public CaveFloorCenter() : base( 0x53B, 4 ) - { - } - - public CaveFloorCenter( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CaveFloorSouth : BaseFloor - { - [Constructible] - public CaveFloorSouth() : base( 0x541, 3 ) - { - } - - public CaveFloorSouth( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CaveFloorEast : BaseFloor - { - [Constructible] - public CaveFloorEast() : base( 0x544, 3 ) - { - } - - public CaveFloorEast( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CaveFloorWest : BaseFloor - { - [Constructible] - public CaveFloorWest() : base( 0x54A, 3 ) - { - } - - public CaveFloorWest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CaveFloorNorth : BaseFloor - { - [Constructible] - public CaveFloorNorth() : base( 0x54D, 3 ) - { - } - - public CaveFloorNorth( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MarblePavers : BaseFloor - { - [Constructible] - public MarblePavers() : base( 0x495, 4 ) - { - } - - public MarblePavers( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BlueSlateFloorCenter : BaseFloor - { - [Constructible] - public BlueSlateFloorCenter() : base( 0x49B, 1 ) - { - } - - public BlueSlateFloorCenter( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreySlateFloor : BaseFloor - { - [Constructible] - public GreySlateFloor() : base( 0x49C, 1 ) - { - } - - public GreySlateFloor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public abstract class BaseFloor : Item + { + public BaseFloor(int itemID, int count) : base(Utility.Random(itemID, count)) + { + Movable = false; + } + + public BaseFloor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StonePaversLight : BaseFloor + { + [Constructible] + public StonePaversLight() : base(0x519, 4) + { + } + + public StonePaversLight(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StonePaversMedium : BaseFloor + { + [Constructible] + public StonePaversMedium() : base(0x51D, 4) + { + } + + public StonePaversMedium(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StonePaversDark : BaseFloor + { + [Constructible] + public StonePaversDark() : base(0x521, 4) + { + } + + public StonePaversDark(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreyFlagstones : BaseFloor + { + [Constructible] + public GreyFlagstones() : base(0x4FC, 4) + { + } + + public GreyFlagstones(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SandFlagstones : BaseFloor + { + [Constructible] + public SandFlagstones() : base(0x500, 4) + { + } + + public SandFlagstones(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MarbleFloor : BaseFloor + { + [Constructible] + public MarbleFloor() : base(0x50D, 2) + { + } + + public MarbleFloor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenMarbleFloor : BaseFloor + { + [Constructible] + public GreenMarbleFloor() : base(0x50F, 2) + { + } + + public GreenMarbleFloor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreyMarbleFloor : BaseFloor + { + [Constructible] + public GreyMarbleFloor() : base(0x511, 4) + { + } + + public GreyMarbleFloor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CobblestonesFloor : BaseFloor + { + [Constructible] + public CobblestonesFloor() : base(0x515, 4) + { + } + + public CobblestonesFloor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SandstoneFloorN : BaseFloor + { + [Constructible] + public SandstoneFloorN() : base(0x525, 4) + { + } + + public SandstoneFloorN(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SandstoneFloorW : BaseFloor + { + [Constructible] + public SandstoneFloorW() : base(0x529, 4) + { + } + + public SandstoneFloorW(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DarkSandstoneFloorN : BaseFloor + { + [Constructible] + public DarkSandstoneFloorN() : base(0x52F, 4) + { + } + + public DarkSandstoneFloorN(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DarkSandstoneFloorW : BaseFloor + { + [Constructible] + public DarkSandstoneFloorW() : base(0x533, 4) + { + } + + public DarkSandstoneFloorW(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BricksFloor1 : BaseFloor + { + [Constructible] + public BricksFloor1() : base(0x4E2, 8) + { + } + + public BricksFloor1(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BricksFloor2 : BaseFloor + { + [Constructible] + public BricksFloor2() : base(0x537, 4) + { + } + + public BricksFloor2(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CaveFloorCenter : BaseFloor + { + [Constructible] + public CaveFloorCenter() : base(0x53B, 4) + { + } + + public CaveFloorCenter(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CaveFloorSouth : BaseFloor + { + [Constructible] + public CaveFloorSouth() : base(0x541, 3) + { + } + + public CaveFloorSouth(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CaveFloorEast : BaseFloor + { + [Constructible] + public CaveFloorEast() : base(0x544, 3) + { + } + + public CaveFloorEast(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CaveFloorWest : BaseFloor + { + [Constructible] + public CaveFloorWest() : base(0x54A, 3) + { + } + + public CaveFloorWest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CaveFloorNorth : BaseFloor + { + [Constructible] + public CaveFloorNorth() : base(0x54D, 3) + { + } + + public CaveFloorNorth(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MarblePavers : BaseFloor + { + [Constructible] + public MarblePavers() : base(0x495, 4) + { + } + + public MarblePavers(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BlueSlateFloorCenter : BaseFloor + { + [Constructible] + public BlueSlateFloorCenter() : base(0x49B, 1) + { + } + + public BlueSlateFloorCenter(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreySlateFloor : BaseFloor + { + [Constructible] + public GreySlateFloor() : base(0x49C, 1) + { + } + + public GreySlateFloor(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/BarrelParts.cs b/Scripts/Items/Construction/Misc/BarrelParts.cs index 81b4f6165..302963cf7 100644 --- a/Scripts/Items/Construction/Misc/BarrelParts.cs +++ b/Scripts/Items/Construction/Misc/BarrelParts.cs @@ -1,113 +1,113 @@ namespace Server.Items { - public class BarrelLid : Item - { - [Constructible] - public BarrelLid() : base(0x1DB8) - { - Weight = 2; - } + public class BarrelLid : Item + { + [Constructible] + public BarrelLid() : base(0x1DB8) + { + Weight = 2; + } - public BarrelLid(Serial serial) : base(serial) - { - } + public BarrelLid(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute(0x1EB1, 0x1EB2, 0x1EB3, 0x1EB4)] - public class BarrelStaves : Item - { - [Constructible] - public BarrelStaves() : base(0x1EB1) - { - Weight = 1; - } + [Flippable(0x1EB1, 0x1EB2, 0x1EB3, 0x1EB4)] + public class BarrelStaves : Item + { + [Constructible] + public BarrelStaves() : base(0x1EB1) + { + Weight = 1; + } - public BarrelStaves(Serial serial) : base(serial) - { - } + public BarrelStaves(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BarrelHoops : Item - { - public override int LabelNumber => 1011228; // Barrel hoops + public class BarrelHoops : Item + { + [Constructible] + public BarrelHoops() : base(0x1DB7) + { + Weight = 5; + } - [Constructible] - public BarrelHoops() : base(0x1DB7) - { - Weight = 5; - } + public BarrelHoops(Serial serial) : base(serial) + { + } - public BarrelHoops(Serial serial) : base(serial) - { - } + public override int LabelNumber => 1011228; // Barrel hoops - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class BarrelTap : Item - { - [Constructible] - public BarrelTap() : base(0x1004) - { - Weight = 1; - } + public class BarrelTap : Item + { + [Constructible] + public BarrelTap() : base(0x1004) + { + Weight = 1; + } - public BarrelTap(Serial serial) : base(serial) - { - } + public BarrelTap(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/Easle.cs b/Scripts/Items/Construction/Misc/Easle.cs index 59a4ed13b..854f432b1 100644 --- a/Scripts/Items/Construction/Misc/Easle.cs +++ b/Scripts/Items/Construction/Misc/Easle.cs @@ -1,34 +1,34 @@ namespace Server.Items { - [Furniture] - [Flippable(0xF65, 0xF67, 0xF69)] - public class Easle : Item - { - [Constructible] - public Easle() : base(0xF65) - { - Weight = 25.0; - } + [Furniture] + [Flippable(0xF65, 0xF67, 0xF69)] + public class Easle : Item + { + [Constructible] + public Easle() : base(0xF65) + { + Weight = 25.0; + } - public Easle(Serial serial) : base(serial) - { - } + public Easle(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 10.0 ) - Weight = 25.0; - } - } + if (Weight == 10.0) + Weight = 25.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/MeltedWax.cs b/Scripts/Items/Construction/Misc/MeltedWax.cs index 998218c0e..de4ab63dd 100644 --- a/Scripts/Items/Construction/Misc/MeltedWax.cs +++ b/Scripts/Items/Construction/Misc/MeltedWax.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class MeltedWax : Item - { - public override int LabelNumber => 1016492; // melted wax + public class MeltedWax : Item + { + [Constructible] + public MeltedWax() : base(0x122A) + { + Movable = false; + Hue = 0x835; + } - [Constructible] - public MeltedWax() : base( 0x122A ) - { - Movable = false; - Hue = 0x835; - } + public MeltedWax(Serial serial) : base(serial) + { + } - public MeltedWax(Serial serial) : base(serial) - { - } + public override int LabelNumber => 1016492; // melted wax - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/MusicStand.cs b/Scripts/Items/Construction/Misc/MusicStand.cs index f81c789dd..a196a6e04 100644 --- a/Scripts/Items/Construction/Misc/MusicStand.cs +++ b/Scripts/Items/Construction/Misc/MusicStand.cs @@ -1,66 +1,66 @@ namespace Server.Items { - [Furniture] - [Flippable(0xEBB, 0xEBC)] - public class TallMusicStand : Item - { - [Constructible] - public TallMusicStand() : base(0xEBB) - { - Weight = 10.0; - } + [Furniture] + [Flippable(0xEBB, 0xEBC)] + public class TallMusicStand : Item + { + [Constructible] + public TallMusicStand() : base(0xEBB) + { + Weight = 10.0; + } - public TallMusicStand(Serial serial) : base(serial) - { - } + public TallMusicStand(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 8.0 ) - Weight = 10.0; - } - } + if (Weight == 8.0) + Weight = 10.0; + } + } - [Furniture] - [Flippable(0xEB6,0xEB8)] - public class ShortMusicStand : Item - { - [Constructible] - public ShortMusicStand() : base(0xEB6) - { - Weight = 10.0; - } + [Furniture] + [Flippable(0xEB6, 0xEB8)] + public class ShortMusicStand : Item + { + [Constructible] + public ShortMusicStand() : base(0xEB6) + { + Weight = 10.0; + } - public ShortMusicStand(Serial serial) : base(serial) - { - } + public ShortMusicStand(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 10.0; - } - } -} + if (Weight == 6.0) + Weight = 10.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/Obelisk.cs b/Scripts/Items/Construction/Misc/Obelisk.cs index b07a22032..96b3d953a 100644 --- a/Scripts/Items/Construction/Misc/Obelisk.cs +++ b/Scripts/Items/Construction/Misc/Obelisk.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class Obelisk : Item - { - public override int LabelNumber => 1016474; // an obelisk + public class Obelisk : Item + { + [Constructible] + public Obelisk() : base(0x1184) + { + Movable = false; + } - [Constructible] - public Obelisk() : base(0x1184) - { - Movable = false; - } + public Obelisk(Serial serial) : base(serial) + { + } - public Obelisk(Serial serial) : base(serial) - { - } + public override int LabelNumber => 1016474; // an obelisk - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/Screens.cs b/Scripts/Items/Construction/Misc/Screens.cs index 9bf402a77..347ae9300 100644 --- a/Scripts/Items/Construction/Misc/Screens.cs +++ b/Scripts/Items/Construction/Misc/Screens.cs @@ -1,63 +1,60 @@ namespace Server.Items { - [Furniture] - [Flippable( 0x24D0, 0x24D1, 0x24D2, 0x24D3, 0x24D4 )] - public class BambooScreen : Item - { - [Constructible] - public BambooScreen() : base(0x24D0) - { - Weight = 20.0; - } + [Furniture] + [Flippable(0x24D0, 0x24D1, 0x24D2, 0x24D3, 0x24D4)] + public class BambooScreen : Item + { + [Constructible] + public BambooScreen() : base(0x24D0) + { + Weight = 20.0; + } - public BambooScreen(Serial serial) : base(serial) - { - } + public BambooScreen(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); + } + } - } - } + [Furniture] + [Flippable(0x24CB, 0x24CC, 0x24CD, 0x24CE, 0x24CF)] + public class ShojiScreen : Item + { + [Constructible] + public ShojiScreen() : base(0x24CB) + { + Weight = 20.0; + } - [Furniture] - [Flippable( 0x24CB, 0x24CC, 0x24CD, 0x24CE, 0x24CF )] - public class ShojiScreen : Item - { - [Constructible] - public ShojiScreen() : base(0x24CB) - { - Weight = 20.0; - } + public ShojiScreen(Serial serial) : base(serial) + { + } - public ShojiScreen(Serial serial) : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/Statues.cs b/Scripts/Items/Construction/Misc/Statues.cs index 02c2648b1..32337d1ab 100644 --- a/Scripts/Items/Construction/Misc/Statues.cs +++ b/Scripts/Items/Construction/Misc/Statues.cs @@ -1,348 +1,348 @@ namespace Server.Items { - public class StatueSouth : Item - { - [Constructible] - public StatueSouth() : base(0x139A) - { - Weight = 10; - } - - public StatueSouth(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatueSouth2 : Item - { - [Constructible] - public StatueSouth2() : base(0x1227) - { - Weight = 10; - } - - public StatueSouth2(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatueNorth : Item - { - [Constructible] - public StatueNorth() : base(0x139B) - { - Weight = 10; - } - - public StatueNorth(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatueWest : Item - { - [Constructible] - public StatueWest() : base(0x1226) - { - Weight = 10; - } - - public StatueWest(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatueEast : Item - { - [Constructible] - public StatueEast() : base(0x139C) - { - Weight = 10; - } - - public StatueEast(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatueEast2 : Item - { - [Constructible] - public StatueEast2() : base(0x1224) - { - Weight = 10; - } - - public StatueEast2(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatueSouthEast : Item - { - [Constructible] - public StatueSouthEast() : base(0x1225) - { - Weight = 10; - } - - public StatueSouthEast(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class BustSouth : Item - { - [Constructible] - public BustSouth() : base(0x12CB) - { - Weight = 10; - } - - public BustSouth(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class BustEast : Item - { - [Constructible] - public BustEast() : base(0x12CA) - { - Weight = 10; - } - - public BustEast(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatuePegasus : Item - { - [Constructible] - public StatuePegasus() : base(0x139D) - { - Weight = 10; - } - - public StatuePegasus(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class StatuePegasus2 : Item - { - [Constructible] - public StatuePegasus2() : base(0x1228) - { - Weight = 10; - } - - public StatuePegasus2(Serial serial) : base(serial) - { - } - - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } - - public class SmallTowerSculpture : Item - { - [Constructible] - public SmallTowerSculpture() : base(0x241A) - { - Weight = 20.0; - } - - public SmallTowerSculpture(Serial serial) : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write( (int) 0 ); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } -} + public class StatueSouth : Item + { + [Constructible] + public StatueSouth() : base(0x139A) + { + Weight = 10; + } + + public StatueSouth(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatueSouth2 : Item + { + [Constructible] + public StatueSouth2() : base(0x1227) + { + Weight = 10; + } + + public StatueSouth2(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatueNorth : Item + { + [Constructible] + public StatueNorth() : base(0x139B) + { + Weight = 10; + } + + public StatueNorth(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatueWest : Item + { + [Constructible] + public StatueWest() : base(0x1226) + { + Weight = 10; + } + + public StatueWest(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatueEast : Item + { + [Constructible] + public StatueEast() : base(0x139C) + { + Weight = 10; + } + + public StatueEast(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatueEast2 : Item + { + [Constructible] + public StatueEast2() : base(0x1224) + { + Weight = 10; + } + + public StatueEast2(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatueSouthEast : Item + { + [Constructible] + public StatueSouthEast() : base(0x1225) + { + Weight = 10; + } + + public StatueSouthEast(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BustSouth : Item + { + [Constructible] + public BustSouth() : base(0x12CB) + { + Weight = 10; + } + + public BustSouth(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BustEast : Item + { + [Constructible] + public BustEast() : base(0x12CA) + { + Weight = 10; + } + + public BustEast(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatuePegasus : Item + { + [Constructible] + public StatuePegasus() : base(0x139D) + { + Weight = 10; + } + + public StatuePegasus(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StatuePegasus2 : Item + { + [Constructible] + public StatuePegasus2() : base(0x1228) + { + Weight = 10; + } + + public StatuePegasus2(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallTowerSculpture : Item + { + [Constructible] + public SmallTowerSculpture() : base(0x241A) + { + Weight = 20.0; + } + + public SmallTowerSculpture(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/Vase.cs b/Scripts/Items/Construction/Misc/Vase.cs index 0db651560..f0f18f05e 100644 --- a/Scripts/Items/Construction/Misc/Vase.cs +++ b/Scripts/Items/Construction/Misc/Vase.cs @@ -1,83 +1,83 @@ namespace Server.Items { - public class Vase : Item - { - [Constructible] - public Vase() : base( 0xB46 ) - { - Weight = 10; - } + public class Vase : Item + { + [Constructible] + public Vase() : base(0xB46) + { + Weight = 10; + } - public Vase( Serial serial ) : base( serial ) - { - } + public Vase(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeVase : Item - { - [Constructible] - public LargeVase() : base( 0xB45 ) - { - Weight = 15; - } + public class LargeVase : Item + { + [Constructible] + public LargeVase() : base(0xB45) + { + Weight = 15; + } - public LargeVase( Serial serial ) : base(serial) - { - } + public LargeVase(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SmallUrn : Item - { - [Constructible] - public SmallUrn() : base( 0x241C ) - { - Weight = 20.0; - } + public class SmallUrn : Item + { + [Constructible] + public SmallUrn() : base(0x241C) + { + Weight = 20.0; + } - public SmallUrn(Serial serial) : base(serial) - { - } + public SmallUrn(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Misc/Vines.cs b/Scripts/Items/Construction/Misc/Vines.cs index 65e026208..35fb6ab30 100644 --- a/Scripts/Items/Construction/Misc/Vines.cs +++ b/Scripts/Items/Construction/Misc/Vines.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class Vines : Item - { - [Constructible] - public Vines() : this( Utility.Random( 8 ) ) - { - } + public class Vines : Item + { + [Constructible] + public Vines() : this(Utility.Random(8)) + { + } - [Constructible] - public Vines( int v ) : base( 0xCEB ) - { - if ( v < 0 || v > 7 ) - v = 0; + [Constructible] + public Vines(int v) : base(0xCEB) + { + if (v < 0 || v > 7) + v = 0; - ItemID += v; - Weight = 1.0; - } + ItemID += v; + Weight = 1.0; + } - public Vines(Serial serial) : base(serial) - { - } + public Vines(Serial serial) : base(serial) + { + } - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Ruined/RuinedItemSingle.cs b/Scripts/Items/Construction/Ruined/RuinedItemSingle.cs index 739bd251f..b9a1e39c7 100644 --- a/Scripts/Items/Construction/Ruined/RuinedItemSingle.cs +++ b/Scripts/Items/Construction/Ruined/RuinedItemSingle.cs @@ -1,312 +1,307 @@ namespace Server.Items { - [FlippableAttribute( 0xC10, 0xC11 )] - public class RuinedFallenChairA : Item - { - [Constructible] - public RuinedFallenChairA() : base( 0xC10 ) - { - Movable = false; - } - - public RuinedFallenChairA( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - [FlippableAttribute( 0xC13, 0xC12 )] - public class RuinedArmoire : Item - { - [Constructible] - public RuinedArmoire() : base( 0xC13 ) - { - Movable = false; - } - - public RuinedArmoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - [FlippableAttribute( 0xC14, 0xC15 )] - public class RuinedBookcase : Item - { - [Constructible] - public RuinedBookcase() : base( 0xC14 ) - { - Movable = false; - } - - public RuinedBookcase( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - public class RuinedBooks : Item - { - [Constructible] - public RuinedBooks() : base( 0xC16 ) - { - Movable = false; - } - - public RuinedBooks( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC17, 0xC18 )] - public class CoveredChair : Item - { - [Constructible] - public CoveredChair() : base( 0xC17 ) - { - Movable = false; - } - - public CoveredChair( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - [FlippableAttribute( 0xC19, 0xC1A )] - public class RuinedFallenChairB : Item - { - [Constructible] - public RuinedFallenChairB() : base( 0xC19 ) - { - Movable = false; - } - - public RuinedFallenChairB( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - } - - [FlippableAttribute( 0xC1B, 0xC1C, 0xC1E, 0xC1D )] - public class RuinedChair : Item - { - [Constructible] - public RuinedChair() : base( 0xC1B ) - { - Movable = false; - } - - public RuinedChair( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RuinedClock : Item - { - [Constructible] - public RuinedClock() : base( 0xC1F ) - { - Movable = false; - } - - public RuinedClock( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC24, 0xC25 )] - public class RuinedDrawers : Item - { - [Constructible] - public RuinedDrawers() : base( 0xC24 ) - { - Movable = false; - } - - public RuinedDrawers( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RuinedPainting : Item - { - [Constructible] - public RuinedPainting() : base( 0xC2C ) - { - Movable = false; - } - - public RuinedPainting( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC2D, 0xC2F, 0xC2E, 0xC30 )] - public class WoodDebris : Item - { - [Constructible] - public WoodDebris() : base( 0xC2D ) - { - Movable = false; - } - - public WoodDebris( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + [Flippable(0xC10, 0xC11)] + public class RuinedFallenChairA : Item + { + [Constructible] + public RuinedFallenChairA() : base(0xC10) + { + Movable = false; + } + + public RuinedFallenChairA(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC13, 0xC12)] + public class RuinedArmoire : Item + { + [Constructible] + public RuinedArmoire() : base(0xC13) + { + Movable = false; + } + + public RuinedArmoire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC14, 0xC15)] + public class RuinedBookcase : Item + { + [Constructible] + public RuinedBookcase() : base(0xC14) + { + Movable = false; + } + + public RuinedBookcase(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RuinedBooks : Item + { + [Constructible] + public RuinedBooks() : base(0xC16) + { + Movable = false; + } + + public RuinedBooks(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC17, 0xC18)] + public class CoveredChair : Item + { + [Constructible] + public CoveredChair() : base(0xC17) + { + Movable = false; + } + + public CoveredChair(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC19, 0xC1A)] + public class RuinedFallenChairB : Item + { + [Constructible] + public RuinedFallenChairB() : base(0xC19) + { + Movable = false; + } + + public RuinedFallenChairB(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC1B, 0xC1C, 0xC1E, 0xC1D)] + public class RuinedChair : Item + { + [Constructible] + public RuinedChair() : base(0xC1B) + { + Movable = false; + } + + public RuinedChair(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RuinedClock : Item + { + [Constructible] + public RuinedClock() : base(0xC1F) + { + Movable = false; + } + + public RuinedClock(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC24, 0xC25)] + public class RuinedDrawers : Item + { + [Constructible] + public RuinedDrawers() : base(0xC24) + { + Movable = false; + } + + public RuinedDrawers(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RuinedPainting : Item + { + [Constructible] + public RuinedPainting() : base(0xC2C) + { + Movable = false; + } + + public RuinedPainting(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC2D, 0xC2F, 0xC2E, 0xC30)] + public class WoodDebris : Item + { + [Constructible] + public WoodDebris() : base(0xC2D) + { + Movable = false; + } + + public WoodDebris(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Signs/BaseSign.cs b/Scripts/Items/Construction/Signs/BaseSign.cs index 19c98cd9b..69e194137 100644 --- a/Scripts/Items/Construction/Signs/BaseSign.cs +++ b/Scripts/Items/Construction/Signs/BaseSign.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public abstract class BaseSign : Item - { - public BaseSign( int dispID ) : base( dispID ) - { - Movable = false; - } + public abstract class BaseSign : Item + { + public BaseSign(int dispID) : base(dispID) + { + Movable = false; + } - public BaseSign( Serial serial ) : base( serial ) - { - } + public BaseSign(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Signs/LocalizedSign.cs b/Scripts/Items/Construction/Signs/LocalizedSign.cs index 96c911c84..bfabffa9e 100644 --- a/Scripts/Items/Construction/Signs/LocalizedSign.cs +++ b/Scripts/Items/Construction/Signs/LocalizedSign.cs @@ -1,54 +1,61 @@ namespace Server.Items { - public class LocalizedSign : Sign - { - private int m_LabelNumber; + public class LocalizedSign : Sign + { + private int m_LabelNumber; - public override int LabelNumber => m_LabelNumber; + [Constructible] + public LocalizedSign(SignType type, SignFacing facing, int labelNumber) : base(0xB95 + 2 * (int)type + (int)facing) + { + m_LabelNumber = labelNumber; + } - [CommandProperty( AccessLevel.GameMaster )] - public int Number{ get => m_LabelNumber; - set{ m_LabelNumber = value; InvalidateProperties(); } } + [Constructible] + public LocalizedSign(int itemID, int labelNumber) : base(itemID) + { + m_LabelNumber = labelNumber; + } - [Constructible] - public LocalizedSign( SignType type, SignFacing facing, int labelNumber ) : base( ( 0xB95 + (2 * (int)type) ) + (int)facing ) - { - m_LabelNumber = labelNumber; - } + public LocalizedSign(Serial serial) : base(serial) + { + } - [Constructible] - public LocalizedSign( int itemID, int labelNumber ) : base( itemID ) - { - m_LabelNumber = labelNumber; - } + public override int LabelNumber => m_LabelNumber; - public LocalizedSign( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_LabelNumber; + set + { + m_LabelNumber = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( m_LabelNumber ); - } + writer.Write(m_LabelNumber); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Construction/Signs/Sign.cs b/Scripts/Items/Construction/Signs/Sign.cs index 059a7ec3d..876bc7dda 100644 --- a/Scripts/Items/Construction/Signs/Sign.cs +++ b/Scripts/Items/Construction/Signs/Sign.cs @@ -1,104 +1,104 @@ namespace Server.Items { - public enum SignFacing - { - North, - West - } + public enum SignFacing + { + North, + West + } - public enum SignType - { - Library, - DarkWoodenPost, - LightWoodenPost, - MetalPostC, - MetalPostB, - MetalPostA, - MetalPost, - Bakery, - Tailor, - Tinker, - Butcher, - Healer, - Mage, - Woodworker, - Customs, - Inn, - Shipwright, - Stables, - BarberShop, - Bard, - Fletcher, - Armourer, - Jeweler, - Tavern, - ReagentShop, - Blacksmith, - Painter, - Provisioner, - Bowyer, - WoodenSign, - BrassSign, - ArmamentsGuild, - ArmourersGuild, - BlacksmithsGuild, - WeaponsGuild, - BardicGuild, - BartersGuild, - ProvisionersGuild, - TradersGuild, - CooksGuild, - HealersGuild, - MagesGuild, - SorcerersGuild, - IllusionistGuild, - MinersGuild, - ArchersGuild, - SeamensGuild, - FishermensGuild, - SailorsGuild, - ShipwrightsGuild, - TailorsGuild, - ThievesGuild, - RoguesGuild, - AssassinsGuild, - TinkersGuild, - WarriorsGuild, - CavalryGuild, - FightersGuild, - MerchantsGuild, - Bank, - Theatre - } + public enum SignType + { + Library, + DarkWoodenPost, + LightWoodenPost, + MetalPostC, + MetalPostB, + MetalPostA, + MetalPost, + Bakery, + Tailor, + Tinker, + Butcher, + Healer, + Mage, + Woodworker, + Customs, + Inn, + Shipwright, + Stables, + BarberShop, + Bard, + Fletcher, + Armourer, + Jeweler, + Tavern, + ReagentShop, + Blacksmith, + Painter, + Provisioner, + Bowyer, + WoodenSign, + BrassSign, + ArmamentsGuild, + ArmourersGuild, + BlacksmithsGuild, + WeaponsGuild, + BardicGuild, + BartersGuild, + ProvisionersGuild, + TradersGuild, + CooksGuild, + HealersGuild, + MagesGuild, + SorcerersGuild, + IllusionistGuild, + MinersGuild, + ArchersGuild, + SeamensGuild, + FishermensGuild, + SailorsGuild, + ShipwrightsGuild, + TailorsGuild, + ThievesGuild, + RoguesGuild, + AssassinsGuild, + TinkersGuild, + WarriorsGuild, + CavalryGuild, + FightersGuild, + MerchantsGuild, + Bank, + Theatre + } - public class Sign : BaseSign - { - [Constructible] - public Sign( SignType type, SignFacing facing ) : base( ( 0xB95 + (2 * (int)type) ) + (int)facing ) - { - } + public class Sign : BaseSign + { + [Constructible] + public Sign(SignType type, SignFacing facing) : base(0xB95 + 2 * (int)type + (int)facing) + { + } - [Constructible] - public Sign( int itemID ) : base( itemID ) - { - } + [Constructible] + public Sign(int itemID) : base(itemID) + { + } - public Sign( Serial serial ) : base( serial ) - { - } + public Sign(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Signs/SubtextSign.cs b/Scripts/Items/Construction/Signs/SubtextSign.cs index c5a4bdddd..8ba2cd0d9 100644 --- a/Scripts/Items/Construction/Signs/SubtextSign.cs +++ b/Scripts/Items/Construction/Signs/SubtextSign.cs @@ -1,69 +1,71 @@ -using System; - namespace Server.Items { - public class SubtextSign : Sign - { - private string m_Subtext; + public class SubtextSign : Sign + { + private string m_Subtext; - [CommandProperty( AccessLevel.GameMaster )] - public string Subtext - { - get => m_Subtext; - set { m_Subtext = value; InvalidateProperties(); } - } + [Constructible] + public SubtextSign(SignType type, SignFacing facing, string subtext) + : base(type, facing) + { + m_Subtext = subtext; + } - [Constructible] - public SubtextSign( SignType type, SignFacing facing, string subtext ) - : base( type, facing ) - { - m_Subtext = subtext; - } + [Constructible] + public SubtextSign(int itemID, string subtext) + : base(itemID) + { + m_Subtext = subtext; + } - [Constructible] - public SubtextSign( int itemID, string subtext ) - : base( itemID ) - { - m_Subtext = subtext; - } + public SubtextSign(Serial serial) + : base(serial) + { + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + [CommandProperty(AccessLevel.GameMaster)] + public string Subtext + { + get => m_Subtext; + set + { + m_Subtext = value; + InvalidateProperties(); + } + } - if ( !string.IsNullOrEmpty( m_Subtext ) ) - LabelTo( from, m_Subtext ); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + if (!string.IsNullOrEmpty(m_Subtext)) + LabelTo(from, m_Subtext); + } - if ( !string.IsNullOrEmpty( m_Subtext ) ) - list.Add( m_Subtext ); - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - public SubtextSign( Serial serial ) - : base( serial ) - { - } + if (!string.IsNullOrEmpty(m_Subtext)) + list.Add(m_Subtext); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( m_Subtext ); - } + writer.Write(m_Subtext); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Subtext = reader.ReadString(); - } - } + m_Subtext = reader.ReadString(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Tables/Tables.cs b/Scripts/Items/Construction/Tables/Tables.cs index 3f21afe3f..e7fd287ec 100644 --- a/Scripts/Items/Construction/Tables/Tables.cs +++ b/Scripts/Items/Construction/Tables/Tables.cs @@ -1,157 +1,154 @@ namespace Server.Items { + [Furniture] + public class ElegantLowTable : Item + { + [Constructible] + public ElegantLowTable() : base(0x2819) + { + Weight = 1.0; + } - [Furniture] - public class ElegantLowTable : Item - { - [Constructible] - public ElegantLowTable() : base(0x2819) - { - Weight = 1.0; - } + public ElegantLowTable(Serial serial) : base(serial) + { + } - public ElegantLowTable(Serial serial) : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int) 0); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); + [Furniture] + public class PlainLowTable : Item + { + [Constructible] + public PlainLowTable() : base(0x281A) + { + Weight = 1.0; + } - } - } + public PlainLowTable(Serial serial) : base(serial) + { + } - [Furniture] - public class PlainLowTable : Item - { - [Constructible] - public PlainLowTable() : base(0x281A) - { - Weight = 1.0; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public PlainLowTable(Serial serial) : base(serial) - { - } + writer.Write(0); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write((int) 0); - } + int version = reader.ReadInt(); + } + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + [Furniture] + [Flippable(0xB90, 0xB7D)] + public class LargeTable : Item + { + [Constructible] + public LargeTable() : base(0xB90) + { + Weight = 1.0; + } - int version = reader.ReadInt(); + public LargeTable(Serial serial) : base(serial) + { + } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Furniture] - [Flippable(0xB90,0xB7D)] - public class LargeTable : Item - { - [Constructible] - public LargeTable() : base(0xB90) - { - Weight = 1.0; - } + writer.Write(0); + } - public LargeTable(Serial serial) : base(serial) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + int version = reader.ReadInt(); - writer.Write((int) 0); - } + if (Weight == 4.0) + Weight = 1.0; + } + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + [Furniture] + [Flippable(0xB35, 0xB34)] + public class Nightstand : Item + { + [Constructible] + public Nightstand() : base(0xB35) + { + Weight = 1.0; + } - int version = reader.ReadInt(); + public Nightstand(Serial serial) : base(serial) + { + } - if ( Weight == 4.0 ) - Weight = 1.0; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Furniture] - [Flippable(0xB35,0xB34)] - public class Nightstand : Item - { - [Constructible] - public Nightstand() : base(0xB35) - { - Weight = 1.0; - } + writer.Write(0); + } - public Nightstand(Serial serial) : base(serial) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + int version = reader.ReadInt(); - writer.Write((int) 0); - } + if (Weight == 4.0) + Weight = 1.0; + } + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + [Furniture] + [Flippable(0xB8F, 0xB7C)] + public class YewWoodTable : Item + { + [Constructible] + public YewWoodTable() : base(0xB8F) + { + Weight = 1.0; + } - int version = reader.ReadInt(); + public YewWoodTable(Serial serial) : base(serial) + { + } - if ( Weight == 4.0 ) - Weight = 1.0; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Furniture] - [Flippable(0xB8F,0xB7C)] - public class YewWoodTable : Item - { - [Constructible] - public YewWoodTable() : base(0xB8F) - { - Weight = 1.0; - } + writer.Write(0); + } - public YewWoodTable(Serial serial) : base(serial) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + int version = reader.ReadInt(); - writer.Write((int) 0); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - if ( Weight == 4.0 ) - Weight = 1.0; - } - } + if (Weight == 4.0) + Weight = 1.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Tables/WritingTable.cs b/Scripts/Items/Construction/Tables/WritingTable.cs index d4378c820..46d0fa91c 100644 --- a/Scripts/Items/Construction/Tables/WritingTable.cs +++ b/Scripts/Items/Construction/Tables/WritingTable.cs @@ -1,34 +1,34 @@ namespace Server.Items { - [Furniture] - [Flippable(0xB4A,0xB49, 0xB4B, 0xB4C)] - public class WritingTable : Item - { - [Constructible] - public WritingTable() : base(0xB4A) - { - Weight = 1.0; - } + [Furniture] + [Flippable(0xB4A, 0xB49, 0xB4B, 0xB4C)] + public class WritingTable : Item + { + [Constructible] + public WritingTable() : base(0xB4A) + { + Weight = 1.0; + } - public WritingTable(Serial serial) : base(serial) - { - } + public WritingTable(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 4.0 ) - Weight = 1.0; - } - } + if (Weight == 4.0) + Weight = 1.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Walls/BaseWall.cs b/Scripts/Items/Construction/Walls/BaseWall.cs index 1b66ca735..54a2c6d4d 100644 --- a/Scripts/Items/Construction/Walls/BaseWall.cs +++ b/Scripts/Items/Construction/Walls/BaseWall.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public abstract class BaseWall : Item - { - public BaseWall( int itemID ) : base( itemID ) - { - Movable = false; - } + public abstract class BaseWall : Item + { + public BaseWall(int itemID) : base(itemID) + { + Movable = false; + } - public BaseWall( Serial serial ) : base( serial ) - { - } + public BaseWall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Walls/DarkWoodWall.cs b/Scripts/Items/Construction/Walls/DarkWoodWall.cs index 4ea28a2a6..073693bee 100644 --- a/Scripts/Items/Construction/Walls/DarkWoodWall.cs +++ b/Scripts/Items/Construction/Walls/DarkWoodWall.cs @@ -1,52 +1,52 @@ namespace Server.Items { - public enum DarkWoodWallTypes - { - Corner, - SouthWall, - EastWall, - CornerPost, - EastDoorFrame, - SouthDoorFrame, - WestDoorFrame, - NorthDoorFrame, - SouthWindow, - EastWindow, - CornerMedium, - EastWallMedium, - SouthWallMedium, - CornerPostMedium, - CornerShort, - EastWallShort, - SouthWallShort, - CornerPostShort, - SouthWallVShort, - EastWallVShort - } + public enum DarkWoodWallTypes + { + Corner, + SouthWall, + EastWall, + CornerPost, + EastDoorFrame, + SouthDoorFrame, + WestDoorFrame, + NorthDoorFrame, + SouthWindow, + EastWindow, + CornerMedium, + EastWallMedium, + SouthWallMedium, + CornerPostMedium, + CornerShort, + EastWallShort, + SouthWallShort, + CornerPostShort, + SouthWallVShort, + EastWallVShort + } - public class DarkWoodWall : BaseWall - { - [Constructible] - public DarkWoodWall( DarkWoodWallTypes type ) : base( 0x0006 + (int)type ) - { - } + public class DarkWoodWall : BaseWall + { + [Constructible] + public DarkWoodWall(DarkWoodWallTypes type) : base(0x0006 + (int)type) + { + } - public DarkWoodWall( Serial serial ) : base( serial ) - { - } + public DarkWoodWall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Walls/ThickGrayStoneWall.cs b/Scripts/Items/Construction/Walls/ThickGrayStoneWall.cs index 2826d1196..c003d90ee 100644 --- a/Scripts/Items/Construction/Walls/ThickGrayStoneWall.cs +++ b/Scripts/Items/Construction/Walls/ThickGrayStoneWall.cs @@ -8,55 +8,55 @@ namespace Server.Items { - public enum ThickGrayStoneWallTypes - { - WestArch, - NorthArch, - SouthArchTop, - EastArchTop, - EastArch, - SouthArch, - Wall1, - Wall2, - Wall3, - SouthWindow, - Wall4, - EastWindow, - WestArch2, - NorthArch2, - SouthArchTop2, - EastArchTop2, - EastArch2, - SouthArch2, - SWArchEdge2, - SouthWindow2, - NEArchEdge2, - EastWindow2 - } + public enum ThickGrayStoneWallTypes + { + WestArch, + NorthArch, + SouthArchTop, + EastArchTop, + EastArch, + SouthArch, + Wall1, + Wall2, + Wall3, + SouthWindow, + Wall4, + EastWindow, + WestArch2, + NorthArch2, + SouthArchTop2, + EastArchTop2, + EastArch2, + SouthArch2, + SWArchEdge2, + SouthWindow2, + NEArchEdge2, + EastWindow2 + } - public class ThickGrayStoneWall : BaseWall - { - [Constructible] - public ThickGrayStoneWall( ThickGrayStoneWallTypes type) : base( 0x007A + (int)type ) - { - } + public class ThickGrayStoneWall : BaseWall + { + [Constructible] + public ThickGrayStoneWall(ThickGrayStoneWallTypes type) : base(0x007A + (int)type) + { + } - public ThickGrayStoneWall( Serial serial ) : base( serial ) - { - } + public ThickGrayStoneWall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Walls/ThinBrickWall.cs b/Scripts/Items/Construction/Walls/ThinBrickWall.cs index 1f59691cd..e89523e2a 100644 --- a/Scripts/Items/Construction/Walls/ThinBrickWall.cs +++ b/Scripts/Items/Construction/Walls/ThinBrickWall.cs @@ -1,68 +1,68 @@ namespace Server.Items { - public enum ThinBrickWallTypes - { - Corner, - SouthWall, - EastWall, - CornerPost, - EastDoorFrame, - SouthDoorFrame, - WestDoorFrame, - NorthDoorFrame, - SouthWindow, - EastWindow, - CornerMedium, - SouthWallMedium, - EastWallMedium, - CornerPostMedium, - CornerShort, - SouthWallShort, - EastWallShort, - CornerPostShort, - CornerArch, - SouthArch, - WestArch, - EastArch, - NorthArch, - SouthCenterArchTall, - EastCenterArchTall, - EastCornerArchTall, - SouthCornerArchTall, - SouthCornerArch, - EastCornerArch, - SouthCenterArch, - EastCenterArch, - CornerVVShort, - SouthWallVVShort, - EastWallVVShort, - SouthWallVShort, - EastWallVShort - }; + public enum ThinBrickWallTypes + { + Corner, + SouthWall, + EastWall, + CornerPost, + EastDoorFrame, + SouthDoorFrame, + WestDoorFrame, + NorthDoorFrame, + SouthWindow, + EastWindow, + CornerMedium, + SouthWallMedium, + EastWallMedium, + CornerPostMedium, + CornerShort, + SouthWallShort, + EastWallShort, + CornerPostShort, + CornerArch, + SouthArch, + WestArch, + EastArch, + NorthArch, + SouthCenterArchTall, + EastCenterArchTall, + EastCornerArchTall, + SouthCornerArchTall, + SouthCornerArch, + EastCornerArch, + SouthCenterArch, + EastCenterArch, + CornerVVShort, + SouthWallVVShort, + EastWallVVShort, + SouthWallVShort, + EastWallVShort + } - public class ThinBrickWall : BaseWall - { - [Constructible] - public ThinBrickWall( ThinBrickWallTypes type ) : base( 0x0033 + (int)type ) - { - } + public class ThinBrickWall : BaseWall + { + [Constructible] + public ThinBrickWall(ThinBrickWallTypes type) : base(0x0033 + (int)type) + { + } - public ThinBrickWall( Serial serial ) : base( serial ) - { - } + public ThinBrickWall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Walls/ThinStoneWall.cs b/Scripts/Items/Construction/Walls/ThinStoneWall.cs index eeb13aa70..aa2263087 100644 --- a/Scripts/Items/Construction/Walls/ThinStoneWall.cs +++ b/Scripts/Items/Construction/Walls/ThinStoneWall.cs @@ -1,57 +1,57 @@ namespace Server.Items { - public enum ThinStoneWallTypes - { - Corner, - EastWall, - SouthWall, - CornerPost, - EastDoorFrame, - SouthDoorFrame, - NorthDoorFrame, - WestDoorFrame, - SouthWindow, - EastWindow, - CornerMedium, - SouthWallMedium, - EastWallMedium, - CornerPostMedium, - CornerArch, - EastArch, - SouthArch, - NorthArch, - WestArch, - CornerShort, - EastWallShort, - SouthWallShort, - CornerPostShort, - SouthWallShort2, - EastWallShort2 - } + public enum ThinStoneWallTypes + { + Corner, + EastWall, + SouthWall, + CornerPost, + EastDoorFrame, + SouthDoorFrame, + NorthDoorFrame, + WestDoorFrame, + SouthWindow, + EastWindow, + CornerMedium, + SouthWallMedium, + EastWallMedium, + CornerPostMedium, + CornerArch, + EastArch, + SouthArch, + NorthArch, + WestArch, + CornerShort, + EastWallShort, + SouthWallShort, + CornerPostShort, + SouthWallShort2, + EastWallShort2 + } - public class ThinStoneWall : BaseWall - { - [Constructible] - public ThinStoneWall( ThinStoneWallTypes type ) : base( 0x001A + (int)type ) - { - } + public class ThinStoneWall : BaseWall + { + [Constructible] + public ThinStoneWall(ThinStoneWallTypes type) : base(0x001A + (int)type) + { + } - public ThinStoneWall( Serial serial ) : base( serial ) - { - } + public ThinStoneWall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Construction/Walls/WhiteStoneWall.cs b/Scripts/Items/Construction/Walls/WhiteStoneWall.cs index 1093ba647..0bfdc9ea2 100644 --- a/Scripts/Items/Construction/Walls/WhiteStoneWall.cs +++ b/Scripts/Items/Construction/Walls/WhiteStoneWall.cs @@ -8,68 +8,68 @@ namespace Server.Items { - public enum WhiteStoneWallTypes - { - EastWall, - SouthWall, - SECorner, - NWCornerPost, - EastArrowLoop, - SouthArrowLoop, - EastWindow, - SouthWindow, - SouthWallMedium, - EastWallMedium, - SECornerMedium, - NWCornerPostMedium, - SouthWallShort, - EastWallShort, - SECornerShort, - NWCornerPostShort, - NECornerPostShort, - SWCornerPostShort, - SouthWallVShort, - EastWallVShort, - SECornerVShort, - NWCornerPostVShort, - SECornerArch, - SouthArch, - WestArch, - EastArch, - NorthArch, - EastBattlement, - SECornerBattlement, - SouthBattlement, - NECornerBattlement, - SWCornerBattlement, - Column, - SouthWallVVShort, - EastWallVVShort - } + public enum WhiteStoneWallTypes + { + EastWall, + SouthWall, + SECorner, + NWCornerPost, + EastArrowLoop, + SouthArrowLoop, + EastWindow, + SouthWindow, + SouthWallMedium, + EastWallMedium, + SECornerMedium, + NWCornerPostMedium, + SouthWallShort, + EastWallShort, + SECornerShort, + NWCornerPostShort, + NECornerPostShort, + SWCornerPostShort, + SouthWallVShort, + EastWallVShort, + SECornerVShort, + NWCornerPostVShort, + SECornerArch, + SouthArch, + WestArch, + EastArch, + NorthArch, + EastBattlement, + SECornerBattlement, + SouthBattlement, + NECornerBattlement, + SWCornerBattlement, + Column, + SouthWallVVShort, + EastWallVVShort + } - public class WhiteStoneWall : BaseWall - { - [Constructible] - public WhiteStoneWall( WhiteStoneWallTypes type) : base( 0x0057 + (int)type ) - { - } + public class WhiteStoneWall : BaseWall + { + [Constructible] + public WhiteStoneWall(WhiteStoneWallTypes type) : base(0x0057 + (int)type) + { + } - public WhiteStoneWall( Serial serial ) : base( serial ) - { - } + public WhiteStoneWall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Containers/BaseTreasureChest.cs b/Scripts/Items/Containers/BaseTreasureChest.cs index 3899d1cee..7c68fbb69 100644 --- a/Scripts/Items/Containers/BaseTreasureChest.cs +++ b/Scripts/Items/Containers/BaseTreasureChest.cs @@ -2,214 +2,214 @@ using System; namespace Server.Items { - public class BaseTreasureChest : LockableContainer - { - private TreasureResetTimer m_ResetTimer; + public class BaseTreasureChest : LockableContainer + { + public enum TreasureLevel + { + Level1, + Level2, + Level3, + Level4, + Level5, + Level6 + } - [CommandProperty( AccessLevel.GameMaster )] - public TreasureLevel Level { get; set; } + private TreasureResetTimer m_ResetTimer; - [CommandProperty( AccessLevel.GameMaster )] - public short MaxSpawnTime { get; set; } = 60; + public BaseTreasureChest(int itemID) : this(itemID, TreasureLevel.Level2) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public short MinSpawnTime { get; set; } = 10; + public BaseTreasureChest(int itemID, TreasureLevel level) : base(itemID) + { + Level = level; + Locked = true; + Movable = false; - [CommandProperty( AccessLevel.GameMaster )] - public override bool Locked { - get => base.Locked; - set { - if ( base.Locked != value ) { - base.Locked = value; + SetLockLevel(); + GenerateTreasure(); + } - if ( !value ) - StartResetTimer(); - } - } - } + public BaseTreasureChest(Serial serial) : base(serial) + { + } - public override bool IsDecoContainer => false; + [CommandProperty(AccessLevel.GameMaster)] + public TreasureLevel Level{ get; set; } - public BaseTreasureChest( int itemID ) : this( itemID, TreasureLevel.Level2 ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public short MaxSpawnTime{ get; set; } = 60; - public BaseTreasureChest( int itemID, TreasureLevel level ) : base( itemID ) - { - Level = level; - Locked = true; - Movable = false; + [CommandProperty(AccessLevel.GameMaster)] + public short MinSpawnTime{ get; set; } = 10; - SetLockLevel(); - GenerateTreasure(); - } + [CommandProperty(AccessLevel.GameMaster)] + public override bool Locked + { + get => base.Locked; + set + { + if (base.Locked != value) + { + base.Locked = value; - public BaseTreasureChest( Serial serial ) : base( serial ) - { - } + if (!value) + StartResetTimer(); + } + } + } - public override string DefaultName - { - get - { - if ( Locked ) - return "a locked treasure chest"; + public override bool IsDecoContainer => false; - return "a treasure chest"; - } - } + public override string DefaultName + { + get + { + if (Locked) + return "a locked treasure chest"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return "a treasure chest"; + } + } - writer.Write( (int) 0 ); - writer.Write( (byte) Level ); - writer.Write( MinSpawnTime ); - writer.Write( MaxSpawnTime ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); + writer.Write((byte)Level); + writer.Write(MinSpawnTime); + writer.Write(MaxSpawnTime); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Level = (TreasureLevel)reader.ReadByte(); - MinSpawnTime = reader.ReadShort(); - MaxSpawnTime = reader.ReadShort(); + int version = reader.ReadInt(); - if ( !Locked ) - StartResetTimer(); - } + Level = (TreasureLevel)reader.ReadByte(); + MinSpawnTime = reader.ReadShort(); + MaxSpawnTime = reader.ReadShort(); - protected virtual void SetLockLevel() - { - switch( Level ) - { - case TreasureLevel.Level1: - RequiredSkill = LockLevel = 5; - break; + if (!Locked) + StartResetTimer(); + } - case TreasureLevel.Level2: - RequiredSkill = LockLevel = 20; - break; + protected virtual void SetLockLevel() + { + switch (Level) + { + case TreasureLevel.Level1: + RequiredSkill = LockLevel = 5; + break; - case TreasureLevel.Level3: - RequiredSkill = LockLevel = 50; - break; + case TreasureLevel.Level2: + RequiredSkill = LockLevel = 20; + break; - case TreasureLevel.Level4: - RequiredSkill = LockLevel = 70; - break; + case TreasureLevel.Level3: + RequiredSkill = LockLevel = 50; + break; - case TreasureLevel.Level5: - RequiredSkill = LockLevel = 90; - break; + case TreasureLevel.Level4: + RequiredSkill = LockLevel = 70; + break; - case TreasureLevel.Level6: - RequiredSkill = LockLevel = 100; - break; - } - } + case TreasureLevel.Level5: + RequiredSkill = LockLevel = 90; + break; - private void StartResetTimer() - { - if ( m_ResetTimer == null ) - m_ResetTimer = new TreasureResetTimer( this ); - else - m_ResetTimer.Delay = TimeSpan.FromMinutes( Utility.Random( MinSpawnTime, MaxSpawnTime )); + case TreasureLevel.Level6: + RequiredSkill = LockLevel = 100; + break; + } + } - m_ResetTimer.Start(); - } + private void StartResetTimer() + { + if (m_ResetTimer == null) + m_ResetTimer = new TreasureResetTimer(this); + else + m_ResetTimer.Delay = TimeSpan.FromMinutes(Utility.Random(MinSpawnTime, MaxSpawnTime)); - protected virtual void GenerateTreasure() - { - int MinGold = 1; - int MaxGold = 2; + m_ResetTimer.Start(); + } - switch( Level ) - { - case TreasureLevel.Level1: - MinGold = 100; - MaxGold = 300; - break; + protected virtual void GenerateTreasure() + { + int MinGold = 1; + int MaxGold = 2; - case TreasureLevel.Level2: - MinGold = 300; - MaxGold = 600; - break; + switch (Level) + { + case TreasureLevel.Level1: + MinGold = 100; + MaxGold = 300; + break; - case TreasureLevel.Level3: - MinGold = 600; - MaxGold = 900; - break; + case TreasureLevel.Level2: + MinGold = 300; + MaxGold = 600; + break; - case TreasureLevel.Level4: - MinGold = 900; - MaxGold = 1200; - break; + case TreasureLevel.Level3: + MinGold = 600; + MaxGold = 900; + break; - case TreasureLevel.Level5: - MinGold = 1200; - MaxGold = 5000; - break; + case TreasureLevel.Level4: + MinGold = 900; + MaxGold = 1200; + break; - case TreasureLevel.Level6: - MinGold = 5000; - MaxGold = 9000; - break; - } + case TreasureLevel.Level5: + MinGold = 1200; + MaxGold = 5000; + break; - DropItem( new Gold( MinGold, MaxGold ) ); - } + case TreasureLevel.Level6: + MinGold = 5000; + MaxGold = 9000; + break; + } - public void ClearContents() - { - for ( int i = Items.Count - 1; i >= 0; --i ) - { - if ( i < Items.Count ) - Items[i].Delete(); - } - } + DropItem(new Gold(MinGold, MaxGold)); + } - public void Reset() - { - if ( m_ResetTimer != null ) - { - if ( m_ResetTimer.Running ) - m_ResetTimer.Stop(); - } + public void ClearContents() + { + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + Items[i].Delete(); + } - Locked = true; - ClearContents(); - GenerateTreasure(); - } + public void Reset() + { + if (m_ResetTimer != null) + if (m_ResetTimer.Running) + m_ResetTimer.Stop(); - public enum TreasureLevel - { - Level1, - Level2, - Level3, - Level4, - Level5, - Level6, - }; + Locked = true; + ClearContents(); + GenerateTreasure(); + } - private class TreasureResetTimer : Timer - { - private BaseTreasureChest m_Chest; + private class TreasureResetTimer : Timer + { + private BaseTreasureChest m_Chest; - public TreasureResetTimer( BaseTreasureChest chest ) : base ( TimeSpan.FromMinutes( Utility.Random( chest.MinSpawnTime, chest.MaxSpawnTime ) ) ) - { - m_Chest = chest; - Priority = TimerPriority.OneMinute; - } + public TreasureResetTimer(BaseTreasureChest chest) : base( + TimeSpan.FromMinutes(Utility.Random(chest.MinSpawnTime, chest.MaxSpawnTime))) + { + m_Chest = chest; + Priority = TimerPriority.OneMinute; + } - protected override void OnTick() - { - m_Chest.Reset(); - } - } - } -} + protected override void OnTick() + { + m_Chest.Reset(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/Container.cs b/Scripts/Items/Containers/Container.cs index 3a21dfbdf..faf1b2f0c 100644 --- a/Scripts/Items/Containers/Container.cs +++ b/Scripts/Items/Containers/Container.cs @@ -1,984 +1,989 @@ using System.Collections.Generic; -using Server.Multis; -using Server.Mobiles; -using Server.Network; using Server.ContextMenus; +using Server.Mobiles; +using Server.Multis; +using Server.Network; namespace Server.Items { - public abstract class BaseContainer : Container - { - public override int DefaultMaxWeight - { - get - { - if ( IsSecure ) - return 0; - - return base.DefaultMaxWeight; - } - } - - public BaseContainer( int itemID ) : base( itemID ) - { - } - - public override bool IsAccessibleTo( Mobile m ) - { - if ( !BaseHouse.CheckAccessible( m, this ) ) - return false; - - return base.IsAccessibleTo( m ); - } - - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if ( IsSecure && !BaseHouse.CheckHold( m, this, item, message, checkItems, plusItems, plusWeight ) ) - return false; - - return base.CheckHold( m, item, message, checkItems, plusItems, plusWeight ); - } - - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( IsDecoContainer && item is BaseBook ) - return true; - - return base.CheckItemUse( from, item ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } - - public override bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage ) - { - if ( !CheckHold( from, dropped, sendFullMessage, true ) ) - return false; - - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house?.IsLockedDown( this ) == true ) - { - if ( dropped is VendorRentalContract || ( dropped is Container container && container.FindItemByType( typeof( VendorRentalContract ) ) != null ) ) - { - from.SendLocalizedMessage( 1062492 ); // You cannot place a rental contract in a locked down container. - return false; - } - - if ( !house.LockDown( from, dropped, false ) ) - return false; - } - - List list = Items; - - for ( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; - - if ( !(item is Container) && item.StackWith( from, dropped, false ) ) - return true; - } - - DropItem( dropped ); - - return true; - } - - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( !CheckHold( from, item, true, true ) ) - return false; - - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house?.IsLockedDown( this ) == true ) - { - if ( item is VendorRentalContract || ( item is Container container && container.FindItemByType( typeof( VendorRentalContract ) ) != null ) ) - { - from.SendLocalizedMessage( 1062492 ); // You cannot place a rental contract in a locked down container. - return false; - } - - if ( !house.LockDown( from, item, false ) ) - return false; - } - - item.Location = new Point3D( p.X, p.Y, 0 ); - AddItem( item ); - - from.SendSound( GetDroppedSound( item ), GetWorldLocation() ); - - return true; - } - - public override void UpdateTotal( Item sender, TotalType type, int delta ) - { - base.UpdateTotal( sender, type, delta ); - - if ( type == TotalType.Weight ) - (RootParent as Mobile)?.InvalidateProperties(); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel > AccessLevel.Player || from.InRange( GetWorldLocation(), 2 ) || RootParent is PlayerVendor ) - Open( from ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - - public virtual void Open( Mobile from ) - { - DisplayTo( from ); - } - - public BaseContainer( Serial serial ) : base( serial ) - { - } - - /* Note: base class insertion; we cannot serialize anything here */ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - } - } - - public class CreatureBackpack : Backpack //Used on BaseCreature - { - [Constructible] - public CreatureBackpack( string name ) - { - Name = name; - Layer = Layer.Backpack; - Hue = 5; - Weight = 3.0; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( Name != null ) - list.Add( 1075257, Name ); // Contents of ~1_PETNAME~'s pack. - else - base.AddNameProperty( list ); - } - - public override void OnItemRemoved( Item item ) - { - if ( Items.Count == 0 ) - Delete(); - - base.OnItemRemoved( item ); - } - - public override bool OnDragLift( Mobile from ) - { - if ( from.AccessLevel > AccessLevel.Player ) - return true; - - from.SendLocalizedMessage( 500169 ); // You cannot pick that up. - return false; - } - - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - return false; - } - - public override bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage ) - { - return false; - } - - public CreatureBackpack( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 ) - Weight = 13.0; - } - } - - public class StrongBackpack : Backpack //Used on Pack animals - { - [Constructible] - public StrongBackpack() - { - Layer = Layer.Backpack; - Weight = 13.0; - } - - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - return base.CheckHold( m, item, false, checkItems, plusItems, plusWeight ); - } - - public override int DefaultMaxWeight => 1600; - - public override bool CheckContentDisplay( Mobile from ) - { - return RootParent is BaseCreature creature && creature.Controlled && creature.ControlMaster == from || base.CheckContentDisplay( from ); - } - - public StrongBackpack( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 ) - Weight = 13.0; - } - } - - public class Backpack : BaseContainer, IDyable - { - [Constructible] - public Backpack() : base( 0xE75 ) - { - Layer = Layer.Backpack; - Weight = 3.0; - } - - public override int DefaultMaxWeight { - get { - if ( Core.ML && Parent is Mobile m && m.Player && m.Backpack == this ) - return 550; - - return base.DefaultMaxWeight; - } - } - - public Backpack( Serial serial ) : base( serial ) - { - } - - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) return false; - - Hue = sender.DyedHue; - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && ItemID == 0x9B2 ) - ItemID = 0xE75; - } - } - - public class Pouch : TrappableContainer - { - [Constructible] - public Pouch() : base( 0xE79 ) - { - Weight = 1.0; - } - - public Pouch( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public abstract class BaseBagBall : BaseContainer, IDyable - { - public BaseBagBall( int itemID ) : base( itemID ) - { - Weight = 1.0; - } - - public BaseBagBall( Serial serial ) : base( serial ) - { - } - - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; - - Hue = sender.DyedHue; - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallBagBall : BaseBagBall - { - [Constructible] - public SmallBagBall() : base( 0x2256 ) - { - } - - public SmallBagBall( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LargeBagBall : BaseBagBall - { - [Constructible] - public LargeBagBall() : base( 0x2257 ) - { - } - - public LargeBagBall( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Bag : BaseContainer, IDyable - { - [Constructible] - public Bag() : base( 0xE76 ) - { - Weight = 2.0; - } - - public Bag( Serial serial ) : base( serial ) - { - } - - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) return false; - - Hue = sender.DyedHue; - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Barrel : BaseContainer - { - [Constructible] - public Barrel() : base( 0xE77 ) - { - Weight = 25.0; - } - - public Barrel( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 0.0 ) - Weight = 25.0; - } - } - - public class Keg : BaseContainer - { - [Constructible] - public Keg() : base( 0xE7F ) - { - Weight = 15.0; - } - - public Keg( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PicnicBasket : BaseContainer - { - [Constructible] - public PicnicBasket() : base( 0xE7A ) - { - Weight = 2.0; // Stratics doesn't know weight - } - - public PicnicBasket( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Basket : BaseContainer - { - [Constructible] - public Basket() : base( 0x990 ) - { - Weight = 1.0; // Stratics doesn't know weight - } - - public Basket( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0x9AA, 0xE7D )] - public class WoodenBox : LockableContainer - { - [Constructible] - public WoodenBox() : base( 0x9AA ) - { - Weight = 4.0; - } - - public WoodenBox( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0x9A9, 0xE7E )] - public class SmallCrate : LockableContainer - { - [Constructible] - public SmallCrate() : base( 0x9A9 ) - { - Weight = 2.0; - } - - public SmallCrate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 4.0 ) - Weight = 2.0; - } - } - - [Furniture] - [Flippable( 0xE3F, 0xE3E )] - public class MediumCrate : LockableContainer - { - [Constructible] - public MediumCrate() : base( 0xE3F ) - { - Weight = 2.0; - } - - public MediumCrate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 6.0 ) - Weight = 2.0; - } - } - - [Furniture] - [Flippable( 0xE3D, 0xE3C )] - public class LargeCrate : LockableContainer - { - [Constructible] - public LargeCrate() : base( 0xE3D ) - { - Weight = 1.0; - } - - public LargeCrate( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 8.0 ) - Weight = 1.0; - } - } - - [DynamicFliping] - [Flippable( 0x9A8, 0xE80 )] - public class MetalBox : LockableContainer - { - [Constructible] - public MetalBox() : base( 0x9A8 ) - { - } - - public MetalBox( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 3 ) - Weight = -1; - } - } - - [DynamicFliping] - [Flippable( 0x9AB, 0xE7C )] - public class MetalChest : LockableContainer - { - [Constructible] - public MetalChest() : base( 0x9AB ) - { - } - - public MetalChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 25 ) - Weight = -1; - } - } - - [DynamicFliping] - [Flippable( 0xE41, 0xE40 )] - public class MetalGoldenChest : LockableContainer - { - [Constructible] - public MetalGoldenChest() : base( 0xE41 ) - { - } - - public MetalGoldenChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 25 ) - Weight = -1; - } - } - - [Furniture] - [Flippable( 0xe43, 0xe42 )] - public class WoodenChest : LockableContainer - { - [Constructible] - public WoodenChest() : base( 0xe43 ) - { - Weight = 2.0; - } - - public WoodenChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 15.0 ) - Weight = 2.0; - } - } - - [Furniture] - [Flippable( 0x280B, 0x280C )] - public class PlainWoodenChest : LockableContainer - { - [Constructible] - public PlainWoodenChest() : base( 0x280B ) - { - } - - public PlainWoodenChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 15 ) - Weight = -1; - } - } - - [Furniture] - [Flippable( 0x280D, 0x280E )] - public class OrnateWoodenChest : LockableContainer - { - [Constructible] - public OrnateWoodenChest() : base( 0x280D ) - { - } - - public OrnateWoodenChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 15 ) - Weight = -1; - } - } - - [Furniture] - [Flippable( 0x280F, 0x2810 )] - public class GildedWoodenChest : LockableContainer - { - [Constructible] - public GildedWoodenChest() : base( 0x280F ) - { - } - - public GildedWoodenChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 15 ) - Weight = -1; - } - } - - [Furniture] - [Flippable( 0x2811, 0x2812 )] - public class WoodenFootLocker : LockableContainer - { - [Constructible] - public WoodenFootLocker() : base( 0x2811 ) - { - GumpID = 0x10B; - } - - public WoodenFootLocker( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 15 ) - Weight = -1; - - if ( version < 2 ) - GumpID = 0x10B; - } - } - - [Furniture] - [Flippable( 0x2813, 0x2814 )] - public class FinishedWoodenChest : LockableContainer - { - [Constructible] - public FinishedWoodenChest() : base( 0x2813 ) - { - } - - public FinishedWoodenChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 15 ) - Weight = -1; - } - } -} + public abstract class BaseContainer : Container + { + public BaseContainer(int itemID) : base(itemID) + { + } + + public BaseContainer(Serial serial) : base(serial) + { + } + + public override int DefaultMaxWeight + { + get + { + if (IsSecure) + return 0; + + return base.DefaultMaxWeight; + } + } + + public override bool IsAccessibleTo(Mobile m) + { + if (!BaseHouse.CheckAccessible(m, this)) + return false; + + return base.IsAccessibleTo(m); + } + + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (IsSecure && !BaseHouse.CheckHold(m, this, item, message, checkItems, plusItems, plusWeight)) + return false; + + return base.CheckHold(m, item, message, checkItems, plusItems, plusWeight); + } + + public override bool CheckItemUse(Mobile from, Item item) + { + if (IsDecoContainer && item is BaseBook) + return true; + + return base.CheckItemUse(from, item); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } + + public override bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage) + { + if (!CheckHold(from, dropped, sendFullMessage, true)) + return false; + + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house?.IsLockedDown(this) == true) + { + if (dropped is VendorRentalContract || dropped is Container container && + container.FindItemByType(typeof(VendorRentalContract)) != null) + { + from.SendLocalizedMessage(1062492); // You cannot place a rental contract in a locked down container. + return false; + } + + if (!house.LockDown(from, dropped, false)) + return false; + } + + List list = Items; + + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; + + if (!(item is Container) && item.StackWith(from, dropped, false)) + return true; + } + + DropItem(dropped); + + return true; + } + + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (!CheckHold(from, item, true, true)) + return false; + + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house?.IsLockedDown(this) == true) + { + if (item is VendorRentalContract || item is Container container && + container.FindItemByType(typeof(VendorRentalContract)) != null) + { + from.SendLocalizedMessage(1062492); // You cannot place a rental contract in a locked down container. + return false; + } + + if (!house.LockDown(from, item, false)) + return false; + } + + item.Location = new Point3D(p.X, p.Y, 0); + AddItem(item); + + from.SendSound(GetDroppedSound(item), GetWorldLocation()); + + return true; + } + + public override void UpdateTotal(Item sender, TotalType type, int delta) + { + base.UpdateTotal(sender, type, delta); + + if (type == TotalType.Weight) + (RootParent as Mobile)?.InvalidateProperties(); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel > AccessLevel.Player || from.InRange(GetWorldLocation(), 2) || RootParent is PlayerVendor) + Open(from); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + + public virtual void Open(Mobile from) + { + DisplayTo(from); + } + + /* Note: base class insertion; we cannot serialize anything here */ + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + } + } + + public class CreatureBackpack : Backpack //Used on BaseCreature + { + [Constructible] + public CreatureBackpack(string name) + { + Name = name; + Layer = Layer.Backpack; + Hue = 5; + Weight = 3.0; + } + + public CreatureBackpack(Serial serial) : base(serial) + { + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (Name != null) + list.Add(1075257, Name); // Contents of ~1_PETNAME~'s pack. + else + base.AddNameProperty(list); + } + + public override void OnItemRemoved(Item item) + { + if (Items.Count == 0) + Delete(); + + base.OnItemRemoved(item); + } + + public override bool OnDragLift(Mobile from) + { + if (from.AccessLevel > AccessLevel.Player) + return true; + + from.SendLocalizedMessage(500169); // You cannot pick that up. + return false; + } + + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + return false; + } + + public override bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage) + { + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0) + Weight = 13.0; + } + } + + public class StrongBackpack : Backpack //Used on Pack animals + { + [Constructible] + public StrongBackpack() + { + Layer = Layer.Backpack; + Weight = 13.0; + } + + public StrongBackpack(Serial serial) : base(serial) + { + } + + public override int DefaultMaxWeight => 1600; + + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + return base.CheckHold(m, item, false, checkItems, plusItems, plusWeight); + } + + public override bool CheckContentDisplay(Mobile from) + { + return RootParent is BaseCreature creature && creature.Controlled && creature.ControlMaster == from || + base.CheckContentDisplay(from); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0) + Weight = 13.0; + } + } + + public class Backpack : BaseContainer, IDyable + { + [Constructible] + public Backpack() : base(0xE75) + { + Layer = Layer.Backpack; + Weight = 3.0; + } + + public Backpack(Serial serial) : base(serial) + { + } + + public override int DefaultMaxWeight + { + get + { + if (Core.ML && Parent is Mobile m && m.Player && m.Backpack == this) + return 550; + + return base.DefaultMaxWeight; + } + } + + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) return false; + + Hue = sender.DyedHue; + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && ItemID == 0x9B2) + ItemID = 0xE75; + } + } + + public class Pouch : TrappableContainer + { + [Constructible] + public Pouch() : base(0xE79) + { + Weight = 1.0; + } + + public Pouch(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public abstract class BaseBagBall : BaseContainer, IDyable + { + public BaseBagBall(int itemID) : base(itemID) + { + Weight = 1.0; + } + + public BaseBagBall(Serial serial) : base(serial) + { + } + + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; + + Hue = sender.DyedHue; + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallBagBall : BaseBagBall + { + [Constructible] + public SmallBagBall() : base(0x2256) + { + } + + public SmallBagBall(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LargeBagBall : BaseBagBall + { + [Constructible] + public LargeBagBall() : base(0x2257) + { + } + + public LargeBagBall(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Bag : BaseContainer, IDyable + { + [Constructible] + public Bag() : base(0xE76) + { + Weight = 2.0; + } + + public Bag(Serial serial) : base(serial) + { + } + + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) return false; + + Hue = sender.DyedHue; + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Barrel : BaseContainer + { + [Constructible] + public Barrel() : base(0xE77) + { + Weight = 25.0; + } + + public Barrel(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 0.0) + Weight = 25.0; + } + } + + public class Keg : BaseContainer + { + [Constructible] + public Keg() : base(0xE7F) + { + Weight = 15.0; + } + + public Keg(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PicnicBasket : BaseContainer + { + [Constructible] + public PicnicBasket() : base(0xE7A) + { + Weight = 2.0; // Stratics doesn't know weight + } + + public PicnicBasket(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Basket : BaseContainer + { + [Constructible] + public Basket() : base(0x990) + { + Weight = 1.0; // Stratics doesn't know weight + } + + public Basket(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0x9AA, 0xE7D)] + public class WoodenBox : LockableContainer + { + [Constructible] + public WoodenBox() : base(0x9AA) + { + Weight = 4.0; + } + + public WoodenBox(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0x9A9, 0xE7E)] + public class SmallCrate : LockableContainer + { + [Constructible] + public SmallCrate() : base(0x9A9) + { + Weight = 2.0; + } + + public SmallCrate(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 4.0) + Weight = 2.0; + } + } + + [Furniture] + [Flippable(0xE3F, 0xE3E)] + public class MediumCrate : LockableContainer + { + [Constructible] + public MediumCrate() : base(0xE3F) + { + Weight = 2.0; + } + + public MediumCrate(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 6.0) + Weight = 2.0; + } + } + + [Furniture] + [Flippable(0xE3D, 0xE3C)] + public class LargeCrate : LockableContainer + { + [Constructible] + public LargeCrate() : base(0xE3D) + { + Weight = 1.0; + } + + public LargeCrate(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 8.0) + Weight = 1.0; + } + } + + [DynamicFliping] + [Flippable(0x9A8, 0xE80)] + public class MetalBox : LockableContainer + { + [Constructible] + public MetalBox() : base(0x9A8) + { + } + + public MetalBox(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 3) + Weight = -1; + } + } + + [DynamicFliping] + [Flippable(0x9AB, 0xE7C)] + public class MetalChest : LockableContainer + { + [Constructible] + public MetalChest() : base(0x9AB) + { + } + + public MetalChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 25) + Weight = -1; + } + } + + [DynamicFliping] + [Flippable(0xE41, 0xE40)] + public class MetalGoldenChest : LockableContainer + { + [Constructible] + public MetalGoldenChest() : base(0xE41) + { + } + + public MetalGoldenChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 25) + Weight = -1; + } + } + + [Furniture] + [Flippable(0xe43, 0xe42)] + public class WoodenChest : LockableContainer + { + [Constructible] + public WoodenChest() : base(0xe43) + { + Weight = 2.0; + } + + public WoodenChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 15.0) + Weight = 2.0; + } + } + + [Furniture] + [Flippable(0x280B, 0x280C)] + public class PlainWoodenChest : LockableContainer + { + [Constructible] + public PlainWoodenChest() : base(0x280B) + { + } + + public PlainWoodenChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 15) + Weight = -1; + } + } + + [Furniture] + [Flippable(0x280D, 0x280E)] + public class OrnateWoodenChest : LockableContainer + { + [Constructible] + public OrnateWoodenChest() : base(0x280D) + { + } + + public OrnateWoodenChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 15) + Weight = -1; + } + } + + [Furniture] + [Flippable(0x280F, 0x2810)] + public class GildedWoodenChest : LockableContainer + { + [Constructible] + public GildedWoodenChest() : base(0x280F) + { + } + + public GildedWoodenChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 15) + Weight = -1; + } + } + + [Furniture] + [Flippable(0x2811, 0x2812)] + public class WoodenFootLocker : LockableContainer + { + [Constructible] + public WoodenFootLocker() : base(0x2811) + { + GumpID = 0x10B; + } + + public WoodenFootLocker(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 15) + Weight = -1; + + if (version < 2) + GumpID = 0x10B; + } + } + + [Furniture] + [Flippable(0x2813, 0x2814)] + public class FinishedWoodenChest : LockableContainer + { + [Constructible] + public FinishedWoodenChest() : base(0x2813) + { + } + + public FinishedWoodenChest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 15) + Weight = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/FillableContainers.cs b/Scripts/Items/Containers/FillableContainers.cs index 57321144f..aaad7efc9 100644 --- a/Scripts/Items/Containers/FillableContainers.cs +++ b/Scripts/Items/Containers/FillableContainers.cs @@ -5,1516 +5,1538 @@ using Server.Mobiles; namespace Server.Items { - public abstract class FillableContainer : LockableContainer - { - public virtual int MinRespawnMinutes => 60; - public virtual int MaxRespawnMinutes => 90; - - public virtual bool IsLockable => true; - public virtual bool IsTrappable => IsLockable; - - public virtual int SpawnThreshold => 2; - - protected FillableContent m_Content; - - protected DateTime m_NextRespawnTime; - protected Timer m_RespawnTimer; - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextRespawnTime => m_NextRespawnTime; - - [CommandProperty( AccessLevel.GameMaster )] - public FillableContentType ContentType - { - get => FillableContent.Lookup( m_Content ); - set => Content = FillableContent.Lookup( value ); - } - - public FillableContent Content - { - get => m_Content; - set - { - if ( m_Content == value ) - return; - - m_Content = value; - - for( int i = Items.Count - 1; i >= 0; --i ) - { - if ( i < Items.Count ) - Items[ i ].Delete(); - } - - Respawn(); - } - } - - public FillableContainer( int itemID ) - : base( itemID ) - { - Movable = false; - } - - public override void OnMapChange() - { - base.OnMapChange(); - AcquireContent(); - } - - public override void OnLocationChange( Point3D oldLocation ) - { - base.OnLocationChange( oldLocation ); - AcquireContent(); - } - - public virtual void AcquireContent() - { - if ( m_Content != null ) - return; - - m_Content = FillableContent.Acquire( GetWorldLocation(), Map ); - - if ( m_Content != null ) - Respawn(); - } - - public override void OnItemRemoved( Item item ) - { - CheckRespawn(); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - if ( m_RespawnTimer != null ) - { - m_RespawnTimer.Stop(); - m_RespawnTimer = null; - } - } - - public int GetItemsCount() - { - int count = 0; - - foreach( Item item in Items ) - { - count += item.Amount; - } - - return count; - } - - public void CheckRespawn() - { - bool canSpawn = ( m_Content != null && !Deleted && GetItemsCount() <= SpawnThreshold && !Movable && Parent == null && !IsLockedDown && !IsSecure ); - - if ( canSpawn ) - { - if ( m_RespawnTimer == null ) - { - int mins = Utility.RandomMinMax( MinRespawnMinutes, MaxRespawnMinutes ); - TimeSpan delay = TimeSpan.FromMinutes( mins ); - - m_NextRespawnTime = DateTime.UtcNow + delay; - m_RespawnTimer = Timer.DelayCall( delay, Respawn ); - } - } - else if ( m_RespawnTimer != null ) - { - m_RespawnTimer.Stop(); - m_RespawnTimer = null; - } - } - - public void Respawn() - { - if ( m_RespawnTimer != null ) - { - m_RespawnTimer.Stop(); - m_RespawnTimer = null; - } - - if ( m_Content == null || Deleted ) - return; - - GenerateContent(); - - if ( IsLockable ) - { - Locked = true; - - int difficulty = ( m_Content.Level - 1 ) * 30; - - LockLevel = difficulty - 10; - MaxLockLevel = difficulty + 30; - RequiredSkill = difficulty; - } - - if ( IsTrappable && ( m_Content.Level > 1 || 4 > Utility.Random( 5 ) ) ) - { - if ( m_Content.Level > Utility.Random( 5 ) ) - TrapType = TrapType.PoisonTrap; - else - TrapType = TrapType.ExplosionTrap; - - TrapPower = m_Content.Level * Utility.RandomMinMax( 10, 30 ); - TrapLevel = m_Content.Level; - } - else - { - TrapType = TrapType.None; - TrapPower = 0; - TrapLevel = 0; - } - - CheckRespawn(); - } - - protected virtual int GetSpawnCount() - { - int itemsCount = GetItemsCount(); - - if ( itemsCount > SpawnThreshold ) - return 0; - - int maxSpawnCount = ( 1 + SpawnThreshold - itemsCount ) * 2; - - return Utility.RandomMinMax( 0, maxSpawnCount ); - } - - public virtual void GenerateContent() - { - if ( m_Content == null || Deleted ) - return; - - int toSpawn = GetSpawnCount(); - - for( int i = 0; i < toSpawn; ++i ) - { - Item item = m_Content.Construct(); - - if ( item != null ) - { - List list = Items; - - for( int j = 0; j < list.Count; ++j ) - { - Item subItem = list[ j ]; - - if ( !( subItem is Container ) && subItem.StackWith( null, item, false ) ) - break; - } - - if ( item != null && !item.Deleted ) - DropItem( item ); - } - } - } - - public FillableContainer( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 1 ); // version - - writer.Write( (int)ContentType ); - - if ( m_RespawnTimer != null ) - { - writer.Write( true ); - writer.WriteDeltaTime( (DateTime)m_NextRespawnTime ); - } - else - { - writer.Write( false ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - switch( version ) - { - case 1: - { - m_Content = FillableContent.Lookup( (FillableContentType)reader.ReadInt() ); - goto case 0; - } - case 0: - { - if ( reader.ReadBool() ) - { - m_NextRespawnTime = reader.ReadDeltaTime(); - - TimeSpan delay = m_NextRespawnTime - DateTime.UtcNow; - m_RespawnTimer = Timer.DelayCall( delay > TimeSpan.Zero ? delay : TimeSpan.Zero, Respawn ); - } - else - { - CheckRespawn(); - } - - break; - } - } - } - } - - [Flippable( 0xA97, 0xA99, 0xA98, 0xA9A, 0xA9B, 0xA9C )] - public class LibraryBookcase : FillableContainer - { - public override bool IsLockable => false; - public override int SpawnThreshold => 5; - - protected override int GetSpawnCount() - { - return ( 5 - GetItemsCount() ); - } - - public override void AcquireContent() - { - if ( m_Content != null ) - return; - - m_Content = FillableContent.Library; - - if ( m_Content != null ) - Respawn(); - } - - [Constructible] - public LibraryBookcase() - : base( 0xA97 ) - { - Weight = 1.0; - } - - public LibraryBookcase( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - if ( version == 0 && m_Content == null ) - Timer.DelayCall( TimeSpan.Zero, AcquireContent ); - } - } - - [Flippable( 0xE3D, 0xE3C )] - public class FillableLargeCrate : FillableContainer - { - [Constructible] - public FillableLargeCrate() - : base( 0xE3D ) - { - Weight = 1.0; - } - - public FillableLargeCrate( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - [Flippable( 0x9A9, 0xE7E )] - public class FillableSmallCrate : FillableContainer - { - [Constructible] - public FillableSmallCrate() - : base( 0x9A9 ) - { - Weight = 1.0; - } - - public FillableSmallCrate( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - [Flippable( 0x9AA, 0xE7D )] - public class FillableWoodenBox : FillableContainer - { - [Constructible] - public FillableWoodenBox() - : base( 0x9AA ) - { - Weight = 4.0; - } - - public FillableWoodenBox( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x9A8, 0xE80 )] - public class FillableMetalBox : FillableContainer - { - [Constructible] - public FillableMetalBox() - : base( 0x9A8 ) - { - } - - public FillableMetalBox( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - if ( version == 0 && Weight == 3 ) - Weight = -1; - } - } - - public class FillableBarrel : FillableContainer - { - public override bool IsLockable => false; - - [Constructible] - public FillableBarrel() - : base( 0xE77 ) - { - } - - public FillableBarrel( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - if ( version == 0 && Weight == 25 ) - Weight = -1; - } - } - - [Flippable( 0x9AB, 0xE7C )] - public class FillableMetalChest : FillableContainer - { - [Constructible] - public FillableMetalChest() - : base( 0x9AB ) - { - } - - public FillableMetalChest( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 25 ) - Weight = -1; - } - } - - [Flippable( 0xE41, 0xE40 )] - public class FillableMetalGoldenChest : FillableContainer - { - [Constructible] - public FillableMetalGoldenChest() - : base( 0xE41 ) - { - } - - public FillableMetalGoldenChest( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 25 ) - Weight = -1; - } - } - - [Flippable( 0xE43, 0xE42 )] - public class FillableWoodenChest : FillableContainer - { - [Constructible] - public FillableWoodenChest() - : base( 0xE43 ) - { - } - - public FillableWoodenChest( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 2 ) - Weight = -1; - } - } - - public class FillableEntry - { - protected Type[] m_Types; - protected int m_Weight; - - public Type[] Types => m_Types; - public int Weight => m_Weight; - - public FillableEntry( Type type ) - : this( 1, new[] { type } ) - { - } - - public FillableEntry( int weight, Type type ) - : this( weight, new[] { type } ) - { - } - - public FillableEntry( Type[] types ) - : this( 1, types ) - { - } - - public FillableEntry( int weight, Type[] types ) - { - m_Weight = weight; - m_Types = types; - } - - public FillableEntry( int weight, Type[] types, int offset, int count ) - { - m_Weight = weight; - m_Types = new Type[ count ]; - - for( int i = 0; i < m_Types.Length; ++i ) - m_Types[ i ] = types[ offset + i ]; - } - - public virtual Item Construct() - { - Item item = Loot.Construct( m_Types ); - - if ( item is Key key ) - key.ItemID = Utility.RandomList( (int)KeyType.Copper, (int)KeyType.Gold, (int)KeyType.Iron, (int)KeyType.Rusty ); - else if ( item is Arrow || item is Bolt ) - item.Amount = Utility.RandomMinMax( 2, 6 ); - else if ( item is Bandage || item is Lockpick ) - item.Amount = Utility.RandomMinMax( 1, 3 ); - - return item; - } - } - - public class FillableBvrge : FillableEntry - { - public BeverageType Content { get; } - - public FillableBvrge( Type type, BeverageType content ) - : this( 1, type, content ) - { - } - - public FillableBvrge( int weight, Type type, BeverageType content ) - : base( weight, type ) - { - Content = content; - } - - public override Item Construct() - { - Item item; - - int index = Utility.Random( m_Types.Length ); - - if ( m_Types[ index ] == typeof( BeverageBottle ) ) - { - item = new BeverageBottle( Content ); - } - else if ( m_Types[ index ] == typeof( Jug ) ) - { - item = new Jug( Content ); - } - else - { - item = base.Construct(); - - if ( item is BaseBeverage bev ) - { - bev.Content = Content; - bev.Quantity = bev.MaxQuantity; - } - } - - return item; - } - } - - public enum FillableContentType - { - None = -1, - Weaponsmith, Provisioner, Mage, - Alchemist, Armorer, ArtisanGuild, - Baker, Bard, Blacksmith, - Bowyer, Butcher, Carpenter, - Clothier, Cobbler, Docks, - Farm, FighterGuild, Guard, - Healer, Herbalist, Inn, - Jeweler, Library, Merchant, - Mill, Mine, Observatory, - Painter, Ranger, Stables, - Tanner, Tavern, ThiefGuild, - Tinker, Veterinarian - } - - public class FillableContent - { - private FillableEntry[] m_Entries; - private int m_Weight; - - public int Level { get; } - - public Type[] Vendors { get; } - - public FillableContentType TypeID => Lookup( this ); - - public FillableContent( int level, Type[] vendors, FillableEntry[] entries ) - { - Level = level; - Vendors = vendors; - m_Entries = entries; - - for( int i = 0; i < entries.Length; ++i ) - m_Weight += entries[ i ].Weight; - } - - public virtual Item Construct() - { - int index = Utility.Random( m_Weight ); - - for( int i = 0; i < m_Entries.Length; ++i ) - { - FillableEntry entry = m_Entries[ i ]; - - if ( index < entry.Weight ) - return entry.Construct(); - - index -= entry.Weight; - } - - return null; - } - - public static FillableContent Alchemist = new FillableContent( - 1, - new[] - { - typeof( Alchemist ) - }, - new[] - { - new FillableEntry( typeof( NightSightPotion ) ), - new FillableEntry( typeof( LesserCurePotion ) ), - new FillableEntry( typeof( AgilityPotion ) ), - new FillableEntry( typeof( StrengthPotion ) ), - new FillableEntry( typeof( LesserPoisonPotion ) ), - new FillableEntry( typeof( RefreshPotion ) ), - new FillableEntry( typeof( LesserHealPotion ) ), - new FillableEntry( typeof( LesserExplosionPotion ) ), - new FillableEntry( typeof( MortarPestle ) ) - } ); - - public static FillableContent Armorer = new FillableContent( - 2, - new[] - { - typeof( Armorer ) - }, - new[] - { - new FillableEntry( 2, typeof( ChainCoif ) ), - new FillableEntry( 1, typeof( PlateGorget ) ), - new FillableEntry( 1, typeof( BronzeShield ) ), - new FillableEntry( 1, typeof( Buckler ) ), - new FillableEntry( 2, typeof( MetalKiteShield ) ), - new FillableEntry( 2, typeof( HeaterShield ) ), - new FillableEntry( 1, typeof( WoodenShield ) ), - new FillableEntry( 1, typeof( MetalShield ) ) - } ); - - public static FillableContent ArtisanGuild = new FillableContent( - 1, - new Type[] - { - }, - new[] - { - new FillableEntry( 1, typeof( PaintsAndBrush ) ), - new FillableEntry( 1, typeof( SledgeHammer ) ), - new FillableEntry( 2, typeof( SmithHammer ) ), - new FillableEntry( 2, typeof( Tongs ) ), - new FillableEntry( 4, typeof( Lockpick ) ), - new FillableEntry( 4, typeof( TinkerTools ) ), - new FillableEntry( 1, typeof( MalletAndChisel ) ), - new FillableEntry( 1, typeof( StatueEast2 ) ), - new FillableEntry( 1, typeof( StatueSouth ) ), - new FillableEntry( 1, typeof( StatueSouthEast ) ), - new FillableEntry( 1, typeof( StatueWest ) ), - new FillableEntry( 1, typeof( StatueNorth ) ), - new FillableEntry( 1, typeof( StatueEast ) ), - new FillableEntry( 1, typeof( BustEast ) ), - new FillableEntry( 1, typeof( BustSouth ) ), - new FillableEntry( 1, typeof( BearMask ) ), - new FillableEntry( 1, typeof( DeerMask ) ), - new FillableEntry( 4, typeof( OrcHelm ) ), - new FillableEntry( 1, typeof( TribalMask ) ), - new FillableEntry( 1, typeof( HornedTribalMask ) ) - } ); - - public static FillableContent Baker = new FillableContent( - 1, - new[] - { - typeof( Baker ), - }, - new[] - { - new FillableEntry( 1, typeof( RollingPin ) ), - new FillableEntry( 2, typeof( SackFlour ) ), - new FillableEntry( 2, typeof( BreadLoaf ) ), - new FillableEntry( 1, typeof( FrenchBread ) ) - } ); - - public static FillableContent Bard = new FillableContent( - 1, - new[] - { - typeof( Bard ), - typeof( BardGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( LapHarp ) ), - new FillableEntry( 2, typeof( Lute ) ), - new FillableEntry( 1, typeof( Drums ) ), - new FillableEntry( 1, typeof( Tambourine ) ), - new FillableEntry( 1, typeof( TambourineTassel ) ) - } ); - - public static FillableContent Blacksmith = new FillableContent( - 2, - new[] - { - typeof( Blacksmith ), - typeof( BlacksmithGuildmaster ) - }, - new[] - { - new FillableEntry( 8, typeof( SmithHammer ) ), - new FillableEntry( 8, typeof( Tongs ) ), - new FillableEntry( 8, typeof( SledgeHammer ) ), - //new FillableEntry( 8, typeof( IronOre ) ), TODO: Smaller ore - new FillableEntry( 8, typeof( IronIngot ) ), - new FillableEntry( 1, typeof( IronWire ) ), - new FillableEntry( 1, typeof( SilverWire ) ), - new FillableEntry( 1, typeof( GoldWire ) ), - new FillableEntry( 1, typeof( CopperWire ) ), - new FillableEntry( 1, typeof( HorseShoes ) ), - new FillableEntry( 1, typeof( ForgedMetal ) ) - } ); - - public static FillableContent Bowyer = new FillableContent( - 2, - new[] - { - typeof( Bowyer ) - }, - new[] - { - new FillableEntry( 2, typeof( Bow ) ), - new FillableEntry( 2, typeof( Crossbow ) ), - new FillableEntry( 1, typeof( Arrow ) ) - } ); - - public static FillableContent Butcher = new FillableContent( - 1, - new[] - { - typeof( Butcher ), - }, - new[] - { - new FillableEntry( 2, typeof( Cleaver ) ), - new FillableEntry( 2, typeof( SlabOfBacon ) ), - new FillableEntry( 2, typeof( Bacon ) ), - new FillableEntry( 1, typeof( RawFishSteak ) ), - new FillableEntry( 1, typeof( FishSteak ) ), - new FillableEntry( 2, typeof( CookedBird ) ), - new FillableEntry( 2, typeof( RawBird ) ), - new FillableEntry( 2, typeof( Ham ) ), - new FillableEntry( 1, typeof( RawLambLeg ) ), - new FillableEntry( 1, typeof( LambLeg ) ), - new FillableEntry( 1, typeof( Ribs ) ), - new FillableEntry( 1, typeof( RawRibs ) ), - new FillableEntry( 2, typeof( Sausage ) ), - new FillableEntry( 1, typeof( RawChickenLeg ) ), - new FillableEntry( 1, typeof( ChickenLeg ) ) - } ); - - public static FillableContent Carpenter = new FillableContent( - 1, - new[] - { - typeof( Carpenter ), - typeof( Architect ), - typeof( RealEstateBroker ) - }, - new[] - { - new FillableEntry( 1, typeof( ChiselsNorth ) ), - new FillableEntry( 1, typeof( ChiselsWest ) ), - new FillableEntry( 2, typeof( DovetailSaw ) ), - new FillableEntry( 2, typeof( Hammer ) ), - new FillableEntry( 2, typeof( MouldingPlane ) ), - new FillableEntry( 2, typeof( Nails ) ), - new FillableEntry( 2, typeof( JointingPlane ) ), - new FillableEntry( 2, typeof( SmoothingPlane ) ), - new FillableEntry( 2, typeof( Saw ) ), - new FillableEntry( 2, typeof( DrawKnife ) ), - new FillableEntry( 1, typeof( Log ) ), - new FillableEntry( 1, typeof( Froe ) ), - new FillableEntry( 1, typeof( Inshave ) ), - new FillableEntry( 1, typeof( Scorp ) ) - } ); - - public static FillableContent Clothier = new FillableContent( - 1, - new[] - { - typeof( Tailor ), - typeof( Weaver ), - typeof( TailorGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( Cotton ) ), - new FillableEntry( 1, typeof( Wool ) ), - new FillableEntry( 1, typeof( DarkYarn ) ), - new FillableEntry( 1, typeof( LightYarn ) ), - new FillableEntry( 1, typeof( LightYarnUnraveled ) ), - new FillableEntry( 1, typeof( SpoolOfThread ) ), - // Four different types - //new FillableEntry( 1, typeof( FoldedCloth ) ), - //new FillableEntry( 1, typeof( FoldedCloth ) ), - //new FillableEntry( 1, typeof( FoldedCloth ) ), - //new FillableEntry( 1, typeof( FoldedCloth ) ), - new FillableEntry( 1, typeof( Dyes ) ), - new FillableEntry( 2, typeof( Leather ) ) - } ); - - public static FillableContent Cobbler = new FillableContent( - 1, - new[] - { - typeof( Cobbler ) - }, - new[] - { - new FillableEntry( 1, typeof( Boots ) ), - new FillableEntry( 2, typeof( Shoes ) ), - new FillableEntry( 2, typeof( Sandals ) ), - new FillableEntry( 1, typeof( ThighBoots ) ) - } ); - - public static FillableContent Docks = new FillableContent( - 1, - new[] - { - typeof( Fisherman ), - typeof( FisherGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( FishingPole ) ), - // Two different types - //new FillableEntry( 1, typeof( SmallFish ) ), - //new FillableEntry( 1, typeof( SmallFish ) ), - new FillableEntry( 4, typeof( Fish ) ) - } ); - - public static FillableContent Farm = new FillableContent( - 1, - new[] - { - typeof( Farmer ), - typeof( Rancher ) - }, - new[] - { - new FillableEntry( 1, typeof( Shirt ) ), - new FillableEntry( 1, typeof( ShortPants ) ), - new FillableEntry( 1, typeof( Skirt ) ), - new FillableEntry( 1, typeof( PlainDress ) ), - new FillableEntry( 1, typeof( Cap ) ), - new FillableEntry( 2, typeof( Sandals ) ), - new FillableEntry( 2, typeof( GnarledStaff ) ), - new FillableEntry( 2, typeof( Pitchfork ) ), - new FillableEntry( 1, typeof( Bag ) ), - new FillableEntry( 1, typeof( Kindling ) ), - new FillableEntry( 1, typeof( Lettuce ) ), - new FillableEntry( 1, typeof( Onion ) ), - new FillableEntry( 1, typeof( Turnip ) ), - new FillableEntry( 1, typeof( Ham ) ), - new FillableEntry( 1, typeof( Bacon ) ), - new FillableEntry( 1, typeof( RawLambLeg ) ), - new FillableEntry( 1, typeof( SheafOfHay ) ), - new FillableBvrge( 1, typeof( Pitcher ), BeverageType.Milk ) - } ); - - public static FillableContent FighterGuild = new FillableContent( - 3, - new[] - { - typeof( WarriorGuildmaster ) - }, - new[] - { - new FillableEntry( 12, Loot.ArmorTypes ), - new FillableEntry( 8, Loot.WeaponTypes ), - new FillableEntry( 3, Loot.ShieldTypes ), - new FillableEntry( 1, typeof( Arrow ) ) - } ); - - public static FillableContent Guard = new FillableContent( - 3, - new Type[] - { - }, - new[] - { - new FillableEntry( 12, Loot.ArmorTypes ), - new FillableEntry( 8, Loot.WeaponTypes ), - new FillableEntry( 3, Loot.ShieldTypes ), - new FillableEntry( 1, typeof( Arrow ) ) - } ); - - public static FillableContent Healer = new FillableContent( - 1, - new[] - { - typeof( Healer ), - typeof( HealerGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( Bandage ) ), - new FillableEntry( 1, typeof( MortarPestle ) ), - new FillableEntry( 1, typeof( LesserHealPotion ) ) - } ); - - public static FillableContent Herbalist = new FillableContent( - 1, - new[] - { - typeof( Herbalist ) - }, - new[] - { - new FillableEntry( 10, typeof( Garlic ) ), - new FillableEntry( 10, typeof( Ginseng ) ), - new FillableEntry( 10, typeof( MandrakeRoot ) ), - new FillableEntry( 1, typeof( DeadWood ) ), - new FillableEntry( 1, typeof( WhiteDriedFlowers ) ), - new FillableEntry( 1, typeof( GreenDriedFlowers ) ), - new FillableEntry( 1, typeof( DriedOnions ) ), - new FillableEntry( 1, typeof( DriedHerbs ) ) - } ); - - public static FillableContent Inn = new FillableContent( - 1, - new Type[] - { - }, - new[] - { - new FillableEntry( 1, typeof( Candle ) ), - new FillableEntry( 1, typeof( Torch ) ), - new FillableEntry( 1, typeof( Lantern ) ) - } ); - - public static FillableContent Jeweler = new FillableContent( - 2, - new[] - { - typeof( Jeweler ) - }, - new[] - { - new FillableEntry( 1, typeof( GoldRing ) ), - new FillableEntry( 1, typeof( GoldBracelet ) ), - new FillableEntry( 1, typeof( GoldEarrings ) ), - new FillableEntry( 1, typeof( GoldNecklace ) ), - new FillableEntry( 1, typeof( GoldBeadNecklace ) ), - new FillableEntry( 1, typeof( Necklace ) ), - new FillableEntry( 1, typeof( Beads ) ), - new FillableEntry( 9, Loot.GemTypes ) - } ); - - public static FillableContent Library = new FillableContent( - 1, - new[] - { - typeof( Scribe ) - }, - new[] - { - new FillableEntry( 8, Loot.LibraryBookTypes ), - new FillableEntry( 1, typeof( RedBook ) ), - new FillableEntry( 1, typeof( BlueBook ) ) - } ); - - public static FillableContent Mage = new FillableContent( - 2, - new[] - { - typeof( Mage ), - typeof( HolyMage ), - typeof( MageGuildmaster ) - }, - new[] - { - new FillableEntry( 16, typeof( BlankScroll ) ), - new FillableEntry( 14, typeof( Spellbook ) ), - new FillableEntry( 12, Loot.RegularScrollTypes, 0, 8 ), - new FillableEntry( 11, Loot.RegularScrollTypes, 8, 8 ), - new FillableEntry( 10, Loot.RegularScrollTypes, 16, 8 ), - new FillableEntry( 9, Loot.RegularScrollTypes, 24, 8 ), - new FillableEntry( 8, Loot.RegularScrollTypes, 32, 8 ), - new FillableEntry( 7, Loot.RegularScrollTypes, 40, 8 ), - new FillableEntry( 6, Loot.RegularScrollTypes, 48, 8 ), - new FillableEntry( 5, Loot.RegularScrollTypes, 56, 8 ) - } ); - - public static FillableContent Merchant = new FillableContent( - 1, - new[] - { - typeof( MerchantGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( CheeseWheel ) ), - new FillableEntry( 1, typeof( CheeseWedge ) ), - new FillableEntry( 1, typeof( CheeseSlice ) ), - new FillableEntry( 1, typeof( Eggs ) ), - new FillableEntry( 4, typeof( Fish ) ), - new FillableEntry( 2, typeof( RawFishSteak ) ), - new FillableEntry( 2, typeof( FishSteak ) ), - new FillableEntry( 1, typeof( Apple ) ), - new FillableEntry( 2, typeof( Banana ) ), - new FillableEntry( 2, typeof( Bananas ) ), - new FillableEntry( 2, typeof( OpenCoconut ) ), - new FillableEntry( 1, typeof( SplitCoconut ) ), - new FillableEntry( 1, typeof( Coconut ) ), - new FillableEntry( 1, typeof( Dates ) ), - new FillableEntry( 1, typeof( Grapes ) ), - new FillableEntry( 1, typeof( Lemon ) ), - new FillableEntry( 1, typeof( Lemons ) ), - new FillableEntry( 1, typeof( Lime ) ), - new FillableEntry( 1, typeof( Limes ) ), - new FillableEntry( 1, typeof( Peach ) ), - new FillableEntry( 1, typeof( Pear ) ), - new FillableEntry( 2, typeof( SlabOfBacon ) ), - new FillableEntry( 2, typeof( Bacon ) ), - new FillableEntry( 2, typeof( CookedBird ) ), - new FillableEntry( 2, typeof( RawBird ) ), - new FillableEntry( 2, typeof( Ham ) ), - new FillableEntry( 1, typeof( RawLambLeg ) ), - new FillableEntry( 1, typeof( LambLeg ) ), - new FillableEntry( 1, typeof( Ribs ) ), - new FillableEntry( 1, typeof( RawRibs ) ), - new FillableEntry( 2, typeof( Sausage ) ), - new FillableEntry( 1, typeof( RawChickenLeg ) ), - new FillableEntry( 1, typeof( ChickenLeg ) ), - new FillableEntry( 1, typeof( Watermelon ) ), - new FillableEntry( 1, typeof( SmallWatermelon ) ), - new FillableEntry( 3, typeof( Turnip ) ), - new FillableEntry( 2, typeof( YellowGourd ) ), - new FillableEntry( 2, typeof( GreenGourd ) ), - new FillableEntry( 2, typeof( Pumpkin ) ), - new FillableEntry( 1, typeof( SmallPumpkin ) ), - new FillableEntry( 2, typeof( Onion ) ), - new FillableEntry( 2, typeof( Lettuce ) ), - new FillableEntry( 2, typeof( Squash ) ), - new FillableEntry( 2, typeof( HoneydewMelon ) ), - new FillableEntry( 1, typeof( Carrot ) ), - new FillableEntry( 2, typeof( Cantaloupe ) ), - new FillableEntry( 2, typeof( Cabbage ) ), - new FillableEntry( 4, typeof( EarOfCorn ) ) - } ); - - public static FillableContent Mill = new FillableContent( - 1, - new Type[] - { - }, - new[] - { - new FillableEntry( 1, typeof( SackFlour ) ) - } ); - - public static FillableContent Mine = new FillableContent( - 1, - new[] - { - typeof( Miner ) - }, - new[] - { - new FillableEntry( 2, typeof( Pickaxe ) ), - new FillableEntry( 2, typeof( Shovel ) ), - new FillableEntry( 2, typeof( IronIngot ) ), - //new FillableEntry( 2, typeof( IronOre ) ), TODO: Smaller Ore - new FillableEntry( 1, typeof( ForgedMetal ) ) - } ); - - public static FillableContent Observatory = new FillableContent( - 1, - new Type[] - { - }, - new[] - { - new FillableEntry( 2, typeof( Sextant ) ), - new FillableEntry( 2, typeof( Clock ) ), - new FillableEntry( 1, typeof( Spyglass ) ) - } ); - - public static FillableContent Painter = new FillableContent( - 1, - new Type[] - { - }, - new[] - { - new FillableEntry( 1, typeof( PaintsAndBrush ) ), - new FillableEntry( 2, typeof( PenAndInk ) ) - } ); - - public static FillableContent Provisioner = new FillableContent( - 1, - new[] - { - typeof( Provisioner ) - }, - new[] - { - new FillableEntry( 1, typeof( CheeseWheel ) ), - new FillableEntry( 1, typeof( CheeseWedge ) ), - new FillableEntry( 1, typeof( CheeseSlice ) ), - new FillableEntry( 1, typeof( Eggs ) ), - new FillableEntry( 4, typeof( Fish ) ), - new FillableEntry( 1, typeof( DirtyFrypan ) ), - new FillableEntry( 1, typeof( DirtyPan ) ), - new FillableEntry( 1, typeof( DirtyKettle ) ), - new FillableEntry( 1, typeof( DirtySmallRoundPot ) ), - new FillableEntry( 1, typeof( DirtyRoundPot ) ), - new FillableEntry( 1, typeof( DirtySmallPot ) ), - new FillableEntry( 1, typeof( DirtyPot ) ), - new FillableEntry( 1, typeof( Apple ) ), - new FillableEntry( 2, typeof( Banana ) ), - new FillableEntry( 2, typeof( Bananas ) ), - new FillableEntry( 2, typeof( OpenCoconut ) ), - new FillableEntry( 1, typeof( SplitCoconut ) ), - new FillableEntry( 1, typeof( Coconut ) ), - new FillableEntry( 1, typeof( Dates ) ), - new FillableEntry( 1, typeof( Grapes ) ), - new FillableEntry( 1, typeof( Lemon ) ), - new FillableEntry( 1, typeof( Lemons ) ), - new FillableEntry( 1, typeof( Lime ) ), - new FillableEntry( 1, typeof( Limes ) ), - new FillableEntry( 1, typeof( Peach ) ), - new FillableEntry( 1, typeof( Pear ) ), - new FillableEntry( 2, typeof( SlabOfBacon ) ), - new FillableEntry( 2, typeof( Bacon ) ), - new FillableEntry( 1, typeof( RawFishSteak ) ), - new FillableEntry( 1, typeof( FishSteak ) ), - new FillableEntry( 2, typeof( CookedBird ) ), - new FillableEntry( 2, typeof( RawBird ) ), - new FillableEntry( 2, typeof( Ham ) ), - new FillableEntry( 1, typeof( RawLambLeg ) ), - new FillableEntry( 1, typeof( LambLeg ) ), - new FillableEntry( 1, typeof( Ribs ) ), - new FillableEntry( 1, typeof( RawRibs ) ), - new FillableEntry( 2, typeof( Sausage ) ), - new FillableEntry( 1, typeof( RawChickenLeg ) ), - new FillableEntry( 1, typeof( ChickenLeg ) ), - new FillableEntry( 1, typeof( Watermelon ) ), - new FillableEntry( 1, typeof( SmallWatermelon ) ), - new FillableEntry( 3, typeof( Turnip ) ), - new FillableEntry( 2, typeof( YellowGourd ) ), - new FillableEntry( 2, typeof( GreenGourd ) ), - new FillableEntry( 2, typeof( Pumpkin ) ), - new FillableEntry( 1, typeof( SmallPumpkin ) ), - new FillableEntry( 2, typeof( Onion ) ), - new FillableEntry( 2, typeof( Lettuce ) ), - new FillableEntry( 2, typeof( Squash ) ), - new FillableEntry( 2, typeof( HoneydewMelon ) ), - new FillableEntry( 1, typeof( Carrot ) ), - new FillableEntry( 2, typeof( Cantaloupe ) ), - new FillableEntry( 2, typeof( Cabbage ) ), - new FillableEntry( 4, typeof( EarOfCorn ) ) - } ); - - public static FillableContent Ranger = new FillableContent( - 2, - new[] - { - typeof( Ranger ), - typeof( RangerGuildmaster ) - }, - new[] - { - new FillableEntry( 2, typeof( StuddedChest ) ), - new FillableEntry( 2, typeof( StuddedLegs ) ), - new FillableEntry( 2, typeof( StuddedArms ) ), - new FillableEntry( 2, typeof( StuddedGloves ) ), - new FillableEntry( 1, typeof( StuddedGorget ) ), - - new FillableEntry( 2, typeof( LeatherChest ) ), - new FillableEntry( 2, typeof( LeatherLegs ) ), - new FillableEntry( 2, typeof( LeatherArms ) ), - new FillableEntry( 2, typeof( LeatherGloves ) ), - new FillableEntry( 1, typeof( LeatherGorget ) ), - - new FillableEntry( 2, typeof( FeatheredHat ) ), - new FillableEntry( 1, typeof( CloseHelm ) ), - new FillableEntry( 1, typeof( TallStrawHat ) ), - new FillableEntry( 1, typeof( Bandana ) ), - new FillableEntry( 1, typeof( Cloak ) ), - new FillableEntry( 2, typeof( Boots ) ), - new FillableEntry( 2, typeof( ThighBoots ) ), - - new FillableEntry( 2, typeof( GnarledStaff ) ), - new FillableEntry( 1, typeof( Whip ) ), - - new FillableEntry( 2, typeof( Bow ) ), - new FillableEntry( 2, typeof( Crossbow ) ), - new FillableEntry( 2, typeof( HeavyCrossbow ) ), - new FillableEntry( 4, typeof( Arrow ) ) - } ); - - public static FillableContent Stables = new FillableContent( - 1, - new[] - { - typeof( AnimalTrainer ), - typeof( GypsyAnimalTrainer ) - }, - new[] - { - //new FillableEntry( 1, typeof( Wheat ) ), - new FillableEntry( 1, typeof( Carrot ) ) - } ); - - public static FillableContent Tanner = new FillableContent( - 2, - new[] - { - typeof( Tanner ), - typeof( LeatherWorker ), - typeof( Furtrader ) - }, - new[] - { - new FillableEntry( 1, typeof( FeatheredHat ) ), - new FillableEntry( 1, typeof( LeatherArms ) ), - new FillableEntry( 2, typeof( LeatherLegs ) ), - new FillableEntry( 2, typeof( LeatherChest ) ), - new FillableEntry( 2, typeof( LeatherGloves ) ), - new FillableEntry( 1, typeof( LeatherGorget ) ), - new FillableEntry( 2, typeof( Leather ) ) - } ); - - public static FillableContent Tavern = new FillableContent( - 1, - new[] - { - typeof( TavernKeeper ), - typeof( Barkeeper ), - typeof( Waiter ), - typeof( Cook ) - }, - new FillableEntry[] - { - new FillableBvrge( 1, typeof( BeverageBottle ), BeverageType.Ale ), - new FillableBvrge( 1, typeof( BeverageBottle ), BeverageType.Wine ), - new FillableBvrge( 1, typeof( BeverageBottle ), BeverageType.Liquor ), - new FillableBvrge( 1, typeof( Jug ), BeverageType.Cider ) - } ); - - public static FillableContent ThiefGuild = new FillableContent( - 1, - new[] - { - typeof( Thief ), - typeof( ThiefGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( Lockpick ) ), - new FillableEntry( 1, typeof( BearMask ) ), - new FillableEntry( 1, typeof( DeerMask ) ), - new FillableEntry( 1, typeof( TribalMask ) ), - new FillableEntry( 1, typeof( HornedTribalMask ) ), - new FillableEntry( 4, typeof( OrcHelm ) ) - } ); - - public static FillableContent Tinker = new FillableContent( - 1, - new[] - { - typeof( Tinker ), - typeof( TinkerGuildmaster ) - }, - new[] - { - new FillableEntry( 1, typeof( Lockpick ) ), - //new FillableEntry( 1, typeof( KeyRing ) ), - new FillableEntry( 2, typeof( Clock ) ), - new FillableEntry( 2, typeof( ClockParts ) ), - new FillableEntry( 2, typeof( AxleGears ) ), - new FillableEntry( 2, typeof( Gears ) ), - new FillableEntry( 2, typeof( Hinge ) ), - //new FillableEntry( 1, typeof( ArrowShafts ) ), - new FillableEntry( 2, typeof( Sextant ) ), - new FillableEntry( 2, typeof( SextantParts ) ), - new FillableEntry( 2, typeof( Axle ) ), - new FillableEntry( 2, typeof( Springs ) ), - new FillableEntry( 5, typeof( TinkerTools ) ), - new FillableEntry( 4, typeof( Key ) ), - new FillableEntry( 1, typeof( DecoArrowShafts )), - new FillableEntry( 1, typeof( Lockpicks )), - new FillableEntry( 1, typeof( ToolKit )) - } ); - - public static FillableContent Veterinarian = new FillableContent( - 1, - new[] - { - typeof( Veterinarian ) - }, - new[] - { - new FillableEntry( 1, typeof( Bandage ) ), - new FillableEntry( 1, typeof( MortarPestle ) ), - new FillableEntry( 1, typeof( LesserHealPotion ) ), - //new FillableEntry( 1, typeof( Wheat ) ), - new FillableEntry( 1, typeof( Carrot ) ) - } ); - - public static FillableContent Weaponsmith = new FillableContent( - 2, - new[] - { - typeof( Weaponsmith ) - }, - new[] - { - new FillableEntry( 8, Loot.WeaponTypes ), - new FillableEntry( 1, typeof( Arrow ) ) - } ); - - public static FillableContent Lookup( FillableContentType type ) - { - int v = (int)type; - - if ( v >= 0 && v < m_ContentTypes.Length ) - return m_ContentTypes[ v ]; - - return null; - } - - public static FillableContentType Lookup( FillableContent content ) - { - if ( content == null ) - return FillableContentType.None; - - return (FillableContentType)Array.IndexOf( m_ContentTypes, content ); - } - - private static Hashtable m_AcquireTable; - - private static FillableContent[] m_ContentTypes = { - Weaponsmith, Provisioner, Mage, - Alchemist, Armorer, ArtisanGuild, - Baker, Bard, Blacksmith, - Bowyer, Butcher, Carpenter, - Clothier, Cobbler, Docks, - Farm, FighterGuild, Guard, - Healer, Herbalist, Inn, - Jeweler, Library, Merchant, - Mill, Mine, Observatory, - Painter, Ranger, Stables, - Tanner, Tavern, ThiefGuild, - Tinker, Veterinarian - }; - - public static FillableContent Acquire( Point3D loc, Map map ) - { - if ( map == null || map == Map.Internal ) - return null; - - if ( m_AcquireTable == null ) - { - m_AcquireTable = new Hashtable(); - - for( int i = 0; i < m_ContentTypes.Length; ++i ) - { - FillableContent fill = m_ContentTypes[ i ]; - - for( int j = 0; j < fill.Vendors.Length; ++j ) - m_AcquireTable[ fill.Vendors[ j ] ] = fill; - } - } - - Mobile nearest = null; - FillableContent content = null; - - foreach( Mobile mob in map.GetMobilesInRange( loc, 20 ) ) - { - if ( nearest != null && mob.GetDistanceToSqrt( loc ) > nearest.GetDistanceToSqrt( loc ) && !( nearest is Cobbler && mob is Provisioner ) ) - continue; - - if ( m_AcquireTable[ mob.GetType() ] is FillableContent check ) - { - nearest = mob; - content = check; - } - } - - return content; - } - } -} + public abstract class FillableContainer : LockableContainer + { + protected FillableContent m_Content; + + protected DateTime m_NextRespawnTime; + protected Timer m_RespawnTimer; + + public FillableContainer(int itemID) + : base(itemID) + { + Movable = false; + } + + public FillableContainer(Serial serial) + : base(serial) + { + } + + public virtual int MinRespawnMinutes => 60; + public virtual int MaxRespawnMinutes => 90; + + public virtual bool IsLockable => true; + public virtual bool IsTrappable => IsLockable; + + public virtual int SpawnThreshold => 2; + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextRespawnTime => m_NextRespawnTime; + + [CommandProperty(AccessLevel.GameMaster)] + public FillableContentType ContentType + { + get => FillableContent.Lookup(m_Content); + set => Content = FillableContent.Lookup(value); + } + + public FillableContent Content + { + get => m_Content; + set + { + if (m_Content == value) + return; + + m_Content = value; + + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + Items[i].Delete(); + + Respawn(); + } + } + + public override void OnMapChange() + { + base.OnMapChange(); + AcquireContent(); + } + + public override void OnLocationChange(Point3D oldLocation) + { + base.OnLocationChange(oldLocation); + AcquireContent(); + } + + public virtual void AcquireContent() + { + if (m_Content != null) + return; + + m_Content = FillableContent.Acquire(GetWorldLocation(), Map); + + if (m_Content != null) + Respawn(); + } + + public override void OnItemRemoved(Item item) + { + CheckRespawn(); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + if (m_RespawnTimer != null) + { + m_RespawnTimer.Stop(); + m_RespawnTimer = null; + } + } + + public int GetItemsCount() + { + int count = 0; + + foreach (Item item in Items) count += item.Amount; + + return count; + } + + public void CheckRespawn() + { + bool canSpawn = m_Content != null && !Deleted && GetItemsCount() <= SpawnThreshold && !Movable && + Parent == null && !IsLockedDown && !IsSecure; + + if (canSpawn) + { + if (m_RespawnTimer == null) + { + int mins = Utility.RandomMinMax(MinRespawnMinutes, MaxRespawnMinutes); + TimeSpan delay = TimeSpan.FromMinutes(mins); + + m_NextRespawnTime = DateTime.UtcNow + delay; + m_RespawnTimer = Timer.DelayCall(delay, Respawn); + } + } + else if (m_RespawnTimer != null) + { + m_RespawnTimer.Stop(); + m_RespawnTimer = null; + } + } + + public void Respawn() + { + if (m_RespawnTimer != null) + { + m_RespawnTimer.Stop(); + m_RespawnTimer = null; + } + + if (m_Content == null || Deleted) + return; + + GenerateContent(); + + if (IsLockable) + { + Locked = true; + + int difficulty = (m_Content.Level - 1) * 30; + + LockLevel = difficulty - 10; + MaxLockLevel = difficulty + 30; + RequiredSkill = difficulty; + } + + if (IsTrappable && (m_Content.Level > 1 || 4 > Utility.Random(5))) + { + if (m_Content.Level > Utility.Random(5)) + TrapType = TrapType.PoisonTrap; + else + TrapType = TrapType.ExplosionTrap; + + TrapPower = m_Content.Level * Utility.RandomMinMax(10, 30); + TrapLevel = m_Content.Level; + } + else + { + TrapType = TrapType.None; + TrapPower = 0; + TrapLevel = 0; + } + + CheckRespawn(); + } + + protected virtual int GetSpawnCount() + { + int itemsCount = GetItemsCount(); + + if (itemsCount > SpawnThreshold) + return 0; + + int maxSpawnCount = (1 + SpawnThreshold - itemsCount) * 2; + + return Utility.RandomMinMax(0, maxSpawnCount); + } + + public virtual void GenerateContent() + { + if (m_Content == null || Deleted) + return; + + int toSpawn = GetSpawnCount(); + + for (int i = 0; i < toSpawn; ++i) + { + Item item = m_Content.Construct(); + + if (item != null) + { + List list = Items; + + for (int j = 0; j < list.Count; ++j) + { + Item subItem = list[j]; + + if (!(subItem is Container) && subItem.StackWith(null, item, false)) + break; + } + + if (item != null && !item.Deleted) + DropItem(item); + } + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + + writer.Write((int)ContentType); + + if (m_RespawnTimer != null) + { + writer.Write(true); + writer.WriteDeltaTime(m_NextRespawnTime); + } + else + { + writer.Write(false); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 1: + { + m_Content = FillableContent.Lookup((FillableContentType)reader.ReadInt()); + goto case 0; + } + case 0: + { + if (reader.ReadBool()) + { + m_NextRespawnTime = reader.ReadDeltaTime(); + + TimeSpan delay = m_NextRespawnTime - DateTime.UtcNow; + m_RespawnTimer = Timer.DelayCall(delay > TimeSpan.Zero ? delay : TimeSpan.Zero, Respawn); + } + else + { + CheckRespawn(); + } + + break; + } + } + } + } + + [Flippable(0xA97, 0xA99, 0xA98, 0xA9A, 0xA9B, 0xA9C)] + public class LibraryBookcase : FillableContainer + { + [Constructible] + public LibraryBookcase() + : base(0xA97) + { + Weight = 1.0; + } + + public LibraryBookcase(Serial serial) + : base(serial) + { + } + + public override bool IsLockable => false; + public override int SpawnThreshold => 5; + + protected override int GetSpawnCount() + { + return 5 - GetItemsCount(); + } + + public override void AcquireContent() + { + if (m_Content != null) + return; + + m_Content = FillableContent.Library; + + if (m_Content != null) + Respawn(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + if (version == 0 && m_Content == null) + Timer.DelayCall(TimeSpan.Zero, AcquireContent); + } + } + + [Flippable(0xE3D, 0xE3C)] + public class FillableLargeCrate : FillableContainer + { + [Constructible] + public FillableLargeCrate() + : base(0xE3D) + { + Weight = 1.0; + } + + public FillableLargeCrate(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + [Flippable(0x9A9, 0xE7E)] + public class FillableSmallCrate : FillableContainer + { + [Constructible] + public FillableSmallCrate() + : base(0x9A9) + { + Weight = 1.0; + } + + public FillableSmallCrate(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + [Flippable(0x9AA, 0xE7D)] + public class FillableWoodenBox : FillableContainer + { + [Constructible] + public FillableWoodenBox() + : base(0x9AA) + { + Weight = 4.0; + } + + public FillableWoodenBox(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x9A8, 0xE80)] + public class FillableMetalBox : FillableContainer + { + [Constructible] + public FillableMetalBox() + : base(0x9A8) + { + } + + public FillableMetalBox(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + if (version == 0 && Weight == 3) + Weight = -1; + } + } + + public class FillableBarrel : FillableContainer + { + [Constructible] + public FillableBarrel() + : base(0xE77) + { + } + + public FillableBarrel(Serial serial) + : base(serial) + { + } + + public override bool IsLockable => false; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + if (version == 0 && Weight == 25) + Weight = -1; + } + } + + [Flippable(0x9AB, 0xE7C)] + public class FillableMetalChest : FillableContainer + { + [Constructible] + public FillableMetalChest() + : base(0x9AB) + { + } + + public FillableMetalChest(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 25) + Weight = -1; + } + } + + [Flippable(0xE41, 0xE40)] + public class FillableMetalGoldenChest : FillableContainer + { + [Constructible] + public FillableMetalGoldenChest() + : base(0xE41) + { + } + + public FillableMetalGoldenChest(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 25) + Weight = -1; + } + } + + [Flippable(0xE43, 0xE42)] + public class FillableWoodenChest : FillableContainer + { + [Constructible] + public FillableWoodenChest() + : base(0xE43) + { + } + + public FillableWoodenChest(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 2) + Weight = -1; + } + } + + public class FillableEntry + { + protected Type[] m_Types; + protected int m_Weight; + + public FillableEntry(Type type) + : this(1, new[] { type }) + { + } + + public FillableEntry(int weight, Type type) + : this(weight, new[] { type }) + { + } + + public FillableEntry(Type[] types) + : this(1, types) + { + } + + public FillableEntry(int weight, Type[] types) + { + m_Weight = weight; + m_Types = types; + } + + public FillableEntry(int weight, Type[] types, int offset, int count) + { + m_Weight = weight; + m_Types = new Type[count]; + + for (int i = 0; i < m_Types.Length; ++i) + m_Types[i] = types[offset + i]; + } + + public Type[] Types => m_Types; + public int Weight => m_Weight; + + public virtual Item Construct() + { + Item item = Loot.Construct(m_Types); + + if (item is Key key) + key.ItemID = Utility.RandomList((int)KeyType.Copper, (int)KeyType.Gold, (int)KeyType.Iron, + (int)KeyType.Rusty); + else if (item is Arrow || item is Bolt) + item.Amount = Utility.RandomMinMax(2, 6); + else if (item is Bandage || item is Lockpick) + item.Amount = Utility.RandomMinMax(1, 3); + + return item; + } + } + + public class FillableBvrge : FillableEntry + { + public FillableBvrge(Type type, BeverageType content) + : this(1, type, content) + { + } + + public FillableBvrge(int weight, Type type, BeverageType content) + : base(weight, type) + { + Content = content; + } + + public BeverageType Content{ get; } + + public override Item Construct() + { + Item item; + + int index = Utility.Random(m_Types.Length); + + if (m_Types[index] == typeof(BeverageBottle)) + { + item = new BeverageBottle(Content); + } + else if (m_Types[index] == typeof(Jug)) + { + item = new Jug(Content); + } + else + { + item = base.Construct(); + + if (item is BaseBeverage bev) + { + bev.Content = Content; + bev.Quantity = bev.MaxQuantity; + } + } + + return item; + } + } + + public enum FillableContentType + { + None = -1, + Weaponsmith, + Provisioner, + Mage, + Alchemist, + Armorer, + ArtisanGuild, + Baker, + Bard, + Blacksmith, + Bowyer, + Butcher, + Carpenter, + Clothier, + Cobbler, + Docks, + Farm, + FighterGuild, + Guard, + Healer, + Herbalist, + Inn, + Jeweler, + Library, + Merchant, + Mill, + Mine, + Observatory, + Painter, + Ranger, + Stables, + Tanner, + Tavern, + ThiefGuild, + Tinker, + Veterinarian + } + + public class FillableContent + { + public static FillableContent Alchemist = new FillableContent( + 1, + new[] + { + typeof(Alchemist) + }, + new[] + { + new FillableEntry(typeof(NightSightPotion)), + new FillableEntry(typeof(LesserCurePotion)), + new FillableEntry(typeof(AgilityPotion)), + new FillableEntry(typeof(StrengthPotion)), + new FillableEntry(typeof(LesserPoisonPotion)), + new FillableEntry(typeof(RefreshPotion)), + new FillableEntry(typeof(LesserHealPotion)), + new FillableEntry(typeof(LesserExplosionPotion)), + new FillableEntry(typeof(MortarPestle)) + }); + + public static FillableContent Armorer = new FillableContent( + 2, + new[] + { + typeof(Armorer) + }, + new[] + { + new FillableEntry(2, typeof(ChainCoif)), + new FillableEntry(1, typeof(PlateGorget)), + new FillableEntry(1, typeof(BronzeShield)), + new FillableEntry(1, typeof(Buckler)), + new FillableEntry(2, typeof(MetalKiteShield)), + new FillableEntry(2, typeof(HeaterShield)), + new FillableEntry(1, typeof(WoodenShield)), + new FillableEntry(1, typeof(MetalShield)) + }); + + public static FillableContent ArtisanGuild = new FillableContent( + 1, + new Type[] + { + }, + new[] + { + new FillableEntry(1, typeof(PaintsAndBrush)), + new FillableEntry(1, typeof(SledgeHammer)), + new FillableEntry(2, typeof(SmithHammer)), + new FillableEntry(2, typeof(Tongs)), + new FillableEntry(4, typeof(Lockpick)), + new FillableEntry(4, typeof(TinkerTools)), + new FillableEntry(1, typeof(MalletAndChisel)), + new FillableEntry(1, typeof(StatueEast2)), + new FillableEntry(1, typeof(StatueSouth)), + new FillableEntry(1, typeof(StatueSouthEast)), + new FillableEntry(1, typeof(StatueWest)), + new FillableEntry(1, typeof(StatueNorth)), + new FillableEntry(1, typeof(StatueEast)), + new FillableEntry(1, typeof(BustEast)), + new FillableEntry(1, typeof(BustSouth)), + new FillableEntry(1, typeof(BearMask)), + new FillableEntry(1, typeof(DeerMask)), + new FillableEntry(4, typeof(OrcHelm)), + new FillableEntry(1, typeof(TribalMask)), + new FillableEntry(1, typeof(HornedTribalMask)) + }); + + public static FillableContent Baker = new FillableContent( + 1, + new[] + { + typeof(Baker) + }, + new[] + { + new FillableEntry(1, typeof(RollingPin)), + new FillableEntry(2, typeof(SackFlour)), + new FillableEntry(2, typeof(BreadLoaf)), + new FillableEntry(1, typeof(FrenchBread)) + }); + + public static FillableContent Bard = new FillableContent( + 1, + new[] + { + typeof(Bard), + typeof(BardGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(LapHarp)), + new FillableEntry(2, typeof(Lute)), + new FillableEntry(1, typeof(Drums)), + new FillableEntry(1, typeof(Tambourine)), + new FillableEntry(1, typeof(TambourineTassel)) + }); + + public static FillableContent Blacksmith = new FillableContent( + 2, + new[] + { + typeof(Blacksmith), + typeof(BlacksmithGuildmaster) + }, + new[] + { + new FillableEntry(8, typeof(SmithHammer)), + new FillableEntry(8, typeof(Tongs)), + new FillableEntry(8, typeof(SledgeHammer)), + //new FillableEntry( 8, typeof( IronOre ) ), TODO: Smaller ore + new FillableEntry(8, typeof(IronIngot)), + new FillableEntry(1, typeof(IronWire)), + new FillableEntry(1, typeof(SilverWire)), + new FillableEntry(1, typeof(GoldWire)), + new FillableEntry(1, typeof(CopperWire)), + new FillableEntry(1, typeof(HorseShoes)), + new FillableEntry(1, typeof(ForgedMetal)) + }); + + public static FillableContent Bowyer = new FillableContent( + 2, + new[] + { + typeof(Bowyer) + }, + new[] + { + new FillableEntry(2, typeof(Bow)), + new FillableEntry(2, typeof(Crossbow)), + new FillableEntry(1, typeof(Arrow)) + }); + + public static FillableContent Butcher = new FillableContent( + 1, + new[] + { + typeof(Butcher) + }, + new[] + { + new FillableEntry(2, typeof(Cleaver)), + new FillableEntry(2, typeof(SlabOfBacon)), + new FillableEntry(2, typeof(Bacon)), + new FillableEntry(1, typeof(RawFishSteak)), + new FillableEntry(1, typeof(FishSteak)), + new FillableEntry(2, typeof(CookedBird)), + new FillableEntry(2, typeof(RawBird)), + new FillableEntry(2, typeof(Ham)), + new FillableEntry(1, typeof(RawLambLeg)), + new FillableEntry(1, typeof(LambLeg)), + new FillableEntry(1, typeof(Ribs)), + new FillableEntry(1, typeof(RawRibs)), + new FillableEntry(2, typeof(Sausage)), + new FillableEntry(1, typeof(RawChickenLeg)), + new FillableEntry(1, typeof(ChickenLeg)) + }); + + public static FillableContent Carpenter = new FillableContent( + 1, + new[] + { + typeof(Carpenter), + typeof(Architect), + typeof(RealEstateBroker) + }, + new[] + { + new FillableEntry(1, typeof(ChiselsNorth)), + new FillableEntry(1, typeof(ChiselsWest)), + new FillableEntry(2, typeof(DovetailSaw)), + new FillableEntry(2, typeof(Hammer)), + new FillableEntry(2, typeof(MouldingPlane)), + new FillableEntry(2, typeof(Nails)), + new FillableEntry(2, typeof(JointingPlane)), + new FillableEntry(2, typeof(SmoothingPlane)), + new FillableEntry(2, typeof(Saw)), + new FillableEntry(2, typeof(DrawKnife)), + new FillableEntry(1, typeof(Log)), + new FillableEntry(1, typeof(Froe)), + new FillableEntry(1, typeof(Inshave)), + new FillableEntry(1, typeof(Scorp)) + }); + + public static FillableContent Clothier = new FillableContent( + 1, + new[] + { + typeof(Tailor), + typeof(Weaver), + typeof(TailorGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(Cotton)), + new FillableEntry(1, typeof(Wool)), + new FillableEntry(1, typeof(DarkYarn)), + new FillableEntry(1, typeof(LightYarn)), + new FillableEntry(1, typeof(LightYarnUnraveled)), + new FillableEntry(1, typeof(SpoolOfThread)), + // Four different types + //new FillableEntry( 1, typeof( FoldedCloth ) ), + //new FillableEntry( 1, typeof( FoldedCloth ) ), + //new FillableEntry( 1, typeof( FoldedCloth ) ), + //new FillableEntry( 1, typeof( FoldedCloth ) ), + new FillableEntry(1, typeof(Dyes)), + new FillableEntry(2, typeof(Leather)) + }); + + public static FillableContent Cobbler = new FillableContent( + 1, + new[] + { + typeof(Cobbler) + }, + new[] + { + new FillableEntry(1, typeof(Boots)), + new FillableEntry(2, typeof(Shoes)), + new FillableEntry(2, typeof(Sandals)), + new FillableEntry(1, typeof(ThighBoots)) + }); + + public static FillableContent Docks = new FillableContent( + 1, + new[] + { + typeof(Fisherman), + typeof(FisherGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(FishingPole)), + // Two different types + //new FillableEntry( 1, typeof( SmallFish ) ), + //new FillableEntry( 1, typeof( SmallFish ) ), + new FillableEntry(4, typeof(Fish)) + }); + + public static FillableContent Farm = new FillableContent( + 1, + new[] + { + typeof(Farmer), + typeof(Rancher) + }, + new[] + { + new FillableEntry(1, typeof(Shirt)), + new FillableEntry(1, typeof(ShortPants)), + new FillableEntry(1, typeof(Skirt)), + new FillableEntry(1, typeof(PlainDress)), + new FillableEntry(1, typeof(Cap)), + new FillableEntry(2, typeof(Sandals)), + new FillableEntry(2, typeof(GnarledStaff)), + new FillableEntry(2, typeof(Pitchfork)), + new FillableEntry(1, typeof(Bag)), + new FillableEntry(1, typeof(Kindling)), + new FillableEntry(1, typeof(Lettuce)), + new FillableEntry(1, typeof(Onion)), + new FillableEntry(1, typeof(Turnip)), + new FillableEntry(1, typeof(Ham)), + new FillableEntry(1, typeof(Bacon)), + new FillableEntry(1, typeof(RawLambLeg)), + new FillableEntry(1, typeof(SheafOfHay)), + new FillableBvrge(1, typeof(Pitcher), BeverageType.Milk) + }); + + public static FillableContent FighterGuild = new FillableContent( + 3, + new[] + { + typeof(WarriorGuildmaster) + }, + new[] + { + new FillableEntry(12, Loot.ArmorTypes), + new FillableEntry(8, Loot.WeaponTypes), + new FillableEntry(3, Loot.ShieldTypes), + new FillableEntry(1, typeof(Arrow)) + }); + + public static FillableContent Guard = new FillableContent( + 3, + new Type[] + { + }, + new[] + { + new FillableEntry(12, Loot.ArmorTypes), + new FillableEntry(8, Loot.WeaponTypes), + new FillableEntry(3, Loot.ShieldTypes), + new FillableEntry(1, typeof(Arrow)) + }); + + public static FillableContent Healer = new FillableContent( + 1, + new[] + { + typeof(Healer), + typeof(HealerGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(Bandage)), + new FillableEntry(1, typeof(MortarPestle)), + new FillableEntry(1, typeof(LesserHealPotion)) + }); + + public static FillableContent Herbalist = new FillableContent( + 1, + new[] + { + typeof(Herbalist) + }, + new[] + { + new FillableEntry(10, typeof(Garlic)), + new FillableEntry(10, typeof(Ginseng)), + new FillableEntry(10, typeof(MandrakeRoot)), + new FillableEntry(1, typeof(DeadWood)), + new FillableEntry(1, typeof(WhiteDriedFlowers)), + new FillableEntry(1, typeof(GreenDriedFlowers)), + new FillableEntry(1, typeof(DriedOnions)), + new FillableEntry(1, typeof(DriedHerbs)) + }); + + public static FillableContent Inn = new FillableContent( + 1, + new Type[] + { + }, + new[] + { + new FillableEntry(1, typeof(Candle)), + new FillableEntry(1, typeof(Torch)), + new FillableEntry(1, typeof(Lantern)) + }); + + public static FillableContent Jeweler = new FillableContent( + 2, + new[] + { + typeof(Jeweler) + }, + new[] + { + new FillableEntry(1, typeof(GoldRing)), + new FillableEntry(1, typeof(GoldBracelet)), + new FillableEntry(1, typeof(GoldEarrings)), + new FillableEntry(1, typeof(GoldNecklace)), + new FillableEntry(1, typeof(GoldBeadNecklace)), + new FillableEntry(1, typeof(Necklace)), + new FillableEntry(1, typeof(Beads)), + new FillableEntry(9, Loot.GemTypes) + }); + + public static FillableContent Library = new FillableContent( + 1, + new[] + { + typeof(Scribe) + }, + new[] + { + new FillableEntry(8, Loot.LibraryBookTypes), + new FillableEntry(1, typeof(RedBook)), + new FillableEntry(1, typeof(BlueBook)) + }); + + public static FillableContent Mage = new FillableContent( + 2, + new[] + { + typeof(Mage), + typeof(HolyMage), + typeof(MageGuildmaster) + }, + new[] + { + new FillableEntry(16, typeof(BlankScroll)), + new FillableEntry(14, typeof(Spellbook)), + new FillableEntry(12, Loot.RegularScrollTypes, 0, 8), + new FillableEntry(11, Loot.RegularScrollTypes, 8, 8), + new FillableEntry(10, Loot.RegularScrollTypes, 16, 8), + new FillableEntry(9, Loot.RegularScrollTypes, 24, 8), + new FillableEntry(8, Loot.RegularScrollTypes, 32, 8), + new FillableEntry(7, Loot.RegularScrollTypes, 40, 8), + new FillableEntry(6, Loot.RegularScrollTypes, 48, 8), + new FillableEntry(5, Loot.RegularScrollTypes, 56, 8) + }); + + public static FillableContent Merchant = new FillableContent( + 1, + new[] + { + typeof(MerchantGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(CheeseWheel)), + new FillableEntry(1, typeof(CheeseWedge)), + new FillableEntry(1, typeof(CheeseSlice)), + new FillableEntry(1, typeof(Eggs)), + new FillableEntry(4, typeof(Fish)), + new FillableEntry(2, typeof(RawFishSteak)), + new FillableEntry(2, typeof(FishSteak)), + new FillableEntry(1, typeof(Apple)), + new FillableEntry(2, typeof(Banana)), + new FillableEntry(2, typeof(Bananas)), + new FillableEntry(2, typeof(OpenCoconut)), + new FillableEntry(1, typeof(SplitCoconut)), + new FillableEntry(1, typeof(Coconut)), + new FillableEntry(1, typeof(Dates)), + new FillableEntry(1, typeof(Grapes)), + new FillableEntry(1, typeof(Lemon)), + new FillableEntry(1, typeof(Lemons)), + new FillableEntry(1, typeof(Lime)), + new FillableEntry(1, typeof(Limes)), + new FillableEntry(1, typeof(Peach)), + new FillableEntry(1, typeof(Pear)), + new FillableEntry(2, typeof(SlabOfBacon)), + new FillableEntry(2, typeof(Bacon)), + new FillableEntry(2, typeof(CookedBird)), + new FillableEntry(2, typeof(RawBird)), + new FillableEntry(2, typeof(Ham)), + new FillableEntry(1, typeof(RawLambLeg)), + new FillableEntry(1, typeof(LambLeg)), + new FillableEntry(1, typeof(Ribs)), + new FillableEntry(1, typeof(RawRibs)), + new FillableEntry(2, typeof(Sausage)), + new FillableEntry(1, typeof(RawChickenLeg)), + new FillableEntry(1, typeof(ChickenLeg)), + new FillableEntry(1, typeof(Watermelon)), + new FillableEntry(1, typeof(SmallWatermelon)), + new FillableEntry(3, typeof(Turnip)), + new FillableEntry(2, typeof(YellowGourd)), + new FillableEntry(2, typeof(GreenGourd)), + new FillableEntry(2, typeof(Pumpkin)), + new FillableEntry(1, typeof(SmallPumpkin)), + new FillableEntry(2, typeof(Onion)), + new FillableEntry(2, typeof(Lettuce)), + new FillableEntry(2, typeof(Squash)), + new FillableEntry(2, typeof(HoneydewMelon)), + new FillableEntry(1, typeof(Carrot)), + new FillableEntry(2, typeof(Cantaloupe)), + new FillableEntry(2, typeof(Cabbage)), + new FillableEntry(4, typeof(EarOfCorn)) + }); + + public static FillableContent Mill = new FillableContent( + 1, + new Type[] + { + }, + new[] + { + new FillableEntry(1, typeof(SackFlour)) + }); + + public static FillableContent Mine = new FillableContent( + 1, + new[] + { + typeof(Miner) + }, + new[] + { + new FillableEntry(2, typeof(Pickaxe)), + new FillableEntry(2, typeof(Shovel)), + new FillableEntry(2, typeof(IronIngot)), + //new FillableEntry( 2, typeof( IronOre ) ), TODO: Smaller Ore + new FillableEntry(1, typeof(ForgedMetal)) + }); + + public static FillableContent Observatory = new FillableContent( + 1, + new Type[] + { + }, + new[] + { + new FillableEntry(2, typeof(Sextant)), + new FillableEntry(2, typeof(Clock)), + new FillableEntry(1, typeof(Spyglass)) + }); + + public static FillableContent Painter = new FillableContent( + 1, + new Type[] + { + }, + new[] + { + new FillableEntry(1, typeof(PaintsAndBrush)), + new FillableEntry(2, typeof(PenAndInk)) + }); + + public static FillableContent Provisioner = new FillableContent( + 1, + new[] + { + typeof(Provisioner) + }, + new[] + { + new FillableEntry(1, typeof(CheeseWheel)), + new FillableEntry(1, typeof(CheeseWedge)), + new FillableEntry(1, typeof(CheeseSlice)), + new FillableEntry(1, typeof(Eggs)), + new FillableEntry(4, typeof(Fish)), + new FillableEntry(1, typeof(DirtyFrypan)), + new FillableEntry(1, typeof(DirtyPan)), + new FillableEntry(1, typeof(DirtyKettle)), + new FillableEntry(1, typeof(DirtySmallRoundPot)), + new FillableEntry(1, typeof(DirtyRoundPot)), + new FillableEntry(1, typeof(DirtySmallPot)), + new FillableEntry(1, typeof(DirtyPot)), + new FillableEntry(1, typeof(Apple)), + new FillableEntry(2, typeof(Banana)), + new FillableEntry(2, typeof(Bananas)), + new FillableEntry(2, typeof(OpenCoconut)), + new FillableEntry(1, typeof(SplitCoconut)), + new FillableEntry(1, typeof(Coconut)), + new FillableEntry(1, typeof(Dates)), + new FillableEntry(1, typeof(Grapes)), + new FillableEntry(1, typeof(Lemon)), + new FillableEntry(1, typeof(Lemons)), + new FillableEntry(1, typeof(Lime)), + new FillableEntry(1, typeof(Limes)), + new FillableEntry(1, typeof(Peach)), + new FillableEntry(1, typeof(Pear)), + new FillableEntry(2, typeof(SlabOfBacon)), + new FillableEntry(2, typeof(Bacon)), + new FillableEntry(1, typeof(RawFishSteak)), + new FillableEntry(1, typeof(FishSteak)), + new FillableEntry(2, typeof(CookedBird)), + new FillableEntry(2, typeof(RawBird)), + new FillableEntry(2, typeof(Ham)), + new FillableEntry(1, typeof(RawLambLeg)), + new FillableEntry(1, typeof(LambLeg)), + new FillableEntry(1, typeof(Ribs)), + new FillableEntry(1, typeof(RawRibs)), + new FillableEntry(2, typeof(Sausage)), + new FillableEntry(1, typeof(RawChickenLeg)), + new FillableEntry(1, typeof(ChickenLeg)), + new FillableEntry(1, typeof(Watermelon)), + new FillableEntry(1, typeof(SmallWatermelon)), + new FillableEntry(3, typeof(Turnip)), + new FillableEntry(2, typeof(YellowGourd)), + new FillableEntry(2, typeof(GreenGourd)), + new FillableEntry(2, typeof(Pumpkin)), + new FillableEntry(1, typeof(SmallPumpkin)), + new FillableEntry(2, typeof(Onion)), + new FillableEntry(2, typeof(Lettuce)), + new FillableEntry(2, typeof(Squash)), + new FillableEntry(2, typeof(HoneydewMelon)), + new FillableEntry(1, typeof(Carrot)), + new FillableEntry(2, typeof(Cantaloupe)), + new FillableEntry(2, typeof(Cabbage)), + new FillableEntry(4, typeof(EarOfCorn)) + }); + + public static FillableContent Ranger = new FillableContent( + 2, + new[] + { + typeof(Ranger), + typeof(RangerGuildmaster) + }, + new[] + { + new FillableEntry(2, typeof(StuddedChest)), + new FillableEntry(2, typeof(StuddedLegs)), + new FillableEntry(2, typeof(StuddedArms)), + new FillableEntry(2, typeof(StuddedGloves)), + new FillableEntry(1, typeof(StuddedGorget)), + + new FillableEntry(2, typeof(LeatherChest)), + new FillableEntry(2, typeof(LeatherLegs)), + new FillableEntry(2, typeof(LeatherArms)), + new FillableEntry(2, typeof(LeatherGloves)), + new FillableEntry(1, typeof(LeatherGorget)), + + new FillableEntry(2, typeof(FeatheredHat)), + new FillableEntry(1, typeof(CloseHelm)), + new FillableEntry(1, typeof(TallStrawHat)), + new FillableEntry(1, typeof(Bandana)), + new FillableEntry(1, typeof(Cloak)), + new FillableEntry(2, typeof(Boots)), + new FillableEntry(2, typeof(ThighBoots)), + + new FillableEntry(2, typeof(GnarledStaff)), + new FillableEntry(1, typeof(Whip)), + + new FillableEntry(2, typeof(Bow)), + new FillableEntry(2, typeof(Crossbow)), + new FillableEntry(2, typeof(HeavyCrossbow)), + new FillableEntry(4, typeof(Arrow)) + }); + + public static FillableContent Stables = new FillableContent( + 1, + new[] + { + typeof(AnimalTrainer), + typeof(GypsyAnimalTrainer) + }, + new[] + { + //new FillableEntry( 1, typeof( Wheat ) ), + new FillableEntry(1, typeof(Carrot)) + }); + + public static FillableContent Tanner = new FillableContent( + 2, + new[] + { + typeof(Tanner), + typeof(LeatherWorker), + typeof(Furtrader) + }, + new[] + { + new FillableEntry(1, typeof(FeatheredHat)), + new FillableEntry(1, typeof(LeatherArms)), + new FillableEntry(2, typeof(LeatherLegs)), + new FillableEntry(2, typeof(LeatherChest)), + new FillableEntry(2, typeof(LeatherGloves)), + new FillableEntry(1, typeof(LeatherGorget)), + new FillableEntry(2, typeof(Leather)) + }); + + public static FillableContent Tavern = new FillableContent( + 1, + new[] + { + typeof(TavernKeeper), + typeof(Barkeeper), + typeof(Waiter), + typeof(Cook) + }, + new FillableEntry[] + { + new FillableBvrge(1, typeof(BeverageBottle), BeverageType.Ale), + new FillableBvrge(1, typeof(BeverageBottle), BeverageType.Wine), + new FillableBvrge(1, typeof(BeverageBottle), BeverageType.Liquor), + new FillableBvrge(1, typeof(Jug), BeverageType.Cider) + }); + + public static FillableContent ThiefGuild = new FillableContent( + 1, + new[] + { + typeof(Thief), + typeof(ThiefGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(Lockpick)), + new FillableEntry(1, typeof(BearMask)), + new FillableEntry(1, typeof(DeerMask)), + new FillableEntry(1, typeof(TribalMask)), + new FillableEntry(1, typeof(HornedTribalMask)), + new FillableEntry(4, typeof(OrcHelm)) + }); + + public static FillableContent Tinker = new FillableContent( + 1, + new[] + { + typeof(Tinker), + typeof(TinkerGuildmaster) + }, + new[] + { + new FillableEntry(1, typeof(Lockpick)), + //new FillableEntry( 1, typeof( KeyRing ) ), + new FillableEntry(2, typeof(Clock)), + new FillableEntry(2, typeof(ClockParts)), + new FillableEntry(2, typeof(AxleGears)), + new FillableEntry(2, typeof(Gears)), + new FillableEntry(2, typeof(Hinge)), + //new FillableEntry( 1, typeof( ArrowShafts ) ), + new FillableEntry(2, typeof(Sextant)), + new FillableEntry(2, typeof(SextantParts)), + new FillableEntry(2, typeof(Axle)), + new FillableEntry(2, typeof(Springs)), + new FillableEntry(5, typeof(TinkerTools)), + new FillableEntry(4, typeof(Key)), + new FillableEntry(1, typeof(DecoArrowShafts)), + new FillableEntry(1, typeof(Lockpicks)), + new FillableEntry(1, typeof(ToolKit)) + }); + + public static FillableContent Veterinarian = new FillableContent( + 1, + new[] + { + typeof(Veterinarian) + }, + new[] + { + new FillableEntry(1, typeof(Bandage)), + new FillableEntry(1, typeof(MortarPestle)), + new FillableEntry(1, typeof(LesserHealPotion)), + //new FillableEntry( 1, typeof( Wheat ) ), + new FillableEntry(1, typeof(Carrot)) + }); + + public static FillableContent Weaponsmith = new FillableContent( + 2, + new[] + { + typeof(Weaponsmith) + }, + new[] + { + new FillableEntry(8, Loot.WeaponTypes), + new FillableEntry(1, typeof(Arrow)) + }); + + private static Hashtable m_AcquireTable; + + private static FillableContent[] m_ContentTypes = + { + Weaponsmith, Provisioner, Mage, + Alchemist, Armorer, ArtisanGuild, + Baker, Bard, Blacksmith, + Bowyer, Butcher, Carpenter, + Clothier, Cobbler, Docks, + Farm, FighterGuild, Guard, + Healer, Herbalist, Inn, + Jeweler, Library, Merchant, + Mill, Mine, Observatory, + Painter, Ranger, Stables, + Tanner, Tavern, ThiefGuild, + Tinker, Veterinarian + }; + + private FillableEntry[] m_Entries; + private int m_Weight; + + public FillableContent(int level, Type[] vendors, FillableEntry[] entries) + { + Level = level; + Vendors = vendors; + m_Entries = entries; + + for (int i = 0; i < entries.Length; ++i) + m_Weight += entries[i].Weight; + } + + public int Level{ get; } + + public Type[] Vendors{ get; } + + public FillableContentType TypeID => Lookup(this); + + public virtual Item Construct() + { + int index = Utility.Random(m_Weight); + + for (int i = 0; i < m_Entries.Length; ++i) + { + FillableEntry entry = m_Entries[i]; + + if (index < entry.Weight) + return entry.Construct(); + + index -= entry.Weight; + } + + return null; + } + + public static FillableContent Lookup(FillableContentType type) + { + int v = (int)type; + + if (v >= 0 && v < m_ContentTypes.Length) + return m_ContentTypes[v]; + + return null; + } + + public static FillableContentType Lookup(FillableContent content) + { + if (content == null) + return FillableContentType.None; + + return (FillableContentType)Array.IndexOf(m_ContentTypes, content); + } + + public static FillableContent Acquire(Point3D loc, Map map) + { + if (map == null || map == Map.Internal) + return null; + + if (m_AcquireTable == null) + { + m_AcquireTable = new Hashtable(); + + for (int i = 0; i < m_ContentTypes.Length; ++i) + { + FillableContent fill = m_ContentTypes[i]; + + for (int j = 0; j < fill.Vendors.Length; ++j) + m_AcquireTable[fill.Vendors[j]] = fill; + } + } + + Mobile nearest = null; + FillableContent content = null; + + foreach (Mobile mob in map.GetMobilesInRange(loc, 20)) + { + if (nearest != null && mob.GetDistanceToSqrt(loc) > nearest.GetDistanceToSqrt(loc) && + !(nearest is Cobbler && mob is Provisioner)) + continue; + + if (m_AcquireTable[mob.GetType()] is FillableContent check) + { + nearest = mob; + content = check; + } + } + + return content; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/FurnitureContainer.cs b/Scripts/Items/Containers/FurnitureContainer.cs index ad4db191b..f0babd11c 100644 --- a/Scripts/Items/Containers/FurnitureContainer.cs +++ b/Scripts/Items/Containers/FurnitureContainer.cs @@ -3,423 +3,437 @@ using System.Collections.Generic; namespace Server.Items { - [Furniture] - [Flippable( 0x2815, 0x2816 )] - public class TallCabinet : BaseContainer - { - [Constructible] - public TallCabinet() : base( 0x2815 ) - { - Weight = 1.0; - } - - public TallCabinet( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0x2817, 0x2818 )] - public class ShortCabinet : BaseContainer - { - [Constructible] - public ShortCabinet() : base( 0x2817 ) - { - Weight = 1.0; - } - - public ShortCabinet( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - - [Furniture] - [Flippable( 0x2857, 0x2858 )] - public class RedArmoire : BaseContainer - { - [Constructible] - public RedArmoire() : base( 0x2857 ) - { - Weight = 1.0; - } - - public RedArmoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0x285D, 0x285E )] - public class CherryArmoire : BaseContainer - { - [Constructible] - public CherryArmoire() : base( 0x285D ) - { - Weight = 1.0; - } - - public CherryArmoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0x285B, 0x285C )] - public class MapleArmoire : BaseContainer - { - [Constructible] - public MapleArmoire() : base( 0x285B ) - { - Weight = 1.0; - } - - public MapleArmoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0x2859, 0x285A )] - public class ElegantArmoire : BaseContainer - { - [Constructible] - public ElegantArmoire() : base( 0x2859 ) - { - Weight = 1.0; - } - - public ElegantArmoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0xa97, 0xa99, 0xa98, 0xa9a, 0xa9b, 0xa9c )] - public class FullBookcase : BaseContainer - { - [Constructible] - public FullBookcase() : base( 0xA97 ) - { - Weight = 1.0; - } - - public FullBookcase( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0xa9d, 0xa9e )] - public class EmptyBookcase : BaseContainer - { - [Constructible] - public EmptyBookcase() : base( 0xA9D ) - { - } - - public EmptyBookcase( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 1.0 ) - Weight = -1; - } - } - - [Furniture] - [Flippable( 0xa2c, 0xa34 )] - public class Drawer : BaseContainer - { - [Constructible] - public Drawer() : base( 0xA2C ) - { - Weight = 1.0; - } - - public Drawer( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0xa30, 0xa38 )] - public class FancyDrawer : BaseContainer - { - [Constructible] - public FancyDrawer() : base( 0xA30 ) - { - Weight = 1.0; - } - - public FancyDrawer( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - [Furniture] - [Flippable( 0xa4f, 0xa53 )] - public class Armoire : BaseContainer - { - [Constructible] - public Armoire() : base( 0xA4F ) - { - Weight = 1.0; - } - - public override void DisplayTo( Mobile m ) - { - if ( DynamicFurniture.Open( this, m ) ) - base.DisplayTo( m ); - } - - public Armoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - DynamicFurniture.Close( this ); - } - } - - [Furniture] - [Flippable( 0xa4d, 0xa51 )] - public class FancyArmoire : BaseContainer - { - [Constructible] - public FancyArmoire() : base( 0xA4D ) - { - Weight = 1.0; - } - - public override void DisplayTo( Mobile m ) - { - if ( DynamicFurniture.Open( this, m ) ) - base.DisplayTo( m ); - } - - public FancyArmoire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - DynamicFurniture.Close( this ); - } - } - - public class DynamicFurniture - { - private static Dictionary m_Table = new Dictionary(); - - public static bool Open( Container c, Mobile m ) - { - if ( m_Table.ContainsKey( c ) ) - { - c.SendRemovePacket(); - Close( c ); - c.Delta( ItemDelta.Update ); - c.ProcessDelta(); - return false; - } - - if ( c is Armoire || c is FancyArmoire ) - { - Timer t = new FurnitureTimer( c, m ); - t.Start(); - m_Table[c] = t; - - switch ( c.ItemID ) - { - case 0xA4D: c.ItemID = 0xA4C; break; - case 0xA4F: c.ItemID = 0xA4E; break; - case 0xA51: c.ItemID = 0xA50; break; - case 0xA53: c.ItemID = 0xA52; break; - } - } - - return true; - } - - public static void Close( Container c ) - { - m_Table.TryGetValue( c, out Timer t ); - - if ( t != null ) - { - t.Stop(); - m_Table.Remove( c ); - } - - if ( c is Armoire || c is FancyArmoire ) - { - switch ( c.ItemID ) - { - case 0xA4C: c.ItemID = 0xA4D; break; - case 0xA4E: c.ItemID = 0xA4F; break; - case 0xA50: c.ItemID = 0xA51; break; - case 0xA52: c.ItemID = 0xA53; break; - } - } - } - } - - public class FurnitureTimer : Timer - { - private Container m_Container; - private Mobile m_Mobile; - - public FurnitureTimer( Container c, Mobile m ) : base( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ) ) - { - Priority = TimerPriority.TwoFiftyMS; - - m_Container = c; - m_Mobile = m; - } - - protected override void OnTick() - { - if ( m_Mobile.Map != m_Container.Map || !m_Mobile.InRange( m_Container.GetWorldLocation(), 3 ) ) - DynamicFurniture.Close( m_Container ); - } - } -} + [Furniture] + [Flippable(0x2815, 0x2816)] + public class TallCabinet : BaseContainer + { + [Constructible] + public TallCabinet() : base(0x2815) + { + Weight = 1.0; + } + + public TallCabinet(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0x2817, 0x2818)] + public class ShortCabinet : BaseContainer + { + [Constructible] + public ShortCabinet() : base(0x2817) + { + Weight = 1.0; + } + + public ShortCabinet(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + + [Furniture] + [Flippable(0x2857, 0x2858)] + public class RedArmoire : BaseContainer + { + [Constructible] + public RedArmoire() : base(0x2857) + { + Weight = 1.0; + } + + public RedArmoire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0x285D, 0x285E)] + public class CherryArmoire : BaseContainer + { + [Constructible] + public CherryArmoire() : base(0x285D) + { + Weight = 1.0; + } + + public CherryArmoire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0x285B, 0x285C)] + public class MapleArmoire : BaseContainer + { + [Constructible] + public MapleArmoire() : base(0x285B) + { + Weight = 1.0; + } + + public MapleArmoire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0x2859, 0x285A)] + public class ElegantArmoire : BaseContainer + { + [Constructible] + public ElegantArmoire() : base(0x2859) + { + Weight = 1.0; + } + + public ElegantArmoire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0xa97, 0xa99, 0xa98, 0xa9a, 0xa9b, 0xa9c)] + public class FullBookcase : BaseContainer + { + [Constructible] + public FullBookcase() : base(0xA97) + { + Weight = 1.0; + } + + public FullBookcase(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0xa9d, 0xa9e)] + public class EmptyBookcase : BaseContainer + { + [Constructible] + public EmptyBookcase() : base(0xA9D) + { + } + + public EmptyBookcase(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (version == 0 && Weight == 1.0) + Weight = -1; + } + } + + [Furniture] + [Flippable(0xa2c, 0xa34)] + public class Drawer : BaseContainer + { + [Constructible] + public Drawer() : base(0xA2C) + { + Weight = 1.0; + } + + public Drawer(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0xa30, 0xa38)] + public class FancyDrawer : BaseContainer + { + [Constructible] + public FancyDrawer() : base(0xA30) + { + Weight = 1.0; + } + + public FancyDrawer(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + [Furniture] + [Flippable(0xa4f, 0xa53)] + public class Armoire : BaseContainer + { + [Constructible] + public Armoire() : base(0xA4F) + { + Weight = 1.0; + } + + public Armoire(Serial serial) : base(serial) + { + } + + public override void DisplayTo(Mobile m) + { + if (DynamicFurniture.Open(this, m)) + base.DisplayTo(m); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + DynamicFurniture.Close(this); + } + } + + [Furniture] + [Flippable(0xa4d, 0xa51)] + public class FancyArmoire : BaseContainer + { + [Constructible] + public FancyArmoire() : base(0xA4D) + { + Weight = 1.0; + } + + public FancyArmoire(Serial serial) : base(serial) + { + } + + public override void DisplayTo(Mobile m) + { + if (DynamicFurniture.Open(this, m)) + base.DisplayTo(m); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + DynamicFurniture.Close(this); + } + } + + public class DynamicFurniture + { + private static Dictionary m_Table = new Dictionary(); + + public static bool Open(Container c, Mobile m) + { + if (m_Table.ContainsKey(c)) + { + c.SendRemovePacket(); + Close(c); + c.Delta(ItemDelta.Update); + c.ProcessDelta(); + return false; + } + + if (c is Armoire || c is FancyArmoire) + { + Timer t = new FurnitureTimer(c, m); + t.Start(); + m_Table[c] = t; + + switch (c.ItemID) + { + case 0xA4D: + c.ItemID = 0xA4C; + break; + case 0xA4F: + c.ItemID = 0xA4E; + break; + case 0xA51: + c.ItemID = 0xA50; + break; + case 0xA53: + c.ItemID = 0xA52; + break; + } + } + + return true; + } + + public static void Close(Container c) + { + m_Table.TryGetValue(c, out Timer t); + + if (t != null) + { + t.Stop(); + m_Table.Remove(c); + } + + if (c is Armoire || c is FancyArmoire) + switch (c.ItemID) + { + case 0xA4C: + c.ItemID = 0xA4D; + break; + case 0xA4E: + c.ItemID = 0xA4F; + break; + case 0xA50: + c.ItemID = 0xA51; + break; + case 0xA52: + c.ItemID = 0xA53; + break; + } + } + } + + public class FurnitureTimer : Timer + { + private Container m_Container; + private Mobile m_Mobile; + + public FurnitureTimer(Container c, Mobile m) : base(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5)) + { + Priority = TimerPriority.TwoFiftyMS; + + m_Container = c; + m_Mobile = m; + } + + protected override void OnTick() + { + if (m_Mobile.Map != m_Container.Map || !m_Mobile.InRange(m_Container.GetWorldLocation(), 3)) + DynamicFurniture.Close(m_Container); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/LockableContainer.cs b/Scripts/Items/Containers/LockableContainer.cs index 82cc60c96..f1f3bbd5a 100644 --- a/Scripts/Items/Containers/LockableContainer.cs +++ b/Scripts/Items/Containers/LockableContainer.cs @@ -1,334 +1,332 @@ using System; -using Server.Network; using Server.Engines.Craft; +using Server.Network; namespace Server.Items { - public abstract class LockableContainer : TrappableContainer, ILockable, ILockpickable, ICraftable, IShipwreckedItem - { - private bool m_Locked; + public abstract class LockableContainer : TrappableContainer, ILockable, ILockpickable, ICraftable, IShipwreckedItem + { + private bool m_Locked; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Picker { get; set; } + public LockableContainer(int itemID) : base(itemID) + { + MaxLockLevel = 100; + } - [CommandProperty( AccessLevel.GameMaster )] - public int MaxLockLevel { get; set; } + public LockableContainer(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int LockLevel { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RequiredSkill { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool Locked - { - get => m_Locked; - set - { - m_Locked = value; - - if ( m_Locked ) - Picker = null; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public uint KeyValue { get; set; } - - public override bool TrapOnOpen => !TrapOnLockpick; - - [CommandProperty( AccessLevel.GameMaster )] - public bool TrapOnLockpick { get; set; } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 6 ); // version - - writer.Write( IsShipwreckedItem ); - - writer.Write( (bool) TrapOnLockpick ); - - writer.Write( (int) RequiredSkill ); - - writer.Write( (int) MaxLockLevel ); - - writer.Write( KeyValue ); - writer.Write( (int) LockLevel ); - writer.Write( (bool) m_Locked ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 6: - { - IsShipwreckedItem = reader.ReadBool(); - - goto case 5; - } - case 5: - { - TrapOnLockpick = reader.ReadBool(); - - goto case 4; - } - case 4: - { - RequiredSkill = reader.ReadInt(); - - goto case 3; - } - case 3: - { - MaxLockLevel = reader.ReadInt(); - - goto case 2; - } - case 2: - { - KeyValue = reader.ReadUInt(); - - goto case 1; - } - case 1: - { - LockLevel = reader.ReadInt(); - - goto case 0; - } - case 0: - { - if ( version < 3 ) - MaxLockLevel = 100; - - if ( version < 4 ) - { - if ( (MaxLockLevel - LockLevel) == 40 ) - { - RequiredSkill = LockLevel + 6; - LockLevel = RequiredSkill - 10; - MaxLockLevel = RequiredSkill + 39; - } - else - { - RequiredSkill = LockLevel; - } - } - - m_Locked = reader.ReadBool(); - - break; - } - } - } - - public LockableContainer( int itemID ) : base( itemID ) - { - MaxLockLevel = 100; - } - - public LockableContainer( Serial serial ) : base( serial ) - { - } - - public override bool CheckContentDisplay( Mobile from ) - { - return !m_Locked && base.CheckContentDisplay( from ); - } - - public override bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage ) - { - if ( from.AccessLevel < AccessLevel.GameMaster && m_Locked ) - { - from.SendLocalizedMessage( 501747 ); // It appears to be locked. - return false; - } - - return base.TryDropItem( from, dropped, sendFullMessage ); - } - - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( from.AccessLevel < AccessLevel.GameMaster && m_Locked ) - { - from.SendLocalizedMessage( 501747 ); // It appears to be locked. - return false; - } - - return base.OnDragDropInto( from, item, p ); - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( !base.CheckLift( from, item, ref reject ) ) - return false; - - if ( item != this && from.AccessLevel < AccessLevel.GameMaster && m_Locked ) - return false; - - return true; - } - - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( !base.CheckItemUse( from, item ) ) - return false; - - if ( item != this && from.AccessLevel < AccessLevel.GameMaster && m_Locked ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return false; - } - - return true; - } - - public override bool DisplaysContent => !m_Locked; - - public virtual bool CheckLocked( Mobile from ) - { - bool inaccessible = false; - - if ( m_Locked ) - { - int number; - - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - number = 502502; // That is locked, but you open it with your godly powers. - } - else - { - number = 501747; // It appears to be locked. - inaccessible = true; - } - - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", "" ) ); - } - - return inaccessible; - } - - public override void OnTelekinesis( Mobile from ) - { - if ( CheckLocked( from ) ) - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5022 ); - Effects.PlaySound( Location, Map, 0x1F5 ); - return; - } - - base.OnTelekinesis( from ); - } - - public override void OnDoubleClickSecureTrade( Mobile from ) - { - if ( CheckLocked( from ) ) - return; - - base.OnDoubleClickSecureTrade( from ); - } - - public override void Open( Mobile from ) - { - if ( CheckLocked( from ) ) - return; - - base.Open( from ); - } - - public override void OnSnoop( Mobile from ) - { - if ( CheckLocked( from ) ) - return; - - base.OnSnoop( from ); - } - - public virtual void LockPick( Mobile from ) - { - Locked = false; - Picker = from; - - if ( TrapOnLockpick && ExecuteTrap( from ) ) - { - TrapOnLockpick = false; - } - } + public override bool TrapOnOpen => !TrapOnLockpick; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public bool TrapOnLockpick{ get; set; } - if ( IsShipwreckedItem ) - list.Add( 1041645 ); // recovered from a shipwreck - } + public override bool DisplaysContent => !m_Locked; - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + #region ICraftable Members - if ( IsShipwreckedItem ) - LabelTo( from, 1041645 ); //recovered from a shipwreck - } + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + if (from.CheckSkill(SkillName.Tinkering, -5.0, 15.0)) + { + from.SendLocalizedMessage(500636); // Your tinker skill was sufficient to make the item lockable. - #region ICraftable Members + Key key = new Key(KeyType.Copper, Key.RandomValue()); - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - if ( from.CheckSkill( SkillName.Tinkering, -5.0, 15.0 ) ) - { - from.SendLocalizedMessage( 500636 ); // Your tinker skill was sufficient to make the item lockable. + KeyValue = key.KeyValue; + DropItem(key); - Key key = new Key( KeyType.Copper, Key.RandomValue() ); + double tinkering = from.Skills[SkillName.Tinkering].Value; + int level = (int)(tinkering * 0.8); - KeyValue = key.KeyValue; - DropItem( key ); + RequiredSkill = level - 4; + LockLevel = level - 14; + MaxLockLevel = level + 35; - double tinkering = from.Skills[SkillName.Tinkering].Value; - int level = (int)(tinkering * 0.8); + if (LockLevel == 0) + LockLevel = -1; + else if (LockLevel > 95) + LockLevel = 95; - RequiredSkill = level - 4; - LockLevel = level - 14; - MaxLockLevel = level + 35; + if (RequiredSkill > 95) + RequiredSkill = 95; - if ( LockLevel == 0 ) - LockLevel = -1; - else if ( LockLevel > 95 ) - LockLevel = 95; + if (MaxLockLevel > 95) + MaxLockLevel = 95; + } + else + { + from.SendLocalizedMessage(500637); // Your tinker skill was insufficient to make the item lockable. + } - if ( RequiredSkill > 95 ) - RequiredSkill = 95; + return 1; + } - if ( MaxLockLevel > 95 ) - MaxLockLevel = 95; - } - else - { - from.SendLocalizedMessage( 500637 ); // Your tinker skill was insufficient to make the item lockable. - } + #endregion - return 1; - } + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool Locked + { + get => m_Locked; + set + { + m_Locked = value; - #endregion + if (m_Locked) + Picker = null; - #region IShipwreckedItem Members + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsShipwreckedItem { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public uint KeyValue{ get; set; } - #endregion + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Picker{ get; set; } - } -} + [CommandProperty(AccessLevel.GameMaster)] + public int MaxLockLevel{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int LockLevel{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int RequiredSkill{ get; set; } + + public virtual void LockPick(Mobile from) + { + Locked = false; + Picker = from; + + if (TrapOnLockpick && ExecuteTrap(from)) TrapOnLockpick = false; + } + + #region IShipwreckedItem Members + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsShipwreckedItem{ get; set; } + + #endregion + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(6); // version + + writer.Write(IsShipwreckedItem); + + writer.Write(TrapOnLockpick); + + writer.Write(RequiredSkill); + + writer.Write(MaxLockLevel); + + writer.Write(KeyValue); + writer.Write(LockLevel); + writer.Write(m_Locked); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 6: + { + IsShipwreckedItem = reader.ReadBool(); + + goto case 5; + } + case 5: + { + TrapOnLockpick = reader.ReadBool(); + + goto case 4; + } + case 4: + { + RequiredSkill = reader.ReadInt(); + + goto case 3; + } + case 3: + { + MaxLockLevel = reader.ReadInt(); + + goto case 2; + } + case 2: + { + KeyValue = reader.ReadUInt(); + + goto case 1; + } + case 1: + { + LockLevel = reader.ReadInt(); + + goto case 0; + } + case 0: + { + if (version < 3) + MaxLockLevel = 100; + + if (version < 4) + { + if (MaxLockLevel - LockLevel == 40) + { + RequiredSkill = LockLevel + 6; + LockLevel = RequiredSkill - 10; + MaxLockLevel = RequiredSkill + 39; + } + else + { + RequiredSkill = LockLevel; + } + } + + m_Locked = reader.ReadBool(); + + break; + } + } + } + + public override bool CheckContentDisplay(Mobile from) + { + return !m_Locked && base.CheckContentDisplay(from); + } + + public override bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage) + { + if (from.AccessLevel < AccessLevel.GameMaster && m_Locked) + { + from.SendLocalizedMessage(501747); // It appears to be locked. + return false; + } + + return base.TryDropItem(from, dropped, sendFullMessage); + } + + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (from.AccessLevel < AccessLevel.GameMaster && m_Locked) + { + from.SendLocalizedMessage(501747); // It appears to be locked. + return false; + } + + return base.OnDragDropInto(from, item, p); + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (!base.CheckLift(from, item, ref reject)) + return false; + + if (item != this && from.AccessLevel < AccessLevel.GameMaster && m_Locked) + return false; + + return true; + } + + public override bool CheckItemUse(Mobile from, Item item) + { + if (!base.CheckItemUse(from, item)) + return false; + + if (item != this && from.AccessLevel < AccessLevel.GameMaster && m_Locked) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return false; + } + + return true; + } + + public virtual bool CheckLocked(Mobile from) + { + bool inaccessible = false; + + if (m_Locked) + { + int number; + + if (from.AccessLevel >= AccessLevel.GameMaster) + { + number = 502502; // That is locked, but you open it with your godly powers. + } + else + { + number = 501747; // It appears to be locked. + inaccessible = true; + } + + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", "")); + } + + return inaccessible; + } + + public override void OnTelekinesis(Mobile from) + { + if (CheckLocked(from)) + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x376A, 9, 32, + 5022); + Effects.PlaySound(Location, Map, 0x1F5); + return; + } + + base.OnTelekinesis(from); + } + + public override void OnDoubleClickSecureTrade(Mobile from) + { + if (CheckLocked(from)) + return; + + base.OnDoubleClickSecureTrade(from); + } + + public override void Open(Mobile from) + { + if (CheckLocked(from)) + return; + + base.Open(from); + } + + public override void OnSnoop(Mobile from) + { + if (CheckLocked(from)) + return; + + base.OnSnoop(from); + } + + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + + if (IsShipwreckedItem) + list.Add(1041645); // recovered from a shipwreck + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (IsShipwreckedItem) + LabelTo(from, 1041645); //recovered from a shipwreck + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/MarkContainer.cs b/Scripts/Items/Containers/MarkContainer.cs index 143055c47..ee4fd7614 100644 --- a/Scripts/Items/Containers/MarkContainer.cs +++ b/Scripts/Items/Containers/MarkContainer.cs @@ -3,245 +3,244 @@ using Server.Commands; namespace Server.Items { - public class MarkContainer : LockableContainer - { - public static void Initialize() - { - CommandSystem.Register( "SecretLocGen", AccessLevel.Administrator, SecretLocGen_OnCommand ); - } + public class MarkContainer : LockableContainer + { + private bool m_AutoLock; + private InternalTimer m_RelockTimer; - [Usage( "SecretLocGen" )] - [Description( "Generates mark containers to Malas secret locations." )] - public static void SecretLocGen_OnCommand( CommandEventArgs e ) - { - CreateMalasPassage( 951, 546, -70, 1006, 994, -70, false, false ); - CreateMalasPassage( 914, 192, -79, 1019, 1062, -70, false, false ); - CreateMalasPassage( 1614, 143, -90, 1214, 1313, -90, false, false ); - CreateMalasPassage( 2176, 324, -90, 1554, 172, -90, false, false ); - CreateMalasPassage( 864, 812, -90, 1061, 1161, -70, false, false ); - CreateMalasPassage( 1051, 1434, -85, 1076, 1244, -70, false, true ); - CreateMalasPassage( 1326, 523, -87, 1201, 1554, -70, false, false ); - CreateMalasPassage( 424, 189, -1, 2333, 1501, -90, true, false ); - CreateMalasPassage( 1313, 1115, -85, 1183, 462, -45, false, false ); + [Constructible] + public MarkContainer() : this(false) + { + } - e.Mobile.SendMessage( "Secret mark containers have been created." ); - } + [Constructible] + public MarkContainer(bool bone) : this(bone, false) + { + } - private static bool FindMarkContainer( Point3D p, Map map ) - { - IPooledEnumerable eable = map.GetItemsInRange( p, 0 ); + [Constructible] + public MarkContainer(bool bone, bool locked) : base(bone ? 0xECA : 0xE79) + { + Movable = false; - foreach ( Item item in eable ) - { - if ( item.Z == p.Z ) - { - eable.Free(); - return true; - } - } + if (bone) + Hue = 1102; - eable.Free(); - return false; - } + m_AutoLock = locked; + Locked = locked; - private static void CreateMalasPassage( int x, int y, int z, int xTarget, int yTarget, int zTarget, bool bone, bool locked ) - { - Point3D location = new Point3D( x, y, z ); + if (locked) + LockLevel = -255; + } - if ( FindMarkContainer( location, Map.Malas ) ) - return; + public MarkContainer(Serial serial) : base(serial) + { + } - MarkContainer cont = new MarkContainer( bone, locked ); - cont.TargetMap = Map.Malas; - cont.Target = new Point3D( xTarget, yTarget, zTarget ); - cont.Description = "strange location"; + [CommandProperty(AccessLevel.GameMaster)] + public bool AutoLock + { + get => m_AutoLock; + set + { + m_AutoLock = value; - cont.MoveToWorld( location, Map.Malas ); - } + if (!m_AutoLock) + StopTimer(); + else if (!Locked && m_RelockTimer == null) + m_RelockTimer = new InternalTimer(this); + } + } - private bool m_AutoLock; - private InternalTimer m_RelockTimer; + [CommandProperty(AccessLevel.GameMaster)] + public Map TargetMap{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public bool AutoLock - { - get => m_AutoLock; - set - { - m_AutoLock = value; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Target{ get; set; } - if ( !m_AutoLock ) - StopTimer(); - else if ( !Locked && m_RelockTimer == null ) - m_RelockTimer = new InternalTimer( this ); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Bone + { + get => ItemID == 0xECA; + set + { + ItemID = value ? 0xECA : 0xE79; + Hue = value ? 1102 : 0; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public Map TargetMap { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public string Description{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Target { get; set; } + public override bool IsDecoContainer => false; - [CommandProperty( AccessLevel.GameMaster )] - public bool Bone - { - get => ItemID == 0xECA; - set - { - ItemID = value ? 0xECA : 0xE79; - Hue = value ? 1102 : 0; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public override bool Locked + { + get => base.Locked; + set + { + base.Locked = value; - [CommandProperty( AccessLevel.GameMaster )] - public string Description { get; set; } + if (m_AutoLock) + { + StopTimer(); - public override bool IsDecoContainer => false; + if (!Locked) + m_RelockTimer = new InternalTimer(this); + } + } + } - [Constructible] - public MarkContainer() : this( false ) - { - } + public static void Initialize() + { + CommandSystem.Register("SecretLocGen", AccessLevel.Administrator, SecretLocGen_OnCommand); + } - [Constructible] - public MarkContainer( bool bone ) : this( bone, false ) - { - } + [Usage("SecretLocGen")] + [Description("Generates mark containers to Malas secret locations.")] + public static void SecretLocGen_OnCommand(CommandEventArgs e) + { + CreateMalasPassage(951, 546, -70, 1006, 994, -70, false, false); + CreateMalasPassage(914, 192, -79, 1019, 1062, -70, false, false); + CreateMalasPassage(1614, 143, -90, 1214, 1313, -90, false, false); + CreateMalasPassage(2176, 324, -90, 1554, 172, -90, false, false); + CreateMalasPassage(864, 812, -90, 1061, 1161, -70, false, false); + CreateMalasPassage(1051, 1434, -85, 1076, 1244, -70, false, true); + CreateMalasPassage(1326, 523, -87, 1201, 1554, -70, false, false); + CreateMalasPassage(424, 189, -1, 2333, 1501, -90, true, false); + CreateMalasPassage(1313, 1115, -85, 1183, 462, -45, false, false); - [Constructible] - public MarkContainer( bool bone, bool locked ) : base( bone ? 0xECA : 0xE79 ) - { - Movable = false; + e.Mobile.SendMessage("Secret mark containers have been created."); + } - if ( bone ) - Hue = 1102; + private static bool FindMarkContainer(Point3D p, Map map) + { + IPooledEnumerable eable = map.GetItemsInRange(p, 0); - m_AutoLock = locked; - Locked = locked; + foreach (Item item in eable) + if (item.Z == p.Z) + { + eable.Free(); + return true; + } - if ( locked ) - LockLevel = -255; - } + eable.Free(); + return false; + } - public MarkContainer( Serial serial ) : base( serial ) - { - } + private static void CreateMalasPassage(int x, int y, int z, int xTarget, int yTarget, int zTarget, bool bone, + bool locked) + { + Point3D location = new Point3D(x, y, z); - [CommandProperty( AccessLevel.GameMaster )] - public override bool Locked - { - get => base.Locked; - set - { - base.Locked = value; + if (FindMarkContainer(location, Map.Malas)) + return; - if ( m_AutoLock ) - { - StopTimer(); + MarkContainer cont = new MarkContainer(bone, locked); + cont.TargetMap = Map.Malas; + cont.Target = new Point3D(xTarget, yTarget, zTarget); + cont.Description = "strange location"; - if ( !Locked ) - m_RelockTimer = new InternalTimer( this ); - } - } - } + cont.MoveToWorld(location, Map.Malas); + } - public void StopTimer() - { - m_RelockTimer?.Stop(); + public void StopTimer() + { + m_RelockTimer?.Stop(); - m_RelockTimer = null; - } + m_RelockTimer = null; + } - private class InternalTimer : Timer - { - public MarkContainer Container { get; } + public void Mark(RecallRune rune) + { + if (TargetMap != null) + { + rune.Marked = true; + rune.TargetMap = TargetMap; + rune.Target = Target; + rune.Description = Description; + rune.House = null; + } + } - public DateTime RelockTime { get; } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is RecallRune rune && base.OnDragDrop(from, dropped)) + { + Mark(rune); + return true; + } - public InternalTimer( MarkContainer container ) : this( container, TimeSpan.FromMinutes( 5.0 ) ) - { - } + return false; + } - public InternalTimer( MarkContainer container, TimeSpan delay ) : base( delay ) - { - Container = container; - RelockTime = DateTime.UtcNow + delay; + public override bool OnDragDropInto(Mobile from, Item dropped, Point3D p) + { + if (dropped is RecallRune rune && base.OnDragDropInto(from, dropped, p)) + { + Mark(rune); + return true; + } - Start(); - } + return false; + } - protected override void OnTick() - { - Container.Locked = true; - Container.LockLevel = -255; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void Mark( RecallRune rune ) - { - if ( TargetMap != null ) - { - rune.Marked = true; - rune.TargetMap = TargetMap; - rune.Target = Target; - rune.Description = Description; - rune.House = null; - } - } + writer.Write(0); // version - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is RecallRune rune && base.OnDragDrop( from, dropped ) ) - { - Mark( rune ); - return true; - } + writer.Write(m_AutoLock); - return false; - } + if (!Locked && m_AutoLock) + writer.WriteDeltaTime(m_RelockTimer.RelockTime); - public override bool OnDragDropInto( Mobile from, Item dropped, Point3D p ) - { - if ( dropped is RecallRune rune && base.OnDragDropInto( from, dropped, p ) ) - { - Mark( rune ); - return true; - } + writer.Write(TargetMap); + writer.Write(Target); + writer.Write(Description); + } - return false; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); - writer.Write( (int)0 ); // version + m_AutoLock = reader.ReadBool(); - writer.Write( m_AutoLock ); + if (!Locked && m_AutoLock) + m_RelockTimer = new InternalTimer(this, reader.ReadDeltaTime() - DateTime.UtcNow); - if ( !Locked && m_AutoLock ) - writer.WriteDeltaTime( m_RelockTimer.RelockTime ); + TargetMap = reader.ReadMap(); + Target = reader.ReadPoint3D(); + Description = reader.ReadString(); + } - writer.Write( TargetMap ); - writer.Write( Target ); - writer.Write( Description ); - } + private class InternalTimer : Timer + { + public InternalTimer(MarkContainer container) : this(container, TimeSpan.FromMinutes(5.0)) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public InternalTimer(MarkContainer container, TimeSpan delay) : base(delay) + { + Container = container; + RelockTime = DateTime.UtcNow + delay; - int version = reader.ReadInt(); + Start(); + } - m_AutoLock = reader.ReadBool(); + public MarkContainer Container{ get; } - if ( !Locked && m_AutoLock ) - m_RelockTimer = new InternalTimer( this, reader.ReadDeltaTime() - DateTime.UtcNow ); + public DateTime RelockTime{ get; } - TargetMap = reader.ReadMap(); - Target = reader.ReadPoint3D(); - Description = reader.ReadString(); - } - } -} + protected override void OnTick() + { + Container.Locked = true; + Container.LockLevel = -255; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/ParagonChest.cs b/Scripts/Items/Containers/ParagonChest.cs index b56de9d2d..cdc00abb7 100644 --- a/Scripts/Items/Containers/ParagonChest.cs +++ b/Scripts/Items/Containers/ParagonChest.cs @@ -1,202 +1,227 @@ namespace Server.Items { - [Flippable] - public class ParagonChest : LockableContainer - { - private static int[] m_ItemIDs = { - 0x9AB, 0xE40, 0xE41, 0xE7C - }; + [Flippable] + public class ParagonChest : LockableContainer + { + private static int[] m_ItemIDs = + { + 0x9AB, 0xE40, 0xE41, 0xE7C + }; - private static int[] m_Hues = { - 0x0, 0x455, 0x47E, 0x89F, 0x8A5, 0x8AB, - 0x966, 0x96D, 0x972, 0x973, 0x979 - }; + private static int[] m_Hues = + { + 0x0, 0x455, 0x47E, 0x89F, 0x8A5, 0x8AB, + 0x966, 0x96D, 0x972, 0x973, 0x979 + }; - private string m_Name; + private string m_Name; - [Constructible] - public ParagonChest( string name, int level ) : base( Utility.RandomList( m_ItemIDs ) ) - { - m_Name = name; - Hue = Utility.RandomList( m_Hues ); - Fill( level ); - } + [Constructible] + public ParagonChest(string name, int level) : base(Utility.RandomList(m_ItemIDs)) + { + m_Name = name; + Hue = Utility.RandomList(m_Hues); + Fill(level); + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick(from); - LabelTo( from, 1063449, m_Name ); - } + public ParagonChest(Serial serial) : base(serial) + { + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + LabelTo(from, 1063449, m_Name); + } - list.Add( 1063449, m_Name ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - private static void GetRandomAOSStats( out int attributeCount, out int min, out int max ) - { - int rnd = Utility.Random( 15 ); + list.Add(1063449, m_Name); + } - if ( rnd < 1 ) - { - attributeCount = Utility.RandomMinMax( 2, 6 ); - min = 20; max = 70; - } - else if ( rnd < 3 ) - { - attributeCount = Utility.RandomMinMax( 2, 4 ); - min = 20; max = 50; - } - else if ( rnd < 6 ) - { - attributeCount = Utility.RandomMinMax( 2, 3 ); - min = 20; max = 40; - } - else if ( rnd < 10 ) - { - attributeCount = Utility.RandomMinMax( 1, 2 ); - min = 10; max = 30; - } - else - { - attributeCount = 1; - min = 10; max = 20; - } - } + private static void GetRandomAOSStats(out int attributeCount, out int min, out int max) + { + int rnd = Utility.Random(15); - public void Flip() - { - switch ( ItemID ) - { - case 0x9AB : ItemID = 0xE7C; break; - case 0xE7C : ItemID = 0x9AB; break; + if (rnd < 1) + { + attributeCount = Utility.RandomMinMax(2, 6); + min = 20; + max = 70; + } + else if (rnd < 3) + { + attributeCount = Utility.RandomMinMax(2, 4); + min = 20; + max = 50; + } + else if (rnd < 6) + { + attributeCount = Utility.RandomMinMax(2, 3); + min = 20; + max = 40; + } + else if (rnd < 10) + { + attributeCount = Utility.RandomMinMax(1, 2); + min = 10; + max = 30; + } + else + { + attributeCount = 1; + min = 10; + max = 20; + } + } - case 0xE40 : ItemID = 0xE41; break; - case 0xE41 : ItemID = 0xE40; break; - } - } + public void Flip() + { + switch (ItemID) + { + case 0x9AB: + ItemID = 0xE7C; + break; + case 0xE7C: + ItemID = 0x9AB; + break; - private void Fill( int level ) - { - TrapType = TrapType.ExplosionTrap; - TrapPower = level * 25; - TrapLevel = level; - Locked = true; + case 0xE40: + ItemID = 0xE41; + break; + case 0xE41: + ItemID = 0xE40; + break; + } + } - switch ( level ) - { - case 1: RequiredSkill = 36; break; - case 2: RequiredSkill = 76; break; - case 3: RequiredSkill = 84; break; - case 4: RequiredSkill = 92; break; - case 5: RequiredSkill = 100; break; - } + private void Fill(int level) + { + TrapType = TrapType.ExplosionTrap; + TrapPower = level * 25; + TrapLevel = level; + Locked = true; - LockLevel = RequiredSkill - 10; - MaxLockLevel = RequiredSkill + 40; + switch (level) + { + case 1: + RequiredSkill = 36; + break; + case 2: + RequiredSkill = 76; + break; + case 3: + RequiredSkill = 84; + break; + case 4: + RequiredSkill = 92; + break; + case 5: + RequiredSkill = 100; + break; + } - DropItem( new Gold( level * 200 ) ); + LockLevel = RequiredSkill - 10; + MaxLockLevel = RequiredSkill + 40; - for ( int i = 0; i < level; ++i ) - DropItem( Loot.RandomScroll( 0, 63, SpellbookType.Regular ) ); + DropItem(new Gold(level * 200)); - for ( int i = 0; i < level * 2; ++i ) - { - Item item; + for (int i = 0; i < level; ++i) + DropItem(Loot.RandomScroll(0, 63, SpellbookType.Regular)); - if ( Core.AOS ) - item = Loot.RandomArmorOrShieldOrWeaponOrJewelry(); - else - item = Loot.RandomArmorOrShieldOrWeapon(); + for (int i = 0; i < level * 2; ++i) + { + Item item; - if ( item is BaseWeapon weapon ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( weapon, attributeCount, min, max ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)Utility.Random( 6 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random( 6 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random( 6 ); - } + if (Core.AOS) + item = Loot.RandomArmorOrShieldOrWeaponOrJewelry(); + else + item = Loot.RandomArmorOrShieldOrWeapon(); - DropItem( weapon ); - } - else if ( item is BaseArmor armor ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( armor, attributeCount, min, max ); - } - else - { - armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random( 6 ); - armor.Durability = (ArmorDurabilityLevel)Utility.Random( 6 ); - } + if (item is BaseWeapon weapon) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(weapon, attributeCount, min, max); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)Utility.Random(6); + weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random(6); + weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random(6); + } - DropItem( armor ); - } - else if ( item is BaseHat hat ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( hat, attributeCount, min, max ); - } + DropItem(weapon); + } + else if (item is BaseArmor armor) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(armor, attributeCount, min, max); + } + else + { + armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random(6); + armor.Durability = (ArmorDurabilityLevel)Utility.Random(6); + } - DropItem( hat ); - } - else if ( item is BaseJewel jewel ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( jewel, attributeCount, min, max ); + DropItem(armor); + } + else if (item is BaseHat hat) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(hat, attributeCount, min, max); + } - DropItem( jewel ); - } - } + DropItem(hat); + } + else if (item is BaseJewel jewel) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(jewel, attributeCount, min, max); - for ( int i = 0; i < level; i++ ) - { - Item item = Loot.RandomPossibleReagent(); - item.Amount = Utility.RandomMinMax( 40, 60 ); - DropItem( item ); - } + DropItem(jewel); + } + } - for ( int i = 0; i < level; i++ ) - { - Item item = Loot.RandomGem(); - DropItem( item ); - } + for (int i = 0; i < level; i++) + { + Item item = Loot.RandomPossibleReagent(); + item.Amount = Utility.RandomMinMax(40, 60); + DropItem(item); + } - DropItem( new TreasureMap( level + 1, ( Utility.RandomBool() ? Map.Felucca : Map.Trammel ) ) ); - } + for (int i = 0; i < level; i++) + { + Item item = Loot.RandomGem(); + DropItem(item); + } - public ParagonChest( Serial serial ) : base( serial ) - { - } + DropItem(new TreasureMap(level + 1, Utility.RandomBool() ? Map.Felucca : Map.Trammel)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Name ); - } + writer.Write(m_Name); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Name = Utility.Intern( reader.ReadString() ); - } - } -} + m_Name = Utility.Intern(reader.ReadString()); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/SalvageBag.cs b/Scripts/Items/Containers/SalvageBag.cs index a4be8ebd5..7f8d8703b 100644 --- a/Scripts/Items/Containers/SalvageBag.cs +++ b/Scripts/Items/Containers/SalvageBag.cs @@ -6,350 +6,373 @@ using Server.Network; namespace Server.Items { - public class SalvageBag : Bag + public class SalvageBag : Bag + { + private bool m_Failure; + + [Constructible] + public SalvageBag() + : this(Utility.RandomBlueHue()) { - private bool m_Failure; - - public override int LabelNumber => 1079931; // Salvage Bag - - [Constructible] - public SalvageBag() - : this( Utility.RandomBlueHue() ) - { - } - - [Constructible] - public SalvageBag( int hue ) - { - Weight = 2.0; - Hue = hue; - m_Failure = false; - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.Alive ) - { - list.Add( new SalvageIngotsEntry( this, IsChildOf( from.Backpack ) && Resmeltables() ) ); - list.Add( new SalvageClothEntry( this, IsChildOf( from.Backpack ) && Scissorables() ) ); - list.Add( new SalvageAllEntry( this, IsChildOf( from.Backpack ) && Resmeltables() && Scissorables() ) ); - } - } - - #region Checks - private bool Resmeltables() //Where context menu checks for metal items and dragon barding deeds - { - foreach (Item i in Items) - { - return i?.Deleted == false && ( - i is BaseWeapon weapon && CraftResources.GetType(weapon.Resource) == CraftResourceType.Metal || - i is BaseArmor armor && CraftResources.GetType(armor.Resource) == CraftResourceType.Metal || - i is DragonBardingDeed); - } - - return false; - } - - private bool Scissorables() //Where context menu checks for Leather items and cloth items - { - foreach( Item i in Items ) - { - if (!(i is IScissorable) || i.Deleted) - continue; - - if (i is BaseClothing || i is Cloth || i is BoltOfCloth || i is Hides || i is BonePile || - i is BaseArmor armor && CraftResources.GetType(armor.Resource) == CraftResourceType.Leather) - return true; - } - - return false; - } - #endregion - - #region Resmelt.cs - private bool Resmelt( Mobile from, Item item, CraftResource resource ) - { - try - { - if ( CraftResources.GetType( resource ) != CraftResourceType.Metal ) - return false; - - CraftResourceInfo info = CraftResources.GetInfo( resource ); - - if ( info == null || info.ResourceTypes.Length == 0 ) - return false; - - CraftItem craftItem = DefBlacksmithy.CraftSystem.CraftItems.SearchFor( item.GetType() ); - - if ( craftItem == null || craftItem.Resources.Count == 0 ) - return false; - - CraftRes craftResource = craftItem.Resources.GetAt( 0 ); - - if ( craftResource.Amount < 2 ) - return false; // Not enough metal to resmelt - - double difficulty = 0.0; - - switch ( resource ) - { - case CraftResource.DullCopper: difficulty = 65.0; break; - case CraftResource.ShadowIron: difficulty = 70.0; break; - case CraftResource.Copper: difficulty = 75.0; break; - case CraftResource.Bronze: difficulty = 80.0; break; - case CraftResource.Gold: difficulty = 85.0; break; - case CraftResource.Agapite: difficulty = 90.0; break; - case CraftResource.Verite: difficulty = 95.0; break; - case CraftResource.Valorite: difficulty = 99.0; break; - } - - Type resourceType = info.ResourceTypes[ 0 ]; - Item ingot = (Item)Activator.CreateInstance( resourceType ); - - if ( item is DragonBardingDeed || ( item is BaseArmor armor && armor.PlayerConstructed ) || ( item is BaseWeapon weapon && weapon.PlayerConstructed ) || ( item is BaseClothing clothing && clothing.PlayerConstructed ) ) - { - double mining = from.Skills[ SkillName.Mining ].Value; - if ( mining > 100.0 ) - mining = 100.0; - double amount = ( ( ( 4 + mining ) * craftResource.Amount - 4 ) * 0.0068 ); - if ( amount < 2 ) - ingot.Amount = 2; - else - ingot.Amount = (int)amount; - } - else - { - ingot.Amount = 2; - } - - if ( difficulty > from.Skills[ SkillName.Mining ].Value ) - { - m_Failure = true; - ingot.Delete(); - } - else - item.Delete(); - - from.AddToBackpack( ingot ); - - from.PlaySound( 0x2A ); - from.PlaySound( 0x240 ); - - return true; - } - catch( Exception ex ) - { - Console.WriteLine( ex.ToString() ); - } - - return false; - } - #endregion - - #region Salvaging - private void SalvageIngots( Mobile from ) - { - Item[] tools = from.Backpack.FindItemsByType( typeof( BaseTool ) ); - - bool ToolFound = false; - foreach( Item tool in tools ) - { - if ( tool is BaseTool baseTool && baseTool.CraftSystem == DefBlacksmithy.CraftSystem ) - ToolFound = true; - } - - if ( !ToolFound ) - { - from.SendLocalizedMessage( 1079822 ); // You need a blacksmithing tool in order to salvage ingots. - return; - } - - DefBlacksmithy.CheckAnvilAndForge( from, 2, out _, out var forge ); - - if ( !forge ) - { - from.SendLocalizedMessage( 1044265 ); // You must be near a forge. - return; - } - - int salvaged = 0; - int notSalvaged = 0; - - Container sBag = this; - - List smeltables = sBag.FindItemsByType(); - - foreach (Item item in smeltables) - { - if (item?.Deleted != false) - continue; - - if (item is BaseArmor armor && Resmelt(from, armor, armor.Resource) || - item is BaseWeapon weapon && Resmelt(from, weapon, weapon.Resource) || - item is DragonBardingDeed) - { - salvaged++; - } - else - { - notSalvaged++; - } - } - - if ( m_Failure ) - { - from.SendLocalizedMessage( 1079975 ); // You failed to smelt some metal for lack of skill. - m_Failure = false; - } - else - from.SendLocalizedMessage( 1079973, $"{salvaged}\t{salvaged + notSalvaged}"); // Salvaged: ~1_COUNT~/~2_NUM~ blacksmithed items - } - - private void SalvageCloth( Mobile from ) - { - if ( !(from.Backpack.FindItemByType( typeof( Scissors ) ) is Scissors scissors) ) - { - from.SendLocalizedMessage( 1079823 ); // You need scissors in order to salvage cloth. - return; - } - - int salvaged = 0; - int notSalvaged = 0; - - Container sBag = this; - - List scissorables = sBag.FindItemsByType(); - - for ( int i = scissorables.Count - 1; i >= 0; --i ) - { - Item item = scissorables[i]; - - if (!(item is IScissorable scissorable)) - continue; - - if ( Scissors.CanScissor( from, scissorable ) && scissorable.Scissor( from, scissors ) ) - ++salvaged; - else - ++notSalvaged; - } - - from.SendLocalizedMessage( 1079974, $"{salvaged}\t{salvaged + notSalvaged}"); // Salvaged: ~1_COUNT~/~2_NUM~ tailored items - - foreach (Item i in FindItemsByType(typeof(Item), true)) - { - if ( ( i is Leather ) || ( i is Cloth ) || ( i is SpinedLeather ) || ( i is HornedLeather ) || ( i is BarbedLeather ) || ( i is Bandage ) || ( i is Bone ) ) - { - from.AddToBackpack( i ); - } - } - } - - private void SalvageAll( Mobile from ) - { - SalvageIngots( from ); - - SalvageCloth( from ); - } - #endregion - - #region ContextMenuEntries - private class SalvageAllEntry : ContextMenuEntry - { - private SalvageBag m_Bag; - - public SalvageAllEntry( SalvageBag bag, bool enabled ) - : base( 6276 ) - { - m_Bag = bag; - - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } - - public override void OnClick() - { - if ( m_Bag.Deleted ) - return; - - Mobile from = Owner.From; - - if ( from.CheckAlive() ) - m_Bag.SalvageAll( from ); - } - } - - private class SalvageIngotsEntry : ContextMenuEntry - { - private SalvageBag m_Bag; - - public SalvageIngotsEntry( SalvageBag bag, bool enabled ) - : base( 6277 ) - { - m_Bag = bag; - - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } - - public override void OnClick() - { - if ( m_Bag.Deleted ) - return; - - Mobile from = Owner.From; - - if ( from.CheckAlive() ) - m_Bag.SalvageIngots( from ); - } - } - - private class SalvageClothEntry : ContextMenuEntry - { - private SalvageBag m_Bag; - - public SalvageClothEntry( SalvageBag bag, bool enabled ) - : base( 6278 ) - { - m_Bag = bag; - - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } - - public override void OnClick() - { - if ( m_Bag.Deleted ) - return; - - Mobile from = Owner.From; - - if ( from.CheckAlive() ) - m_Bag.SalvageCloth( from ); - } - } - #endregion - - #region Serialization - public SalvageBag( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - #endregion } -} + + [Constructible] + public SalvageBag(int hue) + { + Weight = 2.0; + Hue = hue; + m_Failure = false; + } + + public override int LabelNumber => 1079931; // Salvage Bag + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.Alive) + { + list.Add(new SalvageIngotsEntry(this, IsChildOf(from.Backpack) && Resmeltables())); + list.Add(new SalvageClothEntry(this, IsChildOf(from.Backpack) && Scissorables())); + list.Add(new SalvageAllEntry(this, IsChildOf(from.Backpack) && Resmeltables() && Scissorables())); + } + } + + #region Resmelt.cs + + private bool Resmelt(Mobile from, Item item, CraftResource resource) + { + try + { + if (CraftResources.GetType(resource) != CraftResourceType.Metal) + return false; + + CraftResourceInfo info = CraftResources.GetInfo(resource); + + if (info == null || info.ResourceTypes.Length == 0) + return false; + + CraftItem craftItem = DefBlacksmithy.CraftSystem.CraftItems.SearchFor(item.GetType()); + + if (craftItem == null || craftItem.Resources.Count == 0) + return false; + + CraftRes craftResource = craftItem.Resources.GetAt(0); + + if (craftResource.Amount < 2) + return false; // Not enough metal to resmelt + + double difficulty = 0.0; + + switch (resource) + { + case CraftResource.DullCopper: + difficulty = 65.0; + break; + case CraftResource.ShadowIron: + difficulty = 70.0; + break; + case CraftResource.Copper: + difficulty = 75.0; + break; + case CraftResource.Bronze: + difficulty = 80.0; + break; + case CraftResource.Gold: + difficulty = 85.0; + break; + case CraftResource.Agapite: + difficulty = 90.0; + break; + case CraftResource.Verite: + difficulty = 95.0; + break; + case CraftResource.Valorite: + difficulty = 99.0; + break; + } + + Type resourceType = info.ResourceTypes[0]; + Item ingot = (Item)Activator.CreateInstance(resourceType); + + if (item is DragonBardingDeed || item is BaseArmor armor && armor.PlayerConstructed || + item is BaseWeapon weapon && weapon.PlayerConstructed || + item is BaseClothing clothing && clothing.PlayerConstructed) + { + double mining = from.Skills[SkillName.Mining].Value; + if (mining > 100.0) + mining = 100.0; + double amount = ((4 + mining) * craftResource.Amount - 4) * 0.0068; + if (amount < 2) + ingot.Amount = 2; + else + ingot.Amount = (int)amount; + } + else + { + ingot.Amount = 2; + } + + if (difficulty > from.Skills[SkillName.Mining].Value) + { + m_Failure = true; + ingot.Delete(); + } + else + { + item.Delete(); + } + + from.AddToBackpack(ingot); + + from.PlaySound(0x2A); + from.PlaySound(0x240); + + return true; + } + catch (Exception ex) + { + Console.WriteLine(ex.ToString()); + } + + return false; + } + + #endregion + + #region Checks + + private bool Resmeltables() //Where context menu checks for metal items and dragon barding deeds + { + foreach (Item i in Items) + return i?.Deleted == false && ( + i is BaseWeapon weapon && CraftResources.GetType(weapon.Resource) == CraftResourceType.Metal || + i is BaseArmor armor && CraftResources.GetType(armor.Resource) == CraftResourceType.Metal || + i is DragonBardingDeed); + + return false; + } + + private bool Scissorables() //Where context menu checks for Leather items and cloth items + { + foreach (Item i in Items) + { + if (!(i is IScissorable) || i.Deleted) + continue; + + if (i is BaseClothing || i is Cloth || i is BoltOfCloth || i is Hides || i is BonePile || + i is BaseArmor armor && CraftResources.GetType(armor.Resource) == CraftResourceType.Leather) + return true; + } + + return false; + } + + #endregion + + #region Salvaging + + private void SalvageIngots(Mobile from) + { + Item[] tools = from.Backpack.FindItemsByType(typeof(BaseTool)); + + bool ToolFound = false; + foreach (Item tool in tools) + if (tool is BaseTool baseTool && baseTool.CraftSystem == DefBlacksmithy.CraftSystem) + ToolFound = true; + + if (!ToolFound) + { + from.SendLocalizedMessage(1079822); // You need a blacksmithing tool in order to salvage ingots. + return; + } + + DefBlacksmithy.CheckAnvilAndForge(from, 2, out _, out bool forge); + + if (!forge) + { + from.SendLocalizedMessage(1044265); // You must be near a forge. + return; + } + + int salvaged = 0; + int notSalvaged = 0; + + Container sBag = this; + + List smeltables = sBag.FindItemsByType(); + + foreach (Item item in smeltables) + { + if (item?.Deleted != false) + continue; + + if (item is BaseArmor armor && Resmelt(from, armor, armor.Resource) || + item is BaseWeapon weapon && Resmelt(from, weapon, weapon.Resource) || + item is DragonBardingDeed) + salvaged++; + else + notSalvaged++; + } + + if (m_Failure) + { + from.SendLocalizedMessage(1079975); // You failed to smelt some metal for lack of skill. + m_Failure = false; + } + else + { + from.SendLocalizedMessage(1079973, + $"{salvaged}\t{salvaged + notSalvaged}"); // Salvaged: ~1_COUNT~/~2_NUM~ blacksmithed items + } + } + + private void SalvageCloth(Mobile from) + { + if (!(from.Backpack.FindItemByType(typeof(Scissors)) is Scissors scissors)) + { + from.SendLocalizedMessage(1079823); // You need scissors in order to salvage cloth. + return; + } + + int salvaged = 0; + int notSalvaged = 0; + + Container sBag = this; + + List scissorables = sBag.FindItemsByType(); + + for (int i = scissorables.Count - 1; i >= 0; --i) + { + Item item = scissorables[i]; + + if (!(item is IScissorable scissorable)) + continue; + + if (Scissors.CanScissor(from, scissorable) && scissorable.Scissor(from, scissors)) + ++salvaged; + else + ++notSalvaged; + } + + from.SendLocalizedMessage(1079974, + $"{salvaged}\t{salvaged + notSalvaged}"); // Salvaged: ~1_COUNT~/~2_NUM~ tailored items + + foreach (Item i in FindItemsByType(typeof(Item), true)) + if (i is Leather || i is Cloth || i is SpinedLeather || i is HornedLeather || i is BarbedLeather || + i is Bandage || i is Bone) + from.AddToBackpack(i); + } + + private void SalvageAll(Mobile from) + { + SalvageIngots(from); + + SalvageCloth(from); + } + + #endregion + + #region ContextMenuEntries + + private class SalvageAllEntry : ContextMenuEntry + { + private SalvageBag m_Bag; + + public SalvageAllEntry(SalvageBag bag, bool enabled) + : base(6276) + { + m_Bag = bag; + + if (!enabled) + Flags |= CMEFlags.Disabled; + } + + public override void OnClick() + { + if (m_Bag.Deleted) + return; + + Mobile from = Owner.From; + + if (from.CheckAlive()) + m_Bag.SalvageAll(from); + } + } + + private class SalvageIngotsEntry : ContextMenuEntry + { + private SalvageBag m_Bag; + + public SalvageIngotsEntry(SalvageBag bag, bool enabled) + : base(6277) + { + m_Bag = bag; + + if (!enabled) + Flags |= CMEFlags.Disabled; + } + + public override void OnClick() + { + if (m_Bag.Deleted) + return; + + Mobile from = Owner.From; + + if (from.CheckAlive()) + m_Bag.SalvageIngots(from); + } + } + + private class SalvageClothEntry : ContextMenuEntry + { + private SalvageBag m_Bag; + + public SalvageClothEntry(SalvageBag bag, bool enabled) + : base(6278) + { + m_Bag = bag; + + if (!enabled) + Flags |= CMEFlags.Disabled; + } + + public override void OnClick() + { + if (m_Bag.Deleted) + return; + + Mobile from = Owner.From; + + if (from.CheckAlive()) + m_Bag.SalvageCloth(from); + } + } + + #endregion + + #region Serialization + + public SalvageBag(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/Strongbox.cs b/Scripts/Items/Containers/Strongbox.cs index a7c8a96bf..8c3aada18 100644 --- a/Scripts/Items/Containers/Strongbox.cs +++ b/Scripts/Items/Containers/Strongbox.cs @@ -4,155 +4,153 @@ using Server.Multis; namespace Server.Items { - [FlippableAttribute( 0xE80, 0x9A8 )] - public class StrongBox : BaseContainer, IChopable - { - private Mobile m_Owner; - private BaseHouse m_House; + [Flippable(0xE80, 0x9A8)] + public class StrongBox : BaseContainer, IChopable + { + private BaseHouse m_House; + private Mobile m_Owner; - public override double DefaultWeight => 100; - public override int LabelNumber => 1023712; + public StrongBox(Mobile owner, BaseHouse house) : base(0xE80) + { + m_Owner = owner; + m_House = house; - public StrongBox( Mobile owner, BaseHouse house ) : base( 0xE80 ) - { - m_Owner = owner; - m_House = house; + MaxItems = 25; + } - MaxItems = 25; - } + public StrongBox(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner - { - get => m_Owner; - set - { - m_Owner = value; - InvalidateProperties(); - } - } + public override double DefaultWeight => 100; + public override int LabelNumber => 1023712; - public override int DefaultMaxWeight => 0; + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner + { + get => m_Owner; + set + { + m_Owner = value; + InvalidateProperties(); + } + } - public StrongBox( Serial serial ) : base(serial) - { - } + public override int DefaultMaxWeight => 0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool Decays + { + get + { + if (m_House != null && m_Owner != null && !m_Owner.Deleted) + return !m_House.IsCoOwner(m_Owner); + return true; + } + } - writer.Write( (int) 0 ); // version + public override TimeSpan DecayTime => TimeSpan.FromMinutes(30.0); - writer.Write( m_Owner ); - writer.Write( m_House ); - } + public void OnChop(Mobile from) + { + if (m_House != null && !m_House.Deleted && m_Owner != null && !m_Owner.Deleted) + { + if (from == m_Owner || m_House.IsOwner(from)) + Chop(from); + } + else + { + Chop(from); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(0); // version - switch ( version ) - { - case 0: - { - m_Owner = reader.ReadMobile(); - m_House = reader.ReadItem() as BaseHouse; + writer.Write(m_Owner); + writer.Write(m_House); + } - break; - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), Validate ); - } + int version = reader.ReadInt(); - private void Validate() - { - if ( m_Owner != null && m_House != null && !m_House.IsCoOwner( m_Owner ) ) - { - Console.WriteLine( "Warning: Destroying strongbox of {0}", m_Owner.Name ); - Destroy(); - } - } + switch (version) + { + case 0: + { + m_Owner = reader.ReadMobile(); + m_House = reader.ReadItem() as BaseHouse; - public override bool Decays - { - get - { - if ( m_House != null && m_Owner != null && !m_Owner.Deleted ) - return !m_House.IsCoOwner( m_Owner ); - return true; - } - } + break; + } + } - public override TimeSpan DecayTime => TimeSpan.FromMinutes( 30.0 ); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), Validate); + } - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_Owner != null ) - list.Add( 1042887, m_Owner.Name ); // a strong box owned by ~1_OWNER_NAME~ - else - base.AddNameProperty( list ); - } + private void Validate() + { + if (m_Owner != null && m_House != null && !m_House.IsCoOwner(m_Owner)) + { + Console.WriteLine("Warning: Destroying strongbox of {0}", m_Owner.Name); + Destroy(); + } + } - public override void OnSingleClick( Mobile from ) - { - if ( m_Owner != null ) - { - LabelTo( from, 1042887, m_Owner.Name ); // a strong box owned by ~1_OWNER_NAME~ + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_Owner != null) + list.Add(1042887, m_Owner.Name); // a strong box owned by ~1_OWNER_NAME~ + else + base.AddNameProperty(list); + } - if ( CheckContentDisplay( from ) ) - LabelTo( from, "({0} items, {1} stones)", TotalItems, TotalWeight ); - } - else - { - base.OnSingleClick( from ); - } - } + public override void OnSingleClick(Mobile from) + { + if (m_Owner != null) + { + LabelTo(from, 1042887, m_Owner.Name); // a strong box owned by ~1_OWNER_NAME~ - public override bool IsAccessibleTo( Mobile m ) - { - if ( m_Owner == null || m_Owner.Deleted || m_House == null || m_House.Deleted || m.AccessLevel >= AccessLevel.GameMaster ) - return true; + if (CheckContentDisplay(from)) + LabelTo(from, "({0} items, {1} stones)", TotalItems, TotalWeight); + } + else + { + base.OnSingleClick(from); + } + } - return m == m_Owner && m_House.IsCoOwner( m ) && base.IsAccessibleTo( m ); - } + public override bool IsAccessibleTo(Mobile m) + { + if (m_Owner == null || m_Owner.Deleted || m_House == null || m_House.Deleted || + m.AccessLevel >= AccessLevel.GameMaster) + return true; - private void Chop( Mobile from ) - { - Effects.PlaySound( Location, Map, 0x3B3 ); - from.SendLocalizedMessage( 500461 ); // You destroy the item. - Destroy(); - } + return m == m_Owner && m_House.IsCoOwner(m) && base.IsAccessibleTo(m); + } - public void OnChop( Mobile from ) - { - if ( m_House != null && !m_House.Deleted && m_Owner != null && !m_Owner.Deleted ) - { - if ( from == m_Owner || m_House.IsOwner( from ) ) - Chop( from ); - } - else - { - Chop( from ); - } - } + private void Chop(Mobile from) + { + Effects.PlaySound(Location, Map, 0x3B3); + from.SendLocalizedMessage(500461); // You destroy the item. + Destroy(); + } - public Container ConvertToStandardContainer() - { - Container metalBox = new MetalBox(); - List subItems = new List( Items ); + public Container ConvertToStandardContainer() + { + Container metalBox = new MetalBox(); + List subItems = new List(Items); - foreach ( Item subItem in subItems ) - { - metalBox.AddItem( subItem ); - } + foreach (Item subItem in subItems) metalBox.AddItem(subItem); - Delete(); + Delete(); - return metalBox; - } - } -} + return metalBox; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/TrappableContainer.cs b/Scripts/Items/Containers/TrappableContainer.cs index a79b19890..c5de08e12 100644 --- a/Scripts/Items/Containers/TrappableContainer.cs +++ b/Scripts/Items/Containers/TrappableContainer.cs @@ -1,226 +1,224 @@ using System; +using Server.Network; namespace Server.Items { - public enum TrapType - { - None, - MagicTrap, - ExplosionTrap, - DartTrap, - PoisonTrap - } + public enum TrapType + { + None, + MagicTrap, + ExplosionTrap, + DartTrap, + PoisonTrap + } - public abstract class TrappableContainer : BaseContainer, ITelekinesisable - { - [CommandProperty( AccessLevel.GameMaster )] - public TrapType TrapType { get; set; } + public abstract class TrappableContainer : BaseContainer, ITelekinesisable + { + public TrappableContainer(int itemID) : base(itemID) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int TrapPower { get; set; } + public TrappableContainer(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int TrapLevel { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public TrapType TrapType{ get; set; } - public virtual bool TrapOnOpen => true; + [CommandProperty(AccessLevel.GameMaster)] + public int TrapPower{ get; set; } - public TrappableContainer( int itemID ) : base( itemID ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int TrapLevel{ get; set; } - public TrappableContainer( Serial serial ) : base( serial ) - { - } + public virtual bool TrapOnOpen => true; - private void SendMessageTo( Mobile to, int number, int hue ) - { - if ( Deleted || !to.CanSee( this ) ) - return; + public virtual void OnTelekinesis(Mobile from) + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x376A, 9, 32, 5022); + Effects.PlaySound(Location, Map, 0x1F5); - to.Send( new Network.MessageLocalized( Serial, ItemID, Network.MessageType.Regular, hue, 3, number, "", "" ) ); - } + if (TrapOnOpen) ExecuteTrap(from); + } - private void SendMessageTo( Mobile to, string text, int hue ) - { - if ( Deleted || !to.CanSee( this ) ) - return; + private void SendMessageTo(Mobile to, int number, int hue) + { + if (Deleted || !to.CanSee(this)) + return; - to.Send( new Network.UnicodeMessage( Serial, ItemID, Network.MessageType.Regular, hue, 3, "ENU", "", text ) ); - } + to.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, hue, 3, number, "", "")); + } - public virtual bool ExecuteTrap( Mobile from ) - { - if ( TrapType != TrapType.None ) - { - Point3D loc = GetWorldLocation(); - Map facet = Map; + private void SendMessageTo(Mobile to, string text, int hue) + { + if (Deleted || !to.CanSee(this)) + return; - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - SendMessageTo( from, "That is trapped, but you open it with your godly powers.", 0x3B2 ); - return false; - } + to.Send(new UnicodeMessage(Serial, ItemID, MessageType.Regular, hue, 3, "ENU", "", text)); + } - switch ( TrapType ) - { - case TrapType.ExplosionTrap: - { - SendMessageTo( from, 502999, 0x3B2 ); // You set off a trap! + public virtual bool ExecuteTrap(Mobile from) + { + if (TrapType != TrapType.None) + { + Point3D loc = GetWorldLocation(); + Map facet = Map; - if ( from.InRange( loc, 3 ) ) - { - int damage; + if (from.AccessLevel >= AccessLevel.GameMaster) + { + SendMessageTo(from, "That is trapped, but you open it with your godly powers.", 0x3B2); + return false; + } - if ( TrapLevel > 0 ) - damage = Utility.RandomMinMax( 10, 30 ) * TrapLevel; - else - damage = TrapPower; + switch (TrapType) + { + case TrapType.ExplosionTrap: + { + SendMessageTo(from, 502999, 0x3B2); // You set off a trap! - AOS.Damage( from, damage, 0, 100, 0, 0, 0 ); + if (from.InRange(loc, 3)) + { + int damage; - // Your skin blisters from the heat! - from.LocalOverheadMessage( Network.MessageType.Regular, 0x2A, 503000 ); - } + if (TrapLevel > 0) + damage = Utility.RandomMinMax(10, 30) * TrapLevel; + else + damage = TrapPower; - Effects.SendLocationEffect( loc, facet, 0x36BD, 15, 10 ); - Effects.PlaySound( loc, facet, 0x307 ); + AOS.Damage(from, damage, 0, 100, 0, 0, 0); - break; - } - case TrapType.MagicTrap: - { - if ( from.InRange( loc, 1 ) ) - from.Damage( TrapPower ); - //AOS.Damage( from, m_TrapPower, 0, 100, 0, 0, 0 ); + // Your skin blisters from the heat! + from.LocalOverheadMessage(MessageType.Regular, 0x2A, 503000); + } - Effects.PlaySound( loc, Map, 0x307 ); + Effects.SendLocationEffect(loc, facet, 0x36BD, 15, 10); + Effects.PlaySound(loc, facet, 0x307); - Effects.SendLocationEffect( new Point3D( loc.X - 1, loc.Y, loc.Z ), Map, 0x36BD, 15 ); - Effects.SendLocationEffect( new Point3D( loc.X + 1, loc.Y, loc.Z ), Map, 0x36BD, 15 ); + break; + } + case TrapType.MagicTrap: + { + if (from.InRange(loc, 1)) + from.Damage(TrapPower); + //AOS.Damage( from, m_TrapPower, 0, 100, 0, 0, 0 ); - Effects.SendLocationEffect( new Point3D( loc.X, loc.Y - 1, loc.Z ), Map, 0x36BD, 15 ); - Effects.SendLocationEffect( new Point3D( loc.X, loc.Y + 1, loc.Z ), Map, 0x36BD, 15 ); + Effects.PlaySound(loc, Map, 0x307); - Effects.SendLocationEffect( new Point3D( loc.X + 1, loc.Y + 1, loc.Z + 11 ), Map, 0x36BD, 15 ); + Effects.SendLocationEffect(new Point3D(loc.X - 1, loc.Y, loc.Z), Map, 0x36BD, 15); + Effects.SendLocationEffect(new Point3D(loc.X + 1, loc.Y, loc.Z), Map, 0x36BD, 15); - break; - } - case TrapType.DartTrap: - { - SendMessageTo( from, 502999, 0x3B2 ); // You set off a trap! + Effects.SendLocationEffect(new Point3D(loc.X, loc.Y - 1, loc.Z), Map, 0x36BD, 15); + Effects.SendLocationEffect(new Point3D(loc.X, loc.Y + 1, loc.Z), Map, 0x36BD, 15); - if ( from.InRange( loc, 3 ) ) - { - int damage; + Effects.SendLocationEffect(new Point3D(loc.X + 1, loc.Y + 1, loc.Z + 11), Map, 0x36BD, 15); - if ( TrapLevel > 0 ) - damage = Utility.RandomMinMax( 5, 15 ) * TrapLevel; - else - damage = TrapPower; + break; + } + case TrapType.DartTrap: + { + SendMessageTo(from, 502999, 0x3B2); // You set off a trap! - AOS.Damage( from, damage, 100, 0, 0, 0, 0 ); + if (from.InRange(loc, 3)) + { + int damage; - // A dart imbeds itself in your flesh! - from.LocalOverheadMessage( Network.MessageType.Regular, 0x62, 502998 ); - } + if (TrapLevel > 0) + damage = Utility.RandomMinMax(5, 15) * TrapLevel; + else + damage = TrapPower; - Effects.PlaySound( loc, facet, 0x223 ); + AOS.Damage(from, damage, 100, 0, 0, 0, 0); - break; - } - case TrapType.PoisonTrap: - { - SendMessageTo( from, 502999, 0x3B2 ); // You set off a trap! + // A dart imbeds itself in your flesh! + from.LocalOverheadMessage(MessageType.Regular, 0x62, 502998); + } - if ( from.InRange( loc, 3 ) ) - { - Poison poison; + Effects.PlaySound(loc, facet, 0x223); - if ( TrapLevel > 0 ) - { - poison = Poison.GetPoison( Math.Max( 0, Math.Min( 4, TrapLevel - 1 ) ) ); - } - else - { - AOS.Damage( from, TrapPower, 0, 0, 0, 100, 0 ); - poison = Poison.Greater; - } + break; + } + case TrapType.PoisonTrap: + { + SendMessageTo(from, 502999, 0x3B2); // You set off a trap! - from.ApplyPoison( from, poison ); + if (from.InRange(loc, 3)) + { + Poison poison; - // You are enveloped in a noxious green cloud! - from.LocalOverheadMessage( Network.MessageType.Regular, 0x44, 503004 ); - } + if (TrapLevel > 0) + { + poison = Poison.GetPoison(Math.Max(0, Math.Min(4, TrapLevel - 1))); + } + else + { + AOS.Damage(from, TrapPower, 0, 0, 0, 100, 0); + poison = Poison.Greater; + } - Effects.SendLocationEffect( loc, facet, 0x113A, 10, 20 ); - Effects.PlaySound( loc, facet, 0x231 ); + from.ApplyPoison(from, poison); - break; - } - } + // You are enveloped in a noxious green cloud! + from.LocalOverheadMessage(MessageType.Regular, 0x44, 503004); + } - TrapType = TrapType.None; - TrapPower = 0; - TrapLevel = 0; - return true; - } + Effects.SendLocationEffect(loc, facet, 0x113A, 10, 20); + Effects.PlaySound(loc, facet, 0x231); - return false; - } + break; + } + } - public virtual void OnTelekinesis( Mobile from ) - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5022 ); - Effects.PlaySound( Location, Map, 0x1F5 ); + TrapType = TrapType.None; + TrapPower = 0; + TrapLevel = 0; + return true; + } - if ( TrapOnOpen ) - { - ExecuteTrap( from ); - } - } + return false; + } - public override void Open( Mobile from ) - { - if ( !TrapOnOpen || !ExecuteTrap( from ) ) - base.Open( from ); - } + public override void Open(Mobile from) + { + if (!TrapOnOpen || !ExecuteTrap(from)) + base.Open(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 2 ); // version + writer.Write(2); // version - writer.Write( (int) TrapLevel ); + writer.Write(TrapLevel); - writer.Write( (int) TrapPower ); - writer.Write( (int) TrapType ); - } + writer.Write(TrapPower); + writer.Write((int)TrapType); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 2: - { - TrapLevel = reader.ReadInt(); - goto case 1; - } - case 1: - { - TrapPower = reader.ReadInt(); - goto case 0; - } - case 0: - { - TrapType = (TrapType)reader.ReadInt(); - break; - } - } - } - } -} + switch (version) + { + case 2: + { + TrapLevel = reader.ReadInt(); + goto case 1; + } + case 1: + { + TrapPower = reader.ReadInt(); + goto case 0; + } + case 0: + { + TrapType = (TrapType)reader.ReadInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Containers/TreasureChest.cs b/Scripts/Items/Containers/TreasureChest.cs index ce3df3d30..6f34b4db8 100644 --- a/Scripts/Items/Containers/TreasureChest.cs +++ b/Scripts/Items/Containers/TreasureChest.cs @@ -1,83 +1,83 @@ namespace Server.Items { - [FlippableAttribute( 0xe43, 0xe42 )] - public class WoodenTreasureChest : BaseTreasureChest - { - [Constructible] - public WoodenTreasureChest() : base( 0xE43 ) - { - } + [Flippable(0xe43, 0xe42)] + public class WoodenTreasureChest : BaseTreasureChest + { + [Constructible] + public WoodenTreasureChest() : base(0xE43) + { + } - public WoodenTreasureChest( Serial serial ) : base( serial ) - { - } + public WoodenTreasureChest(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0xe41, 0xe40 )] - public class MetalGoldenTreasureChest : BaseTreasureChest - { - [Constructible] - public MetalGoldenTreasureChest() : base( 0xE41 ) - { - } + [Flippable(0xe41, 0xe40)] + public class MetalGoldenTreasureChest : BaseTreasureChest + { + [Constructible] + public MetalGoldenTreasureChest() : base(0xE41) + { + } - public MetalGoldenTreasureChest( Serial serial ) : base( serial ) - { - } + public MetalGoldenTreasureChest(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x9ab, 0xe7c )] - public class MetalTreasureChest : BaseTreasureChest - { - [Constructible] - public MetalTreasureChest() : base( 0x9AB ) - { - } + [Flippable(0x9ab, 0xe7c)] + public class MetalTreasureChest : BaseTreasureChest + { + [Constructible] + public MetalTreasureChest() : base(0x9AB) + { + } - public MetalTreasureChest( Serial serial ) : base( serial ) - { - } + public MetalTreasureChest(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Containers/TreasureMapChest.cs b/Scripts/Items/Containers/TreasureMapChest.cs index 8e9e3429a..402979173 100644 --- a/Scripts/Items/Containers/TreasureMapChest.cs +++ b/Scripts/Items/Containers/TreasureMapChest.cs @@ -7,531 +7,572 @@ using Server.Network; namespace Server.Items { - public class TreasureMapChest : LockableContainer - { - public override int LabelNumber => 3000541; - - public static Type[] Artifacts { get; } = - { - typeof( CandelabraOfSouls ), typeof( GoldBricks ), typeof( PhillipsWoodenSteed ), - typeof( ArcticDeathDealer ), typeof( BlazeOfDeath ), typeof( BurglarsBandana ), - typeof( CavortingClub ), typeof( DreadPirateHat ), - typeof( EnchantedTitanLegBone ), typeof( GwennosHarp ), typeof( IolosLute ), - typeof( LunaLance ), typeof( NightsKiss ), typeof( NoxRangersHeavyCrossbow ), - typeof( PolarBearMask ), typeof( VioletCourage ), typeof( HeartOfTheLion ), - typeof( ColdBlood ), typeof( AlchemistsBauble ) - }; - - private Timer m_Timer; - - [CommandProperty( AccessLevel.GameMaster )] - public int Level { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime DeleteTime { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Temporary { get; set; } - - public List Guardians { get; private set; } - - [Constructible] - public TreasureMapChest( int level ) : this( null, level, false ) - { - } - - public TreasureMapChest( Mobile owner, int level, bool temporary ) : base( 0xE40 ) - { - Owner = owner; - Level = level; - DeleteTime = DateTime.UtcNow + TimeSpan.FromHours( 3.0 ); - - Temporary = temporary; - Guardians = new List(); - - m_Timer = new DeleteTimer( this, DeleteTime ); - m_Timer.Start(); - - Fill( this, level ); - } - - private static void GetRandomAOSStats( out int attributeCount, out int min, out int max ) - { - int rnd = Utility.Random( 15 ); - - if ( Core.SE ) - { - if ( rnd < 1 ) - { - attributeCount = Utility.RandomMinMax( 3, 5 ); - min = 50; max = 100; - } - else if ( rnd < 3 ) - { - attributeCount = Utility.RandomMinMax( 2, 5 ); - min = 40; max = 80; - } - else if ( rnd < 6 ) - { - attributeCount = Utility.RandomMinMax( 2, 4 ); - min = 30; max = 60; - } - else if ( rnd < 10 ) - { - attributeCount = Utility.RandomMinMax( 1, 3 ); - min = 20; max = 40; - } - else - { - attributeCount = 1; - min = 10; max = 20; - } - } - else - { - if ( rnd < 1 ) - { - attributeCount = Utility.RandomMinMax( 2, 5 ); - min = 20; max = 70; - } - else if ( rnd < 3 ) - { - attributeCount = Utility.RandomMinMax( 2, 4 ); - min = 20; max = 50; - } - else if ( rnd < 6 ) - { - attributeCount = Utility.RandomMinMax( 2, 3 ); - min = 20; max = 40; - } - else if ( rnd < 10 ) - { - attributeCount = Utility.RandomMinMax( 1, 2 ); - min = 10; max = 30; - } - else - { - attributeCount = 1; - min = 10; max = 20; - } - } - } - - public static void Fill( LockableContainer cont, int level ) - { - cont.Movable = false; - cont.Locked = true; - int numberItems; - - if ( level == 0 ) - { - cont.LockLevel = 0; // Can't be unlocked - - cont.DropItem( new Gold( Utility.RandomMinMax( 50, 100 ) ) ); - - if ( Utility.RandomDouble() < 0.75 ) - cont.DropItem( new TreasureMap( 0, Map.Trammel ) ); - } - else - { - cont.TrapType = TrapType.ExplosionTrap; - cont.TrapPower = level * 25; - cont.TrapLevel = level; - - switch ( level ) - { - case 1: cont.RequiredSkill = 36; break; - case 2: cont.RequiredSkill = 76; break; - case 3: cont.RequiredSkill = 84; break; - case 4: cont.RequiredSkill = 92; break; - case 5: cont.RequiredSkill = 100; break; - case 6: cont.RequiredSkill = 100; break; - } - - cont.LockLevel = cont.RequiredSkill - 10; - cont.MaxLockLevel = cont.RequiredSkill + 40; - - //Publish 67 gold change - //if ( Core.SA ) - // cont.DropItem( new Gold( level * 5000 ) ); - //else - cont.DropItem( new Gold( level * 1000 ) ); - - for ( int i = 0; i < level * 5; ++i ) - cont.DropItem( Loot.RandomScroll( 0, 63, SpellbookType.Regular ) ); - - if ( Core.SE) - { - switch ( level ) - { - case 1: numberItems = 5; break; - case 2: numberItems = 10; break; - case 3: numberItems = 15; break; - case 4: numberItems = 38; break; - case 5: numberItems = 50; break; - case 6: numberItems = 60; break; - default: numberItems = 0; break; - }; - } - else - numberItems = level * 6; - - for ( int i = 0; i < numberItems; ++i ) - { - Item item; - - if ( Core.AOS ) - item = Loot.RandomArmorOrShieldOrWeaponOrJewelry(); - else - item = Loot.RandomArmorOrShieldOrWeapon(); - - if ( item is BaseWeapon weapon ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( weapon, attributeCount, min, max ); - } - else - { - weapon.DamageLevel = (WeaponDamageLevel)Utility.Random( 6 ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random( 6 ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random( 6 ); - } - - cont.DropItem( weapon ); - } - else if ( item is BaseArmor armor ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( armor, attributeCount, min, max ); - } - else - { - armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random( 6 ); - armor.Durability = (ArmorDurabilityLevel)Utility.Random( 6 ); - } - - cont.DropItem( armor ); - } - else if ( item is BaseHat hat ) - { - if ( Core.AOS ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( hat, attributeCount, min, max ); - } - - cont.DropItem( hat ); - } - else if ( item is BaseJewel jewel ) - { - GetRandomAOSStats( out var attributeCount, out var min, out var max ); - BaseRunicTool.ApplyAttributesTo( jewel, attributeCount, min, max ); - - cont.DropItem( jewel ); - } - } - } - - int reagents; - if ( level == 0 ) - reagents = 12; - else - reagents = level * 3; - - for ( int i = 0; i < reagents; i++ ) - { - Item item = Loot.RandomPossibleReagent(); - item.Amount = Utility.RandomMinMax( 40, 60 ); - cont.DropItem( item ); - } - - int gems; - if ( level == 0 ) - gems = 2; - else - gems = level * 3; - - for ( int i = 0; i < gems; i++ ) - { - Item item = Loot.RandomGem(); - cont.DropItem( item ); - } - - if ( level == 6 && Core.AOS ) - cont.DropItem( (Item)Activator.CreateInstance( Artifacts[Utility.Random(Artifacts.Length)] ) ); - } - - public override bool CheckLocked( Mobile from ) - { - if ( !Locked ) - return false; - - if ( Level == 0 && from.AccessLevel < AccessLevel.GameMaster ) - { - foreach ( Mobile m in Guardians ) - { - if ( m.Alive ) - { - from.SendLocalizedMessage( 1046448 ); // You must first kill the guardians before you may open this chest. - return true; - } - } - - LockPick( from ); - return false; - } - - return base.CheckLocked( from ); - } - - private List m_Lifted = new List(); - - private bool CheckLoot( Mobile m, bool criminalAction ) - { - if ( Temporary ) - return false; - - if ( m.AccessLevel >= AccessLevel.GameMaster || Owner == null || m == Owner ) - return true; - - Party p = Party.Get( Owner ); - - if ( p != null && p.Contains( m ) ) - return true; - - Map map = Map; - - if ( map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0 ) - { - if ( criminalAction ) - m.CriminalAction( true ); - else - m.SendLocalizedMessage( 1010630 ); // Taking someone else's treasure is a criminal offense! - - return true; - } - - m.SendLocalizedMessage( 1010631 ); // You did not discover this chest! - return false; - } - - public override bool IsDecoContainer => false; - - public override bool CheckItemUse( Mobile from, Item item ) - { - return CheckLoot( from, item != this ) && base.CheckItemUse( from, item ); - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - return CheckLoot( from, true ) && base.CheckLift( from, item, ref reject ); - } - - public override void OnItemLifted( Mobile from, Item item ) - { - bool notYetLifted = !m_Lifted.Contains( item ); - - from.RevealingAction(); - - if ( notYetLifted ) - { - m_Lifted.Add( item ); - - if ( 0.1 >= Utility.RandomDouble() ) // 10% chance to spawn a new monster - TreasureMap.Spawn( Level, GetWorldLocation(), Map, from, false ); - } - - base.OnItemLifted( from, item ); - } - - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if ( m.AccessLevel < AccessLevel.GameMaster ) - { - m.SendLocalizedMessage( 1048122, "", 0x8A5 ); // The chest refuses to be filled with treasure again. - return false; - } - - return base.CheckHold( m, item, message, checkItems, plusItems, plusWeight ); - } - - public TreasureMapChest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - - writer.Write( Guardians, true ); - writer.Write( (bool) Temporary ); - - writer.Write( Owner ); - - writer.Write( (int) Level ); - writer.WriteDeltaTime( DeleteTime ); - writer.Write( m_Lifted, true ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - { - Guardians = reader.ReadStrongMobileList(); - Temporary = reader.ReadBool(); - - goto case 1; - } - case 1: - { - Owner = reader.ReadMobile(); - - goto case 0; - } - case 0: - { - Level = reader.ReadInt(); - DeleteTime = reader.ReadDeltaTime(); - m_Lifted = reader.ReadStrongItemList(); - - if ( version < 2 ) - Guardians = new List(); - - break; - } - } - - if ( !Temporary ) - { - m_Timer = new DeleteTimer( this, DeleteTime ); - m_Timer.Start(); - } - else - { - Delete(); - } - } - - public override void OnAfterDelete() - { - m_Timer?.Stop(); - - m_Timer = null; - - base.OnAfterDelete(); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.Alive ) - list.Add( new RemoveEntry( from, this ) ); - } - - public void BeginRemove( Mobile from ) - { - if ( !from.Alive ) - return; - - from.CloseGump( typeof( RemoveGump ) ); - from.SendGump( new RemoveGump( from, this ) ); - } - - public void EndRemove( Mobile from ) - { - if ( Deleted || from != Owner || !from.InRange( GetWorldLocation(), 3 ) ) - return; - - from.SendLocalizedMessage( 1048124, "", 0x8A5 ); // The old, rusted chest crumbles when you hit it. - Delete(); - } - - private class RemoveGump : Gump - { - private Mobile m_From; - private TreasureMapChest m_Chest; - - public RemoveGump( Mobile from, TreasureMapChest chest ) : base( 15, 15 ) - { - m_From = from; - m_Chest = chest; - - Closable = false; - Disposable = false; - - AddPage( 0 ); - - AddBackground( 30, 0, 240, 240, 2620 ); - - AddHtmlLocalized( 45, 15, 200, 80, 1048125, 0xFFFFFF, false, false ); // When this treasure chest is removed, any items still inside of it will be lost. - AddHtmlLocalized( 45, 95, 200, 60, 1048126, 0xFFFFFF, false, false ); // Are you certain you're ready to remove this chest? - - AddButton( 40, 153, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 75, 155, 180, 40, 1048127, 0xFFFFFF, false, false ); // Remove the Treasure Chest - - AddButton( 40, 195, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 75, 197, 180, 35, 1006045, 0xFFFFFF, false, false ); // Cancel - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Chest.EndRemove( m_From ); - } - } - - private class RemoveEntry : ContextMenuEntry - { - private Mobile m_From; - private TreasureMapChest m_Chest; - - public RemoveEntry( Mobile from, TreasureMapChest chest ) : base( 6149, 3 ) - { - m_From = from; - m_Chest = chest; - - Enabled = ( from == chest.Owner ); - } - - public override void OnClick() - { - if ( m_Chest.Deleted || m_From != m_Chest.Owner || !m_From.CheckAlive() ) - return; - - m_Chest.BeginRemove( m_From ); - } - } - - private class DeleteTimer : Timer - { - private Item m_Item; - - public DeleteTimer( Item item, DateTime time ) : base( time - DateTime.UtcNow ) - { - m_Item = item; - Priority = TimerPriority.OneMinute; - } - - protected override void OnTick() - { - m_Item.Delete(); - } - } - } -} + public class TreasureMapChest : LockableContainer + { + private List m_Lifted = new List(); + + private Timer m_Timer; + + [Constructible] + public TreasureMapChest(int level) : this(null, level, false) + { + } + + public TreasureMapChest(Mobile owner, int level, bool temporary) : base(0xE40) + { + Owner = owner; + Level = level; + DeleteTime = DateTime.UtcNow + TimeSpan.FromHours(3.0); + + Temporary = temporary; + Guardians = new List(); + + m_Timer = new DeleteTimer(this, DeleteTime); + m_Timer.Start(); + + Fill(this, level); + } + + public TreasureMapChest(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 3000541; + + public static Type[] Artifacts{ get; } = + { + typeof(CandelabraOfSouls), typeof(GoldBricks), typeof(PhillipsWoodenSteed), + typeof(ArcticDeathDealer), typeof(BlazeOfDeath), typeof(BurglarsBandana), + typeof(CavortingClub), typeof(DreadPirateHat), + typeof(EnchantedTitanLegBone), typeof(GwennosHarp), typeof(IolosLute), + typeof(LunaLance), typeof(NightsKiss), typeof(NoxRangersHeavyCrossbow), + typeof(PolarBearMask), typeof(VioletCourage), typeof(HeartOfTheLion), + typeof(ColdBlood), typeof(AlchemistsBauble) + }; + + [CommandProperty(AccessLevel.GameMaster)] + public int Level{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime DeleteTime{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Temporary{ get; set; } + + public List Guardians{ get; private set; } + + public override bool IsDecoContainer => false; + + private static void GetRandomAOSStats(out int attributeCount, out int min, out int max) + { + int rnd = Utility.Random(15); + + if (Core.SE) + { + if (rnd < 1) + { + attributeCount = Utility.RandomMinMax(3, 5); + min = 50; + max = 100; + } + else if (rnd < 3) + { + attributeCount = Utility.RandomMinMax(2, 5); + min = 40; + max = 80; + } + else if (rnd < 6) + { + attributeCount = Utility.RandomMinMax(2, 4); + min = 30; + max = 60; + } + else if (rnd < 10) + { + attributeCount = Utility.RandomMinMax(1, 3); + min = 20; + max = 40; + } + else + { + attributeCount = 1; + min = 10; + max = 20; + } + } + else + { + if (rnd < 1) + { + attributeCount = Utility.RandomMinMax(2, 5); + min = 20; + max = 70; + } + else if (rnd < 3) + { + attributeCount = Utility.RandomMinMax(2, 4); + min = 20; + max = 50; + } + else if (rnd < 6) + { + attributeCount = Utility.RandomMinMax(2, 3); + min = 20; + max = 40; + } + else if (rnd < 10) + { + attributeCount = Utility.RandomMinMax(1, 2); + min = 10; + max = 30; + } + else + { + attributeCount = 1; + min = 10; + max = 20; + } + } + } + + public static void Fill(LockableContainer cont, int level) + { + cont.Movable = false; + cont.Locked = true; + int numberItems; + + if (level == 0) + { + cont.LockLevel = 0; // Can't be unlocked + + cont.DropItem(new Gold(Utility.RandomMinMax(50, 100))); + + if (Utility.RandomDouble() < 0.75) + cont.DropItem(new TreasureMap(0, Map.Trammel)); + } + else + { + cont.TrapType = TrapType.ExplosionTrap; + cont.TrapPower = level * 25; + cont.TrapLevel = level; + + switch (level) + { + case 1: + cont.RequiredSkill = 36; + break; + case 2: + cont.RequiredSkill = 76; + break; + case 3: + cont.RequiredSkill = 84; + break; + case 4: + cont.RequiredSkill = 92; + break; + case 5: + cont.RequiredSkill = 100; + break; + case 6: + cont.RequiredSkill = 100; + break; + } + + cont.LockLevel = cont.RequiredSkill - 10; + cont.MaxLockLevel = cont.RequiredSkill + 40; + + //Publish 67 gold change + //if ( Core.SA ) + // cont.DropItem( new Gold( level * 5000 ) ); + //else + cont.DropItem(new Gold(level * 1000)); + + for (int i = 0; i < level * 5; ++i) + cont.DropItem(Loot.RandomScroll(0, 63, SpellbookType.Regular)); + + if (Core.SE) + { + switch (level) + { + case 1: + numberItems = 5; + break; + case 2: + numberItems = 10; + break; + case 3: + numberItems = 15; + break; + case 4: + numberItems = 38; + break; + case 5: + numberItems = 50; + break; + case 6: + numberItems = 60; + break; + default: + numberItems = 0; + break; + } + + ; + } + else + { + numberItems = level * 6; + } + + for (int i = 0; i < numberItems; ++i) + { + Item item; + + if (Core.AOS) + item = Loot.RandomArmorOrShieldOrWeaponOrJewelry(); + else + item = Loot.RandomArmorOrShieldOrWeapon(); + + if (item is BaseWeapon weapon) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(weapon, attributeCount, min, max); + } + else + { + weapon.DamageLevel = (WeaponDamageLevel)Utility.Random(6); + weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random(6); + weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random(6); + } + + cont.DropItem(weapon); + } + else if (item is BaseArmor armor) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(armor, attributeCount, min, max); + } + else + { + armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random(6); + armor.Durability = (ArmorDurabilityLevel)Utility.Random(6); + } + + cont.DropItem(armor); + } + else if (item is BaseHat hat) + { + if (Core.AOS) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(hat, attributeCount, min, max); + } + + cont.DropItem(hat); + } + else if (item is BaseJewel jewel) + { + GetRandomAOSStats(out int attributeCount, out int min, out int max); + BaseRunicTool.ApplyAttributesTo(jewel, attributeCount, min, max); + + cont.DropItem(jewel); + } + } + } + + int reagents; + if (level == 0) + reagents = 12; + else + reagents = level * 3; + + for (int i = 0; i < reagents; i++) + { + Item item = Loot.RandomPossibleReagent(); + item.Amount = Utility.RandomMinMax(40, 60); + cont.DropItem(item); + } + + int gems; + if (level == 0) + gems = 2; + else + gems = level * 3; + + for (int i = 0; i < gems; i++) + { + Item item = Loot.RandomGem(); + cont.DropItem(item); + } + + if (level == 6 && Core.AOS) + cont.DropItem((Item)Activator.CreateInstance(Artifacts[Utility.Random(Artifacts.Length)])); + } + + public override bool CheckLocked(Mobile from) + { + if (!Locked) + return false; + + if (Level == 0 && from.AccessLevel < AccessLevel.GameMaster) + { + foreach (Mobile m in Guardians) + if (m.Alive) + { + from.SendLocalizedMessage( + 1046448); // You must first kill the guardians before you may open this chest. + return true; + } + + LockPick(from); + return false; + } + + return base.CheckLocked(from); + } + + private bool CheckLoot(Mobile m, bool criminalAction) + { + if (Temporary) + return false; + + if (m.AccessLevel >= AccessLevel.GameMaster || Owner == null || m == Owner) + return true; + + Party p = Party.Get(Owner); + + if (p != null && p.Contains(m)) + return true; + + Map map = Map; + + if (map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0) + { + if (criminalAction) + m.CriminalAction(true); + else + m.SendLocalizedMessage(1010630); // Taking someone else's treasure is a criminal offense! + + return true; + } + + m.SendLocalizedMessage(1010631); // You did not discover this chest! + return false; + } + + public override bool CheckItemUse(Mobile from, Item item) + { + return CheckLoot(from, item != this) && base.CheckItemUse(from, item); + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + return CheckLoot(from, true) && base.CheckLift(from, item, ref reject); + } + + public override void OnItemLifted(Mobile from, Item item) + { + bool notYetLifted = !m_Lifted.Contains(item); + + from.RevealingAction(); + + if (notYetLifted) + { + m_Lifted.Add(item); + + if (0.1 >= Utility.RandomDouble()) // 10% chance to spawn a new monster + TreasureMap.Spawn(Level, GetWorldLocation(), Map, from, false); + } + + base.OnItemLifted(from, item); + } + + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (m.AccessLevel < AccessLevel.GameMaster) + { + m.SendLocalizedMessage(1048122, "", 0x8A5); // The chest refuses to be filled with treasure again. + return false; + } + + return base.CheckHold(m, item, message, checkItems, plusItems, plusWeight); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + + writer.Write(Guardians, true); + writer.Write(Temporary); + + writer.Write(Owner); + + writer.Write(Level); + writer.WriteDeltaTime(DeleteTime); + writer.Write(m_Lifted, true); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: + { + Guardians = reader.ReadStrongMobileList(); + Temporary = reader.ReadBool(); + + goto case 1; + } + case 1: + { + Owner = reader.ReadMobile(); + + goto case 0; + } + case 0: + { + Level = reader.ReadInt(); + DeleteTime = reader.ReadDeltaTime(); + m_Lifted = reader.ReadStrongItemList(); + + if (version < 2) + Guardians = new List(); + + break; + } + } + + if (!Temporary) + { + m_Timer = new DeleteTimer(this, DeleteTime); + m_Timer.Start(); + } + else + { + Delete(); + } + } + + public override void OnAfterDelete() + { + m_Timer?.Stop(); + + m_Timer = null; + + base.OnAfterDelete(); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.Alive) + list.Add(new RemoveEntry(from, this)); + } + + public void BeginRemove(Mobile from) + { + if (!from.Alive) + return; + + from.CloseGump(typeof(RemoveGump)); + from.SendGump(new RemoveGump(from, this)); + } + + public void EndRemove(Mobile from) + { + if (Deleted || from != Owner || !from.InRange(GetWorldLocation(), 3)) + return; + + from.SendLocalizedMessage(1048124, "", 0x8A5); // The old, rusted chest crumbles when you hit it. + Delete(); + } + + private class RemoveGump : Gump + { + private TreasureMapChest m_Chest; + private Mobile m_From; + + public RemoveGump(Mobile from, TreasureMapChest chest) : base(15, 15) + { + m_From = from; + m_Chest = chest; + + Closable = false; + Disposable = false; + + AddPage(0); + + AddBackground(30, 0, 240, 240, 2620); + + AddHtmlLocalized(45, 15, 200, 80, 1048125, 0xFFFFFF, false, + false); // When this treasure chest is removed, any items still inside of it will be lost. + AddHtmlLocalized(45, 95, 200, 60, 1048126, 0xFFFFFF, false, + false); // Are you certain you're ready to remove this chest? + + AddButton(40, 153, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(75, 155, 180, 40, 1048127, 0xFFFFFF, false, false); // Remove the Treasure Chest + + AddButton(40, 195, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(75, 197, 180, 35, 1006045, 0xFFFFFF, false, false); // Cancel + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_Chest.EndRemove(m_From); + } + } + + private class RemoveEntry : ContextMenuEntry + { + private TreasureMapChest m_Chest; + private Mobile m_From; + + public RemoveEntry(Mobile from, TreasureMapChest chest) : base(6149, 3) + { + m_From = from; + m_Chest = chest; + + Enabled = from == chest.Owner; + } + + public override void OnClick() + { + if (m_Chest.Deleted || m_From != m_Chest.Owner || !m_From.CheckAlive()) + return; + + m_Chest.BeginRemove(m_From); + } + } + + private class DeleteTimer : Timer + { + private Item m_Item; + + public DeleteTimer(Item item, DateTime time) : base(time - DateTime.UtcNow) + { + m_Item = item; + Priority = TimerPriority.OneMinute; + } + + protected override void OnTick() + { + m_Item.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Decoration Artifacts/BaseDecorationArtifact.cs b/Scripts/Items/Decoration Artifacts/BaseDecorationArtifact.cs index bea3ce605..a489ba826 100644 --- a/Scripts/Items/Decoration Artifacts/BaseDecorationArtifact.cs +++ b/Scripts/Items/Decoration Artifacts/BaseDecorationArtifact.cs @@ -1,76 +1,76 @@ namespace Server.Items { - public abstract class BaseDecorationArtifact : Item - { - public abstract int ArtifactRarity{ get; } + public abstract class BaseDecorationArtifact : Item + { + public BaseDecorationArtifact(int itemID) : base(itemID) + { + Weight = 10.0; + } - public override bool ForceShowProperties => true; + public BaseDecorationArtifact(Serial serial) : base(serial) + { + } - public BaseDecorationArtifact( int itemID ) : base( itemID ) - { - Weight = 10.0; - } + public abstract int ArtifactRarity{ get; } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override bool ForceShowProperties => true; - list.Add( 1061078, ArtifactRarity.ToString() ); // artifact rarity ~1_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public BaseDecorationArtifact( Serial serial ) : base( serial ) - { - } + list.Add(1061078, ArtifactRarity.ToString()); // artifact rarity ~1_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public abstract class BaseDecorationContainerArtifact : BaseContainer - { - public abstract int ArtifactRarity{ get; } + public abstract class BaseDecorationContainerArtifact : BaseContainer + { + public BaseDecorationContainerArtifact(int itemID) : base(itemID) + { + Weight = 10.0; + } - public override bool ForceShowProperties => true; + public BaseDecorationContainerArtifact(Serial serial) : base(serial) + { + } - public BaseDecorationContainerArtifact( int itemID ) : base( itemID ) - { - Weight = 10.0; - } + public abstract int ArtifactRarity{ get; } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override bool ForceShowProperties => true; - list.Add( 1061078, ArtifactRarity.ToString() ); // artifact rarity ~1_val~ - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - public BaseDecorationContainerArtifact( Serial serial ) : base( serial ) - { - } + list.Add(1061078, ArtifactRarity.ToString()); // artifact rarity ~1_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Decoration Artifacts/DoomDecorationArtifacts.cs b/Scripts/Items/Decoration Artifacts/DoomDecorationArtifacts.cs index 5bf5b52b0..7f4532a07 100644 --- a/Scripts/Items/Decoration Artifacts/DoomDecorationArtifacts.cs +++ b/Scripts/Items/Decoration Artifacts/DoomDecorationArtifacts.cs @@ -1,695 +1,741 @@ namespace Server.Items { - #region BackpackArtifact - public class BackpackArtifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public BackpackArtifact() : base( 0x9B2 ) - { - } - - public BackpackArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BloodyWaterArtifact - public class BloodyWaterArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public BloodyWaterArtifact() : base( 0xE23 ) - { - } - - public BloodyWaterArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BooksWestArtifact - public class BooksWestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public BooksWestArtifact() : base( 0x1E25 ) - { - } - - public BooksWestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BooksNorthArtifact - public class BooksNorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public BooksNorthArtifact() : base( 0x1E24 ) - { - } - - public BooksNorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BooksFaceDownArtifact - public class BooksFaceDownArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public BooksFaceDownArtifact() : base( 0x1E21 ) - { - } - - public BooksFaceDownArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BottleArtifact - public class BottleArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public BottleArtifact() : base( 0xE28 ) - { - } - - public BottleArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BrazierArtifact - public class BrazierArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public BrazierArtifact() : base( 0xE31 ) - { - Light = LightType.Circle150; - } - - public BrazierArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region CocoonArtifact - public class CocoonArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 7; - - [Constructible] - public CocoonArtifact() : base( 0x10DA ) - { - } - - public CocoonArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region DamagedBooksArtifact - public class DamagedBooksArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public DamagedBooksArtifact() : base( 0xC16 ) - { - } - - public DamagedBooksArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region EggCaseArtifact - public class EggCaseArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public EggCaseArtifact() : base( 0x10D9 ) - { - } - - public EggCaseArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region GruesomeStandardArtifact - public class GruesomeStandardArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public GruesomeStandardArtifact() : base( 0x428 ) - { - } - - public GruesomeStandardArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region LampPostArtifact - public class LampPostArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public LampPostArtifact() : base( 0xB24 ) - { - Light = LightType.Circle300; - } - - public LampPostArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region LeatherTunicArtifact - public class LeatherTunicArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public LeatherTunicArtifact() : base( 0x13CA ) - { - } - - public LeatherTunicArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region RockArtifact - public class RockArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public RockArtifact() : base( 0x1363 ) - { - } - - public RockArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region RuinedPaintingArtifact - public class RuinedPaintingArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 12; - - [Constructible] - public RuinedPaintingArtifact() : base( 0xC2C ) - { - } - - public RuinedPaintingArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SaddleArtifact - public class SaddleArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public SaddleArtifact() : base( 0xF38 ) - { - } - - public SaddleArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SkinnedDeerArtifact - public class SkinnedDeerArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public SkinnedDeerArtifact() : base( 0x1E91 ) - { - } - - public SkinnedDeerArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SkinnedGoatArtifact - public class SkinnedGoatArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public SkinnedGoatArtifact() : base( 0x1E88 ) - { - } - - public SkinnedGoatArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SkullCandleArtifact - public class SkullCandleArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public SkullCandleArtifact() : base( 0x1858 ) - { - Light = LightType.Circle150; - } - - public SkullCandleArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region StretchedHideArtifact - public class StretchedHideArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public StretchedHideArtifact() : base( 0x106B ) - { - } - - public StretchedHideArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region StuddedLeggingsArtifact - public class StuddedLeggingsArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public StuddedLeggingsArtifact() : base( 0x13D8 ) - { - } - - public StuddedLeggingsArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region StuddedTunicArtifact - public class StuddedTunicArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 7; - - [Constructible] - public StuddedTunicArtifact() : base( 0x13D9 ) - { - } - - public StuddedTunicArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region TarotCardsArtifact - public class TarotCardsArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public TarotCardsArtifact() : base( 0x12A5 ) - { - } - - public TarotCardsArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion -} + #region BackpackArtifact + + public class BackpackArtifact : BaseDecorationContainerArtifact + { + [Constructible] + public BackpackArtifact() : base(0x9B2) + { + } + + public BackpackArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BloodyWaterArtifact + + public class BloodyWaterArtifact : BaseDecorationArtifact + { + [Constructible] + public BloodyWaterArtifact() : base(0xE23) + { + } + + public BloodyWaterArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BooksWestArtifact + + public class BooksWestArtifact : BaseDecorationArtifact + { + [Constructible] + public BooksWestArtifact() : base(0x1E25) + { + } + + public BooksWestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BooksNorthArtifact + + public class BooksNorthArtifact : BaseDecorationArtifact + { + [Constructible] + public BooksNorthArtifact() : base(0x1E24) + { + } + + public BooksNorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BooksFaceDownArtifact + + public class BooksFaceDownArtifact : BaseDecorationArtifact + { + [Constructible] + public BooksFaceDownArtifact() : base(0x1E21) + { + } + + public BooksFaceDownArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BottleArtifact + + public class BottleArtifact : BaseDecorationArtifact + { + [Constructible] + public BottleArtifact() : base(0xE28) + { + } + + public BottleArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BrazierArtifact + + public class BrazierArtifact : BaseDecorationArtifact + { + [Constructible] + public BrazierArtifact() : base(0xE31) + { + Light = LightType.Circle150; + } + + public BrazierArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region CocoonArtifact + + public class CocoonArtifact : BaseDecorationArtifact + { + [Constructible] + public CocoonArtifact() : base(0x10DA) + { + } + + public CocoonArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 7; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region DamagedBooksArtifact + + public class DamagedBooksArtifact : BaseDecorationArtifact + { + [Constructible] + public DamagedBooksArtifact() : base(0xC16) + { + } + + public DamagedBooksArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region EggCaseArtifact + + public class EggCaseArtifact : BaseDecorationArtifact + { + [Constructible] + public EggCaseArtifact() : base(0x10D9) + { + } + + public EggCaseArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region GruesomeStandardArtifact + + public class GruesomeStandardArtifact : BaseDecorationArtifact + { + [Constructible] + public GruesomeStandardArtifact() : base(0x428) + { + } + + public GruesomeStandardArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region LampPostArtifact + + public class LampPostArtifact : BaseDecorationArtifact + { + [Constructible] + public LampPostArtifact() : base(0xB24) + { + Light = LightType.Circle300; + } + + public LampPostArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region LeatherTunicArtifact + + public class LeatherTunicArtifact : BaseDecorationArtifact + { + [Constructible] + public LeatherTunicArtifact() : base(0x13CA) + { + } + + public LeatherTunicArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region RockArtifact + + public class RockArtifact : BaseDecorationArtifact + { + [Constructible] + public RockArtifact() : base(0x1363) + { + } + + public RockArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region RuinedPaintingArtifact + + public class RuinedPaintingArtifact : BaseDecorationArtifact + { + [Constructible] + public RuinedPaintingArtifact() : base(0xC2C) + { + } + + public RuinedPaintingArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 12; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SaddleArtifact + + public class SaddleArtifact : BaseDecorationArtifact + { + [Constructible] + public SaddleArtifact() : base(0xF38) + { + } + + public SaddleArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SkinnedDeerArtifact + + public class SkinnedDeerArtifact : BaseDecorationArtifact + { + [Constructible] + public SkinnedDeerArtifact() : base(0x1E91) + { + } + + public SkinnedDeerArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SkinnedGoatArtifact + + public class SkinnedGoatArtifact : BaseDecorationArtifact + { + [Constructible] + public SkinnedGoatArtifact() : base(0x1E88) + { + } + + public SkinnedGoatArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SkullCandleArtifact + + public class SkullCandleArtifact : BaseDecorationArtifact + { + [Constructible] + public SkullCandleArtifact() : base(0x1858) + { + Light = LightType.Circle150; + } + + public SkullCandleArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region StretchedHideArtifact + + public class StretchedHideArtifact : BaseDecorationArtifact + { + [Constructible] + public StretchedHideArtifact() : base(0x106B) + { + } + + public StretchedHideArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region StuddedLeggingsArtifact + + public class StuddedLeggingsArtifact : BaseDecorationArtifact + { + [Constructible] + public StuddedLeggingsArtifact() : base(0x13D8) + { + } + + public StuddedLeggingsArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region StuddedTunicArtifact + + public class StuddedTunicArtifact : BaseDecorationArtifact + { + [Constructible] + public StuddedTunicArtifact() : base(0x13D9) + { + } + + public StuddedTunicArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 7; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region TarotCardsArtifact + + public class TarotCardsArtifact : BaseDecorationArtifact + { + [Constructible] + public TarotCardsArtifact() : base(0x12A5) + { + } + + public TarotCardsArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Items/Decoration Artifacts/SEDecorationArtifacts.cs b/Scripts/Items/Decoration Artifacts/SEDecorationArtifacts.cs index 41dca8643..ff29a730e 100644 --- a/Scripts/Items/Decoration Artifacts/SEDecorationArtifacts.cs +++ b/Scripts/Items/Decoration Artifacts/SEDecorationArtifacts.cs @@ -1,1624 +1,1732 @@ +using Server.Network; + namespace Server.Items { - #region Basket1Artifact - public class Basket1Artifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public Basket1Artifact() : base( 0x24DD ) - { - } - - public Basket1Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket2Artifact - public class Basket2Artifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public Basket2Artifact() : base( 0x24D7 ) - { - } - - public Basket2Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket3WestArtifact - public class Basket3WestArtifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public Basket3WestArtifact() : base( 0x24D9 ) - { - } - - public Basket3WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket3NorthArtifact - public class Basket3NorthArtifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 1; - - [Constructible] - public Basket3NorthArtifact() : base( 0x24DA ) - { - } - - public Basket3NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket4Artifact - public class Basket4Artifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public Basket4Artifact() : base( 0x24D8 ) - { - } - - public Basket4Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket5WestArtifact - public class Basket5WestArtifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public Basket5WestArtifact() : base( 0x24DC ) - { - } - - public Basket5WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket5NorthArtifact - public class Basket5NorthArtifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public Basket5NorthArtifact() : base( 0x24DB ) - { - } - - public Basket5NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Basket6Artifact - public class Basket6Artifact : BaseDecorationContainerArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public Basket6Artifact() : base( 0x24D5 ) - { - } - - public Basket6Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BowlArtifact - public class BowlArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public BowlArtifact() : base( 0x24DE ) - { - } - - public BowlArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BowlsVerticalArtifact - public class BowlsVerticalArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public BowlsVerticalArtifact() : base( 0x24DF ) - { - } - - public BowlsVerticalArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region BowlsHorizontalArtifact - public class BowlsHorizontalArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public BowlsHorizontalArtifact() : base( 0x24E0 ) - { - } - - public BowlsHorizontalArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region CupsArtifact - public class CupsArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public CupsArtifact() : base( 0x24E1 ) - { - } - - public CupsArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region FanWestArtifact - public class FanWestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public FanWestArtifact() : base( 0x240A ) - { - } - - public FanWestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region FanNorthArtifact - public class FanNorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public FanNorthArtifact() : base( 0x2409 ) - { - } - - public FanNorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region TripleFanWestArtifact - public class TripleFanWestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public TripleFanWestArtifact() : base( 0x240C ) - { - } - - public TripleFanWestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region TripleFanNorthArtifact - public class TripleFanNorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public TripleFanNorthArtifact() : base( 0x240B ) - { - } - - public TripleFanNorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region FlowersArtifact - public class FlowersArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 7; - - [Constructible] - public FlowersArtifact() : base( 0x284A ) - { - } - - public FlowersArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting1WestArtifact - public class Painting1WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public Painting1WestArtifact() : base( 0x240E ) - { - } - - public Painting1WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting1NorthArtifact - public class Painting1NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public Painting1NorthArtifact() : base( 0x240D ) - { - } - - public Painting1NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting2WestArtifact - public class Painting2WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public Painting2WestArtifact() : base( 0x2410 ) - { - } - - public Painting2WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting2NorthArtifact - public class Painting2NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public Painting2NorthArtifact() : base( 0x240F ) - { - } - - public Painting2NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting3Artifact - public class Painting3Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public Painting3Artifact() : base( 0x2411 ) - { - } - - public Painting3Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting4WestArtifact - public class Painting4WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 6; - - [Constructible] - public Painting4WestArtifact() : base( 0x2412 ) - { - } - - public Painting4WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting4NorthArtifact - public class Painting4NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 6; - - [Constructible] - public Painting4NorthArtifact() : base( 0x2411 ) - { - } - - public Painting4NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting5WestArtifact - public class Painting5WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public Painting5WestArtifact() : base( 0x2416 ) - { - } - - public Painting5WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting5NorthArtifact - public class Painting5NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public Painting5NorthArtifact() : base( 0x2415 ) - { - } - - public Painting5NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting6WestArtifact - public class Painting6WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public Painting6WestArtifact() : base( 0x2418 ) - { - } - - public Painting6WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Painting6NorthArtifact - public class Painting6NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public Painting6NorthArtifact() : base( 0x2417 ) - { - } - - public Painting6NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SakeArtifact - public class SakeArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 4; - - [Constructible] - public SakeArtifact() : base( 0x24E2 ) - { - } - - public SakeArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Sculpture1Artifact - public class Sculpture1Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public Sculpture1Artifact() : base( 0x2419 ) - { - } - - public Sculpture1Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Sculpture2Artifact - public class Sculpture2Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public Sculpture2Artifact() : base( 0x241B ) - { - } - - public Sculpture2Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region DolphinLeftArtifact - public class DolphinLeftArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public DolphinLeftArtifact() : base( 0x2846 ) - { - } - - public DolphinLeftArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region DolphinRightArtifact - public class DolphinRightArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public DolphinRightArtifact() : base( 0x2847 ) - { - } - - public DolphinRightArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region ManStatuetteSouthArtifact - public class ManStatuetteSouthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public ManStatuetteSouthArtifact() : base( 0x2848 ) - { - } - - public ManStatuetteSouthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region ManStatuetteEastArtifact - public class ManStatuetteEastArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public ManStatuetteEastArtifact() : base( 0x2849 ) - { - } - - public ManStatuetteEastArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay1WestArtifact - public class SwordDisplay1WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public SwordDisplay1WestArtifact() : base( 0x2842 ) - { - } - - public SwordDisplay1WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay1NorthArtifact - public class SwordDisplay1NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 5; - - [Constructible] - public SwordDisplay1NorthArtifact() : base( 0x2843 ) - { - } - - public SwordDisplay1NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay2WestArtifact - public class SwordDisplay2WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 6; - - [Constructible] - public SwordDisplay2WestArtifact() : base( 0x2844 ) - { - } - - public SwordDisplay2WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay2NorthArtifact - public class SwordDisplay2NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 6; - - [Constructible] - public SwordDisplay2NorthArtifact() : base( 0x2845 ) - { - } - - public SwordDisplay2NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay3SouthArtifact - public class SwordDisplay3SouthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public SwordDisplay3SouthArtifact() : base( 0x2855 ) - { - } - - public SwordDisplay3SouthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay3EastArtifact - public class SwordDisplay3EastArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public SwordDisplay3EastArtifact() : base( 0x2856 ) - { - } - - public SwordDisplay3EastArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay4WestArtifact - public class SwordDisplay4WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 8; - - [Constructible] - public SwordDisplay4WestArtifact() : base( 0x2853 ) - { - } - - public SwordDisplay4WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay4NorthArtifact - public class SwordDisplay4NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public SwordDisplay4NorthArtifact() : base( 0x2854 ) - { - } - - public SwordDisplay4NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay5WestArtifact - public class SwordDisplay5WestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public SwordDisplay5WestArtifact() : base( 0x2851 ) - { - } - - public SwordDisplay5WestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region SwordDisplay5NorthArtifact - public class SwordDisplay5NorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 9; - - [Constructible] - public SwordDisplay5NorthArtifact() : base( 0x2852 ) - { - } - - public SwordDisplay5NorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region TeapotWestArtifact - public class TeapotWestArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public TeapotWestArtifact() : base( 0x24E7 ) - { - } - - public TeapotWestArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region TeapotNorthArtifact - public class TeapotNorthArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public TeapotNorthArtifact() : base( 0x24E6 ) - { - } - - public TeapotNorthArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region TowerLanternArtifact - public class TowerLanternArtifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsOn - { - get => ItemID == 0x24BF; - set => ItemID = value ? 0x24BF : 0x24C0; - } - - [Constructible] - public TowerLanternArtifact() : base( 0x24C0 ) - { - Light = LightType.Circle225; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - if ( IsOn ) - { - IsOn = false; - from.PlaySound( 0x3BE ); - } - else - { - IsOn = true; - from.PlaySound( 0x47 ); - } - } - else - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } - - public TowerLanternArtifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - if ( version == 0 ) - Light = LightType.Circle225; - } - } - #endregion - - #region Urn1Artifact - public class Urn1Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public Urn1Artifact() : base( 0x241D ) - { - } - - public Urn1Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region Urn2Artifact - public class Urn2Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public Urn2Artifact() : base( 0x241E ) - { - } - - public Urn2Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region ZenRock1Artifact - public class ZenRock1Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 2; - - [Constructible] - public ZenRock1Artifact() : base( 0x24E4 ) - { - } - - public ZenRock1Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region ZenRock2Artifact - public class ZenRock2Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public ZenRock2Artifact() : base( 0x24E3 ) - { - } - - public ZenRock2Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion - - #region ZenRock3Artifact - public class ZenRock3Artifact : BaseDecorationArtifact - { - public override int ArtifactRarity => 3; - - [Constructible] - public ZenRock3Artifact() : base( 0x24E5 ) - { - } - - public ZenRock3Artifact( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - #endregion -} + #region Basket1Artifact + + public class Basket1Artifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket1Artifact() : base(0x24DD) + { + } + + public Basket1Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket2Artifact + + public class Basket2Artifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket2Artifact() : base(0x24D7) + { + } + + public Basket2Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket3WestArtifact + + public class Basket3WestArtifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket3WestArtifact() : base(0x24D9) + { + } + + public Basket3WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket3NorthArtifact + + public class Basket3NorthArtifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket3NorthArtifact() : base(0x24DA) + { + } + + public Basket3NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket4Artifact + + public class Basket4Artifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket4Artifact() : base(0x24D8) + { + } + + public Basket4Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket5WestArtifact + + public class Basket5WestArtifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket5WestArtifact() : base(0x24DC) + { + } + + public Basket5WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket5NorthArtifact + + public class Basket5NorthArtifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket5NorthArtifact() : base(0x24DB) + { + } + + public Basket5NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Basket6Artifact + + public class Basket6Artifact : BaseDecorationContainerArtifact + { + [Constructible] + public Basket6Artifact() : base(0x24D5) + { + } + + public Basket6Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BowlArtifact + + public class BowlArtifact : BaseDecorationArtifact + { + [Constructible] + public BowlArtifact() : base(0x24DE) + { + } + + public BowlArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BowlsVerticalArtifact + + public class BowlsVerticalArtifact : BaseDecorationArtifact + { + [Constructible] + public BowlsVerticalArtifact() : base(0x24DF) + { + } + + public BowlsVerticalArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region BowlsHorizontalArtifact + + public class BowlsHorizontalArtifact : BaseDecorationArtifact + { + [Constructible] + public BowlsHorizontalArtifact() : base(0x24E0) + { + } + + public BowlsHorizontalArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region CupsArtifact + + public class CupsArtifact : BaseDecorationArtifact + { + [Constructible] + public CupsArtifact() : base(0x24E1) + { + } + + public CupsArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region FanWestArtifact + + public class FanWestArtifact : BaseDecorationArtifact + { + [Constructible] + public FanWestArtifact() : base(0x240A) + { + } + + public FanWestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region FanNorthArtifact + + public class FanNorthArtifact : BaseDecorationArtifact + { + [Constructible] + public FanNorthArtifact() : base(0x2409) + { + } + + public FanNorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region TripleFanWestArtifact + + public class TripleFanWestArtifact : BaseDecorationArtifact + { + [Constructible] + public TripleFanWestArtifact() : base(0x240C) + { + } + + public TripleFanWestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region TripleFanNorthArtifact + + public class TripleFanNorthArtifact : BaseDecorationArtifact + { + [Constructible] + public TripleFanNorthArtifact() : base(0x240B) + { + } + + public TripleFanNorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region FlowersArtifact + + public class FlowersArtifact : BaseDecorationArtifact + { + [Constructible] + public FlowersArtifact() : base(0x284A) + { + } + + public FlowersArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 7; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting1WestArtifact + + public class Painting1WestArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting1WestArtifact() : base(0x240E) + { + } + + public Painting1WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting1NorthArtifact + + public class Painting1NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting1NorthArtifact() : base(0x240D) + { + } + + public Painting1NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting2WestArtifact + + public class Painting2WestArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting2WestArtifact() : base(0x2410) + { + } + + public Painting2WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting2NorthArtifact + + public class Painting2NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting2NorthArtifact() : base(0x240F) + { + } + + public Painting2NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting3Artifact + + public class Painting3Artifact : BaseDecorationArtifact + { + [Constructible] + public Painting3Artifact() : base(0x2411) + { + } + + public Painting3Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting4WestArtifact + + public class Painting4WestArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting4WestArtifact() : base(0x2412) + { + } + + public Painting4WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 6; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting4NorthArtifact + + public class Painting4NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting4NorthArtifact() : base(0x2411) + { + } + + public Painting4NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 6; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting5WestArtifact + + public class Painting5WestArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting5WestArtifact() : base(0x2416) + { + } + + public Painting5WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting5NorthArtifact + + public class Painting5NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting5NorthArtifact() : base(0x2415) + { + } + + public Painting5NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting6WestArtifact + + public class Painting6WestArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting6WestArtifact() : base(0x2418) + { + } + + public Painting6WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Painting6NorthArtifact + + public class Painting6NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public Painting6NorthArtifact() : base(0x2417) + { + } + + public Painting6NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SakeArtifact + + public class SakeArtifact : BaseDecorationArtifact + { + [Constructible] + public SakeArtifact() : base(0x24E2) + { + } + + public SakeArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 4; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Sculpture1Artifact + + public class Sculpture1Artifact : BaseDecorationArtifact + { + [Constructible] + public Sculpture1Artifact() : base(0x2419) + { + } + + public Sculpture1Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Sculpture2Artifact + + public class Sculpture2Artifact : BaseDecorationArtifact + { + [Constructible] + public Sculpture2Artifact() : base(0x241B) + { + } + + public Sculpture2Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region DolphinLeftArtifact + + public class DolphinLeftArtifact : BaseDecorationArtifact + { + [Constructible] + public DolphinLeftArtifact() : base(0x2846) + { + } + + public DolphinLeftArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region DolphinRightArtifact + + public class DolphinRightArtifact : BaseDecorationArtifact + { + [Constructible] + public DolphinRightArtifact() : base(0x2847) + { + } + + public DolphinRightArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region ManStatuetteSouthArtifact + + public class ManStatuetteSouthArtifact : BaseDecorationArtifact + { + [Constructible] + public ManStatuetteSouthArtifact() : base(0x2848) + { + } + + public ManStatuetteSouthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region ManStatuetteEastArtifact + + public class ManStatuetteEastArtifact : BaseDecorationArtifact + { + [Constructible] + public ManStatuetteEastArtifact() : base(0x2849) + { + } + + public ManStatuetteEastArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay1WestArtifact + + public class SwordDisplay1WestArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay1WestArtifact() : base(0x2842) + { + } + + public SwordDisplay1WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay1NorthArtifact + + public class SwordDisplay1NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay1NorthArtifact() : base(0x2843) + { + } + + public SwordDisplay1NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 5; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay2WestArtifact + + public class SwordDisplay2WestArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay2WestArtifact() : base(0x2844) + { + } + + public SwordDisplay2WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 6; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay2NorthArtifact + + public class SwordDisplay2NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay2NorthArtifact() : base(0x2845) + { + } + + public SwordDisplay2NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 6; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay3SouthArtifact + + public class SwordDisplay3SouthArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay3SouthArtifact() : base(0x2855) + { + } + + public SwordDisplay3SouthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay3EastArtifact + + public class SwordDisplay3EastArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay3EastArtifact() : base(0x2856) + { + } + + public SwordDisplay3EastArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay4WestArtifact + + public class SwordDisplay4WestArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay4WestArtifact() : base(0x2853) + { + } + + public SwordDisplay4WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 8; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay4NorthArtifact + + public class SwordDisplay4NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay4NorthArtifact() : base(0x2854) + { + } + + public SwordDisplay4NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay5WestArtifact + + public class SwordDisplay5WestArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay5WestArtifact() : base(0x2851) + { + } + + public SwordDisplay5WestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region SwordDisplay5NorthArtifact + + public class SwordDisplay5NorthArtifact : BaseDecorationArtifact + { + [Constructible] + public SwordDisplay5NorthArtifact() : base(0x2852) + { + } + + public SwordDisplay5NorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 9; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region TeapotWestArtifact + + public class TeapotWestArtifact : BaseDecorationArtifact + { + [Constructible] + public TeapotWestArtifact() : base(0x24E7) + { + } + + public TeapotWestArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region TeapotNorthArtifact + + public class TeapotNorthArtifact : BaseDecorationArtifact + { + [Constructible] + public TeapotNorthArtifact() : base(0x24E6) + { + } + + public TeapotNorthArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region TowerLanternArtifact + + public class TowerLanternArtifact : BaseDecorationArtifact + { + [Constructible] + public TowerLanternArtifact() : base(0x24C0) + { + Light = LightType.Circle225; + } + + public TowerLanternArtifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsOn + { + get => ItemID == 0x24BF; + set => ItemID = value ? 0x24BF : 0x24C0; + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + { + if (IsOn) + { + IsOn = false; + from.PlaySound(0x3BE); + } + else + { + IsOn = true; + from.PlaySound(0x47); + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + if (version == 0) + Light = LightType.Circle225; + } + } + + #endregion + + #region Urn1Artifact + + public class Urn1Artifact : BaseDecorationArtifact + { + [Constructible] + public Urn1Artifact() : base(0x241D) + { + } + + public Urn1Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region Urn2Artifact + + public class Urn2Artifact : BaseDecorationArtifact + { + [Constructible] + public Urn2Artifact() : base(0x241E) + { + } + + public Urn2Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region ZenRock1Artifact + + public class ZenRock1Artifact : BaseDecorationArtifact + { + [Constructible] + public ZenRock1Artifact() : base(0x24E4) + { + } + + public ZenRock1Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 2; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region ZenRock2Artifact + + public class ZenRock2Artifact : BaseDecorationArtifact + { + [Constructible] + public ZenRock2Artifact() : base(0x24E3) + { + } + + public ZenRock2Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion + + #region ZenRock3Artifact + + public class ZenRock3Artifact : BaseDecorationArtifact + { + [Constructible] + public ZenRock3Artifact() : base(0x24E5) + { + } + + public ZenRock3Artifact(Serial serial) : base(serial) + { + } + + public override int ArtifactRarity => 3; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + #endregion +} \ No newline at end of file diff --git a/Scripts/Items/Decoration Artifacts/StealableArtifactsSpawner.cs b/Scripts/Items/Decoration Artifacts/StealableArtifactsSpawner.cs index f5fa88566..59f56a06f 100644 --- a/Scripts/Items/Decoration Artifacts/StealableArtifactsSpawner.cs +++ b/Scripts/Items/Decoration Artifacts/StealableArtifactsSpawner.cs @@ -4,397 +4,384 @@ using Server.Commands; namespace Server.Items { - public class StealableArtifactsSpawner : Item - { - public class StealableEntry - { - public Map Map { get; } - - public Point3D Location { get; } - - public int MinDelay { get; } - - public int MaxDelay { get; } - - public Type Type { get; } - - public int Hue { get; } - - public StealableEntry( Map map, Point3D location, int minDelay, int maxDelay, Type type ) : this( map, location, minDelay, maxDelay, type, 0 ) - { - } - - public StealableEntry( Map map, Point3D location, int minDelay, int maxDelay, Type type, int hue ) - { - Map = map; - Location = location; - MinDelay = minDelay; - MaxDelay = maxDelay; - Type = type; - Hue = hue; - } - - public Item CreateInstance() - { - Item item = (Item) Activator.CreateInstance( Type ); - - if ( Hue > 0 ) - item.Hue = Hue; - - item.Movable = false; - item.MoveToWorld( Location, Map ); - - return item; - } - } - - public static StealableEntry[] Entries { get; } = - { - // Doom - Artifact rarity 1 - new StealableEntry( Map.Malas, new Point3D( 317, 56, -1 ), 72, 108, typeof( RockArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 360, 31, 8 ), 72, 108, typeof( SkullCandleArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 369, 372, -1 ), 72, 108, typeof( BottleArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 378, 372, 0 ), 72, 108, typeof( DamagedBooksArtifact ) ), - // Doom - Artifact rarity 2 - new StealableEntry( Map.Malas, new Point3D( 432, 16, -1 ), 144, 216, typeof( StretchedHideArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 489, 9, 0 ), 144, 216, typeof( BrazierArtifact ) ), - // Doom - Artifact rarity 3 - new StealableEntry( Map.Malas, new Point3D( 471, 96, -1 ), 288, 432, typeof( LampPostArtifact ), GetLampPostHue() ), - new StealableEntry( Map.Malas, new Point3D( 421, 198, 2 ), 288, 432, typeof( BooksNorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 431, 189, -1 ), 288, 432, typeof( BooksWestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 435, 196, -1 ), 288, 432, typeof( BooksFaceDownArtifact ) ), - // Doom - Artifact rarity 5 - new StealableEntry( Map.Malas, new Point3D( 447, 9, 8 ), 1152, 1728, typeof( StuddedLeggingsArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 423, 28, 0 ), 1152, 1728, typeof( EggCaseArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 347, 44, 4 ), 1152, 1728, typeof( SkinnedGoatArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 497, 57, -1 ), 1152, 1728, typeof( GruesomeStandardArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 381, 375, 11 ), 1152, 1728, typeof( BloodyWaterArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 489, 369, 2 ), 1152, 1728, typeof( TarotCardsArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 497, 369, 5 ), 1152, 1728, typeof( BackpackArtifact ) ), - // Doom - Artifact rarity 7 - new StealableEntry( Map.Malas, new Point3D( 475, 23, 4 ), 4608, 6912, typeof( StuddedTunicArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 423, 28, 0 ), 4608, 6912, typeof( CocoonArtifact ) ), - // Doom - Artifact rarity 8 - new StealableEntry( Map.Malas, new Point3D( 354, 36, -1 ), 9216, 13824, typeof( SkinnedDeerArtifact ) ), - // Doom - Artifact rarity 9 - new StealableEntry( Map.Malas, new Point3D( 433, 11, -1 ), 18432, 27648, typeof( SaddleArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 403, 31, 4 ), 18432, 27648, typeof( LeatherTunicArtifact ) ), - // Doom - Artifact rarity 10 - new StealableEntry( Map.Malas, new Point3D( 257, 70, -2 ), 36864, 55296, typeof( ZyronicClaw ) ), - new StealableEntry( Map.Malas, new Point3D( 354, 176, 7 ), 36864, 55296, typeof( TitansHammer ) ), - new StealableEntry( Map.Malas, new Point3D( 369, 389, -1 ), 36864, 55296, typeof( BladeOfTheRighteous ) ), - new StealableEntry( Map.Malas, new Point3D( 467, 92, 4 ), 36864, 55296, typeof( InquisitorsResolution ) ), - // Doom - Artifact rarity 12 - new StealableEntry( Map.Malas, new Point3D( 487, 364, -1 ), 147456, 221184, typeof( RuinedPaintingArtifact ) ), - - // Yomotsu Mines - Artifact rarity 1 - new StealableEntry( Map.Malas, new Point3D( 18, 110, -1 ), 72, 108, typeof( Basket1Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 66, 114, -1 ), 72, 108, typeof( Basket2Artifact ) ), - // Yomotsu Mines - Artifact rarity 2 - new StealableEntry( Map.Malas, new Point3D( 63, 12, 11 ), 144, 216, typeof( Basket4Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 5, 29, -1 ), 144, 216, typeof( Basket5NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 30, 81, 3 ), 144, 216, typeof( Basket5WestArtifact ) ), - // Yomotsu Mines - Artifact rarity 3 - new StealableEntry( Map.Malas, new Point3D( 115, 7, -1 ), 288, 432, typeof( Urn1Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 85, 13, -1 ), 288, 432, typeof( Urn2Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 110, 53, -1 ), 288, 432, typeof( Sculpture1Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 108, 37, -1 ), 288, 432, typeof( Sculpture2Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 121, 14, -1 ), 288, 432, typeof( TeapotNorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 121, 115, -1 ), 288, 432, typeof( TeapotWestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 84, 40, -1 ), 288, 432, typeof( TowerLanternArtifact ) ), - // Yomotsu Mines - Artifact rarity 9 - new StealableEntry( Map.Malas, new Point3D( 94, 7, -1 ), 18432, 27648, typeof( ManStatuetteSouthArtifact ) ), - - // Fan Dancer's Dojo - Artifact rarity 1 - new StealableEntry( Map.Malas, new Point3D( 113, 640, -2 ), 72, 108, typeof( Basket3NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 102, 355, -1 ), 72, 108, typeof( Basket3WestArtifact ) ), - // Fan Dancer's Dojo - Artifact rarity 2 - new StealableEntry( Map.Malas, new Point3D( 99, 370, -1 ), 144, 216, typeof( Basket6Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 100, 357, -1 ), 144, 216, typeof( ZenRock1Artifact ) ), - // Fan Dancer's Dojo - Artifact rarity 3 - new StealableEntry( Map.Malas, new Point3D( 73, 473, -1 ), 288, 432, typeof( FanNorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 99, 372, -1 ), 288, 432, typeof( FanWestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 92, 326, -1 ), 288, 432, typeof( BowlsVerticalArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 97, 470, -1 ), 288, 432, typeof( ZenRock2Artifact ) ), - new StealableEntry( Map.Malas, new Point3D( 103, 691, -1 ), 288, 432, typeof( ZenRock3Artifact ) ), - // Fan Dancer's Dojo - Artifact rarity 4 - new StealableEntry( Map.Malas, new Point3D( 103, 336, 4 ), 576, 864, typeof( Painting1NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 59, 381, 4 ), 576, 864, typeof( Painting1WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 84, 401, 2 ), 576, 864, typeof( Painting2NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 59, 392, 2 ), 576, 864, typeof( Painting2WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 107, 483, -1 ), 576, 864, typeof( TripleFanNorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 50, 475, -1 ), 576, 864, typeof( TripleFanWestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 107, 460, -1 ), 576, 864, typeof( BowlArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 90, 502, -1 ), 576, 864, typeof( CupsArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 107, 688, -1 ), 576, 864, typeof( BowlsHorizontalArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 112, 676, -1 ), 576, 864, typeof( SakeArtifact ) ), - // Fan Dancer's Dojo - Artifact rarity 5 - new StealableEntry( Map.Malas, new Point3D( 135, 614, -1 ), 1152, 1728, typeof( SwordDisplay1NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 50, 482, -1 ), 1152, 1728, typeof( SwordDisplay1WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 119, 672, -1 ), 1152, 1728, typeof( Painting3Artifact ) ), - // Fan Dancer's Dojo - Artifact rarity 6 - new StealableEntry( Map.Malas, new Point3D( 90, 326, -1 ), 2304, 3456, typeof( Painting4NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 99, 354, -1 ), 2304, 3456, typeof( Painting4WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 179, 652, -1 ), 2304, 3456, typeof( SwordDisplay2NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 118, 627, -1 ), 2304, 3456, typeof( SwordDisplay2WestArtifact ) ), - // Fan Dancer's Dojo - Artifact rarity 7 - new StealableEntry( Map.Malas, new Point3D( 90, 483, -1 ), 4608, 6912, typeof( FlowersArtifact ) ), - // Fan Dancer's Dojo - Artifact rarity 8 - new StealableEntry( Map.Malas, new Point3D( 71, 562, -1 ), 9216, 13824, typeof( DolphinLeftArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 102, 677, -1 ), 9216, 13824, typeof( DolphinRightArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 61, 499, 0 ), 9216, 13824, typeof( SwordDisplay3SouthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 182, 669, -1 ), 9216, 13824, typeof( SwordDisplay3EastArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 162, 647, -1 ), 9216, 13824, typeof( SwordDisplay4WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 124, 624, 0 ), 9216, 13824, typeof( Painting5NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 146, 649, 2 ), 9216, 13824, typeof( Painting5WestArtifact ) ), - // Fan Dancer's Dojo - Artifact rarity 9 - new StealableEntry( Map.Malas, new Point3D( 100, 488, -1 ), 18432, 27648, typeof( SwordDisplay4NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 175, 606, 0 ), 18432, 27648, typeof( SwordDisplay5NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 157, 608, -1 ), 18432, 27648, typeof( SwordDisplay5WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 187, 643, 1 ), 18432, 27648, typeof( Painting6NorthArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 146, 623, 1 ), 18432, 27648, typeof( Painting6WestArtifact ) ), - new StealableEntry( Map.Malas, new Point3D( 178, 629, -1 ), 18432, 27648, typeof( ManStatuetteEastArtifact ) ) - }; - - private static Type[] m_TypesOfEntries; - public static Type[] TypesOfEntires - { - get - { - if ( m_TypesOfEntries == null ) - { - m_TypesOfEntries = new Type[Entries.Length]; - - for( int i = 0; i < Entries.Length; i++ ) - m_TypesOfEntries[i] = Entries[i].Type; - } - - return m_TypesOfEntries; - } - } - - public static StealableArtifactsSpawner Instance { get; private set; } - - private static int GetLampPostHue() - { - if ( 0.9 > Utility.RandomDouble() ) - return 0; - - return Utility.RandomList( 0x455, 0x47E, 0x482, 0x486, 0x48F, 0x4F2, 0x58C, 0x66C ); - } - - - public static void Initialize() - { - CommandSystem.Register( "GenStealArties", AccessLevel.Administrator, GenStealArties_OnCommand ); - CommandSystem.Register( "RemoveStealArties", AccessLevel.Administrator, RemoveStealArties_OnCommand ); - } - - [Usage( "GenStealArties" )] - [Description( "Generates the stealable artifacts spawner." )] - private static void GenStealArties_OnCommand( CommandEventArgs args ) - { - Mobile from = args.Mobile; - - if ( Create() ) - from.SendMessage( "Stealable artifacts spawner generated." ); - else - from.SendMessage( "Stealable artifacts spawner already present." ); - } - - [Usage( "RemoveStealArties" )] - [Description( "Removes the stealable artifacts spawner and every not yet stolen stealable artifacts." )] - private static void RemoveStealArties_OnCommand( CommandEventArgs args ) - { - Mobile from = args.Mobile; - - if ( Remove() ) - from.SendMessage( "Stealable artifacts spawner removed." ); - else - from.SendMessage( "Stealable artifacts spawner not present." ); - } - - public static bool Create() - { - if ( Instance != null && !Instance.Deleted ) - return false; - - Instance = new StealableArtifactsSpawner(); - return true; - } - - public static bool Remove() - { - if ( Instance == null ) - return false; - - Instance.Delete(); - Instance = null; - return true; - } - - public static StealableInstance GetStealableInstance( Item item ) - { - return (StealableInstance) Instance?.m_Table[item]; - } - - - public class StealableInstance - { - private Item m_Item; - - public StealableEntry Entry { get; } - - public Item Item - { - get => m_Item; - set - { - if ( m_Item != null && value == null ) - { - int delay = Utility.RandomMinMax( Entry.MinDelay, Entry.MaxDelay ); - NextRespawn = DateTime.UtcNow + TimeSpan.FromMinutes( delay ); - } - - if ( Instance != null ) - { - if ( m_Item != null ) - Instance.m_Table.Remove( m_Item ); - - if ( value != null ) - Instance.m_Table[value] = this; - } - - m_Item = value; - } - } - - public DateTime NextRespawn { get; set; } - - public StealableInstance( StealableEntry entry ) : this( entry, null, DateTime.UtcNow ) - { - } - - public StealableInstance( StealableEntry entry, Item item, DateTime nextRespawn ) - { - m_Item = item; - NextRespawn = nextRespawn; - Entry = entry; - } - - public void CheckRespawn() - { - if ( Item != null && ( Item.Deleted || Item.Movable || Item.Parent != null ) ) - Item = null; - - if ( Item == null && DateTime.UtcNow >= NextRespawn ) - { - Item = Entry.CreateInstance(); - } - } - } - - private Timer m_RespawnTimer; - private StealableInstance[] m_Artifacts; - private Hashtable m_Table; - - public override string DefaultName => "Stealable Artifacts Spawner - Internal"; - - private StealableArtifactsSpawner() : base( 1 ) - { - Movable = false; - - m_Artifacts = new StealableInstance[Entries.Length]; - m_Table = new Hashtable( Entries.Length ); - - for ( int i = 0; i < Entries.Length; i++ ) - { - m_Artifacts[i] = new StealableInstance( Entries[i] ); - } - - m_RespawnTimer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromMinutes( 15.0 ), CheckRespawn ); - } - - public override void OnDelete() - { - base.OnDelete(); - - if ( m_RespawnTimer != null ) - { - m_RespawnTimer.Stop(); - m_RespawnTimer = null; - } - - foreach ( StealableInstance si in m_Artifacts ) - { - si.Item?.Delete(); - } - - Instance = null; - } - - public void CheckRespawn() - { - foreach ( StealableInstance si in m_Artifacts ) - { - si.CheckRespawn(); - } - } - - public StealableArtifactsSpawner( Serial serial ) : base( serial ) - { - Instance = this; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.WriteEncodedInt( m_Artifacts.Length ); - - for ( int i = 0; i < m_Artifacts.Length; i++ ) - { - StealableInstance si = m_Artifacts[i]; - - writer.Write( (Item) si.Item ); - writer.WriteDeltaTime( (DateTime) si.NextRespawn ); - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Artifacts = new StealableInstance[Entries.Length]; - m_Table = new Hashtable( Entries.Length ); - - int length = reader.ReadEncodedInt(); - - for ( int i = 0; i < length; i++ ) - { - Item item = reader.ReadItem(); - DateTime nextRespawn = reader.ReadDeltaTime(); - - if ( i < m_Artifacts.Length ) - { - StealableInstance si = new StealableInstance( Entries[i], item, nextRespawn ); - m_Artifacts[i] = si; - - if ( si.Item != null ) - m_Table[si.Item] = si; - } - } - - for ( int i = length; i < Entries.Length; i++ ) - { - m_Artifacts[i] = new StealableInstance( Entries[i] ); - } + public class StealableArtifactsSpawner : Item + { + private static Type[] m_TypesOfEntries; + private StealableInstance[] m_Artifacts; + + private Timer m_RespawnTimer; + private Hashtable m_Table; + + private StealableArtifactsSpawner() : base(1) + { + Movable = false; + + m_Artifacts = new StealableInstance[Entries.Length]; + m_Table = new Hashtable(Entries.Length); + + for (int i = 0; i < Entries.Length; i++) m_Artifacts[i] = new StealableInstance(Entries[i]); + + m_RespawnTimer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromMinutes(15.0), CheckRespawn); + } + + public StealableArtifactsSpawner(Serial serial) : base(serial) + { + Instance = this; + } + + public static StealableEntry[] Entries{ get; } = + { + // Doom - Artifact rarity 1 + new StealableEntry(Map.Malas, new Point3D(317, 56, -1), 72, 108, typeof(RockArtifact)), + new StealableEntry(Map.Malas, new Point3D(360, 31, 8), 72, 108, typeof(SkullCandleArtifact)), + new StealableEntry(Map.Malas, new Point3D(369, 372, -1), 72, 108, typeof(BottleArtifact)), + new StealableEntry(Map.Malas, new Point3D(378, 372, 0), 72, 108, typeof(DamagedBooksArtifact)), + // Doom - Artifact rarity 2 + new StealableEntry(Map.Malas, new Point3D(432, 16, -1), 144, 216, typeof(StretchedHideArtifact)), + new StealableEntry(Map.Malas, new Point3D(489, 9, 0), 144, 216, typeof(BrazierArtifact)), + // Doom - Artifact rarity 3 + new StealableEntry(Map.Malas, new Point3D(471, 96, -1), 288, 432, typeof(LampPostArtifact), GetLampPostHue()), + new StealableEntry(Map.Malas, new Point3D(421, 198, 2), 288, 432, typeof(BooksNorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(431, 189, -1), 288, 432, typeof(BooksWestArtifact)), + new StealableEntry(Map.Malas, new Point3D(435, 196, -1), 288, 432, typeof(BooksFaceDownArtifact)), + // Doom - Artifact rarity 5 + new StealableEntry(Map.Malas, new Point3D(447, 9, 8), 1152, 1728, typeof(StuddedLeggingsArtifact)), + new StealableEntry(Map.Malas, new Point3D(423, 28, 0), 1152, 1728, typeof(EggCaseArtifact)), + new StealableEntry(Map.Malas, new Point3D(347, 44, 4), 1152, 1728, typeof(SkinnedGoatArtifact)), + new StealableEntry(Map.Malas, new Point3D(497, 57, -1), 1152, 1728, typeof(GruesomeStandardArtifact)), + new StealableEntry(Map.Malas, new Point3D(381, 375, 11), 1152, 1728, typeof(BloodyWaterArtifact)), + new StealableEntry(Map.Malas, new Point3D(489, 369, 2), 1152, 1728, typeof(TarotCardsArtifact)), + new StealableEntry(Map.Malas, new Point3D(497, 369, 5), 1152, 1728, typeof(BackpackArtifact)), + // Doom - Artifact rarity 7 + new StealableEntry(Map.Malas, new Point3D(475, 23, 4), 4608, 6912, typeof(StuddedTunicArtifact)), + new StealableEntry(Map.Malas, new Point3D(423, 28, 0), 4608, 6912, typeof(CocoonArtifact)), + // Doom - Artifact rarity 8 + new StealableEntry(Map.Malas, new Point3D(354, 36, -1), 9216, 13824, typeof(SkinnedDeerArtifact)), + // Doom - Artifact rarity 9 + new StealableEntry(Map.Malas, new Point3D(433, 11, -1), 18432, 27648, typeof(SaddleArtifact)), + new StealableEntry(Map.Malas, new Point3D(403, 31, 4), 18432, 27648, typeof(LeatherTunicArtifact)), + // Doom - Artifact rarity 10 + new StealableEntry(Map.Malas, new Point3D(257, 70, -2), 36864, 55296, typeof(ZyronicClaw)), + new StealableEntry(Map.Malas, new Point3D(354, 176, 7), 36864, 55296, typeof(TitansHammer)), + new StealableEntry(Map.Malas, new Point3D(369, 389, -1), 36864, 55296, typeof(BladeOfTheRighteous)), + new StealableEntry(Map.Malas, new Point3D(467, 92, 4), 36864, 55296, typeof(InquisitorsResolution)), + // Doom - Artifact rarity 12 + new StealableEntry(Map.Malas, new Point3D(487, 364, -1), 147456, 221184, typeof(RuinedPaintingArtifact)), + + // Yomotsu Mines - Artifact rarity 1 + new StealableEntry(Map.Malas, new Point3D(18, 110, -1), 72, 108, typeof(Basket1Artifact)), + new StealableEntry(Map.Malas, new Point3D(66, 114, -1), 72, 108, typeof(Basket2Artifact)), + // Yomotsu Mines - Artifact rarity 2 + new StealableEntry(Map.Malas, new Point3D(63, 12, 11), 144, 216, typeof(Basket4Artifact)), + new StealableEntry(Map.Malas, new Point3D(5, 29, -1), 144, 216, typeof(Basket5NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(30, 81, 3), 144, 216, typeof(Basket5WestArtifact)), + // Yomotsu Mines - Artifact rarity 3 + new StealableEntry(Map.Malas, new Point3D(115, 7, -1), 288, 432, typeof(Urn1Artifact)), + new StealableEntry(Map.Malas, new Point3D(85, 13, -1), 288, 432, typeof(Urn2Artifact)), + new StealableEntry(Map.Malas, new Point3D(110, 53, -1), 288, 432, typeof(Sculpture1Artifact)), + new StealableEntry(Map.Malas, new Point3D(108, 37, -1), 288, 432, typeof(Sculpture2Artifact)), + new StealableEntry(Map.Malas, new Point3D(121, 14, -1), 288, 432, typeof(TeapotNorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(121, 115, -1), 288, 432, typeof(TeapotWestArtifact)), + new StealableEntry(Map.Malas, new Point3D(84, 40, -1), 288, 432, typeof(TowerLanternArtifact)), + // Yomotsu Mines - Artifact rarity 9 + new StealableEntry(Map.Malas, new Point3D(94, 7, -1), 18432, 27648, typeof(ManStatuetteSouthArtifact)), + + // Fan Dancer's Dojo - Artifact rarity 1 + new StealableEntry(Map.Malas, new Point3D(113, 640, -2), 72, 108, typeof(Basket3NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(102, 355, -1), 72, 108, typeof(Basket3WestArtifact)), + // Fan Dancer's Dojo - Artifact rarity 2 + new StealableEntry(Map.Malas, new Point3D(99, 370, -1), 144, 216, typeof(Basket6Artifact)), + new StealableEntry(Map.Malas, new Point3D(100, 357, -1), 144, 216, typeof(ZenRock1Artifact)), + // Fan Dancer's Dojo - Artifact rarity 3 + new StealableEntry(Map.Malas, new Point3D(73, 473, -1), 288, 432, typeof(FanNorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(99, 372, -1), 288, 432, typeof(FanWestArtifact)), + new StealableEntry(Map.Malas, new Point3D(92, 326, -1), 288, 432, typeof(BowlsVerticalArtifact)), + new StealableEntry(Map.Malas, new Point3D(97, 470, -1), 288, 432, typeof(ZenRock2Artifact)), + new StealableEntry(Map.Malas, new Point3D(103, 691, -1), 288, 432, typeof(ZenRock3Artifact)), + // Fan Dancer's Dojo - Artifact rarity 4 + new StealableEntry(Map.Malas, new Point3D(103, 336, 4), 576, 864, typeof(Painting1NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(59, 381, 4), 576, 864, typeof(Painting1WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(84, 401, 2), 576, 864, typeof(Painting2NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(59, 392, 2), 576, 864, typeof(Painting2WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(107, 483, -1), 576, 864, typeof(TripleFanNorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(50, 475, -1), 576, 864, typeof(TripleFanWestArtifact)), + new StealableEntry(Map.Malas, new Point3D(107, 460, -1), 576, 864, typeof(BowlArtifact)), + new StealableEntry(Map.Malas, new Point3D(90, 502, -1), 576, 864, typeof(CupsArtifact)), + new StealableEntry(Map.Malas, new Point3D(107, 688, -1), 576, 864, typeof(BowlsHorizontalArtifact)), + new StealableEntry(Map.Malas, new Point3D(112, 676, -1), 576, 864, typeof(SakeArtifact)), + // Fan Dancer's Dojo - Artifact rarity 5 + new StealableEntry(Map.Malas, new Point3D(135, 614, -1), 1152, 1728, typeof(SwordDisplay1NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(50, 482, -1), 1152, 1728, typeof(SwordDisplay1WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(119, 672, -1), 1152, 1728, typeof(Painting3Artifact)), + // Fan Dancer's Dojo - Artifact rarity 6 + new StealableEntry(Map.Malas, new Point3D(90, 326, -1), 2304, 3456, typeof(Painting4NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(99, 354, -1), 2304, 3456, typeof(Painting4WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(179, 652, -1), 2304, 3456, typeof(SwordDisplay2NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(118, 627, -1), 2304, 3456, typeof(SwordDisplay2WestArtifact)), + // Fan Dancer's Dojo - Artifact rarity 7 + new StealableEntry(Map.Malas, new Point3D(90, 483, -1), 4608, 6912, typeof(FlowersArtifact)), + // Fan Dancer's Dojo - Artifact rarity 8 + new StealableEntry(Map.Malas, new Point3D(71, 562, -1), 9216, 13824, typeof(DolphinLeftArtifact)), + new StealableEntry(Map.Malas, new Point3D(102, 677, -1), 9216, 13824, typeof(DolphinRightArtifact)), + new StealableEntry(Map.Malas, new Point3D(61, 499, 0), 9216, 13824, typeof(SwordDisplay3SouthArtifact)), + new StealableEntry(Map.Malas, new Point3D(182, 669, -1), 9216, 13824, typeof(SwordDisplay3EastArtifact)), + new StealableEntry(Map.Malas, new Point3D(162, 647, -1), 9216, 13824, typeof(SwordDisplay4WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(124, 624, 0), 9216, 13824, typeof(Painting5NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(146, 649, 2), 9216, 13824, typeof(Painting5WestArtifact)), + // Fan Dancer's Dojo - Artifact rarity 9 + new StealableEntry(Map.Malas, new Point3D(100, 488, -1), 18432, 27648, typeof(SwordDisplay4NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(175, 606, 0), 18432, 27648, typeof(SwordDisplay5NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(157, 608, -1), 18432, 27648, typeof(SwordDisplay5WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(187, 643, 1), 18432, 27648, typeof(Painting6NorthArtifact)), + new StealableEntry(Map.Malas, new Point3D(146, 623, 1), 18432, 27648, typeof(Painting6WestArtifact)), + new StealableEntry(Map.Malas, new Point3D(178, 629, -1), 18432, 27648, typeof(ManStatuetteEastArtifact)) + }; + + public static Type[] TypesOfEntires + { + get + { + if (m_TypesOfEntries == null) + { + m_TypesOfEntries = new Type[Entries.Length]; + + for (int i = 0; i < Entries.Length; i++) + m_TypesOfEntries[i] = Entries[i].Type; + } + + return m_TypesOfEntries; + } + } + + public static StealableArtifactsSpawner Instance{ get; private set; } + + public override string DefaultName => "Stealable Artifacts Spawner - Internal"; + + private static int GetLampPostHue() + { + if (0.9 > Utility.RandomDouble()) + return 0; + + return Utility.RandomList(0x455, 0x47E, 0x482, 0x486, 0x48F, 0x4F2, 0x58C, 0x66C); + } + + + public static void Initialize() + { + CommandSystem.Register("GenStealArties", AccessLevel.Administrator, GenStealArties_OnCommand); + CommandSystem.Register("RemoveStealArties", AccessLevel.Administrator, RemoveStealArties_OnCommand); + } + + [Usage("GenStealArties")] + [Description("Generates the stealable artifacts spawner.")] + private static void GenStealArties_OnCommand(CommandEventArgs args) + { + Mobile from = args.Mobile; + + if (Create()) + from.SendMessage("Stealable artifacts spawner generated."); + else + from.SendMessage("Stealable artifacts spawner already present."); + } + + [Usage("RemoveStealArties")] + [Description("Removes the stealable artifacts spawner and every not yet stolen stealable artifacts.")] + private static void RemoveStealArties_OnCommand(CommandEventArgs args) + { + Mobile from = args.Mobile; + + if (Remove()) + from.SendMessage("Stealable artifacts spawner removed."); + else + from.SendMessage("Stealable artifacts spawner not present."); + } + + public static bool Create() + { + if (Instance != null && !Instance.Deleted) + return false; + + Instance = new StealableArtifactsSpawner(); + return true; + } + + public static bool Remove() + { + if (Instance == null) + return false; + + Instance.Delete(); + Instance = null; + return true; + } + + public static StealableInstance GetStealableInstance(Item item) + { + return (StealableInstance)Instance?.m_Table[item]; + } + + public override void OnDelete() + { + base.OnDelete(); + + if (m_RespawnTimer != null) + { + m_RespawnTimer.Stop(); + m_RespawnTimer = null; + } + + foreach (StealableInstance si in m_Artifacts) si.Item?.Delete(); - m_RespawnTimer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromMinutes( 15.0 ), CheckRespawn ); - } - } -} + Instance = null; + } + + public void CheckRespawn() + { + foreach (StealableInstance si in m_Artifacts) si.CheckRespawn(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(m_Artifacts.Length); + + for (int i = 0; i < m_Artifacts.Length; i++) + { + StealableInstance si = m_Artifacts[i]; + + writer.Write(si.Item); + writer.WriteDeltaTime(si.NextRespawn); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Artifacts = new StealableInstance[Entries.Length]; + m_Table = new Hashtable(Entries.Length); + + int length = reader.ReadEncodedInt(); + + for (int i = 0; i < length; i++) + { + Item item = reader.ReadItem(); + DateTime nextRespawn = reader.ReadDeltaTime(); + + if (i < m_Artifacts.Length) + { + StealableInstance si = new StealableInstance(Entries[i], item, nextRespawn); + m_Artifacts[i] = si; + + if (si.Item != null) + m_Table[si.Item] = si; + } + } + + for (int i = length; i < Entries.Length; i++) m_Artifacts[i] = new StealableInstance(Entries[i]); + + m_RespawnTimer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromMinutes(15.0), CheckRespawn); + } + + public class StealableEntry + { + public StealableEntry(Map map, Point3D location, int minDelay, int maxDelay, Type type) : this(map, location, + minDelay, maxDelay, type, 0) + { + } + + public StealableEntry(Map map, Point3D location, int minDelay, int maxDelay, Type type, int hue) + { + Map = map; + Location = location; + MinDelay = minDelay; + MaxDelay = maxDelay; + Type = type; + Hue = hue; + } + + public Map Map{ get; } + + public Point3D Location{ get; } + + public int MinDelay{ get; } + + public int MaxDelay{ get; } + + public Type Type{ get; } + + public int Hue{ get; } + + public Item CreateInstance() + { + Item item = (Item)Activator.CreateInstance(Type); + + if (Hue > 0) + item.Hue = Hue; + + item.Movable = false; + item.MoveToWorld(Location, Map); + + return item; + } + } + + + public class StealableInstance + { + private Item m_Item; + + public StealableInstance(StealableEntry entry) : this(entry, null, DateTime.UtcNow) + { + } + + public StealableInstance(StealableEntry entry, Item item, DateTime nextRespawn) + { + m_Item = item; + NextRespawn = nextRespawn; + Entry = entry; + } + + public StealableEntry Entry{ get; } + + public Item Item + { + get => m_Item; + set + { + if (m_Item != null && value == null) + { + int delay = Utility.RandomMinMax(Entry.MinDelay, Entry.MaxDelay); + NextRespawn = DateTime.UtcNow + TimeSpan.FromMinutes(delay); + } + + if (Instance != null) + { + if (m_Item != null) + Instance.m_Table.Remove(m_Item); + + if (value != null) + Instance.m_Table[value] = this; + } + + m_Item = value; + } + } + + public DateTime NextRespawn{ get; set; } + + public void CheckRespawn() + { + if (Item != null && (Item.Deleted || Item.Movable || Item.Parent != null)) + Item = null; + + if (Item == null && DateTime.UtcNow >= NextRespawn) Item = Entry.CreateInstance(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/BarkeepContract.cs b/Scripts/Items/Deeds/BarkeepContract.cs index cebbb5494..f50059af0 100644 --- a/Scripts/Items/Deeds/BarkeepContract.cs +++ b/Scripts/Items/Deeds/BarkeepContract.cs @@ -1,91 +1,94 @@ using Server.Mobiles; -using Server.Network; using Server.Multis; +using Server.Network; namespace Server.Items { - public class BarkeepContract : Item - { - public override string DefaultName => "a barkeep contract"; + public class BarkeepContract : Item + { + [Constructible] + public BarkeepContract() : base(0x14F0) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public BarkeepContract() : base( 0x14F0 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public BarkeepContract(Serial serial) : base(serial) + { + } - public BarkeepContract( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a barkeep contract"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); //version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } + writer.Write(0); //version + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.SendLocalizedMessage( 503248 ); // Your godly powers allow you to place this vendor whereever you wish. + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Mobile v = new PlayerBarkeeper( from, BaseHouse.FindHouseAt( from ) ); + int version = reader.ReadInt(); + } - v.Direction = from.Direction & Direction.Mask; - v.MoveToWorld( from.Location, from.Map ); + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.SendLocalizedMessage(503248); // Your godly powers allow you to place this vendor whereever you wish. - Delete(); - } - else - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + Mobile v = new PlayerBarkeeper(from, BaseHouse.FindHouseAt(from)); - if ( house == null || !house.IsOwner( from ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You are not the full owner of this house." ); - } - else if ( !house.CanPlaceNewBarkeep() ) - { - from.SendLocalizedMessage( 1062490 ); // That action would exceed the maximum number of barkeeps for this house. - } - else - { - bool vendor, contract; - BaseHouse.IsThereVendor( from.Location, from.Map, out vendor, out contract ); + v.Direction = from.Direction & Direction.Mask; + v.MoveToWorld(from.Location, from.Map); - if ( vendor ) - { - from.SendLocalizedMessage( 1062677 ); // You cannot place a vendor or barkeep at this location. - } - else if ( contract ) - { - from.SendLocalizedMessage( 1062678 ); // You cannot place a vendor or barkeep on top of a rental contract! - } - else - { - Mobile v = new PlayerBarkeeper( from, house ); + Delete(); + } + else + { + BaseHouse house = BaseHouse.FindHouseAt(from); - v.Direction = from.Direction & Direction.Mask; - v.MoveToWorld( from.Location, from.Map ); - - Delete(); - } - } - } - } - } + if (house == null || !house.IsOwner(from)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You are not the full owner of this house."); + } + else if (!house.CanPlaceNewBarkeep()) + { + from.SendLocalizedMessage( + 1062490); // That action would exceed the maximum number of barkeeps for this house. + } + else + { + bool vendor, contract; + BaseHouse.IsThereVendor(from.Location, from.Map, out vendor, out contract); + + if (vendor) + { + from.SendLocalizedMessage(1062677); // You cannot place a vendor or barkeep at this location. + } + else if (contract) + { + from.SendLocalizedMessage( + 1062678); // You cannot place a vendor or barkeep on top of a rental contract! + } + else + { + Mobile v = new PlayerBarkeeper(from, house); + + v.Direction = from.Direction & Direction.Mask; + v.MoveToWorld(from.Location, from.Map); + + Delete(); + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Deeds/ClothingBlessDeed.cs b/Scripts/Items/Deeds/ClothingBlessDeed.cs index 3782a29c0..47b5f11e7 100644 --- a/Scripts/Items/Deeds/ClothingBlessDeed.cs +++ b/Scripts/Items/Deeds/ClothingBlessDeed.cs @@ -2,98 +2,99 @@ using Server.Targeting; namespace Server.Items { - public class ClothingBlessTarget : Target // Create our targeting class (which we derive from the base target class) - { - private ClothingBlessDeed m_Deed; + public class ClothingBlessTarget : Target // Create our targeting class (which we derive from the base target class) + { + private ClothingBlessDeed m_Deed; - public ClothingBlessTarget( ClothingBlessDeed deed ) : base( 1, false, TargetFlags.None ) - { - m_Deed = deed; - } + public ClothingBlessTarget(ClothingBlessDeed deed) : base(1, false, TargetFlags.None) + { + m_Deed = deed; + } - protected override void OnTarget( Mobile from, object target ) // Override the protected OnTarget() for our feature - { - if ( m_Deed.Deleted || m_Deed.RootParent != from ) - return; + protected override void OnTarget(Mobile from, object target) // Override the protected OnTarget() for our feature + { + if (m_Deed.Deleted || m_Deed.RootParent != from) + return; - if ( target is BaseClothing item ) - { - if ( (item as IArcaneEquip)?.IsArcane == true ) - { - from.SendLocalizedMessage( 1005019 ); // This bless deed is for Clothes only. - return; - } + if (target is BaseClothing item) + { + if ((item as IArcaneEquip)?.IsArcane == true) + { + from.SendLocalizedMessage(1005019); // This bless deed is for Clothes only. + return; + } - if ( item.LootType == LootType.Blessed || item.BlessedFor == from || (Mobile.InsuranceEnabled && item.Insured) ) // Check if its already newbied (blessed) - { - from.SendLocalizedMessage( 1045113 ); // That item is already blessed - } - else if ( item.LootType != LootType.Regular ) - { - from.SendLocalizedMessage( 1045114 ); // You can not bless that item - } - else if ( !item.CanBeBlessed || item.RootParent != from ) - { - from.SendLocalizedMessage( 500509 ); // You cannot bless that object - } - else - { - item.LootType = LootType.Blessed; - from.SendLocalizedMessage( 1010026 ); // You bless the item.... + if (item.LootType == LootType.Blessed || item.BlessedFor == from || Mobile.InsuranceEnabled && item.Insured + ) // Check if its already newbied (blessed) + { + from.SendLocalizedMessage(1045113); // That item is already blessed + } + else if (item.LootType != LootType.Regular) + { + from.SendLocalizedMessage(1045114); // You can not bless that item + } + else if (!item.CanBeBlessed || item.RootParent != from) + { + from.SendLocalizedMessage(500509); // You cannot bless that object + } + else + { + item.LootType = LootType.Blessed; + from.SendLocalizedMessage(1010026); // You bless the item.... - m_Deed.Delete(); // Delete the bless deed - } - } - else - { - from.SendLocalizedMessage( 500509 ); // You cannot bless that object - } - } - } + m_Deed.Delete(); // Delete the bless deed + } + } + else + { + from.SendLocalizedMessage(500509); // You cannot bless that object + } + } + } - public class ClothingBlessDeed : Item // Create the item class which is derived from the base item class - { - public override string DefaultName => "a clothing bless deed"; + public class ClothingBlessDeed : Item // Create the item class which is derived from the base item class + { + [Constructible] + public ClothingBlessDeed() : base(0x14F0) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public ClothingBlessDeed() : base( 0x14F0 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public ClothingBlessDeed(Serial serial) : base(serial) + { + } - public ClothingBlessDeed( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a clothing bless deed"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool DisplayLootType => false; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; - public override bool DisplayLootType => false; + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) // Override double click of the deed to call our target - { - if ( !IsChildOf( from.Backpack ) ) // Make sure its in their pack - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - from.SendLocalizedMessage( 1005018 ); // What would you like to bless? (Clothes Only) - from.Target = new ClothingBlessTarget( this ); // Call our target - } - } - } -} + public override void OnDoubleClick(Mobile from) // Override double click of the deed to call our target + { + if (!IsChildOf(from.Backpack)) // Make sure its in their pack + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + from.SendLocalizedMessage(1005018); // What would you like to bless? (Clothes Only) + from.Target = new ClothingBlessTarget(this); // Call our target + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/CommodityDeed.cs b/Scripts/Items/Deeds/CommodityDeed.cs index 3514eef5e..a06e6c580 100644 --- a/Scripts/Items/Deeds/CommodityDeed.cs +++ b/Scripts/Items/Deeds/CommodityDeed.cs @@ -1,258 +1,248 @@ -using System; using Server.Targeting; namespace Server.Items { - public interface ICommodity /* added IsDeedable prop so expansion-based deedables can determine true/false */ - { - int DescriptionNumber{ get; } - bool IsDeedable { get; } - } + public interface ICommodity /* added IsDeedable prop so expansion-based deedables can determine true/false */ + { + int DescriptionNumber{ get; } + bool IsDeedable{ get; } + } - public class CommodityDeed : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public Item Commodity { get; private set; } + public class CommodityDeed : Item + { + public CommodityDeed(Item commodity) : base(0x14F0) + { + Weight = 1.0; + Hue = 0x47; - public bool SetCommodity( Item item ) - { - InvalidateProperties(); + Commodity = commodity; - if ( Commodity == null && (item as ICommodity)?.IsDeedable == true ) - { - Commodity = item; - Commodity.Internalize(); - InvalidateProperties(); + LootType = LootType.Blessed; + } - return true; - } + [Constructible] + public CommodityDeed() : this(null) + { + } - return false; - } + public CommodityDeed(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [CommandProperty(AccessLevel.GameMaster)] + public Item Commodity{ get; private set; } - writer.Write( (int) 1 ); // version + public override int LabelNumber => Commodity == null ? 1047016 : 1047017; - writer.Write( Commodity ); - } + public bool SetCommodity(Item item) + { + InvalidateProperties(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (Commodity == null && (item as ICommodity)?.IsDeedable == true) + { + Commodity = item; + Commodity.Internalize(); + InvalidateProperties(); - int version = reader.ReadInt(); + return true; + } - Commodity = reader.ReadItem(); + return false; + } - switch ( version ) - { - case 0: - { - if (Commodity != null) - { - Hue = 0x592; - } - break; - } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public CommodityDeed( Item commodity ) : base( 0x14F0 ) - { - Weight = 1.0; - Hue = 0x47; + writer.Write(1); // version - Commodity = commodity; + writer.Write(Commodity); + } - LootType = LootType.Blessed; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public CommodityDeed() : this( null ) - { - } + int version = reader.ReadInt(); - public CommodityDeed( Serial serial ) : base( serial ) - { - } + Commodity = reader.ReadItem(); - public override void OnDelete() - { - Commodity?.Delete(); + switch (version) + { + case 0: + { + if (Commodity != null) Hue = 0x592; + break; + } + } + } - base.OnDelete(); - } + public override void OnDelete() + { + Commodity?.Delete(); - public override int LabelNumber => Commodity == null ? 1047016 : 1047017; + base.OnDelete(); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Commodity != null ) - { - string args; + if (Commodity != null) + { + string args; - if ( Commodity.Name == null ) - args = - $"#{((Commodity is ICommodity commodity) ? commodity.DescriptionNumber : Commodity.LabelNumber)}\t{Commodity.Amount}"; - else - args = $"{Commodity.Name}\t{Commodity.Amount}"; + if (Commodity.Name == null) + args = + $"#{(Commodity is ICommodity commodity ? commodity.DescriptionNumber : Commodity.LabelNumber)}\t{Commodity.Amount}"; + else + args = $"{Commodity.Name}\t{Commodity.Amount}"; - list.Add( 1060658, args ); // ~1_val~: ~2_val~ - } - else - { - list.Add( 1060748 ); // unfilled - } - } + list.Add(1060658, args); // ~1_val~: ~2_val~ + } + else + { + list.Add(1060748); // unfilled + } + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - if ( Commodity != null ) - { - string args; + if (Commodity != null) + { + string args; - if ( Commodity.Name == null ) - args = - $"#{((Commodity is ICommodity commodity) ? commodity.DescriptionNumber : Commodity.LabelNumber)}\t{Commodity.Amount}"; - else - args = $"{Commodity.Name}\t{Commodity.Amount}"; + if (Commodity.Name == null) + args = + $"#{(Commodity is ICommodity commodity ? commodity.DescriptionNumber : Commodity.LabelNumber)}\t{Commodity.Amount}"; + else + args = $"{Commodity.Name}\t{Commodity.Amount}"; - LabelTo( from, 1060658, args ); // ~1_val~: ~2_val~ - } - } + LabelTo(from, 1060658, args); // ~1_val~: ~2_val~ + } + } - public override void OnDoubleClick( Mobile from ) - { - int number; + public override void OnDoubleClick(Mobile from) + { + int number; - BankBox box = from.FindBankNoCreate(); - CommodityDeedBox cox = CommodityDeedBox.Find( this ); + BankBox box = from.FindBankNoCreate(); + CommodityDeedBox cox = CommodityDeedBox.Find(this); - // Veteran Rewards mods - if ( Commodity != null ) - { - if ( box != null && IsChildOf( box ) ) - { - number = 1047031; // The commodity has been redeemed. + // Veteran Rewards mods + if (Commodity != null) + { + if (box != null && IsChildOf(box)) + { + number = 1047031; // The commodity has been redeemed. - box.DropItem( Commodity ); + box.DropItem(Commodity); - Commodity = null; - Delete(); - } - else if ( cox != null ) - { - if ( cox.IsSecure ) - { - number = 1047031; // The commodity has been redeemed. + Commodity = null; + Delete(); + } + else if (cox != null) + { + if (cox.IsSecure) + { + number = 1047031; // The commodity has been redeemed. - cox.DropItem( Commodity ); + cox.DropItem(Commodity); - Commodity = null; - Delete(); - } - else - number = 1080525; // The commodity deed box must be secured before you can use it. - } - else - { - if ( Core.ML ) - { - number = 1080526; // That must be in your bank box or commodity deed box to use it. - } - else - { - number = 1047024; // To claim the resources .... - } - } - } - else if ( cox != null && !cox.IsSecure ) - { - number = 1080525; // The commodity deed box must be secured before you can use it. - } - else if ( ( box == null || !IsChildOf( box ) ) && cox == null ) - { - if ( Core.ML ) - { - number = 1080526; // That must be in your bank box or commodity deed box to use it. - } - else - { - number = 1047026; // That must be in your bank box to use it. - } - } - else - { - number = 1047029; // Target the commodity to fill this deed with. + Commodity = null; + Delete(); + } + else + { + number = 1080525; // The commodity deed box must be secured before you can use it. + } + } + else + { + if (Core.ML) + number = 1080526; // That must be in your bank box or commodity deed box to use it. + else + number = 1047024; // To claim the resources .... + } + } + else if (cox != null && !cox.IsSecure) + { + number = 1080525; // The commodity deed box must be secured before you can use it. + } + else if ((box == null || !IsChildOf(box)) && cox == null) + { + if (Core.ML) + number = 1080526; // That must be in your bank box or commodity deed box to use it. + else + number = 1047026; // That must be in your bank box to use it. + } + else + { + number = 1047029; // Target the commodity to fill this deed with. - from.Target = new InternalTarget( this ); - } + from.Target = new InternalTarget(this); + } - from.SendLocalizedMessage( number ); - } + from.SendLocalizedMessage(number); + } - private class InternalTarget : Target - { - private CommodityDeed m_Deed; + private class InternalTarget : Target + { + private CommodityDeed m_Deed; - public InternalTarget( CommodityDeed deed ) : base( 3, false, TargetFlags.None ) - { - m_Deed = deed; - } + public InternalTarget(CommodityDeed deed) : base(3, false, TargetFlags.None) + { + m_Deed = deed; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Deed.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Deed.Deleted) + return; - int number; + int number; - if ( m_Deed.Commodity != null ) - { - number = 1047028; // The commodity deed has already been filled. - } - else if ( targeted is Item item ) - { - BankBox box = from.FindBankNoCreate(); - CommodityDeedBox cox = CommodityDeedBox.Find( m_Deed ); + if (m_Deed.Commodity != null) + { + number = 1047028; // The commodity deed has already been filled. + } + else if (targeted is Item item) + { + BankBox box = from.FindBankNoCreate(); + CommodityDeedBox cox = CommodityDeedBox.Find(m_Deed); - // Veteran Rewards mods - if ( box != null && m_Deed.IsChildOf( box ) && item.IsChildOf( box ) || - cox != null && cox.IsSecure && item.IsChildOf( cox ) ) - { - if ( m_Deed.SetCommodity( item ) ) - { - m_Deed.Hue = 0x592; - number = 1047030; // The commodity deed has been filled. - } - else - { - number = 1047027; // That is not a commodity the bankers will fill a commodity deed with. - } - } - else if ( Core.ML ) - { - number = 1080526; // That must be in your bank box or commodity deed box to use it. - } - else - { - number = 1047026; // That must be in your bank box to use it. - } - } - else - { - number = 1047027; // That is not a commodity the bankers will fill a commodity deed with. - } + // Veteran Rewards mods + if (box != null && m_Deed.IsChildOf(box) && item.IsChildOf(box) || + cox != null && cox.IsSecure && item.IsChildOf(cox)) + { + if (m_Deed.SetCommodity(item)) + { + m_Deed.Hue = 0x592; + number = 1047030; // The commodity deed has been filled. + } + else + { + number = 1047027; // That is not a commodity the bankers will fill a commodity deed with. + } + } + else if (Core.ML) + { + number = 1080526; // That must be in your bank box or commodity deed box to use it. + } + else + { + number = 1047026; // That must be in your bank box to use it. + } + } + else + { + number = 1047027; // That is not a commodity the bankers will fill a commodity deed with. + } - from.SendLocalizedMessage( number ); - } - } - } -} + from.SendLocalizedMessage(number); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/DragonBardingDeed.cs b/Scripts/Items/Deeds/DragonBardingDeed.cs index d8468c675..27b8ece1d 100644 --- a/Scripts/Items/Deeds/DragonBardingDeed.cs +++ b/Scripts/Items/Deeds/DragonBardingDeed.cs @@ -1,149 +1,175 @@ using System; +using Server.Engines.Craft; using Server.Mobiles; using Server.Targeting; -using Server.Engines.Craft; + namespace Server.Items { - [TypeAlias( "Server.Items.DragonBarding" )] - public class DragonBardingDeed : Item, ICraftable - { - private bool m_Exceptional; - private Mobile m_Crafter; - private CraftResource m_Resource; + [TypeAlias("Server.Items.DragonBarding")] + public class DragonBardingDeed : Item, ICraftable + { + private Mobile m_Crafter; + private bool m_Exceptional; + private CraftResource m_Resource; - public override int LabelNumber => m_Exceptional ? 1053181 : 1053012; // dragon barding deed + public DragonBardingDeed() : base(0x14F0) + { + Weight = 1.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter{ get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } } + public DragonBardingDeed(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool Exceptional{ get => m_Exceptional; - set{ m_Exceptional = value; InvalidateProperties(); } } + public override int LabelNumber => m_Exceptional ? 1053181 : 1053012; // dragon barding deed - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource{ get => m_Resource; - set{ m_Resource = value; Hue = CraftResources.GetHue( value ); InvalidateProperties(); } } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } - public DragonBardingDeed() : base( 0x14F0 ) - { - Weight = 1.0; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Exceptional + { + get => m_Exceptional; + set + { + m_Exceptional = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + Hue = CraftResources.GetHue(value); + InvalidateProperties(); + } + } - if ( m_Exceptional && m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ - } + #region ICraftable Members - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.BeginTarget( 6, false, TargetFlags.None, OnTarget ); - from.SendLocalizedMessage( 1053024 ); // Select the swamp dragon you wish to place the barding on. - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Exceptional = quality >= 2; - public virtual void OnTarget( Mobile from, object obj ) - { - if ( Deleted ) - return; + if (makersMark) + Crafter = from; - if ( !(obj is SwampDragon pet) || pet.HasBarding ) - { - from.SendLocalizedMessage( 1053025 ); // That is not an unarmored swamp dragon. - } - else if ( !pet.Controlled || pet.ControlMaster != from ) - { - from.SendLocalizedMessage( 1053026 ); // You can only put barding on a tamed swamp dragon that you own. - } - else if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1060640 ); // The item must be in your backpack to use it. - } - else - { - pet.BardingExceptional = Exceptional; - pet.BardingCrafter = Crafter; - pet.BardingHP = pet.BardingMaxHP; - pet.BardingResource = Resource; - pet.HasBarding = true; - pet.Hue = Hue; + Type resourceType = typeRes; - Delete(); + if (resourceType == null) + resourceType = craftItem.Resources.GetAt(0).ItemType; - from.SendLocalizedMessage( 1053027 ); // You place the barding on your swamp dragon. Use a bladed item on your dragon to remove the armor. - } - } + Resource = CraftResources.GetFromType(resourceType); - public DragonBardingDeed( Serial serial ) : base( serial ) - { - } + CraftContext context = craftSystem.GetContext(from); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (context != null && context.DoNotColor) + Hue = 0; - writer.Write( (int) 1 ); // version + return quality; + } - writer.Write( (bool) m_Exceptional ); - writer.Write( (Mobile) m_Crafter ); - writer.Write( (int) m_Resource ); - } + #endregion - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - int version = reader.ReadInt(); + if (m_Exceptional && m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ + } - switch ( version ) - { - case 1: - case 0: - { - m_Exceptional = reader.ReadBool(); - m_Crafter = reader.ReadMobile(); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.BeginTarget(6, false, TargetFlags.None, OnTarget); + from.SendLocalizedMessage(1053024); // Select the swamp dragon you wish to place the barding on. + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - if ( version < 1 ) - reader.ReadInt(); + public virtual void OnTarget(Mobile from, object obj) + { + if (Deleted) + return; - m_Resource = (CraftResource) reader.ReadInt(); - break; - } - } - } - #region ICraftable Members + if (!(obj is SwampDragon pet) || pet.HasBarding) + { + from.SendLocalizedMessage(1053025); // That is not an unarmored swamp dragon. + } + else if (!pet.Controlled || pet.ControlMaster != from) + { + from.SendLocalizedMessage(1053026); // You can only put barding on a tamed swamp dragon that you own. + } + else if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1060640); // The item must be in your backpack to use it. + } + else + { + pet.BardingExceptional = Exceptional; + pet.BardingCrafter = Crafter; + pet.BardingHP = pet.BardingMaxHP; + pet.BardingResource = Resource; + pet.HasBarding = true; + pet.Hue = Hue; - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Exceptional = ( quality >= 2 ); + Delete(); - if ( makersMark ) - Crafter = from; + from.SendLocalizedMessage( + 1053027); // You place the barding on your swamp dragon. Use a bladed item on your dragon to remove the armor. + } + } - Type resourceType = typeRes; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( resourceType == null ) - resourceType = craftItem.Resources.GetAt( 0 ).ItemType; + writer.Write(1); // version - Resource = CraftResources.GetFromType( resourceType ); + writer.Write(m_Exceptional); + writer.Write(m_Crafter); + writer.Write((int)m_Resource); + } - CraftContext context = craftSystem.GetContext( from ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( context != null && context.DoNotColor ) - Hue = 0; + int version = reader.ReadInt(); - return quality; - } + switch (version) + { + case 1: + case 0: + { + m_Exceptional = reader.ReadBool(); + m_Crafter = reader.ReadMobile(); - #endregion - } -} + if (version < 1) + reader.ReadInt(); + + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/HairRestylingDeed.cs b/Scripts/Items/Deeds/HairRestylingDeed.cs index 01809f238..c1359e2cb 100644 --- a/Scripts/Items/Deeds/HairRestylingDeed.cs +++ b/Scripts/Items/Deeds/HairRestylingDeed.cs @@ -1,151 +1,150 @@ +using Server.Gumps; using Server.Mobiles; using Server.Network; -using Server.Gumps; namespace Server.Items { - public class HairRestylingDeed : Item - { - public override int LabelNumber => 1041061; // a coupon for a free hair restyling + public class HairRestylingDeed : Item + { + [Constructible] + public HairRestylingDeed() : base(0x14F0) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public HairRestylingDeed() : base( 0x14F0 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public HairRestylingDeed(Serial serial) : base(serial) + { + } - public HairRestylingDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041061; // a coupon for a free hair restyling - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack... - } - else - { - from.SendGump( new InternalGump( from, this ) ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + from.SendLocalizedMessage(1042001); // That must be in your pack... + else + from.SendGump(new InternalGump(from, this)); + } - private class InternalGump : Gump - { - private Mobile m_From; - private HairRestylingDeed m_Deed; - - public InternalGump( Mobile from, HairRestylingDeed deed ) : base( 50, 50 ) - { - m_From = from; - m_Deed = deed; - - from.CloseGump( typeof( InternalGump ) ); - - AddBackground( 100, 10, 400, 385, 0xA28 ); - - AddHtmlLocalized( 100, 25, 400, 35, 1013008, false, false ); - AddButton( 175, 340, 0xFA5, 0xFA7, 0x0, GumpButtonType.Reply, 0 ); // CANCEL - - AddHtmlLocalized( 210, 342, 90, 35, 1011012, false, false );//
HAIRSTYLE SELECTION MENU
- - int[][] RacialData = (from.Race == Race.Human) ? HumanArray : ElvenArray; - - for(int i=1; i 10 ) - return; - - int[][] RacialData = (m_From.Race == Race.Human) ? HumanArray : ElvenArray; - - if ( m_From is PlayerMobile pm ) - { - pm.SetHairMods( -1, -1 ); // clear any hairmods (disguise kit, incognito) - pm.HairItemID = (pm.Female) ? RacialData[info.ButtonID][2] : RacialData[info.ButtonID][3]; - m_Deed.Delete(); - } - } -/* - gump data: bgX, bgY, htmlX, htmlY, imgX, imgY, butX, butY -*/ - - int[][] LayoutArray = - { - new[] { 0 }, /* padding: its more efficient than code to ++ the index/buttonid */ - new[] { 425, 280, 342, 295, 000, 000, 310, 292 }, - new[] { 235, 060, 150, 075, 168, 020, 118, 073 }, - new[] { 235, 115, 150, 130, 168, 070, 118, 128 }, - new[] { 235, 170, 150, 185, 168, 130, 118, 183 }, - new[] { 235, 225, 150, 240, 168, 185, 118, 238 }, - new[] { 425, 060, 342, 075, 358, 018, 310, 073 }, - new[] { 425, 115, 342, 130, 358, 075, 310, 128 }, - new[] { 425, 170, 342, 185, 358, 125, 310, 183 }, - new[] { 425, 225, 342, 240, 358, 185, 310, 238 }, - new[] { 235, 280, 150, 295, 168, 245, 118, 292 } // slot 10, Curly - N/A for elfs. - }; + private class InternalGump : Gump + { + private int[][] ElvenArray = + { + new[] { 0 }, + new[] { 1011064, 1011064, 0, 0, 0, 0 }, // bald + new[] { 1074386, 1074386, 0x2fc0, 0x2fc0, 0xedf5, 0xc6e5 }, // long feather + new[] { 1074387, 1074387, 0x2fc1, 0x2fc1, 0xedf6, 0xc6e6 }, // short + new[] { 1074388, 1074388, 0x2fc2, 0x2fc2, 0xedf7, 0xc6e7 }, // mullet + new[] { 1074391, 1074391, 0x2fce, 0x2fce, 0xeddc, 0xc6cc }, // knob + new[] { 1074392, 1074392, 0x2fcf, 0x2fcf, 0xeddd, 0xc6cd }, // braided + new[] { 1074394, 1074394, 0x2fd1, 0x2fd1, 0xeddf, 0xc6cf }, // spiked + new[] { 1074389, 1074385, 0x2fcc, 0x2fbf, 0xedda, 0xc6e4 }, // flower, mid-long + new[] { 1074393, 1074390, 0x2fd0, 0x2fcd, 0xedde, 0xc6cb } // buns, long + }; /* racial arrays are: cliloc_F, cliloc_M, ItemID_F, ItemID_M, gump_img_F, gump_img_M */ - int[][] HumanArray = /* why on earth cant these utilies be consistent with hex/dec */ - { - new[] { 0 }, - new[] { 1011064, 1011064, 0, 0, 0, 0 }, // bald - new[] { 1011052, 1011052, 0x203B, 0x203B, 0xed1c, 0xC60C }, // Short - new[] { 1011053, 1011053, 0x203C, 0x203C, 0xed1d, 0xc60d }, // Long - new[] { 1011054, 1011054, 0x203D, 0x203D, 0xed1e, 0xc60e }, // Ponytail - new[] { 1011055, 1011055, 0x2044, 0x2044, 0xed27, 0xC60F }, // Mohawk - new[] { 1011047, 1011047, 0x2045, 0x2045, 0xED26, 0xED26 }, // Pageboy - new[] { 1074393, 1011048, 0x2046, 0x2048, 0xed28, 0xEDE5 }, // Buns, Receding - new[] { 1011049, 1011049, 0x2049, 0x2049, 0xede6, 0xede6 }, // 2-tails - new[] { 1011050, 1011050, 0x204A, 0x204A, 0xED29, 0xED29 }, // Topknot - new[] { 1011396, 1011396, 0x2047, 0x2047, 0xed25, 0xc618 } // Curly - }; - int[][] ElvenArray = - { - new[] { 0 }, - new[] { 1011064, 1011064, 0, 0, 0, 0, }, // bald - new[] { 1074386, 1074386, 0x2fc0, 0x2fc0, 0xedf5, 0xc6e5 }, // long feather - new[] { 1074387, 1074387, 0x2fc1, 0x2fc1, 0xedf6, 0xc6e6 }, // short - new[] { 1074388, 1074388, 0x2fc2, 0x2fc2, 0xedf7, 0xc6e7 }, // mullet - new[] { 1074391, 1074391, 0x2fce, 0x2fce, 0xeddc, 0xc6cc }, // knob - new[] { 1074392, 1074392, 0x2fcf, 0x2fcf, 0xeddd, 0xc6cd }, // braided - new[] { 1074394, 1074394, 0x2fd1, 0x2fd1, 0xeddf, 0xc6cf }, // spiked - new[] { 1074389, 1074385, 0x2fcc, 0x2fbf, 0xedda, 0xc6e4 }, // flower, mid-long - new[] { 1074393, 1074390, 0x2fd0, 0x2fcd, 0xedde, 0xc6cb } // buns, long - }; - } - } -} + private int[][] HumanArray = /* why on earth cant these utilies be consistent with hex/dec */ + { + new[] { 0 }, + new[] { 1011064, 1011064, 0, 0, 0, 0 }, // bald + new[] { 1011052, 1011052, 0x203B, 0x203B, 0xed1c, 0xC60C }, // Short + new[] { 1011053, 1011053, 0x203C, 0x203C, 0xed1d, 0xc60d }, // Long + new[] { 1011054, 1011054, 0x203D, 0x203D, 0xed1e, 0xc60e }, // Ponytail + new[] { 1011055, 1011055, 0x2044, 0x2044, 0xed27, 0xC60F }, // Mohawk + new[] { 1011047, 1011047, 0x2045, 0x2045, 0xED26, 0xED26 }, // Pageboy + new[] { 1074393, 1011048, 0x2046, 0x2048, 0xed28, 0xEDE5 }, // Buns, Receding + new[] { 1011049, 1011049, 0x2049, 0x2049, 0xede6, 0xede6 }, // 2-tails + new[] { 1011050, 1011050, 0x204A, 0x204A, 0xED29, 0xED29 }, // Topknot + new[] { 1011396, 1011396, 0x2047, 0x2047, 0xed25, 0xc618 } // Curly + }; +/* + gump data: bgX, bgY, htmlX, htmlY, imgX, imgY, butX, butY +*/ + + private int[][] LayoutArray = + { + new[] { 0 }, /* padding: its more efficient than code to ++ the index/buttonid */ + new[] { 425, 280, 342, 295, 000, 000, 310, 292 }, + new[] { 235, 060, 150, 075, 168, 020, 118, 073 }, + new[] { 235, 115, 150, 130, 168, 070, 118, 128 }, + new[] { 235, 170, 150, 185, 168, 130, 118, 183 }, + new[] { 235, 225, 150, 240, 168, 185, 118, 238 }, + new[] { 425, 060, 342, 075, 358, 018, 310, 073 }, + new[] { 425, 115, 342, 130, 358, 075, 310, 128 }, + new[] { 425, 170, 342, 185, 358, 125, 310, 183 }, + new[] { 425, 225, 342, 240, 358, 185, 310, 238 }, + new[] { 235, 280, 150, 295, 168, 245, 118, 292 } // slot 10, Curly - N/A for elfs. + }; + + private HairRestylingDeed m_Deed; + private Mobile m_From; + + public InternalGump(Mobile from, HairRestylingDeed deed) : base(50, 50) + { + m_From = from; + m_Deed = deed; + + from.CloseGump(typeof(InternalGump)); + + AddBackground(100, 10, 400, 385, 0xA28); + + AddHtmlLocalized(100, 25, 400, 35, 1013008, false, false); + AddButton(175, 340, 0xFA5, 0xFA7, 0x0, GumpButtonType.Reply, 0); // CANCEL + + AddHtmlLocalized(210, 342, 90, 35, 1011012, false, false); //
HAIRSTYLE SELECTION MENU
+ + int[][] RacialData = from.Race == Race.Human ? HumanArray : ElvenArray; + + for (int i = 1; i < RacialData.Length; i++) + { + AddHtmlLocalized(LayoutArray[i][2], LayoutArray[i][3], i == 1 ? 125 : 80, i == 1 ? 70 : 35, + m_From.Female ? RacialData[i][0] : RacialData[i][1], false, false); + if (LayoutArray[i][4] != 0) + { + AddBackground(LayoutArray[i][0], LayoutArray[i][1], 50, 50, 0xA3C); + AddImage(LayoutArray[i][4], LayoutArray[i][5], m_From.Female ? RacialData[i][4] : RacialData[i][5]); + } + + AddButton(LayoutArray[i][6], LayoutArray[i][7], 0xFA5, 0xFA7, i, GumpButtonType.Reply, 0); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_From == null || !m_From.Alive) + return; + + if (m_Deed.Deleted) + return; + + if (info.ButtonID < 1 || info.ButtonID > 10) + return; + + int[][] RacialData = m_From.Race == Race.Human ? HumanArray : ElvenArray; + + if (m_From is PlayerMobile pm) + { + pm.SetHairMods(-1, -1); // clear any hairmods (disguise kit, incognito) + pm.HairItemID = pm.Female ? RacialData[info.ButtonID][2] : RacialData[info.ButtonID][3]; + m_Deed.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/HolidayTreeDeed.cs b/Scripts/Items/Deeds/HolidayTreeDeed.cs index 72612b549..46a255f80 100644 --- a/Scripts/Items/Deeds/HolidayTreeDeed.cs +++ b/Scripts/Items/Deeds/HolidayTreeDeed.cs @@ -6,153 +6,155 @@ using Server.Targeting; namespace Server.Items { - public class HolidayTreeDeed : Item - { - public override int LabelNumber => 1041116; // a deed for a holiday tree + public class HolidayTreeDeed : Item + { + [Constructible] + public HolidayTreeDeed() : base(0x14F0) + { + Hue = 0x488; + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public HolidayTreeDeed() : base( 0x14F0 ) - { - Hue = 0x488; - Weight = 1.0; - LootType = LootType.Blessed; - } + public HolidayTreeDeed(Serial serial) : base(serial) + { + } - public HolidayTreeDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041116; // a deed for a holiday tree - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - LootType = LootType.Blessed; - } + LootType = LootType.Blessed; + } - public bool ValidatePlacement( Mobile from, Point3D loc ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; + public bool ValidatePlacement(Mobile from, Point3D loc) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; - if ( !from.InRange( GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - return false; - } + if (!from.InRange(GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(500446); // That is too far away. + return false; + } - if ( DateTime.UtcNow.Month != 12 ) - { - from.SendLocalizedMessage( 1005700 ); // You will have to wait till next December to put your tree back up for display. - return false; - } + if (DateTime.UtcNow.Month != 12) + { + from.SendLocalizedMessage( + 1005700); // You will have to wait till next December to put your tree back up for display. + return false; + } - Map map = from.Map; + Map map = from.Map; - if ( map == null ) - return false; + if (map == null) + return false; - BaseHouse house = BaseHouse.FindHouseAt( loc, map, 20 ); + BaseHouse house = BaseHouse.FindHouseAt(loc, map, 20); - if ( house == null || !house.IsFriend( from ) ) - { - from.SendLocalizedMessage( 1005701 ); // The holiday tree can only be placed in your house. - return false; - } + if (house == null || !house.IsFriend(from)) + { + from.SendLocalizedMessage(1005701); // The holiday tree can only be placed in your house. + return false; + } - if ( !map.CanFit( loc, 20 ) ) - { - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - return false; - } + if (!map.CanFit(loc, 20)) + { + from.SendLocalizedMessage(500269); // You cannot build that there. + return false; + } - return true; - } + return true; + } - public void BeginPlace( Mobile from, HolidayTreeType type ) - { - from.BeginTarget( -1, true, TargetFlags.None, new TargetStateCallback( Placement_OnTarget ), type ); - } + public void BeginPlace(Mobile from, HolidayTreeType type) + { + from.BeginTarget(-1, true, TargetFlags.None, new TargetStateCallback(Placement_OnTarget), type); + } - public void Placement_OnTarget( Mobile from, object targeted, object state ) - { - if ( !(targeted is IPoint3D p) ) - return; + public void Placement_OnTarget(Mobile from, object targeted, object state) + { + if (!(targeted is IPoint3D p)) + return; - Point3D loc = new Point3D( p ); + Point3D loc = new Point3D(p); - if ( p is StaticTarget target ) - loc.Z -= TileData.ItemTable[target.ItemID].CalcHeight; /* NOTE: OSI does not properly normalize Z positioning here. + if (p is StaticTarget target) + loc.Z -= TileData.ItemTable[target.ItemID] + .CalcHeight; /* NOTE: OSI does not properly normalize Z positioning here. * A side affect is that you can only place on floors (due to the CanFit call). * That functionality may be desired. And so, it's included in this script. */ - if ( ValidatePlacement( from, loc ) ) - EndPlace( from, (HolidayTreeType) state, loc ); - } + if (ValidatePlacement(from, loc)) + EndPlace(from, (HolidayTreeType)state, loc); + } - public void EndPlace( Mobile from, HolidayTreeType type, Point3D loc ) - { - Delete(); - HolidayTree tree = new HolidayTree( from, type, loc ); - BaseHouse.FindHouseAt( tree )?.Addons.Add( tree ); - } + public void EndPlace(Mobile from, HolidayTreeType type, Point3D loc) + { + Delete(); + HolidayTree tree = new HolidayTree(from, type, loc); + BaseHouse.FindHouseAt(tree)?.Addons.Add(tree); + } - public override void OnDoubleClick( Mobile from ) - { - from.CloseGump( typeof( HolidayTreeChoiceGump ) ); - from.SendGump( new HolidayTreeChoiceGump( from, this ) ); - } - } + public override void OnDoubleClick(Mobile from) + { + from.CloseGump(typeof(HolidayTreeChoiceGump)); + from.SendGump(new HolidayTreeChoiceGump(from, this)); + } + } - public class HolidayTreeChoiceGump : Gump - { - private Mobile m_From; - private HolidayTreeDeed m_Deed; + public class HolidayTreeChoiceGump : Gump + { + private HolidayTreeDeed m_Deed; + private Mobile m_From; - public HolidayTreeChoiceGump( Mobile from, HolidayTreeDeed deed ) : base( 200, 200 ) - { - m_From = from; - m_Deed = deed; + public HolidayTreeChoiceGump(Mobile from, HolidayTreeDeed deed) : base(200, 200) + { + m_From = from; + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 220, 120, 5054 ); - AddBackground( 10, 10, 200, 100, 3000 ); + AddBackground(0, 0, 220, 120, 5054); + AddBackground(10, 10, 200, 100, 3000); - AddButton( 20, 35, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 35, 145, 25, 1018322, false, false ); // Classic + AddButton(20, 35, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 35, 145, 25, 1018322, false, false); // Classic - AddButton( 20, 65, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 65, 145, 25, 1018321, false, false ); // Modern - } + AddButton(20, 65, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 65, 145, 25, 1018321, false, false); // Modern + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed.Deleted) + return; - switch ( info.ButtonID ) - { - case 1: - { - m_Deed.BeginPlace( m_From, HolidayTreeType.Classic ); - break; - } - case 2: - { - m_Deed.BeginPlace( m_From, HolidayTreeType.Modern ); - break; - } - } - } - } -} + switch (info.ButtonID) + { + case 1: + { + m_Deed.BeginPlace(m_From, HolidayTreeType.Classic); + break; + } + case 2: + { + m_Deed.BeginPlace(m_From, HolidayTreeType.Modern); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/NameChangeDeed.cs b/Scripts/Items/Deeds/NameChangeDeed.cs index 52cfdb37a..8dee3b2bb 100644 --- a/Scripts/Items/Deeds/NameChangeDeed.cs +++ b/Scripts/Items/Deeds/NameChangeDeed.cs @@ -1,123 +1,124 @@ -using System; using Server.Gumps; using Server.Misc; using Server.Network; namespace Server.Items { - public class NameChangeDeed : Item - { - public override string DefaultName => "a name change deed"; + public class NameChangeDeed : Item + { + [Constructible] + public NameChangeDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + } - [Constructible] - public NameChangeDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - } + public NameChangeDeed(Serial serial) : base(serial) + { + } - public NameChangeDeed( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a name change deed"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( RootParent == from ) - { - from.CloseGump( typeof( NameChangeDeedGump ) ); - from.SendGump( new NameChangeDeedGump( this ) ); - } - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + public override void OnDoubleClick(Mobile from) + { + if (RootParent == from) + { + from.CloseGump(typeof(NameChangeDeedGump)); + from.SendGump(new NameChangeDeedGump(this)); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } - public class NameChangeDeedGump : Gump - { - Item m_Sender; + public class NameChangeDeedGump : Gump + { + private Item m_Sender; - public void AddBlackAlpha( int x, int y, int width, int height ) - { - AddImageTiled( x, y, width, height, 2624 ); - AddAlphaRegion( x, y, width, height ); - } + public NameChangeDeedGump(Item sender) : base(50, 50) + { + m_Sender = sender; - public void AddTextField( int x, int y, int width, int height, int index ) - { - AddBackground( x - 2, y - 2, width + 4, height + 4, 0x2486 ); - AddTextEntry( x + 2, y + 2, width - 4, height - 4, 0, index, "" ); - } + Closable = true; + Dragable = true; + Resizable = false; - public string Center( string text ) - { - return $"
{text}
"; - } + AddPage(0); - public string Color( string text, int color ) - { - return $"{text}"; - } + AddBlackAlpha(10, 120, 250, 85); + AddHtml(10, 125, 250, 20, Color(Center("Name Change Deed"), 0xFFFFFF), false, false); - public void AddButtonLabeled( int x, int y, int buttonID, string text ) - { - AddButton( x, y - 1, 4005, 4007, buttonID, GumpButtonType.Reply, 0 ); - AddHtml( x + 35, y, 240, 20, Color( text, 0xFFFFFF ), false, false ); - } + AddLabel(73, 15, 1152, ""); + AddLabel(20, 150, 0x480, "New Name:"); + AddTextField(100, 150, 150, 20, 0); - public NameChangeDeedGump( Item sender ) : base( 50, 50 ) - { - m_Sender = sender; + AddButtonLabeled(75, 180, 1, "Submit"); + } - Closable=true; - Dragable=true; - Resizable=false; + public void AddBlackAlpha(int x, int y, int width, int height) + { + AddImageTiled(x, y, width, height, 2624); + AddAlphaRegion(x, y, width, height); + } - AddPage(0); + public void AddTextField(int x, int y, int width, int height, int index) + { + AddBackground(x - 2, y - 2, width + 4, height + 4, 0x2486); + AddTextEntry(x + 2, y + 2, width - 4, height - 4, 0, index, ""); + } - AddBlackAlpha( 10, 120, 250, 85 ); - AddHtml( 10, 125, 250, 20, Color( Center( "Name Change Deed" ), 0xFFFFFF ), false, false ); + public string Center(string text) + { + return $"
{text}
"; + } - AddLabel( 73, 15, 1152, "" ); - AddLabel( 20, 150, 0x480, "New Name:" ); - AddTextField( 100, 150, 150, 20, 0 ); + public string Color(string text, int color) + { + return $"{text}"; + } - AddButtonLabeled( 75, 180, 1, "Submit" ); - } + public void AddButtonLabeled(int x, int y, int buttonID, string text) + { + AddButton(x, y - 1, 4005, 4007, buttonID, GumpButtonType.Reply, 0); + AddHtml(x + 35, y, 240, 20, Color(text, 0xFFFFFF), false, false); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Sender == null || m_Sender.Deleted || info.ButtonID != 1 || m_Sender.RootParent != sender.Mobile ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Sender == null || m_Sender.Deleted || info.ButtonID != 1 || m_Sender.RootParent != sender.Mobile) + return; - Mobile m = sender.Mobile; - TextRelay nameEntry = info.GetTextEntry( 0 ); + Mobile m = sender.Mobile; + TextRelay nameEntry = info.GetTextEntry(0); - string newName = nameEntry?.Text.Trim(); - + string newName = nameEntry?.Text.Trim(); - if ( !NameVerification.Validate( newName, 2, 16, true, false, true, 1, NameVerification.SpaceDashPeriodQuote ) ) - { - m.SendMessage( "That name is unacceptable." ); - return; - } - m.RawName = newName; - m.SendMessage( "Your name has been changed!" ); - m.SendMessage($"You are now known as {newName}"); - m_Sender.Delete(); - } - } + if (!NameVerification.Validate(newName, 2, 16, true, false, true, 1, NameVerification.SpaceDashPeriodQuote)) + { + m.SendMessage("That name is unacceptable."); + return; + } + + m.RawName = newName; + m.SendMessage("Your name has been changed!"); + m.SendMessage($"You are now known as {newName}"); + m_Sender.Delete(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Deeds/NewPlayerTicket.cs b/Scripts/Items/Deeds/NewPlayerTicket.cs index 2d917ecdc..8b6e10f26 100644 --- a/Scripts/Items/Deeds/NewPlayerTicket.cs +++ b/Scripts/Items/Deeds/NewPlayerTicket.cs @@ -1,188 +1,208 @@ +using Server.Gumps; using Server.Network; using Server.Targeting; -using Server.Gumps; namespace Server.Items { - public class NewPlayerTicket : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } + public class NewPlayerTicket : Item + { + [Constructible] + public NewPlayerTicket() : base(0x14EF) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public override int LabelNumber => 1062094; // a young player ticket + public NewPlayerTicket(Serial serial) : base(serial) + { + } - [Constructible] - public NewPlayerTicket() : base( 0x14EF ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override int LabelNumber => 1062094; // a young player ticket - list.Add( 1041492 ); // This is half a prize ticket! Double-click this ticket and target any other ticket marked NEW PLAYER and get a prize! This ticket will only work for YOU, so don't give it away! - } + public override bool DisplayLootType => false; - public override bool DisplayLootType => false; + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public NewPlayerTicket( Serial serial ) : base( serial ) - { - } + list.Add(1041492); // This is half a prize ticket! Double-click this ticket and target any other ticket marked NEW PLAYER and get a prize! This ticket will only work for YOU, so don't give it away! + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (Mobile) Owner ); - } + writer.Write(Owner); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Owner = reader.ReadMobile(); - break; - } - } + switch (version) + { + case 0: + { + Owner = reader.ReadMobile(); + break; + } + } - if ( Name == "a young player ticket" ) - Name = null; - } + if (Name == "a young player ticket") + Name = null; + } - public override void OnDoubleClick( Mobile from ) - { - if ( from != Owner ) - { - from.SendLocalizedMessage( 501926 ); // This isn't your ticket! Shame on you! You have to use YOUR ticket. - } - else if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - from.SendLocalizedMessage( 501927 ); // Target any other ticket marked NEW PLAYER to win a prize. - from.Target = new InternalTarget( this ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (from != Owner) + { + from.SendLocalizedMessage(501926); // This isn't your ticket! Shame on you! You have to use YOUR ticket. + } + else if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + from.SendLocalizedMessage(501927); // Target any other ticket marked NEW PLAYER to win a prize. + from.Target = new InternalTarget(this); + } + } - private class InternalTarget : Target - { - private NewPlayerTicket m_Ticket; + private class InternalTarget : Target + { + private NewPlayerTicket m_Ticket; - public InternalTarget( NewPlayerTicket ticket ) : base( 2, false, TargetFlags.None ) - { - m_Ticket = ticket; - } + public InternalTarget(NewPlayerTicket ticket) : base(2, false, TargetFlags.None) + { + m_Ticket = ticket; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted == m_Ticket ) - { - from.SendLocalizedMessage( 501928 ); // You can't target the same ticket! - } - else if ( targeted is NewPlayerTicket theirTicket ) - { - Mobile them = theirTicket.Owner; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted == m_Ticket) + { + from.SendLocalizedMessage(501928); // You can't target the same ticket! + } + else if (targeted is NewPlayerTicket theirTicket) + { + Mobile them = theirTicket.Owner; - if ( them == null || them.Deleted ) - { - from.SendLocalizedMessage( 501930 ); // That is not a valid ticket. - } - else - { - from.SendGump( new InternalGump( from, m_Ticket ) ); - them.SendGump( new InternalGump( them, theirTicket ) ); - } - } - else if ((targeted as Item)?.ItemID == 0x14F0 ) - { - from.SendLocalizedMessage( 501931 ); // You need to find another ticket marked NEW PLAYER. - } - else - { - from.SendLocalizedMessage( 501929 ); // You will need to select a ticket. - } - } - } + if (them == null || them.Deleted) + { + from.SendLocalizedMessage(501930); // That is not a valid ticket. + } + else + { + from.SendGump(new InternalGump(from, m_Ticket)); + them.SendGump(new InternalGump(them, theirTicket)); + } + } + else if ((targeted as Item)?.ItemID == 0x14F0) + { + from.SendLocalizedMessage(501931); // You need to find another ticket marked NEW PLAYER. + } + else + { + from.SendLocalizedMessage(501929); // You will need to select a ticket. + } + } + } - private class InternalGump : Gump - { - private Mobile m_From; - private NewPlayerTicket m_Ticket; + private class InternalGump : Gump + { + private Mobile m_From; + private NewPlayerTicket m_Ticket; - public InternalGump( Mobile from, NewPlayerTicket ticket ) : base( 50, 50 ) - { - m_From = from; - m_Ticket = ticket; + public InternalGump(Mobile from, NewPlayerTicket ticket) : base(50, 50) + { + m_From = from; + m_Ticket = ticket; - AddBackground( 0, 0, 400, 385, 0xA28 ); + AddBackground(0, 0, 400, 385, 0xA28); - AddHtmlLocalized( 30, 45, 340, 70, 1013011, true, true ); // Choose the gift you prefer. WARNING: if you cancel, and your partner does not, you will need to find another matching ticket! + AddHtmlLocalized(30, 45, 340, 70, 1013011, true, + true); // Choose the gift you prefer. WARNING: if you cancel, and your partner does not, you will need to find another matching ticket! - AddButton( 46, 128, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 130, 320, 35, 1013012, false, false ); // A sextant + AddButton(46, 128, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 130, 320, 35, 1013012, false, false); // A sextant - AddButton( 46, 163, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 165, 320, 35, 1013013, false, false ); // A coupon for a single hair restyling + AddButton(46, 163, 0xFA5, 0xFA7, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 165, 320, 35, 1013013, false, false); // A coupon for a single hair restyling - AddButton( 46, 198, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 200, 320, 35, 1013014, false, false ); // A spellbook with all 1st - 4th spells. + AddButton(46, 198, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 200, 320, 35, 1013014, false, false); // A spellbook with all 1st - 4th spells. - AddButton( 46, 233, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 235, 320, 35, 1013015, false, false ); // A wand of fireworks + AddButton(46, 233, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 235, 320, 35, 1013015, false, false); // A wand of fireworks - AddButton( 46, 268, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 270, 320, 35, 1013016, false, false ); // A spyglass + AddButton(46, 268, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 270, 320, 35, 1013016, false, false); // A spyglass - AddButton( 46, 303, 0xFA5, 0xFA7, 6, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 305, 320, 35, 1013017, false, false ); // Dyes and a dye tub + AddButton(46, 303, 0xFA5, 0xFA7, 6, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 305, 320, 35, 1013017, false, false); // Dyes and a dye tub - AddButton( 120, 340, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 154, 342, 100, 35, 1011012, false, false ); // CANCEL - } + AddButton(120, 340, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(154, 342, 100, 35, 1011012, false, false); // CANCEL + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Ticket.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Ticket.Deleted) + return; - int number = 0; + int number = 0; - Item item = null; - Item item2 = null; + Item item = null; + Item item2 = null; - switch ( info.ButtonID ) - { - case 1: item = new Sextant(); number = 1010494; break; // A sextant has been placed in your backpack. - case 2: item = new HairRestylingDeed(); number = 501933; break; // A coupon for a free hair restyling has been placed in your backpack. - case 3: item = new Spellbook( 0xFFFFFFFF ); number = 1010495; break; // A spellbook with all 1st to 4th circle spells has been placed in your backpack. - case 4: item = new FireworksWand(); number = 501935; break; // A wand of fireworks has been placed in your backpack. - case 5: item = new Spyglass(); number = 501936; break; // A spyglass has been placed in your backpack. - case 6: item = new DyeTub(); item2 = new Dyes(); number = 501937; break; // The dyes and dye tub have been placed in your backpack. - } + switch (info.ButtonID) + { + case 1: + item = new Sextant(); + number = 1010494; + break; // A sextant has been placed in your backpack. + case 2: + item = new HairRestylingDeed(); + number = 501933; + break; // A coupon for a free hair restyling has been placed in your backpack. + case 3: + item = new Spellbook(0xFFFFFFFF); + number = 1010495; + break; // A spellbook with all 1st to 4th circle spells has been placed in your backpack. + case 4: + item = new FireworksWand(); + number = 501935; + break; // A wand of fireworks has been placed in your backpack. + case 5: + item = new Spyglass(); + number = 501936; + break; // A spyglass has been placed in your backpack. + case 6: + item = new DyeTub(); + item2 = new Dyes(); + number = 501937; + break; // The dyes and dye tub have been placed in your backpack. + } - if ( item != null ) - { - m_Ticket.Delete(); + if (item != null) + { + m_Ticket.Delete(); - m_From.SendLocalizedMessage( number ); - m_From.AddToBackpack( item ); + m_From.SendLocalizedMessage(number); + m_From.AddToBackpack(item); - if ( item2 != null ) - m_From.AddToBackpack( item2 ); - } - } - } - } -} + if (item2 != null) + m_From.AddToBackpack(item2); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Deeds/VendorRentalContract.cs b/Scripts/Items/Deeds/VendorRentalContract.cs index 5f7eeead2..6dac4f299 100644 --- a/Scripts/Items/Deeds/VendorRentalContract.cs +++ b/Scripts/Items/Deeds/VendorRentalContract.cs @@ -1,351 +1,349 @@ using System; using System.Collections.Generic; -using Server.Multis; using Server.ContextMenus; using Server.Gumps; using Server.Mobiles; +using Server.Multis; using Server.Targeting; namespace Server.Items { - public class VendorRentalContract : Item - { - public override int LabelNumber => 1062332; // a vendor rental contract + public class VendorRentalContract : Item + { + private VendorRentalDuration m_Duration; - private VendorRentalDuration m_Duration; + private Mobile m_Offeree; + private Timer m_OfferExpireTimer; - private Mobile m_Offeree; - private Timer m_OfferExpireTimer; + [Constructible] + public VendorRentalContract() : base(0x14F0) + { + Weight = 1.0; + Hue = 0x672; - public VendorRentalDuration Duration - { - get => m_Duration; - set - { - if ( value != null ) - m_Duration = value; - } - } + m_Duration = VendorRentalDuration.Instances[0]; + Price = 1500; + } - [CommandProperty( AccessLevel.GameMaster )] - public int Price { get; set; } + public VendorRentalContract(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool LandlordRenew { get; set; } + public override int LabelNumber => 1062332; // a vendor rental contract - public Mobile Offeree - { - get => m_Offeree; - set - { - if ( m_OfferExpireTimer != null ) - { - m_OfferExpireTimer.Stop(); - m_OfferExpireTimer = null; - } + public VendorRentalDuration Duration + { + get => m_Duration; + set + { + if (value != null) + m_Duration = value; + } + } - m_Offeree = value; + [CommandProperty(AccessLevel.GameMaster)] + public int Price{ get; set; } - if ( value != null ) - { - m_OfferExpireTimer = new OfferExpireTimer( this ); - m_OfferExpireTimer.Start(); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool LandlordRenew{ get; set; } - InvalidateProperties(); - } - } + public Mobile Offeree + { + get => m_Offeree; + set + { + if (m_OfferExpireTimer != null) + { + m_OfferExpireTimer.Stop(); + m_OfferExpireTimer = null; + } - [Constructible] - public VendorRentalContract() : base( 0x14F0 ) - { - Weight = 1.0; - Hue = 0x672; + m_Offeree = value; - m_Duration = VendorRentalDuration.Instances[0]; - Price = 1500; - } + if (value != null) + { + m_OfferExpireTimer = new OfferExpireTimer(this); + m_OfferExpireTimer.Start(); + } - public VendorRentalContract( Serial serial ) : base( serial ) - { - } + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Offeree != null ) - list.Add( 1062368, Offeree.Name ); // Being Offered To ~1_NAME~ - } + if (Offeree != null) + list.Add(1062368, Offeree.Name); // Being Offered To ~1_NAME~ + } - public bool IsLandlord( Mobile m ) - { - if ( IsLockedDown ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public bool IsLandlord(Mobile m) + { + if (IsLockedDown) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - if ( house != null && house.DecayType != DecayType.Condemned ) - return house.IsOwner( m ); - } + if (house != null && house.DecayType != DecayType.Condemned) + return house.IsOwner(m); + } - return false; - } + return false; + } - public bool IsUsableBy( Mobile from, bool byLandlord, bool byBackpack, bool noOfferee, bool sendMessage ) - { - if ( Deleted || !from.CheckAlive( sendMessage ) ) - return false; + public bool IsUsableBy(Mobile from, bool byLandlord, bool byBackpack, bool noOfferee, bool sendMessage) + { + if (Deleted || !from.CheckAlive(sendMessage)) + return false; - if ( noOfferee && Offeree != null ) - { - if ( sendMessage ) - from.SendLocalizedMessage( 1062343 ); // That item is currently in use. + if (noOfferee && Offeree != null) + { + if (sendMessage) + from.SendLocalizedMessage(1062343); // That item is currently in use. - return false; - } + return false; + } - if ( byBackpack && IsChildOf( from.Backpack ) ) - return true; + if (byBackpack && IsChildOf(from.Backpack)) + return true; - if ( byLandlord && IsLandlord( from ) ) - { - if ( from.Map != Map || !from.InRange( this, 5 ) ) - { - if ( sendMessage ) - from.SendLocalizedMessage( 501853 ); // Target is too far away. + if (byLandlord && IsLandlord(from)) + { + if (from.Map != Map || !from.InRange(this, 5)) + { + if (sendMessage) + from.SendLocalizedMessage(501853); // Target is too far away. - return false; - } + return false; + } - return true; - } + return true; + } - return false; - } + return false; + } - public override void OnDelete() - { - if ( IsLockedDown ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public override void OnDelete() + { + if (IsLockedDown) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - house?.VendorRentalContracts.Remove( this ); - } - } + house?.VendorRentalContracts.Remove(this); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( Offeree != null ) - { - from.SendLocalizedMessage( 1062343 ); // That item is currently in use. - } - else if ( !IsLockedDown ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (Offeree != null) + { + from.SendLocalizedMessage(1062343); // That item is currently in use. + } + else if (!IsLockedDown) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + return; + } - BaseHouse house = BaseHouse.FindHouseAt( from ); + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house == null || !house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 1062333 ); // You must be standing inside of a house that you own to make use of this contract. - } - else if ( !house.IsAosRules ) - { - from.SendMessage( "Rental contracts can only be placed in AOS-enabled houses." ); - } - else if ( !house.Public ) - { - from.SendLocalizedMessage( 1062335 ); // Rental contracts can only be placed in public houses. - } - else if ( !house.CanPlaceNewVendor() ) - { - from.SendLocalizedMessage( 1062352 ); // You do not have enough storage available to place this contract. - } - else - { - from.SendLocalizedMessage( 1062337 ); // Target the exact location you wish to rent out. - from.Target = new RentTarget( this ); - } - } - else if ( IsLandlord( from ) ) - { - if ( from.InRange( this, 5 ) ) - { - from.CloseGump( typeof( VendorRentalContractGump ) ); - from.SendGump( new VendorRentalContractGump( this, from ) ); - } - else - { - from.SendLocalizedMessage( 501853 ); // Target is too far away. - } - } - } + if (house == null || !house.IsOwner(from)) + { + from.SendLocalizedMessage( + 1062333); // You must be standing inside of a house that you own to make use of this contract. + } + else if (!house.IsAosRules) + { + from.SendMessage("Rental contracts can only be placed in AOS-enabled houses."); + } + else if (!house.Public) + { + from.SendLocalizedMessage(1062335); // Rental contracts can only be placed in public houses. + } + else if (!house.CanPlaceNewVendor()) + { + from.SendLocalizedMessage(1062352); // You do not have enough storage available to place this contract. + } + else + { + from.SendLocalizedMessage(1062337); // Target the exact location you wish to rent out. + from.Target = new RentTarget(this); + } + } + else if (IsLandlord(from)) + { + if (from.InRange(this, 5)) + { + from.CloseGump(typeof(VendorRentalContractGump)); + from.SendGump(new VendorRentalContractGump(this, from)); + } + else + { + from.SendLocalizedMessage(501853); // Target is too far away. + } + } + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( IsUsableBy( from, true, true, true, false ) ) - { - list.Add( new ContractOptionEntry( this ) ); - } - } + if (IsUsableBy(from, true, true, true, false)) list.Add(new ContractOptionEntry(this)); + } - private class ContractOptionEntry : ContextMenuEntry - { - private VendorRentalContract m_Contract; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public ContractOptionEntry( VendorRentalContract contract ) : base( 6209 ) - { - m_Contract = contract; - } + writer.WriteEncodedInt(0); // version - public override void OnClick() - { - Mobile from = Owner.From; + writer.WriteEncodedInt(m_Duration.ID); - if ( m_Contract.IsUsableBy( from, true, true, true, true ) ) - { - from.CloseGump( typeof( VendorRentalContractGump ) ); - from.SendGump( new VendorRentalContractGump( m_Contract, from ) ); - } - } - } + writer.Write(Price); + writer.Write(LandlordRenew); + } - private class RentTarget : Target - { - private VendorRentalContract m_Contract; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public RentTarget( VendorRentalContract contract ) : base( -1, false, TargetFlags.None ) - { - m_Contract = contract; - } + int version = reader.ReadEncodedInt(); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Contract.IsUsableBy( from, false, true, true, true ) ) - return; + int durationID = reader.ReadEncodedInt(); + if (durationID < VendorRentalDuration.Instances.Length) + m_Duration = VendorRentalDuration.Instances[durationID]; + else + m_Duration = VendorRentalDuration.Instances[0]; - if ( !(targeted is IPoint3D location) ) - return; + Price = reader.ReadInt(); + LandlordRenew = reader.ReadBool(); + } - Point3D pLocation = new Point3D( location ); - Map map = from.Map; + private class ContractOptionEntry : ContextMenuEntry + { + private VendorRentalContract m_Contract; - BaseHouse house = BaseHouse.FindHouseAt( pLocation, map, 0 ); + public ContractOptionEntry(VendorRentalContract contract) : base(6209) + { + m_Contract = contract; + } - if ( house == null || !house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 1062338 ); // The location being rented out must be inside of your house. - } - else if ( BaseHouse.FindHouseAt( from ) != house ) - { - from.SendLocalizedMessage( 1062339 ); // You must be located inside of the house in which you are trying to place the contract. - } - else if ( !house.IsAosRules ) - { - from.SendMessage( "Rental contracts can only be placed in AOS-enabled houses." ); - } - else if ( !house.Public ) - { - from.SendLocalizedMessage( 1062335 ); // Rental contracts can only be placed in public houses. - } - else if ( house.DecayType == DecayType.Condemned ) - { - from.SendLocalizedMessage( 1062468 ); // You cannot place a contract in a condemned house. - } - else if ( !house.CanPlaceNewVendor() ) - { - from.SendLocalizedMessage( 1062352 ); // You do not have enought storage available to place this contract. - } - else if ( !map.CanFit( pLocation, 16, false, false ) ) - { - from.SendLocalizedMessage( 1062486 ); // A vendor cannot exist at that location. Please try again. - } - else - { - BaseHouse.IsThereVendor( pLocation, map, out var vendor, out var contract ); + public override void OnClick() + { + Mobile from = Owner.From; - if ( vendor ) - { - from.SendLocalizedMessage( 1062342 ); // You may not place a rental contract at this location while other beings occupy it. - } - else if ( contract ) - { - from.SendLocalizedMessage( 1062341 ); // That location is cluttered. Please clear out any objects there and try again. - } - else - { - m_Contract.MoveToWorld( pLocation, map ); + if (m_Contract.IsUsableBy(from, true, true, true, true)) + { + from.CloseGump(typeof(VendorRentalContractGump)); + from.SendGump(new VendorRentalContractGump(m_Contract, from)); + } + } + } - if ( !house.LockDown( from, m_Contract ) ) - { - from.AddToBackpack( m_Contract ); - } - } - } - } + private class RentTarget : Target + { + private VendorRentalContract m_Contract; - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - from.SendLocalizedMessage( 1062336 ); // You decide not to place the contract at this time. - } - } + public RentTarget(VendorRentalContract contract) : base(-1, false, TargetFlags.None) + { + m_Contract = contract; + } - private class OfferExpireTimer : Timer - { - private VendorRentalContract m_Contract; + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Contract.IsUsableBy(from, false, true, true, true)) + return; - public OfferExpireTimer( VendorRentalContract contract ) : base( TimeSpan.FromSeconds( 30.0 ) ) - { - m_Contract = contract; + if (!(targeted is IPoint3D location)) + return; - Priority = TimerPriority.OneSecond; - } + Point3D pLocation = new Point3D(location); + Map map = from.Map; - protected override void OnTick() - { - Mobile offeree = m_Contract.Offeree; + BaseHouse house = BaseHouse.FindHouseAt(pLocation, map, 0); - if ( offeree != null ) - { - offeree.CloseGump( typeof( VendorRentalOfferGump ) ); + if (house == null || !house.IsOwner(from)) + { + from.SendLocalizedMessage(1062338); // The location being rented out must be inside of your house. + } + else if (BaseHouse.FindHouseAt(from) != house) + { + from.SendLocalizedMessage( + 1062339); // You must be located inside of the house in which you are trying to place the contract. + } + else if (!house.IsAosRules) + { + from.SendMessage("Rental contracts can only be placed in AOS-enabled houses."); + } + else if (!house.Public) + { + from.SendLocalizedMessage(1062335); // Rental contracts can only be placed in public houses. + } + else if (house.DecayType == DecayType.Condemned) + { + from.SendLocalizedMessage(1062468); // You cannot place a contract in a condemned house. + } + else if (!house.CanPlaceNewVendor()) + { + from.SendLocalizedMessage(1062352); // You do not have enought storage available to place this contract. + } + else if (!map.CanFit(pLocation, 16, false, false)) + { + from.SendLocalizedMessage(1062486); // A vendor cannot exist at that location. Please try again. + } + else + { + BaseHouse.IsThereVendor(pLocation, map, out bool vendor, out bool contract); - m_Contract.Offeree = null; - } - } - } + if (vendor) + { + from.SendLocalizedMessage( + 1062342); // You may not place a rental contract at this location while other beings occupy it. + } + else if (contract) + { + from.SendLocalizedMessage( + 1062341); // That location is cluttered. Please clear out any objects there and try again. + } + else + { + m_Contract.MoveToWorld(pLocation, map); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (!house.LockDown(from, m_Contract)) from.AddToBackpack(m_Contract); + } + } + } - writer.WriteEncodedInt( 0 ); // version + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + from.SendLocalizedMessage(1062336); // You decide not to place the contract at this time. + } + } - writer.WriteEncodedInt( m_Duration.ID ); + private class OfferExpireTimer : Timer + { + private VendorRentalContract m_Contract; - writer.Write( (int) Price ); - writer.Write( (bool) LandlordRenew ); - } + public OfferExpireTimer(VendorRentalContract contract) : base(TimeSpan.FromSeconds(30.0)) + { + m_Contract = contract; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Priority = TimerPriority.OneSecond; + } - int version = reader.ReadEncodedInt(); + protected override void OnTick() + { + Mobile offeree = m_Contract.Offeree; - int durationID = reader.ReadEncodedInt(); - if ( durationID < VendorRentalDuration.Instances.Length ) - m_Duration = VendorRentalDuration.Instances[durationID]; - else - m_Duration = VendorRentalDuration.Instances[0]; + if (offeree != null) + { + offeree.CloseGump(typeof(VendorRentalOfferGump)); - Price = reader.ReadInt(); - LandlordRenew = reader.ReadBool(); - } - } -} + m_Contract.Offeree = null; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Facial/Beard.cs b/Scripts/Items/Facial/Beard.cs index 7657e5b69..7dced0ecc 100644 --- a/Scripts/Items/Facial/Beard.cs +++ b/Scripts/Items/Facial/Beard.cs @@ -1,328 +1,320 @@ namespace Server.Items { - public abstract class Beard : Item - { - /*public static Beard CreateByID( int id, int hue ) - { - switch ( id ) - { - case 0x203E: return new LongBeard( hue ); - case 0x203F: return new ShortBeard( hue ); - case 0x2040: return new Goatee( hue ); - case 0x2041: return new Mustache( hue ); - case 0x204B: return new MediumShortBeard( hue ); - case 0x204C: return new MediumLongBeard( hue ); - case 0x204D: return new Vandyke( hue ); - default: return new GenericBeard( id, hue ); - } - }*/ - - protected Beard( int itemID ) : this( itemID, 0 ) - { - } - - protected Beard( int itemID, int hue ) : base( itemID ) - { - LootType = LootType.Blessed; - Layer = Layer.FacialHair; - Hue = hue; - } - - public Beard( Serial serial ) : base( serial ) - { - } - - public override bool DisplayLootType => false; - - public override bool VerifyMove( Mobile from ) - { - return ( from.AccessLevel >= AccessLevel.GameMaster ); - } - - public override DeathMoveResult OnParentDeath( Mobile parent ) - { - //Dupe( Amount ); - - parent.FacialHairItemID = ItemID; - parent.FacialHairHue = Hue; - - return DeathMoveResult.MoveToCorpse; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; - - int version = reader.ReadInt(); - } - } - - public class GenericBeard : Beard - { - - private GenericBeard( int itemID ) : this( itemID, 0 ) - { - } - - - private GenericBeard( int itemID, int hue ) : base( itemID, hue ) - { - } - - public GenericBeard( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LongBeard : Beard - { + public abstract class Beard : Item + { + /*public static Beard CreateByID( int id, int hue ) + { + switch ( id ) + { + case 0x203E: return new LongBeard( hue ); + case 0x203F: return new ShortBeard( hue ); + case 0x2040: return new Goatee( hue ); + case 0x2041: return new Mustache( hue ); + case 0x204B: return new MediumShortBeard( hue ); + case 0x204C: return new MediumLongBeard( hue ); + case 0x204D: return new Vandyke( hue ); + default: return new GenericBeard( id, hue ); + } + }*/ + + protected Beard(int itemID) : this(itemID, 0) + { + } + + protected Beard(int itemID, int hue) : base(itemID) + { + LootType = LootType.Blessed; + Layer = Layer.FacialHair; + Hue = hue; + } + + public Beard(Serial serial) : base(serial) + { + } + + public override bool DisplayLootType => false; + + public override bool VerifyMove(Mobile from) + { + return from.AccessLevel >= AccessLevel.GameMaster; + } + + public override DeathMoveResult OnParentDeath(Mobile parent) + { + //Dupe( Amount ); + + parent.FacialHairItemID = ItemID; + parent.FacialHairHue = Hue; + + return DeathMoveResult.MoveToCorpse; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; + + int version = reader.ReadInt(); + } + } + + public class GenericBeard : Beard + { + private GenericBeard(int itemID) : this(itemID, 0) + { + } + + + private GenericBeard(int itemID, int hue) : base(itemID, hue) + { + } + + public GenericBeard(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LongBeard : Beard + { + private LongBeard() + : this(0) + { + } + + private LongBeard(int hue) + : base(0x203E, hue) + { + } + + public LongBeard(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private LongBeard() - : this( 0 ) - { - } + writer.Write(0); // version + } - private LongBeard( int hue ) - : base( 0x203E, hue ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public LongBeard( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public class ShortBeard : Beard + { + private ShortBeard() + : this(0) + { + } - writer.Write( (int) 0 ); // version - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + private ShortBeard(int hue) + : base(0x203f, hue) + { + } - int version = reader.ReadInt(); - } - } + public ShortBeard(Serial serial) : base(serial) + { + } - public class ShortBeard : Beard - { + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private ShortBeard() - : this( 0 ) - { - } + writer.Write(0); // version + } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - private ShortBeard( int hue ) - : base( 0x203f, hue ) - { - } + int version = reader.ReadInt(); + } + } + + public class Goatee : Beard + { + private Goatee() + : this(0) + { + } - public ShortBeard( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private Goatee(int hue) + : base(0x2040, hue) + { + } + + public Goatee(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public class Goatee : Beard - { + int version = reader.ReadInt(); + } + } + + public class Mustache : Beard + { + private Mustache() + : this(0) + { + } + + + private Mustache(int hue) + : base(0x2041, hue) + { + } - private Goatee() - : this( 0 ) - { - } + public Mustache(Serial serial) : base(serial) + { + } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private Goatee( int hue ) - : base( 0x2040, hue ) - { - } + writer.Write(0); // version + } - public Goatee( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); + } + } - writer.Write( (int) 0 ); // version - } + public class MediumShortBeard : Beard + { + private MediumShortBeard() + : this(0) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + private MediumShortBeard(int hue) + : base(0x204B, hue) + { + } + + public MediumShortBeard(Serial serial) : base(serial) + { + } - public class Mustache : Beard - { + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private Mustache() - : this( 0 ) - { - } + writer.Write(0); // version + } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - private Mustache( int hue ) - : base( 0x2041, hue ) - { - } + int version = reader.ReadInt(); + } + } - public Mustache( Serial serial ) : base( serial ) - { - } + public class MediumLongBeard : Beard + { + private MediumLongBeard() + : this(0) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + private MediumLongBeard(int hue) + : base(0x204C, hue) + { + } + + public MediumLongBeard(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } - public class MediumShortBeard : Beard - { + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - private MediumShortBeard() - : this( 0 ) - { - } + int version = reader.ReadInt(); + } + } + public class Vandyke : Beard + { + private Vandyke() + : this(0) + { + } - private MediumShortBeard( int hue ) - : base( 0x204B, hue ) - { - } - public MediumShortBeard( Serial serial ) : base( serial ) - { - } + private Vandyke(int hue) + : base(0x204D, hue) + { + } + + public Vandyke(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } - - public class MediumLongBeard : Beard - { - - private MediumLongBeard() - : this( 0 ) - { - } - - - private MediumLongBeard( int hue ) - : base( 0x204C, hue ) - { - } - - public MediumLongBeard( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Vandyke : Beard - { - - private Vandyke() - : this( 0 ) - { - } - - - private Vandyke( int hue ) - : base( 0x204D, hue ) - { - } - - public Vandyke( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Facial/Hair.cs b/Scripts/Items/Facial/Hair.cs index 7e98d9b61..1adce6ab5 100644 --- a/Scripts/Items/Facial/Hair.cs +++ b/Scripts/Items/Facial/Hair.cs @@ -1,489 +1,478 @@ namespace Server.Items { - public abstract class Hair : Item - { - /* + public abstract class Hair : Item + { + /* - public static Hair GetRandomHair( bool female ) - { - return GetRandomHair( female, Utility.RandomHairHue() ); - } + public static Hair GetRandomHair( bool female ) + { + return GetRandomHair( female, Utility.RandomHairHue() ); + } - public static Hair GetRandomHair( bool female, int hairHue ) - { - if ( female ) - { - switch ( Utility.Random( 9 ) ) - { - case 0: return new Afro( hairHue ); - case 1: return new KrisnaHair( hairHue ); - case 2: return new PageboyHair( hairHue ); - case 3: return new PonyTail( hairHue ); - case 4: return new ReceedingHair( hairHue ); - case 5: return new TwoPigTails( hairHue ); - case 6: return new ShortHair( hairHue ); - case 7: return new LongHair( hairHue ); - default: return new BunsHair( hairHue ); - } - } - else - { - switch ( Utility.Random( 8 ) ) - { - case 0: return new Afro( hairHue ); - case 1: return new KrisnaHair( hairHue ); - case 2: return new PageboyHair( hairHue ); - case 3: return new PonyTail( hairHue ); - case 4: return new ReceedingHair( hairHue ); - case 5: return new TwoPigTails( hairHue ); - case 6: return new ShortHair( hairHue ); - default: return new LongHair( hairHue ); - } - } - } + public static Hair GetRandomHair( bool female, int hairHue ) + { + if ( female ) + { + switch ( Utility.Random( 9 ) ) + { + case 0: return new Afro( hairHue ); + case 1: return new KrisnaHair( hairHue ); + case 2: return new PageboyHair( hairHue ); + case 3: return new PonyTail( hairHue ); + case 4: return new ReceedingHair( hairHue ); + case 5: return new TwoPigTails( hairHue ); + case 6: return new ShortHair( hairHue ); + case 7: return new LongHair( hairHue ); + default: return new BunsHair( hairHue ); + } + } + else + { + switch ( Utility.Random( 8 ) ) + { + case 0: return new Afro( hairHue ); + case 1: return new KrisnaHair( hairHue ); + case 2: return new PageboyHair( hairHue ); + case 3: return new PonyTail( hairHue ); + case 4: return new ReceedingHair( hairHue ); + case 5: return new TwoPigTails( hairHue ); + case 6: return new ShortHair( hairHue ); + default: return new LongHair( hairHue ); + } + } + } - public static Hair CreateByID( int id, int hue ) - { - switch ( id ) - { - case 0x203B: return new ShortHair( hue ); - case 0x203C: return new LongHair( hue ); - case 0x203D: return new PonyTail( hue ); - case 0x2044: return new Mohawk( hue ); - case 0x2045: return new PageboyHair( hue ); - case 0x2046: return new BunsHair( hue ); - case 0x2047: return new Afro( hue ); - case 0x2048: return new ReceedingHair( hue ); - case 0x2049: return new TwoPigTails( hue ); - case 0x204A: return new KrisnaHair( hue ); - default: return new GenericHair( id, hue ); - } - } - * */ + public static Hair CreateByID( int id, int hue ) + { + switch ( id ) + { + case 0x203B: return new ShortHair( hue ); + case 0x203C: return new LongHair( hue ); + case 0x203D: return new PonyTail( hue ); + case 0x2044: return new Mohawk( hue ); + case 0x2045: return new PageboyHair( hue ); + case 0x2046: return new BunsHair( hue ); + case 0x2047: return new Afro( hue ); + case 0x2048: return new ReceedingHair( hue ); + case 0x2049: return new TwoPigTails( hue ); + case 0x204A: return new KrisnaHair( hue ); + default: return new GenericHair( id, hue ); + } + } + * */ - protected Hair( int itemID ) - : this( itemID, 0 ) - { - } + protected Hair(int itemID) + : this(itemID, 0) + { + } - protected Hair( int itemID, int hue ) - : base( itemID ) - { - LootType = LootType.Blessed; - Layer = Layer.Hair; - Hue = hue; - } + protected Hair(int itemID, int hue) + : base(itemID) + { + LootType = LootType.Blessed; + Layer = Layer.Hair; + Hue = hue; + } - public Hair( Serial serial ) - : base( serial ) - { - } + public Hair(Serial serial) + : base(serial) + { + } - public override bool DisplayLootType => false; + public override bool DisplayLootType => false; - public override bool VerifyMove( Mobile from ) - { - return (from.AccessLevel >= AccessLevel.GameMaster); - } + public override bool VerifyMove(Mobile from) + { + return from.AccessLevel >= AccessLevel.GameMaster; + } - public override DeathMoveResult OnParentDeath( Mobile parent ) - { + public override DeathMoveResult OnParentDeath(Mobile parent) + { // Dupe( Amount ); - parent.HairItemID = ItemID; - parent.HairHue = Hue; + parent.HairItemID = ItemID; + parent.HairHue = Hue; - return DeathMoveResult.MoveToCorpse; - } + return DeathMoveResult.MoveToCorpse; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GenericHair : Hair - { + public class GenericHair : Hair + { + private GenericHair(int itemID) + : this(itemID, 0) + { + } - private GenericHair( int itemID ) - : this( itemID, 0 ) - { - } + private GenericHair(int itemID, int hue) + : base(itemID, hue) + { + } - private GenericHair( int itemID, int hue ) - : base( itemID, hue ) - { - } + public GenericHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } - public GenericHair( Serial serial ) - : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); + } + } - writer.Write( (int)0 ); // version - } + public class Mohawk : Hair + { + private Mohawk() + : this(0) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + private Mohawk(int hue) + : base(0x2044, hue) + { + } + + public Mohawk(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PageboyHair : Hair + { + private PageboyHair() + : this(0) + { + } - public class Mohawk : Hair - { - private Mohawk() - : this( 0 ) - { - } + private PageboyHair(int hue) + : base(0x2045, hue) + { + } + + public PageboyHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BunsHair : Hair + { + private BunsHair() + : this(0) + { + } + + private BunsHair(int hue) + : base(0x2046, hue) + { + } + + public BunsHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LongHair : Hair + { + private LongHair() + : this(0) + { + } - private Mohawk( int hue ) - : base( 0x2044, hue ) - { - } - public Mohawk( Serial serial ) - : base( serial ) - { - } + private LongHair(int hue) + : base(0x203C, hue) + { + } + + public LongHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ShortHair : Hair + { + private ShortHair() + : this(0) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 ); // version - } + private ShortHair(int hue) + : base(0x203B, hue) + { + } + + public ShortHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PonyTail : Hair + { + private PonyTail() + : this(0) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + private PonyTail(int hue) + : base(0x203D, hue) + { + } + + public PonyTail(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Afro : Hair + { + private Afro() + : this(0) + { + } - public class PageboyHair : Hair - { - private PageboyHair() - : this( 0 ) - { - } + private Afro(int hue) + : base(0x2047, hue) + { + } + + public Afro(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ReceedingHair : Hair + { + private ReceedingHair() + : this(0) + { + } + + + private ReceedingHair(int hue) + : base(0x2048, hue) + { + } + + public ReceedingHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TwoPigTails : Hair + { + private TwoPigTails() + : this(0) + { + } + + private TwoPigTails(int hue) + : base(0x2049, hue) + { + } + + public TwoPigTails(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class KrisnaHair : Hair + { + private KrisnaHair() + : this(0) + { + } - private PageboyHair( int hue ) - : base( 0x2045, hue ) - { - } - public PageboyHair( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BunsHair : Hair - { - - private BunsHair() - : this( 0 ) - { - } - - - private BunsHair( int hue ) - : base( 0x2046, hue ) - { - } - - public BunsHair( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LongHair : Hair - { - - private LongHair() - : this( 0 ) - { - } - - - private LongHair( int hue ) - : base( 0x203C, hue ) - { - } - - public LongHair( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ShortHair : Hair - { - - private ShortHair() - : this( 0 ) - { - } - - - private ShortHair( int hue ) - : base( 0x203B, hue ) - { - } - - public ShortHair( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PonyTail : Hair - { - - private PonyTail() - : this( 0 ) - { - } - - - private PonyTail( int hue ) - : base( 0x203D, hue ) - { - } - - public PonyTail( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Afro : Hair - { - - private Afro() - : this( 0 ) - { - } - - - private Afro( int hue ) - : base( 0x2047, hue ) - { - } - - public Afro( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ReceedingHair : Hair - { - - private ReceedingHair() - : this( 0 ) - { - } - - - private ReceedingHair( int hue ) - : base( 0x2048, hue ) - { - } - - public ReceedingHair( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TwoPigTails : Hair - { - - private TwoPigTails() - : this( 0 ) - { - } - - - private TwoPigTails( int hue ) - : base( 0x2049, hue ) - { - } - - public TwoPigTails( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class KrisnaHair : Hair - { - - private KrisnaHair() - : this( 0 ) - { - } - - - private KrisnaHair( int hue ) - : base( 0x204A, hue ) - { - } - - public KrisnaHair( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + private KrisnaHair(int hue) + : base(0x204A, hue) + { + } + + public KrisnaHair(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableCabbage.cs b/Scripts/Items/Farming/FarmableCabbage.cs index 72c90eb91..ad1d7bde9 100644 --- a/Scripts/Items/Farming/FarmableCabbage.cs +++ b/Scripts/Items/Farming/FarmableCabbage.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class FarmableCabbage : FarmableCrop - { - public static int GetCropID() - { - return 3254; - } + public class FarmableCabbage : FarmableCrop + { + [Constructible] + public FarmableCabbage() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Cabbage cabbage = new Cabbage(); + public FarmableCabbage(Serial serial) : base(serial) + { + } - cabbage.ItemID = Utility.Random( 3195, 2 ); + public static int GetCropID() + { + return 3254; + } - return cabbage; - } + public override Item GetCropObject() + { + Cabbage cabbage = new Cabbage(); - public override int GetPickedID() - { - return 3254; - } + cabbage.ItemID = Utility.Random(3195, 2); - [Constructible] - public FarmableCabbage() : base( GetCropID() ) - { - } + return cabbage; + } - public FarmableCabbage( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableCarrot.cs b/Scripts/Items/Farming/FarmableCarrot.cs index 38a66fe51..dcd043889 100644 --- a/Scripts/Items/Farming/FarmableCarrot.cs +++ b/Scripts/Items/Farming/FarmableCarrot.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class FarmableCarrot : FarmableCrop - { - public static int GetCropID() - { - return 3190; - } + public class FarmableCarrot : FarmableCrop + { + [Constructible] + public FarmableCarrot() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Carrot carrot = new Carrot(); + public FarmableCarrot(Serial serial) : base(serial) + { + } - carrot.ItemID = Utility.Random( 3191, 2 ); + public static int GetCropID() + { + return 3190; + } - return carrot; - } + public override Item GetCropObject() + { + Carrot carrot = new Carrot(); - public override int GetPickedID() - { - return 3254; - } + carrot.ItemID = Utility.Random(3191, 2); - [Constructible] - public FarmableCarrot() : base( GetCropID() ) - { - } + return carrot; + } - public FarmableCarrot( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableCotton.cs b/Scripts/Items/Farming/FarmableCotton.cs index 151cbf9e4..e6539ee02 100644 --- a/Scripts/Items/Farming/FarmableCotton.cs +++ b/Scripts/Items/Farming/FarmableCotton.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class FarmableCotton : FarmableCrop - { - public static int GetCropID() - { - return Utility.Random( 3153, 4 ); - } + public class FarmableCotton : FarmableCrop + { + [Constructible] + public FarmableCotton() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - return new Cotton(); - } + public FarmableCotton(Serial serial) : base(serial) + { + } - public override int GetPickedID() - { - return 3254; - } + public static int GetCropID() + { + return Utility.Random(3153, 4); + } - [Constructible] - public FarmableCotton() : base( GetCropID() ) - { - } + public override Item GetCropObject() + { + return new Cotton(); + } - public FarmableCotton( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableCrop.cs b/Scripts/Items/Farming/FarmableCrop.cs index d9650a2e9..6f0691f3a 100644 --- a/Scripts/Items/Farming/FarmableCrop.cs +++ b/Scripts/Items/Farming/FarmableCrop.cs @@ -3,89 +3,89 @@ using Server.Network; namespace Server.Items { - public abstract class FarmableCrop : Item - { - private bool m_Picked; + public abstract class FarmableCrop : Item + { + private bool m_Picked; - public abstract Item GetCropObject(); - public abstract int GetPickedID(); + public FarmableCrop(int itemID) : base(itemID) + { + Movable = false; + } - public FarmableCrop( int itemID ) : base( itemID ) - { - Movable = false; - } + public FarmableCrop(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - Map map = Map; - Point3D loc = Location; + public abstract Item GetCropObject(); + public abstract int GetPickedID(); - if ( Parent != null || Movable || IsLockedDown || IsSecure || map == null || map == Map.Internal ) - return; + public override void OnDoubleClick(Mobile from) + { + Map map = Map; + Point3D loc = Location; - if ( !from.InRange( loc, 2 ) || !from.InLOS( this ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else if ( !m_Picked ) - OnPicked( from, loc, map ); - } + if (Parent != null || Movable || IsLockedDown || IsSecure || map == null || map == Map.Internal) + return; - public virtual void OnPicked( Mobile from, Point3D loc, Map map ) - { - ItemID = GetPickedID(); + if (!from.InRange(loc, 2) || !from.InLOS(this)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (!m_Picked) + OnPicked(from, loc, map); + } - Item spawn = GetCropObject(); + public virtual void OnPicked(Mobile from, Point3D loc, Map map) + { + ItemID = GetPickedID(); - spawn?.MoveToWorld( loc, map ); + Item spawn = GetCropObject(); - m_Picked = true; + spawn?.MoveToWorld(loc, map); - Unlink(); + m_Picked = true; - Timer.DelayCall( TimeSpan.FromMinutes( 5.0 ), Delete ); - } + Unlink(); - public void Unlink() - { - ISpawner se = Spawner; + Timer.DelayCall(TimeSpan.FromMinutes(5.0), Delete); + } - if ( se != null ) - { - Spawner.Remove( this ); - Spawner = null; - } + public void Unlink() + { + ISpawner se = Spawner; - } + if (se != null) + { + Spawner.Remove(this); + Spawner = null; + } + } - public FarmableCrop( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); // version - writer.WriteEncodedInt( 0 ); // version + writer.Write(m_Picked); + } - writer.Write( m_Picked ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadEncodedInt(); - int version = reader.ReadEncodedInt(); + switch (version) + { + case 0: + m_Picked = reader.ReadBool(); + break; + } - switch ( version ) - { - case 0: - m_Picked = reader.ReadBool(); - break; - } - if ( m_Picked ) - { - Unlink(); - Delete(); - } - } - } + if (m_Picked) + { + Unlink(); + Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableFlax.cs b/Scripts/Items/Farming/FarmableFlax.cs index 7a803f7fe..1fb45eb86 100644 --- a/Scripts/Items/Farming/FarmableFlax.cs +++ b/Scripts/Items/Farming/FarmableFlax.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class FarmableFlax : FarmableCrop - { - public static int GetCropID() - { - return Utility.Random( 6809, 3 ); - } + public class FarmableFlax : FarmableCrop + { + [Constructible] + public FarmableFlax() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Flax flax = new Flax(); + public FarmableFlax(Serial serial) : base(serial) + { + } - flax.ItemID = Utility.Random( 6812, 2 ); + public static int GetCropID() + { + return Utility.Random(6809, 3); + } - return flax; - } + public override Item GetCropObject() + { + Flax flax = new Flax(); - public override int GetPickedID() - { - return 3254; - } + flax.ItemID = Utility.Random(6812, 2); - [Constructible] - public FarmableFlax() : base( GetCropID() ) - { - } + return flax; + } - public FarmableFlax( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableLettuce.cs b/Scripts/Items/Farming/FarmableLettuce.cs index e6cd33743..3db700ba8 100644 --- a/Scripts/Items/Farming/FarmableLettuce.cs +++ b/Scripts/Items/Farming/FarmableLettuce.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class FarmableLettuce : FarmableCrop - { - public static int GetCropID() - { - return 3254; - } + public class FarmableLettuce : FarmableCrop + { + [Constructible] + public FarmableLettuce() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Lettuce lettuce = new Lettuce(); + public FarmableLettuce(Serial serial) : base(serial) + { + } - lettuce.ItemID = Utility.Random( 3184, 2 ); + public static int GetCropID() + { + return 3254; + } - return lettuce; - } + public override Item GetCropObject() + { + Lettuce lettuce = new Lettuce(); - public override int GetPickedID() - { - return 3254; - } + lettuce.ItemID = Utility.Random(3184, 2); - [Constructible] - public FarmableLettuce() : base( GetCropID() ) - { - } + return lettuce; + } - public FarmableLettuce( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableOnion.cs b/Scripts/Items/Farming/FarmableOnion.cs index 5d5780cb7..8ea9dd70e 100644 --- a/Scripts/Items/Farming/FarmableOnion.cs +++ b/Scripts/Items/Farming/FarmableOnion.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class FarmableOnion : FarmableCrop - { - public static int GetCropID() - { - return 3183; - } + public class FarmableOnion : FarmableCrop + { + [Constructible] + public FarmableOnion() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Onion onion = new Onion(); + public FarmableOnion(Serial serial) : base(serial) + { + } - onion.ItemID = Utility.Random( 3181, 2 ); + public static int GetCropID() + { + return 3183; + } - return onion; - } + public override Item GetCropObject() + { + Onion onion = new Onion(); - public override int GetPickedID() - { - return 3254; - } + onion.ItemID = Utility.Random(3181, 2); - [Constructible] - public FarmableOnion() : base( GetCropID() ) - { - } + return onion; + } - public FarmableOnion( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmablePumpkin.cs b/Scripts/Items/Farming/FarmablePumpkin.cs index 895aeb605..9174594a5 100644 --- a/Scripts/Items/Farming/FarmablePumpkin.cs +++ b/Scripts/Items/Farming/FarmablePumpkin.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class FarmablePumpkin : FarmableCrop - { - public static int GetCropID() - { - return Utility.Random( 3166, 3 ); - } + public class FarmablePumpkin : FarmableCrop + { + [Constructible] + public FarmablePumpkin() + : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Pumpkin pumpkin = new Pumpkin(); + public FarmablePumpkin(Serial serial) + : base(serial) + { + } - pumpkin.ItemID = Utility.Random( 3178, 3 ); + public static int GetCropID() + { + return Utility.Random(3166, 3); + } - return pumpkin; - } + public override Item GetCropObject() + { + Pumpkin pumpkin = new Pumpkin(); - public override int GetPickedID() - { - return Utility.Random( 3166, 3 ); - } + pumpkin.ItemID = Utility.Random(3178, 3); - [Constructible] - public FarmablePumpkin() - : base( GetCropID() ) - { - } + return pumpkin; + } - public FarmablePumpkin( Serial serial ) - : base( serial ) - { - } + public override int GetPickedID() + { + return Utility.Random(3166, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableTurnip.cs b/Scripts/Items/Farming/FarmableTurnip.cs index 888a4a0d5..881dd8f65 100644 --- a/Scripts/Items/Farming/FarmableTurnip.cs +++ b/Scripts/Items/Farming/FarmableTurnip.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class FarmableTurnip : FarmableCrop - { - public static int GetCropID() - { - return Utility.Random( 3169, 3 ); - } + public class FarmableTurnip : FarmableCrop + { + [Constructible] + public FarmableTurnip() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - Turnip turnip = new Turnip(); + public FarmableTurnip(Serial serial) : base(serial) + { + } - turnip.ItemID = Utility.Random( 3385, 2 ); + public static int GetCropID() + { + return Utility.Random(3169, 3); + } - return turnip; - } + public override Item GetCropObject() + { + Turnip turnip = new Turnip(); - public override int GetPickedID() - { - return 3254; - } + turnip.ItemID = Utility.Random(3385, 2); - [Constructible] - public FarmableTurnip() : base( GetCropID() ) - { - } + return turnip; + } - public FarmableTurnip( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return 3254; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Farming/FarmableWheat.cs b/Scripts/Items/Farming/FarmableWheat.cs index 78373aeda..7f6250420 100644 --- a/Scripts/Items/Farming/FarmableWheat.cs +++ b/Scripts/Items/Farming/FarmableWheat.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class FarmableWheat : FarmableCrop - { - public static int GetCropID() - { - return Utility.Random( 3157, 4 ); - } + public class FarmableWheat : FarmableCrop + { + [Constructible] + public FarmableWheat() : base(GetCropID()) + { + } - public override Item GetCropObject() - { - return new WheatSheaf(); - } + public FarmableWheat(Serial serial) : base(serial) + { + } - public override int GetPickedID() - { - return Utility.Random( 3502, 2 ); - } + public static int GetCropID() + { + return Utility.Random(3157, 4); + } - [Constructible] - public FarmableWheat() : base( GetCropID() ) - { - } + public override Item GetCropObject() + { + return new WheatSheaf(); + } - public FarmableWheat( Serial serial ) : base( serial ) - { - } + public override int GetPickedID() + { + return Utility.Random(3502, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Food/Asian.cs b/Scripts/Items/Food/Asian.cs index 8b8f3b54e..63704e726 100644 --- a/Scripts/Items/Food/Asian.cs +++ b/Scripts/Items/Food/Asian.cs @@ -1,353 +1,353 @@ namespace Server.Items { - public class Wasabi : Item - { - [Constructible] - public Wasabi() : base( 0x24E8 ) - { - Weight = 1.0; - } - - public Wasabi( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WasabiClumps : Food - { - [Constructible] - public WasabiClumps() : base( 0x24EB ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public WasabiClumps( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EmptyBentoBox : Item - { - [Constructible] - public EmptyBentoBox() : base( 0x2834 ) - { - Weight = 5.0; - } - - public EmptyBentoBox( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BentoBox : Food - { - [Constructible] - public BentoBox() : base( 0x2836 ) - { - Stackable = false; - Weight = 5.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyBentoBox() ); - return true; - } - - public BentoBox( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SushiRolls : Food - { - [Constructible] - public SushiRolls() : base( 0x283E ) - { - Stackable = false; - Weight = 3.0; - FillFactor = 2; - } - - public SushiRolls( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SushiPlatter : Food - { - [Constructible] - public SushiPlatter() : base( 0x2840 ) - { - Stackable = Core.ML; - Weight = 3.0; - FillFactor = 2; - } - - public SushiPlatter( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenTeaBasket : Item - { - [Constructible] - public GreenTeaBasket() : base( 0x284B ) - { - Weight = 10.0; - } - - public GreenTeaBasket( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenTea : Food - { - [Constructible] - public GreenTea() : base( 0x284C ) - { - Stackable = false; - Weight = 4.0; - FillFactor = 2; - } - - public GreenTea( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MisoSoup : Food - { - [Constructible] - public MisoSoup() : base( 0x284D ) - { - Stackable = false; - Weight = 4.0; - FillFactor = 2; - } - - public MisoSoup( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WhiteMisoSoup : Food - { - [Constructible] - public WhiteMisoSoup() : base( 0x284E ) - { - Stackable = false; - Weight = 4.0; - FillFactor = 2; - } - - public WhiteMisoSoup( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RedMisoSoup : Food - { - [Constructible] - public RedMisoSoup() : base( 0x284F ) - { - Stackable = false; - Weight = 4.0; - FillFactor = 2; - } - - public RedMisoSoup( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AwaseMisoSoup : Food - { - [Constructible] - public AwaseMisoSoup() : base( 0x2850 ) - { - Stackable = false; - Weight = 4.0; - FillFactor = 2; - } - - public AwaseMisoSoup( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public class Wasabi : Item + { + [Constructible] + public Wasabi() : base(0x24E8) + { + Weight = 1.0; + } + + public Wasabi(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WasabiClumps : Food + { + [Constructible] + public WasabiClumps() : base(0x24EB) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public WasabiClumps(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EmptyBentoBox : Item + { + [Constructible] + public EmptyBentoBox() : base(0x2834) + { + Weight = 5.0; + } + + public EmptyBentoBox(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BentoBox : Food + { + [Constructible] + public BentoBox() : base(0x2836) + { + Stackable = false; + Weight = 5.0; + FillFactor = 2; + } + + public BentoBox(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyBentoBox()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SushiRolls : Food + { + [Constructible] + public SushiRolls() : base(0x283E) + { + Stackable = false; + Weight = 3.0; + FillFactor = 2; + } + + public SushiRolls(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SushiPlatter : Food + { + [Constructible] + public SushiPlatter() : base(0x2840) + { + Stackable = Core.ML; + Weight = 3.0; + FillFactor = 2; + } + + public SushiPlatter(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenTeaBasket : Item + { + [Constructible] + public GreenTeaBasket() : base(0x284B) + { + Weight = 10.0; + } + + public GreenTeaBasket(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenTea : Food + { + [Constructible] + public GreenTea() : base(0x284C) + { + Stackable = false; + Weight = 4.0; + FillFactor = 2; + } + + public GreenTea(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MisoSoup : Food + { + [Constructible] + public MisoSoup() : base(0x284D) + { + Stackable = false; + Weight = 4.0; + FillFactor = 2; + } + + public MisoSoup(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WhiteMisoSoup : Food + { + [Constructible] + public WhiteMisoSoup() : base(0x284E) + { + Stackable = false; + Weight = 4.0; + FillFactor = 2; + } + + public WhiteMisoSoup(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RedMisoSoup : Food + { + [Constructible] + public RedMisoSoup() : base(0x284F) + { + Stackable = false; + Weight = 4.0; + FillFactor = 2; + } + + public RedMisoSoup(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AwaseMisoSoup : Food + { + [Constructible] + public AwaseMisoSoup() : base(0x2850) + { + Stackable = false; + Weight = 4.0; + FillFactor = 2; + } + + public AwaseMisoSoup(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Food/Beverage.cs b/Scripts/Items/Food/Beverage.cs index 44f8cd9f2..51be7d48c 100644 --- a/Scripts/Items/Food/Beverage.cs +++ b/Scripts/Items/Food/Beverage.cs @@ -5,1183 +5,1188 @@ using Server.Engines.Quests; using Server.Engines.Quests.Hag; using Server.Engines.Quests.Matriarch; using Server.Mobiles; +using Server.Multis; using Server.Network; using Server.Targeting; namespace Server.Items { - public enum BeverageType - { - Ale, - Cider, - Liquor, - Milk, - Wine, - Water - } - - public interface IHasQuantity - { - int Quantity { get; set; } - } - - public interface IWaterSource : IHasQuantity - { - } - - // TODO: Flippable attributes - - [TypeAlias( "Server.Items.BottleAle", "Server.Items.BottleLiquor", "Server.Items.BottleWine" )] - public class BeverageBottle : BaseBeverage - { - public override int BaseLabelNumber => 1042959; // a bottle of Ale - public override int MaxQuantity => 5; - public override bool Fillable => false; - - public override int ComputeItemID() - { - if ( !IsEmpty ) - { - switch( Content ) - { - case BeverageType.Ale: return 0x99F; - case BeverageType.Cider: return 0x99F; - case BeverageType.Liquor: return 0x99B; - case BeverageType.Milk: return 0x99B; - case BeverageType.Wine: return 0x9C7; - case BeverageType.Water: return 0x99B; - } - } - - return 0; - } - - [Constructible] - public BeverageBottle( BeverageType type ) - : base( type ) - { - Weight = 1.0; - } - - public BeverageBottle( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch( version ) - { - case 0: - { - if ( CheckType( "BottleAle" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Ale; - } - else if ( CheckType( "BottleLiquor" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Liquor; - } - else if ( CheckType( "BottleWine" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Wine; - } - else - { - throw new Exception( World.LoadingType ); - } - - break; - } - } - } - } - - public class Jug : BaseBeverage - { - public override int BaseLabelNumber => 1042965; // a jug of Ale - public override int MaxQuantity => 10; - public override bool Fillable => false; - - public override int ComputeItemID() - { - if ( !IsEmpty ) - return 0x9C8; - - return 0; - } - - [Constructible] - public Jug( BeverageType type ) - : base( type ) - { - Weight = 1.0; - } - - public Jug( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CeramicMug : BaseBeverage - { - public override int BaseLabelNumber => 1042982; // a ceramic mug of Ale - public override int MaxQuantity => 1; - - public override int ComputeItemID() - { - if ( ItemID >= 0x995 && ItemID <= 0x999 ) - return ItemID; - if ( ItemID == 0x9CA ) - return ItemID; - - return 0x995; - } - - [Constructible] - public CeramicMug() - { - Weight = 1.0; - } - - [Constructible] - public CeramicMug( BeverageType type ) - : base( type ) - { - Weight = 1.0; - } - - public CeramicMug( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PewterMug : BaseBeverage - { - public override int BaseLabelNumber => 1042994; // a pewter mug with Ale - public override int MaxQuantity => 1; - - public override int ComputeItemID() - { - if ( ItemID >= 0xFFF && ItemID <= 0x1002 ) - return ItemID; - - return 0xFFF; - } - - [Constructible] - public PewterMug() - { - Weight = 1.0; - } - - [Constructible] - public PewterMug( BeverageType type ) - : base( type ) - { - Weight = 1.0; - } - - public PewterMug( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Goblet : BaseBeverage - { - public override int BaseLabelNumber => 1043000; // a goblet of Ale - public override int MaxQuantity => 1; - - public override int ComputeItemID() - { - if ( ItemID == 0x99A || ItemID == 0x9B3 || ItemID == 0x9BF || ItemID == 0x9CB ) - return ItemID; - - return 0x99A; - } - - [Constructible] - public Goblet() - { - Weight = 1.0; - } - - [Constructible] - public Goblet( BeverageType type ) - : base( type ) - { - Weight = 1.0; - } - - public Goblet( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [TypeAlias( "Server.Items.MugAle", "Server.Items.GlassCider", "Server.Items.GlassLiquor", - "Server.Items.GlassMilk", "Server.Items.GlassWine", "Server.Items.GlassWater" )] - public class GlassMug : BaseBeverage - { - public override int EmptyLabelNumber => 1022456; // mug - public override int BaseLabelNumber => 1042976; // a mug of Ale - public override int MaxQuantity => 5; - - public override int ComputeItemID() - { - if ( IsEmpty ) - return ( ItemID >= 0x1F81 && ItemID <= 0x1F84 ? ItemID : 0x1F81 ); - - switch( Content ) - { - case BeverageType.Ale: return ( ItemID == 0x9EF ? 0x9EF : 0x9EE ); - case BeverageType.Cider: return ( ItemID >= 0x1F7D && ItemID <= 0x1F80 ? ItemID : 0x1F7D ); - case BeverageType.Liquor: return ( ItemID >= 0x1F85 && ItemID <= 0x1F88 ? ItemID : 0x1F85 ); - case BeverageType.Milk: return ( ItemID >= 0x1F89 && ItemID <= 0x1F8C ? ItemID : 0x1F89 ); - case BeverageType.Wine: return ( ItemID >= 0x1F8D && ItemID <= 0x1F90 ? ItemID : 0x1F8D ); - case BeverageType.Water: return ( ItemID >= 0x1F91 && ItemID <= 0x1F94 ? ItemID : 0x1F91 ); - } - - return 0; - } - - [Constructible] - public GlassMug() - { - Weight = 1.0; - } - - [Constructible] - public GlassMug( BeverageType type ) - : base( type ) - { - Weight = 1.0; - } - - public GlassMug( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch( version ) - { - case 0: - { - if ( CheckType( "MugAle" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Ale; - } - else if ( CheckType( "GlassCider" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Cider; - } - else if ( CheckType( "GlassLiquor" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Liquor; - } - else if ( CheckType( "GlassMilk" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Milk; - } - else if ( CheckType( "GlassWine" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Wine; - } - else if ( CheckType( "GlassWater" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Water; - } - else - { - throw new Exception( World.LoadingType ); - } - - break; - } - } - } - } - - [TypeAlias( "Server.Items.PitcherAle", "Server.Items.PitcherCider", "Server.Items.PitcherLiquor", - "Server.Items.PitcherMilk", "Server.Items.PitcherWine", "Server.Items.PitcherWater", - "Server.Items.GlassPitcher" )] - public class Pitcher : BaseBeverage - { - public override int BaseLabelNumber => 1048128; // a Pitcher of Ale - public override int MaxQuantity => 5; - - public override int ComputeItemID() - { - if ( IsEmpty ) - { - if ( ItemID == 0x9A7 || ItemID == 0xFF7 ) - return ItemID; - - return 0xFF6; - } - - switch( Content ) - { - case BeverageType.Ale: - { - if ( ItemID == 0x1F96 ) - return ItemID; - - return 0x1F95; - } - case BeverageType.Cider: - { - if ( ItemID == 0x1F98 ) - return ItemID; - - return 0x1F97; - } - case BeverageType.Liquor: - { - if ( ItemID == 0x1F9A ) - return ItemID; - - return 0x1F99; - } - case BeverageType.Milk: - { - if ( ItemID == 0x9AD ) - return ItemID; - - return 0x9F0; - } - case BeverageType.Wine: - { - if ( ItemID == 0x1F9C ) - return ItemID; - - return 0x1F9B; - } - case BeverageType.Water: - { - if ( ItemID == 0xFF8 || ItemID == 0xFF9 || ItemID == 0x1F9E ) - return ItemID; - - return 0x1F9D; - } - } - - return 0; - } - - [Constructible] - public Pitcher() - { - Weight = 2.0; - } - - [Constructible] - public Pitcher( BeverageType type ) - : base( type ) - { - Weight = 2.0; - } - - public Pitcher( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - if ( CheckType( "PitcherWater" ) || CheckType( "GlassPitcher" ) ) - InternalDeserialize( reader, false ); - else - InternalDeserialize( reader, true ); - - int version = reader.ReadInt(); - - switch( version ) - { - case 0: - { - if ( CheckType( "PitcherAle" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Ale; - } - else if ( CheckType( "PitcherCider" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Cider; - } - else if ( CheckType( "PitcherLiquor" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Liquor; - } - else if ( CheckType( "PitcherMilk" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Milk; - } - else if ( CheckType( "PitcherWine" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Wine; - } - else if ( CheckType( "PitcherWater" ) ) - { - Quantity = MaxQuantity; - Content = BeverageType.Water; - } - else if ( CheckType( "GlassPitcher" ) ) - { - Quantity = 0; - Content = BeverageType.Water; - } - else - { - throw new Exception( World.LoadingType ); - } - - break; - } - } - } - } - - public abstract class BaseBeverage : Item, IHasQuantity - { - private BeverageType m_Content; - private int m_Quantity; - - public override int LabelNumber - { - get - { - int num = BaseLabelNumber; - - if ( IsEmpty || num == 0 ) - return EmptyLabelNumber; - - return BaseLabelNumber + (int)m_Content; - } - } - - public virtual bool ShowQuantity => ( MaxQuantity > 1 ); - public virtual bool Fillable => true; - public virtual bool Pourable => true; - - public virtual int EmptyLabelNumber => base.LabelNumber; - public virtual int BaseLabelNumber => 0; - - public abstract int MaxQuantity { get; } - - public abstract int ComputeItemID(); - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsEmpty => ( m_Quantity <= 0 ); - - [CommandProperty( AccessLevel.GameMaster )] - public bool ContainsAlchohol => ( !IsEmpty && m_Content != BeverageType.Milk && m_Content != BeverageType.Water ); - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsFull => ( m_Quantity >= MaxQuantity ); - - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Poisoner { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public BeverageType Content - { - get => m_Content; - set - { - m_Content = value; - - InvalidateProperties(); - - int itemID = ComputeItemID(); - - if ( itemID > 0 ) - ItemID = itemID; - else - Delete(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Quantity - { - get => m_Quantity; - set - { - if ( value < 0 ) - value = 0; - else if ( value > MaxQuantity ) - value = MaxQuantity; - - m_Quantity = value; - - InvalidateProperties(); - - int itemID = ComputeItemID(); - - if ( itemID > 0 ) - ItemID = itemID; - else - Delete(); - } - } - - public virtual int GetQuantityDescription() - { - int perc = ( m_Quantity * 100 ) / MaxQuantity; - - if ( perc <= 0 ) - return 1042975; // It's empty. - if ( perc <= 33 ) - return 1042974; // It's nearly empty. - if ( perc <= 66 ) - return 1042973; // It's half full. - return 1042972; // It's full. - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( ShowQuantity ) - list.Add( GetQuantityDescription() ); - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( ShowQuantity ) - LabelTo( from, GetQuantityDescription() ); - } - - public virtual bool ValidateUse( Mobile from, bool message ) - { - if ( Deleted ) - return false; - - if ( !Movable && !Fillable ) - { - Multis.BaseHouse house = Multis.BaseHouse.FindHouseAt( this ); - - if ( house == null || !house.IsLockedDown( this ) ) - { - if ( message ) - from.SendLocalizedMessage( 502946, "", 0x59 ); // That belongs to someone else. - - return false; - } - } - - if ( from.Map != Map || !from.InRange( GetWorldLocation(), 2 ) || !from.InLOS( this ) ) - { - if ( message ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - - return false; - } - - return true; - } - - public virtual void Fill_OnTarget( Mobile from, object targ ) - { - if ( !IsEmpty || !Fillable || !ValidateUse( from, false ) ) - return; - - if ( targ is BaseBeverage bev ) - { - if ( bev.IsEmpty || !bev.ValidateUse( from, true ) ) - return; - - Content = bev.Content; - Poison = bev.Poison; - Poisoner = bev.Poisoner; - - if ( bev.Quantity > MaxQuantity ) - { - Quantity = MaxQuantity; - bev.Quantity -= MaxQuantity; - } - else - { - Quantity += bev.Quantity; - bev.Quantity = 0; - } - } - else if ( targ is BaseWaterContainer bwc ) - { - if ( Quantity == 0 || ( Content == BeverageType.Water && !IsFull ) ) - { - int iNeed = Math.Min( ( MaxQuantity - Quantity ), bwc.Quantity ); - - if ( iNeed > 0 && !bwc.IsEmpty && !IsFull ) - { - bwc.Quantity -= iNeed; - Quantity += iNeed; - Content = BeverageType.Water; - - from.PlaySound( 0x4E ); - } - } - } - else if ( targ is Item item ) - { - IWaterSource src = ( item as IWaterSource ); - - if ( src == null && item is AddonComponent component ) - src = ( component.Addon as IWaterSource ); - - if ( src == null || src.Quantity <= 0 ) - return; - - if ( from.Map != item.Map || !from.InRange( item.GetWorldLocation(), 2 ) || !from.InLOS( item ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - Content = BeverageType.Water; - Poison = null; - Poisoner = null; - - if ( src.Quantity > MaxQuantity ) - { - Quantity = MaxQuantity; - src.Quantity -= MaxQuantity; - } - else - { - Quantity += src.Quantity; - src.Quantity = 0; - } - - from.SendLocalizedMessage( 1010089 ); // You fill the container with water. - } - else if ( targ is Cow cow ) - { - if ( cow.TryMilk( from ) ) - { - Content = BeverageType.Milk; - Quantity = MaxQuantity; - from.SendLocalizedMessage( 1080197 ); // You fill the container with milk. - } - } - else if ( targ is LandTarget target ) - { - int tileID = target.TileID; - - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; - - if ( qs is WitchApprenticeQuest ) - { - if ( qs.FindObjective( typeof( FindIngredientObjective ) ) is FindIngredientObjective obj && !obj.Completed && obj.Ingredient == Ingredient.SwampWater ) - { - bool contains = false; - - for( int i = 0; !contains && i < m_SwampTiles.Length; i += 2 ) - contains = ( tileID >= m_SwampTiles[ i ] && tileID <= m_SwampTiles[ i + 1 ] ); - - if ( contains ) - { - Delete(); - - player.SendLocalizedMessage( 1055035 ); // You dip the container into the disgusting swamp water, collecting enough for the Hag's vile stew. - obj.Complete(); - } - } - } - } - } - } - - private static int[] m_SwampTiles = { - 0x9C4, 0x9EB, - 0x3D65, 0x3D65, - 0x3DC0, 0x3DD9, - 0x3DDB, 0x3DDC, - 0x3DDE, 0x3EF0, - 0x3FF6, 0x3FF6, - 0x3FFC, 0x3FFE, - }; - - #region Effects of achohol - private static Hashtable m_Table = new Hashtable(); - - public static void Initialize() - { - EventSink.Login += EventSink_Login; - } - - private static void EventSink_Login( LoginEventArgs e ) - { - CheckHeaveTimer( e.Mobile ); - } - - public static void CheckHeaveTimer( Mobile from ) - { - if ( from.BAC > 0 && from.Map != Map.Internal && !from.Deleted ) - { - Timer t = (Timer)m_Table[ from ]; - - if ( t == null ) - { - if ( from.BAC > 60 ) - from.BAC = 60; - - t = new HeaveTimer( from ); - t.Start(); - - m_Table[ from ] = t; - } - } - else - { - Timer t = (Timer)m_Table[ from ]; - - if ( t != null ) - { - t.Stop(); - m_Table.Remove( from ); - - from.SendLocalizedMessage( 500850 ); // You feel sober. - } - } - } - - private class HeaveTimer : Timer - { - private Mobile m_Drunk; - - public HeaveTimer( Mobile drunk ) - : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_Drunk = drunk; - - Priority = TimerPriority.OneSecond; - } - - protected override void OnTick() - { - if ( m_Drunk.Deleted || m_Drunk.Map == Map.Internal ) - { - Stop(); - m_Table.Remove( m_Drunk ); - } - else if ( m_Drunk.Alive ) - { - if ( m_Drunk.BAC > 60 ) - m_Drunk.BAC = 60; - - // chance to get sober - if ( 10 > Utility.Random( 100 ) ) - --m_Drunk.BAC; - - // lose some stats - m_Drunk.Stam -= 1; - m_Drunk.Mana -= 1; - - if ( Utility.Random( 1, 4 ) == 1 ) - { - if ( !m_Drunk.Mounted ) - { - // turn in a random direction - m_Drunk.Direction = (Direction)Utility.Random( 8 ); - - // heave - m_Drunk.Animate( 32, 5, 1, true, false, 0 ); - } - - // *hic* - m_Drunk.PublicOverheadMessage( MessageType.Regular, 0x3B2, 500849 ); - } - - if ( m_Drunk.BAC <= 0 ) - { - Stop(); - m_Table.Remove( m_Drunk ); - - m_Drunk.SendLocalizedMessage( 500850 ); // You feel sober. - } - } - } - } - - #endregion - - public virtual void Pour_OnTarget( Mobile from, object targ ) - { - if ( IsEmpty || !Pourable || !ValidateUse( from, false ) ) - return; - - if ( targ is BaseBeverage bev ) - { - if ( !bev.ValidateUse( from, true ) ) - return; - - if ( bev.IsFull && bev.Content == Content ) - { - from.SendLocalizedMessage( 500848 ); // Couldn't pour it there. It was already full. - } - else if ( !bev.IsEmpty ) - { - from.SendLocalizedMessage( 500846 ); // Can't pour it there. - } - else - { - bev.Content = Content; - bev.Poison = Poison; - bev.Poisoner = Poisoner; - - if ( Quantity > bev.MaxQuantity ) - { - bev.Quantity = bev.MaxQuantity; - Quantity -= bev.MaxQuantity; - } - else - { - bev.Quantity += Quantity; - Quantity = 0; - } - - from.PlaySound( 0x4E ); - } - } - else if ( from == targ ) - { - if ( from.Thirst < 20 ) - from.Thirst += 1; - - if ( ContainsAlchohol ) - { - int bac = 0; - - switch( Content ) - { - case BeverageType.Ale: bac = 1; break; - case BeverageType.Wine: bac = 2; break; - case BeverageType.Cider: bac = 3; break; - case BeverageType.Liquor: bac = 4; break; - } - - from.BAC += bac; - - if ( from.BAC > 60 ) - from.BAC = 60; - - CheckHeaveTimer( from ); - } - - from.PlaySound( Utility.RandomList( 0x30, 0x2D6 ) ); - - if ( Poison != null ) - from.ApplyPoison( Poisoner, Poison ); - - --Quantity; - } - else if ( targ is BaseWaterContainer bwc ) - { - if ( Content != BeverageType.Water ) - { - from.SendLocalizedMessage( 500842 ); // Can't pour that in there. - } - else if ( bwc.Items.Count != 0 ) - { - from.SendLocalizedMessage( 500841 ); // That has something in it. - } - else - { - int itNeeds = Math.Min( ( bwc.MaxQuantity - bwc.Quantity ), Quantity ); - - if ( itNeeds > 0 ) - { - bwc.Quantity += itNeeds; - Quantity -= itNeeds; - - from.PlaySound( 0x4E ); - } - } - } - else if ( targ is PlantItem item ) - { - item.Pour( from, this ); - } - else if ( targ is AddonComponent component && - ( component.Addon is WaterVatEast || component.Addon is WaterVatSouth ) && - Content == BeverageType.Water ) - { - if ( from is PlayerMobile player ) - { - if ( player.Quest is SolenMatriarchQuest qs ) - { - QuestObjective obj = qs.FindObjective( typeof( GatherWaterObjective ) ); - - if ( obj != null && !obj.Completed ) - { - BaseAddon vat = component.Addon; - - if ( vat.X > 5784 && vat.X < 5814 && vat.Y > 1903 && vat.Y < 1934 && - ( ( qs.RedSolen && vat.Map == Map.Trammel ) || ( !qs.RedSolen && vat.Map == Map.Felucca ) ) ) - { - if ( obj.CurProgress + Quantity > obj.MaxProgress ) - { - int delta = obj.MaxProgress - obj.CurProgress; - - Quantity -= delta; - obj.CurProgress = obj.MaxProgress; - } - else - { - obj.CurProgress += Quantity; - Quantity = 0; - } - } - } - } - } - } - else - { - from.SendLocalizedMessage( 500846 ); // Can't pour it there. - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsEmpty ) - { - if ( !Fillable || !ValidateUse( from, true ) ) - return; - - from.BeginTarget( -1, true, TargetFlags.None, Fill_OnTarget ); - SendLocalizedMessageTo( from, 500837 ); // Fill from what? - } - else if ( Pourable && ValidateUse( from, true ) ) - { - from.BeginTarget( -1, true, TargetFlags.None, Pour_OnTarget ); - from.SendLocalizedMessage( 1010086 ); // What do you want to use this on? - } - } - - public static bool ConsumeTotal( Container pack, BeverageType content, int quantity ) - { - return ConsumeTotal( pack, typeof( BaseBeverage ), content, quantity ); - } - - public static bool ConsumeTotal( Container pack, Type itemType, BeverageType content, int quantity ) - { - Item[] items = pack.FindItemsByType( itemType ); - - // First pass, compute total - int total = 0; - - for( int i = 0; i < items.Length; ++i ) - { - if ( items[i] is BaseBeverage bev && bev.Content == content && !bev.IsEmpty ) - total += bev.Quantity; - } - - if ( total >= quantity ) - { - // We've enough, so consume it - - int need = quantity; - - for( int i = 0; i < items.Length; ++i ) - { - if ( !(items[i] is BaseBeverage bev) || bev.Content != content || bev.IsEmpty ) - continue; - - int theirQuantity = bev.Quantity; - - if ( theirQuantity < need ) - { - bev.Quantity = 0; - need -= theirQuantity; - } - else - { - bev.Quantity -= need; - return true; - } - } - } - - return false; - } - - public BaseBeverage() - { - ItemID = ComputeItemID(); - } - - public BaseBeverage( BeverageType type ) - { - m_Content = type; - m_Quantity = MaxQuantity; - ItemID = ComputeItemID(); - } - - public BaseBeverage( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - - writer.Write( (Mobile)Poisoner ); - - Poison.Serialize( Poison, writer ); - writer.Write( (int)m_Content ); - writer.Write( (int)m_Quantity ); - } - - protected bool CheckType( string name ) - { - return ( World.LoadingType == $"Server.Items.{name}"); - } - - public override void Deserialize( GenericReader reader ) - { - InternalDeserialize( reader, true ); - } - - protected void InternalDeserialize( GenericReader reader, bool read ) - { - base.Deserialize( reader ); - - if ( !read ) - return; - - int version = reader.ReadInt(); - - switch( version ) - { - case 1: - { - Poisoner = reader.ReadMobile(); - goto case 0; - } - case 0: - { - Poison = Poison.Deserialize( reader ); - m_Content = (BeverageType)reader.ReadInt(); - m_Quantity = reader.ReadInt(); - break; - } - } - } - } -} + public enum BeverageType + { + Ale, + Cider, + Liquor, + Milk, + Wine, + Water + } + + public interface IHasQuantity + { + int Quantity{ get; set; } + } + + public interface IWaterSource : IHasQuantity + { + } + + // TODO: Flippable attributes + + [TypeAlias("Server.Items.BottleAle", "Server.Items.BottleLiquor", "Server.Items.BottleWine")] + public class BeverageBottle : BaseBeverage + { + [Constructible] + public BeverageBottle(BeverageType type) + : base(type) + { + Weight = 1.0; + } + + public BeverageBottle(Serial serial) + : base(serial) + { + } + + public override int BaseLabelNumber => 1042959; // a bottle of Ale + public override int MaxQuantity => 5; + public override bool Fillable => false; + + public override int ComputeItemID() + { + if (!IsEmpty) + switch (Content) + { + case BeverageType.Ale: return 0x99F; + case BeverageType.Cider: return 0x99F; + case BeverageType.Liquor: return 0x99B; + case BeverageType.Milk: return 0x99B; + case BeverageType.Wine: return 0x9C7; + case BeverageType.Water: return 0x99B; + } + + return 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + if (CheckType("BottleAle")) + { + Quantity = MaxQuantity; + Content = BeverageType.Ale; + } + else if (CheckType("BottleLiquor")) + { + Quantity = MaxQuantity; + Content = BeverageType.Liquor; + } + else if (CheckType("BottleWine")) + { + Quantity = MaxQuantity; + Content = BeverageType.Wine; + } + else + { + throw new Exception(World.LoadingType); + } + + break; + } + } + } + } + + public class Jug : BaseBeverage + { + [Constructible] + public Jug(BeverageType type) + : base(type) + { + Weight = 1.0; + } + + public Jug(Serial serial) + : base(serial) + { + } + + public override int BaseLabelNumber => 1042965; // a jug of Ale + public override int MaxQuantity => 10; + public override bool Fillable => false; + + public override int ComputeItemID() + { + if (!IsEmpty) + return 0x9C8; + + return 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CeramicMug : BaseBeverage + { + [Constructible] + public CeramicMug() + { + Weight = 1.0; + } + + [Constructible] + public CeramicMug(BeverageType type) + : base(type) + { + Weight = 1.0; + } + + public CeramicMug(Serial serial) + : base(serial) + { + } + + public override int BaseLabelNumber => 1042982; // a ceramic mug of Ale + public override int MaxQuantity => 1; + + public override int ComputeItemID() + { + if (ItemID >= 0x995 && ItemID <= 0x999) + return ItemID; + if (ItemID == 0x9CA) + return ItemID; + + return 0x995; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PewterMug : BaseBeverage + { + [Constructible] + public PewterMug() + { + Weight = 1.0; + } + + [Constructible] + public PewterMug(BeverageType type) + : base(type) + { + Weight = 1.0; + } + + public PewterMug(Serial serial) + : base(serial) + { + } + + public override int BaseLabelNumber => 1042994; // a pewter mug with Ale + public override int MaxQuantity => 1; + + public override int ComputeItemID() + { + if (ItemID >= 0xFFF && ItemID <= 0x1002) + return ItemID; + + return 0xFFF; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Goblet : BaseBeverage + { + [Constructible] + public Goblet() + { + Weight = 1.0; + } + + [Constructible] + public Goblet(BeverageType type) + : base(type) + { + Weight = 1.0; + } + + public Goblet(Serial serial) + : base(serial) + { + } + + public override int BaseLabelNumber => 1043000; // a goblet of Ale + public override int MaxQuantity => 1; + + public override int ComputeItemID() + { + if (ItemID == 0x99A || ItemID == 0x9B3 || ItemID == 0x9BF || ItemID == 0x9CB) + return ItemID; + + return 0x99A; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [TypeAlias("Server.Items.MugAle", "Server.Items.GlassCider", "Server.Items.GlassLiquor", + "Server.Items.GlassMilk", "Server.Items.GlassWine", "Server.Items.GlassWater")] + public class GlassMug : BaseBeverage + { + [Constructible] + public GlassMug() + { + Weight = 1.0; + } + + [Constructible] + public GlassMug(BeverageType type) + : base(type) + { + Weight = 1.0; + } + + public GlassMug(Serial serial) + : base(serial) + { + } + + public override int EmptyLabelNumber => 1022456; // mug + public override int BaseLabelNumber => 1042976; // a mug of Ale + public override int MaxQuantity => 5; + + public override int ComputeItemID() + { + if (IsEmpty) + return ItemID >= 0x1F81 && ItemID <= 0x1F84 ? ItemID : 0x1F81; + + switch (Content) + { + case BeverageType.Ale: return ItemID == 0x9EF ? 0x9EF : 0x9EE; + case BeverageType.Cider: return ItemID >= 0x1F7D && ItemID <= 0x1F80 ? ItemID : 0x1F7D; + case BeverageType.Liquor: return ItemID >= 0x1F85 && ItemID <= 0x1F88 ? ItemID : 0x1F85; + case BeverageType.Milk: return ItemID >= 0x1F89 && ItemID <= 0x1F8C ? ItemID : 0x1F89; + case BeverageType.Wine: return ItemID >= 0x1F8D && ItemID <= 0x1F90 ? ItemID : 0x1F8D; + case BeverageType.Water: return ItemID >= 0x1F91 && ItemID <= 0x1F94 ? ItemID : 0x1F91; + } + + return 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + if (CheckType("MugAle")) + { + Quantity = MaxQuantity; + Content = BeverageType.Ale; + } + else if (CheckType("GlassCider")) + { + Quantity = MaxQuantity; + Content = BeverageType.Cider; + } + else if (CheckType("GlassLiquor")) + { + Quantity = MaxQuantity; + Content = BeverageType.Liquor; + } + else if (CheckType("GlassMilk")) + { + Quantity = MaxQuantity; + Content = BeverageType.Milk; + } + else if (CheckType("GlassWine")) + { + Quantity = MaxQuantity; + Content = BeverageType.Wine; + } + else if (CheckType("GlassWater")) + { + Quantity = MaxQuantity; + Content = BeverageType.Water; + } + else + { + throw new Exception(World.LoadingType); + } + + break; + } + } + } + } + + [TypeAlias("Server.Items.PitcherAle", "Server.Items.PitcherCider", "Server.Items.PitcherLiquor", + "Server.Items.PitcherMilk", "Server.Items.PitcherWine", "Server.Items.PitcherWater", + "Server.Items.GlassPitcher")] + public class Pitcher : BaseBeverage + { + [Constructible] + public Pitcher() + { + Weight = 2.0; + } + + [Constructible] + public Pitcher(BeverageType type) + : base(type) + { + Weight = 2.0; + } + + public Pitcher(Serial serial) + : base(serial) + { + } + + public override int BaseLabelNumber => 1048128; // a Pitcher of Ale + public override int MaxQuantity => 5; + + public override int ComputeItemID() + { + if (IsEmpty) + { + if (ItemID == 0x9A7 || ItemID == 0xFF7) + return ItemID; + + return 0xFF6; + } + + switch (Content) + { + case BeverageType.Ale: + { + if (ItemID == 0x1F96) + return ItemID; + + return 0x1F95; + } + case BeverageType.Cider: + { + if (ItemID == 0x1F98) + return ItemID; + + return 0x1F97; + } + case BeverageType.Liquor: + { + if (ItemID == 0x1F9A) + return ItemID; + + return 0x1F99; + } + case BeverageType.Milk: + { + if (ItemID == 0x9AD) + return ItemID; + + return 0x9F0; + } + case BeverageType.Wine: + { + if (ItemID == 0x1F9C) + return ItemID; + + return 0x1F9B; + } + case BeverageType.Water: + { + if (ItemID == 0xFF8 || ItemID == 0xFF9 || ItemID == 0x1F9E) + return ItemID; + + return 0x1F9D; + } + } + + return 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + if (CheckType("PitcherWater") || CheckType("GlassPitcher")) + InternalDeserialize(reader, false); + else + InternalDeserialize(reader, true); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + if (CheckType("PitcherAle")) + { + Quantity = MaxQuantity; + Content = BeverageType.Ale; + } + else if (CheckType("PitcherCider")) + { + Quantity = MaxQuantity; + Content = BeverageType.Cider; + } + else if (CheckType("PitcherLiquor")) + { + Quantity = MaxQuantity; + Content = BeverageType.Liquor; + } + else if (CheckType("PitcherMilk")) + { + Quantity = MaxQuantity; + Content = BeverageType.Milk; + } + else if (CheckType("PitcherWine")) + { + Quantity = MaxQuantity; + Content = BeverageType.Wine; + } + else if (CheckType("PitcherWater")) + { + Quantity = MaxQuantity; + Content = BeverageType.Water; + } + else if (CheckType("GlassPitcher")) + { + Quantity = 0; + Content = BeverageType.Water; + } + else + { + throw new Exception(World.LoadingType); + } + + break; + } + } + } + } + + public abstract class BaseBeverage : Item, IHasQuantity + { + private static int[] m_SwampTiles = + { + 0x9C4, 0x9EB, + 0x3D65, 0x3D65, + 0x3DC0, 0x3DD9, + 0x3DDB, 0x3DDC, + 0x3DDE, 0x3EF0, + 0x3FF6, 0x3FF6, + 0x3FFC, 0x3FFE + }; + + private BeverageType m_Content; + private int m_Quantity; + + public BaseBeverage() + { + ItemID = ComputeItemID(); + } + + public BaseBeverage(BeverageType type) + { + m_Content = type; + m_Quantity = MaxQuantity; + ItemID = ComputeItemID(); + } + + public BaseBeverage(Serial serial) + : base(serial) + { + } + + public override int LabelNumber + { + get + { + int num = BaseLabelNumber; + + if (IsEmpty || num == 0) + return EmptyLabelNumber; + + return BaseLabelNumber + (int)m_Content; + } + } + + public virtual bool ShowQuantity => MaxQuantity > 1; + public virtual bool Fillable => true; + public virtual bool Pourable => true; + + public virtual int EmptyLabelNumber => base.LabelNumber; + public virtual int BaseLabelNumber => 0; + + public abstract int MaxQuantity{ get; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsEmpty => m_Quantity <= 0; + + [CommandProperty(AccessLevel.GameMaster)] + public bool ContainsAlchohol => !IsEmpty && m_Content != BeverageType.Milk && m_Content != BeverageType.Water; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsFull => m_Quantity >= MaxQuantity; + + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Poisoner{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public BeverageType Content + { + get => m_Content; + set + { + m_Content = value; + + InvalidateProperties(); + + int itemID = ComputeItemID(); + + if (itemID > 0) + ItemID = itemID; + else + Delete(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Quantity + { + get => m_Quantity; + set + { + if (value < 0) + value = 0; + else if (value > MaxQuantity) + value = MaxQuantity; + + m_Quantity = value; + + InvalidateProperties(); + + int itemID = ComputeItemID(); + + if (itemID > 0) + ItemID = itemID; + else + Delete(); + } + } + + public abstract int ComputeItemID(); + + public virtual int GetQuantityDescription() + { + int perc = m_Quantity * 100 / MaxQuantity; + + if (perc <= 0) + return 1042975; // It's empty. + if (perc <= 33) + return 1042974; // It's nearly empty. + if (perc <= 66) + return 1042973; // It's half full. + return 1042972; // It's full. + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (ShowQuantity) + list.Add(GetQuantityDescription()); + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (ShowQuantity) + LabelTo(from, GetQuantityDescription()); + } + + public virtual bool ValidateUse(Mobile from, bool message) + { + if (Deleted) + return false; + + if (!Movable && !Fillable) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house == null || !house.IsLockedDown(this)) + { + if (message) + from.SendLocalizedMessage(502946, "", 0x59); // That belongs to someone else. + + return false; + } + } + + if (from.Map != Map || !from.InRange(GetWorldLocation(), 2) || !from.InLOS(this)) + { + if (message) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + + return false; + } + + return true; + } + + public virtual void Fill_OnTarget(Mobile from, object targ) + { + if (!IsEmpty || !Fillable || !ValidateUse(from, false)) + return; + + if (targ is BaseBeverage bev) + { + if (bev.IsEmpty || !bev.ValidateUse(from, true)) + return; + + Content = bev.Content; + Poison = bev.Poison; + Poisoner = bev.Poisoner; + + if (bev.Quantity > MaxQuantity) + { + Quantity = MaxQuantity; + bev.Quantity -= MaxQuantity; + } + else + { + Quantity += bev.Quantity; + bev.Quantity = 0; + } + } + else if (targ is BaseWaterContainer bwc) + { + if (Quantity == 0 || Content == BeverageType.Water && !IsFull) + { + int iNeed = Math.Min(MaxQuantity - Quantity, bwc.Quantity); + + if (iNeed > 0 && !bwc.IsEmpty && !IsFull) + { + bwc.Quantity -= iNeed; + Quantity += iNeed; + Content = BeverageType.Water; + + from.PlaySound(0x4E); + } + } + } + else if (targ is Item item) + { + IWaterSource src = item as IWaterSource; + + if (src == null && item is AddonComponent component) + src = component.Addon as IWaterSource; + + if (src == null || src.Quantity <= 0) + return; + + if (from.Map != item.Map || !from.InRange(item.GetWorldLocation(), 2) || !from.InLOS(item)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + Content = BeverageType.Water; + Poison = null; + Poisoner = null; + + if (src.Quantity > MaxQuantity) + { + Quantity = MaxQuantity; + src.Quantity -= MaxQuantity; + } + else + { + Quantity += src.Quantity; + src.Quantity = 0; + } + + from.SendLocalizedMessage(1010089); // You fill the container with water. + } + else if (targ is Cow cow) + { + if (cow.TryMilk(from)) + { + Content = BeverageType.Milk; + Quantity = MaxQuantity; + from.SendLocalizedMessage(1080197); // You fill the container with milk. + } + } + else if (targ is LandTarget target) + { + int tileID = target.TileID; + + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; + + if (qs is WitchApprenticeQuest) + if (qs.FindObjective(typeof(FindIngredientObjective)) is FindIngredientObjective obj && + !obj.Completed && obj.Ingredient == Ingredient.SwampWater) + { + bool contains = false; + + for (int i = 0; !contains && i < m_SwampTiles.Length; i += 2) + contains = tileID >= m_SwampTiles[i] && tileID <= m_SwampTiles[i + 1]; + + if (contains) + { + Delete(); + + player.SendLocalizedMessage( + 1055035); // You dip the container into the disgusting swamp water, collecting enough for the Hag's vile stew. + obj.Complete(); + } + } + } + } + } + + public virtual void Pour_OnTarget(Mobile from, object targ) + { + if (IsEmpty || !Pourable || !ValidateUse(from, false)) + return; + + if (targ is BaseBeverage bev) + { + if (!bev.ValidateUse(from, true)) + return; + + if (bev.IsFull && bev.Content == Content) + { + from.SendLocalizedMessage(500848); // Couldn't pour it there. It was already full. + } + else if (!bev.IsEmpty) + { + from.SendLocalizedMessage(500846); // Can't pour it there. + } + else + { + bev.Content = Content; + bev.Poison = Poison; + bev.Poisoner = Poisoner; + + if (Quantity > bev.MaxQuantity) + { + bev.Quantity = bev.MaxQuantity; + Quantity -= bev.MaxQuantity; + } + else + { + bev.Quantity += Quantity; + Quantity = 0; + } + + from.PlaySound(0x4E); + } + } + else if (from == targ) + { + if (from.Thirst < 20) + from.Thirst += 1; + + if (ContainsAlchohol) + { + int bac = 0; + + switch (Content) + { + case BeverageType.Ale: + bac = 1; + break; + case BeverageType.Wine: + bac = 2; + break; + case BeverageType.Cider: + bac = 3; + break; + case BeverageType.Liquor: + bac = 4; + break; + } + + from.BAC += bac; + + if (from.BAC > 60) + from.BAC = 60; + + CheckHeaveTimer(from); + } + + from.PlaySound(Utility.RandomList(0x30, 0x2D6)); + + if (Poison != null) + from.ApplyPoison(Poisoner, Poison); + + --Quantity; + } + else if (targ is BaseWaterContainer bwc) + { + if (Content != BeverageType.Water) + { + from.SendLocalizedMessage(500842); // Can't pour that in there. + } + else if (bwc.Items.Count != 0) + { + from.SendLocalizedMessage(500841); // That has something in it. + } + else + { + int itNeeds = Math.Min(bwc.MaxQuantity - bwc.Quantity, Quantity); + + if (itNeeds > 0) + { + bwc.Quantity += itNeeds; + Quantity -= itNeeds; + + from.PlaySound(0x4E); + } + } + } + else if (targ is PlantItem item) + { + item.Pour(from, this); + } + else if (targ is AddonComponent component && + (component.Addon is WaterVatEast || component.Addon is WaterVatSouth) && + Content == BeverageType.Water) + { + if (from is PlayerMobile player) + if (player.Quest is SolenMatriarchQuest qs) + { + QuestObjective obj = qs.FindObjective(typeof(GatherWaterObjective)); + + if (obj != null && !obj.Completed) + { + BaseAddon vat = component.Addon; + + if (vat.X > 5784 && vat.X < 5814 && vat.Y > 1903 && vat.Y < 1934 && + (qs.RedSolen && vat.Map == Map.Trammel || !qs.RedSolen && vat.Map == Map.Felucca)) + { + if (obj.CurProgress + Quantity > obj.MaxProgress) + { + int delta = obj.MaxProgress - obj.CurProgress; + + Quantity -= delta; + obj.CurProgress = obj.MaxProgress; + } + else + { + obj.CurProgress += Quantity; + Quantity = 0; + } + } + } + } + } + else + { + from.SendLocalizedMessage(500846); // Can't pour it there. + } + } + + public override void OnDoubleClick(Mobile from) + { + if (IsEmpty) + { + if (!Fillable || !ValidateUse(from, true)) + return; + + from.BeginTarget(-1, true, TargetFlags.None, Fill_OnTarget); + SendLocalizedMessageTo(from, 500837); // Fill from what? + } + else if (Pourable && ValidateUse(from, true)) + { + from.BeginTarget(-1, true, TargetFlags.None, Pour_OnTarget); + from.SendLocalizedMessage(1010086); // What do you want to use this on? + } + } + + public static bool ConsumeTotal(Container pack, BeverageType content, int quantity) + { + return ConsumeTotal(pack, typeof(BaseBeverage), content, quantity); + } + + public static bool ConsumeTotal(Container pack, Type itemType, BeverageType content, int quantity) + { + Item[] items = pack.FindItemsByType(itemType); + + // First pass, compute total + int total = 0; + + for (int i = 0; i < items.Length; ++i) + if (items[i] is BaseBeverage bev && bev.Content == content && !bev.IsEmpty) + total += bev.Quantity; + + if (total >= quantity) + { + // We've enough, so consume it + + int need = quantity; + + for (int i = 0; i < items.Length; ++i) + { + if (!(items[i] is BaseBeverage bev) || bev.Content != content || bev.IsEmpty) + continue; + + int theirQuantity = bev.Quantity; + + if (theirQuantity < need) + { + bev.Quantity = 0; + need -= theirQuantity; + } + else + { + bev.Quantity -= need; + return true; + } + } + } + + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(Poisoner); + + Poison.Serialize(Poison, writer); + writer.Write((int)m_Content); + writer.Write(m_Quantity); + } + + protected bool CheckType(string name) + { + return World.LoadingType == $"Server.Items.{name}"; + } + + public override void Deserialize(GenericReader reader) + { + InternalDeserialize(reader, true); + } + + protected void InternalDeserialize(GenericReader reader, bool read) + { + base.Deserialize(reader); + + if (!read) + return; + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + Poisoner = reader.ReadMobile(); + goto case 0; + } + case 0: + { + Poison = Poison.Deserialize(reader); + m_Content = (BeverageType)reader.ReadInt(); + m_Quantity = reader.ReadInt(); + break; + } + } + } + + #region Effects of achohol + + private static Hashtable m_Table = new Hashtable(); + + public static void Initialize() + { + EventSink.Login += EventSink_Login; + } + + private static void EventSink_Login(LoginEventArgs e) + { + CheckHeaveTimer(e.Mobile); + } + + public static void CheckHeaveTimer(Mobile from) + { + if (from.BAC > 0 && from.Map != Map.Internal && !from.Deleted) + { + Timer t = (Timer)m_Table[from]; + + if (t == null) + { + if (from.BAC > 60) + from.BAC = 60; + + t = new HeaveTimer(from); + t.Start(); + + m_Table[from] = t; + } + } + else + { + Timer t = (Timer)m_Table[from]; + + if (t != null) + { + t.Stop(); + m_Table.Remove(from); + + from.SendLocalizedMessage(500850); // You feel sober. + } + } + } + + private class HeaveTimer : Timer + { + private Mobile m_Drunk; + + public HeaveTimer(Mobile drunk) + : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + m_Drunk = drunk; + + Priority = TimerPriority.OneSecond; + } + + protected override void OnTick() + { + if (m_Drunk.Deleted || m_Drunk.Map == Map.Internal) + { + Stop(); + m_Table.Remove(m_Drunk); + } + else if (m_Drunk.Alive) + { + if (m_Drunk.BAC > 60) + m_Drunk.BAC = 60; + + // chance to get sober + if (10 > Utility.Random(100)) + --m_Drunk.BAC; + + // lose some stats + m_Drunk.Stam -= 1; + m_Drunk.Mana -= 1; + + if (Utility.Random(1, 4) == 1) + { + if (!m_Drunk.Mounted) + { + // turn in a random direction + m_Drunk.Direction = (Direction)Utility.Random(8); + + // heave + m_Drunk.Animate(32, 5, 1, true, false, 0); + } + + // *hic* + m_Drunk.PublicOverheadMessage(MessageType.Regular, 0x3B2, 500849); + } + + if (m_Drunk.BAC <= 0) + { + Stop(); + m_Table.Remove(m_Drunk); + + m_Drunk.SendLocalizedMessage(500850); // You feel sober. + } + } + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Food/BeverageEmpty.cs b/Scripts/Items/Food/BeverageEmpty.cs index a14bf4b8d..d768e5594 100644 --- a/Scripts/Items/Food/BeverageEmpty.cs +++ b/Scripts/Items/Food/BeverageEmpty.cs @@ -1,57 +1,57 @@ namespace Server.Items { - [FlippableAttribute( 0x1f81, 0x1f82, 0x1f83, 0x1f84 )] - public class Glass : Item - { - [Constructible] - public Glass() : base( 0x1f81 ) - { - Weight = 0.1; - } + [Flippable(0x1f81, 0x1f82, 0x1f83, 0x1f84)] + public class Glass : Item + { + [Constructible] + public Glass() : base(0x1f81) + { + Weight = 0.1; + } - public Glass( Serial serial ) : base( serial ) - { - } + public Glass(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GlassBottle : Item - { - [Constructible] - public GlassBottle() : base( 0xe2b ) - { - Weight = 0.3; - } + public class GlassBottle : Item + { + [Constructible] + public GlassBottle() : base(0xe2b) + { + Weight = 0.3; + } - public GlassBottle( Serial serial ) : base( serial ) - { - } + public GlassBottle(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Food/Bowls.cs b/Scripts/Items/Food/Bowls.cs index 1f33f1aaa..c47d0c5c9 100644 --- a/Scripts/Items/Food/Bowls.cs +++ b/Scripts/Items/Food/Bowls.cs @@ -1,530 +1,530 @@ namespace Server.Items { - public class EmptyWoodenBowl : Item - { - [Constructible] - public EmptyWoodenBowl() : base( 0x15F8 ) - { - Weight = 1.0; - } - - public EmptyWoodenBowl( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EmptyPewterBowl : Item - { - [Constructible] - public EmptyPewterBowl() : base( 0x15FD ) - { - Weight = 1.0; - } - - public EmptyPewterBowl( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodenBowlOfCarrots : Food - { - [Constructible] - public WoodenBowlOfCarrots() : base( 0x15F9 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyWoodenBowl() ); - return true; - } - - public WoodenBowlOfCarrots( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodenBowlOfCorn : Food - { - [Constructible] - public WoodenBowlOfCorn() : base( 0x15FA ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyWoodenBowl() ); - return true; - } - - public WoodenBowlOfCorn( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodenBowlOfLettuce : Food - { - [Constructible] - public WoodenBowlOfLettuce() : base( 0x15FB ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyWoodenBowl() ); - return true; - } - - public WoodenBowlOfLettuce( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodenBowlOfPeas : Food - { - [Constructible] - public WoodenBowlOfPeas() : base( 0x15FC ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyWoodenBowl() ); - return true; - } - - public WoodenBowlOfPeas( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PewterBowlOfCarrots : Food - { - [Constructible] - public PewterBowlOfCarrots() : base( 0x15FE ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyPewterBowl() ); - return true; - } - - public PewterBowlOfCarrots( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PewterBowlOfCorn : Food - { - [Constructible] - public PewterBowlOfCorn() : base( 0x15FF ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyPewterBowl() ); - return true; - } - - public PewterBowlOfCorn( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PewterBowlOfLettuce : Food - { - [Constructible] - public PewterBowlOfLettuce() : base( 0x1600 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyPewterBowl() ); - return true; - } - - public PewterBowlOfLettuce( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PewterBowlOfPeas : Food - { - [Constructible] - public PewterBowlOfPeas() : base( 0x1601 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyPewterBowl() ); - return true; - } - - public PewterBowlOfPeas( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PewterBowlOfPotatos : Food - { - [Constructible] - public PewterBowlOfPotatos() : base( 0x1602 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyPewterBowl() ); - return true; - } - - public PewterBowlOfPotatos( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [TypeAlias( "Server.Items.EmptyLargeWoodenBowl" )] - public class EmptyWoodenTub : Item - { - [Constructible] - public EmptyWoodenTub() : base( 0x1605 ) - { - Weight = 2.0; - } - - public EmptyWoodenTub( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [TypeAlias( "Server.Items.EmptyLargePewterBowl" )] - public class EmptyPewterTub : Item - { - [Constructible] - public EmptyPewterTub() : base( 0x1603 ) - { - Weight = 2.0; - } - - public EmptyPewterTub( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodenBowlOfStew : Food - { - [Constructible] - public WoodenBowlOfStew() : base( 0x1604 ) - { - Stackable = false; - Weight = 2.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyWoodenTub() ); - return true; - } - - public WoodenBowlOfStew( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodenBowlOfTomatoSoup : Food - { - [Constructible] - public WoodenBowlOfTomatoSoup() : base( 0x1606 ) - { - Stackable = false; - Weight = 2.0; - FillFactor = 2; - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new EmptyWoodenTub() ); - return true; - } - - public WoodenBowlOfTomatoSoup( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public class EmptyWoodenBowl : Item + { + [Constructible] + public EmptyWoodenBowl() : base(0x15F8) + { + Weight = 1.0; + } + + public EmptyWoodenBowl(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EmptyPewterBowl : Item + { + [Constructible] + public EmptyPewterBowl() : base(0x15FD) + { + Weight = 1.0; + } + + public EmptyPewterBowl(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodenBowlOfCarrots : Food + { + [Constructible] + public WoodenBowlOfCarrots() : base(0x15F9) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public WoodenBowlOfCarrots(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyWoodenBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodenBowlOfCorn : Food + { + [Constructible] + public WoodenBowlOfCorn() : base(0x15FA) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public WoodenBowlOfCorn(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyWoodenBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodenBowlOfLettuce : Food + { + [Constructible] + public WoodenBowlOfLettuce() : base(0x15FB) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public WoodenBowlOfLettuce(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyWoodenBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodenBowlOfPeas : Food + { + [Constructible] + public WoodenBowlOfPeas() : base(0x15FC) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public WoodenBowlOfPeas(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyWoodenBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PewterBowlOfCarrots : Food + { + [Constructible] + public PewterBowlOfCarrots() : base(0x15FE) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public PewterBowlOfCarrots(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyPewterBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PewterBowlOfCorn : Food + { + [Constructible] + public PewterBowlOfCorn() : base(0x15FF) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public PewterBowlOfCorn(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyPewterBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PewterBowlOfLettuce : Food + { + [Constructible] + public PewterBowlOfLettuce() : base(0x1600) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public PewterBowlOfLettuce(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyPewterBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PewterBowlOfPeas : Food + { + [Constructible] + public PewterBowlOfPeas() : base(0x1601) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public PewterBowlOfPeas(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyPewterBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PewterBowlOfPotatos : Food + { + [Constructible] + public PewterBowlOfPotatos() : base(0x1602) + { + Stackable = false; + Weight = 1.0; + FillFactor = 2; + } + + public PewterBowlOfPotatos(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyPewterBowl()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [TypeAlias("Server.Items.EmptyLargeWoodenBowl")] + public class EmptyWoodenTub : Item + { + [Constructible] + public EmptyWoodenTub() : base(0x1605) + { + Weight = 2.0; + } + + public EmptyWoodenTub(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [TypeAlias("Server.Items.EmptyLargePewterBowl")] + public class EmptyPewterTub : Item + { + [Constructible] + public EmptyPewterTub() : base(0x1603) + { + Weight = 2.0; + } + + public EmptyPewterTub(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodenBowlOfStew : Food + { + [Constructible] + public WoodenBowlOfStew() : base(0x1604) + { + Stackable = false; + Weight = 2.0; + FillFactor = 2; + } + + public WoodenBowlOfStew(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyWoodenTub()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodenBowlOfTomatoSoup : Food + { + [Constructible] + public WoodenBowlOfTomatoSoup() : base(0x1606) + { + Stackable = false; + Weight = 2.0; + FillFactor = 2; + } + + public WoodenBowlOfTomatoSoup(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new EmptyWoodenTub()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Food/Chocolatiering.cs b/Scripts/Items/Food/Chocolatiering.cs index 110e3fca8..5558bc13d 100644 --- a/Scripts/Items/Food/Chocolatiering.cs +++ b/Scripts/Items/Food/Chocolatiering.cs @@ -1,285 +1,285 @@ namespace Server.Items { - public class CocoaLiquor : Item - { - public override int LabelNumber => 1080007; // Cocoa liquor - public override double DefaultWeight => 1.0; + public class CocoaLiquor : Item + { + [Constructible] + public CocoaLiquor() + : base(0x103F) + { + Hue = 0x46A; + } - [Constructible] - public CocoaLiquor() - : base( 0x103F ) - { - Hue = 0x46A; - } + public CocoaLiquor(Serial serial) + : base(serial) + { + } - public CocoaLiquor( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1080007; // Cocoa liquor + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SackOfSugar : Item - { - public override int LabelNumber => 1080003; // Sack of sugar - public override double DefaultWeight => 1.0; + public class SackOfSugar : Item + { + [Constructible] + public SackOfSugar() + : this(1) + { + } - [Constructible] - public SackOfSugar() - : this( 1 ) - { - } + [Constructible] + public SackOfSugar(int amount) + : base(0x1039) + { + Hue = 0x461; + Stackable = true; + Amount = amount; + } - [Constructible] - public SackOfSugar( int amount ) - : base( 0x1039 ) - { - Hue = 0x461; - Stackable = true; - Amount = amount; - } + public SackOfSugar(Serial serial) + : base(serial) + { + } - public SackOfSugar( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1080003; // Sack of sugar + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class CocoaButter : Item - { - public override int LabelNumber => 1080005; // Cocoa butter - public override double DefaultWeight => 1.0; + public class CocoaButter : Item + { + [Constructible] + public CocoaButter() + : base(0x1044) + { + Hue = 0x457; + } - [Constructible] - public CocoaButter() - : base( 0x1044 ) - { - Hue = 0x457; - } + public CocoaButter(Serial serial) + : base(serial) + { + } - public CocoaButter( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1080005; // Cocoa butter + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Vanilla : Item - { - public override int LabelNumber => 1080009; // Vanilla - public override double DefaultWeight => 1.0; + public class Vanilla : Item + { + [Constructible] + public Vanilla() + : this(1) + { + } - [Constructible] - public Vanilla() - : this( 1 ) - { - } + [Constructible] + public Vanilla(int amount) + : base(0xE2A) + { + Hue = 0x462; + Stackable = true; + Amount = amount; + } - [Constructible] - public Vanilla( int amount ) - : base( 0xE2A ) - { - Hue = 0x462; - Stackable = true; - Amount = amount; - } + public Vanilla(Serial serial) + : base(serial) + { + } - public Vanilla( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1080009; // Vanilla + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class CocoaPulp : Item - { - public override int LabelNumber => 1080530; // cocoa pulp - public override double DefaultWeight => 1.0; + public class CocoaPulp : Item + { + [Constructible] + public CocoaPulp() + : this(1) + { + } - [Constructible] - public CocoaPulp() - : this( 1 ) - { - } + [Constructible] + public CocoaPulp(int amount) + : base(0xF7C) + { + Hue = 0x219; + Stackable = true; + Amount = amount; + } - [Constructible] - public CocoaPulp( int amount ) - : base( 0xF7C ) - { - Hue = 0x219; - Stackable = true; - Amount = amount; - } + public CocoaPulp(Serial serial) + : base(serial) + { + } - public CocoaPulp( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1080530; // cocoa pulp + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DarkChocolate : CandyCane - { - public override int LabelNumber => 1079994; // Dark chocolate - public override double DefaultWeight => 1.0; + public class DarkChocolate : CandyCane + { + [Constructible] + public DarkChocolate() + : base(0xF10) + { + Hue = 0x465; + LootType = LootType.Regular; + } - [Constructible] - public DarkChocolate() - : base( 0xF10 ) - { - Hue = 0x465; - LootType = LootType.Regular; - } + public DarkChocolate(Serial serial) + : base(serial) + { + } - public DarkChocolate( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1079994; // Dark chocolate + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class MilkChocolate : CandyCane - { - public override int LabelNumber => 1079995; // Milk chocolate - public override double DefaultWeight => 1.0; + public class MilkChocolate : CandyCane + { + [Constructible] + public MilkChocolate() + : base(0xF18) + { + Hue = 0x461; + LootType = LootType.Regular; + } - [Constructible] - public MilkChocolate() - : base( 0xF18 ) - { - Hue = 0x461; - LootType = LootType.Regular; - } + public MilkChocolate(Serial serial) + : base(serial) + { + } - public MilkChocolate( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1079995; // Milk chocolate + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class WhiteChocolate : CandyCane - { - public override int LabelNumber => 1079996; // White chocolate - public override double DefaultWeight => 1.0; + public class WhiteChocolate : CandyCane + { + [Constructible] + public WhiteChocolate() + : base(0xF11) + { + Hue = 0x47E; + LootType = LootType.Regular; + } - [Constructible] - public WhiteChocolate() - : base( 0xF11 ) - { - Hue = 0x47E; - LootType = LootType.Regular; - } + public WhiteChocolate(Serial serial) + : base(serial) + { + } - public WhiteChocolate( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1079996; // White chocolate + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Food/CookableFood.cs b/Scripts/Items/Food/CookableFood.cs index 8abaa2357..1f2127913 100644 --- a/Scripts/Items/Food/CookableFood.cs +++ b/Scripts/Items/Food/CookableFood.cs @@ -3,48 +3,47 @@ using Server.Targeting; namespace Server.Items { - public abstract class CookableFood : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public int CookingLevel { get; set; } + public abstract class CookableFood : Item + { + [CommandProperty(AccessLevel.GameMaster)] + public int CookingLevel{ get; set; } - public CookableFood( int itemID, int cookingLevel ) : base( itemID ) - { - CookingLevel = cookingLevel; - } + public CookableFood(int itemID, int cookingLevel) : base(itemID) + { + CookingLevel = cookingLevel; + } - public CookableFood( Serial serial ) : base( serial ) - { - } + public CookableFood(Serial serial) : base(serial) + { + } - public abstract Food Cook(); + public abstract Food Cook(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - // Version 1 - writer.Write( (int) CookingLevel ); + writer.Write(1); // version + // Version 1 + writer.Write(CookingLevel); + } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + switch (version) + { + case 1: + { + CookingLevel = reader.ReadInt(); - switch ( version ) - { - case 1: - { - CookingLevel = reader.ReadInt(); - - break; - } - } - } + break; + } + } + } #if false public override void OnDoubleClick( Mobile from ) @@ -56,519 +55,521 @@ namespace Server.Items } #endif - public static bool IsHeatSource( object targeted ) - { - int itemID; - - if ( targeted is Item item ) - itemID = item.ItemID; - else if ( targeted is StaticTarget target ) - itemID = target.ItemID; - else - return false; - - if ( itemID >= 0xDE3 && itemID <= 0xDE9 ) - return true; // Campfire - if ( itemID >= 0x461 && itemID <= 0x48E ) - return true; // Sandstone oven/fireplace - if ( itemID >= 0x92B && itemID <= 0x96C ) - return true; // Stone oven/fireplace - if ( itemID == 0xFAC ) - return true; // Firepit - if ( itemID >= 0x184A && itemID <= 0x184C ) - return true; // Heating stand (left) - if ( itemID >= 0x184E && itemID <= 0x1850 ) - return true; // Heating stand (right) - if ( itemID >= 0x398C && itemID <= 0x399F ) - return true; // Fire field - - return false; - } - - private class InternalTarget : Target - { - private CookableFood m_Item; - - public InternalTarget( CookableFood item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) return; - - if ( IsHeatSource( targeted ) ) - { - if ( from.BeginAction( typeof( CookableFood ) ) ) - { - from.PlaySound( 0x225 ); - - m_Item.Consume(); - - InternalTimer t = new InternalTimer( from, targeted as IPoint3D, from.Map, m_Item ); - t.Start(); - } - else - { - from.SendLocalizedMessage( 500119 ); // You must wait to perform another action - } - } - } - - private class InternalTimer : Timer - { - private Mobile m_From; - private IPoint3D m_Point; - private Map m_Map; - private CookableFood m_CookableFood; - - public InternalTimer( Mobile from, IPoint3D p, Map map, CookableFood cookableFood ) : base( TimeSpan.FromSeconds( 5.0 ) ) - { - m_From = from; - m_Point = p; - m_Map = map; - m_CookableFood = cookableFood; - } - - protected override void OnTick() - { - m_From.EndAction( typeof( CookableFood ) ); - - if ( m_From.Map != m_Map || (m_Point != null && m_From.GetDistanceToSqrt( m_Point ) > 3) ) - { - m_From.SendLocalizedMessage( 500686 ); // You burn the food to a crisp! It's ruined. - return; - } - - if ( m_From.CheckSkill( SkillName.Cooking, m_CookableFood.CookingLevel, 100 ) ) - { - Food cookedFood = m_CookableFood.Cook(); - - if ( m_From.AddToBackpack( cookedFood ) ) - m_From.PlaySound( 0x57 ); - } - else - { - m_From.SendLocalizedMessage( 500686 ); // You burn the food to a crisp! It's ruined. - } - } - } - } - } - - // ********** RawRibs ********** - public class RawRibs : CookableFood - { - [Constructible] - public RawRibs() : this( 1 ) - { - } - - [Constructible] - public RawRibs( int amount ) : base( 0x9F1, 10 ) - { - Weight = 1.0; - Stackable = true; - Amount = amount; - } - - public RawRibs( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new Ribs(); - } - } - - - // ********** RawLambLeg ********** - public class RawLambLeg : CookableFood - { - [Constructible] - public RawLambLeg() : this( 1 ) - { - } - - [Constructible] - public RawLambLeg( int amount ) : base( 0x1609, 10 ) - { - Stackable = true; - Amount = amount; - } - - public RawLambLeg( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version == 0 && Weight == 1 ) - Weight = -1; - } - - public override Food Cook() - { - return new LambLeg(); - } - } - - // ********** RawChickenLeg ********** - public class RawChickenLeg : CookableFood - { - [Constructible] - public RawChickenLeg() : base( 0x1607, 10 ) - { - Weight = 1.0; - Stackable = true; - } - - public RawChickenLeg( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new ChickenLeg(); - } - } - - - // ********** RawBird ********** - public class RawBird : CookableFood - { - [Constructible] - public RawBird() : this( 1 ) - { - } - - [Constructible] - public RawBird( int amount ) : base( 0x9B9, 10 ) - { - Weight = 1.0; - Stackable = true; - Amount = amount; - } - - public RawBird( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new CookedBird(); - } - } - - - // ********** UnbakedPeachCobbler ********** - public class UnbakedPeachCobbler : CookableFood - { - public override int LabelNumber => 1041335; // unbaked peach cobbler - - [Constructible] - public UnbakedPeachCobbler() : base( 0x1042, 25 ) - { - Weight = 1.0; - } - - public UnbakedPeachCobbler( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - public override Food Cook() - { - return new PeachCobbler(); - } - } - - // ********** UnbakedFruitPie ********** - public class UnbakedFruitPie : CookableFood - { - public override int LabelNumber => 1041334; // unbaked fruit pie - - [Constructible] - public UnbakedFruitPie() : base( 0x1042, 25 ) - { - Weight = 1.0; - } - - public UnbakedFruitPie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new FruitPie(); - } - } - - // ********** UnbakedMeatPie ********** - public class UnbakedMeatPie : CookableFood - { - public override int LabelNumber => 1041338; // unbaked meat pie - - [Constructible] - public UnbakedMeatPie() : base( 0x1042, 25 ) - { - Weight = 1.0; - } - - public UnbakedMeatPie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new MeatPie(); - } - } - - // ********** UnbakedPumpkinPie ********** - public class UnbakedPumpkinPie : CookableFood - { - public override int LabelNumber => 1041342; // unbaked pumpkin pie - - [Constructible] - public UnbakedPumpkinPie() : base( 0x1042, 25 ) - { - Weight = 1.0; - } - - public UnbakedPumpkinPie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new PumpkinPie(); - } - } - - // ********** UnbakedApplePie ********** - public class UnbakedApplePie : CookableFood - { - public override int LabelNumber => 1041336; // unbaked apple pie - - [Constructible] - public UnbakedApplePie() : base( 0x1042, 25 ) - { - Weight = 1.0; - } - - public UnbakedApplePie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new ApplePie(); - } - } - - // ********** UncookedCheesePizza ********** - [TypeAlias( "Server.Items.UncookedPizza" )] - public class UncookedCheesePizza : CookableFood - { - public override int LabelNumber => 1041341; // uncooked cheese pizza - - [Constructible] - public UncookedCheesePizza() : base( 0x1083, 20 ) - { - Weight = 1.0; - } - - public UncookedCheesePizza( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( ItemID == 0x1040 ) - ItemID = 0x1083; - - if ( Hue == 51 ) - Hue = 0; - } - - public override Food Cook() - { - return new CheesePizza(); - } - } - - // ********** UncookedSausagePizza ********** - public class UncookedSausagePizza : CookableFood - { - public override int LabelNumber => 1041337; // uncooked sausage pizza - - [Constructible] - public UncookedSausagePizza() : base( 0x1083, 20 ) - { - Weight = 1.0; - } - - public UncookedSausagePizza( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override Food Cook() - { - return new SausagePizza(); - } - } + public static bool IsHeatSource(object targeted) + { + int itemID; + + if (targeted is Item item) + itemID = item.ItemID; + else if (targeted is StaticTarget target) + itemID = target.ItemID; + else + return false; + + if (itemID >= 0xDE3 && itemID <= 0xDE9) + return true; // Campfire + if (itemID >= 0x461 && itemID <= 0x48E) + return true; // Sandstone oven/fireplace + if (itemID >= 0x92B && itemID <= 0x96C) + return true; // Stone oven/fireplace + if (itemID == 0xFAC) + return true; // Firepit + if (itemID >= 0x184A && itemID <= 0x184C) + return true; // Heating stand (left) + if (itemID >= 0x184E && itemID <= 0x1850) + return true; // Heating stand (right) + if (itemID >= 0x398C && itemID <= 0x399F) + return true; // Fire field + + return false; + } + + private class InternalTarget : Target + { + private CookableFood m_Item; + + public InternalTarget(CookableFood item) : base(1, false, TargetFlags.None) + { + m_Item = item; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) return; + + if (IsHeatSource(targeted)) + { + if (from.BeginAction(typeof(CookableFood))) + { + from.PlaySound(0x225); + + m_Item.Consume(); + + InternalTimer t = new InternalTimer(from, targeted as IPoint3D, from.Map, m_Item); + t.Start(); + } + else + { + from.SendLocalizedMessage(500119); // You must wait to perform another action + } + } + } + + private class InternalTimer : Timer + { + private CookableFood m_CookableFood; + private Mobile m_From; + private Map m_Map; + private IPoint3D m_Point; + + public InternalTimer(Mobile from, IPoint3D p, Map map, CookableFood cookableFood) : base( + TimeSpan.FromSeconds(5.0)) + { + m_From = from; + m_Point = p; + m_Map = map; + m_CookableFood = cookableFood; + } + + protected override void OnTick() + { + m_From.EndAction(typeof(CookableFood)); + + if (m_From.Map != m_Map || m_Point != null && m_From.GetDistanceToSqrt(m_Point) > 3) + { + m_From.SendLocalizedMessage(500686); // You burn the food to a crisp! It's ruined. + return; + } + + if (m_From.CheckSkill(SkillName.Cooking, m_CookableFood.CookingLevel, 100)) + { + Food cookedFood = m_CookableFood.Cook(); + + if (m_From.AddToBackpack(cookedFood)) + m_From.PlaySound(0x57); + } + else + { + m_From.SendLocalizedMessage(500686); // You burn the food to a crisp! It's ruined. + } + } + } + } + } + + // ********** RawRibs ********** + public class RawRibs : CookableFood + { + [Constructible] + public RawRibs() : this(1) + { + } + + [Constructible] + public RawRibs(int amount) : base(0x9F1, 10) + { + Weight = 1.0; + Stackable = true; + Amount = amount; + } + + public RawRibs(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new Ribs(); + } + } + + + // ********** RawLambLeg ********** + public class RawLambLeg : CookableFood + { + [Constructible] + public RawLambLeg() : this(1) + { + } + + [Constructible] + public RawLambLeg(int amount) : base(0x1609, 10) + { + Stackable = true; + Amount = amount; + } + + public RawLambLeg(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0 && Weight == 1) + Weight = -1; + } + + public override Food Cook() + { + return new LambLeg(); + } + } + + // ********** RawChickenLeg ********** + public class RawChickenLeg : CookableFood + { + [Constructible] + public RawChickenLeg() : base(0x1607, 10) + { + Weight = 1.0; + Stackable = true; + } + + public RawChickenLeg(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new ChickenLeg(); + } + } + + + // ********** RawBird ********** + public class RawBird : CookableFood + { + [Constructible] + public RawBird() : this(1) + { + } + + [Constructible] + public RawBird(int amount) : base(0x9B9, 10) + { + Weight = 1.0; + Stackable = true; + Amount = amount; + } + + public RawBird(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new CookedBird(); + } + } + + + // ********** UnbakedPeachCobbler ********** + public class UnbakedPeachCobbler : CookableFood + { + [Constructible] + public UnbakedPeachCobbler() : base(0x1042, 25) + { + Weight = 1.0; + } + + public UnbakedPeachCobbler(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041335; // unbaked peach cobbler + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new PeachCobbler(); + } + } + + // ********** UnbakedFruitPie ********** + public class UnbakedFruitPie : CookableFood + { + [Constructible] + public UnbakedFruitPie() : base(0x1042, 25) + { + Weight = 1.0; + } + + public UnbakedFruitPie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041334; // unbaked fruit pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new FruitPie(); + } + } + + // ********** UnbakedMeatPie ********** + public class UnbakedMeatPie : CookableFood + { + [Constructible] + public UnbakedMeatPie() : base(0x1042, 25) + { + Weight = 1.0; + } + + public UnbakedMeatPie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041338; // unbaked meat pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new MeatPie(); + } + } + + // ********** UnbakedPumpkinPie ********** + public class UnbakedPumpkinPie : CookableFood + { + [Constructible] + public UnbakedPumpkinPie() : base(0x1042, 25) + { + Weight = 1.0; + } + + public UnbakedPumpkinPie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041342; // unbaked pumpkin pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new PumpkinPie(); + } + } + + // ********** UnbakedApplePie ********** + public class UnbakedApplePie : CookableFood + { + [Constructible] + public UnbakedApplePie() : base(0x1042, 25) + { + Weight = 1.0; + } + + public UnbakedApplePie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041336; // unbaked apple pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new ApplePie(); + } + } + + // ********** UncookedCheesePizza ********** + [TypeAlias("Server.Items.UncookedPizza")] + public class UncookedCheesePizza : CookableFood + { + [Constructible] + public UncookedCheesePizza() : base(0x1083, 20) + { + Weight = 1.0; + } + + public UncookedCheesePizza(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041341; // uncooked cheese pizza + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (ItemID == 0x1040) + ItemID = 0x1083; + + if (Hue == 51) + Hue = 0; + } + + public override Food Cook() + { + return new CheesePizza(); + } + } + + // ********** UncookedSausagePizza ********** + public class UncookedSausagePizza : CookableFood + { + [Constructible] + public UncookedSausagePizza() : base(0x1083, 20) + { + Weight = 1.0; + } + + public UncookedSausagePizza(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041337; // uncooked sausage pizza + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override Food Cook() + { + return new SausagePizza(); + } + } #if false - // ********** UncookedPizza ********** +// ********** UncookedPizza ********** public class UncookedPizza : CookableFood { [Constructible] @@ -608,266 +609,266 @@ namespace Server.Items } #endif - // ********** UnbakedQuiche ********** - public class UnbakedQuiche : CookableFood - { - public override int LabelNumber => 1041339; // unbaked quiche + // ********** UnbakedQuiche ********** + public class UnbakedQuiche : CookableFood + { + [Constructible] + public UnbakedQuiche() : base(0x1042, 25) + { + Weight = 1.0; + } - [Constructible] - public UnbakedQuiche() : base( 0x1042, 25 ) - { - Weight = 1.0; - } + public UnbakedQuiche(Serial serial) : base(serial) + { + } - public UnbakedQuiche( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041339; // unbaked quiche - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override Food Cook() - { - return new Quiche(); - } - } + public override Food Cook() + { + return new Quiche(); + } + } - // ********** Eggs ********** - public class Eggs : CookableFood - { - [Constructible] - public Eggs() : this( 1 ) - { - } + // ********** Eggs ********** + public class Eggs : CookableFood + { + [Constructible] + public Eggs() : this(1) + { + } - [Constructible] - public Eggs( int amount ) : base( 0x9B5, 15 ) - { - Weight = 1.0; - Stackable = true; - Amount = amount; - } + [Constructible] + public Eggs(int amount) : base(0x9B5, 15) + { + Weight = 1.0; + Stackable = true; + Amount = amount; + } - public Eggs( Serial serial ) : base( serial ) - { - } + public Eggs(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - Stackable = true; + if (version < 1) + { + Stackable = true; - if ( Weight == 0.5 ) - Weight = 1.0; - } - } + if (Weight == 0.5) + Weight = 1.0; + } + } - public override Food Cook() - { - return new FriedEggs(); - } - } + public override Food Cook() + { + return new FriedEggs(); + } + } - // ********** BrightlyColoredEggs ********** - public class BrightlyColoredEggs : CookableFood - { - public override string DefaultName => "brightly colored eggs"; + // ********** BrightlyColoredEggs ********** + public class BrightlyColoredEggs : CookableFood + { + [Constructible] + public BrightlyColoredEggs() : base(0x9B5, 15) + { + Weight = 0.5; + Hue = 3 + Utility.Random(20) * 5; + } - [Constructible] - public BrightlyColoredEggs() : base( 0x9B5, 15 ) - { - Weight = 0.5; - Hue = 3 + (Utility.Random( 20 ) * 5); - } + public BrightlyColoredEggs(Serial serial) : base(serial) + { + } - public BrightlyColoredEggs( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "brightly colored eggs"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override Food Cook() - { - return new FriedEggs(); - } - } + public override Food Cook() + { + return new FriedEggs(); + } + } - // ********** EasterEggs ********** - public class EasterEggs : CookableFood - { - public override int LabelNumber => 1016105; // Easter Eggs + // ********** EasterEggs ********** + public class EasterEggs : CookableFood + { + [Constructible] + public EasterEggs() : base(0x9B5, 15) + { + Weight = 0.5; + Hue = 3 + Utility.Random(20) * 5; + } - [Constructible] - public EasterEggs() : base( 0x9B5, 15 ) - { - Weight = 0.5; - Hue = 3 + (Utility.Random( 20 ) * 5); - } + public EasterEggs(Serial serial) : base(serial) + { + } - public EasterEggs( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1016105; // Easter Eggs - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override Food Cook() - { - return new FriedEggs(); - } - } + public override Food Cook() + { + return new FriedEggs(); + } + } - // ********** CookieMix ********** - public class CookieMix : CookableFood - { - [Constructible] - public CookieMix() : base( 0x103F, 20 ) - { - Weight = 1.0; - } + // ********** CookieMix ********** + public class CookieMix : CookableFood + { + [Constructible] + public CookieMix() : base(0x103F, 20) + { + Weight = 1.0; + } - public CookieMix( Serial serial ) : base( serial ) - { - } + public CookieMix(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override Food Cook() - { - return new Cookies(); - } - } + public override Food Cook() + { + return new Cookies(); + } + } - // ********** CakeMix ********** - public class CakeMix : CookableFood - { - public override int LabelNumber => 1041002; // cake mix + // ********** CakeMix ********** + public class CakeMix : CookableFood + { + [Constructible] + public CakeMix() : base(0x103F, 40) + { + Weight = 1.0; + } - [Constructible] - public CakeMix() : base( 0x103F, 40 ) - { - Weight = 1.0; - } + public CakeMix(Serial serial) : base(serial) + { + } - public CakeMix( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041002; // cake mix - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override Food Cook() - { - return new Cake(); - } - } + public override Food Cook() + { + return new Cake(); + } + } - public class RawFishSteak : CookableFood - { - public override double DefaultWeight => 0.1; + public class RawFishSteak : CookableFood + { + [Constructible] + public RawFishSteak() : this(1) + { + } - [Constructible] - public RawFishSteak() : this( 1 ) - { - } + [Constructible] + public RawFishSteak(int amount) : base(0x097A, 10) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public RawFishSteak( int amount ) : base( 0x097A, 10 ) - { - Stackable = true; - Amount = amount; - } + public RawFishSteak(Serial serial) : base(serial) + { + } - public RawFishSteak( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - public override Food Cook() - { - return new FishSteak(); - } + public override Food Cook() + { + return new FishSteak(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Food/Cooking.cs b/Scripts/Items/Food/Cooking.cs index 6da462e67..aa0660c3b 100644 --- a/Scripts/Items/Food/Cooking.cs +++ b/Scripts/Items/Food/Cooking.cs @@ -3,48 +3,53 @@ using Server.Targeting; namespace Server.Items { - public class UtilityItem - { - static public int RandomChoice( int itemID1, int itemID2 ) - { - int iRet = 0; - switch ( Utility.Random( 2 ) ) - { - default: - case 0: iRet = itemID1; break; - case 1: iRet = itemID2; break; - } - return iRet; - } - } + public class UtilityItem + { + public static int RandomChoice(int itemID1, int itemID2) + { + int iRet = 0; + switch (Utility.Random(2)) + { + default: + case 0: + iRet = itemID1; + break; + case 1: + iRet = itemID2; + break; + } - // ********** Dough ********** - public class Dough : Item - { - [Constructible] - public Dough() : base( 0x103d ) - { - Stackable = Core.ML; - Weight = 1.0; - } + return iRet; + } + } - public Dough( Serial serial ) : base( serial ) - { - } + // ********** Dough ********** + public class Dough : Item + { + [Constructible] + public Dough() : base(0x103d) + { + Stackable = Core.ML; + Weight = 1.0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Dough(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } #if false public override void OnDoubleClick( Mobile from ) @@ -56,93 +61,93 @@ namespace Server.Items } #endif - private class InternalTarget : Target - { - private Dough m_Item; + private class InternalTarget : Target + { + private Dough m_Item; - public InternalTarget( Dough item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget(Dough item) : base(1, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) return; - if ( !(targeted is Item targetItem) || targetItem.Deleted ) - return; + if (!(targeted is Item targetItem) || targetItem.Deleted) + return; - m_Item.Consume(); + m_Item.Consume(); - if ( targeted is Eggs ) - { - targetItem.Consume(); + if (targeted is Eggs) + { + targetItem.Consume(); - from.AddToBackpack( new UnbakedQuiche() ); - from.AddToBackpack( new Eggshells() ); - } - else if ( targeted is CheeseWheel ) - { - targetItem.Consume(); + from.AddToBackpack(new UnbakedQuiche()); + from.AddToBackpack(new Eggshells()); + } + else if (targeted is CheeseWheel) + { + targetItem.Consume(); - from.AddToBackpack( new CheesePizza() ); - } - else if ( targeted is Sausage ) - { - targetItem.Consume(); + from.AddToBackpack(new CheesePizza()); + } + else if (targeted is Sausage) + { + targetItem.Consume(); - from.AddToBackpack( new SausagePizza() ); - } - else if ( targeted is Apple ) - { - targetItem.Consume(); + from.AddToBackpack(new SausagePizza()); + } + else if (targeted is Apple) + { + targetItem.Consume(); - from.AddToBackpack( new UnbakedApplePie() ); - } + from.AddToBackpack(new UnbakedApplePie()); + } - else if ( targeted is Peach ) - { - targetItem.Consume(); + else if (targeted is Peach) + { + targetItem.Consume(); - from.AddToBackpack( new UnbakedPeachCobbler() ); - } - } - } - } + from.AddToBackpack(new UnbakedPeachCobbler()); + } + } + } + } - // ********** SweetDough ********** - public class SweetDough : Item - { - public override int LabelNumber => 1041340; // sweet dough + // ********** SweetDough ********** + public class SweetDough : Item + { + public override int LabelNumber => 1041340; // sweet dough - [Constructible] - public SweetDough() : base( 0x103d ) - { - Stackable = Core.ML; - Weight = 1.0; - Hue = 150; - } + [Constructible] + public SweetDough() : base(0x103d) + { + Stackable = Core.ML; + Weight = 1.0; + Hue = 150; + } - public SweetDough( Serial serial ) : base( serial ) - { - } + public SweetDough(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 51 ) - Hue = 150; - } + if (Hue == 51) + Hue = 150; + } #if false public override void OnDoubleClick( Mobile from ) @@ -154,338 +159,337 @@ namespace Server.Items } #endif - private class InternalTarget : Target - { - private SweetDough m_Item; + private class InternalTarget : Target + { + private SweetDough m_Item; - public InternalTarget( SweetDough item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget(SweetDough item) : base(1, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) return; - m_Item.Consume(); + m_Item.Consume(); - if ( targeted is BowlFlour flour ) - { - flour.Delete(); + if (targeted is BowlFlour flour) + { + flour.Delete(); - from.AddToBackpack( new CakeMix() ); - } - else if ( targeted is Campfire campfire ) - { - from.PlaySound( 0x225 ); - InternalTimer t = new InternalTimer( from, campfire ); - t.Start(); - } - } + from.AddToBackpack(new CakeMix()); + } + else if (targeted is Campfire campfire) + { + from.PlaySound(0x225); + InternalTimer t = new InternalTimer(from, campfire); + t.Start(); + } + } - private class InternalTimer : Timer - { - private Mobile m_From; - private Campfire m_Campfire; + private class InternalTimer : Timer + { + private Campfire m_Campfire; + private Mobile m_From; - public InternalTimer( Mobile from, Campfire campfire ) : base( TimeSpan.FromSeconds( 5.0 ) ) - { - m_From = from; - m_Campfire = campfire; - } + public InternalTimer(Mobile from, Campfire campfire) : base(TimeSpan.FromSeconds(5.0)) + { + m_From = from; + m_Campfire = campfire; + } - protected override void OnTick() - { - if ( m_From.GetDistanceToSqrt( m_Campfire ) > 3 ) - { - m_From.SendLocalizedMessage( 500686 ); // You burn the food to a crisp! It's ruined. - return; - } + protected override void OnTick() + { + if (m_From.GetDistanceToSqrt(m_Campfire) > 3) + { + m_From.SendLocalizedMessage(500686); // You burn the food to a crisp! It's ruined. + return; + } - if ( m_From.CheckSkill( SkillName.Cooking, 0, 10 ) ) - { - if ( m_From.AddToBackpack( new Muffins() ) ) - m_From.PlaySound( 0x57 ); - } - else - { - m_From.SendLocalizedMessage( 500686 ); // You burn the food to a crisp! It's ruined. - } - } - } - } - } + if (m_From.CheckSkill(SkillName.Cooking, 0, 10)) + { + if (m_From.AddToBackpack(new Muffins())) + m_From.PlaySound(0x57); + } + else + { + m_From.SendLocalizedMessage(500686); // You burn the food to a crisp! It's ruined. + } + } + } + } + } - // ********** JarHoney ********** - public class JarHoney : Item - { - [Constructible] - public JarHoney() : base( 0x9ec ) - { - Weight = 1.0; - Stackable = true; - } + // ********** JarHoney ********** + public class JarHoney : Item + { + [Constructible] + public JarHoney() : base(0x9ec) + { + Weight = 1.0; + Stackable = true; + } - public JarHoney( Serial serial ) : base( serial ) - { - } + public JarHoney(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - Stackable = true; - } + int version = reader.ReadInt(); + Stackable = true; + } - /*public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; + /*public override void OnDoubleClick( Mobile from ) + { + if ( !Movable ) + return; - from.Target = new InternalTarget( this ); - }*/ + from.Target = new InternalTarget( this ); + }*/ - private class InternalTarget : Target - { - private JarHoney m_Item; + private class InternalTarget : Target + { + private JarHoney m_Item; - public InternalTarget( JarHoney item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget(JarHoney item) : base(1, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) return; - m_Item.Consume(); + m_Item.Consume(); - if ( targeted is Dough dough ) - { - dough.Consume(); + if (targeted is Dough dough) + { + dough.Consume(); - from.AddToBackpack( new SweetDough() ); - } + from.AddToBackpack(new SweetDough()); + } - if (targeted is BowlFlour flour) - { - flour.Delete(); + if (targeted is BowlFlour flour) + { + flour.Delete(); - from.AddToBackpack( new CookieMix() ); - } - } - } - } + from.AddToBackpack(new CookieMix()); + } + } + } + } - // ********** BowlFlour ********** - public class BowlFlour : Item - { - [Constructible] - public BowlFlour() : base( 0xa1e ) - { - Weight = 1.0; - } + // ********** BowlFlour ********** + public class BowlFlour : Item + { + [Constructible] + public BowlFlour() : base(0xa1e) + { + Weight = 1.0; + } - public BowlFlour( Serial serial ) : base( serial ) - { - } + public BowlFlour(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - // ********** WoodenBowl ********** - public class WoodenBowl : Item - { - [Constructible] - public WoodenBowl() : base( 0x15f8 ) - { - Weight = 1.0; - } + // ********** WoodenBowl ********** + public class WoodenBowl : Item + { + [Constructible] + public WoodenBowl() : base(0x15f8) + { + Weight = 1.0; + } - public WoodenBowl( Serial serial ) : base( serial ) - { - } + public WoodenBowl(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - // ********** PitcherWater ********** - /*public class PitcherWater : Item - { - [Constructible] - public PitcherWater() : base(Utility.Random( 0x1f9d, 2 )) - { - Weight = 1.0; - } + // ********** PitcherWater ********** + /*public class PitcherWater : Item + { + [Constructible] + public PitcherWater() : base(Utility.Random( 0x1f9d, 2 )) + { + Weight = 1.0; + } - public PitcherWater( Serial serial ) : base( serial ) - { - } + public PitcherWater( Serial serial ) : base( serial ) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize( GenericWriter writer ) + { + base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + writer.Write( (int) 0 ); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize( GenericReader reader ) + { + base.Deserialize( reader ); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; + public override void OnDoubleClick( Mobile from ) + { + if ( !Movable ) + return; - from.Target = new InternalTarget( this ); - } + from.Target = new InternalTarget( this ); + } - private class InternalTarget : Target - { - private PitcherWater m_Item; + private class InternalTarget : Target + { + private PitcherWater m_Item; - public InternalTarget( PitcherWater item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget( PitcherWater item ) : base( 1, false, TargetFlags.None ) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) return; + protected override void OnTarget( Mobile from, object targeted ) + { + if ( m_Item.Deleted ) return; - if ( targeted is BowlFlour ) - { - m_Item.Delete(); - ((BowlFlour)targeted).Delete(); + if ( targeted is BowlFlour ) + { + m_Item.Delete(); + ((BowlFlour)targeted).Delete(); - from.AddToBackpack( new Dough() ); - from.AddToBackpack( new WoodenBowl() ); - } - } - } - }*/ + from.AddToBackpack( new Dough() ); + from.AddToBackpack( new WoodenBowl() ); + } + } + } + }*/ - // ********** SackFlour ********** - [TypeAlias( "Server.Items.SackFlourOpen" )] - public class SackFlour : Item, IHasQuantity - { - private int m_Quantity; + // ********** SackFlour ********** + [TypeAlias("Server.Items.SackFlourOpen")] + public class SackFlour : Item, IHasQuantity + { + private int m_Quantity; - [CommandProperty( AccessLevel.GameMaster )] - public int Quantity - { - get => m_Quantity; - set - { - m_Quantity = Math.Min(20, Math.Max(0, value)); + [Constructible] + public SackFlour() : base(0x1039) + { + Weight = 5.0; + m_Quantity = 20; + } - if ( m_Quantity == 0 ) - Delete(); - else if ( m_Quantity < 20 && (ItemID == 0x1039 || ItemID == 0x1045) ) - ++ItemID; - } - } + public SackFlour(Serial serial) : base(serial) + { + } - [Constructible] - public SackFlour() : base( 0x1039 ) - { - Weight = 5.0; - m_Quantity = 20; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Quantity + { + get => m_Quantity; + set + { + m_Quantity = Math.Min(20, Math.Max(0, value)); - public SackFlour( Serial serial ) : base( serial ) - { - } + if (m_Quantity == 0) + Delete(); + else if (m_Quantity < 20 && (ItemID == 0x1039 || ItemID == 0x1045)) + ++ItemID; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 2 ); // version + writer.Write(2); // version - writer.Write( (int) m_Quantity ); - } + writer.Write(m_Quantity); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 2: - case 1: - { - m_Quantity = reader.ReadInt(); - break; - } - case 0: - { - m_Quantity = 20; - break; - } - } + switch (version) + { + case 2: + case 1: + { + m_Quantity = reader.ReadInt(); + break; + } + case 0: + { + m_Quantity = 20; + break; + } + } - if ( version < 2 && Weight == 1.0 ) - Weight = 5.0; - } + if (version < 2 && Weight == 1.0) + Weight = 5.0; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; + public override void OnDoubleClick(Mobile from) + { + if (!Movable) + return; - if ( (ItemID == 0x1039 || ItemID == 0x1045) ) - ++ItemID; + if (ItemID == 0x1039 || ItemID == 0x1045) + ++ItemID; #if false this.Delete(); from.AddToBackpack( new SackFlourOpen() ); #endif - } - - } + } + } #if false - // ********** SackFlourOpen ********** +// ********** SackFlourOpen ********** public class SackFlourOpen : Item { public override int LabelNumber => 1024166; // open sack of flour @@ -563,90 +567,90 @@ namespace Server.Items } #endif - // ********** Eggshells ********** - public class Eggshells : Item - { - [Constructible] - public Eggshells() : base( 0x9b4 ) - { - Weight = 0.5; - } + // ********** Eggshells ********** + public class Eggshells : Item + { + [Constructible] + public Eggshells() : base(0x9b4) + { + Weight = 0.5; + } - public Eggshells( Serial serial ) : base( serial ) - { - } + public Eggshells(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class WheatSheaf : Item - { - [Constructible] - public WheatSheaf() : this( 1 ) - { - } + public class WheatSheaf : Item + { + [Constructible] + public WheatSheaf() : this(1) + { + } - [Constructible] - public WheatSheaf( int amount ) : base( 7869 ) - { - Weight = 1.0; - Stackable = true; - Amount = amount; - } + [Constructible] + public WheatSheaf(int amount) : base(7869) + { + Weight = 1.0; + Stackable = true; + Amount = amount; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; + public WheatSheaf(Serial serial) : base(serial) + { + } - from.BeginTarget( 4, false, TargetFlags.None, OnTarget ); - } + public override void OnDoubleClick(Mobile from) + { + if (!Movable) + return; - public virtual void OnTarget( Mobile from, object obj ) - { - if ( obj is AddonComponent addon ) - obj = addon.Addon; + from.BeginTarget(4, false, TargetFlags.None, OnTarget); + } - if ( obj is IFlourMill mill ) - { - int needs = mill.MaxFlour - mill.CurFlour; + public virtual void OnTarget(Mobile from, object obj) + { + if (obj is AddonComponent addon) + obj = addon.Addon; - if ( needs > Amount ) - needs = Amount; + if (obj is IFlourMill mill) + { + int needs = mill.MaxFlour - mill.CurFlour; - mill.CurFlour += needs; - Consume( needs ); - } - } + if (needs > Amount) + needs = Amount; - public WheatSheaf( Serial serial ) : base( serial ) - { - } + mill.CurFlour += needs; + Consume(needs); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Food/Food.cs b/Scripts/Items/Food/Food.cs index d33ce5b3c..7b797cb28 100644 --- a/Scripts/Items/Food/Food.cs +++ b/Scripts/Items/Food/Food.cs @@ -3,782 +3,789 @@ using Server.ContextMenus; namespace Server.Items { - public abstract class Food : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Poisoner { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int FillFactor { get; set; } - - public Food( int itemID ) : this( 1, itemID ) - { - } - - public Food( int amount, int itemID ) : base( itemID ) - { - Stackable = true; - Amount = amount; - FillFactor = 1; - } - - public Food( Serial serial ) : base( serial ) - { - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.Alive ) - list.Add( new EatEntry( from, this ) ); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; - - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - Eat( from ); - } - } - - public virtual bool Eat( Mobile from ) - { - // Fill the Mobile with FillFactor - if ( CheckHunger( from ) ) - { - // Play a random "eat" sound - from.PlaySound( Utility.Random( 0x3A, 3 ) ); - - if ( from.Body.IsHuman && !from.Mounted ) - from.Animate( 34, 5, 1, true, false, 0 ); - - if ( Poison != null ) - from.ApplyPoison( Poisoner, Poison ); - - Consume(); - - return true; - } - - return false; - } - - public virtual bool CheckHunger( Mobile from ) - { - return FillHunger( from, FillFactor ); - } - - public static bool FillHunger( Mobile from, int fillFactor ) - { - if ( from.Hunger >= 20 ) - { - from.SendLocalizedMessage( 500867 ); // You are simply too full to eat any more! - return false; - } - - int iHunger = from.Hunger + fillFactor; - - if ( from.Stam < from.StamMax ) - from.Stam += Utility.Random( 6, 3 ) + fillFactor / 5; - - if ( iHunger >= 20 ) - { - from.Hunger = 20; - from.SendLocalizedMessage( 500872 ); // You manage to eat the food, but you are stuffed! - } - else - { - from.Hunger = iHunger; - - if ( iHunger < 5 ) - from.SendLocalizedMessage( 500868 ); // You eat the food, but are still extremely hungry. - else if ( iHunger < 10 ) - from.SendLocalizedMessage( 500869 ); // You eat the food, and begin to feel more satiated. - else if ( iHunger < 15 ) - from.SendLocalizedMessage( 500870 ); // After eating the food, you feel much less hungry. - else - from.SendLocalizedMessage( 500871 ); // You feel quite full after consuming the food. - } - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 4 ); // version - - writer.Write( Poisoner ); - - Poison.Serialize( Poison, writer ); - writer.Write( FillFactor ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - switch ( reader.ReadInt() ) - { - case 0: Poison = null; break; - case 1: Poison = Poison.Lesser; break; - case 2: Poison = Poison.Regular; break; - case 3: Poison = Poison.Greater; break; - case 4: Poison = Poison.Deadly; break; - } - - break; - } - case 2: - { - Poison = Poison.Deserialize( reader ); - break; - } - case 3: - { - Poison = Poison.Deserialize( reader ); - FillFactor = reader.ReadInt(); - break; - } - case 4: - { - Poisoner = reader.ReadMobile(); - goto case 3; - } - } - } - } - - public class BreadLoaf : Food - { - [Constructible] - public BreadLoaf() : this( 1 ) - { - } - - [Constructible] - public BreadLoaf( int amount ) : base( amount, 0x103B ) - { - Weight = 1.0; - FillFactor = 3; - } - - public BreadLoaf( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Bacon : Food - { - [Constructible] - public Bacon() : this( 1 ) - { - } - - [Constructible] - public Bacon( int amount ) : base( amount, 0x979 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Bacon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SlabOfBacon : Food - { - [Constructible] - public SlabOfBacon() : this( 1 ) - { - } - - [Constructible] - public SlabOfBacon( int amount ) : base( amount, 0x976 ) - { - Weight = 1.0; - FillFactor = 3; - } - - public SlabOfBacon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FishSteak : Food - { - public override double DefaultWeight => 0.1; - - [Constructible] - public FishSteak() : this( 1 ) - { - } - - [Constructible] - public FishSteak( int amount ) : base( amount, 0x97B ) - { - FillFactor = 3; - } - - public FishSteak( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CheeseWheel : Food - { - public override double DefaultWeight => 0.1; - - [Constructible] - public CheeseWheel() : this( 1 ) - { - } - - [Constructible] - public CheeseWheel( int amount ) : base( amount, 0x97E ) - { - FillFactor = 3; - } - - public CheeseWheel( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CheeseWedge : Food - { - public override double DefaultWeight => 0.1; - - [Constructible] - public CheeseWedge() : this( 1 ) - { - } - - [Constructible] - public CheeseWedge( int amount ) : base( amount, 0x97D ) - { - FillFactor = 3; - } - - public CheeseWedge( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CheeseSlice : Food - { - public override double DefaultWeight => 0.1; - - [Constructible] - public CheeseSlice() : this( 1 ) - { - } - - [Constructible] - public CheeseSlice( int amount ) : base( amount, 0x97C ) - { - FillFactor = 1; - } - - public CheeseSlice( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FrenchBread : Food - { - [Constructible] - public FrenchBread() : this( 1 ) - { - } - - [Constructible] - public FrenchBread( int amount ) : base( amount, 0x98C ) - { - Weight = 2.0; - FillFactor = 3; - } - - public FrenchBread( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class FriedEggs : Food - { - [Constructible] - public FriedEggs() : this( 1 ) - { - } - - [Constructible] - public FriedEggs( int amount ) : base( amount, 0x9B6 ) - { - Weight = 1.0; - FillFactor = 4; - } - - public FriedEggs( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CookedBird : Food - { - [Constructible] - public CookedBird() : this( 1 ) - { - } - - [Constructible] - public CookedBird( int amount ) : base( amount, 0x9B7 ) - { - Weight = 1.0; - FillFactor = 5; - } - - public CookedBird( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RoastPig : Food - { - [Constructible] - public RoastPig() : this( 1 ) - { - } - - [Constructible] - public RoastPig( int amount ) : base( amount, 0x9BB ) - { - Weight = 45.0; - FillFactor = 20; - } - - public RoastPig( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Sausage : Food - { - [Constructible] - public Sausage() : this( 1 ) - { - } - - [Constructible] - public Sausage( int amount ) : base( amount, 0x9C0 ) - { - Weight = 1.0; - FillFactor = 4; - } - - public Sausage( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Ham : Food - { - [Constructible] - public Ham() : this( 1 ) - { - } - - [Constructible] - public Ham( int amount ) : base( amount, 0x9C9 ) - { - Weight = 1.0; - FillFactor = 5; - } - - public Ham( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Cake : Food - { - [Constructible] - public Cake() : base( 0x9E9 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 10; - } - - public Cake( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Ribs : Food - { - [Constructible] - public Ribs() : this( 1 ) - { - } - - [Constructible] - public Ribs( int amount ) : base( amount, 0x9F2 ) - { - Weight = 1.0; - FillFactor = 5; - } - - public Ribs( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Cookies : Food - { - [Constructible] - public Cookies() : base( 0x160b ) - { - Stackable = Core.ML; - Weight = 1.0; - FillFactor = 4; - } - - public Cookies( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Muffins : Food - { - [Constructible] - public Muffins() : base( 0x9eb ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 4; - } - - public Muffins( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [TypeAlias( "Server.Items.Pizza" )] - public class CheesePizza : Food - { - public override int LabelNumber => 1044516; // cheese pizza - - [Constructible] - public CheesePizza() : base( 0x1040 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 6; - } - - public CheesePizza( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SausagePizza : Food - { - public override int LabelNumber => 1044517; // sausage pizza - - [Constructible] - public SausagePizza() : base( 0x1040 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 6; - } - - public SausagePizza( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public abstract class Food : Item + { + public Food(int itemID) : this(1, itemID) + { + } + + public Food(int amount, int itemID) : base(itemID) + { + Stackable = true; + Amount = amount; + FillFactor = 1; + } + + public Food(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Poisoner{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int FillFactor{ get; set; } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.Alive) + list.Add(new EatEntry(from, this)); + } + + public override void OnDoubleClick(Mobile from) + { + if (!Movable) + return; + + if (from.InRange(GetWorldLocation(), 1)) Eat(from); + } + + public virtual bool Eat(Mobile from) + { + // Fill the Mobile with FillFactor + if (CheckHunger(from)) + { + // Play a random "eat" sound + from.PlaySound(Utility.Random(0x3A, 3)); + + if (from.Body.IsHuman && !from.Mounted) + from.Animate(34, 5, 1, true, false, 0); + + if (Poison != null) + from.ApplyPoison(Poisoner, Poison); + + Consume(); + + return true; + } + + return false; + } + + public virtual bool CheckHunger(Mobile from) + { + return FillHunger(from, FillFactor); + } + + public static bool FillHunger(Mobile from, int fillFactor) + { + if (from.Hunger >= 20) + { + from.SendLocalizedMessage(500867); // You are simply too full to eat any more! + return false; + } + + int iHunger = from.Hunger + fillFactor; + + if (from.Stam < from.StamMax) + from.Stam += Utility.Random(6, 3) + fillFactor / 5; + + if (iHunger >= 20) + { + from.Hunger = 20; + from.SendLocalizedMessage(500872); // You manage to eat the food, but you are stuffed! + } + else + { + from.Hunger = iHunger; + + if (iHunger < 5) + from.SendLocalizedMessage(500868); // You eat the food, but are still extremely hungry. + else if (iHunger < 10) + from.SendLocalizedMessage(500869); // You eat the food, and begin to feel more satiated. + else if (iHunger < 15) + from.SendLocalizedMessage(500870); // After eating the food, you feel much less hungry. + else + from.SendLocalizedMessage(500871); // You feel quite full after consuming the food. + } + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(4); // version + + writer.Write(Poisoner); + + Poison.Serialize(Poison, writer); + writer.Write(FillFactor); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + switch (reader.ReadInt()) + { + case 0: + Poison = null; + break; + case 1: + Poison = Poison.Lesser; + break; + case 2: + Poison = Poison.Regular; + break; + case 3: + Poison = Poison.Greater; + break; + case 4: + Poison = Poison.Deadly; + break; + } + + break; + } + case 2: + { + Poison = Poison.Deserialize(reader); + break; + } + case 3: + { + Poison = Poison.Deserialize(reader); + FillFactor = reader.ReadInt(); + break; + } + case 4: + { + Poisoner = reader.ReadMobile(); + goto case 3; + } + } + } + } + + public class BreadLoaf : Food + { + [Constructible] + public BreadLoaf() : this(1) + { + } + + [Constructible] + public BreadLoaf(int amount) : base(amount, 0x103B) + { + Weight = 1.0; + FillFactor = 3; + } + + public BreadLoaf(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Bacon : Food + { + [Constructible] + public Bacon() : this(1) + { + } + + [Constructible] + public Bacon(int amount) : base(amount, 0x979) + { + Weight = 1.0; + FillFactor = 1; + } + + public Bacon(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SlabOfBacon : Food + { + [Constructible] + public SlabOfBacon() : this(1) + { + } + + [Constructible] + public SlabOfBacon(int amount) : base(amount, 0x976) + { + Weight = 1.0; + FillFactor = 3; + } + + public SlabOfBacon(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FishSteak : Food + { + [Constructible] + public FishSteak() : this(1) + { + } + + [Constructible] + public FishSteak(int amount) : base(amount, 0x97B) + { + FillFactor = 3; + } + + public FishSteak(Serial serial) : base(serial) + { + } + + public override double DefaultWeight => 0.1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CheeseWheel : Food + { + [Constructible] + public CheeseWheel() : this(1) + { + } + + [Constructible] + public CheeseWheel(int amount) : base(amount, 0x97E) + { + FillFactor = 3; + } + + public CheeseWheel(Serial serial) : base(serial) + { + } + + public override double DefaultWeight => 0.1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CheeseWedge : Food + { + [Constructible] + public CheeseWedge() : this(1) + { + } + + [Constructible] + public CheeseWedge(int amount) : base(amount, 0x97D) + { + FillFactor = 3; + } + + public CheeseWedge(Serial serial) : base(serial) + { + } + + public override double DefaultWeight => 0.1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CheeseSlice : Food + { + [Constructible] + public CheeseSlice() : this(1) + { + } + + [Constructible] + public CheeseSlice(int amount) : base(amount, 0x97C) + { + FillFactor = 1; + } + + public CheeseSlice(Serial serial) : base(serial) + { + } + + public override double DefaultWeight => 0.1; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FrenchBread : Food + { + [Constructible] + public FrenchBread() : this(1) + { + } + + [Constructible] + public FrenchBread(int amount) : base(amount, 0x98C) + { + Weight = 2.0; + FillFactor = 3; + } + + public FrenchBread(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class FriedEggs : Food + { + [Constructible] + public FriedEggs() : this(1) + { + } + + [Constructible] + public FriedEggs(int amount) : base(amount, 0x9B6) + { + Weight = 1.0; + FillFactor = 4; + } + + public FriedEggs(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CookedBird : Food + { + [Constructible] + public CookedBird() : this(1) + { + } + + [Constructible] + public CookedBird(int amount) : base(amount, 0x9B7) + { + Weight = 1.0; + FillFactor = 5; + } + + public CookedBird(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RoastPig : Food + { + [Constructible] + public RoastPig() : this(1) + { + } + + [Constructible] + public RoastPig(int amount) : base(amount, 0x9BB) + { + Weight = 45.0; + FillFactor = 20; + } + + public RoastPig(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Sausage : Food + { + [Constructible] + public Sausage() : this(1) + { + } + + [Constructible] + public Sausage(int amount) : base(amount, 0x9C0) + { + Weight = 1.0; + FillFactor = 4; + } + + public Sausage(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Ham : Food + { + [Constructible] + public Ham() : this(1) + { + } + + [Constructible] + public Ham(int amount) : base(amount, 0x9C9) + { + Weight = 1.0; + FillFactor = 5; + } + + public Ham(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Cake : Food + { + [Constructible] + public Cake() : base(0x9E9) + { + Stackable = false; + Weight = 1.0; + FillFactor = 10; + } + + public Cake(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Ribs : Food + { + [Constructible] + public Ribs() : this(1) + { + } + + [Constructible] + public Ribs(int amount) : base(amount, 0x9F2) + { + Weight = 1.0; + FillFactor = 5; + } + + public Ribs(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Cookies : Food + { + [Constructible] + public Cookies() : base(0x160b) + { + Stackable = Core.ML; + Weight = 1.0; + FillFactor = 4; + } + + public Cookies(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Muffins : Food + { + [Constructible] + public Muffins() : base(0x9eb) + { + Stackable = false; + Weight = 1.0; + FillFactor = 4; + } + + public Muffins(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [TypeAlias("Server.Items.Pizza")] + public class CheesePizza : Food + { + [Constructible] + public CheesePizza() : base(0x1040) + { + Stackable = false; + Weight = 1.0; + FillFactor = 6; + } + + public CheesePizza(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1044516; // cheese pizza + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SausagePizza : Food + { + [Constructible] + public SausagePizza() : base(0x1040) + { + Stackable = false; + Weight = 1.0; + FillFactor = 6; + } + + public SausagePizza(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1044517; // sausage pizza + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } #if false public class Pizza : Food @@ -811,451 +818,451 @@ namespace Server.Items } #endif - public class FruitPie : Food - { - public override int LabelNumber => 1041346; // baked fruit pie - - [Constructible] - public FruitPie() : base( 0x1041 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 5; - } - - public FruitPie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MeatPie : Food - { - public override int LabelNumber => 1041347; // baked meat pie - - [Constructible] - public MeatPie() : base( 0x1041 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 5; - } - - public MeatPie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PumpkinPie : Food - { - public override int LabelNumber => 1041348; // baked pumpkin pie - - [Constructible] - public PumpkinPie() : base( 0x1041 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 5; - } - - public PumpkinPie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ApplePie : Food - { - public override int LabelNumber => 1041343; // baked apple pie - - [Constructible] - public ApplePie() : base( 0x1041 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 5; - } - - public ApplePie( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PeachCobbler : Food - { - public override int LabelNumber => 1041344; // baked peach cobbler - - [Constructible] - public PeachCobbler() : base( 0x1041 ) - { - Stackable = false; - Weight = 1.0; - FillFactor = 5; - } - - public PeachCobbler( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Quiche : Food - { - public override int LabelNumber => 1041345; // baked quiche - - [Constructible] - public Quiche() : base( 0x1041 ) - { - Stackable = Core.ML; - Weight = 1.0; - FillFactor = 5; - } - - public Quiche( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LambLeg : Food - { - [Constructible] - public LambLeg() : this( 1 ) - { - } - - [Constructible] - public LambLeg( int amount ) : base( amount, 0x160a ) - { - Weight = 2.0; - FillFactor = 5; - } - - public LambLeg( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ChickenLeg : Food - { - [Constructible] - public ChickenLeg() : this( 1 ) - { - } - - [Constructible] - public ChickenLeg( int amount ) : base( amount, 0x1608 ) - { - Weight = 1.0; - FillFactor = 4; - } - - public ChickenLeg( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC74, 0xC75 )] - public class HoneydewMelon : Food - { - [Constructible] - public HoneydewMelon() : this( 1 ) - { - } - - [Constructible] - public HoneydewMelon( int amount ) : base( amount, 0xC74 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public HoneydewMelon( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC64, 0xC65 )] - public class YellowGourd : Food - { - [Constructible] - public YellowGourd() : this( 1 ) - { - } - - [Constructible] - public YellowGourd( int amount ) : base( amount, 0xC64 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public YellowGourd( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC66, 0xC67 )] - public class GreenGourd : Food - { - [Constructible] - public GreenGourd() : this( 1 ) - { - } - - [Constructible] - public GreenGourd( int amount ) : base( amount, 0xC66 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public GreenGourd( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xC7F, 0xC81 )] - public class EarOfCorn : Food - { - [Constructible] - public EarOfCorn() : this( 1 ) - { - } - - [Constructible] - public EarOfCorn( int amount ) : base( amount, 0xC81 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public EarOfCorn( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Turnip : Food - { - [Constructible] - public Turnip() : this( 1 ) - { - } - - [Constructible] - public Turnip( int amount ) : base( amount, 0xD3A ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Turnip( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SheafOfHay : Item - { - [Constructible] - public SheafOfHay() : base( 0xF36 ) - { - Weight = 10.0; - } - - public SheafOfHay( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public class FruitPie : Food + { + [Constructible] + public FruitPie() : base(0x1041) + { + Stackable = false; + Weight = 1.0; + FillFactor = 5; + } + + public FruitPie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041346; // baked fruit pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MeatPie : Food + { + [Constructible] + public MeatPie() : base(0x1041) + { + Stackable = false; + Weight = 1.0; + FillFactor = 5; + } + + public MeatPie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041347; // baked meat pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PumpkinPie : Food + { + [Constructible] + public PumpkinPie() : base(0x1041) + { + Stackable = false; + Weight = 1.0; + FillFactor = 5; + } + + public PumpkinPie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041348; // baked pumpkin pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ApplePie : Food + { + [Constructible] + public ApplePie() : base(0x1041) + { + Stackable = false; + Weight = 1.0; + FillFactor = 5; + } + + public ApplePie(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041343; // baked apple pie + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PeachCobbler : Food + { + [Constructible] + public PeachCobbler() : base(0x1041) + { + Stackable = false; + Weight = 1.0; + FillFactor = 5; + } + + public PeachCobbler(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041344; // baked peach cobbler + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Quiche : Food + { + [Constructible] + public Quiche() : base(0x1041) + { + Stackable = Core.ML; + Weight = 1.0; + FillFactor = 5; + } + + public Quiche(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041345; // baked quiche + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LambLeg : Food + { + [Constructible] + public LambLeg() : this(1) + { + } + + [Constructible] + public LambLeg(int amount) : base(amount, 0x160a) + { + Weight = 2.0; + FillFactor = 5; + } + + public LambLeg(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ChickenLeg : Food + { + [Constructible] + public ChickenLeg() : this(1) + { + } + + [Constructible] + public ChickenLeg(int amount) : base(amount, 0x1608) + { + Weight = 1.0; + FillFactor = 4; + } + + public ChickenLeg(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC74, 0xC75)] + public class HoneydewMelon : Food + { + [Constructible] + public HoneydewMelon() : this(1) + { + } + + [Constructible] + public HoneydewMelon(int amount) : base(amount, 0xC74) + { + Weight = 1.0; + FillFactor = 1; + } + + public HoneydewMelon(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC64, 0xC65)] + public class YellowGourd : Food + { + [Constructible] + public YellowGourd() : this(1) + { + } + + [Constructible] + public YellowGourd(int amount) : base(amount, 0xC64) + { + Weight = 1.0; + FillFactor = 1; + } + + public YellowGourd(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC66, 0xC67)] + public class GreenGourd : Food + { + [Constructible] + public GreenGourd() : this(1) + { + } + + [Constructible] + public GreenGourd(int amount) : base(amount, 0xC66) + { + Weight = 1.0; + FillFactor = 1; + } + + public GreenGourd(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xC7F, 0xC81)] + public class EarOfCorn : Food + { + [Constructible] + public EarOfCorn() : this(1) + { + } + + [Constructible] + public EarOfCorn(int amount) : base(amount, 0xC81) + { + Weight = 1.0; + FillFactor = 1; + } + + public EarOfCorn(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Turnip : Food + { + [Constructible] + public Turnip() : this(1) + { + } + + [Constructible] + public Turnip(int amount) : base(amount, 0xD3A) + { + Weight = 1.0; + FillFactor = 1; + } + + public Turnip(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SheafOfHay : Item + { + [Constructible] + public SheafOfHay() : base(0xF36) + { + Weight = 10.0; + } + + public SheafOfHay(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Food/Fruits.cs b/Scripts/Items/Food/Fruits.cs index 9f3ebe08f..591d4e7af 100644 --- a/Scripts/Items/Food/Fruits.cs +++ b/Scripts/Items/Food/Fruits.cs @@ -1,629 +1,647 @@ namespace Server.Items { - public class FruitBasket : Food - { - [Constructible] - public FruitBasket() : base( 1, 0x993 ) - { - Weight = 2.0; - FillFactor = 5; - Stackable = false; - } - - public FruitBasket( Serial serial ) : base( serial ) - { - } - - public override bool Eat( Mobile from ) - { - if ( !base.Eat( from ) ) - return false; - - from.AddToBackpack( new Basket() ); - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x171f, 0x1720 )] - public class Banana : Food - { - [Constructible] - public Banana() : this( 1 ) - { - } - - [Constructible] - public Banana( int amount ) : base( amount, 0x171f ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Banana( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x1721, 0x1722 )] - public class Bananas : Food - { - [Constructible] - public Bananas() : this( 1 ) - { - } - - [Constructible] - public Bananas( int amount ) : base( amount, 0x1721 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Bananas( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SplitCoconut : Food - { - [Constructible] - public SplitCoconut() : this( 1 ) - { - } - - [Constructible] - public SplitCoconut( int amount ) : base( amount, 0x1725 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public SplitCoconut( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Lemon : Food - { - [Constructible] - public Lemon() : this( 1 ) - { - } - - [Constructible] - public Lemon( int amount ) : base( amount, 0x1728 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Lemon( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Lemons : Food - { - [Constructible] - public Lemons() : this( 1 ) - { - } - - [Constructible] - public Lemons( int amount ) : base( amount, 0x1729 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Lemons( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Lime : Food - { - [Constructible] - public Lime() : this( 1 ) - { - } - - [Constructible] - public Lime( int amount ) : base( amount, 0x172a ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Lime( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Limes : Food - { - [Constructible] - public Limes() : this( 1 ) - { - } - - [Constructible] - public Limes( int amount ) : base( amount, 0x172B ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Limes( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Coconut : Food - { - [Constructible] - public Coconut() : this( 1 ) - { - } - - [Constructible] - public Coconut( int amount ) : base( amount, 0x1726 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Coconut( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class OpenCoconut : Food - { - [Constructible] - public OpenCoconut() : this( 1 ) - { - } - - [Constructible] - public OpenCoconut( int amount ) : base( amount, 0x1723 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public OpenCoconut( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Dates : Food - { - [Constructible] - public Dates() : this( 1 ) - { - } - - [Constructible] - public Dates( int amount ) : base( amount, 0x1727 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Dates( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Grapes : Food - { - [Constructible] - public Grapes() : this( 1 ) - { - } - - [Constructible] - public Grapes( int amount ) : base( amount, 0x9D1 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Grapes( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Peach : Food - { - [Constructible] - public Peach() : this( 1 ) - { - } - - [Constructible] - public Peach( int amount ) : base( amount, 0x9D2 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Peach( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Pear : Food - { - [Constructible] - public Pear() : this( 1 ) - { - } - - [Constructible] - public Pear( int amount ) : base( amount, 0x994 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Pear( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Apple : Food - { - [Constructible] - public Apple() : this( 1 ) - { - } - - [Constructible] - public Apple( int amount ) : base( amount, 0x9D0 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Apple( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Watermelon : Food - { - [Constructible] - public Watermelon() : this( 1 ) - { - } - - [Constructible] - public Watermelon( int amount ) : base( amount, 0xC5C ) - { - Weight = 5.0; - FillFactor = 5; - } - - public Watermelon( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version < 1 ) - { - if ( FillFactor == 2 ) - FillFactor = 5; - - if ( Weight == 2.0 ) - Weight = 5.0; - } - } - } - - public class SmallWatermelon : Food - { - [Constructible] - public SmallWatermelon() : this( 1 ) - { - } - - [Constructible] - public SmallWatermelon( int amount ) : base( amount, 0xC5D ) - { - Weight = 5.0; - FillFactor = 5; - } - - public SmallWatermelon( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xc72, 0xc73 )] - public class Squash : Food - { - [Constructible] - public Squash() : this( 1 ) - { - } - - [Constructible] - public Squash( int amount ) : base( amount, 0xc72 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Squash( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0xc79, 0xc7a )] - public class Cantaloupe : Food - { - [Constructible] - public Cantaloupe() : this( 1 ) - { - } - - [Constructible] - public Cantaloupe( int amount ) : base( amount, 0xc79 ) - { - Weight = 1.0; - FillFactor = 1; - } - - public Cantaloupe( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public class FruitBasket : Food + { + [Constructible] + public FruitBasket() : base(1, 0x993) + { + Weight = 2.0; + FillFactor = 5; + Stackable = false; + } + + public FruitBasket(Serial serial) : base(serial) + { + } + + public override bool Eat(Mobile from) + { + if (!base.Eat(from)) + return false; + + from.AddToBackpack(new Basket()); + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x171f, 0x1720)] + public class Banana : Food + { + [Constructible] + public Banana() : this(1) + { + } + + [Constructible] + public Banana(int amount) : base(amount, 0x171f) + { + Weight = 1.0; + FillFactor = 1; + } + + public Banana(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1721, 0x1722)] + public class Bananas : Food + { + [Constructible] + public Bananas() : this(1) + { + } + + [Constructible] + public Bananas(int amount) : base(amount, 0x1721) + { + Weight = 1.0; + FillFactor = 1; + } + + public Bananas(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SplitCoconut : Food + { + [Constructible] + public SplitCoconut() : this(1) + { + } + + [Constructible] + public SplitCoconut(int amount) : base(amount, 0x1725) + { + Weight = 1.0; + FillFactor = 1; + } + + public SplitCoconut(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Lemon : Food + { + [Constructible] + public Lemon() : this(1) + { + } + + [Constructible] + public Lemon(int amount) : base(amount, 0x1728) + { + Weight = 1.0; + FillFactor = 1; + } + + public Lemon(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Lemons : Food + { + [Constructible] + public Lemons() : this(1) + { + } + + [Constructible] + public Lemons(int amount) : base(amount, 0x1729) + { + Weight = 1.0; + FillFactor = 1; + } + + public Lemons(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Lime : Food + { + [Constructible] + public Lime() : this(1) + { + } + + [Constructible] + public Lime(int amount) : base(amount, 0x172a) + { + Weight = 1.0; + FillFactor = 1; + } + + public Lime(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Limes : Food + { + [Constructible] + public Limes() : this(1) + { + } + + [Constructible] + public Limes(int amount) : base(amount, 0x172B) + { + Weight = 1.0; + FillFactor = 1; + } + + public Limes(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Coconut : Food + { + [Constructible] + public Coconut() : this(1) + { + } + + [Constructible] + public Coconut(int amount) : base(amount, 0x1726) + { + Weight = 1.0; + FillFactor = 1; + } + + public Coconut(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class OpenCoconut : Food + { + [Constructible] + public OpenCoconut() : this(1) + { + } + + [Constructible] + public OpenCoconut(int amount) : base(amount, 0x1723) + { + Weight = 1.0; + FillFactor = 1; + } + + public OpenCoconut(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Dates : Food + { + [Constructible] + public Dates() : this(1) + { + } + + [Constructible] + public Dates(int amount) : base(amount, 0x1727) + { + Weight = 1.0; + FillFactor = 1; + } + + public Dates(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Grapes : Food + { + [Constructible] + public Grapes() : this(1) + { + } + + [Constructible] + public Grapes(int amount) : base(amount, 0x9D1) + { + Weight = 1.0; + FillFactor = 1; + } + + public Grapes(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Peach : Food + { + [Constructible] + public Peach() : this(1) + { + } + + [Constructible] + public Peach(int amount) : base(amount, 0x9D2) + { + Weight = 1.0; + FillFactor = 1; + } + + public Peach(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Pear : Food + { + [Constructible] + public Pear() : this(1) + { + } + + [Constructible] + public Pear(int amount) : base(amount, 0x994) + { + Weight = 1.0; + FillFactor = 1; + } + + public Pear(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Apple : Food + { + [Constructible] + public Apple() : this(1) + { + } + + [Constructible] + public Apple(int amount) : base(amount, 0x9D0) + { + Weight = 1.0; + FillFactor = 1; + } + + public Apple(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Watermelon : Food + { + [Constructible] + public Watermelon() : this(1) + { + } + + [Constructible] + public Watermelon(int amount) : base(amount, 0xC5C) + { + Weight = 5.0; + FillFactor = 5; + } + + public Watermelon(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version < 1) + { + if (FillFactor == 2) + FillFactor = 5; + + if (Weight == 2.0) + Weight = 5.0; + } + } + } + + public class SmallWatermelon : Food + { + [Constructible] + public SmallWatermelon() : this(1) + { + } + + [Constructible] + public SmallWatermelon(int amount) : base(amount, 0xC5D) + { + Weight = 5.0; + FillFactor = 5; + } + + public SmallWatermelon(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xc72, 0xc73)] + public class Squash : Food + { + [Constructible] + public Squash() : this(1) + { + } + + [Constructible] + public Squash(int amount) : base(amount, 0xc72) + { + Weight = 1.0; + FillFactor = 1; + } + + public Squash(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0xc79, 0xc7a)] + public class Cantaloupe : Food + { + [Constructible] + public Cantaloupe() : this(1) + { + } + + [Constructible] + public Cantaloupe(int amount) : base(amount, 0xc79) + { + Weight = 1.0; + FillFactor = 1; + } + + public Cantaloupe(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Food/Vegetables.cs b/Scripts/Items/Food/Vegetables.cs index 017c1d591..c951d2d0a 100644 --- a/Scripts/Items/Food/Vegetables.cs +++ b/Scripts/Items/Food/Vegetables.cs @@ -1,208 +1,214 @@ namespace Server.Items { - [FlippableAttribute( 0xc77, 0xc78 )] - public class Carrot : Food - { - [Constructible] - public Carrot() : this( 1 ) - { - } + [Flippable(0xc77, 0xc78)] + public class Carrot : Food + { + [Constructible] + public Carrot() : this(1) + { + } - [Constructible] - public Carrot( int amount ) : base( amount, 0xc78 ) - { - Weight = 1.0; - FillFactor = 1; - } + [Constructible] + public Carrot(int amount) : base(amount, 0xc78) + { + Weight = 1.0; + FillFactor = 1; + } - public Carrot( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Carrot(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [FlippableAttribute( 0xc7b, 0xc7c )] - public class Cabbage : Food - { - [Constructible] - public Cabbage() : this( 1 ) - { - } + int version = reader.ReadInt(); + } + } - [Constructible] - public Cabbage( int amount ) : base( amount, 0xc7b ) - { - Weight = 1.0; - FillFactor = 1; - } + [Flippable(0xc7b, 0xc7c)] + public class Cabbage : Food + { + [Constructible] + public Cabbage() : this(1) + { + } - public Cabbage( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public Cabbage(int amount) : base(amount, 0xc7b) + { + Weight = 1.0; + FillFactor = 1; + } - writer.Write( (int) 0 ); // version - } + public Cabbage(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } - [FlippableAttribute( 0xc6d, 0xc6e )] - public class Onion : Food - { - [Constructible] - public Onion() : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public Onion( int amount ) : base( amount, 0xc6d ) - { - Weight = 1.0; - FillFactor = 1; - } + int version = reader.ReadInt(); + } + } - public Onion( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Flippable(0xc6d, 0xc6e)] + public class Onion : Food + { + [Constructible] + public Onion() : this(1) + { + } - writer.Write( (int) 0 ); // version - } + [Constructible] + public Onion(int amount) : base(amount, 0xc6d) + { + Weight = 1.0; + FillFactor = 1; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public Onion(Serial serial) : base(serial) + { + } - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [FlippableAttribute( 0xc70, 0xc71 )] - public class Lettuce : Food - { - [Constructible] - public Lettuce() : this( 1 ) - { - } + writer.Write(0); // version + } - [Constructible] - public Lettuce( int amount ) : base( amount, 0xc70 ) - { - Weight = 1.0; - FillFactor = 1; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public Lettuce( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); + } + } - writer.Write( (int) 0 ); // version - } + [Flippable(0xc70, 0xc71)] + public class Lettuce : Food + { + [Constructible] + public Lettuce() : this(1) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public Lettuce(int amount) : base(amount, 0xc70) + { + Weight = 1.0; + FillFactor = 1; + } - int version = reader.ReadInt(); - } - } + public Lettuce(Serial serial) : base(serial) + { + } - [FlippableAttribute( 0xC6A, 0xC6B )] - public class Pumpkin : Food - { - [Constructible] - public Pumpkin() : this( 1 ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Constructible] - public Pumpkin( int amount ) : base( amount, 0xC6A ) - { - Weight = 1.0; - FillFactor = 8; - } + writer.Write(0); // version + } - public Pumpkin( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 1 ); // version - } + int version = reader.ReadInt(); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Flippable(0xC6A, 0xC6B)] + public class Pumpkin : Food + { + [Constructible] + public Pumpkin() : this(1) + { + } - int version = reader.ReadInt(); + [Constructible] + public Pumpkin(int amount) : base(amount, 0xC6A) + { + Weight = 1.0; + FillFactor = 8; + } - if ( version < 1 ) - { - if ( FillFactor == 4 ) - FillFactor = 8; + public Pumpkin(Serial serial) : base(serial) + { + } - if ( Weight == 5.0 ) - Weight = 1.0; - } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public class SmallPumpkin : Food - { - [Constructible] - public SmallPumpkin() : this( 1 ) - { - } + writer.Write(1); // version + } - [Constructible] - public SmallPumpkin( int amount ) : base( amount, 0xC6C ) - { - Weight = 1.0; - FillFactor = 8; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public SmallPumpkin( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); - writer.Write( (int) 0 ); // version - } + if (version < 1) + { + if (FillFactor == 4) + FillFactor = 8; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (Weight == 5.0) + Weight = 1.0; + } + } + } - int version = reader.ReadInt(); - } - } + public class SmallPumpkin : Food + { + [Constructible] + public SmallPumpkin() : this(1) + { + } + + [Constructible] + public SmallPumpkin(int amount) : base(amount, 0xC6C) + { + Weight = 1.0; + FillFactor = 8; + } + + public SmallPumpkin(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Games/Backgammon.cs b/Scripts/Items/Games/Backgammon.cs index c22cbdf7a..e25bba5b3 100644 --- a/Scripts/Items/Games/Backgammon.cs +++ b/Scripts/Items/Games/Backgammon.cs @@ -1,52 +1,51 @@ namespace Server.Items { - [Flippable( 0xE1C, 0xFAD )] - public class Backgammon : BaseBoard - { - [Constructible] - public Backgammon() : base( 0xE1C ) - { - } + [Flippable(0xE1C, 0xFAD)] + public class Backgammon : BaseBoard + { + [Constructible] + public Backgammon() : base(0xE1C) + { + } - public override void CreatePieces() - { - for ( int i = 0; i < 5; i++ ) - { - CreatePiece( new PieceWhiteChecker( this ), 42, ( 17 * i ) + 6 ); - CreatePiece( new PieceBlackChecker( this ), 42, ( 17 * i ) + 119 ); + public Backgammon(Serial serial) : base(serial) + { + } - CreatePiece( new PieceBlackChecker( this ), 142, ( 17 * i ) + 6 ); - CreatePiece( new PieceWhiteChecker( this ), 142, ( 17 * i ) + 119 ); - } + public override void CreatePieces() + { + for (int i = 0; i < 5; i++) + { + CreatePiece(new PieceWhiteChecker(this), 42, 17 * i + 6); + CreatePiece(new PieceBlackChecker(this), 42, 17 * i + 119); - for ( int i = 0; i < 3; i++ ) - { - CreatePiece( new PieceBlackChecker( this ), 108, ( 17 * i ) + 6 ); - CreatePiece( new PieceWhiteChecker( this ), 108, ( 17 * i ) + 153 ); - } + CreatePiece(new PieceBlackChecker(this), 142, 17 * i + 6); + CreatePiece(new PieceWhiteChecker(this), 142, 17 * i + 119); + } - for ( int i = 0; i < 2; i++ ) - { - CreatePiece( new PieceWhiteChecker( this ), 223, ( 17 * i ) + 6 ); - CreatePiece( new PieceBlackChecker( this ), 223, ( 17 * i ) + 170 ); - } - } + for (int i = 0; i < 3; i++) + { + CreatePiece(new PieceBlackChecker(this), 108, 17 * i + 6); + CreatePiece(new PieceWhiteChecker(this), 108, 17 * i + 153); + } - public Backgammon( Serial serial ) : base( serial ) - { - } + for (int i = 0; i < 2; i++) + { + CreatePiece(new PieceWhiteChecker(this), 223, 17 * i + 6); + CreatePiece(new PieceBlackChecker(this), 223, 17 * i + 170); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/BaseBoard.cs b/Scripts/Items/Games/BaseBoard.cs index 89eaa1583..32a8dc5fe 100644 --- a/Scripts/Items/Games/BaseBoard.cs +++ b/Scripts/Items/Games/BaseBoard.cs @@ -1,154 +1,149 @@ using System; using System.Collections.Generic; -using Server.Multis; -using Server.Network; using Server.ContextMenus; using Server.Gumps; +using Server.Multis; +using Server.Network; namespace Server.Items { - public abstract class BaseBoard : Container, ISecurable - { - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + public abstract class BaseBoard : Container, ISecurable + { + public BaseBoard(int itemID) : base(itemID) + { + CreatePieces(); - public BaseBoard( int itemID ) : base( itemID ) - { - CreatePieces(); + Weight = 5.0; + } - Weight = 5.0; - } + public BaseBoard(Serial serial) : base(serial) + { + } - public abstract void CreatePieces(); + public override bool DisplaysContent => false; // Do not display (x items, y stones) - public void Reset() - { - for ( int i = Items.Count - 1; i >= 0; --i ) - { - if ( i < Items.Count ) - Items[i].Delete(); - } + public override bool IsDecoContainer => false; - CreatePieces(); - } + public override TimeSpan DecayTime => TimeSpan.FromDays(1.0); - public void CreatePiece( BasePiece piece, int x, int y ) - { - AddItem( piece ); - piece.Location = new Point3D( x, y, 0 ); - } + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - public override bool DisplaysContent => false; // Do not display (x items, y stones) + public abstract void CreatePieces(); - public override bool IsDecoContainer => false; + public void Reset() + { + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + Items[i].Delete(); - public BaseBoard( Serial serial ) : base( serial ) - { - } + CreatePieces(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); // version + public void CreatePiece(BasePiece piece, int x, int y) + { + AddItem(piece); + piece.Location = new Point3D(x, y, 0); + } - writer.Write( (int)Level ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + writer.Write((int)Level); + } - if ( version == 1 ) - Level = (SecureLevel)reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 5.0; - } + if (version == 1) + Level = (SecureLevel)reader.ReadInt(); - public override TimeSpan DecayTime => TimeSpan.FromDays( 1.0 ); + if (Weight == 1.0) + Weight = 5.0; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - return ( dropped is BasePiece piece && piece.Board == this && base.OnDragDrop( from, dropped ) ); - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + return dropped is BasePiece piece && piece.Board == this && base.OnDragDrop(from, dropped); + } - public override bool OnDragDropInto( Mobile from, Item dropped, Point3D point ) - { - if ( dropped is BasePiece piece && piece.Board == this && base.OnDragDropInto( from, dropped, point ) ) - { - Packet p = new PlaySound( 0x127, GetWorldLocation() ); + public override bool OnDragDropInto(Mobile from, Item dropped, Point3D point) + { + if (dropped is BasePiece piece && piece.Board == this && base.OnDragDropInto(from, dropped, point)) + { + Packet p = new PlaySound(0x127, GetWorldLocation()); - p.Acquire(); + p.Acquire(); - if ( RootParent == from ) - { - from.Send( p ); - } - else - { - foreach ( NetState state in GetClientsInRange( 2 ) ) - state.Send( p ); - } + if (RootParent == from) + from.Send(p); + else + foreach (NetState state in GetClientsInRange(2)) + state.Send(p); - p.Release(); + p.Release(); - return true; - } + return true; + } - return false; - } + return false; + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( ValidateDefault( from, this ) ) - list.Add( new DefaultEntry( from, this ) ); + if (ValidateDefault(from, this)) + list.Add(new DefaultEntry(from, this)); - SetSecureLevelEntry.AddTo( from, this, list ); - } + SetSecureLevelEntry.AddTo(from, this, list); + } - public static bool ValidateDefault( Mobile from, BaseBoard board ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; + public static bool ValidateDefault(Mobile from, BaseBoard board) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; - if ( !from.Alive ) - return false; + if (!from.Alive) + return false; - if ( board.IsChildOf( from.Backpack ) ) - return true; + if (board.IsChildOf(from.Backpack)) + return true; - object root = board.RootParent; + object root = board.RootParent; - if ( root is Mobile && root != from ) - return false; + if (root is Mobile && root != from) + return false; - if ( board.Deleted || board.Map != from.Map || !from.InRange( board.GetWorldLocation(), 1 ) ) - return false; + if (board.Deleted || board.Map != from.Map || !from.InRange(board.GetWorldLocation(), 1)) + return false; - BaseHouse house = BaseHouse.FindHouseAt( board ); + BaseHouse house = BaseHouse.FindHouseAt(board); - return ( house != null && house.IsOwner( from ) ); - } + return house != null && house.IsOwner(from); + } - public class DefaultEntry : ContextMenuEntry - { - private Mobile m_From; - private BaseBoard m_Board; + public class DefaultEntry : ContextMenuEntry + { + private BaseBoard m_Board; + private Mobile m_From; - public DefaultEntry( Mobile from, BaseBoard board ) : base( 6162, from.AccessLevel >= AccessLevel.GameMaster ? -1 : 1 ) - { - m_From = from; - m_Board = board; - } + public DefaultEntry(Mobile from, BaseBoard board) : base(6162, + from.AccessLevel >= AccessLevel.GameMaster ? -1 : 1) + { + m_From = from; + m_Board = board; + } - public override void OnClick() - { - if ( ValidateDefault( m_From, m_Board ) ) - m_Board.Reset(); - } - } - } -} + public override void OnClick() + { + if (ValidateDefault(m_From, m_Board)) + m_Board.Reset(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/BasePiece.cs b/Scripts/Items/Games/BasePiece.cs index 0351fe2f5..be88dbe7e 100644 --- a/Scripts/Items/Games/BasePiece.cs +++ b/Scripts/Items/Games/BasePiece.cs @@ -1,94 +1,95 @@ namespace Server.Items { - public class BasePiece : Item - { - public BaseBoard Board { get; set; } + public class BasePiece : Item + { + public BasePiece(int itemID, BaseBoard board) : base(itemID) + { + Board = board; + } - public override bool IsVirtualItem => true; + public BasePiece(Serial serial) : base(serial) + { + } - public BasePiece( int itemID, BaseBoard board ) : base( itemID ) - { - Board = board; - } + public BaseBoard Board{ get; set; } - public BasePiece( Serial serial ) : base( serial ) - { - } + public override bool IsVirtualItem => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CanTarget => false; - writer.Write( (int) 0 ); - writer.Write( Board ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); + writer.Write(Board); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - Board = (BaseBoard)reader.ReadItem(); + int version = reader.ReadInt(); - if ( Board == null || Parent == null ) - Delete(); + switch (version) + { + case 0: + { + Board = (BaseBoard)reader.ReadItem(); - break; - } - } - } + if (Board == null || Parent == null) + Delete(); - public override void OnSingleClick( Mobile from ) - { - if ( Board == null || Board.Deleted ) - Delete(); - else if ( !IsChildOf( Board ) ) - Board.DropItem( this ); - else - base.OnSingleClick( from ); - } + break; + } + } + } - public override bool OnDragLift( Mobile from ) - { - if ( Board == null || Board.Deleted ) - { - Delete(); - return false; - } + public override void OnSingleClick(Mobile from) + { + if (Board == null || Board.Deleted) + Delete(); + else if (!IsChildOf(Board)) + Board.DropItem(this); + else + base.OnSingleClick(from); + } - if ( !IsChildOf( Board ) ) - { - Board.DropItem( this ); - return false; - } - return true; - } + public override bool OnDragLift(Mobile from) + { + if (Board == null || Board.Deleted) + { + Delete(); + return false; + } - public override bool CanTarget => false; + if (!IsChildOf(Board)) + { + Board.DropItem(this); + return false; + } - public override bool DropToMobile( Mobile from, Mobile target, Point3D p ) - { - return false; - } + return true; + } - public override bool DropToItem( Mobile from, Item target, Point3D p ) - { - return ( target == Board && p.X != -1 && p.Y != -1 && base.DropToItem( from, target, p ) ); - } + public override bool DropToMobile(Mobile from, Mobile target, Point3D p) + { + return false; + } - public override bool DropToWorld( Mobile from, Point3D p ) - { - return false; - } + public override bool DropToItem(Mobile from, Item target, Point3D p) + { + return target == Board && p.X != -1 && p.Y != -1 && base.DropToItem(from, target, p); + } - public override int GetLiftSound( Mobile from ) - { - return -1; - } - } -} + public override bool DropToWorld(Mobile from, Point3D p) + { + return false; + } + + public override int GetLiftSound(Mobile from) + { + return -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/CheckerBoard.cs b/Scripts/Items/Games/CheckerBoard.cs index 7d03588c1..80d9ff6a1 100644 --- a/Scripts/Items/Games/CheckerBoard.cs +++ b/Scripts/Items/Games/CheckerBoard.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class CheckerBoard : BaseBoard - { - public override int LabelNumber => 1016449; // a checker board + public class CheckerBoard : BaseBoard + { + [Constructible] + public CheckerBoard() : base(0xFA6) + { + } - [Constructible] - public CheckerBoard() : base( 0xFA6 ) - { - } + public CheckerBoard(Serial serial) : base(serial) + { + } - public override void CreatePieces() - { - for ( int i = 0; i < 4; i++ ) - { - CreatePiece( new PieceWhiteChecker( this ), ( 50 * i ) + 45, 25 ); - CreatePiece( new PieceWhiteChecker( this ), ( 50 * i ) + 70, 50 ); - CreatePiece( new PieceWhiteChecker( this ), ( 50 * i ) + 45, 75 ); - CreatePiece( new PieceBlackChecker( this ), ( 50 * i ) + 70, 150 ); - CreatePiece( new PieceBlackChecker( this ), ( 50 * i ) + 45, 175 ); - CreatePiece( new PieceBlackChecker( this ), ( 50 * i ) + 70, 200 ); - } - } + public override int LabelNumber => 1016449; // a checker board - public CheckerBoard( Serial serial ) : base( serial ) - { - } + public override void CreatePieces() + { + for (int i = 0; i < 4; i++) + { + CreatePiece(new PieceWhiteChecker(this), 50 * i + 45, 25); + CreatePiece(new PieceWhiteChecker(this), 50 * i + 70, 50); + CreatePiece(new PieceWhiteChecker(this), 50 * i + 45, 75); + CreatePiece(new PieceBlackChecker(this), 50 * i + 70, 150); + CreatePiece(new PieceBlackChecker(this), 50 * i + 45, 175); + CreatePiece(new PieceBlackChecker(this), 50 * i + 70, 200); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/CheckersPieces.cs b/Scripts/Items/Games/CheckersPieces.cs index 67ee12eb5..52cf6072d 100644 --- a/Scripts/Items/Games/CheckersPieces.cs +++ b/Scripts/Items/Games/CheckersPieces.cs @@ -1,52 +1,52 @@ namespace Server.Items { - public class PieceWhiteChecker : BasePiece - { - public override string DefaultName => "white checker"; + public class PieceWhiteChecker : BasePiece + { + public PieceWhiteChecker(BaseBoard board) : base(0x3584, board) + { + } - public PieceWhiteChecker( BaseBoard board ) : base( 0x3584, board ) - { - } + public PieceWhiteChecker(Serial serial) : base(serial) + { + } - public PieceWhiteChecker( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white checker"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackChecker : BasePiece - { - public override string DefaultName => "black checker"; + public class PieceBlackChecker : BasePiece + { + public PieceBlackChecker(BaseBoard board) : base(0x358B, board) + { + } - public PieceBlackChecker( BaseBoard board ) : base( 0x358B, board ) - { - } + public PieceBlackChecker(Serial serial) : base(serial) + { + } - public PieceBlackChecker( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black checker"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Games/ChessPieces.cs b/Scripts/Items/Games/ChessPieces.cs index b692b19c3..3f422780e 100644 --- a/Scripts/Items/Games/ChessPieces.cs +++ b/Scripts/Items/Games/ChessPieces.cs @@ -1,302 +1,302 @@ namespace Server.Items { - public class PieceWhiteKing : BasePiece - { - public override string DefaultName => "white king"; + public class PieceWhiteKing : BasePiece + { + public PieceWhiteKing(BaseBoard board) : base(0x3587, board) + { + } - public PieceWhiteKing( BaseBoard board ) : base( 0x3587, board ) - { - } + public PieceWhiteKing(Serial serial) : base(serial) + { + } - public PieceWhiteKing( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white king"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackKing : BasePiece - { - public override string DefaultName => "black king"; + public class PieceBlackKing : BasePiece + { + public PieceBlackKing(BaseBoard board) : base(0x358E, board) + { + } - public PieceBlackKing( BaseBoard board ) : base( 0x358E, board ) - { - } + public PieceBlackKing(Serial serial) : base(serial) + { + } - public PieceBlackKing( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black king"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceWhiteQueen : BasePiece - { - public override string DefaultName => "white queen"; + public class PieceWhiteQueen : BasePiece + { + public PieceWhiteQueen(BaseBoard board) : base(0x358A, board) + { + } - public PieceWhiteQueen( BaseBoard board ) : base( 0x358A, board ) - { - } + public PieceWhiteQueen(Serial serial) : base(serial) + { + } - public PieceWhiteQueen( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white queen"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackQueen : BasePiece - { - public override string DefaultName => "black queen"; + public class PieceBlackQueen : BasePiece + { + public PieceBlackQueen(BaseBoard board) : base(0x3591, board) + { + } - public PieceBlackQueen( BaseBoard board ) : base( 0x3591, board ) - { - } + public PieceBlackQueen(Serial serial) : base(serial) + { + } - public PieceBlackQueen( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black queen"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceWhiteRook : BasePiece - { - public override string DefaultName => "white rook"; + public class PieceWhiteRook : BasePiece + { + public PieceWhiteRook(BaseBoard board) : base(0x3586, board) + { + } - public PieceWhiteRook( BaseBoard board ) : base( 0x3586, board ) - { - } + public PieceWhiteRook(Serial serial) : base(serial) + { + } - public PieceWhiteRook( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white rook"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackRook : BasePiece - { - public override string DefaultName => "black rook"; + public class PieceBlackRook : BasePiece + { + public PieceBlackRook(BaseBoard board) : base(0x358D, board) + { + } - public PieceBlackRook( BaseBoard board ) : base( 0x358D, board ) - { - } + public PieceBlackRook(Serial serial) : base(serial) + { + } - public PieceBlackRook( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black rook"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceWhiteBishop : BasePiece - { - public override string DefaultName => "white bishop"; + public class PieceWhiteBishop : BasePiece + { + public PieceWhiteBishop(BaseBoard board) : base(0x3585, board) + { + } - public PieceWhiteBishop( BaseBoard board ) : base( 0x3585, board ) - { - } + public PieceWhiteBishop(Serial serial) : base(serial) + { + } - public PieceWhiteBishop( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white bishop"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackBishop : BasePiece - { - public override string DefaultName => "black bishop"; + public class PieceBlackBishop : BasePiece + { + public PieceBlackBishop(BaseBoard board) : base(0x358C, board) + { + } - public PieceBlackBishop( BaseBoard board ) : base( 0x358C, board ) - { - } + public PieceBlackBishop(Serial serial) : base(serial) + { + } - public PieceBlackBishop( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black bishop"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceWhiteKnight : BasePiece - { - public override string DefaultName => "white knight"; + public class PieceWhiteKnight : BasePiece + { + public PieceWhiteKnight(BaseBoard board) : base(0x3588, board) + { + } - public PieceWhiteKnight( BaseBoard board ) : base( 0x3588, board ) - { - } + public PieceWhiteKnight(Serial serial) : base(serial) + { + } - public PieceWhiteKnight( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white knight"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackKnight : BasePiece - { - public override string DefaultName => "black knight"; + public class PieceBlackKnight : BasePiece + { + public PieceBlackKnight(BaseBoard board) : base(0x358F, board) + { + } - public PieceBlackKnight( BaseBoard board ) : base( 0x358F, board ) - { - } + public PieceBlackKnight(Serial serial) : base(serial) + { + } - public PieceBlackKnight( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black knight"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceWhitePawn : BasePiece - { - public override string DefaultName => "white pawn"; + public class PieceWhitePawn : BasePiece + { + public PieceWhitePawn(BaseBoard board) : base(0x3589, board) + { + } - public PieceWhitePawn( BaseBoard board ) : base( 0x3589, board ) - { - } + public PieceWhitePawn(Serial serial) : base(serial) + { + } - public PieceWhitePawn( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "white pawn"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class PieceBlackPawn : BasePiece - { - public override string DefaultName => "black pawn"; + public class PieceBlackPawn : BasePiece + { + public PieceBlackPawn(BaseBoard board) : base(0x3590, board) + { + } - public PieceBlackPawn( BaseBoard board ) : base( 0x3590, board ) - { - } + public PieceBlackPawn(Serial serial) : base(serial) + { + } - public PieceBlackPawn( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "black pawn"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Chessboard.cs b/Scripts/Items/Games/Chessboard.cs index 764effe7d..6078378e9 100644 --- a/Scripts/Items/Games/Chessboard.cs +++ b/Scripts/Items/Games/Chessboard.cs @@ -1,66 +1,66 @@ namespace Server.Items { - public class Chessboard : BaseBoard - { - public override int LabelNumber => 1016450; // a chessboard + public class Chessboard : BaseBoard + { + [Constructible] + public Chessboard() : base(0xFA6) + { + } - [Constructible] - public Chessboard() : base( 0xFA6 ) - { - } + public Chessboard(Serial serial) : base(serial) + { + } - public override void CreatePieces() - { - for ( int i = 0; i < 8; i++ ) - { - CreatePiece( new PieceBlackPawn( this ), 67, ( 25 * i ) + 17 ); - CreatePiece( new PieceWhitePawn( this ), 192, ( 25 * i ) + 17 ); - } + public override int LabelNumber => 1016450; // a chessboard - // Rook - CreatePiece( new PieceBlackRook( this ), 42, 5 ); - CreatePiece( new PieceBlackRook( this ), 42, 180 ); + public override void CreatePieces() + { + for (int i = 0; i < 8; i++) + { + CreatePiece(new PieceBlackPawn(this), 67, 25 * i + 17); + CreatePiece(new PieceWhitePawn(this), 192, 25 * i + 17); + } - CreatePiece( new PieceWhiteRook( this ), 216, 5 ); - CreatePiece( new PieceWhiteRook( this ), 216, 180 ); + // Rook + CreatePiece(new PieceBlackRook(this), 42, 5); + CreatePiece(new PieceBlackRook(this), 42, 180); - // Knight - CreatePiece( new PieceBlackKnight( this ), 42, 30 ); - CreatePiece( new PieceBlackKnight( this ), 42, 155 ); + CreatePiece(new PieceWhiteRook(this), 216, 5); + CreatePiece(new PieceWhiteRook(this), 216, 180); - CreatePiece( new PieceWhiteKnight( this ), 216, 30 ); - CreatePiece( new PieceWhiteKnight( this ), 216, 155 ); + // Knight + CreatePiece(new PieceBlackKnight(this), 42, 30); + CreatePiece(new PieceBlackKnight(this), 42, 155); - // Bishop - CreatePiece( new PieceBlackBishop( this ), 42, 55 ); - CreatePiece( new PieceBlackBishop( this ), 42, 130 ); + CreatePiece(new PieceWhiteKnight(this), 216, 30); + CreatePiece(new PieceWhiteKnight(this), 216, 155); - CreatePiece( new PieceWhiteBishop( this ), 216, 55 ); - CreatePiece( new PieceWhiteBishop( this ), 216, 130 ); + // Bishop + CreatePiece(new PieceBlackBishop(this), 42, 55); + CreatePiece(new PieceBlackBishop(this), 42, 130); - // Queen - CreatePiece( new PieceBlackQueen( this ), 42, 105 ); - CreatePiece( new PieceWhiteQueen( this ), 216, 105 ); + CreatePiece(new PieceWhiteBishop(this), 216, 55); + CreatePiece(new PieceWhiteBishop(this), 216, 130); - // King - CreatePiece( new PieceBlackKing( this ), 42, 80 ); - CreatePiece( new PieceWhiteKing( this ), 216, 80 ); - } + // Queen + CreatePiece(new PieceBlackQueen(this), 42, 105); + CreatePiece(new PieceWhiteQueen(this), 216, 105); - public Chessboard( Serial serial ) : base( serial ) - { - } + // King + CreatePiece(new PieceBlackKing(this), 42, 80); + CreatePiece(new PieceWhiteKing(this), 216, 80); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Dices.cs b/Scripts/Items/Games/Dices.cs index ca4c28ba3..dad2dc13b 100644 --- a/Scripts/Items/Games/Dices.cs +++ b/Scripts/Items/Games/Dices.cs @@ -2,50 +2,50 @@ using Server.Network; namespace Server.Items { - public class Dices : Item, ITelekinesisable - { - [Constructible] - public Dices() : base( 0xFA7 ) - { - Weight = 1.0; - } + public class Dices : Item, ITelekinesisable + { + [Constructible] + public Dices() : base(0xFA7) + { + Weight = 1.0; + } - public Dices( Serial serial ) : base( serial ) - { - } + public Dices(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - return; + public void OnTelekinesis(Mobile from) + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x376A, 9, 32, 5022); + Effects.PlaySound(Location, Map, 0x1F5); - Roll( from ); - } + Roll(from); + } - public void OnTelekinesis( Mobile from ) - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5022 ); - Effects.PlaySound( Location, Map, 0x1F5 ); + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + return; - Roll( from ); - } + Roll(from); + } - public void Roll( Mobile from ) - { - PublicOverheadMessage( MessageType.Regular, 0, false, - $"*{from.Name} rolls {Utility.Random(1, 6)}, {Utility.Random(1, 6)}*"); - } + public void Roll(Mobile from) + { + PublicOverheadMessage(MessageType.Regular, 0, false, + $"*{from.Name} rolls {Utility.Random(1, 6)}, {Utility.Random(1, 6)}*"); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongDealerIndicator.cs b/Scripts/Items/Games/Mahjong/MahjongDealerIndicator.cs index eec181f5f..d657b2231 100644 --- a/Scripts/Items/Games/Mahjong/MahjongDealerIndicator.cs +++ b/Scripts/Items/Games/Mahjong/MahjongDealerIndicator.cs @@ -1,64 +1,64 @@ namespace Server.Engines.Mahjong { - public class MahjongDealerIndicator - { - public static MahjongPieceDim GetDimensions( Point2D position, MahjongPieceDirection direction ) - { - if ( direction == MahjongPieceDirection.Up || direction == MahjongPieceDirection.Down ) - return new MahjongPieceDim( position, 40, 20 ); - return new MahjongPieceDim( position, 20, 40 ); - } + public class MahjongDealerIndicator + { + public MahjongDealerIndicator(MahjongGame game, Point2D position, MahjongPieceDirection direction, MahjongWind wind) + { + Game = game; + Position = position; + Direction = direction; + Wind = wind; + } - public MahjongGame Game { get; } + public MahjongDealerIndicator(MahjongGame game, GenericReader reader) + { + Game = game; - public Point2D Position { get; private set; } + int version = reader.ReadInt(); - public MahjongPieceDirection Direction { get; private set; } + Position = reader.ReadPoint2D(); + Direction = (MahjongPieceDirection)reader.ReadInt(); + Wind = (MahjongWind)reader.ReadInt(); + } - public MahjongWind Wind { get; private set; } + public MahjongGame Game{ get; } - public MahjongDealerIndicator( MahjongGame game, Point2D position, MahjongPieceDirection direction, MahjongWind wind ) - { - Game = game; - Position = position; - Direction = direction; - Wind = wind; - } + public Point2D Position{ get; private set; } - public MahjongPieceDim Dimensions => GetDimensions( Position, Direction ); + public MahjongPieceDirection Direction{ get; private set; } - public void Move( Point2D position, MahjongPieceDirection direction, MahjongWind wind ) - { - MahjongPieceDim dim = GetDimensions( position, direction ); + public MahjongWind Wind{ get; private set; } - if ( !dim.IsValid() ) - return; + public MahjongPieceDim Dimensions => GetDimensions(Position, Direction); - Position = position; - Direction = direction; - Wind = wind; + public static MahjongPieceDim GetDimensions(Point2D position, MahjongPieceDirection direction) + { + if (direction == MahjongPieceDirection.Up || direction == MahjongPieceDirection.Down) + return new MahjongPieceDim(position, 40, 20); + return new MahjongPieceDim(position, 20, 40); + } - Game.Players.SendGeneralPacket( true, true ); - } + public void Move(Point2D position, MahjongPieceDirection direction, MahjongWind wind) + { + MahjongPieceDim dim = GetDimensions(position, direction); - public void Save( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version + if (!dim.IsValid()) + return; - writer.Write( Position ); - writer.Write( (int) Direction ); - writer.Write( (int) Wind ); - } + Position = position; + Direction = direction; + Wind = wind; - public MahjongDealerIndicator( MahjongGame game, GenericReader reader ) - { - Game = game; + Game.Players.SendGeneralPacket(true, true); + } - int version = reader.ReadInt(); + public void Save(GenericWriter writer) + { + writer.Write(0); // version - Position = reader.ReadPoint2D(); - Direction = (MahjongPieceDirection) reader.ReadInt(); - Wind = (MahjongWind) reader.ReadInt(); - } - } -} + writer.Write(Position); + writer.Write((int)Direction); + writer.Write((int)Wind); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongDices.cs b/Scripts/Items/Games/Mahjong/MahjongDices.cs index 5a61fe601..d23ac82b2 100644 --- a/Scripts/Items/Games/Mahjong/MahjongDices.cs +++ b/Scripts/Items/Games/Mahjong/MahjongDices.cs @@ -1,47 +1,48 @@ namespace Server.Engines.Mahjong { - public class MahjongDices - { - public MahjongGame Game { get; } + public class MahjongDices + { + public MahjongDices(MahjongGame game) + { + Game = game; + First = Utility.Random(1, 6); + Second = Utility.Random(1, 6); + } - public int First { get; private set; } + public MahjongDices(MahjongGame game, GenericReader reader) + { + Game = game; - public int Second { get; private set; } + int version = reader.ReadInt(); - public MahjongDices( MahjongGame game ) - { - Game = game; - First = Utility.Random( 1, 6 ); - Second = Utility.Random( 1, 6 ); - } + First = reader.ReadInt(); + Second = reader.ReadInt(); + } - public void RollDices( Mobile from ) - { - First = Utility.Random( 1, 6 ); - Second = Utility.Random( 1, 6 ); + public MahjongGame Game{ get; } - Game.Players.SendGeneralPacket( true, true ); + public int First{ get; private set; } - if ( from != null ) - Game.Players.SendLocalizedMessage( 1062695, $"{from.Name}\t{First}\t{Second}"); // ~1_name~ rolls the dice and gets a ~2_number~ and a ~3_number~! - } + public int Second{ get; private set; } - public void Save( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version + public void RollDices(Mobile from) + { + First = Utility.Random(1, 6); + Second = Utility.Random(1, 6); - writer.Write( First ); - writer.Write( Second ); - } + Game.Players.SendGeneralPacket(true, true); - public MahjongDices( MahjongGame game, GenericReader reader ) - { - Game = game; + if (from != null) + Game.Players.SendLocalizedMessage(1062695, + $"{from.Name}\t{First}\t{Second}"); // ~1_name~ rolls the dice and gets a ~2_number~ and a ~3_number~! + } - int version = reader.ReadInt(); + public void Save(GenericWriter writer) + { + writer.Write(0); // version - First = reader.ReadInt(); - Second = reader.ReadInt(); - } - } -} + writer.Write(First); + writer.Write(Second); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongEnums.cs b/Scripts/Items/Games/Mahjong/MahjongEnums.cs index 73df5f04e..633bf8968 100644 --- a/Scripts/Items/Games/Mahjong/MahjongEnums.cs +++ b/Scripts/Items/Games/Mahjong/MahjongEnums.cs @@ -1,56 +1,56 @@ namespace Server.Engines.Mahjong { - public enum MahjongPieceDirection - { - Up, - Left, - Down, - Right - } + public enum MahjongPieceDirection + { + Up, + Left, + Down, + Right + } - public enum MahjongWind - { - North, - East, - South, - West - } + public enum MahjongWind + { + North, + East, + South, + West + } - public enum MahjongTileType - { - Dagger1 = 1, - Dagger2, - Dagger3, - Dagger4, - Dagger5, - Dagger6, - Dagger7, - Dagger8, - Dagger9, - Gem1, - Gem2, - Gem3, - Gem4, - Gem5, - Gem6, - Gem7, - Gem8, - Gem9, - Number1, - Number2, - Number3, - Number4, - Number5, - Number6, - Number7, - Number8, - Number9, - North, - East, - South, - West, - Green, - Red, - White - } + public enum MahjongTileType + { + Dagger1 = 1, + Dagger2, + Dagger3, + Dagger4, + Dagger5, + Dagger6, + Dagger7, + Dagger8, + Dagger9, + Gem1, + Gem2, + Gem3, + Gem4, + Gem5, + Gem6, + Gem7, + Gem8, + Gem9, + Number1, + Number2, + Number3, + Number4, + Number5, + Number6, + Number7, + Number8, + Number9, + North, + East, + South, + West, + Green, + Red, + White + } } \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongGame.cs b/Scripts/Items/Games/Mahjong/MahjongGame.cs index c3db296d5..d6cfe7103 100644 --- a/Scripts/Items/Games/Mahjong/MahjongGame.cs +++ b/Scripts/Items/Games/Mahjong/MahjongGame.cs @@ -1,293 +1,298 @@ using System; using System.Collections.Generic; +using Server.ContextMenus; using Server.Gumps; using Server.Multis; -using Server.ContextMenus; namespace Server.Engines.Mahjong { - public class MahjongGame : Item, ISecurable - { - public const int MaxPlayers = 4; - public const int BaseScore = 30000; + public class MahjongGame : Item, ISecurable + { + public const int MaxPlayers = 4; + public const int BaseScore = 30000; + private DateTime m_LastReset; + + private bool m_ShowScores; + private bool m_SpectatorVision; + + [Constructible] + public MahjongGame() : base(0xFAA) + { + Weight = 5.0; + + BuildWalls(); + DealerIndicator = + new MahjongDealerIndicator(this, new Point2D(300, 300), MahjongPieceDirection.Up, MahjongWind.North); + WallBreakIndicator = new MahjongWallBreakIndicator(this, new Point2D(335, 335)); + Dices = new MahjongDices(this); + Players = new MahjongPlayers(this, MaxPlayers, BaseScore); + m_LastReset = DateTime.UtcNow; + Level = SecureLevel.CoOwners; + } - private bool m_ShowScores; - private bool m_SpectatorVision; - private DateTime m_LastReset; + public MahjongGame(Serial serial) : base(serial) + { + } - public MahjongTile[] Tiles { get; private set; } + public MahjongTile[] Tiles{ get; private set; } - public MahjongDealerIndicator DealerIndicator { get; private set; } + public MahjongDealerIndicator DealerIndicator{ get; private set; } - public MahjongWallBreakIndicator WallBreakIndicator { get; private set; } + public MahjongWallBreakIndicator WallBreakIndicator{ get; private set; } - public MahjongDices Dices { get; private set; } + public MahjongDices Dices{ get; private set; } - public MahjongPlayers Players { get; private set; } + public MahjongPlayers Players{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public bool ShowScores + { + get => m_ShowScores; + set + { + if (m_ShowScores == value) + return; - [CommandProperty( AccessLevel.GameMaster )] - public bool ShowScores - { - get => m_ShowScores; - set - { - if ( m_ShowScores == value ) - return; + m_ShowScores = value; - m_ShowScores = value; + if (value) + Players.SendPlayersPacket(true, true); - if ( value ) - Players.SendPlayersPacket( true, true ); + Players.SendGeneralPacket(true, true); - Players.SendGeneralPacket( true, true ); + Players.SendLocalizedMessage(value ? 1062777 : 1062778); // The dealer has enabled/disabled score display. + } + } - Players.SendLocalizedMessage( value ? 1062777 : 1062778 ); // The dealer has enabled/disabled score display. - } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool SpectatorVision + { + get => m_SpectatorVision; + set + { + if (m_SpectatorVision == value) + return; - [CommandProperty( AccessLevel.GameMaster )] - public bool SpectatorVision - { - get => m_SpectatorVision; - set - { - if ( m_SpectatorVision == value ) - return; + m_SpectatorVision = value; - m_SpectatorVision = value; + if (Players.IsInGamePlayer(Players.DealerPosition)) + Players.Dealer.Send(new MahjongGeneralInfo(this)); - if ( Players.IsInGamePlayer( Players.DealerPosition ) ) - Players.Dealer.Send( new MahjongGeneralInfo( this ) ); + Players.SendTilesPacket(false, true); - Players.SendTilesPacket( false, true ); + Players.SendLocalizedMessage(value ? 1062715 : 1062716); // The dealer has enabled/disabled Spectator Vision. - Players.SendLocalizedMessage( value ? 1062715 : 1062716 ); // The dealer has enabled/disabled Spectator Vision. + InvalidateProperties(); + } + } - InvalidateProperties(); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - [Constructible] - public MahjongGame() : base( 0xFAA ) - { - Weight = 5.0; + private void BuildHorizontalWall(ref int index, int x, int y, int stackLevel, MahjongPieceDirection direction, + MahjongTileTypeGenerator typeGenerator) + { + for (int i = 0; i < 17; i++) + { + Point2D position = new Point2D(x + i * 20, y); + Tiles[index + i] = new MahjongTile(this, index + i, typeGenerator.Next(), position, stackLevel, direction, + false); + } - BuildWalls(); - DealerIndicator = new MahjongDealerIndicator( this, new Point2D( 300, 300 ), MahjongPieceDirection.Up, MahjongWind.North ); - WallBreakIndicator = new MahjongWallBreakIndicator( this, new Point2D( 335, 335 ) ); - Dices = new MahjongDices( this ); - Players = new MahjongPlayers( this, MaxPlayers, BaseScore ); - m_LastReset = DateTime.UtcNow; - Level = SecureLevel.CoOwners; - } + index += 17; + } - public MahjongGame( Serial serial ) : base( serial ) - { - } + private void BuildVerticalWall(ref int index, int x, int y, int stackLevel, MahjongPieceDirection direction, + MahjongTileTypeGenerator typeGenerator) + { + for (int i = 0; i < 17; i++) + { + Point2D position = new Point2D(x, y + i * 20); + Tiles[index + i] = new MahjongTile(this, index + i, typeGenerator.Next(), position, stackLevel, direction, + false); + } - private void BuildHorizontalWall( ref int index, int x, int y, int stackLevel, MahjongPieceDirection direction, MahjongTileTypeGenerator typeGenerator ) - { - for ( int i = 0; i < 17; i++ ) - { - Point2D position = new Point2D( x + i*20, y ); - Tiles[index + i] = new MahjongTile( this, index + i, typeGenerator.Next(), position, stackLevel, direction, false ); - } + index += 17; + } - index += 17; - } + private void BuildWalls() + { + Tiles = new MahjongTile[17 * 8]; - private void BuildVerticalWall( ref int index, int x, int y, int stackLevel, MahjongPieceDirection direction, MahjongTileTypeGenerator typeGenerator ) - { - for ( int i = 0; i < 17; i++ ) - { - Point2D position = new Point2D( x, y + i*20 ); - Tiles[index + i] = new MahjongTile( this, index + i, typeGenerator.Next(), position, stackLevel, direction, false ); - } + MahjongTileTypeGenerator typeGenerator = new MahjongTileTypeGenerator(4); - index += 17; - } + int i = 0; - private void BuildWalls() - { - Tiles = new MahjongTile[17 * 8]; + BuildHorizontalWall(ref i, 165, 110, 0, MahjongPieceDirection.Up, typeGenerator); + BuildHorizontalWall(ref i, 165, 115, 1, MahjongPieceDirection.Up, typeGenerator); - MahjongTileTypeGenerator typeGenerator = new MahjongTileTypeGenerator( 4 ); + BuildVerticalWall(ref i, 530, 165, 0, MahjongPieceDirection.Left, typeGenerator); + BuildVerticalWall(ref i, 525, 165, 1, MahjongPieceDirection.Left, typeGenerator); - int i = 0; + BuildHorizontalWall(ref i, 165, 530, 0, MahjongPieceDirection.Down, typeGenerator); + BuildHorizontalWall(ref i, 165, 525, 1, MahjongPieceDirection.Down, typeGenerator); - BuildHorizontalWall( ref i, 165, 110, 0, MahjongPieceDirection.Up, typeGenerator ); - BuildHorizontalWall( ref i, 165, 115, 1, MahjongPieceDirection.Up, typeGenerator ); + BuildVerticalWall(ref i, 110, 165, 0, MahjongPieceDirection.Right, typeGenerator); + BuildVerticalWall(ref i, 115, 165, 1, MahjongPieceDirection.Right, typeGenerator); + } - BuildVerticalWall( ref i, 530, 165, 0, MahjongPieceDirection.Left, typeGenerator ); - BuildVerticalWall( ref i, 525, 165, 1, MahjongPieceDirection.Left, typeGenerator ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - BuildHorizontalWall( ref i, 165, 530, 0, MahjongPieceDirection.Down, typeGenerator ); - BuildHorizontalWall( ref i, 165, 525, 1, MahjongPieceDirection.Down, typeGenerator ); + if (m_SpectatorVision) + list.Add(1062717); // Spectator Vision Enabled + else + list.Add(1062718); // Spectator Vision Disabled + } - BuildVerticalWall( ref i, 110, 165, 0, MahjongPieceDirection.Right, typeGenerator ); - BuildVerticalWall( ref i, 115, 165, 1, MahjongPieceDirection.Right, typeGenerator ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + Players.CheckPlayers(); - if ( m_SpectatorVision ) - list.Add( 1062717 ); // Spectator Vision Enabled - else - list.Add( 1062718 ); // Spectator Vision Disabled - } + if (from.Alive && IsAccessibleTo(from) && Players.GetInGameMobiles(true, false).Count == 0) + list.Add(new ResetGameEntry(this)); - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + SetSecureLevelEntry.AddTo(from, this, list); + } - Players.CheckPlayers(); + public override void OnDoubleClick(Mobile from) + { + Players.CheckPlayers(); - if ( from.Alive && IsAccessibleTo( from ) && Players.GetInGameMobiles( true, false ).Count == 0 ) - list.Add( new ResetGameEntry( this ) ); + Players.Join(from); + } - SetSecureLevelEntry.AddTo( from, this, list ); - } + public void ResetGame(Mobile from) + { + if (DateTime.UtcNow - m_LastReset < TimeSpan.FromSeconds(5.0)) + return; - private class ResetGameEntry : ContextMenuEntry - { - private MahjongGame m_Game; + m_LastReset = DateTime.UtcNow; - public ResetGameEntry( MahjongGame game ) : base( 6162 ) - { - m_Game = game; - } + if (from != null) + Players.SendLocalizedMessage(1062771, from.Name); // ~1_name~ has reset the game. - public override void OnClick() - { - Mobile from = Owner.From; + Players.SendRelievePacket(true, true); - if ( from.CheckAlive() && !m_Game.Deleted && m_Game.IsAccessibleTo( from ) && m_Game.Players.GetInGameMobiles( true, false ).Count == 0 ) - m_Game.ResetGame( from ); - } - } + BuildWalls(); + DealerIndicator = + new MahjongDealerIndicator(this, new Point2D(300, 300), MahjongPieceDirection.Up, MahjongWind.North); + WallBreakIndicator = new MahjongWallBreakIndicator(this, new Point2D(335, 335)); + Players = new MahjongPlayers(this, MaxPlayers, BaseScore); + } - public override void OnDoubleClick( Mobile from ) - { - Players.CheckPlayers(); + public void ResetWalls(Mobile from) + { + if (DateTime.UtcNow - m_LastReset < TimeSpan.FromSeconds(5.0)) + return; - Players.Join( from ); - } + m_LastReset = DateTime.UtcNow; - public void ResetGame( Mobile from ) - { - if ( DateTime.UtcNow - m_LastReset < TimeSpan.FromSeconds( 5.0 ) ) - return; + BuildWalls(); - m_LastReset = DateTime.UtcNow; + Players.SendTilesPacket(true, true); - if ( from != null ) - Players.SendLocalizedMessage( 1062771, from.Name ); // ~1_name~ has reset the game. + if (from != null) + Players.SendLocalizedMessage(1062696); // The dealer rebuilds the wall. + } - Players.SendRelievePacket( true, true ); + public int GetStackLevel(MahjongPieceDim dim) + { + int level = -1; + foreach (MahjongTile tile in Tiles) + if (tile.StackLevel > level && dim.IsOverlapping(tile.Dimensions)) + level = tile.StackLevel; + return level; + } - BuildWalls(); - DealerIndicator = new MahjongDealerIndicator( this, new Point2D( 300, 300 ), MahjongPieceDirection.Up, MahjongWind.North ); - WallBreakIndicator = new MahjongWallBreakIndicator( this, new Point2D( 335, 335 ) ); - Players = new MahjongPlayers( this, MaxPlayers, BaseScore ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void ResetWalls( Mobile from ) - { - if ( DateTime.UtcNow - m_LastReset < TimeSpan.FromSeconds( 5.0 ) ) - return; + writer.Write(1); // version - m_LastReset = DateTime.UtcNow; + writer.Write((int)Level); - BuildWalls(); + writer.Write(Tiles.Length); - Players.SendTilesPacket( true, true ); + for (int i = 0; i < Tiles.Length; i++) + Tiles[i].Save(writer); - if ( from != null ) - Players.SendLocalizedMessage( 1062696 ); // The dealer rebuilds the wall. - } + DealerIndicator.Save(writer); - public int GetStackLevel( MahjongPieceDim dim ) - { - int level = -1; - foreach ( MahjongTile tile in Tiles ) - { - if ( tile.StackLevel > level && dim.IsOverlapping( tile.Dimensions ) ) - level = tile.StackLevel; - } - return level; - } + WallBreakIndicator.Save(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Dices.Save(writer); - writer.Write( (int) 1 ); // version + Players.Save(writer); - writer.Write( (int) Level ); + writer.Write(m_ShowScores); + writer.Write(m_SpectatorVision); + } - writer.Write( Tiles.Length ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - for ( int i = 0; i < Tiles.Length; i++ ) - Tiles[i].Save( writer ); + int version = reader.ReadInt(); - DealerIndicator.Save( writer ); + switch (version) + { + case 1: + { + Level = (SecureLevel)reader.ReadInt(); - WallBreakIndicator.Save( writer ); + goto case 0; + } + case 0: + { + if (version < 1) + Level = SecureLevel.CoOwners; - Dices.Save( writer ); + int length = reader.ReadInt(); + Tiles = new MahjongTile[length]; - Players.Save( writer ); + for (int i = 0; i < length; i++) + Tiles[i] = new MahjongTile(this, reader); - writer.Write( m_ShowScores ); - writer.Write( m_SpectatorVision ); - } + DealerIndicator = new MahjongDealerIndicator(this, reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + WallBreakIndicator = new MahjongWallBreakIndicator(this, reader); - int version = reader.ReadInt(); + Dices = new MahjongDices(this, reader); - switch ( version ) - { - case 1: - { - Level = (SecureLevel)reader.ReadInt(); + Players = new MahjongPlayers(this, reader); - goto case 0; - } - case 0: - { - if ( version < 1 ) - Level = SecureLevel.CoOwners; + m_ShowScores = reader.ReadBool(); + m_SpectatorVision = reader.ReadBool(); - int length = reader.ReadInt(); - Tiles = new MahjongTile[length]; + m_LastReset = DateTime.UtcNow; - for ( int i = 0; i < length; i++ ) - Tiles[i] = new MahjongTile( this, reader ); + break; + } + } + } - DealerIndicator = new MahjongDealerIndicator( this, reader ); + private class ResetGameEntry : ContextMenuEntry + { + private MahjongGame m_Game; - WallBreakIndicator = new MahjongWallBreakIndicator( this, reader ); + public ResetGameEntry(MahjongGame game) : base(6162) + { + m_Game = game; + } - Dices = new MahjongDices( this, reader ); + public override void OnClick() + { + Mobile from = Owner.From; - Players = new MahjongPlayers( this, reader ); - - m_ShowScores = reader.ReadBool(); - m_SpectatorVision = reader.ReadBool(); - - m_LastReset = DateTime.UtcNow; - - break; - } - } - } - } -} + if (from.CheckAlive() && !m_Game.Deleted && m_Game.IsAccessibleTo(from) && + m_Game.Players.GetInGameMobiles(true, false).Count == 0) + m_Game.ResetGame(from); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongPacketHandlers.cs b/Scripts/Items/Games/Mahjong/MahjongPacketHandlers.cs index 54abb72f2..e5124a73c 100644 --- a/Scripts/Items/Games/Mahjong/MahjongPacketHandlers.cs +++ b/Scripts/Items/Games/Mahjong/MahjongPacketHandlers.cs @@ -2,239 +2,232 @@ using Server.Network; namespace Server.Engines.Mahjong { - public delegate void OnMahjongPacketReceive( MahjongGame game, NetState state, PacketReader pvSrc ); + public delegate void OnMahjongPacketReceive(MahjongGame game, NetState state, PacketReader pvSrc); - public sealed class MahjongPacketHandlers - { - private static OnMahjongPacketReceive[] m_SubCommandDelegates = new OnMahjongPacketReceive[0x100]; + public sealed class MahjongPacketHandlers + { + private static OnMahjongPacketReceive[] m_SubCommandDelegates = new OnMahjongPacketReceive[0x100]; - public static void RegisterSubCommand( int subCmd, OnMahjongPacketReceive onReceive ) - { - m_SubCommandDelegates[subCmd] = onReceive; - } + public static void RegisterSubCommand(int subCmd, OnMahjongPacketReceive onReceive) + { + m_SubCommandDelegates[subCmd] = onReceive; + } - public static OnMahjongPacketReceive GetSubCommandDelegate( int cmd ) - { - if ( cmd >= 0 && cmd < 0x100 ) - { - return m_SubCommandDelegates[cmd]; - } + public static OnMahjongPacketReceive GetSubCommandDelegate(int cmd) + { + if (cmd >= 0 && cmd < 0x100) return m_SubCommandDelegates[cmd]; - return null; - } + return null; + } - public static void Initialize() - { - PacketHandlers.Register( 0xDA, 0, true, OnPacket ); + public static void Initialize() + { + PacketHandlers.Register(0xDA, 0, true, OnPacket); - RegisterSubCommand( 0x6, ExitGame ); - RegisterSubCommand( 0xA, GivePoints ); - RegisterSubCommand( 0xB, RollDice ); - RegisterSubCommand( 0xC, BuildWalls ); - RegisterSubCommand( 0xD, ResetScores ); - RegisterSubCommand( 0xF, AssignDealer ); - RegisterSubCommand( 0x10, OpenSeat ); - RegisterSubCommand( 0x11, ChangeOption ); - RegisterSubCommand( 0x15, MoveWallBreakIndicator ); - RegisterSubCommand( 0x16, TogglePublicHand ); - RegisterSubCommand( 0x17, MoveTile ); - RegisterSubCommand( 0x18, MoveDealerIndicator ); - } + RegisterSubCommand(0x6, ExitGame); + RegisterSubCommand(0xA, GivePoints); + RegisterSubCommand(0xB, RollDice); + RegisterSubCommand(0xC, BuildWalls); + RegisterSubCommand(0xD, ResetScores); + RegisterSubCommand(0xF, AssignDealer); + RegisterSubCommand(0x10, OpenSeat); + RegisterSubCommand(0x11, ChangeOption); + RegisterSubCommand(0x15, MoveWallBreakIndicator); + RegisterSubCommand(0x16, TogglePublicHand); + RegisterSubCommand(0x17, MoveTile); + RegisterSubCommand(0x18, MoveDealerIndicator); + } - public static void OnPacket( NetState state, PacketReader pvSrc ) - { - MahjongGame game = World.FindItem( pvSrc.ReadInt32() ) as MahjongGame; + public static void OnPacket(NetState state, PacketReader pvSrc) + { + MahjongGame game = World.FindItem(pvSrc.ReadInt32()) as MahjongGame; - game?.Players.CheckPlayers(); + game?.Players.CheckPlayers(); - pvSrc.ReadByte(); + pvSrc.ReadByte(); - int cmd = pvSrc.ReadByte(); + int cmd = pvSrc.ReadByte(); - OnMahjongPacketReceive onReceive = GetSubCommandDelegate( cmd ); + OnMahjongPacketReceive onReceive = GetSubCommandDelegate(cmd); - if ( onReceive != null ) - { - onReceive( game, state, pvSrc ); - } - else - { - pvSrc.Trace( state ); - } - } + if (onReceive != null) + onReceive(game, state, pvSrc); + else + pvSrc.Trace(state); + } - private static MahjongPieceDirection GetDirection( int value ) - { - switch ( value ) - { - case 0: return MahjongPieceDirection.Up; - case 1: return MahjongPieceDirection.Left; - case 2: return MahjongPieceDirection.Down; - default: return MahjongPieceDirection.Right; - } - } + private static MahjongPieceDirection GetDirection(int value) + { + switch (value) + { + case 0: return MahjongPieceDirection.Up; + case 1: return MahjongPieceDirection.Left; + case 2: return MahjongPieceDirection.Down; + default: return MahjongPieceDirection.Right; + } + } - private static MahjongWind GetWind( int value ) - { - switch ( value ) - { - case 0: return MahjongWind.North; - case 1: return MahjongWind.East; - case 2: return MahjongWind.South; - default: return MahjongWind.West; - } - } + private static MahjongWind GetWind(int value) + { + switch (value) + { + case 0: return MahjongWind.North; + case 1: return MahjongWind.East; + case 2: return MahjongWind.South; + default: return MahjongWind.West; + } + } - public static void ExitGame( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null ) - return; + public static void ExitGame(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null) + return; - Mobile from = state.Mobile; + Mobile from = state.Mobile; - game.Players.LeaveGame( from ); - } + game.Players.LeaveGame(from); + } - public static void GivePoints( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGamePlayer( state.Mobile ) ) - return; + public static void GivePoints(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGamePlayer(state.Mobile)) + return; - int to = pvSrc.ReadByte(); - int amount = pvSrc.ReadInt32(); + int to = pvSrc.ReadByte(); + int amount = pvSrc.ReadInt32(); - game.Players.TransferScore( state.Mobile, to, amount ); - } + game.Players.TransferScore(state.Mobile, to, amount); + } - public static void RollDice( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGamePlayer( state.Mobile ) ) - return; + public static void RollDice(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGamePlayer(state.Mobile)) + return; - game.Dices.RollDices( state.Mobile ); - } + game.Dices.RollDices(state.Mobile); + } - public static void BuildWalls( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void BuildWalls(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - game.ResetWalls( state.Mobile ); - } + game.ResetWalls(state.Mobile); + } - public static void ResetScores( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void ResetScores(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - game.Players.ResetScores( MahjongGame.BaseScore ); - } + game.Players.ResetScores(MahjongGame.BaseScore); + } - public static void AssignDealer( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void AssignDealer(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - int position = pvSrc.ReadByte(); + int position = pvSrc.ReadByte(); - game.Players.AssignDealer( position ); - } + game.Players.AssignDealer(position); + } - public static void OpenSeat( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void OpenSeat(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - int position = pvSrc.ReadByte(); + int position = pvSrc.ReadByte(); - if ( game.Players.GetPlayer( position ) == state.Mobile ) - return; + if (game.Players.GetPlayer(position) == state.Mobile) + return; - game.Players.OpenSeat( position ); - } + game.Players.OpenSeat(position); + } - public static void ChangeOption( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void ChangeOption(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - pvSrc.ReadInt16(); - pvSrc.ReadByte(); + pvSrc.ReadInt16(); + pvSrc.ReadByte(); - int options = pvSrc.ReadByte(); + int options = pvSrc.ReadByte(); - game.ShowScores = (options & 0x1) != 0; - game.SpectatorVision = (options & 0x2) != 0; - } + game.ShowScores = (options & 0x1) != 0; + game.SpectatorVision = (options & 0x2) != 0; + } - public static void MoveWallBreakIndicator( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void MoveWallBreakIndicator(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - int y = pvSrc.ReadInt16(); - int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int x = pvSrc.ReadInt16(); - game.WallBreakIndicator.Move( new Point2D( x, y ) ); - } + game.WallBreakIndicator.Move(new Point2D(x, y)); + } - public static void TogglePublicHand( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGamePlayer( state.Mobile ) ) - return; + public static void TogglePublicHand(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGamePlayer(state.Mobile)) + return; - pvSrc.ReadInt16(); - pvSrc.ReadByte(); + pvSrc.ReadInt16(); + pvSrc.ReadByte(); - bool publicHand = pvSrc.ReadBoolean(); + bool publicHand = pvSrc.ReadBoolean(); - game.Players.SetPublic( game.Players.GetPlayerIndex( state.Mobile ), publicHand ); - } + game.Players.SetPublic(game.Players.GetPlayerIndex(state.Mobile), publicHand); + } - public static void MoveTile( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGamePlayer( state.Mobile ) ) - return; + public static void MoveTile(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGamePlayer(state.Mobile)) + return; - int number = pvSrc.ReadByte(); + int number = pvSrc.ReadByte(); - if ( number < 0 || number >= game.Tiles.Length ) - return; + if (number < 0 || number >= game.Tiles.Length) + return; - pvSrc.ReadByte(); // Current direction + pvSrc.ReadByte(); // Current direction - MahjongPieceDirection direction = GetDirection( pvSrc.ReadByte() ); + MahjongPieceDirection direction = GetDirection(pvSrc.ReadByte()); - pvSrc.ReadByte(); + pvSrc.ReadByte(); - bool flip = pvSrc.ReadBoolean(); + bool flip = pvSrc.ReadBoolean(); - pvSrc.ReadInt16(); // Current Y - pvSrc.ReadInt16(); // Current X + pvSrc.ReadInt16(); // Current Y + pvSrc.ReadInt16(); // Current X - pvSrc.ReadByte(); + pvSrc.ReadByte(); - int y = pvSrc.ReadInt16(); - int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int x = pvSrc.ReadInt16(); - pvSrc.ReadByte(); + pvSrc.ReadByte(); - game.Tiles[number].Move( new Point2D( x, y ), direction, flip, game.Players.GetPlayerIndex( state.Mobile ) ); - } + game.Tiles[number].Move(new Point2D(x, y), direction, flip, game.Players.GetPlayerIndex(state.Mobile)); + } - public static void MoveDealerIndicator( MahjongGame game, NetState state, PacketReader pvSrc ) - { - if ( game == null || !game.Players.IsInGameDealer( state.Mobile ) ) - return; + public static void MoveDealerIndicator(MahjongGame game, NetState state, PacketReader pvSrc) + { + if (game == null || !game.Players.IsInGameDealer(state.Mobile)) + return; - MahjongPieceDirection direction = GetDirection( pvSrc.ReadByte() ); + MahjongPieceDirection direction = GetDirection(pvSrc.ReadByte()); - MahjongWind wind = GetWind( pvSrc.ReadByte() ); + MahjongWind wind = GetWind(pvSrc.ReadByte()); - int y = pvSrc.ReadInt16(); - int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int x = pvSrc.ReadInt16(); - game.DealerIndicator.Move( new Point2D( x, y ), direction, wind ); - } - } + game.DealerIndicator.Move(new Point2D(x, y), direction, wind); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongPieceDim.cs b/Scripts/Items/Games/Mahjong/MahjongPieceDim.cs index aed1b149a..68aba572b 100644 --- a/Scripts/Items/Games/Mahjong/MahjongPieceDim.cs +++ b/Scripts/Items/Games/Mahjong/MahjongPieceDim.cs @@ -1,45 +1,46 @@ namespace Server.Engines.Mahjong { - public struct MahjongPieceDim - { - public Point2D Position { get; } + public struct MahjongPieceDim + { + public Point2D Position{ get; } - public int Width { get; } + public int Width{ get; } - public int Height { get; } + public int Height{ get; } - public MahjongPieceDim( Point2D position, int width, int height ) - { - Position = position; - Width = width; - Height = height; - } + public MahjongPieceDim(Point2D position, int width, int height) + { + Position = position; + Width = width; + Height = height; + } - public bool IsValid() - { - return Position.X >= 0 && Position.Y >= 0 && Position.X + Width <= 670 && Position.Y + Height <= 670; - } + public bool IsValid() + { + return Position.X >= 0 && Position.Y >= 0 && Position.X + Width <= 670 && Position.Y + Height <= 670; + } - public bool IsOverlapping( MahjongPieceDim dim ) - { - return Position.X < dim.Position.X + dim.Width && Position.Y < dim.Position.Y + dim.Height && Position.X + Width > dim.Position.X && Position.Y + Height > dim.Position.Y; - } + public bool IsOverlapping(MahjongPieceDim dim) + { + return Position.X < dim.Position.X + dim.Width && Position.Y < dim.Position.Y + dim.Height && + Position.X + Width > dim.Position.X && Position.Y + Height > dim.Position.Y; + } - public int GetHandArea() - { - if ( Position.X + Width > 150 && Position.X < 520 && Position.Y < 35 ) - return 0; + public int GetHandArea() + { + if (Position.X + Width > 150 && Position.X < 520 && Position.Y < 35) + return 0; - if ( Position.X + Width > 635 && Position.Y + Height > 150 && Position.Y < 520 ) - return 1; + if (Position.X + Width > 635 && Position.Y + Height > 150 && Position.Y < 520) + return 1; - if ( Position.X + Width > 150 && Position.X < 520 && Position.Y + Height > 635 ) - return 2; + if (Position.X + Width > 150 && Position.X < 520 && Position.Y + Height > 635) + return 2; - if ( Position.X < 35 && Position.Y + Height > 150 && Position.Y < 520 ) - return 3; + if (Position.X < 35 && Position.Y + Height > 150 && Position.Y < 520) + return 3; - return -1; - } - } -} + return -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongPlayers.cs b/Scripts/Items/Games/Mahjong/MahjongPlayers.cs index 0886b95d5..8c9c6c55f 100644 --- a/Scripts/Items/Games/Mahjong/MahjongPlayers.cs +++ b/Scripts/Items/Games/Mahjong/MahjongPlayers.cs @@ -2,541 +2,497 @@ using System.Collections; namespace Server.Engines.Mahjong { - public class MahjongPlayers - { - private Mobile[] m_Players; - private bool[] m_InGame; - private bool[] m_PublicHand; - private int[] m_Scores; - private ArrayList m_Spectators; - - public MahjongGame Game { get; } - - public int Seats => m_Players.Length; - public Mobile Dealer => m_Players[DealerPosition]; - public int DealerPosition { get; private set; } - - public MahjongPlayers( MahjongGame game, int maxPlayers, int baseScore ) - { - Game = game; - m_Spectators = new ArrayList(); - - m_Players = new Mobile[maxPlayers]; - m_InGame = new bool[maxPlayers]; - m_PublicHand = new bool[maxPlayers]; - m_Scores = new int[maxPlayers]; - - for ( int i = 0; i < m_Scores.Length; i++ ) - m_Scores[i] = baseScore; - } - - public Mobile GetPlayer( int index ) - { - if ( index < 0 || index >= m_Players.Length ) - return null; - return m_Players[index]; - } - - public int GetPlayerIndex( Mobile mobile ) - { - for ( int i = 0; i < m_Players.Length; i++ ) - { - if ( m_Players[i] == mobile ) - return i; - } - return -1; - } - - public bool IsInGameDealer( Mobile mobile ) - { - if ( Dealer != mobile ) - return false; - return m_InGame[DealerPosition]; - } - - public bool IsInGamePlayer( int index ) - { - if ( index < 0 || index >= m_Players.Length || m_Players[index] == null ) - return false; - return m_InGame[index]; - } - - public bool IsInGamePlayer( Mobile mobile ) - { - int index = GetPlayerIndex( mobile ); - - return IsInGamePlayer( index ); - } - - public bool IsSpectator( Mobile mobile ) - { - return m_Spectators.Contains( mobile ); - } - - public int GetScore( int index ) - { - if ( index < 0 || index >= m_Scores.Length ) - return 0; - return m_Scores[index]; - } - - public bool IsPublic( int index ) - { - if ( index < 0 || index >= m_PublicHand.Length ) - return false; - return m_PublicHand[index]; - } - - public void SetPublic( int index, bool value ) - { - if ( index < 0 || index >= m_PublicHand.Length || m_PublicHand[index] == value ) - return; - - m_PublicHand[index] = value; - - SendTilesPacket( true, !Game.SpectatorVision ); - - if ( IsInGamePlayer( index ) ) - m_Players[index].SendLocalizedMessage( value ? 1062775 : 1062776 ); // Your hand is [not] publicly viewable. - } - - public ArrayList GetInGameMobiles( bool players, bool spectators ) - { - ArrayList list = new ArrayList(); - - if ( players ) - { - for ( int i = 0; i < m_Players.Length; i++ ) - { - if ( IsInGamePlayer( i ) ) - list.Add( m_Players[i] ); - } - } - - if ( spectators ) - { - list.AddRange( m_Spectators ); - } - - return list; - } - - public void CheckPlayers() - { - bool removed = false; - - for ( int i = 0; i < m_Players.Length; i++ ) - { - Mobile player = m_Players[i]; - - if ( player != null ) - { - if ( player.Deleted ) - { - m_Players[i] = null; - - SendPlayerExitMessage( player ); - UpdateDealer( true ); - - removed = true; - } - else if ( m_InGame[i] ) - { - if ( player.NetState == null ) - { - m_InGame[i] = false; - - SendPlayerExitMessage( player ); - UpdateDealer( true ); - - removed = true; - } - else if ( !Game.IsAccessibleTo( player ) || player.Map != Game.Map || !player.InRange( Game.GetWorldLocation(), 5 ) ) - { - m_InGame[i] = false; - - player.Send( new MahjongRelieve( Game ) ); - - SendPlayerExitMessage( player ); - UpdateDealer( true ); - - removed = true; - } - } - } - } - - for ( int i = 0; i < m_Spectators.Count; ) - { - Mobile mobile = (Mobile)m_Spectators[i]; - - if ( mobile.NetState == null || mobile.Deleted ) - { - m_Spectators.RemoveAt( i ); - } - else if ( !Game.IsAccessibleTo( mobile ) || mobile.Map != Game.Map || !mobile.InRange( Game.GetWorldLocation(), 5 ) ) - { - m_Spectators.RemoveAt( i ); - - mobile.Send( new MahjongRelieve( Game ) ); - } - else - { - i++; - } - } - - if ( removed && !UpdateSpectators() ) - SendPlayersPacket( true, true ); - } - - private void UpdateDealer( bool message ) - { - if ( IsInGamePlayer( DealerPosition ) ) - return; - - for ( int i = DealerPosition + 1; i < m_Players.Length; i++ ) - { - if ( IsInGamePlayer( i ) ) - { - DealerPosition = i; - - if ( message ) - SendDealerChangedMessage(); - - return; - } - } - - for ( int i = 0; i < DealerPosition; i++ ) - { - if ( IsInGamePlayer( i ) ) - { - DealerPosition = i; - - if ( message ) - SendDealerChangedMessage(); - - return; - } - } - } - - private int GetNextSeat() - { - for ( int i = DealerPosition; i < m_Players.Length; i++ ) - { - if ( m_Players[i] == null ) - return i; - } - - for ( int i = 0; i < DealerPosition; i++ ) - { - if ( m_Players[i] == null ) - return i; - } - - return -1; - } - - private bool UpdateSpectators() - { - if ( m_Spectators.Count == 0 ) - return false; - - int nextSeat = GetNextSeat(); - - if ( nextSeat >= 0 ) - { - Mobile newPlayer = (Mobile)m_Spectators[0]; - - m_Spectators.RemoveAt( 0 ); - - AddPlayer( newPlayer, nextSeat, false ); - - UpdateSpectators(); - - return true; - } - - return false; - } - - private void AddPlayer( Mobile player, int index, bool sendJoinGame ) - { - m_Players[index] = player; - m_InGame[index] = true; - - UpdateDealer( false ); - - if ( sendJoinGame ) - player.Send( new MahjongJoinGame( Game ) ); - - SendPlayersPacket( true, true ); - - player.Send( new MahjongGeneralInfo( Game ) ); - player.Send( new MahjongTilesInfo( Game, player ) ); - - if ( DealerPosition == index ) - SendLocalizedMessage( 1062773, player.Name ); // ~1_name~ has entered the game as the dealer. - else - SendLocalizedMessage( 1062772, player.Name ); // ~1_name~ has entered the game as a player. - } - - private void AddSpectator( Mobile mobile ) - { - if ( !IsSpectator( mobile ) ) - { - m_Spectators.Add( mobile ); - } - - mobile.Send( new MahjongJoinGame( Game ) ); - mobile.Send( new MahjongPlayersInfo( Game, mobile ) ); - mobile.Send( new MahjongGeneralInfo( Game ) ); - mobile.Send( new MahjongTilesInfo( Game, mobile ) ); - } - - public void Join( Mobile mobile ) - { - int index = GetPlayerIndex( mobile ); - - if ( index >= 0 ) - { - AddPlayer( mobile, index, true ); - } - else - { - int nextSeat = GetNextSeat(); - - if ( nextSeat >= 0 ) - { - AddPlayer( mobile, nextSeat, true ); - } - else - { - AddSpectator( mobile ); - } - } - } - - public void LeaveGame( Mobile player ) - { - int index = GetPlayerIndex( player ); - if ( index >= 0 ) - { - m_InGame[index] = false; - - SendPlayerExitMessage( player ); - UpdateDealer( true ); - - SendPlayersPacket( true, true ); - } - else - { - m_Spectators.Remove( player ); - } - } - - public void ResetScores( int value ) - { - for ( int i = 0; i < m_Scores.Length; i++ ) - { - m_Scores[i] = value; - } + public class MahjongPlayers + { + private bool[] m_InGame; + private Mobile[] m_Players; + private bool[] m_PublicHand; + private int[] m_Scores; + private ArrayList m_Spectators; + + public MahjongPlayers(MahjongGame game, int maxPlayers, int baseScore) + { + Game = game; + m_Spectators = new ArrayList(); + + m_Players = new Mobile[maxPlayers]; + m_InGame = new bool[maxPlayers]; + m_PublicHand = new bool[maxPlayers]; + m_Scores = new int[maxPlayers]; + + for (int i = 0; i < m_Scores.Length; i++) + m_Scores[i] = baseScore; + } + + public MahjongPlayers(MahjongGame game, GenericReader reader) + { + Game = game; + m_Spectators = new ArrayList(); + + int version = reader.ReadInt(); + + int seats = reader.ReadInt(); + m_Players = new Mobile[seats]; + m_InGame = new bool[seats]; + m_PublicHand = new bool[seats]; + m_Scores = new int[seats]; + + for (int i = 0; i < seats; i++) + { + m_Players[i] = reader.ReadMobile(); + m_PublicHand[i] = reader.ReadBool(); + m_Scores[i] = reader.ReadInt(); + } + + DealerPosition = reader.ReadInt(); + } + + public MahjongGame Game{ get; } + + public int Seats => m_Players.Length; + public Mobile Dealer => m_Players[DealerPosition]; + public int DealerPosition{ get; private set; } + + public Mobile GetPlayer(int index) + { + if (index < 0 || index >= m_Players.Length) + return null; + return m_Players[index]; + } + + public int GetPlayerIndex(Mobile mobile) + { + for (int i = 0; i < m_Players.Length; i++) + if (m_Players[i] == mobile) + return i; + return -1; + } + + public bool IsInGameDealer(Mobile mobile) + { + if (Dealer != mobile) + return false; + return m_InGame[DealerPosition]; + } + + public bool IsInGamePlayer(int index) + { + if (index < 0 || index >= m_Players.Length || m_Players[index] == null) + return false; + return m_InGame[index]; + } + + public bool IsInGamePlayer(Mobile mobile) + { + int index = GetPlayerIndex(mobile); + + return IsInGamePlayer(index); + } + + public bool IsSpectator(Mobile mobile) + { + return m_Spectators.Contains(mobile); + } + + public int GetScore(int index) + { + if (index < 0 || index >= m_Scores.Length) + return 0; + return m_Scores[index]; + } + + public bool IsPublic(int index) + { + if (index < 0 || index >= m_PublicHand.Length) + return false; + return m_PublicHand[index]; + } + + public void SetPublic(int index, bool value) + { + if (index < 0 || index >= m_PublicHand.Length || m_PublicHand[index] == value) + return; + + m_PublicHand[index] = value; + + SendTilesPacket(true, !Game.SpectatorVision); + + if (IsInGamePlayer(index)) + m_Players[index].SendLocalizedMessage(value ? 1062775 : 1062776); // Your hand is [not] publicly viewable. + } + + public ArrayList GetInGameMobiles(bool players, bool spectators) + { + ArrayList list = new ArrayList(); + + if (players) + for (int i = 0; i < m_Players.Length; i++) + if (IsInGamePlayer(i)) + list.Add(m_Players[i]); + + if (spectators) list.AddRange(m_Spectators); + + return list; + } + + public void CheckPlayers() + { + bool removed = false; + + for (int i = 0; i < m_Players.Length; i++) + { + Mobile player = m_Players[i]; + + if (player != null) + { + if (player.Deleted) + { + m_Players[i] = null; + + SendPlayerExitMessage(player); + UpdateDealer(true); + + removed = true; + } + else if (m_InGame[i]) + { + if (player.NetState == null) + { + m_InGame[i] = false; + + SendPlayerExitMessage(player); + UpdateDealer(true); + + removed = true; + } + else if (!Game.IsAccessibleTo(player) || player.Map != Game.Map || + !player.InRange(Game.GetWorldLocation(), 5)) + { + m_InGame[i] = false; + + player.Send(new MahjongRelieve(Game)); + + SendPlayerExitMessage(player); + UpdateDealer(true); + + removed = true; + } + } + } + } + + for (int i = 0; i < m_Spectators.Count;) + { + Mobile mobile = (Mobile)m_Spectators[i]; - SendPlayersPacket( true, Game.ShowScores ); + if (mobile.NetState == null || mobile.Deleted) + { + m_Spectators.RemoveAt(i); + } + else if (!Game.IsAccessibleTo(mobile) || mobile.Map != Game.Map || + !mobile.InRange(Game.GetWorldLocation(), 5)) + { + m_Spectators.RemoveAt(i); + + mobile.Send(new MahjongRelieve(Game)); + } + else + { + i++; + } + } + + if (removed && !UpdateSpectators()) + SendPlayersPacket(true, true); + } - SendLocalizedMessage( 1062697 ); // The dealer redistributes the score sticks evenly. - } + private void UpdateDealer(bool message) + { + if (IsInGamePlayer(DealerPosition)) + return; + + for (int i = DealerPosition + 1; i < m_Players.Length; i++) + if (IsInGamePlayer(i)) + { + DealerPosition = i; + + if (message) + SendDealerChangedMessage(); + + return; + } + + for (int i = 0; i < DealerPosition; i++) + if (IsInGamePlayer(i)) + { + DealerPosition = i; + + if (message) + SendDealerChangedMessage(); + + return; + } + } + + private int GetNextSeat() + { + for (int i = DealerPosition; i < m_Players.Length; i++) + if (m_Players[i] == null) + return i; + + for (int i = 0; i < DealerPosition; i++) + if (m_Players[i] == null) + return i; + + return -1; + } + + private bool UpdateSpectators() + { + if (m_Spectators.Count == 0) + return false; + + int nextSeat = GetNextSeat(); + + if (nextSeat >= 0) + { + Mobile newPlayer = (Mobile)m_Spectators[0]; + + m_Spectators.RemoveAt(0); + + AddPlayer(newPlayer, nextSeat, false); + + UpdateSpectators(); + + return true; + } + + return false; + } + + private void AddPlayer(Mobile player, int index, bool sendJoinGame) + { + m_Players[index] = player; + m_InGame[index] = true; + + UpdateDealer(false); + + if (sendJoinGame) + player.Send(new MahjongJoinGame(Game)); + + SendPlayersPacket(true, true); + + player.Send(new MahjongGeneralInfo(Game)); + player.Send(new MahjongTilesInfo(Game, player)); + + if (DealerPosition == index) + SendLocalizedMessage(1062773, player.Name); // ~1_name~ has entered the game as the dealer. + else + SendLocalizedMessage(1062772, player.Name); // ~1_name~ has entered the game as a player. + } + + private void AddSpectator(Mobile mobile) + { + if (!IsSpectator(mobile)) m_Spectators.Add(mobile); + + mobile.Send(new MahjongJoinGame(Game)); + mobile.Send(new MahjongPlayersInfo(Game, mobile)); + mobile.Send(new MahjongGeneralInfo(Game)); + mobile.Send(new MahjongTilesInfo(Game, mobile)); + } - public void TransferScore( Mobile from, int toPosition, int amount ) - { - int fromPosition = GetPlayerIndex( from ); - Mobile to = GetPlayer( toPosition ); - - if ( fromPosition < 0 || to == null || m_Scores[fromPosition] < amount ) - return; - - m_Scores[fromPosition] -= amount; - m_Scores[toPosition] += amount; - - if ( Game.ShowScores ) - { - SendPlayersPacket( true, true ); - } - else - { - from.Send( new MahjongPlayersInfo( Game, from ) ); - to.Send( new MahjongPlayersInfo( Game, to ) ); - } - - SendLocalizedMessage( 1062774, $"{from.Name}\t{to.Name}\t{amount}"); // ~1_giver~ gives ~2_receiver~ ~3_number~ points. - } - - public void OpenSeat( int index ) - { - Mobile player = GetPlayer( index ); - if ( player == null ) - return; - - if ( m_InGame[index] ) - player.Send( new MahjongRelieve( Game ) ); - - m_Players[index] = null; - - SendLocalizedMessage( 1062699, player.Name ); // ~1_name~ is relieved from the game by the dealer. - - UpdateDealer( true ); - - if ( !UpdateSpectators() ) - SendPlayersPacket( true, true ); - } - - public void AssignDealer( int index ) - { - Mobile to = GetPlayer( index ); - - if ( to == null || !m_InGame[index] ) - return; - - int oldDealer = DealerPosition; - - DealerPosition = index; - - if ( IsInGamePlayer( oldDealer ) ) - m_Players[oldDealer].Send( new MahjongPlayersInfo( Game, m_Players[oldDealer] ) ); - - to.Send( new MahjongPlayersInfo( Game, to ) ); - - SendDealerChangedMessage(); - } - - private void SendDealerChangedMessage() - { - if ( Dealer != null ) - SendLocalizedMessage( 1062698, Dealer.Name ); // ~1_name~ is assigned the dealer. - } - - private void SendPlayerExitMessage( Mobile who ) - { - SendLocalizedMessage( 1062762, who.Name ); // ~1_name~ has left the game. - } - - public void SendPlayersPacket( bool players, bool spectators ) - { - foreach ( Mobile mobile in GetInGameMobiles( players, spectators ) ) - { - mobile.Send( new MahjongPlayersInfo( Game, mobile ) ); - } - } - - public void SendGeneralPacket( bool players, bool spectators ) - { - ArrayList mobiles = GetInGameMobiles( players, spectators ); - - if ( mobiles.Count == 0 ) - return; - - MahjongGeneralInfo generalInfo = new MahjongGeneralInfo( Game ); - - generalInfo.Acquire(); - - foreach ( Mobile mobile in mobiles ) - { - mobile.Send( generalInfo ); - } - - generalInfo.Release(); - } - - public void SendTilesPacket( bool players, bool spectators ) - { - foreach ( Mobile mobile in GetInGameMobiles( players, spectators ) ) - { - mobile.Send( new MahjongTilesInfo( Game, mobile ) ); - } - } - - public void SendTilePacket( MahjongTile tile, bool players, bool spectators ) - { - foreach ( Mobile mobile in GetInGameMobiles( players, spectators ) ) - { - mobile.Send( new MahjongTileInfo( tile, mobile ) ); - } - } - - public void SendRelievePacket( bool players, bool spectators ) - { - ArrayList mobiles = GetInGameMobiles( players, spectators ); - - if ( mobiles.Count == 0 ) - return; - - MahjongRelieve relieve = new MahjongRelieve( Game ); - - relieve.Acquire(); - - foreach ( Mobile mobile in mobiles ) - { - mobile.Send( relieve ); - } - - relieve.Release(); - } - - public void SendLocalizedMessage( int number ) - { - foreach ( Mobile mobile in GetInGameMobiles( true, true ) ) - { - mobile.SendLocalizedMessage( number ); - } - } - - public void SendLocalizedMessage( int number, string args ) - { - foreach ( Mobile mobile in GetInGameMobiles( true, true ) ) - { - mobile.SendLocalizedMessage( number, args ); - } - } - - public void Save( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version - - writer.Write( Seats ); - - for ( int i = 0; i < Seats; i++ ) - { - writer.Write( m_Players[i] ); - writer.Write( m_PublicHand[i] ); - writer.Write( m_Scores[i] ); - } - - writer.Write( DealerPosition ); - } - - public MahjongPlayers( MahjongGame game, GenericReader reader ) - { - Game = game; - m_Spectators = new ArrayList(); - - int version = reader.ReadInt(); - - int seats = reader.ReadInt(); - m_Players = new Mobile[seats]; - m_InGame = new bool[seats]; - m_PublicHand = new bool[seats]; - m_Scores = new int[seats]; - - for ( int i = 0; i < seats; i++ ) - { - m_Players[i] = reader.ReadMobile(); - m_PublicHand[i] = reader.ReadBool(); - m_Scores[i] = reader.ReadInt(); - } - - DealerPosition = reader.ReadInt(); - } - } -} + public void Join(Mobile mobile) + { + int index = GetPlayerIndex(mobile); + + if (index >= 0) + { + AddPlayer(mobile, index, true); + } + else + { + int nextSeat = GetNextSeat(); + + if (nextSeat >= 0) + AddPlayer(mobile, nextSeat, true); + else + AddSpectator(mobile); + } + } + + public void LeaveGame(Mobile player) + { + int index = GetPlayerIndex(player); + if (index >= 0) + { + m_InGame[index] = false; + + SendPlayerExitMessage(player); + UpdateDealer(true); + + SendPlayersPacket(true, true); + } + else + { + m_Spectators.Remove(player); + } + } + + public void ResetScores(int value) + { + for (int i = 0; i < m_Scores.Length; i++) m_Scores[i] = value; + + SendPlayersPacket(true, Game.ShowScores); + + SendLocalizedMessage(1062697); // The dealer redistributes the score sticks evenly. + } + + public void TransferScore(Mobile from, int toPosition, int amount) + { + int fromPosition = GetPlayerIndex(from); + Mobile to = GetPlayer(toPosition); + + if (fromPosition < 0 || to == null || m_Scores[fromPosition] < amount) + return; + + m_Scores[fromPosition] -= amount; + m_Scores[toPosition] += amount; + + if (Game.ShowScores) + { + SendPlayersPacket(true, true); + } + else + { + from.Send(new MahjongPlayersInfo(Game, from)); + to.Send(new MahjongPlayersInfo(Game, to)); + } + + SendLocalizedMessage(1062774, + $"{from.Name}\t{to.Name}\t{amount}"); // ~1_giver~ gives ~2_receiver~ ~3_number~ points. + } + + public void OpenSeat(int index) + { + Mobile player = GetPlayer(index); + if (player == null) + return; + + if (m_InGame[index]) + player.Send(new MahjongRelieve(Game)); + + m_Players[index] = null; + + SendLocalizedMessage(1062699, player.Name); // ~1_name~ is relieved from the game by the dealer. + + UpdateDealer(true); + + if (!UpdateSpectators()) + SendPlayersPacket(true, true); + } + + public void AssignDealer(int index) + { + Mobile to = GetPlayer(index); + + if (to == null || !m_InGame[index]) + return; + + int oldDealer = DealerPosition; + + DealerPosition = index; + + if (IsInGamePlayer(oldDealer)) + m_Players[oldDealer].Send(new MahjongPlayersInfo(Game, m_Players[oldDealer])); + + to.Send(new MahjongPlayersInfo(Game, to)); + + SendDealerChangedMessage(); + } + + private void SendDealerChangedMessage() + { + if (Dealer != null) + SendLocalizedMessage(1062698, Dealer.Name); // ~1_name~ is assigned the dealer. + } + + private void SendPlayerExitMessage(Mobile who) + { + SendLocalizedMessage(1062762, who.Name); // ~1_name~ has left the game. + } + + public void SendPlayersPacket(bool players, bool spectators) + { + foreach (Mobile mobile in GetInGameMobiles(players, spectators)) + mobile.Send(new MahjongPlayersInfo(Game, mobile)); + } + + public void SendGeneralPacket(bool players, bool spectators) + { + ArrayList mobiles = GetInGameMobiles(players, spectators); + + if (mobiles.Count == 0) + return; + + MahjongGeneralInfo generalInfo = new MahjongGeneralInfo(Game); + + generalInfo.Acquire(); + + foreach (Mobile mobile in mobiles) mobile.Send(generalInfo); + + generalInfo.Release(); + } + + public void SendTilesPacket(bool players, bool spectators) + { + foreach (Mobile mobile in GetInGameMobiles(players, spectators)) mobile.Send(new MahjongTilesInfo(Game, mobile)); + } + + public void SendTilePacket(MahjongTile tile, bool players, bool spectators) + { + foreach (Mobile mobile in GetInGameMobiles(players, spectators)) mobile.Send(new MahjongTileInfo(tile, mobile)); + } + + public void SendRelievePacket(bool players, bool spectators) + { + ArrayList mobiles = GetInGameMobiles(players, spectators); + + if (mobiles.Count == 0) + return; + + MahjongRelieve relieve = new MahjongRelieve(Game); + + relieve.Acquire(); + + foreach (Mobile mobile in mobiles) mobile.Send(relieve); + + relieve.Release(); + } + + public void SendLocalizedMessage(int number) + { + foreach (Mobile mobile in GetInGameMobiles(true, true)) mobile.SendLocalizedMessage(number); + } + + public void SendLocalizedMessage(int number, string args) + { + foreach (Mobile mobile in GetInGameMobiles(true, true)) mobile.SendLocalizedMessage(number, args); + } + + public void Save(GenericWriter writer) + { + writer.Write(0); // version + + writer.Write(Seats); + + for (int i = 0; i < Seats; i++) + { + writer.Write(m_Players[i]); + writer.Write(m_PublicHand[i]); + writer.Write(m_Scores[i]); + } + + writer.Write(DealerPosition); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongTile.cs b/Scripts/Items/Games/Mahjong/MahjongTile.cs index 9ab4d8482..76dfcbba2 100644 --- a/Scripts/Items/Games/Mahjong/MahjongTile.cs +++ b/Scripts/Items/Games/Mahjong/MahjongTile.cs @@ -1,86 +1,88 @@ namespace Server.Engines.Mahjong { - public class MahjongTile - { - public static MahjongPieceDim GetDimensions( Point2D position, MahjongPieceDirection direction ) - { - if ( direction == MahjongPieceDirection.Up || direction == MahjongPieceDirection.Down ) - return new MahjongPieceDim( position, 20, 30 ); - return new MahjongPieceDim( position, 30, 20 ); - } + public class MahjongTile + { + protected Point2D m_Position; - protected Point2D m_Position; + public MahjongTile(MahjongGame game, int number, MahjongTileType value, Point2D position, int stackLevel, + MahjongPieceDirection direction, bool flipped) + { + Game = game; + Number = number; + Value = value; + m_Position = position; + StackLevel = stackLevel; + Direction = direction; + Flipped = flipped; + } - public MahjongGame Game { get; } + public MahjongTile(MahjongGame game, GenericReader reader) + { + Game = game; - public int Number { get; } + int version = reader.ReadInt(); - public MahjongTileType Value { get; } + Number = reader.ReadInt(); + Value = (MahjongTileType)reader.ReadInt(); + m_Position = reader.ReadPoint2D(); + StackLevel = reader.ReadInt(); + Direction = (MahjongPieceDirection)reader.ReadInt(); + Flipped = reader.ReadBool(); + } - public Point2D Position => m_Position; - public int StackLevel { get; private set; } + public MahjongGame Game{ get; } - public MahjongPieceDirection Direction { get; private set; } + public int Number{ get; } - public bool Flipped { get; private set; } + public MahjongTileType Value{ get; } - public MahjongTile( MahjongGame game, int number, MahjongTileType value, Point2D position, int stackLevel, MahjongPieceDirection direction, bool flipped ) - { - Game = game; - Number = number; - Value = value; - m_Position = position; - StackLevel = stackLevel; - Direction = direction; - Flipped = flipped; - } + public Point2D Position => m_Position; + public int StackLevel{ get; private set; } - public MahjongPieceDim Dimensions => GetDimensions( m_Position, Direction ); + public MahjongPieceDirection Direction{ get; private set; } - public bool IsMovable => Game.GetStackLevel( Dimensions ) <= StackLevel; + public bool Flipped{ get; private set; } - public void Move( Point2D position, MahjongPieceDirection direction, bool flip, int validHandArea ) - { - MahjongPieceDim dim = GetDimensions( position, direction ); - int curHandArea = Dimensions.GetHandArea(); - int newHandArea = dim.GetHandArea(); + public MahjongPieceDim Dimensions => GetDimensions(m_Position, Direction); - if ( !IsMovable || !dim.IsValid() || ( validHandArea >= 0 && ((curHandArea >= 0 && curHandArea != validHandArea) || (newHandArea >= 0 && newHandArea != validHandArea)) ) ) - return; + public bool IsMovable => Game.GetStackLevel(Dimensions) <= StackLevel; - m_Position = position; - Direction = direction; - StackLevel = -1; // Avoid self interference - StackLevel = Game.GetStackLevel( dim ) + 1; - Flipped = flip; + public static MahjongPieceDim GetDimensions(Point2D position, MahjongPieceDirection direction) + { + if (direction == MahjongPieceDirection.Up || direction == MahjongPieceDirection.Down) + return new MahjongPieceDim(position, 20, 30); + return new MahjongPieceDim(position, 30, 20); + } - Game.Players.SendTilePacket( this, true, true ); - } + public void Move(Point2D position, MahjongPieceDirection direction, bool flip, int validHandArea) + { + MahjongPieceDim dim = GetDimensions(position, direction); + int curHandArea = Dimensions.GetHandArea(); + int newHandArea = dim.GetHandArea(); - public void Save( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version + if (!IsMovable || !dim.IsValid() || validHandArea >= 0 && + (curHandArea >= 0 && curHandArea != validHandArea || newHandArea >= 0 && newHandArea != validHandArea)) + return; - writer.Write( Number ); - writer.Write( (int) Value ); - writer.Write( m_Position ); - writer.Write( StackLevel ); - writer.Write( (int) Direction ); - writer.Write( Flipped ); - } + m_Position = position; + Direction = direction; + StackLevel = -1; // Avoid self interference + StackLevel = Game.GetStackLevel(dim) + 1; + Flipped = flip; - public MahjongTile( MahjongGame game, GenericReader reader ) - { - Game = game; + Game.Players.SendTilePacket(this, true, true); + } - int version = reader.ReadInt(); + public void Save(GenericWriter writer) + { + writer.Write(0); // version - Number = reader.ReadInt(); - Value = (MahjongTileType) reader.ReadInt(); - m_Position = reader.ReadPoint2D(); - StackLevel = reader.ReadInt(); - Direction = (MahjongPieceDirection) reader.ReadInt(); - Flipped = reader.ReadBool(); - } - } -} + writer.Write(Number); + writer.Write((int)Value); + writer.Write(m_Position); + writer.Write(StackLevel); + writer.Write((int)Direction); + writer.Write(Flipped); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongTileTypeGenerator.cs b/Scripts/Items/Games/Mahjong/MahjongTileTypeGenerator.cs index 394d17e83..dbb1a1d45 100644 --- a/Scripts/Items/Games/Mahjong/MahjongTileTypeGenerator.cs +++ b/Scripts/Items/Games/Mahjong/MahjongTileTypeGenerator.cs @@ -2,30 +2,26 @@ using System.Collections; namespace Server.Engines.Mahjong { - public class MahjongTileTypeGenerator - { - public ArrayList LeftTileTypes { get; } + public class MahjongTileTypeGenerator + { + public MahjongTileTypeGenerator(int count) + { + LeftTileTypes = new ArrayList(34 * count); - public MahjongTileTypeGenerator( int count ) - { - LeftTileTypes = new ArrayList( 34 * count ); + for (int i = 1; i <= 34; i++) + for (int j = 0; j < count; j++) + LeftTileTypes.Add((MahjongTileType)i); + } - for ( int i = 1; i <= 34; i++ ) - { - for ( int j = 0; j < count; j++ ) - { - LeftTileTypes.Add( (MahjongTileType)i ); - } - } - } + public ArrayList LeftTileTypes{ get; } - public MahjongTileType Next() - { - int random = Utility.Random( LeftTileTypes.Count ); - MahjongTileType next = (MahjongTileType)LeftTileTypes[random]; - LeftTileTypes.RemoveAt( random ); + public MahjongTileType Next() + { + int random = Utility.Random(LeftTileTypes.Count); + MahjongTileType next = (MahjongTileType)LeftTileTypes[random]; + LeftTileTypes.RemoveAt(random); - return next; - } - } -} + return next; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/MahjongWallBreakIndicator.cs b/Scripts/Items/Games/Mahjong/MahjongWallBreakIndicator.cs index 29e8e12dc..400822753 100644 --- a/Scripts/Items/Games/Mahjong/MahjongWallBreakIndicator.cs +++ b/Scripts/Items/Games/Mahjong/MahjongWallBreakIndicator.cs @@ -1,50 +1,50 @@ namespace Server.Engines.Mahjong { - public class MahjongWallBreakIndicator - { - public static MahjongPieceDim GetDimensions( Point2D position ) - { - return new MahjongPieceDim( position, 20, 20 ); - } + public class MahjongWallBreakIndicator + { + public MahjongWallBreakIndicator(MahjongGame game, Point2D position) + { + Game = game; + Position = position; + } - public MahjongGame Game { get; } + public MahjongWallBreakIndicator(MahjongGame game, GenericReader reader) + { + Game = game; - public Point2D Position { get; private set; } + int version = reader.ReadInt(); - public MahjongWallBreakIndicator( MahjongGame game, Point2D position ) - { - Game = game; - Position = position; - } + Position = reader.ReadPoint2D(); + } - public MahjongPieceDim Dimensions => GetDimensions( Position ); + public MahjongGame Game{ get; } - public void Move( Point2D position ) - { - MahjongPieceDim dim = GetDimensions( position ); + public Point2D Position{ get; private set; } - if ( !dim.IsValid() ) - return; + public MahjongPieceDim Dimensions => GetDimensions(Position); - Position = position; + public static MahjongPieceDim GetDimensions(Point2D position) + { + return new MahjongPieceDim(position, 20, 20); + } - Game.Players.SendGeneralPacket( true, true ); - } + public void Move(Point2D position) + { + MahjongPieceDim dim = GetDimensions(position); - public void Save( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version + if (!dim.IsValid()) + return; - writer.Write( Position ); - } + Position = position; - public MahjongWallBreakIndicator( MahjongGame game, GenericReader reader ) - { - Game = game; + Game.Players.SendGeneralPacket(true, true); + } - int version = reader.ReadInt(); + public void Save(GenericWriter writer) + { + writer.Write(0); // version - Position = reader.ReadPoint2D(); - } - } -} + writer.Write(Position); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Games/Mahjong/Packets.cs b/Scripts/Items/Games/Mahjong/Packets.cs index c4eef3a72..39be5ea77 100644 --- a/Scripts/Items/Games/Mahjong/Packets.cs +++ b/Scripts/Items/Games/Mahjong/Packets.cs @@ -1,206 +1,209 @@ +using System.IO; using Server.Network; namespace Server.Engines.Mahjong { - public sealed class MahjongJoinGame : Packet - { - public MahjongJoinGame( MahjongGame game ) : base( 0xDA ) - { - EnsureCapacity( 9 ); + public sealed class MahjongJoinGame : Packet + { + public MahjongJoinGame(MahjongGame game) : base(0xDA) + { + EnsureCapacity(9); - m_Stream.Write( (int) game.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0x19 ); - } - } + m_Stream.Write(game.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0x19); + } + } - public sealed class MahjongPlayersInfo : Packet - { - public MahjongPlayersInfo( MahjongGame game, Mobile to ) : base( 0xDA ) - { - MahjongPlayers players = game.Players; + public sealed class MahjongPlayersInfo : Packet + { + public MahjongPlayersInfo(MahjongGame game, Mobile to) : base(0xDA) + { + MahjongPlayers players = game.Players; - EnsureCapacity( 11 + 45 * players.Seats ); + EnsureCapacity(11 + 45 * players.Seats); - m_Stream.Write( (int) game.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0x2 ); + m_Stream.Write(game.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0x2); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) players.Seats ); + m_Stream.Write((byte)0); + m_Stream.Write((byte)players.Seats); - int n = 0; - for ( int i = 0; i < players.Seats; i++ ) - { - Mobile mobile = players.GetPlayer( i ); + int n = 0; + for (int i = 0; i < players.Seats; i++) + { + Mobile mobile = players.GetPlayer(i); - if ( mobile != null ) - { - m_Stream.Write( (int) mobile.Serial ); - m_Stream.Write( players.DealerPosition == i ? (byte) 0x1 : (byte) 0x2 ); - m_Stream.Write( (byte) i ); + if (mobile != null) + { + m_Stream.Write(mobile.Serial); + m_Stream.Write(players.DealerPosition == i ? (byte)0x1 : (byte)0x2); + m_Stream.Write((byte)i); - if ( game.ShowScores || mobile == to ) - m_Stream.Write( (int) players.GetScore( i ) ); - else - m_Stream.Write( (int) 0 ); + if (game.ShowScores || mobile == to) + m_Stream.Write(players.GetScore(i)); + else + m_Stream.Write(0); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (byte) 0 ); + m_Stream.Write((short)0); + m_Stream.Write((byte)0); - m_Stream.Write( players.IsPublic( i ) ); + m_Stream.Write(players.IsPublic(i)); - m_Stream.WriteAsciiFixed( mobile.Name, 30 ); - m_Stream.Write( !players.IsInGamePlayer( i ) ); + m_Stream.WriteAsciiFixed(mobile.Name, 30); + m_Stream.Write(!players.IsInGamePlayer(i)); - n++; - } - else if ( game.ShowScores ) - { - m_Stream.Write( (int) 0 ); - m_Stream.Write( (byte) 0x2 ); - m_Stream.Write( (byte) i ); + n++; + } + else if (game.ShowScores) + { + m_Stream.Write(0); + m_Stream.Write((byte)0x2); + m_Stream.Write((byte)i); - m_Stream.Write( (int) players.GetScore( i ) ); + m_Stream.Write(players.GetScore(i)); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (byte) 0 ); + m_Stream.Write((short)0); + m_Stream.Write((byte)0); - m_Stream.Write( players.IsPublic( i ) ); + m_Stream.Write(players.IsPublic(i)); - m_Stream.WriteAsciiFixed( "", 30 ); - m_Stream.Write( true ); + m_Stream.WriteAsciiFixed("", 30); + m_Stream.Write(true); - n++; - } - } + n++; + } + } - if ( n != players.Seats ) - { - m_Stream.Seek( 10, System.IO.SeekOrigin.Begin ); - m_Stream.Write( (byte) n ); - } - } - } + if (n != players.Seats) + { + m_Stream.Seek(10, SeekOrigin.Begin); + m_Stream.Write((byte)n); + } + } + } - public sealed class MahjongGeneralInfo : Packet - { - public MahjongGeneralInfo( MahjongGame game ) : base( 0xDA ) - { - EnsureCapacity( 13 ); + public sealed class MahjongGeneralInfo : Packet + { + public MahjongGeneralInfo(MahjongGame game) : base(0xDA) + { + EnsureCapacity(13); - m_Stream.Write( (int) game.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0x5 ); + m_Stream.Write(game.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0x5); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (byte) 0 ); + m_Stream.Write((short)0); + m_Stream.Write((byte)0); - m_Stream.Write( (byte) ((game.ShowScores ? 0x1 : 0x0) | (game.SpectatorVision ? 0x2 : 0x0)) ); + m_Stream.Write((byte)((game.ShowScores ? 0x1 : 0x0) | (game.SpectatorVision ? 0x2 : 0x0))); - m_Stream.Write( (byte) game.Dices.First ); - m_Stream.Write( (byte) game.Dices.Second ); + m_Stream.Write((byte)game.Dices.First); + m_Stream.Write((byte)game.Dices.Second); - m_Stream.Write( (byte) game.DealerIndicator.Wind ); - m_Stream.Write( (short) game.DealerIndicator.Position.Y ); - m_Stream.Write( (short) game.DealerIndicator.Position.X ); - m_Stream.Write( (byte) game.DealerIndicator.Direction ); + m_Stream.Write((byte)game.DealerIndicator.Wind); + m_Stream.Write((short)game.DealerIndicator.Position.Y); + m_Stream.Write((short)game.DealerIndicator.Position.X); + m_Stream.Write((byte)game.DealerIndicator.Direction); - m_Stream.Write( (short) game.WallBreakIndicator.Position.Y ); - m_Stream.Write( (short) game.WallBreakIndicator.Position.X ); - } - } + m_Stream.Write((short)game.WallBreakIndicator.Position.Y); + m_Stream.Write((short)game.WallBreakIndicator.Position.X); + } + } - public sealed class MahjongTilesInfo : Packet - { - public MahjongTilesInfo( MahjongGame game, Mobile to ) : base( 0xDA ) - { - MahjongTile[] tiles = game.Tiles; - MahjongPlayers players = game.Players; + public sealed class MahjongTilesInfo : Packet + { + public MahjongTilesInfo(MahjongGame game, Mobile to) : base(0xDA) + { + MahjongTile[] tiles = game.Tiles; + MahjongPlayers players = game.Players; - EnsureCapacity( 11 + 9 * tiles.Length ); + EnsureCapacity(11 + 9 * tiles.Length); - m_Stream.Write( (int) game.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0x4 ); + m_Stream.Write(game.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0x4); - m_Stream.Write( (short) tiles.Length ); + m_Stream.Write((short)tiles.Length); - foreach ( MahjongTile tile in tiles ) - { - m_Stream.Write( (byte) tile.Number ); + foreach (MahjongTile tile in tiles) + { + m_Stream.Write((byte)tile.Number); - if ( tile.Flipped ) - { - int hand = tile.Dimensions.GetHandArea(); + if (tile.Flipped) + { + int hand = tile.Dimensions.GetHandArea(); - if ( hand < 0 || players.IsPublic( hand ) || players.GetPlayer( hand ) == to || (game.SpectatorVision && players.IsSpectator( to )) ) - m_Stream.Write( (byte)tile.Value ); - else - m_Stream.Write( (byte) 0 ); - } - else - { - m_Stream.Write( (byte) 0 ); - } + if (hand < 0 || players.IsPublic(hand) || players.GetPlayer(hand) == to || + game.SpectatorVision && players.IsSpectator(to)) + m_Stream.Write((byte)tile.Value); + else + m_Stream.Write((byte)0); + } + else + { + m_Stream.Write((byte)0); + } - m_Stream.Write( (short) tile.Position.Y ); - m_Stream.Write( (short) tile.Position.X ); - m_Stream.Write( (byte) tile.StackLevel ); - m_Stream.Write( (byte) tile.Direction ); + m_Stream.Write((short)tile.Position.Y); + m_Stream.Write((short)tile.Position.X); + m_Stream.Write((byte)tile.StackLevel); + m_Stream.Write((byte)tile.Direction); - m_Stream.Write( tile.Flipped ? (byte) 0x10 : (byte) 0x0 ); - } - } - } + m_Stream.Write(tile.Flipped ? (byte)0x10 : (byte)0x0); + } + } + } - public sealed class MahjongTileInfo : Packet - { - public MahjongTileInfo( MahjongTile tile, Mobile to ) : base( 0xDA ) - { - MahjongGame game = tile.Game; - MahjongPlayers players = game.Players; + public sealed class MahjongTileInfo : Packet + { + public MahjongTileInfo(MahjongTile tile, Mobile to) : base(0xDA) + { + MahjongGame game = tile.Game; + MahjongPlayers players = game.Players; - EnsureCapacity( 18 ); + EnsureCapacity(18); - m_Stream.Write( (int) tile.Game.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0x3 ); + m_Stream.Write(tile.Game.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0x3); - m_Stream.Write( (byte) tile.Number ); + m_Stream.Write((byte)tile.Number); - if ( tile.Flipped ) - { - int hand = tile.Dimensions.GetHandArea(); + if (tile.Flipped) + { + int hand = tile.Dimensions.GetHandArea(); - if ( hand < 0 || players.IsPublic( hand ) || players.GetPlayer( hand ) == to || (game.SpectatorVision && players.IsSpectator( to )) ) - m_Stream.Write( (byte)tile.Value ); - else - m_Stream.Write( (byte) 0 ); - } - else - { - m_Stream.Write( (byte) 0 ); - } + if (hand < 0 || players.IsPublic(hand) || players.GetPlayer(hand) == to || + game.SpectatorVision && players.IsSpectator(to)) + m_Stream.Write((byte)tile.Value); + else + m_Stream.Write((byte)0); + } + else + { + m_Stream.Write((byte)0); + } - m_Stream.Write( (short) tile.Position.Y ); - m_Stream.Write( (short) tile.Position.X ); - m_Stream.Write( (byte) tile.StackLevel ); - m_Stream.Write( (byte) tile.Direction ); + m_Stream.Write((short)tile.Position.Y); + m_Stream.Write((short)tile.Position.X); + m_Stream.Write((byte)tile.StackLevel); + m_Stream.Write((byte)tile.Direction); - m_Stream.Write( tile.Flipped ? (byte) 0x10 : (byte) 0x0 ); - } - } + m_Stream.Write(tile.Flipped ? (byte)0x10 : (byte)0x0); + } + } - public sealed class MahjongRelieve : Packet - { - public MahjongRelieve( MahjongGame game ) : base( 0xDA ) - { - EnsureCapacity( 9 ); + public sealed class MahjongRelieve : Packet + { + public MahjongRelieve(MahjongGame game) : base(0xDA) + { + EnsureCapacity(9); - m_Stream.Write( (int) game.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0x1A ); - } - } + m_Stream.Write(game.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0x1A); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Amber.cs b/Scripts/Items/Gems/Amber.cs index a1c3746e2..53410017a 100644 --- a/Scripts/Items/Gems/Amber.cs +++ b/Scripts/Items/Gems/Amber.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Amber : Item - { - public override double DefaultWeight => 0.1; + public class Amber : Item + { + [Constructible] + public Amber() : this(1) + { + } - [Constructible] - public Amber() : this( 1 ) - { - } + [Constructible] + public Amber(int amount) : base(0xF25) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Amber( int amount ) : base( 0xF25 ) - { - Stackable = true; - Amount = amount; - } + public Amber(Serial serial) : base(serial) + { + } - public Amber( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Amethyst.cs b/Scripts/Items/Gems/Amethyst.cs index b95ba98a8..ee40435b6 100644 --- a/Scripts/Items/Gems/Amethyst.cs +++ b/Scripts/Items/Gems/Amethyst.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Amethyst : Item - { - public override double DefaultWeight => 0.1; + public class Amethyst : Item + { + [Constructible] + public Amethyst() : this(1) + { + } - [Constructible] - public Amethyst() : this( 1 ) - { - } + [Constructible] + public Amethyst(int amount) : base(0xF16) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Amethyst( int amount ) : base( 0xF16 ) - { - Stackable = true; - Amount = amount; - } + public Amethyst(Serial serial) : base(serial) + { + } - public Amethyst( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Citrine.cs b/Scripts/Items/Gems/Citrine.cs index b507e15d2..d71f748d7 100644 --- a/Scripts/Items/Gems/Citrine.cs +++ b/Scripts/Items/Gems/Citrine.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Citrine : Item - { - public override double DefaultWeight => 0.1; + public class Citrine : Item + { + [Constructible] + public Citrine() : this(1) + { + } - [Constructible] - public Citrine() : this( 1 ) - { - } + [Constructible] + public Citrine(int amount) : base(0xF15) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Citrine( int amount ) : base( 0xF15 ) - { - Stackable = true; - Amount = amount; - } + public Citrine(Serial serial) : base(serial) + { + } - public Citrine( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Diamond.cs b/Scripts/Items/Gems/Diamond.cs index 229a418bc..316f1cfad 100644 --- a/Scripts/Items/Gems/Diamond.cs +++ b/Scripts/Items/Gems/Diamond.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Diamond : Item - { - public override double DefaultWeight => 0.1; + public class Diamond : Item + { + [Constructible] + public Diamond() : this(1) + { + } - [Constructible] - public Diamond() : this( 1 ) - { - } + [Constructible] + public Diamond(int amount) : base(0xF26) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Diamond( int amount ) : base( 0xF26 ) - { - Stackable = true; - Amount = amount; - } + public Diamond(Serial serial) : base(serial) + { + } - public Diamond( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Emerald.cs b/Scripts/Items/Gems/Emerald.cs index 5fc727c68..0605bc44c 100644 --- a/Scripts/Items/Gems/Emerald.cs +++ b/Scripts/Items/Gems/Emerald.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Emerald : Item - { - public override double DefaultWeight => 0.1; + public class Emerald : Item + { + [Constructible] + public Emerald() : this(1) + { + } - [Constructible] - public Emerald() : this( 1 ) - { - } + [Constructible] + public Emerald(int amount) : base(0xF10) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Emerald( int amount ) : base( 0xF10 ) - { - Stackable = true; - Amount = amount; - } + public Emerald(Serial serial) : base(serial) + { + } - public Emerald( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Ruby.cs b/Scripts/Items/Gems/Ruby.cs index 1f52b38a3..74d6f5598 100644 --- a/Scripts/Items/Gems/Ruby.cs +++ b/Scripts/Items/Gems/Ruby.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Ruby : Item - { - public override double DefaultWeight => 0.1; + public class Ruby : Item + { + [Constructible] + public Ruby() : this(1) + { + } - [Constructible] - public Ruby() : this( 1 ) - { - } + [Constructible] + public Ruby(int amount) : base(0xF13) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Ruby( int amount ) : base( 0xF13 ) - { - Stackable = true; - Amount = amount; - } + public Ruby(Serial serial) : base(serial) + { + } - public Ruby( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Sapphire.cs b/Scripts/Items/Gems/Sapphire.cs index ef2a16144..5f776c0b5 100644 --- a/Scripts/Items/Gems/Sapphire.cs +++ b/Scripts/Items/Gems/Sapphire.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Sapphire : Item - { - public override double DefaultWeight => 0.1; + public class Sapphire : Item + { + [Constructible] + public Sapphire() : this(1) + { + } - [Constructible] - public Sapphire() : this( 1 ) - { - } + [Constructible] + public Sapphire(int amount) : base(0xF19) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Sapphire( int amount ) : base( 0xF19 ) - { - Stackable = true; - Amount = amount; - } + public Sapphire(Serial serial) : base(serial) + { + } - public Sapphire( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/StarSapphire.cs b/Scripts/Items/Gems/StarSapphire.cs index c4a2bb74a..1a89ce1d3 100644 --- a/Scripts/Items/Gems/StarSapphire.cs +++ b/Scripts/Items/Gems/StarSapphire.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class StarSapphire : Item - { - public override double DefaultWeight => 0.1; + public class StarSapphire : Item + { + [Constructible] + public StarSapphire() : this(1) + { + } - [Constructible] - public StarSapphire() : this( 1 ) - { - } + [Constructible] + public StarSapphire(int amount) : base(0xF21) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public StarSapphire( int amount ) : base( 0xF21 ) - { - Stackable = true; - Amount = amount; - } + public StarSapphire(Serial serial) : base(serial) + { + } - public StarSapphire( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Gems/Tourmaline.cs b/Scripts/Items/Gems/Tourmaline.cs index 1d77eb108..6f81db0c0 100644 --- a/Scripts/Items/Gems/Tourmaline.cs +++ b/Scripts/Items/Gems/Tourmaline.cs @@ -1,39 +1,38 @@ namespace Server.Items { - public class Tourmaline : Item - { - public override double DefaultWeight => 0.1; + public class Tourmaline : Item + { + [Constructible] + public Tourmaline() : this(1) + { + } - [Constructible] - public Tourmaline() : this( 1 ) - { - } + [Constructible] + public Tourmaline(int amount) : base(0xF2D) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Tourmaline( int amount ) : base( 0xF2D ) - { - Stackable = true; - Amount = amount; - } + public Tourmaline(Serial serial) : base(serial) + { + } - public Tourmaline( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Guilds/GuildDeed.cs b/Scripts/Items/Guilds/GuildDeed.cs index d25155223..adafeffe2 100644 --- a/Scripts/Items/Guilds/GuildDeed.cs +++ b/Scripts/Items/Guilds/GuildDeed.cs @@ -1,140 +1,140 @@ -using Server.Prompts; using Server.Guilds; using Server.Multis; +using Server.Prompts; namespace Server.Items { - public class GuildDeed : Item - { - public override int LabelNumber => 1041055; // a guild deed + public class GuildDeed : Item + { + [Constructible] + public GuildDeed() : base(0x14F0) + { + Weight = 1.0; + } - [Constructible] - public GuildDeed() : base( 0x14F0 ) - { - Weight = 1.0; - } + public GuildDeed(Serial serial) : base(serial) + { + } - public GuildDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041055; // a guild deed - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 0.0 ) - Weight = 1.0; - } + if (Weight == 0.0) + Weight = 1.0; + } - public override void OnDoubleClick( Mobile from ) - { - if ( Guild.NewGuildSystem ) - return; + public override void OnDoubleClick(Mobile from) + { + if (Guild.NewGuildSystem) + return; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.Guild != null ) - { - from.SendLocalizedMessage( 501137 ); // You must resign from your current guild before founding another! - } - else - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.Guild != null) + { + from.SendLocalizedMessage(501137); // You must resign from your current guild before founding another! + } + else + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house == null ) - { - from.SendLocalizedMessage( 501138 ); // You can only place a guildstone in a house. - } - else if ( house.FindGuildstone() != null ) - { - from.SendLocalizedMessage( 501142 );//Only one guildstone may reside in a given house. - } - else if ( !house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 501141 ); // You can only place a guildstone in a house you own! - } - else - { - from.SendLocalizedMessage( 1013060 ); // Enter new guild name (40 characters max): - from.Prompt = new InternalPrompt( this ); - } - } - } + if (house == null) + { + from.SendLocalizedMessage(501138); // You can only place a guildstone in a house. + } + else if (house.FindGuildstone() != null) + { + from.SendLocalizedMessage(501142); //Only one guildstone may reside in a given house. + } + else if (!house.IsOwner(from)) + { + from.SendLocalizedMessage(501141); // You can only place a guildstone in a house you own! + } + else + { + from.SendLocalizedMessage(1013060); // Enter new guild name (40 characters max): + from.Prompt = new InternalPrompt(this); + } + } + } - private class InternalPrompt : Prompt - { - private GuildDeed m_Deed; + private class InternalPrompt : Prompt + { + private GuildDeed m_Deed; - public InternalPrompt( GuildDeed deed ) - { - m_Deed = deed; - } + public InternalPrompt(GuildDeed deed) + { + m_Deed = deed; + } - public override void OnResponse( Mobile from, string text ) - { - if ( m_Deed.Deleted ) - return; + public override void OnResponse(Mobile from, string text) + { + if (m_Deed.Deleted) + return; - if ( !m_Deed.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.Guild != null ) - { - from.SendLocalizedMessage( 501137 ); // You must resign from your current guild before founding another! - } - else - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (!m_Deed.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.Guild != null) + { + from.SendLocalizedMessage(501137); // You must resign from your current guild before founding another! + } + else + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house == null ) - { - from.SendLocalizedMessage( 501138 ); // You can only place a guildstone in a house. - } - else if ( house.FindGuildstone() != null ) - { - from.SendLocalizedMessage( 501142 );//Only one guildstone may reside in a given house. - } - else if ( !house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 501141 ); // You can only place a guildstone in a house you own! - } - else - { - m_Deed.Delete(); + if (house == null) + { + from.SendLocalizedMessage(501138); // You can only place a guildstone in a house. + } + else if (house.FindGuildstone() != null) + { + from.SendLocalizedMessage(501142); //Only one guildstone may reside in a given house. + } + else if (!house.IsOwner(from)) + { + from.SendLocalizedMessage(501141); // You can only place a guildstone in a house you own! + } + else + { + m_Deed.Delete(); - if ( text.Length > 40 ) - text = text.Substring( 0, 40 ); + if (text.Length > 40) + text = text.Substring(0, 40); - Guild guild = new Guild( from, text, "none" ); + Guild guild = new Guild(from, text, "none"); - from.Guild = guild; - from.GuildTitle = "Guildmaster"; + from.Guild = guild; + from.GuildTitle = "Guildmaster"; - Guildstone stone = new Guildstone( guild ); + Guildstone stone = new Guildstone(guild); - stone.MoveToWorld( from.Location, from.Map ); + stone.MoveToWorld(from.Location, from.Map); - guild.Guildstone = stone; - } - } - } + guild.Guildstone = stone; + } + } + } - public override void OnCancel( Mobile from ) - { - from.SendLocalizedMessage( 501145 ); // Placement of guildstone cancelled. - } - } - } -} + public override void OnCancel(Mobile from) + { + from.SendLocalizedMessage(501145); // Placement of guildstone cancelled. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Guilds/GuildTeleporter.cs b/Scripts/Items/Guilds/GuildTeleporter.cs index 090e2f12c..a7de75a93 100644 --- a/Scripts/Items/Guilds/GuildTeleporter.cs +++ b/Scripts/Items/Guilds/GuildTeleporter.cs @@ -3,99 +3,99 @@ using Server.Multis; namespace Server.Items { - public class GuildTeleporter : Item - { - private Item m_Stone; + public class GuildTeleporter : Item + { + private Item m_Stone; - public override int LabelNumber => 1041054; // guildstone teleporter + [Constructible] + public GuildTeleporter() : this(null) + { + } - [Constructible] - public GuildTeleporter() : this( null ) - { - } + public GuildTeleporter(Item stone) : base(0x1869) + { + Weight = 1.0; + LootType = LootType.Blessed; - public GuildTeleporter( Item stone ) : base( 0x1869 ) - { - Weight = 1.0; - LootType = LootType.Blessed; + m_Stone = stone; + } - m_Stone = stone; - } + public GuildTeleporter(Serial serial) : base(serial) + { + } - public GuildTeleporter( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041054; // guildstone teleporter - public override bool DisplayLootType => false; + public override bool DisplayLootType => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Stone ); - } + writer.Write(m_Stone); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Stone = reader.ReadItem(); + switch (version) + { + case 0: + { + m_Stone = reader.ReadItem(); - break; - } - } + break; + } + } - if ( Weight == 0.0 ) - Weight = 1.0; - } + if (Weight == 0.0) + Weight = 1.0; + } - public override void OnDoubleClick( Mobile from ) - { - if ( Guild.NewGuildSystem ) - return; + public override void OnDoubleClick(Mobile from) + { + if (Guild.NewGuildSystem) + return; - Guildstone stone = m_Stone as Guildstone; + Guildstone stone = m_Stone as Guildstone; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( stone == null || stone.Deleted || stone.Guild == null || stone.Guild.Teleporter != this ) - { - from.SendLocalizedMessage( 501197 ); // This teleporting object can not determine what guildstone to teleport - } - else - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (stone == null || stone.Deleted || stone.Guild == null || stone.Guild.Teleporter != this) + { + from.SendLocalizedMessage(501197); // This teleporting object can not determine what guildstone to teleport + } + else + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house == null ) - { - from.SendLocalizedMessage( 501138 ); // You can only place a guildstone in a house. - } - else if ( !house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 501141 ); // You can only place a guildstone in a house you own! - } - else if ( house.FindGuildstone() != null ) - { - from.SendLocalizedMessage( 501142 );//Only one guildstone may reside in a given house. - } - else - { - m_Stone.MoveToWorld( from.Location, from.Map ); - Delete(); - stone.Guild.Teleporter = null; - } - } - } - } -} + if (house == null) + { + from.SendLocalizedMessage(501138); // You can only place a guildstone in a house. + } + else if (!house.IsOwner(from)) + { + from.SendLocalizedMessage(501141); // You can only place a guildstone in a house you own! + } + else if (house.FindGuildstone() != null) + { + from.SendLocalizedMessage(501142); //Only one guildstone may reside in a given house. + } + else + { + m_Stone.MoveToWorld(from.Location, from.Map); + Delete(); + stone.Guild.Teleporter = null; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Guilds/Guildstone.cs b/Scripts/Items/Guilds/Guildstone.cs index 80e997d2d..9682db78d 100644 --- a/Scripts/Items/Guilds/Guildstone.cs +++ b/Scripts/Items/Guilds/Guildstone.cs @@ -1,427 +1,446 @@ using System; -using Server.Gumps; -using Server.Guilds; -using Server.Network; using Server.Factions; +using Server.Guilds; +using Server.Gumps; using Server.Multis; +using Server.Network; +using Server.Targeting; namespace Server.Items { - public class Guildstone : Item, IAddon, IChopable - { - private string m_GuildName; - private string m_GuildAbbrev; - - [CommandProperty( AccessLevel.GameMaster )] - public string GuildName - { - get => m_GuildName; - set { m_GuildName = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string GuildAbbrev - { - get => m_GuildAbbrev; - set { m_GuildAbbrev = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Guild Guild { get; private set; } - - public override int LabelNumber => 1041429; // a guildstone - - public Guildstone( Guild g ) : this( g, g.Name, g.Abbreviation ) - { - } - - public Guildstone( Guild g, string guildName, string abbrev ) : base( Guild.NewGuildSystem ? 0xED6 : 0xED4 ) - { - Guild = g; - m_GuildName = guildName; - m_GuildAbbrev = abbrev; - - Movable = false; - } - - public Guildstone( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - if ( Guild != null && !Guild.Disbanded ) - { - m_GuildName = Guild.Name; - m_GuildAbbrev = Guild.Abbreviation; - } - - writer.Write( (int)3 ); // version - - writer.Write( m_BeforeChangeover ); - - writer.Write( m_GuildName ); - writer.Write( m_GuildAbbrev ); - - writer.Write( Guild ); - } - - private bool m_BeforeChangeover; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch( version ) - { - case 3: - { - m_BeforeChangeover = reader.ReadBool(); - goto case 2; - } - case 2: - { - m_GuildName = reader.ReadString(); - m_GuildAbbrev = reader.ReadString(); - - goto case 1; - } - case 1: - { - Guild = reader.ReadGuild() as Guild; - - goto case 0; - } - case 0: - { - break; - } - } - - if ( Guild.NewGuildSystem && ItemID == 0xED4 ) - ItemID = 0xED6; - - if ( version <= 2 ) - m_BeforeChangeover = true; - - if ( Guild.NewGuildSystem && m_BeforeChangeover ) - Timer.DelayCall( TimeSpan.Zero, AddToHouse ); - - if ( !Guild.NewGuildSystem && Guild == null ) - Delete(); - } - - private void AddToHouse() - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( Guild.NewGuildSystem && m_BeforeChangeover && house != null && !house.Addons.Contains( this ) ) - { - house.Addons.Add( this ); - m_BeforeChangeover = false; - } - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Guild != null && !Guild.Disbanded ) - { - string name; - string abbr; - - if ( (name = Guild.Name) == null || (name = name.Trim()).Length <= 0 ) - name = "(unnamed)"; - - if ( (abbr = Guild.Abbreviation) == null || (abbr = abbr.Trim()).Length <= 0 ) - abbr = ""; - - //list.Add( 1060802, Utility.FixHtml( name ) ); // Guild name: ~1_val~ - list.Add( 1060802, $"{Utility.FixHtml(name)} [{Utility.FixHtml(abbr)}]"); - } - else if ( m_GuildName != null && m_GuildAbbrev != null ) - { - list.Add( 1060802, $"{Utility.FixHtml(m_GuildName)} [{Utility.FixHtml(m_GuildAbbrev)}]"); - } - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( Guild != null && !Guild.Disbanded ) - { - string name; - - if ( (name = Guild.Name) == null || (name = name.Trim()).Length <= 0 ) - name = "(unnamed)"; - - LabelTo( from, name ); - } - else if ( m_GuildName != null ) - { - LabelTo( from, m_GuildName ); - } - } - - public override void OnAfterDelete() - { - if ( !Guild.NewGuildSystem && Guild != null && !Guild.Disbanded ) - Guild.Disband(); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( Guild.NewGuildSystem ) - return; - - if ( Guild == null || Guild.Disbanded ) - { - Delete(); - } - else if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( Guild.Accepted.Contains( from ) ) - { - #region Factions - PlayerState guildState = PlayerState.Find( Guild.Leader ); - PlayerState targetState = PlayerState.Find( from ); - - Faction guildFaction = guildState?.Faction; - Faction targetFaction = targetState?.Faction; - - if ( guildFaction != targetFaction || (targetState != null && targetState.IsLeaving) ) - return; - - if ( guildState != null && targetState != null ) - targetState.Leaving = guildState.Leaving; - #endregion - - Guild.Accepted.Remove( from ); - Guild.AddMember( from ); - - GuildGump.EnsureClosed( from ); - from.SendGump( new GuildGump( from, Guild ) ); - } - else if ( from.AccessLevel < AccessLevel.GameMaster && !Guild.IsMember( from ) ) - { - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, 501158, "", "" ) ); // You are not a member ... - } - else - { - GuildGump.EnsureClosed( from ); - from.SendGump( new GuildGump( from, Guild ) ); - } - } - - #region IAddon Members - public Item Deed => new GuildstoneDeed( Guild, m_GuildName, m_GuildAbbrev ); - - public bool CouldFit( IPoint3D p, Map map ) - { - return map.CanFit( p.X, p.Y, p.Z, ItemData.Height ); - } - - #endregion - - #region IChopable Members - - public void OnChop( Mobile from ) - { - if ( !Guild.NewGuildSystem ) - return; - - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( ( house == null && m_BeforeChangeover ) || ( house != null && house.IsOwner( from ) && house.Addons.Contains( this ) )) - { - Effects.PlaySound( GetWorldLocation(), Map, 0x3B3 ); - from.SendLocalizedMessage( 500461 ); // You destroy the item. - - Delete(); - - if ( house != null && house.Addons.Contains( this ) ) - house.Addons.Remove( this ); - - Item deed = Deed; - - if ( deed != null ) - { - from.AddToBackpack( deed ); - } - } - } - - #endregion - } - - [Flippable( 0x14F0, 0x14EF )] - public class GuildstoneDeed : Item - { - public override int LabelNumber => 1041233; // deed to a guildstone - - private string m_GuildName; - private string m_GuildAbbrev; - - [CommandProperty( AccessLevel.GameMaster )] - public string GuildName - { - get => m_GuildName; - set { m_GuildName = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string GuildAbbrev - { - get => m_GuildAbbrev; - set { m_GuildAbbrev = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Guild Guild { get; private set; } - - [Constructible] - public GuildstoneDeed() : this( null, null ) - { - } - - [Constructible] - public GuildstoneDeed( string guildName, string abbrev ) : this( null, guildName, abbrev ) - { - } - - public GuildstoneDeed( Guild g, string guildName, string abbrev ) : base( 0x14F0 ) - { - Guild = g; - m_GuildName = guildName; - m_GuildAbbrev = abbrev; - - Weight = 1.0; - } - - public GuildstoneDeed( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - if ( Guild != null && !Guild.Disbanded ) - { - m_GuildName = Guild.Name; - m_GuildAbbrev = Guild.Abbreviation; - } - - writer.Write( (int)1 ); // version - - writer.Write( m_GuildName ); - writer.Write( m_GuildAbbrev ); - - writer.Write( Guild ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_GuildName = reader.ReadString(); - m_GuildAbbrev = reader.ReadString(); - - Guild = reader.ReadGuild() as Guild; - - break; - } - } - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Guild != null && !Guild.Disbanded ) - { - string name; - string abbr; - - if ( (name = Guild.Name) == null || (name = name.Trim()).Length <= 0 ) - name = "(unnamed)"; - - if ( (abbr = Guild.Abbreviation) == null || (abbr = abbr.Trim()).Length <= 0 ) - abbr = ""; - - //list.Add( 1060802, Utility.FixHtml( name ) ); // Guild name: ~1_val~ - list.Add( 1060802, $"{Utility.FixHtml(name)} [{Utility.FixHtml(abbr)}]"); - } - else if ( m_GuildName != null && m_GuildAbbrev != null ) - { - list.Add( 1060802, $"{Utility.FixHtml(m_GuildName)} [{Utility.FixHtml(m_GuildAbbrev)}]"); - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 1062838 ); // Where would you like to place this decoration? - from.BeginTarget( -1, true, Targeting.TargetFlags.None, Placement_OnTarget, null ); - } - else - { - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - - public void Placement_OnTarget( Mobile from, object targeted, object state ) - { - if ( !(targeted is IPoint3D p) || Deleted ) - return; - - Point3D loc = new Point3D( p ); - - BaseHouse house = BaseHouse.FindHouseAt( loc, from.Map, 16 ); - - if ( IsChildOf( from.Backpack ) ) - { - if ( house != null && house.IsOwner( from ) ) - { - Item addon = new Guildstone( Guild, m_GuildName, m_GuildAbbrev ); - - addon.MoveToWorld( loc, from.Map ); - - house.Addons.Add( addon ); - Delete(); - } - else - { - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - } -} + public class Guildstone : Item, IAddon, IChopable + { + private bool m_BeforeChangeover; + private string m_GuildAbbrev; + private string m_GuildName; + + public Guildstone(Guild g) : this(g, g.Name, g.Abbreviation) + { + } + + public Guildstone(Guild g, string guildName, string abbrev) : base(Guild.NewGuildSystem ? 0xED6 : 0xED4) + { + Guild = g; + m_GuildName = guildName; + m_GuildAbbrev = abbrev; + + Movable = false; + } + + public Guildstone(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string GuildName + { + get => m_GuildName; + set + { + m_GuildName = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string GuildAbbrev + { + get => m_GuildAbbrev; + set + { + m_GuildAbbrev = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Guild Guild{ get; private set; } + + public override int LabelNumber => 1041429; // a guildstone + + #region IChopable Members + + public void OnChop(Mobile from) + { + if (!Guild.NewGuildSystem) + return; + + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house == null && m_BeforeChangeover || house != null && house.IsOwner(from) && house.Addons.Contains(this)) + { + Effects.PlaySound(GetWorldLocation(), Map, 0x3B3); + from.SendLocalizedMessage(500461); // You destroy the item. + + Delete(); + + if (house != null && house.Addons.Contains(this)) + house.Addons.Remove(this); + + Item deed = Deed; + + if (deed != null) from.AddToBackpack(deed); + } + } + + #endregion + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + if (Guild != null && !Guild.Disbanded) + { + m_GuildName = Guild.Name; + m_GuildAbbrev = Guild.Abbreviation; + } + + writer.Write(3); // version + + writer.Write(m_BeforeChangeover); + + writer.Write(m_GuildName); + writer.Write(m_GuildAbbrev); + + writer.Write(Guild); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + m_BeforeChangeover = reader.ReadBool(); + goto case 2; + } + case 2: + { + m_GuildName = reader.ReadString(); + m_GuildAbbrev = reader.ReadString(); + + goto case 1; + } + case 1: + { + Guild = reader.ReadGuild() as Guild; + + goto case 0; + } + case 0: + { + break; + } + } + + if (Guild.NewGuildSystem && ItemID == 0xED4) + ItemID = 0xED6; + + if (version <= 2) + m_BeforeChangeover = true; + + if (Guild.NewGuildSystem && m_BeforeChangeover) + Timer.DelayCall(TimeSpan.Zero, AddToHouse); + + if (!Guild.NewGuildSystem && Guild == null) + Delete(); + } + + private void AddToHouse() + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (Guild.NewGuildSystem && m_BeforeChangeover && house != null && !house.Addons.Contains(this)) + { + house.Addons.Add(this); + m_BeforeChangeover = false; + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Guild != null && !Guild.Disbanded) + { + string name; + string abbr; + + if ((name = Guild.Name) == null || (name = name.Trim()).Length <= 0) + name = "(unnamed)"; + + if ((abbr = Guild.Abbreviation) == null || (abbr = abbr.Trim()).Length <= 0) + abbr = ""; + + //list.Add( 1060802, Utility.FixHtml( name ) ); // Guild name: ~1_val~ + list.Add(1060802, $"{Utility.FixHtml(name)} [{Utility.FixHtml(abbr)}]"); + } + else if (m_GuildName != null && m_GuildAbbrev != null) + { + list.Add(1060802, $"{Utility.FixHtml(m_GuildName)} [{Utility.FixHtml(m_GuildAbbrev)}]"); + } + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (Guild != null && !Guild.Disbanded) + { + string name; + + if ((name = Guild.Name) == null || (name = name.Trim()).Length <= 0) + name = "(unnamed)"; + + LabelTo(from, name); + } + else if (m_GuildName != null) + { + LabelTo(from, m_GuildName); + } + } + + public override void OnAfterDelete() + { + if (!Guild.NewGuildSystem && Guild != null && !Guild.Disbanded) + Guild.Disband(); + } + + public override void OnDoubleClick(Mobile from) + { + if (Guild.NewGuildSystem) + return; + + if (Guild == null || Guild.Disbanded) + { + Delete(); + } + else if (!from.InRange(GetWorldLocation(), 2)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (Guild.Accepted.Contains(from)) + { + #region Factions + + PlayerState guildState = PlayerState.Find(Guild.Leader); + PlayerState targetState = PlayerState.Find(from); + + Faction guildFaction = guildState?.Faction; + Faction targetFaction = targetState?.Faction; + + if (guildFaction != targetFaction || targetState != null && targetState.IsLeaving) + return; + + if (guildState != null && targetState != null) + targetState.Leaving = guildState.Leaving; + + #endregion + + Guild.Accepted.Remove(from); + Guild.AddMember(from); + + GuildGump.EnsureClosed(from); + from.SendGump(new GuildGump(from, Guild)); + } + else if (from.AccessLevel < AccessLevel.GameMaster && !Guild.IsMember(from)) + { + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, 501158, "", + "")); // You are not a member ... + } + else + { + GuildGump.EnsureClosed(from); + from.SendGump(new GuildGump(from, Guild)); + } + } + + #region IAddon Members + + public Item Deed => new GuildstoneDeed(Guild, m_GuildName, m_GuildAbbrev); + + public bool CouldFit(IPoint3D p, Map map) + { + return map.CanFit(p.X, p.Y, p.Z, ItemData.Height); + } + + #endregion + } + + [Flippable(0x14F0, 0x14EF)] + public class GuildstoneDeed : Item + { + private string m_GuildAbbrev; + + private string m_GuildName; + + [Constructible] + public GuildstoneDeed() : this(null, null) + { + } + + [Constructible] + public GuildstoneDeed(string guildName, string abbrev) : this(null, guildName, abbrev) + { + } + + public GuildstoneDeed(Guild g, string guildName, string abbrev) : base(0x14F0) + { + Guild = g; + m_GuildName = guildName; + m_GuildAbbrev = abbrev; + + Weight = 1.0; + } + + public GuildstoneDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041233; // deed to a guildstone + + [CommandProperty(AccessLevel.GameMaster)] + public string GuildName + { + get => m_GuildName; + set + { + m_GuildName = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string GuildAbbrev + { + get => m_GuildAbbrev; + set + { + m_GuildAbbrev = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Guild Guild{ get; private set; } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + if (Guild != null && !Guild.Disbanded) + { + m_GuildName = Guild.Name; + m_GuildAbbrev = Guild.Abbreviation; + } + + writer.Write(1); // version + + writer.Write(m_GuildName); + writer.Write(m_GuildAbbrev); + + writer.Write(Guild); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_GuildName = reader.ReadString(); + m_GuildAbbrev = reader.ReadString(); + + Guild = reader.ReadGuild() as Guild; + + break; + } + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Guild != null && !Guild.Disbanded) + { + string name; + string abbr; + + if ((name = Guild.Name) == null || (name = name.Trim()).Length <= 0) + name = "(unnamed)"; + + if ((abbr = Guild.Abbreviation) == null || (abbr = abbr.Trim()).Length <= 0) + abbr = ""; + + //list.Add( 1060802, Utility.FixHtml( name ) ); // Guild name: ~1_val~ + list.Add(1060802, $"{Utility.FixHtml(name)} [{Utility.FixHtml(abbr)}]"); + } + else if (m_GuildName != null && m_GuildAbbrev != null) + { + list.Add(1060802, $"{Utility.FixHtml(m_GuildName)} [{Utility.FixHtml(m_GuildAbbrev)}]"); + } + } + + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsOwner(from)) + { + from.SendLocalizedMessage(1062838); // Where would you like to place this decoration? + from.BeginTarget(-1, true, TargetFlags.None, Placement_OnTarget, null); + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + + public void Placement_OnTarget(Mobile from, object targeted, object state) + { + if (!(targeted is IPoint3D p) || Deleted) + return; + + Point3D loc = new Point3D(p); + + BaseHouse house = BaseHouse.FindHouseAt(loc, from.Map, 16); + + if (IsChildOf(from.Backpack)) + { + if (house != null && house.IsOwner(from)) + { + Item addon = new Guildstone(Guild, m_GuildName, m_GuildAbbrev); + + addon.MoveToWorld(loc, from.Map); + + house.Addons.Add(addon); + Delete(); + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/BraceletOfHealth.cs b/Scripts/Items/Jewels/Artifacts/BraceletOfHealth.cs index 7ef013602..cbaf3a310 100644 --- a/Scripts/Items/Jewels/Artifacts/BraceletOfHealth.cs +++ b/Scripts/Items/Jewels/Artifacts/BraceletOfHealth.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public class BraceletOfHealth : GoldBracelet - { - public override int LabelNumber => 1061103; // Bracelet of Health - public override int ArtifactRarity => 11; + public class BraceletOfHealth : GoldBracelet + { + [Constructible] + public BraceletOfHealth() + { + Hue = 0x21; + Attributes.BonusHits = 5; + Attributes.RegenHits = 10; + } - [Constructible] - public BraceletOfHealth() - { - Hue = 0x21; - Attributes.BonusHits = 5; - Attributes.RegenHits = 10; - } + public BraceletOfHealth(Serial serial) : base(serial) + { + } - public BraceletOfHealth( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1061103; // Bracelet of Health + public override int ArtifactRarity => 11; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/Craftable/EssenceOfBattle.cs b/Scripts/Items/Jewels/Artifacts/Craftable/EssenceOfBattle.cs index d1495b242..8321091ca 100644 --- a/Scripts/Items/Jewels/Artifacts/Craftable/EssenceOfBattle.cs +++ b/Scripts/Items/Jewels/Artifacts/Craftable/EssenceOfBattle.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public class EssenceOfBattle : GoldRing - { - public override int LabelNumber => 1072935; // Essence of Battle + public class EssenceOfBattle : GoldRing + { + [Constructible] + public EssenceOfBattle() + { + Hue = 0x550; + Attributes.BonusDex = 7; + Attributes.BonusStr = 7; + Attributes.WeaponDamage = 30; + } - [Constructible] - public EssenceOfBattle() - { - Hue = 0x550; - Attributes.BonusDex = 7; - Attributes.BonusStr = 7; - Attributes.WeaponDamage = 30; - } + public EssenceOfBattle(Serial serial) : base(serial) + { + } - public EssenceOfBattle( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072935; // Essence of Battle - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/Craftable/PendantOfTheMagi.cs b/Scripts/Items/Jewels/Artifacts/Craftable/PendantOfTheMagi.cs index c2b883333..21a3514e9 100644 --- a/Scripts/Items/Jewels/Artifacts/Craftable/PendantOfTheMagi.cs +++ b/Scripts/Items/Jewels/Artifacts/Craftable/PendantOfTheMagi.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class PendantOfTheMagi : GoldNecklace - { - public override int LabelNumber => 1072937; // Pendant of the Magi + public class PendantOfTheMagi : GoldNecklace + { + [Constructible] + public PendantOfTheMagi() + { + Hue = 0x48D; + Attributes.BonusInt = 10; + Attributes.RegenMana = 3; + Attributes.SpellDamage = 5; + Attributes.LowerManaCost = 10; + Attributes.LowerRegCost = 30; + } - [Constructible] - public PendantOfTheMagi() - { - Hue = 0x48D; - Attributes.BonusInt = 10; - Attributes.RegenMana = 3; - Attributes.SpellDamage = 5; - Attributes.LowerManaCost = 10; - Attributes.LowerRegCost = 30; - } + public PendantOfTheMagi(Serial serial) : base(serial) + { + } - public PendantOfTheMagi( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072937; // Pendant of the Magi - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/Craftable/ResillientBracer.cs b/Scripts/Items/Jewels/Artifacts/Craftable/ResillientBracer.cs index e01e24274..364828ca4 100644 --- a/Scripts/Items/Jewels/Artifacts/Craftable/ResillientBracer.cs +++ b/Scripts/Items/Jewels/Artifacts/Craftable/ResillientBracer.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ResilientBracer : GoldBracelet - { - public override int LabelNumber => 1072933; // Resillient Bracer + public class ResilientBracer : GoldBracelet + { + [Constructible] + public ResilientBracer() + { + Hue = 0x488; - public override int PhysicalResistance => 20; + SkillBonuses.SetValues(0, SkillName.MagicResist, 15.0); - [Constructible] - public ResilientBracer() - { - Hue = 0x488; + Attributes.BonusHits = 5; + Attributes.RegenHits = 2; + Attributes.DefendChance = 10; + } - SkillBonuses.SetValues( 0, SkillName.MagicResist, 15.0 ); + public ResilientBracer(Serial serial) : base(serial) + { + } - Attributes.BonusHits = 5; - Attributes.RegenHits = 2; - Attributes.DefendChance = 10; - } + public override int LabelNumber => 1072933; // Resillient Bracer - public ResilientBracer( Serial serial ) : base( serial ) - { - } + public override int PhysicalResistance => 20; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/OrnamentOfTheMagician.cs b/Scripts/Items/Jewels/Artifacts/OrnamentOfTheMagician.cs index 7a3234c1f..121e7fb3a 100644 --- a/Scripts/Items/Jewels/Artifacts/OrnamentOfTheMagician.cs +++ b/Scripts/Items/Jewels/Artifacts/OrnamentOfTheMagician.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class OrnamentOfTheMagician : GoldBracelet - { - public override int LabelNumber => 1061105; // Ornament of the Magician - public override int ArtifactRarity => 11; + public class OrnamentOfTheMagician : GoldBracelet + { + [Constructible] + public OrnamentOfTheMagician() + { + Hue = 0x554; + Attributes.CastRecovery = 3; + Attributes.CastSpeed = 2; + Attributes.LowerManaCost = 10; + Attributes.LowerRegCost = 20; + Resistances.Energy = 15; + } - [Constructible] - public OrnamentOfTheMagician() - { - Hue = 0x554; - Attributes.CastRecovery = 3; - Attributes.CastSpeed = 2; - Attributes.LowerManaCost = 10; - Attributes.LowerRegCost = 20; - Resistances.Energy = 15; - } + public OrnamentOfTheMagician(Serial serial) : base(serial) + { + } - public OrnamentOfTheMagician( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1061105; // Ornament of the Magician + public override int ArtifactRarity => 11; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 0x12B ) - Hue = 0x554; - } - } -} + if (Hue == 0x12B) + Hue = 0x554; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/RingOfTheElements.cs b/Scripts/Items/Jewels/Artifacts/RingOfTheElements.cs index 7848bc742..c11bade20 100644 --- a/Scripts/Items/Jewels/Artifacts/RingOfTheElements.cs +++ b/Scripts/Items/Jewels/Artifacts/RingOfTheElements.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class RingOfTheElements : GoldRing - { - public override int LabelNumber => 1061104; // Ring of the Elements - public override int ArtifactRarity => 11; + public class RingOfTheElements : GoldRing + { + [Constructible] + public RingOfTheElements() + { + Hue = 0x4E9; + Attributes.Luck = 100; + Resistances.Fire = 16; + Resistances.Cold = 16; + Resistances.Poison = 16; + Resistances.Energy = 16; + } - [Constructible] - public RingOfTheElements() - { - Hue = 0x4E9; - Attributes.Luck = 100; - Resistances.Fire = 16; - Resistances.Cold = 16; - Resistances.Poison = 16; - Resistances.Energy = 16; - } + public RingOfTheElements(Serial serial) : base(serial) + { + } - public RingOfTheElements( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1061104; // Ring of the Elements + public override int ArtifactRarity => 11; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Artifacts/RingOfTheVile.cs b/Scripts/Items/Jewels/Artifacts/RingOfTheVile.cs index 7453c92de..e2b0da4dc 100644 --- a/Scripts/Items/Jewels/Artifacts/RingOfTheVile.cs +++ b/Scripts/Items/Jewels/Artifacts/RingOfTheVile.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class RingOfTheVile : GoldRing - { - public override int LabelNumber => 1061102; // Ring of the Vile - public override int ArtifactRarity => 11; + public class RingOfTheVile : GoldRing + { + [Constructible] + public RingOfTheVile() + { + Hue = 0x4F7; + Attributes.BonusDex = 8; + Attributes.RegenStam = 6; + Attributes.AttackChance = 15; + Resistances.Poison = 20; + } - [Constructible] - public RingOfTheVile() - { - Hue = 0x4F7; - Attributes.BonusDex = 8; - Attributes.RegenStam = 6; - Attributes.AttackChance = 15; - Resistances.Poison = 20; - } + public RingOfTheVile(Serial serial) : base(serial) + { + } - public RingOfTheVile( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1061102; // Ring of the Vile + public override int ArtifactRarity => 11; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 0x4F4 ) - Hue = 0x4F7; - } - } -} + if (Hue == 0x4F4) + Hue = 0x4F7; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/BaseJewel.cs b/Scripts/Items/Jewels/BaseJewel.cs index 1fc5cdca3..6220d68ef 100644 --- a/Scripts/Items/Jewels/BaseJewel.cs +++ b/Scripts/Items/Jewels/BaseJewel.cs @@ -3,407 +3,420 @@ using Server.Engines.Craft; namespace Server.Items { - public enum GemType - { - None, - StarSapphire, - Emerald, - Sapphire, - Ruby, - Citrine, - Amethyst, - Tourmaline, - Amber, - Diamond - } - - public abstract class BaseJewel : Item, ICraftable - { - private int m_MaxHitPoints; - private int m_HitPoints; - - private AosAttributes m_AosAttributes; - private AosElementAttributes m_AosResistances; - private AosSkillBonuses m_AosSkillBonuses; - private CraftResource m_Resource; - private GemType m_GemType; - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxHitPoints - { - get => m_MaxHitPoints; - set{ m_MaxHitPoints = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitPoints - { - get => m_HitPoints; - set - { - if ( value != m_HitPoints && MaxHitPoints > 0 ) - { - m_HitPoints = value; - - if ( m_HitPoints < 0 ) - Delete(); - else if ( m_HitPoints > MaxHitPoints ) - m_HitPoints = MaxHitPoints; - - InvalidateProperties(); - } - } - } - - [CommandProperty( AccessLevel.Player )] - public AosAttributes Attributes - { - get => m_AosAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosElementAttributes Resistances - { - get => m_AosResistances; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosSkillBonuses SkillBonuses - { - get => m_AosSkillBonuses; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; Hue = CraftResources.GetHue( m_Resource ); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public GemType GemType - { - get => m_GemType; - set{ m_GemType = value; InvalidateProperties(); } - } - - public override int PhysicalResistance => m_AosResistances.Physical; - public override int FireResistance => m_AosResistances.Fire; - public override int ColdResistance => m_AosResistances.Cold; - public override int PoisonResistance => m_AosResistances.Poison; - public override int EnergyResistance => m_AosResistances.Energy; - public virtual int BaseGemTypeNumber => 0; - - public virtual int InitMinHits => 0; - public virtual int InitMaxHits => 0; - - public override int LabelNumber - { - get - { - if ( m_GemType == GemType.None ) - return base.LabelNumber; - - return BaseGemTypeNumber + (int)m_GemType - 1; - } - } - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is BaseJewel jewel) ) - return; - - jewel.m_AosAttributes = new AosAttributes( newItem, m_AosAttributes ); - jewel.m_AosResistances = new AosElementAttributes( newItem, m_AosResistances ); - jewel.m_AosSkillBonuses = new AosSkillBonuses( newItem, m_AosSkillBonuses ); - } - - public virtual int ArtifactRarity => 0; - - public BaseJewel( int itemID, Layer layer ) : base( itemID ) - { - m_AosAttributes = new AosAttributes( this ); - m_AosResistances = new AosElementAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - m_Resource = CraftResource.Iron; - m_GemType = GemType.None; - - Layer = layer; - - m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - } - - public override void OnAdded(IEntity parent) - { - if ( Core.AOS && parent is Mobile from ) - { - m_AosSkillBonuses.AddTo( from ); - - int strBonus = m_AosAttributes.BonusStr; - int dexBonus = m_AosAttributes.BonusDex; - int intBonus = m_AosAttributes.BonusInt; + public enum GemType + { + None, + StarSapphire, + Emerald, + Sapphire, + Ruby, + Citrine, + Amethyst, + Tourmaline, + Amber, + Diamond + } + + public abstract class BaseJewel : Item, ICraftable + { + private AosAttributes m_AosAttributes; + private AosElementAttributes m_AosResistances; + private AosSkillBonuses m_AosSkillBonuses; + private GemType m_GemType; + private int m_HitPoints; + private int m_MaxHitPoints; + private CraftResource m_Resource; + + public BaseJewel(int itemID, Layer layer) : base(itemID) + { + m_AosAttributes = new AosAttributes(this); + m_AosResistances = new AosElementAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + m_Resource = CraftResource.Iron; + m_GemType = GemType.None; + + Layer = layer; + + m_HitPoints = m_MaxHitPoints = Utility.RandomMinMax(InitMinHits, InitMaxHits); + } + + public BaseJewel(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxHitPoints + { + get => m_MaxHitPoints; + set + { + m_MaxHitPoints = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitPoints + { + get => m_HitPoints; + set + { + if (value != m_HitPoints && MaxHitPoints > 0) + { + m_HitPoints = value; + + if (m_HitPoints < 0) + Delete(); + else if (m_HitPoints > MaxHitPoints) + m_HitPoints = MaxHitPoints; + + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.Player)] + public AosAttributes Attributes + { + get => m_AosAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosElementAttributes Resistances + { + get => m_AosResistances; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosSkillBonuses SkillBonuses + { + get => m_AosSkillBonuses; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public GemType GemType + { + get => m_GemType; + set + { + m_GemType = value; + InvalidateProperties(); + } + } + + public override int PhysicalResistance => m_AosResistances.Physical; + public override int FireResistance => m_AosResistances.Fire; + public override int ColdResistance => m_AosResistances.Cold; + public override int PoisonResistance => m_AosResistances.Poison; + public override int EnergyResistance => m_AosResistances.Energy; + public virtual int BaseGemTypeNumber => 0; + + public virtual int InitMinHits => 0; + public virtual int InitMaxHits => 0; + + public override int LabelNumber + { + get + { + if (m_GemType == GemType.None) + return base.LabelNumber; + + return BaseGemTypeNumber + (int)m_GemType - 1; + } + } + + public virtual int ArtifactRarity => 0; + + #region ICraftable Members + + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Type resourceType = typeRes; + + if (resourceType == null) + resourceType = craftItem.Resources.GetAt(0).ItemType; + + Resource = CraftResources.GetFromType(resourceType); + + CraftContext context = craftSystem.GetContext(from); + + if (context != null && context.DoNotColor) + Hue = 0; + + if (1 < craftItem.Resources.Count) + { + resourceType = craftItem.Resources.GetAt(1).ItemType; + + if (resourceType == typeof(StarSapphire)) + GemType = GemType.StarSapphire; + else if (resourceType == typeof(Emerald)) + GemType = GemType.Emerald; + else if (resourceType == typeof(Sapphire)) + GemType = GemType.Sapphire; + else if (resourceType == typeof(Ruby)) + GemType = GemType.Ruby; + else if (resourceType == typeof(Citrine)) + GemType = GemType.Citrine; + else if (resourceType == typeof(Amethyst)) + GemType = GemType.Amethyst; + else if (resourceType == typeof(Tourmaline)) + GemType = GemType.Tourmaline; + else if (resourceType == typeof(Amber)) + GemType = GemType.Amber; + else if (resourceType == typeof(Diamond)) + GemType = GemType.Diamond; + } + + return 1; + } + + #endregion + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is BaseJewel jewel)) + return; + + jewel.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); + jewel.m_AosResistances = new AosElementAttributes(newItem, m_AosResistances); + jewel.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); + } + + public override void OnAdded(IEntity parent) + { + if (Core.AOS && parent is Mobile from) + { + m_AosSkillBonuses.AddTo(from); - if ( strBonus != 0 || dexBonus != 0 || intBonus != 0 ) - { - string modName = Serial.ToString(); + int strBonus = m_AosAttributes.BonusStr; + int dexBonus = m_AosAttributes.BonusDex; + int intBonus = m_AosAttributes.BonusInt; - if ( strBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); + if (strBonus != 0 || dexBonus != 0 || intBonus != 0) + { + string modName = Serial.ToString(); - if ( dexBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); + if (strBonus != 0) + from.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); - if ( intBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } + if (dexBonus != 0) + from.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); - from.CheckStatTimers(); - } - } + if (intBonus != 0) + from.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } - public override void OnRemoved(IEntity parent) - { - if ( Core.AOS && parent is Mobile from ) - { - m_AosSkillBonuses.Remove(); + from.CheckStatTimers(); + } + } - string modName = Serial.ToString(); + public override void OnRemoved(IEntity parent) + { + if (Core.AOS && parent is Mobile from) + { + m_AosSkillBonuses.Remove(); - from.RemoveStatMod( modName + "Str" ); - from.RemoveStatMod( modName + "Dex" ); - from.RemoveStatMod( modName + "Int" ); + string modName = Serial.ToString(); - from.CheckStatTimers(); - } - } + from.RemoveStatMod(modName + "Str"); + from.RemoveStatMod(modName + "Dex"); + from.RemoveStatMod(modName + "Int"); - public BaseJewel( Serial serial ) : base( serial ) - { - } + from.CheckStatTimers(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - m_AosSkillBonuses.GetProperties( list ); + m_AosSkillBonuses.GetProperties(list); - int prop; + int prop; - if ( (prop = ArtifactRarity) > 0 ) - list.Add( 1061078, prop.ToString() ); // artifact rarity ~1_val~ + if ((prop = ArtifactRarity) > 0) + list.Add(1061078, prop.ToString()); // artifact rarity ~1_val~ - if ( (prop = m_AosAttributes.WeaponDamage) != 0 ) - list.Add( 1060401, prop.ToString() ); // damage increase ~1_val~% + if ((prop = m_AosAttributes.WeaponDamage) != 0) + list.Add(1060401, prop.ToString()); // damage increase ~1_val~% - if ( (prop = m_AosAttributes.DefendChance) != 0 ) - list.Add( 1060408, prop.ToString() ); // defense chance increase ~1_val~% + if ((prop = m_AosAttributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% - if ( (prop = m_AosAttributes.BonusDex) != 0 ) - list.Add( 1060409, prop.ToString() ); // dexterity bonus ~1_val~ + if ((prop = m_AosAttributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ - if ( (prop = m_AosAttributes.EnhancePotions) != 0 ) - list.Add( 1060411, prop.ToString() ); // enhance potions ~1_val~% + if ((prop = m_AosAttributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% - if ( (prop = m_AosAttributes.CastRecovery) != 0 ) - list.Add( 1060412, prop.ToString() ); // faster cast recovery ~1_val~ + if ((prop = m_AosAttributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ - if ( (prop = m_AosAttributes.CastSpeed) != 0 ) - list.Add( 1060413, prop.ToString() ); // faster casting ~1_val~ + if ((prop = m_AosAttributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - if ( (prop = m_AosAttributes.AttackChance) != 0 ) - list.Add( 1060415, prop.ToString() ); // hit chance increase ~1_val~% + if ((prop = m_AosAttributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - if ( (prop = m_AosAttributes.BonusHits) != 0 ) - list.Add( 1060431, prop.ToString() ); // hit point increase ~1_val~ + if ((prop = m_AosAttributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if ( (prop = m_AosAttributes.BonusInt) != 0 ) - list.Add( 1060432, prop.ToString() ); // intelligence bonus ~1_val~ + if ((prop = m_AosAttributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - if ( (prop = m_AosAttributes.LowerManaCost) != 0 ) - list.Add( 1060433, prop.ToString() ); // lower mana cost ~1_val~% + if ((prop = m_AosAttributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if ( (prop = m_AosAttributes.LowerRegCost) != 0 ) - list.Add( 1060434, prop.ToString() ); // lower reagent cost ~1_val~% + if ((prop = m_AosAttributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - if ( (prop = m_AosAttributes.Luck) != 0 ) - list.Add( 1060436, prop.ToString() ); // luck ~1_val~ + if ((prop = m_AosAttributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - if ( (prop = m_AosAttributes.BonusMana) != 0 ) - list.Add( 1060439, prop.ToString() ); // mana increase ~1_val~ + if ((prop = m_AosAttributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - if ( (prop = m_AosAttributes.RegenMana) != 0 ) - list.Add( 1060440, prop.ToString() ); // mana regeneration ~1_val~ + if ((prop = m_AosAttributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - if ( (prop = m_AosAttributes.NightSight) != 0 ) - list.Add( 1060441 ); // night sight + if ((prop = m_AosAttributes.NightSight) != 0) + list.Add(1060441); // night sight - if ( (prop = m_AosAttributes.ReflectPhysical) != 0 ) - list.Add( 1060442, prop.ToString() ); // reflect physical damage ~1_val~% + if ((prop = m_AosAttributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - if ( (prop = m_AosAttributes.RegenStam) != 0 ) - list.Add( 1060443, prop.ToString() ); // stamina regeneration ~1_val~ + if ((prop = m_AosAttributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - if ( (prop = m_AosAttributes.RegenHits) != 0 ) - list.Add( 1060444, prop.ToString() ); // hit point regeneration ~1_val~ + if ((prop = m_AosAttributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if ( (prop = m_AosAttributes.SpellChanneling) != 0 ) - list.Add( 1060482 ); // spell channeling + if ((prop = m_AosAttributes.SpellChanneling) != 0) + list.Add(1060482); // spell channeling - if ( (prop = m_AosAttributes.SpellDamage) != 0 ) - list.Add( 1060483, prop.ToString() ); // spell damage increase ~1_val~% + if ((prop = m_AosAttributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - if ( (prop = m_AosAttributes.BonusStam) != 0 ) - list.Add( 1060484, prop.ToString() ); // stamina increase ~1_val~ + if ((prop = m_AosAttributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - if ( (prop = m_AosAttributes.BonusStr) != 0 ) - list.Add( 1060485, prop.ToString() ); // strength bonus ~1_val~ + if ((prop = m_AosAttributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - if ( (prop = m_AosAttributes.WeaponSpeed) != 0 ) - list.Add( 1060486, prop.ToString() ); // swing speed increase ~1_val~% + if ((prop = m_AosAttributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - if ( Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0 ) - list.Add( 1075210, prop.ToString() ); // Increased Karma Loss ~1val~% + if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) + list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% - base.AddResistanceProperties( list ); + base.AddResistanceProperties(list); - if ( m_HitPoints >= 0 && m_MaxHitPoints > 0 ) - list.Add( 1060639, "{0}\t{1}", m_HitPoints, m_MaxHitPoints ); // durability ~1_val~ / ~2_val~ - } + if (m_HitPoints >= 0 && m_MaxHitPoints > 0) + list.Add(1060639, "{0}\t{1}", m_HitPoints, m_MaxHitPoints); // durability ~1_val~ / ~2_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 3 ); // version + writer.Write(3); // version - writer.WriteEncodedInt( (int) m_MaxHitPoints ); - writer.WriteEncodedInt( (int) m_HitPoints ); + writer.WriteEncodedInt(m_MaxHitPoints); + writer.WriteEncodedInt(m_HitPoints); - writer.WriteEncodedInt( (int) m_Resource ); - writer.WriteEncodedInt( (int) m_GemType ); + writer.WriteEncodedInt((int)m_Resource); + writer.WriteEncodedInt((int)m_GemType); - m_AosAttributes.Serialize( writer ); - m_AosResistances.Serialize( writer ); - m_AosSkillBonuses.Serialize( writer ); - } + m_AosAttributes.Serialize(writer); + m_AosResistances.Serialize(writer); + m_AosSkillBonuses.Serialize(writer); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 3: - { - m_MaxHitPoints = reader.ReadEncodedInt(); - m_HitPoints = reader.ReadEncodedInt(); + switch (version) + { + case 3: + { + m_MaxHitPoints = reader.ReadEncodedInt(); + m_HitPoints = reader.ReadEncodedInt(); - goto case 2; - } - case 2: - { - m_Resource = (CraftResource)reader.ReadEncodedInt(); - m_GemType = (GemType)reader.ReadEncodedInt(); + goto case 2; + } + case 2: + { + m_Resource = (CraftResource)reader.ReadEncodedInt(); + m_GemType = (GemType)reader.ReadEncodedInt(); - goto case 1; - } - case 1: - { - m_AosAttributes = new AosAttributes( this, reader ); - m_AosResistances = new AosElementAttributes( this, reader ); - m_AosSkillBonuses = new AosSkillBonuses( this, reader ); + goto case 1; + } + case 1: + { + m_AosAttributes = new AosAttributes(this, reader); + m_AosResistances = new AosElementAttributes(this, reader); + m_AosSkillBonuses = new AosSkillBonuses(this, reader); - Mobile m = Parent as Mobile; + Mobile m = Parent as Mobile; - if ( Core.AOS && m != null ) - m_AosSkillBonuses.AddTo( m ); + if (Core.AOS && m != null) + m_AosSkillBonuses.AddTo(m); - int strBonus = m_AosAttributes.BonusStr; - int dexBonus = m_AosAttributes.BonusDex; - int intBonus = m_AosAttributes.BonusInt; + int strBonus = m_AosAttributes.BonusStr; + int dexBonus = m_AosAttributes.BonusDex; + int intBonus = m_AosAttributes.BonusInt; - if ( m != null && (strBonus != 0 || dexBonus != 0 || intBonus != 0) ) - { - string modName = Serial.ToString(); + if (m != null && (strBonus != 0 || dexBonus != 0 || intBonus != 0)) + { + string modName = Serial.ToString(); - if ( strBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); + if (strBonus != 0) + m.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); - if ( dexBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); + if (dexBonus != 0) + m.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); - if ( intBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - m?.CheckStatTimers(); - - break; - } - case 0: - { - m_AosAttributes = new AosAttributes( this ); - m_AosResistances = new AosElementAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - - break; - } - } - - if ( version < 2 ) - { - m_Resource = CraftResource.Iron; - m_GemType = GemType.None; - } - } - #region ICraftable Members - - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Type resourceType = typeRes; - - if ( resourceType == null ) - resourceType = craftItem.Resources.GetAt( 0 ).ItemType; - - Resource = CraftResources.GetFromType( resourceType ); - - CraftContext context = craftSystem.GetContext( from ); - - if ( context != null && context.DoNotColor ) - Hue = 0; - - if ( 1 < craftItem.Resources.Count ) - { - resourceType = craftItem.Resources.GetAt( 1 ).ItemType; - - if ( resourceType == typeof( StarSapphire ) ) - GemType = GemType.StarSapphire; - else if ( resourceType == typeof( Emerald ) ) - GemType = GemType.Emerald; - else if ( resourceType == typeof( Sapphire ) ) - GemType = GemType.Sapphire; - else if ( resourceType == typeof( Ruby ) ) - GemType = GemType.Ruby; - else if ( resourceType == typeof( Citrine ) ) - GemType = GemType.Citrine; - else if ( resourceType == typeof( Amethyst ) ) - GemType = GemType.Amethyst; - else if ( resourceType == typeof( Tourmaline ) ) - GemType = GemType.Tourmaline; - else if ( resourceType == typeof( Amber ) ) - GemType = GemType.Amber; - else if ( resourceType == typeof( Diamond ) ) - GemType = GemType.Diamond; - } - - return 1; - } - - #endregion - } -} + if (intBonus != 0) + m.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + m?.CheckStatTimers(); + + break; + } + case 0: + { + m_AosAttributes = new AosAttributes(this); + m_AosResistances = new AosElementAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + + break; + } + } + + if (version < 2) + { + m_Resource = CraftResource.Iron; + m_GemType = GemType.None; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Beads.cs b/Scripts/Items/Jewels/Beads.cs index d52bc9cd7..7519565c3 100644 --- a/Scripts/Items/Jewels/Beads.cs +++ b/Scripts/Items/Jewels/Beads.cs @@ -1,27 +1,27 @@ namespace Server.Items { - public class Beads : Item - { - [Constructible] - public Beads() : base( 0x108B ) - { - Weight = 1.0; - } + public class Beads : Item + { + [Constructible] + public Beads() : base(0x108B) + { + Weight = 1.0; + } - public Beads( Serial serial ) : base( serial ) - { - } + public Beads(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Jewels/Bracelet.cs b/Scripts/Items/Jewels/Bracelet.cs index cf2d15c16..9890fb42b 100644 --- a/Scripts/Items/Jewels/Bracelet.cs +++ b/Scripts/Items/Jewels/Bracelet.cs @@ -1,83 +1,83 @@ namespace Server.Items { - public abstract class BaseBracelet : BaseJewel - { - public override int BaseGemTypeNumber => 1044221; // star sapphire bracelet + public abstract class BaseBracelet : BaseJewel + { + public BaseBracelet(int itemID) : base(itemID, Layer.Bracelet) + { + } - public BaseBracelet( int itemID ) : base( itemID, Layer.Bracelet ) - { - } + public BaseBracelet(Serial serial) : base(serial) + { + } - public BaseBracelet( Serial serial ) : base( serial ) - { - } + public override int BaseGemTypeNumber => 1044221; // star sapphire bracelet - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GoldBracelet : BaseBracelet - { - [Constructible] - public GoldBracelet() : base( 0x1086 ) - { - Weight = 0.1; - } + public class GoldBracelet : BaseBracelet + { + [Constructible] + public GoldBracelet() : base(0x1086) + { + Weight = 0.1; + } - public GoldBracelet( Serial serial ) : base( serial ) - { - } + public GoldBracelet(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SilverBracelet : BaseBracelet - { - [Constructible] - public SilverBracelet() : base( 0x1F06 ) - { - Weight = 0.1; - } + public class SilverBracelet : BaseBracelet + { + [Constructible] + public SilverBracelet() : base(0x1F06) + { + Weight = 0.1; + } - public SilverBracelet( Serial serial ) : base( serial ) - { - } + public SilverBracelet(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Earrings.cs b/Scripts/Items/Jewels/Earrings.cs index 3c4dfa9a6..db762236a 100644 --- a/Scripts/Items/Jewels/Earrings.cs +++ b/Scripts/Items/Jewels/Earrings.cs @@ -1,83 +1,83 @@ namespace Server.Items { - public abstract class BaseEarrings : BaseJewel - { - public override int BaseGemTypeNumber => 1044203; // star sapphire earrings + public abstract class BaseEarrings : BaseJewel + { + public BaseEarrings(int itemID) : base(itemID, Layer.Earrings) + { + } - public BaseEarrings( int itemID ) : base( itemID, Layer.Earrings ) - { - } + public BaseEarrings(Serial serial) : base(serial) + { + } - public BaseEarrings( Serial serial ) : base( serial ) - { - } + public override int BaseGemTypeNumber => 1044203; // star sapphire earrings - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GoldEarrings : BaseEarrings - { - [Constructible] - public GoldEarrings() : base( 0x1087 ) - { - Weight = 0.1; - } + public class GoldEarrings : BaseEarrings + { + [Constructible] + public GoldEarrings() : base(0x1087) + { + Weight = 0.1; + } - public GoldEarrings( Serial serial ) : base( serial ) - { - } + public GoldEarrings(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SilverEarrings : BaseEarrings - { - [Constructible] - public SilverEarrings() : base( 0x1F07 ) - { - Weight = 0.1; - } + public class SilverEarrings : BaseEarrings + { + [Constructible] + public SilverEarrings() : base(0x1F07) + { + Weight = 0.1; + } - public SilverEarrings( Serial serial ) : base( serial ) - { - } + public SilverEarrings(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Necklace.cs b/Scripts/Items/Jewels/Necklace.cs index 6d6edc14d..14b70f5e2 100644 --- a/Scripts/Items/Jewels/Necklace.cs +++ b/Scripts/Items/Jewels/Necklace.cs @@ -1,165 +1,165 @@ namespace Server.Items { - public abstract class BaseNecklace : BaseJewel - { - public override int BaseGemTypeNumber => 1044241; // star sapphire necklace + public abstract class BaseNecklace : BaseJewel + { + public BaseNecklace(int itemID) : base(itemID, Layer.Neck) + { + } - public BaseNecklace( int itemID ) : base( itemID, Layer.Neck ) - { - } + public BaseNecklace(Serial serial) : base(serial) + { + } - public BaseNecklace( Serial serial ) : base( serial ) - { - } + public override int BaseGemTypeNumber => 1044241; // star sapphire necklace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Necklace : BaseNecklace - { - [Constructible] - public Necklace() : base( 0x1085 ) - { - Weight = 0.1; - } + public class Necklace : BaseNecklace + { + [Constructible] + public Necklace() : base(0x1085) + { + Weight = 0.1; + } - public Necklace( Serial serial ) : base( serial ) - { - } + public Necklace(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GoldNecklace : BaseNecklace - { - [Constructible] - public GoldNecklace() : base( 0x1088 ) - { - Weight = 0.1; - } + public class GoldNecklace : BaseNecklace + { + [Constructible] + public GoldNecklace() : base(0x1088) + { + Weight = 0.1; + } - public GoldNecklace( Serial serial ) : base( serial ) - { - } + public GoldNecklace(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GoldBeadNecklace : BaseNecklace - { - [Constructible] - public GoldBeadNecklace() : base( 0x1089 ) - { - Weight = 0.1; - } + public class GoldBeadNecklace : BaseNecklace + { + [Constructible] + public GoldBeadNecklace() : base(0x1089) + { + Weight = 0.1; + } - public GoldBeadNecklace( Serial serial ) : base( serial ) - { - } + public GoldBeadNecklace(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SilverNecklace : BaseNecklace - { - [Constructible] - public SilverNecklace() : base( 0x1F08 ) - { - Weight = 0.1; - } + public class SilverNecklace : BaseNecklace + { + [Constructible] + public SilverNecklace() : base(0x1F08) + { + Weight = 0.1; + } - public SilverNecklace( Serial serial ) : base( serial ) - { - } + public SilverNecklace(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SilverBeadNecklace : BaseNecklace - { - [Constructible] - public SilverBeadNecklace() : base( 0x1F05 ) - { - Weight = 0.1; - } + public class SilverBeadNecklace : BaseNecklace + { + [Constructible] + public SilverBeadNecklace() : base(0x1F05) + { + Weight = 0.1; + } - public SilverBeadNecklace( Serial serial ) : base( serial ) - { - } + public SilverBeadNecklace(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Jewels/Ring.cs b/Scripts/Items/Jewels/Ring.cs index 80dd084b3..57de851c1 100644 --- a/Scripts/Items/Jewels/Ring.cs +++ b/Scripts/Items/Jewels/Ring.cs @@ -1,83 +1,83 @@ namespace Server.Items { - public abstract class BaseRing : BaseJewel - { - public override int BaseGemTypeNumber => 1044176; // star sapphire ring + public abstract class BaseRing : BaseJewel + { + public BaseRing(int itemID) : base(itemID, Layer.Ring) + { + } - public BaseRing( int itemID ) : base( itemID, Layer.Ring ) - { - } + public BaseRing(Serial serial) : base(serial) + { + } - public BaseRing( Serial serial ) : base( serial ) - { - } + public override int BaseGemTypeNumber => 1044176; // star sapphire ring - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class GoldRing : BaseRing - { - [Constructible] - public GoldRing() : base( 0x108a ) - { - Weight = 0.1; - } + public class GoldRing : BaseRing + { + [Constructible] + public GoldRing() : base(0x108a) + { + Weight = 0.1; + } - public GoldRing( Serial serial ) : base( serial ) - { - } + public GoldRing(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SilverRing : BaseRing - { - [Constructible] - public SilverRing() : base( 0x1F09 ) - { - Weight = 0.1; - } + public class SilverRing : BaseRing + { + [Constructible] + public SilverRing() : base(0x1F09) + { + Weight = 0.1; + } - public SilverRing( Serial serial ) : base( serial ) - { - } + public SilverRing(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/BaseEquippableLight.cs b/Scripts/Items/Lights/BaseEquippableLight.cs index a825bfddd..9067f1c9b 100644 --- a/Scripts/Items/Lights/BaseEquippableLight.cs +++ b/Scripts/Items/Lights/BaseEquippableLight.cs @@ -1,59 +1,59 @@ namespace Server.Items { - public abstract class BaseEquipableLight : BaseLight - { - [Constructible] - public BaseEquipableLight( int itemID ) : base( itemID ) - { - Layer = Layer.TwoHanded; - } + public abstract class BaseEquipableLight : BaseLight + { + [Constructible] + public BaseEquipableLight(int itemID) : base(itemID) + { + Layer = Layer.TwoHanded; + } - public BaseEquipableLight( Serial serial ) : base( serial ) - { - } + public BaseEquipableLight(Serial serial) : base(serial) + { + } - public override void Ignite() - { - if ( !(Parent is Mobile) && RootParent is Mobile holder ) - { - if ( holder.EquipItem( this ) ) - { - if ( this is Candle ) - holder.SendLocalizedMessage( 502969 ); // You put the candle in your left hand. - else if ( this is Torch ) - holder.SendLocalizedMessage( 502971 ); // You put the torch in your left hand. + public override void Ignite() + { + if (!(Parent is Mobile) && RootParent is Mobile holder) + { + if (holder.EquipItem(this)) + { + if (this is Candle) + holder.SendLocalizedMessage(502969); // You put the candle in your left hand. + else if (this is Torch) + holder.SendLocalizedMessage(502971); // You put the torch in your left hand. - base.Ignite(); - } - else - { - holder.SendLocalizedMessage( 502449 ); // You cannot hold this item. - } - } - else - { - base.Ignite(); - } - } + base.Ignite(); + } + else + { + holder.SendLocalizedMessage(502449); // You cannot hold this item. + } + } + else + { + base.Ignite(); + } + } - public override void OnAdded(IEntity parent) - { - if ( Burning && parent is Container ) - Douse(); + public override void OnAdded(IEntity parent) + { + if (Burning && parent is Container) + Douse(); - base.OnAdded( parent ); - } + base.OnAdded(parent); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/BaseLight.cs b/Scripts/Items/Lights/BaseLight.cs index 1f6b5bea0..70c23fe06 100644 --- a/Scripts/Items/Lights/BaseLight.cs +++ b/Scripts/Items/Lights/BaseLight.cs @@ -2,219 +2,215 @@ using System; namespace Server.Items { - public abstract class BaseLight : Item - { - private Timer m_Timer; - private DateTime m_End; - private bool m_Burning; - private TimeSpan m_Duration = TimeSpan.Zero; + public abstract class BaseLight : Item + { + public static readonly bool Burnout = false; + private bool m_Burning; + private TimeSpan m_Duration = TimeSpan.Zero; + private DateTime m_End; + private Timer m_Timer; - public abstract int LitItemID{ get; } + [Constructible] + public BaseLight(int itemID) : base(itemID) + { + } - public virtual int UnlitItemID => 0; - public virtual int BurntOutItemID => 0; + public BaseLight(Serial serial) : base(serial) + { + } - public virtual int LitSound => 0x47; - public virtual int UnlitSound => 0x3be; - public virtual int BurntOutSound => 0x4b8; + public abstract int LitItemID{ get; } - public static readonly bool Burnout = false; + public virtual int UnlitItemID => 0; + public virtual int BurntOutItemID => 0; - [CommandProperty( AccessLevel.GameMaster )] - public bool Burning - { - get => m_Burning; - set - { - if ( m_Burning != value ) - { - m_Burning = true; - DoTimer( m_Duration ); - } - } - } + public virtual int LitSound => 0x47; + public virtual int UnlitSound => 0x3be; + public virtual int BurntOutSound => 0x4b8; - [CommandProperty( AccessLevel.GameMaster )] - public bool BurntOut { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public bool Burning + { + get => m_Burning; + set + { + if (m_Burning != value) + { + m_Burning = true; + DoTimer(m_Duration); + } + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool Protected { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public bool BurntOut{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan Duration - { - get - { - if ( m_Duration != TimeSpan.Zero && m_Burning ) - { - return m_End - DateTime.UtcNow; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Protected{ get; set; } - return m_Duration; - } + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan Duration + { + get + { + if (m_Duration != TimeSpan.Zero && m_Burning) return m_End - DateTime.UtcNow; - set => m_Duration = value; - } + return m_Duration; + } - [Constructible] - public BaseLight( int itemID ) : base( itemID ) - { - } + set => m_Duration = value; + } - public BaseLight( Serial serial ) : base( serial ) - { - } + public virtual void PlayLitSound() + { + if (LitSound != 0) + { + Point3D loc = GetWorldLocation(); + Effects.PlaySound(loc, Map, LitSound); + } + } - public virtual void PlayLitSound() - { - if ( LitSound != 0 ) - { - Point3D loc = GetWorldLocation(); - Effects.PlaySound( loc, Map, LitSound ); - } - } + public virtual void PlayUnlitSound() + { + int sound = UnlitSound; - public virtual void PlayUnlitSound() - { - int sound = UnlitSound; - - if ( BurntOut && BurntOutSound != 0 ) - sound = BurntOutSound; + if (BurntOut && BurntOutSound != 0) + sound = BurntOutSound; - if ( sound != 0 ) - { - Point3D loc = GetWorldLocation(); - Effects.PlaySound( loc, Map, sound ); - } - } + if (sound != 0) + { + Point3D loc = GetWorldLocation(); + Effects.PlaySound(loc, Map, sound); + } + } - public virtual void Ignite() - { - if ( !BurntOut ) - { - PlayLitSound(); + public virtual void Ignite() + { + if (!BurntOut) + { + PlayLitSound(); - m_Burning = true; - ItemID = LitItemID; - DoTimer( m_Duration ); - } - } + m_Burning = true; + ItemID = LitItemID; + DoTimer(m_Duration); + } + } - public virtual void Douse() - { - m_Burning = false; + public virtual void Douse() + { + m_Burning = false; - if ( BurntOut && BurntOutItemID != 0 ) - ItemID = BurntOutItemID; - else - ItemID = UnlitItemID; + if (BurntOut && BurntOutItemID != 0) + ItemID = BurntOutItemID; + else + ItemID = UnlitItemID; - if ( BurntOut ) - m_Duration = TimeSpan.Zero; - else if ( m_Duration != TimeSpan.Zero ) - m_Duration = m_End - DateTime.UtcNow; + if (BurntOut) + m_Duration = TimeSpan.Zero; + else if (m_Duration != TimeSpan.Zero) + m_Duration = m_End - DateTime.UtcNow; - m_Timer?.Stop(); + m_Timer?.Stop(); - PlayUnlitSound(); - } + PlayUnlitSound(); + } - public virtual void Burn() - { - BurntOut = true; - Douse(); - } + public virtual void Burn() + { + BurntOut = true; + Douse(); + } - private void DoTimer( TimeSpan delay ) - { - m_Duration = delay; + private void DoTimer(TimeSpan delay) + { + m_Duration = delay; - m_Timer?.Stop(); + m_Timer?.Stop(); - if ( delay == TimeSpan.Zero ) - return; + if (delay == TimeSpan.Zero) + return; - m_End = DateTime.UtcNow + delay; + m_End = DateTime.UtcNow + delay; - m_Timer = new InternalTimer( this, delay ); - m_Timer.Start(); - } + m_Timer = new InternalTimer(this, delay); + m_Timer.Start(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( BurntOut ) - return; + public override void OnDoubleClick(Mobile from) + { + if (BurntOut) + return; - if ( Protected && from.AccessLevel == AccessLevel.Player ) - return; + if (Protected && from.AccessLevel == AccessLevel.Player) + return; - if ( !from.InRange( GetWorldLocation(), 2 ) ) - return; + if (!from.InRange(GetWorldLocation(), 2)) + return; - if ( m_Burning ) - { - if ( UnlitItemID != 0 ) - Douse(); - } - else - { - Ignite(); - } - } + if (m_Burning) + { + if (UnlitItemID != 0) + Douse(); + } + else + { + Ignite(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - writer.Write( BurntOut ); - writer.Write( m_Burning ); - writer.Write( m_Duration ); - writer.Write( Protected ); + writer.Write(0); + writer.Write(BurntOut); + writer.Write(m_Burning); + writer.Write(m_Duration); + writer.Write(Protected); - if ( m_Burning && m_Duration != TimeSpan.Zero ) - writer.WriteDeltaTime( m_End ); - } + if (m_Burning && m_Duration != TimeSpan.Zero) + writer.WriteDeltaTime(m_End); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - BurntOut = reader.ReadBool(); - m_Burning = reader.ReadBool(); - m_Duration = reader.ReadTimeSpan(); - Protected = reader.ReadBool(); + switch (version) + { + case 0: + { + BurntOut = reader.ReadBool(); + m_Burning = reader.ReadBool(); + m_Duration = reader.ReadTimeSpan(); + Protected = reader.ReadBool(); - if ( m_Burning && m_Duration != TimeSpan.Zero ) - DoTimer( reader.ReadDeltaTime() - DateTime.UtcNow ); + if (m_Burning && m_Duration != TimeSpan.Zero) + DoTimer(reader.ReadDeltaTime() - DateTime.UtcNow); - break; - } - } - } + break; + } + } + } - private class InternalTimer : Timer - { - private BaseLight m_Light; + private class InternalTimer : Timer + { + private BaseLight m_Light; - public InternalTimer( BaseLight light, TimeSpan delay ) : base( delay ) - { - m_Light = light; - Priority = TimerPriority.FiveSeconds; - } + public InternalTimer(BaseLight light, TimeSpan delay) : base(delay) + { + m_Light = light; + Priority = TimerPriority.FiveSeconds; + } - protected override void OnTick() - { - if ( m_Light != null && !m_Light.Deleted ) - m_Light.Burn(); - } - } - } -} + protected override void OnTick() + { + if (m_Light != null && !m_Light.Deleted) + m_Light.Burn(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/Brazier.cs b/Scripts/Items/Lights/Brazier.cs index 1895c53ab..b02fc2d61 100644 --- a/Scripts/Items/Lights/Brazier.cs +++ b/Scripts/Items/Lights/Brazier.cs @@ -2,34 +2,34 @@ using System; namespace Server.Items { - public class Brazier : BaseLight - { - public override int LitItemID => 0xE31; + public class Brazier : BaseLight + { + [Constructible] + public Brazier() : base(0xE31) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = true; + Light = LightType.Circle225; + Weight = 20.0; + } - [Constructible] - public Brazier() : base( 0xE31 ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = true; - Light = LightType.Circle225; - Weight = 20.0; - } + public Brazier(Serial serial) : base(serial) + { + } - public Brazier( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xE31; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/BrazierTall.cs b/Scripts/Items/Lights/BrazierTall.cs index c711f084c..03a8d2fa1 100644 --- a/Scripts/Items/Lights/BrazierTall.cs +++ b/Scripts/Items/Lights/BrazierTall.cs @@ -2,34 +2,34 @@ using System; namespace Server.Items { - public class BrazierTall : BaseLight - { - public override int LitItemID => 0x19AA; + public class BrazierTall : BaseLight + { + [Constructible] + public BrazierTall() : base(0x19AA) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = true; + Light = LightType.Circle300; + Weight = 25.0; + } - [Constructible] - public BrazierTall() : base( 0x19AA ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = true; - Light = LightType.Circle300; - Weight = 25.0; - } + public BrazierTall(Serial serial) : base(serial) + { + } - public BrazierTall( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0x19AA; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/Candelabra.cs b/Scripts/Items/Lights/Candelabra.cs index 9d2ee4e97..eb4214f16 100644 --- a/Scripts/Items/Lights/Candelabra.cs +++ b/Scripts/Items/Lights/Candelabra.cs @@ -2,68 +2,68 @@ using System; namespace Server.Items { - public class Candelabra : BaseLight, IShipwreckedItem - { - public override int LitItemID => 0xB1D; - public override int UnlitItemID => 0xA27; + public class Candelabra : BaseLight, IShipwreckedItem + { + [Constructible] + public Candelabra() : base(0xA27) + { + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle225; + Weight = 3.0; + } - [Constructible] - public Candelabra() : base( 0xA27 ) - { - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle225; - Weight = 3.0; - } + public Candelabra(Serial serial) : base(serial) + { + } - public Candelabra( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xB1D; + public override int UnlitItemID => 0xA27; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); + #region IShipwreckedItem Members - writer.Write( IsShipwreckedItem ); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsShipwreckedItem{ get; set; } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + #endregion - switch ( version ) - { - case 1: - { - IsShipwreckedItem = reader.ReadBool(); - break; - } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + writer.Write(IsShipwreckedItem); + } - if ( IsShipwreckedItem ) - list.Add( 1041645 ); // recovered from a shipwreck - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + switch (version) + { + case 1: + { + IsShipwreckedItem = reader.ReadBool(); + break; + } + } + } - if ( IsShipwreckedItem ) - LabelTo( from, 1041645 ); //recovered from a shipwreck - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - #region IShipwreckedItem Members + if (IsShipwreckedItem) + list.Add(1041645); // recovered from a shipwreck + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsShipwreckedItem { get; set; } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - #endregion - } -} + if (IsShipwreckedItem) + LabelTo(from, 1041645); //recovered from a shipwreck + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/CandelabraStand.cs b/Scripts/Items/Lights/CandelabraStand.cs index 7c6ddd968..370228bc5 100644 --- a/Scripts/Items/Lights/CandelabraStand.cs +++ b/Scripts/Items/Lights/CandelabraStand.cs @@ -2,34 +2,34 @@ using System; namespace Server.Items { - public class CandelabraStand : BaseLight - { - public override int LitItemID => 0xB26; - public override int UnlitItemID => 0xA29; + public class CandelabraStand : BaseLight + { + [Constructible] + public CandelabraStand() : base(0xA29) + { + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle225; + Weight = 20.0; + } - [Constructible] - public CandelabraStand() : base( 0xA29 ) - { - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle225; - Weight = 20.0; - } + public CandelabraStand(Serial serial) : base(serial) + { + } - public CandelabraStand( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xB26; + public override int UnlitItemID => 0xA29; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/Candle.cs b/Scripts/Items/Lights/Candle.cs index b335a900c..44f98eae5 100644 --- a/Scripts/Items/Lights/Candle.cs +++ b/Scripts/Items/Lights/Candle.cs @@ -2,38 +2,38 @@ using System; namespace Server.Items { - public class Candle : BaseEquipableLight - { - public override int LitItemID => 0xA0F; - public override int UnlitItemID => 0xA28; + public class Candle : BaseEquipableLight + { + [Constructible] + public Candle() : base(0xA28) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(20); + else + Duration = TimeSpan.Zero; - [Constructible] - public Candle() : base( 0xA28 ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 20 ); - else - Duration = TimeSpan.Zero; + Burning = false; + Light = LightType.Circle150; + Weight = 1.0; + } - Burning = false; - Light = LightType.Circle150; - Weight = 1.0; - } + public Candle(Serial serial) : base(serial) + { + } - public Candle( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xA0F; + public override int UnlitItemID => 0xA28; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/CandleLarge.cs b/Scripts/Items/Lights/CandleLarge.cs index f5d7257a5..c6003c422 100644 --- a/Scripts/Items/Lights/CandleLarge.cs +++ b/Scripts/Items/Lights/CandleLarge.cs @@ -2,38 +2,38 @@ using System; namespace Server.Items { - public class CandleLarge : BaseLight - { - public override int LitItemID => 0xB1A; - public override int UnlitItemID => 0xA26; + public class CandleLarge : BaseLight + { + [Constructible] + public CandleLarge() : base(0xA26) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(25); + else + Duration = TimeSpan.Zero; - [Constructible] - public CandleLarge() : base( 0xA26 ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 25 ); - else - Duration = TimeSpan.Zero; + Burning = false; + Light = LightType.Circle150; + Weight = 2.0; + } - Burning = false; - Light = LightType.Circle150; - Weight = 2.0; - } + public CandleLarge(Serial serial) : base(serial) + { + } - public CandleLarge( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xB1A; + public override int UnlitItemID => 0xA26; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/CandleLong.cs b/Scripts/Items/Lights/CandleLong.cs index 7ffd50ddb..2e2c174ad 100644 --- a/Scripts/Items/Lights/CandleLong.cs +++ b/Scripts/Items/Lights/CandleLong.cs @@ -2,38 +2,38 @@ using System; namespace Server.Items { - public class CandleLong : BaseLight - { - public override int LitItemID => 0x1430; - public override int UnlitItemID => 0x1433; + public class CandleLong : BaseLight + { + [Constructible] + public CandleLong() : base(0x1433) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(30); + else + Duration = TimeSpan.Zero; - [Constructible] - public CandleLong() : base( 0x1433 ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 30 ); - else - Duration = TimeSpan.Zero; + Burning = false; + Light = LightType.Circle150; + Weight = 1.0; + } - Burning = false; - Light = LightType.Circle150; - Weight = 1.0; - } + public CandleLong(Serial serial) : base(serial) + { + } - public CandleLong( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0x1430; + public override int UnlitItemID => 0x1433; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/CandleShort.cs b/Scripts/Items/Lights/CandleShort.cs index 4d6e802d5..db392d098 100644 --- a/Scripts/Items/Lights/CandleShort.cs +++ b/Scripts/Items/Lights/CandleShort.cs @@ -2,38 +2,38 @@ using System; namespace Server.Items { - public class CandleShort : BaseLight - { - public override int LitItemID => 0x142C; - public override int UnlitItemID => 0x142F; + public class CandleShort : BaseLight + { + [Constructible] + public CandleShort() : base(0x142F) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(25); + else + Duration = TimeSpan.Zero; - [Constructible] - public CandleShort() : base( 0x142F ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 25 ); - else - Duration = TimeSpan.Zero; + Burning = false; + Light = LightType.Circle150; + Weight = 1.0; + } - Burning = false; - Light = LightType.Circle150; - Weight = 1.0; - } + public CandleShort(Serial serial) : base(serial) + { + } - public CandleShort( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0x142C; + public override int UnlitItemID => 0x142F; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/CandleSkull.cs b/Scripts/Items/Lights/CandleSkull.cs index 791d5d7a0..23154db0d 100644 --- a/Scripts/Items/Lights/CandleSkull.cs +++ b/Scripts/Items/Lights/CandleSkull.cs @@ -2,57 +2,57 @@ using System; namespace Server.Items { - public class CandleSkull : BaseLight - { - public override int LitItemID - { - get - { - if ( ItemID == 0x1583 || ItemID == 0x1854 ) - return 0x1854; + public class CandleSkull : BaseLight + { + [Constructible] + public CandleSkull() : base(0x1853) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(25); + else + Duration = TimeSpan.Zero; - return 0x1858; - } - } + Burning = false; + Light = LightType.Circle150; + Weight = 5.0; + } - public override int UnlitItemID - { - get - { - if ( ItemID == 0x1853 || ItemID == 0x1584 ) - return 0x1853; + public CandleSkull(Serial serial) : base(serial) + { + } - return 0x1857; - } - } + public override int LitItemID + { + get + { + if (ItemID == 0x1583 || ItemID == 0x1854) + return 0x1854; - [Constructible] - public CandleSkull() : base( 0x1853 ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 25 ); - else - Duration = TimeSpan.Zero; + return 0x1858; + } + } - Burning = false; - Light = LightType.Circle150; - Weight = 5.0; - } + public override int UnlitItemID + { + get + { + if (ItemID == 0x1853 || ItemID == 0x1584) + return 0x1853; - public CandleSkull( Serial serial ) : base( serial ) - { - } + return 0x1857; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Lights/DarkSource.cs b/Scripts/Items/Lights/DarkSource.cs index b2aea3c3e..cb29c25d2 100644 --- a/Scripts/Items/Lights/DarkSource.cs +++ b/Scripts/Items/Lights/DarkSource.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class DarkSource : Item - { - [Constructible] - public DarkSource() : base( 0x1646 ) - { - Layer = Layer.TwoHanded; - Movable = false; - } + public class DarkSource : Item + { + [Constructible] + public DarkSource() : base(0x1646) + { + Layer = Layer.TwoHanded; + Movable = false; + } - public DarkSource( Serial serial ) : base( serial ) - { - } + public DarkSource(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Lights/HangingLantern.cs b/Scripts/Items/Lights/HangingLantern.cs index c2a5af845..a0b7e9316 100644 --- a/Scripts/Items/Lights/HangingLantern.cs +++ b/Scripts/Items/Lights/HangingLantern.cs @@ -2,35 +2,35 @@ using System; namespace Server.Items { - public class HangingLantern : BaseLight - { - public override int LitItemID => 0xA1A; - public override int UnlitItemID => 0xA1D; + public class HangingLantern : BaseLight + { + [Constructible] + public HangingLantern() : base(0xA1D) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle300; + Weight = 40.0; + } - [Constructible] - public HangingLantern() : base( 0xA1D ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle300; - Weight = 40.0; - } + public HangingLantern(Serial serial) : base(serial) + { + } - public HangingLantern( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xA1A; + public override int UnlitItemID => 0xA1D; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/HeatingStand.cs b/Scripts/Items/Lights/HeatingStand.cs index 4b71ec368..734ce869f 100644 --- a/Scripts/Items/Lights/HeatingStand.cs +++ b/Scripts/Items/Lights/HeatingStand.cs @@ -2,58 +2,58 @@ using System; namespace Server.Items { - public class HeatingStand : BaseLight - { - public override int LitItemID => 0x184A; - public override int UnlitItemID => 0x1849; + public class HeatingStand : BaseLight + { + [Constructible] + public HeatingStand() : base(0x1849) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(25); + else + Duration = TimeSpan.Zero; - [Constructible] - public HeatingStand() : base( 0x1849 ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 25 ); - else - Duration = TimeSpan.Zero; + Burning = false; + Light = LightType.Empty; + Weight = 1.0; + } - Burning = false; - Light = LightType.Empty; - Weight = 1.0; - } + public HeatingStand(Serial serial) : base(serial) + { + } - public override void Ignite() - { - base.Ignite(); + public override int LitItemID => 0x184A; + public override int UnlitItemID => 0x1849; - if ( ItemID == LitItemID ) - Light = LightType.Circle150; - else if ( ItemID == UnlitItemID ) - Light = LightType.Empty; - } + public override void Ignite() + { + base.Ignite(); - public override void Douse() - { - base.Douse(); + if (ItemID == LitItemID) + Light = LightType.Circle150; + else if (ItemID == UnlitItemID) + Light = LightType.Empty; + } - if ( ItemID == LitItemID ) - Light = LightType.Circle150; - else if ( ItemID == UnlitItemID ) - Light = LightType.Empty; - } + public override void Douse() + { + base.Douse(); - public HeatingStand( Serial serial ) : base( serial ) - { - } + if (ItemID == LitItemID) + Light = LightType.Circle150; + else if (ItemID == UnlitItemID) + Light = LightType.Empty; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/LampPost1.cs b/Scripts/Items/Lights/LampPost1.cs index 65f57622d..c3e4e13bb 100644 --- a/Scripts/Items/Lights/LampPost1.cs +++ b/Scripts/Items/Lights/LampPost1.cs @@ -2,35 +2,35 @@ using System; namespace Server.Items { - public class LampPost1 : BaseLight - { - public override int LitItemID => 0xB20; - public override int UnlitItemID => 0xB21; + public class LampPost1 : BaseLight + { + [Constructible] + public LampPost1() : base(0xB21) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle300; + Weight = 40.0; + } - [Constructible] - public LampPost1() : base( 0xB21 ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle300; - Weight = 40.0; - } + public LampPost1(Serial serial) : base(serial) + { + } - public LampPost1( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xB20; + public override int UnlitItemID => 0xB21; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/LampPost2.cs b/Scripts/Items/Lights/LampPost2.cs index bf2ddb3e8..19ca9c934 100644 --- a/Scripts/Items/Lights/LampPost2.cs +++ b/Scripts/Items/Lights/LampPost2.cs @@ -2,35 +2,35 @@ using System; namespace Server.Items { - public class LampPost2 : BaseLight - { - public override int LitItemID => 0xB22; - public override int UnlitItemID => 0xB23; + public class LampPost2 : BaseLight + { + [Constructible] + public LampPost2() : base(0xB23) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle300; + Weight = 40.0; + } - [Constructible] - public LampPost2() : base( 0xB23 ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle300; - Weight = 40.0; - } + public LampPost2(Serial serial) : base(serial) + { + } - public LampPost2( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xB22; + public override int UnlitItemID => 0xB23; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/LampPost3.cs b/Scripts/Items/Lights/LampPost3.cs index 2e43430a3..0b7506f91 100644 --- a/Scripts/Items/Lights/LampPost3.cs +++ b/Scripts/Items/Lights/LampPost3.cs @@ -2,35 +2,35 @@ using System; namespace Server.Items { - public class LampPost3 : BaseLight - { - public override int LitItemID => 0xB24; - public override int UnlitItemID => 0xB25; + public class LampPost3 : BaseLight + { + [Constructible] + public LampPost3() : base(0xb25) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle300; + Weight = 40.0; + } - [Constructible] - public LampPost3() : base( 0xb25 ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle300; - Weight = 40.0; - } + public LampPost3(Serial serial) : base(serial) + { + } - public LampPost3( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0xB24; + public override int UnlitItemID => 0xB25; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/Lantern.cs b/Scripts/Items/Lights/Lantern.cs index e1ae17ede..70f9fc271 100644 --- a/Scripts/Items/Lights/Lantern.cs +++ b/Scripts/Items/Lights/Lantern.cs @@ -2,84 +2,84 @@ using System; namespace Server.Items { - public class Lantern : BaseEquipableLight - { - public override int LitItemID - { - get - { - if ( ItemID == 0xA15 || ItemID == 0xA17 ) - return ItemID; + public class Lantern : BaseEquipableLight + { + [Constructible] + public Lantern() : base(0xA25) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(20); + else + Duration = TimeSpan.Zero; - return 0xA22; - } - } + Burning = false; + Light = LightType.Circle300; + Weight = 2.0; + } - public override int UnlitItemID - { - get - { - if ( ItemID == 0xA18 ) - return ItemID; + public Lantern(Serial serial) : base(serial) + { + } - return 0xA25; - } - } + public override int LitItemID + { + get + { + if (ItemID == 0xA15 || ItemID == 0xA17) + return ItemID; - [Constructible] - public Lantern() : base( 0xA25 ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 20 ); - else - Duration = TimeSpan.Zero; + return 0xA22; + } + } - Burning = false; - Light = LightType.Circle300; - Weight = 2.0; - } + public override int UnlitItemID + { + get + { + if (ItemID == 0xA18) + return ItemID; - public Lantern( Serial serial ) : base( serial ) - { - } + return 0xA25; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class LanternOfSouls : Lantern - { - public override int LabelNumber => 1061618; // Lantern of Souls + public class LanternOfSouls : Lantern + { + [Constructible] + public LanternOfSouls() + { + Hue = 0x482; + } - [Constructible] - public LanternOfSouls() - { - Hue = 0x482; - } + public LanternOfSouls(Serial serial) : base(serial) + { + } - public LanternOfSouls( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1061618; // Lantern of Souls - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/LightSource.cs b/Scripts/Items/Lights/LightSource.cs index 98a7e6246..2a8902782 100644 --- a/Scripts/Items/Lights/LightSource.cs +++ b/Scripts/Items/Lights/LightSource.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class LightSource : Item - { - [Constructible] - public LightSource() : base( 0x1647 ) - { - Layer = Layer.TwoHanded; - Movable = false; - } + public class LightSource : Item + { + [Constructible] + public LightSource() : base(0x1647) + { + Layer = Layer.TwoHanded; + Movable = false; + } - public LightSource( Serial serial ) : base( serial ) - { - } + public LightSource(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Lights/PaperLantern.cs b/Scripts/Items/Lights/PaperLantern.cs index 4de38183c..0993bcf8b 100644 --- a/Scripts/Items/Lights/PaperLantern.cs +++ b/Scripts/Items/Lights/PaperLantern.cs @@ -2,36 +2,36 @@ using System; namespace Server.Items { - [Flippable] - public class PaperLantern : BaseLight - { - public override int LitItemID => 0x24BD; - public override int UnlitItemID => 0x24BE; + [Flippable] + public class PaperLantern : BaseLight + { + [Constructible] + public PaperLantern() : base(0x24BE) + { + Movable = true; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle150; + Weight = 3.0; + } - [Constructible] - public PaperLantern() : base( 0x24BE ) - { - Movable = true; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle150; - Weight = 3.0; - } + public PaperLantern(Serial serial) : base(serial) + { + } - public PaperLantern( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0x24BD; + public override int UnlitItemID => 0x24BE; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/RedHangingLantern.cs b/Scripts/Items/Lights/RedHangingLantern.cs index 757977b5c..26df79f5d 100644 --- a/Scripts/Items/Lights/RedHangingLantern.cs +++ b/Scripts/Items/Lights/RedHangingLantern.cs @@ -2,67 +2,75 @@ using System; namespace Server.Items { - [Flippable] - public class RedHangingLantern : BaseLight - { - public override int LitItemID - { - get - { - if ( ItemID == 0x24C2 ) - return 0x24C1; - return 0x24C3; - } - } - - public override int UnlitItemID - { - get - { - if ( ItemID == 0x24C1 ) - return 0x24C2; - return 0x24C4; - } - } - - [Constructible] - public RedHangingLantern() : base( 0x24C2 ) - { - Movable = true; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle300; - Weight = 3.0; - } + [Flippable] + public class RedHangingLantern : BaseLight + { + [Constructible] + public RedHangingLantern() : base(0x24C2) + { + Movable = true; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle300; + Weight = 3.0; + } - public RedHangingLantern( Serial serial ) : base( serial ) - { - } + public RedHangingLantern(Serial serial) : base(serial) + { + } - public void Flip() - { - Light = LightType.Circle300; + public override int LitItemID + { + get + { + if (ItemID == 0x24C2) + return 0x24C1; + return 0x24C3; + } + } - switch ( ItemID ) - { - case 0x24C2: ItemID = 0x24C4; break; - case 0x24C1: ItemID = 0x24C3; break; + public override int UnlitItemID + { + get + { + if (ItemID == 0x24C1) + return 0x24C2; + return 0x24C4; + } + } - case 0x24C4: ItemID = 0x24C2; break; - case 0x24C3: ItemID = 0x24C1; break; - } - } + public void Flip() + { + Light = LightType.Circle300; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + switch (ItemID) + { + case 0x24C2: + ItemID = 0x24C4; + break; + case 0x24C1: + ItemID = 0x24C3; + break; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + case 0x24C4: + ItemID = 0x24C2; + break; + case 0x24C3: + ItemID = 0x24C1; + break; + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Lights/RoundPaperLantern.cs b/Scripts/Items/Lights/RoundPaperLantern.cs index b2af489f0..1be795efd 100644 --- a/Scripts/Items/Lights/RoundPaperLantern.cs +++ b/Scripts/Items/Lights/RoundPaperLantern.cs @@ -2,36 +2,36 @@ using System; namespace Server.Items { - [Flippable] - public class RoundPaperLantern : BaseLight - { - public override int LitItemID => 0x24C9; - public override int UnlitItemID => 0x24CA; + [Flippable] + public class RoundPaperLantern : BaseLight + { + [Constructible] + public RoundPaperLantern() : base(0x24CA) + { + Movable = true; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle150; + Weight = 3.0; + } - [Constructible] - public RoundPaperLantern() : base( 0x24CA ) - { - Movable = true; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle150; - Weight = 3.0; - } + public RoundPaperLantern(Serial serial) : base(serial) + { + } - public RoundPaperLantern( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0x24C9; + public override int UnlitItemID => 0x24CA; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/ShojiLantern.cs b/Scripts/Items/Lights/ShojiLantern.cs index d0a035032..bde63996d 100644 --- a/Scripts/Items/Lights/ShojiLantern.cs +++ b/Scripts/Items/Lights/ShojiLantern.cs @@ -2,36 +2,36 @@ using System; namespace Server.Items { - [Flippable] - public class ShojiLantern : BaseLight - { - public override int LitItemID => 0x24BB; - public override int UnlitItemID => 0x24BC; + [Flippable] + public class ShojiLantern : BaseLight + { + [Constructible] + public ShojiLantern() : base(0x24BC) + { + Movable = true; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle150; + Weight = 3.0; + } - [Constructible] - public ShojiLantern() : base( 0x24BC ) - { - Movable = true; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle150; - Weight = 3.0; - } + public ShojiLantern(Serial serial) : base(serial) + { + } - public ShojiLantern( Serial serial ) : base( serial ) - { - } + public override int LitItemID => 0x24BB; + public override int UnlitItemID => 0x24BC; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/Torch.cs b/Scripts/Items/Lights/Torch.cs index d9adb2374..046b83c13 100644 --- a/Scripts/Items/Lights/Torch.cs +++ b/Scripts/Items/Lights/Torch.cs @@ -1,61 +1,62 @@ using System; +using Server.Mobiles; namespace Server.Items { - public class Torch : BaseEquipableLight - { - public override int LitItemID => 0xA12; - public override int UnlitItemID => 0xF6B; + public class Torch : BaseEquipableLight + { + [Constructible] + public Torch() : base(0xF6B) + { + if (Burnout) + Duration = TimeSpan.FromMinutes(30); + else + Duration = TimeSpan.Zero; - public override int LitSound => 0x54; - public override int UnlitSound => 0x4BB; + Burning = false; + Light = LightType.Circle300; + Weight = 1.0; + } - [Constructible] - public Torch() : base( 0xF6B ) - { - if ( Burnout ) - Duration = TimeSpan.FromMinutes( 30 ); - else - Duration = TimeSpan.Zero; + public Torch(Serial serial) : base(serial) + { + } - Burning = false; - Light = LightType.Circle300; - Weight = 1.0; - } + public override int LitItemID => 0xA12; + public override int UnlitItemID => 0xF6B; - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); + public override int LitSound => 0x54; + public override int UnlitSound => 0x4BB; - if ( parent is Mobile mobile && Burning ) - Mobiles.MeerMage.StopEffect( mobile, true ); - } + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - public override void Ignite() - { - base.Ignite(); + if (parent is Mobile mobile && Burning) + MeerMage.StopEffect(mobile, true); + } - if ( Parent is Mobile mobile && Burning ) - Mobiles.MeerMage.StopEffect( mobile, true ); - } + public override void Ignite() + { + base.Ignite(); - public Torch( Serial serial ) : base( serial ) - { - } + if (Parent is Mobile mobile && Burning) + MeerMage.StopEffect(mobile, true); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } -} + if (Weight == 2.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Lights/WallSconce.cs b/Scripts/Items/Lights/WallSconce.cs index bbf5cf2e9..2f01399b4 100644 --- a/Scripts/Items/Lights/WallSconce.cs +++ b/Scripts/Items/Lights/WallSconce.cs @@ -2,70 +2,78 @@ using System; namespace Server.Items { - [Flippable] - public class WallSconce : BaseLight - { - public override int LitItemID - { - get - { - if ( ItemID == 0x9FB ) - return 0x9FD; - return 0xA02; - } - } - - public override int UnlitItemID - { - get - { - if ( ItemID == 0x9FD ) - return 0x9FB; - return 0xA00; - } - } - - [Constructible] - public WallSconce() : base( 0x9FB ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.WestBig; - Weight = 3.0; - } + [Flippable] + public class WallSconce : BaseLight + { + [Constructible] + public WallSconce() : base(0x9FB) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.WestBig; + Weight = 3.0; + } - public WallSconce( Serial serial ) : base( serial ) - { - } + public WallSconce(Serial serial) : base(serial) + { + } - public void Flip() - { - if ( Light == LightType.WestBig ) - Light = LightType.NorthBig; - else if ( Light == LightType.NorthBig ) - Light = LightType.WestBig; + public override int LitItemID + { + get + { + if (ItemID == 0x9FB) + return 0x9FD; + return 0xA02; + } + } - switch ( ItemID ) - { - case 0x9FB: ItemID = 0xA00; break; - case 0x9FD: ItemID = 0xA02; break; + public override int UnlitItemID + { + get + { + if (ItemID == 0x9FD) + return 0x9FB; + return 0xA00; + } + } - case 0xA00: ItemID = 0x9FB; break; - case 0xA02: ItemID = 0x9FD; break; - } - } + public void Flip() + { + if (Light == LightType.WestBig) + Light = LightType.NorthBig; + else if (Light == LightType.NorthBig) + Light = LightType.WestBig; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + switch (ItemID) + { + case 0x9FB: + ItemID = 0xA00; + break; + case 0x9FD: + ItemID = 0xA02; + break; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + case 0xA00: + ItemID = 0x9FB; + break; + case 0xA02: + ItemID = 0x9FD; + break; + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Lights/WallTorch.cs b/Scripts/Items/Lights/WallTorch.cs index e8016d136..eb0be6321 100644 --- a/Scripts/Items/Lights/WallTorch.cs +++ b/Scripts/Items/Lights/WallTorch.cs @@ -2,70 +2,78 @@ using System; namespace Server.Items { - [Flippable] - public class WallTorch : BaseLight - { - public override int LitItemID - { - get - { - if ( ItemID == 0xA05 ) - return 0xA07; - return 0xA0C; - } - } - - public override int UnlitItemID - { - get - { - if ( ItemID == 0xA07 ) - return 0xA05; - return 0xA0A; - } - } - - [Constructible] - public WallTorch() : base( 0xA05 ) - { - Movable = false; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.WestBig; - Weight = 3.0; - } + [Flippable] + public class WallTorch : BaseLight + { + [Constructible] + public WallTorch() : base(0xA05) + { + Movable = false; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.WestBig; + Weight = 3.0; + } - public WallTorch( Serial serial ) : base( serial ) - { - } + public WallTorch(Serial serial) : base(serial) + { + } - public void Flip() - { - if ( Light == LightType.WestBig ) - Light = LightType.NorthBig; - else if ( Light == LightType.NorthBig ) - Light = LightType.WestBig; + public override int LitItemID + { + get + { + if (ItemID == 0xA05) + return 0xA07; + return 0xA0C; + } + } - switch ( ItemID ) - { - case 0xA05: ItemID = 0xA0A; break; - case 0xA07: ItemID = 0xA0C; break; + public override int UnlitItemID + { + get + { + if (ItemID == 0xA07) + return 0xA05; + return 0xA0A; + } + } - case 0xA0A: ItemID = 0xA05; break; - case 0xA0C: ItemID = 0xA07; break; - } - } + public void Flip() + { + if (Light == LightType.WestBig) + Light = LightType.NorthBig; + else if (Light == LightType.NorthBig) + Light = LightType.WestBig; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + switch (ItemID) + { + case 0xA05: + ItemID = 0xA0A; + break; + case 0xA07: + ItemID = 0xA0C; + break; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + case 0xA0A: + ItemID = 0xA05; + break; + case 0xA0C: + ItemID = 0xA07; + break; + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Lights/WhiteHangingLantern.cs b/Scripts/Items/Lights/WhiteHangingLantern.cs index 26dd8af82..1c0cd8749 100644 --- a/Scripts/Items/Lights/WhiteHangingLantern.cs +++ b/Scripts/Items/Lights/WhiteHangingLantern.cs @@ -2,67 +2,75 @@ using System; namespace Server.Items { - [Flippable] - public class WhiteHangingLantern : BaseLight - { - public override int LitItemID - { - get - { - if ( ItemID == 0x24C6 ) - return 0x24C5; - return 0x24C7; - } - } - - public override int UnlitItemID - { - get - { - if ( ItemID == 0x24C5 ) - return 0x24C6; - return 0x24C8; - } - } - - [Constructible] - public WhiteHangingLantern() : base( 0x24C6 ) - { - Movable = true; - Duration = TimeSpan.Zero; // Never burnt out - Burning = false; - Light = LightType.Circle300; - Weight = 3.0; - } + [Flippable] + public class WhiteHangingLantern : BaseLight + { + [Constructible] + public WhiteHangingLantern() : base(0x24C6) + { + Movable = true; + Duration = TimeSpan.Zero; // Never burnt out + Burning = false; + Light = LightType.Circle300; + Weight = 3.0; + } - public WhiteHangingLantern( Serial serial ) : base( serial ) - { - } + public WhiteHangingLantern(Serial serial) : base(serial) + { + } - public void Flip() - { - Light = LightType.Circle300; + public override int LitItemID + { + get + { + if (ItemID == 0x24C6) + return 0x24C5; + return 0x24C7; + } + } - switch ( ItemID ) - { - case 0x24C6: ItemID = 0x24C8; break; - case 0x24C5: ItemID = 0x24C7; break; + public override int UnlitItemID + { + get + { + if (ItemID == 0x24C5) + return 0x24C6; + return 0x24C8; + } + } - case 0x24C8: ItemID = 0x24C6; break; - case 0x24C7: ItemID = 0x24C5; break; - } - } + public void Flip() + { + Light = LightType.Circle300; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + switch (ItemID) + { + case 0x24C6: + ItemID = 0x24C8; + break; + case 0x24C5: + ItemID = 0x24C7; + break; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + case 0x24C8: + ItemID = 0x24C6; + break; + case 0x24C7: + ItemID = 0x24C5; + break; + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Maps/BlankMap.cs b/Scripts/Items/Maps/BlankMap.cs index 4eb7883cd..091d4c861 100644 --- a/Scripts/Items/Maps/BlankMap.cs +++ b/Scripts/Items/Maps/BlankMap.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class BlankMap : MapItem - { - [Constructible] - public BlankMap() - { - } + public class BlankMap : MapItem + { + [Constructible] + public BlankMap() + { + } - public override void OnDoubleClick( Mobile from ) - { - SendLocalizedMessageTo( from, 500208 ); // It appears to be blank. - } + public BlankMap(Serial serial) : base(serial) + { + } - public BlankMap( Serial serial ) : base( serial ) - { - } + public override void OnDoubleClick(Mobile from) + { + SendLocalizedMessageTo(from, 500208); // It appears to be blank. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Maps/CityMap.cs b/Scripts/Items/Maps/CityMap.cs index e7508de96..146a7e2d9 100644 --- a/Scripts/Items/Maps/CityMap.cs +++ b/Scripts/Items/Maps/CityMap.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class CityMap : MapItem - { - [Constructible] - public CityMap() - { - SetDisplay( 0, 0, 5119, 4095, 400, 400 ); - } + public class CityMap : MapItem + { + [Constructible] + public CityMap() + { + SetDisplay(0, 0, 5119, 4095, 400, 400); + } - public override void CraftInit( Mobile from ) - { - double skillValue = from.Skills[SkillName.Cartography].Value; - int dist = 64 + (int)(skillValue * 4); + public CityMap(Serial serial) : base(serial) + { + } - if ( dist < 200 ) - dist = 200; + public override int LabelNumber => 1015231; // city map - int size = 32 + (int)(skillValue * 2); + public override void CraftInit(Mobile from) + { + double skillValue = from.Skills[SkillName.Cartography].Value; + int dist = 64 + (int)(skillValue * 4); - if ( size < 200 ) - size = 200; - else if ( size > 400 ) - size = 400; + if (dist < 200) + dist = 200; - SetDisplay( from.X - dist, from.Y - dist, from.X + dist, from.Y + dist, size, size ); - } + int size = 32 + (int)(skillValue * 2); - public override int LabelNumber => 1015231; // city map + if (size < 200) + size = 200; + else if (size > 400) + size = 400; - public CityMap( Serial serial ) : base( serial ) - { - } + SetDisplay(from.X - dist, from.Y - dist, from.X + dist, from.Y + dist, size, size); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/IndecipherableMap.cs b/Scripts/Items/Maps/IndecipherableMap.cs index 30b78e5d8..9cc9dfe9d 100644 --- a/Scripts/Items/Maps/IndecipherableMap.cs +++ b/Scripts/Items/Maps/IndecipherableMap.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class IndecipherableMap : MapItem - { - public override int LabelNumber => 1070799; // indecipherable map + public class IndecipherableMap : MapItem + { + [Constructible] + public IndecipherableMap() + { + if (Utility.RandomDouble() < 0.2) + Hue = 0x965; + else + Hue = 0x961; + } - [Constructible] - public IndecipherableMap() - { - if ( Utility.RandomDouble() < 0.2 ) - Hue = 0x965; - else - Hue = 0x961; - } + public IndecipherableMap(Serial serial) : base(serial) + { + } - public IndecipherableMap( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1070799; // indecipherable map - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 1070801 ); // You cannot decipher this ruined map. - } + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(1070801); // You cannot decipher this ruined map. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/LocalMap.cs b/Scripts/Items/Maps/LocalMap.cs index 98400fbe0..995492377 100644 --- a/Scripts/Items/Maps/LocalMap.cs +++ b/Scripts/Items/Maps/LocalMap.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class LocalMap : MapItem - { - [Constructible] - public LocalMap() - { - SetDisplay( 0, 0, 5119, 4095, 400, 400 ); - } + public class LocalMap : MapItem + { + [Constructible] + public LocalMap() + { + SetDisplay(0, 0, 5119, 4095, 400, 400); + } - public override void CraftInit( Mobile from ) - { - double skillValue = from.Skills[SkillName.Cartography].Value; - int dist = 64 + (int)(skillValue * 2); + public LocalMap(Serial serial) : base(serial) + { + } - SetDisplay( from.X - dist, from.Y - dist, from.X + dist, from.Y + dist, 200, 200 ); - } + public override int LabelNumber => 1015230; // local map - public override int LabelNumber => 1015230; // local map + public override void CraftInit(Mobile from) + { + double skillValue = from.Skills[SkillName.Cartography].Value; + int dist = 64 + (int)(skillValue * 2); - public LocalMap( Serial serial ) : base( serial ) - { - } + SetDisplay(from.X - dist, from.Y - dist, from.X + dist, from.Y + dist, 200, 200); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/MapItem.cs b/Scripts/Items/Maps/MapItem.cs index 1e34e67ec..c4ccac327 100644 --- a/Scripts/Items/Maps/MapItem.cs +++ b/Scripts/Items/Maps/MapItem.cs @@ -1,373 +1,386 @@ using System; using System.Collections.Generic; -using Server.Network; using Server.Engines.Craft; +using Server.Network; namespace Server.Items { - [Flippable( 0x14EB, 0x14EC )] - public class MapItem : Item, ICraftable - { - private bool m_Editable; + [Flippable(0x14EB, 0x14EC)] + public class MapItem : Item, ICraftable + { + private const int MaxUserPins = 50; + private bool m_Editable; - private const int MaxUserPins = 50; + [Constructible] + public MapItem() : base(0x14EC) + { + Weight = 1.0; - [CommandProperty( AccessLevel.GameMaster )] - public bool Protected { get; set; } + Width = 200; + Height = 200; + } - [CommandProperty( AccessLevel.GameMaster )] - public Rectangle2D Bounds { get; set; } + public MapItem(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Width { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public bool Protected{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int Height { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public Rectangle2D Bounds{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Width{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Height{ get; set; } - public List Pins { get; } = new List(); + public List Pins{ get; } = new List(); + + #region ICraftable Members - [Constructible] - public MapItem() : base( 0x14EC ) - { - Weight = 1.0; + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + CraftInit(from); + return 1; + } - Width = 200; - Height = 200; - } - - public virtual void CraftInit( Mobile from ) - { - } - - public void SetDisplay( int x1, int y1, int x2, int y2, int w, int h ) - { - Width = w; - Height = h; - - if ( x1 < 0 ) - x1 = 0; - - if ( y1 < 0 ) - y1 = 0; - - if ( x2 >= 5120 ) - x2 = 5119; - - if ( y2 >= 4096 ) - y2 = 4095; - - Bounds = new Rectangle2D( x1, y1, x2-x1, y2-y1 ); - } - - public MapItem( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - DisplayTo( from ); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - - public virtual void DisplayTo( Mobile from ) - { - from.Send( new MapDetails( this ) ); - from.Send( new MapDisplay( this ) ); - - for ( int i = 0; i < Pins.Count; ++i ) - from.Send( new MapAddPin( this, Pins[i] ) ); - - from.Send( new MapSetEditable( this, ValidateEdit( from ) ) ); - } - - public virtual void OnAddPin( Mobile from, int x, int y ) - { - if ( !ValidateEdit( from ) ) - return; - if ( Pins.Count >= MaxUserPins ) - return; - - Validate( ref x, ref y ); - AddPin( x, y ); - } - - public virtual void OnRemovePin( Mobile from, int number ) - { - if ( !ValidateEdit( from ) ) - return; - - RemovePin( number ); - } - - public virtual void OnChangePin( Mobile from, int number, int x, int y ) - { - if ( !ValidateEdit( from ) ) - return; - - Validate( ref x, ref y ); - ChangePin( number, x, y ); - } - - public virtual void OnInsertPin( Mobile from, int number, int x, int y ) - { - if ( !ValidateEdit( from ) ) - return; - if ( Pins.Count >= MaxUserPins ) - return; - - Validate( ref x, ref y ); - InsertPin( number, x, y ); - } - - public virtual void OnClearPins( Mobile from ) - { - if ( !ValidateEdit( from ) ) - return; - - ClearPins(); - } - - public virtual void OnToggleEditable( Mobile from ) - { - if ( Validate( from ) ) - m_Editable = !m_Editable; - - from.Send( new MapSetEditable( this, Validate( from ) && m_Editable ) ); - } - - public virtual void Validate( ref int x, ref int y ) - { - if ( x < 0 ) - x = 0; - else if ( x >= Width ) - x = Width - 1; - - if ( y < 0 ) - y = 0; - else if ( y >= Height ) - y = Height - 1; - } - - public virtual bool ValidateEdit( Mobile from ) - { - return m_Editable && Validate( from ); - } - - public virtual bool Validate( Mobile from ) - { - if ( !from.CanSee( this ) || from.Map != Map || !from.Alive || InSecureTrade ) - return false; - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - if ( !Movable || Protected || !from.InRange( GetWorldLocation(), 2 ) ) - return false; - - object root = RootParent; - - if ( root is Mobile && root != from ) - return false; - - return true; - } - - public void ConvertToWorld( int x, int y, out int worldX, out int worldY ) - { - worldX = ( ( Bounds.Width * x ) / Width ) + Bounds.X; - worldY = ( ( Bounds.Height * y ) / Height ) + Bounds.Y; - } - - public void ConvertToMap( int x, int y, out int mapX, out int mapY ) - { - mapX = ( ( x - Bounds.X ) * Width ) / Bounds.Width; - mapY = ( ( y - Bounds.Y ) * Width ) / Bounds.Height; - } - - public virtual void AddWorldPin( int x, int y ) - { - int mapX, mapY; - ConvertToMap( x, y, out mapX, out mapY ); - - AddPin( mapX, mapY ); - } - - public virtual void AddPin( int x, int y ) - { - Pins.Add( new Point2D( x, y ) ); - } - - public virtual void RemovePin( int index ) - { - if ( index > 0 && index < Pins.Count ) - Pins.RemoveAt( index ); - } - - public virtual void InsertPin( int index, int x, int y ) - { - if ( index < 0 || index >= Pins.Count ) - Pins.Add( new Point2D( x, y ) ); - else - Pins.Insert( index, new Point2D( x, y ) ); - } - - public virtual void ChangePin( int index, int x, int y ) - { - if ( index >= 0 && index < Pins.Count ) - Pins[index] = new Point2D( x, y ); - } - - public virtual void ClearPins() - { - Pins.Clear(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - - writer.Write( Bounds ); - - writer.Write( Width ); - writer.Write( Height ); - - writer.Write( Protected ); - - writer.Write( Pins.Count ); - for ( int i = 0; i < Pins.Count; ++i ) - writer.Write( Pins[i] ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Bounds = reader.ReadRect2D(); - - Width = reader.ReadInt(); - Height = reader.ReadInt(); - - Protected = reader.ReadBool(); - - int count = reader.ReadInt(); - for ( int i = 0; i < count; i++ ) - Pins.Add( reader.ReadPoint2D() ); - - break; - } - } - } - - public static void Initialize() - { - PacketHandlers.Register( 0x56, 11, true, OnMapCommand ); - } - - private static void OnMapCommand( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if ( !(World.FindItem( pvSrc.ReadInt32() ) is MapItem map) ) - return; - - int command = pvSrc.ReadByte(); - int number = pvSrc.ReadByte(); - - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - - switch ( command ) - { - case 1: map.OnAddPin( from, x, y ); break; - case 2: map.OnInsertPin( from, number, x, y ); break; - case 3: map.OnChangePin( from, number, x, y ); break; - case 4: map.OnRemovePin( from, number ); break; - case 5: map.OnClearPins( from ); break; - case 6: map.OnToggleEditable( from ); break; - } - } - - private sealed class MapDetails : Packet - { - public MapDetails( MapItem map ) : base ( 0x90, 19 ) - { - m_Stream.Write( (int) map.Serial ); - m_Stream.Write( (short) 0x139D ); - m_Stream.Write( (short) map.Bounds.Start.X ); - m_Stream.Write( (short) map.Bounds.Start.Y ); - m_Stream.Write( (short) map.Bounds.End.X ); - m_Stream.Write( (short) map.Bounds.End.Y ); - m_Stream.Write( (short) map.Width ); - m_Stream.Write( (short) map.Height ); - } - } - - /* - private sealed class MapDetailsNew : Packet - { - public MapDetailsNew( MapItem map ) : base ( 0xF5, 21 ) - { - m_Stream.Write( (int) map.Serial ); - m_Stream.Write( (short) 0x139D ); - m_Stream.Write( (short) map.Bounds.Start.X ); - m_Stream.Write( (short) map.Bounds.Start.Y ); - m_Stream.Write( (short) map.Bounds.End.X ); - m_Stream.Write( (short) map.Bounds.End.Y ); - m_Stream.Write( (short) map.Width ); - m_Stream.Write( (short) map.Height ); - m_Stream.Write( (short) ( map.Facet == null ? 0 : map.Facet.MapID ) ); - } - } - */ - - private abstract class MapCommand : Packet - { - public MapCommand( MapItem map, int command, int number, int x, int y ) : base ( 0x56, 11 ) - { - m_Stream.Write( (int) map.Serial ); - m_Stream.Write( (byte) command ); - m_Stream.Write( (byte) number ); - m_Stream.Write( (short) x ); - m_Stream.Write( (short) y ); - } - } - - private sealed class MapDisplay : MapCommand - { - public MapDisplay( MapItem map ) : base( map, 5, 0, 0, 0 ) - { - } - } - - private sealed class MapAddPin : MapCommand - { - public MapAddPin( MapItem map, Point2D point ) : base( map, 1, 0, point.X, point.Y ) - { - } - } - - private sealed class MapSetEditable : MapCommand - { - public MapSetEditable( MapItem map, bool editable ) : base( map, 7, editable ? 1 : 0, 0, 0 ) - { - } - } - #region ICraftable Members - - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - CraftInit( from ); - return 1; - } - - #endregion - } -} + #endregion + + public virtual void CraftInit(Mobile from) + { + } + + public void SetDisplay(int x1, int y1, int x2, int y2, int w, int h) + { + Width = w; + Height = h; + + if (x1 < 0) + x1 = 0; + + if (y1 < 0) + y1 = 0; + + if (x2 >= 5120) + x2 = 5119; + + if (y2 >= 4096) + y2 = 4095; + + Bounds = new Rectangle2D(x1, y1, x2 - x1, y2 - y1); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + DisplayTo(from); + else + from.SendLocalizedMessage(500446); // That is too far away. + } + + public virtual void DisplayTo(Mobile from) + { + from.Send(new MapDetails(this)); + from.Send(new MapDisplay(this)); + + for (int i = 0; i < Pins.Count; ++i) + from.Send(new MapAddPin(this, Pins[i])); + + from.Send(new MapSetEditable(this, ValidateEdit(from))); + } + + public virtual void OnAddPin(Mobile from, int x, int y) + { + if (!ValidateEdit(from)) + return; + if (Pins.Count >= MaxUserPins) + return; + + Validate(ref x, ref y); + AddPin(x, y); + } + + public virtual void OnRemovePin(Mobile from, int number) + { + if (!ValidateEdit(from)) + return; + + RemovePin(number); + } + + public virtual void OnChangePin(Mobile from, int number, int x, int y) + { + if (!ValidateEdit(from)) + return; + + Validate(ref x, ref y); + ChangePin(number, x, y); + } + + public virtual void OnInsertPin(Mobile from, int number, int x, int y) + { + if (!ValidateEdit(from)) + return; + if (Pins.Count >= MaxUserPins) + return; + + Validate(ref x, ref y); + InsertPin(number, x, y); + } + + public virtual void OnClearPins(Mobile from) + { + if (!ValidateEdit(from)) + return; + + ClearPins(); + } + + public virtual void OnToggleEditable(Mobile from) + { + if (Validate(from)) + m_Editable = !m_Editable; + + from.Send(new MapSetEditable(this, Validate(from) && m_Editable)); + } + + public virtual void Validate(ref int x, ref int y) + { + if (x < 0) + x = 0; + else if (x >= Width) + x = Width - 1; + + if (y < 0) + y = 0; + else if (y >= Height) + y = Height - 1; + } + + public virtual bool ValidateEdit(Mobile from) + { + return m_Editable && Validate(from); + } + + public virtual bool Validate(Mobile from) + { + if (!from.CanSee(this) || from.Map != Map || !from.Alive || InSecureTrade) + return false; + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + if (!Movable || Protected || !from.InRange(GetWorldLocation(), 2)) + return false; + + object root = RootParent; + + if (root is Mobile && root != from) + return false; + + return true; + } + + public void ConvertToWorld(int x, int y, out int worldX, out int worldY) + { + worldX = Bounds.Width * x / Width + Bounds.X; + worldY = Bounds.Height * y / Height + Bounds.Y; + } + + public void ConvertToMap(int x, int y, out int mapX, out int mapY) + { + mapX = (x - Bounds.X) * Width / Bounds.Width; + mapY = (y - Bounds.Y) * Width / Bounds.Height; + } + + public virtual void AddWorldPin(int x, int y) + { + int mapX, mapY; + ConvertToMap(x, y, out mapX, out mapY); + + AddPin(mapX, mapY); + } + + public virtual void AddPin(int x, int y) + { + Pins.Add(new Point2D(x, y)); + } + + public virtual void RemovePin(int index) + { + if (index > 0 && index < Pins.Count) + Pins.RemoveAt(index); + } + + public virtual void InsertPin(int index, int x, int y) + { + if (index < 0 || index >= Pins.Count) + Pins.Add(new Point2D(x, y)); + else + Pins.Insert(index, new Point2D(x, y)); + } + + public virtual void ChangePin(int index, int x, int y) + { + if (index >= 0 && index < Pins.Count) + Pins[index] = new Point2D(x, y); + } + + public virtual void ClearPins() + { + Pins.Clear(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + + writer.Write(Bounds); + + writer.Write(Width); + writer.Write(Height); + + writer.Write(Protected); + + writer.Write(Pins.Count); + for (int i = 0; i < Pins.Count; ++i) + writer.Write(Pins[i]); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Bounds = reader.ReadRect2D(); + + Width = reader.ReadInt(); + Height = reader.ReadInt(); + + Protected = reader.ReadBool(); + + int count = reader.ReadInt(); + for (int i = 0; i < count; i++) + Pins.Add(reader.ReadPoint2D()); + + break; + } + } + } + + public static void Initialize() + { + PacketHandlers.Register(0x56, 11, true, OnMapCommand); + } + + private static void OnMapCommand(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (!(World.FindItem(pvSrc.ReadInt32()) is MapItem map)) + return; + + int command = pvSrc.ReadByte(); + int number = pvSrc.ReadByte(); + + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + + switch (command) + { + case 1: + map.OnAddPin(from, x, y); + break; + case 2: + map.OnInsertPin(from, number, x, y); + break; + case 3: + map.OnChangePin(from, number, x, y); + break; + case 4: + map.OnRemovePin(from, number); + break; + case 5: + map.OnClearPins(from); + break; + case 6: + map.OnToggleEditable(from); + break; + } + } + + private sealed class MapDetails : Packet + { + public MapDetails(MapItem map) : base(0x90, 19) + { + m_Stream.Write(map.Serial); + m_Stream.Write((short)0x139D); + m_Stream.Write((short)map.Bounds.Start.X); + m_Stream.Write((short)map.Bounds.Start.Y); + m_Stream.Write((short)map.Bounds.End.X); + m_Stream.Write((short)map.Bounds.End.Y); + m_Stream.Write((short)map.Width); + m_Stream.Write((short)map.Height); + } + } + + /* + private sealed class MapDetailsNew : Packet + { + public MapDetailsNew( MapItem map ) : base ( 0xF5, 21 ) + { + m_Stream.Write( (int) map.Serial ); + m_Stream.Write( (short) 0x139D ); + m_Stream.Write( (short) map.Bounds.Start.X ); + m_Stream.Write( (short) map.Bounds.Start.Y ); + m_Stream.Write( (short) map.Bounds.End.X ); + m_Stream.Write( (short) map.Bounds.End.Y ); + m_Stream.Write( (short) map.Width ); + m_Stream.Write( (short) map.Height ); + m_Stream.Write( (short) ( map.Facet == null ? 0 : map.Facet.MapID ) ); + } + } + */ + + private abstract class MapCommand : Packet + { + public MapCommand(MapItem map, int command, int number, int x, int y) : base(0x56, 11) + { + m_Stream.Write(map.Serial); + m_Stream.Write((byte)command); + m_Stream.Write((byte)number); + m_Stream.Write((short)x); + m_Stream.Write((short)y); + } + } + + private sealed class MapDisplay : MapCommand + { + public MapDisplay(MapItem map) : base(map, 5, 0, 0, 0) + { + } + } + + private sealed class MapAddPin : MapCommand + { + public MapAddPin(MapItem map, Point2D point) : base(map, 1, 0, point.X, point.Y) + { + } + } + + private sealed class MapSetEditable : MapCommand + { + public MapSetEditable(MapItem map, bool editable) : base(map, 7, editable ? 1 : 0, 0, 0) + { + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/PresetMap.cs b/Scripts/Items/Maps/PresetMap.cs index a580c6c65..9f79db312 100644 --- a/Scripts/Items/Maps/PresetMap.cs +++ b/Scripts/Items/Maps/PresetMap.cs @@ -1,145 +1,145 @@ namespace Server.Items { - public class PresetMap : MapItem - { - private int m_LabelNumber; + public class PresetMap : MapItem + { + private int m_LabelNumber; - [Constructible] - public PresetMap( PresetMapType type ) - { - int v = (int)type; + [Constructible] + public PresetMap(PresetMapType type) + { + int v = (int)type; - if ( v >= 0 && v < PresetMapEntry.Table.Length ) - InitEntry( PresetMapEntry.Table[v] ); - } + if (v >= 0 && v < PresetMapEntry.Table.Length) + InitEntry(PresetMapEntry.Table[v]); + } - public PresetMap( PresetMapEntry entry ) - { - InitEntry( entry ); - } + public PresetMap(PresetMapEntry entry) + { + InitEntry(entry); + } - public void InitEntry( PresetMapEntry entry ) - { - m_LabelNumber = entry.Name; + public PresetMap(Serial serial) : base(serial) + { + } - Width = entry.Width; - Height = entry.Height; + public override int LabelNumber => m_LabelNumber == 0 ? base.LabelNumber : m_LabelNumber; - Bounds = entry.Bounds; - } + public void InitEntry(PresetMapEntry entry) + { + m_LabelNumber = entry.Name; - public override int LabelNumber => (m_LabelNumber == 0 ? base.LabelNumber : m_LabelNumber); + Width = entry.Width; + Height = entry.Height; - public PresetMap( Serial serial ) : base( serial ) - { - } + Bounds = entry.Bounds; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( (int) m_LabelNumber ); - } + writer.Write(m_LabelNumber); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadInt(); - break; - } - } - } - } + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadInt(); + break; + } + } + } + } - public class PresetMapEntry - { - public int Name { get; } + public class PresetMapEntry + { + public PresetMapEntry(int name, int width, int height, int xLeft, int yTop, int xRight, int yBottom) + { + Name = name; + Width = width; + Height = height; + Bounds = new Rectangle2D(xLeft, yTop, xRight - xLeft, yBottom - yTop); + } - public int Width { get; } + public int Name{ get; } - public int Height { get; } + public int Width{ get; } - public Rectangle2D Bounds { get; } + public int Height{ get; } - public PresetMapEntry( int name, int width, int height, int xLeft, int yTop, int xRight, int yBottom ) - { - Name = name; - Width = width; - Height = height; - Bounds = new Rectangle2D( xLeft, yTop, xRight - xLeft, yBottom - yTop ); - } + public Rectangle2D Bounds{ get; } - public static PresetMapEntry[] Table { get; } = - { - new PresetMapEntry( 1041189, 200, 200, 1092, 1396, 1736, 1924 ), // map of Britain - new PresetMapEntry( 1041203, 200, 200, 0256, 1792, 1736, 2560 ), // map of Britain to Skara Brae - new PresetMapEntry( 1041192, 200, 200, 1024, 1280, 2304, 3072 ), // map of Britain to Trinsic - new PresetMapEntry( 1041183, 200, 200, 2500, 1900, 3000, 2400 ), // map of Buccaneer's Den - new PresetMapEntry( 1041198, 200, 200, 2560, 1792, 3840, 2560 ), // map of Buccaneer's Den to Magincia - new PresetMapEntry( 1041194, 200, 200, 2560, 1792, 3840, 3072 ), // map of Buccaneer's Den to Ocllo - new PresetMapEntry( 1041181, 200, 200, 1088, 3572, 1528, 4056 ), // map of Jhelom - new PresetMapEntry( 1041186, 200, 200, 3530, 2022, 3818, 2298 ), // map of Magincia - new PresetMapEntry( 1041199, 200, 200, 3328, 1792, 3840, 2304 ), // map of Magincia to Ocllo - new PresetMapEntry( 1041182, 200, 200, 2360, 0356, 2706, 0702 ), // map of Minoc - new PresetMapEntry( 1041190, 200, 200, 0000, 0256, 2304, 3072 ), // map of Minoc to Yew - new PresetMapEntry( 1041191, 200, 200, 2467, 0572, 2878, 0746 ), // map of Minoc to Vesper - new PresetMapEntry( 1041188, 200, 200, 4156, 0808, 4732, 1528 ), // map of Moonglow - new PresetMapEntry( 1041201, 200, 200, 3328, 0768, 4864, 1536 ), // map of Moonglow to Nujelm - new PresetMapEntry( 1041185, 200, 200, 3446, 1030, 3832, 1424 ), // map of Nujelm - new PresetMapEntry( 1041197, 200, 200, 3328, 1024, 3840, 2304 ), // map of Nujelm to Magincia - new PresetMapEntry( 1041187, 200, 200, 3582, 2456, 3770, 2742 ), // map of Ocllo - new PresetMapEntry( 1041184, 200, 200, 2714, 3329, 3100, 3639 ), // map of Serpent's Hold - new PresetMapEntry( 1041200, 200, 200, 2560, 2560, 3840, 3840 ), // map of Serpent's Hold to Ocllo - new PresetMapEntry( 1041180, 200, 200, 0524, 2064, 0960, 2452 ), // map of Skara Brae - new PresetMapEntry( 1041204, 200, 200, 0000, 0000, 5199, 4095 ), // map of The World - new PresetMapEntry( 1041177, 200, 200, 1792, 2630, 2118, 2952 ), // map of Trinsic - new PresetMapEntry( 1041193, 200, 200, 1792, 1792, 3072, 3072 ), // map of Trinsic to Buccaneer's Den - new PresetMapEntry( 1041195, 200, 200, 0256, 1792, 2304, 4095 ), // map of Trinsic to Jhelom - new PresetMapEntry( 1041178, 200, 200, 2636, 0592, 3064, 1012 ), // map of Vesper - new PresetMapEntry( 1041196, 200, 200, 2636, 0592, 3840, 1536 ), // map of Vesper to Nujelm - new PresetMapEntry( 1041179, 200, 200, 0236, 0741, 0766, 1269 ), // map of Yew - new PresetMapEntry( 1041202, 200, 200, 0000, 0512, 1792, 2048 ) // map of Yew to Britain - }; - } + public static PresetMapEntry[] Table{ get; } = + { + new PresetMapEntry(1041189, 200, 200, 1092, 1396, 1736, 1924), // map of Britain + new PresetMapEntry(1041203, 200, 200, 0256, 1792, 1736, 2560), // map of Britain to Skara Brae + new PresetMapEntry(1041192, 200, 200, 1024, 1280, 2304, 3072), // map of Britain to Trinsic + new PresetMapEntry(1041183, 200, 200, 2500, 1900, 3000, 2400), // map of Buccaneer's Den + new PresetMapEntry(1041198, 200, 200, 2560, 1792, 3840, 2560), // map of Buccaneer's Den to Magincia + new PresetMapEntry(1041194, 200, 200, 2560, 1792, 3840, 3072), // map of Buccaneer's Den to Ocllo + new PresetMapEntry(1041181, 200, 200, 1088, 3572, 1528, 4056), // map of Jhelom + new PresetMapEntry(1041186, 200, 200, 3530, 2022, 3818, 2298), // map of Magincia + new PresetMapEntry(1041199, 200, 200, 3328, 1792, 3840, 2304), // map of Magincia to Ocllo + new PresetMapEntry(1041182, 200, 200, 2360, 0356, 2706, 0702), // map of Minoc + new PresetMapEntry(1041190, 200, 200, 0000, 0256, 2304, 3072), // map of Minoc to Yew + new PresetMapEntry(1041191, 200, 200, 2467, 0572, 2878, 0746), // map of Minoc to Vesper + new PresetMapEntry(1041188, 200, 200, 4156, 0808, 4732, 1528), // map of Moonglow + new PresetMapEntry(1041201, 200, 200, 3328, 0768, 4864, 1536), // map of Moonglow to Nujelm + new PresetMapEntry(1041185, 200, 200, 3446, 1030, 3832, 1424), // map of Nujelm + new PresetMapEntry(1041197, 200, 200, 3328, 1024, 3840, 2304), // map of Nujelm to Magincia + new PresetMapEntry(1041187, 200, 200, 3582, 2456, 3770, 2742), // map of Ocllo + new PresetMapEntry(1041184, 200, 200, 2714, 3329, 3100, 3639), // map of Serpent's Hold + new PresetMapEntry(1041200, 200, 200, 2560, 2560, 3840, 3840), // map of Serpent's Hold to Ocllo + new PresetMapEntry(1041180, 200, 200, 0524, 2064, 0960, 2452), // map of Skara Brae + new PresetMapEntry(1041204, 200, 200, 0000, 0000, 5199, 4095), // map of The World + new PresetMapEntry(1041177, 200, 200, 1792, 2630, 2118, 2952), // map of Trinsic + new PresetMapEntry(1041193, 200, 200, 1792, 1792, 3072, 3072), // map of Trinsic to Buccaneer's Den + new PresetMapEntry(1041195, 200, 200, 0256, 1792, 2304, 4095), // map of Trinsic to Jhelom + new PresetMapEntry(1041178, 200, 200, 2636, 0592, 3064, 1012), // map of Vesper + new PresetMapEntry(1041196, 200, 200, 2636, 0592, 3840, 1536), // map of Vesper to Nujelm + new PresetMapEntry(1041179, 200, 200, 0236, 0741, 0766, 1269), // map of Yew + new PresetMapEntry(1041202, 200, 200, 0000, 0512, 1792, 2048) // map of Yew to Britain + }; + } - public enum PresetMapType - { - Britain, - BritainToSkaraBrae, - BritainToTrinsic, - BucsDen, - BucsDenToMagincia, - BucsDenToOcllo, - Jhelom, - Magincia, - MaginciaToOcllo, - Minoc, - MinocToYew, - MinocToVesper, - Moonglow, - MoonglowToNujelm, - Nujelm, - NujelmToMagincia, - Ocllo, - SerpentsHold, - SerpentsHoldToOcllo, - SkaraBrae, - TheWorld, - Trinsic, - TrinsicToBucsDen, - TrinsicToJhelom, - Vesper, - VesperToNujelm, - Yew, - YewToBritain - } -} + public enum PresetMapType + { + Britain, + BritainToSkaraBrae, + BritainToTrinsic, + BucsDen, + BucsDenToMagincia, + BucsDenToOcllo, + Jhelom, + Magincia, + MaginciaToOcllo, + Minoc, + MinocToYew, + MinocToVesper, + Moonglow, + MoonglowToNujelm, + Nujelm, + NujelmToMagincia, + Ocllo, + SerpentsHold, + SerpentsHoldToOcllo, + SkaraBrae, + TheWorld, + Trinsic, + TrinsicToBucsDen, + TrinsicToJhelom, + Vesper, + VesperToNujelm, + Yew, + YewToBritain + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/SeaChart.cs b/Scripts/Items/Maps/SeaChart.cs index 73818526b..bda8ae3f2 100644 --- a/Scripts/Items/Maps/SeaChart.cs +++ b/Scripts/Items/Maps/SeaChart.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class SeaChart : MapItem - { - [Constructible] - public SeaChart() - { - SetDisplay( 0, 0, 5119, 4095, 400, 400 ); - } + public class SeaChart : MapItem + { + [Constructible] + public SeaChart() + { + SetDisplay(0, 0, 5119, 4095, 400, 400); + } - public override void CraftInit( Mobile from ) - { - double skillValue = from.Skills[SkillName.Cartography].Value; - int dist = 64 + (int)(skillValue * 10); + public SeaChart(Serial serial) : base(serial) + { + } - if ( dist < 200 ) - dist = 200; + public override int LabelNumber => 1015232; // sea chart - int size = 24 + (int)(skillValue * 3.3); + public override void CraftInit(Mobile from) + { + double skillValue = from.Skills[SkillName.Cartography].Value; + int dist = 64 + (int)(skillValue * 10); - if ( size < 200 ) - size = 200; - else if ( size > 400 ) - size = 400; + if (dist < 200) + dist = 200; - SetDisplay( from.X - dist, from.Y - dist, from.X + dist, from.Y + dist, size, size ); - } + int size = 24 + (int)(skillValue * 3.3); - public override int LabelNumber => 1015232; // sea chart + if (size < 200) + size = 200; + else if (size > 400) + size = 400; - public SeaChart( Serial serial ) : base( serial ) - { - } + SetDisplay(from.X - dist, from.Y - dist, from.X + dist, from.Y + dist, size, size); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/TreasureMap.cs b/Scripts/Items/Maps/TreasureMap.cs index 3aca23d0b..b33610756 100644 --- a/Scripts/Items/Maps/TreasureMap.cs +++ b/Scripts/Items/Maps/TreasureMap.cs @@ -1,933 +1,986 @@ using System; -using System.IO; using System.Collections.Generic; +using System.IO; +using Server.ContextMenus; +using Server.Engines.Harvest; using Server.Mobiles; using Server.Network; using Server.Targeting; -using Server.ContextMenus; namespace Server.Items { - public class TreasureMap : MapItem - { - private int m_Level; - private bool m_Completed; - private Mobile m_CompletedBy; - private Mobile m_Decoder; - private Map m_Map; - - [CommandProperty( AccessLevel.GameMaster )] - public int Level{ get => m_Level; - set{ m_Level = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Completed{ get => m_Completed; - set{ m_Completed = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile CompletedBy{ get => m_CompletedBy; - set{ m_CompletedBy = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Decoder{ get => m_Decoder; - set{ m_Decoder = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public Map ChestMap{ get => m_Map; - set{ m_Map = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public Point2D ChestLocation { get; set; } - - private static Point2D[] m_Locations; - private static Point2D[] m_HavenLocations; - - private static Type[][] m_SpawnTypes = { - new[]{ typeof( HeadlessOne ), typeof( Skeleton ) }, - new[]{ typeof( Mongbat ), typeof( Ratman ), typeof( HeadlessOne ), typeof( Skeleton ), typeof( Zombie ) }, - new[]{ typeof( OrcishMage ), typeof( Gargoyle ), typeof( Gazer ), typeof( HellHound ), typeof( EarthElemental ) }, - new[]{ typeof( Lich ), typeof( OgreLord ), typeof( DreadSpider ), typeof( AirElemental ), typeof( FireElemental ) }, - new[]{ typeof( DreadSpider ), typeof( LichLord ), typeof( Daemon ), typeof( ElderGazer ), typeof( OgreLord ) }, - new[]{ typeof( LichLord ), typeof( Daemon ), typeof( ElderGazer ), typeof( PoisonElemental ), typeof( BloodElemental ) }, - new[]{ typeof( AncientWyrm ), typeof( Balron ), typeof( BloodElemental ), typeof( PoisonElemental ), typeof( Titan ) } - }; - - public const double LootChance = 0.01; // 1% chance to appear as loot - - public static Point2D GetRandomLocation() - { - if ( m_Locations == null ) - LoadLocations(); - - if ( m_Locations.Length > 0 ) - return m_Locations[Utility.Random( m_Locations.Length )]; - - return Point2D.Zero; - } - - public static Point2D GetRandomHavenLocation() - { - if ( m_HavenLocations == null ) - LoadLocations(); - - if ( m_HavenLocations.Length > 0 ) - return m_HavenLocations[Utility.Random( m_HavenLocations.Length )]; - - return Point2D.Zero; - } - - private static void LoadLocations() - { - string filePath = Path.Combine( Core.BaseDirectory, "Data/treasure.cfg" ); - - List list = new List(); - List havenList = new List(); - - if ( File.Exists( filePath ) ) - { - using ( StreamReader ip = new StreamReader( filePath ) ) - { - string line; - - while ( (line = ip.ReadLine()) != null ) - { - try - { - string[] split = line.Split( ' ' ); - - int x = Convert.ToInt32( split[0] ), y = Convert.ToInt32( split[1] ); - - Point2D loc = new Point2D( x, y ); - list.Add( loc ); - - if ( IsInHavenIsland( loc ) ) - havenList.Add( loc ); - } - catch - { - } - } - } - } - - m_Locations = list.ToArray(); - m_HavenLocations = havenList.ToArray(); - } - - public static bool IsInHavenIsland( IPoint2D loc ) - { - return ( loc.X >= 3314 && loc.X <= 3814 && loc.Y >= 2345 && loc.Y <= 3095 ); - } - - public static BaseCreature Spawn( int level, Point3D p, bool guardian ) - { - if ( level >= 0 && level < m_SpawnTypes.Length ) - { - BaseCreature bc; - - try - { - bc = (BaseCreature)Activator.CreateInstance( m_SpawnTypes[level][Utility.Random( m_SpawnTypes[level].Length )] ); - } - catch - { - return null; - } - - bc.Home = p; - bc.RangeHome = 5; - - if ( guardian && level == 0 ) - { - bc.Name = "a chest guardian"; - bc.Hue = 0x835; - } - - return bc; - } - - return null; - } - - public static BaseCreature Spawn( int level, Point3D p, Map map, Mobile target, bool guardian ) - { - if ( map == null ) - return null; - - BaseCreature c = Spawn( level, p, guardian ); - - if ( c != null ) - { - bool spawned = false; - - for ( int i = 0; !spawned && i < 10; ++i ) - { - int x = p.X - 3 + Utility.Random( 7 ); - int y = p.Y - 3 + Utility.Random( 7 ); - - if ( map.CanSpawnMobile( x, y, p.Z ) ) - { - c.MoveToWorld( new Point3D( x, y, p.Z ), map ); - spawned = true; - } - else - { - int z = map.GetAverageZ( x, y ); - - if ( map.CanSpawnMobile( x, y, z ) ) - { - c.MoveToWorld( new Point3D( x, y, z ), map ); - spawned = true; - } - } - } - - if ( !spawned ) - { - c.Delete(); - return null; - } - - if ( target != null ) - c.Combatant = target; - - return c; - } - - return null; - } - - [Constructible] - public TreasureMap( int level, Map map ) - { - m_Level = level; - m_Map = map; - - if ( level == 0 ) - ChestLocation = GetRandomHavenLocation(); - else - ChestLocation = GetRandomLocation(); - - Width = 300; - Height = 300; - - int width = 600; - int height = 600; - - int x1 = ChestLocation.X - Utility.RandomMinMax( width / 4, (width / 4) * 3 ); - int y1 = ChestLocation.Y - Utility.RandomMinMax( height / 4, (height / 4) * 3 ); - - if ( x1 < 0 ) - x1 = 0; - - if ( y1 < 0 ) - y1 = 0; - - int x2 = x1 + width; - int y2 = y1 + height; - - if ( x2 >= 5120 ) - x2 = 5119; - - if ( y2 >= 4096 ) - y2 = 4095; - - x1 = x2 - width; - y1 = y2 - height; - - Bounds = new Rectangle2D( x1, y1, width, height ); - Protected = true; - - AddWorldPin( ChestLocation.X, ChestLocation.Y ); - } - - public TreasureMap( Serial serial ) : base( serial ) - { - } - - public static bool HasDiggingTool( Mobile m ) - { - if ( m.Backpack == null ) - return false; - - List items = m.Backpack.FindItemsByType(); - - foreach ( BaseHarvestTool tool in items ) - { - if ( tool.HarvestSystem == Engines.Harvest.Mining.System ) - return true; - } - - return false; - } - - public void OnBeginDig( Mobile from ) - { - if ( m_Completed ) - { - from.SendLocalizedMessage( 503028 ); // The treasure for this map has already been found. - } - else if ( m_Level == 0 && !CheckYoung( from ) ) - { - from.SendLocalizedMessage( 1046447 ); // Only a young player may use this treasure map. - } - /* - else if ( from != m_Decoder ) - { - from.SendLocalizedMessage( 503016 ); // Only the person who decoded this map may actually dig up the treasure. - } - */ - else if ( m_Decoder != from && !HasRequiredSkill( from ) ) - { - from.SendLocalizedMessage( 503031 ); // You did not decode this map and have no clue where to look for the treasure. - } - else if ( !from.CanBeginAction( typeof( TreasureMap ) ) ) - { - from.SendLocalizedMessage( 503020 ); // You are already digging treasure. - } - else if ( from.Map != m_Map ) - { - from.SendLocalizedMessage( 1010479 ); // You seem to be in the right place, but may be on the wrong facet! - } - else - { - from.SendLocalizedMessage( 503033 ); // Where do you wish to dig? - from.Target = new DigTarget( this ); - } - } - - private class DigTarget : Target - { - private TreasureMap m_Map; - - public DigTarget( TreasureMap map ) : base( 6, true, TargetFlags.None ) - { - m_Map = map; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Map.Deleted ) - return; - - Map map = m_Map.m_Map; - - if ( m_Map.m_Completed ) - { - from.SendLocalizedMessage( 503028 ); // The treasure for this map has already been found. - } - /* - else if ( from != m_Map.m_Decoder ) - { - from.SendLocalizedMessage( 503016 ); // Only the person who decoded this map may actually dig up the treasure. - } - */ - else if ( m_Map.m_Decoder != from && !m_Map.HasRequiredSkill( from ) ) - { - from.SendLocalizedMessage( 503031 ); // You did not decode this map and have no clue where to look for the treasure. - } - else if ( !from.CanBeginAction( typeof( TreasureMap ) ) ) - { - from.SendLocalizedMessage( 503020 ); // You are already digging treasure. - } - else if ( !HasDiggingTool( from ) ) - { - from.SendMessage( "You must have a digging tool to dig for treasure." ); - } - else if ( from.Map != map ) - { - from.SendLocalizedMessage( 1010479 ); // You seem to be in the right place, but may be on the wrong facet! - } - else - { - IPoint3D p = targeted as IPoint3D; - - Point3D targ3D = (p as Item)?.GetWorldLocation() ?? new Point3D(p); - - int maxRange; - double skillValue = from.Skills[SkillName.Mining].Value; - - if ( skillValue >= 100.0 ) - maxRange = 4; - else if ( skillValue >= 81.0 ) - maxRange = 3; - else if ( skillValue >= 51.0 ) - maxRange = 2; - else - maxRange = 1; - - Point2D loc = m_Map.ChestLocation; - int x = loc.X, y = loc.Y; - - Point3D chest3D0 = new Point3D( loc, 0 ); - - if ( Utility.InRange( targ3D, chest3D0, maxRange ) ) - { - if ( from.Location.X == x && from.Location.Y == y ) - { - from.SendLocalizedMessage( 503030 ); // The chest can't be dug up because you are standing on top of it. - } - else if ( map != null ) - { - int z = map.GetAverageZ( x, y ); - - if ( !map.CanFit( x, y, z, 16, true, true ) ) - { - from.SendLocalizedMessage( 503021 ); // You have found the treasure chest but something is keeping it from being dug up. - } - else if ( from.BeginAction( typeof( TreasureMap ) ) ) - { - new DigTimer( from, m_Map, new Point3D( x, y, z ), map ).Start(); - } - else - { - from.SendLocalizedMessage( 503020 ); // You are already digging treasure. - } - } - } - else if ( m_Map.Level > 0 ) - { - if ( Utility.InRange( targ3D, chest3D0, 8 ) ) // We're close, but not quite - { - from.SendLocalizedMessage( 503032 ); // You dig and dig but no treasure seems to be here. - } - else - { - from.SendLocalizedMessage( 503035 ); // You dig and dig but fail to find any treasure. - } - } - else - { - if ( Utility.InRange( targ3D, chest3D0, 8 ) ) // We're close, but not quite - { - from.SendAsciiMessage( 0x44, "The treasure chest is very close!" ); - } - else - { - Direction dir = Utility.GetDirection( targ3D, chest3D0 ); - - string sDir; - switch ( dir ) - { - case Direction.North: sDir = "north"; break; - case Direction.Right: sDir = "northeast"; break; - case Direction.East: sDir = "east"; break; - case Direction.Down: sDir = "southeast"; break; - case Direction.South: sDir = "south"; break; - case Direction.Left: sDir = "southwest"; break; - case Direction.West: sDir = "west"; break; - default: sDir = "northwest"; break; - } - - from.SendAsciiMessage( 0x44, "Try looking for the treasure chest more to the {0}.", sDir ); - } - } - } - } - } - - private class DigTimer : Timer - { - private Mobile m_From; - private TreasureMap m_TreasureMap; - - private Point3D m_Location; - private Map m_Map; - - private TreasureChestDirt m_Dirt1; - private TreasureChestDirt m_Dirt2; - private TreasureMapChest m_Chest; - - private int m_Count; - - private long m_NextSkillTime; - private long m_NextSpellTime; - private long m_NextActionTime; - private long m_LastMoveTime; - - public DigTimer( Mobile from, TreasureMap treasureMap, Point3D location, Map map ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ) ) - { - m_From = from; - m_TreasureMap = treasureMap; - - m_Location = location; - m_Map = map; - - m_NextSkillTime = from.NextSkillTime; - m_NextSpellTime = from.NextSpellTime; - m_NextActionTime = from.NextActionTime; - m_LastMoveTime = from.LastMoveTime; - - Priority = TimerPriority.TenMS; - } - - private void Terminate() - { - Stop(); - m_From.EndAction( typeof( TreasureMap ) ); - - m_Chest?.Delete(); - - if ( m_Dirt1 != null ) - { - m_Dirt1.Delete(); - m_Dirt2.Delete(); - } - } - - protected override void OnTick() - { - if ( m_NextSkillTime != m_From.NextSkillTime || m_NextSpellTime != m_From.NextSpellTime || m_NextActionTime != m_From.NextActionTime ) - { - Terminate(); - return; - } - - if ( m_LastMoveTime != m_From.LastMoveTime ) - { - m_From.SendLocalizedMessage( 503023 ); // You cannot move around while digging up treasure. You will need to start digging anew. - Terminate(); - return; - } - - int z = ( m_Chest != null ) ? m_Chest.Z + m_Chest.ItemData.Height : int.MinValue; - int height = 16; - - if ( z > m_Location.Z ) - height -= ( z - m_Location.Z ); - else - z = m_Location.Z; - - if ( !m_Map.CanFit( m_Location.X, m_Location.Y, z, height, true, true, false ) ) - { - m_From.SendLocalizedMessage( 503024 ); // You stop digging because something is directly on top of the treasure chest. - Terminate(); - return; - } - - m_Count++; - - m_From.RevealingAction(); - m_From.Direction = m_From.GetDirectionTo( m_Location ); - - if ( m_Count > 1 && m_Dirt1 == null ) - { - m_Dirt1 = new TreasureChestDirt(); - m_Dirt1.MoveToWorld( m_Location, m_Map ); - - m_Dirt2 = new TreasureChestDirt(); - m_Dirt2.MoveToWorld( new Point3D( m_Location.X, m_Location.Y - 1, m_Location.Z ), m_Map ); - } - - if ( m_Count == 5 ) - { - m_Dirt1.Turn1(); - } - else if ( m_Count == 10 ) - { - m_Dirt1.Turn2(); - m_Dirt2.Turn2(); - } - else if ( m_Count > 10 ) - { - if ( m_Chest == null ) - { - m_Chest = new TreasureMapChest( m_From, m_TreasureMap.Level, true ); - m_Chest.MoveToWorld( new Point3D( m_Location.X, m_Location.Y, m_Location.Z - 15 ), m_Map ); - } - else - { - m_Chest.Z++; - } - - Effects.PlaySound( m_Chest, m_Map, 0x33B ); - } - - if ( m_Chest != null && m_Chest.Location.Z >= m_Location.Z ) - { - Stop(); - m_From.EndAction( typeof( TreasureMap ) ); - - m_Chest.Temporary = false; - m_TreasureMap.Completed = true; - m_TreasureMap.CompletedBy = m_From; - - int spawns; - switch ( m_TreasureMap.Level ) - { - case 0: spawns = 3; break; - case 1: spawns = 0; break; - default: spawns = 4; break; - } - - for ( int i = 0; i < spawns; ++i ) - { - BaseCreature bc = Spawn( m_TreasureMap.Level, m_Chest.Location, m_Chest.Map, null, true ); - - if ( bc != null ) - m_Chest.Guardians.Add( bc ); - } - } - else - { - if ( m_From.Body.IsHuman && !m_From.Mounted ) - m_From.Animate( 11, 5, 1, true, false, 0 ); - - new SoundTimer( m_From, 0x125 + (m_Count % 2) ).Start(); - } - } - - private class SoundTimer : Timer - { - private Mobile m_From; - private int m_SoundID; - - public SoundTimer( Mobile from, int soundID ) : base( TimeSpan.FromSeconds( 0.9 ) ) - { - m_From = from; - m_SoundID = soundID; - - Priority = TimerPriority.TenMS; - } - - protected override void OnTick() - { - m_From.PlaySound( m_SoundID ); - } - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - if ( !m_Completed && m_Decoder == null ) - Decode( from ); - else - DisplayTo( from ); - } - - private bool CheckYoung( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - - if ( from is PlayerMobile mobile && mobile.Young ) - return true; - - if ( from == Decoder ) - { - Level = 1; - from.SendLocalizedMessage( 1046446 ); // This is now a level one treasure map. - return true; - } - - return false; - } - - private double GetMinSkillLevel() - { - switch ( m_Level ) - { - case 1: return -3.0; - case 2: return 41.0; - case 3: return 51.0; - case 4: return 61.0; - case 5: return 70.0; - case 6: return 70.0; - - default: return 0.0; - } - } - - private bool HasRequiredSkill( Mobile from ) - { - return ( from.Skills[SkillName.Cartography].Value >= GetMinSkillLevel() ); - } - - public void Decode( Mobile from ) - { - if ( m_Completed || m_Decoder != null ) - return; - - if ( m_Level == 0 ) - { - if ( !CheckYoung( from ) ) - { - from.SendLocalizedMessage( 1046447 ); // Only a young player may use this treasure map. - return; - } - } - else - { - double minSkill = GetMinSkillLevel(); - - if ( from.Skills[SkillName.Cartography].Value < minSkill ) - from.SendLocalizedMessage( 503013 ); // The map is too difficult to attempt to decode. - - double maxSkill = minSkill + 60.0; - - if ( !from.CheckSkill( SkillName.Cartography, minSkill, maxSkill ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 503018 ); // You fail to make anything of the map. - return; - } - } - - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 503019 ); // You successfully decode a treasure map! - Decoder = from; - - if ( Core.AOS ) - LootType = LootType.Blessed; - - DisplayTo( from ); - } - - public override void DisplayTo( Mobile from ) - { - if ( m_Completed ) - { - SendLocalizedMessageTo( from, 503014 ); // This treasure hunt has already been completed. - } - else if ( m_Level == 0 && !CheckYoung( from ) ) - { - from.SendLocalizedMessage( 1046447 ); // Only a young player may use this treasure map. - return; - } - else if ( m_Decoder != from && !HasRequiredSkill( from ) ) - { - from.SendLocalizedMessage( 503031 ); // You did not decode this map and have no clue where to look for the treasure. - return; - } - else - { - SendLocalizedMessageTo( from, 503017 ); // The treasure is marked by the red pin. Grab a shovel and go dig it up! - } - - from.PlaySound( 0x249 ); - base.DisplayTo( from ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( !m_Completed ) - { - if ( m_Decoder == null ) - { - list.Add( new DecodeMapEntry( this ) ); - } - else - { - bool digTool = HasDiggingTool( from ); - - list.Add( new OpenMapEntry( this ) ); - list.Add( new DigEntry( this, digTool ) ); - } - } - } - - private class DecodeMapEntry : ContextMenuEntry - { - private TreasureMap m_Map; - - public DecodeMapEntry( TreasureMap map ) : base( 6147, 2 ) - { - m_Map = map; - } - - public override void OnClick() - { - if ( !m_Map.Deleted ) - m_Map.Decode( Owner.From ); - } - } - - private class OpenMapEntry : ContextMenuEntry - { - private TreasureMap m_Map; - - public OpenMapEntry( TreasureMap map ) : base( 6150, 2 ) - { - m_Map = map; - } - - public override void OnClick() - { - if ( !m_Map.Deleted ) - m_Map.DisplayTo( Owner.From ); - } - } - - private class DigEntry : ContextMenuEntry - { - private TreasureMap m_Map; - - public DigEntry( TreasureMap map, bool enabled ) : base( 6148, 2 ) - { - m_Map = map; - - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } - - public override void OnClick() - { - if ( m_Map.Deleted ) - return; - - Mobile from = Owner.From; - - if ( HasDiggingTool( from ) ) - m_Map.OnBeginDig( from ); - else - from.SendMessage( "You must have a digging tool to dig for treasure." ); - } - } - - public override int LabelNumber - { - get - { - if ( m_Decoder != null ) - { - if ( m_Level == 6 ) - return 1063453; - return 1041516 + m_Level; - } - - if ( m_Level == 6 ) - return 1063452; - return 1041510 + m_Level; - } - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - list.Add( m_Map == Map.Felucca ? 1041502 : 1041503 ); // for somewhere in Felucca : for somewhere in Trammel - - if ( m_Completed ) - { - list.Add( 1041507, m_CompletedBy == null ? "someone" : m_CompletedBy.Name ); // completed by ~1_val~ - } - } - - public override void OnSingleClick( Mobile from ) - { - if ( m_Completed ) - { - from.Send( new MessageLocalizedAffix( Serial, ItemID, MessageType.Label, 0x3B2, 3, 1048030, "", AffixType.Append, - $" completed by {(m_CompletedBy == null ? "someone" : m_CompletedBy.Name)}", "" ) ); - } - else if ( m_Decoder != null ) - { - if ( m_Level == 6 ) - LabelTo( from, 1063453 ); - else - LabelTo( from, 1041516 + m_Level ); - } - else - { - if ( m_Level == 6 ) - LabelTo( from, 1041522, $"#{1063452}\t \t#{(m_Map == Map.Felucca ? 1041502 : 1041503)}"); - else - LabelTo( from, 1041522, $"#{1041510 + m_Level}\t \t#{(m_Map == Map.Felucca ? 1041502 : 1041503)}"); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); - - writer.Write( (Mobile) m_CompletedBy ); - - writer.Write( m_Level ); - writer.Write( m_Completed ); - writer.Write( m_Decoder ); - writer.Write( m_Map ); - writer.Write( ChestLocation ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_CompletedBy = reader.ReadMobile(); - - goto case 0; - } - case 0: - { - m_Level = (int)reader.ReadInt(); - m_Completed = reader.ReadBool(); - m_Decoder = reader.ReadMobile(); - m_Map = reader.ReadMap(); - ChestLocation = reader.ReadPoint2D(); - - if ( version == 0 && m_Completed ) - m_CompletedBy = m_Decoder; - - break; - } - } - - if ( Core.AOS && m_Decoder != null && LootType == LootType.Regular) - LootType = LootType.Blessed; - } - } - - public class TreasureChestDirt : Item - { - public TreasureChestDirt() : base( 0x912 ) - { - Movable = false; - - Timer.DelayCall( TimeSpan.FromMinutes( 2.0 ), Delete ); - } - - public TreasureChestDirt( Serial serial ) : base( serial ) - { - } - - public void Turn1() - { - ItemID = 0x913; - } - - public void Turn2() - { - ItemID = 0x914; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - Delete(); - } - } -} + public class TreasureMap : MapItem + { + public const double LootChance = 0.01; // 1% chance to appear as loot + + private static Point2D[] m_Locations; + private static Point2D[] m_HavenLocations; + + private static Type[][] m_SpawnTypes = + { + new[] { typeof(HeadlessOne), typeof(Skeleton) }, + new[] { typeof(Mongbat), typeof(Ratman), typeof(HeadlessOne), typeof(Skeleton), typeof(Zombie) }, + new[] { typeof(OrcishMage), typeof(Gargoyle), typeof(Gazer), typeof(HellHound), typeof(EarthElemental) }, + new[] { typeof(Lich), typeof(OgreLord), typeof(DreadSpider), typeof(AirElemental), typeof(FireElemental) }, + new[] { typeof(DreadSpider), typeof(LichLord), typeof(Daemon), typeof(ElderGazer), typeof(OgreLord) }, + new[] { typeof(LichLord), typeof(Daemon), typeof(ElderGazer), typeof(PoisonElemental), typeof(BloodElemental) }, + new[] { typeof(AncientWyrm), typeof(Balron), typeof(BloodElemental), typeof(PoisonElemental), typeof(Titan) } + }; + + private bool m_Completed; + private Mobile m_CompletedBy; + private Mobile m_Decoder; + private int m_Level; + private Map m_Map; + + [Constructible] + public TreasureMap(int level, Map map) + { + m_Level = level; + m_Map = map; + + if (level == 0) + ChestLocation = GetRandomHavenLocation(); + else + ChestLocation = GetRandomLocation(); + + Width = 300; + Height = 300; + + int width = 600; + int height = 600; + + int x1 = ChestLocation.X - Utility.RandomMinMax(width / 4, width / 4 * 3); + int y1 = ChestLocation.Y - Utility.RandomMinMax(height / 4, height / 4 * 3); + + if (x1 < 0) + x1 = 0; + + if (y1 < 0) + y1 = 0; + + int x2 = x1 + width; + int y2 = y1 + height; + + if (x2 >= 5120) + x2 = 5119; + + if (y2 >= 4096) + y2 = 4095; + + x1 = x2 - width; + y1 = y2 - height; + + Bounds = new Rectangle2D(x1, y1, width, height); + Protected = true; + + AddWorldPin(ChestLocation.X, ChestLocation.Y); + } + + public TreasureMap(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Level + { + get => m_Level; + set + { + m_Level = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Completed + { + get => m_Completed; + set + { + m_Completed = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile CompletedBy + { + get => m_CompletedBy; + set + { + m_CompletedBy = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Decoder + { + get => m_Decoder; + set + { + m_Decoder = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Map ChestMap + { + get => m_Map; + set + { + m_Map = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point2D ChestLocation{ get; set; } + + public override int LabelNumber + { + get + { + if (m_Decoder != null) + { + if (m_Level == 6) + return 1063453; + return 1041516 + m_Level; + } + + if (m_Level == 6) + return 1063452; + return 1041510 + m_Level; + } + } + + public static Point2D GetRandomLocation() + { + if (m_Locations == null) + LoadLocations(); + + if (m_Locations.Length > 0) + return m_Locations[Utility.Random(m_Locations.Length)]; + + return Point2D.Zero; + } + + public static Point2D GetRandomHavenLocation() + { + if (m_HavenLocations == null) + LoadLocations(); + + if (m_HavenLocations.Length > 0) + return m_HavenLocations[Utility.Random(m_HavenLocations.Length)]; + + return Point2D.Zero; + } + + private static void LoadLocations() + { + string filePath = Path.Combine(Core.BaseDirectory, "Data/treasure.cfg"); + + List list = new List(); + List havenList = new List(); + + if (File.Exists(filePath)) + using (StreamReader ip = new StreamReader(filePath)) + { + string line; + + while ((line = ip.ReadLine()) != null) + try + { + string[] split = line.Split(' '); + + int x = Convert.ToInt32(split[0]), y = Convert.ToInt32(split[1]); + + Point2D loc = new Point2D(x, y); + list.Add(loc); + + if (IsInHavenIsland(loc)) + havenList.Add(loc); + } + catch + { + } + } + + m_Locations = list.ToArray(); + m_HavenLocations = havenList.ToArray(); + } + + public static bool IsInHavenIsland(IPoint2D loc) + { + return loc.X >= 3314 && loc.X <= 3814 && loc.Y >= 2345 && loc.Y <= 3095; + } + + public static BaseCreature Spawn(int level, Point3D p, bool guardian) + { + if (level >= 0 && level < m_SpawnTypes.Length) + { + BaseCreature bc; + + try + { + bc = (BaseCreature)Activator.CreateInstance( + m_SpawnTypes[level][Utility.Random(m_SpawnTypes[level].Length)]); + } + catch + { + return null; + } + + bc.Home = p; + bc.RangeHome = 5; + + if (guardian && level == 0) + { + bc.Name = "a chest guardian"; + bc.Hue = 0x835; + } + + return bc; + } + + return null; + } + + public static BaseCreature Spawn(int level, Point3D p, Map map, Mobile target, bool guardian) + { + if (map == null) + return null; + + BaseCreature c = Spawn(level, p, guardian); + + if (c != null) + { + bool spawned = false; + + for (int i = 0; !spawned && i < 10; ++i) + { + int x = p.X - 3 + Utility.Random(7); + int y = p.Y - 3 + Utility.Random(7); + + if (map.CanSpawnMobile(x, y, p.Z)) + { + c.MoveToWorld(new Point3D(x, y, p.Z), map); + spawned = true; + } + else + { + int z = map.GetAverageZ(x, y); + + if (map.CanSpawnMobile(x, y, z)) + { + c.MoveToWorld(new Point3D(x, y, z), map); + spawned = true; + } + } + } + + if (!spawned) + { + c.Delete(); + return null; + } + + if (target != null) + c.Combatant = target; + + return c; + } + + return null; + } + + public static bool HasDiggingTool(Mobile m) + { + if (m.Backpack == null) + return false; + + List items = m.Backpack.FindItemsByType(); + + foreach (BaseHarvestTool tool in items) + if (tool.HarvestSystem == Mining.System) + return true; + + return false; + } + + public void OnBeginDig(Mobile from) + { + if (m_Completed) + { + from.SendLocalizedMessage(503028); // The treasure for this map has already been found. + } + else if (m_Level == 0 && !CheckYoung(from)) + { + from.SendLocalizedMessage(1046447); // Only a young player may use this treasure map. + } + /* + else if ( from != m_Decoder ) + { + from.SendLocalizedMessage( 503016 ); // Only the person who decoded this map may actually dig up the treasure. + } + */ + else if (m_Decoder != from && !HasRequiredSkill(from)) + { + from.SendLocalizedMessage( + 503031); // You did not decode this map and have no clue where to look for the treasure. + } + else if (!from.CanBeginAction(typeof(TreasureMap))) + { + from.SendLocalizedMessage(503020); // You are already digging treasure. + } + else if (from.Map != m_Map) + { + from.SendLocalizedMessage(1010479); // You seem to be in the right place, but may be on the wrong facet! + } + else + { + from.SendLocalizedMessage(503033); // Where do you wish to dig? + from.Target = new DigTarget(this); + } + } + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + if (!m_Completed && m_Decoder == null) + Decode(from); + else + DisplayTo(from); + } + + private bool CheckYoung(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + + if (from is PlayerMobile mobile && mobile.Young) + return true; + + if (from == Decoder) + { + Level = 1; + from.SendLocalizedMessage(1046446); // This is now a level one treasure map. + return true; + } + + return false; + } + + private double GetMinSkillLevel() + { + switch (m_Level) + { + case 1: return -3.0; + case 2: return 41.0; + case 3: return 51.0; + case 4: return 61.0; + case 5: return 70.0; + case 6: return 70.0; + + default: return 0.0; + } + } + + private bool HasRequiredSkill(Mobile from) + { + return from.Skills[SkillName.Cartography].Value >= GetMinSkillLevel(); + } + + public void Decode(Mobile from) + { + if (m_Completed || m_Decoder != null) + return; + + if (m_Level == 0) + { + if (!CheckYoung(from)) + { + from.SendLocalizedMessage(1046447); // Only a young player may use this treasure map. + return; + } + } + else + { + double minSkill = GetMinSkillLevel(); + + if (from.Skills[SkillName.Cartography].Value < minSkill) + from.SendLocalizedMessage(503013); // The map is too difficult to attempt to decode. + + double maxSkill = minSkill + 60.0; + + if (!from.CheckSkill(SkillName.Cartography, minSkill, maxSkill)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 503018); // You fail to make anything of the map. + return; + } + } + + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 503019); // You successfully decode a treasure map! + Decoder = from; + + if (Core.AOS) + LootType = LootType.Blessed; + + DisplayTo(from); + } + + public override void DisplayTo(Mobile from) + { + if (m_Completed) + { + SendLocalizedMessageTo(from, 503014); // This treasure hunt has already been completed. + } + else if (m_Level == 0 && !CheckYoung(from)) + { + from.SendLocalizedMessage(1046447); // Only a young player may use this treasure map. + return; + } + else if (m_Decoder != from && !HasRequiredSkill(from)) + { + from.SendLocalizedMessage( + 503031); // You did not decode this map and have no clue where to look for the treasure. + return; + } + else + { + SendLocalizedMessageTo(from, + 503017); // The treasure is marked by the red pin. Grab a shovel and go dig it up! + } + + from.PlaySound(0x249); + base.DisplayTo(from); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (!m_Completed) + { + if (m_Decoder == null) + { + list.Add(new DecodeMapEntry(this)); + } + else + { + bool digTool = HasDiggingTool(from); + + list.Add(new OpenMapEntry(this)); + list.Add(new DigEntry(this, digTool)); + } + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(m_Map == Map.Felucca ? 1041502 : 1041503); // for somewhere in Felucca : for somewhere in Trammel + + if (m_Completed) + list.Add(1041507, m_CompletedBy == null ? "someone" : m_CompletedBy.Name); // completed by ~1_val~ + } + + public override void OnSingleClick(Mobile from) + { + if (m_Completed) + { + from.Send(new MessageLocalizedAffix(Serial, ItemID, MessageType.Label, 0x3B2, 3, 1048030, "", + AffixType.Append, + $" completed by {(m_CompletedBy == null ? "someone" : m_CompletedBy.Name)}", "")); + } + else if (m_Decoder != null) + { + if (m_Level == 6) + LabelTo(from, 1063453); + else + LabelTo(from, 1041516 + m_Level); + } + else + { + if (m_Level == 6) + LabelTo(from, 1041522, $"#{1063452}\t \t#{(m_Map == Map.Felucca ? 1041502 : 1041503)}"); + else + LabelTo(from, 1041522, $"#{1041510 + m_Level}\t \t#{(m_Map == Map.Felucca ? 1041502 : 1041503)}"); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + + writer.Write(m_CompletedBy); + + writer.Write(m_Level); + writer.Write(m_Completed); + writer.Write(m_Decoder); + writer.Write(m_Map); + writer.Write(ChestLocation); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_CompletedBy = reader.ReadMobile(); + + goto case 0; + } + case 0: + { + m_Level = reader.ReadInt(); + m_Completed = reader.ReadBool(); + m_Decoder = reader.ReadMobile(); + m_Map = reader.ReadMap(); + ChestLocation = reader.ReadPoint2D(); + + if (version == 0 && m_Completed) + m_CompletedBy = m_Decoder; + + break; + } + } + + if (Core.AOS && m_Decoder != null && LootType == LootType.Regular) + LootType = LootType.Blessed; + } + + private class DigTarget : Target + { + private TreasureMap m_Map; + + public DigTarget(TreasureMap map) : base(6, true, TargetFlags.None) + { + m_Map = map; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Map.Deleted) + return; + + Map map = m_Map.m_Map; + + if (m_Map.m_Completed) + { + from.SendLocalizedMessage(503028); // The treasure for this map has already been found. + } + /* + else if ( from != m_Map.m_Decoder ) + { + from.SendLocalizedMessage( 503016 ); // Only the person who decoded this map may actually dig up the treasure. + } + */ + else if (m_Map.m_Decoder != from && !m_Map.HasRequiredSkill(from)) + { + from.SendLocalizedMessage( + 503031); // You did not decode this map and have no clue where to look for the treasure. + } + else if (!from.CanBeginAction(typeof(TreasureMap))) + { + from.SendLocalizedMessage(503020); // You are already digging treasure. + } + else if (!HasDiggingTool(from)) + { + from.SendMessage("You must have a digging tool to dig for treasure."); + } + else if (from.Map != map) + { + from.SendLocalizedMessage(1010479); // You seem to be in the right place, but may be on the wrong facet! + } + else + { + IPoint3D p = targeted as IPoint3D; + + Point3D targ3D = (p as Item)?.GetWorldLocation() ?? new Point3D(p); + + int maxRange; + double skillValue = from.Skills[SkillName.Mining].Value; + + if (skillValue >= 100.0) + maxRange = 4; + else if (skillValue >= 81.0) + maxRange = 3; + else if (skillValue >= 51.0) + maxRange = 2; + else + maxRange = 1; + + Point2D loc = m_Map.ChestLocation; + int x = loc.X, y = loc.Y; + + Point3D chest3D0 = new Point3D(loc, 0); + + if (Utility.InRange(targ3D, chest3D0, maxRange)) + { + if (from.Location.X == x && from.Location.Y == y) + { + from.SendLocalizedMessage( + 503030); // The chest can't be dug up because you are standing on top of it. + } + else if (map != null) + { + int z = map.GetAverageZ(x, y); + + if (!map.CanFit(x, y, z, 16, true, true)) + from.SendLocalizedMessage( + 503021); // You have found the treasure chest but something is keeping it from being dug up. + else if (from.BeginAction(typeof(TreasureMap))) + new DigTimer(from, m_Map, new Point3D(x, y, z), map).Start(); + else + from.SendLocalizedMessage(503020); // You are already digging treasure. + } + } + else if (m_Map.Level > 0) + { + if (Utility.InRange(targ3D, chest3D0, 8)) // We're close, but not quite + from.SendLocalizedMessage(503032); // You dig and dig but no treasure seems to be here. + else + from.SendLocalizedMessage(503035); // You dig and dig but fail to find any treasure. + } + else + { + if (Utility.InRange(targ3D, chest3D0, 8)) // We're close, but not quite + { + from.SendAsciiMessage(0x44, "The treasure chest is very close!"); + } + else + { + Direction dir = Utility.GetDirection(targ3D, chest3D0); + + string sDir; + switch (dir) + { + case Direction.North: + sDir = "north"; + break; + case Direction.Right: + sDir = "northeast"; + break; + case Direction.East: + sDir = "east"; + break; + case Direction.Down: + sDir = "southeast"; + break; + case Direction.South: + sDir = "south"; + break; + case Direction.Left: + sDir = "southwest"; + break; + case Direction.West: + sDir = "west"; + break; + default: + sDir = "northwest"; + break; + } + + from.SendAsciiMessage(0x44, "Try looking for the treasure chest more to the {0}.", sDir); + } + } + } + } + } + + private class DigTimer : Timer + { + private TreasureMapChest m_Chest; + + private int m_Count; + + private TreasureChestDirt m_Dirt1; + private TreasureChestDirt m_Dirt2; + private Mobile m_From; + private long m_LastMoveTime; + + private Point3D m_Location; + private Map m_Map; + private long m_NextActionTime; + + private long m_NextSkillTime; + private long m_NextSpellTime; + private TreasureMap m_TreasureMap; + + public DigTimer(Mobile from, TreasureMap treasureMap, Point3D location, Map map) : base(TimeSpan.Zero, + TimeSpan.FromSeconds(1.0)) + { + m_From = from; + m_TreasureMap = treasureMap; + + m_Location = location; + m_Map = map; + + m_NextSkillTime = from.NextSkillTime; + m_NextSpellTime = from.NextSpellTime; + m_NextActionTime = from.NextActionTime; + m_LastMoveTime = from.LastMoveTime; + + Priority = TimerPriority.TenMS; + } + + private void Terminate() + { + Stop(); + m_From.EndAction(typeof(TreasureMap)); + + m_Chest?.Delete(); + + if (m_Dirt1 != null) + { + m_Dirt1.Delete(); + m_Dirt2.Delete(); + } + } + + protected override void OnTick() + { + if (m_NextSkillTime != m_From.NextSkillTime || m_NextSpellTime != m_From.NextSpellTime || + m_NextActionTime != m_From.NextActionTime) + { + Terminate(); + return; + } + + if (m_LastMoveTime != m_From.LastMoveTime) + { + m_From.SendLocalizedMessage( + 503023); // You cannot move around while digging up treasure. You will need to start digging anew. + Terminate(); + return; + } + + int z = m_Chest != null ? m_Chest.Z + m_Chest.ItemData.Height : int.MinValue; + int height = 16; + + if (z > m_Location.Z) + height -= z - m_Location.Z; + else + z = m_Location.Z; + + if (!m_Map.CanFit(m_Location.X, m_Location.Y, z, height, true, true, false)) + { + m_From.SendLocalizedMessage( + 503024); // You stop digging because something is directly on top of the treasure chest. + Terminate(); + return; + } + + m_Count++; + + m_From.RevealingAction(); + m_From.Direction = m_From.GetDirectionTo(m_Location); + + if (m_Count > 1 && m_Dirt1 == null) + { + m_Dirt1 = new TreasureChestDirt(); + m_Dirt1.MoveToWorld(m_Location, m_Map); + + m_Dirt2 = new TreasureChestDirt(); + m_Dirt2.MoveToWorld(new Point3D(m_Location.X, m_Location.Y - 1, m_Location.Z), m_Map); + } + + if (m_Count == 5) + { + m_Dirt1.Turn1(); + } + else if (m_Count == 10) + { + m_Dirt1.Turn2(); + m_Dirt2.Turn2(); + } + else if (m_Count > 10) + { + if (m_Chest == null) + { + m_Chest = new TreasureMapChest(m_From, m_TreasureMap.Level, true); + m_Chest.MoveToWorld(new Point3D(m_Location.X, m_Location.Y, m_Location.Z - 15), m_Map); + } + else + { + m_Chest.Z++; + } + + Effects.PlaySound(m_Chest, m_Map, 0x33B); + } + + if (m_Chest != null && m_Chest.Location.Z >= m_Location.Z) + { + Stop(); + m_From.EndAction(typeof(TreasureMap)); + + m_Chest.Temporary = false; + m_TreasureMap.Completed = true; + m_TreasureMap.CompletedBy = m_From; + + int spawns; + switch (m_TreasureMap.Level) + { + case 0: + spawns = 3; + break; + case 1: + spawns = 0; + break; + default: + spawns = 4; + break; + } + + for (int i = 0; i < spawns; ++i) + { + BaseCreature bc = Spawn(m_TreasureMap.Level, m_Chest.Location, m_Chest.Map, null, true); + + if (bc != null) + m_Chest.Guardians.Add(bc); + } + } + else + { + if (m_From.Body.IsHuman && !m_From.Mounted) + m_From.Animate(11, 5, 1, true, false, 0); + + new SoundTimer(m_From, 0x125 + m_Count % 2).Start(); + } + } + + private class SoundTimer : Timer + { + private Mobile m_From; + private int m_SoundID; + + public SoundTimer(Mobile from, int soundID) : base(TimeSpan.FromSeconds(0.9)) + { + m_From = from; + m_SoundID = soundID; + + Priority = TimerPriority.TenMS; + } + + protected override void OnTick() + { + m_From.PlaySound(m_SoundID); + } + } + } + + private class DecodeMapEntry : ContextMenuEntry + { + private TreasureMap m_Map; + + public DecodeMapEntry(TreasureMap map) : base(6147, 2) + { + m_Map = map; + } + + public override void OnClick() + { + if (!m_Map.Deleted) + m_Map.Decode(Owner.From); + } + } + + private class OpenMapEntry : ContextMenuEntry + { + private TreasureMap m_Map; + + public OpenMapEntry(TreasureMap map) : base(6150, 2) + { + m_Map = map; + } + + public override void OnClick() + { + if (!m_Map.Deleted) + m_Map.DisplayTo(Owner.From); + } + } + + private class DigEntry : ContextMenuEntry + { + private TreasureMap m_Map; + + public DigEntry(TreasureMap map, bool enabled) : base(6148, 2) + { + m_Map = map; + + if (!enabled) + Flags |= CMEFlags.Disabled; + } + + public override void OnClick() + { + if (m_Map.Deleted) + return; + + Mobile from = Owner.From; + + if (HasDiggingTool(from)) + m_Map.OnBeginDig(from); + else + from.SendMessage("You must have a digging tool to dig for treasure."); + } + } + } + + public class TreasureChestDirt : Item + { + public TreasureChestDirt() : base(0x912) + { + Movable = false; + + Timer.DelayCall(TimeSpan.FromMinutes(2.0), Delete); + } + + public TreasureChestDirt(Serial serial) : base(serial) + { + } + + public void Turn1() + { + ItemID = 0x913; + } + + public void Turn2() + { + ItemID = 0x914; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Maps/WorldMap.cs b/Scripts/Items/Maps/WorldMap.cs index 986de485b..24a92e7b1 100644 --- a/Scripts/Items/Maps/WorldMap.cs +++ b/Scripts/Items/Maps/WorldMap.cs @@ -1,47 +1,47 @@ namespace Server.Items { - public class WorldMap : MapItem - { - [Constructible] - public WorldMap() - { - SetDisplay( 0, 0, 5119, 4095, 400, 400 ); - } + public class WorldMap : MapItem + { + [Constructible] + public WorldMap() + { + SetDisplay(0, 0, 5119, 4095, 400, 400); + } - public override void CraftInit( Mobile from ) - { - // Unlike the others, world map is not based on crafted location + public WorldMap(Serial serial) : base(serial) + { + } - double skillValue = from.Skills[SkillName.Cartography].Value; - int x20 = (int)(skillValue * 20); - int size = 25 + (int)(skillValue * 6.6); + public override int LabelNumber => 1015233; // world map - if ( size < 200 ) - size = 200; - else if ( size > 400 ) - size = 400; + public override void CraftInit(Mobile from) + { + // Unlike the others, world map is not based on crafted location - SetDisplay( 1344 - x20, 1600 - x20, 1472 + x20, 1728 + x20, size, size ); - } + double skillValue = from.Skills[SkillName.Cartography].Value; + int x20 = (int)(skillValue * 20); + int size = 25 + (int)(skillValue * 6.6); - public override int LabelNumber => 1015233; // world map + if (size < 200) + size = 200; + else if (size > 400) + size = 400; - public WorldMap( Serial serial ) : base( serial ) - { - } + SetDisplay(1344 - x20, 1600 - x20, 1472 + x20, 1728 + x20, size, size); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/AdmiralsHeartyRum.cs b/Scripts/Items/Minor Artifacts/AdmiralsHeartyRum.cs index 78a3ab622..b083ac4f8 100644 --- a/Scripts/Items/Minor Artifacts/AdmiralsHeartyRum.cs +++ b/Scripts/Items/Minor Artifacts/AdmiralsHeartyRum.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AdmiralsHeartyRum : BeverageBottle - { - public override int LabelNumber => 1063477; + public class AdmiralsHeartyRum : BeverageBottle + { + [Constructible] + public AdmiralsHeartyRum() : base(BeverageType.Ale) + { + Hue = 0x66C; + } - [Constructible] - public AdmiralsHeartyRum() : base( BeverageType.Ale ) - { - Hue = 0x66C; - } + public AdmiralsHeartyRum(Serial serial) : base(serial) + { + } - public AdmiralsHeartyRum( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063477; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/AlchemistsBauble.cs b/Scripts/Items/Minor Artifacts/AlchemistsBauble.cs index 72daab43a..0fe06141e 100644 --- a/Scripts/Items/Minor Artifacts/AlchemistsBauble.cs +++ b/Scripts/Items/Minor Artifacts/AlchemistsBauble.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class AlchemistsBauble : GoldBracelet - { - public override int LabelNumber => 1070638; + public class AlchemistsBauble : GoldBracelet + { + [Constructible] + public AlchemistsBauble() + { + Hue = 0x290; + SkillBonuses.SetValues(0, SkillName.Magery, 10.0); + Attributes.EnhancePotions = 30; + Attributes.LowerRegCost = 20; + Resistances.Poison = 10; + } - [Constructible] - public AlchemistsBauble() - { - Hue = 0x290; - SkillBonuses.SetValues( 0, SkillName.Magery, 10.0 ); - Attributes.EnhancePotions = 30; - Attributes.LowerRegCost = 20; - Resistances.Poison = 10; - } + public AlchemistsBauble(Serial serial) : base(serial) + { + } - public AlchemistsBauble( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1070638; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ArcticDeathDealer.cs b/Scripts/Items/Minor Artifacts/ArcticDeathDealer.cs index d9e892465..5b6ea18b7 100644 --- a/Scripts/Items/Minor Artifacts/ArcticDeathDealer.cs +++ b/Scripts/Items/Minor Artifacts/ArcticDeathDealer.cs @@ -1,47 +1,48 @@ namespace Server.Items { - public class ArcticDeathDealer : WarMace - { - public override int LabelNumber => 1063481; + public class ArcticDeathDealer : WarMace + { + [Constructible] + public ArcticDeathDealer() + { + Hue = 0x480; + WeaponAttributes.HitHarm = 33; + WeaponAttributes.HitLowerAttack = 40; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 40; + WeaponAttributes.ResistColdBonus = 10; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public ArcticDeathDealer(Serial serial) : base(serial) + { + } - [Constructible] - public ArcticDeathDealer() - { - Hue = 0x480; - WeaponAttributes.HitHarm = 33; - WeaponAttributes.HitLowerAttack = 40; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 40; - WeaponAttributes.ResistColdBonus = 10; - } + public override int LabelNumber => 1063481; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - cold = 50; - phys = 50; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - pois = fire = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + cold = 50; + phys = 50; - public ArcticDeathDealer( Serial serial ) : base( serial ) - { - } + pois = fire = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/BlazeOfDeath.cs b/Scripts/Items/Minor Artifacts/BlazeOfDeath.cs index 88d285b13..e74eaf280 100644 --- a/Scripts/Items/Minor Artifacts/BlazeOfDeath.cs +++ b/Scripts/Items/Minor Artifacts/BlazeOfDeath.cs @@ -1,48 +1,49 @@ namespace Server.Items { - public class BlazeOfDeath : Halberd - { - public override int LabelNumber => 1063486; + public class BlazeOfDeath : Halberd + { + [Constructible] + public BlazeOfDeath() + { + Hue = 0x501; + WeaponAttributes.HitFireArea = 50; + WeaponAttributes.HitFireball = 50; + Attributes.WeaponSpeed = 25; + Attributes.WeaponDamage = 35; + WeaponAttributes.ResistFireBonus = 10; + WeaponAttributes.LowerStatReq = 100; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public BlazeOfDeath(Serial serial) : base(serial) + { + } - [Constructible] - public BlazeOfDeath() - { - Hue = 0x501; - WeaponAttributes.HitFireArea = 50; - WeaponAttributes.HitFireball = 50; - Attributes.WeaponSpeed = 25; - Attributes.WeaponDamage = 35; - WeaponAttributes.ResistFireBonus = 10; - WeaponAttributes.LowerStatReq = 100; - } + public override int LabelNumber => 1063486; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - fire = 50; - phys = 50; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - cold = pois = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + fire = 50; + phys = 50; - public BlazeOfDeath( Serial serial ) : base( serial ) - { - } + cold = pois = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/BowOfTheJukaKing.cs b/Scripts/Items/Minor Artifacts/BowOfTheJukaKing.cs index 9723d8c25..71528bb37 100644 --- a/Scripts/Items/Minor Artifacts/BowOfTheJukaKing.cs +++ b/Scripts/Items/Minor Artifacts/BowOfTheJukaKing.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class BowOfTheJukaKing : Bow - { - public override int LabelNumber => 1070636; + public class BowOfTheJukaKing : Bow + { + [Constructible] + public BowOfTheJukaKing() + { + Hue = 0x460; + WeaponAttributes.HitMagicArrow = 25; + Slayer = SlayerName.ReptilianDeath; + Attributes.AttackChance = 15; + Attributes.WeaponDamage = 40; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public BowOfTheJukaKing(Serial serial) : base(serial) + { + } - [Constructible] - public BowOfTheJukaKing() - { - Hue = 0x460; - WeaponAttributes.HitMagicArrow = 25; - Slayer = SlayerName.ReptilianDeath; - Attributes.AttackChance = 15; - Attributes.WeaponDamage = 40; - } + public override int LabelNumber => 1070636; - public BowOfTheJukaKing( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/BurglarsBandana.cs b/Scripts/Items/Minor Artifacts/BurglarsBandana.cs index 05b7e8cdc..5e0d94c17 100644 --- a/Scripts/Items/Minor Artifacts/BurglarsBandana.cs +++ b/Scripts/Items/Minor Artifacts/BurglarsBandana.cs @@ -1,55 +1,55 @@ namespace Server.Items { - public class BurglarsBandana : Bandana - { - public override int LabelNumber => 1063473; + public class BurglarsBandana : Bandana + { + [Constructible] + public BurglarsBandana() + { + Hue = Utility.RandomBool() ? 0x58C : 0x10; - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + SkillBonuses.SetValues(0, SkillName.Stealing, 10.0); + SkillBonuses.SetValues(1, SkillName.Stealth, 10.0); + SkillBonuses.SetValues(2, SkillName.Snooping, 10.0); - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.BonusDex = 5; + } - [Constructible] - public BurglarsBandana() - { - Hue = Utility.RandomBool() ? 0x58C : 0x10; + public BurglarsBandana(Serial serial) : base(serial) + { + } - SkillBonuses.SetValues( 0, SkillName.Stealing, 10.0 ); - SkillBonuses.SetValues( 1, SkillName.Stealth, 10.0 ); - SkillBonuses.SetValues( 2, SkillName.Snooping, 10.0 ); + public override int LabelNumber => 1063473; - Attributes.BonusDex = 5; - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public BurglarsBandana( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 2 ); - } + writer.Write(2); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 2 ) - { - Resistances.Physical = 0; - Resistances.Fire = 0; - Resistances.Cold = 0; - Resistances.Poison = 0; - Resistances.Energy = 0; - } - } - } -} + if (version < 2) + { + Resistances.Physical = 0; + Resistances.Fire = 0; + Resistances.Cold = 0; + Resistances.Poison = 0; + Resistances.Energy = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/CandelabraOfSouls.cs b/Scripts/Items/Minor Artifacts/CandelabraOfSouls.cs index 4d010a73e..b65ac609d 100644 --- a/Scripts/Items/Minor Artifacts/CandelabraOfSouls.cs +++ b/Scripts/Items/Minor Artifacts/CandelabraOfSouls.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class CandelabraOfSouls : Item - { - public override int LabelNumber => 1063478; + public class CandelabraOfSouls : Item + { + [Constructible] + public CandelabraOfSouls() : base(0xB26) + { + } - [Constructible] - public CandelabraOfSouls() : base( 0xB26 ) - { - } + public CandelabraOfSouls(Serial serial) : base(serial) + { + } - public CandelabraOfSouls( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063478; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/CaptainQuacklebushsCutlass.cs b/Scripts/Items/Minor Artifacts/CaptainQuacklebushsCutlass.cs index 7b875b496..ab5e8ded1 100644 --- a/Scripts/Items/Minor Artifacts/CaptainQuacklebushsCutlass.cs +++ b/Scripts/Items/Minor Artifacts/CaptainQuacklebushsCutlass.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class CaptainQuacklebushsCutlass : Cutlass - { - public override int LabelNumber => 1063474; + public class CaptainQuacklebushsCutlass : Cutlass + { + [Constructible] + public CaptainQuacklebushsCutlass() + { + Hue = 0x66C; + Attributes.BonusDex = 5; + Attributes.AttackChance = 10; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 50; + WeaponAttributes.UseBestSkill = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public CaptainQuacklebushsCutlass(Serial serial) : base(serial) + { + } - [Constructible] - public CaptainQuacklebushsCutlass() - { - Hue = 0x66C; - Attributes.BonusDex = 5; - Attributes.AttackChance = 10; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 50; - WeaponAttributes.UseBestSkill = 1; - } + public override int LabelNumber => 1063474; - public CaptainQuacklebushsCutlass( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Attributes.AttackChance == 50 ) - Attributes.AttackChance = 10; - } - } -} + if (Attributes.AttackChance == 50) + Attributes.AttackChance = 10; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/CavortingClub.cs b/Scripts/Items/Minor Artifacts/CavortingClub.cs index 1f4773ef9..656e0d1b9 100644 --- a/Scripts/Items/Minor Artifacts/CavortingClub.cs +++ b/Scripts/Items/Minor Artifacts/CavortingClub.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class CavortingClub : Club - { - public override int LabelNumber => 1063472; + public class CavortingClub : Club + { + [Constructible] + public CavortingClub() + { + Hue = 0x593; + WeaponAttributes.SelfRepair = 3; + Attributes.WeaponSpeed = 25; + Attributes.WeaponDamage = 35; + WeaponAttributes.ResistFireBonus = 8; + WeaponAttributes.ResistColdBonus = 8; + WeaponAttributes.ResistPoisonBonus = 8; + WeaponAttributes.ResistEnergyBonus = 8; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public CavortingClub(Serial serial) : base(serial) + { + } - [Constructible] - public CavortingClub() - { - Hue = 0x593; - WeaponAttributes.SelfRepair = 3; - Attributes.WeaponSpeed = 25; - Attributes.WeaponDamage = 35; - WeaponAttributes.ResistFireBonus = 8; - WeaponAttributes.ResistColdBonus = 8; - WeaponAttributes.ResistPoisonBonus = 8; - WeaponAttributes.ResistEnergyBonus = 8; - } + public override int LabelNumber => 1063472; - public CavortingClub( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ColdBlood.cs b/Scripts/Items/Minor Artifacts/ColdBlood.cs index 7f4439d1e..bc9c74274 100644 --- a/Scripts/Items/Minor Artifacts/ColdBlood.cs +++ b/Scripts/Items/Minor Artifacts/ColdBlood.cs @@ -1,47 +1,48 @@ namespace Server.Items { - public class ColdBlood : Cleaver - { - public override int LabelNumber => 1070818; // Cold Blood + public class ColdBlood : Cleaver + { + [Constructible] + public ColdBlood() + { + Hue = 0x4F2; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.WeaponSpeed = 40; - [Constructible] - public ColdBlood() - { - Hue = 0x4F2; + Attributes.BonusHits = 6; + Attributes.BonusStam = 6; + Attributes.BonusMana = 6; + } - Attributes.WeaponSpeed = 40; + public ColdBlood(Serial serial) : base(serial) + { + } - Attributes.BonusHits = 6; - Attributes.BonusStam = 6; - Attributes.BonusMana = 6; - } + public override int LabelNumber => 1070818; // Cold Blood - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - cold = 100; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - fire = phys = pois = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + cold = 100; - public ColdBlood( Serial serial ) : base( serial ) - { - } + fire = phys = pois = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/DreadPirateHat.cs b/Scripts/Items/Minor Artifacts/DreadPirateHat.cs index a256313f1..44e1a90cc 100644 --- a/Scripts/Items/Minor Artifacts/DreadPirateHat.cs +++ b/Scripts/Items/Minor Artifacts/DreadPirateHat.cs @@ -1,58 +1,58 @@ namespace Server.Items { - public class DreadPirateHat : TricorneHat - { - public override int LabelNumber => 1063467; + public class DreadPirateHat : TricorneHat + { + [Constructible] + public DreadPirateHat() + { + Hue = 0x497; - public override int BaseColdResistance => 14; - public override int BasePoisonResistance => 10; + SkillBonuses.SetValues(0, Utility.RandomCombatSkill(), 10.0); - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.BonusDex = 8; + Attributes.AttackChance = 10; + Attributes.NightSight = 1; + } - [Constructible] - public DreadPirateHat() - { - Hue = 0x497; + public DreadPirateHat(Serial serial) : base(serial) + { + } - SkillBonuses.SetValues( 0, Utility.RandomCombatSkill(), 10.0 ); + public override int LabelNumber => 1063467; - Attributes.BonusDex = 8; - Attributes.AttackChance = 10; - Attributes.NightSight = 1; - } + public override int BaseColdResistance => 14; + public override int BasePoisonResistance => 10; - public DreadPirateHat( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 3 ); - } + writer.Write(3); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 3 ) - { - Resistances.Cold = 0; - Resistances.Poison = 0; - } + if (version < 3) + { + Resistances.Cold = 0; + Resistances.Poison = 0; + } - if ( version < 1 ) - { - Attributes.Luck = 0; - Attributes.AttackChance = 10; - Attributes.NightSight = 1; - SkillBonuses.SetValues( 0, Utility.RandomCombatSkill(), 10.0 ); - SkillBonuses.SetBonus( 1, 0 ); - } - } - } -} + if (version < 1) + { + Attributes.Luck = 0; + Attributes.AttackChance = 10; + Attributes.NightSight = 1; + SkillBonuses.SetValues(0, Utility.RandomCombatSkill(), 10.0); + SkillBonuses.SetBonus(1, 0); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/EnchantedTitanLegBone.cs b/Scripts/Items/Minor Artifacts/EnchantedTitanLegBone.cs index 769ba4587..f54a5ef46 100644 --- a/Scripts/Items/Minor Artifacts/EnchantedTitanLegBone.cs +++ b/Scripts/Items/Minor Artifacts/EnchantedTitanLegBone.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class EnchantedTitanLegBone : ShortSpear - { - public override int LabelNumber => 1063482; + public class EnchantedTitanLegBone : ShortSpear + { + [Constructible] + public EnchantedTitanLegBone() + { + Hue = 0x8A5; + WeaponAttributes.HitLowerDefend = 40; + WeaponAttributes.HitLightning = 40; + Attributes.AttackChance = 10; + Attributes.WeaponDamage = 20; + WeaponAttributes.ResistPhysicalBonus = 10; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public EnchantedTitanLegBone(Serial serial) : base(serial) + { + } - [Constructible] - public EnchantedTitanLegBone() - { - Hue = 0x8A5; - WeaponAttributes.HitLowerDefend = 40; - WeaponAttributes.HitLightning = 40; - Attributes.AttackChance = 10; - Attributes.WeaponDamage = 20; - WeaponAttributes.ResistPhysicalBonus = 10; - } + public override int LabelNumber => 1063482; - public EnchantedTitanLegBone( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/GhostShipAnchor.cs b/Scripts/Items/Minor Artifacts/GhostShipAnchor.cs index fed138a02..41cb026a4 100644 --- a/Scripts/Items/Minor Artifacts/GhostShipAnchor.cs +++ b/Scripts/Items/Minor Artifacts/GhostShipAnchor.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public class GhostShipAnchor : Item - { - public override int LabelNumber => 1070816; // Ghost Ship Anchor + public class GhostShipAnchor : Item + { + [Constructible] + public GhostShipAnchor() : base(0x14F7) + { + Hue = 0x47E; + } - [Constructible] - public GhostShipAnchor() : base( 0x14F7 ) - { - Hue = 0x47E; - } + public GhostShipAnchor(Serial serial) : base(serial) + { + } - public GhostShipAnchor( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1070816; // Ghost Ship Anchor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( ItemID == 0x1F47 ) - ItemID = 0x14F7; - } - } -} + if (ItemID == 0x1F47) + ItemID = 0x14F7; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/GlovesOfThePugilist.cs b/Scripts/Items/Minor Artifacts/GlovesOfThePugilist.cs index 1b96eab8a..a26853721 100644 --- a/Scripts/Items/Minor Artifacts/GlovesOfThePugilist.cs +++ b/Scripts/Items/Minor Artifacts/GlovesOfThePugilist.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class GlovesOfThePugilist : LeatherGloves - { - public override int LabelNumber => 1070690; + public class GlovesOfThePugilist : LeatherGloves + { + [Constructible] + public GlovesOfThePugilist() + { + Hue = 0x6D1; + SkillBonuses.SetValues(0, SkillName.Wrestling, 10.0); + Attributes.BonusDex = 8; + Attributes.WeaponDamage = 15; + } - public override int BasePhysicalResistance => 18; + public GlovesOfThePugilist(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1070690; - [Constructible] - public GlovesOfThePugilist() - { - Hue = 0x6D1; - SkillBonuses.SetValues( 0, SkillName.Wrestling, 10.0 ); - Attributes.BonusDex = 8; - Attributes.WeaponDamage = 15; - } + public override int BasePhysicalResistance => 18; - public GlovesOfThePugilist( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/GoldBricks.cs b/Scripts/Items/Minor Artifacts/GoldBricks.cs index 780578804..9bdd6f501 100644 --- a/Scripts/Items/Minor Artifacts/GoldBricks.cs +++ b/Scripts/Items/Minor Artifacts/GoldBricks.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class GoldBricks : Item - { - public override int LabelNumber => 1063489; + public class GoldBricks : Item + { + [Constructible] + public GoldBricks() : base(0x1BEB) + { + } - [Constructible] - public GoldBricks() : base( 0x1BEB ) - { - } + public GoldBricks(Serial serial) : base(serial) + { + } - public GoldBricks( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063489; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/GwennosHarp.cs b/Scripts/Items/Minor Artifacts/GwennosHarp.cs index d0a573def..a90093d02 100644 --- a/Scripts/Items/Minor Artifacts/GwennosHarp.cs +++ b/Scripts/Items/Minor Artifacts/GwennosHarp.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class GwennosHarp : LapHarp - { - public override int LabelNumber => 1063480; + public class GwennosHarp : LapHarp + { + [Constructible] + public GwennosHarp() + { + Hue = 0x47E; + Slayer = SlayerName.Repond; + Slayer2 = SlayerName.ReptilianDeath; + } - public override int InitMinUses => 1600; - public override int InitMaxUses => 1600; + public GwennosHarp(Serial serial) : base(serial) + { + } - [Constructible] - public GwennosHarp() - { - Hue = 0x47E; - Slayer = SlayerName.Repond; - Slayer2 = SlayerName.ReptilianDeath; - } + public override int LabelNumber => 1063480; - public GwennosHarp( Serial serial ) : base( serial ) - { - } + public override int InitMinUses => 1600; + public override int InitMaxUses => 1600; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/HeartOfTheLion.cs b/Scripts/Items/Minor Artifacts/HeartOfTheLion.cs index 5f9f97d3d..858c7022d 100644 --- a/Scripts/Items/Minor Artifacts/HeartOfTheLion.cs +++ b/Scripts/Items/Minor Artifacts/HeartOfTheLion.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class HeartOfTheLion : PlateChest - { - public override int LabelNumber => 1070817; // Heart of the Lion + public class HeartOfTheLion : PlateChest + { + [Constructible] + public HeartOfTheLion() + { + Hue = 0x501; + Attributes.Luck = 95; + Attributes.DefendChance = 15; + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + } - public override int BasePhysicalResistance => 15; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 10; - public override int BaseEnergyResistance => 10; + public HeartOfTheLion(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1070817; // Heart of the Lion - [Constructible] - public HeartOfTheLion() - { - Hue = 0x501; - Attributes.Luck = 95; - Attributes.DefendChance = 15; - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - } + public override int BasePhysicalResistance => 15; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 10; + public override int BaseEnergyResistance => 10; - public HeartOfTheLion( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/IolosLute.cs b/Scripts/Items/Minor Artifacts/IolosLute.cs index f93c52646..26160b4b0 100644 --- a/Scripts/Items/Minor Artifacts/IolosLute.cs +++ b/Scripts/Items/Minor Artifacts/IolosLute.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class IolosLute : Lute - { - public override int LabelNumber => 1063479; + public class IolosLute : Lute + { + [Constructible] + public IolosLute() + { + Hue = 0x47E; + Slayer = SlayerName.Silver; + //Slayer2 = SlayerName.DaemonDismissal; + Slayer2 = SlayerName.Exorcism; + } - public override int InitMinUses => 1600; - public override int InitMaxUses => 1600; + public IolosLute(Serial serial) : base(serial) + { + } - [Constructible] - public IolosLute() - { - Hue = 0x47E; - Slayer = SlayerName.Silver; - //Slayer2 = SlayerName.DaemonDismissal; - Slayer2 = SlayerName.Exorcism; - } + public override int LabelNumber => 1063479; - public IolosLute( Serial serial ) : base( serial ) - { - } + public override int InitMinUses => 1600; + public override int InitMaxUses => 1600; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/LunaLance.cs b/Scripts/Items/Minor Artifacts/LunaLance.cs index e8920c019..897801f39 100644 --- a/Scripts/Items/Minor Artifacts/LunaLance.cs +++ b/Scripts/Items/Minor Artifacts/LunaLance.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class LunaLance : Lance - { - public override int LabelNumber => 1063469; + public class LunaLance : Lance + { + [Constructible] + public LunaLance() + { + Hue = 0x47E; + SkillBonuses.SetValues(0, SkillName.Chivalry, 10.0); + Attributes.BonusStr = 5; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 35; + WeaponAttributes.UseBestSkill = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public LunaLance(Serial serial) : base(serial) + { + } - [Constructible] - public LunaLance() - { - Hue = 0x47E; - SkillBonuses.SetValues( 0, SkillName.Chivalry, 10.0 ); - Attributes.BonusStr = 5; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 35; - WeaponAttributes.UseBestSkill = 1; - } + public override int LabelNumber => 1063469; - public LunaLance( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/AegisOfGrace.cs b/Scripts/Items/Minor Artifacts/ML/AegisOfGrace.cs index 42b81f718..13b1e18ac 100644 --- a/Scripts/Items/Minor Artifacts/ML/AegisOfGrace.cs +++ b/Scripts/Items/Minor Artifacts/ML/AegisOfGrace.cs @@ -1,49 +1,49 @@ namespace Server.Items { - public class AegisOfGrace : DragonHelm - { - public override int LabelNumber => 1075047; // Aegis of Grace + public class AegisOfGrace : DragonHelm + { + [Constructible] + public AegisOfGrace() + { + SkillBonuses.SetValues(0, SkillName.MagicResist, 10.0); - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 9; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 7; - public override int BaseEnergyResistance => 15; + Attributes.DefendChance = 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; - public override CraftResource DefaultResource => CraftResource.Iron; + ArmorAttributes.SelfRepair = 2; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public AegisOfGrace(Serial serial) : base(serial) + { + } - [Constructible] - public AegisOfGrace() - { - SkillBonuses.SetValues( 0, SkillName.MagicResist, 10.0 ); + public override int LabelNumber => 1075047; // Aegis of Grace - Attributes.DefendChance = 20; + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 9; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 7; + public override int BaseEnergyResistance => 15; - ArmorAttributes.SelfRepair = 2; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Dragon; + public override CraftResource DefaultResource => CraftResource.Iron; - public override Race RequiredRace => Race.Elf; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public AegisOfGrace( Serial serial ) : base( serial ) - { - } + public override Race RequiredRace => Race.Elf; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/BladeDance.cs b/Scripts/Items/Minor Artifacts/ML/BladeDance.cs index 4eaac83ea..90b7ecad6 100644 --- a/Scripts/Items/Minor Artifacts/ML/BladeDance.cs +++ b/Scripts/Items/Minor Artifacts/ML/BladeDance.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class BladeDance : RuneBlade - { - public override int LabelNumber => 1075033; // Blade Dance + public class BladeDance : RuneBlade + { + [Constructible] + public BladeDance() + { + Hue = 0x66C; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.BonusMana = 8; + Attributes.SpellChanneling = 1; + Attributes.WeaponDamage = 30; + WeaponAttributes.HitLeechMana = 20; + WeaponAttributes.UseBestSkill = 1; + } - [Constructible] - public BladeDance() - { - Hue = 0x66C; + public BladeDance(Serial serial) : base(serial) + { + } - Attributes.BonusMana = 8; - Attributes.SpellChanneling = 1; - Attributes.WeaponDamage = 30; - WeaponAttributes.HitLeechMana = 20; - WeaponAttributes.UseBestSkill = 1; - } + public override int LabelNumber => 1075033; // Blade Dance - public BladeDance( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/BloodwoodSpirit.cs b/Scripts/Items/Minor Artifacts/ML/BloodwoodSpirit.cs index d767a4502..435615145 100644 --- a/Scripts/Items/Minor Artifacts/ML/BloodwoodSpirit.cs +++ b/Scripts/Items/Minor Artifacts/ML/BloodwoodSpirit.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class BloodwoodSpirit : BaseTalisman - { - public override int LabelNumber => 1075034; // Bloodwood Spirit - public override bool ForceShowName => true; + public class BloodwoodSpirit : BaseTalisman + { + [Constructible] + public BloodwoodSpirit() : base(0x2F5A) + { + Hue = 0x27; + MaxChargeTime = 1200; - [Constructible] - public BloodwoodSpirit() : base( 0x2F5A ) - { - Hue = 0x27; - MaxChargeTime = 1200; + Removal = TalismanRemoval.Damage; + Blessed = GetRandomBlessed(); + Protection = GetRandomProtection(false); - Removal = TalismanRemoval.Damage; - Blessed = GetRandomBlessed(); - Protection = GetRandomProtection( false ); + SkillBonuses.SetValues(0, SkillName.SpiritSpeak, 10.0); + SkillBonuses.SetValues(1, SkillName.Necromancy, 5.0); + } - SkillBonuses.SetValues( 0, SkillName.SpiritSpeak, 10.0 ); - SkillBonuses.SetValues( 1, SkillName.Necromancy, 5.0 ); - } + public BloodwoodSpirit(Serial serial) : base(serial) + { + } - public BloodwoodSpirit( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075034; // Bloodwood Spirit + public override bool ForceShowName => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && ( Protection == null || Protection.IsEmpty ) ) - Protection = GetRandomProtection( false ); - } - } -} + if (version == 0 && (Protection == null || Protection.IsEmpty)) + Protection = GetRandomProtection(false); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/Bonesmasher.cs b/Scripts/Items/Minor Artifacts/ML/Bonesmasher.cs index 022c7930f..15569c47b 100644 --- a/Scripts/Items/Minor Artifacts/ML/Bonesmasher.cs +++ b/Scripts/Items/Minor Artifacts/ML/Bonesmasher.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class Bonesmasher : DiamondMace - { - public override int LabelNumber => 1075030; // Bonesmasher + public class Bonesmasher : DiamondMace + { + [Constructible] + public Bonesmasher() + { + ItemID = 0x2D30; + Hue = 0x482; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + SkillBonuses.SetValues(0, SkillName.Macing, 10.0); - [Constructible] - public Bonesmasher() - { - ItemID = 0x2D30; - Hue = 0x482; + WeaponAttributes.HitLeechMana = 40; + WeaponAttributes.SelfRepair = 2; + } - SkillBonuses.SetValues( 0, SkillName.Macing, 10.0 ); + public Bonesmasher(Serial serial) : base(serial) + { + } - WeaponAttributes.HitLeechMana = 40; - WeaponAttributes.SelfRepair = 2; - } + public override int LabelNumber => 1075030; // Bonesmasher - public Bonesmasher( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/Boomstick.cs b/Scripts/Items/Minor Artifacts/ML/Boomstick.cs index 55dbd0267..a06b76fc6 100644 --- a/Scripts/Items/Minor Artifacts/ML/Boomstick.cs +++ b/Scripts/Items/Minor Artifacts/ML/Boomstick.cs @@ -1,45 +1,46 @@ namespace Server.Items { - public class Boomstick : WildStaff - { - public override int LabelNumber => 1075032; // Boomstick + public class Boomstick : WildStaff + { + [Constructible] + public Boomstick() + { + Hue = 0x25; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.SpellChanneling = 1; + Attributes.RegenMana = 3; + Attributes.CastSpeed = 1; + Attributes.LowerRegCost = 20; + } - [Constructible] - public Boomstick() - { - Hue = 0x25; + public Boomstick(Serial serial) : base(serial) + { + } - Attributes.SpellChanneling = 1; - Attributes.RegenMana = 3; - Attributes.CastSpeed = 1; - Attributes.LowerRegCost = 20; - } + public override int LabelNumber => 1075032; // Boomstick - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = nrgy = direct = 0; - chaos = 100; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public Boomstick( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = nrgy = direct = 0; + chaos = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/BrightsightLenses.cs b/Scripts/Items/Minor Artifacts/ML/BrightsightLenses.cs index bcc4fc352..b9fc5d100 100644 --- a/Scripts/Items/Minor Artifacts/ML/BrightsightLenses.cs +++ b/Scripts/Items/Minor Artifacts/ML/BrightsightLenses.cs @@ -1,51 +1,51 @@ namespace Server.Items { - public class BrightsightLenses : ElvenGlasses - { - public override int LabelNumber => 1075039; // Brightsight Lenses + public class BrightsightLenses : ElvenGlasses + { + [Constructible] + public BrightsightLenses() + { + Hue = 0x501; - public override int BasePhysicalResistance => 9; - public override int BaseFireResistance => 29; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 8; - public override int BaseEnergyResistance => 7; + Attributes.NightSight = 1; + Attributes.RegenMana = 3; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + ArmorAttributes.SelfRepair = 3; + } - [Constructible] - public BrightsightLenses() - { - Hue = 0x501; + public BrightsightLenses(Serial serial) : base(serial) + { + } - Attributes.NightSight = 1; - Attributes.RegenMana = 3; + public override int LabelNumber => 1075039; // Brightsight Lenses - ArmorAttributes.SelfRepair = 3; - } + public override int BasePhysicalResistance => 9; + public override int BaseFireResistance => 29; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 8; + public override int BaseEnergyResistance => 7; - public BrightsightLenses( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - WeaponAttributes.SelfRepair = 0; - ArmorAttributes.SelfRepair = 3; - } - } - } -} + if (version < 1) + { + WeaponAttributes.SelfRepair = 0; + ArmorAttributes.SelfRepair = 3; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/FeyLeggings.cs b/Scripts/Items/Minor Artifacts/ML/FeyLeggings.cs index 7db68a18c..460228af3 100644 --- a/Scripts/Items/Minor Artifacts/ML/FeyLeggings.cs +++ b/Scripts/Items/Minor Artifacts/ML/FeyLeggings.cs @@ -1,46 +1,45 @@ namespace Server.Items { - public class FeyLeggings : ChainLegs - { - public override int LabelNumber => 1075041; // Fey Leggings + public class FeyLeggings : ChainLegs + { + [Constructible] + public FeyLeggings() + { + Attributes.BonusHits = 6; + Attributes.DefendChance = 20; - public override int BasePhysicalResistance => 12; - public override int BaseFireResistance => 8; - public override int BaseColdResistance => 7; - public override int BasePoisonResistance => 4; - public override int BaseEnergyResistance => 19; + ArmorAttributes.MageArmor = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public FeyLeggings(Serial serial) : base(serial) + { + } + public override int LabelNumber => 1075041; // Fey Leggings - [Constructible] - public FeyLeggings() - { - Attributes.BonusHits = 6; - Attributes.DefendChance = 20; + public override int BasePhysicalResistance => 12; + public override int BaseFireResistance => 8; + public override int BaseColdResistance => 7; + public override int BasePoisonResistance => 4; + public override int BaseEnergyResistance => 19; - ArmorAttributes.MageArmor = 1; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override Race RequiredRace => Race.Elf; + public override Race RequiredRace => Race.Elf; - public FeyLeggings( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); // version + } - writer.WriteEncodedInt( 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/FleshRipper.cs b/Scripts/Items/Minor Artifacts/ML/FleshRipper.cs index 7f9101390..5ef30da1b 100644 --- a/Scripts/Items/Minor Artifacts/ML/FleshRipper.cs +++ b/Scripts/Items/Minor Artifacts/ML/FleshRipper.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class FleshRipper : AssassinSpike - { - public override int LabelNumber => 1075045; // Flesh Ripper + public class FleshRipper : AssassinSpike + { + [Constructible] + public FleshRipper() + { + Hue = 0x341; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + SkillBonuses.SetValues(0, SkillName.Anatomy, 10.0); - [Constructible] - public FleshRipper() - { - Hue = 0x341; + Attributes.BonusStr = 5; + Attributes.AttackChance = 15; + Attributes.WeaponSpeed = 40; - SkillBonuses.SetValues( 0, SkillName.Anatomy, 10.0 ); + WeaponAttributes.UseBestSkill = 1; + // TODO: Mage Slayer + } - Attributes.BonusStr = 5; - Attributes.AttackChance = 15; - Attributes.WeaponSpeed = 40; + public FleshRipper(Serial serial) : base(serial) + { + } - WeaponAttributes.UseBestSkill = 1; - // TODO: Mage Slayer - } + public override int LabelNumber => 1075045; // Flesh Ripper - public FleshRipper( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/HelmOfSwiftness.cs b/Scripts/Items/Minor Artifacts/ML/HelmOfSwiftness.cs index 85ffc6b44..18cb77770 100644 --- a/Scripts/Items/Minor Artifacts/ML/HelmOfSwiftness.cs +++ b/Scripts/Items/Minor Artifacts/ML/HelmOfSwiftness.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class HelmOfSwiftness : WingedHelm - { - public override int LabelNumber => 1075037; // Helm of Swiftness + public class HelmOfSwiftness : WingedHelm + { + [Constructible] + public HelmOfSwiftness() + { + Hue = 0x592; - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 6; - public override int BasePoisonResistance => 6; - public override int BaseEnergyResistance => 8; + Attributes.BonusInt = 5; + Attributes.CastSpeed = 1; + Attributes.CastRecovery = 2; + ArmorAttributes.MageArmor = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public HelmOfSwiftness(Serial serial) : base(serial) + { + } - [Constructible] - public HelmOfSwiftness() - { - Hue = 0x592; + public override int LabelNumber => 1075037; // Helm of Swiftness - Attributes.BonusInt = 5; - Attributes.CastSpeed = 1; - Attributes.CastRecovery = 2; - ArmorAttributes.MageArmor = 1; - } + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 6; + public override int BasePoisonResistance => 6; + public override int BaseEnergyResistance => 8; - public HelmOfSwiftness( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/MelisandesCorrodedHatchet.cs b/Scripts/Items/Minor Artifacts/ML/MelisandesCorrodedHatchet.cs index a78dff47f..22631b667 100644 --- a/Scripts/Items/Minor Artifacts/ML/MelisandesCorrodedHatchet.cs +++ b/Scripts/Items/Minor Artifacts/ML/MelisandesCorrodedHatchet.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class MelisandesCorrodedHatchet : Hatchet - { - public override int LabelNumber => 1072115; // Melisande's Corroded Hatchet + public class MelisandesCorrodedHatchet : Hatchet + { + [Constructible] + public MelisandesCorrodedHatchet() + { + Hue = 0x494; - [Constructible] - public MelisandesCorrodedHatchet() - { - Hue = 0x494; + SkillBonuses.SetValues(0, SkillName.Lumberjacking, 5.0); - SkillBonuses.SetValues( 0, SkillName.Lumberjacking, 5.0 ); + Attributes.SpellChanneling = 1; + Attributes.WeaponSpeed = 15; + Attributes.WeaponDamage = -50; - Attributes.SpellChanneling = 1; - Attributes.WeaponSpeed = 15; - Attributes.WeaponDamage = -50; + WeaponAttributes.SelfRepair = 4; + } - WeaponAttributes.SelfRepair = 4; - } + public MelisandesCorrodedHatchet(Serial serial) : base(serial) + { + } - public MelisandesCorrodedHatchet( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072115; // Melisande's Corroded Hatchet - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/PadsOfTheCuSidhe.cs b/Scripts/Items/Minor Artifacts/ML/PadsOfTheCuSidhe.cs index cef8f9b06..914cf86b7 100644 --- a/Scripts/Items/Minor Artifacts/ML/PadsOfTheCuSidhe.cs +++ b/Scripts/Items/Minor Artifacts/ML/PadsOfTheCuSidhe.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class PadsOfTheCuSidhe : FurBoots - { - public override int LabelNumber => 1075048; // Pads of the Cu Sidhe + public class PadsOfTheCuSidhe : FurBoots + { + [Constructible] + public PadsOfTheCuSidhe() : base(0x47E) + { + } - [Constructible] - public PadsOfTheCuSidhe() : base( 0x47E ) - { - } + public PadsOfTheCuSidhe(Serial serial) : base(serial) + { + } - public PadsOfTheCuSidhe( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075048; // Pads of the Cu Sidhe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/QuiverOfElements.cs b/Scripts/Items/Minor Artifacts/ML/QuiverOfElements.cs index 71dfce31f..d77a5fb8d 100644 --- a/Scripts/Items/Minor Artifacts/ML/QuiverOfElements.cs +++ b/Scripts/Items/Minor Artifacts/ML/QuiverOfElements.cs @@ -1,38 +1,39 @@ namespace Server.Items { - public class QuiverOfElements : BaseQuiver - { - public override int LabelNumber => 1075040; // Quiver of the Elements + public class QuiverOfElements : BaseQuiver + { + [Constructible] + public QuiverOfElements() + { + Hue = 0xEB; + WeightReduction = 50; + } - [Constructible] - public QuiverOfElements() - { - Hue = 0xEB; - WeightReduction = 50; - } + public QuiverOfElements(Serial serial) : base(serial) + { + } - public QuiverOfElements( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075040; // Quiver of the Elements - public override void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - phys = fire = cold = pois = nrgy = direct = 0; - chaos = 100; - } + public override void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + phys = fire = cold = pois = nrgy = direct = 0; + chaos = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/QuiverOfRage.cs b/Scripts/Items/Minor Artifacts/ML/QuiverOfRage.cs index f93148f9f..eb1effd9c 100644 --- a/Scripts/Items/Minor Artifacts/ML/QuiverOfRage.cs +++ b/Scripts/Items/Minor Artifacts/ML/QuiverOfRage.cs @@ -1,40 +1,41 @@ namespace Server.Items { - public class QuiverOfRage : BaseQuiver - { - public override int LabelNumber => 1075038; // Quiver of Rage + public class QuiverOfRage : BaseQuiver + { + [Constructible] + public QuiverOfRage() + { + Hue = 0x24C; - [Constructible] - public QuiverOfRage() - { - Hue = 0x24C; + WeightReduction = 25; + DamageIncrease = 10; + } - WeightReduction = 25; - DamageIncrease = 10; - } + public QuiverOfRage(Serial serial) : base(serial) + { + } - public QuiverOfRage( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075038; // Quiver of Rage - public override void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - chaos = direct = 0; - phys = fire = cold = pois = nrgy = 20; - } + public override void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + chaos = direct = 0; + phys = fire = cold = pois = nrgy = 20; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/RaedsGlory.cs b/Scripts/Items/Minor Artifacts/ML/RaedsGlory.cs index 97fc01f43..3eeee3a0c 100644 --- a/Scripts/Items/Minor Artifacts/ML/RaedsGlory.cs +++ b/Scripts/Items/Minor Artifacts/ML/RaedsGlory.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class RaedsGlory : WarCleaver - { - public override int LabelNumber => 1075036; // Raed's Glory + public class RaedsGlory : WarCleaver + { + [Constructible] + public RaedsGlory() + { + ItemID = 0x2D23; + Hue = 0x1E6; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.BonusMana = 8; + Attributes.SpellChanneling = 1; + Attributes.WeaponSpeed = 20; - [Constructible] - public RaedsGlory() - { - ItemID = 0x2D23; - Hue = 0x1E6; + WeaponAttributes.HitLeechHits = 40; + } - Attributes.BonusMana = 8; - Attributes.SpellChanneling = 1; - Attributes.WeaponSpeed = 20; + public RaedsGlory(Serial serial) : base(serial) + { + } - WeaponAttributes.HitLeechHits = 40; - } + public override int LabelNumber => 1075036; // Raed's Glory - public RaedsGlory( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/RighteousAnger.cs b/Scripts/Items/Minor Artifacts/ML/RighteousAnger.cs index 1d6e7b2b5..acc33ef22 100644 --- a/Scripts/Items/Minor Artifacts/ML/RighteousAnger.cs +++ b/Scripts/Items/Minor Artifacts/ML/RighteousAnger.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class RighteousAnger : ElvenMachete - { - public override int LabelNumber => 1075049; // Righteous Anger + public class RighteousAnger : ElvenMachete + { + [Constructible] + public RighteousAnger() + { + Hue = 0x284; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.AttackChance = 15; + Attributes.DefendChance = 5; + Attributes.WeaponSpeed = 35; + Attributes.WeaponDamage = 40; + } - [Constructible] - public RighteousAnger() - { - Hue = 0x284; + public RighteousAnger(Serial serial) : base(serial) + { + } - Attributes.AttackChance = 15; - Attributes.DefendChance = 5; - Attributes.WeaponSpeed = 35; - Attributes.WeaponDamage = 40; - } + public override int LabelNumber => 1075049; // Righteous Anger - public RighteousAnger( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/RobeOfTheEclipse.cs b/Scripts/Items/Minor Artifacts/ML/RobeOfTheEclipse.cs index 62de848fe..4ff46f683 100644 --- a/Scripts/Items/Minor Artifacts/ML/RobeOfTheEclipse.cs +++ b/Scripts/Items/Minor Artifacts/ML/RobeOfTheEclipse.cs @@ -1,36 +1,36 @@ namespace Server.Items { - [Flippable( 0x1F03, 0x1F04 )] - public class RobeOfTheEclipse : BaseOuterTorso - { - public override int LabelNumber => 1075082; // Robe of the Eclipse + [Flippable(0x1F03, 0x1F04)] + public class RobeOfTheEclipse : BaseOuterTorso + { + [Constructible] + public RobeOfTheEclipse() : base(0x1F03, 0x486) + { + Weight = 3.0; - [Constructible] - public RobeOfTheEclipse() : base( 0x1F03, 0x486 ) - { - Weight = 3.0; + Attributes.Luck = 95; - Attributes.Luck = 95; + // TODO: Supports arcane? + } - // TODO: Supports arcane? - } + public RobeOfTheEclipse(Serial serial) : base(serial) + { + } - public RobeOfTheEclipse( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075082; // Robe of the Eclipse - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/RobeOfTheEquinox.cs b/Scripts/Items/Minor Artifacts/ML/RobeOfTheEquinox.cs index 7085af1ae..12e42626a 100644 --- a/Scripts/Items/Minor Artifacts/ML/RobeOfTheEquinox.cs +++ b/Scripts/Items/Minor Artifacts/ML/RobeOfTheEquinox.cs @@ -1,37 +1,37 @@ namespace Server.Items { - [Flippable( 0x1F03, 0x1F04 )] - public class RobeOfTheEquinox : BaseOuterTorso - { - public override int LabelNumber => 1075042; // Robe of the Equinox + [Flippable(0x1F03, 0x1F04)] + public class RobeOfTheEquinox : BaseOuterTorso + { + [Constructible] + public RobeOfTheEquinox() : base(0x1F04, 0xD6) + { + Weight = 3.0; - [Constructible] - public RobeOfTheEquinox() : base( 0x1F04, 0xD6 ) - { - Weight = 3.0; + Attributes.Luck = 95; - Attributes.Luck = 95; + // TODO: Supports arcane? + // TODO: Elves Only + } - // TODO: Supports arcane? - // TODO: Elves Only - } + public RobeOfTheEquinox(Serial serial) : base(serial) + { + } - public RobeOfTheEquinox( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075042; // Robe of the Equinox - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/SoulSeeker.cs b/Scripts/Items/Minor Artifacts/ML/SoulSeeker.cs index 313576d97..1912681cf 100644 --- a/Scripts/Items/Minor Artifacts/ML/SoulSeeker.cs +++ b/Scripts/Items/Minor Artifacts/ML/SoulSeeker.cs @@ -1,47 +1,48 @@ namespace Server.Items { - public class SoulSeeker : RadiantScimitar - { - public override int LabelNumber => 1075046; // Soul Seeker + public class SoulSeeker : RadiantScimitar + { + [Constructible] + public SoulSeeker() + { + Hue = 0x38C; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + WeaponAttributes.HitLeechStam = 40; + WeaponAttributes.HitLeechMana = 40; + WeaponAttributes.HitLeechHits = 40; + Attributes.WeaponSpeed = 60; + Slayer = SlayerName.Repond; + } - [Constructible] - public SoulSeeker() - { - Hue = 0x38C; + public SoulSeeker(Serial serial) : base(serial) + { + } - WeaponAttributes.HitLeechStam = 40; - WeaponAttributes.HitLeechMana = 40; - WeaponAttributes.HitLeechHits = 40; - Attributes.WeaponSpeed = 60; - Slayer = SlayerName.Repond; - } + public override int LabelNumber => 1075046; // Soul Seeker - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - cold = 100; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - pois = fire = phys = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + cold = 100; - public SoulSeeker( Serial serial ) : base( serial ) - { - } + pois = fire = phys = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/TalonBite.cs b/Scripts/Items/Minor Artifacts/ML/TalonBite.cs index 256ab3a92..0c5835c85 100644 --- a/Scripts/Items/Minor Artifacts/ML/TalonBite.cs +++ b/Scripts/Items/Minor Artifacts/ML/TalonBite.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class TalonBite : OrnateAxe - { - public override int LabelNumber => 1075029; // Talon Bite + public class TalonBite : OrnateAxe + { + [Constructible] + public TalonBite() + { + ItemID = 0x2D34; + Hue = 0x47E; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + SkillBonuses.SetValues(0, SkillName.Tactics, 10.0); - [Constructible] - public TalonBite() - { - ItemID = 0x2D34; - Hue = 0x47E; + Attributes.BonusDex = 8; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 35; - SkillBonuses.SetValues( 0, SkillName.Tactics, 10.0 ); + WeaponAttributes.HitHarm = 33; + WeaponAttributes.UseBestSkill = 1; + } - Attributes.BonusDex = 8; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 35; + public TalonBite(Serial serial) : base(serial) + { + } - WeaponAttributes.HitHarm = 33; - WeaponAttributes.UseBestSkill = 1; - } + public override int LabelNumber => 1075029; // Talon Bite - public TalonBite( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/TotemOfVoid.cs b/Scripts/Items/Minor Artifacts/ML/TotemOfVoid.cs index 1ba8acdc2..cfd6a9b5a 100644 --- a/Scripts/Items/Minor Artifacts/ML/TotemOfVoid.cs +++ b/Scripts/Items/Minor Artifacts/ML/TotemOfVoid.cs @@ -3,48 +3,48 @@ using Server.Mobiles; namespace Server.Items { - public class TotemOfVoid : BaseTalisman - { - public override int LabelNumber => 1075035; // Totem of the Void - public override bool ForceShowName => true; + public class TotemOfVoid : BaseTalisman + { + [Constructible] + public TotemOfVoid() : base(0x2F5B) + { + Hue = 0x2D0; + MaxChargeTime = 1800; - [Constructible] - public TotemOfVoid() : base( 0x2F5B ) - { - Hue = 0x2D0; - MaxChargeTime = 1800; + Blessed = GetRandomBlessed(); + Protection = GetRandomProtection(false); - Blessed = GetRandomBlessed(); - Protection = GetRandomProtection( false ); + Attributes.RegenHits = 2; + Attributes.LowerManaCost = 10; + } - Attributes.RegenHits = 2; - Attributes.LowerManaCost = 10; - } + public TotemOfVoid(Serial serial) : base(serial) + { + } - public TotemOfVoid( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075035; // Totem of the Void + public override bool ForceShowName => true; - public override Type GetSummoner() - { - return Utility.RandomBool() ? typeof( SummonedSkeletalKnight ) : typeof( SummonedSheep ); - } + public override Type GetSummoner() + { + return Utility.RandomBool() ? typeof(SummonedSkeletalKnight) : typeof(SummonedSheep); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && ( Protection == null || Protection.IsEmpty ) ) - Protection = GetRandomProtection( false ); - } - } -} + if (version == 0 && (Protection == null || Protection.IsEmpty)) + Protection = GetRandomProtection(false); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/WildfireBow.cs b/Scripts/Items/Minor Artifacts/ML/WildfireBow.cs index 00edf3fff..f5a152e0b 100644 --- a/Scripts/Items/Minor Artifacts/ML/WildfireBow.cs +++ b/Scripts/Items/Minor Artifacts/ML/WildfireBow.cs @@ -1,45 +1,46 @@ namespace Server.Items { - public class WildfireBow : ElvenCompositeLongbow - { - public override int LabelNumber => 1075044; // Wildfire Bow + public class WildfireBow : ElvenCompositeLongbow + { + [Constructible] + public WildfireBow() + { + Hue = 0x489; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + SkillBonuses.SetValues(0, SkillName.Archery, 10); + WeaponAttributes.ResistFireBonus = 25; - [Constructible] - public WildfireBow() - { - Hue = 0x489; + Velocity = 15; + } - SkillBonuses.SetValues( 0, SkillName.Archery, 10 ); - WeaponAttributes.ResistFireBonus = 25; + public WildfireBow(Serial serial) : base(serial) + { + } - Velocity = 15; - } + public override int LabelNumber => 1075044; // Wildfire Bow - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = cold = pois = nrgy = chaos = direct = 0; - fire = 100; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public WildfireBow( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = cold = pois = nrgy = chaos = direct = 0; + fire = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ML/Windsong.cs b/Scripts/Items/Minor Artifacts/ML/Windsong.cs index 66156d4f1..0813c7d49 100644 --- a/Scripts/Items/Minor Artifacts/ML/Windsong.cs +++ b/Scripts/Items/Minor Artifacts/ML/Windsong.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class Windsong : MagicalShortbow - { - public override int LabelNumber => 1075031; // Windsong + public class Windsong : MagicalShortbow + { + [Constructible] + public Windsong() + { + Hue = 0xF7; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.WeaponDamage = 35; + WeaponAttributes.SelfRepair = 3; - [Constructible] - public Windsong() - { - Hue = 0xF7; + Velocity = 25; + } - Attributes.WeaponDamage = 35; - WeaponAttributes.SelfRepair = 3; + public Windsong(Serial serial) : base(serial) + { + } - Velocity = 25; - } + public override int LabelNumber => 1075031; // Windsong - public Windsong( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/NightsKiss.cs b/Scripts/Items/Minor Artifacts/NightsKiss.cs index c81dc6af6..7801df800 100644 --- a/Scripts/Items/Minor Artifacts/NightsKiss.cs +++ b/Scripts/Items/Minor Artifacts/NightsKiss.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class NightsKiss : Dagger - { - public override int LabelNumber => 1063475; + public class NightsKiss : Dagger + { + [Constructible] + public NightsKiss() + { + ItemID = 0xF51; + Hue = 0x455; + WeaponAttributes.HitLeechHits = 40; + Slayer = SlayerName.Repond; + Attributes.WeaponSpeed = 30; + Attributes.WeaponDamage = 35; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public NightsKiss(Serial serial) : base(serial) + { + } - [Constructible] - public NightsKiss() - { - ItemID = 0xF51; - Hue = 0x455; - WeaponAttributes.HitLeechHits = 40; - Slayer = SlayerName.Repond; - Attributes.WeaponSpeed = 30; - Attributes.WeaponDamage = 35; - } + public override int LabelNumber => 1063475; - public NightsKiss( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/NoxRangersHeavyCrossbow.cs b/Scripts/Items/Minor Artifacts/NoxRangersHeavyCrossbow.cs index f7ed802b8..e30d04f4a 100644 --- a/Scripts/Items/Minor Artifacts/NoxRangersHeavyCrossbow.cs +++ b/Scripts/Items/Minor Artifacts/NoxRangersHeavyCrossbow.cs @@ -1,47 +1,48 @@ namespace Server.Items { - public class NoxRangersHeavyCrossbow : HeavyCrossbow - { - public override int LabelNumber => 1063485; + public class NoxRangersHeavyCrossbow : HeavyCrossbow + { + [Constructible] + public NoxRangersHeavyCrossbow() + { + Hue = 0x58C; + WeaponAttributes.HitLeechStam = 40; + Attributes.SpellChanneling = 1; + Attributes.WeaponSpeed = 30; + Attributes.WeaponDamage = 20; + WeaponAttributes.ResistPoisonBonus = 10; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public NoxRangersHeavyCrossbow(Serial serial) : base(serial) + { + } - [Constructible] - public NoxRangersHeavyCrossbow() - { - Hue = 0x58C; - WeaponAttributes.HitLeechStam = 40; - Attributes.SpellChanneling = 1; - Attributes.WeaponSpeed = 30; - Attributes.WeaponDamage = 20; - WeaponAttributes.ResistPoisonBonus = 10; - } + public override int LabelNumber => 1063485; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - pois = 50; - phys = 50; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - fire = cold = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + pois = 50; + phys = 50; - public NoxRangersHeavyCrossbow( Serial serial ) : base( serial ) - { - } + fire = cold = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/OrcishVisage.cs b/Scripts/Items/Minor Artifacts/OrcishVisage.cs index 610d508a2..ad14fc104 100644 --- a/Scripts/Items/Minor Artifacts/OrcishVisage.cs +++ b/Scripts/Items/Minor Artifacts/OrcishVisage.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class OrcishVisage : OrcHelm - { - public override int LabelNumber => 1070691; + public class OrcishVisage : OrcHelm + { + [Constructible] + public OrcishVisage() + { + Hue = 0x592; + ArmorAttributes.SelfRepair = 3; + Attributes.BonusStr = 10; + Attributes.BonusStam = 5; + } - public override int BasePhysicalResistance => 8; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 5; + public OrcishVisage(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1070691; - [Constructible] - public OrcishVisage() - { - Hue = 0x592; - ArmorAttributes.SelfRepair = 3; - Attributes.BonusStr = 10; - Attributes.BonusStam = 5; - } + public override int BasePhysicalResistance => 8; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 5; - public OrcishVisage( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/PhillipsWoodenSteed.cs b/Scripts/Items/Minor Artifacts/PhillipsWoodenSteed.cs index 34d8bd4df..ca51b9c11 100644 --- a/Scripts/Items/Minor Artifacts/PhillipsWoodenSteed.cs +++ b/Scripts/Items/Minor Artifacts/PhillipsWoodenSteed.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class PhillipsWoodenSteed : MonsterStatuette - { - [Constructible] - public PhillipsWoodenSteed() : base( MonsterStatuetteType.PhillipsWoodenSteed ) - { - LootType = LootType.Regular; - } + public class PhillipsWoodenSteed : MonsterStatuette + { + [Constructible] + public PhillipsWoodenSteed() : base(MonsterStatuetteType.PhillipsWoodenSteed) + { + LootType = LootType.Regular; + } - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public PhillipsWoodenSteed(Serial serial) : base(serial) + { + } - public PhillipsWoodenSteed( Serial serial ) : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/PixieSwatter.cs b/Scripts/Items/Minor Artifacts/PixieSwatter.cs index 861f6efad..d43b47c1e 100644 --- a/Scripts/Items/Minor Artifacts/PixieSwatter.cs +++ b/Scripts/Items/Minor Artifacts/PixieSwatter.cs @@ -1,49 +1,50 @@ namespace Server.Items { - public class PixieSwatter : Scepter - { - public override int LabelNumber => 1070854; // Pixie Swatter + public class PixieSwatter : Scepter + { + [Constructible] + public PixieSwatter() + { + Hue = 0x8A; + WeaponAttributes.HitPoisonArea = 75; + Attributes.WeaponSpeed = 30; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + WeaponAttributes.UseBestSkill = 1; + WeaponAttributes.ResistFireBonus = 12; + WeaponAttributes.ResistEnergyBonus = 12; - [Constructible] - public PixieSwatter() - { - Hue = 0x8A; - WeaponAttributes.HitPoisonArea = 75; - Attributes.WeaponSpeed = 30; + Slayer = SlayerName.Fey; + } - WeaponAttributes.UseBestSkill = 1; - WeaponAttributes.ResistFireBonus = 12; - WeaponAttributes.ResistEnergyBonus = 12; + public PixieSwatter(Serial serial) : base(serial) + { + } - Slayer = SlayerName.Fey; - } + public override int LabelNumber => 1070854; // Pixie Swatter - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - fire = 100; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - cold = pois = phys = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + fire = 100; - public PixieSwatter( Serial serial ) : base( serial ) - { - } + cold = pois = phys = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/PolarBearMask.cs b/Scripts/Items/Minor Artifacts/PolarBearMask.cs index 5a99bc89c..2bcd2fc0d 100644 --- a/Scripts/Items/Minor Artifacts/PolarBearMask.cs +++ b/Scripts/Items/Minor Artifacts/PolarBearMask.cs @@ -1,51 +1,51 @@ namespace Server.Items { - public class PolarBearMask : BearMask - { - public override int LabelNumber => 1070637; + public class PolarBearMask : BearMask + { + [Constructible] + public PolarBearMask() + { + Hue = 0x481; - public override int BasePhysicalResistance => 15; - public override int BaseColdResistance => 21; + ClothingAttributes.SelfRepair = 3; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.RegenHits = 2; + Attributes.NightSight = 1; + } - [Constructible] - public PolarBearMask() - { - Hue = 0x481; + public PolarBearMask(Serial serial) : base(serial) + { + } - ClothingAttributes.SelfRepair = 3; + public override int LabelNumber => 1070637; - Attributes.RegenHits = 2; - Attributes.NightSight = 1; - } + public override int BasePhysicalResistance => 15; + public override int BaseColdResistance => 21; - public PolarBearMask( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 2 ); - } + writer.Write(2); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 2 ) - { - Resistances.Physical = 0; - Resistances.Cold = 0; - } + if (version < 2) + { + Resistances.Physical = 0; + Resistances.Cold = 0; + } - if ( Attributes.NightSight == 0 ) - Attributes.NightSight = 1; - } - } -} + if (Attributes.NightSight == 0) + Attributes.NightSight = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/SeahorseStatuette.cs b/Scripts/Items/Minor Artifacts/SeahorseStatuette.cs index 65995cd75..6c6673d36 100644 --- a/Scripts/Items/Minor Artifacts/SeahorseStatuette.cs +++ b/Scripts/Items/Minor Artifacts/SeahorseStatuette.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SeahorseStatuette : MonsterStatuette - { - [Constructible] - public SeahorseStatuette() : base( MonsterStatuetteType.Seahorse ) - { - LootType = LootType.Regular; + public class SeahorseStatuette : MonsterStatuette + { + [Constructible] + public SeahorseStatuette() : base(MonsterStatuetteType.Seahorse) + { + LootType = LootType.Regular; - Hue = Utility.RandomList( 0, 0x482, 0x489, 0x495, 0x4F2 ); - } + Hue = Utility.RandomList(0, 0x482, 0x489, 0x495, 0x4F2); + } - public SeahorseStatuette( Serial serial ) : base( serial ) - { - } + public SeahorseStatuette(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + writer.Write(0); + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ShieldOfInvulnerability.cs b/Scripts/Items/Minor Artifacts/ShieldOfInvulnerability.cs index ff876da0e..06b90c40f 100644 --- a/Scripts/Items/Minor Artifacts/ShieldOfInvulnerability.cs +++ b/Scripts/Items/Minor Artifacts/ShieldOfInvulnerability.cs @@ -1,50 +1,50 @@ namespace Server.Items { - public class ShieldOfInvulnerability : OrderShield - { - public override int LabelNumber => 1070693; + public class ShieldOfInvulnerability : OrderShield + { + [Constructible] + public ShieldOfInvulnerability() + { + Hue = 0x4F2; - public override int BasePhysicalResistance => 8; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + Attributes.SpellChanneling = 1; + Attributes.ReflectPhysical = 10; + Attributes.DefendChance = 15; + ArmorAttributes.LowerStatReq = 100; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public ShieldOfInvulnerability(Serial serial) : base(serial) + { + } - [Constructible] - public ShieldOfInvulnerability() - { - Hue = 0x4F2; + public override int LabelNumber => 1070693; - Attributes.SpellChanneling = 1; - Attributes.ReflectPhysical = 10; - Attributes.DefendChance = 15; - ArmorAttributes.LowerStatReq = 100; - } + public override int BasePhysicalResistance => 8; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - public override bool Validate( Mobile m ) - { - return true; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public ShieldOfInvulnerability( Serial serial ) : base( serial ) - { - } + public override bool Validate(Mobile m) + { + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/ShipModelOfTheHMSCape.cs b/Scripts/Items/Minor Artifacts/ShipModelOfTheHMSCape.cs index 885db4da1..1e2304232 100644 --- a/Scripts/Items/Minor Artifacts/ShipModelOfTheHMSCape.cs +++ b/Scripts/Items/Minor Artifacts/ShipModelOfTheHMSCape.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class ShipModelOfTheHMSCape : Item - { - public override int LabelNumber => 1063476; + public class ShipModelOfTheHMSCape : Item + { + [Constructible] + public ShipModelOfTheHMSCape() : base(0x14F3) + { + Hue = 0x37B; + } - [Constructible] - public ShipModelOfTheHMSCape() : base( 0x14F3 ) - { - Hue = 0x37B; - } + public ShipModelOfTheHMSCape(Serial serial) : base(serial) + { + } - public ShipModelOfTheHMSCape( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1063476; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/StaffOfPower.cs b/Scripts/Items/Minor Artifacts/StaffOfPower.cs index 3fa17786a..88e088b0e 100644 --- a/Scripts/Items/Minor Artifacts/StaffOfPower.cs +++ b/Scripts/Items/Minor Artifacts/StaffOfPower.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class StaffOfPower : BlackStaff - { - public override int LabelNumber => 1070692; + public class StaffOfPower : BlackStaff + { + [Constructible] + public StaffOfPower() + { + Hue = 0x4F2; + WeaponAttributes.MageWeapon = 15; + Attributes.SpellChanneling = 1; + Attributes.SpellDamage = 5; + Attributes.CastRecovery = 2; + Attributes.LowerManaCost = 5; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public StaffOfPower(Serial serial) : base(serial) + { + } - [Constructible] - public StaffOfPower() - { - Hue = 0x4F2; - WeaponAttributes.MageWeapon = 15; - Attributes.SpellChanneling = 1; - Attributes.SpellDamage = 5; - Attributes.CastRecovery = 2; - Attributes.LowerManaCost = 5; - } + public override int LabelNumber => 1070692; - public StaffOfPower( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/VioletCourage.cs b/Scripts/Items/Minor Artifacts/VioletCourage.cs index c2de9d0cf..bfcaf28e6 100644 --- a/Scripts/Items/Minor Artifacts/VioletCourage.cs +++ b/Scripts/Items/Minor Artifacts/VioletCourage.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class VioletCourage : FemalePlateChest - { - public override int LabelNumber => 1063471; + public class VioletCourage : FemalePlateChest + { + [Constructible] + public VioletCourage() + { + Hue = 0x486; + Attributes.Luck = 95; + Attributes.DefendChance = 15; + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + } - public override int BasePhysicalResistance => 14; - public override int BaseFireResistance => 12; - public override int BaseColdResistance => 12; - public override int BasePoisonResistance => 8; - public override int BaseEnergyResistance => 9; + public VioletCourage(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1063471; - [Constructible] - public VioletCourage() - { - Hue = 0x486; - Attributes.Luck = 95; - Attributes.DefendChance = 15; - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - } + public override int BasePhysicalResistance => 14; + public override int BaseFireResistance => 12; + public override int BaseColdResistance => 12; + public override int BasePoisonResistance => 8; + public override int BaseEnergyResistance => 9; - public VioletCourage( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Minor Artifacts/WrathOfTheDryad.cs b/Scripts/Items/Minor Artifacts/WrathOfTheDryad.cs index 24694bfc7..951f1e18b 100644 --- a/Scripts/Items/Minor Artifacts/WrathOfTheDryad.cs +++ b/Scripts/Items/Minor Artifacts/WrathOfTheDryad.cs @@ -1,45 +1,46 @@ namespace Server.Items { - public class WrathOfTheDryad : GnarledStaff - { - public override int LabelNumber => 1070853; // Wrath of the Dryad + public class WrathOfTheDryad : GnarledStaff + { + [Constructible] + public WrathOfTheDryad() + { + Hue = 0x29C; + WeaponAttributes.HitLeechMana = 50; + WeaponAttributes.HitLightning = 33; + Attributes.AttackChance = 15; + Attributes.WeaponDamage = 40; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public WrathOfTheDryad(Serial serial) : base(serial) + { + } - [Constructible] - public WrathOfTheDryad() - { - Hue = 0x29C; - WeaponAttributes.HitLeechMana = 50; - WeaponAttributes.HitLightning = 33; - Attributes.AttackChance = 15; - Attributes.WeaponDamage = 40; - } + public override int LabelNumber => 1070853; // Wrath of the Dryad - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - pois = 100; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - cold = fire = phys = nrgy = chaos = direct = 0; - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + pois = 100; - public WrathOfTheDryad( Serial serial ) : base( serial ) - { - } + cold = fire = phys = nrgy = chaos = direct = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/AcidSlime.cs b/Scripts/Items/Misc/AcidSlime.cs index aeca45243..32aac2724 100644 --- a/Scripts/Items/Misc/AcidSlime.cs +++ b/Scripts/Items/Misc/AcidSlime.cs @@ -1,97 +1,96 @@ using System; -using Server.Mobiles; using System.Collections.Generic; +using Server.Mobiles; namespace Server.Items { - public class AcidSlime : Item - { - private TimeSpan m_Duration; - private int m_MinDamage; - private int m_MaxDamage; - private DateTime m_Created; - private bool m_Drying; - private Timer m_Timer; + public class AcidSlime : Item + { + private DateTime m_Created; + private bool m_Drying; + private TimeSpan m_Duration; + private int m_MaxDamage; + private int m_MinDamage; + private Timer m_Timer; - [Constructible] - public AcidSlime() : this( TimeSpan.FromSeconds( 10.0 ), 5, 10 ) - { - } + [Constructible] + public AcidSlime() : this(TimeSpan.FromSeconds(10.0), 5, 10) + { + } - public override string DefaultName => "slime"; + [Constructible] + public AcidSlime(TimeSpan duration, int minDamage, int maxDamage) + : base(0x122A) + { + Hue = 0x3F; + Movable = false; + m_MinDamage = minDamage; + m_MaxDamage = maxDamage; + m_Created = DateTime.UtcNow; + m_Duration = duration; + m_Timer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromSeconds(1), OnTick); + } - [Constructible] - public AcidSlime( TimeSpan duration, int minDamage, int maxDamage ) - : base( 0x122A ) - { - Hue = 0x3F; - Movable = false; - m_MinDamage = minDamage; - m_MaxDamage = maxDamage; - m_Created = DateTime.UtcNow; - m_Duration = duration; - m_Timer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromSeconds( 1 ), OnTick ); - } + public AcidSlime(Serial serial) : base(serial) + { + } - public override void OnAfterDelete() - { - m_Timer?.Stop(); - } + public override string DefaultName => "slime"; - private void OnTick() - { - DateTime now = DateTime.UtcNow; - TimeSpan age = now - m_Created; + public override void OnAfterDelete() + { + m_Timer?.Stop(); + } - if ( age > m_Duration ) { - Delete(); - } else { - if ( !m_Drying && age > (m_Duration - age) ) - { - m_Drying = true; - ItemID = 0x122B; - } + private void OnTick() + { + DateTime now = DateTime.UtcNow; + TimeSpan age = now - m_Created; - List toDamage = new List(); + if (age > m_Duration) + { + Delete(); + } + else + { + if (!m_Drying && age > m_Duration - age) + { + m_Drying = true; + ItemID = 0x122B; + } - foreach( Mobile m in GetMobilesInRange( 0 ) ) - { - if ( m.Alive && !m.IsDeadBondedPet && (!(m is BaseCreature bc) || bc.Controlled || bc.Summoned) ) - { - toDamage.Add( m ); - } - } + List toDamage = new List(); - for ( int i = 0; i < toDamage.Count; i++ ) - Damage( toDamage[i] ); - } - } + foreach (Mobile m in GetMobilesInRange(0)) + if (m.Alive && !m.IsDeadBondedPet && (!(m is BaseCreature bc) || bc.Controlled || bc.Summoned)) + toDamage.Add(m); - public override bool OnMoveOver( Mobile m ) - { - Damage( m ); - return true; - } + for (int i = 0; i < toDamage.Count; i++) + Damage(toDamage[i]); + } + } - public void Damage ( Mobile m ) - { - int damage = Utility.RandomMinMax( m_MinDamage, m_MaxDamage ); - if ( Core.AOS ) - AOS.Damage( m, damage, 0, 0, 0, 100, 0 ); - else - m.Damage( damage ); - } + public override bool OnMoveOver(Mobile m) + { + Damage(m); + return true; + } - public AcidSlime( Serial serial ) : base( serial ) - { - } + public void Damage(Mobile m) + { + int damage = Utility.RandomMinMax(m_MinDamage, m_MaxDamage); + if (Core.AOS) + AOS.Damage(m, damage, 0, 0, 0, 100, 0); + else + m.Damage(damage); + } - public override void Serialize( GenericWriter writer ) - { - } + public override void Serialize(GenericWriter writer) + { + } - public override void Deserialize( GenericReader reader ) - { - } - } -} + public override void Deserialize(GenericReader reader) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/ArcaneGem.cs b/Scripts/Items/Misc/ArcaneGem.cs index 2f9a6d2b0..59e07bde4 100644 --- a/Scripts/Items/Misc/ArcaneGem.cs +++ b/Scripts/Items/Misc/ArcaneGem.cs @@ -3,202 +3,209 @@ using Server.Targeting; namespace Server.Items { - public class ArcaneGem : Item - { - public override string DefaultName => "arcane gem"; + public class ArcaneGem : Item + { + public const int DefaultArcaneHue = 2117; - [Constructible] - public ArcaneGem() : base( 0x1EA7 ) - { - Stackable = Core.ML; - Weight = 1.0; - } + [Constructible] + public ArcaneGem() : base(0x1EA7) + { + Stackable = Core.ML; + Weight = 1.0; + } - public ArcaneGem( Serial serial ) : base( serial ) - { - } + public ArcaneGem(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - from.BeginTarget( 2, false, TargetFlags.None, OnTarget ); - from.SendMessage( "What do you wish to use the gem on?" ); - } - } + public override string DefaultName => "arcane gem"; - public int GetChargesFor( Mobile m ) - { - int v = (int)(m.Skills[SkillName.Tailoring].Value / 5); + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + from.BeginTarget(2, false, TargetFlags.None, OnTarget); + from.SendMessage("What do you wish to use the gem on?"); + } + } - if ( v < 16 ) - return 16; - if ( v > 24 ) - return 24; + public int GetChargesFor(Mobile m) + { + int v = (int)(m.Skills[SkillName.Tailoring].Value / 5); - return v; - } + if (v < 16) + return 16; + if (v > 24) + return 24; - public const int DefaultArcaneHue = 2117; + return v; + } - public void OnTarget( Mobile from, object obj ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } + public void OnTarget(Mobile from, object obj) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - if ( obj is IArcaneEquip eq && eq is Item item ) - { - BaseClothing clothing = item as BaseClothing; - BaseArmor armor = item as BaseArmor; - BaseWeapon weapon = item as BaseWeapon; + if (obj is IArcaneEquip eq && eq is Item item) + { + BaseClothing clothing = item as BaseClothing; + BaseArmor armor = item as BaseArmor; + BaseWeapon weapon = item as BaseWeapon; - CraftResource resource = clothing?.Resource ?? armor?.Resource ?? weapon?.Resource ?? CraftResource.None; + CraftResource resource = clothing?.Resource ?? armor?.Resource ?? weapon?.Resource ?? CraftResource.None; - if ( !item.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } - if ( item.LootType == LootType.Blessed ) - { - from.SendMessage( "You can only use this on exceptionally crafted robes, thigh boots, cloaks, or leather gloves." ); - return; - } - if ( resource != CraftResource.None && resource != CraftResource.RegularLeather ) - { - from.SendLocalizedMessage( 1049690 ); // Arcane gems can not be used on that type of leather. - return; - } + if (!item.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - int charges = GetChargesFor( from ); + if (item.LootType == LootType.Blessed) + { + from.SendMessage( + "You can only use this on exceptionally crafted robes, thigh boots, cloaks, or leather gloves."); + return; + } - if ( eq.IsArcane ) - { - if ( eq.CurArcaneCharges >= eq.MaxArcaneCharges ) - { - from.SendMessage( "That item is already fully charged." ); - } - else - { - if ( eq.CurArcaneCharges <= 0 ) - item.Hue = DefaultArcaneHue; + if (resource != CraftResource.None && resource != CraftResource.RegularLeather) + { + from.SendLocalizedMessage(1049690); // Arcane gems can not be used on that type of leather. + return; + } - if ( (eq.CurArcaneCharges + charges) > eq.MaxArcaneCharges ) - eq.CurArcaneCharges = eq.MaxArcaneCharges; - else - eq.CurArcaneCharges += charges; + int charges = GetChargesFor(from); - from.SendMessage( "You recharge the item." ); - if ( Amount <= 1 ) - Delete(); - else Amount--; - } - } - else if ( from.Skills[SkillName.Tailoring].Value >= 80.0 ) - { - bool isExceptional = clothing?.Quality == ClothingQuality.Exceptional || - armor?.Quality == ArmorQuality.Exceptional || - weapon?.Quality == WeaponQuality.Exceptional; + if (eq.IsArcane) + { + if (eq.CurArcaneCharges >= eq.MaxArcaneCharges) + { + from.SendMessage("That item is already fully charged."); + } + else + { + if (eq.CurArcaneCharges <= 0) + item.Hue = DefaultArcaneHue; - if ( isExceptional ) - { - if (clothing != null) - { - clothing.Quality = ClothingQuality.Regular; - clothing.Crafter = from; - } - else if (armor != null) - { - armor.Quality = ArmorQuality.Regular; - armor.Crafter = from; - armor.PhysicalBonus = armor.FireBonus = armor.ColdBonus = armor.PoisonBonus = armor.EnergyBonus = 0; // Is there a method to remove bonuses? - } - else if (weapon != null) - { - weapon.Quality = WeaponQuality.Regular; - weapon.Crafter = from; - } + if (eq.CurArcaneCharges + charges > eq.MaxArcaneCharges) + eq.CurArcaneCharges = eq.MaxArcaneCharges; + else + eq.CurArcaneCharges += charges; - eq.CurArcaneCharges = eq.MaxArcaneCharges = charges; + from.SendMessage("You recharge the item."); + if (Amount <= 1) + Delete(); + else Amount--; + } + } + else if (from.Skills[SkillName.Tailoring].Value >= 80.0) + { + bool isExceptional = clothing?.Quality == ClothingQuality.Exceptional || + armor?.Quality == ArmorQuality.Exceptional || + weapon?.Quality == WeaponQuality.Exceptional; - item.Hue = DefaultArcaneHue; + if (isExceptional) + { + if (clothing != null) + { + clothing.Quality = ClothingQuality.Regular; + clothing.Crafter = from; + } + else if (armor != null) + { + armor.Quality = ArmorQuality.Regular; + armor.Crafter = from; + armor.PhysicalBonus = + armor.FireBonus = + armor.ColdBonus = + armor.PoisonBonus = armor.EnergyBonus = 0; // Is there a method to remove bonuses? + } + else if (weapon != null) + { + weapon.Quality = WeaponQuality.Regular; + weapon.Crafter = from; + } - from.SendMessage( "You enhance the item with your gem." ); - if ( Amount <= 1 ) - Delete(); - else Amount--; - } - else - { - from.SendMessage( "Only exceptional items can be enhanced with the gem." ); - } - } - else - { - from.SendMessage( "You do not have enough skill in tailoring to enhance the item." ); - } - } - else - { - from.SendMessage( "You can only use this on exceptionally crafted robes, thigh boots, cloaks, or leather gloves." ); - } - } + eq.CurArcaneCharges = eq.MaxArcaneCharges = charges; - public static bool ConsumeCharges( Mobile from, int amount ) - { - List items = from.Items; - int avail = 0; + item.Hue = DefaultArcaneHue; - for ( int i = 0; i < items.Count; ++i ) - { - Item obj = items[i]; + from.SendMessage("You enhance the item with your gem."); + if (Amount <= 1) + Delete(); + else Amount--; + } + else + { + from.SendMessage("Only exceptional items can be enhanced with the gem."); + } + } + else + { + from.SendMessage("You do not have enough skill in tailoring to enhance the item."); + } + } + else + { + from.SendMessage( + "You can only use this on exceptionally crafted robes, thigh boots, cloaks, or leather gloves."); + } + } - if ( obj is IArcaneEquip eq && eq.IsArcane ) - avail += eq.CurArcaneCharges; - } + public static bool ConsumeCharges(Mobile from, int amount) + { + List items = from.Items; + int avail = 0; - if ( avail < amount ) - return false; + for (int i = 0; i < items.Count; ++i) + { + Item obj = items[i]; - for ( int i = 0; i < items.Count; ++i ) - { - Item obj = items[i]; + if (obj is IArcaneEquip eq && eq.IsArcane) + avail += eq.CurArcaneCharges; + } - if ( obj is IArcaneEquip eq && eq.IsArcane ) - { - if ( eq.CurArcaneCharges > amount ) - { - eq.CurArcaneCharges -= amount; - break; - } + if (avail < amount) + return false; - amount -= eq.CurArcaneCharges; - eq.CurArcaneCharges = 0; - } - } + for (int i = 0; i < items.Count; ++i) + { + Item obj = items[i]; - return true; - } + if (obj is IArcaneEquip eq && eq.IsArcane) + { + if (eq.CurArcaneCharges > amount) + { + eq.CurArcaneCharges -= amount; + break; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + amount -= eq.CurArcaneCharges; + eq.CurArcaneCharges = 0; + } + } - writer.Write( (int) 0 ); - } + return true; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/BankCheck.cs b/Scripts/Items/Misc/BankCheck.cs index 118ec5e32..154ed86dd 100644 --- a/Scripts/Items/Misc/BankCheck.cs +++ b/Scripts/Items/Misc/BankCheck.cs @@ -1,259 +1,250 @@ using System; using System.Globalization; using Server.Accounting; +using Server.Engines.Quests; +using Server.Engines.Quests.Haven; +using Server.Engines.Quests.Necro; using Server.Mobiles; using Server.Network; -using Necro = Server.Engines.Quests.Necro; -using Haven = Server.Engines.Quests.Haven; +using CashBankCheckObjective = Server.Engines.Quests.Necro.CashBankCheckObjective; namespace Server.Items { - public class BankCheck : Item - { - private int m_Worth; + public class BankCheck : Item + { + private int m_Worth; - [CommandProperty( AccessLevel.GameMaster )] - public int Worth - { - get => m_Worth; - set{ m_Worth = value; InvalidateProperties(); } - } + public BankCheck(Serial serial) : base(serial) + { + } - public BankCheck( Serial serial ) : base( serial ) - { - } + [Constructible] + public BankCheck(int worth) : base(0x14F0) + { + Weight = 1.0; + Hue = 0x34; + LootType = LootType.Blessed; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Worth = worth; + } - writer.Write( (int) 0 ); // version + [CommandProperty(AccessLevel.GameMaster)] + public int Worth + { + get => m_Worth; + set + { + m_Worth = value; + InvalidateProperties(); + } + } - writer.Write( (int) m_Worth ); - } + public override bool DisplayLootType => Core.AOS; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; + public override int LabelNumber => 1041361; // A bank check - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - switch ( version ) - { - case 0: - { - m_Worth = reader.ReadInt(); - break; - } - } - } + writer.Write(0); // version - [Constructible] - public BankCheck( int worth ) : base( 0x14F0 ) - { - Weight = 1.0; - Hue = 0x34; - LootType = LootType.Blessed; + writer.Write(m_Worth); + } - m_Worth = worth; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; - public override bool DisplayLootType => Core.AOS; + int version = reader.ReadInt(); - public override int LabelNumber => 1041361; // A bank check + switch (version) + { + case 0: + { + m_Worth = reader.ReadInt(); + break; + } + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - string worth; + string worth; - if ( Core.ML ) - worth = m_Worth.ToString( "N0", CultureInfo.GetCultureInfo( "en-US" ) ); - else - worth = m_Worth.ToString(); + if (Core.ML) + worth = m_Worth.ToString("N0", CultureInfo.GetCultureInfo("en-US")); + else + worth = m_Worth.ToString(); - list.Add( 1060738, worth ); // value: ~1_val~ - } + list.Add(1060738, worth); // value: ~1_val~ + } #if NEWPARENT - public override void OnAdded(IEntity parent) + public override void OnAdded(IEntity parent) #else public override void OnAdded(object parent) #endif - { - base.OnAdded(parent); + { + base.OnAdded(parent); - if (!AccountGold.Enabled) - { - return; - } + if (!AccountGold.Enabled) return; - Mobile owner = null; - SecureTradeInfo tradeInfo = null; + Mobile owner = null; + SecureTradeInfo tradeInfo = null; - Container root = parent as Container; + Container root = parent as Container; - while (root?.Parent is Container) - { - root = (Container)root.Parent; - } + while (root?.Parent is Container) root = (Container)root.Parent; - parent = root ?? parent; + parent = root ?? parent; - if (parent is SecureTradeContainer trade && AccountGold.ConvertOnTrade) - { - if (trade.Trade.From.Container == trade) - { - tradeInfo = trade.Trade.From; - owner = tradeInfo.Mobile; - } - else if (trade.Trade.To.Container == trade) - { - tradeInfo = trade.Trade.To; - owner = tradeInfo.Mobile; - } - } - else if (parent is BankBox box && AccountGold.ConvertOnBank) - { - owner = box.Owner; - } + if (parent is SecureTradeContainer trade && AccountGold.ConvertOnTrade) + { + if (trade.Trade.From.Container == trade) + { + tradeInfo = trade.Trade.From; + owner = tradeInfo.Mobile; + } + else if (trade.Trade.To.Container == trade) + { + tradeInfo = trade.Trade.To; + owner = tradeInfo.Mobile; + } + } + else if (parent is BankBox box && AccountGold.ConvertOnBank) + { + owner = box.Owner; + } - if (owner?.Account == null || !owner.Account.DepositGold(Worth)) - { - return; - } + if (owner?.Account == null || !owner.Account.DepositGold(Worth)) return; - if (tradeInfo != null) - { - if (owner.NetState != null && !owner.NetState.NewSecureTrading) - { - int plat = Math.DivRem(Worth, AccountGold.CurrencyThreshold, out var gold); + if (tradeInfo != null) + { + if (owner.NetState != null && !owner.NetState.NewSecureTrading) + { + int plat = Math.DivRem(Worth, AccountGold.CurrencyThreshold, out int gold); - tradeInfo.Plat += plat; - tradeInfo.Gold += gold; - } + tradeInfo.Plat += plat; + tradeInfo.Gold += gold; + } - tradeInfo.VirtualCheck?.UpdateTrade(tradeInfo.Mobile); - } + tradeInfo.VirtualCheck?.UpdateTrade(tradeInfo.Mobile); + } - owner.SendLocalizedMessage(1042763, Worth.ToString("#,0")); + owner.SendLocalizedMessage(1042763, Worth.ToString("#,0")); - Delete(); + Delete(); - ((Container)parent).UpdateTotals(); - } + ((Container)parent).UpdateTotals(); + } - public override void OnSingleClick(Mobile from) - { - from.Send( - new MessageLocalizedAffix( - Serial, - ItemID, - MessageType.Label, - 0x3B2, - 3, - 1041361, - "", - AffixType.Append, - string.Concat(" ", m_Worth.ToString()), - "")); // A bank check: - } + public override void OnSingleClick(Mobile from) + { + from.Send( + new MessageLocalizedAffix( + Serial, + ItemID, + MessageType.Label, + 0x3B2, + 3, + 1041361, + "", + AffixType.Append, + string.Concat(" ", m_Worth.ToString()), + "")); // A bank check: + } - public override void OnDoubleClick(Mobile from) - { - // This probably isn't OSI accurate, but we can't just make the quests redundant. - // Double-clicking the BankCheck in your pack will now credit your account. + public override void OnDoubleClick(Mobile from) + { + // This probably isn't OSI accurate, but we can't just make the quests redundant. + // Double-clicking the BankCheck in your pack will now credit your account. - var box = AccountGold.Enabled ? from.Backpack : from.FindBankNoCreate(); + Container box = AccountGold.Enabled ? from.Backpack : from.FindBankNoCreate(); - if (box == null || !IsChildOf(box)) - { - from.SendLocalizedMessage(AccountGold.Enabled ? 1080058 : 1047026); - // This must be in your backpack to use it. : That must be in your bank box to use it. - return; - } + if (box == null || !IsChildOf(box)) + { + from.SendLocalizedMessage(AccountGold.Enabled ? 1080058 : 1047026); + // This must be in your backpack to use it. : That must be in your bank box to use it. + return; + } - Delete(); + Delete(); - var deposited = 0; - var toAdd = m_Worth; + int deposited = 0; + int toAdd = m_Worth; - if (AccountGold.Enabled && from.Account != null && from.Account.DepositGold(toAdd)) - { - deposited = toAdd; - toAdd = 0; - } + if (AccountGold.Enabled && from.Account != null && from.Account.DepositGold(toAdd)) + { + deposited = toAdd; + toAdd = 0; + } - if (toAdd > 0) - { - Gold gold; + if (toAdd > 0) + { + Gold gold; - while (toAdd > 60000) - { - gold = new Gold(60000); + while (toAdd > 60000) + { + gold = new Gold(60000); - if (box.TryDropItem(from, gold, false)) - { - toAdd -= 60000; - deposited += 60000; - } - else - { - gold.Delete(); + if (box.TryDropItem(from, gold, false)) + { + toAdd -= 60000; + deposited += 60000; + } + else + { + gold.Delete(); - from.AddToBackpack(new BankCheck(toAdd)); - toAdd = 0; + from.AddToBackpack(new BankCheck(toAdd)); + toAdd = 0; - break; - } - } + break; + } + } - if (toAdd > 0) - { - gold = new Gold(toAdd); + if (toAdd > 0) + { + gold = new Gold(toAdd); - if (box.TryDropItem(from, gold, false)) - { - deposited += toAdd; - } - else - { - gold.Delete(); + if (box.TryDropItem(from, gold, false)) + { + deposited += toAdd; + } + else + { + gold.Delete(); - from.AddToBackpack(new BankCheck(toAdd)); - } - } - } + from.AddToBackpack(new BankCheck(toAdd)); + } + } + } - // Gold was deposited in your account: - from.SendLocalizedMessage(1042672, true, deposited.ToString("#,0")); + // Gold was deposited in your account: + from.SendLocalizedMessage(1042672, true, deposited.ToString("#,0")); - if (from is PlayerMobile pm) - { - var qs = pm.Quest; + if (from is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; - if (qs is Necro.DarkTidesQuest) - { - var obj = qs.FindObjective(typeof(Necro.CashBankCheckObjective)); + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(CashBankCheckObjective)); - if (obj != null && !obj.Completed) - { - obj.Complete(); - } - } + if (obj != null && !obj.Completed) obj.Complete(); + } - if (qs is Haven.UzeraanTurmoilQuest) - { - var obj = qs.FindObjective(typeof(Haven.CashBankCheckObjective)); + if (qs is UzeraanTurmoilQuest) + { + QuestObjective obj = qs.FindObjective(typeof(Engines.Quests.Haven.CashBankCheckObjective)); - if (obj != null && !obj.Completed) - { - obj.Complete(); - } - } - } - } - } -} + if (obj != null && !obj.Completed) obj.Complete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Bedlam/GlobOfMonstreousInterredGrizzle.cs b/Scripts/Items/Misc/Bedlam/GlobOfMonstreousInterredGrizzle.cs index 351d6e92f..6afd1d2b1 100644 --- a/Scripts/Items/Misc/Bedlam/GlobOfMonstreousInterredGrizzle.cs +++ b/Scripts/Items/Misc/Bedlam/GlobOfMonstreousInterredGrizzle.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class GlobOfMonstreousInterredGrizzle : Item - { - public override int LabelNumber => 1072117; // Glob of Monsterous Interred Grizzle + public class GlobOfMonstreousInterredGrizzle : Item + { + [Constructible] + public GlobOfMonstreousInterredGrizzle() : base(0x2F3) + { + } - [Constructible] - public GlobOfMonstreousInterredGrizzle() : base( 0x2F3 ) - { - } + public GlobOfMonstreousInterredGrizzle(Serial serial) : base(serial) + { + } - public GlobOfMonstreousInterredGrizzle( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072117; // Glob of Monsterous Interred Grizzle - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Bedlam/GrizzledSkullCollection.cs b/Scripts/Items/Misc/Bedlam/GrizzledSkullCollection.cs index b5a67a13b..55b977cbd 100644 --- a/Scripts/Items/Misc/Bedlam/GrizzledSkullCollection.cs +++ b/Scripts/Items/Misc/Bedlam/GrizzledSkullCollection.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class GrizzledSkullCollection : Item - { - public override int LabelNumber => 1072116; // Grizzled Skull collection + public class GrizzledSkullCollection : Item + { + [Constructible] + public GrizzledSkullCollection() : base(0x21FC) + { + } - [Constructible] - public GrizzledSkullCollection() : base( 0x21FC ) - { - } + public GrizzledSkullCollection(Serial serial) : base(serial) + { + } - public GrizzledSkullCollection( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072116; // Grizzled Skull collection - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Bedlam/MonsterousInterredGrizzleMaggots.cs b/Scripts/Items/Misc/Bedlam/MonsterousInterredGrizzleMaggots.cs index 764b54491..867aa998a 100644 --- a/Scripts/Items/Misc/Bedlam/MonsterousInterredGrizzleMaggots.cs +++ b/Scripts/Items/Misc/Bedlam/MonsterousInterredGrizzleMaggots.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class MonsterousInterredGrizzleMaggots : Item - { - public override int LabelNumber => 1075090; // Monsterous Interred Grizzle Maggots + public class MonsterousInterredGrizzleMaggots : Item + { + [Constructible] + public MonsterousInterredGrizzleMaggots() : base(0x2633) + { + } - [Constructible] - public MonsterousInterredGrizzleMaggots() : base( 0x2633 ) - { - } + public MonsterousInterredGrizzleMaggots(Serial serial) : base(serial) + { + } - public MonsterousInterredGrizzleMaggots( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075090; // Monsterous Interred Grizzle Maggots - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Bedlam/ResolvesBridle.cs b/Scripts/Items/Misc/Bedlam/ResolvesBridle.cs index 4da1bded8..ffccc95d6 100644 --- a/Scripts/Items/Misc/Bedlam/ResolvesBridle.cs +++ b/Scripts/Items/Misc/Bedlam/ResolvesBridle.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class ResolvesBridle : Item - { - public override int LabelNumber => 1074761; // Resolve's Bridle + public class ResolvesBridle : Item + { + [Constructible] + public ResolvesBridle() : base(0x1374) + { + } - [Constructible] - public ResolvesBridle() : base( 0x1374 ) - { - } + public ResolvesBridle(Serial serial) : base(serial) + { + } - public ResolvesBridle( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074761; // Resolve's Bridle - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Bedlam/TombstoneOfTheDamned.cs b/Scripts/Items/Misc/Bedlam/TombstoneOfTheDamned.cs index 8dc31fba1..9301bc03f 100644 --- a/Scripts/Items/Misc/Bedlam/TombstoneOfTheDamned.cs +++ b/Scripts/Items/Misc/Bedlam/TombstoneOfTheDamned.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class TombstoneOfTheDamned : Item - { - public override int LabelNumber => 1072123; // Tombstone of the Damned + public class TombstoneOfTheDamned : Item + { + [Constructible] + public TombstoneOfTheDamned() : base(Utility.RandomMinMax(0xED7, 0xEDE)) + { + } - [Constructible] - public TombstoneOfTheDamned() : base( Utility.RandomMinMax( 0xED7, 0xEDE ) ) - { - } + public TombstoneOfTheDamned(Serial serial) : base(serial) + { + } - public TombstoneOfTheDamned( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072123; // Tombstone of the Damned - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Beeswax.cs b/Scripts/Items/Misc/Beeswax.cs index 0e7e125fe..0a0510209 100644 --- a/Scripts/Items/Misc/Beeswax.cs +++ b/Scripts/Items/Misc/Beeswax.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class Beeswax : Item - { - [Constructible] - public Beeswax() : this( 1 ) - { - } + public class Beeswax : Item + { + [Constructible] + public Beeswax() : this(1) + { + } - [Constructible] - public Beeswax( int amount ) : base( 0x1422 ) - { - Weight = 1.0; - Stackable = true; - Amount = amount; - } + [Constructible] + public Beeswax(int amount) : base(0x1422) + { + Weight = 1.0; + Stackable = true; + Amount = amount; + } - public Beeswax( Serial serial ) : base( serial ) - { - } + public Beeswax(Serial serial) : base(serial) + { + } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/AbscessTail.cs b/Scripts/Items/Misc/Blighted Grove/AbscessTail.cs index f891cb701..ba81c0a06 100644 --- a/Scripts/Items/Misc/Blighted Grove/AbscessTail.cs +++ b/Scripts/Items/Misc/Blighted Grove/AbscessTail.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class AbscessTail : Item - { - public override int LabelNumber => 1074231; // Abscess' Tail + public class AbscessTail : Item + { + [Constructible] + public AbscessTail() : base(0x1A9D) + { + LootType = LootType.Blessed; + Hue = 0x51D; // TODO check + } - [Constructible] - public AbscessTail() : base( 0x1A9D ) - { - LootType = LootType.Blessed; - Hue = 0x51D; // TODO check - } + public AbscessTail(Serial serial) : base(serial) + { + } - public AbscessTail( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074231; // Abscess' Tail - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/CoilsFang.cs b/Scripts/Items/Misc/Blighted Grove/CoilsFang.cs index c2b26dae7..b7dfb0ab8 100644 --- a/Scripts/Items/Misc/Blighted Grove/CoilsFang.cs +++ b/Scripts/Items/Misc/Blighted Grove/CoilsFang.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class CoilsFang : Item - { - public override int LabelNumber => 1074229; // Coil's Fang + public class CoilsFang : Item + { + [Constructible] + public CoilsFang() : base(0x10E8) + { + LootType = LootType.Blessed; + Hue = 0x487; + } - [Constructible] - public CoilsFang() : base( 0x10E8 ) - { - LootType = LootType.Blessed; - Hue = 0x487; - } + public CoilsFang(Serial serial) : base(serial) + { + } - public CoilsFang( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074229; // Coil's Fang - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/EternallyCorruptTree.cs b/Scripts/Items/Misc/Blighted Grove/EternallyCorruptTree.cs index 6bfb51946..737b2dc80 100644 --- a/Scripts/Items/Misc/Blighted Grove/EternallyCorruptTree.cs +++ b/Scripts/Items/Misc/Blighted Grove/EternallyCorruptTree.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class EternallyCorruptTree : Item - { - public override int LabelNumber => 1072093; // Eternally Corrupt Tree + public class EternallyCorruptTree : Item + { + [Constructible] + public EternallyCorruptTree() : base(0x20FA) + { + Hue = Utility.RandomMinMax(0x899, 0x8B0); + } - [Constructible] - public EternallyCorruptTree() : base( 0x20FA ) - { - Hue = Utility.RandomMinMax( 0x899, 0x8B0 ); - } + public EternallyCorruptTree(Serial serial) : base(serial) + { + } - public EternallyCorruptTree( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072093; // Eternally Corrupt Tree - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/HydraScale.cs b/Scripts/Items/Misc/Blighted Grove/HydraScale.cs index e07fba6ef..201ca6075 100644 --- a/Scripts/Items/Misc/Blighted Grove/HydraScale.cs +++ b/Scripts/Items/Misc/Blighted Grove/HydraScale.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class HydraScale : Item - { - public override int LabelNumber => 1074760; // A hydra scale. + public class HydraScale : Item + { + [Constructible] + public HydraScale() : base(0x26B4) + { + LootType = LootType.Blessed; + Hue = 0xC2; // TODO check + } - [Constructible] - public HydraScale() : base( 0x26B4 ) - { - LootType = LootType.Blessed; - Hue = 0xC2; // TODO check - } + public HydraScale(Serial serial) : base(serial) + { + } - public HydraScale( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074760; // A hydra scale. - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/MelisandesFermentedWine.cs b/Scripts/Items/Misc/Blighted Grove/MelisandesFermentedWine.cs index 25e32d34e..88a64aff3 100644 --- a/Scripts/Items/Misc/Blighted Grove/MelisandesFermentedWine.cs +++ b/Scripts/Items/Misc/Blighted Grove/MelisandesFermentedWine.cs @@ -1,49 +1,47 @@ namespace Server.Items { - public class MelisandesFermentedWine : GreaterExplosionPotion - { - public override int LabelNumber => 1072114; // Melisande's Fermented Wine + public class MelisandesFermentedWine : GreaterExplosionPotion + { + [Constructible] + public MelisandesFermentedWine() + { + Stackable = false; + ItemID = 0x99B; + Hue = Utility.RandomList(0xB, 0xF, 0x48D); // TODO update + } - [Constructible] - public MelisandesFermentedWine() - { - Stackable = false; - ItemID = 0x99B; - Hue = Utility.RandomList( 0xB, 0xF, 0x48D ); // TODO update - } + public MelisandesFermentedWine(Serial serial) : base(serial) + { + } - public MelisandesFermentedWine( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072114; // Melisande's Fermented Wine - public override void Drink( Mobile from ) - { - if ( MondainsLegacy.CheckML( from ) ) - base.Drink( from ); - } + public override void Drink(Mobile from) + { + if (MondainsLegacy.CheckML(from)) + base.Drink(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1074502 ); // It looks explosive. - list.Add( 1075085 ); // Requirement: Mondain's Legacy - } + list.Add(1074502); // It looks explosive. + list.Add(1075085); // Requirement: Mondain's Legacy + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + writer.Write(0); // version + } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/MelisandesHairDye.cs b/Scripts/Items/Misc/Blighted Grove/MelisandesHairDye.cs index baed7bfc7..a654d9f59 100644 --- a/Scripts/Items/Misc/Blighted Grove/MelisandesHairDye.cs +++ b/Scripts/Items/Misc/Blighted Grove/MelisandesHairDye.cs @@ -2,87 +2,94 @@ using Server.Gumps; namespace Server.Items { - public class MelisandesHairDye : Item - { - public override int LabelNumber => 1041088; // Hair Dye + public class MelisandesHairDye : Item + { + [Constructible] + public MelisandesHairDye() : base(0xEFF) + { + Hue = Utility.RandomMinMax(0x47E, 0x499); + } - [Constructible] - public MelisandesHairDye() : base( 0xEFF ) - { - Hue = Utility.RandomMinMax( 0x47E, 0x499 ); - } + public MelisandesHairDye(Serial serial) : base(serial) + { + } - public MelisandesHairDye( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041088; // Hair Dye - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - if ( MondainsLegacy.CheckML( from ) ) - from.SendGump( new ConfirmGump( this ) ); - } - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + if (MondainsLegacy.CheckML(from)) + from.SendGump(new ConfirmGump(this)); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1075085 ); // Requirement: Mondain's Legacy - } + list.Add(1075085); // Requirement: Mondain's Legacy + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - private class ConfirmGump : BaseConfirmGump - { - public override int TitleNumber => 1074395; //
Use Permanent Hair Dye
- public override int LabelNumber => 1074396; // This special hair dye is made of a unique mixture of leaves, permanently changing one's hair color until another dye is used. + private class ConfirmGump : BaseConfirmGump + { + private Item m_Item; - private Item m_Item; + public ConfirmGump(Item item) + { + m_Item = item; + } - public ConfirmGump( Item item ) - { - m_Item = item; - } + public override int TitleNumber => 1074395; //
Use Permanent Hair Dye
- public override void Confirm( Mobile from ) - { - if ( m_Item != null && !m_Item.Deleted && m_Item.IsChildOf( from.Backpack ) ) - { - if ( from.HairItemID != 0 ) - { - from.HairHue = m_Item.Hue; - from.PlaySound( 0x240 ); - from.SendLocalizedMessage( 502622 ); // You dye your hair. - m_Item.Delete(); - } - else - from.SendLocalizedMessage( 502623 ); // You have no hair to dye and you cannot use this. - } - else - from.SendLocalizedMessage( 1073461 ); // You don't have enough dye. - } + public override int LabelNumber => + 1074396; // This special hair dye is made of a unique mixture of leaves, permanently changing one's hair color until another dye is used. - public override void Refuse( Mobile from ) - { - from.SendLocalizedMessage( 502620 ); // You decide not to dye your hair. - } - } - } -} + public override void Confirm(Mobile from) + { + if (m_Item != null && !m_Item.Deleted && m_Item.IsChildOf(from.Backpack)) + { + if (from.HairItemID != 0) + { + from.HairHue = m_Item.Hue; + from.PlaySound(0x240); + from.SendLocalizedMessage(502622); // You dye your hair. + m_Item.Delete(); + } + else + { + from.SendLocalizedMessage(502623); // You have no hair to dye and you cannot use this. + } + } + else + { + from.SendLocalizedMessage(1073461); // You don't have enough dye. + } + } + public override void Refuse(Mobile from) + { + from.SendLocalizedMessage(502620); // You decide not to dye your hair. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/SalivasFeather.cs b/Scripts/Items/Misc/Blighted Grove/SalivasFeather.cs index ad20805e0..031d9b78e 100644 --- a/Scripts/Items/Misc/Blighted Grove/SalivasFeather.cs +++ b/Scripts/Items/Misc/Blighted Grove/SalivasFeather.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class SalivasFeather : Item - { - public override int LabelNumber => 1074234; // Saliva's Feather + public class SalivasFeather : Item + { + [Constructible] + public SalivasFeather() : base(0x1020) + { + LootType = LootType.Blessed; + Hue = 0x5C; + } - [Constructible] - public SalivasFeather() : base( 0x1020 ) - { - LootType = LootType.Blessed; - Hue = 0x5C; - } + public SalivasFeather(Serial serial) : base(serial) + { + } - public SalivasFeather( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074234; // Saliva's Feather - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/SamplesOfCorruptedWater.cs b/Scripts/Items/Misc/Blighted Grove/SamplesOfCorruptedWater.cs index 48f01ccd7..7a71fa60f 100644 --- a/Scripts/Items/Misc/Blighted Grove/SamplesOfCorruptedWater.cs +++ b/Scripts/Items/Misc/Blighted Grove/SamplesOfCorruptedWater.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class SamplesOfCorruptedWater : Item - { - public override int LabelNumber => 1074999; // samples of corrupted water + public class SamplesOfCorruptedWater : Item + { + [Constructible] + public SamplesOfCorruptedWater() : base(0xEFE) + { + LootType = LootType.Blessed; + } - [Constructible] - public SamplesOfCorruptedWater() : base( 0xEFE ) - { - LootType = LootType.Blessed; - } + public SamplesOfCorruptedWater(Serial serial) : base(serial) + { + } - public SamplesOfCorruptedWater( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074999; // samples of corrupted water - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/TaintedSeeds.cs b/Scripts/Items/Misc/Blighted Grove/TaintedSeeds.cs index c0229c229..e1c4ae794 100644 --- a/Scripts/Items/Misc/Blighted Grove/TaintedSeeds.cs +++ b/Scripts/Items/Misc/Blighted Grove/TaintedSeeds.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class TaintedSeeds : Item - { - public override int LabelNumber => 1074233; // Tainted Seeds + public class TaintedSeeds : Item + { + [Constructible] + public TaintedSeeds() : base(0xDFA) + { + LootType = LootType.Blessed; + Hue = 0x48; // TODO check + } - [Constructible] - public TaintedSeeds() : base( 0xDFA ) - { - LootType = LootType.Blessed; - Hue = 0x48; // TODO check - } + public TaintedSeeds(Serial serial) : base(serial) + { + } - public TaintedSeeds( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074233; // Tainted Seeds - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/ThorvaldsMedallion.cs b/Scripts/Items/Misc/Blighted Grove/ThorvaldsMedallion.cs index 060ce34ba..a117f0763 100644 --- a/Scripts/Items/Misc/Blighted Grove/ThorvaldsMedallion.cs +++ b/Scripts/Items/Misc/Blighted Grove/ThorvaldsMedallion.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class ThorvaldsMedallion : Item - { - public override int LabelNumber => 1074232; // Thorvald's Medallion + public class ThorvaldsMedallion : Item + { + [Constructible] + public ThorvaldsMedallion() : base(0x2AAA) + { + LootType = LootType.Blessed; + Hue = 0x47F; // TODO check + } - [Constructible] - public ThorvaldsMedallion() : base( 0x2AAA ) - { - LootType = LootType.Blessed; - Hue = 0x47F; // TODO check - } + public ThorvaldsMedallion(Serial serial) : base(serial) + { + } - public ThorvaldsMedallion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074232; // Thorvald's Medallion - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blighted Grove/ThrashersTail.cs b/Scripts/Items/Misc/Blighted Grove/ThrashersTail.cs index 62df6431b..9aabc3f1c 100644 --- a/Scripts/Items/Misc/Blighted Grove/ThrashersTail.cs +++ b/Scripts/Items/Misc/Blighted Grove/ThrashersTail.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class ThrashersTail : Item - { - public override int LabelNumber => 1074230; // Thrasher's Tail + public class ThrashersTail : Item + { + [Constructible] + public ThrashersTail() : base(0x1A9D) + { + LootType = LootType.Blessed; + Hue = 0x455; + } - [Constructible] - public ThrashersTail() : base( 0x1A9D ) - { - LootType = LootType.Blessed; - Hue = 0x455; - } + public ThrashersTail(Serial serial) : base(serial) + { + } - public ThrashersTail( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074230; // Thrasher's Tail - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blocker.cs b/Scripts/Items/Misc/Blocker.cs index 11fdae665..f0099f728 100644 --- a/Scripts/Items/Misc/Blocker.cs +++ b/Scripts/Items/Misc/Blocker.cs @@ -2,103 +2,104 @@ using Server.Network; namespace Server.Items { - public class Blocker : Item - { - public override int LabelNumber => 503057; // Impassable! + public class Blocker : Item + { + [Constructible] + public Blocker() : base(0x21A4) + { + Movable = false; + } - [Constructible] - public Blocker() : base( 0x21A4 ) - { - Movable = false; - } + public Blocker(Serial serial) : base(serial) + { + } - public Blocker( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 503057; // Impassable! - protected override Packet GetWorldPacketFor( NetState state ) { - Mobile mob = state.Mobile; + protected override Packet GetWorldPacketFor(NetState state) + { + Mobile mob = state.Mobile; - if ( mob != null && mob.AccessLevel >= AccessLevel.GameMaster ) - return new GMItemPacket( this ); + if (mob != null && mob.AccessLevel >= AccessLevel.GameMaster) + return new GMItemPacket(this); - return base.GetWorldPacketFor( state ); - } + return base.GetWorldPacketFor(state); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public sealed class GMItemPacket : Packet - { - public GMItemPacket( Item item ) : base( 0x1A ) - { - EnsureCapacity( 20 ); + public sealed class GMItemPacket : Packet + { + public GMItemPacket(Item item) : base(0x1A) + { + EnsureCapacity(20); - // 14 base length - // +2 - Amount - // +2 - Hue - // +1 - Flags + // 14 base length + // +2 - Amount + // +2 - Hue + // +1 - Flags - uint serial = (uint)item.Serial.Value; - int itemID = 0x1183; - int amount = item.Amount; - Point3D loc = item.Location; - int x = loc.X; - int y = loc.Y; - int hue = item.Hue; - int flags = item.GetPacketFlags(); - int direction = (int)item.Direction; + uint serial = (uint)item.Serial.Value; + int itemID = 0x1183; + int amount = item.Amount; + Point3D loc = item.Location; + int x = loc.X; + int y = loc.Y; + int hue = item.Hue; + int flags = item.GetPacketFlags(); + int direction = (int)item.Direction; - if ( amount != 0 ) - serial |= 0x80000000; - else - serial &= 0x7FFFFFFF; + if (amount != 0) + serial |= 0x80000000; + else + serial &= 0x7FFFFFFF; - m_Stream.Write( (uint) serial ); - m_Stream.Write( (short) (itemID & 0x7FFF) ); + m_Stream.Write(serial); + m_Stream.Write((short)(itemID & 0x7FFF)); - if ( amount != 0 ) - m_Stream.Write( (short) amount ); + if (amount != 0) + m_Stream.Write((short)amount); - x &= 0x7FFF; + x &= 0x7FFF; - if ( direction != 0 ) - x |= 0x8000; + if (direction != 0) + x |= 0x8000; - m_Stream.Write( (short) x ); + m_Stream.Write((short)x); - y &= 0x3FFF; + y &= 0x3FFF; - if ( hue != 0 ) - y |= 0x8000; + if (hue != 0) + y |= 0x8000; - if ( flags != 0 ) - y |= 0x4000; + if (flags != 0) + y |= 0x4000; - m_Stream.Write( (short) y ); + m_Stream.Write((short)y); - if ( direction != 0 ) - m_Stream.Write( (byte) direction ); + if (direction != 0) + m_Stream.Write((byte)direction); - m_Stream.Write( (sbyte) loc.Z ); + m_Stream.Write((sbyte)loc.Z); - if ( hue != 0 ) - m_Stream.Write( (ushort) hue ); + if (hue != 0) + m_Stream.Write((ushort)hue); - if ( flags != 0 ) - m_Stream.Write( (byte) flags ); - } - } - } -} + if (flags != 0) + m_Stream.Write((byte)flags); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Blood.cs b/Scripts/Items/Misc/Blood.cs index 864b18873..c71e21173 100644 --- a/Scripts/Items/Misc/Blood.cs +++ b/Scripts/Items/Misc/Blood.cs @@ -2,55 +2,55 @@ using System; namespace Server.Items { - public class Blood : Item - { - [Constructible] - public Blood() : this( Utility.RandomList( 0x1645, 0x122A, 0x122B, 0x122C, 0x122D, 0x122E, 0x122F )) - { - } + public class Blood : Item + { + [Constructible] + public Blood() : this(Utility.RandomList(0x1645, 0x122A, 0x122B, 0x122C, 0x122D, 0x122E, 0x122F)) + { + } - [Constructible] - public Blood( int itemID ) : base( itemID ) - { - Movable = false; + [Constructible] + public Blood(int itemID) : base(itemID) + { + Movable = false; - new InternalTimer( this ).Start(); - } + new InternalTimer(this).Start(); + } - public Blood( Serial serial ) : base( serial ) - { - new InternalTimer( this ).Start(); - } + public Blood(Serial serial) : base(serial) + { + new InternalTimer(this).Start(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - private class InternalTimer : Timer - { - private Item m_Blood; + private class InternalTimer : Timer + { + private Item m_Blood; - public InternalTimer( Item blood ) : base( TimeSpan.FromSeconds( 5.0 ) ) - { - Priority = TimerPriority.OneSecond; + public InternalTimer(Item blood) : base(TimeSpan.FromSeconds(5.0)) + { + Priority = TimerPriority.OneSecond; - m_Blood = blood; - } + m_Blood = blood; + } - protected override void OnTick() - { - m_Blood.Delete(); - } - } - } + protected override void OnTick() + { + m_Blood.Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Bola.cs b/Scripts/Items/Misc/Bola.cs index 0e8b3d09c..e25b7bd0b 100644 --- a/Scripts/Items/Misc/Bola.cs +++ b/Scripts/Items/Misc/Bola.cs @@ -1,230 +1,228 @@ using System; using Server.Mobiles; using Server.Network; +using Server.Spells.Ninjitsu; using Server.Targeting; namespace Server.Items { - public class Bola : Item - { - [Constructible] - public Bola() : this( 1 ) - { - } + public class Bola : Item + { + [Constructible] + public Bola() : this(1) + { + } - [Constructible] - public Bola( int amount ) : base( 0x26AC ) - { - Weight = 4.0; - Stackable = true; - Amount = amount; - } + [Constructible] + public Bola(int amount) : base(0x26AC) + { + Weight = 4.0; + Stackable = true; + Amount = amount; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1040019 ); // The bola must be in your pack to use it. - } - else if ( !from.CanBeginAction( typeof( Bola ) ) ) - { - from.SendLocalizedMessage( 1049624 ); // You have to wait a few moments before you can use another bola! - } - else if ( from.Target is BolaTarget ) - { - from.SendLocalizedMessage( 1049631 ); // This bola is already being used. - } - else if ( !HasFreeHands( from ) ) - { - from.SendLocalizedMessage( 1040015 ); // Your hands must be free to use this - } - else if ( from.Mounted ) - { - from.SendLocalizedMessage( 1040016 ); // You cannot use this while riding a mount - } - else if ( Spells.Ninjitsu.AnimalForm.UnderTransformation( from ) ) - { - from.SendLocalizedMessage( 1070902 ); // You can't use this while in an animal form! - } - else - { - EtherealMount.StopMounting( from ); + public Bola(Serial serial) : base(serial) + { + } - from.Target = new BolaTarget( this ); - from.LocalOverheadMessage( MessageType.Emote, 0x3B2, 1049632 ); // * You begin to swing the bola...* - from.NonlocalOverheadMessage( MessageType.Emote, 0x3B2, 1049633, from.Name ); // ~1_NAME~ begins to menacingly swing a bola... - } - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1040019); // The bola must be in your pack to use it. + } + else if (!from.CanBeginAction(typeof(Bola))) + { + from.SendLocalizedMessage(1049624); // You have to wait a few moments before you can use another bola! + } + else if (from.Target is BolaTarget) + { + from.SendLocalizedMessage(1049631); // This bola is already being used. + } + else if (!HasFreeHands(from)) + { + from.SendLocalizedMessage(1040015); // Your hands must be free to use this + } + else if (from.Mounted) + { + from.SendLocalizedMessage(1040016); // You cannot use this while riding a mount + } + else if (AnimalForm.UnderTransformation(from)) + { + from.SendLocalizedMessage(1070902); // You can't use this while in an animal form! + } + else + { + EtherealMount.StopMounting(from); - private static void ReleaseBolaLock( object state ) - { - ((Mobile)state).EndAction( typeof( Bola ) ); - } + from.Target = new BolaTarget(this); + from.LocalOverheadMessage(MessageType.Emote, 0x3B2, 1049632); // * You begin to swing the bola...* + from.NonlocalOverheadMessage(MessageType.Emote, 0x3B2, 1049633, + from.Name); // ~1_NAME~ begins to menacingly swing a bola... + } + } - private static void FinishThrow( object state ) - { - object[] states = (object[])state; + private static void ReleaseBolaLock(object state) + { + ((Mobile)state).EndAction(typeof(Bola)); + } - Mobile from = (Mobile)states[0]; - Mobile to = (Mobile)states[1]; + private static void FinishThrow(object state) + { + object[] states = (object[])state; - if ( Core.AOS ) - new Bola().MoveToWorld( to.Location, to.Map ); + Mobile from = (Mobile)states[0]; + Mobile to = (Mobile)states[1]; - if ( to is ChaosDragoon || to is ChaosDragoonElite ) - from.SendLocalizedMessage( 1042047 ); // You fail to knock the rider from its mount. + if (Core.AOS) + new Bola().MoveToWorld(to.Location, to.Map); - IMount mt = to.Mount; - if ( mt != null && !( to is ChaosDragoon || to is ChaosDragoonElite ) ) - mt.Rider = null; + if (to is ChaosDragoon || to is ChaosDragoonElite) + from.SendLocalizedMessage(1042047); // You fail to knock the rider from its mount. - if (to is PlayerMobile mobile) - { - if (Spells.Ninjitsu.AnimalForm.UnderTransformation(mobile)) - { - mobile.SendLocalizedMessage(1114066, from.Name); // ~1_NAME~ knocked you out of animal form! - } - else if (mobile.Mounted) - { - mobile.SendLocalizedMessage(1040023); // You have been knocked off of your mount! - } + IMount mt = to.Mount; + if (mt != null && !(to is ChaosDragoon || to is ChaosDragoonElite)) + mt.Rider = null; - mobile.SetMountBlock(BlockMountType.Dazed, TimeSpan.FromSeconds( Core.ML ? 10 : 3 ), true); - } + if (to is PlayerMobile mobile) + { + if (AnimalForm.UnderTransformation(mobile)) + mobile.SendLocalizedMessage(1114066, from.Name); // ~1_NAME~ knocked you out of animal form! + else if (mobile.Mounted) mobile.SendLocalizedMessage(1040023); // You have been knocked off of your mount! - if (Core.AOS) /* only failsafe, attacker should already be dismounted */ - { - (from as PlayerMobile)?.SetMountBlock( BlockMountType.BolaRecovery, TimeSpan.FromSeconds( Core.ML ? 10 : 3 ), true ); - } + mobile.SetMountBlock(BlockMountType.Dazed, TimeSpan.FromSeconds(Core.ML ? 10 : 3), true); + } - to.Damage(1); + if (Core.AOS) /* only failsafe, attacker should already be dismounted */ + (from as PlayerMobile)?.SetMountBlock(BlockMountType.BolaRecovery, TimeSpan.FromSeconds(Core.ML ? 10 : 3), + true); - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), new TimerStateCallback( ReleaseBolaLock ), from ); - } + to.Damage(1); - private static bool HasFreeHands( Mobile from ) - { - Item one = from.FindItemOnLayer( Layer.OneHanded ); - Item two = from.FindItemOnLayer( Layer.TwoHanded ); + Timer.DelayCall(TimeSpan.FromSeconds(2.0), new TimerStateCallback(ReleaseBolaLock), from); + } - if ( Core.SE ) - { - Container pack = from.Backpack; + private static bool HasFreeHands(Mobile from) + { + Item one = from.FindItemOnLayer(Layer.OneHanded); + Item two = from.FindItemOnLayer(Layer.TwoHanded); - if ( pack != null ) - { - if ( one != null && one.Movable ) - { - pack.DropItem( one ); - one = null; - } + if (Core.SE) + { + Container pack = from.Backpack; - if ( two != null && two.Movable ) - { - pack.DropItem( two ); - two = null; - } - } - } - else if ( Core.AOS ) - { - if ( one != null && one.Movable ) - { - from.AddToBackpack( one ); - one = null; - } + if (pack != null) + { + if (one != null && one.Movable) + { + pack.DropItem(one); + one = null; + } - if ( two != null && two.Movable ) - { - from.AddToBackpack( two ); - two = null; - } - } + if (two != null && two.Movable) + { + pack.DropItem(two); + two = null; + } + } + } + else if (Core.AOS) + { + if (one != null && one.Movable) + { + from.AddToBackpack(one); + one = null; + } - return ( one == null && two == null ); - } + if (two != null && two.Movable) + { + from.AddToBackpack(two); + two = null; + } + } - public class BolaTarget : Target - { - private Bola m_Bola; + return one == null && two == null; + } - public BolaTarget( Bola bola ) : base( 8, false, TargetFlags.Harmful ) - { - m_Bola = bola; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - protected override void OnTarget( Mobile from, object obj ) - { - if ( m_Bola.Deleted ) - return; + writer.Write(0); + } - if ( obj is Mobile to ) - { - if ( !m_Bola.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1040019 ); // The bola must be in your pack to use it. - } - else if ( !HasFreeHands( from ) ) - { - from.SendLocalizedMessage( 1040015 ); // Your hands must be free to use this - } - else if ( from.Mounted ) - { - from.SendLocalizedMessage( 1040016 ); // You cannot use this while riding a mount - } - else if ( Spells.Ninjitsu.AnimalForm.UnderTransformation( from ) ) - { - from.SendLocalizedMessage( 1070902 ); // You can't use this while in an animal form! - } - else if (!to.Mounted && !Spells.Ninjitsu.AnimalForm.UnderTransformation(to)) - { - from.SendLocalizedMessage( 1049628 ); // You have no reason to throw a bola at that. - } - else if ( !from.CanBeHarmful( to ) ) - { - } - else if ( from.BeginAction( typeof( Bola ) ) ) - { - EtherealMount.StopMounting( from ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - from.DoHarmful( to ); + int version = reader.ReadInt(); + } - m_Bola.Consume(); + public class BolaTarget : Target + { + private Bola m_Bola; - from.Direction = from.GetDirectionTo( to ); - from.Animate( 11, 5, 1, true, false, 0 ); - from.MovingEffect( to, 0x26AC, 10, 0, false, false ); + public BolaTarget(Bola bola) : base(8, false, TargetFlags.Harmful) + { + m_Bola = bola; + } - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), new TimerStateCallback( FinishThrow ), new object[]{ from, to } ); - } - else - { - from.SendLocalizedMessage( 1049624 ); // You have to wait a few moments before you can use another bola! - } - } - else - { - from.SendLocalizedMessage( 1049629 ); // You cannot throw a bola at that. - } - } - } + protected override void OnTarget(Mobile from, object obj) + { + if (m_Bola.Deleted) + return; - public Bola( Serial serial ) : base( serial ) - { - } + if (obj is Mobile to) + { + if (!m_Bola.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1040019); // The bola must be in your pack to use it. + } + else if (!HasFreeHands(from)) + { + from.SendLocalizedMessage(1040015); // Your hands must be free to use this + } + else if (from.Mounted) + { + from.SendLocalizedMessage(1040016); // You cannot use this while riding a mount + } + else if (AnimalForm.UnderTransformation(from)) + { + from.SendLocalizedMessage(1070902); // You can't use this while in an animal form! + } + else if (!to.Mounted && !AnimalForm.UnderTransformation(to)) + { + from.SendLocalizedMessage(1049628); // You have no reason to throw a bola at that. + } + else if (!from.CanBeHarmful(to)) + { + } + else if (from.BeginAction(typeof(Bola))) + { + EtherealMount.StopMounting(from); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + from.DoHarmful(to); - writer.Write( (int) 0 ); - } + m_Bola.Consume(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + from.Direction = from.GetDirectionTo(to); + from.Animate(11, 5, 1, true, false, 0); + from.MovingEffect(to, 0x26AC, 10, 0, false, false); - int version = reader.ReadInt(); - } - } -} + Timer.DelayCall(TimeSpan.FromSeconds(0.5), new TimerStateCallback(FinishThrow), + new object[] { from, to }); + } + else + { + from.SendLocalizedMessage( + 1049624); // You have to wait a few moments before you can use another bola! + } + } + else + { + from.SendLocalizedMessage(1049629); // You cannot throw a bola at that. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/BolaBall.cs b/Scripts/Items/Misc/BolaBall.cs index 92028fd7a..260287fc5 100644 --- a/Scripts/Items/Misc/BolaBall.cs +++ b/Scripts/Items/Misc/BolaBall.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class BolaBall : Item - { - [Constructible] - public BolaBall() : this( 1 ) - { - } + public class BolaBall : Item + { + [Constructible] + public BolaBall() : this(1) + { + } - [Constructible] - public BolaBall( int amount ) : base( 0xE73 ) - { - Weight = 4.0; - Stackable = true; - Amount = amount; - Hue = 0x8AC; - } + [Constructible] + public BolaBall(int amount) : base(0xE73) + { + Weight = 4.0; + Stackable = true; + Amount = amount; + Hue = 0x8AC; + } - public BolaBall( Serial serial ) : base( serial ) - { - } + public BolaBall(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/BulletinBoards.cs b/Scripts/Items/Misc/BulletinBoards.cs index afbbc0eac..f11a49f72 100644 --- a/Scripts/Items/Misc/BulletinBoards.cs +++ b/Scripts/Items/Misc/BulletinBoards.cs @@ -1,616 +1,623 @@ using System; using System.Collections.Generic; using Server.Network; +using Server.Targeting; namespace Server.Items { - [Flippable( 0x1E5E, 0x1E5F )] - public class BulletinBoard : BaseBulletinBoard - { - [Constructible] - public BulletinBoard() : base( 0x1E5E ) - { - } - - public BulletinBoard( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public abstract class BaseBulletinBoard : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public string BoardName { get; set; } - - public BaseBulletinBoard( int itemID ) : base( itemID ) - { - BoardName = "bulletin board"; - Movable = false; - } - - // Threads will be removed six hours after the last post was made - private static TimeSpan ThreadDeletionTime = TimeSpan.FromHours( 6.0 ); - - // A player may only create a thread once every two minutes - private static TimeSpan ThreadCreateTime = TimeSpan.FromMinutes( 2.0 ); - - // A player may only reply once every thirty seconds - private static TimeSpan ThreadReplyTime = TimeSpan.FromSeconds( 30.0 ); - - public static bool CheckTime( DateTime time, TimeSpan range ) - { - return (time + range) < DateTime.UtcNow; - } - - public static string FormatTS( TimeSpan ts ) - { - int totalSeconds = (int)ts.TotalSeconds; - int seconds = totalSeconds % 60; - int minutes = totalSeconds / 60; - - if ( minutes != 0 && seconds != 0 ) - return $"{minutes} minute{(minutes == 1 ? "" : "s")} and {seconds} second{(seconds == 1 ? "" : "s")}"; - if ( minutes != 0 ) - return $"{minutes} minute{(minutes == 1 ? "" : "s")}"; - return $"{seconds} second{(seconds == 1 ? "" : "s")}"; - } - - public virtual void Cleanup() - { - List items = Items; - - for ( int i = items.Count - 1; i >= 0; --i ) - { - if ( i >= items.Count ) - continue; - - if ( !(items[i] is BulletinMessage msg) ) - continue; - - if ( msg.Thread == null && CheckTime( msg.LastPostTime, ThreadDeletionTime ) ) - { - msg.Delete(); - RecurseDelete( msg ); // A root-level thread has expired - } - } - } - - private void RecurseDelete( BulletinMessage msg ) - { - List found = new List(); - List items = Items; - - for ( int i = items.Count - 1; i >= 0; --i ) - { - if ( i >= items.Count ) - continue; - - if ( !(items[i] is BulletinMessage check) ) - continue; - - if ( check.Thread == msg ) - { - check.Delete(); - found.Add( check ); - } - } - - for ( int i = 0; i < found.Count; ++i ) - RecurseDelete( (BulletinMessage)found[i] ); - } - - public virtual bool GetLastPostTime( Mobile poster, bool onlyCheckRoot, ref DateTime lastPostTime ) - { - List items = Items; - bool wasSet = false; - - for ( int i = 0; i < items.Count; ++i ) - { - if ( !(items[i] is BulletinMessage msg) || msg.Poster != poster ) - continue; - - if ( onlyCheckRoot && msg.Thread != null ) - continue; - - if ( msg.Time > lastPostTime ) - { - wasSet = true; - lastPostTime = msg.Time; - } - } - - return wasSet; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( CheckRange( from ) ) - { - Cleanup(); - - NetState state = from.NetState; - - state.Send( new BBDisplayBoard( this ) ); - if ( state.ContainerGridLines ) - state.Send( new ContainerContent6017( from, this ) ); - else - state.Send( new ContainerContent( from, this ) ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } - - public virtual bool CheckRange( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - - return ( from.Map == Map && from.InRange( GetWorldLocation(), 2 ) ); - } - - public void PostMessage( Mobile from, BulletinMessage thread, string subject, string[] lines ) - { - if ( thread != null ) - thread.LastPostTime = DateTime.UtcNow; - - AddItem( new BulletinMessage( from, thread, subject, lines ) ); - } - - public BaseBulletinBoard( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( (string) BoardName ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - BoardName = reader.ReadString(); - break; - } - } - } - - public static void Initialize() - { - PacketHandlers.Register( 0x71, 0, true, BBClientRequest ); - } - - public static void BBClientRequest( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - int packetID = pvSrc.ReadByte(); - - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BaseBulletinBoard board) || !board.CheckRange( from ) ) - return; - - switch ( packetID ) - { - case 3: BBRequestContent( from, board, pvSrc ); break; - case 4: BBRequestHeader( from, board, pvSrc ); break; - case 5: BBPostMessage( from, board, pvSrc ); break; - case 6: BBRemoveMessage( from, board, pvSrc ); break; - } - } - - public static void BBRequestContent( Mobile from, BaseBulletinBoard board, PacketReader pvSrc ) - { - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BulletinMessage msg) || msg.Parent != board ) - return; - - from.Send( new BBMessageContent( board, msg ) ); - } - - public static void BBRequestHeader( Mobile from, BaseBulletinBoard board, PacketReader pvSrc ) - { - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BulletinMessage msg) || msg.Parent != board ) - return; - - from.Send( new BBMessageHeader( board, msg ) ); - } - - public static void BBPostMessage( Mobile from, BaseBulletinBoard board, PacketReader pvSrc ) - { - BulletinMessage thread = World.FindItem( pvSrc.ReadInt32() ) as BulletinMessage; - - if ( thread != null && thread.Parent != board ) - thread = null; - - int breakout = 0; - - while ( thread?.Thread != null && breakout++ < 10 ) - thread = thread.Thread; - - DateTime lastPostTime = DateTime.MinValue; - - if ( board.GetLastPostTime( from, ( thread == null ), ref lastPostTime ) ) - { - if ( !CheckTime( lastPostTime, (thread == null ? ThreadCreateTime : ThreadReplyTime) ) ) - { - if ( thread == null ) - from.SendMessage( "You must wait {0} before creating a new thread.", FormatTS( ThreadCreateTime ) ); - else - from.SendMessage( "You must wait {0} before replying to another thread.", FormatTS( ThreadReplyTime ) ); + [Flippable(0x1E5E, 0x1E5F)] + public class BulletinBoard : BaseBulletinBoard + { + [Constructible] + public BulletinBoard() : base(0x1E5E) + { + } + + public BulletinBoard(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public abstract class BaseBulletinBoard : Item + { + // Threads will be removed six hours after the last post was made + private static TimeSpan ThreadDeletionTime = TimeSpan.FromHours(6.0); + + // A player may only create a thread once every two minutes + private static TimeSpan ThreadCreateTime = TimeSpan.FromMinutes(2.0); + + // A player may only reply once every thirty seconds + private static TimeSpan ThreadReplyTime = TimeSpan.FromSeconds(30.0); + + public BaseBulletinBoard(int itemID) : base(itemID) + { + BoardName = "bulletin board"; + Movable = false; + } + + public BaseBulletinBoard(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string BoardName{ get; set; } + + public static bool CheckTime(DateTime time, TimeSpan range) + { + return time + range < DateTime.UtcNow; + } + + public static string FormatTS(TimeSpan ts) + { + int totalSeconds = (int)ts.TotalSeconds; + int seconds = totalSeconds % 60; + int minutes = totalSeconds / 60; + + if (minutes != 0 && seconds != 0) + return $"{minutes} minute{(minutes == 1 ? "" : "s")} and {seconds} second{(seconds == 1 ? "" : "s")}"; + if (minutes != 0) + return $"{minutes} minute{(minutes == 1 ? "" : "s")}"; + return $"{seconds} second{(seconds == 1 ? "" : "s")}"; + } + + public virtual void Cleanup() + { + List items = Items; + + for (int i = items.Count - 1; i >= 0; --i) + { + if (i >= items.Count) + continue; + + if (!(items[i] is BulletinMessage msg)) + continue; + + if (msg.Thread == null && CheckTime(msg.LastPostTime, ThreadDeletionTime)) + { + msg.Delete(); + RecurseDelete(msg); // A root-level thread has expired + } + } + } + + private void RecurseDelete(BulletinMessage msg) + { + List found = new List(); + List items = Items; + + for (int i = items.Count - 1; i >= 0; --i) + { + if (i >= items.Count) + continue; + + if (!(items[i] is BulletinMessage check)) + continue; + + if (check.Thread == msg) + { + check.Delete(); + found.Add(check); + } + } + + for (int i = 0; i < found.Count; ++i) + RecurseDelete((BulletinMessage)found[i]); + } + + public virtual bool GetLastPostTime(Mobile poster, bool onlyCheckRoot, ref DateTime lastPostTime) + { + List items = Items; + bool wasSet = false; + + for (int i = 0; i < items.Count; ++i) + { + if (!(items[i] is BulletinMessage msg) || msg.Poster != poster) + continue; + + if (onlyCheckRoot && msg.Thread != null) + continue; + + if (msg.Time > lastPostTime) + { + wasSet = true; + lastPostTime = msg.Time; + } + } + + return wasSet; + } + + public override void OnDoubleClick(Mobile from) + { + if (CheckRange(from)) + { + Cleanup(); + + NetState state = from.NetState; + + state.Send(new BBDisplayBoard(this)); + if (state.ContainerGridLines) + state.Send(new ContainerContent6017(from, this)); + else + state.Send(new ContainerContent(from, this)); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + + public virtual bool CheckRange(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + + return from.Map == Map && from.InRange(GetWorldLocation(), 2); + } + + public void PostMessage(Mobile from, BulletinMessage thread, string subject, string[] lines) + { + if (thread != null) + thread.LastPostTime = DateTime.UtcNow; + + AddItem(new BulletinMessage(from, thread, subject, lines)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(BoardName); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + BoardName = reader.ReadString(); + break; + } + } + } + + public static void Initialize() + { + PacketHandlers.Register(0x71, 0, true, BBClientRequest); + } + + public static void BBClientRequest(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + int packetID = pvSrc.ReadByte(); + + if (!(World.FindItem(pvSrc.ReadInt32()) is BaseBulletinBoard board) || !board.CheckRange(from)) + return; + + switch (packetID) + { + case 3: + BBRequestContent(from, board, pvSrc); + break; + case 4: + BBRequestHeader(from, board, pvSrc); + break; + case 5: + BBPostMessage(from, board, pvSrc); + break; + case 6: + BBRemoveMessage(from, board, pvSrc); + break; + } + } + + public static void BBRequestContent(Mobile from, BaseBulletinBoard board, PacketReader pvSrc) + { + if (!(World.FindItem(pvSrc.ReadInt32()) is BulletinMessage msg) || msg.Parent != board) + return; + + from.Send(new BBMessageContent(board, msg)); + } + + public static void BBRequestHeader(Mobile from, BaseBulletinBoard board, PacketReader pvSrc) + { + if (!(World.FindItem(pvSrc.ReadInt32()) is BulletinMessage msg) || msg.Parent != board) + return; + + from.Send(new BBMessageHeader(board, msg)); + } + + public static void BBPostMessage(Mobile from, BaseBulletinBoard board, PacketReader pvSrc) + { + BulletinMessage thread = World.FindItem(pvSrc.ReadInt32()) as BulletinMessage; + + if (thread != null && thread.Parent != board) + thread = null; + + int breakout = 0; - return; - } - } + while (thread?.Thread != null && breakout++ < 10) + thread = thread.Thread; - string subject = pvSrc.ReadUTF8StringSafe( pvSrc.ReadByte() ); + DateTime lastPostTime = DateTime.MinValue; - if ( subject.Length == 0 ) - return; + if (board.GetLastPostTime(from, thread == null, ref lastPostTime)) + if (!CheckTime(lastPostTime, thread == null ? ThreadCreateTime : ThreadReplyTime)) + { + if (thread == null) + from.SendMessage("You must wait {0} before creating a new thread.", FormatTS(ThreadCreateTime)); + else + from.SendMessage("You must wait {0} before replying to another thread.", FormatTS(ThreadReplyTime)); - string[] lines = new string[pvSrc.ReadByte()]; + return; + } - if ( lines.Length == 0 ) - return; + string subject = pvSrc.ReadUTF8StringSafe(pvSrc.ReadByte()); - for ( int i = 0; i < lines.Length; ++i ) - lines[i] = pvSrc.ReadUTF8StringSafe( pvSrc.ReadByte() ); + if (subject.Length == 0) + return; - board.PostMessage( from, thread, subject, lines ); - } + string[] lines = new string[pvSrc.ReadByte()]; - public static void BBRemoveMessage( Mobile from, BaseBulletinBoard board, PacketReader pvSrc ) - { - if ( !(World.FindItem( pvSrc.ReadInt32() ) is BulletinMessage msg) || msg.Parent != board ) - return; + if (lines.Length == 0) + return; - if ( from.AccessLevel < AccessLevel.GameMaster && msg.Poster != from ) - return; + for (int i = 0; i < lines.Length; ++i) + lines[i] = pvSrc.ReadUTF8StringSafe(pvSrc.ReadByte()); - msg.Delete(); - } - } + board.PostMessage(from, thread, subject, lines); + } - public struct BulletinEquip - { - public int itemID; - public int hue; + public static void BBRemoveMessage(Mobile from, BaseBulletinBoard board, PacketReader pvSrc) + { + if (!(World.FindItem(pvSrc.ReadInt32()) is BulletinMessage msg) || msg.Parent != board) + return; - public BulletinEquip( int itemID, int hue ) - { - this.itemID = itemID; - this.hue = hue; - } - } + if (from.AccessLevel < AccessLevel.GameMaster && msg.Poster != from) + return; - public class BulletinMessage : Item - { - public string GetTimeAsString() - { - return Time.ToString( "MMM dd, yyyy" ); - } + msg.Delete(); + } + } - public override bool CheckTarget( Mobile from, Targeting.Target targ, object targeted ) - { - return false; - } + public struct BulletinEquip + { + public int itemID; + public int hue; - public override bool IsAccessibleTo( Mobile check ) - { - return false; - } + public BulletinEquip(int itemID, int hue) + { + this.itemID = itemID; + this.hue = hue; + } + } - public BulletinMessage( Mobile poster, BulletinMessage thread, string subject, string[] lines ) : base( 0xEB0 ) - { - Movable = false; + public class BulletinMessage : Item + { + public BulletinMessage(Mobile poster, BulletinMessage thread, string subject, string[] lines) : base(0xEB0) + { + Movable = false; - Poster = poster; - Subject = subject; - Time = DateTime.UtcNow; - LastPostTime = Time; - Thread = thread; - PostedName = Poster.Name; - PostedBody = Poster.Body; - PostedHue = Poster.Hue; - Lines = lines; + Poster = poster; + Subject = subject; + Time = DateTime.UtcNow; + LastPostTime = Time; + Thread = thread; + PostedName = Poster.Name; + PostedBody = Poster.Body; + PostedHue = Poster.Hue; + Lines = lines; - List list = new List(); + List list = new List(); - for ( int i = 0; i < poster.Items.Count; ++i ) - { - Item item = poster.Items[i]; + for (int i = 0; i < poster.Items.Count; ++i) + { + Item item = poster.Items[i]; - if ( item.Layer >= Layer.OneHanded && item.Layer <= Layer.Mount ) - list.Add( new BulletinEquip( item.ItemID, item.Hue ) ); - } + if (item.Layer >= Layer.OneHanded && item.Layer <= Layer.Mount) + list.Add(new BulletinEquip(item.ItemID, item.Hue)); + } - PostedEquip = list.ToArray(); - } + PostedEquip = list.ToArray(); + } - public Mobile Poster { get; private set; } + public BulletinMessage(Serial serial) : base(serial) + { + } - public BulletinMessage Thread { get; private set; } + public Mobile Poster{ get; private set; } - public string Subject { get; private set; } + public BulletinMessage Thread{ get; private set; } - public DateTime Time { get; private set; } + public string Subject{ get; private set; } - public DateTime LastPostTime { get; set; } + public DateTime Time{ get; private set; } - public string PostedName { get; private set; } + public DateTime LastPostTime{ get; set; } - public int PostedBody { get; private set; } + public string PostedName{ get; private set; } - public int PostedHue { get; private set; } + public int PostedBody{ get; private set; } - public BulletinEquip[] PostedEquip { get; private set; } + public int PostedHue{ get; private set; } - public string[] Lines { get; private set; } + public BulletinEquip[] PostedEquip{ get; private set; } - public BulletinMessage( Serial serial ) : base( serial ) - { - } + public string[] Lines{ get; private set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public string GetTimeAsString() + { + return Time.ToString("MMM dd, yyyy"); + } - writer.Write( (int) 1 ); // version - - writer.Write( (Mobile) Poster ); - writer.Write( (string) Subject ); - writer.Write( (DateTime) Time ); - writer.Write( (DateTime) LastPostTime ); - writer.Write( (bool) (Thread != null) ); - writer.Write( (Item) Thread ); - writer.Write( (string) PostedName ); - writer.Write( (int) PostedBody ); - writer.Write( (int) PostedHue ); - - writer.Write( (int) PostedEquip.Length ); - - for ( int i = 0; i < PostedEquip.Length; ++i ) - { - writer.Write( (int) PostedEquip[i].itemID ); - writer.Write( (int) PostedEquip[i].hue ); - } - - writer.Write( (int) Lines.Length ); - - for ( int i = 0; i < Lines.Length; ++i ) - writer.Write( (string) Lines[i] ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - case 0: - { - Poster = reader.ReadMobile(); - Subject = reader.ReadString(); - Time = reader.ReadDateTime(); - LastPostTime = reader.ReadDateTime(); - bool hasThread = reader.ReadBool(); - Thread = reader.ReadItem() as BulletinMessage; - PostedName = reader.ReadString(); - PostedBody = reader.ReadInt(); - PostedHue = reader.ReadInt(); + public override bool CheckTarget(Mobile from, Target targ, object targeted) + { + return false; + } - PostedEquip = new BulletinEquip[reader.ReadInt()]; + public override bool IsAccessibleTo(Mobile check) + { + return false; + } - for ( int i = 0; i < PostedEquip.Length; ++i ) - { - PostedEquip[i].itemID = reader.ReadInt(); - PostedEquip[i].hue = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Lines = new string[reader.ReadInt()]; + writer.Write(1); // version + + writer.Write(Poster); + writer.Write(Subject); + writer.Write(Time); + writer.Write(LastPostTime); + writer.Write(Thread != null); + writer.Write(Thread); + writer.Write(PostedName); + writer.Write(PostedBody); + writer.Write(PostedHue); + + writer.Write(PostedEquip.Length); + + for (int i = 0; i < PostedEquip.Length; ++i) + { + writer.Write(PostedEquip[i].itemID); + writer.Write(PostedEquip[i].hue); + } + + writer.Write(Lines.Length); + + for (int i = 0; i < Lines.Length; ++i) + writer.Write(Lines[i]); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + case 0: + { + Poster = reader.ReadMobile(); + Subject = reader.ReadString(); + Time = reader.ReadDateTime(); + LastPostTime = reader.ReadDateTime(); + bool hasThread = reader.ReadBool(); + Thread = reader.ReadItem() as BulletinMessage; + PostedName = reader.ReadString(); + PostedBody = reader.ReadInt(); + PostedHue = reader.ReadInt(); - for ( int i = 0; i < Lines.Length; ++i ) - Lines[i] = reader.ReadString(); + PostedEquip = new BulletinEquip[reader.ReadInt()]; - if ( hasThread && Thread == null ) - Delete(); - - if ( version == 0 ) - ValidationQueue.Add( this ); + for (int i = 0; i < PostedEquip.Length; ++i) + { + PostedEquip[i].itemID = reader.ReadInt(); + PostedEquip[i].hue = reader.ReadInt(); + } + + Lines = new string[reader.ReadInt()]; - break; - } - } - } + for (int i = 0; i < Lines.Length; ++i) + Lines[i] = reader.ReadString(); + + if (hasThread && Thread == null) + Delete(); + + if (version == 0) + ValidationQueue.Add(this); + + break; + } + } + } + + public void Validate() + { + if ((Parent as BulletinBoard)?.Items.Contains(this) == false) + Delete(); + } + } + + public class BBDisplayBoard : Packet + { + public BBDisplayBoard(BaseBulletinBoard board) : base(0x71) + { + string name = board.BoardName; + + if (name == null) + name = ""; + + EnsureCapacity(38); + + byte[] buffer = Utility.UTF8.GetBytes(name); + + m_Stream.Write((byte)0x00); // PacketID + m_Stream.Write(board.Serial); // Bulletin board serial + + // Bulletin board name + if (buffer.Length >= 29) + { + m_Stream.Write(buffer, 0, 29); + m_Stream.Write((byte)0); + } + else + { + m_Stream.Write(buffer, 0, buffer.Length); + m_Stream.Fill(30 - buffer.Length); + } + } + } + + public class BBMessageHeader : Packet + { + public BBMessageHeader(BaseBulletinBoard board, BulletinMessage msg) : base(0x71) + { + string poster = SafeString(msg.PostedName); + string subject = SafeString(msg.Subject); + string time = SafeString(msg.GetTimeAsString()); + + EnsureCapacity(22 + poster.Length + subject.Length + time.Length); + + m_Stream.Write((byte)0x01); // PacketID + m_Stream.Write(board.Serial); // Bulletin board serial + m_Stream.Write(msg.Serial); // Message serial + + BulletinMessage thread = msg.Thread; + + if (thread == null) + m_Stream.Write(0); // Thread serial--root + else + m_Stream.Write(thread.Serial); // Thread serial--parent + + WriteString(poster); + WriteString(subject); + WriteString(time); + } + + public void WriteString(string v) + { + byte[] buffer = Utility.UTF8.GetBytes(v); + int len = buffer.Length + 1; + + if (len > 255) + len = 255; + + m_Stream.Write((byte)len); + m_Stream.Write(buffer, 0, len - 1); + m_Stream.Write((byte)0); + } + + public string SafeString(string v) + { + if (v == null) + return string.Empty; + + return v; + } + } + + public class BBMessageContent : Packet + { + public BBMessageContent(BaseBulletinBoard board, BulletinMessage msg) : base(0x71) + { + string poster = SafeString(msg.PostedName); + string subject = SafeString(msg.Subject); + string time = SafeString(msg.GetTimeAsString()); + + EnsureCapacity(22 + poster.Length + subject.Length + time.Length); + + m_Stream.Write((byte)0x02); // PacketID + m_Stream.Write(board.Serial); // Bulletin board serial + m_Stream.Write(msg.Serial); // Message serial + + WriteString(poster); + WriteString(subject); + WriteString(time); + + m_Stream.Write((short)msg.PostedBody); + m_Stream.Write((short)msg.PostedHue); + + int len = msg.PostedEquip.Length; + + if (len > 255) + len = 255; + + m_Stream.Write((byte)len); + + for (int i = 0; i < len; ++i) + { + BulletinEquip eq = msg.PostedEquip[i]; + + m_Stream.Write((short)eq.itemID); + m_Stream.Write((short)eq.hue); + } + + len = msg.Lines.Length; + + if (len > 255) + len = 255; + + m_Stream.Write((byte)len); + + for (int i = 0; i < len; ++i) + WriteString(msg.Lines[i], true); + } + + public void WriteString(string v) + { + WriteString(v, false); + } - public void Validate() - { - if ( (Parent as BulletinBoard)?.Items.Contains( this ) == false ) - Delete(); - } - } - - public class BBDisplayBoard : Packet - { - public BBDisplayBoard( BaseBulletinBoard board ) : base( 0x71 ) - { - string name = board.BoardName; - - if ( name == null ) - name = ""; - - EnsureCapacity( 38 ); - - byte[] buffer = Utility.UTF8.GetBytes( name ); - - m_Stream.Write( (byte) 0x00 ); // PacketID - m_Stream.Write( (int) board.Serial ); // Bulletin board serial - - // Bulletin board name - if ( buffer.Length >= 29 ) - { - m_Stream.Write( buffer, 0, 29 ); - m_Stream.Write( (byte) 0 ); - } - else - { - m_Stream.Write( buffer, 0, buffer.Length ); - m_Stream.Fill( 30 - buffer.Length ); - } - } - } - - public class BBMessageHeader : Packet - { - public BBMessageHeader( BaseBulletinBoard board, BulletinMessage msg ) : base( 0x71 ) - { - string poster = SafeString( msg.PostedName ); - string subject = SafeString( msg.Subject ); - string time = SafeString( msg.GetTimeAsString() ); - - EnsureCapacity( 22 + poster.Length + subject.Length + time.Length ); - - m_Stream.Write( (byte) 0x01 ); // PacketID - m_Stream.Write( (int) board.Serial ); // Bulletin board serial - m_Stream.Write( (int) msg.Serial ); // Message serial - - BulletinMessage thread = msg.Thread; - - if ( thread == null ) - m_Stream.Write( (int) 0 ); // Thread serial--root - else - m_Stream.Write( (int) thread.Serial ); // Thread serial--parent - - WriteString( poster ); - WriteString( subject ); - WriteString( time ); - } - - public void WriteString( string v ) - { - byte[] buffer = Utility.UTF8.GetBytes( v ); - int len = buffer.Length + 1; - - if ( len > 255 ) - len = 255; - - m_Stream.Write( (byte) len ); - m_Stream.Write( buffer, 0, len-1 ); - m_Stream.Write( (byte) 0 ); - } - - public string SafeString( string v ) - { - if ( v == null ) - return string.Empty; - - return v; - } - } - - public class BBMessageContent : Packet - { - public BBMessageContent( BaseBulletinBoard board, BulletinMessage msg ) : base( 0x71 ) - { - string poster = SafeString( msg.PostedName ); - string subject = SafeString( msg.Subject ); - string time = SafeString( msg.GetTimeAsString() ); - - EnsureCapacity( 22 + poster.Length + subject.Length + time.Length ); - - m_Stream.Write( (byte) 0x02 ); // PacketID - m_Stream.Write( (int) board.Serial ); // Bulletin board serial - m_Stream.Write( (int) msg.Serial ); // Message serial - - WriteString( poster ); - WriteString( subject ); - WriteString( time ); - - m_Stream.Write( (short) msg.PostedBody ); - m_Stream.Write( (short) msg.PostedHue ); - - int len = msg.PostedEquip.Length; - - if ( len > 255 ) - len = 255; - - m_Stream.Write( (byte) len ); - - for ( int i = 0; i < len; ++i ) - { - BulletinEquip eq = msg.PostedEquip[i]; - - m_Stream.Write( (short) eq.itemID ); - m_Stream.Write( (short) eq.hue ); - } - - len = msg.Lines.Length; - - if ( len > 255 ) - len = 255; - - m_Stream.Write( (byte) len ); - - for ( int i = 0; i < len; ++i ) - WriteString( msg.Lines[i], true ); - } - - public void WriteString( string v ) - { - WriteString( v, false ); - } + public void WriteString(string v, bool padding) + { + byte[] buffer = Utility.UTF8.GetBytes(v); + int tail = padding ? 2 : 1; + int len = buffer.Length + tail; - public void WriteString( string v, bool padding ) - { - byte[] buffer = Utility.UTF8.GetBytes( v ); - int tail = padding ? 2 : 1; - int len = buffer.Length + tail; + if (len > 255) + len = 255; - if ( len > 255 ) - len = 255; + m_Stream.Write((byte)len); + m_Stream.Write(buffer, 0, len - tail); - m_Stream.Write( (byte) len ); - m_Stream.Write( buffer, 0, len - tail ); + if (padding) + m_Stream.Write((short)0); // padding compensates for a client bug + else + m_Stream.Write((byte)0); + } - if ( padding ) - m_Stream.Write( (short) 0 ); // padding compensates for a client bug - else - m_Stream.Write( (byte) 0 ); - } + public string SafeString(string v) + { + if (v == null) + return string.Empty; - public string SafeString( string v ) - { - if ( v == null ) - return string.Empty; - - return v; - } - } -} + return v; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/ClockworkAssembly.cs b/Scripts/Items/Misc/ClockworkAssembly.cs index 5f560259d..b88c21635 100644 --- a/Scripts/Items/Misc/ClockworkAssembly.cs +++ b/Scripts/Items/Misc/ClockworkAssembly.cs @@ -1,130 +1,129 @@ -using System; using Server.Mobiles; namespace Server.Items { - public class ClockworkAssembly : Item - { - public override string DefaultName => "clockwork assembly"; + public class ClockworkAssembly : Item + { + [Constructible] + public ClockworkAssembly() : base(0x1EA8) + { + Weight = 5.0; + Hue = 1102; + } - [Constructible] - public ClockworkAssembly() : base( 0x1EA8 ) - { - Weight = 5.0; - Hue = 1102; - } + public ClockworkAssembly(Serial serial) : base(serial) + { + } - public ClockworkAssembly( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "clockwork assembly"; - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - double tinkerSkill = from.Skills[SkillName.Tinkering].Value; + double tinkerSkill = from.Skills[SkillName.Tinkering].Value; - if ( tinkerSkill < 60.0 ) - { - from.SendMessage( "You must have at least 60.0 skill in tinkering to construct a golem." ); - return; - } + if (tinkerSkill < 60.0) + { + from.SendMessage("You must have at least 60.0 skill in tinkering to construct a golem."); + return; + } - if ( (from.Followers + 4) > from.FollowersMax ) - { - from.SendLocalizedMessage( 1049607 ); // You have too many followers to control that creature. - return; - } + if (from.Followers + 4 > from.FollowersMax) + { + from.SendLocalizedMessage(1049607); // You have too many followers to control that creature. + return; + } - double scalar; + double scalar; - if ( tinkerSkill >= 100.0 ) - scalar = 1.0; - else if ( tinkerSkill >= 90.0 ) - scalar = 0.9; - else if ( tinkerSkill >= 80.0 ) - scalar = 0.8; - else if ( tinkerSkill >= 70.0 ) - scalar = 0.7; - else - scalar = 0.6; + if (tinkerSkill >= 100.0) + scalar = 1.0; + else if (tinkerSkill >= 90.0) + scalar = 0.9; + else if (tinkerSkill >= 80.0) + scalar = 0.8; + else if (tinkerSkill >= 70.0) + scalar = 0.7; + else + scalar = 0.6; - Container pack = from.Backpack; + Container pack = from.Backpack; - if ( pack == null ) - return; + if (pack == null) + return; - int res = pack.ConsumeTotal( - new[] - { - typeof( PowerCrystal ), - typeof( IronIngot ), - typeof( BronzeIngot ), - typeof( Gears ) - }, - new[] - { - 1, - 50, - 50, - 5 - } ); + int res = pack.ConsumeTotal( + new[] + { + typeof(PowerCrystal), + typeof(IronIngot), + typeof(BronzeIngot), + typeof(Gears) + }, + new[] + { + 1, + 50, + 50, + 5 + }); - switch ( res ) - { - case 0: - { - from.SendMessage( "You must have a power crystal to construct the golem." ); - break; - } - case 1: - { - from.SendMessage( "You must have 50 iron ingots to construct the golem." ); - break; - } - case 2: - { - from.SendMessage( "You must have 50 bronze ingots to construct the golem." ); - break; - } - case 3: - { - from.SendMessage( "You must have 5 gears to construct the golem." ); - break; - } - default: - { - Golem g = new Golem( true, scalar ); + switch (res) + { + case 0: + { + from.SendMessage("You must have a power crystal to construct the golem."); + break; + } + case 1: + { + from.SendMessage("You must have 50 iron ingots to construct the golem."); + break; + } + case 2: + { + from.SendMessage("You must have 50 bronze ingots to construct the golem."); + break; + } + case 3: + { + from.SendMessage("You must have 5 gears to construct the golem."); + break; + } + default: + { + Golem g = new Golem(true, scalar); - if ( g.SetControlMaster( from ) ) - { - Delete(); + if (g.SetControlMaster(from)) + { + Delete(); - g.MoveToWorld( from.Location, from.Map ); - from.PlaySound( 0x241 ); - } + g.MoveToWorld(from.Location, from.Map); + from.PlaySound(0x241); + } - break; - } - } - } + break; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/CommunicationCrystals.cs b/Scripts/Items/Misc/CommunicationCrystals.cs index 345d452c7..aa9b7873f 100644 --- a/Scripts/Items/Misc/CommunicationCrystals.cs +++ b/Scripts/Items/Misc/CommunicationCrystals.cs @@ -1,466 +1,455 @@ using System; +using System.Collections.Generic; using Server.Network; using Server.Targeting; -using System.Collections.Generic; namespace Server.Items { - public class CrystalRechargeInfo - { - public static readonly CrystalRechargeInfo[] Table = { - new CrystalRechargeInfo( typeof( Citrine ), 500 ), - new CrystalRechargeInfo( typeof( Amber ), 500 ), - new CrystalRechargeInfo( typeof( Tourmaline ), 750 ), - new CrystalRechargeInfo( typeof( Emerald ), 1000 ), - new CrystalRechargeInfo( typeof( Sapphire ), 1000 ), - new CrystalRechargeInfo( typeof( Amethyst ), 1000 ), - new CrystalRechargeInfo( typeof( StarSapphire ), 1250 ), - new CrystalRechargeInfo( typeof( Diamond ), 2000 ) - }; - - public static CrystalRechargeInfo Get( Type type ) - { - foreach ( CrystalRechargeInfo info in Table ) - { - if ( info.Type == type ) - return info; - } - - return null; - } - - public Type Type { get; } - - public int Amount { get; } - - private CrystalRechargeInfo( Type type, int amount ) - { - Type = type; - Amount = amount; - } - } - - public class BroadcastCrystal : Item - { - public static readonly int MaxCharges = 2000; - - public override int LabelNumber => 1060740; // communication crystal - - private int m_Charges; - - [CommandProperty( AccessLevel.GameMaster )] - public bool Active - { - get => ItemID == 0x1ECD; - set - { - ItemID = value ? 0x1ECD : 0x1ED0; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set - { - m_Charges = value; - InvalidateProperties(); - } - } - - public List Receivers { get; private set; } - - [Constructible] - public BroadcastCrystal() : this( 2000 ) - { - } - - [Constructible] - public BroadcastCrystal( int charges ) : base( 0x1ED0 ) - { - Light = LightType.Circle150; - - m_Charges = charges; - - Receivers = new List(); - } - - public BroadcastCrystal( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - list.Add( Active ? 1060742 : 1060743 ); // active / inactive - list.Add( 1060745 ); // broadcast - list.Add( 1060741, Charges.ToString() ); // charges: ~1_val~ - - if ( Receivers.Count > 0 ) - list.Add( 1060746, Receivers.Count.ToString() ); // links: ~1_val~ - } - - public override void OnSingleClick(Mobile from) - { - base.OnSingleClick( from ); - - LabelTo( from, Active ? 1060742 : 1060743 ); // active / inactive - LabelTo( from, 1060745 ); // broadcast - LabelTo( from, 1060741, Charges.ToString() ); // charges: ~1_val~ - - if ( Receivers.Count > 0 ) - LabelTo( from, 1060746, Receivers.Count.ToString() ); // links: ~1_val~ - } - - public override bool HandlesOnSpeech => true; - - public override void OnSpeech( SpeechEventArgs e ) - { - if ( !Active || Receivers.Count == 0 || ( RootParent != null && !(RootParent is Mobile) ) ) - return; - - if ( e.Type == MessageType.Emote ) - return; - - Mobile from = e.Mobile; - string speech = e.Speech; - - foreach ( ReceiverCrystal receiver in new List( Receivers ) ) - { - if ( receiver.Deleted ) - { - Receivers.Remove( receiver ); - } - else if ( Charges > 0 ) - { - receiver.TransmitMessage( from, speech ); - Charges--; - } - else - { - Active = false; - break; - } - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - from.Target = new InternalTarget( this ); - } - - private class InternalTarget : Target - { - private BroadcastCrystal m_Crystal; - - public InternalTarget( BroadcastCrystal crystal ) : base( 2, false, TargetFlags.None ) - { - m_Crystal = crystal; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Crystal.IsAccessibleTo( from ) ) - return; - - if ( from.Map != m_Crystal.Map || !from.InRange( m_Crystal.GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - if ( targeted == m_Crystal ) - { - if ( m_Crystal.Active ) - { - m_Crystal.Active = false; - from.SendLocalizedMessage( 500672 ); // You turn the crystal off. - } - else - { - if ( m_Crystal.Charges > 0 ) - { - m_Crystal.Active = true; - from.SendLocalizedMessage( 500673 ); // You turn the crystal on. - } - else - { - from.SendLocalizedMessage( 500676 ); // This crystal is out of charges. - } - } - } - else if ( targeted is ReceiverCrystal receiver ) - { - if ( m_Crystal.Receivers.Count >= 10 ) - { - from.SendLocalizedMessage( 1010042 ); // This broadcast crystal is already linked to 10 receivers. - } - else if ( receiver.Sender == m_Crystal ) - { - from.SendLocalizedMessage( 500674 ); // This crystal is already linked with that crystal. - } - else if ( receiver.Sender != null ) - { - from.SendLocalizedMessage( 1010043 ); // That receiver crystal is already linked to another broadcast crystal. - } - else - { - receiver.Sender = m_Crystal; - from.SendLocalizedMessage( 500675 ); // That crystal has been linked to this crystal. - } - } - else if ( targeted == from ) - { - foreach( ReceiverCrystal rc in new List( m_Crystal.Receivers ) ) - { - rc.Sender = null; - } - - from.SendLocalizedMessage( 1010046 ); // You unlink the broadcast crystal from all of its receivers. - } - else - { - if ( targeted is Item targItem && targItem.VerifyMove( from ) ) - { - CrystalRechargeInfo info = CrystalRechargeInfo.Get( targItem.GetType() ); - - if ( info != null ) - { - if ( m_Crystal.Charges >= MaxCharges ) - { - from.SendLocalizedMessage( 500678 ); // This crystal is already fully charged. - } - else - { - targItem.Consume(); - - if ( m_Crystal.Charges + info.Amount >= MaxCharges ) - { - m_Crystal.Charges = MaxCharges; - from.SendLocalizedMessage( 500679 ); // You completely recharge the crystal. - } - else - { - m_Crystal.Charges += info.Amount; - from.SendLocalizedMessage( 500680 ); // You recharge the crystal. - } - } - - return; - } - } - - from.SendLocalizedMessage( 500681 ); // You cannot use this crystal on that. - } - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.WriteEncodedInt( m_Charges ); - writer.WriteItemList( Receivers ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Charges = reader.ReadEncodedInt(); - Receivers = reader.ReadStrongItemList(); - } - } - - public class ReceiverCrystal : Item - { - public override int LabelNumber => 1060740; // communication crystal - - private BroadcastCrystal m_Sender; - - [CommandProperty( AccessLevel.GameMaster )] - public bool Active - { - get => ItemID == 0x1ED1; - set - { - ItemID = value ? 0x1ED1 : 0x1ED0; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public BroadcastCrystal Sender - { - get => m_Sender; - set - { - if ( m_Sender != null ) - { - m_Sender.Receivers.Remove( this ); - m_Sender.InvalidateProperties(); - } - - m_Sender = value; - - if ( value != null ) - { - value.Receivers.Add( this ); - value.InvalidateProperties(); - } - } - } - - [Constructible] - public ReceiverCrystal() : base( 0x1ED0 ) - { - Light = LightType.Circle150; - } - - public ReceiverCrystal( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - list.Add( Active ? 1060742 : 1060743 ); // active / inactive - list.Add( 1060744 ); // receiver - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - LabelTo( from, Active ? 1060742 : 1060743 ); // active / inactive - LabelTo( from, 1060744 ); // receiver - } - - public void TransmitMessage( Mobile from, string message ) - { - if ( !Active ) - return; - - string text = $"{from.Name} says {message}"; - - if ( RootParent is Mobile mobile ) - { - mobile.SendMessage( 0x2B2, "Crystal: " + text ); - } - else if ( RootParent is Item item ) - { - item.PublicOverheadMessage( MessageType.Regular, 0x2B2, false, "Crystal: " + text ); - } - else - { - PublicOverheadMessage( MessageType.Regular, 0x2B2, false, text ); - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - from.Target = new InternalTarget( this ); - } - - private class InternalTarget : Target - { - private ReceiverCrystal m_Crystal; - - public InternalTarget( ReceiverCrystal crystal ) : base( -1, false, TargetFlags.None ) - { - m_Crystal = crystal; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Crystal.IsAccessibleTo( from ) ) - return; - - if ( from.Map != m_Crystal.Map || !from.InRange( m_Crystal.GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - if ( targeted == m_Crystal ) - { - if ( m_Crystal.Active ) - { - m_Crystal.Active = false; - from.SendLocalizedMessage( 500672 ); // You turn the crystal off. - } - else - { - m_Crystal.Active = true; - from.SendLocalizedMessage( 500673 ); // You turn the crystal on. - } - } - else if ( targeted == from ) - { - if ( m_Crystal.Sender != null ) - { - m_Crystal.Sender = null; - from.SendLocalizedMessage( 1010044 ); // You unlink the receiver crystal. - } - else - { - from.SendLocalizedMessage( 1010045 ); // That receiver crystal is not linked. - } - } - else - { - if ( targeted is Item targItem && targItem.VerifyMove( from ) ) - { - CrystalRechargeInfo info = CrystalRechargeInfo.Get( targItem.GetType() ); - - if ( info != null ) - { - from.SendLocalizedMessage( 500677 ); // This crystal cannot be recharged. - return; - } - } - - from.SendLocalizedMessage( 1010045 ); // That receiver crystal is not linked. - } - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.WriteItem( m_Sender ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Sender = reader.ReadItem(); - } - } -} + public class CrystalRechargeInfo + { + public static readonly CrystalRechargeInfo[] Table = + { + new CrystalRechargeInfo(typeof(Citrine), 500), + new CrystalRechargeInfo(typeof(Amber), 500), + new CrystalRechargeInfo(typeof(Tourmaline), 750), + new CrystalRechargeInfo(typeof(Emerald), 1000), + new CrystalRechargeInfo(typeof(Sapphire), 1000), + new CrystalRechargeInfo(typeof(Amethyst), 1000), + new CrystalRechargeInfo(typeof(StarSapphire), 1250), + new CrystalRechargeInfo(typeof(Diamond), 2000) + }; + + private CrystalRechargeInfo(Type type, int amount) + { + Type = type; + Amount = amount; + } + + public Type Type{ get; } + + public int Amount{ get; } + + public static CrystalRechargeInfo Get(Type type) + { + foreach (CrystalRechargeInfo info in Table) + if (info.Type == type) + return info; + + return null; + } + } + + public class BroadcastCrystal : Item + { + public static readonly int MaxCharges = 2000; + + private int m_Charges; + + [Constructible] + public BroadcastCrystal() : this(2000) + { + } + + [Constructible] + public BroadcastCrystal(int charges) : base(0x1ED0) + { + Light = LightType.Circle150; + + m_Charges = charges; + + Receivers = new List(); + } + + public BroadcastCrystal(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1060740; // communication crystal + + [CommandProperty(AccessLevel.GameMaster)] + public bool Active + { + get => ItemID == 0x1ECD; + set + { + ItemID = value ? 0x1ECD : 0x1ED0; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + InvalidateProperties(); + } + } + + public List Receivers{ get; private set; } + + public override bool HandlesOnSpeech => true; + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(Active ? 1060742 : 1060743); // active / inactive + list.Add(1060745); // broadcast + list.Add(1060741, Charges.ToString()); // charges: ~1_val~ + + if (Receivers.Count > 0) + list.Add(1060746, Receivers.Count.ToString()); // links: ~1_val~ + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + LabelTo(from, Active ? 1060742 : 1060743); // active / inactive + LabelTo(from, 1060745); // broadcast + LabelTo(from, 1060741, Charges.ToString()); // charges: ~1_val~ + + if (Receivers.Count > 0) + LabelTo(from, 1060746, Receivers.Count.ToString()); // links: ~1_val~ + } + + public override void OnSpeech(SpeechEventArgs e) + { + if (!Active || Receivers.Count == 0 || RootParent != null && !(RootParent is Mobile)) + return; + + if (e.Type == MessageType.Emote) + return; + + Mobile from = e.Mobile; + string speech = e.Speech; + + foreach (ReceiverCrystal receiver in new List(Receivers)) + if (receiver.Deleted) + { + Receivers.Remove(receiver); + } + else if (Charges > 0) + { + receiver.TransmitMessage(from, speech); + Charges--; + } + else + { + Active = false; + break; + } + } + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + from.Target = new InternalTarget(this); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(m_Charges); + writer.WriteItemList(Receivers); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Charges = reader.ReadEncodedInt(); + Receivers = reader.ReadStrongItemList(); + } + + private class InternalTarget : Target + { + private BroadcastCrystal m_Crystal; + + public InternalTarget(BroadcastCrystal crystal) : base(2, false, TargetFlags.None) + { + m_Crystal = crystal; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Crystal.IsAccessibleTo(from)) + return; + + if (from.Map != m_Crystal.Map || !from.InRange(m_Crystal.GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + if (targeted == m_Crystal) + { + if (m_Crystal.Active) + { + m_Crystal.Active = false; + from.SendLocalizedMessage(500672); // You turn the crystal off. + } + else + { + if (m_Crystal.Charges > 0) + { + m_Crystal.Active = true; + from.SendLocalizedMessage(500673); // You turn the crystal on. + } + else + { + from.SendLocalizedMessage(500676); // This crystal is out of charges. + } + } + } + else if (targeted is ReceiverCrystal receiver) + { + if (m_Crystal.Receivers.Count >= 10) + { + from.SendLocalizedMessage(1010042); // This broadcast crystal is already linked to 10 receivers. + } + else if (receiver.Sender == m_Crystal) + { + from.SendLocalizedMessage(500674); // This crystal is already linked with that crystal. + } + else if (receiver.Sender != null) + { + from.SendLocalizedMessage( + 1010043); // That receiver crystal is already linked to another broadcast crystal. + } + else + { + receiver.Sender = m_Crystal; + from.SendLocalizedMessage(500675); // That crystal has been linked to this crystal. + } + } + else if (targeted == from) + { + foreach (ReceiverCrystal rc in new List(m_Crystal.Receivers)) rc.Sender = null; + + from.SendLocalizedMessage(1010046); // You unlink the broadcast crystal from all of its receivers. + } + else + { + if (targeted is Item targItem && targItem.VerifyMove(from)) + { + CrystalRechargeInfo info = CrystalRechargeInfo.Get(targItem.GetType()); + + if (info != null) + { + if (m_Crystal.Charges >= MaxCharges) + { + from.SendLocalizedMessage(500678); // This crystal is already fully charged. + } + else + { + targItem.Consume(); + + if (m_Crystal.Charges + info.Amount >= MaxCharges) + { + m_Crystal.Charges = MaxCharges; + from.SendLocalizedMessage(500679); // You completely recharge the crystal. + } + else + { + m_Crystal.Charges += info.Amount; + from.SendLocalizedMessage(500680); // You recharge the crystal. + } + } + + return; + } + } + + from.SendLocalizedMessage(500681); // You cannot use this crystal on that. + } + } + } + } + + public class ReceiverCrystal : Item + { + private BroadcastCrystal m_Sender; + + [Constructible] + public ReceiverCrystal() : base(0x1ED0) + { + Light = LightType.Circle150; + } + + public ReceiverCrystal(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1060740; // communication crystal + + [CommandProperty(AccessLevel.GameMaster)] + public bool Active + { + get => ItemID == 0x1ED1; + set + { + ItemID = value ? 0x1ED1 : 0x1ED0; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public BroadcastCrystal Sender + { + get => m_Sender; + set + { + if (m_Sender != null) + { + m_Sender.Receivers.Remove(this); + m_Sender.InvalidateProperties(); + } + + m_Sender = value; + + if (value != null) + { + value.Receivers.Add(this); + value.InvalidateProperties(); + } + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(Active ? 1060742 : 1060743); // active / inactive + list.Add(1060744); // receiver + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + LabelTo(from, Active ? 1060742 : 1060743); // active / inactive + LabelTo(from, 1060744); // receiver + } + + public void TransmitMessage(Mobile from, string message) + { + if (!Active) + return; + + string text = $"{from.Name} says {message}"; + + if (RootParent is Mobile mobile) + mobile.SendMessage(0x2B2, "Crystal: " + text); + else if (RootParent is Item item) + item.PublicOverheadMessage(MessageType.Regular, 0x2B2, false, "Crystal: " + text); + else + PublicOverheadMessage(MessageType.Regular, 0x2B2, false, text); + } + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + from.Target = new InternalTarget(this); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteItem(m_Sender); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Sender = reader.ReadItem(); + } + + private class InternalTarget : Target + { + private ReceiverCrystal m_Crystal; + + public InternalTarget(ReceiverCrystal crystal) : base(-1, false, TargetFlags.None) + { + m_Crystal = crystal; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Crystal.IsAccessibleTo(from)) + return; + + if (from.Map != m_Crystal.Map || !from.InRange(m_Crystal.GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + if (targeted == m_Crystal) + { + if (m_Crystal.Active) + { + m_Crystal.Active = false; + from.SendLocalizedMessage(500672); // You turn the crystal off. + } + else + { + m_Crystal.Active = true; + from.SendLocalizedMessage(500673); // You turn the crystal on. + } + } + else if (targeted == from) + { + if (m_Crystal.Sender != null) + { + m_Crystal.Sender = null; + from.SendLocalizedMessage(1010044); // You unlink the receiver crystal. + } + else + { + from.SendLocalizedMessage(1010045); // That receiver crystal is not linked. + } + } + else + { + if (targeted is Item targItem && targItem.VerifyMove(from)) + { + CrystalRechargeInfo info = CrystalRechargeInfo.Get(targItem.GetType()); + + if (info != null) + { + from.SendLocalizedMessage(500677); // This crystal cannot be recharged. + return; + } + } + + from.SendLocalizedMessage(1010045); // That receiver crystal is not linked. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Corpses/Corpse.cs b/Scripts/Items/Misc/Corpses/Corpse.cs index d5b78a0ee..fa7eec7f2 100644 --- a/Scripts/Items/Misc/Corpses/Corpse.cs +++ b/Scripts/Items/Misc/Corpses/Corpse.cs @@ -12,1197 +12,1201 @@ using Server.Network; namespace Server.Items { - public interface IDevourer - { - bool Devour( Corpse corpse ); - } - - [Flags] - public enum CorpseFlag - { - None = 0x00000000, - - /// - /// Has this corpse been carved? - /// - Carved = 0x00000001, - - /// - /// If true, this corpse will not turn into bones - /// - NoBones = 0x00000002, - - /// - /// If true, the corpse has turned into bones - /// - IsBones = 0x00000004, - - /// - /// Has this corpse yet been visited by a taxidermist? - /// - VisitedByTaxidermist = 0x00000008, - - /// - /// Has this corpse yet been used to channel spiritual energy? (AOS Spirit Speak) - /// - Channeled = 0x00000010, - - /// - /// Was the owner criminal when he died? - /// - Criminal = 0x00000020, - - /// - /// Has this corpse been animated? - /// - Animated = 0x00000040, - - /// - /// Has this corpse been self looted? - /// - SelfLooted = 0x00000080, - } - - public class Corpse : Container, ICarvable - { - private CorpseFlag m_Flags; // @see CorpseFlag - - private string m_CorpseName; // Value of the CorpseNameAttribute attached to the owner when he died -or- null if the owner had no CorpseNameAttribute; use "the remains of ~name~" - private IDevourer m_Devourer; // The creature that devoured this corpse - - // For notoriety: - - // For Forensics Evaluation - public string m_Forensicist; // Name of the first PlayerMobile who used Forensic Evaluation on the corpse - - public static readonly TimeSpan MonsterLootRightSacrifice = TimeSpan.FromMinutes( 2.0 ); - - public static readonly TimeSpan InstancedCorpseTime = TimeSpan.FromMinutes( 3.0 ); - - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool InstancedCorpse - { - get - { - if ( !Core.SE ) - return false; - - return ( DateTime.UtcNow < (TimeOfDeath + InstancedCorpseTime) ); - } - } - - private Dictionary m_InstancedItems; - - private class InstancedItemInfo - { - private Mobile m_Mobile; - private Item m_Item; - - public bool Perpetual { get; set; } - - public InstancedItemInfo( Item i, Mobile m ) - { - m_Item = i; - m_Mobile = m; - } - - public bool IsOwner( Mobile m ) - { - if ( m_Item.LootType == LootType.Cursed ) //Cursed Items are part of everyone's instanced corpse... (?) - return true; - - if ( m == null ) - return false; //sanity - - if ( m_Mobile == m ) - return true; - - Party myParty = Party.Get( m_Mobile ); - - return (myParty != null && myParty == Party.Get( m )); - } - } - - public override bool IsChildVisibleTo( Mobile m, Item child ) - { - if ( !m.Player || m.AccessLevel > AccessLevel.Player ) //Staff and creatures not subject to instancing. - return true; - - if ( m_InstancedItems != null ) - { - if ( m_InstancedItems.TryGetValue( child, out InstancedItemInfo info ) && (InstancedCorpse || info.Perpetual) ) - { - return info.IsOwner( m ); //IsOwner checks Party stuff. - } - } - - return true; - } - - private void AssignInstancedLoot() - { - if ( Aggressors.Count == 0 || Items.Count == 0 ) - return; - - if ( m_InstancedItems == null ) - m_InstancedItems = new Dictionary(); + public interface IDevourer + { + bool Devour(Corpse corpse); + } - List m_Stackables = new List(); - List m_Unstackables = new List(); + [Flags] + public enum CorpseFlag + { + None = 0x00000000, - for ( int i = 0; i < Items.Count; i++ ) - { - Item item = Items[i]; - - if ( item.LootType != LootType.Cursed ) //Don't have curesd items take up someone's item spot.. (?) - { - if ( item.Stackable ) - m_Stackables.Add( item ); - else - m_Unstackables.Add( item ); - } - } - - List attackers = new List( Aggressors ); - - for ( int i = 1; i < attackers.Count -1; i++ ) //randomize - { - int rand = Utility.Random( i + 1 ); - - Mobile temp = attackers[rand]; - attackers[rand] = attackers[i]; - attackers[i] = temp; - } - - //stackables first, for the remaining stackables, have those be randomly added after - - for ( int i = 0; i < m_Stackables.Count; i++ ) - { - Item item = m_Stackables[i]; - - if ( item.Amount >= attackers.Count ) - { - int amountPerAttacker = (item.Amount / attackers.Count); - int remainder = (item.Amount % attackers.Count); - - for ( int j = 0; j < ((remainder == 0) ? attackers.Count -1 : attackers.Count); j++ ) - { - Item splitItem = Mobile.LiftItemDupe( item, item.Amount - amountPerAttacker ); //LiftItemDupe automagically adds it as a child item to the corpse - - m_InstancedItems.Add( splitItem, new InstancedItemInfo( splitItem, attackers[j] ) ); - - //What happens to the remaining portion? TEMP FOR NOW UNTIL OSI VERIFICATION: Treat as Single Item. - } - - if ( remainder == 0 ) - { - m_InstancedItems.Add( item, new InstancedItemInfo( item, attackers[attackers.Count - 1] ) ); - //Add in the original item (which has an equal amount as the others) to the instance for the last attacker, cause it wasn't added above. - } - else - { - m_Unstackables.Add( item ); - } - } - else - { - //What happens in this case? TEMP FOR NOW UNTIL OSI VERIFICATION: Treat as Single Item. - m_Unstackables.Add( item ); - } - } - - for ( int i = 0; i < m_Unstackables.Count; i++ ) - { - Mobile m = attackers[i % attackers.Count]; - Item item = m_Unstackables[i]; - - m_InstancedItems.Add( item, new InstancedItemInfo( item, m ) ); - } - } - - public void AddCarvedItem( Item carved, Mobile carver ) - { - DropItem( carved ); - - if ( InstancedCorpse ) - { - if ( m_InstancedItems == null ) - m_InstancedItems = new Dictionary(); - - m_InstancedItems.Add( carved, new InstancedItemInfo( carved, carver ) ); - } - } - - public override bool IsDecoContainer => false; - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime TimeOfDeath { get; set; } - - public override bool DisplayWeight => false; - - public HairInfo Hair { get; } - - public FacialHairInfo FacialHair { get; } + /// + /// Has this corpse been carved? + /// + Carved = 0x00000001, - [CommandProperty( AccessLevel.GameMaster )] - public bool IsBones => GetFlag( CorpseFlag.IsBones ); + /// + /// If true, this corpse will not turn into bones + /// + NoBones = 0x00000002, - [CommandProperty( AccessLevel.GameMaster )] - public bool Devoured => (m_Devourer != null); - - [CommandProperty( AccessLevel.GameMaster )] - public bool Carved - { - get => GetFlag( CorpseFlag.Carved ); - set => SetFlag( CorpseFlag.Carved, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool VisitedByTaxidermist - { - get => GetFlag( CorpseFlag.VisitedByTaxidermist ); - set => SetFlag( CorpseFlag.VisitedByTaxidermist, value ); - } + /// + /// If true, the corpse has turned into bones + /// + IsBones = 0x00000004, - [CommandProperty( AccessLevel.GameMaster )] - public bool Channeled - { - get => GetFlag( CorpseFlag.Channeled ); - set => SetFlag( CorpseFlag.Channeled, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Animated - { - get => GetFlag( CorpseFlag.Animated ); - set => SetFlag( CorpseFlag.Animated, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool SelfLooted - { - get => GetFlag( CorpseFlag.SelfLooted ); - set => SetFlag( CorpseFlag.SelfLooted, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public AccessLevel AccessLevel { get; private set; } - - public List Aggressors { get; private set; } - - public List Looters { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Killer { get; private set; } - - public List EquipItems { get; private set; } - - public List RestoreEquip { get; set; } - - public Guild Guild { get; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Kills { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Criminal - { - get => GetFlag( CorpseFlag.Criminal ); - set => SetFlag( CorpseFlag.Criminal, value ); - } + /// + /// Has this corpse yet been visited by a taxidermist? + /// + VisitedByTaxidermist = 0x00000008, - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; private set; } + /// + /// Has this corpse yet been used to channel spiritual energy? (AOS Spirit Speak) + /// + Channeled = 0x00000010, - public void TurnToBones() - { - if ( Deleted ) - return; - - ProcessDelta(); - SendRemovePacket(); - ItemID = Utility.Random( 0xECA, 9 ); // bone graphic - Hue = 0; - ProcessDelta(); - - SetFlag( CorpseFlag.NoBones, true ); - SetFlag( CorpseFlag.IsBones, true ); - - BeginDecay( m_BoneDecayTime ); - } - - private static TimeSpan m_DefaultDecayTime = TimeSpan.FromMinutes( 7.0 ); - private static TimeSpan m_BoneDecayTime = TimeSpan.FromMinutes( 7.0 ); - - private Timer m_DecayTimer; - private DateTime m_DecayTime; - - public void BeginDecay( TimeSpan delay ) - { - m_DecayTimer?.Stop(); - - m_DecayTime = DateTime.UtcNow + delay; - - m_DecayTimer = new InternalTimer( this, delay ); - m_DecayTimer.Start(); - } - - public override void OnAfterDelete() - { - m_DecayTimer?.Stop(); - - m_DecayTimer = null; - } - - private class InternalTimer : Timer - { - private Corpse m_Corpse; - - public InternalTimer( Corpse c, TimeSpan delay ) : base( delay ) - { - m_Corpse = c; - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - if ( !m_Corpse.GetFlag( CorpseFlag.NoBones ) ) - m_Corpse.TurnToBones(); - else - m_Corpse.Delete(); - } - } - - public static string GetCorpseName( Mobile m ) - { - return m is BaseCreature bc ? bc.CorpseNameOverride ?? bc.CorpseName : null; - } + /// + /// Was the owner criminal when he died? + /// + Criminal = 0x00000020, - public static void Initialize() - { - Mobile.CreateCorpseHandler += Mobile_CreateCorpseHandler; - } + /// + /// Has this corpse been animated? + /// + Animated = 0x00000040, - public static Container Mobile_CreateCorpseHandler( Mobile owner, HairInfo hair, FacialHairInfo facialhair, List initialContent, List equipItems ) - { - bool shouldFillCorpse = true; + /// + /// Has this corpse been self looted? + /// + SelfLooted = 0x00000080 + } - //if ( owner is BaseCreature ) - // shouldFillCorpse = !((BaseCreature)owner).IsBonded; + public class Corpse : Container, ICarvable + { + public static readonly TimeSpan MonsterLootRightSacrifice = TimeSpan.FromMinutes(2.0); - Corpse c; - if ( owner is MilitiaFighter ) - c = new MilitiaFighterCorpse( owner, hair, facialhair, shouldFillCorpse ? equipItems : new List() ); - else - c = new Corpse( owner, hair, facialhair, shouldFillCorpse ? equipItems : new List() ); + public static readonly TimeSpan InstancedCorpseTime = TimeSpan.FromMinutes(3.0); - owner.Corpse = c; - - if ( shouldFillCorpse ) - { - for ( int i = 0; i < initialContent.Count; ++i ) - { - Item item = initialContent[i]; - - if ( Core.AOS && owner.Player && item.Parent == owner.Backpack ) - c.AddItem( item ); - else - c.DropItem( item ); - - if ( owner.Player && Core.AOS ) - c.SetRestoreInfo( item, item.Location ); - } - - if ( Core.SE && !owner.Player ) - { - c.AssignInstancedLoot(); - } - else if ( Core.AOS && owner is PlayerMobile pm ) - c.RestoreEquip = pm.EquipSnapshot; - } - else - { - c.Carved = true; // TODO: Is it needed? - } - - Point3D loc = owner.Location; - Map map = owner.Map; - - if ( map == null || map == Map.Internal ) - { - loc = owner.LogoutLocation; - map = owner.LogoutMap; - } - - c.MoveToWorld( loc, map ); - - return c; - } - - // Why was this public? - // public override bool IsPublicContainer => true; - - public Corpse( Mobile owner, List equipItems ) : this( owner, null, null, equipItems ) - { - } - - public Corpse( Mobile owner, HairInfo hair, FacialHairInfo facialhair, List equipItems ) - : base( 0x2006 ) - { - // To supress console warnings, stackable must be true - Stackable = true; - Amount = owner.Body; // protocol defines that for itemid 0x2006, amount=body - Stackable = false; - - Movable = false; - Hue = owner.Hue; - Direction = owner.Direction; - Name = owner.Name; - - Owner = owner; - - m_CorpseName = GetCorpseName( owner ); - - TimeOfDeath = DateTime.UtcNow; - - AccessLevel = owner.AccessLevel; - Guild = owner.Guild as Guild; - Kills = owner.Kills; - SetFlag( CorpseFlag.Criminal, owner.Criminal ); - - Hair = hair; - FacialHair = facialhair; - - // This corpse does not turn to bones if: the owner is not a player - SetFlag( CorpseFlag.NoBones, !owner.Player ); + private static TimeSpan m_DefaultDecayTime = TimeSpan.FromMinutes(7.0); + private static TimeSpan m_BoneDecayTime = TimeSpan.FromMinutes(7.0); - Looters = new List(); - EquipItems = equipItems; - - Aggressors = new List( owner.Aggressors.Count + owner.Aggressed.Count ); - //bool addToAggressors = !( owner is BaseCreature ); + private string + m_CorpseName; // Value of the CorpseNameAttribute attached to the owner when he died -or- null if the owner had no CorpseNameAttribute; use "the remains of ~name~" - bool isBaseCreature = (owner is BaseCreature); + private DateTime m_DecayTime; - TimeSpan lastTime = TimeSpan.MaxValue; + private Timer m_DecayTimer; + private IDevourer m_Devourer; // The creature that devoured this corpse + private CorpseFlag m_Flags; // @see CorpseFlag - for ( int i = 0; i < owner.Aggressors.Count; ++i ) - { - AggressorInfo info = owner.Aggressors[i]; - - if ( (DateTime.UtcNow - info.LastCombatTime) < lastTime ) - { - Killer = info.Attacker; - lastTime = (DateTime.UtcNow - info.LastCombatTime); - } - - if ( !isBaseCreature && !info.CriminalAggression ) - Aggressors.Add( info.Attacker ); - } - - for ( int i = 0; i < owner.Aggressed.Count; ++i ) - { - AggressorInfo info = owner.Aggressed[i]; + // For notoriety: - if ( (DateTime.UtcNow - info.LastCombatTime) < lastTime ) - { - Killer = info.Defender; - lastTime = (DateTime.UtcNow - info.LastCombatTime); - } + // For Forensics Evaluation + public string m_Forensicist; // Name of the first PlayerMobile who used Forensic Evaluation on the corpse - if ( !isBaseCreature ) - Aggressors.Add( info.Defender ); - } + private Dictionary m_InstancedItems; - if ( isBaseCreature ) - { - BaseCreature bc = (BaseCreature)owner; + private Dictionary m_RestoreTable; - Mobile master = bc.GetMaster(); - if ( master != null ) - Aggressors.Add( master ); + // Why was this public? + // public override bool IsPublicContainer => true; - List rights = BaseCreature.GetLootingRights( bc.DamageEntries, bc.HitsMax ); - for ( int i = 0; i < rights.Count; ++i ) - { - DamageStore ds = rights[i]; + public Corpse(Mobile owner, List equipItems) : this(owner, null, null, equipItems) + { + } - if ( ds.m_HasRight ) - Aggressors.Add( ds.m_Mobile ); - } - } + public Corpse(Mobile owner, HairInfo hair, FacialHairInfo facialhair, List equipItems) + : base(0x2006) + { + // To supress console warnings, stackable must be true + Stackable = true; + Amount = owner.Body; // protocol defines that for itemid 0x2006, amount=body + Stackable = false; - BeginDecay( m_DefaultDecayTime ); + Movable = false; + Hue = owner.Hue; + Direction = owner.Direction; + Name = owner.Name; - DevourCorpse(); - } + Owner = owner; - public Corpse( Serial serial ) : base( serial ) - { - } + m_CorpseName = GetCorpseName(owner); - protected bool GetFlag( CorpseFlag flag ) - { - return ((m_Flags & flag) != 0); - } + TimeOfDeath = DateTime.UtcNow; - protected void SetFlag( CorpseFlag flag, bool on ) - { - m_Flags = (on ? m_Flags | flag : m_Flags & ~flag); - } + AccessLevel = owner.AccessLevel; + Guild = owner.Guild as Guild; + Kills = owner.Kills; + SetFlag(CorpseFlag.Criminal, owner.Criminal); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Hair = hair; + FacialHair = facialhair; - writer.Write( (int) 12 ); // version + // This corpse does not turn to bones if: the owner is not a player + SetFlag(CorpseFlag.NoBones, !owner.Player); - if ( RestoreEquip == null ) - { - writer.Write( false ); - } - else - { - writer.Write( true ); - writer.Write( RestoreEquip ); - } + Looters = new List(); + EquipItems = equipItems; - writer.Write( (int)m_Flags ); + Aggressors = new List(owner.Aggressors.Count + owner.Aggressed.Count); + //bool addToAggressors = !( owner is BaseCreature ); - writer.WriteDeltaTime( TimeOfDeath ); + bool isBaseCreature = owner is BaseCreature; - List> list = ( m_RestoreTable == null ? null : new List>( m_RestoreTable ) ); - int count = list?.Count ?? 0; + TimeSpan lastTime = TimeSpan.MaxValue; - writer.Write( count ); + for (int i = 0; i < owner.Aggressors.Count; ++i) + { + AggressorInfo info = owner.Aggressors[i]; - for ( int i = 0; i < count; ++i ) - { - KeyValuePair kvp = list[i]; - Item item = kvp.Key; - Point3D loc = kvp.Value; + if (DateTime.UtcNow - info.LastCombatTime < lastTime) + { + Killer = info.Attacker; + lastTime = DateTime.UtcNow - info.LastCombatTime; + } - writer.Write( item ); + if (!isBaseCreature && !info.CriminalAggression) + Aggressors.Add(info.Attacker); + } - if ( item.Location == loc ) - { - writer.Write( false ); - } - else - { - writer.Write( true ); - writer.Write( loc ); - } - } + for (int i = 0; i < owner.Aggressed.Count; ++i) + { + AggressorInfo info = owner.Aggressed[i]; - writer.Write( m_DecayTimer != null ); - - if ( m_DecayTimer != null ) - writer.WriteDeltaTime( m_DecayTime ); - - writer.Write( Looters ); - writer.Write( Killer ); - - writer.Write( Aggressors ); - - writer.Write( Owner ); - - writer.Write( (string) m_CorpseName ); - - writer.Write( (int) AccessLevel ); - writer.Write( (Guild) Guild ); - writer.Write( (int) Kills ); - - writer.Write( EquipItems ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 12: - { - if ( reader.ReadBool() ) - RestoreEquip = reader.ReadStrongItemList(); - - goto case 11; - } - case 11: - { - // Version 11, we move all bools to a CorpseFlag - m_Flags = (CorpseFlag)reader.ReadInt(); - - TimeOfDeath = reader.ReadDeltaTime(); - - int count = reader.ReadInt(); - - for( int i = 0; i < count; ++i ) - { - Item item = reader.ReadItem(); - - if ( reader.ReadBool() ) - SetRestoreInfo( item, reader.ReadPoint3D() ); - else if ( item != null ) - SetRestoreInfo( item, item.Location ); - } - - if ( reader.ReadBool() ) - BeginDecay( reader.ReadDeltaTime() - DateTime.UtcNow ); - - Looters = reader.ReadStrongMobileList(); - Killer = reader.ReadMobile(); - - Aggressors = reader.ReadStrongMobileList(); - Owner = reader.ReadMobile(); - - m_CorpseName = reader.ReadString(); - - AccessLevel = (AccessLevel)reader.ReadInt(); - reader.ReadInt(); // guild reserve - Kills = reader.ReadInt(); - - EquipItems = reader.ReadStrongItemList(); - break; - } - case 10: - { - TimeOfDeath = reader.ReadDeltaTime(); - - goto case 9; - } - case 9: - { - int count = reader.ReadInt(); - - for ( int i = 0; i < count; ++i ) - { - Item item = reader.ReadItem(); - - if ( reader.ReadBool() ) - SetRestoreInfo( item, reader.ReadPoint3D() ); - else if ( item != null ) - SetRestoreInfo( item, item.Location ); - } - - goto case 8; - } - case 8: - { - SetFlag( CorpseFlag.VisitedByTaxidermist, reader.ReadBool() ); - - goto case 7; - } - case 7: - { - if ( reader.ReadBool() ) - BeginDecay( reader.ReadDeltaTime() - DateTime.UtcNow ); - - goto case 6; - } - case 6: - { - Looters = reader.ReadStrongMobileList(); - Killer = reader.ReadMobile(); - - goto case 5; - } - case 5: - { - SetFlag( CorpseFlag.Carved, reader.ReadBool() ); - - goto case 4; - } - case 4: - { - Aggressors = reader.ReadStrongMobileList(); - - goto case 3; - } - case 3: - { - Owner = reader.ReadMobile(); - - goto case 2; - } - case 2: - { - SetFlag( CorpseFlag.NoBones, reader.ReadBool() ); - - goto case 1; - } - case 1: - { - m_CorpseName = reader.ReadString(); - - goto case 0; - } - case 0: - { - if ( version < 10 ) - TimeOfDeath = DateTime.UtcNow; - - if ( version < 7 ) - BeginDecay( m_DefaultDecayTime ); - - if ( version < 6 ) - Looters = new List(); - - if ( version < 4 ) - Aggressors = new List(); - - AccessLevel = (AccessLevel)reader.ReadInt(); - reader.ReadInt(); // guild reserve - Kills = reader.ReadInt(); - SetFlag( CorpseFlag.Criminal, reader.ReadBool() ); - - EquipItems = reader.ReadStrongItemList(); - - break; - } - } - } - - public bool DevourCorpse() - { - if ( Devoured || Deleted || Killer == null || Killer.Deleted || !Killer.Alive || !(Killer is IDevourer) || Owner == null || Owner.Deleted ) - return false; - - m_Devourer = (IDevourer)Killer; // Set the devourer the killer - return m_Devourer.Devour( this ); // Devour the corpse if it hasn't - } - - public override void SendInfoTo( NetState state, bool sendOplPacket ) - { - base.SendInfoTo( state, sendOplPacket ); - - if (((Body)Amount).IsHuman && ItemID == 0x2006) - { - if (state.ContainerGridLines) - { - state.Send(new CorpseContent6017(state.Mobile, this)); - } - else - { - state.Send(new CorpseContent(state.Mobile, this)); - } - - state.Send(new CorpseEquip(state.Mobile, this)); - } - } - - public bool IsCriminalAction( Mobile from ) - { - if ( from == Owner || from.AccessLevel >= AccessLevel.GameMaster ) - return false; - - Party p = Party.Get( Owner ); - - if ( p != null && p.Contains( from ) ) - { - PartyMemberInfo pmi = p[Owner]; - - if ( pmi != null && pmi.CanLoot ) - return false; - } - - return ( NotorietyHandlers.CorpseNotoriety( from, this ) == Notoriety.Innocent ); - } - - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( !base.CheckItemUse( from, item ) ) - return false; - - if ( item != this ) - return CanLoot( from, item ); - - return true; - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( !base.CheckLift( from, item, ref reject ) ) - return false; + if (DateTime.UtcNow - info.LastCombatTime < lastTime) + { + Killer = info.Defender; + lastTime = DateTime.UtcNow - info.LastCombatTime; + } - return CanLoot( from,item ); - } + if (!isBaseCreature) + Aggressors.Add(info.Defender); + } - public override void OnItemUsed( Mobile from, Item item ) - { - base.OnItemUsed( from, item ); + if (isBaseCreature) + { + BaseCreature bc = (BaseCreature)owner; - if ( item is Food ) - from.RevealingAction(); + Mobile master = bc.GetMaster(); + if (master != null) + Aggressors.Add(master); - if ( item != this && IsCriminalAction( from ) ) - from.CriminalAction( true ); + List rights = BaseCreature.GetLootingRights(bc.DamageEntries, bc.HitsMax); + for (int i = 0; i < rights.Count; ++i) + { + DamageStore ds = rights[i]; - if ( !Looters.Contains( from ) ) - Looters.Add( from ); + if (ds.m_HasRight) + Aggressors.Add(ds.m_Mobile); + } + } - if ( m_InstancedItems != null && m_InstancedItems.ContainsKey( item ) ) - m_InstancedItems.Remove( item ); - } + BeginDecay(m_DefaultDecayTime); - public override void OnItemLifted( Mobile from, Item item ) - { - base.OnItemLifted( from, item ); - - if ( item != this && from != Owner ) - from.RevealingAction(); - - if ( item != this && IsCriminalAction( from ) ) - from.CriminalAction( true ); - - if ( !Looters.Contains( from ) ) - Looters.Add( from ); - - if ( m_InstancedItems != null && m_InstancedItems.ContainsKey( item ) ) - m_InstancedItems.Remove( item ); - } - - private class OpenCorpseEntry : ContextMenuEntry - { - public OpenCorpseEntry() : base( 6215, 2 ) - { - } - - public override void OnClick() - { - if ( Owner.Target is Corpse corpse && Owner.From.CheckAlive() ) - corpse.Open( Owner.From, false ); - } - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( Core.AOS && Owner == from && from.Alive ) - list.Add( new OpenCorpseEntry() ); - } - - private Dictionary m_RestoreTable; - - public bool GetRestoreInfo( Item item, ref Point3D loc ) - { - if ( m_RestoreTable == null || item == null ) - return false; + DevourCorpse(); + } - return m_RestoreTable.TryGetValue( item, out loc ); - } + public Corpse(Serial serial) : base(serial) + { + } - public void SetRestoreInfo( Item item, Point3D loc ) - { - if ( item == null ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool InstancedCorpse + { + get + { + if (!Core.SE) + return false; - if ( m_RestoreTable == null ) - m_RestoreTable = new Dictionary(); + return DateTime.UtcNow < TimeOfDeath + InstancedCorpseTime; + } + } - m_RestoreTable[item] = loc; - } - - public void ClearRestoreInfo( Item item ) - { - if ( m_RestoreTable == null || item == null ) - return; - - m_RestoreTable.Remove( item ); - - if ( m_RestoreTable.Count == 0 ) - m_RestoreTable = null; - } - - public bool CanLoot( Mobile from, Item item ) - { - if ( !IsCriminalAction( from ) ) - return true; - - Map map = Map; - - if ( map == null || (map.Rules & MapRules.HarmfulRestrictions) != 0 ) - return false; - - return true; - } - - public bool CheckLoot( Mobile from, Item item ) - { - if ( !CanLoot( from, item ) ) - { - if ( Owner == null || !Owner.Player ) - from.SendLocalizedMessage( 1005035 ); // You did not earn the right to loot this creature! - else - from.SendLocalizedMessage( 1010049 ); // You may not loot this corpse. - - return false; - } - - if ( IsCriminalAction( from ) ) - { - if ( Owner == null || !Owner.Player ) - from.SendLocalizedMessage( 1005036 ); // Looting this monster corpse will be a criminal act! - else - from.SendLocalizedMessage( 1005038 ); // Looting this corpse will be a criminal act! - } - - return true; - } - - public virtual void Open( Mobile from, bool checkSelfLoot ) - { - if ( from.AccessLevel > AccessLevel.Player || from.InRange( GetWorldLocation(), 2 ) ) - { - #region Self Looting - if ( checkSelfLoot && from == Owner && !GetFlag( CorpseFlag.SelfLooted ) && Items.Count != 0 ) - { - if ( from.FindItemOnLayer( Layer.OuterTorso ) is DeathRobe robe ) - { - Map map = from.Map; - - if ( map != null && map != Map.Internal ) - { - robe.MoveToWorld( from.Location, map ); - robe.BeginDecay(); - } - } - - Container pack = from.Backpack; - - if ( RestoreEquip != null && pack != null ) - { - List packItems = new List( pack.Items ); // Only items in the top-level pack are re-equipped - - for ( int i = 0; i < packItems.Count; i++ ) - { - Item packItem = packItems[i]; - - if ( RestoreEquip.Contains( packItem ) && packItem.Movable ) - from.EquipItem( packItem ); - } - } - - List items = new List( Items ); - - bool didntFit = false; - - for ( int i = 0; !didntFit && i < items.Count; ++i ) - { - Item item = items[i]; - Point3D loc = item.Location; - - if ( ( item.Layer == Layer.Hair || item.Layer == Layer.FacialHair ) || !item.Movable || !GetRestoreInfo( item, ref loc ) ) - continue; - - if ( pack != null && pack.CheckHold( from, item, false, true ) ) - { - item.Location = loc; - pack.AddItem( item ); - - if ( RestoreEquip != null && RestoreEquip.Contains( item ) ) - from.EquipItem( item ); - } - else - { - didntFit = true; - } - } - - from.PlaySound( 0x3E3 ); - - if ( Items.Count != 0 ) - { - from.SendLocalizedMessage( 1062472 ); // You gather some of your belongings. The rest remain on the corpse. - } - else - { - SetFlag( CorpseFlag.Carved, true ); - - if ( ItemID == 0x2006 ) - { - ProcessDelta(); - SendRemovePacket(); - ItemID = Utility.Random( 0xECA, 9 ); // bone graphic - Hue = 0; - ProcessDelta(); - } - - from.SendLocalizedMessage( 1062471 ); // You quickly gather all of your belongings. - } - - SetFlag( CorpseFlag.SelfLooted, true ); - } - #endregion - - if ( !CheckLoot( from, null ) ) - return; - - #region Quests - - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; - - if ( qs is UzeraanTurmoilQuest ) - { - if ( qs.FindObjective( typeof( GetDaemonBoneObjective ) ) is GetDaemonBoneObjective obj && obj.CorpseWithBone == this && ( !obj.Completed || UzeraanTurmoilQuest.HasLostDaemonBone( player ) ) ) - { - Item bone = new QuestDaemonBone(); - - if ( player.PlaceInBackpack( bone ) ) - { - obj.CorpseWithBone = null; - player.SendLocalizedMessage( 1049341, "", 0x22 ); // You rummage through the bones and find a Daemon Bone! You quickly place the item in your pack. - - if ( !obj.Completed ) - obj.Complete(); - } - else - { - bone.Delete(); - player.SendLocalizedMessage( 1049342, "", 0x22 ); // Rummaging through the bones you find a Daemon Bone, but can't pick it up because your pack is too full. Come back when you have more room in your pack. - } - - return; - } - } - else if ( qs is TheSummoningQuest ) - { - if ( qs.FindObjective( typeof( VanquishDaemonObjective ) ) is VanquishDaemonObjective obj && obj.Completed && obj.CorpseWithSkull == this ) - { - GoldenSkull sk = new GoldenSkull(); - - if ( player.PlaceInBackpack( sk ) ) - { - obj.CorpseWithSkull = null; - player.SendLocalizedMessage( 1050022 ); // For your valor in combating the devourer, you have been awarded a golden skull. - qs.Complete(); - } - else - { - sk.Delete(); - player.SendLocalizedMessage( 1050023 ); // You find a golden skull, but your backpack is too full to carry it. - } - } - } - } - - #endregion - - base.OnDoubleClick( from ); - } - else - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } - - public override void OnDoubleClick( Mobile from ) - { - Open( from, Core.AOS ); - } - - public override bool CheckContentDisplay( Mobile from ) - { - return false; - } - - public override bool DisplaysContent => false; - - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( ItemID == 0x2006 ) // Corpse form - { - if ( m_CorpseName != null ) - list.Add( m_CorpseName ); - else - list.Add( 1046414, Name ); // the remains of ~1_NAME~ - } - else // Bone form - { - list.Add( 1046414, Name ); // the remains of ~1_NAME~ - } - } - - public override void OnAosSingleClick( Mobile from ) - { - int hue = Notoriety.GetHue( NotorietyHandlers.CorpseNotoriety( from, this ) ); - ObjectPropertyList opl = PropertyList; - - if ( opl.Header > 0 ) - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, opl.Header, Name, opl.HeaderArgs ) ); - } - - public override void OnSingleClick( Mobile from ) - { - int hue = Notoriety.GetHue( NotorietyHandlers.CorpseNotoriety( from, this ) ); - - if ( ItemID == 0x2006 ) // Corpse form - { - if ( m_CorpseName != null ) - from.Send( new AsciiMessage( Serial, ItemID, MessageType.Label, hue, 3, "", m_CorpseName ) ); - else - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, 1046414, "", Name ) ); - } - else // Bone form - { - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, hue, 3, 1046414, "", Name ) ); - } - } - - public void Carve( Mobile from, Item item ) - { - if ( IsCriminalAction( from ) && Map != null && (Map.Rules & MapRules.HarmfulRestrictions) != 0 ) - { - if ( Owner == null || !Owner.Player ) - from.SendLocalizedMessage( 1005035 ); // You did not earn the right to loot this creature! - else - from.SendLocalizedMessage( 1010049 ); // You may not loot this corpse. - - return; - } - - Mobile dead = Owner; - - if ( GetFlag( CorpseFlag.Carved ) || dead == null ) - { - from.SendLocalizedMessage( 500485 ); // You see nothing useful to carve from the corpse. - } - else if ( ((Body)Amount).IsHuman && ItemID == 0x2006 ) - { - new Blood( 0x122D ).MoveToWorld( Location, Map ); - - new Torso().MoveToWorld( Location, Map ); - new LeftLeg().MoveToWorld( Location, Map ); - new LeftArm().MoveToWorld( Location, Map ); - new RightLeg().MoveToWorld( Location, Map ); - new RightArm().MoveToWorld( Location, Map ); - new Head( dead.Name ).MoveToWorld( Location, Map ); - - SetFlag( CorpseFlag.Carved, true ); - - ProcessDelta(); - SendRemovePacket(); - ItemID = Utility.Random( 0xECA, 9 ); // bone graphic - Hue = 0; - ProcessDelta(); - - if ( IsCriminalAction( from ) ) - from.CriminalAction( true ); - } - else if ( dead is BaseCreature creature ) - { - creature.OnCarve( from, this, item ); - } - else - { - from.SendLocalizedMessage( 500485 ); // You see nothing useful to carve from the corpse. - } - } - } -} + public override bool IsDecoContainer => false; + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime TimeOfDeath{ get; set; } + + public override bool DisplayWeight => false; + + public HairInfo Hair{ get; } + + public FacialHairInfo FacialHair{ get; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsBones => GetFlag(CorpseFlag.IsBones); + + [CommandProperty(AccessLevel.GameMaster)] + public bool Devoured => m_Devourer != null; + + [CommandProperty(AccessLevel.GameMaster)] + public bool Carved + { + get => GetFlag(CorpseFlag.Carved); + set => SetFlag(CorpseFlag.Carved, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool VisitedByTaxidermist + { + get => GetFlag(CorpseFlag.VisitedByTaxidermist); + set => SetFlag(CorpseFlag.VisitedByTaxidermist, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Channeled + { + get => GetFlag(CorpseFlag.Channeled); + set => SetFlag(CorpseFlag.Channeled, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Animated + { + get => GetFlag(CorpseFlag.Animated); + set => SetFlag(CorpseFlag.Animated, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool SelfLooted + { + get => GetFlag(CorpseFlag.SelfLooted); + set => SetFlag(CorpseFlag.SelfLooted, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public AccessLevel AccessLevel{ get; private set; } + + public List Aggressors{ get; private set; } + + public List Looters{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Killer{ get; private set; } + + public List EquipItems{ get; private set; } + + public List RestoreEquip{ get; set; } + + public Guild Guild{ get; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Kills{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Criminal + { + get => GetFlag(CorpseFlag.Criminal); + set => SetFlag(CorpseFlag.Criminal, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; private set; } + + public override bool DisplaysContent => false; + + public void Carve(Mobile from, Item item) + { + if (IsCriminalAction(from) && Map != null && (Map.Rules & MapRules.HarmfulRestrictions) != 0) + { + if (Owner == null || !Owner.Player) + from.SendLocalizedMessage(1005035); // You did not earn the right to loot this creature! + else + from.SendLocalizedMessage(1010049); // You may not loot this corpse. + + return; + } + + Mobile dead = Owner; + + if (GetFlag(CorpseFlag.Carved) || dead == null) + { + from.SendLocalizedMessage(500485); // You see nothing useful to carve from the corpse. + } + else if (((Body)Amount).IsHuman && ItemID == 0x2006) + { + new Blood(0x122D).MoveToWorld(Location, Map); + + new Torso().MoveToWorld(Location, Map); + new LeftLeg().MoveToWorld(Location, Map); + new LeftArm().MoveToWorld(Location, Map); + new RightLeg().MoveToWorld(Location, Map); + new RightArm().MoveToWorld(Location, Map); + new Head(dead.Name).MoveToWorld(Location, Map); + + SetFlag(CorpseFlag.Carved, true); + + ProcessDelta(); + SendRemovePacket(); + ItemID = Utility.Random(0xECA, 9); // bone graphic + Hue = 0; + ProcessDelta(); + + if (IsCriminalAction(from)) + from.CriminalAction(true); + } + else if (dead is BaseCreature creature) + { + creature.OnCarve(from, this, item); + } + else + { + from.SendLocalizedMessage(500485); // You see nothing useful to carve from the corpse. + } + } + + public override bool IsChildVisibleTo(Mobile m, Item child) + { + if (!m.Player || m.AccessLevel > AccessLevel.Player) //Staff and creatures not subject to instancing. + return true; + + if (m_InstancedItems != null) + if (m_InstancedItems.TryGetValue(child, out InstancedItemInfo info) && (InstancedCorpse || info.Perpetual)) + return info.IsOwner(m); //IsOwner checks Party stuff. + + return true; + } + + private void AssignInstancedLoot() + { + if (Aggressors.Count == 0 || Items.Count == 0) + return; + + if (m_InstancedItems == null) + m_InstancedItems = new Dictionary(); + + List m_Stackables = new List(); + List m_Unstackables = new List(); + + for (int i = 0; i < Items.Count; i++) + { + Item item = Items[i]; + + if (item.LootType != LootType.Cursed) //Don't have curesd items take up someone's item spot.. (?) + { + if (item.Stackable) + m_Stackables.Add(item); + else + m_Unstackables.Add(item); + } + } + + List attackers = new List(Aggressors); + + for (int i = 1; i < attackers.Count - 1; i++) //randomize + { + int rand = Utility.Random(i + 1); + + Mobile temp = attackers[rand]; + attackers[rand] = attackers[i]; + attackers[i] = temp; + } + + //stackables first, for the remaining stackables, have those be randomly added after + + for (int i = 0; i < m_Stackables.Count; i++) + { + Item item = m_Stackables[i]; + + if (item.Amount >= attackers.Count) + { + int amountPerAttacker = item.Amount / attackers.Count; + int remainder = item.Amount % attackers.Count; + + for (int j = 0; j < (remainder == 0 ? attackers.Count - 1 : attackers.Count); j++) + { + Item splitItem = + Mobile.LiftItemDupe(item, + item.Amount - + amountPerAttacker); //LiftItemDupe automagically adds it as a child item to the corpse + + m_InstancedItems.Add(splitItem, new InstancedItemInfo(splitItem, attackers[j])); + + //What happens to the remaining portion? TEMP FOR NOW UNTIL OSI VERIFICATION: Treat as Single Item. + } + + if (remainder == 0) + m_InstancedItems.Add(item, new InstancedItemInfo(item, attackers[attackers.Count - 1])); + else + m_Unstackables.Add(item); + } + else + { + //What happens in this case? TEMP FOR NOW UNTIL OSI VERIFICATION: Treat as Single Item. + m_Unstackables.Add(item); + } + } + + for (int i = 0; i < m_Unstackables.Count; i++) + { + Mobile m = attackers[i % attackers.Count]; + Item item = m_Unstackables[i]; + + m_InstancedItems.Add(item, new InstancedItemInfo(item, m)); + } + } + + public void AddCarvedItem(Item carved, Mobile carver) + { + DropItem(carved); + + if (InstancedCorpse) + { + if (m_InstancedItems == null) + m_InstancedItems = new Dictionary(); + + m_InstancedItems.Add(carved, new InstancedItemInfo(carved, carver)); + } + } + + public void TurnToBones() + { + if (Deleted) + return; + + ProcessDelta(); + SendRemovePacket(); + ItemID = Utility.Random(0xECA, 9); // bone graphic + Hue = 0; + ProcessDelta(); + + SetFlag(CorpseFlag.NoBones, true); + SetFlag(CorpseFlag.IsBones, true); + + BeginDecay(m_BoneDecayTime); + } + + public void BeginDecay(TimeSpan delay) + { + m_DecayTimer?.Stop(); + + m_DecayTime = DateTime.UtcNow + delay; + + m_DecayTimer = new InternalTimer(this, delay); + m_DecayTimer.Start(); + } + + public override void OnAfterDelete() + { + m_DecayTimer?.Stop(); + + m_DecayTimer = null; + } + + public static string GetCorpseName(Mobile m) + { + return m is BaseCreature bc ? bc.CorpseNameOverride ?? bc.CorpseName : null; + } + + public static void Initialize() + { + Mobile.CreateCorpseHandler += Mobile_CreateCorpseHandler; + } + + public static Container Mobile_CreateCorpseHandler(Mobile owner, HairInfo hair, FacialHairInfo facialhair, + List initialContent, List equipItems) + { + bool shouldFillCorpse = true; + + //if ( owner is BaseCreature ) + // shouldFillCorpse = !((BaseCreature)owner).IsBonded; + + Corpse c; + if (owner is MilitiaFighter) + c = new MilitiaFighterCorpse(owner, hair, facialhair, shouldFillCorpse ? equipItems : new List()); + else + c = new Corpse(owner, hair, facialhair, shouldFillCorpse ? equipItems : new List()); + + owner.Corpse = c; + + if (shouldFillCorpse) + { + for (int i = 0; i < initialContent.Count; ++i) + { + Item item = initialContent[i]; + + if (Core.AOS && owner.Player && item.Parent == owner.Backpack) + c.AddItem(item); + else + c.DropItem(item); + + if (owner.Player && Core.AOS) + c.SetRestoreInfo(item, item.Location); + } + + if (Core.SE && !owner.Player) + c.AssignInstancedLoot(); + else if (Core.AOS && owner is PlayerMobile pm) + c.RestoreEquip = pm.EquipSnapshot; + } + else + { + c.Carved = true; // TODO: Is it needed? + } + + Point3D loc = owner.Location; + Map map = owner.Map; + + if (map == null || map == Map.Internal) + { + loc = owner.LogoutLocation; + map = owner.LogoutMap; + } + + c.MoveToWorld(loc, map); + + return c; + } + + protected bool GetFlag(CorpseFlag flag) + { + return (m_Flags & flag) != 0; + } + + protected void SetFlag(CorpseFlag flag, bool on) + { + m_Flags = on ? m_Flags | flag : m_Flags & ~flag; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(12); // version + + if (RestoreEquip == null) + { + writer.Write(false); + } + else + { + writer.Write(true); + writer.Write(RestoreEquip); + } + + writer.Write((int)m_Flags); + + writer.WriteDeltaTime(TimeOfDeath); + + List> list = m_RestoreTable == null + ? null + : new List>(m_RestoreTable); + int count = list?.Count ?? 0; + + writer.Write(count); + + for (int i = 0; i < count; ++i) + { + KeyValuePair kvp = list[i]; + Item item = kvp.Key; + Point3D loc = kvp.Value; + + writer.Write(item); + + if (item.Location == loc) + { + writer.Write(false); + } + else + { + writer.Write(true); + writer.Write(loc); + } + } + + writer.Write(m_DecayTimer != null); + + if (m_DecayTimer != null) + writer.WriteDeltaTime(m_DecayTime); + + writer.Write(Looters); + writer.Write(Killer); + + writer.Write(Aggressors); + + writer.Write(Owner); + + writer.Write(m_CorpseName); + + writer.Write((int)AccessLevel); + writer.Write(Guild); + writer.Write(Kills); + + writer.Write(EquipItems); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 12: + { + if (reader.ReadBool()) + RestoreEquip = reader.ReadStrongItemList(); + + goto case 11; + } + case 11: + { + // Version 11, we move all bools to a CorpseFlag + m_Flags = (CorpseFlag)reader.ReadInt(); + + TimeOfDeath = reader.ReadDeltaTime(); + + int count = reader.ReadInt(); + + for (int i = 0; i < count; ++i) + { + Item item = reader.ReadItem(); + + if (reader.ReadBool()) + SetRestoreInfo(item, reader.ReadPoint3D()); + else if (item != null) + SetRestoreInfo(item, item.Location); + } + + if (reader.ReadBool()) + BeginDecay(reader.ReadDeltaTime() - DateTime.UtcNow); + + Looters = reader.ReadStrongMobileList(); + Killer = reader.ReadMobile(); + + Aggressors = reader.ReadStrongMobileList(); + Owner = reader.ReadMobile(); + + m_CorpseName = reader.ReadString(); + + AccessLevel = (AccessLevel)reader.ReadInt(); + reader.ReadInt(); // guild reserve + Kills = reader.ReadInt(); + + EquipItems = reader.ReadStrongItemList(); + break; + } + case 10: + { + TimeOfDeath = reader.ReadDeltaTime(); + + goto case 9; + } + case 9: + { + int count = reader.ReadInt(); + + for (int i = 0; i < count; ++i) + { + Item item = reader.ReadItem(); + + if (reader.ReadBool()) + SetRestoreInfo(item, reader.ReadPoint3D()); + else if (item != null) + SetRestoreInfo(item, item.Location); + } + + goto case 8; + } + case 8: + { + SetFlag(CorpseFlag.VisitedByTaxidermist, reader.ReadBool()); + + goto case 7; + } + case 7: + { + if (reader.ReadBool()) + BeginDecay(reader.ReadDeltaTime() - DateTime.UtcNow); + + goto case 6; + } + case 6: + { + Looters = reader.ReadStrongMobileList(); + Killer = reader.ReadMobile(); + + goto case 5; + } + case 5: + { + SetFlag(CorpseFlag.Carved, reader.ReadBool()); + + goto case 4; + } + case 4: + { + Aggressors = reader.ReadStrongMobileList(); + + goto case 3; + } + case 3: + { + Owner = reader.ReadMobile(); + + goto case 2; + } + case 2: + { + SetFlag(CorpseFlag.NoBones, reader.ReadBool()); + + goto case 1; + } + case 1: + { + m_CorpseName = reader.ReadString(); + + goto case 0; + } + case 0: + { + if (version < 10) + TimeOfDeath = DateTime.UtcNow; + + if (version < 7) + BeginDecay(m_DefaultDecayTime); + + if (version < 6) + Looters = new List(); + + if (version < 4) + Aggressors = new List(); + + AccessLevel = (AccessLevel)reader.ReadInt(); + reader.ReadInt(); // guild reserve + Kills = reader.ReadInt(); + SetFlag(CorpseFlag.Criminal, reader.ReadBool()); + + EquipItems = reader.ReadStrongItemList(); + + break; + } + } + } + + public bool DevourCorpse() + { + if (Devoured || Deleted || Killer == null || Killer.Deleted || !Killer.Alive || !(Killer is IDevourer) || + Owner == null || Owner.Deleted) + return false; + + m_Devourer = (IDevourer)Killer; // Set the devourer the killer + return m_Devourer.Devour(this); // Devour the corpse if it hasn't + } + + public override void SendInfoTo(NetState state, bool sendOplPacket) + { + base.SendInfoTo(state, sendOplPacket); + + if (((Body)Amount).IsHuman && ItemID == 0x2006) + { + if (state.ContainerGridLines) + state.Send(new CorpseContent6017(state.Mobile, this)); + else + state.Send(new CorpseContent(state.Mobile, this)); + + state.Send(new CorpseEquip(state.Mobile, this)); + } + } + + public bool IsCriminalAction(Mobile from) + { + if (from == Owner || from.AccessLevel >= AccessLevel.GameMaster) + return false; + + Party p = Party.Get(Owner); + + if (p != null && p.Contains(from)) + { + PartyMemberInfo pmi = p[Owner]; + + if (pmi != null && pmi.CanLoot) + return false; + } + + return NotorietyHandlers.CorpseNotoriety(from, this) == Notoriety.Innocent; + } + + public override bool CheckItemUse(Mobile from, Item item) + { + if (!base.CheckItemUse(from, item)) + return false; + + if (item != this) + return CanLoot(from, item); + + return true; + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (!base.CheckLift(from, item, ref reject)) + return false; + + return CanLoot(from, item); + } + + public override void OnItemUsed(Mobile from, Item item) + { + base.OnItemUsed(from, item); + + if (item is Food) + from.RevealingAction(); + + if (item != this && IsCriminalAction(from)) + from.CriminalAction(true); + + if (!Looters.Contains(from)) + Looters.Add(from); + + if (m_InstancedItems != null && m_InstancedItems.ContainsKey(item)) + m_InstancedItems.Remove(item); + } + + public override void OnItemLifted(Mobile from, Item item) + { + base.OnItemLifted(from, item); + + if (item != this && from != Owner) + from.RevealingAction(); + + if (item != this && IsCriminalAction(from)) + from.CriminalAction(true); + + if (!Looters.Contains(from)) + Looters.Add(from); + + if (m_InstancedItems != null && m_InstancedItems.ContainsKey(item)) + m_InstancedItems.Remove(item); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (Core.AOS && Owner == from && from.Alive) + list.Add(new OpenCorpseEntry()); + } + + public bool GetRestoreInfo(Item item, ref Point3D loc) + { + if (m_RestoreTable == null || item == null) + return false; + + return m_RestoreTable.TryGetValue(item, out loc); + } + + public void SetRestoreInfo(Item item, Point3D loc) + { + if (item == null) + return; + + if (m_RestoreTable == null) + m_RestoreTable = new Dictionary(); + + m_RestoreTable[item] = loc; + } + + public void ClearRestoreInfo(Item item) + { + if (m_RestoreTable == null || item == null) + return; + + m_RestoreTable.Remove(item); + + if (m_RestoreTable.Count == 0) + m_RestoreTable = null; + } + + public bool CanLoot(Mobile from, Item item) + { + if (!IsCriminalAction(from)) + return true; + + Map map = Map; + + if (map == null || (map.Rules & MapRules.HarmfulRestrictions) != 0) + return false; + + return true; + } + + public bool CheckLoot(Mobile from, Item item) + { + if (!CanLoot(from, item)) + { + if (Owner == null || !Owner.Player) + from.SendLocalizedMessage(1005035); // You did not earn the right to loot this creature! + else + from.SendLocalizedMessage(1010049); // You may not loot this corpse. + + return false; + } + + if (IsCriminalAction(from)) + { + if (Owner == null || !Owner.Player) + from.SendLocalizedMessage(1005036); // Looting this monster corpse will be a criminal act! + else + from.SendLocalizedMessage(1005038); // Looting this corpse will be a criminal act! + } + + return true; + } + + public virtual void Open(Mobile from, bool checkSelfLoot) + { + if (from.AccessLevel > AccessLevel.Player || from.InRange(GetWorldLocation(), 2)) + { + #region Self Looting + + if (checkSelfLoot && from == Owner && !GetFlag(CorpseFlag.SelfLooted) && Items.Count != 0) + { + if (from.FindItemOnLayer(Layer.OuterTorso) is DeathRobe robe) + { + Map map = from.Map; + + if (map != null && map != Map.Internal) + { + robe.MoveToWorld(from.Location, map); + robe.BeginDecay(); + } + } + + Container pack = from.Backpack; + + if (RestoreEquip != null && pack != null) + { + List + packItems = new List(pack.Items); // Only items in the top-level pack are re-equipped + + for (int i = 0; i < packItems.Count; i++) + { + Item packItem = packItems[i]; + + if (RestoreEquip.Contains(packItem) && packItem.Movable) + from.EquipItem(packItem); + } + } + + List items = new List(Items); + + bool didntFit = false; + + for (int i = 0; !didntFit && i < items.Count; ++i) + { + Item item = items[i]; + Point3D loc = item.Location; + + if (item.Layer == Layer.Hair || item.Layer == Layer.FacialHair || !item.Movable || + !GetRestoreInfo(item, ref loc)) + continue; + + if (pack != null && pack.CheckHold(from, item, false, true)) + { + item.Location = loc; + pack.AddItem(item); + + if (RestoreEquip != null && RestoreEquip.Contains(item)) + from.EquipItem(item); + } + else + { + didntFit = true; + } + } + + from.PlaySound(0x3E3); + + if (Items.Count != 0) + { + from.SendLocalizedMessage( + 1062472); // You gather some of your belongings. The rest remain on the corpse. + } + else + { + SetFlag(CorpseFlag.Carved, true); + + if (ItemID == 0x2006) + { + ProcessDelta(); + SendRemovePacket(); + ItemID = Utility.Random(0xECA, 9); // bone graphic + Hue = 0; + ProcessDelta(); + } + + from.SendLocalizedMessage(1062471); // You quickly gather all of your belongings. + } + + SetFlag(CorpseFlag.SelfLooted, true); + } + + #endregion + + if (!CheckLoot(from, null)) + return; + + #region Quests + + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; + + if (qs is UzeraanTurmoilQuest) + { + if (qs.FindObjective(typeof(GetDaemonBoneObjective)) is GetDaemonBoneObjective obj && + obj.CorpseWithBone == this && (!obj.Completed || UzeraanTurmoilQuest.HasLostDaemonBone(player))) + { + Item bone = new QuestDaemonBone(); + + if (player.PlaceInBackpack(bone)) + { + obj.CorpseWithBone = null; + player.SendLocalizedMessage(1049341, "", + 0x22); // You rummage through the bones and find a Daemon Bone! You quickly place the item in your pack. + + if (!obj.Completed) + obj.Complete(); + } + else + { + bone.Delete(); + player.SendLocalizedMessage(1049342, "", + 0x22); // Rummaging through the bones you find a Daemon Bone, but can't pick it up because your pack is too full. Come back when you have more room in your pack. + } + + return; + } + } + else if (qs is TheSummoningQuest) + { + if (qs.FindObjective(typeof(VanquishDaemonObjective)) is VanquishDaemonObjective obj && + obj.Completed && obj.CorpseWithSkull == this) + { + GoldenSkull sk = new GoldenSkull(); + + if (player.PlaceInBackpack(sk)) + { + obj.CorpseWithSkull = null; + player.SendLocalizedMessage( + 1050022); // For your valor in combating the devourer, you have been awarded a golden skull. + qs.Complete(); + } + else + { + sk.Delete(); + player.SendLocalizedMessage( + 1050023); // You find a golden skull, but your backpack is too full to carry it. + } + } + } + } + + #endregion + + base.OnDoubleClick(from); + } + else + { + from.SendLocalizedMessage(500446); // That is too far away. + } + } + + public override void OnDoubleClick(Mobile from) + { + Open(from, Core.AOS); + } + + public override bool CheckContentDisplay(Mobile from) + { + return false; + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (ItemID == 0x2006) // Corpse form + { + if (m_CorpseName != null) + list.Add(m_CorpseName); + else + list.Add(1046414, Name); // the remains of ~1_NAME~ + } + else // Bone form + { + list.Add(1046414, Name); // the remains of ~1_NAME~ + } + } + + public override void OnAosSingleClick(Mobile from) + { + int hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this)); + ObjectPropertyList opl = PropertyList; + + if (opl.Header > 0) + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, opl.Header, Name, opl.HeaderArgs)); + } + + public override void OnSingleClick(Mobile from) + { + int hue = Notoriety.GetHue(NotorietyHandlers.CorpseNotoriety(from, this)); + + if (ItemID == 0x2006) // Corpse form + { + if (m_CorpseName != null) + from.Send(new AsciiMessage(Serial, ItemID, MessageType.Label, hue, 3, "", m_CorpseName)); + else + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1046414, "", Name)); + } + else // Bone form + { + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Label, hue, 3, 1046414, "", Name)); + } + } + + private class InstancedItemInfo + { + private Item m_Item; + private Mobile m_Mobile; + + public InstancedItemInfo(Item i, Mobile m) + { + m_Item = i; + m_Mobile = m; + } + + public bool Perpetual{ get; set; } + + public bool IsOwner(Mobile m) + { + if (m_Item.LootType == LootType.Cursed) //Cursed Items are part of everyone's instanced corpse... (?) + return true; + + if (m == null) + return false; //sanity + + if (m_Mobile == m) + return true; + + Party myParty = Party.Get(m_Mobile); + + return myParty != null && myParty == Party.Get(m); + } + } + + private class InternalTimer : Timer + { + private Corpse m_Corpse; + + public InternalTimer(Corpse c, TimeSpan delay) : base(delay) + { + m_Corpse = c; + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + if (!m_Corpse.GetFlag(CorpseFlag.NoBones)) + m_Corpse.TurnToBones(); + else + m_Corpse.Delete(); + } + } + + private class OpenCorpseEntry : ContextMenuEntry + { + public OpenCorpseEntry() : base(6215, 2) + { + } + + public override void OnClick() + { + if (Owner.Target is Corpse corpse && Owner.From.CheckAlive()) + corpse.Open(Owner.From, false); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Corpses/CorpseNameAttribute.cs b/Scripts/Items/Misc/Corpses/CorpseNameAttribute.cs index f8ea5fcf6..000c86454 100644 --- a/Scripts/Items/Misc/Corpses/CorpseNameAttribute.cs +++ b/Scripts/Items/Misc/Corpses/CorpseNameAttribute.cs @@ -2,14 +2,14 @@ using System; namespace Server { - [AttributeUsage( AttributeTargets.Class )] - public class CorpseNameAttribute : Attribute - { - public string Name { get; } + [AttributeUsage(AttributeTargets.Class)] + public class CorpseNameAttribute : Attribute + { + public CorpseNameAttribute(string name) + { + Name = name; + } - public CorpseNameAttribute( string name ) - { - Name = name; - } - } + public string Name{ get; } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Corpses/DecayedCorpse.cs b/Scripts/Items/Misc/Corpses/DecayedCorpse.cs index 2f34b143d..752af35fb 100644 --- a/Scripts/Items/Misc/Corpses/DecayedCorpse.cs +++ b/Scripts/Items/Misc/Corpses/DecayedCorpse.cs @@ -2,111 +2,110 @@ using System; namespace Server.Items { - public class DecayedCorpse : Container - { - private Timer m_DecayTimer; - private DateTime m_DecayTime; + public class DecayedCorpse : Container + { + private static TimeSpan m_DefaultDecayTime = TimeSpan.FromMinutes(7.0); + private DateTime m_DecayTime; + private Timer m_DecayTimer; - private static TimeSpan m_DefaultDecayTime = TimeSpan.FromMinutes( 7.0 ); + public DecayedCorpse(string name) : base(Utility.Random(0xECA, 9)) + { + Movable = false; + Name = name; - public DecayedCorpse( string name ) : base( Utility.Random( 0xECA, 9 ) ) - { - Movable = false; - Name = name; + BeginDecay(m_DefaultDecayTime); + } - BeginDecay( m_DefaultDecayTime ); - } + public DecayedCorpse(Serial serial) : base(serial) + { + } - public void BeginDecay( TimeSpan delay ) - { - m_DecayTimer?.Stop(); + // Do not display (x items, y stones) + public override bool DisplaysContent => false; - m_DecayTime = DateTime.UtcNow + delay; + public void BeginDecay(TimeSpan delay) + { + m_DecayTimer?.Stop(); - m_DecayTimer = new InternalTimer( this, delay ); - m_DecayTimer.Start(); - } + m_DecayTime = DateTime.UtcNow + delay; - public override void OnAfterDelete() - { - m_DecayTimer?.Stop(); + m_DecayTimer = new InternalTimer(this, delay); + m_DecayTimer.Start(); + } - m_DecayTimer = null; - } + public override void OnAfterDelete() + { + m_DecayTimer?.Stop(); - private class InternalTimer : Timer - { - private DecayedCorpse m_Corpse; + m_DecayTimer = null; + } - public InternalTimer( DecayedCorpse c, TimeSpan delay ) : base( delay ) - { - m_Corpse = c; - Priority = TimerPriority.FiveSeconds; - } + // Do not display (x items, y stones) + public override bool CheckContentDisplay(Mobile from) + { + return false; + } - protected override void OnTick() - { - m_Corpse.Delete(); - } - } + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1046414, Name); // the remains of ~1_NAME~ + } - // Do not display (x items, y stones) - public override bool CheckContentDisplay( Mobile from ) - { - return false; - } + public override void OnSingleClick(Mobile from) + { + LabelTo(from, 1046414, Name); // the remains of ~1_NAME~ + } - // Do not display (x items, y stones) - public override bool DisplaysContent => false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1046414, Name ); // the remains of ~1_NAME~ - } + writer.Write(1); // version - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, 1046414, Name ); // the remains of ~1_NAME~ - } + writer.Write(m_DecayTimer != null); - public DecayedCorpse( Serial serial ) : base( serial ) - { - } + if (m_DecayTimer != null) + writer.WriteDeltaTime(m_DecayTime); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 1 ); // version + int version = reader.ReadInt(); - writer.Write( m_DecayTimer != null ); + switch (version) + { + case 0: + { + BeginDecay(m_DefaultDecayTime); - if ( m_DecayTimer != null ) - writer.WriteDeltaTime( m_DecayTime ); - } + break; + } + case 1: + { + if (reader.ReadBool()) + BeginDecay(reader.ReadDeltaTime() - DateTime.UtcNow); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + break; + } + } + } - int version = reader.ReadInt(); + private class InternalTimer : Timer + { + private DecayedCorpse m_Corpse; - switch ( version ) - { - case 0: - { - BeginDecay( m_DefaultDecayTime ); + public InternalTimer(DecayedCorpse c, TimeSpan delay) : base(delay) + { + m_Corpse = c; + Priority = TimerPriority.FiveSeconds; + } - break; - } - case 1: - { - if ( reader.ReadBool() ) - BeginDecay( reader.ReadDeltaTime() - DateTime.UtcNow ); - - break; - } - } - } - } -} + protected override void OnTick() + { + m_Corpse.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Corpses/Packets.cs b/Scripts/Items/Misc/Corpses/Packets.cs index 81b06a098..cb4cb10d9 100644 --- a/Scripts/Items/Misc/Corpses/Packets.cs +++ b/Scripts/Items/Misc/Corpses/Packets.cs @@ -1,198 +1,198 @@ -using System.IO; using System.Collections.Generic; +using System.IO; using Server.Items; namespace Server.Network { - public sealed class CorpseEquip : Packet - { - public CorpseEquip( Mobile beholder, Corpse beheld ) : base( 0x89 ) - { - List list = beheld.EquipItems; + public sealed class CorpseEquip : Packet + { + public CorpseEquip(Mobile beholder, Corpse beheld) : base(0x89) + { + List list = beheld.EquipItems; - int count = list.Count; - if ( beheld.Hair != null && beheld.Hair.ItemID > 0 ) - count++; - if ( beheld.FacialHair != null && beheld.FacialHair.ItemID > 0 ) - count++; + int count = list.Count; + if (beheld.Hair != null && beheld.Hair.ItemID > 0) + count++; + if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) + count++; - EnsureCapacity( 8 + (count * 5) ); + EnsureCapacity(8 + count * 5); - m_Stream.Write( (int) beheld.Serial ); + m_Stream.Write(beheld.Serial); - for ( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; - if ( !item.Deleted && beholder.CanSee( item ) && item.Parent == beheld ) - { - m_Stream.Write( (byte) (item.Layer + 1) ); - m_Stream.Write( (int) item.Serial ); - } - } + if (!item.Deleted && beholder.CanSee(item) && item.Parent == beheld) + { + m_Stream.Write((byte)(item.Layer + 1)); + m_Stream.Write(item.Serial); + } + } - if ( beheld.Hair != null && beheld.Hair.ItemID > 0 ) - { - m_Stream.Write( (byte)(Layer.Hair + 1) ); - m_Stream.Write( (int)HairInfo.FakeSerial( beheld.Owner ) - 2 ); - } + if (beheld.Hair != null && beheld.Hair.ItemID > 0) + { + m_Stream.Write((byte)(Layer.Hair + 1)); + m_Stream.Write(HairInfo.FakeSerial(beheld.Owner) - 2); + } - if ( beheld.FacialHair != null && beheld.FacialHair.ItemID > 0 ) - { - m_Stream.Write( (byte)(Layer.FacialHair + 1) ); - m_Stream.Write( (int)FacialHairInfo.FakeSerial( beheld.Owner ) - 2 ); - } + if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) + { + m_Stream.Write((byte)(Layer.FacialHair + 1)); + m_Stream.Write(FacialHairInfo.FakeSerial(beheld.Owner) - 2); + } - m_Stream.Write( (byte) Layer.Invalid ); - } - } + m_Stream.Write((byte)Layer.Invalid); + } + } - public sealed class CorpseContent : Packet - { - public CorpseContent( Mobile beholder, Corpse beheld ) - : base( 0x3C ) - { - List items = beheld.EquipItems; - int count = items.Count; + public sealed class CorpseContent : Packet + { + public CorpseContent(Mobile beholder, Corpse beheld) + : base(0x3C) + { + List items = beheld.EquipItems; + int count = items.Count; - if ( beheld.Hair != null && beheld.Hair.ItemID > 0 ) - count++; - if ( beheld.FacialHair != null && beheld.FacialHair.ItemID > 0 ) - count++; + if (beheld.Hair != null && beheld.Hair.ItemID > 0) + count++; + if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) + count++; - EnsureCapacity( 5 + (count * 19) ); + EnsureCapacity(5 + count * 19); - long pos = m_Stream.Position; + long pos = m_Stream.Position; - int written = 0; + int written = 0; - m_Stream.Write( (ushort)0 ); + m_Stream.Write((ushort)0); - for( int i = 0; i < items.Count; ++i ) - { - Item child = items[i]; + for (int i = 0; i < items.Count; ++i) + { + Item child = items[i]; - if ( !child.Deleted && child.Parent == beheld && beholder.CanSee( child ) ) - { - m_Stream.Write( (int)child.Serial ); - m_Stream.Write( (ushort)child.ItemID ); - m_Stream.Write( (byte)0 ); // signed, itemID offset - m_Stream.Write( (ushort)child.Amount ); - m_Stream.Write( (short)child.X ); - m_Stream.Write( (short)child.Y ); - m_Stream.Write( (int)beheld.Serial ); - m_Stream.Write( (ushort)child.Hue ); + if (!child.Deleted && child.Parent == beheld && beholder.CanSee(child)) + { + m_Stream.Write(child.Serial); + m_Stream.Write((ushort)child.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)child.Amount); + m_Stream.Write((short)child.X); + m_Stream.Write((short)child.Y); + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)child.Hue); - ++written; - } - } + ++written; + } + } - if ( beheld.Hair != null && beheld.Hair.ItemID > 0 ) - { - m_Stream.Write( (int)HairInfo.FakeSerial( beheld.Owner ) - 2 ); - m_Stream.Write( (ushort)beheld.Hair.ItemID ); - m_Stream.Write( (byte)0 ); // signed, itemID offset - m_Stream.Write( (ushort)1 ); - m_Stream.Write( (short)0 ); - m_Stream.Write( (short)0 ); - m_Stream.Write( (int)beheld.Serial ); - m_Stream.Write( (ushort)beheld.Hair.Hue ); + if (beheld.Hair != null && beheld.Hair.ItemID > 0) + { + m_Stream.Write(HairInfo.FakeSerial(beheld.Owner) - 2); + m_Stream.Write((ushort)beheld.Hair.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)1); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)beheld.Hair.Hue); - ++written; - } + ++written; + } - if ( beheld.FacialHair != null && beheld.FacialHair.ItemID > 0 ) - { - m_Stream.Write( (int)FacialHairInfo.FakeSerial( beheld.Owner ) - 2 ); - m_Stream.Write( (ushort)beheld.FacialHair.ItemID ); - m_Stream.Write( (byte)0 ); // signed, itemID offset - m_Stream.Write( (ushort)1 ); - m_Stream.Write( (short)0 ); - m_Stream.Write( (short)0 ); - m_Stream.Write( (int)beheld.Serial ); - m_Stream.Write( (ushort)beheld.FacialHair.Hue ); + if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) + { + m_Stream.Write(FacialHairInfo.FakeSerial(beheld.Owner) - 2); + m_Stream.Write((ushort)beheld.FacialHair.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)1); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)beheld.FacialHair.Hue); - ++written; - } + ++written; + } - m_Stream.Seek( pos, SeekOrigin.Begin ); - m_Stream.Write( (ushort)written ); - } - } + m_Stream.Seek(pos, SeekOrigin.Begin); + m_Stream.Write((ushort)written); + } + } - public sealed class CorpseContent6017 : Packet - { - public CorpseContent6017(Mobile beholder, Corpse beheld) - : base(0x3C) - { - List items = beheld.EquipItems; - int count = items.Count; + public sealed class CorpseContent6017 : Packet + { + public CorpseContent6017(Mobile beholder, Corpse beheld) + : base(0x3C) + { + List items = beheld.EquipItems; + int count = items.Count; - if (beheld.Hair != null && beheld.Hair.ItemID > 0) - count++; - if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) - count++; + if (beheld.Hair != null && beheld.Hair.ItemID > 0) + count++; + if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) + count++; - EnsureCapacity(5 + (count * 20)); + EnsureCapacity(5 + count * 20); - long pos = m_Stream.Position; + long pos = m_Stream.Position; - int written = 0; + int written = 0; - m_Stream.Write((ushort)0); + m_Stream.Write((ushort)0); - for (int i = 0; i < items.Count; ++i) - { - Item child = items[i]; + for (int i = 0; i < items.Count; ++i) + { + Item child = items[i]; - if (!child.Deleted && child.Parent == beheld && beholder.CanSee(child)) - { - m_Stream.Write((int)child.Serial); - m_Stream.Write((ushort)child.ItemID); - m_Stream.Write((byte)0); // signed, itemID offset - m_Stream.Write((ushort)child.Amount); - m_Stream.Write((short)child.X); - m_Stream.Write((short)child.Y); - m_Stream.Write((byte)0); // Grid Location? - m_Stream.Write((int)beheld.Serial); - m_Stream.Write((ushort)child.Hue); + if (!child.Deleted && child.Parent == beheld && beholder.CanSee(child)) + { + m_Stream.Write(child.Serial); + m_Stream.Write((ushort)child.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)child.Amount); + m_Stream.Write((short)child.X); + m_Stream.Write((short)child.Y); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)child.Hue); - ++written; - } - } + ++written; + } + } - if (beheld.Hair != null && beheld.Hair.ItemID > 0) - { - m_Stream.Write((int)HairInfo.FakeSerial(beheld.Owner) - 2); - m_Stream.Write((ushort)beheld.Hair.ItemID); - m_Stream.Write((byte)0); // signed, itemID offset - m_Stream.Write((ushort)1); - m_Stream.Write((short)0); - m_Stream.Write((short)0); - m_Stream.Write((byte)0); // Grid Location? - m_Stream.Write((int)beheld.Serial); - m_Stream.Write((ushort)beheld.Hair.Hue); + if (beheld.Hair != null && beheld.Hair.ItemID > 0) + { + m_Stream.Write(HairInfo.FakeSerial(beheld.Owner) - 2); + m_Stream.Write((ushort)beheld.Hair.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)1); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)beheld.Hair.Hue); - ++written; - } + ++written; + } - if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) - { - m_Stream.Write((int)FacialHairInfo.FakeSerial(beheld.Owner) - 2); - m_Stream.Write((ushort)beheld.FacialHair.ItemID); - m_Stream.Write((byte)0); // signed, itemID offset - m_Stream.Write((ushort)1); - m_Stream.Write((short)0); - m_Stream.Write((short)0); - m_Stream.Write((byte)0); // Grid Location? - m_Stream.Write((int)beheld.Serial); - m_Stream.Write((ushort)beheld.FacialHair.Hue); + if (beheld.FacialHair != null && beheld.FacialHair.ItemID > 0) + { + m_Stream.Write(FacialHairInfo.FakeSerial(beheld.Owner) - 2); + m_Stream.Write((ushort)beheld.FacialHair.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)1); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)beheld.FacialHair.Hue); - ++written; - } + ++written; + } - m_Stream.Seek(pos, SeekOrigin.Begin); - m_Stream.Write((ushort)written); - } - } -} + m_Stream.Seek(pos, SeekOrigin.Begin); + m_Stream.Write((ushort)written); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/DeceitBrazier.cs b/Scripts/Items/Misc/DeceitBrazier.cs index ce42943c3..b001f778d 100644 --- a/Scripts/Items/Misc/DeceitBrazier.cs +++ b/Scripts/Items/Misc/DeceitBrazier.cs @@ -1,219 +1,235 @@ using System; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Items { - public class DeceitBrazier : Item - { - public static Type[] Creatures { get; } = - { - #region Animals - typeof( FireSteed ), //Set the tents up people! - #endregion + public class DeceitBrazier : Item + { + private Timer m_Timer; - #region Undead - typeof( Skeleton ), typeof( SkeletalKnight ), typeof( SkeletalMage ), typeof( Mummy ), - typeof( BoneKnight ), typeof( Lich ), typeof( LichLord ), typeof( BoneMagi ), - typeof( Wraith ), typeof( Shade ), typeof( Spectre ), typeof( Zombie ), - typeof( RottingCorpse ), typeof( Ghoul ), - #endregion + [Constructible] + public DeceitBrazier() : base(0xE31) + { + Movable = false; + Light = LightType.Circle225; + NextSpawn = DateTime.UtcNow; + NextSpawnDelay = TimeSpan.FromMinutes(15.0); + SpawnRange = 5; + } - #region Demons - typeof( Balron ), typeof( Daemon ), typeof( Imp ), typeof( GreaterMongbat ), - typeof( Mongbat ), typeof( IceFiend ), typeof( Gargoyle ), typeof( StoneGargoyle ), - typeof( FireGargoyle ), typeof( HordeMinion ), - #endregion + public DeceitBrazier(Serial serial) : base(serial) + { + } - #region Gazers - typeof( Gazer ), typeof( ElderGazer ), typeof( GazerLarva ), - #endregion + public static Type[] Creatures{ get; } = + { + #region Animals - #region Uncategorized - typeof( Harpy ), typeof( StoneHarpy ), typeof( HeadlessOne ), typeof( HellHound ), - typeof( HellCat ), typeof( Phoenix ), typeof( LavaLizard ), typeof( SandVortex ), - typeof( ShadowWisp ), typeof( SwampTentacle ), typeof( PredatorHellCat ), typeof( Wisp ), - #endregion + typeof(FireSteed), //Set the tents up people! - #region Arachnid - typeof( GiantSpider ), typeof( DreadSpider ), typeof( FrostSpider ), typeof( Scorpion ), - #endregion + #endregion - #region Repond - typeof( ArcticOgreLord ), typeof( Cyclops ), typeof( Ettin ), typeof( EvilMage ), - typeof( FrostTroll ), typeof( Ogre ), typeof( OgreLord ), typeof( Orc ), - typeof( OrcishLord ), typeof( OrcishMage ), typeof( OrcBrute ), typeof( Ratman ), - typeof( RatmanMage ), typeof( OrcCaptain ), typeof( Troll ), typeof( Titan ), - typeof( EvilMageLord ), typeof( OrcBomber ), typeof( RatmanArcher ), - #endregion + #region Undead - #region Reptilian - typeof( Dragon ), typeof( Drake ), typeof( Snake ), typeof( GreaterDragon ), - typeof( IceSerpent ), typeof( GiantSerpent ), typeof( IceSnake ), typeof( LavaSerpent ), - typeof( Lizardman ), typeof( Wyvern ), typeof( WhiteWyrm ), - typeof( ShadowWyrm ), typeof( SilverSerpent ), typeof( LavaSnake ), - #endregion + typeof(Skeleton), typeof(SkeletalKnight), typeof(SkeletalMage), typeof(Mummy), + typeof(BoneKnight), typeof(Lich), typeof(LichLord), typeof(BoneMagi), + typeof(Wraith), typeof(Shade), typeof(Spectre), typeof(Zombie), + typeof(RottingCorpse), typeof(Ghoul), - #region Elementals - typeof( EarthElemental ), typeof( PoisonElemental ), typeof( FireElemental ), typeof( SnowElemental ), - typeof( IceElemental ), typeof( AcidElemental ), typeof( WaterElemental ), typeof( Efreet ), - typeof( AirElemental ), typeof( Golem ), - #endregion + #endregion - #region Random Critters - typeof( SewerRat ), typeof( GiantRat ), typeof( DireWolf ), typeof( TimberWolf ), - typeof( Cougar ), typeof( Alligator ) - #endregion - }; + #region Demons - private Timer m_Timer; + typeof(Balron), typeof(Daemon), typeof(Imp), typeof(GreaterMongbat), + typeof(Mongbat), typeof(IceFiend), typeof(Gargoyle), typeof(StoneGargoyle), + typeof(FireGargoyle), typeof(HordeMinion), - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextSpawn { get; private set; } + #endregion - [CommandProperty( AccessLevel.GameMaster )] - public int SpawnRange { get; set; } + #region Gazers - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan NextSpawnDelay { get; set; } + typeof(Gazer), typeof(ElderGazer), typeof(GazerLarva), - public override int LabelNumber => 1023633; // Brazier + #endregion - [Constructible] - public DeceitBrazier() : base( 0xE31 ) - { - Movable = false; - Light = LightType.Circle225; - NextSpawn = DateTime.UtcNow; - NextSpawnDelay = TimeSpan.FromMinutes( 15.0 ); - SpawnRange = 5; - } + #region Uncategorized - public DeceitBrazier( Serial serial ) : base( serial ) - { - } + typeof(Harpy), typeof(StoneHarpy), typeof(HeadlessOne), typeof(HellHound), + typeof(HellCat), typeof(Phoenix), typeof(LavaLizard), typeof(SandVortex), + typeof(ShadowWisp), typeof(SwampTentacle), typeof(PredatorHellCat), typeof(Wisp), - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + #endregion - writer.Write( (int)0 ); // version + #region Arachnid - writer.Write( (int)SpawnRange ); - writer.Write( NextSpawnDelay ); - } + typeof(GiantSpider), typeof(DreadSpider), typeof(FrostSpider), typeof(Scorpion), - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + #endregion - int version = reader.ReadInt(); + #region Repond - if ( version >= 0 ) - { - SpawnRange = reader.ReadInt(); - NextSpawnDelay = reader.ReadTimeSpan(); - } + typeof(ArcticOgreLord), typeof(Cyclops), typeof(Ettin), typeof(EvilMage), + typeof(FrostTroll), typeof(Ogre), typeof(OgreLord), typeof(Orc), + typeof(OrcishLord), typeof(OrcishMage), typeof(OrcBrute), typeof(Ratman), + typeof(RatmanMage), typeof(OrcCaptain), typeof(Troll), typeof(Titan), + typeof(EvilMageLord), typeof(OrcBomber), typeof(RatmanArcher), - NextSpawn = DateTime.UtcNow; - } + #endregion - public virtual void HeedWarning() - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500761 );// Heed this warning well, and use this brazier at your own peril. - } + #region Reptilian - public override bool HandlesOnMovement => true; + typeof(Dragon), typeof(Drake), typeof(Snake), typeof(GreaterDragon), + typeof(IceSerpent), typeof(GiantSerpent), typeof(IceSnake), typeof(LavaSerpent), + typeof(Lizardman), typeof(Wyvern), typeof(WhiteWyrm), + typeof(ShadowWyrm), typeof(SilverSerpent), typeof(LavaSnake), - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( NextSpawn < DateTime.UtcNow ) // means we haven't spawned anything if the next spawn is below - { - if ( Utility.InRange( m.Location, Location, 1 ) && !Utility.InRange( oldLocation, Location, 1 ) && m.Player && !(m.AccessLevel > AccessLevel.Player || m.Hidden) ) - { - if ( m_Timer == null || !m_Timer.Running ) - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 2 ), HeedWarning ); - } - } + #endregion - base.OnMovement( m, oldLocation ); - } + #region Elementals - public Point3D GetSpawnPosition() - { - Map map = Map; + typeof(EarthElemental), typeof(PoisonElemental), typeof(FireElemental), typeof(SnowElemental), + typeof(IceElemental), typeof(AcidElemental), typeof(WaterElemental), typeof(Efreet), + typeof(AirElemental), typeof(Golem), - if ( map == null ) - return Location; + #endregion - // Try 10 times to find a Spawnable location. - for( int i = 0; i < 10; i++ ) - { - int x = Location.X + (Utility.Random( (SpawnRange * 2) + 1 ) - SpawnRange); - int y = Location.Y + (Utility.Random( (SpawnRange * 2) + 1 ) - SpawnRange); - int z = Map.GetAverageZ( x, y ); + #region Random Critters - if ( Map.CanSpawnMobile( new Point2D( x, y ), Z ) ) - return new Point3D( x, y, Z ); - if ( Map.CanSpawnMobile( new Point2D( x, y ), z ) ) - return new Point3D( x, y, z ); - } + typeof(SewerRat), typeof(GiantRat), typeof(DireWolf), typeof(TimberWolf), + typeof(Cougar), typeof(Alligator) - return Location; - } + #endregion + }; - public virtual void DoEffect( Point3D loc, Map map ) - { - Effects.SendLocationParticles( EffectItem.Create( loc, map, EffectItem.DefaultDuration ), 0x3709, 10, 30, 5052 ); - Effects.PlaySound( loc, map, 0x225 ); - } + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextSpawn{ get; private set; } - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( from.Location, Location, 2 ) ) - { - try - { - if ( NextSpawn < DateTime.UtcNow ) - { - Map map = Map; - BaseCreature bc = (BaseCreature)Activator.CreateInstance( Creatures[Utility.Random( Creatures.Length )] ); + [CommandProperty(AccessLevel.GameMaster)] + public int SpawnRange{ get; set; } - if ( bc != null ) - { - Point3D spawnLoc = GetSpawnPosition(); + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan NextSpawnDelay{ get; set; } - DoEffect( spawnLoc, map ); + public override int LabelNumber => 1023633; // Brazier - Timer.DelayCall( TimeSpan.FromSeconds( 1 ), delegate - { - bc.Home = Location; - bc.RangeHome = SpawnRange; - bc.FightMode = FightMode.Closest; + public override bool HandlesOnMovement => true; - bc.MoveToWorld( spawnLoc, map ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - DoEffect( spawnLoc, map ); + writer.Write(0); // version - bc.ForceReacquire(); - } ); + writer.Write(SpawnRange); + writer.Write(NextSpawnDelay); + } - NextSpawn = DateTime.UtcNow + NextSpawnDelay; - } - } - else - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500760 ); // The brazier fizzes and pops, but nothing seems to happen. - } - } - catch - { - } - } - else - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version >= 0) + { + SpawnRange = reader.ReadInt(); + NextSpawnDelay = reader.ReadTimeSpan(); + } + + NextSpawn = DateTime.UtcNow; + } + + public virtual void HeedWarning() + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, + 500761); // Heed this warning well, and use this brazier at your own peril. + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (NextSpawn < DateTime.UtcNow) // means we haven't spawned anything if the next spawn is below + if (Utility.InRange(m.Location, Location, 1) && !Utility.InRange(oldLocation, Location, 1) && m.Player && + !(m.AccessLevel > AccessLevel.Player || m.Hidden)) + if (m_Timer == null || !m_Timer.Running) + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(2), HeedWarning); + + base.OnMovement(m, oldLocation); + } + + public Point3D GetSpawnPosition() + { + Map map = Map; + + if (map == null) + return Location; + + // Try 10 times to find a Spawnable location. + for (int i = 0; i < 10; i++) + { + int x = Location.X + (Utility.Random(SpawnRange * 2 + 1) - SpawnRange); + int y = Location.Y + (Utility.Random(SpawnRange * 2 + 1) - SpawnRange); + int z = Map.GetAverageZ(x, y); + + if (Map.CanSpawnMobile(new Point2D(x, y), Z)) + return new Point3D(x, y, Z); + if (Map.CanSpawnMobile(new Point2D(x, y), z)) + return new Point3D(x, y, z); + } + + return Location; + } + + public virtual void DoEffect(Point3D loc, Map map) + { + Effects.SendLocationParticles(EffectItem.Create(loc, map, EffectItem.DefaultDuration), 0x3709, 10, 30, 5052); + Effects.PlaySound(loc, map, 0x225); + } + + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(from.Location, Location, 2)) + try + { + if (NextSpawn < DateTime.UtcNow) + { + Map map = Map; + BaseCreature bc = + (BaseCreature)Activator.CreateInstance(Creatures[Utility.Random(Creatures.Length)]); + + if (bc != null) + { + Point3D spawnLoc = GetSpawnPosition(); + + DoEffect(spawnLoc, map); + + Timer.DelayCall(TimeSpan.FromSeconds(1), delegate + { + bc.Home = Location; + bc.RangeHome = SpawnRange; + bc.FightMode = FightMode.Closest; + + bc.MoveToWorld(spawnLoc, map); + + DoEffect(spawnLoc, map); + + bc.ForceReacquire(); + }); + + NextSpawn = DateTime.UtcNow + NextSpawnDelay; + } + } + else + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, + 500760); // The brazier fizzes and pops, but nothing seems to happen. + } + } + catch + { + } + else + from.SendLocalizedMessage(500446); // That is too far away. + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/EffectController.cs b/Scripts/Items/Misc/EffectController.cs index 57ee575b7..e8a2e6c72 100644 --- a/Scripts/Items/Misc/EffectController.cs +++ b/Scripts/Items/Misc/EffectController.cs @@ -2,314 +2,339 @@ using System; namespace Server.Items { - public enum ECEffectType - { - None, - Moving, - Location, - Target, - Lightning - } + public enum ECEffectType + { + None, + Moving, + Location, + Target, + Lightning + } + + public enum EffectTriggerType + { + None, + Sequenced, + DoubleClick, + InRange + } + + public class EffectController : Item + { + private IEntity m_Source; + private IEntity m_Target; + + [Constructible] + public EffectController() : base(0x1B72) + { + Movable = false; + Visible = false; + TriggerType = EffectTriggerType.Sequenced; + EffectLayer = (EffectLayer)255; + } + + public EffectController(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public ECEffectType EffectType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public EffectTriggerType TriggerType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public EffectLayer EffectLayer{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan EffectDelay{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan TriggerDelay{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan SoundDelay{ get; set; } - public enum EffectTriggerType - { - None, - Sequenced, - DoubleClick, - InRange - } - public class EffectController : Item - { - private IEntity m_Source; - private IEntity m_Target; + [CommandProperty(AccessLevel.GameMaster)] + public Item SourceItem + { + get => m_Source as Item; + set => m_Source = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile SourceMobile + { + get => m_Source as Mobile; + set => m_Source = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool SourceNull + { + get => m_Source == null; + set + { + if (value) m_Source = null; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public ECEffectType EffectType { get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public EffectTriggerType TriggerType { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public Item TargetItem + { + get => m_Target as Item; + set => m_Target = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile TargetMobile + { + get => m_Target as Mobile; + set => m_Target = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool TargetNull + { + get => m_Target == null; + set + { + if (value) m_Target = null; + } + } + + + [CommandProperty(AccessLevel.GameMaster)] + public EffectController Sequence{ get; set; } + + + [CommandProperty(AccessLevel.GameMaster)] + private bool FixedDirection{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + private bool Explodes{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + private bool PlaySoundAtTrigger{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public EffectLayer EffectLayer { get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan EffectDelay { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int EffectItemID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int EffectHue{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan TriggerDelay { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int RenderMode{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan SoundDelay { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int Speed{ get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int Duration{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public Item SourceItem{ get => m_Source as Item; - set => m_Source = value; - } + [CommandProperty(AccessLevel.GameMaster)] + public int ParticleEffect{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile SourceMobile{ get => m_Source as Mobile; - set => m_Source = value; - } + [CommandProperty(AccessLevel.GameMaster)] + public int ExplodeParticleEffect{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public bool SourceNull{ get => ( m_Source == null ); - set{ if ( value ) m_Source = null; } } + [CommandProperty(AccessLevel.GameMaster)] + public int ExplodeSound{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Unknown{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int SoundID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int TriggerRange{ get; set; } + + public override string DefaultName => "Effect Controller"; + + public override bool HandlesOnMovement => TriggerType == EffectTriggerType.InRange; + + public override void OnDoubleClick(Mobile from) + { + if (TriggerType == EffectTriggerType.DoubleClick) + DoEffect(from); + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m.Location != oldLocation && TriggerType == EffectTriggerType.InRange && + Utility.InRange(GetWorldLocation(), m.Location, TriggerRange) && + !Utility.InRange(GetWorldLocation(), oldLocation, TriggerRange)) + DoEffect(m); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(EffectDelay); + writer.Write(TriggerDelay); + writer.Write(SoundDelay); + + if (m_Source is Item srcItem) + writer.Write(srcItem); + else + writer.Write(m_Source as Mobile); + if (m_Target is Item targItem) + writer.Write(targItem); + else + writer.Write(m_Target as Mobile); - [CommandProperty( AccessLevel.GameMaster )] - public Item TargetItem{ get => m_Target as Item; - set => m_Target = value; - } + writer.Write(Sequence); - [CommandProperty( AccessLevel.GameMaster )] - public Mobile TargetMobile{ get => m_Target as Mobile; - set => m_Target = value; - } + writer.Write(FixedDirection); + writer.Write(Explodes); + writer.Write(PlaySoundAtTrigger); - [CommandProperty( AccessLevel.GameMaster )] - public bool TargetNull{ get => ( m_Target == null ); - set{ if ( value ) m_Target = null; } } + writer.WriteEncodedInt((int)EffectType); + writer.WriteEncodedInt((int)EffectLayer); + writer.WriteEncodedInt((int)TriggerType); - - [CommandProperty( AccessLevel.GameMaster )] - public EffectController Sequence { get; set; } - - - [CommandProperty( AccessLevel.GameMaster )] - private bool FixedDirection { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - private bool Explodes { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - private bool PlaySoundAtTrigger { get; set; } - - - [CommandProperty( AccessLevel.GameMaster )] - public int EffectItemID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int EffectHue { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RenderMode { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Speed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Duration { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ParticleEffect { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ExplodeParticleEffect { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ExplodeSound { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Unknown { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int SoundID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int TriggerRange { get; set; } - - public override string DefaultName => "Effect Controller"; - - [Constructible] - public EffectController() : base( 0x1B72 ) - { - Movable = false; - Visible = false; - TriggerType = EffectTriggerType.Sequenced; - EffectLayer = (EffectLayer)255; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( TriggerType == EffectTriggerType.DoubleClick ) - DoEffect( from ); - } - - public override bool HandlesOnMovement => ( TriggerType == EffectTriggerType.InRange ); - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m.Location != oldLocation && TriggerType == EffectTriggerType.InRange && Utility.InRange( GetWorldLocation(), m.Location, TriggerRange ) && !Utility.InRange( GetWorldLocation(), oldLocation, TriggerRange ) ) - DoEffect( m ); - } - - public EffectController( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( EffectDelay ); - writer.Write( TriggerDelay ); - writer.Write( SoundDelay ); - - if ( m_Source is Item srcItem ) - writer.Write( srcItem ); - else - writer.Write( m_Source as Mobile ); - - if ( m_Target is Item targItem ) - writer.Write( targItem ); - else - writer.Write( m_Target as Mobile ); - - writer.Write( Sequence as Item ); - - writer.Write( FixedDirection ); - writer.Write( Explodes ); - writer.Write( PlaySoundAtTrigger ); - - writer.WriteEncodedInt( (int) EffectType ); - writer.WriteEncodedInt( (int) EffectLayer ); - writer.WriteEncodedInt( (int) TriggerType ); - - writer.WriteEncodedInt( EffectItemID ); - writer.WriteEncodedInt( EffectHue ); - writer.WriteEncodedInt( RenderMode ); - writer.WriteEncodedInt( Speed ); - writer.WriteEncodedInt( Duration ); - writer.WriteEncodedInt( ParticleEffect ); - writer.WriteEncodedInt( ExplodeParticleEffect ); - writer.WriteEncodedInt( ExplodeSound ); - writer.WriteEncodedInt( Unknown ); - writer.WriteEncodedInt( SoundID ); - writer.WriteEncodedInt( TriggerRange ); - } - - private IEntity ReadEntity( GenericReader reader ) - { - return World.FindEntity( reader.ReadInt() ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - EffectDelay = reader.ReadTimeSpan(); - TriggerDelay = reader.ReadTimeSpan(); - SoundDelay = reader.ReadTimeSpan(); - - m_Source = ReadEntity( reader ); - m_Target = ReadEntity( reader ); - Sequence = reader.ReadItem() as EffectController; - - FixedDirection = reader.ReadBool(); - Explodes = reader.ReadBool(); - PlaySoundAtTrigger = reader.ReadBool(); - - EffectType = (ECEffectType)reader.ReadEncodedInt(); - EffectLayer = (EffectLayer)reader.ReadEncodedInt(); - TriggerType = (EffectTriggerType)reader.ReadEncodedInt(); - - EffectItemID = reader.ReadEncodedInt(); - EffectHue = reader.ReadEncodedInt(); - RenderMode = reader.ReadEncodedInt(); - Speed = reader.ReadEncodedInt(); - Duration = reader.ReadEncodedInt(); - ParticleEffect = reader.ReadEncodedInt(); - ExplodeParticleEffect = reader.ReadEncodedInt(); - ExplodeSound = reader.ReadEncodedInt(); - Unknown = reader.ReadEncodedInt(); - SoundID = reader.ReadEncodedInt(); - TriggerRange = reader.ReadEncodedInt(); - - break; - } - } - } - - public void PlaySound(IEntity trigger) - { - IEntity ent = null; - - if (PlaySoundAtTrigger) - ent = trigger; - - if (ent == null) - ent = this; - - Effects.PlaySound((ent as Item)?.GetWorldLocation() ?? ent.Location, ent.Map, SoundID); - } - - public void DoEffect(IEntity trigger) - { - if (Deleted || TriggerType == EffectTriggerType.None) - return; - - if (trigger is Mobile mobile && mobile.Hidden && mobile.AccessLevel > AccessLevel.Player) - return; - - if (SoundID > 0) - Timer.DelayCall(SoundDelay, PlaySound, trigger); - - if (Sequence != null) - Timer.DelayCall(TriggerDelay, Sequence.DoEffect, trigger); - - if (EffectType != ECEffectType.None) - Timer.DelayCall(EffectDelay, InternalDoEffect, trigger); - } - - public void InternalDoEffect(IEntity trigger) - { - IEntity from = m_Source, to = m_Target; - - if (from == null) - from = trigger; - - if (to == null) - to = trigger; - - switch (EffectType) - { - case ECEffectType.Lightning: - { - Effects.SendBoltEffect(from, false, EffectHue); - break; - } - case ECEffectType.Location: - { - Effects.SendLocationParticles(EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration), EffectItemID, Speed, Duration, EffectHue, RenderMode, ParticleEffect, Unknown); - break; - } - case ECEffectType.Moving: - { - if (from == this) - from = EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration); - - if (to == this) - to = EffectItem.Create(to.Location, to.Map, EffectItem.DefaultDuration); - - Effects.SendMovingParticles(from, to, EffectItemID, Speed, Duration, FixedDirection, Explodes, EffectHue, RenderMode, ParticleEffect, ExplodeParticleEffect, ExplodeSound, EffectLayer, Unknown); - break; - } - case ECEffectType.Target: - { - Effects.SendTargetParticles(from, EffectItemID, Speed, Duration, EffectHue, RenderMode, ParticleEffect, EffectLayer, Unknown); - break; - } - } - } - } -} + writer.WriteEncodedInt(EffectItemID); + writer.WriteEncodedInt(EffectHue); + writer.WriteEncodedInt(RenderMode); + writer.WriteEncodedInt(Speed); + writer.WriteEncodedInt(Duration); + writer.WriteEncodedInt(ParticleEffect); + writer.WriteEncodedInt(ExplodeParticleEffect); + writer.WriteEncodedInt(ExplodeSound); + writer.WriteEncodedInt(Unknown); + writer.WriteEncodedInt(SoundID); + writer.WriteEncodedInt(TriggerRange); + } + + private IEntity ReadEntity(GenericReader reader) + { + return World.FindEntity(reader.ReadInt()); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + EffectDelay = reader.ReadTimeSpan(); + TriggerDelay = reader.ReadTimeSpan(); + SoundDelay = reader.ReadTimeSpan(); + + m_Source = ReadEntity(reader); + m_Target = ReadEntity(reader); + Sequence = reader.ReadItem() as EffectController; + + FixedDirection = reader.ReadBool(); + Explodes = reader.ReadBool(); + PlaySoundAtTrigger = reader.ReadBool(); + + EffectType = (ECEffectType)reader.ReadEncodedInt(); + EffectLayer = (EffectLayer)reader.ReadEncodedInt(); + TriggerType = (EffectTriggerType)reader.ReadEncodedInt(); + + EffectItemID = reader.ReadEncodedInt(); + EffectHue = reader.ReadEncodedInt(); + RenderMode = reader.ReadEncodedInt(); + Speed = reader.ReadEncodedInt(); + Duration = reader.ReadEncodedInt(); + ParticleEffect = reader.ReadEncodedInt(); + ExplodeParticleEffect = reader.ReadEncodedInt(); + ExplodeSound = reader.ReadEncodedInt(); + Unknown = reader.ReadEncodedInt(); + SoundID = reader.ReadEncodedInt(); + TriggerRange = reader.ReadEncodedInt(); + + break; + } + } + } + + public void PlaySound(IEntity trigger) + { + IEntity ent = null; + + if (PlaySoundAtTrigger) + ent = trigger; + + if (ent == null) + ent = this; + + Effects.PlaySound((ent as Item)?.GetWorldLocation() ?? ent.Location, ent.Map, SoundID); + } + + public void DoEffect(IEntity trigger) + { + if (Deleted || TriggerType == EffectTriggerType.None) + return; + + if (trigger is Mobile mobile && mobile.Hidden && mobile.AccessLevel > AccessLevel.Player) + return; + + if (SoundID > 0) + Timer.DelayCall(SoundDelay, PlaySound, trigger); + + if (Sequence != null) + Timer.DelayCall(TriggerDelay, Sequence.DoEffect, trigger); + + if (EffectType != ECEffectType.None) + Timer.DelayCall(EffectDelay, InternalDoEffect, trigger); + } + + public void InternalDoEffect(IEntity trigger) + { + IEntity from = m_Source, to = m_Target; + + if (from == null) + from = trigger; + + if (to == null) + to = trigger; + + switch (EffectType) + { + case ECEffectType.Lightning: + { + Effects.SendBoltEffect(from, false, EffectHue); + break; + } + case ECEffectType.Location: + { + Effects.SendLocationParticles(EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration), + EffectItemID, Speed, Duration, EffectHue, RenderMode, ParticleEffect, Unknown); + break; + } + case ECEffectType.Moving: + { + if (from == this) + from = EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration); + + if (to == this) + to = EffectItem.Create(to.Location, to.Map, EffectItem.DefaultDuration); + + Effects.SendMovingParticles(from, to, EffectItemID, Speed, Duration, FixedDirection, Explodes, EffectHue, + RenderMode, ParticleEffect, ExplodeParticleEffect, ExplodeSound, EffectLayer, Unknown); + break; + } + case ECEffectType.Target: + { + Effects.SendTargetParticles(from, EffectItemID, Speed, Duration, EffectHue, RenderMode, ParticleEffect, + EffectLayer, Unknown); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/EffectItem.cs b/Scripts/Items/Misc/EffectItem.cs index 2d569f3d7..b54e8ab45 100644 --- a/Scripts/Items/Misc/EffectItem.cs +++ b/Scripts/Items/Misc/EffectItem.cs @@ -3,85 +3,85 @@ using System.Collections.Generic; namespace Server.Items { - public class EffectItem : Item - { - private static List m_Free = new List(); // List of available EffectItems + public class EffectItem : Item + { + private static List m_Free = new List(); // List of available EffectItems - public static readonly TimeSpan DefaultDuration = TimeSpan.FromSeconds( 5.0 ); + public static readonly TimeSpan DefaultDuration = TimeSpan.FromSeconds(5.0); - public static EffectItem Create( Point3D p, Map map, TimeSpan duration ) - { - EffectItem item = null; + private EffectItem() : base(1) // nodraw + { + Movable = false; + } - for ( int i = m_Free.Count - 1; item == null && i >= 0; --i ) // We reuse new entries first so decay works better - { - EffectItem free = m_Free[i]; + public EffectItem(Serial serial) : base(serial) + { + } - m_Free.RemoveAt( i ); + public override bool Decays => true; - if ( !free.Deleted && free.Map == Map.Internal ) - item = free; - } + public static EffectItem Create(Point3D p, Map map, TimeSpan duration) + { + EffectItem item = null; - if ( item == null ) - item = new EffectItem(); - else - item.ItemID = 1; + for (int i = m_Free.Count - 1; item == null && i >= 0; --i) // We reuse new entries first so decay works better + { + EffectItem free = m_Free[i]; - item.MoveToWorld( p, map ); - item.BeginFree( duration ); + m_Free.RemoveAt(i); - return item; - } + if (!free.Deleted && free.Map == Map.Internal) + item = free; + } - private EffectItem() : base( 1 ) // nodraw - { - Movable = false; - } + if (item == null) + item = new EffectItem(); + else + item.ItemID = 1; - public void BeginFree( TimeSpan duration ) - { - new FreeTimer( this, duration ).Start(); - } + item.MoveToWorld(p, map); + item.BeginFree(duration); - public override bool Decays => true; + return item; + } - public EffectItem( Serial serial ) : base( serial ) - { - } + public void BeginFree(TimeSpan duration) + { + new FreeTimer(this, duration).Start(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } + Delete(); + } - private class FreeTimer : Timer - { - private EffectItem m_Item; + private class FreeTimer : Timer + { + private EffectItem m_Item; - public FreeTimer( EffectItem item, TimeSpan delay ) : base( delay ) - { - m_Item = item; - Priority = TimerPriority.OneSecond; - } + public FreeTimer(EffectItem item, TimeSpan delay) : base(delay) + { + m_Item = item; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - m_Item.Internalize(); + protected override void OnTick() + { + m_Item.Internalize(); - m_Free.Add( m_Item ); - } - } - } + m_Free.Add(m_Item); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/ExecutionersCap.cs b/Scripts/Items/Misc/ExecutionersCap.cs index bdae2932d..4ea91829d 100644 --- a/Scripts/Items/Misc/ExecutionersCap.cs +++ b/Scripts/Items/Misc/ExecutionersCap.cs @@ -1,29 +1,29 @@ namespace Server.Items { - public class ExecutionersCap : Item - { - [Constructible] - public ExecutionersCap() : base(0xF83) - { - Weight = 1.0; - } + public class ExecutionersCap : Item + { + [Constructible] + public ExecutionersCap() : base(0xF83) + { + Weight = 1.0; + } - public ExecutionersCap(Serial serial) : base(serial) - { - } + public ExecutionersCap(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Firebomb.cs b/Scripts/Items/Misc/Firebomb.cs index 8d6b4174e..a96b41010 100644 --- a/Scripts/Items/Misc/Firebomb.cs +++ b/Scripts/Items/Misc/Firebomb.cs @@ -1,290 +1,298 @@ +using System; +using System.Collections.Generic; using Server.Network; using Server.Spells; using Server.Targeting; -using System; -using System.Collections.Generic; namespace Server.Items { - public class Firebomb : Item - { - private Timer m_Timer; - private int m_Ticks; - private Mobile m_LitBy; - private List m_Users; + public class Firebomb : Item + { + private Mobile m_LitBy; + private int m_Ticks; + private Timer m_Timer; + private List m_Users; - [Constructible] - public Firebomb() : this( 0x99B ) - { - } + [Constructible] + public Firebomb() : this(0x99B) + { + } - [Constructible] - public Firebomb( int itemID ) : base( itemID ) - { - //Name = "a firebomb"; - Weight = 2.0; - Hue = 1260; - } + [Constructible] + public Firebomb(int itemID) : base(itemID) + { + //Name = "a firebomb"; + Weight = 2.0; + Hue = 1260; + } - public Firebomb( Serial serial ) : base( serial ) - { - } + public Firebomb(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - if ( Core.AOS && (from.Paralyzed || from.Frozen || (from.Spell != null && from.Spell.IsCasting)) ) - { - // to prevent exploiting for pvp - from.SendLocalizedMessage( 1075857 ); // You cannot use that while paralyzed. - return; - } + if (Core.AOS && (from.Paralyzed || from.Frozen || from.Spell != null && from.Spell.IsCasting)) + { + // to prevent exploiting for pvp + from.SendLocalizedMessage(1075857); // You cannot use that while paralyzed. + return; + } - if ( m_Timer == null ) - { - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1 ), TimeSpan.FromSeconds( 1 ), OnFirebombTimerTick ); - m_LitBy = from; - from.SendLocalizedMessage( 1060582 ); // You light the firebomb. Throw it now! - } - else - from.SendLocalizedMessage( 1060581 ); // You've already lit it! Better throw it now! + if (m_Timer == null) + { + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1), TimeSpan.FromSeconds(1), OnFirebombTimerTick); + m_LitBy = from; + from.SendLocalizedMessage(1060582); // You light the firebomb. Throw it now! + } + else + { + from.SendLocalizedMessage(1060581); // You've already lit it! Better throw it now! + } - if ( m_Users == null ) - m_Users = new List(); + if (m_Users == null) + m_Users = new List(); - if ( !m_Users.Contains( from ) ) - m_Users.Add( from ); + if (!m_Users.Contains(from)) + m_Users.Add(from); - from.Target = new ThrowTarget( this ); - } + from.Target = new ThrowTarget(this); + } - private void OnFirebombTimerTick() - { - if ( Deleted ) - { - m_Timer.Stop(); - return; - } + private void OnFirebombTimerTick() + { + if (Deleted) + { + m_Timer.Stop(); + return; + } - if ( Map == Map.Internal && HeldBy == null ) - return; + if (Map == Map.Internal && HeldBy == null) + return; - switch ( m_Ticks ) - { - case 0: - case 1: - case 2: - { - ++m_Ticks; + switch (m_Ticks) + { + case 0: + case 1: + case 2: + { + ++m_Ticks; - if ( HeldBy != null ) - HeldBy.PublicOverheadMessage( MessageType.Regular, 957, false, m_Ticks.ToString() ); - else if ( RootParent == null ) - PublicOverheadMessage( MessageType.Regular, 957, false, m_Ticks.ToString() ); - else if ( RootParent is Mobile mobile ) - mobile.PublicOverheadMessage( MessageType.Regular, 957, false, m_Ticks.ToString() ); + if (HeldBy != null) + HeldBy.PublicOverheadMessage(MessageType.Regular, 957, false, m_Ticks.ToString()); + else if (RootParent == null) + PublicOverheadMessage(MessageType.Regular, 957, false, m_Ticks.ToString()); + else if (RootParent is Mobile mobile) + mobile.PublicOverheadMessage(MessageType.Regular, 957, false, m_Ticks.ToString()); - break; - } - default: - { - HeldBy?.DropHolding(); + break; + } + default: + { + HeldBy?.DropHolding(); - if ( m_Users != null ) - { - foreach ( Mobile m in m_Users ) - { - if ( m.Target is ThrowTarget targ && targ.Bomb == this ) - Target.Cancel( m ); - } + if (m_Users != null) + { + foreach (Mobile m in m_Users) + if (m.Target is ThrowTarget targ && targ.Bomb == this) + Target.Cancel(m); - m_Users.Clear(); - m_Users = null; - } + m_Users.Clear(); + m_Users = null; + } - if ( RootParent is Mobile parent ) - { - parent.SendLocalizedMessage( 1060583 ); // The firebomb explodes in your hand! - AOS.Damage( parent, Utility.Random( 3 ) + 4, 0, 100, 0, 0, 0 ); - } - else if ( RootParent == null ) - { - List toDamage = new List(); - IPooledEnumerable eable = Map.GetMobilesInRange( Location, 1 ); + if (RootParent is Mobile parent) + { + parent.SendLocalizedMessage(1060583); // The firebomb explodes in your hand! + AOS.Damage(parent, Utility.Random(3) + 4, 0, 100, 0, 0, 0); + } + else if (RootParent == null) + { + List toDamage = new List(); + IPooledEnumerable eable = Map.GetMobilesInRange(Location, 1); - foreach ( Mobile m in eable ) - toDamage.Add( m ); + foreach (Mobile m in eable) + toDamage.Add(m); - eable.Free(); + eable.Free(); - for ( int i = 0; i < toDamage.Count; ++i ) - { - Mobile victim = toDamage[i]; + for (int i = 0; i < toDamage.Count; ++i) + { + Mobile victim = toDamage[i]; - if ( m_LitBy == null || (SpellHelper.ValidIndirectTarget( m_LitBy, victim ) && m_LitBy.CanBeHarmful( victim, false )) ) - { - m_LitBy?.DoHarmful( victim ); + if (m_LitBy == null || SpellHelper.ValidIndirectTarget(m_LitBy, victim) && + m_LitBy.CanBeHarmful(victim, false)) + { + m_LitBy?.DoHarmful(victim); - AOS.Damage( victim, m_LitBy, Utility.Random( 3 ) + 4, 0, 100, 0, 0, 0 ); - } - } - (new FirebombField( m_LitBy, toDamage )).MoveToWorld( Location, Map ); - } + AOS.Damage(victim, m_LitBy, Utility.Random(3) + 4, 0, 100, 0, 0, 0); + } + } - m_Timer.Stop(); - Delete(); - break; - } - } - } + new FirebombField(m_LitBy, toDamage).MoveToWorld(Location, Map); + } - private void OnFirebombTarget( Mobile from, object obj ) - { - if ( Deleted || Map == Map.Internal || !IsChildOf( from.Backpack ) ) - return; + m_Timer.Stop(); + Delete(); + break; + } + } + } - if ( !(obj is IPoint3D p) ) - return; + private void OnFirebombTarget(Mobile from, object obj) + { + if (Deleted || Map == Map.Internal || !IsChildOf(from.Backpack)) + return; - SpellHelper.GetSurfaceTop( ref p ); + if (!(obj is IPoint3D p)) + return; - from.RevealingAction(); + SpellHelper.GetSurfaceTop(ref p); - IEntity to = p as IEntity ?? new Entity( Serial.Zero, new Point3D( p ), Map ); + from.RevealingAction(); - Effects.SendMovingEffect( from, to, ItemID, 7, 0, false, false, Hue, 0 ); + IEntity to = p as IEntity ?? new Entity(Serial.Zero, new Point3D(p), Map); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( FirebombReposition_OnTick ), new object[]{ p, Map } ); - Internalize(); - } + Effects.SendMovingEffect(from, to, ItemID, 7, 0, false, false, Hue, 0); - private void FirebombReposition_OnTick( object state ) - { - if ( Deleted ) - return; + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(FirebombReposition_OnTick), + new object[] { p, Map }); + Internalize(); + } - object[] states = (object[])state; - IPoint3D p = (IPoint3D)states[0]; - Map map = (Map)states[1]; + private void FirebombReposition_OnTick(object state) + { + if (Deleted) + return; - MoveToWorld( new Point3D( p ), map ); - } + object[] states = (object[])state; + IPoint3D p = (IPoint3D)states[0]; + Map map = (Map)states[1]; - private class ThrowTarget : Target - { - public Firebomb Bomb { get; } + MoveToWorld(new Point3D(p), map); + } - public ThrowTarget( Firebomb bomb ) - : base( 12, true, TargetFlags.None ) - { - Bomb = bomb; - } + private class ThrowTarget : Target + { + public ThrowTarget(Firebomb bomb) + : base(12, true, TargetFlags.None) + { + Bomb = bomb; + } - protected override void OnTarget( Mobile from, object targeted ) - { - Bomb.OnFirebombTarget( from, targeted ); - } - } - } + public Firebomb Bomb{ get; } - public class FirebombField : Item - { - private List m_Burning; - private Timer m_Timer; - private Mobile m_LitBy; - private DateTime m_Expire; + protected override void OnTarget(Mobile from, object targeted) + { + Bomb.OnFirebombTarget(from, targeted); + } + } + } - public FirebombField( Mobile litBy, List toDamage ) : base( 0x376A ) - { - Movable = false; - m_LitBy = litBy; - m_Expire = DateTime.UtcNow + TimeSpan.FromSeconds( 10 ); - m_Burning = toDamage; - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ), OnFirebombFieldTimerTick ); - } + public class FirebombField : Item + { + private List m_Burning; + private DateTime m_Expire; + private Mobile m_LitBy; + private Timer m_Timer; - public FirebombField( Serial serial ) : base( serial ) - { - } + public FirebombField(Mobile litBy, List toDamage) : base(0x376A) + { + Movable = false; + m_LitBy = litBy; + m_Expire = DateTime.UtcNow + TimeSpan.FromSeconds(10); + m_Burning = toDamage; + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0), OnFirebombFieldTimerTick); + } - public override void Serialize( GenericWriter writer ) - { - // Don't serialize these... - } + public FirebombField(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - } + public override void Serialize(GenericWriter writer) + { + // Don't serialize these... + } - public override bool OnMoveOver( Mobile m ) - { - if ( ItemID == 0x398C && m_LitBy == null || (SpellHelper.ValidIndirectTarget( m_LitBy, m ) && m_LitBy.CanBeHarmful( m, false )) ) - { - m_LitBy?.DoHarmful( m ); + public override void Deserialize(GenericReader reader) + { + } - AOS.Damage( m, m_LitBy, 2, 0, 100, 0, 0, 0 ); - m.PlaySound( 0x208 ); + public override bool OnMoveOver(Mobile m) + { + if (ItemID == 0x398C && m_LitBy == null || + SpellHelper.ValidIndirectTarget(m_LitBy, m) && m_LitBy.CanBeHarmful(m, false)) + { + m_LitBy?.DoHarmful(m); - if ( !m_Burning.Contains( m ) ) - m_Burning.Add( m ); - } + AOS.Damage(m, m_LitBy, 2, 0, 100, 0, 0, 0); + m.PlaySound(0x208); - return true; - } + if (!m_Burning.Contains(m)) + m_Burning.Add(m); + } - private void OnFirebombFieldTimerTick() - { - if ( Deleted ) - { - m_Timer.Stop(); - return; - } + return true; + } - if ( ItemID == 0x376A ) - { - ItemID = 0x398C; - return; - } + private void OnFirebombFieldTimerTick() + { + if (Deleted) + { + m_Timer.Stop(); + return; + } - for ( int i = 0; i < m_Burning.Count; ) - { - Mobile victim = m_Burning[i]; + if (ItemID == 0x376A) + { + ItemID = 0x398C; + return; + } - if ( victim.Location == Location && victim.Map == Map && (m_LitBy == null || ( SpellHelper.ValidIndirectTarget( m_LitBy, victim ) && m_LitBy.CanBeHarmful( victim, false ) )) ) - { - m_LitBy?.DoHarmful( victim ); + for (int i = 0; i < m_Burning.Count;) + { + Mobile victim = m_Burning[i]; - AOS.Damage( victim, m_LitBy, Utility.Random( 3 ) + 4, 0, 100, 0, 0, 0 ); - ++i; - } - else - m_Burning.RemoveAt( i ); - } + if (victim.Location == Location && victim.Map == Map && + (m_LitBy == null || SpellHelper.ValidIndirectTarget(m_LitBy, victim) && + m_LitBy.CanBeHarmful(victim, false))) + { + m_LitBy?.DoHarmful(victim); - if ( DateTime.UtcNow >= m_Expire ) - { - m_Timer.Stop(); - Delete(); - } - } - } -} + AOS.Damage(victim, m_LitBy, Utility.Random(3) + 4, 0, 100, 0, 0, 0); + ++i; + } + else + { + m_Burning.RemoveAt(i); + } + } + + if (DateTime.UtcNow >= m_Expire) + { + m_Timer.Stop(); + Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/FlippableAddonAttribute.cs b/Scripts/Items/Misc/FlippableAddonAttribute.cs index f39fc93be..4e6cfb4aa 100644 --- a/Scripts/Items/Misc/FlippableAddonAttribute.cs +++ b/Scripts/Items/Misc/FlippableAddonAttribute.cs @@ -4,116 +4,113 @@ using Server.Multis; namespace Server.Items { - [AttributeUsage( AttributeTargets.Class )] - public class FlippableAddonAttribute : Attribute - { - private static string m_MethodName = "Flip"; + [AttributeUsage(AttributeTargets.Class)] + public class FlippableAddonAttribute : Attribute + { + private static string m_MethodName = "Flip"; - private static Type[] m_Params = { - typeof( Mobile ), typeof( Direction ) - }; + private static Type[] m_Params = + { + typeof(Mobile), typeof(Direction) + }; - public Direction[] Directions { get; } + public FlippableAddonAttribute(params Direction[] directions) + { + Directions = directions; + } - public FlippableAddonAttribute( params Direction[] directions ) - { - Directions = directions; - } + public Direction[] Directions{ get; } - public virtual void Flip( Mobile from, Item addon ) - { - if ( Directions != null && Directions.Length > 1 ) - { - try - { - MethodInfo flipMethod = addon.GetType().GetMethod( m_MethodName, m_Params ); + public virtual void Flip(Mobile from, Item addon) + { + if (Directions != null && Directions.Length > 1) + try + { + MethodInfo flipMethod = addon.GetType().GetMethod(m_MethodName, m_Params); - if ( flipMethod != null ) - { - int index = 0; + if (flipMethod != null) + { + int index = 0; - for ( int i = 0; i < Directions.Length; i++ ) - { - if ( addon.Direction == Directions[ i ] ) - { - index = i + 1; - break; - } - } + for (int i = 0; i < Directions.Length; i++) + if (addon.Direction == Directions[i]) + { + index = i + 1; + break; + } - if ( index >= Directions.Length ) - index = 0; + if (index >= Directions.Length) + index = 0; - ClearComponents( addon ); + ClearComponents(addon); - flipMethod.Invoke( addon, new object[ 2 ] { from, Directions[ index ] } ); + flipMethod.Invoke(addon, new object[2] { from, Directions[index] }); - BaseHouse house = null; - AddonFitResult result = AddonFitResult.Valid; + BaseHouse house = null; + AddonFitResult result = AddonFitResult.Valid; - addon.Map = Map.Internal; + addon.Map = Map.Internal; - if ( addon is BaseAddon baseAddon ) - result = baseAddon.CouldFit( baseAddon.Location, from.Map, from, ref house ); - else if ( addon is BaseAddonContainer container ) - result = container.CouldFit( container.Location, from.Map, from, ref house ); + if (addon is BaseAddon baseAddon) + result = baseAddon.CouldFit(baseAddon.Location, from.Map, from, ref house); + else if (addon is BaseAddonContainer container) + result = container.CouldFit(container.Location, from.Map, from, ref house); - addon.Map = from.Map; + addon.Map = from.Map; - if ( result != AddonFitResult.Valid ) - { - if ( index == 0 ) - index = Directions.Length - 1; - else - index -= 1; + if (result != AddonFitResult.Valid) + { + if (index == 0) + index = Directions.Length - 1; + else + index -= 1; - ClearComponents( addon ); + ClearComponents(addon); - flipMethod.Invoke( addon, new object[ 2 ] { from, Directions[ index ] } ); + flipMethod.Invoke(addon, new object[2] { from, Directions[index] }); - if ( result == AddonFitResult.Blocked ) - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - else if ( result == AddonFitResult.NotInHouse ) - from.SendLocalizedMessage( 500274 ); // You can only place this in a house that you own! - else if ( result == AddonFitResult.DoorsNotClosed ) - from.SendMessage( "You must close all house doors before placing this." ); - else if ( result == AddonFitResult.DoorTooClose ) - from.SendLocalizedMessage( 500271 ); // You cannot build near the door. - else if ( result == AddonFitResult.NoWall ) - from.SendLocalizedMessage( 500268 ); // This object needs to be mounted on something. - } + if (result == AddonFitResult.Blocked) + from.SendLocalizedMessage(500269); // You cannot build that there. + else if (result == AddonFitResult.NotInHouse) + from.SendLocalizedMessage(500274); // You can only place this in a house that you own! + else if (result == AddonFitResult.DoorsNotClosed) + from.SendMessage("You must close all house doors before placing this."); + else if (result == AddonFitResult.DoorTooClose) + from.SendLocalizedMessage(500271); // You cannot build near the door. + else if (result == AddonFitResult.NoWall) + from.SendLocalizedMessage(500268); // This object needs to be mounted on something. + } - addon.Direction = Directions[ index ]; - } - } - catch - { - } - } - } + addon.Direction = Directions[index]; + } + } + catch + { + } + } - private void ClearComponents( Item item ) - { - if ( item is BaseAddon addon ) - { - foreach ( AddonComponent c in addon.Components ) - { - c.Addon = null; - c.Delete(); - } + private void ClearComponents(Item item) + { + if (item is BaseAddon addon) + { + foreach (AddonComponent c in addon.Components) + { + c.Addon = null; + c.Delete(); + } - addon.Components.Clear(); - } - else if ( item is BaseAddonContainer addonContainer ) - { - foreach ( AddonContainerComponent c in addonContainer.Components ) - { - c.Addon = null; - c.Delete(); - } + addon.Components.Clear(); + } + else if (item is BaseAddonContainer addonContainer) + { + foreach (AddonContainerComponent c in addonContainer.Components) + { + c.Addon = null; + c.Delete(); + } - addonContainer.Components.Clear(); - } - } - } -} + addonContainer.Components.Clear(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/FlippableAttribute.cs b/Scripts/Items/Misc/FlippableAttribute.cs index d28c5caef..e55a23786 100644 --- a/Scripts/Items/Misc/FlippableAttribute.cs +++ b/Scripts/Items/Misc/FlippableAttribute.cs @@ -1,110 +1,102 @@ using System; using System.Reflection; -using Server.Targeting; using Server.Commands; +using Server.Targeting; namespace Server.Items { - public class FlipCommandHandlers - { - public static void Initialize() - { - CommandSystem.Register( "Flip", AccessLevel.GameMaster, Flip_OnCommand ); - } + public class FlipCommandHandlers + { + public static void Initialize() + { + CommandSystem.Register("Flip", AccessLevel.GameMaster, Flip_OnCommand); + } - [Usage( "Flip" )] - [Description( "Turns an item." )] - public static void Flip_OnCommand( CommandEventArgs e ) - { - e.Mobile.Target = new FlipTarget(); - } + [Usage("Flip")] + [Description("Turns an item.")] + public static void Flip_OnCommand(CommandEventArgs e) + { + e.Mobile.Target = new FlipTarget(); + } - private class FlipTarget : Target - { - public FlipTarget() - : base( -1, false, TargetFlags.None ) - { - } + private class FlipTarget : Target + { + public FlipTarget() + : base(-1, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Item item ) - { - if ( item.Movable == false && from.AccessLevel == AccessLevel.Player ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Item item) + { + if (item.Movable == false && from.AccessLevel == AccessLevel.Player) + return; - Type type = item.GetType(); + Type type = item.GetType(); - FlippableAttribute[] AttributeArray = (FlippableAttribute[])type.GetCustomAttributes( typeof( FlippableAttribute ), false ); + FlippableAttribute[] AttributeArray = + (FlippableAttribute[])type.GetCustomAttributes(typeof(FlippableAttribute), false); - if ( AttributeArray.Length == 0 ) - { - return; - } + if (AttributeArray.Length == 0) return; - FlippableAttribute fa = AttributeArray[0]; + FlippableAttribute fa = AttributeArray[0]; - fa.Flip( item ); - } - } - } - } + fa.Flip(item); + } + } + } + } - [AttributeUsage( AttributeTargets.Class )] - public class DynamicFlipingAttribute : Attribute - { - public DynamicFlipingAttribute() - { - } - } + [AttributeUsage(AttributeTargets.Class)] + public class DynamicFlipingAttribute : Attribute + { + } - [AttributeUsage( AttributeTargets.Class )] - public class FlippableAttribute : Attribute - { - public int[] ItemIDs { get; } + [AttributeUsage(AttributeTargets.Class)] + public class FlippableAttribute : Attribute + { + public FlippableAttribute() + : this(null) + { + } - public FlippableAttribute() - : this( null ) - { - } + public FlippableAttribute(params int[] itemIDs) + { + ItemIDs = itemIDs; + } - public FlippableAttribute( params int[] itemIDs ) - { - ItemIDs = itemIDs; - } + public int[] ItemIDs{ get; } - public virtual void Flip( Item item ) - { - if ( ItemIDs == null ) - { - try - { - MethodInfo flipMethod = item.GetType().GetMethod( "Flip", Type.EmptyTypes ); - if ( flipMethod != null ) - flipMethod.Invoke( item, new object[0] ); - } - catch - { - } + public virtual void Flip(Item item) + { + if (ItemIDs == null) + { + try + { + MethodInfo flipMethod = item.GetType().GetMethod("Flip", Type.EmptyTypes); + if (flipMethod != null) + flipMethod.Invoke(item, new object[0]); + } + catch + { + } + } + else + { + int index = 0; + for (int i = 0; i < ItemIDs.Length; i++) + if (item.ItemID == ItemIDs[i]) + { + index = i + 1; + break; + } - } - else - { - int index = 0; - for( int i = 0; i < ItemIDs.Length; i++ ) - { - if ( item.ItemID == ItemIDs[i] ) - { - index = i + 1; - break; - } - } + if (index > ItemIDs.Length - 1) + index = 0; - if ( index > ItemIDs.Length - 1 ) - index = 0; - - item.ItemID = ItemIDs[index]; - } - } - } -} + item.ItemID = ItemIDs[index]; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/GlassItems.cs b/Scripts/Items/Misc/GlassItems.cs index caae5b7ea..7ac415ff0 100644 --- a/Scripts/Items/Misc/GlassItems.cs +++ b/Scripts/Items/Misc/GlassItems.cs @@ -1,1215 +1,1216 @@ namespace Server.Items { - [FlippableAttribute( 0x182E, 0x182F, 0x1830, 0x1831 )] - public class SmallFlask : Item - { - [Constructible] - public SmallFlask() : base( 0x182E ) - { - Weight = 1.0; - Movable = true; - } - - public SmallFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x182A, 0x182B, 0x182C, 0x182D )] - public class MediumFlask : Item - { - [Constructible] - public MediumFlask() : base( 0x182A ) - { - Weight = 1.0; - Movable = true; - } - - public MediumFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x183B, 0x183C, 0x183D )] - public class LargeFlask : Item - { - [Constructible] - public LargeFlask() : base( 0x183B ) - { - Weight = 1.0; - Movable = true; - } - - public LargeFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1832, 0x1833, 0x1834, 0x1835, 0x1836, 0x1837 )] - public class CurvedFlask : Item - { - [Constructible] - public CurvedFlask() : base( 0x1832 ) - { - Weight = 1.0; - Movable = true; - } - - public CurvedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x1838, 0x1839, 0x183A )] - public class LongFlask : Item - { - [Constructible] - public LongFlask() : base( 0x1838 ) - { - Weight = 1.0; - Movable = true; - } - - public LongFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x1810, 0x1811 )] - public class SpinningHourglass : Item - { - [Constructible] - public SpinningHourglass() : base( 0x1810 ) - { - Weight = 1.0; - Movable = true; - } - - public SpinningHourglass( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenBottle : Item - { - [Constructible] - public GreenBottle() : base( 0x0EFB ) - { - Weight = 1.0; - Movable = true; - } - - public GreenBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RedBottle : Item - { - [Constructible] - public RedBottle() : base( 0x0EFC ) - { - Weight = 1.0; - Movable = true; - } - - public RedBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallBrownBottle : Item - { - [Constructible] - public SmallBrownBottle() : base( 0x0EFD ) - { - Weight = 1.0; - Movable = true; - } - - public SmallBrownBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallGreenBottle : Item - { - [Constructible] - public SmallGreenBottle() : base( 0x0F01 ) - { - Weight = 1.0; - Movable = true; - } - - public SmallGreenBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallVioletBottle : Item - { - [Constructible] - public SmallVioletBottle() : base( 0x0F02 ) - { - Weight = 1.0; - Movable = true; - } - - public SmallVioletBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TinyYellowBottle : Item - { - [Constructible] - public TinyYellowBottle() : base( 0x0F03 ) - { - Weight = 1.0; - Movable = true; - } - - public TinyYellowBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - //remove - public class SmallBlueFlask : Item - { - [Constructible] - public SmallBlueFlask() : base( 0x182A ) - { - Weight = 1.0; - Movable = true; - } - - public SmallBlueFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallYellowFlask : Item - { - [Constructible] - public SmallYellowFlask() : base( 0x182B ) - { - Weight = 1.0; - Movable = true; - } - - public SmallYellowFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallRedFlask : Item - { - [Constructible] - public SmallRedFlask() : base( 0x182C ) - { - Weight = 1.0; - Movable = true; - } - - public SmallRedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallEmptyFlask : Item - { - [Constructible] - public SmallEmptyFlask() : base( 0x182D ) - { - Weight = 1.0; - Movable = true; - } - - public SmallEmptyFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class YellowBeaker : Item - { - [Constructible] - public YellowBeaker() : base( 0x182E ) - { - Weight = 1.0; - Movable = true; - } - - public YellowBeaker( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RedBeaker : Item - { - [Constructible] - public RedBeaker() : base( 0x182F ) - { - Weight = 1.0; - Movable = true; - } - - public RedBeaker( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BlueBeaker : Item - { - [Constructible] - public BlueBeaker() : base( 0x1830 ) - { - Weight = 1.0; - Movable = true; - } - - public BlueBeaker( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenBeaker : Item - { - [Constructible] - public GreenBeaker() : base( 0x1831 ) - { - Weight = 1.0; - Movable = true; - } - - public GreenBeaker( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EmptyCurvedFlaskW : Item - { - [Constructible] - public EmptyCurvedFlaskW() : base( 0x1832 ) - { - Weight = 1.0; - Movable = true; - } - - public EmptyCurvedFlaskW( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RedCurvedFlask : Item - { - [Constructible] - public RedCurvedFlask() : base( 0x1833 ) - { - Weight = 1.0; - Movable = true; - } - - public RedCurvedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LtBlueCurvedFlask : Item - { - [Constructible] - public LtBlueCurvedFlask() : base( 0x1834 ) - { - Weight = 1.0; - Movable = true; - } - - public LtBlueCurvedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EmptyCurvedFlaskE : Item - { - [Constructible] - public EmptyCurvedFlaskE() : base( 0x1835 ) - { - Weight = 1.0; - Movable = true; - } - - public EmptyCurvedFlaskE( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BlueCurvedFlask : Item - { - [Constructible] - public BlueCurvedFlask() : base( 0x1836 ) - { - Weight = 1.0; - Movable = true; - } - - public BlueCurvedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenCurvedFlask : Item - { - [Constructible] - public GreenCurvedFlask() : base( 0x1837 ) - { - Weight = 1.0; - Movable = true; - } - - public GreenCurvedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RedRibbedFlask : Item - { - [Constructible] - public RedRibbedFlask() : base( 0x1838 ) - { - Weight = 1.0; - Movable = true; - } - - public RedRibbedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class VioletRibbedFlask : Item - { - [Constructible] - public VioletRibbedFlask() : base( 0x1839 ) - { - Weight = 1.0; - Movable = true; - } - - public VioletRibbedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EmptyRibbedFlask : Item - { - [Constructible] - public EmptyRibbedFlask() : base( 0x183A ) - { - Weight = 1.0; - Movable = true; - } - - public EmptyRibbedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LargeYellowFlask : Item - { - [Constructible] - public LargeYellowFlask() : base( 0x183B ) - { - Weight = 1.0; - Movable = true; - } - - public LargeYellowFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LargeVioletFlask : Item - { - [Constructible] - public LargeVioletFlask() : base( 0x183C ) - { - Weight = 1.0; - Movable = true; - } - - public LargeVioletFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LargeEmptyFlask : Item - { - [Constructible] - public LargeEmptyFlask() : base( 0x183D ) - { - Weight = 1.0; - Movable = true; - } - - public LargeEmptyFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AniRedRibbedFlask : Item - { - [Constructible] - public AniRedRibbedFlask() : base( 0x183E ) - { - Weight = 1.0; - Movable = true; - } - - public AniRedRibbedFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AniLargeVioletFlask : Item - { - [Constructible] - public AniLargeVioletFlask() : base( 0x1841 ) - { - Weight = 1.0; - Movable = true; - } - - public AniLargeVioletFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AniSmallBlueFlask : Item - { - [Constructible] - public AniSmallBlueFlask() : base( 0x1844 ) - { - Weight = 1.0; - Movable = true; - } - - public AniSmallBlueFlask( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallBlueBottle : Item - { - [Constructible] - public SmallBlueBottle() : base( 0x1847 ) - { - Weight = 1.0; - Movable = true; - } - - public SmallBlueBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallGreenBottle2 : Item - { - [Constructible] - public SmallGreenBottle2() : base( 0x1848 ) - { - Weight = 1.0; - Movable = true; - } - - public SmallGreenBottle2( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x185B, 0x185C )] - public class EmptyVialsWRack : Item - { - [Constructible] - public EmptyVialsWRack() : base( 0x185B ) - { - Weight = 1.0; - Movable = true; - } - - public EmptyVialsWRack( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [FlippableAttribute( 0x185D, 0x185E )] - public class FullVialsWRack : Item - { - [Constructible] - public FullVialsWRack() : base( 0x185D ) - { - Weight = 1.0; - Movable = true; - } - - public FullVialsWRack( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class EmptyVial : Item - { - [Constructible] - public EmptyVial() : base( 0x0E24 ) - { - Weight = 1.0; - Movable = true; - } - - public EmptyVial( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class HourglassAni : Item - { - [Constructible] - public HourglassAni() : base( 0x1811 ) - { - Weight = 1.0; - Movable = true; - } - - public HourglassAni( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Hourglass : Item - { - [Constructible] - public Hourglass() : base( 0x1810 ) - { - Weight = 1.0; - Movable = true; - } - - public Hourglass( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TinyRedBottle : Item - { - [Constructible] - public TinyRedBottle() : base( 0x0F04 ) - { - Weight = 1.0; - Movable = true; - } - - public TinyRedBottle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + [Flippable(0x182E, 0x182F, 0x1830, 0x1831)] + public class SmallFlask : Item + { + [Constructible] + public SmallFlask() : base(0x182E) + { + Weight = 1.0; + Movable = true; + } + + public SmallFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x182A, 0x182B, 0x182C, 0x182D)] + public class MediumFlask : Item + { + [Constructible] + public MediumFlask() : base(0x182A) + { + Weight = 1.0; + Movable = true; + } + + public MediumFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x183B, 0x183C, 0x183D)] + public class LargeFlask : Item + { + [Constructible] + public LargeFlask() : base(0x183B) + { + Weight = 1.0; + Movable = true; + } + + public LargeFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1832, 0x1833, 0x1834, 0x1835, 0x1836, 0x1837)] + public class CurvedFlask : Item + { + [Constructible] + public CurvedFlask() : base(0x1832) + { + Weight = 1.0; + Movable = true; + } + + public CurvedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1838, 0x1839, 0x183A)] + public class LongFlask : Item + { + [Constructible] + public LongFlask() : base(0x1838) + { + Weight = 1.0; + Movable = true; + } + + public LongFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1810, 0x1811)] + public class SpinningHourglass : Item + { + [Constructible] + public SpinningHourglass() : base(0x1810) + { + Weight = 1.0; + Movable = true; + } + + public SpinningHourglass(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenBottle : Item + { + [Constructible] + public GreenBottle() : base(0x0EFB) + { + Weight = 1.0; + Movable = true; + } + + public GreenBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RedBottle : Item + { + [Constructible] + public RedBottle() : base(0x0EFC) + { + Weight = 1.0; + Movable = true; + } + + public RedBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallBrownBottle : Item + { + [Constructible] + public SmallBrownBottle() : base(0x0EFD) + { + Weight = 1.0; + Movable = true; + } + + public SmallBrownBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallGreenBottle : Item + { + [Constructible] + public SmallGreenBottle() : base(0x0F01) + { + Weight = 1.0; + Movable = true; + } + + public SmallGreenBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallVioletBottle : Item + { + [Constructible] + public SmallVioletBottle() : base(0x0F02) + { + Weight = 1.0; + Movable = true; + } + + public SmallVioletBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TinyYellowBottle : Item + { + [Constructible] + public TinyYellowBottle() : base(0x0F03) + { + Weight = 1.0; + Movable = true; + } + + public TinyYellowBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + //remove + public class SmallBlueFlask : Item + { + [Constructible] + public SmallBlueFlask() : base(0x182A) + { + Weight = 1.0; + Movable = true; + } + + public SmallBlueFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallYellowFlask : Item + { + [Constructible] + public SmallYellowFlask() : base(0x182B) + { + Weight = 1.0; + Movable = true; + } + + public SmallYellowFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallRedFlask : Item + { + [Constructible] + public SmallRedFlask() : base(0x182C) + { + Weight = 1.0; + Movable = true; + } + + public SmallRedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallEmptyFlask : Item + { + [Constructible] + public SmallEmptyFlask() : base(0x182D) + { + Weight = 1.0; + Movable = true; + } + + public SmallEmptyFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class YellowBeaker : Item + { + [Constructible] + public YellowBeaker() : base(0x182E) + { + Weight = 1.0; + Movable = true; + } + + public YellowBeaker(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RedBeaker : Item + { + [Constructible] + public RedBeaker() : base(0x182F) + { + Weight = 1.0; + Movable = true; + } + + public RedBeaker(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BlueBeaker : Item + { + [Constructible] + public BlueBeaker() : base(0x1830) + { + Weight = 1.0; + Movable = true; + } + + public BlueBeaker(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenBeaker : Item + { + [Constructible] + public GreenBeaker() : base(0x1831) + { + Weight = 1.0; + Movable = true; + } + + public GreenBeaker(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EmptyCurvedFlaskW : Item + { + [Constructible] + public EmptyCurvedFlaskW() : base(0x1832) + { + Weight = 1.0; + Movable = true; + } + + public EmptyCurvedFlaskW(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RedCurvedFlask : Item + { + [Constructible] + public RedCurvedFlask() : base(0x1833) + { + Weight = 1.0; + Movable = true; + } + + public RedCurvedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LtBlueCurvedFlask : Item + { + [Constructible] + public LtBlueCurvedFlask() : base(0x1834) + { + Weight = 1.0; + Movable = true; + } + + public LtBlueCurvedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EmptyCurvedFlaskE : Item + { + [Constructible] + public EmptyCurvedFlaskE() : base(0x1835) + { + Weight = 1.0; + Movable = true; + } + + public EmptyCurvedFlaskE(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BlueCurvedFlask : Item + { + [Constructible] + public BlueCurvedFlask() : base(0x1836) + { + Weight = 1.0; + Movable = true; + } + + public BlueCurvedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenCurvedFlask : Item + { + [Constructible] + public GreenCurvedFlask() : base(0x1837) + { + Weight = 1.0; + Movable = true; + } + + public GreenCurvedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RedRibbedFlask : Item + { + [Constructible] + public RedRibbedFlask() : base(0x1838) + { + Weight = 1.0; + Movable = true; + } + + public RedRibbedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class VioletRibbedFlask : Item + { + [Constructible] + public VioletRibbedFlask() : base(0x1839) + { + Weight = 1.0; + Movable = true; + } + + public VioletRibbedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EmptyRibbedFlask : Item + { + [Constructible] + public EmptyRibbedFlask() : base(0x183A) + { + Weight = 1.0; + Movable = true; + } + + public EmptyRibbedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LargeYellowFlask : Item + { + [Constructible] + public LargeYellowFlask() : base(0x183B) + { + Weight = 1.0; + Movable = true; + } + + public LargeYellowFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LargeVioletFlask : Item + { + [Constructible] + public LargeVioletFlask() : base(0x183C) + { + Weight = 1.0; + Movable = true; + } + + public LargeVioletFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LargeEmptyFlask : Item + { + [Constructible] + public LargeEmptyFlask() : base(0x183D) + { + Weight = 1.0; + Movable = true; + } + + public LargeEmptyFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AniRedRibbedFlask : Item + { + [Constructible] + public AniRedRibbedFlask() : base(0x183E) + { + Weight = 1.0; + Movable = true; + } + + public AniRedRibbedFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AniLargeVioletFlask : Item + { + [Constructible] + public AniLargeVioletFlask() : base(0x1841) + { + Weight = 1.0; + Movable = true; + } + + public AniLargeVioletFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AniSmallBlueFlask : Item + { + [Constructible] + public AniSmallBlueFlask() : base(0x1844) + { + Weight = 1.0; + Movable = true; + } + + public AniSmallBlueFlask(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallBlueBottle : Item + { + [Constructible] + public SmallBlueBottle() : base(0x1847) + { + Weight = 1.0; + Movable = true; + } + + public SmallBlueBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallGreenBottle2 : Item + { + [Constructible] + public SmallGreenBottle2() : base(0x1848) + { + Weight = 1.0; + Movable = true; + } + + public SmallGreenBottle2(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x185B, 0x185C)] + public class EmptyVialsWRack : Item + { + [Constructible] + public EmptyVialsWRack() : base(0x185B) + { + Weight = 1.0; + Movable = true; + } + + public EmptyVialsWRack(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x185D, 0x185E)] + public class FullVialsWRack : Item + { + [Constructible] + public FullVialsWRack() : base(0x185D) + { + Weight = 1.0; + Movable = true; + } + + public FullVialsWRack(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class EmptyVial : Item + { + [Constructible] + public EmptyVial() : base(0x0E24) + { + Weight = 1.0; + Movable = true; + } + + public EmptyVial(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class HourglassAni : Item + { + [Constructible] + public HourglassAni() : base(0x1811) + { + Weight = 1.0; + Movable = true; + } + + public HourglassAni(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Hourglass : Item + { + [Constructible] + public Hourglass() : base(0x1810) + { + Weight = 1.0; + Movable = true; + } + + public Hourglass(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TinyRedBottle : Item + { + [Constructible] + public TinyRedBottle() : base(0x0F04) + { + Weight = 1.0; + Movable = true; + } + + public TinyRedBottle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Gold.cs b/Scripts/Items/Misc/Gold.cs index b444da9cb..649088263 100644 --- a/Scripts/Items/Misc/Gold.cs +++ b/Scripts/Items/Misc/Gold.cs @@ -1,140 +1,130 @@ using System; - using Server.Accounting; namespace Server.Items { - public class Gold : Item - { - public override double DefaultWeight => ( Core.ML ? ( 0.02 / 3 ) : 0.02 ); + public class Gold : Item + { + [Constructible] + public Gold() : this(1) + { + } - [Constructible] - public Gold() : this( 1 ) - { - } + [Constructible] + public Gold(int amountFrom, int amountTo) : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } - [Constructible] - public Gold( int amountFrom, int amountTo ) : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } + [Constructible] + public Gold(int amount) : base(0xEED) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Gold( int amount ) : base( 0xEED ) - { - Stackable = true; - Amount = amount; - } + public Gold(Serial serial) : base(serial) + { + } - public Gold( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => Core.ML ? 0.02 / 3 : 0.02; - public override int GetDropSound() - { - if ( Amount <= 1 ) - return 0x2E4; - if ( Amount <= 5 ) - return 0x2E5; - return 0x2E6; - } + public override int GetDropSound() + { + if (Amount <= 1) + return 0x2E4; + if (Amount <= 5) + return 0x2E5; + return 0x2E6; + } - protected override void OnAmountChange( int oldValue ) - { - int newValue = Amount; + protected override void OnAmountChange(int oldValue) + { + int newValue = Amount; - UpdateTotal( this, TotalType.Gold, newValue - oldValue ); - } + UpdateTotal(this, TotalType.Gold, newValue - oldValue); + } #if NEWPARENT - public override void OnAdded(IEntity parent) + public override void OnAdded(IEntity parent) #else public override void OnAdded(object parent) #endif - { - base.OnAdded(parent); + { + base.OnAdded(parent); - if (!AccountGold.Enabled) - { - return; - } + if (!AccountGold.Enabled) return; - Mobile owner = null; - SecureTradeInfo tradeInfo = null; + Mobile owner = null; + SecureTradeInfo tradeInfo = null; - Container root = parent as Container; + Container root = parent as Container; - while (root?.Parent is Container) - { - root = (Container)root.Parent; - } + while (root?.Parent is Container) root = (Container)root.Parent; - parent = root ?? parent; + parent = root ?? parent; - if (parent is SecureTradeContainer trade && AccountGold.ConvertOnTrade) - { - if (trade.Trade.From.Container == trade) - { - tradeInfo = trade.Trade.From; - owner = tradeInfo.Mobile; - } - else if (trade.Trade.To.Container == trade) - { - tradeInfo = trade.Trade.To; - owner = tradeInfo.Mobile; - } - } - else if (parent is BankBox box && AccountGold.ConvertOnBank) - { - owner = box.Owner; - } + if (parent is SecureTradeContainer trade && AccountGold.ConvertOnTrade) + { + if (trade.Trade.From.Container == trade) + { + tradeInfo = trade.Trade.From; + owner = tradeInfo.Mobile; + } + else if (trade.Trade.To.Container == trade) + { + tradeInfo = trade.Trade.To; + owner = tradeInfo.Mobile; + } + } + else if (parent is BankBox box && AccountGold.ConvertOnBank) + { + owner = box.Owner; + } - if (owner?.Account == null || !owner.Account.DepositGold(Amount)) - { - return; - } + if (owner?.Account == null || !owner.Account.DepositGold(Amount)) return; - if (tradeInfo != null) - { - if (owner.NetState != null && !owner.NetState.NewSecureTrading) - { - int plat = Math.DivRem(Amount, AccountGold.CurrencyThreshold, out var gold); + if (tradeInfo != null) + { + if (owner.NetState != null && !owner.NetState.NewSecureTrading) + { + int plat = Math.DivRem(Amount, AccountGold.CurrencyThreshold, out int gold); - tradeInfo.Plat += plat; - tradeInfo.Gold += gold; - } + tradeInfo.Plat += plat; + tradeInfo.Gold += gold; + } - tradeInfo.VirtualCheck?.UpdateTrade(tradeInfo.Mobile); - } + tradeInfo.VirtualCheck?.UpdateTrade(tradeInfo.Mobile); + } - owner.SendLocalizedMessage(1042763, Amount.ToString("#,0")); + owner.SendLocalizedMessage(1042763, Amount.ToString("#,0")); - Delete(); + Delete(); - ((Container)parent).UpdateTotals(); - } + ((Container)parent).UpdateTotals(); + } - public override int GetTotal( TotalType type ) - { - int baseTotal = base.GetTotal( type ); + public override int GetTotal(TotalType type) + { + int baseTotal = base.GetTotal(type); - if ( type == TotalType.Gold ) - baseTotal += Amount; + if (type == TotalType.Gold) + baseTotal += Amount; - return baseTotal; - } + return baseTotal; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Guillotine.cs b/Scripts/Items/Misc/Guillotine.cs index a7cbbcaf5..b6104fa30 100644 --- a/Scripts/Items/Misc/Guillotine.cs +++ b/Scripts/Items/Misc/Guillotine.cs @@ -1,112 +1,113 @@ using System; using Server.Network; +using Server.Spells; namespace Server.Items { - public class Guillotine : Item - { - [Constructible] - public Guillotine() - : base( 4656 ) - { - Movable = false; - } + public class Guillotine : Item + { + private DateTime m_NextUse; - private DateTime m_NextUse; + [Constructible] + public Guillotine() + : base(4656) + { + Movable = false; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) || !from.InLOS( this ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that - } - else if ( Visible && ( ItemID == 4656 || ItemID == 4702 ) && DateTime.UtcNow >= m_NextUse ) - { - Point3D p = GetWorldLocation(); + public Guillotine(Serial serial) + : base(serial) + { + } - if ( 1 > Utility.Random( Math.Max( Math.Abs( from.X - p.X ), Math.Abs( from.Y - p.Y ) ) ) ) - { - Effects.PlaySound( from.Location, from.Map, from.GetHurtSound() ); - from.PublicOverheadMessage( MessageType.Regular, from.SpeechHue, true, "Ouch!" ); - Spells.SpellHelper.Damage( TimeSpan.FromSeconds( 0.5 ), from, Utility.Dice( 2, 10, 5 ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2) || !from.InLOS(this)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that + } + else if (Visible && (ItemID == 4656 || ItemID == 4702) && DateTime.UtcNow >= m_NextUse) + { + Point3D p = GetWorldLocation(); - Effects.PlaySound( GetWorldLocation(), Map, 0x387 ); + if (1 > Utility.Random(Math.Max(Math.Abs(from.X - p.X), Math.Abs(from.Y - p.Y)))) + { + Effects.PlaySound(from.Location, from.Map, from.GetHurtSound()); + from.PublicOverheadMessage(MessageType.Regular, from.SpeechHue, true, "Ouch!"); + SpellHelper.Damage(TimeSpan.FromSeconds(0.5), from, Utility.Dice(2, 10, 5)); + } - Timer.DelayCall( TimeSpan.FromSeconds( 0.25 ), Down1 ); - Timer.DelayCall( TimeSpan.FromSeconds( 0.50 ), Down2 ); + Effects.PlaySound(GetWorldLocation(), Map, 0x387); - Timer.DelayCall( TimeSpan.FromSeconds( 5.00 ), BackUp ); + Timer.DelayCall(TimeSpan.FromSeconds(0.25), Down1); + Timer.DelayCall(TimeSpan.FromSeconds(0.50), Down2); - m_NextUse = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 ); - } - } + Timer.DelayCall(TimeSpan.FromSeconds(5.00), BackUp); - private void Down1() - { - ItemID = ( ItemID == 4656 ? 4678 : 4712 ); - } + m_NextUse = DateTime.UtcNow + TimeSpan.FromSeconds(10.0); + } + } - private void Down2() - { - ItemID = ( ItemID == 4678 ? 4679 : 4713 ); + private void Down1() + { + ItemID = ItemID == 4656 ? 4678 : 4712; + } - Point3D p = GetWorldLocation(); - Map f = Map; + private void Down2() + { + ItemID = ItemID == 4678 ? 4679 : 4713; - if ( f == null ) - return; + Point3D p = GetWorldLocation(); + Map f = Map; - new Blood( 4650 ).MoveToWorld( p, f ); + if (f == null) + return; - for ( int i = 0; i < 4; ++i ) - { - int x = p.X - 2 + Utility.Random( 5 ); - int y = p.Y - 2 + Utility.Random( 5 ); - int z = p.Z; + new Blood(4650).MoveToWorld(p, f); - if ( !f.CanFit( x, y, z, 1, false, false, true ) ) - { - z = f.GetAverageZ( x, y ); + for (int i = 0; i < 4; ++i) + { + int x = p.X - 2 + Utility.Random(5); + int y = p.Y - 2 + Utility.Random(5); + int z = p.Z; - if ( !f.CanFit( x, y, z, 1, false, false, true ) ) - continue; - } + if (!f.CanFit(x, y, z, 1, false, false, true)) + { + z = f.GetAverageZ(x, y); - new Blood().MoveToWorld( new Point3D( x, y, z ), f ); - } - } + if (!f.CanFit(x, y, z, 1, false, false, true)) + continue; + } - private void BackUp() - { - if ( ItemID == 4678 || ItemID == 4679 ) - ItemID = 4656; - else if ( ItemID == 4712 || ItemID == 4713 ) - ItemID = 4702; - } + new Blood().MoveToWorld(new Point3D(x, y, z), f); + } + } - public Guillotine( Serial serial ) - : base( serial ) - { - } + private void BackUp() + { + if (ItemID == 4678 || ItemID == 4679) + ItemID = 4656; + else if (ItemID == 4712 || ItemID == 4713) + ItemID = 4702; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - } + writer.Write((byte)0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); + int version = reader.ReadByte(); - if ( ItemID == 4678 || ItemID == 4679 ) - ItemID = 4656; - else if ( ItemID == 4712 || ItemID == 4713 ) - ItemID = 4702; - } - } + if (ItemID == 4678 || ItemID == 4679) + ItemID = 4656; + else if (ItemID == 4712 || ItemID == 4713) + ItemID = 4702; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/HairDye.cs b/Scripts/Items/Misc/HairDye.cs index ad68162cb..d4736fe6e 100644 --- a/Scripts/Items/Misc/HairDye.cs +++ b/Scripts/Items/Misc/HairDye.cs @@ -3,166 +3,167 @@ using Server.Network; namespace Server.Items { - public class HairDye : Item - { - public override int LabelNumber => 1041060; // Hair Dye + public class HairDye : Item + { + [Constructible] + public HairDye() : base(0xEFF) + { + Weight = 1.0; + } - [Constructible] - public HairDye() : base( 0xEFF ) - { - Weight = 1.0; - } + public HairDye(Serial serial) : base(serial) + { + } - public HairDye( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041060; // Hair Dye - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - from.CloseGump( typeof( HairDyeGump ) ); - from.SendGump( new HairDyeGump( this ) ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 906, 1019045 ); // I can't reach that. - } - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 1)) + { + from.CloseGump(typeof(HairDyeGump)); + from.SendGump(new HairDyeGump(this)); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 906, 1019045); // I can't reach that. + } + } + } - public class HairDyeGump : Gump - { - private HairDye m_HairDye; + public class HairDyeGump : Gump + { + private static HairDyeEntry[] m_Entries = + { + new HairDyeEntry("*****", 1602, 26), + new HairDyeEntry("*****", 1628, 27), + new HairDyeEntry("*****", 1502, 32), + new HairDyeEntry("*****", 1302, 32), + new HairDyeEntry("*****", 1402, 32), + new HairDyeEntry("*****", 1202, 24), + new HairDyeEntry("*****", 2402, 29), + new HairDyeEntry("*****", 2213, 6), + new HairDyeEntry("*****", 1102, 8), + new HairDyeEntry("*****", 1110, 8), + new HairDyeEntry("*****", 1118, 16), + new HairDyeEntry("*****", 1134, 16) + }; - private class HairDyeEntry - { - public string Name { get; } + private HairDye m_HairDye; - public int HueStart { get; } + public HairDyeGump(HairDye dye) : base(50, 50) + { + m_HairDye = dye; - public int HueCount { get; } + AddPage(0); - public HairDyeEntry( string name, int hueStart, int hueCount ) - { - Name = name; - HueStart = hueStart; - HueCount = hueCount; - } - } + AddBackground(100, 10, 350, 355, 2600); + AddBackground(120, 54, 110, 270, 5100); - private static HairDyeEntry[] m_Entries = { - new HairDyeEntry( "*****", 1602, 26 ), - new HairDyeEntry( "*****", 1628, 27 ), - new HairDyeEntry( "*****", 1502, 32 ), - new HairDyeEntry( "*****", 1302, 32 ), - new HairDyeEntry( "*****", 1402, 32 ), - new HairDyeEntry( "*****", 1202, 24 ), - new HairDyeEntry( "*****", 2402, 29 ), - new HairDyeEntry( "*****", 2213, 6 ), - new HairDyeEntry( "*****", 1102, 8 ), - new HairDyeEntry( "*****", 1110, 8 ), - new HairDyeEntry( "*****", 1118, 16 ), - new HairDyeEntry( "*****", 1134, 16 ) - }; + AddHtmlLocalized(70, 25, 400, 35, 1011013, false, false); //
Hair Color Selection Menu
- public HairDyeGump( HairDye dye ) : base( 50, 50 ) - { - m_HairDye = dye; + AddButton(149, 328, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(185, 329, 250, 35, 1011014, false, false); // Dye my hair this color! - AddPage( 0 ); + for (int i = 0; i < m_Entries.Length; ++i) + { + AddLabel(130, 59 + i * 22, m_Entries[i].HueStart - 1, m_Entries[i].Name); + AddButton(207, 60 + i * 22, 5224, 5224, 0, GumpButtonType.Page, i + 1); + } - AddBackground( 100, 10, 350, 355, 2600 ); - AddBackground( 120, 54, 110, 270, 5100 ); + for (int i = 0; i < m_Entries.Length; ++i) + { + HairDyeEntry e = m_Entries[i]; - AddHtmlLocalized( 70, 25, 400, 35, 1011013, false, false ); //
Hair Color Selection Menu
+ AddPage(i + 1); - AddButton( 149, 328, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 185, 329, 250, 35, 1011014, false, false ); // Dye my hair this color! + for (int j = 0; j < e.HueCount; ++j) + { + AddLabel(278 + j / 16 * 80, 52 + j % 16 * 17, e.HueStart + j - 1, "*****"); + AddRadio(260 + j / 16 * 80, 52 + j % 16 * 17, 210, 211, false, i * 100 + j); + } + } + } - for ( int i = 0; i < m_Entries.Length; ++i ) - { - AddLabel( 130, 59 + (i * 22), m_Entries[i].HueStart - 1, m_Entries[i].Name ); - AddButton( 207, 60 + (i * 22), 5224, 5224, 0, GumpButtonType.Page, i + 1 ); - } + public override void OnResponse(NetState from, RelayInfo info) + { + if (m_HairDye.Deleted) + return; - for ( int i = 0; i < m_Entries.Length; ++i ) - { - HairDyeEntry e = m_Entries[i]; + Mobile m = from.Mobile; + int[] switches = info.Switches; - AddPage( i + 1 ); + if (!m_HairDye.IsChildOf(m.Backpack)) + { + m.SendLocalizedMessage(1042010); //You must have the objectin your backpack to use it. + return; + } - for ( int j = 0; j < e.HueCount; ++j ) - { - AddLabel( 278 + ((j / 16) * 80), 52 + ((j % 16) * 17), e.HueStart + j - 1, "*****" ); - AddRadio( 260 + ((j / 16) * 80), 52 + ((j % 16) * 17), 210, 211, false, (i * 100) + j ); - } - } - } + if (info.ButtonID != 0 && switches.Length > 0) + { + if (m.HairItemID == 0 && m.FacialHairItemID == 0) + { + m.SendLocalizedMessage(502623); // You have no hair to dye and cannot use this + } + else + { + // To prevent this from being exploited, the hue is abstracted into an internal list - public override void OnResponse( NetState from, RelayInfo info ) - { - if ( m_HairDye.Deleted ) - return; + int entryIndex = switches[0] / 100; + int hueOffset = switches[0] % 100; - Mobile m = from.Mobile; - int[] switches = info.Switches; + if (entryIndex >= 0 && entryIndex < m_Entries.Length) + { + HairDyeEntry e = m_Entries[entryIndex]; - if ( !m_HairDye.IsChildOf( m.Backpack ) ) - { - m.SendLocalizedMessage( 1042010 ); //You must have the objectin your backpack to use it. - return; - } + if (hueOffset >= 0 && hueOffset < e.HueCount) + { + int hue = e.HueStart + hueOffset; - if ( info.ButtonID != 0 && switches.Length > 0 ) - { - if ( m.HairItemID == 0 && m.FacialHairItemID == 0 ) - { - m.SendLocalizedMessage( 502623 ); // You have no hair to dye and cannot use this - } - else - { - // To prevent this from being exploited, the hue is abstracted into an internal list + m.HairHue = hue; + m.FacialHairHue = hue; - int entryIndex = switches[0] / 100; - int hueOffset = switches[0] % 100; + m.SendLocalizedMessage(501199); // You dye your hair + m_HairDye.Delete(); + m.PlaySound(0x4E); + } + } + } + } + else + { + m.SendLocalizedMessage(501200); // You decide not to dye your hair + } + } - if ( entryIndex >= 0 && entryIndex < m_Entries.Length ) - { - HairDyeEntry e = m_Entries[entryIndex]; + private class HairDyeEntry + { + public HairDyeEntry(string name, int hueStart, int hueCount) + { + Name = name; + HueStart = hueStart; + HueCount = hueCount; + } - if ( hueOffset >= 0 && hueOffset < e.HueCount ) - { - int hue = e.HueStart + hueOffset; + public string Name{ get; } - m.HairHue = hue; - m.FacialHairHue = hue; + public int HueStart{ get; } - m.SendLocalizedMessage( 501199 ); // You dye your hair - m_HairDye.Delete(); - m.PlaySound( 0x4E ); - } - } - } - } - else - { - m.SendLocalizedMessage( 501200 ); // You decide not to dye your hair - } - } - } -} + public int HueCount{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/HoveringWisp.cs b/Scripts/Items/Misc/HoveringWisp.cs index c8df48e17..300d690dd 100644 --- a/Scripts/Items/Misc/HoveringWisp.cs +++ b/Scripts/Items/Misc/HoveringWisp.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class HoveringWisp : Item - { - public override int LabelNumber => 1072881; // hovering wisp + public class HoveringWisp : Item + { + [Constructible] + public HoveringWisp() : base(0x2100) + { + } - [Constructible] - public HoveringWisp() : base( 0x2100 ) - { - } + public HoveringWisp(Serial serial) : base(serial) + { + } - public HoveringWisp( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072881; // hovering wisp - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/IDurability.cs b/Scripts/Items/Misc/IDurability.cs index 1b82dc9ee..8a3181805 100644 --- a/Scripts/Items/Misc/IDurability.cs +++ b/Scripts/Items/Misc/IDurability.cs @@ -1,21 +1,21 @@ namespace Server.Items { - interface IDurability - { - bool CanFortify { get; } + internal interface IDurability + { + bool CanFortify{ get; } - int InitMinHits { get; } - int InitMaxHits { get; } + int InitMinHits{ get; } + int InitMaxHits{ get; } - int HitPoints { get; set; } - int MaxHitPoints { get; set; } + int HitPoints{ get; set; } + int MaxHitPoints{ get; set; } - void ScaleDurability(); - void UnscaleDurability(); - } + void ScaleDurability(); + void UnscaleDurability(); + } - interface IWearableDurability : IDurability - { - int OnHit( BaseWeapon weapon, int damageTaken ); - } + internal interface IWearableDurability : IDurability + { + int OnHit(BaseWeapon weapon, int damageTaken); + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/InteriorDecorator.cs b/Scripts/Items/Misc/InteriorDecorator.cs index 711e6b59c..d89053ebb 100644 --- a/Scripts/Items/Misc/InteriorDecorator.cs +++ b/Scripts/Items/Misc/InteriorDecorator.cs @@ -1,309 +1,337 @@ -using Server.Network; -using Server.Multis; using Server.Gumps; +using Server.Multis; +using Server.Network; using Server.Targeting; namespace Server.Items { - public enum DecorateCommand - { - None, - Turn, - Up, - Down - } + public enum DecorateCommand + { + None, + Turn, + Up, + Down + } - public class InteriorDecorator : Item - { - private DecorateCommand m_Command; + public class InteriorDecorator : Item + { + private DecorateCommand m_Command; - [CommandProperty( AccessLevel.GameMaster )] - public DecorateCommand Command{ get => m_Command; - set{ m_Command = value; InvalidateProperties(); } } + [Constructible] + public InteriorDecorator() : base(0xFC1) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public InteriorDecorator() : base( 0xFC1 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public InteriorDecorator(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1041280; // an interior decorator + [CommandProperty(AccessLevel.GameMaster)] + public DecorateCommand Command + { + get => m_Command; + set + { + m_Command = value; + InvalidateProperties(); + } + } - public InteriorDecorator( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041280; // an interior decorator - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_Command != DecorateCommand.None ) - list.Add( 1018322 + (int)m_Command ); // Turn/Up/Down - } + if (m_Command != DecorateCommand.None) + list.Add(1018322 + (int)m_Command); // Turn/Up/Down + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !CheckUse( this, from ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (!CheckUse(this, from)) + return; - if ( from.FindGump( typeof( InternalGump ) ) == null ) - from.SendGump( new InternalGump( this ) ); + if (from.FindGump(typeof(InternalGump)) == null) + from.SendGump(new InternalGump(this)); - if ( m_Command != DecorateCommand.None ) - from.Target = new InternalTarget( this ); - } + if (m_Command != DecorateCommand.None) + from.Target = new InternalTarget(this); + } - public static bool InHouse( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + public static bool InHouse(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - return ( house != null && house.IsCoOwner( from ) ); - } + return house != null && house.IsCoOwner(from); + } - public static bool CheckUse( InteriorDecorator tool, Mobile from ) - { - /*if ( tool.Deleted || !tool.IsChildOf( from.Backpack ) ) - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - else*/ - if ( !InHouse( from ) ) - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - else - return true; + public static bool CheckUse(InteriorDecorator tool, Mobile from) + { + /*if ( tool.Deleted || !tool.IsChildOf( from.Backpack ) ) + from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. + else*/ + if (!InHouse(from)) + from.SendLocalizedMessage(502092); // You must be in your house to do this. + else + return true; - return false; - } + return false; + } - private class InternalGump : Gump - { - private InteriorDecorator m_Decorator; + private class InternalGump : Gump + { + private InteriorDecorator m_Decorator; - public InternalGump( InteriorDecorator decorator ) : base( 150, 50 ) - { - m_Decorator = decorator; + public InternalGump(InteriorDecorator decorator) : base(150, 50) + { + m_Decorator = decorator; - AddBackground( 0, 0, 200, 200, 2600 ); + AddBackground(0, 0, 200, 200, 2600); - AddButton( 50, 45, ( decorator.Command == DecorateCommand.Turn ? 2154 : 2152 ), 2154, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 90, 50, 70, 40, 1018323, false, false ); // Turn + AddButton(50, 45, decorator.Command == DecorateCommand.Turn ? 2154 : 2152, 2154, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(90, 50, 70, 40, 1018323, false, false); // Turn - AddButton( 50, 95, ( decorator.Command == DecorateCommand.Up ? 2154 : 2152 ), 2154, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 90, 100, 70, 40, 1018324, false, false ); // Up + AddButton(50, 95, decorator.Command == DecorateCommand.Up ? 2154 : 2152, 2154, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(90, 100, 70, 40, 1018324, false, false); // Up - AddButton( 50, 145, ( decorator.Command == DecorateCommand.Down ? 2154 : 2152 ), 2154, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 90, 150, 70, 40, 1018325, false, false ); // Down - } + AddButton(50, 145, decorator.Command == DecorateCommand.Down ? 2154 : 2152, 2154, 3, GumpButtonType.Reply, + 0); + AddHtmlLocalized(90, 150, 70, 40, 1018325, false, false); // Down + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - DecorateCommand command = DecorateCommand.None; + public override void OnResponse(NetState sender, RelayInfo info) + { + DecorateCommand command = DecorateCommand.None; - switch ( info.ButtonID ) - { - case 1: command = DecorateCommand.Turn; break; - case 2: command = DecorateCommand.Up; break; - case 3: command = DecorateCommand.Down; break; - } + switch (info.ButtonID) + { + case 1: + command = DecorateCommand.Turn; + break; + case 2: + command = DecorateCommand.Up; + break; + case 3: + command = DecorateCommand.Down; + break; + } - if ( command != DecorateCommand.None ) - { - m_Decorator.Command = command; - sender.Mobile.SendGump( new InternalGump( m_Decorator ) ); - sender.Mobile.Target = new InternalTarget( m_Decorator ); - } - else - Target.Cancel( sender.Mobile ); - } - } + if (command != DecorateCommand.None) + { + m_Decorator.Command = command; + sender.Mobile.SendGump(new InternalGump(m_Decorator)); + sender.Mobile.Target = new InternalTarget(m_Decorator); + } + else + { + Target.Cancel(sender.Mobile); + } + } + } - private class InternalTarget : Target - { - private InteriorDecorator m_Decorator; + private class InternalTarget : Target + { + private InteriorDecorator m_Decorator; - public InternalTarget( InteriorDecorator decorator ) : base( -1, false, TargetFlags.None ) - { - CheckLOS = false; + public InternalTarget(InteriorDecorator decorator) : base(-1, false, TargetFlags.None) + { + CheckLOS = false; - m_Decorator = decorator; - } + m_Decorator = decorator; + } - protected override void OnTargetNotAccessible( Mobile from, object targeted ) - { - OnTarget( from, targeted ); - } + protected override void OnTargetNotAccessible(Mobile from, object targeted) + { + OnTarget(from, targeted); + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Item item && CheckUse( m_Decorator, from ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Item item && CheckUse(m_Decorator, from)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - bool isDecorableComponent = false; - object addon = null; - int count = 0; + bool isDecorableComponent = false; + object addon = null; + int count = 0; - if (item is AddonComponent component) - { - count = component.Addon.Components.Count; - addon = component.Addon; - } else if (item is AddonContainerComponent containerComponent) - { - count = containerComponent.Addon.Components.Count; - addon = containerComponent.Addon; - } else if (item is BaseAddonContainer container) - { - count = container.Components.Count; - addon = container; - } + if (item is AddonComponent component) + { + count = component.Addon.Components.Count; + addon = component.Addon; + } + else if (item is AddonContainerComponent containerComponent) + { + count = containerComponent.Addon.Components.Count; + addon = containerComponent.Addon; + } + else if (item is BaseAddonContainer container) + { + count = container.Components.Count; + addon = container; + } - if (addon != null) - { - if ( count == 1 && Core.SE ) - isDecorableComponent = true; + if (addon != null) + { + if (count == 1 && Core.SE) + isDecorableComponent = true; - if ( m_Decorator.Command == DecorateCommand.Turn ) - { - FlippableAddonAttribute[] attributes = (FlippableAddonAttribute[]) addon.GetType().GetCustomAttributes( typeof( FlippableAddonAttribute ), false ); + if (m_Decorator.Command == DecorateCommand.Turn) + { + FlippableAddonAttribute[] attributes = + (FlippableAddonAttribute[])addon.GetType() + .GetCustomAttributes(typeof(FlippableAddonAttribute), false); - if ( attributes.Length > 0 ) - isDecorableComponent = true; - } - } + if (attributes.Length > 0) + isDecorableComponent = true; + } + } - if ( house == null || !house.IsCoOwner( from ) ) - { - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else if ( item.Parent != null || !house.IsInside( item ) ) - { - from.SendLocalizedMessage( 1042270 ); // That is not in your house. - } - else if ( !house.IsLockedDown( item ) && !house.IsSecure( item ) && !isDecorableComponent ) - { - if ( item is AddonComponent && m_Decorator.Command == DecorateCommand.Up ) - from.SendLocalizedMessage( 1042274 ); // You cannot raise it up any higher. - else if ( item is AddonComponent && m_Decorator.Command == DecorateCommand.Down ) - from.SendLocalizedMessage( 1042275 ); // You cannot lower it down any further. - else - from.SendLocalizedMessage( 1042271 ); // That is not locked down. - } - else if ( item is VendorRentalContract ) - { - from.SendLocalizedMessage( 1062491 ); // You cannot use the house decorator on that object. - } - else if ( item.TotalWeight + item.PileWeight > 100 ) - { - from.SendLocalizedMessage( 1042272 ); // That is too heavy. - } - else - { - switch ( m_Decorator.Command ) - { - case DecorateCommand.Up: Up( item, from ); break; - case DecorateCommand.Down: Down( item, from ); break; - case DecorateCommand.Turn: Turn( item, from ); break; - } - } - } + if (house == null || !house.IsCoOwner(from)) + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + else if (item.Parent != null || !house.IsInside(item)) + { + from.SendLocalizedMessage(1042270); // That is not in your house. + } + else if (!house.IsLockedDown(item) && !house.IsSecure(item) && !isDecorableComponent) + { + if (item is AddonComponent && m_Decorator.Command == DecorateCommand.Up) + from.SendLocalizedMessage(1042274); // You cannot raise it up any higher. + else if (item is AddonComponent && m_Decorator.Command == DecorateCommand.Down) + from.SendLocalizedMessage(1042275); // You cannot lower it down any further. + else + from.SendLocalizedMessage(1042271); // That is not locked down. + } + else if (item is VendorRentalContract) + { + from.SendLocalizedMessage(1062491); // You cannot use the house decorator on that object. + } + else if (item.TotalWeight + item.PileWeight > 100) + { + from.SendLocalizedMessage(1042272); // That is too heavy. + } + else + { + switch (m_Decorator.Command) + { + case DecorateCommand.Up: + Up(item, from); + break; + case DecorateCommand.Down: + Down(item, from); + break; + case DecorateCommand.Turn: + Turn(item, from); + break; + } + } + } - from.Target = new InternalTarget( m_Decorator ); - } + from.Target = new InternalTarget(m_Decorator); + } - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - if ( cancelType == TargetCancelType.Canceled ) - from.CloseGump( typeof( InternalGump ) ); - } + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + if (cancelType == TargetCancelType.Canceled) + from.CloseGump(typeof(InternalGump)); + } - private static void Turn( Item item, Mobile from ) - { - object addon = null; + private static void Turn(Item item, Mobile from) + { + object addon = null; - if (item is AddonComponent component) - addon = component.Addon; - else if (item is AddonContainerComponent containerComponent) - addon = containerComponent.Addon; - else if (item is BaseAddonContainer container) - addon = container; + if (item is AddonComponent component) + addon = component.Addon; + else if (item is AddonContainerComponent containerComponent) + addon = containerComponent.Addon; + else if (item is BaseAddonContainer container) + addon = container; - if (addon != null) - { + if (addon != null) + { + FlippableAddonAttribute[] aAttributes = + (FlippableAddonAttribute[])addon.GetType() + .GetCustomAttributes(typeof(FlippableAddonAttribute), false); - FlippableAddonAttribute[] aAttributes = (FlippableAddonAttribute[]) addon.GetType().GetCustomAttributes( typeof( FlippableAddonAttribute ), false ); + if (aAttributes.Length > 0) + { + aAttributes[0].Flip(from, (Item)addon); + return; + } + } - if ( aAttributes.Length > 0 ) - { - aAttributes[ 0 ].Flip( from, (Item) addon ); - return; - } - } + FlippableAttribute[] attributes = + (FlippableAttribute[])item.GetType().GetCustomAttributes(typeof(FlippableAttribute), false); - FlippableAttribute[] attributes = (FlippableAttribute[]) item.GetType().GetCustomAttributes( typeof( FlippableAttribute ), false ); + if (attributes.Length > 0) + attributes[0].Flip(item); + else + from.SendLocalizedMessage(1042273); // You cannot turn that. + } - if ( attributes.Length > 0 ) - attributes[ 0 ].Flip( item ); - else - from.SendLocalizedMessage( 1042273 ); // You cannot turn that. - } + private static void Up(Item item, Mobile from) + { + int floorZ = GetFloorZ(item); - private static void Up( Item item, Mobile from ) - { - int floorZ = GetFloorZ( item ); + if (floorZ > int.MinValue && item.Z < floorZ + 15) // Confirmed : no height checks here + item.Location = new Point3D(item.Location, item.Z + 1); + else + from.SendLocalizedMessage(1042274); // You cannot raise it up any higher. + } - if ( floorZ > int.MinValue && item.Z < (floorZ + 15) ) // Confirmed : no height checks here - item.Location = new Point3D( item.Location, item.Z + 1 ); - else - from.SendLocalizedMessage( 1042274 ); // You cannot raise it up any higher. - } + private static void Down(Item item, Mobile from) + { + int floorZ = GetFloorZ(item); - private static void Down( Item item, Mobile from ) - { - int floorZ = GetFloorZ( item ); + if (floorZ > int.MinValue && item.Z > GetFloorZ(item)) + item.Location = new Point3D(item.Location, item.Z - 1); + else + from.SendLocalizedMessage(1042275); // You cannot lower it down any further. + } - if ( floorZ > int.MinValue && item.Z > GetFloorZ( item ) ) - item.Location = new Point3D( item.Location, item.Z - 1 ); - else - from.SendLocalizedMessage( 1042275 ); // You cannot lower it down any further. - } + private static int GetFloorZ(Item item) + { + Map map = item.Map; - private static int GetFloorZ( Item item ) - { - Map map = item.Map; + if (map == null) + return int.MinValue; - if ( map == null ) - return int.MinValue; + StaticTile[] tiles = map.Tiles.GetStaticTiles(item.X, item.Y, true); - StaticTile[] tiles = map.Tiles.GetStaticTiles( item.X, item.Y, true ); + int z = int.MinValue; - int z = int.MinValue; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + int top = tile.Z; // Confirmed : no height checks here - int top = tile.Z; // Confirmed : no height checks here + if (id.Surface && !id.Impassable && top > z && top <= item.Z) + z = top; + } - if ( id.Surface && !id.Impassable && top > z && top <= item.Z ) - z = top; - } - - return z; - } - } - } -} + return z; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Key.cs b/Scripts/Items/Misc/Key.cs index 36d395536..e35f9c7c6 100644 --- a/Scripts/Items/Misc/Key.cs +++ b/Scripts/Items/Misc/Key.cs @@ -1,416 +1,407 @@ -using System; using Server.Network; -using Server.Targeting; using Server.Prompts; +using Server.Targeting; namespace Server.Items { - public enum KeyType - { - Copper = 0x100E, - Gold = 0x100F, - Iron = 0x1010, - Rusty = 0x1013 - } - - public interface ILockable - { - bool Locked{ get; set; } - uint KeyValue{ get; set; } - } - - public class Key : Item - { - private string m_Description; - private uint m_KeyVal; - - public static uint RandomValue() - { - return (uint)(0xFFFFFFFE * Utility.RandomDouble()) + 1; - } - - public static void RemoveKeys( Mobile m, uint keyValue ) - { - if ( keyValue == 0 ) - return; - - RemoveKeys( m.Backpack, keyValue ); - RemoveKeys( m.BankBox, keyValue ); - } - - public static void RemoveKeys( Container cont, uint keyValue ) - { - if ( cont == null || keyValue == 0 ) - return; - - Item[] items = cont.FindItemsByType( new[] { typeof( Key ), typeof( KeyRing ) } ); - - foreach ( Item item in items ) - { - if ( item is Key key ) - { - if ( key.KeyValue == keyValue ) - key.Delete(); - } - else - { - KeyRing keyRing = (KeyRing) item; - - keyRing.RemoveKeys( keyValue ); - } - } - } - - public static bool ContainsKey( Container cont, uint keyValue ) - { - if ( cont == null ) - return false; - - Item[] items = cont.FindItemsByType( new[] { typeof( Key ), typeof( KeyRing ) } ); - - foreach ( Item item in items ) - { - if ( item is Key key ) - { - if ( key.KeyValue == keyValue ) - return true; - } - else - { - KeyRing keyRing = (KeyRing) item; - - if ( keyRing.ContainsKey( keyValue ) ) - return true; - } - } - - return false; - } - - [CommandProperty( AccessLevel.GameMaster )] - public string Description - { - get => m_Description; - set - { - m_Description = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxRange { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public uint KeyValue - { - get => m_KeyVal; - - set - { - m_KeyVal = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Item Link { get; set; } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - - writer.Write( (int) MaxRange ); - - writer.Write( (Item) Link ); - - writer.Write( (string) m_Description ); - writer.Write( (uint) m_KeyVal ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - { - MaxRange = reader.ReadInt(); - - goto case 1; - } - case 1: - { - Link = reader.ReadItem(); - - goto case 0; - } - case 0: - { - if ( version < 2 || MaxRange == 0 ) - MaxRange = 3; - - m_Description = reader.ReadString(); - - m_KeyVal = reader.ReadUInt(); - - break; - } - } - } - - [Constructible] - public Key() : this( KeyType.Iron, 0 ) - { - } - - [Constructible] - public Key( KeyType type ) : this( type, 0 ) - { - } - - [Constructible] - public Key( uint val ) : this ( KeyType.Iron, val ) - { - } - - [Constructible] - public Key( KeyType type, uint LockVal ) : this( type, LockVal, null ) - { - m_KeyVal = LockVal; - } - - public Key( KeyType type, uint LockVal, Item link ) : base( (int)type ) - { - Weight = 1.0; - - MaxRange = 3; - m_KeyVal = LockVal; - Link = link; - } - - public Key( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 501661 ); // That key is unreachable. - return; - } - - Target t; - int number; - - if ( m_KeyVal != 0 ) - { - number = 501662; // What shall I use this key on? - t = new UnlockTarget( this ); - } - else - { - number = 501663; // This key is a key blank. Which key would you like to make a copy of? - t = new CopyTarget( this ); - } - - from.SendLocalizedMessage( number ); - from.Target = t; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - string desc; - - if ( m_KeyVal == 0 ) - desc = "(blank)"; - else if ( (desc = m_Description) == null || (desc = desc.Trim()).Length <= 0 ) - desc = null; - - if ( desc != null ) - list.Add( desc ); - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - string desc; - - if ( m_KeyVal == 0 ) - desc = "(blank)"; - else if ( (desc = m_Description) == null || (desc = desc.Trim()).Length <= 0 ) - desc = ""; - - if ( desc.Length > 0 ) - from.Send( new UnicodeMessage( Serial, ItemID, MessageType.Regular, 0x3B2, 3, "ENU", "", desc ) ); - } - - public bool UseOn( Mobile from, ILockable o ) - { - if ( o.KeyValue == KeyValue ) - { - if ( o is BaseDoor door && !door.UseLocks() ) - return false; - - o.Locked = !o.Locked; - - if ( o is LockableContainer cont1 ) - { - if ( cont1.LockLevel == -255 ) - cont1.LockLevel = cont1.RequiredSkill - 10; - } - - if ( o is Item item ) - { - if ( o.Locked ) - item.SendLocalizedMessageTo( from, 1048000 ); // You lock it. - else - item.SendLocalizedMessageTo( from, 1048001 ); // You unlock it. - - if ( item is LockableContainer cont && cont.TrapType != TrapType.None && cont.TrapOnLockpick ) - { - if ( o.Locked ) - cont.SendLocalizedMessageTo( from, 501673 ); // You re-enable the trap. - else - cont.SendLocalizedMessageTo( from, 501672 ); // You disable the trap temporarily. Lock it again to re-enable it. - } - } - - return true; - } - - return false; - } - - private class RenamePrompt : Prompt - { - private Key m_Key; - - public RenamePrompt( Key key ) - { - m_Key = key; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Key.Deleted || !m_Key.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 501661 ); // That key is unreachable. - return; - } - - m_Key.Description = Utility.FixHtml( text ); - } - } - - private class UnlockTarget : Target - { - private Key m_Key; - - public UnlockTarget( Key key ) : base( key.MaxRange, false, TargetFlags.None ) - { - m_Key = key; - CheckLOS = false; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Key.Deleted || !m_Key.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 501661 ); // That key is unreachable. - return; - } - - int number; - - if ( targeted == m_Key ) - { - number = 501665; // Enter a description for this key. - - from.Prompt = new RenamePrompt( m_Key ); - } - else if ( targeted is ILockable lockable ) - { - if ( m_Key.UseOn( from, lockable ) ) - number = -1; - else - number = 501668; // This key doesn't seem to unlock that. - } - else - { - number = 501666; // You can't unlock that! - } - - if ( number != -1 ) - { - from.SendLocalizedMessage( number ); - } - } - } - - private class CopyTarget : Target - { - private Key m_Key; - - public CopyTarget( Key key ) : base( 3, false, TargetFlags.None ) - { - m_Key = key; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Key.Deleted || !m_Key.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 501661 ); // That key is unreachable. - return; - } - - int number; - - if ( targeted is Key k ) - { - if ( k.m_KeyVal == 0 ) - { - number = 501675; // This key is also blank. - } - else if ( from.CheckTargetSkill( SkillName.Tinkering, k, 0, 75.0 ) ) - { - number = 501676; // You make a copy of the key. - - m_Key.Description = k.Description; - m_Key.KeyValue = k.KeyValue; - m_Key.Link = k.Link; - m_Key.MaxRange = k.MaxRange; - } - else if ( Utility.RandomDouble() <= 0.1 ) // 10% chance to destroy the key - { - from.SendLocalizedMessage( 501677 ); // You fail to make a copy of the key. - - number = 501678; // The key was destroyed in the attempt. - - m_Key.Delete(); - } - else - { - number = 501677; // You fail to make a copy of the key. - } - } - else - { - number = 501688; // Not a key. - } - - from.SendLocalizedMessage( number ); - } - } - } -} + public enum KeyType + { + Copper = 0x100E, + Gold = 0x100F, + Iron = 0x1010, + Rusty = 0x1013 + } + + public interface ILockable + { + bool Locked{ get; set; } + uint KeyValue{ get; set; } + } + + public class Key : Item + { + private string m_Description; + private uint m_KeyVal; + + [Constructible] + public Key() : this(KeyType.Iron, 0) + { + } + + [Constructible] + public Key(KeyType type) : this(type, 0) + { + } + + [Constructible] + public Key(uint val) : this(KeyType.Iron, val) + { + } + + [Constructible] + public Key(KeyType type, uint LockVal) : this(type, LockVal, null) + { + m_KeyVal = LockVal; + } + + public Key(KeyType type, uint LockVal, Item link) : base((int)type) + { + Weight = 1.0; + + MaxRange = 3; + m_KeyVal = LockVal; + Link = link; + } + + public Key(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Description + { + get => m_Description; + set + { + m_Description = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxRange{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public uint KeyValue + { + get => m_KeyVal; + + set + { + m_KeyVal = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Item Link{ get; set; } + + public static uint RandomValue() + { + return (uint)(0xFFFFFFFE * Utility.RandomDouble()) + 1; + } + + public static void RemoveKeys(Mobile m, uint keyValue) + { + if (keyValue == 0) + return; + + RemoveKeys(m.Backpack, keyValue); + RemoveKeys(m.BankBox, keyValue); + } + + public static void RemoveKeys(Container cont, uint keyValue) + { + if (cont == null || keyValue == 0) + return; + + Item[] items = cont.FindItemsByType(new[] { typeof(Key), typeof(KeyRing) }); + + foreach (Item item in items) + if (item is Key key) + { + if (key.KeyValue == keyValue) + key.Delete(); + } + else + { + KeyRing keyRing = (KeyRing)item; + + keyRing.RemoveKeys(keyValue); + } + } + + public static bool ContainsKey(Container cont, uint keyValue) + { + if (cont == null) + return false; + + Item[] items = cont.FindItemsByType(new[] { typeof(Key), typeof(KeyRing) }); + + foreach (Item item in items) + if (item is Key key) + { + if (key.KeyValue == keyValue) + return true; + } + else + { + KeyRing keyRing = (KeyRing)item; + + if (keyRing.ContainsKey(keyValue)) + return true; + } + + return false; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + + writer.Write(MaxRange); + + writer.Write(Link); + + writer.Write(m_Description); + writer.Write(m_KeyVal); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: + { + MaxRange = reader.ReadInt(); + + goto case 1; + } + case 1: + { + Link = reader.ReadItem(); + + goto case 0; + } + case 0: + { + if (version < 2 || MaxRange == 0) + MaxRange = 3; + + m_Description = reader.ReadString(); + + m_KeyVal = reader.ReadUInt(); + + break; + } + } + } + + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(501661); // That key is unreachable. + return; + } + + Target t; + int number; + + if (m_KeyVal != 0) + { + number = 501662; // What shall I use this key on? + t = new UnlockTarget(this); + } + else + { + number = 501663; // This key is a key blank. Which key would you like to make a copy of? + t = new CopyTarget(this); + } + + from.SendLocalizedMessage(number); + from.Target = t; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + string desc; + + if (m_KeyVal == 0) + desc = "(blank)"; + else if ((desc = m_Description) == null || (desc = desc.Trim()).Length <= 0) + desc = null; + + if (desc != null) + list.Add(desc); + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + string desc; + + if (m_KeyVal == 0) + desc = "(blank)"; + else if ((desc = m_Description) == null || (desc = desc.Trim()).Length <= 0) + desc = ""; + + if (desc.Length > 0) + from.Send(new UnicodeMessage(Serial, ItemID, MessageType.Regular, 0x3B2, 3, "ENU", "", desc)); + } + + public bool UseOn(Mobile from, ILockable o) + { + if (o.KeyValue == KeyValue) + { + if (o is BaseDoor door && !door.UseLocks()) + return false; + + o.Locked = !o.Locked; + + if (o is LockableContainer cont1) + if (cont1.LockLevel == -255) + cont1.LockLevel = cont1.RequiredSkill - 10; + + if (o is Item item) + { + if (o.Locked) + item.SendLocalizedMessageTo(from, 1048000); // You lock it. + else + item.SendLocalizedMessageTo(from, 1048001); // You unlock it. + + if (item is LockableContainer cont && cont.TrapType != TrapType.None && cont.TrapOnLockpick) + { + if (o.Locked) + cont.SendLocalizedMessageTo(from, 501673); // You re-enable the trap. + else + cont.SendLocalizedMessageTo(from, + 501672); // You disable the trap temporarily. Lock it again to re-enable it. + } + } + + return true; + } + + return false; + } + + private class RenamePrompt : Prompt + { + private Key m_Key; + + public RenamePrompt(Key key) + { + m_Key = key; + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Key.Deleted || !m_Key.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(501661); // That key is unreachable. + return; + } + + m_Key.Description = Utility.FixHtml(text); + } + } + + private class UnlockTarget : Target + { + private Key m_Key; + + public UnlockTarget(Key key) : base(key.MaxRange, false, TargetFlags.None) + { + m_Key = key; + CheckLOS = false; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Key.Deleted || !m_Key.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(501661); // That key is unreachable. + return; + } + + int number; + + if (targeted == m_Key) + { + number = 501665; // Enter a description for this key. + + from.Prompt = new RenamePrompt(m_Key); + } + else if (targeted is ILockable lockable) + { + if (m_Key.UseOn(from, lockable)) + number = -1; + else + number = 501668; // This key doesn't seem to unlock that. + } + else + { + number = 501666; // You can't unlock that! + } + + if (number != -1) from.SendLocalizedMessage(number); + } + } + + private class CopyTarget : Target + { + private Key m_Key; + + public CopyTarget(Key key) : base(3, false, TargetFlags.None) + { + m_Key = key; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Key.Deleted || !m_Key.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(501661); // That key is unreachable. + return; + } + + int number; + + if (targeted is Key k) + { + if (k.m_KeyVal == 0) + { + number = 501675; // This key is also blank. + } + else if (from.CheckTargetSkill(SkillName.Tinkering, k, 0, 75.0)) + { + number = 501676; // You make a copy of the key. + + m_Key.Description = k.Description; + m_Key.KeyValue = k.KeyValue; + m_Key.Link = k.Link; + m_Key.MaxRange = k.MaxRange; + } + else if (Utility.RandomDouble() <= 0.1) // 10% chance to destroy the key + { + from.SendLocalizedMessage(501677); // You fail to make a copy of the key. + + number = 501678; // The key was destroyed in the attempt. + + m_Key.Delete(); + } + else + { + number = 501677; // You fail to make a copy of the key. + } + } + else + { + number = 501688; // Not a key. + } + + from.SendLocalizedMessage(number); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/KeyRing.cs b/Scripts/Items/Misc/KeyRing.cs index f919bb55d..c73052af0 100644 --- a/Scripts/Items/Misc/KeyRing.cs +++ b/Scripts/Items/Misc/KeyRing.cs @@ -1,194 +1,188 @@ -using Server.Targeting; using System.Collections.Generic; +using Server.Targeting; namespace Server.Items { - public class KeyRing : Item - { - public static readonly int MaxKeys = 20; + public class KeyRing : Item + { + public static readonly int MaxKeys = 20; - public List Keys { get; private set; } + [Constructible] + public KeyRing() : base(0x1011) + { + Weight = 1.0; // They seem to have no weight on OSI ?! - [Constructible] - public KeyRing() : base( 0x1011 ) - { - Weight = 1.0; // They seem to have no weight on OSI ?! + Keys = new List(); + } - Keys = new List(); - } + public KeyRing(Serial serial) : base(serial) + { + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1060640 ); // The item must be in your backpack to use it. - return false; - } + public List Keys{ get; private set; } - if ( !(dropped is Key key) || key.KeyValue == 0 ) - { - from.SendLocalizedMessage( 501689 ); // Only non-blank keys can be put on a keyring. - return false; - } - if ( Keys.Count >= MaxKeys ) - { - from.SendLocalizedMessage( 1008138 ); // This keyring is full. - return false; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1060640); // The item must be in your backpack to use it. + return false; + } - Add( key ); - from.SendLocalizedMessage( 501691 ); // You put the key on the keyring. - return true; - } + if (!(dropped is Key key) || key.KeyValue == 0) + { + from.SendLocalizedMessage(501689); // Only non-blank keys can be put on a keyring. + return false; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1060640 ); // The item must be in your backpack to use it. - return; - } + if (Keys.Count >= MaxKeys) + { + from.SendLocalizedMessage(1008138); // This keyring is full. + return false; + } - from.SendLocalizedMessage( 501680 ); // What do you want to unlock? - from.Target = new InternalTarget( this ); - } + Add(key); + from.SendLocalizedMessage(501691); // You put the key on the keyring. + return true; + } - private class InternalTarget : Target - { - private KeyRing m_KeyRing; + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1060640); // The item must be in your backpack to use it. + return; + } - public InternalTarget( KeyRing keyRing ) : base( -1, false, TargetFlags.None ) - { - m_KeyRing = keyRing; - } + from.SendLocalizedMessage(501680); // What do you want to unlock? + from.Target = new InternalTarget(this); + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_KeyRing.Deleted || !m_KeyRing.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1060640 ); // The item must be in your backpack to use it. - return; - } + public override void OnDelete() + { + base.OnDelete(); - if ( m_KeyRing == targeted ) - { - m_KeyRing.Open( from ); - from.SendLocalizedMessage( 501685 ); // You open the keyring. - } - else if ( targeted is ILockable o ) - { - foreach ( Key key in m_KeyRing.Keys ) - { - if ( key.UseOn( from, o ) ) - return; - } + foreach (Key key in Keys) key.Delete(); - from.SendLocalizedMessage( 1008140 ); // You do not have a key for that. - } - else - { - from.SendLocalizedMessage( 501666 ); // You can't unlock that! - } - } - } + Keys.Clear(); + } - public override void OnDelete() - { - base.OnDelete(); + public void Add(Key key) + { + key.Internalize(); + Keys.Add(key); - foreach ( Key key in Keys ) - { - key.Delete(); - } + UpdateItemID(); + } - Keys.Clear(); - } + public void Open(Mobile from) + { + if (!(Parent is Container cont)) + return; - public void Add( Key key ) - { - key.Internalize(); - Keys.Add( key ); + for (int i = Keys.Count - 1; i >= 0; i--) + { + Key key = Keys[i]; - UpdateItemID(); - } + if (!key.Deleted && !cont.TryDropItem(from, key, true)) + break; - public void Open( Mobile from ) - { - if ( !(Parent is Container cont) ) - return; + Keys.RemoveAt(i); + } - for ( int i = Keys.Count - 1; i >= 0; i-- ) - { - Key key = Keys[i]; + UpdateItemID(); + } - if ( !key.Deleted && !cont.TryDropItem( from, key, true ) ) - break; + public void RemoveKeys(uint keyValue) + { + for (int i = Keys.Count - 1; i >= 0; i--) + { + Key key = Keys[i]; - Keys.RemoveAt( i ); - } + if (key.KeyValue == keyValue) + { + key.Delete(); + Keys.RemoveAt(i); + } + } - UpdateItemID(); - } + UpdateItemID(); + } - public void RemoveKeys( uint keyValue ) - { - for ( int i = Keys.Count - 1; i >= 0; i-- ) - { - Key key = Keys[i]; + public bool ContainsKey(uint keyValue) + { + foreach (Key key in Keys) + if (key.KeyValue == keyValue) + return true; - if ( key.KeyValue == keyValue ) - { - key.Delete(); - Keys.RemoveAt( i ); - } - } + return false; + } - UpdateItemID(); - } + private void UpdateItemID() + { + if (Keys.Count < 1) + ItemID = 0x1011; + else if (Keys.Count < 3) + ItemID = 0x1769; + else if (Keys.Count < 5) + ItemID = 0x176A; + else + ItemID = 0x176B; + } - public bool ContainsKey( uint keyValue ) - { - foreach ( Key key in Keys ) - { - if ( key.KeyValue == keyValue ) - return true; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return false; - } + writer.WriteEncodedInt(0); // version - private void UpdateItemID() - { - if ( Keys.Count < 1 ) - ItemID = 0x1011; - else if ( Keys.Count < 3 ) - ItemID = 0x1769; - else if ( Keys.Count < 5 ) - ItemID = 0x176A; - else - ItemID = 0x176B; - } + writer.WriteItemList(Keys); + } - public KeyRing( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadEncodedInt(); - writer.WriteEncodedInt( 0 ); // version + Keys = reader.ReadStrongItemList(); + } - writer.WriteItemList( Keys ); - } + private class InternalTarget : Target + { + private KeyRing m_KeyRing; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public InternalTarget(KeyRing keyRing) : base(-1, false, TargetFlags.None) + { + m_KeyRing = keyRing; + } - int version = reader.ReadEncodedInt(); + protected override void OnTarget(Mobile from, object targeted) + { + if (m_KeyRing.Deleted || !m_KeyRing.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1060640); // The item must be in your backpack to use it. + return; + } - Keys = reader.ReadStrongItemList(); - } - } -} + if (m_KeyRing == targeted) + { + m_KeyRing.Open(from); + from.SendLocalizedMessage(501685); // You open the keyring. + } + else if (targeted is ILockable o) + { + foreach (Key key in m_KeyRing.Keys) + if (key.UseOn(from, o)) + return; + + from.SendLocalizedMessage(1008140); // You do not have a key for that. + } + else + { + from.SendLocalizedMessage(501666); // You can't unlock that! + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/LOSBlocker.cs b/Scripts/Items/Misc/LOSBlocker.cs index ccfd144ad..4d8d8f570 100644 --- a/Scripts/Items/Misc/LOSBlocker.cs +++ b/Scripts/Items/Misc/LOSBlocker.cs @@ -2,113 +2,112 @@ using Server.Network; namespace Server.Items { - public class LOSBlocker : Item - { - public static void Initialize() - { - TileData.ItemTable[0x21A2].Flags = TileFlag.Wall | TileFlag.NoShoot; - TileData.ItemTable[0x21A2].Height = 20; - } + public class LOSBlocker : Item + { + [Constructible] + public LOSBlocker() : base(0x21A2) + { + Movable = false; + } - public override string DefaultName => "no line of sight"; + public LOSBlocker(Serial serial) : base(serial) + { + } - [Constructible] - public LOSBlocker() : base( 0x21A2 ) - { - Movable = false; - } + public override string DefaultName => "no line of sight"; - public LOSBlocker( Serial serial ) : base( serial ) - { - } + public static void Initialize() + { + TileData.ItemTable[0x21A2].Flags = TileFlag.Wall | TileFlag.NoShoot; + TileData.ItemTable[0x21A2].Height = 20; + } - protected override Packet GetWorldPacketFor( NetState state ) { - Mobile mob = state.Mobile; + protected override Packet GetWorldPacketFor(NetState state) + { + Mobile mob = state.Mobile; - if ( mob != null && mob.AccessLevel >= AccessLevel.GameMaster ) { - return new GMItemPacket( this ); - } + if (mob != null && mob.AccessLevel >= AccessLevel.GameMaster) return new GMItemPacket(this); - return base.GetWorldPacketFor( state ); - } + return base.GetWorldPacketFor(state); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 && ItemID == 0x2199 ) - ItemID = 0x21A2; - } + if (version < 1 && ItemID == 0x2199) + ItemID = 0x21A2; + } - public sealed class GMItemPacket : Packet - { - public GMItemPacket( Item item ) : base( 0x1A ) - { - EnsureCapacity( 20 ); + public sealed class GMItemPacket : Packet + { + public GMItemPacket(Item item) : base(0x1A) + { + EnsureCapacity(20); - // 14 base length - // +2 - Amount - // +2 - Hue - // +1 - Flags + // 14 base length + // +2 - Amount + // +2 - Hue + // +1 - Flags - uint serial = (uint)item.Serial.Value; - int itemID = 0x36FF; - int amount = item.Amount; - Point3D loc = item.Location; - int x = loc.X; - int y = loc.Y; - int hue = item.Hue; - int flags = item.GetPacketFlags(); - int direction = (int)item.Direction; + uint serial = (uint)item.Serial.Value; + int itemID = 0x36FF; + int amount = item.Amount; + Point3D loc = item.Location; + int x = loc.X; + int y = loc.Y; + int hue = item.Hue; + int flags = item.GetPacketFlags(); + int direction = (int)item.Direction; - if ( amount != 0 ) - serial |= 0x80000000; - else - serial &= 0x7FFFFFFF; + if (amount != 0) + serial |= 0x80000000; + else + serial &= 0x7FFFFFFF; - m_Stream.Write( (uint) serial ); - m_Stream.Write( (short) (itemID & 0x7FFF) ); + m_Stream.Write(serial); + m_Stream.Write((short)(itemID & 0x7FFF)); - if ( amount != 0 ) - m_Stream.Write( (short) amount ); + if (amount != 0) + m_Stream.Write((short)amount); - x &= 0x7FFF; + x &= 0x7FFF; - if ( direction != 0 ) - x |= 0x8000; + if (direction != 0) + x |= 0x8000; - m_Stream.Write( (short) x ); + m_Stream.Write((short)x); - y &= 0x3FFF; + y &= 0x3FFF; - if ( hue != 0 ) - y |= 0x8000; + if (hue != 0) + y |= 0x8000; - if ( flags != 0 ) - y |= 0x4000; + if (flags != 0) + y |= 0x4000; - m_Stream.Write( (short) y ); + m_Stream.Write((short)y); - if ( direction != 0 ) - m_Stream.Write( (byte) direction ); + if (direction != 0) + m_Stream.Write((byte)direction); - m_Stream.Write( (sbyte) loc.Z ); + m_Stream.Write((sbyte)loc.Z); - if ( hue != 0 ) - m_Stream.Write( (ushort) hue ); + if (hue != 0) + m_Stream.Write((ushort)hue); - if ( flags != 0 ) - m_Stream.Write( (byte) flags ); - } - } - } + if (flags != 0) + m_Stream.Write((byte)flags); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Labyrinth/MinotaurArtifact.cs b/Scripts/Items/Misc/Labyrinth/MinotaurArtifact.cs index aa703ded5..c4a354a25 100644 --- a/Scripts/Items/Misc/Labyrinth/MinotaurArtifact.cs +++ b/Scripts/Items/Misc/Labyrinth/MinotaurArtifact.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class MinotaurArtifact : Item - { - public override int LabelNumber => 1074826; // Minotaur Artifact - public override double DefaultWeight => 5.0; + public class MinotaurArtifact : Item + { + [Constructible] + public MinotaurArtifact() : base(Utility.RandomList(0xB46, 0xB48, 0x9ED)) + { + if (ItemID == 0x9ED) + Weight = 30; - [Constructible] - public MinotaurArtifact() : base( Utility.RandomList( 0xB46, 0xB48, 0x9ED ) ) - { - if ( ItemID == 0x9ED ) - Weight = 30; + LootType = LootType.Blessed; + Hue = 0x100; + } - LootType = LootType.Blessed; - Hue = 0x100; - } + public MinotaurArtifact(Serial serial) : base(serial) + { + } - public MinotaurArtifact( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074826; // Minotaur Artifact + public override double DefaultWeight => 5.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Moonstone.cs b/Scripts/Items/Misc/Moonstone.cs index 8e10a8ad8..53d4d38f0 100644 --- a/Scripts/Items/Misc/Moonstone.cs +++ b/Scripts/Items/Misc/Moonstone.cs @@ -1,200 +1,205 @@ using System; -using Server.Network; +using Server.Factions; using Server.Mobiles; +using Server.Network; namespace Server.Items { - public enum MoonstoneType - { - Felucca, Trammel - } + public enum MoonstoneType + { + Felucca, + Trammel + } - public class Moonstone : Item - { - private MoonstoneType m_Type; + public class Moonstone : Item + { + private MoonstoneType m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public MoonstoneType Type - { - get => m_Type; - set - { - m_Type = value; - InvalidateProperties(); - } - } + [Constructible] + public Moonstone(MoonstoneType type) : base(0xF8B) + { + Weight = 1.0; + m_Type = type; + } - public override int LabelNumber => 1041490 + (int)m_Type; + public Moonstone(Serial serial) : base(serial) + { + } - [Constructible] - public Moonstone( MoonstoneType type ) : base( 0xF8B ) - { - Weight = 1.0; - m_Type = type; - } + [CommandProperty(AccessLevel.GameMaster)] + public MoonstoneType Type + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - public Moonstone( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041490 + (int)m_Type; - public override void OnSingleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - Hue = Utility.RandomBirdHue(); - ProcessDelta(); - from.SendLocalizedMessage( 1005398 ); // The stone's substance shifts as you examine it. - } + public override void OnSingleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + Hue = Utility.RandomBirdHue(); + ProcessDelta(); + from.SendLocalizedMessage(1005398); // The stone's substance shifts as you examine it. + } - base.OnSingleClick( from ); - } + base.OnSingleClick(from); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.Mounted ) - { - from.SendLocalizedMessage( 1005399 ); // You can not bury a stone while you sit on a mount. - } - else if ( !from.Body.IsHuman ) - { - from.SendLocalizedMessage( 1005400 ); // You can not bury a stone in this form. - } - else if ( Factions.Sigil.ExistsOn( from ) ) - { - from.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( from.Map == GetTargetMap() || ( from.Map != Map.Trammel && from.Map != Map.Felucca ) ) - { - from.SendLocalizedMessage( 1005401 ); // You cannot bury the stone here. - } - else if ( from is PlayerMobile mobile && mobile.Young ) - { - mobile.SendLocalizedMessage( 1049543 ); // You decide against traveling to Felucca while you are still young. - } - else if ( from.Kills >= 5 ) - { - from.SendLocalizedMessage( 1005402 ); // The magic of the stone cannot be evoked by someone with blood on their hands. - } - else if ( from.Criminal ) - { - from.SendLocalizedMessage( 1005403 ); // The magic of the stone cannot be evoked by the lawless. - } - else if ( !Region.Find( from.Location, from.Map ).IsDefault || !Region.Find( from.Location, GetTargetMap() ).IsDefault ) - { - from.SendLocalizedMessage( 1005401 ); // You cannot bury the stone here. - } - else if ( !GetTargetMap().CanFit( from.Location, 16 ) ) - { - from.SendLocalizedMessage( 1005408 ); // Something is blocking the facet gate exit. - } - else - { - Movable = false; - MoveToWorld( from.Location, from.Map ); + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.Mounted) + { + from.SendLocalizedMessage(1005399); // You can not bury a stone while you sit on a mount. + } + else if (!from.Body.IsHuman) + { + from.SendLocalizedMessage(1005400); // You can not bury a stone in this form. + } + else if (Sigil.ExistsOn(from)) + { + from.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (from.Map == GetTargetMap() || from.Map != Map.Trammel && from.Map != Map.Felucca) + { + from.SendLocalizedMessage(1005401); // You cannot bury the stone here. + } + else if (from is PlayerMobile mobile && mobile.Young) + { + mobile.SendLocalizedMessage(1049543); // You decide against traveling to Felucca while you are still young. + } + else if (from.Kills >= 5) + { + from.SendLocalizedMessage( + 1005402); // The magic of the stone cannot be evoked by someone with blood on their hands. + } + else if (from.Criminal) + { + from.SendLocalizedMessage(1005403); // The magic of the stone cannot be evoked by the lawless. + } + else if (!Region.Find(from.Location, from.Map).IsDefault || + !Region.Find(from.Location, GetTargetMap()).IsDefault) + { + from.SendLocalizedMessage(1005401); // You cannot bury the stone here. + } + else if (!GetTargetMap().CanFit(from.Location, 16)) + { + from.SendLocalizedMessage(1005408); // Something is blocking the facet gate exit. + } + else + { + Movable = false; + MoveToWorld(from.Location, from.Map); - from.Animate( 32, 5, 1, true, false, 0 ); + from.Animate(32, 5, 1, true, false, 0); - new SettleTimer( this, from.Location, from.Map, GetTargetMap(), from ).Start(); - } - } + new SettleTimer(this, from.Location, from.Map, GetTargetMap(), from).Start(); + } + } - public Map GetTargetMap() - { - return ( m_Type == MoonstoneType.Felucca ) ? Map.Felucca : Map.Trammel; - } + public Map GetTargetMap() + { + return m_Type == MoonstoneType.Felucca ? Map.Felucca : Map.Trammel; + } - private class SettleTimer : Timer - { - private Item m_Stone; - private Point3D m_Location; - private Map m_Map, m_TargetMap; - private Mobile m_Caster; - private int m_Count; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public SettleTimer( Item stone, Point3D loc, Map map, Map targetMap, Mobile caster ) : base( TimeSpan.FromSeconds( 2.5 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Stone = stone; + writer.Write(0); // version - m_Location = loc; - m_Map = map; - m_TargetMap = targetMap; + writer.Write((int)m_Type); + } - m_Caster = caster; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - protected override void OnTick() - { - ++m_Count; + int version = reader.ReadInt(); - if ( m_Count == 1 ) - { - m_Stone.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1005414 ); // The stone settles into the ground. - } - else if ( m_Count >= 10 ) - { - m_Stone.Location = new Point3D( m_Stone.X, m_Stone.Y, m_Stone.Z - 1 ); + switch (version) + { + case 0: + { + m_Type = (MoonstoneType)reader.ReadInt(); - if ( m_Count == 16 ) - { - if ( !Region.Find( m_Location, m_Map ).IsDefault || !Region.Find( m_Location, m_TargetMap ).IsDefault ) - { - m_Stone.Movable = true; - m_Caster.AddToBackpack( m_Stone ); - Stop(); - return; - } + break; + } + } + } - if ( !m_TargetMap.CanFit( m_Location, 16 ) ) - { - m_Stone.Movable = true; - m_Caster.AddToBackpack( m_Stone ); - Stop(); - return; - } + private class SettleTimer : Timer + { + private Mobile m_Caster; + private int m_Count; + private Point3D m_Location; + private Map m_Map, m_TargetMap; + private Item m_Stone; - int hue = m_Stone.Hue; + public SettleTimer(Item stone, Point3D loc, Map map, Map targetMap, Mobile caster) : base( + TimeSpan.FromSeconds(2.5), TimeSpan.FromSeconds(1.0)) + { + m_Stone = stone; - if ( hue == 0 ) - hue = Utility.RandomBirdHue(); + m_Location = loc; + m_Map = map; + m_TargetMap = targetMap; - new MoonstoneGate( m_Location, m_TargetMap, m_Map, m_Caster, hue ); - new MoonstoneGate( m_Location, m_Map, m_TargetMap, m_Caster, hue ); + m_Caster = caster; + } - m_Stone.Delete(); - Stop(); - } - } - } - } + protected override void OnTick() + { + ++m_Count; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (m_Count == 1) + { + m_Stone.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1005414); // The stone settles into the ground. + } + else if (m_Count >= 10) + { + m_Stone.Location = new Point3D(m_Stone.X, m_Stone.Y, m_Stone.Z - 1); - writer.Write( (int) 0 ); // version + if (m_Count == 16) + { + if (!Region.Find(m_Location, m_Map).IsDefault || !Region.Find(m_Location, m_TargetMap).IsDefault) + { + m_Stone.Movable = true; + m_Caster.AddToBackpack(m_Stone); + Stop(); + return; + } - writer.Write( (int) m_Type ); - } + if (!m_TargetMap.CanFit(m_Location, 16)) + { + m_Stone.Movable = true; + m_Caster.AddToBackpack(m_Stone); + Stop(); + return; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int hue = m_Stone.Hue; - int version = reader.ReadInt(); + if (hue == 0) + hue = Utility.RandomBirdHue(); - switch ( version ) - { - case 0: - { - m_Type = (MoonstoneType)reader.ReadInt(); + new MoonstoneGate(m_Location, m_TargetMap, m_Map, m_Caster, hue); + new MoonstoneGate(m_Location, m_Map, m_TargetMap, m_Caster, hue); - break; - } - } - } - } -} + m_Stone.Delete(); + Stop(); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/MoonstoneGate.cs b/Scripts/Items/Misc/MoonstoneGate.cs index dbab51c09..9c0bbf352 100644 --- a/Scripts/Items/Misc/MoonstoneGate.cs +++ b/Scripts/Items/Misc/MoonstoneGate.cs @@ -3,81 +3,81 @@ using Server.Engines.PartySystem; namespace Server.Items { - public class MoonstoneGate : Moongate - { - private Mobile m_Caster; + public class MoonstoneGate : Moongate + { + private Mobile m_Caster; - public MoonstoneGate( Point3D loc, Map map, Map targetMap, Mobile caster, int hue ) : base( loc, targetMap ) - { - MoveToWorld( loc, map ); - Dispellable = false; - Hue = hue; + public MoonstoneGate(Point3D loc, Map map, Map targetMap, Mobile caster, int hue) : base(loc, targetMap) + { + MoveToWorld(loc, map); + Dispellable = false; + Hue = hue; - m_Caster = caster; + m_Caster = caster; - new InternalTimer( this ).Start(); + new InternalTimer(this).Start(); - Effects.PlaySound( loc, map, 0x20E ); - } + Effects.PlaySound(loc, map, 0x20E); + } - public MoonstoneGate( Serial serial ) : base( serial ) - { - } + public MoonstoneGate(Serial serial) : base(serial) + { + } - public override void CheckGate( Mobile m, int range ) - { - if ( m.Kills >= 5 ) - return; + public override void CheckGate(Mobile m, int range) + { + if (m.Kills >= 5) + return; - Party casterParty = Party.Get( m_Caster ); - Party userParty = Party.Get( m ); + Party casterParty = Party.Get(m_Caster); + Party userParty = Party.Get(m); - if ( m == m_Caster || (casterParty != null && userParty == casterParty) ) - base.CheckGate( m, range ); - } + if (m == m_Caster || casterParty != null && userParty == casterParty) + base.CheckGate(m, range); + } - public override void UseGate( Mobile m ) - { - if ( m.Kills >= 5 ) - return; + public override void UseGate(Mobile m) + { + if (m.Kills >= 5) + return; - Party casterParty = Party.Get( m_Caster ); - Party userParty = Party.Get( m ); + Party casterParty = Party.Get(m_Caster); + Party userParty = Party.Get(m); - if ( m == m_Caster || (casterParty != null && userParty == casterParty) ) - base.UseGate( m ); - } + if (m == m_Caster || casterParty != null && userParty == casterParty) + base.UseGate(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } + Delete(); + } - private class InternalTimer : Timer - { - private Item m_Item; + private class InternalTimer : Timer + { + private Item m_Item; - public InternalTimer( Item item ) : base( TimeSpan.FromSeconds( 30.0 ) ) - { - m_Item = item; - Priority = TimerPriority.OneSecond; - } + public InternalTimer(Item item) : base(TimeSpan.FromSeconds(30.0)) + { + m_Item = item; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - m_Item.Delete(); - } - } - } + protected override void OnTick() + { + m_Item.Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/MorphItem.cs b/Scripts/Items/Misc/MorphItem.cs index dc8296076..62a342f02 100644 --- a/Scripts/Items/Misc/MorphItem.cs +++ b/Scripts/Items/Misc/MorphItem.cs @@ -2,135 +2,143 @@ using System; namespace Server.Items { - public class MorphItem : Item - { - private int m_InRange; - private int m_OutRange; + public class MorphItem : Item + { + private int m_InRange; + private int m_OutRange; - [CommandProperty( AccessLevel.GameMaster )] - public int InactiveItemID { get; set; } + [Constructible] + public MorphItem(int inactiveItemID, int activeItemID, int range) : this(inactiveItemID, activeItemID, range, range) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int ActiveItemID { get; set; } + [Constructible] + public MorphItem(int inactiveItemID, int activeItemID, int inRange, int outRange) : base(inactiveItemID) + { + Movable = false; - [CommandProperty( AccessLevel.GameMaster )] - public int InRange - { - get => m_InRange; - set{ if ( value > 18 ) value = 18; m_InRange = value; } - } + InactiveItemID = inactiveItemID; + ActiveItemID = activeItemID; + InRange = inRange; + OutRange = outRange; + } - [CommandProperty( AccessLevel.GameMaster )] - public int OutRange - { - get => m_OutRange; - set{ if ( value > 18 ) value = 18; m_OutRange = value; } - } + public MorphItem(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int CurrentRange => ItemID == InactiveItemID ? InRange : OutRange; + [CommandProperty(AccessLevel.GameMaster)] + public int InactiveItemID{ get; set; } - [Constructible] - public MorphItem( int inactiveItemID, int activeItemID, int range ) : this( inactiveItemID, activeItemID, range, range ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int ActiveItemID{ get; set; } - [Constructible] - public MorphItem( int inactiveItemID, int activeItemID, int inRange, int outRange ) : base( inactiveItemID ) - { - Movable = false; + [CommandProperty(AccessLevel.GameMaster)] + public int InRange + { + get => m_InRange; + set + { + if (value > 18) value = 18; + m_InRange = value; + } + } - InactiveItemID = inactiveItemID; - ActiveItemID = activeItemID; - InRange = inRange; - OutRange = outRange; - } + [CommandProperty(AccessLevel.GameMaster)] + public int OutRange + { + get => m_OutRange; + set + { + if (value > 18) value = 18; + m_OutRange = value; + } + } - public MorphItem( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int CurrentRange => ItemID == InactiveItemID ? InRange : OutRange; - public override bool HandlesOnMovement => true; + public override bool HandlesOnMovement => true; - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( Utility.InRange( m.Location, Location, CurrentRange ) || Utility.InRange( oldLocation, Location, CurrentRange ) ) - Refresh(); - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (Utility.InRange(m.Location, Location, CurrentRange) || Utility.InRange(oldLocation, Location, CurrentRange)) + Refresh(); + } - public override void OnMapChange() - { - if ( !Deleted ) - Refresh(); - } + public override void OnMapChange() + { + if (!Deleted) + Refresh(); + } - public override void OnLocationChange( Point3D oldLoc ) - { - if ( !Deleted ) - Refresh(); - } + public override void OnLocationChange(Point3D oldLoc) + { + if (!Deleted) + Refresh(); + } - public void Refresh() - { - bool found = false; + public void Refresh() + { + bool found = false; - foreach ( Mobile mob in GetMobilesInRange( CurrentRange ) ) - { - if ( mob.Hidden && mob.AccessLevel > AccessLevel.Player ) - continue; + foreach (Mobile mob in GetMobilesInRange(CurrentRange)) + { + if (mob.Hidden && mob.AccessLevel > AccessLevel.Player) + continue; - found = true; - break; - } + found = true; + break; + } - if ( found ) - ItemID = ActiveItemID; - else - ItemID = InactiveItemID; + if (found) + ItemID = ActiveItemID; + else + ItemID = InactiveItemID; - Visible = ( ItemID != 0x1 ); - } + Visible = ItemID != 0x1; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) m_OutRange ); + writer.Write(m_OutRange); - writer.Write( (int) InactiveItemID ); - writer.Write( (int) ActiveItemID ); - writer.Write( (int) m_InRange ); - } + writer.Write(InactiveItemID); + writer.Write(ActiveItemID); + writer.Write(m_InRange); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_OutRange = reader.ReadInt(); - goto case 0; - } - case 0: - { - InactiveItemID = reader.ReadInt(); - ActiveItemID = reader.ReadInt(); - m_InRange = reader.ReadInt(); + switch (version) + { + case 1: + { + m_OutRange = reader.ReadInt(); + goto case 0; + } + case 0: + { + InactiveItemID = reader.ReadInt(); + ActiveItemID = reader.ReadInt(); + m_InRange = reader.ReadInt(); - if ( version < 1 ) - m_OutRange = m_InRange; + if (version < 1) + m_OutRange = m_InRange; - break; - } - } + break; + } + } - Timer.DelayCall( TimeSpan.Zero, Refresh ); - } - } -} + Timer.DelayCall(TimeSpan.Zero, Refresh); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/OilCloth.cs b/Scripts/Items/Misc/OilCloth.cs index efd81d945..73a25632d 100644 --- a/Scripts/Items/Misc/OilCloth.cs +++ b/Scripts/Items/Misc/OilCloth.cs @@ -1,144 +1,151 @@ using System; using Server.Mobiles; +using Server.Network; using Server.Targeting; namespace Server.Items { - public class OilCloth : Item, IScissorable, IDyable - { - public override int LabelNumber => 1041498; // oil cloth + public class OilCloth : Item, IScissorable, IDyable + { + [Constructible] + public OilCloth() : base(0x175D) + { + Hue = 2001; + } - public override double DefaultWeight => 1.0; + public OilCloth(Serial serial) : base(serial) + { + } - [Constructible] - public OilCloth() : base( 0x175D ) - { - Hue = 2001; - } + public override int LabelNumber => 1041498; // oil cloth - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + public override double DefaultWeight => 1.0; - Hue = sender.DyedHue; + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - return true; - } + Hue = sender.DyedHue; - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) - return false; + return true; + } - base.ScissorHelper( from, new Bandage(), 1 ); + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) + return false; - return true; - } + base.ScissorHelper(from, new Bandage(), 1); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.BeginTarget( -1, false, TargetFlags.None, OnTarget ); - from.SendLocalizedMessage( 1005424 ); // Select the weapon or armor you wish to use the cloth on. - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + return true; + } - public void OnTarget( Mobile from, object obj ) - { - // TODO: Need details on how oil cloths should get consumed here + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.BeginTarget(-1, false, TargetFlags.None, OnTarget); + from.SendLocalizedMessage(1005424); // Select the weapon or armor you wish to use the cloth on. + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( obj is Item item && item.RootParent != from ) - { - from.SendLocalizedMessage( 1005425 ); // You may only wipe down items you are holding or carrying. - } - else if ( obj is BaseWeapon weapon ) - { - if ( weapon.Poison == null || weapon.PoisonCharges <= 0 ) - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, 1005422 ); // Hmmmm... this does not need to be cleaned. - } - else - { - if ( weapon.PoisonCharges < 2 ) - weapon.PoisonCharges = 0; - else - weapon.PoisonCharges -= 2; + public void OnTarget(Mobile from, object obj) + { + // TODO: Need details on how oil cloths should get consumed here - if ( weapon.PoisonCharges > 0 ) - from.SendLocalizedMessage( 1005423 ); // You have removed some of the caustic substance, but not all. - else - from.SendLocalizedMessage( 1010497 ); // You have cleaned the item. - } - } - else if ( obj == from && obj is PlayerMobile pm ) - { - if ( pm.BodyMod == 183 || pm.BodyMod == 184 ) - { - pm.SavagePaintExpiration = TimeSpan.Zero; + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (obj is Item item && item.RootParent != from) + { + from.SendLocalizedMessage(1005425); // You may only wipe down items you are holding or carrying. + } + else if (obj is BaseWeapon weapon) + { + if (weapon.Poison == null || weapon.PoisonCharges <= 0) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1005422); // Hmmmm... this does not need to be cleaned. + } + else + { + if (weapon.PoisonCharges < 2) + weapon.PoisonCharges = 0; + else + weapon.PoisonCharges -= 2; - pm.BodyMod = 0; - pm.HueMod = -1; + if (weapon.PoisonCharges > 0) + from.SendLocalizedMessage(1005423); // You have removed some of the caustic substance, but not all. + else + from.SendLocalizedMessage(1010497); // You have cleaned the item. + } + } + else if (obj == from && obj is PlayerMobile pm) + { + if (pm.BodyMod == 183 || pm.BodyMod == 184) + { + pm.SavagePaintExpiration = TimeSpan.Zero; - from.SendLocalizedMessage( 1040006 ); // You wipe away all of your body paint. + pm.BodyMod = 0; + pm.HueMod = -1; - Consume(); - } - else - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, 1005422 ); // Hmmmm... this does not need to be cleaned. - } - } - #region Firebomb - else if ( obj is BaseBeverage beverage ) - { - if ( beverage.Content == BeverageType.Liquor ) - { - Firebomb bomb = new Firebomb( beverage.ItemID ); - bomb.Name = beverage.Name; + from.SendLocalizedMessage(1040006); // You wipe away all of your body paint. - beverage.ReplaceWith( bomb ); + Consume(); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1005422); // Hmmmm... this does not need to be cleaned. + } + } - from.SendLocalizedMessage( 1060580 ); // You prepare a firebomb. - Consume(); - } - } - else if ( obj is Firebomb ) - { - from.SendLocalizedMessage( 1060579 ); // That is already a firebomb! - } - #endregion - else - { - from.SendLocalizedMessage( 1005426 ); // The cloth will not work on that. - } - } + #region Firebomb - public OilCloth( Serial serial ) : base( serial ) - { - } + else if (obj is BaseBeverage beverage) + { + if (beverage.Content == BeverageType.Liquor) + { + Firebomb bomb = new Firebomb(beverage.ItemID); + bomb.Name = beverage.Name; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + beverage.ReplaceWith(bomb); - writer.Write( (int) 0 ); - } + from.SendLocalizedMessage(1060580); // You prepare a firebomb. + Consume(); + } + } + else if (obj is Firebomb) + { + from.SendLocalizedMessage(1060579); // That is already a firebomb! + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + #endregion - int version = reader.ReadInt(); - } - } -} + else + { + from.SendLocalizedMessage(1005426); // The cloth will not work on that. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Origami.cs b/Scripts/Items/Misc/Origami.cs index e44a891a5..3adb1b226 100644 --- a/Scripts/Items/Misc/Origami.cs +++ b/Scripts/Items/Misc/Origami.cs @@ -1,243 +1,245 @@ namespace Server.Items { - public class OrigamiPaper : Item - { - public override int LabelNumber => 1030288; // origami paper + public class OrigamiPaper : Item + { + [Constructible] + public OrigamiPaper() : base(0x2830) + { + } - [Constructible] - public OrigamiPaper() : base( 0x2830 ) - { - } + public OrigamiPaper(Serial serial) : base(serial) + { + } - public OrigamiPaper( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1030288; // origami paper - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - Delete(); + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + Delete(); - Item i = null; + Item i = null; - switch ( Utility.Random( (from.BAC >= 5) ? 6 : 5) ) - { - case 0: i = new OrigamiButterfly(); break; - case 1: i = new OrigamiSwan(); break; - case 2: i = new OrigamiFrog(); break; - case 3: i = new OrigamiShape(); break; - case 4: i = new OrigamiSongbird(); break; - case 5: i = new OrigamiFish(); break; - } + switch (Utility.Random(from.BAC >= 5 ? 6 : 5)) + { + case 0: + i = new OrigamiButterfly(); + break; + case 1: + i = new OrigamiSwan(); + break; + case 2: + i = new OrigamiFrog(); + break; + case 3: + i = new OrigamiShape(); + break; + case 4: + i = new OrigamiSongbird(); + break; + case 5: + i = new OrigamiFish(); + break; + } - if ( i != null ) - from.AddToBackpack( i ); + if (i != null) + from.AddToBackpack(i); - from.SendLocalizedMessage( 1070822 ); // You fold the paper into an interesting shape. - } - } + from.SendLocalizedMessage(1070822); // You fold the paper into an interesting shape. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class OrigamiButterfly : Item - { - public override int LabelNumber => 1030296; // a delicate origami butterfly + public class OrigamiButterfly : Item + { + [Constructible] + public OrigamiButterfly() : base(0x2838) + { + LootType = LootType.Blessed; + } - [Constructible] - public OrigamiButterfly() : base( 0x2838 ) - { - LootType = LootType.Blessed; - } + public OrigamiButterfly(Serial serial) : base(serial) + { + } - public OrigamiButterfly( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1030296; // a delicate origami butterfly - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); - } + writer.WriteEncodedInt(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class OrigamiSwan : Item - { - public override int LabelNumber => 1030297; // a delicate origami swan + public class OrigamiSwan : Item + { + [Constructible] + public OrigamiSwan() : base(0x2839) + { + LootType = LootType.Blessed; + } - [Constructible] - public OrigamiSwan() : base( 0x2839 ) - { - LootType = LootType.Blessed; + public OrigamiSwan(Serial serial) : base(serial) + { + } + public override int LabelNumber => 1030297; // a delicate origami swan - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public OrigamiSwan( Serial serial ) : base( serial ) - { - } + writer.WriteEncodedInt(0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.WriteEncodedInt( 0 ); - } + int version = reader.ReadEncodedInt(); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public class OrigamiFrog : Item + { + [Constructible] + public OrigamiFrog() : base(0x283A) + { + LootType = LootType.Blessed; + } - int version = reader.ReadEncodedInt(); - } - } + public OrigamiFrog(Serial serial) : base(serial) + { + } - public class OrigamiFrog : Item - { - public override int LabelNumber => 1030298; // a delicate origami frog + public override int LabelNumber => 1030298; // a delicate origami frog - [Constructible] - public OrigamiFrog() : base( 0x283A ) - { - LootType = LootType.Blessed; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.WriteEncodedInt(0); + } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public OrigamiFrog( Serial serial ) : base( serial ) - { - } + int version = reader.ReadEncodedInt(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public class OrigamiShape : Item + { + [Constructible] + public OrigamiShape() : base(0x283B) + { + LootType = LootType.Blessed; + } - writer.WriteEncodedInt( 0 ); - } + public OrigamiShape(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int LabelNumber => 1030299; // an intricate geometric origami shape - int version = reader.ReadEncodedInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public class OrigamiShape : Item - { - public override int LabelNumber => 1030299; // an intricate geometric origami shape + writer.WriteEncodedInt(0); + } - [Constructible] - public OrigamiShape() : base( 0x283B ) - { - LootType = LootType.Blessed; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadEncodedInt(); + } + } - } + public class OrigamiSongbird : Item + { + [Constructible] + public OrigamiSongbird() : base(0x283C) + { + LootType = LootType.Blessed; + } - public OrigamiShape( Serial serial ) : base( serial ) - { - } + public OrigamiSongbird(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int LabelNumber => 1030300; // a delicate origami songbird - writer.WriteEncodedInt( 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); + } - int version = reader.ReadEncodedInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public class OrigamiSongbird : Item - { - public override int LabelNumber => 1030300; // a delicate origami songbird + int version = reader.ReadEncodedInt(); + } + } - [Constructible] - public OrigamiSongbird() : base( 0x283C ) - { - LootType = LootType.Blessed; + public class OrigamiFish : Item + { + [Constructible] + public OrigamiFish() : base(0x283D) + { + LootType = LootType.Blessed; + } + public OrigamiFish(Serial serial) : base(serial) + { + } - } + public override int LabelNumber => 1030301; // a delicate origami fish - public OrigamiSongbird( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); + } - writer.WriteEncodedInt( 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class OrigamiFish : Item - { - public override int LabelNumber => 1030301; // a delicate origami fish - - [Constructible] - public OrigamiFish() : base( 0x283D ) - { - LootType = LootType.Blessed; - - - } - - public OrigamiFish( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Painted Caves/GrobusFur.cs b/Scripts/Items/Misc/Painted Caves/GrobusFur.cs index 3bfd620cc..2c85752f3 100644 --- a/Scripts/Items/Misc/Painted Caves/GrobusFur.cs +++ b/Scripts/Items/Misc/Painted Caves/GrobusFur.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class GrobusFur : Item - { - public override int LabelNumber => 1074676; // Grobu's Fur + public class GrobusFur : Item + { + [Constructible] + public GrobusFur() : base(0x11F4) + { + LootType = LootType.Blessed; + Hue = 0x455; + } - [Constructible] - public GrobusFur() : base( 0x11F4 ) - { - LootType = LootType.Blessed; - Hue = 0x455; - } + public GrobusFur(Serial serial) : base(serial) + { + } - public GrobusFur( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074676; // Grobu's Fur - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Painted Caves/PrimitiveFetish.cs b/Scripts/Items/Misc/Painted Caves/PrimitiveFetish.cs index 4c2bba812..2948ce202 100644 --- a/Scripts/Items/Misc/Painted Caves/PrimitiveFetish.cs +++ b/Scripts/Items/Misc/Painted Caves/PrimitiveFetish.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class PrimitiveFetish : Item - { - public override int LabelNumber => 1074675; // Primitive Fetish + public class PrimitiveFetish : Item + { + [Constructible] + public PrimitiveFetish() : base(0x23F) + { + LootType = LootType.Blessed; + Hue = 0x244; + } - [Constructible] - public PrimitiveFetish() : base( 0x23F ) - { - LootType = LootType.Blessed; - Hue = 0x244; - } + public PrimitiveFetish(Serial serial) : base(serial) + { + } - public PrimitiveFetish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074675; // Primitive Fetish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Palace of Paroxysmus/AcidProofRope.cs b/Scripts/Items/Misc/Palace of Paroxysmus/AcidProofRope.cs index 2661de0ad..c0785fca9 100644 --- a/Scripts/Items/Misc/Palace of Paroxysmus/AcidProofRope.cs +++ b/Scripts/Items/Misc/Palace of Paroxysmus/AcidProofRope.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class AcidProofRope : Item - { - public override int LabelNumber => 1074886; // Acid Proof Rope + public class AcidProofRope : Item + { + [Constructible] + public AcidProofRope() : base(0x20D) + { + Hue = 0x3D1; // TODO check + } - [Constructible] - public AcidProofRope() : base( 0x20D ) - { - Hue = 0x3D1; // TODO check - } + public AcidProofRope(Serial serial) : base(serial) + { + } - public AcidProofRope( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074886; // Acid Proof Rope - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusCorrodedStein.cs b/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusCorrodedStein.cs index 5e26652e4..94ebeb7a3 100644 --- a/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusCorrodedStein.cs +++ b/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusCorrodedStein.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class ParoxysmusCorrodedStein : Item - { - public override int LabelNumber => 1072083; // Paroxysmus' Corroded Stein + public class ParoxysmusCorrodedStein : Item + { + [Constructible] + public ParoxysmusCorrodedStein() : base(0x9D6) + { + } - [Constructible] - public ParoxysmusCorrodedStein() : base( 0x9D6 ) - { - } + public ParoxysmusCorrodedStein(Serial serial) : base(serial) + { + } - public ParoxysmusCorrodedStein( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072083; // Paroxysmus' Corroded Stein - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusDinner.cs b/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusDinner.cs index 5fb63ca72..407d0cfa7 100644 --- a/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusDinner.cs +++ b/Scripts/Items/Misc/Palace of Paroxysmus/ParoxysmusDinner.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class ParoxysmusDinner : Item - { - public override int LabelNumber => 1072086; // Paroxysmus' Dinner + public class ParoxysmusDinner : Item + { + [Constructible] + public ParoxysmusDinner() : base(0x1E95) + { + } - [Constructible] - public ParoxysmusDinner() : base( 0x1E95 ) - { - } + public ParoxysmusDinner(Serial serial) : base(serial) + { + } - public ParoxysmusDinner( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072086; // Paroxysmus' Dinner - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Palace of Paroxysmus/StringOfPartsOfParoxysmusVictims.cs b/Scripts/Items/Misc/Palace of Paroxysmus/StringOfPartsOfParoxysmusVictims.cs index 6685f3ce8..f38944bb0 100644 --- a/Scripts/Items/Misc/Palace of Paroxysmus/StringOfPartsOfParoxysmusVictims.cs +++ b/Scripts/Items/Misc/Palace of Paroxysmus/StringOfPartsOfParoxysmusVictims.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class StringOfPartsOfParoxysmusVictims : Item - { - public override int LabelNumber => 1072082; // String of Parts of Paroxysmus' Victims + public class StringOfPartsOfParoxysmusVictims : Item + { + [Constructible] + public StringOfPartsOfParoxysmusVictims() : base(0xFD2) + { + } - [Constructible] - public StringOfPartsOfParoxysmusVictims() : base( 0xFD2 ) - { - } + public StringOfPartsOfParoxysmusVictims(Serial serial) : base(serial) + { + } - public StringOfPartsOfParoxysmusVictims( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072082; // String of Parts of Paroxysmus' Victims - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Palace of Paroxysmus/SweatOfParoxysmus.cs b/Scripts/Items/Misc/Palace of Paroxysmus/SweatOfParoxysmus.cs index 1455f19c1..aca0bb8d0 100644 --- a/Scripts/Items/Misc/Palace of Paroxysmus/SweatOfParoxysmus.cs +++ b/Scripts/Items/Misc/Palace of Paroxysmus/SweatOfParoxysmus.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class SweatOfParoxysmus : Item - { - public override int LabelNumber => 1072081; // Sweat of Paroxysmus + public class SweatOfParoxysmus : Item + { + [Constructible] + public SweatOfParoxysmus() : base(0xF01) + { + } - [Constructible] - public SweatOfParoxysmus() : base( 0xF01 ) - { - } + public SweatOfParoxysmus(Serial serial) : base(serial) + { + } - public SweatOfParoxysmus( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072081; // Sweat of Paroxysmus - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/PlayerVendorDeed.cs b/Scripts/Items/Misc/PlayerVendorDeed.cs index 43ee6ab6d..034f28bf3 100644 --- a/Scripts/Items/Misc/PlayerVendorDeed.cs +++ b/Scripts/Items/Misc/PlayerVendorDeed.cs @@ -3,100 +3,104 @@ using Server.Multis; namespace Server.Items { - public class ContractOfEmployment : Item - { - public override int LabelNumber => 1041243; // a contract of employment + public class ContractOfEmployment : Item + { + [Constructible] + public ContractOfEmployment() : base(0x14F0) + { + Weight = 1.0; + //LootType = LootType.Blessed; + } - [Constructible] - public ContractOfEmployment() : base( 0x14F0 ) - { - Weight = 1.0; - //LootType = LootType.Blessed; - } + public ContractOfEmployment(Serial serial) : base(serial) + { + } - public ContractOfEmployment( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041243; // a contract of employment - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); //version - } + writer.Write(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.SendLocalizedMessage( 503248 ); // Your godly powers allow you to place this vendor whereever you wish. + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.SendLocalizedMessage(503248); // Your godly powers allow you to place this vendor whereever you wish. - Mobile v = new PlayerVendor( from, BaseHouse.FindHouseAt( from ) ); + Mobile v = new PlayerVendor(from, BaseHouse.FindHouseAt(from)); - v.Direction = from.Direction & Direction.Mask; - v.MoveToWorld( from.Location, from.Map ); + v.Direction = from.Direction & Direction.Mask; + v.MoveToWorld(from.Location, from.Map); - v.SayTo( from, 503246 ); // Ah! it feels good to be working again. + v.SayTo(from, 503246); // Ah! it feels good to be working again. - Delete(); - } - else - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + Delete(); + } + else + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house == null ) - { - from.SendLocalizedMessage( 503240 ); // Vendors can only be placed in houses. - } - else if ( !BaseHouse.NewVendorSystem && !house.IsFriend( from ) ) - { - from.SendLocalizedMessage( 503242 ); // You must ask the owner of this building to name you a friend of the household in order to place a vendor here. - } - else if ( BaseHouse.NewVendorSystem && !house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 1062423 ); // Only the house owner can directly place vendors. Please ask the house owner to offer you a vendor contract so that you may place a vendor in this house. - } - else if ( !house.Public || !house.CanPlaceNewVendor() ) - { - from.SendLocalizedMessage( 503241 ); // You cannot place this vendor or barkeep. Make sure the house is public and has sufficient storage available. - } - else - { - bool vendor, contract; - BaseHouse.IsThereVendor( from.Location, from.Map, out vendor, out contract ); + if (house == null) + { + from.SendLocalizedMessage(503240); // Vendors can only be placed in houses. + } + else if (!BaseHouse.NewVendorSystem && !house.IsFriend(from)) + { + from.SendLocalizedMessage( + 503242); // You must ask the owner of this building to name you a friend of the household in order to place a vendor here. + } + else if (BaseHouse.NewVendorSystem && !house.IsOwner(from)) + { + from.SendLocalizedMessage( + 1062423); // Only the house owner can directly place vendors. Please ask the house owner to offer you a vendor contract so that you may place a vendor in this house. + } + else if (!house.Public || !house.CanPlaceNewVendor()) + { + from.SendLocalizedMessage( + 503241); // You cannot place this vendor or barkeep. Make sure the house is public and has sufficient storage available. + } + else + { + bool vendor, contract; + BaseHouse.IsThereVendor(from.Location, from.Map, out vendor, out contract); - if ( vendor ) - { - from.SendLocalizedMessage( 1062677 ); // You cannot place a vendor or barkeep at this location. - } - else if ( contract ) - { - from.SendLocalizedMessage( 1062678 ); // You cannot place a vendor or barkeep on top of a rental contract! - } - else - { - Mobile v = new PlayerVendor( from, house ); + if (vendor) + { + from.SendLocalizedMessage(1062677); // You cannot place a vendor or barkeep at this location. + } + else if (contract) + { + from.SendLocalizedMessage( + 1062678); // You cannot place a vendor or barkeep on top of a rental contract! + } + else + { + Mobile v = new PlayerVendor(from, house); - v.Direction = from.Direction & Direction.Mask; - v.MoveToWorld( from.Location, from.Map ); + v.Direction = from.Direction & Direction.Mask; + v.MoveToWorld(from.Location, from.Map); - v.SayTo( from, 503246 ); // Ah! it feels good to be working again. + v.SayTo(from, 503246); // Ah! it feels good to be working again. - Delete(); - } - } - } - } - } -} + Delete(); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/PowerCrystal.cs b/Scripts/Items/Misc/PowerCrystal.cs index 3ca6f816e..7c8df6a9b 100644 --- a/Scripts/Items/Misc/PowerCrystal.cs +++ b/Scripts/Items/Misc/PowerCrystal.cs @@ -2,40 +2,40 @@ using Server.Network; namespace Server.Items { - public class PowerCrystal : Item - { - public override string DefaultName => "power crystal"; + public class PowerCrystal : Item + { + [Constructible] + public PowerCrystal() : base(0x1F1C) + { + Weight = 1.0; + } - [Constructible] - public PowerCrystal() : base( 0x1F1C ) - { - Weight = 1.0; - } + public PowerCrystal(Serial serial) : base(serial) + { + } - public PowerCrystal( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "power crystal"; - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 3 )) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - else - from.SendAsciiMessage( "This looks like part of a larger contraption." ); - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 3)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else + from.SendAsciiMessage("This looks like part of a larger contraption."); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/PowerGenerator.cs b/Scripts/Items/Misc/PowerGenerator.cs index 2728f609b..9e22f6c35 100644 --- a/Scripts/Items/Misc/PowerGenerator.cs +++ b/Scripts/Items/Misc/PowerGenerator.cs @@ -5,561 +5,545 @@ using Server.Network; namespace Server.Items { - public class PowerGenerator : BaseAddon - { - [Constructible] - public PowerGenerator() : this( Utility.RandomMinMax( 3, 6 ) ) - { - } - - [Constructible] - public PowerGenerator( int sideLength ) - { - AddGeneratorComponent( 0x4FA1, 0, 0, 0 ); - AddGeneratorComponent( 0x76, -1, 0, 0 ); - AddGeneratorComponent( 0x75, 0, -1, 0 ); - AddGeneratorComponent( 0x37F4, 0, 0, 13 ); - - AddComponent( new ControlPanel( sideLength ), 1, 0, -2 ); - } - - public override bool ShareHue => false; - - private void AddGeneratorComponent( int itemID, int x, int y, int z ) - { - AddonComponent component = new AddonComponent( itemID ); - component.Name = "a power generator"; - component.Hue = 0x451; - - AddComponent( component, x, y, z ); - } - - public PowerGenerator( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class ControlPanel : AddonComponent - { - private static readonly TimeSpan m_UseTimeout = TimeSpan.FromMinutes( 2.0 ); - - public struct Node - { - public int X { get; set; } - - public int Y { get; set; } - - public Node( int x, int y ) - { - X = x; - Y = y; - } - } - - private int m_SideLength; - - [CommandProperty( AccessLevel.GameMaster )] - public int SideLength - { - get => m_SideLength; - set - { - if ( value < 3 ) - value = 3; - else if ( value > 6 ) - value = 6; - - if ( m_SideLength != value ) - { - m_SideLength = value; - InitPath(); - } - } - } - - public Node[] Path { get; private set; } - - public override string DefaultName => "a control panel"; - - public ControlPanel( int sideLength ) : base( 0xBDC ) - { - Hue = 0x835; - - SideLength = sideLength; - } - - private enum PathDirection - { - Left, - Up, - Right, - Down - } - - public void InitPath() - { - // Depth-First Search algorithm - - int totalNodes = SideLength * SideLength; - - Node[] stack = new Node[totalNodes]; - Node current = stack[0] = new Node( 0, 0 ); - int stackSize = 1; - - bool[,] visited = new bool[SideLength, SideLength]; - visited[0, 0] = true; - - while ( true ) - { - PathDirection[] choices = new PathDirection[4]; - int count = 0; - - if ( current.X > 0 && !visited[current.X - 1, current.Y] ) - choices[count++] = PathDirection.Left; - - if ( current.Y > 0 && !visited[current.X, current.Y - 1] ) - choices[count++] = PathDirection.Up; - - if ( current.X < SideLength - 1 && !visited[current.X + 1, current.Y] ) - choices[count++] = PathDirection.Right; - - if ( current.Y < SideLength - 1 && !visited[current.X, current.Y + 1] ) - choices[count++] = PathDirection.Down; - - if ( count > 0 ) - { - PathDirection dir = choices[Utility.Random( count )]; - - switch ( dir ) - { - case PathDirection.Left: - current = new Node( current.X - 1, current.Y ); - break; - case PathDirection.Up: - current = new Node( current.X, current.Y - 1 ); - break; - case PathDirection.Right: - current = new Node( current.X + 1, current.Y ); - break; - default: - current = new Node( current.X, current.Y + 1 ); - break; - } - - stack[stackSize++] = current; - - if ( current.X == SideLength - 1 && current.Y == SideLength - 1 ) - break; - - visited[current.X, current.Y] = true; - } - else - { - current = stack[--stackSize - 1]; - } - } - - Path = new Node[stackSize]; - - for ( int i = 0; i < stackSize; i++ ) - { - Path[i] = stack[i]; - } - - if ( m_User != null ) - { - m_User.CloseGump( typeof( GameGump ) ); - m_User = null; - } - } - - private Mobile m_User; - private DateTime m_LastUse; - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( this, 3 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - return; - } - - if ( m_User != null ) - { - if ( m_User == from ) - return; - - if ( m_User.Deleted || m_User.Map != Map || !m_User.InRange( this, 3 ) - || m_User.NetState == null || DateTime.UtcNow - m_LastUse >= m_UseTimeout ) - { - m_User.CloseGump( typeof( GameGump ) ); - } - else - { - from.SendMessage( "Someone is currently using the control panel." ); - return; - } - } - - m_User = from; - m_LastUse = DateTime.UtcNow; - - from.SendGump( new GameGump( this, from, 0, false ) ); - } - - private class GameGump : Gump - { - private enum NodeHue - { - Gray, - Blue, - Red - } - - private ControlPanel m_Panel; - private Mobile m_From; - private int m_Step; - - public GameGump( ControlPanel panel, Mobile from, int step, bool hint ) : base( 5, 30 ) - { - m_Panel = panel; - m_From = from; - m_Step = step; - - int sideLength = panel.SideLength; - - AddBackground( 50, 0, 530, 410, 0xA28 ); - - AddImage( 0, 0, 0x28C8 ); - AddImage( 547, 0, 0x28C9 ); - - AddBackground( 95, 20, 442, 90, 0xA28 ); - - AddHtml( 229, 35, 300, 45, "GENERATOR CONTROL PANEL", false, false ); - - AddHtml( 223, 60, 300, 70, "Use the Directional Controls to", false, false ); - AddHtml( 253, 75, 300, 85, "Close the Grid Circuit", false, false ); - - AddImage( 140, 40, 0x28D3 ); - AddImage( 420, 40, 0x28D3 ); - - AddBackground( 365, 120, 178, 210, 0x1400 ); - - AddImage( 365, 115, 0x28D4 ); - AddImage( 365, 288, 0x28D4 ); - - AddImage( 414, 189, 0x589 ); - AddImage( 435, 210, 0xA52 ); - - AddButton( 408, 222, 0x29EA, 0x29EC, 1, GumpButtonType.Reply, 0 ); // Left - AddButton( 448, 185, 0x29CC, 0x29CE, 2, GumpButtonType.Reply, 0 ); // Up - AddButton( 473, 222, 0x29D6, 0x29D8, 3, GumpButtonType.Reply, 0 ); // Right - AddButton( 448, 243, 0x29E0, 0x29E2, 4, GumpButtonType.Reply, 0 ); // Down - - AddBackground( 90, 115, 30 + 40 * sideLength, 30 + 40 * sideLength, 0xA28 ); - AddBackground( 100, 125, 10 + 40 * sideLength, 10 + 40 * sideLength, 0x1400 ); - - for ( int i = 0; i < sideLength; i++ ) - { - for ( int j = 0; j < sideLength - 1; j++ ) - { - AddImage( 120 + 40 * i, 162 + 40 * j, 0x13F9 ); - } - } - - for ( int i = 0; i < sideLength - 1; i++ ) - { - for ( int j = 0; j < sideLength; j++ ) - { - AddImage( 138 + 40 * i, 147 + 40 * j, 0x13FD ); - } - } - - Node[] path = panel.Path; - - NodeHue[,] hues = new NodeHue[sideLength, sideLength]; - - for ( int i = 0; i <= step; i++ ) - { - Node n = path[i]; - hues[n.X, n.Y] = NodeHue.Blue; - } - - Node lastNode = path[path.Length - 1]; - hues[lastNode.X, lastNode.Y] = NodeHue.Red; - - for ( int i = 0; i < sideLength; i++ ) - { - for ( int j = 0; j < sideLength; j++ ) - { - AddNode( 110 + 40 * i, 135 + 40 * j, hues[i, j] ); - } - } - - Node curNode = path[step]; - AddImage( 118 + 40 * curNode.X, 143 + 40 * curNode.Y, 0x13A8 ); - - if ( hint ) - { - Node nextNode = path[step + 1]; - AddImage( 119 + 40 * nextNode.X, 143 + 40 * nextNode.Y, 0x939 ); - } - - if ( from.Skills.Lockpicking.Value >= 65.0 ) - { - AddButton( 365, 350, 0xFA6, 0xFA7, 5, GumpButtonType.Reply, 0 ); - AddHtml( 405, 345, 140, 40, "Attempt to Decipher the Circuit Path", false, false ); - } - } - - private void AddNode( int x, int y, NodeHue hue ) - { - int id; - switch ( hue ) - { - case NodeHue.Gray: id = 0x25F8; break; - case NodeHue.Blue: id = 0x868; break; - default: id = 0x9A8; break; - } - - AddImage( x, y, id ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Panel.Deleted || info.ButtonID == 0 || !m_From.CheckAlive() ) - { - m_Panel.m_User = null; - return; - } - - if ( m_From.Map != m_Panel.Map || !m_From.InRange( m_Panel, 3 ) ) - { - m_From.SendLocalizedMessage( 500446 ); // That is too far away. - m_Panel.m_User = null; - return; - } - - Node nextNode = m_Panel.Path[m_Step + 1]; - - if ( info.ButtonID == 5 ) // Attempt to Decipher - { - double lockpicking = m_From.Skills.Lockpicking.Value; - - if ( lockpicking < 65.0 ) - return; - - m_From.PlaySound( 0x241 ); - - if ( 40.0 + Utility.RandomDouble() * 80.0 < lockpicking ) - { - m_From.SendGump( new GameGump( m_Panel, m_From, m_Step, true ) ); - m_Panel.m_LastUse = DateTime.UtcNow; - } - else - { - m_Panel.DoDamage( m_From ); - m_Panel.m_User = null; - } - } - else - { - Node curNode = m_Panel.Path[m_Step]; - - int newX, newY; - switch ( info.ButtonID ) - { - case 1: // Left - newX = curNode.X - 1; - newY = curNode.Y; - break; - case 2: // Up - newX = curNode.X; - newY = curNode.Y - 1; - break; - case 3: // Right - newX = curNode.X + 1; - newY = curNode.Y; - break; - case 4: // Down - newX = curNode.X; - newY = curNode.Y + 1; - break; - - default: - return; - } - - if ( nextNode.X == newX && nextNode.Y == newY ) - { - if ( m_Step + 1 == m_Panel.Path.Length - 1 ) - { - m_Panel.Solve( m_From ); - m_Panel.m_User = null; - } - else - { - m_From.PlaySound( 0x1F4 ); - m_From.SendGump( new GameGump( m_Panel, m_From, m_Step + 1, false ) ); - m_Panel.m_LastUse = DateTime.UtcNow; - } - } - else - { - m_Panel.DoDamage( m_From ); - m_Panel.m_User = null; - } - } - } - } - - private Hashtable m_DamageTable = new Hashtable(); - - public void DoDamage( Mobile to ) - { - to.Send( new UnicodeMessage( Serial, ItemID, MessageType.Regular, 0x3B2, 3, "", "", "The generator shoots an arc of electricity at you!" ) ); - to.BoltEffect( 0 ); - to.LocalOverheadMessage( MessageType.Regular, 0xC9, true, "* Your body convulses from electric shock *" ); - to.NonlocalOverheadMessage( MessageType.Regular, 0xC9, true, $"* {to.Name} spasms from electric shock *"); - - AOS.Damage( to, to, 60, 0, 0, 0, 0, 100 ); - - if ( !to.Alive ) - return; - - if ( m_DamageTable[to] == null ) - { - to.Frozen = true; - - DamageTimer timer = new DamageTimer( this, to ); - m_DamageTable[to] = timer; - - timer.Start(); - } - } - - private class DamageTimer : Timer - { - private ControlPanel m_Panel; - private Mobile m_To; - private int m_Step; - - public DamageTimer( ControlPanel panel, Mobile to ) : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_Panel = panel; - m_To = to; - m_Step = 0; - - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - if ( m_Panel.Deleted || m_To.Deleted || !m_To.Alive ) - { - End(); - return; - } - - m_To.PlaySound( 0x28 ); - - m_To.LocalOverheadMessage( MessageType.Regular, 0xC9, true, "* Your body convulses from electric shock *" ); - m_To.NonlocalOverheadMessage( MessageType.Regular, 0xC9, true, - $"* {m_To.Name} spasms from electric shock *"); - - AOS.Damage( m_To, m_To, 20, 0, 0, 0, 0, 100 ); - - if ( ++m_Step >= 3 || !m_To.Alive ) - { - End(); - } - } - - private void End() - { - m_Panel.m_DamageTable.Remove( m_To ); - m_To.Frozen = false; - - Stop(); - } - } - - public void Solve( Mobile from ) - { - Effects.PlaySound( Location, Map, 0x211 ); - Effects.PlaySound( Location, Map, 0x1F3 ); - - Effects.SendLocationEffect( Location, Map, 0x36B0, 4, 4 ); - Effects.SendLocationEffect( new Point3D( X - 1, Y - 1, Z + 2 ), Map, 0x36B0, 4, 4 ); - Effects.SendLocationEffect( new Point3D( X - 2, Y - 1, Z + 2 ), Map, 0x36B0, 4, 4 ); - - from.SendMessage( "You scrounge some gems from the wreckage." ); - - for ( int i = 0; i < SideLength; i++ ) - { - from.AddToBackpack( new ArcaneGem() ); - } - - from.AddToBackpack( new Diamond( SideLength ) ); - - Item ore = new ShadowIronOre( 9 ); - ore.MoveToWorld( new Point3D( X - 1, Y, Z + 2 ), Map ); - - ore = new ShadowIronOre( 14 ); - ore.MoveToWorld( new Point3D( X - 2, Y - 1, Z + 2 ), Map ); + public class PowerGenerator : BaseAddon + { + [Constructible] + public PowerGenerator() : this(Utility.RandomMinMax(3, 6)) + { + } - Delete(); - } + [Constructible] + public PowerGenerator(int sideLength) + { + AddGeneratorComponent(0x4FA1, 0, 0, 0); + AddGeneratorComponent(0x76, -1, 0, 0); + AddGeneratorComponent(0x75, 0, -1, 0); + AddGeneratorComponent(0x37F4, 0, 0, 13); - public ControlPanel( Serial serial ) : base( serial ) - { - } + AddComponent(new ControlPanel(sideLength), 1, 0, -2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public PowerGenerator(Serial serial) : base(serial) + { + } - writer.WriteEncodedInt( (int) 0 ); // version + public override bool ShareHue => false; - writer.WriteEncodedInt( (int) m_SideLength ); + private void AddGeneratorComponent(int itemID, int x, int y, int z) + { + AddonComponent component = new AddonComponent(itemID); + component.Name = "a power generator"; + component.Hue = 0x451; - writer.WriteEncodedInt( (int) Path.Length ); - for ( int i = 0; i < Path.Length; i++ ) - { - Node cur = Path[i]; + AddComponent(component, x, y, z); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class ControlPanel : AddonComponent + { + private static readonly TimeSpan m_UseTimeout = TimeSpan.FromMinutes(2.0); + + private Hashtable m_DamageTable = new Hashtable(); + private DateTime m_LastUse; + + private int m_SideLength; + + private Mobile m_User; + + public ControlPanel(int sideLength) : base(0xBDC) + { + Hue = 0x835; + + SideLength = sideLength; + } + + public ControlPanel(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SideLength + { + get => m_SideLength; + set + { + if (value < 3) + value = 3; + else if (value > 6) + value = 6; + + if (m_SideLength != value) + { + m_SideLength = value; + InitPath(); + } + } + } + + public Node[] Path{ get; private set; } + + public override string DefaultName => "a control panel"; + + public void InitPath() + { + // Depth-First Search algorithm + + int totalNodes = SideLength * SideLength; + + Node[] stack = new Node[totalNodes]; + Node current = stack[0] = new Node(0, 0); + int stackSize = 1; + + bool[,] visited = new bool[SideLength, SideLength]; + visited[0, 0] = true; + + while (true) + { + PathDirection[] choices = new PathDirection[4]; + int count = 0; + + if (current.X > 0 && !visited[current.X - 1, current.Y]) + choices[count++] = PathDirection.Left; + + if (current.Y > 0 && !visited[current.X, current.Y - 1]) + choices[count++] = PathDirection.Up; + + if (current.X < SideLength - 1 && !visited[current.X + 1, current.Y]) + choices[count++] = PathDirection.Right; + + if (current.Y < SideLength - 1 && !visited[current.X, current.Y + 1]) + choices[count++] = PathDirection.Down; + + if (count > 0) + { + PathDirection dir = choices[Utility.Random(count)]; + + switch (dir) + { + case PathDirection.Left: + current = new Node(current.X - 1, current.Y); + break; + case PathDirection.Up: + current = new Node(current.X, current.Y - 1); + break; + case PathDirection.Right: + current = new Node(current.X + 1, current.Y); + break; + default: + current = new Node(current.X, current.Y + 1); + break; + } + + stack[stackSize++] = current; + + if (current.X == SideLength - 1 && current.Y == SideLength - 1) + break; + + visited[current.X, current.Y] = true; + } + else + { + current = stack[--stackSize - 1]; + } + } + + Path = new Node[stackSize]; + + for (int i = 0; i < stackSize; i++) Path[i] = stack[i]; + + if (m_User != null) + { + m_User.CloseGump(typeof(GameGump)); + m_User = null; + } + } + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(this, 3)) + { + from.SendLocalizedMessage(500446); // That is too far away. + return; + } + + if (m_User != null) + { + if (m_User == from) + return; - writer.WriteEncodedInt( cur.X ); - writer.WriteEncodedInt( cur.Y ); - } - } + if (m_User.Deleted || m_User.Map != Map || !m_User.InRange(this, 3) + || m_User.NetState == null || DateTime.UtcNow - m_LastUse >= m_UseTimeout) + { + m_User.CloseGump(typeof(GameGump)); + } + else + { + from.SendMessage("Someone is currently using the control panel."); + return; + } + } + + m_User = from; + m_LastUse = DateTime.UtcNow; + + from.SendGump(new GameGump(this, from, 0, false)); + } + + public void DoDamage(Mobile to) + { + to.Send(new UnicodeMessage(Serial, ItemID, MessageType.Regular, 0x3B2, 3, "", "", + "The generator shoots an arc of electricity at you!")); + to.BoltEffect(0); + to.LocalOverheadMessage(MessageType.Regular, 0xC9, true, "* Your body convulses from electric shock *"); + to.NonlocalOverheadMessage(MessageType.Regular, 0xC9, true, $"* {to.Name} spasms from electric shock *"); + + AOS.Damage(to, to, 60, 0, 0, 0, 0, 100); + + if (!to.Alive) + return; + + if (m_DamageTable[to] == null) + { + to.Frozen = true; + + DamageTimer timer = new DamageTimer(this, to); + m_DamageTable[to] = timer; + + timer.Start(); + } + } + + public void Solve(Mobile from) + { + Effects.PlaySound(Location, Map, 0x211); + Effects.PlaySound(Location, Map, 0x1F3); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Effects.SendLocationEffect(Location, Map, 0x36B0, 4, 4); + Effects.SendLocationEffect(new Point3D(X - 1, Y - 1, Z + 2), Map, 0x36B0, 4, 4); + Effects.SendLocationEffect(new Point3D(X - 2, Y - 1, Z + 2), Map, 0x36B0, 4, 4); - int version = reader.ReadEncodedInt(); + from.SendMessage("You scrounge some gems from the wreckage."); - m_SideLength = reader.ReadEncodedInt(); + for (int i = 0; i < SideLength; i++) from.AddToBackpack(new ArcaneGem()); - Path = new Node[reader.ReadEncodedInt()]; - for ( int i = 0; i < Path.Length; i++ ) - { - Path[i] = new Node( reader.ReadEncodedInt(), reader.ReadEncodedInt() ); - } - } - } -} + from.AddToBackpack(new Diamond(SideLength)); + + Item ore = new ShadowIronOre(9); + ore.MoveToWorld(new Point3D(X - 1, Y, Z + 2), Map); + + ore = new ShadowIronOre(14); + ore.MoveToWorld(new Point3D(X - 2, Y - 1, Z + 2), Map); + + Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(m_SideLength); + + writer.WriteEncodedInt(Path.Length); + for (int i = 0; i < Path.Length; i++) + { + Node cur = Path[i]; + + writer.WriteEncodedInt(cur.X); + writer.WriteEncodedInt(cur.Y); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_SideLength = reader.ReadEncodedInt(); + + Path = new Node[reader.ReadEncodedInt()]; + for (int i = 0; i < Path.Length; i++) Path[i] = new Node(reader.ReadEncodedInt(), reader.ReadEncodedInt()); + } + + public struct Node + { + public int X{ get; set; } + + public int Y{ get; set; } + + public Node(int x, int y) + { + X = x; + Y = y; + } + } + + private enum PathDirection + { + Left, + Up, + Right, + Down + } + + private class GameGump : Gump + { + private Mobile m_From; + + private ControlPanel m_Panel; + private int m_Step; + + public GameGump(ControlPanel panel, Mobile from, int step, bool hint) : base(5, 30) + { + m_Panel = panel; + m_From = from; + m_Step = step; + + int sideLength = panel.SideLength; + + AddBackground(50, 0, 530, 410, 0xA28); + + AddImage(0, 0, 0x28C8); + AddImage(547, 0, 0x28C9); + + AddBackground(95, 20, 442, 90, 0xA28); + + AddHtml(229, 35, 300, 45, "GENERATOR CONTROL PANEL", false, false); + + AddHtml(223, 60, 300, 70, "Use the Directional Controls to", false, false); + AddHtml(253, 75, 300, 85, "Close the Grid Circuit", false, false); + + AddImage(140, 40, 0x28D3); + AddImage(420, 40, 0x28D3); + + AddBackground(365, 120, 178, 210, 0x1400); + + AddImage(365, 115, 0x28D4); + AddImage(365, 288, 0x28D4); + + AddImage(414, 189, 0x589); + AddImage(435, 210, 0xA52); + + AddButton(408, 222, 0x29EA, 0x29EC, 1, GumpButtonType.Reply, 0); // Left + AddButton(448, 185, 0x29CC, 0x29CE, 2, GumpButtonType.Reply, 0); // Up + AddButton(473, 222, 0x29D6, 0x29D8, 3, GumpButtonType.Reply, 0); // Right + AddButton(448, 243, 0x29E0, 0x29E2, 4, GumpButtonType.Reply, 0); // Down + + AddBackground(90, 115, 30 + 40 * sideLength, 30 + 40 * sideLength, 0xA28); + AddBackground(100, 125, 10 + 40 * sideLength, 10 + 40 * sideLength, 0x1400); + + for (int i = 0; i < sideLength; i++) + for (int j = 0; j < sideLength - 1; j++) + AddImage(120 + 40 * i, 162 + 40 * j, 0x13F9); + + for (int i = 0; i < sideLength - 1; i++) + for (int j = 0; j < sideLength; j++) + AddImage(138 + 40 * i, 147 + 40 * j, 0x13FD); + + Node[] path = panel.Path; + + NodeHue[,] hues = new NodeHue[sideLength, sideLength]; + + for (int i = 0; i <= step; i++) + { + Node n = path[i]; + hues[n.X, n.Y] = NodeHue.Blue; + } + + Node lastNode = path[path.Length - 1]; + hues[lastNode.X, lastNode.Y] = NodeHue.Red; + + for (int i = 0; i < sideLength; i++) + for (int j = 0; j < sideLength; j++) + AddNode(110 + 40 * i, 135 + 40 * j, hues[i, j]); + + Node curNode = path[step]; + AddImage(118 + 40 * curNode.X, 143 + 40 * curNode.Y, 0x13A8); + + if (hint) + { + Node nextNode = path[step + 1]; + AddImage(119 + 40 * nextNode.X, 143 + 40 * nextNode.Y, 0x939); + } + + if (from.Skills.Lockpicking.Value >= 65.0) + { + AddButton(365, 350, 0xFA6, 0xFA7, 5, GumpButtonType.Reply, 0); + AddHtml(405, 345, 140, 40, "Attempt to Decipher the Circuit Path", false, false); + } + } + + private void AddNode(int x, int y, NodeHue hue) + { + int id; + switch (hue) + { + case NodeHue.Gray: + id = 0x25F8; + break; + case NodeHue.Blue: + id = 0x868; + break; + default: + id = 0x9A8; + break; + } + + AddImage(x, y, id); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Panel.Deleted || info.ButtonID == 0 || !m_From.CheckAlive()) + { + m_Panel.m_User = null; + return; + } + + if (m_From.Map != m_Panel.Map || !m_From.InRange(m_Panel, 3)) + { + m_From.SendLocalizedMessage(500446); // That is too far away. + m_Panel.m_User = null; + return; + } + + Node nextNode = m_Panel.Path[m_Step + 1]; + + if (info.ButtonID == 5) // Attempt to Decipher + { + double lockpicking = m_From.Skills.Lockpicking.Value; + + if (lockpicking < 65.0) + return; + + m_From.PlaySound(0x241); + + if (40.0 + Utility.RandomDouble() * 80.0 < lockpicking) + { + m_From.SendGump(new GameGump(m_Panel, m_From, m_Step, true)); + m_Panel.m_LastUse = DateTime.UtcNow; + } + else + { + m_Panel.DoDamage(m_From); + m_Panel.m_User = null; + } + } + else + { + Node curNode = m_Panel.Path[m_Step]; + + int newX, newY; + switch (info.ButtonID) + { + case 1: // Left + newX = curNode.X - 1; + newY = curNode.Y; + break; + case 2: // Up + newX = curNode.X; + newY = curNode.Y - 1; + break; + case 3: // Right + newX = curNode.X + 1; + newY = curNode.Y; + break; + case 4: // Down + newX = curNode.X; + newY = curNode.Y + 1; + break; + + default: + return; + } + + if (nextNode.X == newX && nextNode.Y == newY) + { + if (m_Step + 1 == m_Panel.Path.Length - 1) + { + m_Panel.Solve(m_From); + m_Panel.m_User = null; + } + else + { + m_From.PlaySound(0x1F4); + m_From.SendGump(new GameGump(m_Panel, m_From, m_Step + 1, false)); + m_Panel.m_LastUse = DateTime.UtcNow; + } + } + else + { + m_Panel.DoDamage(m_From); + m_Panel.m_User = null; + } + } + } + + private enum NodeHue + { + Gray, + Blue, + Red + } + } + + private class DamageTimer : Timer + { + private ControlPanel m_Panel; + private int m_Step; + private Mobile m_To; + + public DamageTimer(ControlPanel panel, Mobile to) : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + m_Panel = panel; + m_To = to; + m_Step = 0; + + Priority = TimerPriority.TwoFiftyMS; + } + + protected override void OnTick() + { + if (m_Panel.Deleted || m_To.Deleted || !m_To.Alive) + { + End(); + return; + } + + m_To.PlaySound(0x28); + + m_To.LocalOverheadMessage(MessageType.Regular, 0xC9, true, "* Your body convulses from electric shock *"); + m_To.NonlocalOverheadMessage(MessageType.Regular, 0xC9, true, + $"* {m_To.Name} spasms from electric shock *"); + + AOS.Damage(m_To, m_To, 20, 0, 0, 0, 0, 100); + + if (++m_Step >= 3 || !m_To.Alive) End(); + } + + private void End() + { + m_Panel.m_DamageTable.Remove(m_To); + m_To.Frozen = false; + + Stop(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Prism of Light/CrystallineFragments.cs b/Scripts/Items/Misc/Prism of Light/CrystallineFragments.cs index 6ba8b56c1..0dfdf2509 100644 --- a/Scripts/Items/Misc/Prism of Light/CrystallineFragments.cs +++ b/Scripts/Items/Misc/Prism of Light/CrystallineFragments.cs @@ -1,33 +1,32 @@ namespace Server.Items { - public class CrystallineFragments : Item - { - public override int LabelNumber => 1073160; // Crystalline Fragments + public class CrystallineFragments : Item + { + [Constructible] + public CrystallineFragments() : base(0x223B) + { + LootType = LootType.Blessed; + Hue = 0x47E; + } - [Constructible] - public CrystallineFragments() : base( 0x223B ) - { - LootType = LootType.Blessed; - Hue = 0x47E; - } + public CrystallineFragments(Serial serial) : base(serial) + { + } - public CrystallineFragments( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073160; // Crystalline Fragments - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Prism of Light/IcyHeart.cs b/Scripts/Items/Misc/Prism of Light/IcyHeart.cs index 5a7948915..cf784bf88 100644 --- a/Scripts/Items/Misc/Prism of Light/IcyHeart.cs +++ b/Scripts/Items/Misc/Prism of Light/IcyHeart.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class IcyHeart : Item - { - public override int LabelNumber => 1073162; // Icy Heart + public class IcyHeart : Item + { + [Constructible] + public IcyHeart() : base(0x24B) + { + } - [Constructible] - public IcyHeart() : base( 0x24B ) - { - } + public IcyHeart(Serial serial) : base(serial) + { + } - public IcyHeart( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073162; // Icy Heart - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Prism of Light/LuckyDagger.cs b/Scripts/Items/Misc/Prism of Light/LuckyDagger.cs index 7c1f3c03b..c9ba7c3ce 100644 --- a/Scripts/Items/Misc/Prism of Light/LuckyDagger.cs +++ b/Scripts/Items/Misc/Prism of Light/LuckyDagger.cs @@ -1,30 +1,29 @@ namespace Server.Items { - public class LuckyDagger : Item - { - [Constructible] - public LuckyDagger() : base( 0xF52 ) - { - Hue = 0x8A5; - } + public class LuckyDagger : Item + { + [Constructible] + public LuckyDagger() : base(0xF52) + { + Hue = 0x8A5; + } - public LuckyDagger( Serial serial ) : base( serial ) - { - } + public LuckyDagger(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Prism of Light/ProtectorsEssence.cs b/Scripts/Items/Misc/Prism of Light/ProtectorsEssence.cs index 44ee8e5d7..3ad0952ac 100644 --- a/Scripts/Items/Misc/Prism of Light/ProtectorsEssence.cs +++ b/Scripts/Items/Misc/Prism of Light/ProtectorsEssence.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class ProtectorsEssence : Item - { - public override int LabelNumber => 1073159; // Protector's Essence + public class ProtectorsEssence : Item + { + [Constructible] + public ProtectorsEssence() : base(0x23F) + { + } - [Constructible] - public ProtectorsEssence() : base( 0x23F ) - { - } + public ProtectorsEssence(Serial serial) : base(serial) + { + } - public ProtectorsEssence( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073159; // Protector's Essence - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Prism of Light/ShimmeringCrystal.cs b/Scripts/Items/Misc/Prism of Light/ShimmeringCrystal.cs index 344bd030a..07045003d 100644 --- a/Scripts/Items/Misc/Prism of Light/ShimmeringCrystal.cs +++ b/Scripts/Items/Misc/Prism of Light/ShimmeringCrystal.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ShimmeringCrystals : Item - { - public override int LabelNumber => 1075095; // Shimmering Crystals - public override bool ForceShowProperties => true; + public class ShimmeringCrystals : Item + { + private static readonly int[] m_ItemIDs = + { + 0x2206, 0x2207, 0x2208, 0x2209, 0x220A, 0x220B, 0x220C, 0x220D, 0x220E, + 0x2210, 0x2211, 0x2212, 0x2213, 0x2214, 0x2215, 0x2216, 0x2217, 0x2218, + 0x221A, 0x221B, 0x221C, 0x221D, 0x221E, 0x221F, 0x2220, 0x2221, 0x2222, + 0x2224, 0x2225, 0x2226, 0x2227, 0x2228, 0x2229, 0x222A, 0x222B, 0x222C + }; - private static readonly int[] m_ItemIDs = { - 0x2206, 0x2207, 0x2208, 0x2209, 0x220A, 0x220B, 0x220C, 0x220D, 0x220E, - 0x2210, 0x2211, 0x2212, 0x2213, 0x2214, 0x2215, 0x2216, 0x2217, 0x2218, - 0x221A, 0x221B, 0x221C, 0x221D, 0x221E, 0x221F, 0x2220, 0x2221, 0x2222, - 0x2224, 0x2225, 0x2226, 0x2227, 0x2228, 0x2229, 0x222A, 0x222B, 0x222C - }; + [Constructible] + public ShimmeringCrystals() : base(Utility.RandomList(m_ItemIDs)) + { + } - [Constructible] - public ShimmeringCrystals() : base( Utility.RandomList( m_ItemIDs ) ) - { - } + public ShimmeringCrystals(Serial serial) : base(serial) + { + } - public ShimmeringCrystals( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075095; // Shimmering Crystals + public override bool ForceShowProperties => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/PublicMoongate.cs b/Scripts/Items/Misc/PublicMoongate.cs index 4d13a381e..76d1f40b5 100644 --- a/Scripts/Items/Misc/PublicMoongate.cs +++ b/Scripts/Items/Misc/PublicMoongate.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using Server.Commands; +using Server.Factions; using Server.Gumps; using Server.Mobiles; using Server.Network; @@ -8,417 +9,413 @@ using Server.Spells; namespace Server.Items { - public class PublicMoongate : Item - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - [Constructible] - public PublicMoongate() : base( 0xF6C ) - { - Movable = false; - Light = LightType.Circle300; - } - - public PublicMoongate( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.Player ) - return; - - if ( from.InRange( GetWorldLocation(), 1 ) ) - UseGate( from ); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - - public override bool OnMoveOver( Mobile m ) - { - // Changed so criminals are not blocked by it. - if ( m.Player ) - UseGate( m ); - - return true; - } - - public override bool HandlesOnMovement => true; - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m is PlayerMobile ) - { - if ( !Utility.InRange( m.Location, Location, 1 ) && Utility.InRange( oldLocation, Location, 1 ) ) - m.CloseGump( typeof( MoongateGump ) ); - } - } - - public bool UseGate( Mobile m ) - { - if ( m.Criminal ) - { - m.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - return false; - } - - if ( SpellHelper.CheckCombat( m ) ) - { - m.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - return false; - } - if ( m.Spell != null ) - { - m.SendLocalizedMessage( 1049616 ); // You are too busy to do that at the moment. - return false; - } - m.CloseGump( typeof( MoongateGump ) ); - m.SendGump( new MoongateGump( m, this ) ); - - if ( !m.Hidden || m.AccessLevel == AccessLevel.Player ) - Effects.PlaySound( m.Location, m.Map, 0x20E ); - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public static void Initialize() - { - CommandSystem.Register( "MoonGen", AccessLevel.Administrator, MoonGen_OnCommand ); - } - - [Usage( "MoonGen" )] - [Description( "Generates public moongates. Removes all old moongates." )] - public static void MoonGen_OnCommand( CommandEventArgs e ) - { - DeleteAll(); - - int count = 0; - - count += MoonGen( PMList.Trammel ); - count += MoonGen( PMList.Felucca ); - count += MoonGen( PMList.Ilshenar ); - count += MoonGen( PMList.Malas ); - count += MoonGen( PMList.Tokuno ); - - World.Broadcast( 0x35, true, "{0} moongates generated.", count ); - } - - private static void DeleteAll() - { - List list = new List(); - - foreach ( Item item in World.Items.Values ) - { - if ( item is PublicMoongate ) - list.Add( item ); - } - - foreach ( Item item in list ) - item.Delete(); - - if ( list.Count > 0 ) - World.Broadcast( 0x35, true, "{0} moongates removed.", list.Count ); - } - - private static int MoonGen( PMList list ) - { - foreach ( PMEntry entry in list.Entries ) - { - Item item = new PublicMoongate(); - - item.MoveToWorld( entry.Location, list.Map ); - - if ( entry.Number == 1060642 ) // Umbra - item.Hue = 0x497; - } - - return list.Entries.Length; - } - } - - public class PMEntry - { - public Point3D Location { get; } - - public int Number { get; } - - public PMEntry( Point3D loc, int number ) - { - Location = loc; - Number = number; - } - } - - public class PMList - { - public int Number { get; } - - public int SelNumber { get; } - - public Map Map { get; } - - public PMEntry[] Entries { get; } - - public PMList( int number, int selNumber, Map map, PMEntry[] entries ) - { - Number = number; - SelNumber = selNumber; - Map = map; - Entries = entries; - } - - public static readonly PMList Trammel = - new PMList( 1012000, 1012012, Map.Trammel, new[] - { - new PMEntry( new Point3D( 4467, 1283, 5 ), 1012003 ), // Moonglow - new PMEntry( new Point3D( 1336, 1997, 5 ), 1012004 ), // Britain - new PMEntry( new Point3D( 1499, 3771, 5 ), 1012005 ), // Jhelom - new PMEntry( new Point3D( 771, 752, 5 ), 1012006 ), // Yew - new PMEntry( new Point3D( 2701, 692, 5 ), 1012007 ), // Minoc - new PMEntry( new Point3D( 1828, 2948,-20), 1012008 ), // Trinsic - new PMEntry( new Point3D( 643, 2067, 5 ), 1012009 ), // Skara Brae - /* Dynamic Z for Magincia to support both old and new maps. */ - new PMEntry( new Point3D( 3563, 2139, Map.Trammel.GetAverageZ( 3563, 2139 ) ), 1012010 ), // (New) Magincia - new PMEntry( new Point3D( 3450, 2677, 25), 1078098 ) // New Haven - } ); - - public static readonly PMList Felucca = - new PMList( 1012001, 1012013, Map.Felucca, new[] - { - new PMEntry( new Point3D( 4467, 1283, 5 ), 1012003 ), // Moonglow - new PMEntry( new Point3D( 1336, 1997, 5 ), 1012004 ), // Britain - new PMEntry( new Point3D( 1499, 3771, 5 ), 1012005 ), // Jhelom - new PMEntry( new Point3D( 771, 752, 5 ), 1012006 ), // Yew - new PMEntry( new Point3D( 2701, 692, 5 ), 1012007 ), // Minoc - new PMEntry( new Point3D( 1828, 2948,-20), 1012008 ), // Trinsic - new PMEntry( new Point3D( 643, 2067, 5 ), 1012009 ), // Skara Brae - /* Dynamic Z for Magincia to support both old and new maps. */ - new PMEntry( new Point3D( 3563, 2139, Map.Felucca.GetAverageZ( 3563, 2139 ) ), 1012010 ), // (New) Magincia - new PMEntry( new Point3D( 2711, 2234, 0 ), 1019001 ) // Buccaneer's Den - } ); - - public static readonly PMList Ilshenar = - new PMList( 1012002, 1012014, Map.Ilshenar, new[] - { - new PMEntry( new Point3D( 1215, 467, -13 ), 1012015 ), // Compassion - new PMEntry( new Point3D( 722, 1366, -60 ), 1012016 ), // Honesty - new PMEntry( new Point3D( 744, 724, -28 ), 1012017 ), // Honor - new PMEntry( new Point3D( 281, 1016, 0 ), 1012018 ), // Humility - new PMEntry( new Point3D( 987, 1011, -32 ), 1012019 ), // Justice - new PMEntry( new Point3D( 1174, 1286, -30 ), 1012020 ), // Sacrifice - new PMEntry( new Point3D( 1532, 1340, - 3 ), 1012021 ), // Spirituality - new PMEntry( new Point3D( 528, 216, -45 ), 1012022 ), // Valor - new PMEntry( new Point3D( 1721, 218, 96 ), 1019000 ) // Chaos - } ); - - public static readonly PMList Malas = - new PMList( 1060643, 1062039, Map.Malas, new[] - { - new PMEntry( new Point3D( 1015, 527, -65 ), 1060641 ), // Luna - new PMEntry( new Point3D( 1997, 1386, -85 ), 1060642 ) // Umbra - } ); - - public static readonly PMList Tokuno = - new PMList( 1063258, 1063415, Map.Tokuno, new[] - { - new PMEntry( new Point3D( 1169, 998, 41 ), 1063412 ), // Isamu-Jima - new PMEntry( new Point3D( 802, 1204, 25 ), 1063413 ), // Makoto-Jima - new PMEntry( new Point3D( 270, 628, 15 ), 1063414 ) // Homare-Jima - } ); - - public static readonly PMList[] UORLists = { Trammel, Felucca }; - public static readonly PMList[] UORListsYoung = { Trammel }; - public static readonly PMList[] LBRLists = { Trammel, Felucca, Ilshenar }; - public static readonly PMList[] LBRListsYoung = { Trammel, Ilshenar }; - public static readonly PMList[] AOSLists = { Trammel, Felucca, Ilshenar, Malas }; - public static readonly PMList[] AOSListsYoung = { Trammel, Ilshenar, Malas }; - public static readonly PMList[] SELists = { Trammel, Felucca, Ilshenar, Malas, Tokuno }; - public static readonly PMList[] SEListsYoung = { Trammel, Ilshenar, Malas, Tokuno }; - public static readonly PMList[] RedLists = { Felucca }; - public static readonly PMList[] SigilLists = { Felucca }; - } - - public class MoongateGump : Gump - { - private Mobile m_Mobile; - private Item m_Moongate; - private PMList[] m_Lists; - - public MoongateGump( Mobile mobile, Item moongate ) : base( 100, 100 ) - { - m_Mobile = mobile; - m_Moongate = moongate; - - PMList[] checkLists; - - if ( mobile.Player ) - { - if ( Factions.Sigil.ExistsOn( mobile ) ) - { - checkLists = PMList.SigilLists; - } - else if ( mobile.Kills >= 5 ) - { - checkLists = PMList.RedLists; - } - else - { - ClientFlags flags = mobile.NetState?.Flags ?? ClientFlags.None; - bool young = mobile is PlayerMobile playerMobile && playerMobile.Young; - - if ( Core.SE && (flags & ClientFlags.Tokuno) != 0 ) - checkLists = young ? PMList.SEListsYoung : PMList.SELists; - else if ( Core.AOS && (flags & ClientFlags.Malas) != 0 ) - checkLists = young ? PMList.AOSListsYoung : PMList.AOSLists; - else if ( (flags & ClientFlags.Ilshenar) != 0 ) - checkLists = young ? PMList.LBRListsYoung : PMList.LBRLists; - else - checkLists = young ? PMList.UORListsYoung : PMList.UORLists; - } - } - else - { - checkLists = PMList.SELists; - } - - m_Lists = new PMList[checkLists.Length]; - - for ( int i = 0; i < m_Lists.Length; ++i ) - m_Lists[i] = checkLists[i]; - - for ( int i = 0; i < m_Lists.Length; ++i ) - { - if ( m_Lists[i].Map == mobile.Map ) - { - PMList temp = m_Lists[i]; - - m_Lists[i] = m_Lists[0]; - m_Lists[0] = temp; - - break; - } - } - - AddPage( 0 ); - - AddBackground( 0, 0, 380, 280, 5054 ); - - AddButton( 10, 210, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 210, 140, 25, 1011036, false, false ); // OKAY - - AddButton( 10, 235, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 235, 140, 25, 1011012, false, false ); // CANCEL - - AddHtmlLocalized( 5, 5, 200, 20, 1012011, false, false ); // Pick your destination: - - for ( int i = 0; i < checkLists.Length; ++i ) - { - AddButton( 10, 35 + (i * 25), 2117, 2118, 0, GumpButtonType.Page, Array.IndexOf( m_Lists, checkLists[i] ) + 1 ); - AddHtmlLocalized( 30, 35 + (i * 25), 150, 20, checkLists[i].Number, false, false ); - } - - for ( int i = 0; i < m_Lists.Length; ++i ) - RenderPage( i, Array.IndexOf( checkLists, m_Lists[i] ) ); - } - - private void RenderPage( int index, int offset ) - { - PMList list = m_Lists[index]; - - AddPage( index + 1 ); - - AddButton( 10, 35 + (offset * 25), 2117, 2118, 0, GumpButtonType.Page, index + 1 ); - AddHtmlLocalized( 30, 35 + (offset * 25), 150, 20, list.SelNumber, false, false ); - - PMEntry[] entries = list.Entries; - - for ( int i = 0; i < entries.Length; ++i ) - { - AddRadio( 200, 35 + (i * 25), 210, 211, false, (index * 100) + i ); - AddHtmlLocalized( 225, 35 + (i * 25), 150, 20, entries[i].Number, false, false ); - } - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 0 ) // Cancel - return; - if ( m_Mobile.Deleted || m_Moongate.Deleted || m_Mobile.Map == null ) - return; - - int[] switches = info.Switches; - - if ( switches.Length == 0 ) - return; - - int switchID = switches[0]; - int listIndex = switchID / 100; - int listEntry = switchID % 100; - - if ( listIndex < 0 || listIndex >= m_Lists.Length ) - return; - - PMList list = m_Lists[listIndex]; - - if ( listEntry < 0 || listEntry >= list.Entries.Length ) - return; - - PMEntry entry = list.Entries[listEntry]; - - if ( !m_Mobile.InRange( m_Moongate.GetWorldLocation(), 1 ) || m_Mobile.Map != m_Moongate.Map ) - { - m_Mobile.SendLocalizedMessage( 1019002 ); // You are too far away to use the gate. - } - else if ( m_Mobile.Player && m_Mobile.Kills >= 5 && list.Map != Map.Felucca ) - { - m_Mobile.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - } - else if ( Factions.Sigil.ExistsOn( m_Mobile ) && list.Map != Factions.Faction.Facet ) - { - m_Mobile.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - } - else if ( m_Mobile.Criminal ) - { - m_Mobile.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - } - else if ( SpellHelper.CheckCombat( m_Mobile ) ) - { - m_Mobile.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - } - else if ( m_Mobile.Spell != null ) - { - m_Mobile.SendLocalizedMessage( 1049616 ); // You are too busy to do that at the moment. - } - else if ( m_Mobile.Map == list.Map && m_Mobile.InRange( entry.Location, 1 ) ) - { - m_Mobile.SendLocalizedMessage( 1019003 ); // You are already there. - } - else - { - BaseCreature.TeleportPets( m_Mobile, entry.Location, list.Map ); - - m_Mobile.Combatant = null; - m_Mobile.Warmode = false; - m_Mobile.Hidden = true; - - m_Mobile.MoveToWorld( entry.Location, list.Map ); - - Effects.PlaySound( entry.Location, list.Map, 0x1FE ); - } - } - } -} + public class PublicMoongate : Item + { + [Constructible] + public PublicMoongate() : base(0xF6C) + { + Movable = false; + Light = LightType.Circle300; + } + + public PublicMoongate(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public override bool HandlesOnMovement => true; + + public override void OnDoubleClick(Mobile from) + { + if (!from.Player) + return; + + if (from.InRange(GetWorldLocation(), 1)) + UseGate(from); + else + from.SendLocalizedMessage(500446); // That is too far away. + } + + public override bool OnMoveOver(Mobile m) + { + // Changed so criminals are not blocked by it. + if (m.Player) + UseGate(m); + + return true; + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m is PlayerMobile) + if (!Utility.InRange(m.Location, Location, 1) && Utility.InRange(oldLocation, Location, 1)) + m.CloseGump(typeof(MoongateGump)); + } + + public bool UseGate(Mobile m) + { + if (m.Criminal) + { + m.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + return false; + } + + if (SpellHelper.CheckCombat(m)) + { + m.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + return false; + } + + if (m.Spell != null) + { + m.SendLocalizedMessage(1049616); // You are too busy to do that at the moment. + return false; + } + + m.CloseGump(typeof(MoongateGump)); + m.SendGump(new MoongateGump(m, this)); + + if (!m.Hidden || m.AccessLevel == AccessLevel.Player) + Effects.PlaySound(m.Location, m.Map, 0x20E); + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public static void Initialize() + { + CommandSystem.Register("MoonGen", AccessLevel.Administrator, MoonGen_OnCommand); + } + + [Usage("MoonGen")] + [Description("Generates public moongates. Removes all old moongates.")] + public static void MoonGen_OnCommand(CommandEventArgs e) + { + DeleteAll(); + + int count = 0; + + count += MoonGen(PMList.Trammel); + count += MoonGen(PMList.Felucca); + count += MoonGen(PMList.Ilshenar); + count += MoonGen(PMList.Malas); + count += MoonGen(PMList.Tokuno); + + World.Broadcast(0x35, true, "{0} moongates generated.", count); + } + + private static void DeleteAll() + { + List list = new List(); + + foreach (Item item in World.Items.Values) + if (item is PublicMoongate) + list.Add(item); + + foreach (Item item in list) + item.Delete(); + + if (list.Count > 0) + World.Broadcast(0x35, true, "{0} moongates removed.", list.Count); + } + + private static int MoonGen(PMList list) + { + foreach (PMEntry entry in list.Entries) + { + Item item = new PublicMoongate(); + + item.MoveToWorld(entry.Location, list.Map); + + if (entry.Number == 1060642) // Umbra + item.Hue = 0x497; + } + + return list.Entries.Length; + } + } + + public class PMEntry + { + public PMEntry(Point3D loc, int number) + { + Location = loc; + Number = number; + } + + public Point3D Location{ get; } + + public int Number{ get; } + } + + public class PMList + { + public static readonly PMList Trammel = + new PMList(1012000, 1012012, Map.Trammel, new[] + { + new PMEntry(new Point3D(4467, 1283, 5), 1012003), // Moonglow + new PMEntry(new Point3D(1336, 1997, 5), 1012004), // Britain + new PMEntry(new Point3D(1499, 3771, 5), 1012005), // Jhelom + new PMEntry(new Point3D(771, 752, 5), 1012006), // Yew + new PMEntry(new Point3D(2701, 692, 5), 1012007), // Minoc + new PMEntry(new Point3D(1828, 2948, -20), 1012008), // Trinsic + new PMEntry(new Point3D(643, 2067, 5), 1012009), // Skara Brae + /* Dynamic Z for Magincia to support both old and new maps. */ + new PMEntry(new Point3D(3563, 2139, Map.Trammel.GetAverageZ(3563, 2139)), 1012010), // (New) Magincia + new PMEntry(new Point3D(3450, 2677, 25), 1078098) // New Haven + }); + + public static readonly PMList Felucca = + new PMList(1012001, 1012013, Map.Felucca, new[] + { + new PMEntry(new Point3D(4467, 1283, 5), 1012003), // Moonglow + new PMEntry(new Point3D(1336, 1997, 5), 1012004), // Britain + new PMEntry(new Point3D(1499, 3771, 5), 1012005), // Jhelom + new PMEntry(new Point3D(771, 752, 5), 1012006), // Yew + new PMEntry(new Point3D(2701, 692, 5), 1012007), // Minoc + new PMEntry(new Point3D(1828, 2948, -20), 1012008), // Trinsic + new PMEntry(new Point3D(643, 2067, 5), 1012009), // Skara Brae + /* Dynamic Z for Magincia to support both old and new maps. */ + new PMEntry(new Point3D(3563, 2139, Map.Felucca.GetAverageZ(3563, 2139)), 1012010), // (New) Magincia + new PMEntry(new Point3D(2711, 2234, 0), 1019001) // Buccaneer's Den + }); + + public static readonly PMList Ilshenar = + new PMList(1012002, 1012014, Map.Ilshenar, new[] + { + new PMEntry(new Point3D(1215, 467, -13), 1012015), // Compassion + new PMEntry(new Point3D(722, 1366, -60), 1012016), // Honesty + new PMEntry(new Point3D(744, 724, -28), 1012017), // Honor + new PMEntry(new Point3D(281, 1016, 0), 1012018), // Humility + new PMEntry(new Point3D(987, 1011, -32), 1012019), // Justice + new PMEntry(new Point3D(1174, 1286, -30), 1012020), // Sacrifice + new PMEntry(new Point3D(1532, 1340, -3), 1012021), // Spirituality + new PMEntry(new Point3D(528, 216, -45), 1012022), // Valor + new PMEntry(new Point3D(1721, 218, 96), 1019000) // Chaos + }); + + public static readonly PMList Malas = + new PMList(1060643, 1062039, Map.Malas, new[] + { + new PMEntry(new Point3D(1015, 527, -65), 1060641), // Luna + new PMEntry(new Point3D(1997, 1386, -85), 1060642) // Umbra + }); + + public static readonly PMList Tokuno = + new PMList(1063258, 1063415, Map.Tokuno, new[] + { + new PMEntry(new Point3D(1169, 998, 41), 1063412), // Isamu-Jima + new PMEntry(new Point3D(802, 1204, 25), 1063413), // Makoto-Jima + new PMEntry(new Point3D(270, 628, 15), 1063414) // Homare-Jima + }); + + public static readonly PMList[] UORLists = { Trammel, Felucca }; + public static readonly PMList[] UORListsYoung = { Trammel }; + public static readonly PMList[] LBRLists = { Trammel, Felucca, Ilshenar }; + public static readonly PMList[] LBRListsYoung = { Trammel, Ilshenar }; + public static readonly PMList[] AOSLists = { Trammel, Felucca, Ilshenar, Malas }; + public static readonly PMList[] AOSListsYoung = { Trammel, Ilshenar, Malas }; + public static readonly PMList[] SELists = { Trammel, Felucca, Ilshenar, Malas, Tokuno }; + public static readonly PMList[] SEListsYoung = { Trammel, Ilshenar, Malas, Tokuno }; + public static readonly PMList[] RedLists = { Felucca }; + public static readonly PMList[] SigilLists = { Felucca }; + + public PMList(int number, int selNumber, Map map, PMEntry[] entries) + { + Number = number; + SelNumber = selNumber; + Map = map; + Entries = entries; + } + + public int Number{ get; } + + public int SelNumber{ get; } + + public Map Map{ get; } + + public PMEntry[] Entries{ get; } + } + + public class MoongateGump : Gump + { + private PMList[] m_Lists; + private Mobile m_Mobile; + private Item m_Moongate; + + public MoongateGump(Mobile mobile, Item moongate) : base(100, 100) + { + m_Mobile = mobile; + m_Moongate = moongate; + + PMList[] checkLists; + + if (mobile.Player) + { + if (Sigil.ExistsOn(mobile)) + { + checkLists = PMList.SigilLists; + } + else if (mobile.Kills >= 5) + { + checkLists = PMList.RedLists; + } + else + { + ClientFlags flags = mobile.NetState?.Flags ?? ClientFlags.None; + bool young = mobile is PlayerMobile playerMobile && playerMobile.Young; + + if (Core.SE && (flags & ClientFlags.Tokuno) != 0) + checkLists = young ? PMList.SEListsYoung : PMList.SELists; + else if (Core.AOS && (flags & ClientFlags.Malas) != 0) + checkLists = young ? PMList.AOSListsYoung : PMList.AOSLists; + else if ((flags & ClientFlags.Ilshenar) != 0) + checkLists = young ? PMList.LBRListsYoung : PMList.LBRLists; + else + checkLists = young ? PMList.UORListsYoung : PMList.UORLists; + } + } + else + { + checkLists = PMList.SELists; + } + + m_Lists = new PMList[checkLists.Length]; + + for (int i = 0; i < m_Lists.Length; ++i) + m_Lists[i] = checkLists[i]; + + for (int i = 0; i < m_Lists.Length; ++i) + if (m_Lists[i].Map == mobile.Map) + { + PMList temp = m_Lists[i]; + + m_Lists[i] = m_Lists[0]; + m_Lists[0] = temp; + + break; + } + + AddPage(0); + + AddBackground(0, 0, 380, 280, 5054); + + AddButton(10, 210, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 210, 140, 25, 1011036, false, false); // OKAY + + AddButton(10, 235, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 235, 140, 25, 1011012, false, false); // CANCEL + + AddHtmlLocalized(5, 5, 200, 20, 1012011, false, false); // Pick your destination: + + for (int i = 0; i < checkLists.Length; ++i) + { + AddButton(10, 35 + i * 25, 2117, 2118, 0, GumpButtonType.Page, Array.IndexOf(m_Lists, checkLists[i]) + 1); + AddHtmlLocalized(30, 35 + i * 25, 150, 20, checkLists[i].Number, false, false); + } + + for (int i = 0; i < m_Lists.Length; ++i) + RenderPage(i, Array.IndexOf(checkLists, m_Lists[i])); + } + + private void RenderPage(int index, int offset) + { + PMList list = m_Lists[index]; + + AddPage(index + 1); + + AddButton(10, 35 + offset * 25, 2117, 2118, 0, GumpButtonType.Page, index + 1); + AddHtmlLocalized(30, 35 + offset * 25, 150, 20, list.SelNumber, false, false); + + PMEntry[] entries = list.Entries; + + for (int i = 0; i < entries.Length; ++i) + { + AddRadio(200, 35 + i * 25, 210, 211, false, index * 100 + i); + AddHtmlLocalized(225, 35 + i * 25, 150, 20, entries[i].Number, false, false); + } + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 0) // Cancel + return; + if (m_Mobile.Deleted || m_Moongate.Deleted || m_Mobile.Map == null) + return; + + int[] switches = info.Switches; + + if (switches.Length == 0) + return; + + int switchID = switches[0]; + int listIndex = switchID / 100; + int listEntry = switchID % 100; + + if (listIndex < 0 || listIndex >= m_Lists.Length) + return; + + PMList list = m_Lists[listIndex]; + + if (listEntry < 0 || listEntry >= list.Entries.Length) + return; + + PMEntry entry = list.Entries[listEntry]; + + if (!m_Mobile.InRange(m_Moongate.GetWorldLocation(), 1) || m_Mobile.Map != m_Moongate.Map) + { + m_Mobile.SendLocalizedMessage(1019002); // You are too far away to use the gate. + } + else if (m_Mobile.Player && m_Mobile.Kills >= 5 && list.Map != Map.Felucca) + { + m_Mobile.SendLocalizedMessage(1019004); // You are not allowed to travel there. + } + else if (Sigil.ExistsOn(m_Mobile) && list.Map != Faction.Facet) + { + m_Mobile.SendLocalizedMessage(1019004); // You are not allowed to travel there. + } + else if (m_Mobile.Criminal) + { + m_Mobile.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + } + else if (SpellHelper.CheckCombat(m_Mobile)) + { + m_Mobile.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + } + else if (m_Mobile.Spell != null) + { + m_Mobile.SendLocalizedMessage(1049616); // You are too busy to do that at the moment. + } + else if (m_Mobile.Map == list.Map && m_Mobile.InRange(entry.Location, 1)) + { + m_Mobile.SendLocalizedMessage(1019003); // You are already there. + } + else + { + BaseCreature.TeleportPets(m_Mobile, entry.Location, list.Map); + + m_Mobile.Combatant = null; + m_Mobile.Warmode = false; + m_Mobile.Hidden = true; + + m_Mobile.MoveToWorld(entry.Location, list.Map); + + Effects.PlaySound(entry.Location, list.Map, 0x1FE); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Rares.cs b/Scripts/Items/Misc/Rares.cs index 6bee1864f..b83ab784b 100644 --- a/Scripts/Items/Misc/Rares.cs +++ b/Scripts/Items/Misc/Rares.cs @@ -1,716 +1,707 @@ namespace Server.Items { - public class Rope : Item - { - [Constructible] - public Rope() : this( 1 ) - { - } - - [Constructible] - public Rope( int amount ) : base( 0x14F8 ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } - - - - public Rope( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class IronWire : Item - { - [Constructible] - public IronWire() : this( 1 ) - { - } - - [Constructible] - public IronWire( int amount ) : base( 0x1876 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - } - - - - public IronWire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version < 1 && Weight == 2.0 ) - Weight = 5.0; - } - } - - public class SilverWire : Item - { - [Constructible] - public SilverWire() : this( 1 ) - { - } - - [Constructible] - public SilverWire( int amount ) : base( 0x1877 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - } - - - - public SilverWire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version < 1 && Weight == 2.0 ) - Weight = 5.0; - } - } - - public class GoldWire : Item - { - [Constructible] - public GoldWire() : this( 1 ) - { - } - - [Constructible] - public GoldWire( int amount ) : base( 0x1878 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - } - - - - public GoldWire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version < 1 && Weight == 2.0 ) - Weight = 5.0; - } - } - - public class CopperWire : Item - { - [Constructible] - public CopperWire() : this( 1 ) - { - } - - [Constructible] - public CopperWire( int amount ) : base( 0x1879 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - } - - - - public CopperWire( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version < 1 && Weight == 2.0 ) - Weight = 5.0; - } - } - - public class WhiteDriedFlowers : Item - { - [Constructible] - public WhiteDriedFlowers() : this( 1 ) - { - } - - [Constructible] - public WhiteDriedFlowers( int amount ) : base( 0xC3C ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } - - - - public WhiteDriedFlowers( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GreenDriedFlowers : Item - { - [Constructible] - public GreenDriedFlowers() : this( 1 ) - { - } - - [Constructible] - public GreenDriedFlowers( int amount ) : base( 0xC3E ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } - - - - public GreenDriedFlowers( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DriedOnions : Item - { - [Constructible] - public DriedOnions() : this( 1 ) - { - } - - [Constructible] - public DriedOnions( int amount ) : base( 0xC40 ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } - - - - public DriedOnions( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DriedHerbs : Item - { - [Constructible] - public DriedHerbs() : this( 1 ) - { - } - - [Constructible] - public DriedHerbs( int amount ) : base( 0xC42 ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } - - - - public DriedHerbs( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class HorseShoes : Item - { - [Constructible] - public HorseShoes() : base( 0xFB6 ) - { - Weight = 3.0; - } - - public HorseShoes( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ForgedMetal : Item - { - [Constructible] - public ForgedMetal() : base( 0xFB8 ) - { - Weight = 5.0; - } - - public ForgedMetal( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Whip : Item - { - [Constructible] - public Whip() : base( 0x166E ) - { - Weight = 1.0; - } - - public Whip( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PaintsAndBrush : Item - { - [Constructible] - public PaintsAndBrush() : base( 0xFC1 ) - { - Weight = 1.0; - } - - public PaintsAndBrush( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PenAndInk : Item - { - [Constructible] - public PenAndInk() : base( 0xFBF ) - { - Weight = 1.0; - } - - public PenAndInk( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ChiselsNorth : Item - { - [Constructible] - public ChiselsNorth() : base( 0x1026 ) - { - Weight = 1.0; - } - - public ChiselsNorth( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class ChiselsWest : Item - { - [Constructible] - public ChiselsWest() : base( 0x1027 ) - { - Weight = 1.0; - } - - public ChiselsWest( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtyPan : Item - { - [Constructible] - public DirtyPan() : base( 0x9E8 ) - { - Weight = 1.0; - } - - public DirtyPan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtySmallRoundPot : Item - { - [Constructible] - public DirtySmallRoundPot() : base( 0x9E7 ) - { - Weight = 1.0; - } - - public DirtySmallRoundPot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtyPot : Item - { - [Constructible] - public DirtyPot() : base( 0x9E6 ) - { - Weight = 1.0; - } - - public DirtyPot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtyRoundPot : Item - { - [Constructible] - public DirtyRoundPot() : base( 0x9DF ) - { - Weight = 1.0; - } - - public DirtyRoundPot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtyFrypan : Item - { - [Constructible] - public DirtyFrypan() : base( 0x9DE ) - { - Weight = 1.0; - } - - public DirtyFrypan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtySmallPot : Item - { - [Constructible] - public DirtySmallPot() : base( 0x9DD ) - { - Weight = 1.0; - } - - public DirtySmallPot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class DirtyKettle : Item - { - [Constructible] - public DirtyKettle() : base( 0x9DC ) - { - Weight = 1.0; - } - - public DirtyKettle( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } + public class Rope : Item + { + [Constructible] + public Rope() : this(1) + { + } + + [Constructible] + public Rope(int amount) : base(0x14F8) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } + + + public Rope(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class IronWire : Item + { + [Constructible] + public IronWire() : this(1) + { + } + + [Constructible] + public IronWire(int amount) : base(0x1876) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + } + + + public IronWire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version < 1 && Weight == 2.0) + Weight = 5.0; + } + } + + public class SilverWire : Item + { + [Constructible] + public SilverWire() : this(1) + { + } + + [Constructible] + public SilverWire(int amount) : base(0x1877) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + } + + + public SilverWire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version < 1 && Weight == 2.0) + Weight = 5.0; + } + } + + public class GoldWire : Item + { + [Constructible] + public GoldWire() : this(1) + { + } + + [Constructible] + public GoldWire(int amount) : base(0x1878) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + } + + + public GoldWire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version < 1 && Weight == 2.0) + Weight = 5.0; + } + } + + public class CopperWire : Item + { + [Constructible] + public CopperWire() : this(1) + { + } + + [Constructible] + public CopperWire(int amount) : base(0x1879) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + } + + + public CopperWire(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version < 1 && Weight == 2.0) + Weight = 5.0; + } + } + + public class WhiteDriedFlowers : Item + { + [Constructible] + public WhiteDriedFlowers() : this(1) + { + } + + [Constructible] + public WhiteDriedFlowers(int amount) : base(0xC3C) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } + + + public WhiteDriedFlowers(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenDriedFlowers : Item + { + [Constructible] + public GreenDriedFlowers() : this(1) + { + } + + [Constructible] + public GreenDriedFlowers(int amount) : base(0xC3E) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } + + + public GreenDriedFlowers(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DriedOnions : Item + { + [Constructible] + public DriedOnions() : this(1) + { + } + + [Constructible] + public DriedOnions(int amount) : base(0xC40) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } + + + public DriedOnions(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DriedHerbs : Item + { + [Constructible] + public DriedHerbs() : this(1) + { + } + + [Constructible] + public DriedHerbs(int amount) : base(0xC42) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } + + + public DriedHerbs(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class HorseShoes : Item + { + [Constructible] + public HorseShoes() : base(0xFB6) + { + Weight = 3.0; + } + + public HorseShoes(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ForgedMetal : Item + { + [Constructible] + public ForgedMetal() : base(0xFB8) + { + Weight = 5.0; + } + + public ForgedMetal(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Whip : Item + { + [Constructible] + public Whip() : base(0x166E) + { + Weight = 1.0; + } + + public Whip(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PaintsAndBrush : Item + { + [Constructible] + public PaintsAndBrush() : base(0xFC1) + { + Weight = 1.0; + } + + public PaintsAndBrush(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PenAndInk : Item + { + [Constructible] + public PenAndInk() : base(0xFBF) + { + Weight = 1.0; + } + + public PenAndInk(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ChiselsNorth : Item + { + [Constructible] + public ChiselsNorth() : base(0x1026) + { + Weight = 1.0; + } + + public ChiselsNorth(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class ChiselsWest : Item + { + [Constructible] + public ChiselsWest() : base(0x1027) + { + Weight = 1.0; + } + + public ChiselsWest(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtyPan : Item + { + [Constructible] + public DirtyPan() : base(0x9E8) + { + Weight = 1.0; + } + + public DirtyPan(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtySmallRoundPot : Item + { + [Constructible] + public DirtySmallRoundPot() : base(0x9E7) + { + Weight = 1.0; + } + + public DirtySmallRoundPot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtyPot : Item + { + [Constructible] + public DirtyPot() : base(0x9E6) + { + Weight = 1.0; + } + + public DirtyPot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtyRoundPot : Item + { + [Constructible] + public DirtyRoundPot() : base(0x9DF) + { + Weight = 1.0; + } + + public DirtyRoundPot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtyFrypan : Item + { + [Constructible] + public DirtyFrypan() : base(0x9DE) + { + Weight = 1.0; + } + + public DirtyFrypan(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtySmallPot : Item + { + [Constructible] + public DirtySmallPot() : base(0x9DD) + { + Weight = 1.0; + } + + public DirtySmallPot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class DirtyKettle : Item + { + [Constructible] + public DirtyKettle() : base(0x9DC) + { + Weight = 1.0; + } + + public DirtyKettle(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Scales.cs b/Scripts/Items/Misc/Scales.cs index 2c176d909..f10c8cfef 100644 --- a/Scripts/Items/Misc/Scales.cs +++ b/Scripts/Items/Misc/Scales.cs @@ -1,91 +1,90 @@ -using System; using Server.Targeting; namespace Server.Items { - public class Scales : Item - { - [Constructible] - public Scales() : base( 0x1852 ) - { - Weight = 4.0; - } + public class Scales : Item + { + [Constructible] + public Scales() : base(0x1852) + { + Weight = 4.0; + } - public Scales( Serial serial ) : base( serial ) - { - } + public Scales(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 502431 ); // What would you like to weigh? - from.Target = new InternalTarget( this ); - } + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(502431); // What would you like to weigh? + from.Target = new InternalTarget(this); + } - private class InternalTarget : Target - { - private Scales m_Item; + private class InternalTarget : Target + { + private Scales m_Item; - public InternalTarget( Scales item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget(Scales item) : base(1, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object targeted ) - { - string message; + protected override void OnTarget(Mobile from, object targeted) + { + string message; - if ( targeted == m_Item ) - { - message = "It cannot weight itself."; - } - else if ( targeted is Item item ) - { - object root = item.RootParent; + if (targeted == m_Item) + { + message = "It cannot weight itself."; + } + else if (targeted is Item item) + { + object root = item.RootParent; - if ( (root != null && root != from) || item.Parent == from ) - { - message = "You decide that item's current location is too awkward to get an accurate result."; - } - else if ( item.Movable ) - { - if ( item.Amount > 1 ) - message = "You place one item on the scale. "; - else - message = "You place that item on the scale. "; + if (root != null && root != from || item.Parent == from) + { + message = "You decide that item's current location is too awkward to get an accurate result."; + } + else if (item.Movable) + { + if (item.Amount > 1) + message = "You place one item on the scale. "; + else + message = "You place that item on the scale. "; - double weight = item.Weight; + double weight = item.Weight; - if ( weight <= 0.0 ) - message += "It is lighter than a feather."; - else - message += $"It weighs {weight} stones."; - } - else - { - message = "You cannot weigh that object."; - } - } - else - { - message = "You cannot weigh that object."; - } + if (weight <= 0.0) + message += "It is lighter than a feather."; + else + message += $"It weighs {weight} stones."; + } + else + { + message = "You cannot weigh that object."; + } + } + else + { + message = "You cannot weigh that object."; + } - from.SendMessage( message ); - } - } - } -} + from.SendMessage(message); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/SerpentPillar.cs b/Scripts/Items/Misc/SerpentPillar.cs index 5590c3f50..800715669 100644 --- a/Scripts/Items/Misc/SerpentPillar.cs +++ b/Scripts/Items/Misc/SerpentPillar.cs @@ -2,105 +2,106 @@ using Server.Multis; namespace Server.Items { - public class SerpentPillar : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public bool Active { get; set; } + public class SerpentPillar : Item + { + [Constructible] + public SerpentPillar() : this(null, new Rectangle2D(), false) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public string Word { get; set; } + public SerpentPillar(string word, Rectangle2D destination) : this(word, destination, true) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public Rectangle2D Destination { get; set; } + public SerpentPillar(string word, Rectangle2D destination, bool active) : base(0x233F) + { + Movable = false; - [Constructible] - public SerpentPillar() : this( null, new Rectangle2D(), false ) - { - } + Active = active; + Word = word; + Destination = destination; + } - public SerpentPillar( string word, Rectangle2D destination ) : this( word, destination, true ) - { - } + public SerpentPillar(Serial serial) : base(serial) + { + } - public SerpentPillar( string word, Rectangle2D destination, bool active ) : base( 0x233F ) - { - Movable = false; + [CommandProperty(AccessLevel.GameMaster)] + public bool Active{ get; set; } - Active = active; - Word = word; - Destination = destination; - } + [CommandProperty(AccessLevel.GameMaster)] + public string Word{ get; set; } - public override bool HandlesOnSpeech => true; + [CommandProperty(AccessLevel.GameMaster)] + public Rectangle2D Destination{ get; set; } - public override void OnSpeech( SpeechEventArgs e ) - { - Mobile from = e.Mobile; + public override bool HandlesOnSpeech => true; - if ( !e.Handled && from.InRange( this, 10 ) && e.Speech.ToLower() == Word ) - { - BaseBoat boat = BaseBoat.FindBoatAt( from, from.Map ); + public override void OnSpeech(SpeechEventArgs e) + { + Mobile from = e.Mobile; - if ( boat == null ) - return; + if (!e.Handled && from.InRange(this, 10) && e.Speech.ToLower() == Word) + { + BaseBoat boat = BaseBoat.FindBoatAt(from, from.Map); - if ( !Active ) - { - boat.TillerMan?.Say( 502507 ); // Ar, Legend has it that these pillars are inactive! No man knows how it might be undone! + if (boat == null) + return; - return; - } + if (!Active) + { + boat.TillerMan + ?.Say(502507); // Ar, Legend has it that these pillars are inactive! No man knows how it might be undone! - Map map = from.Map; + return; + } - for ( int i = 0; i < 5; i++ ) // Try 5 times - { - int x = Utility.Random( Destination.X, Destination.Width ); - int y = Utility.Random( Destination.Y, Destination.Height ); - int z = map.GetAverageZ( x, y ); + Map map = from.Map; - Point3D dest = new Point3D( x, y, z ); + for (int i = 0; i < 5; i++) // Try 5 times + { + int x = Utility.Random(Destination.X, Destination.Width); + int y = Utility.Random(Destination.Y, Destination.Height); + int z = map.GetAverageZ(x, y); - if ( boat.CanFit( dest, map, boat.ItemID ) ) - { - int xOffset = x - boat.X; - int yOffset = y - boat.Y; - int zOffset = z - boat.Z; + Point3D dest = new Point3D(x, y, z); - boat.Teleport( xOffset, yOffset, zOffset ); + if (boat.CanFit(dest, map, boat.ItemID)) + { + int xOffset = x - boat.X; + int yOffset = y - boat.Y; + int zOffset = z - boat.Z; - return; - } - } + boat.Teleport(xOffset, yOffset, zOffset); - boat.TillerMan?.Say( 502508 ); // Ar, I refuse to take that matey through here! - } - } + return; + } + } - public SerpentPillar( Serial serial ) : base( serial ) - { - } + boat.TillerMan?.Say(502508); // Ar, I refuse to take that matey through here! + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) Active ); - writer.Write( (string) Word ); - writer.Write( (Rectangle2D) Destination ); - } + writer.Write(Active); + writer.Write(Word); + writer.Write(Destination); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Active = reader.ReadBool(); - Word = reader.ReadString(); - Destination = reader.ReadRect2D(); - } - } -} + Active = reader.ReadBool(); + Word = reader.ReadString(); + Destination = reader.ReadRect2D(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/SpecialBeardDye.cs b/Scripts/Items/Misc/SpecialBeardDye.cs index f367a6450..0928dec51 100644 --- a/Scripts/Items/Misc/SpecialBeardDye.cs +++ b/Scripts/Items/Misc/SpecialBeardDye.cs @@ -3,159 +3,160 @@ using Server.Network; namespace Server.Items { - public class SpecialBeardDye : Item - { - public override int LabelNumber => 1041087; // Special Beard Dye + public class SpecialBeardDye : Item + { + [Constructible] + public SpecialBeardDye() : base(0xE26) + { + Weight = 1.0; + LootType = LootType.Newbied; + } - [Constructible] - public SpecialBeardDye() : base( 0xE26 ) - { - Weight = 1.0; - LootType = LootType.Newbied; - } + public SpecialBeardDye(Serial serial) : base(serial) + { + } - public SpecialBeardDye( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041087; // Special Beard Dye - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - from.CloseGump( typeof( SpecialBeardDyeGump ) ); - from.SendGump( new SpecialBeardDyeGump( this ) ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 906, 1019045 ); // I can't reach that. - } - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 1)) + { + from.CloseGump(typeof(SpecialBeardDyeGump)); + from.SendGump(new SpecialBeardDyeGump(this)); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 906, 1019045); // I can't reach that. + } + } + } - public class SpecialBeardDyeGump : Gump - { - private SpecialBeardDye m_SpecialBeardDye; + public class SpecialBeardDyeGump : Gump + { + private static SpecialBeardDyeEntry[] m_Entries = + { + new SpecialBeardDyeEntry("*****", 12, 10), + new SpecialBeardDyeEntry("*****", 32, 5), + new SpecialBeardDyeEntry("*****", 38, 8), + new SpecialBeardDyeEntry("*****", 54, 3), + new SpecialBeardDyeEntry("*****", 62, 10), + new SpecialBeardDyeEntry("*****", 81, 2), + new SpecialBeardDyeEntry("*****", 89, 2), + new SpecialBeardDyeEntry("*****", 1153, 2) + }; - private class SpecialBeardDyeEntry - { - public string Name { get; } + private SpecialBeardDye m_SpecialBeardDye; - public int HueStart { get; } + public SpecialBeardDyeGump(SpecialBeardDye dye) : base(0, 0) + { + m_SpecialBeardDye = dye; - public int HueCount { get; } + AddPage(0); + AddBackground(150, 60, 350, 358, 2600); + AddBackground(170, 104, 110, 270, 5100); + AddHtmlLocalized(230, 75, 200, 20, 1011013, false, false); // Hair Color Selection Menu + AddHtmlLocalized(235, 380, 300, 20, 1013007, false, false); // Dye my beard this color! + AddButton(200, 380, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); // DYE HAIR - public SpecialBeardDyeEntry( string name, int hueStart, int hueCount ) - { - Name = name; - HueStart = hueStart; - HueCount = hueCount; - } - } + for (int i = 0; i < m_Entries.Length; ++i) + { + AddLabel(180, 109 + i * 22, m_Entries[i].HueStart - 1, m_Entries[i].Name); + AddButton(257, 110 + i * 22, 5224, 5224, 0, GumpButtonType.Page, i + 1); + } - private static SpecialBeardDyeEntry[] m_Entries = { - new SpecialBeardDyeEntry( "*****", 12, 10 ), - new SpecialBeardDyeEntry( "*****", 32, 5 ), - new SpecialBeardDyeEntry( "*****", 38, 8 ), - new SpecialBeardDyeEntry( "*****", 54, 3 ), - new SpecialBeardDyeEntry( "*****", 62, 10 ), - new SpecialBeardDyeEntry( "*****", 81, 2 ), - new SpecialBeardDyeEntry( "*****", 89, 2 ), - new SpecialBeardDyeEntry( "*****", 1153, 2 ) - }; + for (int i = 0; i < m_Entries.Length; ++i) + { + SpecialBeardDyeEntry e = m_Entries[i]; - public SpecialBeardDyeGump( SpecialBeardDye dye ) : base( 0, 0 ) - { - m_SpecialBeardDye = dye; + AddPage(i + 1); - AddPage( 0 ); - AddBackground( 150, 60, 350, 358, 2600 ); - AddBackground( 170, 104, 110, 270, 5100 ); - AddHtmlLocalized( 230, 75, 200, 20, 1011013, false, false ); // Hair Color Selection Menu - AddHtmlLocalized( 235, 380, 300, 20, 1013007, false, false ); // Dye my beard this color! - AddButton( 200, 380, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); // DYE HAIR + for (int j = 0; j < e.HueCount; ++j) + { + AddLabel(328 + j / 16 * 80, 102 + j % 16 * 17, e.HueStart + j - 1, "*****"); + AddRadio(310 + j / 16 * 80, 102 + j % 16 * 17, 210, 211, false, i * 100 + j); + } + } + } - for ( int i = 0; i < m_Entries.Length; ++i ) - { - AddLabel( 180, 109 + (i * 22), m_Entries[i].HueStart - 1, m_Entries[i].Name ); - AddButton( 257, 110 + (i * 22), 5224, 5224, 0, GumpButtonType.Page, i + 1 ); - } + public override void OnResponse(NetState from, RelayInfo info) + { + if (m_SpecialBeardDye.Deleted) + return; - for ( int i = 0; i < m_Entries.Length; ++i ) - { - SpecialBeardDyeEntry e = m_Entries[i]; + Mobile m = from.Mobile; + int[] switches = info.Switches; - AddPage( i + 1 ); + if (!m_SpecialBeardDye.IsChildOf(m.Backpack)) + { + m.SendLocalizedMessage(1042010); //You must have the objectin your backpack to use it. + return; + } - for ( int j = 0; j < e.HueCount; ++j ) - { - AddLabel( 328 + ((j / 16) * 80), 102 + ((j % 16) * 17), e.HueStart + j - 1, "*****" ); - AddRadio( 310 + ((j / 16) * 80), 102 + ((j % 16) * 17), 210, 211, false, (i * 100) + j ); - } - } - } + if (info.ButtonID != 0 && switches.Length > 0) + { + if (m.FacialHairItemID == 0) + { + m.SendLocalizedMessage(502623); // You have no hair to dye and cannot use this + } + else + { + // To prevent this from being exploited, the hue is abstracted into an internal list - public override void OnResponse( NetState from, RelayInfo info ) - { - if ( m_SpecialBeardDye.Deleted ) - return; + int entryIndex = switches[0] / 100; + int hueOffset = switches[0] % 100; - Mobile m = from.Mobile; - int[] switches = info.Switches; + if (entryIndex >= 0 && entryIndex < m_Entries.Length) + { + SpecialBeardDyeEntry e = m_Entries[entryIndex]; - if ( !m_SpecialBeardDye.IsChildOf( m.Backpack ) ) - { - m.SendLocalizedMessage( 1042010 ); //You must have the objectin your backpack to use it. - return; - } + if (hueOffset >= 0 && hueOffset < e.HueCount) + { + int hue = e.HueStart + hueOffset; - if ( info.ButtonID != 0 && switches.Length > 0 ) - { - if ( m.FacialHairItemID == 0 ) - { - m.SendLocalizedMessage( 502623 ); // You have no hair to dye and cannot use this - } - else - { - // To prevent this from being exploited, the hue is abstracted into an internal list + m.FacialHairHue = hue; - int entryIndex = switches[0] / 100; - int hueOffset = switches[0] % 100; + m.SendLocalizedMessage(501199); // You dye your hair + m_SpecialBeardDye.Delete(); + m.PlaySound(0x4E); + } + } + } + } + else + { + m.SendLocalizedMessage(501200); // You decide not to dye your hair + } + } - if ( entryIndex >= 0 && entryIndex < m_Entries.Length ) - { - SpecialBeardDyeEntry e = m_Entries[entryIndex]; + private class SpecialBeardDyeEntry + { + public SpecialBeardDyeEntry(string name, int hueStart, int hueCount) + { + Name = name; + HueStart = hueStart; + HueCount = hueCount; + } - if ( hueOffset >= 0 && hueOffset < e.HueCount ) - { - int hue = e.HueStart + hueOffset; + public string Name{ get; } - m.FacialHairHue = hue; + public int HueStart{ get; } - m.SendLocalizedMessage( 501199 ); // You dye your hair - m_SpecialBeardDye.Delete(); - m.PlaySound( 0x4E ); - } - } - } - } - else - { - m.SendLocalizedMessage( 501200 ); // You decide not to dye your hair - } - } - } -} + public int HueCount{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/SpecialHairDye.cs b/Scripts/Items/Misc/SpecialHairDye.cs index bf9d1f091..745c54ed4 100644 --- a/Scripts/Items/Misc/SpecialHairDye.cs +++ b/Scripts/Items/Misc/SpecialHairDye.cs @@ -3,161 +3,161 @@ using Server.Network; namespace Server.Items { - public class SpecialHairDye : Item - { - public override string DefaultName => "Special Hair Dye"; + public class SpecialHairDye : Item + { + [Constructible] + public SpecialHairDye() : base(0xE26) + { + Weight = 1.0; + LootType = LootType.Newbied; + } - [Constructible] - public SpecialHairDye() : base( 0xE26 ) - { - Weight = 1.0; - LootType = LootType.Newbied; - } + public SpecialHairDye(Serial serial) : base(serial) + { + } - public SpecialHairDye( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Special Hair Dye"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - from.CloseGump( typeof( SpecialHairDyeGump ) ); - from.SendGump( new SpecialHairDyeGump( this ) ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 906, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 1)) + { + from.CloseGump(typeof(SpecialHairDyeGump)); + from.SendGump(new SpecialHairDyeGump(this)); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 906, 1019045); // I can't reach that. + } + } + } - } - } + public class SpecialHairDyeGump : Gump + { + private static SpecialHairDyeEntry[] m_Entries = + { + new SpecialHairDyeEntry("*****", 12, 10), + new SpecialHairDyeEntry("*****", 32, 5), + new SpecialHairDyeEntry("*****", 38, 8), + new SpecialHairDyeEntry("*****", 54, 3), + new SpecialHairDyeEntry("*****", 62, 10), + new SpecialHairDyeEntry("*****", 81, 2), + new SpecialHairDyeEntry("*****", 89, 2), + new SpecialHairDyeEntry("*****", 1153, 2) + }; - public class SpecialHairDyeGump : Gump - { - private SpecialHairDye m_SpecialHairDye; + private SpecialHairDye m_SpecialHairDye; - private class SpecialHairDyeEntry - { - public string Name { get; } + public SpecialHairDyeGump(SpecialHairDye dye) : base(0, 0) + { + m_SpecialHairDye = dye; - public int HueStart { get; } + AddPage(0); + AddBackground(150, 60, 350, 358, 2600); + AddBackground(170, 104, 110, 270, 5100); + AddHtmlLocalized(230, 75, 200, 20, 1011013, false, false); // Hair Color Selection Menu + AddHtmlLocalized(235, 380, 300, 20, 1011014, false, false); // Dye my hair this color! + AddButton(200, 380, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); // DYE HAIR - public int HueCount { get; } + for (int i = 0; i < m_Entries.Length; ++i) + { + AddLabel(180, 109 + i * 22, m_Entries[i].HueStart - 1, m_Entries[i].Name); + AddButton(257, 110 + i * 22, 5224, 5224, 0, GumpButtonType.Page, i + 1); + } - public SpecialHairDyeEntry( string name, int hueStart, int hueCount ) - { - Name = name; - HueStart = hueStart; - HueCount = hueCount; - } - } + for (int i = 0; i < m_Entries.Length; ++i) + { + SpecialHairDyeEntry e = m_Entries[i]; - private static SpecialHairDyeEntry[] m_Entries = { - new SpecialHairDyeEntry( "*****", 12, 10 ), - new SpecialHairDyeEntry( "*****", 32, 5 ), - new SpecialHairDyeEntry( "*****", 38, 8 ), - new SpecialHairDyeEntry( "*****", 54, 3 ), - new SpecialHairDyeEntry( "*****", 62, 10 ), - new SpecialHairDyeEntry( "*****", 81, 2 ), - new SpecialHairDyeEntry( "*****", 89, 2 ), - new SpecialHairDyeEntry( "*****", 1153, 2 ) - }; + AddPage(i + 1); - public SpecialHairDyeGump( SpecialHairDye dye ) : base( 0, 0 ) - { - m_SpecialHairDye = dye; + for (int j = 0; j < e.HueCount; ++j) + { + AddLabel(328 + j / 16 * 80, 102 + j % 16 * 17, e.HueStart + j - 1, "*****"); + AddRadio(310 + j / 16 * 80, 102 + j % 16 * 17, 210, 211, false, i * 100 + j); + } + } + } - AddPage( 0 ); - AddBackground( 150, 60, 350, 358, 2600 ); - AddBackground( 170, 104, 110, 270, 5100 ); - AddHtmlLocalized( 230, 75, 200, 20, 1011013, false, false ); // Hair Color Selection Menu - AddHtmlLocalized( 235, 380, 300, 20, 1011014, false, false ); // Dye my hair this color! - AddButton( 200, 380, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); // DYE HAIR + public override void OnResponse(NetState from, RelayInfo info) + { + if (m_SpecialHairDye.Deleted) + return; - for ( int i = 0; i < m_Entries.Length; ++i ) - { - AddLabel( 180, 109 + (i * 22), m_Entries[i].HueStart - 1, m_Entries[i].Name ); - AddButton( 257, 110 + (i * 22), 5224, 5224, 0, GumpButtonType.Page, i + 1 ); - } + Mobile m = from.Mobile; + int[] switches = info.Switches; - for ( int i = 0; i < m_Entries.Length; ++i ) - { - SpecialHairDyeEntry e = m_Entries[i]; + if (!m_SpecialHairDye.IsChildOf(m.Backpack)) + { + m.SendLocalizedMessage(1042010); //You must have the objectin your backpack to use it. + return; + } - AddPage( i + 1 ); + if (info.ButtonID != 0 && switches.Length > 0) + { + if (m.HairItemID == 0) + { + m.SendLocalizedMessage(502623); // You have no hair to dye and cannot use this + } + else + { + // To prevent this from being exploited, the hue is abstracted into an internal list - for ( int j = 0; j < e.HueCount; ++j ) - { - AddLabel( 328 + ((j / 16) * 80), 102 + ((j % 16) * 17), e.HueStart + j - 1, "*****" ); - AddRadio( 310 + ((j / 16) * 80), 102 + ((j % 16) * 17), 210, 211, false, (i * 100) + j ); - } - } - } + int entryIndex = switches[0] / 100; + int hueOffset = switches[0] % 100; - public override void OnResponse( NetState from, RelayInfo info ) - { - if ( m_SpecialHairDye.Deleted ) - return; + if (entryIndex >= 0 && entryIndex < m_Entries.Length) + { + SpecialHairDyeEntry e = m_Entries[entryIndex]; - Mobile m = from.Mobile; - int[] switches = info.Switches; + if (hueOffset >= 0 && hueOffset < e.HueCount) + { + m_SpecialHairDye.Delete(); - if ( !m_SpecialHairDye.IsChildOf( m.Backpack ) ) - { - m.SendLocalizedMessage( 1042010 ); //You must have the objectin your backpack to use it. - return; - } + int hue = e.HueStart + hueOffset; - if ( info.ButtonID != 0 && switches.Length > 0 ) - { - if ( m.HairItemID == 0 ) - { - m.SendLocalizedMessage( 502623 ); // You have no hair to dye and cannot use this - } - else - { - // To prevent this from being exploited, the hue is abstracted into an internal list + m.HairHue = hue; - int entryIndex = switches[0] / 100; - int hueOffset = switches[0] % 100; + m.SendLocalizedMessage(501199); // You dye your hair + m.PlaySound(0x4E); + } + } + } + } + else + { + m.SendLocalizedMessage(501200); // You decide not to dye your hair + } + } - if ( entryIndex >= 0 && entryIndex < m_Entries.Length ) - { - SpecialHairDyeEntry e = m_Entries[entryIndex]; + private class SpecialHairDyeEntry + { + public SpecialHairDyeEntry(string name, int hueStart, int hueCount) + { + Name = name; + HueStart = hueStart; + HueCount = hueCount; + } - if ( hueOffset >= 0 && hueOffset < e.HueCount ) - { - m_SpecialHairDye.Delete(); + public string Name{ get; } - int hue = e.HueStart + hueOffset; + public int HueStart{ get; } - m.HairHue = hue; - - m.SendLocalizedMessage( 501199 ); // You dye your hair - m.PlaySound( 0x4E ); - } - } - } - } - else - { - m.SendLocalizedMessage( 501200 ); // You decide not to dye your hair - } - } - } -} + public int HueCount{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Static.cs b/Scripts/Items/Misc/Static.cs index 85daa2d59..bac253619 100644 --- a/Scripts/Items/Misc/Static.cs +++ b/Scripts/Items/Misc/Static.cs @@ -1,95 +1,99 @@ namespace Server.Items { - public class Static : Item - { - public Static() : base( 0x80 ) - { - Movable = false; - } + public class Static : Item + { + public Static() : base(0x80) + { + Movable = false; + } - [Constructible] - public Static( int itemID ) : base( itemID ) - { - Movable = false; - } + [Constructible] + public Static(int itemID) : base(itemID) + { + Movable = false; + } - [Constructible] - public Static( int itemID, int count ) : this( Utility.Random( itemID, count ) ) - { - } + [Constructible] + public Static(int itemID, int count) : this(Utility.Random(itemID, count)) + { + } - public Static( Serial serial ) : base( serial ) - { - } + public Static(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && Weight == 0 ) - Weight = -1; - } - } + if (version == 0 && Weight == 0) + Weight = -1; + } + } - public class LocalizedStatic : Static - { - private int m_LabelNumber; + public class LocalizedStatic : Static + { + private int m_LabelNumber; - [CommandProperty( AccessLevel.GameMaster )] - public int Number - { - get => m_LabelNumber; - set{ m_LabelNumber = value; InvalidateProperties(); } - } + [Constructible] + public LocalizedStatic(int itemID) : this(itemID, itemID < 0x4000 ? 1020000 + itemID : 1078872 + itemID) + { + } - public override int LabelNumber => m_LabelNumber; + [Constructible] + public LocalizedStatic(int itemID, int labelNumber) : base(itemID) + { + m_LabelNumber = labelNumber; + } - [Constructible] - public LocalizedStatic( int itemID ) : this( itemID, itemID < 0x4000 ? 1020000 + itemID : 1078872 + itemID ) - { - } + public LocalizedStatic(Serial serial) : base(serial) + { + } - [Constructible] - public LocalizedStatic( int itemID, int labelNumber ) : base( itemID ) - { - m_LabelNumber = labelNumber; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Number + { + get => m_LabelNumber; + set + { + m_LabelNumber = value; + InvalidateProperties(); + } + } - public LocalizedStatic( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => m_LabelNumber; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (byte) 0 ); // version - writer.WriteEncodedInt( (int) m_LabelNumber ); - } + writer.Write((byte)0); // version + writer.WriteEncodedInt(m_LabelNumber); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadByte(); + int version = reader.ReadByte(); - switch ( version ) - { - case 0: - { - m_LabelNumber = reader.ReadEncodedInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + m_LabelNumber = reader.ReadEncodedInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/SwarmOfFlies.cs b/Scripts/Items/Misc/SwarmOfFlies.cs index 1fb1488e5..d8c0e00db 100644 --- a/Scripts/Items/Misc/SwarmOfFlies.cs +++ b/Scripts/Items/Misc/SwarmOfFlies.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class SwarmOfFlies : Item - { - public override string DefaultName => "a swarm of flies"; + public class SwarmOfFlies : Item + { + [Constructible] + public SwarmOfFlies() : base(0x91B) + { + Hue = 1; + Movable = false; + } - [Constructible] - public SwarmOfFlies() : base( 0x91B ) - { - Hue = 1; - Movable = false; - } + public SwarmOfFlies(Serial serial) : base(serial) + { + } - public SwarmOfFlies( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a swarm of flies"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/Teleporter.cs b/Scripts/Items/Misc/Teleporter.cs index a8c0541e3..f26849eb9 100644 --- a/Scripts/Items/Misc/Teleporter.cs +++ b/Scripts/Items/Misc/Teleporter.cs @@ -7,1095 +7,1198 @@ using Server.Spells; namespace Server.Items { - public class Teleporter : Item - { - private bool m_Active, m_Creatures, m_CombatCheck, m_CriminalCheck; - private Point3D m_PointDest; - private Map m_MapDest; - private bool m_SourceEffect; - private bool m_DestEffect; - private int m_SoundID; - private TimeSpan m_Delay; - - [CommandProperty(AccessLevel.GameMaster)] - public bool SourceEffect - { - get => m_SourceEffect; - set { m_SourceEffect = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DestEffect - { - get => m_DestEffect; - set { m_DestEffect = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int SoundID - { - get => m_SoundID; - set { m_SoundID = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public TimeSpan Delay - { - get => m_Delay; - set { m_Delay = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool Active - { - get => m_Active; - set { m_Active = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public Point3D PointDest - { - get => m_PointDest; - set { m_PointDest = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public Map MapDest - { - get => m_MapDest; - set { m_MapDest = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool Creatures - { - get => m_Creatures; - set { m_Creatures = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool CombatCheck - { - get => m_CombatCheck; - set { m_CombatCheck = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool CriminalCheck - { - get => m_CriminalCheck; - set { m_CriminalCheck = value; InvalidateProperties(); } - } - - public override int LabelNumber => 1026095; // teleporter - - [Constructible] - public Teleporter() - : this(new Point3D(0, 0, 0), null, false) - { - } - - [Constructible] - public Teleporter(Point3D pointDest, Map mapDest) - : this(pointDest, mapDest, false) - { - } - - [Constructible] - public Teleporter(Point3D pointDest, Map mapDest, bool creatures) - : base(0x1BC3) - { - Movable = false; - Visible = false; - - m_Active = true; - m_PointDest = pointDest; - m_MapDest = mapDest; - m_Creatures = creatures; - - m_CombatCheck = false; - m_CriminalCheck = false; - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - if (m_Active) - list.Add(1060742); // active - else - list.Add(1060743); // inactive - - if (m_MapDest != null) - list.Add(1060658, "Map\t{0}", m_MapDest); - - if (m_PointDest != Point3D.Zero) - list.Add(1060659, "Coords\t{0}", m_PointDest); - - list.Add(1060660, "Creatures\t{0}", m_Creatures ? "Yes" : "No"); - } - - public override void OnSingleClick(Mobile from) - { - base.OnSingleClick(from); - - if (m_Active) - { - if (m_MapDest != null && m_PointDest != Point3D.Zero) - LabelTo(from, "{0} [{1}]", m_PointDest, m_MapDest); - else if (m_MapDest != null) - LabelTo(from, "[{0}]", m_MapDest); - else if (m_PointDest != Point3D.Zero) - LabelTo(from, m_PointDest.ToString()); - } - else - { - LabelTo(from, "(inactive)"); - } - } - - public virtual bool CanTeleport(Mobile m) - { - if (!m_Creatures && !m.Player) - { - return false; - } - - if (m_CriminalCheck && m.Criminal) - { - m.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. - return false; - } - if (m_CombatCheck && SpellHelper.CheckCombat(m)) - { - m.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? - return false; - } - - return true; - } - - public virtual void StartTeleport(Mobile m) - { - if (m_Delay == TimeSpan.Zero) - DoTeleport(m); - else - Timer.DelayCall(m_Delay, DoTeleport, m); - } - - public virtual void DoTeleport(Mobile m) - { - Map map = m_MapDest; - - if (map == null || map == Map.Internal) - map = m.Map; - - Point3D p = m_PointDest; - - if (p == Point3D.Zero) - p = m.Location; - - BaseCreature.TeleportPets(m, p, map); - - bool sendEffect = (!m.Hidden || m.AccessLevel == AccessLevel.Player); - - if (m_SourceEffect && sendEffect) - Effects.SendLocationEffect(m.Location, m.Map, 0x3728, 10, 10); - - m.MoveToWorld(p, map); - - if (m_DestEffect && sendEffect) - Effects.SendLocationEffect(m.Location, m.Map, 0x3728, 10, 10); - - if (m_SoundID > 0 && sendEffect) - Effects.PlaySound(m.Location, m.Map, m_SoundID); - } - - public override bool OnMoveOver(Mobile m) - { - if (m_Active && CanTeleport(m)) - { - StartTeleport(m); - return false; - } - - return true; - } - - public Teleporter(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)4); // version - - writer.Write((bool)m_CriminalCheck); - writer.Write((bool)m_CombatCheck); - - writer.Write((bool)m_SourceEffect); - writer.Write((bool)m_DestEffect); - writer.Write((TimeSpan)m_Delay); - writer.WriteEncodedInt((int)m_SoundID); - - writer.Write(m_Creatures); - - writer.Write(m_Active); - writer.Write(m_PointDest); - writer.Write(m_MapDest); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 4: - { - m_CriminalCheck = reader.ReadBool(); - goto case 3; - } - case 3: - { - m_CombatCheck = reader.ReadBool(); - goto case 2; - } - case 2: - { - m_SourceEffect = reader.ReadBool(); - m_DestEffect = reader.ReadBool(); - m_Delay = reader.ReadTimeSpan(); - m_SoundID = reader.ReadEncodedInt(); - - goto case 1; - } - case 1: - { - m_Creatures = reader.ReadBool(); - - goto case 0; - } - case 0: - { - m_Active = reader.ReadBool(); - m_PointDest = reader.ReadPoint3D(); - m_MapDest = reader.ReadMap(); - - break; - } - } - } - } - - public class SkillTeleporter : Teleporter - { - private SkillName m_Skill; - private double m_Required; - private string m_MessageString; - private int m_MessageNumber; - - [CommandProperty(AccessLevel.GameMaster)] - public SkillName Skill - { - get => m_Skill; - set { m_Skill = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public double Required - { - get => m_Required; - set { m_Required = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public string MessageString - { - get => m_MessageString; - set { m_MessageString = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int MessageNumber - { - get => m_MessageNumber; - set { m_MessageNumber = value; InvalidateProperties(); } - } - - private void EndMessageLock(object state) - { - ((Mobile)state).EndAction(this); - } - - public override bool CanTeleport(Mobile m) - { - if (!base.CanTeleport(m)) - return false; - - Skill sk = m.Skills[m_Skill]; - - if (sk == null || sk.Base < m_Required) - { - if (m.BeginAction(this)) - { - if (m_MessageString != null) - m.Send(new UnicodeMessage(Serial, ItemID, MessageType.Regular, 0x3B2, 3, "ENU", null, m_MessageString)); - else if (m_MessageNumber != 0) - m.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, m_MessageNumber, null, "")); - - Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(EndMessageLock), m); - } - - return false; - } - - return true; - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - int skillIndex = (int)m_Skill; - string skillName; - - if (skillIndex >= 0 && skillIndex < SkillInfo.Table.Length) - skillName = SkillInfo.Table[skillIndex].Name; - else - skillName = "(Invalid)"; - - list.Add(1060661, "{0}\t{1:F1}", skillName, m_Required); - - if (m_MessageString != null) - list.Add(1060662, "Message\t{0}", m_MessageString); - else if (m_MessageNumber != 0) - list.Add(1060662, "Message\t#{0}", m_MessageNumber); - } - - [Constructible] - public SkillTeleporter() - { - } - - public SkillTeleporter(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - - writer.Write((int)m_Skill); - writer.Write((double)m_Required); - writer.Write((string)m_MessageString); - writer.Write((int)m_MessageNumber); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 0: - { - m_Skill = (SkillName)reader.ReadInt(); - m_Required = reader.ReadDouble(); - m_MessageString = reader.ReadString(); - m_MessageNumber = reader.ReadInt(); - - break; - } - } - } - } - - public class KeywordTeleporter : Teleporter - { - private string m_Substring; - private int m_Keyword; - private int m_Range; - - [CommandProperty(AccessLevel.GameMaster)] - public string Substring - { - get => m_Substring; - set { m_Substring = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int Keyword - { - get => m_Keyword; - set { m_Keyword = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int Range - { - get => m_Range; - set { m_Range = value; InvalidateProperties(); } - } - - public override bool HandlesOnSpeech => true; - - public override void OnSpeech(SpeechEventArgs e) - { - if (!e.Handled && Active) - { - Mobile m = e.Mobile; - - if (!m.InRange(GetWorldLocation(), m_Range)) - return; - - bool isMatch = false; - - if (m_Keyword >= 0 && e.HasKeyword(m_Keyword)) - isMatch = true; - else if (m_Substring != null && e.Speech.ToLower().IndexOf(m_Substring.ToLower()) >= 0) - isMatch = true; - - if (!isMatch || !CanTeleport(m)) - return; - - e.Handled = true; - StartTeleport(m); - } - } - - public override void DoTeleport(Mobile m) - { - if (!m.InRange(GetWorldLocation(), m_Range) || m.Map != Map) - return; - - base.DoTeleport(m); - } - - public override bool OnMoveOver(Mobile m) - { - return true; - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - list.Add(1060661, "Range\t{0}", m_Range); - - if (m_Keyword >= 0) - list.Add(1060662, "Keyword\t{0}", m_Keyword); - - if (m_Substring != null) - list.Add(1060663, "Substring\t{0}", m_Substring); - } - - [Constructible] - public KeywordTeleporter() - { - m_Keyword = -1; - m_Substring = null; - } - - public KeywordTeleporter(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - - writer.Write(m_Substring); - writer.Write(m_Keyword); - writer.Write(m_Range); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 0: - { - m_Substring = reader.ReadString(); - m_Keyword = reader.ReadInt(); - m_Range = reader.ReadInt(); - - break; - } - } - } - } - - public class WaitTeleporter : KeywordTeleporter - { - private static Dictionary m_Table; - - public static void Initialize() - { - m_Table = new Dictionary(); - - EventSink.Logout += EventSink_Logout; - } - - public static void EventSink_Logout(LogoutEventArgs e) - { - Mobile from = e.Mobile; - - if (from == null || !m_Table.TryGetValue(from, out TeleportingInfo info)) - return; - - info.Timer.Stop(); - m_Table.Remove(from); - } - - [CommandProperty(AccessLevel.GameMaster)] - public int StartNumber { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public string StartMessage { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public int ProgressNumber { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public string ProgressMessage { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public bool ShowTimeRemaining { get; set; } - - [Constructible] - public WaitTeleporter() - { - } - - public static string FormatTime(TimeSpan ts) - { - if (ts.TotalHours >= 1) - { - int h = (int)Math.Round(ts.TotalHours); - return $"{h} hour{((h == 1) ? "" : "s")}"; - } - - if (ts.TotalMinutes >= 1) - { - int m = (int)Math.Round(ts.TotalMinutes); - return $"{m} minute{((m == 1) ? "" : "s")}"; - } - - int s = Math.Max((int)Math.Round(ts.TotalSeconds), 0); - return $"{s} second{((s == 1) ? "" : "s")}"; - } - - private void EndLock(Mobile m) - { - m.EndAction(this); - } - - public override void StartTeleport(Mobile m) - { - if (m_Table.TryGetValue( m, out TeleportingInfo info )) - { - if (info.Teleporter == this) - { - if (m.BeginAction(this)) - { - if (ProgressMessage != null) - m.SendMessage(ProgressMessage); - else if (ProgressNumber != 0) - m.SendLocalizedMessage(ProgressNumber); - - if (ShowTimeRemaining) - m.SendMessage("Time remaining: {0}", FormatTime(m_Table[m].Timer.Next - DateTime.UtcNow)); - - Timer.DelayCall(TimeSpan.FromSeconds(5), EndLock, m); - } - - return; - } - - info.Timer.Stop(); - } - - if (StartMessage != null) - m.SendMessage(StartMessage); - else if (StartNumber != 0) - m.SendLocalizedMessage(StartNumber); - - if (Delay == TimeSpan.Zero) - DoTeleport(m); - else - m_Table[m] = new TeleportingInfo(this, Timer.DelayCall(Delay, DoTeleport, m)); - } - - public override void DoTeleport(Mobile m) - { - m_Table.Remove(m); - - base.DoTeleport(m); - } - - public WaitTeleporter(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - - writer.Write(StartNumber); - writer.Write(StartMessage); - writer.Write(ProgressNumber); - writer.Write(ProgressMessage); - writer.Write(ShowTimeRemaining); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - StartNumber = reader.ReadInt(); - StartMessage = reader.ReadString(); - ProgressNumber = reader.ReadInt(); - ProgressMessage = reader.ReadString(); - ShowTimeRemaining = reader.ReadBool(); - } - - private class TeleportingInfo - { - public WaitTeleporter Teleporter { get; } - - public Timer Timer { get; } - - public TeleportingInfo(WaitTeleporter tele, Timer t) - { - Teleporter = tele; - Timer = t; - } - } - } - - public class TimeoutTeleporter : Teleporter - { - private Dictionary m_Teleporting; - - [CommandProperty(AccessLevel.GameMaster)] - public TimeSpan TimeoutDelay { get; set; } - - [Constructible] - public TimeoutTeleporter() - : this(new Point3D(0, 0, 0), null, false) - { - } - - [Constructible] - public TimeoutTeleporter(Point3D pointDest, Map mapDest) - : this(pointDest, mapDest, false) - { - } - - [Constructible] - public TimeoutTeleporter(Point3D pointDest, Map mapDest, bool creatures) - : base(pointDest, mapDest, creatures) - { - m_Teleporting = new Dictionary(); - } - - public void StartTimer(Mobile m) - { - StartTimer(m, TimeoutDelay); - } - - private void StartTimer(Mobile m, TimeSpan delay) - { - if (m_Teleporting.TryGetValue( m, out Timer t )) - t.Stop(); - - m_Teleporting[m] = Timer.DelayCall(delay, StartTeleport, m); - } - - public void StopTimer(Mobile m) - { - if (m_Teleporting.TryGetValue( m, out Timer t )) - { - t.Stop(); - m_Teleporting.Remove(m); - } - } - - public override void DoTeleport(Mobile m) - { - m_Teleporting.Remove(m); - - base.DoTeleport(m); - } - - public override bool OnMoveOver(Mobile m) - { - if (Active) - { - if (!CanTeleport(m)) - return false; - - StartTimer(m); - } - - return true; - } - - public TimeoutTeleporter(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - - writer.Write(TimeoutDelay); - writer.Write(m_Teleporting.Count); - - foreach (KeyValuePair kvp in m_Teleporting) - { - writer.Write(kvp.Key); - writer.Write(kvp.Value.Next); - } - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - TimeoutDelay = reader.ReadTimeSpan(); - m_Teleporting = new Dictionary(); - - int count = reader.ReadInt(); - - for (int i = 0; i < count; ++i) - { - Mobile m = reader.ReadMobile(); - DateTime end = reader.ReadDateTime(); - - StartTimer(m, end - DateTime.UtcNow); - } - } - } - - public class TimeoutGoal : Item - { - [CommandProperty(AccessLevel.GameMaster)] - public TimeoutTeleporter Teleporter { get; set; } - - [Constructible] - public TimeoutGoal() - : base(0x1822) - { - Movable = false; - Visible = false; - - Hue = 1154; - } - - public override bool OnMoveOver(Mobile m) - { - Teleporter?.StopTimer(m); - - return true; - } - - public override string DefaultName => "timeout teleporter goal"; - - public TimeoutGoal(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - - writer.WriteItem(Teleporter); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - Teleporter = reader.ReadItem(); - } - } - - public class ConditionTeleporter : Teleporter - { - [Flags] - protected enum ConditionFlag - { - None = 0x000, - DenyMounted = 0x001, - DenyFollowers = 0x002, - DenyPackContents = 0x004, - DenyHolding = 0x008, - DenyEquipment = 0x010, - DenyTransformed = 0x020, - StaffOnly = 0x040, - DenyPackEthereals = 0x080, - DeadOnly = 0x100 - } - - private ConditionFlag m_Flags; - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyMounted - { - get => GetFlag(ConditionFlag.DenyMounted); - set { SetFlag(ConditionFlag.DenyMounted, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyFollowers - { - get => GetFlag(ConditionFlag.DenyFollowers); - set { SetFlag(ConditionFlag.DenyFollowers, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyPackContents - { - get => GetFlag(ConditionFlag.DenyPackContents); - set { SetFlag(ConditionFlag.DenyPackContents, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyHolding - { - get => GetFlag(ConditionFlag.DenyHolding); - set { SetFlag(ConditionFlag.DenyHolding, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyEquipment - { - get => GetFlag(ConditionFlag.DenyEquipment); - set { SetFlag(ConditionFlag.DenyEquipment, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyTransformed - { - get => GetFlag(ConditionFlag.DenyTransformed); - set { SetFlag(ConditionFlag.DenyTransformed, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool StaffOnly - { - get => GetFlag(ConditionFlag.StaffOnly); - set { SetFlag(ConditionFlag.StaffOnly, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DenyPackEthereals - { - get => GetFlag(ConditionFlag.DenyPackEthereals); - set { SetFlag(ConditionFlag.DenyPackEthereals, value); InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool DeadOnly - { - get => GetFlag(ConditionFlag.DeadOnly); - set { SetFlag(ConditionFlag.DeadOnly, value); InvalidateProperties(); } - } - - public override bool CanTeleport(Mobile m) - { - if (!base.CanTeleport(m)) - return false; - - if (GetFlag(ConditionFlag.StaffOnly) && m.AccessLevel < AccessLevel.Counselor) - return false; - - if (GetFlag(ConditionFlag.DenyMounted) && m.Mounted) - { - m.SendLocalizedMessage(1077252); // You must dismount before proceeding. - return false; - } - - if (GetFlag(ConditionFlag.DenyFollowers) && (m.Followers != 0 || (m is PlayerMobile mobile && mobile.AutoStabled.Count != 0))) - { - m.SendLocalizedMessage(1077250); // No pets permitted beyond this point. - return false; - } - - Container pack = m.Backpack; - - if (pack != null) - { - if (GetFlag(ConditionFlag.DenyPackContents) && pack.TotalItems != 0) - { - m.SendMessage("You must empty your backpack before proceeding."); - return false; - } - - if (GetFlag(ConditionFlag.DenyPackEthereals) && (pack.FindItemByType(typeof(EtherealMount)) != null || pack.FindItemByType(typeof(BaseImprisonedMobile)) != null)) - { - m.SendMessage("You must empty your backpack of ethereal mounts before proceeding."); - return false; - } - } - - if (GetFlag(ConditionFlag.DenyHolding) && m.Holding != null) - { - m.SendMessage("You must let go of what you are holding before proceeding."); - return false; - } - - if (GetFlag(ConditionFlag.DenyEquipment)) - { - foreach (Item item in m.Items) - { - switch (item.Layer) - { - case Layer.Hair: - case Layer.FacialHair: - case Layer.Backpack: - case Layer.Mount: - case Layer.Bank: - { - continue; // ignore - } - default: - { - m.SendMessage("You must remove all of your equipment before proceeding."); - return false; - } - } - } - } - - if (GetFlag(ConditionFlag.DenyTransformed) && m.IsBodyMod) - { - m.SendMessage("You cannot go there in this form."); - return false; - } - - if (GetFlag(ConditionFlag.DeadOnly) && m.Alive) - { - m.SendLocalizedMessage(1060014); // Only the dead may pass. - return false; - } - - return true; - } - - [Constructible] - public ConditionTeleporter() - { - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - StringBuilder props = new StringBuilder(); - - if (GetFlag(ConditionFlag.DenyMounted)) - props.Append("
Deny Mounted"); - - if (GetFlag(ConditionFlag.DenyFollowers)) - props.Append("
Deny Followers"); - - if (GetFlag(ConditionFlag.DenyPackContents)) - props.Append("
Deny Pack Contents"); - - if (GetFlag(ConditionFlag.DenyPackEthereals)) - props.Append("
Deny Pack Ethereals"); - - if (GetFlag(ConditionFlag.DenyHolding)) - props.Append("
Deny Holding"); - - if (GetFlag(ConditionFlag.DenyEquipment)) - props.Append("
Deny Equipment"); - - if (GetFlag(ConditionFlag.DenyTransformed)) - props.Append("
Deny Transformed"); - - if (GetFlag(ConditionFlag.StaffOnly)) - props.Append("
Staff Only"); - - if (GetFlag(ConditionFlag.DeadOnly)) - props.Append("
Dead Only"); - - if (props.Length != 0) - { - props.Remove(0, 4); - list.Add(props.ToString()); - } - } - - public ConditionTeleporter(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - - writer.Write((int)m_Flags); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - m_Flags = (ConditionFlag)reader.ReadInt(); - } - - protected bool GetFlag(ConditionFlag flag) - { - return ((m_Flags & flag) != 0); - } - - protected void SetFlag(ConditionFlag flag, bool value) - { - if (value) - m_Flags |= flag; - else - m_Flags &= ~flag; - } - } -} + public class Teleporter : Item + { + private bool m_Active, m_Creatures, m_CombatCheck, m_CriminalCheck; + private TimeSpan m_Delay; + private bool m_DestEffect; + private Map m_MapDest; + private Point3D m_PointDest; + private int m_SoundID; + private bool m_SourceEffect; + + [Constructible] + public Teleporter() + : this(new Point3D(0, 0, 0), null, false) + { + } + + [Constructible] + public Teleporter(Point3D pointDest, Map mapDest) + : this(pointDest, mapDest, false) + { + } + + [Constructible] + public Teleporter(Point3D pointDest, Map mapDest, bool creatures) + : base(0x1BC3) + { + Movable = false; + Visible = false; + + m_Active = true; + m_PointDest = pointDest; + m_MapDest = mapDest; + m_Creatures = creatures; + + m_CombatCheck = false; + m_CriminalCheck = false; + } + + public Teleporter(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool SourceEffect + { + get => m_SourceEffect; + set + { + m_SourceEffect = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DestEffect + { + get => m_DestEffect; + set + { + m_DestEffect = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SoundID + { + get => m_SoundID; + set + { + m_SoundID = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan Delay + { + get => m_Delay; + set + { + m_Delay = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Active + { + get => m_Active; + set + { + m_Active = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D PointDest + { + get => m_PointDest; + set + { + m_PointDest = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Map MapDest + { + get => m_MapDest; + set + { + m_MapDest = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Creatures + { + get => m_Creatures; + set + { + m_Creatures = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool CombatCheck + { + get => m_CombatCheck; + set + { + m_CombatCheck = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool CriminalCheck + { + get => m_CriminalCheck; + set + { + m_CriminalCheck = value; + InvalidateProperties(); + } + } + + public override int LabelNumber => 1026095; // teleporter + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Active) + list.Add(1060742); // active + else + list.Add(1060743); // inactive + + if (m_MapDest != null) + list.Add(1060658, "Map\t{0}", m_MapDest); + + if (m_PointDest != Point3D.Zero) + list.Add(1060659, "Coords\t{0}", m_PointDest); + + list.Add(1060660, "Creatures\t{0}", m_Creatures ? "Yes" : "No"); + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (m_Active) + { + if (m_MapDest != null && m_PointDest != Point3D.Zero) + LabelTo(from, "{0} [{1}]", m_PointDest, m_MapDest); + else if (m_MapDest != null) + LabelTo(from, "[{0}]", m_MapDest); + else if (m_PointDest != Point3D.Zero) + LabelTo(from, m_PointDest.ToString()); + } + else + { + LabelTo(from, "(inactive)"); + } + } + + public virtual bool CanTeleport(Mobile m) + { + if (!m_Creatures && !m.Player) return false; + + if (m_CriminalCheck && m.Criminal) + { + m.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + return false; + } + + if (m_CombatCheck && SpellHelper.CheckCombat(m)) + { + m.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + return false; + } + + return true; + } + + public virtual void StartTeleport(Mobile m) + { + if (m_Delay == TimeSpan.Zero) + DoTeleport(m); + else + Timer.DelayCall(m_Delay, DoTeleport, m); + } + + public virtual void DoTeleport(Mobile m) + { + Map map = m_MapDest; + + if (map == null || map == Map.Internal) + map = m.Map; + + Point3D p = m_PointDest; + + if (p == Point3D.Zero) + p = m.Location; + + BaseCreature.TeleportPets(m, p, map); + + bool sendEffect = !m.Hidden || m.AccessLevel == AccessLevel.Player; + + if (m_SourceEffect && sendEffect) + Effects.SendLocationEffect(m.Location, m.Map, 0x3728, 10, 10); + + m.MoveToWorld(p, map); + + if (m_DestEffect && sendEffect) + Effects.SendLocationEffect(m.Location, m.Map, 0x3728, 10, 10); + + if (m_SoundID > 0 && sendEffect) + Effects.PlaySound(m.Location, m.Map, m_SoundID); + } + + public override bool OnMoveOver(Mobile m) + { + if (m_Active && CanTeleport(m)) + { + StartTeleport(m); + return false; + } + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(4); // version + + writer.Write(m_CriminalCheck); + writer.Write(m_CombatCheck); + + writer.Write(m_SourceEffect); + writer.Write(m_DestEffect); + writer.Write(m_Delay); + writer.WriteEncodedInt(m_SoundID); + + writer.Write(m_Creatures); + + writer.Write(m_Active); + writer.Write(m_PointDest); + writer.Write(m_MapDest); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 4: + { + m_CriminalCheck = reader.ReadBool(); + goto case 3; + } + case 3: + { + m_CombatCheck = reader.ReadBool(); + goto case 2; + } + case 2: + { + m_SourceEffect = reader.ReadBool(); + m_DestEffect = reader.ReadBool(); + m_Delay = reader.ReadTimeSpan(); + m_SoundID = reader.ReadEncodedInt(); + + goto case 1; + } + case 1: + { + m_Creatures = reader.ReadBool(); + + goto case 0; + } + case 0: + { + m_Active = reader.ReadBool(); + m_PointDest = reader.ReadPoint3D(); + m_MapDest = reader.ReadMap(); + + break; + } + } + } + } + + public class SkillTeleporter : Teleporter + { + private int m_MessageNumber; + private string m_MessageString; + private double m_Required; + private SkillName m_Skill; + + [Constructible] + public SkillTeleporter() + { + } + + public SkillTeleporter(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill + { + get => m_Skill; + set + { + m_Skill = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public double Required + { + get => m_Required; + set + { + m_Required = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string MessageString + { + get => m_MessageString; + set + { + m_MessageString = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MessageNumber + { + get => m_MessageNumber; + set + { + m_MessageNumber = value; + InvalidateProperties(); + } + } + + private void EndMessageLock(object state) + { + ((Mobile)state).EndAction(this); + } + + public override bool CanTeleport(Mobile m) + { + if (!base.CanTeleport(m)) + return false; + + Skill sk = m.Skills[m_Skill]; + + if (sk == null || sk.Base < m_Required) + { + if (m.BeginAction(this)) + { + if (m_MessageString != null) + m.Send(new UnicodeMessage(Serial, ItemID, MessageType.Regular, 0x3B2, 3, "ENU", null, + m_MessageString)); + else if (m_MessageNumber != 0) + m.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, m_MessageNumber, null, + "")); + + Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(EndMessageLock), m); + } + + return false; + } + + return true; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + int skillIndex = (int)m_Skill; + string skillName; + + if (skillIndex >= 0 && skillIndex < SkillInfo.Table.Length) + skillName = SkillInfo.Table[skillIndex].Name; + else + skillName = "(Invalid)"; + + list.Add(1060661, "{0}\t{1:F1}", skillName, m_Required); + + if (m_MessageString != null) + list.Add(1060662, "Message\t{0}", m_MessageString); + else if (m_MessageNumber != 0) + list.Add(1060662, "Message\t#{0}", m_MessageNumber); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write((int)m_Skill); + writer.Write(m_Required); + writer.Write(m_MessageString); + writer.Write(m_MessageNumber); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Skill = (SkillName)reader.ReadInt(); + m_Required = reader.ReadDouble(); + m_MessageString = reader.ReadString(); + m_MessageNumber = reader.ReadInt(); + + break; + } + } + } + } + + public class KeywordTeleporter : Teleporter + { + private int m_Keyword; + private int m_Range; + private string m_Substring; + + [Constructible] + public KeywordTeleporter() + { + m_Keyword = -1; + m_Substring = null; + } + + public KeywordTeleporter(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Substring + { + get => m_Substring; + set + { + m_Substring = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Keyword + { + get => m_Keyword; + set + { + m_Keyword = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Range + { + get => m_Range; + set + { + m_Range = value; + InvalidateProperties(); + } + } + + public override bool HandlesOnSpeech => true; + + public override void OnSpeech(SpeechEventArgs e) + { + if (!e.Handled && Active) + { + Mobile m = e.Mobile; + + if (!m.InRange(GetWorldLocation(), m_Range)) + return; + + bool isMatch = false; + + if (m_Keyword >= 0 && e.HasKeyword(m_Keyword)) + isMatch = true; + else if (m_Substring != null && e.Speech.ToLower().IndexOf(m_Substring.ToLower()) >= 0) + isMatch = true; + + if (!isMatch || !CanTeleport(m)) + return; + + e.Handled = true; + StartTeleport(m); + } + } + + public override void DoTeleport(Mobile m) + { + if (!m.InRange(GetWorldLocation(), m_Range) || m.Map != Map) + return; + + base.DoTeleport(m); + } + + public override bool OnMoveOver(Mobile m) + { + return true; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(1060661, "Range\t{0}", m_Range); + + if (m_Keyword >= 0) + list.Add(1060662, "Keyword\t{0}", m_Keyword); + + if (m_Substring != null) + list.Add(1060663, "Substring\t{0}", m_Substring); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Substring); + writer.Write(m_Keyword); + writer.Write(m_Range); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Substring = reader.ReadString(); + m_Keyword = reader.ReadInt(); + m_Range = reader.ReadInt(); + + break; + } + } + } + } + + public class WaitTeleporter : KeywordTeleporter + { + private static Dictionary m_Table; + + [Constructible] + public WaitTeleporter() + { + } + + public WaitTeleporter(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int StartNumber{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string StartMessage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ProgressNumber{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string ProgressMessage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool ShowTimeRemaining{ get; set; } + + public static void Initialize() + { + m_Table = new Dictionary(); + + EventSink.Logout += EventSink_Logout; + } + + public static void EventSink_Logout(LogoutEventArgs e) + { + Mobile from = e.Mobile; + + if (from == null || !m_Table.TryGetValue(from, out TeleportingInfo info)) + return; + + info.Timer.Stop(); + m_Table.Remove(from); + } + + public static string FormatTime(TimeSpan ts) + { + if (ts.TotalHours >= 1) + { + int h = (int)Math.Round(ts.TotalHours); + return $"{h} hour{(h == 1 ? "" : "s")}"; + } + + if (ts.TotalMinutes >= 1) + { + int m = (int)Math.Round(ts.TotalMinutes); + return $"{m} minute{(m == 1 ? "" : "s")}"; + } + + int s = Math.Max((int)Math.Round(ts.TotalSeconds), 0); + return $"{s} second{(s == 1 ? "" : "s")}"; + } + + private void EndLock(Mobile m) + { + m.EndAction(this); + } + + public override void StartTeleport(Mobile m) + { + if (m_Table.TryGetValue(m, out TeleportingInfo info)) + { + if (info.Teleporter == this) + { + if (m.BeginAction(this)) + { + if (ProgressMessage != null) + m.SendMessage(ProgressMessage); + else if (ProgressNumber != 0) + m.SendLocalizedMessage(ProgressNumber); + + if (ShowTimeRemaining) + m.SendMessage("Time remaining: {0}", FormatTime(m_Table[m].Timer.Next - DateTime.UtcNow)); + + Timer.DelayCall(TimeSpan.FromSeconds(5), EndLock, m); + } + + return; + } + + info.Timer.Stop(); + } + + if (StartMessage != null) + m.SendMessage(StartMessage); + else if (StartNumber != 0) + m.SendLocalizedMessage(StartNumber); + + if (Delay == TimeSpan.Zero) + DoTeleport(m); + else + m_Table[m] = new TeleportingInfo(this, Timer.DelayCall(Delay, DoTeleport, m)); + } + + public override void DoTeleport(Mobile m) + { + m_Table.Remove(m); + + base.DoTeleport(m); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(StartNumber); + writer.Write(StartMessage); + writer.Write(ProgressNumber); + writer.Write(ProgressMessage); + writer.Write(ShowTimeRemaining); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + StartNumber = reader.ReadInt(); + StartMessage = reader.ReadString(); + ProgressNumber = reader.ReadInt(); + ProgressMessage = reader.ReadString(); + ShowTimeRemaining = reader.ReadBool(); + } + + private class TeleportingInfo + { + public TeleportingInfo(WaitTeleporter tele, Timer t) + { + Teleporter = tele; + Timer = t; + } + + public WaitTeleporter Teleporter{ get; } + + public Timer Timer{ get; } + } + } + + public class TimeoutTeleporter : Teleporter + { + private Dictionary m_Teleporting; + + [Constructible] + public TimeoutTeleporter() + : this(new Point3D(0, 0, 0), null, false) + { + } + + [Constructible] + public TimeoutTeleporter(Point3D pointDest, Map mapDest) + : this(pointDest, mapDest, false) + { + } + + [Constructible] + public TimeoutTeleporter(Point3D pointDest, Map mapDest, bool creatures) + : base(pointDest, mapDest, creatures) + { + m_Teleporting = new Dictionary(); + } + + public TimeoutTeleporter(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan TimeoutDelay{ get; set; } + + public void StartTimer(Mobile m) + { + StartTimer(m, TimeoutDelay); + } + + private void StartTimer(Mobile m, TimeSpan delay) + { + if (m_Teleporting.TryGetValue(m, out Timer t)) + t.Stop(); + + m_Teleporting[m] = Timer.DelayCall(delay, StartTeleport, m); + } + + public void StopTimer(Mobile m) + { + if (m_Teleporting.TryGetValue(m, out Timer t)) + { + t.Stop(); + m_Teleporting.Remove(m); + } + } + + public override void DoTeleport(Mobile m) + { + m_Teleporting.Remove(m); + + base.DoTeleport(m); + } + + public override bool OnMoveOver(Mobile m) + { + if (Active) + { + if (!CanTeleport(m)) + return false; + + StartTimer(m); + } + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(TimeoutDelay); + writer.Write(m_Teleporting.Count); + + foreach (KeyValuePair kvp in m_Teleporting) + { + writer.Write(kvp.Key); + writer.Write(kvp.Value.Next); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + TimeoutDelay = reader.ReadTimeSpan(); + m_Teleporting = new Dictionary(); + + int count = reader.ReadInt(); + + for (int i = 0; i < count; ++i) + { + Mobile m = reader.ReadMobile(); + DateTime end = reader.ReadDateTime(); + + StartTimer(m, end - DateTime.UtcNow); + } + } + } + + public class TimeoutGoal : Item + { + [Constructible] + public TimeoutGoal() + : base(0x1822) + { + Movable = false; + Visible = false; + + Hue = 1154; + } + + public TimeoutGoal(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeoutTeleporter Teleporter{ get; set; } + + public override string DefaultName => "timeout teleporter goal"; + + public override bool OnMoveOver(Mobile m) + { + Teleporter?.StopTimer(m); + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.WriteItem(Teleporter); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Teleporter = reader.ReadItem(); + } + } + + public class ConditionTeleporter : Teleporter + { + private ConditionFlag m_Flags; + + [Constructible] + public ConditionTeleporter() + { + } + + public ConditionTeleporter(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyMounted + { + get => GetFlag(ConditionFlag.DenyMounted); + set + { + SetFlag(ConditionFlag.DenyMounted, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyFollowers + { + get => GetFlag(ConditionFlag.DenyFollowers); + set + { + SetFlag(ConditionFlag.DenyFollowers, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyPackContents + { + get => GetFlag(ConditionFlag.DenyPackContents); + set + { + SetFlag(ConditionFlag.DenyPackContents, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyHolding + { + get => GetFlag(ConditionFlag.DenyHolding); + set + { + SetFlag(ConditionFlag.DenyHolding, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyEquipment + { + get => GetFlag(ConditionFlag.DenyEquipment); + set + { + SetFlag(ConditionFlag.DenyEquipment, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyTransformed + { + get => GetFlag(ConditionFlag.DenyTransformed); + set + { + SetFlag(ConditionFlag.DenyTransformed, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool StaffOnly + { + get => GetFlag(ConditionFlag.StaffOnly); + set + { + SetFlag(ConditionFlag.StaffOnly, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DenyPackEthereals + { + get => GetFlag(ConditionFlag.DenyPackEthereals); + set + { + SetFlag(ConditionFlag.DenyPackEthereals, value); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DeadOnly + { + get => GetFlag(ConditionFlag.DeadOnly); + set + { + SetFlag(ConditionFlag.DeadOnly, value); + InvalidateProperties(); + } + } + + public override bool CanTeleport(Mobile m) + { + if (!base.CanTeleport(m)) + return false; + + if (GetFlag(ConditionFlag.StaffOnly) && m.AccessLevel < AccessLevel.Counselor) + return false; + + if (GetFlag(ConditionFlag.DenyMounted) && m.Mounted) + { + m.SendLocalizedMessage(1077252); // You must dismount before proceeding. + return false; + } + + if (GetFlag(ConditionFlag.DenyFollowers) && + (m.Followers != 0 || m is PlayerMobile mobile && mobile.AutoStabled.Count != 0)) + { + m.SendLocalizedMessage(1077250); // No pets permitted beyond this point. + return false; + } + + Container pack = m.Backpack; + + if (pack != null) + { + if (GetFlag(ConditionFlag.DenyPackContents) && pack.TotalItems != 0) + { + m.SendMessage("You must empty your backpack before proceeding."); + return false; + } + + if (GetFlag(ConditionFlag.DenyPackEthereals) && + (pack.FindItemByType(typeof(EtherealMount)) != null || + pack.FindItemByType(typeof(BaseImprisonedMobile)) != null)) + { + m.SendMessage("You must empty your backpack of ethereal mounts before proceeding."); + return false; + } + } + + if (GetFlag(ConditionFlag.DenyHolding) && m.Holding != null) + { + m.SendMessage("You must let go of what you are holding before proceeding."); + return false; + } + + if (GetFlag(ConditionFlag.DenyEquipment)) + foreach (Item item in m.Items) + switch (item.Layer) + { + case Layer.Hair: + case Layer.FacialHair: + case Layer.Backpack: + case Layer.Mount: + case Layer.Bank: + { + continue; // ignore + } + default: + { + m.SendMessage("You must remove all of your equipment before proceeding."); + return false; + } + } + + if (GetFlag(ConditionFlag.DenyTransformed) && m.IsBodyMod) + { + m.SendMessage("You cannot go there in this form."); + return false; + } + + if (GetFlag(ConditionFlag.DeadOnly) && m.Alive) + { + m.SendLocalizedMessage(1060014); // Only the dead may pass. + return false; + } + + return true; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + StringBuilder props = new StringBuilder(); + + if (GetFlag(ConditionFlag.DenyMounted)) + props.Append("
Deny Mounted"); + + if (GetFlag(ConditionFlag.DenyFollowers)) + props.Append("
Deny Followers"); + + if (GetFlag(ConditionFlag.DenyPackContents)) + props.Append("
Deny Pack Contents"); + + if (GetFlag(ConditionFlag.DenyPackEthereals)) + props.Append("
Deny Pack Ethereals"); + + if (GetFlag(ConditionFlag.DenyHolding)) + props.Append("
Deny Holding"); + + if (GetFlag(ConditionFlag.DenyEquipment)) + props.Append("
Deny Equipment"); + + if (GetFlag(ConditionFlag.DenyTransformed)) + props.Append("
Deny Transformed"); + + if (GetFlag(ConditionFlag.StaffOnly)) + props.Append("
Staff Only"); + + if (GetFlag(ConditionFlag.DeadOnly)) + props.Append("
Dead Only"); + + if (props.Length != 0) + { + props.Remove(0, 4); + list.Add(props.ToString()); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write((int)m_Flags); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Flags = (ConditionFlag)reader.ReadInt(); + } + + protected bool GetFlag(ConditionFlag flag) + { + return (m_Flags & flag) != 0; + } + + protected void SetFlag(ConditionFlag flag, bool value) + { + if (value) + m_Flags |= flag; + else + m_Flags &= ~flag; + } + + [Flags] + protected enum ConditionFlag + { + None = 0x000, + DenyMounted = 0x001, + DenyFollowers = 0x002, + DenyPackContents = 0x004, + DenyHolding = 0x008, + DenyEquipment = 0x010, + DenyTransformed = 0x020, + StaffOnly = 0x040, + DenyPackEthereals = 0x080, + DeadOnly = 0x100 + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/DragonFlameSectBadge.cs b/Scripts/Items/Misc/The Citadel/DragonFlameSectBadge.cs index 49c7b0b32..26161790b 100644 --- a/Scripts/Items/Misc/The Citadel/DragonFlameSectBadge.cs +++ b/Scripts/Items/Misc/The Citadel/DragonFlameSectBadge.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class DragonFlameSectBadge : Item - { - public override int LabelNumber => 1073141; // A Dragon Flame Sect Badge + public class DragonFlameSectBadge : Item + { + [Constructible] + public DragonFlameSectBadge() : base(0x23E) + { + LootType = LootType.Blessed; + } - [Constructible] - public DragonFlameSectBadge() : base( 0x23E ) - { - LootType = LootType.Blessed; - } + public DragonFlameSectBadge(Serial serial) : base(serial) + { + } - public DragonFlameSectBadge( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073141; // A Dragon Flame Sect Badge - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/OrdersFromMinax.cs b/Scripts/Items/Misc/The Citadel/OrdersFromMinax.cs index 7911209eb..020fe0383 100644 --- a/Scripts/Items/Misc/The Citadel/OrdersFromMinax.cs +++ b/Scripts/Items/Misc/The Citadel/OrdersFromMinax.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class OrdersFromMinax : Item - { - public override int LabelNumber => 1074639; // Orders from Minax + public class OrdersFromMinax : Item + { + [Constructible] + public OrdersFromMinax() : base(0x2279) + { + LootType = LootType.Blessed; + } - [Constructible] - public OrdersFromMinax() : base( 0x2279 ) - { - LootType = LootType.Blessed; - } + public OrdersFromMinax(Serial serial) : base(serial) + { + } - public OrdersFromMinax( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074639; // Orders from Minax - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/SerpentFangSectBadge.cs b/Scripts/Items/Misc/The Citadel/SerpentFangSectBadge.cs index 87ec2095b..ab7068d86 100644 --- a/Scripts/Items/Misc/The Citadel/SerpentFangSectBadge.cs +++ b/Scripts/Items/Misc/The Citadel/SerpentFangSectBadge.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class SerpentFangSectBadge : Item - { - public override int LabelNumber => 1073139; // A Serpent Fang Sect Badge + public class SerpentFangSectBadge : Item + { + [Constructible] + public SerpentFangSectBadge() : base(0x23C) + { + LootType = LootType.Blessed; + } - [Constructible] - public SerpentFangSectBadge() : base( 0x23C ) - { - LootType = LootType.Blessed; - } + public SerpentFangSectBadge(Serial serial) : base(serial) + { + } - public SerpentFangSectBadge( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073139; // A Serpent Fang Sect Badge - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/TigerClawSectBadge.cs b/Scripts/Items/Misc/The Citadel/TigerClawSectBadge.cs index ffe24a994..fc3b855c9 100644 --- a/Scripts/Items/Misc/The Citadel/TigerClawSectBadge.cs +++ b/Scripts/Items/Misc/The Citadel/TigerClawSectBadge.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class TigerClawSectBadge : Item - { - public override int LabelNumber => 1073140; // A Tiger Claw Sect Badge + public class TigerClawSectBadge : Item + { + [Constructible] + public TigerClawSectBadge() : base(0x23D) + { + LootType = LootType.Blessed; + } - [Constructible] - public TigerClawSectBadge() : base( 0x23D ) - { - LootType = LootType.Blessed; - } + public TigerClawSectBadge(Serial serial) : base(serial) + { + } - public TigerClawSectBadge( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073140; // A Tiger Claw Sect Badge - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/TravestysCollectionOfShells.cs b/Scripts/Items/Misc/The Citadel/TravestysCollectionOfShells.cs index d1d87399a..04738559c 100644 --- a/Scripts/Items/Misc/The Citadel/TravestysCollectionOfShells.cs +++ b/Scripts/Items/Misc/The Citadel/TravestysCollectionOfShells.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class TravestysCollectionOfShells : Item - { - public override int LabelNumber => 1072090; // Travesty's Collection of Shells + public class TravestysCollectionOfShells : Item + { + [Constructible] + public TravestysCollectionOfShells() : base(0xFD3) + { + } - [Constructible] - public TravestysCollectionOfShells() : base( 0xFD3 ) - { - } + public TravestysCollectionOfShells(Serial serial) : base(serial) + { + } - public TravestysCollectionOfShells( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072090; // Travesty's Collection of Shells - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/TravestysFineTeakwoodTray.cs b/Scripts/Items/Misc/The Citadel/TravestysFineTeakwoodTray.cs index df201d06d..94b4996ed 100644 --- a/Scripts/Items/Misc/The Citadel/TravestysFineTeakwoodTray.cs +++ b/Scripts/Items/Misc/The Citadel/TravestysFineTeakwoodTray.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class TravestysFineTeakwoodTray : Item - { - public override int LabelNumber => 1075094; // Travesty's Fine Teakwood Tray + public class TravestysFineTeakwoodTray : Item + { + [Constructible] + public TravestysFineTeakwoodTray() : base(Utility.Random(0x991, 2)) + { + } - [Constructible] - public TravestysFineTeakwoodTray() : base( Utility.Random( 0x991, 2 ) ) - { - } + public TravestysFineTeakwoodTray(Serial serial) : base(serial) + { + } - public TravestysFineTeakwoodTray( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075094; // Travesty's Fine Teakwood Tray - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/The Citadel/TravestysSushiPreparations.cs b/Scripts/Items/Misc/The Citadel/TravestysSushiPreparations.cs index 80dc45133..315f16ba0 100644 --- a/Scripts/Items/Misc/The Citadel/TravestysSushiPreparations.cs +++ b/Scripts/Items/Misc/The Citadel/TravestysSushiPreparations.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class TravestysSushiPreparations : Item - { - public override int LabelNumber => 1075093; // Travesty's Sushi Preparations + public class TravestysSushiPreparations : Item + { + [Constructible] + public TravestysSushiPreparations() : base(Utility.Random(0x1E15, 2)) + { + } - [Constructible] - public TravestysSushiPreparations() : base( Utility.Random( 0x1E15, 2 ) ) - { - } + public TravestysSushiPreparations(Serial serial) : base(serial) + { + } - public TravestysSushiPreparations( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075093; // Travesty's Sushi Preparations - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/TrashBarrel.cs b/Scripts/Items/Misc/TrashBarrel.cs index e00e1d32a..7913851ff 100644 --- a/Scripts/Items/Misc/TrashBarrel.cs +++ b/Scripts/Items/Misc/TrashBarrel.cs @@ -1,146 +1,147 @@ using System; using System.Collections.Generic; using Server.Multis; +using Server.Network; namespace Server.Items { - public class TrashBarrel : Container, IChopable - { - public override int LabelNumber => 1041064; // a trash barrel + public class TrashBarrel : Container, IChopable + { + private Timer m_Timer; - public override int DefaultMaxWeight => 0; // A value of 0 signals unlimited weight + [Constructible] + public TrashBarrel() : base(0xE77) + { + Hue = 0x3B2; + Movable = false; + } - public override bool IsDecoContainer => false; + public TrashBarrel(Serial serial) : base(serial) + { + } - [Constructible] - public TrashBarrel() : base( 0xE77 ) - { - Hue = 0x3B2; - Movable = false; - } + public override int LabelNumber => 1041064; // a trash barrel - public TrashBarrel( Serial serial ) : base( serial ) - { - } + public override int DefaultMaxWeight => 0; // A value of 0 signals unlimited weight - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool IsDecoContainer => false; - writer.Write( (int) 0 ); // version - } + public void OnChop(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (house != null && house.IsCoOwner(from)) + { + Effects.PlaySound(Location, Map, 0x3B3); + from.SendLocalizedMessage(500461); // You destroy the item. + Destroy(); + } + } - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( Items.Count > 0 ) - { - m_Timer = new EmptyTimer( this ); - m_Timer.Start(); - } - } + writer.Write(0); // version + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( !base.OnDragDrop( from, dropped ) ) - return false; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( TotalItems >= 50 ) - { - Empty( 501478 ); // The trash is full! Emptying! - } - else - { - SendLocalizedMessageTo( from, 1010442 ); // The item will be deleted in three minutes + int version = reader.ReadInt(); - if ( m_Timer != null ) - m_Timer.Stop(); - else - m_Timer = new EmptyTimer( this ); + if (Items.Count > 0) + { + m_Timer = new EmptyTimer(this); + m_Timer.Start(); + } + } - m_Timer.Start(); - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (!base.OnDragDrop(from, dropped)) + return false; - return true; - } + if (TotalItems >= 50) + { + Empty(501478); // The trash is full! Emptying! + } + else + { + SendLocalizedMessageTo(from, 1010442); // The item will be deleted in three minutes - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( !base.OnDragDropInto( from, item, p ) ) - return false; + if (m_Timer != null) + m_Timer.Stop(); + else + m_Timer = new EmptyTimer(this); - if ( TotalItems >= 50 ) - { - Empty( 501478 ); // The trash is full! Emptying! - } - else - { - SendLocalizedMessageTo( from, 1010442 ); // The item will be deleted in three minutes + m_Timer.Start(); + } - if ( m_Timer != null ) - m_Timer.Stop(); - else - m_Timer = new EmptyTimer( this ); + return true; + } - m_Timer.Start(); - } + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (!base.OnDragDropInto(from, item, p)) + return false; - return true; - } + if (TotalItems >= 50) + { + Empty(501478); // The trash is full! Emptying! + } + else + { + SendLocalizedMessageTo(from, 1010442); // The item will be deleted in three minutes - public void OnChop( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (m_Timer != null) + m_Timer.Stop(); + else + m_Timer = new EmptyTimer(this); - if ( house != null && house.IsCoOwner( from ) ) - { - Effects.PlaySound( Location, Map, 0x3B3 ); - from.SendLocalizedMessage( 500461 ); // You destroy the item. - Destroy(); - } - } + m_Timer.Start(); + } - public void Empty( int message ) - { - List items = Items; + return true; + } - if ( items.Count > 0 ) - { - PublicOverheadMessage( Network.MessageType.Regular, 0x3B2, message, "" ); + public void Empty(int message) + { + List items = Items; - for ( int i = items.Count - 1; i >= 0; --i ) - { - if ( i >= items.Count ) - continue; + if (items.Count > 0) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, message, ""); - items[i].Delete(); - } - } + for (int i = items.Count - 1; i >= 0; --i) + { + if (i >= items.Count) + continue; - m_Timer?.Stop(); + items[i].Delete(); + } + } - m_Timer = null; - } + m_Timer?.Stop(); - private Timer m_Timer; + m_Timer = null; + } - private class EmptyTimer : Timer - { - private TrashBarrel m_Barrel; + private class EmptyTimer : Timer + { + private TrashBarrel m_Barrel; - public EmptyTimer( TrashBarrel barrel ) : base( TimeSpan.FromMinutes( 3.0 ) ) - { - m_Barrel = barrel; - Priority = TimerPriority.FiveSeconds; - } + public EmptyTimer(TrashBarrel barrel) : base(TimeSpan.FromMinutes(3.0)) + { + m_Barrel = barrel; + Priority = TimerPriority.FiveSeconds; + } - protected override void OnTick() - { - m_Barrel.Empty( 501479 ); // Emptying the trashcan! - } - } - } -} + protected override void OnTick() + { + m_Barrel.Empty(501479); // Emptying the trashcan! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/TrashChest.cs b/Scripts/Items/Misc/TrashChest.cs index 273a40ced..fcfa4bbf4 100644 --- a/Scripts/Items/Misc/TrashChest.cs +++ b/Scripts/Items/Misc/TrashChest.cs @@ -1,56 +1,58 @@ +using Server.Network; + namespace Server.Items { - [FlippableAttribute( 0xE41, 0xE40 )] - public class TrashChest : Container - { - public override int DefaultMaxWeight => 0; // A value of 0 signals unlimited weight + [Flippable(0xE41, 0xE40)] + public class TrashChest : Container + { + [Constructible] + public TrashChest() : base(0xE41) + { + Movable = false; + } - public override bool IsDecoContainer => false; + public TrashChest(Serial serial) : base(serial) + { + } - [Constructible] - public TrashChest() : base( 0xE41 ) - { - Movable = false; - } + public override int DefaultMaxWeight => 0; // A value of 0 signals unlimited weight - public TrashChest( Serial serial ) : base( serial ) - { - } + public override bool IsDecoContainer => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( !base.OnDragDrop( from, dropped ) ) - return false; + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (!base.OnDragDrop(from, dropped)) + return false; - PublicOverheadMessage( Network.MessageType.Regular, 0x3B2, Utility.Random( 1042891, 8 ) ); - dropped.Delete(); + PublicOverheadMessage(MessageType.Regular, 0x3B2, Utility.Random(1042891, 8)); + dropped.Delete(); - return true; - } + return true; + } - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( !base.OnDragDropInto( from, item, p ) ) - return false; + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (!base.OnDragDropInto(from, item, p)) + return false; - PublicOverheadMessage( Network.MessageType.Regular, 0x3B2, Utility.Random( 1042891, 8 ) ); - item.Delete(); + PublicOverheadMessage(MessageType.Regular, 0x3B2, Utility.Random(1042891, 8)); + item.Delete(); - return true; - } - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/TribalBerry.cs b/Scripts/Items/Misc/TribalBerry.cs index 6037e199b..1c17fd2ed 100644 --- a/Scripts/Items/Misc/TribalBerry.cs +++ b/Scripts/Items/Misc/TribalBerry.cs @@ -1,44 +1,43 @@ namespace Server.Items { - public class TribalBerry : Item - { - public override int LabelNumber => 1040001; // tribal berry + public class TribalBerry : Item + { + [Constructible] + public TribalBerry() : this(1) + { + } - [Constructible] - public TribalBerry() : this( 1 ) - { - } + [Constructible] + public TribalBerry(int amount) : base(0x9D0) + { + Weight = 1.0; + Stackable = true; + Amount = amount; + Hue = 6; + } - [Constructible] - public TribalBerry( int amount ) : base( 0x9D0 ) - { - Weight = 1.0; - Stackable = true; - Amount = amount; - Hue = 6; - } + public TribalBerry(Serial serial) : base(serial) + { + } - public TribalBerry( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1040001; // tribal berry + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); - - if ( Hue == 4 ) - Hue = 6; - } - } -} + if (Hue == 4) + Hue = 6; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/TribalPaint.cs b/Scripts/Items/Misc/TribalPaint.cs index 9bb025e01..55daaf9a8 100644 --- a/Scripts/Items/Misc/TribalPaint.cs +++ b/Scripts/Items/Misc/TribalPaint.cs @@ -1,84 +1,89 @@ using System; +using Server.Factions; using Server.Mobiles; using Server.Spells; +using Server.Spells.Fifth; +using Server.Spells.Ninjitsu; +using Server.Spells.Seventh; namespace Server.Items { - public class TribalPaint : Item - { - public override int LabelNumber => 1040000; // savage kin paint + public class TribalPaint : Item + { + [Constructible] + public TribalPaint() : base(0x9EC) + { + Hue = 2101; + Weight = 2.0; + Stackable = Core.ML; + } - [Constructible] - public TribalPaint() : base( 0x9EC ) - { - Hue = 2101; - Weight = 2.0; - Stackable = Core.ML; - } + public TribalPaint(Serial serial) : base(serial) + { + } - public TribalPaint( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1040000; // savage kin paint - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - if ( Factions.Sigil.ExistsOn( from ) ) - { - from.SendLocalizedMessage( 1010465 ); // You cannot disguise yourself while holding a sigil. - } - else if ( !from.CanBeginAction( typeof( Spells.Fifth.IncognitoSpell ) ) ) - { - from.SendLocalizedMessage( 501698 ); // You cannot disguise yourself while incognitoed. - } - else if ( !from.CanBeginAction( typeof( Spells.Seventh.PolymorphSpell ) ) ) - { - from.SendLocalizedMessage( 501699 ); // You cannot disguise yourself while polymorphed. - } - else if ( TransformationSpellHelper.UnderTransformation( from ) ) - { - from.SendLocalizedMessage( 501699 ); // You cannot disguise yourself while polymorphed. - } - else if ( Spells.Ninjitsu.AnimalForm.UnderTransformation( from ) ) - { - from.SendLocalizedMessage( 1061634 ); // You cannot disguise yourself while in that form. - } - else if ( from.IsBodyMod || from.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - { - from.SendLocalizedMessage( 501605 ); // You are already disguised. - } - else - { - from.BodyMod = ( from.Female ? 184 : 183 ); - from.HueMod = 0; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + if (Sigil.ExistsOn(from)) + { + from.SendLocalizedMessage(1010465); // You cannot disguise yourself while holding a sigil. + } + else if (!from.CanBeginAction(typeof(IncognitoSpell))) + { + from.SendLocalizedMessage(501698); // You cannot disguise yourself while incognitoed. + } + else if (!from.CanBeginAction(typeof(PolymorphSpell))) + { + from.SendLocalizedMessage(501699); // You cannot disguise yourself while polymorphed. + } + else if (TransformationSpellHelper.UnderTransformation(from)) + { + from.SendLocalizedMessage(501699); // You cannot disguise yourself while polymorphed. + } + else if (AnimalForm.UnderTransformation(from)) + { + from.SendLocalizedMessage(1061634); // You cannot disguise yourself while in that form. + } + else if (from.IsBodyMod || from.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + { + from.SendLocalizedMessage(501605); // You are already disguised. + } + else + { + from.BodyMod = from.Female ? 184 : 183; + from.HueMod = 0; - if ( from is PlayerMobile mobile ) - mobile.SavagePaintExpiration = TimeSpan.FromDays( 7.0 ); + if (from is PlayerMobile mobile) + mobile.SavagePaintExpiration = TimeSpan.FromDays(7.0); - from.SendLocalizedMessage( 1042537 ); // You now bear the markings of the savage tribe. Your body paint will last about a week or you can remove it with an oil cloth. + from.SendLocalizedMessage( + 1042537); // You now bear the markings of the savage tribe. Your body paint will last about a week or you can remove it with an oil cloth. - Consume(); - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + Consume(); + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Twisted Weald/HornOfTheDreadhorn.cs b/Scripts/Items/Misc/Twisted Weald/HornOfTheDreadhorn.cs index 05b90d6e2..88fa3fb84 100644 --- a/Scripts/Items/Misc/Twisted Weald/HornOfTheDreadhorn.cs +++ b/Scripts/Items/Misc/Twisted Weald/HornOfTheDreadhorn.cs @@ -1,32 +1,31 @@ namespace Server.Items { - [Flippable(0x315C, 0x315D)] - public class HornOfTheDreadhorn : Item - { - public override int LabelNumber => 1072089; // Horn of the Dread + [Flippable(0x315C, 0x315D)] + public class HornOfTheDreadhorn : Item + { + [Constructible] + public HornOfTheDreadhorn() : base(0x315C) + { + } - [Constructible] - public HornOfTheDreadhorn() : base( 0x315C ) - { - } + public HornOfTheDreadhorn(Serial serial) : base(serial) + { + } - public HornOfTheDreadhorn( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072089; // Horn of the Dread - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Twisted Weald/MangledHeadOfDreadhorn.cs b/Scripts/Items/Misc/Twisted Weald/MangledHeadOfDreadhorn.cs index fd6803615..d5b4e503b 100644 --- a/Scripts/Items/Misc/Twisted Weald/MangledHeadOfDreadhorn.cs +++ b/Scripts/Items/Misc/Twisted Weald/MangledHeadOfDreadhorn.cs @@ -1,32 +1,31 @@ namespace Server.Items { - [Flippable(0x3156, 0x3157)] - public class MangledHeadOfDreadhorn : Item - { - public override int LabelNumber => 1072088; // The Mangled Head of Dread Horn + [Flippable(0x3156, 0x3157)] + public class MangledHeadOfDreadhorn : Item + { + [Constructible] + public MangledHeadOfDreadhorn() : base(0x3156) + { + } - [Constructible] - public MangledHeadOfDreadhorn() : base( 0x3156 ) - { - } + public MangledHeadOfDreadhorn(Serial serial) : base(serial) + { + } - public MangledHeadOfDreadhorn( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072088; // The Mangled Head of Dread Horn - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Twisted Weald/TaintedMushroom.cs b/Scripts/Items/Misc/Twisted Weald/TaintedMushroom.cs index 8c5bbef03..31e495f61 100644 --- a/Scripts/Items/Misc/Twisted Weald/TaintedMushroom.cs +++ b/Scripts/Items/Misc/Twisted Weald/TaintedMushroom.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class TaintedMushroom : Item - { - public override int LabelNumber => 1075088; // Dread Horn Tainted Mushroom - public override bool ForceShowProperties => true; + public class TaintedMushroom : Item + { + [Constructible] + public TaintedMushroom() : base(Utility.RandomMinMax(0x222E, 0x2231)) + { + } - [Constructible] - public TaintedMushroom() : base( Utility.RandomMinMax( 0x222E, 0x2231 ) ) - { - } + public TaintedMushroom(Serial serial) : base(serial) + { + } - public TaintedMushroom( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075088; // Dread Horn Tainted Mushroom + public override bool ForceShowProperties => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/UnholyBone.cs b/Scripts/Items/Misc/UnholyBone.cs index eba5f6d5e..8d6784673 100644 --- a/Scripts/Items/Misc/UnholyBone.cs +++ b/Scripts/Items/Misc/UnholyBone.cs @@ -3,111 +3,135 @@ using Server.Mobiles; namespace Server.Items { - public class UnholyBone : Item, ICarvable - { - private SpawnTimer m_Timer; + public class UnholyBone : Item, ICarvable + { + private SpawnTimer m_Timer; - public override string DefaultName => "unholy bone"; + [Constructible] + public UnholyBone() : base(0xF7E) + { + Movable = false; + Hue = 0x497; - [Constructible] - public UnholyBone() : base( 0xF7E ) - { - Movable = false; - Hue = 0x497; + m_Timer = new SpawnTimer(this); + m_Timer.Start(); + } - m_Timer = new SpawnTimer( this ); - m_Timer.Start(); - } + public UnholyBone(Serial serial) : base(serial) + { + } - public void Carve( Mobile from, Item item ) - { - Effects.PlaySound( GetWorldLocation(), Map, 0x48F ); - Effects.SendLocationEffect( GetWorldLocation(), Map, 0x3728, 10, 10, 0, 0 ); + public override string DefaultName => "unholy bone"; - if ( 0.3 > Utility.RandomDouble() ) - { - if ( ItemID == 0xF7E ) - from.SendMessage( "You destroy the bone." ); - else - from.SendMessage( "You destroy the bone pile." ); + public void Carve(Mobile from, Item item) + { + Effects.PlaySound(GetWorldLocation(), Map, 0x48F); + Effects.SendLocationEffect(GetWorldLocation(), Map, 0x3728, 10, 10, 0, 0); - Gold gold = new Gold( 25, 100 ); + if (0.3 > Utility.RandomDouble()) + { + if (ItemID == 0xF7E) + from.SendMessage("You destroy the bone."); + else + from.SendMessage("You destroy the bone pile."); - gold.MoveToWorld( GetWorldLocation(), Map ); + Gold gold = new Gold(25, 100); - Delete(); + gold.MoveToWorld(GetWorldLocation(), Map); - m_Timer.Stop(); - } - else - { - if ( ItemID == 0xF7E ) - from.SendMessage( "You damage the bone." ); - else - from.SendMessage( "You damage the bone pile." ); - } - } + Delete(); - public UnholyBone( Serial serial ) : base( serial ) - { - } + m_Timer.Stop(); + } + else + { + if (ItemID == 0xF7E) + from.SendMessage("You damage the bone."); + else + from.SendMessage("You damage the bone pile."); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Timer = new SpawnTimer( this ); - m_Timer.Start(); - } + m_Timer = new SpawnTimer(this); + m_Timer.Start(); + } - private class SpawnTimer : Timer - { - private Item m_Item; + private class SpawnTimer : Timer + { + private Item m_Item; - public SpawnTimer( Item item ) : base( TimeSpan.FromSeconds( Utility.RandomMinMax( 5, 10 ) ) ) - { - Priority = TimerPriority.FiftyMS; + public SpawnTimer(Item item) : base(TimeSpan.FromSeconds(Utility.RandomMinMax(5, 10))) + { + Priority = TimerPriority.FiftyMS; - m_Item = item; - } + m_Item = item; + } - protected override void OnTick() - { - if ( m_Item.Deleted ) - return; + protected override void OnTick() + { + if (m_Item.Deleted) + return; - Mobile spawn; + Mobile spawn; - switch ( Utility.Random( 12 ) ) - { - default: - case 0: spawn = new Skeleton(); break; - case 1: spawn = new Zombie(); break; - case 2: spawn = new Wraith(); break; - case 3: spawn = new Spectre(); break; - case 4: spawn = new Ghoul(); break; - case 5: spawn = new Mummy(); break; - case 6: spawn = new Bogle(); break; - case 7: spawn = new RottingCorpse(); break; - case 8: spawn = new BoneKnight(); break; - case 9: spawn = new SkeletalKnight(); break; - case 10: spawn = new Lich(); break; - case 11: spawn = new LichLord(); break; - } + switch (Utility.Random(12)) + { + default: + case 0: + spawn = new Skeleton(); + break; + case 1: + spawn = new Zombie(); + break; + case 2: + spawn = new Wraith(); + break; + case 3: + spawn = new Spectre(); + break; + case 4: + spawn = new Ghoul(); + break; + case 5: + spawn = new Mummy(); + break; + case 6: + spawn = new Bogle(); + break; + case 7: + spawn = new RottingCorpse(); + break; + case 8: + spawn = new BoneKnight(); + break; + case 9: + spawn = new SkeletalKnight(); + break; + case 10: + spawn = new Lich(); + break; + case 11: + spawn = new LichLord(); + break; + } - spawn.MoveToWorld( m_Item.Location, m_Item.Map ); + spawn.MoveToWorld(m_Item.Location, m_Item.Map); - m_Item.Delete(); - } - } - } + m_Item.Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Misc/WarningItem.cs b/Scripts/Items/Misc/WarningItem.cs index 502dbfb57..dbf60eeea 100644 --- a/Scripts/Items/Misc/WarningItem.cs +++ b/Scripts/Items/Misc/WarningItem.cs @@ -1,214 +1,216 @@ using System; -using Server.Network; using System.Collections.Generic; +using Server.Network; namespace Server.Items { - public class WarningItem : Item - { - private int m_Range; + public class WarningItem : Item + { + private bool m_Broadcasting; - [CommandProperty( AccessLevel.GameMaster )] - public string WarningString { get; set; } + private DateTime m_LastBroadcast; + private int m_Range; - [CommandProperty( AccessLevel.GameMaster )] - public int WarningNumber { get; set; } + [Constructible] + public WarningItem(int itemID, int range, int warning) : base(itemID) + { + if (range > 18) + range = 18; - [CommandProperty( AccessLevel.GameMaster )] - public int Range - { - get => m_Range; - set{ if ( value > 18 ) value = 18; m_Range = value; } - } + Movable = false; - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan ResetDelay { get; set; } + WarningNumber = warning; + m_Range = range; + } - [Constructible] - public WarningItem( int itemID, int range, int warning ) : base( itemID ) - { - if ( range > 18 ) - range = 18; + [Constructible] + public WarningItem(int itemID, int range, string warning) : base(itemID) + { + if (range > 18) + range = 18; - Movable = false; + Movable = false; - WarningNumber = warning; - m_Range = range; - } + WarningString = warning; + m_Range = range; + } - [Constructible] - public WarningItem( int itemID, int range, string warning ) : base( itemID ) - { - if ( range > 18 ) - range = 18; + public WarningItem(Serial serial) : base(serial) + { + } - Movable = false; + [CommandProperty(AccessLevel.GameMaster)] + public string WarningString{ get; set; } - WarningString = warning; - m_Range = range; - } + [CommandProperty(AccessLevel.GameMaster)] + public int WarningNumber{ get; set; } - public WarningItem( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Range + { + get => m_Range; + set + { + if (value > 18) value = 18; + m_Range = value; + } + } - private bool m_Broadcasting; + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan ResetDelay{ get; set; } - private DateTime m_LastBroadcast; + public virtual bool OnlyToTriggerer => false; + public virtual int NeighborRange => 5; - public virtual void SendMessage( Mobile triggerer, bool onlyToTriggerer, string messageString, int messageNumber ) - { - if ( onlyToTriggerer ) - { - if ( messageString != null ) - triggerer.SendMessage( messageString ); - else - triggerer.SendLocalizedMessage( messageNumber ); - } - else - { - if ( messageString != null ) - PublicOverheadMessage( MessageType.Regular, 0x3B2, false, messageString ); - else - PublicOverheadMessage( MessageType.Regular, 0x3B2, messageNumber ); - } - } + public override bool HandlesOnMovement => true; - public virtual bool OnlyToTriggerer => false; - public virtual int NeighborRange => 5; + public virtual void SendMessage(Mobile triggerer, bool onlyToTriggerer, string messageString, int messageNumber) + { + if (onlyToTriggerer) + { + if (messageString != null) + triggerer.SendMessage(messageString); + else + triggerer.SendLocalizedMessage(messageNumber); + } + else + { + if (messageString != null) + PublicOverheadMessage(MessageType.Regular, 0x3B2, false, messageString); + else + PublicOverheadMessage(MessageType.Regular, 0x3B2, messageNumber); + } + } - public virtual void Broadcast( Mobile triggerer ) - { - if ( m_Broadcasting || (DateTime.UtcNow < (m_LastBroadcast + ResetDelay)) ) - return; + public virtual void Broadcast(Mobile triggerer) + { + if (m_Broadcasting || DateTime.UtcNow < m_LastBroadcast + ResetDelay) + return; - m_LastBroadcast = DateTime.UtcNow; + m_LastBroadcast = DateTime.UtcNow; - m_Broadcasting = true; + m_Broadcasting = true; - SendMessage( triggerer, OnlyToTriggerer, WarningString, WarningNumber ); + SendMessage(triggerer, OnlyToTriggerer, WarningString, WarningNumber); - if ( NeighborRange >= 0 ) - { - List list = new List(); + if (NeighborRange >= 0) + { + List list = new List(); - foreach ( Item item in GetItemsInRange( NeighborRange ) ) - { - if ( item != this && item is WarningItem warningItem ) - list.Add( warningItem ); - } + foreach (Item item in GetItemsInRange(NeighborRange)) + if (item != this && item is WarningItem warningItem) + list.Add(warningItem); - for ( int i = 0; i < list.Count; i++ ) - list[i].Broadcast( triggerer ); - } + for (int i = 0; i < list.Count; i++) + list[i].Broadcast(triggerer); + } - Timer.DelayCall( TimeSpan.Zero, InternalCallback ); - } + Timer.DelayCall(TimeSpan.Zero, InternalCallback); + } - private void InternalCallback() - { - m_Broadcasting = false; - } + private void InternalCallback() + { + m_Broadcasting = false; + } - public override bool HandlesOnMovement => true; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m.Player && Utility.InRange(m.Location, Location, m_Range) && + !Utility.InRange(oldLocation, Location, m_Range)) + Broadcast(m); + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m.Player && Utility.InRange( m.Location, Location, m_Range ) && !Utility.InRange( oldLocation, Location, m_Range ) ) - Broadcast( m ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); - writer.Write( (int) 0 ); + writer.Write(WarningString); + writer.Write(WarningNumber); + writer.Write(m_Range); - writer.Write( (string) WarningString ); - writer.Write( (int) WarningNumber ); - writer.Write( (int) m_Range ); + writer.Write(ResetDelay); + } - writer.Write( (TimeSpan) ResetDelay ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + switch (version) + { + case 0: + { + WarningString = reader.ReadString(); + WarningNumber = reader.ReadInt(); + m_Range = reader.ReadInt(); + ResetDelay = reader.ReadTimeSpan(); - switch ( version ) - { - case 0: - { - WarningString = reader.ReadString(); - WarningNumber = reader.ReadInt(); - m_Range = reader.ReadInt(); - ResetDelay = reader.ReadTimeSpan(); + break; + } + } + } + } - break; - } - } - } - } + public class HintItem : WarningItem + { + [Constructible] + public HintItem(int itemID, int range, int warning, int hint) : base(itemID, range, warning) + { + HintNumber = hint; + } - public class HintItem : WarningItem - { - [CommandProperty( AccessLevel.GameMaster )] - public string HintString { get; set; } + [Constructible] + public HintItem(int itemID, int range, string warning, string hint) : base(itemID, range, warning) + { + HintString = hint; + } - [CommandProperty( AccessLevel.GameMaster )] - public int HintNumber { get; set; } + public HintItem(Serial serial) : base(serial) + { + } - public override bool OnlyToTriggerer => true; + [CommandProperty(AccessLevel.GameMaster)] + public string HintString{ get; set; } - [Constructible] - public HintItem( int itemID, int range, int warning, int hint ) : base( itemID, range, warning ) - { - HintNumber = hint; - } + [CommandProperty(AccessLevel.GameMaster)] + public int HintNumber{ get; set; } - [Constructible] - public HintItem( int itemID, int range, string warning, string hint ) : base( itemID, range, warning ) - { - HintString = hint; - } + public override bool OnlyToTriggerer => true; - public HintItem( Serial serial ) : base( serial ) - { - } + public override void OnDoubleClick(Mobile from) + { + SendMessage(from, true, HintString, HintNumber); + } - public override void OnDoubleClick( Mobile from ) - { - SendMessage( from, true, HintString, HintNumber ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); - writer.Write( (int) 0 ); + writer.Write(HintString); + writer.Write(HintNumber); + } - writer.Write( (string) HintString ); - writer.Write( (int) HintNumber ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + switch (version) + { + case 0: + { + HintString = reader.ReadString(); + HintNumber = reader.ReadInt(); - switch ( version ) - { - case 0: - { - HintString = reader.ReadString(); - HintNumber = reader.ReadInt(); - - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/Waypoint.cs b/Scripts/Items/Misc/Waypoint.cs index fd674805d..7383e9a53 100644 --- a/Scripts/Items/Misc/Waypoint.cs +++ b/Scripts/Items/Misc/Waypoint.cs @@ -1,153 +1,150 @@ -using Server.Targeting; using Server.Commands; +using Server.Targeting; namespace Server.Items { - [FlippableAttribute( 0x1f14, 0x1f15, 0x1f16, 0x1f17 )] - public class WayPoint : Item - { - public static void Initialize() - { - CommandSystem.Register( "WayPointSeq", AccessLevel.GameMaster, WayPointSeq_OnCommand ); - } + [Flippable(0x1f14, 0x1f15, 0x1f16, 0x1f17)] + public class WayPoint : Item + { + private WayPoint m_Next; - public static void WayPointSeq_OnCommand( CommandEventArgs arg ) - { - arg.Mobile.SendMessage( "Target the position of the first way point." ); - arg.Mobile.Target = new WayPointSeqTarget( null ); - } + [Constructible] + public WayPoint() : base(0x1f14) + { + Hue = 0x498; + Visible = false; + //this.Movable = false; + } - private WayPoint m_Next; + public WayPoint(WayPoint prev) : this() + { + if (prev != null) + prev.NextPoint = this; + } - public override string DefaultName => "AI Way Point"; + public WayPoint(Serial serial) : base(serial) + { + } - [Constructible] - public WayPoint() : base( 0x1f14 ) - { - Hue = 0x498; - Visible = false; - //this.Movable = false; - } + public override string DefaultName => "AI Way Point"; - public WayPoint( WayPoint prev ) : this() - { - if ( prev != null ) - prev.NextPoint = this; - } + [CommandProperty(AccessLevel.GameMaster)] + public WayPoint NextPoint + { + get => m_Next; + set + { + if (m_Next != this) + m_Next = value; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public WayPoint NextPoint - { - get => m_Next; - set - { - if ( m_Next != this ) - m_Next = value; - } - } + public static void Initialize() + { + CommandSystem.Register("WayPointSeq", AccessLevel.GameMaster, WayPointSeq_OnCommand); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.SendMessage( "Target the next way point in the sequence." ); + public static void WayPointSeq_OnCommand(CommandEventArgs arg) + { + arg.Mobile.SendMessage("Target the position of the first way point."); + arg.Mobile.Target = new WayPointSeqTarget(null); + } - from.Target = new NextPointTarget( this ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.SendMessage("Target the next way point in the sequence."); - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + from.Target = new NextPointTarget(this); + } + } - if ( m_Next == null ) - LabelTo( from, "(Unlinked)" ); - else - LabelTo( from, "(Linked: {0})", m_Next.Location ); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - public WayPoint( Serial serial ) : base( serial ) - { - } + if (m_Next == null) + LabelTo(from, "(Unlinked)"); + else + LabelTo(from, "(Linked: {0})", m_Next.Location); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch( version ) - { - case 0: - { - m_Next = reader.ReadItem() as WayPoint; - break; - } - } - } + switch (version) + { + case 0: + { + m_Next = reader.ReadItem() as WayPoint; + break; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( m_Next ); - } - } + writer.Write(m_Next); + } + } - public class NextPointTarget : Target - { - private WayPoint m_Point; + public class NextPointTarget : Target + { + private WayPoint m_Point; - public NextPointTarget( WayPoint pt ) : base( -1, false, TargetFlags.None ) - { - m_Point = pt; - } + public NextPointTarget(WayPoint pt) : base(-1, false, TargetFlags.None) + { + m_Point = pt; + } - protected override void OnTarget( Mobile from, object target ) - { - if ( target is WayPoint point && m_Point != null ) - { - m_Point.NextPoint = point; - } - else - { - from.SendMessage( "Target a way point." ); - } - } - } + protected override void OnTarget(Mobile from, object target) + { + if (target is WayPoint point && m_Point != null) + m_Point.NextPoint = point; + else + from.SendMessage("Target a way point."); + } + } - public class WayPointSeqTarget : Target - { - private WayPoint m_Last; + public class WayPointSeqTarget : Target + { + private WayPoint m_Last; - public WayPointSeqTarget( WayPoint last ) : base( -1, true, TargetFlags.None ) - { - m_Last = last; - } + public WayPointSeqTarget(WayPoint last) : base(-1, true, TargetFlags.None) + { + m_Last = last; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is WayPoint wayPoint ) - { - if ( m_Last != null ) - m_Last.NextPoint = wayPoint; - } - else if ( targeted is IPoint3D d ) - { - Point3D p = new Point3D( d ); + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is WayPoint wayPoint) + { + if (m_Last != null) + m_Last.NextPoint = wayPoint; + } + else if (targeted is IPoint3D d) + { + Point3D p = new Point3D(d); - WayPoint point = new WayPoint( m_Last ); - point.MoveToWorld( p, from.Map ); + WayPoint point = new WayPoint(m_Last); + point.MoveToWorld(p, from.Map); - from.Target = new WayPointSeqTarget( point ); - from.SendMessage( "Target the position of the next way point in the sequence, or target a way point link the newest way point to." ); - } - else - { - from.SendMessage( "Target a position, or another way point." ); - } - } - } -} + from.Target = new WayPointSeqTarget(point); + from.SendMessage( + "Target the position of the next way point in the sequence, or target a way point link the newest way point to."); + } + else + { + from.SendMessage("Target a position, or another way point."); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Misc/WindChimes.cs b/Scripts/Items/Misc/WindChimes.cs index 8972caeb0..8ac33639d 100644 --- a/Scripts/Items/Misc/WindChimes.cs +++ b/Scripts/Items/Misc/WindChimes.cs @@ -1,181 +1,187 @@ -using Server.Multis; using Server.Gumps; +using Server.Multis; using Server.Network; namespace Server.Items { - public abstract class BaseWindChimes : Item - { - private bool m_TurnedOn; + public abstract class BaseWindChimes : Item + { + private bool m_TurnedOn; - [CommandProperty( AccessLevel.GameMaster )] - public bool TurnedOn - { - get => m_TurnedOn; - set{ m_TurnedOn = value; InvalidateProperties(); } - } + public BaseWindChimes(int itemID) : base(itemID) + { + } - public BaseWindChimes( int itemID ) : base( itemID ) - { - } + public BaseWindChimes(Serial serial) : base(serial) + { + } - public static int[] Sounds { get; } = { 0x505, 0x506, 0x507 }; + [CommandProperty(AccessLevel.GameMaster)] + public bool TurnedOn + { + get => m_TurnedOn; + set + { + m_TurnedOn = value; + InvalidateProperties(); + } + } - public override bool HandlesOnMovement => m_TurnedOn && IsLockedDown; + public static int[] Sounds{ get; } = { 0x505, 0x506, 0x507 }; - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m_TurnedOn && IsLockedDown && (!m.Hidden || m.AccessLevel == AccessLevel.Player) && Utility.InRange( m.Location, Location, 2 ) && !Utility.InRange( oldLocation, Location, 2 ) ) - Effects.PlaySound( Location, Map, Sounds[Utility.Random( Sounds.Length )] ); + public override bool HandlesOnMovement => m_TurnedOn && IsLockedDown; - base.OnMovement( m, oldLocation ); - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m_TurnedOn && IsLockedDown && (!m.Hidden || m.AccessLevel == AccessLevel.Player) && + Utility.InRange(m.Location, Location, 2) && !Utility.InRange(oldLocation, Location, 2)) + Effects.PlaySound(Location, Map, Sounds[Utility.Random(Sounds.Length)]); - public BaseWindChimes( Serial serial ) : base( serial ) - { - } + base.OnMovement(m, oldLocation); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_TurnedOn ) - list.Add( 502695 ); // turned on - else - list.Add( 502696 ); // turned off - } + if (m_TurnedOn) + list.Add(502695); // turned on + else + list.Add(502696); // turned off + } - public bool IsOwner( Mobile mob ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public bool IsOwner(Mobile mob) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - return ( house != null && house.IsOwner( mob ) ); - } + return house != null && house.IsOwner(mob); + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsOwner( from ) ) - { - OnOffGump onOffGump = new OnOffGump( this ); - from.SendGump( onOffGump ); - } - else - { - from.SendLocalizedMessage( 502691 ); // You must be the owner to use this. - } - } + public override void OnDoubleClick(Mobile from) + { + if (IsOwner(from)) + { + OnOffGump onOffGump = new OnOffGump(this); + from.SendGump(onOffGump); + } + else + { + from.SendLocalizedMessage(502691); // You must be the owner to use this. + } + } - private class OnOffGump : Gump - { - private BaseWindChimes m_Chimes; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public OnOffGump( BaseWindChimes chimes ) : base( 150, 200 ) - { - m_Chimes = chimes; + writer.Write(0); // version - AddBackground( 0, 0, 300, 150, 0xA28 ); - AddHtmlLocalized( 45, 20, 300, 35, chimes.TurnedOn ? 1011035 : 1011034, false, false ); // [De]Activate this item - AddButton( 40, 53, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 55, 65, 35, 1011036, false, false ); // OKAY - AddButton( 150, 53, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 190, 55, 100, 35, 1011012, false, false ); // CANCEL - } + writer.Write(m_TurnedOn); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( info.ButtonID == 1 ) - { - bool newValue = !m_Chimes.TurnedOn; + int version = reader.ReadInt(); - m_Chimes.TurnedOn = newValue; + switch (version) + { + case 0: + { + m_TurnedOn = reader.ReadBool(); + break; + } + } + } - if ( newValue && !m_Chimes.IsLockedDown ) - from.SendLocalizedMessage( 502693 ); // Remember, this only works when locked down. - } - else - { - from.SendLocalizedMessage( 502694 ); // Cancelled action. - } - } - } + private class OnOffGump : Gump + { + private BaseWindChimes m_Chimes; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public OnOffGump(BaseWindChimes chimes) : base(150, 200) + { + m_Chimes = chimes; - writer.Write( (int) 0 ); // version + AddBackground(0, 0, 300, 150, 0xA28); + AddHtmlLocalized(45, 20, 300, 35, chimes.TurnedOn ? 1011035 : 1011034, false, + false); // [De]Activate this item + AddButton(40, 53, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 55, 65, 35, 1011036, false, false); // OKAY + AddButton(150, 53, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(190, 55, 100, 35, 1011012, false, false); // CANCEL + } - writer.Write( (bool) m_TurnedOn ); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (info.ButtonID == 1) + { + bool newValue = !m_Chimes.TurnedOn; - int version = reader.ReadInt(); + m_Chimes.TurnedOn = newValue; - switch ( version ) - { - case 0: - { - m_TurnedOn = reader.ReadBool(); - break; - } - } - } - } + if (newValue && !m_Chimes.IsLockedDown) + from.SendLocalizedMessage(502693); // Remember, this only works when locked down. + } + else + { + from.SendLocalizedMessage(502694); // Cancelled action. + } + } + } + } - public class WindChimes : BaseWindChimes - { - public override int LabelNumber => 1030290; + public class WindChimes : BaseWindChimes + { + [Constructible] + public WindChimes() : base(0x2832) + { + } - [Constructible] - public WindChimes() : base( 0x2832 ) - { - } + public WindChimes(Serial serial) : base(serial) + { + } - public WindChimes( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1030290; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class FancyWindChimes : BaseWindChimes - { - public override int LabelNumber => 1030291; + public class FancyWindChimes : BaseWindChimes + { + [Constructible] + public FancyWindChimes() : base(0x2833) + { + } - [Constructible] - public FancyWindChimes() : base( 0x2833 ) - { - } + public FancyWindChimes(Serial serial) : base(serial) + { + } - public FancyWindChimes( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1030291; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/AmeliasToolbox.cs b/Scripts/Items/New Haven Quest Rewards/AmeliasToolbox.cs index 54545591a..e62623afc 100644 --- a/Scripts/Items/New Haven Quest Rewards/AmeliasToolbox.cs +++ b/Scripts/Items/New Haven Quest Rewards/AmeliasToolbox.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class AmeliasToolbox : TinkerTools - { - public override int LabelNumber => 1077749; // Amelias Toolbox + public class AmeliasToolbox : TinkerTools + { + [Constructible] + public AmeliasToolbox() : base(500) + { + LootType = LootType.Blessed; + Hue = 1895; // TODO check + } - [Constructible] - public AmeliasToolbox() : base( 500 ) - { - LootType = LootType.Blessed; - Hue = 1895; // TODO check - } + public AmeliasToolbox(Serial serial) : base(serial) + { + } - public AmeliasToolbox( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077749; // Amelias Toolbox - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/ArmsOfArmstrong.cs b/Scripts/Items/New Haven Quest Rewards/ArmsOfArmstrong.cs index dc0b8af83..482a6f29f 100644 --- a/Scripts/Items/New Haven Quest Rewards/ArmsOfArmstrong.cs +++ b/Scripts/Items/New Haven Quest Rewards/ArmsOfArmstrong.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class ArmsOfArmstrong : LeatherArms - { - public override int LabelNumber => 1077675; // Arms of Armstrong + public class ArmsOfArmstrong : LeatherArms + { + [Constructible] + public ArmsOfArmstrong() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + Attributes.BonusStr = 3; + Attributes.RegenHits = 1; + } - [Constructible] - public ArmsOfArmstrong() - { - LootType = LootType.Blessed; + public ArmsOfArmstrong(Serial serial) : base(serial) + { + } - Attributes.BonusStr = 3; - Attributes.RegenHits = 1; - } + public override int LabelNumber => 1077675; // Arms of Armstrong - public ArmsOfArmstrong( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/BagOfNecromancerReagents.cs b/Scripts/Items/New Haven Quest Rewards/BagOfNecromancerReagents.cs index 42b83cc10..5f7e12ee4 100644 --- a/Scripts/Items/New Haven Quest Rewards/BagOfNecromancerReagents.cs +++ b/Scripts/Items/New Haven Quest Rewards/BagOfNecromancerReagents.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class BagOfNecromancerReagents : Bag - { - [Constructible] - public BagOfNecromancerReagents() : this( 50 ) - { - } + public class BagOfNecromancerReagents : Bag + { + [Constructible] + public BagOfNecromancerReagents() : this(50) + { + } - [Constructible] - public BagOfNecromancerReagents( int amount ) - { - DropItem( new BatWing ( amount ) ); - DropItem( new GraveDust ( amount ) ); - DropItem( new DaemonBlood( amount ) ); - DropItem( new NoxCrystal ( amount ) ); - DropItem( new PigIron ( amount ) ); - } + [Constructible] + public BagOfNecromancerReagents(int amount) + { + DropItem(new BatWing(amount)); + DropItem(new GraveDust(amount)); + DropItem(new DaemonBlood(amount)); + DropItem(new NoxCrystal(amount)); + DropItem(new PigIron(amount)); + } - public BagOfNecromancerReagents( Serial serial ) : base( serial ) - { - } + public BagOfNecromancerReagents(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/BagOfSmokeBombs.cs b/Scripts/Items/New Haven Quest Rewards/BagOfSmokeBombs.cs index 241e48773..16d2e2373 100644 --- a/Scripts/Items/New Haven Quest Rewards/BagOfSmokeBombs.cs +++ b/Scripts/Items/New Haven Quest Rewards/BagOfSmokeBombs.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class BagOfSmokeBombs : Bag - { - [Constructible] - public BagOfSmokeBombs() : this( 20 ) - { - } + public class BagOfSmokeBombs : Bag + { + [Constructible] + public BagOfSmokeBombs() : this(20) + { + } - [Constructible] - public BagOfSmokeBombs( int amount ) - { - for ( int i = 0; i < amount; ++i ) - DropItem( new SmokeBomb() ); - } + [Constructible] + public BagOfSmokeBombs(int amount) + { + for (int i = 0; i < amount; ++i) + DropItem(new SmokeBomb()); + } - public BagOfSmokeBombs( Serial serial ) : base( serial ) - { - } + public BagOfSmokeBombs(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/BraceletOfResilience.cs b/Scripts/Items/New Haven Quest Rewards/BraceletOfResilience.cs index 147a1992d..ac7170135 100644 --- a/Scripts/Items/New Haven Quest Rewards/BraceletOfResilience.cs +++ b/Scripts/Items/New Haven Quest Rewards/BraceletOfResilience.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class BraceletOfResilience : GoldBracelet - { - public override int LabelNumber => 1077627; // Bracelet of Resilience + public class BraceletOfResilience : GoldBracelet + { + [Constructible] + public BraceletOfResilience() + { + LootType = LootType.Blessed; - [Constructible] - public BraceletOfResilience() - { - LootType = LootType.Blessed; + Attributes.DefendChance = 5; + Resistances.Fire = 5; + Resistances.Cold = 5; + Resistances.Poison = 5; + Resistances.Energy = 5; + } - Attributes.DefendChance = 5; - Resistances.Fire = 5; - Resistances.Cold = 5; - Resistances.Poison = 5; - Resistances.Energy = 5; - } + public BraceletOfResilience(Serial serial) : base(serial) + { + } - public BraceletOfResilience( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077627; // Bracelet of Resilience - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/BulwarkLeggings.cs b/Scripts/Items/New Haven Quest Rewards/BulwarkLeggings.cs index 1cfd18f4c..736d0a122 100644 --- a/Scripts/Items/New Haven Quest Rewards/BulwarkLeggings.cs +++ b/Scripts/Items/New Haven Quest Rewards/BulwarkLeggings.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class BulwarkLeggings : RingmailLegs - { - public override int LabelNumber => 1077727; // Bulwark Leggings + public class BulwarkLeggings : RingmailLegs + { + [Constructible] + public BulwarkLeggings() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 9; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + Attributes.RegenStam = 1; + Attributes.RegenMana = 1; + } - [Constructible] - public BulwarkLeggings() - { - LootType = LootType.Blessed; + public BulwarkLeggings(Serial serial) : base(serial) + { + } - Attributes.RegenStam = 1; - Attributes.RegenMana = 1; - } + public override int LabelNumber => 1077727; // Bulwark Leggings - public BulwarkLeggings( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 9; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/ChurchillsWarMace.cs b/Scripts/Items/New Haven Quest Rewards/ChurchillsWarMace.cs index d3337dfa9..7a7713795 100644 --- a/Scripts/Items/New Haven Quest Rewards/ChurchillsWarMace.cs +++ b/Scripts/Items/New Haven Quest Rewards/ChurchillsWarMace.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class ChurchillsWarMace : WarMace - { - public override int LabelNumber => 1078062; // Churchill's War Mace + public class ChurchillsWarMace : WarMace + { + [Constructible] + public ChurchillsWarMace() + { + LootType = LootType.Blessed; - [Constructible] - public ChurchillsWarMace() - { - LootType = LootType.Blessed; + Attributes.AttackChance = 5; + Attributes.WeaponSpeed = 10; + Attributes.WeaponDamage = 25; + WeaponAttributes.LowerStatReq = 70; + } - Attributes.AttackChance = 5; - Attributes.WeaponSpeed = 10; - Attributes.WeaponDamage = 25; - WeaponAttributes.LowerStatReq = 70; - } + public ChurchillsWarMace(Serial serial) : base(serial) + { + } - public ChurchillsWarMace( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1078062; // Churchill's War Mace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/ClaspOfConcentration.cs b/Scripts/Items/New Haven Quest Rewards/ClaspOfConcentration.cs index 262163f22..91ce4c158 100644 --- a/Scripts/Items/New Haven Quest Rewards/ClaspOfConcentration.cs +++ b/Scripts/Items/New Haven Quest Rewards/ClaspOfConcentration.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class ClaspOfConcentration : SilverBracelet - { - public override int LabelNumber => 1077695; // Clasp of Concentration + public class ClaspOfConcentration : SilverBracelet + { + [Constructible] + public ClaspOfConcentration() + { + LootType = LootType.Blessed; - [Constructible] - public ClaspOfConcentration() - { - LootType = LootType.Blessed; + Attributes.RegenStam = 2; + Attributes.RegenMana = 1; + Resistances.Fire = 5; + Resistances.Cold = 5; + } - Attributes.RegenStam = 2; - Attributes.RegenMana = 1; - Resistances.Fire = 5; - Resistances.Cold = 5; - } + public ClaspOfConcentration(Serial serial) : base(serial) + { + } - public ClaspOfConcentration( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077695; // Clasp of Concentration - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/EmberStaff.cs b/Scripts/Items/New Haven Quest Rewards/EmberStaff.cs index c3d43482f..99c6602fb 100644 --- a/Scripts/Items/New Haven Quest Rewards/EmberStaff.cs +++ b/Scripts/Items/New Haven Quest Rewards/EmberStaff.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class EmberStaff : QuarterStaff - { - public override int LabelNumber => 1077582; // Ember Staff + public class EmberStaff : QuarterStaff + { + [Constructible] + public EmberStaff() + { + LootType = LootType.Blessed; - [Constructible] - public EmberStaff() - { - LootType = LootType.Blessed; + WeaponAttributes.HitFireball = 15; + WeaponAttributes.MageWeapon = 10; + Attributes.SpellChanneling = 1; + Attributes.CastSpeed = -1; + WeaponAttributes.LowerStatReq = 50; + } - WeaponAttributes.HitFireball = 15; - WeaponAttributes.MageWeapon = 10; - Attributes.SpellChanneling = 1; - Attributes.CastSpeed = -1; - WeaponAttributes.LowerStatReq = 50; - } + public EmberStaff(Serial serial) : base(serial) + { + } - public EmberStaff( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077582; // Ember Staff - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/EscutcheonDeAriadne.cs b/Scripts/Items/New Haven Quest Rewards/EscutcheonDeAriadne.cs index 780ea670e..b067c9587 100644 --- a/Scripts/Items/New Haven Quest Rewards/EscutcheonDeAriadne.cs +++ b/Scripts/Items/New Haven Quest Rewards/EscutcheonDeAriadne.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class EscutcheonDeAriadne : MetalKiteShield - { - public override int LabelNumber => 1077694; // Escutcheon de Ariadne + public class EscutcheonDeAriadne : MetalKiteShield + { + [Constructible] + public EscutcheonDeAriadne() + { + LootType = LootType.Blessed; + Hue = 0x8A5; - public override int BasePhysicalResistance => 5; - public override int BaseEnergyResistance => 1; + ArmorAttributes.DurabilityBonus = 49; + Attributes.ReflectPhysical = 5; + Attributes.DefendChance = 5; + } - public override int AosStrReq => 14; + public EscutcheonDeAriadne(Serial serial) : base(serial) + { + } - [Constructible] - public EscutcheonDeAriadne() - { - LootType = LootType.Blessed; - Hue = 0x8A5; + public override int LabelNumber => 1077694; // Escutcheon de Ariadne - ArmorAttributes.DurabilityBonus = 49; - Attributes.ReflectPhysical = 5; - Attributes.DefendChance = 5; - } + public override int BasePhysicalResistance => 5; + public override int BaseEnergyResistance => 1; - public EscutcheonDeAriadne( Serial serial ) : base( serial ) - { - } + public override int AosStrReq => 14; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/GlovesOfSafeguarding.cs b/Scripts/Items/New Haven Quest Rewards/GlovesOfSafeguarding.cs index c2df53f48..d1950ad31 100644 --- a/Scripts/Items/New Haven Quest Rewards/GlovesOfSafeguarding.cs +++ b/Scripts/Items/New Haven Quest Rewards/GlovesOfSafeguarding.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class GlovesOfSafeguarding : LeatherGloves - { - public override int LabelNumber => 1077614; // Gloves of Safeguarding + public class GlovesOfSafeguarding : LeatherGloves + { + [Constructible] + public GlovesOfSafeguarding() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + Attributes.BonusStam = 3; + Attributes.RegenHits = 1; + } - [Constructible] - public GlovesOfSafeguarding() - { - LootType = LootType.Blessed; + public GlovesOfSafeguarding(Serial serial) : base(serial) + { + } - Attributes.BonusStam = 3; - Attributes.RegenHits = 1; - } + public override int LabelNumber => 1077614; // Gloves of Safeguarding - public GlovesOfSafeguarding( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/HallowedSpellbook.cs b/Scripts/Items/New Haven Quest Rewards/HallowedSpellbook.cs index 9934a0ef8..2a22293c5 100644 --- a/Scripts/Items/New Haven Quest Rewards/HallowedSpellbook.cs +++ b/Scripts/Items/New Haven Quest Rewards/HallowedSpellbook.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class HallowedSpellbook : Spellbook - { - public override int LabelNumber => 1077620; // Hallowed Spellbook + public class HallowedSpellbook : Spellbook + { + [Constructible] + public HallowedSpellbook() : base(0x3FFFFFFFF) + { + LootType = LootType.Blessed; - [Constructible] - public HallowedSpellbook() : base( 0x3FFFFFFFF ) - { - LootType = LootType.Blessed; + Slayer = SlayerName.Silver; + } - Slayer = SlayerName.Silver; - } + public HallowedSpellbook(Serial serial) : base(serial) + { + } - public HallowedSpellbook( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077620; // Hallowed Spellbook - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/HammerOfHephaestus.cs b/Scripts/Items/New Haven Quest Rewards/HammerOfHephaestus.cs index ed8901c29..436c33000 100644 --- a/Scripts/Items/New Haven Quest Rewards/HammerOfHephaestus.cs +++ b/Scripts/Items/New Haven Quest Rewards/HammerOfHephaestus.cs @@ -2,72 +2,73 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x13E3, 0x13E4 )] - public class HammerOfHephaestus : SmithHammer - { - public override int LabelNumber => 1077740; // Hammer of Hephaestus + [Flippable(0x13E3, 0x13E4)] + public class HammerOfHephaestus : SmithHammer + { + public static readonly TimeSpan RechargeDelay = TimeSpan.FromMinutes(5); - public static readonly TimeSpan RechargeDelay = TimeSpan.FromMinutes( 5 ); + [Constructible] + public HammerOfHephaestus() + { + UsesRemaining = 20; + LootType = LootType.Blessed; - [Constructible] - public HammerOfHephaestus() - { - UsesRemaining = 20; - LootType = LootType.Blessed; + // TODO: Blacksmith +10 bonus when equipped - // TODO: Blacksmith +10 bonus when equipped + StartRechargeTimer(); + } - StartRechargeTimer(); - } + public HammerOfHephaestus(Serial serial) + : base(serial) + { + } - public override bool BreakOnDepletion => false; - /* Note: - * On EA, it also leaves the crafting gump open when it reaches 0 charges. - * When crafting again, only then the crafting gump closes with the 1072306 system message. - */ + public override int LabelNumber => 1077740; // Hammer of Hephaestus - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) && Parent != from ) // TODO: These checks don't match EA, but they match BaseTool for now - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - else if ( UsesRemaining <= 0 ) - from.SendLocalizedMessage( 1072306 ); // You must wait a moment for it to recharge. - else - base.OnDoubleClick( from ); - } + public override bool BreakOnDepletion => false; + /* Note: + * On EA, it also leaves the crafting gump open when it reaches 0 charges. + * When crafting again, only then the crafting gump closes with the 1072306 system message. + */ - private void StartRechargeTimer() - { - // TODO: Needs work - //Timer.DelayCall( RechargeDelay, RechargeDelay, new TimerCallback( Recharge ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack) && Parent != from + ) // TODO: These checks don't match EA, but they match BaseTool for now + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + else if (UsesRemaining <= 0) + from.SendLocalizedMessage(1072306); // You must wait a moment for it to recharge. + else + base.OnDoubleClick(from); + } - public void Recharge() - { - // TODO: Stop timer at 20? Count downtime? Something more generic so we can use it for JacobsPickaxe too (both are IUsesRemaining)? - if ( UsesRemaining < 20 ) - ++UsesRemaining; - } + private void StartRechargeTimer() + { + // TODO: Needs work + //Timer.DelayCall( RechargeDelay, RechargeDelay, new TimerCallback( Recharge ) ); + } - public HammerOfHephaestus( Serial serial ) - : base( serial ) - { - } + public void Recharge() + { + // TODO: Stop timer at 20? Count downtime? Something more generic so we can use it for JacobsPickaxe too (both are IUsesRemaining)? + if (UsesRemaining < 20) + ++UsesRemaining; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - StartRechargeTimer(); - } - } -} + StartRechargeTimer(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/HealersTouch.cs b/Scripts/Items/New Haven Quest Rewards/HealersTouch.cs index 53a323e9c..0d0dd62ce 100644 --- a/Scripts/Items/New Haven Quest Rewards/HealersTouch.cs +++ b/Scripts/Items/New Haven Quest Rewards/HealersTouch.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class HealersTouch : LeatherGloves - { - public override int LabelNumber => 1077684; // Healer's Touch + public class HealersTouch : LeatherGloves + { + [Constructible] + public HealersTouch() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + Attributes.BonusStam = 3; + Attributes.ReflectPhysical = 5; + } - [Constructible] - public HealersTouch() - { - LootType = LootType.Blessed; + public HealersTouch(Serial serial) : base(serial) + { + } - Attributes.BonusStam = 3; - Attributes.ReflectPhysical = 5; - } + public override int LabelNumber => 1077684; // Healer's Touch - public HealersTouch( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/Heartseeker.cs b/Scripts/Items/New Haven Quest Rewards/Heartseeker.cs index 7043fdaf3..5fc192612 100644 --- a/Scripts/Items/New Haven Quest Rewards/Heartseeker.cs +++ b/Scripts/Items/New Haven Quest Rewards/Heartseeker.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class Heartseeker : CompositeBow - { - public override int LabelNumber => 1078210; // Heartseeker + public class Heartseeker : CompositeBow + { + [Constructible] + public Heartseeker() + { + LootType = LootType.Blessed; - [Constructible] - public Heartseeker() - { - LootType = LootType.Blessed; + Attributes.AttackChance = 5; + Attributes.WeaponSpeed = 10; + Attributes.WeaponDamage = 25; + WeaponAttributes.LowerStatReq = 70; + } - Attributes.AttackChance = 5; - Attributes.WeaponSpeed = 10; - Attributes.WeaponDamage = 25; - WeaponAttributes.LowerStatReq = 70; - } + public Heartseeker(Serial serial) : base(serial) + { + } - public Heartseeker( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1078210; // Heartseeker - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/JacobsPickaxe.cs b/Scripts/Items/New Haven Quest Rewards/JacobsPickaxe.cs index 3b5e9ee37..9583569af 100644 --- a/Scripts/Items/New Haven Quest Rewards/JacobsPickaxe.cs +++ b/Scripts/Items/New Haven Quest Rewards/JacobsPickaxe.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class JacobsPickaxe : Pickaxe - { - public override int LabelNumber => 1077758; // Jacob's Pickaxe + public class JacobsPickaxe : Pickaxe + { + // TODO: Recharges 1 use every 5 minutes. Doesn't break when it reaches 0, you get a system message "You must wait a moment for it to recharge" 1072306 if you attempt to use it with no uses remaining. - // TODO: Recharges 1 use every 5 minutes. Doesn't break when it reaches 0, you get a system message "You must wait a moment for it to recharge" 1072306 if you attempt to use it with no uses remaining. + [Constructible] + public JacobsPickaxe() + { + UsesRemaining = 20; + LootType = LootType.Blessed; - [Constructible] - public JacobsPickaxe() - { - UsesRemaining = 20; - LootType = LootType.Blessed; + SkillBonuses.SetValues(0, SkillName.Mining, 10.0); + } - SkillBonuses.SetValues( 0, SkillName.Mining, 10.0 ); - } + public JacobsPickaxe(Serial serial) + : base(serial) + { + } - public JacobsPickaxe( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1077758; // Jacob's Pickaxe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/JocklesQuicksword.cs b/Scripts/Items/New Haven Quest Rewards/JocklesQuicksword.cs index 392079a7e..9df265157 100644 --- a/Scripts/Items/New Haven Quest Rewards/JocklesQuicksword.cs +++ b/Scripts/Items/New Haven Quest Rewards/JocklesQuicksword.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class JocklesQuicksword : Longsword - { - public override int LabelNumber => 1077666; // Jockles' Quicksword + public class JocklesQuicksword : Longsword + { + [Constructible] + public JocklesQuicksword() + { + LootType = LootType.Blessed; - [Constructible] - public JocklesQuicksword() - { - LootType = LootType.Blessed; + Attributes.AttackChance = 5; + Attributes.WeaponSpeed = 10; + Attributes.WeaponDamage = 25; + } - Attributes.AttackChance = 5; - Attributes.WeaponSpeed = 10; - Attributes.WeaponDamage = 25; - } + public JocklesQuicksword(Serial serial) : base(serial) + { + } - public JocklesQuicksword( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077666; // Jockles' Quicksword - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/PhilosophersHat.cs b/Scripts/Items/New Haven Quest Rewards/PhilosophersHat.cs index 236015f4b..9736a1aae 100644 --- a/Scripts/Items/New Haven Quest Rewards/PhilosophersHat.cs +++ b/Scripts/Items/New Haven Quest Rewards/PhilosophersHat.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class PhilosophersHat : WizardsHat - { - public override int LabelNumber => 1077602; // Philosopher's Hat + public class PhilosophersHat : WizardsHat + { + [Constructible] + public PhilosophersHat() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 5; - public override int BaseFireResistance => 5; - public override int BaseColdResistance => 9; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + Attributes.RegenMana = 1; + Attributes.LowerRegCost = 7; + } - [Constructible] - public PhilosophersHat() - { - LootType = LootType.Blessed; + public PhilosophersHat(Serial serial) : base(serial) + { + } - Attributes.RegenMana = 1; - Attributes.LowerRegCost = 7; - } + public override int LabelNumber => 1077602; // Philosopher's Hat - public PhilosophersHat( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 5; + public override int BaseFireResistance => 5; + public override int BaseColdResistance => 9; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/RecarosRiposte.cs b/Scripts/Items/New Haven Quest Rewards/RecarosRiposte.cs index e416e58d8..e36ac2f04 100644 --- a/Scripts/Items/New Haven Quest Rewards/RecarosRiposte.cs +++ b/Scripts/Items/New Haven Quest Rewards/RecarosRiposte.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class RecarosRiposte : WarFork - { - public override int LabelNumber => 1078195; // Recaro's Riposte + public class RecarosRiposte : WarFork + { + [Constructible] + public RecarosRiposte() + { + LootType = LootType.Blessed; - [Constructible] - public RecarosRiposte() - { - LootType = LootType.Blessed; + Attributes.AttackChance = 5; + Attributes.WeaponSpeed = 10; + Attributes.WeaponDamage = 25; + } - Attributes.AttackChance = 5; - Attributes.WeaponSpeed = 10; - Attributes.WeaponDamage = 25; - } + public RecarosRiposte(Serial serial) : base(serial) + { + } - public RecarosRiposte( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1078195; // Recaro's Riposte - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/RingOfTheSavant.cs b/Scripts/Items/New Haven Quest Rewards/RingOfTheSavant.cs index 42d9aa78c..f390ee8a6 100644 --- a/Scripts/Items/New Haven Quest Rewards/RingOfTheSavant.cs +++ b/Scripts/Items/New Haven Quest Rewards/RingOfTheSavant.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class RingOfTheSavant : GoldRing - { - public override int LabelNumber => 1077608; // Ring of the Savant + public class RingOfTheSavant : GoldRing + { + [Constructible] + public RingOfTheSavant() + { + LootType = LootType.Blessed; - [Constructible] - public RingOfTheSavant() - { - LootType = LootType.Blessed; + Attributes.BonusInt = 3; + Attributes.CastRecovery = 1; + Attributes.CastSpeed = 1; + } - Attributes.BonusInt = 3; - Attributes.CastRecovery = 1; - Attributes.CastSpeed = 1; - } + public RingOfTheSavant(Serial serial) : base(serial) + { + } - public RingOfTheSavant( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077608; // Ring of the Savant - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/SilverSerpentBlade.cs b/Scripts/Items/New Haven Quest Rewards/SilverSerpentBlade.cs index 54552a403..995e0bbf0 100644 --- a/Scripts/Items/New Haven Quest Rewards/SilverSerpentBlade.cs +++ b/Scripts/Items/New Haven Quest Rewards/SilverSerpentBlade.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public class SilverSerpentBlade : Kryss - { - public override int LabelNumber => 1078163; // Silver Serpent Blade + public class SilverSerpentBlade : Kryss + { + [Constructible] + public SilverSerpentBlade() + { + LootType = LootType.Blessed; - [Constructible] - public SilverSerpentBlade() - { - LootType = LootType.Blessed; + Attributes.AttackChance = 5; + Attributes.WeaponSpeed = 10; + Attributes.WeaponDamage = 25; + } - Attributes.AttackChance = 5; - Attributes.WeaponSpeed = 10; - Attributes.WeaponDamage = 25; - } + public SilverSerpentBlade(Serial serial) : base(serial) + { + } - public SilverSerpentBlade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1078163; // Silver Serpent Blade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/TheDragonsTail.cs b/Scripts/Items/New Haven Quest Rewards/TheDragonsTail.cs index 8f894bf1b..18e271838 100644 --- a/Scripts/Items/New Haven Quest Rewards/TheDragonsTail.cs +++ b/Scripts/Items/New Haven Quest Rewards/TheDragonsTail.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class TheDragonsTail : NoDachi - { - public override int LabelNumber => 1078015; // The Dragon's Tail + public class TheDragonsTail : NoDachi + { + [Constructible] + public TheDragonsTail() + { + LootType = LootType.Blessed; - public override int InitMinHits => 80; - public override int InitMaxHits => 80; + WeaponAttributes.HitLeechStam = 16; + Attributes.WeaponSpeed = 10; + Attributes.WeaponDamage = 25; + } - [Constructible] - public TheDragonsTail() - { - LootType = LootType.Blessed; + public TheDragonsTail(Serial serial) : base(serial) + { + } - WeaponAttributes.HitLeechStam = 16; - Attributes.WeaponSpeed = 10; - Attributes.WeaponDamage = 25; - } + public override int LabelNumber => 1078015; // The Dragon's Tail - public TheDragonsTail( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 80; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/TunicOfGuarding.cs b/Scripts/Items/New Haven Quest Rewards/TunicOfGuarding.cs index e357897dc..23a35709e 100644 --- a/Scripts/Items/New Haven Quest Rewards/TunicOfGuarding.cs +++ b/Scripts/Items/New Haven Quest Rewards/TunicOfGuarding.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class TunicOfGuarding : LeatherChest - { - public override int LabelNumber => 1077693; // Tunic of Guarding + public class TunicOfGuarding : LeatherChest + { + [Constructible] + public TunicOfGuarding() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 5; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 5; + Attributes.BonusHits = 2; + Attributes.ReflectPhysical = 5; + } - [Constructible] - public TunicOfGuarding() - { - LootType = LootType.Blessed; + public TunicOfGuarding(Serial serial) : base(serial) + { + } - Attributes.BonusHits = 2; - Attributes.ReflectPhysical = 5; - } + public override int LabelNumber => 1077693; // Tunic of Guarding - public TunicOfGuarding( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 5; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/TwilightJacket.cs b/Scripts/Items/New Haven Quest Rewards/TwilightJacket.cs index 8617fe719..b2f5460bb 100644 --- a/Scripts/Items/New Haven Quest Rewards/TwilightJacket.cs +++ b/Scripts/Items/New Haven Quest Rewards/TwilightJacket.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class TwilightJacket : LeatherNinjaJacket - { - public override int LabelNumber => 1078183; // Twilight Jacket + public class TwilightJacket : LeatherNinjaJacket + { + [Constructible] + public TwilightJacket() + { + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 6; - public override int BaseFireResistance => 12; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + Attributes.ReflectPhysical = 5; + } - [Constructible] - public TwilightJacket() - { - LootType = LootType.Blessed; + public TwilightJacket(Serial serial) : base(serial) + { + } - Attributes.ReflectPhysical = 5; - } + public override int LabelNumber => 1078183; // Twilight Jacket - public TwilightJacket( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 6; + public override int BaseFireResistance => 12; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/New Haven Quest Rewards/WalkersLeggings.cs b/Scripts/Items/New Haven Quest Rewards/WalkersLeggings.cs index c36c401f8..610599b3e 100644 --- a/Scripts/Items/New Haven Quest Rewards/WalkersLeggings.cs +++ b/Scripts/Items/New Haven Quest Rewards/WalkersLeggings.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class WalkersLeggings : LeatherNinjaPants - { - public override int LabelNumber => 1078222; // Walker's Leggings + public class WalkersLeggings : LeatherNinjaPants + { + [Constructible] + public WalkersLeggings() + { + LootType = LootType.Blessed; + } - public override int BasePhysicalResistance => 10; - public override int BaseFireResistance => 6; - public override int BaseColdResistance => 6; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + public WalkersLeggings(Serial serial) : base(serial) + { + } - [Constructible] - public WalkersLeggings() - { - LootType = LootType.Blessed; - } + public override int LabelNumber => 1078222; // Walker's Leggings - public WalkersLeggings( Serial serial ) : base( serial ) - { - } + public override int BasePhysicalResistance => 10; + public override int BaseFireResistance => 6; + public override int BaseColdResistance => 6; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/PlantsFlowers/Potted/EmptyPots.cs b/Scripts/Items/PlantsFlowers/Potted/EmptyPots.cs index e07b01131..59063c847 100644 --- a/Scripts/Items/PlantsFlowers/Potted/EmptyPots.cs +++ b/Scripts/Items/PlantsFlowers/Potted/EmptyPots.cs @@ -1,56 +1,56 @@ namespace Server.Items { - public class SmallEmptyPot : Item - { - [Constructible] - public SmallEmptyPot() : base(0x11C6) - { - Weight = 100; - } + public class SmallEmptyPot : Item + { + [Constructible] + public SmallEmptyPot() : base(0x11C6) + { + Weight = 100; + } - public SmallEmptyPot(Serial serial) : base(serial) - { - } + public SmallEmptyPot(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LargeEmptyPot : Item - { - [Constructible] - public LargeEmptyPot() : base(0x11C7) - { - Weight = 6; - } + public class LargeEmptyPot : Item + { + [Constructible] + public LargeEmptyPot() : base(0x11C7) + { + Weight = 6; + } - public LargeEmptyPot(Serial serial) : base(serial) - { - } + public LargeEmptyPot(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/PlantsFlowers/Potted/PottedCactus.cs b/Scripts/Items/PlantsFlowers/Potted/PottedCactus.cs index 3977e5bc0..a926f2aec 100644 --- a/Scripts/Items/PlantsFlowers/Potted/PottedCactus.cs +++ b/Scripts/Items/PlantsFlowers/Potted/PottedCactus.cs @@ -1,164 +1,164 @@ namespace Server.Items { - public class PottedCactus : Item - { - [Constructible] - public PottedCactus() : base(0x1E0F) - { - Weight = 100; - } + public class PottedCactus : Item + { + [Constructible] + public PottedCactus() : base(0x1E0F) + { + Weight = 100; + } - public PottedCactus(Serial serial) : base(serial) - { - } + public PottedCactus(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedCactus1 : Item - { - [Constructible] - public PottedCactus1() : base(0x1E10) - { - Weight = 100; - } + public class PottedCactus1 : Item + { + [Constructible] + public PottedCactus1() : base(0x1E10) + { + Weight = 100; + } - public PottedCactus1(Serial serial) : base(serial) - { - } + public PottedCactus1(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedCactus2 : Item - { - [Constructible] - public PottedCactus2() : base(0x1E11) - { - Weight = 100; - } + public class PottedCactus2 : Item + { + [Constructible] + public PottedCactus2() : base(0x1E11) + { + Weight = 100; + } - public PottedCactus2(Serial serial) : base(serial) - { - } + public PottedCactus2(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedCactus3 : Item - { - [Constructible] - public PottedCactus3() : base(0x1E12) - { - Weight = 100; - } + public class PottedCactus3 : Item + { + [Constructible] + public PottedCactus3() : base(0x1E12) + { + Weight = 100; + } - public PottedCactus3(Serial serial) : base(serial) - { - } + public PottedCactus3(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedCactus4 : Item - { - [Constructible] - public PottedCactus4() : base(0x1E13) - { - Weight = 100; - } + public class PottedCactus4 : Item + { + [Constructible] + public PottedCactus4() : base(0x1E13) + { + Weight = 100; + } - public PottedCactus4(Serial serial) : base(serial) - { - } + public PottedCactus4(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedCactus5 : Item - { - [Constructible] - public PottedCactus5() : base(0x1E14) - { - Weight = 100; - } + public class PottedCactus5 : Item + { + [Constructible] + public PottedCactus5() : base(0x1E14) + { + Weight = 100; + } - public PottedCactus5(Serial serial) : base(serial) - { - } + public PottedCactus5(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/PlantsFlowers/Potted/PottedPlants.cs b/Scripts/Items/PlantsFlowers/Potted/PottedPlants.cs index a3f54544e..0272c96a3 100644 --- a/Scripts/Items/PlantsFlowers/Potted/PottedPlants.cs +++ b/Scripts/Items/PlantsFlowers/Potted/PottedPlants.cs @@ -1,83 +1,83 @@ namespace Server.Items { - public class PottedPlant : Item - { - [Constructible] - public PottedPlant() : base(0x11CA) - { - Weight = 100; - } + public class PottedPlant : Item + { + [Constructible] + public PottedPlant() : base(0x11CA) + { + Weight = 100; + } - public PottedPlant(Serial serial) : base(serial) - { - } + public PottedPlant(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedPlant1 : Item - { - [Constructible] - public PottedPlant1() : base(0x11CB) - { - Weight = 100; - } + public class PottedPlant1 : Item + { + [Constructible] + public PottedPlant1() : base(0x11CB) + { + Weight = 100; + } - public PottedPlant1(Serial serial) : base(serial) - { - } + public PottedPlant1(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedPlant2 : Item - { - [Constructible] - public PottedPlant2() : base(0x11CC) - { - Weight = 100; - } + public class PottedPlant2 : Item + { + [Constructible] + public PottedPlant2() : base(0x11CC) + { + Weight = 100; + } - public PottedPlant2(Serial serial) : base(serial) - { - } + public PottedPlant2(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/PlantsFlowers/Potted/PottedTrees.cs b/Scripts/Items/PlantsFlowers/Potted/PottedTrees.cs index bde0213b2..5de0dbe13 100644 --- a/Scripts/Items/PlantsFlowers/Potted/PottedTrees.cs +++ b/Scripts/Items/PlantsFlowers/Potted/PottedTrees.cs @@ -1,56 +1,56 @@ namespace Server.Items { - public class PottedTree : Item - { - [Constructible] - public PottedTree() : base(0x11C8) - { - Weight = 100; - } + public class PottedTree : Item + { + [Constructible] + public PottedTree() : base(0x11C8) + { + Weight = 100; + } - public PottedTree(Serial serial) : base(serial) - { - } + public PottedTree(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PottedTree1 : Item - { - [Constructible] - public PottedTree1() : base(0x11C9) - { - Weight = 100; - } + public class PottedTree1 : Item + { + [Constructible] + public PottedTree1() : base(0x11C9) + { + Weight = 100; + } - public PottedTree1(Serial serial) : base(serial) - { - } + public PottedTree1(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Quivers/BaseQuiver.cs b/Scripts/Items/Quivers/BaseQuiver.cs index 04ebce8f3..bf1e1207e 100644 --- a/Scripts/Items/Quivers/BaseQuiver.cs +++ b/Scripts/Items/Quivers/BaseQuiver.cs @@ -3,456 +3,477 @@ using Server.Engines.Craft; namespace Server.Items { - public class BaseQuiver : Container, ICraftable - { - public override int DefaultGumpID => 0x108; - public override int DefaultMaxItems => 1; - public override int DefaultMaxWeight => 50; - public override double DefaultWeight => 2.0; - - private AosAttributes m_Attributes; - private int m_Capacity; - private int m_LowerAmmoCost; - private int m_WeightReduction; - private int m_DamageIncrease; - - [CommandProperty( AccessLevel.GameMaster)] - public AosAttributes Attributes - { - get => m_Attributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster)] - public int Capacity - { - get => m_Capacity; - set{ m_Capacity = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster)] - public int LowerAmmoCost - { - get => m_LowerAmmoCost; - set{ m_LowerAmmoCost = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster)] - public int WeightReduction - { - get => m_WeightReduction; - set{ m_WeightReduction = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster)] - public int DamageIncrease - { - get => m_DamageIncrease; - set{ m_DamageIncrease = value; InvalidateProperties(); } - } - - private Mobile m_Crafter; - private ClothingQuality m_Quality; - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public ClothingQuality Quality - { - get => m_Quality; - set{ m_Quality = value; InvalidateProperties(); } - } - - public Item Ammo => Items.Count > 0 ? Items[ 0 ] : null; - - public BaseQuiver() : this( 0x2FB7 ) - { - } - - public BaseQuiver( int itemID ) : base( itemID ) - { - Weight = 2.0; - Capacity = 500; - Layer = Layer.Cloak; - - m_Attributes = new AosAttributes( this ); - - DamageIncrease = 10; - } - - public BaseQuiver( Serial serial ) : base( serial ) - { - } - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is BaseQuiver quiver) ) - return; - - quiver.m_Attributes = new AosAttributes( newItem, m_Attributes ); - } - - public override void UpdateTotal( Item sender, TotalType type, int delta ) - { - InvalidateProperties(); - - base.UpdateTotal(sender, type, delta); - } - - public override int GetTotal( TotalType type ) - { - int total = base.GetTotal( type ); - - if ( type == TotalType.Weight ) - total -= total * m_WeightReduction / 100; - - return total; - } - - private static Type[] m_Ammo = { - typeof( Arrow ), typeof( Bolt ) - }; - - public bool CheckType( Item item ) - { - Type type = item.GetType(); - Item ammo = Ammo; - - if ( ammo != null ) - { - if ( ammo.GetType() == type ) - return true; - } - else - { - for ( int i = 0; i < m_Ammo.Length; i++ ) - { - if ( type == m_Ammo[ i ] ) - return true; - } - } - - return false; - } - - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if ( !CheckType( item ) ) - { - if ( message ) - m.SendLocalizedMessage( 1074836 ); // The container can not hold that type of object. - - return false; - } + public class BaseQuiver : Container, ICraftable + { + private static Type[] m_Ammo = + { + typeof(Arrow), typeof(Bolt) + }; + + private AosAttributes m_Attributes; + private int m_Capacity; + + private Mobile m_Crafter; + private int m_DamageIncrease; + private int m_LowerAmmoCost; + private ClothingQuality m_Quality; + private int m_WeightReduction; + + public BaseQuiver() : this(0x2FB7) + { + } + + public BaseQuiver(int itemID) : base(itemID) + { + Weight = 2.0; + Capacity = 500; + Layer = Layer.Cloak; + + m_Attributes = new AosAttributes(this); + + DamageIncrease = 10; + } + + public BaseQuiver(Serial serial) : base(serial) + { + } + + public override int DefaultGumpID => 0x108; + public override int DefaultMaxItems => 1; + public override int DefaultMaxWeight => 50; + public override double DefaultWeight => 2.0; + + [CommandProperty(AccessLevel.GameMaster)] + public AosAttributes Attributes + { + get => m_Attributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Capacity + { + get => m_Capacity; + set + { + m_Capacity = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int LowerAmmoCost + { + get => m_LowerAmmoCost; + set + { + m_LowerAmmoCost = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int WeightReduction + { + get => m_WeightReduction; + set + { + m_WeightReduction = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DamageIncrease + { + get => m_DamageIncrease; + set + { + m_DamageIncrease = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public ClothingQuality Quality + { + get => m_Quality; + set + { + m_Quality = value; + InvalidateProperties(); + } + } + + public Item Ammo => Items.Count > 0 ? Items[0] : null; + + #region ICraftable + + public virtual int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, + BaseTool tool, CraftItem craftItem, int resHue) + { + Quality = (ClothingQuality)quality; + + if (makersMark) + Crafter = from; + + return quality; + } + + #endregion + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is BaseQuiver quiver)) + return; + + quiver.m_Attributes = new AosAttributes(newItem, m_Attributes); + } + + public override void UpdateTotal(Item sender, TotalType type, int delta) + { + InvalidateProperties(); + + base.UpdateTotal(sender, type, delta); + } + + public override int GetTotal(TotalType type) + { + int total = base.GetTotal(type); + + if (type == TotalType.Weight) + total -= total * m_WeightReduction / 100; + + return total; + } + + public bool CheckType(Item item) + { + Type type = item.GetType(); + Item ammo = Ammo; + + if (ammo != null) + { + if (ammo.GetType() == type) + return true; + } + else + { + for (int i = 0; i < m_Ammo.Length; i++) + if (type == m_Ammo[i]) + return true; + } + + return false; + } + + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (!CheckType(item)) + { + if (message) + m.SendLocalizedMessage(1074836); // The container can not hold that type of object. + + return false; + } + + if (Items.Count < DefaultMaxItems) + { + if (item.Amount <= m_Capacity) + return base.CheckHold(m, item, message, checkItems, plusItems, plusWeight); - if ( Items.Count < DefaultMaxItems ) - { - if ( item.Amount <= m_Capacity ) - return base.CheckHold( m, item, message, checkItems, plusItems, plusWeight ); + return false; + } - return false; - } + if (checkItems) + return false; - if ( checkItems ) - return false; + Item ammo = Ammo; - Item ammo = Ammo; + if (ammo == null || ammo.Deleted) + return false; - if ( ammo == null || ammo.Deleted ) - return false; + if (ammo.Amount + item.Amount <= m_Capacity) + return true; - if ( ammo.Amount + item.Amount <= m_Capacity ) - return true; + return false; + } - return false; - } + public override void AddItem(Item dropped) + { + base.AddItem(dropped); - public override void AddItem( Item dropped ) - { - base.AddItem( dropped ); + InvalidateWeight(); + } - InvalidateWeight(); - } + public override void RemoveItem(Item dropped) + { + base.RemoveItem(dropped); - public override void RemoveItem( Item dropped ) - { - base.RemoveItem( dropped ); + InvalidateWeight(); + } - InvalidateWeight(); - } + public override void OnAdded(IEntity parent) + { + if (parent is Mobile mob) m_Attributes.AddStatBonuses(mob); + } - public override void OnAdded(IEntity parent) - { - if ( parent is Mobile mob ) - { - m_Attributes.AddStatBonuses( mob ); - } - } + public override void OnRemoved(IEntity parent) + { + if (parent is Mobile mob) m_Attributes.RemoveStatBonuses(mob); + } - public override void OnRemoved(IEntity parent) - { - if ( parent is Mobile mob ) - { - m_Attributes.RemoveStatBonuses( mob ); - } - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if (m_Quality == ClothingQuality.Exceptional) + list.Add(1063341); // exceptional - if ( m_Quality == ClothingQuality.Exceptional ) - list.Add( 1063341 ); // exceptional + Item ammo = Ammo; - Item ammo = Ammo; + if (ammo != null) + { + if (ammo is Arrow) + list.Add(1075265, "{0}\t{1}", ammo.Amount, Capacity); // Ammo: ~1_QUANTITY~/~2_CAPACITY~ arrows + else if (ammo is Bolt) + list.Add(1075266, "{0}\t{1}", ammo.Amount, Capacity); // Ammo: ~1_QUANTITY~/~2_CAPACITY~ bolts + } + else + { + list.Add(1075265, "{0}\t{1}", 0, Capacity); // Ammo: ~1_QUANTITY~/~2_CAPACITY~ arrows + } - if ( ammo != null ) - { - if ( ammo is Arrow ) - list.Add( 1075265, "{0}\t{1}", ammo.Amount, Capacity ); // Ammo: ~1_QUANTITY~/~2_CAPACITY~ arrows - else if ( ammo is Bolt ) - list.Add( 1075266, "{0}\t{1}", ammo.Amount, Capacity ); // Ammo: ~1_QUANTITY~/~2_CAPACITY~ bolts - } - else - list.Add( 1075265, "{0}\t{1}", 0, Capacity ); // Ammo: ~1_QUANTITY~/~2_CAPACITY~ arrows + int prop; - int prop; + if ((prop = m_DamageIncrease) != 0) + list.Add(1074762, prop.ToString()); // Damage modifier: ~1_PERCENT~% - if ( (prop = m_DamageIncrease) != 0 ) - list.Add( 1074762, prop.ToString() ); // Damage modifier: ~1_PERCENT~% + int phys, fire, cold, pois, nrgy, chaos, direct; + phys = fire = cold = pois = nrgy = chaos = direct = 0; - int phys, fire, cold, pois, nrgy, chaos, direct; - phys = fire = cold = pois = nrgy = chaos = direct = 0; + AlterBowDamage(ref phys, ref fire, ref cold, ref pois, ref nrgy, ref chaos, ref direct); - AlterBowDamage( ref phys, ref fire, ref cold, ref pois, ref nrgy, ref chaos, ref direct ); + if (phys != 0) + list.Add(1060403, phys.ToString()); // physical damage ~1_val~% - if ( phys != 0 ) - list.Add( 1060403, phys.ToString() ); // physical damage ~1_val~% + if (fire != 0) + list.Add(1060405, fire.ToString()); // fire damage ~1_val~% - if ( fire != 0 ) - list.Add( 1060405, fire.ToString() ); // fire damage ~1_val~% + if (cold != 0) + list.Add(1060404, cold.ToString()); // cold damage ~1_val~% - if ( cold != 0 ) - list.Add( 1060404, cold.ToString() ); // cold damage ~1_val~% + if (pois != 0) + list.Add(1060406, pois.ToString()); // poison damage ~1_val~% - if ( pois != 0 ) - list.Add( 1060406, pois.ToString() ); // poison damage ~1_val~% + if (nrgy != 0) + list.Add(1060407, nrgy.ToString()); // energy damage ~1_val - if ( nrgy != 0 ) - list.Add( 1060407, nrgy.ToString() ); // energy damage ~1_val + if (chaos != 0) + list.Add(1072846, chaos.ToString()); // chaos damage ~1_val~% - if ( chaos != 0 ) - list.Add( 1072846, chaos.ToString() ); // chaos damage ~1_val~% + if (direct != 0) + list.Add(1079978, direct.ToString()); // Direct Damage: ~1_PERCENT~% - if ( direct != 0 ) - list.Add( 1079978, direct.ToString() ); // Direct Damage: ~1_PERCENT~% + list.Add(1075085); // Requirement: Mondain's Legacy - list.Add( 1075085 ); // Requirement: Mondain's Legacy + if ((prop = m_Attributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% - if ( (prop = m_Attributes.DefendChance) != 0 ) - list.Add( 1060408, prop.ToString() ); // defense chance increase ~1_val~% + if ((prop = m_Attributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ - if ( (prop = m_Attributes.BonusDex) != 0 ) - list.Add( 1060409, prop.ToString() ); // dexterity bonus ~1_val~ + if ((prop = m_Attributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% - if ( (prop = m_Attributes.EnhancePotions) != 0 ) - list.Add( 1060411, prop.ToString() ); // enhance potions ~1_val~% + if ((prop = m_Attributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ - if ( (prop = m_Attributes.CastRecovery) != 0 ) - list.Add( 1060412, prop.ToString() ); // faster cast recovery ~1_val~ + if ((prop = m_Attributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - if ( (prop = m_Attributes.CastSpeed) != 0 ) - list.Add( 1060413, prop.ToString() ); // faster casting ~1_val~ + if ((prop = m_Attributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - if ( (prop = m_Attributes.AttackChance) != 0 ) - list.Add( 1060415, prop.ToString() ); // hit chance increase ~1_val~% + if ((prop = m_Attributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if ( (prop = m_Attributes.BonusHits) != 0 ) - list.Add( 1060431, prop.ToString() ); // hit point increase ~1_val~ + if ((prop = m_Attributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - if ( (prop = m_Attributes.BonusInt) != 0 ) - list.Add( 1060432, prop.ToString() ); // intelligence bonus ~1_val~ + if ((prop = m_Attributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if ( (prop = m_Attributes.LowerManaCost) != 0 ) - list.Add( 1060433, prop.ToString() ); // lower mana cost ~1_val~% + if ((prop = m_Attributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - if ( (prop = m_Attributes.LowerRegCost) != 0 ) - list.Add( 1060434, prop.ToString() ); // lower reagent cost ~1_val~% + if ((prop = m_Attributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - if ( (prop = m_Attributes.Luck) != 0 ) - list.Add( 1060436, prop.ToString() ); // luck ~1_val~ + if ((prop = m_Attributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - if ( (prop = m_Attributes.BonusMana) != 0 ) - list.Add( 1060439, prop.ToString() ); // mana increase ~1_val~ + if ((prop = m_Attributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - if ( (prop = m_Attributes.RegenMana) != 0 ) - list.Add( 1060440, prop.ToString() ); // mana regeneration ~1_val~ + if ((prop = m_Attributes.NightSight) != 0) + list.Add(1060441); // night sight - if ( (prop = m_Attributes.NightSight) != 0 ) - list.Add( 1060441 ); // night sight + if ((prop = m_Attributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - if ( (prop = m_Attributes.ReflectPhysical) != 0 ) - list.Add( 1060442, prop.ToString() ); // reflect physical damage ~1_val~% + if ((prop = m_Attributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - if ( (prop = m_Attributes.RegenStam) != 0 ) - list.Add( 1060443, prop.ToString() ); // stamina regeneration ~1_val~ + if ((prop = m_Attributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if ( (prop = m_Attributes.RegenHits) != 0 ) - list.Add( 1060444, prop.ToString() ); // hit point regeneration ~1_val~ + if ((prop = m_Attributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - if ( (prop = m_Attributes.SpellDamage) != 0 ) - list.Add( 1060483, prop.ToString() ); // spell damage increase ~1_val~% + if ((prop = m_Attributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - if ( (prop = m_Attributes.BonusStam) != 0 ) - list.Add( 1060484, prop.ToString() ); // stamina increase ~1_val~ + if ((prop = m_Attributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - if ( (prop = m_Attributes.BonusStr) != 0 ) - list.Add( 1060485, prop.ToString() ); // strength bonus ~1_val~ + if ((prop = m_Attributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - if ( (prop = m_Attributes.WeaponSpeed) != 0 ) - list.Add( 1060486, prop.ToString() ); // swing speed increase ~1_val~% + if ((prop = m_LowerAmmoCost) > 0) + list.Add(1075208, prop.ToString()); // Lower Ammo Cost ~1_Percentage~% - if ( (prop = m_LowerAmmoCost) > 0 ) - list.Add( 1075208, prop.ToString() ); // Lower Ammo Cost ~1_Percentage~% + double weight = 0; - double weight = 0; + if (ammo != null) + weight = ammo.Weight * ammo.Amount; - if ( ammo != null ) - weight = ammo.Weight * ammo.Amount; + list.Add(1072241, "{0}\t{1}\t{2}\t{3}", Items.Count, DefaultMaxItems, (int)weight, + DefaultMaxWeight); // Contents: ~1_COUNT~/~2_MAXCOUNT items, ~3_WEIGHT~/~4_MAXWEIGHT~ stones - list.Add( 1072241, "{0}\t{1}\t{2}\t{3}", Items.Count, DefaultMaxItems, (int) weight, DefaultMaxWeight ); // Contents: ~1_COUNT~/~2_MAXCOUNT items, ~3_WEIGHT~/~4_MAXWEIGHT~ stones + if ((prop = m_WeightReduction) != 0) + list.Add(1072210, prop.ToString()); // Weight reduction: ~1_PERCENTAGE~% + } - if ( (prop = m_WeightReduction) != 0 ) - list.Add( 1072210, prop.ToString() ); // Weight reduction: ~1_PERCENTAGE~% - } + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [Flags] - private enum SaveFlag - { - None = 0x00000000, - Attributes = 0x00000001, - DamageModifier = 0x00000002, - LowerAmmoCost = 0x00000004, - WeightReduction = 0x00000008, - Crafter = 0x00000010, - Quality = 0x00000020, - Capacity = 0x00000040, - DamageIncrease = 0x00000080 - } + writer.Write(0); // version - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + SaveFlag flags = SaveFlag.None; - writer.Write( 0 ); // version + SetSaveFlag(ref flags, SaveFlag.Attributes, !m_Attributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.LowerAmmoCost, m_LowerAmmoCost != 0); + SetSaveFlag(ref flags, SaveFlag.WeightReduction, m_WeightReduction != 0); + SetSaveFlag(ref flags, SaveFlag.DamageIncrease, m_DamageIncrease != 0); + SetSaveFlag(ref flags, SaveFlag.Crafter, m_Crafter != null); + SetSaveFlag(ref flags, SaveFlag.Quality, true); + SetSaveFlag(ref flags, SaveFlag.Capacity, m_Capacity > 0); - SaveFlag flags = SaveFlag.None; + writer.WriteEncodedInt((int)flags); - SetSaveFlag( ref flags, SaveFlag.Attributes, !m_Attributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.LowerAmmoCost, m_LowerAmmoCost != 0 ); - SetSaveFlag( ref flags, SaveFlag.WeightReduction, m_WeightReduction != 0 ); - SetSaveFlag( ref flags, SaveFlag.DamageIncrease, m_DamageIncrease != 0 ); - SetSaveFlag( ref flags, SaveFlag.Crafter, m_Crafter != null ); - SetSaveFlag( ref flags, SaveFlag.Quality, true ); - SetSaveFlag( ref flags, SaveFlag.Capacity, m_Capacity > 0 ); + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_Attributes.Serialize(writer); - writer.WriteEncodedInt( (int) flags ); + if (GetSaveFlag(flags, SaveFlag.LowerAmmoCost)) + writer.Write(m_LowerAmmoCost); - if ( GetSaveFlag( flags, SaveFlag.Attributes ) ) - m_Attributes.Serialize( writer ); + if (GetSaveFlag(flags, SaveFlag.WeightReduction)) + writer.Write(m_WeightReduction); - if ( GetSaveFlag( flags, SaveFlag.LowerAmmoCost ) ) - writer.Write( (int) m_LowerAmmoCost ); + if (GetSaveFlag(flags, SaveFlag.DamageIncrease)) + writer.Write(m_DamageIncrease); - if ( GetSaveFlag( flags, SaveFlag.WeightReduction ) ) - writer.Write( (int) m_WeightReduction ); + if (GetSaveFlag(flags, SaveFlag.Crafter)) + writer.Write(m_Crafter); - if ( GetSaveFlag( flags, SaveFlag.DamageIncrease ) ) - writer.Write( (int) m_DamageIncrease ); + if (GetSaveFlag(flags, SaveFlag.Quality)) + writer.Write((int)m_Quality); - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - writer.Write( (Mobile) m_Crafter ); + if (GetSaveFlag(flags, SaveFlag.Capacity)) + writer.Write(m_Capacity); + } - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - writer.Write( (int) m_Quality ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( GetSaveFlag( flags, SaveFlag.Capacity ) ) - writer.Write( (int) m_Capacity ); - } + int version = reader.ReadInt(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); - int version = reader.ReadInt(); + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_Attributes = new AosAttributes(this, reader); + else + m_Attributes = new AosAttributes(this); - SaveFlag flags = (SaveFlag) reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.LowerAmmoCost)) + m_LowerAmmoCost = reader.ReadInt(); - if ( GetSaveFlag( flags, SaveFlag.Attributes ) ) - m_Attributes = new AosAttributes( this, reader ); - else - m_Attributes = new AosAttributes( this ); + if (GetSaveFlag(flags, SaveFlag.WeightReduction)) + m_WeightReduction = reader.ReadInt(); - if ( GetSaveFlag( flags, SaveFlag.LowerAmmoCost ) ) - m_LowerAmmoCost = reader.ReadInt(); + if (GetSaveFlag(flags, SaveFlag.DamageIncrease)) + m_DamageIncrease = reader.ReadInt(); - if ( GetSaveFlag( flags, SaveFlag.WeightReduction ) ) - m_WeightReduction = reader.ReadInt(); + if (GetSaveFlag(flags, SaveFlag.Crafter)) + m_Crafter = reader.ReadMobile(); - if ( GetSaveFlag( flags, SaveFlag.DamageIncrease ) ) - m_DamageIncrease = reader.ReadInt(); + if (GetSaveFlag(flags, SaveFlag.Quality)) + m_Quality = (ClothingQuality)reader.ReadInt(); - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - m_Crafter = reader.ReadMobile(); + if (GetSaveFlag(flags, SaveFlag.Capacity)) + m_Capacity = reader.ReadInt(); + } - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - m_Quality = (ClothingQuality) reader.ReadInt(); + public virtual void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + } - if ( GetSaveFlag( flags, SaveFlag.Capacity ) ) - m_Capacity = reader.ReadInt(); - } - - public virtual void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - } - - public void InvalidateWeight() - { - if ( RootParent is Mobile m ) - { - m.UpdateTotals(); - } - } + public void InvalidateWeight() + { + if (RootParent is Mobile m) m.UpdateTotals(); + } - #region ICraftable - public virtual int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (ClothingQuality) quality; - - if ( makersMark ) - Crafter = from; - - return quality; - } - #endregion - } -} + [Flags] + private enum SaveFlag + { + None = 0x00000000, + Attributes = 0x00000001, + DamageModifier = 0x00000002, + LowerAmmoCost = 0x00000004, + WeightReduction = 0x00000008, + Crafter = 0x00000010, + Quality = 0x00000020, + Capacity = 0x00000040, + DamageIncrease = 0x00000080 + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Quivers/ElvenQuiver.cs b/Scripts/Items/Quivers/ElvenQuiver.cs index 557451b91..8fa899b54 100644 --- a/Scripts/Items/Quivers/ElvenQuiver.cs +++ b/Scripts/Items/Quivers/ElvenQuiver.cs @@ -1,32 +1,32 @@ namespace Server.Items { - [FlippableAttribute( 0x2FB7, 0x3171 )] - public class ElvenQuiver : BaseQuiver - { - public override int LabelNumber => 1032657; // elven quiver + [Flippable(0x2FB7, 0x3171)] + public class ElvenQuiver : BaseQuiver + { + [Constructible] + public ElvenQuiver() + { + WeightReduction = 30; + } - [Constructible] - public ElvenQuiver() - { - WeightReduction = 30; - } + public ElvenQuiver(Serial serial) : base(serial) + { + } - public ElvenQuiver( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1032657; // elven quiver - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Quivers/QuiverOfBlight.cs b/Scripts/Items/Quivers/QuiverOfBlight.cs index 1e9d9fc1b..07b2b9706 100644 --- a/Scripts/Items/Quivers/QuiverOfBlight.cs +++ b/Scripts/Items/Quivers/QuiverOfBlight.cs @@ -1,37 +1,38 @@ namespace Server.Items { - public class QuiverOfBlight : ElvenQuiver - { - public override int LabelNumber => 1073111; // Quiver of Blight + public class QuiverOfBlight : ElvenQuiver + { + [Constructible] + public QuiverOfBlight() + { + Hue = 0x4F3; + } - [Constructible] - public QuiverOfBlight() - { - Hue = 0x4F3; - } + public QuiverOfBlight(Serial serial) : base(serial) + { + } - public QuiverOfBlight( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073111; // Quiver of Blight - public override void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - phys = fire = nrgy = chaos = direct = 0; - cold = pois = 50; - } + public override void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + phys = fire = nrgy = chaos = direct = 0; + cold = pois = 50; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Quivers/QuiverOfFire.cs b/Scripts/Items/Quivers/QuiverOfFire.cs index 018473666..f191665b3 100644 --- a/Scripts/Items/Quivers/QuiverOfFire.cs +++ b/Scripts/Items/Quivers/QuiverOfFire.cs @@ -1,37 +1,38 @@ namespace Server.Items { - public class QuiverOfFire : ElvenQuiver - { - public override int LabelNumber => 1073109; // quiver of fire + public class QuiverOfFire : ElvenQuiver + { + [Constructible] + public QuiverOfFire() + { + Hue = 0x4E7; + } - [Constructible] - public QuiverOfFire() - { - Hue = 0x4E7; - } + public QuiverOfFire(Serial serial) : base(serial) + { + } - public QuiverOfFire( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073109; // quiver of fire - public override void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - cold = pois = nrgy = chaos = direct = 0; - phys = fire = 50; - } + public override void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + cold = pois = nrgy = chaos = direct = 0; + phys = fire = 50; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Quivers/QuiverOfIce.cs b/Scripts/Items/Quivers/QuiverOfIce.cs index 240dc4cf5..66a95e8f2 100644 --- a/Scripts/Items/Quivers/QuiverOfIce.cs +++ b/Scripts/Items/Quivers/QuiverOfIce.cs @@ -1,37 +1,38 @@ namespace Server.Items { - public class QuiverOfIce : ElvenQuiver - { - public override int LabelNumber => 1073110; // quiver of ice + public class QuiverOfIce : ElvenQuiver + { + [Constructible] + public QuiverOfIce() + { + Hue = 0x4ED; + } - [Constructible] - public QuiverOfIce() - { - Hue = 0x4ED; - } + public QuiverOfIce(Serial serial) : base(serial) + { + } - public QuiverOfIce( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073110; // quiver of ice - public override void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - fire = pois = nrgy = chaos = direct = 0; - phys = cold = 50; - } + public override void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + fire = pois = nrgy = chaos = direct = 0; + phys = cold = 50; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Quivers/QuiverOfLightning.cs b/Scripts/Items/Quivers/QuiverOfLightning.cs index 6f79e2d82..4039b8c0e 100644 --- a/Scripts/Items/Quivers/QuiverOfLightning.cs +++ b/Scripts/Items/Quivers/QuiverOfLightning.cs @@ -1,37 +1,38 @@ namespace Server.Items { - public class QuiverOfLightning : ElvenQuiver - { - public override int LabelNumber => 1073112; // Quiver of Lightning + public class QuiverOfLightning : ElvenQuiver + { + [Constructible] + public QuiverOfLightning() + { + Hue = 0x4F9; + } - [Constructible] - public QuiverOfLightning() - { - Hue = 0x4F9; - } + public QuiverOfLightning(Serial serial) : base(serial) + { + } - public QuiverOfLightning( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073112; // Quiver of Lightning - public override void AlterBowDamage( ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, ref int chaos, ref int direct ) - { - fire = cold = pois = chaos = direct = 0; - phys = nrgy = 50; - } + public override void AlterBowDamage(ref int phys, ref int fire, ref int cold, ref int pois, ref int nrgy, + ref int chaos, ref int direct) + { + fire = cold = pois = chaos = direct = 0; + phys = nrgy = 50; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Arrows/Arrow.cs b/Scripts/Items/Resources/Arrows/Arrow.cs index 1c879789d..fba85c744 100644 --- a/Scripts/Items/Resources/Arrows/Arrow.cs +++ b/Scripts/Items/Resources/Arrows/Arrow.cs @@ -1,42 +1,40 @@ namespace Server.Items { - public class Arrow : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Arrow : Item, ICommodity + { + [Constructible] + public Arrow() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public Arrow(int amount) : base(0xF3F) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Arrow() : this( 1 ) - { - } + public Arrow(Serial serial) : base(serial) + { + } - [Constructible] - public Arrow( int amount ) : base( 0xF3F ) - { - Stackable = true; - Amount = amount; - } + public override double DefaultWeight => 0.1; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public Arrow( Serial serial ) : base( serial ) - { - } - + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Arrows/Bolt.cs b/Scripts/Items/Resources/Arrows/Bolt.cs index 003effe1b..67aa02d56 100644 --- a/Scripts/Items/Resources/Arrows/Bolt.cs +++ b/Scripts/Items/Resources/Arrows/Bolt.cs @@ -1,42 +1,40 @@ namespace Server.Items { - public class Bolt : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Bolt : Item, ICommodity + { + [Constructible] + public Bolt() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public Bolt(int amount) : base(0x1BFB) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Bolt() : this( 1 ) - { - } + public Bolt(Serial serial) : base(serial) + { + } - [Constructible] - public Bolt( int amount ) : base( 0x1BFB ) - { - Stackable = true; - Amount = amount; - } + public override double DefaultWeight => 0.1; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public Bolt( Serial serial ) : base( serial ) - { - } - + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Arrows/Feather.cs b/Scripts/Items/Resources/Arrows/Feather.cs index 124981ee5..3af198b1e 100644 --- a/Scripts/Items/Resources/Arrows/Feather.cs +++ b/Scripts/Items/Resources/Arrows/Feather.cs @@ -1,42 +1,39 @@ namespace Server.Items { - public class Feather : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Feather : Item, ICommodity + { + [Constructible] + public Feather() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public Feather(int amount) : base(0x1BD1) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Feather() : this( 1 ) - { - } + public Feather(Serial serial) : base(serial) + { + } - [Constructible] - public Feather( int amount ) : base( 0x1BD1 ) - { - Stackable = true; - Amount = amount; - } + public override double DefaultWeight => 0.1; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public Feather( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Arrows/Shaft.cs b/Scripts/Items/Resources/Arrows/Shaft.cs index a01adc17d..90a285426 100644 --- a/Scripts/Items/Resources/Arrows/Shaft.cs +++ b/Scripts/Items/Resources/Arrows/Shaft.cs @@ -1,42 +1,40 @@ namespace Server.Items { - public class Shaft : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Shaft : Item, ICommodity + { + [Constructible] + public Shaft() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public Shaft(int amount) : base(0x1BD4) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Shaft() : this( 1 ) - { - } + public Shaft(Serial serial) : base(serial) + { + } - [Constructible] - public Shaft( int amount ) : base( 0x1BD4 ) - { - Stackable = true; - Amount = amount; - } + public override double DefaultWeight => 0.1; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public Shaft( Serial serial ) : base( serial ) - { - } - + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Blacksmithing/Ingots.cs b/Scripts/Items/Resources/Blacksmithing/Ingots.cs index c0f8f6510..85cd94b17 100644 --- a/Scripts/Items/Resources/Blacksmithing/Ingots.cs +++ b/Scripts/Items/Resources/Blacksmithing/Ingots.cs @@ -1,422 +1,428 @@ namespace Server.Items { - public abstract class BaseIngot : Item, ICommodity - { - private CraftResource m_Resource; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; InvalidateProperties(); } - } - - public override double DefaultWeight => 0.1; - - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( (int) m_Resource ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - case 0: - { - OreInfo info; - - switch ( reader.ReadInt() ) - { - case 0: info = OreInfo.Iron; break; - case 1: info = OreInfo.DullCopper; break; - case 2: info = OreInfo.ShadowIron; break; - case 3: info = OreInfo.Copper; break; - case 4: info = OreInfo.Bronze; break; - case 5: info = OreInfo.Gold; break; - case 6: info = OreInfo.Agapite; break; - case 7: info = OreInfo.Verite; break; - case 8: info = OreInfo.Valorite; break; - default: info = null; break; - } - - m_Resource = CraftResources.GetFromOreInfo( info ); - break; - } - } - } - - public BaseIngot( CraftResource resource ) : this( resource, 1 ) - { - } - - public BaseIngot( CraftResource resource, int amount ) : base( 0x1BF2 ) - { - Stackable = true; - Amount = amount; - Hue = CraftResources.GetHue( resource ); - - m_Resource = resource; - } - - public BaseIngot( Serial serial ) : base( serial ) - { - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( Amount > 1 ) - list.Add( 1050039, "{0}\t#{1}", Amount, 1027154 ); // ~1_NUMBER~ ~2_ITEMNAME~ - else - list.Add( 1027154 ); // ingots - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); - - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } - - public override int LabelNumber - { - get - { - if ( m_Resource >= CraftResource.DullCopper && m_Resource <= CraftResource.Valorite ) - return 1042684 + (int)(m_Resource - CraftResource.DullCopper); - - return 1042692; - } - } - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class IronIngot : BaseIngot - { - [Constructible] - public IronIngot() : this( 1 ) - { - } - - [Constructible] - public IronIngot( int amount ) : base( CraftResource.Iron, amount ) - { - } - - public IronIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class DullCopperIngot : BaseIngot - { - [Constructible] - public DullCopperIngot() : this( 1 ) - { - } - - [Constructible] - public DullCopperIngot( int amount ) : base( CraftResource.DullCopper, amount ) - { - } - - public DullCopperIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class ShadowIronIngot : BaseIngot - { - [Constructible] - public ShadowIronIngot() : this( 1 ) - { - } - - [Constructible] - public ShadowIronIngot( int amount ) : base( CraftResource.ShadowIron, amount ) - { - } - - public ShadowIronIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class CopperIngot : BaseIngot - { - [Constructible] - public CopperIngot() : this( 1 ) - { - } - - [Constructible] - public CopperIngot( int amount ) : base( CraftResource.Copper, amount ) - { - } - - public CopperIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class BronzeIngot : BaseIngot - { - [Constructible] - public BronzeIngot() : this( 1 ) - { - } - - [Constructible] - public BronzeIngot( int amount ) : base( CraftResource.Bronze, amount ) - { - } - - public BronzeIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class GoldIngot : BaseIngot - { - [Constructible] - public GoldIngot() : this( 1 ) - { - } - - [Constructible] - public GoldIngot( int amount ) : base( CraftResource.Gold, amount ) - { - } - - public GoldIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class AgapiteIngot : BaseIngot - { - [Constructible] - public AgapiteIngot() : this( 1 ) - { - } - - [Constructible] - public AgapiteIngot( int amount ) : base( CraftResource.Agapite, amount ) - { - } - - public AgapiteIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class VeriteIngot : BaseIngot - { - [Constructible] - public VeriteIngot() : this( 1 ) - { - } - - [Constructible] - public VeriteIngot( int amount ) : base( CraftResource.Verite, amount ) - { - } - - public VeriteIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - [FlippableAttribute( 0x1BF2, 0x1BEF )] - public class ValoriteIngot : BaseIngot - { - [Constructible] - public ValoriteIngot() : this( 1 ) - { - } - - [Constructible] - public ValoriteIngot( int amount ) : base( CraftResource.Valorite, amount ) - { - } - - public ValoriteIngot( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } + public abstract class BaseIngot : Item, ICommodity + { + private CraftResource m_Resource; + + public BaseIngot(CraftResource resource) : this(resource, 1) + { + } + + public BaseIngot(CraftResource resource, int amount) : base(0x1BF2) + { + Stackable = true; + Amount = amount; + Hue = CraftResources.GetHue(resource); + + m_Resource = resource; + } + + public BaseIngot(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } + + public override double DefaultWeight => 0.1; + + public override int LabelNumber + { + get + { + if (m_Resource >= CraftResource.DullCopper && m_Resource <= CraftResource.Valorite) + return 1042684 + (m_Resource - CraftResource.DullCopper); + + return 1042692; + } + } + + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write((int)m_Resource); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + case 0: + { + OreInfo info; + + switch (reader.ReadInt()) + { + case 0: + info = OreInfo.Iron; + break; + case 1: + info = OreInfo.DullCopper; + break; + case 2: + info = OreInfo.ShadowIron; + break; + case 3: + info = OreInfo.Copper; + break; + case 4: + info = OreInfo.Bronze; + break; + case 5: + info = OreInfo.Gold; + break; + case 6: + info = OreInfo.Agapite; + break; + case 7: + info = OreInfo.Verite; + break; + case 8: + info = OreInfo.Valorite; + break; + default: + info = null; + break; + } + + m_Resource = CraftResources.GetFromOreInfo(info); + break; + } + } + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (Amount > 1) + list.Add(1050039, "{0}\t#{1}", Amount, 1027154); // ~1_NUMBER~ ~2_ITEMNAME~ + else + list.Add(1027154); // ingots + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); + + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class IronIngot : BaseIngot + { + [Constructible] + public IronIngot() : this(1) + { + } + + [Constructible] + public IronIngot(int amount) : base(CraftResource.Iron, amount) + { + } + + public IronIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class DullCopperIngot : BaseIngot + { + [Constructible] + public DullCopperIngot() : this(1) + { + } + + [Constructible] + public DullCopperIngot(int amount) : base(CraftResource.DullCopper, amount) + { + } + + public DullCopperIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class ShadowIronIngot : BaseIngot + { + [Constructible] + public ShadowIronIngot() : this(1) + { + } + + [Constructible] + public ShadowIronIngot(int amount) : base(CraftResource.ShadowIron, amount) + { + } + + public ShadowIronIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class CopperIngot : BaseIngot + { + [Constructible] + public CopperIngot() : this(1) + { + } + + [Constructible] + public CopperIngot(int amount) : base(CraftResource.Copper, amount) + { + } + + public CopperIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class BronzeIngot : BaseIngot + { + [Constructible] + public BronzeIngot() : this(1) + { + } + + [Constructible] + public BronzeIngot(int amount) : base(CraftResource.Bronze, amount) + { + } + + public BronzeIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class GoldIngot : BaseIngot + { + [Constructible] + public GoldIngot() : this(1) + { + } + + [Constructible] + public GoldIngot(int amount) : base(CraftResource.Gold, amount) + { + } + + public GoldIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class AgapiteIngot : BaseIngot + { + [Constructible] + public AgapiteIngot() : this(1) + { + } + + [Constructible] + public AgapiteIngot(int amount) : base(CraftResource.Agapite, amount) + { + } + + public AgapiteIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class VeriteIngot : BaseIngot + { + [Constructible] + public VeriteIngot() : this(1) + { + } + + [Constructible] + public VeriteIngot(int amount) : base(CraftResource.Verite, amount) + { + } + + public VeriteIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x1BF2, 0x1BEF)] + public class ValoriteIngot : BaseIngot + { + [Constructible] + public ValoriteIngot() : this(1) + { + } + + [Constructible] + public ValoriteIngot(int amount) : base(CraftResource.Valorite, amount) + { + } + + public ValoriteIngot(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Blacksmithing/Ore.cs b/Scripts/Items/Resources/Blacksmithing/Ore.cs index 6065d3070..0f9a7d423 100644 --- a/Scripts/Items/Resources/Blacksmithing/Ore.cs +++ b/Scripts/Items/Resources/Blacksmithing/Ore.cs @@ -1,699 +1,752 @@ -using Server.Targeting; using Server.Engines.Craft; using Server.Mobiles; +using Server.Targeting; namespace Server.Items { - public abstract class BaseOre : Item - { - private CraftResource m_Resource; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; InvalidateProperties(); } - } - - public abstract BaseIngot GetIngot(); - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( (int) m_Resource ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - case 0: - { - OreInfo info; - - switch ( reader.ReadInt() ) - { - case 0: info = OreInfo.Iron; break; - case 1: info = OreInfo.DullCopper; break; - case 2: info = OreInfo.ShadowIron; break; - case 3: info = OreInfo.Copper; break; - case 4: info = OreInfo.Bronze; break; - case 5: info = OreInfo.Gold; break; - case 6: info = OreInfo.Agapite; break; - case 7: info = OreInfo.Verite; break; - case 8: info = OreInfo.Valorite; break; - default: info = null; break; - } - - m_Resource = CraftResources.GetFromOreInfo( info ); - break; - } - } - } - - private static int RandomSize() - { - double rand = Utility.RandomDouble(); - - if ( rand < 0.12 ) - return 0x19B7; - if ( rand < 0.18 ) - return 0x19B8; - if ( rand < 0.25 ) - return 0x19BA; - return 0x19B9; - } - - public BaseOre( CraftResource resource ) : this( resource, 1 ) - { - } - - public BaseOre( CraftResource resource, int amount ) : base( RandomSize() ) - { - Stackable = true; - Amount = amount; - Hue = CraftResources.GetHue( resource ); - - m_Resource = resource; - } - - public BaseOre( Serial serial ) : base( serial ) - { - } - public override bool CanStackWith(Item dropped) - { - return dropped.Stackable && Stackable && dropped.GetType() == GetType() && dropped.Hue == Hue && dropped.Name == Name && (dropped.Amount + Amount) <= 60000 && dropped != this; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( Amount > 1 ) - list.Add( 1050039, "{0}\t#{1}", Amount, 1026583 ); // ~1_NUMBER~ ~2_ITEMNAME~ - else - list.Add( 1026583 ); // ore - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); - - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } - - public override int LabelNumber - { - get - { - if ( m_Resource >= CraftResource.DullCopper && m_Resource <= CraftResource.Valorite ) - return 1042845 + (int)(m_Resource - CraftResource.DullCopper); - - return 1042853; // iron ore; - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; - - if ( RootParent is BaseCreature ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible - } - else if ( from.InRange( GetWorldLocation(), 2 ) ) - { - from.SendLocalizedMessage( 501971 ); // Select the forge on which to smelt the ore, or another pile of ore with which to combine it. - from.Target = new InternalTarget( this ); - } - else - { - from.SendLocalizedMessage( 501976 ); // The ore is too far away. - } - } - - private class InternalTarget : Target - { - private BaseOre m_Ore; - - public InternalTarget( BaseOre ore ) : base ( 2, false, TargetFlags.None ) - { - m_Ore = ore; - } - - private bool IsForge( object obj ) - { - if ( Core.ML && obj is Mobile mobile && mobile.IsDeadBondedPet ) - return false; - - if ( obj.GetType().IsDefined( typeof( ForgeAttribute ), false ) ) - return true; - - int itemID = 0; - - if ( obj is Item item ) - itemID = item.ItemID; - else if ( obj is StaticTarget target ) - itemID = target.ItemID; - - return ( itemID == 4017 || (itemID >= 6522 && itemID <= 6569) ); - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Ore.Deleted ) - return; - - if ( !from.InRange( m_Ore.GetWorldLocation(), 2 ) ) - { - from.SendLocalizedMessage( 501976 ); // The ore is too far away. - return; - } - - #region Combine Ore - if ( targeted is BaseOre ore ) - { - if ( !ore.Movable ) - { - return; - } - if ( m_Ore == ore ) - { - from.SendLocalizedMessage( 501972 ); // Select another pile or ore with which to combine this. - from.Target = new InternalTarget( ore ); - return; - } - if ( ore.Resource != m_Ore.Resource ) - { - from.SendLocalizedMessage( 501979 ); // You cannot combine ores of different metals. - return; - } - - int worth = ore.Amount; - - if ( ore.ItemID == 0x19B9 ) - worth *= 8; - else if ( ore.ItemID == 0x19B7 ) - worth *= 2; - else - worth *= 4; - - int sourceWorth = m_Ore.Amount; - - if ( m_Ore.ItemID == 0x19B9 ) - sourceWorth *= 8; - else if ( m_Ore.ItemID == 0x19B7 ) - sourceWorth *= 2; - else - sourceWorth *= 4; - - worth += sourceWorth; - - int plusWeight = 0; - int newID = ore.ItemID; - - if ( ore.DefaultWeight != m_Ore.DefaultWeight ) - { - if ( ore.ItemID == 0x19B7 || m_Ore.ItemID == 0x19B7 ) - { - newID = 0x19B7; - } - else if ( ore.ItemID == 0x19B9 ) - { - newID = m_Ore.ItemID; - plusWeight = ore.Amount * 2; - } - else - { - plusWeight = m_Ore.Amount * 2; - } - } - - if ( ( ore.ItemID == 0x19B9 && worth > 120000 ) || ( ( ore.ItemID == 0x19B8 || ore.ItemID == 0x19BA ) && worth > 60000 ) || ( ore.ItemID == 0x19B7 && worth > 30000 ) ) - { - from.SendLocalizedMessage( 1062844 ); // There is too much ore to combine. - return; - } - if ( ore.RootParent is Mobile mobile && ( plusWeight + mobile.Backpack.TotalWeight ) > mobile.Backpack.MaxWeight ) - { - from.SendLocalizedMessage( 501978 ); // The weight is too great to combine in a container. - return; - } - - ore.ItemID = newID; - - if ( ore.ItemID == 0x19B9 ) - ore.Amount = worth / 8; - else if ( ore.ItemID == 0x19B7 ) - ore.Amount = worth / 2; - else - ore.Amount = worth / 4; - - m_Ore.Delete(); - return; - } - #endregion - - if ( IsForge( targeted ) ) - { - double difficulty; - - switch ( m_Ore.Resource ) - { - default: difficulty = 50.0; break; - case CraftResource.DullCopper: difficulty = 65.0; break; - case CraftResource.ShadowIron: difficulty = 70.0; break; - case CraftResource.Copper: difficulty = 75.0; break; - case CraftResource.Bronze: difficulty = 80.0; break; - case CraftResource.Gold: difficulty = 85.0; break; - case CraftResource.Agapite: difficulty = 90.0; break; - case CraftResource.Verite: difficulty = 95.0; break; - case CraftResource.Valorite: difficulty = 99.0; break; - } - - double minSkill = difficulty - 25.0; - double maxSkill = difficulty + 25.0; - - if ( difficulty > 50.0 && difficulty > from.Skills[SkillName.Mining].Value ) - { - from.SendLocalizedMessage( 501986 ); // You have no idea how to smelt this strange ore! - return; - } - - if ( m_Ore.ItemID == 0x19B7 && m_Ore.Amount < 2 ) - { - from.SendLocalizedMessage( 501987 ); // There is not enough metal-bearing ore in this pile to make an ingot. - return; - } - - if ( from.CheckTargetSkill( SkillName.Mining, targeted, minSkill, maxSkill ) ) - { - int toConsume = m_Ore.Amount; - - if ( toConsume <= 0 ) - { - from.SendLocalizedMessage( 501987 ); // There is not enough metal-bearing ore in this pile to make an ingot. - } - else - { - if ( toConsume > 30000 ) - toConsume = 30000; - - int ingotAmount; - - if ( m_Ore.ItemID == 0x19B7 ) - { - ingotAmount = toConsume / 2; - - if ( toConsume % 2 != 0 ) - --toConsume; - } - else if ( m_Ore.ItemID == 0x19B9 ) - { - ingotAmount = toConsume * 2; - } - else - { - ingotAmount = toConsume; - } - - BaseIngot ingot = m_Ore.GetIngot(); - ingot.Amount = ingotAmount; - - m_Ore.Consume( toConsume ); - from.AddToBackpack( ingot ); - //from.PlaySound( 0x57 ); - - from.SendLocalizedMessage( 501988 ); // You smelt the ore removing the impurities and put the metal in your backpack. - } - } - else - { - if ( m_Ore.Amount < 2 ) - { - if ( m_Ore.ItemID == 0x19B9 ) - m_Ore.ItemID = 0x19B8; - else - m_Ore.ItemID = 0x19B7; - } - else - { - m_Ore.Amount /= 2; - } - - from.SendLocalizedMessage( 501990 ); // You burn away the impurities but are left with less useable metal. - } - } - } - } - } - - public class IronOre : BaseOre - { - [Constructible] - public IronOre() : this( 1 ) - { - } - - [Constructible] - public IronOre( int amount ) : base( CraftResource.Iron, amount ) - { - } - - public IronOre( bool fixedSize ) : this( 1 ) - { - if ( fixedSize ) - ItemID = 0x19B8; - } - - public IronOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new IronIngot(); - } - } - - public class DullCopperOre : BaseOre - { - [Constructible] - public DullCopperOre() : this( 1 ) - { - } - - [Constructible] - public DullCopperOre( int amount ) : base( CraftResource.DullCopper, amount ) - { - } - - public DullCopperOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new DullCopperIngot(); - } - } - - public class ShadowIronOre : BaseOre - { - [Constructible] - public ShadowIronOre() : this( 1 ) - { - } - - [Constructible] - public ShadowIronOre( int amount ) : base( CraftResource.ShadowIron, amount ) - { - } - - public ShadowIronOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new ShadowIronIngot(); - } - } - - public class CopperOre : BaseOre - { - [Constructible] - public CopperOre() : this( 1 ) - { - } - - [Constructible] - public CopperOre( int amount ) : base( CraftResource.Copper, amount ) - { - } - - public CopperOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new CopperIngot(); - } - } - - public class BronzeOre : BaseOre - { - [Constructible] - public BronzeOre() : this( 1 ) - { - } - - [Constructible] - public BronzeOre( int amount ) : base( CraftResource.Bronze, amount ) - { - } - - public BronzeOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new BronzeIngot(); - } - } - - public class GoldOre : BaseOre - { - [Constructible] - public GoldOre() : this( 1 ) - { - } - - [Constructible] - public GoldOre( int amount ) : base( CraftResource.Gold, amount ) - { - } - - public GoldOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new GoldIngot(); - } - } - - public class AgapiteOre : BaseOre - { - [Constructible] - public AgapiteOre() : this( 1 ) - { - } - - [Constructible] - public AgapiteOre( int amount ) : base( CraftResource.Agapite, amount ) - { - } - - public AgapiteOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new AgapiteIngot(); - } - } - - public class VeriteOre : BaseOre - { - [Constructible] - public VeriteOre() : this( 1 ) - { - } - - [Constructible] - public VeriteOre( int amount ) : base( CraftResource.Verite, amount ) - { - } - - public VeriteOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new VeriteIngot(); - } - } - - public class ValoriteOre : BaseOre - { - [Constructible] - public ValoriteOre() : this( 1 ) - { - } - - [Constructible] - public ValoriteOre( int amount ) : base( CraftResource.Valorite, amount ) - { - } - - public ValoriteOre( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override BaseIngot GetIngot() - { - return new ValoriteIngot(); - } - } -} + public abstract class BaseOre : Item + { + private CraftResource m_Resource; + + public BaseOre(CraftResource resource) : this(resource, 1) + { + } + + public BaseOre(CraftResource resource, int amount) : base(RandomSize()) + { + Stackable = true; + Amount = amount; + Hue = CraftResources.GetHue(resource); + + m_Resource = resource; + } + + public BaseOre(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } + + public override int LabelNumber + { + get + { + if (m_Resource >= CraftResource.DullCopper && m_Resource <= CraftResource.Valorite) + return 1042845 + (m_Resource - CraftResource.DullCopper); + + return 1042853; // iron ore; + } + } + + public abstract BaseIngot GetIngot(); + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write((int)m_Resource); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + case 0: + { + OreInfo info; + + switch (reader.ReadInt()) + { + case 0: + info = OreInfo.Iron; + break; + case 1: + info = OreInfo.DullCopper; + break; + case 2: + info = OreInfo.ShadowIron; + break; + case 3: + info = OreInfo.Copper; + break; + case 4: + info = OreInfo.Bronze; + break; + case 5: + info = OreInfo.Gold; + break; + case 6: + info = OreInfo.Agapite; + break; + case 7: + info = OreInfo.Verite; + break; + case 8: + info = OreInfo.Valorite; + break; + default: + info = null; + break; + } + + m_Resource = CraftResources.GetFromOreInfo(info); + break; + } + } + } + + private static int RandomSize() + { + double rand = Utility.RandomDouble(); + + if (rand < 0.12) + return 0x19B7; + if (rand < 0.18) + return 0x19B8; + if (rand < 0.25) + return 0x19BA; + return 0x19B9; + } + + public override bool CanStackWith(Item dropped) + { + return dropped.Stackable && Stackable && dropped.GetType() == GetType() && dropped.Hue == Hue && + dropped.Name == Name && dropped.Amount + Amount <= 60000 && dropped != this; + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (Amount > 1) + list.Add(1050039, "{0}\t#{1}", Amount, 1026583); // ~1_NUMBER~ ~2_ITEMNAME~ + else + list.Add(1026583); // ore + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); + + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } + + public override void OnDoubleClick(Mobile from) + { + if (!Movable) + return; + + if (RootParent is BaseCreature) + { + from.SendLocalizedMessage(500447); // That is not accessible + } + else if (from.InRange(GetWorldLocation(), 2)) + { + from.SendLocalizedMessage( + 501971); // Select the forge on which to smelt the ore, or another pile of ore with which to combine it. + from.Target = new InternalTarget(this); + } + else + { + from.SendLocalizedMessage(501976); // The ore is too far away. + } + } + + private class InternalTarget : Target + { + private BaseOre m_Ore; + + public InternalTarget(BaseOre ore) : base(2, false, TargetFlags.None) + { + m_Ore = ore; + } + + private bool IsForge(object obj) + { + if (Core.ML && obj is Mobile mobile && mobile.IsDeadBondedPet) + return false; + + if (obj.GetType().IsDefined(typeof(ForgeAttribute), false)) + return true; + + int itemID = 0; + + if (obj is Item item) + itemID = item.ItemID; + else if (obj is StaticTarget target) + itemID = target.ItemID; + + return itemID == 4017 || itemID >= 6522 && itemID <= 6569; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Ore.Deleted) + return; + + if (!from.InRange(m_Ore.GetWorldLocation(), 2)) + { + from.SendLocalizedMessage(501976); // The ore is too far away. + return; + } + + #region Combine Ore + + if (targeted is BaseOre ore) + { + if (!ore.Movable) return; + if (m_Ore == ore) + { + from.SendLocalizedMessage(501972); // Select another pile or ore with which to combine this. + from.Target = new InternalTarget(ore); + return; + } + + if (ore.Resource != m_Ore.Resource) + { + from.SendLocalizedMessage(501979); // You cannot combine ores of different metals. + return; + } + + int worth = ore.Amount; + + if (ore.ItemID == 0x19B9) + worth *= 8; + else if (ore.ItemID == 0x19B7) + worth *= 2; + else + worth *= 4; + + int sourceWorth = m_Ore.Amount; + + if (m_Ore.ItemID == 0x19B9) + sourceWorth *= 8; + else if (m_Ore.ItemID == 0x19B7) + sourceWorth *= 2; + else + sourceWorth *= 4; + + worth += sourceWorth; + + int plusWeight = 0; + int newID = ore.ItemID; + + if (ore.DefaultWeight != m_Ore.DefaultWeight) + { + if (ore.ItemID == 0x19B7 || m_Ore.ItemID == 0x19B7) + { + newID = 0x19B7; + } + else if (ore.ItemID == 0x19B9) + { + newID = m_Ore.ItemID; + plusWeight = ore.Amount * 2; + } + else + { + plusWeight = m_Ore.Amount * 2; + } + } + + if (ore.ItemID == 0x19B9 && worth > 120000 || + (ore.ItemID == 0x19B8 || ore.ItemID == 0x19BA) && worth > 60000 || + ore.ItemID == 0x19B7 && worth > 30000) + { + from.SendLocalizedMessage(1062844); // There is too much ore to combine. + return; + } + + if (ore.RootParent is Mobile mobile && + plusWeight + mobile.Backpack.TotalWeight > mobile.Backpack.MaxWeight) + { + from.SendLocalizedMessage(501978); // The weight is too great to combine in a container. + return; + } + + ore.ItemID = newID; + + if (ore.ItemID == 0x19B9) + ore.Amount = worth / 8; + else if (ore.ItemID == 0x19B7) + ore.Amount = worth / 2; + else + ore.Amount = worth / 4; + + m_Ore.Delete(); + return; + } + + #endregion + + if (IsForge(targeted)) + { + double difficulty; + + switch (m_Ore.Resource) + { + default: + difficulty = 50.0; + break; + case CraftResource.DullCopper: + difficulty = 65.0; + break; + case CraftResource.ShadowIron: + difficulty = 70.0; + break; + case CraftResource.Copper: + difficulty = 75.0; + break; + case CraftResource.Bronze: + difficulty = 80.0; + break; + case CraftResource.Gold: + difficulty = 85.0; + break; + case CraftResource.Agapite: + difficulty = 90.0; + break; + case CraftResource.Verite: + difficulty = 95.0; + break; + case CraftResource.Valorite: + difficulty = 99.0; + break; + } + + double minSkill = difficulty - 25.0; + double maxSkill = difficulty + 25.0; + + if (difficulty > 50.0 && difficulty > from.Skills[SkillName.Mining].Value) + { + from.SendLocalizedMessage(501986); // You have no idea how to smelt this strange ore! + return; + } + + if (m_Ore.ItemID == 0x19B7 && m_Ore.Amount < 2) + { + from.SendLocalizedMessage( + 501987); // There is not enough metal-bearing ore in this pile to make an ingot. + return; + } + + if (from.CheckTargetSkill(SkillName.Mining, targeted, minSkill, maxSkill)) + { + int toConsume = m_Ore.Amount; + + if (toConsume <= 0) + { + from.SendLocalizedMessage( + 501987); // There is not enough metal-bearing ore in this pile to make an ingot. + } + else + { + if (toConsume > 30000) + toConsume = 30000; + + int ingotAmount; + + if (m_Ore.ItemID == 0x19B7) + { + ingotAmount = toConsume / 2; + + if (toConsume % 2 != 0) + --toConsume; + } + else if (m_Ore.ItemID == 0x19B9) + { + ingotAmount = toConsume * 2; + } + else + { + ingotAmount = toConsume; + } + + BaseIngot ingot = m_Ore.GetIngot(); + ingot.Amount = ingotAmount; + + m_Ore.Consume(toConsume); + from.AddToBackpack(ingot); + //from.PlaySound( 0x57 ); + + from.SendLocalizedMessage( + 501988); // You smelt the ore removing the impurities and put the metal in your backpack. + } + } + else + { + if (m_Ore.Amount < 2) + { + if (m_Ore.ItemID == 0x19B9) + m_Ore.ItemID = 0x19B8; + else + m_Ore.ItemID = 0x19B7; + } + else + { + m_Ore.Amount /= 2; + } + + from.SendLocalizedMessage( + 501990); // You burn away the impurities but are left with less useable metal. + } + } + } + } + } + + public class IronOre : BaseOre + { + [Constructible] + public IronOre() : this(1) + { + } + + [Constructible] + public IronOre(int amount) : base(CraftResource.Iron, amount) + { + } + + public IronOre(bool fixedSize) : this(1) + { + if (fixedSize) + ItemID = 0x19B8; + } + + public IronOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new IronIngot(); + } + } + + public class DullCopperOre : BaseOre + { + [Constructible] + public DullCopperOre() : this(1) + { + } + + [Constructible] + public DullCopperOre(int amount) : base(CraftResource.DullCopper, amount) + { + } + + public DullCopperOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new DullCopperIngot(); + } + } + + public class ShadowIronOre : BaseOre + { + [Constructible] + public ShadowIronOre() : this(1) + { + } + + [Constructible] + public ShadowIronOre(int amount) : base(CraftResource.ShadowIron, amount) + { + } + + public ShadowIronOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new ShadowIronIngot(); + } + } + + public class CopperOre : BaseOre + { + [Constructible] + public CopperOre() : this(1) + { + } + + [Constructible] + public CopperOre(int amount) : base(CraftResource.Copper, amount) + { + } + + public CopperOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new CopperIngot(); + } + } + + public class BronzeOre : BaseOre + { + [Constructible] + public BronzeOre() : this(1) + { + } + + [Constructible] + public BronzeOre(int amount) : base(CraftResource.Bronze, amount) + { + } + + public BronzeOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new BronzeIngot(); + } + } + + public class GoldOre : BaseOre + { + [Constructible] + public GoldOre() : this(1) + { + } + + [Constructible] + public GoldOre(int amount) : base(CraftResource.Gold, amount) + { + } + + public GoldOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new GoldIngot(); + } + } + + public class AgapiteOre : BaseOre + { + [Constructible] + public AgapiteOre() : this(1) + { + } + + [Constructible] + public AgapiteOre(int amount) : base(CraftResource.Agapite, amount) + { + } + + public AgapiteOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new AgapiteIngot(); + } + } + + public class VeriteOre : BaseOre + { + [Constructible] + public VeriteOre() : this(1) + { + } + + [Constructible] + public VeriteOre(int amount) : base(CraftResource.Verite, amount) + { + } + + public VeriteOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new VeriteIngot(); + } + } + + public class ValoriteOre : BaseOre + { + [Constructible] + public ValoriteOre() : this(1) + { + } + + [Constructible] + public ValoriteOre(int amount) : base(CraftResource.Valorite, amount) + { + } + + public ValoriteOre(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override BaseIngot GetIngot() + { + return new ValoriteIngot(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Blacksmithing/Scales.cs b/Scripts/Items/Resources/Blacksmithing/Scales.cs index cb60eb70f..24f5f397c 100644 --- a/Scripts/Items/Resources/Blacksmithing/Scales.cs +++ b/Scripts/Items/Resources/Blacksmithing/Scales.cs @@ -1,263 +1,255 @@ namespace Server.Items { - public abstract class BaseScales : Item, ICommodity - { - public override int LabelNumber => 1053139; // dragon scales - - private CraftResource m_Resource; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; InvalidateProperties(); } - } - - public override double DefaultWeight => 0.1; - - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( (int) m_Resource ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - } - } - - public BaseScales( CraftResource resource ) : this( resource, 1 ) - { - } - - public BaseScales( CraftResource resource, int amount ) : base( 0x26B4 ) - { - Stackable = true; - Amount = amount; - Hue = CraftResources.GetHue( resource ); - - m_Resource = resource; - } - - public BaseScales( Serial serial ) : base( serial ) - { - } - } - - public class RedScales : BaseScales - { - [Constructible] - public RedScales() : this( 1 ) - { - } - - [Constructible] - public RedScales( int amount ) : base( CraftResource.RedScales, amount ) - { - } - - public RedScales( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - public class YellowScales : BaseScales - { - [Constructible] - public YellowScales() : this( 1 ) - { - } - - [Constructible] - public YellowScales( int amount ) : base( CraftResource.YellowScales, amount ) - { - } - - public YellowScales( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - public class BlackScales : BaseScales - { - [Constructible] - public BlackScales() : this( 1 ) - { - } - - [Constructible] - public BlackScales( int amount ) : base( CraftResource.BlackScales, amount ) - { - } - - public BlackScales( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - public class GreenScales : BaseScales - { - [Constructible] - public GreenScales() : this( 1 ) - { - } - - [Constructible] - public GreenScales( int amount ) : base( CraftResource.GreenScales, amount ) - { - } - - public GreenScales( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - public class WhiteScales : BaseScales - { - [Constructible] - public WhiteScales() : this( 1 ) - { - } - - [Constructible] - public WhiteScales( int amount ) : base( CraftResource.WhiteScales, amount ) - { - } - - public WhiteScales( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } - - public class BlueScales : BaseScales - { - public override int LabelNumber => 1053140; // sea serpent scales - - [Constructible] - public BlueScales() : this( 1 ) - { - } - - [Constructible] - public BlueScales( int amount ) : base( CraftResource.BlueScales, amount ) - { - } - - public BlueScales( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } -} + public abstract class BaseScales : Item, ICommodity + { + private CraftResource m_Resource; + + public BaseScales(CraftResource resource) : this(resource, 1) + { + } + + public BaseScales(CraftResource resource, int amount) : base(0x26B4) + { + Stackable = true; + Amount = amount; + Hue = CraftResources.GetHue(resource); + + m_Resource = resource; + } + + public BaseScales(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1053139; // dragon scales + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } + + public override double DefaultWeight => 0.1; + + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write((int)m_Resource); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } + } + } + + public class RedScales : BaseScales + { + [Constructible] + public RedScales() : this(1) + { + } + + [Constructible] + public RedScales(int amount) : base(CraftResource.RedScales, amount) + { + } + + public RedScales(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class YellowScales : BaseScales + { + [Constructible] + public YellowScales() : this(1) + { + } + + [Constructible] + public YellowScales(int amount) : base(CraftResource.YellowScales, amount) + { + } + + public YellowScales(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BlackScales : BaseScales + { + [Constructible] + public BlackScales() : this(1) + { + } + + [Constructible] + public BlackScales(int amount) : base(CraftResource.BlackScales, amount) + { + } + + public BlackScales(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GreenScales : BaseScales + { + [Constructible] + public GreenScales() : this(1) + { + } + + [Constructible] + public GreenScales(int amount) : base(CraftResource.GreenScales, amount) + { + } + + public GreenScales(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WhiteScales : BaseScales + { + [Constructible] + public WhiteScales() : this(1) + { + } + + [Constructible] + public WhiteScales(int amount) : base(CraftResource.WhiteScales, amount) + { + } + + public WhiteScales(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BlueScales : BaseScales + { + [Constructible] + public BlueScales() : this(1) + { + } + + [Constructible] + public BlueScales(int amount) : base(CraftResource.BlueScales, amount) + { + } + + public BlueScales(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1053140; // sea serpent scales + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Fishing/BigFish.cs b/Scripts/Items/Resources/Fishing/BigFish.cs index 108a2ade2..150f72b0e 100644 --- a/Scripts/Items/Resources/Fishing/BigFish.cs +++ b/Scripts/Items/Resources/Fishing/BigFish.cs @@ -2,76 +2,81 @@ using System; namespace Server.Items { - public class BigFish : Item, ICarvable - { - private Mobile m_Fisher; + public class BigFish : Item, ICarvable + { + private Mobile m_Fisher; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Fisher - { - get => m_Fisher; - set{ m_Fisher = value; InvalidateProperties(); } - } + [Constructible] + public BigFish() : base(0x09CC) + { + Weight = Utility.RandomMinMax(3, + 200); //TODO: Find correct formula. max on OSI currently 200, OSI dev says it's not 200 as max, and ~ 1/1,000,000 chance to get highest + Hue = Utility.RandomBool() ? 0x847 : 0x58C; + } - public void Carve( Mobile from, Item item ) - { - base.ScissorHelper( from, new RawFishSteak(), Math.Max( 16, (int)Weight ) / 4 , false ); - } + public BigFish(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1041112; // a big fish + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Fisher + { + get => m_Fisher; + set + { + m_Fisher = value; + InvalidateProperties(); + } + } - [Constructible] - public BigFish() : base( 0x09CC ) - { - Weight = Utility.RandomMinMax( 3, 200 ); //TODO: Find correct formula. max on OSI currently 200, OSI dev says it's not 200 as max, and ~ 1/1,000,000 chance to get highest - Hue = Utility.RandomBool() ? 0x847 : 0x58C; - } + public override int LabelNumber => 1041112; // a big fish - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public void Carve(Mobile from, Item item) + { + base.ScissorHelper(from, new RawFishSteak(), Math.Max(16, (int)Weight) / 4, false); + } - if ( Weight >= 20 ) - { - if ( m_Fisher != null ) - list.Add( 1070857, m_Fisher.Name ); // Caught by ~1_fisherman~ + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070858, ((int)Weight).ToString() ); // ~1_weight~ stones - } - } + if (Weight >= 20) + { + if (m_Fisher != null) + list.Add(1070857, m_Fisher.Name); // Caught by ~1_fisherman~ - public BigFish( Serial serial ) : base( serial ) - { - } + list.Add(1070858, ((int)Weight).ToString()); // ~1_weight~ stones + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (Mobile) m_Fisher ); - } + writer.Write(m_Fisher); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_Fisher = reader.ReadMobile(); - break; - } - case 0: - { - Weight = Utility.RandomMinMax( 3, 200 ); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + m_Fisher = reader.ReadMobile(); + break; + } + case 0: + { + Weight = Utility.RandomMinMax(3, 200); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Fishing/Fish.cs b/Scripts/Items/Resources/Fishing/Fish.cs index 8cdc3f417..d90f45020 100644 --- a/Scripts/Items/Resources/Fishing/Fish.cs +++ b/Scripts/Items/Resources/Fishing/Fish.cs @@ -1,43 +1,42 @@ namespace Server.Items { - public class Fish : Item, ICarvable - { - public void Carve( Mobile from, Item item ) - { - base.ScissorHelper( from, new RawFishSteak(), 4 ); - } + public class Fish : Item, ICarvable + { + [Constructible] + public Fish() : this(1) + { + } - [Constructible] - public Fish() : this( 1 ) - { - } + [Constructible] + public Fish(int amount) : base(Utility.Random(0x09CC, 4)) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } - [Constructible] - public Fish( int amount ) : base( Utility.Random( 0x09CC, 4 ) ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } - + public Fish(Serial serial) : base(serial) + { + } - public Fish( Serial serial ) : base( serial ) - { - } + public void Carve(Mobile from, Item item) + { + base.ScissorHelper(from, new RawFishSteak(), 4); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Fishing/MagicFish.cs b/Scripts/Items/Resources/Fishing/MagicFish.cs index c943e6e9c..84eaf0db4 100644 --- a/Scripts/Items/Resources/Fishing/MagicFish.cs +++ b/Scripts/Items/Resources/Fishing/MagicFish.cs @@ -1,200 +1,201 @@ using System; using Server.Network; +using Server.Spells; namespace Server.Items { - public abstract class BaseMagicFish : Item - { - public virtual int Bonus => 0; - public virtual StatType Type => StatType.Str; + public abstract class BaseMagicFish : Item + { + public BaseMagicFish(int hue) : base(0xDD6) + { + Hue = hue; + } - public override double DefaultWeight => 1.0; + public BaseMagicFish(Serial serial) : base(serial) + { + } - public BaseMagicFish( int hue ) : base( 0xDD6 ) - { - Hue = hue; - } + public virtual int Bonus => 0; + public virtual StatType Type => StatType.Str; - public BaseMagicFish( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 1.0; - public virtual bool Apply( Mobile from ) - { - bool applied = Spells.SpellHelper.AddStatOffset( from, Type, Bonus, TimeSpan.FromMinutes( 1.0 ) ); + public virtual bool Apply(Mobile from) + { + bool applied = SpellHelper.AddStatOffset(from, Type, Bonus, TimeSpan.FromMinutes(1.0)); - if ( !applied ) - from.SendLocalizedMessage( 502173 ); // You are already under a similar effect. + if (!applied) + from.SendLocalizedMessage(502173); // You are already under a similar effect. - return applied; - } + return applied; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( Apply( from ) ) - { - from.FixedEffect( 0x375A, 10, 15 ); - from.PlaySound( 0x1E7 ); - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501774 ); // You swallow the fish whole! - Delete(); - } - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (Apply(from)) + { + from.FixedEffect(0x375A, 10, 15); + from.PlaySound(0x1E7); + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501774); // You swallow the fish whole! + Delete(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class PrizedFish : BaseMagicFish - { - public override int Bonus => 5; - public override StatType Type => StatType.Int; + public class PrizedFish : BaseMagicFish + { + [Constructible] + public PrizedFish() : base(51) + { + } - public override int LabelNumber => 1041073; // prized fish + public PrizedFish(Serial serial) : base(serial) + { + } - [Constructible] - public PrizedFish() : base( 51 ) - { - } + public override int Bonus => 5; + public override StatType Type => StatType.Int; - public PrizedFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041073; // prized fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 151 ) - Hue = 51; - } - } + if (Hue == 151) + Hue = 51; + } + } - public class WondrousFish : BaseMagicFish - { - public override int Bonus => 5; - public override StatType Type => StatType.Dex; + public class WondrousFish : BaseMagicFish + { + [Constructible] + public WondrousFish() : base(86) + { + } - public override int LabelNumber => 1041074; // wondrous fish + public WondrousFish(Serial serial) : base(serial) + { + } - [Constructible] - public WondrousFish() : base( 86 ) - { - } + public override int Bonus => 5; + public override StatType Type => StatType.Dex; - public WondrousFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041074; // wondrous fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 286 ) - Hue = 86; - } - } + if (Hue == 286) + Hue = 86; + } + } - public class TrulyRareFish : BaseMagicFish - { - public override int Bonus => 5; - public override StatType Type => StatType.Str; + public class TrulyRareFish : BaseMagicFish + { + [Constructible] + public TrulyRareFish() : base(76) + { + } - public override int LabelNumber => 1041075; // truly rare fish + public TrulyRareFish(Serial serial) : base(serial) + { + } - [Constructible] - public TrulyRareFish() : base( 76 ) - { - } + public override int Bonus => 5; + public override StatType Type => StatType.Str; - public TrulyRareFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041075; // truly rare fish - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 376 ) - Hue = 76; - } - } + if (Hue == 376) + Hue = 76; + } + } - public class PeculiarFish : BaseMagicFish - { - public override int LabelNumber => 1041076; // highly peculiar fish + public class PeculiarFish : BaseMagicFish + { + [Constructible] + public PeculiarFish() : base(66) + { + } - [Constructible] - public PeculiarFish() : base( 66 ) - { - } + public PeculiarFish(Serial serial) : base(serial) + { + } - public PeculiarFish( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041076; // highly peculiar fish - public override bool Apply( Mobile from ) - { - from.Stam += 10; - return true; - } + public override bool Apply(Mobile from) + { + from.Stam += 10; + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 266 ) - Hue = 66; - } - } -} + if (Hue == 266) + Hue = 66; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Masonry/Granite.cs b/Scripts/Items/Resources/Masonry/Granite.cs index 98a680898..8c0026516 100644 --- a/Scripts/Items/Resources/Masonry/Granite.cs +++ b/Scripts/Items/Resources/Masonry/Granite.cs @@ -1,308 +1,312 @@ namespace Server.Items { - public abstract class BaseGranite : Item - { - private CraftResource m_Resource; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; InvalidateProperties(); } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( (int) m_Resource ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - case 0: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - } - - if ( version < 1 ) - Stackable = Core.ML; - } - - public override double DefaultWeight => Core.ML ? 1.0 : 10.0; - - public BaseGranite( CraftResource resource ) : base( 0x1779 ) - { - Hue = CraftResources.GetHue( resource ); - Stackable = Core.ML; - - m_Resource = resource; - } - - public BaseGranite( Serial serial ) : base( serial ) - { - } - - public override int LabelNumber => 1044607; // high quality granite - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); - - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } - } - - public class Granite : BaseGranite - { - [Constructible] - public Granite() : base( CraftResource.Iron ) - { - } - - public Granite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DullCopperGranite : BaseGranite - { - [Constructible] - public DullCopperGranite() : base( CraftResource.DullCopper ) - { - } - - public DullCopperGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ShadowIronGranite : BaseGranite - { - [Constructible] - public ShadowIronGranite() : base( CraftResource.ShadowIron ) - { - } - - public ShadowIronGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CopperGranite : BaseGranite - { - [Constructible] - public CopperGranite() : base( CraftResource.Copper ) - { - } - - public CopperGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BronzeGranite : BaseGranite - { - [Constructible] - public BronzeGranite() : base( CraftResource.Bronze ) - { - } - - public BronzeGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GoldGranite : BaseGranite - { - [Constructible] - public GoldGranite() : base( CraftResource.Gold ) - { - } - - public GoldGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AgapiteGranite : BaseGranite - { - [Constructible] - public AgapiteGranite() : base( CraftResource.Agapite ) - { - } - - public AgapiteGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class VeriteGranite : BaseGranite - { - [Constructible] - public VeriteGranite() : base( CraftResource.Verite ) - { - } - - public VeriteGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ValoriteGranite : BaseGranite - { - [Constructible] - public ValoriteGranite() : base( CraftResource.Valorite ) - { - } - - public ValoriteGranite( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public abstract class BaseGranite : Item + { + private CraftResource m_Resource; + + public BaseGranite(CraftResource resource) : base(0x1779) + { + Hue = CraftResources.GetHue(resource); + Stackable = Core.ML; + + m_Resource = resource; + } + + public BaseGranite(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } + + public override double DefaultWeight => Core.ML ? 1.0 : 10.0; + + public override int LabelNumber => 1044607; // high quality granite + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write((int)m_Resource); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + case 0: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } + + if (version < 1) + Stackable = Core.ML; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); + + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } + } + + public class Granite : BaseGranite + { + [Constructible] + public Granite() : base(CraftResource.Iron) + { + } + + public Granite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DullCopperGranite : BaseGranite + { + [Constructible] + public DullCopperGranite() : base(CraftResource.DullCopper) + { + } + + public DullCopperGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ShadowIronGranite : BaseGranite + { + [Constructible] + public ShadowIronGranite() : base(CraftResource.ShadowIron) + { + } + + public ShadowIronGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CopperGranite : BaseGranite + { + [Constructible] + public CopperGranite() : base(CraftResource.Copper) + { + } + + public CopperGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BronzeGranite : BaseGranite + { + [Constructible] + public BronzeGranite() : base(CraftResource.Bronze) + { + } + + public BronzeGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GoldGranite : BaseGranite + { + [Constructible] + public GoldGranite() : base(CraftResource.Gold) + { + } + + public GoldGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AgapiteGranite : BaseGranite + { + [Constructible] + public AgapiteGranite() : base(CraftResource.Agapite) + { + } + + public AgapiteGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class VeriteGranite : BaseGranite + { + [Constructible] + public VeriteGranite() : base(CraftResource.Verite) + { + } + + public VeriteGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ValoriteGranite : BaseGranite + { + [Constructible] + public ValoriteGranite() : base(CraftResource.Valorite) + { + } + + public ValoriteGranite(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/MiscMLResources.cs b/Scripts/Items/Resources/MiscMLResources.cs index 6156c66bf..f726dee1e 100644 --- a/Scripts/Items/Resources/MiscMLResources.cs +++ b/Scripts/Items/Resources/MiscMLResources.cs @@ -1,1046 +1,1045 @@ namespace Server.Items { - public class Blight : Item - { - [Constructible] - public Blight() - : this( 1 ) - { - } - - [Constructible] - public Blight( int amount ) - : base( 0x3183 ) - { - Stackable = true; - Amount = amount; - } - - public Blight( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LuminescentFungi : Item - { - [Constructible] - public LuminescentFungi() - : this( 1 ) - { - } - - [Constructible] - public LuminescentFungi( int amount ) - : base( 0x3191 ) - { - Stackable = true; - Amount = amount; - } - - public LuminescentFungi( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class CapturedEssence : Item - { - [Constructible] - public CapturedEssence() - : this( 1 ) - { - } - - [Constructible] - public CapturedEssence( int amount ) - : base( 0x318E ) - { - Stackable = true; - Amount = amount; - } - - public CapturedEssence( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class EyeOfTheTravesty : Item - { - [Constructible] - public EyeOfTheTravesty() - : this( 1 ) - { - } - - [Constructible] - public EyeOfTheTravesty( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public EyeOfTheTravesty( int amount ) - : base( 0x318D ) - { - Stackable = true; - Amount = amount; - } - - public EyeOfTheTravesty( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class Corruption : Item - { - [Constructible] - public Corruption() - : this( 1 ) - { - } - - [Constructible] - public Corruption( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public Corruption( int amount ) - : base( 0x3184 ) - { - Stackable = true; - Amount = amount; - } - - public Corruption( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class DreadHornMane : Item - { - [Constructible] - public DreadHornMane() - : this( 1 ) - { - } - - [Constructible] - public DreadHornMane( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public DreadHornMane( int amount ) - : base( 0x318A ) - { - Stackable = true; - Amount = amount; - } - - public DreadHornMane( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class ParasiticPlant : Item - { - [Constructible] - public ParasiticPlant() - : this( 1 ) - { - } - - [Constructible] - public ParasiticPlant( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public ParasiticPlant( int amount ) - : base( 0x3190 ) - { - Stackable = true; - Amount = amount; - } - - public ParasiticPlant( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class Muculent : Item - { - [Constructible] - public Muculent() - : this( 1 ) - { - } - - [Constructible] - public Muculent( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public Muculent( int amount ) - : base( 0x3188 ) - { - Stackable = true; - Amount = amount; - } - - public Muculent( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class DiseasedBark : Item - { - [Constructible] - public DiseasedBark() - : this( 1 ) - { - } - - [Constructible] - public DiseasedBark( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public DiseasedBark( int amount ) - : base( 0x318B ) - { - Stackable = true; - Amount = amount; - } - - public DiseasedBark( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class BarkFragment : Item - { - [Constructible] - public BarkFragment() - : this( 1 ) - { - } - - [Constructible] - public BarkFragment( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public BarkFragment( int amount ) - : base( 0x318F ) - { - Stackable = true; - Amount = amount; - } - - public BarkFragment( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class GrizzledBones : Item - { - [Constructible] - public GrizzledBones() - : this( 1 ) - { - } - - [Constructible] - public GrizzledBones( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public GrizzledBones( int amount ) - : base( 0x318C ) - { - Stackable = true; - Amount = amount; - } - - public GrizzledBones( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version <= 0 && ItemID == 0x318F ) - ItemID = 0x318C; - } - } - - - public class LardOfParoxysmus : Item - { - [Constructible] - public LardOfParoxysmus() - : this( 1 ) - { - } - - [Constructible] - public LardOfParoxysmus( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public LardOfParoxysmus( int amount ) - : base( 0x3189 ) - { - Stackable = true; - Amount = amount; - } - - public LardOfParoxysmus( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class PerfectEmerald : Item - { - [Constructible] - public PerfectEmerald() - : this( 1 ) - { - } - - [Constructible] - public PerfectEmerald( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public PerfectEmerald( int amount ) - : base( 0x3194 ) - { - Stackable = true; - Amount = amount; - } - - public PerfectEmerald( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DarkSapphire : Item - { - [Constructible] - public DarkSapphire() - : this( 1 ) - { - } - - [Constructible] - public DarkSapphire( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public DarkSapphire( int amount ) - : base( 0x3192 ) - { - Stackable = true; - Amount = amount; - } - - public DarkSapphire( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class Turquoise : Item - { - [Constructible] - public Turquoise() - : this( 1 ) - { - } - - [Constructible] - public Turquoise( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public Turquoise( int amount ) - : base( 0x3193 ) - { - Stackable = true; - Amount = amount; - } - - public Turquoise( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class EcruCitrine : Item - { - [Constructible] - public EcruCitrine() - : this( 1 ) - { - } - - [Constructible] - public EcruCitrine( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public EcruCitrine( int amount ) - : base( 0x3195 ) - { - Stackable = true; - Amount = amount; - } - - public EcruCitrine( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class WhitePearl : Item - { - [Constructible] - public WhitePearl() - : this( 1 ) - { - } - - [Constructible] - public WhitePearl( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public WhitePearl( int amount ) - : base( 0x3196 ) - { - Stackable = true; - Amount = amount; - } - - public WhitePearl( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class FireRuby : Item - { - [Constructible] - public FireRuby() - : this( 1 ) - { - } - - [Constructible] - public FireRuby( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public FireRuby( int amount ) - : base( 0x3197 ) - { - Stackable = true; - Amount = amount; - } - - public FireRuby( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class BlueDiamond : Item - { - [Constructible] - public BlueDiamond() - : this( 1 ) - { - } - - [Constructible] - public BlueDiamond( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public BlueDiamond( int amount ) - : base( 0x3198 ) - { - Stackable = true; - Amount = amount; - } - - public BlueDiamond( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class BrilliantAmber : Item - { - [Constructible] - public BrilliantAmber() - : this( 1 ) - { - } - - [Constructible] - public BrilliantAmber( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public BrilliantAmber( int amount ) - : base( 0x3199 ) - { - Stackable = true; - Amount = amount; - } - - public BrilliantAmber( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class Scourge : Item - { - [Constructible] - public Scourge() - : this( 1 ) - { - } - - [Constructible] - public Scourge( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public Scourge( int amount ) - : base( 0x3185 ) - { - Stackable = true; - Amount = amount; - Hue = 150; - } - - public Scourge( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class Putrefication : Item - { - [Constructible] - public Putrefication() - : this( 1 ) - { - } - - [Constructible] - public Putrefication( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public Putrefication( int amount ) - : base( 0x3186 ) - { - Stackable = true; - Amount = amount; - Hue = 883; - } - - public Putrefication( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - - public class Taint : Item - { - [Constructible] - public Taint() - : this( 1 ) - { - } - - [Constructible] - public Taint( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public Taint( int amount ) - : base( 0x3187 ) - { - Stackable = true; - Amount = amount; - Hue = 731; - } - - public Taint( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [Flippable( 0x315A, 0x315B )] - public class PristineDreadHorn : Item - { - [Constructible] - public PristineDreadHorn() - : base( 0x315A ) - { - - } - - public PristineDreadHorn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SwitchItem : Item - { - [Constructible] - public SwitchItem() - : this( 1 ) - { - } - - [Constructible] - public SwitchItem( int amountFrom, int amountTo ) - : this( Utility.RandomMinMax( amountFrom, amountTo ) ) - { - } - - [Constructible] - public SwitchItem( int amount ) - : base( 0x2F5F ) - { - Stackable = true; - Amount = amount; - } - - public SwitchItem( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public class Blight : Item + { + [Constructible] + public Blight() + : this(1) + { + } + + [Constructible] + public Blight(int amount) + : base(0x3183) + { + Stackable = true; + Amount = amount; + } + + public Blight(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LuminescentFungi : Item + { + [Constructible] + public LuminescentFungi() + : this(1) + { + } + + [Constructible] + public LuminescentFungi(int amount) + : base(0x3191) + { + Stackable = true; + Amount = amount; + } + + public LuminescentFungi(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class CapturedEssence : Item + { + [Constructible] + public CapturedEssence() + : this(1) + { + } + + [Constructible] + public CapturedEssence(int amount) + : base(0x318E) + { + Stackable = true; + Amount = amount; + } + + public CapturedEssence(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class EyeOfTheTravesty : Item + { + [Constructible] + public EyeOfTheTravesty() + : this(1) + { + } + + [Constructible] + public EyeOfTheTravesty(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public EyeOfTheTravesty(int amount) + : base(0x318D) + { + Stackable = true; + Amount = amount; + } + + public EyeOfTheTravesty(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class Corruption : Item + { + [Constructible] + public Corruption() + : this(1) + { + } + + [Constructible] + public Corruption(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public Corruption(int amount) + : base(0x3184) + { + Stackable = true; + Amount = amount; + } + + public Corruption(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class DreadHornMane : Item + { + [Constructible] + public DreadHornMane() + : this(1) + { + } + + [Constructible] + public DreadHornMane(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public DreadHornMane(int amount) + : base(0x318A) + { + Stackable = true; + Amount = amount; + } + + public DreadHornMane(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class ParasiticPlant : Item + { + [Constructible] + public ParasiticPlant() + : this(1) + { + } + + [Constructible] + public ParasiticPlant(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public ParasiticPlant(int amount) + : base(0x3190) + { + Stackable = true; + Amount = amount; + } + + public ParasiticPlant(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class Muculent : Item + { + [Constructible] + public Muculent() + : this(1) + { + } + + [Constructible] + public Muculent(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public Muculent(int amount) + : base(0x3188) + { + Stackable = true; + Amount = amount; + } + + public Muculent(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class DiseasedBark : Item + { + [Constructible] + public DiseasedBark() + : this(1) + { + } + + [Constructible] + public DiseasedBark(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public DiseasedBark(int amount) + : base(0x318B) + { + Stackable = true; + Amount = amount; + } + + public DiseasedBark(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class BarkFragment : Item + { + [Constructible] + public BarkFragment() + : this(1) + { + } + + [Constructible] + public BarkFragment(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public BarkFragment(int amount) + : base(0x318F) + { + Stackable = true; + Amount = amount; + } + + public BarkFragment(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class GrizzledBones : Item + { + [Constructible] + public GrizzledBones() + : this(1) + { + } + + [Constructible] + public GrizzledBones(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public GrizzledBones(int amount) + : base(0x318C) + { + Stackable = true; + Amount = amount; + } + + public GrizzledBones(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version <= 0 && ItemID == 0x318F) + ItemID = 0x318C; + } + } + + + public class LardOfParoxysmus : Item + { + [Constructible] + public LardOfParoxysmus() + : this(1) + { + } + + [Constructible] + public LardOfParoxysmus(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public LardOfParoxysmus(int amount) + : base(0x3189) + { + Stackable = true; + Amount = amount; + } + + public LardOfParoxysmus(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class PerfectEmerald : Item + { + [Constructible] + public PerfectEmerald() + : this(1) + { + } + + [Constructible] + public PerfectEmerald(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public PerfectEmerald(int amount) + : base(0x3194) + { + Stackable = true; + Amount = amount; + } + + public PerfectEmerald(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DarkSapphire : Item + { + [Constructible] + public DarkSapphire() + : this(1) + { + } + + [Constructible] + public DarkSapphire(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public DarkSapphire(int amount) + : base(0x3192) + { + Stackable = true; + Amount = amount; + } + + public DarkSapphire(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class Turquoise : Item + { + [Constructible] + public Turquoise() + : this(1) + { + } + + [Constructible] + public Turquoise(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public Turquoise(int amount) + : base(0x3193) + { + Stackable = true; + Amount = amount; + } + + public Turquoise(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class EcruCitrine : Item + { + [Constructible] + public EcruCitrine() + : this(1) + { + } + + [Constructible] + public EcruCitrine(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public EcruCitrine(int amount) + : base(0x3195) + { + Stackable = true; + Amount = amount; + } + + public EcruCitrine(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class WhitePearl : Item + { + [Constructible] + public WhitePearl() + : this(1) + { + } + + [Constructible] + public WhitePearl(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public WhitePearl(int amount) + : base(0x3196) + { + Stackable = true; + Amount = amount; + } + + public WhitePearl(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class FireRuby : Item + { + [Constructible] + public FireRuby() + : this(1) + { + } + + [Constructible] + public FireRuby(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public FireRuby(int amount) + : base(0x3197) + { + Stackable = true; + Amount = amount; + } + + public FireRuby(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class BlueDiamond : Item + { + [Constructible] + public BlueDiamond() + : this(1) + { + } + + [Constructible] + public BlueDiamond(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public BlueDiamond(int amount) + : base(0x3198) + { + Stackable = true; + Amount = amount; + } + + public BlueDiamond(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class BrilliantAmber : Item + { + [Constructible] + public BrilliantAmber() + : this(1) + { + } + + [Constructible] + public BrilliantAmber(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public BrilliantAmber(int amount) + : base(0x3199) + { + Stackable = true; + Amount = amount; + } + + public BrilliantAmber(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class Scourge : Item + { + [Constructible] + public Scourge() + : this(1) + { + } + + [Constructible] + public Scourge(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public Scourge(int amount) + : base(0x3185) + { + Stackable = true; + Amount = amount; + Hue = 150; + } + + public Scourge(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class Putrefication : Item + { + [Constructible] + public Putrefication() + : this(1) + { + } + + [Constructible] + public Putrefication(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public Putrefication(int amount) + : base(0x3186) + { + Stackable = true; + Amount = amount; + Hue = 883; + } + + public Putrefication(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + + public class Taint : Item + { + [Constructible] + public Taint() + : this(1) + { + } + + [Constructible] + public Taint(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public Taint(int amount) + : base(0x3187) + { + Stackable = true; + Amount = amount; + Hue = 731; + } + + public Taint(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [Flippable(0x315A, 0x315B)] + public class PristineDreadHorn : Item + { + [Constructible] + public PristineDreadHorn() + : base(0x315A) + { + } + + public PristineDreadHorn(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SwitchItem : Item + { + [Constructible] + public SwitchItem() + : this(1) + { + } + + [Constructible] + public SwitchItem(int amountFrom, int amountTo) + : this(Utility.RandomMinMax(amountFrom, amountTo)) + { + } + + [Constructible] + public SwitchItem(int amount) + : base(0x2F5F) + { + Stackable = true; + Amount = amount; + } + + public SwitchItem(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/BagOfAllReagents.cs b/Scripts/Items/Resources/Reagents/BagOfAllReagents.cs index dd432f3d9..f95bcbd20 100644 --- a/Scripts/Items/Resources/Reagents/BagOfAllReagents.cs +++ b/Scripts/Items/Resources/Reagents/BagOfAllReagents.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class BagOfAllReagents : Bag - { - [Constructible] - public BagOfAllReagents() : this( 50 ) - { - } + public class BagOfAllReagents : Bag + { + [Constructible] + public BagOfAllReagents() : this(50) + { + } - [Constructible] - public BagOfAllReagents( int amount ) - { - DropItem( new BlackPearl ( amount ) ); - DropItem( new Bloodmoss ( amount ) ); - DropItem( new Garlic ( amount ) ); - DropItem( new Ginseng ( amount ) ); - DropItem( new MandrakeRoot ( amount ) ); - DropItem( new Nightshade ( amount ) ); - DropItem( new SulfurousAsh ( amount ) ); - DropItem( new SpidersSilk ( amount ) ); - DropItem( new BatWing ( amount ) ); - DropItem( new GraveDust ( amount ) ); - DropItem( new DaemonBlood ( amount ) ); - DropItem( new NoxCrystal ( amount ) ); - DropItem( new PigIron ( amount ) ); - } + [Constructible] + public BagOfAllReagents(int amount) + { + DropItem(new BlackPearl(amount)); + DropItem(new Bloodmoss(amount)); + DropItem(new Garlic(amount)); + DropItem(new Ginseng(amount)); + DropItem(new MandrakeRoot(amount)); + DropItem(new Nightshade(amount)); + DropItem(new SulfurousAsh(amount)); + DropItem(new SpidersSilk(amount)); + DropItem(new BatWing(amount)); + DropItem(new GraveDust(amount)); + DropItem(new DaemonBlood(amount)); + DropItem(new NoxCrystal(amount)); + DropItem(new PigIron(amount)); + } - public BagOfAllReagents( Serial serial ) : base( serial ) - { - } + public BagOfAllReagents(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/BagOfNecroReagents.cs b/Scripts/Items/Resources/Reagents/BagOfNecroReagents.cs index 09bc7150b..2c5c03da5 100644 --- a/Scripts/Items/Resources/Reagents/BagOfNecroReagents.cs +++ b/Scripts/Items/Resources/Reagents/BagOfNecroReagents.cs @@ -1,38 +1,38 @@ namespace Server.Items { - public class BagOfNecroReagents : Bag - { - [Constructible] - public BagOfNecroReagents() : this( 50 ) - { - } + public class BagOfNecroReagents : Bag + { + [Constructible] + public BagOfNecroReagents() : this(50) + { + } - [Constructible] - public BagOfNecroReagents( int amount ) - { - DropItem( new BatWing ( amount ) ); - DropItem( new GraveDust ( amount ) ); - DropItem( new DaemonBlood( amount ) ); - DropItem( new NoxCrystal ( amount ) ); - DropItem( new PigIron ( amount ) ); - } + [Constructible] + public BagOfNecroReagents(int amount) + { + DropItem(new BatWing(amount)); + DropItem(new GraveDust(amount)); + DropItem(new DaemonBlood(amount)); + DropItem(new NoxCrystal(amount)); + DropItem(new PigIron(amount)); + } - public BagOfNecroReagents( Serial serial ) : base( serial ) - { - } + public BagOfNecroReagents(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/BagOfReagents.cs b/Scripts/Items/Resources/Reagents/BagOfReagents.cs index 686f7a910..6896b8603 100644 --- a/Scripts/Items/Resources/Reagents/BagOfReagents.cs +++ b/Scripts/Items/Resources/Reagents/BagOfReagents.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class BagOfReagents : Bag - { - [Constructible] - public BagOfReagents() : this( 50 ) - { - } + public class BagOfReagents : Bag + { + [Constructible] + public BagOfReagents() : this(50) + { + } - [Constructible] - public BagOfReagents( int amount ) - { - DropItem( new BlackPearl ( amount ) ); - DropItem( new Bloodmoss ( amount ) ); - DropItem( new Garlic ( amount ) ); - DropItem( new Ginseng ( amount ) ); - DropItem( new MandrakeRoot ( amount ) ); - DropItem( new Nightshade ( amount ) ); - DropItem( new SulfurousAsh ( amount ) ); - DropItem( new SpidersSilk ( amount ) ); - } + [Constructible] + public BagOfReagents(int amount) + { + DropItem(new BlackPearl(amount)); + DropItem(new Bloodmoss(amount)); + DropItem(new Garlic(amount)); + DropItem(new Ginseng(amount)); + DropItem(new MandrakeRoot(amount)); + DropItem(new Nightshade(amount)); + DropItem(new SulfurousAsh(amount)); + DropItem(new SpidersSilk(amount)); + } - public BagOfReagents( Serial serial ) : base( serial ) - { - } + public BagOfReagents(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/BaseReagent.cs b/Scripts/Items/Resources/Reagents/BaseReagent.cs index 189f63fee..1dd6d7b59 100644 --- a/Scripts/Items/Resources/Reagents/BaseReagent.cs +++ b/Scripts/Items/Resources/Reagents/BaseReagent.cs @@ -1,35 +1,35 @@ namespace Server.Items { - public abstract class BaseReagent : Item - { - public override double DefaultWeight => 0.1; + public abstract class BaseReagent : Item + { + public BaseReagent(int itemID) : this(itemID, 1) + { + } - public BaseReagent( int itemID ) : this( itemID, 1 ) - { - } + public BaseReagent(int itemID, int amount) : base(itemID) + { + Stackable = true; + Amount = amount; + } - public BaseReagent( int itemID, int amount ) : base( itemID ) - { - Stackable = true; - Amount = amount; - } + public BaseReagent(Serial serial) : base(serial) + { + } - public BaseReagent( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 0.1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/BatWing.cs b/Scripts/Items/Resources/Reagents/BatWing.cs index 5e0db1c8d..46247b7f0 100644 --- a/Scripts/Items/Resources/Reagents/BatWing.cs +++ b/Scripts/Items/Resources/Reagents/BatWing.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class BatWing : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class BatWing : BaseReagent, ICommodity + { + [Constructible] + public BatWing() : this(1) + { + } - [Constructible] - public BatWing() : this( 1 ) - { - } + [Constructible] + public BatWing(int amount) : base(0xF78, amount) + { + } - [Constructible] - public BatWing( int amount ) : base( 0xF78, amount ) - { - } + public BatWing(Serial serial) : base(serial) + { + } - public BatWing( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/BlackPearl.cs b/Scripts/Items/Resources/Reagents/BlackPearl.cs index 32aee0ead..0cc6dffd1 100644 --- a/Scripts/Items/Resources/Reagents/BlackPearl.cs +++ b/Scripts/Items/Resources/Reagents/BlackPearl.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class BlackPearl : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class BlackPearl : BaseReagent, ICommodity + { + [Constructible] + public BlackPearl() : this(1) + { + } - [Constructible] - public BlackPearl() : this( 1 ) - { - } + [Constructible] + public BlackPearl(int amount) : base(0xF7A, amount) + { + } - [Constructible] - public BlackPearl( int amount ) : base( 0xF7A, amount ) - { - } + public BlackPearl(Serial serial) : base(serial) + { + } - public BlackPearl( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/Bloodmoss.cs b/Scripts/Items/Resources/Reagents/Bloodmoss.cs index f49ffbac0..c50261e2a 100644 --- a/Scripts/Items/Resources/Reagents/Bloodmoss.cs +++ b/Scripts/Items/Resources/Reagents/Bloodmoss.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class Bloodmoss : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Bloodmoss : BaseReagent, ICommodity + { + [Constructible] + public Bloodmoss() : this(1) + { + } - [Constructible] - public Bloodmoss() : this( 1 ) - { - } + [Constructible] + public Bloodmoss(int amount) : base(0xF7B, amount) + { + } - [Constructible] - public Bloodmoss( int amount ) : base( 0xF7B, amount ) - { - } + public Bloodmoss(Serial serial) : base(serial) + { + } - public Bloodmoss( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/DaemonBlood.cs b/Scripts/Items/Resources/Reagents/DaemonBlood.cs index 24f07a484..c23e96895 100644 --- a/Scripts/Items/Resources/Reagents/DaemonBlood.cs +++ b/Scripts/Items/Resources/Reagents/DaemonBlood.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class DaemonBlood : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class DaemonBlood : BaseReagent, ICommodity + { + [Constructible] + public DaemonBlood() : this(1) + { + } - [Constructible] - public DaemonBlood() : this( 1 ) - { - } + [Constructible] + public DaemonBlood(int amount) : base(0xF7D, amount) + { + } - [Constructible] - public DaemonBlood( int amount ) : base( 0xF7D, amount ) - { - } + public DaemonBlood(Serial serial) : base(serial) + { + } - public DaemonBlood( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/DaemonBone.cs b/Scripts/Items/Resources/Reagents/DaemonBone.cs index 0ffa9971a..9142c0a2a 100644 --- a/Scripts/Items/Resources/Reagents/DaemonBone.cs +++ b/Scripts/Items/Resources/Reagents/DaemonBone.cs @@ -1,38 +1,37 @@ namespace Server.Items { - // TODO: Commodity? - public class DaemonBone : BaseReagent - { - public override double DefaultWeight => 1.0; + // TODO: Commodity? + public class DaemonBone : BaseReagent + { + [Constructible] + public DaemonBone() : this(1) + { + } - [Constructible] - public DaemonBone() : this( 1 ) - { - } + [Constructible] + public DaemonBone(int amount) : base(0xF80, amount) + { + } - [Constructible] - public DaemonBone( int amount ) : base( 0xF80, amount ) - { - } + public DaemonBone(Serial serial) : base(serial) + { + } - public DaemonBone( Serial serial ) : base( serial ) - { - } + public override double DefaultWeight => 1.0; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/DeadWood.cs b/Scripts/Items/Resources/Reagents/DeadWood.cs index 6a5cf3e6a..5e00a06cf 100644 --- a/Scripts/Items/Resources/Reagents/DeadWood.cs +++ b/Scripts/Items/Resources/Reagents/DeadWood.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class DeadWood : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class DeadWood : BaseReagent, ICommodity + { + [Constructible] + public DeadWood() : this(1) + { + } - [Constructible] - public DeadWood() : this( 1 ) - { - } + [Constructible] + public DeadWood(int amount) : base(0xF90, amount) + { + } - [Constructible] - public DeadWood( int amount ) : base( 0xF90, amount ) - { - } + public DeadWood(Serial serial) : base(serial) + { + } - public DeadWood( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/DragonsBlood.cs b/Scripts/Items/Resources/Reagents/DragonsBlood.cs index 7cd67f355..9154b5c04 100644 --- a/Scripts/Items/Resources/Reagents/DragonsBlood.cs +++ b/Scripts/Items/Resources/Reagents/DragonsBlood.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class DragonsBlood : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => Core.ML; + public class DragonsBlood : BaseReagent, ICommodity + { + [Constructible] + public DragonsBlood() + : this(1) + { + } - [Constructible] - public DragonsBlood() - : this( 1 ) - { - } + [Constructible] + public DragonsBlood(int amount) + : base(0x4077, amount) + { + } - [Constructible] - public DragonsBlood( int amount ) - : base( 0x4077, amount ) - { - } + public DragonsBlood(Serial serial) + : base(serial) + { + } - public DragonsBlood( Serial serial ) - : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => Core.ML; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/Garlic.cs b/Scripts/Items/Resources/Reagents/Garlic.cs index b1d24b434..0d1608a6f 100644 --- a/Scripts/Items/Resources/Reagents/Garlic.cs +++ b/Scripts/Items/Resources/Reagents/Garlic.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class Garlic : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Garlic : BaseReagent, ICommodity + { + [Constructible] + public Garlic() : this(1) + { + } - [Constructible] - public Garlic() : this( 1 ) - { - } + [Constructible] + public Garlic(int amount) : base(0xF84, amount) + { + } - [Constructible] - public Garlic( int amount ) : base( 0xF84, amount ) - { - } + public Garlic(Serial serial) : base(serial) + { + } - public Garlic( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/Ginseng.cs b/Scripts/Items/Resources/Reagents/Ginseng.cs index b59a6a8cf..cafd6d79a 100644 --- a/Scripts/Items/Resources/Reagents/Ginseng.cs +++ b/Scripts/Items/Resources/Reagents/Ginseng.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class Ginseng : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Ginseng : BaseReagent, ICommodity + { + [Constructible] + public Ginseng() : this(1) + { + } - [Constructible] - public Ginseng() : this( 1 ) - { - } + [Constructible] + public Ginseng(int amount) : base(0xF85, amount) + { + } - [Constructible] - public Ginseng( int amount ) : base( 0xF85, amount ) - { - } + public Ginseng(Serial serial) : base(serial) + { + } - public Ginseng( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/GraveDust.cs b/Scripts/Items/Resources/Reagents/GraveDust.cs index 5fa2a4da8..cd2e9c804 100644 --- a/Scripts/Items/Resources/Reagents/GraveDust.cs +++ b/Scripts/Items/Resources/Reagents/GraveDust.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class GraveDust : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class GraveDust : BaseReagent, ICommodity + { + [Constructible] + public GraveDust() : this(1) + { + } - [Constructible] - public GraveDust() : this( 1 ) - { - } + [Constructible] + public GraveDust(int amount) : base(0xF8F, amount) + { + } - [Constructible] - public GraveDust( int amount ) : base( 0xF8F, amount ) - { - } + public GraveDust(Serial serial) : base(serial) + { + } - public GraveDust( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/MandrakeRoot.cs b/Scripts/Items/Resources/Reagents/MandrakeRoot.cs index c6a3cd3d4..65a3928a1 100644 --- a/Scripts/Items/Resources/Reagents/MandrakeRoot.cs +++ b/Scripts/Items/Resources/Reagents/MandrakeRoot.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class MandrakeRoot : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class MandrakeRoot : BaseReagent, ICommodity + { + [Constructible] + public MandrakeRoot() : this(1) + { + } - [Constructible] - public MandrakeRoot() : this( 1 ) - { - } + [Constructible] + public MandrakeRoot(int amount) : base(0xF86, amount) + { + } - [Constructible] - public MandrakeRoot( int amount ) : base( 0xF86, amount ) - { - } + public MandrakeRoot(Serial serial) : base(serial) + { + } - public MandrakeRoot( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/Nightshade.cs b/Scripts/Items/Resources/Reagents/Nightshade.cs index 9868408c0..163b6f909 100644 --- a/Scripts/Items/Resources/Reagents/Nightshade.cs +++ b/Scripts/Items/Resources/Reagents/Nightshade.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class Nightshade : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Nightshade : BaseReagent, ICommodity + { + [Constructible] + public Nightshade() : this(1) + { + } - [Constructible] - public Nightshade() : this( 1 ) - { - } + [Constructible] + public Nightshade(int amount) : base(0xF88, amount) + { + } - [Constructible] - public Nightshade( int amount ) : base( 0xF88, amount ) - { - } + public Nightshade(Serial serial) : base(serial) + { + } - public Nightshade( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/NoxCrystal.cs b/Scripts/Items/Resources/Reagents/NoxCrystal.cs index d7736cda1..0e5aec390 100644 --- a/Scripts/Items/Resources/Reagents/NoxCrystal.cs +++ b/Scripts/Items/Resources/Reagents/NoxCrystal.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class NoxCrystal : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class NoxCrystal : BaseReagent, ICommodity + { + [Constructible] + public NoxCrystal() : this(1) + { + } - [Constructible] - public NoxCrystal() : this( 1 ) - { - } + [Constructible] + public NoxCrystal(int amount) : base(0xF8E, amount) + { + } - [Constructible] - public NoxCrystal( int amount ) : base( 0xF8E, amount ) - { - } + public NoxCrystal(Serial serial) : base(serial) + { + } - public NoxCrystal( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/PigIron.cs b/Scripts/Items/Resources/Reagents/PigIron.cs index 0b88ec676..2fe6ed4a0 100644 --- a/Scripts/Items/Resources/Reagents/PigIron.cs +++ b/Scripts/Items/Resources/Reagents/PigIron.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class PigIron : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class PigIron : BaseReagent, ICommodity + { + [Constructible] + public PigIron() : this(1) + { + } - [Constructible] - public PigIron() : this( 1 ) - { - } + [Constructible] + public PigIron(int amount) : base(0xF8A, amount) + { + } - [Constructible] - public PigIron( int amount ) : base( 0xF8A, amount ) - { - } + public PigIron(Serial serial) : base(serial) + { + } - public PigIron( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/SpidersSilk.cs b/Scripts/Items/Resources/Reagents/SpidersSilk.cs index 3d84ea39a..07dc98dab 100644 --- a/Scripts/Items/Resources/Reagents/SpidersSilk.cs +++ b/Scripts/Items/Resources/Reagents/SpidersSilk.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class SpidersSilk : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class SpidersSilk : BaseReagent, ICommodity + { + [Constructible] + public SpidersSilk() : this(1) + { + } - [Constructible] - public SpidersSilk() : this( 1 ) - { - } + [Constructible] + public SpidersSilk(int amount) : base(0xF8D, amount) + { + } - [Constructible] - public SpidersSilk( int amount ) : base( 0xF8D, amount ) - { - } + public SpidersSilk(Serial serial) : base(serial) + { + } - public SpidersSilk( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Reagents/SulfurousAsh.cs b/Scripts/Items/Resources/Reagents/SulfurousAsh.cs index 2be7fed8c..e4bf1bd87 100644 --- a/Scripts/Items/Resources/Reagents/SulfurousAsh.cs +++ b/Scripts/Items/Resources/Reagents/SulfurousAsh.cs @@ -1,38 +1,37 @@ namespace Server.Items { - public class SulfurousAsh : BaseReagent, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class SulfurousAsh : BaseReagent, ICommodity + { + [Constructible] + public SulfurousAsh() : this(1) + { + } - [Constructible] - public SulfurousAsh() : this( 1 ) - { - } + [Constructible] + public SulfurousAsh(int amount) : base(0xF8C, amount) + { + } - [Constructible] - public SulfurousAsh( int amount ) : base( 0xF8C, amount ) - { - } + public SulfurousAsh(Serial serial) : base(serial) + { + } - public SulfurousAsh( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/BoltOfCloth.cs b/Scripts/Items/Resources/Tailor/BoltOfCloth.cs index ba856c83f..6179c06d6 100644 --- a/Scripts/Items/Resources/Tailor/BoltOfCloth.cs +++ b/Scripts/Items/Resources/Tailor/BoltOfCloth.cs @@ -2,65 +2,67 @@ using Server.Network; namespace Server.Items { - [FlippableAttribute( 0xF95, 0xF96, 0xF97, 0xF98, 0xF99, 0xF9A, 0xF9B, 0xF9C )] - public class BoltOfCloth : Item, IScissorable, IDyable, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + [Flippable(0xF95, 0xF96, 0xF97, 0xF98, 0xF99, 0xF9A, 0xF9B, 0xF9C)] + public class BoltOfCloth : Item, IScissorable, IDyable, ICommodity + { + [Constructible] + public BoltOfCloth() : this(1) + { + } - [Constructible] - public BoltOfCloth() : this( 1 ) - { - } + [Constructible] + public BoltOfCloth(int amount) : base(0xF95) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + } - [Constructible] - public BoltOfCloth( int amount ) : base( 0xF95 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - } + public BoltOfCloth(Serial serial) : base(serial) + { + } - public BoltOfCloth( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) return false; + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) return false; - Hue = sender.DyedHue; + Hue = sender.DyedHue; - return true; - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } - writer.Write( (int) 0 ); // version - } + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + base.ScissorHelper(from, new Cloth(), 50); - int version = reader.ReadInt(); - } + return true; + } - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - base.ScissorHelper( from, new Cloth(), 50 ); + writer.Write(0); // version + } - return true; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnSingleClick( Mobile from ) - { - int number = (Amount == 1) ? 1049122 : 1049121; + int version = reader.ReadInt(); + } - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Label, 0x3B2, 3, number, "", (Amount * 50).ToString() ) ); - } - } + public override void OnSingleClick(Mobile from) + { + int number = Amount == 1 ? 1049122 : 1049121; + + from.Send( + new MessageLocalized(Serial, ItemID, MessageType.Label, 0x3B2, 3, number, "", (Amount * 50).ToString())); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Bone.cs b/Scripts/Items/Resources/Tailor/Bone.cs index e31657257..d777c6f42 100644 --- a/Scripts/Items/Resources/Tailor/Bone.cs +++ b/Scripts/Items/Resources/Tailor/Bone.cs @@ -1,41 +1,40 @@ namespace Server.Items { - public class Bone : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public class Bone : Item, ICommodity + { + [Constructible] + public Bone() : this(1) + { + } - [Constructible] - public Bone() : this( 1 ) - { - } + [Constructible] + public Bone(int amount) : base(0xf7e) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - [Constructible] - public Bone( int amount ) : base( 0xf7e ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + public Bone(Serial serial) : base(serial) + { + } - public Bone( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Cloth.cs b/Scripts/Items/Resources/Tailor/Cloth.cs index 9e47a1e3d..a6a05bad4 100644 --- a/Scripts/Items/Resources/Tailor/Cloth.cs +++ b/Scripts/Items/Resources/Tailor/Cloth.cs @@ -2,68 +2,67 @@ using Server.Network; namespace Server.Items { - [FlippableAttribute( 0x1766, 0x1768 )] - public class Cloth : Item, IScissorable, IDyable, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + [Flippable(0x1766, 0x1768)] + public class Cloth : Item, IScissorable, IDyable, ICommodity + { + [Constructible] + public Cloth() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public Cloth(int amount) : base(0x1766) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Cloth() : this( 1 ) - { - } + public Cloth(Serial serial) : base(serial) + { + } - [Constructible] - public Cloth( int amount ) : base( 0x1766 ) - { - Stackable = true; - Amount = amount; - } + public override double DefaultWeight => 0.1; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public Cloth( Serial serial ) : base( serial ) - { - } + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + Hue = sender.DyedHue; - Hue = sender.DyedHue; + return true; + } - return true; - } + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + base.ScissorHelper(from, new Bandage(), 1); - writer.Write( (int) 0 ); // version - } + return true; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } + writer.Write(0); // version + } - public override void OnSingleClick( Mobile from ) - { - int number = (Amount == 1) ? 1049124 : 1049123; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", Amount.ToString() ) ); - } - - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + int version = reader.ReadInt(); + } - base.ScissorHelper( from, new Bandage(), 1 ); + public override void OnSingleClick(Mobile from) + { + int number = Amount == 1 ? 1049124 : 1049123; - return true; - } - } + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", Amount.ToString())); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Cotton.cs b/Scripts/Items/Resources/Tailor/Cotton.cs index a750075a8..4e00b6199 100644 --- a/Scripts/Items/Resources/Tailor/Cotton.cs +++ b/Scripts/Items/Resources/Tailor/Cotton.cs @@ -2,110 +2,111 @@ using Server.Targeting; namespace Server.Items { - public class Cotton : Item, IDyable - { - [Constructible] - public Cotton() : this( 1 ) - { - } + public class Cotton : Item, IDyable + { + [Constructible] + public Cotton() : this(1) + { + } - [Constructible] - public Cotton( int amount ) : base( 0xDF9 ) - { - Stackable = true; - Weight = 4.0; - Amount = amount; - } + [Constructible] + public Cotton(int amount) : base(0xDF9) + { + Stackable = true; + Weight = 4.0; + Amount = amount; + } - public Cotton( Serial serial ) : base( serial ) - { - } + public Cotton(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - writer.Write( (int) 0 ); // version - } + Hue = sender.DyedHue; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return true; + } - int version = reader.ReadInt(); - } - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Hue = sender.DyedHue; + writer.Write(0); // version + } - return true; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 502655 ); // What spinning wheel do you wish to spin this on? - from.Target = new PickWheelTarget( this ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + int version = reader.ReadInt(); + } - public virtual void OnSpun( ISpinningWheel wheel, Mobile from, int hue ) - { - Item item = new SpoolOfThread( 6 ); - item.Hue = hue; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502655); // What spinning wheel do you wish to spin this on? + from.Target = new PickWheelTarget(this); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - from.AddToBackpack( item ); - from.SendLocalizedMessage( 1010577 ); // You put the spools of thread in your backpack. - } + public virtual void OnSpun(ISpinningWheel wheel, Mobile from, int hue) + { + Item item = new SpoolOfThread(6); + item.Hue = hue; - private class PickWheelTarget : Target - { - private Cotton m_Cotton; + from.AddToBackpack(item); + from.SendLocalizedMessage(1010577); // You put the spools of thread in your backpack. + } - public PickWheelTarget( Cotton cotton ) : base( 3, false, TargetFlags.None ) - { - m_Cotton = cotton; - } + private class PickWheelTarget : Target + { + private Cotton m_Cotton; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Cotton.Deleted ) - return; + public PickWheelTarget(Cotton cotton) : base(3, false, TargetFlags.None) + { + m_Cotton = cotton; + } - ISpinningWheel wheel = targeted as ISpinningWheel; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Cotton.Deleted) + return; - if ( wheel == null && targeted is AddonComponent component ) - wheel = component.Addon as ISpinningWheel; + ISpinningWheel wheel = targeted as ISpinningWheel; - if ( wheel is Item ) - { - if ( !m_Cotton.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( wheel.Spinning ) - { - from.SendLocalizedMessage( 502656 ); // That spinning wheel is being used. - } - else - { - m_Cotton.Consume(); - wheel.BeginSpin( m_Cotton.OnSpun, from, m_Cotton.Hue ); - } - } - else - { - from.SendLocalizedMessage( 502658 ); // Use that on a spinning wheel. - } - } - } - } -} + if (wheel == null && targeted is AddonComponent component) + wheel = component.Addon as ISpinningWheel; + + if (wheel is Item) + { + if (!m_Cotton.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (wheel.Spinning) + { + from.SendLocalizedMessage(502656); // That spinning wheel is being used. + } + else + { + m_Cotton.Consume(); + wheel.BeginSpin(m_Cotton.OnSpun, from, m_Cotton.Hue); + } + } + else + { + from.SendLocalizedMessage(502658); // Use that on a spinning wheel. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Flax.cs b/Scripts/Items/Resources/Tailor/Flax.cs index 50b1a9458..58141263a 100644 --- a/Scripts/Items/Resources/Tailor/Flax.cs +++ b/Scripts/Items/Resources/Tailor/Flax.cs @@ -2,100 +2,101 @@ using Server.Targeting; namespace Server.Items { - public class Flax : Item - { - [Constructible] - public Flax() : this( 1 ) - { - } + public class Flax : Item + { + [Constructible] + public Flax() : this(1) + { + } - [Constructible] - public Flax( int amount ) : base( 0x1A9C ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } + [Constructible] + public Flax(int amount) : base(0x1A9C) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } - public Flax( Serial serial ) : base( serial ) - { - } + public Flax(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 502655 ); // What spinning wheel do you wish to spin this on? - from.Target = new PickWheelTarget( this ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + int version = reader.ReadInt(); + } - public virtual void OnSpun( ISpinningWheel wheel, Mobile from, int hue ) - { - Item item = new SpoolOfThread( 6 ); - item.Hue = hue; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502655); // What spinning wheel do you wish to spin this on? + from.Target = new PickWheelTarget(this); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - from.AddToBackpack( item ); - from.SendLocalizedMessage( 1010577 ); // You put the spools of thread in your backpack. - } + public virtual void OnSpun(ISpinningWheel wheel, Mobile from, int hue) + { + Item item = new SpoolOfThread(6); + item.Hue = hue; - private class PickWheelTarget : Target - { - private Flax m_Flax; + from.AddToBackpack(item); + from.SendLocalizedMessage(1010577); // You put the spools of thread in your backpack. + } - public PickWheelTarget( Flax flax ) : base( 3, false, TargetFlags.None ) - { - m_Flax = flax; - } + private class PickWheelTarget : Target + { + private Flax m_Flax; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Flax.Deleted ) - return; + public PickWheelTarget(Flax flax) : base(3, false, TargetFlags.None) + { + m_Flax = flax; + } - ISpinningWheel wheel = targeted as ISpinningWheel; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Flax.Deleted) + return; - if ( wheel == null && targeted is AddonComponent component ) - wheel = component.Addon as ISpinningWheel; + ISpinningWheel wheel = targeted as ISpinningWheel; - if ( wheel is Item ) - { - if ( !m_Flax.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( wheel.Spinning ) - { - from.SendLocalizedMessage( 502656 ); // That spinning wheel is being used. - } - else - { - m_Flax.Consume(); - wheel.BeginSpin( m_Flax.OnSpun, from, m_Flax.Hue ); - } - } - else - { - from.SendLocalizedMessage( 502658 ); // Use that on a spinning wheel. - } - } - } - } -} + if (wheel == null && targeted is AddonComponent component) + wheel = component.Addon as ISpinningWheel; + + if (wheel is Item) + { + if (!m_Flax.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (wheel.Spinning) + { + from.SendLocalizedMessage(502656); // That spinning wheel is being used. + } + else + { + m_Flax.Consume(); + wheel.BeginSpin(m_Flax.OnSpun, from, m_Flax.Hue); + } + } + else + { + from.SendLocalizedMessage(502658); // Use that on a spinning wheel. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Hides.cs b/Scripts/Items/Resources/Tailor/Hides.cs index 126602328..ce122e574 100644 --- a/Scripts/Items/Resources/Tailor/Hides.cs +++ b/Scripts/Items/Resources/Tailor/Hides.cs @@ -1,288 +1,293 @@ namespace Server.Items { - public abstract class BaseHides : Item, ICommodity - { - private CraftResource m_Resource; + public abstract class BaseHides : Item, ICommodity + { + private CraftResource m_Resource; - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; InvalidateProperties(); } - } - - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public BaseHides(CraftResource resource) : this(resource, 1) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public BaseHides(CraftResource resource, int amount) : base(0x1079) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + Hue = CraftResources.GetHue(resource); - writer.Write( (int) 1 ); // version + m_Resource = resource; + } - writer.Write( (int) m_Resource ); - } + public BaseHides(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } - int version = reader.ReadInt(); + public override int LabelNumber + { + get + { + if (m_Resource >= CraftResource.SpinedLeather && m_Resource <= CraftResource.BarbedLeather) + return 1049687 + (m_Resource - CraftResource.SpinedLeather); - switch ( version ) - { - case 1: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - case 0: - { - OreInfo info = new OreInfo( reader.ReadInt(), reader.ReadInt(), reader.ReadString() ); + return 1047023; + } + } - m_Resource = CraftResources.GetFromOreInfo( info ); - break; - } - } - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public BaseHides( CraftResource resource ) : this( resource, 1 ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public BaseHides( CraftResource resource, int amount ) : base( 0x1079 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - Hue = CraftResources.GetHue( resource ); + writer.Write(1); // version - m_Resource = resource; - } + writer.Write((int)m_Resource); + } - public BaseHides( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( Amount > 1 ) - list.Add( 1050039, "{0}\t#{1}", Amount, 1024216 ); // ~1_NUMBER~ ~2_ITEMNAME~ - else - list.Add( 1024216 ); // pile of hides - } + int version = reader.ReadInt(); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + switch (version) + { + case 1: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + case 0: + { + OreInfo info = new OreInfo(reader.ReadInt(), reader.ReadInt(), reader.ReadString()); - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); + m_Resource = CraftResources.GetFromOreInfo(info); + break; + } + } + } - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (Amount > 1) + list.Add(1050039, "{0}\t#{1}", Amount, 1024216); // ~1_NUMBER~ ~2_ITEMNAME~ + else + list.Add(1024216); // pile of hides + } - public override int LabelNumber - { - get - { - if ( m_Resource >= CraftResource.SpinedLeather && m_Resource <= CraftResource.BarbedLeather ) - return 1049687 + (int)(m_Resource - CraftResource.SpinedLeather); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - return 1047023; - } - } - } + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); - [FlippableAttribute( 0x1079, 0x1078 )] - public class Hides : BaseHides, IScissorable - { - [Constructible] - public Hides() : this( 1 ) - { - } + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } + } - [Constructible] - public Hides( int amount ) : base( CraftResource.RegularLeather, amount ) - { - } + [Flippable(0x1079, 0x1078)] + public class Hides : BaseHides, IScissorable + { + [Constructible] + public Hides() : this(1) + { + } - public Hides( Serial serial ) : base( serial ) - { - } + [Constructible] + public Hides(int amount) : base(CraftResource.RegularLeather, amount) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Hides(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (Core.AOS && !IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502437); // Items you wish to cut must be in your backpack + return false; + } - int version = reader.ReadInt(); - } + base.ScissorHelper(from, new Leather(), 1); - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + return true; + } - if ( Core.AOS && !IsChildOf ( from.Backpack ) ) - { - from.SendLocalizedMessage ( 502437 ); // Items you wish to cut must be in your backpack - return false; - } - base.ScissorHelper( from, new Leather(), 1 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } + writer.Write(0); // version + } - [FlippableAttribute( 0x1079, 0x1078 )] - public class SpinedHides : BaseHides, IScissorable - { - [Constructible] - public SpinedHides() : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public SpinedHides( int amount ) : base( CraftResource.SpinedLeather, amount ) - { - } + int version = reader.ReadInt(); + } + } - public SpinedHides( Serial serial ) : base( serial ) - { - } + [Flippable(0x1079, 0x1078)] + public class SpinedHides : BaseHides, IScissorable + { + [Constructible] + public SpinedHides() : this(1) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public SpinedHides(int amount) : base(CraftResource.SpinedLeather, amount) + { + } - writer.Write( (int) 0 ); // version - } + public SpinedHides(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - int version = reader.ReadInt(); - } + if (Core.AOS && !IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502437); // Items you wish to cut must be in your backpack + return false; + } - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + base.ScissorHelper(from, new SpinedLeather(), 1); - if ( Core.AOS && !IsChildOf ( from.Backpack ) ) - { - from.SendLocalizedMessage ( 502437 ); // Items you wish to cut must be in your backpack - return false; - } + return true; + } - base.ScissorHelper( from, new SpinedLeather(), 1 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } + writer.Write(0); // version + } - [FlippableAttribute( 0x1079, 0x1078 )] - public class HornedHides : BaseHides, IScissorable - { - [Constructible] - public HornedHides() : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public HornedHides( int amount ) : base( CraftResource.HornedLeather, amount ) - { - } + int version = reader.ReadInt(); + } + } - public HornedHides( Serial serial ) : base( serial ) - { - } + [Flippable(0x1079, 0x1078)] + public class HornedHides : BaseHides, IScissorable + { + [Constructible] + public HornedHides() : this(1) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public HornedHides(int amount) : base(CraftResource.HornedLeather, amount) + { + } - writer.Write( (int) 0 ); // version - } + public HornedHides(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - int version = reader.ReadInt(); - } + if (Core.AOS && !IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502437); // Items you wish to cut must be in your backpack + return false; + } - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + base.ScissorHelper(from, new HornedLeather(), 1); - if ( Core.AOS && !IsChildOf ( from.Backpack ) ) - { - from.SendLocalizedMessage ( 502437 ); // Items you wish to cut must be in your backpack - return false; - } - - base.ScissorHelper( from, new HornedLeather(), 1 ); + return true; + } - return true; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [FlippableAttribute( 0x1079, 0x1078 )] - public class BarbedHides : BaseHides, IScissorable - { - [Constructible] - public BarbedHides() : this( 1 ) - { - } + writer.Write(0); // version + } - [Constructible] - public BarbedHides( int amount ) : base( CraftResource.BarbedLeather, amount ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public BarbedHides( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Flippable(0x1079, 0x1078)] + public class BarbedHides : BaseHides, IScissorable + { + [Constructible] + public BarbedHides() : this(1) + { + } - writer.Write( (int) 0 ); // version - } + [Constructible] + public BarbedHides(int amount) : base(CraftResource.BarbedLeather, amount) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public BarbedHides(Serial serial) : base(serial) + { + } - int version = reader.ReadInt(); - } + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + if (Core.AOS && !IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502437); // Items you wish to cut must be in your backpack + return false; + } - if ( Core.AOS && !IsChildOf ( from.Backpack ) ) - { - from.SendLocalizedMessage ( 502437 ); // Items you wish to cut must be in your backpack - return false; - } + base.ScissorHelper(from, new BarbedLeather(), 1); - base.ScissorHelper( from, new BarbedLeather(), 1 ); + return true; + } - return true; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Leathers.cs b/Scripts/Items/Resources/Tailor/Leathers.cs index ec9024e43..89f791728 100644 --- a/Scripts/Items/Resources/Tailor/Leathers.cs +++ b/Scripts/Items/Resources/Tailor/Leathers.cs @@ -1,237 +1,233 @@ namespace Server.Items { - public abstract class BaseLeather : Item, ICommodity - { - private CraftResource m_Resource; + public abstract class BaseLeather : Item, ICommodity + { + private CraftResource m_Resource; - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; InvalidateProperties(); } - } - - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + public BaseLeather(CraftResource resource) : this(resource, 1) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public BaseLeather(CraftResource resource, int amount) : base(0x1081) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + Hue = CraftResources.GetHue(resource); - writer.Write( (int) 1 ); // version + m_Resource = resource; + } - writer.Write( (int) m_Resource ); - } + public BaseLeather(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } - int version = reader.ReadInt(); + public override int LabelNumber + { + get + { + if (m_Resource >= CraftResource.SpinedLeather && m_Resource <= CraftResource.BarbedLeather) + return 1049684 + (m_Resource - CraftResource.SpinedLeather); - switch ( version ) - { - case 1: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - case 0: - { - OreInfo info = new OreInfo( reader.ReadInt(), reader.ReadInt(), reader.ReadString() ); + return 1047022; + } + } - m_Resource = CraftResources.GetFromOreInfo( info ); - break; - } - } - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public BaseLeather( CraftResource resource ) : this( resource, 1 ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public BaseLeather( CraftResource resource, int amount ) : base( 0x1081 ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - Hue = CraftResources.GetHue( resource ); + writer.Write(1); // version - m_Resource = resource; - } + writer.Write((int)m_Resource); + } - public BaseLeather( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( Amount > 1 ) - list.Add( 1050039, "{0}\t#{1}", Amount, 1024199 ); // ~1_NUMBER~ ~2_ITEMNAME~ - else - list.Add( 1024199 ); // cut leather - } + int version = reader.ReadInt(); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + switch (version) + { + case 1: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + case 0: + { + OreInfo info = new OreInfo(reader.ReadInt(), reader.ReadInt(), reader.ReadString()); - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); + m_Resource = CraftResources.GetFromOreInfo(info); + break; + } + } + } - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (Amount > 1) + list.Add(1050039, "{0}\t#{1}", Amount, 1024199); // ~1_NUMBER~ ~2_ITEMNAME~ + else + list.Add(1024199); // cut leather + } - public override int LabelNumber - { - get - { - if ( m_Resource >= CraftResource.SpinedLeather && m_Resource <= CraftResource.BarbedLeather ) - return 1049684 + (int)(m_Resource - CraftResource.SpinedLeather); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - return 1047022; - } - } - } + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); - [FlippableAttribute( 0x1081, 0x1082 )] - public class Leather : BaseLeather - { - [Constructible] - public Leather() : this( 1 ) - { - } + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } + } - [Constructible] - public Leather( int amount ) : base( CraftResource.RegularLeather, amount ) - { - } + [Flippable(0x1081, 0x1082)] + public class Leather : BaseLeather + { + [Constructible] + public Leather() : this(1) + { + } - public Leather( Serial serial ) : base( serial ) - { - } + [Constructible] + public Leather(int amount) : base(CraftResource.RegularLeather, amount) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Leather(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - - } + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x1081, 0x1082 )] - public class SpinedLeather : BaseLeather - { - [Constructible] - public SpinedLeather() : this( 1 ) - { - } + [Flippable(0x1081, 0x1082)] + public class SpinedLeather : BaseLeather + { + [Constructible] + public SpinedLeather() : this(1) + { + } - [Constructible] - public SpinedLeather( int amount ) : base( CraftResource.SpinedLeather, amount ) - { - } + [Constructible] + public SpinedLeather(int amount) : base(CraftResource.SpinedLeather, amount) + { + } - public SpinedLeather( Serial serial ) : base( serial ) - { - } + public SpinedLeather(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } + } - - } + [Flippable(0x1081, 0x1082)] + public class HornedLeather : BaseLeather + { + [Constructible] + public HornedLeather() : this(1) + { + } - [FlippableAttribute( 0x1081, 0x1082 )] - public class HornedLeather : BaseLeather - { - [Constructible] - public HornedLeather() : this( 1 ) - { - } + [Constructible] + public HornedLeather(int amount) : base(CraftResource.HornedLeather, amount) + { + } - [Constructible] - public HornedLeather( int amount ) : base( CraftResource.HornedLeather, amount ) - { - } + public HornedLeather(Serial serial) : base(serial) + { + } - public HornedLeather( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } + [Flippable(0x1081, 0x1082)] + public class BarbedLeather : BaseLeather + { + [Constructible] + public BarbedLeather() : this(1) + { + } - - } + [Constructible] + public BarbedLeather(int amount) : base(CraftResource.BarbedLeather, amount) + { + } - [FlippableAttribute( 0x1081, 0x1082 )] - public class BarbedLeather : BaseLeather - { - [Constructible] - public BarbedLeather() : this( 1 ) - { - } + public BarbedLeather(Serial serial) : base(serial) + { + } - [Constructible] - public BarbedLeather( int amount ) : base( CraftResource.BarbedLeather, amount ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public BarbedLeather( Serial serial ) : base( serial ) - { - } + writer.Write(0); // version + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/UncutCloth.cs b/Scripts/Items/Resources/Tailor/UncutCloth.cs index 8dd032ff2..db5fe8c62 100644 --- a/Scripts/Items/Resources/Tailor/UncutCloth.cs +++ b/Scripts/Items/Resources/Tailor/UncutCloth.cs @@ -2,67 +2,67 @@ using Server.Network; namespace Server.Items { - [FlippableAttribute( 0x1765, 0x1767 )] - public class UncutCloth : Item, IScissorable, IDyable, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + [Flippable(0x1765, 0x1767)] + public class UncutCloth : Item, IScissorable, IDyable, ICommodity + { + [Constructible] + public UncutCloth() : this(1) + { + } - public override double DefaultWeight => 0.1; + [Constructible] + public UncutCloth(int amount) : base(0x1767) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public UncutCloth() : this( 1 ) - { - } + public UncutCloth(Serial serial) : base(serial) + { + } - [Constructible] - public UncutCloth( int amount ) : base( 0x1767 ) - { - Stackable = true; - Amount = amount; - } + public override double DefaultWeight => 0.1; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public UncutCloth( Serial serial ) : base( serial ) - { - } + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + Hue = sender.DyedHue; - Hue = sender.DyedHue; + return true; + } - return true; - } + public bool Scissor(Mobile from, Scissors scissors) + { + if (Deleted || !from.CanSee(this)) return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + base.ScissorHelper(from, new Bandage(), 1); - writer.Write( (int) 0 ); // version - } + return true; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } + writer.Write(0); // version + } - public override void OnSingleClick( Mobile from ) - { - int number = (Amount == 1) ? 1049124 : 1049123; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - from.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", Amount.ToString() ) ); - } - public bool Scissor( Mobile from, Scissors scissors ) - { - if ( Deleted || !from.CanSee( this ) ) return false; + int version = reader.ReadInt(); + } - base.ScissorHelper( from, new Bandage(), 1 ); + public override void OnSingleClick(Mobile from) + { + int number = Amount == 1 ? 1049124 : 1049123; - return true; - } - } + from.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", Amount.ToString())); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/Wool.cs b/Scripts/Items/Resources/Tailor/Wool.cs index fe3ab99ce..787827d24 100644 --- a/Scripts/Items/Resources/Tailor/Wool.cs +++ b/Scripts/Items/Resources/Tailor/Wool.cs @@ -2,152 +2,154 @@ using Server.Targeting; namespace Server.Items { - public class Wool : Item, IDyable - { - [Constructible] - public Wool() : this( 1 ) - { - } + public class Wool : Item, IDyable + { + [Constructible] + public Wool() : this(1) + { + } - [Constructible] - public Wool( int amount ) : base( 0xDF8 ) - { - Stackable = true; - Weight = 4.0; - Amount = amount; - } + [Constructible] + public Wool(int amount) : base(0xDF8) + { + Stackable = true; + Weight = 4.0; + Amount = amount; + } - public Wool( Serial serial ) : base( serial ) - { - } + public Wool(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - writer.Write( (int) 0 ); // version - } + Hue = sender.DyedHue; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return true; + } - int version = reader.ReadInt(); - } - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Hue = sender.DyedHue; + writer.Write(0); // version + } - return true; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 502655 ); // What spinning wheel do you wish to spin this on? - from.Target = new PickWheelTarget( this ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + int version = reader.ReadInt(); + } - public virtual void OnSpun( ISpinningWheel wheel, Mobile from, int hue ) - { - Item item = new DarkYarn( 3 ); - item.Hue = hue; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(502655); // What spinning wheel do you wish to spin this on? + from.Target = new PickWheelTarget(this); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - from.AddToBackpack( item ); - from.SendLocalizedMessage( 1010576 ); // You put the balls of yarn in your backpack. - } + public virtual void OnSpun(ISpinningWheel wheel, Mobile from, int hue) + { + Item item = new DarkYarn(3); + item.Hue = hue; - private class PickWheelTarget : Target - { - private Wool m_Wool; + from.AddToBackpack(item); + from.SendLocalizedMessage(1010576); // You put the balls of yarn in your backpack. + } - public PickWheelTarget( Wool wool ) : base( 3, false, TargetFlags.None ) - { - m_Wool = wool; - } + private class PickWheelTarget : Target + { + private Wool m_Wool; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Wool.Deleted ) - return; + public PickWheelTarget(Wool wool) : base(3, false, TargetFlags.None) + { + m_Wool = wool; + } - ISpinningWheel wheel = targeted as ISpinningWheel; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Wool.Deleted) + return; - if ( wheel == null && targeted is AddonComponent component ) - wheel = component.Addon as ISpinningWheel; + ISpinningWheel wheel = targeted as ISpinningWheel; - if ( wheel is Item ) - { - if ( !m_Wool.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( wheel.Spinning ) - { - from.SendLocalizedMessage( 502656 ); // That spinning wheel is being used. - } - else - { - m_Wool.Consume(); - wheel.BeginSpin( m_Wool.OnSpun, from, m_Wool.Hue ); - } - } - else - { - from.SendLocalizedMessage( 502658 ); // Use that on a spinning wheel. - } - } - } - } - public class TaintedWool : Wool - { - [Constructible] - public TaintedWool() : this( 1 ) - { - } + if (wheel == null && targeted is AddonComponent component) + wheel = component.Addon as ISpinningWheel; - [Constructible] - public TaintedWool( int amount ) : base( 0x101F ) - { - Stackable = true; - Weight = 4.0; - Amount = amount; - } + if (wheel is Item) + { + if (!m_Wool.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (wheel.Spinning) + { + from.SendLocalizedMessage(502656); // That spinning wheel is being used. + } + else + { + m_Wool.Consume(); + wheel.BeginSpin(m_Wool.OnSpun, from, m_Wool.Hue); + } + } + else + { + from.SendLocalizedMessage(502658); // Use that on a spinning wheel. + } + } + } + } - public TaintedWool( Serial serial ) : base( serial ) - { - } + public class TaintedWool : Wool + { + [Constructible] + public TaintedWool() : this(1) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public TaintedWool(int amount) : base(0x101F) + { + Stackable = true; + Weight = 4.0; + Amount = amount; + } - writer.Write( (int) 0 ); // version - } + public TaintedWool(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } + writer.Write(0); // version + } - public override void OnSpun( ISpinningWheel wheel, Mobile from, int hue ) - { - Item item = new DarkYarn( 1 ); - item.Hue = hue; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - from.AddToBackpack( item ); - from.SendLocalizedMessage( 1010574 ); // You put a ball of yarn in your backpack. - } - } -} + int version = reader.ReadInt(); + } + + public override void OnSpun(ISpinningWheel wheel, Mobile from, int hue) + { + Item item = new DarkYarn(1); + item.Hue = hue; + + from.AddToBackpack(item); + from.SendLocalizedMessage(1010574); // You put a ball of yarn in your backpack. + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Resources/Tailor/YarnsAndThreads.cs b/Scripts/Items/Resources/Tailor/YarnsAndThreads.cs index 4ad32f4e6..26b072330 100644 --- a/Scripts/Items/Resources/Tailor/YarnsAndThreads.cs +++ b/Scripts/Items/Resources/Tailor/YarnsAndThreads.cs @@ -2,232 +2,232 @@ using Server.Targeting; namespace Server.Items { - public abstract class BaseClothMaterial : Item, IDyable - { - public BaseClothMaterial( int itemID ) : this( itemID, 1 ) - { - } + public abstract class BaseClothMaterial : Item, IDyable + { + public BaseClothMaterial(int itemID) : this(itemID, 1) + { + } - public BaseClothMaterial( int itemID, int amount ) : base( itemID ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } + public BaseClothMaterial(int itemID, int amount) : base(itemID) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } - public BaseClothMaterial( Serial serial ) : base( serial ) - { - } + public BaseClothMaterial(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - writer.Write( (int) 0 ); // version - } + Hue = sender.DyedHue; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return true; + } - int version = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + writer.Write(0); // version + } - Hue = sender.DyedHue; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return true; - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 500366 ); // Select a loom to use that on. - from.Target = new PickLoomTarget( this ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(500366); // Select a loom to use that on. + from.Target = new PickLoomTarget(this); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - private class PickLoomTarget : Target - { - private BaseClothMaterial m_Material; + private class PickLoomTarget : Target + { + private BaseClothMaterial m_Material; - public PickLoomTarget( BaseClothMaterial material ) : base( 3, false, TargetFlags.None ) - { - m_Material = material; - } + public PickLoomTarget(BaseClothMaterial material) : base(3, false, TargetFlags.None) + { + m_Material = material; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Material.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Material.Deleted) + return; - ILoom loom = targeted as ILoom; + ILoom loom = targeted as ILoom; - if ( loom == null && targeted is AddonComponent component ) - loom = component.Addon as ILoom; + if (loom == null && targeted is AddonComponent component) + loom = component.Addon as ILoom; - if ( loom != null ) - { - if ( !m_Material.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( loom.Phase < 4 ) - { - m_Material.Consume(); + if (loom != null) + { + if (!m_Material.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (loom.Phase < 4) + { + m_Material.Consume(); - if ( targeted is Item item ) - item.SendLocalizedMessageTo( from, 1010001 + loom.Phase++ ); - } - else - { - Item create = new BoltOfCloth(); - create.Hue = m_Material.Hue; + if (targeted is Item item) + item.SendLocalizedMessageTo(from, 1010001 + loom.Phase++); + } + else + { + Item create = new BoltOfCloth(); + create.Hue = m_Material.Hue; - m_Material.Consume(); - loom.Phase = 0; - from.SendLocalizedMessage( 500368 ); // You create some cloth and put it in your backpack. - from.AddToBackpack( create ); - } - } - else - { - from.SendLocalizedMessage( 500367 ); // Try using that on a loom. - } - } - } - } + m_Material.Consume(); + loom.Phase = 0; + from.SendLocalizedMessage(500368); // You create some cloth and put it in your backpack. + from.AddToBackpack(create); + } + } + else + { + from.SendLocalizedMessage(500367); // Try using that on a loom. + } + } + } + } - public class DarkYarn : BaseClothMaterial - { - [Constructible] - public DarkYarn() : this( 1 ) - { - } + public class DarkYarn : BaseClothMaterial + { + [Constructible] + public DarkYarn() : this(1) + { + } - [Constructible] - public DarkYarn( int amount ) : base( 0xE1D, amount ) - { - } + [Constructible] + public DarkYarn(int amount) : base(0xE1D, amount) + { + } - public DarkYarn( Serial serial ) : base( serial ) - { - } + public DarkYarn(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LightYarn : BaseClothMaterial - { - [Constructible] - public LightYarn() : this( 1 ) - { - } + public class LightYarn : BaseClothMaterial + { + [Constructible] + public LightYarn() : this(1) + { + } - [Constructible] - public LightYarn( int amount ) : base( 0xE1E, amount ) - { - } + [Constructible] + public LightYarn(int amount) : base(0xE1E, amount) + { + } - public LightYarn( Serial serial ) : base( serial ) - { - } + public LightYarn(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class LightYarnUnraveled : BaseClothMaterial - { - [Constructible] - public LightYarnUnraveled() : this( 1 ) - { - } + public class LightYarnUnraveled : BaseClothMaterial + { + [Constructible] + public LightYarnUnraveled() : this(1) + { + } - [Constructible] - public LightYarnUnraveled( int amount ) : base( 0xE1F, amount ) - { - } + [Constructible] + public LightYarnUnraveled(int amount) : base(0xE1F, amount) + { + } - public LightYarnUnraveled( Serial serial ) : base( serial ) - { - } + public LightYarnUnraveled(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SpoolOfThread : BaseClothMaterial - { - [Constructible] - public SpoolOfThread() : this( 1 ) - { - } + public class SpoolOfThread : BaseClothMaterial + { + [Constructible] + public SpoolOfThread() : this(1) + { + } - [Constructible] - public SpoolOfThread( int amount ) : base( 0xFA0, amount ) - { - } + [Constructible] + public SpoolOfThread(int amount) : base(0xFA0, amount) + { + } - public SpoolOfThread( Serial serial ) : base( serial ) - { - } + public SpoolOfThread(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/Artifacts/Aegis.cs b/Scripts/Items/Shields/Artifacts/Aegis.cs index 12814cef8..1b409276d 100644 --- a/Scripts/Items/Shields/Artifacts/Aegis.cs +++ b/Scripts/Items/Shields/Artifacts/Aegis.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class Aegis : HeaterShield - { - public override int LabelNumber => 1061602; // �gis - public override int ArtifactRarity => 11; + public class Aegis : HeaterShield + { + [Constructible] + public Aegis() + { + Hue = 0x47E; + ArmorAttributes.SelfRepair = 5; + Attributes.ReflectPhysical = 15; + Attributes.DefendChance = 15; + Attributes.LowerManaCost = 8; + } - public override int BasePhysicalResistance => 15; + public Aegis(Serial serial) : base(serial) + { + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public override int LabelNumber => 1061602; // �gis + public override int ArtifactRarity => 11; - [Constructible] - public Aegis() - { - Hue = 0x47E; - ArmorAttributes.SelfRepair = 5; - Attributes.ReflectPhysical = 15; - Attributes.DefendChance = 15; - Attributes.LowerManaCost = 8; - } + public override int BasePhysicalResistance => 15; - public Aegis( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - PhysicalBonus = 0; - } - } -} + if (version < 1) + PhysicalBonus = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/Artifacts/ArcaneShield.cs b/Scripts/Items/Shields/Artifacts/ArcaneShield.cs index 60b2e851d..128e776a8 100644 --- a/Scripts/Items/Shields/Artifacts/ArcaneShield.cs +++ b/Scripts/Items/Shields/Artifacts/ArcaneShield.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class ArcaneShield : WoodenKiteShield - { - public override int LabelNumber => 1061101; // Arcane Shield - public override int ArtifactRarity => 11; + public class ArcaneShield : WoodenKiteShield + { + [Constructible] + public ArcaneShield() + { + ItemID = 0x1B78; + Hue = 0x556; + Attributes.NightSight = 1; + Attributes.SpellChanneling = 1; + Attributes.DefendChance = 15; + Attributes.CastSpeed = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public ArcaneShield(Serial serial) : base(serial) + { + } - [Constructible] - public ArcaneShield() - { - ItemID = 0x1B78; - Hue = 0x556; - Attributes.NightSight = 1; - Attributes.SpellChanneling = 1; - Attributes.DefendChance = 15; - Attributes.CastSpeed = 1; - } + public override int LabelNumber => 1061101; // Arcane Shield + public override int ArtifactRarity => 11; - public ArcaneShield( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Attributes.NightSight == 0 ) - Attributes.NightSight = 1; - } - } -} + if (Attributes.NightSight == 0) + Attributes.NightSight = 1; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/BaseShield.cs b/Scripts/Items/Shields/BaseShield.cs index ba7d7168c..443985d63 100644 --- a/Scripts/Items/Shields/BaseShield.cs +++ b/Scripts/Items/Shields/BaseShield.cs @@ -2,176 +2,178 @@ using Server.Network; namespace Server.Items { - public class BaseShield : BaseArmor - { - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public class BaseShield : BaseArmor + { + public BaseShield(int itemID) : base(itemID) + { + } - public BaseShield( int itemID ) : base( itemID ) - { - } + public BaseShield(Serial serial) : base(serial) + { + } - public BaseShield( Serial serial ) : base(serial) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override double ArmorRating + { + get + { + Mobile m = Parent as Mobile; + double ar = base.ArmorRating; - writer.Write( (int) 1 );//version - } + if (m != null) + return m.Skills[SkillName.Parry].Value * ar / 200.0 + 1.0; + return ar; + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(1); //version + } - if ( version < 1 ) - { - if ( this is Aegis ) - return; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - // The 15 bonus points to resistances are not applied to shields on OSI. - PhysicalBonus = 0; - FireBonus = 0; - ColdBonus = 0; - PoisonBonus = 0; - EnergyBonus = 0; - } - } + int version = reader.ReadInt(); - public override double ArmorRating - { - get - { - Mobile m = Parent as Mobile; - double ar = base.ArmorRating; + if (version < 1) + { + if (this is Aegis) + return; - if ( m != null ) - return ( ( m.Skills[SkillName.Parry].Value * ar ) / 200.0 ) + 1.0; - return ar; - } - } + // The 15 bonus points to resistances are not applied to shields on OSI. + PhysicalBonus = 0; + FireBonus = 0; + ColdBonus = 0; + PoisonBonus = 0; + EnergyBonus = 0; + } + } - public override int OnHit( BaseWeapon weapon, int damage ) - { - if ( Core.AOS ) - { - if ( ArmorAttributes.SelfRepair > Utility.Random( 10 ) ) - { - HitPoints += 2; - } - else - { - double halfArmor = ArmorRating / 2.0; - int absorbed = (int)(halfArmor + (halfArmor*Utility.RandomDouble())); + public override int OnHit(BaseWeapon weapon, int damage) + { + if (Core.AOS) + { + if (ArmorAttributes.SelfRepair > Utility.Random(10)) + { + HitPoints += 2; + } + else + { + double halfArmor = ArmorRating / 2.0; + int absorbed = (int)(halfArmor + halfArmor * Utility.RandomDouble()); - if ( absorbed < 2 ) - absorbed = 2; + if (absorbed < 2) + absorbed = 2; - int wear; + int wear; - if ( weapon.Type == WeaponType.Bashing ) - wear = (absorbed / 2); - else - wear = Utility.Random( 2 ); + if (weapon.Type == WeaponType.Bashing) + wear = absorbed / 2; + else + wear = Utility.Random(2); - if ( wear > 0 && MaxHitPoints > 0 ) - { - if ( HitPoints >= wear ) - { - HitPoints -= wear; - wear = 0; - } - else - { - wear -= HitPoints; - HitPoints = 0; - } + if (wear > 0 && MaxHitPoints > 0) + { + if (HitPoints >= wear) + { + HitPoints -= wear; + wear = 0; + } + else + { + wear -= HitPoints; + HitPoints = 0; + } - if ( wear > 0 ) - { - if ( MaxHitPoints > wear ) - { - MaxHitPoints -= wear; + if (wear > 0) + { + if (MaxHitPoints > wear) + { + MaxHitPoints -= wear; - if ( Parent is Mobile mobile ) - mobile.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061121 ); // Your equipment is severely damaged. - } - else - { - Delete(); - } - } - } - } + if (Parent is Mobile mobile) + mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061121); // Your equipment is severely damaged. + } + else + { + Delete(); + } + } + } + } - return 0; - } + return 0; + } - if ( !(Parent is Mobile owner) ) - return damage; + if (!(Parent is Mobile owner)) + return damage; - double ar = ArmorRating; - double chance = (owner.Skills[SkillName.Parry].Value - (ar * 2.0)) / 100.0; + double ar = ArmorRating; + double chance = (owner.Skills[SkillName.Parry].Value - ar * 2.0) / 100.0; - if ( chance < 0.01 ) - chance = 0.01; - /* - FORMULA: Displayed AR = ((Parrying Skill * Base AR of Shield) � 200) + 1 + if (chance < 0.01) + chance = 0.01; + /* + FORMULA: Displayed AR = ((Parrying Skill * Base AR of Shield) � 200) + 1 - FORMULA: % Chance of Blocking = parry skill - (shieldAR * 2) + FORMULA: % Chance of Blocking = parry skill - (shieldAR * 2) - FORMULA: Melee Damage Absorbed = (AR of Shield) / 2 | Archery Damage Absorbed = AR of Shield - */ - if ( owner.CheckSkill( SkillName.Parry, chance ) ) - { - if ( weapon.Skill == SkillName.Archery ) - damage -= (int)ar; - else - damage -= (int)(ar / 2.0); + FORMULA: Melee Damage Absorbed = (AR of Shield) / 2 | Archery Damage Absorbed = AR of Shield + */ + if (owner.CheckSkill(SkillName.Parry, chance)) + { + if (weapon.Skill == SkillName.Archery) + damage -= (int)ar; + else + damage -= (int)(ar / 2.0); - if ( damage < 0 ) - damage = 0; + if (damage < 0) + damage = 0; - owner.FixedEffect( 0x37B9, 10, 16 ); + owner.FixedEffect(0x37B9, 10, 16); - if ( 25 > Utility.Random( 100 ) ) // 25% chance to lower durability - { - int wear = Utility.Random( 2 ); + if (25 > Utility.Random(100)) // 25% chance to lower durability + { + int wear = Utility.Random(2); - if ( wear > 0 && MaxHitPoints > 0 ) - { - if ( HitPoints >= wear ) - { - HitPoints -= wear; - wear = 0; - } - else - { - wear -= HitPoints; - HitPoints = 0; - } + if (wear > 0 && MaxHitPoints > 0) + { + if (HitPoints >= wear) + { + HitPoints -= wear; + wear = 0; + } + else + { + wear -= HitPoints; + HitPoints = 0; + } - if ( wear > 0 ) - { - if ( MaxHitPoints > wear ) - { - MaxHitPoints -= wear; + if (wear > 0) + { + if (MaxHitPoints > wear) + { + MaxHitPoints -= wear; - ((Mobile)Parent).LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061121 ); // Your equipment is severely damaged. - } - else - { - Delete(); - } - } - } - } - } + ((Mobile)Parent).LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061121); // Your equipment is severely damaged. + } + else + { + Delete(); + } + } + } + } + } - return damage; - } - } -} + return damage; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/BronzeShield.cs b/Scripts/Items/Shields/BronzeShield.cs index 758e0e54d..fd0b45b2d 100644 --- a/Scripts/Items/Shields/BronzeShield.cs +++ b/Scripts/Items/Shields/BronzeShield.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class BronzeShield : BaseShield - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 1; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + public class BronzeShield : BaseShield + { + [Constructible] + public BronzeShield() : base(0x1B72) + { + Weight = 6.0; + } - public override int InitMinHits => 25; - public override int InitMaxHits => 30; + public BronzeShield(Serial serial) : base(serial) + { + } - public override int AosStrReq => 35; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 1; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - public override int ArmorBase => 10; + public override int InitMinHits => 25; + public override int InitMaxHits => 30; - [Constructible] - public BronzeShield() : base( 0x1B72 ) - { - Weight = 6.0; - } + public override int AosStrReq => 35; - public BronzeShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 10; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/Buckler.cs b/Scripts/Items/Shields/Buckler.cs index bb6f579cf..5300c771e 100644 --- a/Scripts/Items/Shields/Buckler.cs +++ b/Scripts/Items/Shields/Buckler.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class Buckler : BaseShield - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 1; - public override int BaseEnergyResistance => 0; + public class Buckler : BaseShield + { + [Constructible] + public Buckler() : base(0x1B73) + { + Weight = 5.0; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public Buckler(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 1; + public override int BaseEnergyResistance => 0; - public override int ArmorBase => 7; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - [Constructible] - public Buckler() : base( 0x1B73 ) - { - Weight = 5.0; - } + public override int AosStrReq => 20; - public Buckler( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 7; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/ChaosShield.cs b/Scripts/Items/Shields/ChaosShield.cs index 2a28c3c8e..97e3a3aac 100644 --- a/Scripts/Items/Shields/ChaosShield.cs +++ b/Scripts/Items/Shields/ChaosShield.cs @@ -2,73 +2,73 @@ using Server.Guilds; namespace Server.Items { - public class ChaosShield : BaseShield - { - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + public class ChaosShield : BaseShield + { + [Constructible] + public ChaosShield() : base(0x1BC3) + { + if (!Core.AOS) + LootType = LootType.Newbied; - public override int InitMinHits => 100; - public override int InitMaxHits => 125; + Weight = 5.0; + } - public override int AosStrReq => 95; + public ChaosShield(Serial serial) : base(serial) + { + } - public override int ArmorBase => 32; + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - [Constructible] - public ChaosShield() : base( 0x1BC3 ) - { - if ( !Core.AOS ) - LootType = LootType.Newbied; + public override int InitMinHits => 100; + public override int InitMaxHits => 125; - Weight = 5.0; - } + public override int AosStrReq => 95; - public ChaosShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 32; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } + writer.Write(0); //version + } - public override bool OnEquip( Mobile from ) - { - return Validate( from ) && base.OnEquip( from ); - } + public override bool OnEquip(Mobile from) + { + return Validate(from) && base.OnEquip(from); + } - public override void OnSingleClick( Mobile from ) - { - if ( Validate( Parent as Mobile ) ) - base.OnSingleClick( from ); - } + public override void OnSingleClick(Mobile from) + { + if (Validate(Parent as Mobile)) + base.OnSingleClick(from); + } - public virtual bool Validate( Mobile m ) - { - if ( m == null || !m.Player || m.AccessLevel != AccessLevel.Player || Core.AOS ) - return true; + public virtual bool Validate(Mobile m) + { + if (m == null || !m.Player || m.AccessLevel != AccessLevel.Player || Core.AOS) + return true; - if ( !(m.Guild is Guild g) || g.Type != GuildType.Chaos ) - { - m.FixedEffect( 0x3728, 10, 13 ); - Delete(); + if (!(m.Guild is Guild g) || g.Type != GuildType.Chaos) + { + m.FixedEffect(0x3728, 10, 13); + Delete(); - return false; - } + return false; + } - return true; - } - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/HeaterShield.cs b/Scripts/Items/Shields/HeaterShield.cs index ed3f82fb1..c9e6726fb 100644 --- a/Scripts/Items/Shields/HeaterShield.cs +++ b/Scripts/Items/Shields/HeaterShield.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class HeaterShield : BaseShield - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + public class HeaterShield : BaseShield + { + [Constructible] + public HeaterShield() : base(0x1B76) + { + Weight = 8.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public HeaterShield(Serial serial) : base(serial) + { + } - public override int AosStrReq => 90; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - public override int ArmorBase => 23; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - [Constructible] - public HeaterShield() : base( 0x1B76 ) - { - Weight = 8.0; - } + public override int AosStrReq => 90; - public HeaterShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 23; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/MetalKiteShield.cs b/Scripts/Items/Shields/MetalKiteShield.cs index fadd150e7..0e7b828e3 100644 --- a/Scripts/Items/Shields/MetalKiteShield.cs +++ b/Scripts/Items/Shields/MetalKiteShield.cs @@ -1,55 +1,55 @@ namespace Server.Items { - public class MetalKiteShield : BaseShield, IDyable - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 1; + public class MetalKiteShield : BaseShield, IDyable + { + [Constructible] + public MetalKiteShield() : base(0x1B74) + { + Weight = 7.0; + } - public override int InitMinHits => 45; - public override int InitMaxHits => 60; + public MetalKiteShield(Serial serial) : base(serial) + { + } - public override int AosStrReq => 45; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 1; - public override int ArmorBase => 16; + public override int InitMinHits => 45; + public override int InitMaxHits => 60; - [Constructible] - public MetalKiteShield() : base( 0x1B74 ) - { - Weight = 7.0; - } + public override int AosStrReq => 45; - public MetalKiteShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 16; - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - Hue = sender.DyedHue; + Hue = sender.DyedHue; - return true; - } + return true; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 5.0 ) - Weight = 7.0; - } + if (Weight == 5.0) + Weight = 7.0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/MetalShield.cs b/Scripts/Items/Shields/MetalShield.cs index 644988ae4..f27d06cd2 100644 --- a/Scripts/Items/Shields/MetalShield.cs +++ b/Scripts/Items/Shields/MetalShield.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class MetalShield : BaseShield - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 1; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + public class MetalShield : BaseShield + { + [Constructible] + public MetalShield() : base(0x1B7B) + { + Weight = 6.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public MetalShield(Serial serial) : base(serial) + { + } - public override int AosStrReq => 45; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 1; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - public override int ArmorBase => 11; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - [Constructible] - public MetalShield() : base( 0x1B7B ) - { - Weight = 6.0; - } + public override int AosStrReq => 45; - public MetalShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 11; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/OrderShield.cs b/Scripts/Items/Shields/OrderShield.cs index 4b4e7837b..eb864f9c1 100644 --- a/Scripts/Items/Shields/OrderShield.cs +++ b/Scripts/Items/Shields/OrderShield.cs @@ -2,76 +2,76 @@ using Server.Guilds; namespace Server.Items { - public class OrderShield : BaseShield - { - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 0; + public class OrderShield : BaseShield + { + [Constructible] + public OrderShield() : base(0x1BC4) + { + if (!Core.AOS) + LootType = LootType.Newbied; - public override int InitMinHits => 100; - public override int InitMaxHits => 125; + Weight = 7.0; + } - public override int AosStrReq => 95; + public OrderShield(Serial serial) : base(serial) + { + } - public override int ArmorBase => 30; + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 0; - [Constructible] - public OrderShield() : base( 0x1BC4 ) - { - if ( !Core.AOS ) - LootType = LootType.Newbied; + public override int InitMinHits => 100; + public override int InitMaxHits => 125; - Weight = 7.0; - } + public override int AosStrReq => 95; - public OrderShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 30; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 6.0 ) - Weight = 7.0; - } + if (Weight == 6.0) + Weight = 7.0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } + writer.Write(0); //version + } - public override bool OnEquip( Mobile from ) - { - return Validate( from ) && base.OnEquip( from ); - } + public override bool OnEquip(Mobile from) + { + return Validate(from) && base.OnEquip(from); + } - public override void OnSingleClick( Mobile from ) - { - if ( Validate( Parent as Mobile ) ) - base.OnSingleClick( from ); - } + public override void OnSingleClick(Mobile from) + { + if (Validate(Parent as Mobile)) + base.OnSingleClick(from); + } - public virtual bool Validate( Mobile m ) - { - if ( Core.AOS || m == null || !m.Player || m.AccessLevel != AccessLevel.Player ) - return true; + public virtual bool Validate(Mobile m) + { + if (Core.AOS || m == null || !m.Player || m.AccessLevel != AccessLevel.Player) + return true; - if ( !(m.Guild is Guild g) || g.Type != GuildType.Order ) - { - m.FixedEffect( 0x3728, 10, 13 ); - Delete(); + if (!(m.Guild is Guild g) || g.Type != GuildType.Order) + { + m.FixedEffect(0x3728, 10, 13); + Delete(); - return false; - } + return false; + } - return true; - } - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/WoodenKiteShield.cs b/Scripts/Items/Shields/WoodenKiteShield.cs index 829716f71..310c074c4 100644 --- a/Scripts/Items/Shields/WoodenKiteShield.cs +++ b/Scripts/Items/Shields/WoodenKiteShield.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class WoodenKiteShield : BaseShield - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 1; + public class WoodenKiteShield : BaseShield + { + [Constructible] + public WoodenKiteShield() : base(0x1B79) + { + Weight = 5.0; + } - public override int InitMinHits => 50; - public override int InitMaxHits => 65; + public WoodenKiteShield(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 1; - public override int ArmorBase => 12; + public override int InitMinHits => 50; + public override int InitMaxHits => 65; - [Constructible] - public WoodenKiteShield() : base( 0x1B79 ) - { - Weight = 5.0; - } + public override int AosStrReq => 20; - public WoodenKiteShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 12; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 7.0 ) - Weight = 5.0; - } + if (Weight == 7.0) + Weight = 5.0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Shields/WoodenShield.cs b/Scripts/Items/Shields/WoodenShield.cs index 24b8c356e..079175f84 100644 --- a/Scripts/Items/Shields/WoodenShield.cs +++ b/Scripts/Items/Shields/WoodenShield.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class WoodenShield : BaseShield - { - public override int BasePhysicalResistance => 0; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 1; + public class WoodenShield : BaseShield + { + [Constructible] + public WoodenShield() : base(0x1B7A) + { + Weight = 5.0; + } - public override int InitMinHits => 20; - public override int InitMaxHits => 25; + public WoodenShield(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; + public override int BasePhysicalResistance => 0; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 1; - public override int ArmorBase => 8; + public override int InitMinHits => 20; + public override int InitMaxHits => 25; - [Constructible] - public WoodenShield() : base( 0x1B7A ) - { - Weight = 5.0; - } + public override int AosStrReq => 20; - public WoodenShield( Serial serial ) : base(serial) - { - } + public override int ArmorBase => 8; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 );//version - } - } -} + writer.Write(0); //version + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Blacksmith Items/Misc/AnvilForge.cs b/Scripts/Items/Skill Items/Blacksmith Items/Misc/AnvilForge.cs index ce42a143e..71d4416f9 100644 --- a/Scripts/Items/Skill Items/Blacksmith Items/Misc/AnvilForge.cs +++ b/Scripts/Items/Skill Items/Blacksmith Items/Misc/AnvilForge.cs @@ -1,59 +1,61 @@ +using Server.Engines.Craft; + namespace Server.Items { - [FlippableAttribute( 0xFAF, 0xFB0 )] - [Engines.Craft.Anvil] - public class Anvil : Item - { - [Constructible] - public Anvil() : base( 0xFAF ) - { - Movable = false; - } + [Flippable(0xFAF, 0xFB0)] + [Anvil] + public class Anvil : Item + { + [Constructible] + public Anvil() : base(0xFAF) + { + Movable = false; + } - public Anvil( Serial serial ) : base( serial ) - { - } + public Anvil(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Engines.Craft.Forge] - public class Forge : Item - { - [Constructible] - public Forge() : base( 0xFB1 ) - { - Movable = false; - } + [Forge] + public class Forge : Item + { + [Constructible] + public Forge() : base(0xFB1) + { + Movable = false; + } - public Forge( Serial serial ) : base( serial ) - { - } + public Forge(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Blacksmith Items/Misc/LargeForge.cs b/Scripts/Items/Skill Items/Blacksmith Items/Misc/LargeForge.cs index 84477df8a..06d3f7bcb 100644 --- a/Scripts/Items/Skill Items/Blacksmith Items/Misc/LargeForge.cs +++ b/Scripts/Items/Skill Items/Blacksmith Items/Misc/LargeForge.cs @@ -1,346 +1,348 @@ +using Server.Engines.Craft; + namespace Server.Items { - [Engines.Craft.Forge] - public class LargeForgeWest : Item - { - private InternalItem m_Item; - private InternalItem2 m_Item2; - - [Constructible] - public LargeForgeWest() : base( 0x199A ) - { - Movable = false; - - m_Item = new InternalItem( this ); - m_Item2 = new InternalItem2( this ); - } - - public LargeForgeWest( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X, Y + 1, Z ); - if ( m_Item2 != null ) - m_Item2.Location = new Point3D( X, Y + 2, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - if ( m_Item2 != null ) - m_Item2.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - m_Item2?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - writer.Write( m_Item2 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as InternalItem; - m_Item2 = reader.ReadItem() as InternalItem2; - } - - [Engines.Craft.Forge] - private class InternalItem : Item - { - private LargeForgeWest m_Item; - - public InternalItem( LargeForgeWest item ) : base( 0x1996 ) - { - Movable = false; - - m_Item = item; - } - - public InternalItem( Serial serial ) : base( serial ) - { - } - - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X, Y - 1, Z ); - } - - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as LargeForgeWest; - } - } - - [Engines.Craft.Forge] - private class InternalItem2 : Item - { - private LargeForgeWest m_Item; - - public InternalItem2( LargeForgeWest item ) : base( 0x1992 ) - { - Movable = false; - - m_Item = item; - } - - public InternalItem2( Serial serial ) : base( serial ) - { - } + [Forge] + public class LargeForgeWest : Item + { + private InternalItem m_Item; + private InternalItem2 m_Item2; + + [Constructible] + public LargeForgeWest() : base(0x199A) + { + Movable = false; + + m_Item = new InternalItem(this); + m_Item2 = new InternalItem2(this); + } + + public LargeForgeWest(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y + 1, Z); + if (m_Item2 != null) + m_Item2.Location = new Point3D(X, Y + 2, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + if (m_Item2 != null) + m_Item2.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + m_Item2?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + writer.Write(m_Item2); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + m_Item2 = reader.ReadItem() as InternalItem2; + } + + [Forge] + private class InternalItem : Item + { + private LargeForgeWest m_Item; + + public InternalItem(LargeForgeWest item) : base(0x1996) + { + Movable = false; + + m_Item = item; + } + + public InternalItem(Serial serial) : base(serial) + { + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 1, Z); + } + + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as LargeForgeWest; + } + } + + [Forge] + private class InternalItem2 : Item + { + private LargeForgeWest m_Item; + + public InternalItem2(LargeForgeWest item) : base(0x1992) + { + Movable = false; + + m_Item = item; + } + + public InternalItem2(Serial serial) : base(serial) + { + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X, Y - 2, Z ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X, Y - 2, Z); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Item?.Delete(); - } + m_Item?.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as LargeForgeWest; - } - } - } - - [Engines.Craft.Forge] - public class LargeForgeEast : Item - { - private InternalItem m_Item; - private InternalItem2 m_Item2; - - [Constructible] - public LargeForgeEast() : base( 0x197A ) - { - Movable = false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as LargeForgeWest; + } + } + } + + [Forge] + public class LargeForgeEast : Item + { + private InternalItem m_Item; + private InternalItem2 m_Item2; + + [Constructible] + public LargeForgeEast() : base(0x197A) + { + Movable = false; - m_Item = new InternalItem( this ); - m_Item2 = new InternalItem2( this ); - } + m_Item = new InternalItem(this); + m_Item2 = new InternalItem2(this); + } - public LargeForgeEast( Serial serial ) : base( serial ) - { - } + public LargeForgeEast(Serial serial) : base(serial) + { + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X + 1, Y, Z ); - if ( m_Item2 != null ) - m_Item2.Location = new Point3D( X + 2, Y, Z ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X + 1, Y, Z); + if (m_Item2 != null) + m_Item2.Location = new Point3D(X + 2, Y, Z); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - if ( m_Item2 != null ) - m_Item2.Map = Map; - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + if (m_Item2 != null) + m_Item2.Map = Map; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Item?.Delete(); - m_Item2?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - writer.Write( m_Item2 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Item = reader.ReadItem() as InternalItem; - m_Item2 = reader.ReadItem() as InternalItem2; - } - - [Engines.Craft.Forge] - private class InternalItem : Item - { - private LargeForgeEast m_Item; + m_Item?.Delete(); + m_Item2?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + writer.Write(m_Item2); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + m_Item = reader.ReadItem() as InternalItem; + m_Item2 = reader.ReadItem() as InternalItem2; + } + + [Forge] + private class InternalItem : Item + { + private LargeForgeEast m_Item; - public InternalItem( LargeForgeEast item ) : base( 0x197E ) - { - Movable = false; + public InternalItem(LargeForgeEast item) : base(0x197E) + { + Movable = false; - m_Item = item; - } + m_Item = item; + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public InternalItem(Serial serial) : base(serial) + { + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 1, Y, Z ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 1, Y, Z); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Item?.Delete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Item ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Item?.Delete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Item); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Item = reader.ReadItem() as LargeForgeEast; - } - } + m_Item = reader.ReadItem() as LargeForgeEast; + } + } - [Engines.Craft.Forge] - private class InternalItem2 : Item - { - private LargeForgeEast m_Item; + [Forge] + private class InternalItem2 : Item + { + private LargeForgeEast m_Item; - public InternalItem2( LargeForgeEast item ) : base( 0x1982 ) - { - Movable = false; + public InternalItem2(LargeForgeEast item) : base(0x1982) + { + Movable = false; - m_Item = item; - } + m_Item = item; + } - public InternalItem2( Serial serial ) : base( serial ) - { - } + public InternalItem2(Serial serial) : base(serial) + { + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( m_Item != null ) - m_Item.Location = new Point3D( X - 2, Y, Z ); - } + public override void OnLocationChange(Point3D oldLocation) + { + if (m_Item != null) + m_Item.Location = new Point3D(X - 2, Y, Z); + } - public override void OnMapChange() - { - if ( m_Item != null ) - m_Item.Map = Map; - } + public override void OnMapChange() + { + if (m_Item != null) + m_Item.Map = Map; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Item?.Delete(); - } + m_Item?.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Item ); - } + writer.Write(m_Item); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_Item = reader.ReadItem() as LargeForgeEast; - } - } - } + m_Item = reader.ReadItem() as LargeForgeEast; + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Camping/Bedroll.cs b/Scripts/Items/Skill Items/Camping/Bedroll.cs index 3bf220fec..8853ba9d7 100644 --- a/Scripts/Items/Skill Items/Camping/Bedroll.cs +++ b/Scripts/Items/Skill Items/Camping/Bedroll.cs @@ -1,130 +1,130 @@ using System; -using Server.Network; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; +using Server.Network; namespace Server.Items { - [FlippableAttribute( 0xA57, 0xA58, 0xA59 )] - public class Bedroll : Item - { - [Constructible] - public Bedroll() : base( 0xA57 ) - { - Weight = 5.0; - } + [Flippable(0xA57, 0xA58, 0xA59)] + public class Bedroll : Item + { + [Constructible] + public Bedroll() : base(0xA57) + { + Weight = 5.0; + } - public Bedroll( Serial serial ) : base( serial ) - { - } + public Bedroll(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( Parent != null || !VerifyMove( from ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (Parent != null || !VerifyMove(from)) + return; - if ( !from.InRange( this, 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + if (!from.InRange(this, 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } - if ( ItemID == 0xA57 ) // rolled - { - Direction dir = PlayerMobile.GetDirection4( from.Location, Location ); + if (ItemID == 0xA57) // rolled + { + Direction dir = PlayerMobile.GetDirection4(from.Location, Location); - if ( dir == Direction.North || dir == Direction.South ) - ItemID = 0xA55; - else - ItemID = 0xA56; - } - else // unrolled - { - ItemID = 0xA57; + if (dir == Direction.North || dir == Direction.South) + ItemID = 0xA55; + else + ItemID = 0xA56; + } + else // unrolled + { + ItemID = 0xA57; - if ( !from.HasGump( typeof( LogoutGump ) ) ) - { - CampfireEntry entry = Campfire.GetEntry( from ); + if (!from.HasGump(typeof(LogoutGump))) + { + CampfireEntry entry = Campfire.GetEntry(from); - if ( entry != null && entry.Safe ) - from.SendGump( new LogoutGump( entry, this ) ); - } - } - } + if (entry != null && entry.Safe) + from.SendGump(new LogoutGump(entry, this)); + } + } + } - private class LogoutGump : Gump - { - private Timer m_CloseTimer; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private CampfireEntry m_Entry; - private Bedroll m_Bedroll; + writer.WriteEncodedInt(0); // version + } - public LogoutGump( CampfireEntry entry, Bedroll bedroll ) : base( 100, 0 ) - { - m_Entry = entry; - m_Bedroll = bedroll; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_CloseTimer = Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), CloseGump ); + int version = reader.ReadEncodedInt(); + } - AddBackground( 0, 0, 400, 350, 0xA28 ); + private class LogoutGump : Gump + { + private Bedroll m_Bedroll; + private Timer m_CloseTimer; - AddHtmlLocalized( 100, 20, 200, 35, 1011015, false, false ); //
Logging out via camping
+ private CampfireEntry m_Entry; - /* Using a bedroll in the safety of a camp will log you out of the game safely. - * If this is what you wish to do choose CONTINUE and you will be logged out. - * Otherwise, select the CANCEL button to avoid logging out at this time. - * The camp will remain secure for 10 seconds at which time this window will close - * and you not be logged out. - */ - AddHtmlLocalized( 50, 55, 300, 140, 1011016, true, true ); + public LogoutGump(CampfireEntry entry, Bedroll bedroll) : base(100, 0) + { + m_Entry = entry; + m_Bedroll = bedroll; - AddButton( 45, 298, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 300, 110, 35, 1011011, false, false ); // CONTINUE + m_CloseTimer = Timer.DelayCall(TimeSpan.FromSeconds(10.0), CloseGump); - AddButton( 200, 298, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 235, 300, 110, 35, 1011012, false, false ); // CANCEL - } + AddBackground(0, 0, 400, 350, 0xA28); - public override void OnResponse( NetState sender, RelayInfo info ) - { - PlayerMobile pm = m_Entry.Player; + AddHtmlLocalized(100, 20, 200, 35, 1011015, false, false); //
Logging out via camping
- m_CloseTimer.Stop(); + /* Using a bedroll in the safety of a camp will log you out of the game safely. + * If this is what you wish to do choose CONTINUE and you will be logged out. + * Otherwise, select the CANCEL button to avoid logging out at this time. + * The camp will remain secure for 10 seconds at which time this window will close + * and you not be logged out. + */ + AddHtmlLocalized(50, 55, 300, 140, 1011016, true, true); - if ( Campfire.GetEntry( pm ) != m_Entry ) - return; + AddButton(45, 298, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 300, 110, 35, 1011011, false, false); // CONTINUE - if ( info.ButtonID == 1 && m_Entry.Safe && m_Bedroll.Parent == null && m_Bedroll.IsAccessibleTo( pm ) - && m_Bedroll.VerifyMove( pm ) && m_Bedroll.Map == pm.Map && pm.InRange( m_Bedroll, 2 ) ) - { - pm.PlaceInBackpack( m_Bedroll ); + AddButton(200, 298, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(235, 300, 110, 35, 1011012, false, false); // CANCEL + } - pm.BedrollLogout = true; - sender.Dispose(); - } + public override void OnResponse(NetState sender, RelayInfo info) + { + PlayerMobile pm = m_Entry.Player; - Campfire.RemoveEntry( m_Entry ); - } + m_CloseTimer.Stop(); - private void CloseGump() - { - Campfire.RemoveEntry( m_Entry ); - m_Entry.Player.CloseGump( typeof( LogoutGump ) ); - } - } + if (Campfire.GetEntry(pm) != m_Entry) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (info.ButtonID == 1 && m_Entry.Safe && m_Bedroll.Parent == null && m_Bedroll.IsAccessibleTo(pm) + && m_Bedroll.VerifyMove(pm) && m_Bedroll.Map == pm.Map && pm.InRange(m_Bedroll, 2)) + { + pm.PlaceInBackpack(m_Bedroll); - writer.WriteEncodedInt( 0 ); // version - } + pm.BedrollLogout = true; + sender.Dispose(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Campfire.RemoveEntry(m_Entry); + } - int version = reader.ReadEncodedInt(); - } - } + private void CloseGump() + { + Campfire.RemoveEntry(m_Entry); + m_Entry.Player.CloseGump(typeof(LogoutGump)); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Camping/Campfire.cs b/Scripts/Items/Skill Items/Camping/Campfire.cs index ccc83fc9a..8a116ce72 100644 --- a/Scripts/Items/Skill Items/Camping/Campfire.cs +++ b/Scripts/Items/Skill Items/Camping/Campfire.cs @@ -1,204 +1,198 @@ using System; using System.Collections; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Items { - public enum CampfireStatus - { - Burning, - Extinguishing, - Off - } + public enum CampfireStatus + { + Burning, + Extinguishing, + Off + } - public class Campfire : Item - { - public static readonly int SecureRange = 7; + public class Campfire : Item + { + public static readonly int SecureRange = 7; - private static readonly Hashtable m_Table = new Hashtable(); + private static readonly Hashtable m_Table = new Hashtable(); - public static CampfireEntry GetEntry( Mobile player ) - { - return (CampfireEntry) m_Table[player]; - } + private ArrayList m_Entries; - public static void RemoveEntry( CampfireEntry entry ) - { - m_Table.Remove( entry.Player ); - entry.Fire.m_Entries.Remove( entry ); - } + private Timer m_Timer; - private Timer m_Timer; + public Campfire() : base(0xDE3) + { + Movable = false; + Light = LightType.Circle300; - private ArrayList m_Entries; + m_Entries = new ArrayList(); - public Campfire() : base( 0xDE3 ) - { - Movable = false; - Light = LightType.Circle300; + Created = DateTime.UtcNow; + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0), OnTick); + } - m_Entries = new ArrayList(); + public Campfire(Serial serial) : base(serial) + { + } - Created = DateTime.UtcNow; - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ), OnTick ); - } + [CommandProperty(AccessLevel.GameMaster)] + public DateTime Created{ get; } - public Campfire( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public CampfireStatus Status + { + get + { + switch (ItemID) + { + case 0xDE3: + return CampfireStatus.Burning; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime Created { get; } + case 0xDE9: + return CampfireStatus.Extinguishing; - [CommandProperty( AccessLevel.GameMaster )] - public CampfireStatus Status - { - get - { - switch ( ItemID ) - { - case 0xDE3: - return CampfireStatus.Burning; + default: + return CampfireStatus.Off; + } + } + set + { + if (Status == value) + return; - case 0xDE9: - return CampfireStatus.Extinguishing; + switch (value) + { + case CampfireStatus.Burning: + ItemID = 0xDE3; + Light = LightType.Circle300; + break; - default: - return CampfireStatus.Off; - } - } - set - { - if ( Status == value ) - return; + case CampfireStatus.Extinguishing: + ItemID = 0xDE9; + Light = LightType.Circle150; + break; - switch ( value ) - { - case CampfireStatus.Burning: - ItemID = 0xDE3; - Light = LightType.Circle300; - break; + default: + ItemID = 0xDEA; + Light = LightType.ArchedWindowEast; + ClearEntries(); + break; + } + } + } - case CampfireStatus.Extinguishing: - ItemID = 0xDE9; - Light = LightType.Circle150; - break; + public static CampfireEntry GetEntry(Mobile player) + { + return (CampfireEntry)m_Table[player]; + } - default: - ItemID = 0xDEA; - Light = LightType.ArchedWindowEast; - ClearEntries(); - break; - } - } - } + public static void RemoveEntry(CampfireEntry entry) + { + m_Table.Remove(entry.Player); + entry.Fire.m_Entries.Remove(entry); + } - private void OnTick() - { - DateTime now = DateTime.UtcNow; - TimeSpan age = now - Created; + private void OnTick() + { + DateTime now = DateTime.UtcNow; + TimeSpan age = now - Created; - if ( age >= TimeSpan.FromSeconds( 100.0 ) ) - Delete(); - else if ( age >= TimeSpan.FromSeconds( 90.0 ) ) - Status = CampfireStatus.Off; - else if ( age >= TimeSpan.FromSeconds( 60.0 ) ) - Status = CampfireStatus.Extinguishing; + if (age >= TimeSpan.FromSeconds(100.0)) + Delete(); + else if (age >= TimeSpan.FromSeconds(90.0)) + Status = CampfireStatus.Off; + else if (age >= TimeSpan.FromSeconds(60.0)) + Status = CampfireStatus.Extinguishing; - if ( Status == CampfireStatus.Off || Deleted ) - return; + if (Status == CampfireStatus.Off || Deleted) + return; - foreach ( CampfireEntry entry in new ArrayList( m_Entries ) ) - { - if ( !entry.Valid || entry.Player.NetState == null ) - { - RemoveEntry( entry ); - } - else if ( !entry.Safe && now - entry.Start >= TimeSpan.FromSeconds( 30.0 ) ) - { - entry.Safe = true; - entry.Player.SendLocalizedMessage( 500621 ); // The camp is now secure. - } - } + foreach (CampfireEntry entry in new ArrayList(m_Entries)) + if (!entry.Valid || entry.Player.NetState == null) + { + RemoveEntry(entry); + } + else if (!entry.Safe && now - entry.Start >= TimeSpan.FromSeconds(30.0)) + { + entry.Safe = true; + entry.Player.SendLocalizedMessage(500621); // The camp is now secure. + } - IPooledEnumerable eable = GetClientsInRange( SecureRange ); + IPooledEnumerable eable = GetClientsInRange(SecureRange); - foreach ( NetState state in eable ) - { - if ( state.Mobile is PlayerMobile pm && GetEntry( pm ) == null ) - { - CampfireEntry entry = new CampfireEntry( pm, this ); + foreach (NetState state in eable) + if (state.Mobile is PlayerMobile pm && GetEntry(pm) == null) + { + CampfireEntry entry = new CampfireEntry(pm, this); - m_Table[pm] = entry; - m_Entries.Add( entry ); + m_Table[pm] = entry; + m_Entries.Add(entry); - pm.SendLocalizedMessage( 500620 ); // You feel it would take a few moments to secure your camp. - } - } + pm.SendLocalizedMessage(500620); // You feel it would take a few moments to secure your camp. + } - eable.Free(); - } + eable.Free(); + } - private void ClearEntries() - { - if ( m_Entries == null ) - return; + private void ClearEntries() + { + if (m_Entries == null) + return; - foreach ( CampfireEntry entry in new ArrayList( m_Entries ) ) - { - RemoveEntry( entry ); - } - } + foreach (CampfireEntry entry in new ArrayList(m_Entries)) RemoveEntry(entry); + } - public override void OnAfterDelete() - { - m_Timer?.Stop(); + public override void OnAfterDelete() + { + m_Timer?.Stop(); - ClearEntries(); - } + ClearEntries(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } - } + Delete(); + } + } - public class CampfireEntry - { - private bool m_Safe; + public class CampfireEntry + { + private bool m_Safe; - public PlayerMobile Player { get; } + public CampfireEntry(PlayerMobile player, Campfire fire) + { + Player = player; + Fire = fire; + Start = DateTime.UtcNow; + m_Safe = false; + } - public Campfire Fire { get; } + public PlayerMobile Player{ get; } - public DateTime Start { get; } + public Campfire Fire{ get; } - public bool Valid => !Fire.Deleted && Fire.Status != CampfireStatus.Off && Player.Map == Fire.Map && Player.InRange( Fire, Campfire.SecureRange ); + public DateTime Start{ get; } - public bool Safe - { - get => Valid && m_Safe; - set => m_Safe = value; - } + public bool Valid => !Fire.Deleted && Fire.Status != CampfireStatus.Off && Player.Map == Fire.Map && + Player.InRange(Fire, Campfire.SecureRange); - public CampfireEntry( PlayerMobile player, Campfire fire ) - { - Player = player; - Fire = fire; - Start = DateTime.UtcNow; - m_Safe = false; - } - } -} + public bool Safe + { + get => Valid && m_Safe; + set => m_Safe = value; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Camping/Kindling.cs b/Scripts/Items/Skill Items/Camping/Kindling.cs index 699262e03..20cbc7c4b 100644 --- a/Scripts/Items/Skill Items/Camping/Kindling.cs +++ b/Scripts/Items/Skill Items/Camping/Kindling.cs @@ -4,115 +4,114 @@ using Server.Regions; namespace Server.Items { - public class Kindling : Item - { - [Constructible] - public Kindling() : this( 1 ) - { - } + public class Kindling : Item + { + [Constructible] + public Kindling() : this(1) + { + } - [Constructible] - public Kindling( int amount ) : base( 0xDE1 ) - { - Stackable = true; - Weight = 5.0; - Amount = amount; - } + [Constructible] + public Kindling(int amount) : base(0xDE1) + { + Stackable = true; + Weight = 5.0; + Amount = amount; + } - public Kindling( Serial serial ) : base( serial ) - { - } + public Kindling(Serial serial) : base(serial) + { + } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !VerifyMove( from ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (!VerifyMove(from)) + return; - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } - Point3D fireLocation = GetFireLocation( from ); + Point3D fireLocation = GetFireLocation(from); - if ( fireLocation == Point3D.Zero ) - { - from.SendLocalizedMessage( 501695 ); // There is not a spot nearby to place your campfire. - } - else if ( !from.CheckSkill( SkillName.Camping, 0.0, 100.0 ) ) - { - from.SendLocalizedMessage( 501696 ); // You fail to ignite the campfire. - } - else - { - Consume(); + if (fireLocation == Point3D.Zero) + { + from.SendLocalizedMessage(501695); // There is not a spot nearby to place your campfire. + } + else if (!from.CheckSkill(SkillName.Camping, 0.0, 100.0)) + { + from.SendLocalizedMessage(501696); // You fail to ignite the campfire. + } + else + { + Consume(); - if ( !Deleted && Parent == null ) - from.PlaceInBackpack( this ); + if (!Deleted && Parent == null) + from.PlaceInBackpack(this); - new Campfire().MoveToWorld( fireLocation, from.Map ); - } - } + new Campfire().MoveToWorld(fireLocation, from.Map); + } + } - private Point3D GetFireLocation( Mobile from ) - { - if ( from.Region.IsPartOf( typeof( DungeonRegion ) ) ) - return Point3D.Zero; + private Point3D GetFireLocation(Mobile from) + { + if (from.Region.IsPartOf(typeof(DungeonRegion))) + return Point3D.Zero; - if ( Parent == null ) - return Location; + if (Parent == null) + return Location; - ArrayList list = new ArrayList( 4 ); + ArrayList list = new ArrayList(4); - AddOffsetLocation( from, 0, -1, list ); - AddOffsetLocation( from, -1, 0, list ); - AddOffsetLocation( from, 0, 1, list ); - AddOffsetLocation( from, 1, 0, list ); + AddOffsetLocation(from, 0, -1, list); + AddOffsetLocation(from, -1, 0, list); + AddOffsetLocation(from, 0, 1, list); + AddOffsetLocation(from, 1, 0, list); - if ( list.Count == 0 ) - return Point3D.Zero; + if (list.Count == 0) + return Point3D.Zero; - int idx = Utility.Random( list.Count ); - return (Point3D) list[idx]; - } + int idx = Utility.Random(list.Count); + return (Point3D)list[idx]; + } - private void AddOffsetLocation( Mobile from, int offsetX, int offsetY, ArrayList list ) - { - Map map = from.Map; + private void AddOffsetLocation(Mobile from, int offsetX, int offsetY, ArrayList list) + { + Map map = from.Map; - int x = from.X + offsetX; - int y = from.Y + offsetY; + int x = from.X + offsetX; + int y = from.Y + offsetY; - Point3D loc = new Point3D( x, y, from.Z ); + Point3D loc = new Point3D(x, y, from.Z); - if ( map.CanFit( loc, 1 ) && from.InLOS( loc ) ) - { - list.Add( loc ); - } - else - { - loc = new Point3D( x, y, map.GetAverageZ( x, y ) ); + if (map.CanFit(loc, 1) && from.InLOS(loc)) + { + list.Add(loc); + } + else + { + loc = new Point3D(x, y, map.GetAverageZ(x, y)); - if ( map.CanFit( loc, 1 ) && from.InLOS( loc ) ) - list.Add( loc ); - } - } - } + if (map.CanFit(loc, 1) && from.InLOS(loc)) + list.Add(loc); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Carpenter Items/Board.cs b/Scripts/Items/Skill Items/Carpenter Items/Board.cs index 9a5e1879b..392b9f89b 100644 --- a/Scripts/Items/Skill Items/Carpenter Items/Board.cs +++ b/Scripts/Items/Skill Items/Carpenter Items/Board.cs @@ -1,322 +1,325 @@ namespace Server.Items { - [FlippableAttribute( 0x1BD7, 0x1BDA )] - public class Board : Item, ICommodity - { - private CraftResource m_Resource; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set { m_Resource = value; InvalidateProperties(); } - } - - int ICommodity.DescriptionNumber - { - get - { - if ( m_Resource >= CraftResource.OakWood && m_Resource <= CraftResource.YewWood ) - return 1075052 + ( (int)m_Resource - (int)CraftResource.OakWood ); - - switch ( m_Resource ) - { - case CraftResource.Bloodwood: return 1075055; - case CraftResource.Frostwood: return 1075056; - case CraftResource.Heartwood: return 1075062; //WHY Osi. Why? - } - - return LabelNumber; - } - } - - bool ICommodity.IsDeedable => true; - - [Constructible] - public Board() - : this( 1 ) - { - } - - [Constructible] - public Board( int amount ) - : this( CraftResource.RegularWood, amount ) - { - } - - public Board( Serial serial ) - : base( serial ) - { - } - - [Constructible] - public Board( CraftResource resource ) : this( resource, 1 ) - { - } - - [Constructible] - public Board( CraftResource resource, int amount ) - : base( 0x1BD7 ) - { - Stackable = true; - Amount = amount; - - m_Resource = resource; - Hue = CraftResources.GetHue( resource ); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); - - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } - - - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 3 ); - - writer.Write( (int)m_Resource ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 3: - case 2: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - } - - if ( (version == 0 && Weight == 0.1) || ( version <= 2 && Weight == 2 ) ) - Weight = -1; - - if ( version <= 1 ) - m_Resource = CraftResource.RegularWood; - } - } - - - public class HeartwoodBoard : Board - { - [Constructible] - public HeartwoodBoard() - : this( 1 ) - { - } - - [Constructible] - public HeartwoodBoard( int amount ) - : base( CraftResource.Heartwood, amount ) - { - } - - public HeartwoodBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BloodwoodBoard : Board - { - [Constructible] - public BloodwoodBoard() - : this( 1 ) - { - } - - [Constructible] - public BloodwoodBoard( int amount ) - : base( CraftResource.Bloodwood, amount ) - { - } - - public BloodwoodBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FrostwoodBoard : Board - { - [Constructible] - public FrostwoodBoard() - : this( 1 ) - { - } - - [Constructible] - public FrostwoodBoard( int amount ) - : base( CraftResource.Frostwood, amount ) - { - } - - public FrostwoodBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class OakBoard : Board - { - [Constructible] - public OakBoard() - : this( 1 ) - { - } - - [Constructible] - public OakBoard( int amount ) - : base( CraftResource.OakWood, amount ) - { - } - - public OakBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AshBoard : Board - { - [Constructible] - public AshBoard() - : this( 1 ) - { - } - - [Constructible] - public AshBoard( int amount ) - : base( CraftResource.AshWood, amount ) - { - } - - public AshBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class YewBoard : Board - { - [Constructible] - public YewBoard() - : this( 1 ) - { - } - - [Constructible] - public YewBoard( int amount ) - : base( CraftResource.YewWood, amount ) - { - } - - public YewBoard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + [Flippable(0x1BD7, 0x1BDA)] + public class Board : Item, ICommodity + { + private CraftResource m_Resource; + + [Constructible] + public Board() + : this(1) + { + } + + [Constructible] + public Board(int amount) + : this(CraftResource.RegularWood, amount) + { + } + + public Board(Serial serial) + : base(serial) + { + } + + [Constructible] + public Board(CraftResource resource) : this(resource, 1) + { + } + + [Constructible] + public Board(CraftResource resource, int amount) + : base(0x1BD7) + { + Stackable = true; + Amount = amount; + + m_Resource = resource; + Hue = CraftResources.GetHue(resource); + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } + + int ICommodity.DescriptionNumber + { + get + { + if (m_Resource >= CraftResource.OakWood && m_Resource <= CraftResource.YewWood) + return 1075052 + ((int)m_Resource - (int)CraftResource.OakWood); + + switch (m_Resource) + { + case CraftResource.Bloodwood: return 1075055; + case CraftResource.Frostwood: return 1075056; + case CraftResource.Heartwood: return 1075062; //WHY Osi. Why? + } + + return LabelNumber; + } + } + + bool ICommodity.IsDeedable => true; + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); + + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } + + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(3); + + writer.Write((int)m_Resource); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + case 2: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } + + if (version == 0 && Weight == 0.1 || version <= 2 && Weight == 2) + Weight = -1; + + if (version <= 1) + m_Resource = CraftResource.RegularWood; + } + } + + + public class HeartwoodBoard : Board + { + [Constructible] + public HeartwoodBoard() + : this(1) + { + } + + [Constructible] + public HeartwoodBoard(int amount) + : base(CraftResource.Heartwood, amount) + { + } + + public HeartwoodBoard(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BloodwoodBoard : Board + { + [Constructible] + public BloodwoodBoard() + : this(1) + { + } + + [Constructible] + public BloodwoodBoard(int amount) + : base(CraftResource.Bloodwood, amount) + { + } + + public BloodwoodBoard(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FrostwoodBoard : Board + { + [Constructible] + public FrostwoodBoard() + : this(1) + { + } + + [Constructible] + public FrostwoodBoard(int amount) + : base(CraftResource.Frostwood, amount) + { + } + + public FrostwoodBoard(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class OakBoard : Board + { + [Constructible] + public OakBoard() + : this(1) + { + } + + [Constructible] + public OakBoard(int amount) + : base(CraftResource.OakWood, amount) + { + } + + public OakBoard(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AshBoard : Board + { + [Constructible] + public AshBoard() + : this(1) + { + } + + [Constructible] + public AshBoard(int amount) + : base(CraftResource.AshWood, amount) + { + } + + public AshBoard(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class YewBoard : Board + { + [Constructible] + public YewBoard() + : this(1) + { + } + + [Constructible] + public YewBoard(int amount) + : base(CraftResource.YewWood, amount) + { + } + + public YewBoard(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Carpenter Items/TaxidermyKit.cs b/Scripts/Items/Skill Items/Carpenter Items/TaxidermyKit.cs index 2c34f93f6..5b88738de 100644 --- a/Scripts/Items/Skill Items/Carpenter Items/TaxidermyKit.cs +++ b/Scripts/Items/Skill Items/Carpenter Items/TaxidermyKit.cs @@ -1,490 +1,542 @@ using System; -using Server.Multis; using Server.Mobiles; +using Server.Multis; using Server.Targeting; namespace Server.Items { - [FlippableAttribute( 0x1EBA, 0x1EBB )] - public class TaxidermyKit : Item - { - public override int LabelNumber => 1041279; // a taxidermy kit + [Flippable(0x1EBA, 0x1EBB)] + public class TaxidermyKit : Item + { + private static TrophyInfo[] m_Table = + { + new TrophyInfo(typeof(BrownBear), 0x1E60, 1041093, 1041107), + new TrophyInfo(typeof(GreatHart), 0x1E61, 1041095, 1041109), + new TrophyInfo(typeof(BigFish), 0x1E62, 1041096, 1041110), + new TrophyInfo(typeof(Gorilla), 0x1E63, 1041091, 1041105), + new TrophyInfo(typeof(Orc), 0x1E64, 1041090, 1041104), + new TrophyInfo(typeof(PolarBear), 0x1E65, 1041094, 1041108), + new TrophyInfo(typeof(Troll), 0x1E66, 1041092, 1041106) + }; - [Constructible] - public TaxidermyKit() : base( 0x1EBA ) - { - Weight = 1.0; - } + [Constructible] + public TaxidermyKit() : base(0x1EBA) + { + Weight = 1.0; + } - public TaxidermyKit( Serial serial ) : base( serial ) - { - } + public TaxidermyKit(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int LabelNumber => 1041279; // a taxidermy kit - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnDoubleClick(Mobile from) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.Skills[SkillName.Carpentry].Base < 90.0 ) - { - from.SendLocalizedMessage( 1042594 ); // You do not understand how to use this. - } - else - { - from.SendLocalizedMessage( 1042595 ); // Target the corpse to make a trophy out of. - from.Target = new CorpseTarget( this ); - } - } + int version = reader.ReadInt(); + } - private static TrophyInfo[] m_Table = { - new TrophyInfo( typeof( BrownBear ), 0x1E60, 1041093, 1041107 ), - new TrophyInfo( typeof( GreatHart ), 0x1E61, 1041095, 1041109 ), - new TrophyInfo( typeof( BigFish ), 0x1E62, 1041096, 1041110 ), - new TrophyInfo( typeof( Gorilla ), 0x1E63, 1041091, 1041105 ), - new TrophyInfo( typeof( Orc ), 0x1E64, 1041090, 1041104 ), - new TrophyInfo( typeof( PolarBear ), 0x1E65, 1041094, 1041108 ), - new TrophyInfo( typeof( Troll ), 0x1E66, 1041092, 1041106 ) - }; + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.Skills[SkillName.Carpentry].Base < 90.0) + { + from.SendLocalizedMessage(1042594); // You do not understand how to use this. + } + else + { + from.SendLocalizedMessage(1042595); // Target the corpse to make a trophy out of. + from.Target = new CorpseTarget(this); + } + } - public class TrophyInfo + public class TrophyInfo + { + public TrophyInfo(Type type, int id, int deedNum, int addonNum) + { + CreatureType = type; + NorthID = id; + DeedNumber = deedNum; + AddonNumber = addonNum; + } + + public Type CreatureType{ get; } + + public int NorthID{ get; } + + public int DeedNumber{ get; } + + public int AddonNumber{ get; } + } + + + private class CorpseTarget : Target + { + private TaxidermyKit m_Kit; + + public CorpseTarget(TaxidermyKit kit) : base(3, false, TargetFlags.None) + { + m_Kit = kit; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Kit.Deleted) + return; + + if (!(targeted is Corpse) && !(targeted is BigFish)) { - public TrophyInfo( Type type, int id, int deedNum, int addonNum ) + from.SendLocalizedMessage(1042600); // That is not a corpse! + } + else if (targeted is Corpse corpse && corpse.VisitedByTaxidermist) + { + from.SendLocalizedMessage(1042596); // That corpse seems to have been visited by a taxidermist already. + } + else if (!m_Kit.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.Skills[SkillName.Carpentry].Base < 90.0) + { + from.SendLocalizedMessage(1042603); // You would not understand how to use the kit. + } + else + { + object obj = targeted; + + if (obj is Corpse) + obj = ((Corpse)obj).Owner; + + if (obj != null) + for (int i = 0; i < m_Table.Length; i++) + if (m_Table[i].CreatureType == obj.GetType()) + { + Container pack = from.Backpack; + + if (pack != null && pack.ConsumeTotal(typeof(Board), 10)) + { + from.SendLocalizedMessage( + 1042278); // You review the corpse and find it worthy of a trophy. + from.SendLocalizedMessage(1042602); // You use your kit up making the trophy. + + Mobile hunter = null; + int weight = 0; + + if (targeted is BigFish fish) + { + hunter = fish.Fisher; + weight = (int)fish.Weight; + + fish.Consume(); + } + + + from.AddToBackpack(new TrophyDeed(m_Table[i], hunter, weight)); + + if (targeted is Corpse corpse1) + corpse1.VisitedByTaxidermist = true; + + m_Kit.Delete(); + return; + } + + from.SendLocalizedMessage(1042598); // You do not have enough boards. + return; + } + + from.SendLocalizedMessage(1042599); // That does not look like something you want hanging on a wall. + } + } + } + } + + public class TrophyAddon : Item, IAddon + { + private int m_AddonNumber; + private int m_AnimalWeight; + + private Mobile m_Hunter; + + [Constructible] + public TrophyAddon(Mobile from, int itemID, int westID, int northID, int deedNumber, int addonNumber) : this(from, + itemID, westID, northID, deedNumber, addonNumber, null, 0) + { + } + + public TrophyAddon(Mobile from, int itemID, int westID, int northID, int deedNumber, int addonNumber, Mobile hunter, + int animalWeight) : base(itemID) + { + WestID = westID; + NorthID = northID; + DeedNumber = deedNumber; + m_AddonNumber = addonNumber; + + m_Hunter = hunter; + m_AnimalWeight = animalWeight; + + Movable = false; + + MoveToWorld(from.Location, from.Map); + } + + public TrophyAddon(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + [CommandProperty(AccessLevel.GameMaster)] + public int WestID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int NorthID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int DeedNumber{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int AddonNumber + { + get => m_AddonNumber; + set + { + m_AddonNumber = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Hunter + { + get => m_Hunter; + set + { + m_Hunter = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int AnimalWeight + { + get => m_AnimalWeight; + set + { + m_AnimalWeight = value; + InvalidateProperties(); + } + } + + public override int LabelNumber => m_AddonNumber; + + public bool CouldFit(IPoint3D p, Map map) + { + if (!map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; + + if (ItemID == NorthID) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // North wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // West wall + } + + public Item Deed => new TrophyDeed(WestID, NorthID, DeedNumber, m_AddonNumber, m_Hunter, m_AnimalWeight); + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_AnimalWeight >= 20) + { + if (m_Hunter != null) + list.Add(1070857, m_Hunter.Name); // Caught by ~1_fisherman~ + + list.Add(1070858, m_AnimalWeight.ToString()); // ~1_weight~ stones + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(m_Hunter); + writer.Write(m_AnimalWeight); + + writer.Write(WestID); + writer.Write(NorthID); + writer.Write(DeedNumber); + writer.Write(m_AddonNumber); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Hunter = reader.ReadMobile(); + m_AnimalWeight = reader.ReadInt(); + goto case 0; + } + case 0: + { + WestID = reader.ReadInt(); + NorthID = reader.ReadInt(); + DeedNumber = reader.ReadInt(); + m_AddonNumber = reader.ReadInt(); + break; + } + } + + Timer.DelayCall(TimeSpan.Zero, FixMovingCrate); + } + + private void FixMovingCrate() + { + if (Deleted) + return; + + if (Movable || IsLockedDown) + { + Item deed = Deed; + + if (Parent is Item item) + { + item.AddItem(deed); + deed.Location = Location; + } + else + { + deed.MoveToWorld(Location, Map); + } + + Delete(); + } + } + + public override void OnDoubleClick(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsCoOwner(from)) + { + if (from.InRange(GetWorldLocation(), 1)) + { + from.AddToBackpack(Deed); + Delete(); + } + else + { + from.SendLocalizedMessage(500295); // You are too far away to do that. + } + } + } + } + + [Flippable(0x14F0, 0x14EF)] + public class TrophyDeed : Item + { + private int m_AnimalWeight; + private int m_DeedNumber; + + private Mobile m_Hunter; + + [Constructible] + public TrophyDeed(int westID, int northID, int deedNumber, int addonNumber) : this(westID, northID, deedNumber, + addonNumber, null, 0) + { + } + + public TrophyDeed(int westID, int northID, int deedNumber, int addonNumber, Mobile hunter, int animalWeight) : + base(0x14F0) + { + WestID = westID; + NorthID = northID; + m_DeedNumber = deedNumber; + AddonNumber = addonNumber; + m_Hunter = hunter; + m_AnimalWeight = animalWeight; + } + + public TrophyDeed(TaxidermyKit.TrophyInfo info, Mobile hunter, int animalWeight) + : this(info.NorthID + 7, info.NorthID, info.DeedNumber, info.AddonNumber, hunter, animalWeight) + { + } + + public TrophyDeed(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int WestID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int NorthID{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int DeedNumber + { + get => m_DeedNumber; + set + { + m_DeedNumber = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int AddonNumber{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Hunter + { + get => m_Hunter; + set + { + m_Hunter = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int AnimalWeight + { + get => m_AnimalWeight; + set + { + m_AnimalWeight = value; + InvalidateProperties(); + } + } + + public override int LabelNumber => m_DeedNumber; + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_AnimalWeight >= 20) + { + if (m_Hunter != null) + list.Add(1070857, m_Hunter.Name); // Caught by ~1_fisherman~ + + list.Add(1070858, m_AnimalWeight.ToString()); // ~1_weight~ stones + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(m_Hunter); + writer.Write(m_AnimalWeight); + + writer.Write(WestID); + writer.Write(NorthID); + writer.Write(m_DeedNumber); + writer.Write(AddonNumber); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Hunter = reader.ReadMobile(); + m_AnimalWeight = reader.ReadInt(); + goto case 0; + } + case 0: + { + WestID = reader.ReadInt(); + NorthID = reader.ReadInt(); + m_DeedNumber = reader.ReadInt(); + AddonNumber = reader.ReadInt(); + break; + } + } + } + + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsCoOwner(from)) + { + bool northWall = BaseAddon.IsWall(from.X, from.Y - 1, from.Z, from.Map); + bool westWall = BaseAddon.IsWall(from.X - 1, from.Y, from.Z, from.Map); + + if (northWall && westWall) + switch (from.Direction & Direction.Mask) { - CreatureType = type; - NorthID = id; - DeedNumber = deedNum; - AddonNumber = addonNum; + case Direction.North: + case Direction.South: + northWall = true; + westWall = false; + break; + + case Direction.East: + case Direction.West: + northWall = false; + westWall = true; + break; + + default: + from.SendMessage("Turn to face the wall on which to hang this trophy."); + return; } - public Type CreatureType { get; } + int itemID = 0; - public int NorthID { get; } + if (northWall) + itemID = NorthID; + else if (westWall) + itemID = WestID; + else + from.SendLocalizedMessage(1042626); // The trophy must be placed next to a wall. - public int DeedNumber { get; } - - public int AddonNumber { get; } + if (itemID > 0) + { + house.Addons.Add(new TrophyAddon(from, itemID, WestID, NorthID, m_DeedNumber, AddonNumber, m_Hunter, + m_AnimalWeight)); + Delete(); + } } - - - private class CorpseTarget : Target - { - private TaxidermyKit m_Kit; - - public CorpseTarget( TaxidermyKit kit ) : base( 3, false, TargetFlags.None ) - { - m_Kit = kit; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Kit.Deleted ) - return; - - if ( !(targeted is Corpse) && !(targeted is BigFish) ) - { - from.SendLocalizedMessage( 1042600 ); // That is not a corpse! - } - else if ( targeted is Corpse corpse && corpse.VisitedByTaxidermist ) - { - from.SendLocalizedMessage( 1042596 ); // That corpse seems to have been visited by a taxidermist already. - } - else if ( !m_Kit.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.Skills[SkillName.Carpentry].Base < 90.0 ) - { - from.SendLocalizedMessage( 1042603 ); // You would not understand how to use the kit. - } - else - { - object obj = targeted; - - if ( obj is Corpse ) - obj = ((Corpse)obj).Owner; - - if ( obj != null ) - { - for ( int i = 0; i < m_Table.Length; i++ ) - { - if ( m_Table[i].CreatureType == obj.GetType() ) - { - Container pack = from.Backpack; - - if ( pack != null && pack.ConsumeTotal( typeof( Board ), 10 ) ) - { - from.SendLocalizedMessage( 1042278 ); // You review the corpse and find it worthy of a trophy. - from.SendLocalizedMessage( 1042602 ); // You use your kit up making the trophy. - - Mobile hunter = null; - int weight = 0; - - if ( targeted is BigFish fish ) - { - hunter = fish.Fisher; - weight = (int)fish.Weight; - - fish.Consume(); - } - - - from.AddToBackpack( new TrophyDeed( m_Table[i], hunter, weight ) ); - - if ( targeted is Corpse corpse1 ) - corpse1.VisitedByTaxidermist = true; - - m_Kit.Delete(); - return; - } - - from.SendLocalizedMessage( 1042598 ); // You do not have enough boards. - return; - } - } - } - - from.SendLocalizedMessage( 1042599 ); // That does not look like something you want hanging on a wall. - } - } - } - } - - public class TrophyAddon : Item, IAddon - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - private int m_AddonNumber; - - private Mobile m_Hunter; - private int m_AnimalWeight; - - [CommandProperty( AccessLevel.GameMaster )] - public int WestID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int NorthID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int DeedNumber { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int AddonNumber{ get => m_AddonNumber; - set{ m_AddonNumber = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Hunter{ get => m_Hunter; - set{ m_Hunter = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int AnimalWeight{ get => m_AnimalWeight; - set{ m_AnimalWeight = value; InvalidateProperties(); } } - - public override int LabelNumber => m_AddonNumber; - - [Constructible] - public TrophyAddon( Mobile from, int itemID, int westID, int northID, int deedNumber, int addonNumber ) : this( from, itemID, westID, northID, deedNumber, addonNumber, null, 0 ) - { - } - - public TrophyAddon( Mobile from, int itemID, int westID, int northID, int deedNumber, int addonNumber, Mobile hunter, int animalWeight ) : base( itemID ) - { - WestID = westID; - NorthID = northID; - DeedNumber = deedNumber; - m_AddonNumber = addonNumber; - - m_Hunter = hunter; - m_AnimalWeight = animalWeight; - - Movable = false; - - MoveToWorld( from.Location, from.Map ); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_AnimalWeight >= 20 ) - { - if ( m_Hunter != null ) - list.Add( 1070857, m_Hunter.Name ); // Caught by ~1_fisherman~ - - list.Add( 1070858, m_AnimalWeight.ToString() ); // ~1_weight~ stones - } - } - - public TrophyAddon( Serial serial ) : base( serial ) - { - } - - public bool CouldFit( IPoint3D p, Map map ) - { - if ( !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; - - if ( ItemID == NorthID ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // North wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // West wall - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( (Mobile) m_Hunter ); - writer.Write( (int) m_AnimalWeight ); - - writer.Write( (int) WestID ); - writer.Write( (int) NorthID ); - writer.Write( (int) DeedNumber ); - writer.Write( (int) m_AddonNumber ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_Hunter = reader.ReadMobile(); - m_AnimalWeight = reader.ReadInt(); - goto case 0; - } - case 0: - { - WestID = reader.ReadInt(); - NorthID = reader.ReadInt(); - DeedNumber = reader.ReadInt(); - m_AddonNumber = reader.ReadInt(); - break; - } - } - - Timer.DelayCall( TimeSpan.Zero, FixMovingCrate ); - } - - private void FixMovingCrate() - { - if ( Deleted ) - return; - - if ( Movable || IsLockedDown ) - { - Item deed = Deed; - - if ( Parent is Item item ) - { - item.AddItem( deed ); - deed.Location = Location; - } - else - { - deed.MoveToWorld( Location, Map ); - } - - Delete(); - } - } - - public Item Deed => new TrophyDeed( WestID, NorthID, DeedNumber, m_AddonNumber, m_Hunter, m_AnimalWeight ); - - public override void OnDoubleClick( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null && house.IsCoOwner( from ) ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - from.AddToBackpack( Deed ); - Delete(); - } - else - { - from.SendLocalizedMessage( 500295 ); // You are too far away to do that. - } - } - } - } - - [Flippable( 0x14F0, 0x14EF )] - public class TrophyDeed : Item - { - private int m_DeedNumber; - - private Mobile m_Hunter; - private int m_AnimalWeight; - - [CommandProperty( AccessLevel.GameMaster )] - public int WestID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int NorthID { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int DeedNumber{ get => m_DeedNumber; - set{ m_DeedNumber = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int AddonNumber { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Hunter{ get => m_Hunter; - set{ m_Hunter = value; InvalidateProperties(); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int AnimalWeight{ get => m_AnimalWeight; - set{ m_AnimalWeight = value; InvalidateProperties(); } } - - public override int LabelNumber => m_DeedNumber; - - [Constructible] - public TrophyDeed( int westID, int northID, int deedNumber, int addonNumber ) : this( westID, northID, deedNumber, addonNumber, null, 0 ) - { - } - - public TrophyDeed( int westID, int northID, int deedNumber, int addonNumber, Mobile hunter, int animalWeight ) : base( 0x14F0 ) - { - WestID = westID; - NorthID = northID; - m_DeedNumber = deedNumber; - AddonNumber = addonNumber; - m_Hunter = hunter; - m_AnimalWeight = animalWeight; - } - - public TrophyDeed( TaxidermyKit.TrophyInfo info, Mobile hunter, int animalWeight ) - : this( info.NorthID + 7, info.NorthID, info.DeedNumber, info.AddonNumber, hunter, animalWeight ) + else { + from.SendLocalizedMessage(502092); // You must be in your house to do this. } - public TrophyDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_AnimalWeight >= 20 ) - { - if ( m_Hunter != null ) - list.Add( 1070857, m_Hunter.Name ); // Caught by ~1_fisherman~ - - list.Add( 1070858, m_AnimalWeight.ToString() ); // ~1_weight~ stones - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( (Mobile) m_Hunter ); - writer.Write( (int) m_AnimalWeight ); - - writer.Write( (int) WestID ); - writer.Write( (int) NorthID ); - writer.Write( (int) m_DeedNumber ); - writer.Write( (int) AddonNumber ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_Hunter = reader.ReadMobile(); - m_AnimalWeight = reader.ReadInt(); - goto case 0; - } - case 0: - { - WestID = reader.ReadInt(); - NorthID = reader.ReadInt(); - m_DeedNumber = reader.ReadInt(); - AddonNumber = reader.ReadInt(); - break; - } - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsCoOwner( from ) ) - { - bool northWall = BaseAddon.IsWall( from.X, from.Y - 1, from.Z, from.Map ); - bool westWall = BaseAddon.IsWall( from.X - 1, from.Y, from.Z, from.Map ); - - if ( northWall && westWall ) - { - switch ( from.Direction & Direction.Mask ) - { - case Direction.North: - case Direction.South: northWall = true; westWall = false; break; - - case Direction.East: - case Direction.West: northWall = false; westWall = true; break; - - default: from.SendMessage( "Turn to face the wall on which to hang this trophy." ); return; - } - } - - int itemID = 0; - - if ( northWall ) - itemID = NorthID; - else if ( westWall ) - itemID = WestID; - else - from.SendLocalizedMessage( 1042626 ); // The trophy must be placed next to a wall. - - if ( itemID > 0 ) - { - house.Addons.Add( new TrophyAddon( from, itemID, WestID, NorthID, m_DeedNumber, AddonNumber, m_Hunter, m_AnimalWeight ) ); - Delete(); - } - } - else - { - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - } -} + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Fishing/FishingPole.cs b/Scripts/Items/Skill Items/Fishing/FishingPole.cs index 9f675a38b..f77ace741 100644 --- a/Scripts/Items/Skill Items/Fishing/FishingPole.cs +++ b/Scripts/Items/Skill Items/Fishing/FishingPole.cs @@ -1,69 +1,69 @@ -using Server.Engines.Harvest; using System.Collections.Generic; using Server.ContextMenus; +using Server.Engines.Harvest; using Server.Network; namespace Server.Items { - public class FishingPole : Item - { - [Constructible] - public FishingPole() : base( 0x0DC0 ) - { - Layer = Layer.TwoHanded; - Weight = 8.0; - } + public class FishingPole : Item + { + [Constructible] + public FishingPole() : base(0x0DC0) + { + Layer = Layer.TwoHanded; + Weight = 8.0; + } - public override void OnDoubleClick( Mobile from ) - { - Point3D loc = GetWorldLocation(); + public FishingPole(Serial serial) : base(serial) + { + } - if ( !from.InLOS( loc ) || !from.InRange( loc, 2 ) ) - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 1019045 ); // I can't reach that - else - Fishing.System.BeginHarvesting( from, this ); - } + public override void OnDoubleClick(Mobile from) + { + Point3D loc = GetWorldLocation(); - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (!from.InLOS(loc) || !from.InRange(loc, 2)) + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 1019045); // I can't reach that + else + Fishing.System.BeginHarvesting(from, this); + } - BaseHarvestTool.AddContextMenuEntries( from, this, list, Fishing.System ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override bool CheckConflictingLayer( Mobile m, Item item, Layer layer ) - { - if ( base.CheckConflictingLayer( m, item, layer ) ) - return true; + BaseHarvestTool.AddContextMenuEntries(from, this, list, Fishing.System); + } - if ( layer == Layer.OneHanded ) - { - m.SendLocalizedMessage( 500214 ); // You already have something in both hands. - return true; - } + public override bool CheckConflictingLayer(Mobile m, Item item, Layer layer) + { + if (base.CheckConflictingLayer(m, item, layer)) + return true; - return false; - } + if (layer == Layer.OneHanded) + { + m.SendLocalizedMessage(500214); // You already have something in both hands. + return true; + } - public FishingPole( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 && Layer == Layer.OneHanded ) - Layer = Layer.TwoHanded; - } - } + if (version < 1 && Layer == Layer.OneHanded) + Layer = Layer.TwoHanded; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Fishing/Misc/MessageInABottle.cs b/Scripts/Items/Skill Items/Fishing/Misc/MessageInABottle.cs index 5b9f72945..ab16decf2 100644 --- a/Scripts/Items/Skill Items/Fishing/Misc/MessageInABottle.cs +++ b/Scripts/Items/Skill Items/Fishing/Misc/MessageInABottle.cs @@ -1,107 +1,108 @@ using System; +using Server.Network; namespace Server.Items { - public class MessageInABottle : Item - { - public static int GetRandomLevel() - { - if ( Core.AOS && 1 > Utility.Random( 25 ) ) - return 4; // ancient + public class MessageInABottle : Item + { + private int m_Level; - return Utility.RandomMinMax( 1, 3 ); - } + [Constructible] + public MessageInABottle() : this(Map.Trammel) + { + } - public override int LabelNumber => 1041080; // a message in a bottle + public MessageInABottle(Map map) : this(map, GetRandomLevel()) + { + } - private int m_Level; + [Constructible] + public MessageInABottle(Map map, int level) : base(0x099F) + { + Weight = 1.0; + TargetMap = map; + m_Level = level; + } - [CommandProperty( AccessLevel.GameMaster )] - public Map TargetMap { get; set; } + public MessageInABottle(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Level - { - get => m_Level; - set => m_Level = Math.Max( 1, Math.Min( value, 4 ) ); - } + public override int LabelNumber => 1041080; // a message in a bottle - [Constructible] - public MessageInABottle() : this( Map.Trammel ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public Map TargetMap{ get; set; } - public MessageInABottle( Map map ) : this( map, GetRandomLevel() ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Level + { + get => m_Level; + set => m_Level = Math.Max(1, Math.Min(value, 4)); + } - [Constructible] - public MessageInABottle( Map map, int level ) : base( 0x099F ) - { - Weight = 1.0; - TargetMap = map; - m_Level = level; - } + public static int GetRandomLevel() + { + if (Core.AOS && 1 > Utility.Random(25)) + return 4; // ancient - public MessageInABottle( Serial serial ) : base( serial ) - { - } + return Utility.RandomMinMax(1, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 3 ); // version + writer.Write(3); // version - writer.Write( (int) m_Level ); + writer.Write(m_Level); - writer.Write( TargetMap ); - } + writer.Write(TargetMap); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 3: - case 2: - { - m_Level = reader.ReadInt(); - goto case 1; - } - case 1: - { - TargetMap = reader.ReadMap(); - break; - } - case 0: - { - TargetMap = Map.Trammel; - break; - } - } + switch (version) + { + case 3: + case 2: + { + m_Level = reader.ReadInt(); + goto case 1; + } + case 1: + { + TargetMap = reader.ReadMap(); + break; + } + case 0: + { + TargetMap = Map.Trammel; + break; + } + } - if ( version < 2 ) - m_Level = GetRandomLevel(); + if (version < 2) + m_Level = GetRandomLevel(); - if ( version < 3 && TargetMap == Map.Tokuno ) - TargetMap = Map.Trammel; - } + if (version < 3 && TargetMap == Map.Tokuno) + TargetMap = Map.Trammel; + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - ReplaceWith( new SOS( TargetMap, m_Level ) ); - from.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, 501891 ); // You extract the message from the bottle. - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - } -} + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + ReplaceWith(new SOS(TargetMap, m_Level)); + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501891); // You extract the message from the bottle. + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Fishing/Misc/SOS.cs b/Scripts/Items/Skill Items/Fishing/Misc/SOS.cs index 9f03d5d4a..8db8f5ec7 100644 --- a/Scripts/Items/Skill Items/Fishing/Misc/SOS.cs +++ b/Scripts/Items/Skill Items/Fishing/Misc/SOS.cs @@ -3,229 +3,231 @@ using Server.Gumps; namespace Server.Items { - [Flippable( 0x14ED, 0x14EE )] - public class SOS : Item - { - public override int LabelNumber - { - get - { - if ( IsAncient ) - return 1063450; // an ancient SOS + [Flippable(0x14ED, 0x14EE)] + public class SOS : Item + { + public override int LabelNumber + { + get + { + if (IsAncient) + return 1063450; // an ancient SOS - return 1041081; // a waterstained SOS - } - } + return 1041081; // a waterstained SOS + } + } - private int m_Level; + private int m_Level; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsAncient => ( m_Level >= 4 ); + [CommandProperty(AccessLevel.GameMaster)] + public bool IsAncient => m_Level >= 4; - [CommandProperty( AccessLevel.GameMaster )] - public int Level - { - get => m_Level; - set - { - m_Level = Math.Max( 1, Math.Min( value, 4 ) ); - UpdateHue(); - InvalidateProperties(); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public int Level + { + get => m_Level; + set + { + m_Level = Math.Max(1, Math.Min(value, 4)); + UpdateHue(); + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public Map TargetMap { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public Map TargetMap{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public Point3D TargetLocation { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public Point3D TargetLocation{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int MessageIndex { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int MessageIndex{ get; set; } - public void UpdateHue() - { - if ( IsAncient ) - Hue = 0x481; - else - Hue = 0; - } + public void UpdateHue() + { + if (IsAncient) + Hue = 0x481; + else + Hue = 0; + } - [Constructible] - public SOS() : this( Map.Trammel ) - { - } + [Constructible] + public SOS() : this(Map.Trammel) + { + } - [Constructible] - public SOS( Map map ) : this( map, MessageInABottle.GetRandomLevel() ) - { - } + [Constructible] + public SOS(Map map) : this(map, MessageInABottle.GetRandomLevel()) + { + } - [Constructible] - public SOS( Map map, int level ) : base( 0x14EE ) - { - Weight = 1.0; + [Constructible] + public SOS(Map map, int level) : base(0x14EE) + { + Weight = 1.0; - m_Level = level; - MessageIndex = Utility.Random( MessageEntry.Entries.Length ); - TargetMap = map; - TargetLocation = FindLocation( TargetMap ); + m_Level = level; + MessageIndex = Utility.Random(MessageEntry.Entries.Length); + TargetMap = map; + TargetLocation = FindLocation(TargetMap); - UpdateHue(); - } + UpdateHue(); + } - public SOS( Serial serial ) : base( serial ) - { - } + public SOS(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 4 ); // version + writer.Write(4); // version - writer.Write( m_Level ); + writer.Write(m_Level); - writer.Write( TargetMap ); - writer.Write( TargetLocation ); - writer.Write( MessageIndex ); - } + writer.Write(TargetMap); + writer.Write(TargetLocation); + writer.Write(MessageIndex); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 4: - case 3: - case 2: - { - m_Level = reader.ReadInt(); - goto case 1; - } - case 1: - { - TargetMap = reader.ReadMap(); - TargetLocation = reader.ReadPoint3D(); - MessageIndex = reader.ReadInt(); + switch (version) + { + case 4: + case 3: + case 2: + { + m_Level = reader.ReadInt(); + goto case 1; + } + case 1: + { + TargetMap = reader.ReadMap(); + TargetLocation = reader.ReadPoint3D(); + MessageIndex = reader.ReadInt(); - break; - } - case 0: - { - TargetMap = Map; + break; + } + case 0: + { + TargetMap = Map; - if ( TargetMap == null || TargetMap == Map.Internal ) - TargetMap = Map.Trammel; + if (TargetMap == null || TargetMap == Map.Internal) + TargetMap = Map.Trammel; - TargetLocation = FindLocation( TargetMap ); - MessageIndex = Utility.Random( MessageEntry.Entries.Length ); + TargetLocation = FindLocation(TargetMap); + MessageIndex = Utility.Random(MessageEntry.Entries.Length); - break; - } - } + break; + } + } - if ( version < 2 ) - m_Level = MessageInABottle.GetRandomLevel(); + if (version < 2) + m_Level = MessageInABottle.GetRandomLevel(); - if ( version < 3 ) - UpdateHue(); + if (version < 3) + UpdateHue(); - if ( version < 4 && TargetMap == Map.Tokuno ) - TargetMap = Map.Trammel; - } + if (version < 4 && TargetMap == Map.Tokuno) + TargetMap = Map.Trammel; + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - MessageEntry entry; + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + MessageEntry entry; - if ( MessageIndex >= 0 && MessageIndex < MessageEntry.Entries.Length ) - entry = MessageEntry.Entries[MessageIndex]; - else - entry = MessageEntry.Entries[MessageIndex = Utility.Random( MessageEntry.Entries.Length )]; + if (MessageIndex >= 0 && MessageIndex < MessageEntry.Entries.Length) + entry = MessageEntry.Entries[MessageIndex]; + else + entry = MessageEntry.Entries[MessageIndex = Utility.Random(MessageEntry.Entries.Length)]; - //from.CloseGump( typeof( MessageGump ) ); - from.SendGump( new MessageGump( entry, TargetMap, TargetLocation ) ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + //from.CloseGump( typeof( MessageGump ) ); + from.SendGump(new MessageGump(entry, TargetMap, TargetLocation)); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - private static int[] m_WaterTiles = { - 0x00A8, 0x00AB, - 0x0136, 0x0137 - }; + private static int[] m_WaterTiles = + { + 0x00A8, 0x00AB, + 0x0136, 0x0137 + }; - private static Rectangle2D[] m_BritRegions = { new Rectangle2D( 0, 0, 5120, 4096 ) }; - private static Rectangle2D[] m_IlshRegions = { new Rectangle2D( 1472, 272, 304, 240 ), new Rectangle2D( 1240, 1000, 312, 160 ) }; - private static Rectangle2D[] m_MalasRegions = { new Rectangle2D( 1376, 1520, 464, 280 ) }; + private static Rectangle2D[] m_BritRegions = { new Rectangle2D(0, 0, 5120, 4096) }; - public static Point3D FindLocation( Map map ) - { - if ( map == null || map == Map.Internal ) - return Point3D.Zero; + private static Rectangle2D[] m_IlshRegions = + { new Rectangle2D(1472, 272, 304, 240), new Rectangle2D(1240, 1000, 312, 160) }; - Rectangle2D[] regions; + private static Rectangle2D[] m_MalasRegions = { new Rectangle2D(1376, 1520, 464, 280) }; - if ( map == Map.Felucca || map == Map.Trammel ) - regions = m_BritRegions; - else if ( map == Map.Ilshenar ) - regions = m_IlshRegions; - else if ( map == Map.Malas ) - regions = m_MalasRegions; - else - regions = new[]{ new Rectangle2D( 0, 0, map.Width, map.Height ) }; + public static Point3D FindLocation(Map map) + { + if (map == null || map == Map.Internal) + return Point3D.Zero; - if ( regions.Length == 0 ) - return Point3D.Zero; + Rectangle2D[] regions; - for ( int i = 0; i < 50; ++i ) - { - Rectangle2D reg = regions[Utility.Random( regions.Length )]; - int x = Utility.Random( reg.X, reg.Width ); - int y = Utility.Random( reg.Y, reg.Height ); + if (map == Map.Felucca || map == Map.Trammel) + regions = m_BritRegions; + else if (map == Map.Ilshenar) + regions = m_IlshRegions; + else if (map == Map.Malas) + regions = m_MalasRegions; + else + regions = new[] { new Rectangle2D(0, 0, map.Width, map.Height) }; - if ( !ValidateDeepWater( map, x, y ) ) - continue; + if (regions.Length == 0) + return Point3D.Zero; - bool valid = true; + for (int i = 0; i < 50; ++i) + { + Rectangle2D reg = regions[Utility.Random(regions.Length)]; + int x = Utility.Random(reg.X, reg.Width); + int y = Utility.Random(reg.Y, reg.Height); - for ( int j = 1, offset = 5; valid && j <= 5; ++j, offset += 5 ) - { - if ( !ValidateDeepWater( map, x + offset, y + offset ) ) - valid = false; - else if ( !ValidateDeepWater( map, x + offset, y - offset ) ) - valid = false; - else if ( !ValidateDeepWater( map, x - offset, y + offset ) ) - valid = false; - else if ( !ValidateDeepWater( map, x - offset, y - offset ) ) - valid = false; - } + if (!ValidateDeepWater(map, x, y)) + continue; - if ( valid ) - return new Point3D( x, y, 0 ); - } + bool valid = true; - return Point3D.Zero; - } + for (int j = 1, offset = 5; valid && j <= 5; ++j, offset += 5) + if (!ValidateDeepWater(map, x + offset, y + offset)) + valid = false; + else if (!ValidateDeepWater(map, x + offset, y - offset)) + valid = false; + else if (!ValidateDeepWater(map, x - offset, y + offset)) + valid = false; + else if (!ValidateDeepWater(map, x - offset, y - offset)) + valid = false; - private static bool ValidateDeepWater( Map map, int x, int y ) - { - int tileID = map.Tiles.GetLandTile( x, y ).ID; - bool water = false; + if (valid) + return new Point3D(x, y, 0); + } - for ( int i = 0; !water && i < m_WaterTiles.Length; i += 2 ) - water = ( tileID >= m_WaterTiles[i] && tileID <= m_WaterTiles[i + 1] ); + return Point3D.Zero; + } - return water; - } + private static bool ValidateDeepWater(Map map, int x, int y) + { + int tileID = map.Tiles.GetLandTile(x, y).ID; + bool water = false; + + for (int i = 0; !water && i < m_WaterTiles.Length; i += 2) + water = tileID >= m_WaterTiles[i] && tileID <= m_WaterTiles[i + 1]; + + return water; + } #if false private class MessageGump : Gump @@ -238,7 +240,8 @@ namespace Server.Items string fmt; if ( Sextant.Format( loc, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - fmt = String.Format( "{0}°{1}'{2},{3}°{4}'{5}", yLat, yMins, ySouth ? "S" : "N", xLong, xMins, xEast ? "E" : "W" ); + fmt = + String.Format( "{0}°{1}'{2},{3}°{4}'{5}", yLat, yMins, ySouth ? "S" : "N", xLong, xMins, xEast ? "E" : "W" ); else fmt = "?????"; @@ -248,68 +251,81 @@ namespace Server.Items } } #else - private class MessageGump : Gump - { - public MessageGump( MessageEntry entry, Map map, Point3D loc ) : base( 150, 50 ) - { - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - string fmt; + private class MessageGump : Gump + { + public MessageGump(MessageEntry entry, Map map, Point3D loc) : base(150, 50) + { + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + string fmt; - if ( Sextant.Format( loc, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - fmt = $"{yLat}°{yMins}'{(ySouth ? "S" : "N")},{xLong}°{xMins}'{(xEast ? "E" : "W")}"; - else - fmt = "?????"; + if (Sextant.Format(loc, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth)) + fmt = $"{yLat}°{yMins}'{(ySouth ? "S" : "N")},{xLong}°{xMins}'{(xEast ? "E" : "W")}"; + else + fmt = "?????"; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 40, 350, 300, 2520 ); + AddBackground(0, 40, 350, 300, 2520); - AddHtmlLocalized( 30, 80, 285, 160, 1018326, true, true ); /* This is a message hastily scribbled by a passenger aboard a sinking ship. + AddHtmlLocalized(30, 80, 285, 160, 1018326, true, + true); /* This is a message hastily scribbled by a passenger aboard a sinking ship. * While it is probably too late to save the passengers and crew, * perhaps some treasure went down with the ship! * The message gives the ship's last known sextant co-ordinates. */ - AddHtml( 35, 240, 230, 20, fmt, false, false ); + AddHtml(35, 240, 230, 20, fmt, false, false); - AddButton( 35, 265, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 70, 265, 100, 20, 1011036, false, false ); // OKAY - } - } + AddButton(35, 265, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(70, 265, 100, 20, 1011036, false, false); // OKAY + } + } #endif - private class MessageEntry - { - public int Width { get; } + private class MessageEntry + { + public MessageEntry(int width, int height, string message) + { + Width = width; + Height = height; + Message = message; + } - public int Height { get; } + public int Width{ get; } - public string Message { get; } + public int Height{ get; } - public MessageEntry( int width, int height, string message ) - { - Width = width; - Height = height; - Message = message; - } + public string Message{ get; } - public static MessageEntry[] Entries { get; } = - { - new MessageEntry( 280, 180, "...Ar! {0} and a fair wind! No chance... storms, though--ar! Is that a sea serp...

uh oh." ), - new MessageEntry( 280, 215, "...been inside this whale for three days now. I've run out of food I can pick out of his teeth. I took a sextant reading through the blowhole: {0}. I'll never see my treasure again..." ), - new MessageEntry( 280, 285, "...grand adventure! Captain Quacklebush had me swab down the decks daily...
...pirates came, I was in the rigging practicing with my sextant. {0} if I am not mistaken...
....scuttled the ship, and our precious cargo went with her and the screaming pirates, down to the bottom of the sea..." ), - new MessageEntry( 280, 180, "Help! Ship going dow...n heavy storms...precious cargo...st reach dest...current coordinates {0}...ve any survivors... ease!" ), - new MessageEntry( 280, 215, "...know that the wreck is near {0} but have not found it. Could the message passed down in my family for generations be wrong? No... I swear on the soul of my grandfather, I will find..." ), - new MessageEntry( 280, 195, "...never expected an iceberg...silly woman on bow crushed instantly...send help to {0}...ey'll never forget the tragedy of the sinking of the Miniscule..." ), - new MessageEntry( 280, 265, "...nobody knew I was a girl. They just assumed I was another sailor...then we met the undine. {0}. It was demanded sacrifice...I was youngset, they figured...
...grabbed the captain's treasure, screamed, 'It'll go down with me!'
...they took me up on it." ), - new MessageEntry( 280, 230, "...so I threw the treasure overboard, before the curse could get me too. But I was too late. Now I am doomed to wander these seas, a ghost forever. Join me: seek ye at {0} if thou wishest my company..." ), - new MessageEntry( 280, 285, "...then the ship exploded. A dragon swooped by. The slime swallowed Bertie whole--he screamed, it was amazing. The sky glowed orange. A sextant reading put us at {0}. Norma was chattering about sailing over the edge of the world. I looked at my hands and saw through them..." ), - new MessageEntry( 280, 285, "...trapped on a deserted island, with a magic fountain supplying wood, fresh water springs, gorgeous scenery, and my lovely young wife. I know the ship with all our life's earnings sank at {0} but I don't know what our coordinates are... someone has GOT to rescue me before Sunday's finals game or I'll go mad..." ), - new MessageEntry( 280, 160, "WANTED: divers exp...d in shipwre...overy. Must have own vess...pply at {0}
...good benefits, flexible hours..." ), - new MessageEntry( 280, 250, "...was a cad and a boor, no matter what momma s...rew him overboard! Oh, Anna, 'twas so exciting!
Unfort...y he grabbe...est, and all his riches went with him!
...sked the captain, and he says we're at {0}
...so maybe..." ) - }; - } - } -} + public static MessageEntry[] Entries{ get; } = + { + new MessageEntry(280, 180, + "...Ar! {0} and a fair wind! No chance... storms, though--ar! Is that a sea serp...

uh oh."), + new MessageEntry(280, 215, + "...been inside this whale for three days now. I've run out of food I can pick out of his teeth. I took a sextant reading through the blowhole: {0}. I'll never see my treasure again..."), + new MessageEntry(280, 285, + "...grand adventure! Captain Quacklebush had me swab down the decks daily...
...pirates came, I was in the rigging practicing with my sextant. {0} if I am not mistaken...
....scuttled the ship, and our precious cargo went with her and the screaming pirates, down to the bottom of the sea..."), + new MessageEntry(280, 180, + "Help! Ship going dow...n heavy storms...precious cargo...st reach dest...current coordinates {0}...ve any survivors... ease!"), + new MessageEntry(280, 215, + "...know that the wreck is near {0} but have not found it. Could the message passed down in my family for generations be wrong? No... I swear on the soul of my grandfather, I will find..."), + new MessageEntry(280, 195, + "...never expected an iceberg...silly woman on bow crushed instantly...send help to {0}...ey'll never forget the tragedy of the sinking of the Miniscule..."), + new MessageEntry(280, 265, + "...nobody knew I was a girl. They just assumed I was another sailor...then we met the undine. {0}. It was demanded sacrifice...I was youngset, they figured...
...grabbed the captain's treasure, screamed, 'It'll go down with me!'
...they took me up on it."), + new MessageEntry(280, 230, + "...so I threw the treasure overboard, before the curse could get me too. But I was too late. Now I am doomed to wander these seas, a ghost forever. Join me: seek ye at {0} if thou wishest my company..."), + new MessageEntry(280, 285, + "...then the ship exploded. A dragon swooped by. The slime swallowed Bertie whole--he screamed, it was amazing. The sky glowed orange. A sextant reading put us at {0}. Norma was chattering about sailing over the edge of the world. I looked at my hands and saw through them..."), + new MessageEntry(280, 285, + "...trapped on a deserted island, with a magic fountain supplying wood, fresh water springs, gorgeous scenery, and my lovely young wife. I know the ship with all our life's earnings sank at {0} but I don't know what our coordinates are... someone has GOT to rescue me before Sunday's finals game or I'll go mad..."), + new MessageEntry(280, 160, + "WANTED: divers exp...d in shipwre...overy. Must have own vess...pply at {0}
...good benefits, flexible hours..."), + new MessageEntry(280, 250, + "...was a cad and a boor, no matter what momma s...rew him overboard! Oh, Anna, 'twas so exciting!
Unfort...y he grabbe...est, and all his riches went with him!
...sked the captain, and he says we're at {0}
...so maybe...") + }; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Fishing/Misc/Sextant.cs b/Scripts/Items/Skill Items/Fishing/Misc/Sextant.cs index c227b8fe9..ce0fd986b 100644 --- a/Scripts/Items/Skill Items/Fishing/Misc/Sextant.cs +++ b/Scripts/Items/Skill Items/Fishing/Misc/Sextant.cs @@ -1,159 +1,166 @@ -using System; using Server.Network; namespace Server.Items { - public class Sextant : Item - { - [Constructible] - public Sextant() : base( 0x1058 ) - { - Weight = 2.0; - } + public class Sextant : Item + { + [Constructible] + public Sextant() : base(0x1058) + { + Weight = 2.0; + } - public Sextant( Serial serial ) : base( serial ) - { - } + public Sextant(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; + public override void OnDoubleClick(Mobile from) + { + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; - if ( Format( from.Location, from.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - { - string location = $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; - from.LocalOverheadMessage( MessageType.Regular, from.SpeechHue, false, location ); - } - } + if (Format(from.Location, from.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth)) + { + string location = $"{yLat}� {yMins}'{(ySouth ? "S" : "N")}, {xLong}� {xMins}'{(xEast ? "E" : "W")}"; + from.LocalOverheadMessage(MessageType.Regular, from.SpeechHue, false, location); + } + } - public static bool ComputeMapDetails( Map map, int x, int y, out int xCenter, out int yCenter, out int xWidth, out int yHeight ) - { - xWidth = 5120; yHeight = 4096; + public static bool ComputeMapDetails(Map map, int x, int y, out int xCenter, out int yCenter, out int xWidth, + out int yHeight) + { + xWidth = 5120; + yHeight = 4096; - if ( map == Map.Trammel || map == Map.Felucca ) - { - if ( x >= 0 && y >= 0 && x < 5120 && y < 4096 ) - { - xCenter = 1323; yCenter = 1624; - } - else if ( x >= 5120 && y >= 2304 && x < 6144 && y < 4096 ) - { - xCenter = 5936; yCenter = 3112; - } - else - { - xCenter = 0; yCenter = 0; - return false; - } - } - else if ( x >= 0 && y >= 0 && x < map.Width && y < map.Height ) - { - xCenter = 1323; yCenter = 1624; - } - else - { - xCenter = 0; yCenter = 0; - return false; - } + if (map == Map.Trammel || map == Map.Felucca) + { + if (x >= 0 && y >= 0 && x < 5120 && y < 4096) + { + xCenter = 1323; + yCenter = 1624; + } + else if (x >= 5120 && y >= 2304 && x < 6144 && y < 4096) + { + xCenter = 5936; + yCenter = 3112; + } + else + { + xCenter = 0; + yCenter = 0; + return false; + } + } + else if (x >= 0 && y >= 0 && x < map.Width && y < map.Height) + { + xCenter = 1323; + yCenter = 1624; + } + else + { + xCenter = 0; + yCenter = 0; + return false; + } - return true; - } + return true; + } - public static Point3D ReverseLookup( Map map, int xLong, int yLat, int xMins, int yMins, bool xEast, bool ySouth ) - { - if ( map == null || map == Map.Internal ) - return Point3D.Zero; + public static Point3D ReverseLookup(Map map, int xLong, int yLat, int xMins, int yMins, bool xEast, bool ySouth) + { + if (map == null || map == Map.Internal) + return Point3D.Zero; - int xCenter, yCenter; - int xWidth, yHeight; + int xCenter, yCenter; + int xWidth, yHeight; - if ( !ComputeMapDetails( map, 0, 0, out xCenter, out yCenter, out xWidth, out yHeight ) ) - return Point3D.Zero; + if (!ComputeMapDetails(map, 0, 0, out xCenter, out yCenter, out xWidth, out yHeight)) + return Point3D.Zero; - double absLong = xLong + ((double)xMins / 60); - double absLat = yLat + ((double)yMins / 60); + double absLong = xLong + (double)xMins / 60; + double absLat = yLat + (double)yMins / 60; - if ( !xEast ) - absLong = 360.0 - absLong; + if (!xEast) + absLong = 360.0 - absLong; - if ( !ySouth ) - absLat = 360.0 - absLat; + if (!ySouth) + absLat = 360.0 - absLat; - int x, y, z; + int x, y, z; - x = xCenter + (int)((absLong * xWidth) / 360); - y = yCenter + (int)((absLat * yHeight) / 360); + x = xCenter + (int)(absLong * xWidth / 360); + y = yCenter + (int)(absLat * yHeight / 360); - if ( x < 0 ) - x += xWidth; - else if ( x >= xWidth ) - x -= xWidth; + if (x < 0) + x += xWidth; + else if (x >= xWidth) + x -= xWidth; - if ( y < 0 ) - y += yHeight; - else if ( y >= yHeight ) - y -= yHeight; + if (y < 0) + y += yHeight; + else if (y >= yHeight) + y -= yHeight; - z = map.GetAverageZ( x, y ); + z = map.GetAverageZ(x, y); - return new Point3D( x, y, z ); - } + return new Point3D(x, y, z); + } - public static bool Format( Point3D p, Map map, ref int xLong, ref int yLat, ref int xMins, ref int yMins, ref bool xEast, ref bool ySouth ) - { - if ( map == null || map == Map.Internal ) - return false; + public static bool Format(Point3D p, Map map, ref int xLong, ref int yLat, ref int xMins, ref int yMins, + ref bool xEast, ref bool ySouth) + { + if (map == null || map == Map.Internal) + return false; - int x = p.X, y = p.Y; - int xCenter, yCenter; - int xWidth, yHeight; + int x = p.X, y = p.Y; + int xCenter, yCenter; + int xWidth, yHeight; - if ( !ComputeMapDetails( map, x, y, out xCenter, out yCenter, out xWidth, out yHeight ) ) - return false; + if (!ComputeMapDetails(map, x, y, out xCenter, out yCenter, out xWidth, out yHeight)) + return false; - double absLong = (double)((x - xCenter) * 360) / xWidth; - double absLat = (double)((y - yCenter) * 360) / yHeight; + double absLong = (double)((x - xCenter) * 360) / xWidth; + double absLat = (double)((y - yCenter) * 360) / yHeight; - if ( absLong > 180.0 ) - absLong = -180.0 + (absLong % 180.0); + if (absLong > 180.0) + absLong = -180.0 + absLong % 180.0; - if ( absLat > 180.0 ) - absLat = -180.0 + (absLat % 180.0); + if (absLat > 180.0) + absLat = -180.0 + absLat % 180.0; - bool east = ( absLong >= 0 ), south = ( absLat >= 0 ); + bool east = absLong >= 0, south = absLat >= 0; - if ( absLong < 0.0 ) - absLong = -absLong; + if (absLong < 0.0) + absLong = -absLong; - if ( absLat < 0.0 ) - absLat = -absLat; + if (absLat < 0.0) + absLat = -absLat; - xLong = (int)absLong; - yLat = (int)absLat; + xLong = (int)absLong; + yLat = (int)absLat; - xMins = (int)((absLong % 1.0) * 60); - yMins = (int)((absLat % 1.0) * 60); + xMins = (int)(absLong % 1.0 * 60); + yMins = (int)(absLat % 1.0 * 60); - xEast = east; - ySouth = south; + xEast = east; + ySouth = south; - return true; - } - } + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Fishing/Misc/ShipwreckedItem.cs b/Scripts/Items/Skill Items/Fishing/Misc/ShipwreckedItem.cs index c8aa74e78..d219748d5 100644 --- a/Scripts/Items/Skill Items/Fishing/Misc/ShipwreckedItem.cs +++ b/Scripts/Items/Skill Items/Fishing/Misc/ShipwreckedItem.cs @@ -1,78 +1,74 @@ -using System; - namespace Server.Items { - public interface IShipwreckedItem - { - bool IsShipwreckedItem { get; set; } - } + public interface IShipwreckedItem + { + bool IsShipwreckedItem{ get; set; } + } - public class ShipwreckedItem : Item, IDyable, IShipwreckedItem - { - public ShipwreckedItem( int itemID ) : base( itemID ) - { - int weight = ItemData.Weight; + public class ShipwreckedItem : Item, IDyable, IShipwreckedItem + { + public ShipwreckedItem(int itemID) : base(itemID) + { + int weight = ItemData.Weight; - if ( weight >= 255 ) - weight = 1; + if (weight >= 255) + weight = 1; - Weight = weight; - } + Weight = weight; + } - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, 1050039, $"#{LabelNumber}\t#1041645"); - } + public ShipwreckedItem(Serial serial) : base(serial) + { + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - list.Add( 1041645 ); // recovered from a shipwreck - } + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - public ShipwreckedItem( Serial serial ) : base( serial ) - { - } + if (ItemID >= 0x13A4 && ItemID <= 0x13AE) + { + Hue = sender.DyedHue; + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + from.SendLocalizedMessage(sender.FailMessage); + return false; + } - writer.Write( (int) 0 ); // version - } + #region IShipwreckedItem Members - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public bool IsShipwreckedItem + { + get => true; + set { } + } - int version = reader.ReadInt(); - } + #endregion - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + public override void OnSingleClick(Mobile from) + { + LabelTo(from, 1050039, $"#{LabelNumber}\t#1041645"); + } - if ( ItemID >= 0x13A4 && ItemID <= 0x13AE ) - { - Hue = sender.DyedHue; - return true; - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + list.Add(1041645); // recovered from a shipwreck + } - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - #region IShipwreckedItem Members + writer.Write(0); // version + } - public bool IsShipwreckedItem - { - get => true; - set - { - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Fishing/Misc/SpecialFishingNet.cs b/Scripts/Items/Skill Items/Fishing/Misc/SpecialFishingNet.cs index 8635e6373..4585897ea 100644 --- a/Scripts/Items/Skill Items/Fishing/Misc/SpecialFishingNet.cs +++ b/Scripts/Items/Skill Items/Fishing/Misc/SpecialFishingNet.cs @@ -6,392 +6,425 @@ using Server.Targeting; namespace Server.Items { - public class SpecialFishingNet : Item - { - public override int LabelNumber => 1041079; // a special fishing net - - [CommandProperty( AccessLevel.GameMaster )] - public bool InUse { get; set; } - - [Constructible] - public SpecialFishingNet() : base( 0x0DCA ) - { - Weight = 1.0; - - if ( 0.01 > Utility.RandomDouble() ) - Hue = Utility.RandomList( m_Hues ); - else - Hue = 0x8A0; - } - - private static int[] m_Hues = { - 0x09B, - 0x0CD, - 0x0D3, - 0x14D, - 0x1DD, - 0x1E9, - 0x1F4, - 0x373, - 0x451, - 0x47F, - 0x489, - 0x492, - 0x4B5, - 0x8AA - }; - - public SpecialFishingNet( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - AddNetProperties( list ); - } - - protected virtual void AddNetProperties( ObjectPropertyList list ) - { - // as if the name wasn't enough.. - list.Add( 1017410 ); // Special Fishing Net - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( InUse ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - InUse = reader.ReadBool(); - - if ( InUse ) - Delete(); - - break; - } - } - - Stackable = false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( InUse ) - { - from.SendLocalizedMessage( 1010483 ); // Someone is already using that net! - } - else if ( IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1010484 ); // Where do you wish to use the net? - from.BeginTarget( -1, true, TargetFlags.None, OnTarget ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - - public virtual bool RequireDeepWater => true; - - public void OnTarget( Mobile from, object obj ) - { - if ( Deleted || InUse ) - return; - - if ( !(obj is IPoint3D p3D) ) - return; - - Map map = from.Map; - - if ( map == null || map == Map.Internal ) - return; - - int x = p3D.X, y = p3D.Y, z = map.GetAverageZ( x, y ); // OSI just takes the targeted Z - - if ( !from.InRange( p3D, 6 ) ) - { - from.SendLocalizedMessage( 500976 ); // You need to be closer to the water to fish! - } - else if ( !from.InLOS( obj ) ) - { - from.SendLocalizedMessage( 500979 ); // You cannot see that location. - } - else if ( RequireDeepWater ? FullValidation( map, x, y ) : ( ValidateDeepWater( map, x, y ) || ValidateUndeepWater( map, obj, ref z ) ) ) - { - Point3D p = new Point3D( x, y, z ); - - if ( GetType() == typeof( SpecialFishingNet ) ) - { - for ( int i = 1; i < Amount; ++i ) // these were stackable before, doh - from.AddToBackpack( new SpecialFishingNet() ); - } - - InUse = true; - Movable = false; - MoveToWorld( p, map ); - - SpellHelper.Turn( from, p ); - from.Animate( 12, 5, 1, true, false, 0 ); - - Effects.SendLocationEffect( p, map, 0x352D, 16, 4 ); - Effects.PlaySound( p, map, 0x364 ); - - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.25 ), 14, new TimerStateCallback( DoEffect ), new object[]{ p, 0, from } ); - - from.SendLocalizedMessage( RequireDeepWater ? 1010487 : 1074492 ); // You plunge the net into the sea... / You plunge the net into the water... - } - else - { - from.SendLocalizedMessage( RequireDeepWater ? 1010485 : 1074491 ); // You can only use this net in deep water! / You can only use this net in water! - } - } - - private void DoEffect( object state ) - { - if ( Deleted ) - return; - - object[] states = (object[])state; - - Point3D p = (Point3D)states[0]; - int index = (int)states[1]; - Mobile from = (Mobile)states[2]; - - states[1] = ++index; - - if ( index == 1 ) - { - Effects.SendLocationEffect( p, Map, 0x352D, 16, 4 ); - Effects.PlaySound( p, Map, 0x364 ); - } - else if ( index <= 7 || index == 14 ) - { - if ( RequireDeepWater ) - { - for ( int i = 0; i < 3; ++i ) - { - int x, y; - - switch ( Utility.Random( 8 ) ) - { - default: - case 0: x = -1; y = -1; break; - case 1: x = -1; y = 0; break; - case 2: x = -1; y = +1; break; - case 3: x = 0; y = -1; break; - case 4: x = 0; y = +1; break; - case 5: x = +1; y = -1; break; - case 6: x = +1; y = 0; break; - case 7: x = +1; y = +1; break; - } - - Effects.SendLocationEffect( new Point3D( p.X + x, p.Y + y, p.Z ), Map, 0x352D, 16, 4 ); - } - } - else - { - Effects.SendLocationEffect( p, Map, 0x352D, 16, 4 ); - } - - if ( Utility.RandomBool() ) - Effects.PlaySound( p, Map, 0x364 ); - - if ( index == 14 ) - FinishEffect( p, Map, from ); - else - Z -= 1; - } - } - - protected virtual int GetSpawnCount() - { - int count = Utility.RandomMinMax( 1, 3 ); - - if ( Hue != 0x8A0 ) - count += Utility.RandomMinMax( 1, 2 ); - - return count; - } - - protected void Spawn( Point3D p, Map map, BaseCreature spawn ) - { - if ( map == null ) - { - spawn.Delete(); - return; - } - - int x = p.X, y = p.Y; - - for ( int j = 0; j < 20; ++j ) - { - int tx = p.X - 2 + Utility.Random( 5 ); - int ty = p.Y - 2 + Utility.Random( 5 ); - - LandTile t = map.Tiles.GetLandTile( tx, ty ); - - if ( t.Z == p.Z && ( (t.ID >= 0xA8 && t.ID <= 0xAB) || (t.ID >= 0x136 && t.ID <= 0x137) ) && !SpellHelper.CheckMulti( new Point3D( tx, ty, p.Z ), map ) ) - { - x = tx; - y = ty; - break; - } - } - - spawn.MoveToWorld( new Point3D( x, y, p.Z ), map ); - - if ( spawn is Kraken && 0.2 > Utility.RandomDouble() ) - spawn.PackItem( new MessageInABottle( map == Map.Felucca ? Map.Felucca : Map.Trammel ) ); - } - - protected virtual void FinishEffect( Point3D p, Map map, Mobile from ) - { - from.RevealingAction(); - - int count = GetSpawnCount(); - - for ( int i = 0; map != null && i < count; ++i ) - { - BaseCreature spawn; - - switch ( Utility.Random( 4 ) ) - { - default: - case 0: spawn = new SeaSerpent(); break; - case 1: spawn = new DeepSeaSerpent(); break; - case 2: spawn = new WaterElemental(); break; - case 3: spawn = new Kraken(); break; - } - - Spawn( p, map, spawn ); - - spawn.Combatant = from; - } - - Delete(); - } - - public static bool FullValidation( Map map, int x, int y ) - { - bool valid = ValidateDeepWater( map, x, y ); - - for ( int j = 1, offset = 5; valid && j <= 5; ++j, offset += 5 ) - { - if ( !ValidateDeepWater( map, x + offset, y + offset ) ) - valid = false; - else if ( !ValidateDeepWater( map, x + offset, y - offset ) ) - valid = false; - else if ( !ValidateDeepWater( map, x - offset, y + offset ) ) - valid = false; - else if ( !ValidateDeepWater( map, x - offset, y - offset ) ) - valid = false; - } - - return valid; - } - - private static int[] m_WaterTiles = { - 0x00A8, 0x00AB, - 0x0136, 0x0137 - }; - - private static bool ValidateDeepWater( Map map, int x, int y ) - { - int tileID = map.Tiles.GetLandTile( x, y ).ID; - bool water = false; - - for ( int i = 0; !water && i < m_WaterTiles.Length; i += 2 ) - water = ( tileID >= m_WaterTiles[i] && tileID <= m_WaterTiles[i + 1] ); - - return water; - } - - private static int[] m_UndeepWaterTiles = { - 0x1797, 0x179C - }; - - private static bool ValidateUndeepWater( Map map, object obj, ref int z ) - { - if ( !( obj is StaticTarget ) ) - return false; - - StaticTarget target = (StaticTarget)obj; - - if ( BaseHouse.FindHouseAt( target.Location, map, 0 ) != null ) - return false; - - int itemID = target.ItemID; - - for ( int i = 0; i < m_UndeepWaterTiles.Length; i += 2 ) - { - if ( itemID >= m_UndeepWaterTiles[i] && itemID <= m_UndeepWaterTiles[i + 1] ) - { - z = target.Z; - return true; - } - } - - return false; - } - } - - public class FabledFishingNet : SpecialFishingNet - { - public override int LabelNumber => 1063451; // a fabled fishing net - - [Constructible] - public FabledFishingNet() - { - Hue = 0x481; - } - - protected override void AddNetProperties( ObjectPropertyList list ) - { - } - - protected override int GetSpawnCount() - { - return base.GetSpawnCount() + 4; - } - - protected override void FinishEffect( Point3D p, Map map, Mobile from ) - { - Spawn( p, map, new Leviathan( from ) ); - - base.FinishEffect( p, map, from ); - } - - public FabledFishingNet( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public class SpecialFishingNet : Item + { + private static int[] m_Hues = + { + 0x09B, + 0x0CD, + 0x0D3, + 0x14D, + 0x1DD, + 0x1E9, + 0x1F4, + 0x373, + 0x451, + 0x47F, + 0x489, + 0x492, + 0x4B5, + 0x8AA + }; + + private static int[] m_WaterTiles = + { + 0x00A8, 0x00AB, + 0x0136, 0x0137 + }; + + private static int[] m_UndeepWaterTiles = + { + 0x1797, 0x179C + }; + + [Constructible] + public SpecialFishingNet() : base(0x0DCA) + { + Weight = 1.0; + + if (0.01 > Utility.RandomDouble()) + Hue = Utility.RandomList(m_Hues); + else + Hue = 0x8A0; + } + + public SpecialFishingNet(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041079; // a special fishing net + + [CommandProperty(AccessLevel.GameMaster)] + public bool InUse{ get; set; } + + public virtual bool RequireDeepWater => true; + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + AddNetProperties(list); + } + + protected virtual void AddNetProperties(ObjectPropertyList list) + { + // as if the name wasn't enough.. + list.Add(1017410); // Special Fishing Net + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(InUse); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + InUse = reader.ReadBool(); + + if (InUse) + Delete(); + + break; + } + } + + Stackable = false; + } + + public override void OnDoubleClick(Mobile from) + { + if (InUse) + { + from.SendLocalizedMessage(1010483); // Someone is already using that net! + } + else if (IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1010484); // Where do you wish to use the net? + from.BeginTarget(-1, true, TargetFlags.None, OnTarget); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + + public void OnTarget(Mobile from, object obj) + { + if (Deleted || InUse) + return; + + if (!(obj is IPoint3D p3D)) + return; + + Map map = from.Map; + + if (map == null || map == Map.Internal) + return; + + int x = p3D.X, y = p3D.Y, z = map.GetAverageZ(x, y); // OSI just takes the targeted Z + + if (!from.InRange(p3D, 6)) + { + from.SendLocalizedMessage(500976); // You need to be closer to the water to fish! + } + else if (!from.InLOS(obj)) + { + from.SendLocalizedMessage(500979); // You cannot see that location. + } + else if (RequireDeepWater + ? FullValidation(map, x, y) + : ValidateDeepWater(map, x, y) || ValidateUndeepWater(map, obj, ref z)) + { + Point3D p = new Point3D(x, y, z); + + if (GetType() == typeof(SpecialFishingNet)) + for (int i = 1; i < Amount; ++i) // these were stackable before, doh + from.AddToBackpack(new SpecialFishingNet()); + + InUse = true; + Movable = false; + MoveToWorld(p, map); + + SpellHelper.Turn(from, p); + from.Animate(12, 5, 1, true, false, 0); + + Effects.SendLocationEffect(p, map, 0x352D, 16, 4); + Effects.PlaySound(p, map, 0x364); + + Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.25), 14, new TimerStateCallback(DoEffect), + new object[] { p, 0, from }); + + from.SendLocalizedMessage(RequireDeepWater + ? 1010487 + : 1074492); // You plunge the net into the sea... / You plunge the net into the water... + } + else + { + from.SendLocalizedMessage(RequireDeepWater + ? 1010485 + : 1074491); // You can only use this net in deep water! / You can only use this net in water! + } + } + + private void DoEffect(object state) + { + if (Deleted) + return; + + object[] states = (object[])state; + + Point3D p = (Point3D)states[0]; + int index = (int)states[1]; + Mobile from = (Mobile)states[2]; + + states[1] = ++index; + + if (index == 1) + { + Effects.SendLocationEffect(p, Map, 0x352D, 16, 4); + Effects.PlaySound(p, Map, 0x364); + } + else if (index <= 7 || index == 14) + { + if (RequireDeepWater) + for (int i = 0; i < 3; ++i) + { + int x, y; + + switch (Utility.Random(8)) + { + default: + case 0: + x = -1; + y = -1; + break; + case 1: + x = -1; + y = 0; + break; + case 2: + x = -1; + y = +1; + break; + case 3: + x = 0; + y = -1; + break; + case 4: + x = 0; + y = +1; + break; + case 5: + x = +1; + y = -1; + break; + case 6: + x = +1; + y = 0; + break; + case 7: + x = +1; + y = +1; + break; + } + + Effects.SendLocationEffect(new Point3D(p.X + x, p.Y + y, p.Z), Map, 0x352D, 16, 4); + } + else + Effects.SendLocationEffect(p, Map, 0x352D, 16, 4); + + if (Utility.RandomBool()) + Effects.PlaySound(p, Map, 0x364); + + if (index == 14) + FinishEffect(p, Map, from); + else + Z -= 1; + } + } + + protected virtual int GetSpawnCount() + { + int count = Utility.RandomMinMax(1, 3); + + if (Hue != 0x8A0) + count += Utility.RandomMinMax(1, 2); + + return count; + } + + protected void Spawn(Point3D p, Map map, BaseCreature spawn) + { + if (map == null) + { + spawn.Delete(); + return; + } + + int x = p.X, y = p.Y; + + for (int j = 0; j < 20; ++j) + { + int tx = p.X - 2 + Utility.Random(5); + int ty = p.Y - 2 + Utility.Random(5); + + LandTile t = map.Tiles.GetLandTile(tx, ty); + + if (t.Z == p.Z && (t.ID >= 0xA8 && t.ID <= 0xAB || t.ID >= 0x136 && t.ID <= 0x137) && + !SpellHelper.CheckMulti(new Point3D(tx, ty, p.Z), map)) + { + x = tx; + y = ty; + break; + } + } + + spawn.MoveToWorld(new Point3D(x, y, p.Z), map); + + if (spawn is Kraken && 0.2 > Utility.RandomDouble()) + spawn.PackItem(new MessageInABottle(map == Map.Felucca ? Map.Felucca : Map.Trammel)); + } + + protected virtual void FinishEffect(Point3D p, Map map, Mobile from) + { + from.RevealingAction(); + + int count = GetSpawnCount(); + + for (int i = 0; map != null && i < count; ++i) + { + BaseCreature spawn; + + switch (Utility.Random(4)) + { + default: + case 0: + spawn = new SeaSerpent(); + break; + case 1: + spawn = new DeepSeaSerpent(); + break; + case 2: + spawn = new WaterElemental(); + break; + case 3: + spawn = new Kraken(); + break; + } + + Spawn(p, map, spawn); + + spawn.Combatant = from; + } + + Delete(); + } + + public static bool FullValidation(Map map, int x, int y) + { + bool valid = ValidateDeepWater(map, x, y); + + for (int j = 1, offset = 5; valid && j <= 5; ++j, offset += 5) + if (!ValidateDeepWater(map, x + offset, y + offset)) + valid = false; + else if (!ValidateDeepWater(map, x + offset, y - offset)) + valid = false; + else if (!ValidateDeepWater(map, x - offset, y + offset)) + valid = false; + else if (!ValidateDeepWater(map, x - offset, y - offset)) + valid = false; + + return valid; + } + + private static bool ValidateDeepWater(Map map, int x, int y) + { + int tileID = map.Tiles.GetLandTile(x, y).ID; + bool water = false; + + for (int i = 0; !water && i < m_WaterTiles.Length; i += 2) + water = tileID >= m_WaterTiles[i] && tileID <= m_WaterTiles[i + 1]; + + return water; + } + + private static bool ValidateUndeepWater(Map map, object obj, ref int z) + { + if (!(obj is StaticTarget)) + return false; + + StaticTarget target = (StaticTarget)obj; + + if (BaseHouse.FindHouseAt(target.Location, map, 0) != null) + return false; + + int itemID = target.ItemID; + + for (int i = 0; i < m_UndeepWaterTiles.Length; i += 2) + if (itemID >= m_UndeepWaterTiles[i] && itemID <= m_UndeepWaterTiles[i + 1]) + { + z = target.Z; + return true; + } + + return false; + } + } + + public class FabledFishingNet : SpecialFishingNet + { + [Constructible] + public FabledFishingNet() + { + Hue = 0x481; + } + + public FabledFishingNet(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1063451; // a fabled fishing net + + protected override void AddNetProperties(ObjectPropertyList list) + { + } + + protected override int GetSpawnCount() + { + return base.GetSpawnCount() + 4; + } + + protected override void FinishEffect(Point3D p, Map map, Mobile from) + { + Spawn(p, map, new Leviathan(from)); + + base.FinishEffect(p, map, from); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Harvest Tools/BaseHarvestTool.cs b/Scripts/Items/Skill Items/Harvest Tools/BaseHarvestTool.cs index 66518c74b..fdd1e01ce 100644 --- a/Scripts/Items/Skill Items/Harvest Tools/BaseHarvestTool.cs +++ b/Scripts/Items/Skill Items/Harvest Tools/BaseHarvestTool.cs @@ -1,241 +1,260 @@ using System; using System.Collections.Generic; -using Server.Mobiles; -using Server.Network; +using Server.ContextMenus; using Server.Engines.Craft; using Server.Engines.Harvest; -using Server.ContextMenus; +using Server.Mobiles; +using Server.Network; namespace Server.Items { - public interface IUsesRemaining - { - int UsesRemaining{ get; set; } - bool ShowUsesRemaining{ get; set; } - } + public interface IUsesRemaining + { + int UsesRemaining{ get; set; } + bool ShowUsesRemaining{ get; set; } + } - public abstract class BaseHarvestTool : Item, IUsesRemaining, ICraftable - { - private Mobile m_Crafter; - private ToolQuality m_Quality; - private int m_UsesRemaining; + public abstract class BaseHarvestTool : Item, IUsesRemaining, ICraftable + { + private Mobile m_Crafter; + private ToolQuality m_Quality; + private int m_UsesRemaining; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } + public BaseHarvestTool(int itemID) : this(50, itemID) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public ToolQuality Quality - { - get => m_Quality; - set{ UnscaleUses(); m_Quality = value; InvalidateProperties(); ScaleUses(); } - } + public BaseHarvestTool(int usesRemaining, int itemID) : base(itemID) + { + m_UsesRemaining = usesRemaining; + m_Quality = ToolQuality.Regular; + } - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + public BaseHarvestTool(Serial serial) : base(serial) + { + } - public void ScaleUses() - { - m_UsesRemaining = (m_UsesRemaining * GetUsesScalar()) / 100; - InvalidateProperties(); - } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } - public void UnscaleUses() - { - m_UsesRemaining = (m_UsesRemaining * 100) / GetUsesScalar(); - } + [CommandProperty(AccessLevel.GameMaster)] + public ToolQuality Quality + { + get => m_Quality; + set + { + UnscaleUses(); + m_Quality = value; + InvalidateProperties(); + ScaleUses(); + } + } - public int GetUsesScalar() - { - if ( m_Quality == ToolQuality.Exceptional ) - return 200; + public abstract HarvestSystem HarvestSystem{ get; } - return 100; - } + #region ICraftable Members - public bool ShowUsesRemaining{ get => true; - set{} } + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Quality = (ToolQuality)quality; - public abstract HarvestSystem HarvestSystem{ get; } + if (makersMark) + Crafter = from; - public BaseHarvestTool( int itemID ) : this( 50, itemID ) - { - } + return quality; + } - public BaseHarvestTool( int usesRemaining, int itemID ) : base( itemID ) - { - m_UsesRemaining = usesRemaining; - m_Quality = ToolQuality.Regular; - } + #endregion - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - // Makers mark not displayed on OSI - //if ( m_Crafter != null ) - // list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + public bool ShowUsesRemaining + { + get => true; + set { } + } - if ( m_Quality == ToolQuality.Exceptional ) - list.Add( 1060636 ); // exceptional + public void ScaleUses() + { + m_UsesRemaining = m_UsesRemaining * GetUsesScalar() / 100; + InvalidateProperties(); + } - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ - } + public void UnscaleUses() + { + m_UsesRemaining = m_UsesRemaining * 100 / GetUsesScalar(); + } - public virtual void DisplayDurabilityTo( Mobile m ) - { - LabelToAffix( m, 1017323, AffixType.Append, ": " + m_UsesRemaining.ToString() ); // Durability - } + public int GetUsesScalar() + { + if (m_Quality == ToolQuality.Exceptional) + return 200; - public override void OnSingleClick( Mobile from ) - { - DisplayDurabilityTo( from ); + return 100; + } - base.OnSingleClick( from ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) || Parent == from ) - HarvestSystem.BeginHarvesting( from, this ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + // Makers mark not displayed on OSI + //if ( m_Crafter != null ) + // list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (m_Quality == ToolQuality.Exceptional) + list.Add(1060636); // exceptional - AddContextMenuEntries( from, this, list, HarvestSystem ); - } + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ + } - public static void AddContextMenuEntries( Mobile from, Item item, List list, HarvestSystem system ) - { - if ( system != Mining.System ) - return; + public virtual void DisplayDurabilityTo(Mobile m) + { + LabelToAffix(m, 1017323, AffixType.Append, ": " + m_UsesRemaining); // Durability + } - if ( !item.IsChildOf( from.Backpack ) && item.Parent != from ) - return; + public override void OnSingleClick(Mobile from) + { + DisplayDurabilityTo(from); - if ( !(from is PlayerMobile pm) ) - return; + base.OnSingleClick(from); + } - ContextMenuEntry miningEntry = new ContextMenuEntry( pm.ToggleMiningStone ? 6179 : 6178 ); - miningEntry.Color = 0x421F; - list.Add( miningEntry ); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack) || Parent == from) + HarvestSystem.BeginHarvesting(from, this); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } - list.Add( new ToggleMiningStoneEntry( pm, false, 6176 ) ); - list.Add( new ToggleMiningStoneEntry( pm, true, 6177 ) ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - private class ToggleMiningStoneEntry : ContextMenuEntry - { - private PlayerMobile m_Mobile; - private bool m_Value; + AddContextMenuEntries(from, this, list, HarvestSystem); + } - public ToggleMiningStoneEntry( PlayerMobile mobile, bool value, int number ) : base( number ) - { - m_Mobile = mobile; - m_Value = value; + public static void AddContextMenuEntries(Mobile from, Item item, List list, HarvestSystem system) + { + if (system != Mining.System) + return; - bool stoneMining = ( mobile.StoneMining && mobile.Skills[SkillName.Mining].Base >= 100.0 ); + if (!item.IsChildOf(from.Backpack) && item.Parent != from) + return; - if ( mobile.ToggleMiningStone == value || ( value && !stoneMining ) ) - Flags |= CMEFlags.Disabled; - } + if (!(from is PlayerMobile pm)) + return; - public override void OnClick() - { - bool oldValue = m_Mobile.ToggleMiningStone; + ContextMenuEntry miningEntry = new ContextMenuEntry(pm.ToggleMiningStone ? 6179 : 6178); + miningEntry.Color = 0x421F; + list.Add(miningEntry); - if ( m_Value ) - { - if ( oldValue ) - { - m_Mobile.SendLocalizedMessage( 1054023 ); // You are already set to mine both ore and stone! - } - else if ( !m_Mobile.StoneMining || m_Mobile.Skills[SkillName.Mining].Base < 100.0 ) - { - m_Mobile.SendLocalizedMessage( 1054024 ); // You have not learned how to mine stone or you do not have enough skill! - } - else - { - m_Mobile.ToggleMiningStone = true; - m_Mobile.SendLocalizedMessage( 1054022 ); // You are now set to mine both ore and stone. - } - } - else - { - if ( oldValue ) - { - m_Mobile.ToggleMiningStone = false; - m_Mobile.SendLocalizedMessage( 1054020 ); // You are now set to mine only ore. - } - else - { - m_Mobile.SendLocalizedMessage( 1054021 ); // You are already set to mine only ore! - } - } - } - } + list.Add(new ToggleMiningStoneEntry(pm, false, 6176)); + list.Add(new ToggleMiningStoneEntry(pm, true, 6177)); + } - public BaseHarvestTool( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(1); // version - writer.Write( (int) 1 ); // version + writer.Write(m_Crafter); + writer.Write((int)m_Quality); - writer.Write( (Mobile) m_Crafter ); - writer.Write( (int) m_Quality ); + writer.Write(m_UsesRemaining); + } - writer.Write( (int) m_UsesRemaining ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + switch (version) + { + case 1: + { + m_Crafter = reader.ReadMobile(); + m_Quality = (ToolQuality)reader.ReadInt(); + goto case 0; + } + case 0: + { + m_UsesRemaining = reader.ReadInt(); + break; + } + } + } - switch ( version ) - { - case 1: - { - m_Crafter = reader.ReadMobile(); - m_Quality = (ToolQuality) reader.ReadInt(); - goto case 0; - } - case 0: - { - m_UsesRemaining = reader.ReadInt(); - break; - } - } - } + private class ToggleMiningStoneEntry : ContextMenuEntry + { + private PlayerMobile m_Mobile; + private bool m_Value; - #region ICraftable Members + public ToggleMiningStoneEntry(PlayerMobile mobile, bool value, int number) : base(number) + { + m_Mobile = mobile; + m_Value = value; - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (ToolQuality)quality; + bool stoneMining = mobile.StoneMining && mobile.Skills[SkillName.Mining].Base >= 100.0; - if ( makersMark ) - Crafter = from; + if (mobile.ToggleMiningStone == value || value && !stoneMining) + Flags |= CMEFlags.Disabled; + } - return quality; - } + public override void OnClick() + { + bool oldValue = m_Mobile.ToggleMiningStone; - #endregion - } -} + if (m_Value) + { + if (oldValue) + { + m_Mobile.SendLocalizedMessage(1054023); // You are already set to mine both ore and stone! + } + else if (!m_Mobile.StoneMining || m_Mobile.Skills[SkillName.Mining].Base < 100.0) + { + m_Mobile.SendLocalizedMessage( + 1054024); // You have not learned how to mine stone or you do not have enough skill! + } + else + { + m_Mobile.ToggleMiningStone = true; + m_Mobile.SendLocalizedMessage(1054022); // You are now set to mine both ore and stone. + } + } + else + { + if (oldValue) + { + m_Mobile.ToggleMiningStone = false; + m_Mobile.SendLocalizedMessage(1054020); // You are now set to mine only ore. + } + else + { + m_Mobile.SendLocalizedMessage(1054021); // You are already set to mine only ore! + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Harvest Tools/GargoylesPickaxe.cs b/Scripts/Items/Skill Items/Harvest Tools/GargoylesPickaxe.cs index 2f0dfb10f..9276c59f7 100644 --- a/Scripts/Items/Skill Items/Harvest Tools/GargoylesPickaxe.cs +++ b/Scripts/Items/Skill Items/Harvest Tools/GargoylesPickaxe.cs @@ -2,62 +2,62 @@ using Server.Engines.Harvest; namespace Server.Items { - public class GargoylesPickaxe : BaseAxe, IUsesRemaining - { - public override int LabelNumber => 1041281; // a gargoyle's pickaxe - public override HarvestSystem HarvestSystem => Mining.System; + public class GargoylesPickaxe : BaseAxe, IUsesRemaining + { + [Constructible] + public GargoylesPickaxe() : this(Utility.RandomMinMax(101, 125)) + { + } - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Constructible] + public GargoylesPickaxe(int uses) : base(0xE85 + Utility.Random(2)) + { + Weight = 11.0; + UsesRemaining = uses; + ShowUsesRemaining = true; + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 35; - public override float MlSpeed => 3.00f; + public GargoylesPickaxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 25; - public override int OldMinDamage => 1; - public override int OldMaxDamage => 15; - public override int OldSpeed => 35; + public override int LabelNumber => 1041281; // a gargoyle's pickaxe + public override HarvestSystem HarvestSystem => Mining.System; - public override int InitMinHits => 31; - public override int InitMaxHits => 60; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; + public override int AosStrengthReq => 50; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 35; + public override float MlSpeed => 3.00f; - [Constructible] - public GargoylesPickaxe() : this( Utility.RandomMinMax( 101, 125 )) - { - } + public override int OldStrengthReq => 25; + public override int OldMinDamage => 1; + public override int OldMaxDamage => 15; + public override int OldSpeed => 35; - [Constructible] - public GargoylesPickaxe( int uses ) : base( 0xE85 + Utility.Random( 2 )) - { - Weight = 11.0; - UsesRemaining = uses; - ShowUsesRemaining = true; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 60; - public GargoylesPickaxe( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 0x973 ) - Hue = 0x0; - } - } -} + if (Hue == 0x973) + Hue = 0x0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Harvest Tools/ProspectorsTool.cs b/Scripts/Items/Skill Items/Harvest Tools/ProspectorsTool.cs index 5b2c4b4c3..e230f8219 100644 --- a/Scripts/Items/Skill Items/Harvest Tools/ProspectorsTool.cs +++ b/Scripts/Items/Skill Items/Harvest Tools/ProspectorsTool.cs @@ -1,174 +1,181 @@ using System; -using Server.Targeting; using Server.Engines.Harvest; +using Server.Targeting; namespace Server.Items { - public class ProspectorsTool : BaseBashing, IUsesRemaining - { - private int m_UsesRemaining; + public class ProspectorsTool : BaseBashing, IUsesRemaining + { + private int m_UsesRemaining; - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + [Constructible] + public ProspectorsTool() : base(0xFB4) + { + Weight = 9.0; + UsesRemaining = 50; + } - public bool ShowUsesRemaining{ get => true; - set{} } + public ProspectorsTool(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1049065; // prospector's tool + public override int LabelNumber => 1049065; // prospector's tool - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; - public override int AosStrengthReq => 40; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 33; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 33; - public override int OldStrengthReq => 10; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 8; - public override int OldSpeed => 33; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 8; + public override int OldSpeed => 33; - [Constructible] - public ProspectorsTool() : base( 0xFB4 ) - { - Weight = 9.0; - UsesRemaining = 50; - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public ProspectorsTool( Serial serial ) : base( serial ) - { - } + public bool ShowUsesRemaining + { + get => true; + set { } + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) || Parent == from ) - from.Target = new InternalTarget( this ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack) || Parent == from) + from.Target = new InternalTarget(this); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } - public void Prospect( Mobile from, object toProspect ) - { - if ( !IsChildOf( from.Backpack ) && Parent != from ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } + public void Prospect(Mobile from, object toProspect) + { + if (!IsChildOf(from.Backpack) && Parent != from) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - HarvestSystem system = Mining.System; + HarvestSystem system = Mining.System; - int tileID; - Map map; - Point3D loc; + int tileID; + Map map; + Point3D loc; - if ( !system.GetHarvestDetails( from, this, toProspect, out tileID, out map, out loc ) ) - { - from.SendLocalizedMessage( 1049048 ); // You cannot use your prospector tool on that. - return; - } + if (!system.GetHarvestDetails(from, this, toProspect, out tileID, out map, out loc)) + { + from.SendLocalizedMessage(1049048); // You cannot use your prospector tool on that. + return; + } - HarvestDefinition def = system.GetDefinition( tileID ); + HarvestDefinition def = system.GetDefinition(tileID); - if ( def == null || def.Veins.Length <= 1 ) - { - from.SendLocalizedMessage( 1049048 ); // You cannot use your prospector tool on that. - return; - } + if (def == null || def.Veins.Length <= 1) + { + from.SendLocalizedMessage(1049048); // You cannot use your prospector tool on that. + return; + } - HarvestBank bank = def.GetBank( map, loc.X, loc.Y ); + HarvestBank bank = def.GetBank(map, loc.X, loc.Y); - if ( bank == null ) - { - from.SendLocalizedMessage( 1049048 ); // You cannot use your prospector tool on that. - return; - } + if (bank == null) + { + from.SendLocalizedMessage(1049048); // You cannot use your prospector tool on that. + return; + } - HarvestVein vein = bank.Vein, defaultVein = bank.DefaultVein; + HarvestVein vein = bank.Vein, defaultVein = bank.DefaultVein; - if ( vein == null || defaultVein == null ) - { - from.SendLocalizedMessage( 1049048 ); // You cannot use your prospector tool on that. - return; - } + if (vein == null || defaultVein == null) + { + from.SendLocalizedMessage(1049048); // You cannot use your prospector tool on that. + return; + } - if ( vein != defaultVein ) - { - from.SendLocalizedMessage( 1049049 ); // That ore looks to be prospected already. - return; - } + if (vein != defaultVein) + { + from.SendLocalizedMessage(1049049); // That ore looks to be prospected already. + return; + } - int veinIndex = Array.IndexOf( def.Veins, vein ); + int veinIndex = Array.IndexOf(def.Veins, vein); - if ( veinIndex < 0 ) - { - from.SendLocalizedMessage( 1049048 ); // You cannot use your prospector tool on that. - } - else if ( veinIndex >= (def.Veins.Length - 1) ) - { - from.SendLocalizedMessage( 1049061 ); // You cannot improve valorite ore through prospecting. - } - else - { - bank.Vein = def.Veins[veinIndex + 1]; - from.SendLocalizedMessage( 1049050 + veinIndex ); + if (veinIndex < 0) + { + from.SendLocalizedMessage(1049048); // You cannot use your prospector tool on that. + } + else if (veinIndex >= def.Veins.Length - 1) + { + from.SendLocalizedMessage(1049061); // You cannot improve valorite ore through prospecting. + } + else + { + bank.Vein = def.Veins[veinIndex + 1]; + from.SendLocalizedMessage(1049050 + veinIndex); - --UsesRemaining; + --UsesRemaining; - if ( UsesRemaining <= 0 ) - { - from.SendLocalizedMessage( 1049062 ); // You have used up your prospector's tool. - Delete(); - } - } - } + if (UsesRemaining <= 0) + { + from.SendLocalizedMessage(1049062); // You have used up your prospector's tool. + Delete(); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - writer.Write( (int) m_UsesRemaining ); - } + writer.Write(1); // version + writer.Write(m_UsesRemaining); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_UsesRemaining = reader.ReadInt(); - break; - } - case 0: - { - m_UsesRemaining = 50; - break; - } - } - } + switch (version) + { + case 1: + { + m_UsesRemaining = reader.ReadInt(); + break; + } + case 0: + { + m_UsesRemaining = 50; + break; + } + } + } - private class InternalTarget : Target - { - private ProspectorsTool m_Tool; + private class InternalTarget : Target + { + private ProspectorsTool m_Tool; - public InternalTarget( ProspectorsTool tool ) : base( 2, true, TargetFlags.None ) - { - m_Tool = tool; - } + public InternalTarget(ProspectorsTool tool) : base(2, true, TargetFlags.None) + { + m_Tool = tool; + } - protected override void OnTarget( Mobile from, object targeted ) - { - m_Tool.Prospect( from, targeted ); - } - } - } -} + protected override void OnTarget(Mobile from, object targeted) + { + m_Tool.Prospect(from, targeted); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Harvest Tools/Shovel.cs b/Scripts/Items/Skill Items/Harvest Tools/Shovel.cs index c2675cc56..6578d8ab2 100644 --- a/Scripts/Items/Skill Items/Harvest Tools/Shovel.cs +++ b/Scripts/Items/Skill Items/Harvest Tools/Shovel.cs @@ -2,37 +2,37 @@ using Server.Engines.Harvest; namespace Server.Items { - public class Shovel : BaseHarvestTool - { - public override HarvestSystem HarvestSystem => Mining.System; + public class Shovel : BaseHarvestTool + { + [Constructible] + public Shovel() : this(50) + { + } - [Constructible] - public Shovel() : this( 50 ) - { - } + [Constructible] + public Shovel(int uses) : base(uses, 0xF39) + { + Weight = 5.0; + } - [Constructible] - public Shovel( int uses ) : base( uses, 0xF39 ) - { - Weight = 5.0; - } + public Shovel(Serial serial) : base(serial) + { + } - public Shovel( Serial serial ) : base( serial ) - { - } + public override HarvestSystem HarvestSystem => Mining.System; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Harvest Tools/SturdyPickaxe.cs b/Scripts/Items/Skill Items/Harvest Tools/SturdyPickaxe.cs index 1bd13fffe..c332af5bd 100644 --- a/Scripts/Items/Skill Items/Harvest Tools/SturdyPickaxe.cs +++ b/Scripts/Items/Skill Items/Harvest Tools/SturdyPickaxe.cs @@ -2,57 +2,57 @@ using Server.Engines.Harvest; namespace Server.Items { - public class SturdyPickaxe : BaseAxe, IUsesRemaining - { - public override int LabelNumber => 1045126; // sturdy pickaxe - public override HarvestSystem HarvestSystem => Mining.System; + public class SturdyPickaxe : BaseAxe, IUsesRemaining + { + [Constructible] + public SturdyPickaxe() : this(180) + { + } - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Constructible] + public SturdyPickaxe(int uses) : base(0xE86) + { + Weight = 11.0; + Hue = 0x973; + UsesRemaining = uses; + ShowUsesRemaining = true; + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 35; - public override float MlSpeed => 3.00f; + public SturdyPickaxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 25; - public override int OldMinDamage => 1; - public override int OldMaxDamage => 15; - public override int OldSpeed => 35; + public override int LabelNumber => 1045126; // sturdy pickaxe + public override HarvestSystem HarvestSystem => Mining.System; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - [Constructible] - public SturdyPickaxe() : this( 180 ) - { - } + public override int AosStrengthReq => 50; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 35; + public override float MlSpeed => 3.00f; - [Constructible] - public SturdyPickaxe( int uses ) : base( 0xE86 ) - { - Weight = 11.0; - Hue = 0x973; - UsesRemaining = uses; - ShowUsesRemaining = true; - } + public override int OldStrengthReq => 25; + public override int OldMinDamage => 1; + public override int OldMaxDamage => 15; + public override int OldSpeed => 35; - public SturdyPickaxe( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Harvest Tools/SturdyShovel.cs b/Scripts/Items/Skill Items/Harvest Tools/SturdyShovel.cs index 3c018a718..4e632d01f 100644 --- a/Scripts/Items/Skill Items/Harvest Tools/SturdyShovel.cs +++ b/Scripts/Items/Skill Items/Harvest Tools/SturdyShovel.cs @@ -2,39 +2,39 @@ using Server.Engines.Harvest; namespace Server.Items { - public class SturdyShovel : BaseHarvestTool - { - public override int LabelNumber => 1045125; // sturdy shovel - public override HarvestSystem HarvestSystem => Mining.System; + public class SturdyShovel : BaseHarvestTool + { + [Constructible] + public SturdyShovel() : this(180) + { + } - [Constructible] - public SturdyShovel() : this( 180 ) - { - } + [Constructible] + public SturdyShovel(int uses) : base(uses, 0xF39) + { + Weight = 5.0; + Hue = 0x973; + } - [Constructible] - public SturdyShovel( int uses ) : base( uses, 0xF39 ) - { - Weight = 5.0; - Hue = 0x973; - } + public SturdyShovel(Serial serial) : base(serial) + { + } - public SturdyShovel( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1045125; // sturdy shovel + public override HarvestSystem HarvestSystem => Mining.System; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Lumberjack/Log.cs b/Scripts/Items/Skill Items/Lumberjack/Log.cs index b05ccd273..1bdb326a2 100644 --- a/Scripts/Items/Skill Items/Lumberjack/Log.cs +++ b/Scripts/Items/Skill Items/Lumberjack/Log.cs @@ -1,355 +1,374 @@ namespace Server.Items { - [FlippableAttribute( 0x1bdd, 0x1be0 )] - public class Log : Item, ICommodity, IAxe - { - private CraftResource m_Resource; + [Flippable(0x1bdd, 0x1be0)] + public class Log : Item, ICommodity, IAxe + { + private CraftResource m_Resource; - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set { m_Resource = value; InvalidateProperties(); } - } + [Constructible] + public Log() : this(1) + { + } - int ICommodity.DescriptionNumber => CraftResources.IsStandard( m_Resource ) ? LabelNumber : 1075062 + ( (int)m_Resource - (int)CraftResource.RegularWood ); - bool ICommodity.IsDeedable => true; + [Constructible] + public Log(int amount) : this(CraftResource.RegularWood, amount) + { + } - [Constructible] - public Log() : this( 1 ) - { - } + [Constructible] + public Log(CraftResource resource) + : this(resource, 1) + { + } - [Constructible] - public Log( int amount ) : this( CraftResource.RegularWood, amount ) - { - } + [Constructible] + public Log(CraftResource resource, int amount) + : base(0x1BDD) + { + Stackable = true; + Weight = 2.0; + Amount = amount; - [Constructible] - public Log( CraftResource resource ) - : this( resource, 1 ) - { - } - [Constructible] - public Log( CraftResource resource, int amount ) - : base( 0x1BDD ) - { - Stackable = true; - Weight = 2.0; - Amount = amount; + m_Resource = resource; + Hue = CraftResources.GetHue(resource); + } - m_Resource = resource; - Hue = CraftResources.GetHue( resource ); - } + public Log(Serial serial) : base(serial) + { + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + InvalidateProperties(); + } + } - if ( !CraftResources.IsStandard( m_Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( m_Resource ); + public virtual bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 0, new Board())) + return false; - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( m_Resource ) ); - } - } - public Log( Serial serial ) : base( serial ) - { - } + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int ICommodity.DescriptionNumber => CraftResources.IsStandard(m_Resource) + ? LabelNumber + : 1075062 + ((int)m_Resource - (int)CraftResource.RegularWood); - writer.Write( (int) 1 ); // version + bool ICommodity.IsDeedable => true; - writer.Write( (int)m_Resource ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (!CraftResources.IsStandard(m_Resource)) + { + int num = CraftResources.GetLocalizationNumber(m_Resource); - int version = reader.ReadInt(); + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(m_Resource)); + } + } - switch ( version ) - { - case 1: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( version == 0 ) - m_Resource = CraftResource.RegularWood; - } + writer.Write(1); // version - public virtual bool TryCreateBoards( Mobile from, double skill, Item item ) - { - if ( Deleted || !from.CanSee( this ) ) - return false; - if ( from.Skills.Carpentry.Value < skill && - from.Skills.Lumberjacking.Value < skill ) - { - item.Delete(); - from.SendLocalizedMessage( 1072652 ); // You cannot work this strange and unusual wood. - return false; - } - base.ScissorHelper( from, item, 1, false ); - return true; - } + writer.Write((int)m_Resource); + } - public virtual bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 0, new Board() ) ) - return false; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return true; - } - } - public class HeartwoodLog : Log - { - [Constructible] - public HeartwoodLog() : this( 1 ) - { - } - [Constructible] - public HeartwoodLog( int amount ) - : base( CraftResource.Heartwood, amount ) - { - } - public HeartwoodLog( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); - writer.Write( (int)0 ); // version - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + switch (version) + { + case 1: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } - int version = reader.ReadInt(); - } + if (version == 0) + m_Resource = CraftResource.RegularWood; + } - public override bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 100, new HeartwoodBoard() ) ) - return false; + public virtual bool TryCreateBoards(Mobile from, double skill, Item item) + { + if (Deleted || !from.CanSee(this)) + return false; + if (from.Skills.Carpentry.Value < skill && + from.Skills.Lumberjacking.Value < skill) + { + item.Delete(); + from.SendLocalizedMessage(1072652); // You cannot work this strange and unusual wood. + return false; + } - return true; - } - } + base.ScissorHelper(from, item, 1, false); + return true; + } + } - public class BloodwoodLog : Log - { - [Constructible] - public BloodwoodLog() - : this( 1 ) - { - } - [Constructible] - public BloodwoodLog( int amount ) - : base( CraftResource.Bloodwood, amount ) - { - } - public BloodwoodLog( Serial serial ) - : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public class HeartwoodLog : Log + { + [Constructible] + public HeartwoodLog() : this(1) + { + } - writer.Write( (int)0 ); // version - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public HeartwoodLog(int amount) + : base(CraftResource.Heartwood, amount) + { + } - int version = reader.ReadInt(); - } + public HeartwoodLog(Serial serial) : base(serial) + { + } - public override bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 100, new BloodwoodBoard() ) ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } + writer.Write(0); // version + } - public class FrostwoodLog : Log - { - [Constructible] - public FrostwoodLog() - : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public FrostwoodLog( int amount ) - : base( CraftResource.Frostwood, amount ) - { - } + int version = reader.ReadInt(); + } - public FrostwoodLog( Serial serial ) - : base( serial ) - { - } + public override bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 100, new HeartwoodBoard())) + return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } + } - writer.Write( (int)0 ); // version - } + public class BloodwoodLog : Log + { + [Constructible] + public BloodwoodLog() + : this(1) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public BloodwoodLog(int amount) + : base(CraftResource.Bloodwood, amount) + { + } - int version = reader.ReadInt(); - } + public BloodwoodLog(Serial serial) + : base(serial) + { + } - public override bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 100, new FrostwoodBoard() ) ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } + writer.Write(0); // version + } - public class OakLog : Log - { - [Constructible] - public OakLog() - : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public OakLog( int amount ) - : base( CraftResource.OakWood, amount ) - { - } + int version = reader.ReadInt(); + } - public OakLog( Serial serial ) - : base( serial ) - { - } + public override bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 100, new BloodwoodBoard())) + return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } + } - writer.Write( (int)0 ); // version - } + public class FrostwoodLog : Log + { + [Constructible] + public FrostwoodLog() + : this(1) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public FrostwoodLog(int amount) + : base(CraftResource.Frostwood, amount) + { + } - int version = reader.ReadInt(); - } + public FrostwoodLog(Serial serial) + : base(serial) + { + } - public override bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 65, new OakBoard() ) ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } + writer.Write(0); // version + } - public class AshLog : Log - { - [Constructible] - public AshLog() - : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public AshLog( int amount ) - : base( CraftResource.AshWood, amount ) - { - } + int version = reader.ReadInt(); + } - public AshLog( Serial serial ) - : base( serial ) - { - } + public override bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 100, new FrostwoodBoard())) + return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } + } - writer.Write( (int)0 ); // version - } + public class OakLog : Log + { + [Constructible] + public OakLog() + : this(1) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public OakLog(int amount) + : base(CraftResource.OakWood, amount) + { + } - int version = reader.ReadInt(); - } + public OakLog(Serial serial) + : base(serial) + { + } - public override bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 80, new AshBoard() ) ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } + writer.Write(0); // version + } - public class YewLog : Log - { - [Constructible] - public YewLog() - : this( 1 ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public YewLog( int amount ) - : base( CraftResource.YewWood, amount ) - { - } + int version = reader.ReadInt(); + } - public YewLog( Serial serial ) - : base( serial ) - { - } + public override bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 65, new OakBoard())) + return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } + } - writer.Write( (int)0 ); // version - } + public class AshLog : Log + { + [Constructible] + public AshLog() + : this(1) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [Constructible] + public AshLog(int amount) + : base(CraftResource.AshWood, amount) + { + } - int version = reader.ReadInt(); - } + public AshLog(Serial serial) + : base(serial) + { + } - public override bool Axe( Mobile from, BaseAxe axe ) - { - if ( !TryCreateBoards( from , 95, new YewBoard() ) ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 80, new AshBoard())) + return false; + + return true; + } + } + + public class YewLog : Log + { + [Constructible] + public YewLog() + : this(1) + { + } + + [Constructible] + public YewLog(int amount) + : base(CraftResource.YewWood, amount) + { + } + + public YewLog(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override bool Axe(Mobile from, BaseAxe axe) + { + if (!TryCreateBoards(from, 95, new YewBoard())) + return false; + + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/BookOfBushido.cs b/Scripts/Items/Skill Items/Magical/BookOfBushido.cs index 6f5d87051..5eafe24e3 100644 --- a/Scripts/Items/Skill Items/Magical/BookOfBushido.cs +++ b/Scripts/Items/Skill Items/Magical/BookOfBushido.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class BookOfBushido : Spellbook - { - public override SpellbookType SpellbookType => SpellbookType.Samurai; - public override int BookOffset => 400; - public override int BookCount => 6; + public class BookOfBushido : Spellbook + { + [Constructible] + public BookOfBushido() : this((ulong)0x3F) + { + } - [Constructible] - public BookOfBushido() : this( (ulong)0x3F ) - { - } + [Constructible] + public BookOfBushido(ulong content) : base(content, 0x238C) + { + Layer = Core.ML ? Layer.OneHanded : Layer.Invalid; + } - [Constructible] - public BookOfBushido( ulong content ) : base( content, 0x238C ) - { - Layer = (Core.ML ? Layer.OneHanded : Layer.Invalid); - } + public BookOfBushido(Serial serial) : base(serial) + { + } - public BookOfBushido( Serial serial ) : base( serial ) - { - } + public override SpellbookType SpellbookType => SpellbookType.Samurai; + public override int BookOffset => 400; + public override int BookCount => 6; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && Core.ML ) - Layer = Layer.OneHanded; - } - } -} + if (version == 0 && Core.ML) + Layer = Layer.OneHanded; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/BookOfChivalry.cs b/Scripts/Items/Skill Items/Magical/BookOfChivalry.cs index b8b7d0a85..13f75bb69 100644 --- a/Scripts/Items/Skill Items/Magical/BookOfChivalry.cs +++ b/Scripts/Items/Skill Items/Magical/BookOfChivalry.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class BookOfChivalry : Spellbook - { - public override SpellbookType SpellbookType => SpellbookType.Paladin; - public override int BookOffset => 200; - public override int BookCount => 10; + public class BookOfChivalry : Spellbook + { + [Constructible] + public BookOfChivalry() : this((ulong)0x3FF) + { + } - [Constructible] - public BookOfChivalry() : this( (ulong)0x3FF ) - { - } + [Constructible] + public BookOfChivalry(ulong content) : base(content, 0x2252) + { + Layer = Core.ML ? Layer.OneHanded : Layer.Invalid; + } - [Constructible] - public BookOfChivalry( ulong content ) : base( content, 0x2252 ) - { - Layer = (Core.ML ? Layer.OneHanded : Layer.Invalid); - } + public BookOfChivalry(Serial serial) : base(serial) + { + } - public BookOfChivalry( Serial serial ) : base( serial ) - { - } + public override SpellbookType SpellbookType => SpellbookType.Paladin; + public override int BookOffset => 200; + public override int BookCount => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && Core.ML ) - Layer = Layer.OneHanded; - } - } -} + if (version == 0 && Core.ML) + Layer = Layer.OneHanded; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/BookOfNinjitsu.cs b/Scripts/Items/Skill Items/Magical/BookOfNinjitsu.cs index fb216864f..33a500345 100644 --- a/Scripts/Items/Skill Items/Magical/BookOfNinjitsu.cs +++ b/Scripts/Items/Skill Items/Magical/BookOfNinjitsu.cs @@ -1,42 +1,41 @@ namespace Server.Items { - public class BookOfNinjitsu : Spellbook - { - public override SpellbookType SpellbookType => SpellbookType.Ninja; - public override int BookOffset => 500; - public override int BookCount => 8; + public class BookOfNinjitsu : Spellbook + { + [Constructible] + public BookOfNinjitsu() : this((ulong)0xFF) + { + } + [Constructible] + public BookOfNinjitsu(ulong content) : base(content, 0x23A0) + { + Layer = Core.ML ? Layer.OneHanded : Layer.Invalid; + } - [Constructible] - public BookOfNinjitsu() : this( (ulong)0xFF ) - { - } + public BookOfNinjitsu(Serial serial) : base(serial) + { + } - [Constructible] - public BookOfNinjitsu( ulong content ) : base( content, 0x23A0 ) - { - Layer = (Core.ML ? Layer.OneHanded : Layer.Invalid); - } + public override SpellbookType SpellbookType => SpellbookType.Ninja; + public override int BookOffset => 500; + public override int BookCount => 8; - public BookOfNinjitsu( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(1); // version + } - writer.Write( (int)1 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); - - if ( version == 0 && Core.ML ) - Layer = Layer.OneHanded; - } - } -} + if (version == 0 && Core.ML) + Layer = Layer.OneHanded; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Misc/BlankScroll.cs b/Scripts/Items/Skill Items/Magical/Misc/BlankScroll.cs index f7f70269f..4a783a956 100644 --- a/Scripts/Items/Skill Items/Magical/Misc/BlankScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Misc/BlankScroll.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class BlankScroll : Item, ICommodity - { - [Constructible] - public BlankScroll() : this( 1 ) - { - } + public class BlankScroll : Item, ICommodity + { + [Constructible] + public BlankScroll() : this(1) + { + } - [Constructible] - public BlankScroll( int amount ) : base( 0xEF3 ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } + [Constructible] + public BlankScroll(int amount) : base(0xEF3) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => (Core.ML); + public BlankScroll(Serial serial) : base(serial) + { + } - public BlankScroll( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => Core.ML; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Misc/Bottle.cs b/Scripts/Items/Skill Items/Magical/Misc/Bottle.cs index 6c8237e2c..64caf2f86 100644 --- a/Scripts/Items/Skill Items/Magical/Misc/Bottle.cs +++ b/Scripts/Items/Skill Items/Magical/Misc/Bottle.cs @@ -1,41 +1,40 @@ namespace Server.Items { - public class Bottle : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => (Core.ML); + public class Bottle : Item, ICommodity + { + [Constructible] + public Bottle() : this(1) + { + } - [Constructible] - public Bottle() : this( 1 ) - { - } + [Constructible] + public Bottle(int amount) : base(0xF0E) + { + Stackable = true; + Weight = 1.0; + Amount = amount; + } - [Constructible] - public Bottle( int amount ) : base( 0xF0E ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; - } + public Bottle(Serial serial) : base(serial) + { + } - public Bottle( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => Core.ML; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Misc/Moongate.cs b/Scripts/Items/Skill Items/Magical/Misc/Moongate.cs index 355368aab..0eb3fcbe3 100644 --- a/Scripts/Items/Skill Items/Magical/Misc/Moongate.cs +++ b/Scripts/Items/Skill Items/Magical/Misc/Moongate.cs @@ -1,390 +1,403 @@ using System; +using Server.Factions; +using Server.Gumps; using Server.Misc; using Server.Mobiles; using Server.Network; -using Server.Gumps; using Server.Regions; namespace Server.Items { - [DispellableFieldAttribute] - public class Moongate : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Target { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Map TargetMap { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Dispellable { get; set; } - - public virtual bool ShowFeluccaWarning => false; - - [Constructible] - public Moongate() : this( Point3D.Zero, null ) - { - Dispellable = true; - } - - [Constructible] - public Moongate(bool bDispellable) : this( Point3D.Zero, null ) - { - Dispellable = bDispellable; - } - - [Constructible] - public Moongate( Point3D target, Map targetMap ) : base( 0xF6C ) - { - Movable = false; - Light = LightType.Circle300; - - Target = target; - TargetMap = targetMap; - } - - public Moongate( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.Player ) - return; - - if ( from.InRange( GetWorldLocation(), 1 ) ) - CheckGate( from, 1 ); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - - public override bool OnMoveOver( Mobile m ) - { - if ( m.Player ) - CheckGate( m, 0 ); - - return true; - } - - public virtual void CheckGate( Mobile m, int range ) - { - #region Mondain's Legacy - if ( m.Hidden && m.AccessLevel == AccessLevel.Player && Core.ML ) - m.RevealingAction(); - #endregion - - new DelayTimer( m, this, range ).Start(); - } - - public virtual void OnGateUsed( Mobile m ) - { - } - - public virtual void UseGate( Mobile m ) - { - ClientFlags flags = m.NetState?.Flags ?? ClientFlags.None; - - if ( Factions.Sigil.ExistsOn( m ) ) - { - m.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( TargetMap == Map.Felucca && m is PlayerMobile mobile && mobile.Young ) - { - mobile.SendLocalizedMessage( 1049543 ); // You decide against traveling to Felucca while you are still young. - } - else if ( (m.Kills >= 5 && TargetMap != Map.Felucca) || ( TargetMap == Map.Tokuno && (flags & ClientFlags.Tokuno) == 0 ) || ( TargetMap == Map.Malas && (flags & ClientFlags.Malas) == 0 ) || ( TargetMap == Map.Ilshenar && (flags & ClientFlags.Ilshenar) == 0 ) ) - { - m.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - } - else if ( m.Spell != null ) - { - m.SendLocalizedMessage( 1049616 ); // You are too busy to do that at the moment. - } - else if ( TargetMap != null && TargetMap != Map.Internal ) - { - BaseCreature.TeleportPets( m, Target, TargetMap ); - - m.MoveToWorld( Target, TargetMap ); - - if ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) - m.PlaySound( 0x1FE ); - - OnGateUsed( m ); - } - else - { - m.SendMessage( "This moongate does not seem to go anywhere." ); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( Target ); - writer.Write( TargetMap ); - - // Version 1 - writer.Write( Dispellable ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Target = reader.ReadPoint3D(); - TargetMap = reader.ReadMap(); - - if ( version >= 1 ) - Dispellable = reader.ReadBool(); - } - - public virtual bool ValidateUse( Mobile from, bool message ) - { - if ( from.Deleted || Deleted ) - return false; - - if ( from.Map != Map || !from.InRange( this, 1 ) ) - { - if ( message ) - from.SendLocalizedMessage( 500446 ); // That is too far away. - - return false; - } - - return true; - } - - public virtual void BeginConfirmation( Mobile from ) - { - if ( IsInTown( from.Location, from.Map ) && !IsInTown( Target, TargetMap ) || (from.Map != Map.Felucca && TargetMap == Map.Felucca && ShowFeluccaWarning) ) - { - if ( from.AccessLevel == AccessLevel.Player || !from.Hidden ) - from.Send( new PlaySound( 0x20E, from.Location ) ); - from.CloseGump( typeof( MoongateConfirmGump ) ); - from.SendGump( new MoongateConfirmGump( from, this ) ); - } - else - { - EndConfirmation( from ); - } - } - - public virtual void EndConfirmation( Mobile from ) - { - if ( !ValidateUse( from, true ) ) - return; - - UseGate( from ); - } - - public virtual void DelayCallback( Mobile from, int range ) - { - if ( !ValidateUse( from, false ) || !from.InRange( this, range ) ) - return; - - if ( TargetMap != null ) - BeginConfirmation( from ); - else - from.SendMessage( "This moongate does not seem to go anywhere." ); - } - - public static bool IsInTown( Point3D p, Map map ) - { - if ( map == null ) - return false; - - GuardedRegion reg = (GuardedRegion) Region.Find( p, map ).GetRegion( typeof( GuardedRegion ) ); - - return ( reg != null && !reg.IsDisabled() ); - } - - private class DelayTimer : Timer - { - private Mobile m_From; - private Moongate m_Gate; - private int m_Range; - - public DelayTimer( Mobile from, Moongate gate, int range ) : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_From = from; - m_Gate = gate; - m_Range = range; - } - - protected override void OnTick() - { - m_Gate.DelayCallback( m_From, m_Range ); - } - } - } - - public class ConfirmationMoongate : Moongate - { - [CommandProperty( AccessLevel.GameMaster )] - public int GumpWidth { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int GumpHeight { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int TitleColor { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int MessageColor { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int TitleNumber { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int MessageNumber { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string MessageString { get; set; } - - [Constructible] - public ConfirmationMoongate() : this( Point3D.Zero, null ) - { - } - - [Constructible] - public ConfirmationMoongate( Point3D target, Map targetMap ) : base( target, targetMap ) - { - } - - public ConfirmationMoongate( Serial serial ) : base( serial ) - { - } - - public virtual void Warning_Callback( Mobile from, bool okay, object state ) - { - if ( okay ) - EndConfirmation( from ); - } - - public override void BeginConfirmation( Mobile from ) - { - if ( GumpWidth > 0 && GumpHeight > 0 && TitleNumber > 0 && (MessageNumber > 0 || MessageString != null) ) - { - from.CloseGump( typeof( WarningGump ) ); - from.SendGump( new WarningGump( TitleNumber, TitleColor, MessageString == null ? (object)MessageNumber : (object)MessageString, MessageColor, GumpWidth, GumpHeight, Warning_Callback, from ) ); - } - else - { - base.BeginConfirmation( from ); - } - } + [DispellableField] + public class Moongate : Item + { + [Constructible] + public Moongate() : this(Point3D.Zero, null) + { + Dispellable = true; + } + + [Constructible] + public Moongate(bool bDispellable) : this(Point3D.Zero, null) + { + Dispellable = bDispellable; + } + + [Constructible] + public Moongate(Point3D target, Map targetMap) : base(0xF6C) + { + Movable = false; + Light = LightType.Circle300; + + Target = target; + TargetMap = targetMap; + } + + public Moongate(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Target{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Map TargetMap{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Dispellable{ get; set; } + + public virtual bool ShowFeluccaWarning => false; + + public override void OnDoubleClick(Mobile from) + { + if (!from.Player) + return; + + if (from.InRange(GetWorldLocation(), 1)) + CheckGate(from, 1); + else + from.SendLocalizedMessage(500446); // That is too far away. + } + + public override bool OnMoveOver(Mobile m) + { + if (m.Player) + CheckGate(m, 0); + + return true; + } + + public virtual void CheckGate(Mobile m, int range) + { + #region Mondain's Legacy + + if (m.Hidden && m.AccessLevel == AccessLevel.Player && Core.ML) + m.RevealingAction(); + + #endregion + + new DelayTimer(m, this, range).Start(); + } + + public virtual void OnGateUsed(Mobile m) + { + } + + public virtual void UseGate(Mobile m) + { + ClientFlags flags = m.NetState?.Flags ?? ClientFlags.None; + + if (Sigil.ExistsOn(m)) + { + m.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (TargetMap == Map.Felucca && m is PlayerMobile mobile && mobile.Young) + { + mobile.SendLocalizedMessage(1049543); // You decide against traveling to Felucca while you are still young. + } + else if (m.Kills >= 5 && TargetMap != Map.Felucca || + TargetMap == Map.Tokuno && (flags & ClientFlags.Tokuno) == 0 || + TargetMap == Map.Malas && (flags & ClientFlags.Malas) == 0 || + TargetMap == Map.Ilshenar && (flags & ClientFlags.Ilshenar) == 0) + { + m.SendLocalizedMessage(1019004); // You are not allowed to travel there. + } + else if (m.Spell != null) + { + m.SendLocalizedMessage(1049616); // You are too busy to do that at the moment. + } + else if (TargetMap != null && TargetMap != Map.Internal) + { + BaseCreature.TeleportPets(m, Target, TargetMap); + + m.MoveToWorld(Target, TargetMap); + + if (m.AccessLevel == AccessLevel.Player || !m.Hidden) + m.PlaySound(0x1FE); + + OnGateUsed(m); + } + else + { + m.SendMessage("This moongate does not seem to go anywhere."); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(Target); + writer.Write(TargetMap); + + // Version 1 + writer.Write(Dispellable); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Target = reader.ReadPoint3D(); + TargetMap = reader.ReadMap(); + + if (version >= 1) + Dispellable = reader.ReadBool(); + } + + public virtual bool ValidateUse(Mobile from, bool message) + { + if (from.Deleted || Deleted) + return false; + + if (from.Map != Map || !from.InRange(this, 1)) + { + if (message) + from.SendLocalizedMessage(500446); // That is too far away. + + return false; + } + + return true; + } + + public virtual void BeginConfirmation(Mobile from) + { + if (IsInTown(from.Location, from.Map) && !IsInTown(Target, TargetMap) || + from.Map != Map.Felucca && TargetMap == Map.Felucca && ShowFeluccaWarning) + { + if (from.AccessLevel == AccessLevel.Player || !from.Hidden) + from.Send(new PlaySound(0x20E, from.Location)); + from.CloseGump(typeof(MoongateConfirmGump)); + from.SendGump(new MoongateConfirmGump(from, this)); + } + else + { + EndConfirmation(from); + } + } + + public virtual void EndConfirmation(Mobile from) + { + if (!ValidateUse(from, true)) + return; + + UseGate(from); + } + + public virtual void DelayCallback(Mobile from, int range) + { + if (!ValidateUse(from, false) || !from.InRange(this, range)) + return; + + if (TargetMap != null) + BeginConfirmation(from); + else + from.SendMessage("This moongate does not seem to go anywhere."); + } + + public static bool IsInTown(Point3D p, Map map) + { + if (map == null) + return false; + + GuardedRegion reg = (GuardedRegion)Region.Find(p, map).GetRegion(typeof(GuardedRegion)); + + return reg != null && !reg.IsDisabled(); + } + + private class DelayTimer : Timer + { + private Mobile m_From; + private Moongate m_Gate; + private int m_Range; + + public DelayTimer(Mobile from, Moongate gate, int range) : base(TimeSpan.FromSeconds(1.0)) + { + m_From = from; + m_Gate = gate; + m_Range = range; + } + + protected override void OnTick() + { + m_Gate.DelayCallback(m_From, m_Range); + } + } + } + + public class ConfirmationMoongate : Moongate + { + [Constructible] + public ConfirmationMoongate() : this(Point3D.Zero, null) + { + } + + [Constructible] + public ConfirmationMoongate(Point3D target, Map targetMap) : base(target, targetMap) + { + } + + public ConfirmationMoongate(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int GumpWidth{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int GumpHeight{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int TitleColor{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int MessageColor{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int TitleNumber{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int MessageNumber{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string MessageString{ get; set; } + + public virtual void Warning_Callback(Mobile from, bool okay, object state) + { + if (okay) + EndConfirmation(from); + } + + public override void BeginConfirmation(Mobile from) + { + if (GumpWidth > 0 && GumpHeight > 0 && TitleNumber > 0 && (MessageNumber > 0 || MessageString != null)) + { + from.CloseGump(typeof(WarningGump)); + from.SendGump(new WarningGump(TitleNumber, TitleColor, + MessageString == null ? MessageNumber : (object)MessageString, MessageColor, GumpWidth, GumpHeight, + Warning_Callback, from)); + } + else + { + base.BeginConfirmation(from); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.WriteEncodedInt(GumpWidth); + writer.WriteEncodedInt(GumpHeight); + + writer.WriteEncodedInt(TitleColor); + writer.WriteEncodedInt(MessageColor); + + writer.WriteEncodedInt(TitleNumber); + writer.WriteEncodedInt(MessageNumber); + + writer.Write(MessageString); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + GumpWidth = reader.ReadEncodedInt(); + GumpHeight = reader.ReadEncodedInt(); + + TitleColor = reader.ReadEncodedInt(); + MessageColor = reader.ReadEncodedInt(); + + TitleNumber = reader.ReadEncodedInt(); + MessageNumber = reader.ReadEncodedInt(); + + MessageString = reader.ReadString(); + + break; + } + } + } + } + + public class MoongateConfirmGump : Gump + { + private Mobile m_From; + private Moongate m_Gate; + + public MoongateConfirmGump(Mobile from, Moongate gate) : base(Core.AOS ? 110 : 20, Core.AOS ? 100 : 30) + { + m_From = from; + m_Gate = gate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.WriteEncodedInt( GumpWidth ); - writer.WriteEncodedInt( GumpHeight ); - - writer.WriteEncodedInt( TitleColor ); - writer.WriteEncodedInt( MessageColor ); - - writer.WriteEncodedInt( TitleNumber ); - writer.WriteEncodedInt( MessageNumber ); - - writer.Write( MessageString ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - GumpWidth = reader.ReadEncodedInt(); - GumpHeight = reader.ReadEncodedInt(); - - TitleColor = reader.ReadEncodedInt(); - MessageColor = reader.ReadEncodedInt(); - - TitleNumber = reader.ReadEncodedInt(); - MessageNumber = reader.ReadEncodedInt(); + if (Core.AOS) + { + Closable = false; - MessageString = reader.ReadString(); + AddPage(0); - break; - } - } - } - } + AddBackground(0, 0, 420, 280, 5054); - public class MoongateConfirmGump : Gump - { - private Mobile m_From; - private Moongate m_Gate; + AddImageTiled(10, 10, 400, 20, 2624); + AddAlphaRegion(10, 10, 400, 20); + + AddHtmlLocalized(10, 10, 400, 20, 1062051, 30720, false, false); // Gate Warning + + AddImageTiled(10, 40, 400, 200, 2624); + AddAlphaRegion(10, 40, 400, 200); + + if (from.Map != Map.Felucca && gate.TargetMap == Map.Felucca && gate.ShowFeluccaWarning) + AddHtmlLocalized(10, 40, 400, 200, 1062050, 32512, false, + true); // This Gate goes to Felucca... Continue to enter the gate, Cancel to stay here + else + AddHtmlLocalized(10, 40, 400, 200, 1062049, 32512, false, + true); // Dost thou wish to step into the moongate? Continue to enter the gate, Cancel to stay here + + AddImageTiled(10, 250, 400, 20, 2624); + AddAlphaRegion(10, 250, 400, 20); + + AddButton(10, 250, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 250, 170, 20, 1011036, 32767, false, false); // OKAY + + AddButton(210, 250, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(240, 250, 170, 20, 1011012, 32767, false, false); // CANCEL + } + else + { + AddPage(0); - public MoongateConfirmGump( Mobile from, Moongate gate ) : base( Core.AOS ? 110 : 20, Core.AOS ? 100 : 30 ) - { - m_From = from; - m_Gate = gate; + AddBackground(0, 0, 420, 400, 5054); + AddBackground(10, 10, 400, 380, 3000); - if ( Core.AOS ) - { - Closable = false; + AddHtml(20, 40, 380, 60, + @"Dost thou wish to step into the moongate? Continue to enter the gate, Cancel to stay here", false, + false); - AddPage( 0 ); + AddHtmlLocalized(55, 110, 290, 20, 1011012, false, false); // CANCEL + AddButton(20, 110, 4005, 4007, 0, GumpButtonType.Reply, 0); - AddBackground( 0, 0, 420, 280, 5054 ); + AddHtmlLocalized(55, 140, 290, 40, 1011011, false, false); // CONTINUE + AddButton(20, 140, 4005, 4007, 1, GumpButtonType.Reply, 0); + } + } - AddImageTiled( 10, 10, 400, 20, 2624 ); - AddAlphaRegion( 10, 10, 400, 20 ); - - AddHtmlLocalized( 10, 10, 400, 20, 1062051, 30720, false, false ); // Gate Warning - - AddImageTiled( 10, 40, 400, 200, 2624 ); - AddAlphaRegion( 10, 40, 400, 200 ); - - if ( from.Map != Map.Felucca && gate.TargetMap == Map.Felucca && gate.ShowFeluccaWarning ) - AddHtmlLocalized( 10, 40, 400, 200, 1062050, 32512, false, true ); // This Gate goes to Felucca... Continue to enter the gate, Cancel to stay here - else - AddHtmlLocalized( 10, 40, 400, 200, 1062049, 32512, false, true ); // Dost thou wish to step into the moongate? Continue to enter the gate, Cancel to stay here - - AddImageTiled( 10, 250, 400, 20, 2624 ); - AddAlphaRegion( 10, 250, 400, 20 ); - - AddButton( 10, 250, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 250, 170, 20, 1011036, 32767, false, false ); // OKAY - - AddButton( 210, 250, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 240, 250, 170, 20, 1011012, 32767, false, false ); // CANCEL - } - else - { - AddPage( 0 ); - - AddBackground( 0, 0, 420, 400, 5054 ); - AddBackground( 10, 10, 400, 380, 3000 ); - - AddHtml( 20, 40, 380, 60, @"Dost thou wish to step into the moongate? Continue to enter the gate, Cancel to stay here", false, false ); - - AddHtmlLocalized( 55, 110, 290, 20, 1011012, false, false ); // CANCEL - AddButton( 20, 110, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - - AddHtmlLocalized( 55, 140, 290, 40, 1011011, false, false ); // CONTINUE - AddButton( 20, 140, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - } - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Gate.EndConfirmation( m_From ); - } - } -} + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1) + m_Gate.EndConfirmation(m_From); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Misc/PotionKeg.cs b/Scripts/Items/Skill Items/Magical/Misc/PotionKeg.cs index c11ee8b08..9e76afd72 100644 --- a/Scripts/Items/Skill Items/Magical/Misc/PotionKeg.cs +++ b/Scripts/Items/Skill Items/Magical/Misc/PotionKeg.cs @@ -1,340 +1,342 @@ using System; +using Server.Network; namespace Server.Items { - public class PotionKeg : Item - { - private PotionEffect m_Type; - private int m_Held; + public class PotionKeg : Item + { + private int m_Held; + private PotionEffect m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public int Held - { - get => m_Held; - set - { - if ( m_Held != value ) - { - m_Held = value; - UpdateWeight(); - InvalidateProperties(); - } - } - } + [Constructible] + public PotionKeg() : base(0x1940) + { + UpdateWeight(); + } - [CommandProperty( AccessLevel.GameMaster )] - public PotionEffect Type - { - get => m_Type; - set - { - m_Type = value; - InvalidateProperties(); - } - } + public PotionKeg(Serial serial) : base(serial) + { + } - [Constructible] - public PotionKeg() : base( 0x1940 ) - { - UpdateWeight(); - } + [CommandProperty(AccessLevel.GameMaster)] + public int Held + { + get => m_Held; + set + { + if (m_Held != value) + { + m_Held = value; + UpdateWeight(); + InvalidateProperties(); + } + } + } - public virtual void UpdateWeight() - { - int held = Math.Max( 0, Math.Min( m_Held, 100 ) ); + [CommandProperty(AccessLevel.GameMaster)] + public PotionEffect Type + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - Weight = 20 + ((held * 80) / 100); - } + public override int LabelNumber + { + get + { + if (m_Held > 0 && (int)m_Type >= (int)PotionEffect.Conflagration) + return 1072658 + (int)m_Type - (int)PotionEffect.Conflagration; - public PotionKeg( Serial serial ) : base( serial ) - { - } + return m_Held > 0 ? 1041620 + (int)m_Type : 1041641; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public virtual void UpdateWeight() + { + int held = Math.Max(0, Math.Min(m_Held, 100)); - writer.Write( (int) 1 ); // version + Weight = 20 + held * 80 / 100; + } - writer.Write( (int) m_Type ); - writer.Write( (int) m_Held ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(1); // version - int version = reader.ReadInt(); + writer.Write((int)m_Type); + writer.Write(m_Held); + } - switch ( version ) - { - case 1: - case 0: - { - m_Type = (PotionEffect)reader.ReadInt(); - m_Held = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - break; - } - } + int version = reader.ReadInt(); - if ( version < 1 ) - Timer.DelayCall( TimeSpan.Zero, UpdateWeight ); - } + switch (version) + { + case 1: + case 0: + { + m_Type = (PotionEffect)reader.ReadInt(); + m_Held = reader.ReadInt(); - public override int LabelNumber - { - get - { - if ( m_Held > 0 && ( int )m_Type >= ( int )PotionEffect.Conflagration ) - { - return 1072658 + ( int )m_Type - ( int )PotionEffect.Conflagration; - } + break; + } + } - return (m_Held > 0 ? 1041620 + (int)m_Type : 1041641); - } - } + if (version < 1) + Timer.DelayCall(TimeSpan.Zero, UpdateWeight); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - int number; + int number; - if ( m_Held <= 0 ) - number = 502246; // The keg is empty. - else if ( m_Held < 5 ) - number = 502248; // The keg is nearly empty. - else if ( m_Held < 20 ) - number = 502249; // The keg is not very full. - else if ( m_Held < 30 ) - number = 502250; // The keg is about one quarter full. - else if ( m_Held < 40 ) - number = 502251; // The keg is about one third full. - else if ( m_Held < 47 ) - number = 502252; // The keg is almost half full. - else if ( m_Held < 54 ) - number = 502254; // The keg is approximately half full. - else if ( m_Held < 70 ) - number = 502253; // The keg is more than half full. - else if ( m_Held < 80 ) - number = 502255; // The keg is about three quarters full. - else if ( m_Held < 96 ) - number = 502256; // The keg is very full. - else if ( m_Held < 100 ) - number = 502257; // The liquid is almost to the top of the keg. - else - number = 502258; // The keg is completely full. + if (m_Held <= 0) + number = 502246; // The keg is empty. + else if (m_Held < 5) + number = 502248; // The keg is nearly empty. + else if (m_Held < 20) + number = 502249; // The keg is not very full. + else if (m_Held < 30) + number = 502250; // The keg is about one quarter full. + else if (m_Held < 40) + number = 502251; // The keg is about one third full. + else if (m_Held < 47) + number = 502252; // The keg is almost half full. + else if (m_Held < 54) + number = 502254; // The keg is approximately half full. + else if (m_Held < 70) + number = 502253; // The keg is more than half full. + else if (m_Held < 80) + number = 502255; // The keg is about three quarters full. + else if (m_Held < 96) + number = 502256; // The keg is very full. + else if (m_Held < 100) + number = 502257; // The liquid is almost to the top of the keg. + else + number = 502258; // The keg is completely full. - list.Add( number ); - } + list.Add(number); + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - int number; + int number; - if ( m_Held <= 0 ) - number = 502246; // The keg is empty. - else if ( m_Held < 5 ) - number = 502248; // The keg is nearly empty. - else if ( m_Held < 20 ) - number = 502249; // The keg is not very full. - else if ( m_Held < 30 ) - number = 502250; // The keg is about one quarter full. - else if ( m_Held < 40 ) - number = 502251; // The keg is about one third full. - else if ( m_Held < 47 ) - number = 502252; // The keg is almost half full. - else if ( m_Held < 54 ) - number = 502254; // The keg is approximately half full. - else if ( m_Held < 70 ) - number = 502253; // The keg is more than half full. - else if ( m_Held < 80 ) - number = 502255; // The keg is about three quarters full. - else if ( m_Held < 96 ) - number = 502256; // The keg is very full. - else if ( m_Held < 100 ) - number = 502257; // The liquid is almost to the top of the keg. - else - number = 502258; // The keg is completely full. + if (m_Held <= 0) + number = 502246; // The keg is empty. + else if (m_Held < 5) + number = 502248; // The keg is nearly empty. + else if (m_Held < 20) + number = 502249; // The keg is not very full. + else if (m_Held < 30) + number = 502250; // The keg is about one quarter full. + else if (m_Held < 40) + number = 502251; // The keg is about one third full. + else if (m_Held < 47) + number = 502252; // The keg is almost half full. + else if (m_Held < 54) + number = 502254; // The keg is approximately half full. + else if (m_Held < 70) + number = 502253; // The keg is more than half full. + else if (m_Held < 80) + number = 502255; // The keg is about three quarters full. + else if (m_Held < 96) + number = 502256; // The keg is very full. + else if (m_Held < 100) + number = 502257; // The liquid is almost to the top of the keg. + else + number = 502258; // The keg is completely full. - LabelTo( from, number ); - } + LabelTo(from, number); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - if ( m_Held > 0 ) - { - Container pack = from.Backpack; + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + { + if (m_Held > 0) + { + Container pack = from.Backpack; - if ( pack != null && pack.ConsumeTotal( typeof( Bottle ), 1 ) ) - { - from.SendLocalizedMessage( 502242 ); // You pour some of the keg's contents into an empty bottle... + if (pack != null && pack.ConsumeTotal(typeof(Bottle), 1)) + { + from.SendLocalizedMessage(502242); // You pour some of the keg's contents into an empty bottle... - BasePotion pot = FillBottle(); + BasePotion pot = FillBottle(); - if ( pack.TryDropItem( from, pot, false ) ) - { - from.SendLocalizedMessage( 502243 ); // ...and place it into your backpack. - from.PlaySound( 0x240 ); + if (pack.TryDropItem(from, pot, false)) + { + from.SendLocalizedMessage(502243); // ...and place it into your backpack. + from.PlaySound(0x240); - if ( --Held == 0 ) - from.SendLocalizedMessage( 502245 ); // The keg is now empty. - } - else - { - from.SendLocalizedMessage( 502244 ); // ...but there is no room for the bottle in your backpack. - pot.Delete(); - } - } - } - else - { - from.SendLocalizedMessage( 502246 ); // The keg is empty. - } - } - else - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } + if (--Held == 0) + from.SendLocalizedMessage(502245); // The keg is now empty. + } + else + { + from.SendLocalizedMessage(502244); // ...but there is no room for the bottle in your backpack. + pot.Delete(); + } + } + } + else + { + from.SendLocalizedMessage(502246); // The keg is empty. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override bool OnDragDrop( Mobile from, Item item ) - { - if (!(item is BasePotion pot)) - { - from.SendLocalizedMessage( 502232 ); // The keg is not designed to hold that type of object. - return false; - } + public override bool OnDragDrop(Mobile from, Item item) + { + if (!(item is BasePotion pot)) + { + from.SendLocalizedMessage(502232); // The keg is not designed to hold that type of object. + return false; + } - int toHold = Math.Min( 100 - m_Held, pot.Amount ); + int toHold = Math.Min(100 - m_Held, pot.Amount); - if ( toHold <= 0 ) - { - from.SendLocalizedMessage( 502233 ); // The keg will not hold any more! - return false; - } + if (toHold <= 0) + { + from.SendLocalizedMessage(502233); // The keg will not hold any more! + return false; + } - if ( m_Held == 0 ) - { - #region Mondain's Legacy - if ( (int) pot.PotionEffect >= (int) PotionEffect.Invisibility ) - { - from.SendLocalizedMessage( 502232 ); // The keg is not designed to hold that type of object. - return false; - } - #endregion + if (m_Held == 0) + { + #region Mondain's Legacy - if ( GiveBottle( from, toHold ) ) - { - m_Type = pot.PotionEffect; - Held = toHold; + if ((int)pot.PotionEffect >= (int)PotionEffect.Invisibility) + { + from.SendLocalizedMessage(502232); // The keg is not designed to hold that type of object. + return false; + } - from.PlaySound( 0x240 ); + #endregion - from.SendLocalizedMessage( 502237 ); // You place the empty bottle in your backpack. + if (GiveBottle(from, toHold)) + { + m_Type = pot.PotionEffect; + Held = toHold; - pot.Consume( toHold ); + from.PlaySound(0x240); - if ( !pot.Deleted ) - pot.Bounce( from ); + from.SendLocalizedMessage(502237); // You place the empty bottle in your backpack. - return true; - } + pot.Consume(toHold); - from.SendLocalizedMessage( 502238 ); // You don't have room for the empty bottle in your backpack. - return false; - } + if (!pot.Deleted) + pot.Bounce(from); - if ( pot.PotionEffect != m_Type ) - { - from.SendLocalizedMessage( 502236 ); // You decide that it would be a bad idea to mix different types of potions. - return false; - } + return true; + } - if ( GiveBottle( from, toHold ) ) - { - Held += toHold; + from.SendLocalizedMessage(502238); // You don't have room for the empty bottle in your backpack. + return false; + } - from.PlaySound( 0x240 ); + if (pot.PotionEffect != m_Type) + { + from.SendLocalizedMessage( + 502236); // You decide that it would be a bad idea to mix different types of potions. + return false; + } - from.SendLocalizedMessage( 502237 ); // You place the empty bottle in your backpack. + if (GiveBottle(from, toHold)) + { + Held += toHold; - pot.Consume( toHold ); + from.PlaySound(0x240); - if ( !pot.Deleted ) - pot.Bounce( from ); + from.SendLocalizedMessage(502237); // You place the empty bottle in your backpack. - return true; - } + pot.Consume(toHold); - from.SendLocalizedMessage( 502238 ); // You don't have room for the empty bottle in your backpack. - return false; - } + if (!pot.Deleted) + pot.Bounce(from); - public bool GiveBottle( Mobile m, int amount ) - { - Container pack = m.Backpack; + return true; + } - Bottle bottle = new Bottle( amount ); + from.SendLocalizedMessage(502238); // You don't have room for the empty bottle in your backpack. + return false; + } - if ( pack == null || !pack.TryDropItem( m, bottle, false ) ) - { - bottle.Delete(); - return false; - } + public bool GiveBottle(Mobile m, int amount) + { + Container pack = m.Backpack; - return true; - } + Bottle bottle = new Bottle(amount); - public BasePotion FillBottle() - { - switch ( m_Type ) - { - default: - case PotionEffect.Nightsight: return new NightSightPotion(); + if (pack == null || !pack.TryDropItem(m, bottle, false)) + { + bottle.Delete(); + return false; + } - case PotionEffect.CureLesser: return new LesserCurePotion(); - case PotionEffect.Cure: return new CurePotion(); - case PotionEffect.CureGreater: return new GreaterCurePotion(); + return true; + } - case PotionEffect.Agility: return new AgilityPotion(); - case PotionEffect.AgilityGreater: return new GreaterAgilityPotion(); + public BasePotion FillBottle() + { + switch (m_Type) + { + default: + case PotionEffect.Nightsight: return new NightSightPotion(); - case PotionEffect.Strength: return new StrengthPotion(); - case PotionEffect.StrengthGreater: return new GreaterStrengthPotion(); + case PotionEffect.CureLesser: return new LesserCurePotion(); + case PotionEffect.Cure: return new CurePotion(); + case PotionEffect.CureGreater: return new GreaterCurePotion(); - case PotionEffect.PoisonLesser: return new LesserPoisonPotion(); - case PotionEffect.Poison: return new PoisonPotion(); - case PotionEffect.PoisonGreater: return new GreaterPoisonPotion(); - case PotionEffect.PoisonDeadly: return new DeadlyPoisonPotion(); + case PotionEffect.Agility: return new AgilityPotion(); + case PotionEffect.AgilityGreater: return new GreaterAgilityPotion(); - case PotionEffect.Refresh: return new RefreshPotion(); - case PotionEffect.RefreshTotal: return new TotalRefreshPotion(); + case PotionEffect.Strength: return new StrengthPotion(); + case PotionEffect.StrengthGreater: return new GreaterStrengthPotion(); - case PotionEffect.HealLesser: return new LesserHealPotion(); - case PotionEffect.Heal: return new HealPotion(); - case PotionEffect.HealGreater: return new GreaterHealPotion(); + case PotionEffect.PoisonLesser: return new LesserPoisonPotion(); + case PotionEffect.Poison: return new PoisonPotion(); + case PotionEffect.PoisonGreater: return new GreaterPoisonPotion(); + case PotionEffect.PoisonDeadly: return new DeadlyPoisonPotion(); - case PotionEffect.ExplosionLesser: return new LesserExplosionPotion(); - case PotionEffect.Explosion: return new ExplosionPotion(); - case PotionEffect.ExplosionGreater: return new GreaterExplosionPotion(); + case PotionEffect.Refresh: return new RefreshPotion(); + case PotionEffect.RefreshTotal: return new TotalRefreshPotion(); - case PotionEffect.Conflagration: return new ConflagrationPotion(); - case PotionEffect.ConflagrationGreater: return new GreaterConflagrationPotion(); + case PotionEffect.HealLesser: return new LesserHealPotion(); + case PotionEffect.Heal: return new HealPotion(); + case PotionEffect.HealGreater: return new GreaterHealPotion(); - case PotionEffect.ConfusionBlast: return new ConfusionBlastPotion(); - case PotionEffect.ConfusionBlastGreater: return new GreaterConfusionBlastPotion(); - } - } + case PotionEffect.ExplosionLesser: return new LesserExplosionPotion(); + case PotionEffect.Explosion: return new ExplosionPotion(); + case PotionEffect.ExplosionGreater: return new GreaterExplosionPotion(); - public static void Initialize() - { - TileData.ItemTable[0x1940].Height = 4; - } - } -} + case PotionEffect.Conflagration: return new ConflagrationPotion(); + case PotionEffect.ConflagrationGreater: return new GreaterConflagrationPotion(); + + case PotionEffect.ConfusionBlast: return new ConfusionBlastPotion(); + case PotionEffect.ConfusionBlastGreater: return new GreaterConfusionBlastPotion(); + } + } + + public static void Initialize() + { + TileData.ItemTable[0x1940].Height = 4; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Misc/RecallRune.cs b/Scripts/Items/Skill Items/Magical/Misc/RecallRune.cs index 33f5e12c8..844c3c2d3 100644 --- a/Scripts/Items/Skill Items/Magical/Misc/RecallRune.cs +++ b/Scripts/Items/Skill Items/Magical/Misc/RecallRune.cs @@ -1,300 +1,308 @@ -using System; -using Server.Prompts; using Server.Multis; +using Server.Prompts; using Server.Regions; namespace Server.Items { - [FlippableAttribute( 0x1f14, 0x1f15, 0x1f16, 0x1f17 )] - public class RecallRune : Item - { - private string m_Description; - private bool m_Marked; - private Map m_TargetMap; - private BaseHouse m_House; + [Flippable(0x1f14, 0x1f15, 0x1f16, 0x1f17)] + public class RecallRune : Item + { + private const string RuneFormat = "a recall rune for {0}"; + private string m_Description; + private BaseHouse m_House; + private bool m_Marked; + private Map m_TargetMap; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [Constructible] + public RecallRune() : base(0x1F14) + { + Weight = 1.0; + CalculateHue(); + } - if ( m_House != null && !m_House.Deleted ) - { - writer.Write( (int) 1 ); // version + public RecallRune(Serial serial) : base(serial) + { + } - writer.Write( (Item) m_House ); - } - else - { - writer.Write( (int) 0 ); // version - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public BaseHouse House + { + get + { + if (m_House != null && m_House.Deleted) + House = null; - writer.Write( (string) m_Description ); - writer.Write( (bool) m_Marked ); - writer.Write( (Point3D) Target ); - writer.Write( (Map) m_TargetMap ); - } + return m_House; + } + set + { + m_House = value; + CalculateHue(); + InvalidateProperties(); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public string Description + { + get => m_Description; + set + { + m_Description = value; + InvalidateProperties(); + } + } - int version = reader.ReadInt(); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public bool Marked + { + get => m_Marked; + set + { + if (m_Marked != value) + { + m_Marked = value; + CalculateHue(); + InvalidateProperties(); + } + } + } - switch ( version ) - { - case 1: - { - m_House = reader.ReadItem() as BaseHouse; - goto case 0; - } - case 0: - { - m_Description = reader.ReadString(); - m_Marked = reader.ReadBool(); - Target = reader.ReadPoint3D(); - m_TargetMap = reader.ReadMap(); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Point3D Target{ get; set; } - CalculateHue(); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Map TargetMap + { + get => m_TargetMap; + set + { + if (m_TargetMap != value) + { + m_TargetMap = value; + CalculateHue(); + InvalidateProperties(); + } + } + } - break; - } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public BaseHouse House - { - get - { - if ( m_House != null && m_House.Deleted ) - House = null; + if (m_House != null && !m_House.Deleted) + { + writer.Write(1); // version - return m_House; - } - set{ m_House = value; CalculateHue(); InvalidateProperties(); } - } + writer.Write(m_House); + } + else + { + writer.Write(0); // version + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public string Description - { - get => m_Description; - set - { - m_Description = value; - InvalidateProperties(); - } - } + writer.Write(m_Description); + writer.Write(m_Marked); + writer.Write(Target); + writer.Write(m_TargetMap); + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public bool Marked - { - get => m_Marked; - set - { - if ( m_Marked != value ) - { - m_Marked = value; - CalculateHue(); - InvalidateProperties(); - } - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Point3D Target { get; set; } + int version = reader.ReadInt(); - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Map TargetMap - { - get => m_TargetMap; - set - { - if ( m_TargetMap != value ) - { - m_TargetMap = value; - CalculateHue(); - InvalidateProperties(); - } - } - } + switch (version) + { + case 1: + { + m_House = reader.ReadItem() as BaseHouse; + goto case 0; + } + case 0: + { + m_Description = reader.ReadString(); + m_Marked = reader.ReadBool(); + Target = reader.ReadPoint3D(); + m_TargetMap = reader.ReadMap(); - private void CalculateHue() - { - if ( !m_Marked ) - Hue = 0; - else if ( m_TargetMap == Map.Trammel ) - Hue = (House != null ? 0x47F : 50); - else if ( m_TargetMap == Map.Felucca ) - Hue = (House != null ? 0x66D : 0); - else if ( m_TargetMap == Map.Ilshenar ) - Hue = (House != null ? 0x55F : 1102); - else if ( m_TargetMap == Map.Malas ) - Hue = (House != null ? 0x55F : 1102); - else if ( m_TargetMap == Map.Tokuno ) - Hue = (House != null ? 0x47F : 1154); - } + CalculateHue(); - public void Mark( Mobile m ) - { - m_Marked = true; + break; + } + } + } - bool setDesc = false; - if ( Core.AOS ) - { - m_House = BaseHouse.FindHouseAt( m ); + private void CalculateHue() + { + if (!m_Marked) + Hue = 0; + else if (m_TargetMap == Map.Trammel) + Hue = House != null ? 0x47F : 50; + else if (m_TargetMap == Map.Felucca) + Hue = House != null ? 0x66D : 0; + else if (m_TargetMap == Map.Ilshenar) + Hue = House != null ? 0x55F : 1102; + else if (m_TargetMap == Map.Malas) + Hue = House != null ? 0x55F : 1102; + else if (m_TargetMap == Map.Tokuno) + Hue = House != null ? 0x47F : 1154; + } - if ( m_House == null ) - { - Target = m.Location; - m_TargetMap = m.Map; - } - else - { - HouseSign sign = m_House.Sign; + public void Mark(Mobile m) + { + m_Marked = true; - if ( sign != null ) - m_Description = sign.Name; - else - m_Description = null; + bool setDesc = false; + if (Core.AOS) + { + m_House = BaseHouse.FindHouseAt(m); - if ( m_Description == null || (m_Description = m_Description.Trim()).Length == 0 ) - m_Description = "an unnamed house"; + if (m_House == null) + { + Target = m.Location; + m_TargetMap = m.Map; + } + else + { + HouseSign sign = m_House.Sign; - setDesc = true; + if (sign != null) + m_Description = sign.Name; + else + m_Description = null; - int x = m_House.BanLocation.X; - int y = m_House.BanLocation.Y + 2; - int z = m_House.BanLocation.Z; + if (m_Description == null || (m_Description = m_Description.Trim()).Length == 0) + m_Description = "an unnamed house"; - Map map = m_House.Map; + setDesc = true; - if ( map != null && !map.CanFit( x, y, z, 16, false, false ) ) - z = map.GetAverageZ( x, y ); + int x = m_House.BanLocation.X; + int y = m_House.BanLocation.Y + 2; + int z = m_House.BanLocation.Z; - Target = new Point3D( x, y, z ); - m_TargetMap = map; - } - } - else - { - m_House = null; - Target = m.Location; - m_TargetMap = m.Map; - } + Map map = m_House.Map; - if ( !setDesc ) - m_Description = BaseRegion.GetRuneNameFor( Region.Find( Target, m_TargetMap ) ); + if (map != null && !map.CanFit(x, y, z, 16, false, false)) + z = map.GetAverageZ(x, y); - CalculateHue(); - InvalidateProperties(); - } + Target = new Point3D(x, y, z); + m_TargetMap = map; + } + } + else + { + m_House = null; + Target = m.Location; + m_TargetMap = m.Map; + } - private const string RuneFormat = "a recall rune for {0}"; + if (!setDesc) + m_Description = BaseRegion.GetRuneNameFor(Region.Find(Target, m_TargetMap)); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + CalculateHue(); + InvalidateProperties(); + } - if ( m_Marked ) - { - string desc; + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( (desc = m_Description) == null || (desc = desc.Trim()).Length == 0 ) - desc = "an unknown location"; + if (m_Marked) + { + string desc; - if ( m_TargetMap == Map.Tokuno ) - list.Add( (House != null ? 1063260 : 1063259), RuneFormat, desc ); // ~1_val~ (Tokuno Islands)[(House)] - else if ( m_TargetMap == Map.Malas ) - list.Add( (House != null ? 1062454 : 1060804), RuneFormat, desc ); // ~1_val~ (Malas)[(House)] - else if ( m_TargetMap == Map.Felucca ) - list.Add( (House != null ? 1062452 : 1060805), RuneFormat, desc ); // ~1_val~ (Felucca)[(House)] - else if ( m_TargetMap == Map.Trammel ) - list.Add( (House != null ? 1062453 : 1060806), RuneFormat, desc ); // ~1_val~ (Trammel)[(House)] - else - list.Add( (House != null ? "{0} ({1})(House)" : "{0} ({1})"), string.Format( RuneFormat, desc ), m_TargetMap ); - } - } + if ((desc = m_Description) == null || (desc = desc.Trim()).Length == 0) + desc = "an unknown location"; - public override void OnSingleClick( Mobile from ) - { - if ( m_Marked ) - { - string desc; + if (m_TargetMap == Map.Tokuno) + list.Add(House != null ? 1063260 : 1063259, RuneFormat, desc); // ~1_val~ (Tokuno Islands)[(House)] + else if (m_TargetMap == Map.Malas) + list.Add(House != null ? 1062454 : 1060804, RuneFormat, desc); // ~1_val~ (Malas)[(House)] + else if (m_TargetMap == Map.Felucca) + list.Add(House != null ? 1062452 : 1060805, RuneFormat, desc); // ~1_val~ (Felucca)[(House)] + else if (m_TargetMap == Map.Trammel) + list.Add(House != null ? 1062453 : 1060806, RuneFormat, desc); // ~1_val~ (Trammel)[(House)] + else + list.Add(House != null ? "{0} ({1})(House)" : "{0} ({1})", string.Format(RuneFormat, desc), m_TargetMap); + } + } - if ( (desc = m_Description) == null || (desc = desc.Trim()).Length == 0 ) - desc = "an unknown location"; + public override void OnSingleClick(Mobile from) + { + if (m_Marked) + { + string desc; - if ( m_TargetMap == Map.Tokuno ) - LabelTo( from, (House != null ? 1063260 : 1063259), string.Format( RuneFormat, desc ) ); // ~1_val~ (Tokuno Islands)[(House)] - else if ( m_TargetMap == Map.Malas ) - LabelTo( from, (House != null ? 1062454 : 1060804), string.Format( RuneFormat, desc ) ); // ~1_val~ (Malas)[(House)] - else if ( m_TargetMap == Map.Felucca ) - LabelTo( from, (House != null ? 1062452 : 1060805), string.Format( RuneFormat, desc ) ); // ~1_val~ (Felucca)[(House)] - else if ( m_TargetMap == Map.Trammel ) - LabelTo( from, (House != null ? 1062453 : 1060806), string.Format( RuneFormat, desc ) ); // ~1_val~ (Trammel)[(House)] - else - LabelTo( from, (House != null ? "{0} ({1})(House)" : "{0} ({1})"), string.Format( RuneFormat, desc ), m_TargetMap ); - } - else - { - LabelTo( from, "an unmarked recall rune" ); - } - } + if ((desc = m_Description) == null || (desc = desc.Trim()).Length == 0) + desc = "an unknown location"; - public override void OnDoubleClick( Mobile from ) - { - int number; + if (m_TargetMap == Map.Tokuno) + LabelTo(from, House != null ? 1063260 : 1063259, + string.Format(RuneFormat, desc)); // ~1_val~ (Tokuno Islands)[(House)] + else if (m_TargetMap == Map.Malas) + LabelTo(from, House != null ? 1062454 : 1060804, + string.Format(RuneFormat, desc)); // ~1_val~ (Malas)[(House)] + else if (m_TargetMap == Map.Felucca) + LabelTo(from, House != null ? 1062452 : 1060805, + string.Format(RuneFormat, desc)); // ~1_val~ (Felucca)[(House)] + else if (m_TargetMap == Map.Trammel) + LabelTo(from, House != null ? 1062453 : 1060806, + string.Format(RuneFormat, desc)); // ~1_val~ (Trammel)[(House)] + else + LabelTo(from, House != null ? "{0} ({1})(House)" : "{0} ({1})", string.Format(RuneFormat, desc), + m_TargetMap); + } + else + { + LabelTo(from, "an unmarked recall rune"); + } + } - if ( !IsChildOf( from.Backpack ) ) - { - number = 1042001; // That must be in your pack for you to use it. - } - else if ( House != null ) - { - number = 1062399; // You cannot edit the description for this rune. - } - else if ( m_Marked ) - { - number = 501804; // Please enter a description for this marked object. + public override void OnDoubleClick(Mobile from) + { + int number; - from.Prompt = new RenamePrompt( this ); - } - else - { - number = 501805; // That rune is not yet marked. - } + if (!IsChildOf(from.Backpack)) + { + number = 1042001; // That must be in your pack for you to use it. + } + else if (House != null) + { + number = 1062399; // You cannot edit the description for this rune. + } + else if (m_Marked) + { + number = 501804; // Please enter a description for this marked object. - from.SendLocalizedMessage( number ); - } + from.Prompt = new RenamePrompt(this); + } + else + { + number = 501805; // That rune is not yet marked. + } - private class RenamePrompt : Prompt - { - private RecallRune m_Rune; + from.SendLocalizedMessage(number); + } - public RenamePrompt( RecallRune rune ) - { - m_Rune = rune; - } + private class RenamePrompt : Prompt + { + private RecallRune m_Rune; - public override void OnResponse( Mobile from, string text ) - { - if ( m_Rune.House == null && m_Rune.Marked ) - { - m_Rune.Description = text; - from.SendLocalizedMessage( 1010474 ); // The etching on the rune has been changed. - } - } - } + public RenamePrompt(RecallRune rune) + { + m_Rune = rune; + } - [Constructible] - public RecallRune() : base( 0x1F14 ) - { - Weight = 1.0; - CalculateHue(); - } - - public RecallRune( Serial serial ) : base( serial ) - { - } - } -} + public override void OnResponse(Mobile from, string text) + { + if (m_Rune.House == null && m_Rune.Marked) + { + m_Rune.Description = text; + from.SendLocalizedMessage(1010474); // The etching on the rune has been changed. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/MysticSpellbook.cs b/Scripts/Items/Skill Items/Magical/MysticSpellbook.cs index 340720c64..636028726 100644 --- a/Scripts/Items/Skill Items/Magical/MysticSpellbook.cs +++ b/Scripts/Items/Skill Items/Magical/MysticSpellbook.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class MysticSpellbook : Spellbook - { - public override SpellbookType SpellbookType => SpellbookType.Mystic; + public class MysticSpellbook : Spellbook + { + [Constructible] + public MysticSpellbook() + : this((ulong)0) + { + } - public override int BookOffset => 677; - public override int BookCount => 16; + [Constructible] + public MysticSpellbook(ulong content) + : base(content, 0x2D9D) + { + Layer = Layer.OneHanded; + } - [Constructible] - public MysticSpellbook() - : this( (ulong) 0 ) - { - } + public MysticSpellbook(Serial serial) + : base(serial) + { + } - [Constructible] - public MysticSpellbook( ulong content ) - : base( content, 0x2D9D ) - { - Layer = Layer.OneHanded; - } + public override SpellbookType SpellbookType => SpellbookType.Mystic; - public MysticSpellbook( Serial serial ) - : base( serial ) - { - } + public override int BookOffset => 677; + public override int BookCount => 16; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/NecromancerSpellbook.cs b/Scripts/Items/Skill Items/Magical/NecromancerSpellbook.cs index cc03275e3..6f8569a2d 100644 --- a/Scripts/Items/Skill Items/Magical/NecromancerSpellbook.cs +++ b/Scripts/Items/Skill Items/Magical/NecromancerSpellbook.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public class NecromancerSpellbook : Spellbook - { - public override SpellbookType SpellbookType => SpellbookType.Necromancer; - public override int BookOffset => 100; - public override int BookCount => ((Core.SE) ? 17 : 16); + public class NecromancerSpellbook : Spellbook + { + [Constructible] + public NecromancerSpellbook() : this((ulong)0) + { + } - [Constructible] - public NecromancerSpellbook() : this( (ulong)0 ) - { - } + [Constructible] + public NecromancerSpellbook(ulong content) : base(content, 0x2253) + { + Layer = Core.ML ? Layer.OneHanded : Layer.Invalid; + } - [Constructible] - public NecromancerSpellbook( ulong content ) : base( content, 0x2253 ) - { - Layer = (Core.ML ? Layer.OneHanded : Layer.Invalid); - } + public NecromancerSpellbook(Serial serial) : base(serial) + { + } - public NecromancerSpellbook( Serial serial ) : base( serial ) - { - } + public override SpellbookType SpellbookType => SpellbookType.Necromancer; + public override int BookOffset => 100; + public override int BookCount => Core.SE ? 17 : 16; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && Core.ML ) - Layer = Layer.OneHanded; - } - } -} + if (version == 0 && Core.ML) + Layer = Layer.OneHanded; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/AgilityPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/AgilityPotion.cs index 0f24f22fa..ad4044678 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/AgilityPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/AgilityPotion.cs @@ -2,32 +2,32 @@ using System; namespace Server.Items { - public class AgilityPotion : BaseAgilityPotion - { - public override int DexOffset => 10; - public override TimeSpan Duration => TimeSpan.FromMinutes( 2.0 ); + public class AgilityPotion : BaseAgilityPotion + { + [Constructible] + public AgilityPotion() : base(PotionEffect.Agility) + { + } - [Constructible] - public AgilityPotion() : base( PotionEffect.Agility ) - { - } + public AgilityPotion(Serial serial) : base(serial) + { + } - public AgilityPotion( Serial serial ) : base( serial ) - { - } + public override int DexOffset => 10; + public override TimeSpan Duration => TimeSpan.FromMinutes(2.0); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/BaseAgilityPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/BaseAgilityPotion.cs index 70cc5e50f..3ff4f8189 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/BaseAgilityPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/BaseAgilityPotion.cs @@ -1,57 +1,59 @@ using System; +using Server.Engines.ConPVP; +using Server.Spells; namespace Server.Items { - public abstract class BaseAgilityPotion : BasePotion - { - public abstract int DexOffset{ get; } - public abstract TimeSpan Duration{ get; } + public abstract class BaseAgilityPotion : BasePotion + { + public BaseAgilityPotion(PotionEffect effect) : base(0xF08, effect) + { + } - public BaseAgilityPotion( PotionEffect effect ) : base( 0xF08, effect ) - { - } + public BaseAgilityPotion(Serial serial) : base(serial) + { + } - public BaseAgilityPotion( Serial serial ) : base( serial ) - { - } + public abstract int DexOffset{ get; } + public abstract TimeSpan Duration{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public bool DoAgility( Mobile from ) - { - // TODO: Verify scaled; is it offset, duration, or both? - if ( Spells.SpellHelper.AddStatOffset( from, StatType.Dex, Scale( from, DexOffset ), Duration ) ) - { - from.FixedEffect( 0x375A, 10, 15 ); - from.PlaySound( 0x1E7 ); - return true; - } + public bool DoAgility(Mobile from) + { + // TODO: Verify scaled; is it offset, duration, or both? + if (SpellHelper.AddStatOffset(from, StatType.Dex, Scale(from, DexOffset), Duration)) + { + from.FixedEffect(0x375A, 10, 15); + from.PlaySound(0x1E7); + return true; + } - from.SendLocalizedMessage( 502173 ); // You are already under a similar effect. - return false; - } + from.SendLocalizedMessage(502173); // You are already under a similar effect. + return false; + } - public override void Drink( Mobile from ) - { - if ( DoAgility( from ) ) - { - PlayDrinkEffect( from ); + public override void Drink(Mobile from) + { + if (DoAgility(from)) + { + PlayDrinkEffect(from); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); - } - } - } + if (!DuelContext.IsFreeConsume(from)) + Consume(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/GreaterAgilityPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/GreaterAgilityPotion.cs index 9bb52dd4a..2e0cfa061 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/GreaterAgilityPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Agility Potions/GreaterAgilityPotion.cs @@ -2,32 +2,32 @@ using System; namespace Server.Items { - public class GreaterAgilityPotion : BaseAgilityPotion - { - public override int DexOffset => 20; - public override TimeSpan Duration => TimeSpan.FromMinutes( 2.0 ); + public class GreaterAgilityPotion : BaseAgilityPotion + { + [Constructible] + public GreaterAgilityPotion() : base(PotionEffect.AgilityGreater) + { + } - [Constructible] - public GreaterAgilityPotion() : base( PotionEffect.AgilityGreater ) - { - } + public GreaterAgilityPotion(Serial serial) : base(serial) + { + } - public GreaterAgilityPotion( Serial serial ) : base( serial ) - { - } + public override int DexOffset => 20; + public override TimeSpan Duration => TimeSpan.FromMinutes(2.0); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/BasePotion.cs b/Scripts/Items/Skill Items/Magical/Potions/BasePotion.cs index e32999fe4..34f4b6980 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/BasePotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/BasePotion.cs @@ -1,265 +1,265 @@ using System; -using Server.Engines.Craft; using System.Collections.Generic; +using Server.Engines.ConPVP; +using Server.Engines.Craft; namespace Server.Items { - public enum PotionEffect - { - Nightsight, - CureLesser, - Cure, - CureGreater, - Agility, - AgilityGreater, - Strength, - StrengthGreater, - PoisonLesser, - Poison, - PoisonGreater, - PoisonDeadly, - Refresh, - RefreshTotal, - HealLesser, - Heal, - HealGreater, - ExplosionLesser, - Explosion, - ExplosionGreater, - Conflagration, - ConflagrationGreater, - MaskOfDeath, // Mask of Death is not available in OSI but does exist in cliloc files - MaskOfDeathGreater, // included in enumeration for compatibility if later enabled by OSI - ConfusionBlast, - ConfusionBlastGreater, - Invisibility, - Parasitic, - Darkglow, - } + public enum PotionEffect + { + Nightsight, + CureLesser, + Cure, + CureGreater, + Agility, + AgilityGreater, + Strength, + StrengthGreater, + PoisonLesser, + Poison, + PoisonGreater, + PoisonDeadly, + Refresh, + RefreshTotal, + HealLesser, + Heal, + HealGreater, + ExplosionLesser, + Explosion, + ExplosionGreater, + Conflagration, + ConflagrationGreater, + MaskOfDeath, // Mask of Death is not available in OSI but does exist in cliloc files + MaskOfDeathGreater, // included in enumeration for compatibility if later enabled by OSI + ConfusionBlast, + ConfusionBlastGreater, + Invisibility, + Parasitic, + Darkglow + } - public abstract class BasePotion : Item, ICraftable, ICommodity - { - private PotionEffect m_PotionEffect; + public abstract class BasePotion : Item, ICraftable, ICommodity + { + private PotionEffect m_PotionEffect; - public PotionEffect PotionEffect - { - get => m_PotionEffect; - set - { - m_PotionEffect = value; - InvalidateProperties(); - } - } + public BasePotion(int itemID, PotionEffect effect) : base(itemID) + { + m_PotionEffect = effect; - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => (Core.ML); + Stackable = Core.ML; + Weight = 1.0; + } - public override int LabelNumber => 1041314 + (int)m_PotionEffect; + public BasePotion(Serial serial) : base(serial) + { + } - public BasePotion( int itemID, PotionEffect effect ) : base( itemID ) - { - m_PotionEffect = effect; + public PotionEffect PotionEffect + { + get => m_PotionEffect; + set + { + m_PotionEffect = value; + InvalidateProperties(); + } + } - Stackable = Core.ML; - Weight = 1.0; - } + public override int LabelNumber => 1041314 + (int)m_PotionEffect; - public BasePotion( Serial serial ) : base( serial ) - { - } + public virtual bool RequireFreeHand => true; - public virtual bool RequireFreeHand => true; + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => Core.ML; - public static bool HasFreeHand( Mobile m ) - { - Item handOne = m.FindItemOnLayer( Layer.OneHanded ); - Item handTwo = m.FindItemOnLayer( Layer.TwoHanded ); + #region ICraftable Members - if ( handTwo is BaseWeapon ) - handOne = handTwo; + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + if (craftSystem is DefAlchemy) + { + Container pack = from.Backpack; - if ( handTwo is BaseRanged ranged && ranged.Balanced ) - return true; + if (pack != null) + { + if ((int)PotionEffect >= (int)PotionEffect.Invisibility) + return 1; - return ( handOne == null || handTwo == null ); - } + List kegs = pack.FindItemsByType(); - public override void OnDoubleClick( Mobile from ) - { - if ( !Movable ) - return; + for (int i = 0; i < kegs.Count; ++i) + { + PotionKeg keg = kegs[i]; - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - if (!RequireFreeHand || HasFreeHand(from)) - { - if (this is BaseExplosionPotion && Amount > 1) - { - BasePotion pot = (BasePotion)Activator.CreateInstance(GetType()); + if (keg == null) + continue; - if (pot != null) - { - Amount--; + if (keg.Held <= 0 || keg.Held >= 100) + continue; - if (from.Backpack != null && !from.Backpack.Deleted) - { - from.Backpack.DropItem(pot); - } - else - { - pot.MoveToWorld(from.Location, from.Map); - } - pot.Drink( from ); - } - } - else - { - Drink( from ); - } - } - else - { - from.SendLocalizedMessage(502172); // You must have a free hand to drink a potion. - } - } - else - { - from.SendLocalizedMessage( 502138 ); // That is too far away for you to use - } - } + if (keg.Type != PotionEffect) + continue; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + ++keg.Held; - writer.Write( (int) 1 ); // version + Consume(); + from.AddToBackpack(new Bottle()); - writer.Write( (int) m_PotionEffect ); - } + return -1; // signal placed in keg + } + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + return 1; + } - int version = reader.ReadInt(); + #endregion - switch ( version ) - { - case 1: - case 0: - { - m_PotionEffect = (PotionEffect)reader.ReadInt(); - break; - } - } + public static bool HasFreeHand(Mobile m) + { + Item handOne = m.FindItemOnLayer(Layer.OneHanded); + Item handTwo = m.FindItemOnLayer(Layer.TwoHanded); - if ( version == 0 ) - Stackable = Core.ML; - } + if (handTwo is BaseWeapon) + handOne = handTwo; - public abstract void Drink( Mobile from ); + if (handTwo is BaseRanged ranged && ranged.Balanced) + return true; - public static void PlayDrinkEffect( Mobile m ) - { - m.RevealingAction(); + return handOne == null || handTwo == null; + } - m.PlaySound( 0x2D6 ); + public override void OnDoubleClick(Mobile from) + { + if (!Movable) + return; - #region Dueling - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( m ) ) - m.AddToBackpack( new Bottle() ); - #endregion + if (from.InRange(GetWorldLocation(), 1)) + { + if (!RequireFreeHand || HasFreeHand(from)) + { + if (this is BaseExplosionPotion && Amount > 1) + { + BasePotion pot = (BasePotion)Activator.CreateInstance(GetType()); - if ( m.Body.IsHuman && !m.Mounted ) - m.Animate( 34, 5, 1, true, false, 0 ); - } + if (pot != null) + { + Amount--; - public static int EnhancePotions( Mobile m ) - { - int EP = AosAttributes.GetValue( m, AosAttribute.EnhancePotions ); - int skillBonus = m.Skills.Alchemy.Fixed / 330 * 10; + if (from.Backpack != null && !from.Backpack.Deleted) + from.Backpack.DropItem(pot); + else + pot.MoveToWorld(from.Location, from.Map); + pot.Drink(from); + } + } + else + { + Drink(from); + } + } + else + { + from.SendLocalizedMessage(502172); // You must have a free hand to drink a potion. + } + } + else + { + from.SendLocalizedMessage(502138); // That is too far away for you to use + } + } - if ( Core.ML && EP > 50 && m.AccessLevel <= AccessLevel.Player ) - EP = 50; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return ( EP + skillBonus ); - } + writer.Write(1); // version - public static TimeSpan Scale( Mobile m, TimeSpan v ) - { - if ( !Core.AOS ) - return v; + writer.Write((int)m_PotionEffect); + } - double scalar = 1.0 + ( 0.01 * EnhancePotions( m ) ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return TimeSpan.FromSeconds( v.TotalSeconds * scalar ); - } + int version = reader.ReadInt(); - public static double Scale( Mobile m, double v ) - { - if ( !Core.AOS ) - return v; + switch (version) + { + case 1: + case 0: + { + m_PotionEffect = (PotionEffect)reader.ReadInt(); + break; + } + } - double scalar = 1.0 + ( 0.01 * EnhancePotions( m ) ); + if (version == 0) + Stackable = Core.ML; + } - return v * scalar; - } + public abstract void Drink(Mobile from); - public static int Scale( Mobile m, int v ) - { - if ( !Core.AOS ) - return v; + public static void PlayDrinkEffect(Mobile m) + { + m.RevealingAction(); - return AOS.Scale( v, 100 + EnhancePotions( m ) ); - } + m.PlaySound(0x2D6); - public override bool StackWith( Mobile from, Item dropped, bool playSound ) - { - return dropped is BasePotion potion && potion.m_PotionEffect == m_PotionEffect && - base.StackWith(from, potion, playSound); - } + #region Dueling - #region ICraftable Members + if (!DuelContext.IsFreeConsume(m)) + m.AddToBackpack(new Bottle()); - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - if ( craftSystem is DefAlchemy ) - { - Container pack = from.Backpack; + #endregion - if ( pack != null ) - { - if ( (int) PotionEffect >= (int) PotionEffect.Invisibility ) - return 1; + if (m.Body.IsHuman && !m.Mounted) + m.Animate(34, 5, 1, true, false, 0); + } - List kegs = pack.FindItemsByType(); + public static int EnhancePotions(Mobile m) + { + int EP = AosAttributes.GetValue(m, AosAttribute.EnhancePotions); + int skillBonus = m.Skills.Alchemy.Fixed / 330 * 10; - for ( int i = 0; i < kegs.Count; ++i ) - { - PotionKeg keg = kegs[i]; + if (Core.ML && EP > 50 && m.AccessLevel <= AccessLevel.Player) + EP = 50; - if ( keg == null ) - continue; + return EP + skillBonus; + } - if ( keg.Held <= 0 || keg.Held >= 100 ) - continue; + public static TimeSpan Scale(Mobile m, TimeSpan v) + { + if (!Core.AOS) + return v; - if ( keg.Type != PotionEffect ) - continue; + double scalar = 1.0 + 0.01 * EnhancePotions(m); - ++keg.Held; + return TimeSpan.FromSeconds(v.TotalSeconds * scalar); + } - Consume(); - from.AddToBackpack( new Bottle() ); + public static double Scale(Mobile m, double v) + { + if (!Core.AOS) + return v; - return -1; // signal placed in keg - } - } - } + double scalar = 1.0 + 0.01 * EnhancePotions(m); - return 1; - } + return v * scalar; + } - #endregion - } -} + public static int Scale(Mobile m, int v) + { + if (!Core.AOS) + return v; + + return AOS.Scale(v, 100 + EnhancePotions(m)); + } + + public override bool StackWith(Mobile from, Item dropped, bool playSound) + { + return dropped is BasePotion potion && potion.m_PotionEffect == m_PotionEffect && + base.StackWith(from, potion, playSound); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/BaseConflagrationPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/BaseConflagrationPotion.cs index f3a15bbad..c15fd916f 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/BaseConflagrationPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/BaseConflagrationPotion.cs @@ -1,325 +1,330 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Targeting; using Server.Spells; +using Server.Targeting; namespace Server.Items { - public abstract class BaseConflagrationPotion : BasePotion - { - public abstract int MinDamage{ get; } - public abstract int MaxDamage{ get; } + public abstract class BaseConflagrationPotion : BasePotion + { + private List m_Users = new List(); - public override bool RequireFreeHand => false; + public BaseConflagrationPotion(PotionEffect effect) : base(0xF06, effect) + { + Hue = 0x489; + } - public BaseConflagrationPotion( PotionEffect effect ) : base( 0xF06, effect ) - { - Hue = 0x489; - } + public BaseConflagrationPotion(Serial serial) : base(serial) + { + } - public BaseConflagrationPotion( Serial serial ) : base( serial ) - { - } + public abstract int MinDamage{ get; } + public abstract int MaxDamage{ get; } - public override void Drink( Mobile from ) - { - if ( Core.AOS && (from.Paralyzed || from.Frozen || (from.Spell != null && from.Spell.IsCasting)) ) - { - from.SendLocalizedMessage( 1062725 ); // You can not use that potion while paralyzed. - return; - } - - int delay = GetDelay( from ); - - if ( delay > 0 ) - { - from.SendLocalizedMessage( 1072529, $"{delay}\t{(delay > 1 ? "seconds." : "second.")}"); // You cannot use that for another ~1_NUM~ ~2_TIMEUNITS~ - return; - } - - if ( from.Target is ThrowTarget targ && targ.Potion == this ) - return; - - from.RevealingAction(); - - if ( !m_Users.Contains( from ) ) - m_Users.Add( from ); - - from.Target = new ThrowTarget( this ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool RequireFreeHand => false; - int version = reader.ReadInt(); - } + public override void Drink(Mobile from) + { + if (Core.AOS && (from.Paralyzed || from.Frozen || from.Spell != null && from.Spell.IsCasting)) + { + from.SendLocalizedMessage(1062725); // You can not use that potion while paralyzed. + return; + } - private List m_Users = new List(); + int delay = GetDelay(from); - public void Explode_Callback( object state ) - { - object[] states = (object[]) state; + if (delay > 0) + { + from.SendLocalizedMessage(1072529, + $"{delay}\t{(delay > 1 ? "seconds." : "second.")}"); // You cannot use that for another ~1_NUM~ ~2_TIMEUNITS~ + return; + } - Explode( (Mobile) states[ 0 ], (Point3D) states[ 1 ], (Map) states[ 2 ] ); - } + if (from.Target is ThrowTarget targ && targ.Potion == this) + return; - public virtual void Explode( Mobile from, Point3D loc, Map map ) - { - if ( Deleted || map == null ) - return; - - Consume(); - - // Check if any other players are using this potion - for ( int i = 0; i < m_Users.Count; i ++ ) - { - if ( m_Users[ i ].Target is ThrowTarget targ && targ.Potion == this ) - Target.Cancel( from ); - } - - // Effects - Effects.PlaySound( loc, map, 0x20C ); + from.RevealingAction(); - for ( int i = -2; i <= 2; i ++ ) - { - for ( int j = -2; j <= 2; j ++ ) - { - Point3D p = new Point3D( loc.X + i, loc.Y + j, loc.Z ); + if (!m_Users.Contains(from)) + m_Users.Add(from); - if ( map.CanFit( p, 12, true, false ) && from.InLOS( p ) ) - new InternalItem( from, p, map, MinDamage, MaxDamage ); - } - } - } + from.Target = new ThrowTarget(this); + } - #region Delay - private static Hashtable m_Delay = new Hashtable(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public static void AddDelay( Mobile m ) - { - if ( m_Delay[ m ] is Timer timer ) - timer.Stop(); + writer.Write(0); // version + } - m_Delay[ m ] = Timer.DelayCall( TimeSpan.FromSeconds( 30 ), new TimerStateCallback( EndDelay_Callback ), m ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public static int GetDelay( Mobile m ) - { - if ( m_Delay[ m ] is Timer timer && timer.Next > DateTime.UtcNow ) - return (int) (timer.Next - DateTime.UtcNow).TotalSeconds; + int version = reader.ReadInt(); + } - return 0; - } + public void Explode_Callback(object state) + { + object[] states = (object[])state; - private static void EndDelay_Callback( object obj ) - { - if ( obj is Mobile mobile ) - EndDelay( mobile ); - } + Explode((Mobile)states[0], (Point3D)states[1], (Map)states[2]); + } - public static void EndDelay( Mobile m ) - { - if ( m_Delay[ m ] is Timer timer ) - { - timer.Stop(); - m_Delay.Remove( m ); - } - } - #endregion + public virtual void Explode(Mobile from, Point3D loc, Map map) + { + if (Deleted || map == null) + return; - private class ThrowTarget : Target - { - public BaseConflagrationPotion Potion { get; } + Consume(); - public ThrowTarget( BaseConflagrationPotion potion ) : base( 12, true, TargetFlags.None ) - { - Potion = potion; - } + // Check if any other players are using this potion + for (int i = 0; i < m_Users.Count; i++) + if (m_Users[i].Target is ThrowTarget targ && targ.Potion == this) + Target.Cancel(from); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( Potion.Deleted || Potion.Map == Map.Internal ) - return; + // Effects + Effects.PlaySound(loc, map, 0x20C); - if ( !(targeted is IPoint3D p) || from.Map == null ) - return; + for (int i = -2; i <= 2; i++) + for (int j = -2; j <= 2; j++) + { + Point3D p = new Point3D(loc.X + i, loc.Y + j, loc.Z); - // Add delay - AddDelay( from ); + if (map.CanFit(p, 12, true, false) && from.InLOS(p)) + new InternalItem(from, p, map, MinDamage, MaxDamage); + } + } - SpellHelper.GetSurfaceTop( ref p ); + private class ThrowTarget : Target + { + public ThrowTarget(BaseConflagrationPotion potion) : base(12, true, TargetFlags.None) + { + Potion = potion; + } - from.RevealingAction(); + public BaseConflagrationPotion Potion{ get; } - IEntity to; + protected override void OnTarget(Mobile from, object targeted) + { + if (Potion.Deleted || Potion.Map == Map.Internal) + return; - if ( p is Mobile mobile ) - to = mobile; - else - to = new Entity( Serial.Zero, new Point3D( p ), from.Map ); + if (!(targeted is IPoint3D p) || from.Map == null) + return; - Effects.SendMovingEffect( from, to, 0xF0D, 7, 0, false, false, Potion.Hue, 0 ); - Timer.DelayCall( TimeSpan.FromSeconds( 1.5 ), new TimerStateCallback( Potion.Explode_Callback ), new object[] { from, new Point3D( p ), from.Map } ); - } - } + // Add delay + AddDelay(from); - public class InternalItem : Item - { - private int m_MinDamage; - private int m_MaxDamage; - private DateTime m_End; - private Timer m_Timer; + SpellHelper.GetSurfaceTop(ref p); - public Mobile From { get; private set; } + from.RevealingAction(); - public override bool BlocksFit => true; + IEntity to; - public InternalItem( Mobile from, Point3D loc, Map map, int min, int max ) : base( 0x398C ) - { - Movable = false; - Light = LightType.Circle300; + if (p is Mobile mobile) + to = mobile; + else + to = new Entity(Serial.Zero, new Point3D(p), from.Map); - MoveToWorld( loc, map ); + Effects.SendMovingEffect(from, to, 0xF0D, 7, 0, false, false, Potion.Hue, 0); + Timer.DelayCall(TimeSpan.FromSeconds(1.5), new TimerStateCallback(Potion.Explode_Callback), + new object[] { from, new Point3D(p), from.Map }); + } + } - From = from; - m_End = DateTime.UtcNow + TimeSpan.FromSeconds( 10 ); + public class InternalItem : Item + { + private DateTime m_End; + private int m_MaxDamage; + private int m_MinDamage; + private Timer m_Timer; - SetDamage( min, max ); + public InternalItem(Mobile from, Point3D loc, Map map, int min, int max) : base(0x398C) + { + Movable = false; + Light = LightType.Circle300; - m_Timer = new InternalTimer( this, m_End ); - m_Timer.Start(); - } + MoveToWorld(loc, map); - public override void OnAfterDelete() - { - base.OnAfterDelete(); + From = from; + m_End = DateTime.UtcNow + TimeSpan.FromSeconds(10); - m_Timer?.Stop(); - } + SetDamage(min, max); - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Timer = new InternalTimer(this, m_End); + m_Timer.Start(); + } - public int GetDamage(){ return Utility.RandomMinMax( m_MinDamage, m_MaxDamage ); } + public InternalItem(Serial serial) : base(serial) + { + } - private void SetDamage( int min, int max ) - { - /* new way to apply alchemy bonus according to Stratics' calculator. - this gives a mean to values 25, 50, 75 and 100. Stratics' calculator is outdated. - Those goals will give 2 to alchemy bonus. It's not really OSI-like but it's an approximation. */ + public Mobile From{ get; private set; } - m_MinDamage = min; - m_MaxDamage = max; + public override bool BlocksFit => true; - if ( From == null ) - return; + public override void OnAfterDelete() + { + base.OnAfterDelete(); - int alchemySkill = From.Skills.Alchemy.Fixed; - int alchemyBonus = alchemySkill / 125 + alchemySkill / 250 ; + m_Timer?.Stop(); + } - m_MinDamage = Scale( From, m_MinDamage + alchemyBonus ); - m_MaxDamage = Scale( From, m_MaxDamage + alchemyBonus ); - } + public int GetDamage() + { + return Utility.RandomMinMax(m_MinDamage, m_MaxDamage); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private void SetDamage(int min, int max) + { + /* new way to apply alchemy bonus according to Stratics' calculator. + this gives a mean to values 25, 50, 75 and 100. Stratics' calculator is outdated. + Those goals will give 2 to alchemy bonus. It's not really OSI-like but it's an approximation. */ - writer.Write( (int) 0 ); // version + m_MinDamage = min; + m_MaxDamage = max; - writer.Write( (Mobile) From ); - writer.Write( (DateTime) m_End ); - writer.Write( (int) m_MinDamage ); - writer.Write( (int) m_MaxDamage ); - } + if (From == null) + return; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int alchemySkill = From.Skills.Alchemy.Fixed; + int alchemyBonus = alchemySkill / 125 + alchemySkill / 250; - int version = reader.ReadInt(); + m_MinDamage = Scale(From, m_MinDamage + alchemyBonus); + m_MaxDamage = Scale(From, m_MaxDamage + alchemyBonus); + } - From = reader.ReadMobile(); - m_End = reader.ReadDateTime(); - m_MinDamage = reader.ReadInt(); - m_MaxDamage = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_Timer = new InternalTimer( this, m_End ); - m_Timer.Start(); - } + writer.Write(0); // version - public override bool OnMoveOver( Mobile m ) - { - if ( Visible && From != null && (!Core.AOS || m != From) && SpellHelper.ValidIndirectTarget( From, m ) && From.CanBeHarmful( m, false ) ) - { - From.DoHarmful( m ); + writer.Write(From); + writer.Write(m_End); + writer.Write(m_MinDamage); + writer.Write(m_MaxDamage); + } - AOS.Damage( m, From, GetDamage(), 0, 100, 0, 0, 0 ); - m.PlaySound( 0x208 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return true; - } + int version = reader.ReadInt(); - private class InternalTimer : Timer - { - private InternalItem m_Item; - private DateTime m_End; + From = reader.ReadMobile(); + m_End = reader.ReadDateTime(); + m_MinDamage = reader.ReadInt(); + m_MaxDamage = reader.ReadInt(); - public InternalTimer( InternalItem item, DateTime end ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.0 ) ) - { - m_Item = item; - m_End = end; + m_Timer = new InternalTimer(this, m_End); + m_Timer.Start(); + } + + public override bool OnMoveOver(Mobile m) + { + if (Visible && From != null && (!Core.AOS || m != From) && SpellHelper.ValidIndirectTarget(From, m) && + From.CanBeHarmful(m, false)) + { + From.DoHarmful(m); + + AOS.Damage(m, From, GetDamage(), 0, 100, 0, 0, 0); + m.PlaySound(0x208); + } - Priority = TimerPriority.FiftyMS; - } + return true; + } - protected override void OnTick() - { - if ( m_Item.Deleted ) - return; + private class InternalTimer : Timer + { + private DateTime m_End; + private InternalItem m_Item; - if ( DateTime.UtcNow > m_End ) - { - m_Item.Delete(); - Stop(); - return; - } - - Mobile from = m_Item.From; + public InternalTimer(InternalItem item, DateTime end) : base(TimeSpan.Zero, TimeSpan.FromSeconds(1.0)) + { + m_Item = item; + m_End = end; - if ( m_Item.Map == null || from == null ) - return; + Priority = TimerPriority.FiftyMS; + } - List mobiles = new List(); - - foreach( Mobile mobile in m_Item.GetMobilesInRange( 0 ) ) - mobiles.Add( mobile ); - - for( int i = 0; i < mobiles.Count; i++ ) - { - Mobile m = mobiles[i]; - - if ( (m.Z + 16) > m_Item.Z && (m_Item.Z + 12) > m.Z && (!Core.AOS || m != from) && SpellHelper.ValidIndirectTarget( from, m ) && from.CanBeHarmful( m, false ) ) - { - from?.DoHarmful( m ); - - AOS.Damage( m, from, m_Item.GetDamage(), 0, 100, 0, 0, 0 ); - m.PlaySound( 0x208 ); - } - } - } - } - } - } -} + protected override void OnTick() + { + if (m_Item.Deleted) + return; + + if (DateTime.UtcNow > m_End) + { + m_Item.Delete(); + Stop(); + return; + } + + Mobile from = m_Item.From; + + if (m_Item.Map == null || from == null) + return; + + List mobiles = new List(); + + foreach (Mobile mobile in m_Item.GetMobilesInRange(0)) + mobiles.Add(mobile); + + for (int i = 0; i < mobiles.Count; i++) + { + Mobile m = mobiles[i]; + + if (m.Z + 16 > m_Item.Z && m_Item.Z + 12 > m.Z && (!Core.AOS || m != from) && + SpellHelper.ValidIndirectTarget(from, m) && from.CanBeHarmful(m, false)) + { + from?.DoHarmful(m); + + AOS.Damage(m, from, m_Item.GetDamage(), 0, 100, 0, 0, 0); + m.PlaySound(0x208); + } + } + } + } + } + + #region Delay + + private static Hashtable m_Delay = new Hashtable(); + + public static void AddDelay(Mobile m) + { + if (m_Delay[m] is Timer timer) + timer.Stop(); + + m_Delay[m] = Timer.DelayCall(TimeSpan.FromSeconds(30), new TimerStateCallback(EndDelay_Callback), m); + } + + public static int GetDelay(Mobile m) + { + if (m_Delay[m] is Timer timer && timer.Next > DateTime.UtcNow) + return (int)(timer.Next - DateTime.UtcNow).TotalSeconds; + + return 0; + } + + private static void EndDelay_Callback(object obj) + { + if (obj is Mobile mobile) + EndDelay(mobile); + } + + public static void EndDelay(Mobile m) + { + if (m_Delay[m] is Timer timer) + { + timer.Stop(); + m_Delay.Remove(m); + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/ConflagrationPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/ConflagrationPotion.cs index 964595c40..16ff3cde3 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/ConflagrationPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/ConflagrationPotion.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class ConflagrationPotion : BaseConflagrationPotion - { - public override int MinDamage => 2; - public override int MaxDamage => 4; + public class ConflagrationPotion : BaseConflagrationPotion + { + [Constructible] + public ConflagrationPotion() : base(PotionEffect.Conflagration) + { + } - public override int LabelNumber => 1072095; // a Conflagration potion + public ConflagrationPotion(Serial serial) : base(serial) + { + } - [Constructible] - public ConflagrationPotion() : base( PotionEffect.Conflagration ) - { - } + public override int MinDamage => 2; + public override int MaxDamage => 4; - public ConflagrationPotion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072095; // a Conflagration potion - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/GreaterConflagrationPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/GreaterConflagrationPotion.cs index cb201c73c..8a1093c92 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/GreaterConflagrationPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Conflagration Potions/GreaterConflagrationPotion.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class GreaterConflagrationPotion : BaseConflagrationPotion - { - public override int MinDamage => 4; - public override int MaxDamage => 8; + public class GreaterConflagrationPotion : BaseConflagrationPotion + { + [Constructible] + public GreaterConflagrationPotion() : base(PotionEffect.ConflagrationGreater) + { + } - public override int LabelNumber => 1072098; // a Greater Conflagration potion + public GreaterConflagrationPotion(Serial serial) : base(serial) + { + } - [Constructible] - public GreaterConflagrationPotion() : base( PotionEffect.ConflagrationGreater ) - { - } + public override int MinDamage => 4; + public override int MaxDamage => 8; - public GreaterConflagrationPotion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072098; // a Greater Conflagration potion - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/BaseConfusionBlastPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/BaseConfusionBlastPotion.cs index e53b8712c..bae86f129 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/BaseConfusionBlastPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/BaseConfusionBlastPotion.cs @@ -1,195 +1,197 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Targeting; -using Server.Spells; -using Server.Mobiles; using Server.Misc; +using Server.Mobiles; +using Server.Spells; +using Server.Targeting; namespace Server.Items { - public abstract class BaseConfusionBlastPotion : BasePotion - { - public abstract int Radius{ get; } + public abstract class BaseConfusionBlastPotion : BasePotion + { + private List m_Users = new List(); - public override bool RequireFreeHand => false; + public BaseConfusionBlastPotion(PotionEffect effect) : base(0xF06, effect) + { + Hue = 0x48D; + } - public BaseConfusionBlastPotion( PotionEffect effect ) : base( 0xF06, effect ) - { - Hue = 0x48D; - } + public BaseConfusionBlastPotion(Serial serial) : base(serial) + { + } - public BaseConfusionBlastPotion( Serial serial ) : base( serial ) - { - } + public abstract int Radius{ get; } - public override void Drink( Mobile from ) - { - if ( Core.AOS && (from.Paralyzed || from.Frozen || (from.Spell != null && from.Spell.IsCasting)) ) - { - from.SendLocalizedMessage( 1062725 ); // You can not use that potion while paralyzed. - return; - } + public override bool RequireFreeHand => false; - int delay = GetDelay( from ); + public override void Drink(Mobile from) + { + if (Core.AOS && (from.Paralyzed || from.Frozen || from.Spell != null && from.Spell.IsCasting)) + { + from.SendLocalizedMessage(1062725); // You can not use that potion while paralyzed. + return; + } - if ( delay > 0 ) - { - from.SendLocalizedMessage( 1072529, $"{delay}\t{(delay > 1 ? "seconds." : "second.")}"); // You cannot use that for another ~1_NUM~ ~2_TIMEUNITS~ - return; - } + int delay = GetDelay(from); - if ( from.Target is ThrowTarget targ && targ.Potion == this ) - return; + if (delay > 0) + { + from.SendLocalizedMessage(1072529, + $"{delay}\t{(delay > 1 ? "seconds." : "second.")}"); // You cannot use that for another ~1_NUM~ ~2_TIMEUNITS~ + return; + } - from.RevealingAction(); + if (from.Target is ThrowTarget targ && targ.Potion == this) + return; - if ( !m_Users.Contains( from ) ) - m_Users.Add( from ); + from.RevealingAction(); - from.Target = new ThrowTarget( this ); - } + if (!m_Users.Contains(from)) + m_Users.Add(from); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + from.Target = new ThrowTarget(this); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - private List m_Users = new List(); + int version = reader.ReadInt(); + } - public void Explode_Callback( object state ) - { - object[] states = (object[]) state; + public void Explode_Callback(object state) + { + object[] states = (object[])state; - Explode( (Mobile) states[ 0 ], (Point3D) states[ 1 ], (Map) states[ 2 ] ); - } + Explode((Mobile)states[0], (Point3D)states[1], (Map)states[2]); + } - public virtual void Explode( Mobile from, Point3D loc, Map map ) - { - if ( Deleted || map == null ) - return; + public virtual void Explode(Mobile from, Point3D loc, Map map) + { + if (Deleted || map == null) + return; - Consume(); + Consume(); - // Check if any other players are using this potion - for ( int i = 0; i < m_Users.Count; i ++ ) - { - if ( m_Users[ i ].Target is ThrowTarget targ && targ.Potion == this ) - Target.Cancel( from ); - } + // Check if any other players are using this potion + for (int i = 0; i < m_Users.Count; i++) + if (m_Users[i].Target is ThrowTarget targ && targ.Potion == this) + Target.Cancel(from); - // Effects - Effects.PlaySound( loc, map, 0x207 ); + // Effects + Effects.PlaySound(loc, map, 0x207); - Geometry.Circle2D( loc, map, Radius, BlastEffect, 270, 90 ); + Geometry.Circle2D(loc, map, Radius, BlastEffect, 270, 90); - Timer.DelayCall( TimeSpan.FromSeconds( 0.3 ), new TimerStateCallback( CircleEffect2 ), new object[] { loc, map } ); + Timer.DelayCall(TimeSpan.FromSeconds(0.3), new TimerStateCallback(CircleEffect2), new object[] { loc, map }); - foreach ( Mobile mobile in map.GetMobilesInRange( loc, Radius ) ) - { - if ( mobile is BaseCreature mon ) - { - if ( mon.Controlled || mon.Summoned ) - continue; + foreach (Mobile mobile in map.GetMobilesInRange(loc, Radius)) + if (mobile is BaseCreature mon) + { + if (mon.Controlled || mon.Summoned) + continue; - mon.Pacify( from, DateTime.UtcNow + TimeSpan.FromSeconds( 5.0 ) ); // TODO check - } - } - } + mon.Pacify(from, DateTime.UtcNow + TimeSpan.FromSeconds(5.0)); // TODO check + } + } - #region Effects - public virtual void BlastEffect( Point3D p, Map map ) - { - if ( map.CanFit( p, 12, true, false ) ) - Effects.SendLocationEffect( p, map, 0x376A, 4, 9 ); - } + private class ThrowTarget : Target + { + public ThrowTarget(BaseConfusionBlastPotion potion) : base(12, true, TargetFlags.None) + { + Potion = potion; + } - public void CircleEffect2( object state ) - { - object[] states = (object[]) state; + public BaseConfusionBlastPotion Potion{ get; } - Geometry.Circle2D( (Point3D)states[0], (Map)states[1], Radius, BlastEffect, 90, 270 ); - } - #endregion + protected override void OnTarget(Mobile from, object targeted) + { + if (Potion.Deleted || Potion.Map == Map.Internal) + return; - #region Delay - private static Hashtable m_Delay = new Hashtable(); + if (!(targeted is IPoint3D p) || from.Map == null) + return; - public static void AddDelay( Mobile m ) - { - if ( m_Delay[ m ] is Timer timer ) - timer.Stop(); + // Add delay + AddDelay(from); - m_Delay[ m ] = Timer.DelayCall( TimeSpan.FromSeconds( 60 ), new TimerStateCallback( EndDelay_Callback ), m ); - } + SpellHelper.GetSurfaceTop(ref p); - public static int GetDelay( Mobile m ) - { - if ( m_Delay[ m ] is Timer timer && timer.Next > DateTime.UtcNow ) - return (int) (timer.Next - DateTime.UtcNow).TotalSeconds; + from.RevealingAction(); - return 0; - } + IEntity to; - private static void EndDelay_Callback( object obj ) - { - if ( obj is Mobile mobile ) - EndDelay( mobile ); - } + if (p is Mobile mobile) + to = mobile; + else + to = new Entity(Serial.Zero, new Point3D(p), from.Map); - public static void EndDelay( Mobile m ) - { - if ( m_Delay[ m ] is Timer timer ) - { - timer.Stop(); - m_Delay.Remove( m ); - } - } - #endregion + Effects.SendMovingEffect(from, to, 0xF0D, 7, 0, false, false, Potion.Hue, 0); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(Potion.Explode_Callback), + new object[] { from, new Point3D(p), from.Map }); + } + } - private class ThrowTarget : Target - { - public BaseConfusionBlastPotion Potion { get; } + #region Effects - public ThrowTarget( BaseConfusionBlastPotion potion ) : base( 12, true, TargetFlags.None ) - { - Potion = potion; - } + public virtual void BlastEffect(Point3D p, Map map) + { + if (map.CanFit(p, 12, true, false)) + Effects.SendLocationEffect(p, map, 0x376A, 4, 9); + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( Potion.Deleted || Potion.Map == Map.Internal ) - return; + public void CircleEffect2(object state) + { + object[] states = (object[])state; - if ( !(targeted is IPoint3D p) || from.Map == null ) - return; + Geometry.Circle2D((Point3D)states[0], (Map)states[1], Radius, BlastEffect, 90, 270); + } - // Add delay - AddDelay( from ); + #endregion - SpellHelper.GetSurfaceTop( ref p ); + #region Delay - from.RevealingAction(); + private static Hashtable m_Delay = new Hashtable(); - IEntity to; + public static void AddDelay(Mobile m) + { + if (m_Delay[m] is Timer timer) + timer.Stop(); - if ( p is Mobile mobile ) - to = mobile; - else - to = new Entity( Serial.Zero, new Point3D( p ), from.Map ); + m_Delay[m] = Timer.DelayCall(TimeSpan.FromSeconds(60), new TimerStateCallback(EndDelay_Callback), m); + } - Effects.SendMovingEffect( from, to, 0xF0D, 7, 0, false, false, Potion.Hue, 0 ); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( Potion.Explode_Callback ), new object[] { from, new Point3D( p ), from.Map } ); - } - } - } -} + public static int GetDelay(Mobile m) + { + if (m_Delay[m] is Timer timer && timer.Next > DateTime.UtcNow) + return (int)(timer.Next - DateTime.UtcNow).TotalSeconds; + + return 0; + } + + private static void EndDelay_Callback(object obj) + { + if (obj is Mobile mobile) + EndDelay(mobile); + } + + public static void EndDelay(Mobile m) + { + if (m_Delay[m] is Timer timer) + { + timer.Stop(); + m_Delay.Remove(m); + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/ConfusionBlastPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/ConfusionBlastPotion.cs index 56703c850..71743059f 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/ConfusionBlastPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/ConfusionBlastPotion.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class ConfusionBlastPotion : BaseConfusionBlastPotion - { - public override int Radius => 5; + public class ConfusionBlastPotion : BaseConfusionBlastPotion + { + [Constructible] + public ConfusionBlastPotion() : base(PotionEffect.ConfusionBlast) + { + } - public override int LabelNumber => 1072105; // a Confusion Blast potion + public ConfusionBlastPotion(Serial serial) : base(serial) + { + } - [Constructible] - public ConfusionBlastPotion() : base( PotionEffect.ConfusionBlast ) - { - } + public override int Radius => 5; - public ConfusionBlastPotion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072105; // a Confusion Blast potion - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/GreaterConfusionBlastPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/GreaterConfusionBlastPotion.cs index 846bd61cb..927f23f15 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/GreaterConfusionBlastPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Confusion Blast Potions/GreaterConfusionBlastPotion.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class GreaterConfusionBlastPotion : BaseConfusionBlastPotion - { - public override int Radius => 7; + public class GreaterConfusionBlastPotion : BaseConfusionBlastPotion + { + [Constructible] + public GreaterConfusionBlastPotion() : base(PotionEffect.ConfusionBlastGreater) + { + } - public override int LabelNumber => 1072108; // a Greater Confusion Blast potion + public GreaterConfusionBlastPotion(Serial serial) : base(serial) + { + } - [Constructible] - public GreaterConfusionBlastPotion() : base( PotionEffect.ConfusionBlastGreater ) - { - } + public override int Radius => 7; - public GreaterConfusionBlastPotion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072108; // a Greater Confusion Blast potion - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/BaseCurePotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/BaseCurePotion.cs index 66c3e276d..3c22af3d8 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/BaseCurePotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/BaseCurePotion.cs @@ -1,98 +1,100 @@ +using Server.Engines.ConPVP; using Server.Spells; +using Server.Spells.Necromancy; namespace Server.Items { - public class CureLevelInfo - { - public Poison Poison { get; } + public class CureLevelInfo + { + public CureLevelInfo(Poison poison, double chance) + { + Poison = poison; + Chance = chance; + } - public double Chance { get; } + public Poison Poison{ get; } - public CureLevelInfo( Poison poison, double chance ) - { - Poison = poison; - Chance = chance; - } - } + public double Chance{ get; } + } - public abstract class BaseCurePotion : BasePotion - { - public abstract CureLevelInfo[] LevelInfo{ get; } + public abstract class BaseCurePotion : BasePotion + { + public BaseCurePotion(PotionEffect effect) : base(0xF07, effect) + { + } - public BaseCurePotion( PotionEffect effect ) : base( 0xF07, effect ) - { - } + public BaseCurePotion(Serial serial) : base(serial) + { + } - public BaseCurePotion( Serial serial ) : base( serial ) - { - } + public abstract CureLevelInfo[] LevelInfo{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public void DoCure( Mobile from ) - { - bool cure = false; + public void DoCure(Mobile from) + { + bool cure = false; - CureLevelInfo[] info = LevelInfo; + CureLevelInfo[] info = LevelInfo; - for ( int i = 0; i < info.Length; ++i ) - { - CureLevelInfo li = info[i]; + for (int i = 0; i < info.Length; ++i) + { + CureLevelInfo li = info[i]; - if ( li.Poison == from.Poison && Scale( from, li.Chance ) > Utility.RandomDouble() ) - { - cure = true; - break; - } - } + if (li.Poison == from.Poison && Scale(from, li.Chance) > Utility.RandomDouble()) + { + cure = true; + break; + } + } - if ( cure && from.CurePoison( from ) ) - { - from.SendLocalizedMessage( 500231 ); // You feel cured of poison! + if (cure && from.CurePoison(from)) + { + from.SendLocalizedMessage(500231); // You feel cured of poison! - from.FixedEffect( 0x373A, 10, 15 ); - from.PlaySound( 0x1E0 ); - } - else if ( !cure ) - { - from.SendLocalizedMessage( 500232 ); // That potion was not strong enough to cure your ailment! - } - } + from.FixedEffect(0x373A, 10, 15); + from.PlaySound(0x1E0); + } + else if (!cure) + { + from.SendLocalizedMessage(500232); // That potion was not strong enough to cure your ailment! + } + } - public override void Drink( Mobile from ) - { - if ( TransformationSpellHelper.UnderTransformation( from, typeof( Spells.Necromancy.VampiricEmbraceSpell ) ) ) - { - from.SendLocalizedMessage( 1061652 ); // The garlic in the potion would surely kill you. - } - else if ( from.Poisoned ) - { - DoCure( from ); + public override void Drink(Mobile from) + { + if (TransformationSpellHelper.UnderTransformation(from, typeof(VampiricEmbraceSpell))) + { + from.SendLocalizedMessage(1061652); // The garlic in the potion would surely kill you. + } + else if (from.Poisoned) + { + DoCure(from); - PlayDrinkEffect( from ); + PlayDrinkEffect(from); - from.FixedParticles( 0x373A, 10, 15, 5012, EffectLayer.Waist ); - from.PlaySound( 0x1E0 ); + from.FixedParticles(0x373A, 10, 15, 5012, EffectLayer.Waist); + from.PlaySound(0x1E0); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); - } - else - { - from.SendLocalizedMessage( 1042000 ); // You are not poisoned. - } - } - } + if (!DuelContext.IsFreeConsume(from)) + Consume(); + } + else + { + from.SendLocalizedMessage(1042000); // You are not poisoned. + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/CurePotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/CurePotion.cs index 39acd86a7..929e55719 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/CurePotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/CurePotion.cs @@ -1,45 +1,47 @@ namespace Server.Items { - public class CurePotion : BaseCurePotion - { - private static CureLevelInfo[] m_OldLevelInfo = { - new CureLevelInfo( Poison.Lesser, 1.00 ), // 100% chance to cure lesser poison - new CureLevelInfo( Poison.Regular, 0.75 ), // 75% chance to cure regular poison - new CureLevelInfo( Poison.Greater, 0.50 ), // 50% chance to cure greater poison - new CureLevelInfo( Poison.Deadly, 0.15 ) // 15% chance to cure deadly poison - }; + public class CurePotion : BaseCurePotion + { + private static CureLevelInfo[] m_OldLevelInfo = + { + new CureLevelInfo(Poison.Lesser, 1.00), // 100% chance to cure lesser poison + new CureLevelInfo(Poison.Regular, 0.75), // 75% chance to cure regular poison + new CureLevelInfo(Poison.Greater, 0.50), // 50% chance to cure greater poison + new CureLevelInfo(Poison.Deadly, 0.15) // 15% chance to cure deadly poison + }; - private static CureLevelInfo[] m_AosLevelInfo = { - new CureLevelInfo( Poison.Lesser, 1.00 ), - new CureLevelInfo( Poison.Regular, 0.95 ), - new CureLevelInfo( Poison.Greater, 0.75 ), - new CureLevelInfo( Poison.Deadly, 0.50 ), - new CureLevelInfo( Poison.Lethal, 0.25 ) - }; + private static CureLevelInfo[] m_AosLevelInfo = + { + new CureLevelInfo(Poison.Lesser, 1.00), + new CureLevelInfo(Poison.Regular, 0.95), + new CureLevelInfo(Poison.Greater, 0.75), + new CureLevelInfo(Poison.Deadly, 0.50), + new CureLevelInfo(Poison.Lethal, 0.25) + }; - public override CureLevelInfo[] LevelInfo => Core.AOS ? m_AosLevelInfo : m_OldLevelInfo; + [Constructible] + public CurePotion() : base(PotionEffect.Cure) + { + } - [Constructible] - public CurePotion() : base( PotionEffect.Cure ) - { - } + public CurePotion(Serial serial) : base(serial) + { + } - public CurePotion( Serial serial ) : base( serial ) - { - } + public override CureLevelInfo[] LevelInfo => Core.AOS ? m_AosLevelInfo : m_OldLevelInfo; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/GreaterCurePotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/GreaterCurePotion.cs index 1eab43dcb..9656773ec 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/GreaterCurePotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/GreaterCurePotion.cs @@ -1,46 +1,48 @@ namespace Server.Items { - public class GreaterCurePotion : BaseCurePotion - { - private static CureLevelInfo[] m_OldLevelInfo = { - new CureLevelInfo( Poison.Lesser, 1.00 ), // 100% chance to cure lesser poison - new CureLevelInfo( Poison.Regular, 1.00 ), // 100% chance to cure regular poison - new CureLevelInfo( Poison.Greater, 1.00 ), // 100% chance to cure greater poison - new CureLevelInfo( Poison.Deadly, 0.75 ), // 75% chance to cure deadly poison - new CureLevelInfo( Poison.Lethal, 0.25 ) // 25% chance to cure lethal poison - }; + public class GreaterCurePotion : BaseCurePotion + { + private static CureLevelInfo[] m_OldLevelInfo = + { + new CureLevelInfo(Poison.Lesser, 1.00), // 100% chance to cure lesser poison + new CureLevelInfo(Poison.Regular, 1.00), // 100% chance to cure regular poison + new CureLevelInfo(Poison.Greater, 1.00), // 100% chance to cure greater poison + new CureLevelInfo(Poison.Deadly, 0.75), // 75% chance to cure deadly poison + new CureLevelInfo(Poison.Lethal, 0.25) // 25% chance to cure lethal poison + }; - private static CureLevelInfo[] m_AosLevelInfo = { - new CureLevelInfo( Poison.Lesser, 1.00 ), - new CureLevelInfo( Poison.Regular, 1.00 ), - new CureLevelInfo( Poison.Greater, 1.00 ), - new CureLevelInfo( Poison.Deadly, 0.95 ), - new CureLevelInfo( Poison.Lethal, 0.75 ) - }; + private static CureLevelInfo[] m_AosLevelInfo = + { + new CureLevelInfo(Poison.Lesser, 1.00), + new CureLevelInfo(Poison.Regular, 1.00), + new CureLevelInfo(Poison.Greater, 1.00), + new CureLevelInfo(Poison.Deadly, 0.95), + new CureLevelInfo(Poison.Lethal, 0.75) + }; - public override CureLevelInfo[] LevelInfo => Core.AOS ? m_AosLevelInfo : m_OldLevelInfo; + [Constructible] + public GreaterCurePotion() : base(PotionEffect.CureGreater) + { + } - [Constructible] - public GreaterCurePotion() : base( PotionEffect.CureGreater ) - { - } + public GreaterCurePotion(Serial serial) : base(serial) + { + } - public GreaterCurePotion( Serial serial ) : base( serial ) - { - } + public override CureLevelInfo[] LevelInfo => Core.AOS ? m_AosLevelInfo : m_OldLevelInfo; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/LesserCurePotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/LesserCurePotion.cs index 66116de47..a8ef9cc92 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/LesserCurePotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Cure Potions/LesserCurePotion.cs @@ -1,42 +1,44 @@ namespace Server.Items { - public class LesserCurePotion : BaseCurePotion - { - private static CureLevelInfo[] m_OldLevelInfo = { - new CureLevelInfo( Poison.Lesser, 0.75 ), // 75% chance to cure lesser poison - new CureLevelInfo( Poison.Regular, 0.50 ), // 50% chance to cure regular poison - new CureLevelInfo( Poison.Greater, 0.15 ) // 15% chance to cure greater poison - }; + public class LesserCurePotion : BaseCurePotion + { + private static CureLevelInfo[] m_OldLevelInfo = + { + new CureLevelInfo(Poison.Lesser, 0.75), // 75% chance to cure lesser poison + new CureLevelInfo(Poison.Regular, 0.50), // 50% chance to cure regular poison + new CureLevelInfo(Poison.Greater, 0.15) // 15% chance to cure greater poison + }; - private static CureLevelInfo[] m_AosLevelInfo = { - new CureLevelInfo( Poison.Lesser, 0.75 ), - new CureLevelInfo( Poison.Regular, 0.50 ), - new CureLevelInfo( Poison.Greater, 0.25 ) - }; + private static CureLevelInfo[] m_AosLevelInfo = + { + new CureLevelInfo(Poison.Lesser, 0.75), + new CureLevelInfo(Poison.Regular, 0.50), + new CureLevelInfo(Poison.Greater, 0.25) + }; - public override CureLevelInfo[] LevelInfo => Core.AOS ? m_AosLevelInfo : m_OldLevelInfo; + [Constructible] + public LesserCurePotion() : base(PotionEffect.CureLesser) + { + } - [Constructible] - public LesserCurePotion() : base( PotionEffect.CureLesser ) - { - } + public LesserCurePotion(Serial serial) : base(serial) + { + } - public LesserCurePotion( Serial serial ) : base( serial ) - { - } + public override CureLevelInfo[] LevelInfo => Core.AOS ? m_AosLevelInfo : m_OldLevelInfo; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/DarkglowPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/DarkglowPotion.cs index 59b464f43..27ac6a488 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/DarkglowPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/DarkglowPotion.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class DarkglowPotion : BasePoisonPotion - { - public override Poison Poison => Poison.Greater; /* MUST be restored when prerequisites are done */ + public class DarkglowPotion : BasePoisonPotion + { + [Constructible] + public DarkglowPotion() : base(PotionEffect.Darkglow) + { + Hue = 0x96; + } - public override double MinPoisoningSkill => 95.0; - public override double MaxPoisoningSkill => 100.0; + public DarkglowPotion(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1072849; // Darkglow Poison + public override Poison Poison => Poison.Greater; /* MUST be restored when prerequisites are done */ - [Constructible] - public DarkglowPotion() : base( PotionEffect.Darkglow ) - { - Hue = 0x96; - } + public override double MinPoisoningSkill => 95.0; + public override double MaxPoisoningSkill => 100.0; - public DarkglowPotion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072849; // Darkglow Poison - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/BaseExplosionPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/BaseExplosionPotion.cs index 487fc69f0..3982742c6 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/BaseExplosionPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/BaseExplosionPotion.cs @@ -1,286 +1,287 @@ using System; using System.Collections.Generic; using Server.Network; -using Server.Targeting; using Server.Spells; +using Server.Targeting; namespace Server.Items { - public abstract class BaseExplosionPotion : BasePotion - { - public abstract int MinDamage { get; } - public abstract int MaxDamage { get; } + public abstract class BaseExplosionPotion : BasePotion + { + private const int ExplosionRange = 2; // How long is the blast radius? - public override bool RequireFreeHand => false; + private static bool LeveledExplosion = false; // Should explosion potions explode other nearby potions? + private static bool InstantExplosion = false; // Should explosion potions explode on impact? + private static bool RelativeLocation = false; // Is the explosion target location relative for mobiles? - private static bool LeveledExplosion = false; // Should explosion potions explode other nearby potions? - private static bool InstantExplosion = false; // Should explosion potions explode on impact? - private static bool RelativeLocation = false; // Is the explosion target location relative for mobiles? - private const int ExplosionRange = 2; // How long is the blast radius? + private Timer m_Timer; - public BaseExplosionPotion( PotionEffect effect ) : base( 0xF0D, effect ) - { - } + public BaseExplosionPotion(PotionEffect effect) : base(0xF0D, effect) + { + } - public BaseExplosionPotion( Serial serial ) : base( serial ) - { - } + public BaseExplosionPotion(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public abstract int MinDamage{ get; } + public abstract int MaxDamage{ get; } - writer.Write( (int) 0 ); // version - } + public override bool RequireFreeHand => false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public virtual object FindParent( Mobile from ) - { - Mobile m = HeldBy; - - if ( m != null && m.Holding == this ) - return m; - - object obj = RootParent; - - if ( obj != null ) - return obj; - - if ( Map == Map.Internal ) - return from; - - return this; - } - - private Timer m_Timer; - - public List Users { get; private set; } - - public override void Drink( Mobile from ) - { - if ( Core.AOS && (from.Paralyzed || from.Frozen || (from.Spell != null && from.Spell.IsCasting)) ) - { - from.SendLocalizedMessage( 1062725 ); // You can not use a purple potion while paralyzed. - return; - } - - ThrowTarget targ = from.Target as ThrowTarget; - Stackable = false; // Scavenged explosion potions won't stack with those ones in backpack, and still will explode. - - if ( targ != null && targ.Potion == this ) - return; - - from.RevealingAction(); - - if ( Users == null ) - Users = new List(); - - if ( !Users.Contains( from ) ) - Users.Add( from ); + public List Users{ get; private set; } - from.Target = new ThrowTarget( this ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( m_Timer == null ) - { - from.SendLocalizedMessage( 500236 ); // You should throw it now! + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } - if ( Core.ML ) - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.25 ), 5, new TimerStateCallback( Detonate_OnTick ), new object[]{ from, 3 } ); // 3.6 seconds explosion delay - else - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 0.75 ), TimeSpan.FromSeconds( 1.0 ), 4, new TimerStateCallback( Detonate_OnTick ), new object[]{ from, 3 } ); // 2.6 seconds explosion delay - } - } + public virtual object FindParent(Mobile from) + { + Mobile m = HeldBy; + + if (m != null && m.Holding == this) + return m; + + object obj = RootParent; + + if (obj != null) + return obj; - private void Detonate_OnTick( object state ) - { - if ( Deleted ) - return; - - object[] states = (object[])state; - Mobile from = (Mobile)states[0]; - int timer = (int)states[1]; - - object parent = FindParent( from ); + if (Map == Map.Internal) + return from; + + return this; + } + + public override void Drink(Mobile from) + { + if (Core.AOS && (from.Paralyzed || from.Frozen || from.Spell != null && from.Spell.IsCasting)) + { + from.SendLocalizedMessage(1062725); // You can not use a purple potion while paralyzed. + return; + } + + ThrowTarget targ = from.Target as ThrowTarget; + Stackable = false; // Scavenged explosion potions won't stack with those ones in backpack, and still will explode. + + if (targ != null && targ.Potion == this) + return; + + from.RevealingAction(); + + if (Users == null) + Users = new List(); + + if (!Users.Contains(from)) + Users.Add(from); - if ( timer == 0 ) - { - Point3D loc; - Map map; + from.Target = new ThrowTarget(this); - if ( parent is Item item ) - { - loc = item.GetWorldLocation(); - map = item.Map; - } - else if ( parent is Mobile m ) - { - loc = m.Location; - map = m.Map; - } - else - { - return; - } + if (m_Timer == null) + { + from.SendLocalizedMessage(500236); // You should throw it now! - Explode( from, true, loc, map ); - m_Timer = null; - } - else - { - if ( parent is Item item ) - item.PublicOverheadMessage( MessageType.Regular, 0x22, false, timer.ToString() ); - else if ( parent is Mobile mobile ) - mobile.PublicOverheadMessage( MessageType.Regular, 0x22, false, timer.ToString() ); + if (Core.ML) + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.25), 5, + new TimerStateCallback(Detonate_OnTick), new object[] { from, 3 }); // 3.6 seconds explosion delay + else + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(0.75), TimeSpan.FromSeconds(1.0), 4, + new TimerStateCallback(Detonate_OnTick), new object[] { from, 3 }); // 2.6 seconds explosion delay + } + } - states[1] = timer - 1; - } - } + private void Detonate_OnTick(object state) + { + if (Deleted) + return; + + object[] states = (object[])state; + Mobile from = (Mobile)states[0]; + int timer = (int)states[1]; - private void Reposition_OnTick( object state ) - { - if ( Deleted ) - return; + object parent = FindParent(from); + + if (timer == 0) + { + Point3D loc; + Map map; - object[] states = (object[])state; - Mobile from = (Mobile)states[0]; - IPoint3D p = (IPoint3D)states[1]; - Map map = (Map)states[2]; - - Point3D loc = new Point3D( p ); - - if ( InstantExplosion ) - Explode( from, true, loc, map ); - else - MoveToWorld( loc, map ); - } - - private class ThrowTarget : Target - { - public BaseExplosionPotion Potion { get; } - - public ThrowTarget( BaseExplosionPotion potion ) : base( 12, true, TargetFlags.None ) - { - Potion = potion; - } + if (parent is Item item) + { + loc = item.GetWorldLocation(); + map = item.Map; + } + else if (parent is Mobile m) + { + loc = m.Location; + map = m.Map; + } + else + { + return; + } + + Explode(from, true, loc, map); + m_Timer = null; + } + else + { + if (parent is Item item) + item.PublicOverheadMessage(MessageType.Regular, 0x22, false, timer.ToString()); + else if (parent is Mobile mobile) + mobile.PublicOverheadMessage(MessageType.Regular, 0x22, false, timer.ToString()); + + states[1] = timer - 1; + } + } + + private void Reposition_OnTick(object state) + { + if (Deleted) + return; + + object[] states = (object[])state; + Mobile from = (Mobile)states[0]; + IPoint3D p = (IPoint3D)states[1]; + Map map = (Map)states[2]; + + Point3D loc = new Point3D(p); + + if (InstantExplosion) + Explode(from, true, loc, map); + else + MoveToWorld(loc, map); + } + + public void Explode(Mobile from, bool direct, Point3D loc, Map map) + { + if (Deleted) + return; + + Consume(); + + for (int i = 0; Users != null && i < Users.Count; ++i) + { + Mobile m = Users[i]; + + if (m.Target is ThrowTarget targ && targ.Potion == this) + Target.Cancel(m); + } + + if (map == null) + return; + + Effects.PlaySound(loc, map, 0x307); + + Effects.SendLocationEffect(loc, map, 0x36B0, 9, 10, 0, 0); + int alchemyBonus = 0; + + if (direct) + alchemyBonus = (int)(from.Skills.Alchemy.Value / (Core.AOS ? 5 : 10)); + + IPooledEnumerable eable = map.GetObjectsInRange(loc, ExplosionRange, LeveledExplosion, true); + List toExplode = new List(); + + int toDamage = 0; + + foreach (IEntity o in eable) + if (o is Mobile mobile && (from == null || + SpellHelper.ValidIndirectTarget(from, mobile) && + from.CanBeHarmful(mobile, false))) + { + toExplode.Add(mobile); + ++toDamage; + } + else if (o is BaseExplosionPotion && o != this) + { + toExplode.Add(o); + } + + eable.Free(); + + int min = Scale(from, MinDamage); + int max = Scale(from, MaxDamage); + + for (int i = 0; i < toExplode.Count; ++i) + { + object o = toExplode[i]; + + if (o is Mobile m) + { + from?.DoHarmful(m); + + int damage = Utility.RandomMinMax(min, max); + + damage += alchemyBonus; + + if (!Core.AOS && damage > 40) + damage = 40; + else if (Core.AOS && toDamage > 2) + damage /= toDamage - 1; + + AOS.Damage(m, from, damage, 0, 100, 0, 0, 0); + } + else if (o is BaseExplosionPotion pot) + { + pot.Explode(from, false, pot.GetWorldLocation(), pot.Map); + } + } + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( Potion.Deleted || Potion.Map == Map.Internal ) - return; - - if ( !(targeted is IPoint3D p) ) - return; - - Map map = from.Map; - - if ( map == null ) - return; - - SpellHelper.GetSurfaceTop( ref p ); - - from.RevealingAction(); - - IEntity to = new Entity( Serial.Zero, new Point3D( p ), map ); - - if ( p is Mobile m ) - { - if ( !RelativeLocation ) // explosion location = current mob location. - p = m.Location; - else - to = m; - } - - Effects.SendMovingEffect( from, to, Potion.ItemID, 7, 0, false, false, Potion.Hue, 0 ); - - if ( Potion.Amount > 1 ) - { - Mobile.LiftItemDupe( Potion, 1 ); - } - - Potion.Internalize(); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( Potion.Reposition_OnTick ), new object[]{ from, p, map } ); - } - } - - public void Explode( Mobile from, bool direct, Point3D loc, Map map ) - { - if ( Deleted ) - return; - - Consume(); - - for ( int i = 0; Users != null && i < Users.Count; ++i ) - { - Mobile m = Users[i]; - - if ( m.Target is ThrowTarget targ && targ.Potion == this ) - Target.Cancel( m ); - } - - if ( map == null ) - return; - - Effects.PlaySound(loc, map, 0x307); - - Effects.SendLocationEffect(loc, map, 0x36B0, 9, 10, 0, 0); - int alchemyBonus = 0; - - if ( direct ) - alchemyBonus = (int)(from.Skills.Alchemy.Value / (Core.AOS ? 5 : 10)); + private class ThrowTarget : Target + { + public ThrowTarget(BaseExplosionPotion potion) : base(12, true, TargetFlags.None) + { + Potion = potion; + } - IPooledEnumerable eable = map.GetObjectsInRange(loc, ExplosionRange, LeveledExplosion, true); - List toExplode = new List(); + public BaseExplosionPotion Potion{ get; } - int toDamage = 0; + protected override void OnTarget(Mobile from, object targeted) + { + if (Potion.Deleted || Potion.Map == Map.Internal) + return; - foreach ( IEntity o in eable ) - { - if ( o is Mobile mobile && (from == null || (SpellHelper.ValidIndirectTarget( from, mobile ) && from.CanBeHarmful( mobile, false )))) - { - toExplode.Add( mobile ); - ++toDamage; - } - else if ( o is BaseExplosionPotion && o != this ) - { - toExplode.Add( o ); - } - } + if (!(targeted is IPoint3D p)) + return; - eable.Free(); + Map map = from.Map; - int min = Scale( from, MinDamage ); - int max = Scale( from, MaxDamage ); + if (map == null) + return; - for ( int i = 0; i < toExplode.Count; ++i ) - { - object o = toExplode[i]; + SpellHelper.GetSurfaceTop(ref p); - if ( o is Mobile m ) - { - from?.DoHarmful( m ); + from.RevealingAction(); - int damage = Utility.RandomMinMax( min, max ); + IEntity to = new Entity(Serial.Zero, new Point3D(p), map); - damage += alchemyBonus; + if (p is Mobile m) + { + if (!RelativeLocation) // explosion location = current mob location. + p = m.Location; + else + to = m; + } - if ( !Core.AOS && damage > 40 ) - damage = 40; - else if ( Core.AOS && toDamage > 2 ) - damage /= toDamage - 1; + Effects.SendMovingEffect(from, to, Potion.ItemID, 7, 0, false, false, Potion.Hue, 0); - AOS.Damage( m, from, damage, 0, 100, 0, 0, 0 ); - } - else if ( o is BaseExplosionPotion pot ) - { - pot.Explode( from, false, pot.GetWorldLocation(), pot.Map ); - } - } - } - } -} + if (Potion.Amount > 1) Mobile.LiftItemDupe(Potion, 1); + + Potion.Internalize(); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(Potion.Reposition_OnTick), + new object[] { from, p, map }); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/ExplosionPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/ExplosionPotion.cs index 5d8ce4ed9..125c75deb 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/ExplosionPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/ExplosionPotion.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class ExplosionPotion : BaseExplosionPotion - { - public override int MinDamage => 10; - public override int MaxDamage => 20; + public class ExplosionPotion : BaseExplosionPotion + { + [Constructible] + public ExplosionPotion() : base(PotionEffect.Explosion) + { + } - [Constructible] - public ExplosionPotion() : base( PotionEffect.Explosion ) - { - } + public ExplosionPotion(Serial serial) : base(serial) + { + } - public ExplosionPotion( Serial serial ) : base( serial ) - { - } + public override int MinDamage => 10; + public override int MaxDamage => 20; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/GreaterExplosionPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/GreaterExplosionPotion.cs index a3a8a11f8..de757decc 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/GreaterExplosionPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/GreaterExplosionPotion.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class GreaterExplosionPotion : BaseExplosionPotion - { - public override int MinDamage => Core.AOS ? 20 : 15; - public override int MaxDamage => Core.AOS ? 40 : 30; + public class GreaterExplosionPotion : BaseExplosionPotion + { + [Constructible] + public GreaterExplosionPotion() : base(PotionEffect.ExplosionGreater) + { + } - [Constructible] - public GreaterExplosionPotion() : base( PotionEffect.ExplosionGreater ) - { - } + public GreaterExplosionPotion(Serial serial) : base(serial) + { + } - public GreaterExplosionPotion( Serial serial ) : base( serial ) - { - } + public override int MinDamage => Core.AOS ? 20 : 15; + public override int MaxDamage => Core.AOS ? 40 : 30; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/LesserExplosionPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/LesserExplosionPotion.cs index fce098ab6..ffbd4ecaa 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/LesserExplosionPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Explosion Potions/LesserExplosionPotion.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class LesserExplosionPotion : BaseExplosionPotion - { - public override int MinDamage => 5; - public override int MaxDamage => 10; + public class LesserExplosionPotion : BaseExplosionPotion + { + [Constructible] + public LesserExplosionPotion() : base(PotionEffect.ExplosionLesser) + { + } - [Constructible] - public LesserExplosionPotion() : base( PotionEffect.ExplosionLesser ) - { - } + public LesserExplosionPotion(Serial serial) : base(serial) + { + } - public LesserExplosionPotion( Serial serial ) : base( serial ) - { - } + public override int MinDamage => 5; + public override int MaxDamage => 10; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/BaseHealPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/BaseHealPotion.cs index 6d50670fd..2ce8507fb 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/BaseHealPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/BaseHealPotion.cs @@ -1,80 +1,84 @@ using System; +using Server.Engines.ConPVP; using Server.Network; namespace Server.Items { - public abstract class BaseHealPotion : BasePotion - { - public abstract int MinHeal { get; } - public abstract int MaxHeal { get; } - public abstract double Delay { get; } + public abstract class BaseHealPotion : BasePotion + { + public BaseHealPotion(PotionEffect effect) : base(0xF0C, effect) + { + } - public BaseHealPotion( PotionEffect effect ) : base( 0xF0C, effect ) - { - } + public BaseHealPotion(Serial serial) : base(serial) + { + } - public BaseHealPotion( Serial serial ) : base( serial ) - { - } + public abstract int MinHeal{ get; } + public abstract int MaxHeal{ get; } + public abstract double Delay{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public void DoHeal( Mobile from ) - { - int min = Scale( from, MinHeal ); - int max = Scale( from, MaxHeal ); + public void DoHeal(Mobile from) + { + int min = Scale(from, MinHeal); + int max = Scale(from, MaxHeal); - from.Heal( Utility.RandomMinMax( min, max ) ); - } + from.Heal(Utility.RandomMinMax(min, max)); + } - public override void Drink( Mobile from ) - { - if ( from.Hits < from.HitsMax ) - { - if ( from.Poisoned || MortalStrike.IsWounded( from ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x22, 1005000 ); // You can not heal yourself in your current state. - } - else - { - if ( from.BeginAction( typeof( BaseHealPotion ) ) ) - { - DoHeal( from ); + public override void Drink(Mobile from) + { + if (from.Hits < from.HitsMax) + { + if (from.Poisoned || MortalStrike.IsWounded(from)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x22, + 1005000); // You can not heal yourself in your current state. + } + else + { + if (from.BeginAction(typeof(BaseHealPotion))) + { + DoHeal(from); - PlayDrinkEffect( from ); + PlayDrinkEffect(from); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); + if (!DuelContext.IsFreeConsume(from)) + Consume(); - Timer.DelayCall( TimeSpan.FromSeconds( Delay ), new TimerStateCallback( ReleaseHealLock ), from ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x22, 500235 ); // You must wait 10 seconds before using another healing potion. - } - } - } - else - { - from.SendLocalizedMessage( 1049547 ); // You decide against drinking this potion, as you are already at full health. - } - } + Timer.DelayCall(TimeSpan.FromSeconds(Delay), new TimerStateCallback(ReleaseHealLock), from); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x22, + 500235); // You must wait 10 seconds before using another healing potion. + } + } + } + else + { + from.SendLocalizedMessage( + 1049547); // You decide against drinking this potion, as you are already at full health. + } + } - private static void ReleaseHealLock( object state ) - { - ((Mobile)state).EndAction( typeof( BaseHealPotion ) ); - } - } + private static void ReleaseHealLock(object state) + { + ((Mobile)state).EndAction(typeof(BaseHealPotion)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/GreaterHealPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/GreaterHealPotion.cs index 1484cf3ce..ac89cb1e3 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/GreaterHealPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/GreaterHealPotion.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class GreaterHealPotion : BaseHealPotion - { - public override int MinHeal => (Core.AOS ? 20 : 9); - public override int MaxHeal => (Core.AOS ? 25 : 30); - public override double Delay => 10.0; + public class GreaterHealPotion : BaseHealPotion + { + [Constructible] + public GreaterHealPotion() : base(PotionEffect.HealGreater) + { + } - [Constructible] - public GreaterHealPotion() : base( PotionEffect.HealGreater ) - { - } + public GreaterHealPotion(Serial serial) : base(serial) + { + } - public GreaterHealPotion( Serial serial ) : base( serial ) - { - } + public override int MinHeal => Core.AOS ? 20 : 9; + public override int MaxHeal => Core.AOS ? 25 : 30; + public override double Delay => 10.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/HealPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/HealPotion.cs index aac144988..c25cc769d 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/HealPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/HealPotion.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class HealPotion : BaseHealPotion - { - public override int MinHeal => (Core.AOS ? 13 : 6); - public override int MaxHeal => (Core.AOS ? 16 : 20); - public override double Delay => (Core.AOS ? 8.0 : 10.0); + public class HealPotion : BaseHealPotion + { + [Constructible] + public HealPotion() : base(PotionEffect.Heal) + { + } - [Constructible] - public HealPotion() : base( PotionEffect.Heal ) - { - } + public HealPotion(Serial serial) : base(serial) + { + } - public HealPotion( Serial serial ) : base( serial ) - { - } + public override int MinHeal => Core.AOS ? 13 : 6; + public override int MaxHeal => Core.AOS ? 16 : 20; + public override double Delay => Core.AOS ? 8.0 : 10.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/LesserHealPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/LesserHealPotion.cs index ea3fedf30..b5389520a 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/LesserHealPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Heal Potions/LesserHealPotion.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class LesserHealPotion : BaseHealPotion - { - public override int MinHeal => (Core.AOS ? 6 : 3); - public override int MaxHeal => (Core.AOS ? 8 : 10); - public override double Delay => (Core.AOS ? 3.0 : 10.0); + public class LesserHealPotion : BaseHealPotion + { + [Constructible] + public LesserHealPotion() : base(PotionEffect.HealLesser) + { + } - [Constructible] - public LesserHealPotion() : base( PotionEffect.HealLesser ) - { - } + public LesserHealPotion(Serial serial) : base(serial) + { + } - public LesserHealPotion( Serial serial ) : base( serial ) - { - } + public override int MinHeal => Core.AOS ? 6 : 3; + public override int MaxHeal => Core.AOS ? 8 : 10; + public override double Delay => Core.AOS ? 3.0 : 10.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/InvisibilityPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/InvisibilityPotion.cs index 7f814a943..c0e7d99f6 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/InvisibilityPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/InvisibilityPotion.cs @@ -3,108 +3,109 @@ using System.Collections; namespace Server.Items { - public class InvisibilityPotion : BasePotion - { - public override int LabelNumber => 1072941; // Potion of Invisibility + public class InvisibilityPotion : BasePotion + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public InvisibilityPotion() : base( 0xF0A, PotionEffect.Invisibility ) - { - Hue = 0x48D; - } + [Constructible] + public InvisibilityPotion() : base(0xF0A, PotionEffect.Invisibility) + { + Hue = 0x48D; + } - public InvisibilityPotion( Serial serial ) : base( serial ) - { - } + public InvisibilityPotion(Serial serial) : base(serial) + { + } - public override void Drink( Mobile from ) - { - if ( from.Hidden ) - { - from.SendLocalizedMessage( 1073185 ); // You are already unseen. - return; - } + public override int LabelNumber => 1072941; // Potion of Invisibility - if ( HasTimer( from ) ) - { - from.SendLocalizedMessage( 1073186 ); // An invisibility potion is already taking effect on your person. - return; - } + public override void Drink(Mobile from) + { + if (from.Hidden) + { + from.SendLocalizedMessage(1073185); // You are already unseen. + return; + } - Consume(); - m_Table[ from ] = Timer.DelayCall( TimeSpan.FromSeconds( 2 ), new TimerStateCallback( Hide_Callback ), from ); - PlayDrinkEffect( from ); - } + if (HasTimer(from)) + { + from.SendLocalizedMessage(1073186); // An invisibility potion is already taking effect on your person. + return; + } - private static void Hide_Callback( object obj ) - { - if ( obj is Mobile mobile ) - Hide( mobile ); - } + Consume(); + m_Table[from] = Timer.DelayCall(TimeSpan.FromSeconds(2), new TimerStateCallback(Hide_Callback), from); + PlayDrinkEffect(from); + } - public static void Hide( Mobile m ) - { - Effects.SendLocationParticles( EffectItem.Create( new Point3D( m.X, m.Y, m.Z + 16 ), m.Map, EffectItem.DefaultDuration ), 0x376A, 10, 15, 5045 ); - m.PlaySound( 0x3C4 ); + private static void Hide_Callback(object obj) + { + if (obj is Mobile mobile) + Hide(mobile); + } - m.Hidden = true; + public static void Hide(Mobile m) + { + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(m.X, m.Y, m.Z + 16), m.Map, EffectItem.DefaultDuration), 0x376A, 10, 15, 5045); + m.PlaySound(0x3C4); - BuffInfo.RemoveBuff( m, BuffIcon.HidingAndOrStealth ); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Invisibility, 1075825 ) ); //Invisibility/Invisible + m.Hidden = true; - RemoveTimer( m ); + BuffInfo.RemoveBuff(m, BuffIcon.HidingAndOrStealth); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Invisibility, 1075825)); //Invisibility/Invisible - Timer.DelayCall( TimeSpan.FromSeconds( 30 ), new TimerStateCallback( EndHide_Callback ), m ); - } + RemoveTimer(m); - private static void EndHide_Callback( object obj ) - { - if ( obj is Mobile mobile ) - EndHide( mobile ); - } + Timer.DelayCall(TimeSpan.FromSeconds(30), new TimerStateCallback(EndHide_Callback), m); + } - public static void EndHide( Mobile m ) - { - m.RevealingAction(); - RemoveTimer( m ); - } + private static void EndHide_Callback(object obj) + { + if (obj is Mobile mobile) + EndHide(mobile); + } - private static Hashtable m_Table = new Hashtable(); + public static void EndHide(Mobile m) + { + m.RevealingAction(); + RemoveTimer(m); + } - public static bool HasTimer( Mobile m ) - { - return m_Table[ m ] != null; - } + public static bool HasTimer(Mobile m) + { + return m_Table[m] != null; + } - public static void RemoveTimer( Mobile m ) - { - Timer t = (Timer) m_Table[ m ]; + public static void RemoveTimer(Mobile m) + { + Timer t = (Timer)m_Table[m]; - if ( t != null ) - { - t.Stop(); - m_Table.Remove( m ); - } - } + if (t != null) + { + t.Stop(); + m_Table.Remove(m); + } + } - public static void Iterrupt( Mobile m ) - { - m.SendLocalizedMessage( 1073187 ); // The invisibility effect is interrupted. - RemoveTimer( m ); - } + public static void Iterrupt(Mobile m) + { + m.SendLocalizedMessage(1073187); // The invisibility effect is interrupted. + RemoveTimer(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/NightSight.cs b/Scripts/Items/Skill Items/Magical/Potions/NightSight.cs index d8037844c..e9ba57ebd 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/NightSight.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/NightSight.cs @@ -1,49 +1,51 @@ +using Server.Engines.ConPVP; + namespace Server.Items { - public class NightSightPotion : BasePotion - { - [Constructible] - public NightSightPotion() : base( 0xF06, PotionEffect.Nightsight ) - { - } + public class NightSightPotion : BasePotion + { + [Constructible] + public NightSightPotion() : base(0xF06, PotionEffect.Nightsight) + { + } - public NightSightPotion( Serial serial ) : base( serial ) - { - } + public NightSightPotion(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Drink( Mobile from ) - { - if ( from.BeginAction( typeof( LightCycle ) ) ) - { - new LightCycle.NightSightTimer( from ).Start(); - from.LightLevel = LightCycle.DungeonLevel / 2; + public override void Drink(Mobile from) + { + if (from.BeginAction(typeof(LightCycle))) + { + new LightCycle.NightSightTimer(from).Start(); + from.LightLevel = LightCycle.DungeonLevel / 2; - from.FixedParticles( 0x376A, 9, 32, 5007, EffectLayer.Waist ); - from.PlaySound( 0x1E3 ); + from.FixedParticles(0x376A, 9, 32, 5007, EffectLayer.Waist); + from.PlaySound(0x1E3); - PlayDrinkEffect( from ); + PlayDrinkEffect(from); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); - } - else - { - from.SendMessage( "You already have nightsight." ); - } - } - } + if (!DuelContext.IsFreeConsume(from)) + Consume(); + } + else + { + from.SendMessage("You already have nightsight."); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/ParasiticPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/ParasiticPotion.cs index 183446058..3aa405262 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/ParasiticPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/ParasiticPotion.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class ParasiticPotion : BasePoisonPotion - { - /* public override Poison Poison => Poison.Darkglow; MUST be restored when prerequisites are done */ - public override Poison Poison => Poison.Greater; + public class ParasiticPotion : BasePoisonPotion + { + [Constructible] + public ParasiticPotion() : base(PotionEffect.Parasitic) + { + Hue = 0x17C; + } - public override double MinPoisoningSkill => 95.0; - public override double MaxPoisoningSkill => 100.0; + public ParasiticPotion(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1072848; // Parasitic Poison + /* public override Poison Poison => Poison.Darkglow; MUST be restored when prerequisites are done */ + public override Poison Poison => Poison.Greater; - [Constructible] - public ParasiticPotion() : base( PotionEffect.Parasitic ) - { - Hue = 0x17C; - } + public override double MinPoisoningSkill => 95.0; + public override double MaxPoisoningSkill => 100.0; - public ParasiticPotion( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072848; // Parasitic Poison - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/BasePoisonPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/BasePoisonPotion.cs index 05530c8d5..732b51735 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/BasePoisonPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/BasePoisonPotion.cs @@ -1,47 +1,49 @@ +using Server.Engines.ConPVP; + namespace Server.Items { - public abstract class BasePoisonPotion : BasePotion - { - public abstract Poison Poison{ get; } + public abstract class BasePoisonPotion : BasePotion + { + public BasePoisonPotion(PotionEffect effect) : base(0xF0A, effect) + { + } - public abstract double MinPoisoningSkill{ get; } - public abstract double MaxPoisoningSkill{ get; } + public BasePoisonPotion(Serial serial) : base(serial) + { + } - public BasePoisonPotion( PotionEffect effect ) : base( 0xF0A, effect ) - { - } + public abstract Poison Poison{ get; } - public BasePoisonPotion( Serial serial ) : base( serial ) - { - } + public abstract double MinPoisoningSkill{ get; } + public abstract double MaxPoisoningSkill{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public void DoPoison( Mobile from ) - { - from.ApplyPoison( from, Poison ); - } + public void DoPoison(Mobile from) + { + from.ApplyPoison(from, Poison); + } - public override void Drink( Mobile from ) - { - DoPoison( from ); + public override void Drink(Mobile from) + { + DoPoison(from); - PlayDrinkEffect( from ); + PlayDrinkEffect(from); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); - } - } + if (!DuelContext.IsFreeConsume(from)) + Consume(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/DeadlyPoisonPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/DeadlyPoisonPotion.cs index f7925f578..43c99c4dd 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/DeadlyPoisonPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/DeadlyPoisonPotion.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class DeadlyPoisonPotion : BasePoisonPotion - { - public override Poison Poison => Poison.Deadly; + public class DeadlyPoisonPotion : BasePoisonPotion + { + [Constructible] + public DeadlyPoisonPotion() : base(PotionEffect.PoisonDeadly) + { + } - public override double MinPoisoningSkill => 95.0; - public override double MaxPoisoningSkill => 100.0; + public DeadlyPoisonPotion(Serial serial) : base(serial) + { + } - [Constructible] - public DeadlyPoisonPotion() : base( PotionEffect.PoisonDeadly ) - { - } + public override Poison Poison => Poison.Deadly; - public DeadlyPoisonPotion( Serial serial ) : base( serial ) - { - } + public override double MinPoisoningSkill => 95.0; + public override double MaxPoisoningSkill => 100.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/GreaterPoisonPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/GreaterPoisonPotion.cs index 99c581cd3..8c81a142d 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/GreaterPoisonPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/GreaterPoisonPotion.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class GreaterPoisonPotion : BasePoisonPotion - { - public override Poison Poison => Poison.Greater; + public class GreaterPoisonPotion : BasePoisonPotion + { + [Constructible] + public GreaterPoisonPotion() : base(PotionEffect.PoisonGreater) + { + } - public override double MinPoisoningSkill => 60.0; - public override double MaxPoisoningSkill => 100.0; + public GreaterPoisonPotion(Serial serial) : base(serial) + { + } - [Constructible] - public GreaterPoisonPotion() : base( PotionEffect.PoisonGreater ) - { - } + public override Poison Poison => Poison.Greater; - public GreaterPoisonPotion( Serial serial ) : base( serial ) - { - } + public override double MinPoisoningSkill => 60.0; + public override double MaxPoisoningSkill => 100.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/LesserPoisonPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/LesserPoisonPotion.cs index 9841db6ad..6d21bb4b7 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/LesserPoisonPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/LesserPoisonPotion.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class LesserPoisonPotion : BasePoisonPotion - { - public override Poison Poison => Poison.Lesser; + public class LesserPoisonPotion : BasePoisonPotion + { + [Constructible] + public LesserPoisonPotion() : base(PotionEffect.PoisonLesser) + { + } - public override double MinPoisoningSkill => 0.0; - public override double MaxPoisoningSkill => 60.0; + public LesserPoisonPotion(Serial serial) : base(serial) + { + } - [Constructible] - public LesserPoisonPotion() : base( PotionEffect.PoisonLesser ) - { - } + public override Poison Poison => Poison.Lesser; - public LesserPoisonPotion( Serial serial ) : base( serial ) - { - } + public override double MinPoisoningSkill => 0.0; + public override double MaxPoisoningSkill => 60.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/PoisonPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/PoisonPotion.cs index a60ffda29..97165ef5d 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/PoisonPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Poison Potions/PoisonPotion.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class PoisonPotion : BasePoisonPotion - { - public override Poison Poison => Poison.Regular; + public class PoisonPotion : BasePoisonPotion + { + [Constructible] + public PoisonPotion() : base(PotionEffect.Poison) + { + } - public override double MinPoisoningSkill => 30.0; - public override double MaxPoisoningSkill => 70.0; + public PoisonPotion(Serial serial) : base(serial) + { + } - [Constructible] - public PoisonPotion() : base( PotionEffect.Poison ) - { - } + public override Poison Poison => Poison.Regular; - public PoisonPotion( Serial serial ) : base( serial ) - { - } + public override double MinPoisoningSkill => 30.0; + public override double MaxPoisoningSkill => 70.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/BaseRefreshPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/BaseRefreshPotion.cs index 3315cd37d..464f98995 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/BaseRefreshPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/BaseRefreshPotion.cs @@ -1,46 +1,48 @@ +using Server.Engines.ConPVP; + namespace Server.Items { - public abstract class BaseRefreshPotion : BasePotion - { - public abstract double Refresh{ get; } + public abstract class BaseRefreshPotion : BasePotion + { + public BaseRefreshPotion(PotionEffect effect) : base(0xF0B, effect) + { + } - public BaseRefreshPotion( PotionEffect effect ) : base( 0xF0B, effect ) - { - } + public BaseRefreshPotion(Serial serial) : base(serial) + { + } - public BaseRefreshPotion( Serial serial ) : base( serial ) - { - } + public abstract double Refresh{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Drink( Mobile from ) - { - if ( from.Stam < from.StamMax ) - { - from.Stam += Scale( from, (int)(Refresh * from.StamMax) ); + public override void Drink(Mobile from) + { + if (from.Stam < from.StamMax) + { + from.Stam += Scale(from, (int)(Refresh * from.StamMax)); - PlayDrinkEffect( from ); + PlayDrinkEffect(from); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); - } - else - { - from.SendMessage( "You decide against drinking this potion, as you are already at full stamina." ); - } - } - } + if (!DuelContext.IsFreeConsume(from)) + Consume(); + } + else + { + from.SendMessage("You decide against drinking this potion, as you are already at full stamina."); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/RefreshPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/RefreshPotion.cs index 8e2a7b72a..3cbe2bce8 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/RefreshPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/RefreshPotion.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class RefreshPotion : BaseRefreshPotion - { - public override double Refresh => 0.25; + public class RefreshPotion : BaseRefreshPotion + { + [Constructible] + public RefreshPotion() : base(PotionEffect.Refresh) + { + } - [Constructible] - public RefreshPotion() : base( PotionEffect.Refresh ) - { - } + public RefreshPotion(Serial serial) : base(serial) + { + } - public RefreshPotion( Serial serial ) : base( serial ) - { - } + public override double Refresh => 0.25; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/TotalRefreshPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/TotalRefreshPotion.cs index 73785c38b..9da7f55f7 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/TotalRefreshPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Refresh Potions/TotalRefreshPotion.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class TotalRefreshPotion : BaseRefreshPotion - { - public override double Refresh => 1.0; + public class TotalRefreshPotion : BaseRefreshPotion + { + [Constructible] + public TotalRefreshPotion() : base(PotionEffect.RefreshTotal) + { + } - [Constructible] - public TotalRefreshPotion() : base( PotionEffect.RefreshTotal ) - { - } + public TotalRefreshPotion(Serial serial) : base(serial) + { + } - public TotalRefreshPotion( Serial serial ) : base( serial ) - { - } + public override double Refresh => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/BaseStrengthPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/BaseStrengthPotion.cs index 21bdd2af7..eff2fca5a 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/BaseStrengthPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/BaseStrengthPotion.cs @@ -1,57 +1,59 @@ using System; +using Server.Engines.ConPVP; +using Server.Spells; namespace Server.Items { - public abstract class BaseStrengthPotion : BasePotion - { - public abstract int StrOffset{ get; } - public abstract TimeSpan Duration{ get; } + public abstract class BaseStrengthPotion : BasePotion + { + public BaseStrengthPotion(PotionEffect effect) : base(0xF09, effect) + { + } - public BaseStrengthPotion( PotionEffect effect ) : base( 0xF09, effect ) - { - } + public BaseStrengthPotion(Serial serial) : base(serial) + { + } - public BaseStrengthPotion( Serial serial ) : base( serial ) - { - } + public abstract int StrOffset{ get; } + public abstract TimeSpan Duration{ get; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public bool DoStrength( Mobile from ) - { - // TODO: Verify scaled; is it offset, duration, or both? - if ( Spells.SpellHelper.AddStatOffset( from, StatType.Str, Scale( from, StrOffset ), Duration ) ) - { - from.FixedEffect( 0x375A, 10, 15 ); - from.PlaySound( 0x1E7 ); - return true; - } + public bool DoStrength(Mobile from) + { + // TODO: Verify scaled; is it offset, duration, or both? + if (SpellHelper.AddStatOffset(from, StatType.Str, Scale(from, StrOffset), Duration)) + { + from.FixedEffect(0x375A, 10, 15); + from.PlaySound(0x1E7); + return true; + } - from.SendLocalizedMessage( 502173 ); // You are already under a similar effect. - return false; - } + from.SendLocalizedMessage(502173); // You are already under a similar effect. + return false; + } - public override void Drink( Mobile from ) - { - if ( DoStrength( from ) ) - { - PlayDrinkEffect( from ); + public override void Drink(Mobile from) + { + if (DoStrength(from)) + { + PlayDrinkEffect(from); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - Consume(); - } - } - } + if (!DuelContext.IsFreeConsume(from)) + Consume(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/GreaterStrengthPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/GreaterStrengthPotion.cs index 90a87eedf..95b6066cd 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/GreaterStrengthPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/GreaterStrengthPotion.cs @@ -2,32 +2,32 @@ using System; namespace Server.Items { - public class GreaterStrengthPotion : BaseStrengthPotion - { - public override int StrOffset => 20; - public override TimeSpan Duration => TimeSpan.FromMinutes( 2.0 ); + public class GreaterStrengthPotion : BaseStrengthPotion + { + [Constructible] + public GreaterStrengthPotion() : base(PotionEffect.StrengthGreater) + { + } - [Constructible] - public GreaterStrengthPotion() : base( PotionEffect.StrengthGreater ) - { - } + public GreaterStrengthPotion(Serial serial) : base(serial) + { + } - public GreaterStrengthPotion( Serial serial ) : base( serial ) - { - } + public override int StrOffset => 20; + public override TimeSpan Duration => TimeSpan.FromMinutes(2.0); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/StrengthPotion.cs b/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/StrengthPotion.cs index eb60a84dd..2237792f7 100644 --- a/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/StrengthPotion.cs +++ b/Scripts/Items/Skill Items/Magical/Potions/Strength Potions/StrengthPotion.cs @@ -2,32 +2,32 @@ using System; namespace Server.Items { - public class StrengthPotion : BaseStrengthPotion - { - public override int StrOffset => 10; - public override TimeSpan Duration => TimeSpan.FromMinutes( 2.0 ); + public class StrengthPotion : BaseStrengthPotion + { + [Constructible] + public StrengthPotion() : base(PotionEffect.Strength) + { + } - [Constructible] - public StrengthPotion() : base( PotionEffect.Strength ) - { - } + public StrengthPotion(Serial serial) : base(serial) + { + } - public StrengthPotion( Serial serial ) : base( serial ) - { - } + public override int StrOffset => 10; + public override TimeSpan Duration => TimeSpan.FromMinutes(2.0); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Runebook.cs b/Scripts/Items/Skill Items/Magical/Runebook.cs index 24521e5a2..5b1ec9bb4 100644 --- a/Scripts/Items/Skill Items/Magical/Runebook.cs +++ b/Scripts/Items/Skill Items/Magical/Runebook.cs @@ -1,480 +1,486 @@ using System; using System.Collections.Generic; +using Server.ContextMenus; +using Server.Engines.Craft; using Server.Gumps; -using Server.Network; using Server.Mobiles; using Server.Multis; -using Server.Engines.Craft; -using Server.ContextMenus; +using Server.Network; namespace Server.Items { - public class Runebook : Item, ISecurable, ICraftable - { - public static readonly TimeSpan UseDelay = TimeSpan.FromSeconds( 7.0 ); - - private BookQuality m_Quality; - - [CommandProperty( AccessLevel.GameMaster )] - public BookQuality Quality - { - get => m_Quality; - set{ m_Quality = value; InvalidateProperties(); } - } - - private string m_Description; - private int m_DefaultIndex; - private Mobile m_Crafter; - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextUse { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } + public class Runebook : Item, ISecurable, ICraftable + { + public static readonly TimeSpan UseDelay = TimeSpan.FromSeconds(7.0); + private Mobile m_Crafter; + private int m_DefaultIndex; + + private string m_Description; + + private BookQuality m_Quality; + + [Constructible] + public Runebook(int maxCharges) : base(Core.AOS ? 0x22C5 : 0xEFA) + { + Weight = Core.SE ? 1.0 : 3.0; + LootType = LootType.Blessed; + Hue = 0x461; + + Layer = Core.AOS ? Layer.Invalid : Layer.OneHanded; + + Entries = new List(); + + MaxCharges = maxCharges; + + m_DefaultIndex = -1; + + Level = SecureLevel.CoOwners; + } + + [Constructible] + public Runebook() : this(Core.SE ? 12 : 6) + { + } + + public Runebook(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public BookQuality Quality + { + get => m_Quality; + set + { + m_Quality = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextUse{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public string Description - { - get => m_Description; - set - { - m_Description = value; - InvalidateProperties(); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public string Description + { + get => m_Description; + set + { + m_Description = value; + InvalidateProperties(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public int CurCharges { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int CurCharges{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int MaxCharges { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxCharges{ get; set; } - public List Openers { get; set; } = new List(); + public List Openers{ get; set; } = new List(); - public override int LabelNumber => 1041267; // runebook + public override int LabelNumber => 1041267; // runebook - [Constructible] - public Runebook( int maxCharges ) : base( Core.AOS ? 0x22C5 : 0xEFA ) - { - Weight = (Core.SE ? 1.0 : 3.0); - LootType = LootType.Blessed; - Hue = 0x461; - - Layer = (Core.AOS ? Layer.Invalid : Layer.OneHanded); - - Entries = new List(); - - MaxCharges = maxCharges; - - m_DefaultIndex = -1; - - Level = SecureLevel.CoOwners; - } - - [Constructible] - public Runebook() : this( Core.SE ? 12 : 6 ) - { - } - - public List Entries { get; private set; } - - public RunebookEntry Default - { - get - { - if ( m_DefaultIndex >= 0 && m_DefaultIndex < Entries.Count ) - return Entries[m_DefaultIndex]; - - return null; - } - set - { - if ( value == null ) - m_DefaultIndex = -1; - else - m_DefaultIndex = Entries.IndexOf( value ); - } - } - - public Runebook( Serial serial ) : base( serial ) - { - } - - public override bool AllowEquippedCast( Mobile from ) - { - return true; - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 3 ); - - writer.Write( (byte) m_Quality ); - - writer.Write( m_Crafter ); - - writer.Write( (int) Level ); - - writer.Write( Entries.Count ); - - for ( int i = 0; i < Entries.Count; ++i ) - Entries[i].Serialize( writer ); - - writer.Write( m_Description ); - writer.Write( CurCharges ); - writer.Write( MaxCharges ); - writer.Write( m_DefaultIndex ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public List Entries{ get; private set; } - LootType = LootType.Blessed; + public RunebookEntry Default + { + get + { + if (m_DefaultIndex >= 0 && m_DefaultIndex < Entries.Count) + return Entries[m_DefaultIndex]; + + return null; + } + set + { + if (value == null) + m_DefaultIndex = -1; + else + m_DefaultIndex = Entries.IndexOf(value); + } + } + + public override bool DisplayLootType => Core.AOS; + + #region ICraftable Members + + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + int charges = 5 + quality + (int)(from.Skills[SkillName.Inscribe].Value / 30); + + if (charges > 10) + charges = 10; + + MaxCharges = Core.SE ? charges * 2 : charges; + + if (makersMark) + Crafter = from; + + m_Quality = (BookQuality)(quality - 1); + + return quality; + } + + #endregion + + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } + + public override bool AllowEquippedCast(Mobile from) + { + return true; + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(3); - if ( Core.SE && Weight == 3.0 ) - Weight = 1.0; + writer.Write((byte)m_Quality); + + writer.Write(m_Crafter); - int version = reader.ReadInt(); + writer.Write((int)Level); + + writer.Write(Entries.Count); - switch ( version ) - { - case 3: - { - m_Quality = (BookQuality) reader.ReadByte(); - goto case 2; - } - case 2: - { - m_Crafter = reader.ReadMobile(); - goto case 1; - } - case 1: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 0; - } - case 0: - { - int count = reader.ReadInt(); - - Entries = new List( count ); - - for ( int i = 0; i < count; ++i ) - Entries.Add( new RunebookEntry( reader ) ); - - m_Description = reader.ReadString(); - CurCharges = reader.ReadInt(); - MaxCharges = reader.ReadInt(); - m_DefaultIndex = reader.ReadInt(); - - break; - } - } - } - - public void DropRune( Mobile from, RunebookEntry e, int index ) - { - if ( m_DefaultIndex > index ) - m_DefaultIndex -= 1; - else if ( m_DefaultIndex == index ) - m_DefaultIndex = -1; - - Entries.RemoveAt( index ); - - RecallRune rune = new RecallRune(); - - rune.Target = e.Location; - rune.TargetMap = e.Map; - rune.Description = e.Description; - rune.House = e.House; - rune.Marked = true; - - from.AddToBackpack( rune ); - - from.SendLocalizedMessage( 502421 ); // You have removed the rune. - } - - public bool IsOpen( Mobile toCheck ) - { - NetState ns = toCheck.NetState; - - if (ns == null) - return false; - - foreach ( Gump gump in ns.Gumps ) - { - if ( gump is RunebookGump bookGump && bookGump.Book == this ) - { - return true; - } - } - - return false; - } - - public override bool DisplayLootType => Core.AOS; - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_Quality == BookQuality.Exceptional ) - list.Add( 1063341 ); // exceptional - - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ - - if ( !string.IsNullOrEmpty(m_Description) ) - list.Add( m_Description ); - } - - public override bool OnDragLift( Mobile from ) - { - if ( from.HasGump( typeof( RunebookGump ) ) ) - { - from.SendLocalizedMessage( 500169 ); // You cannot pick that up. - return false; - } - - foreach ( Mobile m in Openers ) - if ( IsOpen( m ) ) - m.CloseGump( typeof( RunebookGump ) ); - - Openers.Clear(); - - return true; - } - - public override void OnSingleClick( Mobile from ) - { - if ( m_Description != null && m_Description.Length > 0 ) - LabelTo( from, m_Description ); - - base.OnSingleClick( from ); - - if ( m_Crafter != null ) - LabelTo( from, 1050043, m_Crafter.Name ); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), (Core.ML ? 3 : 1) ) && CheckAccess( from ) ) - { - if ( RootParent is BaseCreature ) - { - from.SendLocalizedMessage( 502402 ); // That is inaccessible. - return; - } - - if ( DateTime.UtcNow < NextUse ) - { - from.SendLocalizedMessage( 502406 ); // This book needs time to recharge. - return; - } - - from.CloseGump( typeof( RunebookGump ) ); - from.SendGump( new RunebookGump( from, this ) ); - - Openers.Add( from ); - } - } - - public virtual void OnTravel() - { - if ( !Core.SA ) - NextUse = DateTime.UtcNow + UseDelay; - } - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is Runebook book) ) - return; - - book.Entries = new List(); - - for ( int i = 0; i < Entries.Count; i++ ) - { - RunebookEntry entry = Entries[i]; - - book.Entries.Add( new RunebookEntry( entry.Location, entry.Map, entry.Description, entry.House ) ); - } - } - - public bool CheckAccess( Mobile m ) - { - if ( !IsLockedDown || m.AccessLevel >= AccessLevel.GameMaster ) - return true; - - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null && house.IsAosRules && (house.Public ? house.IsBanned( m ) : !house.HasAccess( m )) ) - return false; - - return ( house != null && house.HasSecureAccess( m, Level ) ); - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is RecallRune rune ) - { - if ( IsLockedDown && from.AccessLevel < AccessLevel.GameMaster ) - { - from.SendLocalizedMessage( 502413, null, 0x35 ); // That cannot be done while the book is locked down. - } - else if ( IsOpen( from ) ) - { - from.SendLocalizedMessage( 1005571 ); // You cannot place objects in the book while viewing the contents. - } - else if ( Entries.Count < 16 ) - { - if ( rune.Marked && rune.TargetMap != null ) - { - Entries.Add( new RunebookEntry( rune.Target, rune.TargetMap, rune.Description, rune.House ) ); - - rune.Delete(); - - from.Send( new PlaySound( 0x42, GetWorldLocation() ) ); - - string desc = rune.Description; - - if ( desc == null || (desc = desc.Trim()).Length == 0 ) - desc = "(indescript)"; - - from.SendMessage( desc ); - - return true; - } - - from.SendLocalizedMessage( 502409 ); // This rune does not have a marked location. - } - else - { - from.SendLocalizedMessage( 502401 ); // This runebook is full. - } - } - else if ( dropped is RecallScroll ) - { - if ( CurCharges < MaxCharges ) - { - from.Send( new PlaySound( 0x249, GetWorldLocation() ) ); - - int amount = dropped.Amount; - - if ( amount > (MaxCharges - CurCharges) ) - { - dropped.Consume( MaxCharges - CurCharges ); - CurCharges = MaxCharges; - } - else - { - CurCharges += amount; - dropped.Delete(); - - return true; - } - } - else - { - from.SendLocalizedMessage( 502410 ); // This book already has the maximum amount of charges. - } - } - - return false; - } - #region ICraftable Members - - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - int charges = 5 + quality + (int)(from.Skills[SkillName.Inscribe].Value / 30); - - if ( charges > 10 ) - charges = 10; - - MaxCharges = (Core.SE ? charges * 2 : charges); - - if ( makersMark ) - Crafter = from; - - m_Quality = (BookQuality) ( quality - 1 ); - - return quality; - } - - #endregion - } - - public class RunebookEntry - { - public Point3D Location { get; } - - public Map Map { get; } - - public string Description { get; } - - public BaseHouse House { get; } - - public RunebookEntry( Point3D loc, Map map, string desc, BaseHouse house ) - { - Location = loc; - Map = map; - Description = desc; - House = house; - } - - public RunebookEntry( GenericReader reader ) - { - int version = reader.ReadByte(); - - switch ( version ) - { - case 1: - { - House = reader.ReadItem() as BaseHouse; - goto case 0; - } - case 0: - { - Location = reader.ReadPoint3D(); - Map = reader.ReadMap(); - Description = reader.ReadString(); - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - if ( House != null && !House.Deleted ) - { - writer.Write( (byte) 1 ); // version - - writer.Write( House ); - } - else - { - writer.Write( (byte) 0 ); // version - } - - writer.Write( Location ); - writer.Write( Map ); - writer.Write( Description ); - } - } -} + for (int i = 0; i < Entries.Count; ++i) + Entries[i].Serialize(writer); + + writer.Write(m_Description); + writer.Write(CurCharges); + writer.Write(MaxCharges); + writer.Write(m_DefaultIndex); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + LootType = LootType.Blessed; + + if (Core.SE && Weight == 3.0) + Weight = 1.0; + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + m_Quality = (BookQuality)reader.ReadByte(); + goto case 2; + } + case 2: + { + m_Crafter = reader.ReadMobile(); + goto case 1; + } + case 1: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 0; + } + case 0: + { + int count = reader.ReadInt(); + + Entries = new List(count); + + for (int i = 0; i < count; ++i) + Entries.Add(new RunebookEntry(reader)); + + m_Description = reader.ReadString(); + CurCharges = reader.ReadInt(); + MaxCharges = reader.ReadInt(); + m_DefaultIndex = reader.ReadInt(); + + break; + } + } + } + + public void DropRune(Mobile from, RunebookEntry e, int index) + { + if (m_DefaultIndex > index) + m_DefaultIndex -= 1; + else if (m_DefaultIndex == index) + m_DefaultIndex = -1; + + Entries.RemoveAt(index); + + RecallRune rune = new RecallRune(); + + rune.Target = e.Location; + rune.TargetMap = e.Map; + rune.Description = e.Description; + rune.House = e.House; + rune.Marked = true; + + from.AddToBackpack(rune); + + from.SendLocalizedMessage(502421); // You have removed the rune. + } + + public bool IsOpen(Mobile toCheck) + { + NetState ns = toCheck.NetState; + + if (ns == null) + return false; + + foreach (Gump gump in ns.Gumps) + if (gump is RunebookGump bookGump && bookGump.Book == this) + return true; + + return false; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Quality == BookQuality.Exceptional) + list.Add(1063341); // exceptional + + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ + + if (!string.IsNullOrEmpty(m_Description)) + list.Add(m_Description); + } + + public override bool OnDragLift(Mobile from) + { + if (from.HasGump(typeof(RunebookGump))) + { + from.SendLocalizedMessage(500169); // You cannot pick that up. + return false; + } + + foreach (Mobile m in Openers) + if (IsOpen(m)) + m.CloseGump(typeof(RunebookGump)); + + Openers.Clear(); + + return true; + } + + public override void OnSingleClick(Mobile from) + { + if (m_Description != null && m_Description.Length > 0) + LabelTo(from, m_Description); + + base.OnSingleClick(from); + + if (m_Crafter != null) + LabelTo(from, 1050043, m_Crafter.Name); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), Core.ML ? 3 : 1) && CheckAccess(from)) + { + if (RootParent is BaseCreature) + { + from.SendLocalizedMessage(502402); // That is inaccessible. + return; + } + + if (DateTime.UtcNow < NextUse) + { + from.SendLocalizedMessage(502406); // This book needs time to recharge. + return; + } + + from.CloseGump(typeof(RunebookGump)); + from.SendGump(new RunebookGump(from, this)); + + Openers.Add(from); + } + } + + public virtual void OnTravel() + { + if (!Core.SA) + NextUse = DateTime.UtcNow + UseDelay; + } + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is Runebook book)) + return; + + book.Entries = new List(); + + for (int i = 0; i < Entries.Count; i++) + { + RunebookEntry entry = Entries[i]; + + book.Entries.Add(new RunebookEntry(entry.Location, entry.Map, entry.Description, entry.House)); + } + } + + public bool CheckAccess(Mobile m) + { + if (!IsLockedDown || m.AccessLevel >= AccessLevel.GameMaster) + return true; + + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsAosRules && (house.Public ? house.IsBanned(m) : !house.HasAccess(m))) + return false; + + return house != null && house.HasSecureAccess(m, Level); + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is RecallRune rune) + { + if (IsLockedDown && from.AccessLevel < AccessLevel.GameMaster) + { + from.SendLocalizedMessage(502413, null, 0x35); // That cannot be done while the book is locked down. + } + else if (IsOpen(from)) + { + from.SendLocalizedMessage(1005571); // You cannot place objects in the book while viewing the contents. + } + else if (Entries.Count < 16) + { + if (rune.Marked && rune.TargetMap != null) + { + Entries.Add(new RunebookEntry(rune.Target, rune.TargetMap, rune.Description, rune.House)); + + rune.Delete(); + + from.Send(new PlaySound(0x42, GetWorldLocation())); + + string desc = rune.Description; + + if (desc == null || (desc = desc.Trim()).Length == 0) + desc = "(indescript)"; + + from.SendMessage(desc); + + return true; + } + + from.SendLocalizedMessage(502409); // This rune does not have a marked location. + } + else + { + from.SendLocalizedMessage(502401); // This runebook is full. + } + } + else if (dropped is RecallScroll) + { + if (CurCharges < MaxCharges) + { + from.Send(new PlaySound(0x249, GetWorldLocation())); + + int amount = dropped.Amount; + + if (amount > MaxCharges - CurCharges) + { + dropped.Consume(MaxCharges - CurCharges); + CurCharges = MaxCharges; + } + else + { + CurCharges += amount; + dropped.Delete(); + + return true; + } + } + else + { + from.SendLocalizedMessage(502410); // This book already has the maximum amount of charges. + } + } + + return false; + } + } + + public class RunebookEntry + { + public RunebookEntry(Point3D loc, Map map, string desc, BaseHouse house) + { + Location = loc; + Map = map; + Description = desc; + House = house; + } + + public RunebookEntry(GenericReader reader) + { + int version = reader.ReadByte(); + + switch (version) + { + case 1: + { + House = reader.ReadItem() as BaseHouse; + goto case 0; + } + case 0: + { + Location = reader.ReadPoint3D(); + Map = reader.ReadMap(); + Description = reader.ReadString(); + + break; + } + } + } + + public Point3D Location{ get; } + + public Map Map{ get; } + + public string Description{ get; } + + public BaseHouse House{ get; } + + public void Serialize(GenericWriter writer) + { + if (House != null && !House.Deleted) + { + writer.Write((byte)1); // version + + writer.Write(House); + } + else + { + writer.Write((byte)0); // version + } + + writer.Write(Location); + writer.Write(Map); + writer.Write(Description); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EarthquakeScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EarthquakeScroll.cs index c35703ac1..3ab21547b 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EarthquakeScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EarthquakeScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class EarthquakeScroll : SpellScroll - { - [Constructible] - public EarthquakeScroll() : this( 1 ) - { - } + public class EarthquakeScroll : SpellScroll + { + [Constructible] + public EarthquakeScroll() : this(1) + { + } - [Constructible] - public EarthquakeScroll( int amount ) : base( 56, 0x1F65, amount ) - { - } + [Constructible] + public EarthquakeScroll(int amount) : base(56, 0x1F65, amount) + { + } - public EarthquakeScroll( Serial serial ) : base( serial ) - { - } + public EarthquakeScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EnergyVortexScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EnergyVortexScroll.cs index bc3acf9b3..da96ce56a 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EnergyVortexScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/EnergyVortexScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class EnergyVortexScroll : SpellScroll - { - [Constructible] - public EnergyVortexScroll() : this( 1 ) - { - } + public class EnergyVortexScroll : SpellScroll + { + [Constructible] + public EnergyVortexScroll() : this(1) + { + } - [Constructible] - public EnergyVortexScroll( int amount ) : base( 57, 0x1F66, amount ) - { - } + [Constructible] + public EnergyVortexScroll(int amount) : base(57, 0x1F66, amount) + { + } - public EnergyVortexScroll( Serial serial ) : base( serial ) - { - } + public EnergyVortexScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/ResurrectionScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/ResurrectionScroll.cs index ac8ae22b6..2e1567889 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/ResurrectionScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/ResurrectionScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ResurrectionScroll : SpellScroll - { - [Constructible] - public ResurrectionScroll() : this( 1 ) - { - } + public class ResurrectionScroll : SpellScroll + { + [Constructible] + public ResurrectionScroll() : this(1) + { + } - [Constructible] - public ResurrectionScroll( int amount ) : base( 58, 0x1F67, amount ) - { - } + [Constructible] + public ResurrectionScroll(int amount) : base(58, 0x1F67, amount) + { + } - public ResurrectionScroll( Serial serial ) : base( serial ) - { - } + public ResurrectionScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonAirElementalScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonAirElementalScroll.cs index eabd26288..c339a17c1 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonAirElementalScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonAirElementalScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonAirElementalScroll : SpellScroll - { - [Constructible] - public SummonAirElementalScroll() : this( 1 ) - { - } + public class SummonAirElementalScroll : SpellScroll + { + [Constructible] + public SummonAirElementalScroll() : this(1) + { + } - [Constructible] - public SummonAirElementalScroll( int amount ) : base( 59, 0x1F68, amount ) - { - } + [Constructible] + public SummonAirElementalScroll(int amount) : base(59, 0x1F68, amount) + { + } - public SummonAirElementalScroll( Serial serial ) : base( serial ) - { - } + public SummonAirElementalScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonDaemonScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonDaemonScroll.cs index 00e79007c..c916db1e6 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonDaemonScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonDaemonScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonDaemonScroll : SpellScroll - { - [Constructible] - public SummonDaemonScroll() : this( 1 ) - { - } + public class SummonDaemonScroll : SpellScroll + { + [Constructible] + public SummonDaemonScroll() : this(1) + { + } - [Constructible] - public SummonDaemonScroll( int amount ) : base( 60, 0x1F69, amount ) - { - } + [Constructible] + public SummonDaemonScroll(int amount) : base(60, 0x1F69, amount) + { + } - public SummonDaemonScroll( Serial serial ) : base( serial ) - { - } + public SummonDaemonScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonEarthElementalScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonEarthElementalScroll.cs index 5c3e2b37b..316a067e0 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonEarthElementalScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonEarthElementalScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonEarthElementalScroll : SpellScroll - { - [Constructible] - public SummonEarthElementalScroll() : this( 1 ) - { - } + public class SummonEarthElementalScroll : SpellScroll + { + [Constructible] + public SummonEarthElementalScroll() : this(1) + { + } - [Constructible] - public SummonEarthElementalScroll( int amount ) : base( 61, 0x1F6A, amount ) - { - } + [Constructible] + public SummonEarthElementalScroll(int amount) : base(61, 0x1F6A, amount) + { + } - public SummonEarthElementalScroll( Serial serial ) : base( serial ) - { - } + public SummonEarthElementalScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonFireElementalScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonFireElementalScroll.cs index 1c97cb5dc..a2e01d6b7 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonFireElementalScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonFireElementalScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonFireElementalScroll : SpellScroll - { - [Constructible] - public SummonFireElementalScroll() : this( 1 ) - { - } + public class SummonFireElementalScroll : SpellScroll + { + [Constructible] + public SummonFireElementalScroll() : this(1) + { + } - [Constructible] - public SummonFireElementalScroll( int amount ) : base( 62, 0x1F6B, amount ) - { - } + [Constructible] + public SummonFireElementalScroll(int amount) : base(62, 0x1F6B, amount) + { + } - public SummonFireElementalScroll( Serial serial ) : base( serial ) - { - } + public SummonFireElementalScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonWaterElementalScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonWaterElementalScroll.cs index bd294dfce..25ca9d75b 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonWaterElementalScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Eighth Circle/SummonWaterElementalScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonWaterElementalScroll : SpellScroll - { - [Constructible] - public SummonWaterElementalScroll() : this( 1 ) - { - } + public class SummonWaterElementalScroll : SpellScroll + { + [Constructible] + public SummonWaterElementalScroll() : this(1) + { + } - [Constructible] - public SummonWaterElementalScroll( int amount ) : base( 63, 0x1F6C, amount ) - { - } + [Constructible] + public SummonWaterElementalScroll(int amount) : base(63, 0x1F6C, amount) + { + } - public SummonWaterElementalScroll( Serial serial ) : base( serial ) - { - } + public SummonWaterElementalScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/BladeSpiritsScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/BladeSpiritsScroll.cs index dd22dd45c..cf94e46b0 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/BladeSpiritsScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/BladeSpiritsScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class BladeSpiritsScroll : SpellScroll - { - [Constructible] - public BladeSpiritsScroll() : this( 1 ) - { - } + public class BladeSpiritsScroll : SpellScroll + { + [Constructible] + public BladeSpiritsScroll() : this(1) + { + } - [Constructible] - public BladeSpiritsScroll( int amount ) : base( 32, 0x1F4D, amount ) - { - } + [Constructible] + public BladeSpiritsScroll(int amount) : base(32, 0x1F4D, amount) + { + } - public BladeSpiritsScroll( Serial serial ) : base( serial ) - { - } + public BladeSpiritsScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/DispelFieldScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/DispelFieldScroll.cs index adeb06821..5cd507af9 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/DispelFieldScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/DispelFieldScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class DispelFieldScroll : SpellScroll - { - [Constructible] - public DispelFieldScroll() : this( 1 ) - { - } + public class DispelFieldScroll : SpellScroll + { + [Constructible] + public DispelFieldScroll() : this(1) + { + } - [Constructible] - public DispelFieldScroll( int amount ) : base( 33, 0x1F4E, amount ) - { - } + [Constructible] + public DispelFieldScroll(int amount) : base(33, 0x1F4E, amount) + { + } - public DispelFieldScroll( Serial serial ) : base( serial ) - { - } + public DispelFieldScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/IncognitoScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/IncognitoScroll.cs index 0fa583f6a..26cf51c68 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/IncognitoScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/IncognitoScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class IncognitoScroll : SpellScroll - { - [Constructible] - public IncognitoScroll() : this( 1 ) - { - } + public class IncognitoScroll : SpellScroll + { + [Constructible] + public IncognitoScroll() : this(1) + { + } - [Constructible] - public IncognitoScroll( int amount ) : base( 34, 0x1F4F, amount ) - { - } + [Constructible] + public IncognitoScroll(int amount) : base(34, 0x1F4F, amount) + { + } - public IncognitoScroll( Serial serial ) : base( serial ) - { - } + public IncognitoScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MagicReflectScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MagicReflectScroll.cs index c4b54502a..8f363e550 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MagicReflectScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MagicReflectScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MagicReflectScroll : SpellScroll - { - [Constructible] - public MagicReflectScroll() : this( 1 ) - { - } + public class MagicReflectScroll : SpellScroll + { + [Constructible] + public MagicReflectScroll() : this(1) + { + } - [Constructible] - public MagicReflectScroll( int amount ) : base( 35, 0x1F50, amount ) - { - } + [Constructible] + public MagicReflectScroll(int amount) : base(35, 0x1F50, amount) + { + } - public MagicReflectScroll( Serial serial ) : base( serial ) - { - } + public MagicReflectScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MindBlastScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MindBlastScroll.cs index 6f1e12833..0eb741ba5 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MindBlastScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/MindBlastScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MindBlastScroll : SpellScroll - { - [Constructible] - public MindBlastScroll() : this( 1 ) - { - } + public class MindBlastScroll : SpellScroll + { + [Constructible] + public MindBlastScroll() : this(1) + { + } - [Constructible] - public MindBlastScroll( int amount ) : base( 36, 0x1F51, amount ) - { - } + [Constructible] + public MindBlastScroll(int amount) : base(36, 0x1F51, amount) + { + } - public MindBlastScroll( Serial serial ) : base( serial ) - { - } + public MindBlastScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/ParalyzeScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/ParalyzeScroll.cs index cf8a3a4d4..98ae2513b 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/ParalyzeScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/ParalyzeScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ParalyzeScroll : SpellScroll - { - [Constructible] - public ParalyzeScroll() : this( 1 ) - { - } + public class ParalyzeScroll : SpellScroll + { + [Constructible] + public ParalyzeScroll() : this(1) + { + } - [Constructible] - public ParalyzeScroll( int amount ) : base( 37, 0x1F52, amount ) - { - } - - public ParalyzeScroll( Serial serial ) : base( serial ) - { - } + [Constructible] + public ParalyzeScroll(int amount) : base(37, 0x1F52, amount) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public ParalyzeScroll(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/PoisonFieldScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/PoisonFieldScroll.cs index 56005e0c7..3a802c176 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/PoisonFieldScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/PoisonFieldScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class PoisonFieldScroll : SpellScroll - { - [Constructible] - public PoisonFieldScroll() : this( 1 ) - { - } + public class PoisonFieldScroll : SpellScroll + { + [Constructible] + public PoisonFieldScroll() : this(1) + { + } - [Constructible] - public PoisonFieldScroll( int amount ) : base( 38, 0x1F53, amount ) - { - } + [Constructible] + public PoisonFieldScroll(int amount) : base(38, 0x1F53, amount) + { + } - public PoisonFieldScroll( Serial serial ) : base( serial ) - { - } + public PoisonFieldScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/SummonCreatureScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/SummonCreatureScroll.cs index 40a1b620c..2144a41aa 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/SummonCreatureScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fifth Circle/SummonCreatureScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonCreatureScroll : SpellScroll - { - [Constructible] - public SummonCreatureScroll() : this( 1 ) - { - } + public class SummonCreatureScroll : SpellScroll + { + [Constructible] + public SummonCreatureScroll() : this(1) + { + } - [Constructible] - public SummonCreatureScroll( int amount ) : base( 39, 0x1F54, amount ) - { - } + [Constructible] + public SummonCreatureScroll(int amount) : base(39, 0x1F54, amount) + { + } - public SummonCreatureScroll( Serial serial ) : base( serial ) - { - } + public SummonCreatureScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ClumsyScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ClumsyScroll.cs index 195ad2ea1..17889990f 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ClumsyScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ClumsyScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ClumsyScroll : SpellScroll - { - [Constructible] - public ClumsyScroll() : this( 1 ) - { - } + public class ClumsyScroll : SpellScroll + { + [Constructible] + public ClumsyScroll() : this(1) + { + } - [Constructible] - public ClumsyScroll( int amount ) : base( 0, 0x1F2E, amount ) - { - } + [Constructible] + public ClumsyScroll(int amount) : base(0, 0x1F2E, amount) + { + } - public ClumsyScroll( Serial serial ) : base( serial ) - { - } + public ClumsyScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/CreateFoodScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/CreateFoodScroll.cs index d4d0555aa..169d8bbbf 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/CreateFoodScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/CreateFoodScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class CreateFoodScroll : SpellScroll - { - [Constructible] - public CreateFoodScroll() : this( 1 ) - { - } + public class CreateFoodScroll : SpellScroll + { + [Constructible] + public CreateFoodScroll() : this(1) + { + } - [Constructible] - public CreateFoodScroll( int amount ) : base( 1, 0x1F2F, amount ) - { - } + [Constructible] + public CreateFoodScroll(int amount) : base(1, 0x1F2F, amount) + { + } - public CreateFoodScroll( Serial serial ) : base( serial ) - { - } + public CreateFoodScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/FeeblemindScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/FeeblemindScroll.cs index e696b511b..7c401fa69 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/FeeblemindScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/FeeblemindScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class FeeblemindScroll : SpellScroll - { - [Constructible] - public FeeblemindScroll() : this( 1 ) - { - } + public class FeeblemindScroll : SpellScroll + { + [Constructible] + public FeeblemindScroll() : this(1) + { + } - [Constructible] - public FeeblemindScroll( int amount ) : base( 2, 0x1F30, amount ) - { - } + [Constructible] + public FeeblemindScroll(int amount) : base(2, 0x1F30, amount) + { + } - public FeeblemindScroll( Serial serial ) : base( serial ) - { - } + public FeeblemindScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/HealScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/HealScroll.cs index db1b91d00..5e0162ee3 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/HealScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/HealScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class HealScroll : SpellScroll - { - [Constructible] - public HealScroll() : this( 1 ) - { - } + public class HealScroll : SpellScroll + { + [Constructible] + public HealScroll() : this(1) + { + } - [Constructible] - public HealScroll( int amount ) : base( 3, 0x1F31, amount ) - { - } + [Constructible] + public HealScroll(int amount) : base(3, 0x1F31, amount) + { + } - public HealScroll( Serial serial ) : base( serial ) - { - } + public HealScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/MagicArrowScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/MagicArrowScroll.cs index b68e60c74..ca01564cf 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/MagicArrowScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/MagicArrowScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MagicArrowScroll : SpellScroll - { - [Constructible] - public MagicArrowScroll() : this( 1 ) - { - } + public class MagicArrowScroll : SpellScroll + { + [Constructible] + public MagicArrowScroll() : this(1) + { + } - [Constructible] - public MagicArrowScroll( int amount ) : base( 4, 0x1F32, amount ) - { - } - - public MagicArrowScroll( Serial serial ) : base( serial ) - { - } + [Constructible] + public MagicArrowScroll(int amount) : base(4, 0x1F32, amount) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public MagicArrowScroll(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/NightSightScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/NightSightScroll.cs index 6260ec973..803b3ec97 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/NightSightScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/NightSightScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class NightSightScroll : SpellScroll - { - [Constructible] - public NightSightScroll() : this( 1 ) - { - } + public class NightSightScroll : SpellScroll + { + [Constructible] + public NightSightScroll() : this(1) + { + } - [Constructible] - public NightSightScroll( int amount ) : base( 5, 0x1F33, amount ) - { - } + [Constructible] + public NightSightScroll(int amount) : base(5, 0x1F33, amount) + { + } - public NightSightScroll( Serial ser ) : base(ser) - { - } + public NightSightScroll(Serial ser) : base(ser) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ReactiveArmorScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ReactiveArmorScroll.cs index e5bfcf95f..7c94295db 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ReactiveArmorScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/ReactiveArmorScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ReactiveArmorScroll : SpellScroll - { - [Constructible] - public ReactiveArmorScroll() : this( 1 ) - { - } + public class ReactiveArmorScroll : SpellScroll + { + [Constructible] + public ReactiveArmorScroll() : this(1) + { + } - [Constructible] - public ReactiveArmorScroll( int amount ) : base( 6, 0x1F2D, amount ) - { - } + [Constructible] + public ReactiveArmorScroll(int amount) : base(6, 0x1F2D, amount) + { + } - public ReactiveArmorScroll( Serial ser ) : base(ser) - { - } + public ReactiveArmorScroll(Serial ser) : base(ser) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/WeakenScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/WeakenScroll.cs index 99368490b..c61a744b0 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/WeakenScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/First Circle/WeakenScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class WeakenScroll : SpellScroll - { - [Constructible] - public WeakenScroll() : this( 1 ) - { - } + public class WeakenScroll : SpellScroll + { + [Constructible] + public WeakenScroll() : this(1) + { + } - [Constructible] - public WeakenScroll( int amount ) : base( 7, 0x1F34, amount ) - { - } + [Constructible] + public WeakenScroll(int amount) : base(7, 0x1F34, amount) + { + } - public WeakenScroll( Serial serial ) : base( serial ) - { - } + public WeakenScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchProtectionScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchProtectionScroll.cs index d89c51e1f..dfbb655ab 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchProtectionScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchProtectionScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ArchProtectionScroll : SpellScroll - { - [Constructible] - public ArchProtectionScroll() : this( 1 ) - { - } + public class ArchProtectionScroll : SpellScroll + { + [Constructible] + public ArchProtectionScroll() : this(1) + { + } - [Constructible] - public ArchProtectionScroll( int amount ) : base( 25, 0x1F46, amount ) - { - } + [Constructible] + public ArchProtectionScroll(int amount) : base(25, 0x1F46, amount) + { + } - public ArchProtectionScroll( Serial serial ) : base( serial ) - { - } + public ArchProtectionScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchcureScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchcureScroll.cs index 857dc2b8e..a3620c902 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchcureScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ArchcureScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ArchCureScroll : SpellScroll - { - [Constructible] - public ArchCureScroll() : this( 1 ) - { - } + public class ArchCureScroll : SpellScroll + { + [Constructible] + public ArchCureScroll() : this(1) + { + } - [Constructible] - public ArchCureScroll( int amount ) : base( 24, 0x1F45, amount ) - { - } + [Constructible] + public ArchCureScroll(int amount) : base(24, 0x1F45, amount) + { + } - public ArchCureScroll( Serial serial ) : base( serial ) - { - } + public ArchCureScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/CurseScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/CurseScroll.cs index e0601061d..8f1e95059 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/CurseScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/CurseScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class CurseScroll : SpellScroll - { - [Constructible] - public CurseScroll() : this( 1 ) - { - } + public class CurseScroll : SpellScroll + { + [Constructible] + public CurseScroll() : this(1) + { + } - [Constructible] - public CurseScroll( int amount ) : base( 26, 0x1F47, amount ) - { - } + [Constructible] + public CurseScroll(int amount) : base(26, 0x1F47, amount) + { + } - public CurseScroll( Serial serial ) : base( serial ) - { - } + public CurseScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/FireFieldScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/FireFieldScroll.cs index de4de8c6d..9bc93b857 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/FireFieldScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/FireFieldScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class FireFieldScroll : SpellScroll - { - [Constructible] - public FireFieldScroll() : this( 1 ) - { - } + public class FireFieldScroll : SpellScroll + { + [Constructible] + public FireFieldScroll() : this(1) + { + } - [Constructible] - public FireFieldScroll( int amount ) : base( 27, 0x1F48, amount ) - { - } + [Constructible] + public FireFieldScroll(int amount) : base(27, 0x1F48, amount) + { + } - public FireFieldScroll( Serial serial ) : base( serial ) - { - } + public FireFieldScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/GreaterHealScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/GreaterHealScroll.cs index c50d2c05c..4776f90a0 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/GreaterHealScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/GreaterHealScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class GreaterHealScroll : SpellScroll - { - [Constructible] - public GreaterHealScroll() : this( 1 ) - { - } + public class GreaterHealScroll : SpellScroll + { + [Constructible] + public GreaterHealScroll() : this(1) + { + } - [Constructible] - public GreaterHealScroll( int amount ) : base( 28, 0x1F49, amount ) - { - } + [Constructible] + public GreaterHealScroll(int amount) : base(28, 0x1F49, amount) + { + } - public GreaterHealScroll( Serial serial ) : base( serial ) - { - } + public GreaterHealScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/LightningScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/LightningScroll.cs index 6043f83f1..e6ea3ae4b 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/LightningScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/LightningScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class LightningScroll : SpellScroll - { - [Constructible] - public LightningScroll() : this( 1 ) - { - } + public class LightningScroll : SpellScroll + { + [Constructible] + public LightningScroll() : this(1) + { + } - [Constructible] - public LightningScroll( int amount ) : base( 29, 0x1F4A, amount ) - { - } + [Constructible] + public LightningScroll(int amount) : base(29, 0x1F4A, amount) + { + } - public LightningScroll( Serial serial ) : base( serial ) - { - } + public LightningScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ManaDrainScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ManaDrainScroll.cs index d3a9939f6..02592afc3 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ManaDrainScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/ManaDrainScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ManaDrainScroll : SpellScroll - { - [Constructible] - public ManaDrainScroll() : this( 1 ) - { - } + public class ManaDrainScroll : SpellScroll + { + [Constructible] + public ManaDrainScroll() : this(1) + { + } - [Constructible] - public ManaDrainScroll( int amount ) : base( 30, 0x1F4B, amount ) - { - } + [Constructible] + public ManaDrainScroll(int amount) : base(30, 0x1F4B, amount) + { + } - public ManaDrainScroll( Serial serial ) : base( serial ) - { - } + public ManaDrainScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/RecallScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/RecallScroll.cs index 5b8b2d9a0..ae7ca9542 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/RecallScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Fourth Circle/RecallScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class RecallScroll : SpellScroll - { - [Constructible] - public RecallScroll() : this( 1 ) - { - } + public class RecallScroll : SpellScroll + { + [Constructible] + public RecallScroll() : this(1) + { + } - [Constructible] - public RecallScroll( int amount ) : base( 31, 0x1F4C, amount ) - { - } + [Constructible] + public RecallScroll(int amount) : base(31, 0x1F4C, amount) + { + } - public RecallScroll( Serial serial ) : base( serial ) - { - } + public RecallScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/AnimatedWeaponScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/AnimatedWeaponScroll.cs index 433a741cc..a91cf2c35 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/AnimatedWeaponScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/AnimatedWeaponScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class AnimatedWeaponScroll : SpellScroll - { - [Constructible] - public AnimatedWeaponScroll() - : this( 1 ) - { - } + public class AnimatedWeaponScroll : SpellScroll + { + [Constructible] + public AnimatedWeaponScroll() + : this(1) + { + } - [Constructible] - public AnimatedWeaponScroll( int amount ) - : base( 683, 0x2DA4, amount ) - { - } + [Constructible] + public AnimatedWeaponScroll(int amount) + : base(683, 0x2DA4, amount) + { + } - public AnimatedWeaponScroll( Serial serial ) - : base( serial ) - { - } + public AnimatedWeaponScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/BombardScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/BombardScroll.cs index 964d62385..c2915c518 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/BombardScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/BombardScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class BombardScroll : SpellScroll - { - [Constructible] - public BombardScroll() - : this( 1 ) - { - } + public class BombardScroll : SpellScroll + { + [Constructible] + public BombardScroll() + : this(1) + { + } - [Constructible] - public BombardScroll( int amount ) - : base( 688, 0x2DA9, amount ) - { - } + [Constructible] + public BombardScroll(int amount) + : base(688, 0x2DA9, amount) + { + } - public BombardScroll( Serial serial ) - : base( serial ) - { - } + public BombardScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/CleansingWindsScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/CleansingWindsScroll.cs index 3280f70c3..799c0eeb2 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/CleansingWindsScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/CleansingWindsScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class CleansingWindsScroll : SpellScroll - { - [Constructible] - public CleansingWindsScroll() - : this( 1 ) - { - } + public class CleansingWindsScroll : SpellScroll + { + [Constructible] + public CleansingWindsScroll() + : this(1) + { + } - [Constructible] - public CleansingWindsScroll( int amount ) - : base( 687, 0x2DA8, amount ) - { - } + [Constructible] + public CleansingWindsScroll(int amount) + : base(687, 0x2DA8, amount) + { + } - public CleansingWindsScroll( Serial serial ) - : base( serial ) - { - } + public CleansingWindsScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EagleStrikeScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EagleStrikeScroll.cs index 0c8b16d80..ca925c2c9 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EagleStrikeScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EagleStrikeScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class EagleStrikeScroll : SpellScroll - { - [Constructible] - public EagleStrikeScroll() - : this( 1 ) - { - } + public class EagleStrikeScroll : SpellScroll + { + [Constructible] + public EagleStrikeScroll() + : this(1) + { + } - [Constructible] - public EagleStrikeScroll( int amount ) - : base( 682, 0x2DA3, amount ) - { - } + [Constructible] + public EagleStrikeScroll(int amount) + : base(682, 0x2DA3, amount) + { + } - public EagleStrikeScroll( Serial serial ) - : base( serial ) - { - } + public EagleStrikeScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EnchantScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EnchantScroll.cs index 1aa901ce2..30ade7cad 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EnchantScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/EnchantScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class EnchantScroll : SpellScroll - { - [Constructible] - public EnchantScroll() - : this( 1 ) - { - } + public class EnchantScroll : SpellScroll + { + [Constructible] + public EnchantScroll() + : this(1) + { + } - [Constructible] - public EnchantScroll( int amount ) - : base( 680, 0x2DA1, amount ) - { - } + [Constructible] + public EnchantScroll(int amount) + : base(680, 0x2DA1, amount) + { + } - public EnchantScroll( Serial serial ) - : base( serial ) - { - } + public EnchantScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HailStormScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HailStormScroll.cs index e21b60467..18b87ba69 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HailStormScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HailStormScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class HailStormScroll : SpellScroll - { - [Constructible] - public HailStormScroll() - : this( 1 ) - { - } + public class HailStormScroll : SpellScroll + { + [Constructible] + public HailStormScroll() + : this(1) + { + } - [Constructible] - public HailStormScroll( int amount ) - : base( 690, 0x2DAB, amount ) - { - } + [Constructible] + public HailStormScroll(int amount) + : base(690, 0x2DAB, amount) + { + } - public HailStormScroll( Serial serial ) - : base( serial ) - { - } + public HailStormScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HealingStoneScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HealingStoneScroll.cs index 8f9c82a17..8dd510fa7 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HealingStoneScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/HealingStoneScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class HealingStoneScroll : SpellScroll - { - [Constructible] - public HealingStoneScroll() - : this( 1 ) - { - } + public class HealingStoneScroll : SpellScroll + { + [Constructible] + public HealingStoneScroll() + : this(1) + { + } - [Constructible] - public HealingStoneScroll( int amount ) - : base( 678, 0x2D9F, amount ) - { - } + [Constructible] + public HealingStoneScroll(int amount) + : base(678, 0x2D9F, amount) + { + } - public HealingStoneScroll( Serial serial ) - : base( serial ) - { - } + public HealingStoneScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/MassSleepScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/MassSleepScroll.cs index 4c70aebb0..c849cb1ee 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/MassSleepScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/MassSleepScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class MassSleepScroll : SpellScroll - { - [Constructible] - public MassSleepScroll() - : this( 1 ) - { - } + public class MassSleepScroll : SpellScroll + { + [Constructible] + public MassSleepScroll() + : this(1) + { + } - [Constructible] - public MassSleepScroll( int amount ) - : base( 686, 0x2DA7, amount ) - { - } + [Constructible] + public MassSleepScroll(int amount) + : base(686, 0x2DA7, amount) + { + } - public MassSleepScroll( Serial serial ) - : base( serial ) - { - } + public MassSleepScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherBoltScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherBoltScroll.cs index 42755bc3b..0cca48558 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherBoltScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherBoltScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class NetherBoltScroll : SpellScroll - { - [Constructible] - public NetherBoltScroll() - : this( 1 ) - { - } + public class NetherBoltScroll : SpellScroll + { + [Constructible] + public NetherBoltScroll() + : this(1) + { + } - [Constructible] - public NetherBoltScroll( int amount ) - : base( 677, 0x2D9E, amount ) - { - } + [Constructible] + public NetherBoltScroll(int amount) + : base(677, 0x2D9E, amount) + { + } - public NetherBoltScroll( Serial serial ) - : base( serial ) - { - } + public NetherBoltScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherCycloneScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherCycloneScroll.cs index 57dc5ba41..320aae763 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherCycloneScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/NetherCycloneScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class NetherCycloneScroll : SpellScroll - { - [Constructible] - public NetherCycloneScroll() - : this( 1 ) - { - } + public class NetherCycloneScroll : SpellScroll + { + [Constructible] + public NetherCycloneScroll() + : this(1) + { + } - [Constructible] - public NetherCycloneScroll( int amount ) - : base( 691, 0x2DAC, amount ) - { - } + [Constructible] + public NetherCycloneScroll(int amount) + : base(691, 0x2DAC, amount) + { + } - public NetherCycloneScroll( Serial serial ) - : base( serial ) - { - } + public NetherCycloneScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/PurgeMagicScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/PurgeMagicScroll.cs index 779302a34..7a313035d 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/PurgeMagicScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/PurgeMagicScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class PurgeMagicScroll : SpellScroll - { - [Constructible] - public PurgeMagicScroll() - : this( 1 ) - { - } + public class PurgeMagicScroll : SpellScroll + { + [Constructible] + public PurgeMagicScroll() + : this(1) + { + } - [Constructible] - public PurgeMagicScroll( int amount ) - : base( 679, 0x2DA0, amount ) - { - } + [Constructible] + public PurgeMagicScroll(int amount) + : base(679, 0x2DA0, amount) + { + } - public PurgeMagicScroll( Serial serial ) - : base( serial ) - { - } + public PurgeMagicScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/RisingColossusScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/RisingColossusScroll.cs index fe8037d85..1a364fdfc 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/RisingColossusScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/RisingColossusScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class RisingColossusScroll : SpellScroll - { - [Constructible] - public RisingColossusScroll() - : this( 1 ) - { - } + public class RisingColossusScroll : SpellScroll + { + [Constructible] + public RisingColossusScroll() + : this(1) + { + } - [Constructible] - public RisingColossusScroll( int amount ) - : base( 692, 0x2DAD, amount ) - { - } + [Constructible] + public RisingColossusScroll(int amount) + : base(692, 0x2DAD, amount) + { + } - public RisingColossusScroll( Serial serial ) - : base( serial ) - { - } + public RisingColossusScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SleepScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SleepScroll.cs index be3b56abc..1e102867e 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SleepScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SleepScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class SleepScroll : SpellScroll - { - [Constructible] - public SleepScroll() - : this( 1 ) - { - } + public class SleepScroll : SpellScroll + { + [Constructible] + public SleepScroll() + : this(1) + { + } - [Constructible] - public SleepScroll( int amount ) - : base( 681, 0x2DA2, amount ) - { - } + [Constructible] + public SleepScroll(int amount) + : base(681, 0x2DA2, amount) + { + } - public SleepScroll( Serial serial ) - : base( serial ) - { - } + public SleepScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellPlagueScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellPlagueScroll.cs index b00efbedf..4cc306f8a 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellPlagueScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellPlagueScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class SpellPlagueScroll : SpellScroll - { - [Constructible] - public SpellPlagueScroll() - : this( 1 ) - { - } + public class SpellPlagueScroll : SpellScroll + { + [Constructible] + public SpellPlagueScroll() + : this(1) + { + } - [Constructible] - public SpellPlagueScroll( int amount ) - : base( 689, 0x2DAA, amount ) - { - } + [Constructible] + public SpellPlagueScroll(int amount) + : base(689, 0x2DAA, amount) + { + } - public SpellPlagueScroll( Serial serial ) - : base( serial ) - { - } + public SpellPlagueScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellTriggerScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellTriggerScroll.cs index 7f21fefa3..facc8063c 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellTriggerScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/SpellTriggerScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class SpellTriggerScroll : SpellScroll - { - [Constructible] - public SpellTriggerScroll() - : this( 1 ) - { - } + public class SpellTriggerScroll : SpellScroll + { + [Constructible] + public SpellTriggerScroll() + : this(1) + { + } - [Constructible] - public SpellTriggerScroll( int amount ) - : base( 685, 0x2DA6, amount ) - { - } + [Constructible] + public SpellTriggerScroll(int amount) + : base(685, 0x2DA6, amount) + { + } - public SpellTriggerScroll( Serial serial ) - : base( serial ) - { - } + public SpellTriggerScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/StoneFormScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/StoneFormScroll.cs index 02b0d68cf..7baf86c43 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/StoneFormScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Mysticism/StoneFormScroll.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class StoneFormScroll : SpellScroll - { - [Constructible] - public StoneFormScroll() - : this( 1 ) - { - } + public class StoneFormScroll : SpellScroll + { + [Constructible] + public StoneFormScroll() + : this(1) + { + } - [Constructible] - public StoneFormScroll( int amount ) - : base( 684, 0x2DA5, amount ) - { - } + [Constructible] + public StoneFormScroll(int amount) + : base(684, 0x2DA5, amount) + { + } - public StoneFormScroll( Serial serial ) - : base( serial ) - { - } + public StoneFormScroll(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/AnimateDeadScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/AnimateDeadScroll.cs index 0c1a9a682..c1667d406 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/AnimateDeadScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/AnimateDeadScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class AnimateDeadScroll : SpellScroll - { - [Constructible] - public AnimateDeadScroll() : this( 1 ) - { - } + public class AnimateDeadScroll : SpellScroll + { + [Constructible] + public AnimateDeadScroll() : this(1) + { + } - [Constructible] - public AnimateDeadScroll( int amount ) : base( 100, 0x2260, amount ) - { - } + [Constructible] + public AnimateDeadScroll(int amount) : base(100, 0x2260, amount) + { + } - public AnimateDeadScroll( Serial serial ) : base( serial ) - { - } + public AnimateDeadScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/BloodOathScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/BloodOathScroll.cs index 92c671ee6..28a45013d 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/BloodOathScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/BloodOathScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class BloodOathScroll : SpellScroll - { - [Constructible] - public BloodOathScroll() : this( 1 ) - { - } + public class BloodOathScroll : SpellScroll + { + [Constructible] + public BloodOathScroll() : this(1) + { + } - [Constructible] - public BloodOathScroll( int amount ) : base( 101, 0x2261, amount ) - { - } + [Constructible] + public BloodOathScroll(int amount) : base(101, 0x2261, amount) + { + } - public BloodOathScroll( Serial serial ) : base( serial ) - { - } + public BloodOathScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CorpseSkinScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CorpseSkinScroll.cs index 30fb5737f..3560736e1 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CorpseSkinScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CorpseSkinScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class CorpseSkinScroll : SpellScroll - { - [Constructible] - public CorpseSkinScroll() : this( 1 ) - { - } + public class CorpseSkinScroll : SpellScroll + { + [Constructible] + public CorpseSkinScroll() : this(1) + { + } - [Constructible] - public CorpseSkinScroll( int amount ) : base( 102, 0x2262, amount ) - { - } + [Constructible] + public CorpseSkinScroll(int amount) : base(102, 0x2262, amount) + { + } - public CorpseSkinScroll( Serial serial ) : base( serial ) - { - } + public CorpseSkinScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CurseWeaponScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CurseWeaponScroll.cs index 2e389be2a..cabcf4666 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CurseWeaponScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/CurseWeaponScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class CurseWeaponScroll : SpellScroll - { - [Constructible] - public CurseWeaponScroll() : this( 1 ) - { - } + public class CurseWeaponScroll : SpellScroll + { + [Constructible] + public CurseWeaponScroll() : this(1) + { + } - [Constructible] - public CurseWeaponScroll( int amount ) : base( 103, 0x2263, amount ) - { - } + [Constructible] + public CurseWeaponScroll(int amount) : base(103, 0x2263, amount) + { + } - public CurseWeaponScroll( Serial serial ) : base( serial ) - { - } + public CurseWeaponScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/EvilOmenScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/EvilOmenScroll.cs index 61c7770d2..a90ddb7ca 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/EvilOmenScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/EvilOmenScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class EvilOmenScroll : SpellScroll - { - [Constructible] - public EvilOmenScroll() : this( 1 ) - { - } + public class EvilOmenScroll : SpellScroll + { + [Constructible] + public EvilOmenScroll() : this(1) + { + } - [Constructible] - public EvilOmenScroll( int amount ) : base( 104, 0x2264, amount ) - { - } + [Constructible] + public EvilOmenScroll(int amount) : base(104, 0x2264, amount) + { + } - public EvilOmenScroll( Serial serial ) : base( serial ) - { - } + public EvilOmenScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/ExorcismScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/ExorcismScroll.cs index 8405d7c4f..0a439d3eb 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/ExorcismScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/ExorcismScroll.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class ExorcismScroll : SpellScroll - { - [Constructible] - public ExorcismScroll() : this( 1 ) - { - } + public class ExorcismScroll : SpellScroll + { + [Constructible] + public ExorcismScroll() : this(1) + { + } - [Constructible] - public ExorcismScroll( int amount ) : base( 116, 0x2270, amount ) - { - } + [Constructible] + public ExorcismScroll(int amount) : base(116, 0x2270, amount) + { + } - public ExorcismScroll( Serial serial ) : base( serial ) - { - } + public ExorcismScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/HorrificBeastScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/HorrificBeastScroll.cs index e83043fee..6f4193133 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/HorrificBeastScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/HorrificBeastScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class HorrificBeastScroll : SpellScroll - { - [Constructible] - public HorrificBeastScroll() : this( 1 ) - { - } + public class HorrificBeastScroll : SpellScroll + { + [Constructible] + public HorrificBeastScroll() : this(1) + { + } - [Constructible] - public HorrificBeastScroll( int amount ) : base( 105, 0x2265, amount ) - { - } + [Constructible] + public HorrificBeastScroll(int amount) : base(105, 0x2265, amount) + { + } - public HorrificBeastScroll( Serial serial ) : base( serial ) - { - } + public HorrificBeastScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/LichFormScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/LichFormScroll.cs index e2f451276..18bc20215 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/LichFormScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/LichFormScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class LichFormScroll : SpellScroll - { - [Constructible] - public LichFormScroll() : this( 1 ) - { - } + public class LichFormScroll : SpellScroll + { + [Constructible] + public LichFormScroll() : this(1) + { + } - [Constructible] - public LichFormScroll( int amount ) : base( 106, 0x2266, amount ) - { - } + [Constructible] + public LichFormScroll(int amount) : base(106, 0x2266, amount) + { + } - public LichFormScroll( Serial serial ) : base( serial ) - { - } + public LichFormScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/MindRotScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/MindRotScroll.cs index 303304188..ecc6a6770 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/MindRotScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/MindRotScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MindRotScroll : SpellScroll - { - [Constructible] - public MindRotScroll() : this( 1 ) - { - } + public class MindRotScroll : SpellScroll + { + [Constructible] + public MindRotScroll() : this(1) + { + } - [Constructible] - public MindRotScroll( int amount ) : base( 107, 0x2267, amount ) - { - } + [Constructible] + public MindRotScroll(int amount) : base(107, 0x2267, amount) + { + } - public MindRotScroll( Serial serial ) : base( serial ) - { - } + public MindRotScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PainSpikeScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PainSpikeScroll.cs index 65244238d..c763d542d 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PainSpikeScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PainSpikeScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class PainSpikeScroll : SpellScroll - { - [Constructible] - public PainSpikeScroll() : this( 1 ) - { - } + public class PainSpikeScroll : SpellScroll + { + [Constructible] + public PainSpikeScroll() : this(1) + { + } - [Constructible] - public PainSpikeScroll( int amount ) : base( 108, 0x2268, amount ) - { - } + [Constructible] + public PainSpikeScroll(int amount) : base(108, 0x2268, amount) + { + } - public PainSpikeScroll( Serial serial ) : base( serial ) - { - } + public PainSpikeScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PoisonStrikeScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PoisonStrikeScroll.cs index dd26a07d1..c07da0cf3 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PoisonStrikeScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/PoisonStrikeScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class PoisonStrikeScroll : SpellScroll - { - [Constructible] - public PoisonStrikeScroll() : this( 1 ) - { - } + public class PoisonStrikeScroll : SpellScroll + { + [Constructible] + public PoisonStrikeScroll() : this(1) + { + } - [Constructible] - public PoisonStrikeScroll( int amount ) : base( 109, 0x2269, amount ) - { - } + [Constructible] + public PoisonStrikeScroll(int amount) : base(109, 0x2269, amount) + { + } - public PoisonStrikeScroll( Serial serial ) : base( serial ) - { - } + public PoisonStrikeScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/StrangleScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/StrangleScroll.cs index ad1c4ccbd..1ba75a170 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/StrangleScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/StrangleScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class StrangleScroll : SpellScroll - { - [Constructible] - public StrangleScroll() : this( 1 ) - { - } + public class StrangleScroll : SpellScroll + { + [Constructible] + public StrangleScroll() : this(1) + { + } - [Constructible] - public StrangleScroll( int amount ) : base( 110, 0x226A, amount ) - { - } + [Constructible] + public StrangleScroll(int amount) : base(110, 0x226A, amount) + { + } - public StrangleScroll( Serial serial ) : base( serial ) - { - } + public StrangleScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/SummonFamiliarScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/SummonFamiliarScroll.cs index 79048070e..8ffda47b2 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/SummonFamiliarScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/SummonFamiliarScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class SummonFamiliarScroll : SpellScroll - { - [Constructible] - public SummonFamiliarScroll() : this( 1 ) - { - } + public class SummonFamiliarScroll : SpellScroll + { + [Constructible] + public SummonFamiliarScroll() : this(1) + { + } - [Constructible] - public SummonFamiliarScroll( int amount ) : base( 111, 0x226B, amount ) - { - } + [Constructible] + public SummonFamiliarScroll(int amount) : base(111, 0x226B, amount) + { + } - public SummonFamiliarScroll( Serial serial ) : base( serial ) - { - } + public SummonFamiliarScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VampiricEmbraceScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VampiricEmbraceScroll.cs index 5a9eac956..f5e0cf657 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VampiricEmbraceScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VampiricEmbraceScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class VampiricEmbraceScroll : SpellScroll - { - [Constructible] - public VampiricEmbraceScroll() : this( 1 ) - { - } + public class VampiricEmbraceScroll : SpellScroll + { + [Constructible] + public VampiricEmbraceScroll() : this(1) + { + } - [Constructible] - public VampiricEmbraceScroll( int amount ) : base( 112, 0x226C, amount ) - { - } + [Constructible] + public VampiricEmbraceScroll(int amount) : base(112, 0x226C, amount) + { + } - public VampiricEmbraceScroll( Serial serial ) : base( serial ) - { - } + public VampiricEmbraceScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VengefulSpiritScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VengefulSpiritScroll.cs index eb35bdbac..c3c85c504 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VengefulSpiritScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/VengefulSpiritScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class VengefulSpiritScroll : SpellScroll - { - [Constructible] - public VengefulSpiritScroll() : this( 1 ) - { - } + public class VengefulSpiritScroll : SpellScroll + { + [Constructible] + public VengefulSpiritScroll() : this(1) + { + } - [Constructible] - public VengefulSpiritScroll( int amount ) : base( 113, 0x226D, amount ) - { - } + [Constructible] + public VengefulSpiritScroll(int amount) : base(113, 0x226D, amount) + { + } - public VengefulSpiritScroll( Serial serial ) : base( serial ) - { - } + public VengefulSpiritScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WitherScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WitherScroll.cs index 74bb5ef9f..22f44258f 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WitherScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WitherScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class WitherScroll : SpellScroll - { - [Constructible] - public WitherScroll() : this( 1 ) - { - } + public class WitherScroll : SpellScroll + { + [Constructible] + public WitherScroll() : this(1) + { + } - [Constructible] - public WitherScroll( int amount ) : base( 114, 0x226E, amount ) - { - } + [Constructible] + public WitherScroll(int amount) : base(114, 0x226E, amount) + { + } - public WitherScroll( Serial serial ) : base( serial ) - { - } + public WitherScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WraithFormScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WraithFormScroll.cs index 7949dc5f8..bac25f917 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WraithFormScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Necromancy/WraithFormScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class WraithFormScroll : SpellScroll - { - [Constructible] - public WraithFormScroll() : this( 1 ) - { - } + public class WraithFormScroll : SpellScroll + { + [Constructible] + public WraithFormScroll() : this(1) + { + } - [Constructible] - public WraithFormScroll( int amount ) : base( 115, 0x226F, amount ) - { - } + [Constructible] + public WraithFormScroll(int amount) : base(115, 0x226F, amount) + { + } - public WraithFormScroll( Serial serial ) : base( serial ) - { - } + public WraithFormScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/AgilityScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/AgilityScroll.cs index a9d3d00a9..b0c0a6f58 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/AgilityScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/AgilityScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class AgilityScroll : SpellScroll - { - [Constructible] - public AgilityScroll() : this( 1 ) - { - } + public class AgilityScroll : SpellScroll + { + [Constructible] + public AgilityScroll() : this(1) + { + } - [Constructible] - public AgilityScroll( int amount ) : base( 8, 0x1F35, amount ) - { - } + [Constructible] + public AgilityScroll(int amount) : base(8, 0x1F35, amount) + { + } - public AgilityScroll( Serial serial ) : base( serial ) - { - } + public AgilityScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CunningScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CunningScroll.cs index e1d80f76e..6ccda1a8d 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CunningScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CunningScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class CunningScroll : SpellScroll - { - [Constructible] - public CunningScroll() : this( 1 ) - { - } + public class CunningScroll : SpellScroll + { + [Constructible] + public CunningScroll() : this(1) + { + } - [Constructible] - public CunningScroll( int amount ) : base( 9, 0x1F36, amount ) - { - } + [Constructible] + public CunningScroll(int amount) : base(9, 0x1F36, amount) + { + } - public CunningScroll( Serial serial ) : base( serial ) - { - } + public CunningScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CureScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CureScroll.cs index e8107dc21..956344220 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CureScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/CureScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class CureScroll : SpellScroll - { - [Constructible] - public CureScroll() : this( 1 ) - { - } + public class CureScroll : SpellScroll + { + [Constructible] + public CureScroll() : this(1) + { + } - [Constructible] - public CureScroll( int amount ) : base( 10, 0x1F37, amount ) - { - } + [Constructible] + public CureScroll(int amount) : base(10, 0x1F37, amount) + { + } - public CureScroll( Serial serial ) : base( serial ) - { - } + public CureScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/HarmScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/HarmScroll.cs index 120db7dea..4d295fb72 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/HarmScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/HarmScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class HarmScroll : SpellScroll - { - [Constructible] - public HarmScroll() : this( 1 ) - { - } + public class HarmScroll : SpellScroll + { + [Constructible] + public HarmScroll() : this(1) + { + } - [Constructible] - public HarmScroll( int amount ) : base( 11, 0x1F38, amount ) - { - } + [Constructible] + public HarmScroll(int amount) : base(11, 0x1F38, amount) + { + } - public HarmScroll( Serial serial ) : base( serial ) - { - } + public HarmScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicTrapScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicTrapScroll.cs index c7918053b..3ab44a402 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicTrapScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicTrapScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MagicTrapScroll : SpellScroll - { - [Constructible] - public MagicTrapScroll() : this( 1 ) - { - } + public class MagicTrapScroll : SpellScroll + { + [Constructible] + public MagicTrapScroll() : this(1) + { + } - [Constructible] - public MagicTrapScroll( int amount ) : base( 12, 0x1F39, amount ) - { - } + [Constructible] + public MagicTrapScroll(int amount) : base(12, 0x1F39, amount) + { + } - public MagicTrapScroll( Serial serial ) : base( serial ) - { - } + public MagicTrapScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicUnTrapScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicUnTrapScroll.cs index 4ed73ddb9..165fd199f 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicUnTrapScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/MagicUnTrapScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MagicUnTrapScroll : SpellScroll - { - [Constructible] - public MagicUnTrapScroll() : this( 1 ) - { - } + public class MagicUnTrapScroll : SpellScroll + { + [Constructible] + public MagicUnTrapScroll() : this(1) + { + } - [Constructible] - public MagicUnTrapScroll( int amount ) : base( 13, 0x1F3A, amount ) - { - } + [Constructible] + public MagicUnTrapScroll(int amount) : base(13, 0x1F3A, amount) + { + } - public MagicUnTrapScroll( Serial serial ) : base( serial ) - { - } + public MagicUnTrapScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/ProtectionScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/ProtectionScroll.cs index f99667ff0..423909ad4 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/ProtectionScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/ProtectionScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ProtectionScroll : SpellScroll - { - [Constructible] - public ProtectionScroll() : this( 1 ) - { - } + public class ProtectionScroll : SpellScroll + { + [Constructible] + public ProtectionScroll() : this(1) + { + } - [Constructible] - public ProtectionScroll( int amount ) : base( 14, 0x1F3B, amount ) - { - } + [Constructible] + public ProtectionScroll(int amount) : base(14, 0x1F3B, amount) + { + } - public ProtectionScroll( Serial serial ) : base( serial ) - { - } + public ProtectionScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/StrengthScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/StrengthScroll.cs index c39bf061a..001a1576c 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/StrengthScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Second Circle/StrengthScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class StrengthScroll : SpellScroll - { - [Constructible] - public StrengthScroll() : this( 1 ) - { - } + public class StrengthScroll : SpellScroll + { + [Constructible] + public StrengthScroll() : this(1) + { + } - [Constructible] - public StrengthScroll( int amount ) : base( 15, 0x1F3C, amount ) - { - } + [Constructible] + public StrengthScroll(int amount) : base(15, 0x1F3C, amount) + { + } - public StrengthScroll( Serial serial ) : base( serial ) - { - } + public StrengthScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ChainLightningScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ChainLightningScroll.cs index 1a7ad34b8..e7fb19a33 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ChainLightningScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ChainLightningScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ChainLightningScroll : SpellScroll - { - [Constructible] - public ChainLightningScroll() : this( 1 ) - { - } + public class ChainLightningScroll : SpellScroll + { + [Constructible] + public ChainLightningScroll() : this(1) + { + } - [Constructible] - public ChainLightningScroll( int amount ) : base( 48, 0x1F5D, amount ) - { - } + [Constructible] + public ChainLightningScroll(int amount) : base(48, 0x1F5D, amount) + { + } - public ChainLightningScroll( Serial serial ) : base( serial ) - { - } + public ChainLightningScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/EnergyFieldScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/EnergyFieldScroll.cs index 1bfc6f1ff..3a8d5f8b0 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/EnergyFieldScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/EnergyFieldScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class EnergyFieldScroll : SpellScroll - { - [Constructible] - public EnergyFieldScroll() : this( 1 ) - { - } + public class EnergyFieldScroll : SpellScroll + { + [Constructible] + public EnergyFieldScroll() : this(1) + { + } - [Constructible] - public EnergyFieldScroll( int amount ) : base( 49, 0x1F5E, amount ) - { - } + [Constructible] + public EnergyFieldScroll(int amount) : base(49, 0x1F5E, amount) + { + } - public EnergyFieldScroll( Serial serial ) : base( serial ) - { - } + public EnergyFieldScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/FlamestrikeScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/FlamestrikeScroll.cs index c625d2ec3..96b6c1fe7 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/FlamestrikeScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/FlamestrikeScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class FlamestrikeScroll : SpellScroll - { - [Constructible] - public FlamestrikeScroll() : this( 1 ) - { - } + public class FlamestrikeScroll : SpellScroll + { + [Constructible] + public FlamestrikeScroll() : this(1) + { + } - [Constructible] - public FlamestrikeScroll( int amount ) : base( 50, 0x1F5F, amount ) - { - } + [Constructible] + public FlamestrikeScroll(int amount) : base(50, 0x1F5F, amount) + { + } - public FlamestrikeScroll( Serial serial ) : base( serial ) - { - } + public FlamestrikeScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/GateTravelScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/GateTravelScroll.cs index 6639a45ae..39ee11534 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/GateTravelScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/GateTravelScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class GateTravelScroll : SpellScroll - { - [Constructible] - public GateTravelScroll() : this( 1 ) - { - } + public class GateTravelScroll : SpellScroll + { + [Constructible] + public GateTravelScroll() : this(1) + { + } - [Constructible] - public GateTravelScroll( int amount ) : base( 51, 0x1F60, amount ) - { - } + [Constructible] + public GateTravelScroll(int amount) : base(51, 0x1F60, amount) + { + } - public GateTravelScroll( Serial serial ) : base( serial ) - { - } + public GateTravelScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ManaVampireScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ManaVampireScroll.cs index 73f8f474e..6fb6838ef 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ManaVampireScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/ManaVampireScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ManaVampireScroll : SpellScroll - { - [Constructible] - public ManaVampireScroll() : this( 1 ) - { - } + public class ManaVampireScroll : SpellScroll + { + [Constructible] + public ManaVampireScroll() : this(1) + { + } - [Constructible] - public ManaVampireScroll( int amount ) : base( 52, 0x1F61, amount ) - { - } + [Constructible] + public ManaVampireScroll(int amount) : base(52, 0x1F61, amount) + { + } - public ManaVampireScroll( Serial serial ) : base( serial ) - { - } + public ManaVampireScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MassDispelScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MassDispelScroll.cs index 40106b523..57c492764 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MassDispelScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MassDispelScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MassDispelScroll : SpellScroll - { - [Constructible] - public MassDispelScroll() : this( 1 ) - { - } + public class MassDispelScroll : SpellScroll + { + [Constructible] + public MassDispelScroll() : this(1) + { + } - [Constructible] - public MassDispelScroll( int amount ) : base( 53, 0x1F62, amount ) - { - } + [Constructible] + public MassDispelScroll(int amount) : base(53, 0x1F62, amount) + { + } - public MassDispelScroll( Serial serial ) : base( serial ) - { - } + public MassDispelScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MeteorStormScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MeteorStormScroll.cs index 83a398089..f4318728d 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MeteorStormScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/MeteorStormScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MeteorSwarmScroll : SpellScroll - { - [Constructible] - public MeteorSwarmScroll() : this( 1 ) - { - } + public class MeteorSwarmScroll : SpellScroll + { + [Constructible] + public MeteorSwarmScroll() : this(1) + { + } - [Constructible] - public MeteorSwarmScroll( int amount ) : base( 54, 0x1F63, amount ) - { - } + [Constructible] + public MeteorSwarmScroll(int amount) : base(54, 0x1F63, amount) + { + } - public MeteorSwarmScroll( Serial serial ) : base( serial ) - { - } + public MeteorSwarmScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/PolymorphScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/PolymorphScroll.cs index 0577a3819..9c268a57f 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/PolymorphScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Seventh Circle/PolymorphScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class PolymorphScroll : SpellScroll - { - [Constructible] - public PolymorphScroll() : this( 1 ) - { - } + public class PolymorphScroll : SpellScroll + { + [Constructible] + public PolymorphScroll() : this(1) + { + } - [Constructible] - public PolymorphScroll( int amount ) : base( 55, 0x1F64, amount ) - { - } + [Constructible] + public PolymorphScroll(int amount) : base(55, 0x1F64, amount) + { + } - public PolymorphScroll( Serial serial ) : base( serial ) - { - } + public PolymorphScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/DispelScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/DispelScroll.cs index d6f211303..78d98f302 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/DispelScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/DispelScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class DispelScroll : SpellScroll - { - [Constructible] - public DispelScroll() : this( 1 ) - { - } + public class DispelScroll : SpellScroll + { + [Constructible] + public DispelScroll() : this(1) + { + } - [Constructible] - public DispelScroll( int amount ) : base( 40, 0x1F55, amount ) - { - } + [Constructible] + public DispelScroll(int amount) : base(40, 0x1F55, amount) + { + } - public DispelScroll( Serial serial ) : base( serial ) - { - } + public DispelScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/EnergyBoltScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/EnergyBoltScroll.cs index 30e912c86..f3296f073 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/EnergyBoltScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/EnergyBoltScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class EnergyBoltScroll : SpellScroll - { - [Constructible] - public EnergyBoltScroll() : this( 1 ) - { - } + public class EnergyBoltScroll : SpellScroll + { + [Constructible] + public EnergyBoltScroll() : this(1) + { + } - [Constructible] - public EnergyBoltScroll( int amount ) : base( 41, 0x1F56, amount ) - { - } + [Constructible] + public EnergyBoltScroll(int amount) : base(41, 0x1F56, amount) + { + } - public EnergyBoltScroll( Serial serial ) : base( serial ) - { - } + public EnergyBoltScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ExplosionScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ExplosionScroll.cs index a1d2f45ec..cf380e190 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ExplosionScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ExplosionScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ExplosionScroll : SpellScroll - { - [Constructible] - public ExplosionScroll() : this( 1 ) - { - } + public class ExplosionScroll : SpellScroll + { + [Constructible] + public ExplosionScroll() : this(1) + { + } - [Constructible] - public ExplosionScroll( int amount ) : base( 42, 0x1F57, amount ) - { - } + [Constructible] + public ExplosionScroll(int amount) : base(42, 0x1F57, amount) + { + } - public ExplosionScroll( Serial serial ) : base( serial ) - { - } + public ExplosionScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/InvisibilityScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/InvisibilityScroll.cs index e4002d385..5edf03b1c 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/InvisibilityScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/InvisibilityScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class InvisibilityScroll : SpellScroll - { - [Constructible] - public InvisibilityScroll() : this( 1 ) - { - } + public class InvisibilityScroll : SpellScroll + { + [Constructible] + public InvisibilityScroll() : this(1) + { + } - [Constructible] - public InvisibilityScroll( int amount ) : base( 43, 0x1F58, amount ) - { - } + [Constructible] + public InvisibilityScroll(int amount) : base(43, 0x1F58, amount) + { + } - public InvisibilityScroll( Serial serial ) : base( serial ) - { - } + public InvisibilityScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MarkScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MarkScroll.cs index ff84244f9..38e97dbae 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MarkScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MarkScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MarkScroll : SpellScroll - { - [Constructible] - public MarkScroll() : this( 1 ) - { - } + public class MarkScroll : SpellScroll + { + [Constructible] + public MarkScroll() : this(1) + { + } - [Constructible] - public MarkScroll( int amount ) : base( 44, 0x1F59, amount ) - { - } + [Constructible] + public MarkScroll(int amount) : base(44, 0x1F59, amount) + { + } - public MarkScroll( Serial serial ) : base( serial ) - { - } + public MarkScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MassCurseScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MassCurseScroll.cs index 529ef8bd7..46a3a7d47 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MassCurseScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/MassCurseScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MassCurseScroll : SpellScroll - { - [Constructible] - public MassCurseScroll() : this( 1 ) - { - } + public class MassCurseScroll : SpellScroll + { + [Constructible] + public MassCurseScroll() : this(1) + { + } - [Constructible] - public MassCurseScroll( int amount ) : base( 45, 0x1F5A, amount ) - { - } + [Constructible] + public MassCurseScroll(int amount) : base(45, 0x1F5A, amount) + { + } - public MassCurseScroll( Serial serial ) : base( serial ) - { - } + public MassCurseScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ParalyzeFieldSpell.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ParalyzeFieldSpell.cs index a798fe867..009af8e9b 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ParalyzeFieldSpell.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/ParalyzeFieldSpell.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class ParalyzeFieldScroll : SpellScroll - { - [Constructible] - public ParalyzeFieldScroll() : this( 1 ) - { - } + public class ParalyzeFieldScroll : SpellScroll + { + [Constructible] + public ParalyzeFieldScroll() : this(1) + { + } - [Constructible] - public ParalyzeFieldScroll( int amount ) : base( 46, 0x1F5B, amount ) - { - } + [Constructible] + public ParalyzeFieldScroll(int amount) : base(46, 0x1F5B, amount) + { + } - public ParalyzeFieldScroll( Serial serial ) : base( serial ) - { - } + public ParalyzeFieldScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/RevealScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/RevealScroll.cs index 85371707f..9b65b0a1c 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/RevealScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Sixth Circle/RevealScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class RevealScroll : SpellScroll - { - [Constructible] - public RevealScroll() : this( 1 ) - { - } + public class RevealScroll : SpellScroll + { + [Constructible] + public RevealScroll() : this(1) + { + } - [Constructible] - public RevealScroll( int amount ) : base( 47, 0x1F5C, amount ) - { - } + [Constructible] + public RevealScroll(int amount) : base(47, 0x1F5C, amount) + { + } - public RevealScroll( Serial serial ) : base( serial ) - { - } + public RevealScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/SpellScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/SpellScroll.cs index 32d300ae0..8ffb6c2b6 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/SpellScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/SpellScroll.cs @@ -1,86 +1,87 @@ using System.Collections.Generic; -using Server.Spells; using Server.ContextMenus; +using Server.Multis; +using Server.Spells; namespace Server.Items { - public class SpellScroll : Item, ICommodity - { - public int SpellID { get; private set; } + public class SpellScroll : Item, ICommodity + { + public SpellScroll(Serial serial) : base(serial) + { + } - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => (Core.ML); + [Constructible] + public SpellScroll(int spellID, int itemID) : this(spellID, itemID, 1) + { + } - public SpellScroll( Serial serial ) : base( serial ) - { - } + [Constructible] + public SpellScroll(int spellID, int itemID, int amount) : base(itemID) + { + Stackable = true; + Weight = 1.0; + Amount = amount; - [Constructible] - public SpellScroll( int spellID, int itemID ) : this( spellID, itemID, 1 ) - { - } + SpellID = spellID; + } - [Constructible] - public SpellScroll( int spellID, int itemID, int amount ) : base( itemID ) - { - Stackable = true; - Weight = 1.0; - Amount = amount; + public int SpellID{ get; private set; } - SpellID = spellID; - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => Core.ML; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) SpellID ); - } + writer.Write(SpellID); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - SpellID = reader.ReadInt(); + switch (version) + { + case 0: + { + SpellID = reader.ReadInt(); - break; - } - } - } + break; + } + } + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( from.Alive && Movable ) - list.Add( new AddToSpellbookEntry() ); - } + if (from.Alive && Movable) + list.Add(new AddToSpellbookEntry()); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !Multis.DesignContext.Check( from ) ) - return; // They are customizing + public override void OnDoubleClick(Mobile from) + { + if (!DesignContext.Check(from)) + return; // They are customizing - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - return; - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return; + } - Spell spell = SpellRegistry.NewSpell( SpellID, from, this ); + Spell spell = SpellRegistry.NewSpell(SpellID, from, this); - if ( spell != null ) - spell.Cast(); - else - from.SendLocalizedMessage( 502345 ); // This spell has been temporarily disabled. - } - } + if (spell != null) + spell.Cast(); + else + from.SendLocalizedMessage(502345); // This spell has been temporarily disabled. + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/SpellweavingScrolls.cs b/Scripts/Items/Skill Items/Magical/Scrolls/SpellweavingScrolls.cs index 625b54a08..921180059 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/SpellweavingScrolls.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/SpellweavingScrolls.cs @@ -1,562 +1,562 @@ namespace Server.Items { - public class ArcaneCircleScroll : SpellScroll - { - [Constructible] - public ArcaneCircleScroll() - : this( 1 ) - { - } - - [Constructible] - public ArcaneCircleScroll( int amount ) - : base( 600, 0x2D51, amount ) - { - Hue = 0x8FD; - } - - public ArcaneCircleScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GiftOfRenewalScroll : SpellScroll - { - [Constructible] - public GiftOfRenewalScroll() - : this( 1 ) - { - } - - [Constructible] - public GiftOfRenewalScroll( int amount ) - : base( 601, 0x2D52, amount ) - { - Hue = 0x8FD; - } - - public GiftOfRenewalScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ImmolatingWeaponScroll : SpellScroll - { - [Constructible] - public ImmolatingWeaponScroll() - : this( 1 ) - { - } - - [Constructible] - public ImmolatingWeaponScroll( int amount ) - : base( 602, 0x2D53, amount ) - { - Hue = 0x8FD; - } - - public ImmolatingWeaponScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class AttuneWeaponScroll : SpellScroll - { - [Constructible] - public AttuneWeaponScroll() - : this( 1 ) - { - } - - [Constructible] - public AttuneWeaponScroll( int amount ) - : base( 603, 0x2D54, amount ) - { - Hue = 0x8FD; - } - - public AttuneWeaponScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ThunderstormScroll : SpellScroll - { - [Constructible] - public ThunderstormScroll() - : this( 1 ) - { - } - - [Constructible] - public ThunderstormScroll( int amount ) - : base( 604, 0x2D55, amount ) - { - Hue = 0x8FD; - } - - public ThunderstormScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class NatureFuryScroll : SpellScroll - { - [Constructible] - public NatureFuryScroll() - : this( 1 ) - { - } - - [Constructible] - public NatureFuryScroll( int amount ) - : base( 605, 0x2D56, amount ) - { - Hue = 0x8FD; - } - - public NatureFuryScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SummonFeyScroll : SpellScroll - { - [Constructible] - public SummonFeyScroll() - : this( 1 ) - { - } - - [Constructible] - public SummonFeyScroll( int amount ) - : base( 606, 0x2D57, amount ) - { - Hue = 0x8FD; - } - - public SummonFeyScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SummonFiendScroll : SpellScroll - { - [Constructible] - public SummonFiendScroll() - : this( 1 ) - { - } - - [Constructible] - public SummonFiendScroll( int amount ) - : base( 607, 0x2D58, amount ) - { - Hue = 0x8FD; - } - - public SummonFiendScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ReaperFormScroll : SpellScroll - { - [Constructible] - public ReaperFormScroll() - : this( 1 ) - { - } - - [Constructible] - public ReaperFormScroll( int amount ) - : base( 608, 0x2D59, amount ) - { - Hue = 0x8FD; - } - - public ReaperFormScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WildfireScroll : SpellScroll - { - [Constructible] - public WildfireScroll() - : this( 1 ) - { - } - - [Constructible] - public WildfireScroll( int amount ) - : base( 609, 0x2D5A, amount ) - { - Hue = 0x8FD; - } - - public WildfireScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EssenceOfWindScroll : SpellScroll - { - [Constructible] - public EssenceOfWindScroll() - : this( 1 ) - { - } - - [Constructible] - public EssenceOfWindScroll( int amount ) - : base( 610, 0x2D5B, amount ) - { - Hue = 0x8FD; - } - - public EssenceOfWindScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DryadAllureScroll : SpellScroll - { - [Constructible] - public DryadAllureScroll() - : this( 1 ) - { - } - - [Constructible] - public DryadAllureScroll( int amount ) - : base( 611, 0x2D5C, amount ) - { - Hue = 0x8FD; - } - - public DryadAllureScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class EtherealVoyageScroll : SpellScroll - { - [Constructible] - public EtherealVoyageScroll() - : this( 1 ) - { - } - - [Constructible] - public EtherealVoyageScroll( int amount ) - : base( 612, 0x2D5D, amount ) - { - Hue = 0x8FD; - } - - public EtherealVoyageScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WordOfDeathScroll : SpellScroll - { - [Constructible] - public WordOfDeathScroll() - : this( 1 ) - { - } - - [Constructible] - public WordOfDeathScroll( int amount ) - : base( 613, 0x2D5E, amount ) - { - Hue = 0x8FD; - } - - public WordOfDeathScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class GiftOfLifeScroll : SpellScroll - { - [Constructible] - public GiftOfLifeScroll() - : this( 1 ) - { - } - - [Constructible] - public GiftOfLifeScroll( int amount ) - : base( 614, 0x2D5F, amount ) - { - Hue = 0x8FD; - } - - public GiftOfLifeScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ArcaneEmpowermentScroll : SpellScroll - { - [Constructible] - public ArcaneEmpowermentScroll() - : this( 1 ) - { - } - - [Constructible] - public ArcaneEmpowermentScroll( int amount ) - : base( 615, 0x2D60, amount ) - { - Hue = 0x8FD; - } - - public ArcaneEmpowermentScroll( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + public class ArcaneCircleScroll : SpellScroll + { + [Constructible] + public ArcaneCircleScroll() + : this(1) + { + } + + [Constructible] + public ArcaneCircleScroll(int amount) + : base(600, 0x2D51, amount) + { + Hue = 0x8FD; + } + + public ArcaneCircleScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GiftOfRenewalScroll : SpellScroll + { + [Constructible] + public GiftOfRenewalScroll() + : this(1) + { + } + + [Constructible] + public GiftOfRenewalScroll(int amount) + : base(601, 0x2D52, amount) + { + Hue = 0x8FD; + } + + public GiftOfRenewalScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ImmolatingWeaponScroll : SpellScroll + { + [Constructible] + public ImmolatingWeaponScroll() + : this(1) + { + } + + [Constructible] + public ImmolatingWeaponScroll(int amount) + : base(602, 0x2D53, amount) + { + Hue = 0x8FD; + } + + public ImmolatingWeaponScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class AttuneWeaponScroll : SpellScroll + { + [Constructible] + public AttuneWeaponScroll() + : this(1) + { + } + + [Constructible] + public AttuneWeaponScroll(int amount) + : base(603, 0x2D54, amount) + { + Hue = 0x8FD; + } + + public AttuneWeaponScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ThunderstormScroll : SpellScroll + { + [Constructible] + public ThunderstormScroll() + : this(1) + { + } + + [Constructible] + public ThunderstormScroll(int amount) + : base(604, 0x2D55, amount) + { + Hue = 0x8FD; + } + + public ThunderstormScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class NatureFuryScroll : SpellScroll + { + [Constructible] + public NatureFuryScroll() + : this(1) + { + } + + [Constructible] + public NatureFuryScroll(int amount) + : base(605, 0x2D56, amount) + { + Hue = 0x8FD; + } + + public NatureFuryScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SummonFeyScroll : SpellScroll + { + [Constructible] + public SummonFeyScroll() + : this(1) + { + } + + [Constructible] + public SummonFeyScroll(int amount) + : base(606, 0x2D57, amount) + { + Hue = 0x8FD; + } + + public SummonFeyScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SummonFiendScroll : SpellScroll + { + [Constructible] + public SummonFiendScroll() + : this(1) + { + } + + [Constructible] + public SummonFiendScroll(int amount) + : base(607, 0x2D58, amount) + { + Hue = 0x8FD; + } + + public SummonFiendScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ReaperFormScroll : SpellScroll + { + [Constructible] + public ReaperFormScroll() + : this(1) + { + } + + [Constructible] + public ReaperFormScroll(int amount) + : base(608, 0x2D59, amount) + { + Hue = 0x8FD; + } + + public ReaperFormScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WildfireScroll : SpellScroll + { + [Constructible] + public WildfireScroll() + : this(1) + { + } + + [Constructible] + public WildfireScroll(int amount) + : base(609, 0x2D5A, amount) + { + Hue = 0x8FD; + } + + public WildfireScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EssenceOfWindScroll : SpellScroll + { + [Constructible] + public EssenceOfWindScroll() + : this(1) + { + } + + [Constructible] + public EssenceOfWindScroll(int amount) + : base(610, 0x2D5B, amount) + { + Hue = 0x8FD; + } + + public EssenceOfWindScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DryadAllureScroll : SpellScroll + { + [Constructible] + public DryadAllureScroll() + : this(1) + { + } + + [Constructible] + public DryadAllureScroll(int amount) + : base(611, 0x2D5C, amount) + { + Hue = 0x8FD; + } + + public DryadAllureScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class EtherealVoyageScroll : SpellScroll + { + [Constructible] + public EtherealVoyageScroll() + : this(1) + { + } + + [Constructible] + public EtherealVoyageScroll(int amount) + : base(612, 0x2D5D, amount) + { + Hue = 0x8FD; + } + + public EtherealVoyageScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WordOfDeathScroll : SpellScroll + { + [Constructible] + public WordOfDeathScroll() + : this(1) + { + } + + [Constructible] + public WordOfDeathScroll(int amount) + : base(613, 0x2D5E, amount) + { + Hue = 0x8FD; + } + + public WordOfDeathScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class GiftOfLifeScroll : SpellScroll + { + [Constructible] + public GiftOfLifeScroll() + : this(1) + { + } + + [Constructible] + public GiftOfLifeScroll(int amount) + : base(614, 0x2D5F, amount) + { + Hue = 0x8FD; + } + + public GiftOfLifeScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ArcaneEmpowermentScroll : SpellScroll + { + [Constructible] + public ArcaneEmpowermentScroll() + : this(1) + { + } + + [Constructible] + public ArcaneEmpowermentScroll(int amount) + : base(615, 0x2D60, amount) + { + Hue = 0x8FD; + } + + public ArcaneEmpowermentScroll(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/BlessScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/BlessScroll.cs index 767ffa7a4..d465bb2d1 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/BlessScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/BlessScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class BlessScroll : SpellScroll - { - [Constructible] - public BlessScroll() : this( 1 ) - { - } + public class BlessScroll : SpellScroll + { + [Constructible] + public BlessScroll() : this(1) + { + } - [Constructible] - public BlessScroll( int amount ) : base( 16, 0x1F3D, amount ) - { - } + [Constructible] + public BlessScroll(int amount) : base(16, 0x1F3D, amount) + { + } - public BlessScroll( Serial serial ) : base( serial ) - { - } + public BlessScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/FireballScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/FireballScroll.cs index c75d3a94c..cc405f4e7 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/FireballScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/FireballScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class FireballScroll : SpellScroll - { - [Constructible] - public FireballScroll() : this( 1 ) - { - } + public class FireballScroll : SpellScroll + { + [Constructible] + public FireballScroll() : this(1) + { + } - [Constructible] - public FireballScroll( int amount ) : base( 17, 0x1F3E, amount ) - { - } + [Constructible] + public FireballScroll(int amount) : base(17, 0x1F3E, amount) + { + } - public FireballScroll( Serial serial ) : base( serial ) - { - } + public FireballScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/MagicLockScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/MagicLockScroll.cs index c5147259c..eba14df08 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/MagicLockScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/MagicLockScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class MagicLockScroll : SpellScroll - { - [Constructible] - public MagicLockScroll() : this( 1 ) - { - } + public class MagicLockScroll : SpellScroll + { + [Constructible] + public MagicLockScroll() : this(1) + { + } - [Constructible] - public MagicLockScroll( int amount ) : base( 18, 0x1F3F, amount ) - { - } + [Constructible] + public MagicLockScroll(int amount) : base(18, 0x1F3F, amount) + { + } - public MagicLockScroll( Serial serial ) : base( serial ) - { - } + public MagicLockScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/PoisonScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/PoisonScroll.cs index e841c8c8e..9c57aeb6d 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/PoisonScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/PoisonScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class PoisonScroll : SpellScroll - { - [Constructible] - public PoisonScroll() : this( 1 ) - { - } + public class PoisonScroll : SpellScroll + { + [Constructible] + public PoisonScroll() : this(1) + { + } - [Constructible] - public PoisonScroll( int amount ) : base( 19, 0x1F40, amount ) - { - } + [Constructible] + public PoisonScroll(int amount) : base(19, 0x1F40, amount) + { + } - public PoisonScroll( Serial serial ) : base( serial ) - { - } + public PoisonScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TelekinisisScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TelekinisisScroll.cs index dac637736..9a872fa1f 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TelekinisisScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TelekinisisScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class TelekinisisScroll : SpellScroll - { - [Constructible] - public TelekinisisScroll() : this( 1 ) - { - } + public class TelekinisisScroll : SpellScroll + { + [Constructible] + public TelekinisisScroll() : this(1) + { + } - [Constructible] - public TelekinisisScroll( int amount ) : base( 20, 0x1F41, amount ) - { - } + [Constructible] + public TelekinisisScroll(int amount) : base(20, 0x1F41, amount) + { + } - public TelekinisisScroll( Serial serial ) : base( serial ) - { - } + public TelekinisisScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TeleportScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TeleportScroll.cs index 1105738a5..e99460c98 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TeleportScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/TeleportScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class TeleportScroll : SpellScroll - { - [Constructible] - public TeleportScroll() : this( 1 ) - { - } + public class TeleportScroll : SpellScroll + { + [Constructible] + public TeleportScroll() : this(1) + { + } - [Constructible] - public TeleportScroll( int amount ) : base( 21, 0x1F42, amount ) - { - } + [Constructible] + public TeleportScroll(int amount) : base(21, 0x1F42, amount) + { + } - public TeleportScroll( Serial serial ) : base( serial ) - { - } + public TeleportScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/UnlockScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/UnlockScroll.cs index 7522983f4..0e7de86b0 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/UnlockScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/UnlockScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class UnlockScroll : SpellScroll - { - [Constructible] - public UnlockScroll() : this( 1 ) - { - } + public class UnlockScroll : SpellScroll + { + [Constructible] + public UnlockScroll() : this(1) + { + } - [Constructible] - public UnlockScroll( int amount ) : base( 22, 0x1F43, amount ) - { - } + [Constructible] + public UnlockScroll(int amount) : base(22, 0x1F43, amount) + { + } - public UnlockScroll( Serial serial ) : base( serial ) - { - } + public UnlockScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/WallOfStoneScroll.cs b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/WallOfStoneScroll.cs index 190a256a1..d2ae27fd4 100644 --- a/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/WallOfStoneScroll.cs +++ b/Scripts/Items/Skill Items/Magical/Scrolls/Third Circle/WallOfStoneScroll.cs @@ -1,35 +1,33 @@ namespace Server.Items { - public class WallOfStoneScroll : SpellScroll - { - [Constructible] - public WallOfStoneScroll() : this( 1 ) - { - } + public class WallOfStoneScroll : SpellScroll + { + [Constructible] + public WallOfStoneScroll() : this(1) + { + } - [Constructible] - public WallOfStoneScroll( int amount ) : base( 23, 0x1F44, amount ) - { - } + [Constructible] + public WallOfStoneScroll(int amount) : base(23, 0x1F44, amount) + { + } - public WallOfStoneScroll( Serial serial ) : base( serial ) - { - } + public WallOfStoneScroll(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - - - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/Spellbook.cs b/Scripts/Items/Skill Items/Magical/Spellbook.cs index 757ed5f2c..16da7bab9 100644 --- a/Scripts/Items/Skill Items/Magical/Spellbook.cs +++ b/Scripts/Items/Skill Items/Magical/Spellbook.cs @@ -2,886 +2,924 @@ using System; using System.Collections.Generic; using Server.Commands; using Server.Engines.Craft; +using Server.Ethics; +using Server.Multis; using Server.Network; using Server.Spells; using Server.Targeting; namespace Server.Items { - public enum SpellbookType - { - Invalid = -1, - Regular, - Necromancer, - Paladin, - Ninja, - Samurai, - Arcanist, - Mystic - } - - public enum BookQuality - { - Regular, - Exceptional, - } - - public class Spellbook : Item, ICraftable, ISlayer - { - private string m_EngravedText; - private BookQuality m_Quality; - - [CommandProperty( AccessLevel.GameMaster )] - public string EngravedText - { - get => m_EngravedText; - set{ m_EngravedText = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public BookQuality Quality - { - get => m_Quality; - set{ m_Quality = value; InvalidateProperties(); } - } - - public static void Initialize() - { - EventSink.OpenSpellbookRequest += EventSink_OpenSpellbookRequest; - EventSink.CastSpellRequest += EventSink_CastSpellRequest; - - CommandSystem.Register( "AllSpells", AccessLevel.GameMaster, AllSpells_OnCommand ); - } - - [Usage( "AllSpells" )] - [Description( "Completely fills a targeted spellbook with scrolls." )] - private static void AllSpells_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, AllSpells_OnTarget ); - e.Mobile.SendMessage( "Target the spellbook to fill." ); - } - - private static void AllSpells_OnTarget( Mobile from, object obj ) - { - if ( obj is Spellbook book ) - { - if ( book.BookCount == 64 ) - book.Content = ulong.MaxValue; - else - book.Content = (1ul << book.BookCount) - 1; - - from.SendMessage( "The spellbook has been filled." ); - - CommandLogging.WriteLine( from, "{0} {1} filling spellbook {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( book ) ); - } - else - { - from.BeginTarget( -1, false, TargetFlags.None, AllSpells_OnTarget ); - from.SendMessage( "That is not a spellbook. Try again." ); - } - } - - private static void EventSink_OpenSpellbookRequest( OpenSpellbookRequestEventArgs e ) - { - Mobile from = e.Mobile; - - if ( !Multis.DesignContext.Check( from ) ) - return; // They are customizing - - SpellbookType type; - - switch ( e.Type ) - { - default: - case 1: type = SpellbookType.Regular; break; - case 2: type = SpellbookType.Necromancer; break; - case 3: type = SpellbookType.Paladin; break; - case 4: type = SpellbookType.Ninja; break; - case 5: type = SpellbookType.Samurai; break; - case 6: type = SpellbookType.Arcanist; break; - case 7: type = SpellbookType.Mystic; break; - } - - Spellbook book = Find( from, -1, type ); - - book?.DisplayTo( from ); - } - - private static void EventSink_CastSpellRequest( CastSpellRequestEventArgs e ) - { - Mobile from = e.Mobile; - - if ( !Multis.DesignContext.Check( from ) ) - return; // They are customizing - - Spellbook book = e.Spellbook as Spellbook; - int spellID = e.SpellID; - - if ( book == null || !book.HasSpell( spellID ) ) - book = Find( from, spellID ); - - if ( book != null && book.HasSpell( spellID ) ) - { - SpecialMove move = SpellRegistry.GetSpecialMove( spellID ); - - if ( move != null ) - { - SpecialMove.SetCurrentMove( from, move ); - } - else - { - Spell spell = SpellRegistry.NewSpell( spellID, from, null ); - - if ( spell != null ) - spell.Cast(); - else - from.SendLocalizedMessage( 502345 ); // This spell has been temporarily disabled. - } - } - else - { - from.SendLocalizedMessage( 500015 ); // You do not have that spell! - } - } - - private static Dictionary> m_Table = new Dictionary>(); - - public static SpellbookType GetTypeForSpell( int spellID ) - { - if ( spellID >= 0 && spellID < 64 ) - return SpellbookType.Regular; - if ( spellID >= 100 && spellID < 117 ) - return SpellbookType.Necromancer; - if ( spellID >= 200 && spellID < 210 ) - return SpellbookType.Paladin; - if ( spellID >= 400 && spellID < 406 ) - return SpellbookType.Samurai; - if ( spellID >= 500 && spellID < 508 ) - return SpellbookType.Ninja; - if ( spellID >= 600 && spellID < 617 ) - return SpellbookType.Arcanist; - if ( spellID >= 677 && spellID < 693 ) - return SpellbookType.Mystic; - - return SpellbookType.Invalid; - } - - public static Spellbook FindRegular( Mobile from ) - { - return Find( from, -1, SpellbookType.Regular ); - } - - public static Spellbook FindNecromancer( Mobile from ) - { - return Find( from, -1, SpellbookType.Necromancer ); - } - - public static Spellbook FindPaladin( Mobile from ) - { - return Find( from, -1, SpellbookType.Paladin ); - } - - public static Spellbook FindSamurai( Mobile from ) - { - return Find( from, -1, SpellbookType.Samurai ); - } - - public static Spellbook FindNinja( Mobile from ) - { - return Find( from, -1, SpellbookType.Ninja ); - } - - public static Spellbook FindArcanist( Mobile from ) - { - return Find( from, -1, SpellbookType.Arcanist ); - } - - public static Spellbook FindMystic( Mobile from ) - { - return Find( from, -1, SpellbookType.Mystic ); - } - - public static Spellbook Find( Mobile from, int spellID ) - { - return Find( from, spellID, GetTypeForSpell( spellID ) ); - } - - public static Spellbook Find( Mobile from, int spellID, SpellbookType type ) - { - if ( from == null ) - return null; - - if ( from.Deleted ) - { - m_Table.Remove( from ); - return null; - } - - m_Table.TryGetValue( from, out List list ); - - bool searchAgain = false; - - if ( list == null ) - m_Table[from] = list = FindAllSpellbooks( from ); - else - searchAgain = true; - - Spellbook book = FindSpellbookInList( list, from, spellID, type ); - - if ( book == null && searchAgain ) - { - m_Table[from] = list = FindAllSpellbooks( from ); - - book = FindSpellbookInList( list, from, spellID, type ); - } - - return book; - } - - public static Spellbook FindSpellbookInList( List list, Mobile from, int spellID, SpellbookType type ) - { - Container pack = from.Backpack; - - for ( int i = list.Count - 1; i >= 0; --i ) - { - if ( i >= list.Count ) - continue; - - Spellbook book = list[i]; - - if ( !book.Deleted && (book.Parent == from || (pack != null && book.Parent == pack)) && ValidateSpellbook( book, spellID, type ) ) - return book; - - list.RemoveAt( i ); - } - - return null; - } - - public static List FindAllSpellbooks( Mobile from ) - { - List list = new List(); - - Item item = from.FindItemOnLayer( Layer.OneHanded ); - - if ( item is Spellbook spellbook ) - list.Add( spellbook ); - - Container pack = from.Backpack; - - if ( pack == null ) - return list; + public enum SpellbookType + { + Invalid = -1, + Regular, + Necromancer, + Paladin, + Ninja, + Samurai, + Arcanist, + Mystic + } + + public enum BookQuality + { + Regular, + Exceptional + } + + public class Spellbook : Item, ICraftable, ISlayer + { + private static Dictionary> m_Table = new Dictionary>(); + + private static int[] m_LegendPropertyCounts = + { + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0 properties : 21/52 : 40% + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 1 property : 15/52 : 29% + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 2 properties : 10/52 : 19% + 3, 3, 3, 3, 3, 3 // 3 properties : 6/52 : 12% + }; + + private static int[] m_ElderPropertyCounts = + { + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0 properties : 15/34 : 44% + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 1 property : 10/34 : 29% + 2, 2, 2, 2, 2, 2, // 2 properties : 6/34 : 18% + 3, 3, 3 // 3 properties : 3/34 : 9% + }; + + private static int[] m_GrandPropertyCounts = + { + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0 properties : 10/20 : 50% + 1, 1, 1, 1, 1, 1, // 1 property : 6/20 : 30% + 2, 2, 2, // 2 properties : 3/20 : 15% + 3 // 3 properties : 1/20 : 5% + }; + + private static int[] m_MasterPropertyCounts = + { + 0, 0, 0, 0, 0, 0, // 0 properties : 6/10 : 60% + 1, 1, 1, // 1 property : 3/10 : 30% + 2 // 2 properties : 1/10 : 10% + }; + + private static int[] m_AdeptPropertyCounts = + { + 0, 0, 0, // 0 properties : 3/4 : 75% + 1 // 1 property : 1/4 : 25% + }; + + private AosAttributes m_AosAttributes; + private AosSkillBonuses m_AosSkillBonuses; + + private ulong m_Content; + + private Mobile m_Crafter; + private string m_EngravedText; + private BookQuality m_Quality; + + + private SlayerName m_Slayer; + private SlayerName m_Slayer2; + + [Constructible] + public Spellbook() : this((ulong)0) + { + } + + [Constructible] + public Spellbook(ulong content) : this(content, 0xEFA) + { + } + + public Spellbook(ulong content, int itemID) : base(itemID) + { + m_AosAttributes = new AosAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + + Weight = 3.0; + Layer = Layer.OneHanded; + LootType = LootType.Blessed; + + Content = content; + } + + public Spellbook(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string EngravedText + { + get => m_EngravedText; + set + { + m_EngravedText = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public BookQuality Quality + { + get => m_Quality; + set + { + m_Quality = value; + InvalidateProperties(); + } + } + + public override bool DisplayWeight => false; + + [CommandProperty(AccessLevel.GameMaster)] + public AosAttributes Attributes + { + get => m_AosAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosSkillBonuses SkillBonuses + { + get => m_AosSkillBonuses; + set { } + } + + public virtual SpellbookType SpellbookType => SpellbookType.Regular; + public virtual int BookOffset => 0; + public virtual int BookCount => 64; + + [CommandProperty(AccessLevel.GameMaster)] + public ulong Content + { + get => m_Content; + set + { + if (m_Content != value) + { + m_Content = value; + + SpellCount = 0; + + while (value > 0) + { + SpellCount += (int)(value & 0x1); + value >>= 1; + } + + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SpellCount{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + public override bool DisplayLootType => Core.AOS; + + public virtual int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, + BaseTool tool, CraftItem craftItem, int resHue) + { + int magery = from.Skills.Magery.BaseFixedPoint; + + if (magery >= 800) + { + int[] propertyCounts; + int minIntensity; + int maxIntensity; + + if (magery >= 1000) + { + if (magery >= 1200) + propertyCounts = m_LegendPropertyCounts; + else if (magery >= 1100) + propertyCounts = m_ElderPropertyCounts; + else + propertyCounts = m_GrandPropertyCounts; + + minIntensity = 55; + maxIntensity = 75; + } + else if (magery >= 900) + { + propertyCounts = m_MasterPropertyCounts; + minIntensity = 25; + maxIntensity = 45; + } + else + { + propertyCounts = m_AdeptPropertyCounts; + minIntensity = 0; + maxIntensity = 15; + } + + int propertyCount = propertyCounts[Utility.Random(propertyCounts.Length)]; + + BaseRunicTool.ApplyAttributesTo(this, true, 0, propertyCount, minIntensity, maxIntensity); + } + + if (makersMark) + Crafter = from; + + m_Quality = (BookQuality)(quality - 1); + + return quality; + } + //Currently though there are no dual slayer spellbooks, OSI has a habit of putting dual slayer stuff in later + + [CommandProperty(AccessLevel.GameMaster)] + public SlayerName Slayer + { + get => m_Slayer; + set + { + m_Slayer = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public SlayerName Slayer2 + { + get => m_Slayer2; + set + { + m_Slayer2 = value; + InvalidateProperties(); + } + } + + public static void Initialize() + { + EventSink.OpenSpellbookRequest += EventSink_OpenSpellbookRequest; + EventSink.CastSpellRequest += EventSink_CastSpellRequest; + + CommandSystem.Register("AllSpells", AccessLevel.GameMaster, AllSpells_OnCommand); + } + + [Usage("AllSpells")] + [Description("Completely fills a targeted spellbook with scrolls.")] + private static void AllSpells_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, AllSpells_OnTarget); + e.Mobile.SendMessage("Target the spellbook to fill."); + } + + private static void AllSpells_OnTarget(Mobile from, object obj) + { + if (obj is Spellbook book) + { + if (book.BookCount == 64) + book.Content = ulong.MaxValue; + else + book.Content = (1ul << book.BookCount) - 1; + + from.SendMessage("The spellbook has been filled."); + + CommandLogging.WriteLine(from, "{0} {1} filling spellbook {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(book)); + } + else + { + from.BeginTarget(-1, false, TargetFlags.None, AllSpells_OnTarget); + from.SendMessage("That is not a spellbook. Try again."); + } + } + + private static void EventSink_OpenSpellbookRequest(OpenSpellbookRequestEventArgs e) + { + Mobile from = e.Mobile; + + if (!DesignContext.Check(from)) + return; // They are customizing + + SpellbookType type; + + switch (e.Type) + { + default: + case 1: + type = SpellbookType.Regular; + break; + case 2: + type = SpellbookType.Necromancer; + break; + case 3: + type = SpellbookType.Paladin; + break; + case 4: + type = SpellbookType.Ninja; + break; + case 5: + type = SpellbookType.Samurai; + break; + case 6: + type = SpellbookType.Arcanist; + break; + case 7: + type = SpellbookType.Mystic; + break; + } + + Spellbook book = Find(from, -1, type); + + book?.DisplayTo(from); + } + + private static void EventSink_CastSpellRequest(CastSpellRequestEventArgs e) + { + Mobile from = e.Mobile; + + if (!DesignContext.Check(from)) + return; // They are customizing + + Spellbook book = e.Spellbook as Spellbook; + int spellID = e.SpellID; + + if (book == null || !book.HasSpell(spellID)) + book = Find(from, spellID); + + if (book != null && book.HasSpell(spellID)) + { + SpecialMove move = SpellRegistry.GetSpecialMove(spellID); + + if (move != null) + { + SpecialMove.SetCurrentMove(from, move); + } + else + { + Spell spell = SpellRegistry.NewSpell(spellID, from, null); + + if (spell != null) + spell.Cast(); + else + from.SendLocalizedMessage(502345); // This spell has been temporarily disabled. + } + } + else + { + from.SendLocalizedMessage(500015); // You do not have that spell! + } + } + + public static SpellbookType GetTypeForSpell(int spellID) + { + if (spellID >= 0 && spellID < 64) + return SpellbookType.Regular; + if (spellID >= 100 && spellID < 117) + return SpellbookType.Necromancer; + if (spellID >= 200 && spellID < 210) + return SpellbookType.Paladin; + if (spellID >= 400 && spellID < 406) + return SpellbookType.Samurai; + if (spellID >= 500 && spellID < 508) + return SpellbookType.Ninja; + if (spellID >= 600 && spellID < 617) + return SpellbookType.Arcanist; + if (spellID >= 677 && spellID < 693) + return SpellbookType.Mystic; + + return SpellbookType.Invalid; + } + + public static Spellbook FindRegular(Mobile from) + { + return Find(from, -1, SpellbookType.Regular); + } + + public static Spellbook FindNecromancer(Mobile from) + { + return Find(from, -1, SpellbookType.Necromancer); + } + + public static Spellbook FindPaladin(Mobile from) + { + return Find(from, -1, SpellbookType.Paladin); + } + + public static Spellbook FindSamurai(Mobile from) + { + return Find(from, -1, SpellbookType.Samurai); + } + + public static Spellbook FindNinja(Mobile from) + { + return Find(from, -1, SpellbookType.Ninja); + } + + public static Spellbook FindArcanist(Mobile from) + { + return Find(from, -1, SpellbookType.Arcanist); + } + + public static Spellbook FindMystic(Mobile from) + { + return Find(from, -1, SpellbookType.Mystic); + } + + public static Spellbook Find(Mobile from, int spellID) + { + return Find(from, spellID, GetTypeForSpell(spellID)); + } + + public static Spellbook Find(Mobile from, int spellID, SpellbookType type) + { + if (from == null) + return null; + + if (from.Deleted) + { + m_Table.Remove(from); + return null; + } + + m_Table.TryGetValue(from, out List list); + + bool searchAgain = false; + + if (list == null) + m_Table[from] = list = FindAllSpellbooks(from); + else + searchAgain = true; + + Spellbook book = FindSpellbookInList(list, from, spellID, type); + + if (book == null && searchAgain) + { + m_Table[from] = list = FindAllSpellbooks(from); + + book = FindSpellbookInList(list, from, spellID, type); + } + + return book; + } + + public static Spellbook FindSpellbookInList(List list, Mobile from, int spellID, SpellbookType type) + { + Container pack = from.Backpack; + + for (int i = list.Count - 1; i >= 0; --i) + { + if (i >= list.Count) + continue; + + Spellbook book = list[i]; - for ( int i = 0; i < pack.Items.Count; ++i ) - { - item = pack.Items[i]; + if (!book.Deleted && (book.Parent == from || pack != null && book.Parent == pack) && + ValidateSpellbook(book, spellID, type)) + return book; - if ( item is Spellbook spellbook1 ) - list.Add( spellbook1 ); - } + list.RemoveAt(i); + } - return list; - } + return null; + } - public static Spellbook FindEquippedSpellbook( Mobile from ) - { - return (from.FindItemOnLayer( Layer.OneHanded ) as Spellbook); - } + public static List FindAllSpellbooks(Mobile from) + { + List list = new List(); - public static bool ValidateSpellbook( Spellbook book, int spellID, SpellbookType type ) - { - return ( book.SpellbookType == type && ( spellID == -1 || book.HasSpell( spellID ) ) ); - } + Item item = from.FindItemOnLayer(Layer.OneHanded); - public override bool DisplayWeight => false; + if (item is Spellbook spellbook) + list.Add(spellbook); - private AosAttributes m_AosAttributes; - private AosSkillBonuses m_AosSkillBonuses; + Container pack = from.Backpack; - [CommandProperty( AccessLevel.GameMaster )] - public AosAttributes Attributes - { - get => m_AosAttributes; - set{} - } + if (pack == null) + return list; - [CommandProperty( AccessLevel.GameMaster )] - public AosSkillBonuses SkillBonuses - { - get => m_AosSkillBonuses; - set{} - } + for (int i = 0; i < pack.Items.Count; ++i) + { + item = pack.Items[i]; - public virtual SpellbookType SpellbookType => SpellbookType.Regular; - public virtual int BookOffset => 0; - public virtual int BookCount => 64; + if (item is Spellbook spellbook1) + list.Add(spellbook1); + } - private ulong m_Content; + return list; + } - public override bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - if ( !Ethics.Ethic.CheckTrade( from, to, newOwner, this ) ) - return false; + public static Spellbook FindEquippedSpellbook(Mobile from) + { + return from.FindItemOnLayer(Layer.OneHanded) as Spellbook; + } - return base.AllowSecureTrade( from, to, newOwner, accepted ); - } + public static bool ValidateSpellbook(Spellbook book, int spellID, SpellbookType type) + { + return book.SpellbookType == type && (spellID == -1 || book.HasSpell(spellID)); + } - public override bool CanEquip( Mobile from ) - { - if ( !Ethics.Ethic.CheckEquip( from, this ) ) - { - return false; - } - - if ( !from.CanBeginAction( typeof( BaseWeapon ) ) ) - { - return false; - } - - return base.CanEquip( from ); - } - - public override bool AllowEquippedCast( Mobile from ) - { - return true; - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is SpellScroll scroll && scroll.Amount == 1 ) - { - SpellbookType type = GetTypeForSpell( scroll.SpellID ); - - if ( type != SpellbookType ) - { - return false; - } - - if ( HasSpell( scroll.SpellID ) ) - { - from.SendLocalizedMessage( 500179 ); // That spell is already present in that spellbook. - return false; - } - - int val = scroll.SpellID - BookOffset; - - if ( val >= 0 && val < BookCount ) - { - m_Content |= (ulong)1 << val; - ++SpellCount; - - InvalidateProperties(); - - scroll.Delete(); - - from.Send( new PlaySound( 0x249, GetWorldLocation() ) ); - return true; - } - } - - return false; - } - - [CommandProperty( AccessLevel.GameMaster )] - public ulong Content - { - get => m_Content; - set - { - if ( m_Content != value ) - { - m_Content = value; - - SpellCount = 0; - - while ( value > 0 ) - { - SpellCount += (int)(value & 0x1); - value >>= 1; - } - - InvalidateProperties(); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SpellCount { get; private set; } - - [Constructible] - public Spellbook() : this( (ulong)0 ) - { - } - - [Constructible] - public Spellbook( ulong content ) : this( content, 0xEFA ) - { - } - - public Spellbook( ulong content, int itemID ) : base( itemID ) - { - m_AosAttributes = new AosAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - - Weight = 3.0; - Layer = Layer.OneHanded; - LootType = LootType.Blessed; - - Content = content; - } - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is Spellbook book) ) - return; - - book.m_AosAttributes = new AosAttributes( newItem, m_AosAttributes ); - book.m_AosSkillBonuses = new AosSkillBonuses( newItem, m_AosSkillBonuses ); - } - - public override void OnAdded(IEntity parent) - { - if ( Core.AOS && parent is Mobile from ) - { - m_AosSkillBonuses.AddTo( from ); - - int strBonus = m_AosAttributes.BonusStr; - int dexBonus = m_AosAttributes.BonusDex; - int intBonus = m_AosAttributes.BonusInt; - - if ( strBonus != 0 || dexBonus != 0 || intBonus != 0 ) - { - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - from.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - from.CheckStatTimers(); - } - } - - public override void OnRemoved(IEntity parent) - { - if ( Core.AOS && parent is Mobile from ) - { - m_AosSkillBonuses.Remove(); - - string modName = Serial.ToString(); - - from.RemoveStatMod( modName + "Str" ); - from.RemoveStatMod( modName + "Dex" ); - from.RemoveStatMod( modName + "Int" ); - - from.CheckStatTimers(); - } - } - - public bool HasSpell( int spellID ) - { - spellID -= BookOffset; - - return ( spellID >= 0 && spellID < BookCount && (m_Content & ((ulong)1 << spellID)) != 0 ); - } - - public Spellbook( Serial serial ) : base( serial ) - { - } - - public void DisplayTo( Mobile to ) - { - // The client must know about the spellbook or it will crash! - - NetState ns = to.NetState; - - if ( ns == null ) - return; - - if ( Parent == null ) - { - to.Send( WorldPacket ); - } - else if ( Parent is Item ) - { - // What will happen if the client doesn't know about our parent? - if ( ns.ContainerGridLines ) - to.Send( new ContainerContentUpdate6017( this ) ); - else - to.Send( new ContainerContentUpdate( this ) ); - } - else if ( Parent is Mobile ) - { - // What will happen if the client doesn't know about our parent? - to.Send( new EquipUpdate( this ) ); - } - - if ( ns.HighSeas ) - to.Send( new DisplaySpellbookHS( this ) ); - else - to.Send( new DisplaySpellbook( this ) ); - - if ( ObjectPropertyList.Enabled ) { - if ( ns.NewSpellbook ) { - to.Send( new NewSpellbookContent( this, ItemID, BookOffset + 1, m_Content ) ); - } else { - if (ns.ContainerGridLines) { - to.Send(new SpellbookContent6017(SpellCount, BookOffset + 1, m_Content, this)); - } else { - to.Send(new SpellbookContent(SpellCount, BookOffset + 1, m_Content, this)); - } - } - } else { - if ( ns.ContainerGridLines ) { - to.Send( new SpellbookContent6017( SpellCount, BookOffset + 1, m_Content, this ) ); - } else { - to.Send( new SpellbookContent( SpellCount, BookOffset + 1, m_Content, this ) ); - } - } - } + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (!Ethic.CheckTrade(from, to, newOwner, this)) + return false; - private Mobile m_Crafter; + return base.AllowSecureTrade(from, to, newOwner, accepted); + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } + public override bool CanEquip(Mobile from) + { + if (!Ethic.CheckEquip(from, this)) return false; - public override bool DisplayLootType => Core.AOS; + if (!from.CanBeginAction(typeof(BaseWeapon))) return false; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + return base.CanEquip(from); + } - if ( m_Quality == BookQuality.Exceptional ) - list.Add( 1063341 ); // exceptional + public override bool AllowEquippedCast(Mobile from) + { + return true; + } - if ( m_EngravedText != null ) - list.Add( 1072305, m_EngravedText ); // Engraved: ~1_INSCRIPTION~ + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is SpellScroll scroll && scroll.Amount == 1) + { + SpellbookType type = GetTypeForSpell(scroll.SpellID); - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if (type != SpellbookType) return false; - m_AosSkillBonuses.GetProperties( list ); + if (HasSpell(scroll.SpellID)) + { + from.SendLocalizedMessage(500179); // That spell is already present in that spellbook. + return false; + } - if ( m_Slayer != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer ); - if ( entry != null ) - list.Add( entry.Title ); - } + int val = scroll.SpellID - BookOffset; - if ( m_Slayer2 != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer2 ); - if ( entry != null ) - list.Add( entry.Title ); - } + if (val >= 0 && val < BookCount) + { + m_Content |= (ulong)1 << val; + ++SpellCount; - int prop; + InvalidateProperties(); - if ( (prop = m_AosAttributes.WeaponDamage) != 0 ) - list.Add( 1060401, prop.ToString() ); // damage increase ~1_val~% + scroll.Delete(); - if ( (prop = m_AosAttributes.DefendChance) != 0 ) - list.Add( 1060408, prop.ToString() ); // defense chance increase ~1_val~% + from.Send(new PlaySound(0x249, GetWorldLocation())); + return true; + } + } - if ( (prop = m_AosAttributes.BonusDex) != 0 ) - list.Add( 1060409, prop.ToString() ); // dexterity bonus ~1_val~ + return false; + } + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is Spellbook book)) + return; + + book.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); + book.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); + } + + public override void OnAdded(IEntity parent) + { + if (Core.AOS && parent is Mobile from) + { + m_AosSkillBonuses.AddTo(from); + + int strBonus = m_AosAttributes.BonusStr; + int dexBonus = m_AosAttributes.BonusDex; + int intBonus = m_AosAttributes.BonusInt; + + if (strBonus != 0 || dexBonus != 0 || intBonus != 0) + { + string modName = Serial.ToString(); + + if (strBonus != 0) + from.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + from.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + from.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + from.CheckStatTimers(); + } + } + + public override void OnRemoved(IEntity parent) + { + if (Core.AOS && parent is Mobile from) + { + m_AosSkillBonuses.Remove(); + + string modName = Serial.ToString(); + + from.RemoveStatMod(modName + "Str"); + from.RemoveStatMod(modName + "Dex"); + from.RemoveStatMod(modName + "Int"); + + from.CheckStatTimers(); + } + } + + public bool HasSpell(int spellID) + { + spellID -= BookOffset; + + return spellID >= 0 && spellID < BookCount && (m_Content & ((ulong)1 << spellID)) != 0; + } + + public void DisplayTo(Mobile to) + { + // The client must know about the spellbook or it will crash! + + NetState ns = to.NetState; + + if (ns == null) + return; + + if (Parent == null) + { + to.Send(WorldPacket); + } + else if (Parent is Item) + { + // What will happen if the client doesn't know about our parent? + if (ns.ContainerGridLines) + to.Send(new ContainerContentUpdate6017(this)); + else + to.Send(new ContainerContentUpdate(this)); + } + else if (Parent is Mobile) + { + // What will happen if the client doesn't know about our parent? + to.Send(new EquipUpdate(this)); + } + + if (ns.HighSeas) + to.Send(new DisplaySpellbookHS(this)); + else + to.Send(new DisplaySpellbook(this)); + + if (ObjectPropertyList.Enabled) + { + if (ns.NewSpellbook) + { + to.Send(new NewSpellbookContent(this, ItemID, BookOffset + 1, m_Content)); + } + else + { + if (ns.ContainerGridLines) + to.Send(new SpellbookContent6017(SpellCount, BookOffset + 1, m_Content, this)); + else + to.Send(new SpellbookContent(SpellCount, BookOffset + 1, m_Content, this)); + } + } + else + { + if (ns.ContainerGridLines) + to.Send(new SpellbookContent6017(SpellCount, BookOffset + 1, m_Content, this)); + else + to.Send(new SpellbookContent(SpellCount, BookOffset + 1, m_Content, this)); + } + } - if ( (prop = m_AosAttributes.EnhancePotions) != 0 ) - list.Add( 1060411, prop.ToString() ); // enhance potions ~1_val~% - - if ( (prop = m_AosAttributes.CastRecovery) != 0 ) - list.Add( 1060412, prop.ToString() ); // faster cast recovery ~1_val~ - - if ( (prop = m_AosAttributes.CastSpeed) != 0 ) - list.Add( 1060413, prop.ToString() ); // faster casting ~1_val~ - - if ( (prop = m_AosAttributes.AttackChance) != 0 ) - list.Add( 1060415, prop.ToString() ); // hit chance increase ~1_val~% + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( (prop = m_AosAttributes.BonusHits) != 0 ) - list.Add( 1060431, prop.ToString() ); // hit point increase ~1_val~ + if (m_Quality == BookQuality.Exceptional) + list.Add(1063341); // exceptional - if ( (prop = m_AosAttributes.BonusInt) != 0 ) - list.Add( 1060432, prop.ToString() ); // intelligence bonus ~1_val~ + if (m_EngravedText != null) + list.Add(1072305, m_EngravedText); // Engraved: ~1_INSCRIPTION~ - if ( (prop = m_AosAttributes.LowerManaCost) != 0 ) - list.Add( 1060433, prop.ToString() ); // lower mana cost ~1_val~% + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ - if ( (prop = m_AosAttributes.LowerRegCost) != 0 ) - list.Add( 1060434, prop.ToString() ); // lower reagent cost ~1_val~% + m_AosSkillBonuses.GetProperties(list); + + if (m_Slayer != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer); + if (entry != null) + list.Add(entry.Title); + } - if ( (prop = m_AosAttributes.Luck) != 0 ) - list.Add( 1060436, prop.ToString() ); // luck ~1_val~ + if (m_Slayer2 != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer2); + if (entry != null) + list.Add(entry.Title); + } + + int prop; + + if ((prop = m_AosAttributes.WeaponDamage) != 0) + list.Add(1060401, prop.ToString()); // damage increase ~1_val~% - if ( (prop = m_AosAttributes.BonusMana) != 0 ) - list.Add( 1060439, prop.ToString() ); // mana increase ~1_val~ + if ((prop = m_AosAttributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% - if ( (prop = m_AosAttributes.RegenMana) != 0 ) - list.Add( 1060440, prop.ToString() ); // mana regeneration ~1_val~ + if ((prop = m_AosAttributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ - if ( (prop = m_AosAttributes.NightSight) != 0 ) - list.Add( 1060441 ); // night sight + if ((prop = m_AosAttributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% - if ( (prop = m_AosAttributes.ReflectPhysical) != 0 ) - list.Add( 1060442, prop.ToString() ); // reflect physical damage ~1_val~% + if ((prop = m_AosAttributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ - if ( (prop = m_AosAttributes.RegenStam) != 0 ) - list.Add( 1060443, prop.ToString() ); // stamina regeneration ~1_val~ + if ((prop = m_AosAttributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - if ( (prop = m_AosAttributes.RegenHits) != 0 ) - list.Add( 1060444, prop.ToString() ); // hit point regeneration ~1_val~ + if ((prop = m_AosAttributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - if ( (prop = m_AosAttributes.SpellChanneling) != 0 ) - list.Add( 1060482 ); // spell channeling + if ((prop = m_AosAttributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if ( (prop = m_AosAttributes.SpellDamage) != 0 ) - list.Add( 1060483, prop.ToString() ); // spell damage increase ~1_val~% + if ((prop = m_AosAttributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - if ( (prop = m_AosAttributes.BonusStam) != 0 ) - list.Add( 1060484, prop.ToString() ); // stamina increase ~1_val~ + if ((prop = m_AosAttributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if ( (prop = m_AosAttributes.BonusStr) != 0 ) - list.Add( 1060485, prop.ToString() ); // strength bonus ~1_val~ + if ((prop = m_AosAttributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - if ( (prop = m_AosAttributes.WeaponSpeed) != 0 ) - list.Add( 1060486, prop.ToString() ); // swing speed increase ~1_val~% + if ((prop = m_AosAttributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - if ( Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0 ) - list.Add( 1075210, prop.ToString() ); // Increased Karma Loss ~1val~% + if ((prop = m_AosAttributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - list.Add( 1042886, SpellCount.ToString() ); // ~1_NUMBERS_OF_SPELLS~ Spells - } + if ((prop = m_AosAttributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + if ((prop = m_AosAttributes.NightSight) != 0) + list.Add(1060441); // night sight - if ( m_Crafter != null ) - LabelTo( from, 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if ((prop = m_AosAttributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - LabelTo( from, 1042886, SpellCount.ToString() ); - } + if ((prop = m_AosAttributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - public override void OnDoubleClick( Mobile from ) - { - Container pack = from.Backpack; + if ((prop = m_AosAttributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if ( Parent == from || ( pack != null && Parent == pack ) ) - DisplayTo( from ); - else - from.SendLocalizedMessage( 500207 ); // The spellbook must be in your backpack (and not in a container within) to open. - } + if ((prop = m_AosAttributes.SpellChanneling) != 0) + list.Add(1060482); // spell channeling + if ((prop = m_AosAttributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - private SlayerName m_Slayer; - private SlayerName m_Slayer2; - //Currently though there are no dual slayer spellbooks, OSI has a habit of putting dual slayer stuff in later + if ((prop = m_AosAttributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - [CommandProperty( AccessLevel.GameMaster )] - public SlayerName Slayer - { - get => m_Slayer; - set { m_Slayer = value; InvalidateProperties(); } - } + if ((prop = m_AosAttributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - [CommandProperty( AccessLevel.GameMaster )] - public SlayerName Slayer2 - { - get => m_Slayer2; - set { m_Slayer2 = value; InvalidateProperties(); } - } + if ((prop = m_AosAttributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) + list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% - writer.Write( (int) 5 ); // version + list.Add(1042886, SpellCount.ToString()); // ~1_NUMBERS_OF_SPELLS~ Spells + } - writer.Write( (byte) m_Quality ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - writer.Write( (string) m_EngravedText ); + if (m_Crafter != null) + LabelTo(from, 1050043, m_Crafter.Name); // crafted by ~1_NAME~ - writer.Write( m_Crafter ); + LabelTo(from, 1042886, SpellCount.ToString()); + } - writer.Write( (int)m_Slayer ); - writer.Write( (int)m_Slayer2 ); + public override void OnDoubleClick(Mobile from) + { + Container pack = from.Backpack; - m_AosAttributes.Serialize( writer ); - m_AosSkillBonuses.Serialize( writer ); + if (Parent == from || pack != null && Parent == pack) + DisplayTo(from); + else + from.SendLocalizedMessage( + 500207); // The spellbook must be in your backpack (and not in a container within) to open. + } - writer.Write( m_Content ); - writer.Write( SpellCount ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 5: - { - m_Quality = (BookQuality) reader.ReadByte(); - - goto case 4; - } - case 4: - { - m_EngravedText = reader.ReadString(); - - goto case 3; - } - case 3: - { - m_Crafter = reader.ReadMobile(); - goto case 2; - } - case 2: - { - m_Slayer = (SlayerName)reader.ReadInt(); - m_Slayer2 = (SlayerName)reader.ReadInt(); - goto case 1; - } - case 1: - { - m_AosAttributes = new AosAttributes( this, reader ); - m_AosSkillBonuses = new AosSkillBonuses( this, reader ); - - goto case 0; - } - case 0: - { - m_Content = reader.ReadULong(); - SpellCount = reader.ReadInt(); - - break; - } - } - - if ( m_AosAttributes == null ) - m_AosAttributes = new AosAttributes( this ); - - if ( m_AosSkillBonuses == null ) - m_AosSkillBonuses = new AosSkillBonuses( this ); - - if ( Core.AOS && Parent is Mobile mobile ) - m_AosSkillBonuses.AddTo( mobile ); - - int strBonus = m_AosAttributes.BonusStr; - int dexBonus = m_AosAttributes.BonusDex; - int intBonus = m_AosAttributes.BonusInt; - - if ( Parent is Mobile m ) - { - if (strBonus != 0 || dexBonus != 0 || intBonus != 0) - { - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - m.CheckStatTimers(); - } - } - - private static int[] m_LegendPropertyCounts = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0 properties : 21/52 : 40% - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 1 property : 15/52 : 29% - 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // 2 properties : 10/52 : 19% - 3, 3, 3, 3, 3, 3 // 3 properties : 6/52 : 12% - - }; - - private static int[] m_ElderPropertyCounts = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,// 0 properties : 15/34 : 44% - 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // 1 property : 10/34 : 29% - 2, 2, 2, 2, 2, 2, // 2 properties : 6/34 : 18% - 3, 3, 3 // 3 properties : 3/34 : 9% - }; - - private static int[] m_GrandPropertyCounts = { - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0 properties : 10/20 : 50% - 1, 1, 1, 1, 1, 1, // 1 property : 6/20 : 30% - 2, 2, 2, // 2 properties : 3/20 : 15% - 3 // 3 properties : 1/20 : 5% - }; - - private static int[] m_MasterPropertyCounts = { - 0, 0, 0, 0, 0, 0, // 0 properties : 6/10 : 60% - 1, 1, 1, // 1 property : 3/10 : 30% - 2 // 2 properties : 1/10 : 10% - }; - - private static int[] m_AdeptPropertyCounts = { - 0, 0, 0, // 0 properties : 3/4 : 75% - 1 // 1 property : 1/4 : 25% - }; - - public virtual int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - int magery = from.Skills.Magery.BaseFixedPoint; - - if ( magery >= 800 ) - { - int[] propertyCounts; - int minIntensity; - int maxIntensity; - - if ( magery >= 1000 ) - { - if ( magery >= 1200 ) - propertyCounts = m_LegendPropertyCounts; - else if ( magery >= 1100 ) - propertyCounts = m_ElderPropertyCounts; - else - propertyCounts = m_GrandPropertyCounts; - - minIntensity = 55; - maxIntensity = 75; - } - else if ( magery >= 900 ) - { - propertyCounts = m_MasterPropertyCounts; - minIntensity = 25; - maxIntensity = 45; - } - else - { - propertyCounts = m_AdeptPropertyCounts; - minIntensity = 0; - maxIntensity = 15; - } - - int propertyCount = propertyCounts[Utility.Random( propertyCounts.Length )]; - - BaseRunicTool.ApplyAttributesTo( this, true, 0, propertyCount, minIntensity, maxIntensity ); - } - - if ( makersMark ) - Crafter = from; - - m_Quality = (BookQuality) ( quality - 1 ); - - return quality; - } - } -} + writer.Write(5); // version + + writer.Write((byte)m_Quality); + + writer.Write(m_EngravedText); + + writer.Write(m_Crafter); + + writer.Write((int)m_Slayer); + writer.Write((int)m_Slayer2); + + m_AosAttributes.Serialize(writer); + m_AosSkillBonuses.Serialize(writer); + + writer.Write(m_Content); + writer.Write(SpellCount); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 5: + { + m_Quality = (BookQuality)reader.ReadByte(); + + goto case 4; + } + case 4: + { + m_EngravedText = reader.ReadString(); + + goto case 3; + } + case 3: + { + m_Crafter = reader.ReadMobile(); + goto case 2; + } + case 2: + { + m_Slayer = (SlayerName)reader.ReadInt(); + m_Slayer2 = (SlayerName)reader.ReadInt(); + goto case 1; + } + case 1: + { + m_AosAttributes = new AosAttributes(this, reader); + m_AosSkillBonuses = new AosSkillBonuses(this, reader); + + goto case 0; + } + case 0: + { + m_Content = reader.ReadULong(); + SpellCount = reader.ReadInt(); + + break; + } + } + + if (m_AosAttributes == null) + m_AosAttributes = new AosAttributes(this); + + if (m_AosSkillBonuses == null) + m_AosSkillBonuses = new AosSkillBonuses(this); + + if (Core.AOS && Parent is Mobile mobile) + m_AosSkillBonuses.AddTo(mobile); + + int strBonus = m_AosAttributes.BonusStr; + int dexBonus = m_AosAttributes.BonusDex; + int intBonus = m_AosAttributes.BonusInt; + + if (Parent is Mobile m) + { + if (strBonus != 0 || dexBonus != 0 || intBonus != 0) + { + string modName = Serial.ToString(); + + if (strBonus != 0) + m.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + m.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + m.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + m.CheckStatTimers(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Magical/SpellweavingBook.cs b/Scripts/Items/Skill Items/Magical/SpellweavingBook.cs index 8f4dcf3cf..92887eb0c 100644 --- a/Scripts/Items/Skill Items/Magical/SpellweavingBook.cs +++ b/Scripts/Items/Skill Items/Magical/SpellweavingBook.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class SpellweavingBook : Spellbook - { - public override SpellbookType SpellbookType => SpellbookType.Arcanist; - public override int BookOffset => 600; - public override int BookCount => 16; + public class SpellweavingBook : Spellbook + { + [Constructible] + public SpellweavingBook() : this((ulong)0) + { + } - [Constructible] - public SpellweavingBook() : this( (ulong)0 ) - { - } + [Constructible] + public SpellweavingBook(ulong content) : base(content, 0x2D50) + { + Hue = 0x8A2; - [Constructible] - public SpellweavingBook( ulong content ) : base( content, 0x2D50 ) - { - Hue = 0x8A2; + Layer = Layer.OneHanded; + } - Layer = Layer.OneHanded; - } + public SpellweavingBook(Serial serial) : base(serial) + { + } - public SpellweavingBook( Serial serial ) : base( serial ) - { - } + public override SpellbookType SpellbookType => SpellbookType.Arcanist; + public override int BookOffset => 600; + public override int BookCount => 16; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Misc/Bandage.cs b/Scripts/Items/Skill Items/Misc/Bandage.cs index e4d0cd7ef..da94c05f4 100644 --- a/Scripts/Items/Skill Items/Misc/Bandage.cs +++ b/Scripts/Items/Skill Items/Misc/Bandage.cs @@ -1,541 +1,539 @@ using System; using System.Collections.Generic; +using Server.Engines.ConPVP; +using Server.Factions; using Server.Gumps; using Server.Mobiles; using Server.Targeting; namespace Server.Items { - public class Bandage : Item, IDyable - { - public static int Range = ( Core.AOS ? 2 : 1 ); - - public override double DefaultWeight => 0.1; - - public static void Initialize() - { - EventSink.BandageTargetRequest += EventSink_BandageTargetRequest; - } - - [Constructible] - public Bandage() : this( 1 ) - { - } - - [Constructible] - public Bandage( int amount ) : base( 0xE21 ) - { - Stackable = true; - Amount = amount; - } - - public Bandage( Serial serial ) : base( serial ) - { - } - - public virtual bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; - - Hue = sender.DyedHue; - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), Range ) ) - { - from.RevealingAction(); - - from.SendLocalizedMessage( 500948 ); // Who will you use the bandages on? - - from.Target = new InternalTarget( this ); - } - else - { - from.SendLocalizedMessage( 500295 ); // You are too far away to do that. - } - } - - private static void EventSink_BandageTargetRequest(BandageTargetRequestEventArgs e) - { - if (!(e.Bandage is Bandage b) || b.Deleted) - return; - - Mobile from = e.Mobile; - - if (from.InRange(b.GetWorldLocation(), Range)) - { - Target t = from.Target; - - if (t != null) - { - Target.Cancel(from); - from.Target = null; - } - - from.RevealingAction(); - - from.SendLocalizedMessage(500948); // Who will you use the bandages on? - - new InternalTarget(b).Invoke(from, e.Target); - } - else - { - from.SendLocalizedMessage(500295); // You are too far away to do that. - } - } - - private class InternalTarget : Target - { - private Bandage m_Bandage; - - public InternalTarget( Bandage bandage ) : base( Bandage.Range, false, TargetFlags.Beneficial ) - { - m_Bandage = bandage; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Bandage.Deleted ) - return; - - if ( targeted is Mobile mobile ) - { - if ( from.InRange( m_Bandage.GetWorldLocation(), Bandage.Range ) ) - { - if ( BandageContext.BeginHeal( from, mobile ) != null ) - { - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - m_Bandage.Consume(); - } - } - else - { - from.SendLocalizedMessage( 500295 ); // You are too far away to do that. - } - } - else if ( targeted is PlagueBeastInnard innard ) - { - if ( innard.OnBandage( from ) ) - m_Bandage.Consume(); - } - else - { - from.SendLocalizedMessage( 500970 ); // Bandages can not be used on that. - } - } - - protected override void OnNonlocalTarget( Mobile from, object targeted ) - { - if ( targeted is PlagueBeastInnard innard ) - { - if ( innard.OnBandage( from ) ) - m_Bandage.Consume(); - } - else - base.OnNonlocalTarget( from, targeted ); - } - } - } - - public class BandageContext - { - public Mobile Healer { get; } - - public Mobile Patient { get; } - - public int Slips { get; set; } - - public Timer Timer { get; private set; } - - public void Slip() - { - Healer.SendLocalizedMessage( 500961 ); // Your fingers slip! - ++Slips; - } - - public BandageContext( Mobile healer, Mobile patient, TimeSpan delay ) - { - Healer = healer; - Patient = patient; - - Timer = new InternalTimer( this, delay ); - Timer.Start(); - } - - public void StopHeal() - { - m_Table.Remove( Healer ); - - Timer?.Stop(); - - Timer = null; - } - - private static Dictionary m_Table = new Dictionary(); - - public static BandageContext GetContext( Mobile healer ) - { - m_Table.TryGetValue( healer, out BandageContext bc ); - return bc; - } - - public static SkillName GetPrimarySkill( Mobile m ) - { - if ( !m.Player && (m.Body.IsMonster || m.Body.IsAnimal) ) - return SkillName.Veterinary; - return SkillName.Healing; - } - - public static SkillName GetSecondarySkill( Mobile m ) - { - if ( !m.Player && (m.Body.IsMonster || m.Body.IsAnimal) ) - return SkillName.AnimalLore; - return SkillName.Anatomy; - } - - public void EndHeal() - { - StopHeal(); - - int healerNumber = -1, patientNumber = -1; - bool playSound = true; - bool checkSkills = false; - - SkillName primarySkill = GetPrimarySkill( Patient ); - SkillName secondarySkill = GetSecondarySkill( Patient ); - - BaseCreature petPatient = Patient as BaseCreature; - - if ( !Healer.Alive ) - { - healerNumber = 500962; // You were unable to finish your work before you died. - patientNumber = -1; - playSound = false; - } - else if ( !Healer.InRange( Patient, Bandage.Range ) ) - { - healerNumber = 500963; // You did not stay close enough to heal your target. - patientNumber = -1; - playSound = false; - } - else if ( !Patient.Alive || (petPatient != null && petPatient.IsDeadPet) ) - { - double healing = Healer.Skills[primarySkill].Value; - double anatomy = Healer.Skills[secondarySkill].Value; - double chance = ((healing - 68.0) / 50.0) - (Slips * 0.02); - - if (( (checkSkills = (healing >= 80.0 && anatomy >= 80.0)) && chance > Utility.RandomDouble() ) - || ( Core.SE && petPatient is Factions.FactionWarHorse && petPatient.ControlMaster == Healer) ) //TODO: Dbl check doesn't check for faction of the horse here? - { - if ( Patient.Map == null || !Patient.Map.CanFit( Patient.Location, 16, false, false ) ) - { - healerNumber = 501042; // Target can not be resurrected at that location. - patientNumber = 502391; // Thou can not be resurrected there! - } - else if ( Patient.Region != null && Patient.Region.IsPartOf( "Khaldun" ) ) - { - healerNumber = 1010395; // The veil of death in this area is too strong and resists thy efforts to restore life. - patientNumber = -1; - } - else - { - healerNumber = 500965; // You are able to resurrect your patient. - patientNumber = -1; - - Patient.PlaySound( 0x214 ); - Patient.FixedEffect( 0x376A, 10, 16 ); - - if ( petPatient != null && petPatient.IsDeadPet ) - { - Mobile master = petPatient.ControlMaster; - - if ( master != null && Healer == master ) - { - petPatient.ResurrectPet(); - - for ( int i = 0; i < petPatient.Skills.Length; ++i ) - { - petPatient.Skills[i].Base -= 0.1; - } - } - else if ( master != null && master.InRange( petPatient, 3 ) ) - { - healerNumber = 503255; // You are able to resurrect the creature. - - master.CloseGump( typeof( PetResurrectGump ) ); - master.SendGump( new PetResurrectGump( Healer, petPatient ) ); - } - else - { - bool found = false; - - List friends = petPatient.Friends; - - for ( int i = 0; friends != null && i < friends.Count; ++i ) - { - Mobile friend = friends[i]; - - if ( friend.InRange( petPatient, 3 ) ) - { - healerNumber = 503255; // You are able to resurrect the creature. - - friend.CloseGump( typeof( PetResurrectGump ) ); - friend.SendGump( new PetResurrectGump( Healer, petPatient ) ); - - found = true; - break; - } - } - - if ( !found ) - healerNumber = 1049670; // The pet's owner must be nearby to attempt resurrection. - } - } - else - { - Patient.CloseGump( typeof( ResurrectGump ) ); - Patient.SendGump( new ResurrectGump( Patient, Healer ) ); - } - } - } - else - { - if ( petPatient != null && petPatient.IsDeadPet ) - healerNumber = 503256; // You fail to resurrect the creature. - else - healerNumber = 500966; // You are unable to resurrect your patient. - - patientNumber = -1; - } - } - else if ( Patient.Poisoned ) - { - Healer.SendLocalizedMessage( 500969 ); // You finish applying the bandages. - - double healing = Healer.Skills[primarySkill].Value; - double anatomy = Healer.Skills[secondarySkill].Value; - double chance = ((healing - 30.0) / 50.0) - (Patient.Poison.Level * 0.1) - (Slips * 0.02); - - if ( (checkSkills = (healing >= 60.0 && anatomy >= 60.0)) && chance > Utility.RandomDouble() ) - { - if ( Patient.CurePoison( Healer ) ) - { - healerNumber = (Healer == Patient) ? -1 : 1010058; // You have cured the target of all poisons. - patientNumber = 1010059; // You have been cured of all poisons. - } - else - { - healerNumber = -1; - patientNumber = -1; - } - } - else - { - healerNumber = 1010060; // You have failed to cure your target! - patientNumber = -1; - } - } - else if ( BleedAttack.IsBleeding( Patient ) ) - { - healerNumber = 1060088; // You bind the wound and stop the bleeding - patientNumber = 1060167; // The bleeding wounds have healed, you are no longer bleeding! - - BleedAttack.EndBleed( Patient, false ); - } - else if ( MortalStrike.IsWounded( Patient ) ) - { - healerNumber = ( Healer == Patient ? 1005000 : 1010398 ); - patientNumber = -1; - playSound = false; - } - else if ( Patient.Hits == Patient.HitsMax ) - { - healerNumber = 500967; // You heal what little damage your patient had. - patientNumber = -1; - } - else - { - checkSkills = true; - patientNumber = -1; - - double healing = Healer.Skills[primarySkill].Value; - double anatomy = Healer.Skills[secondarySkill].Value; - double chance = ((healing + 10.0) / 100.0) - (Slips * 0.02); - - if ( chance > Utility.RandomDouble() ) - { - healerNumber = 500969; // You finish applying the bandages. - - double min, max; - - if ( Core.AOS ) - { - min = (anatomy / 8.0) + (healing / 5.0) + 4.0; - max = (anatomy / 6.0) + (healing / 2.5) + 4.0; - } - else - { - min = (anatomy / 5.0) + (healing / 5.0) + 3.0; - max = (anatomy / 5.0) + (healing / 2.0) + 10.0; - } - - double toHeal = min + (Utility.RandomDouble() * (max - min)); - - if ( Patient.Body.IsMonster || Patient.Body.IsAnimal ) - toHeal += Patient.HitsMax / 100; - - if ( Core.AOS ) - toHeal -= toHeal * Slips * 0.35; // TODO: Verify algorithm - else - toHeal -= Slips * 4; - - if ( toHeal < 1 ) - { - toHeal = 1; - healerNumber = 500968; // You apply the bandages, but they barely help. - } - - Patient.Heal( (int) toHeal, Healer, false ); - } - else - { - healerNumber = 500968; // You apply the bandages, but they barely help. - playSound = false; - } - } - - if ( healerNumber != -1 ) - Healer.SendLocalizedMessage( healerNumber ); - - if ( patientNumber != -1 ) - Patient.SendLocalizedMessage( patientNumber ); - - if ( playSound ) - Patient.PlaySound( 0x57 ); - - if ( checkSkills ) - { - Healer.CheckSkill( secondarySkill, 0.0, 120.0 ); - Healer.CheckSkill( primarySkill, 0.0, 120.0 ); - } - } - - private class InternalTimer : Timer - { - private BandageContext m_Context; - - public InternalTimer( BandageContext context, TimeSpan delay ) : base( delay ) - { - m_Context = context; - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - m_Context.EndHeal(); - } - } - - public static BandageContext BeginHeal( Mobile healer, Mobile patient ) - { - BaseCreature creature = patient as BaseCreature; - - if ( patient is Golem ) - { - healer.SendLocalizedMessage( 500970 ); // Bandages cannot be used on that. - } - else if ( creature?.IsAnimatedDead == true ) - { - healer.SendLocalizedMessage( 500951 ); // You cannot heal that. - } - else if ( !patient.Poisoned && patient.Hits == patient.HitsMax && !BleedAttack.IsBleeding( patient ) && creature?.IsDeadPet != true ) - { - healer.SendLocalizedMessage( 500955 ); // That being is not damaged! - } - else if ( !patient.Alive && (patient.Map == null || !patient.Map.CanFit( patient.Location, 16, false, false )) ) - { - healer.SendLocalizedMessage( 501042 ); // Target cannot be resurrected at that location. - } - else if ( healer.CanBeBeneficial( patient, true, true ) ) - { - healer.DoBeneficial( patient ); - - bool onSelf = ( healer == patient ); - int dex = healer.Dex; - - double seconds; - double resDelay = ( patient.Alive ? 0.0 : 5.0 ); - - if ( onSelf ) - { - if ( Core.AOS ) - seconds = 5.0 + (0.5 * ((double)(120 - dex) / 10)); // TODO: Verify algorithm - else - seconds = 9.4 + (0.6 * ((double)(120 - dex) / 10)); - } - else - { - if ( Core.AOS && GetPrimarySkill( patient ) == SkillName.Veterinary ) - { - seconds = 2.0; - } - else if ( Core.AOS ) - { - if (dex < 204) - { - seconds = 3.2-(Math.Sin((double)dex/130)*2.5) + resDelay; - } - else - { - seconds = 0.7 + resDelay; - } - } - else - { - if ( dex >= 100 ) - seconds = 3.0 + resDelay; - else if ( dex >= 40 ) - seconds = 4.0 + resDelay; - else - seconds = 5.0 + resDelay; - } - } - - BandageContext context = GetContext( healer ); - - context?.StopHeal(); - seconds *= 1000; - - context = new BandageContext( healer, patient, TimeSpan.FromMilliseconds( seconds ) ); - - m_Table[healer] = context; - - if ( !onSelf ) - patient.SendLocalizedMessage( 1008078, false, healer.Name ); // : Attempting to heal you. - - healer.SendLocalizedMessage( 500956 ); // You begin applying the bandages. - return context; - } - - return null; - } - } -} + public class Bandage : Item, IDyable + { + public static int Range = Core.AOS ? 2 : 1; + + [Constructible] + public Bandage() : this(1) + { + } + + [Constructible] + public Bandage(int amount) : base(0xE21) + { + Stackable = true; + Amount = amount; + } + + public Bandage(Serial serial) : base(serial) + { + } + + public override double DefaultWeight => 0.1; + + public virtual bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; + + Hue = sender.DyedHue; + + return true; + } + + public static void Initialize() + { + EventSink.BandageTargetRequest += EventSink_BandageTargetRequest; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), Range)) + { + from.RevealingAction(); + + from.SendLocalizedMessage(500948); // Who will you use the bandages on? + + from.Target = new InternalTarget(this); + } + else + { + from.SendLocalizedMessage(500295); // You are too far away to do that. + } + } + + private static void EventSink_BandageTargetRequest(BandageTargetRequestEventArgs e) + { + if (!(e.Bandage is Bandage b) || b.Deleted) + return; + + Mobile from = e.Mobile; + + if (from.InRange(b.GetWorldLocation(), Range)) + { + Target t = from.Target; + + if (t != null) + { + Target.Cancel(from); + from.Target = null; + } + + from.RevealingAction(); + + from.SendLocalizedMessage(500948); // Who will you use the bandages on? + + new InternalTarget(b).Invoke(from, e.Target); + } + else + { + from.SendLocalizedMessage(500295); // You are too far away to do that. + } + } + + private class InternalTarget : Target + { + private Bandage m_Bandage; + + public InternalTarget(Bandage bandage) : base(Bandage.Range, false, TargetFlags.Beneficial) + { + m_Bandage = bandage; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Bandage.Deleted) + return; + + if (targeted is Mobile mobile) + { + if (from.InRange(m_Bandage.GetWorldLocation(), Bandage.Range)) + { + if (BandageContext.BeginHeal(from, mobile) != null) + if (!DuelContext.IsFreeConsume(from)) + m_Bandage.Consume(); + } + else + { + from.SendLocalizedMessage(500295); // You are too far away to do that. + } + } + else if (targeted is PlagueBeastInnard innard) + { + if (innard.OnBandage(from)) + m_Bandage.Consume(); + } + else + { + from.SendLocalizedMessage(500970); // Bandages can not be used on that. + } + } + + protected override void OnNonlocalTarget(Mobile from, object targeted) + { + if (targeted is PlagueBeastInnard innard) + { + if (innard.OnBandage(from)) + m_Bandage.Consume(); + } + else + { + base.OnNonlocalTarget(from, targeted); + } + } + } + } + + public class BandageContext + { + private static Dictionary m_Table = new Dictionary(); + + public BandageContext(Mobile healer, Mobile patient, TimeSpan delay) + { + Healer = healer; + Patient = patient; + + Timer = new InternalTimer(this, delay); + Timer.Start(); + } + + public Mobile Healer{ get; } + + public Mobile Patient{ get; } + + public int Slips{ get; set; } + + public Timer Timer{ get; private set; } + + public void Slip() + { + Healer.SendLocalizedMessage(500961); // Your fingers slip! + ++Slips; + } + + public void StopHeal() + { + m_Table.Remove(Healer); + + Timer?.Stop(); + + Timer = null; + } + + public static BandageContext GetContext(Mobile healer) + { + m_Table.TryGetValue(healer, out BandageContext bc); + return bc; + } + + public static SkillName GetPrimarySkill(Mobile m) + { + if (!m.Player && (m.Body.IsMonster || m.Body.IsAnimal)) + return SkillName.Veterinary; + return SkillName.Healing; + } + + public static SkillName GetSecondarySkill(Mobile m) + { + if (!m.Player && (m.Body.IsMonster || m.Body.IsAnimal)) + return SkillName.AnimalLore; + return SkillName.Anatomy; + } + + public void EndHeal() + { + StopHeal(); + + int healerNumber = -1, patientNumber = -1; + bool playSound = true; + bool checkSkills = false; + + SkillName primarySkill = GetPrimarySkill(Patient); + SkillName secondarySkill = GetSecondarySkill(Patient); + + BaseCreature petPatient = Patient as BaseCreature; + + if (!Healer.Alive) + { + healerNumber = 500962; // You were unable to finish your work before you died. + patientNumber = -1; + playSound = false; + } + else if (!Healer.InRange(Patient, Bandage.Range)) + { + healerNumber = 500963; // You did not stay close enough to heal your target. + patientNumber = -1; + playSound = false; + } + else if (!Patient.Alive || petPatient != null && petPatient.IsDeadPet) + { + double healing = Healer.Skills[primarySkill].Value; + double anatomy = Healer.Skills[secondarySkill].Value; + double chance = (healing - 68.0) / 50.0 - Slips * 0.02; + + if ((checkSkills = healing >= 80.0 && anatomy >= 80.0) && chance > Utility.RandomDouble() + || Core.SE && petPatient is FactionWarHorse && petPatient.ControlMaster == Healer + ) //TODO: Dbl check doesn't check for faction of the horse here? + { + if (Patient.Map == null || !Patient.Map.CanFit(Patient.Location, 16, false, false)) + { + healerNumber = 501042; // Target can not be resurrected at that location. + patientNumber = 502391; // Thou can not be resurrected there! + } + else if (Patient.Region != null && Patient.Region.IsPartOf("Khaldun")) + { + healerNumber = + 1010395; // The veil of death in this area is too strong and resists thy efforts to restore life. + patientNumber = -1; + } + else + { + healerNumber = 500965; // You are able to resurrect your patient. + patientNumber = -1; + + Patient.PlaySound(0x214); + Patient.FixedEffect(0x376A, 10, 16); + + if (petPatient != null && petPatient.IsDeadPet) + { + Mobile master = petPatient.ControlMaster; + + if (master != null && Healer == master) + { + petPatient.ResurrectPet(); + + for (int i = 0; i < petPatient.Skills.Length; ++i) petPatient.Skills[i].Base -= 0.1; + } + else if (master != null && master.InRange(petPatient, 3)) + { + healerNumber = 503255; // You are able to resurrect the creature. + + master.CloseGump(typeof(PetResurrectGump)); + master.SendGump(new PetResurrectGump(Healer, petPatient)); + } + else + { + bool found = false; + + List friends = petPatient.Friends; + + for (int i = 0; friends != null && i < friends.Count; ++i) + { + Mobile friend = friends[i]; + + if (friend.InRange(petPatient, 3)) + { + healerNumber = 503255; // You are able to resurrect the creature. + + friend.CloseGump(typeof(PetResurrectGump)); + friend.SendGump(new PetResurrectGump(Healer, petPatient)); + + found = true; + break; + } + } + + if (!found) + healerNumber = 1049670; // The pet's owner must be nearby to attempt resurrection. + } + } + else + { + Patient.CloseGump(typeof(ResurrectGump)); + Patient.SendGump(new ResurrectGump(Patient, Healer)); + } + } + } + else + { + if (petPatient != null && petPatient.IsDeadPet) + healerNumber = 503256; // You fail to resurrect the creature. + else + healerNumber = 500966; // You are unable to resurrect your patient. + + patientNumber = -1; + } + } + else if (Patient.Poisoned) + { + Healer.SendLocalizedMessage(500969); // You finish applying the bandages. + + double healing = Healer.Skills[primarySkill].Value; + double anatomy = Healer.Skills[secondarySkill].Value; + double chance = (healing - 30.0) / 50.0 - Patient.Poison.Level * 0.1 - Slips * 0.02; + + if ((checkSkills = healing >= 60.0 && anatomy >= 60.0) && chance > Utility.RandomDouble()) + { + if (Patient.CurePoison(Healer)) + { + healerNumber = Healer == Patient ? -1 : 1010058; // You have cured the target of all poisons. + patientNumber = 1010059; // You have been cured of all poisons. + } + else + { + healerNumber = -1; + patientNumber = -1; + } + } + else + { + healerNumber = 1010060; // You have failed to cure your target! + patientNumber = -1; + } + } + else if (BleedAttack.IsBleeding(Patient)) + { + healerNumber = 1060088; // You bind the wound and stop the bleeding + patientNumber = 1060167; // The bleeding wounds have healed, you are no longer bleeding! + + BleedAttack.EndBleed(Patient, false); + } + else if (MortalStrike.IsWounded(Patient)) + { + healerNumber = Healer == Patient ? 1005000 : 1010398; + patientNumber = -1; + playSound = false; + } + else if (Patient.Hits == Patient.HitsMax) + { + healerNumber = 500967; // You heal what little damage your patient had. + patientNumber = -1; + } + else + { + checkSkills = true; + patientNumber = -1; + + double healing = Healer.Skills[primarySkill].Value; + double anatomy = Healer.Skills[secondarySkill].Value; + double chance = (healing + 10.0) / 100.0 - Slips * 0.02; + + if (chance > Utility.RandomDouble()) + { + healerNumber = 500969; // You finish applying the bandages. + + double min, max; + + if (Core.AOS) + { + min = anatomy / 8.0 + healing / 5.0 + 4.0; + max = anatomy / 6.0 + healing / 2.5 + 4.0; + } + else + { + min = anatomy / 5.0 + healing / 5.0 + 3.0; + max = anatomy / 5.0 + healing / 2.0 + 10.0; + } + + double toHeal = min + Utility.RandomDouble() * (max - min); + + if (Patient.Body.IsMonster || Patient.Body.IsAnimal) + toHeal += Patient.HitsMax / 100; + + if (Core.AOS) + toHeal -= toHeal * Slips * 0.35; // TODO: Verify algorithm + else + toHeal -= Slips * 4; + + if (toHeal < 1) + { + toHeal = 1; + healerNumber = 500968; // You apply the bandages, but they barely help. + } + + Patient.Heal((int)toHeal, Healer, false); + } + else + { + healerNumber = 500968; // You apply the bandages, but they barely help. + playSound = false; + } + } + + if (healerNumber != -1) + Healer.SendLocalizedMessage(healerNumber); + + if (patientNumber != -1) + Patient.SendLocalizedMessage(patientNumber); + + if (playSound) + Patient.PlaySound(0x57); + + if (checkSkills) + { + Healer.CheckSkill(secondarySkill, 0.0, 120.0); + Healer.CheckSkill(primarySkill, 0.0, 120.0); + } + } + + public static BandageContext BeginHeal(Mobile healer, Mobile patient) + { + BaseCreature creature = patient as BaseCreature; + + if (patient is Golem) + { + healer.SendLocalizedMessage(500970); // Bandages cannot be used on that. + } + else if (creature?.IsAnimatedDead == true) + { + healer.SendLocalizedMessage(500951); // You cannot heal that. + } + else if (!patient.Poisoned && patient.Hits == patient.HitsMax && !BleedAttack.IsBleeding(patient) && + creature?.IsDeadPet != true) + { + healer.SendLocalizedMessage(500955); // That being is not damaged! + } + else if (!patient.Alive && (patient.Map == null || !patient.Map.CanFit(patient.Location, 16, false, false))) + { + healer.SendLocalizedMessage(501042); // Target cannot be resurrected at that location. + } + else if (healer.CanBeBeneficial(patient, true, true)) + { + healer.DoBeneficial(patient); + + bool onSelf = healer == patient; + int dex = healer.Dex; + + double seconds; + double resDelay = patient.Alive ? 0.0 : 5.0; + + if (onSelf) + { + if (Core.AOS) + seconds = 5.0 + 0.5 * ((double)(120 - dex) / 10); // TODO: Verify algorithm + else + seconds = 9.4 + 0.6 * ((double)(120 - dex) / 10); + } + else + { + if (Core.AOS && GetPrimarySkill(patient) == SkillName.Veterinary) + { + seconds = 2.0; + } + else if (Core.AOS) + { + if (dex < 204) + seconds = 3.2 - Math.Sin((double)dex / 130) * 2.5 + resDelay; + else + seconds = 0.7 + resDelay; + } + else + { + if (dex >= 100) + seconds = 3.0 + resDelay; + else if (dex >= 40) + seconds = 4.0 + resDelay; + else + seconds = 5.0 + resDelay; + } + } + + BandageContext context = GetContext(healer); + + context?.StopHeal(); + seconds *= 1000; + + context = new BandageContext(healer, patient, TimeSpan.FromMilliseconds(seconds)); + + m_Table[healer] = context; + + if (!onSelf) + patient.SendLocalizedMessage(1008078, false, healer.Name); // : Attempting to heal you. + + healer.SendLocalizedMessage(500956); // You begin applying the bandages. + return context; + } + + return null; + } + + private class InternalTimer : Timer + { + private BandageContext m_Context; + + public InternalTimer(BandageContext context, TimeSpan delay) : base(delay) + { + m_Context = context; + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + m_Context.EndHeal(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Misc/FireHorn.cs b/Scripts/Items/Skill Items/Misc/FireHorn.cs index cd1302d59..15e4f167d 100644 --- a/Scripts/Items/Skill Items/Misc/FireHorn.cs +++ b/Scripts/Items/Skill Items/Misc/FireHorn.cs @@ -1,224 +1,225 @@ using System; using System.Collections.Generic; using Server.Network; -using Server.Targeting; using Server.Spells; +using Server.Targeting; namespace Server.Items { - public class FireHorn : Item - { - public override int LabelNumber => 1060456; // fire horn + public class FireHorn : Item + { + [Constructible] + public FireHorn() : base(0xFC7) + { + Hue = 0x466; + Weight = 1.0; + } - [Constructible] - public FireHorn() : base( 0xFC7 ) - { - Hue = 0x466; - Weight = 1.0; - } + public FireHorn(Serial serial) : base(serial) + { + } - public FireHorn( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1060456; // fire horn - private bool CheckUse( Mobile from ) - { - if ( !IsAccessibleTo( from ) ) - return false; + private bool CheckUse(Mobile from) + { + if (!IsAccessibleTo(from)) + return false; - if ( from.Map != Map || !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return false; - } + if (from.Map != Map || !from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return false; + } - if ( !from.CanBeginAction( typeof( FireHorn ) ) ) - { - from.SendLocalizedMessage( 1049615 ); // You must take a moment to catch your breath. - return false; - } + if (!from.CanBeginAction(typeof(FireHorn))) + { + from.SendLocalizedMessage(1049615); // You must take a moment to catch your breath. + return false; + } - int sulfAsh = Core.AOS ? 4 : 15; - if ( from.Backpack == null || from.Backpack.GetAmount( typeof( SulfurousAsh ) ) < sulfAsh ) - { - from.SendLocalizedMessage( 1049617 ); // You do not have enough sulfurous ash. - return false; - } + int sulfAsh = Core.AOS ? 4 : 15; + if (from.Backpack == null || from.Backpack.GetAmount(typeof(SulfurousAsh)) < sulfAsh) + { + from.SendLocalizedMessage(1049617); // You do not have enough sulfurous ash. + return false; + } - return true; - } + return true; + } - public override void OnDoubleClick( Mobile from ) - { - if ( CheckUse( from ) ) - { - from.SendLocalizedMessage( 1049620 ); // Select an area to incinerate. - from.Target = new InternalTarget( this ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (CheckUse(from)) + { + from.SendLocalizedMessage(1049620); // Select an area to incinerate. + from.Target = new InternalTarget(this); + } + } - public void Use( Mobile from, IPoint3D loc ) - { - if ( !CheckUse( from ) ) - return; + public void Use(Mobile from, IPoint3D loc) + { + if (!CheckUse(from)) + return; - from.BeginAction( typeof( FireHorn ) ); - Timer.DelayCall( Core.AOS ? TimeSpan.FromSeconds( 6.0 ) : TimeSpan.FromSeconds( 12.0 ), new TimerStateCallback( EndAction ), from ); + from.BeginAction(typeof(FireHorn)); + Timer.DelayCall(Core.AOS ? TimeSpan.FromSeconds(6.0) : TimeSpan.FromSeconds(12.0), + new TimerStateCallback(EndAction), from); - int music = from.Skills[SkillName.Musicianship].Fixed; + int music = from.Skills[SkillName.Musicianship].Fixed; - int sucChance = 500 + ( music - 775 ) * 2; - double dSucChance = ((double)sucChance) / 1000.0; + int sucChance = 500 + (music - 775) * 2; + double dSucChance = sucChance / 1000.0; - if ( !from.CheckSkill( SkillName.Musicianship, dSucChance ) ) - { - from.SendLocalizedMessage( 1049618 ); // The horn emits a pathetic squeak. - from.PlaySound( 0x18A ); - return; - } + if (!from.CheckSkill(SkillName.Musicianship, dSucChance)) + { + from.SendLocalizedMessage(1049618); // The horn emits a pathetic squeak. + from.PlaySound(0x18A); + return; + } - int sulfAsh = Core.AOS ? 4 : 15; - from.Backpack.ConsumeUpTo( typeof( SulfurousAsh ), sulfAsh ); + int sulfAsh = Core.AOS ? 4 : 15; + from.Backpack.ConsumeUpTo(typeof(SulfurousAsh), sulfAsh); - from.PlaySound( 0x15F ); - Effects.SendPacket( from, from.Map, new HuedEffect( EffectType.Moving, from.Serial, Serial.Zero, 0x36D4, from.Location, loc, 5, 0, false, true, 0, 0 ) ); + from.PlaySound(0x15F); + Effects.SendPacket(from, from.Map, + new HuedEffect(EffectType.Moving, from.Serial, Serial.Zero, 0x36D4, from.Location, loc, 5, 0, false, true, 0, + 0)); - List targets = new List(); - bool playerVsPlayer = false; + List targets = new List(); + bool playerVsPlayer = false; - IPooledEnumerable eable = from.Map.GetMobilesInRange( new Point3D( loc ), 2 ); + IPooledEnumerable eable = from.Map.GetMobilesInRange(new Point3D(loc), 2); - foreach ( Mobile m in eable ) - { - if ( from != m && SpellHelper.ValidIndirectTarget( from, m ) && from.CanBeHarmful( m, false ) ) - { - if ( Core.AOS && !from.InLOS( m ) ) - continue; + foreach (Mobile m in eable) + if (from != m && SpellHelper.ValidIndirectTarget(from, m) && from.CanBeHarmful(m, false)) + { + if (Core.AOS && !from.InLOS(m)) + continue; - targets.Add( m ); + targets.Add(m); - if ( m.Player ) - playerVsPlayer = true; - } - } + if (m.Player) + playerVsPlayer = true; + } - eable.Free(); + eable.Free(); - if ( targets.Count > 0 ) - { - int prov = from.Skills[SkillName.Provocation].Fixed; - int disc = from.Skills[SkillName.Discordance].Fixed; - int peace = from.Skills[SkillName.Peacemaking].Fixed; + if (targets.Count > 0) + { + int prov = from.Skills[SkillName.Provocation].Fixed; + int disc = from.Skills[SkillName.Discordance].Fixed; + int peace = from.Skills[SkillName.Peacemaking].Fixed; - int minDamage, maxDamage; + int minDamage, maxDamage; - if ( Core.AOS ) - { - int musicScaled = music + Math.Max( 0, music - 900 ) * 2; - int provScaled = prov + Math.Max( 0, prov - 900 ) * 2; - int discScaled = disc + Math.Max( 0, disc - 900 ) * 2; - int peaceScaled = peace + Math.Max( 0, peace - 900 ) * 2; + if (Core.AOS) + { + int musicScaled = music + Math.Max(0, music - 900) * 2; + int provScaled = prov + Math.Max(0, prov - 900) * 2; + int discScaled = disc + Math.Max(0, disc - 900) * 2; + int peaceScaled = peace + Math.Max(0, peace - 900) * 2; - int weightAvg = ( musicScaled + provScaled * 3 + discScaled * 3 + peaceScaled ) / 80; + int weightAvg = (musicScaled + provScaled * 3 + discScaled * 3 + peaceScaled) / 80; - int avgDamage; - if ( playerVsPlayer ) - avgDamage = weightAvg / 3; - else - avgDamage = weightAvg / 2; + int avgDamage; + if (playerVsPlayer) + avgDamage = weightAvg / 3; + else + avgDamage = weightAvg / 2; - minDamage = ( avgDamage * 9 ) / 10; - maxDamage = ( avgDamage * 10 ) / 9; - } - else - { - int total = prov + disc / 5 + peace / 5; + minDamage = avgDamage * 9 / 10; + maxDamage = avgDamage * 10 / 9; + } + else + { + int total = prov + disc / 5 + peace / 5; - if ( playerVsPlayer ) - total /= 3; + if (playerVsPlayer) + total /= 3; - maxDamage = ( total * 2 ) / 30; - minDamage = ( maxDamage * 7 ) / 10; - } + maxDamage = total * 2 / 30; + minDamage = maxDamage * 7 / 10; + } - double damage = Utility.RandomMinMax( minDamage, maxDamage ); + double damage = Utility.RandomMinMax(minDamage, maxDamage); - if ( Core.AOS && targets.Count > 1 ) - damage = (damage * 2) / targets.Count; - else if ( !Core.AOS ) - damage /= targets.Count; + if (Core.AOS && targets.Count > 1) + damage = damage * 2 / targets.Count; + else if (!Core.AOS) + damage /= targets.Count; - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = (Mobile)targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - double toDeal = damage; + double toDeal = damage; - if ( !Core.AOS && m.CheckSkill( SkillName.MagicResist, 0.0, 120.0 ) ) - { - toDeal *= 0.5; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + if (!Core.AOS && m.CheckSkill(SkillName.MagicResist, 0.0, 120.0)) + { + toDeal *= 0.5; + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - from.DoHarmful( m ); - SpellHelper.Damage( TimeSpan.Zero, m, from, toDeal, 0, 100, 0, 0, 0 ); + from.DoHarmful(m); + SpellHelper.Damage(TimeSpan.Zero, m, from, toDeal, 0, 100, 0, 0, 0); - Effects.SendTargetEffect( m, 0x3709, 10, 30 ); - } - } + Effects.SendTargetEffect(m, 0x3709, 10, 30); + } + } - double breakChance = Core.AOS ? 0.01 : 0.16; - if ( Utility.RandomDouble() < breakChance ) - { - from.SendLocalizedMessage( 1049619 ); // The fire horn crumbles in your hands. - Delete(); - } - } + double breakChance = Core.AOS ? 0.01 : 0.16; + if (Utility.RandomDouble() < breakChance) + { + from.SendLocalizedMessage(1049619); // The fire horn crumbles in your hands. + Delete(); + } + } - private static void EndAction( object state ) - { - Mobile m = (Mobile) state; + private static void EndAction(object state) + { + Mobile m = (Mobile)state; - m.EndAction( typeof( FireHorn ) ); - m.SendLocalizedMessage( 1049621 ); // You catch your breath. - } + m.EndAction(typeof(FireHorn)); + m.SendLocalizedMessage(1049621); // You catch your breath. + } - private class InternalTarget : Target - { - private FireHorn m_Horn; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public InternalTarget( FireHorn horn ) : base( Core.AOS ? 3 : 2, true, TargetFlags.Harmful ) - { - m_Horn = horn; - } + writer.WriteEncodedInt(0); // version + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Horn.Deleted ) - return; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - IPoint3D loc; - if ( targeted is Item item ) - loc = item.GetWorldLocation(); - else - loc = targeted as IPoint3D; + int version = reader.ReadEncodedInt(); + } - m_Horn.Use( from, loc ); - } - } + private class InternalTarget : Target + { + private FireHorn m_Horn; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public InternalTarget(FireHorn horn) : base(Core.AOS ? 3 : 2, true, TargetFlags.Harmful) + { + m_Horn = horn; + } - writer.WriteEncodedInt( 0 ); // version - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Horn.Deleted) + return; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + IPoint3D loc; + if (targeted is Item item) + loc = item.GetWorldLocation(); + else + loc = targeted as IPoint3D; - int version = reader.ReadEncodedInt(); - } - } -} + m_Horn.Use(from, loc); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Misc/RecipeScroll.cs b/Scripts/Items/Skill Items/Misc/RecipeScroll.cs index 395df92ac..74144799f 100644 --- a/Scripts/Items/Skill Items/Misc/RecipeScroll.cs +++ b/Scripts/Items/Skill Items/Misc/RecipeScroll.cs @@ -4,117 +4,121 @@ using Server.Network; namespace Server.Items { - public class RecipeScroll : Item - { - public override int LabelNumber => 1074560; // recipe scroll + public class RecipeScroll : Item + { + private int m_RecipeID; - private int m_RecipeID; + public RecipeScroll(Recipe r) + : this(r.ID) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int RecipeID - { - get => m_RecipeID; - set { m_RecipeID = value; InvalidateProperties(); } - } + [Constructible] + public RecipeScroll(int recipeID) + : base(0x2831) + { + m_RecipeID = recipeID; + } - public Recipe Recipe - { - get - { - if ( Recipe.Recipes.ContainsKey( m_RecipeID ) ) - return Recipe.Recipes[m_RecipeID]; + public RecipeScroll(Serial serial) + : base(serial) + { + } - return null; - } - } + public override int LabelNumber => 1074560; // recipe scroll - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public int RecipeID + { + get => m_RecipeID; + set + { + m_RecipeID = value; + InvalidateProperties(); + } + } - Recipe r = Recipe; + public Recipe Recipe + { + get + { + if (Recipe.Recipes.ContainsKey(m_RecipeID)) + return Recipe.Recipes[m_RecipeID]; - if ( r != null ) - list.Add( 1049644, r.TextDefinition.ToString() ); // [~1_stuff~] - } + return null; + } + } - public RecipeScroll( Recipe r ) - : this( r.ID ) - { - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - [Constructible] - public RecipeScroll( int recipeID ) - : base( 0x2831 ) - { - m_RecipeID = recipeID; - } + Recipe r = Recipe; - public RecipeScroll( Serial serial ) - : base( serial ) - { - } + if (r != null) + list.Add(1049644, r.TextDefinition.ToString()); // [~1_stuff~] + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } - Recipe r = Recipe; + Recipe r = Recipe; - if ( r != null && from is PlayerMobile pm ) - { - if ( !pm.HasRecipe( r ) ) - { - bool allRequiredSkills = true; - double chance = r.CraftItem.GetSuccessChance( pm, null, r.CraftSystem, false, ref allRequiredSkills ); + if (r != null && from is PlayerMobile pm) + { + if (!pm.HasRecipe(r)) + { + bool allRequiredSkills = true; + double chance = r.CraftItem.GetSuccessChance(pm, null, r.CraftSystem, false, ref allRequiredSkills); - if ( allRequiredSkills && chance >= 0.0 ) - { - pm.SendLocalizedMessage( 1073451, r.TextDefinition.ToString() ); // You have learned a new recipe: ~1_RECIPE~ - pm.AcquireRecipe( r ); - Delete(); - } - else - { - pm.SendLocalizedMessage( 1044153 ); // You don't have the required skills to attempt this item. - } - } - else - { - pm.SendLocalizedMessage( 1073427 ); // You already know this recipe. - } + if (allRequiredSkills && chance >= 0.0) + { + pm.SendLocalizedMessage(1073451, + r.TextDefinition.ToString()); // You have learned a new recipe: ~1_RECIPE~ + pm.AcquireRecipe(r); + Delete(); + } + else + { + pm.SendLocalizedMessage(1044153); // You don't have the required skills to attempt this item. + } + } + else + { + pm.SendLocalizedMessage(1073427); // You already know this recipe. + } + } + } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version - writer.Write( (int)0 ); // version + writer.Write(m_RecipeID); + } - writer.Write( (int)m_RecipeID ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); + switch (version) + { + case 0: + { + m_RecipeID = reader.ReadInt(); - switch( version ) - { - case 0: - { - m_RecipeID = reader.ReadInt(); - - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Misc/RepairDeed.cs b/Scripts/Items/Skill Items/Misc/RepairDeed.cs index af7fa247f..b864d33a3 100644 --- a/Scripts/Items/Skill Items/Misc/RepairDeed.cs +++ b/Scripts/Items/Skill Items/Misc/RepairDeed.cs @@ -1,242 +1,257 @@ using System; using Server.Engines.Craft; +using Server.Factions; using Server.Mobiles; using Server.Regions; namespace Server.Items { - public class RepairDeed : Item - { - private class RepairSkillInfo - { - public TextDefinition NotNearbyMessage { get; } + public class RepairDeed : Item + { + public enum RepairSkillType + { + Smithing, + Tailoring, + Tinkering, + Carpentry, + Fletching + } - public TextDefinition Name { get; } + private Mobile m_Crafter; + + private RepairSkillType m_Skill; + private double m_SkillLevel; + + [Constructible] + public RepairDeed() : this(RepairSkillType.Smithing, 100.0, null, true) + { + } + + [Constructible] + public RepairDeed(RepairSkillType skill, double level) : this(skill, level, null, true) + { + } + + [Constructible] + public RepairDeed(RepairSkillType skill, double level, bool normalizeLevel) : this(skill, level, null, + normalizeLevel) + { + } + + public RepairDeed(RepairSkillType skill, double level, Mobile crafter) : this(skill, level, crafter, true) + { + } + + public RepairDeed(RepairSkillType skill, double level, Mobile crafter, bool normalizeLevel) : base(0x14F0) + { + if (normalizeLevel) + SkillLevel = (int)(level / 10) * 10; + else + SkillLevel = level; + + m_Skill = skill; + m_Crafter = crafter; + Hue = 0x1BC; + LootType = LootType.Blessed; + } + + public RepairDeed(Serial serial) : base(serial) + { + } + + public override bool DisplayLootType => false; + + [CommandProperty(AccessLevel.GameMaster)] + public RepairSkillType RepairSkill + { + get => m_Skill; + set + { + m_Skill = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public double SkillLevel + { + get => m_SkillLevel; + set + { + m_SkillLevel = Math.Max(Math.Min(value, 120.0), 0); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1061133, + $"{GetSkillTitle(m_SkillLevel)}\t{RepairSkillInfo.GetInfo(m_Skill).Name}"); // A repair service contract from ~1_SKILL_TITLE~ ~2_SKILL_NAME~. + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ + + //On OSI it says it's exceptional. Intentional difference. + } + + public override void OnSingleClick(Mobile from) + { + if (Deleted || !from.CanSee(this)) + return; + + LabelTo(from, 1061133, + $"{GetSkillTitle(m_SkillLevel)}\t{RepairSkillInfo.GetInfo(m_Skill).Name}"); // A repair service contract from ~1_SKILL_TITLE~ ~2_SKILL_NAME~. + + if (m_Crafter != null) + LabelTo(from, 1050043, m_Crafter.Name); // crafted by ~1_NAME~ + } + + private static TextDefinition GetSkillTitle(double skillLevel) + { + int skill = (int)(skillLevel / 10); + + if (skill >= 11) + return 1062008 + skill - 11; + if (skill >= 5) + return 1061123 + skill - 5; + + switch (skill) + { + case 4: + return "a Novice"; + case 3: + return "a Neophyte"; + default: + return "a Newbie"; //On OSI, it shouldn't go below 50, but, this is for 'custom' support. + } + } + + public static RepairSkillType GetTypeFor(CraftSystem s) + { + for (int i = 0; i < RepairSkillInfo.Table.Length; i++) + if (RepairSkillInfo.Table[i].System == s) + return (RepairSkillType)i; + + return RepairSkillType.Smithing; + } + + public override void OnDoubleClick(Mobile from) + { + if (Check(from)) + Repair.Do(from, RepairSkillInfo.GetInfo(m_Skill).System, this); + } + + public bool Check(Mobile from) + { + if (!IsChildOf(from.Backpack)) + from.SendLocalizedMessage(1047012); // The contract must be in your backpack to use it. + else if (!VerifyRegion(from)) + TextDefinition.SendMessageTo(from, RepairSkillInfo.GetInfo(m_Skill).NotNearbyMessage); + else + return true; + + return false; + } + + public bool VerifyRegion(Mobile m) + { + //TODO: When the entire region system data is in, convert to that instead of a proximity thing. + + if (!m.Region.IsPartOf(typeof(TownRegion))) + return false; + + return Faction.IsNearType(m, RepairSkillInfo.GetInfo(m_Skill).NearbyTypes, 6); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write((int)m_Skill); + writer.Write(m_SkillLevel); + writer.Write(m_Crafter); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Skill = (RepairSkillType)reader.ReadInt(); + m_SkillLevel = reader.ReadDouble(); + m_Crafter = reader.ReadMobile(); + + break; + } + } + } + + private class RepairSkillInfo + { + public RepairSkillInfo(CraftSystem system, Type[] nearbyTypes, TextDefinition notNearbyMessage, + TextDefinition name) + { + System = system; + NearbyTypes = nearbyTypes; + NotNearbyMessage = notNearbyMessage; + Name = name; + } + + public RepairSkillInfo(CraftSystem system, Type nearbyType, TextDefinition notNearbyMessage, TextDefinition name) + : this(system, new[] { nearbyType }, notNearbyMessage, name) + { + } + + public TextDefinition NotNearbyMessage{ get; } + + public TextDefinition Name{ get; } - public CraftSystem System { get; } + public CraftSystem System{ get; } - public Type[] NearbyTypes { get; } + public Type[] NearbyTypes{ get; } - public RepairSkillInfo( CraftSystem system, Type[] nearbyTypes, TextDefinition notNearbyMessage, TextDefinition name ) - { - System = system; - NearbyTypes = nearbyTypes; - NotNearbyMessage = notNearbyMessage; - Name = name; - } + public static RepairSkillInfo[] Table{ get; } = + { + new RepairSkillInfo(DefBlacksmithy.CraftSystem, typeof(Blacksmith), 1047013, 1023015), + new RepairSkillInfo(DefTailoring.CraftSystem, typeof(Tailor), 1061132, 1022981), + new RepairSkillInfo(DefTinkering.CraftSystem, typeof(Tinker), 1061166, 1022983), + new RepairSkillInfo(DefCarpentry.CraftSystem, typeof(Carpenter), 1061135, 1060774), + new RepairSkillInfo(DefBowFletching.CraftSystem, typeof(Bowyer), 1061134, 1023005) + }; - public RepairSkillInfo( CraftSystem system, Type nearbyType, TextDefinition notNearbyMessage, TextDefinition name ) - : this( system, new[] { nearbyType }, notNearbyMessage, name ) - { - } + public static RepairSkillInfo GetInfo(RepairSkillType type) + { + int v = (int)type; - public static RepairSkillInfo[] Table { get; } = - { - new RepairSkillInfo( DefBlacksmithy.CraftSystem, typeof( Blacksmith ), 1047013, 1023015 ), - new RepairSkillInfo( DefTailoring.CraftSystem, typeof( Tailor ), 1061132, 1022981 ), - new RepairSkillInfo( DefTinkering.CraftSystem, typeof( Tinker ), 1061166, 1022983 ), - new RepairSkillInfo( DefCarpentry.CraftSystem, typeof( Carpenter ), 1061135, 1060774 ), - new RepairSkillInfo( DefBowFletching.CraftSystem, typeof( Bowyer ), 1061134, 1023005 ) - }; + if (v < 0 || v >= Table.Length) + v = 0; - public static RepairSkillInfo GetInfo( RepairSkillType type ) - { - int v = (int)type; - - if ( v < 0 || v >= Table.Length ) - v = 0; - - return Table[v]; - } - } - public enum RepairSkillType - { - Smithing, - Tailoring, - Tinkering, - Carpentry, - Fletching - } - - public override bool DisplayLootType => false; - - private RepairSkillType m_Skill; - private double m_SkillLevel; - - private Mobile m_Crafter; - - [CommandProperty( AccessLevel.GameMaster )] - public RepairSkillType RepairSkill - { - get => m_Skill; - set { m_Skill = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public double SkillLevel - { - get => m_SkillLevel; - set { m_SkillLevel = Math.Max( Math.Min( value, 120.0 ), 0 ) ; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set { m_Crafter = value; InvalidateProperties(); } - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1061133, $"{GetSkillTitle(m_SkillLevel).ToString()}\t{RepairSkillInfo.GetInfo(m_Skill).Name}"); // A repair service contract from ~1_SKILL_TITLE~ ~2_SKILL_NAME~. - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ - - //On OSI it says it's exceptional. Intentional difference. - } - - public override void OnSingleClick( Mobile from ) - { - if ( Deleted || !from.CanSee( this ) ) - return; - - LabelTo( from, 1061133, - $"{GetSkillTitle(m_SkillLevel).ToString()}\t{RepairSkillInfo.GetInfo(m_Skill).Name}"); // A repair service contract from ~1_SKILL_TITLE~ ~2_SKILL_NAME~. - - if ( m_Crafter != null ) - LabelTo( from, 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ - } - - [Constructible] - public RepairDeed() : this( RepairSkillType.Smithing, 100.0, null, true ) - { - } - - [Constructible] - public RepairDeed( RepairSkillType skill, double level ) : this( skill, level, null, true ) - { - } - - [Constructible] - public RepairDeed( RepairSkillType skill, double level, bool normalizeLevel ) : this( skill, level, null, normalizeLevel ) - { - } - - public RepairDeed( RepairSkillType skill, double level, Mobile crafter ) : this( skill, level, crafter, true ) - { - } - - public RepairDeed( RepairSkillType skill, double level, Mobile crafter, bool normalizeLevel ) : base( 0x14F0 ) - { - if ( normalizeLevel ) - SkillLevel = (int)(level/10)*10; - else - SkillLevel = level; - - m_Skill = skill; - m_Crafter = crafter; - Hue = 0x1BC; - LootType = LootType.Blessed; - } - - public RepairDeed( Serial serial ) : base( serial ) - { - } - - private static TextDefinition GetSkillTitle( double skillLevel ) - { - int skill = (int)(skillLevel/10); - - if ( skill >= 11 ) - return (1062008 + skill-11); - if ( skill >=5 ) - return (1061123 + skill-5); - - switch( skill ) - { - case 4: - return "a Novice"; - case 3: - return "a Neophyte"; - default: - return "a Newbie"; //On OSI, it shouldn't go below 50, but, this is for 'custom' support. - } - } - - public static RepairSkillType GetTypeFor( CraftSystem s ) - { - for( int i = 0; i < RepairSkillInfo.Table.Length; i++ ) - { - if ( RepairSkillInfo.Table[i].System == s ) - return (RepairSkillType)i; - } - - return RepairSkillType.Smithing; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( Check( from ) ) - Repair.Do( from, RepairSkillInfo.GetInfo( m_Skill ).System, this ); - } - - public bool Check( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - from.SendLocalizedMessage( 1047012 ); // The contract must be in your backpack to use it. - else if ( !VerifyRegion( from ) ) - TextDefinition.SendMessageTo( from, RepairSkillInfo.GetInfo( m_Skill ).NotNearbyMessage ); - else - return true; - - return false; - } - - public bool VerifyRegion( Mobile m ) - { - //TODO: When the entire region system data is in, convert to that instead of a proximity thing. - - if ( !m.Region.IsPartOf( typeof( TownRegion ) ) ) - return false; - - return Factions.Faction.IsNearType( m, RepairSkillInfo.GetInfo( m_Skill ).NearbyTypes, 6 ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - - writer.Write( (int)m_Skill ); - writer.Write( m_SkillLevel ); - writer.Write( m_Crafter ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch( version ) - { - case 0: - { - m_Skill = (RepairSkillType)reader.ReadInt(); - m_SkillLevel = reader.ReadDouble(); - m_Crafter = reader.ReadMobile(); - - break; - } - } - } - } -} + return Table[v]; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/BambooFlute.cs b/Scripts/Items/Skill Items/Musical Instruments/BambooFlute.cs index dece1e5d5..4c12b615a 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/BambooFlute.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/BambooFlute.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class BambooFlute : BaseInstrument - { - [Constructible] - public BambooFlute() : base( 0x2805, 0x504, 0x503 ) - { - Weight = 2.0; - } + public class BambooFlute : BaseInstrument + { + [Constructible] + public BambooFlute() : base(0x2805, 0x504, 0x503) + { + Weight = 2.0; + } - public BambooFlute( Serial serial ) : base( serial ) - { - } + public BambooFlute(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 2.0; - } - } + if (Weight == 3.0) + Weight = 2.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/BaseInstrument.cs b/Scripts/Items/Skill Items/Musical Instruments/BaseInstrument.cs index b00968bfe..7d7c3a928 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/BaseInstrument.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/BaseInstrument.cs @@ -1,567 +1,600 @@ using System; using System.Collections; -using Server.Network; -using Server.Mobiles; -using Server.Targeting; using Server.Engines.Craft; +using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Items { - public delegate void InstrumentPickedCallback( Mobile from, BaseInstrument instrument ); - - public enum InstrumentQuality - { - Low, - Regular, - Exceptional - } - - public abstract class BaseInstrument : Item, ICraftable, ISlayer - { - private SlayerName m_Slayer, m_Slayer2; - private InstrumentQuality m_Quality; - private Mobile m_Crafter; - private int m_UsesRemaining; - - [CommandProperty( AccessLevel.GameMaster )] - public int SuccessSound { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int FailureSound { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public SlayerName Slayer - { - get => m_Slayer; - set{ m_Slayer = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public SlayerName Slayer2 - { - get => m_Slayer2; - set{ m_Slayer2 = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public InstrumentQuality Quality - { - get => m_Quality; - set{ UnscaleUses(); m_Quality = value; InvalidateProperties(); ScaleUses(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } - - public virtual int InitMinUses => 350; - public virtual int InitMaxUses => 450; - - public virtual TimeSpan ChargeReplenishRate => TimeSpan.FromMinutes( 5.0 ); - - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get{ CheckReplenishUses(); return m_UsesRemaining; } - set{ m_UsesRemaining = value; InvalidateProperties(); } - } - - private DateTime m_LastReplenished; - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastReplenished - { - get => m_LastReplenished; - set { m_LastReplenished = value; CheckReplenishUses(); } - } - - private bool m_ReplenishesCharges; - [CommandProperty( AccessLevel.GameMaster )] - public bool ReplenishesCharges - { - get => m_ReplenishesCharges; - set - { - if ( value != m_ReplenishesCharges && value ) - m_LastReplenished = DateTime.UtcNow; - - m_ReplenishesCharges = value; - } - } - - public void CheckReplenishUses() - { - CheckReplenishUses( true ); - } - - public void CheckReplenishUses( bool invalidate ) - { - if ( !m_ReplenishesCharges || m_UsesRemaining >= InitMaxUses ) - return; - - if ( m_LastReplenished + ChargeReplenishRate < DateTime.UtcNow ) - { - TimeSpan timeDifference = DateTime.UtcNow - m_LastReplenished; - - m_UsesRemaining = Math.Min( m_UsesRemaining + (int)( timeDifference.Ticks / ChargeReplenishRate.Ticks), InitMaxUses ); //How rude of TimeSpan to not allow timespan division. - m_LastReplenished = DateTime.UtcNow; - - if ( invalidate ) - InvalidateProperties(); - - } - } - - public void ScaleUses() - { - UsesRemaining = (UsesRemaining * GetUsesScalar()) / 100; - //InvalidateProperties(); - } - - public void UnscaleUses() - { - UsesRemaining = (UsesRemaining * 100) / GetUsesScalar(); - } - - public int GetUsesScalar() - { - if ( m_Quality == InstrumentQuality.Exceptional ) - return 200; - - return 100; - } - - public void ConsumeUse( Mobile from ) - { - // TODO: Confirm what must happen here? - - if ( UsesRemaining > 1 ) - { - --UsesRemaining; - } - else - { - from?.SendLocalizedMessage( 502079 ); // The instrument played its last tune. - - Delete(); - } - } - - private static Hashtable m_Instruments = new Hashtable(); - - public static BaseInstrument GetInstrument( Mobile from ) - { - if ( !(m_Instruments[from] is BaseInstrument item) ) - return null; - - if ( !item.IsChildOf( from.Backpack ) ) - { - m_Instruments.Remove( from ); - return null; - } - - return item; - } - - public static int GetBardRange( Mobile bard, SkillName skill ) - { - return 8 + (int)(bard.Skills[skill].Value / 15); - } - - public static void PickInstrument( Mobile from, InstrumentPickedCallback callback ) - { - BaseInstrument instrument = GetInstrument( from ); - - if ( instrument != null ) - { - callback?.Invoke( from, instrument ); - } - else - { - from.SendLocalizedMessage( 500617 ); // What instrument shall you play? - from.BeginTarget( 1, false, TargetFlags.None, new TargetStateCallback( OnPickedInstrument ), callback ); - } - } - - public static void OnPickedInstrument( Mobile from, object targeted, object state ) - { - if ( !(targeted is BaseInstrument instrument) ) - { - from.SendLocalizedMessage( 500619 ); // That is not a musical instrument. - } - else - { - SetInstrument( from, instrument ); - - InstrumentPickedCallback callback = state as InstrumentPickedCallback; - - callback?.Invoke( from, instrument ); - } - } - - public static bool IsMageryCreature( BaseCreature bc ) - { - return ( bc != null && bc.AI == AIType.AI_Mage && bc.Skills[SkillName.Magery].Base > 5.0 ); - } - - public static bool IsFireBreathingCreature( BaseCreature bc ) - { - if ( bc == null ) - return false; - - return bc.HasBreath; - } - - public static bool IsPoisonImmune( BaseCreature bc ) - { - return ( bc?.PoisonImmune != null ); - } - - public static int GetPoisonLevel( BaseCreature bc ) - { - Poison p = bc?.HitPoison; - - if ( p == null ) - return 0; - - return p.Level + 1; - } - - public static double GetBaseDifficulty( Mobile targ ) - { - /* Difficulty TODO: Add another 100 points for each of the following abilities: - - Radiation or Aura Damage (Heat, Cold etc.) - - Summoning Undead - */ - - double val = (targ.HitsMax * 1.6) + targ.StamMax + targ.ManaMax; - - val += targ.SkillsTotal / 10; - - if ( val > 700 ) - val = 700 + (int)((val - 700) * (3.0 / 11)); - - BaseCreature bc = targ as BaseCreature; - - if ( IsMageryCreature( bc ) ) - val += 100; - - if ( IsFireBreathingCreature( bc ) ) - val += 100; - - if ( IsPoisonImmune( bc ) ) - val += 100; - - if ( targ is VampireBat || targ is VampireBatFamiliar ) - val += 100; - - val += GetPoisonLevel( bc ) * 20; - - val /= 10; - - if ( bc != null && bc.IsParagon ) - val += 40.0; - - if ( Core.SE && val > 160.0 ) - val = 160.0; - - return val; - } - - public double GetDifficultyFor( Mobile targ ) - { - double val = GetBaseDifficulty( targ ); - - if ( m_Quality == InstrumentQuality.Exceptional ) - val -= 5.0; // 10% - - if ( m_Slayer != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer ); - - if ( entry != null ) - { - if ( entry.Slays( targ ) ) - val -= 10.0; // 20% - else if ( entry.Group.OppositionSuperSlays( targ ) ) - val += 10.0; // -20% - } - } - - if ( m_Slayer2 != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer2 ); - - if ( entry != null ) - { - if ( entry.Slays( targ ) ) - val -= 10.0; // 20% - else if ( entry.Group.OppositionSuperSlays( targ ) ) - val += 10.0; // -20% - } - } - - return val; - } - - public static void SetInstrument( Mobile from, BaseInstrument item ) - { - m_Instruments[from] = item; - } + public delegate void InstrumentPickedCallback(Mobile from, BaseInstrument instrument); + + public enum InstrumentQuality + { + Low, + Regular, + Exceptional + } + + public abstract class BaseInstrument : Item, ICraftable, ISlayer + { + private static Hashtable m_Instruments = new Hashtable(); + private Mobile m_Crafter; + + private DateTime m_LastReplenished; + private InstrumentQuality m_Quality; + + private bool m_ReplenishesCharges; + private SlayerName m_Slayer, m_Slayer2; + private int m_UsesRemaining; + + public BaseInstrument(int itemID, int wellSound, int badlySound) : base(itemID) + { + SuccessSound = wellSound; + FailureSound = badlySound; + UsesRemaining = Utility.RandomMinMax(InitMinUses, InitMaxUses); + } + + public BaseInstrument(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SuccessSound{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int FailureSound{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public InstrumentQuality Quality + { + get => m_Quality; + set + { + UnscaleUses(); + m_Quality = value; + InvalidateProperties(); + ScaleUses(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + public virtual int InitMinUses => 350; + public virtual int InitMaxUses => 450; + + public virtual TimeSpan ChargeReplenishRate => TimeSpan.FromMinutes(5.0); + + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get + { + CheckReplenishUses(); + return m_UsesRemaining; + } + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastReplenished + { + get => m_LastReplenished; + set + { + m_LastReplenished = value; + CheckReplenishUses(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool ReplenishesCharges + { + get => m_ReplenishesCharges; + set + { + if (value != m_ReplenishesCharges && value) + m_LastReplenished = DateTime.UtcNow; + + m_ReplenishesCharges = value; + } + } + + #region ICraftable Members + + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Quality = (InstrumentQuality)quality; + + if (makersMark) + Crafter = from; + + return quality; + } + + #endregion + + [CommandProperty(AccessLevel.GameMaster)] + public SlayerName Slayer + { + get => m_Slayer; + set + { + m_Slayer = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public SlayerName Slayer2 + { + get => m_Slayer2; + set + { + m_Slayer2 = value; + InvalidateProperties(); + } + } + + public void CheckReplenishUses() + { + CheckReplenishUses(true); + } + + public void CheckReplenishUses(bool invalidate) + { + if (!m_ReplenishesCharges || m_UsesRemaining >= InitMaxUses) + return; + + if (m_LastReplenished + ChargeReplenishRate < DateTime.UtcNow) + { + TimeSpan timeDifference = DateTime.UtcNow - m_LastReplenished; + + m_UsesRemaining = Math.Min(m_UsesRemaining + (int)(timeDifference.Ticks / ChargeReplenishRate.Ticks), + InitMaxUses); //How rude of TimeSpan to not allow timespan division. + m_LastReplenished = DateTime.UtcNow; + + if (invalidate) + InvalidateProperties(); + } + } + + public void ScaleUses() + { + UsesRemaining = UsesRemaining * GetUsesScalar() / 100; + //InvalidateProperties(); + } + + public void UnscaleUses() + { + UsesRemaining = UsesRemaining * 100 / GetUsesScalar(); + } + + public int GetUsesScalar() + { + if (m_Quality == InstrumentQuality.Exceptional) + return 200; + + return 100; + } + + public void ConsumeUse(Mobile from) + { + // TODO: Confirm what must happen here? + + if (UsesRemaining > 1) + { + --UsesRemaining; + } + else + { + from?.SendLocalizedMessage(502079); // The instrument played its last tune. + + Delete(); + } + } + + public static BaseInstrument GetInstrument(Mobile from) + { + if (!(m_Instruments[from] is BaseInstrument item)) + return null; + + if (!item.IsChildOf(from.Backpack)) + { + m_Instruments.Remove(from); + return null; + } + + return item; + } + + public static int GetBardRange(Mobile bard, SkillName skill) + { + return 8 + (int)(bard.Skills[skill].Value / 15); + } + + public static void PickInstrument(Mobile from, InstrumentPickedCallback callback) + { + BaseInstrument instrument = GetInstrument(from); + + if (instrument != null) + { + callback?.Invoke(from, instrument); + } + else + { + from.SendLocalizedMessage(500617); // What instrument shall you play? + from.BeginTarget(1, false, TargetFlags.None, new TargetStateCallback(OnPickedInstrument), callback); + } + } + + public static void OnPickedInstrument(Mobile from, object targeted, object state) + { + if (!(targeted is BaseInstrument instrument)) + { + from.SendLocalizedMessage(500619); // That is not a musical instrument. + } + else + { + SetInstrument(from, instrument); + + InstrumentPickedCallback callback = state as InstrumentPickedCallback; + + callback?.Invoke(from, instrument); + } + } + + public static bool IsMageryCreature(BaseCreature bc) + { + return bc != null && bc.AI == AIType.AI_Mage && bc.Skills[SkillName.Magery].Base > 5.0; + } + + public static bool IsFireBreathingCreature(BaseCreature bc) + { + if (bc == null) + return false; + + return bc.HasBreath; + } + + public static bool IsPoisonImmune(BaseCreature bc) + { + return bc?.PoisonImmune != null; + } + + public static int GetPoisonLevel(BaseCreature bc) + { + Poison p = bc?.HitPoison; + + if (p == null) + return 0; + + return p.Level + 1; + } + + public static double GetBaseDifficulty(Mobile targ) + { + /* Difficulty TODO: Add another 100 points for each of the following abilities: + - Radiation or Aura Damage (Heat, Cold etc.) + - Summoning Undead + */ + + double val = targ.HitsMax * 1.6 + targ.StamMax + targ.ManaMax; + + val += targ.SkillsTotal / 10; + + if (val > 700) + val = 700 + (int)((val - 700) * (3.0 / 11)); + + BaseCreature bc = targ as BaseCreature; + + if (IsMageryCreature(bc)) + val += 100; + + if (IsFireBreathingCreature(bc)) + val += 100; + + if (IsPoisonImmune(bc)) + val += 100; + + if (targ is VampireBat || targ is VampireBatFamiliar) + val += 100; + + val += GetPoisonLevel(bc) * 20; + + val /= 10; + + if (bc != null && bc.IsParagon) + val += 40.0; + + if (Core.SE && val > 160.0) + val = 160.0; + + return val; + } + + public double GetDifficultyFor(Mobile targ) + { + double val = GetBaseDifficulty(targ); + + if (m_Quality == InstrumentQuality.Exceptional) + val -= 5.0; // 10% + + if (m_Slayer != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer); + + if (entry != null) + { + if (entry.Slays(targ)) + val -= 10.0; // 20% + else if (entry.Group.OppositionSuperSlays(targ)) + val += 10.0; // -20% + } + } + + if (m_Slayer2 != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer2); + + if (entry != null) + { + if (entry.Slays(targ)) + val -= 10.0; // 20% + else if (entry.Group.OppositionSuperSlays(targ)) + val += 10.0; // -20% + } + } + + return val; + } - public BaseInstrument( int itemID, int wellSound, int badlySound ) : base( itemID ) - { - SuccessSound = wellSound; - FailureSound = badlySound; - UsesRemaining = Utility.RandomMinMax( InitMinUses, InitMaxUses ); - } + public static void SetInstrument(Mobile from, BaseInstrument item) + { + m_Instruments[from] = item; + } - public override void GetProperties( ObjectPropertyList list ) - { - int oldUses = m_UsesRemaining; - CheckReplenishUses( false ); + public override void GetProperties(ObjectPropertyList list) + { + int oldUses = m_UsesRemaining; + CheckReplenishUses(false); - base.GetProperties( list ); + base.GetProperties(list); - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ - if ( m_Quality == InstrumentQuality.Exceptional ) - list.Add( 1060636 ); // exceptional + if (m_Quality == InstrumentQuality.Exceptional) + list.Add(1060636); // exceptional - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ - if ( m_ReplenishesCharges ) - list.Add( 1070928 ); // Replenish Charges + if (m_ReplenishesCharges) + list.Add(1070928); // Replenish Charges - if ( m_Slayer != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer ); - if ( entry != null ) - list.Add( entry.Title ); - } + if (m_Slayer != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer); + if (entry != null) + list.Add(entry.Title); + } - if ( m_Slayer2 != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer2 ); - if ( entry != null ) - list.Add( entry.Title ); - } + if (m_Slayer2 != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer2); + if (entry != null) + list.Add(entry.Title); + } - if ( m_UsesRemaining != oldUses ) - Timer.DelayCall( TimeSpan.Zero, InvalidateProperties ); - } - - public override void OnSingleClick( Mobile from ) - { - ArrayList attrs = new ArrayList(); - - if ( DisplayLootType ) - { - if ( LootType == LootType.Blessed ) - attrs.Add( new EquipInfoAttribute( 1038021 ) ); // blessed - else if ( LootType == LootType.Cursed ) - attrs.Add( new EquipInfoAttribute( 1049643 ) ); // cursed - } - - if ( m_Quality == InstrumentQuality.Exceptional ) - attrs.Add( new EquipInfoAttribute( 1018305 - (int)m_Quality ) ); - - if ( m_ReplenishesCharges ) - attrs.Add( new EquipInfoAttribute( 1070928 ) ); // Replenish Charges - - // TODO: Must this support item identification? - if ( m_Slayer != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer ); - if ( entry != null ) - attrs.Add( new EquipInfoAttribute( entry.Title ) ); - } - - if ( m_Slayer2 != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer2 ); - if ( entry != null ) - attrs.Add( new EquipInfoAttribute( entry.Title ) ); - } - - int number; - - if ( Name == null ) - { - number = LabelNumber; - } - else - { - LabelTo( from, Name ); - number = 1041000; - } - - if ( attrs.Count == 0 && Crafter == null && Name != null ) - return; - - EquipmentInfo eqInfo = new EquipmentInfo( number, m_Crafter, false, (EquipInfoAttribute[])attrs.ToArray( typeof( EquipInfoAttribute ) ) ); - - from.Send( new DisplayEquipmentInfo( this, eqInfo ) ); - } - - public BaseInstrument( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 3 ); // version - - writer.Write( m_ReplenishesCharges ); - if ( m_ReplenishesCharges ) - writer.Write( m_LastReplenished ); - - - writer.Write( m_Crafter ); - - writer.WriteEncodedInt( (int) m_Quality ); - writer.WriteEncodedInt( (int) m_Slayer ); - writer.WriteEncodedInt( (int) m_Slayer2 ); - - writer.WriteEncodedInt( (int)UsesRemaining ); - - writer.WriteEncodedInt( (int) SuccessSound ); - writer.WriteEncodedInt( (int) FailureSound ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 3: - { - m_ReplenishesCharges = reader.ReadBool(); - - if ( m_ReplenishesCharges ) - m_LastReplenished = reader.ReadDateTime(); - - goto case 2; - } - case 2: - { - m_Crafter = reader.ReadMobile(); - - m_Quality = (InstrumentQuality)reader.ReadEncodedInt(); - m_Slayer = (SlayerName)reader.ReadEncodedInt(); - m_Slayer2 = (SlayerName)reader.ReadEncodedInt(); - - UsesRemaining = reader.ReadEncodedInt(); - - SuccessSound = reader.ReadEncodedInt(); - FailureSound = reader.ReadEncodedInt(); - - break; - } - case 1: - { - m_Crafter = reader.ReadMobile(); - - m_Quality = (InstrumentQuality)reader.ReadEncodedInt(); - m_Slayer = (SlayerName)reader.ReadEncodedInt(); - - UsesRemaining = reader.ReadEncodedInt(); - - SuccessSound = reader.ReadEncodedInt(); - FailureSound = reader.ReadEncodedInt(); - - break; - } - case 0: - { - SuccessSound = reader.ReadInt(); - FailureSound = reader.ReadInt(); - UsesRemaining = Utility.RandomMinMax( InitMinUses, InitMaxUses ); - - break; - } - } - - CheckReplenishUses(); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( from.BeginAction( typeof( BaseInstrument ) ) ) - { - SetInstrument( from, this ); - - // Delay of 7 second before beign able to play another instrument again - new InternalTimer( from ).Start(); - - if ( CheckMusicianship( from ) ) - PlayInstrumentWell( from ); - else - PlayInstrumentBadly( from ); - } - else - { - from.SendLocalizedMessage( 500119 ); // You must wait to perform another action - } - } - - public static bool CheckMusicianship( Mobile m ) - { - m.CheckSkill( SkillName.Musicianship, 0.0, 120.0 ); - - return ( (m.Skills[SkillName.Musicianship].Value / 100) > Utility.RandomDouble() ); - } - - public void PlayInstrumentWell( Mobile from ) - { - from.PlaySound( SuccessSound ); - } - - public void PlayInstrumentBadly( Mobile from ) - { - from.PlaySound( FailureSound ); - } - - private class InternalTimer : Timer - { - private Mobile m_From; - - public InternalTimer( Mobile from ) : base( TimeSpan.FromSeconds( 6.0 ) ) - { - m_From = from; - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - m_From.EndAction( typeof( BaseInstrument ) ); - } - } - #region ICraftable Members - - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (InstrumentQuality)quality; - - if ( makersMark ) - Crafter = from; - - return quality; - } - - #endregion - } -} + if (m_UsesRemaining != oldUses) + Timer.DelayCall(TimeSpan.Zero, InvalidateProperties); + } + + public override void OnSingleClick(Mobile from) + { + ArrayList attrs = new ArrayList(); + + if (DisplayLootType) + { + if (LootType == LootType.Blessed) + attrs.Add(new EquipInfoAttribute(1038021)); // blessed + else if (LootType == LootType.Cursed) + attrs.Add(new EquipInfoAttribute(1049643)); // cursed + } + + if (m_Quality == InstrumentQuality.Exceptional) + attrs.Add(new EquipInfoAttribute(1018305 - (int)m_Quality)); + + if (m_ReplenishesCharges) + attrs.Add(new EquipInfoAttribute(1070928)); // Replenish Charges + + // TODO: Must this support item identification? + if (m_Slayer != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer); + if (entry != null) + attrs.Add(new EquipInfoAttribute(entry.Title)); + } + + if (m_Slayer2 != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer2); + if (entry != null) + attrs.Add(new EquipInfoAttribute(entry.Title)); + } + + int number; + + if (Name == null) + { + number = LabelNumber; + } + else + { + LabelTo(from, Name); + number = 1041000; + } + + if (attrs.Count == 0 && Crafter == null && Name != null) + return; + + EquipmentInfo eqInfo = new EquipmentInfo(number, m_Crafter, false, + (EquipInfoAttribute[])attrs.ToArray(typeof(EquipInfoAttribute))); + + from.Send(new DisplayEquipmentInfo(this, eqInfo)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(3); // version + + writer.Write(m_ReplenishesCharges); + if (m_ReplenishesCharges) + writer.Write(m_LastReplenished); + + + writer.Write(m_Crafter); + + writer.WriteEncodedInt((int)m_Quality); + writer.WriteEncodedInt((int)m_Slayer); + writer.WriteEncodedInt((int)m_Slayer2); + + writer.WriteEncodedInt(UsesRemaining); + + writer.WriteEncodedInt(SuccessSound); + writer.WriteEncodedInt(FailureSound); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + m_ReplenishesCharges = reader.ReadBool(); + + if (m_ReplenishesCharges) + m_LastReplenished = reader.ReadDateTime(); + + goto case 2; + } + case 2: + { + m_Crafter = reader.ReadMobile(); + + m_Quality = (InstrumentQuality)reader.ReadEncodedInt(); + m_Slayer = (SlayerName)reader.ReadEncodedInt(); + m_Slayer2 = (SlayerName)reader.ReadEncodedInt(); + + UsesRemaining = reader.ReadEncodedInt(); + + SuccessSound = reader.ReadEncodedInt(); + FailureSound = reader.ReadEncodedInt(); + + break; + } + case 1: + { + m_Crafter = reader.ReadMobile(); + + m_Quality = (InstrumentQuality)reader.ReadEncodedInt(); + m_Slayer = (SlayerName)reader.ReadEncodedInt(); + + UsesRemaining = reader.ReadEncodedInt(); + + SuccessSound = reader.ReadEncodedInt(); + FailureSound = reader.ReadEncodedInt(); + + break; + } + case 0: + { + SuccessSound = reader.ReadInt(); + FailureSound = reader.ReadInt(); + UsesRemaining = Utility.RandomMinMax(InitMinUses, InitMaxUses); + + break; + } + } + + CheckReplenishUses(); + } + + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (from.BeginAction(typeof(BaseInstrument))) + { + SetInstrument(from, this); + + // Delay of 7 second before beign able to play another instrument again + new InternalTimer(from).Start(); + + if (CheckMusicianship(from)) + PlayInstrumentWell(from); + else + PlayInstrumentBadly(from); + } + else + { + from.SendLocalizedMessage(500119); // You must wait to perform another action + } + } + + public static bool CheckMusicianship(Mobile m) + { + m.CheckSkill(SkillName.Musicianship, 0.0, 120.0); + + return m.Skills[SkillName.Musicianship].Value / 100 > Utility.RandomDouble(); + } + + public void PlayInstrumentWell(Mobile from) + { + from.PlaySound(SuccessSound); + } + + public void PlayInstrumentBadly(Mobile from) + { + from.PlaySound(FailureSound); + } + + private class InternalTimer : Timer + { + private Mobile m_From; + + public InternalTimer(Mobile from) : base(TimeSpan.FromSeconds(6.0)) + { + m_From = from; + Priority = TimerPriority.TwoFiftyMS; + } + + protected override void OnTick() + { + m_From.EndAction(typeof(BaseInstrument)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/Drums.cs b/Scripts/Items/Skill Items/Musical Instruments/Drums.cs index 3d96b33f4..395f63510 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/Drums.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/Drums.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class Drums : BaseInstrument - { - [Constructible] - public Drums() : base( 0xE9C, 0x38, 0x39 ) - { - Weight = 4.0; - } + public class Drums : BaseInstrument + { + [Constructible] + public Drums() : base(0xE9C, 0x38, 0x39) + { + Weight = 4.0; + } - public Drums( Serial serial ) : base( serial ) - { - } + public Drums(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 4.0; - } - } + if (Weight == 3.0) + Weight = 4.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/Harp.cs b/Scripts/Items/Skill Items/Musical Instruments/Harp.cs index 4c0589a7a..355bf9613 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/Harp.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/Harp.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class Harp : BaseInstrument - { - [Constructible] - public Harp() : base( 0xEB1, 0x43, 0x44 ) - { - Weight = 35.0; - } + public class Harp : BaseInstrument + { + [Constructible] + public Harp() : base(0xEB1, 0x43, 0x44) + { + Weight = 35.0; + } - public Harp( Serial serial ) : base( serial ) - { - } + public Harp(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 35.0; - } - } + if (Weight == 3.0) + Weight = 35.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/LapHarp.cs b/Scripts/Items/Skill Items/Musical Instruments/LapHarp.cs index a7697f960..0ea59ad1b 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/LapHarp.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/LapHarp.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class LapHarp : BaseInstrument - { - [Constructible] - public LapHarp() : base( 0xEB2, 0x45, 0x46 ) - { - Weight = 10.0; - } + public class LapHarp : BaseInstrument + { + [Constructible] + public LapHarp() : base(0xEB2, 0x45, 0x46) + { + Weight = 10.0; + } - public LapHarp( Serial serial ) : base( serial ) - { - } + public LapHarp(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 10.0; - } - } + if (Weight == 3.0) + Weight = 10.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/Lute.cs b/Scripts/Items/Skill Items/Musical Instruments/Lute.cs index 6b897cf54..9c4287530 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/Lute.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/Lute.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class Lute : BaseInstrument - { - [Constructible] - public Lute() : base( 0xEB3, 0x4C, 0x4D ) - { - Weight = 5.0; - } + public class Lute : BaseInstrument + { + [Constructible] + public Lute() : base(0xEB3, 0x4C, 0x4D) + { + Weight = 5.0; + } - public Lute( Serial serial ) : base( serial ) - { - } + public Lute(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 3.0 ) - Weight = 5.0; - } - } + if (Weight == 3.0) + Weight = 5.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/Tambourine.cs b/Scripts/Items/Skill Items/Musical Instruments/Tambourine.cs index c68c26b58..0cc0ac795 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/Tambourine.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/Tambourine.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class Tambourine : BaseInstrument - { - [Constructible] - public Tambourine() : base( 0xE9D, 0x52, 0x53 ) - { - Weight = 1.0; - } + public class Tambourine : BaseInstrument + { + [Constructible] + public Tambourine() : base(0xE9D, 0x52, 0x53) + { + Weight = 1.0; + } - public Tambourine( Serial serial ) : base( serial ) - { - } + public Tambourine(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } + if (Weight == 2.0) + Weight = 1.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Musical Instruments/TambourineTassel.cs b/Scripts/Items/Skill Items/Musical Instruments/TambourineTassel.cs index 35d659a48..52d623faa 100644 --- a/Scripts/Items/Skill Items/Musical Instruments/TambourineTassel.cs +++ b/Scripts/Items/Skill Items/Musical Instruments/TambourineTassel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class TambourineTassel : BaseInstrument - { - [Constructible] - public TambourineTassel() : base( 0xE9E, 0x52, 0x53 ) - { - Weight = 1.0; - } + public class TambourineTassel : BaseInstrument + { + [Constructible] + public TambourineTassel() : base(0xE9E, 0x52, 0x53) + { + Weight = 1.0; + } - public TambourineTassel( Serial serial ) : base( serial ) - { - } + public TambourineTassel(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } + if (Weight == 2.0) + Weight = 1.0; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/EggBomb.cs b/Scripts/Items/Skill Items/Ninjitsu/EggBomb.cs index 07412265f..01ab460dd 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/EggBomb.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/EggBomb.cs @@ -1,76 +1,78 @@ +using Server.SkillHandlers; + namespace Server.Items { - public class EggBomb : Item - { - public override int LabelNumber => 1030249; + public class EggBomb : Item + { + [Constructible] + public EggBomb() : base(0x2808) + { + // Item ID should be 0x2809 - Temporary solution for clients 7.0.0.0 and up + Stackable = Core.ML; + Weight = 1.0; + } - [Constructible] - public EggBomb() : base( 0x2808 ) - { - // Item ID should be 0x2809 - Temporary solution for clients 7.0.0.0 and up - Stackable = Core.ML; - Weight = 1.0; - } + public EggBomb(Serial serial) : base(serial) + { + } - public EggBomb( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1030249; - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - // The item must be in your backpack to use it. - from.SendLocalizedMessage( 1060640 ); - } - else if ( from.Skills.Ninjitsu.Value < 50.0 ) - { - // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - from.SendLocalizedMessage( 1063013, "50\tNinjitsu" ); - } - else if (Core.TickCount - from.NextSkillTime < 0) - { - // You must wait a few seconds before you can use that item. - from.SendLocalizedMessage( 1070772 ); - } - else if ( from.Mana < 10 ) - { - // You don't have enough mana to do that. - from.SendLocalizedMessage( 1049456 ); - } - else - { - SkillHandlers.Hiding.CombatOverride = true; + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + // The item must be in your backpack to use it. + from.SendLocalizedMessage(1060640); + } + else if (from.Skills.Ninjitsu.Value < 50.0) + { + // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + from.SendLocalizedMessage(1063013, "50\tNinjitsu"); + } + else if (Core.TickCount - from.NextSkillTime < 0) + { + // You must wait a few seconds before you can use that item. + from.SendLocalizedMessage(1070772); + } + else if (from.Mana < 10) + { + // You don't have enough mana to do that. + from.SendLocalizedMessage(1049456); + } + else + { + Hiding.CombatOverride = true; - if ( from.UseSkill( SkillName.Hiding ) ) - { - from.Mana -= 10; + if (from.UseSkill(SkillName.Hiding)) + { + from.Mana -= 10; - from.FixedParticles( 0x3709, 1, 30, 9904, 1108, 6, EffectLayer.RightFoot ); - from.PlaySound( 0x22F ); + from.FixedParticles(0x3709, 1, 30, 9904, 1108, 6, EffectLayer.RightFoot); + from.PlaySound(0x22F); - Consume(); - } + Consume(); + } - SkillHandlers.Hiding.CombatOverride = false; - } - } + Hiding.CombatOverride = false; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - - if ( ItemID == 0x2809 ) // Temporary solution for clients 7.0.0.0 and up - ItemID = 0x2808; - } - } + int version = reader.ReadInt(); + + if (ItemID == 0x2809) // Temporary solution for clients 7.0.0.0 and up + ItemID = 0x2808; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/Fukiya.cs b/Scripts/Items/Skill Items/Ninjitsu/Fukiya.cs index ff8a1387d..24e8dd0d2 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/Fukiya.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/Fukiya.cs @@ -5,128 +5,141 @@ using Server.Mobiles; namespace Server.Items { - [FlippableAttribute( 0x27AA, 0x27F5 )] - public class Fukiya : Item, INinjaWeapon - { - public virtual int WrongAmmoMessage => 1063329; //You can only load fukiya darts - public virtual int NoFreeHandMessage => 1063327; //You must have a free hand to use a fukiya. - public virtual int EmptyWeaponMessage => 1063325; //You have no fukiya darts! - public virtual int RecentlyUsedMessage => 1063326; //You are already using that fukiya. - public virtual int FullWeaponMessage => 1063330; //You can only load fukiya darts + [Flippable(0x27AA, 0x27F5)] + public class Fukiya : Item, INinjaWeapon + { + private Poison m_Poison; + private int m_PoisonCharges; - public virtual int WeaponMinRange => 0; - public virtual int WeaponMaxRange => 6; + private int m_UsesRemaining; - public virtual int WeaponDamage => Utility.RandomMinMax(4, 6); + [Constructible] + public Fukiya() : base(0x27AA) + { + Weight = 4.0; + Layer = Layer.OneHanded; + } - public Type AmmoType => typeof(FukiyaDarts); + public Fukiya(Serial serial) : base(serial) + { + } - private int m_UsesRemaining; - private Poison m_Poison; - private int m_PoisonCharges; + public virtual int WrongAmmoMessage => 1063329; //You can only load fukiya darts + public virtual int NoFreeHandMessage => 1063327; //You must have a free hand to use a fukiya. + public virtual int EmptyWeaponMessage => 1063325; //You have no fukiya darts! + public virtual int RecentlyUsedMessage => 1063326; //You are already using that fukiya. + public virtual int FullWeaponMessage => 1063330; //You can only load fukiya darts - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + public virtual int WeaponMinRange => 0; + public virtual int WeaponMaxRange => 6; - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison - { - get => m_Poison; - set{ m_Poison = value; InvalidateProperties(); } - } + public virtual int WeaponDamage => Utility.RandomMinMax(4, 6); - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonCharges - { - get => m_PoisonCharges; - set { m_PoisonCharges = value; InvalidateProperties(); } - } + public Type AmmoType => typeof(FukiyaDarts); - public bool ShowUsesRemaining{ get => true; - set{} } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - [Constructible] - public Fukiya() : base( 0x27AA ) - { - Weight = 4.0; - Layer = Layer.OneHanded; - } + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison + { + get => m_Poison; + set + { + m_Poison = value; + InvalidateProperties(); + } + } - public Fukiya( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonCharges + { + get => m_PoisonCharges; + set + { + m_PoisonCharges = value; + InvalidateProperties(); + } + } - public void AttackAnimation(Mobile from, Mobile to) - { - if (from.Body.IsHuman && !from.Mounted) - { - from.Animate(33, 2, 1, true, true, 0); - } + public bool ShowUsesRemaining + { + get => true; + set { } + } - from.PlaySound(0x223); - from.MovingEffect(to, 0x2804, 5, 0, false, false); - } + public void AttackAnimation(Mobile from, Mobile to) + { + if (from.Body.IsHuman && !from.Mounted) from.Animate(33, 2, 1, true, true, 0); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + from.PlaySound(0x223); + from.MovingEffect(to, 0x2804, 5, 0, false, false); + } - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_Poison != null && m_PoisonCharges > 0 ) - list.Add( 1062412 + m_Poison.Level, m_PoisonCharges.ToString() ); - } + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ - public override void OnDoubleClick( Mobile from ) - { - NinjaWeapon.AttemptShoot((PlayerMobile)from, this); - } + if (m_Poison != null && m_PoisonCharges > 0) + list.Add(1062412 + m_Poison.Level, m_PoisonCharges.ToString()); + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void OnDoubleClick(Mobile from) + { + NinjaWeapon.AttemptShoot((PlayerMobile)from, this); + } - if ( IsChildOf( from ) ) - { - list.Add(new NinjaWeapon.LoadEntry(this, 6224)); - list.Add(new NinjaWeapon.UnloadEntry(this, 6225)); - } - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (IsChildOf(from)) + { + list.Add(new NinjaWeapon.LoadEntry(this, 6224)); + list.Add(new NinjaWeapon.UnloadEntry(this, 6225)); + } + } - writer.Write( (int) 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) m_UsesRemaining ); + writer.Write(0); - Poison.Serialize( m_Poison, writer ); - writer.Write( (int) m_PoisonCharges ); - } + writer.Write(m_UsesRemaining); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Poison.Serialize(m_Poison, writer); + writer.Write(m_PoisonCharges); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - m_UsesRemaining = reader.ReadInt(); + int version = reader.ReadInt(); - m_Poison = Poison.Deserialize( reader ); - m_PoisonCharges = reader.ReadInt(); + switch (version) + { + case 0: + { + m_UsesRemaining = reader.ReadInt(); - break; - } - } - } - } -} + m_Poison = Poison.Deserialize(reader); + m_PoisonCharges = reader.ReadInt(); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/FukiyaDarts.cs b/Scripts/Items/Skill Items/Ninjitsu/FukiyaDarts.cs index b023450ec..1776d4c41 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/FukiyaDarts.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/FukiyaDarts.cs @@ -3,102 +3,117 @@ using Server.Engines.Craft; namespace Server.Items { - public class FukiyaDarts : Item, ICraftable, INinjaAmmo - { - private int m_UsesRemaining; + public class FukiyaDarts : Item, ICraftable, INinjaAmmo + { + private Poison m_Poison; + private int m_PoisonCharges; + private int m_UsesRemaining; - private Poison m_Poison; - private int m_PoisonCharges; + [Constructible] + public FukiyaDarts() : this(1) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + [Constructible] + public FukiyaDarts(int amount) : base(0x2806) + { + Weight = 1.0; - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison - { - get => m_Poison; - set{ m_Poison = value; InvalidateProperties(); } - } + m_UsesRemaining = amount; + } - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonCharges - { - get => m_PoisonCharges; - set { m_PoisonCharges = value; InvalidateProperties(); } - } + public FukiyaDarts(Serial serial) : base(serial) + { + } - public bool ShowUsesRemaining{ get => true; - set{} } + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + if (quality == 2) + UsesRemaining *= 2; - [Constructible] - public FukiyaDarts() : this( 1 ) - { - } + return quality; + } - [Constructible] - public FukiyaDarts( int amount ) : base( 0x2806 ) - { - Weight = 1.0; + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - m_UsesRemaining = amount; - } + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison + { + get => m_Poison; + set + { + m_Poison = value; + InvalidateProperties(); + } + } - public FukiyaDarts( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonCharges + { + get => m_PoisonCharges; + set + { + m_PoisonCharges = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public bool ShowUsesRemaining + { + get => true; + set { } + } - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_Poison != null && m_PoisonCharges > 0 ) - list.Add( 1062412 + m_Poison.Level, m_PoisonCharges.ToString() ); - } + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (m_Poison != null && m_PoisonCharges > 0) + list.Add(1062412 + m_Poison.Level, m_PoisonCharges.ToString()); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) m_UsesRemaining ); + writer.Write(0); // version - Poison.Serialize( m_Poison, writer ); - writer.Write( (int) m_PoisonCharges ); - } + writer.Write(m_UsesRemaining); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Poison.Serialize(m_Poison, writer); + writer.Write(m_PoisonCharges); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - m_UsesRemaining = reader.ReadInt(); + int version = reader.ReadInt(); - m_Poison = Poison.Deserialize( reader ); - m_PoisonCharges = reader.ReadInt(); + switch (version) + { + case 0: + { + m_UsesRemaining = reader.ReadInt(); - break; - } - } - } + m_Poison = Poison.Deserialize(reader); + m_PoisonCharges = reader.ReadInt(); - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - if ( quality == 2 ) - UsesRemaining *= 2; - - return quality; - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/LeatherNinjaBelt.cs b/Scripts/Items/Skill Items/Ninjitsu/LeatherNinjaBelt.cs index e0b47231b..2c77e45ea 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/LeatherNinjaBelt.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/LeatherNinjaBelt.cs @@ -5,141 +5,155 @@ using Server.Mobiles; namespace Server.Items { - [FlippableAttribute( 0x2790, 0x27DB )] - public class LeatherNinjaBelt : BaseWaist, IDyable, INinjaWeapon - { - public override CraftResource DefaultResource => CraftResource.RegularLeather; + [Flippable(0x2790, 0x27DB)] + public class LeatherNinjaBelt : BaseWaist, IDyable, INinjaWeapon + { + private Poison m_Poison; + private int m_PoisonCharges; - public virtual int WrongAmmoMessage => 1063301; //You can only place shuriken in a ninja belt. - public virtual int NoFreeHandMessage => 1063299; //You must have a free hand to throw shuriken. - public virtual int EmptyWeaponMessage => 1063297; //You have no shuriken in your ninja belt! - public virtual int RecentlyUsedMessage => 1063298; //You cannot throw another shuriken yet. - public virtual int FullWeaponMessage => 1063302; //You cannot add any more shuriken. + private int m_UsesRemaining; - public virtual int WeaponMinRange => 2; - public virtual int WeaponMaxRange => 10; + [Constructible] + public LeatherNinjaBelt() : base(0x2790) - public virtual int WeaponDamage => Utility.RandomMinMax(3, 5); + { + Weight = 1.0; + Layer = Layer.Waist; + } - public virtual Type AmmoType => typeof(Shuriken); + public LeatherNinjaBelt(Serial serial) : base(serial) + { + } - private int m_UsesRemaining; - private Poison m_Poison; - private int m_PoisonCharges; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + public virtual int WrongAmmoMessage => 1063301; //You can only place shuriken in a ninja belt. + public virtual int NoFreeHandMessage => 1063299; //You must have a free hand to throw shuriken. + public virtual int EmptyWeaponMessage => 1063297; //You have no shuriken in your ninja belt! + public virtual int RecentlyUsedMessage => 1063298; //You cannot throw another shuriken yet. + public virtual int FullWeaponMessage => 1063302; //You cannot add any more shuriken. - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison - { - get => m_Poison; - set{ m_Poison = value; InvalidateProperties(); } - } + public virtual int WeaponMinRange => 2; + public virtual int WeaponMaxRange => 10; - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonCharges - { - get => m_PoisonCharges; - set { m_PoisonCharges = value; InvalidateProperties(); } - } + public virtual int WeaponDamage => Utility.RandomMinMax(3, 5); - public bool ShowUsesRemaining{ get => true; - set{} } + public virtual Type AmmoType => typeof(Shuriken); - [Constructible] - public LeatherNinjaBelt() : base( 0x2790 ) + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - { - Weight = 1.0; - Layer = Layer.Waist; - } + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison + { + get => m_Poison; + set + { + m_Poison = value; + InvalidateProperties(); + } + } - public LeatherNinjaBelt( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonCharges + { + get => m_PoisonCharges; + set + { + m_PoisonCharges = value; + InvalidateProperties(); + } + } - public void AttackAnimation(Mobile from, Mobile to) - { - if (from.Body.IsHuman) - { - from.Animate(from.Mounted ? 26 : 9, 7, 1, true, false, 0); - } + public bool ShowUsesRemaining + { + get => true; + set { } + } - from.PlaySound(0x23A); - from.MovingEffect(to, 0x27AC, 1, 0, false, false); - } + public void AttackAnimation(Mobile from, Mobile to) + { + if (from.Body.IsHuman) from.Animate(from.Mounted ? 26 : 9, 7, 1, true, false, 0); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + from.PlaySound(0x23A); + from.MovingEffect(to, 0x27AC, 1, 0, false, false); + } - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_Poison != null && m_PoisonCharges > 0 ) - list.Add( 1062412 + m_Poison.Level, m_PoisonCharges.ToString() ); - } + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ - public override bool OnEquip( Mobile from ) - { - if (base.OnEquip(from)) - { - from.SendLocalizedMessage(1070785); // Double click this item each time you wish to throw a shuriken. - return true; - } - return false; - } + if (m_Poison != null && m_PoisonCharges > 0) + list.Add(1062412 + m_Poison.Level, m_PoisonCharges.ToString()); + } - public override void OnDoubleClick(Mobile from) - { - NinjaWeapon.AttemptShoot((PlayerMobile)from, this); - } + public override bool OnEquip(Mobile from) + { + if (base.OnEquip(from)) + { + from.SendLocalizedMessage(1070785); // Double click this item each time you wish to throw a shuriken. + return true; + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + return false; + } - if ( IsChildOf( from ) ) - { - list.Add(new NinjaWeapon.LoadEntry(this, 6222)); - list.Add(new NinjaWeapon.UnloadEntry(this, 6223)); - } - } + public override void OnDoubleClick(Mobile from) + { + NinjaWeapon.AttemptShoot((PlayerMobile)from, this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - writer.Write( (int) 0 ); + if (IsChildOf(from)) + { + list.Add(new NinjaWeapon.LoadEntry(this, 6222)); + list.Add(new NinjaWeapon.UnloadEntry(this, 6223)); + } + } - writer.Write( (int) m_UsesRemaining ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Poison.Serialize( m_Poison, writer ); - writer.Write( (int) m_PoisonCharges ); - } + writer.Write(0); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_UsesRemaining); - int version = reader.ReadInt(); + Poison.Serialize(m_Poison, writer); + writer.Write(m_PoisonCharges); + } - switch ( version ) - { - case 0: - { - m_UsesRemaining = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Poison = Poison.Deserialize( reader ); - m_PoisonCharges = reader.ReadInt(); + int version = reader.ReadInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + m_UsesRemaining = reader.ReadInt(); + + m_Poison = Poison.Deserialize(reader); + m_PoisonCharges = reader.ReadInt(); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/NinjaWeapons.cs b/Scripts/Items/Skill Items/Ninjitsu/NinjaWeapons.cs index 277a4096a..d4c1c3a34 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/NinjaWeapons.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/NinjaWeapons.cs @@ -1,6 +1,8 @@ using System; using Server.ContextMenus; using Server.Mobiles; +using Server.SkillHandlers; +using Server.Spells.Chivalry; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; using Server.Targeting; @@ -13,371 +15,303 @@ using Server.Targeting; namespace Server.Items { - public interface INinjaAmmo : IUsesRemaining - { - int PoisonCharges { get; set; } - Poison Poison { get; set; } - } + public interface INinjaAmmo : IUsesRemaining + { + int PoisonCharges{ get; set; } + Poison Poison{ get; set; } + } - public interface INinjaWeapon : IUsesRemaining - { - int NoFreeHandMessage { get; } - int EmptyWeaponMessage { get; } - int RecentlyUsedMessage { get; } - int FullWeaponMessage { get; } - int WrongAmmoMessage { get; } - Type AmmoType { get; } - int PoisonCharges { get; set; } - Poison Poison { get; set; } - int WeaponDamage { get; } - int WeaponMinRange { get; } - int WeaponMaxRange { get; } + public interface INinjaWeapon : IUsesRemaining + { + int NoFreeHandMessage{ get; } + int EmptyWeaponMessage{ get; } + int RecentlyUsedMessage{ get; } + int FullWeaponMessage{ get; } + int WrongAmmoMessage{ get; } + Type AmmoType{ get; } + int PoisonCharges{ get; set; } + Poison Poison{ get; set; } + int WeaponDamage{ get; } + int WeaponMinRange{ get; } + int WeaponMaxRange{ get; } - void AttackAnimation(Mobile from, Mobile to); - } + void AttackAnimation(Mobile from, Mobile to); + } - public class NinjaWeapon - { - private const int MaxUses = 10; + public class NinjaWeapon + { + private const int MaxUses = 10; - public static void AttemptShoot(PlayerMobile from, INinjaWeapon weapon) - { - if (CanUseWeapon(from, weapon)) - { - from.BeginTarget(weapon.WeaponMaxRange, false, TargetFlags.Harmful, OnTarget, weapon); - } - } + public static void AttemptShoot(PlayerMobile from, INinjaWeapon weapon) + { + if (CanUseWeapon(from, weapon)) + from.BeginTarget(weapon.WeaponMaxRange, false, TargetFlags.Harmful, OnTarget, weapon); + } - private static void Shoot(PlayerMobile from, Mobile target, INinjaWeapon weapon) - { - if (from != target && CanUseWeapon(from, weapon) && from.CanBeHarmful(target)) - { - if (weapon.WeaponMinRange == 0 || !from.InRange(target, weapon.WeaponMinRange)) - { - from.NinjaWepCooldown = true; + private static void Shoot(PlayerMobile from, Mobile target, INinjaWeapon weapon) + { + if (from != target && CanUseWeapon(from, weapon) && from.CanBeHarmful(target)) + { + if (weapon.WeaponMinRange == 0 || !from.InRange(target, weapon.WeaponMinRange)) + { + from.NinjaWepCooldown = true; - from.Direction = from.GetDirectionTo(target); + from.Direction = from.GetDirectionTo(target); - from.RevealingAction(); + from.RevealingAction(); - weapon.AttackAnimation(from, target); + weapon.AttackAnimation(from, target); - ConsumeUse(weapon); + ConsumeUse(weapon); - if (CombatCheck(from, target)) - { - Timer.DelayCall(TimeSpan.FromSeconds(1.0), OnHit, new object[] { from, target, weapon }); - } + if (CombatCheck(from, target)) + Timer.DelayCall(TimeSpan.FromSeconds(1.0), OnHit, new object[] { from, target, weapon }); - Timer.DelayCall(TimeSpan.FromSeconds(2.5), ResetUsing, from); - } - else - { - from.SendLocalizedMessage(1063303); // Your target is too close! - } - } - } + Timer.DelayCall(TimeSpan.FromSeconds(2.5), ResetUsing, from); + } + else + { + from.SendLocalizedMessage(1063303); // Your target is too close! + } + } + } - private static void ResetUsing(PlayerMobile from) - { - from.NinjaWepCooldown = false; - } + private static void ResetUsing(PlayerMobile from) + { + from.NinjaWepCooldown = false; + } - private static void Unload(Mobile from, INinjaWeapon weapon) - { - if (weapon.UsesRemaining > 0) - { - INinjaAmmo ammo = Activator.CreateInstance(weapon.AmmoType, new object[] { weapon.UsesRemaining }) as INinjaAmmo; + private static void Unload(Mobile from, INinjaWeapon weapon) + { + if (weapon.UsesRemaining > 0) + { + INinjaAmmo ammo = Activator.CreateInstance(weapon.AmmoType, weapon.UsesRemaining) as INinjaAmmo; - ammo.Poison = weapon.Poison; - ammo.PoisonCharges = weapon.PoisonCharges; + ammo.Poison = weapon.Poison; + ammo.PoisonCharges = weapon.PoisonCharges; - from.AddToBackpack((Item)ammo); + from.AddToBackpack((Item)ammo); - weapon.UsesRemaining = 0; - weapon.PoisonCharges = 0; - weapon.Poison = null; - } - } + weapon.UsesRemaining = 0; + weapon.PoisonCharges = 0; + weapon.Poison = null; + } + } - private static void Reload(PlayerMobile from, INinjaWeapon weapon, INinjaAmmo ammo) - { - if (weapon.UsesRemaining < MaxUses) - { - int need = Math.Min((MaxUses - weapon.UsesRemaining), ammo.UsesRemaining); + private static void Reload(PlayerMobile from, INinjaWeapon weapon, INinjaAmmo ammo) + { + if (weapon.UsesRemaining < MaxUses) + { + int need = Math.Min(MaxUses - weapon.UsesRemaining, ammo.UsesRemaining); - if (need > 0) - { - if (weapon.Poison != null && (ammo.Poison == null || weapon.Poison.Level > ammo.Poison.Level)) - { - from.SendLocalizedMessage(1070767); // Loaded projectile is stronger, unload it first - } - else - { - if (weapon.UsesRemaining > 0) - { - if ((weapon.Poison == null && ammo.Poison != null) - || ((weapon.Poison != null && ammo.Poison != null) && weapon.Poison.Level != ammo.Poison.Level)) - { - Unload(from, weapon); - need = Math.Min(MaxUses, ammo.UsesRemaining); - } - } - int poisonneeded = Math.Min((MaxUses - weapon.PoisonCharges), ammo.PoisonCharges); + if (need > 0) + { + if (weapon.Poison != null && (ammo.Poison == null || weapon.Poison.Level > ammo.Poison.Level)) + { + from.SendLocalizedMessage(1070767); // Loaded projectile is stronger, unload it first + } + else + { + if (weapon.UsesRemaining > 0) + if (weapon.Poison == null && ammo.Poison != null + || weapon.Poison != null && ammo.Poison != null && weapon.Poison.Level != ammo.Poison.Level) + { + Unload(from, weapon); + need = Math.Min(MaxUses, ammo.UsesRemaining); + } - weapon.UsesRemaining += need; - weapon.PoisonCharges += poisonneeded; + int poisonneeded = Math.Min(MaxUses - weapon.PoisonCharges, ammo.PoisonCharges); - if (weapon.PoisonCharges > 0) - { - weapon.Poison = ammo.Poison; - } + weapon.UsesRemaining += need; + weapon.PoisonCharges += poisonneeded; - ammo.PoisonCharges -= poisonneeded; - ammo.UsesRemaining -= need; + if (weapon.PoisonCharges > 0) weapon.Poison = ammo.Poison; - if (ammo.UsesRemaining < 1) - { - ((Item)ammo).Delete(); - } - else if (ammo.PoisonCharges < 1) - { - ammo.Poison = null; - } - } - } // "else" here would mean they targeted "ammo" with 0 uses. undefined behavior. - } - else - { - from.SendLocalizedMessage(weapon.FullWeaponMessage); - } - } + ammo.PoisonCharges -= poisonneeded; + ammo.UsesRemaining -= need; - private static void ConsumeUse(INinjaWeapon weapon) - { - if (weapon.UsesRemaining > 0) - { - weapon.UsesRemaining--; + if (ammo.UsesRemaining < 1) + ((Item)ammo).Delete(); + else if (ammo.PoisonCharges < 1) ammo.Poison = null; + } + } // "else" here would mean they targeted "ammo" with 0 uses. undefined behavior. + } + else + { + from.SendLocalizedMessage(weapon.FullWeaponMessage); + } + } - if (weapon.UsesRemaining < 1) - { - weapon.PoisonCharges = 0; - weapon.Poison = null; - } - } - } + private static void ConsumeUse(INinjaWeapon weapon) + { + if (weapon.UsesRemaining > 0) + { + weapon.UsesRemaining--; - private static bool CanUseWeapon(PlayerMobile from, INinjaWeapon weapon) - { - if (WeaponIsValid(weapon, from)) - { - if (weapon.UsesRemaining > 0) - { - if (!from.NinjaWepCooldown) - { - if (BasePotion.HasFreeHand(from)) - { - return true; - } + if (weapon.UsesRemaining < 1) + { + weapon.PoisonCharges = 0; + weapon.Poison = null; + } + } + } - from.SendLocalizedMessage(weapon.NoFreeHandMessage); - } - else - { - from.SendLocalizedMessage(weapon.RecentlyUsedMessage); - } - } - else - { - from.SendLocalizedMessage(weapon.EmptyWeaponMessage); - } - } - return false; - } + private static bool CanUseWeapon(PlayerMobile from, INinjaWeapon weapon) + { + if (WeaponIsValid(weapon, from)) + { + if (weapon.UsesRemaining > 0) + { + if (!from.NinjaWepCooldown) + { + if (BasePotion.HasFreeHand(from)) return true; - private static bool CombatCheck(Mobile attacker, Mobile defender) /* mod'd from baseweapon */ - { - BaseWeapon defWeapon = defender.Weapon as BaseWeapon; + from.SendLocalizedMessage(weapon.NoFreeHandMessage); + } + else + { + from.SendLocalizedMessage(weapon.RecentlyUsedMessage); + } + } + else + { + from.SendLocalizedMessage(weapon.EmptyWeaponMessage); + } + } - Skill atkSkill = defender.Skills.Ninjitsu; - Skill defSkill = defender.Skills[defWeapon.Skill]; + return false; + } - double atSkillValue = attacker.Skills.Ninjitsu.Value; - double defSkillValue = defWeapon.GetDefendSkillValue(attacker, defender); + private static bool CombatCheck(Mobile attacker, Mobile defender) /* mod'd from baseweapon */ + { + BaseWeapon defWeapon = defender.Weapon as BaseWeapon; - double attackValue = AosAttributes.GetValue(attacker, AosAttribute.AttackChance); + Skill atkSkill = defender.Skills.Ninjitsu; + Skill defSkill = defender.Skills[defWeapon.Skill]; - if (defSkillValue <= -20.0) - { - defSkillValue = -19.9; - } + double atSkillValue = attacker.Skills.Ninjitsu.Value; + double defSkillValue = defWeapon.GetDefendSkillValue(attacker, defender); - if (Spells.Chivalry.DivineFurySpell.UnderEffect(attacker)) - { - attackValue += 10; - } + double attackValue = AosAttributes.GetValue(attacker, AosAttribute.AttackChance); - if (AnimalForm.UnderTransformation(attacker, typeof(GreyWolf)) || AnimalForm.UnderTransformation(attacker, typeof(BakeKitsune))) - { - attackValue += 20; - } + if (defSkillValue <= -20.0) defSkillValue = -19.9; - if (HitLower.IsUnderAttackEffect(attacker)) - { - attackValue -= 25; - } + if (DivineFurySpell.UnderEffect(attacker)) attackValue += 10; - if (attackValue > 45) - { - attackValue = 45; - } + if (AnimalForm.UnderTransformation(attacker, typeof(GreyWolf)) || + AnimalForm.UnderTransformation(attacker, typeof(BakeKitsune))) attackValue += 20; - attackValue = (atSkillValue + 20.0) * (100 + attackValue); + if (HitLower.IsUnderAttackEffect(attacker)) attackValue -= 25; - double defenseValue = AosAttributes.GetValue(defender, AosAttribute.DefendChance); + if (attackValue > 45) attackValue = 45; - if (Spells.Chivalry.DivineFurySpell.UnderEffect(defender)) - { - defenseValue -= 20; - } + attackValue = (atSkillValue + 20.0) * (100 + attackValue); - if (HitLower.IsUnderDefenseEffect(defender)) - { - defenseValue -= 25; - } + double defenseValue = AosAttributes.GetValue(defender, AosAttribute.DefendChance); - int refBonus = 0; + if (DivineFurySpell.UnderEffect(defender)) defenseValue -= 20; - if (Block.GetBonus(defender, ref refBonus)) - { - defenseValue += refBonus; - } + if (HitLower.IsUnderDefenseEffect(defender)) defenseValue -= 25; - if (SkillHandlers.Discordance.GetEffect(attacker, ref refBonus)) - { - defenseValue -= refBonus; - } + int refBonus = 0; - if (defenseValue > 45) - { - defenseValue = 45; - } + if (Block.GetBonus(defender, ref refBonus)) defenseValue += refBonus; - defenseValue = (defSkillValue + 20.0) * (100 + defenseValue); + if (Discordance.GetEffect(attacker, ref refBonus)) defenseValue -= refBonus; - double chance = attackValue / (defenseValue * 2.0); + if (defenseValue > 45) defenseValue = 45; - if (chance < 0.02) - { - chance = 0.02; - } + defenseValue = (defSkillValue + 20.0) * (100 + defenseValue); - return attacker.CheckSkill(atkSkill.SkillName, chance); - } + double chance = attackValue / (defenseValue * 2.0); - private static void OnHit(object[] states) - { - Mobile from = states[0] as Mobile; - Mobile target = states[1] as Mobile; - INinjaWeapon weapon = states[2] as INinjaWeapon; + if (chance < 0.02) chance = 0.02; - if (from.CanBeHarmful(target)) - { - from.DoHarmful(target); + return attacker.CheckSkill(atkSkill.SkillName, chance); + } - AOS.Damage(target, from, weapon.WeaponDamage, 100, 0, 0, 0, 0); + private static void OnHit(object[] states) + { + Mobile from = states[0] as Mobile; + Mobile target = states[1] as Mobile; + INinjaWeapon weapon = states[2] as INinjaWeapon; - if (weapon.Poison != null && weapon.PoisonCharges > 0) - { - if (EvilOmenSpell.TryEndEffect(target)) - { - target.ApplyPoison(from, Poison.GetPoison(weapon.Poison.Level + 1)); - } - else - { - target.ApplyPoison(from, weapon.Poison); - } + if (from.CanBeHarmful(target)) + { + from.DoHarmful(target); - weapon.PoisonCharges--; + AOS.Damage(target, from, weapon.WeaponDamage, 100, 0, 0, 0, 0); - if (weapon.PoisonCharges < 1) - { - weapon.Poison = null; - } - } - } - } + if (weapon.Poison != null && weapon.PoisonCharges > 0) + { + if (EvilOmenSpell.TryEndEffect(target)) + target.ApplyPoison(from, Poison.GetPoison(weapon.Poison.Level + 1)); + else + target.ApplyPoison(from, weapon.Poison); - private static void OnTarget(Mobile from, object targeted, INinjaWeapon weapon) - { - PlayerMobile player = from as PlayerMobile; + weapon.PoisonCharges--; - if (WeaponIsValid(weapon, from)) - { - if (targeted is Mobile mobile) - { - Shoot(player, mobile, weapon); - } - else if (targeted.GetType() == weapon.AmmoType) - { - Reload(player, weapon, (INinjaAmmo)targeted); - } - else - { - player.SendLocalizedMessage(weapon.WrongAmmoMessage); - } - } - } + if (weapon.PoisonCharges < 1) weapon.Poison = null; + } + } + } - private static bool WeaponIsValid(INinjaWeapon weapon, Mobile from) - { - Item item = weapon as Item; + private static void OnTarget(Mobile from, object targeted, INinjaWeapon weapon) + { + PlayerMobile player = from as PlayerMobile; - if (!item.Deleted && item.RootParent == from) - { - return true; - } - return false; - } + if (WeaponIsValid(weapon, from)) + { + if (targeted is Mobile mobile) + Shoot(player, mobile, weapon); + else if (targeted.GetType() == weapon.AmmoType) + Reload(player, weapon, (INinjaAmmo)targeted); + else + player.SendLocalizedMessage(weapon.WrongAmmoMessage); + } + } - public class LoadEntry : ContextMenuEntry - { - private INinjaWeapon weapon; + private static bool WeaponIsValid(INinjaWeapon weapon, Mobile from) + { + Item item = weapon as Item; - public LoadEntry(INinjaWeapon wep, int entry) - : base(entry, 0) - { - weapon = wep; - } + if (!item.Deleted && item.RootParent == from) return true; + return false; + } - public override void OnClick() - { - if (WeaponIsValid(weapon, Owner.From)) - { - Owner.From.BeginTarget(10, false, TargetFlags.Harmful, OnTarget, weapon); - } - } - } + public class LoadEntry : ContextMenuEntry + { + private INinjaWeapon weapon; - public class UnloadEntry : ContextMenuEntry - { - private INinjaWeapon weapon; + public LoadEntry(INinjaWeapon wep, int entry) + : base(entry, 0) + { + weapon = wep; + } - public UnloadEntry(INinjaWeapon wep, int entry) - : base(entry, 0) - { - weapon = wep; + public override void OnClick() + { + if (WeaponIsValid(weapon, Owner.From)) + Owner.From.BeginTarget(10, false, TargetFlags.Harmful, OnTarget, weapon); + } + } - Enabled = (weapon.UsesRemaining > 0); - } + public class UnloadEntry : ContextMenuEntry + { + private INinjaWeapon weapon; - public override void OnClick() - { - if (WeaponIsValid(weapon, Owner.From)) - { - Unload(Owner.From, weapon); - } - } - } - } -} + public UnloadEntry(INinjaWeapon wep, int entry) + : base(entry, 0) + { + weapon = wep; + + Enabled = weapon.UsesRemaining > 0; + } + + public override void OnClick() + { + if (WeaponIsValid(weapon, Owner.From)) Unload(Owner.From, weapon); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/Shuriken.cs b/Scripts/Items/Skill Items/Ninjitsu/Shuriken.cs index d0ecd0d58..bcb2cee93 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/Shuriken.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/Shuriken.cs @@ -3,103 +3,118 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x27AC, 0x27F7 )] - public class Shuriken : Item, ICraftable, INinjaAmmo - { - private int m_UsesRemaining; + [Flippable(0x27AC, 0x27F7)] + public class Shuriken : Item, ICraftable, INinjaAmmo + { + private Poison m_Poison; + private int m_PoisonCharges; + private int m_UsesRemaining; - private Poison m_Poison; - private int m_PoisonCharges; + [Constructible] + public Shuriken() : this(1) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + [Constructible] + public Shuriken(int amount) : base(0x27AC) + { + Weight = 1.0; - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison - { - get => m_Poison; - set{ m_Poison = value; InvalidateProperties(); } - } + m_UsesRemaining = amount; + } - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonCharges - { - get => m_PoisonCharges; - set { m_PoisonCharges = value; InvalidateProperties(); } - } + public Shuriken(Serial serial) : base(serial) + { + } - public bool ShowUsesRemaining{ get => true; - set{} } + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + if (quality == 2) + UsesRemaining *= 2; - [Constructible] - public Shuriken() : this( 1 ) - { - } + return quality; + } - [Constructible] - public Shuriken( int amount ) : base( 0x27AC ) - { - Weight = 1.0; + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - m_UsesRemaining = amount; - } + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison + { + get => m_Poison; + set + { + m_Poison = value; + InvalidateProperties(); + } + } - public Shuriken( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonCharges + { + get => m_PoisonCharges; + set + { + m_PoisonCharges = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public bool ShowUsesRemaining + { + get => true; + set { } + } - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_Poison != null && m_PoisonCharges > 0 ) - list.Add( 1062412 + m_Poison.Level, m_PoisonCharges.ToString() ); - } + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (m_Poison != null && m_PoisonCharges > 0) + list.Add(1062412 + m_Poison.Level, m_PoisonCharges.ToString()); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) m_UsesRemaining ); + writer.Write(0); // version - Poison.Serialize( m_Poison, writer ); - writer.Write( (int) m_PoisonCharges ); - } + writer.Write(m_UsesRemaining); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Poison.Serialize(m_Poison, writer); + writer.Write(m_PoisonCharges); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - m_UsesRemaining = reader.ReadInt(); + int version = reader.ReadInt(); - m_Poison = Poison.Deserialize( reader ); - m_PoisonCharges = reader.ReadInt(); + switch (version) + { + case 0: + { + m_UsesRemaining = reader.ReadInt(); - break; - } - } - } + m_Poison = Poison.Deserialize(reader); + m_PoisonCharges = reader.ReadInt(); - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - if ( quality == 2 ) - UsesRemaining *= 2; - - return quality; - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Ninjitsu/SmokeBomb.cs b/Scripts/Items/Skill Items/Ninjitsu/SmokeBomb.cs index cab146eba..f2254b1e5 100644 --- a/Scripts/Items/Skill Items/Ninjitsu/SmokeBomb.cs +++ b/Scripts/Items/Skill Items/Ninjitsu/SmokeBomb.cs @@ -1,70 +1,72 @@ +using Server.SkillHandlers; + namespace Server.Items { - public class SmokeBomb : Item - { - [Constructible] - public SmokeBomb() : base( 0x2808 ) - { - Stackable = Core.ML; - Weight = 1.0; - } + public class SmokeBomb : Item + { + [Constructible] + public SmokeBomb() : base(0x2808) + { + Stackable = Core.ML; + Weight = 1.0; + } - public SmokeBomb( Serial serial ) : base( serial ) - { - } + public SmokeBomb(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - // The item must be in your backpack to use it. - from.SendLocalizedMessage( 1060640 ); - } - else if ( from.Skills.Ninjitsu.Value < 50.0 ) - { - // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - from.SendLocalizedMessage( 1063013, "50\tNinjitsu" ); - } - else if (Core.TickCount - from.NextSkillTime < 0) - { - // You must wait a few seconds before you can use that item. - from.SendLocalizedMessage( 1070772 ); - } - else if ( from.Mana < 10 ) - { - // You don't have enough mana to do that. - from.SendLocalizedMessage( 1049456 ); - } - else - { - SkillHandlers.Hiding.CombatOverride = true; + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + // The item must be in your backpack to use it. + from.SendLocalizedMessage(1060640); + } + else if (from.Skills.Ninjitsu.Value < 50.0) + { + // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + from.SendLocalizedMessage(1063013, "50\tNinjitsu"); + } + else if (Core.TickCount - from.NextSkillTime < 0) + { + // You must wait a few seconds before you can use that item. + from.SendLocalizedMessage(1070772); + } + else if (from.Mana < 10) + { + // You don't have enough mana to do that. + from.SendLocalizedMessage(1049456); + } + else + { + Hiding.CombatOverride = true; - if ( from.UseSkill( SkillName.Hiding ) ) - { - from.Mana -= 10; + if (from.UseSkill(SkillName.Hiding)) + { + from.Mana -= 10; - from.FixedParticles( 0x3709, 1, 30, 9904, 1108, 6, EffectLayer.RightFoot ); - from.PlaySound( 0x22F ); + from.FixedParticles(0x3709, 1, 30, 9904, 1108, 6, EffectLayer.RightFoot); + from.PlaySound(0x22F); - Consume(); - } + Consume(); + } - SkillHandlers.Hiding.CombatOverride = false; - } - } + Hiding.CombatOverride = false; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Specialized/GlassblowingBook.cs b/Scripts/Items/Skill Items/Specialized/GlassblowingBook.cs index 4faeb4339..8757df7df 100644 --- a/Scripts/Items/Skill Items/Specialized/GlassblowingBook.cs +++ b/Scripts/Items/Skill Items/Specialized/GlassblowingBook.cs @@ -2,56 +2,57 @@ using Server.Mobiles; namespace Server.Items { - public class GlassblowingBook : Item - { - public override string DefaultName => "Crafting Glass With Glassblowing"; + public class GlassblowingBook : Item + { + [Constructible] + public GlassblowingBook() : base(0xFF4) + { + Weight = 1.0; + } - [Constructible] - public GlassblowingBook() : base( 0xFF4 ) - { - Weight = 1.0; - } + public GlassblowingBook(Serial serial) : base(serial) + { + } - public GlassblowingBook( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Crafting Glass With Glassblowing"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - PlayerMobile pm = from as PlayerMobile; + public override void OnDoubleClick(Mobile from) + { + PlayerMobile pm = from as PlayerMobile; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( pm == null || from.Skills[SkillName.Alchemy].Base < 100.0 ) - { - pm.SendMessage( "Only a Grandmaster Alchemist can learn from this book." ); - } - else if ( pm.Glassblowing ) - { - pm.SendMessage( "You have already learned this information." ); - } - else - { - pm.Glassblowing = true; - pm.SendMessage( "You have learned to make items from glass. You will need to find miners to mine find sand for you to make these items." ); - Delete(); - } - } - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (pm == null || from.Skills[SkillName.Alchemy].Base < 100.0) + { + pm.SendMessage("Only a Grandmaster Alchemist can learn from this book."); + } + else if (pm.Glassblowing) + { + pm.SendMessage("You have already learned this information."); + } + else + { + pm.Glassblowing = true; + pm.SendMessage( + "You have learned to make items from glass. You will need to find miners to mine find sand for you to make these items."); + Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Specialized/MasonryBook.cs b/Scripts/Items/Skill Items/Specialized/MasonryBook.cs index 1558e8a21..05bd2acb7 100644 --- a/Scripts/Items/Skill Items/Specialized/MasonryBook.cs +++ b/Scripts/Items/Skill Items/Specialized/MasonryBook.cs @@ -2,56 +2,57 @@ using Server.Mobiles; namespace Server.Items { - public class MasonryBook : Item - { - public override string DefaultName => "Making Valuables With Stonecrafting"; + public class MasonryBook : Item + { + [Constructible] + public MasonryBook() : base(0xFBE) + { + Weight = 1.0; + } - [Constructible] - public MasonryBook() : base( 0xFBE ) - { - Weight = 1.0; - } + public MasonryBook(Serial serial) : base(serial) + { + } - public MasonryBook( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Making Valuables With Stonecrafting"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - PlayerMobile pm = from as PlayerMobile; + public override void OnDoubleClick(Mobile from) + { + PlayerMobile pm = from as PlayerMobile; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( pm == null || from.Skills[SkillName.Carpentry].Base < 100.0 ) - { - pm.SendMessage( "Only a Grandmaster Carpenter can learn from this book." ); - } - else if ( pm.Masonry ) - { - pm.SendMessage( "You have already learned this information." ); - } - else - { - pm.Masonry = true; - pm.SendMessage( "You have learned to make items from stone. You will need miners to gather stones for you to make these items." ); - Delete(); - } - } - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (pm == null || from.Skills[SkillName.Carpentry].Base < 100.0) + { + pm.SendMessage("Only a Grandmaster Carpenter can learn from this book."); + } + else if (pm.Masonry) + { + pm.SendMessage("You have already learned this information."); + } + else + { + pm.Masonry = true; + pm.SendMessage( + "You have learned to make items from stone. You will need miners to gather stones for you to make these items."); + Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Specialized/Sand.cs b/Scripts/Items/Skill Items/Specialized/Sand.cs index df7c04b97..d2d4dfbcc 100644 --- a/Scripts/Items/Skill Items/Specialized/Sand.cs +++ b/Scripts/Items/Skill Items/Specialized/Sand.cs @@ -1,44 +1,43 @@ namespace Server.Items { - [FlippableAttribute( 0x11EA, 0x11EB )] - public class Sand : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => true; + [Flippable(0x11EA, 0x11EB)] + public class Sand : Item, ICommodity + { + [Constructible] + public Sand() : this(1) + { + } - public override int LabelNumber => 1044626; // sand + [Constructible] + public Sand(int amount) : base(0x11EA) + { + Stackable = Core.ML; + Weight = 1.0; + } - [Constructible] - public Sand() : this( 1 ) - { - } + public Sand(Serial serial) : base(serial) + { + } - [Constructible] - public Sand( int amount ) : base( 0x11EA ) - { - Stackable = Core.ML; - Weight = 1.0; - } + public override int LabelNumber => 1044626; // sand + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => true; - public Sand( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(1); // version + } - writer.Write( (int) 1 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); - int version = reader.ReadInt(); - - if ( version == 0 && Name == "sand" ) - Name = null; - } - } -} + if (version == 0 && Name == "sand") + Name = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Specialized/SandMiningBook.cs b/Scripts/Items/Skill Items/Specialized/SandMiningBook.cs index 785474b92..9e3927abb 100644 --- a/Scripts/Items/Skill Items/Specialized/SandMiningBook.cs +++ b/Scripts/Items/Skill Items/Specialized/SandMiningBook.cs @@ -2,56 +2,57 @@ using Server.Mobiles; namespace Server.Items { - public class SandMiningBook : Item - { - public override string DefaultName => "Find Glass-Quality Sand"; + public class SandMiningBook : Item + { + [Constructible] + public SandMiningBook() : base(0xFF4) + { + Weight = 1.0; + } - [Constructible] - public SandMiningBook() : base( 0xFF4 ) - { - Weight = 1.0; - } + public SandMiningBook(Serial serial) : base(serial) + { + } - public SandMiningBook( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Find Glass-Quality Sand"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - PlayerMobile pm = from as PlayerMobile; + public override void OnDoubleClick(Mobile from) + { + PlayerMobile pm = from as PlayerMobile; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( pm == null || from.Skills[SkillName.Mining].Base < 100.0 ) - { - pm.SendMessage( "Only a Grandmaster Miner can learn from this book." ); - } - else if ( pm.SandMining ) - { - pm.SendMessage( "You have already learned this information." ); - } - else - { - pm.SandMining = true; - pm.SendMessage( "You have learned how to mine fine sand. Target sand areas when mining to look for fine sand." ); - Delete(); - } - } - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (pm == null || from.Skills[SkillName.Mining].Base < 100.0) + { + pm.SendMessage("Only a Grandmaster Miner can learn from this book."); + } + else if (pm.SandMining) + { + pm.SendMessage("You have already learned this information."); + } + else + { + pm.SandMining = true; + pm.SendMessage( + "You have learned how to mine fine sand. Target sand areas when mining to look for fine sand."); + Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Specialized/StoneMiningBook.cs b/Scripts/Items/Skill Items/Specialized/StoneMiningBook.cs index 7ee9ec107..e8fe5a2b8 100644 --- a/Scripts/Items/Skill Items/Specialized/StoneMiningBook.cs +++ b/Scripts/Items/Skill Items/Specialized/StoneMiningBook.cs @@ -2,56 +2,56 @@ using Server.Mobiles; namespace Server.Items { - public class StoneMiningBook : Item - { - public override string DefaultName => "Mining For Quality Stone"; + public class StoneMiningBook : Item + { + [Constructible] + public StoneMiningBook() : base(0xFBE) + { + Weight = 1.0; + } - [Constructible] - public StoneMiningBook() : base( 0xFBE ) - { - Weight = 1.0; - } + public StoneMiningBook(Serial serial) : base(serial) + { + } - public StoneMiningBook( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Mining For Quality Stone"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - PlayerMobile pm = from as PlayerMobile; + public override void OnDoubleClick(Mobile from) + { + PlayerMobile pm = from as PlayerMobile; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( pm == null || from.Skills[SkillName.Mining].Base < 100.0 ) - { - from.SendMessage( "Only a Grandmaster Miner can learn from this book." ); - } - else if ( pm.StoneMining ) - { - pm.SendMessage( "You have already learned this knowledge." ); - } - else - { - pm.StoneMining = true; - pm.SendMessage( "You have learned to mine for stones. Target mountains when mining to find stones." ); - Delete(); - } - } - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (pm == null || from.Skills[SkillName.Mining].Base < 100.0) + { + from.SendMessage("Only a Grandmaster Miner can learn from this book."); + } + else if (pm.StoneMining) + { + pm.SendMessage("You have already learned this knowledge."); + } + else + { + pm.StoneMining = true; + pm.SendMessage("You have learned to mine for stones. Target mountains when mining to find stones."); + Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlackDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlackDyeTub.cs index 66c6ff0b4..bde1010e7 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlackDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlackDyeTub.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class BlackDyeTub : DyeTub - { - [Constructible] - public BlackDyeTub() - { - Hue = DyedHue = 0x0001; - Redyable = false; - } + public class BlackDyeTub : DyeTub + { + [Constructible] + public BlackDyeTub() + { + Hue = DyedHue = 0x0001; + Redyable = false; + } - public BlackDyeTub( Serial serial ) : base( serial ) - { - } + public BlackDyeTub(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlazeDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlazeDyeTub.cs index f7245794a..8df655537 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlazeDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/BlazeDyeTub.cs @@ -1,30 +1,30 @@ namespace Server.Items { - public class BlazeDyeTub : DyeTub - { - [Constructible] - public BlazeDyeTub() - { - Hue = DyedHue = 0x489; - Redyable = false; - } + public class BlazeDyeTub : DyeTub + { + [Constructible] + public BlazeDyeTub() + { + Hue = DyedHue = 0x489; + Redyable = false; + } - public BlazeDyeTub( Serial serial ) : base( serial ) - { - } + public BlazeDyeTub(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/CustomHuePicker.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/CustomHuePicker.cs index 52fadb5b8..287b29287 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/CustomHuePicker.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/CustomHuePicker.cs @@ -3,215 +3,216 @@ using Server.Network; namespace Server.Items { - public class CustomHueGroup - { - public int Name { get; } + public class CustomHueGroup + { + public CustomHueGroup(int name, int[] hues) + { + Name = name; + Hues = hues; + } - public string NameString { get; } + public CustomHueGroup(string name, int[] hues) + { + NameString = name; + Hues = hues; + } - public int[] Hues { get; } + public int Name{ get; } - public CustomHueGroup( int name, int[] hues ) - { - Name = name; - Hues = hues; - } + public string NameString{ get; } - public CustomHueGroup( string name, int[] hues ) - { - NameString = name; - Hues = hues; - } - } + public int[] Hues{ get; } + } - public class CustomHuePicker - { - public bool DefaultSupported { get; } + public class CustomHuePicker + { + public static readonly CustomHuePicker SpecialDyeTub = new CustomHuePicker(new[] + { + /* Violet */ + new CustomHueGroup(1018345, new[] { 1230, 1231, 1232, 1233, 1234, 1235 }), + /* Tan */ + new CustomHueGroup(1018346, new[] { 1501, 1502, 1503, 1504, 1505, 1506, 1507, 1508 }), + /* Brown */ + new CustomHueGroup(1018347, new[] { 2012, 2013, 2014, 2015, 2016, 2017 }), + /* Dark Blue */ + new CustomHueGroup(1018348, new[] { 1303, 1304, 1305, 1306, 1307, 1308 }), + /* Forest Green */ + new CustomHueGroup(1018349, new[] { 1420, 1421, 1422, 1423, 1424, 1425, 1426 }), + /* Pink */ + new CustomHueGroup(1018350, new[] { 1619, 1620, 1621, 1622, 1623, 1624, 1625, 1626 }), + /* Red */ + new CustomHueGroup(1018351, new[] { 1640, 1641, 1642, 1643, 1644 }), + /* Olive */ + new CustomHueGroup(1018352, new[] { 2001, 2002, 2003, 2004, 2005 }) + }, false, 1018344); - public CustomHueGroup[] Groups { get; } + public static readonly CustomHuePicker LeatherDyeTub = new CustomHuePicker(new[] + { + /* Dull Copper */ + new CustomHueGroup(1018332, new[] { 2419, 2420, 2421, 2422, 2423, 2424 }), + /* Shadow Iron */ + new CustomHueGroup(1018333, new[] { 2406, 2407, 2408, 2409, 2410, 2411, 2412 }), + /* Copper */ + new CustomHueGroup(1018334, new[] { 2413, 2414, 2415, 2416, 2417, 2418 }), + /* Bronze */ + new CustomHueGroup(1018335, new[] { 2414, 2415, 2416, 2417, 2418 }), + /* Glden */ + new CustomHueGroup(1018336, new[] { 2213, 2214, 2215, 2216, 2217, 2218 }), + /* Agapite */ + new CustomHueGroup(1018337, new[] { 2425, 2426, 2427, 2428, 2429, 2430 }), + /* Verite */ + new CustomHueGroup(1018338, new[] { 2207, 2208, 2209, 2210, 2211, 2212 }), + /* Valorite */ + new CustomHueGroup(1018339, new[] { 2219, 2220, 2221, 2222, 2223, 2224 }), + /* Reds */ + new CustomHueGroup(1018340, new[] { 2113, 2114, 2115, 2116, 2117, 2118 }), + /* Blues */ + new CustomHueGroup(1018341, new[] { 2119, 2120, 2121, 2122, 2123, 2124 }), + /* Greens */ + new CustomHueGroup(1018342, new[] { 2126, 2127, 2128, 2129, 2130 }), + /* Yellows */ + new CustomHueGroup(1018343, new[] { 2213, 2214, 2215, 2216, 2217, 2218 }) + }, true); - public int Title { get; } + public CustomHuePicker(CustomHueGroup[] groups, bool defaultSupported) + { + Groups = groups; + DefaultSupported = defaultSupported; + } - public string TitleString { get; } + public CustomHuePicker(CustomHueGroup[] groups, bool defaultSupported, int title) + { + Groups = groups; + DefaultSupported = defaultSupported; + Title = title; + } - public CustomHuePicker( CustomHueGroup[] groups, bool defaultSupported ) - { - Groups = groups; - DefaultSupported = defaultSupported; - } + public CustomHuePicker(CustomHueGroup[] groups, bool defaultSupported, string title) + { + Groups = groups; + DefaultSupported = defaultSupported; + TitleString = title; + } - public CustomHuePicker( CustomHueGroup[] groups, bool defaultSupported, int title ) - { - Groups = groups; - DefaultSupported = defaultSupported; - Title = title; - } + public bool DefaultSupported{ get; } - public CustomHuePicker( CustomHueGroup[] groups, bool defaultSupported, string title ) - { - Groups = groups; - DefaultSupported = defaultSupported; - TitleString = title; - } + public CustomHueGroup[] Groups{ get; } - public static readonly CustomHuePicker SpecialDyeTub = new CustomHuePicker( new[] - { - /* Violet */ - new CustomHueGroup( 1018345, new[]{ 1230, 1231, 1232, 1233, 1234, 1235 } ), - /* Tan */ - new CustomHueGroup( 1018346, new[]{ 1501, 1502, 1503, 1504, 1505, 1506, 1507, 1508 } ), - /* Brown */ - new CustomHueGroup( 1018347, new[]{ 2012, 2013, 2014, 2015, 2016, 2017 } ), - /* Dark Blue */ - new CustomHueGroup( 1018348, new[]{ 1303, 1304, 1305, 1306, 1307, 1308 } ), - /* Forest Green */ - new CustomHueGroup( 1018349, new[]{ 1420, 1421, 1422, 1423, 1424, 1425, 1426 } ), - /* Pink */ - new CustomHueGroup( 1018350, new[]{ 1619, 1620, 1621, 1622, 1623, 1624, 1625, 1626 } ), - /* Red */ - new CustomHueGroup( 1018351, new[]{ 1640, 1641, 1642, 1643, 1644 } ), - /* Olive */ - new CustomHueGroup( 1018352, new[]{ 2001, 2002, 2003, 2004, 2005 } ) - }, false, 1018344 ); + public int Title{ get; } - public static readonly CustomHuePicker LeatherDyeTub = new CustomHuePicker( new[] - { - /* Dull Copper */ - new CustomHueGroup( 1018332, new[]{ 2419, 2420, 2421, 2422, 2423, 2424 } ), - /* Shadow Iron */ - new CustomHueGroup( 1018333, new[]{ 2406, 2407, 2408, 2409, 2410, 2411, 2412 } ), - /* Copper */ - new CustomHueGroup( 1018334, new[]{ 2413, 2414, 2415, 2416, 2417, 2418 } ), - /* Bronze */ - new CustomHueGroup( 1018335, new[]{ 2414, 2415, 2416, 2417, 2418 } ), - /* Glden */ - new CustomHueGroup( 1018336, new[]{ 2213, 2214, 2215, 2216, 2217, 2218 } ), - /* Agapite */ - new CustomHueGroup( 1018337, new[]{ 2425, 2426, 2427, 2428, 2429, 2430 } ), - /* Verite */ - new CustomHueGroup( 1018338, new[]{ 2207, 2208, 2209, 2210, 2211, 2212 } ), - /* Valorite */ - new CustomHueGroup( 1018339, new[]{ 2219, 2220, 2221, 2222, 2223, 2224 } ), - /* Reds */ - new CustomHueGroup( 1018340, new[]{ 2113, 2114, 2115, 2116, 2117, 2118 } ), - /* Blues */ - new CustomHueGroup( 1018341, new[]{ 2119, 2120, 2121, 2122, 2123, 2124 } ), - /* Greens */ - new CustomHueGroup( 1018342, new[]{ 2126, 2127, 2128, 2129, 2130 } ), - /* Yellows */ - new CustomHueGroup( 1018343, new[]{ 2213, 2214, 2215, 2216, 2217, 2218 } ) - }, true ); - } + public string TitleString{ get; } + } - public delegate void CustomHuePickerCallback( Mobile from, object state, int hue ); + public delegate void CustomHuePickerCallback(Mobile from, object state, int hue); - public class CustomHuePickerGump : Gump - { - private Mobile m_From; - private CustomHuePicker m_Definition; - private CustomHuePickerCallback m_Callback; - private object m_State; + public class CustomHuePickerGump : Gump + { + private CustomHuePickerCallback m_Callback; + private CustomHuePicker m_Definition; + private Mobile m_From; + private object m_State; - private int GetRadioID( int group, int index ) - { - return (index * m_Definition.Groups.Length) + group; - } + public CustomHuePickerGump(Mobile from, CustomHuePicker definition, CustomHuePickerCallback callback, object state) : + base(50, 50) + { + m_From = from; + m_Definition = definition; + m_Callback = callback; + m_State = state; - private void RenderBackground() - { - AddPage( 0 ); + RenderBackground(); + RenderCategories(); + } - AddBackground( 0, 0, 450, 450, 5054 ); - AddBackground( 10, 10, 430, 430, 3000 ); + private int GetRadioID(int group, int index) + { + return index * m_Definition.Groups.Length + group; + } - if ( m_Definition.TitleString != null ) - AddHtml( 20, 30, 400, 25, m_Definition.TitleString, false, false ); - else if ( m_Definition.Title > 0 ) - AddHtmlLocalized( 20, 30, 400, 25, m_Definition.Title, false, false ); + private void RenderBackground() + { + AddPage(0); - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 400, 200, 25, 1011036, false, false ); // OKAY + AddBackground(0, 0, 450, 450, 5054); + AddBackground(10, 10, 430, 430, 3000); - if ( m_Definition.DefaultSupported ) - { - AddButton( 200, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddLabel( 235, 400, 0, "DEFAULT" ); - } - } + if (m_Definition.TitleString != null) + AddHtml(20, 30, 400, 25, m_Definition.TitleString, false, false); + else if (m_Definition.Title > 0) + AddHtmlLocalized(20, 30, 400, 25, m_Definition.Title, false, false); - private void RenderCategories() - { - CustomHueGroup[] groups = m_Definition.Groups; + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 400, 200, 25, 1011036, false, false); // OKAY - for ( int i = 0; i < groups.Length; ++i ) - { - AddButton( 30, 85 + (i * 25), 5224, 5224, 0, GumpButtonType.Page, 1 + i ); + if (m_Definition.DefaultSupported) + { + AddButton(200, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddLabel(235, 400, 0, "DEFAULT"); + } + } - if ( groups[i].NameString != null ) - AddHtml( 55, 85 + (i * 25), 200, 25, groups[i].NameString, false, false ); - else - AddHtmlLocalized( 55, 85 + (i * 25), 200, 25, groups[i].Name, false, false ); - } + private void RenderCategories() + { + CustomHueGroup[] groups = m_Definition.Groups; - for ( int i = 0; i < groups.Length; ++i ) - { - AddPage( 1 + i ); + for (int i = 0; i < groups.Length; ++i) + { + AddButton(30, 85 + i * 25, 5224, 5224, 0, GumpButtonType.Page, 1 + i); - int[] hues = groups[i].Hues; + if (groups[i].NameString != null) + AddHtml(55, 85 + i * 25, 200, 25, groups[i].NameString, false, false); + else + AddHtmlLocalized(55, 85 + i * 25, 200, 25, groups[i].Name, false, false); + } - for ( int j = 0; j < hues.Length; ++j ) - { - AddRadio( 260, 90 + (j * 25), 210, 211, false, GetRadioID( i, j ) ); - AddLabel( 278, 90 + (j * 25), hues[j] - 1, "*****" ); - } - } - } + for (int i = 0; i < groups.Length; ++i) + { + AddPage(1 + i); - public CustomHuePickerGump( Mobile from, CustomHuePicker definition, CustomHuePickerCallback callback, object state ) : base( 50, 50 ) - { - m_From = from; - m_Definition = definition; - m_Callback = callback; - m_State = state; + int[] hues = groups[i].Hues; - RenderBackground(); - RenderCategories(); - } + for (int j = 0; j < hues.Length; ++j) + { + AddRadio(260, 90 + j * 25, 210, 211, false, GetRadioID(i, j)); + AddLabel(278, 90 + j * 25, hues[j] - 1, "*****"); + } + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 1: // Okay - { - int[] switches = info.Switches; + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: // Okay + { + int[] switches = info.Switches; - if ( switches.Length > 0 ) - { - int index = switches[0]; + if (switches.Length > 0) + { + int index = switches[0]; - int group = index % m_Definition.Groups.Length; - index /= m_Definition.Groups.Length; + int group = index % m_Definition.Groups.Length; + index /= m_Definition.Groups.Length; - if ( group >= 0 && group < m_Definition.Groups.Length ) - { - int[] hues = m_Definition.Groups[group].Hues; + if (group >= 0 && group < m_Definition.Groups.Length) + { + int[] hues = m_Definition.Groups[group].Hues; - if ( index >= 0 && index < hues.Length ) - m_Callback( m_From, m_State, hues[index] ); - } - } + if (index >= 0 && index < hues.Length) + m_Callback(m_From, m_State, hues[index]); + } + } - break; - } - case 2: // Default - { - if ( m_Definition.DefaultSupported ) - m_Callback( m_From, m_State, 0 ); + break; + } + case 2: // Default + { + if (m_Definition.DefaultSupported) + m_Callback(m_From, m_State, 0); - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/DyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/DyeTub.cs index cad02af27..5f22a828f 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/DyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/DyeTub.cs @@ -1,254 +1,258 @@ using System.Collections.Generic; -using Server.Multis; -using Server.Targeting; using Server.ContextMenus; using Server.Gumps; +using Server.Multis; +using Server.Targeting; namespace Server.Items { - public interface IDyable - { - bool Dye( Mobile from, DyeTub sender ); - } + public interface IDyable + { + bool Dye(Mobile from, DyeTub sender); + } - public class DyeTub : Item, ISecurable - { - private bool m_Redyable; - private int m_DyedHue; + public class DyeTub : Item, ISecurable + { + private int m_DyedHue; + private bool m_Redyable; - public virtual CustomHuePicker CustomHuePicker => null; + [Constructible] + public DyeTub() : base(0xFAB) + { + Weight = 10.0; + m_Redyable = true; + } - public virtual bool AllowRunebooks => false; + public DyeTub(Serial serial) : base(serial) + { + } - public virtual bool AllowFurniture => false; + public virtual CustomHuePicker CustomHuePicker => null; - public virtual bool AllowStatuettes => false; + public virtual bool AllowRunebooks => false; - public virtual bool AllowLeather => false; + public virtual bool AllowFurniture => false; - public virtual bool AllowDyables => true; + public virtual bool AllowStatuettes => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public virtual bool AllowLeather => false; - writer.Write( (int) 1 ); // version + public virtual bool AllowDyables => true; - writer.Write( (int)Level ); - writer.Write( (bool) m_Redyable ); - writer.Write( (int) m_DyedHue ); - } + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool Redyable + { + get => m_Redyable; + set => m_Redyable = value; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [CommandProperty(AccessLevel.GameMaster)] + public int DyedHue + { + get => m_DyedHue; + set + { + if (m_Redyable) + { + m_DyedHue = value; + Hue = value; + } + } + } - int version = reader.ReadInt(); + // Three metallic tubs now. + public virtual bool MetallicHues => false; - switch ( version ) - { - case 1: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 0; - } - case 0: - { - m_Redyable = reader.ReadBool(); - m_DyedHue = reader.ReadInt(); + // Select the clothing to dye. + public virtual int TargetMessage => 500859; - break; - } - } - } + // You can not dye that. + public virtual int FailMessage => 1042083; - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool Redyable - { - get => m_Redyable; - set => m_Redyable = value; - } + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int DyedHue - { - get => m_DyedHue; - set - { - if ( m_Redyable ) - { - m_DyedHue = value; - Hue = value; - } - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + writer.Write(1); // version - [Constructible] - public DyeTub() : base( 0xFAB ) - { - Weight = 10.0; - m_Redyable = true; - } + writer.Write((int)Level); + writer.Write(m_Redyable); + writer.Write(m_DyedHue); + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public DyeTub( Serial serial ) : base( serial ) - { - } + int version = reader.ReadInt(); - // Three metallic tubs now. - public virtual bool MetallicHues => false; + switch (version) + { + case 1: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 0; + } + case 0: + { + m_Redyable = reader.ReadBool(); + m_DyedHue = reader.ReadInt(); - // Select the clothing to dye. - public virtual int TargetMessage => 500859; + break; + } + } + } - // You can not dye that. - public virtual int FailMessage => 1042083; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( TargetMessage ); - from.Target = new InternalTarget( this ); - } - else - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(TargetMessage); + from.Target = new InternalTarget(this); + } + else + { + from.SendLocalizedMessage(500446); // That is too far away. + } + } - private class InternalTarget : Target - { - private DyeTub m_Tub; + private class InternalTarget : Target + { + private DyeTub m_Tub; - public InternalTarget( DyeTub tub ) : base( 1, false, TargetFlags.None ) - { - m_Tub = tub; - } + public InternalTarget(DyeTub tub) : base(1, false, TargetFlags.None) + { + m_Tub = tub; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Item item ) - { - if ( item.QuestItem ) - { - from.SendLocalizedMessage( 1151836 ); // You may not dye toggled quest items. - } - else if ( item is IDyable dyable && m_Tub.AllowDyables ) - { - if ( !from.InRange( m_Tub.GetWorldLocation(), 1 ) || !from.InRange( item.GetWorldLocation(), 1 ) ) - from.SendLocalizedMessage( 500446 ); // That is too far away. - else if ( item.Parent is Mobile ) - from.SendLocalizedMessage( 500861 ); // Can't Dye clothing that is being worn. - else if ( dyable.Dye( from, m_Tub ) ) - from.PlaySound( 0x23E ); - } - else if ( (FurnitureAttribute.Check( item ) || (item is PotionKeg)) && m_Tub.AllowFurniture ) - { - if ( !from.InRange( m_Tub.GetWorldLocation(), 1 ) || !from.InRange( item.GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else - { - bool okay = ( item.IsChildOf( from.Backpack ) ); + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Item item) + { + if (item.QuestItem) + { + from.SendLocalizedMessage(1151836); // You may not dye toggled quest items. + } + else if (item is IDyable dyable && m_Tub.AllowDyables) + { + if (!from.InRange(m_Tub.GetWorldLocation(), 1) || !from.InRange(item.GetWorldLocation(), 1)) + from.SendLocalizedMessage(500446); // That is too far away. + else if (item.Parent is Mobile) + from.SendLocalizedMessage(500861); // Can't Dye clothing that is being worn. + else if (dyable.Dye(from, m_Tub)) + from.PlaySound(0x23E); + } + else if ((FurnitureAttribute.Check(item) || item is PotionKeg) && m_Tub.AllowFurniture) + { + if (!from.InRange(m_Tub.GetWorldLocation(), 1) || !from.InRange(item.GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else + { + bool okay = item.IsChildOf(from.Backpack); - if ( !okay ) - { - if ( item.Parent == null ) - { - BaseHouse house = BaseHouse.FindHouseAt( item ); + if (!okay) + { + if (item.Parent == null) + { + BaseHouse house = BaseHouse.FindHouseAt(item); - if ( house == null || ( !house.IsLockedDown( item ) && !house.IsSecure( item ) ) ) - from.SendLocalizedMessage( 501022 ); // Furniture must be locked down to paint it. - else if ( !house.IsCoOwner( from ) ) - from.SendLocalizedMessage( 501023 ); // You must be the owner to use this item. - else - okay = true; - } - else - { - from.SendLocalizedMessage( 1048135 ); // The furniture must be in your backpack to be painted. - } - } + if (house == null || !house.IsLockedDown(item) && !house.IsSecure(item)) + from.SendLocalizedMessage(501022); // Furniture must be locked down to paint it. + else if (!house.IsCoOwner(from)) + from.SendLocalizedMessage(501023); // You must be the owner to use this item. + else + okay = true; + } + else + { + from.SendLocalizedMessage( + 1048135); // The furniture must be in your backpack to be painted. + } + } - if ( okay ) - { - item.Hue = m_Tub.DyedHue; - from.PlaySound( 0x23E ); - } - } - } - else if ( (item is Runebook || item is RecallRune ) && m_Tub.AllowRunebooks ) - { - if ( !from.InRange( m_Tub.GetWorldLocation(), 1 ) || !from.InRange( item.GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( !item.Movable ) - { - from.SendLocalizedMessage( 1049776 ); // You cannot dye runes or runebooks that are locked down. - } - else - { - item.Hue = m_Tub.DyedHue; - from.PlaySound( 0x23E ); - } - } - else if ( item is MonsterStatuette && m_Tub.AllowStatuettes ) - { - if ( !from.InRange( m_Tub.GetWorldLocation(), 1 ) || !from.InRange( item.GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( !item.Movable ) - { - from.SendLocalizedMessage( 1049779 ); // You cannot dye statuettes that are locked down. - } - else - { - item.Hue = m_Tub.DyedHue; - from.PlaySound( 0x23E ); - } - } - else if ( (item is BaseArmor armor && (armor.MaterialType == ArmorMaterialType.Leather || armor.MaterialType == ArmorMaterialType.Studded) || item is ElvenBoots || item is WoodlandBelt) && m_Tub.AllowLeather ) - { - if ( !from.InRange( m_Tub.GetWorldLocation(), 1 ) || !from.InRange( item.GetWorldLocation(), 1 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( !item.Movable ) - { - from.SendLocalizedMessage( 1042419 ); // You may not dye leather items which are locked down. - } - else if ( item.Parent is Mobile ) - { - from.SendLocalizedMessage( 500861 ); // Can't Dye clothing that is being worn. - } - else - { - item.Hue = m_Tub.DyedHue; - from.PlaySound( 0x23E ); - } - } - else - { - from.SendLocalizedMessage( m_Tub.FailMessage ); - } - } - else - { - from.SendLocalizedMessage( m_Tub.FailMessage ); - } - } - } - } -} + if (okay) + { + item.Hue = m_Tub.DyedHue; + from.PlaySound(0x23E); + } + } + } + else if ((item is Runebook || item is RecallRune) && m_Tub.AllowRunebooks) + { + if (!from.InRange(m_Tub.GetWorldLocation(), 1) || !from.InRange(item.GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (!item.Movable) + { + from.SendLocalizedMessage(1049776); // You cannot dye runes or runebooks that are locked down. + } + else + { + item.Hue = m_Tub.DyedHue; + from.PlaySound(0x23E); + } + } + else if (item is MonsterStatuette && m_Tub.AllowStatuettes) + { + if (!from.InRange(m_Tub.GetWorldLocation(), 1) || !from.InRange(item.GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (!item.Movable) + { + from.SendLocalizedMessage(1049779); // You cannot dye statuettes that are locked down. + } + else + { + item.Hue = m_Tub.DyedHue; + from.PlaySound(0x23E); + } + } + else if ((item is BaseArmor armor && + (armor.MaterialType == ArmorMaterialType.Leather || + armor.MaterialType == ArmorMaterialType.Studded) || item is ElvenBoots || + item is WoodlandBelt) && m_Tub.AllowLeather) + { + if (!from.InRange(m_Tub.GetWorldLocation(), 1) || !from.InRange(item.GetWorldLocation(), 1)) + { + from.SendLocalizedMessage(500446); // That is too far away. + } + else if (!item.Movable) + { + from.SendLocalizedMessage(1042419); // You may not dye leather items which are locked down. + } + else if (item.Parent is Mobile) + { + from.SendLocalizedMessage(500861); // Can't Dye clothing that is being worn. + } + else + { + item.Hue = m_Tub.DyedHue; + from.PlaySound(0x23E); + } + } + else + { + from.SendLocalizedMessage(m_Tub.FailMessage); + } + } + else + { + from.SendLocalizedMessage(m_Tub.FailMessage); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/FurnitureDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/FurnitureDyeTub.cs index 0cc06a033..4a28a7d32 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/FurnitureDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/FurnitureDyeTub.cs @@ -1,68 +1,70 @@ +using Server.Engines.VeteranRewards; + namespace Server.Items { - public class FurnitureDyeTub : DyeTub, Engines.VeteranRewards.IRewardItem - { - public override bool AllowDyables => false; - public override bool AllowFurniture => true; - public override int TargetMessage => 501019; // Select the furniture to dye. - public override int FailMessage => 501021; // That is not a piece of furniture. - public override int LabelNumber => 1041246; // Furniture Dye Tub + public class FurnitureDyeTub : DyeTub, IRewardItem + { + [Constructible] + public FurnitureDyeTub() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + public FurnitureDyeTub(Serial serial) : base(serial) + { + } - [Constructible] - public FurnitureDyeTub() - { - LootType = LootType.Blessed; - } + public override bool AllowDyables => false; + public override bool AllowFurniture => true; + public override int TargetMessage => 501019; // Select the furniture to dye. + public override int FailMessage => 501021; // That is not a piece of furniture. + public override int LabelNumber => 1041246; // Furniture Dye Tub - public override void OnDoubleClick( Mobile from ) - { - if ( IsRewardItem && !Engines.VeteranRewards.RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public FurnitureDyeTub( Serial serial ) : base( serial ) - { - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076217 ); // 1st Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076217); // 1st Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (bool) IsRewardItem ); - } + writer.Write(IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - IsRewardItem = reader.ReadBool(); - break; - } - } + switch (version) + { + case 1: + { + IsRewardItem = reader.ReadBool(); + break; + } + } - if ( LootType == LootType.Regular ) - LootType = LootType.Blessed; - } - } -} + if (LootType == LootType.Regular) + LootType = LootType.Blessed; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/LeatherDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/LeatherDyeTub.cs index 17f106b78..018708c5f 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/LeatherDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/LeatherDyeTub.cs @@ -1,66 +1,68 @@ +using Server.Engines.VeteranRewards; + namespace Server.Items { - public class LeatherDyeTub : DyeTub, Engines.VeteranRewards.IRewardItem - { - public override bool AllowDyables => false; - public override bool AllowLeather => true; - public override int TargetMessage => 1042416; // Select the leather item to dye. - public override int FailMessage => 1042418; // You can only dye leather with this tub. - public override int LabelNumber => 1041284; // Leather Dye Tub - public override CustomHuePicker CustomHuePicker => CustomHuePicker.LeatherDyeTub; + public class LeatherDyeTub : DyeTub, IRewardItem + { + [Constructible] + public LeatherDyeTub() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + public LeatherDyeTub(Serial serial) : base(serial) + { + } - [Constructible] - public LeatherDyeTub() - { - LootType = LootType.Blessed; - } + public override bool AllowDyables => false; + public override bool AllowLeather => true; + public override int TargetMessage => 1042416; // Select the leather item to dye. + public override int FailMessage => 1042418; // You can only dye leather with this tub. + public override int LabelNumber => 1041284; // Leather Dye Tub + public override CustomHuePicker CustomHuePicker => CustomHuePicker.LeatherDyeTub; - public override void OnDoubleClick( Mobile from ) - { - if ( IsRewardItem && !Engines.VeteranRewards.RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public LeatherDyeTub( Serial serial ) : base( serial ) - { - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076218 ); // 2nd Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076218); // 2nd Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (bool) IsRewardItem ); - } + writer.Write(IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + IsRewardItem = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicClothDyetub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicClothDyetub.cs index 4a52d2fca..7c32abf80 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicClothDyetub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicClothDyetub.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public class MetallicClothDyetub : DyeTub - { - public override int LabelNumber => 1152920; // Metallic Cloth ... + public class MetallicClothDyetub : DyeTub + { + [Constructible] + public MetallicClothDyetub() + { + LootType = LootType.Blessed; + } - public override bool MetallicHues => true; + public MetallicClothDyetub(Serial serial) + : base(serial) + { + } - [Constructible] - public MetallicClothDyetub() - { - LootType = LootType.Blessed; - } + public override int LabelNumber => 1152920; // Metallic Cloth ... - public MetallicClothDyetub( Serial serial ) - : base( serial ) - { - } + public override bool MetallicHues => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicHuePicker.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicHuePicker.cs index c4ffe71ab..e20a80df9 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicHuePicker.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicHuePicker.cs @@ -3,78 +3,77 @@ using Server.Network; namespace Server.Items { - public class MetallicHuePicker : Gump - { - public delegate void MetallicHuePickerCallback( Mobile from, object state, int hue ); + public class MetallicHuePicker : Gump + { + public delegate void MetallicHuePickerCallback(Mobile from, object state, int hue); - private Mobile m_From; - private MetallicHuePickerCallback m_Callback; - private object m_State; + private MetallicHuePickerCallback m_Callback; - public void Render() - { - AddPage( 0 ); + private Mobile m_From; + private object m_State; - AddBackground( 0, 0, 450, 450, 0x13BE ); - AddBackground( 10, 10, 430, 430, 0xBB8 ); + public MetallicHuePicker(Mobile from, MetallicHuePickerCallback callback, object state) + : base(450, 450) + { + m_From = from; + m_Callback = callback; + m_State = state; - AddHtmlLocalized( 55, 400, 200, 25, 1011036, false, false ); // OKAY + Render(); + } - AddButton( 20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddButton( 200, 400, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddLabel( 235, 400, 0, "DEFAULT" ); + public void Render() + { + AddPage(0); - AddHtmlLocalized( 55, 25, 200, 25, 1150063, false, false ); // Base/Shadow Color - AddHtmlLocalized( 260, 25, 200, 25, 1150064, false, false ); // Highlight Color + AddBackground(0, 0, 450, 450, 0x13BE); + AddBackground(10, 10, 430, 430, 0xBB8); - for( int row = 0; row < 13; row++ ) - { - AddButton( 30, ( 65 + ( row * 25 ) ), 0x1467, 0x1468, row + 1, GumpButtonType.Page, row + 1 ); - AddItem( 50, ( 65 + ( row * 25 ) ), 0x1412, 2501 + ( row * 12 ) + ( ( row == 12 ) ? 6 : 0 ) ); - } + AddHtmlLocalized(55, 400, 200, 25, 1011036, false, false); // OKAY - for( int page = 1; page < 14; page++ ) - { - AddPage( page ); + AddButton(20, 400, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddButton(200, 400, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddLabel(235, 400, 0, "DEFAULT"); - for( int row = 0; row < 12; row++ ) - { - int hue = ( 2501 + ( ( page == 13 ) ? 6 : 0 ) + ( row + ( 12 * ( page - 1 ) ) ) ); /* OSI just had to skip 6 unused hues, didnt they */ - AddRadio( 260, ( 65 + ( row * 25 ) ), 0xd2, 0xd3, false, hue ); - AddItem( 280, ( 65 + ( row * 25 ) ), 0x1412, hue ); - } - } - } + AddHtmlLocalized(55, 25, 200, 25, 1150063, false, false); // Base/Shadow Color + AddHtmlLocalized(260, 25, 200, 25, 1150064, false, false); // Highlight Color - public MetallicHuePicker( Mobile from, MetallicHuePickerCallback callback, object state ) - : base( 450, 450 ) - { - m_From = from; - m_Callback = callback; - m_State = state; + for (int row = 0; row < 13; row++) + { + AddButton(30, 65 + row * 25, 0x1467, 0x1468, row + 1, GumpButtonType.Page, row + 1); + AddItem(50, 65 + row * 25, 0x1412, 2501 + row * 12 + (row == 12 ? 6 : 0)); + } - Render(); - } + for (int page = 1; page < 14; page++) + { + AddPage(page); - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch( info.ButtonID ) - { - case 1: // Okay - { - if ( info.Switches.Length > 0 ) - { - m_Callback( m_From, m_State, info.Switches[ 0 ] ); - } - break; - } - case 2: // Default - { - m_Callback( m_From, m_State, 0 ); + for (int row = 0; row < 12; row++) + { + int hue = 2501 + (page == 13 ? 6 : 0) + row + + 12 * (page - 1); /* OSI just had to skip 6 unused hues, didnt they */ + AddRadio(260, 65 + row * 25, 0xd2, 0xd3, false, hue); + AddItem(280, 65 + row * 25, 0x1412, hue); + } + } + } - break; - } - } - } - } -} + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: // Okay + { + if (info.Switches.Length > 0) m_Callback(m_From, m_State, info.Switches[0]); + break; + } + case 2: // Default + { + m_Callback(m_From, m_State, 0); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicLeatherDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicLeatherDyeTub.cs index 279c8ff88..015f017dc 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicLeatherDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/MetallicLeatherDyeTub.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class MetallicLeatherDyeTub : LeatherDyeTub - { - public override CustomHuePicker CustomHuePicker => null; + public class MetallicLeatherDyeTub : LeatherDyeTub + { + [Constructible] + public MetallicLeatherDyeTub() + { + LootType = LootType.Blessed; + } - public override int LabelNumber => 1153495; // Metallic Leather ... + public MetallicLeatherDyeTub(Serial serial) + : base(serial) + { + } - public override bool MetallicHues => true; + public override CustomHuePicker CustomHuePicker => null; - [Constructible] - public MetallicLeatherDyeTub() - { - LootType = LootType.Blessed; - } + public override int LabelNumber => 1153495; // Metallic Leather ... - public MetallicLeatherDyeTub( Serial serial ) - : base( serial ) - { - } + public override bool MetallicHues => true; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076221 ); // 5th Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076221); // 5th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RewardBlackDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RewardBlackDyeTub.cs index 8c6fc8fa1..9f24a0101 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RewardBlackDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RewardBlackDyeTub.cs @@ -1,63 +1,65 @@ +using Server.Engines.VeteranRewards; + namespace Server.Items { - public class RewardBlackDyeTub : DyeTub, Engines.VeteranRewards.IRewardItem - { - public override int LabelNumber => 1006008; // Black Dye Tub + public class RewardBlackDyeTub : DyeTub, IRewardItem + { + [Constructible] + public RewardBlackDyeTub() + { + Hue = DyedHue = 0x0001; + Redyable = false; + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + public RewardBlackDyeTub(Serial serial) : base(serial) + { + } - [Constructible] - public RewardBlackDyeTub() - { - Hue = DyedHue = 0x0001; - Redyable = false; - LootType = LootType.Blessed; - } + public override int LabelNumber => 1006008; // Black Dye Tub - public override void OnDoubleClick( Mobile from ) - { - if ( IsRewardItem && !Engines.VeteranRewards.RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public RewardBlackDyeTub( Serial serial ) : base( serial ) - { - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076217 ); // 1st Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076217); // 1st Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (bool) IsRewardItem ); - } + writer.Write(IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + IsRewardItem = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RunebookDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RunebookDyeTub.cs index 49fd474dd..155bbf662 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RunebookDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/RunebookDyeTub.cs @@ -1,66 +1,68 @@ +using Server.Engines.VeteranRewards; + namespace Server.Items { - public class RunebookDyeTub : DyeTub, Engines.VeteranRewards.IRewardItem - { - public override bool AllowDyables => false; - public override bool AllowRunebooks => true; - public override int TargetMessage => 1049774; // Target the runebook or runestone to dye - public override int FailMessage => 1049775; // You can only dye runestones or runebooks with this tub. - public override int LabelNumber => 1049740; // Runebook Dye Tub - public override CustomHuePicker CustomHuePicker => CustomHuePicker.LeatherDyeTub; + public class RunebookDyeTub : DyeTub, IRewardItem + { + [Constructible] + public RunebookDyeTub() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + public RunebookDyeTub(Serial serial) : base(serial) + { + } - [Constructible] - public RunebookDyeTub() - { - LootType = LootType.Blessed; - } + public override bool AllowDyables => false; + public override bool AllowRunebooks => true; + public override int TargetMessage => 1049774; // Target the runebook or runestone to dye + public override int FailMessage => 1049775; // You can only dye runestones or runebooks with this tub. + public override int LabelNumber => 1049740; // Runebook Dye Tub + public override CustomHuePicker CustomHuePicker => CustomHuePicker.LeatherDyeTub; - public override void OnDoubleClick( Mobile from ) - { - if ( IsRewardItem && !Engines.VeteranRewards.RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public RunebookDyeTub( Serial serial ) : base( serial ) - { - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076220 ); // 4th Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076220); // 4th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (bool) IsRewardItem ); - } + writer.Write(IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + IsRewardItem = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/SpecialDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/SpecialDyeTub.cs index cefa6ca0a..4fc696206 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/SpecialDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/SpecialDyeTub.cs @@ -2,63 +2,63 @@ using Server.Engines.VeteranRewards; namespace Server.Items { - public class SpecialDyeTub : DyeTub, IRewardItem - { - public override CustomHuePicker CustomHuePicker => CustomHuePicker.SpecialDyeTub; - public override int LabelNumber => 1041285; // Special Dye Tub + public class SpecialDyeTub : DyeTub, IRewardItem + { + [Constructible] + public SpecialDyeTub() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + public SpecialDyeTub(Serial serial) : base(serial) + { + } - [Constructible] - public SpecialDyeTub() - { - LootType = LootType.Blessed; - } + public override CustomHuePicker CustomHuePicker => CustomHuePicker.SpecialDyeTub; + public override int LabelNumber => 1041285; // Special Dye Tub - public override void OnDoubleClick( Mobile from ) - { - if ( IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public SpecialDyeTub( Serial serial ) : base( serial ) - { - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076217 ); // 1st Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076217); // 1st Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (bool) IsRewardItem ); - } + writer.Write(IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + IsRewardItem = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/StatuetteDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/StatuetteDyeTub.cs index f58f9baaf..fdc58f0af 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/StatuetteDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/StatuetteDyeTub.cs @@ -1,66 +1,68 @@ +using Server.Engines.VeteranRewards; + namespace Server.Items { - public class StatuetteDyeTub : DyeTub, Engines.VeteranRewards.IRewardItem - { - public override bool AllowDyables => false; - public override bool AllowStatuettes => true; - public override int TargetMessage => 1049777; // Target the statuette to dye - public override int FailMessage => 1049778; // You can only dye veteran reward statuettes with this tub. - public override int LabelNumber => 1049741; // Reward Statuette Dye Tub - public override CustomHuePicker CustomHuePicker => CustomHuePicker.LeatherDyeTub; + public class StatuetteDyeTub : DyeTub, IRewardItem + { + [Constructible] + public StatuetteDyeTub() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + public StatuetteDyeTub(Serial serial) : base(serial) + { + } - [Constructible] - public StatuetteDyeTub() - { - LootType = LootType.Blessed; - } + public override bool AllowDyables => false; + public override bool AllowStatuettes => true; + public override int TargetMessage => 1049777; // Target the statuette to dye + public override int FailMessage => 1049778; // You can only dye veteran reward statuettes with this tub. + public override int LabelNumber => 1049741; // Reward Statuette Dye Tub + public override CustomHuePicker CustomHuePicker => CustomHuePicker.LeatherDyeTub; - public override void OnDoubleClick( Mobile from ) - { - if ( IsRewardItem && !Engines.VeteranRewards.RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public StatuetteDyeTub( Serial serial ) : base( serial ) - { - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( 1076221 ); // 5th Year Veteran Reward - } + if (Core.ML && IsRewardItem) + list.Add(1076221); // 5th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (bool) IsRewardItem ); - } + writer.Write(IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + IsRewardItem = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteClothDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteClothDyeTub.cs index 29a8b71a8..6d5af436c 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteClothDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteClothDyeTub.cs @@ -1,34 +1,34 @@ namespace Server.Items /* High seas, loot from merchant ship's hold, also a "uncommon" loot item */ { - public class WhiteClothDyeTub : DyeTub - { - public override int LabelNumber => 1149984; // White Cloth Dye Tub + public class WhiteClothDyeTub : DyeTub + { + [Constructible] + public WhiteClothDyeTub() + { + DyedHue = Hue = 0x9C2; + } - public override bool Redyable => false; + public WhiteClothDyeTub(Serial serial) + : base(serial) + { + } - [Constructible] - public WhiteClothDyeTub() - { - DyedHue = Hue = 0x9C2; - } + public override int LabelNumber => 1149984; // White Cloth Dye Tub - public WhiteClothDyeTub( Serial serial ) - : base( serial ) - { - } + public override bool Redyable => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( ( int )0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteLeatherDyeTub.cs b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteLeatherDyeTub.cs index f29c0e481..4f0427268 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteLeatherDyeTub.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Dyetubs/WhiteLeatherDyeTub.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class WhiteLeatherDyeTub : LeatherDyeTub /* OSI UO 13th anniv gift, from redeemable gift tickets */ - { - public override int LabelNumber => 1149900; // White Leather Dye Tub - - public override bool Redyable => false; - - [Constructible] - public WhiteLeatherDyeTub() - { - DyedHue = Hue = 0x9C2; - LootType = LootType.Blessed; - } + public class WhiteLeatherDyeTub : LeatherDyeTub /* OSI UO 13th anniv gift, from redeemable gift tickets */ + { + [Constructible] + public WhiteLeatherDyeTub() + { + DyedHue = Hue = 0x9C2; + LootType = LootType.Blessed; + } - public WhiteLeatherDyeTub( Serial serial ) - : base( serial ) - { - } + public WhiteLeatherDyeTub(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int LabelNumber => 1149900; // White Leather Dye Tub - writer.Write( ( int )1 ); // version - } + public override bool Redyable => false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Misc/Dressform.cs b/Scripts/Items/Skill Items/Tailor Items/Misc/Dressform.cs index a3c4eaed5..4f534da44 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Misc/Dressform.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Misc/Dressform.cs @@ -1,30 +1,30 @@ namespace Server.Items { - [FlippableAttribute(0xec6, 0xec7)] - public class Dressform : Item - { - [Constructible] - public Dressform() : base(0xec6) - { - Weight = 10; - } + [Flippable(0xec6, 0xec7)] + public class Dressform : Item + { + [Constructible] + public Dressform() : base(0xec6) + { + Weight = 10; + } - public Dressform(Serial serial) : base(serial) - { - } + public Dressform(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Misc/Dyes.cs b/Scripts/Items/Skill Items/Tailor Items/Misc/Dyes.cs index 9d003e872..ee2e9e81e 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Misc/Dyes.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Misc/Dyes.cs @@ -1,122 +1,111 @@ -using Server.Targeting; using Server.HuePickers; +using Server.Targeting; namespace Server.Items { - public class Dyes : Item /* , IUsesRemaining */ /* TODO complete usesremaing */ - { - /* - public bool ShowUsesRemaining { get { return false; } set { } } + public class Dyes : Item /* , IUsesRemaining */ /* TODO complete usesremaing */ + { + /* + public bool ShowUsesRemaining { get { return false; } set { } } - [CommandProperty( AccessLevel.GameMaster )] - public virtual int UsesRemaining { get { return m_UsesRemaining; } set { m_UsesRemaining = value; } } + [CommandProperty( AccessLevel.GameMaster )] + public virtual int UsesRemaining { get { return m_UsesRemaining; } set { m_UsesRemaining = value; } } - private int m_UsesRemaining; - */ + private int m_UsesRemaining; + */ - [Constructible] - public Dyes() : base( 0xFA9 ) - { - Weight = 3.0; + [Constructible] + public Dyes() : base(0xFA9) + { + Weight = 3.0; - /* m_UsesRemaining = 25; */ - } + /* m_UsesRemaining = 25; */ + } - public Dyes( Serial serial ) : base( serial ) - { - } + public Dyes(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - /* writer.Write( ( int )m_UsesRemaining ); */ - } + /* writer.Write( ( int )m_UsesRemaining ); */ + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 0.0 ) - Weight = 3.0; + if (Weight == 0.0) + Weight = 3.0; - /* m_UsesRemaining = ( version == 0 ) ? 25 : reader.ReadInt(); */ - } + /* m_UsesRemaining = ( version == 0 ) ? 25 : reader.ReadInt(); */ + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 500856 ); // Select the dye tub to use the dyes on. - from.Target = new InternalTarget(); - } + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(500856); // Select the dye tub to use the dyes on. + from.Target = new InternalTarget(); + } - private class InternalTarget : Target - { - public InternalTarget() : base( 1, false, TargetFlags.None ) - { - } + private class InternalTarget : Target + { + public InternalTarget() : base(1, false, TargetFlags.None) + { + } - private class InternalPicker : HuePicker - { - private DyeTub m_Tub; + public virtual void SetTubHue(Mobile from, object state, int hue) + { + if (state is DyeTub tub) tub.DyedHue = hue; + } - public InternalPicker( DyeTub tub ) : base( tub.ItemID ) - { - m_Tub = tub; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is DyeTub tub) + { + if (tub.Redyable) + { + if (tub.MetallicHues) /* OSI has three metallic tubs now */ + from.SendGump(new MetallicHuePicker(from, SetTubHue, tub)); + else if (tub.CustomHuePicker != null) + from.SendGump(new CustomHuePickerGump(from, tub.CustomHuePicker, SetTubHue, tub)); + else + from.SendHuePicker(new InternalPicker(tub)); + } + else if (tub is BlackDyeTub) + { + from.SendLocalizedMessage(1010092); // You can not use this on a black dye tub. + } + else + { + from.SendMessage("That dye tub may not be redyed."); + } + } + else + { + from.SendLocalizedMessage(500857); // Use this on a dye tub. + } + } - public override void OnResponse( int hue ) - { - m_Tub.DyedHue = hue; - } - } + private class InternalPicker : HuePicker + { + private DyeTub m_Tub; - public virtual void SetTubHue( Mobile from, object state, int hue ) - { - if ( state is DyeTub tub ) - { - tub.DyedHue = hue; + public InternalPicker(DyeTub tub) : base(tub.ItemID) + { + m_Tub = tub; + } - /* dyes.m_UsesRemaining--; let this change ride till the overhaul */ - } - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is DyeTub tub ) - { - if ( tub.Redyable ) - { - if ( tub.MetallicHues ) /* OSI has three metallic tubs now */ - { - from.SendGump( new MetallicHuePicker( from, SetTubHue, tub ) ); - } - else if ( tub.CustomHuePicker != null ) - { - from.SendGump( new CustomHuePickerGump( from, tub.CustomHuePicker, SetTubHue, tub ) ); - } - else - { - from.SendHuePicker( new InternalPicker( tub ) ); - } - } - else if ( tub is BlackDyeTub ) - { - from.SendLocalizedMessage( 1010092 ); // You can not use this on a black dye tub. - } - else - { - from.SendMessage( "That dye tub may not be redyed." ); - } - } - else - { - from.SendLocalizedMessage( 500857 ); // Use this on a dye tub. - } - } - } - } -} + public override void OnResponse(int hue) + { + m_Tub.DyedHue = hue; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tailor Items/Misc/Scissors.cs b/Scripts/Items/Skill Items/Tailor Items/Misc/Scissors.cs index a03ca1668..23bacd1a6 100644 --- a/Scripts/Items/Skill Items/Tailor Items/Misc/Scissors.cs +++ b/Scripts/Items/Skill Items/Tailor Items/Misc/Scissors.cs @@ -2,114 +2,118 @@ using Server.Targeting; namespace Server.Items { - public interface IScissorable - { - bool Scissor( Mobile from, Scissors scissors ); - } + public interface IScissorable + { + bool Scissor(Mobile from, Scissors scissors); + } - [FlippableAttribute( 0xf9f, 0xf9e )] - public class Scissors : Item - { - [Constructible] - public Scissors() : base( 0xF9F ) - { - Weight = 1.0; - } + [Flippable(0xf9f, 0xf9e)] + public class Scissors : Item + { + [Constructible] + public Scissors() : base(0xF9F) + { + Weight = 1.0; + } - public Scissors( Serial serial ) : base( serial ) - { - } + public Scissors(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 502434 ); // What should I use these scissors on? + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(502434); // What should I use these scissors on? - from.Target = new InternalTarget( this ); - } + from.Target = new InternalTarget(this); + } - private class InternalTarget : Target - { - private Scissors m_Item; + public static bool CanScissor(Mobile from, IScissorable obj) + { + if (obj is Item item && item.Nontransferable) + { + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + return false; + } - public InternalTarget( Scissors item ) : base( 2, false, TargetFlags.None ) - { - m_Item = item; - } + // TODO: Move other general checks from the different implementations here - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) - return; + return true; + } - /*if ( targeted is Item && !((Item)targeted).IsStandardLoot() ) - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - } - else */ - if ( Core.AOS && targeted == from ) - { - from.SendLocalizedMessage( 1062845 + Utility.Random( 3 ) ); //"That doesn't seem like the smartest thing to do." / "That was an encounter you don't wish to repeat." / "Ha! You missed!" - } - else if (Core.SE && Utility.RandomDouble() > .20 && (from.Direction & Direction.Running) != 0 && (Core.TickCount - from.LastMoveTime) < from.ComputeMovementSpeed(from.Direction)) - { - from.SendLocalizedMessage( 1063305 ); // Didn't your parents ever tell you not to run with scissors in your hand?! - } - else if ( targeted is Item item && !item.Movable ) - { - if ( item is IScissorable obj && ( obj is PlagueBeastInnard || obj is PlagueBeastMutationCore ) ) - { - if ( CanScissor( from, obj ) && obj.Scissor( from, m_Item ) ) - from.PlaySound( 0x248 ); - } - } - else if ( targeted is IScissorable obj ) - { - if ( CanScissor( from, obj ) && obj.Scissor( from, m_Item ) ) - from.PlaySound( 0x248 ); - } - else - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - } - } + private class InternalTarget : Target + { + private Scissors m_Item; - protected override void OnNonlocalTarget( Mobile from, object targeted ) - { - if ( targeted is IScissorable obj && ( obj is PlagueBeastInnard || obj is PlagueBeastMutationCore ) ) - { - if ( CanScissor( from, obj ) && obj.Scissor( from, m_Item ) ) - from.PlaySound( 0x248 ); - } - else - base.OnNonlocalTarget( from, targeted ); - } - } + public InternalTarget(Scissors item) : base(2, false, TargetFlags.None) + { + m_Item = item; + } - public static bool CanScissor( Mobile from, IScissorable obj ) - { - if ( obj is Item item && item.Nontransferable ) - { - from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. - return false; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) + return; - // TODO: Move other general checks from the different implementations here + /*if ( targeted is Item && !((Item)targeted).IsStandardLoot() ) + { + from.SendLocalizedMessage( 502440 ); // Scissors can not be used on that to produce anything. + } + else */ + if (Core.AOS && targeted == from) + { + from.SendLocalizedMessage( + 1062845 + Utility + .Random(3)); //"That doesn't seem like the smartest thing to do." / "That was an encounter you don't wish to repeat." / "Ha! You missed!" + } + else if (Core.SE && Utility.RandomDouble() > .20 && (from.Direction & Direction.Running) != 0 && + Core.TickCount - from.LastMoveTime < from.ComputeMovementSpeed(from.Direction)) + { + from.SendLocalizedMessage( + 1063305); // Didn't your parents ever tell you not to run with scissors in your hand?! + } + else if (targeted is Item item && !item.Movable) + { + if (item is IScissorable obj && (obj is PlagueBeastInnard || obj is PlagueBeastMutationCore)) + if (CanScissor(from, obj) && obj.Scissor(from, m_Item)) + from.PlaySound(0x248); + } + else if (targeted is IScissorable obj) + { + if (CanScissor(from, obj) && obj.Scissor(from, m_Item)) + from.PlaySound(0x248); + } + else + { + from.SendLocalizedMessage(502440); // Scissors can not be used on that to produce anything. + } + } - return true; - } - } -} + protected override void OnNonlocalTarget(Mobile from, object targeted) + { + if (targeted is IScissorable obj && (obj is PlagueBeastInnard || obj is PlagueBeastMutationCore)) + { + if (CanScissor(from, obj) && obj.Scissor(from, m_Item)) + from.PlaySound(0x248); + } + else + { + base.OnNonlocalTarget(from, targeted); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Thief/DisguiseKit.cs b/Scripts/Items/Skill Items/Thief/DisguiseKit.cs index f7efae3d8..71d371275 100644 --- a/Scripts/Items/Skill Items/Thief/DisguiseKit.cs +++ b/Scripts/Items/Skill Items/Thief/DisguiseKit.cs @@ -1,364 +1,339 @@ using System; using System.Collections.Generic; +using Server.Factions; using Server.Gumps; -using Server.Spells; -using Server.Spells.Fifth; -using Server.Spells.Seventh; using Server.Mobiles; using Server.Network; using Server.SkillHandlers; +using Server.Spells; +using Server.Spells.Fifth; +using Server.Spells.Seventh; namespace Server.Items { - public class DisguiseKit : Item - { - public override int LabelNumber => 1041078; // a disguise kit - - [Constructible] - public DisguiseKit() : base( 0xE05 ) - { - Weight = 1.0; - } - - public DisguiseKit( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public bool ValidateUse( Mobile from ) - { - PlayerMobile pm = from as PlayerMobile; - - if ( !IsChildOf( from.Backpack ) ) - { - // That must be in your pack for you to use it. - from.SendLocalizedMessage( 1042001 ); - } - else if ( pm == null || pm.NpcGuild != NpcGuild.ThievesGuild ) - { - // Only Members of the thieves guild are trained to use this item. - from.SendLocalizedMessage( 501702 ); - } - else if ( Stealing.SuspendOnMurder && pm.Kills > 0 ) - { - // You are currently suspended from the thieves guild. They would frown upon your actions. - from.SendLocalizedMessage( 501703 ); - } - else if ( !from.CanBeginAction( typeof( IncognitoSpell ) ) ) - { - // You cannot disguise yourself while incognitoed. - from.SendLocalizedMessage( 501704 ); - } - else if ( Factions.Sigil.ExistsOn( from ) ) - { - from.SendLocalizedMessage( 1010465 ); // You cannot disguise yourself while holding a sigil - } - else if ( TransformationSpellHelper.UnderTransformation( from ) ) - { - // You cannot disguise yourself while in that form. - from.SendLocalizedMessage( 1061634 ); - } - else if ( from.BodyMod == 183 || from.BodyMod == 184 ) - { - // You cannot disguise yourself while wearing body paint - from.SendLocalizedMessage( 1040002 ); - } - else if ( !from.CanBeginAction( typeof( PolymorphSpell ) ) || from.IsBodyMod ) - { - // You cannot disguise yourself while polymorphed. - from.SendLocalizedMessage( 501705 ); - } - else - { - return true; - } - - return false; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( ValidateUse( from ) ) - from.SendGump( new DisguiseGump( from, this, true, false ) ); - } - } - - public class DisguiseGump : Gump - { - private Mobile m_From; - private DisguiseKit m_Kit; - private bool m_Used; - - public DisguiseGump( Mobile from, DisguiseKit kit, bool startAtHair, bool used ) : base( 50, 50 ) - { - m_From = from; - m_Kit = kit; - m_Used = used; - - from.CloseGump( typeof( DisguiseGump ) ); - - AddPage( 0 ); - - AddBackground( 100, 10, 400, 385, 2600 ); - - //
THIEF DISGUISE KIT
- AddHtmlLocalized( 100, 25, 400, 35, 1011045, false, false ); - - AddButton( 140, 353, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 172, 355, 90, 35, 1011036, false, false ); // OKAY - - AddButton( 257, 353, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 289, 355, 90, 35, 1011046, false, false ); // APPLY - - if ( from.Female || from.Body.IsFemale ) - { - DrawEntries( 0, 1, -1, m_HairEntries, -1 ); - } - else if ( startAtHair ) - { - DrawEntries( 0, 1, 2, m_HairEntries, 1011056 ); - DrawEntries( 1, 2, 1, m_BeardEntries, 1011059 ); - } - else - { - DrawEntries( 1, 1, 2, m_BeardEntries, 1011059 ); - DrawEntries( 0, 2, 1, m_HairEntries, 1011056 ); - } - } - - private void DrawEntries( int index, int page, int nextPage, DisguiseEntry[] entries, int nextNumber ) - { - AddPage( page ); - - if ( nextPage != -1 ) - { - AddButton( 155, 320, 250 + (index*2), 251 + (index*2), 0, GumpButtonType.Page, nextPage ); - AddHtmlLocalized( 180, 320, 150, 35, nextNumber, false, false ); - } - - for ( int i = 0; i < entries.Length; ++i ) - { - DisguiseEntry entry = entries[i]; - - if ( entry == null ) - continue; - - int x = (i % 2) * 205; - int y = (i / 2) * 55; - - if ( entry.m_GumpID != 0 ) - { - AddBackground( 220 + x, 60 + y, 50, 50, 2620 ); - AddImage( 153 + x + entry.m_OffsetX, 15 + y + entry.m_OffsetY, entry.m_GumpID ); - } - - AddHtmlLocalized( 140 + x, 72 + y, 80, 35, entry.m_Number, false, false ); - AddRadio( 118 + x, 73 + y, 208, 209, false, (i * 2) + index ); - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 ) - { - if ( m_Used ) - m_From.SendLocalizedMessage( 501706 ); // Disguises wear off after 2 hours. - else - m_From.SendLocalizedMessage( 501707 ); // You're looking good. - - return; - } - - int[] switches = info.Switches; - - if ( switches.Length == 0 ) - return; - - int switched = switches[0]; - int type = switched % 2; - int index = switched / 2; - - bool hair = ( type == 0 ); - - DisguiseEntry[] entries = ( hair ? m_HairEntries : m_BeardEntries ); - - if ( index >= 0 && index < entries.Length ) - { - DisguiseEntry entry = entries[index]; - - if ( entry == null ) - return; - - if ( !m_Kit.ValidateUse( m_From ) ) - return; - - if ( !hair && (m_From.Female || m_From.Body.IsFemale) ) - return; - - m_From.NameMod = NameList.RandomName( m_From.Female ? "female" : "male" ); - - if ( m_From is PlayerMobile pm ) - { - if ( hair ) - pm.SetHairMods( entry.m_ItemID, -2 ); - else - pm.SetHairMods( -2, entry.m_ItemID ); - } - - m_From.SendGump( new DisguiseGump( m_From, m_Kit, hair, true ) ); - - DisguiseTimers.RemoveTimer( m_From ); - - DisguiseTimers.CreateTimer( m_From, TimeSpan.FromHours( 2.0 ) ); - DisguiseTimers.StartTimer( m_From ); - } - } - - private static DisguiseEntry[] m_HairEntries = { - new DisguiseEntry( 8251, 50700, 0, 5, 1011052 ), // Short - new DisguiseEntry( 8261, 60710, 0, 3, 1011047 ), // Pageboy - new DisguiseEntry( 8252, 60708, 0,- 5, 1011053 ), // Long - new DisguiseEntry( 8264, 60901, 0, 5, 1011048 ), // Receding - new DisguiseEntry( 8253, 60702, 0,- 5, 1011054 ), // Ponytail - new DisguiseEntry( 8265, 60707, 0,- 5, 1011049 ), // 2-tails - new DisguiseEntry( 8260, 50703, 0, 5, 1011055 ), // Mohawk - new DisguiseEntry( 8266, 60713, 0, 10, 1011050 ), // Topknot - null, - new DisguiseEntry( 0, 0, 0, 0, 1011051 ) // None - }; - - private static DisguiseEntry[] m_BeardEntries = { - new DisguiseEntry( 8269, 50906, 0, 0, 1011401 ), // Vandyke - new DisguiseEntry( 8257, 50808, 0,- 2, 1011062 ), // Mustache - new DisguiseEntry( 8255, 50802, 0, 0, 1011060 ), // Short beard - new DisguiseEntry( 8268, 50905, 0,-10, 1011061 ), // Long beard - new DisguiseEntry( 8267, 50904, 0, 0, 1011060 ), // Short beard - new DisguiseEntry( 8254, 50801, 0,-10, 1011061 ), // Long beard - null, - new DisguiseEntry( 0, 0, 0, 0, 1011051 ) // None - }; - - private class DisguiseEntry - { - public int m_Number; - public int m_ItemID; - public int m_GumpID; - public int m_OffsetX; - public int m_OffsetY; - - public DisguiseEntry( int itemID, int gumpID, int ox, int oy, int name ) - { - m_ItemID = itemID; - m_GumpID = gumpID; - m_OffsetX = ox; - m_OffsetY = oy; - m_Number = name; - } - } - } - - public class DisguiseTimers - { - public static void Initialize() - { - new DisguisePersistance(); - } - - private class InternalTimer : Timer - { - private Mobile m_Player; - - public InternalTimer( Mobile m, TimeSpan delay ) : base( delay ) - { - m_Player = m; - Priority = TimerPriority.OneMinute; - } - - protected override void OnTick() - { - m_Player.NameMod = null; - - if ( m_Player is PlayerMobile mobile ) - mobile.SetHairMods( -1, -1 ); - - RemoveTimer( m_Player ); - } - } - - public static void CreateTimer( Mobile m, TimeSpan delay ) - { - if ( m != null ) - if ( !Timers.ContainsKey( m ) ) - Timers[m] = new InternalTimer( m, delay ); - } - - public static void StartTimer( Mobile m ) - { - Timers.TryGetValue( m, out Timer t ); - - t?.Start(); - } - - public static bool IsDisguised( Mobile m ) - { - return Timers.ContainsKey( m ); - } - - public static bool StopTimer( Mobile m ) - { - Timers.TryGetValue( m, out Timer t ); - - if ( t != null ) - { - TimeSpan ts = t.Next - DateTime.UtcNow; - if (ts < TimeSpan.Zero) - ts = TimeSpan.Zero; - - t.Delay = ts; - t.Stop(); - } - - return ( t != null ); - } - - public static bool RemoveTimer( Mobile m ) - { - Timers.TryGetValue( m, out Timer t ); - - if ( t != null ) - { - t.Stop(); - Timers.Remove( m ); - } - - return ( t != null ); - } - - public static TimeSpan TimeRemaining( Mobile m ) - { - Timers.TryGetValue( m, out Timer t ); - - if ( t != null ) - { - return t.Next - DateTime.UtcNow; - } - - return TimeSpan.Zero; - } - - public static Dictionary Timers { get; } = new Dictionary(); - } -} + public class DisguiseKit : Item + { + [Constructible] + public DisguiseKit() : base(0xE05) + { + Weight = 1.0; + } + + public DisguiseKit(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041078; // a disguise kit + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public bool ValidateUse(Mobile from) + { + PlayerMobile pm = from as PlayerMobile; + + if (!IsChildOf(from.Backpack)) + from.SendLocalizedMessage(1042001); + else if (pm == null || pm.NpcGuild != NpcGuild.ThievesGuild) + from.SendLocalizedMessage(501702); + else if (Stealing.SuspendOnMurder && pm.Kills > 0) + from.SendLocalizedMessage(501703); + else if (!from.CanBeginAction(typeof(IncognitoSpell))) + from.SendLocalizedMessage(501704); + else if (Sigil.ExistsOn(from)) + from.SendLocalizedMessage(1010465); // You cannot disguise yourself while holding a sigil + else if (TransformationSpellHelper.UnderTransformation(from)) + from.SendLocalizedMessage(1061634); + else if (from.BodyMod == 183 || from.BodyMod == 184) + from.SendLocalizedMessage(1040002); + else if (!from.CanBeginAction(typeof(PolymorphSpell)) || from.IsBodyMod) + from.SendLocalizedMessage(501705); + else + return true; + + return false; + } + + public override void OnDoubleClick(Mobile from) + { + if (ValidateUse(from)) + from.SendGump(new DisguiseGump(from, this, true, false)); + } + } + + public class DisguiseGump : Gump + { + private static DisguiseEntry[] m_HairEntries = + { + new DisguiseEntry(8251, 50700, 0, 5, 1011052), // Short + new DisguiseEntry(8261, 60710, 0, 3, 1011047), // Pageboy + new DisguiseEntry(8252, 60708, 0, -5, 1011053), // Long + new DisguiseEntry(8264, 60901, 0, 5, 1011048), // Receding + new DisguiseEntry(8253, 60702, 0, -5, 1011054), // Ponytail + new DisguiseEntry(8265, 60707, 0, -5, 1011049), // 2-tails + new DisguiseEntry(8260, 50703, 0, 5, 1011055), // Mohawk + new DisguiseEntry(8266, 60713, 0, 10, 1011050), // Topknot + null, + new DisguiseEntry(0, 0, 0, 0, 1011051) // None + }; + + private static DisguiseEntry[] m_BeardEntries = + { + new DisguiseEntry(8269, 50906, 0, 0, 1011401), // Vandyke + new DisguiseEntry(8257, 50808, 0, -2, 1011062), // Mustache + new DisguiseEntry(8255, 50802, 0, 0, 1011060), // Short beard + new DisguiseEntry(8268, 50905, 0, -10, 1011061), // Long beard + new DisguiseEntry(8267, 50904, 0, 0, 1011060), // Short beard + new DisguiseEntry(8254, 50801, 0, -10, 1011061), // Long beard + null, + new DisguiseEntry(0, 0, 0, 0, 1011051) // None + }; + + private Mobile m_From; + private DisguiseKit m_Kit; + private bool m_Used; + + public DisguiseGump(Mobile from, DisguiseKit kit, bool startAtHair, bool used) : base(50, 50) + { + m_From = from; + m_Kit = kit; + m_Used = used; + + from.CloseGump(typeof(DisguiseGump)); + + AddPage(0); + + AddBackground(100, 10, 400, 385, 2600); + + //
THIEF DISGUISE KIT
+ AddHtmlLocalized(100, 25, 400, 35, 1011045, false, false); + + AddButton(140, 353, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(172, 355, 90, 35, 1011036, false, false); // OKAY + + AddButton(257, 353, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(289, 355, 90, 35, 1011046, false, false); // APPLY + + if (from.Female || from.Body.IsFemale) + { + DrawEntries(0, 1, -1, m_HairEntries, -1); + } + else if (startAtHair) + { + DrawEntries(0, 1, 2, m_HairEntries, 1011056); + DrawEntries(1, 2, 1, m_BeardEntries, 1011059); + } + else + { + DrawEntries(1, 1, 2, m_BeardEntries, 1011059); + DrawEntries(0, 2, 1, m_HairEntries, 1011056); + } + } + + private void DrawEntries(int index, int page, int nextPage, DisguiseEntry[] entries, int nextNumber) + { + AddPage(page); + + if (nextPage != -1) + { + AddButton(155, 320, 250 + index * 2, 251 + index * 2, 0, GumpButtonType.Page, nextPage); + AddHtmlLocalized(180, 320, 150, 35, nextNumber, false, false); + } + + for (int i = 0; i < entries.Length; ++i) + { + DisguiseEntry entry = entries[i]; + + if (entry == null) + continue; + + int x = i % 2 * 205; + int y = i / 2 * 55; + + if (entry.m_GumpID != 0) + { + AddBackground(220 + x, 60 + y, 50, 50, 2620); + AddImage(153 + x + entry.m_OffsetX, 15 + y + entry.m_OffsetY, entry.m_GumpID); + } + + AddHtmlLocalized(140 + x, 72 + y, 80, 35, entry.m_Number, false, false); + AddRadio(118 + x, 73 + y, 208, 209, false, i * 2 + index); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0) + { + if (m_Used) + m_From.SendLocalizedMessage(501706); // Disguises wear off after 2 hours. + else + m_From.SendLocalizedMessage(501707); // You're looking good. + + return; + } + + int[] switches = info.Switches; + + if (switches.Length == 0) + return; + + int switched = switches[0]; + int type = switched % 2; + int index = switched / 2; + + bool hair = type == 0; + + DisguiseEntry[] entries = hair ? m_HairEntries : m_BeardEntries; + + if (index >= 0 && index < entries.Length) + { + DisguiseEntry entry = entries[index]; + + if (entry == null) + return; + + if (!m_Kit.ValidateUse(m_From)) + return; + + if (!hair && (m_From.Female || m_From.Body.IsFemale)) + return; + + m_From.NameMod = NameList.RandomName(m_From.Female ? "female" : "male"); + + if (m_From is PlayerMobile pm) + { + if (hair) + pm.SetHairMods(entry.m_ItemID, -2); + else + pm.SetHairMods(-2, entry.m_ItemID); + } + + m_From.SendGump(new DisguiseGump(m_From, m_Kit, hair, true)); + + DisguiseTimers.RemoveTimer(m_From); + + DisguiseTimers.CreateTimer(m_From, TimeSpan.FromHours(2.0)); + DisguiseTimers.StartTimer(m_From); + } + } + + private class DisguiseEntry + { + public int m_GumpID; + public int m_ItemID; + public int m_Number; + public int m_OffsetX; + public int m_OffsetY; + + public DisguiseEntry(int itemID, int gumpID, int ox, int oy, int name) + { + m_ItemID = itemID; + m_GumpID = gumpID; + m_OffsetX = ox; + m_OffsetY = oy; + m_Number = name; + } + } + } + + public class DisguiseTimers + { + public static Dictionary Timers{ get; } = new Dictionary(); + + public static void Initialize() + { + new DisguisePersistance(); + } + + public static void CreateTimer(Mobile m, TimeSpan delay) + { + if (m != null) + if (!Timers.ContainsKey(m)) + Timers[m] = new InternalTimer(m, delay); + } + + public static void StartTimer(Mobile m) + { + Timers.TryGetValue(m, out Timer t); + + t?.Start(); + } + + public static bool IsDisguised(Mobile m) + { + return Timers.ContainsKey(m); + } + + public static bool StopTimer(Mobile m) + { + Timers.TryGetValue(m, out Timer t); + + if (t != null) + { + TimeSpan ts = t.Next - DateTime.UtcNow; + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; + + t.Delay = ts; + t.Stop(); + } + + return t != null; + } + + public static bool RemoveTimer(Mobile m) + { + Timers.TryGetValue(m, out Timer t); + + if (t != null) + { + t.Stop(); + Timers.Remove(m); + } + + return t != null; + } + + public static TimeSpan TimeRemaining(Mobile m) + { + Timers.TryGetValue(m, out Timer t); + + if (t != null) return t.Next - DateTime.UtcNow; + + return TimeSpan.Zero; + } + + private class InternalTimer : Timer + { + private Mobile m_Player; + + public InternalTimer(Mobile m, TimeSpan delay) : base(delay) + { + m_Player = m; + Priority = TimerPriority.OneMinute; + } + + protected override void OnTick() + { + m_Player.NameMod = null; + + if (m_Player is PlayerMobile mobile) + mobile.SetHairMods(-1, -1); + + RemoveTimer(m_Player); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Thief/DisguisePersistance.cs b/Scripts/Items/Skill Items/Thief/DisguisePersistance.cs index fecbae57d..daa1cd284 100644 --- a/Scripts/Items/Skill Items/Thief/DisguisePersistance.cs +++ b/Scripts/Items/Skill Items/Thief/DisguisePersistance.cs @@ -3,73 +3,73 @@ using System.Collections.Generic; namespace Server.Items { - public class DisguisePersistance : Item - { - public static DisguisePersistance Instance { get; private set; } + public class DisguisePersistance : Item + { + public DisguisePersistance() : base(1) + { + Movable = false; - public override string DefaultName => "Disguise Persistance - Internal"; + if (Instance == null || Instance.Deleted) + Instance = this; + else + base.Delete(); + } - public DisguisePersistance() : base( 1 ) - { - Movable = false; - - if ( Instance == null || Instance.Deleted ) - Instance = this; - else - base.Delete(); - } + public DisguisePersistance(Serial serial) : base(serial) + { + Instance = this; + } - public DisguisePersistance( Serial serial ) : base( serial ) - { - Instance = this; - } + public static DisguisePersistance Instance{ get; private set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string DefaultName => "Disguise Persistance - Internal"; - writer.Write( (int) 0 ); // version - - int timerCount = DisguiseTimers.Timers.Count; - - writer.Write( timerCount ); - - foreach ( KeyValuePair entry in DisguiseTimers.Timers ) - { - Mobile m = entry.Key; - - writer.Write( m ); - writer.Write( entry.Value.Next - DateTime.UtcNow ); - writer.Write( m.NameMod ); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + writer.Write(0); // version - int version = reader.ReadInt(); + int timerCount = DisguiseTimers.Timers.Count; - switch ( version ) - { - case 0: - { - int count = reader.ReadInt(); - - for ( int i = 0; i < count; ++i ) - { - Mobile m = reader.ReadMobile(); - DisguiseTimers.CreateTimer( m, reader.ReadTimeSpan() ); - m.NameMod = reader.ReadString(); - } + writer.Write(timerCount); - break; - } - } - } + foreach (KeyValuePair entry in DisguiseTimers.Timers) + { + Mobile m = entry.Key; - public override void Delete() - { - } - } -} + writer.Write(m); + writer.Write(entry.Value.Next - DateTime.UtcNow); + writer.Write(m.NameMod); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + int count = reader.ReadInt(); + + for (int i = 0; i < count; ++i) + { + Mobile m = reader.ReadMobile(); + DisguiseTimers.CreateTimer(m, reader.ReadTimeSpan()); + m.NameMod = reader.ReadString(); + } + + break; + } + } + } + + public override void Delete() + { + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Thief/LockPick.cs b/Scripts/Items/Skill Items/Thief/LockPick.cs index f56435a99..a7f7913be 100644 --- a/Scripts/Items/Skill Items/Thief/LockPick.cs +++ b/Scripts/Items/Skill Items/Thief/LockPick.cs @@ -3,167 +3,167 @@ using Server.Targeting; namespace Server.Items { - public interface ILockpickable : IPoint2D - { - int LockLevel{ get; set; } - bool Locked{ get; set; } - Mobile Picker{ get; set; } - int MaxLockLevel{ get; set; } - int RequiredSkill{ get; set; } + public interface ILockpickable : IPoint2D + { + int LockLevel{ get; set; } + bool Locked{ get; set; } + Mobile Picker{ get; set; } + int MaxLockLevel{ get; set; } + int RequiredSkill{ get; set; } - void LockPick( Mobile from ); - } + void LockPick(Mobile from); + } + [Flippable(0x14fc, 0x14fb)] + public class Lockpick : Item + { + [Constructible] + public Lockpick() : this(1) + { + } - [FlippableAttribute( 0x14fc, 0x14fb )] - public class Lockpick : Item - { - [Constructible] - public Lockpick() : this( 1 ) - { - } + [Constructible] + public Lockpick(int amount) : base(0x14FC) + { + Stackable = true; + Amount = amount; + } - [Constructible] - public Lockpick( int amount ) : base( 0x14FC ) - { - Stackable = true; - Amount = amount; - } + public Lockpick(Serial serial) : base(serial) + { + } - public Lockpick( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 && Weight == 0.1 ) - Weight = -1; - } + if (version == 0 && Weight == 0.1) + Weight = -1; + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 502068 ); // What do you want to pick? - from.Target = new InternalTarget( this ); - } + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(502068); // What do you want to pick? + from.Target = new InternalTarget(this); + } - private class InternalTarget : Target - { - private Lockpick m_Item; + private class InternalTarget : Target + { + private Lockpick m_Item; - public InternalTarget( Lockpick item ) : base( 1, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget(Lockpick item) : base(1, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) + return; - if ( targeted is ILockpickable lockpickable ) - { - Item item = lockpickable as Item; - from.Direction = from.GetDirectionTo( item ); + if (targeted is ILockpickable lockpickable) + { + Item item = lockpickable as Item; + from.Direction = from.GetDirectionTo(item); - if ( lockpickable.Locked ) - { - from.PlaySound( 0x241 ); + if (lockpickable.Locked) + { + from.PlaySound(0x241); - new InternalTimer( from, lockpickable, m_Item ).Start(); - } - else - { - // The door is not locked - from.SendLocalizedMessage( 502069 ); // This does not appear to be locked - } - } - else - { - from.SendLocalizedMessage( 501666 ); // You can't unlock that! - } - } + new InternalTimer(from, lockpickable, m_Item).Start(); + } + else + { + // The door is not locked + from.SendLocalizedMessage(502069); // This does not appear to be locked + } + } + else + { + from.SendLocalizedMessage(501666); // You can't unlock that! + } + } - private class InternalTimer : Timer - { - private Mobile m_From; - private ILockpickable m_Item; - private Lockpick m_Lockpick; + private class InternalTimer : Timer + { + private Mobile m_From; + private ILockpickable m_Item; + private Lockpick m_Lockpick; - public InternalTimer( Mobile from, ILockpickable item, Lockpick lockpick ) : base( TimeSpan.FromSeconds( 3.0 ) ) - { - m_From = from; - m_Item = item; - m_Lockpick = lockpick; - Priority = TimerPriority.TwoFiftyMS; - } + public InternalTimer(Mobile from, ILockpickable item, Lockpick lockpick) : base(TimeSpan.FromSeconds(3.0)) + { + m_From = from; + m_Item = item; + m_Lockpick = lockpick; + Priority = TimerPriority.TwoFiftyMS; + } - protected void BrokeLockPickTest() - { - // When failed, a 25% chance to break the lockpick - if ( Utility.Random( 4 ) == 0 ) - { - Item item = (Item)m_Item; + protected void BrokeLockPickTest() + { + // When failed, a 25% chance to break the lockpick + if (Utility.Random(4) == 0) + { + Item item = (Item)m_Item; - // You broke the lockpick. - item.SendLocalizedMessageTo( m_From, 502074 ); + // You broke the lockpick. + item.SendLocalizedMessageTo(m_From, 502074); - m_From.PlaySound( 0x3A4 ); - m_Lockpick.Consume(); - } - } + m_From.PlaySound(0x3A4); + m_Lockpick.Consume(); + } + } - protected override void OnTick() - { - Item item = (Item)m_Item; + protected override void OnTick() + { + Item item = (Item)m_Item; - if ( !m_From.InRange( item.GetWorldLocation(), 1 ) ) - return; + if (!m_From.InRange(item.GetWorldLocation(), 1)) + return; - if ( m_Item.LockLevel == 0 || m_Item.LockLevel == -255 ) - { - // LockLevel of 0 means that the door can't be picklocked - // LockLevel of -255 means it's magic locked - item.SendLocalizedMessageTo( m_From, 502073 ); // This lock cannot be picked by normal means - return; - } + if (m_Item.LockLevel == 0 || m_Item.LockLevel == -255) + { + // LockLevel of 0 means that the door can't be picklocked + // LockLevel of -255 means it's magic locked + item.SendLocalizedMessageTo(m_From, 502073); // This lock cannot be picked by normal means + return; + } - if ( m_From.Skills[SkillName.Lockpicking].Value < m_Item.RequiredSkill ) - { - /* - // Do some training to gain skills - m_From.CheckSkill( SkillName.Lockpicking, 0, m_Item.LockLevel );*/ + if (m_From.Skills[SkillName.Lockpicking].Value < m_Item.RequiredSkill) + { + /* + // Do some training to gain skills + m_From.CheckSkill( SkillName.Lockpicking, 0, m_Item.LockLevel );*/ - // The LockLevel is higher thant the LockPicking of the player - item.SendLocalizedMessageTo( m_From, 502072 ); // You don't see how that lock can be manipulated. - return; - } + // The LockLevel is higher thant the LockPicking of the player + item.SendLocalizedMessageTo(m_From, 502072); // You don't see how that lock can be manipulated. + return; + } - if ( m_From.CheckTargetSkill( SkillName.Lockpicking, m_Item, m_Item.LockLevel, m_Item.MaxLockLevel ) ) - { - // Success! Pick the lock! - item.SendLocalizedMessageTo( m_From, 502076 ); // The lock quickly yields to your skill. - m_From.PlaySound( 0x4A ); - m_Item.LockPick( m_From ); - } - else - { - // The player failed to pick the lock - BrokeLockPickTest(); - item.SendLocalizedMessageTo( m_From, 502075 ); // You are unable to pick the lock. - } - } - } - } - } -} + if (m_From.CheckTargetSkill(SkillName.Lockpicking, m_Item, m_Item.LockLevel, m_Item.MaxLockLevel)) + { + // Success! Pick the lock! + item.SendLocalizedMessageTo(m_From, 502076); // The lock quickly yields to your skill. + m_From.PlaySound(0x4A); + m_Item.LockPick(m_From); + } + else + { + // The player failed to pick the lock + BrokeLockPickTest(); + item.SendLocalizedMessageTo(m_From, 502075); // You are unable to pick the lock. + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Axle.cs b/Scripts/Items/Skill Items/Tinkering/Axle.cs index a46c72d61..3d8c98da3 100644 --- a/Scripts/Items/Skill Items/Tinkering/Axle.cs +++ b/Scripts/Items/Skill Items/Tinkering/Axle.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x105B, 0x105C )] - public class Axle : Item - { - [Constructible] - public Axle() : this( 1 ) - { - } + [Flippable(0x105B, 0x105C)] + public class Axle : Item + { + [Constructible] + public Axle() : this(1) + { + } - [Constructible] - public Axle( int amount ) : base( 0x105B ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + [Constructible] + public Axle(int amount) : base(0x105B) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - public Axle( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Axle(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/AxleGears.cs b/Scripts/Items/Skill Items/Tinkering/AxleGears.cs index 03fb4aab6..fdab2f161 100644 --- a/Scripts/Items/Skill Items/Tinkering/AxleGears.cs +++ b/Scripts/Items/Skill Items/Tinkering/AxleGears.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x1051, 0x1052 )] - public class AxleGears : Item - { - [Constructible] - public AxleGears() : this( 1 ) - { - } + [Flippable(0x1051, 0x1052)] + public class AxleGears : Item + { + [Constructible] + public AxleGears() : this(1) + { + } - [Constructible] - public AxleGears( int amount ) : base( 0x1051 ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + [Constructible] + public AxleGears(int amount) : base(0x1051) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - public AxleGears( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public AxleGears(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/ClockFrame.cs b/Scripts/Items/Skill Items/Tinkering/ClockFrame.cs index fe23811f3..8658cbae6 100644 --- a/Scripts/Items/Skill Items/Tinkering/ClockFrame.cs +++ b/Scripts/Items/Skill Items/Tinkering/ClockFrame.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x104D, 0x104E )] - public class ClockFrame : Item - { - [Constructible] - public ClockFrame() : this( 1 ) - { - } + [Flippable(0x104D, 0x104E)] + public class ClockFrame : Item + { + [Constructible] + public ClockFrame() : this(1) + { + } - [Constructible] - public ClockFrame( int amount ) : base( 0x104D ) - { - Stackable = true; - Amount = amount; - Weight = 2.0; - } + [Constructible] + public ClockFrame(int amount) : base(0x104D) + { + Stackable = true; + Amount = amount; + Weight = 2.0; + } - public ClockFrame( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public ClockFrame(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/ClockParts.cs b/Scripts/Items/Skill Items/Tinkering/ClockParts.cs index 9ef1ad014..dcb4b6318 100644 --- a/Scripts/Items/Skill Items/Tinkering/ClockParts.cs +++ b/Scripts/Items/Skill Items/Tinkering/ClockParts.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x104F, 0x1050 )] - public class ClockParts : Item - { - [Constructible] - public ClockParts() : this( 1 ) - { - } + [Flippable(0x104F, 0x1050)] + public class ClockParts : Item + { + [Constructible] + public ClockParts() : this(1) + { + } - [Constructible] - public ClockParts( int amount ) : base( 0x104F ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + [Constructible] + public ClockParts(int amount) : base(0x104F) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - public ClockParts( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public ClockParts(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Clocks.cs b/Scripts/Items/Skill Items/Tinkering/Clocks.cs index f0725af8b..dcab00610 100644 --- a/Scripts/Items/Skill Items/Tinkering/Clocks.cs +++ b/Scripts/Items/Skill Items/Tinkering/Clocks.cs @@ -2,213 +2,213 @@ using System; namespace Server.Items { - public enum MoonPhase - { - NewMoon, - WaxingCrescentMoon, - FirstQuarter, - WaxingGibbous, - FullMoon, - WaningGibbous, - LastQuarter, - WaningCrescent - } + public enum MoonPhase + { + NewMoon, + WaxingCrescentMoon, + FirstQuarter, + WaxingGibbous, + FullMoon, + WaningGibbous, + LastQuarter, + WaningCrescent + } - [Flippable( 0x104B, 0x104C )] - public class Clock : Item - { - public static DateTime ServerStart { get; private set; } + [Flippable(0x104B, 0x104C)] + public class Clock : Item + { + public const double SecondsPerUOMinute = 5.0; + public const double MinutesPerUODay = SecondsPerUOMinute * 24; - public static void Initialize() - { - ServerStart = DateTime.UtcNow; - } + private static DateTime WorldStart = new DateTime(1997, 9, 1); - [Constructible] - public Clock() : this( 0x104B ) - { - } + [Constructible] + public Clock() : this(0x104B) + { + } - [Constructible] - public Clock( int itemID ) : base( itemID ) - { - Weight = 3.0; - } + [Constructible] + public Clock(int itemID) : base(itemID) + { + Weight = 3.0; + } - public Clock( Serial serial ) : base( serial ) - { - } + public Clock(Serial serial) : base(serial) + { + } - public const double SecondsPerUOMinute = 5.0; - public const double MinutesPerUODay = SecondsPerUOMinute * 24; + public static DateTime ServerStart{ get; private set; } - private static DateTime WorldStart = new DateTime( 1997, 9, 1 ); + public static void Initialize() + { + ServerStart = DateTime.UtcNow; + } - public static MoonPhase GetMoonPhase( Map map, int x, int y ) - { - int hours, minutes, totalMinutes; + public static MoonPhase GetMoonPhase(Map map, int x, int y) + { + int hours, minutes, totalMinutes; - GetTime( map, x, y, out hours, out minutes, out totalMinutes ); + GetTime(map, x, y, out hours, out minutes, out totalMinutes); - if ( map != null ) - totalMinutes /= 10 + (map.MapIndex * 20); + if (map != null) + totalMinutes /= 10 + map.MapIndex * 20; - return (MoonPhase)(totalMinutes % 8); - } + return (MoonPhase)(totalMinutes % 8); + } - public static void GetTime( Map map, int x, int y, out int hours, out int minutes ) - { - int totalMinutes; + public static void GetTime(Map map, int x, int y, out int hours, out int minutes) + { + int totalMinutes; - GetTime( map, x, y, out hours, out minutes, out totalMinutes ); - } + GetTime(map, x, y, out hours, out minutes, out totalMinutes); + } - public static void GetTime( Map map, int x, int y, out int hours, out int minutes, out int totalMinutes ) - { - TimeSpan timeSpan = DateTime.UtcNow - WorldStart; + public static void GetTime(Map map, int x, int y, out int hours, out int minutes, out int totalMinutes) + { + TimeSpan timeSpan = DateTime.UtcNow - WorldStart; - totalMinutes = (int)(timeSpan.TotalSeconds / SecondsPerUOMinute); + totalMinutes = (int)(timeSpan.TotalSeconds / SecondsPerUOMinute); - if ( map != null ) - totalMinutes += map.MapIndex * 320; + if (map != null) + totalMinutes += map.MapIndex * 320; - // Really on OSI this must be by subserver - totalMinutes += x / 16; + // Really on OSI this must be by subserver + totalMinutes += x / 16; - hours = (totalMinutes / 60) % 24; - minutes = totalMinutes % 60; - } + hours = totalMinutes / 60 % 24; + minutes = totalMinutes % 60; + } - public static void GetTime( out int generalNumber, out string exactTime ) - { - GetTime( null, 0, 0, out generalNumber, out exactTime ); - } + public static void GetTime(out int generalNumber, out string exactTime) + { + GetTime(null, 0, 0, out generalNumber, out exactTime); + } - public static void GetTime( Mobile from, out int generalNumber, out string exactTime ) - { - GetTime( from.Map, from.X, from.Y, out generalNumber, out exactTime ); - } + public static void GetTime(Mobile from, out int generalNumber, out string exactTime) + { + GetTime(from.Map, from.X, from.Y, out generalNumber, out exactTime); + } - public static void GetTime( Map map, int x, int y, out int generalNumber, out string exactTime ) - { - int hours, minutes; + public static void GetTime(Map map, int x, int y, out int generalNumber, out string exactTime) + { + int hours, minutes; - GetTime( map, x, y, out hours, out minutes ); + GetTime(map, x, y, out hours, out minutes); - // 00:00 AM - 00:59 AM : Witching hour - // 01:00 AM - 03:59 AM : Middle of night - // 04:00 AM - 07:59 AM : Early morning - // 08:00 AM - 11:59 AM : Late morning - // 12:00 PM - 12:59 PM : Noon - // 01:00 PM - 03:59 PM : Afternoon - // 04:00 PM - 07:59 PM : Early evening - // 08:00 PM - 11:59 AM : Late at night + // 00:00 AM - 00:59 AM : Witching hour + // 01:00 AM - 03:59 AM : Middle of night + // 04:00 AM - 07:59 AM : Early morning + // 08:00 AM - 11:59 AM : Late morning + // 12:00 PM - 12:59 PM : Noon + // 01:00 PM - 03:59 PM : Afternoon + // 04:00 PM - 07:59 PM : Early evening + // 08:00 PM - 11:59 AM : Late at night - if ( hours >= 20 ) - generalNumber = 1042957; // It's late at night - else if ( hours >= 16 ) - generalNumber = 1042956; // It's early in the evening - else if ( hours >= 13 ) - generalNumber = 1042955; // It's the afternoon - else if ( hours >= 12 ) - generalNumber = 1042954; // It's around noon - else if ( hours >= 08 ) - generalNumber = 1042953; // It's late in the morning - else if ( hours >= 04 ) - generalNumber = 1042952; // It's early in the morning - else if ( hours >= 01 ) - generalNumber = 1042951; // It's the middle of the night - else - generalNumber = 1042950; // 'Tis the witching hour. 12 Midnight. + if (hours >= 20) + generalNumber = 1042957; // It's late at night + else if (hours >= 16) + generalNumber = 1042956; // It's early in the evening + else if (hours >= 13) + generalNumber = 1042955; // It's the afternoon + else if (hours >= 12) + generalNumber = 1042954; // It's around noon + else if (hours >= 08) + generalNumber = 1042953; // It's late in the morning + else if (hours >= 04) + generalNumber = 1042952; // It's early in the morning + else if (hours >= 01) + generalNumber = 1042951; // It's the middle of the night + else + generalNumber = 1042950; // 'Tis the witching hour. 12 Midnight. - hours %= 12; + hours %= 12; - if ( hours == 0 ) - hours = 12; + if (hours == 0) + hours = 12; - exactTime = $"{hours}:{minutes:D2}"; - } + exactTime = $"{hours}:{minutes:D2}"; + } - public override void OnDoubleClick( Mobile from ) - { - int genericNumber; - string exactTime; + public override void OnDoubleClick(Mobile from) + { + int genericNumber; + string exactTime; - GetTime( from, out genericNumber, out exactTime ); + GetTime(from, out genericNumber, out exactTime); - SendLocalizedMessageTo( from, genericNumber ); - SendLocalizedMessageTo( from, 1042958, exactTime ); // ~1_TIME~ to be exact - } + SendLocalizedMessageTo(from, genericNumber); + SendLocalizedMessageTo(from, 1042958, exactTime); // ~1_TIME~ to be exact + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 3.0; - } - } + if (Weight == 2.0) + Weight = 3.0; + } + } - [Flippable( 0x104B, 0x104C )] - public class ClockRight : Clock - { - [Constructible] - public ClockRight() : base( 0x104B ) - { - } + [Flippable(0x104B, 0x104C)] + public class ClockRight : Clock + { + [Constructible] + public ClockRight() : base(0x104B) + { + } - public ClockRight( Serial serial ) : base( serial ) - { - } + public ClockRight(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x104B, 0x104C )] - public class ClockLeft : Clock - { - [Constructible] - public ClockLeft() : base( 0x104C ) - { - } + [Flippable(0x104B, 0x104C)] + public class ClockLeft : Clock + { + [Constructible] + public ClockLeft() : base(0x104C) + { + } - public ClockLeft( Serial serial ) : base( serial ) - { - } + public ClockLeft(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Gears.cs b/Scripts/Items/Skill Items/Tinkering/Gears.cs index 3640bf443..1aaecc7b0 100644 --- a/Scripts/Items/Skill Items/Tinkering/Gears.cs +++ b/Scripts/Items/Skill Items/Tinkering/Gears.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x1053, 0x1054 )] - public class Gears : Item - { - [Constructible] - public Gears() : this( 1 ) - { - } + [Flippable(0x1053, 0x1054)] + public class Gears : Item + { + [Constructible] + public Gears() : this(1) + { + } - [Constructible] - public Gears( int amount ) : base( 0x1053 ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + [Constructible] + public Gears(int amount) : base(0x1053) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - public Gears( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Gears(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Globe.cs b/Scripts/Items/Skill Items/Tinkering/Globe.cs index fc3fe4e3a..c2608840d 100644 --- a/Scripts/Items/Skill Items/Tinkering/Globe.cs +++ b/Scripts/Items/Skill Items/Tinkering/Globe.cs @@ -1,29 +1,29 @@ namespace Server.Items { - public class Globe : Item - { - [Constructible] - public Globe() : base( 0x1047 ) // It isn't flippable - { - Weight = 3.0; - } + public class Globe : Item + { + [Constructible] + public Globe() : base(0x1047) // It isn't flippable + { + Weight = 3.0; + } - public Globe( Serial serial ) : base( serial ) - { - } + public Globe(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Hinge.cs b/Scripts/Items/Skill Items/Tinkering/Hinge.cs index 48d325225..6dfb89d67 100644 --- a/Scripts/Items/Skill Items/Tinkering/Hinge.cs +++ b/Scripts/Items/Skill Items/Tinkering/Hinge.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x1055, 0x1056 )] - public class Hinge : Item - { - [Constructible] - public Hinge() : this( 1 ) - { - } + [Flippable(0x1055, 0x1056)] + public class Hinge : Item + { + [Constructible] + public Hinge() : this(1) + { + } - [Constructible] - public Hinge( int amount ) : base( 0x1055 ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + [Constructible] + public Hinge(int amount) : base(0x1055) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - public Hinge( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Hinge(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/SextantParts.cs b/Scripts/Items/Skill Items/Tinkering/SextantParts.cs index 475149af8..5eeb3d0a8 100644 --- a/Scripts/Items/Skill Items/Tinkering/SextantParts.cs +++ b/Scripts/Items/Skill Items/Tinkering/SextantParts.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x1059, 0x105A )] - public class SextantParts : Item - { - [Constructible] - public SextantParts() : this( 1 ) - { - } + [Flippable(0x1059, 0x105A)] + public class SextantParts : Item + { + [Constructible] + public SextantParts() : this(1) + { + } - [Constructible] - public SextantParts( int amount ) : base( 0x1059 ) - { - Stackable = true; - Amount = amount; - Weight = 2.0; - } + [Constructible] + public SextantParts(int amount) : base(0x1059) + { + Stackable = true; + Amount = amount; + Weight = 2.0; + } - public SextantParts( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public SextantParts(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Springs.cs b/Scripts/Items/Skill Items/Tinkering/Springs.cs index 77023c6aa..a9df9ac4e 100644 --- a/Scripts/Items/Skill Items/Tinkering/Springs.cs +++ b/Scripts/Items/Skill Items/Tinkering/Springs.cs @@ -1,36 +1,37 @@ namespace Server.Items { - [Flippable( 0x105D, 0x105E )] - public class Springs : Item - { - [Constructible] - public Springs() : this( 1 ) - { - } + [Flippable(0x105D, 0x105E)] + public class Springs : Item + { + [Constructible] + public Springs() : this(1) + { + } - [Constructible] - public Springs( int amount ) : base( 0x105D ) - { - Stackable = true; - Amount = amount; - Weight = 1.0; - } + [Constructible] + public Springs(int amount) : base(0x105D) + { + Stackable = true; + Amount = amount; + Weight = 1.0; + } - public Springs( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Springs(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Spyglass.cs b/Scripts/Items/Skill Items/Tinkering/Spyglass.cs index e2054da9c..f426b1e05 100644 --- a/Scripts/Items/Skill Items/Tinkering/Spyglass.cs +++ b/Scripts/Items/Skill Items/Tinkering/Spyglass.cs @@ -1,67 +1,71 @@ -using Server.Network; -using Server.Mobiles; using Server.Engines.Quests; using Server.Engines.Quests.Hag; +using Server.Mobiles; +using Server.Network; namespace Server.Items { - [Flippable( 0x14F5, 0x14F6 )] - public class Spyglass : Item - { - [Constructible] - public Spyglass() : base( 0x14F5 ) - { - Weight = 3.0; - } + [Flippable(0x14F5, 0x14F6)] + public class Spyglass : Item + { + [Constructible] + public Spyglass() : base(0x14F5) + { + Weight = 3.0; + } - public override void OnDoubleClick( Mobile from ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1008155 ); // You peer into the heavens, seeking the moons... + public Spyglass(Serial serial) : base(serial) + { + } - from.Send( new MessageLocalizedAffix( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 1008146 + (int)Clock.GetMoonPhase( Map.Trammel, from.X, from.Y ), "", AffixType.Prepend, "Trammel : ", "" ) ); - from.Send( new MessageLocalizedAffix( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 1008146 + (int)Clock.GetMoonPhase( Map.Felucca, from.X, from.Y ), "", AffixType.Prepend, "Felucca : ", "" ) ); + public override void OnDoubleClick(Mobile from) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1008155); // You peer into the heavens, seeking the moons... - if ( from is PlayerMobile player ) - { - QuestSystem qs = player.Quest; + from.Send(new MessageLocalizedAffix(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, + 1008146 + (int)Clock.GetMoonPhase(Map.Trammel, from.X, from.Y), "", AffixType.Prepend, "Trammel : ", "")); + from.Send(new MessageLocalizedAffix(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, + 1008146 + (int)Clock.GetMoonPhase(Map.Felucca, from.X, from.Y), "", AffixType.Prepend, "Felucca : ", "")); - if ( qs is WitchApprenticeQuest ) - { - if ( qs.FindObjective( typeof( FindIngredientObjective ) ) is FindIngredientObjective obj && !obj.Completed && obj.Ingredient == Ingredient.StarChart ) - { - Clock.GetTime( from.Map, from.X, from.Y, out int hours, out int _ ); + if (from is PlayerMobile player) + { + QuestSystem qs = player.Quest; - if ( hours < 5 || hours > 17 ) - { - player.SendLocalizedMessage( 1055040 ); // You gaze up into the glittering night sky. With great care, you compose a chart of the most prominent star patterns. + if (qs is WitchApprenticeQuest) + if (qs.FindObjective(typeof(FindIngredientObjective)) is FindIngredientObjective obj && !obj.Completed && + obj.Ingredient == Ingredient.StarChart) + { + Clock.GetTime(from.Map, from.X, from.Y, out int hours, out int _); - obj.Complete(); - } - else - { - player.SendLocalizedMessage( 1055039 ); // You gaze up into the sky, but it is not dark enough to see any stars. - } - } - } - } - } + if (hours < 5 || hours > 17) + { + player.SendLocalizedMessage( + 1055040); // You gaze up into the glittering night sky. With great care, you compose a chart of the most prominent star patterns. - public Spyglass( Serial serial ) : base( serial ) - { - } + obj.Complete(); + } + else + { + player.SendLocalizedMessage( + 1055039); // You gaze up into the sky, but it is not dark enough to see any stars. + } + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tinkering/Utensils.cs b/Scripts/Items/Skill Items/Tinkering/Utensils.cs index 1e3e0acb1..09ad722dd 100644 --- a/Scripts/Items/Skill Items/Tinkering/Utensils.cs +++ b/Scripts/Items/Skill Items/Tinkering/Utensils.cs @@ -1,275 +1,275 @@ namespace Server.Items { - [Flippable( 0x9F4, 0x9F5, 0x9A3, 0x9A4 )] - public class Fork : Item - { - [Constructible] - public Fork() : base( 0x9F4 ) - { - Weight = 1.0; - } + [Flippable(0x9F4, 0x9F5, 0x9A3, 0x9A4)] + public class Fork : Item + { + [Constructible] + public Fork() : base(0x9F4) + { + Weight = 1.0; + } - public Fork( Serial serial ) : base( serial ) - { - } + public Fork(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class ForkLeft : Item - { - [Constructible] - public ForkLeft() : base( 0x9F4 ) - { - Weight = 1.0; - } + public class ForkLeft : Item + { + [Constructible] + public ForkLeft() : base(0x9F4) + { + Weight = 1.0; + } - public ForkLeft( Serial serial ) : base( serial ) - { - } + public ForkLeft(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class ForkRight : Item - { - [Constructible] - public ForkRight() : base( 0x9F5 ) - { - Weight = 1.0; - } + public class ForkRight : Item + { + [Constructible] + public ForkRight() : base(0x9F5) + { + Weight = 1.0; + } - public ForkRight( Serial serial ) : base( serial ) - { - } + public ForkRight(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x9F8, 0x9F9, 0x9C2, 0x9C3 )] - public class Spoon : Item - { - [Constructible] - public Spoon() : base( 0x9F8 ) - { - Weight = 1.0; - } + [Flippable(0x9F8, 0x9F9, 0x9C2, 0x9C3)] + public class Spoon : Item + { + [Constructible] + public Spoon() : base(0x9F8) + { + Weight = 1.0; + } - public Spoon( Serial serial ) : base( serial ) - { - } + public Spoon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SpoonLeft : Item - { - [Constructible] - public SpoonLeft() : base( 0x9F8 ) - { - Weight = 1.0; - } + public class SpoonLeft : Item + { + [Constructible] + public SpoonLeft() : base(0x9F8) + { + Weight = 1.0; + } - public SpoonLeft( Serial serial ) : base( serial ) - { - } + public SpoonLeft(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class SpoonRight : Item - { - [Constructible] - public SpoonRight() : base( 0x9F9 ) - { - Weight = 1.0; - } + public class SpoonRight : Item + { + [Constructible] + public SpoonRight() : base(0x9F9) + { + Weight = 1.0; + } - public SpoonRight( Serial serial ) : base( serial ) - { - } + public SpoonRight(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - [Flippable( 0x9F6, 0x9F7, 0x9A5, 0x9A6 )] - public class Knife : Item - { - [Constructible] - public Knife() : base( 0x9F6 ) - { - Weight = 1.0; - } + [Flippable(0x9F6, 0x9F7, 0x9A5, 0x9A6)] + public class Knife : Item + { + [Constructible] + public Knife() : base(0x9F6) + { + Weight = 1.0; + } - public Knife( Serial serial ) : base( serial ) - { - } + public Knife(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class KnifeLeft : Item - { - [Constructible] - public KnifeLeft() : base( 0x9F6 ) - { - Weight = 1.0; - } + public class KnifeLeft : Item + { + [Constructible] + public KnifeLeft() : base(0x9F6) + { + Weight = 1.0; + } - public KnifeLeft( Serial serial ) : base( serial ) - { - } + public KnifeLeft(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class KnifeRight : Item - { - [Constructible] - public KnifeRight() : base( 0x9F7 ) - { - Weight = 1.0; - } + public class KnifeRight : Item + { + [Constructible] + public KnifeRight() : base(0x9F7) + { + Weight = 1.0; + } - public KnifeRight( Serial serial ) : base( serial ) - { - } + public KnifeRight(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Plate : Item - { - [Constructible] - public Plate() : base( 0x9D7 ) - { - Weight = 1.0; - } + public class Plate : Item + { + [Constructible] + public Plate() : base(0x9D7) + { + Weight = 1.0; + } - public Plate( Serial serial ) : base( serial ) - { - } + public Plate(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/BaseRunicTool.cs b/Scripts/Items/Skill Items/Tools/BaseRunicTool.cs index 4d8557a8e..f9b132e5a 100644 --- a/Scripts/Items/Skill Items/Tools/BaseRunicTool.cs +++ b/Scripts/Items/Skill Items/Tools/BaseRunicTool.cs @@ -4,678 +4,931 @@ using System.Collections.Generic; namespace Server.Items { - public abstract class BaseRunicTool : BaseTool - { - private CraftResource m_Resource; - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ m_Resource = value; Hue = CraftResources.GetHue( m_Resource ); InvalidateProperties(); } - } - - public BaseRunicTool( CraftResource resource, int itemID ) : base( itemID ) - { - m_Resource = resource; - } - - public BaseRunicTool( CraftResource resource, int uses, int itemID ) : base( uses, itemID ) - { - m_Resource = resource; - } - - public BaseRunicTool( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - writer.Write( (int) m_Resource ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Resource = (CraftResource)reader.ReadInt(); - break; - } - } - } - - private static bool m_IsRunicTool; - private static int m_LuckChance; - - private static int Scale( int min, int max, int low, int high ) - { - int percent; - - if ( m_IsRunicTool ) - { - percent = Utility.RandomMinMax( min, max ); - } - else - { - // Behold, the worst system ever! - int v = Utility.RandomMinMax( 0, 10000 ); - - v = (int) Math.Sqrt( v ); - v = 100 - v; - - if ( LootPack.CheckLuck( m_LuckChance ) ) - v += 10; - - if ( v < min ) - v = min; - else if ( v > max ) - v = max; - - percent = v; - } - - int scaledBy = Math.Abs( high - low ) + 1; - - if ( scaledBy != 0 ) - scaledBy = 10000 / scaledBy; - - percent *= (10000 + scaledBy); - - return low + (((high - low) * percent) / 1000001); - } - - private static void ApplyAttribute( AosAttributes attrs, int min, int max, AosAttribute attr, int low, int high ) - { - ApplyAttribute( attrs, min, max, attr, low, high, 1 ); - } - - private static void ApplyAttribute( AosAttributes attrs, int min, int max, AosAttribute attr, int low, int high, int scale ) - { - if ( attr == AosAttribute.CastSpeed ) - attrs[attr] += Scale( min, max, low / scale, high / scale ) * scale; - else - attrs[attr] = Scale( min, max, low / scale, high / scale ) * scale; - - if ( attr == AosAttribute.SpellChanneling ) - attrs[AosAttribute.CastSpeed] -= 1; - } - - private static void ApplyAttribute( AosArmorAttributes attrs, int min, int max, AosArmorAttribute attr, int low, int high ) - { - attrs[attr] = Scale( min, max, low, high ); - } - - private static void ApplyAttribute( AosArmorAttributes attrs, int min, int max, AosArmorAttribute attr, int low, int high, int scale ) - { - attrs[attr] = Scale( min, max, low / scale, high / scale ) * scale; - } - - private static void ApplyAttribute( AosWeaponAttributes attrs, int min, int max, AosWeaponAttribute attr, int low, int high ) - { - attrs[attr] = Scale( min, max, low, high ); - } - - private static void ApplyAttribute( AosWeaponAttributes attrs, int min, int max, AosWeaponAttribute attr, int low, int high, int scale ) - { - attrs[attr] = Scale( min, max, low / scale, high / scale ) * scale; - } - - private static void ApplyAttribute( AosElementAttributes attrs, int min, int max, AosElementAttribute attr, int low, int high ) - { - attrs[attr] = Scale( min, max, low, high ); - } - - private static void ApplyAttribute( AosElementAttributes attrs, int min, int max, AosElementAttribute attr, int low, int high, int scale ) - { - attrs[attr] = Scale( min, max, low / scale, high / scale ) * scale; - } - - private static SkillName[] m_PossibleBonusSkills = { - SkillName.Swords, - SkillName.Fencing, - SkillName.Macing, - SkillName.Archery, - SkillName.Wrestling, - SkillName.Parry, - SkillName.Tactics, - SkillName.Anatomy, - SkillName.Healing, - SkillName.Magery, - SkillName.Meditation, - SkillName.EvalInt, - SkillName.MagicResist, - SkillName.AnimalTaming, - SkillName.AnimalLore, - SkillName.Veterinary, - SkillName.Musicianship, - SkillName.Provocation, - SkillName.Discordance, - SkillName.Peacemaking, - SkillName.Chivalry, - SkillName.Focus, - SkillName.Necromancy, - SkillName.Stealing, - SkillName.Stealth, - SkillName.SpiritSpeak, - SkillName.Bushido, - SkillName.Ninjitsu - }; - - private static SkillName[] m_PossibleSpellbookSkills = { - SkillName.Magery, - SkillName.Meditation, - SkillName.EvalInt, - SkillName.MagicResist - }; - - private static void ApplySkillBonus( AosSkillBonuses attrs, int min, int max, int index, int low, int high ) - { - List possibleSkills = new List( attrs.Owner is Spellbook ? m_PossibleSpellbookSkills : m_PossibleBonusSkills ); - int count = ( Core.SE ? possibleSkills.Count : possibleSkills.Count - 2 ); - - SkillName sk, check; - double bonus; - bool found; - - do - { - found = false; - sk = possibleSkills[Utility.Random( count-- )]; - possibleSkills.Remove(sk); - - for ( int i = 0; !found && i < 5; ++i ) - found = ( attrs.GetValues( i, out check, out bonus ) && check == sk ); - } while ( found && count > 0 ); - - attrs.SetValues( index, sk, Scale( min, max, low, high ) ); - } - - private static void ApplyResistance( BaseArmor ar, int min, int max, ResistanceType res, int low, int high ) - { - switch ( res ) - { - case ResistanceType.Physical: ar.PhysicalBonus += Scale( min, max, low, high ); break; - case ResistanceType.Fire: ar.FireBonus += Scale( min, max, low, high ); break; - case ResistanceType.Cold: ar.ColdBonus += Scale( min, max, low, high ); break; - case ResistanceType.Poison: ar.PoisonBonus += Scale( min, max, low, high ); break; - case ResistanceType.Energy: ar.EnergyBonus += Scale( min, max, low, high ); break; - } - } - - private const int MaxProperties = 32; - private static BitArray m_Props = new BitArray( MaxProperties ); - private static int[] m_Possible = new int[MaxProperties]; - - public static int GetUniqueRandom( int count ) - { - int avail = 0; - - for ( int i = 0; i < count; ++i ) - { - if ( !m_Props[i] ) - m_Possible[avail++] = i; - } - - if ( avail == 0 ) - return -1; - - int v = m_Possible[Utility.Random( avail )]; - - m_Props.Set( v, true ); - - return v; - } - - public void ApplyAttributesTo( BaseWeapon weapon ) - { - CraftResourceInfo resInfo = CraftResources.GetInfo( m_Resource ); - - CraftAttributeInfo attrs = resInfo?.AttributeInfo; - - if ( attrs == null ) - return; - - int attributeCount = Utility.RandomMinMax( attrs.RunicMinAttributes, attrs.RunicMaxAttributes ); - int min = attrs.RunicMinIntensity; - int max = attrs.RunicMaxIntensity; - - ApplyAttributesTo( weapon, true, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( BaseWeapon weapon, int attributeCount, int min, int max ) - { - ApplyAttributesTo( weapon, false, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( BaseWeapon weapon, bool isRunicTool, int luckChance, int attributeCount, int min, int max ) - { - m_IsRunicTool = isRunicTool; - m_LuckChance = luckChance; - - AosAttributes primary = weapon.Attributes; - AosWeaponAttributes secondary = weapon.WeaponAttributes; - - m_Props.SetAll( false ); - - if ( weapon is BaseRanged ) - m_Props.Set( 2, true ); // ranged weapons cannot be ubws or mageweapon - - for ( int i = 0; i < attributeCount; ++i ) - { - int random = GetUniqueRandom( 25 ); - - if ( random == -1 ) - break; - - switch ( random ) - { - case 0: - { - switch ( Utility.Random( 5 ) ) - { - case 0: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitPhysicalArea,2, 50, 2 ); break; - case 1: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitFireArea, 2, 50, 2 ); break; - case 2: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitColdArea, 2, 50, 2 ); break; - case 3: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitPoisonArea, 2, 50, 2 ); break; - case 4: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitEnergyArea, 2, 50, 2 ); break; - } - - break; - } - case 1: - { - switch ( Utility.Random( 4 ) ) - { - case 0: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitMagicArrow, 2, 50, 2 ); break; - case 1: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitHarm, 2, 50, 2 ); break; - case 2: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitFireball, 2, 50, 2 ); break; - case 3: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitLightning, 2, 50, 2 ); break; - } - - break; - } - case 2: - { - switch ( Utility.Random( 2 ) ) - { - case 0: ApplyAttribute( secondary, min, max, AosWeaponAttribute.UseBestSkill, 1, 1 ); break; - case 1: ApplyAttribute( secondary, min, max, AosWeaponAttribute.MageWeapon, 1, 10 ); break; - } - - break; - } - case 3: ApplyAttribute( primary, min, max, AosAttribute.WeaponDamage, 1, 50 ); break; - case 4: ApplyAttribute( primary, min, max, AosAttribute.DefendChance, 1, 15 ); break; - case 5: ApplyAttribute( primary, min, max, AosAttribute.CastSpeed, 1, 1 ); break; - case 6: ApplyAttribute( primary, min, max, AosAttribute.AttackChance, 1, 15 ); break; - case 7: ApplyAttribute( primary, min, max, AosAttribute.Luck, 1, 100 ); break; - case 8: ApplyAttribute( primary, min, max, AosAttribute.WeaponSpeed, 5, 30, 5 ); break; - case 9: ApplyAttribute( primary, min, max, AosAttribute.SpellChanneling, 1, 1 ); break; - case 10: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitDispel, 2, 50, 2 ); break; - case 11: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitLeechHits, 2, 50, 2 ); break; - case 12: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitLowerAttack, 2, 50, 2 ); break; - case 13: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitLowerDefend, 2, 50, 2 ); break; - case 14: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitLeechMana, 2, 50, 2 ); break; - case 15: ApplyAttribute( secondary, min, max, AosWeaponAttribute.HitLeechStam, 2, 50, 2 ); break; - case 16: ApplyAttribute( secondary, min, max, AosWeaponAttribute.LowerStatReq, 10, 100, 10 ); break; - case 17: ApplyAttribute( secondary, min, max, AosWeaponAttribute.ResistPhysicalBonus, 1, 15 ); break; - case 18: ApplyAttribute( secondary, min, max, AosWeaponAttribute.ResistFireBonus, 1, 15 ); break; - case 19: ApplyAttribute( secondary, min, max, AosWeaponAttribute.ResistColdBonus, 1, 15 ); break; - case 20: ApplyAttribute( secondary, min, max, AosWeaponAttribute.ResistPoisonBonus, 1, 15 ); break; - case 21: ApplyAttribute( secondary, min, max, AosWeaponAttribute.ResistEnergyBonus, 1, 15 ); break; - case 22: ApplyAttribute( secondary, min, max, AosWeaponAttribute.DurabilityBonus, 10, 100, 10 ); break; - case 23: weapon.Slayer = GetRandomSlayer(); break; - case 24: GetElementalDamages( weapon ); break; - } - } - } - - public static void GetElementalDamages( BaseWeapon weapon ) - { - GetElementalDamages( weapon, true ); - } - - public static void GetElementalDamages( BaseWeapon weapon, bool randomizeOrder ) - { - int fire, phys, cold, nrgy, pois, chaos, direct; - - weapon.GetDamageTypes( null, out phys, out fire, out cold, out pois, out nrgy, out chaos, out direct ); - - int totalDamage = phys; - - AosElementAttribute[] attrs = { - AosElementAttribute.Cold, - AosElementAttribute.Energy, - AosElementAttribute.Fire, - AosElementAttribute.Poison - }; - - if ( randomizeOrder ) - { - for( int i = 0; i < attrs.Length; i++ ) - { - int rand = Utility.Random( attrs.Length ); - AosElementAttribute temp = attrs[i]; - - attrs[i] = attrs[rand]; - attrs[rand] = temp; - } - } - - - /* - totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Cold, totalDamage ); - totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Energy, totalDamage ); - totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Fire, totalDamage ); - totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Poison, totalDamage ); - - weapon.AosElementDamages[AosElementAttribute.Physical] = 100 - totalDamage; - * */ - - for( int i = 0; i < attrs.Length; i++ ) - totalDamage = AssignElementalDamage( weapon, attrs[i], totalDamage ); - - - //Order is Cold, Energy, Fire, Poison -> Physical left - //Cannot be looped, AoselementAttribute is 'out of order' - - weapon.Hue = weapon.GetElementalDamageHue(); - } - - private static int AssignElementalDamage( BaseWeapon weapon, AosElementAttribute attr, int totalDamage ) - { - if ( totalDamage <= 0 ) - return 0; - - int random = Utility.Random( (int)(totalDamage/10) + 1 ) * 10; - weapon.AosElementDamages[attr] = random; - - return (totalDamage - random); - } - - public static SlayerName GetRandomSlayer() - { - // TODO: Check random algorithm on OSI - - SlayerGroup[] groups = SlayerGroup.Groups; - - if ( groups.Length == 0 ) - return SlayerName.None; - - SlayerGroup group = groups[Utility.Random( groups.Length -1 )]; //-1 To Exclude the Fey Slayer which appears ONLY on a certain artifact. - SlayerEntry entry; - - if ( 10 > Utility.Random( 100 ) ) // 10% chance to do super slayer - { - entry = group.Super; - } - else - { - SlayerEntry[] entries = group.Entries; - - if ( entries.Length == 0 ) - return SlayerName.None; - - entry = entries[Utility.Random( entries.Length )]; - } - - return entry.Name; - } - - public void ApplyAttributesTo( BaseArmor armor ) - { - CraftResourceInfo resInfo = CraftResources.GetInfo( m_Resource ); - - CraftAttributeInfo attrs = resInfo?.AttributeInfo; - - if ( attrs == null ) - return; - - int attributeCount = Utility.RandomMinMax( attrs.RunicMinAttributes, attrs.RunicMaxAttributes ); - int min = attrs.RunicMinIntensity; - int max = attrs.RunicMaxIntensity; - - ApplyAttributesTo( armor, true, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( BaseArmor armor, int attributeCount, int min, int max ) - { - ApplyAttributesTo( armor, false, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( BaseArmor armor, bool isRunicTool, int luckChance, int attributeCount, int min, int max ) - { - m_IsRunicTool = isRunicTool; - m_LuckChance = luckChance; - - AosAttributes primary = armor.Attributes; - AosArmorAttributes secondary = armor.ArmorAttributes; - - m_Props.SetAll( false ); - - bool isShield = ( armor is BaseShield ); - int baseCount = ( isShield ? 7 : 20 ); - int baseOffset = ( isShield ? 0 : 4 ); - - if ( !isShield && armor.MeditationAllowance == ArmorMeditationAllowance.All ) - m_Props.Set( 3, true ); // remove mage armor from possible properties - if ( armor.Resource >= CraftResource.RegularLeather && armor.Resource <= CraftResource.BarbedLeather ) - { - m_Props.Set( 0, true ); // remove lower requirements from possible properties for leather armor - m_Props.Set( 2, true ); // remove durability bonus from possible properties - } - if ( armor.RequiredRace == Race.Elf ) - m_Props.Set( 7, true ); // elves inherently have night sight and elf only armor doesn't get night sight as a mod - - for ( int i = 0; i < attributeCount; ++i ) - { - int random = GetUniqueRandom( baseCount ); - - if ( random == -1 ) - break; - - random += baseOffset; - - switch ( random ) - { - /* Begin Sheilds */ - case 0: ApplyAttribute( primary, min, max, AosAttribute.SpellChanneling, 1, 1 ); break; - case 1: ApplyAttribute( primary, min, max, AosAttribute.DefendChance, 1, 15 ); break; - case 2: - if (Core.ML) { - ApplyAttribute( primary, min, max, AosAttribute.ReflectPhysical, 1, 15 ); - } else { - ApplyAttribute( primary, min, max, AosAttribute.AttackChance, 1, 15 ); - } - break; - case 3: ApplyAttribute( primary, min, max, AosAttribute.CastSpeed, 1, 1 ); break; - /* Begin Armor */ - case 4: ApplyAttribute( secondary, min, max, AosArmorAttribute.LowerStatReq, 10, 100, 10 ); break; - case 5: ApplyAttribute( secondary, min, max, AosArmorAttribute.SelfRepair, 1, 5 ); break; - case 6: ApplyAttribute( secondary, min, max, AosArmorAttribute.DurabilityBonus, 10, 100, 10 ); break; - /* End Shields */ - case 7: ApplyAttribute( secondary, min, max, AosArmorAttribute.MageArmor, 1, 1 ); break; - case 8: ApplyAttribute( primary, min, max, AosAttribute.RegenHits, 1, 2 ); break; - case 9: ApplyAttribute( primary, min, max, AosAttribute.RegenStam, 1, 3 ); break; - case 10: ApplyAttribute( primary, min, max, AosAttribute.RegenMana, 1, 2 ); break; - case 11: ApplyAttribute( primary, min, max, AosAttribute.NightSight, 1, 1 ); break; - case 12: ApplyAttribute( primary, min, max, AosAttribute.BonusHits, 1, 5 ); break; - case 13: ApplyAttribute( primary, min, max, AosAttribute.BonusStam, 1, 8 ); break; - case 14: ApplyAttribute( primary, min, max, AosAttribute.BonusMana, 1, 8 ); break; - case 15: ApplyAttribute( primary, min, max, AosAttribute.LowerManaCost, 1, 8 ); break; - case 16: ApplyAttribute( primary, min, max, AosAttribute.LowerRegCost, 1, 20 ); break; - case 17: ApplyAttribute( primary, min, max, AosAttribute.Luck, 1, 100 ); break; - case 18: ApplyAttribute( primary, min, max, AosAttribute.ReflectPhysical, 1, 15 ); break; - case 19: ApplyResistance( armor, min, max, ResistanceType.Physical, 1, 15 ); break; - case 20: ApplyResistance( armor, min, max, ResistanceType.Fire, 1, 15 ); break; - case 21: ApplyResistance( armor, min, max, ResistanceType.Cold, 1, 15 ); break; - case 22: ApplyResistance( armor, min, max, ResistanceType.Poison, 1, 15 ); break; - case 23: ApplyResistance( armor, min, max, ResistanceType.Energy, 1, 15 ); break; - /* End Armor */ - } - } - } - - public static void ApplyAttributesTo( BaseHat hat, int attributeCount, int min, int max ) - { - ApplyAttributesTo( hat, false, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( BaseHat hat, bool isRunicTool, int luckChance, int attributeCount, int min, int max ) - { - m_IsRunicTool = isRunicTool; - m_LuckChance = luckChance; - - AosAttributes primary = hat.Attributes; - AosArmorAttributes secondary = hat.ClothingAttributes; - AosElementAttributes resists = hat.Resistances; - - m_Props.SetAll( false ); - - for ( int i = 0; i < attributeCount; ++i ) - { - int random = GetUniqueRandom( 19 ); - - if ( random == -1 ) - break; - - switch ( random ) - { - case 0: ApplyAttribute( primary, min, max, AosAttribute.ReflectPhysical, 1, 15 ); break; - case 1: ApplyAttribute( primary, min, max, AosAttribute.RegenHits, 1, 2 ); break; - case 2: ApplyAttribute( primary, min, max, AosAttribute.RegenStam, 1, 3 ); break; - case 3: ApplyAttribute( primary, min, max, AosAttribute.RegenMana, 1, 2 ); break; - case 4: ApplyAttribute( primary, min, max, AosAttribute.NightSight, 1, 1 ); break; - case 5: ApplyAttribute( primary, min, max, AosAttribute.BonusHits, 1, 5 ); break; - case 6: ApplyAttribute( primary, min, max, AosAttribute.BonusStam, 1, 8 ); break; - case 7: ApplyAttribute( primary, min, max, AosAttribute.BonusMana, 1, 8 ); break; - case 8: ApplyAttribute( primary, min, max, AosAttribute.LowerManaCost, 1, 8 ); break; - case 9: ApplyAttribute( primary, min, max, AosAttribute.LowerRegCost, 1, 20 ); break; - case 10: ApplyAttribute( primary, min, max, AosAttribute.Luck, 1, 100 ); break; - case 11: ApplyAttribute( secondary, min, max, AosArmorAttribute.LowerStatReq, 10, 100, 10 ); break; - case 12: ApplyAttribute( secondary, min, max, AosArmorAttribute.SelfRepair, 1, 5 ); break; - case 13: ApplyAttribute( secondary, min, max, AosArmorAttribute.DurabilityBonus, 10, 100, 10 ); break; - case 14: ApplyAttribute( resists, min, max, AosElementAttribute.Physical, 1, 15 ); break; - case 15: ApplyAttribute( resists, min, max, AosElementAttribute.Fire, 1, 15 ); break; - case 16: ApplyAttribute( resists, min, max, AosElementAttribute.Cold, 1, 15 ); break; - case 17: ApplyAttribute( resists, min, max, AosElementAttribute.Poison, 1, 15 ); break; - case 18: ApplyAttribute( resists, min, max, AosElementAttribute.Energy, 1, 15 ); break; - } - } - } - - public static void ApplyAttributesTo( BaseJewel jewelry, int attributeCount, int min, int max ) - { - ApplyAttributesTo( jewelry, false, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( BaseJewel jewelry, bool isRunicTool, int luckChance, int attributeCount, int min, int max ) - { - m_IsRunicTool = isRunicTool; - m_LuckChance = luckChance; - - AosAttributes primary = jewelry.Attributes; - AosElementAttributes resists = jewelry.Resistances; - AosSkillBonuses skills = jewelry.SkillBonuses; - - m_Props.SetAll( false ); - - for ( int i = 0; i < attributeCount; ++i ) - { - int random = GetUniqueRandom( 24 ); - - if ( random == -1 ) - break; - - switch ( random ) - { - case 0: ApplyAttribute( resists, min, max, AosElementAttribute.Physical, 1, 15 ); break; - case 1: ApplyAttribute( resists, min, max, AosElementAttribute.Fire, 1, 15 ); break; - case 2: ApplyAttribute( resists, min, max, AosElementAttribute.Cold, 1, 15 ); break; - case 3: ApplyAttribute( resists, min, max, AosElementAttribute.Poison, 1, 15 ); break; - case 4: ApplyAttribute( resists, min, max, AosElementAttribute.Energy, 1, 15 ); break; - case 5: ApplyAttribute( primary, min, max, AosAttribute.WeaponDamage, 1, 25 ); break; - case 6: ApplyAttribute( primary, min, max, AosAttribute.DefendChance, 1, 15 ); break; - case 7: ApplyAttribute( primary, min, max, AosAttribute.AttackChance, 1, 15 ); break; - case 8: ApplyAttribute( primary, min, max, AosAttribute.BonusStr, 1, 8 ); break; - case 9: ApplyAttribute( primary, min, max, AosAttribute.BonusDex, 1, 8 ); break; - case 10: ApplyAttribute( primary, min, max, AosAttribute.BonusInt, 1, 8 ); break; - case 11: ApplyAttribute( primary, min, max, AosAttribute.EnhancePotions, 5, 25, 5 ); break; - case 12: ApplyAttribute( primary, min, max, AosAttribute.CastSpeed, 1, 1 ); break; - case 13: ApplyAttribute( primary, min, max, AosAttribute.CastRecovery, 1, 3 ); break; - case 14: ApplyAttribute( primary, min, max, AosAttribute.LowerManaCost, 1, 8 ); break; - case 15: ApplyAttribute( primary, min, max, AosAttribute.LowerRegCost, 1, 20 ); break; - case 16: ApplyAttribute( primary, min, max, AosAttribute.Luck, 1, 100 ); break; - case 17: ApplyAttribute( primary, min, max, AosAttribute.SpellDamage, 1, 12 ); break; - case 18: ApplyAttribute( primary, min, max, AosAttribute.NightSight, 1, 1 ); break; - case 19: ApplySkillBonus( skills, min, max, 0, 1, 15 ); break; - case 20: ApplySkillBonus( skills, min, max, 1, 1, 15 ); break; - case 21: ApplySkillBonus( skills, min, max, 2, 1, 15 ); break; - case 22: ApplySkillBonus( skills, min, max, 3, 1, 15 ); break; - case 23: ApplySkillBonus( skills, min, max, 4, 1, 15 ); break; - } - } - } - - public static void ApplyAttributesTo( Spellbook spellbook, int attributeCount, int min, int max ) - { - ApplyAttributesTo( spellbook, false, 0, attributeCount, min, max ); - } - - public static void ApplyAttributesTo( Spellbook spellbook, bool isRunicTool, int luckChance, int attributeCount, int min, int max ) - { - m_IsRunicTool = isRunicTool; - m_LuckChance = luckChance; - - AosAttributes primary = spellbook.Attributes; - AosSkillBonuses skills = spellbook.SkillBonuses; - - m_Props.SetAll( false ); - - for ( int i = 0; i < attributeCount; ++i ) - { - int random = GetUniqueRandom( 16 ); - - if ( random == -1 ) - break; - - switch ( random ) - { - case 0: - case 1: - case 2: - case 3: - { - ApplyAttribute( primary, min, max, AosAttribute.BonusInt, 1, 8 ); - - for ( int j = 0; j < 4; ++j ) - m_Props.Set( j, true ); - - break; - } - case 4: ApplyAttribute( primary, min, max, AosAttribute.BonusMana, 1, 8 ); break; - case 5: ApplyAttribute( primary, min, max, AosAttribute.CastSpeed, 1, 1 ); break; - case 6: ApplyAttribute( primary, min, max, AosAttribute.CastRecovery, 1, 3 ); break; - case 7: ApplyAttribute( primary, min, max, AosAttribute.SpellDamage, 1, 12 ); break; - case 8: ApplySkillBonus( skills, min, max, 0, 1, 15 ); break; - case 9: ApplySkillBonus( skills, min, max, 1, 1, 15 ); break; - case 10: ApplySkillBonus( skills, min, max, 2, 1, 15 ); break; - case 11: ApplySkillBonus( skills, min, max, 3, 1, 15 ); break; - case 12: ApplyAttribute( primary, min, max, AosAttribute.LowerRegCost, 1, 20 ); break; - case 13: ApplyAttribute( primary, min, max, AosAttribute.LowerManaCost, 1, 8 ); break; - case 14: ApplyAttribute( primary, min, max, AosAttribute.RegenMana, 1, 2 ); break; - case 15: spellbook.Slayer = GetRandomSlayer(); break; - } - } - } - } -} + public abstract class BaseRunicTool : BaseTool + { + private const int MaxProperties = 32; + + private static bool m_IsRunicTool; + private static int m_LuckChance; + + private static SkillName[] m_PossibleBonusSkills = + { + SkillName.Swords, + SkillName.Fencing, + SkillName.Macing, + SkillName.Archery, + SkillName.Wrestling, + SkillName.Parry, + SkillName.Tactics, + SkillName.Anatomy, + SkillName.Healing, + SkillName.Magery, + SkillName.Meditation, + SkillName.EvalInt, + SkillName.MagicResist, + SkillName.AnimalTaming, + SkillName.AnimalLore, + SkillName.Veterinary, + SkillName.Musicianship, + SkillName.Provocation, + SkillName.Discordance, + SkillName.Peacemaking, + SkillName.Chivalry, + SkillName.Focus, + SkillName.Necromancy, + SkillName.Stealing, + SkillName.Stealth, + SkillName.SpiritSpeak, + SkillName.Bushido, + SkillName.Ninjitsu + }; + + private static SkillName[] m_PossibleSpellbookSkills = + { + SkillName.Magery, + SkillName.Meditation, + SkillName.EvalInt, + SkillName.MagicResist + }; + + private static BitArray m_Props = new BitArray(MaxProperties); + private static int[] m_Possible = new int[MaxProperties]; + private CraftResource m_Resource; + + public BaseRunicTool(CraftResource resource, int itemID) : base(itemID) + { + m_Resource = resource; + } + + public BaseRunicTool(CraftResource resource, int uses, int itemID) : base(uses, itemID) + { + m_Resource = resource; + } + + public BaseRunicTool(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + InvalidateProperties(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + writer.Write((int)m_Resource); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Resource = (CraftResource)reader.ReadInt(); + break; + } + } + } + + private static int Scale(int min, int max, int low, int high) + { + int percent; + + if (m_IsRunicTool) + { + percent = Utility.RandomMinMax(min, max); + } + else + { + // Behold, the worst system ever! + int v = Utility.RandomMinMax(0, 10000); + + v = (int)Math.Sqrt(v); + v = 100 - v; + + if (LootPack.CheckLuck(m_LuckChance)) + v += 10; + + if (v < min) + v = min; + else if (v > max) + v = max; + + percent = v; + } + + int scaledBy = Math.Abs(high - low) + 1; + + if (scaledBy != 0) + scaledBy = 10000 / scaledBy; + + percent *= 10000 + scaledBy; + + return low + (high - low) * percent / 1000001; + } + + private static void ApplyAttribute(AosAttributes attrs, int min, int max, AosAttribute attr, int low, int high) + { + ApplyAttribute(attrs, min, max, attr, low, high, 1); + } + + private static void ApplyAttribute(AosAttributes attrs, int min, int max, AosAttribute attr, int low, int high, + int scale) + { + if (attr == AosAttribute.CastSpeed) + attrs[attr] += Scale(min, max, low / scale, high / scale) * scale; + else + attrs[attr] = Scale(min, max, low / scale, high / scale) * scale; + + if (attr == AosAttribute.SpellChanneling) + attrs[AosAttribute.CastSpeed] -= 1; + } + + private static void ApplyAttribute(AosArmorAttributes attrs, int min, int max, AosArmorAttribute attr, int low, + int high) + { + attrs[attr] = Scale(min, max, low, high); + } + + private static void ApplyAttribute(AosArmorAttributes attrs, int min, int max, AosArmorAttribute attr, int low, + int high, int scale) + { + attrs[attr] = Scale(min, max, low / scale, high / scale) * scale; + } + + private static void ApplyAttribute(AosWeaponAttributes attrs, int min, int max, AosWeaponAttribute attr, int low, + int high) + { + attrs[attr] = Scale(min, max, low, high); + } + + private static void ApplyAttribute(AosWeaponAttributes attrs, int min, int max, AosWeaponAttribute attr, int low, + int high, int scale) + { + attrs[attr] = Scale(min, max, low / scale, high / scale) * scale; + } + + private static void ApplyAttribute(AosElementAttributes attrs, int min, int max, AosElementAttribute attr, int low, + int high) + { + attrs[attr] = Scale(min, max, low, high); + } + + private static void ApplyAttribute(AosElementAttributes attrs, int min, int max, AosElementAttribute attr, int low, + int high, int scale) + { + attrs[attr] = Scale(min, max, low / scale, high / scale) * scale; + } + + private static void ApplySkillBonus(AosSkillBonuses attrs, int min, int max, int index, int low, int high) + { + List possibleSkills = + new List(attrs.Owner is Spellbook ? m_PossibleSpellbookSkills : m_PossibleBonusSkills); + int count = Core.SE ? possibleSkills.Count : possibleSkills.Count - 2; + + SkillName sk, check; + double bonus; + bool found; + + do + { + found = false; + sk = possibleSkills[Utility.Random(count--)]; + possibleSkills.Remove(sk); + + for (int i = 0; !found && i < 5; ++i) + found = attrs.GetValues(i, out check, out bonus) && check == sk; + } while (found && count > 0); + + attrs.SetValues(index, sk, Scale(min, max, low, high)); + } + + private static void ApplyResistance(BaseArmor ar, int min, int max, ResistanceType res, int low, int high) + { + switch (res) + { + case ResistanceType.Physical: + ar.PhysicalBonus += Scale(min, max, low, high); + break; + case ResistanceType.Fire: + ar.FireBonus += Scale(min, max, low, high); + break; + case ResistanceType.Cold: + ar.ColdBonus += Scale(min, max, low, high); + break; + case ResistanceType.Poison: + ar.PoisonBonus += Scale(min, max, low, high); + break; + case ResistanceType.Energy: + ar.EnergyBonus += Scale(min, max, low, high); + break; + } + } + + public static int GetUniqueRandom(int count) + { + int avail = 0; + + for (int i = 0; i < count; ++i) + if (!m_Props[i]) + m_Possible[avail++] = i; + + if (avail == 0) + return -1; + + int v = m_Possible[Utility.Random(avail)]; + + m_Props.Set(v, true); + + return v; + } + + public void ApplyAttributesTo(BaseWeapon weapon) + { + CraftResourceInfo resInfo = CraftResources.GetInfo(m_Resource); + + CraftAttributeInfo attrs = resInfo?.AttributeInfo; + + if (attrs == null) + return; + + int attributeCount = Utility.RandomMinMax(attrs.RunicMinAttributes, attrs.RunicMaxAttributes); + int min = attrs.RunicMinIntensity; + int max = attrs.RunicMaxIntensity; + + ApplyAttributesTo(weapon, true, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(BaseWeapon weapon, int attributeCount, int min, int max) + { + ApplyAttributesTo(weapon, false, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(BaseWeapon weapon, bool isRunicTool, int luckChance, int attributeCount, + int min, int max) + { + m_IsRunicTool = isRunicTool; + m_LuckChance = luckChance; + + AosAttributes primary = weapon.Attributes; + AosWeaponAttributes secondary = weapon.WeaponAttributes; + + m_Props.SetAll(false); + + if (weapon is BaseRanged) + m_Props.Set(2, true); // ranged weapons cannot be ubws or mageweapon + + for (int i = 0; i < attributeCount; ++i) + { + int random = GetUniqueRandom(25); + + if (random == -1) + break; + + switch (random) + { + case 0: + { + switch (Utility.Random(5)) + { + case 0: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitPhysicalArea, 2, 50, 2); + break; + case 1: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitFireArea, 2, 50, 2); + break; + case 2: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitColdArea, 2, 50, 2); + break; + case 3: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitPoisonArea, 2, 50, 2); + break; + case 4: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitEnergyArea, 2, 50, 2); + break; + } + + break; + } + case 1: + { + switch (Utility.Random(4)) + { + case 0: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitMagicArrow, 2, 50, 2); + break; + case 1: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitHarm, 2, 50, 2); + break; + case 2: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitFireball, 2, 50, 2); + break; + case 3: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitLightning, 2, 50, 2); + break; + } + + break; + } + case 2: + { + switch (Utility.Random(2)) + { + case 0: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.UseBestSkill, 1, 1); + break; + case 1: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.MageWeapon, 1, 10); + break; + } + + break; + } + case 3: + ApplyAttribute(primary, min, max, AosAttribute.WeaponDamage, 1, 50); + break; + case 4: + ApplyAttribute(primary, min, max, AosAttribute.DefendChance, 1, 15); + break; + case 5: + ApplyAttribute(primary, min, max, AosAttribute.CastSpeed, 1, 1); + break; + case 6: + ApplyAttribute(primary, min, max, AosAttribute.AttackChance, 1, 15); + break; + case 7: + ApplyAttribute(primary, min, max, AosAttribute.Luck, 1, 100); + break; + case 8: + ApplyAttribute(primary, min, max, AosAttribute.WeaponSpeed, 5, 30, 5); + break; + case 9: + ApplyAttribute(primary, min, max, AosAttribute.SpellChanneling, 1, 1); + break; + case 10: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitDispel, 2, 50, 2); + break; + case 11: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitLeechHits, 2, 50, 2); + break; + case 12: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitLowerAttack, 2, 50, 2); + break; + case 13: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitLowerDefend, 2, 50, 2); + break; + case 14: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitLeechMana, 2, 50, 2); + break; + case 15: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.HitLeechStam, 2, 50, 2); + break; + case 16: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.LowerStatReq, 10, 100, 10); + break; + case 17: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.ResistPhysicalBonus, 1, 15); + break; + case 18: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.ResistFireBonus, 1, 15); + break; + case 19: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.ResistColdBonus, 1, 15); + break; + case 20: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.ResistPoisonBonus, 1, 15); + break; + case 21: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.ResistEnergyBonus, 1, 15); + break; + case 22: + ApplyAttribute(secondary, min, max, AosWeaponAttribute.DurabilityBonus, 10, 100, 10); + break; + case 23: + weapon.Slayer = GetRandomSlayer(); + break; + case 24: + GetElementalDamages(weapon); + break; + } + } + } + + public static void GetElementalDamages(BaseWeapon weapon) + { + GetElementalDamages(weapon, true); + } + + public static void GetElementalDamages(BaseWeapon weapon, bool randomizeOrder) + { + int fire, phys, cold, nrgy, pois, chaos, direct; + + weapon.GetDamageTypes(null, out phys, out fire, out cold, out pois, out nrgy, out chaos, out direct); + + int totalDamage = phys; + + AosElementAttribute[] attrs = + { + AosElementAttribute.Cold, + AosElementAttribute.Energy, + AosElementAttribute.Fire, + AosElementAttribute.Poison + }; + + if (randomizeOrder) + for (int i = 0; i < attrs.Length; i++) + { + int rand = Utility.Random(attrs.Length); + AosElementAttribute temp = attrs[i]; + + attrs[i] = attrs[rand]; + attrs[rand] = temp; + } + + + /* + totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Cold, totalDamage ); + totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Energy, totalDamage ); + totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Fire, totalDamage ); + totalDamage = AssignElementalDamage( weapon, AosElementAttribute.Poison, totalDamage ); + + weapon.AosElementDamages[AosElementAttribute.Physical] = 100 - totalDamage; + * */ + + for (int i = 0; i < attrs.Length; i++) + totalDamage = AssignElementalDamage(weapon, attrs[i], totalDamage); + + + //Order is Cold, Energy, Fire, Poison -> Physical left + //Cannot be looped, AoselementAttribute is 'out of order' + + weapon.Hue = weapon.GetElementalDamageHue(); + } + + private static int AssignElementalDamage(BaseWeapon weapon, AosElementAttribute attr, int totalDamage) + { + if (totalDamage <= 0) + return 0; + + int random = Utility.Random(totalDamage / 10 + 1) * 10; + weapon.AosElementDamages[attr] = random; + + return totalDamage - random; + } + + public static SlayerName GetRandomSlayer() + { + // TODO: Check random algorithm on OSI + + SlayerGroup[] groups = SlayerGroup.Groups; + + if (groups.Length == 0) + return SlayerName.None; + + SlayerGroup + group = groups[ + Utility.Random(groups.Length - + 1)]; //-1 To Exclude the Fey Slayer which appears ONLY on a certain artifact. + SlayerEntry entry; + + if (10 > Utility.Random(100)) // 10% chance to do super slayer + { + entry = group.Super; + } + else + { + SlayerEntry[] entries = group.Entries; + + if (entries.Length == 0) + return SlayerName.None; + + entry = entries[Utility.Random(entries.Length)]; + } + + return entry.Name; + } + + public void ApplyAttributesTo(BaseArmor armor) + { + CraftResourceInfo resInfo = CraftResources.GetInfo(m_Resource); + + CraftAttributeInfo attrs = resInfo?.AttributeInfo; + + if (attrs == null) + return; + + int attributeCount = Utility.RandomMinMax(attrs.RunicMinAttributes, attrs.RunicMaxAttributes); + int min = attrs.RunicMinIntensity; + int max = attrs.RunicMaxIntensity; + + ApplyAttributesTo(armor, true, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(BaseArmor armor, int attributeCount, int min, int max) + { + ApplyAttributesTo(armor, false, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(BaseArmor armor, bool isRunicTool, int luckChance, int attributeCount, int min, + int max) + { + m_IsRunicTool = isRunicTool; + m_LuckChance = luckChance; + + AosAttributes primary = armor.Attributes; + AosArmorAttributes secondary = armor.ArmorAttributes; + + m_Props.SetAll(false); + + bool isShield = armor is BaseShield; + int baseCount = isShield ? 7 : 20; + int baseOffset = isShield ? 0 : 4; + + if (!isShield && armor.MeditationAllowance == ArmorMeditationAllowance.All) + m_Props.Set(3, true); // remove mage armor from possible properties + if (armor.Resource >= CraftResource.RegularLeather && armor.Resource <= CraftResource.BarbedLeather) + { + m_Props.Set(0, true); // remove lower requirements from possible properties for leather armor + m_Props.Set(2, true); // remove durability bonus from possible properties + } + + if (armor.RequiredRace == Race.Elf) + m_Props.Set(7, + true); // elves inherently have night sight and elf only armor doesn't get night sight as a mod + + for (int i = 0; i < attributeCount; ++i) + { + int random = GetUniqueRandom(baseCount); + + if (random == -1) + break; + + random += baseOffset; + + switch (random) + { + /* Begin Sheilds */ + case 0: + ApplyAttribute(primary, min, max, AosAttribute.SpellChanneling, 1, 1); + break; + case 1: + ApplyAttribute(primary, min, max, AosAttribute.DefendChance, 1, 15); + break; + case 2: + if (Core.ML) + ApplyAttribute(primary, min, max, AosAttribute.ReflectPhysical, 1, 15); + else + ApplyAttribute(primary, min, max, AosAttribute.AttackChance, 1, 15); + break; + case 3: + ApplyAttribute(primary, min, max, AosAttribute.CastSpeed, 1, 1); + break; + /* Begin Armor */ + case 4: + ApplyAttribute(secondary, min, max, AosArmorAttribute.LowerStatReq, 10, 100, 10); + break; + case 5: + ApplyAttribute(secondary, min, max, AosArmorAttribute.SelfRepair, 1, 5); + break; + case 6: + ApplyAttribute(secondary, min, max, AosArmorAttribute.DurabilityBonus, 10, 100, 10); + break; + /* End Shields */ + case 7: + ApplyAttribute(secondary, min, max, AosArmorAttribute.MageArmor, 1, 1); + break; + case 8: + ApplyAttribute(primary, min, max, AosAttribute.RegenHits, 1, 2); + break; + case 9: + ApplyAttribute(primary, min, max, AosAttribute.RegenStam, 1, 3); + break; + case 10: + ApplyAttribute(primary, min, max, AosAttribute.RegenMana, 1, 2); + break; + case 11: + ApplyAttribute(primary, min, max, AosAttribute.NightSight, 1, 1); + break; + case 12: + ApplyAttribute(primary, min, max, AosAttribute.BonusHits, 1, 5); + break; + case 13: + ApplyAttribute(primary, min, max, AosAttribute.BonusStam, 1, 8); + break; + case 14: + ApplyAttribute(primary, min, max, AosAttribute.BonusMana, 1, 8); + break; + case 15: + ApplyAttribute(primary, min, max, AosAttribute.LowerManaCost, 1, 8); + break; + case 16: + ApplyAttribute(primary, min, max, AosAttribute.LowerRegCost, 1, 20); + break; + case 17: + ApplyAttribute(primary, min, max, AosAttribute.Luck, 1, 100); + break; + case 18: + ApplyAttribute(primary, min, max, AosAttribute.ReflectPhysical, 1, 15); + break; + case 19: + ApplyResistance(armor, min, max, ResistanceType.Physical, 1, 15); + break; + case 20: + ApplyResistance(armor, min, max, ResistanceType.Fire, 1, 15); + break; + case 21: + ApplyResistance(armor, min, max, ResistanceType.Cold, 1, 15); + break; + case 22: + ApplyResistance(armor, min, max, ResistanceType.Poison, 1, 15); + break; + case 23: + ApplyResistance(armor, min, max, ResistanceType.Energy, 1, 15); + break; + /* End Armor */ + } + } + } + + public static void ApplyAttributesTo(BaseHat hat, int attributeCount, int min, int max) + { + ApplyAttributesTo(hat, false, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(BaseHat hat, bool isRunicTool, int luckChance, int attributeCount, int min, + int max) + { + m_IsRunicTool = isRunicTool; + m_LuckChance = luckChance; + + AosAttributes primary = hat.Attributes; + AosArmorAttributes secondary = hat.ClothingAttributes; + AosElementAttributes resists = hat.Resistances; + + m_Props.SetAll(false); + + for (int i = 0; i < attributeCount; ++i) + { + int random = GetUniqueRandom(19); + + if (random == -1) + break; + + switch (random) + { + case 0: + ApplyAttribute(primary, min, max, AosAttribute.ReflectPhysical, 1, 15); + break; + case 1: + ApplyAttribute(primary, min, max, AosAttribute.RegenHits, 1, 2); + break; + case 2: + ApplyAttribute(primary, min, max, AosAttribute.RegenStam, 1, 3); + break; + case 3: + ApplyAttribute(primary, min, max, AosAttribute.RegenMana, 1, 2); + break; + case 4: + ApplyAttribute(primary, min, max, AosAttribute.NightSight, 1, 1); + break; + case 5: + ApplyAttribute(primary, min, max, AosAttribute.BonusHits, 1, 5); + break; + case 6: + ApplyAttribute(primary, min, max, AosAttribute.BonusStam, 1, 8); + break; + case 7: + ApplyAttribute(primary, min, max, AosAttribute.BonusMana, 1, 8); + break; + case 8: + ApplyAttribute(primary, min, max, AosAttribute.LowerManaCost, 1, 8); + break; + case 9: + ApplyAttribute(primary, min, max, AosAttribute.LowerRegCost, 1, 20); + break; + case 10: + ApplyAttribute(primary, min, max, AosAttribute.Luck, 1, 100); + break; + case 11: + ApplyAttribute(secondary, min, max, AosArmorAttribute.LowerStatReq, 10, 100, 10); + break; + case 12: + ApplyAttribute(secondary, min, max, AosArmorAttribute.SelfRepair, 1, 5); + break; + case 13: + ApplyAttribute(secondary, min, max, AosArmorAttribute.DurabilityBonus, 10, 100, 10); + break; + case 14: + ApplyAttribute(resists, min, max, AosElementAttribute.Physical, 1, 15); + break; + case 15: + ApplyAttribute(resists, min, max, AosElementAttribute.Fire, 1, 15); + break; + case 16: + ApplyAttribute(resists, min, max, AosElementAttribute.Cold, 1, 15); + break; + case 17: + ApplyAttribute(resists, min, max, AosElementAttribute.Poison, 1, 15); + break; + case 18: + ApplyAttribute(resists, min, max, AosElementAttribute.Energy, 1, 15); + break; + } + } + } + + public static void ApplyAttributesTo(BaseJewel jewelry, int attributeCount, int min, int max) + { + ApplyAttributesTo(jewelry, false, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(BaseJewel jewelry, bool isRunicTool, int luckChance, int attributeCount, + int min, int max) + { + m_IsRunicTool = isRunicTool; + m_LuckChance = luckChance; + + AosAttributes primary = jewelry.Attributes; + AosElementAttributes resists = jewelry.Resistances; + AosSkillBonuses skills = jewelry.SkillBonuses; + + m_Props.SetAll(false); + + for (int i = 0; i < attributeCount; ++i) + { + int random = GetUniqueRandom(24); + + if (random == -1) + break; + + switch (random) + { + case 0: + ApplyAttribute(resists, min, max, AosElementAttribute.Physical, 1, 15); + break; + case 1: + ApplyAttribute(resists, min, max, AosElementAttribute.Fire, 1, 15); + break; + case 2: + ApplyAttribute(resists, min, max, AosElementAttribute.Cold, 1, 15); + break; + case 3: + ApplyAttribute(resists, min, max, AosElementAttribute.Poison, 1, 15); + break; + case 4: + ApplyAttribute(resists, min, max, AosElementAttribute.Energy, 1, 15); + break; + case 5: + ApplyAttribute(primary, min, max, AosAttribute.WeaponDamage, 1, 25); + break; + case 6: + ApplyAttribute(primary, min, max, AosAttribute.DefendChance, 1, 15); + break; + case 7: + ApplyAttribute(primary, min, max, AosAttribute.AttackChance, 1, 15); + break; + case 8: + ApplyAttribute(primary, min, max, AosAttribute.BonusStr, 1, 8); + break; + case 9: + ApplyAttribute(primary, min, max, AosAttribute.BonusDex, 1, 8); + break; + case 10: + ApplyAttribute(primary, min, max, AosAttribute.BonusInt, 1, 8); + break; + case 11: + ApplyAttribute(primary, min, max, AosAttribute.EnhancePotions, 5, 25, 5); + break; + case 12: + ApplyAttribute(primary, min, max, AosAttribute.CastSpeed, 1, 1); + break; + case 13: + ApplyAttribute(primary, min, max, AosAttribute.CastRecovery, 1, 3); + break; + case 14: + ApplyAttribute(primary, min, max, AosAttribute.LowerManaCost, 1, 8); + break; + case 15: + ApplyAttribute(primary, min, max, AosAttribute.LowerRegCost, 1, 20); + break; + case 16: + ApplyAttribute(primary, min, max, AosAttribute.Luck, 1, 100); + break; + case 17: + ApplyAttribute(primary, min, max, AosAttribute.SpellDamage, 1, 12); + break; + case 18: + ApplyAttribute(primary, min, max, AosAttribute.NightSight, 1, 1); + break; + case 19: + ApplySkillBonus(skills, min, max, 0, 1, 15); + break; + case 20: + ApplySkillBonus(skills, min, max, 1, 1, 15); + break; + case 21: + ApplySkillBonus(skills, min, max, 2, 1, 15); + break; + case 22: + ApplySkillBonus(skills, min, max, 3, 1, 15); + break; + case 23: + ApplySkillBonus(skills, min, max, 4, 1, 15); + break; + } + } + } + + public static void ApplyAttributesTo(Spellbook spellbook, int attributeCount, int min, int max) + { + ApplyAttributesTo(spellbook, false, 0, attributeCount, min, max); + } + + public static void ApplyAttributesTo(Spellbook spellbook, bool isRunicTool, int luckChance, int attributeCount, + int min, int max) + { + m_IsRunicTool = isRunicTool; + m_LuckChance = luckChance; + + AosAttributes primary = spellbook.Attributes; + AosSkillBonuses skills = spellbook.SkillBonuses; + + m_Props.SetAll(false); + + for (int i = 0; i < attributeCount; ++i) + { + int random = GetUniqueRandom(16); + + if (random == -1) + break; + + switch (random) + { + case 0: + case 1: + case 2: + case 3: + { + ApplyAttribute(primary, min, max, AosAttribute.BonusInt, 1, 8); + + for (int j = 0; j < 4; ++j) + m_Props.Set(j, true); + + break; + } + case 4: + ApplyAttribute(primary, min, max, AosAttribute.BonusMana, 1, 8); + break; + case 5: + ApplyAttribute(primary, min, max, AosAttribute.CastSpeed, 1, 1); + break; + case 6: + ApplyAttribute(primary, min, max, AosAttribute.CastRecovery, 1, 3); + break; + case 7: + ApplyAttribute(primary, min, max, AosAttribute.SpellDamage, 1, 12); + break; + case 8: + ApplySkillBonus(skills, min, max, 0, 1, 15); + break; + case 9: + ApplySkillBonus(skills, min, max, 1, 1, 15); + break; + case 10: + ApplySkillBonus(skills, min, max, 2, 1, 15); + break; + case 11: + ApplySkillBonus(skills, min, max, 3, 1, 15); + break; + case 12: + ApplyAttribute(primary, min, max, AosAttribute.LowerRegCost, 1, 20); + break; + case 13: + ApplyAttribute(primary, min, max, AosAttribute.LowerManaCost, 1, 8); + break; + case 14: + ApplyAttribute(primary, min, max, AosAttribute.RegenMana, 1, 2); + break; + case 15: + spellbook.Slayer = GetRandomSlayer(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/BaseTool.cs b/Scripts/Items/Skill Items/Tools/BaseTool.cs index 3b7207010..861e052b6 100644 --- a/Scripts/Items/Skill Items/Tools/BaseTool.cs +++ b/Scripts/Items/Skill Items/Tools/BaseTool.cs @@ -1,199 +1,219 @@ using System; -using Server.Network; using Server.Engines.Craft; +using Server.Network; namespace Server.Items { - public enum ToolQuality - { - Low, - Regular, - Exceptional - } + public enum ToolQuality + { + Low, + Regular, + Exceptional + } - public abstract class BaseTool : Item, IUsesRemaining, ICraftable - { - private Mobile m_Crafter; - private ToolQuality m_Quality; - private int m_UsesRemaining; + public abstract class BaseTool : Item, IUsesRemaining, ICraftable + { + private Mobile m_Crafter; + private ToolQuality m_Quality; + private int m_UsesRemaining; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } + public BaseTool(int itemID) : this(Utility.RandomMinMax(25, 75), itemID) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public ToolQuality Quality - { - get => m_Quality; - set{ UnscaleUses(); m_Quality = value; InvalidateProperties(); ScaleUses(); } - } + public BaseTool(int uses, int itemID) : base(itemID) + { + m_UsesRemaining = uses; + m_Quality = ToolQuality.Regular; + } - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + public BaseTool(Serial serial) : base(serial) + { + } - public virtual bool BreakOnDepletion => true; + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } - public void ScaleUses() - { - m_UsesRemaining = (m_UsesRemaining * GetUsesScalar()) / 100; - InvalidateProperties(); - } + [CommandProperty(AccessLevel.GameMaster)] + public ToolQuality Quality + { + get => m_Quality; + set + { + UnscaleUses(); + m_Quality = value; + InvalidateProperties(); + ScaleUses(); + } + } - public void UnscaleUses() - { - m_UsesRemaining = (m_UsesRemaining * 100) / GetUsesScalar(); - } + public virtual bool BreakOnDepletion => true; - public int GetUsesScalar() - { - if ( m_Quality == ToolQuality.Exceptional ) - return 200; + public abstract CraftSystem CraftSystem{ get; } - return 100; - } + #region ICraftable Members - public bool ShowUsesRemaining{ get => true; - set{} } + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Quality = (ToolQuality)quality; - public abstract CraftSystem CraftSystem{ get; } + if (makersMark) + Crafter = from; - public BaseTool( int itemID ) : this( Utility.RandomMinMax( 25, 75 ), itemID ) - { - } + return quality; + } - public BaseTool( int uses, int itemID ) : base( itemID ) - { - m_UsesRemaining = uses; - m_Quality = ToolQuality.Regular; - } + #endregion - public BaseTool( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public bool ShowUsesRemaining + { + get => true; + set { } + } - // Makers mark not displayed on OSI - //if ( m_Crafter != null ) - // list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + public void ScaleUses() + { + m_UsesRemaining = m_UsesRemaining * GetUsesScalar() / 100; + InvalidateProperties(); + } - if ( m_Quality == ToolQuality.Exceptional ) - list.Add( 1060636 ); // exceptional + public void UnscaleUses() + { + m_UsesRemaining = m_UsesRemaining * 100 / GetUsesScalar(); + } - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ - } + public int GetUsesScalar() + { + if (m_Quality == ToolQuality.Exceptional) + return 200; - public virtual void DisplayDurabilityTo( Mobile m ) - { - LabelToAffix( m, 1017323, AffixType.Append, ": " + m_UsesRemaining.ToString() ); // Durability - } + return 100; + } - public static bool CheckAccessible( Item tool, Mobile m ) - { - return ( tool.IsChildOf( m ) || tool.Parent == m ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public static bool CheckTool( Item tool, Mobile m ) - { - Item check = m.FindItemOnLayer( Layer.OneHanded ); + // Makers mark not displayed on OSI + //if ( m_Crafter != null ) + // list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ - if ( check is BaseTool && check != tool && !(check is AncientSmithyHammer) ) - return false; + if (m_Quality == ToolQuality.Exceptional) + list.Add(1060636); // exceptional - check = m.FindItemOnLayer( Layer.TwoHanded ); + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ + } - if ( check is BaseTool && check != tool && !(check is AncientSmithyHammer) ) - return false; + public virtual void DisplayDurabilityTo(Mobile m) + { + LabelToAffix(m, 1017323, AffixType.Append, ": " + m_UsesRemaining); // Durability + } - return true; - } + public static bool CheckAccessible(Item tool, Mobile m) + { + return tool.IsChildOf(m) || tool.Parent == m; + } - public override void OnSingleClick( Mobile from ) - { - DisplayDurabilityTo( from ); + public static bool CheckTool(Item tool, Mobile m) + { + Item check = m.FindItemOnLayer(Layer.OneHanded); - base.OnSingleClick( from ); - } + if (check is BaseTool && check != tool && !(check is AncientSmithyHammer)) + return false; - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) || Parent == from ) - { - CraftSystem system = CraftSystem; + check = m.FindItemOnLayer(Layer.TwoHanded); - int num = system.CanCraft( from, this, null ); + if (check is BaseTool && check != tool && !(check is AncientSmithyHammer)) + return false; - if ( num > 0 && ( num != 1044267 || !Core.SE ) ) // Blacksmithing shows the gump regardless of proximity of an anvil and forge after SE - { - from.SendLocalizedMessage( num ); - } - else - { - CraftContext context = system.GetContext( from ); + return true; + } - from.SendGump( new CraftGump( from, system, this, null ) ); - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + public override void OnSingleClick(Mobile from) + { + DisplayDurabilityTo(from); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + base.OnSingleClick(from); + } - writer.Write( (int) 1 ); // version + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack) || Parent == from) + { + CraftSystem system = CraftSystem; - writer.Write( (Mobile) m_Crafter ); - writer.Write( (int) m_Quality ); + int num = system.CanCraft(from, this, null); - writer.Write( (int) m_UsesRemaining ); - } + if (num > 0 && (num != 1044267 || !Core.SE) + ) // Blacksmithing shows the gump regardless of proximity of an anvil and forge after SE + { + from.SendLocalizedMessage(num); + } + else + { + CraftContext context = system.GetContext(from); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + from.SendGump(new CraftGump(from, system, this, null)); + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - switch ( version ) - { - case 1: - { - m_Crafter = reader.ReadMobile(); - m_Quality = (ToolQuality) reader.ReadInt(); - goto case 0; - } - case 0: - { - m_UsesRemaining = reader.ReadInt(); - break; - } - } - } - #region ICraftable Members + writer.Write(1); // version - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (ToolQuality)quality; + writer.Write(m_Crafter); + writer.Write((int)m_Quality); - if ( makersMark ) - Crafter = from; + writer.Write(m_UsesRemaining); + } - return quality; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion - } -} + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Crafter = reader.ReadMobile(); + m_Quality = (ToolQuality)reader.ReadInt(); + goto case 0; + } + case 0: + { + m_UsesRemaining = reader.ReadInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Blowpipe.cs b/Scripts/Items/Skill Items/Tools/Blowpipe.cs index 25e8bbf9a..a63ed2323 100644 --- a/Scripts/Items/Skill Items/Tools/Blowpipe.cs +++ b/Scripts/Items/Skill Items/Tools/Blowpipe.cs @@ -2,46 +2,46 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0xE8A, 0xE89 )] - public class Blowpipe : BaseTool - { - public override CraftSystem CraftSystem => DefGlassblowing.CraftSystem; + [Flippable(0xE8A, 0xE89)] + public class Blowpipe : BaseTool + { + [Constructible] + public Blowpipe() : base(0xE8A) + { + Weight = 4.0; + Hue = 0x3B9; + } - public override int LabelNumber => 1044608; // blow pipe + [Constructible] + public Blowpipe(int uses) : base(uses, 0xE8A) + { + Weight = 4.0; + Hue = 0x3B9; + } - [Constructible] - public Blowpipe() : base( 0xE8A ) - { - Weight = 4.0; - Hue = 0x3B9; - } + public Blowpipe(Serial serial) : base(serial) + { + } - [Constructible] - public Blowpipe( int uses ) : base( uses, 0xE8A ) - { - Weight = 4.0; - Hue = 0x3B9; - } + public override CraftSystem CraftSystem => DefGlassblowing.CraftSystem; - public Blowpipe( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1044608; // blow pipe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 4.0; - } - } -} + if (Weight == 2.0) + Weight = 4.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/DovetailSaw.cs b/Scripts/Items/Skill Items/Tools/DovetailSaw.cs index 7385a52c7..f9661b7a7 100644 --- a/Scripts/Items/Skill Items/Tools/DovetailSaw.cs +++ b/Scripts/Items/Skill Items/Tools/DovetailSaw.cs @@ -2,42 +2,42 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x1028, 0x1029 )] - public class DovetailSaw : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + [Flippable(0x1028, 0x1029)] + public class DovetailSaw : BaseTool + { + [Constructible] + public DovetailSaw() : base(0x1028) + { + Weight = 2.0; + } - [Constructible] - public DovetailSaw() : base( 0x1028 ) - { - Weight = 2.0; - } + [Constructible] + public DovetailSaw(int uses) : base(uses, 0x1028) + { + Weight = 2.0; + } - [Constructible] - public DovetailSaw( int uses ) : base( uses, 0x1028 ) - { - Weight = 2.0; - } + public DovetailSaw(Serial serial) : base(serial) + { + } - public DovetailSaw( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/DrawKnife.cs b/Scripts/Items/Skill Items/Tools/DrawKnife.cs index 700024c0d..3c3e6fe46 100644 --- a/Scripts/Items/Skill Items/Tools/DrawKnife.cs +++ b/Scripts/Items/Skill Items/Tools/DrawKnife.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class DrawKnife : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + public class DrawKnife : BaseTool + { + [Constructible] + public DrawKnife() : base(0x10E4) + { + Weight = 1.0; + } - [Constructible] - public DrawKnife() : base( 0x10E4 ) - { - Weight = 1.0; - } + [Constructible] + public DrawKnife(int uses) : base(uses, 0x10E4) + { + Weight = 1.0; + } - [Constructible] - public DrawKnife( int uses ) : base( uses, 0x10E4 ) - { - Weight = 1.0; - } + public DrawKnife(Serial serial) : base(serial) + { + } - public DrawKnife( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/FletcherTools.cs b/Scripts/Items/Skill Items/Tools/FletcherTools.cs index 0242ba7ee..6454dd88c 100644 --- a/Scripts/Items/Skill Items/Tools/FletcherTools.cs +++ b/Scripts/Items/Skill Items/Tools/FletcherTools.cs @@ -2,42 +2,42 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x1022, 0x1023 )] - public class FletcherTools : BaseTool - { - public override CraftSystem CraftSystem => DefBowFletching.CraftSystem; + [Flippable(0x1022, 0x1023)] + public class FletcherTools : BaseTool + { + [Constructible] + public FletcherTools() : base(0x1022) + { + Weight = 2.0; + } - [Constructible] - public FletcherTools() : base( 0x1022 ) - { - Weight = 2.0; - } + [Constructible] + public FletcherTools(int uses) : base(uses, 0x1022) + { + Weight = 2.0; + } - [Constructible] - public FletcherTools( int uses ) : base( uses, 0x1022 ) - { - Weight = 2.0; - } + public FletcherTools(Serial serial) : base(serial) + { + } - public FletcherTools( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefBowFletching.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/FlourSifter.cs b/Scripts/Items/Skill Items/Tools/FlourSifter.cs index f42dbbf44..cf825cb8d 100644 --- a/Scripts/Items/Skill Items/Tools/FlourSifter.cs +++ b/Scripts/Items/Skill Items/Tools/FlourSifter.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class FlourSifter : BaseTool - { - public override CraftSystem CraftSystem => DefCooking.CraftSystem; + public class FlourSifter : BaseTool + { + [Constructible] + public FlourSifter() : base(0x103E) + { + Weight = 1.0; + } - [Constructible] - public FlourSifter() : base( 0x103E ) - { - Weight = 1.0; - } + [Constructible] + public FlourSifter(int uses) : base(uses, 0x103E) + { + Weight = 1.0; + } - [Constructible] - public FlourSifter( int uses ) : base( uses, 0x103E ) - { - Weight = 1.0; - } + public FlourSifter(Serial serial) : base(serial) + { + } - public FlourSifter( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCooking.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Froe.cs b/Scripts/Items/Skill Items/Tools/Froe.cs index 68f3a1b5a..5a635a39a 100644 --- a/Scripts/Items/Skill Items/Tools/Froe.cs +++ b/Scripts/Items/Skill Items/Tools/Froe.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class Froe : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + public class Froe : BaseTool + { + [Constructible] + public Froe() : base(0x10E5) + { + Weight = 1.0; + } - [Constructible] - public Froe() : base( 0x10E5 ) - { - Weight = 1.0; - } + [Constructible] + public Froe(int uses) : base(uses, 0x10E5) + { + Weight = 1.0; + } - [Constructible] - public Froe( int uses ) : base( uses, 0x10E5 ) - { - Weight = 1.0; - } + public Froe(Serial serial) : base(serial) + { + } - public Froe( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Hammer.cs b/Scripts/Items/Skill Items/Tools/Hammer.cs index 668ffb478..7de71ebbd 100644 --- a/Scripts/Items/Skill Items/Tools/Hammer.cs +++ b/Scripts/Items/Skill Items/Tools/Hammer.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class Hammer : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + public class Hammer : BaseTool + { + [Constructible] + public Hammer() : base(0x102A) + { + Weight = 2.0; + } - [Constructible] - public Hammer() : base( 0x102A ) - { - Weight = 2.0; - } + [Constructible] + public Hammer(int uses) : base(uses, 0x102A) + { + Weight = 2.0; + } - [Constructible] - public Hammer( int uses ) : base( uses, 0x102A ) - { - Weight = 2.0; - } + public Hammer(Serial serial) : base(serial) + { + } - public Hammer( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Inshave.cs b/Scripts/Items/Skill Items/Tools/Inshave.cs index 3eaa1e929..adff4c2db 100644 --- a/Scripts/Items/Skill Items/Tools/Inshave.cs +++ b/Scripts/Items/Skill Items/Tools/Inshave.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class Inshave : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + public class Inshave : BaseTool + { + [Constructible] + public Inshave() : base(0x10E6) + { + Weight = 1.0; + } - [Constructible] - public Inshave() : base( 0x10E6 ) - { - Weight = 1.0; - } + [Constructible] + public Inshave(int uses) : base(uses, 0x10E6) + { + Weight = 1.0; + } - [Constructible] - public Inshave( int uses ) : base( uses, 0x10E6 ) - { - Weight = 1.0; - } + public Inshave(Serial serial) : base(serial) + { + } - public Inshave( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/JointingPlane.cs b/Scripts/Items/Skill Items/Tools/JointingPlane.cs index cdbbf3ccb..3d5eade58 100644 --- a/Scripts/Items/Skill Items/Tools/JointingPlane.cs +++ b/Scripts/Items/Skill Items/Tools/JointingPlane.cs @@ -2,42 +2,42 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x1030, 0x1031 )] - public class JointingPlane : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + [Flippable(0x1030, 0x1031)] + public class JointingPlane : BaseTool + { + [Constructible] + public JointingPlane() : base(0x1030) + { + Weight = 2.0; + } - [Constructible] - public JointingPlane() : base( 0x1030 ) - { - Weight = 2.0; - } + [Constructible] + public JointingPlane(int uses) : base(uses, 0x1030) + { + Weight = 2.0; + } - [Constructible] - public JointingPlane( int uses ) : base( uses, 0x1030 ) - { - Weight = 2.0; - } + public JointingPlane(Serial serial) : base(serial) + { + } - public JointingPlane( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/MalletAndChisel.cs b/Scripts/Items/Skill Items/Tools/MalletAndChisel.cs index 39160e533..057774c95 100644 --- a/Scripts/Items/Skill Items/Tools/MalletAndChisel.cs +++ b/Scripts/Items/Skill Items/Tools/MalletAndChisel.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class MalletAndChisel : BaseTool - { - public override CraftSystem CraftSystem => DefMasonry.CraftSystem; + public class MalletAndChisel : BaseTool + { + [Constructible] + public MalletAndChisel() : base(0x12B3) + { + Weight = 1.0; + } - [Constructible] - public MalletAndChisel() : base( 0x12B3 ) - { - Weight = 1.0; - } + [Constructible] + public MalletAndChisel(int uses) : base(uses, 0x12B3) + { + Weight = 1.0; + } - [Constructible] - public MalletAndChisel( int uses ) : base( uses, 0x12B3 ) - { - Weight = 1.0; - } + public MalletAndChisel(Serial serial) : base(serial) + { + } - public MalletAndChisel( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefMasonry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/MapmakersPen.cs b/Scripts/Items/Skill Items/Tools/MapmakersPen.cs index eb219a920..f3931a789 100644 --- a/Scripts/Items/Skill Items/Tools/MapmakersPen.cs +++ b/Scripts/Items/Skill Items/Tools/MapmakersPen.cs @@ -2,44 +2,44 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x0FBF, 0x0FC0 )] - public class MapmakersPen : BaseTool - { - public override CraftSystem CraftSystem => DefCartography.CraftSystem; + [Flippable(0x0FBF, 0x0FC0)] + public class MapmakersPen : BaseTool + { + [Constructible] + public MapmakersPen() : base(0x0FBF) + { + Weight = 1.0; + } - public override int LabelNumber => 1044167; // mapmaker's pen + [Constructible] + public MapmakersPen(int uses) : base(uses, 0x0FBF) + { + Weight = 1.0; + } - [Constructible] - public MapmakersPen() : base( 0x0FBF ) - { - Weight = 1.0; - } + public MapmakersPen(Serial serial) : base(serial) + { + } - [Constructible] - public MapmakersPen( int uses ) : base( uses, 0x0FBF ) - { - Weight = 1.0; - } + public override CraftSystem CraftSystem => DefCartography.CraftSystem; - public MapmakersPen( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1044167; // mapmaker's pen - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } -} + if (Weight == 2.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/MortarPestle.cs b/Scripts/Items/Skill Items/Tools/MortarPestle.cs index b47200723..54770387f 100644 --- a/Scripts/Items/Skill Items/Tools/MortarPestle.cs +++ b/Scripts/Items/Skill Items/Tools/MortarPestle.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class MortarPestle : BaseTool - { - public override CraftSystem CraftSystem => DefAlchemy.CraftSystem; + public class MortarPestle : BaseTool + { + [Constructible] + public MortarPestle() : base(0xE9B) + { + Weight = 1.0; + } - [Constructible] - public MortarPestle() : base( 0xE9B ) - { - Weight = 1.0; - } + [Constructible] + public MortarPestle(int uses) : base(uses, 0xE9B) + { + Weight = 1.0; + } - [Constructible] - public MortarPestle( int uses ) : base( uses, 0xE9B ) - { - Weight = 1.0; - } + public MortarPestle(Serial serial) : base(serial) + { + } - public MortarPestle( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefAlchemy.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/MouldingPlane.cs b/Scripts/Items/Skill Items/Tools/MouldingPlane.cs index f545689d5..d4b4932d3 100644 --- a/Scripts/Items/Skill Items/Tools/MouldingPlane.cs +++ b/Scripts/Items/Skill Items/Tools/MouldingPlane.cs @@ -2,39 +2,39 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x102C, 0x102D )] - public class MouldingPlane : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + [Flippable(0x102C, 0x102D)] + public class MouldingPlane : BaseTool + { + [Constructible] + public MouldingPlane() : base(0x102C) + { + Weight = 2.0; + } - [Constructible] - public MouldingPlane() : base( 0x102C ) - { - Weight = 2.0; - } + [Constructible] + public MouldingPlane(int uses) : base(uses, 0x102C) + { + Weight = 2.0; + } - [Constructible] - public MouldingPlane( int uses ) : base( uses, 0x102C ) - { - Weight = 2.0; - } + public MouldingPlane(Serial serial) : base(serial) + { + } - public MouldingPlane( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Nails.cs b/Scripts/Items/Skill Items/Tools/Nails.cs index 6ed3582c9..8bb379b0e 100644 --- a/Scripts/Items/Skill Items/Tools/Nails.cs +++ b/Scripts/Items/Skill Items/Tools/Nails.cs @@ -2,39 +2,39 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x102E, 0x102F )] - public class Nails : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + [Flippable(0x102E, 0x102F)] + public class Nails : BaseTool + { + [Constructible] + public Nails() : base(0x102E) + { + Weight = 2.0; + } - [Constructible] - public Nails() : base( 0x102E ) - { - Weight = 2.0; - } + [Constructible] + public Nails(int uses) : base(uses, 0x102C) + { + Weight = 2.0; + } - [Constructible] - public Nails( int uses ) : base( uses, 0x102C ) - { - Weight = 2.0; - } + public Nails(Serial serial) : base(serial) + { + } - public Nails( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/RollingPin.cs b/Scripts/Items/Skill Items/Tools/RollingPin.cs index 0b0d91daa..ce779b34f 100644 --- a/Scripts/Items/Skill Items/Tools/RollingPin.cs +++ b/Scripts/Items/Skill Items/Tools/RollingPin.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class RollingPin : BaseTool - { - public override CraftSystem CraftSystem => DefCooking.CraftSystem; + public class RollingPin : BaseTool + { + [Constructible] + public RollingPin() : base(0x1043) + { + Weight = 1.0; + } - [Constructible] - public RollingPin() : base( 0x1043 ) - { - Weight = 1.0; - } + [Constructible] + public RollingPin(int uses) : base(uses, 0x1043) + { + Weight = 1.0; + } - [Constructible] - public RollingPin( int uses ) : base( uses, 0x1043 ) - { - Weight = 1.0; - } + public RollingPin(Serial serial) : base(serial) + { + } - public RollingPin( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCooking.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/RunicDovetailSaw.cs b/Scripts/Items/Skill Items/Tools/RunicDovetailSaw.cs index b7512bc37..62fb87d46 100644 --- a/Scripts/Items/Skill Items/Tools/RunicDovetailSaw.cs +++ b/Scripts/Items/Skill Items/Tools/RunicDovetailSaw.cs @@ -2,53 +2,53 @@ using Server.Engines.Craft; namespace Server.Items { - public class RunicDovetailSaw : BaseRunicTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + public class RunicDovetailSaw : BaseRunicTool + { + [Constructible] + public RunicDovetailSaw(CraftResource resource) : base(resource, 0x1028) + { + Weight = 2.0; + Hue = CraftResources.GetHue(resource); + } - public override int LabelNumber - { - get - { - int index = CraftResources.GetIndex( Resource ); + [Constructible] + public RunicDovetailSaw(CraftResource resource, int uses) : base(resource, uses, 0x1028) + { + Weight = 2.0; + Hue = CraftResources.GetHue(resource); + } - if ( index >= 1 && index <= 6 ) - return 1072633 + index; + public RunicDovetailSaw(Serial serial) : base(serial) + { + } - return 1024137; // dovetail saw - } - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - [Constructible] - public RunicDovetailSaw( CraftResource resource ) : base( resource, 0x1028 ) - { - Weight = 2.0; - Hue = CraftResources.GetHue( resource ); - } + public override int LabelNumber + { + get + { + int index = CraftResources.GetIndex(Resource); - [Constructible] - public RunicDovetailSaw( CraftResource resource, int uses ) : base( resource, uses, 0x1028 ) - { - Weight = 2.0; - Hue = CraftResources.GetHue( resource ); - } + if (index >= 1 && index <= 6) + return 1072633 + index; - public RunicDovetailSaw( Serial serial ) : base( serial ) - { - } + return 1024137; // dovetail saw + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/RunicFletcherTool.cs b/Scripts/Items/Skill Items/Tools/RunicFletcherTool.cs index a8ee77238..f67be28f1 100644 --- a/Scripts/Items/Skill Items/Tools/RunicFletcherTool.cs +++ b/Scripts/Items/Skill Items/Tools/RunicFletcherTool.cs @@ -2,53 +2,53 @@ using Server.Engines.Craft; namespace Server.Items { - public class RunicFletcherTool : BaseRunicTool - { - public override CraftSystem CraftSystem => DefBowFletching.CraftSystem; + public class RunicFletcherTool : BaseRunicTool + { + [Constructible] + public RunicFletcherTool(CraftResource resource) : base(resource, 0x1022) + { + Weight = 2.0; + Hue = CraftResources.GetHue(resource); + } - public override int LabelNumber - { - get - { - int index = CraftResources.GetIndex( Resource ); + [Constructible] + public RunicFletcherTool(CraftResource resource, int uses) : base(resource, uses, 0x1022) + { + Weight = 2.0; + Hue = CraftResources.GetHue(resource); + } - if ( index >= 1 && index <= 6 ) - return 1072627 + index; + public RunicFletcherTool(Serial serial) : base(serial) + { + } - return 1044559; // Fletcher's Tools - } - } + public override CraftSystem CraftSystem => DefBowFletching.CraftSystem; - [Constructible] - public RunicFletcherTool( CraftResource resource ) : base( resource, 0x1022 ) - { - Weight = 2.0; - Hue = CraftResources.GetHue( resource ); - } + public override int LabelNumber + { + get + { + int index = CraftResources.GetIndex(Resource); - [Constructible] - public RunicFletcherTool( CraftResource resource, int uses ) : base( resource, uses, 0x1022 ) - { - Weight = 2.0; - Hue = CraftResources.GetHue( resource ); - } + if (index >= 1 && index <= 6) + return 1072627 + index; - public RunicFletcherTool( Serial serial ) : base( serial ) - { - } + return 1044559; // Fletcher's Tools + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/RunicHammer.cs b/Scripts/Items/Skill Items/Tools/RunicHammer.cs index a1748d8f4..326e0b9d8 100644 --- a/Scripts/Items/Skill Items/Tools/RunicHammer.cs +++ b/Scripts/Items/Skill Items/Tools/RunicHammer.cs @@ -2,76 +2,76 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x13E4, 0x13E3 )] - public class RunicHammer : BaseRunicTool - { - public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; + [Flippable(0x13E4, 0x13E3)] + public class RunicHammer : BaseRunicTool + { + [Constructible] + public RunicHammer(CraftResource resource) : base(resource, 0x13E3) + { + Weight = 8.0; + Layer = Layer.OneHanded; + Hue = CraftResources.GetHue(resource); + } - public override int LabelNumber - { - get - { - int index = CraftResources.GetIndex( Resource ); + [Constructible] + public RunicHammer(CraftResource resource, int uses) : base(resource, uses, 0x13E3) + { + Weight = 8.0; + Layer = Layer.OneHanded; + Hue = CraftResources.GetHue(resource); + } - if ( index >= 1 && index <= 8 ) - return 1049019 + index; + public RunicHammer(Serial serial) : base(serial) + { + } - return 1045128; // runic smithy hammer - } - } + public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override int LabelNumber + { + get + { + int index = CraftResources.GetIndex(Resource); - int index = CraftResources.GetIndex( Resource ); + if (index >= 1 && index <= 8) + return 1049019 + index; - if ( index >= 1 && index <= 8 ) - return; + return 1045128; // runic smithy hammer + } + } - if ( !CraftResources.IsStandard( Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( Resource ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - if ( num > 0 ) - list.Add( num ); - else - list.Add( CraftResources.GetName( Resource ) ); - } - } + int index = CraftResources.GetIndex(Resource); - [Constructible] - public RunicHammer( CraftResource resource ) : base( resource, 0x13E3 ) - { - Weight = 8.0; - Layer = Layer.OneHanded; - Hue = CraftResources.GetHue( resource ); - } + if (index >= 1 && index <= 8) + return; - [Constructible] - public RunicHammer( CraftResource resource, int uses ) : base( resource, uses, 0x13E3 ) - { - Weight = 8.0; - Layer = Layer.OneHanded; - Hue = CraftResources.GetHue( resource ); - } + if (!CraftResources.IsStandard(Resource)) + { + int num = CraftResources.GetLocalizationNumber(Resource); - public RunicHammer( Serial serial ) : base( serial ) - { - } + if (num > 0) + list.Add(num); + else + list.Add(CraftResources.GetName(Resource)); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/RunicSewingKit.cs b/Scripts/Items/Skill Items/Tools/RunicSewingKit.cs index 33213a1a8..2de64ab18 100644 --- a/Scripts/Items/Skill Items/Tools/RunicSewingKit.cs +++ b/Scripts/Items/Skill Items/Tools/RunicSewingKit.cs @@ -1,79 +1,78 @@ -using System; using Server.Engines.Craft; namespace Server.Items { - public class RunicSewingKit : BaseRunicTool - { - public override CraftSystem CraftSystem => DefTailoring.CraftSystem; + public class RunicSewingKit : BaseRunicTool + { + [Constructible] + public RunicSewingKit(CraftResource resource) : base(resource, 0xF9D) + { + Weight = 2.0; + Hue = CraftResources.GetHue(resource); + } - public override void AddNameProperty( ObjectPropertyList list ) - { - string v = " "; + [Constructible] + public RunicSewingKit(CraftResource resource, int uses) : base(resource, uses, 0xF9D) + { + Weight = 2.0; + Hue = CraftResources.GetHue(resource); + } - if ( !CraftResources.IsStandard( Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( Resource ); + public RunicSewingKit(Serial serial) : base(serial) + { + } - if ( num > 0 ) - v = $"#{num}"; - else - v = CraftResources.GetName( Resource ); - } + public override CraftSystem CraftSystem => DefTailoring.CraftSystem; - list.Add( 1061119, v ); // ~1_LEATHER_TYPE~ runic sewing kit - } + public override void AddNameProperty(ObjectPropertyList list) + { + string v = " "; - public override void OnSingleClick( Mobile from ) - { - string v = " "; + if (!CraftResources.IsStandard(Resource)) + { + int num = CraftResources.GetLocalizationNumber(Resource); - if ( !CraftResources.IsStandard( Resource ) ) - { - int num = CraftResources.GetLocalizationNumber( Resource ); + if (num > 0) + v = $"#{num}"; + else + v = CraftResources.GetName(Resource); + } - if ( num > 0 ) - v = $"#{num}"; - else - v = CraftResources.GetName( Resource ); - } + list.Add(1061119, v); // ~1_LEATHER_TYPE~ runic sewing kit + } - LabelTo( from, 1061119, v ); // ~1_LEATHER_TYPE~ runic sewing kit - } + public override void OnSingleClick(Mobile from) + { + string v = " "; - [Constructible] - public RunicSewingKit( CraftResource resource ) : base( resource, 0xF9D ) - { - Weight = 2.0; - Hue = CraftResources.GetHue( resource ); - } + if (!CraftResources.IsStandard(Resource)) + { + int num = CraftResources.GetLocalizationNumber(Resource); - [Constructible] - public RunicSewingKit( CraftResource resource, int uses ) : base( resource, uses, 0xF9D ) - { - Weight = 2.0; - Hue = CraftResources.GetHue( resource ); - } + if (num > 0) + v = $"#{num}"; + else + v = CraftResources.GetName(Resource); + } - public RunicSewingKit( Serial serial ) : base( serial ) - { - } + LabelTo(from, 1061119, v); // ~1_LEATHER_TYPE~ runic sewing kit + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( ItemID == 0x13E4 || ItemID == 0x13E3 ) - ItemID = 0xF9D; - } - } -} + if (ItemID == 0x13E4 || ItemID == 0x13E3) + ItemID = 0xF9D; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Saw.cs b/Scripts/Items/Skill Items/Tools/Saw.cs index 421f1ca3a..c28458d86 100644 --- a/Scripts/Items/Skill Items/Tools/Saw.cs +++ b/Scripts/Items/Skill Items/Tools/Saw.cs @@ -2,39 +2,39 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x1034, 0x1035 )] - public class Saw : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + [Flippable(0x1034, 0x1035)] + public class Saw : BaseTool + { + [Constructible] + public Saw() : base(0x1034) + { + Weight = 2.0; + } - [Constructible] - public Saw() : base( 0x1034 ) - { - Weight = 2.0; - } + [Constructible] + public Saw(int uses) : base(uses, 0x1034) + { + Weight = 2.0; + } - [Constructible] - public Saw( int uses ) : base( uses, 0x1034 ) - { - Weight = 2.0; - } + public Saw(Serial serial) : base(serial) + { + } - public Saw( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Scorp.cs b/Scripts/Items/Skill Items/Tools/Scorp.cs index c1b85bfd5..b78fc6aa0 100644 --- a/Scripts/Items/Skill Items/Tools/Scorp.cs +++ b/Scripts/Items/Skill Items/Tools/Scorp.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class Scorp : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + public class Scorp : BaseTool + { + [Constructible] + public Scorp() : base(0x10E7) + { + Weight = 1.0; + } - [Constructible] - public Scorp() : base( 0x10E7 ) - { - Weight = 1.0; - } + [Constructible] + public Scorp(int uses) : base(uses, 0x10E7) + { + Weight = 1.0; + } - [Constructible] - public Scorp( int uses ) : base( uses, 0x10E7 ) - { - Weight = 1.0; - } + public Scorp(Serial serial) : base(serial) + { + } - public Scorp( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/ScribesPen.cs b/Scripts/Items/Skill Items/Tools/ScribesPen.cs index c80eb1a90..90023c912 100644 --- a/Scripts/Items/Skill Items/Tools/ScribesPen.cs +++ b/Scripts/Items/Skill Items/Tools/ScribesPen.cs @@ -2,44 +2,44 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x0FBF, 0x0FC0 )] - public class ScribesPen : BaseTool - { - public override CraftSystem CraftSystem => DefInscription.CraftSystem; + [Flippable(0x0FBF, 0x0FC0)] + public class ScribesPen : BaseTool + { + [Constructible] + public ScribesPen() : base(0x0FBF) + { + Weight = 1.0; + } - public override int LabelNumber => 1044168; // scribe's pen + [Constructible] + public ScribesPen(int uses) : base(uses, 0x0FBF) + { + Weight = 1.0; + } - [Constructible] - public ScribesPen() : base( 0x0FBF ) - { - Weight = 1.0; - } + public ScribesPen(Serial serial) : base(serial) + { + } - [Constructible] - public ScribesPen( int uses ) : base( uses, 0x0FBF ) - { - Weight = 1.0; - } + public override CraftSystem CraftSystem => DefInscription.CraftSystem; - public ScribesPen( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1044168; // scribe's pen - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 1.0; - } - } -} + if (Weight == 2.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/SewingKit.cs b/Scripts/Items/Skill Items/Tools/SewingKit.cs index d75979f12..bd777a1dd 100644 --- a/Scripts/Items/Skill Items/Tools/SewingKit.cs +++ b/Scripts/Items/Skill Items/Tools/SewingKit.cs @@ -2,38 +2,38 @@ using Server.Engines.Craft; namespace Server.Items { - public class SewingKit : BaseTool - { - public override CraftSystem CraftSystem => DefTailoring.CraftSystem; + public class SewingKit : BaseTool + { + [Constructible] + public SewingKit() : base(0xF9D) + { + Weight = 2.0; + } - [Constructible] - public SewingKit() : base( 0xF9D ) - { - Weight = 2.0; - } + [Constructible] + public SewingKit(int uses) : base(uses, 0xF9D) + { + Weight = 2.0; + } - [Constructible] - public SewingKit( int uses ) : base( uses, 0xF9D ) - { - Weight = 2.0; - } + public SewingKit(Serial serial) : base(serial) + { + } - public SewingKit( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefTailoring.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Skillet.cs b/Scripts/Items/Skill Items/Tools/Skillet.cs index 1f11c0561..812058ec0 100644 --- a/Scripts/Items/Skill Items/Tools/Skillet.cs +++ b/Scripts/Items/Skill Items/Tools/Skillet.cs @@ -2,40 +2,40 @@ using Server.Engines.Craft; namespace Server.Items { - public class Skillet : BaseTool - { - public override int LabelNumber => 1044567; // skillet + public class Skillet : BaseTool + { + [Constructible] + public Skillet() : base(0x97F) + { + Weight = 1.0; + } - public override CraftSystem CraftSystem => DefCooking.CraftSystem; + [Constructible] + public Skillet(int uses) : base(uses, 0x97F) + { + Weight = 1.0; + } - [Constructible] - public Skillet() : base( 0x97F ) - { - Weight = 1.0; - } + public Skillet(Serial serial) : base(serial) + { + } - [Constructible] - public Skillet( int uses ) : base( uses, 0x97F ) - { - Weight = 1.0; - } + public override int LabelNumber => 1044567; // skillet - public Skillet( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCooking.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/SledgeHammer.cs b/Scripts/Items/Skill Items/Tools/SledgeHammer.cs index 2ce890c64..b54d23da8 100644 --- a/Scripts/Items/Skill Items/Tools/SledgeHammer.cs +++ b/Scripts/Items/Skill Items/Tools/SledgeHammer.cs @@ -2,39 +2,39 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0xFB5, 0xFB4 )] - public class SledgeHammer : BaseTool - { - public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; + [Flippable(0xFB5, 0xFB4)] + public class SledgeHammer : BaseTool + { + [Constructible] + public SledgeHammer() : base(0xFB5) + { + Layer = Layer.OneHanded; + } - [Constructible] - public SledgeHammer() : base( 0xFB5 ) - { - Layer = Layer.OneHanded; - } + [Constructible] + public SledgeHammer(int uses) : base(uses, 0xFB5) + { + Layer = Layer.OneHanded; + } - [Constructible] - public SledgeHammer( int uses ) : base( uses, 0xFB5 ) - { - Layer = Layer.OneHanded; - } + public SledgeHammer(Serial serial) : base(serial) + { + } - public SledgeHammer( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/SmithHammer.cs b/Scripts/Items/Skill Items/Tools/SmithHammer.cs index 5708ad9e8..69870ac89 100644 --- a/Scripts/Items/Skill Items/Tools/SmithHammer.cs +++ b/Scripts/Items/Skill Items/Tools/SmithHammer.cs @@ -2,41 +2,41 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x13E3, 0x13E4 )] - public class SmithHammer : BaseTool - { - public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; + [Flippable(0x13E3, 0x13E4)] + public class SmithHammer : BaseTool + { + [Constructible] + public SmithHammer() : base(0x13E3) + { + Weight = 8.0; + Layer = Layer.OneHanded; + } - [Constructible] - public SmithHammer() : base( 0x13E3 ) - { - Weight = 8.0; - Layer = Layer.OneHanded; - } + [Constructible] + public SmithHammer(int uses) : base(uses, 0x13E3) + { + Weight = 8.0; + Layer = Layer.OneHanded; + } - [Constructible] - public SmithHammer( int uses ) : base( uses, 0x13E3 ) - { - Weight = 8.0; - Layer = Layer.OneHanded; - } + public SmithHammer(Serial serial) : base(serial) + { + } - public SmithHammer( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/SmoothingPlane.cs b/Scripts/Items/Skill Items/Tools/SmoothingPlane.cs index bac44f5c4..b84ebb800 100644 --- a/Scripts/Items/Skill Items/Tools/SmoothingPlane.cs +++ b/Scripts/Items/Skill Items/Tools/SmoothingPlane.cs @@ -2,39 +2,39 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x1032, 0x1033 )] - public class SmoothingPlane : BaseTool - { - public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; + [Flippable(0x1032, 0x1033)] + public class SmoothingPlane : BaseTool + { + [Constructible] + public SmoothingPlane() : base(0x1032) + { + Weight = 1.0; + } - [Constructible] - public SmoothingPlane() : base( 0x1032 ) - { - Weight = 1.0; - } + [Constructible] + public SmoothingPlane(int uses) : base(uses, 0x1032) + { + Weight = 1.0; + } - [Constructible] - public SmoothingPlane( int uses ) : base( uses, 0x1032 ) - { - Weight = 1.0; - } + public SmoothingPlane(Serial serial) : base(serial) + { + } - public SmoothingPlane( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefCarpentry.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/TinkerTools.cs b/Scripts/Items/Skill Items/Tools/TinkerTools.cs index 851d5a69a..37b19f5f4 100644 --- a/Scripts/Items/Skill Items/Tools/TinkerTools.cs +++ b/Scripts/Items/Skill Items/Tools/TinkerTools.cs @@ -2,77 +2,77 @@ using Server.Engines.Craft; namespace Server.Items { - [Flippable( 0x1EB8, 0x1EB9 )] - public class TinkerTools : BaseTool - { - public override CraftSystem CraftSystem => DefTinkering.CraftSystem; + [Flippable(0x1EB8, 0x1EB9)] + public class TinkerTools : BaseTool + { + [Constructible] + public TinkerTools() : base(0x1EB8) + { + Weight = 1.0; + } - [Constructible] - public TinkerTools() : base( 0x1EB8 ) - { - Weight = 1.0; - } + [Constructible] + public TinkerTools(int uses) : base(uses, 0x1EB8) + { + Weight = 1.0; + } - [Constructible] - public TinkerTools( int uses ) : base( uses, 0x1EB8 ) - { - Weight = 1.0; - } + public TinkerTools(Serial serial) : base(serial) + { + } - public TinkerTools( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefTinkering.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class TinkersTools : BaseTool - { - public override CraftSystem CraftSystem => DefTinkering.CraftSystem; + public class TinkersTools : BaseTool + { + [Constructible] + public TinkersTools() + : base(0x1EBC) + { + Weight = 1.0; + } - [Constructible] - public TinkersTools() - : base(0x1EBC) - { - Weight = 1.0; - } + [Constructible] + public TinkersTools(int uses) + : base(uses, 0x1EBC) + { + Weight = 1.0; + } - [Constructible] - public TinkersTools(int uses) - : base(uses, 0x1EBC) - { - Weight = 1.0; - } + public TinkersTools(Serial serial) + : base(serial) + { + } - public TinkersTools(Serial serial) - : base(serial) - { - } + public override CraftSystem CraftSystem => DefTinkering.CraftSystem; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Skill Items/Tools/Tongs.cs b/Scripts/Items/Skill Items/Tools/Tongs.cs index 32f8bf1b8..ed9f3c300 100644 --- a/Scripts/Items/Skill Items/Tools/Tongs.cs +++ b/Scripts/Items/Skill Items/Tools/Tongs.cs @@ -2,39 +2,39 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0xfbb, 0xfbc )] - public class Tongs : BaseTool - { - public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; + [Flippable(0xfbb, 0xfbc)] + public class Tongs : BaseTool + { + [Constructible] + public Tongs() : base(0xFBB) + { + Weight = 2.0; + } - [Constructible] - public Tongs() : base( 0xFBB ) - { - Weight = 2.0; - } + [Constructible] + public Tongs(int uses) : base(uses, 0xFBB) + { + Weight = 2.0; + } - [Constructible] - public Tongs( int uses ) : base( uses, 0xFBB ) - { - Weight = 2.0; - } + public Tongs(Serial serial) : base(serial) + { + } - public Tongs( Serial serial ) : base( serial ) - { - } + public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/11th Year promo/EarringsOfProtection.cs b/Scripts/Items/Special/11th Year promo/EarringsOfProtection.cs index 217d5450b..660822792 100644 --- a/Scripts/Items/Special/11th Year promo/EarringsOfProtection.cs +++ b/Scripts/Items/Special/11th Year promo/EarringsOfProtection.cs @@ -1,113 +1,113 @@ namespace Server.Items { - public class EarringBoxSet : RedVelvetGiftBox - { - [Constructible] - public EarringBoxSet() - { - DropItem( new EarringsOfProtection( AosElementAttribute.Physical ) ); - DropItem( new EarringsOfProtection( AosElementAttribute.Fire ) ); - DropItem( new EarringsOfProtection( AosElementAttribute.Cold ) ); - DropItem( new EarringsOfProtection( AosElementAttribute.Poison ) ); - DropItem( new EarringsOfProtection( AosElementAttribute.Energy ) ); - } + public class EarringBoxSet : RedVelvetGiftBox + { + [Constructible] + public EarringBoxSet() + { + DropItem(new EarringsOfProtection(AosElementAttribute.Physical)); + DropItem(new EarringsOfProtection(AosElementAttribute.Fire)); + DropItem(new EarringsOfProtection(AosElementAttribute.Cold)); + DropItem(new EarringsOfProtection(AosElementAttribute.Poison)); + DropItem(new EarringsOfProtection(AosElementAttribute.Energy)); + } - public EarringBoxSet( Serial serial ) - : base( serial ) - { - } + public EarringBoxSet(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class EarringsOfProtection : BaseJewel - { - [CommandProperty( AccessLevel.GameMaster )] - public virtual AosElementAttribute Attribute => m_Attribute; + public class EarringsOfProtection : BaseJewel + { + private AosElementAttribute m_Attribute; - public override int LabelNumber => GetItemData( m_Attribute, true ); + [Constructible] + public EarringsOfProtection() : this(RandomType()) + { + } - public override int Hue => GetItemData( m_Attribute, false ); + [Constructible] + public EarringsOfProtection(AosElementAttribute element) + : base(0x1087, Layer.Earrings) + { + Resistances[element] = 2; - private AosElementAttribute m_Attribute; + m_Attribute = element; + LootType = LootType.Blessed; + } - [Constructible] - public EarringsOfProtection() : this( RandomType() ) - { - } + public EarringsOfProtection(Serial serial) + : base(serial) + { + } - [Constructible] - public EarringsOfProtection( AosElementAttribute element ) - : base( 0x1087, Layer.Earrings ) - { - Resistances[ ( (AosElementAttribute)element ) ] = 2; + [CommandProperty(AccessLevel.GameMaster)] + public virtual AosElementAttribute Attribute => m_Attribute; - m_Attribute = element; - LootType = LootType.Blessed; - } + public override int LabelNumber => GetItemData(m_Attribute, true); - public EarringsOfProtection( Serial serial ) - : base( serial ) - { - } + public override int Hue => GetItemData(m_Attribute, false); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - writer.Write( (int)m_Attribute ); - } + writer.Write(0); // version + writer.Write((int)m_Attribute); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - m_Attribute = (AosElementAttribute)reader.ReadInt(); - } + int version = reader.ReadInt(); + m_Attribute = (AosElementAttribute)reader.ReadInt(); + } - public static AosElementAttribute RandomType() - { - return GetTypes( Utility.Random( 5 ) ); - } + public static AosElementAttribute RandomType() + { + return GetTypes(Utility.Random(5)); + } - public static AosElementAttribute GetTypes( int value ) - { - switch( value ) - { - case 0: return AosElementAttribute.Physical; - case 1: return AosElementAttribute.Fire; - case 2: return AosElementAttribute.Cold; - case 3: return AosElementAttribute.Poison; - default: return AosElementAttribute.Energy; - } - } + public static AosElementAttribute GetTypes(int value) + { + switch (value) + { + case 0: return AosElementAttribute.Physical; + case 1: return AosElementAttribute.Fire; + case 2: return AosElementAttribute.Cold; + case 3: return AosElementAttribute.Poison; + default: return AosElementAttribute.Energy; + } + } - public static int GetItemData( AosElementAttribute element, bool label ) - { - switch( element ) - { - case AosElementAttribute.Physical: return ( label ) ? 1071091 : 0; // Earring of Protection (Physical) 1071091 - case AosElementAttribute.Fire: return ( label ) ? 1071092 : 0x4ec; // Earring of Protection (Fire) 1071092 - case AosElementAttribute.Cold: return ( label ) ? 1071093 : 0x4f2; // Earring of Protection (Cold) 1071093 - case AosElementAttribute.Poison: return ( label ) ? 1071094 : 0x4f8; // Earring of Protection (Poison) 1071094 - case AosElementAttribute.Energy: return ( label ) ? 1071095 : 0x4fe; // Earring of Protection (Energy) 1071095 + public static int GetItemData(AosElementAttribute element, bool label) + { + switch (element) + { + case AosElementAttribute.Physical: return label ? 1071091 : 0; // Earring of Protection (Physical) 1071091 + case AosElementAttribute.Fire: return label ? 1071092 : 0x4ec; // Earring of Protection (Fire) 1071092 + case AosElementAttribute.Cold: return label ? 1071093 : 0x4f2; // Earring of Protection (Cold) 1071093 + case AosElementAttribute.Poison: return label ? 1071094 : 0x4f8; // Earring of Protection (Poison) 1071094 + case AosElementAttribute.Energy: return label ? 1071095 : 0x4fe; // Earring of Protection (Energy) 1071095 - default: return -1; - } - } - } -} + default: return -1; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicBox.cs b/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicBox.cs index b254b5452..69ecbd4a7 100644 --- a/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicBox.cs +++ b/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicBox.cs @@ -7,293 +7,316 @@ using Server.Network; namespace Server.Items { - public sealed class StopMusic : Packet - { - public static readonly Packet Instance = SetStatic( new StopMusic() ); + public sealed class StopMusic : Packet + { + public static readonly Packet Instance = SetStatic(new StopMusic()); - public StopMusic() : base( 0x6D, 3 ) - { - m_Stream.Write( (short) 0x1FFF ); - } - } + public StopMusic() : base(0x6D, 3) + { + m_Stream.Write((short)0x1FFF); + } + } - [Flippable( 0x2AF9, 0x2AFD )] - public class DawnsMusicBox : Item, ISecurable - { - public override int LabelNumber => 1075198; // Dawn�s Music Box + [Flippable(0x2AF9, 0x2AFD)] + public class DawnsMusicBox : Item, ISecurable + { + private static Dictionary m_Info = new Dictionary(); - public List Tracks { get; private set; } + public static MusicName[] m_CommonTracks = + { + MusicName.Samlethe, MusicName.Sailing, MusicName.Britain2, MusicName.Britain1, + MusicName.Bucsden, MusicName.Forest_a, MusicName.Cove, MusicName.Death, + MusicName.Dungeon9, MusicName.Dungeon2, MusicName.Cave01, MusicName.Combat3, + MusicName.Combat1, MusicName.Combat2, MusicName.Jhelom, MusicName.Linelle, + MusicName.LBCastle, MusicName.Minoc, MusicName.Moonglow, MusicName.Magincia, + MusicName.Nujelm, MusicName.BTCastle, MusicName.Tavern04, MusicName.Skarabra, + MusicName.Stones2, MusicName.Serpents, MusicName.Taiko, MusicName.Tavern01, + MusicName.Tavern02, MusicName.Tavern03, MusicName.TokunoDungeon, MusicName.Trinsic, + MusicName.OldUlt01, MusicName.Ocllo, MusicName.Vesper, MusicName.Victory, + MusicName.Mountn_a, MusicName.Wind, MusicName.Yew, MusicName.Zento + }; - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + public static MusicName[] m_UncommonTracks = + { + MusicName.GwennoConversation, MusicName.DreadHornArea, MusicName.ElfCity, + MusicName.GoodEndGame, MusicName.GoodVsEvil, MusicName.GreatEarthSerpents, + MusicName.GrizzleDungeon, MusicName.Humanoids_U9, MusicName.MelisandesLair, + MusicName.MinocNegative, MusicName.ParoxysmusLair, MusicName.Paws + }; - [Constructible] - public DawnsMusicBox() : base( 0x2AF9 ) - { - Weight = 1.0; + public static MusicName[] m_RareTracks = + { + MusicName.SelimsBar, MusicName.SerpentIsleCombat_U7, MusicName.ValoriaShips + }; - Tracks = new List(); + private int m_Count; + private int m_ItemID; - while ( Tracks.Count < 4 ) - { - MusicName name = RandomTrack( DawnsMusicRarity.Common ); + private Timer m_Timer; - if ( !Tracks.Contains( name ) ) - Tracks.Add( name ); - } - } + [Constructible] + public DawnsMusicBox() : base(0x2AF9) + { + Weight = 1.0; - public DawnsMusicBox( Serial serial ) : base( serial ) - { - } + Tracks = new List(); - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is DawnsMusicBox box) ) - return; + while (Tracks.Count < 4) + { + MusicName name = RandomTrack(DawnsMusicRarity.Common); - box.Tracks = new List(); - box.Tracks.AddRange( Tracks ); - } + if (!Tracks.Contains(name)) + Tracks.Add(name); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public DawnsMusicBox(Serial serial) : base(serial) + { + } - int commonSongs = 0; - int uncommonSongs = 0; - int rareSongs = 0; + public override int LabelNumber => 1075198; // Dawn�s Music Box - for ( int i = 0; i < Tracks.Count; i++ ) - { - DawnsMusicInfo info = GetInfo( Tracks[ i ] ); + public List Tracks{ get; private set; } - switch ( info.Rarity ) - { - case DawnsMusicRarity.Common: commonSongs++; break; - case DawnsMusicRarity.Uncommon: uncommonSongs++; break; - case DawnsMusicRarity.Rare: rareSongs++; break; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - if ( commonSongs > 0 ) - list.Add( 1075234, commonSongs.ToString() ); // ~1_NUMBER~ Common Tracks - if ( uncommonSongs > 0 ) - list.Add( 1075235, uncommonSongs.ToString() ); // ~1_NUMBER~ Uncommon Tracks - if ( rareSongs > 0 ) - list.Add( 1075236, rareSongs.ToString() ); // ~1_NUMBER~ Rare Tracks - } + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is DawnsMusicBox box)) + return; - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + box.Tracks = new List(); + box.Tracks.AddRange(Tracks); + } - SetSecureLevelEntry.AddTo( from, this, list ); // Set secure level - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) && !IsLockedDown ) - from.SendLocalizedMessage( 1061856 ); // You must have the item in your backpack or locked down in order to use it. - else if ( IsLockedDown && !HasAccces( from ) ) - from.SendLocalizedMessage( 502436 ); // That is not accessible. - else - { - from.CloseGump( typeof( DawnsMusicBoxGump ) ); - from.SendGump( new DawnsMusicBoxGump( this ) ); - } - } + int commonSongs = 0; + int uncommonSongs = 0; + int rareSongs = 0; - public bool HasAccces( Mobile m ) - { - if ( m.AccessLevel >= AccessLevel.GameMaster ) - return true; + for (int i = 0; i < Tracks.Count; i++) + { + DawnsMusicInfo info = GetInfo(Tracks[i]); - BaseHouse house = BaseHouse.FindHouseAt( this ); + switch (info.Rarity) + { + case DawnsMusicRarity.Common: + commonSongs++; + break; + case DawnsMusicRarity.Uncommon: + uncommonSongs++; + break; + case DawnsMusicRarity.Rare: + rareSongs++; + break; + } + } - return ( house != null && house.HasAccess( m ) ); - } + if (commonSongs > 0) + list.Add(1075234, commonSongs.ToString()); // ~1_NUMBER~ Common Tracks + if (uncommonSongs > 0) + list.Add(1075235, uncommonSongs.ToString()); // ~1_NUMBER~ Uncommon Tracks + if (rareSongs > 0) + list.Add(1075236, rareSongs.ToString()); // ~1_NUMBER~ Rare Tracks + } - private Timer m_Timer; - private int m_ItemID; - private int m_Count; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public void PlayMusic( Mobile m, MusicName music ) - { - if ( m_Timer != null && m_Timer.Running ) - EndMusic( m ); - else - m_ItemID = ItemID; + SetSecureLevelEntry.AddTo(from, this, list); // Set secure level + } - m.Send( new PlayMusic( music ) ); - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ), 4, Animate ); - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack) && !IsLockedDown) + { + from.SendLocalizedMessage( + 1061856); // You must have the item in your backpack or locked down in order to use it. + } + else if (IsLockedDown && !HasAccces(from)) + { + from.SendLocalizedMessage(502436); // That is not accessible. + } + else + { + from.CloseGump(typeof(DawnsMusicBoxGump)); + from.SendGump(new DawnsMusicBoxGump(this)); + } + } - public void EndMusic( Mobile m ) - { - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); + public bool HasAccces(Mobile m) + { + if (m.AccessLevel >= AccessLevel.GameMaster) + return true; - m.Send( StopMusic.Instance ); + BaseHouse house = BaseHouse.FindHouseAt(this); - if ( m_Count > 0 ) - ItemID = m_ItemID; + return house != null && house.HasAccess(m); + } - m_Count = 0; - } + public void PlayMusic(Mobile m, MusicName music) + { + if (m_Timer != null && m_Timer.Running) + EndMusic(m); + else + m_ItemID = ItemID; - private void Animate() - { - m_Count++; + m.Send(new PlayMusic(music)); + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5), 4, Animate); + } - if ( m_Count >= 4 ) - { - m_Count = 0; - ItemID = m_ItemID; - } - else - ItemID++; - } + public void EndMusic(Mobile m) + { + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m.Send(StopMusic.Instance); - writer.WriteEncodedInt( 0 ); // version + if (m_Count > 0) + ItemID = m_ItemID; - writer.Write( (int) Tracks.Count ); + m_Count = 0; + } - for ( int i = 0; i < Tracks.Count; i++ ) - writer.Write( (int) Tracks[ i ] ); + private void Animate() + { + m_Count++; - writer.Write( (int) Level ); - writer.Write( (int) m_ItemID ); - } + if (m_Count >= 4) + { + m_Count = 0; + ItemID = m_ItemID; + } + else + { + ItemID++; + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadEncodedInt(); + writer.WriteEncodedInt(0); // version - int count = reader.ReadInt(); - Tracks = new List(); + writer.Write(Tracks.Count); - for ( int i = 0; i < count; i++ ) - Tracks.Add( (MusicName) reader.ReadInt() ); + for (int i = 0; i < Tracks.Count; i++) + writer.Write((int)Tracks[i]); - Level = (SecureLevel) reader.ReadInt(); - m_ItemID = reader.ReadInt(); - } + writer.Write((int)Level); + writer.Write(m_ItemID); + } - private static Dictionary m_Info = new Dictionary(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public static void Initialize() - { - m_Info.Add( MusicName.Samlethe, new DawnsMusicInfo( 1075152, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Sailing, new DawnsMusicInfo( 1075163, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Britain2, new DawnsMusicInfo( 1075145, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Britain1, new DawnsMusicInfo( 1075144, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Bucsden, new DawnsMusicInfo( 1075146, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Forest_a, new DawnsMusicInfo( 1075161, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Cove, new DawnsMusicInfo( 1075176, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Death, new DawnsMusicInfo( 1075171, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Dungeon9, new DawnsMusicInfo( 1075160, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Dungeon2, new DawnsMusicInfo( 1075175, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Cave01, new DawnsMusicInfo( 1075159, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Combat3, new DawnsMusicInfo( 1075170, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Combat1, new DawnsMusicInfo( 1075168, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Combat2, new DawnsMusicInfo( 1075169, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Jhelom, new DawnsMusicInfo( 1075147, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Linelle, new DawnsMusicInfo( 1075185, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.LBCastle, new DawnsMusicInfo( 1075148, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Minoc, new DawnsMusicInfo( 1075150, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Moonglow, new DawnsMusicInfo( 1075177, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Magincia, new DawnsMusicInfo( 1075149, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Nujelm, new DawnsMusicInfo( 1075174, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.BTCastle, new DawnsMusicInfo( 1075173, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Tavern04, new DawnsMusicInfo( 1075167, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Skarabra, new DawnsMusicInfo( 1075154, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Stones2, new DawnsMusicInfo( 1075143, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Serpents, new DawnsMusicInfo( 1075153, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Taiko, new DawnsMusicInfo( 1075180, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Tavern01, new DawnsMusicInfo( 1075164, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Tavern02, new DawnsMusicInfo( 1075165, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Tavern03, new DawnsMusicInfo( 1075166, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.TokunoDungeon, new DawnsMusicInfo( 1075179, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Trinsic, new DawnsMusicInfo( 1075155, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.OldUlt01, new DawnsMusicInfo( 1075142, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Ocllo, new DawnsMusicInfo( 1075151, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Vesper, new DawnsMusicInfo( 1075156, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Victory, new DawnsMusicInfo( 1075172, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Mountn_a, new DawnsMusicInfo( 1075162, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Wind, new DawnsMusicInfo( 1075157, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Yew, new DawnsMusicInfo( 1075158, DawnsMusicRarity.Common ) ); - m_Info.Add( MusicName.Zento, new DawnsMusicInfo( 1075178, DawnsMusicRarity.Common ) ); + int version = reader.ReadEncodedInt(); - m_Info.Add( MusicName.GwennoConversation, new DawnsMusicInfo( 1075131, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.DreadHornArea, new DawnsMusicInfo( 1075181, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.ElfCity, new DawnsMusicInfo( 1075182, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.GoodEndGame, new DawnsMusicInfo( 1075132, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.GoodVsEvil, new DawnsMusicInfo( 1075133, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.GreatEarthSerpents, new DawnsMusicInfo( 1075134, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.GrizzleDungeon, new DawnsMusicInfo( 1075186, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.Humanoids_U9, new DawnsMusicInfo( 1075135, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.MelisandesLair, new DawnsMusicInfo( 1075183, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.MinocNegative, new DawnsMusicInfo( 1075136, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.ParoxysmusLair, new DawnsMusicInfo( 1075184, DawnsMusicRarity.Uncommon ) ); - m_Info.Add( MusicName.Paws, new DawnsMusicInfo( 1075137, DawnsMusicRarity.Uncommon ) ); + int count = reader.ReadInt(); + Tracks = new List(); - m_Info.Add( MusicName.SelimsBar, new DawnsMusicInfo( 1075138, DawnsMusicRarity.Rare ) ); - m_Info.Add( MusicName.SerpentIsleCombat_U7, new DawnsMusicInfo( 1075139, DawnsMusicRarity.Rare ) ); - m_Info.Add( MusicName.ValoriaShips, new DawnsMusicInfo( 1075140, DawnsMusicRarity.Rare ) ); - } + for (int i = 0; i < count; i++) + Tracks.Add((MusicName)reader.ReadInt()); - public static MusicName[] m_CommonTracks = { - MusicName.Samlethe, MusicName.Sailing, MusicName.Britain2, MusicName.Britain1, - MusicName.Bucsden, MusicName.Forest_a, MusicName.Cove, MusicName.Death, - MusicName.Dungeon9, MusicName.Dungeon2, MusicName.Cave01, MusicName.Combat3, - MusicName.Combat1, MusicName.Combat2, MusicName.Jhelom, MusicName.Linelle, - MusicName.LBCastle, MusicName.Minoc, MusicName.Moonglow, MusicName.Magincia, - MusicName.Nujelm, MusicName.BTCastle, MusicName.Tavern04, MusicName.Skarabra, - MusicName.Stones2, MusicName.Serpents, MusicName.Taiko, MusicName.Tavern01, - MusicName.Tavern02, MusicName.Tavern03, MusicName.TokunoDungeon, MusicName.Trinsic, - MusicName.OldUlt01, MusicName.Ocllo, MusicName.Vesper, MusicName.Victory, - MusicName.Mountn_a, MusicName.Wind, MusicName.Yew, MusicName.Zento - }; + Level = (SecureLevel)reader.ReadInt(); + m_ItemID = reader.ReadInt(); + } - public static MusicName[] m_UncommonTracks = { - MusicName.GwennoConversation, MusicName.DreadHornArea, MusicName.ElfCity, - MusicName.GoodEndGame, MusicName.GoodVsEvil, MusicName.GreatEarthSerpents, - MusicName.GrizzleDungeon, MusicName.Humanoids_U9, MusicName.MelisandesLair, - MusicName.MinocNegative, MusicName.ParoxysmusLair, MusicName.Paws - }; + public static void Initialize() + { + m_Info.Add(MusicName.Samlethe, new DawnsMusicInfo(1075152, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Sailing, new DawnsMusicInfo(1075163, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Britain2, new DawnsMusicInfo(1075145, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Britain1, new DawnsMusicInfo(1075144, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Bucsden, new DawnsMusicInfo(1075146, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Forest_a, new DawnsMusicInfo(1075161, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Cove, new DawnsMusicInfo(1075176, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Death, new DawnsMusicInfo(1075171, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Dungeon9, new DawnsMusicInfo(1075160, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Dungeon2, new DawnsMusicInfo(1075175, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Cave01, new DawnsMusicInfo(1075159, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Combat3, new DawnsMusicInfo(1075170, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Combat1, new DawnsMusicInfo(1075168, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Combat2, new DawnsMusicInfo(1075169, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Jhelom, new DawnsMusicInfo(1075147, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Linelle, new DawnsMusicInfo(1075185, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.LBCastle, new DawnsMusicInfo(1075148, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Minoc, new DawnsMusicInfo(1075150, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Moonglow, new DawnsMusicInfo(1075177, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Magincia, new DawnsMusicInfo(1075149, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Nujelm, new DawnsMusicInfo(1075174, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.BTCastle, new DawnsMusicInfo(1075173, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Tavern04, new DawnsMusicInfo(1075167, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Skarabra, new DawnsMusicInfo(1075154, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Stones2, new DawnsMusicInfo(1075143, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Serpents, new DawnsMusicInfo(1075153, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Taiko, new DawnsMusicInfo(1075180, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Tavern01, new DawnsMusicInfo(1075164, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Tavern02, new DawnsMusicInfo(1075165, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Tavern03, new DawnsMusicInfo(1075166, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.TokunoDungeon, new DawnsMusicInfo(1075179, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Trinsic, new DawnsMusicInfo(1075155, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.OldUlt01, new DawnsMusicInfo(1075142, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Ocllo, new DawnsMusicInfo(1075151, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Vesper, new DawnsMusicInfo(1075156, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Victory, new DawnsMusicInfo(1075172, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Mountn_a, new DawnsMusicInfo(1075162, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Wind, new DawnsMusicInfo(1075157, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Yew, new DawnsMusicInfo(1075158, DawnsMusicRarity.Common)); + m_Info.Add(MusicName.Zento, new DawnsMusicInfo(1075178, DawnsMusicRarity.Common)); - public static MusicName[] m_RareTracks = { - MusicName.SelimsBar, MusicName.SerpentIsleCombat_U7, MusicName.ValoriaShips - }; + m_Info.Add(MusicName.GwennoConversation, new DawnsMusicInfo(1075131, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.DreadHornArea, new DawnsMusicInfo(1075181, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.ElfCity, new DawnsMusicInfo(1075182, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.GoodEndGame, new DawnsMusicInfo(1075132, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.GoodVsEvil, new DawnsMusicInfo(1075133, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.GreatEarthSerpents, new DawnsMusicInfo(1075134, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.GrizzleDungeon, new DawnsMusicInfo(1075186, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.Humanoids_U9, new DawnsMusicInfo(1075135, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.MelisandesLair, new DawnsMusicInfo(1075183, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.MinocNegative, new DawnsMusicInfo(1075136, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.ParoxysmusLair, new DawnsMusicInfo(1075184, DawnsMusicRarity.Uncommon)); + m_Info.Add(MusicName.Paws, new DawnsMusicInfo(1075137, DawnsMusicRarity.Uncommon)); - public static DawnsMusicInfo GetInfo( MusicName name ) - { - if ( m_Info.ContainsKey( name ) ) - return m_Info[ name ]; + m_Info.Add(MusicName.SelimsBar, new DawnsMusicInfo(1075138, DawnsMusicRarity.Rare)); + m_Info.Add(MusicName.SerpentIsleCombat_U7, new DawnsMusicInfo(1075139, DawnsMusicRarity.Rare)); + m_Info.Add(MusicName.ValoriaShips, new DawnsMusicInfo(1075140, DawnsMusicRarity.Rare)); + } - return null; - } + public static DawnsMusicInfo GetInfo(MusicName name) + { + if (m_Info.ContainsKey(name)) + return m_Info[name]; - public static MusicName RandomTrack( DawnsMusicRarity rarity ) - { - MusicName[] list = null; + return null; + } - switch ( rarity ) - { - default: - case DawnsMusicRarity.Common: list = m_CommonTracks; break; - case DawnsMusicRarity.Uncommon: list = m_UncommonTracks; break; - case DawnsMusicRarity.Rare: list = m_RareTracks; break; - } + public static MusicName RandomTrack(DawnsMusicRarity rarity) + { + MusicName[] list = null; - return list[ Utility.Random( list.Length ) ]; - } - } -} + switch (rarity) + { + default: + case DawnsMusicRarity.Common: + list = m_CommonTracks; + break; + case DawnsMusicRarity.Uncommon: + list = m_UncommonTracks; + break; + case DawnsMusicRarity.Rare: + list = m_RareTracks; + break; + } + + return list[Utility.Random(list.Length)]; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicGear.cs b/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicGear.cs index 01df62595..39ddf2b1f 100644 --- a/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicGear.cs +++ b/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicGear.cs @@ -2,130 +2,137 @@ namespace Server.Items { - [Flippable( 0x1053, 0x1054 )] - public class DawnsMusicGear : Item - { - public static DawnsMusicGear RandomCommon => new DawnsMusicGear( DawnsMusicBox.RandomTrack( DawnsMusicRarity.Common ) ); + [Flippable(0x1053, 0x1054)] + public class DawnsMusicGear : Item + { + [Constructible] + public DawnsMusicGear() : this(DawnsMusicBox.RandomTrack(DawnsMusicRarity.Common)) + { + } - public static DawnsMusicGear RandomUncommon => new DawnsMusicGear( DawnsMusicBox.RandomTrack( DawnsMusicRarity.Uncommon ) ); + [Constructible] + public DawnsMusicGear(MusicName music) : base(0x1053) + { + Music = music; - public static DawnsMusicGear RandomRare => new DawnsMusicGear( DawnsMusicBox.RandomTrack( DawnsMusicRarity.Rare ) ); + Weight = 1.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public MusicName Music { get; set; } + public DawnsMusicGear(Serial serial) : base(serial) + { + } - [Constructible] - public DawnsMusicGear() : this( DawnsMusicBox.RandomTrack( DawnsMusicRarity.Common ) ) - { - } + public static DawnsMusicGear RandomCommon => new DawnsMusicGear(DawnsMusicBox.RandomTrack(DawnsMusicRarity.Common)); - [Constructible] - public DawnsMusicGear( MusicName music ) : base( 0x1053 ) - { - Music = music; + public static DawnsMusicGear RandomUncommon => + new DawnsMusicGear(DawnsMusicBox.RandomTrack(DawnsMusicRarity.Uncommon)); - Weight = 1.0; - } + public static DawnsMusicGear RandomRare => new DawnsMusicGear(DawnsMusicBox.RandomTrack(DawnsMusicRarity.Rare)); - public DawnsMusicGear( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public MusicName Music{ get; set; } - public override void AddNameProperty( ObjectPropertyList list ) - { - DawnsMusicInfo info = DawnsMusicBox.GetInfo( Music ); + public override void AddNameProperty(ObjectPropertyList list) + { + DawnsMusicInfo info = DawnsMusicBox.GetInfo(Music); - if ( info != null ) - { - if ( info.Rarity == DawnsMusicRarity.Common ) - list.Add( 1075204 ); // Gear for Dawn's Music Box (Common) - else if ( info.Rarity == DawnsMusicRarity.Uncommon ) - list.Add( 1075205 ); // Gear for Dawn's Music Box (Uncommon) - else if ( info.Rarity == DawnsMusicRarity.Rare ) - list.Add( 1075206 ); // Gear for Dawn's Music Box (Rare) + if (info != null) + { + if (info.Rarity == DawnsMusicRarity.Common) + list.Add(1075204); // Gear for Dawn's Music Box (Common) + else if (info.Rarity == DawnsMusicRarity.Uncommon) + list.Add(1075205); // Gear for Dawn's Music Box (Uncommon) + else if (info.Rarity == DawnsMusicRarity.Rare) + list.Add(1075206); // Gear for Dawn's Music Box (Rare) - list.Add( info.Name ); - } - else - base.AddNameProperty( list ); - } + list.Add(info.Name); + } + else + { + base.AddNameProperty(list); + } + } - public override void OnDoubleClick( Mobile from ) - { - from.Target = new InternalTarget( this ); - } + public override void OnDoubleClick(Mobile from) + { + from.Target = new InternalTarget(this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 1 ); // version + writer.WriteEncodedInt(1); // version - writer.Write( (int) Music ); - } + writer.Write((int)Music); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - switch ( version ) - { - case 1: - { - Music = (MusicName) reader.ReadInt(); - break; - } - } + switch (version) + { + case 1: + { + Music = (MusicName)reader.ReadInt(); + break; + } + } - if ( version == 0 ) // Music wasn't serialized in version 0, pick a new track of random rarity - { - DawnsMusicRarity rarity; - double rand = Utility.RandomDouble(); + if (version == 0) // Music wasn't serialized in version 0, pick a new track of random rarity + { + DawnsMusicRarity rarity; + double rand = Utility.RandomDouble(); - if ( rand < 0.025 ) - rarity = DawnsMusicRarity.Rare; - else if ( rand < 0.225 ) - rarity = DawnsMusicRarity.Uncommon; - else - rarity = DawnsMusicRarity.Common; + if (rand < 0.025) + rarity = DawnsMusicRarity.Rare; + else if (rand < 0.225) + rarity = DawnsMusicRarity.Uncommon; + else + rarity = DawnsMusicRarity.Common; - Music = DawnsMusicBox.RandomTrack( rarity ); - } - } + Music = DawnsMusicBox.RandomTrack(rarity); + } + } - public class InternalTarget : Target - { - private DawnsMusicGear m_Gear; + public class InternalTarget : Target + { + private DawnsMusicGear m_Gear; - public InternalTarget( DawnsMusicGear gear ) : base( 2, false, TargetFlags.None ) - { - m_Gear = gear; - } + public InternalTarget(DawnsMusicGear gear) : base(2, false, TargetFlags.None) + { + m_Gear = gear; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Gear == null || m_Gear.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Gear == null || m_Gear.Deleted) + return; - if ( targeted is DawnsMusicBox box ) - { - if ( !box.Tracks.Contains( m_Gear.Music ) ) - { - box.Tracks.Add( m_Gear.Music ); - box.InvalidateProperties(); + if (targeted is DawnsMusicBox box) + { + if (!box.Tracks.Contains(m_Gear.Music)) + { + box.Tracks.Add(m_Gear.Music); + box.InvalidateProperties(); - m_Gear.Delete(); + m_Gear.Delete(); - from.SendLocalizedMessage( 1071961 ); // This song has been added to the musicbox. - } - else - from.SendLocalizedMessage( 1071962 ); // This song track is already in the musicbox. - } - else - from.SendLocalizedMessage( 1071964 ); // Gears can only be put into a musicbox. - } - } - } -} + from.SendLocalizedMessage(1071961); // This song has been added to the musicbox. + } + else + { + from.SendLocalizedMessage(1071962); // This song track is already in the musicbox. + } + } + else + { + from.SendLocalizedMessage(1071964); // Gears can only be put into a musicbox. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicInfo.cs b/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicInfo.cs index 7b1e64d15..3f7245464 100644 --- a/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicInfo.cs +++ b/Scripts/Items/Special/8th Anniversary Items/Dawn's Music Box/DawnsMusicInfo.cs @@ -1,22 +1,22 @@ namespace Server.Items { - public enum DawnsMusicRarity - { - Common, - Uncommon, - Rare, - } + public enum DawnsMusicRarity + { + Common, + Uncommon, + Rare + } - public class DawnsMusicInfo - { - public int Name { get; } + public class DawnsMusicInfo + { + public DawnsMusicInfo(int name, DawnsMusicRarity rarity) + { + Name = name; + Rarity = rarity; + } - public DawnsMusicRarity Rarity { get; } + public int Name{ get; } - public DawnsMusicInfo( int name, DawnsMusicRarity rarity ) - { - Name = name; - Rarity = rarity; - } - } -} + public DawnsMusicRarity Rarity{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/DupresShield.cs b/Scripts/Items/Special/8th Anniversary Items/DupresShield.cs index 8c7b48caf..c4015a786 100644 --- a/Scripts/Items/Special/8th Anniversary Items/DupresShield.cs +++ b/Scripts/Items/Special/8th Anniversary Items/DupresShield.cs @@ -1,50 +1,50 @@ namespace Server.Items { - public class DupresShield : BaseShield, ITokunoDyable - { - public override int LabelNumber => 1075196; // Dupre�s Shield + public class DupresShield : BaseShield, ITokunoDyable + { + [Constructible] + public DupresShield() : base(0x2B01) + { + LootType = LootType.Blessed; + Weight = 6.0; - public override int BasePhysicalResistance => 1; - public override int BaseFireResistance => 0; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 0; - public override int BaseEnergyResistance => 1; + Attributes.BonusHits = 5; + Attributes.RegenHits = 1; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + SkillBonuses.SetValues(0, SkillName.Parry, 5); + } - public override int AosStrReq => 50; + public DupresShield(Serial serial) : base(serial) + { + } - public override int ArmorBase => 15; + public override int LabelNumber => 1075196; // Dupre�s Shield - [Constructible] - public DupresShield() : base( 0x2B01 ) - { - LootType = LootType.Blessed; - Weight = 6.0; + public override int BasePhysicalResistance => 1; + public override int BaseFireResistance => 0; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 0; + public override int BaseEnergyResistance => 1; - Attributes.BonusHits = 5; - Attributes.RegenHits = 1; + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - SkillBonuses.SetValues( 0, SkillName.Parry, 5 ); - } + public override int AosStrReq => 50; - public DupresShield( Serial serial ) : base( serial ) - { - } + public override int ArmorBase => 15; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/FountainOfLife.cs b/Scripts/Items/Special/8th Anniversary Items/FountainOfLife.cs index 4f923423c..454df54de 100644 --- a/Scripts/Items/Special/8th Anniversary Items/FountainOfLife.cs +++ b/Scripts/Items/Special/8th Anniversary Items/FountainOfLife.cs @@ -2,265 +2,273 @@ using System; namespace Server.Items { - public class EnhancedBandage : Bandage - { - public static int HealingBonus => 10; + public class EnhancedBandage : Bandage + { + [Constructible] + public EnhancedBandage() + : this(1) + { + } - public override int LabelNumber => 1152441; // enhanced bandage + [Constructible] + public EnhancedBandage(int amount) + : base(amount) + { + Hue = 0x8A5; + } - [Constructible] - public EnhancedBandage() - : this( 1 ) - { - } + public EnhancedBandage(Serial serial) + : base(serial) + { + } - [Constructible] - public EnhancedBandage( int amount ) - : base( amount ) - { - Hue = 0x8A5; - } + public static int HealingBonus => 10; - public EnhancedBandage( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1152441; // enhanced bandage - public override bool Dye( Mobile from, DyeTub sender ) - { - return false; - } + public override bool Dye(Mobile from, DyeTub sender) + { + return false; + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1075216 ); // these bandages have been enhanced - } + list.Add(1075216); // these bandages have been enhanced + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [FlippableAttribute( 0x2AC0, 0x2AC3 )] - public class FountainOfLife : BaseAddonContainer - { - public override BaseAddonContainerDeed Deed => new FountainOfLifeDeed( m_Charges ); + [Flippable(0x2AC0, 0x2AC3)] + public class FountainOfLife : BaseAddonContainer + { + private int m_Charges; - public override bool OnDragLift( Mobile from ) - { - return false; - } + private Timer m_Timer; - public virtual TimeSpan RechargeTime => TimeSpan.FromDays( 1 ); + [Constructible] + public FountainOfLife() + : this(10) + { + } - public override int LabelNumber => 1075197; // Fountain of Life - public override int DefaultGumpID => 0x484; - public override int DefaultDropSound => 66; - public override int DefaultMaxItems => 125; + [Constructible] + public FountainOfLife(int charges) + : base(0x2AC0) + { + m_Charges = charges; - private int m_Charges; + m_Timer = Timer.DelayCall(RechargeTime, RechargeTime, Recharge); + } - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set { m_Charges = Math.Min( value, 10 ); InvalidateProperties(); } - } + public FountainOfLife(Serial serial) + : base(serial) + { + } - private Timer m_Timer; + public override BaseAddonContainerDeed Deed => new FountainOfLifeDeed(m_Charges); - [Constructible] - public FountainOfLife() - : this( 10 ) - { - } + public virtual TimeSpan RechargeTime => TimeSpan.FromDays(1); - [Constructible] - public FountainOfLife( int charges ) - : base( 0x2AC0 ) - { - m_Charges = charges; + public override int LabelNumber => 1075197; // Fountain of Life + public override int DefaultGumpID => 0x484; + public override int DefaultDropSound => 66; + public override int DefaultMaxItems => 125; - m_Timer = Timer.DelayCall( RechargeTime, RechargeTime, Recharge ); - } + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = Math.Min(value, 10); + InvalidateProperties(); + } + } - public FountainOfLife( Serial serial ) - : base( serial ) - { - } + public override bool OnDragLift(Mobile from) + { + return false; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is Bandage ) - { - bool allow = base.OnDragDrop( from, dropped ); + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is Bandage) + { + bool allow = base.OnDragDrop(from, dropped); - if ( allow ) - Enhance( from ); + if (allow) + Enhance(from); - return allow; - } + return allow; + } - from.SendLocalizedMessage( 1075209 ); // Only bandages may be dropped into the fountain. - return false; - } + from.SendLocalizedMessage(1075209); // Only bandages may be dropped into the fountain. + return false; + } - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( item is Bandage ) - { - bool allow = base.OnDragDropInto( from, item, p ); + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (item is Bandage) + { + bool allow = base.OnDragDropInto(from, item, p); - if ( allow ) - Enhance( from ); + if (allow) + Enhance(from); - return allow; - } + return allow; + } - from.SendLocalizedMessage( 1075209 ); // Only bandages may be dropped into the fountain. - return false; - } + from.SendLocalizedMessage(1075209); // Only bandages may be dropped into the fountain. + return false; + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1075217, m_Charges.ToString() ); // ~1_val~ charges remaining - } + list.Add(1075217, m_Charges.ToString()); // ~1_val~ charges remaining + } - public override void OnDelete() - { - m_Timer?.Stop(); + public override void OnDelete() + { + m_Timer?.Stop(); - base.OnDelete(); - } + base.OnDelete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version + writer.WriteEncodedInt(0); //version - writer.Write( m_Charges ); - writer.Write( (DateTime)m_Timer.Next ); - } + writer.Write(m_Charges); + writer.Write(m_Timer.Next); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Charges = reader.ReadInt(); + m_Charges = reader.ReadInt(); - DateTime next = reader.ReadDateTime(); + DateTime next = reader.ReadDateTime(); - if ( next < DateTime.UtcNow ) - m_Timer = Timer.DelayCall( TimeSpan.Zero, RechargeTime, Recharge ); - else - m_Timer = Timer.DelayCall( next - DateTime.UtcNow, RechargeTime, Recharge ); - } + if (next < DateTime.UtcNow) + m_Timer = Timer.DelayCall(TimeSpan.Zero, RechargeTime, Recharge); + else + m_Timer = Timer.DelayCall(next - DateTime.UtcNow, RechargeTime, Recharge); + } - public void Recharge() - { - m_Charges = 10; + public void Recharge() + { + m_Charges = 10; - Enhance( null ); - } + Enhance(null); + } - public void Enhance( Mobile from ) - { - for( int i = Items.Count - 1; i >= 0 && m_Charges > 0; --i ) - { - if ( Items[i] is EnhancedBandage ) - continue; + public void Enhance(Mobile from) + { + for (int i = Items.Count - 1; i >= 0 && m_Charges > 0; --i) + { + if (Items[i] is EnhancedBandage) + continue; - if ( Items[i] is Bandage bandage ) - { - Item enhanced; + if (Items[i] is Bandage bandage) + { + Item enhanced; - if ( bandage.Amount > m_Charges ) - { - bandage.Amount -= m_Charges; - enhanced = new EnhancedBandage( m_Charges ); - m_Charges = 0; - } - else - { - enhanced = new EnhancedBandage( bandage.Amount ); - m_Charges -= bandage.Amount; - bandage.Delete(); - } + if (bandage.Amount > m_Charges) + { + bandage.Amount -= m_Charges; + enhanced = new EnhancedBandage(m_Charges); + m_Charges = 0; + } + else + { + enhanced = new EnhancedBandage(bandage.Amount); + m_Charges -= bandage.Amount; + bandage.Delete(); + } - if ( from == null || !TryDropItem( from, enhanced, false ) ) // try stacking first - DropItem( enhanced ); - } - } + if (from == null || !TryDropItem(from, enhanced, false)) // try stacking first + DropItem(enhanced); + } + } - InvalidateProperties(); - } - } + InvalidateProperties(); + } + } - public class FountainOfLifeDeed : BaseAddonContainerDeed - { - public override int LabelNumber => 1075197; // Fountain of Life - public override BaseAddonContainer Addon => new FountainOfLife( m_Charges ); + public class FountainOfLifeDeed : BaseAddonContainerDeed + { + private int m_Charges; - private int m_Charges; + [Constructible] + public FountainOfLifeDeed() + : this(10) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set { m_Charges = Math.Min( value, 10 ); InvalidateProperties(); } - } + [Constructible] + public FountainOfLifeDeed(int charges) + { + LootType = LootType.Blessed; + m_Charges = charges; + } - [Constructible] - public FountainOfLifeDeed() - : this( 10 ) - { - } + public FountainOfLifeDeed(Serial serial) + : base(serial) + { + } - [Constructible] - public FountainOfLifeDeed( int charges ) - { - LootType = LootType.Blessed; - m_Charges = charges; - } + public override int LabelNumber => 1075197; // Fountain of Life + public override BaseAddonContainer Addon => new FountainOfLife(m_Charges); - public FountainOfLifeDeed( Serial serial ) - : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = Math.Min(value, 10); + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version + writer.WriteEncodedInt(0); //version - writer.Write( m_Charges ); - } + writer.Write(m_Charges); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Charges = reader.ReadInt(); - } - } -} + m_Charges = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/OssianGrimoire.cs b/Scripts/Items/Special/8th Anniversary Items/OssianGrimoire.cs index 9658e1461..727ccb86e 100644 --- a/Scripts/Items/Special/8th Anniversary Items/OssianGrimoire.cs +++ b/Scripts/Items/Special/8th Anniversary Items/OssianGrimoire.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class OssianGrimoire : NecromancerSpellbook, ITokunoDyable - { - public override int LabelNumber => 1078148; // Ossian Grimoire + public class OssianGrimoire : NecromancerSpellbook, ITokunoDyable + { + [Constructible] + public OssianGrimoire() + { + LootType = LootType.Blessed; - [Constructible] - public OssianGrimoire() - { - LootType = LootType.Blessed; + SkillBonuses.SetValues(0, SkillName.Necromancy, 10.0); + Attributes.RegenMana = 1; + Attributes.CastSpeed = 1; + Attributes.IncreasedKarmaLoss = 5; + } - SkillBonuses.SetValues( 0, SkillName.Necromancy, 10.0 ); - Attributes.RegenMana = 1; - Attributes.CastSpeed = 1; - Attributes.IncreasedKarmaLoss = 5; - } + public OssianGrimoire(Serial serial) : base(serial) + { + } - public OssianGrimoire( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1078148; // Ossian Grimoire - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); //version - } + writer.WriteEncodedInt(1); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if ( version == 0 ) - Attributes.IncreasedKarmaLoss = 5; - } - } -} + if (version == 0) + Attributes.IncreasedKarmaLoss = 5; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/QuiverOfInfinity.cs b/Scripts/Items/Special/8th Anniversary Items/QuiverOfInfinity.cs index ea2560edf..267061df1 100644 --- a/Scripts/Items/Special/8th Anniversary Items/QuiverOfInfinity.cs +++ b/Scripts/Items/Special/8th Anniversary Items/QuiverOfInfinity.cs @@ -1,43 +1,43 @@ namespace Server.Items { - public class QuiverOfInfinity : BaseQuiver, ITokunoDyable - { - public override int LabelNumber => 1075201; // Quiver of Infinity + public class QuiverOfInfinity : BaseQuiver, ITokunoDyable + { + [Constructible] + public QuiverOfInfinity() : base(0x2B02) + { + LootType = LootType.Blessed; + Weight = 8.0; - [Constructible] - public QuiverOfInfinity() : base( 0x2B02 ) - { - LootType = LootType.Blessed; - Weight = 8.0; + WeightReduction = 30; + LowerAmmoCost = 20; - WeightReduction = 30; - LowerAmmoCost = 20; + Attributes.DefendChance = 5; + } - Attributes.DefendChance = 5; - } + public QuiverOfInfinity(Serial serial) : base(serial) + { + } - public QuiverOfInfinity( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1075201; // Quiver of Infinity - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 2 ); // version - } + writer.WriteEncodedInt(2); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if ( version < 1 && DamageIncrease == 0 ) - DamageIncrease = 10; + if (version < 1 && DamageIncrease == 0) + DamageIncrease = 10; - if ( version < 2 && Attributes.WeaponDamage == 10 ) - Attributes.WeaponDamage = 0; - } - } -} + if (version < 2 && Attributes.WeaponDamage == 10) + Attributes.WeaponDamage = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/8th Anniversary Items/Talismans.cs b/Scripts/Items/Special/8th Anniversary Items/Talismans.cs index b6e0b78e1..3c8cfb4bd 100644 --- a/Scripts/Items/Special/8th Anniversary Items/Talismans.cs +++ b/Scripts/Items/Special/8th Anniversary Items/Talismans.cs @@ -4,182 +4,179 @@ using Server.Spells.Ninjitsu; namespace Server.Items { - public enum TalismanForm - { - Ferret = 1031672, - Squirrel = 1031671, - CuSidhe = 1031670, - Reptalon = 1075202 - } + public enum TalismanForm + { + Ferret = 1031672, + Squirrel = 1031671, + CuSidhe = 1031670, + Reptalon = 1075202 + } - public class BaseFormTalisman : Item, ITokunoDyable - { - public virtual TalismanForm Form => TalismanForm.Squirrel; + public class BaseFormTalisman : Item, ITokunoDyable + { + public BaseFormTalisman() : base(0x2F59) + { + LootType = LootType.Blessed; + Layer = Layer.Talisman; + Weight = 1.0; + } - public BaseFormTalisman() : base( 0x2F59 ) - { - LootType = LootType.Blessed; - Layer = Layer.Talisman; - Weight = 1.0; - } + public BaseFormTalisman(Serial serial) : base(serial) + { + } - public BaseFormTalisman( Serial serial ) : base( serial ) - { - } + public virtual TalismanForm Form => TalismanForm.Squirrel; - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1075200, $"#{(int) Form}"); - } + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1075200, $"#{(int)Form}"); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); - if ( parent is Mobile m ) - { - AnimalForm.RemoveContext( m, true ); - } - } + if (parent is Mobile m) AnimalForm.RemoveContext(m, true); + } - public static bool EntryEnabled( Mobile m, Type type ) - { - if ( type == typeof( Squirrel ) ) - return m.Talisman is SquirrelFormTalisman; - if ( type == typeof( Ferret ) ) - return m.Talisman is FerretFormTalisman; - if ( type == typeof( CuSidhe ) ) - return m.Talisman is CuSidheFormTalisman; - if ( type == typeof( Reptalon ) ) - return m.Talisman is ReptalonFormTalisman; + public static bool EntryEnabled(Mobile m, Type type) + { + if (type == typeof(Squirrel)) + return m.Talisman is SquirrelFormTalisman; + if (type == typeof(Ferret)) + return m.Talisman is FerretFormTalisman; + if (type == typeof(CuSidhe)) + return m.Talisman is CuSidheFormTalisman; + if (type == typeof(Reptalon)) + return m.Talisman is ReptalonFormTalisman; - return true; - } - } + return true; + } + } - public class FerretFormTalisman : BaseFormTalisman - { - public override TalismanForm Form => TalismanForm.Ferret; + public class FerretFormTalisman : BaseFormTalisman + { + [Constructible] + public FerretFormTalisman() + { + } - [Constructible] - public FerretFormTalisman() - { - } + public FerretFormTalisman(Serial serial) : base(serial) + { + } - public FerretFormTalisman( Serial serial ) : base( serial ) - { - } + public override TalismanForm Form => TalismanForm.Ferret; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SquirrelFormTalisman : BaseFormTalisman - { - public override TalismanForm Form => TalismanForm.Squirrel; + public class SquirrelFormTalisman : BaseFormTalisman + { + [Constructible] + public SquirrelFormTalisman() + { + } - [Constructible] - public SquirrelFormTalisman () - { - } + public SquirrelFormTalisman(Serial serial) : base(serial) + { + } - public SquirrelFormTalisman ( Serial serial ) : base( serial ) - { - } + public override TalismanForm Form => TalismanForm.Squirrel; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class CuSidheFormTalisman : BaseFormTalisman - { - public override TalismanForm Form => TalismanForm.CuSidhe; + public class CuSidheFormTalisman : BaseFormTalisman + { + [Constructible] + public CuSidheFormTalisman() + { + } - [Constructible] - public CuSidheFormTalisman() - { - } + public CuSidheFormTalisman(Serial serial) : base(serial) + { + } - public CuSidheFormTalisman( Serial serial ) : base( serial ) - { - } + public override TalismanForm Form => TalismanForm.CuSidhe; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ReptalonFormTalisman : BaseFormTalisman - { - public override TalismanForm Form => TalismanForm.Reptalon; + public class ReptalonFormTalisman : BaseFormTalisman + { + [Constructible] + public ReptalonFormTalisman() + { + } - [Constructible] - public ReptalonFormTalisman() - { - } + public ReptalonFormTalisman(Serial serial) : base(serial) + { + } - public ReptalonFormTalisman( Serial serial ) : base( serial ) - { - } + public override TalismanForm Form => TalismanForm.Reptalon; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); //version - } + writer.WriteEncodedInt(0); //version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/AoS Promotional/HoodedShroudOfShadows.cs b/Scripts/Items/Special/AoS Promotional/HoodedShroudOfShadows.cs index 3f70fb2ff..bb71049e4 100644 --- a/Scripts/Items/Special/AoS Promotional/HoodedShroudOfShadows.cs +++ b/Scripts/Items/Special/AoS Promotional/HoodedShroudOfShadows.cs @@ -1,42 +1,42 @@ namespace Server.Items { - [Flippable( 0x2684, 0x2683 )] - public class HoodedShroudOfShadows : BaseOuterTorso - { - [Constructible] - public HoodedShroudOfShadows() : this( 0x455 ) - { - } + [Flippable(0x2684, 0x2683)] + public class HoodedShroudOfShadows : BaseOuterTorso + { + [Constructible] + public HoodedShroudOfShadows() : this(0x455) + { + } - [Constructible] - public HoodedShroudOfShadows( int hue ) : base( 0x2684, hue ) - { - LootType = LootType.Blessed; - Weight = 3.0; - } + [Constructible] + public HoodedShroudOfShadows(int hue) : base(0x2684, hue) + { + LootType = LootType.Blessed; + Weight = 3.0; + } - public override bool Dye( Mobile from, DyeTub sender ) - { - from.SendLocalizedMessage( sender.FailMessage ); - return false; - } + public HoodedShroudOfShadows(Serial serial) : base(serial) + { + } - public HoodedShroudOfShadows( Serial serial ) : base( serial ) - { - } + public override bool Dye(Mobile from, DyeTub sender) + { + from.SendLocalizedMessage(sender.FailMessage); + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/AoS Promotional/LuckyNecklace.cs b/Scripts/Items/Special/AoS Promotional/LuckyNecklace.cs index 085af49bf..a3cd96b10 100644 --- a/Scripts/Items/Special/AoS Promotional/LuckyNecklace.cs +++ b/Scripts/Items/Special/AoS Promotional/LuckyNecklace.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public class LuckyNecklace : BaseJewel - { - public override int Hue => 1150; - public override int LabelNumber => 1075239; //Lucky Necklace 1075239 + public class LuckyNecklace : BaseJewel + { + [Constructible] + public LuckyNecklace() + : base(0x1088, Layer.Neck) + { + Attributes.Luck = 200; + LootType = LootType.Blessed; + } - [Constructible] - public LuckyNecklace( ) - : base( 0x1088, Layer.Neck ) - { - Attributes.Luck = 200; - LootType = LootType.Blessed; - } + public LuckyNecklace(Serial serial) : base(serial) + { + } - public LuckyNecklace( Serial serial ) : base( serial ) - { - } + public override int Hue => 1150; + public override int LabelNumber => 1075239; //Lucky Necklace 1075239 - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - reader.ReadInt(); /* int version = reader.ReadInt(); Why? Just to have an unused var? */ - } - } -} + reader.ReadInt(); /* int version = reader.ReadInt(); Why? Just to have an unused var? */ + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenArmoire.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenArmoire.cs index 7c5016aef..5e20d9672 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenArmoire.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenArmoire.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0xC12, 0xC13 )] - public class BrokenArmoireComponent : AddonComponent - { - public override int LabelNumber => 1076262; // Broken Armoire + [Flippable(0xC12, 0xC13)] + public class BrokenArmoireComponent : AddonComponent + { + public BrokenArmoireComponent() : base(0xC12) + { + } - public BrokenArmoireComponent() : base( 0xC12 ) - { - } + public BrokenArmoireComponent(Serial serial) : base(serial) + { + } - public BrokenArmoireComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076262; // Broken Armoire - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenArmoireAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenArmoireDeed(); + public class BrokenArmoireAddon : BaseAddon + { + [Constructible] + public BrokenArmoireAddon() + { + AddComponent(new BrokenArmoireComponent(), 0, 0, 0); + } - [Constructible] - public BrokenArmoireAddon() - { - AddComponent( new BrokenArmoireComponent(), 0, 0, 0 ); - } + public BrokenArmoireAddon(Serial serial) : base(serial) + { + } - public BrokenArmoireAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenArmoireDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenArmoireDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenArmoireAddon(); - public override int LabelNumber => 1076262; // Broken Armoire + public class BrokenArmoireDeed : BaseAddonDeed + { + [Constructible] + public BrokenArmoireDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenArmoireDeed() - { - LootType = LootType.Blessed; - } + public BrokenArmoireDeed(Serial serial) : base(serial) + { + } - public BrokenArmoireDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenArmoireAddon(); + public override int LabelNumber => 1076262; // Broken Armoire - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenBed.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenBed.cs index 517406ee2..26b06e78c 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenBed.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenBed.cs @@ -3,130 +3,132 @@ using Server.Network; namespace Server.Items { - public class BrokenBedAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenBedDeed(); + public class BrokenBedAddon : BaseAddon + { + [Constructible] + public BrokenBedAddon(bool east) + { + if (east) // east + { + AddComponent(new LocalizedAddonComponent(0x1895, 1076263), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1894, 1076263), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0x1897, 1076263), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1896, 1076263), 1, 1, 0); + } + else // south + { + AddComponent(new LocalizedAddonComponent(0x1899, 1076263), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1898, 1076263), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0x189B, 1076263), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0x189A, 1076263), 1, 1, 0); + } + } - [Constructible] - public BrokenBedAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new LocalizedAddonComponent( 0x1895, 1076263 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1894, 1076263 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1897, 1076263 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1896, 1076263 ), 1, 1, 0 ); - } - else // south - { - AddComponent( new LocalizedAddonComponent( 0x1899, 1076263 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1898, 1076263 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x189B, 1076263 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0x189A, 1076263 ), 1, 1, 0 ); - } - } + public BrokenBedAddon(Serial serial) : base(serial) + { + } - public BrokenBedAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenBedDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenBedDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenBedAddon( m_East ); - public override int LabelNumber => 1076263; // Broken Bed + public class BrokenBedDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public BrokenBedDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenBedDeed() - { - LootType = LootType.Blessed; - } + public BrokenBedDeed(Serial serial) : base(serial) + { + } - public BrokenBedDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenBedAddon(m_East); + public override int LabelNumber => 1076263; // Broken Bed - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private BrokenBedDeed m_Deed; + private class InternalGump : Gump + { + private BrokenBedDeed m_Deed; - public InternalGump( BrokenBedDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(BrokenBedDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076749, 0x7FFF, false, false ); // Please select your broken bed position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076749, 0x7FFF, false, false); // Please select your broken bed position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenBookcase.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenBookcase.cs index f66233598..e712b2624 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenBookcase.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenBookcase.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0xC14, 0xC15 )] - public class BrokenBookcaseComponent : AddonComponent - { - public override int LabelNumber => 1076258; // Broken Bookcase + [Flippable(0xC14, 0xC15)] + public class BrokenBookcaseComponent : AddonComponent + { + public BrokenBookcaseComponent() : base(0xC14) + { + } - public BrokenBookcaseComponent() : base( 0xC14 ) - { - } + public BrokenBookcaseComponent(Serial serial) : base(serial) + { + } - public BrokenBookcaseComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076258; // Broken Bookcase - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenBookcaseAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenBookcaseDeed(); + public class BrokenBookcaseAddon : BaseAddon + { + [Constructible] + public BrokenBookcaseAddon() + { + AddComponent(new BrokenBookcaseComponent(), 0, 0, 0); + } - [Constructible] - public BrokenBookcaseAddon() - { - AddComponent( new BrokenBookcaseComponent(), 0, 0, 0 ); - } + public BrokenBookcaseAddon(Serial serial) : base(serial) + { + } - public BrokenBookcaseAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenBookcaseDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenBookcaseDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenBookcaseAddon(); - public override int LabelNumber => 1076258; // Broken Bookcase + public class BrokenBookcaseDeed : BaseAddonDeed + { + [Constructible] + public BrokenBookcaseDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenBookcaseDeed() - { - LootType = LootType.Blessed; - } + public BrokenBookcaseDeed(Serial serial) : base(serial) + { + } - public BrokenBookcaseDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenBookcaseAddon(); + public override int LabelNumber => 1076258; // Broken Bookcase - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenChestOfDrawers.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenChestOfDrawers.cs index 3c1189511..60eb46317 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenChestOfDrawers.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenChestOfDrawers.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0xC24, 0xC25 )] - public class BrokenChestOfDrawersComponent : AddonComponent - { - public override int LabelNumber => 1076261; // Broken Chest of Drawers + [Flippable(0xC24, 0xC25)] + public class BrokenChestOfDrawersComponent : AddonComponent + { + public BrokenChestOfDrawersComponent() : base(0xC24) + { + } - public BrokenChestOfDrawersComponent() : base( 0xC24 ) - { - } + public BrokenChestOfDrawersComponent(Serial serial) : base(serial) + { + } - public BrokenChestOfDrawersComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076261; // Broken Chest of Drawers - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenChestOfDrawersAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenChestOfDrawersDeed(); + public class BrokenChestOfDrawersAddon : BaseAddon + { + [Constructible] + public BrokenChestOfDrawersAddon() + { + AddComponent(new BrokenChestOfDrawersComponent(), 0, 0, 0); + } - [Constructible] - public BrokenChestOfDrawersAddon() - { - AddComponent( new BrokenChestOfDrawersComponent(), 0, 0, 0 ); - } + public BrokenChestOfDrawersAddon(Serial serial) : base(serial) + { + } - public BrokenChestOfDrawersAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenChestOfDrawersDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenChestOfDrawersDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenChestOfDrawersAddon(); - public override int LabelNumber => 1076261; // Broken Chest of Drawers + public class BrokenChestOfDrawersDeed : BaseAddonDeed + { + [Constructible] + public BrokenChestOfDrawersDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenChestOfDrawersDeed() - { - LootType = LootType.Blessed; - } + public BrokenChestOfDrawersDeed(Serial serial) : base(serial) + { + } - public BrokenChestOfDrawersDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenChestOfDrawersAddon(); + public override int LabelNumber => 1076261; // Broken Chest of Drawers - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenCoveredChair.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenCoveredChair.cs index e65db41a2..b78f38077 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenCoveredChair.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenCoveredChair.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0xC17, 0xC18 )] - public class BrokenCoveredChairComponent : AddonComponent - { - public override int LabelNumber => 1076257; // Broken Covered Chair + [Flippable(0xC17, 0xC18)] + public class BrokenCoveredChairComponent : AddonComponent + { + public BrokenCoveredChairComponent() : base(0xC17) + { + } - public BrokenCoveredChairComponent() : base( 0xC17 ) - { - } + public BrokenCoveredChairComponent(Serial serial) : base(serial) + { + } - public BrokenCoveredChairComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076257; // Broken Covered Chair - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenCoveredChairAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenCoveredChairDeed(); + public class BrokenCoveredChairAddon : BaseAddon + { + [Constructible] + public BrokenCoveredChairAddon() + { + AddComponent(new BrokenCoveredChairComponent(), 0, 0, 0); + } - [Constructible] - public BrokenCoveredChairAddon() - { - AddComponent( new BrokenCoveredChairComponent(), 0, 0, 0 ); - } + public BrokenCoveredChairAddon(Serial serial) : base(serial) + { + } - public BrokenCoveredChairAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenCoveredChairDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenCoveredChairDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenCoveredChairAddon(); - public override int LabelNumber => 1076257; // Broken Covered Chair + public class BrokenCoveredChairDeed : BaseAddonDeed + { + [Constructible] + public BrokenCoveredChairDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenCoveredChairDeed() - { - LootType = LootType.Blessed; - } + public BrokenCoveredChairDeed(Serial serial) : base(serial) + { + } - public BrokenCoveredChairDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenCoveredChairAddon(); + public override int LabelNumber => 1076257; // Broken Covered Chair - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenFallenChair.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenFallenChair.cs index ce8eb83a2..076319e93 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenFallenChair.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenFallenChair.cs @@ -1,92 +1,92 @@ namespace Server.Items { - [Flippable( 0xC19, 0xC1A )] - public class BrokenFallenChairComponent : AddonComponent - { - public override int LabelNumber => 1076264; // Broken Fallen Chair + [Flippable(0xC19, 0xC1A)] + public class BrokenFallenChairComponent : AddonComponent + { + public BrokenFallenChairComponent() : base(0xC19) + { + } - public BrokenFallenChairComponent() : base( 0xC19 ) - { - } + public BrokenFallenChairComponent(Serial serial) : base(serial) + { + } - public BrokenFallenChairComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076264; // Broken Fallen Chair - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version - } + writer.WriteEncodedInt(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if (version < 1 && ItemID == 0xC17) - ItemID = 0xC19; - } - } + if (version < 1 && ItemID == 0xC17) + ItemID = 0xC19; + } + } - public class BrokenFallenChairAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenFallenChairDeed(); + public class BrokenFallenChairAddon : BaseAddon + { + [Constructible] + public BrokenFallenChairAddon() + { + AddComponent(new BrokenFallenChairComponent(), 0, 0, 0); + } - [Constructible] - public BrokenFallenChairAddon() - { - AddComponent( new BrokenFallenChairComponent(), 0, 0, 0 ); - } + public BrokenFallenChairAddon(Serial serial) : base(serial) + { + } - public BrokenFallenChairAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenFallenChairDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenFallenChairDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenFallenChairAddon(); - public override int LabelNumber => 1076264; // Broken Fallen Chair + public class BrokenFallenChairDeed : BaseAddonDeed + { + [Constructible] + public BrokenFallenChairDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenFallenChairDeed() - { - LootType = LootType.Blessed; - } + public BrokenFallenChairDeed(Serial serial) : base(serial) + { + } - public BrokenFallenChairDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenFallenChairAddon(); + public override int LabelNumber => 1076264; // Broken Fallen Chair - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/BrokenVanity.cs b/Scripts/Items/Special/Broken Furniture Collection/BrokenVanity.cs index 69b8bf738..e1c511d13 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/BrokenVanity.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/BrokenVanity.cs @@ -3,126 +3,129 @@ using Server.Network; namespace Server.Items { - public class BrokenVanityAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BrokenVanityDeed(); + public class BrokenVanityAddon : BaseAddon + { + [Constructible] + public BrokenVanityAddon(bool east) + { + if (east) // east + { + AddComponent(new LocalizedAddonComponent(0xC20, 1076260), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0xC21, 1076260), 0, -1, 0); + } + else // south + { + AddComponent(new LocalizedAddonComponent(0xC22, 1076260), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0xC23, 1076260), -1, 0, 0); + } + } - [Constructible] - public BrokenVanityAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new LocalizedAddonComponent( 0xC20, 1076260 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xC21, 1076260 ), 0, -1, 0 ); - } - else // south - { - AddComponent( new LocalizedAddonComponent( 0xC22, 1076260 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xC23, 1076260 ), -1, 0, 0 ); - } - } + public BrokenVanityAddon(Serial serial) : base(serial) + { + } - public BrokenVanityAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BrokenVanityDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BrokenVanityDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BrokenVanityAddon( m_East ); - public override int LabelNumber => 1076260; // Broken Vanity + public class BrokenVanityDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public BrokenVanityDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BrokenVanityDeed() - { - LootType = LootType.Blessed; - } + public BrokenVanityDeed(Serial serial) : base(serial) + { + } - public BrokenVanityDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BrokenVanityAddon(m_East); + public override int LabelNumber => 1076260; // Broken Vanity - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private BrokenVanityDeed m_Deed; + private class InternalGump : Gump + { + private BrokenVanityDeed m_Deed; - public InternalGump( BrokenVanityDeed deed ) : base( 60, 63 ) - { - m_Deed = deed; + public InternalGump(BrokenVanityDeed deed) : base(60, 63) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076747, 0x7FFF, false, false ); // Please select your broken vanity position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076747, 0x7FFF, false, + false); // Please select your broken vanity position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Broken Furniture Collection/StandingBrokenChair.cs b/Scripts/Items/Special/Broken Furniture Collection/StandingBrokenChair.cs index ce40350e0..fdcc7a362 100644 --- a/Scripts/Items/Special/Broken Furniture Collection/StandingBrokenChair.cs +++ b/Scripts/Items/Special/Broken Furniture Collection/StandingBrokenChair.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0xC1B, 0xC1C, 0xC1E, 0xC1D )] - public class StandingBrokenChairComponent : AddonComponent - { - public override int LabelNumber => 1076259; // Standing Broken Chair + [Flippable(0xC1B, 0xC1C, 0xC1E, 0xC1D)] + public class StandingBrokenChairComponent : AddonComponent + { + public StandingBrokenChairComponent() : base(0xC1B) + { + } - public StandingBrokenChairComponent() : base( 0xC1B ) - { - } + public StandingBrokenChairComponent(Serial serial) : base(serial) + { + } - public StandingBrokenChairComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076259; // Standing Broken Chair - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class StandingBrokenChairAddon : BaseAddon - { - public override BaseAddonDeed Deed => new StandingBrokenChairDeed(); + public class StandingBrokenChairAddon : BaseAddon + { + [Constructible] + public StandingBrokenChairAddon() + { + AddComponent(new StandingBrokenChairComponent(), 0, 0, 0); + } - [Constructible] - public StandingBrokenChairAddon() - { - AddComponent( new StandingBrokenChairComponent(), 0, 0, 0 ); - } + public StandingBrokenChairAddon(Serial serial) : base(serial) + { + } - public StandingBrokenChairAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new StandingBrokenChairDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class StandingBrokenChairDeed : BaseAddonDeed - { - public override BaseAddon Addon => new StandingBrokenChairAddon(); - public override int LabelNumber => 1076259; // Standing Broken Chair + public class StandingBrokenChairDeed : BaseAddonDeed + { + [Constructible] + public StandingBrokenChairDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public StandingBrokenChairDeed() - { - LootType = LootType.Blessed; - } + public StandingBrokenChairDeed(Serial serial) : base(serial) + { + } - public StandingBrokenChairDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new StandingBrokenChairAddon(); + public override int LabelNumber => 1076259; // Standing Broken Chair - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/AncientSmithyHammer.cs b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/AncientSmithyHammer.cs index cc45e4fcc..bd4358644 100644 --- a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/AncientSmithyHammer.cs +++ b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/AncientSmithyHammer.cs @@ -2,124 +2,124 @@ using Server.Engines.Craft; namespace Server.Items { - [FlippableAttribute( 0x13E4, 0x13E3 )] - public class AncientSmithyHammer : BaseTool - { - private int m_Bonus; - private SkillMod m_SkillMod; + [Flippable(0x13E4, 0x13E3)] + public class AncientSmithyHammer : BaseTool + { + private int m_Bonus; + private SkillMod m_SkillMod; - [CommandProperty( AccessLevel.GameMaster )] - public int Bonus - { - get => m_Bonus; - set - { - m_Bonus = value; - InvalidateProperties(); + [Constructible] + public AncientSmithyHammer(int bonus) : this(bonus, 600) + { + } - if ( m_Bonus == 0 ) - { - m_SkillMod?.Remove(); + [Constructible] + public AncientSmithyHammer(int bonus, int uses) : base(uses, 0x13E4) + { + m_Bonus = bonus; + Weight = 8.0; + Layer = Layer.OneHanded; + Hue = 0x482; + } - m_SkillMod = null; - } - else if ( m_SkillMod == null && Parent is Mobile mobile ) - { - m_SkillMod = new DefaultSkillMod( SkillName.Blacksmith, true, m_Bonus ); - mobile.AddSkillMod( m_SkillMod ); - } - else if ( m_SkillMod != null ) - { - m_SkillMod.Value = m_Bonus; - } - } - } + public AncientSmithyHammer(Serial serial) : base(serial) + { + } - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); + [CommandProperty(AccessLevel.GameMaster)] + public int Bonus + { + get => m_Bonus; + set + { + m_Bonus = value; + InvalidateProperties(); - if ( m_Bonus != 0 && parent is Mobile mobile ) - { - m_SkillMod?.Remove(); + if (m_Bonus == 0) + { + m_SkillMod?.Remove(); - m_SkillMod = new DefaultSkillMod( SkillName.Blacksmith, true, m_Bonus ); - mobile.AddSkillMod( m_SkillMod ); - } - } + m_SkillMod = null; + } + else if (m_SkillMod == null && Parent is Mobile mobile) + { + m_SkillMod = new DefaultSkillMod(SkillName.Blacksmith, true, m_Bonus); + mobile.AddSkillMod(m_SkillMod); + } + else if (m_SkillMod != null) + { + m_SkillMod.Value = m_Bonus; + } + } + } - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); + public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; + public override int LabelNumber => 1045127; // ancient smithy hammer - m_SkillMod?.Remove(); + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - m_SkillMod = null; - } + if (m_Bonus != 0 && parent is Mobile mobile) + { + m_SkillMod?.Remove(); - public override CraftSystem CraftSystem => DefBlacksmithy.CraftSystem; - public override int LabelNumber => 1045127; // ancient smithy hammer + m_SkillMod = new DefaultSkillMod(SkillName.Blacksmith, true, m_Bonus); + mobile.AddSkillMod(m_SkillMod); + } + } - [Constructible] - public AncientSmithyHammer( int bonus ) : this( bonus, 600 ) - { - } + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); - [Constructible] - public AncientSmithyHammer( int bonus, int uses ) : base( uses, 0x13E4 ) - { - m_Bonus = bonus; - Weight = 8.0; - Layer = Layer.OneHanded; - Hue = 0x482; - } + m_SkillMod?.Remove(); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + m_SkillMod = null; + } - if ( m_Bonus != 0 ) - list.Add( 1060451, "#1042354\t{0}", m_Bonus.ToString() ); // ~1_skillname~ +~2_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public AncientSmithyHammer( Serial serial ) : base( serial ) - { - } + if (m_Bonus != 0) + list.Add(1060451, "#1042354\t{0}", m_Bonus.ToString()); // ~1_skillname~ +~2_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_Bonus ); - } + writer.Write(m_Bonus); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Bonus = reader.ReadInt(); - break; - } - } + switch (version) + { + case 0: + { + m_Bonus = reader.ReadInt(); + break; + } + } - if ( m_Bonus != 0 && Parent is Mobile mobile ) - { - m_SkillMod?.Remove(); + if (m_Bonus != 0 && Parent is Mobile mobile) + { + m_SkillMod?.Remove(); - m_SkillMod = new DefaultSkillMod( SkillName.Blacksmith, true, m_Bonus ); - mobile.AddSkillMod( m_SkillMod ); - } + m_SkillMod = new DefaultSkillMod(SkillName.Blacksmith, true, m_Bonus); + mobile.AddSkillMod(m_SkillMod); + } - if ( Hue == 0 ) - Hue = 0x482; - } - } -} + if (Hue == 0) + Hue = 0x482; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/ColoredAnvil.cs b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/ColoredAnvil.cs index f51f9c3c6..1583d03d1 100644 --- a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/ColoredAnvil.cs +++ b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/ColoredAnvil.cs @@ -2,35 +2,37 @@ using Server.Engines.Craft; namespace Server.Items { - [Anvil, Flippable( 0xFAF, 0xFB0 )] - public class ColoredAnvil : Item - { - [Constructible] - public ColoredAnvil() : this( CraftResources.GetHue( (CraftResource)Utility.RandomMinMax( (int)CraftResource.DullCopper, (int)CraftResource.Valorite ) ) ) - { - } + [Anvil] + [Flippable(0xFAF, 0xFB0)] + public class ColoredAnvil : Item + { + [Constructible] + public ColoredAnvil() : this(CraftResources.GetHue( + (CraftResource)Utility.RandomMinMax((int)CraftResource.DullCopper, (int)CraftResource.Valorite))) + { + } - [Constructible] - public ColoredAnvil( int hue ) : base( 0xFAF ) - { - Hue = hue; - Weight = 20; - } + [Constructible] + public ColoredAnvil(int hue) : base(0xFAF) + { + Hue = hue; + Weight = 20; + } - public ColoredAnvil( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public ColoredAnvil(Serial serial) : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/GlovesOfMining.cs b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/GlovesOfMining.cs index 890c7c188..8aea8c172 100644 --- a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/GlovesOfMining.cs +++ b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/GlovesOfMining.cs @@ -1,247 +1,248 @@ namespace Server.Items { - [FlippableAttribute( 0x13c6, 0x13ce )] - public class LeatherGlovesOfMining : BaseGlovesOfMining - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 3; + [Flippable(0x13c6, 0x13ce)] + public class LeatherGlovesOfMining : BaseGlovesOfMining + { + [Constructible] + public LeatherGlovesOfMining(int bonus) : base(bonus, 0x13C6) + { + Weight = 1; + } - public override int InitMinHits => 30; - public override int InitMaxHits => 40; + public LeatherGlovesOfMining(Serial serial) : base(serial) + { + } - public override int AosStrReq => 20; - public override int OldStrReq => 10; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 3; - public override int ArmorBase => 13; + public override int InitMinHits => 30; + public override int InitMaxHits => 40; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 20; + public override int OldStrReq => 10; - public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; + public override int ArmorBase => 13; - public override int LabelNumber => 1045122; // leather blacksmith gloves of mining + public override ArmorMaterialType MaterialType => ArmorMaterialType.Leather; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - [Constructible] - public LeatherGlovesOfMining( int bonus ) : base( bonus, 0x13C6 ) - { - Weight = 1; - } + public override ArmorMeditationAllowance DefMedAllowance => ArmorMeditationAllowance.All; - public LeatherGlovesOfMining( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1045122; // leather blacksmith gloves of mining - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x13d5, 0x13dd )] - public class StuddedGlovesOfMining : BaseGlovesOfMining - { - public override int BasePhysicalResistance => 2; - public override int BaseFireResistance => 4; - public override int BaseColdResistance => 3; - public override int BasePoisonResistance => 3; - public override int BaseEnergyResistance => 4; + [Flippable(0x13d5, 0x13dd)] + public class StuddedGlovesOfMining : BaseGlovesOfMining + { + [Constructible] + public StuddedGlovesOfMining(int bonus) : base(bonus, 0x13D5) + { + Weight = 2; + } - public override int InitMinHits => 35; - public override int InitMaxHits => 45; + public StuddedGlovesOfMining(Serial serial) : base(serial) + { + } - public override int AosStrReq => 25; - public override int OldStrReq => 25; + public override int BasePhysicalResistance => 2; + public override int BaseFireResistance => 4; + public override int BaseColdResistance => 3; + public override int BasePoisonResistance => 3; + public override int BaseEnergyResistance => 4; - public override int ArmorBase => 16; + public override int InitMinHits => 35; + public override int InitMaxHits => 45; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; - public override CraftResource DefaultResource => CraftResource.RegularLeather; + public override int AosStrReq => 25; + public override int OldStrReq => 25; - public override int LabelNumber => 1045123; // studded leather blacksmith gloves of mining + public override int ArmorBase => 16; - [Constructible] - public StuddedGlovesOfMining( int bonus ) : base( bonus, 0x13D5 ) - { - Weight = 2; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Studded; + public override CraftResource DefaultResource => CraftResource.RegularLeather; - public StuddedGlovesOfMining( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1045123; // studded leather blacksmith gloves of mining - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [FlippableAttribute( 0x13eb, 0x13f2 )] - public class RingmailGlovesOfMining : BaseGlovesOfMining - { - public override int BasePhysicalResistance => 3; - public override int BaseFireResistance => 3; - public override int BaseColdResistance => 1; - public override int BasePoisonResistance => 5; - public override int BaseEnergyResistance => 3; + [Flippable(0x13eb, 0x13f2)] + public class RingmailGlovesOfMining : BaseGlovesOfMining + { + [Constructible] + public RingmailGlovesOfMining(int bonus) : base(bonus, 0x13EB) + { + Weight = 1; + } - public override int InitMinHits => 40; - public override int InitMaxHits => 50; + public RingmailGlovesOfMining(Serial serial) : base(serial) + { + } - public override int AosStrReq => 40; - public override int OldStrReq => 20; + public override int BasePhysicalResistance => 3; + public override int BaseFireResistance => 3; + public override int BaseColdResistance => 1; + public override int BasePoisonResistance => 5; + public override int BaseEnergyResistance => 3; - public override int OldDexBonus => -1; + public override int InitMinHits => 40; + public override int InitMaxHits => 50; - public override int ArmorBase => 22; + public override int AosStrReq => 40; + public override int OldStrReq => 20; - public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; + public override int OldDexBonus => -1; - public override int LabelNumber => 1045124; // ringmail blacksmith gloves of mining + public override int ArmorBase => 22; - [Constructible] - public RingmailGlovesOfMining( int bonus ) : base( bonus, 0x13EB ) - { - Weight = 1; - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Ringmail; - public RingmailGlovesOfMining( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1045124; // ringmail blacksmith gloves of mining - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public abstract class BaseGlovesOfMining : BaseArmor - { - private int m_Bonus; - private SkillMod m_SkillMod; + public abstract class BaseGlovesOfMining : BaseArmor + { + private int m_Bonus; + private SkillMod m_SkillMod; - [CommandProperty( AccessLevel.GameMaster )] - public int Bonus - { - get => m_Bonus; - set - { - m_Bonus = value; - InvalidateProperties(); + public BaseGlovesOfMining(int bonus, int itemID) : base(itemID) + { + m_Bonus = bonus; - if ( m_Bonus == 0 ) - { - m_SkillMod?.Remove(); + Hue = CraftResources.GetHue( + (CraftResource)Utility.RandomMinMax((int)CraftResource.DullCopper, (int)CraftResource.Valorite)); + } - m_SkillMod = null; - } - else if ( m_SkillMod == null && Parent is Mobile mobile ) - { - m_SkillMod = new DefaultSkillMod( SkillName.Mining, true, m_Bonus ); - mobile.AddSkillMod( m_SkillMod ); - } - else if ( m_SkillMod != null ) - { - m_SkillMod.Value = m_Bonus; - } - } - } + public BaseGlovesOfMining(Serial serial) : base(serial) + { + } - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); + [CommandProperty(AccessLevel.GameMaster)] + public int Bonus + { + get => m_Bonus; + set + { + m_Bonus = value; + InvalidateProperties(); - if ( m_Bonus != 0 && parent is Mobile mobile ) - { - m_SkillMod?.Remove(); + if (m_Bonus == 0) + { + m_SkillMod?.Remove(); - m_SkillMod = new DefaultSkillMod( SkillName.Mining, true, m_Bonus ); - mobile.AddSkillMod( m_SkillMod ); - } - } + m_SkillMod = null; + } + else if (m_SkillMod == null && Parent is Mobile mobile) + { + m_SkillMod = new DefaultSkillMod(SkillName.Mining, true, m_Bonus); + mobile.AddSkillMod(m_SkillMod); + } + else if (m_SkillMod != null) + { + m_SkillMod.Value = m_Bonus; + } + } + } - public override void OnRemoved(IEntity parent) - { - base.OnRemoved( parent ); + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); - m_SkillMod?.Remove(); + if (m_Bonus != 0 && parent is Mobile mobile) + { + m_SkillMod?.Remove(); - m_SkillMod = null; - } + m_SkillMod = new DefaultSkillMod(SkillName.Mining, true, m_Bonus); + mobile.AddSkillMod(m_SkillMod); + } + } - public BaseGlovesOfMining( int bonus, int itemID ) : base( itemID ) - { - m_Bonus = bonus; + public override void OnRemoved(IEntity parent) + { + base.OnRemoved(parent); - Hue = CraftResources.GetHue( (CraftResource)Utility.RandomMinMax( (int)CraftResource.DullCopper, (int)CraftResource.Valorite ) ); - } + m_SkillMod?.Remove(); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + m_SkillMod = null; + } - if ( m_Bonus != 0 ) - list.Add( 1062005, m_Bonus.ToString() ); // mining bonus +~1_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public BaseGlovesOfMining( Serial serial ) : base( serial ) - { - } + if (m_Bonus != 0) + list.Add(1062005, m_Bonus.ToString()); // mining bonus +~1_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_Bonus ); - } + writer.Write(m_Bonus); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Bonus = reader.ReadInt(); - break; - } - } + switch (version) + { + case 0: + { + m_Bonus = reader.ReadInt(); + break; + } + } - if ( m_Bonus != 0 && Parent is Mobile mobile ) - { - m_SkillMod?.Remove(); + if (m_Bonus != 0 && Parent is Mobile mobile) + { + m_SkillMod?.Remove(); - m_SkillMod = new DefaultSkillMod( SkillName.Mining, true, m_Bonus ); - mobile.AddSkillMod( m_SkillMod ); - } - } - } -} + m_SkillMod = new DefaultSkillMod(SkillName.Mining, true, m_Bonus); + mobile.AddSkillMod(m_SkillMod); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/PowderOfTemperament.cs b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/PowderOfTemperament.cs index 6b645a234..962085c15 100644 --- a/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/PowderOfTemperament.cs +++ b/Scripts/Items/Special/Bulk Order Rewards/Blacksmithy/PowderOfTemperament.cs @@ -1,184 +1,192 @@ -using Server.Targeting; using Server.Network; +using Server.Targeting; namespace Server.Items { - public class PowderOfTemperament : Item, IUsesRemaining - { - private int m_UsesRemaining; + public class PowderOfTemperament : Item, IUsesRemaining + { + private int m_UsesRemaining; - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + [Constructible] + public PowderOfTemperament() : this(10) + { + } - public bool ShowUsesRemaining{ get => true; - set{} } + [Constructible] + public PowderOfTemperament(int charges) : base(4102) + { + Weight = 1.0; + Hue = 2419; + UsesRemaining = charges; + } - public override int LabelNumber => 1049082; // powder of fortifying + public PowderOfTemperament(Serial serial) : base(serial) + { + } - [Constructible] - public PowderOfTemperament() : this( 10 ) - { - } + public override int LabelNumber => 1049082; // powder of fortifying - [Constructible] - public PowderOfTemperament( int charges ) : base( 4102 ) - { - Weight = 1.0; - Hue = 2419; - UsesRemaining = charges; - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public PowderOfTemperament( Serial serial ) : base( serial ) - { - } + public bool ShowUsesRemaining + { + get => true; + set { } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - writer.Write( (int) m_UsesRemaining ); - } + writer.Write(0); + writer.Write(m_UsesRemaining); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_UsesRemaining = reader.ReadInt(); - break; - } - } - } + switch (version) + { + case 0: + { + m_UsesRemaining = reader.ReadInt(); + break; + } + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ - } + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ + } - public virtual void DisplayDurabilityTo( Mobile m ) - { - LabelToAffix( m, 1017323, AffixType.Append, ": " + m_UsesRemaining.ToString() ); // Durability - } + public virtual void DisplayDurabilityTo(Mobile m) + { + LabelToAffix(m, 1017323, AffixType.Append, ": " + m_UsesRemaining); // Durability + } - public override void OnSingleClick( Mobile from ) - { - DisplayDurabilityTo( from ); + public override void OnSingleClick(Mobile from) + { + DisplayDurabilityTo(from); - base.OnSingleClick( from ); - } + base.OnSingleClick(from); + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - from.Target = new InternalTarget( this ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + from.Target = new InternalTarget(this); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } - private class InternalTarget : Target - { - private PowderOfTemperament m_Powder; + private class InternalTarget : Target + { + private PowderOfTemperament m_Powder; - public InternalTarget( PowderOfTemperament powder ) : base( 2, false, TargetFlags.None ) - { - m_Powder = powder; - } + public InternalTarget(PowderOfTemperament powder) : base(2, false, TargetFlags.None) + { + m_Powder = powder; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Powder.Deleted || m_Powder.UsesRemaining <= 0 ) - { - from.SendLocalizedMessage( 1049086 ); // You have used up your powder of temperament. - return; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Powder.Deleted || m_Powder.UsesRemaining <= 0) + { + from.SendLocalizedMessage(1049086); // You have used up your powder of temperament. + return; + } - if ( targeted is Item item && item is IDurability wearable ) - { - if ( !wearable.CanFortify ) - { - from.SendLocalizedMessage( 1049083 ); // You cannot use the powder on that item. - return; - } + if (targeted is Item item && item is IDurability wearable) + { + if (!wearable.CanFortify) + { + from.SendLocalizedMessage(1049083); // You cannot use the powder on that item. + return; + } - if ( ( item.IsChildOf( from.Backpack ) || ( Core.ML && item.Parent == from ) ) && m_Powder.IsChildOf( from.Backpack ) ) - { - int origMaxHP = wearable.MaxHitPoints; - int origCurHP = wearable.HitPoints; + if ((item.IsChildOf(from.Backpack) || Core.ML && item.Parent == from) && + m_Powder.IsChildOf(from.Backpack)) + { + int origMaxHP = wearable.MaxHitPoints; + int origCurHP = wearable.HitPoints; - if ( origMaxHP > 0 ) - { - int initMaxHP = Core.AOS ? 255 : wearable.InitMaxHits; + if (origMaxHP > 0) + { + int initMaxHP = Core.AOS ? 255 : wearable.InitMaxHits; - wearable.UnscaleDurability(); + wearable.UnscaleDurability(); - if ( wearable.MaxHitPoints < initMaxHP ) - { - int bonus = initMaxHP - wearable.MaxHitPoints; + if (wearable.MaxHitPoints < initMaxHP) + { + int bonus = initMaxHP - wearable.MaxHitPoints; - if ( bonus > 10 ) - bonus = 10; + if (bonus > 10) + bonus = 10; - wearable.MaxHitPoints += bonus; - wearable.HitPoints += bonus; + wearable.MaxHitPoints += bonus; + wearable.HitPoints += bonus; - wearable.ScaleDurability(); + wearable.ScaleDurability(); - if ( wearable.MaxHitPoints > 255 ) wearable.MaxHitPoints = 255; - if ( wearable.HitPoints > 255 ) wearable.HitPoints = 255; + if (wearable.MaxHitPoints > 255) wearable.MaxHitPoints = 255; + if (wearable.HitPoints > 255) wearable.HitPoints = 255; - if ( wearable.MaxHitPoints > origMaxHP ) - { - from.SendLocalizedMessage( 1049084 ); // You successfully use the powder on the item. - from.PlaySound( 0x247 ); + if (wearable.MaxHitPoints > origMaxHP) + { + from.SendLocalizedMessage(1049084); // You successfully use the powder on the item. + from.PlaySound(0x247); - --m_Powder.UsesRemaining; + --m_Powder.UsesRemaining; - if ( m_Powder.UsesRemaining <= 0 ) - { - from.SendLocalizedMessage( 1049086 ); // You have used up your powder of fortifying. - m_Powder.Delete(); - } - } - else - { - wearable.MaxHitPoints = origMaxHP; - wearable.HitPoints = origCurHP; - from.SendLocalizedMessage( 1049085 ); // The item cannot be improved any further. - } - } - else - { - from.SendLocalizedMessage( 1049085 ); // The item cannot be improved any further. - wearable.ScaleDurability(); - } - } - else - { - from.SendLocalizedMessage( 1049083 ); // You cannot use the powder on that item. - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } - else - { - from.SendLocalizedMessage( 1049083 ); // You cannot use the powder on that item. - } - } - } - } -} + if (m_Powder.UsesRemaining <= 0) + { + from.SendLocalizedMessage(1049086); // You have used up your powder of fortifying. + m_Powder.Delete(); + } + } + else + { + wearable.MaxHitPoints = origMaxHP; + wearable.HitPoints = origCurHP; + from.SendLocalizedMessage(1049085); // The item cannot be improved any further. + } + } + else + { + from.SendLocalizedMessage(1049085); // The item cannot be improved any further. + wearable.ScaleDurability(); + } + } + else + { + from.SendLocalizedMessage(1049083); // You cannot use the powder on that item. + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } + else + { + from.SendLocalizedMessage(1049083); // You cannot use the powder on that item. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Community Collection/JesterHatofChuckles.cs b/Scripts/Items/Special/Community Collection/JesterHatofChuckles.cs index 2b88f9b98..9a0cfff46 100644 --- a/Scripts/Items/Special/Community Collection/JesterHatofChuckles.cs +++ b/Scripts/Items/Special/Community Collection/JesterHatofChuckles.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class JesterHatofChuckles : BaseHat, ITokunoDyable - { - public override int LabelNumber => 1073256; //Jester Hat of Chuckles - Museum of Vesper Replica 1073256 + public class JesterHatofChuckles : BaseHat, ITokunoDyable + { + [Constructible] + public JesterHatofChuckles() : this(Utility.RandomList(0x13e, 0x03, 0x172, 0x3f)) + { + } - public override int BasePhysicalResistance => 12; - public override int BaseFireResistance => 12; - public override int BaseColdResistance => 12; - public override int BasePoisonResistance => 12; - public override int BaseEnergyResistance => 12; + [Constructible] + public JesterHatofChuckles(int hue) : base(0x171C, hue) + { + Attributes.Luck = 150; + Weight = 1.0; + } - public override int InitMinHits => 100; - public override int InitMaxHits => 100; + public JesterHatofChuckles(Serial serial) : base(serial) + { + } - [Constructible] - public JesterHatofChuckles() : this( Utility.RandomList( 0x13e, 0x03, 0x172, 0x3f ) ) - { - } + public override int LabelNumber => 1073256; //Jester Hat of Chuckles - Museum of Vesper Replica 1073256 - [Constructible] - public JesterHatofChuckles( int hue ) : base( 0x171C, hue ) - { - Attributes.Luck = 150; - Weight = 1.0; - } + public override int BasePhysicalResistance => 12; + public override int BaseFireResistance => 12; + public override int BaseColdResistance => 12; + public override int BasePoisonResistance => 12; + public override int BaseEnergyResistance => 12; - public JesterHatofChuckles( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 100; + public override int InitMaxHits => 100; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/AwesomeDisturbingPortrait.cs b/Scripts/Items/Special/Evil Home Decor Collection/AwesomeDisturbingPortrait.cs index 44c546a87..1306ee92e 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/AwesomeDisturbingPortrait.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/AwesomeDisturbingPortrait.cs @@ -3,185 +3,188 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A5D, 0x2A61 )] - public class AwesomeDisturbingPortraitComponent : AddonComponent - { - public override int LabelNumber => 1074479; // Disturbing portrait - public bool FacingSouth => ItemID < 0x2A61; + [Flippable(0x2A5D, 0x2A61)] + public class AwesomeDisturbingPortraitComponent : AddonComponent + { + private InternalTimer m_Timer; - private InternalTimer m_Timer; + public AwesomeDisturbingPortraitComponent() : base(0x2A5D) + { + m_Timer = new InternalTimer(this, TimeSpan.FromSeconds(1)); + m_Timer.Start(); + } - public AwesomeDisturbingPortraitComponent() : base( 0x2A5D ) - { - m_Timer = new InternalTimer( this, TimeSpan.FromSeconds( 1 ) ); - m_Timer.Start(); - } + public AwesomeDisturbingPortraitComponent(Serial serial) : base(serial) + { + } - public AwesomeDisturbingPortraitComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074479; // Disturbing portrait + public bool FacingSouth => ItemID < 0x2A61; - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - { - int hours; - int minutes; + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + { + int hours; + int minutes; - Clock.GetTime( Map, X, Y, out hours, out minutes ); + Clock.GetTime(Map, X, Y, out hours, out minutes); - if ( hours < 4 || hours > 20 ) - Effects.PlaySound( Location, Map, 0x569 ); + if (hours < 4 || hours > 20) + Effects.PlaySound(Location, Map, 0x569); - UpdateImage(); - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + UpdateImage(); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); - } + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Timer = new InternalTimer( this, TimeSpan.Zero ); - m_Timer.Start(); - } + m_Timer = new InternalTimer(this, TimeSpan.Zero); + m_Timer.Start(); + } - private void UpdateImage() - { - int hours; - int minutes; + private void UpdateImage() + { + int hours; + int minutes; - Clock.GetTime( Map, X, Y, out hours, out minutes ); + Clock.GetTime(Map, X, Y, out hours, out minutes); - if ( FacingSouth ) - { - if ( hours < 4 ) - ItemID = 0x2A60; - else if ( hours < 6 ) - ItemID = 0x2A5F; - else if ( hours < 8 ) - ItemID = 0x2A5E; - else if ( hours < 16 ) - ItemID = 0x2A5D; - else if ( hours < 18 ) - ItemID = 0x2A5E; - else if ( hours < 20 ) - ItemID = 0x2A5F; - else - ItemID = 0x2A60; - } - else - { - if ( hours < 4 ) - ItemID = 0x2A64; - else if ( hours < 6 ) - ItemID = 0x2A63; - else if ( hours < 8 ) - ItemID = 0x2A62; - else if ( hours < 16 ) - ItemID = 0x2A61; - else if ( hours < 18 ) - ItemID = 0x2A62; - else if ( hours < 20 ) - ItemID = 0x2A63; - else - ItemID = 0x2A64; - } - } + if (FacingSouth) + { + if (hours < 4) + ItemID = 0x2A60; + else if (hours < 6) + ItemID = 0x2A5F; + else if (hours < 8) + ItemID = 0x2A5E; + else if (hours < 16) + ItemID = 0x2A5D; + else if (hours < 18) + ItemID = 0x2A5E; + else if (hours < 20) + ItemID = 0x2A5F; + else + ItemID = 0x2A60; + } + else + { + if (hours < 4) + ItemID = 0x2A64; + else if (hours < 6) + ItemID = 0x2A63; + else if (hours < 8) + ItemID = 0x2A62; + else if (hours < 16) + ItemID = 0x2A61; + else if (hours < 18) + ItemID = 0x2A62; + else if (hours < 20) + ItemID = 0x2A63; + else + ItemID = 0x2A64; + } + } - private class InternalTimer : Timer - { - private AwesomeDisturbingPortraitComponent m_Component; + private class InternalTimer : Timer + { + private AwesomeDisturbingPortraitComponent m_Component; - public InternalTimer( AwesomeDisturbingPortraitComponent c, TimeSpan delay ) : base( delay, TimeSpan.FromMinutes( 10 ) ) - { - m_Component = c; + public InternalTimer(AwesomeDisturbingPortraitComponent c, TimeSpan delay) : base(delay, + TimeSpan.FromMinutes(10)) + { + m_Component = c; - Priority = TimerPriority.OneMinute; - } + Priority = TimerPriority.OneMinute; + } - protected override void OnTick() - { - if ( m_Component != null && !m_Component.Deleted ) - m_Component.UpdateImage(); - } - } - } + protected override void OnTick() + { + if (m_Component != null && !m_Component.Deleted) + m_Component.UpdateImage(); + } + } + } - public class AwesomeDisturbingPortraitAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AwesomeDisturbingPortraitDeed(); + public class AwesomeDisturbingPortraitAddon : BaseAddon + { + [Constructible] + public AwesomeDisturbingPortraitAddon() + { + AddComponent(new AwesomeDisturbingPortraitComponent(), 0, 0, 0); + } - [Constructible] - public AwesomeDisturbingPortraitAddon() - { - AddComponent( new AwesomeDisturbingPortraitComponent(), 0, 0, 0 ); - } + public AwesomeDisturbingPortraitAddon(Serial serial) : base(serial) + { + } - public AwesomeDisturbingPortraitAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AwesomeDisturbingPortraitDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class AwesomeDisturbingPortraitDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AwesomeDisturbingPortraitAddon(); - public override int LabelNumber => 1074479; // Disturbing portrait + public class AwesomeDisturbingPortraitDeed : BaseAddonDeed + { + [Constructible] + public AwesomeDisturbingPortraitDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public AwesomeDisturbingPortraitDeed() - { - LootType = LootType.Blessed; - } + public AwesomeDisturbingPortraitDeed(Serial serial) : base(serial) + { + } - public AwesomeDisturbingPortraitDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AwesomeDisturbingPortraitAddon(); + public override int LabelNumber => 1074479; // Disturbing portrait - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/BedOfNails.cs b/Scripts/Items/Special/Evil Home Decor Collection/BedOfNails.cs index bfce25415..ed9599e3e 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/BedOfNails.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/BedOfNails.cs @@ -2,192 +2,190 @@ using System; namespace Server.Items { - public class BedOfNailsComponent : AddonComponent - { - public override int LabelNumber => 1074801; // Bed of Nails + public class BedOfNailsComponent : AddonComponent + { + public BedOfNailsComponent(int itemID) + : base(itemID) + { + } - public BedOfNailsComponent( int itemID ) - : base( itemID ) - { - } + public BedOfNailsComponent(Serial serial) + : base(serial) + { + } - public BedOfNailsComponent( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1074801; // Bed of Nails - public override bool OnMoveOver( Mobile m ) - { - bool allow = base.OnMoveOver( m ); + public override bool OnMoveOver(Mobile m) + { + bool allow = base.OnMoveOver(m); - if ( allow && Addon is BedOfNailsAddon addon ) - addon.OnMoveOver( m ); + if (allow && Addon is BedOfNailsAddon addon) + addon.OnMoveOver(m); - return allow; - } + return allow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [FlippableAddon( Direction.South, Direction.East )] - public class BedOfNailsAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BedOfNailsDeed(); + [FlippableAddon(Direction.South, Direction.East)] + public class BedOfNailsAddon : BaseAddon + { + private InternalTimer m_Timer; - private InternalTimer m_Timer; + [Constructible] + public BedOfNailsAddon() + { + Direction = Direction.South; - [Constructible] - public BedOfNailsAddon() - { - Direction = Direction.South; + AddComponent(new BedOfNailsComponent(0x2A81), 0, 0, 0); + AddComponent(new BedOfNailsComponent(0x2A82), 0, -1, 0); + } - AddComponent( new BedOfNailsComponent( 0x2A81 ), 0, 0, 0 ); - AddComponent( new BedOfNailsComponent( 0x2A82 ), 0, -1, 0 ); - } + public BedOfNailsAddon(Serial serial) + : base(serial) + { + } - public BedOfNailsAddon( Serial serial ) - : base( serial ) - { - } + public override BaseAddonDeed Deed => new BedOfNailsDeed(); - public override bool OnMoveOver( Mobile m ) - { - if ( m.Alive && ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) ) - { - if ( m.Player ) - { - if ( m.Female ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x53B, 0x53D ) ); - else - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x53E, 0x540 ) ); - } + public override bool OnMoveOver(Mobile m) + { + if (m.Alive && (m.AccessLevel == AccessLevel.Player || !m.Hidden)) + { + if (m.Player) + { + if (m.Female) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x53B, 0x53D)); + else + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x53E, 0x540)); + } - if ( m_Timer == null || !m_Timer.Running ) - ( m_Timer = new InternalTimer( m ) ).Start(); - } + if (m_Timer == null || !m_Timer.Running) + (m_Timer = new InternalTimer(m)).Start(); + } - return true; - } + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - public virtual void Flip( Mobile from, Direction direction ) - { - switch( direction ) - { - case Direction.East: - AddComponent( new BedOfNailsComponent( 0x2A89 ), 0, 0, 0 ); - AddComponent( new BedOfNailsComponent( 0x2A8A ), -1, 0, 0 ); - break; - case Direction.South: - AddComponent( new BedOfNailsComponent( 0x2A81 ), 0, 0, 0 ); - AddComponent( new BedOfNailsComponent( 0x2A82 ), 0, -1, 0 ); - break; - } - } + public virtual void Flip(Mobile from, Direction direction) + { + switch (direction) + { + case Direction.East: + AddComponent(new BedOfNailsComponent(0x2A89), 0, 0, 0); + AddComponent(new BedOfNailsComponent(0x2A8A), -1, 0, 0); + break; + case Direction.South: + AddComponent(new BedOfNailsComponent(0x2A81), 0, 0, 0); + AddComponent(new BedOfNailsComponent(0x2A82), 0, -1, 0); + break; + } + } - private class InternalTimer : Timer - { - private Mobile m_Mobile; - private Point3D m_Location; + private class InternalTimer : Timer + { + private Point3D m_Location; + private Mobile m_Mobile; - public InternalTimer( Mobile m ) - : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1 ), 5 ) - { - m_Mobile = m; - m_Location = Point3D.Zero; - } + public InternalTimer(Mobile m) + : base(TimeSpan.Zero, TimeSpan.FromSeconds(1), 5) + { + m_Mobile = m; + m_Location = Point3D.Zero; + } - protected override void OnTick() - { - if ( m_Mobile?.Map == null || m_Mobile.Deleted || !m_Mobile.Alive || m_Mobile.Map == Map.Internal ) - { - Stop(); - } - else - { - if ( m_Location != m_Mobile.Location ) - { - int amount = Utility.RandomMinMax( 0, 7 ); + protected override void OnTick() + { + if (m_Mobile?.Map == null || m_Mobile.Deleted || !m_Mobile.Alive || m_Mobile.Map == Map.Internal) + { + Stop(); + } + else + { + if (m_Location != m_Mobile.Location) + { + int amount = Utility.RandomMinMax(0, 7); - for( int i = 0; i < amount; i++ ) - { - int x = m_Mobile.X + Utility.RandomMinMax( -1, 1 ); - int y = m_Mobile.Y + Utility.RandomMinMax( -1, 1 ); - int z = m_Mobile.Z; + for (int i = 0; i < amount; i++) + { + int x = m_Mobile.X + Utility.RandomMinMax(-1, 1); + int y = m_Mobile.Y + Utility.RandomMinMax(-1, 1); + int z = m_Mobile.Z; - if ( !m_Mobile.Map.CanFit( x, y, z, 1, false, false, true ) ) - { - z = m_Mobile.Map.GetAverageZ( x, y ); + if (!m_Mobile.Map.CanFit(x, y, z, 1, false, false, true)) + { + z = m_Mobile.Map.GetAverageZ(x, y); - if ( !m_Mobile.Map.CanFit( x, y, z, 1, false, false, true ) ) - { - continue; - } - } + if (!m_Mobile.Map.CanFit(x, y, z, 1, false, false, true)) continue; + } - Blood blood = new Blood( Utility.RandomMinMax( 0x122C, 0x122F ) ); - blood.MoveToWorld( new Point3D( x, y, z ), m_Mobile.Map ); - } - m_Location = m_Mobile.Location; - } - } - } - } - } + Blood blood = new Blood(Utility.RandomMinMax(0x122C, 0x122F)); + blood.MoveToWorld(new Point3D(x, y, z), m_Mobile.Map); + } - public class BedOfNailsDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BedOfNailsAddon(); - public override int LabelNumber => 1074801; // Bed of Nails + m_Location = m_Mobile.Location; + } + } + } + } + } - [Constructible] - public BedOfNailsDeed() - { - LootType = LootType.Blessed; - } + public class BedOfNailsDeed : BaseAddonDeed + { + [Constructible] + public BedOfNailsDeed() + { + LootType = LootType.Blessed; + } - public BedOfNailsDeed( Serial serial ) - : base( serial ) - { - } + public BedOfNailsDeed(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override BaseAddon Addon => new BedOfNailsAddon(); + public override int LabelNumber => 1074801; // Bed of Nails - writer.WriteEncodedInt( 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/BoneCouch.cs b/Scripts/Items/Special/Evil Home Decor Collection/BoneCouch.cs index 42ae060a3..cb071cd1b 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/BoneCouch.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/BoneCouch.cs @@ -1,117 +1,117 @@ namespace Server.Items { - public class BoneCouchComponent : AddonComponent - { - public override int LabelNumber => 1074477; // Bone couch + public class BoneCouchComponent : AddonComponent + { + public BoneCouchComponent(int itemID) : base(itemID) + { + } - public BoneCouchComponent( int itemID ) : base( itemID ) - { - } + public BoneCouchComponent(Serial serial) : base(serial) + { + } - public BoneCouchComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074477; // Bone couch - public override bool OnMoveOver( Mobile m ) - { - bool allow = base.OnMoveOver( m ); + public override bool OnMoveOver(Mobile m) + { + bool allow = base.OnMoveOver(m); - if ( allow && m.Alive && m.Player && ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x547, 0x54A ) ); + if (allow && m.Alive && m.Player && (m.AccessLevel == AccessLevel.Player || !m.Hidden)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x547, 0x54A)); - return allow; - } + return allow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [FlippableAddon( Direction.South, Direction.East )] - public class BoneCouchAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BoneCouchDeed(); + [FlippableAddon(Direction.South, Direction.East)] + public class BoneCouchAddon : BaseAddon + { + [Constructible] + public BoneCouchAddon() + { + Direction = Direction.South; - [Constructible] - public BoneCouchAddon() - { - Direction = Direction.South; + AddComponent(new BoneCouchComponent(0x2A5A), 0, 0, 0); + AddComponent(new BoneCouchComponent(0x2A5B), -1, 0, 0); + } - AddComponent( new BoneCouchComponent( 0x2A5A ), 0, 0, 0 ); - AddComponent( new BoneCouchComponent( 0x2A5B ), -1, 0, 0 ); - } + public BoneCouchAddon(Serial serial) : base(serial) + { + } - public BoneCouchAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BoneCouchDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - public virtual void Flip( Mobile from, Direction direction ) - { - switch ( direction ) - { - case Direction.East: - AddComponent( new BoneCouchComponent( 0x2A80 ), 0, 0, 0 ); - AddComponent( new BoneCouchComponent( 0x2A7F ), 0, 1, 0 ); - break; - case Direction.South: - AddComponent( new BoneCouchComponent( 0x2A5A ), 0, 0, 0 ); - AddComponent( new BoneCouchComponent( 0x2A5B ), -1, 0, 0 ); - break; - } - } - } + public virtual void Flip(Mobile from, Direction direction) + { + switch (direction) + { + case Direction.East: + AddComponent(new BoneCouchComponent(0x2A80), 0, 0, 0); + AddComponent(new BoneCouchComponent(0x2A7F), 0, 1, 0); + break; + case Direction.South: + AddComponent(new BoneCouchComponent(0x2A5A), 0, 0, 0); + AddComponent(new BoneCouchComponent(0x2A5B), -1, 0, 0); + break; + } + } + } - public class BoneCouchDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BoneCouchAddon(); - public override int LabelNumber => 1074477; // Bone couch + public class BoneCouchDeed : BaseAddonDeed + { + [Constructible] + public BoneCouchDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BoneCouchDeed() - { - LootType = LootType.Blessed; - } + public BoneCouchDeed(Serial serial) : base(serial) + { + } - public BoneCouchDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BoneCouchAddon(); + public override int LabelNumber => 1074477; // Bone couch - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/BoneTable.cs b/Scripts/Items/Special/Evil Home Decor Collection/BoneTable.cs index 7f58f2a00..ae79185ea 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/BoneTable.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/BoneTable.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class BoneTableAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BoneTableDeed(); + public class BoneTableAddon : BaseAddon + { + [Constructible] + public BoneTableAddon() + { + AddComponent(new LocalizedAddonComponent(0x2A5C, 1074478), 0, 0, 0); + } - [Constructible] - public BoneTableAddon() - { - AddComponent( new LocalizedAddonComponent( 0x2A5C, 1074478 ), 0, 0, 0 ); - } + public BoneTableAddon(Serial serial) : base(serial) + { + } - public BoneTableAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BoneTableDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BoneTableDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BoneTableAddon(); - public override int LabelNumber => 1074478; // Bone table + public class BoneTableDeed : BaseAddonDeed + { + [Constructible] + public BoneTableDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BoneTableDeed() - { - LootType = LootType.Blessed; - } + public BoneTableDeed(Serial serial) : base(serial) + { + } - public BoneTableDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BoneTableAddon(); + public override int LabelNumber => 1074478; // Bone table - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/BoneThrone.cs b/Scripts/Items/Special/Evil Home Decor Collection/BoneThrone.cs index 2221fc070..b17d23ef6 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/BoneThrone.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/BoneThrone.cs @@ -1,99 +1,99 @@ namespace Server.Items { - [Flippable( 0x2A58, 0x2A59 )] - public class BoneThroneComponent : AddonComponent - { - public override int LabelNumber => 1074476; // Bone throne + [Flippable(0x2A58, 0x2A59)] + public class BoneThroneComponent : AddonComponent + { + public BoneThroneComponent() : base(0x2A58) + { + } - public BoneThroneComponent() : base( 0x2A58 ) - { - } + public BoneThroneComponent(Serial serial) : base(serial) + { + } - public BoneThroneComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074476; // Bone throne - public override bool OnMoveOver( Mobile m ) - { - bool allow = base.OnMoveOver( m ); + public override bool OnMoveOver(Mobile m) + { + bool allow = base.OnMoveOver(m); - if ( allow && m.Alive && m.Player && ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x54B, 0x54D ) ); + if (allow && m.Alive && m.Player && (m.AccessLevel == AccessLevel.Player || !m.Hidden)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x54B, 0x54D)); - return allow; - } + return allow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BoneThroneAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BoneThroneDeed(); + public class BoneThroneAddon : BaseAddon + { + [Constructible] + public BoneThroneAddon() + { + AddComponent(new BoneThroneComponent(), 0, 0, 0); + } - [Constructible] - public BoneThroneAddon() - { - AddComponent( new BoneThroneComponent(), 0, 0, 0 ); - } + public BoneThroneAddon(Serial serial) : base(serial) + { + } - public BoneThroneAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BoneThroneDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BoneThroneDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BoneThroneAddon(); - public override int LabelNumber => 1074476; // Bone throne + public class BoneThroneDeed : BaseAddonDeed + { + [Constructible] + public BoneThroneDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BoneThroneDeed() - { - LootType = LootType.Blessed; - } + public BoneThroneDeed(Serial serial) : base(serial) + { + } - public BoneThroneDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BoneThroneAddon(); + public override int LabelNumber => 1074476; // Bone throne - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/CreepyPortrait.cs b/Scripts/Items/Special/Evil Home Decor Collection/CreepyPortrait.cs index 8a8879ff3..5820c5070 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/CreepyPortrait.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/CreepyPortrait.cs @@ -3,135 +3,135 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A69, 0x2A6D )] - public class CreepyPortraitComponent : AddonComponent - { - public override int LabelNumber => 1074481; // Creepy portrait - public override bool HandlesOnMovement => true; + [Flippable(0x2A69, 0x2A6D)] + public class CreepyPortraitComponent : AddonComponent + { + public CreepyPortraitComponent() : base(0x2A69) + { + } - public CreepyPortraitComponent() : base( 0x2A69 ) - { - } + public CreepyPortraitComponent(Serial serial) : base(serial) + { + } - public CreepyPortraitComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074481; // Creepy portrait + public override bool HandlesOnMovement => true; - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x565, 0x566 ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x565, 0x566)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void OnMovement( Mobile m, Point3D old ) - { - if ( m.Alive && m.Player && ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) ) - { - if ( !Utility.InRange( old, Location, 2 ) && Utility.InRange( m.Location, Location, 2 ) ) - { - if ( ItemID == 0x2A69 || ItemID == 0x2A6D ) - { - Up(); - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ), 2, Up ); - } - } - else if ( Utility.InRange( old, Location, 2 ) && !Utility.InRange( m.Location, Location, 2 ) ) - { - if ( ItemID == 0x2A6C || ItemID == 0x2A70 ) - { - Down(); - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ), 2, Down ); - } - } - } - } + public override void OnMovement(Mobile m, Point3D old) + { + if (m.Alive && m.Player && (m.AccessLevel == AccessLevel.Player || !m.Hidden)) + { + if (!Utility.InRange(old, Location, 2) && Utility.InRange(m.Location, Location, 2)) + { + if (ItemID == 0x2A69 || ItemID == 0x2A6D) + { + Up(); + Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5), 2, Up); + } + } + else if (Utility.InRange(old, Location, 2) && !Utility.InRange(m.Location, Location, 2)) + { + if (ItemID == 0x2A6C || ItemID == 0x2A70) + { + Down(); + Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5), 2, Down); + } + } + } + } - private void Up() - { - ItemID += 1; - } + private void Up() + { + ItemID += 1; + } - private void Down() - { - ItemID -= 1; - } + private void Down() + { + ItemID -= 1; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version - } + writer.WriteEncodedInt(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if ( version == 0 && ItemID != 0x2A69 && ItemID != 0x2A6D ) - ItemID = 0x2A69; - } - } + if (version == 0 && ItemID != 0x2A69 && ItemID != 0x2A6D) + ItemID = 0x2A69; + } + } - public class CreepyPortraitAddon : BaseAddon - { - public override BaseAddonDeed Deed => new CreepyPortraitDeed(); + public class CreepyPortraitAddon : BaseAddon + { + [Constructible] + public CreepyPortraitAddon() + { + AddComponent(new CreepyPortraitComponent(), 0, 0, 0); + } - [Constructible] - public CreepyPortraitAddon() - { - AddComponent( new CreepyPortraitComponent(), 0, 0, 0 ); - } + public CreepyPortraitAddon(Serial serial) : base(serial) + { + } - public CreepyPortraitAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new CreepyPortraitDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class CreepyPortraitDeed : BaseAddonDeed - { - public override BaseAddon Addon => new CreepyPortraitAddon(); - public override int LabelNumber => 1074481; // Creepy portrait + public class CreepyPortraitDeed : BaseAddonDeed + { + [Constructible] + public CreepyPortraitDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public CreepyPortraitDeed() - { - LootType = LootType.Blessed; - } + public CreepyPortraitDeed(Serial serial) : base(serial) + { + } - public CreepyPortraitDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new CreepyPortraitAddon(); + public override int LabelNumber => 1074481; // Creepy portrait - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/DisturbingPortrait.cs b/Scripts/Items/Special/Evil Home Decor Collection/DisturbingPortrait.cs index b0457e99b..4789560f0 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/DisturbingPortrait.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/DisturbingPortrait.cs @@ -3,119 +3,119 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A5D, 0x2A61 )] - public class DisturbingPortraitComponent : AddonComponent - { - public override int LabelNumber => 1074479; // Disturbing portrait + [Flippable(0x2A5D, 0x2A61)] + public class DisturbingPortraitComponent : AddonComponent + { + private Timer m_Timer; - private Timer m_Timer; + public DisturbingPortraitComponent() : base(0x2A5D) + { + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), TimeSpan.FromMinutes(3), Change); + } - public DisturbingPortraitComponent() : base( 0x2A5D ) - { - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), TimeSpan.FromMinutes( 3 ), Change ); - } + public DisturbingPortraitComponent(Serial serial) : base(serial) + { + } - public DisturbingPortraitComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074479; // Disturbing portrait - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x567, 0x568 ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x567, 0x568)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); - } + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), TimeSpan.FromMinutes( 3 ), Change ); - } + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), TimeSpan.FromMinutes(3), Change); + } - private void Change() - { - if ( ItemID < 0x2A61 ) - ItemID = Utility.RandomMinMax( 0x2A5D, 0x2A60 ); - else - ItemID = Utility.RandomMinMax( 0x2A61, 0x2A64 ); - } - } + private void Change() + { + if (ItemID < 0x2A61) + ItemID = Utility.RandomMinMax(0x2A5D, 0x2A60); + else + ItemID = Utility.RandomMinMax(0x2A61, 0x2A64); + } + } - public class DisturbingPortraitAddon : BaseAddon - { - public override BaseAddonDeed Deed => new DisturbingPortraitDeed(); + public class DisturbingPortraitAddon : BaseAddon + { + [Constructible] + public DisturbingPortraitAddon() + { + AddComponent(new DisturbingPortraitComponent(), 0, 0, 0); + } - [Constructible] - public DisturbingPortraitAddon() - { - AddComponent( new DisturbingPortraitComponent(), 0, 0, 0 ); - } + public DisturbingPortraitAddon(Serial serial) : base(serial) + { + } - public DisturbingPortraitAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new DisturbingPortraitDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class DisturbingPortraitDeed : BaseAddonDeed - { - public override BaseAddon Addon => new DisturbingPortraitAddon(); - public override int LabelNumber => 1074479; // Disturbing portrait + public class DisturbingPortraitDeed : BaseAddonDeed + { + [Constructible] + public DisturbingPortraitDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public DisturbingPortraitDeed() - { - LootType = LootType.Blessed; - } + public DisturbingPortraitDeed(Serial serial) : base(serial) + { + } - public DisturbingPortraitDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new DisturbingPortraitAddon(); + public override int LabelNumber => 1074479; // Disturbing portrait - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/HauntedMirror.cs b/Scripts/Items/Special/Evil Home Decor Collection/HauntedMirror.cs index 520bf681a..f595fd7d3 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/HauntedMirror.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/HauntedMirror.cs @@ -1,112 +1,112 @@ namespace Server.Items { - [Flippable( 0x2A7B, 0x2A7D )] - public class HaunterMirrorComponent : AddonComponent - { - public override int LabelNumber => 1074800; // Haunted Mirror - public override bool HandlesOnMovement => true; + [Flippable(0x2A7B, 0x2A7D)] + public class HaunterMirrorComponent : AddonComponent + { + public HaunterMirrorComponent() : base(0x2A7B) + { + } - public HaunterMirrorComponent() : base( 0x2A7B ) - { - } + public HaunterMirrorComponent(Serial serial) : base(serial) + { + } - public HaunterMirrorComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074800; // Haunted Mirror + public override bool HandlesOnMovement => true; - public override void OnMovement( Mobile m, Point3D old ) - { - base.OnMovement( m, old ); + public override void OnMovement(Mobile m, Point3D old) + { + base.OnMovement(m, old); - if ( m.Alive && m.Player && ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) ) - { - if ( !Utility.InRange( old, Location, 2 ) && Utility.InRange( m.Location, Location, 2 ) ) - { - if ( ItemID == 0x2A7B || ItemID == 0x2A7D ) - { - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x551, 0x553 ) ); - ItemID += 1; - } - } - else if ( Utility.InRange( old, Location, 2 ) && !Utility.InRange( m.Location, Location, 2 ) ) - { - if ( ItemID == 0x2A7C || ItemID == 0x2A7E ) - ItemID -= 1; - } - } - } + if (m.Alive && m.Player && (m.AccessLevel == AccessLevel.Player || !m.Hidden)) + { + if (!Utility.InRange(old, Location, 2) && Utility.InRange(m.Location, Location, 2)) + { + if (ItemID == 0x2A7B || ItemID == 0x2A7D) + { + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x551, 0x553)); + ItemID += 1; + } + } + else if (Utility.InRange(old, Location, 2) && !Utility.InRange(m.Location, Location, 2)) + { + if (ItemID == 0x2A7C || ItemID == 0x2A7E) + ItemID -= 1; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class HaunterMirrorAddon : BaseAddon - { - public override BaseAddonDeed Deed => new HaunterMirrorDeed(); + public class HaunterMirrorAddon : BaseAddon + { + [Constructible] + public HaunterMirrorAddon() + { + AddComponent(new HaunterMirrorComponent(), 0, 0, 0); + } - [Constructible] - public HaunterMirrorAddon() - { - AddComponent( new HaunterMirrorComponent(), 0, 0, 0 ); - } + public HaunterMirrorAddon(Serial serial) : base(serial) + { + } - public HaunterMirrorAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new HaunterMirrorDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class HaunterMirrorDeed : BaseAddonDeed - { - public override BaseAddon Addon => new HaunterMirrorAddon(); - public override int LabelNumber => 1074800; // Haunted Mirror + public class HaunterMirrorDeed : BaseAddonDeed + { + [Constructible] + public HaunterMirrorDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public HaunterMirrorDeed() - { - LootType = LootType.Blessed; - } + public HaunterMirrorDeed(Serial serial) : base(serial) + { + } - public HaunterMirrorDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new HaunterMirrorAddon(); + public override int LabelNumber => 1074800; // Haunted Mirror - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieBlue.cs b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieBlue.cs index 19b9f0f33..b049148be 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieBlue.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieBlue.cs @@ -2,97 +2,97 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A75, 0x2A76 )] - public class MountedPixieBlueComponent : AddonComponent - { - public override int LabelNumber => 1074482; // Mounted pixie + [Flippable(0x2A75, 0x2A76)] + public class MountedPixieBlueComponent : AddonComponent + { + public MountedPixieBlueComponent() : base(0x2A75) + { + } - public MountedPixieBlueComponent() : base( 0x2A75 ) - { - } + public MountedPixieBlueComponent(Serial serial) : base(serial) + { + } - public MountedPixieBlueComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074482; // Mounted pixie - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x55C, 0x55E ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x55C, 0x55E)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieBlueAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MountedPixieBlueDeed(); + public class MountedPixieBlueAddon : BaseAddon + { + public MountedPixieBlueAddon() + { + AddComponent(new MountedPixieBlueComponent(), 0, 0, 0); + } - public MountedPixieBlueAddon() - { - AddComponent( new MountedPixieBlueComponent(), 0, 0, 0 ); - } + public MountedPixieBlueAddon(Serial serial) : base(serial) + { + } - public MountedPixieBlueAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MountedPixieBlueDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieBlueDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MountedPixieBlueAddon(); - public override int LabelNumber => 1074482; // Mounted pixie + public class MountedPixieBlueDeed : BaseAddonDeed + { + [Constructible] + public MountedPixieBlueDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public MountedPixieBlueDeed() - { - LootType = LootType.Blessed; - } + public MountedPixieBlueDeed(Serial serial) : base(serial) + { + } - public MountedPixieBlueDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MountedPixieBlueAddon(); + public override int LabelNumber => 1074482; // Mounted pixie - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieGreen.cs b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieGreen.cs index b2ea5bc55..649d0c46d 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieGreen.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieGreen.cs @@ -2,97 +2,97 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A71, 0x2A72 )] - public class MountedPixieGreenComponent : AddonComponent - { - public override int LabelNumber => 1074482; // Mounted pixie + [Flippable(0x2A71, 0x2A72)] + public class MountedPixieGreenComponent : AddonComponent + { + public MountedPixieGreenComponent() : base(0x2A71) + { + } - public MountedPixieGreenComponent() : base( 0x2A71 ) - { - } + public MountedPixieGreenComponent(Serial serial) : base(serial) + { + } - public MountedPixieGreenComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074482; // Mounted pixie - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x554, 0x557 ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x554, 0x557)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieGreenAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MountedPixieGreenDeed(); + public class MountedPixieGreenAddon : BaseAddon + { + public MountedPixieGreenAddon() + { + AddComponent(new MountedPixieGreenComponent(), 0, 0, 0); + } - public MountedPixieGreenAddon() - { - AddComponent( new MountedPixieGreenComponent(), 0, 0, 0 ); - } + public MountedPixieGreenAddon(Serial serial) : base(serial) + { + } - public MountedPixieGreenAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MountedPixieGreenDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieGreenDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MountedPixieGreenAddon(); - public override int LabelNumber => 1074482; // Mounted pixie + public class MountedPixieGreenDeed : BaseAddonDeed + { + [Constructible] + public MountedPixieGreenDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public MountedPixieGreenDeed() - { - LootType = LootType.Blessed; - } + public MountedPixieGreenDeed(Serial serial) : base(serial) + { + } - public MountedPixieGreenDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MountedPixieGreenAddon(); + public override int LabelNumber => 1074482; // Mounted pixie - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieLime.cs b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieLime.cs index b355f95c9..3bb190f72 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieLime.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieLime.cs @@ -2,97 +2,97 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A77, 0x2A78 )] - public class MountedPixieLimeComponent : AddonComponent - { - public override int LabelNumber => 1074482; // Mounted pixie + [Flippable(0x2A77, 0x2A78)] + public class MountedPixieLimeComponent : AddonComponent + { + public MountedPixieLimeComponent() : base(0x2A77) + { + } - public MountedPixieLimeComponent() : base( 0x2A77 ) - { - } + public MountedPixieLimeComponent(Serial serial) : base(serial) + { + } - public MountedPixieLimeComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074482; // Mounted pixie - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x55F, 0x561 ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x55F, 0x561)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieLimeAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MountedPixieLimeDeed(); + public class MountedPixieLimeAddon : BaseAddon + { + public MountedPixieLimeAddon() + { + AddComponent(new MountedPixieLimeComponent(), 0, 0, 0); + } - public MountedPixieLimeAddon() - { - AddComponent( new MountedPixieLimeComponent(), 0, 0, 0 ); - } + public MountedPixieLimeAddon(Serial serial) : base(serial) + { + } - public MountedPixieLimeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MountedPixieLimeDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieLimeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MountedPixieLimeAddon(); - public override int LabelNumber => 1074482; // Mounted pixie + public class MountedPixieLimeDeed : BaseAddonDeed + { + [Constructible] + public MountedPixieLimeDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public MountedPixieLimeDeed() - { - LootType = LootType.Blessed; - } + public MountedPixieLimeDeed(Serial serial) : base(serial) + { + } - public MountedPixieLimeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MountedPixieLimeAddon(); + public override int LabelNumber => 1074482; // Mounted pixie - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieOrange.cs b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieOrange.cs index f940ef7d3..c91e44cdd 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieOrange.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieOrange.cs @@ -2,97 +2,97 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A73, 0x2A74 )] - public class MountedPixieOrangeComponent : AddonComponent - { - public override int LabelNumber => 1074482; // Mounted pixie + [Flippable(0x2A73, 0x2A74)] + public class MountedPixieOrangeComponent : AddonComponent + { + public MountedPixieOrangeComponent() : base(0x2A73) + { + } - public MountedPixieOrangeComponent() : base( 0x2A73 ) - { - } + public MountedPixieOrangeComponent(Serial serial) : base(serial) + { + } - public MountedPixieOrangeComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074482; // Mounted pixie - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x558, 0x55B ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x558, 0x55B)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieOrangeAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MountedPixieOrangeDeed(); + public class MountedPixieOrangeAddon : BaseAddon + { + public MountedPixieOrangeAddon() + { + AddComponent(new MountedPixieOrangeComponent(), 0, 0, 0); + } - public MountedPixieOrangeAddon() - { - AddComponent( new MountedPixieOrangeComponent(), 0, 0, 0 ); - } + public MountedPixieOrangeAddon(Serial serial) : base(serial) + { + } - public MountedPixieOrangeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MountedPixieOrangeDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieOrangeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MountedPixieOrangeAddon(); - public override int LabelNumber => 1074482; // Mounted pixie + public class MountedPixieOrangeDeed : BaseAddonDeed + { + [Constructible] + public MountedPixieOrangeDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public MountedPixieOrangeDeed() - { - LootType = LootType.Blessed; - } + public MountedPixieOrangeDeed(Serial serial) : base(serial) + { + } - public MountedPixieOrangeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MountedPixieOrangeAddon(); + public override int LabelNumber => 1074482; // Mounted pixie - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieWhite.cs b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieWhite.cs index 51469b4ca..30a0d2db3 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieWhite.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/MountedPixieWhite.cs @@ -2,97 +2,97 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A79, 0x2A7A )] - public class MountedPixieWhiteComponent : AddonComponent - { - public override int LabelNumber => 1074482; // Mounted pixie + [Flippable(0x2A79, 0x2A7A)] + public class MountedPixieWhiteComponent : AddonComponent + { + public MountedPixieWhiteComponent() : base(0x2A79) + { + } - public MountedPixieWhiteComponent() : base( 0x2A79 ) - { - } + public MountedPixieWhiteComponent(Serial serial) : base(serial) + { + } - public MountedPixieWhiteComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074482; // Mounted pixie - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x562, 0x564 ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x562, 0x564)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieWhiteAddon : BaseAddon - { - public override BaseAddonDeed Deed => new MountedPixieWhiteDeed(); + public class MountedPixieWhiteAddon : BaseAddon + { + public MountedPixieWhiteAddon() + { + AddComponent(new MountedPixieWhiteComponent(), 0, 0, 0); + } - public MountedPixieWhiteAddon() - { - AddComponent( new MountedPixieWhiteComponent(), 0, 0, 0 ); - } + public MountedPixieWhiteAddon(Serial serial) : base(serial) + { + } - public MountedPixieWhiteAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new MountedPixieWhiteDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class MountedPixieWhiteDeed : BaseAddonDeed - { - public override BaseAddon Addon => new MountedPixieWhiteAddon(); - public override int LabelNumber => 1074482; // Mounted pixie + public class MountedPixieWhiteDeed : BaseAddonDeed + { + [Constructible] + public MountedPixieWhiteDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public MountedPixieWhiteDeed() - { - LootType = LootType.Blessed; - } + public MountedPixieWhiteDeed(Serial serial) : base(serial) + { + } - public MountedPixieWhiteDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new MountedPixieWhiteAddon(); + public override int LabelNumber => 1074482; // Mounted pixie - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/SacrificialAltar.cs b/Scripts/Items/Special/Evil Home Decor Collection/SacrificialAltar.cs index 7b3d77bce..8b7428d41 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/SacrificialAltar.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/SacrificialAltar.cs @@ -2,160 +2,158 @@ using System; namespace Server.Items { - [FlippableAddon( Direction.South, Direction.East )] - public class SacrificialAltarAddon : BaseAddonContainer - { - public override BaseAddonContainerDeed Deed => new SacrificialAltarDeed(); - public override int LabelNumber => 1074818; // Sacrificial Altar - public override int DefaultMaxWeight => 0; - public override int DefaultGumpID => 0x107; - public override int DefaultDropSound => 0x42; + [FlippableAddon(Direction.South, Direction.East)] + public class SacrificialAltarAddon : BaseAddonContainer + { + private Timer m_Timer; - private Timer m_Timer; + [Constructible] + public SacrificialAltarAddon() : base(0x2A9B) + { + Direction = Direction.South; - [Constructible] - public SacrificialAltarAddon() : base( 0x2A9B ) - { - Direction = Direction.South; + AddComponent(new LocalizedContainerComponent(0x2A9A, 1074818), 1, 0, 0); + } - AddComponent( new LocalizedContainerComponent( 0x2A9A, 1074818 ), 1, 0, 0 ); - } + public SacrificialAltarAddon(Serial serial) : base(serial) + { + } - public SacrificialAltarAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonContainerDeed Deed => new SacrificialAltarDeed(); + public override int LabelNumber => 1074818; // Sacrificial Altar + public override int DefaultMaxWeight => 0; + public override int DefaultGumpID => 0x107; + public override int DefaultDropSound => 0x42; - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( !base.OnDragDrop( from, dropped ) ) - return false; + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (!base.OnDragDrop(from, dropped)) + return false; - if ( TotalItems >= 50 ) - { - SendLocalizedMessageTo( from, 501478 ); // The trash is full! Emptying! - Empty(); - } - else - { - SendLocalizedMessageTo( from, 1010442 ); // The item will be deleted in three minutes + if (TotalItems >= 50) + { + SendLocalizedMessageTo(from, 501478); // The trash is full! Emptying! + Empty(); + } + else + { + SendLocalizedMessageTo(from, 1010442); // The item will be deleted in three minutes - m_Timer?.Stop(); + m_Timer?.Stop(); - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), Empty ); - } + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), Empty); + } - return true; - } + return true; + } - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( !base.OnDragDropInto( from, item, p ) ) - return false; + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (!base.OnDragDropInto(from, item, p)) + return false; - if ( TotalItems >= 50 ) - { - SendLocalizedMessageTo( from, 501478 ); // The trash is full! Emptying! - Empty(); - } - else - { - SendLocalizedMessageTo( from, 1010442 ); // The item will be deleted in three minutes + if (TotalItems >= 50) + { + SendLocalizedMessageTo(from, 501478); // The trash is full! Emptying! + Empty(); + } + else + { + SendLocalizedMessageTo(from, 1010442); // The item will be deleted in three minutes - m_Timer?.Stop(); + m_Timer?.Stop(); - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), Empty ); - } + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), Empty); + } - return true; - } + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - if ( Items.Count > 0 ) - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), Empty ); - } + if (Items.Count > 0) + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), Empty); + } - public virtual void Flip( Mobile from, Direction direction ) - { - switch ( direction ) - { - case Direction.East: - ItemID = 0x2A9C; - AddComponent( new LocalizedContainerComponent( 0x2A9D, 1074818 ), 0, -1, 0 ); - break; - case Direction.South: - ItemID = 0x2A9B; - AddComponent( new LocalizedContainerComponent( 0x2A9A, 1074818 ), 1, 0, 0 ); - break; - } - } + public virtual void Flip(Mobile from, Direction direction) + { + switch (direction) + { + case Direction.East: + ItemID = 0x2A9C; + AddComponent(new LocalizedContainerComponent(0x2A9D, 1074818), 0, -1, 0); + break; + case Direction.South: + ItemID = 0x2A9B; + AddComponent(new LocalizedContainerComponent(0x2A9A, 1074818), 1, 0, 0); + break; + } + } - public virtual void Empty() - { - if ( Items.Count > 0 ) - { - Point3D location = Location; - location.Z += 10; + public virtual void Empty() + { + if (Items.Count > 0) + { + Point3D location = Location; + location.Z += 10; - Effects.SendLocationEffect( location, Map, 0x3709, 10, 10, 0x356, 0 ); - Effects.PlaySound( location, Map, 0x32E ); + Effects.SendLocationEffect(location, Map, 0x3709, 10, 10, 0x356, 0); + Effects.PlaySound(location, Map, 0x32E); - if ( Items.Count > 0 ) - { - for ( int i = Items.Count - 1; i >= 0; --i ) - { - if ( i >= Items.Count ) - continue; + if (Items.Count > 0) + for (int i = Items.Count - 1; i >= 0; --i) + { + if (i >= Items.Count) + continue; - Items[ i ].Delete(); - } - } - } + Items[i].Delete(); + } + } - m_Timer?.Stop(); + m_Timer?.Stop(); - m_Timer = null; - } - } + m_Timer = null; + } + } - public class SacrificialAltarDeed : BaseAddonContainerDeed - { - public override BaseAddonContainer Addon => new SacrificialAltarAddon(); - public override int LabelNumber => 1074818; // Sacrificial Altar + public class SacrificialAltarDeed : BaseAddonContainerDeed + { + [Constructible] + public SacrificialAltarDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public SacrificialAltarDeed() - { - LootType = LootType.Blessed; - } + public SacrificialAltarDeed(Serial serial) : base(serial) + { + } - public SacrificialAltarDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddonContainer Addon => new SacrificialAltarAddon(); + public override int LabelNumber => 1074818; // Sacrificial Altar - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Evil Home Decor Collection/UnsettlingPortrait.cs b/Scripts/Items/Special/Evil Home Decor Collection/UnsettlingPortrait.cs index 54223a89c..4577d93a8 100644 --- a/Scripts/Items/Special/Evil Home Decor Collection/UnsettlingPortrait.cs +++ b/Scripts/Items/Special/Evil Home Decor Collection/UnsettlingPortrait.cs @@ -3,122 +3,122 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x2A65, 0x2A67 )] - public class UnsettlingPortraitComponent : AddonComponent - { - public override int LabelNumber => 1074480; // Unsettling portrait + [Flippable(0x2A65, 0x2A67)] + public class UnsettlingPortraitComponent : AddonComponent + { + private Timer m_Timer; - private Timer m_Timer; + public UnsettlingPortraitComponent() : base(0x2A65) + { + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), TimeSpan.FromMinutes(3), ChangeDirection); + } - public UnsettlingPortraitComponent() : base( 0x2A65 ) - { - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), TimeSpan.FromMinutes( 3 ), ChangeDirection ); - } + public UnsettlingPortraitComponent(Serial serial) : base(serial) + { + } - public UnsettlingPortraitComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074480; // Unsettling portrait - public override void OnDoubleClick( Mobile from ) - { - if ( Utility.InRange( Location, from.Location, 2 ) ) - Effects.PlaySound( Location, Map, Utility.RandomMinMax( 0x567, 0x568 ) ); - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void OnDoubleClick(Mobile from) + { + if (Utility.InRange(Location, from.Location, 2)) + Effects.PlaySound(Location, Map, Utility.RandomMinMax(0x567, 0x568)); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - m_Timer?.Stop(); - } + m_Timer?.Stop(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Timer = Timer.DelayCall( TimeSpan.FromMinutes( 3 ), TimeSpan.FromMinutes( 3 ), ChangeDirection ); - } + m_Timer = Timer.DelayCall(TimeSpan.FromMinutes(3), TimeSpan.FromMinutes(3), ChangeDirection); + } - private void ChangeDirection() - { - if ( ItemID == 0x2A65 ) - ItemID += 1; - else if ( ItemID == 0x2A66 ) - ItemID -= 1; - else if ( ItemID == 0x2A67 ) - ItemID += 1; - else if ( ItemID == 0x2A68 ) - ItemID -= 1; - } - } + private void ChangeDirection() + { + if (ItemID == 0x2A65) + ItemID += 1; + else if (ItemID == 0x2A66) + ItemID -= 1; + else if (ItemID == 0x2A67) + ItemID += 1; + else if (ItemID == 0x2A68) + ItemID -= 1; + } + } - public class UnsettlingPortraitAddon : BaseAddon - { - public override BaseAddonDeed Deed => new UnsettlingPortraitDeed(); + public class UnsettlingPortraitAddon : BaseAddon + { + [Constructible] + public UnsettlingPortraitAddon() + { + AddComponent(new UnsettlingPortraitComponent(), 0, 0, 0); + } - [Constructible] - public UnsettlingPortraitAddon() - { - AddComponent( new UnsettlingPortraitComponent(), 0, 0, 0 ); - } + public UnsettlingPortraitAddon(Serial serial) : base(serial) + { + } - public UnsettlingPortraitAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new UnsettlingPortraitDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class UnsettlingPortraitDeed : BaseAddonDeed - { - public override BaseAddon Addon => new UnsettlingPortraitAddon(); - public override int LabelNumber => 1074480; // Unsettling portrait + public class UnsettlingPortraitDeed : BaseAddonDeed + { + [Constructible] + public UnsettlingPortraitDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public UnsettlingPortraitDeed() - { - LootType = LootType.Blessed; - } + public UnsettlingPortraitDeed(Serial serial) : base(serial) + { + } - public UnsettlingPortraitDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new UnsettlingPortraitAddon(); + public override int LabelNumber => 1074480; // Unsettling portrait - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/HearthOfHomeFire.cs b/Scripts/Items/Special/Gifts/HearthOfHomeFire.cs index d875b4a2d..19de05473 100644 --- a/Scripts/Items/Special/Gifts/HearthOfHomeFire.cs +++ b/Scripts/Items/Special/Gifts/HearthOfHomeFire.cs @@ -3,128 +3,128 @@ using Server.Network; namespace Server.Items { - public class HearthOfHomeFire : BaseAddon - { - public override BaseAddonDeed Deed => new HearthOfHomeFireDeed(); + public class HearthOfHomeFire : BaseAddon + { + [Constructible] + public HearthOfHomeFire(bool east) + { + if (east) + { + AddLightComponent(new AddonComponent(0x2352), 0, 0, 0); + AddLightComponent(new AddonComponent(0x2358), 0, -1, 0); + } + else + { + AddLightComponent(new AddonComponent(0x2360), 0, 0, 0); + AddLightComponent(new AddonComponent(0x2366), -1, 0, 0); + } + } - [Constructible] - public HearthOfHomeFire( bool east ) - { - if ( east ) - { - AddLightComponent( new AddonComponent( 0x2352 ), 0, 0, 0 ); - AddLightComponent( new AddonComponent( 0x2358 ), 0, -1, 0 ); - } - else - { - AddLightComponent( new AddonComponent( 0x2360 ), 0, 0, 0 ); - AddLightComponent( new AddonComponent( 0x2366 ), -1, 0, 0 ); - } - } + public HearthOfHomeFire(Serial serial) : base(serial) + { + } - private void AddLightComponent( AddonComponent component, int x, int y, int z ) - { - component.Light = LightType.Circle150; + public override BaseAddonDeed Deed => new HearthOfHomeFireDeed(); - AddComponent( component, x, y, z ); - } + private void AddLightComponent(AddonComponent component, int x, int y, int z) + { + component.Light = LightType.Circle150; - public HearthOfHomeFire( Serial serial ) : base( serial ) - { - } + AddComponent(component, x, y, z); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class HearthOfHomeFireDeed : BaseAddonDeed - { - private bool m_East; + public class HearthOfHomeFireDeed : BaseAddonDeed + { + private bool m_East; - public override BaseAddon Addon => new HearthOfHomeFire( m_East ); + [Constructible] + public HearthOfHomeFireDeed() + { + LootType = LootType.Blessed; + } - public override int LabelNumber => 1062919; // Hearth of the Home Fire + public HearthOfHomeFireDeed(Serial serial) : base(serial) + { + } - [Constructible] - public HearthOfHomeFireDeed() - { - LootType = LootType.Blessed; - } + public override BaseAddon Addon => new HearthOfHomeFire(m_East); - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + public override int LabelNumber => 1062919; // Hearth of the Home Fire - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - private class InternalGump : Gump - { - private HearthOfHomeFireDeed m_Deed; + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public InternalGump( HearthOfHomeFireDeed deed ) : base( 150, 50 ) - { - m_Deed = deed; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - AddBackground( 0, 0, 350, 250, 0xA28 ); + writer.WriteEncodedInt(0); // version + } - AddItem( 90, 52, 0x2367 ); - AddItem( 112, 35, 0x2360 ); - AddButton( 70, 35, 0x868, 0x869, 1, GumpButtonType.Reply, 0 ); // South + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - AddItem( 220, 35, 0x2352 ); - AddItem( 242, 52, 0x2358 ); - AddButton( 185, 35, 0x868, 0x869, 2, GumpButtonType.Reply, 0 ); // East - } + int version = reader.ReadEncodedInt(); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed.Deleted || info.ButtonID == 0 ) - return; + private class InternalGump : Gump + { + private HearthOfHomeFireDeed m_Deed; - m_Deed.m_East = (info.ButtonID != 1); - m_Deed.SendTarget( sender.Mobile ); - } - } + public InternalGump(HearthOfHomeFireDeed deed) : base(150, 50) + { + m_Deed = deed; - public HearthOfHomeFireDeed( Serial serial ) : base( serial ) - { - } + AddBackground(0, 0, 350, 250, 0xA28); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(90, 52, 0x2367); + AddItem(112, 35, 0x2360); + AddButton(70, 35, 0x868, 0x869, 1, GumpButtonType.Reply, 0); // South - writer.WriteEncodedInt( (int) 0 ); // version - } + AddItem(220, 35, 0x2352); + AddItem(242, 52, 0x2358); + AddButton(185, 35, 0x868, 0x869, 2, GumpButtonType.Reply, 0); // East + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed.Deleted || info.ButtonID == 0) + return; - int version = reader.ReadEncodedInt(); - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/HolySword.cs b/Scripts/Items/Special/Gifts/HolySword.cs index 553349432..83f9fc326 100644 --- a/Scripts/Items/Special/Gifts/HolySword.cs +++ b/Scripts/Items/Special/Gifts/HolySword.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class HolySword : Longsword - { - public override int LabelNumber => 1062921; // The Holy Sword + public class HolySword : Longsword + { + [Constructible] + public HolySword() + { + Hue = 0x482; + LootType = LootType.Blessed; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Slayer = SlayerName.Silver; - [Constructible] - public HolySword() - { - Hue = 0x482; - LootType = LootType.Blessed; + Attributes.WeaponDamage = 40; + WeaponAttributes.SelfRepair = 10; + WeaponAttributes.LowerStatReq = 100; + WeaponAttributes.UseBestSkill = 1; + } - Slayer = SlayerName.Silver; + public HolySword(Serial serial) : base(serial) + { + } - Attributes.WeaponDamage = 40; - WeaponAttributes.SelfRepair = 10; - WeaponAttributes.LowerStatReq = 100; - WeaponAttributes.UseBestSkill = 1; - } + public override int LabelNumber => 1062921; // The Holy Sword - public HolySword( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/LeggingsOfEmbers.cs b/Scripts/Items/Special/Gifts/LeggingsOfEmbers.cs index e17d09876..cdda8d311 100644 --- a/Scripts/Items/Special/Gifts/LeggingsOfEmbers.cs +++ b/Scripts/Items/Special/Gifts/LeggingsOfEmbers.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class LeggingsOfEmbers : PlateLegs - { - public override int LabelNumber => 1062911; // Royal Leggings of Embers + public class LeggingsOfEmbers : PlateLegs + { + [Constructible] + public LeggingsOfEmbers() + { + Hue = 0x2C; + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 15; - public override int BaseFireResistance => 25; - public override int BaseColdResistance => 0; - public override int BasePoisonResistance => 15; - public override int BaseEnergyResistance => 15; + ArmorAttributes.SelfRepair = 10; + ArmorAttributes.MageArmor = 1; + ArmorAttributes.LowerStatReq = 100; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public LeggingsOfEmbers(Serial serial) : base(serial) + { + } - [Constructible] - public LeggingsOfEmbers() - { - Hue = 0x2C; - LootType = LootType.Blessed; + public override int LabelNumber => 1062911; // Royal Leggings of Embers - ArmorAttributes.SelfRepair = 10; - ArmorAttributes.MageArmor = 1; - ArmorAttributes.LowerStatReq = 100; - } + public override int BasePhysicalResistance => 15; + public override int BaseFireResistance => 25; + public override int BaseColdResistance => 0; + public override int BasePoisonResistance => 15; + public override int BaseEnergyResistance => 15; - public LeggingsOfEmbers( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/RoseOfTrinsic.cs b/Scripts/Items/Special/Gifts/RoseOfTrinsic.cs index 930984c61..8af58ee00 100644 --- a/Scripts/Items/Special/Gifts/RoseOfTrinsic.cs +++ b/Scripts/Items/Special/Gifts/RoseOfTrinsic.cs @@ -1,215 +1,215 @@ using System; using System.Collections.Generic; -using Server.Network; +using Server.ContextMenus; using Server.Gumps; using Server.Multis; -using Server.ContextMenus; +using Server.Network; namespace Server.Items { - [FlippableAttribute( 0x234C, 0x234D )] - public class RoseOfTrinsic : Item, ISecurable - { - private static readonly TimeSpan m_SpawnTime = TimeSpan.FromHours( 4.0 ); + [Flippable(0x234C, 0x234D)] + public class RoseOfTrinsic : Item, ISecurable + { + private static readonly TimeSpan m_SpawnTime = TimeSpan.FromHours(4.0); + private DateTime m_NextSpawnTime; - private int m_Petals; - private DateTime m_NextSpawnTime; - private SpawnTimer m_SpawnTimer; + private int m_Petals; + private SpawnTimer m_SpawnTimer; - public override int LabelNumber => 1062913; // Rose of Trinsic + [Constructible] + public RoseOfTrinsic() : base(0x234D) + { + Weight = 1.0; + LootType = LootType.Blessed; - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + m_Petals = 0; + StartSpawnTimer(TimeSpan.FromMinutes(1.0)); + } - [CommandProperty( AccessLevel.GameMaster )] - public int Petals - { - get => m_Petals; - set - { - if ( value >= 10 ) - { - m_Petals = 10; + public RoseOfTrinsic(Serial serial) : base(serial) + { + } - StopSpawnTimer(); - } - else - { - if ( value <= 0 ) - m_Petals = 0; - else - m_Petals = value; + public override int LabelNumber => 1062913; // Rose of Trinsic - StartSpawnTimer( m_SpawnTime ); - } + [CommandProperty(AccessLevel.GameMaster)] + public int Petals + { + get => m_Petals; + set + { + if (value >= 10) + { + m_Petals = 10; - InvalidateProperties(); - } - } + StopSpawnTimer(); + } + else + { + if (value <= 0) + m_Petals = 0; + else + m_Petals = value; - [Constructible] - public RoseOfTrinsic() : base( 0x234D ) - { - Weight = 1.0; - LootType = LootType.Blessed; + StartSpawnTimer(m_SpawnTime); + } - m_Petals = 0; - StartSpawnTimer( TimeSpan.FromMinutes( 1.0 ) ); - } + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - list.Add( 1062925, Petals.ToString() ); // Petals: ~1_COUNT~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + list.Add(1062925, Petals.ToString()); // Petals: ~1_COUNT~ + } - SetSecureLevelEntry.AddTo( from, this, list ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - private void StartSpawnTimer( TimeSpan delay ) - { - StopSpawnTimer(); + SetSecureLevelEntry.AddTo(from, this, list); + } - m_SpawnTimer = new SpawnTimer( this, delay ); - m_SpawnTimer.Start(); + private void StartSpawnTimer(TimeSpan delay) + { + StopSpawnTimer(); - m_NextSpawnTime = DateTime.UtcNow + delay; - } + m_SpawnTimer = new SpawnTimer(this, delay); + m_SpawnTimer.Start(); - private void StopSpawnTimer() - { - if ( m_SpawnTimer != null ) - { - m_SpawnTimer.Stop(); - m_SpawnTimer = null; - } - } + m_NextSpawnTime = DateTime.UtcNow + delay; + } - private class SpawnTimer : Timer - { - private RoseOfTrinsic m_Rose; + private void StopSpawnTimer() + { + if (m_SpawnTimer != null) + { + m_SpawnTimer.Stop(); + m_SpawnTimer = null; + } + } - public SpawnTimer( RoseOfTrinsic rose, TimeSpan delay ) : base( delay ) - { - m_Rose = rose; + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + else if (Petals > 0) + { + from.AddToBackpack(new RoseOfTrinsicPetal(Petals)); + Petals = 0; + } + } - Priority = TimerPriority.OneMinute; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - protected override void OnTick() - { - if ( m_Rose.Deleted ) - return; + writer.WriteEncodedInt(0); // version - m_Rose.m_SpawnTimer = null; - m_Rose.Petals++; - } - } + writer.WriteEncodedInt(m_Petals); + writer.WriteDeltaTime(m_NextSpawnTime); + writer.WriteEncodedInt((int)Level); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - else if ( Petals > 0 ) - { - from.AddToBackpack( new RoseOfTrinsicPetal( Petals ) ); - Petals = 0; - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public RoseOfTrinsic( Serial serial ) : base( serial ) - { - } + int version = reader.ReadEncodedInt(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Petals = reader.ReadEncodedInt(); + m_NextSpawnTime = reader.ReadDeltaTime(); + Level = (SecureLevel)reader.ReadEncodedInt(); - writer.WriteEncodedInt( (int) 0 ); // version + if (m_Petals < 10) + StartSpawnTimer(m_NextSpawnTime - DateTime.UtcNow); + } - writer.WriteEncodedInt( (int) m_Petals ); - writer.WriteDeltaTime( (DateTime) m_NextSpawnTime ); - writer.WriteEncodedInt( (int) Level ); - } + private class SpawnTimer : Timer + { + private RoseOfTrinsic m_Rose; - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public SpawnTimer(RoseOfTrinsic rose, TimeSpan delay) : base(delay) + { + m_Rose = rose; - int version = reader.ReadEncodedInt(); + Priority = TimerPriority.OneMinute; + } - m_Petals = reader.ReadEncodedInt(); - m_NextSpawnTime = reader.ReadDeltaTime(); - Level = (SecureLevel) reader.ReadEncodedInt(); + protected override void OnTick() + { + if (m_Rose.Deleted) + return; - if ( m_Petals < 10 ) - StartSpawnTimer( m_NextSpawnTime - DateTime.UtcNow ); - } - } + m_Rose.m_SpawnTimer = null; + m_Rose.Petals++; + } + } + } - public class RoseOfTrinsicPetal : Item - { - public override int LabelNumber => 1062926; // Petal of the Rose of Trinsic + public class RoseOfTrinsicPetal : Item + { + [Constructible] + public RoseOfTrinsicPetal() : this(1) + { + } - [Constructible] - public RoseOfTrinsicPetal() : this( 1 ) - { - } + [Constructible] + public RoseOfTrinsicPetal(int amount) : base(0x1021) + { + Stackable = true; + Amount = amount; - [Constructible] - public RoseOfTrinsicPetal( int amount ) : base( 0x1021 ) - { - Stackable = true; - Amount = amount; + Weight = 1.0; + Hue = 0xE; + } - Weight = 1.0; - Hue = 0xE; - } + public RoseOfTrinsicPetal(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1062926; // Petal of the Rose of Trinsic + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + else if (from.GetStatMod("RoseOfTrinsicPetal") != null) + { + from.SendLocalizedMessage( + 1062927); // You have eaten one of these recently and eating another would provide no benefit. + } + else + { + from.PlaySound(0x1EE); + from.AddStatMod(new StatMod(StatType.Str, "RoseOfTrinsicPetal", 5, TimeSpan.FromMinutes(5.0))); - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - else if ( from.GetStatMod( "RoseOfTrinsicPetal" ) != null ) - { - from.SendLocalizedMessage( 1062927 ); // You have eaten one of these recently and eating another would provide no benefit. - } - else - { - from.PlaySound( 0x1EE ); - from.AddStatMod( new StatMod( StatType.Str, "RoseOfTrinsicPetal", 5, TimeSpan.FromMinutes( 5.0 ) ) ); + Consume(); + } + } - Consume(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public RoseOfTrinsicPetal( Serial serial ) : base( serial ) - { - } + writer.WriteEncodedInt(0); // version + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.WriteEncodedInt( (int) 0 ); // version - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/SamuraiHelm.cs b/Scripts/Items/Special/Gifts/SamuraiHelm.cs index 5ad1b61db..08fdc6009 100644 --- a/Scripts/Items/Special/Gifts/SamuraiHelm.cs +++ b/Scripts/Items/Special/Gifts/SamuraiHelm.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x236C, 0x236D )] - public class SamuraiHelm : BaseArmor - { - public override int LabelNumber => 1062923; // Ancient Samurai Helm + [Flippable(0x236C, 0x236D)] + public class SamuraiHelm : BaseArmor + { + [Constructible] + public SamuraiHelm() : base(0x236C) + { + Weight = 5.0; + LootType = LootType.Blessed; - public override int BasePhysicalResistance => 15; - public override int BaseFireResistance => 10; - public override int BaseColdResistance => 10; - public override int BasePoisonResistance => 15; - public override int BaseEnergyResistance => 10; + Attributes.DefendChance = 15; + ArmorAttributes.SelfRepair = 10; + ArmorAttributes.LowerStatReq = 100; + ArmorAttributes.MageArmor = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public SamuraiHelm(Serial serial) : base(serial) + { + } - public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; + public override int LabelNumber => 1062923; // Ancient Samurai Helm - [Constructible] - public SamuraiHelm() : base( 0x236C ) - { - Weight = 5.0; - LootType = LootType.Blessed; + public override int BasePhysicalResistance => 15; + public override int BaseFireResistance => 10; + public override int BaseColdResistance => 10; + public override int BasePoisonResistance => 15; + public override int BaseEnergyResistance => 10; - Attributes.DefendChance = 15; - ArmorAttributes.SelfRepair = 10; - ArmorAttributes.LowerStatReq = 100; - ArmorAttributes.MageArmor = 1; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public SamuraiHelm( Serial serial ) : base( serial ) - { - } + public override ArmorMaterialType MaterialType => ArmorMaterialType.Plate; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/ShaminoCrossbow.cs b/Scripts/Items/Special/Gifts/ShaminoCrossbow.cs index 2d3a437a4..044bfa810 100644 --- a/Scripts/Items/Special/Gifts/ShaminoCrossbow.cs +++ b/Scripts/Items/Special/Gifts/ShaminoCrossbow.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class ShaminoCrossbow : RepeatingCrossbow - { - public override int LabelNumber => 1062915; // Shamino�s Best Crossbow + public class ShaminoCrossbow : RepeatingCrossbow + { + [Constructible] + public ShaminoCrossbow() + { + Hue = 0x504; + LootType = LootType.Blessed; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + Attributes.AttackChance = 15; + Attributes.WeaponDamage = 40; + WeaponAttributes.SelfRepair = 10; + WeaponAttributes.LowerStatReq = 100; + } - [Constructible] - public ShaminoCrossbow() - { - Hue = 0x504; - LootType = LootType.Blessed; + public ShaminoCrossbow(Serial serial) : base(serial) + { + } - Attributes.AttackChance = 15; - Attributes.WeaponDamage = 40; - WeaponAttributes.SelfRepair = 10; - WeaponAttributes.LowerStatReq = 100; - } + public override int LabelNumber => 1062915; // Shamino�s Best Crossbow - public ShaminoCrossbow( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Gifts/TapestryOfSosaria.cs b/Scripts/Items/Special/Gifts/TapestryOfSosaria.cs index a5045f49c..ea607dad7 100644 --- a/Scripts/Items/Special/Gifts/TapestryOfSosaria.cs +++ b/Scripts/Items/Special/Gifts/TapestryOfSosaria.cs @@ -1,74 +1,74 @@ using System.Collections.Generic; -using Server.Gumps; -using Server.Network; -using Server.Multis; using Server.ContextMenus; +using Server.Gumps; +using Server.Multis; +using Server.Network; namespace Server.Items { - [FlippableAttribute( 0x234E, 0x234F )] - public class TapestryOfSosaria : Item, ISecurable - { - public override int LabelNumber => 1062917; // The Tapestry of Sosaria + [Flippable(0x234E, 0x234F)] + public class TapestryOfSosaria : Item, ISecurable + { + [Constructible] + public TapestryOfSosaria() : base(0x234E) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + public TapestryOfSosaria(Serial serial) : base(serial) + { + } - [Constructible] - public TapestryOfSosaria() : base( 0x234E ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public override int LabelNumber => 1062917; // The Tapestry of Sosaria - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - SetSecureLevelEntry.AddTo( from, this, list ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump() ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } + SetSecureLevelEntry.AddTo(from, this, list); + } - private class InternalGump : Gump - { - public InternalGump() : base( 50, 50 ) - { - AddImage( 0, 0, 0x2C95 ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump()); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public TapestryOfSosaria( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); // version - writer.WriteEncodedInt( (int) 0 ); // version + writer.WriteEncodedInt((int)Level); + } - writer.WriteEncodedInt( (int) Level ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + int version = reader.ReadEncodedInt(); - int version = reader.ReadEncodedInt(); + Level = (SecureLevel)reader.ReadEncodedInt(); + } - Level = (SecureLevel) reader.ReadEncodedInt(); - } - } -} + private class InternalGump : Gump + { + public InternalGump() : base(50, 50) + { + AddImage(0, 0, 0x2C95); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/AppleTrunk.cs b/Scripts/Items/Special/Heritage Items/AppleTrunk.cs index 2f96bed61..ba3ba7b7b 100644 --- a/Scripts/Items/Special/Heritage Items/AppleTrunk.cs +++ b/Scripts/Items/Special/Heritage Items/AppleTrunk.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class AppleTrunkAddon : BaseAddon - { - public override BaseAddonDeed Deed => new AppleTrunkDeed(); + public class AppleTrunkAddon : BaseAddon + { + [Constructible] + public AppleTrunkAddon() + { + AddComponent(new LocalizedAddonComponent(0xD98, 1076785), 0, 0, 0); + } - [Constructible] - public AppleTrunkAddon() - { - AddComponent( new LocalizedAddonComponent( 0xD98, 1076785 ), 0, 0, 0 ); - } + public AppleTrunkAddon(Serial serial) : base(serial) + { + } - public AppleTrunkAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AppleTrunkDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class AppleTrunkDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AppleTrunkAddon(); - public override int LabelNumber => 1076785; // Apple Trunk + public class AppleTrunkDeed : BaseAddonDeed + { + [Constructible] + public AppleTrunkDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public AppleTrunkDeed() - { - LootType = LootType.Blessed; - } + public AppleTrunkDeed(Serial serial) : base(serial) + { + } - public AppleTrunkDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AppleTrunkAddon(); + public override int LabelNumber => 1076785; // Apple Trunk - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/BlueDecorativeRug.cs b/Scripts/Items/Special/Heritage Items/BlueDecorativeRug.cs index 5feff2555..a84d76e24 100644 --- a/Scripts/Items/Special/Heritage Items/BlueDecorativeRug.cs +++ b/Scripts/Items/Special/Heritage Items/BlueDecorativeRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class BlueDecorativeRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BlueDecorativeRugDeed(); + public class BlueDecorativeRugAddon : BaseAddon + { + [Constructible] + public BlueDecorativeRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xAD2, 1076589), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAD3, 1076589), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAD4, 1076589), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAD5, 1076589), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAD6, 1076589), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAD7, 1076589), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAD8, 1076589), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAD9, 1076589), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAD1, 1076589), 0, 0, 0); + } - [Constructible] - public BlueDecorativeRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xAD2, 1076589 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD3, 1076589 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD4, 1076589 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD5, 1076589 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD6, 1076589 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD7, 1076589 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD8, 1076589 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD9, 1076589 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD1, 1076589 ), 0, 0, 0 ); - } + public BlueDecorativeRugAddon(Serial serial) : base(serial) + { + } - public BlueDecorativeRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BlueDecorativeRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BlueDecorativeRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BlueDecorativeRugAddon(); - public override int LabelNumber => 1076589; // Blue decorative rug + public class BlueDecorativeRugDeed : BaseAddonDeed + { + [Constructible] + public BlueDecorativeRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BlueDecorativeRugDeed() - { - LootType = LootType.Blessed; - } + public BlueDecorativeRugDeed(Serial serial) : base(serial) + { + } - public BlueDecorativeRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BlueDecorativeRugAddon(); + public override int LabelNumber => 1076589; // Blue decorative rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/BlueFancyRug.cs b/Scripts/Items/Special/Heritage Items/BlueFancyRug.cs index 751baf008..7bb39b6f7 100644 --- a/Scripts/Items/Special/Heritage Items/BlueFancyRug.cs +++ b/Scripts/Items/Special/Heritage Items/BlueFancyRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class BlueFancyRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BlueFancyRugDeed(); + public class BlueFancyRugAddon : BaseAddon + { + [Constructible] + public BlueFancyRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xAC2, 1076273), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAC3, 1076273), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAC4, 1076273), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAC5, 1076273), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF6, 1076273), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAF7, 1076273), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF8, 1076273), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAF9, 1076273), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAFA, 1076273), 0, 0, 0); + } - [Constructible] - public BlueFancyRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xAC2, 1076273 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC3, 1076273 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC4, 1076273 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC5, 1076273 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF6, 1076273 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF7, 1076273 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF8, 1076273 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF9, 1076273 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAFA, 1076273 ), 0, 0, 0 ); - } + public BlueFancyRugAddon(Serial serial) : base(serial) + { + } - public BlueFancyRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BlueFancyRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BlueFancyRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BlueFancyRugAddon(); - public override int LabelNumber => 1076273; // Blue fancy rug + public class BlueFancyRugDeed : BaseAddonDeed + { + [Constructible] + public BlueFancyRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BlueFancyRugDeed() - { - LootType = LootType.Blessed; - } + public BlueFancyRugDeed(Serial serial) : base(serial) + { + } - public BlueFancyRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BlueFancyRugAddon(); + public override int LabelNumber => 1076273; // Blue fancy rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/BluePlainRug.cs b/Scripts/Items/Special/Heritage Items/BluePlainRug.cs index bb85c3dd1..4746e7357 100644 --- a/Scripts/Items/Special/Heritage Items/BluePlainRug.cs +++ b/Scripts/Items/Special/Heritage Items/BluePlainRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class BluePlainRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new BluePlainRugDeed(); + public class BluePlainRugAddon : BaseAddon + { + [Constructible] + public BluePlainRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xAC2, 1076585), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAC3, 1076585), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAC4, 1076585), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAC5, 1076585), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF6, 1076585), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAF7, 1076585), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF8, 1076585), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAF9, 1076585), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAC0, 1076585), 0, 0, 0); + } - [Constructible] - public BluePlainRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xAC2, 1076585 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC3, 1076585 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC4, 1076585 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC5, 1076585 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF6, 1076585 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF7, 1076585 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF8, 1076585 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF9, 1076585 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC0, 1076585 ), 0, 0, 0 ); - } + public BluePlainRugAddon(Serial serial) : base(serial) + { + } - public BluePlainRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new BluePlainRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BluePlainRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new BluePlainRugAddon(); - public override int LabelNumber => 1076585; // Blue plain rug + public class BluePlainRugDeed : BaseAddonDeed + { + [Constructible] + public BluePlainRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BluePlainRugDeed() - { - LootType = LootType.Blessed; - } + public BluePlainRugDeed(Serial serial) : base(serial) + { + } - public BluePlainRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new BluePlainRugAddon(); + public override int LabelNumber => 1076585; // Blue plain rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/BoilingCauldron.cs b/Scripts/Items/Special/Heritage Items/BoilingCauldron.cs index 06fe00115..0eed82cf5 100644 --- a/Scripts/Items/Special/Heritage Items/BoilingCauldron.cs +++ b/Scripts/Items/Special/Heritage Items/BoilingCauldron.cs @@ -1,66 +1,66 @@ namespace Server.Items { - [Flippable( 0x2068, 0x207A )] - public class BoilingCauldronAddon : BaseAddonContainer - { - public override BaseAddonContainerDeed Deed => new BoilingCauldronDeed(); - public override int LabelNumber => 1076267; // Boiling Cauldron - public override int DefaultGumpID => 0x9; - public override int DefaultDropSound => 0x42; + [Flippable(0x2068, 0x207A)] + public class BoilingCauldronAddon : BaseAddonContainer + { + [Constructible] + public BoilingCauldronAddon() : base(0x2068) + { + AddComponent(new LocalizedContainerComponent(0xFAC, 1076267), 0, 0, 0); + AddComponent(new LocalizedContainerComponent(0x970, 1076267), 0, 0, 8); + } - [Constructible] - public BoilingCauldronAddon() : base( 0x2068 ) - { - AddComponent( new LocalizedContainerComponent( 0xFAC, 1076267 ), 0, 0, 0 ); - AddComponent( new LocalizedContainerComponent( 0x970, 1076267 ), 0, 0, 8 ); - } + public BoilingCauldronAddon(Serial serial) : base(serial) + { + } - public BoilingCauldronAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonContainerDeed Deed => new BoilingCauldronDeed(); + public override int LabelNumber => 1076267; // Boiling Cauldron + public override int DefaultGumpID => 0x9; + public override int DefaultDropSound => 0x42; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BoilingCauldronDeed : BaseAddonContainerDeed - { - public override BaseAddonContainer Addon => new BoilingCauldronAddon(); - public override int LabelNumber => 1076267; // Boiling Cauldron + public class BoilingCauldronDeed : BaseAddonContainerDeed + { + [Constructible] + public BoilingCauldronDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public BoilingCauldronDeed() - { - LootType = LootType.Blessed; - } + public BoilingCauldronDeed(Serial serial) : base(serial) + { + } - public BoilingCauldronDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddonContainer Addon => new BoilingCauldronAddon(); + public override int LabelNumber => 1076267; // Boiling Cauldron - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/CherryBlossomTree.cs b/Scripts/Items/Special/Heritage Items/CherryBlossomTree.cs index e0fe028f8..82540e7e8 100644 --- a/Scripts/Items/Special/Heritage Items/CherryBlossomTree.cs +++ b/Scripts/Items/Special/Heritage Items/CherryBlossomTree.cs @@ -1,62 +1,62 @@ namespace Server.Items { - public class CherryBlossomTreeAddon : BaseAddon - { - public override BaseAddonDeed Deed => new CherryBlossomTreeDeed(); + public class CherryBlossomTreeAddon : BaseAddon + { + [Constructible] + public CherryBlossomTreeAddon() + { + AddComponent(new LocalizedAddonComponent(0x26EE, 1076268), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3122, 1076268), 0, 0, 0); + } - [Constructible] - public CherryBlossomTreeAddon() - { - AddComponent( new LocalizedAddonComponent( 0x26EE, 1076268 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3122, 1076268 ), 0, 0, 0 ); - } + public CherryBlossomTreeAddon(Serial serial) : base(serial) + { + } - public CherryBlossomTreeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new CherryBlossomTreeDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class CherryBlossomTreeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new CherryBlossomTreeAddon(); - public override int LabelNumber => 1076268; // Cherry Blossom Tree + public class CherryBlossomTreeDeed : BaseAddonDeed + { + [Constructible] + public CherryBlossomTreeDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public CherryBlossomTreeDeed() - { - LootType = LootType.Blessed; - } + public CherryBlossomTreeDeed(Serial serial) : base(serial) + { + } - public CherryBlossomTreeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new CherryBlossomTreeAddon(); + public override int LabelNumber => 1076268; // Cherry Blossom Tree - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/CherryBlossomTrunk.cs b/Scripts/Items/Special/Heritage Items/CherryBlossomTrunk.cs index 9f9f5d5e6..ca1b4965a 100644 --- a/Scripts/Items/Special/Heritage Items/CherryBlossomTrunk.cs +++ b/Scripts/Items/Special/Heritage Items/CherryBlossomTrunk.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class CherryBlossomTrunkAddon : BaseAddon - { - public override BaseAddonDeed Deed => new CherryBlossomTrunkDeed(); + public class CherryBlossomTrunkAddon : BaseAddon + { + [Constructible] + public CherryBlossomTrunkAddon() + { + AddComponent(new LocalizedAddonComponent(0x26EE, 1076784), 0, 0, 0); + } - [Constructible] - public CherryBlossomTrunkAddon() - { - AddComponent( new LocalizedAddonComponent( 0x26EE, 1076784 ), 0, 0, 0 ); - } + public CherryBlossomTrunkAddon(Serial serial) : base(serial) + { + } - public CherryBlossomTrunkAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new CherryBlossomTrunkDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class CherryBlossomTrunkDeed : BaseAddonDeed - { - public override BaseAddon Addon => new CherryBlossomTrunkAddon(); - public override int LabelNumber => 1076784; // Cherry Blossom Trunk + public class CherryBlossomTrunkDeed : BaseAddonDeed + { + [Constructible] + public CherryBlossomTrunkDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public CherryBlossomTrunkDeed() - { - LootType = LootType.Blessed; - } + public CherryBlossomTrunkDeed(Serial serial) : base(serial) + { + } - public CherryBlossomTrunkDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new CherryBlossomTrunkAddon(); + public override int LabelNumber => 1076784; // Cherry Blossom Trunk - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/CinnamonFancyRug.cs b/Scripts/Items/Special/Heritage Items/CinnamonFancyRug.cs index b68e77503..f1ae357ff 100644 --- a/Scripts/Items/Special/Heritage Items/CinnamonFancyRug.cs +++ b/Scripts/Items/Special/Heritage Items/CinnamonFancyRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class CinnamonFancyRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new CinnamonFancyRugDeed(); + public class CinnamonFancyRugAddon : BaseAddon + { + [Constructible] + public CinnamonFancyRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xAE3, 1076587), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAE4, 1076587), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAE5, 1076587), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAE6, 1076587), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAE7, 1076587), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAE8, 1076587), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAE9, 1076587), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAEA, 1076587), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAEB, 1076587), 0, 0, 0); + } - [Constructible] - public CinnamonFancyRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xAE3, 1076587 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE4, 1076587 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE5, 1076587 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE6, 1076587 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE7, 1076587 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE8, 1076587 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE9, 1076587 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAEA, 1076587 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAEB, 1076587 ), 0, 0, 0 ); - } + public CinnamonFancyRugAddon(Serial serial) : base(serial) + { + } - public CinnamonFancyRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new CinnamonFancyRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class CinnamonFancyRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new CinnamonFancyRugAddon(); - public override int LabelNumber => 1076587; // Cinnamon fancy rug + public class CinnamonFancyRugDeed : BaseAddonDeed + { + [Constructible] + public CinnamonFancyRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public CinnamonFancyRugDeed() - { - LootType = LootType.Blessed; - } + public CinnamonFancyRugDeed(Serial serial) : base(serial) + { + } - public CinnamonFancyRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new CinnamonFancyRugAddon(); + public override int LabelNumber => 1076587; // Cinnamon fancy rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/Curtains.cs b/Scripts/Items/Special/Heritage Items/Curtains.cs index 8ef6abee6..2c006008d 100644 --- a/Scripts/Items/Special/Heritage Items/Curtains.cs +++ b/Scripts/Items/Special/Heritage Items/Curtains.cs @@ -3,201 +3,201 @@ using Server.Network; namespace Server.Items { - public class CurtainsComponent : AddonComponent, IDyable - { - public override int LabelNumber => 1076280; // Curtains - public override bool DisplayWeight => false; + public class CurtainsComponent : AddonComponent, IDyable + { + public CurtainsComponent(int itemID, int closedID) : base(itemID) + { + ClosedID = closedID; + } - [CommandProperty( AccessLevel.GameMaster )] - public int ClosedID { get; set; } + public CurtainsComponent(Serial serial) : base(serial) + { + } - public CurtainsComponent( int itemID, int closedID ) : base( itemID ) - { - ClosedID = closedID; - } + public override int LabelNumber => 1076280; // Curtains + public override bool DisplayWeight => false; - public CurtainsComponent( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int ClosedID{ get; set; } - public override void OnDoubleClick( Mobile from ) - { - base.OnDoubleClick( from ); + #region IDyable - if ( Addon != null ) - { - if ( from.InRange( Location, 1 ) ) - { - foreach ( AddonComponent c in Addon.Components ) - { - if ( c is CurtainsComponent curtain ) - { - int temp = curtain.ItemID; - curtain.ItemID = curtain.ClosedID; - curtain.ClosedID = temp; - } - } - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } + public virtual bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Hue = sender.DyedHue; + return true; + } - writer.WriteEncodedInt( 0 ); // version + #endregion - writer.Write( (int) ClosedID ); - } + public override void OnDoubleClick(Mobile from) + { + base.OnDoubleClick(from); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (Addon != null) + if (from.InRange(Location, 1)) + foreach (AddonComponent c in Addon.Components) + if (c is CurtainsComponent curtain) + { + int temp = curtain.ItemID; + curtain.ItemID = curtain.ClosedID; + curtain.ClosedID = temp; + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - int version = reader.ReadEncodedInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - ClosedID = reader.ReadInt(); - } + writer.WriteEncodedInt(0); // version - #region IDyable - public virtual bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + writer.Write(ClosedID); + } - Hue = sender.DyedHue; - return true; - } - #endregion - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public class CurtainsAddon : BaseAddon - { - public override BaseAddonDeed Deed => new CurtainsDeed(); - public override bool RetainDeedHue => true; + int version = reader.ReadEncodedInt(); - [Constructible] - public CurtainsAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new CurtainsComponent( 0x3D9E, 0x3DA8 ), 0, -1, 0 ); - AddComponent( new CurtainsComponent( 0x3DAC, 0x3DAE ), 0, 0, 0 ); - AddComponent( new CurtainsComponent( 0x3DA0, 0x3DA6 ), 0, 2, 0 ); - AddComponent( new CurtainsComponent( 0x3D9F, 0x3DA7 ), 0, 1, 0 ); - } - else // south - { - AddComponent( new CurtainsComponent( 0x3D9C, 0x3DAD ), 0, 0, 0 ); - AddComponent( new CurtainsComponent( 0x3D9D, 0x3DA3 ), -1, 0, 0 ); - AddComponent( new CurtainsComponent( 0x3DA1, 0x3DA5 ), 2, 0, 0 ); - AddComponent( new CurtainsComponent( 0x3DAB, 0x3DA4 ), 1, 0, 0 ); - } - } + ClosedID = reader.ReadInt(); + } + } - public CurtainsAddon( Serial serial ) : base( serial ) - { - } + public class CurtainsAddon : BaseAddon + { + [Constructible] + public CurtainsAddon(bool east) + { + if (east) // east + { + AddComponent(new CurtainsComponent(0x3D9E, 0x3DA8), 0, -1, 0); + AddComponent(new CurtainsComponent(0x3DAC, 0x3DAE), 0, 0, 0); + AddComponent(new CurtainsComponent(0x3DA0, 0x3DA6), 0, 2, 0); + AddComponent(new CurtainsComponent(0x3D9F, 0x3DA7), 0, 1, 0); + } + else // south + { + AddComponent(new CurtainsComponent(0x3D9C, 0x3DAD), 0, 0, 0); + AddComponent(new CurtainsComponent(0x3D9D, 0x3DA3), -1, 0, 0); + AddComponent(new CurtainsComponent(0x3DA1, 0x3DA5), 2, 0, 0); + AddComponent(new CurtainsComponent(0x3DAB, 0x3DA4), 1, 0, 0); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public CurtainsAddon(Serial serial) : base(serial) + { + } - writer.WriteEncodedInt( 0 ); // version - } + public override BaseAddonDeed Deed => new CurtainsDeed(); + public override bool RetainDeedHue => true; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadEncodedInt(); - } - } + writer.WriteEncodedInt(0); // version + } - public class CurtainsDeed : BaseAddonDeed - { - public override BaseAddon Addon => new CurtainsAddon( m_East ); - public override int LabelNumber => 1076280; // Curtains + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - private bool m_East; + int version = reader.ReadEncodedInt(); + } + } - [Constructible] - public CurtainsDeed() - { - LootType = LootType.Blessed; - } + public class CurtainsDeed : BaseAddonDeed + { + private bool m_East; - public CurtainsDeed( Serial serial ) : base( serial ) - { - } + [Constructible] + public CurtainsDeed() + { + LootType = LootType.Blessed; + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public CurtainsDeed(Serial serial) : base(serial) + { + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + public override BaseAddon Addon => new CurtainsAddon(m_East); + public override int LabelNumber => 1076280; // Curtains - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - writer.WriteEncodedInt( 0 ); // version - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadEncodedInt(); - } + writer.WriteEncodedInt(0); // version + } - private class InternalGump : Gump - { - private CurtainsDeed m_Deed; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalGump( CurtainsDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + int version = reader.ReadEncodedInt(); + } - AddPage( 0 ); + private class InternalGump : Gump + { + private CurtainsDeed m_Deed; - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076581, 0x7FFF, false, false ); // Please select your curtain position + public InternalGump(CurtainsDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 1 ); + AddPage(0); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076581, 0x7FFF, false, false); // Please select your curtain position - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + AddPage(1); - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; + + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/Fountain.cs b/Scripts/Items/Special/Heritage Items/Fountain.cs index e4c625162..4806d278f 100644 --- a/Scripts/Items/Special/Heritage Items/Fountain.cs +++ b/Scripts/Items/Special/Heritage Items/Fountain.cs @@ -1,60 +1,60 @@ namespace Server.Items { - public class FountainAddon : StoneFountainAddon - { - public override BaseAddonDeed Deed => new FountainDeed(); + public class FountainAddon : StoneFountainAddon + { + [Constructible] + public FountainAddon() + { + } - [Constructible] - public FountainAddon() - { - } + public FountainAddon(Serial serial) : base(serial) + { + } - public FountainAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new FountainDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class FountainDeed : BaseAddonDeed - { - public override BaseAddon Addon => new FountainAddon(); - public override int LabelNumber => 1076283; // Fountain + public class FountainDeed : BaseAddonDeed + { + [Constructible] + public FountainDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public FountainDeed() - { - LootType = LootType.Blessed; - } + public FountainDeed(Serial serial) : base(serial) + { + } - public FountainDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new FountainAddon(); + public override int LabelNumber => 1076283; // Fountain - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/FruitTrees.cs b/Scripts/Items/Special/Heritage Items/FruitTrees.cs index 86677d3c1..b58f59661 100644 --- a/Scripts/Items/Special/Heritage Items/FruitTrees.cs +++ b/Scripts/Items/Special/Heritage Items/FruitTrees.cs @@ -3,212 +3,216 @@ using Server.Network; namespace Server.Items { - public abstract class BaseFruitTreeAddon : BaseAddon - { - public override abstract BaseAddonDeed Deed { get; } - public abstract Item Fruit { get; } + public abstract class BaseFruitTreeAddon : BaseAddon + { + private int m_Fruits; - private int m_Fruits; + public BaseFruitTreeAddon() + { + Timer.DelayCall(TimeSpan.FromMinutes(5), Respawn); + } - [CommandProperty( AccessLevel.GameMaster )] - public int Fruits - { - get => m_Fruits; - set - { - if ( value < 0 ) - m_Fruits = 0; - else - m_Fruits = value; - } - } + public BaseFruitTreeAddon(Serial serial) : base(serial) + { + } - public BaseFruitTreeAddon() - { - Timer.DelayCall( TimeSpan.FromMinutes( 5 ), Respawn ); - } + public abstract override BaseAddonDeed Deed{ get; } + public abstract Item Fruit{ get; } - public BaseFruitTreeAddon( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Fruits + { + get => m_Fruits; + set + { + if (value < 0) + m_Fruits = 0; + else + m_Fruits = value; + } + } - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( from.InRange( c.Location, 2 ) ) - { - if ( m_Fruits > 0 ) - { - Item fruit = Fruit; + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (from.InRange(c.Location, 2)) + { + if (m_Fruits > 0) + { + Item fruit = Fruit; - if ( fruit == null ) - return; + if (fruit == null) + return; - if ( !from.PlaceInBackpack( fruit ) ) - { - fruit.Delete(); - from.SendLocalizedMessage( 501015 ); // There is no room in your backpack for the fruit. - } - else - { - if ( --m_Fruits == 0 ) - Timer.DelayCall( TimeSpan.FromMinutes( 30 ), Respawn ); + if (!from.PlaceInBackpack(fruit)) + { + fruit.Delete(); + from.SendLocalizedMessage(501015); // There is no room in your backpack for the fruit. + } + else + { + if (--m_Fruits == 0) + Timer.DelayCall(TimeSpan.FromMinutes(30), Respawn); - from.SendLocalizedMessage( 501016 ); // You pick some fruit and put it in your backpack. - } - } - else - from.SendLocalizedMessage( 501017 ); // There is no more fruit on this tree - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + from.SendLocalizedMessage(501016); // You pick some fruit and put it in your backpack. + } + } + else + { + from.SendLocalizedMessage(501017); // There is no more fruit on this tree + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - private void Respawn() - { - m_Fruits = Utility.RandomMinMax( 1, 4 ); - } + private void Respawn() + { + m_Fruits = Utility.RandomMinMax(1, 4); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (int) m_Fruits ); - } + writer.Write(m_Fruits); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Fruits = reader.ReadInt(); + m_Fruits = reader.ReadInt(); - if ( m_Fruits == 0 ) - Respawn(); - } - } + if (m_Fruits == 0) + Respawn(); + } + } - public class AppleTreeAddon : BaseFruitTreeAddon - { - public override BaseAddonDeed Deed => new AppleTreeDeed(); - public override Item Fruit => new Apple(); + public class AppleTreeAddon : BaseFruitTreeAddon + { + [Constructible] + public AppleTreeAddon() + { + AddComponent(new LocalizedAddonComponent(0xD98, 1076269), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3124, 1076269), 0, 0, 0); + } - [Constructible] - public AppleTreeAddon() - { - AddComponent( new LocalizedAddonComponent( 0xD98, 1076269 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3124, 1076269 ), 0, 0, 0 ); - } + public AppleTreeAddon(Serial serial) : base(serial) + { + } - public AppleTreeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new AppleTreeDeed(); + public override Item Fruit => new Apple(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class AppleTreeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new AppleTreeAddon(); - public override int LabelNumber => 1076269; // Apple Tree + public class AppleTreeDeed : BaseAddonDeed + { + [Constructible] + public AppleTreeDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public AppleTreeDeed() - { - LootType = LootType.Blessed; - } + public AppleTreeDeed(Serial serial) : base(serial) + { + } - public AppleTreeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new AppleTreeAddon(); + public override int LabelNumber => 1076269; // Apple Tree - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class PeachTreeAddon : BaseFruitTreeAddon - { - public override BaseAddonDeed Deed => new PeachTreeDeed(); - public override Item Fruit => new Peach(); + public class PeachTreeAddon : BaseFruitTreeAddon + { + [Constructible] + public PeachTreeAddon() + { + AddComponent(new LocalizedAddonComponent(0xD9C, 1076270), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3123, 1076270), 0, 0, 0); + } - [Constructible] - public PeachTreeAddon() - { - AddComponent( new LocalizedAddonComponent( 0xD9C, 1076270 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3123, 1076270 ), 0, 0, 0 ); - } + public PeachTreeAddon(Serial serial) : base(serial) + { + } - public PeachTreeAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PeachTreeDeed(); + public override Item Fruit => new Peach(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class PeachTreeDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PeachTreeAddon(); - public override int LabelNumber => 1076270; // Peach Tree + public class PeachTreeDeed : BaseAddonDeed + { + [Constructible] + public PeachTreeDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public PeachTreeDeed() - { - LootType = LootType.Blessed; - } + public PeachTreeDeed(Serial serial) : base(serial) + { + } - public PeachTreeDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PeachTreeAddon(); + public override int LabelNumber => 1076270; // Peach Tree - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/GoldenDecorativeRug.cs b/Scripts/Items/Special/Heritage Items/GoldenDecorativeRug.cs index 963cc20d2..638760f9b 100644 --- a/Scripts/Items/Special/Heritage Items/GoldenDecorativeRug.cs +++ b/Scripts/Items/Special/Heritage Items/GoldenDecorativeRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class GoldenDecorativeRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GoldenDecorativeRugDeed(); + public class GoldenDecorativeRugAddon : BaseAddon + { + [Constructible] + public GoldenDecorativeRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xADB, 1076586), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xADC, 1076586), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xADD, 1076586), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xADE, 1076586), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xADF, 1076586), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAE0, 1076586), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAE1, 1076586), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAE2, 1076586), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xADA, 1076586), 0, 0, 0); + } - [Constructible] - public GoldenDecorativeRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xADB, 1076586 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xADC, 1076586 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xADD, 1076586 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xADE, 1076586 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xADF, 1076586 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE0, 1076586 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE1, 1076586 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAE2, 1076586 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xADA, 1076586 ), 0, 0, 0 ); - } + public GoldenDecorativeRugAddon(Serial serial) : base(serial) + { + } - public GoldenDecorativeRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new GoldenDecorativeRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class GoldenDecorativeRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new GoldenDecorativeRugAddon(); - public override int LabelNumber => 1076586; // Golden decorative rug + public class GoldenDecorativeRugDeed : BaseAddonDeed + { + [Constructible] + public GoldenDecorativeRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public GoldenDecorativeRugDeed() - { - LootType = LootType.Blessed; - } + public GoldenDecorativeRugDeed(Serial serial) : base(serial) + { + } - public GoldenDecorativeRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new GoldenDecorativeRugAddon(); + public override int LabelNumber => 1076586; // Golden decorative rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/Guillotine.cs b/Scripts/Items/Special/Heritage Items/Guillotine.cs index b07de323a..71f1a54db 100644 --- a/Scripts/Items/Special/Heritage Items/Guillotine.cs +++ b/Scripts/Items/Special/Heritage Items/Guillotine.cs @@ -1,172 +1,178 @@ using System; -using Server.Spells; using Server.Network; +using Server.Spells; namespace Server.Items { - [Flippable( 0x125E, 0x1230 )] - public class GuillotineComponent : AddonComponent - { - public override int LabelNumber => 1024656; // Guillotine + [Flippable(0x125E, 0x1230)] + public class GuillotineComponent : AddonComponent + { + public GuillotineComponent() : base(0x125E) + { + } - public GuillotineComponent() : base( 0x125E ) - { - } + public GuillotineComponent(Serial serial) : base(serial) + { + } - public GuillotineComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1024656; // Guillotine - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class GuillotineAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GuillotineDeed(); + public class GuillotineAddon : BaseAddon + { + [Constructible] + public GuillotineAddon() + { + AddComponent(new GuillotineComponent(), 0, 0, 0); + } - [Constructible] - public GuillotineAddon() - { - AddComponent( new GuillotineComponent(), 0, 0, 0 ); - } + public GuillotineAddon(Serial serial) : base(serial) + { + } - public GuillotineAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new GuillotineDeed(); - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - if ( Utility.RandomBool() ) - { - from.Location = Location; + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (from.InRange(Location, 2)) + { + if (Utility.RandomBool()) + { + from.Location = Location; - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), new TimerStateCallback( Activate ), new object[] { c, from } ); - } - else - from.LocalOverheadMessage( MessageType.Regular, 0, 501777 ); // Hmm... you suspect that if you used this again, it might hurt. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + Timer.DelayCall(TimeSpan.FromSeconds(0.5), new TimerStateCallback(Activate), new object[] { c, from }); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0, + 501777); // Hmm... you suspect that if you used this again, it might hurt. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private void Activate( object obj ) - { - object[] param = (object[]) obj; + private void Activate(object obj) + { + object[] param = (object[])obj; - if ( param[ 0 ] is AddonComponent component && param[ 1 ] is Mobile mobile ) - Activate( component, mobile ); - } + if (param[0] is AddonComponent component && param[1] is Mobile mobile) + Activate(component, mobile); + } - public virtual void Activate( AddonComponent c, Mobile from ) - { - if ( c.ItemID == 0x125E || c.ItemID == 0x1269 || c.ItemID == 0x1260 ) - c.ItemID = 0x1269; - else - c.ItemID = 0x1247; + public virtual void Activate(AddonComponent c, Mobile from) + { + if (c.ItemID == 0x125E || c.ItemID == 0x1269 || c.ItemID == 0x1260) + c.ItemID = 0x1269; + else + c.ItemID = 0x1247; - // blood - int amount = Utility.RandomMinMax( 3, 7 ); + // blood + int amount = Utility.RandomMinMax(3, 7); - for ( int i = 0; i < amount; i++ ) - { - int x = c.X + Utility.RandomMinMax( -1, 1 ); - int y = c.Y + Utility.RandomMinMax( -1, 1 ); - int z = c.Z; + for (int i = 0; i < amount; i++) + { + int x = c.X + Utility.RandomMinMax(-1, 1); + int y = c.Y + Utility.RandomMinMax(-1, 1); + int z = c.Z; - if ( !c.Map.CanFit( x, y, z, 1, false, false, true ) ) - { - z = c.Map.GetAverageZ( x, y ); + if (!c.Map.CanFit(x, y, z, 1, false, false, true)) + { + z = c.Map.GetAverageZ(x, y); - if ( !c.Map.CanFit( x, y, z, 1, false, false, true ) ) - continue; - } + if (!c.Map.CanFit(x, y, z, 1, false, false, true)) + continue; + } - Blood blood = new Blood( Utility.RandomMinMax( 0x122C, 0x122F ) ); - blood.MoveToWorld( new Point3D( x, y, z ), c.Map ); - } + Blood blood = new Blood(Utility.RandomMinMax(0x122C, 0x122F)); + blood.MoveToWorld(new Point3D(x, y, z), c.Map); + } - if ( from.Female ) - from.PlaySound( Utility.RandomMinMax( 0x150, 0x153 ) ); - else - from.PlaySound( Utility.RandomMinMax( 0x15A, 0x15D ) ); + if (from.Female) + from.PlaySound(Utility.RandomMinMax(0x150, 0x153)); + else + from.PlaySound(Utility.RandomMinMax(0x15A, 0x15D)); - from.LocalOverheadMessage( MessageType.Regular, 0, 501777 ); // Hmm... you suspect that if you used this again, it might hurt. - SpellHelper.Damage( TimeSpan.Zero, from, Utility.Dice( 2, 10, 5 ) ); + from.LocalOverheadMessage(MessageType.Regular, 0, + 501777); // Hmm... you suspect that if you used this again, it might hurt. + SpellHelper.Damage(TimeSpan.Zero, from, Utility.Dice(2, 10, 5)); - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ), 2, new TimerStateCallback( Deactivate ), c ); - } + Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5), 2, new TimerStateCallback(Deactivate), c); + } - private void Deactivate( object obj ) - { - if ( obj is AddonComponent c ) - { - if ( c.ItemID == 0x1269 ) - c.ItemID = 0x1260; - else if ( c.ItemID == 0x1260 ) - c.ItemID = 0x125E; - else if ( c.ItemID == 0x1247 ) - c.ItemID = 0x1246; - else if ( c.ItemID == 0x1246 ) - c.ItemID = 0x1230; - } - } - } + private void Deactivate(object obj) + { + if (obj is AddonComponent c) + { + if (c.ItemID == 0x1269) + c.ItemID = 0x1260; + else if (c.ItemID == 0x1260) + c.ItemID = 0x125E; + else if (c.ItemID == 0x1247) + c.ItemID = 0x1246; + else if (c.ItemID == 0x1246) + c.ItemID = 0x1230; + } + } + } - public class GuillotineDeed : BaseAddonDeed - { - public override BaseAddon Addon => new GuillotineAddon(); - public override int LabelNumber => 1024656; // Guillotine + public class GuillotineDeed : BaseAddonDeed + { + [Constructible] + public GuillotineDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public GuillotineDeed() - { - LootType = LootType.Blessed; - } + public GuillotineDeed(Serial serial) : base(serial) + { + } - public GuillotineDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new GuillotineAddon(); + public override int LabelNumber => 1024656; // Guillotine - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/HangingAxes.cs b/Scripts/Items/Special/Heritage Items/HangingAxes.cs index f1d5a1696..ff322f2db 100644 --- a/Scripts/Items/Special/Heritage Items/HangingAxes.cs +++ b/Scripts/Items/Special/Heritage Items/HangingAxes.cs @@ -3,126 +3,128 @@ using Server.Network; namespace Server.Items { - public class HangingAxesAddon : BaseAddon - { - public override BaseAddonDeed Deed => new HangingAxesDeed(); + public class HangingAxesAddon : BaseAddon + { + [Constructible] + public HangingAxesAddon(bool east) + { + if (east) // east + { + AddComponent(new LocalizedAddonComponent(0x156A, 1076271), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x156B, 1076271), 0, -1, 0); + } + else // south + { + AddComponent(new LocalizedAddonComponent(0x1568, 1076271), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1569, 1076271), 1, 0, 0); + } + } - [Constructible] - public HangingAxesAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new LocalizedAddonComponent( 0x156A, 1076271 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x156B, 1076271 ), 0, -1, 0 ); - } - else // south - { - AddComponent( new LocalizedAddonComponent( 0x1568, 1076271 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1569, 1076271 ), 1, 0, 0 ); - } - } + public HangingAxesAddon(Serial serial) : base(serial) + { + } - public HangingAxesAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new HangingAxesDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class HangingAxesDeed : BaseAddonDeed - { - public override BaseAddon Addon => new HangingAxesAddon( m_East ); - public override int LabelNumber => 1076271; // Hanging Axes + public class HangingAxesDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public HangingAxesDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public HangingAxesDeed() - { - LootType = LootType.Blessed; - } + public HangingAxesDeed(Serial serial) : base(serial) + { + } - public HangingAxesDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new HangingAxesAddon(m_East); + public override int LabelNumber => 1076271; // Hanging Axes - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private HangingAxesDeed m_Deed; + private class InternalGump : Gump + { + private HangingAxesDeed m_Deed; - public InternalGump( HangingAxesDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(HangingAxesDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076745, 0x7FFF, false, false ); // Please select your hanging axe position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076745, 0x7FFF, false, false); // Please select your hanging axe position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/HangingSwords.cs b/Scripts/Items/Special/Heritage Items/HangingSwords.cs index 4fc3905ce..6969722ee 100644 --- a/Scripts/Items/Special/Heritage Items/HangingSwords.cs +++ b/Scripts/Items/Special/Heritage Items/HangingSwords.cs @@ -3,126 +3,129 @@ using Server.Network; namespace Server.Items { - public class HangingSwordsAddon : BaseAddon - { - public override BaseAddonDeed Deed => new HangingSwordsDeed(); + public class HangingSwordsAddon : BaseAddon + { + [Constructible] + public HangingSwordsAddon(bool east) + { + if (east) // east + { + AddComponent(new LocalizedAddonComponent(0x1566, 1076272), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1567, 1076272), 0, -1, 0); + } + else // south + { + AddComponent(new LocalizedAddonComponent(0x1564, 1076272), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1565, 1076272), 1, 0, 0); + } + } - [Constructible] - public HangingSwordsAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new LocalizedAddonComponent( 0x1566, 1076272 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1567, 1076272 ), 0, -1, 0 ); - } - else // south - { - AddComponent( new LocalizedAddonComponent( 0x1564, 1076272 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1565, 1076272 ), 1, 0, 0 ); - } - } + public HangingSwordsAddon(Serial serial) : base(serial) + { + } - public HangingSwordsAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new HangingSwordsDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class HangingSwordsDeed : BaseAddonDeed - { - public override BaseAddon Addon => new HangingSwordsAddon( m_East ); - public override int LabelNumber => 1076272; // Hanging Swords + public class HangingSwordsDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public HangingSwordsDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public HangingSwordsDeed() - { - LootType = LootType.Blessed; - } + public HangingSwordsDeed(Serial serial) : base(serial) + { + } - public HangingSwordsDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new HangingSwordsAddon(m_East); + public override int LabelNumber => 1076272; // Hanging Swords - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private HangingSwordsDeed m_Deed; + private class InternalGump : Gump + { + private HangingSwordsDeed m_Deed; - public InternalGump( HangingSwordsDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(HangingSwordsDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076746, 0x7FFF, false, false ); // Please select your hanging sword position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076746, 0x7FFF, false, + false); // Please select your hanging sword position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/HouseLadder.cs b/Scripts/Items/Special/Heritage Items/HouseLadder.cs index 4608debb6..7fbf47927 100644 --- a/Scripts/Items/Special/Heritage Items/HouseLadder.cs +++ b/Scripts/Items/Special/Heritage Items/HouseLadder.cs @@ -3,166 +3,169 @@ using Server.Network; namespace Server.Items { - public class HouseLadderAddon : BaseAddon - { - public override BaseAddonDeed Deed => new HouseLadderDeed(); + public class HouseLadderAddon : BaseAddon + { + [Constructible] + public HouseLadderAddon(int type) + { + switch (type) + { + case 0: // castle south + AddComponent(new LocalizedAddonComponent(0x3DB2, 1076791), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3F28, 1076791), 0, 1, 28); + AddComponent(new LocalizedAddonComponent(0x3DB4, 1076791), 0, 2, 20); + break; + case 1: // castle east + AddComponent(new LocalizedAddonComponent(0x3DB3, 1076791), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3F28, 1076791), 1, 0, 28); + AddComponent(new LocalizedAddonComponent(0x3DB5, 1076791), 2, 0, 20); + break; + case 2: // castle north + AddComponent(new LocalizedAddonComponent(0x2FDF, 1076791), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3F28, 1076791), 0, -1, 28); + AddComponent(new LocalizedAddonComponent(0x3DB6, 1076791), 0, -2, 20); + break; + case 3: // castle west + AddComponent(new LocalizedAddonComponent(0x2FDE, 1076791), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x3F28, 1076791), -1, 0, 28); + AddComponent(new LocalizedAddonComponent(0x3DB7, 1076791), -2, 0, 20); + break; + case 4: // south + AddComponent(new LocalizedAddonComponent(0x3DB2, 1076287), 0, 0, 0); + break; + case 5: // east + AddComponent(new LocalizedAddonComponent(0x3DB3, 1076287), 0, 0, 0); + break; + case 6: // north + AddComponent(new LocalizedAddonComponent(0x2FDF, 1076287), 0, 0, 0); + break; + case 7: // west + AddComponent(new LocalizedAddonComponent(0x2FDE, 1076287), 0, 0, 0); + break; + } + } - [Constructible] - public HouseLadderAddon( int type ) - { - switch ( type ) - { - case 0: // castle south - AddComponent( new LocalizedAddonComponent( 0x3DB2, 1076791 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3F28, 1076791 ), 0, 1, 28 ); - AddComponent( new LocalizedAddonComponent( 0x3DB4, 1076791 ), 0, 2, 20 ); - break; - case 1: // castle east - AddComponent( new LocalizedAddonComponent( 0x3DB3, 1076791 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3F28, 1076791 ), 1, 0, 28 ); - AddComponent( new LocalizedAddonComponent( 0x3DB5, 1076791 ), 2, 0, 20 ); - break; - case 2: // castle north - AddComponent( new LocalizedAddonComponent( 0x2FDF, 1076791 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3F28, 1076791 ), 0, -1, 28 ); - AddComponent( new LocalizedAddonComponent( 0x3DB6, 1076791 ), 0, -2, 20 ); - break; - case 3: // castle west - AddComponent( new LocalizedAddonComponent( 0x2FDE, 1076791 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x3F28, 1076791 ), -1, 0, 28 ); - AddComponent( new LocalizedAddonComponent( 0x3DB7, 1076791 ), -2, 0, 20 ); - break; - case 4: // south - AddComponent( new LocalizedAddonComponent( 0x3DB2, 1076287 ), 0, 0, 0 ); - break; - case 5: // east - AddComponent( new LocalizedAddonComponent( 0x3DB3, 1076287 ), 0, 0, 0 ); - break; - case 6: // north - AddComponent( new LocalizedAddonComponent( 0x2FDF, 1076287 ), 0, 0, 0 ); - break; - case 7: // west - AddComponent( new LocalizedAddonComponent( 0x2FDE, 1076287 ), 0, 0, 0 ); - break; - } - } + public HouseLadderAddon(Serial serial) : base(serial) + { + } - public HouseLadderAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new HouseLadderDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class HouseLadderDeed : BaseAddonDeed - { - public override BaseAddon Addon => new HouseLadderAddon( m_Type ); - public override int LabelNumber => 1076287; // Ladder + public class HouseLadderDeed : BaseAddonDeed + { + private int m_Type; - private int m_Type; + [Constructible] + public HouseLadderDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public HouseLadderDeed() - { - LootType = LootType.Blessed; - } + public HouseLadderDeed(Serial serial) : base(serial) + { + } - public HouseLadderDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new HouseLadderAddon(m_Type); + public override int LabelNumber => 1076287; // Ladder - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private HouseLadderDeed m_Deed; + private class InternalGump : Gump + { + private HouseLadderDeed m_Deed; - public InternalGump( HouseLadderDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(HouseLadderDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076780, 0x7FFF, false, false ); // Please select your ladder position.
Use the ladders marked (castle)
for accessing the tops of keeps
and castles. + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076780, 0x7FFF, false, + false); // Please select your ladder position.
Use the ladders marked (castle)
for accessing the tops of keeps
and castles. - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1076794, 0x7FFF, false, false ); // South (Castle) - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1076795, 0x7FFF, false, false ); // East (Castle) - AddButton( 19, 97, 0x845, 0x846, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 95, 213, 20, 1076792, 0x7FFF, false, false ); // North (Castle) - AddButton( 19, 121, 0x845, 0x846, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 119, 213, 20, 1076793, 0x7FFF, false, false ); // West (Castle) - AddButton( 19, 145, 0x845, 0x846, 5, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 143, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 169, 0x845, 0x846, 6, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 167, 213, 20, 1075387, 0x7FFF, false, false ); // East - AddButton( 19, 193, 0x845, 0x846, 7, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 191, 213, 20, 1075389, 0x7FFF, false, false ); // North - AddButton( 19, 217, 0x845, 0x846, 8, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 215, 213, 20, 1075390, 0x7FFF, false, false ); // West - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1076794, 0x7FFF, false, false); // South (Castle) + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1076795, 0x7FFF, false, false); // East (Castle) + AddButton(19, 97, 0x845, 0x846, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 95, 213, 20, 1076792, 0x7FFF, false, false); // North (Castle) + AddButton(19, 121, 0x845, 0x846, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 119, 213, 20, 1076793, 0x7FFF, false, false); // West (Castle) + AddButton(19, 145, 0x845, 0x846, 5, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 143, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 169, 0x845, 0x846, 6, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 167, 213, 20, 1075387, 0x7FFF, false, false); // East + AddButton(19, 193, 0x845, 0x846, 7, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 191, 213, 20, 1075389, 0x7FFF, false, false); // North + AddButton(19, 217, 0x845, 0x846, 8, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 215, 213, 20, 1075390, 0x7FFF, false, false); // West + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - if ( info.ButtonID >= 1 && info.ButtonID <= 8 ) - { - m_Deed.m_Type = info.ButtonID - 1; - m_Deed.SendTarget( sender.Mobile ); - } - } - } - } -} + if (info.ButtonID >= 1 && info.ButtonID <= 8) + { + m_Deed.m_Type = info.ButtonID - 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/IronMaiden.cs b/Scripts/Items/Special/Heritage Items/IronMaiden.cs index 43ece53e5..023909312 100644 --- a/Scripts/Items/Special/Heritage Items/IronMaiden.cs +++ b/Scripts/Items/Special/Heritage Items/IronMaiden.cs @@ -1,135 +1,142 @@ using System; -using Server.Spells; using Server.Network; +using Server.Spells; namespace Server.Items { - public class IronMaidenAddon : BaseAddon - { - public override BaseAddonDeed Deed => new IronMaidenDeed(); + public class IronMaidenAddon : BaseAddon + { + public IronMaidenAddon() + { + AddComponent(new LocalizedAddonComponent(0x1249, 1076288), 0, 0, 0); + } - public IronMaidenAddon() - { - AddComponent( new LocalizedAddonComponent( 0x1249, 1076288 ), 0, 0, 0 ); - } + public IronMaidenAddon(Serial serial) : base(serial) + { + } - public IronMaidenAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new IronMaidenDeed(); - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) && from.InLOS( GetWorldLocation() ) ) - { - if ( Utility.RandomBool() ) - { - from.Location = Location; - c.ItemID = 0x124A; + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (from.InRange(GetWorldLocation(), 2) && from.InLOS(GetWorldLocation())) + { + if (Utility.RandomBool()) + { + from.Location = Location; + c.ItemID = 0x124A; - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ), 3, new TimerStateCallback( Activate ), new object[] { c, from } ); - } - else - from.LocalOverheadMessage( MessageType.Regular, 0, 501777 ); // Hmm... you suspect that if you used this again, it might hurt. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5), 3, + new TimerStateCallback(Activate), new object[] { c, from }); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0, + 501777); // Hmm... you suspect that if you used this again, it might hurt. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private void Activate( object obj ) - { - object[] param = (object[]) obj; + private void Activate(object obj) + { + object[] param = (object[])obj; - if ( param[ 0 ] is AddonComponent component && param[ 1 ] is Mobile mobile ) - Activate( component, mobile ); - } + if (param[0] is AddonComponent component && param[1] is Mobile mobile) + Activate(component, mobile); + } - public virtual void Activate( AddonComponent c, Mobile from ) - { - c.ItemID += 1; + public virtual void Activate(AddonComponent c, Mobile from) + { + c.ItemID += 1; - if ( c.ItemID >= 0x124D ) - { - // blood - int amount = Utility.RandomMinMax( 3, 7 ); + if (c.ItemID >= 0x124D) + { + // blood + int amount = Utility.RandomMinMax(3, 7); - for ( int i = 0; i < amount; i++ ) - { - int x = c.X + Utility.RandomMinMax( -1, 1 ); - int y = c.Y + Utility.RandomMinMax( -1, 1 ); - int z = c.Z; + for (int i = 0; i < amount; i++) + { + int x = c.X + Utility.RandomMinMax(-1, 1); + int y = c.Y + Utility.RandomMinMax(-1, 1); + int z = c.Z; - if ( !c.Map.CanFit( x, y, z, 1, false, false, true ) ) - { - z = c.Map.GetAverageZ( x, y ); + if (!c.Map.CanFit(x, y, z, 1, false, false, true)) + { + z = c.Map.GetAverageZ(x, y); - if ( !c.Map.CanFit( x, y, z, 1, false, false, true ) ) - continue; - } + if (!c.Map.CanFit(x, y, z, 1, false, false, true)) + continue; + } - Blood blood = new Blood( Utility.RandomMinMax( 0x122C, 0x122F ) ); - blood.MoveToWorld( new Point3D( x, y, z ), c.Map ); - } + Blood blood = new Blood(Utility.RandomMinMax(0x122C, 0x122F)); + blood.MoveToWorld(new Point3D(x, y, z), c.Map); + } - if ( from.Female ) - from.PlaySound( Utility.RandomMinMax( 0x150, 0x153 ) ); - else - from.PlaySound( Utility.RandomMinMax( 0x15A, 0x15D ) ); + if (from.Female) + from.PlaySound(Utility.RandomMinMax(0x150, 0x153)); + else + from.PlaySound(Utility.RandomMinMax(0x15A, 0x15D)); - from.LocalOverheadMessage( MessageType.Regular, 0, 501777 ); // Hmm... you suspect that if you used this again, it might hurt. - SpellHelper.Damage( TimeSpan.Zero, from, Utility.Dice( 2, 10, 5 ) ); + from.LocalOverheadMessage(MessageType.Regular, 0, + 501777); // Hmm... you suspect that if you used this again, it might hurt. + SpellHelper.Damage(TimeSpan.Zero, from, Utility.Dice(2, 10, 5)); - Timer.DelayCall( TimeSpan.FromSeconds( 1 ), new TimerStateCallback( Deactivate ), c ); - } - } + Timer.DelayCall(TimeSpan.FromSeconds(1), new TimerStateCallback(Deactivate), c); + } + } - private void Deactivate( object obj ) - { - if ( obj is AddonComponent component ) - component.ItemID = 0x1249; - } - } + private void Deactivate(object obj) + { + if (obj is AddonComponent component) + component.ItemID = 0x1249; + } + } - public class IronMaidenDeed : BaseAddonDeed - { - public override BaseAddon Addon => new IronMaidenAddon(); - public override int LabelNumber => 1076288; // Iron Maiden + public class IronMaidenDeed : BaseAddonDeed + { + [Constructible] + public IronMaidenDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public IronMaidenDeed() - { - LootType = LootType.Blessed; - } + public IronMaidenDeed(Serial serial) : base(serial) + { + } - public IronMaidenDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new IronMaidenAddon(); + public override int LabelNumber => 1076288; // Iron Maiden - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/LargeFishingNet.cs b/Scripts/Items/Special/Heritage Items/LargeFishingNet.cs index c4a3d8ed6..69f60ac75 100644 --- a/Scripts/Items/Special/Heritage Items/LargeFishingNet.cs +++ b/Scripts/Items/Special/Heritage Items/LargeFishingNet.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0x3D8E, 0x3D8F )] - public class LargeFishingNetComponent : AddonComponent - { - public override int LabelNumber => 1076285; // Large Fish Net + [Flippable(0x3D8E, 0x3D8F)] + public class LargeFishingNetComponent : AddonComponent + { + public LargeFishingNetComponent() : base(0x3D8E) + { + } - public LargeFishingNetComponent() : base( 0x3D8E ) - { - } + public LargeFishingNetComponent(Serial serial) : base(serial) + { + } - public LargeFishingNetComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076285; // Large Fish Net - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LargeFishingNetAddon : BaseAddon - { - public override BaseAddonDeed Deed => new LargeFishingNetDeed(); + public class LargeFishingNetAddon : BaseAddon + { + [Constructible] + public LargeFishingNetAddon() + { + AddComponent(new LargeFishingNetComponent(), 0, 0, 0); + } - [Constructible] - public LargeFishingNetAddon() - { - AddComponent( new LargeFishingNetComponent(), 0, 0, 0 ); - } + public LargeFishingNetAddon(Serial serial) : base(serial) + { + } - public LargeFishingNetAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new LargeFishingNetDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class LargeFishingNetDeed : BaseAddonDeed - { - public override BaseAddon Addon => new LargeFishingNetAddon(); - public override int LabelNumber => 1076285; // Large Fish Net + public class LargeFishingNetDeed : BaseAddonDeed + { + [Constructible] + public LargeFishingNetDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public LargeFishingNetDeed() - { - LootType = LootType.Blessed; - } + public LargeFishingNetDeed(Serial serial) : base(serial) + { + } - public LargeFishingNetDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new LargeFishingNetAddon(); + public override int LabelNumber => 1076285; // Large Fish Net - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/PeachTrunk.cs b/Scripts/Items/Special/Heritage Items/PeachTrunk.cs index c18eb0523..a5c40976d 100644 --- a/Scripts/Items/Special/Heritage Items/PeachTrunk.cs +++ b/Scripts/Items/Special/Heritage Items/PeachTrunk.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class PeachTrunkAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PeachTrunkDeed(); + public class PeachTrunkAddon : BaseAddon + { + [Constructible] + public PeachTrunkAddon() + { + AddComponent(new LocalizedAddonComponent(0xD9C, 1076786), 0, 0, 0); + } - [Constructible] - public PeachTrunkAddon() - { - AddComponent( new LocalizedAddonComponent( 0xD9C, 1076786 ), 0, 0, 0 ); - } + public PeachTrunkAddon(Serial serial) : base(serial) + { + } - public PeachTrunkAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PeachTrunkDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class PeachTrunkDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PeachTrunkAddon(); - public override int LabelNumber => 1076786; // Peach Trunk + public class PeachTrunkDeed : BaseAddonDeed + { + [Constructible] + public PeachTrunkDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public PeachTrunkDeed() - { - LootType = LootType.Blessed; - } + public PeachTrunkDeed(Serial serial) : base(serial) + { + } - public PeachTrunkDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PeachTrunkAddon(); + public override int LabelNumber => 1076786; // Peach Trunk - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/PinkFancyRug.cs b/Scripts/Items/Special/Heritage Items/PinkFancyRug.cs index 47657681a..2ca208d0b 100644 --- a/Scripts/Items/Special/Heritage Items/PinkFancyRug.cs +++ b/Scripts/Items/Special/Heritage Items/PinkFancyRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class PinkFancyRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new PinkFancyRugDeed(); + public class PinkFancyRugAddon : BaseAddon + { + [Constructible] + public PinkFancyRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xAEE, 1076590), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAEF, 1076590), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF0, 1076590), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAF1, 1076590), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF2, 1076590), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAF3, 1076590), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xAF4, 1076590), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAF5, 1076590), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAEC, 1076590), 0, 0, 0); + } - [Constructible] - public PinkFancyRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xAEE, 1076590 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAEF, 1076590 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF0, 1076590 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF1, 1076590 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF2, 1076590 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF3, 1076590 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF4, 1076590 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAF5, 1076590 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAEC, 1076590 ), 0, 0, 0 ); - } + public PinkFancyRugAddon(Serial serial) : base(serial) + { + } - public PinkFancyRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new PinkFancyRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class PinkFancyRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new PinkFancyRugAddon(); - public override int LabelNumber => 1076590; // Pink fancy rug + public class PinkFancyRugDeed : BaseAddonDeed + { + [Constructible] + public PinkFancyRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public PinkFancyRugDeed() - { - LootType = LootType.Blessed; - } + public PinkFancyRugDeed(Serial serial) : base(serial) + { + } - public PinkFancyRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new PinkFancyRugAddon(); + public override int LabelNumber => 1076590; // Pink fancy rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/RedPlainRug.cs b/Scripts/Items/Special/Heritage Items/RedPlainRug.cs index 398c64b94..5ae76630e 100644 --- a/Scripts/Items/Special/Heritage Items/RedPlainRug.cs +++ b/Scripts/Items/Special/Heritage Items/RedPlainRug.cs @@ -1,69 +1,69 @@ namespace Server.Items { - public class RedPlainRugAddon : BaseAddon - { - public override BaseAddonDeed Deed => new RedPlainRugDeed(); + public class RedPlainRugAddon : BaseAddon + { + [Constructible] + public RedPlainRugAddon() + { + AddComponent(new LocalizedAddonComponent(0xAC9, 1076588), 1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xACA, 1076588), -1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xACB, 1076588), -1, 1, 0); + AddComponent(new LocalizedAddonComponent(0xACC, 1076588), 1, -1, 0); + AddComponent(new LocalizedAddonComponent(0xACD, 1076588), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xACE, 1076588), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xACF, 1076588), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xAD0, 1076588), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0xAC6, 1076588), 0, 0, 0); + } - [Constructible] - public RedPlainRugAddon() - { - AddComponent( new LocalizedAddonComponent( 0xAC9, 1076588 ), 1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xACA, 1076588 ), -1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xACB, 1076588 ), -1, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xACC, 1076588 ), 1, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xACD, 1076588 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xACE, 1076588 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xACF, 1076588 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAD0, 1076588 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xAC6, 1076588 ), 0, 0, 0 ); - } + public RedPlainRugAddon(Serial serial) : base(serial) + { + } - public RedPlainRugAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new RedPlainRugDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class RedPlainRugDeed : BaseAddonDeed - { - public override BaseAddon Addon => new RedPlainRugAddon(); - public override int LabelNumber => 1076588; // Red plain rug + public class RedPlainRugDeed : BaseAddonDeed + { + [Constructible] + public RedPlainRugDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public RedPlainRugDeed() - { - LootType = LootType.Blessed; - } + public RedPlainRugDeed(Serial serial) : base(serial) + { + } - public RedPlainRugDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new RedPlainRugAddon(); + public override int LabelNumber => 1076588; // Red plain rug - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/Scarecrow.cs b/Scripts/Items/Special/Heritage Items/Scarecrow.cs index 1e3057176..95c4b17b6 100644 --- a/Scripts/Items/Special/Heritage Items/Scarecrow.cs +++ b/Scripts/Items/Special/Heritage Items/Scarecrow.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0x1E34, 0x1E35 )] - public class ScarecrowComponent : AddonComponent - { - public override int LabelNumber => 1076608; // Scarecrow + [Flippable(0x1E34, 0x1E35)] + public class ScarecrowComponent : AddonComponent + { + public ScarecrowComponent() : base(0x1E34) + { + } - public ScarecrowComponent() : base( 0x1E34 ) - { - } + public ScarecrowComponent(Serial serial) : base(serial) + { + } - public ScarecrowComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076608; // Scarecrow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ScarecrowAddon : BaseAddon - { - public override BaseAddonDeed Deed => new ScarecrowDeed(); + public class ScarecrowAddon : BaseAddon + { + [Constructible] + public ScarecrowAddon() + { + AddComponent(new ScarecrowComponent(), 0, 0, 0); + } - [Constructible] - public ScarecrowAddon() - { - AddComponent( new ScarecrowComponent(), 0, 0, 0 ); - } + public ScarecrowAddon(Serial serial) : base(serial) + { + } - public ScarecrowAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new ScarecrowDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class ScarecrowDeed : BaseAddonDeed - { - public override BaseAddon Addon => new ScarecrowAddon(); - public override int LabelNumber => 1076608; // Scarecrow + public class ScarecrowDeed : BaseAddonDeed + { + [Constructible] + public ScarecrowDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public ScarecrowDeed() - { - LootType = LootType.Blessed; - } + public ScarecrowDeed(Serial serial) : base(serial) + { + } - public ScarecrowDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new ScarecrowAddon(); + public override int LabelNumber => 1076608; // Scarecrow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/SmallFishingNet.cs b/Scripts/Items/Special/Heritage Items/SmallFishingNet.cs index b5b92bfc2..84c4c5b81 100644 --- a/Scripts/Items/Special/Heritage Items/SmallFishingNet.cs +++ b/Scripts/Items/Special/Heritage Items/SmallFishingNet.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0x1EA3, 0x1EA4 )] - public class SmallFishingNetComponent : AddonComponent - { - public override int LabelNumber => 1076286; // Small Fish Net + [Flippable(0x1EA3, 0x1EA4)] + public class SmallFishingNetComponent : AddonComponent + { + public SmallFishingNetComponent() : base(0x1EA3) + { + } - public SmallFishingNetComponent() : base( 0x1EA3 ) - { - } + public SmallFishingNetComponent(Serial serial) : base(serial) + { + } - public SmallFishingNetComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076286; // Small Fish Net - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SmallFishingNetAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SmallFishingNetDeed(); + public class SmallFishingNetAddon : BaseAddon + { + [Constructible] + public SmallFishingNetAddon() + { + AddComponent(new SmallFishingNetComponent(), 0, 0, 0); + } - [Constructible] - public SmallFishingNetAddon() - { - AddComponent( new SmallFishingNetComponent(), 0, 0, 0 ); - } + public SmallFishingNetAddon(Serial serial) : base(serial) + { + } - public SmallFishingNetAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SmallFishingNetDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SmallFishingNetDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SmallFishingNetAddon(); - public override int LabelNumber => 1076286; // Small Fish Net + public class SmallFishingNetDeed : BaseAddonDeed + { + [Constructible] + public SmallFishingNetDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public SmallFishingNetDeed() - { - LootType = LootType.Blessed; - } + public SmallFishingNetDeed(Serial serial) : base(serial) + { + } - public SmallFishingNetDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SmallFishingNetAddon(); + public override int LabelNumber => 1076286; // Small Fish Net - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/Statue.cs b/Scripts/Items/Special/Heritage Items/Statue.cs index e68e2fc1e..829e04735 100644 --- a/Scripts/Items/Special/Heritage Items/Statue.cs +++ b/Scripts/Items/Special/Heritage Items/Statue.cs @@ -3,128 +3,130 @@ using Server.Network; namespace Server.Items { - public class StoneStatueAddon : BaseAddon - { - public override BaseAddonDeed Deed => new StoneStatueDeed(); + public class StoneStatueAddon : BaseAddon + { + [Constructible] + public StoneStatueAddon(bool east) + { + if (east) // east + { + AddComponent(new LocalizedAddonComponent(0x139E, 1076284), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x139F, 1076284), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0x13A0, 1076284), 0, -1, 0); + } + else // south + { + AddComponent(new LocalizedAddonComponent(0x129F, 1076284), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x12A0, 1076284), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0x12A1, 1076284), -1, 0, 0); + } + } - [Constructible] - public StoneStatueAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new LocalizedAddonComponent( 0x139E, 1076284 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x139F, 1076284 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x13A0, 1076284 ), 0, -1, 0 ); - } - else // south - { - AddComponent( new LocalizedAddonComponent( 0x129F, 1076284 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x12A0, 1076284 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0x12A1, 1076284 ), -1, 0, 0 ); - } - } + public StoneStatueAddon(Serial serial) : base(serial) + { + } - public StoneStatueAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new StoneStatueDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class StoneStatueDeed : BaseAddonDeed - { - public override BaseAddon Addon => new StoneStatueAddon( m_East ); - public override int LabelNumber => 1076284; // Statue + public class StoneStatueDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public StoneStatueDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public StoneStatueDeed() - { - LootType = LootType.Blessed; - } + public StoneStatueDeed(Serial serial) : base(serial) + { + } - public StoneStatueDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new StoneStatueAddon(m_East); + public override int LabelNumber => 1076284; // Statue - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private StoneStatueDeed m_Deed; + private class InternalGump : Gump + { + private StoneStatueDeed m_Deed; - public InternalGump( StoneStatueDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(StoneStatueDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076579, 0x7FFF, false, false ); // Please select your statue position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076579, 0x7FFF, false, false); // Please select your statue position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/SuitOfGoldArmor.cs b/Scripts/Items/Special/Heritage Items/SuitOfGoldArmor.cs index 430c8044a..4f361aac1 100644 --- a/Scripts/Items/Special/Heritage Items/SuitOfGoldArmor.cs +++ b/Scripts/Items/Special/Heritage Items/SuitOfGoldArmor.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0x3DAA, 0x3DA9 )] - public class SuitOfGoldArmorComponent : AddonComponent - { - public override int LabelNumber => 1076265; // Suit of Gold Armor + [Flippable(0x3DAA, 0x3DA9)] + public class SuitOfGoldArmorComponent : AddonComponent + { + public SuitOfGoldArmorComponent() : base(0x3DAA) + { + } - public SuitOfGoldArmorComponent() : base( 0x3DAA ) - { - } + public SuitOfGoldArmorComponent(Serial serial) : base(serial) + { + } - public SuitOfGoldArmorComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076265; // Suit of Gold Armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SuitOfGoldArmorAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SuitOfGoldArmorDeed(); + public class SuitOfGoldArmorAddon : BaseAddon + { + [Constructible] + public SuitOfGoldArmorAddon() + { + AddComponent(new SuitOfGoldArmorComponent(), 0, 0, 0); + } - [Constructible] - public SuitOfGoldArmorAddon() - { - AddComponent( new SuitOfGoldArmorComponent(), 0, 0, 0 ); - } + public SuitOfGoldArmorAddon(Serial serial) : base(serial) + { + } - public SuitOfGoldArmorAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SuitOfGoldArmorDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SuitOfGoldArmorDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SuitOfGoldArmorAddon(); - public override int LabelNumber => 1076265; // Suit of Gold Armor + public class SuitOfGoldArmorDeed : BaseAddonDeed + { + [Constructible] + public SuitOfGoldArmorDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public SuitOfGoldArmorDeed() - { - LootType = LootType.Blessed; - } + public SuitOfGoldArmorDeed(Serial serial) : base(serial) + { + } - public SuitOfGoldArmorDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SuitOfGoldArmorAddon(); + public override int LabelNumber => 1076265; // Suit of Gold Armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/SuitOfSilverArmor.cs b/Scripts/Items/Special/Heritage Items/SuitOfSilverArmor.cs index 88550c8cf..6eaf4ee7d 100644 --- a/Scripts/Items/Special/Heritage Items/SuitOfSilverArmor.cs +++ b/Scripts/Items/Special/Heritage Items/SuitOfSilverArmor.cs @@ -1,89 +1,89 @@ namespace Server.Items { - [Flippable( 0x3D86, 0x3D87 )] - public class SuitOfSilverArmorComponent : AddonComponent - { - public override int LabelNumber => 1076266; // Suit of Silver Armor + [Flippable(0x3D86, 0x3D87)] + public class SuitOfSilverArmorComponent : AddonComponent + { + public SuitOfSilverArmorComponent() : base(0x3D86) + { + } - public SuitOfSilverArmorComponent() : base( 0x3D86 ) - { - } + public SuitOfSilverArmorComponent(Serial serial) : base(serial) + { + } - public SuitOfSilverArmorComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076266; // Suit of Silver Armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SuitOfSilverArmorAddon : BaseAddon - { - public override BaseAddonDeed Deed => new SuitOfSilverArmorDeed(); + public class SuitOfSilverArmorAddon : BaseAddon + { + [Constructible] + public SuitOfSilverArmorAddon() + { + AddComponent(new SuitOfSilverArmorComponent(), 0, 0, 0); + } - [Constructible] - public SuitOfSilverArmorAddon() - { - AddComponent( new SuitOfSilverArmorComponent(), 0, 0, 0 ); - } + public SuitOfSilverArmorAddon(Serial serial) : base(serial) + { + } - public SuitOfSilverArmorAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new SuitOfSilverArmorDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SuitOfSilverArmorDeed : BaseAddonDeed - { - public override BaseAddon Addon => new SuitOfSilverArmorAddon(); - public override int LabelNumber => 1076266; // Suit of Silver Armor + public class SuitOfSilverArmorDeed : BaseAddonDeed + { + [Constructible] + public SuitOfSilverArmorDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public SuitOfSilverArmorDeed() - { - LootType = LootType.Blessed; - } + public SuitOfSilverArmorDeed(Serial serial) : base(serial) + { + } - public SuitOfSilverArmorDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new SuitOfSilverArmorAddon(); + public override int LabelNumber => 1076266; // Suit of Silver Armor - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/TableWithBlueCloth.cs b/Scripts/Items/Special/Heritage Items/TableWithBlueCloth.cs index aee3c7075..547713e3c 100644 --- a/Scripts/Items/Special/Heritage Items/TableWithBlueCloth.cs +++ b/Scripts/Items/Special/Heritage Items/TableWithBlueCloth.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class TableWithBlueClothAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TableWithBlueClothDeed(); + public class TableWithBlueClothAddon : BaseAddon + { + [Constructible] + public TableWithBlueClothAddon() + { + AddComponent(new LocalizedAddonComponent(0x118C, 1076276), 0, 0, 0); + } - [Constructible] - public TableWithBlueClothAddon() - { - AddComponent( new LocalizedAddonComponent( 0x118C, 1076276 ), 0, 0, 0 ); - } + public TableWithBlueClothAddon(Serial serial) : base(serial) + { + } - public TableWithBlueClothAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TableWithBlueClothDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class TableWithBlueClothDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TableWithBlueClothAddon(); - public override int LabelNumber => 1076276; // Table With A Blue Tablecloth + public class TableWithBlueClothDeed : BaseAddonDeed + { + [Constructible] + public TableWithBlueClothDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public TableWithBlueClothDeed() - { - LootType = LootType.Blessed; - } + public TableWithBlueClothDeed(Serial serial) : base(serial) + { + } - public TableWithBlueClothDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TableWithBlueClothAddon(); + public override int LabelNumber => 1076276; // Table With A Blue Tablecloth - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/TableWithOrangeCloth.cs b/Scripts/Items/Special/Heritage Items/TableWithOrangeCloth.cs index 91a19a35b..e2b6820b3 100644 --- a/Scripts/Items/Special/Heritage Items/TableWithOrangeCloth.cs +++ b/Scripts/Items/Special/Heritage Items/TableWithOrangeCloth.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class TableWithOrangeClothAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TableWithOrangeClothDeed(); + public class TableWithOrangeClothAddon : BaseAddon + { + [Constructible] + public TableWithOrangeClothAddon() + { + AddComponent(new LocalizedAddonComponent(0x118E, 1076278), 0, 0, 0); + } - [Constructible] - public TableWithOrangeClothAddon() - { - AddComponent( new LocalizedAddonComponent( 0x118E, 1076278 ), 0, 0, 0 ); - } + public TableWithOrangeClothAddon(Serial serial) : base(serial) + { + } - public TableWithOrangeClothAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TableWithOrangeClothDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class TableWithOrangeClothDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TableWithOrangeClothAddon(); - public override int LabelNumber => 1076278; // Table With An Orange Tablecloth + public class TableWithOrangeClothDeed : BaseAddonDeed + { + [Constructible] + public TableWithOrangeClothDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public TableWithOrangeClothDeed() - { - LootType = LootType.Blessed; - } + public TableWithOrangeClothDeed(Serial serial) : base(serial) + { + } - public TableWithOrangeClothDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TableWithOrangeClothAddon(); + public override int LabelNumber => 1076278; // Table With An Orange Tablecloth - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/TableWithPurpleCloth.cs b/Scripts/Items/Special/Heritage Items/TableWithPurpleCloth.cs index 5737c56e3..ebdb22702 100644 --- a/Scripts/Items/Special/Heritage Items/TableWithPurpleCloth.cs +++ b/Scripts/Items/Special/Heritage Items/TableWithPurpleCloth.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class TableWithPurpleClothAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TableWithPurpleClothDeed(); + public class TableWithPurpleClothAddon : BaseAddon + { + [Constructible] + public TableWithPurpleClothAddon() + { + AddComponent(new LocalizedAddonComponent(0x118B, 1076275), 0, 0, 0); + } - [Constructible] - public TableWithPurpleClothAddon() - { - AddComponent( new LocalizedAddonComponent( 0x118B, 1076275 ), 0, 0, 0 ); - } + public TableWithPurpleClothAddon(Serial serial) : base(serial) + { + } - public TableWithPurpleClothAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TableWithPurpleClothDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class TableWithPurpleClothDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TableWithPurpleClothAddon(); - public override int LabelNumber => 1076275; // Table With A Purple Tablecloth + public class TableWithPurpleClothDeed : BaseAddonDeed + { + [Constructible] + public TableWithPurpleClothDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public TableWithPurpleClothDeed() - { - LootType = LootType.Blessed; - } + public TableWithPurpleClothDeed(Serial serial) : base(serial) + { + } - public TableWithPurpleClothDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TableWithPurpleClothAddon(); + public override int LabelNumber => 1076275; // Table With A Purple Tablecloth - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/TableWithRedCloth.cs b/Scripts/Items/Special/Heritage Items/TableWithRedCloth.cs index 35d526028..3a3d2ac9c 100644 --- a/Scripts/Items/Special/Heritage Items/TableWithRedCloth.cs +++ b/Scripts/Items/Special/Heritage Items/TableWithRedCloth.cs @@ -1,61 +1,61 @@ namespace Server.Items { - public class TableWithRedClothAddon : BaseAddon - { - public override BaseAddonDeed Deed => new TableWithRedClothDeed(); + public class TableWithRedClothAddon : BaseAddon + { + [Constructible] + public TableWithRedClothAddon() + { + AddComponent(new LocalizedAddonComponent(0x118D, 1076277), 0, 0, 0); + } - [Constructible] - public TableWithRedClothAddon() - { - AddComponent( new LocalizedAddonComponent( 0x118D, 1076277 ), 0, 0, 0 ); - } + public TableWithRedClothAddon(Serial serial) : base(serial) + { + } - public TableWithRedClothAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new TableWithRedClothDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class TableWithRedClothDeed : BaseAddonDeed - { - public override BaseAddon Addon => new TableWithRedClothAddon(); - public override int LabelNumber => 1076277; // Table With A Red Tablecloth + public class TableWithRedClothDeed : BaseAddonDeed + { + [Constructible] + public TableWithRedClothDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public TableWithRedClothDeed() - { - LootType = LootType.Blessed; - } + public TableWithRedClothDeed(Serial serial) : base(serial) + { + } - public TableWithRedClothDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new TableWithRedClothAddon(); + public override int LabelNumber => 1076277; // Table With A Red Tablecloth - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/UnmadeBed.cs b/Scripts/Items/Special/Heritage Items/UnmadeBed.cs index 6259a2075..0f1d4c785 100644 --- a/Scripts/Items/Special/Heritage Items/UnmadeBed.cs +++ b/Scripts/Items/Special/Heritage Items/UnmadeBed.cs @@ -3,130 +3,132 @@ using Server.Network; namespace Server.Items { - public class UnmadeBedAddon : BaseAddon - { - public override BaseAddonDeed Deed => new UnmadeBedDeed(); + public class UnmadeBedAddon : BaseAddon + { + [Constructible] + public UnmadeBedAddon(bool east) + { + if (east) // east + { + AddComponent(new LocalizedAddonComponent(0xA8C, 1076279), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0xA8D, 1076279), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xA90, 1076279), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xA91, 1076279), -1, -1, 0); + } + else // south + { + AddComponent(new LocalizedAddonComponent(0xDB0, 1076279), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0xDB1, 1076279), -1, 0, 0); + AddComponent(new LocalizedAddonComponent(0xDB4, 1076279), 0, -1, 0); + AddComponent(new LocalizedAddonComponent(0xDB5, 1076279), -1, -1, 0); + } + } - [Constructible] - public UnmadeBedAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new LocalizedAddonComponent( 0xA8C, 1076279 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xA8D, 1076279 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xA90, 1076279 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xA91, 1076279 ), -1, -1, 0 ); - } - else // south - { - AddComponent( new LocalizedAddonComponent( 0xDB0, 1076279 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xDB1, 1076279 ), -1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0xDB4, 1076279 ), 0, -1, 0 ); - AddComponent( new LocalizedAddonComponent( 0xDB5, 1076279 ), -1, -1, 0 ); - } - } + public UnmadeBedAddon(Serial serial) : base(serial) + { + } - public UnmadeBedAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new UnmadeBedDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class UnmadeBedDeed : BaseAddonDeed - { - public override BaseAddon Addon => new UnmadeBedAddon( m_East ); - public override int LabelNumber => 1076279; // Unmade Bed + public class UnmadeBedDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public UnmadeBedDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public UnmadeBedDeed() - { - LootType = LootType.Blessed; - } + public UnmadeBedDeed(Serial serial) : base(serial) + { + } - public UnmadeBedDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new UnmadeBedAddon(m_East); + public override int LabelNumber => 1076279; // Unmade Bed - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private UnmadeBedDeed m_Deed; + private class InternalGump : Gump + { + private UnmadeBedDeed m_Deed; - public InternalGump( UnmadeBedDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(UnmadeBedDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076580, 0x7FFF, false, false ); // Pleae select your unmade bed position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076580, 0x7FFF, false, false); // Pleae select your unmade bed position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/Vanity.cs b/Scripts/Items/Special/Heritage Items/Vanity.cs index a5228b5be..c61bb25f0 100644 --- a/Scripts/Items/Special/Heritage Items/Vanity.cs +++ b/Scripts/Items/Special/Heritage Items/Vanity.cs @@ -3,127 +3,125 @@ using Server.Network; namespace Server.Items { - public class VanityAddon : BaseAddonContainer - { - public override BaseAddonContainerDeed Deed => new VanityDeed(); - public override int LabelNumber => 1074027; // Vanity - public override int DefaultGumpID => 0x51; - public override int DefaultDropSound => 0x42; + public class VanityAddon : BaseAddonContainer + { + [Constructible] + public VanityAddon(bool east) : base(east ? 0xA44 : 0xA3C) + { + if (east) // east + AddComponent(new AddonContainerComponent(0xA45), 0, -1, 0); + else // south + AddComponent(new AddonContainerComponent(0xA3D), -1, 0, 0); + } - [Constructible] - public VanityAddon( bool east ) : base( east ? 0xA44 : 0xA3C ) - { - if ( east ) // east - { - AddComponent( new AddonContainerComponent( 0xA45 ), 0, -1, 0 ); - } - else // south - { - AddComponent( new AddonContainerComponent( 0xA3D ), -1, 0, 0 ); - } - } + public VanityAddon(Serial serial) : base(serial) + { + } - public VanityAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonContainerDeed Deed => new VanityDeed(); + public override int LabelNumber => 1074027; // Vanity + public override int DefaultGumpID => 0x51; + public override int DefaultDropSound => 0x42; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class VanityDeed : BaseAddonContainerDeed - { - public override BaseAddonContainer Addon => new VanityAddon( m_East ); - public override int LabelNumber => 1074027; // Vanity + public class VanityDeed : BaseAddonContainerDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public VanityDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public VanityDeed() - { - LootType = LootType.Blessed; - } + public VanityDeed(Serial serial) : base(serial) + { + } - public VanityDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddonContainer Addon => new VanityAddon(m_East); + public override int LabelNumber => 1074027; // Vanity - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private VanityDeed m_Deed; + private class InternalGump : Gump + { + private VanityDeed m_Deed; - public InternalGump( VanityDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(VanityDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076744, 0x7FFF, false, false ); // Please select your vanity position. + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076744, 0x7FFF, false, false); // Please select your vanity position. - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/WallTorch.cs b/Scripts/Items/Special/Heritage Items/WallTorch.cs index bc1802f75..d4c26a8c6 100644 --- a/Scripts/Items/Special/Heritage Items/WallTorch.cs +++ b/Scripts/Items/Special/Heritage Items/WallTorch.cs @@ -2,108 +2,118 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x3D98, 0x3D94 )] - public class WallTorchComponent : AddonComponent - { - public override int LabelNumber => 1076282; // Wall Torch + [Flippable(0x3D98, 0x3D94)] + public class WallTorchComponent : AddonComponent + { + public WallTorchComponent() : base(0x3D98) + { + } - public WallTorchComponent() : base( 0x3D98 ) - { - } + public WallTorchComponent(Serial serial) : base(serial) + { + } - public WallTorchComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076282; // Wall Torch - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - switch ( ItemID ) - { - case 0x3D98: ItemID = 0x3D9B; break; - case 0x3D9B: ItemID = 0x3D98; break; - case 0x3D94: ItemID = 0x3D97; break; - case 0x3D97: ItemID = 0x3D94; break; - } + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(Location, 2)) + { + switch (ItemID) + { + case 0x3D98: + ItemID = 0x3D9B; + break; + case 0x3D9B: + ItemID = 0x3D98; + break; + case 0x3D94: + ItemID = 0x3D97; + break; + case 0x3D97: + ItemID = 0x3D94; + break; + } - Effects.PlaySound( Location, Map, 0x3BE ); - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + Effects.PlaySound(Location, Map, 0x3BE); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WallTorchAddon : BaseAddon - { - public override BaseAddonDeed Deed => new WallTorchDeed(); + public class WallTorchAddon : BaseAddon + { + public WallTorchAddon() + { + AddComponent(new WallTorchComponent(), 0, 0, 0); + } - public WallTorchAddon() - { - AddComponent( new WallTorchComponent(), 0, 0, 0 ); - } + public WallTorchAddon(Serial serial) : base(serial) + { + } - public WallTorchAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new WallTorchDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WallTorchDeed : BaseAddonDeed - { - public override BaseAddon Addon => new WallTorchAddon(); - public override int LabelNumber => 1076282; // Wall Torch + public class WallTorchDeed : BaseAddonDeed + { + [Constructible] + public WallTorchDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public WallTorchDeed() - { - LootType = LootType.Blessed; - } + public WallTorchDeed(Serial serial) : base(serial) + { + } - public WallTorchDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new WallTorchAddon(); + public override int LabelNumber => 1076282; // Wall Torch - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Heritage Items/WoodenCoffin.cs b/Scripts/Items/Special/Heritage Items/WoodenCoffin.cs index 44be7a9e0..9a6d233ca 100644 --- a/Scripts/Items/Special/Heritage Items/WoodenCoffin.cs +++ b/Scripts/Items/Special/Heritage Items/WoodenCoffin.cs @@ -3,155 +3,157 @@ using Server.Network; namespace Server.Items { - public class WoodenCoffinComponent : AddonComponent - { - public override int LabelNumber => 1076274; // Coffin + public class WoodenCoffinComponent : AddonComponent + { + public WoodenCoffinComponent(int itemID) : base(itemID) + { + } - public WoodenCoffinComponent( int itemID ) : base( itemID ) - { - } + public WoodenCoffinComponent(Serial serial) : base(serial) + { + } - public WoodenCoffinComponent( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076274; // Coffin - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WoodenCoffinAddon : BaseAddon - { - public override BaseAddonDeed Deed => new WoodenCoffinDeed(); + public class WoodenCoffinAddon : BaseAddon + { + [Constructible] + public WoodenCoffinAddon(bool east) + { + if (east) // east + { + AddComponent(new WoodenCoffinComponent(0x1C41), 0, 0, 0); + AddComponent(new WoodenCoffinComponent(0x1C42), 1, 0, 0); + AddComponent(new WoodenCoffinComponent(0x1C43), 2, 0, 0); + } + else // south + { + AddComponent(new WoodenCoffinComponent(0x1C4F), 0, 0, 0); + AddComponent(new WoodenCoffinComponent(0x1C50), 0, 1, 0); + AddComponent(new WoodenCoffinComponent(0x1C51), 0, 2, 0); + } + } - [Constructible] - public WoodenCoffinAddon( bool east ) - { - if ( east ) // east - { - AddComponent( new WoodenCoffinComponent( 0x1C41 ), 0, 0, 0 ); - AddComponent( new WoodenCoffinComponent( 0x1C42 ), 1, 0, 0 ); - AddComponent( new WoodenCoffinComponent( 0x1C43 ), 2, 0, 0 ); - } - else // south - { - AddComponent( new WoodenCoffinComponent( 0x1C4F ), 0, 0, 0 ); - AddComponent( new WoodenCoffinComponent( 0x1C50 ), 0, 1, 0 ); - AddComponent( new WoodenCoffinComponent( 0x1C51 ), 0, 2, 0 ); - } - } + public WoodenCoffinAddon(Serial serial) : base(serial) + { + } - public WoodenCoffinAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new WoodenCoffinDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class WoodenCoffinDeed : BaseAddonDeed - { - public override BaseAddon Addon => new WoodenCoffinAddon( m_East ); - public override int LabelNumber => 1076274; // Coffin + public class WoodenCoffinDeed : BaseAddonDeed + { + private bool m_East; - private bool m_East; + [Constructible] + public WoodenCoffinDeed() + { + LootType = LootType.Blessed; + } - [Constructible] - public WoodenCoffinDeed() - { - LootType = LootType.Blessed; - } + public WoodenCoffinDeed(Serial serial) : base(serial) + { + } - public WoodenCoffinDeed( Serial serial ) : base( serial ) - { - } + public override BaseAddon Addon => new WoodenCoffinAddon(m_East); + public override int LabelNumber => 1076274; // Coffin - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private WoodenCoffinDeed m_Deed; + private class InternalGump : Gump + { + private WoodenCoffinDeed m_Deed; - public InternalGump( WoodenCoffinDeed deed ) : base( 60, 36 ) - { - m_Deed = deed; + public InternalGump(WoodenCoffinDeed deed) : base(60, 36) + { + m_Deed = deed; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 273, 324, 0x13BE ); - AddImageTiled( 10, 10, 253, 20, 0xA40 ); - AddImageTiled( 10, 40, 253, 244, 0xA40 ); - AddImageTiled( 10, 294, 253, 20, 0xA40 ); - AddAlphaRegion( 10, 10, 253, 304 ); - AddButton( 10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 296, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - AddHtmlLocalized( 14, 12, 273, 20, 1076748, 0x7FFF, false, false ); // Please select your coffin position + AddBackground(0, 0, 273, 324, 0x13BE); + AddImageTiled(10, 10, 253, 20, 0xA40); + AddImageTiled(10, 40, 253, 244, 0xA40); + AddImageTiled(10, 294, 253, 20, 0xA40); + AddAlphaRegion(10, 10, 253, 304); + AddButton(10, 294, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 296, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + AddHtmlLocalized(14, 12, 273, 20, 1076748, 0x7FFF, false, false); // Please select your coffin position - AddPage( 1 ); + AddPage(1); - AddButton( 19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 47, 213, 20, 1075386, 0x7FFF, false, false ); // South - AddButton( 19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 44, 71, 213, 20, 1075387, 0x7FFF, false, false ); // East - } + AddButton(19, 49, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 47, 213, 20, 1075386, 0x7FFF, false, false); // South + AddButton(19, 73, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(44, 71, 213, 20, 1075387, 0x7FFF, false, false); // East + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted || info.ButtonID == 0 ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted || info.ButtonID == 0) + return; - m_Deed.m_East = ( info.ButtonID != 1 ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } -} + m_Deed.m_East = info.ButtonID != 1; + m_Deed.SendTarget(sender.Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/HeritageToken.cs b/Scripts/Items/Special/HeritageToken.cs index 7bc71f4c6..76fa9767d 100644 --- a/Scripts/Items/Special/HeritageToken.cs +++ b/Scripts/Items/Special/HeritageToken.cs @@ -1,57 +1,58 @@ -using System; -using Server.Gumps; +using Server.Gumps; namespace Server.Items { - public interface ITokunoDyable - { - } + public interface ITokunoDyable + { + } - public class HeritageToken : Item - { - public override int LabelNumber => 1076596; // A Heritage Token + public class HeritageToken : Item + { + [Constructible] + public HeritageToken() : base(0x367A) + { + LootType = LootType.Blessed; + Weight = 5.0; + } - [Constructible] - public HeritageToken() : base( 0x367A ) - { - LootType = LootType.Blessed; - Weight = 5.0; - } + public HeritageToken(Serial serial) : base(serial) + { + } - public HeritageToken( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1076596; // A Heritage Token - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( HeritageTokenGump ) ); - from.SendGump( new HeritageTokenGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(HeritageTokenGump)); + from.SendGump(new HeritageTokenGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070998, $"#{1076595}"); // Use this to redeem
Your Heritage Items - } + list.Add(1070998, $"#{1076595}"); // Use this to redeem
Your Heritage Items + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Christmas/HolidayTree.cs b/Scripts/Items/Special/Holiday/Christmas/HolidayTree.cs index 3dde06d75..e58012b65 100644 --- a/Scripts/Items/Special/Holiday/Christmas/HolidayTree.cs +++ b/Scripts/Items/Special/Holiday/Christmas/HolidayTree.cs @@ -4,301 +4,298 @@ using Server.Multis; namespace Server.Items { - public enum HolidayTreeType - { - Classic, - Modern - } + public enum HolidayTreeType + { + Classic, + Modern + } - public class HolidayTree : Item, IAddon - { - private ArrayList m_Components; + public class HolidayTree : Item, IAddon + { + private ArrayList m_Components; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Placer { get; set; } + public HolidayTree(Mobile from, HolidayTreeType type, Point3D loc) : base(1) + { + Movable = false; + MoveToWorld(loc, from.Map); - private class Ornament : Item - { - public override int LabelNumber => 1041118; // a tree ornament + Placer = from; + m_Components = new ArrayList(); - public Ornament( int itemID ) : base( itemID ) - { - Movable = false; - } + switch (type) + { + case HolidayTreeType.Classic: + { + ItemID = 0xCD7; - public Ornament( Serial serial ) : base( serial ) - { - } + AddItem(0, 0, 0, new TreeTrunk(this, 0xCD6)); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddOrnament(0, 0, 2, 0xF22); + AddOrnament(0, 0, 9, 0xF18); + AddOrnament(0, 0, 15, 0xF20); + AddOrnament(0, 0, 19, 0xF17); + AddOrnament(0, 0, 20, 0xF24); + AddOrnament(0, 0, 20, 0xF1F); + AddOrnament(0, 0, 20, 0xF19); + AddOrnament(0, 0, 21, 0xF1B); + AddOrnament(0, 0, 28, 0xF2F); + AddOrnament(0, 0, 30, 0xF23); + AddOrnament(0, 0, 32, 0xF2A); + AddOrnament(0, 0, 33, 0xF30); + AddOrnament(0, 0, 34, 0xF29); + AddOrnament(0, 1, 7, 0xF16); + AddOrnament(0, 1, 7, 0xF1E); + AddOrnament(0, 1, 12, 0xF0F); + AddOrnament(0, 1, 13, 0xF13); + AddOrnament(0, 1, 18, 0xF12); + AddOrnament(0, 1, 19, 0xF15); + AddOrnament(0, 1, 25, 0xF28); + AddOrnament(0, 1, 29, 0xF1A); + AddOrnament(0, 1, 37, 0xF2B); + AddOrnament(1, 0, 13, 0xF10); + AddOrnament(1, 0, 14, 0xF1C); + AddOrnament(1, 0, 16, 0xF14); + AddOrnament(1, 0, 17, 0xF26); + AddOrnament(1, 0, 22, 0xF27); - writer.Write( (int) 0 ); // version - } + break; + } + case HolidayTreeType.Modern: + { + ItemID = 0x1B7E; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + AddOrnament(0, 0, 2, 0xF2F); + AddOrnament(0, 0, 2, 0xF20); + AddOrnament(0, 0, 2, 0xF22); + AddOrnament(0, 0, 5, 0xF30); + AddOrnament(0, 0, 5, 0xF15); + AddOrnament(0, 0, 5, 0xF1F); + AddOrnament(0, 0, 5, 0xF2B); + AddOrnament(0, 0, 6, 0xF0F); + AddOrnament(0, 0, 7, 0xF1E); + AddOrnament(0, 0, 7, 0xF24); + AddOrnament(0, 0, 8, 0xF29); + AddOrnament(0, 0, 9, 0xF18); + AddOrnament(0, 0, 14, 0xF1C); + AddOrnament(0, 0, 15, 0xF13); + AddOrnament(0, 0, 15, 0xF20); + AddOrnament(0, 0, 16, 0xF26); + AddOrnament(0, 0, 17, 0xF12); + AddOrnament(0, 0, 18, 0xF17); + AddOrnament(0, 0, 20, 0xF1B); + AddOrnament(0, 0, 23, 0xF28); + AddOrnament(0, 0, 25, 0xF18); + AddOrnament(0, 0, 25, 0xF2A); + AddOrnament(0, 1, 7, 0xF16); - int version = reader.ReadInt(); - } - } + break; + } + } + } - private class TreeTrunk : Item - { - private HolidayTree m_Tree; + public HolidayTree(Serial serial) : base(serial) + { + } - public override int LabelNumber => 1041117; // a tree for the holidays + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Placer{ get; set; } - public TreeTrunk( HolidayTree tree, int itemID ) : base( itemID ) - { - Movable = false; - MoveToWorld( tree.Location, tree.Map ); + public override int LabelNumber => 1041117; // a tree for the holidays - m_Tree = tree; - } + public bool CouldFit(IPoint3D p, Map map) + { + return map.CanFit((Point3D)p, 20); + } - public TreeTrunk( Serial serial ) : base( serial ) - { - } + Item IAddon.Deed => new HolidayTreeDeed(); - public override void OnDoubleClick( Mobile from ) - { - if ( m_Tree != null && !m_Tree.Deleted ) - m_Tree.OnDoubleClick( from ); - } + public override void OnAfterDelete() + { + for (int i = 0; i < m_Components.Count; ++i) + ((Item)m_Components[i]).Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private void AddOrnament(int x, int y, int z, int itemID) + { + AddItem(x + 1, y + 1, z + 11, new Ornament(itemID)); + } - writer.Write( (int) 0 ); // version + private void AddItem(int x, int y, int z, Item item) + { + item.MoveToWorld(new Point3D(Location.X + x, Location.Y + y, Location.Z + z), Map); - writer.Write( m_Tree ); - } + m_Components.Add(item); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(1); // version - switch ( version ) - { - case 0: - { - m_Tree = reader.ReadItem() as HolidayTree; + writer.Write(Placer); - if ( m_Tree == null ) - Delete(); + writer.Write(m_Components.Count); - break; - } - } - } - } + for (int i = 0; i < m_Components.Count; ++i) + writer.Write((Item)m_Components[i]); + } - public override int LabelNumber => 1041117; // a tree for the holidays + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public HolidayTree( Mobile from, HolidayTreeType type, Point3D loc ) : base( 1 ) - { - Movable = false; - MoveToWorld( loc, from.Map ); + int version = reader.ReadInt(); - Placer = from; - m_Components = new ArrayList(); + switch (version) + { + case 1: + { + Placer = reader.ReadMobile(); - switch ( type ) - { - case HolidayTreeType.Classic: - { - ItemID = 0xCD7; + goto case 0; + } + case 0: + { + int count = reader.ReadInt(); - AddItem( 0, 0, 0, new TreeTrunk( this, 0xCD6 ) ); + m_Components = new ArrayList(count); - AddOrnament( 0, 0, 2, 0xF22 ); - AddOrnament( 0, 0, 9, 0xF18 ); - AddOrnament( 0, 0, 15, 0xF20 ); - AddOrnament( 0, 0, 19, 0xF17 ); - AddOrnament( 0, 0, 20, 0xF24 ); - AddOrnament( 0, 0, 20, 0xF1F ); - AddOrnament( 0, 0, 20, 0xF19 ); - AddOrnament( 0, 0, 21, 0xF1B ); - AddOrnament( 0, 0, 28, 0xF2F ); - AddOrnament( 0, 0, 30, 0xF23 ); - AddOrnament( 0, 0, 32, 0xF2A ); - AddOrnament( 0, 0, 33, 0xF30 ); - AddOrnament( 0, 0, 34, 0xF29 ); - AddOrnament( 0, 1, 7, 0xF16 ); - AddOrnament( 0, 1, 7, 0xF1E ); - AddOrnament( 0, 1, 12, 0xF0F ); - AddOrnament( 0, 1, 13, 0xF13 ); - AddOrnament( 0, 1, 18, 0xF12 ); - AddOrnament( 0, 1, 19, 0xF15 ); - AddOrnament( 0, 1, 25, 0xF28 ); - AddOrnament( 0, 1, 29, 0xF1A ); - AddOrnament( 0, 1, 37, 0xF2B ); - AddOrnament( 1, 0, 13, 0xF10 ); - AddOrnament( 1, 0, 14, 0xF1C ); - AddOrnament( 1, 0, 16, 0xF14 ); - AddOrnament( 1, 0, 17, 0xF26 ); - AddOrnament( 1, 0, 22, 0xF27 ); + for (int i = 0; i < count; ++i) + { + Item item = reader.ReadItem(); - break; - } - case HolidayTreeType.Modern: - { - ItemID = 0x1B7E; + if (item != null) + m_Components.Add(item); + } - AddOrnament( 0, 0, 2, 0xF2F ); - AddOrnament( 0, 0, 2, 0xF20 ); - AddOrnament( 0, 0, 2, 0xF22 ); - AddOrnament( 0, 0, 5, 0xF30 ); - AddOrnament( 0, 0, 5, 0xF15 ); - AddOrnament( 0, 0, 5, 0xF1F ); - AddOrnament( 0, 0, 5, 0xF2B ); - AddOrnament( 0, 0, 6, 0xF0F ); - AddOrnament( 0, 0, 7, 0xF1E ); - AddOrnament( 0, 0, 7, 0xF24 ); - AddOrnament( 0, 0, 8, 0xF29 ); - AddOrnament( 0, 0, 9, 0xF18 ); - AddOrnament( 0, 0, 14, 0xF1C ); - AddOrnament( 0, 0, 15, 0xF13 ); - AddOrnament( 0, 0, 15, 0xF20 ); - AddOrnament( 0, 0, 16, 0xF26 ); - AddOrnament( 0, 0, 17, 0xF12 ); - AddOrnament( 0, 0, 18, 0xF17 ); - AddOrnament( 0, 0, 20, 0xF1B ); - AddOrnament( 0, 0, 23, 0xF28 ); - AddOrnament( 0, 0, 25, 0xF18 ); - AddOrnament( 0, 0, 25, 0xF2A ); - AddOrnament( 0, 1, 7, 0xF16 ); + break; + } + } - break; - } - } - } + Timer.DelayCall(TimeSpan.Zero, ValidatePlacement); + } - public override void OnAfterDelete() - { - for ( int i = 0; i < m_Components.Count; ++i ) - ((Item)m_Components[i]).Delete(); - } + public void ValidatePlacement() + { + BaseHouse house = BaseHouse.FindHouseAt(this); - private void AddOrnament( int x, int y, int z, int itemID ) - { - AddItem( x + 1, y + 1, z + 11, new Ornament( itemID ) ); - } - - private void AddItem( int x, int y, int z, Item item ) - { - item.MoveToWorld( new Point3D( Location.X + x, Location.Y + y, Location.Z + z ), Map ); - - m_Components.Add( item ); - } - - public HolidayTree( Serial serial ) : base( serial ) - { - } - - public bool CouldFit( IPoint3D p, Map map ) - { - return map.CanFit( (Point3D)p, 20 ); - } - - Item IAddon.Deed => new HolidayTreeDeed(); - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - - writer.Write( Placer ); - - writer.Write( (int) m_Components.Count ); - - for ( int i = 0; i < m_Components.Count; ++i ) - writer.Write( (Item)m_Components[i] ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - Placer = reader.ReadMobile(); - - goto case 0; - } - case 0: - { - int count = reader.ReadInt(); - - m_Components = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) - { - Item item = reader.ReadItem(); - - if ( item != null ) - m_Components.Add( item ); - } - - break; - } - } - - Timer.DelayCall( TimeSpan.Zero, ValidatePlacement ); - } - - public void ValidatePlacement() - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house == null ) - { - HolidayTreeDeed deed = new HolidayTreeDeed(); - deed.MoveToWorld( Location, Map ); - Delete(); - } - } + if (house == null) + { + HolidayTreeDeed deed = new HolidayTreeDeed(); + deed.MoveToWorld(Location, Map); + Delete(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - if ( Placer == null || from == Placer || from.AccessLevel >= AccessLevel.GameMaster ) - { - from.AddToBackpack( new HolidayTreeDeed() ); + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 1)) + { + if (Placer == null || from == Placer || from.AccessLevel >= AccessLevel.GameMaster) + { + from.AddToBackpack(new HolidayTreeDeed()); - Delete(); + Delete(); - BaseHouse house = BaseHouse.FindHouseAt( this ); + BaseHouse house = BaseHouse.FindHouseAt(this); - if ( house != null && house.Addons.Contains( this ) ) - { - house.Addons.Remove( this ); - } + if (house != null && house.Addons.Contains(this)) house.Addons.Remove(this); - from.SendLocalizedMessage( 503393 ); // A deed for the tree has been placed in your backpack. - } - else - { - from.SendLocalizedMessage( 503396 ); // You cannot take this tree down. - } - } - else - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } - } -} + from.SendLocalizedMessage(503393); // A deed for the tree has been placed in your backpack. + } + else + { + from.SendLocalizedMessage(503396); // You cannot take this tree down. + } + } + else + { + from.SendLocalizedMessage(500446); // That is too far away. + } + } + + private class Ornament : Item + { + public Ornament(int itemID) : base(itemID) + { + Movable = false; + } + + public Ornament(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041118; // a tree ornament + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + private class TreeTrunk : Item + { + private HolidayTree m_Tree; + + public TreeTrunk(HolidayTree tree, int itemID) : base(itemID) + { + Movable = false; + MoveToWorld(tree.Location, tree.Map); + + m_Tree = tree; + } + + public TreeTrunk(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041117; // a tree for the holidays + + public override void OnDoubleClick(Mobile from) + { + if (m_Tree != null && !m_Tree.Deleted) + m_Tree.OnDoubleClick(from); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Tree); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Tree = reader.ReadItem() as HolidayTree; + + if (m_Tree == null) + Delete(); + + break; + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/GiftBox.cs b/Scripts/Items/Special/Holiday/GiftBox.cs index 46f76cea3..075b8cdb6 100644 --- a/Scripts/Items/Special/Holiday/GiftBox.cs +++ b/Scripts/Items/Special/Holiday/GiftBox.cs @@ -1,37 +1,37 @@ namespace Server.Items { - [Furniture] - [Flippable( 0x232A, 0x232B )] - public class GiftBox : BaseContainer - { - [Constructible] - public GiftBox() : this( Utility.RandomDyedHue() ) - { - } + [Furniture] + [Flippable(0x232A, 0x232B)] + public class GiftBox : BaseContainer + { + [Constructible] + public GiftBox() : this(Utility.RandomDyedHue()) + { + } - [Constructible] - public GiftBox( int hue ) : base( Utility.Random( 0x232A, 2 ) ) - { - Weight = 2.0; - Hue = hue; - } + [Constructible] + public GiftBox(int hue) : base(Utility.Random(0x232A, 2)) + { + Weight = 2.0; + Hue = hue; + } - public GiftBox( Serial serial ) : base( serial ) - { - } + public GiftBox(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/GingerBreadHouseDeed.cs b/Scripts/Items/Special/Holiday/GingerBreadHouseDeed.cs index 1eca05a8e..9b54bd44e 100644 --- a/Scripts/Items/Special/Holiday/GingerBreadHouseDeed.cs +++ b/Scripts/Items/Special/Holiday/GingerBreadHouseDeed.cs @@ -1,63 +1,62 @@ namespace Server.Items { - public class GingerBreadHouseAddon : BaseAddon - { - public override BaseAddonDeed Deed => new GingerBreadHouseDeed(); + public class GingerBreadHouseAddon : BaseAddon + { + public GingerBreadHouseAddon() + { + for (int i = 0x2be5; i < 0x2be8; i++) + { + LocalizedAddonComponent laoc = new LocalizedAddonComponent(i, 1077395); // Gingerbread House + laoc.Light = LightType.SouthSmall; + AddComponent(laoc, i == 0x2be5 ? -1 : 0, i == 0x2be7 ? -1 : 0, 0); + } + } - public GingerBreadHouseAddon() - { - for( int i=0x2be5; i<0x2be8; i++ ) - { - LocalizedAddonComponent laoc = new LocalizedAddonComponent( i, 1077395 ); // Gingerbread House - laoc.Light = LightType.SouthSmall; - AddComponent( laoc, (i==0x2be5) ? -1 : 0, (i==0x2be7) ? -1 : 0, 0 ); - } - } + public GingerBreadHouseAddon(Serial serial) : base(serial) + { + } - public GingerBreadHouseAddon( Serial serial ) : base( serial ) - { - } + public override BaseAddonDeed Deed => new GingerBreadHouseDeed(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class GingerBreadHouseDeed : BaseAddonDeed - { - public override int LabelNumber => 1077394; //a Gingerbread House Deed - public override BaseAddon Addon => new GingerBreadHouseAddon(); + public class GingerBreadHouseDeed : BaseAddonDeed + { + [Constructible] + public GingerBreadHouseDeed() + { + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public GingerBreadHouseDeed() - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public GingerBreadHouseDeed(Serial serial) : base(serial) + { + } - public GingerBreadHouseDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1077394; //a Gingerbread House Deed + public override BaseAddon Addon => new GingerBreadHouseAddon(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/HolidayBell.cs b/Scripts/Items/Special/Holiday/HolidayBell.cs index 617d33ddc..7f4575e6c 100644 --- a/Scripts/Items/Special/Holiday/HolidayBell.cs +++ b/Scripts/Items/Special/Holiday/HolidayBell.cs @@ -1,106 +1,111 @@ -using System; - -namespace Server.Items +namespace Server.Items { - public class HolidayBell : Item - { - private static string[] m_StaffNames = { - "Adrick", - "Alai", - "Bulldoz", - "Evocare", - "FierY-iCe", - "Greyburn", - "Hanse", - "Ignatz", - "Jalek", - "LadyMOI", - "Lord Krum", - "Malantus", - "Nimrond", - "Oaks", - "Prophet", - "Runesabre", - "Sage", - "Stellerex", - "T-Bone", - "Tajima", - "Tyrant", - "Vex" - }; - private static int[] m_Hues = { - 0xA, 0x24, 0x42, 0x56, 0x1A, 0x4C, 0x3C, 0x60, 0x2E, 0x55, 0x23, 0x38, 0x482, 0x6, 0x10 - }; + public class HolidayBell : Item + { + private static string[] m_StaffNames = + { + "Adrick", + "Alai", + "Bulldoz", + "Evocare", + "FierY-iCe", + "Greyburn", + "Hanse", + "Ignatz", + "Jalek", + "LadyMOI", + "Lord Krum", + "Malantus", + "Nimrond", + "Oaks", + "Prophet", + "Runesabre", + "Sage", + "Stellerex", + "T-Bone", + "Tajima", + "Tyrant", + "Vex" + }; - [CommandProperty(AccessLevel.GameMaster)] - public int SoundID - { - get => m_SoundID; - set { m_SoundID = value; InvalidateProperties(); } - } + private static int[] m_Hues = + { + 0xA, 0x24, 0x42, 0x56, 0x1A, 0x4C, 0x3C, 0x60, 0x2E, 0x55, 0x23, 0x38, 0x482, 0x6, 0x10 + }; - [CommandProperty(AccessLevel.GameMaster)] - public string Giver { get => m_Maker; - set => m_Maker = value; - } + private string m_Maker; + private int m_SoundID; - public override string DefaultName => $"A Holiday Bell From {Giver}"; + [Constructible] + public HolidayBell() + : this(m_StaffNames[Utility.Random(m_StaffNames.Length)]) + { + } - private string m_Maker; - private int m_SoundID; + [Constructible] + public HolidayBell(string maker) + : base(0x1C12) + { + m_Maker = maker; - [Constructible] - public HolidayBell() - : this(m_StaffNames[Utility.Random(m_StaffNames.Length)]) - { - } + LootType = LootType.Blessed; + Hue = m_Hues[Utility.Random(m_Hues.Length)]; + SoundID = 0x0F5 + Utility.Random(14); + } - [Constructible] - public HolidayBell(string maker) - : base(0x1C12) - { - m_Maker = maker; + public HolidayBell(Serial serial) + : base(serial) + { + } - LootType = LootType.Blessed; - Hue = m_Hues[Utility.Random(m_Hues.Length)]; - SoundID = 0x0F5 + Utility.Random(14); - } + [CommandProperty(AccessLevel.GameMaster)] + public int SoundID + { + get => m_SoundID; + set + { + m_SoundID = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick(Mobile from) - { - if (!from.InRange(GetWorldLocation(), 2)) - { - from.SendLocalizedMessage(500446); // That is too far away. - } - else from.PlaySound(m_SoundID); - } + [CommandProperty(AccessLevel.GameMaster)] + public string Giver + { + get => m_Maker; + set => m_Maker = value; + } - public HolidayBell(Serial serial) - : base(serial) - { - } + public override string DefaultName => $"A Holiday Bell From {Giver}"; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + from.SendLocalizedMessage(500446); // That is too far away. + else from.PlaySound(m_SoundID); + } - writer.Write((int)0); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((string)m_Maker); + writer.Write(0); // version - writer.WriteEncodedInt((int)m_SoundID); - } + writer.Write(m_Maker); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + writer.WriteEncodedInt(m_SoundID); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Maker = reader.ReadString(); - m_SoundID = reader.ReadEncodedInt(); + int version = reader.ReadInt(); - Utility.Intern(ref m_Maker); - } - } + m_Maker = reader.ReadString(); + m_SoundID = reader.ReadEncodedInt(); + + Utility.Intern(ref m_Maker); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/HolidayFoods.cs b/Scripts/Items/Special/Holiday/HolidayFoods.cs index 1846c05f0..db6377497 100644 --- a/Scripts/Items/Special/Holiday/HolidayFoods.cs +++ b/Scripts/Items/Special/Holiday/HolidayFoods.cs @@ -3,172 +3,172 @@ using System.Collections.Generic; namespace Server.Items { - public class CandyCane : Food - { - public static Dictionary ToothAches { get; set; } + public class CandyCane : Food + { + [Constructible] + public CandyCane() + : this(0x2bdd + Utility.Random(4)) + { + } - public static void Initialize() - { - ToothAches = new Dictionary(); - } + public CandyCane(int itemID) + : base(itemID) + { + Stackable = false; + LootType = LootType.Blessed; + } - public class CandyCaneTimer : Timer - { - public Mobile Eater { get; } + public CandyCane(Serial serial) + : base(serial) + { + } - public int Eaten { get; set; } + public static Dictionary ToothAches{ get; set; } - public CandyCaneTimer( Mobile eater ) - : base( TimeSpan.FromSeconds( 30 ), TimeSpan.FromSeconds( 30 ) ) - { - Eater = eater; - Priority = TimerPriority.FiveSeconds; - Start(); - } + public static void Initialize() + { + ToothAches = new Dictionary(); + } - protected override void OnTick() - { - --Eaten; + private static CandyCaneTimer EnsureTimer(Mobile from) + { + if (!ToothAches.TryGetValue(from, out CandyCaneTimer timer)) + ToothAches[from] = timer = new CandyCaneTimer(from); - if ( Eater == null || Eater.Deleted || Eaten <= 0 ) - { - Stop(); - ToothAches.Remove( Eater ); - } - else if ( Eater.Map != Map.Internal && Eater.Alive ) - { - if ( Eaten > 60 ) - { - Eater.Say( 1077388 + Utility.Random( 5 ) ); + return timer; + } - /* ARRGH! My tooth hurts sooo much! - * You just can't find a good Britannian dentist these days... - * My teeth! - * MAKE IT STOP! - * AAAH! It feels like someone kicked me in the teeth! - */ + public static int GetToothAche(Mobile from) + { + if (ToothAches.TryGetValue(from, out CandyCaneTimer timer)) + return timer.Eaten; - if ( Utility.RandomBool() && Eater.Body.IsHuman && !Eater.Mounted ) - Eater.Animate( 32, 5, 1, true, false, 0 ); - } - else if ( Eaten == 60 ) - { - Eater.SendLocalizedMessage( 1077393 ); // The extreme pain in your teeth subsides. - } - } - } - } + return 0; + } - private static CandyCaneTimer EnsureTimer( Mobile from ) - { - if (!ToothAches.TryGetValue( from, out CandyCaneTimer timer )) - ToothAches[from] = timer = new CandyCaneTimer( from ); + public static void SetToothAche(Mobile from, int value) + { + EnsureTimer(from).Eaten = value; + } - return timer; - } + public override bool CheckHunger(Mobile from) + { + EnsureTimer(from).Eaten += 32; - public static int GetToothAche( Mobile from ) - { - if (ToothAches.TryGetValue( from, out CandyCaneTimer timer )) - return timer.Eaten; + from.SendLocalizedMessage(1077387); // You feel as if you could eat as much as you wanted! + return true; + } - return 0; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public static void SetToothAche( Mobile from, int value ) - { - EnsureTimer( from ).Eaten = value; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - [Constructible] - public CandyCane() - : this( 0x2bdd + Utility.Random( 4 ) ) - { - } + public class CandyCaneTimer : Timer + { + public CandyCaneTimer(Mobile eater) + : base(TimeSpan.FromSeconds(30), TimeSpan.FromSeconds(30)) + { + Eater = eater; + Priority = TimerPriority.FiveSeconds; + Start(); + } - public CandyCane( int itemID ) - : base( itemID ) - { - Stackable = false; - LootType = LootType.Blessed; - } + public Mobile Eater{ get; } - public override bool CheckHunger( Mobile from ) - { - EnsureTimer( from ).Eaten += 32; + public int Eaten{ get; set; } - from.SendLocalizedMessage( 1077387 ); // You feel as if you could eat as much as you wanted! - return true; - } + protected override void OnTick() + { + --Eaten; - public CandyCane( Serial serial ) - : base( serial ) - { - } + if (Eater == null || Eater.Deleted || Eaten <= 0) + { + Stop(); + ToothAches.Remove(Eater); + } + else if (Eater.Map != Map.Internal && Eater.Alive) + { + if (Eaten > 60) + { + Eater.Say(1077388 + Utility.Random(5)); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + /* ARRGH! My tooth hurts sooo much! + * You just can't find a good Britannian dentist these days... + * My teeth! + * MAKE IT STOP! + * AAAH! It feels like someone kicked me in the teeth! + */ - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + if (Utility.RandomBool() && Eater.Body.IsHuman && !Eater.Mounted) + Eater.Animate(32, 5, 1, true, false, 0); + } + else if (Eaten == 60) + { + Eater.SendLocalizedMessage(1077393); // The extreme pain in your teeth subsides. + } + } + } + } + } - public class GingerBreadCookie : Food - { - private readonly int[] m_Messages = - { - 0, - 1077396, // Noooo! - 1077397, // Please don't eat me... *whimper* - 1077405, // Not the face! - 1077406, // Ahhhhhh! My foot�s gone! - 1077407, // Please. No! I have gingerkids! - 1077408, // No, no! I�m really made of poison. Really. - 1077409 // Run, run as fast as you can! You can't catch me! I'm the gingerbread man! - }; + public class GingerBreadCookie : Food + { + private readonly int[] m_Messages = + { + 0, + 1077396, // Noooo! + 1077397, // Please don't eat me... *whimper* + 1077405, // Not the face! + 1077406, // Ahhhhhh! My foot�s gone! + 1077407, // Please. No! I have gingerkids! + 1077408, // No, no! I�m really made of poison. Really. + 1077409 // Run, run as fast as you can! You can't catch me! I'm the gingerbread man! + }; - [Constructible] - public GingerBreadCookie() - : base( Utility.RandomBool() ? 0x2be1 : 0x2be2 ) - { - Stackable = false; - LootType = LootType.Blessed; - } + [Constructible] + public GingerBreadCookie() + : base(Utility.RandomBool() ? 0x2be1 : 0x2be2) + { + Stackable = false; + LootType = LootType.Blessed; + } - public GingerBreadCookie( Serial serial ) - : base( serial ) - { - } + public GingerBreadCookie(Serial serial) + : base(serial) + { + } - public override bool Eat( Mobile from ) - { - int message = m_Messages[Utility.Random( m_Messages.Length )]; + public override bool Eat(Mobile from) + { + int message = m_Messages[Utility.Random(m_Messages.Length)]; - if ( message != 0 ) - { - SendLocalizedMessageTo( from, message ); - return false; - } + if (message != 0) + { + SendLocalizedMessageTo(from, message); + return false; + } - return base.Eat( from ); - } + return base.Eat(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/HolidayGiftBoxes.cs b/Scripts/Items/Special/Holiday/HolidayGiftBoxes.cs index a522aa63b..8c8602387 100644 --- a/Scripts/Items/Special/Holiday/HolidayGiftBoxes.cs +++ b/Scripts/Items/Special/Holiday/HolidayGiftBoxes.cs @@ -1,219 +1,220 @@ namespace Server.Items { - public class GiftBoxHues - { - public static int RandomGiftBoxHue => m_NormalHues[Utility.Random(m_NormalHues.Length)]; - public static int RandomNeonBoxHue => m_NeonHues[Utility.Random(m_NeonHues.Length)]; + public class GiftBoxHues + { + /* there's possibly a couple more, but this is what we could verify on OSI */ - /* there's possibly a couple more, but this is what we could verify on OSI */ + private static readonly int[] m_NormalHues = + { + 0x672, + 0x454, + 0x507, + 0x4ac, + 0x504, + 0x84b, + 0x495, + 0x97c, + 0x493, + 0x4a8, + 0x494, + 0x4aa, + 0xb8b, + 0x84f, + 0x491, + 0x851, + 0x503, + 0xb8c, + 0x4ab, + 0x84B + }; - private static readonly int[] m_NormalHues = - { - 0x672, - 0x454, - 0x507, - 0x4ac, - 0x504, - 0x84b, - 0x495, - 0x97c, - 0x493, - 0x4a8, - 0x494, - 0x4aa, - 0xb8b, - 0x84f, - 0x491, - 0x851, - 0x503, - 0xb8c, - 0x4ab, - 0x84B - }; - private static readonly int[] m_NeonHues = - { - 0x438, - 0x424, - 0x433, - 0x445, - 0x42b, - 0x448 - }; - } + private static readonly int[] m_NeonHues = + { + 0x438, + 0x424, + 0x433, + 0x445, + 0x42b, + 0x448 + }; - [FlippableAttribute(0x46A5, 0x46A6)] - public class GiftBoxRectangle : BaseContainer - { - public override int DefaultGumpID => 0x11E; + public static int RandomGiftBoxHue => m_NormalHues[Utility.Random(m_NormalHues.Length)]; + public static int RandomNeonBoxHue => m_NeonHues[Utility.Random(m_NeonHues.Length)]; + } - [Constructible] - public GiftBoxRectangle() - : base(Utility.RandomBool() ? 0x46A5 : 0x46A6) - { - Hue = GiftBoxHues.RandomGiftBoxHue; - } + [Flippable(0x46A5, 0x46A6)] + public class GiftBoxRectangle : BaseContainer + { + [Constructible] + public GiftBoxRectangle() + : base(Utility.RandomBool() ? 0x46A5 : 0x46A6) + { + Hue = GiftBoxHues.RandomGiftBoxHue; + } - public GiftBoxRectangle(Serial serial) - : base(serial) - { - } + public GiftBoxRectangle(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); // version - } + public override int DefaultGumpID => 0x11E; - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public class GiftBoxCube : BaseContainer - { - public override int DefaultGumpID => 0x11B; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [Constructible] - public GiftBoxCube() - : base(0x46A2) - { - Hue = GiftBoxHues.RandomGiftBoxHue; - } + public class GiftBoxCube : BaseContainer + { + [Constructible] + public GiftBoxCube() + : base(0x46A2) + { + Hue = GiftBoxHues.RandomGiftBoxHue; + } - public GiftBoxCube(Serial serial) - : base(serial) - { - } + public GiftBoxCube(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); // version - } + public override int DefaultGumpID => 0x11B; - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public class GiftBoxCylinder : BaseContainer - { - public override int DefaultGumpID => 0x11C; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [Constructible] - public GiftBoxCylinder() - : base(0x46A3) - { - Hue = GiftBoxHues.RandomGiftBoxHue; - } + public class GiftBoxCylinder : BaseContainer + { + [Constructible] + public GiftBoxCylinder() + : base(0x46A3) + { + Hue = GiftBoxHues.RandomGiftBoxHue; + } - public GiftBoxCylinder(Serial serial) - : base(serial) - { - } + public GiftBoxCylinder(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); // version - } + public override int DefaultGumpID => 0x11C; - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public class GiftBoxOctogon : BaseContainer - { - public override int DefaultGumpID => 0x11D; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [Constructible] - public GiftBoxOctogon() - : base(0x46A4) - { - Hue = GiftBoxHues.RandomGiftBoxHue; - } + public class GiftBoxOctogon : BaseContainer + { + [Constructible] + public GiftBoxOctogon() + : base(0x46A4) + { + Hue = GiftBoxHues.RandomGiftBoxHue; + } - public GiftBoxOctogon(Serial serial) - : base(serial) - { - } + public GiftBoxOctogon(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); // version - } + public override int DefaultGumpID => 0x11D; - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public class GiftBoxAngel : BaseContainer - { - public override int DefaultGumpID => 0x11F; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [Constructible] - public GiftBoxAngel() - : base(0x46A7) - { - Hue = GiftBoxHues.RandomGiftBoxHue; - } + public class GiftBoxAngel : BaseContainer + { + [Constructible] + public GiftBoxAngel() + : base(0x46A7) + { + Hue = GiftBoxHues.RandomGiftBoxHue; + } - public GiftBoxAngel(Serial serial) - : base(serial) - { - } + public GiftBoxAngel(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); // version - } + public override int DefaultGumpID => 0x11F; - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - [Flippable(0x232A, 0x232B)] - public class GiftBoxNeon : BaseContainer - { - [Constructible] - public GiftBoxNeon() - : base(Utility.RandomBool() ? 0x232A : 0x232B) - { - Hue = GiftBoxHues.RandomNeonBoxHue; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public GiftBoxNeon(Serial serial) - : base(serial) - { - } + [Flippable(0x232A, 0x232B)] + public class GiftBoxNeon : BaseContainer + { + [Constructible] + public GiftBoxNeon() + : base(Utility.RandomBool() ? 0x232A : 0x232B) + { + Hue = GiftBoxHues.RandomNeonBoxHue; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public GiftBoxNeon(Serial serial) + : base(serial) + { + } - writer.Write((int)0); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/HolidayPottedPlant.cs b/Scripts/Items/Special/Holiday/HolidayPottedPlant.cs index 6dec776c0..8bf3dfeaf 100644 --- a/Scripts/Items/Special/Holiday/HolidayPottedPlant.cs +++ b/Scripts/Items/Special/Holiday/HolidayPottedPlant.cs @@ -3,151 +3,151 @@ using Server.Network; namespace Server.Items { - public class HolidayPottedPlant : Item - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public class HolidayPottedPlant : Item + { + [Constructible] + public HolidayPottedPlant() + : this(Utility.RandomMinMax(0x11C8, 0x11CC)) + { + } - [Constructible] - public HolidayPottedPlant() - : this( Utility.RandomMinMax( 0x11C8, 0x11CC ) ) - { - } + [Constructible] + public HolidayPottedPlant(int itemID) + : base(itemID) + { + } - [Constructible] - public HolidayPottedPlant( int itemID ) - : base( itemID ) - { - } + public HolidayPottedPlant(Serial serial) + : base(serial) + { + } - public HolidayPottedPlant( Serial serial ) - : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class PottedPlantDeed : Item - { - public override int LabelNumber => 1041114; // A deed for a potted plant. - public override double DefaultWeight => 1.0; + public class PottedPlantDeed : Item + { + [Constructible] + public PottedPlantDeed() + : base(0x14F0) + { + LootType = LootType.Blessed; + } - [Constructible] - public PottedPlantDeed() - : base( 0x14F0 ) - { - LootType = LootType.Blessed; - } + public PottedPlantDeed(Serial serial) + : base(serial) + { + } - public PottedPlantDeed( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1041114; // A deed for a potted plant. + public override double DefaultWeight => 1.0; - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private PottedPlantDeed m_Deed; + private class InternalGump : Gump + { + private PottedPlantDeed m_Deed; - public InternalGump( PottedPlantDeed deed ) : base( 100, 200 ) - { - m_Deed = deed; + public InternalGump(PottedPlantDeed deed) : base(100, 200) + { + m_Deed = deed; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); - AddBackground( 0, 0, 360, 195, 0xA28 ); + AddPage(0); + AddBackground(0, 0, 360, 195, 0xA28); - AddPage( 1 ); - AddLabel( 45, 15, 0, "Choose a Potted Plant:" ); + AddPage(1); + AddLabel(45, 15, 0, "Choose a Potted Plant:"); - AddItem( 45, 75, 0x11C8 ); - AddButton( 55, 50, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); + AddItem(45, 75, 0x11C8); + AddButton(55, 50, 0x845, 0x846, 1, GumpButtonType.Reply, 0); - AddItem( 100, 75, 0x11C9 ); - AddButton( 115, 50, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); + AddItem(100, 75, 0x11C9); + AddButton(115, 50, 0x845, 0x846, 2, GumpButtonType.Reply, 0); - AddItem( 160, 75, 0x11CA ); - AddButton( 175, 50, 0x845, 0x846, 3, GumpButtonType.Reply, 0 ); + AddItem(160, 75, 0x11CA); + AddButton(175, 50, 0x845, 0x846, 3, GumpButtonType.Reply, 0); - AddItem( 225, 75, 0x11CB ); - AddButton( 235, 50, 0x845, 0x846, 4, GumpButtonType.Reply, 0 ); + AddItem(225, 75, 0x11CB); + AddButton(235, 50, 0x845, 0x846, 4, GumpButtonType.Reply, 0); - AddItem( 280, 75, 0x11CC ); - AddButton( 295, 50, 0x845, 0x846, 5, GumpButtonType.Reply, 0 ); - } + AddItem(280, 75, 0x11CC); + AddButton(295, 50, 0x845, 0x846, 5, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted) + return; - Mobile from = sender.Mobile; + Mobile from = sender.Mobile; - if ( !m_Deed.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it - return; - } + if (!m_Deed.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it + return; + } - int index = info.ButtonID - 1; + int index = info.ButtonID - 1; - if ( index >= 0 && index <= 4 ) - { - HolidayPottedPlant plant = new HolidayPottedPlant( 0x11C8 + index ); + if (index >= 0 && index <= 4) + { + HolidayPottedPlant plant = new HolidayPottedPlant(0x11C8 + index); - if ( !from.PlaceInBackpack( plant ) ) - { - plant.Delete(); - from.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - { - m_Deed.Delete(); - } - } - } - } - } -} + if (!from.PlaceInBackpack(plant)) + { + plant.Delete(); + from.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + m_Deed.Delete(); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/HolidayTimepiece.cs b/Scripts/Items/Special/Holiday/HolidayTimepiece.cs index 49af11020..2c3177800 100644 --- a/Scripts/Items/Special/Holiday/HolidayTimepiece.cs +++ b/Scripts/Items/Special/Holiday/HolidayTimepiece.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class HolidayTimepiece : Clock - { - public override int LabelNumber => 1041113; // a holiday timepiece - public override double DefaultWeight => 1.0; + public class HolidayTimepiece : Clock + { + [Constructible] + public HolidayTimepiece() + : base(0x1086) + { + Weight = DefaultWeight; + LootType = LootType.Blessed; + Layer = Layer.Bracelet; + } - [Constructible] - public HolidayTimepiece() - : base( 0x1086 ) - { - Weight = DefaultWeight; - LootType = LootType.Blessed; - Layer = Layer.Bracelet; - } + public HolidayTimepiece(Serial serial) + : base(serial) + { + } - public HolidayTimepiece( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1041113; // a holiday timepiece + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Icecicles.cs b/Scripts/Items/Special/Holiday/Icecicles.cs index 684004fac..8e82ca3a3 100644 --- a/Scripts/Items/Special/Holiday/Icecicles.cs +++ b/Scripts/Items/Special/Holiday/Icecicles.cs @@ -1,165 +1,170 @@ namespace Server.Items { - public class IcicleLargeSouth : Item - { - [Constructible] - public IcicleLargeSouth() - : base(0x4572) - { - } + public class IcicleLargeSouth : Item + { + [Constructible] + public IcicleLargeSouth() + : base(0x4572) + { + } - public IcicleLargeSouth(Serial serial) - : base(serial) - { - } + public IcicleLargeSouth(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } - public class IcicleMedSouth : Item - { - [Constructible] - public IcicleMedSouth () - : base(0x4573) - { - } + int version = reader.ReadInt(); + } + } - public IcicleMedSouth (Serial serial) - : base(serial) - { - } + public class IcicleMedSouth : Item + { + [Constructible] + public IcicleMedSouth() + : base(0x4573) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public IcicleMedSouth(Serial serial) + : base(serial) + { + } - writer.Write((int)0); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + writer.Write(0); + } - int version = reader.ReadInt(); - } - } - public class IcicleSmallSouth : Item - { - [Constructible] - public IcicleSmallSouth () - : base(0x4574) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public IcicleSmallSouth (Serial serial) - : base(serial) - { - } + int version = reader.ReadInt(); + } + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public class IcicleSmallSouth : Item + { + [Constructible] + public IcicleSmallSouth() + : base(0x4574) + { + } - writer.Write((int)0); - } + public IcicleSmallSouth(Serial serial) + : base(serial) + { + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } - public class IcicleLargeEast : Item - { - [Constructible] - public IcicleLargeEast () - : base(0x4575) - { - } + writer.Write(0); + } - public IcicleLargeEast (Serial serial) - : base(serial) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + int version = reader.ReadInt(); + } + } - writer.Write((int)0); - } + public class IcicleLargeEast : Item + { + [Constructible] + public IcicleLargeEast() + : base(0x4575) + { + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public IcicleLargeEast(Serial serial) + : base(serial) + { + } - int version = reader.ReadInt(); - } - } - public class IcicleMedEast : Item - { - [Constructible] - public IcicleMedEast () - : base(0x4576) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public IcicleMedEast (Serial serial) - : base(serial) - { - } + writer.Write(0); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write((int)0); - } + int version = reader.ReadInt(); + } + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public class IcicleMedEast : Item + { + [Constructible] + public IcicleMedEast() + : base(0x4576) + { + } - int version = reader.ReadInt(); - } - } - public class IcicleSmallEast : Item - { - [Constructible] - public IcicleSmallEast () - : base(0x4577) - { - } + public IcicleMedEast(Serial serial) + : base(serial) + { + } - public IcicleSmallEast(Serial serial) - : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int)0); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + public class IcicleSmallEast : Item + { + [Constructible] + public IcicleSmallEast() + : base(0x4577) + { + } + + public IcicleSmallEast(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/IcyPatch.cs b/Scripts/Items/Special/Holiday/IcyPatch.cs index a8f02f37a..96b99d9c4 100644 --- a/Scripts/Items/Special/Holiday/IcyPatch.cs +++ b/Scripts/Items/Special/Holiday/IcyPatch.cs @@ -4,122 +4,118 @@ using Server.Spells; namespace Server.Items { - public class IcyPatch : Item - { - public override int LabelNumber => 1095159; //An Icy Patch - public override double DefaultWeight => 5.0; + public class IcyPatch : Item + { + /* On OSI, the iceypatch with itemid 0x122a is "rarer", so we will give it 1:10 chance of creating it that way */ - /* On OSI, the iceypatch with itemid 0x122a is "rarer", so we will give it 1:10 chance of creating it that way */ + [Constructible] + public IcyPatch() + : this(Utility.Random(10) == 0 ? 0x122A : 0x122F) + { + } - [Constructible] - public IcyPatch() - : this((Utility.Random(10) == 0) ? 0x122A : 0x122F) - { - } + public IcyPatch(int itemid) + : base(itemid) + { + Hue = 0x481; + } - public IcyPatch(int itemid) - : base (itemid) - { - Hue = 0x481; - } + public IcyPatch(Serial serial) + : base(serial) + { + } - public IcyPatch(Serial serial) - : base(serial) - { - } + public override int LabelNumber => 1095159; //An Icy Patch + public override double DefaultWeight => 5.0; - public override bool OnMoveOver(Mobile m) - { - if (m is PlayerMobile && m.Alive && m.AccessLevel == AccessLevel.Player) - { - switch (Utility.Random(3)) - { - case 0: RunSequence(m, 1095160, false); break; //You steadily walk over the slippery surface. - case 1: RunSequence(m, 1095161, true); break; //You skillfully manage to maintain your balance. - default: RunSequence(m, 1095162, true); break; //You lose your footing and ungracefully splatter on the ground. - } - } - return base.OnMoveOver(m); - } + public override bool OnMoveOver(Mobile m) + { + if (m is PlayerMobile && m.Alive && m.AccessLevel == AccessLevel.Player) + switch (Utility.Random(3)) + { + case 0: + RunSequence(m, 1095160, false); + break; //You steadily walk over the slippery surface. + case 1: + RunSequence(m, 1095161, true); + break; //You skillfully manage to maintain your balance. + default: + RunSequence(m, 1095162, true); + break; //You lose your footing and ungracefully splatter on the ground. + } + return base.OnMoveOver(m); + } - public virtual void RunSequence(Mobile m, int message, bool freeze) - { - object[] arg = null; + public virtual void RunSequence(Mobile m, int message, bool freeze) + { + object[] arg = null; - if (freeze) - { - m.Frozen = freeze; - Timer.DelayCall(TimeSpan.FromSeconds((message==1095162) ? 2.0 : 1.25), new TimerStateCallback(EndFall_Callback), m); - } + if (freeze) + { + m.Frozen = freeze; + Timer.DelayCall(TimeSpan.FromSeconds(message == 1095162 ? 2.0 : 1.25), + new TimerStateCallback(EndFall_Callback), m); + } - m.SendLocalizedMessage(message); + m.SendLocalizedMessage(message); - if (message == 1095162) - { - if (m.Mounted) - { - m.Mount.Rider = null; - } + if (message == 1095162) + { + if (m.Mounted) m.Mount.Rider = null; - Point3D p = new Point3D(Location); + Point3D p = new Point3D(Location); - if (SpellHelper.FindValidSpawnLocation(Map, ref p, true)) - { - Timer.DelayCall(TimeSpan.FromSeconds(0), new TimerStateCallback(Relocate_Callback), new object[] { m, p }); - } + if (SpellHelper.FindValidSpawnLocation(Map, ref p, true)) + Timer.DelayCall(TimeSpan.FromSeconds(0), new TimerStateCallback(Relocate_Callback), + new object[] { m, p }); - arg = new object[] { m, (21 + Utility.Random(2)), !m.Female ? 0x426 : 0x317 }; - } - else if (message == 1095161) - { - arg = new object[] { m, 17, !m.Female ? 0x429 : 0x319 }; - } - if (arg != null) - { - Timer.DelayCall(TimeSpan.FromSeconds(.4), new TimerStateCallback(BeginFall_Callback), arg); - } - } + arg = new object[] { m, 21 + Utility.Random(2), !m.Female ? 0x426 : 0x317 }; + } + else if (message == 1095161) + { + arg = new object[] { m, 17, !m.Female ? 0x429 : 0x319 }; + } - private static void Relocate_Callback(object state) - { - object[] states = (object[])state; - Mobile m = (Mobile)states[0]; - Point3D to = (Point3D)states[1]; + if (arg != null) Timer.DelayCall(TimeSpan.FromSeconds(.4), new TimerStateCallback(BeginFall_Callback), arg); + } - m.MoveToWorld(to, m.Map); - } + private static void Relocate_Callback(object state) + { + object[] states = (object[])state; + Mobile m = (Mobile)states[0]; + Point3D to = (Point3D)states[1]; - private static void BeginFall_Callback(object state) - { - object[] states = (object[])state; + m.MoveToWorld(to, m.Map); + } - Mobile m = (Mobile)states[0]; - int action = (int)states[1]; - int sound = (int)states[2]; - if (!m.Mounted) - { - m.Animate(action, 1, 1, false, true, 0); - } - m.PlaySound(sound); - } + private static void BeginFall_Callback(object state) + { + object[] states = (object[])state; - private static void EndFall_Callback(object state) - { - ((Mobile)state).Frozen = false; - } + Mobile m = (Mobile)states[0]; + int action = (int)states[1]; + int sound = (int)states[2]; + if (!m.Mounted) m.Animate(action, 1, 1, false, true, 0); + m.PlaySound(sound); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + private static void EndFall_Callback(object state) + { + ((Mobile)state).Frozen = false; + } - writer.Write((int)0); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + writer.Write(0); + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/PKHolidayStuff.cs b/Scripts/Items/Special/Holiday/PKHolidayStuff.cs index b4e9890ee..841d3a177 100644 --- a/Scripts/Items/Special/Holiday/PKHolidayStuff.cs +++ b/Scripts/Items/Special/Holiday/PKHolidayStuff.cs @@ -1,89 +1,89 @@ namespace Server.Items { - public class Coal : Item - { - public override string DefaultName => "Coal"; + public class Coal : Item + { + [Constructible] + public Coal() : base(0x19b9) + { + Stackable = false; + LootType = LootType.Blessed; + Hue = 0x965; + } - [Constructible] - public Coal() : base( 0x19b9 ) - { - Stackable = false; - LootType=LootType.Blessed; - Hue = 0x965; - } + public Coal(Serial serial) : base(serial) + { + } - public Coal( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "Coal"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class BadCard : Item - { - public override int LabelNumber // Maybe next year youll get a better... - => 1041428; + public class BadCard : Item + { + [Constructible] + public BadCard() : base(0x14ef) + { + int[] m_CardHues = { 0x45, 0x27, 0x3d0 }; + Hue = m_CardHues[Utility.Random(m_CardHues.Length)]; + Stackable = false; + LootType = LootType.Blessed; + Movable = true; + } - [Constructible] - public BadCard() : base( 0x14ef ) - { - int[] m_CardHues={ 0x45, 0x27, 0x3d0 }; - Hue = m_CardHues[Utility.Random(m_CardHues.Length)]; - Stackable = false; - LootType=LootType.Blessed; - Movable=true; - } + public BadCard(Serial serial) : base(serial) + { + } - public BadCard( Serial serial ) : base( serial ) - { - } + public override int LabelNumber // Maybe next year youll get a better... + => 1041428; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class Spam : Food - { - [Constructible] - public Spam() : base( 0x1044 ) - { - Stackable = false; - LootType=LootType.Blessed; - } + public class Spam : Food + { + [Constructible] + public Spam() : base(0x1044) + { + Stackable = false; + LootType = LootType.Blessed; + } - public Spam( Serial serial ) : base( serial ) - { - } + public Spam(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Poinsettias.cs b/Scripts/Items/Special/Holiday/Poinsettias.cs index 305647c59..7d4c0a54f 100644 --- a/Scripts/Items/Special/Holiday/Poinsettias.cs +++ b/Scripts/Items/Special/Holiday/Poinsettias.cs @@ -1,58 +1,58 @@ namespace Server.Items { - public class RedPoinsettia : Item - { - [Constructible] - public RedPoinsettia() : base( 0x2330 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class RedPoinsettia : Item + { + [Constructible] + public RedPoinsettia() : base(0x2330) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public RedPoinsettia( Serial serial ) : base( serial ) - { - } + public RedPoinsettia(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class WhitePoinsettia : Item - { - [Constructible] - public WhitePoinsettia() : base( 0x2331 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class WhitePoinsettia : Item + { + [Constructible] + public WhitePoinsettia() : base(0x2331) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public WhitePoinsettia( Serial serial ) : base( serial ) - { - } + public WhitePoinsettia(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/SnowGlobes.cs b/Scripts/Items/Special/Holiday/SnowGlobes.cs index d134f348e..35b53dcdb 100644 --- a/Scripts/Items/Special/Holiday/SnowGlobes.cs +++ b/Scripts/Items/Special/Holiday/SnowGlobes.cs @@ -1,309 +1,320 @@ -using System; - namespace Server.Items { - public class SnowGlobe : Item - { - public override double DefaultWeight => 1.0; + public class SnowGlobe : Item + { + public SnowGlobe() + : base(0xE2F) + { + LootType = LootType.Blessed; + Light = LightType.Circle150; + } - public SnowGlobe() - : base( 0xE2F ) - { - LootType = LootType.Blessed; - Light = LightType.Circle150; - } + public SnowGlobe(Serial serial) + : base(serial) + { + } - public SnowGlobe( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public enum SnowGlobeTypeOne - { - Britain, - Moonglow, - Minoc, - Magincia, - BuccaneersDen, - Trinsic, - Yew, - SkaraBrae, - Jhelom, - Nujelm, - Papua, - Delucia, - Cove, - Ocllo, - SerpentsHold, - EmpathAbbey, - TheLycaeum, - Vesper, - Wind - } + public enum SnowGlobeTypeOne + { + Britain, + Moonglow, + Minoc, + Magincia, + BuccaneersDen, + Trinsic, + Yew, + SkaraBrae, + Jhelom, + Nujelm, + Papua, + Delucia, + Cove, + Ocllo, + SerpentsHold, + EmpathAbbey, + TheLycaeum, + Vesper, + Wind + } - public class SnowGlobeOne : SnowGlobe - { - private SnowGlobeTypeOne m_Type; + public class SnowGlobeOne : SnowGlobe + { + private SnowGlobeTypeOne m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public SnowGlobeTypeOne Place - { - get => m_Type; - set { m_Type = value; InvalidateProperties(); } - } + [Constructible] + public SnowGlobeOne() + : this((SnowGlobeTypeOne)Utility.Random(19)) + { + } - public override int LabelNumber => 1041454 + (int) m_Type; + [Constructible] + public SnowGlobeOne(SnowGlobeTypeOne type) + { + m_Type = type; + } - [Constructible] - public SnowGlobeOne() - : this( (SnowGlobeTypeOne) Utility.Random( 19 ) ) - { - } + public SnowGlobeOne(Serial serial) + : base(serial) + { + } - [Constructible] - public SnowGlobeOne( SnowGlobeTypeOne type ) - { - m_Type = type; - } + [CommandProperty(AccessLevel.GameMaster)] + public SnowGlobeTypeOne Place + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - public SnowGlobeOne( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1041454 + (int)m_Type; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - writer.WriteEncodedInt( (int) m_Type ); - } + writer.Write(0); // version + writer.WriteEncodedInt((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Type = (SnowGlobeTypeOne) reader.ReadEncodedInt(); - break; - } - } - } - } + switch (version) + { + case 0: + { + m_Type = (SnowGlobeTypeOne)reader.ReadEncodedInt(); + break; + } + } + } + } - public enum SnowGlobeTypeTwo - { - AncientCitadel, - BlackthornesCastle, - CityofMontor, - CityofMistas, - ExodusLair, - LakeofFire, - Lakeshire, - PassofKarnaugh, - TheEtherealFortress, - TwinOaksTavern, - ChaosShrine, - ShrineofHumility, - ShrineofSacrifice, - ShrineofCompassion, - ShrineofHonor, - ShrineofHonesty, - ShrineofSpirituality, - ShrineofJustice, - ShrineofValor - } + public enum SnowGlobeTypeTwo + { + AncientCitadel, + BlackthornesCastle, + CityofMontor, + CityofMistas, + ExodusLair, + LakeofFire, + Lakeshire, + PassofKarnaugh, + TheEtherealFortress, + TwinOaksTavern, + ChaosShrine, + ShrineofHumility, + ShrineofSacrifice, + ShrineofCompassion, + ShrineofHonor, + ShrineofHonesty, + ShrineofSpirituality, + ShrineofJustice, + ShrineofValor + } - public class SnowGlobeTwo : SnowGlobe - { - /* Oddly, these are not localized. */ - private static readonly string[] m_PlaceNames = { - /* AncientCitadel */ "Ancient Citadel", - /* BlackthornesCastle */ "Blackthorne's Castle", - /* CityofMontor */ "City of Montor", - /* CityofMistas */ "City of Mistas", - /* ExodusLair */ "Exodus' Lair", - /* LakeofFire */ "Lake of Fire", - /* Lakeshire */ "Lakeshire", - /* PassofKarnaugh */ "Pass of Karnaugh", - /* TheEtherealFortress */ "The Etheral Fortress", - /* TwinOaksTavern */ "Twin Oaks Tavern", - /* ChaosShrine */ "Chaos Shrine", - /* ShrineofHumility */ "Shrine of Humility", - /* ShrineofSacrifice */ "Shrine of Sacrifice", - /* ShrineofCompassion */ "Shrine of Compassion", - /* ShrineofHonor */ "Shrine of Honor", - /* ShrineofHonesty */ "Shrine of Honesty", - /* ShrineofSpirituality */ "Shrine of Spirituality", - /* ShrineofJustice */ "Shrine of Justice", - /* ShrineofValor */ "Shrine of Valor" - }; + public class SnowGlobeTwo : SnowGlobe + { + /* Oddly, these are not localized. */ + private static readonly string[] m_PlaceNames = + { + /* AncientCitadel */ "Ancient Citadel", + /* BlackthornesCastle */ "Blackthorne's Castle", + /* CityofMontor */ "City of Montor", + /* CityofMistas */ "City of Mistas", + /* ExodusLair */ "Exodus' Lair", + /* LakeofFire */ "Lake of Fire", + /* Lakeshire */ "Lakeshire", + /* PassofKarnaugh */ "Pass of Karnaugh", + /* TheEtherealFortress */ "The Etheral Fortress", + /* TwinOaksTavern */ "Twin Oaks Tavern", + /* ChaosShrine */ "Chaos Shrine", + /* ShrineofHumility */ "Shrine of Humility", + /* ShrineofSacrifice */ "Shrine of Sacrifice", + /* ShrineofCompassion */ "Shrine of Compassion", + /* ShrineofHonor */ "Shrine of Honor", + /* ShrineofHonesty */ "Shrine of Honesty", + /* ShrineofSpirituality */ "Shrine of Spirituality", + /* ShrineofJustice */ "Shrine of Justice", + /* ShrineofValor */ "Shrine of Valor" + }; - private SnowGlobeTypeTwo m_Type; + private SnowGlobeTypeTwo m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public SnowGlobeTypeTwo Place - { - get => m_Type; - set { m_Type = value; InvalidateProperties(); } - } + [Constructible] + public SnowGlobeTwo() + : this((SnowGlobeTypeTwo)Utility.Random(19)) + { + } - public override string DefaultName - { - get - { - int idx = (int) m_Type; + [Constructible] + public SnowGlobeTwo(SnowGlobeTypeTwo type) + { + m_Type = type; + } - if ( idx < 0 || idx >= m_PlaceNames.Length ) - return "a snowy scene"; + public SnowGlobeTwo(Serial serial) + : base(serial) + { + } - return $"a snowy scene of {m_PlaceNames[idx]}"; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public SnowGlobeTypeTwo Place + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - [Constructible] - public SnowGlobeTwo() - : this( (SnowGlobeTypeTwo) Utility.Random( 19 ) ) - { - } + public override string DefaultName + { + get + { + int idx = (int)m_Type; - [Constructible] - public SnowGlobeTwo( SnowGlobeTypeTwo type ) - { - m_Type = type; - } + if (idx < 0 || idx >= m_PlaceNames.Length) + return "a snowy scene"; - public SnowGlobeTwo( Serial serial ) - : base( serial ) - { - } + return $"a snowy scene of {m_PlaceNames[idx]}"; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - writer.WriteEncodedInt( (int) m_Type ); - } + writer.Write(0); // version + writer.WriteEncodedInt((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Type = (SnowGlobeTypeTwo) reader.ReadEncodedInt(); - break; - } - } - } - } + switch (version) + { + case 0: + { + m_Type = (SnowGlobeTypeTwo)reader.ReadEncodedInt(); + break; + } + } + } + } - public enum SnowGlobeTypeThree - { - Luna, - Umbra, - Zento, - Heartwood, - Covetous, - Deceit, - Destard, - Hythloth, - Khaldun, - Shame, - Wrong, - Doom, - TheCitadel, - ThePalaceofParoxysmus, - TheBlightedGrove, - ThePrismofLight - } + public enum SnowGlobeTypeThree + { + Luna, + Umbra, + Zento, + Heartwood, + Covetous, + Deceit, + Destard, + Hythloth, + Khaldun, + Shame, + Wrong, + Doom, + TheCitadel, + ThePalaceofParoxysmus, + TheBlightedGrove, + ThePrismofLight + } - public class SnowGlobeThree : SnowGlobe - { - private SnowGlobeTypeThree m_Type; + public class SnowGlobeThree : SnowGlobe + { + private SnowGlobeTypeThree m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public SnowGlobeTypeThree Place - { - get => m_Type; - set { m_Type = value; InvalidateProperties(); } - } + [Constructible] + public SnowGlobeThree() + : this((SnowGlobeTypeThree)Utility.Random(16)) + { + } - public override int LabelNumber - { - get - { - if ( m_Type >= SnowGlobeTypeThree.Covetous ) - return 1075440 + ( (int) m_Type - 4 ); + [Constructible] + public SnowGlobeThree(SnowGlobeTypeThree type) + { + m_Type = type; + } - return 1075294 + (int) m_Type; - } - } + public SnowGlobeThree(Serial serial) + : base(serial) + { + } - [Constructible] - public SnowGlobeThree() - : this( (SnowGlobeTypeThree) Utility.Random( 16 ) ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public SnowGlobeTypeThree Place + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - [Constructible] - public SnowGlobeThree( SnowGlobeTypeThree type ) - { - m_Type = type; - } + public override int LabelNumber + { + get + { + if (m_Type >= SnowGlobeTypeThree.Covetous) + return 1075440 + ((int)m_Type - 4); - public SnowGlobeThree( Serial serial ) - : base( serial ) - { - } + return 1075294 + (int)m_Type; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - writer.WriteEncodedInt( (int) m_Type ); - } + writer.Write(0); // version + writer.WriteEncodedInt((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Type = (SnowGlobeTypeThree) reader.ReadEncodedInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + m_Type = (SnowGlobeTypeThree)reader.ReadEncodedInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/SnowPiles.cs b/Scripts/Items/Special/Holiday/SnowPiles.cs index 65725ab80..2f140b4fc 100644 --- a/Scripts/Items/Special/Holiday/SnowPiles.cs +++ b/Scripts/Items/Special/Holiday/SnowPiles.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class SnowPileDeco : Item - { - public override string DefaultName => "Snow Pile"; - public override double DefaultWeight => 2.0; + public class SnowPileDeco : Item + { + private static readonly int[] m_Types = { 0x8E2, 0x8E0, 0x8E6, 0x8E5, 0x8E3 }; - private static readonly int[] m_Types = { 0x8E2, 0x8E0, 0x8E6, 0x8E5, 0x8E3 }; + [Constructible] + public SnowPileDeco() + : this(m_Types[Utility.Random(m_Types.Length)]) + { + } - [Constructible] - public SnowPileDeco() - : this(m_Types[Utility.Random(m_Types.Length)]) - { - } + [Constructible] + public SnowPileDeco(int itemid) + : base(itemid) + { + Hue = 0x481; + } - [Constructible] - public SnowPileDeco( int itemid ) - : base(itemid) - { - Hue = 0x481; - } + public SnowPileDeco(Serial serial) + : base(serial) + { + } - public SnowPileDeco(Serial serial) - : base(serial) - { - } + public override string DefaultName => "Snow Pile"; + public override double DefaultWeight => 2.0; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/SnowStatue.cs b/Scripts/Items/Special/Holiday/SnowStatue.cs index f2a009725..c3238c1a6 100644 --- a/Scripts/Items/Special/Holiday/SnowStatue.cs +++ b/Scripts/Items/Special/Holiday/SnowStatue.cs @@ -3,242 +3,250 @@ using Server.Network; namespace Server.Items { - [Flippable( 0x456E, 0x456F )] - public class SnowStatuePegasus : Item - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + [Flippable(0x456E, 0x456F)] + public class SnowStatuePegasus : Item + { + [Constructible] + public SnowStatuePegasus() + : base(0x456E) + { + } - [Constructible] - public SnowStatuePegasus() - : base( 0x456E ) - { - } + public SnowStatuePegasus(Serial serial) + : base(serial) + { + } - public SnowStatuePegasus( Serial serial ) - : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [Flippable( 0x4578, 0x4579 )] - public class SnowStatueSeahorse : Item - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + [Flippable(0x4578, 0x4579)] + public class SnowStatueSeahorse : Item + { + [Constructible] + public SnowStatueSeahorse() + : base(0x4578) + { + } - [Constructible] - public SnowStatueSeahorse() - : base( 0x4578 ) - { - } + public SnowStatueSeahorse(Serial serial) + : base(serial) + { + } - public SnowStatueSeahorse( Serial serial ) - : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [Flippable( 0x457A, 0x457B )] - public class SnowStatueMermaid : Item - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + [Flippable(0x457A, 0x457B)] + public class SnowStatueMermaid : Item + { + [Constructible] + public SnowStatueMermaid() + : base(0x457A) + { + } - [Constructible] - public SnowStatueMermaid() - : base( 0x457A ) - { - } + public SnowStatueMermaid(Serial serial) + : base(serial) + { + } - public SnowStatueMermaid( Serial serial ) - : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - [Flippable( 0x457C, 0x457D )] - public class SnowStatueGriffon : Item - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + [Flippable(0x457C, 0x457D)] + public class SnowStatueGriffon : Item + { + [Constructible] + public SnowStatueGriffon() + : base(0x457C) + { + } - [Constructible] - public SnowStatueGriffon() - : base( 0x457C ) - { - } + public SnowStatueGriffon(Serial serial) + : base(serial) + { + } - public SnowStatueGriffon( Serial serial ) - : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class SnowStatueDeed : Item - { - public override int LabelNumber => 1114296; // snow statue deed - public override double DefaultWeight => 1.0; + public class SnowStatueDeed : Item + { + [Constructible] + public SnowStatueDeed() + : base(0x14F0) + { + LootType = LootType.Blessed; + } - [Constructible] - public SnowStatueDeed() - : base( 0x14F0 ) - { - LootType = LootType.Blessed; - } + public SnowStatueDeed(Serial serial) + : base(serial) + { + } - public SnowStatueDeed( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1114296; // snow statue deed + public override double DefaultWeight => 1.0; - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } + int version = reader.ReadEncodedInt(); + } - private class InternalGump : Gump - { - private SnowStatueDeed m_Deed; + private class InternalGump : Gump + { + private SnowStatueDeed m_Deed; - public InternalGump( SnowStatueDeed deed ) : base( 100, 200 ) - { - m_Deed = deed; + public InternalGump(SnowStatueDeed deed) : base(100, 200) + { + m_Deed = deed; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); - AddBackground( 0, 0, 360, 225, 0xA28 ); + AddPage(0); + AddBackground(0, 0, 360, 225, 0xA28); - AddPage( 1 ); - AddLabel( 45, 15, 0, "Select One:" ); + AddPage(1); + AddLabel(45, 15, 0, "Select One:"); - AddItem( 35, 75, 0x456E ); - AddButton( 65, 50, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); + AddItem(35, 75, 0x456E); + AddButton(65, 50, 0x845, 0x846, 1, GumpButtonType.Reply, 0); - AddItem( 120, 75, 0x4578 ); - AddButton( 135, 50, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); + AddItem(120, 75, 0x4578); + AddButton(135, 50, 0x845, 0x846, 2, GumpButtonType.Reply, 0); - AddItem( 190, 75, 0x457A ); - AddButton( 205, 50, 0x845, 0x846, 3, GumpButtonType.Reply, 0 ); + AddItem(190, 75, 0x457A); + AddButton(205, 50, 0x845, 0x846, 3, GumpButtonType.Reply, 0); - AddItem( 250, 75, 0x457C ); - AddButton( 275, 50, 0x845, 0x846, 4, GumpButtonType.Reply, 0 ); - } + AddItem(250, 75, 0x457C); + AddButton(275, 50, 0x845, 0x846, 4, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted) + return; - Mobile from = sender.Mobile; + Mobile from = sender.Mobile; - if ( !m_Deed.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it - return; - } + if (!m_Deed.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it + return; + } - Item statue = null; + Item statue = null; - switch ( info.ButtonID ) - { - case 1: statue = new SnowStatuePegasus(); break; - case 2: statue = new SnowStatueSeahorse(); break; - case 3: statue = new SnowStatueMermaid(); break; - case 4: statue = new SnowStatueGriffon(); break; - } + switch (info.ButtonID) + { + case 1: + statue = new SnowStatuePegasus(); + break; + case 2: + statue = new SnowStatueSeahorse(); + break; + case 3: + statue = new SnowStatueMermaid(); + break; + case 4: + statue = new SnowStatueGriffon(); + break; + } - if ( statue == null ) - return; + if (statue == null) + return; - if ( !from.PlaceInBackpack( statue ) ) - { - statue.Delete(); - from.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - { - m_Deed.Delete(); - } - } - } - } -} + if (!from.PlaceInBackpack(statue)) + { + statue.Delete(); + from.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + m_Deed.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Snowflakes.cs b/Scripts/Items/Special/Holiday/Snowflakes.cs index b2535f8ef..641b4451a 100644 --- a/Scripts/Items/Special/Holiday/Snowflakes.cs +++ b/Scripts/Items/Special/Holiday/Snowflakes.cs @@ -1,58 +1,58 @@ namespace Server.Items { - public class BlueSnowflake : Item - { - [Constructible] - public BlueSnowflake() : base( 0x232E ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class BlueSnowflake : Item + { + [Constructible] + public BlueSnowflake() : base(0x232E) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public BlueSnowflake( Serial serial ) : base( serial ) - { - } + public BlueSnowflake(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class WhiteSnowflake : Item - { - [Constructible] - public WhiteSnowflake() : base( 0x232F ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class WhiteSnowflake : Item + { + [Constructible] + public WhiteSnowflake() : base(0x232F) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public WhiteSnowflake( Serial serial ) : base( serial ) - { - } + public WhiteSnowflake(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Snowman.cs b/Scripts/Items/Special/Holiday/Snowman.cs index ff68e7a24..776eb38b6 100644 --- a/Scripts/Items/Special/Holiday/Snowman.cs +++ b/Scripts/Items/Special/Holiday/Snowman.cs @@ -1,154 +1,159 @@ namespace Server.Items { - [Flippable( 0x2328, 0x2329 )] - public class Snowman : Item, IDyable - { - public static string GetRandomTitle() - { - // All hail OSI staff - string[] titles = { - /* 1 */ "Backflash", - /* 2 */ "Carbon", - /* 3 */ "Colbalistic", - /* 4 */ "Comforl", - /* 5 */ "Coppacchia", - /* 6 */ "Cyrus", - /* 7 */ "DannyB", - /* 8 */ "DJSoul", - /* 9 */ "DraconisRex", - /* 10 */ "Earia", - /* 11 */ "Foster", - /* 12 */ "Gonzo", - /* 13 */ "Haan", - /* 14 */ "Halona", - /* 15 */ "Hugo", - /* 16 */ "Hyacinth", - /* 17 */ "Imirian", - /* 18 */ "Jinsol", - /* 19 */ "Liciatia", - /* 20 */ "Loewen", - /* 21 */ "Loke", - /* 22 */ "Magnus", - /* 23 */ "Maleki", - /* 24 */ "Morpheus", - /* 25 */ "Obberron", - /* 26 */ "Odee", - /* 27 */ "Orbeus", - /* 28 */ "Pax", - /* 29 */ "Phields", - /* 30 */ "Pigpen", - /* 31 */ "Platinum", - /* 32 */ "Polpol", - /* 33 */ "Prume", - /* 34 */ "Quinnly", - /* 35 */ "Ragnarok", - /* 36 */ "Rend", - /* 37 */ "Roland", - /* 38 */ "RyanM", - /* 39 */ "Screach", - /* 40 */ "Seraph", - /* 41 */ "Silvani", - /* 42 */ "Sherbear", - /* 43 */ "SkyWalker", - /* 44 */ "Snark", - /* 45 */ "Sowl", - /* 46 */ "Spada", - /* 47 */ "Starblade", - /* 48 */ "Tenacious", - /* 49 */ "Tnez", - /* 50 */ "Wasia", - /* 51 */ "Zilo", - /* 52 */ "Zippy", - /* 53 */ "Zoer" - }; + [Flippable(0x2328, 0x2329)] + public class Snowman : Item, IDyable + { + private string m_Title; - if ( titles.Length > 0 ) - return titles[Utility.Random( titles.Length )]; + [Constructible] + public Snowman() : this(Utility.RandomDyedHue(), GetRandomTitle()) + { + } - return null; - } + [Constructible] + public Snowman(int hue) : this(hue, GetRandomTitle()) + { + } - private string m_Title; + [Constructible] + public Snowman(string title) : this(Utility.RandomDyedHue(), title) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public string Title - { - get => m_Title; - set{ m_Title = value; InvalidateProperties(); } - } + [Constructible] + public Snowman(int hue, string title) : base(Utility.Random(0x2328, 2)) + { + Weight = 10.0; + Hue = hue; + LootType = LootType.Blessed; - [Constructible] - public Snowman() : this( Utility.RandomDyedHue(), GetRandomTitle() ) - { - } + m_Title = title; + } - [Constructible] - public Snowman( int hue ) : this( hue, GetRandomTitle() ) - { - } + public Snowman(Serial serial) : base(serial) + { + } - [Constructible] - public Snowman( string title ) : this( Utility.RandomDyedHue(), title ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public string Title + { + get => m_Title; + set + { + m_Title = value; + InvalidateProperties(); + } + } - [Constructible] - public Snowman( int hue, string title ) : base( Utility.Random( 0x2328, 2 ) ) - { - Weight = 10.0; - Hue = hue; - LootType = LootType.Blessed; + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - m_Title = title; - } + Hue = sender.DyedHue; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + return true; + } - if ( m_Title != null ) - list.Add( 1062841, m_Title ); // ~1_NAME~ the Snowman - } + public static string GetRandomTitle() + { + // All hail OSI staff + string[] titles = + { + /* 1 */ "Backflash", + /* 2 */ "Carbon", + /* 3 */ "Colbalistic", + /* 4 */ "Comforl", + /* 5 */ "Coppacchia", + /* 6 */ "Cyrus", + /* 7 */ "DannyB", + /* 8 */ "DJSoul", + /* 9 */ "DraconisRex", + /* 10 */ "Earia", + /* 11 */ "Foster", + /* 12 */ "Gonzo", + /* 13 */ "Haan", + /* 14 */ "Halona", + /* 15 */ "Hugo", + /* 16 */ "Hyacinth", + /* 17 */ "Imirian", + /* 18 */ "Jinsol", + /* 19 */ "Liciatia", + /* 20 */ "Loewen", + /* 21 */ "Loke", + /* 22 */ "Magnus", + /* 23 */ "Maleki", + /* 24 */ "Morpheus", + /* 25 */ "Obberron", + /* 26 */ "Odee", + /* 27 */ "Orbeus", + /* 28 */ "Pax", + /* 29 */ "Phields", + /* 30 */ "Pigpen", + /* 31 */ "Platinum", + /* 32 */ "Polpol", + /* 33 */ "Prume", + /* 34 */ "Quinnly", + /* 35 */ "Ragnarok", + /* 36 */ "Rend", + /* 37 */ "Roland", + /* 38 */ "RyanM", + /* 39 */ "Screach", + /* 40 */ "Seraph", + /* 41 */ "Silvani", + /* 42 */ "Sherbear", + /* 43 */ "SkyWalker", + /* 44 */ "Snark", + /* 45 */ "Sowl", + /* 46 */ "Spada", + /* 47 */ "Starblade", + /* 48 */ "Tenacious", + /* 49 */ "Tnez", + /* 50 */ "Wasia", + /* 51 */ "Zilo", + /* 52 */ "Zippy", + /* 53 */ "Zoer" + }; - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + if (titles.Length > 0) + return titles[Utility.Random(titles.Length)]; - Hue = sender.DyedHue; + return null; + } - return true; - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public Snowman( Serial serial ) : base( serial ) - { - } + if (m_Title != null) + list.Add(1062841, m_Title); // ~1_NAME~ the Snowman + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (string) m_Title ); - } + writer.Write(m_Title); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_Title = reader.ReadString(); - break; - } - } + switch (version) + { + case 1: + { + m_Title = reader.ReadString(); + break; + } + } - Utility.Intern( ref m_Title ); - } - } + Utility.Intern(ref m_Title); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Stockings.cs b/Scripts/Items/Special/Holiday/Stockings.cs index d15c0e478..495dfb366 100644 --- a/Scripts/Items/Special/Holiday/Stockings.cs +++ b/Scripts/Items/Special/Holiday/Stockings.cs @@ -1,61 +1,60 @@ namespace Server.Items { - [Furniture] - [FlippableAttribute( 0x2bd9, 0x2bda )] - public class GreenStocking : BaseContainer - { - public override int DefaultGumpID => 0x103; - public override int DefaultDropSound => 0x42; + [Furniture] + [Flippable(0x2bd9, 0x2bda)] + public class GreenStocking : BaseContainer + { + [Constructible] + public GreenStocking() : base(Utility.Random(0x2BD9, 2)) + { + } - [Constructible] - public GreenStocking() : base ( Utility.Random( 0x2BD9, 2 ) ) - { - } + public GreenStocking(Serial serial) : base(serial) + { + } - public GreenStocking( Serial serial ) : base( serial ) - { - } + public override int DefaultGumpID => 0x103; + public override int DefaultDropSound => 0x42; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - [Furniture] - [FlippableAttribute( 0x2bdb, 0x2bdc )] - public class RedStocking : BaseContainer - { - public override int DefaultGumpID => 0x103; - public override int DefaultDropSound => 0x42; + [Furniture] + [Flippable(0x2bdb, 0x2bdc)] + public class RedStocking : BaseContainer + { + [Constructible] + public RedStocking() : base(Utility.Random(0x2BDB, 2)) + { + } - [Constructible] - public RedStocking() : base ( Utility.Random( 0x2BDB, 2 ) ) - { - } + public RedStocking(Serial serial) : base(serial) + { + } - public RedStocking( Serial serial ) : base( serial ) - { - } + public override int DefaultGumpID => 0x103; + public override int DefaultDropSound => 0x42; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); // version + } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/WinterGiftPackage2003.cs b/Scripts/Items/Special/Holiday/WinterGiftPackage2003.cs index 4693b79f7..6cc58f11c 100644 --- a/Scripts/Items/Special/Holiday/WinterGiftPackage2003.cs +++ b/Scripts/Items/Special/Holiday/WinterGiftPackage2003.cs @@ -1,33 +1,33 @@ namespace Server.Items { - [Flippable( 0x232A, 0x232B )] - public class WinterGiftPackage2003 : GiftBox - { - [Constructible] - public WinterGiftPackage2003() - { - DropItem( new Snowman() ); - DropItem( new WreathDeed() ); - DropItem( new BlueSnowflake() ); - DropItem( new RedPoinsettia() ); - } + [Flippable(0x232A, 0x232B)] + public class WinterGiftPackage2003 : GiftBox + { + [Constructible] + public WinterGiftPackage2003() + { + DropItem(new Snowman()); + DropItem(new WreathDeed()); + DropItem(new BlueSnowflake()); + DropItem(new RedPoinsettia()); + } - public WinterGiftPackage2003( Serial serial ) : base( serial ) - { - } + public WinterGiftPackage2003(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/Wreath.cs b/Scripts/Items/Special/Holiday/Wreath.cs index 09f19eafb..3465edbc9 100644 --- a/Scripts/Items/Special/Holiday/Wreath.cs +++ b/Scripts/Items/Special/Holiday/Wreath.cs @@ -6,311 +6,311 @@ using Server.Targeting; namespace Server.Items { - public class WreathAddon : Item, IDyable, IAddon - { - [Constructible] - public WreathAddon() : this( Utility.RandomDyedHue() ) - { - } + public class WreathAddon : Item, IDyable, IAddon + { + [Constructible] + public WreathAddon() : this(Utility.RandomDyedHue()) + { + } - [Constructible] - public WreathAddon( int hue ) : base( 0x232C ) - { - Hue = hue; - Movable = false; - } + [Constructible] + public WreathAddon(int hue) : base(0x232C) + { + Hue = hue; + Movable = false; + } - public WreathAddon( Serial serial ) : base( serial ) - { - } + public WreathAddon(Serial serial) : base(serial) + { + } - public bool CouldFit( IPoint3D p, Map map ) - { - if ( !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; + public bool CouldFit(IPoint3D p, Map map) + { + if (!map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; - if ( ItemID == 0x232C ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // North wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // West wall - } + if (ItemID == 0x232C) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // North wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // West wall + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Item Deed => new WreathDeed(Hue); - writer.Write( (int) 0 ); // version - } + public virtual bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + BaseHouse house = BaseHouse.FindHouseAt(this); - int version = reader.ReadInt(); + if (house != null && house.IsCoOwner(from)) + { + if (from.InRange(GetWorldLocation(), 1)) + { + Hue = sender.DyedHue; + return true; + } - Timer.DelayCall( TimeSpan.Zero, FixMovingCrate ); - } + from.SendLocalizedMessage(500295); // You are too far away to do that. + return false; + } - private void FixMovingCrate() - { - if ( Deleted ) - return; + return false; + } - if ( Movable || IsLockedDown ) - { - Item deed = Deed; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( Parent is Item item ) - { - item.AddItem( deed ); - deed.Location = Location; - } - else - { - deed.MoveToWorld( Location, Map ); - } + writer.Write(0); // version + } - Delete(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public Item Deed => new WreathDeed( Hue ); + int version = reader.ReadInt(); - public override void OnDoubleClick( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + Timer.DelayCall(TimeSpan.Zero, FixMovingCrate); + } - if ( house != null && house.IsCoOwner( from ) ) - { - if ( from.InRange( GetWorldLocation(), 3 ) ) - { - from.CloseGump( typeof( WreathAddonGump ) ); - from.SendGump( new WreathAddonGump( from, this ) ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } - } + private void FixMovingCrate() + { + if (Deleted) + return; - public virtual bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + if (Movable || IsLockedDown) + { + Item deed = Deed; - BaseHouse house = BaseHouse.FindHouseAt( this ); + if (Parent is Item item) + { + item.AddItem(deed); + deed.Location = Location; + } + else + { + deed.MoveToWorld(Location, Map); + } - if ( house != null && house.IsCoOwner( from ) ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - Hue = sender.DyedHue; - return true; - } + Delete(); + } + } - from.SendLocalizedMessage( 500295 ); // You are too far away to do that. - return false; - } + public override void OnDoubleClick(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - return false; - } + if (house != null && house.IsCoOwner(from)) + { + if (from.InRange(GetWorldLocation(), 3)) + { + from.CloseGump(typeof(WreathAddonGump)); + from.SendGump(new WreathAddonGump(from, this)); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + } - private class WreathAddonGump : Gump - { - private Mobile m_From; - private WreathAddon m_Addon; + private class WreathAddonGump : Gump + { + private WreathAddon m_Addon; + private Mobile m_From; - public WreathAddonGump( Mobile from, WreathAddon addon ) : base( 150, 50 ) - { - m_From = from; - m_Addon = addon; + public WreathAddonGump(Mobile from, WreathAddon addon) : base(150, 50) + { + m_From = from; + m_Addon = addon; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 220, 170, 0x13BE ); - AddBackground( 10, 10, 200, 150, 0xBB8 ); - AddHtmlLocalized( 20, 30, 180, 60, 1062839, false, false ); // Do you wish to re-deed this decoration? - AddHtmlLocalized( 55, 100, 160, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 100, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 125, 160, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 125, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - } + AddBackground(0, 0, 220, 170, 0x13BE); + AddBackground(10, 10, 200, 150, 0xBB8); + AddHtmlLocalized(20, 30, 180, 60, 1062839, false, false); // Do you wish to re-deed this decoration? + AddHtmlLocalized(55, 100, 160, 25, 1011011, false, false); // CONTINUE + AddButton(20, 100, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 125, 160, 25, 1011012, false, false); // CANCEL + AddButton(20, 125, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Addon.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Addon.Deleted) + return; - if ( info.ButtonID == 1 ) - { - if ( m_From.InRange( m_Addon.GetWorldLocation(), 3 ) ) - { - m_From.AddToBackpack( m_Addon.Deed ); - m_Addon.Delete(); - } - else - { - m_From.SendLocalizedMessage( 500295 ); // You are too far away to do that. - } - } - } - } - } + if (info.ButtonID == 1) + { + if (m_From.InRange(m_Addon.GetWorldLocation(), 3)) + { + m_From.AddToBackpack(m_Addon.Deed); + m_Addon.Delete(); + } + else + { + m_From.SendLocalizedMessage(500295); // You are too far away to do that. + } + } + } + } + } - [Flippable( 0x14F0, 0x14EF )] - public class WreathDeed : Item - { - public override int LabelNumber => 1062837; // holiday wreath deed + [Flippable(0x14F0, 0x14EF)] + public class WreathDeed : Item + { + [Constructible] + public WreathDeed() : this(Utility.RandomDyedHue()) + { + } - [Constructible] - public WreathDeed() : this( Utility.RandomDyedHue() ) - { - } + [Constructible] + public WreathDeed(int hue) : base(0x14F0) + { + Weight = 1.0; + Hue = hue; + LootType = LootType.Blessed; + } - [Constructible] - public WreathDeed( int hue ) : base( 0x14F0 ) - { - Weight = 1.0; - Hue = hue; - LootType = LootType.Blessed; - } + public WreathDeed(Serial serial) : base(serial) + { + } - public WreathDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1062837; // holiday wreath deed - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house != null && house.IsCoOwner( from ) ) - { - from.SendLocalizedMessage( 1062838 ); // Where would you like to place this decoration? - from.BeginTarget( -1, true, TargetFlags.None, Placement_OnTarget, null ); - } - else - { - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + if (house != null && house.IsCoOwner(from)) + { + from.SendLocalizedMessage(1062838); // Where would you like to place this decoration? + from.BeginTarget(-1, true, TargetFlags.None, Placement_OnTarget, null); + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public void Placement_OnTarget( Mobile from, object targeted, object state ) - { - if ( !(targeted is IPoint3D p) ) - return; + public void Placement_OnTarget(Mobile from, object targeted, object state) + { + if (!(targeted is IPoint3D p)) + return; - Point3D loc = new Point3D( p ); + Point3D loc = new Point3D(p); - BaseHouse house = BaseHouse.FindHouseAt( loc, from.Map, 16 ); + BaseHouse house = BaseHouse.FindHouseAt(loc, from.Map, 16); - if ( house != null && house.IsCoOwner( from ) ) - { - bool northWall = BaseAddon.IsWall( loc.X, loc.Y - 1, loc.Z, from.Map ); - bool westWall = BaseAddon.IsWall( loc.X - 1, loc.Y, loc.Z, from.Map ); + if (house != null && house.IsCoOwner(from)) + { + bool northWall = BaseAddon.IsWall(loc.X, loc.Y - 1, loc.Z, from.Map); + bool westWall = BaseAddon.IsWall(loc.X - 1, loc.Y, loc.Z, from.Map); - if ( northWall && westWall ) - from.SendGump( new WreathDeedGump( from, loc, this ) ); - else - PlaceAddon( from, loc, northWall, westWall ); - } - else - { - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - } + if (northWall && westWall) + from.SendGump(new WreathDeedGump(from, loc, this)); + else + PlaceAddon(from, loc, northWall, westWall); + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } - private void PlaceAddon( Mobile from, Point3D loc, bool northWall, bool westWall ) - { - if ( Deleted ) - return; + private void PlaceAddon(Mobile from, Point3D loc, bool northWall, bool westWall) + { + if (Deleted) + return; - BaseHouse house = BaseHouse.FindHouseAt( loc, from.Map, 16 ); + BaseHouse house = BaseHouse.FindHouseAt(loc, from.Map, 16); - if ( house == null || !house.IsCoOwner( from ) ) - { - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - return; - } + if (house == null || !house.IsCoOwner(from)) + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + return; + } - int itemID = 0; + int itemID = 0; - if ( northWall ) - itemID = 0x232C; - else if ( westWall ) - itemID = 0x232D; - else - from.SendLocalizedMessage( 1062840 ); // The decoration must be placed next to a wall. + if (northWall) + itemID = 0x232C; + else if (westWall) + itemID = 0x232D; + else + from.SendLocalizedMessage(1062840); // The decoration must be placed next to a wall. - if ( itemID > 0 ) - { - Item addon = new WreathAddon( Hue ); + if (itemID > 0) + { + Item addon = new WreathAddon(Hue); - addon.ItemID = itemID; - addon.MoveToWorld( loc, from.Map ); + addon.ItemID = itemID; + addon.MoveToWorld(loc, from.Map); - house.Addons.Add( addon ); - Delete(); - } - } + house.Addons.Add(addon); + Delete(); + } + } - private class WreathDeedGump : Gump - { - private Mobile m_From; - private Point3D m_Loc; - private WreathDeed m_Deed; + private class WreathDeedGump : Gump + { + private WreathDeed m_Deed; + private Mobile m_From; + private Point3D m_Loc; - public WreathDeedGump( Mobile from, Point3D loc, WreathDeed deed ) : base( 150, 50 ) - { - m_From = from; - m_Loc = loc; - m_Deed = deed; + public WreathDeedGump(Mobile from, Point3D loc, WreathDeed deed) : base(150, 50) + { + m_From = from; + m_Loc = loc; + m_Deed = deed; - AddBackground( 0, 0, 300, 150, 0xA28 ); + AddBackground(0, 0, 300, 150, 0xA28); - AddPage( 0 ); + AddPage(0); - AddItem( 90, 30, 0x232D ); - AddItem( 180, 30, 0x232C ); - AddButton( 50, 35, 0x868, 0x869, 1, GumpButtonType.Reply, 0 ); - AddButton( 145, 35, 0x868, 0x869, 2, GumpButtonType.Reply, 0 ); - } + AddItem(90, 30, 0x232D); + AddItem(180, 30, 0x232C); + AddButton(50, 35, 0x868, 0x869, 1, GumpButtonType.Reply, 0); + AddButton(145, 35, 0x868, 0x869, 2, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed.Deleted) + return; - switch( info.ButtonID ) - { - case 1: - m_Deed.PlaceAddon( m_From, m_Loc, false, true ); - break; - case 2: - m_Deed.PlaceAddon( m_From, m_Loc, true, false ); - break; - } - } - } - } -} + switch (info.ButtonID) + { + case 1: + m_Deed.PlaceAddon(m_From, m_Loc, false, true); + break; + case 2: + m_Deed.PlaceAddon(m_From, m_Loc, true, false); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Holiday/WristWatch.cs b/Scripts/Items/Special/Holiday/WristWatch.cs index e13de0d15..80e2a3b58 100644 --- a/Scripts/Items/Special/Holiday/WristWatch.cs +++ b/Scripts/Items/Special/Holiday/WristWatch.cs @@ -1,36 +1,36 @@ namespace Server.Items { - public class WristWatch : Clock - { - public override int LabelNumber => 1041421; // a wrist watch - public override double DefaultWeight => 1.0; + public class WristWatch : Clock + { + [Constructible] + public WristWatch() + : base(0x1086) + { + Weight = DefaultWeight; + LootType = LootType.Blessed; + Layer = Layer.Bracelet; + } - [Constructible] - public WristWatch() - : base( 0x1086 ) - { - Weight = DefaultWeight; - LootType = LootType.Blessed; - Layer = Layer.Bracelet; - } + public WristWatch(Serial serial) + : base(serial) + { + } - public WristWatch( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1041421; // a wrist watch + public override double DefaultWeight => 1.0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/House Raffle/HouseRaffleDeed.cs b/Scripts/Items/Special/House Raffle/HouseRaffleDeed.cs index 6edbbf195..8e7fbb7e7 100644 --- a/Scripts/Items/Special/House Raffle/HouseRaffleDeed.cs +++ b/Scripts/Items/Special/House Raffle/HouseRaffleDeed.cs @@ -3,202 +3,218 @@ using Server.Gumps; namespace Server.Items { - public class HouseRaffleDeed : Item - { - private HouseRaffleStone m_Stone; - private Point3D m_PlotLocation; - private Map m_Facet; - private Mobile m_AwardedTo; + public class HouseRaffleDeed : Item + { + private Mobile m_AwardedTo; + private Map m_Facet; + private Point3D m_PlotLocation; + private HouseRaffleStone m_Stone; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public HouseRaffleStone Stone - { - get => m_Stone; - set { m_Stone = value; InvalidateProperties(); } - } + [Constructible] + public HouseRaffleDeed() + : this(null, null) + { + } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public Point3D PlotLocation - { - get => m_PlotLocation; - set { m_PlotLocation = value; InvalidateProperties(); } - } + public HouseRaffleDeed(HouseRaffleStone stone, Mobile m) : base(0x2830) + { + m_Stone = stone; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public Map PlotFacet - { - get => m_Facet; - set { m_Facet = value; InvalidateProperties(); } - } + if (stone != null) + { + m_PlotLocation = stone.GetPlotCenter(); + m_Facet = stone.PlotFacet; + } - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public Mobile AwardedTo - { - get => m_AwardedTo; - set { m_AwardedTo = value; InvalidateProperties(); } - } + m_AwardedTo = m; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public bool IsExpired => ( m_Stone == null || m_Stone.Deleted || m_Stone.IsExpired ); + LootType = LootType.Blessed; + Hue = 0x501; + } - public override string DefaultName => "a writ of lease"; + public HouseRaffleDeed(Serial serial) + : base(serial) + { + } - public override double DefaultWeight => 1.0; + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public HouseRaffleStone Stone + { + get => m_Stone; + set + { + m_Stone = value; + InvalidateProperties(); + } + } - [Constructible] - public HouseRaffleDeed() - : this ( null, null ) - { - } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public Point3D PlotLocation + { + get => m_PlotLocation; + set + { + m_PlotLocation = value; + InvalidateProperties(); + } + } - public HouseRaffleDeed( HouseRaffleStone stone, Mobile m ) : base( 0x2830 ) - { - m_Stone = stone; + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public Map PlotFacet + { + get => m_Facet; + set + { + m_Facet = value; + InvalidateProperties(); + } + } - if ( stone != null ) - { - m_PlotLocation = stone.GetPlotCenter(); - m_Facet = stone.PlotFacet; - } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public Mobile AwardedTo + { + get => m_AwardedTo; + set + { + m_AwardedTo = value; + InvalidateProperties(); + } + } - m_AwardedTo = m; + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public bool IsExpired => m_Stone == null || m_Stone.Deleted || m_Stone.IsExpired; - LootType = LootType.Blessed; - Hue = 0x501; - } + public override string DefaultName => "a writ of lease"; - public HouseRaffleDeed( Serial serial ) - : base( serial ) - { - } + public override double DefaultWeight => 1.0; - public bool ValidLocation() - { - return ( m_PlotLocation != Point3D.Zero && m_Facet != null && m_Facet != Map.Internal ); - } + public bool ValidLocation() + { + return m_PlotLocation != Point3D.Zero && m_Facet != null && m_Facet != Map.Internal; + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( ValidLocation() ) - { - list.Add( 1060658, "location\t{0}", HouseRaffleStone.FormatLocation( m_PlotLocation, m_Facet, false ) ); // ~1_val~: ~2_val~ - list.Add( 1060659, "facet\t{0}", m_Facet ); // ~1_val~: ~2_val~ - list.Add( 1150486 ); // [Marked Item] - } + if (ValidLocation()) + { + list.Add(1060658, "location\t{0}", + HouseRaffleStone.FormatLocation(m_PlotLocation, m_Facet, false)); // ~1_val~: ~2_val~ + list.Add(1060659, "facet\t{0}", m_Facet); // ~1_val~: ~2_val~ + list.Add(1150486); // [Marked Item] + } - if ( IsExpired ) - list.Add( 1150487 ); // [Expired] + if (IsExpired) + list.Add(1150487); // [Expired] - //list.Add( 1060660, "shard\t{0}", ServerList.ServerName ); // ~1_val~: ~2_val~ - } + //list.Add( 1060660, "shard\t{0}", ServerList.ServerName ); // ~1_val~: ~2_val~ + } - public override void OnDoubleClick( Mobile from ) - { - if ( !ValidLocation() ) - return; + public override void OnDoubleClick(Mobile from) + { + if (!ValidLocation()) + return; - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( WritOfLeaseGump ) ); - from.SendGump( new WritOfLeaseGump( this ) ); - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(WritOfLeaseGump)); + from.SendGump(new WritOfLeaseGump(this)); + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( m_Stone ); - writer.Write( m_PlotLocation ); - writer.Write( m_Facet ); - writer.Write( m_AwardedTo ); - } + writer.Write(m_Stone); + writer.Write(m_PlotLocation); + writer.Write(m_Facet); + writer.Write(m_AwardedTo); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_Stone = reader.ReadItem(); + switch (version) + { + case 1: + { + m_Stone = reader.ReadItem(); - goto case 0; - } - case 0: - { - m_PlotLocation = reader.ReadPoint3D(); - m_Facet = reader.ReadMap(); - m_AwardedTo = reader.ReadMobile(); + goto case 0; + } + case 0: + { + m_PlotLocation = reader.ReadPoint3D(); + m_Facet = reader.ReadMap(); + m_AwardedTo = reader.ReadMobile(); - break; - } - } - } + break; + } + } + } - private class WritOfLeaseGump : Gump - { - public WritOfLeaseGump( HouseRaffleDeed deed ) : base( 150, 50 ) - { - AddPage( 0 ); + private class WritOfLeaseGump : Gump + { + public WritOfLeaseGump(HouseRaffleDeed deed) : base(150, 50) + { + AddPage(0); - AddImage( 0, 0, 9380 ); - AddImage( 114, 0, 9381 ); - AddImage( 171, 0, 9382 ); - AddImage( 0, 140, 9383 ); - AddImage( 114, 140, 9384 ); - AddImage( 171, 140, 9385 ); - AddImage( 0, 182, 9383 ); - AddImage( 114, 182, 9384 ); - AddImage( 171, 182, 9385 ); - AddImage( 0, 224, 9383 ); - AddImage( 114, 224, 9384 ); - AddImage( 171, 224, 9385 ); - AddImage( 0, 266, 9386 ); - AddImage( 114, 266, 9387 ); - AddImage( 171, 266, 9388 ); + AddImage(0, 0, 9380); + AddImage(114, 0, 9381); + AddImage(171, 0, 9382); + AddImage(0, 140, 9383); + AddImage(114, 140, 9384); + AddImage(171, 140, 9385); + AddImage(0, 182, 9383); + AddImage(114, 182, 9384); + AddImage(171, 182, 9385); + AddImage(0, 224, 9383); + AddImage(114, 224, 9384); + AddImage(171, 224, 9385); + AddImage(0, 266, 9386); + AddImage(114, 266, 9387); + AddImage(171, 266, 9388); - AddHtmlLocalized( 30, 48, 229, 20, 1150484, 200, false, false ); // WRIT OF LEASE - AddHtml( 28, 75, 231, 280, FormatDescription( deed ), false, true ); - } + AddHtmlLocalized(30, 48, 229, 20, 1150484, 200, false, false); // WRIT OF LEASE + AddHtml(28, 75, 231, 280, FormatDescription(deed), false, true); + } - private static string FormatDescription( HouseRaffleDeed deed ) - { - if ( deed == null ) - return string.Empty; + private static string FormatDescription(HouseRaffleDeed deed) + { + if (deed == null) + return string.Empty; - if ( deed.IsExpired ) - { - return "" + - "This deed once entitled the bearer to build a house on the plot of land " + - $"located at {HouseRaffleStone.FormatLocation(deed.PlotLocation, deed.PlotFacet, false)} on the {deed.PlotFacet} facet.

" + - "The deed has expired, and now the indicated plot of land " + - "is subject to normal house construction rules.

" + - "This deed functions as a recall rune marked for the location of the plot it represents." + - "
"; - } + if (deed.IsExpired) + return "" + + "This deed once entitled the bearer to build a house on the plot of land " + + $"located at {HouseRaffleStone.FormatLocation(deed.PlotLocation, deed.PlotFacet, false)} on the {deed.PlotFacet} facet.

" + + "The deed has expired, and now the indicated plot of land " + + "is subject to normal house construction rules.

" + + "This deed functions as a recall rune marked for the location of the plot it represents." + + "
"; - int daysLeft = (int)Math.Ceiling( ( deed.Stone.Started + deed.Stone.Duration + HouseRaffleStone.ExpirationTime - DateTime.UtcNow ).TotalDays ); + int daysLeft = (int)Math.Ceiling((deed.Stone.Started + deed.Stone.Duration + + HouseRaffleStone.ExpirationTime - DateTime.UtcNow).TotalDays); - return "" + "This deed entitles the bearer to build a house on the plot of land " + - $"located at {HouseRaffleStone.FormatLocation(deed.PlotLocation, deed.PlotFacet, false)} on the {deed.PlotFacet} facet.

" + - $"The deed will expire after {daysLeft} more day{((daysLeft == 1) ? "" : "s")} have passed, and at that time the right to place " + - "a house reverts to normal house construction rules.

" + - "This deed functions as a recall rune marked for the location of the plot it represents.

" + - "To place a house on the deeded plot, you must simply have this deed in your backpack " + - "or bank box when using a House Placement Tool there." + "
"; - } - } - } -} + return "" + "This deed entitles the bearer to build a house on the plot of land " + + $"located at {HouseRaffleStone.FormatLocation(deed.PlotLocation, deed.PlotFacet, false)} on the {deed.PlotFacet} facet.

" + + $"The deed will expire after {daysLeft} more day{(daysLeft == 1 ? "" : "s")} have passed, and at that time the right to place " + + "a house reverts to normal house construction rules.

" + + "This deed functions as a recall rune marked for the location of the plot it represents.

" + + "To place a house on the deeded plot, you must simply have this deed in your backpack " + + "or bank box when using a House Placement Tool there." + "
"; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/House Raffle/HouseRaffleManagementGump.cs b/Scripts/Items/Special/House Raffle/HouseRaffleManagementGump.cs index a3e3468f1..016b6bd20 100644 --- a/Scripts/Items/Special/House Raffle/HouseRaffleManagementGump.cs +++ b/Scripts/Items/Special/House Raffle/HouseRaffleManagementGump.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Generic; using Server.Accounting; using Server.Items; @@ -6,325 +5,313 @@ using Server.Network; namespace Server.Gumps { - public class HouseRaffleManagementGump : Gump - { - public enum SortMethod - { - Default, - Name, - Account, - Address - } - - public string Right( string text ) - { - return $"
{text}
"; - } - - public string Center( string text ) - { - return $"
{text}
"; - } - - public string Color( string text, int color ) - { - return $"{text}"; - } - - public const int LabelColor = 0xFFFFFF; - public const int HighlightColor = 0x11EE11; - - private HouseRaffleStone m_Stone; - private int m_Page; - private List m_List; - private SortMethod m_Sort; - - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; - int buttonId = info.ButtonID; - - switch ( buttonId ) - { - case 1: // Previous - { - if ( m_Page > 0 ) - m_Page--; - - from.SendGump( new HouseRaffleManagementGump( m_Stone, m_Sort, m_Page ) ); - - break; - } - case 2: // Next - { - if ( (m_Page + 1) * 10 < m_Stone.Entries.Count ) - m_Page++; - - from.SendGump( new HouseRaffleManagementGump( m_Stone, m_Sort, m_Page ) ); - - break; - } - case 3: // Sort by name - { - from.SendGump( new HouseRaffleManagementGump( m_Stone, SortMethod.Name, 0 ) ); - - break; - } - case 4: // Sort by account - { - from.SendGump( new HouseRaffleManagementGump( m_Stone, SortMethod.Account, 0 ) ); - - break; - } - case 5: // Sort by address - { - from.SendGump( new HouseRaffleManagementGump( m_Stone, SortMethod.Address, 0 ) ); - - break; - } - default: // Delete - { - buttonId -= 6; - - if ( buttonId >= 0 && buttonId < m_List.Count ) - { - m_Stone.Entries.Remove( m_List[buttonId] ); - - if ( m_Page > 0 && m_Page * 10 >= m_List.Count - 1 ) - m_Page--; - - from.SendGump( new HouseRaffleManagementGump( m_Stone, m_Sort, m_Page ) ); - } - - break; - } - } - } - - public HouseRaffleManagementGump( HouseRaffleStone stone ) - : this( stone, SortMethod.Default, 0 ) - { - } - - public HouseRaffleManagementGump( HouseRaffleStone stone, SortMethod sort, int page ) : base( 40, 40 ) - { - m_Stone = stone; - m_Page = page; - - m_List = new List( m_Stone.Entries ); - m_Sort = sort; - - switch ( m_Sort ) - { - case SortMethod.Name: - { - m_List.Sort( NameComparer.Instance ); + public class HouseRaffleManagementGump : Gump + { + public enum SortMethod + { + Default, + Name, + Account, + Address + } - break; - } - case SortMethod.Account: - { - m_List.Sort( AccountComparer.Instance ); + public const int LabelColor = 0xFFFFFF; + public const int HighlightColor = 0x11EE11; + private List m_List; + private int m_Page; + private SortMethod m_Sort; - break; - } - case SortMethod.Address: - { - m_List.Sort( AddressComparer.Instance ); + private HouseRaffleStone m_Stone; - break; - } - } + public HouseRaffleManagementGump(HouseRaffleStone stone) + : this(stone, SortMethod.Default, 0) + { + } - AddPage( 0 ); + public HouseRaffleManagementGump(HouseRaffleStone stone, SortMethod sort, int page) : base(40, 40) + { + m_Stone = stone; + m_Page = page; - AddBackground( 0, 0, 618, 354, 9270 ); - AddAlphaRegion( 10, 10, 598, 334 ); + m_List = new List(m_Stone.Entries); + m_Sort = sort; - AddHtml( 10, 10, 598, 20, Color( Center( "Raffle Management" ), LabelColor ), false, false ); + switch (m_Sort) + { + case SortMethod.Name: + { + m_List.Sort(NameComparer.Instance); - AddHtml( 45, 35, 100, 20, Color( "Location:", LabelColor ), false, false ); - AddHtml( 145, 35, 250, 20, Color( m_Stone.FormatLocation(), LabelColor ), false, false ); + break; + } + case SortMethod.Account: + { + m_List.Sort(AccountComparer.Instance); - AddHtml( 45, 55, 100, 20, Color( "Ticket Price:", LabelColor ), false, false ); - AddHtml( 145, 55, 250, 20, Color( m_Stone.FormatPrice(), LabelColor ), false, false ); + break; + } + case SortMethod.Address: + { + m_List.Sort(AddressComparer.Instance); - AddHtml( 45, 75, 100, 20, Color( "Total Entries:", LabelColor ), false, false ); - AddHtml( 145, 75, 250, 20, Color( m_Stone.Entries.Count.ToString(), LabelColor ), false, false ); + break; + } + } - AddButton( 440, 33, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0 ); - AddHtml( 474, 35, 120, 20, Color( "Sort by name", LabelColor ), false, false ); + AddPage(0); - AddButton( 440, 53, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0 ); - AddHtml( 474, 55, 120, 20, Color( "Sort by account", LabelColor ), false, false ); + AddBackground(0, 0, 618, 354, 9270); + AddAlphaRegion(10, 10, 598, 334); - AddButton( 440, 73, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0 ); - AddHtml( 474, 75, 120, 20, Color( "Sort by address", LabelColor ), false, false ); + AddHtml(10, 10, 598, 20, Color(Center("Raffle Management"), LabelColor), false, false); - AddImageTiled( 13, 99, 592, 242, 9264 ); - AddImageTiled( 14, 100, 590, 240, 9274 ); - AddAlphaRegion( 14, 100, 590, 240 ); + AddHtml(45, 35, 100, 20, Color("Location:", LabelColor), false, false); + AddHtml(145, 35, 250, 20, Color(m_Stone.FormatLocation(), LabelColor), false, false); - AddHtml( 14, 100, 590, 20, Color( Center( "Entries" ), LabelColor ), false, false ); + AddHtml(45, 55, 100, 20, Color("Ticket Price:", LabelColor), false, false); + AddHtml(145, 55, 250, 20, Color(m_Stone.FormatPrice(), LabelColor), false, false); - if ( page > 0 ) - AddButton( 567, 104, 0x15E3, 0x15E7, 1, GumpButtonType.Reply, 0 ); - else - AddImage( 567, 104, 0x25EA ); + AddHtml(45, 75, 100, 20, Color("Total Entries:", LabelColor), false, false); + AddHtml(145, 75, 250, 20, Color(m_Stone.Entries.Count.ToString(), LabelColor), false, false); + + AddButton(440, 33, 0xFA5, 0xFA7, 3, GumpButtonType.Reply, 0); + AddHtml(474, 35, 120, 20, Color("Sort by name", LabelColor), false, false); - if ( (page + 1) * 10 < m_List.Count ) - AddButton( 584, 104, 0x15E1, 0x15E5, 2, GumpButtonType.Reply, 0 ); - else - AddImage( 584, 104, 0x25E6 ); + AddButton(440, 53, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0); + AddHtml(474, 55, 120, 20, Color("Sort by account", LabelColor), false, false); - AddHtml( 14, 120, 30, 20, Color( Center( "DEL" ), LabelColor ), false, false ); - AddHtml( 47, 120, 250, 20, Color( "Name", LabelColor ), false, false ); - AddHtml( 295, 120, 100, 20, Color( Center( "Address" ), LabelColor ), false, false ); - AddHtml( 395, 120, 150, 20, Color( Center( "Date" ), LabelColor ), false, false ); - AddHtml( 545, 120, 60, 20, Color( Center( "Num" ), LabelColor ), false, false ); + AddButton(440, 73, 0xFA5, 0xFA7, 5, GumpButtonType.Reply, 0); + AddHtml(474, 75, 120, 20, Color("Sort by address", LabelColor), false, false); + + AddImageTiled(13, 99, 592, 242, 9264); + AddImageTiled(14, 100, 590, 240, 9274); + AddAlphaRegion(14, 100, 590, 240); - int idx = 0; - Mobile winner = m_Stone.Winner; + AddHtml(14, 100, 590, 20, Color(Center("Entries"), LabelColor), false, false); + + if (page > 0) + AddButton(567, 104, 0x15E3, 0x15E7, 1, GumpButtonType.Reply, 0); + else + AddImage(567, 104, 0x25EA); + + if ((page + 1) * 10 < m_List.Count) + AddButton(584, 104, 0x15E1, 0x15E5, 2, GumpButtonType.Reply, 0); + else + AddImage(584, 104, 0x25E6); + + AddHtml(14, 120, 30, 20, Color(Center("DEL"), LabelColor), false, false); + AddHtml(47, 120, 250, 20, Color("Name", LabelColor), false, false); + AddHtml(295, 120, 100, 20, Color(Center("Address"), LabelColor), false, false); + AddHtml(395, 120, 150, 20, Color(Center("Date"), LabelColor), false, false); + AddHtml(545, 120, 60, 20, Color(Center("Num"), LabelColor), false, false); + + int idx = 0; + Mobile winner = m_Stone.Winner; + + for (int i = page * 10; i >= 0 && i < m_List.Count && i < (page + 1) * 10; ++i, ++idx) + { + RaffleEntry entry = m_List[i]; + + if (entry == null) + continue; - for ( int i = page * 10; i >= 0 && i < m_List.Count && i < (page + 1) * 10; ++i, ++idx ) - { - RaffleEntry entry = m_List[i]; + AddButton(13, 138 + idx * 20, 4002, 4004, 6 + i, GumpButtonType.Reply, 0); - if ( entry == null ) - continue; + int x = 45; + int color = winner != null && entry.From == winner ? HighlightColor : LabelColor; - AddButton( 13, 138 + (idx * 20), 4002, 4004, 6 + i, GumpButtonType.Reply, 0 ); + string name = null; - int x = 45; - int color = ( winner != null && entry.From == winner ) ? HighlightColor : LabelColor; + if (entry.From != null) + { + if (entry.From.Account is Account acc) + name = $"{entry.From.Name} ({acc})"; + else + name = entry.From.Name; + } - string name = null; + if (name != null) + AddHtml(x + 2, 140 + idx * 20, 250, 20, Color(name, color), false, false); - if ( entry.From != null ) - { - if ( entry.From.Account is Account acc ) - name = $"{entry.From.Name} ({acc})"; - else - name = entry.From.Name; - } + x += 250; - if ( name != null ) - AddHtml( x + 2, 140 + (idx * 20), 250, 20, Color( name, color ), false, false ); + if (entry.Address != null) + AddHtml(x, 140 + idx * 20, 100, 20, Color(Center(entry.Address.ToString()), color), false, false); + + x += 100; + + AddHtml(x, 140 + idx * 20, 150, 20, Color(Center(entry.Date.ToString()), color), false, false); + x += 150; - x += 250; + AddHtml(x, 140 + idx * 20, 60, 20, Color(Center("1"), color), false, false); + x += 60; + } + } - if ( entry.Address != null ) - AddHtml( x, 140 + (idx * 20), 100, 20, Color( Center( entry.Address.ToString() ), color ), false, false ); + public string Right(string text) + { + return $"
{text}
"; + } - x += 100; + public string Center(string text) + { + return $"
{text}
"; + } - AddHtml( x, 140 + (idx * 20), 150, 20, Color( Center( entry.Date.ToString() ), color ), false, false ); - x += 150; - - AddHtml( x, 140 + (idx * 20), 60, 20, Color( Center( "1" ), color ), false, false ); - x += 60; - } - } - - private class NameComparer : IComparer - { - public static readonly IComparer Instance = new NameComparer(); - - public NameComparer() - { - } - - public int Compare( RaffleEntry x, RaffleEntry y ) - { - bool xIsNull = ( x?.From == null ); - bool yIsNull = ( y?.From == null ); - - if ( xIsNull && yIsNull ) - return 0; - if ( xIsNull ) - return -1; - if ( yIsNull ) - return 1; - - int result = Insensitive.Compare( x.From.Name, y.From.Name ); - - if ( result == 0 ) - return x.Date.CompareTo( y.Date ); - return result; - } - } - - private class AccountComparer : IComparer - { - public static readonly IComparer Instance = new AccountComparer(); - - public AccountComparer() - { - } - - public int Compare( RaffleEntry x, RaffleEntry y ) - { - bool xIsNull = ( x?.From == null ); - bool yIsNull = ( y?.From == null ); - - if ( xIsNull && yIsNull ) - return 0; - if ( xIsNull ) - return -1; - if ( yIsNull ) - return 1; - - Account a = x.From.Account as Account; - Account b = y.From.Account as Account; - - if ( a == null && b == null ) - return 0; - if ( a == null ) - return -1; - if ( b == null ) - return 1; - - int result = Insensitive.Compare( a.Username, b.Username ); - - if ( result == 0 ) - return x.Date.CompareTo( y.Date ); - return result; - } - } - - private class AddressComparer : IComparer - { - public static readonly IComparer Instance = new AddressComparer(); - - public AddressComparer() - { - } - - public int Compare( RaffleEntry x, RaffleEntry y ) - { - bool xIsNull = ( x?.Address == null ); - bool yIsNull = ( y?.Address == null ); - - if ( xIsNull && yIsNull ) - return 0; - if ( xIsNull ) - return -1; - if ( yIsNull ) - return 1; - - byte[] a = x.Address.GetAddressBytes(); - byte[] b = y.Address.GetAddressBytes(); - - for ( int i = 0; i < a.Length && i < b.Length; i++ ) - { - int compare = a[i].CompareTo( b[i] ); - - if ( compare != 0 ) - return compare; - } - - return x.Date.CompareTo( y.Date ); - } - } - } -} + public string Color(string text, int color) + { + return $"{text}"; + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; + int buttonId = info.ButtonID; + + switch (buttonId) + { + case 1: // Previous + { + if (m_Page > 0) + m_Page--; + + from.SendGump(new HouseRaffleManagementGump(m_Stone, m_Sort, m_Page)); + + break; + } + case 2: // Next + { + if ((m_Page + 1) * 10 < m_Stone.Entries.Count) + m_Page++; + + from.SendGump(new HouseRaffleManagementGump(m_Stone, m_Sort, m_Page)); + + break; + } + case 3: // Sort by name + { + from.SendGump(new HouseRaffleManagementGump(m_Stone, SortMethod.Name, 0)); + + break; + } + case 4: // Sort by account + { + from.SendGump(new HouseRaffleManagementGump(m_Stone, SortMethod.Account, 0)); + + break; + } + case 5: // Sort by address + { + from.SendGump(new HouseRaffleManagementGump(m_Stone, SortMethod.Address, 0)); + + break; + } + default: // Delete + { + buttonId -= 6; + + if (buttonId >= 0 && buttonId < m_List.Count) + { + m_Stone.Entries.Remove(m_List[buttonId]); + + if (m_Page > 0 && m_Page * 10 >= m_List.Count - 1) + m_Page--; + + from.SendGump(new HouseRaffleManagementGump(m_Stone, m_Sort, m_Page)); + } + + break; + } + } + } + + private class NameComparer : IComparer + { + public static readonly IComparer Instance = new NameComparer(); + + public int Compare(RaffleEntry x, RaffleEntry y) + { + bool xIsNull = x?.From == null; + bool yIsNull = y?.From == null; + + if (xIsNull && yIsNull) + return 0; + if (xIsNull) + return -1; + if (yIsNull) + return 1; + + int result = Insensitive.Compare(x.From.Name, y.From.Name); + + if (result == 0) + return x.Date.CompareTo(y.Date); + return result; + } + } + + private class AccountComparer : IComparer + { + public static readonly IComparer Instance = new AccountComparer(); + + public int Compare(RaffleEntry x, RaffleEntry y) + { + bool xIsNull = x?.From == null; + bool yIsNull = y?.From == null; + + if (xIsNull && yIsNull) + return 0; + if (xIsNull) + return -1; + if (yIsNull) + return 1; + + Account a = x.From.Account as Account; + Account b = y.From.Account as Account; + + if (a == null && b == null) + return 0; + if (a == null) + return -1; + if (b == null) + return 1; + + int result = Insensitive.Compare(a.Username, b.Username); + + if (result == 0) + return x.Date.CompareTo(y.Date); + return result; + } + } + + private class AddressComparer : IComparer + { + public static readonly IComparer Instance = new AddressComparer(); + + public int Compare(RaffleEntry x, RaffleEntry y) + { + bool xIsNull = x?.Address == null; + bool yIsNull = y?.Address == null; + + if (xIsNull && yIsNull) + return 0; + if (xIsNull) + return -1; + if (yIsNull) + return 1; + + byte[] a = x.Address.GetAddressBytes(); + byte[] b = y.Address.GetAddressBytes(); + + for (int i = 0; i < a.Length && i < b.Length; i++) + { + int compare = a[i].CompareTo(b[i]); + + if (compare != 0) + return compare; + } + + return x.Date.CompareTo(y.Date); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/House Raffle/HouseRaffleRegion.cs b/Scripts/Items/Special/House Raffle/HouseRaffleRegion.cs index d4d1a5de2..da58c7c60 100644 --- a/Scripts/Items/Special/House Raffle/HouseRaffleRegion.cs +++ b/Scripts/Items/Special/House Raffle/HouseRaffleRegion.cs @@ -5,62 +5,60 @@ using Server.Targeting; namespace Server.Regions { - public class HouseRaffleRegion : BaseRegion - { - private HouseRaffleStone m_Stone; + public class HouseRaffleRegion : BaseRegion + { + private HouseRaffleStone m_Stone; - public HouseRaffleRegion( HouseRaffleStone stone ) - : base( null, stone.PlotFacet, DefaultPriority, stone.PlotBounds ) - { - m_Stone = stone; - } + public HouseRaffleRegion(HouseRaffleStone stone) + : base(null, stone.PlotFacet, DefaultPriority, stone.PlotBounds) + { + m_Stone = stone; + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - if ( m_Stone == null ) - return false; + public override bool AllowHousing(Mobile from, Point3D p) + { + if (m_Stone == null) + return false; - if ( m_Stone.IsExpired ) - return true; + if (m_Stone.IsExpired) + return true; - if ( m_Stone.Deed == null ) - return false; + if (m_Stone.Deed == null) + return false; - Container pack = from.Backpack; + Container pack = from.Backpack; - if ( pack != null && ContainsDeed( pack ) ) - return true; + if (pack != null && ContainsDeed(pack)) + return true; - BankBox bank = from.FindBankNoCreate(); + BankBox bank = from.FindBankNoCreate(); - if ( bank != null && ContainsDeed( bank ) ) - return true; + if (bank != null && ContainsDeed(bank)) + return true; - return false; - } + return false; + } - private bool ContainsDeed( Container cont ) - { - List deeds = cont.FindItemsByType(); + private bool ContainsDeed(Container cont) + { + List deeds = cont.FindItemsByType(); - for ( int i = 0; i < deeds.Count; ++i ) - { - if ( deeds[i] == m_Stone.Deed ) - return true; - } + for (int i = 0; i < deeds.Count; ++i) + if (deeds[i] == m_Stone.Deed) + return true; - return false; - } + return false; + } - public override bool OnTarget( Mobile m, Target t, object o ) - { - if ( m.Spell is MarkSpell && m.AccessLevel == AccessLevel.Player ) - { - m.SendLocalizedMessage( 501800 ); // You cannot mark an object at that location. - return false; - } + public override bool OnTarget(Mobile m, Target t, object o) + { + if (m.Spell is MarkSpell && m.AccessLevel == AccessLevel.Player) + { + m.SendLocalizedMessage(501800); // You cannot mark an object at that location. + return false; + } - return base.OnTarget( m, t, o ); - } - } -} + return base.OnTarget(m, t, o); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/House Raffle/HouseRaffleStone.cs b/Scripts/Items/Special/House Raffle/HouseRaffleStone.cs index babfc0ef5..441ba9da8 100644 --- a/Scripts/Items/Special/House Raffle/HouseRaffleStone.cs +++ b/Scripts/Items/Special/House Raffle/HouseRaffleStone.cs @@ -10,679 +10,684 @@ using Server.Regions; namespace Server.Items { - public class RaffleEntry - { - public Mobile From { get; } - - public IPAddress Address { get; } - - public DateTime Date { get; } - - public RaffleEntry( Mobile from ) - { - From = from; - - if ( From.NetState != null ) - Address = From.NetState.Address; - else - Address = IPAddress.None; - - Date = DateTime.UtcNow; - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( From ); - writer.Write( Address ); - writer.Write( Date ); - } - - public RaffleEntry( GenericReader reader, int version ) - { - switch ( version ) - { - case 3: // HouseRaffleStone version changes - case 2: - case 1: - case 0: - { - From = reader.ReadMobile(); - Address = Utility.Intern( reader.ReadIPAddress() ); - Date = reader.ReadDateTime(); - - break; - } - } - } - } - - public enum HouseRaffleState - { - Inactive, - Active, - Completed - } - - public enum HouseRaffleExpireAction - { - None, - HideStone, - DeleteStone - } - - [FlippableAttribute( 0xEDD, 0xEDE )] - public class HouseRaffleStone : Item - { - private const int EntryLimitPerIP = 4; - private const int DefaultTicketPrice = 5000; - private const int MessageHue = 1153; - - public static readonly TimeSpan DefaultDuration = TimeSpan.FromDays( 7.0 ); - public static readonly TimeSpan ExpirationTime = TimeSpan.FromDays( 30.0 ); - - private HouseRaffleRegion m_Region; - private Rectangle2D m_Bounds; - private Map m_Facet; - - private Mobile m_Winner; - - private HouseRaffleState m_State; - private DateTime m_Started; - private TimeSpan m_Duration; - private int m_TicketPrice; - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public HouseRaffleState CurrentState - { - get => m_State; - set - { - if ( m_State != value ) - { - if ( value == HouseRaffleState.Active ) - { - Entries.Clear(); - m_Winner = null; - Deed = null; - m_Started = DateTime.UtcNow; - } - - m_State = value; - InvalidateProperties(); - } - } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public Rectangle2D PlotBounds - { - get => m_Bounds; - set - { - m_Bounds = value; - - InvalidateRegion(); - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public Map PlotFacet - { - get => m_Facet; - set - { - m_Facet = value; - - InvalidateRegion(); - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public Mobile Winner - { - get => m_Winner; - set { m_Winner = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public HouseRaffleDeed Deed { get; set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public DateTime Started - { - get => m_Started; - set { m_Started = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public TimeSpan Duration - { - get => m_Duration; - set { m_Duration = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsExpired - { - get - { - if ( m_State != HouseRaffleState.Completed ) - return false; - - return ( m_Started + m_Duration + ExpirationTime <= DateTime.UtcNow ); - } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public HouseRaffleExpireAction ExpireAction { get; set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Seer )] - public int TicketPrice - { - get => m_TicketPrice; - set - { - m_TicketPrice = Math.Max( 0, value ); - InvalidateProperties(); - } - } - - public List Entries { get; private set; } - - public override string DefaultName => "a house raffle stone"; - - public override bool DisplayWeight => false; - - private static List m_AllStones = new List(); - - public static void CheckEnd_OnTick() - { - for ( int i = 0; i < m_AllStones.Count; i++ ) - m_AllStones[i].CheckEnd(); - } - - public static void Initialize() - { - for ( int i = m_AllStones.Count - 1; i >= 0; i-- ) - { - HouseRaffleStone stone = m_AllStones[i]; - - if ( stone.IsExpired ) - { - switch ( stone.ExpireAction ) - { - case HouseRaffleExpireAction.HideStone: - { - if ( stone.Visible ) - { - stone.Visible = false; - stone.ItemID = 0x1B7B; // Non-blocking ItemID - } - - break; - } - case HouseRaffleExpireAction.DeleteStone: - { - stone.Delete(); - break; - } - } - } - } - - Timer.DelayCall( TimeSpan.FromMinutes( 1.0 ), TimeSpan.FromMinutes( 1.0 ), CheckEnd_OnTick ); - } - - [Constructible] - public HouseRaffleStone() - : base( 0xEDD ) - { - m_Region = null; - m_Bounds = new Rectangle2D(); - m_Facet = null; - - m_Winner = null; - Deed = null; - - m_State = HouseRaffleState.Inactive; - m_Started = DateTime.MinValue; - m_Duration = DefaultDuration; - ExpireAction = HouseRaffleExpireAction.None; - m_TicketPrice = DefaultTicketPrice; - - Entries = new List(); - - Movable = false; - - m_AllStones.Add( this ); - } - - public HouseRaffleStone( Serial serial ) - : base( serial ) - { - } - - public bool ValidLocation() - { - return ( m_Bounds.Start != Point2D.Zero && m_Bounds.End != Point2D.Zero && m_Facet != null && m_Facet != Map.Internal ); - } - - private void InvalidateRegion() - { - if ( m_Region != null ) - { - m_Region.Unregister(); - m_Region = null; - } - - if ( ValidLocation() ) - { - m_Region = new HouseRaffleRegion( this ); - m_Region.Register(); - } - } - - private bool HasEntered( Mobile from ) - { - if ( !(from.Account is Account acc) ) - return false; - - foreach ( RaffleEntry entry in Entries ) - { - if ( entry.From != null ) - { - Account entryAcc = entry.From.Account as Account; - - if ( entryAcc == acc ) - return true; - } - } - - return false; - } - - private bool IsAtIPLimit( Mobile from ) - { - if ( from.NetState == null ) - return false; - - IPAddress address = from.NetState.Address; - int tickets = 0; - - foreach ( RaffleEntry entry in Entries ) - { - if ( Utility.IPMatchClassC( entry.Address, address ) ) - { - if ( ++tickets >= EntryLimitPerIP ) - return true; - } - } - - return false; - } - - public static string FormatLocation( Point3D loc, Map map, bool displayMap ) - { - StringBuilder result = new StringBuilder(); - - int xLong = 0, yLat = 0; - int xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; - - if ( Sextant.Format( loc, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ) ) - result.AppendFormat( "{0}°{1}'{2},{3}°{4}'{5}", yLat, yMins, ySouth ? "S" : "N", xLong, xMins, xEast ? "E" : "W" ); - else - result.AppendFormat( "{0},{1}", loc.X, loc.Y ); - - if ( displayMap ) - result.AppendFormat( " ({0})", map ); - - return result.ToString(); - } - - public Point3D GetPlotCenter() - { - int x = m_Bounds.X + m_Bounds.Width / 2; - int y = m_Bounds.Y + m_Bounds.Height / 2; - int z = m_Facet?.GetAverageZ( x, y ) ?? 0; - - return new Point3D( x, y, z ); - } - - public string FormatLocation() - { - if ( !ValidLocation() ) - return "no location set"; - - return FormatLocation( GetPlotCenter(), m_Facet, true ); - } - - public string FormatPrice() - { - if ( m_TicketPrice == 0 ) - return "FREE"; - return $"{m_TicketPrice} gold"; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( ValidLocation() ) - list.Add( FormatLocation() ); - - switch ( m_State ) - { - case HouseRaffleState.Active: - { - list.Add( 1060658, "ticket price\t{0}", FormatPrice() ); // ~1_val~: ~2_val~ - list.Add( 1060659, "ends\t{0}", m_Started + m_Duration ); // ~1_val~: ~2_val~ - break; - } - case HouseRaffleState.Completed: - { - list.Add( 1060658, "winner\t{0}", ( m_Winner == null ) ? "unknown" : m_Winner.Name ); // ~1_val~: ~2_val~ - break; - } - } - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - switch ( m_State ) - { - case HouseRaffleState.Active: - { - LabelTo( from, 1060658, $"Ends\t{m_Started + m_Duration}"); // ~1_val~: ~2_val~ - break; - } - case HouseRaffleState.Completed: - { - LabelTo( from, 1060658, $"Winner\t{((m_Winner == null) ? "Unknown" : m_Winner.Name)}"); // ~1_val~: ~2_val~ - break; - } - } - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.AccessLevel >= AccessLevel.Seer ) - { - list.Add( new EditEntry( from, this ) ); - - if ( m_State == HouseRaffleState.Inactive ) - list.Add( new ActivateEntry( from, this ) ); - else - list.Add( new ManagementEntry( from, this ) ); - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_State != HouseRaffleState.Active || !from.CheckAlive() ) - return; - - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return; - } - - if ( HasEntered( from ) ) - { - from.SendMessage( MessageHue, "You have already entered this plot's raffle." ); - } - else if ( IsAtIPLimit( from ) ) - { - from.SendMessage( MessageHue, "You may not enter this plot's raffle." ); - } - else - { - from.SendGump( new WarningGump( 1150470, 0x7F00, - $"You are about to purchase a raffle ticket for the house plot located at {FormatLocation()}. The ticket price is {FormatPrice()}. Tickets are non-refundable and you can only purchase one ticket per account. Do you wish to continue?", 0xFFFFFF, 420, 280, Purchase_Callback, null ) ); // CONFIRM TICKET PURCHASE - } - } - - public void Purchase_Callback( Mobile from, bool okay, object state ) - { - if ( Deleted || m_State != HouseRaffleState.Active || !from.CheckAlive() || HasEntered( from ) || IsAtIPLimit( from ) ) - return; - - if ( !(from.Account is Account) ) - return; - - if ( okay ) - { - Container bank = from.FindBankNoCreate(); - - if ( m_TicketPrice == 0 || ( from.Backpack != null && from.Backpack.ConsumeTotal( typeof( Gold ), m_TicketPrice ) ) || ( bank != null && bank.ConsumeTotal( typeof( Gold ), m_TicketPrice ) ) ) - { - Entries.Add( new RaffleEntry( from ) ); - - from.SendMessage( MessageHue, "You have successfully entered the plot's raffle." ); - } - else - { - from.SendMessage( MessageHue, "You do not have the {0} required to enter the raffle.", FormatPrice() ); - } - } - else - { - from.SendMessage( MessageHue, "You have chosen not to enter the raffle." ); - } - } - - public void CheckEnd() - { - if ( m_State != HouseRaffleState.Active || m_Started + m_Duration > DateTime.UtcNow ) - return; - - m_State = HouseRaffleState.Completed; - - if ( m_Region != null && Entries.Count != 0 ) - { - int winner = Utility.Random( Entries.Count ); - - m_Winner = Entries[winner].From; - - if ( m_Winner != null ) - { - Deed = new HouseRaffleDeed( this, m_Winner ); - - m_Winner.SendMessage( MessageHue, "Congratulations, {0}! You have won the raffle for the plot located at {1}.", m_Winner.Name, FormatLocation() ); - - if ( m_Winner.AddToBackpack( Deed ) ) - { - m_Winner.SendMessage( MessageHue, "The writ of lease has been placed in your backpack." ); - } - else - { - m_Winner.BankBox.DropItem( Deed ); - m_Winner.SendMessage( MessageHue, "As your backpack is full, the writ of lease has been placed in your bank box." ); - } - } - } - - InvalidateProperties(); - } - - public override void OnDelete() - { - if ( m_Region != null ) - { - m_Region.Unregister(); - m_Region = null; - } - - m_AllStones.Remove( this ); - - base.OnDelete(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 3 ); // version - - writer.WriteEncodedInt( (int) m_State ); - writer.WriteEncodedInt( (int) ExpireAction ); - - writer.Write( Deed ); - - writer.Write( m_Bounds ); - writer.Write( m_Facet ); - - writer.Write( m_Winner ); - - writer.Write( m_TicketPrice ); - writer.Write( m_Started ); - writer.Write( m_Duration ); - - writer.Write( Entries.Count ); - - foreach ( RaffleEntry entry in Entries ) - entry.Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 3: - { - m_State = (HouseRaffleState) reader.ReadEncodedInt(); - - goto case 2; - } - case 2: - { - ExpireAction = (HouseRaffleExpireAction) reader.ReadEncodedInt(); - - goto case 1; - } - case 1: - { - Deed = reader.ReadItem(); - - goto case 0; - } - case 0: - { - bool oldActive = ( version < 3 ) && reader.ReadBool(); - - m_Bounds = reader.ReadRect2D(); - m_Facet = reader.ReadMap(); - - m_Winner = reader.ReadMobile(); - - m_TicketPrice = reader.ReadInt(); - m_Started = reader.ReadDateTime(); - m_Duration = reader.ReadTimeSpan(); - - int entryCount = reader.ReadInt(); - Entries = new List( entryCount ); - - for ( int i = 0; i < entryCount; i++ ) - { - RaffleEntry entry = new RaffleEntry( reader, version ); - - if ( entry.From == null ) - continue; // Character was deleted - - Entries.Add( entry ); - } - - InvalidateRegion(); - - m_AllStones.Add( this ); - - if ( version < 3 ) - { - if ( oldActive ) - m_State = HouseRaffleState.Active; - else if ( m_Winner != null ) - m_State = HouseRaffleState.Completed; - else - m_State = HouseRaffleState.Inactive; - } - - break; - } - } - } - - private class RaffleContextMenuEntry : ContextMenuEntry - { - protected Mobile m_From; - protected HouseRaffleStone m_Stone; - - public RaffleContextMenuEntry( Mobile from, HouseRaffleStone stone, int label ) - : base( label ) - { - m_From = from; - m_Stone = stone; - } - } - - private class EditEntry : RaffleContextMenuEntry - { - public EditEntry( Mobile from, HouseRaffleStone stone ) - : base( from, stone, 5101 ) // Edit - { - } - - public override void OnClick() - { - if ( m_Stone.Deleted || m_From.AccessLevel < AccessLevel.Seer ) - return; - - m_From.SendGump( new PropertiesGump( m_From, m_Stone ) ); - } - } - - private class ActivateEntry : RaffleContextMenuEntry - { - public ActivateEntry( Mobile from, HouseRaffleStone stone ) - : base( from, stone, 5113 ) // Start - { - if ( !stone.ValidLocation() ) - Flags |= CMEFlags.Disabled; - } - - public override void OnClick() - { - if ( m_Stone.Deleted || m_From.AccessLevel < AccessLevel.Seer || !m_Stone.ValidLocation() ) - return; - - m_Stone.CurrentState = HouseRaffleState.Active; - } - } - - private class ManagementEntry : RaffleContextMenuEntry - { - public ManagementEntry( Mobile from, HouseRaffleStone stone) - : base( from, stone, 5032 ) // Game Monitor - { - } - - public override void OnClick() - { - if ( m_Stone.Deleted || m_From.AccessLevel < AccessLevel.Seer ) - return; - - m_From.SendGump( new HouseRaffleManagementGump( m_Stone ) ); - } - } - } -} + public class RaffleEntry + { + public RaffleEntry(Mobile from) + { + From = from; + + if (From.NetState != null) + Address = From.NetState.Address; + else + Address = IPAddress.None; + + Date = DateTime.UtcNow; + } + + public RaffleEntry(GenericReader reader, int version) + { + switch (version) + { + case 3: // HouseRaffleStone version changes + case 2: + case 1: + case 0: + { + From = reader.ReadMobile(); + Address = Utility.Intern(reader.ReadIPAddress()); + Date = reader.ReadDateTime(); + + break; + } + } + } + + public Mobile From{ get; } + + public IPAddress Address{ get; } + + public DateTime Date{ get; } + + public void Serialize(GenericWriter writer) + { + writer.Write(From); + writer.Write(Address); + writer.Write(Date); + } + } + + public enum HouseRaffleState + { + Inactive, + Active, + Completed + } + + public enum HouseRaffleExpireAction + { + None, + HideStone, + DeleteStone + } + + [Flippable(0xEDD, 0xEDE)] + public class HouseRaffleStone : Item + { + private const int EntryLimitPerIP = 4; + private const int DefaultTicketPrice = 5000; + private const int MessageHue = 1153; + + public static readonly TimeSpan DefaultDuration = TimeSpan.FromDays(7.0); + public static readonly TimeSpan ExpirationTime = TimeSpan.FromDays(30.0); + + private static List m_AllStones = new List(); + private Rectangle2D m_Bounds; + private TimeSpan m_Duration; + private Map m_Facet; + + private HouseRaffleRegion m_Region; + private DateTime m_Started; + + private HouseRaffleState m_State; + private int m_TicketPrice; + + private Mobile m_Winner; + + [Constructible] + public HouseRaffleStone() + : base(0xEDD) + { + m_Region = null; + m_Bounds = new Rectangle2D(); + m_Facet = null; + + m_Winner = null; + Deed = null; + + m_State = HouseRaffleState.Inactive; + m_Started = DateTime.MinValue; + m_Duration = DefaultDuration; + ExpireAction = HouseRaffleExpireAction.None; + m_TicketPrice = DefaultTicketPrice; + + Entries = new List(); + + Movable = false; + + m_AllStones.Add(this); + } + + public HouseRaffleStone(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public HouseRaffleState CurrentState + { + get => m_State; + set + { + if (m_State != value) + { + if (value == HouseRaffleState.Active) + { + Entries.Clear(); + m_Winner = null; + Deed = null; + m_Started = DateTime.UtcNow; + } + + m_State = value; + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public Rectangle2D PlotBounds + { + get => m_Bounds; + set + { + m_Bounds = value; + + InvalidateRegion(); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public Map PlotFacet + { + get => m_Facet; + set + { + m_Facet = value; + + InvalidateRegion(); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public Mobile Winner + { + get => m_Winner; + set + { + m_Winner = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public HouseRaffleDeed Deed{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public DateTime Started + { + get => m_Started; + set + { + m_Started = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public TimeSpan Duration + { + get => m_Duration; + set + { + m_Duration = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsExpired + { + get + { + if (m_State != HouseRaffleState.Completed) + return false; + + return m_Started + m_Duration + ExpirationTime <= DateTime.UtcNow; + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public HouseRaffleExpireAction ExpireAction{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Seer)] + public int TicketPrice + { + get => m_TicketPrice; + set + { + m_TicketPrice = Math.Max(0, value); + InvalidateProperties(); + } + } + + public List Entries{ get; private set; } + + public override string DefaultName => "a house raffle stone"; + + public override bool DisplayWeight => false; + + public static void CheckEnd_OnTick() + { + for (int i = 0; i < m_AllStones.Count; i++) + m_AllStones[i].CheckEnd(); + } + + public static void Initialize() + { + for (int i = m_AllStones.Count - 1; i >= 0; i--) + { + HouseRaffleStone stone = m_AllStones[i]; + + if (stone.IsExpired) + switch (stone.ExpireAction) + { + case HouseRaffleExpireAction.HideStone: + { + if (stone.Visible) + { + stone.Visible = false; + stone.ItemID = 0x1B7B; // Non-blocking ItemID + } + + break; + } + case HouseRaffleExpireAction.DeleteStone: + { + stone.Delete(); + break; + } + } + } + + Timer.DelayCall(TimeSpan.FromMinutes(1.0), TimeSpan.FromMinutes(1.0), CheckEnd_OnTick); + } + + public bool ValidLocation() + { + return m_Bounds.Start != Point2D.Zero && m_Bounds.End != Point2D.Zero && m_Facet != null && + m_Facet != Map.Internal; + } + + private void InvalidateRegion() + { + if (m_Region != null) + { + m_Region.Unregister(); + m_Region = null; + } + + if (ValidLocation()) + { + m_Region = new HouseRaffleRegion(this); + m_Region.Register(); + } + } + + private bool HasEntered(Mobile from) + { + if (!(from.Account is Account acc)) + return false; + + foreach (RaffleEntry entry in Entries) + if (entry.From != null) + { + Account entryAcc = entry.From.Account as Account; + + if (entryAcc == acc) + return true; + } + + return false; + } + + private bool IsAtIPLimit(Mobile from) + { + if (from.NetState == null) + return false; + + IPAddress address = from.NetState.Address; + int tickets = 0; + + foreach (RaffleEntry entry in Entries) + if (Utility.IPMatchClassC(entry.Address, address)) + if (++tickets >= EntryLimitPerIP) + return true; + + return false; + } + + public static string FormatLocation(Point3D loc, Map map, bool displayMap) + { + StringBuilder result = new StringBuilder(); + + int xLong = 0, yLat = 0; + int xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + if (Sextant.Format(loc, map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth)) + result.AppendFormat("{0}°{1}'{2},{3}°{4}'{5}", yLat, yMins, ySouth ? "S" : "N", xLong, xMins, + xEast ? "E" : "W"); + else + result.AppendFormat("{0},{1}", loc.X, loc.Y); + + if (displayMap) + result.AppendFormat(" ({0})", map); + + return result.ToString(); + } + + public Point3D GetPlotCenter() + { + int x = m_Bounds.X + m_Bounds.Width / 2; + int y = m_Bounds.Y + m_Bounds.Height / 2; + int z = m_Facet?.GetAverageZ(x, y) ?? 0; + + return new Point3D(x, y, z); + } + + public string FormatLocation() + { + if (!ValidLocation()) + return "no location set"; + + return FormatLocation(GetPlotCenter(), m_Facet, true); + } + + public string FormatPrice() + { + if (m_TicketPrice == 0) + return "FREE"; + return $"{m_TicketPrice} gold"; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (ValidLocation()) + list.Add(FormatLocation()); + + switch (m_State) + { + case HouseRaffleState.Active: + { + list.Add(1060658, "ticket price\t{0}", FormatPrice()); // ~1_val~: ~2_val~ + list.Add(1060659, "ends\t{0}", m_Started + m_Duration); // ~1_val~: ~2_val~ + break; + } + case HouseRaffleState.Completed: + { + list.Add(1060658, "winner\t{0}", m_Winner == null ? "unknown" : m_Winner.Name); // ~1_val~: ~2_val~ + break; + } + } + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + switch (m_State) + { + case HouseRaffleState.Active: + { + LabelTo(from, 1060658, $"Ends\t{m_Started + m_Duration}"); // ~1_val~: ~2_val~ + break; + } + case HouseRaffleState.Completed: + { + LabelTo(from, 1060658, $"Winner\t{(m_Winner == null ? "Unknown" : m_Winner.Name)}"); // ~1_val~: ~2_val~ + break; + } + } + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.AccessLevel >= AccessLevel.Seer) + { + list.Add(new EditEntry(from, this)); + + if (m_State == HouseRaffleState.Inactive) + list.Add(new ActivateEntry(from, this)); + else + list.Add(new ManagementEntry(from, this)); + } + } + + public override void OnDoubleClick(Mobile from) + { + if (m_State != HouseRaffleState.Active || !from.CheckAlive()) + return; + + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return; + } + + if (HasEntered(from)) + from.SendMessage(MessageHue, "You have already entered this plot's raffle."); + else if (IsAtIPLimit(from)) + from.SendMessage(MessageHue, "You may not enter this plot's raffle."); + else + from.SendGump(new WarningGump(1150470, 0x7F00, + $"You are about to purchase a raffle ticket for the house plot located at {FormatLocation()}. The ticket price is {FormatPrice()}. Tickets are non-refundable and you can only purchase one ticket per account. Do you wish to continue?", + 0xFFFFFF, 420, 280, Purchase_Callback, null)); // CONFIRM TICKET PURCHASE + } + + public void Purchase_Callback(Mobile from, bool okay, object state) + { + if (Deleted || m_State != HouseRaffleState.Active || !from.CheckAlive() || HasEntered(from) || IsAtIPLimit(from)) + return; + + if (!(from.Account is Account)) + return; + + if (okay) + { + Container bank = from.FindBankNoCreate(); + + if (m_TicketPrice == 0 || from.Backpack != null && from.Backpack.ConsumeTotal(typeof(Gold), m_TicketPrice) || + bank != null && bank.ConsumeTotal(typeof(Gold), m_TicketPrice)) + { + Entries.Add(new RaffleEntry(from)); + + from.SendMessage(MessageHue, "You have successfully entered the plot's raffle."); + } + else + { + from.SendMessage(MessageHue, "You do not have the {0} required to enter the raffle.", FormatPrice()); + } + } + else + { + from.SendMessage(MessageHue, "You have chosen not to enter the raffle."); + } + } + + public void CheckEnd() + { + if (m_State != HouseRaffleState.Active || m_Started + m_Duration > DateTime.UtcNow) + return; + + m_State = HouseRaffleState.Completed; + + if (m_Region != null && Entries.Count != 0) + { + int winner = Utility.Random(Entries.Count); + + m_Winner = Entries[winner].From; + + if (m_Winner != null) + { + Deed = new HouseRaffleDeed(this, m_Winner); + + m_Winner.SendMessage(MessageHue, + "Congratulations, {0}! You have won the raffle for the plot located at {1}.", m_Winner.Name, + FormatLocation()); + + if (m_Winner.AddToBackpack(Deed)) + { + m_Winner.SendMessage(MessageHue, "The writ of lease has been placed in your backpack."); + } + else + { + m_Winner.BankBox.DropItem(Deed); + m_Winner.SendMessage(MessageHue, + "As your backpack is full, the writ of lease has been placed in your bank box."); + } + } + } + + InvalidateProperties(); + } + + public override void OnDelete() + { + if (m_Region != null) + { + m_Region.Unregister(); + m_Region = null; + } + + m_AllStones.Remove(this); + + base.OnDelete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(3); // version + + writer.WriteEncodedInt((int)m_State); + writer.WriteEncodedInt((int)ExpireAction); + + writer.Write(Deed); + + writer.Write(m_Bounds); + writer.Write(m_Facet); + + writer.Write(m_Winner); + + writer.Write(m_TicketPrice); + writer.Write(m_Started); + writer.Write(m_Duration); + + writer.Write(Entries.Count); + + foreach (RaffleEntry entry in Entries) + entry.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + m_State = (HouseRaffleState)reader.ReadEncodedInt(); + + goto case 2; + } + case 2: + { + ExpireAction = (HouseRaffleExpireAction)reader.ReadEncodedInt(); + + goto case 1; + } + case 1: + { + Deed = reader.ReadItem(); + + goto case 0; + } + case 0: + { + bool oldActive = version < 3 && reader.ReadBool(); + + m_Bounds = reader.ReadRect2D(); + m_Facet = reader.ReadMap(); + + m_Winner = reader.ReadMobile(); + + m_TicketPrice = reader.ReadInt(); + m_Started = reader.ReadDateTime(); + m_Duration = reader.ReadTimeSpan(); + + int entryCount = reader.ReadInt(); + Entries = new List(entryCount); + + for (int i = 0; i < entryCount; i++) + { + RaffleEntry entry = new RaffleEntry(reader, version); + + if (entry.From == null) + continue; // Character was deleted + + Entries.Add(entry); + } + + InvalidateRegion(); + + m_AllStones.Add(this); + + if (version < 3) + { + if (oldActive) + m_State = HouseRaffleState.Active; + else if (m_Winner != null) + m_State = HouseRaffleState.Completed; + else + m_State = HouseRaffleState.Inactive; + } + + break; + } + } + } + + private class RaffleContextMenuEntry : ContextMenuEntry + { + protected Mobile m_From; + protected HouseRaffleStone m_Stone; + + public RaffleContextMenuEntry(Mobile from, HouseRaffleStone stone, int label) + : base(label) + { + m_From = from; + m_Stone = stone; + } + } + + private class EditEntry : RaffleContextMenuEntry + { + public EditEntry(Mobile from, HouseRaffleStone stone) + : base(from, stone, 5101) // Edit + { + } + + public override void OnClick() + { + if (m_Stone.Deleted || m_From.AccessLevel < AccessLevel.Seer) + return; + + m_From.SendGump(new PropertiesGump(m_From, m_Stone)); + } + } + + private class ActivateEntry : RaffleContextMenuEntry + { + public ActivateEntry(Mobile from, HouseRaffleStone stone) + : base(from, stone, 5113) // Start + { + if (!stone.ValidLocation()) + Flags |= CMEFlags.Disabled; + } + + public override void OnClick() + { + if (m_Stone.Deleted || m_From.AccessLevel < AccessLevel.Seer || !m_Stone.ValidLocation()) + return; + + m_Stone.CurrentState = HouseRaffleState.Active; + } + } + + private class ManagementEntry : RaffleContextMenuEntry + { + public ManagementEntry(Mobile from, HouseRaffleStone stone) + : base(from, stone, 5032) // Game Monitor + { + } + + public override void OnClick() + { + if (m_Stone.Deleted || m_From.AccessLevel < AccessLevel.Seer) + return; + + m_From.SendGump(new HouseRaffleManagementGump(m_Stone)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/ML/BaseImprisonedMobile.cs b/Scripts/Items/Special/ML/BaseImprisonedMobile.cs index 1c1371495..509e2d2d3 100644 --- a/Scripts/Items/Special/ML/BaseImprisonedMobile.cs +++ b/Scripts/Items/Special/ML/BaseImprisonedMobile.cs @@ -1,46 +1,45 @@ -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; namespace Server.Items { - public abstract class BaseImprisonedMobile : Item - { - public abstract BaseCreature Summon{ get; } - - [Constructible] - public BaseImprisonedMobile( int itemID ) : base( itemID ) - { - } + public abstract class BaseImprisonedMobile : Item + { + [Constructible] + public BaseImprisonedMobile(int itemID) : base(itemID) + { + } - public BaseImprisonedMobile( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - from.SendGump( new ConfirmBreakCrystalGump( this ) ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + public BaseImprisonedMobile(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } + public abstract BaseCreature Summon{ get; } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public virtual void Release( Mobile from, BaseCreature summon ) - { - } - } -} + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + from.SendGump(new ConfirmBreakCrystalGump(this)); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public virtual void Release(Mobile from, BaseCreature summon) + { + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/ML/GrizzledMareStatuette.cs b/Scripts/Items/Special/ML/GrizzledMareStatuette.cs index a19a0ea20..4272dd2a9 100644 --- a/Scripts/Items/Special/ML/GrizzledMareStatuette.cs +++ b/Scripts/Items/Special/ML/GrizzledMareStatuette.cs @@ -3,79 +3,76 @@ using Server.Mobiles; namespace Server.Items { - public class GrizzledMareStatuette : BaseImprisonedMobile - { - public override int LabelNumber => 1074475; // Grizzled Mare Statuette - public override BaseCreature Summon => new GrizzledMare(); + public class GrizzledMareStatuette : BaseImprisonedMobile + { + [Constructible] + public GrizzledMareStatuette() : base(0x2617) + { + Weight = 1.0; + } - [Constructible] - public GrizzledMareStatuette() : base( 0x2617 ) - { - Weight = 1.0; - } + public GrizzledMareStatuette(Serial serial) : base(serial) + { + } - public GrizzledMareStatuette( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1074475; // Grizzled Mare Statuette + public override BaseCreature Summon => new GrizzledMare(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } namespace Server.Mobiles { - public class GrizzledMare : HellSteed - { - public override bool DeleteOnRelease => true; + public class GrizzledMare : HellSteed + { + private static readonly string m_Myname = "a grizzled mare"; - private static readonly string m_Myname = "a grizzled mare"; + [Constructible] + public GrizzledMare() + : base(m_Myname) + { + } - [Constructible] - public GrizzledMare() - : base( m_Myname ) - { - } + public GrizzledMare(Serial serial) : base(serial) + { + } - public virtual void OnAfterDeserialize_Callback() - { - SetStats( this ); + public override bool DeleteOnRelease => true; - Name = m_Myname; - } + public virtual void OnAfterDeserialize_Callback() + { + SetStats(this); - public GrizzledMare( Serial serial ) : base( serial ) - { - } + Name = m_Myname; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - { - Timer.DelayCall( TimeSpan.FromSeconds( 0 ), OnAfterDeserialize_Callback ); - } - } - } -} + if (version < 1) Timer.DelayCall(TimeSpan.FromSeconds(0), OnAfterDeserialize_Callback); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/ML/MinotaurHedge.cs b/Scripts/Items/Special/ML/MinotaurHedge.cs index df3435cea..4c695f54c 100644 --- a/Scripts/Items/Special/ML/MinotaurHedge.cs +++ b/Scripts/Items/Special/ML/MinotaurHedge.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class MinotaurHedge : Item - { - public override string DefaultName => "minotaur hedge"; + public class MinotaurHedge : Item + { + [Constructible] + public MinotaurHedge() : base(Utility.Random(3215, 4)) + { + Weight = 1.0; + } - [Constructible] - public MinotaurHedge() : base( Utility.Random( 3215, 4 ) ) - { - Weight = 1.0; - } + public MinotaurHedge(Serial serial) : base(serial) + { + } - public MinotaurHedge( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "minotaur hedge"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/ML/TormentedChains.cs b/Scripts/Items/Special/ML/TormentedChains.cs index 404aff48a..730c0254f 100644 --- a/Scripts/Items/Special/ML/TormentedChains.cs +++ b/Scripts/Items/Special/ML/TormentedChains.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class TormentedChains : Item - { - public override string DefaultName => "chains of the tormented"; + public class TormentedChains : Item + { + [Constructible] + public TormentedChains() : base(Utility.Random(6663, 2)) + { + Weight = 1.0; + } - [Constructible] - public TormentedChains() : base( Utility.Random( 6663, 2 ) ) - { - Weight = 1.0; - } + public TormentedChains(Serial serial) : base(serial) + { + } - public TormentedChains( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "chains of the tormented"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/MiniHouses.cs b/Scripts/Items/Special/MiniHouses.cs index 106b871b6..7e5fbd58f 100644 --- a/Scripts/Items/Special/MiniHouses.cs +++ b/Scripts/Items/Special/MiniHouses.cs @@ -2,232 +2,243 @@ using System; namespace Server.Items { - public class MiniHouseAddon : BaseAddon - { - private MiniHouseType m_Type; + public class MiniHouseAddon : BaseAddon + { + private MiniHouseType m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public MiniHouseType Type - { - get => m_Type; - set{ m_Type = value; Construct(); } - } + [Constructible] + public MiniHouseAddon() : this(MiniHouseType.StoneAndPlaster) + { + } - public override BaseAddonDeed Deed => new MiniHouseDeed( m_Type ); + [Constructible] + public MiniHouseAddon(MiniHouseType type) + { + m_Type = type; - [Constructible] - public MiniHouseAddon() : this( MiniHouseType.StoneAndPlaster ) - { - } + Construct(); + } - [Constructible] - public MiniHouseAddon( MiniHouseType type ) - { - m_Type = type; + public MiniHouseAddon(Serial serial) : base(serial) + { + } - Construct(); - } + [CommandProperty(AccessLevel.GameMaster)] + public MiniHouseType Type + { + get => m_Type; + set + { + m_Type = value; + Construct(); + } + } - public void Construct() - { - foreach ( AddonComponent c in Components ) - { - c.Addon = null; - c.Delete(); - } + public override BaseAddonDeed Deed => new MiniHouseDeed(m_Type); - Components.Clear(); + public void Construct() + { + foreach (AddonComponent c in Components) + { + c.Addon = null; + c.Delete(); + } - MiniHouseInfo info = MiniHouseInfo.GetInfo( m_Type ); + Components.Clear(); - int size = (int)Math.Sqrt( info.Graphics.Length ); - int num = 0; + MiniHouseInfo info = MiniHouseInfo.GetInfo(m_Type); - for ( int y = 0; y < size; ++y ) - for ( int x = 0; x < size; ++x ) - if ( info.Graphics[num] != 0x1 ) // Veteran Rewards Mod - AddComponent( new AddonComponent( info.Graphics[num++] ), size - x - 1, size - y - 1, 0 ); - } + int size = (int)Math.Sqrt(info.Graphics.Length); + int num = 0; - public MiniHouseAddon( Serial serial ) : base( serial ) - { - } + for (int y = 0; y < size; ++y) + for (int x = 0; x < size; ++x) + if (info.Graphics[num] != 0x1) // Veteran Rewards Mod + AddComponent(new AddonComponent(info.Graphics[num++]), size - x - 1, size - y - 1, 0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_Type ); - } + writer.Write((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Type = (MiniHouseType)reader.ReadInt(); - break; - } - } - } - } + switch (version) + { + case 0: + { + m_Type = (MiniHouseType)reader.ReadInt(); + break; + } + } + } + } - public class MiniHouseDeed : BaseAddonDeed - { - private MiniHouseType m_Type; + public class MiniHouseDeed : BaseAddonDeed + { + private MiniHouseType m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public MiniHouseType Type - { - get => m_Type; - set{ m_Type = value; InvalidateProperties(); } - } + [Constructible] + public MiniHouseDeed() : this(MiniHouseType.StoneAndPlaster) + { + } - public override BaseAddon Addon => new MiniHouseAddon( m_Type ); - public override int LabelNumber => 1062096; // a mini house deed + [Constructible] + public MiniHouseDeed(MiniHouseType type) + { + m_Type = type; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + Weight = 1.0; + LootType = LootType.Blessed; + } - list.Add( MiniHouseInfo.GetInfo( m_Type ).LabelNumber ); - } + public MiniHouseDeed(Serial serial) : base(serial) + { + } - [Constructible] - public MiniHouseDeed() : this( MiniHouseType.StoneAndPlaster ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public MiniHouseType Type + { + get => m_Type; + set + { + m_Type = value; + InvalidateProperties(); + } + } - [Constructible] - public MiniHouseDeed( MiniHouseType type ) - { - m_Type = type; + public override BaseAddon Addon => new MiniHouseAddon(m_Type); + public override int LabelNumber => 1062096; // a mini house deed - Weight = 1.0; - LootType = LootType.Blessed; - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public MiniHouseDeed( Serial serial ) : base( serial ) - { - } + list.Add(MiniHouseInfo.GetInfo(m_Type).LabelNumber); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_Type ); - } + writer.Write((int)m_Type); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Type = (MiniHouseType)reader.ReadInt(); - break; - } - } + switch (version) + { + case 0: + { + m_Type = (MiniHouseType)reader.ReadInt(); + break; + } + } - if ( Weight == 0.0 ) - Weight = 1.0; - } - } + if (Weight == 0.0) + Weight = 1.0; + } + } - public enum MiniHouseType - { - StoneAndPlaster, - FieldStone, - SmallBrick, - Wooden, - WoodAndPlaster, - ThatchedRoof, - Brick, - TwoStoryWoodAndPlaster, - TwoStoryStoneAndPlaster, - Tower, - SmallStoneKeep, - Castle, - LargeHouseWithPatio, - MarbleHouseWithPatio, - SmallStoneTower, - TwoStoryLogCabin, - TwoStoryVilla, - SandstoneHouseWithPatio, - SmallStoneWorkshop, - SmallMarbleWorkshop, - MalasMountainPass, //Veteran reward house - ChurchAtNight //Veteran reward house - } + public enum MiniHouseType + { + StoneAndPlaster, + FieldStone, + SmallBrick, + Wooden, + WoodAndPlaster, + ThatchedRoof, + Brick, + TwoStoryWoodAndPlaster, + TwoStoryStoneAndPlaster, + Tower, + SmallStoneKeep, + Castle, + LargeHouseWithPatio, + MarbleHouseWithPatio, + SmallStoneTower, + TwoStoryLogCabin, + TwoStoryVilla, + SandstoneHouseWithPatio, + SmallStoneWorkshop, + SmallMarbleWorkshop, + MalasMountainPass, //Veteran reward house + ChurchAtNight //Veteran reward house + } - public class MiniHouseInfo - { - public int[] Graphics { get; } + public class MiniHouseInfo + { + private static MiniHouseInfo[] m_Info = + { + /* Stone and plaster house */ new MiniHouseInfo(0x22C4, 1, 1011303), + /* Field stone house */ new MiniHouseInfo(0x22DE, 1, 1011304), + /* Small brick house */ new MiniHouseInfo(0x22DF, 1, 1011305), + /* Wooden house */ new MiniHouseInfo(0x22C9, 1, 1011306), + /* Wood and plaster house */ new MiniHouseInfo(0x22E0, 1, 1011307), + /* Thatched-roof cottage */ new MiniHouseInfo(0x22E1, 1, 1011308), + /* Brick house */ new MiniHouseInfo(1011309, 0x22CD, 0x22CB, 0x22CC, 0x22CA), + /* Two-story wood and plaster house */ new MiniHouseInfo(1011310, 0x2301, 0x2302, 0x2304, 0x2303), + /* Two-story stone and plaster house */ new MiniHouseInfo(1011311, 0x22FC, 0x22FD, 0x22FF, 0x22FE), + /* Tower */ new MiniHouseInfo(1011312, 0x22F7, 0x22F8, 0x22FA, 0x22F9), + /* Small stone keep */ new MiniHouseInfo(0x22E6, 9, 1011313), + /* Castle */ + new MiniHouseInfo(1011314, 0x22CE, 0x22D0, 0x22D2, 0x22D7, 0x22CF, 0x22D1, 0x22D4, 0x22D9, 0x22D3, 0x22D5, + 0x22D6, 0x22DB, 0x22D8, 0x22DA, 0x22DC, 0x22DD), + /* Large house with patio */ new MiniHouseInfo(0x22E2, 4, 1011315), + /* Marble house with patio */ new MiniHouseInfo(0x22EF, 4, 1011316), + /* Small stone tower */ new MiniHouseInfo(0x22F5, 1, 1011317), + /* Two-story log cabin */ new MiniHouseInfo(0x22FB, 1, 1011318), + /* Two-story villa */ new MiniHouseInfo(0x2300, 1, 1011319), + /* Sandstone house with patio */ new MiniHouseInfo(0x22F3, 1, 1011320), + /* Small stone workshop */ new MiniHouseInfo(0x22F6, 1, 1011321), + /* Small marble workshop */ new MiniHouseInfo(0x22F4, 1, 1011322), + /* Malas Mountain Pass */ new MiniHouseInfo(1062692, 0x2316, 0x2315, 0x2314, 0x2313), + /* Church At Night */ new MiniHouseInfo(1072215, 0x2318, 0x2317, 0x2319, 0x1) + }; - public int LabelNumber { get; } + public MiniHouseInfo(int start, int count, int labelNumber) + { + Graphics = new int[count]; - public MiniHouseInfo( int start, int count, int labelNumber ) - { - Graphics = new int[count]; + for (int i = 0; i < count; ++i) + Graphics[i] = start + i; - for ( int i = 0; i < count; ++i ) - Graphics[i] = start + i; + LabelNumber = labelNumber; + } - LabelNumber = labelNumber; - } + public MiniHouseInfo(int labelNumber, params int[] graphics) + { + LabelNumber = labelNumber; + Graphics = graphics; + } - public MiniHouseInfo( int labelNumber, params int[] graphics ) - { - LabelNumber = labelNumber; - Graphics = graphics; - } + public int[] Graphics{ get; } - private static MiniHouseInfo[] m_Info = { - /* Stone and plaster house */ new MiniHouseInfo( 0x22C4, 1, 1011303 ), - /* Field stone house */ new MiniHouseInfo( 0x22DE, 1, 1011304 ), - /* Small brick house */ new MiniHouseInfo( 0x22DF, 1, 1011305 ), - /* Wooden house */ new MiniHouseInfo( 0x22C9, 1, 1011306 ), - /* Wood and plaster house */ new MiniHouseInfo( 0x22E0, 1, 1011307 ), - /* Thatched-roof cottage */ new MiniHouseInfo( 0x22E1, 1, 1011308 ), - /* Brick house */ new MiniHouseInfo( 1011309, 0x22CD, 0x22CB, 0x22CC, 0x22CA ), - /* Two-story wood and plaster house */ new MiniHouseInfo( 1011310, 0x2301, 0x2302, 0x2304, 0x2303 ), - /* Two-story stone and plaster house */ new MiniHouseInfo( 1011311, 0x22FC, 0x22FD, 0x22FF, 0x22FE ), - /* Tower */ new MiniHouseInfo( 1011312, 0x22F7, 0x22F8, 0x22FA, 0x22F9 ), - /* Small stone keep */ new MiniHouseInfo( 0x22E6, 9, 1011313 ), - /* Castle */ new MiniHouseInfo( 1011314, 0x22CE, 0x22D0, 0x22D2, 0x22D7, 0x22CF, 0x22D1, 0x22D4, 0x22D9, 0x22D3, 0x22D5, 0x22D6, 0x22DB, 0x22D8, 0x22DA, 0x22DC, 0x22DD ), - /* Large house with patio */ new MiniHouseInfo( 0x22E2, 4, 1011315 ), - /* Marble house with patio */ new MiniHouseInfo( 0x22EF, 4, 1011316 ), - /* Small stone tower */ new MiniHouseInfo( 0x22F5, 1, 1011317 ), - /* Two-story log cabin */ new MiniHouseInfo( 0x22FB, 1, 1011318 ), - /* Two-story villa */ new MiniHouseInfo( 0x2300, 1, 1011319 ), - /* Sandstone house with patio */ new MiniHouseInfo( 0x22F3, 1, 1011320 ), - /* Small stone workshop */ new MiniHouseInfo( 0x22F6, 1, 1011321 ), - /* Small marble workshop */ new MiniHouseInfo( 0x22F4, 1, 1011322 ), - /* Malas Mountain Pass */ new MiniHouseInfo( 1062692, 0x2316, 0x2315, 0x2314, 0x2313 ), - /* Church At Night */ new MiniHouseInfo( 1072215, 0x2318, 0x2317, 0x2319, 0x1 ) - }; + public int LabelNumber{ get; } - public static MiniHouseInfo GetInfo( MiniHouseType type ) - { - int v = (int)type; + public static MiniHouseInfo GetInfo(MiniHouseType type) + { + int v = (int)type; - if ( v < 0 || v >= m_Info.Length ) - v = 0; + if (v < 0 || v >= m_Info.Length) + v = 0; - return m_Info[v]; - } - } -} + return m_Info[v]; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/MonsterStatuette.cs b/Scripts/Items/Special/MonsterStatuette.cs index e3426d425..cbeed2256 100644 --- a/Scripts/Items/Special/MonsterStatuette.cs +++ b/Scripts/Items/Special/MonsterStatuette.cs @@ -1,308 +1,315 @@ -using Server.Multis; -using Server.Gumps; -using Server.Network; using Server.Engines.VeteranRewards; +using Server.Gumps; +using Server.Multis; +using Server.Network; namespace Server.Items { - public enum MonsterStatuetteType - { - Crocodile, - Daemon, - Dragon, - EarthElemental, - Ettin, - Gargoyle, - Gorilla, - Lich, - Lizardman, - Ogre, - Orc, - Ratman, - Skeleton, - Troll, - Cow, - Zombie, - Llama, - Ophidian, - Reaper, - Mongbat, - Gazer, - FireElemental, - Wolf, - PhillipsWoodenSteed, - Seahorse, - Harrower, - Efreet, - Slime, - PlagueBeast, - RedDeath, - Spider, - OphidianArchMage, - OphidianWarrior, - OphidianKnight, - OphidianMage, - DreadHorn, - Minotaur, - BlackCat, - HalloweenGhoul, - Santa - } + public enum MonsterStatuetteType + { + Crocodile, + Daemon, + Dragon, + EarthElemental, + Ettin, + Gargoyle, + Gorilla, + Lich, + Lizardman, + Ogre, + Orc, + Ratman, + Skeleton, + Troll, + Cow, + Zombie, + Llama, + Ophidian, + Reaper, + Mongbat, + Gazer, + FireElemental, + Wolf, + PhillipsWoodenSteed, + Seahorse, + Harrower, + Efreet, + Slime, + PlagueBeast, + RedDeath, + Spider, + OphidianArchMage, + OphidianWarrior, + OphidianKnight, + OphidianMage, + DreadHorn, + Minotaur, + BlackCat, + HalloweenGhoul, + Santa + } - public class MonsterStatuetteInfo - { - public int LabelNumber { get; } + public class MonsterStatuetteInfo + { + private static MonsterStatuetteInfo[] m_Table = + { + /* Crocodile */ new MonsterStatuetteInfo(1041249, 0x20DA, 660), + /* Daemon */ new MonsterStatuetteInfo(1041250, 0x20D3, 357), + /* Dragon */ new MonsterStatuetteInfo(1041251, 0x20D6, 362), + /* EarthElemental */ new MonsterStatuetteInfo(1041252, 0x20D7, 268), + /* Ettin */ new MonsterStatuetteInfo(1041253, 0x20D8, 367), + /* Gargoyle */ new MonsterStatuetteInfo(1041254, 0x20D9, 372), + /* Gorilla */ new MonsterStatuetteInfo(1041255, 0x20F5, 158), + /* Lich */ new MonsterStatuetteInfo(1041256, 0x20F8, 1001), + /* Lizardman */ new MonsterStatuetteInfo(1041257, 0x20DE, 417), + /* Ogre */ new MonsterStatuetteInfo(1041258, 0x20DF, 427), + /* Orc */ new MonsterStatuetteInfo(1041259, 0x20E0, 1114), + /* Ratman */ new MonsterStatuetteInfo(1041260, 0x20E3, 437), + /* Skeleton */ new MonsterStatuetteInfo(1041261, 0x20E7, 1165), + /* Troll */ new MonsterStatuetteInfo(1041262, 0x20E9, 461), + /* Cow */ new MonsterStatuetteInfo(1041263, 0x2103, 120), + /* Zombie */ new MonsterStatuetteInfo(1041264, 0x20EC, 471), + /* Llama */ new MonsterStatuetteInfo(1041265, 0x20F6, 1011), + /* Ophidian */ new MonsterStatuetteInfo(1049742, 0x2133, 634), + /* Reaper */ new MonsterStatuetteInfo(1049743, 0x20FA, 442), + /* Mongbat */ new MonsterStatuetteInfo(1049744, 0x20F9, 422), + /* Gazer */ new MonsterStatuetteInfo(1049768, 0x20F4, 377), + /* FireElemental */ new MonsterStatuetteInfo(1049769, 0x20F3, 838), + /* Wolf */ new MonsterStatuetteInfo(1049770, 0x2122, 229), + /* Phillip's Steed */ new MonsterStatuetteInfo(1063488, 0x3FFE, 168), + /* Seahorse */ new MonsterStatuetteInfo(1070819, 0x25BA, 138), + /* Harrower */ new MonsterStatuetteInfo(1080520, 0x25BB, new[] { 0x289, 0x28A, 0x28B }), + /* Efreet */ new MonsterStatuetteInfo(1080521, 0x2590, 0x300), + /* Slime */ new MonsterStatuetteInfo(1015246, 0x20E8, 456), + /* PlagueBeast */ new MonsterStatuetteInfo(1029747, 0x2613, 0x1BF), + /* RedDeath */ new MonsterStatuetteInfo(1094932, 0x2617, new int[] { }), + /* Spider */ new MonsterStatuetteInfo(1029668, 0x25C4, 1170), + /* OphidianArchMage */ new MonsterStatuetteInfo(1029641, 0x25A9, 639), + /* OphidianWarrior */ new MonsterStatuetteInfo(1029645, 0x25AD, 634), + /* OphidianKnight */ new MonsterStatuetteInfo(1029642, 0x25aa, 634), + /* OphidianMage */ new MonsterStatuetteInfo(1029643, 0x25ab, 639), + /* DreadHorn */ new MonsterStatuetteInfo(1031651, 0x2D83, 0xA8), + /* Minotaur */ new MonsterStatuetteInfo(1031657, 0x2D89, 0x596), + /* Black Cat */ new MonsterStatuetteInfo(1096928, 0x4688, 0x69), + /* HalloweenGhoul */ new MonsterStatuetteInfo(1076782, 0x2109, 0x482), + /* Santa */ new MonsterStatuetteInfo(1097968, 0x4A98, 0x669) + }; - public int ItemID { get; } + public MonsterStatuetteInfo(int labelNumber, int itemID, int baseSoundID) + { + LabelNumber = labelNumber; + ItemID = itemID; + Sounds = new[] { baseSoundID, baseSoundID + 1, baseSoundID + 2, baseSoundID + 3, baseSoundID + 4 }; + } - public int[] Sounds { get; } + public MonsterStatuetteInfo(int labelNumber, int itemID, int[] sounds) + { + LabelNumber = labelNumber; + ItemID = itemID; + Sounds = sounds; + } - public MonsterStatuetteInfo( int labelNumber, int itemID, int baseSoundID ) - { - LabelNumber = labelNumber; - ItemID = itemID; - Sounds = new[]{ baseSoundID, baseSoundID + 1, baseSoundID + 2, baseSoundID + 3, baseSoundID + 4 }; - } + public int LabelNumber{ get; } - public MonsterStatuetteInfo( int labelNumber, int itemID, int[] sounds ) - { - LabelNumber = labelNumber; - ItemID = itemID; - Sounds = sounds; - } + public int ItemID{ get; } - private static MonsterStatuetteInfo[] m_Table = { - /* Crocodile */ new MonsterStatuetteInfo( 1041249, 0x20DA, 660 ), - /* Daemon */ new MonsterStatuetteInfo( 1041250, 0x20D3, 357 ), - /* Dragon */ new MonsterStatuetteInfo( 1041251, 0x20D6, 362 ), - /* EarthElemental */ new MonsterStatuetteInfo( 1041252, 0x20D7, 268 ), - /* Ettin */ new MonsterStatuetteInfo( 1041253, 0x20D8, 367 ), - /* Gargoyle */ new MonsterStatuetteInfo( 1041254, 0x20D9, 372 ), - /* Gorilla */ new MonsterStatuetteInfo( 1041255, 0x20F5, 158 ), - /* Lich */ new MonsterStatuetteInfo( 1041256, 0x20F8, 1001 ), - /* Lizardman */ new MonsterStatuetteInfo( 1041257, 0x20DE, 417 ), - /* Ogre */ new MonsterStatuetteInfo( 1041258, 0x20DF, 427 ), - /* Orc */ new MonsterStatuetteInfo( 1041259, 0x20E0, 1114 ), - /* Ratman */ new MonsterStatuetteInfo( 1041260, 0x20E3, 437 ), - /* Skeleton */ new MonsterStatuetteInfo( 1041261, 0x20E7, 1165 ), - /* Troll */ new MonsterStatuetteInfo( 1041262, 0x20E9, 461 ), - /* Cow */ new MonsterStatuetteInfo( 1041263, 0x2103, 120 ), - /* Zombie */ new MonsterStatuetteInfo( 1041264, 0x20EC, 471 ), - /* Llama */ new MonsterStatuetteInfo( 1041265, 0x20F6, 1011 ), - /* Ophidian */ new MonsterStatuetteInfo( 1049742, 0x2133, 634 ), - /* Reaper */ new MonsterStatuetteInfo( 1049743, 0x20FA, 442 ), - /* Mongbat */ new MonsterStatuetteInfo( 1049744, 0x20F9, 422 ), - /* Gazer */ new MonsterStatuetteInfo( 1049768, 0x20F4, 377 ), - /* FireElemental */ new MonsterStatuetteInfo( 1049769, 0x20F3, 838 ), - /* Wolf */ new MonsterStatuetteInfo( 1049770, 0x2122, 229 ), - /* Phillip's Steed */ new MonsterStatuetteInfo( 1063488, 0x3FFE, 168 ), - /* Seahorse */ new MonsterStatuetteInfo( 1070819, 0x25BA, 138 ), - /* Harrower */ new MonsterStatuetteInfo( 1080520, 0x25BB, new[] { 0x289, 0x28A, 0x28B } ), - /* Efreet */ new MonsterStatuetteInfo( 1080521, 0x2590, 0x300 ), - /* Slime */ new MonsterStatuetteInfo( 1015246, 0x20E8, 456 ), - /* PlagueBeast */ new MonsterStatuetteInfo( 1029747, 0x2613, 0x1BF ), - /* RedDeath */ new MonsterStatuetteInfo( 1094932, 0x2617, new int[] { } ), - /* Spider */ new MonsterStatuetteInfo( 1029668, 0x25C4, 1170 ), - /* OphidianArchMage */ new MonsterStatuetteInfo( 1029641, 0x25A9, 639 ), - /* OphidianWarrior */ new MonsterStatuetteInfo( 1029645, 0x25AD, 634 ), - /* OphidianKnight */ new MonsterStatuetteInfo( 1029642, 0x25aa, 634 ), - /* OphidianMage */ new MonsterStatuetteInfo( 1029643, 0x25ab, 639 ), - /* DreadHorn */ new MonsterStatuetteInfo( 1031651, 0x2D83, 0xA8 ), - /* Minotaur */ new MonsterStatuetteInfo( 1031657, 0x2D89, 0x596 ), - /* Black Cat */ new MonsterStatuetteInfo( 1096928, 0x4688, 0x69 ), - /* HalloweenGhoul */ new MonsterStatuetteInfo( 1076782, 0x2109, 0x482 ), - /* Santa */ new MonsterStatuetteInfo( 1097968, 0x4A98, 0x669 ) - }; + public int[] Sounds{ get; } - public static MonsterStatuetteInfo GetInfo( MonsterStatuetteType type ) - { - int v = (int)type; + public static MonsterStatuetteInfo GetInfo(MonsterStatuetteType type) + { + int v = (int)type; - if ( v < 0 || v >= m_Table.Length ) - v = 0; + if (v < 0 || v >= m_Table.Length) + v = 0; - return m_Table[v]; - } - } + return m_Table[v]; + } + } - public class MonsterStatuette : Item, IRewardItem - { - private MonsterStatuetteType m_Type; - private bool m_TurnedOn; + public class MonsterStatuette : Item, IRewardItem + { + private bool m_TurnedOn; + private MonsterStatuetteType m_Type; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + [Constructible] + public MonsterStatuette() : this(MonsterStatuetteType.Crocodile) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool TurnedOn - { - get => m_TurnedOn; - set{ m_TurnedOn = value; InvalidateProperties(); } - } + [Constructible] + public MonsterStatuette(MonsterStatuetteType type) : base(MonsterStatuetteInfo.GetInfo(type).ItemID) + { + LootType = LootType.Blessed; - [CommandProperty( AccessLevel.GameMaster )] - public MonsterStatuetteType Type - { - get => m_Type; - set - { - m_Type = value; - ItemID = MonsterStatuetteInfo.GetInfo( m_Type ).ItemID; + m_Type = type; - if ( m_Type == MonsterStatuetteType.Slime ) - Hue = Utility.RandomSlimeHue(); - else if ( m_Type == MonsterStatuetteType.RedDeath ) - Hue = 0x21; - else if ( m_Type == MonsterStatuetteType.HalloweenGhoul ) - Hue = 0xF4; - else - Hue = 0; + if (m_Type == MonsterStatuetteType.Slime) + Hue = Utility.RandomSlimeHue(); + else if (m_Type == MonsterStatuetteType.RedDeath) + Hue = 0x21; + else if (m_Type == MonsterStatuetteType.HalloweenGhoul) + Hue = 0xF4; + } - InvalidateProperties(); - } - } + public MonsterStatuette(Serial serial) : base(serial) + { + } - public override int LabelNumber => MonsterStatuetteInfo.GetInfo( m_Type ).LabelNumber; + [CommandProperty(AccessLevel.GameMaster)] + public bool TurnedOn + { + get => m_TurnedOn; + set + { + m_TurnedOn = value; + InvalidateProperties(); + } + } - public override double DefaultWeight => 1.0; + [CommandProperty(AccessLevel.GameMaster)] + public MonsterStatuetteType Type + { + get => m_Type; + set + { + m_Type = value; + ItemID = MonsterStatuetteInfo.GetInfo(m_Type).ItemID; - [Constructible] - public MonsterStatuette() : this( MonsterStatuetteType.Crocodile ) - { - } + if (m_Type == MonsterStatuetteType.Slime) + Hue = Utility.RandomSlimeHue(); + else if (m_Type == MonsterStatuetteType.RedDeath) + Hue = 0x21; + else if (m_Type == MonsterStatuetteType.HalloweenGhoul) + Hue = 0xF4; + else + Hue = 0; - [Constructible] - public MonsterStatuette( MonsterStatuetteType type ) : base( MonsterStatuetteInfo.GetInfo( type ).ItemID ) - { - LootType = LootType.Blessed; + InvalidateProperties(); + } + } - m_Type = type; + public override int LabelNumber => MonsterStatuetteInfo.GetInfo(m_Type).LabelNumber; - if ( m_Type == MonsterStatuetteType.Slime ) - Hue = Utility.RandomSlimeHue(); - else if ( m_Type == MonsterStatuetteType.RedDeath ) - Hue = 0x21; - else if ( m_Type == MonsterStatuetteType.HalloweenGhoul ) - Hue = 0xF4; - } + public override double DefaultWeight => 1.0; - public override bool HandlesOnMovement => m_TurnedOn && IsLockedDown; + public override bool HandlesOnMovement => m_TurnedOn && IsLockedDown; - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m_TurnedOn && IsLockedDown && (!m.Hidden || m.AccessLevel == AccessLevel.Player) && Utility.InRange( m.Location, Location, 2 ) && !Utility.InRange( oldLocation, Location, 2 ) ) - { - int[] sounds = MonsterStatuetteInfo.GetInfo( m_Type ).Sounds; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - if ( sounds.Length > 0 ) - Effects.PlaySound( Location, Map, sounds[Utility.Random( sounds.Length )] ); - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m_TurnedOn && IsLockedDown && (!m.Hidden || m.AccessLevel == AccessLevel.Player) && + Utility.InRange(m.Location, Location, 2) && !Utility.InRange(oldLocation, Location, 2)) + { + int[] sounds = MonsterStatuetteInfo.GetInfo(m_Type).Sounds; - base.OnMovement( m, oldLocation ); - } + if (sounds.Length > 0) + Effects.PlaySound(Location, Map, sounds[Utility.Random(sounds.Length)]); + } - public MonsterStatuette( Serial serial ) : base( serial ) - { - } + base.OnMovement(m, oldLocation); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && IsRewardItem ) - list.Add( RewardSystem.GetRewardYearLabel( this, new object[]{ m_Type } ) ); // X Year Veteran Reward + if (Core.ML && IsRewardItem) + list.Add(RewardSystem.GetRewardYearLabel(this, new object[] { m_Type })); // X Year Veteran Reward - if ( m_TurnedOn ) - list.Add( 502695 ); // turned on - else - list.Add( 502696 ); // turned off - } + if (m_TurnedOn) + list.Add(502695); // turned on + else + list.Add(502696); // turned off + } - public bool IsOwner( Mobile mob ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public bool IsOwner(Mobile mob) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - return ( house != null && house.IsOwner( mob ) ); - } + return house != null && house.IsOwner(mob); + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsOwner( from ) ) - { - OnOffGump onOffGump = new OnOffGump( this ); - from.SendGump( onOffGump ); - } - else - { - from.SendLocalizedMessage( 502691 ); // You must be the owner to use this. - } - } + public override void OnDoubleClick(Mobile from) + { + if (IsOwner(from)) + { + OnOffGump onOffGump = new OnOffGump(this); + from.SendGump(onOffGump); + } + else + { + from.SendLocalizedMessage(502691); // You must be the owner to use this. + } + } - private class OnOffGump : Gump - { - private MonsterStatuette m_Statuette; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public OnOffGump( MonsterStatuette statuette ) : base( 150, 200 ) - { - m_Statuette = statuette; + writer.Write(0); // version - AddBackground( 0, 0, 300, 150, 0xA28 ); + writer.WriteEncodedInt((int)m_Type); + writer.Write(m_TurnedOn); + writer.Write(IsRewardItem); + } - AddHtmlLocalized( 45, 20, 300, 35, statuette.TurnedOn ? 1011035 : 1011034, false, false ); // [De]Activate this item + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - AddButton( 40, 53, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 80, 55, 65, 35, 1011036, false, false ); // OKAY + int version = reader.ReadInt(); - AddButton( 150, 53, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 190, 55, 100, 35, 1011012, false, false ); // CANCEL - } + switch (version) + { + case 0: + { + m_Type = (MonsterStatuetteType)reader.ReadEncodedInt(); + m_TurnedOn = reader.ReadBool(); + IsRewardItem = reader.ReadBool(); + break; + } + } + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - Mobile from = sender.Mobile; + private class OnOffGump : Gump + { + private MonsterStatuette m_Statuette; - if ( info.ButtonID == 1 ) - { - bool newValue = !m_Statuette.TurnedOn; - m_Statuette.TurnedOn = newValue; + public OnOffGump(MonsterStatuette statuette) : base(150, 200) + { + m_Statuette = statuette; - if ( newValue && !m_Statuette.IsLockedDown ) - from.SendLocalizedMessage( 502693 ); // Remember, this only works when locked down. - } - else - { - from.SendLocalizedMessage( 502694 ); // Cancelled action. - } - } - } + AddBackground(0, 0, 300, 150, 0xA28); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddHtmlLocalized(45, 20, 300, 35, statuette.TurnedOn ? 1011035 : 1011034, false, + false); // [De]Activate this item - writer.Write( (int) 0 ); // version + AddButton(40, 53, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(80, 55, 65, 35, 1011036, false, false); // OKAY - writer.WriteEncodedInt( (int) m_Type ); - writer.Write( (bool) m_TurnedOn ); - writer.Write( (bool) IsRewardItem ); - } + AddButton(150, 53, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(190, 55, 100, 35, 1011012, false, false); // CANCEL + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnResponse(NetState sender, RelayInfo info) + { + Mobile from = sender.Mobile; - int version = reader.ReadInt(); + if (info.ButtonID == 1) + { + bool newValue = !m_Statuette.TurnedOn; + m_Statuette.TurnedOn = newValue; - switch ( version ) - { - case 0: - { - m_Type = (MonsterStatuetteType)reader.ReadEncodedInt(); - m_TurnedOn = reader.ReadBool(); - IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + if (newValue && !m_Statuette.IsLockedDown) + from.SendLocalizedMessage(502693); // Remember, this only works when locked down. + } + else + { + from.SendLocalizedMessage(502694); // Cancelled action. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastBackpack.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastBackpack.cs index 7ff43af4e..036936d66 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastBackpack.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastBackpack.cs @@ -2,179 +2,185 @@ using System.Collections.Generic; namespace Server.Items { - public class PlagueBeastBackpack : BaseContainer - { - public override int DefaultMaxWeight => 0; - public override int DefaultMaxItems => 0; - public override int DefaultGumpID => 0x2A63; - public override int DefaultDropSound => 0x23F; + public class PlagueBeastBackpack : BaseContainer + { + private static int[,,] m_Positions = + { + { { 275, 85 }, { 360, 111 }, { 375, 184 }, { 332, 228 }, { 141, 105 }, { 189, 75 } }, + { { 274, 34 }, { 327, 89 }, { 354, 168 }, { 304, 225 }, { 113, 86 }, { 189, 75 } }, + { { 276, 79 }, { 369, 117 }, { 372, 192 }, { 336, 230 }, { 141, 116 }, { 189, 75 } } + }; - private static int[,,] m_Positions = { - { { 275, 85 }, { 360, 111 }, { 375, 184 }, { 332, 228 }, { 141, 105 }, { 189, 75 } }, - { { 274, 34 }, { 327, 89 }, { 354, 168 }, { 304, 225 }, { 113, 86 }, { 189, 75 } }, - { { 276, 79 }, { 369, 117 }, { 372, 192 }, { 336, 230 }, { 141, 116 }, { 189, 75 } }, - }; + private static int[] m_BrainHues = + { + 0x2B, 0x42, 0x54, 0x60 + }; - private static int[] m_BrainHues = { - 0x2B, 0x42, 0x54, 0x60 - }; + public PlagueBeastBackpack() : base(0x261B) + { + Layer = Layer.Backpack; + } - public PlagueBeastBackpack() : base( 0x261B ) - { - Layer = Layer.Backpack; - } + public PlagueBeastBackpack(Serial serial) : base(serial) + { + } - public void Initialize() - { - AddInnard( 0x1CF6, 0x0, 227, 128 ); - AddInnard( 0x1D10, 0x0, 251, 128 ); - AddInnard( 0x1FBE, 0x21, 240, 83 ); + public override int DefaultMaxWeight => 0; + public override int DefaultMaxItems => 0; + public override int DefaultGumpID => 0x2A63; + public override int DefaultDropSound => 0x23F; - AddInnard( new PlagueBeastHeart(), 229, 104 ); + public void Initialize() + { + AddInnard(0x1CF6, 0x0, 227, 128); + AddInnard(0x1D10, 0x0, 251, 128); + AddInnard(0x1FBE, 0x21, 240, 83); - AddInnard( 0x1D06, 0x0, 283, 91 ); - AddInnard( 0x1FAF, 0x21, 315, 107 ); - AddInnard( 0x1FB9, 0x21, 289, 87 ); - AddInnard( 0x9E7, 0x21, 304, 96 ); - AddInnard( 0x1B1A, 0x66D, 335, 102 ); - AddInnard( 0x1D10, 0x0, 338, 146 ); - AddInnard( 0x1FB3, 0x21, 358, 167 ); - AddInnard( 0x1D0B, 0x0, 357, 155 ); - AddInnard( 0x9E7, 0x21, 339, 184 ); - AddInnard( 0x1B1A, 0x66D, 157, 172 ); - AddInnard( 0x1D11, 0x0, 147, 157 ); - AddInnard( 0x1FB9, 0x21, 121, 131 ); - AddInnard( 0x9E7, 0x21, 166, 176 ); - AddInnard( 0x1D0B, 0x0, 122, 138 ); - AddInnard( 0x1D0D, 0x0, 118, 150 ); - AddInnard( 0x1FB3, 0x21, 97, 123 ); - AddInnard( 0x1D08, 0x0, 115, 113 ); - AddInnard( 0x9E7, 0x21, 109, 109 ); - AddInnard( 0x9E7, 0x21, 91, 122 ); - AddInnard( 0x9E7, 0x21, 94, 160 ); - AddInnard( 0x1B19, 0x66D, 170, 121 ); - AddInnard( 0x1FAF, 0x21, 161, 111 ); - AddInnard( 0x1D0B, 0x0, 158, 112 ); - AddInnard( 0x9E7, 0x21, 159, 101 ); - AddInnard( 0x1D10, 0x0, 132, 177 ); - AddInnard( 0x1D0E, 0x0, 110, 178 ); - AddInnard( 0x1FB3, 0x21, 95, 194 ); - AddInnard( 0x1FAF, 0x21, 154, 203 ); - AddInnard( 0x1B1A, 0x66D, 110, 237 ); - AddInnard( 0x9E7, 0x21, 111, 171 ); - AddInnard( 0x9E7, 0x21, 90, 197 ); - AddInnard( 0x9E7, 0x21, 166, 205 ); - AddInnard( 0x9E7, 0x21, 96, 242 ); - AddInnard( 0x1D10, 0x0, 334, 196 ); - AddInnard( 0x1D0B, 0x0, 322, 270 ); + AddInnard(new PlagueBeastHeart(), 229, 104); - List organs = new List(); - PlagueBeastOrgan organ; + AddInnard(0x1D06, 0x0, 283, 91); + AddInnard(0x1FAF, 0x21, 315, 107); + AddInnard(0x1FB9, 0x21, 289, 87); + AddInnard(0x9E7, 0x21, 304, 96); + AddInnard(0x1B1A, 0x66D, 335, 102); + AddInnard(0x1D10, 0x0, 338, 146); + AddInnard(0x1FB3, 0x21, 358, 167); + AddInnard(0x1D0B, 0x0, 357, 155); + AddInnard(0x9E7, 0x21, 339, 184); + AddInnard(0x1B1A, 0x66D, 157, 172); + AddInnard(0x1D11, 0x0, 147, 157); + AddInnard(0x1FB9, 0x21, 121, 131); + AddInnard(0x9E7, 0x21, 166, 176); + AddInnard(0x1D0B, 0x0, 122, 138); + AddInnard(0x1D0D, 0x0, 118, 150); + AddInnard(0x1FB3, 0x21, 97, 123); + AddInnard(0x1D08, 0x0, 115, 113); + AddInnard(0x9E7, 0x21, 109, 109); + AddInnard(0x9E7, 0x21, 91, 122); + AddInnard(0x9E7, 0x21, 94, 160); + AddInnard(0x1B19, 0x66D, 170, 121); + AddInnard(0x1FAF, 0x21, 161, 111); + AddInnard(0x1D0B, 0x0, 158, 112); + AddInnard(0x9E7, 0x21, 159, 101); + AddInnard(0x1D10, 0x0, 132, 177); + AddInnard(0x1D0E, 0x0, 110, 178); + AddInnard(0x1FB3, 0x21, 95, 194); + AddInnard(0x1FAF, 0x21, 154, 203); + AddInnard(0x1B1A, 0x66D, 110, 237); + AddInnard(0x9E7, 0x21, 111, 171); + AddInnard(0x9E7, 0x21, 90, 197); + AddInnard(0x9E7, 0x21, 166, 205); + AddInnard(0x9E7, 0x21, 96, 242); + AddInnard(0x1D10, 0x0, 334, 196); + AddInnard(0x1D0B, 0x0, 322, 270); - for ( int i = 0; i < 6; i++ ) - { - int random = Utility.Random( 3 ); + List organs = new List(); + PlagueBeastOrgan organ; - if ( i == 5 ) - random = 0; + for (int i = 0; i < 6; i++) + { + int random = Utility.Random(3); - switch ( random ) - { - default: - case 0: organ = new PlagueBeastRockOrgan(); break; - case 1: organ = new PlagueBeastMaidenOrgan(); break; - case 2: organ = new PlagueBeastRubbleOrgan(); break; - } + if (i == 5) + random = 0; - organs.Add( organ ); - AddInnard( organ, m_Positions[ random, i, 0 ], m_Positions[ random, i, 1 ] ); - } + switch (random) + { + default: + case 0: + organ = new PlagueBeastRockOrgan(); + break; + case 1: + organ = new PlagueBeastMaidenOrgan(); + break; + case 2: + organ = new PlagueBeastRubbleOrgan(); + break; + } - organ = new PlagueBeastBackupOrgan(); - organs.Add( organ ); - AddInnard( organ, 129, 214 ); + organs.Add(organ); + AddInnard(organ, m_Positions[random, i, 0], m_Positions[random, i, 1]); + } - for ( int i = 0; i < m_BrainHues.Length; i++ ) - { - int random = Utility.Random( organs.Count ); - organ = organs[ random ]; - organ.BrainHue = m_BrainHues[ i ]; - organs.RemoveAt( random ); - } + organ = new PlagueBeastBackupOrgan(); + organs.Add(organ); + AddInnard(organ, 129, 214); - organs.Clear(); + for (int i = 0; i < m_BrainHues.Length; i++) + { + int random = Utility.Random(organs.Count); + organ = organs[random]; + organ.BrainHue = m_BrainHues[i]; + organs.RemoveAt(random); + } - AddInnard( new PlagueBeastMainOrgan(), 240, 161 ); - } + organs.Clear(); - public override bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage ) - { - if ( dropped is PlagueBeastInnard || dropped is PlagueBeastGland ) - return base.TryDropItem( from, dropped, sendFullMessage ); + AddInnard(new PlagueBeastMainOrgan(), 240, 161); + } - return false; - } + public override bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage) + { + if (dropped is PlagueBeastInnard || dropped is PlagueBeastGland) + return base.TryDropItem(from, dropped, sendFullMessage); - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( IsAccessibleTo( from ) && ( item is PlagueBeastInnard || item is PlagueBeastGland ) ) - { - Rectangle2D ir = ItemBounds.Table[ item.ItemID ]; - int x, y; - int cx = p.X + ir.X + ir.Width / 2; - int cy = p.Y + ir.Y + ir.Height / 2; + return false; + } - for ( int i = Items.Count - 1; i >= 0; i-- ) - { - if ( Items[ i ] is PlagueBeastComponent innard ) - { - Rectangle2D r = ItemBounds.Table[ innard.ItemID ]; + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (IsAccessibleTo(from) && (item is PlagueBeastInnard || item is PlagueBeastGland)) + { + Rectangle2D ir = ItemBounds.Table[item.ItemID]; + int x, y; + int cx = p.X + ir.X + ir.Width / 2; + int cy = p.Y + ir.Y + ir.Height / 2; - x = innard.X + r.X; - y = innard.Y + r.Y; + for (int i = Items.Count - 1; i >= 0; i--) + if (Items[i] is PlagueBeastComponent innard) + { + Rectangle2D r = ItemBounds.Table[innard.ItemID]; - if ( cx >= x && cx <= x + r.Width && cy >= y && cy <= y + r.Height ) - { - innard.OnDragDrop( from, item ); - break; - } - } - } + x = innard.X + r.X; + y = innard.Y + r.Y; - return base.OnDragDropInto( from, item, p ); - } + if (cx >= x && cx <= x + r.Width && cy >= y && cy <= y + r.Height) + { + innard.OnDragDrop(from, item); + break; + } + } - return false; - } + return base.OnDragDropInto(from, item, p); + } - public void AddInnard( int itemID, int hue, int x, int y ) - { - AddInnard( new PlagueBeastInnard( itemID, hue ), x, y ); - } + return false; + } - public void AddInnard( PlagueBeastInnard innard, int x, int y ) - { - AddItem( innard ); - innard.Location = new Point3D( x, y, 0 ); - innard.Map = Map; - } + public void AddInnard(int itemID, int hue, int x, int y) + { + AddInnard(new PlagueBeastInnard(itemID, hue), x, y); + } - public PlagueBeastBackpack( Serial serial ) : base( serial ) - { - } + public void AddInnard(PlagueBeastInnard innard, int x, int y) + { + AddItem(innard); + innard.Location = new Point3D(x, y, 0); + innard.Map = Map; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastBlood.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastBlood.cs index f5f617da0..a5de858f9 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastBlood.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastBlood.cs @@ -3,112 +3,108 @@ using Server.Network; namespace Server.Items { - public class PlagueBeastBlood : PlagueBeastComponent - { - public bool Patched => ItemID == 0x1765; + public class PlagueBeastBlood : PlagueBeastComponent + { + private Timer m_Timer; - public bool Starting => ItemID == 0x122C; + public PlagueBeastBlood() : base(0x122C, 0) + { + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1.5), TimeSpan.FromSeconds(1.5), 3, Hemorrhage); + } - private Timer m_Timer; + public PlagueBeastBlood(Serial serial) : base(serial) + { + } - public PlagueBeastBlood() : base( 0x122C, 0 ) - { - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1.5 ), TimeSpan.FromSeconds( 1.5 ), 3, Hemorrhage ); - } + public bool Patched => ItemID == 0x1765; - public override void OnAfterDelete() - { - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); - } + public bool Starting => ItemID == 0x122C; - public override bool OnBandage( Mobile from ) - { - if ( IsAccessibleTo( from ) && !Patched ) - { - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); + public override void OnAfterDelete() + { + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); + } - if ( Starting ) - { - X += 2; - Y -= 9; + public override bool OnBandage(Mobile from) + { + if (IsAccessibleTo(from) && !Patched) + { + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); - if ( Organ is PlagueBeastRubbleOrgan ) - Y -= 5; - else if ( Organ is PlagueBeastBackupOrgan ) - X += 7; - } - else - { - X -= 4; - Y -= 2; - } + if (Starting) + { + X += 2; + Y -= 9; - ItemID = 0x1765; + if (Organ is PlagueBeastRubbleOrgan) + Y -= 5; + else if (Organ is PlagueBeastBackupOrgan) + X += 7; + } + else + { + X -= 4; + Y -= 2; + } - Container pack = Owner?.Backpack; + ItemID = 0x1765; - if ( pack != null ) - { - for ( int i = 0; i < pack.Items.Count; i++ ) - { - if ( pack.Items[ i ] is PlagueBeastMainOrgan main && main.Complete ) - main.FinishOpening( from ); - } - } + Container pack = Owner?.Backpack; - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071916 ); // * You patch up the wound with a bandage * + if (pack != null) + for (int i = 0; i < pack.Items.Count; i++) + if (pack.Items[i] is PlagueBeastMainOrgan main && main.Complete) + main.FinishOpening(from); - return true; - } + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1071916); // * You patch up the wound with a bandage * - return false; - } + return true; + } - private void Hemorrhage() - { - if ( Patched ) - return; + return false; + } - Owner?.PlaySound( 0x25 ); + private void Hemorrhage() + { + if (Patched) + return; - if ( ItemID == 0x122A ) - { - if ( Owner != null ) - { - Owner.Unfreeze(); - Owner.Kill(); - } - } - else - { - if ( Starting ) - { - X += 8; - Y -= 10; - } + Owner?.PlaySound(0x25); - ItemID--; - } - } + if (ItemID == 0x122A) + { + if (Owner != null) + { + Owner.Unfreeze(); + Owner.Kill(); + } + } + else + { + if (Starting) + { + X += 8; + Y -= 10; + } - public PlagueBeastBlood( Serial serial ) : base( serial ) - { - } + ItemID--; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastGland.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastGland.cs index e25b5881b..39c84bee3 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastGland.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastGland.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class PlagueBeastGland : Item - { - public override string DefaultName => "a healthy gland"; + public class PlagueBeastGland : Item + { + [Constructible] + public PlagueBeastGland() : base(0x1CEF) + { + Weight = 1.0; + Hue = 0x6; + } - [Constructible] - public PlagueBeastGland() : base( 0x1CEF ) - { - Weight = 1.0; - Hue = 0x6; - } + public PlagueBeastGland(Serial serial) : base(serial) + { + } - public PlagueBeastGland( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a healthy gland"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastHeart.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastHeart.cs index 9395b5fac..859576914 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastHeart.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastHeart.cs @@ -2,78 +2,78 @@ using System; namespace Server.Items { - public class PlagueBeastHeart : PlagueBeastInnard - { - private Timer m_Timer; + public class PlagueBeastHeart : PlagueBeastInnard + { + private Timer m_Timer; - public PlagueBeastHeart() : base( 0x1363, 0x21 ) - { - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - } + public PlagueBeastHeart() : base(0x1363, 0x21) + { + m_Timer = new InternalTimer(this); + m_Timer.Start(); + } - public override void OnAfterDelete() - { - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); - } + public PlagueBeastHeart(Serial serial) : base(serial) + { + } - public PlagueBeastHeart( Serial serial ) : base( serial ) - { - } + public override void OnAfterDelete() + { + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - } + int version = reader.ReadEncodedInt(); - private class InternalTimer : Timer - { - private PlagueBeastHeart m_Heart; - private bool m_Delay; + m_Timer = new InternalTimer(this); + m_Timer.Start(); + } - public InternalTimer( PlagueBeastHeart heart ) : base( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 0.5 ) ) - { - m_Heart = heart; - } + private class InternalTimer : Timer + { + private bool m_Delay; + private PlagueBeastHeart m_Heart; - protected override void OnTick() - { - if ( m_Heart == null || m_Heart.Deleted || m_Heart.Owner == null || !m_Heart.Owner.Alive ) - { - Stop(); - return; - } + public InternalTimer(PlagueBeastHeart heart) : base(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(0.5)) + { + m_Heart = heart; + } - if ( m_Heart.ItemID == 0x1363 ) - { - if ( m_Delay ) - { - m_Heart.ItemID = 0x1367; - m_Heart.Owner.PlaySound( 0x11F ); - } + protected override void OnTick() + { + if (m_Heart == null || m_Heart.Deleted || m_Heart.Owner == null || !m_Heart.Owner.Alive) + { + Stop(); + return; + } - m_Delay = !m_Delay; - } - else - { - m_Heart.ItemID = 0x1363; - m_Heart.Owner.PlaySound( 0x120 ); - m_Delay = false; - } - } - } - } -} + if (m_Heart.ItemID == 0x1363) + { + if (m_Delay) + { + m_Heart.ItemID = 0x1367; + m_Heart.Owner.PlaySound(0x11F); + } + + m_Delay = !m_Delay; + } + else + { + m_Heart.ItemID = 0x1363; + m_Heart.Owner.PlaySound(0x120); + m_Delay = false; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastInnard.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastInnard.cs index 154033352..c5257dc84 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastInnard.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastInnard.cs @@ -3,170 +3,170 @@ using Server.Network; namespace Server.Items { - public class PlagueBeastInnard : Item, IScissorable, ICarvable - { - public PlagueBeastLord Owner => RootParent as PlagueBeastLord; - public override string DefaultName => "plague beast innards"; + public class PlagueBeastInnard : Item, IScissorable, ICarvable + { + public PlagueBeastInnard(int itemID, int hue) : base(itemID) + { + Hue = hue; + Movable = false; + Weight = 1.0; + } - public PlagueBeastInnard( int itemID, int hue ) : base( itemID ) - { - Hue = hue; - Movable = false; - Weight = 1.0; - } + public PlagueBeastInnard(Serial serial) : base(serial) + { + } - public virtual bool Scissor( Mobile from, Scissors scissors ) - { - return false; - } + public PlagueBeastLord Owner => RootParent as PlagueBeastLord; + public override string DefaultName => "plague beast innards"; - public virtual void Carve( Mobile from, Item with ) - { - } + public virtual void Carve(Mobile from, Item with) + { + } - public virtual bool OnBandage( Mobile from ) - { - return false; - } + public virtual bool Scissor(Mobile from, Scissors scissors) + { + return false; + } - public override bool IsAccessibleTo( Mobile check ) - { - if ( (int) check.AccessLevel >= (int) AccessLevel.GameMaster ) - return true; + public virtual bool OnBandage(Mobile from) + { + return false; + } - PlagueBeastLord owner = Owner; + public override bool IsAccessibleTo(Mobile check) + { + if ((int)check.AccessLevel >= (int)AccessLevel.GameMaster) + return true; - if ( owner == null ) - return false; + PlagueBeastLord owner = Owner; - if ( !owner.InRange( check, 2 ) ) - owner.PrivateOverheadMessage( MessageType.Label, 0x3B2, 500446, check.NetState ); // That is too far away. - else if ( owner.OpenedBy != null && owner.OpenedBy != check ) // TODO check - owner.PrivateOverheadMessage( MessageType.Label, 0x3B2, 500365, check.NetState ); // That is being used by someone else - else if ( owner.Frozen ) - return true; + if (owner == null) + return false; - return false; - } + if (!owner.InRange(check, 2)) + owner.PrivateOverheadMessage(MessageType.Label, 0x3B2, 500446, check.NetState); // That is too far away. + else if (owner.OpenedBy != null && owner.OpenedBy != check) // TODO check + owner.PrivateOverheadMessage(MessageType.Label, 0x3B2, 500365, + check.NetState); // That is being used by someone else + else if (owner.Frozen) + return true; - public PlagueBeastInnard( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - PlagueBeastLord owner = Owner; + PlagueBeastLord owner = Owner; - if ( owner == null || !owner.Alive ) - Delete(); - } - } + if (owner == null || !owner.Alive) + Delete(); + } + } - public class PlagueBeastComponent : PlagueBeastInnard - { - public PlagueBeastOrgan Organ { get; set; } + public class PlagueBeastComponent : PlagueBeastInnard + { + public PlagueBeastComponent(int itemID, int hue) : this(itemID, hue, false) + { + } - public bool IsBrain => ItemID == 0x1CF0; + public PlagueBeastComponent(int itemID, int hue, bool movable) : base(itemID, hue) + { + Movable = movable; + } - public bool IsGland => ItemID == 0x1CEF; + public PlagueBeastComponent(Serial serial) : base(serial) + { + } - public bool IsReceptacle => ItemID == 0x9DF; + public PlagueBeastOrgan Organ{ get; set; } - public PlagueBeastComponent( int itemID, int hue ) : this( itemID, hue, false ) - { - } + public bool IsBrain => ItemID == 0x1CF0; - public PlagueBeastComponent( int itemID, int hue, bool movable ) : base( itemID, hue ) - { - Movable = movable; - } + public bool IsGland => ItemID == 0x1CEF; - public override bool DropToItem( Mobile from, Item target, Point3D p ) - { - if ( target is PlagueBeastBackpack ) - return base.DropToItem( from, target, p ); + public bool IsReceptacle => ItemID == 0x9DF; - return false; - } + public override bool DropToItem(Mobile from, Item target, Point3D p) + { + if (target is PlagueBeastBackpack) + return base.DropToItem(from, target, p); - public override bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - return false; - } + return false; + } - public override bool DropToMobile( Mobile from, Mobile target, Point3D p ) - { - return false; - } + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + return false; + } - public override bool DropToWorld( Mobile from, Point3D p ) - { - return false; - } + public override bool DropToMobile(Mobile from, Mobile target, Point3D p) + { + return false; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( Organ != null && Organ.OnDropped( from, dropped, this ) ) - { - if ( dropped is PlagueBeastComponent component ) - Organ.Components.Add( component ); - } + public override bool DropToWorld(Mobile from, Point3D p) + { + return false; + } - return true; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (Organ != null && Organ.OnDropped(from, dropped, this)) + if (dropped is PlagueBeastComponent component) + Organ.Components.Add(component); - public override bool OnDragLift( Mobile from ) - { - if ( IsAccessibleTo( from ) ) - { - if ( Organ != null && Organ.OnLifted( from, this ) ) - { - from.SendLocalizedMessage( IsGland ? 1071895 : 1071914, null, 0x3B2 ); // * You rip the organ out of the plague beast's flesh * + return true; + } - if ( Organ.Components.Contains( this ) ) - Organ.Components.Remove( this ); + public override bool OnDragLift(Mobile from) + { + if (IsAccessibleTo(from)) + { + if (Organ != null && Organ.OnLifted(from, this)) + { + from.SendLocalizedMessage(IsGland ? 1071895 : 1071914, null, + 0x3B2); // * You rip the organ out of the plague beast's flesh * - Organ = null; - from.PlaySound( 0x1CA ); - } + if (Organ.Components.Contains(this)) + Organ.Components.Remove(this); - return true; - } + Organ = null; + from.PlaySound(0x1CA); + } - return false; - } + return true; + } - public PlagueBeastComponent( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.WriteItem( Organ ); - } + writer.WriteItem(Organ); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Organ = reader.ReadItem(); - } - } -} + Organ = reader.ReadItem(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastMutationCore.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastMutationCore.cs index 6df6021b4..1485d4aaa 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastMutationCore.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastMutationCore.cs @@ -4,68 +4,69 @@ using Server.Network; namespace Server.Items { - public class PlagueBeastMutationCore : Item, IScissorable - { - [CommandProperty( AccessLevel.GameMaster )] - public bool Cut { get; set; } + public class PlagueBeastMutationCore : Item, IScissorable + { + [Constructible] + public PlagueBeastMutationCore() : base(0x1CF0) + { + Cut = true; + Weight = 1.0; + Hue = 0x480; + } - public override string DefaultName => "a plague beast mutation core"; + public PlagueBeastMutationCore(Serial serial) : base(serial) + { + } - [Constructible] - public PlagueBeastMutationCore() : base( 0x1CF0 ) - { - Cut = true; - Weight = 1.0; - Hue = 0x480; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Cut{ get; set; } - public virtual bool Scissor( Mobile from, Scissors scissors ) - { - if ( !Cut ) - { - PlagueBeastLord owner = RootParent as PlagueBeastLord; + public override string DefaultName => "a plague beast mutation core"; - Cut = true; - Movable = true; + public virtual bool Scissor(Mobile from, Scissors scissors) + { + if (!Cut) + { + PlagueBeastLord owner = RootParent as PlagueBeastLord; - from.AddToBackpack( this ); - from.LocalOverheadMessage( MessageType.Regular, 0x34, 1071906 ); // * You remove the plague mutation core from the plague beast, causing it to dissolve into a pile of goo * + Cut = true; + Movable = true; - if ( owner != null ) - Timer.DelayCall( TimeSpan.FromSeconds( 1 ), KillParent, owner ); + from.AddToBackpack(this); + from.LocalOverheadMessage(MessageType.Regular, 0x34, + 1071906); // * You remove the plague mutation core from the plague beast, causing it to dissolve into a pile of goo * - return true; - } + if (owner != null) + Timer.DelayCall(TimeSpan.FromSeconds(1), KillParent, owner); - return false; - } + return true; + } - private void KillParent( PlagueBeastLord parent ) - { - parent.Unfreeze(); - parent.Kill(); - } + return false; + } - public PlagueBeastMutationCore( Serial serial ) : base( serial ) - { - } + private void KillParent(PlagueBeastLord parent) + { + parent.Unfreeze(); + parent.Kill(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) Cut ); - } + writer.Write(Cut); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Cut = reader.ReadBool(); - } - } -} + Cut = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastOrgans.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastOrgans.cs index 3b4f1bf5e..c084e53ed 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastOrgans.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastOrgans.cs @@ -4,557 +4,564 @@ using Server.Network; namespace Server.Items { - public class PlagueBeastOrgan : PlagueBeastInnard - { - public virtual bool IsCuttable => false; + public class PlagueBeastOrgan : PlagueBeastInnard + { + private Timer m_Timer; - public List Components { get; private set; } + public PlagueBeastOrgan() : this(1, 0) + { + Visible = false; + } - public int BrainHue { get; set; } + public PlagueBeastOrgan(int itemID, int hue) : base(itemID, hue) + { + Components = new List(); + Opened = false; - public bool Opened { get; set; } + Movable = false; - private Timer m_Timer; + Timer.DelayCall(TimeSpan.Zero, Initialize); + } - public PlagueBeastOrgan() : this( 1, 0 ) - { - Visible = false; - } + public PlagueBeastOrgan(Serial serial) : base(serial) + { + } - public PlagueBeastOrgan( int itemID, int hue ) : base( itemID, hue ) - { - Components = new List(); - Opened = false; + public virtual bool IsCuttable => false; + + public List Components{ get; private set; } - Movable = false; - - Timer.DelayCall( TimeSpan.Zero, Initialize ); - } + public int BrainHue{ get; set; } + + public bool Opened{ get; set; } - public virtual void Initialize() - { - } + public virtual void Initialize() + { + } - public void AddComponent( PlagueBeastComponent c, int x, int y ) - { - if ( Parent is Container pack ) - pack.DropItem( c ); + public void AddComponent(PlagueBeastComponent c, int x, int y) + { + if (Parent is Container pack) + pack.DropItem(c); - c.Organ = this; - c.Location = new Point3D( X + x, Y + y, Z ); - c.Map = Map; + c.Organ = this; + c.Location = new Point3D(X + x, Y + y, Z); + c.Map = Map; - Components.Add( c ); - } + Components.Add(c); + } - public override bool Scissor( Mobile from, Scissors scissors ) - { - if ( IsCuttable && IsAccessibleTo( from ) ) - { - if ( !Opened && m_Timer == null ) - { - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 3 ), FinishOpening, from ); - scissors.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071897 ); // You carefully cut into the organ. - return true; - } + public override bool Scissor(Mobile from, Scissors scissors) + { + if (IsCuttable && IsAccessibleTo(from)) + { + if (!Opened && m_Timer == null) + { + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(3), FinishOpening, from); + scissors.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1071897); // You carefully cut into the organ. + return true; + } - scissors.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071898 ); // You have already cut this organ open. - } + scissors.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1071898); // You have already cut this organ open. + } - return false; - } + return false; + } - public override void OnAfterDelete() - { - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); - } + public override void OnAfterDelete() + { + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); + } - public virtual bool OnLifted( Mobile from, PlagueBeastComponent c ) - { - return c.IsGland || c.IsBrain; - } + public virtual bool OnLifted(Mobile from, PlagueBeastComponent c) + { + return c.IsGland || c.IsBrain; + } - public virtual bool OnDropped( Mobile from, Item item, PlagueBeastComponent to ) - { - return false; - } + public virtual bool OnDropped(Mobile from, Item item, PlagueBeastComponent to) + { + return false; + } - public virtual void FinishOpening( Mobile from ) - { - Opened = true; - - Owner?.PlaySound( 0x50 ); - } + public virtual void FinishOpening(Mobile from) + { + Opened = true; + + Owner?.PlaySound(0x50); + } - public PlagueBeastOrgan( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.WriteEncodedInt(0); // version - writer.WriteEncodedInt( 0 ); // version + writer.WriteItemList(Components); + writer.Write(BrainHue); + writer.Write(Opened); + } - writer.WriteItemList( Components ); - writer.Write( (int) BrainHue ); - writer.Write( (bool) Opened ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadEncodedInt(); - int version = reader.ReadEncodedInt(); + Components = reader.ReadStrongItemList(); + BrainHue = reader.ReadInt(); + Opened = reader.ReadBool(); + } + } - Components = reader.ReadStrongItemList(); - BrainHue = reader.ReadInt(); - Opened = reader.ReadBool(); - } - } - - public class PlagueBeastMaidenOrgan : PlagueBeastOrgan - { - public PlagueBeastMaidenOrgan() : base( 0x124D, 0x0 ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !Opened ) - FinishOpening( from ); - } - - public override void FinishOpening( Mobile from ) - { - ItemID = 0x1249; - - Owner?.PlaySound( 0x187 ); - - AddComponent( new PlagueBeastComponent( 0x1D0D, 0x0 ), 22, 3 ); - AddComponent( new PlagueBeastComponent( 0x1D12, 0x0 ), 15, 18 ); - AddComponent( new PlagueBeastComponent( 0x1DA3, 0x21 ), 26, 46 ); - - if ( BrainHue > 0 ) - AddComponent( new PlagueBeastComponent( 0x1CF0, BrainHue, true ), 22, 29 ); - - Opened = true; - } - - public PlagueBeastMaidenOrgan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class PlagueBeastRockOrgan : PlagueBeastOrgan - { - public override bool IsCuttable => true; - - public PlagueBeastRockOrgan() : base( 0x177A, 0x60 ) - { - } - - public override void Carve( Mobile from, Item with ) - { - if ( IsAccessibleTo( from ) ) - with.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071896 ); // This is too crude an implement for such a procedure. - } - - public override bool OnLifted( Mobile from, PlagueBeastComponent c ) - { - base.OnLifted( from, c ); - - if ( c.IsBrain ) - { - AddComponent( new PlagueBeastBlood(), -7, 24 ); - return true; - } - - return false; - } - - public override void FinishOpening( Mobile from ) - { - base.FinishOpening( from ); - - AddComponent( new PlagueBeastComponent( 0x1775, 0x60 ), 3, 5 ); - AddComponent( new PlagueBeastComponent( 0x1777, 0x1 ), 10, 14 ); - - if ( BrainHue > 0 ) - AddComponent( new PlagueBeastComponent( 0x1CF0, BrainHue, true ), 1, 24 ); // 22, 29 - else - AddComponent( new PlagueBeastBlood(), -7, 24 ); - } - - public PlagueBeastRockOrgan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class PlagueBeastRubbleOrgan : PlagueBeastOrgan - { - private int m_Veins; - - public PlagueBeastRubbleOrgan() - { - m_Veins = 3; - } - - public override void Initialize() - { - Hue = Utility.RandomList( m_Hues ); - - AddComponent( new PlagueBeastComponent( 0x3BB, Hue ), 0, 0 ); - AddComponent( new PlagueBeastComponent( 0x3BA, Hue ), 4, 6 ); - AddComponent( new PlagueBeastComponent( 0x3BA, Hue ), -6, 17 ); - - int v = Utility.Random( 4 ); - - AddComponent( new PlagueBeastVein( 0x1B1B, v == 0 ? Hue : RandomHue( Hue ) ), -23, -3 ); - AddComponent( new PlagueBeastVein( 0x1B1C, v == 1 ? Hue : RandomHue( Hue ) ), 19, 4 ); - AddComponent( new PlagueBeastVein( 0x1B1B, v == 2 ? Hue : RandomHue( Hue ) ), 21, 27 ); - AddComponent( new PlagueBeastVein( 0x1B1B, v == 3 ? Hue : RandomHue( Hue ) ), 10, 40 ); - } - - public override bool OnLifted( Mobile from, PlagueBeastComponent c ) - { - if ( c.IsBrain ) - { - AddComponent( new PlagueBeastBlood(), -13, 25 ); - return true; - } - - return false; - } - - public override void FinishOpening( Mobile from ) - { - AddComponent( new PlagueBeastComponent( 0x1777, 0x1 ), 5, 14 ); - - if ( BrainHue > 0 ) - AddComponent( new PlagueBeastComponent( 0x1CF0, BrainHue, true ), -5, 22 ); - else - AddComponent( new PlagueBeastBlood(), -13, 25 ); - - Opened = true; - } - - private static int[] m_Hues = { - 0xD, 0x17, 0x2B, 0x42, 0x54, 0x5D - }; - - private static int RandomHue( int exculde ) - { - for ( int i = 0; i < 20; i++ ) - { - int hue = Utility.RandomList( m_Hues ); - - if ( hue != exculde ) - return hue; - } - - return 0xD; - } - - public virtual void OnVeinCut( Mobile from, PlagueBeastVein vein ) - { - if ( vein.Hue != Hue ) - { - if ( !Opened && m_Veins > 0 && --m_Veins == 0 ) - FinishOpening( from ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1071901 ); // * As you cut the vein, a cloud of poison is expelled from the plague beast's organ, and the plague beast dissolves into a puddle of goo * - from.ApplyPoison( from, Poison.Greater ); - from.PlaySound( 0x22F ); - - if ( Owner != null ) - { - Owner.Unfreeze(); - Owner.Kill(); - } - } - } - - public PlagueBeastRubbleOrgan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (int) m_Veins ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Veins = reader.ReadInt(); - } - } - - public class PlagueBeastBackupOrgan : PlagueBeastOrgan - { - public override bool IsCuttable => true; - - private Timer m_Timer; - private Item m_Gland; - - public PlagueBeastBackupOrgan() : base( 0x1362, 0x6 ) - { - } - - public override void Initialize() - { - AddComponent( new PlagueBeastComponent( 0x1B1B, 0x42 ), 16, 39 ); - AddComponent( new PlagueBeastComponent( 0x1B1B, 0x42 ), 39, 49 ); - AddComponent( new PlagueBeastComponent( 0x1B1B, 0x42 ), 39, 48 ); - AddComponent( new PlagueBeastComponent( 0x1B1B, 0x42 ), 44, 42 ); - AddComponent( new PlagueBeastComponent( 0x1CF2, 0x42 ), 20, 34 ); - AddComponent( new PlagueBeastComponent( 0x135F, 0x42 ), 47, 58 ); - AddComponent( new PlagueBeastComponent( 0x1360, 0x42 ), 70, 68 ); - } - - public override void Carve( Mobile from, Item with ) - { - if ( IsAccessibleTo( from ) ) - with.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071896 ); // This is too crude an implement for such a procedure. - } - - public override bool OnLifted( Mobile from, PlagueBeastComponent c ) - { - if ( c.IsBrain ) - { - AddComponent( new PlagueBeastBlood(), 47, 72 ); - return true; - } - - if ( c.IsGland ) - { - m_Gland = null; - return true; - } - - return c.IsGland; - } - - public override bool OnDropped( Mobile from, Item item, PlagueBeastComponent to ) - { - if ( to.Hue == 0x1 && m_Gland == null && item is PlagueBeastGland ) - { - m_Gland = item; - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 3 ), FinishHealing ); - from.SendAsciiMessage( 0x3B2, "* You place the healthy gland inside the organ sac *" ); - item.Movable = false; - - Owner?.PlaySound( 0x20 ); - - return true; - } - - return false; - } - - public override void FinishOpening( Mobile from ) - { - base.FinishOpening( from ); - - AddComponent( new PlagueBeastComponent( 0x1363, 0xF ), -3, 3 ); - AddComponent( new PlagueBeastComponent( 0x1365, 0x1 ), -3, 10 ); - - m_Gland = new PlagueBeastComponent( 0x1CEF, 0x3F, true ); - AddComponent( (PlagueBeastComponent) m_Gland, -4, 16 ); - } - - public void FinishHealing() - { - for ( int i = 0; i < 7 && i < Components.Count; i++ ) - Components[ i ].Hue = 0x6; - - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 2 ), OpenOrgan ); - } - - public void OpenOrgan() - { - AddComponent( new PlagueBeastComponent( 0x1367, 0xF ), 55, 61 ); - AddComponent( new PlagueBeastComponent( 0x1366, 0x1 ), 57, 66 ); - - if ( BrainHue > 0 ) - AddComponent( new PlagueBeastComponent( 0x1CF0, BrainHue, true ), 55, 69 ); - } - - public PlagueBeastBackupOrgan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (Item) m_Gland ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Gland = reader.ReadItem(); - } - } - - public class PlagueBeastMainOrgan : PlagueBeastOrgan - { - private int m_Brains; - - public bool Complete => m_Brains >= 4; - - public PlagueBeastMainOrgan() - { - m_Brains = 0; - } - - public override void Initialize() - { - // receptacles - AddComponent( new PlagueBeastComponent( 0x1B1B, 0x42 ), -36, -2 ); - AddComponent( new PlagueBeastComponent( 0x1FB3, 0x42 ), -42, 0 ); - AddComponent( new PlagueBeastComponent( 0x9DF, 0x42 ), -53, -7 ); - - AddComponent( new PlagueBeastComponent( 0x1B1C, 0x54 ), 29, 9 ); - AddComponent( new PlagueBeastComponent( 0x1D06, 0x54 ), 18, -2 ); - AddComponent( new PlagueBeastComponent( 0x9DF, 0x54 ), 36, -1 ); - - AddComponent( new PlagueBeastComponent( 0x1D10, 0x2B ), -36, 47 ); - AddComponent( new PlagueBeastComponent( 0x1B1C, 0x2B ), -24, 62 ); - AddComponent( new PlagueBeastComponent( 0x9DF, 0x2B ), -41, 74 ); - - AddComponent( new PlagueBeastComponent( 0x1B1B, 0x60 ), 39, 56 ); - AddComponent( new PlagueBeastComponent( 0x1FB4, 0x60 ), 34, 52 ); - AddComponent( new PlagueBeastComponent( 0x9DF, 0x60 ), 45, 71 ); - - // main part - AddComponent( new PlagueBeastComponent( 0x1351, 0x15 ), 23, 0 ); - AddComponent( new PlagueBeastComponent( 0x134F, 0x15 ), -22, 0 ); - AddComponent( new PlagueBeastComponent( 0x1350, 0x15 ), 0, 0 ); - } - - public override bool OnLifted( Mobile from, PlagueBeastComponent c ) - { - if ( c.IsBrain ) - m_Brains--; + public class PlagueBeastMaidenOrgan : PlagueBeastOrgan + { + public PlagueBeastMaidenOrgan() : base(0x124D, 0x0) + { + } - return true; - } - - public override bool OnDropped( Mobile from, Item item, PlagueBeastComponent to ) - { - if ( !Opened && to.IsReceptacle && item.Hue == to.Hue ) - { - to.Organ = this; - m_Brains++; - from.LocalOverheadMessage( MessageType.Regular, 0x34, 1071913 ); // You place the organ in the fleshy receptacle near the core. - - if ( Owner != null ) - { - Owner.PlaySound( 0x1BA ); - - if ( Owner.IsBleeding ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x34, 1071922 ); // The plague beast is still bleeding from open wounds. You must seal any bleeding wounds before the core will open! - return true; - } - } - - if ( m_Brains == 4 ) - FinishOpening( from ); - - return true; - } - - return false; - } - - public override void FinishOpening( Mobile from ) - { - AddComponent( new PlagueBeastComponent( 0x1363, 0x1 ), 0, 22 ); - AddComponent( new PlagueBeastComponent( 0x1D04, 0xD ), 0, 22 ); - - if ( Owner?.Backpack != null ) - { - PlagueBeastMutationCore core = new PlagueBeastMutationCore(); - Owner.Backpack.AddItem( core ); - core.Movable = false; - core.Cut = false; - core.X = X; - core.Y = Y + 34; - - Owner.PlaySound( 0x21 ); - Owner.PlaySound( 0x166 ); - } - - Opened = true; - } - - public PlagueBeastMainOrgan( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (int) m_Brains ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Brains = reader.ReadInt(); - } - } -} + public PlagueBeastMaidenOrgan(Serial serial) : base(serial) + { + } + + public override void OnDoubleClick(Mobile from) + { + if (!Opened) + FinishOpening(from); + } + + public override void FinishOpening(Mobile from) + { + ItemID = 0x1249; + + Owner?.PlaySound(0x187); + + AddComponent(new PlagueBeastComponent(0x1D0D, 0x0), 22, 3); + AddComponent(new PlagueBeastComponent(0x1D12, 0x0), 15, 18); + AddComponent(new PlagueBeastComponent(0x1DA3, 0x21), 26, 46); + + if (BrainHue > 0) + AddComponent(new PlagueBeastComponent(0x1CF0, BrainHue, true), 22, 29); + + Opened = true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class PlagueBeastRockOrgan : PlagueBeastOrgan + { + public PlagueBeastRockOrgan() : base(0x177A, 0x60) + { + } + + public PlagueBeastRockOrgan(Serial serial) : base(serial) + { + } + + public override bool IsCuttable => true; + + public override void Carve(Mobile from, Item with) + { + if (IsAccessibleTo(from)) + with.PublicOverheadMessage(MessageType.Regular, 0x3B2, + 1071896); // This is too crude an implement for such a procedure. + } + + public override bool OnLifted(Mobile from, PlagueBeastComponent c) + { + base.OnLifted(from, c); + + if (c.IsBrain) + { + AddComponent(new PlagueBeastBlood(), -7, 24); + return true; + } + + return false; + } + + public override void FinishOpening(Mobile from) + { + base.FinishOpening(from); + + AddComponent(new PlagueBeastComponent(0x1775, 0x60), 3, 5); + AddComponent(new PlagueBeastComponent(0x1777, 0x1), 10, 14); + + if (BrainHue > 0) + AddComponent(new PlagueBeastComponent(0x1CF0, BrainHue, true), 1, 24); // 22, 29 + else + AddComponent(new PlagueBeastBlood(), -7, 24); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class PlagueBeastRubbleOrgan : PlagueBeastOrgan + { + private static int[] m_Hues = + { + 0xD, 0x17, 0x2B, 0x42, 0x54, 0x5D + }; + + private int m_Veins; + + public PlagueBeastRubbleOrgan() + { + m_Veins = 3; + } + + public PlagueBeastRubbleOrgan(Serial serial) : base(serial) + { + } + + public override void Initialize() + { + Hue = Utility.RandomList(m_Hues); + + AddComponent(new PlagueBeastComponent(0x3BB, Hue), 0, 0); + AddComponent(new PlagueBeastComponent(0x3BA, Hue), 4, 6); + AddComponent(new PlagueBeastComponent(0x3BA, Hue), -6, 17); + + int v = Utility.Random(4); + + AddComponent(new PlagueBeastVein(0x1B1B, v == 0 ? Hue : RandomHue(Hue)), -23, -3); + AddComponent(new PlagueBeastVein(0x1B1C, v == 1 ? Hue : RandomHue(Hue)), 19, 4); + AddComponent(new PlagueBeastVein(0x1B1B, v == 2 ? Hue : RandomHue(Hue)), 21, 27); + AddComponent(new PlagueBeastVein(0x1B1B, v == 3 ? Hue : RandomHue(Hue)), 10, 40); + } + + public override bool OnLifted(Mobile from, PlagueBeastComponent c) + { + if (c.IsBrain) + { + AddComponent(new PlagueBeastBlood(), -13, 25); + return true; + } + + return false; + } + + public override void FinishOpening(Mobile from) + { + AddComponent(new PlagueBeastComponent(0x1777, 0x1), 5, 14); + + if (BrainHue > 0) + AddComponent(new PlagueBeastComponent(0x1CF0, BrainHue, true), -5, 22); + else + AddComponent(new PlagueBeastBlood(), -13, 25); + + Opened = true; + } + + private static int RandomHue(int exculde) + { + for (int i = 0; i < 20; i++) + { + int hue = Utility.RandomList(m_Hues); + + if (hue != exculde) + return hue; + } + + return 0xD; + } + + public virtual void OnVeinCut(Mobile from, PlagueBeastVein vein) + { + if (vein.Hue != Hue) + { + if (!Opened && m_Veins > 0 && --m_Veins == 0) + FinishOpening(from); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1071901); // * As you cut the vein, a cloud of poison is expelled from the plague beast's organ, and the plague beast dissolves into a puddle of goo * + from.ApplyPoison(from, Poison.Greater); + from.PlaySound(0x22F); + + if (Owner != null) + { + Owner.Unfreeze(); + Owner.Kill(); + } + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_Veins); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Veins = reader.ReadInt(); + } + } + + public class PlagueBeastBackupOrgan : PlagueBeastOrgan + { + private Item m_Gland; + + private Timer m_Timer; + + public PlagueBeastBackupOrgan() : base(0x1362, 0x6) + { + } + + public PlagueBeastBackupOrgan(Serial serial) : base(serial) + { + } + + public override bool IsCuttable => true; + + public override void Initialize() + { + AddComponent(new PlagueBeastComponent(0x1B1B, 0x42), 16, 39); + AddComponent(new PlagueBeastComponent(0x1B1B, 0x42), 39, 49); + AddComponent(new PlagueBeastComponent(0x1B1B, 0x42), 39, 48); + AddComponent(new PlagueBeastComponent(0x1B1B, 0x42), 44, 42); + AddComponent(new PlagueBeastComponent(0x1CF2, 0x42), 20, 34); + AddComponent(new PlagueBeastComponent(0x135F, 0x42), 47, 58); + AddComponent(new PlagueBeastComponent(0x1360, 0x42), 70, 68); + } + + public override void Carve(Mobile from, Item with) + { + if (IsAccessibleTo(from)) + with.PublicOverheadMessage(MessageType.Regular, 0x3B2, + 1071896); // This is too crude an implement for such a procedure. + } + + public override bool OnLifted(Mobile from, PlagueBeastComponent c) + { + if (c.IsBrain) + { + AddComponent(new PlagueBeastBlood(), 47, 72); + return true; + } + + if (c.IsGland) + { + m_Gland = null; + return true; + } + + return c.IsGland; + } + + public override bool OnDropped(Mobile from, Item item, PlagueBeastComponent to) + { + if (to.Hue == 0x1 && m_Gland == null && item is PlagueBeastGland) + { + m_Gland = item; + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(3), FinishHealing); + from.SendAsciiMessage(0x3B2, "* You place the healthy gland inside the organ sac *"); + item.Movable = false; + + Owner?.PlaySound(0x20); + + return true; + } + + return false; + } + + public override void FinishOpening(Mobile from) + { + base.FinishOpening(from); + + AddComponent(new PlagueBeastComponent(0x1363, 0xF), -3, 3); + AddComponent(new PlagueBeastComponent(0x1365, 0x1), -3, 10); + + m_Gland = new PlagueBeastComponent(0x1CEF, 0x3F, true); + AddComponent((PlagueBeastComponent)m_Gland, -4, 16); + } + + public void FinishHealing() + { + for (int i = 0; i < 7 && i < Components.Count; i++) + Components[i].Hue = 0x6; + + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(2), OpenOrgan); + } + + public void OpenOrgan() + { + AddComponent(new PlagueBeastComponent(0x1367, 0xF), 55, 61); + AddComponent(new PlagueBeastComponent(0x1366, 0x1), 57, 66); + + if (BrainHue > 0) + AddComponent(new PlagueBeastComponent(0x1CF0, BrainHue, true), 55, 69); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_Gland); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Gland = reader.ReadItem(); + } + } + + public class PlagueBeastMainOrgan : PlagueBeastOrgan + { + private int m_Brains; + + public PlagueBeastMainOrgan() + { + m_Brains = 0; + } + + public PlagueBeastMainOrgan(Serial serial) : base(serial) + { + } + + public bool Complete => m_Brains >= 4; + + public override void Initialize() + { + // receptacles + AddComponent(new PlagueBeastComponent(0x1B1B, 0x42), -36, -2); + AddComponent(new PlagueBeastComponent(0x1FB3, 0x42), -42, 0); + AddComponent(new PlagueBeastComponent(0x9DF, 0x42), -53, -7); + + AddComponent(new PlagueBeastComponent(0x1B1C, 0x54), 29, 9); + AddComponent(new PlagueBeastComponent(0x1D06, 0x54), 18, -2); + AddComponent(new PlagueBeastComponent(0x9DF, 0x54), 36, -1); + + AddComponent(new PlagueBeastComponent(0x1D10, 0x2B), -36, 47); + AddComponent(new PlagueBeastComponent(0x1B1C, 0x2B), -24, 62); + AddComponent(new PlagueBeastComponent(0x9DF, 0x2B), -41, 74); + + AddComponent(new PlagueBeastComponent(0x1B1B, 0x60), 39, 56); + AddComponent(new PlagueBeastComponent(0x1FB4, 0x60), 34, 52); + AddComponent(new PlagueBeastComponent(0x9DF, 0x60), 45, 71); + + // main part + AddComponent(new PlagueBeastComponent(0x1351, 0x15), 23, 0); + AddComponent(new PlagueBeastComponent(0x134F, 0x15), -22, 0); + AddComponent(new PlagueBeastComponent(0x1350, 0x15), 0, 0); + } + + public override bool OnLifted(Mobile from, PlagueBeastComponent c) + { + if (c.IsBrain) + m_Brains--; + + return true; + } + + public override bool OnDropped(Mobile from, Item item, PlagueBeastComponent to) + { + if (!Opened && to.IsReceptacle && item.Hue == to.Hue) + { + to.Organ = this; + m_Brains++; + from.LocalOverheadMessage(MessageType.Regular, 0x34, + 1071913); // You place the organ in the fleshy receptacle near the core. + + if (Owner != null) + { + Owner.PlaySound(0x1BA); + + if (Owner.IsBleeding) + { + from.LocalOverheadMessage(MessageType.Regular, 0x34, + 1071922); // The plague beast is still bleeding from open wounds. You must seal any bleeding wounds before the core will open! + return true; + } + } + + if (m_Brains == 4) + FinishOpening(from); + + return true; + } + + return false; + } + + public override void FinishOpening(Mobile from) + { + AddComponent(new PlagueBeastComponent(0x1363, 0x1), 0, 22); + AddComponent(new PlagueBeastComponent(0x1D04, 0xD), 0, 22); + + if (Owner?.Backpack != null) + { + PlagueBeastMutationCore core = new PlagueBeastMutationCore(); + Owner.Backpack.AddItem(core); + core.Movable = false; + core.Cut = false; + core.X = X; + core.Y = Y + 34; + + Owner.PlaySound(0x21); + Owner.PlaySound(0x166); + } + + Opened = true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_Brains); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Brains = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Mutation Core/PlagueBeastVein.cs b/Scripts/Items/Special/Mutation Core/PlagueBeastVein.cs index 0e8bdcbf3..cbce08871 100644 --- a/Scripts/Items/Special/Mutation Core/PlagueBeastVein.cs +++ b/Scripts/Items/Special/Mutation Core/PlagueBeastVein.cs @@ -3,75 +3,76 @@ using Server.Network; namespace Server.Items { - public class PlagueBeastVein : PlagueBeastComponent - { - public bool Cut { get; private set; } + public class PlagueBeastVein : PlagueBeastComponent + { + private Timer m_Timer; - private Timer m_Timer; + public PlagueBeastVein(int itemID, int hue) : base(itemID, hue) + { + Cut = false; + } - public PlagueBeastVein( int itemID, int hue ) : base( itemID, hue ) - { - Cut = false; - } + public PlagueBeastVein(Serial serial) : base(serial) + { + } - public override bool Scissor( Mobile from, Scissors scissors ) - { - if ( IsAccessibleTo( from ) ) - { - if ( !Cut && m_Timer == null ) - { - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 3 ), CuttingDone, from ); - scissors.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071899 ); // You begin cutting through the vein. - return true; - } + public bool Cut{ get; private set; } - scissors.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071900 ); // // This vein has already been cut. - } + public override bool Scissor(Mobile from, Scissors scissors) + { + if (IsAccessibleTo(from)) + { + if (!Cut && m_Timer == null) + { + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(3), CuttingDone, from); + scissors.PublicOverheadMessage(MessageType.Regular, 0x3B2, + 1071899); // You begin cutting through the vein. + return true; + } - return false; - } + scissors.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1071900); // // This vein has already been cut. + } - public override void OnAfterDelete() - { - if ( m_Timer != null && m_Timer.Running ) - m_Timer.Stop(); - } + return false; + } - private void CuttingDone( Mobile from ) - { - Cut = true; + public override void OnAfterDelete() + { + if (m_Timer != null && m_Timer.Running) + m_Timer.Stop(); + } - if ( ItemID == 0x1B1C ) - ItemID = 0x1B1B; - else - ItemID = 0x1B1C; + private void CuttingDone(Mobile from) + { + Cut = true; - Owner?.PlaySound( 0x199 ); + if (ItemID == 0x1B1C) + ItemID = 0x1B1B; + else + ItemID = 0x1B1C; - if ( Organ is PlagueBeastRubbleOrgan organ ) - organ.OnVeinCut( from, this ); - } + Owner?.PlaySound(0x199); - public PlagueBeastVein( Serial serial ) : base( serial ) - { - } + if (Organ is PlagueBeastRubbleOrgan organ) + organ.OnVeinCut(from, this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) Cut ); - } + writer.Write(Cut); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - Cut = reader.ReadBool(); - } - } -} + Cut = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Containers/BaseWaterContainer.cs b/Scripts/Items/Special/Rares/Containers/BaseWaterContainer.cs index 21fc7d71c..b268d118f 100644 --- a/Scripts/Items/Special/Rares/Containers/BaseWaterContainer.cs +++ b/Scripts/Items/Special/Rares/Containers/BaseWaterContainer.cs @@ -1,129 +1,120 @@ namespace Server.Items { - public abstract class BaseWaterContainer : Container, IHasQuantity - { - public abstract int voidItem_ID { get; } - public abstract int fullItem_ID { get; } - public abstract int MaxQuantity { get; } + public abstract class BaseWaterContainer : Container, IHasQuantity + { + private int m_Quantity; - public override int DefaultGumpID => 0x3e; + public BaseWaterContainer(int Item_Id, bool filled) + : base(Item_Id) + { + m_Quantity = filled ? MaxQuantity : 0; + } - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool IsEmpty => ( m_Quantity <= 0 ); + public BaseWaterContainer(Serial serial) + : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool IsFull => ( m_Quantity >= MaxQuantity ); + public abstract int voidItem_ID{ get; } + public abstract int fullItem_ID{ get; } + public abstract int MaxQuantity{ get; } - [CommandProperty( AccessLevel.GameMaster )] - public virtual int Quantity - { - get => m_Quantity; - set - { - if ( value != m_Quantity ) - { - m_Quantity = ( value < 1 ) ? 0 : ( value > MaxQuantity ) ? MaxQuantity : value; + public override int DefaultGumpID => 0x3e; - Movable = ( !IsLockedDown ) ? IsEmpty : false; + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool IsEmpty => m_Quantity <= 0; - ItemID = ( IsEmpty ) ? voidItem_ID : fullItem_ID; + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool IsFull => m_Quantity >= MaxQuantity; - if ( !IsEmpty ) - { - IEntity rootParent = RootParent; + [CommandProperty(AccessLevel.GameMaster)] + public virtual int Quantity + { + get => m_Quantity; + set + { + if (value != m_Quantity) + { + m_Quantity = value < 1 ? 0 : value > MaxQuantity ? MaxQuantity : value; - if ( rootParent?.Map != null && rootParent.Map != Map.Internal ) - MoveToWorld( rootParent.Location, rootParent.Map ); - } + Movable = !IsLockedDown ? IsEmpty : false; - InvalidateProperties(); - } - } - } + ItemID = IsEmpty ? voidItem_ID : fullItem_ID; - private int m_Quantity; + if (!IsEmpty) + { + IEntity rootParent = RootParent; - public BaseWaterContainer( int Item_Id, bool filled ) - : base( Item_Id ) - { - m_Quantity = ( filled ) ? MaxQuantity : 0; - } + if (rootParent?.Map != null && rootParent.Map != Map.Internal) + MoveToWorld(rootParent.Location, rootParent.Map); + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsEmpty ) - { - base.OnDoubleClick( from ); - } - } + InvalidateProperties(); + } + } + } - public override void OnSingleClick( Mobile from ) - { - if ( IsEmpty ) - { - base.OnSingleClick( from ); - } - else - { - if ( Name == null ) - LabelTo( from, LabelNumber ); - else - LabelTo( from, Name ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (IsEmpty) base.OnDoubleClick(from); + } - public override void OnAosSingleClick( Mobile from ) - { - if ( IsEmpty ) - { - base.OnAosSingleClick( from ); - } - else - { - if ( Name == null ) - LabelTo( from, LabelNumber ); - else - LabelTo( from, Name ); - } - } + public override void OnSingleClick(Mobile from) + { + if (IsEmpty) + { + base.OnSingleClick(from); + } + else + { + if (Name == null) + LabelTo(from, LabelNumber); + else + LabelTo(from, Name); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - if ( IsEmpty ) - { - base.GetProperties( list ); - } - } + public override void OnAosSingleClick(Mobile from) + { + if (IsEmpty) + { + base.OnAosSingleClick(from); + } + else + { + if (Name == null) + LabelTo(from, LabelNumber); + else + LabelTo(from, Name); + } + } - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( !IsEmpty ) - { - return false; - } + public override void GetProperties(ObjectPropertyList list) + { + if (IsEmpty) base.GetProperties(list); + } - return base.OnDragDropInto( from, item, p ); - } + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (!IsEmpty) return false; - public BaseWaterContainer( Serial serial ) - : base( serial ) - { - } + return base.OnDragDropInto(from, item, p); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - writer.Write( (int)m_Quantity ); - } + writer.Write(0); // version + writer.Write(m_Quantity); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - m_Quantity = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + m_Quantity = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Containers/Bucket.cs b/Scripts/Items/Special/Rares/Containers/Bucket.cs index 13cc48d5b..30ed5a87b 100644 --- a/Scripts/Items/Special/Rares/Containers/Bucket.cs +++ b/Scripts/Items/Special/Rares/Containers/Bucket.cs @@ -1,43 +1,43 @@ namespace Server.Items { - class Bucket : BaseWaterContainer - { - public override int voidItem_ID => vItemID; - public override int fullItem_ID => fItemID; - public override int MaxQuantity => 25; + internal class Bucket : BaseWaterContainer + { + private static int vItemID = 0x14e0; + private static int fItemID = 0x2004; - private static int vItemID = 0x14e0; - private static int fItemID = 0x2004; + [Constructible] + public Bucket() + : this(false) + { + } - [Constructible] - public Bucket() - : this( false ) - { - } + [Constructible] + public Bucket(bool filled) + : base(filled ? fItemID : vItemID, filled) + { + } - [Constructible] - public Bucket( bool filled ) - : base( ( filled ) ? fItemID : vItemID, filled ) - { - } + public Bucket(Serial serial) + : base(serial) + { + } - public Bucket( Serial serial ) - : base( serial ) - { - } + public override int voidItem_ID => vItemID; + public override int fullItem_ID => fItemID; + public override int MaxQuantity => 25; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Containers/ClosedBarrel.cs b/Scripts/Items/Special/Rares/Containers/ClosedBarrel.cs index eba8dadc0..19a49f18a 100644 --- a/Scripts/Items/Special/Rares/Containers/ClosedBarrel.cs +++ b/Scripts/Items/Special/Rares/Containers/ClosedBarrel.cs @@ -1,32 +1,32 @@ namespace Server.Items { - class ClosedBarrel : TrappableContainer - { - public override int DefaultGumpID => 0x3e; + internal class ClosedBarrel : TrappableContainer + { + [Constructible] + public ClosedBarrel() + : base(0x0FAE) + { + } - [Constructible] - public ClosedBarrel() - : base( 0x0FAE ) - { - } + public ClosedBarrel(Serial serial) + : base(serial) + { + } - public ClosedBarrel( Serial serial ) - : base( serial ) - { - } + public override int DefaultGumpID => 0x3e; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Containers/UnfinishedBarrel.cs b/Scripts/Items/Special/Rares/Containers/UnfinishedBarrel.cs index e92067d97..654abfb02 100644 --- a/Scripts/Items/Special/Rares/Containers/UnfinishedBarrel.cs +++ b/Scripts/Items/Special/Rares/Containers/UnfinishedBarrel.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class UnfinishedBarrel : Item - { + public class UnfinishedBarrel : Item + { + [Constructible] + public UnfinishedBarrel() : base(0x1EB5) + { + Movable = true; + Stackable = false; + } - [Constructible] - public UnfinishedBarrel() : base( 0x1EB5 ) - { - Movable = true; - Stackable = false; - } + public UnfinishedBarrel(Serial serial) : base(serial) + { + } - public UnfinishedBarrel( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Containers/WaterBarrel.cs b/Scripts/Items/Special/Rares/Containers/WaterBarrel.cs index 20edd8d0b..1a8a63e8a 100644 --- a/Scripts/Items/Special/Rares/Containers/WaterBarrel.cs +++ b/Scripts/Items/Special/Rares/Containers/WaterBarrel.cs @@ -1,45 +1,45 @@ namespace Server.Items { - class WaterBarrel : BaseWaterContainer - { - public override int LabelNumber => 1025453; /* water barrel */ + internal class WaterBarrel : BaseWaterContainer + { + private static int vItemID = 0xe77; + private static int fItemID = 0x154d; - public override int voidItem_ID => vItemID; - public override int fullItem_ID => fItemID; - public override int MaxQuantity => 100; + [Constructible] + public WaterBarrel() + : this(false) + { + } - private static int vItemID = 0xe77; - private static int fItemID = 0x154d; + [Constructible] + public WaterBarrel(bool filled) + : base(filled ? fItemID : vItemID, filled) + { + } - [Constructible] - public WaterBarrel() - : this( false ) - { - } + public WaterBarrel(Serial serial) + : base(serial) + { + } - [Constructible] - public WaterBarrel( bool filled ) - : base( ( filled ) ? fItemID : vItemID, filled ) - { - } + public override int LabelNumber => 1025453; /* water barrel */ - public WaterBarrel( Serial serial ) - : base( serial ) - { - } + public override int voidItem_ID => vItemID; + public override int fullItem_ID => fItemID; + public override int MaxQuantity => 100; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Containers/WaterTub.cs b/Scripts/Items/Special/Rares/Containers/WaterTub.cs index 46cc881f0..a53f7770b 100644 --- a/Scripts/Items/Special/Rares/Containers/WaterTub.cs +++ b/Scripts/Items/Special/Rares/Containers/WaterTub.cs @@ -1,43 +1,43 @@ namespace Server.Items { - class Tub : BaseWaterContainer - { - public override int voidItem_ID => vItemID; - public override int fullItem_ID => fItemID; - public override int MaxQuantity => 50; + internal class Tub : BaseWaterContainer + { + private static int vItemID = 0xe83; + private static int fItemID = 0xe7b; - private static int vItemID = 0xe83; - private static int fItemID = 0xe7b; + [Constructible] + public Tub() + : this(false) + { + } - [Constructible] - public Tub() - : this( false ) - { - } + [Constructible] + public Tub(bool filled) + : base(filled ? fItemID : vItemID, filled) + { + } - [Constructible] - public Tub( bool filled ) - : base( ( filled ) ? fItemID : vItemID, filled ) - { - } + public Tub(Serial serial) + : base(serial) + { + } - public Tub( Serial serial ) - : base( serial ) - { - } + public override int voidItem_ID => vItemID; + public override int fullItem_ID => fItemID; + public override int MaxQuantity => 50; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Daily/DecoRock.cs b/Scripts/Items/Special/Rares/Daily/DecoRock.cs index f7e58a0a9..c58029cf7 100644 --- a/Scripts/Items/Special/Rares/Daily/DecoRock.cs +++ b/Scripts/Items/Special/Rares/Daily/DecoRock.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRock : Item - { + public class DecoRock : Item + { + [Constructible] + public DecoRock() : base(0x1778) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRock() : base( 0x1778 ) - { - Movable = true; - Stackable = false; - } + public DecoRock(Serial serial) : base(serial) + { + } - public DecoRock( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Daily/DecoRock2.cs b/Scripts/Items/Special/Rares/Daily/DecoRock2.cs index bab49c8f9..dfb0306e8 100644 --- a/Scripts/Items/Special/Rares/Daily/DecoRock2.cs +++ b/Scripts/Items/Special/Rares/Daily/DecoRock2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRock2 : Item - { + public class DecoRock2 : Item + { + [Constructible] + public DecoRock2() : base(0x1363) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRock2() : base( 0x1363 ) - { - Movable = true; - Stackable = false; - } + public DecoRock2(Serial serial) : base(serial) + { + } - public DecoRock2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Daily/DecoRocks.cs b/Scripts/Items/Special/Rares/Daily/DecoRocks.cs index e3933fa42..129400167 100644 --- a/Scripts/Items/Special/Rares/Daily/DecoRocks.cs +++ b/Scripts/Items/Special/Rares/Daily/DecoRocks.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRocks : Item - { + public class DecoRocks : Item + { + [Constructible] + public DecoRocks() : base(0x1367) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRocks() : base( 0x1367 ) - { - Movable = true; - Stackable = false; - } + public DecoRocks(Serial serial) : base(serial) + { + } - public DecoRocks( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Daily/DecoRocks2.cs b/Scripts/Items/Special/Rares/Daily/DecoRocks2.cs index b849153b4..d04ac875f 100644 --- a/Scripts/Items/Special/Rares/Daily/DecoRocks2.cs +++ b/Scripts/Items/Special/Rares/Daily/DecoRocks2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRocks2 : Item - { + public class DecoRocks2 : Item + { + [Constructible] + public DecoRocks2() : base(0x136D) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRocks2() : base( 0x136D ) - { - Movable = true; - Stackable = false; - } + public DecoRocks2(Serial serial) : base(serial) + { + } - public DecoRocks2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Flowers/DecoFlower.cs b/Scripts/Items/Special/Rares/Flowers/DecoFlower.cs index c83d8cadf..4eb4660ee 100644 --- a/Scripts/Items/Special/Rares/Flowers/DecoFlower.cs +++ b/Scripts/Items/Special/Rares/Flowers/DecoFlower.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoFlower : Item - { + public class DecoFlower : Item + { + [Constructible] + public DecoFlower() : base(0x18DA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoFlower() : base( 0x18DA ) - { - Movable = true; - Stackable = false; - } + public DecoFlower(Serial serial) : base(serial) + { + } - public DecoFlower( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Flowers/DecoFlower2.cs b/Scripts/Items/Special/Rares/Flowers/DecoFlower2.cs index af927c05d..b7e54b626 100644 --- a/Scripts/Items/Special/Rares/Flowers/DecoFlower2.cs +++ b/Scripts/Items/Special/Rares/Flowers/DecoFlower2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoFlower2 : Item - { + public class DecoFlower2 : Item + { + [Constructible] + public DecoFlower2() : base(0x18D9) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoFlower2() : base( 0x18D9 ) - { - Movable = true; - Stackable = false; - } + public DecoFlower2(Serial serial) : base(serial) + { + } - public DecoFlower2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic.cs b/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic.cs index 9528a363e..8740044da 100644 --- a/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic.cs +++ b/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRoseOfTrinsic : Item - { + public class DecoRoseOfTrinsic : Item + { + [Constructible] + public DecoRoseOfTrinsic() : base(0x234C) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRoseOfTrinsic() : base( 0x234C ) - { - Movable = true; - Stackable = false; - } + public DecoRoseOfTrinsic(Serial serial) : base(serial) + { + } - public DecoRoseOfTrinsic( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic2.cs b/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic2.cs index 47cf3794a..13cf35c2e 100644 --- a/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic2.cs +++ b/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRoseOfTrinsic2 : Item - { + public class DecoRoseOfTrinsic2 : Item + { + [Constructible] + public DecoRoseOfTrinsic2() : base(0x234D) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRoseOfTrinsic2() : base( 0x234D ) - { - Movable = true; - Stackable = false; - } + public DecoRoseOfTrinsic2(Serial serial) : base(serial) + { + } - public DecoRoseOfTrinsic2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic3.cs b/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic3.cs index 76ac6bd09..01b7ec350 100644 --- a/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic3.cs +++ b/Scripts/Items/Special/Rares/Flowers/DecoRoseOfTrinsic3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoRoseOfTrinsic3 : Item - { + public class DecoRoseOfTrinsic3 : Item + { + [Constructible] + public DecoRoseOfTrinsic3() : base(0x234B) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoRoseOfTrinsic3() : base( 0x234B ) - { - Movable = true; - Stackable = false; - } + public DecoRoseOfTrinsic3(Serial serial) : base(serial) + { + } - public DecoRoseOfTrinsic3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Food/BottlesOfLiquor.cs b/Scripts/Items/Special/Rares/Food/BottlesOfLiquor.cs index 50a9a745e..0fd10d0f9 100644 --- a/Scripts/Items/Special/Rares/Food/BottlesOfLiquor.cs +++ b/Scripts/Items/Special/Rares/Food/BottlesOfLiquor.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoBottlesOfLiquor : Item - { + public class DecoBottlesOfLiquor : Item + { + [Constructible] + public DecoBottlesOfLiquor() : base(0x99E) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoBottlesOfLiquor() : base( 0x99E ) - { - Movable = true; - Stackable = false; - } + public DecoBottlesOfLiquor(Serial serial) : base(serial) + { + } - public DecoBottlesOfLiquor( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Food/Tray2.cs b/Scripts/Items/Special/Rares/Food/Tray2.cs index f5636a775..167545af0 100644 --- a/Scripts/Items/Special/Rares/Food/Tray2.cs +++ b/Scripts/Items/Special/Rares/Food/Tray2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTray2 : Item - { + public class DecoTray2 : Item + { + [Constructible] + public DecoTray2() : base(0x991) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTray2() : base( 0x991 ) - { - Movable = true; - Stackable = false; - } + public DecoTray2(Serial serial) : base(serial) + { + } - public DecoTray2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Food/Trays.cs b/Scripts/Items/Special/Rares/Food/Trays.cs index 6131f76ef..543290efe 100644 --- a/Scripts/Items/Special/Rares/Food/Trays.cs +++ b/Scripts/Items/Special/Rares/Food/Trays.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTray : Item - { + public class DecoTray : Item + { + [Constructible] + public DecoTray() : base(Utility.Random(2) + 0x991) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTray() : base( Utility.Random(2) + 0x991 ) - { - Movable = true; - Stackable = false; - } + public DecoTray(Serial serial) : base(serial) + { + } - public DecoTray( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Furniture/BrokenChair.cs b/Scripts/Items/Special/Rares/Furniture/BrokenChair.cs index 22a57e6e8..5fdc24911 100644 --- a/Scripts/Items/Special/Rares/Furniture/BrokenChair.cs +++ b/Scripts/Items/Special/Rares/Furniture/BrokenChair.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class BrokenChair : Item - { + public class BrokenChair : Item + { + [Constructible] + public BrokenChair() : base(Utility.Random(2) + 0xC19) + { + Movable = true; + Stackable = false; + } - [Constructible] - public BrokenChair() : base( Utility.Random(2) + 0xC19 ) - { - Movable = true; - Stackable = false; - } + public BrokenChair(Serial serial) : base(serial) + { + } - public BrokenChair( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/GamePieces/Checkers.cs b/Scripts/Items/Special/Rares/GamePieces/Checkers.cs index 4aa0c9e54..bc83b40b8 100644 --- a/Scripts/Items/Special/Rares/GamePieces/Checkers.cs +++ b/Scripts/Items/Special/Rares/GamePieces/Checkers.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Checkers : Item - { + public class Checkers : Item + { + [Constructible] + public Checkers() : base(0xE1A) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Checkers() : base( 0xE1A ) - { - Movable = true; - Stackable = false; - } + public Checkers(Serial serial) : base(serial) + { + } - public Checkers( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/GamePieces/Checkers2.cs b/Scripts/Items/Special/Rares/GamePieces/Checkers2.cs index 03e7b8f3e..352fb50cc 100644 --- a/Scripts/Items/Special/Rares/GamePieces/Checkers2.cs +++ b/Scripts/Items/Special/Rares/GamePieces/Checkers2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Checkers2 : Item - { + public class Checkers2 : Item + { + [Constructible] + public Checkers2() : base(0xE1B) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Checkers2() : base( 0xE1B ) - { - Movable = true; - Stackable = false; - } + public Checkers2(Serial serial) : base(serial) + { + } - public Checkers2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/GamePieces/Chessmen.cs b/Scripts/Items/Special/Rares/GamePieces/Chessmen.cs index ebf44b19e..c416c979d 100644 --- a/Scripts/Items/Special/Rares/GamePieces/Chessmen.cs +++ b/Scripts/Items/Special/Rares/GamePieces/Chessmen.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Chessmen : Item - { + public class Chessmen : Item + { + [Constructible] + public Chessmen() : base(0xE13) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Chessmen() : base( 0xE13 ) - { - Movable = true; - Stackable = false; - } + public Chessmen(Serial serial) : base(serial) + { + } - public Chessmen( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/GamePieces/Chessmen2.cs b/Scripts/Items/Special/Rares/GamePieces/Chessmen2.cs index 35e5d771c..2530fa8c4 100644 --- a/Scripts/Items/Special/Rares/GamePieces/Chessmen2.cs +++ b/Scripts/Items/Special/Rares/GamePieces/Chessmen2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Chessmen2 : Item - { + public class Chessmen2 : Item + { + [Constructible] + public Chessmen2() : base(0xE12) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Chessmen2() : base( 0xE12 ) - { - Movable = true; - Stackable = false; - } + public Chessmen2(Serial serial) : base(serial) + { + } - public Chessmen2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/GamePieces/Chessmen3.cs b/Scripts/Items/Special/Rares/GamePieces/Chessmen3.cs index 88a52682d..32bf64c42 100644 --- a/Scripts/Items/Special/Rares/GamePieces/Chessmen3.cs +++ b/Scripts/Items/Special/Rares/GamePieces/Chessmen3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Chessmen3 : Item - { + public class Chessmen3 : Item + { + [Constructible] + public Chessmen3() : base(0xE14) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Chessmen3() : base( 0xE14 ) - { - Movable = true; - Stackable = false; - } + public Chessmen3(Serial serial) : base(serial) + { + } - public Chessmen3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot.cs b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot.cs index 4d26718ef..8a04f7a77 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGoldIngot : Item - { + public class DecoGoldIngot : Item + { + [Constructible] + public DecoGoldIngot() : base(0x1BE9) + { + Movable = true; + Stackable = true; + } - [Constructible] - public DecoGoldIngot() : base( 0x1BE9 ) - { - Movable = true; - Stackable = true; - } + public DecoGoldIngot(Serial serial) : base(serial) + { + } - public DecoGoldIngot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot2.cs b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot2.cs index adf15d5c9..175969e31 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot2.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGoldIngot2 : Item - { + public class DecoGoldIngot2 : Item + { + [Constructible] + public DecoGoldIngot2() : base(0x1BEC) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGoldIngot2() : base( 0x1BEC ) - { - Movable = true; - Stackable = false; - } + public DecoGoldIngot2(Serial serial) : base(serial) + { + } - public DecoGoldIngot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots.cs b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots.cs index 7d101dce7..3803f7c6c 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGoldIngots : Item - { + public class DecoGoldIngots : Item + { + [Constructible] + public DecoGoldIngots() : base(0x1BEA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGoldIngots() : base( 0x1BEA ) - { - Movable = true; - Stackable = false; - } + public DecoGoldIngots(Serial serial) : base(serial) + { + } - public DecoGoldIngots( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots2.cs b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots2.cs index 95c84941c..b3951e783 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots2.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGoldIngots2 : Item - { + public class DecoGoldIngots2 : Item + { + [Constructible] + public DecoGoldIngots2() : base(0x1BEB) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGoldIngots2() : base( 0x1BEB ) - { - Movable = true; - Stackable = false; - } + public DecoGoldIngots2(Serial serial) : base(serial) + { + } - public DecoGoldIngots2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots3.cs b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots3.cs index 06a625afb..090836d5b 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots3.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGoldIngots3 : Item - { + public class DecoGoldIngots3 : Item + { + [Constructible] + public DecoGoldIngots3() : base(0x1BED) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGoldIngots3() : base( 0x1BED ) - { - Movable = true; - Stackable = false; - } + public DecoGoldIngots3(Serial serial) : base(serial) + { + } - public DecoGoldIngots3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots4.cs b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots4.cs index afce8ee59..30c35f5ce 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots4.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoGoldIngots4.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGoldIngots4 : Item - { + public class DecoGoldIngots4 : Item + { + [Constructible] + public DecoGoldIngots4() : base(0x1BEE) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGoldIngots4() : base( 0x1BEE ) - { - Movable = true; - Stackable = false; - } + public DecoGoldIngots4(Serial serial) : base(serial) + { + } - public DecoGoldIngots4( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngot.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngot.cs index c08556a5f..3d56c9fd0 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngot.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngot : Item - { + public class DecoIronIngot : Item + { + [Constructible] + public DecoIronIngot() : base(0x1BEF) + { + Movable = true; + Stackable = true; + } - [Constructible] - public DecoIronIngot() : base( 0x1BEF ) - { - Movable = true; - Stackable = true; - } + public DecoIronIngot(Serial serial) : base(serial) + { + } - public DecoIronIngot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngot2.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngot2.cs index 95ebb1fc6..5ccb75cfe 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngot2.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngot2 : Item - { + public class DecoIronIngot2 : Item + { + [Constructible] + public DecoIronIngot2() : base(0x1BEF) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngot2() : base( 0x1BEF ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngot2(Serial serial) : base(serial) + { + } - public DecoIronIngot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots.cs index 89b6e6daf..a2c026b3b 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngots : Item - { + public class DecoIronIngots : Item + { + [Constructible] + public DecoIronIngots() : base(0x1BF1) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngots() : base( 0x1BF1 ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngots(Serial serial) : base(serial) + { + } - public DecoIronIngots( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots2.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots2.cs index 52279b97c..80a6a58ce 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots2.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngots2 : Item - { + public class DecoIronIngots2 : Item + { + [Constructible] + public DecoIronIngots2() : base(0x1BF0) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngots2() : base( 0x1BF0 ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngots2(Serial serial) : base(serial) + { + } - public DecoIronIngots2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots3.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots3.cs index d14dcf159..53f0dd670 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots3.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngots3 : Item - { + public class DecoIronIngots3 : Item + { + [Constructible] + public DecoIronIngots3() : base(0x1BF0) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngots3() : base( 0x1BF0 ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngots3(Serial serial) : base(serial) + { + } - public DecoIronIngots3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots4.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots4.cs index ceb8abc51..25b0d7e6f 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots4.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots4.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngots4 : Item - { + public class DecoIronIngots4 : Item + { + [Constructible] + public DecoIronIngots4() : base(0x1BF1) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngots4() : base( 0x1BF1 ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngots4(Serial serial) : base(serial) + { + } - public DecoIronIngots4( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots5.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots5.cs index 61e06284a..900c5ed5e 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots5.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots5.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngots5 : Item - { + public class DecoIronIngots5 : Item + { + [Constructible] + public DecoIronIngots5() : base(0x1BF3) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngots5() : base( 0x1BF3 ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngots5(Serial serial) : base(serial) + { + } - public DecoIronIngots5( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots6.cs b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots6.cs index 2bf6bb615..934ccf0a6 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoIronIngots6.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoIronIngots6.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoIronIngots6 : Item - { + public class DecoIronIngots6 : Item + { + [Constructible] + public DecoIronIngots6() : base(0x1BF4) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoIronIngots6() : base( 0x1BF4 ) - { - Movable = true; - Stackable = false; - } + public DecoIronIngots6(Serial serial) : base(serial) + { + } - public DecoIronIngots6( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot.cs index ee0311c1a..b971c5022 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngot : Item - { + public class DecoSilverIngot : Item + { + [Constructible] + public DecoSilverIngot() : base(0x1BF5) + { + Movable = true; + Stackable = true; + } - [Constructible] - public DecoSilverIngot() : base( 0x1BF5 ) - { - Movable = true; - Stackable = true; - } + public DecoSilverIngot(Serial serial) : base(serial) + { + } - public DecoSilverIngot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot2.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot2.cs index ffeb55a10..a3277624c 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot2.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngot2 : Item - { + public class DecoSilverIngot2 : Item + { + [Constructible] + public DecoSilverIngot2() : base(0x1BF8) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSilverIngot2() : base( 0x1BF8 ) - { - Movable = true; - Stackable = false; - } + public DecoSilverIngot2(Serial serial) : base(serial) + { + } - public DecoSilverIngot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots.cs index 87d40c2f8..77696d97c 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngots : Item - { + public class DecoSilverIngots : Item + { + [Constructible] + public DecoSilverIngots() : base(0x1BFA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSilverIngots() : base( 0x1BFA ) - { - Movable = true; - Stackable = false; - } + public DecoSilverIngots(Serial serial) : base(serial) + { + } - public DecoSilverIngots( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots2.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots2.cs index 5a0b71166..68ee98a63 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots2.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngots2 : Item - { + public class DecoSilverIngots2 : Item + { + [Constructible] + public DecoSilverIngots2() : base(0x1BF6) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSilverIngots2() : base( 0x1BF6 ) - { - Movable = true; - Stackable = false; - } + public DecoSilverIngots2(Serial serial) : base(serial) + { + } - public DecoSilverIngots2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots3.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots3.cs index e68ddc5ed..c3141df5c 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots3.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngots3 : Item - { + public class DecoSilverIngots3 : Item + { + [Constructible] + public DecoSilverIngots3() : base(0x1BF7) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSilverIngots3() : base( 0x1BF7 ) - { - Movable = true; - Stackable = false; - } + public DecoSilverIngots3(Serial serial) : base(serial) + { + } - public DecoSilverIngots3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots4.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots4.cs index e76a2fb2d..4e3bb97a8 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots4.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots4.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngots4 : Item - { + public class DecoSilverIngots4 : Item + { + [Constructible] + public DecoSilverIngots4() : base(0x1BF9) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSilverIngots4() : base( 0x1BF9 ) - { - Movable = true; - Stackable = false; - } + public DecoSilverIngots4(Serial serial) : base(serial) + { + } - public DecoSilverIngots4( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots5.cs b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots5.cs index 186ffbad7..894ce453e 100644 --- a/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots5.cs +++ b/Scripts/Items/Special/Rares/Ingots/DecoSilverIngots5.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSilverIngots5 : Item - { + public class DecoSilverIngots5 : Item + { + [Constructible] + public DecoSilverIngots5() : base(0x1BFA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSilverIngots5() : base( 0x1BFA ) - { - Movable = true; - Stackable = false; - } + public DecoSilverIngots5(Serial serial) : base(serial) + { + } - public DecoSilverIngots5( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Jars/EmptyJars.cs b/Scripts/Items/Special/Rares/Jars/EmptyJars.cs index 8b37b2278..7d6c5332f 100644 --- a/Scripts/Items/Special/Rares/Jars/EmptyJars.cs +++ b/Scripts/Items/Special/Rares/Jars/EmptyJars.cs @@ -1,153 +1,152 @@ namespace Server.Items { - public class EmptyJar : Item - { - [Constructible] - public EmptyJar() - : base(0x1005) - { - Movable = true; - Stackable = false; - } + public class EmptyJar : Item + { + [Constructible] + public EmptyJar() + : base(0x1005) + { + Movable = true; + Stackable = false; + } - public EmptyJar(Serial serial) - : base(serial) - { - } + public EmptyJar(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class EmptyJars : Item - { - [Constructible] - public EmptyJars() - : base(0xe44) - { - Movable = true; - Stackable = false; - } + public class EmptyJars : Item + { + [Constructible] + public EmptyJars() + : base(0xe44) + { + Movable = true; + Stackable = false; + } - public EmptyJars(Serial serial) - : base(serial) - { - } + public EmptyJars(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class EmptyJars2 : Item - { - [Constructible] - public EmptyJars2() - : base(0xe45) - { - Movable = true; - Stackable = false; - } + public class EmptyJars2 : Item + { + [Constructible] + public EmptyJars2() + : base(0xe45) + { + Movable = true; + Stackable = false; + } - public EmptyJars2(Serial serial) + public EmptyJars2(Serial serial) + : base(serial) + { + } - : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int)0); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + public class EmptyJars3 : Item + { + [Constructible] + public EmptyJars3() + : base(0xe46) + { + Movable = true; + Stackable = false; + } - public class EmptyJars3 : Item - { - [Constructible] - public EmptyJars3() - : base(0xe46) - { - Movable = true; - Stackable = false; - } + public EmptyJars3(Serial serial) + : base(serial) + { + } - public EmptyJars3(Serial serial) - : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int)0); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - int version = reader.ReadInt(); - } - } + public class EmptyJars4 : Item + { + [Constructible] + public EmptyJars4() + : base(0xe47) + { + Movable = true; + Stackable = false; + } - public class EmptyJars4 : Item - { - [Constructible] - public EmptyJars4() - : base(0xe47) - { - Movable = true; - Stackable = false; - } + public EmptyJars4(Serial serial) + : base(serial) + { + } - public EmptyJars4(Serial serial) - : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int)0); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Jars/FullJars.cs b/Scripts/Items/Special/Rares/Jars/FullJars.cs index 4833c381e..31652b94f 100644 --- a/Scripts/Items/Special/Rares/Jars/FullJars.cs +++ b/Scripts/Items/Special/Rares/Jars/FullJars.cs @@ -1,92 +1,92 @@ namespace Server.Items { - public class DecoFullJar : Item - { - [Constructible] - public DecoFullJar() - : base(0x1006) - { - Movable = true; - Stackable = false; - } + public class DecoFullJar : Item + { + [Constructible] + public DecoFullJar() + : base(0x1006) + { + Movable = true; + Stackable = false; + } - public DecoFullJar(Serial serial) - : base(serial) - { - } + public DecoFullJar(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DecoFullJars3 : Item - { - [Constructible] - public DecoFullJars3() - : base(0xE4a) - { - Movable = true; - Stackable = false; - } + public class DecoFullJars3 : Item + { + [Constructible] + public DecoFullJars3() + : base(0xE4a) + { + Movable = true; + Stackable = false; + } - public DecoFullJars3(Serial serial) - : base(serial) - { - } + public DecoFullJars3(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class DecoFullJars4 : Item - { - [Constructible] - public DecoFullJars4() - : base(0xE4b) - { - Movable = true; - Stackable = false; - } + public class DecoFullJars4 : Item + { + [Constructible] + public DecoFullJars4() + : base(0xE4b) + { + Movable = true; + Stackable = false; + } - public DecoFullJars4(Serial serial) - : base(serial) - { - } + public DecoFullJars4(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Jars/HalfEmptyJars.cs b/Scripts/Items/Special/Rares/Jars/HalfEmptyJars.cs index c0919dba1..c95624c76 100644 --- a/Scripts/Items/Special/Rares/Jars/HalfEmptyJars.cs +++ b/Scripts/Items/Special/Rares/Jars/HalfEmptyJars.cs @@ -1,152 +1,152 @@ namespace Server.Items { - public class HalfEmptyJar : Item - { - [Constructible] - public HalfEmptyJar() - : base(0x1007) - { - Movable = true; - Stackable = false; - } + public class HalfEmptyJar : Item + { + [Constructible] + public HalfEmptyJar() + : base(0x1007) + { + Movable = true; + Stackable = false; + } - public HalfEmptyJar(Serial serial) - : base(serial) - { - } + public HalfEmptyJar(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class HalfEmptyJars : Item - { - [Constructible] - public HalfEmptyJars() - : base(0xe4c) - { - Movable = true; - Stackable = false; - } + public class HalfEmptyJars : Item + { + [Constructible] + public HalfEmptyJars() + : base(0xe4c) + { + Movable = true; + Stackable = false; + } - public HalfEmptyJars(Serial serial) - : base(serial) - { - } + public HalfEmptyJars(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Jars2 : Item - { - [Constructible] - public Jars2() - : base(0xE4d) - { - Movable = true; - Stackable = false; - } + public class Jars2 : Item + { + [Constructible] + public Jars2() + : base(0xE4d) + { + Movable = true; + Stackable = false; + } - public Jars2(Serial serial) - : base(serial) - { - } + public Jars2(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Jars3 : Item - { - [Constructible] - public Jars3() - : base(0xE4e) - { - Movable = true; - Stackable = false; - } + public class Jars3 : Item + { + [Constructible] + public Jars3() + : base(0xE4e) + { + Movable = true; + Stackable = false; + } - public Jars3(Serial serial) - : base(serial) - { - } + public Jars3(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class Jars4 : Item - { - [Constructible] - public Jars4() - : base(0xE4f) - { - Movable = true; - Stackable = false; - } + public class Jars4 : Item + { + [Constructible] + public Jars4() + : base(0xE4f) + { + Movable = true; + Stackable = false; + } - public Jars4(Serial serial) - : base(serial) - { - } + public Jars4(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Magic/DecoCrystalBall.cs b/Scripts/Items/Special/Rares/Magic/DecoCrystalBall.cs index 3cfd12ee0..46c7afe1b 100644 --- a/Scripts/Items/Special/Rares/Magic/DecoCrystalBall.cs +++ b/Scripts/Items/Special/Rares/Magic/DecoCrystalBall.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoCrystalBall : Item - { + public class DecoCrystalBall : Item + { + [Constructible] + public DecoCrystalBall() : base(0xE2E) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoCrystalBall() : base( 0xE2E ) - { - Movable = true; - Stackable = false; - } + public DecoCrystalBall(Serial serial) : base(serial) + { + } - public DecoCrystalBall( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Magic/DecoMagicalCrystal.cs b/Scripts/Items/Special/Rares/Magic/DecoMagicalCrystal.cs index 2986825d6..c5b5dde32 100644 --- a/Scripts/Items/Special/Rares/Magic/DecoMagicalCrystal.cs +++ b/Scripts/Items/Special/Rares/Magic/DecoMagicalCrystal.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoMagicalCrystal : Item - { + public class DecoMagicalCrystal : Item + { + [Constructible] + public DecoMagicalCrystal() : base(0x1F19) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoMagicalCrystal() : base( 0x1F19 ) - { - Movable = true; - Stackable = false; - } + public DecoMagicalCrystal(Serial serial) : base(serial) + { + } - public DecoMagicalCrystal( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Misc/DecoSpittoon.cs b/Scripts/Items/Special/Rares/Misc/DecoSpittoon.cs index 27803b4f1..a780530c4 100644 --- a/Scripts/Items/Special/Rares/Misc/DecoSpittoon.cs +++ b/Scripts/Items/Special/Rares/Misc/DecoSpittoon.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoSpittoon : Item - { + public class DecoSpittoon : Item + { + [Constructible] + public DecoSpittoon() : base(0x1003) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoSpittoon() : base( 0x1003 ) - { - Movable = true; - Stackable = false; - } + public DecoSpittoon(Serial serial) : base(serial) + { + } - public DecoSpittoon( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoBlackmoor.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoBlackmoor.cs index 767577de9..aa8cf7148 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoBlackmoor.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoBlackmoor.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoBlackmoor : Item - { + public class DecoBlackmoor : Item + { + [Constructible] + public DecoBlackmoor() : base(0xF79) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoBlackmoor() : base( 0xF79 ) - { - Movable = true; - Stackable = false; - } + public DecoBlackmoor(Serial serial) : base(serial) + { + } - public DecoBlackmoor( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoBloodspawn.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoBloodspawn.cs index ae5526a72..a9895dd51 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoBloodspawn.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoBloodspawn.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoBloodspawn : Item - { + public class DecoBloodspawn : Item + { + [Constructible] + public DecoBloodspawn() : base(0xF7C) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoBloodspawn() : base( 0xF7C ) - { - Movable = true; - Stackable = false; - } + public DecoBloodspawn(Serial serial) : base(serial) + { + } - public DecoBloodspawn( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoBrimstone.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoBrimstone.cs index 6ccd23bd2..462530996 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoBrimstone.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoBrimstone.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoBrimstone : Item - { + public class DecoBrimstone : Item + { + [Constructible] + public DecoBrimstone() : base(0xF7F) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoBrimstone() : base( 0xF7F ) - { - Movable = true; - Stackable = false; - } + public DecoBrimstone(Serial serial) : base(serial) + { + } - public DecoBrimstone( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood.cs index 0097aa588..e831deebe 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoDragonsBlood : Item - { + public class DecoDragonsBlood : Item + { + [Constructible] + public DecoDragonsBlood() : base(0x4077) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoDragonsBlood() : base( 0x4077 ) - { - Movable = true; - Stackable = false; - } + public DecoDragonsBlood(Serial serial) : base(serial) + { + } - public DecoDragonsBlood( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood2.cs index 6b0f0e93b..6b7b9c85e 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoDragonsBlood2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoDragonsBlood2 : Item - { + public class DecoDragonsBlood2 : Item + { + [Constructible] + public DecoDragonsBlood2() : base(0xF82) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoDragonsBlood2() : base( 0xF82 ) - { - Movable = true; - Stackable = false; - } + public DecoDragonsBlood2(Serial serial) : base(serial) + { + } - public DecoDragonsBlood2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoEyeOfNewt.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoEyeOfNewt.cs index 6617da4c5..eb081b9dd 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoEyeOfNewt.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoEyeOfNewt.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoEyeOfNewt : Item - { + public class DecoEyeOfNewt : Item + { + [Constructible] + public DecoEyeOfNewt() : base(0xF87) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoEyeOfNewt() : base( 0xF87 ) - { - Movable = true; - Stackable = false; - } + public DecoEyeOfNewt(Serial serial) : base(serial) + { + } - public DecoEyeOfNewt( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic.cs index 08bf97250..2e1ae6a01 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGarlic : Item - { + public class DecoGarlic : Item + { + [Constructible] + public DecoGarlic() : base(0x18E1) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGarlic() : base( 0x18E1 ) - { - Movable = true; - Stackable = false; - } + public DecoGarlic(Serial serial) : base(serial) + { + } - public DecoGarlic( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic2.cs index 737b87925..96687cad1 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlic2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGarlic2 : Item - { + public class DecoGarlic2 : Item + { + [Constructible] + public DecoGarlic2() : base(0x18E2) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGarlic2() : base( 0x18E2 ) - { - Movable = true; - Stackable = false; - } + public DecoGarlic2(Serial serial) : base(serial) + { + } - public DecoGarlic2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb.cs index a628a5597..60122a06e 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGarlicBulb : Item - { + public class DecoGarlicBulb : Item + { + [Constructible] + public DecoGarlicBulb() : base(0x18E3) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGarlicBulb() : base( 0x18E3 ) - { - Movable = true; - Stackable = false; - } + public DecoGarlicBulb(Serial serial) : base(serial) + { + } - public DecoGarlicBulb( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb2.cs index 9b7fc374c..030608526 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGarlicBulb2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGarlicBulb2 : Item - { + public class DecoGarlicBulb2 : Item + { + [Constructible] + public DecoGarlicBulb2() : base(0x18E4) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGarlicBulb2() : base( 0x18E4 ) - { - Movable = true; - Stackable = false; - } + public DecoGarlicBulb2(Serial serial) : base(serial) + { + } - public DecoGarlicBulb2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng.cs index b12d146dc..86c031171 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGinseng : Item - { + public class DecoGinseng : Item + { + [Constructible] + public DecoGinseng() : base(0x18E9) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGinseng() : base( 0x18E9 ) - { - Movable = true; - Stackable = false; - } + public DecoGinseng(Serial serial) : base(serial) + { + } - public DecoGinseng( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng2.cs index 619db9ea6..fd6eed124 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGinseng2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGinseng2 : Item - { + public class DecoGinseng2 : Item + { + [Constructible] + public DecoGinseng2() : base(0x18EA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGinseng2() : base( 0x18EA ) - { - Movable = true; - Stackable = false; - } + public DecoGinseng2(Serial serial) : base(serial) + { + } - public DecoGinseng2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot.cs index 1c1507ceb..0bf732b7a 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGinsengRoot : Item - { + public class DecoGinsengRoot : Item + { + [Constructible] + public DecoGinsengRoot() : base(0x18EB) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGinsengRoot() : base( 0x18EB ) - { - Movable = true; - Stackable = false; - } + public DecoGinsengRoot(Serial serial) : base(serial) + { + } - public DecoGinsengRoot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot2.cs index 30ad76a97..ce0e845ec 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoGinsengRoot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoGinsengRoot2 : Item - { + public class DecoGinsengRoot2 : Item + { + [Constructible] + public DecoGinsengRoot2() : base(0x18EC) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoGinsengRoot2() : base( 0x18EC ) - { - Movable = true; - Stackable = false; - } + public DecoGinsengRoot2(Serial serial) : base(serial) + { + } - public DecoGinsengRoot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake.cs index 4cf149117..7bce97742 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoMandrake : Item - { + public class DecoMandrake : Item + { + [Constructible] + public DecoMandrake() : base(0x18DF) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoMandrake() : base( 0x18DF ) - { - Movable = true; - Stackable = false; - } + public DecoMandrake(Serial serial) : base(serial) + { + } - public DecoMandrake( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake2.cs index 02ad73835..d037fa5e4 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoMandrake2 : Item - { + public class DecoMandrake2 : Item + { + [Constructible] + public DecoMandrake2() : base(0x18E0) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoMandrake2() : base( 0x18E0 ) - { - Movable = true; - Stackable = false; - } + public DecoMandrake2(Serial serial) : base(serial) + { + } - public DecoMandrake2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake3.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake3.cs index a331d24f4..6d5d86e4f 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake3.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrake3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoMandrake3 : Item - { + public class DecoMandrake3 : Item + { + [Constructible] + public DecoMandrake3() : base(0x18DF) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoMandrake3() : base( 0x18DF ) - { - Movable = true; - Stackable = false; - } + public DecoMandrake3(Serial serial) : base(serial) + { + } - public DecoMandrake3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot.cs index b3146afde..b1fb6a7d1 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoMandrakeRoot : Item - { + public class DecoMandrakeRoot : Item + { + [Constructible] + public DecoMandrakeRoot() : base(0x18DE) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoMandrakeRoot() : base( 0x18DE ) - { - Movable = true; - Stackable = false; - } + public DecoMandrakeRoot(Serial serial) : base(serial) + { + } - public DecoMandrakeRoot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot2.cs index 9882defd3..60b7181c3 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoMandrakeRoot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoMandrakeRoot2 : Item - { + public class DecoMandrakeRoot2 : Item + { + [Constructible] + public DecoMandrakeRoot2() : base(0x18DD) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoMandrakeRoot2() : base( 0x18DD ) - { - Movable = true; - Stackable = false; - } + public DecoMandrakeRoot2(Serial serial) : base(serial) + { + } - public DecoMandrakeRoot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade.cs index 3d98a75a9..ec5b8f08a 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoNightshade : Item - { + public class DecoNightshade : Item + { + [Constructible] + public DecoNightshade() : base(0x18E7) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoNightshade() : base( 0x18E7 ) - { - Movable = true; - Stackable = false; - } + public DecoNightshade(Serial serial) : base(serial) + { + } - public DecoNightshade( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade2.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade2.cs index 6e5141097..c18f67987 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade2.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoNightshade2 : Item - { + public class DecoNightshade2 : Item + { + [Constructible] + public DecoNightshade2() : base(0x18E5) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoNightshade2() : base( 0x18E5 ) - { - Movable = true; - Stackable = false; - } + public DecoNightshade2(Serial serial) : base(serial) + { + } - public DecoNightshade2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade3.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade3.cs index a09205809..bf64a66f7 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade3.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoNightshade3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoNightshade3 : Item - { + public class DecoNightshade3 : Item + { + [Constructible] + public DecoNightshade3() : base(0x18E6) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoNightshade3() : base( 0x18E6 ) - { - Movable = true; - Stackable = false; - } + public DecoNightshade3(Serial serial) : base(serial) + { + } - public DecoNightshade3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoObsidian.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoObsidian.cs index 8959eaacb..70f74b522 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoObsidian.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoObsidian.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoObsidian : Item - { + public class DecoObsidian : Item + { + [Constructible] + public DecoObsidian() : base(0xF89) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoObsidian() : base( 0xF89 ) - { - Movable = true; - Stackable = false; - } + public DecoObsidian(Serial serial) : base(serial) + { + } - public DecoObsidian( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoPumice.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoPumice.cs index 0da2f347d..17185732a 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoPumice.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoPumice.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoPumice : Item - { + public class DecoPumice : Item + { + [Constructible] + public DecoPumice() : base(0xF8B) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoPumice() : base( 0xF8B ) - { - Movable = true; - Stackable = false; - } + public DecoPumice(Serial serial) : base(serial) + { + } - public DecoPumice( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PaganReagents/DecoWyrmsHeart.cs b/Scripts/Items/Special/Rares/PaganReagents/DecoWyrmsHeart.cs index e64adc239..9f20af483 100644 --- a/Scripts/Items/Special/Rares/PaganReagents/DecoWyrmsHeart.cs +++ b/Scripts/Items/Special/Rares/PaganReagents/DecoWyrmsHeart.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoWyrmsHeart : Item - { + public class DecoWyrmsHeart : Item + { + [Constructible] + public DecoWyrmsHeart() : base(0xF91) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoWyrmsHeart() : base( 0xF91 ) - { - Movable = true; - Stackable = false; - } + public DecoWyrmsHeart(Serial serial) : base(serial) + { + } - public DecoWyrmsHeart( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/Cards.cs b/Scripts/Items/Special/Rares/PlayingCards/Cards.cs index 533fa9adc..31b2da38c 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/Cards.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/Cards.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Cards : Item - { + public class Cards : Item + { + [Constructible] + public Cards() : base(0xE19) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Cards() : base( 0xE19 ) - { - Movable = true; - Stackable = false; - } + public Cards(Serial serial) : base(serial) + { + } - public Cards( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/Cards2.cs b/Scripts/Items/Special/Rares/PlayingCards/Cards2.cs index d7ac72821..139eda441 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/Cards2.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/Cards2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Cards2 : Item - { + public class Cards2 : Item + { + [Constructible] + public Cards2() : base(0xE16) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Cards2() : base( 0xE16 ) - { - Movable = true; - Stackable = false; - } + public Cards2(Serial serial) : base(serial) + { + } - public Cards2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/Cards3.cs b/Scripts/Items/Special/Rares/PlayingCards/Cards3.cs index 21ffccceb..4ebea99e3 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/Cards3.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/Cards3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Cards3 : Item - { + public class Cards3 : Item + { + [Constructible] + public Cards3() : base(0xE15) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Cards3() : base( 0xE15 ) - { - Movable = true; - Stackable = false; - } + public Cards3(Serial serial) : base(serial) + { + } - public Cards3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/Cards4.cs b/Scripts/Items/Special/Rares/PlayingCards/Cards4.cs index 08a59f6f5..b5532e3a9 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/Cards4.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/Cards4.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Cards4 : Item - { + public class Cards4 : Item + { + [Constructible] + public Cards4() : base(0xE17) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Cards4() : base( 0xE17 ) - { - Movable = true; - Stackable = false; - } + public Cards4(Serial serial) : base(serial) + { + } - public Cards4( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/Cards5.cs b/Scripts/Items/Special/Rares/PlayingCards/Cards5.cs index e6d5c28b6..1c63716e3 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/Cards5.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/Cards5.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoCards5 : Item - { + public class DecoCards5 : Item + { + [Constructible] + public DecoCards5() : base(0xE18) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoCards5() : base( 0xE18 ) - { - Movable = true; - Stackable = false; - } + public DecoCards5(Serial serial) : base(serial) + { + } - public DecoCards5( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/PlayingCards.cs b/Scripts/Items/Special/Rares/PlayingCards/PlayingCards.cs index afd3f30e4..9e527df15 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/PlayingCards.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/PlayingCards.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class PlayingCards : Item - { + public class PlayingCards : Item + { + [Constructible] + public PlayingCards() : base(0xFA3) + { + Movable = true; + Stackable = false; + } - [Constructible] - public PlayingCards() : base( 0xFA3 ) - { - Movable = true; - Stackable = false; - } + public PlayingCards(Serial serial) : base(serial) + { + } - public PlayingCards( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/PlayingCards/PlayingCards2.cs b/Scripts/Items/Special/Rares/PlayingCards/PlayingCards2.cs index f8ee45dfb..36bdb8a33 100644 --- a/Scripts/Items/Special/Rares/PlayingCards/PlayingCards2.cs +++ b/Scripts/Items/Special/Rares/PlayingCards/PlayingCards2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class PlayingCards2 : Item - { + public class PlayingCards2 : Item + { + [Constructible] + public PlayingCards2() : base(0xFA2) + { + Movable = true; + Stackable = false; + } - [Constructible] - public PlayingCards2() : base( 0xFA2 ) - { - Movable = true; - Stackable = false; - } + public PlayingCards2(Serial serial) : base(serial) + { + } - public PlayingCards2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Stables/Bridle.cs b/Scripts/Items/Special/Rares/Stables/Bridle.cs index 2842db029..eb6edf55d 100644 --- a/Scripts/Items/Special/Rares/Stables/Bridle.cs +++ b/Scripts/Items/Special/Rares/Stables/Bridle.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoBridle : Item - { + public class DecoBridle : Item + { + [Constructible] + public DecoBridle() : base(0x1374) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoBridle() : base( 0x1374 ) - { - Movable = true; - Stackable = false; - } + public DecoBridle(Serial serial) : base(serial) + { + } - public DecoBridle( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Stables/Bridle2.cs b/Scripts/Items/Special/Rares/Stables/Bridle2.cs index f164d19be..3cb66afba 100644 --- a/Scripts/Items/Special/Rares/Stables/Bridle2.cs +++ b/Scripts/Items/Special/Rares/Stables/Bridle2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoBridle2 : Item - { + public class DecoBridle2 : Item + { + [Constructible] + public DecoBridle2() : base(0x1375) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoBridle2() : base( 0x1375 ) - { - Movable = true; - Stackable = false; - } + public DecoBridle2(Serial serial) : base(serial) + { + } - public DecoBridle2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Stables/DecoHay.cs b/Scripts/Items/Special/Rares/Stables/DecoHay.cs index 2b0556db0..49e1b0785 100644 --- a/Scripts/Items/Special/Rares/Stables/DecoHay.cs +++ b/Scripts/Items/Special/Rares/Stables/DecoHay.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoHay : Item - { + public class DecoHay : Item + { + [Constructible] + public DecoHay() : base(0xF35) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoHay() : base( 0xF35 ) - { - Movable = true; - Stackable = false; - } + public DecoHay(Serial serial) : base(serial) + { + } - public DecoHay( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Stables/DecoHay2.cs b/Scripts/Items/Special/Rares/Stables/DecoHay2.cs index 7f7c42771..d053d395a 100644 --- a/Scripts/Items/Special/Rares/Stables/DecoHay2.cs +++ b/Scripts/Items/Special/Rares/Stables/DecoHay2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoHay2 : Item - { + public class DecoHay2 : Item + { + [Constructible] + public DecoHay2() : base(0xF34) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoHay2() : base( 0xF34 ) - { - Movable = true; - Stackable = false; - } + public DecoHay2(Serial serial) : base(serial) + { + } - public DecoHay2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Stables/DecoHorseDung.cs b/Scripts/Items/Special/Rares/Stables/DecoHorseDung.cs index 774f79052..779cae2ac 100644 --- a/Scripts/Items/Special/Rares/Stables/DecoHorseDung.cs +++ b/Scripts/Items/Special/Rares/Stables/DecoHorseDung.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoHorseDung : Item - { + public class DecoHorseDung : Item + { + [Constructible] + public DecoHorseDung() : base(0xF3B) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoHorseDung() : base( 0xF3B ) - { - Movable = true; - Stackable = false; - } + public DecoHorseDung(Serial serial) : base(serial) + { + } - public DecoHorseDung( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot.cs b/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot.cs index a6fd09176..dc52a6193 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoDeckOfTarot : Item - { + public class DecoDeckOfTarot : Item + { + [Constructible] + public DecoDeckOfTarot() : base(0x12AB) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoDeckOfTarot() : base( 0x12AB ) - { - Movable = true; - Stackable = false; - } + public DecoDeckOfTarot(Serial serial) : base(serial) + { + } - public DecoDeckOfTarot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot2.cs b/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot2.cs index 03849b134..c77623246 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot2.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoDeckOfTarot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoDeckOfTarot2 : Item - { + public class DecoDeckOfTarot2 : Item + { + [Constructible] + public DecoDeckOfTarot2() : base(0x12Ac) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoDeckOfTarot2() : base( 0x12Ac ) - { - Movable = true; - Stackable = false; - } + public DecoDeckOfTarot2(Serial serial) : base(serial) + { + } - public DecoDeckOfTarot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot.cs index 868717a2d..7ff365415 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot : Item - { + public class DecoTarot : Item + { + [Constructible] + public DecoTarot() : base(0x12A5) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot() : base( 0x12A5 ) - { - Movable = true; - Stackable = false; - } + public DecoTarot(Serial serial) : base(serial) + { + } - public DecoTarot( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot2.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot2.cs index 817c6dca2..2248ca6d5 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot2.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot2 : Item - { + public class DecoTarot2 : Item + { + [Constructible] + public DecoTarot2() : base(0x12A6) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot2() : base( 0x12A6 ) - { - Movable = true; - Stackable = false; - } + public DecoTarot2(Serial serial) : base(serial) + { + } - public DecoTarot2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot3.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot3.cs index 572415174..56c86e678 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot3.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot3.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot3 : Item - { + public class DecoTarot3 : Item + { + [Constructible] + public DecoTarot3() : base(0x12A7) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot3() : base( 0x12A7 ) - { - Movable = true; - Stackable = false; - } + public DecoTarot3(Serial serial) : base(serial) + { + } - public DecoTarot3( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot4.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot4.cs index b5f068de3..562869e6f 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot4.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot4.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot4 : Item - { + public class DecoTarot4 : Item + { + [Constructible] + public DecoTarot4() : base(0x12A8) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot4() : base( 0x12A8 ) - { - Movable = true; - Stackable = false; - } + public DecoTarot4(Serial serial) : base(serial) + { + } - public DecoTarot4( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot5.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot5.cs index 50dc6e5f7..fa7daf7c8 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot5.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot5.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot5 : Item - { + public class DecoTarot5 : Item + { + [Constructible] + public DecoTarot5() : base(0x12A9) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot5() : base( 0x12A9 ) - { - Movable = true; - Stackable = false; - } + public DecoTarot5(Serial serial) : base(serial) + { + } - public DecoTarot5( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot6.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot6.cs index eb6f043a0..efab9cf55 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot6.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot6.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot6 : Item - { + public class DecoTarot6 : Item + { + [Constructible] + public DecoTarot6() : base(0x12AA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot6() : base( 0x12AA ) - { - Movable = true; - Stackable = false; - } + public DecoTarot6(Serial serial) : base(serial) + { + } - public DecoTarot6( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/TarotCards/DecoTarot7.cs b/Scripts/Items/Special/Rares/TarotCards/DecoTarot7.cs index bf8925ae3..24e06b8ed 100644 --- a/Scripts/Items/Special/Rares/TarotCards/DecoTarot7.cs +++ b/Scripts/Items/Special/Rares/TarotCards/DecoTarot7.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoTarot7 : Item - { + public class DecoTarot7 : Item + { + [Constructible] + public DecoTarot7() : base(0x12A5) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoTarot7() : base( 0x12A5 ) - { - Movable = true; - Stackable = false; - } + public DecoTarot7(Serial serial) : base(serial) + { + } - public DecoTarot7( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Tinker/ArrowShafts.cs b/Scripts/Items/Special/Rares/Tinker/ArrowShafts.cs index a97c0f780..63c58c1de 100644 --- a/Scripts/Items/Special/Rares/Tinker/ArrowShafts.cs +++ b/Scripts/Items/Special/Rares/Tinker/ArrowShafts.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class DecoArrowShafts : Item - { + public class DecoArrowShafts : Item + { + [Constructible] + public DecoArrowShafts() : base(Utility.Random(2) + 0x1024) + { + Movable = true; + Stackable = false; + } - [Constructible] - public DecoArrowShafts() : base( Utility.Random(2) + 0x1024 ) - { - Movable = true; - Stackable = false; - } + public DecoArrowShafts(Serial serial) : base(serial) + { + } - public DecoArrowShafts( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Tinker/CrossbowBolts.cs b/Scripts/Items/Special/Rares/Tinker/CrossbowBolts.cs index e0e9ad557..9447cf536 100644 --- a/Scripts/Items/Special/Rares/Tinker/CrossbowBolts.cs +++ b/Scripts/Items/Special/Rares/Tinker/CrossbowBolts.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class CrossbowBolts : Item - { + public class CrossbowBolts : Item + { + [Constructible] + public CrossbowBolts() : base(0x1BFC) + { + Movable = true; + Stackable = false; + } - [Constructible] - public CrossbowBolts() : base( 0x1BFC ) - { - Movable = true; - Stackable = false; - } + public CrossbowBolts(Serial serial) : base(serial) + { + } - public CrossbowBolts( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Tinker/EmptyToolKit.cs b/Scripts/Items/Special/Rares/Tinker/EmptyToolKit.cs index dc8332cf1..f5ae6acde 100644 --- a/Scripts/Items/Special/Rares/Tinker/EmptyToolKit.cs +++ b/Scripts/Items/Special/Rares/Tinker/EmptyToolKit.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class EmptyToolKit : Item - { + public class EmptyToolKit : Item + { + [Constructible] + public EmptyToolKit() : base(0x1EB6) + { + Movable = true; + Stackable = false; + } - [Constructible] - public EmptyToolKit() : base( 0x1EB6 ) - { - Movable = true; - Stackable = false; - } + public EmptyToolKit(Serial serial) : base(serial) + { + } - public EmptyToolKit( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Tinker/EmptyToolKit2.cs b/Scripts/Items/Special/Rares/Tinker/EmptyToolKit2.cs index 49411913a..c4a78e8bc 100644 --- a/Scripts/Items/Special/Rares/Tinker/EmptyToolKit2.cs +++ b/Scripts/Items/Special/Rares/Tinker/EmptyToolKit2.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class EmptyToolKit2 : Item - { + public class EmptyToolKit2 : Item + { + [Constructible] + public EmptyToolKit2() : base(0x1EB7) + { + Movable = true; + Stackable = false; + } - [Constructible] - public EmptyToolKit2() : base( 0x1EB7 ) - { - Movable = true; - Stackable = false; - } + public EmptyToolKit2(Serial serial) : base(serial) + { + } - public EmptyToolKit2( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Tinker/Lockpicks.cs b/Scripts/Items/Special/Rares/Tinker/Lockpicks.cs index 8c75babde..a98a7b95b 100644 --- a/Scripts/Items/Special/Rares/Tinker/Lockpicks.cs +++ b/Scripts/Items/Special/Rares/Tinker/Lockpicks.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class Lockpicks : Item - { + public class Lockpicks : Item + { + [Constructible] + public Lockpicks() : base(Utility.Random(2) + 0x14FD) + { + Movable = true; + Stackable = false; + } - [Constructible] - public Lockpicks() : base( Utility.Random(2) + 0x14FD ) - { - Movable = true; - Stackable = false; - } + public Lockpicks(Serial serial) : base(serial) + { + } - public Lockpicks( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Rares/Tinker/ToolKit.cs b/Scripts/Items/Special/Rares/Tinker/ToolKit.cs index 7b66ee732..b62af3de7 100644 --- a/Scripts/Items/Special/Rares/Tinker/ToolKit.cs +++ b/Scripts/Items/Special/Rares/Tinker/ToolKit.cs @@ -1,31 +1,30 @@ namespace Server.Items { - public class ToolKit : Item - { + public class ToolKit : Item + { + [Constructible] + public ToolKit() : base(Utility.Random(2) + 0x1EBA) + { + Movable = true; + Stackable = false; + } - [Constructible] - public ToolKit() : base( Utility.Random(2) + 0x1EBA ) - { - Movable = true; - Stackable = false; - } + public ToolKit(Serial serial) : base(serial) + { + } - public ToolKit( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/RewardCake.cs b/Scripts/Items/Special/RewardCake.cs index c79b55e0c..5fe4c166d 100644 --- a/Scripts/Items/Special/RewardCake.cs +++ b/Scripts/Items/Special/RewardCake.cs @@ -2,46 +2,45 @@ using Server.Network; namespace Server.Items { - public class RewardCake : Item - { - public override int LabelNumber => 1049786; // Happy Birthday! ... + public class RewardCake : Item + { + [Constructible] + public RewardCake() : base(0x9e9) + { + Stackable = false; + Weight = 1.0; + Hue = Utility.RandomList(0x135, 0xcd, 0x38, 0x3b, 0x42, 0x4f, 0x11e, 0x60, 0x317, 0x10, 0x136, 0x1f9, 0x1a, 0xeb, + 0x86, 0x2e); + LootType = LootType.Blessed; + } - [Constructible] - public RewardCake() : base( 0x9e9 ) - { - Stackable = false; - Weight = 1.0; - Hue = Utility.RandomList(0x135, 0xcd, 0x38, 0x3b, 0x42, 0x4f, 0x11e, 0x60, 0x317, 0x10, 0x136, 0x1f9, 0x1a, 0xeb, 0x86, 0x2e); - LootType = LootType.Blessed; - } + public RewardCake(Serial serial) : base(serial) + { + } - public RewardCake( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1049786; // Happy Birthday! ... - public override bool DisplayLootType => false; + public override bool DisplayLootType => false; - public override void OnDoubleClick( Mobile from ) - { - if (! from.InRange( GetWorldLocation(), 1 )) - { - from.LocalOverheadMessage( MessageType.Regular, 906, 1019045 ); // I can't reach that. - } - } + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 1)) + from.LocalOverheadMessage(MessageType.Regular, 906, 1019045); // I can't reach that. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Solen Items/BagOfSending.cs b/Scripts/Items/Special/Solen Items/BagOfSending.cs index 036a10d7e..a8240b0fb 100644 --- a/Scripts/Items/Special/Solen Items/BagOfSending.cs +++ b/Scripts/Items/Special/Solen Items/BagOfSending.cs @@ -1,280 +1,289 @@ using System; using System.Collections.Generic; using Server.ContextMenus; -using Server.Targeting; +using Server.Engines.Quests; using Server.Network; +using Server.Regions; +using Server.Spells; +using Server.Targeting; namespace Server.Items { - public enum BagOfSendingHue - { - Yellow, - Blue, - Red - } + public enum BagOfSendingHue + { + Yellow, + Blue, + Red + } - public class BagOfSending : Item, TranslocationItem - { - public static BagOfSendingHue RandomHue() - { - switch ( Utility.Random( 3 ) ) - { - case 0: return BagOfSendingHue.Yellow; - case 1: return BagOfSendingHue.Blue; - default: return BagOfSendingHue.Red; - } - } + public class BagOfSending : Item, TranslocationItem + { + private BagOfSendingHue m_BagOfSendingHue; - private int m_Charges; - private int m_Recharges; - private BagOfSendingHue m_BagOfSendingHue; + private int m_Charges; + private int m_Recharges; - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set - { - if ( value > MaxCharges ) - m_Charges = MaxCharges; - else if ( value < 0 ) - m_Charges = 0; - else - m_Charges = value; + [Constructible] + public BagOfSending() : this(RandomHue()) + { + } - InvalidateProperties(); - } - } + [Constructible] + public BagOfSending(BagOfSendingHue hue) : base(0xE76) + { + Weight = 2.0; - [CommandProperty( AccessLevel.GameMaster )] - public int Recharges - { - get => m_Recharges; - set - { - if ( value > MaxRecharges ) - m_Recharges = MaxRecharges; - else if ( value < 0 ) - m_Recharges = 0; - else - m_Recharges = value; + BagOfSendingHue = hue; - InvalidateProperties(); - } - } + m_Charges = Utility.RandomMinMax(3, 9); + } - [CommandProperty( AccessLevel.GameMaster )] - public int MaxCharges => 30; + public BagOfSending(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int MaxRecharges => 255; + public override int LabelNumber => 1054104; // a bag of sending - public string TranslocationItemName => "bag of sending"; + [CommandProperty(AccessLevel.GameMaster)] + public BagOfSendingHue BagOfSendingHue + { + get => m_BagOfSendingHue; + set + { + m_BagOfSendingHue = value; - public override int LabelNumber => 1054104; // a bag of sending + switch (value) + { + case BagOfSendingHue.Yellow: + Hue = 0x8A5; + break; + case BagOfSendingHue.Blue: + Hue = 0x8AD; + break; + case BagOfSendingHue.Red: + Hue = 0x89B; + break; + } + } + } - [CommandProperty( AccessLevel.GameMaster )] - public BagOfSendingHue BagOfSendingHue - { - get => m_BagOfSendingHue; - set - { - m_BagOfSendingHue = value; + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + if (value > MaxCharges) + m_Charges = MaxCharges; + else if (value < 0) + m_Charges = 0; + else + m_Charges = value; - switch ( value ) - { - case BagOfSendingHue.Yellow: Hue = 0x8A5; break; - case BagOfSendingHue.Blue: Hue = 0x8AD; break; - case BagOfSendingHue.Red: Hue = 0x89B; break; - } - } - } + InvalidateProperties(); + } + } - [Constructible] - public BagOfSending() : this( RandomHue() ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Recharges + { + get => m_Recharges; + set + { + if (value > MaxRecharges) + m_Recharges = MaxRecharges; + else if (value < 0) + m_Recharges = 0; + else + m_Recharges = value; - [Constructible] - public BagOfSending( BagOfSendingHue hue ) : base( 0xE76 ) - { - Weight = 2.0; + InvalidateProperties(); + } + } - BagOfSendingHue = hue; + [CommandProperty(AccessLevel.GameMaster)] + public int MaxCharges => 30; - m_Charges = Utility.RandomMinMax( 3, 9 ); - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxRecharges => 255; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public string TranslocationItemName => "bag of sending"; - list.Add( 1060741, m_Charges.ToString() ); // charges: ~1_val~ - } + public static BagOfSendingHue RandomHue() + { + switch (Utility.Random(3)) + { + case 0: return BagOfSendingHue.Yellow; + case 1: return BagOfSendingHue.Blue; + default: return BagOfSendingHue.Red; + } + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - LabelTo( from, 1060741, m_Charges.ToString() ); // charges: ~1_val~ - } + list.Add(1060741, m_Charges.ToString()); // charges: ~1_val~ + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - if ( from.Alive ) - list.Add( new UseBagEntry( this, Charges > 0 && IsChildOf( from.Backpack ) ) ); - } + LabelTo(from, 1060741, m_Charges.ToString()); // charges: ~1_val~ + } - private class UseBagEntry : ContextMenuEntry - { - private BagOfSending m_Bag; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public UseBagEntry( BagOfSending bag, bool enabled ) : base( 6189 ) - { - m_Bag = bag; + if (from.Alive) + list.Add(new UseBagEntry(this, Charges > 0 && IsChildOf(from.Backpack))); + } - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } + public override void OnDoubleClick(Mobile from) + { + if (from.Region.IsPartOf(typeof(Jail))) + from.SendMessage("You may not do that in jail."); + else if (!IsChildOf(from.Backpack)) + MessageHelper.SendLocalizedMessageTo(this, from, 1062334, + 0x59); // The bag of sending must be in your backpack. + else if (Charges == 0) + MessageHelper.SendLocalizedMessageTo(this, from, 1042544, 0x59); // This item is out of charges. + else + from.Target = new SendTarget(this); + } - public override void OnClick() - { - if ( m_Bag.Deleted ) - return; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - Mobile from = Owner.From; + writer.WriteEncodedInt(1); // version - if ( from.CheckAlive() ) - m_Bag.OnDoubleClick( from ); - } - } + writer.WriteEncodedInt(m_Recharges); - public override void OnDoubleClick( Mobile from ) - { - if ( from.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - from.SendMessage( "You may not do that in jail." ); - } - else if ( !IsChildOf( from.Backpack ) ) - { - MessageHelper.SendLocalizedMessageTo(this, from, 1062334, 0x59); // The bag of sending must be in your backpack. - } - else if ( Charges == 0 ) - { - MessageHelper.SendLocalizedMessageTo( this, from, 1042544, 0x59 ); // This item is out of charges. - } - else - { - from.Target = new SendTarget( this ); - } - } + writer.WriteEncodedInt(m_Charges); + writer.WriteEncodedInt((int)m_BagOfSendingHue); + } - private class SendTarget : Target - { - private BagOfSending m_Bag; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public SendTarget( BagOfSending bag ) : base( -1, false, TargetFlags.None ) - { - m_Bag = bag; - } + int version = reader.ReadEncodedInt(); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Bag.Deleted ) - return; + switch (version) + { + case 1: + { + m_Recharges = reader.ReadEncodedInt(); + goto case 0; + } + case 0: + { + m_Charges = Math.Min(reader.ReadEncodedInt(), MaxCharges); + m_BagOfSendingHue = (BagOfSendingHue)reader.ReadEncodedInt(); + break; + } + } + } - if ( from.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - from.SendMessage( "You may not do that in jail." ); - } - else if ( !m_Bag.IsChildOf( from.Backpack ) ) - { - MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1062334, 0x59); // The bag of sending must be in your backpack. 1054107 is gone from client, using generic response - } - else if ( m_Bag.Charges == 0 ) - { - MessageHelper.SendLocalizedMessageTo( m_Bag, from, 1042544, 0x59 ); // This item is out of charges. - } - else if ( targeted is Item item ) - { - int reqCharges = (int)Math.Max( 1, Math.Ceiling( item.TotalWeight / 10.0 ) ); + private class UseBagEntry : ContextMenuEntry + { + private BagOfSending m_Bag; - if ( !item.IsChildOf( from.Backpack ) ) - { - MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1054152, 0x59); // You may only send items from your backpack to your bank box. - } - else if ( item is BagOfSending || item is Container ) - { - from.Send( new AsciiMessage( m_Bag.Serial, m_Bag.ItemID, MessageType.Regular, 0x3B2, 3, "", "You cannot send a container through the bag of sending." ) ); - } - else if ( item.LootType == LootType.Cursed ) - { - MessageHelper.SendLocalizedMessageTo( m_Bag, from, 1054108, 0x59 ); // The bag of sending rejects the cursed item. - } - else if ( !item.VerifyMove( from ) || item is Engines.Quests.QuestItem || item.Nontransferable ) - { - MessageHelper.SendLocalizedMessageTo( m_Bag, from, 1054109, 0x59 ); // The bag of sending rejects that item. - } - else if ( Spells.SpellHelper.IsDoomGauntlet( from.Map, from.Location ) ) - { - from.SendLocalizedMessage( 1062089 ); // You cannot use that here. - } - else if ( !from.BankBox.TryDropItem( from, item, false ) ) - { - MessageHelper.SendLocalizedMessageTo( m_Bag, from, 1054110, 0x59 ); // Your bank box is full. - } - else if ( Core.ML && reqCharges > m_Bag.Charges ) - { - from.SendLocalizedMessage( 1079932 ); //You don't have enough charges to send that much weight - } - else - { - m_Bag.Charges -= (Core.ML ? reqCharges : 1); + public UseBagEntry(BagOfSending bag, bool enabled) : base(6189) + { + m_Bag = bag; - MessageHelper.SendLocalizedMessageTo( m_Bag, from, 1054150, 0x59 ); // The item was placed in your bank box. - } - } - } - } + if (!enabled) + Flags |= CMEFlags.Disabled; + } - public BagOfSending( Serial serial ) : base( serial ) - { - } + public override void OnClick() + { + if (m_Bag.Deleted) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + Mobile from = Owner.From; - writer.WriteEncodedInt( (int) 1 ); // version + if (from.CheckAlive()) + m_Bag.OnDoubleClick(from); + } + } - writer.WriteEncodedInt( (int) m_Recharges ); + private class SendTarget : Target + { + private BagOfSending m_Bag; - writer.WriteEncodedInt( (int) m_Charges ); - writer.WriteEncodedInt( (int) m_BagOfSendingHue ); - } + public SendTarget(BagOfSending bag) : base(-1, false, TargetFlags.None) + { + m_Bag = bag; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Bag.Deleted) + return; - int version = reader.ReadEncodedInt(); + if (from.Region.IsPartOf(typeof(Jail))) + { + from.SendMessage("You may not do that in jail."); + } + else if (!m_Bag.IsChildOf(from.Backpack)) + { + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1062334, + 0x59); // The bag of sending must be in your backpack. 1054107 is gone from client, using generic response + } + else if (m_Bag.Charges == 0) + { + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1042544, 0x59); // This item is out of charges. + } + else if (targeted is Item item) + { + int reqCharges = (int)Math.Max(1, Math.Ceiling(item.TotalWeight / 10.0)); - switch ( version ) - { - case 1: - { - m_Recharges = reader.ReadEncodedInt(); - goto case 0; - } - case 0: - { - m_Charges = Math.Min( reader.ReadEncodedInt(), MaxCharges ); - m_BagOfSendingHue = (BagOfSendingHue) reader.ReadEncodedInt(); - break; - } - } - } - } -} + if (!item.IsChildOf(from.Backpack)) + { + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1054152, + 0x59); // You may only send items from your backpack to your bank box. + } + else if (item is BagOfSending || item is Container) + { + from.Send(new AsciiMessage(m_Bag.Serial, m_Bag.ItemID, MessageType.Regular, 0x3B2, 3, "", + "You cannot send a container through the bag of sending.")); + } + else if (item.LootType == LootType.Cursed) + { + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1054108, + 0x59); // The bag of sending rejects the cursed item. + } + else if (!item.VerifyMove(from) || item is QuestItem || item.Nontransferable) + { + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1054109, + 0x59); // The bag of sending rejects that item. + } + else if (SpellHelper.IsDoomGauntlet(from.Map, from.Location)) + { + from.SendLocalizedMessage(1062089); // You cannot use that here. + } + else if (!from.BankBox.TryDropItem(from, item, false)) + { + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1054110, 0x59); // Your bank box is full. + } + else if (Core.ML && reqCharges > m_Bag.Charges) + { + from.SendLocalizedMessage(1079932); //You don't have enough charges to send that much weight + } + else + { + m_Bag.Charges -= Core.ML ? reqCharges : 1; + + MessageHelper.SendLocalizedMessageTo(m_Bag, from, 1054150, + 0x59); // The item was placed in your bank box. + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Solen Items/BallOfSummoning.cs b/Scripts/Items/Special/Solen Items/BallOfSummoning.cs index 6bf2d01ae..cf562c1f8 100644 --- a/Scripts/Items/Special/Solen Items/BallOfSummoning.cs +++ b/Scripts/Items/Special/Solen Items/BallOfSummoning.cs @@ -1,460 +1,478 @@ using System; using System.Collections.Generic; -using Server.Mobiles; -using Server.Targeting; using Server.ContextMenus; +using Server.Engines.ConPVP; +using Server.Mobiles; using Server.Network; using Server.Regions; using Server.Spells; using Server.Spells.Ninjitsu; +using Server.Targeting; namespace Server.Items { - public class BallOfSummoning : Item, TranslocationItem - { - private int m_Charges; - private int m_Recharges; - private BaseCreature m_Pet; - - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set - { - if ( value > MaxCharges ) - m_Charges = MaxCharges; - else if ( value < 0 ) - m_Charges = 0; - else - m_Charges = value; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Recharges - { - get => m_Recharges; - set - { - if ( value > MaxRecharges ) - m_Recharges = MaxRecharges; - else if ( value < 0 ) - m_Recharges = 0; - else - m_Recharges = value; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxCharges => 20; - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxRecharges => 255; - - public string TranslocationItemName => "crystal ball of pet summoning"; - - [CommandProperty( AccessLevel.GameMaster )] - public BaseCreature Pet - { - get - { - if ( m_Pet != null && m_Pet.Deleted ) - { - m_Pet = null; - InternalUpdatePetName(); - } - - return m_Pet; - } - set - { - m_Pet = value; - InternalUpdatePetName(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string PetName { get; private set; } - - [Constructible] - public BallOfSummoning() : base( 0xE2E ) - { - Weight = 10.0; - Light = LightType.Circle150; - - m_Charges = Utility.RandomMinMax( 3, 9 ); - - PetName = ""; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1054131, m_Charges.ToString() + ( PetName.Length == 0 ? "\t " : "\t" + PetName ) ); // a crystal ball of pet summoning: [charges: ~1_charges~] : [linked pet: ~2_petName~] - } - - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, 1054131, m_Charges.ToString() + ( PetName.Length == 0 ? "\t " : "\t" + PetName ) ); // a crystal ball of pet summoning: [charges: ~1_charges~] : [linked pet: ~2_petName~] - } - - private delegate void BallCallback( Mobile from ); - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.Alive && RootParent == from ) - { - if ( Pet == null ) - { - list.Add( new BallEntry( LinkPet, 6180 ) ); - } - else - { - list.Add(new BallEntry(CastSummonPet, 6181 )); - list.Add( new BallEntry( UpdatePetName, 6183 ) ); - list.Add( new BallEntry( UnlinkPet, 6182 ) ); - } - } - } - - private class BallEntry : ContextMenuEntry - { - private BallCallback m_Callback; - - public BallEntry( BallCallback callback, int number ) : base( number, 2 ) - { - m_Callback = callback; - } - - public override void OnClick() - { - Mobile from = Owner.From; - - if ( from.CheckAlive() ) - m_Callback( from ); - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( RootParent != from ) // TODO: Previous implementation allowed use on ground, without house protection checks. What is the correct behavior? - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1042001 ); // That must be in your pack for you to use it. - return; - } - - AnimalFormContext animalContext = AnimalForm.GetContext( from ); - - if ( Core.ML && animalContext != null ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1080073 ); // You cannot use a Crystal Ball of Pet Summoning while in animal form. - return; - } - - if ( Pet == null ) - { - LinkPet( from ); - } - else - { - CastSummonPet( from ); - } - } - - public void LinkPet( Mobile from ) - { - BaseCreature pet = Pet; - - if ( Deleted || pet != null || RootParent != from ) - return; - - from.SendLocalizedMessage( 1054114 ); // Target your pet that you wish to link to this Crystal Ball of Pet Summoning. - from.Target = new PetLinkTarget( this ); - } - - private class PetLinkTarget : Target - { - private BallOfSummoning m_Ball; - - public PetLinkTarget( BallOfSummoning ball ) : base( -1, false, TargetFlags.None ) - { - m_Ball = ball; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Ball.Deleted || m_Ball.Pet != null ) - return; - - if ( m_Ball.RootParent != from ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1042001 ); // That must be in your pack for you to use it. - } - else if ( targeted is BaseCreature creature ) - { - if ( !creature.Controlled || creature.ControlMaster != from ) - { - MessageHelper.SendLocalizedMessageTo( m_Ball, from, 1054117, 0x59 ); // You may only link your own pets to a Crystal Ball of Pet Summoning. - } - else if ( !creature.IsBonded ) - { - MessageHelper.SendLocalizedMessageTo( m_Ball, from, 1054118, 0x59 ); // You must bond with your pet before it can be linked to a Crystal Ball of Pet Summoning. - } - else - { - MessageHelper.SendLocalizedMessageTo( m_Ball, from, 1054119, 0x59 ); // Your pet is now linked to this Crystal Ball of Pet Summoning. - - m_Ball.Pet = creature; - } - } - else if ( targeted == m_Ball ) - { - MessageHelper.SendLocalizedMessageTo( m_Ball, from, 1054115, 0x59 ); // The Crystal Ball of Pet Summoning cannot summon itself. - } - else - { - MessageHelper.SendLocalizedMessageTo( m_Ball, from, 1054116, 0x59 ); // Only pets can be linked to this Crystal Ball of Pet Summoning. - } - } - } - - public void CastSummonPet( Mobile from ) - { - BaseCreature pet = Pet; - - if ( Deleted || pet == null || RootParent != from ) - return; - - if ( Charges == 0 ) - { - SendLocalizedMessageTo( from, 1054122 ); // The Crystal Ball darkens. It must be charged before it can be used again. - } - else if ( pet is BaseMount mount && mount.Rider == from ) - { - MessageHelper.SendLocalizedMessageTo( this, from, 1054124, 0x36 ); // The Crystal Ball fills with a yellow mist. Why would you summon your pet while riding it? - } - else if ( pet.Map == Map.Internal && ( !pet.IsStabled || (from.Followers + pet.ControlSlots) > from.FollowersMax ) ) - { - MessageHelper.SendLocalizedMessageTo( this, from, 1054125, 0x5 ); // The Crystal Ball fills with a blue mist. Your pet is not responding to the summons. - } - else if ( ( !pet.Controlled || pet.ControlMaster != from ) && !from.Stabled.Contains( pet ) ) - { - MessageHelper.SendLocalizedMessageTo( this, from, 1054126, 0x8FD ); // The Crystal Ball fills with a grey mist. You are not the owner of the pet you are attempting to summon. - } - else if ( !pet.IsBonded ) - { - MessageHelper.SendLocalizedMessageTo( this, from, 1054127, 0x22 ); // The Crystal Ball fills with a red mist. You appear to have let your bond to your pet deteriorate. - } - else if ( from.Map == Map.Ilshenar || from.Region.IsPartOf( typeof( DungeonRegion ) ) || from.Region.IsPartOf( typeof( Jail ) ) || from.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - from.Send( new AsciiMessage( Serial, ItemID, MessageType.Regular, 0x22, 3, "", "You cannot summon your pet to this location." ) ); - } - else if ( Core.ML && from is PlayerMobile mobile && DateTime.UtcNow < mobile.LastPetBallTime.AddSeconds( 15.0 ) ) - { - MessageHelper.SendLocalizedMessageTo( this, mobile, 1080072, 0x22 ); // You must wait a few seconds before you can summon your pet. - } - else - { - if ( Core.ML ) - new PetSummoningSpell( this, from ).Cast(); - else - SummonPet( from ); - } - - } - - - public void SummonPet( Mobile from ) - { - BaseCreature pet = Pet; - - if ( pet == null ) - return; - - Charges--; - - if ( pet.IsStabled ) - { - pet.SetControlMaster( from ); - - if ( pet.Summoned ) - pet.SummonMaster = from; - - pet.ControlTarget = from; - pet.ControlOrder = OrderType.Follow; - - pet.IsStabled = false; - pet.StabledBy = null; - from.Stabled.Remove( pet ); - - if ( from is PlayerMobile mobile ) - mobile.AutoStabled.Remove( pet ); - } - - pet.MoveToWorld( from.Location, from.Map ); - - MessageHelper.SendLocalizedMessageTo( this, from, 1054128, 0x43 ); // The Crystal Ball fills with a green mist. Your pet has been summoned. - - if ( from is PlayerMobile playerMobile ) - { - playerMobile.LastPetBallTime = DateTime.UtcNow; - } - } - - public void UnlinkPet( Mobile from ) - { - if ( !Deleted && Pet != null && RootParent == from ) - { - Pet = null; - - SendLocalizedMessageTo( from, 1054120 ); // This crystal ball is no longer linked to a pet. - } - } - - public void UpdatePetName( Mobile from ) - { - InternalUpdatePetName(); - } - - private void InternalUpdatePetName() - { - BaseCreature pet = Pet; - - if ( pet == null ) - PetName = ""; - else - PetName = pet.Name; - - InvalidateProperties(); - } - - public BallOfSummoning( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 1 ); // version - - writer.WriteEncodedInt( (int) m_Recharges ); - - writer.WriteEncodedInt( (int) m_Charges ); - writer.Write( (Mobile) Pet ); - writer.Write( (string) PetName ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 1: - { - m_Recharges = reader.ReadEncodedInt(); - goto case 0; - } - case 0: - { - m_Charges = Math.Min( reader.ReadEncodedInt(), MaxCharges ); - Pet = (BaseCreature) reader.ReadMobile(); - PetName = reader.ReadString(); - break; - } - } - } - - private class PetSummoningSpell : Spell - { - private static SpellInfo m_Info = new SpellInfo( "Ball Of Summoning", "", 230 ); - - private BallOfSummoning m_Ball; - private Mobile m_Caster; - - public PetSummoningSpell( BallOfSummoning ball, Mobile caster ) - : base( caster, null, m_Info ) - { - m_Caster = caster; - m_Ball = ball; - } - - public override bool ClearHandsOnCast => false; - public override bool RevealOnCast => true; - - public override TimeSpan GetCastRecovery() - { - return TimeSpan.Zero; - } - - public override double CastDelayFastScalar => 0; - - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); - - public override int GetMana() - { - return 0; - } - - public override bool ConsumeReagents() - { - return true; - } - - public override bool CheckFizzle() - { - return true; - } - - private bool m_Stop; - - public void Stop() - { - m_Stop = true; - Disturb( DisturbType.Hurt, false, false ); - } - - public override bool CheckDisturb( DisturbType type, bool checkFirst, bool resistable ) - { - if ( type == DisturbType.EquipRequest || type == DisturbType.UseRequest/* || type == DisturbType.Hurt*/ ) - return false; - - return true; - } - - public override void DoHurtFizzle() - { - if ( !m_Stop ) - base.DoHurtFizzle(); - } - - public override void DoFizzle() - { - if ( !m_Stop ) - base.DoFizzle(); - } - - public override void OnDisturb( DisturbType type, bool message ) - { - if ( message && !m_Stop ) - Caster.SendLocalizedMessage( 1080074 ); // You have been disrupted while attempting to summon your pet! - } - - public override void OnCast() - { - m_Ball.SummonPet( m_Caster ); - - FinishSequence(); - } - } - } -} + public class BallOfSummoning : Item, TranslocationItem + { + private int m_Charges; + private BaseCreature m_Pet; + private int m_Recharges; + + [Constructible] + public BallOfSummoning() : base(0xE2E) + { + Weight = 10.0; + Light = LightType.Circle150; + + m_Charges = Utility.RandomMinMax(3, 9); + + PetName = ""; + } + + public BallOfSummoning(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public BaseCreature Pet + { + get + { + if (m_Pet != null && m_Pet.Deleted) + { + m_Pet = null; + InternalUpdatePetName(); + } + + return m_Pet; + } + set + { + m_Pet = value; + InternalUpdatePetName(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string PetName{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + if (value > MaxCharges) + m_Charges = MaxCharges; + else if (value < 0) + m_Charges = 0; + else + m_Charges = value; + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Recharges + { + get => m_Recharges; + set + { + if (value > MaxRecharges) + m_Recharges = MaxRecharges; + else if (value < 0) + m_Recharges = 0; + else + m_Recharges = value; + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxCharges => 20; + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxRecharges => 255; + + public string TranslocationItemName => "crystal ball of pet summoning"; + + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1054131, + m_Charges + (PetName.Length == 0 + ? "\t " + : "\t" + PetName)); // a crystal ball of pet summoning: [charges: ~1_charges~] : [linked pet: ~2_petName~] + } + + public override void OnSingleClick(Mobile from) + { + LabelTo(from, 1054131, + m_Charges + (PetName.Length == 0 + ? "\t " + : "\t" + PetName)); // a crystal ball of pet summoning: [charges: ~1_charges~] : [linked pet: ~2_petName~] + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.Alive && RootParent == from) + { + if (Pet == null) + { + list.Add(new BallEntry(LinkPet, 6180)); + } + else + { + list.Add(new BallEntry(CastSummonPet, 6181)); + list.Add(new BallEntry(UpdatePetName, 6183)); + list.Add(new BallEntry(UnlinkPet, 6182)); + } + } + } + + public override void OnDoubleClick(Mobile from) + { + if (RootParent != from + ) // TODO: Previous implementation allowed use on ground, without house protection checks. What is the correct behavior? + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1042001); // That must be in your pack for you to use it. + return; + } + + AnimalFormContext animalContext = AnimalForm.GetContext(from); + + if (Core.ML && animalContext != null) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1080073); // You cannot use a Crystal Ball of Pet Summoning while in animal form. + return; + } + + if (Pet == null) + LinkPet(from); + else + CastSummonPet(from); + } + + public void LinkPet(Mobile from) + { + BaseCreature pet = Pet; + + if (Deleted || pet != null || RootParent != from) + return; + + from.SendLocalizedMessage( + 1054114); // Target your pet that you wish to link to this Crystal Ball of Pet Summoning. + from.Target = new PetLinkTarget(this); + } + + public void CastSummonPet(Mobile from) + { + BaseCreature pet = Pet; + + if (Deleted || pet == null || RootParent != from) + return; + + if (Charges == 0) + { + SendLocalizedMessageTo(from, + 1054122); // The Crystal Ball darkens. It must be charged before it can be used again. + } + else if (pet is BaseMount mount && mount.Rider == from) + { + MessageHelper.SendLocalizedMessageTo(this, from, 1054124, + 0x36); // The Crystal Ball fills with a yellow mist. Why would you summon your pet while riding it? + } + else if (pet.Map == Map.Internal && (!pet.IsStabled || from.Followers + pet.ControlSlots > from.FollowersMax)) + { + MessageHelper.SendLocalizedMessageTo(this, from, 1054125, + 0x5); // The Crystal Ball fills with a blue mist. Your pet is not responding to the summons. + } + else if ((!pet.Controlled || pet.ControlMaster != from) && !from.Stabled.Contains(pet)) + { + MessageHelper.SendLocalizedMessageTo(this, from, 1054126, + 0x8FD); // The Crystal Ball fills with a grey mist. You are not the owner of the pet you are attempting to summon. + } + else if (!pet.IsBonded) + { + MessageHelper.SendLocalizedMessageTo(this, from, 1054127, + 0x22); // The Crystal Ball fills with a red mist. You appear to have let your bond to your pet deteriorate. + } + else if (from.Map == Map.Ilshenar || from.Region.IsPartOf(typeof(DungeonRegion)) || + from.Region.IsPartOf(typeof(Jail)) || from.Region.IsPartOf(typeof(SafeZone))) + { + from.Send(new AsciiMessage(Serial, ItemID, MessageType.Regular, 0x22, 3, "", + "You cannot summon your pet to this location.")); + } + else if (Core.ML && from is PlayerMobile mobile && DateTime.UtcNow < mobile.LastPetBallTime.AddSeconds(15.0)) + { + MessageHelper.SendLocalizedMessageTo(this, mobile, 1080072, + 0x22); // You must wait a few seconds before you can summon your pet. + } + else + { + if (Core.ML) + new PetSummoningSpell(this, from).Cast(); + else + SummonPet(from); + } + } + + + public void SummonPet(Mobile from) + { + BaseCreature pet = Pet; + + if (pet == null) + return; + + Charges--; + + if (pet.IsStabled) + { + pet.SetControlMaster(from); + + if (pet.Summoned) + pet.SummonMaster = from; + + pet.ControlTarget = from; + pet.ControlOrder = OrderType.Follow; + + pet.IsStabled = false; + pet.StabledBy = null; + from.Stabled.Remove(pet); + + if (from is PlayerMobile mobile) + mobile.AutoStabled.Remove(pet); + } + + pet.MoveToWorld(from.Location, from.Map); + + MessageHelper.SendLocalizedMessageTo(this, from, 1054128, + 0x43); // The Crystal Ball fills with a green mist. Your pet has been summoned. + + if (from is PlayerMobile playerMobile) playerMobile.LastPetBallTime = DateTime.UtcNow; + } + + public void UnlinkPet(Mobile from) + { + if (!Deleted && Pet != null && RootParent == from) + { + Pet = null; + + SendLocalizedMessageTo(from, 1054120); // This crystal ball is no longer linked to a pet. + } + } + + public void UpdatePetName(Mobile from) + { + InternalUpdatePetName(); + } + + private void InternalUpdatePetName() + { + BaseCreature pet = Pet; + + if (pet == null) + PetName = ""; + else + PetName = pet.Name; + + InvalidateProperties(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + + writer.WriteEncodedInt(m_Recharges); + + writer.WriteEncodedInt(m_Charges); + writer.Write(Pet); + writer.Write(PetName); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 1: + { + m_Recharges = reader.ReadEncodedInt(); + goto case 0; + } + case 0: + { + m_Charges = Math.Min(reader.ReadEncodedInt(), MaxCharges); + Pet = (BaseCreature)reader.ReadMobile(); + PetName = reader.ReadString(); + break; + } + } + } + + private delegate void BallCallback(Mobile from); + + private class BallEntry : ContextMenuEntry + { + private BallCallback m_Callback; + + public BallEntry(BallCallback callback, int number) : base(number, 2) + { + m_Callback = callback; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (from.CheckAlive()) + m_Callback(from); + } + } + + private class PetLinkTarget : Target + { + private BallOfSummoning m_Ball; + + public PetLinkTarget(BallOfSummoning ball) : base(-1, false, TargetFlags.None) + { + m_Ball = ball; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Ball.Deleted || m_Ball.Pet != null) + return; + + if (m_Ball.RootParent != from) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1042001); // That must be in your pack for you to use it. + } + else if (targeted is BaseCreature creature) + { + if (!creature.Controlled || creature.ControlMaster != from) + { + MessageHelper.SendLocalizedMessageTo(m_Ball, from, 1054117, + 0x59); // You may only link your own pets to a Crystal Ball of Pet Summoning. + } + else if (!creature.IsBonded) + { + MessageHelper.SendLocalizedMessageTo(m_Ball, from, 1054118, + 0x59); // You must bond with your pet before it can be linked to a Crystal Ball of Pet Summoning. + } + else + { + MessageHelper.SendLocalizedMessageTo(m_Ball, from, 1054119, + 0x59); // Your pet is now linked to this Crystal Ball of Pet Summoning. + + m_Ball.Pet = creature; + } + } + else if (targeted == m_Ball) + { + MessageHelper.SendLocalizedMessageTo(m_Ball, from, 1054115, + 0x59); // The Crystal Ball of Pet Summoning cannot summon itself. + } + else + { + MessageHelper.SendLocalizedMessageTo(m_Ball, from, 1054116, + 0x59); // Only pets can be linked to this Crystal Ball of Pet Summoning. + } + } + } + + private class PetSummoningSpell : Spell + { + private static SpellInfo m_Info = new SpellInfo("Ball Of Summoning", "", 230); + + private BallOfSummoning m_Ball; + private Mobile m_Caster; + + private bool m_Stop; + + public PetSummoningSpell(BallOfSummoning ball, Mobile caster) + : base(caster, null, m_Info) + { + m_Caster = caster; + m_Ball = ball; + } + + public override bool ClearHandsOnCast => false; + public override bool RevealOnCast => true; + + public override double CastDelayFastScalar => 0; + + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); + + public override TimeSpan GetCastRecovery() + { + return TimeSpan.Zero; + } + + public override int GetMana() + { + return 0; + } + + public override bool ConsumeReagents() + { + return true; + } + + public override bool CheckFizzle() + { + return true; + } + + public void Stop() + { + m_Stop = true; + Disturb(DisturbType.Hurt, false, false); + } + + public override bool CheckDisturb(DisturbType type, bool checkFirst, bool resistable) + { + if (type == DisturbType.EquipRequest || type == DisturbType.UseRequest /* || type == DisturbType.Hurt*/) + return false; + + return true; + } + + public override void DoHurtFizzle() + { + if (!m_Stop) + base.DoHurtFizzle(); + } + + public override void DoFizzle() + { + if (!m_Stop) + base.DoFizzle(); + } + + public override void OnDisturb(DisturbType type, bool message) + { + if (message && !m_Stop) + Caster.SendLocalizedMessage(1080074); // You have been disrupted while attempting to summon your pet! + } + + public override void OnCast() + { + m_Ball.SummonPet(m_Caster); + + FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Solen Items/BraceletOfBinding.cs b/Scripts/Items/Special/Solen Items/BraceletOfBinding.cs index a174ce1fb..0a431e1bb 100644 --- a/Scripts/Items/Special/Solen Items/BraceletOfBinding.cs +++ b/Scripts/Items/Special/Solen Items/BraceletOfBinding.cs @@ -1,466 +1,475 @@ using System; using System.Collections.Generic; using Server.ContextMenus; +using Server.Factions; +using Server.Misc; +using Server.Mobiles; using Server.Network; using Server.Prompts; -using Server.Targeting; +using Server.Regions; using Server.Spells; -using Server.Mobiles; +using Server.Targeting; namespace Server.Items { - public class BraceletOfBinding : BaseBracelet, TranslocationItem - { - private int m_Charges; - private int m_Recharges; - private string m_Inscription; - private BraceletOfBinding m_Bound; - private TransportTimer m_Timer; - - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set - { - if ( value > MaxCharges ) - m_Charges = MaxCharges; - else if ( value < 0 ) - m_Charges = 0; - else - m_Charges = value; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Recharges - { - get => m_Recharges; - set - { - if ( value > MaxRecharges ) - m_Recharges = MaxRecharges; - else if ( value < 0 ) - m_Recharges = 0; - else - m_Recharges = value; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxCharges => 20; - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxRecharges => 255; - - public string TranslocationItemName => "bracelet of binding"; - - [CommandProperty( AccessLevel.GameMaster )] - public string Inscription - { - get => m_Inscription; - set - { - m_Inscription = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public BraceletOfBinding Bound - { - get - { - if ( m_Bound != null && m_Bound.Deleted ) - m_Bound = null; - - return m_Bound; - } - set => m_Bound = value; - } - - [Constructible] - public BraceletOfBinding() : base( 0x1086 ) - { - Hue = 0x489; - Weight = 1.0; - - m_Inscription = ""; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - list.Add( 1054000, m_Charges.ToString() + ( m_Inscription.Length == 0 ? "\t " : " :\t" + m_Inscription ) ); // a bracelet of binding : ~1_val~ ~2_val~ - } - - public override void OnSingleClick( Mobile from ) - { - LabelTo( from, 1054000, m_Charges.ToString() + ( m_Inscription.Length == 0 ? "\t " : " :\t" + m_Inscription ) ); // a bracelet of binding : ~1_val~ ~2_val~ - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from.Alive && IsChildOf( from ) ) - { - BraceletOfBinding bound = Bound; - - list.Add( new BraceletEntry( Activate, 6170, bound != null ) ); - list.Add( new BraceletEntry( Search, 6171, bound != null ) ); - list.Add( new BraceletEntry( Bind, bound == null ? 6173 : 6174, true ) ); - list.Add( new BraceletEntry( Inscribe, 6175, true ) ); - } - } - - private delegate void BraceletCallback( Mobile from ); - - private class BraceletEntry : ContextMenuEntry - { - private BraceletCallback m_Callback; - - public BraceletEntry( BraceletCallback callback, int number, bool enabled ) : base( number ) - { - m_Callback = callback; - - if ( !enabled ) - Flags |= CMEFlags.Disabled; - } - - public override void OnClick() - { - Mobile from = Owner.From; - - if ( from.CheckAlive() ) - m_Callback( from ); - } - } - - public override void OnDoubleClick( Mobile from ) - { - BraceletOfBinding bound = Bound; - - if ( Bound == null ) - { - Bind( from ); - } - else - { - Activate( from ); - } - } - - public void Activate( Mobile from ) - { - BraceletOfBinding bound = Bound; - - if ( Deleted || bound == null ) - return; - - if ( !IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else if ( m_Timer != null ) - { - from.SendLocalizedMessage( 1054013 ); // The bracelet is already attempting contact. You decide to wait a moment. - } - else - { - from.PlaySound( 0xF9 ); - from.LocalOverheadMessage( MessageType.Regular, 0x5D, true, "* You concentrate on the bracelet to summon its power *" ); - - from.Frozen = true; - - m_Timer = new TransportTimer( this, from ); - m_Timer.Start(); - } - } - - private class TransportTimer : Timer - { - private BraceletOfBinding m_Bracelet; - private Mobile m_From; - - public TransportTimer( BraceletOfBinding bracelet, Mobile from ) : base( TimeSpan.FromSeconds( 2.0 ) ) - { - m_Bracelet = bracelet; - m_From = from; - } - - protected override void OnTick() - { - m_Bracelet.m_Timer = null; - m_From.Frozen = false; - - if ( m_Bracelet.Deleted || m_From.Deleted ) - return; - - if ( m_Bracelet.CheckUse( m_From, false ) ) - { - if ( m_Bracelet.Bound.RootParent is Mobile boundRoot ) - { - m_Bracelet.Charges--; - - BaseCreature.TeleportPets( m_From, boundRoot.Location, boundRoot.Map, true ); - - m_From.PlaySound( 0x1FC ); - m_From.MoveToWorld( boundRoot.Location, boundRoot.Map ); - m_From.PlaySound( 0x1FC ); - } - } - } - } - - public void Search( Mobile from ) - { - BraceletOfBinding bound = Bound; - - if ( Deleted || bound == null ) - return; - - if ( !IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else - { - CheckUse( from, true ); - } - } - - private bool CheckUse( Mobile from, bool successMessage ) - { - BraceletOfBinding bound = Bound; - - if ( bound == null ) - return false; - - Mobile boundRoot = bound.RootParent as Mobile; - - if ( Charges == 0 ) - { - from.SendLocalizedMessage( 1054005 ); // The bracelet glows black. It must be charged before it can be used again. - return false; - } - - if ( from.FindItemOnLayer( Layer.Bracelet ) != this ) - { - from.SendLocalizedMessage( 1054004 ); // You must equip the bracelet in order to use its power. - return false; - } - if ( boundRoot?.NetState == null || boundRoot.FindItemOnLayer( Layer.Bracelet ) != bound ) - { - from.SendLocalizedMessage( 1054006 ); // The bracelet emits a red glow. The bracelet's twin is not available for transport. - return false; - } - if ( !Core.AOS && from.Map != boundRoot.Map ) - { - from.SendLocalizedMessage( 1054014 ); // The bracelet glows black. The bracelet's target is on another facet. - return false; - } - if ( Factions.Sigil.ExistsOn( from ) ) - { - from.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } - if ( !SpellHelper.CheckTravel( from, TravelCheckType.RecallFrom ) ) - { - return false; - } - if ( !SpellHelper.CheckTravel( from, boundRoot.Map, boundRoot.Location, TravelCheckType.RecallTo ) ) - { - return false; - } - if ( boundRoot.Map == Map.Felucca && from is PlayerMobile mobile && mobile.Young ) - { - mobile.SendLocalizedMessage( 1049543 ); // You decide against traveling to Felucca while you are still young. - return false; - } - if ( from.Kills >= 5 && boundRoot.Map != Map.Felucca ) - { - from.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - return false; - } - if ( from.Criminal ) - { - from.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - return false; - } - if ( SpellHelper.CheckCombat( from ) ) - { - from.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - return false; - } - if ( Misc.WeightOverloading.IsOverloaded( from ) ) - { - from.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - return false; - } - if ( from.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - from.SendLocalizedMessage( 1114345, "", 0x35 ); // You'll need a better jailbreak plan than that! - return false; - } - if ( boundRoot.Region.IsPartOf( typeof( Regions.Jail ) ) ) - { - from.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - return false; - } - if ( successMessage ) - from.SendLocalizedMessage( 1054015 ); // The bracelet's twin is available for transport. - - return true; - } - - public void Bind( Mobile from ) - { - if ( Deleted ) - return; - - if ( !IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else - { - from.SendLocalizedMessage( 1054001 ); // Target the bracelet of binding you wish to bind this bracelet to. - from.Target = new BindTarget( this ); - } - } - - private class BindTarget : Target - { - private BraceletOfBinding m_Bracelet; - - public BindTarget( BraceletOfBinding bracelet ) : base( -1, false, TargetFlags.None ) - { - m_Bracelet = bracelet; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Bracelet.Deleted ) - return; - - if ( !m_Bracelet.IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else if ( targeted is BraceletOfBinding bindBracelet ) - { - if ( bindBracelet == m_Bracelet ) - { - from.SendLocalizedMessage( 1054012 ); // You cannot bind a bracelet of binding to itself! - } - else if ( !bindBracelet.IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else - { - from.SendLocalizedMessage( 1054003 ); // You bind the bracelet to its counterpart. The bracelets glow with power. - from.PlaySound( 0x1FA ); - - m_Bracelet.Bound = bindBracelet; - } - } - else - { - from.SendLocalizedMessage( 1054002 ); // You can only bind this bracelet to another bracelet of binding! - } - } - } - - public void Inscribe( Mobile from ) - { - if ( Deleted ) - return; - - if ( !IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else - { - from.SendLocalizedMessage( 1054009 ); // Enter the text to inscribe upon the bracelet : - from.Prompt = new InscribePrompt( this ); - } - } - - private class InscribePrompt : Prompt - { - private BraceletOfBinding m_Bracelet; - - public InscribePrompt( BraceletOfBinding bracelet ) - { - m_Bracelet = bracelet; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Bracelet.Deleted ) - return; - - if ( !m_Bracelet.IsChildOf( from ) ) - { - from.SendLocalizedMessage( 1042664 ); // You must have the object in your backpack to use it. - } - else - { - from.SendLocalizedMessage( 1054011 ); // You mark the bracelet with your inscription. - m_Bracelet.Inscription = text; - } - } - - public override void OnCancel( Mobile from ) - { - from.SendLocalizedMessage( 1054010 ); // You decide not to inscribe the bracelet at this time. - } - } - - public BraceletOfBinding( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( (int) 1 ); // version - - writer.WriteEncodedInt( (int) m_Recharges ); - - writer.WriteEncodedInt( (int) m_Charges ); - writer.Write( (string) m_Inscription ); - writer.Write( (Item) Bound ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - switch ( version ) - { - case 1: - { - m_Recharges = reader.ReadEncodedInt(); - goto case 0; - } - case 0: - { - m_Charges = Math.Min( reader.ReadEncodedInt(), MaxCharges ); - m_Inscription = reader.ReadString(); - Bound = (BraceletOfBinding) reader.ReadItem(); - break; - } - } - } - } -} + public class BraceletOfBinding : BaseBracelet, TranslocationItem + { + private BraceletOfBinding m_Bound; + private int m_Charges; + private string m_Inscription; + private int m_Recharges; + private TransportTimer m_Timer; + + [Constructible] + public BraceletOfBinding() : base(0x1086) + { + Hue = 0x489; + Weight = 1.0; + + m_Inscription = ""; + } + + public BraceletOfBinding(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Inscription + { + get => m_Inscription; + set + { + m_Inscription = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public BraceletOfBinding Bound + { + get + { + if (m_Bound != null && m_Bound.Deleted) + m_Bound = null; + + return m_Bound; + } + set => m_Bound = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + if (value > MaxCharges) + m_Charges = MaxCharges; + else if (value < 0) + m_Charges = 0; + else + m_Charges = value; + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Recharges + { + get => m_Recharges; + set + { + if (value > MaxRecharges) + m_Recharges = MaxRecharges; + else if (value < 0) + m_Recharges = 0; + else + m_Recharges = value; + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxCharges => 20; + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxRecharges => 255; + + public string TranslocationItemName => "bracelet of binding"; + + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1054000, + m_Charges + (m_Inscription.Length == 0 + ? "\t " + : " :\t" + m_Inscription)); // a bracelet of binding : ~1_val~ ~2_val~ + } + + public override void OnSingleClick(Mobile from) + { + LabelTo(from, 1054000, + m_Charges + (m_Inscription.Length == 0 + ? "\t " + : " :\t" + m_Inscription)); // a bracelet of binding : ~1_val~ ~2_val~ + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from.Alive && IsChildOf(from)) + { + BraceletOfBinding bound = Bound; + + list.Add(new BraceletEntry(Activate, 6170, bound != null)); + list.Add(new BraceletEntry(Search, 6171, bound != null)); + list.Add(new BraceletEntry(Bind, bound == null ? 6173 : 6174, true)); + list.Add(new BraceletEntry(Inscribe, 6175, true)); + } + } + + public override void OnDoubleClick(Mobile from) + { + BraceletOfBinding bound = Bound; + + if (Bound == null) + Bind(from); + else + Activate(from); + } + + public void Activate(Mobile from) + { + BraceletOfBinding bound = Bound; + + if (Deleted || bound == null) + return; + + if (!IsChildOf(from)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else if (m_Timer != null) + { + from.SendLocalizedMessage( + 1054013); // The bracelet is already attempting contact. You decide to wait a moment. + } + else + { + from.PlaySound(0xF9); + from.LocalOverheadMessage(MessageType.Regular, 0x5D, true, + "* You concentrate on the bracelet to summon its power *"); + + from.Frozen = true; + + m_Timer = new TransportTimer(this, from); + m_Timer.Start(); + } + } + + public void Search(Mobile from) + { + BraceletOfBinding bound = Bound; + + if (Deleted || bound == null) + return; + + if (!IsChildOf(from)) + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + else + CheckUse(from, true); + } + + private bool CheckUse(Mobile from, bool successMessage) + { + BraceletOfBinding bound = Bound; + + if (bound == null) + return false; + + Mobile boundRoot = bound.RootParent as Mobile; + + if (Charges == 0) + { + from.SendLocalizedMessage( + 1054005); // The bracelet glows black. It must be charged before it can be used again. + return false; + } + + if (from.FindItemOnLayer(Layer.Bracelet) != this) + { + from.SendLocalizedMessage(1054004); // You must equip the bracelet in order to use its power. + return false; + } + + if (boundRoot?.NetState == null || boundRoot.FindItemOnLayer(Layer.Bracelet) != bound) + { + from.SendLocalizedMessage( + 1054006); // The bracelet emits a red glow. The bracelet's twin is not available for transport. + return false; + } + + if (!Core.AOS && from.Map != boundRoot.Map) + { + from.SendLocalizedMessage(1054014); // The bracelet glows black. The bracelet's target is on another facet. + return false; + } + + if (Sigil.ExistsOn(from)) + { + from.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } + + if (!SpellHelper.CheckTravel(from, TravelCheckType.RecallFrom)) return false; + if (!SpellHelper.CheckTravel(from, boundRoot.Map, boundRoot.Location, TravelCheckType.RecallTo)) return false; + if (boundRoot.Map == Map.Felucca && from is PlayerMobile mobile && mobile.Young) + { + mobile.SendLocalizedMessage(1049543); // You decide against traveling to Felucca while you are still young. + return false; + } + + if (from.Kills >= 5 && boundRoot.Map != Map.Felucca) + { + from.SendLocalizedMessage(1019004); // You are not allowed to travel there. + return false; + } + + if (from.Criminal) + { + from.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + return false; + } + + if (SpellHelper.CheckCombat(from)) + { + from.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + return false; + } + + if (WeightOverloading.IsOverloaded(from)) + { + from.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + return false; + } + + if (from.Region.IsPartOf(typeof(Jail))) + { + from.SendLocalizedMessage(1114345, "", 0x35); // You'll need a better jailbreak plan than that! + return false; + } + + if (boundRoot.Region.IsPartOf(typeof(Jail))) + { + from.SendLocalizedMessage(1019004); // You are not allowed to travel there. + return false; + } + + if (successMessage) + from.SendLocalizedMessage(1054015); // The bracelet's twin is available for transport. + + return true; + } + + public void Bind(Mobile from) + { + if (Deleted) + return; + + if (!IsChildOf(from)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else + { + from.SendLocalizedMessage(1054001); // Target the bracelet of binding you wish to bind this bracelet to. + from.Target = new BindTarget(this); + } + } + + public void Inscribe(Mobile from) + { + if (Deleted) + return; + + if (!IsChildOf(from)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else + { + from.SendLocalizedMessage(1054009); // Enter the text to inscribe upon the bracelet : + from.Prompt = new InscribePrompt(this); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); // version + + writer.WriteEncodedInt(m_Recharges); + + writer.WriteEncodedInt(m_Charges); + writer.Write(m_Inscription); + writer.Write(Bound); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 1: + { + m_Recharges = reader.ReadEncodedInt(); + goto case 0; + } + case 0: + { + m_Charges = Math.Min(reader.ReadEncodedInt(), MaxCharges); + m_Inscription = reader.ReadString(); + Bound = (BraceletOfBinding)reader.ReadItem(); + break; + } + } + } + + private delegate void BraceletCallback(Mobile from); + + private class BraceletEntry : ContextMenuEntry + { + private BraceletCallback m_Callback; + + public BraceletEntry(BraceletCallback callback, int number, bool enabled) : base(number) + { + m_Callback = callback; + + if (!enabled) + Flags |= CMEFlags.Disabled; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (from.CheckAlive()) + m_Callback(from); + } + } + + private class TransportTimer : Timer + { + private BraceletOfBinding m_Bracelet; + private Mobile m_From; + + public TransportTimer(BraceletOfBinding bracelet, Mobile from) : base(TimeSpan.FromSeconds(2.0)) + { + m_Bracelet = bracelet; + m_From = from; + } + + protected override void OnTick() + { + m_Bracelet.m_Timer = null; + m_From.Frozen = false; + + if (m_Bracelet.Deleted || m_From.Deleted) + return; + + if (m_Bracelet.CheckUse(m_From, false)) + if (m_Bracelet.Bound.RootParent is Mobile boundRoot) + { + m_Bracelet.Charges--; + + BaseCreature.TeleportPets(m_From, boundRoot.Location, boundRoot.Map, true); + + m_From.PlaySound(0x1FC); + m_From.MoveToWorld(boundRoot.Location, boundRoot.Map); + m_From.PlaySound(0x1FC); + } + } + } + + private class BindTarget : Target + { + private BraceletOfBinding m_Bracelet; + + public BindTarget(BraceletOfBinding bracelet) : base(-1, false, TargetFlags.None) + { + m_Bracelet = bracelet; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Bracelet.Deleted) + return; + + if (!m_Bracelet.IsChildOf(from)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else if (targeted is BraceletOfBinding bindBracelet) + { + if (bindBracelet == m_Bracelet) + { + from.SendLocalizedMessage(1054012); // You cannot bind a bracelet of binding to itself! + } + else if (!bindBracelet.IsChildOf(from)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else + { + from.SendLocalizedMessage( + 1054003); // You bind the bracelet to its counterpart. The bracelets glow with power. + from.PlaySound(0x1FA); + + m_Bracelet.Bound = bindBracelet; + } + } + else + { + from.SendLocalizedMessage(1054002); // You can only bind this bracelet to another bracelet of binding! + } + } + } + + private class InscribePrompt : Prompt + { + private BraceletOfBinding m_Bracelet; + + public InscribePrompt(BraceletOfBinding bracelet) + { + m_Bracelet = bracelet; + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Bracelet.Deleted) + return; + + if (!m_Bracelet.IsChildOf(from)) + { + from.SendLocalizedMessage(1042664); // You must have the object in your backpack to use it. + } + else + { + from.SendLocalizedMessage(1054011); // You mark the bracelet with your inscription. + m_Bracelet.Inscription = text; + } + } + + public override void OnCancel(Mobile from) + { + from.SendLocalizedMessage(1054010); // You decide not to inscribe the bracelet at this time. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Solen Items/MessageHelper.cs b/Scripts/Items/Special/Solen Items/MessageHelper.cs index 6c39df648..09f79bf9d 100644 --- a/Scripts/Items/Special/Solen Items/MessageHelper.cs +++ b/Scripts/Items/Special/Solen Items/MessageHelper.cs @@ -2,21 +2,21 @@ using Server.Network; namespace Server { - public class MessageHelper - { - public static void SendLocalizedMessageTo( Item from, Mobile to, int number, int hue ) - { - SendLocalizedMessageTo( from, to, number, "", hue ); - } + public class MessageHelper + { + public static void SendLocalizedMessageTo(Item from, Mobile to, int number, int hue) + { + SendLocalizedMessageTo(from, to, number, "", hue); + } - public static void SendLocalizedMessageTo( Item from, Mobile to, int number, string args, int hue ) - { - to.Send( new MessageLocalized( from.Serial, from.ItemID, MessageType.Regular, hue, 3, number, "", args ) ); - } + public static void SendLocalizedMessageTo(Item from, Mobile to, int number, string args, int hue) + { + to.Send(new MessageLocalized(from.Serial, from.ItemID, MessageType.Regular, hue, 3, number, "", args)); + } - public static void SendMessageTo( Item from, Mobile to, string text, int hue ) - { - to.Send( new UnicodeMessage( from.Serial, from.ItemID, MessageType.Regular, hue, 3, "ENU", "", text ) ); - } - } -} + public static void SendMessageTo(Item from, Mobile to, string text, int hue) + { + to.Send(new UnicodeMessage(from.Serial, from.ItemID, MessageType.Regular, hue, 3, "ENU", "", text)); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Solen Items/PowderOfTranslocation.cs b/Scripts/Items/Special/Solen Items/PowderOfTranslocation.cs index 1f547d56f..614f94200 100644 --- a/Scripts/Items/Special/Solen Items/PowderOfTranslocation.cs +++ b/Scripts/Items/Special/Solen Items/PowderOfTranslocation.cs @@ -3,117 +3,113 @@ using Server.Targeting; namespace Server.Items { - public interface TranslocationItem - { - int Charges{ get; set; } - int Recharges{ get; set; } - int MaxCharges{ get; } - int MaxRecharges{ get; } - string TranslocationItemName{ get; } - } + public interface TranslocationItem + { + int Charges{ get; set; } + int Recharges{ get; set; } + int MaxCharges{ get; } + int MaxRecharges{ get; } + string TranslocationItemName{ get; } + } - public class PowderOfTranslocation : Item - { - [Constructible] - public PowderOfTranslocation() : this( 1 ) - { - } + public class PowderOfTranslocation : Item + { + [Constructible] + public PowderOfTranslocation() : this(1) + { + } - [Constructible] - public PowderOfTranslocation( int amount ) : base( 0x26B8 ) - { - Stackable = true; - Weight = 0.1; - Amount = amount; - } + [Constructible] + public PowderOfTranslocation(int amount) : base(0x26B8) + { + Stackable = true; + Weight = 0.1; + Amount = amount; + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - from.Target = new InternalTarget( this ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } + public PowderOfTranslocation(Serial serial) : base(serial) + { + } - private class InternalTarget : Target - { - private PowderOfTranslocation m_Powder; + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + from.Target = new InternalTarget(this); + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } - public InternalTarget( PowderOfTranslocation powder ) : base( -1, false, TargetFlags.None ) - { - m_Powder = powder; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Powder.Deleted ) - return; + writer.WriteEncodedInt(0); // version + } - if ( !from.InRange( m_Powder.GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - else if ( targeted is TranslocationItem transItem ) - { - if ( transItem.Charges >= transItem.MaxCharges ) - { - MessageHelper.SendLocalizedMessageTo( m_Powder, from, 1054137, 0x59 ); // This item cannot absorb any more powder of translocation. - } - else if ( transItem.Recharges >= transItem.MaxRecharges ) - { - MessageHelper.SendLocalizedMessageTo( m_Powder, from, 1054138, 0x59 ); // This item has been oversaturated with powder of translocation and can no longer be recharged. - } - else - { - if ( transItem.Charges + m_Powder.Amount > transItem.MaxCharges ) - { - int delta = transItem.MaxCharges - transItem.Charges; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Powder.Amount -= delta; - transItem.Charges = transItem.MaxCharges; - transItem.Recharges += delta; - } - else - { - transItem.Charges += m_Powder.Amount; - transItem.Recharges += m_Powder.Amount; - m_Powder.Delete(); - } + int version = reader.ReadEncodedInt(); + } - if ( transItem is Item item ) - { - // The ~1_translocationItem~ glows with green energy and absorbs magical power from the powder. - MessageHelper.SendLocalizedMessageTo( item, from, 1054139, transItem.TranslocationItemName, 0x43 ); - } - } - } - else - { - MessageHelper.SendLocalizedMessageTo( m_Powder, from, 1054140, 0x59 ); // Powder of translocation has no effect on this item. - } - } - } + private class InternalTarget : Target + { + private PowderOfTranslocation m_Powder; - public PowderOfTranslocation( Serial serial ) : base( serial ) - { - } + public InternalTarget(PowderOfTranslocation powder) : base(-1, false, TargetFlags.None) + { + m_Powder = powder; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Powder.Deleted) + return; - writer.WriteEncodedInt( (int) 0 ); // version - } + if (!from.InRange(m_Powder.GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + else if (targeted is TranslocationItem transItem) + { + if (transItem.Charges >= transItem.MaxCharges) + { + MessageHelper.SendLocalizedMessageTo(m_Powder, from, 1054137, + 0x59); // This item cannot absorb any more powder of translocation. + } + else if (transItem.Recharges >= transItem.MaxRecharges) + { + MessageHelper.SendLocalizedMessageTo(m_Powder, from, 1054138, + 0x59); // This item has been oversaturated with powder of translocation and can no longer be recharged. + } + else + { + if (transItem.Charges + m_Powder.Amount > transItem.MaxCharges) + { + int delta = transItem.MaxCharges - transItem.Charges; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + m_Powder.Amount -= delta; + transItem.Charges = transItem.MaxCharges; + transItem.Recharges += delta; + } + else + { + transItem.Charges += m_Powder.Amount; + transItem.Recharges += m_Powder.Amount; + m_Powder.Delete(); + } - int version = reader.ReadEncodedInt(); - } - } -} + if (transItem is Item item) + MessageHelper.SendLocalizedMessageTo(item, from, 1054139, transItem.TranslocationItemName, 0x43); + } + } + else + { + MessageHelper.SendLocalizedMessageTo(m_Powder, from, 1054140, + 0x59); // Powder of translocation has no effect on this item. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Solen Items/ZoogiFungus.cs b/Scripts/Items/Special/Solen Items/ZoogiFungus.cs index 2354b1376..9c2766101 100644 --- a/Scripts/Items/Special/Solen Items/ZoogiFungus.cs +++ b/Scripts/Items/Special/Solen Items/ZoogiFungus.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ZoogiFungus : Item, ICommodity - { - int ICommodity.DescriptionNumber => LabelNumber; - bool ICommodity.IsDeedable => (Core.ML); + public class ZoogiFungus : Item, ICommodity + { + [Constructible] + public ZoogiFungus() : this(1) + { + } - [Constructible] - public ZoogiFungus() : this( 1 ) - { - } + [Constructible] + public ZoogiFungus(int amount) : base(0x26B7) + { + Stackable = true; + Weight = 0.1; + Amount = amount; + } - [Constructible] - public ZoogiFungus( int amount ) : base( 0x26B7 ) - { - Stackable = true; - Weight = 0.1; - Amount = amount; - } + public ZoogiFungus(Serial serial) : base(serial) + { + } - public ZoogiFungus( Serial serial ) : base( serial ) - { - } + int ICommodity.DescriptionNumber => LabelNumber; + bool ICommodity.IsDeedable => Core.ML; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( (int) 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Special/SoulStone.cs b/Scripts/Items/Special/SoulStone.cs index 8425d8c08..79127461c 100644 --- a/Scripts/Items/Special/SoulStone.cs +++ b/Scripts/Items/Special/SoulStone.cs @@ -1,1012 +1,1058 @@ using System; -using Server.Gumps; -using Server.Network; using Server.Accounting; using Server.Engines.VeteranRewards; -using Server.Multis; +using Server.Factions; +using Server.Gumps; using Server.Mobiles; +using Server.Multis; +using Server.Network; namespace Server.Items { - public class SoulStone : Item, ISecurable - { - public override int LabelNumber => 1030899; // soulstone - - private int m_ActiveItemID; - private int m_InactiveItemID; - - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual int ActiveItemID - { - get => m_ActiveItemID; - set - { - m_ActiveItemID = value; - - if ( !IsEmpty ) - ItemID = m_ActiveItemID; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual int InactiveItemID - { - get => m_InactiveItemID; - set - { - m_InactiveItemID = value; - - if ( IsEmpty ) - ItemID = m_InactiveItemID; - } - } - - private string m_LastUserName; - private DateTime m_NextUse; // TODO: unused, it's here not to break serialize/deserialize - - private SkillName m_Skill; - private double m_SkillValue; - - [CommandProperty( AccessLevel.GameMaster )] - public string Account { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string LastUserName - { - get => m_LastUserName; - set{ m_LastUserName = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill - { - get => m_Skill; - set{ m_Skill = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public double SkillValue - { - get => m_SkillValue; - set - { - m_SkillValue = value; - - if ( !IsEmpty ) - ItemID = m_ActiveItemID; - else - ItemID = m_InactiveItemID; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsEmpty => m_SkillValue <= 0.0; - - [Constructible] - public SoulStone() : this( null ) - { - } - - [Constructible] - public SoulStone( string account ) - : this( account, 0x2A93, 0x2A94 ) - { - } - - public SoulStone( string account, int itemID ) - : this( account, itemID, itemID ) - { - } - - public SoulStone( string account, int inactiveItemID, int activeItemID ) : base( inactiveItemID ) - { - Light = LightType.Circle300; - LootType = LootType.Blessed; - - m_InactiveItemID = inactiveItemID; - m_ActiveItemID = activeItemID; - - Account = account; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( !IsEmpty ) - list.Add( 1070721, "#{0}\t{1:0.0}", AosSkillBonuses.GetLabel( Skill ), SkillValue ); // Skill stored: ~1_skillname~ ~2_skillamount~ - - string name = LastUserName; - - if ( name == null ) - name = $"#{1074235}"; // Unknown - - list.Add( 1041602, "{0}", name ); // Owner: ~1_val~ - } - - private static bool CheckCombat( Mobile m, TimeSpan time ) - { - for ( int i = 0; i < m.Aggressed.Count; ++i ) - { - AggressorInfo info = m.Aggressed[i]; - - if ( DateTime.UtcNow - info.LastCombatTime < time ) - return true; - } - - return false; - } - - protected virtual bool CheckUse( Mobile from ) - { - DateTime now = DateTime.UtcNow; - - PlayerMobile pm = from as PlayerMobile; - - if ( Deleted || !IsAccessibleTo( from ) ) - { - return false; - } - - if ( from.Map != Map || !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return false; - } - if ( Account != null && ( !(from.Account is Account) || from.Account.Username != Account ) ) - { - from.SendLocalizedMessage( 1070714 ); // This is an Account Bound Soulstone, and your character is not bound to it. You cannot use this Soulstone. - return false; - } - if ( CheckCombat( from, TimeSpan.FromMinutes( 2.0 ) ) ) - { - from.SendLocalizedMessage( 1070727 ); // You must wait two minutes after engaging in combat before you can use a Soulstone. - return false; - } - if ( from.Criminal ) - { - from.SendLocalizedMessage( 1070728 ); // You must wait two minutes after committing a criminal act before you can use a Soulstone. - return false; - } - if ( from.Region.GetLogoutDelay( from ) > TimeSpan.Zero ) - { - from.SendLocalizedMessage( 1070729 ); // In order to use your Soulstone, you must be in a safe log-out location. - return false; - } - if ( !from.Alive ) - { - from.SendLocalizedMessage( 1070730 ); // You may not use a Soulstone while your character is dead. - return false; - } - if ( Factions.Sigil.ExistsOn( from ) ) - { - from.SendLocalizedMessage( 1070731 ); // You may not use a Soulstone while your character has a faction town sigil. - return false; - } - if ( from.Spell != null && from.Spell.IsCasting ) - { - from.SendLocalizedMessage( 1070733 ); // You may not use a Soulstone while your character is casting a spell. - return false; - } - if ( from.Poisoned ) - { - from.SendLocalizedMessage( 1070734 ); // You may not use a Soulstone while your character is poisoned. - return false; - } - if ( from.Paralyzed ) - { - from.SendLocalizedMessage( 1070735 ); // You may not use a Soulstone while your character is paralyzed. - return false; - } - - #region Scroll of Alacrity - if ( pm.AcceleratedStart > DateTime.UtcNow ) - { - from.SendLocalizedMessage(1078115); // You may not use a soulstone while your character is under the effects of a Scroll of Alacrity. - return false; - } - #endregion - - return true; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( !CheckUse( from ) ) - return; - - from.CloseGump( typeof( SelectSkillGump ) ); - from.CloseGump( typeof( ConfirmSkillGump ) ); - from.CloseGump( typeof( ConfirmTransferGump ) ); - from.CloseGump( typeof( ConfirmRemovalGump ) ); - from.CloseGump( typeof( ErrorGump ) ); - - if ( IsEmpty ) - from.SendGump( new SelectSkillGump( this, from ) ); - else - from.SendGump( new ConfirmTransferGump( this, from ) ); - } - - private class SelectSkillGump : Gump - { - private SoulStone m_Stone; - - public SelectSkillGump( SoulStone stone, Mobile from ) : base( 50, 50 ) - { - m_Stone = stone; - - AddPage( 0 ); - - AddBackground( 0, 0, 520, 440, 0x13BE ); - - AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 360, 0xA40 ); - AddImageTiled( 10, 410, 500, 20, 0xA40 ); - - AddAlphaRegion( 10, 10, 500, 420 ); - - AddHtmlLocalized( 10, 12, 500, 20, 1061087, 0x7FFF, false, false ); // Which skill do you wish to transfer to the Soulstone? - - AddButton( 10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 412, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - - for ( int i = 0, n = 0; i < from.Skills.Length; i++ ) - { - Skill skill = from.Skills[i]; - - if ( skill.Base > 0.0 ) - { - int p = n % 30; - - if ( p == 0 ) - { - int page = n / 30; - - if ( page > 0 ) - { - AddButton( 260, 380, 0xFA5, 0xFA6, 0, GumpButtonType.Page, page + 1 ); - AddHtmlLocalized( 305, 382, 200, 20, 1011066, 0x7FFF, false, false ); // Next page - } - - AddPage( page + 1 ); - - if ( page > 0 ) - { - AddButton( 10, 380, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page ); - AddHtmlLocalized( 55, 382, 200, 20, 1011067, 0x7FFF, false, false ); // Previous page - } - } - - int x = ( p % 2 == 0 ) ? 10 : 260; - int y = ( p / 2 ) * 20 + 40; - - AddButton( x, y, 0xFA5, 0xFA6, i + 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( x + 45, y + 2, 200, 20, AosSkillBonuses.GetLabel( skill.SkillName ), 0x7FFF, false, false ); - - n++; - } - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 || !m_Stone.IsEmpty ) - return; - - Mobile from = sender.Mobile; - - int iSkill = info.ButtonID - 1; - if ( iSkill < 0 || iSkill >= from.Skills.Length ) - return; + public class SoulStone : Item, ISecurable + { + private int m_ActiveItemID; + private int m_InactiveItemID; + + private string m_LastUserName; + private DateTime m_NextUse; // TODO: unused, it's here not to break serialize/deserialize + + private SkillName m_Skill; + private double m_SkillValue; + + [Constructible] + public SoulStone() : this(null) + { + } + + [Constructible] + public SoulStone(string account) + : this(account, 0x2A93, 0x2A94) + { + } + + public SoulStone(string account, int itemID) + : this(account, itemID, itemID) + { + } + + public SoulStone(string account, int inactiveItemID, int activeItemID) : base(inactiveItemID) + { + Light = LightType.Circle300; + LootType = LootType.Blessed; + + m_InactiveItemID = inactiveItemID; + m_ActiveItemID = activeItemID; + + Account = account; + } + + public SoulStone(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1030899; // soulstone + + [CommandProperty(AccessLevel.GameMaster)] + public virtual int ActiveItemID + { + get => m_ActiveItemID; + set + { + m_ActiveItemID = value; + + if (!IsEmpty) + ItemID = m_ActiveItemID; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public virtual int InactiveItemID + { + get => m_InactiveItemID; + set + { + m_InactiveItemID = value; + + if (IsEmpty) + ItemID = m_InactiveItemID; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Account{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string LastUserName + { + get => m_LastUserName; + set + { + m_LastUserName = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill + { + get => m_Skill; + set + { + m_Skill = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public double SkillValue + { + get => m_SkillValue; + set + { + m_SkillValue = value; + + if (!IsEmpty) + ItemID = m_ActiveItemID; + else + ItemID = m_InactiveItemID; + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsEmpty => m_SkillValue <= 0.0; + + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (!IsEmpty) + list.Add(1070721, "#{0}\t{1:0.0}", AosSkillBonuses.GetLabel(Skill), + SkillValue); // Skill stored: ~1_skillname~ ~2_skillamount~ + + string name = LastUserName; + + if (name == null) + name = $"#{1074235}"; // Unknown + + list.Add(1041602, "{0}", name); // Owner: ~1_val~ + } + + private static bool CheckCombat(Mobile m, TimeSpan time) + { + for (int i = 0; i < m.Aggressed.Count; ++i) + { + AggressorInfo info = m.Aggressed[i]; + + if (DateTime.UtcNow - info.LastCombatTime < time) + return true; + } + + return false; + } + + protected virtual bool CheckUse(Mobile from) + { + DateTime now = DateTime.UtcNow; + + PlayerMobile pm = from as PlayerMobile; + + if (Deleted || !IsAccessibleTo(from)) return false; + + if (from.Map != Map || !from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return false; + } + + if (Account != null && (!(from.Account is Account) || from.Account.Username != Account)) + { + from.SendLocalizedMessage( + 1070714); // This is an Account Bound Soulstone, and your character is not bound to it. You cannot use this Soulstone. + return false; + } + + if (CheckCombat(from, TimeSpan.FromMinutes(2.0))) + { + from.SendLocalizedMessage( + 1070727); // You must wait two minutes after engaging in combat before you can use a Soulstone. + return false; + } + + if (from.Criminal) + { + from.SendLocalizedMessage( + 1070728); // You must wait two minutes after committing a criminal act before you can use a Soulstone. + return false; + } + + if (from.Region.GetLogoutDelay(from) > TimeSpan.Zero) + { + from.SendLocalizedMessage( + 1070729); // In order to use your Soulstone, you must be in a safe log-out location. + return false; + } + + if (!from.Alive) + { + from.SendLocalizedMessage(1070730); // You may not use a Soulstone while your character is dead. + return false; + } + + if (Sigil.ExistsOn(from)) + { + from.SendLocalizedMessage( + 1070731); // You may not use a Soulstone while your character has a faction town sigil. + return false; + } + + if (from.Spell != null && from.Spell.IsCasting) + { + from.SendLocalizedMessage(1070733); // You may not use a Soulstone while your character is casting a spell. + return false; + } + + if (from.Poisoned) + { + from.SendLocalizedMessage(1070734); // You may not use a Soulstone while your character is poisoned. + return false; + } + + if (from.Paralyzed) + { + from.SendLocalizedMessage(1070735); // You may not use a Soulstone while your character is paralyzed. + return false; + } + + #region Scroll of Alacrity + + if (pm.AcceleratedStart > DateTime.UtcNow) + { + from.SendLocalizedMessage( + 1078115); // You may not use a soulstone while your character is under the effects of a Scroll of Alacrity. + return false; + } + + #endregion + + return true; + } + + public override void OnDoubleClick(Mobile from) + { + if (!CheckUse(from)) + return; + + from.CloseGump(typeof(SelectSkillGump)); + from.CloseGump(typeof(ConfirmSkillGump)); + from.CloseGump(typeof(ConfirmTransferGump)); + from.CloseGump(typeof(ConfirmRemovalGump)); + from.CloseGump(typeof(ErrorGump)); + + if (IsEmpty) + from.SendGump(new SelectSkillGump(this, from)); + else + from.SendGump(new ConfirmTransferGump(this, from)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(3); // version + + //version 3 + writer.Write(m_LastUserName); + + //version 2 + writer.Write((int)Level); + + writer.Write(m_ActiveItemID); + writer.Write(m_InactiveItemID); + + writer.Write(Account); + writer.Write(m_NextUse); //TODO: delete it in a harmless way + + writer.WriteEncodedInt((int)m_Skill); + writer.Write(m_SkillValue); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 3: + { + m_LastUserName = reader.ReadString(); + goto case 2; + } + case 2: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 1; + } + case 1: + { + m_ActiveItemID = reader.ReadInt(); + m_InactiveItemID = reader.ReadInt(); + + goto case 0; + } + case 0: + { + Account = reader.ReadString(); + m_NextUse = reader.ReadDateTime(); //TODO: delete it in a harmless way + + m_Skill = (SkillName)reader.ReadEncodedInt(); + m_SkillValue = reader.ReadDouble(); + break; + } + } + + if (version == 0) + { + m_ActiveItemID = 0x2A94; + m_InactiveItemID = 0x2A93; + } + } + + private class SelectSkillGump : Gump + { + private SoulStone m_Stone; + + public SelectSkillGump(SoulStone stone, Mobile from) : base(50, 50) + { + m_Stone = stone; + + AddPage(0); + + AddBackground(0, 0, 520, 440, 0x13BE); + + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 360, 0xA40); + AddImageTiled(10, 410, 500, 20, 0xA40); + + AddAlphaRegion(10, 10, 500, 420); + + AddHtmlLocalized(10, 12, 500, 20, 1061087, 0x7FFF, false, + false); // Which skill do you wish to transfer to the Soulstone? + + AddButton(10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 412, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + + for (int i = 0, n = 0; i < from.Skills.Length; i++) + { + Skill skill = from.Skills[i]; + + if (skill.Base > 0.0) + { + int p = n % 30; + + if (p == 0) + { + int page = n / 30; + + if (page > 0) + { + AddButton(260, 380, 0xFA5, 0xFA6, 0, GumpButtonType.Page, page + 1); + AddHtmlLocalized(305, 382, 200, 20, 1011066, 0x7FFF, false, false); // Next page + } + + AddPage(page + 1); + + if (page > 0) + { + AddButton(10, 380, 0xFAE, 0xFAF, 0, GumpButtonType.Page, page); + AddHtmlLocalized(55, 382, 200, 20, 1011067, 0x7FFF, false, false); // Previous page + } + } + + int x = p % 2 == 0 ? 10 : 260; + int y = p / 2 * 20 + 40; + + AddButton(x, y, 0xFA5, 0xFA6, i + 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(x + 45, y + 2, 200, 20, AosSkillBonuses.GetLabel(skill.SkillName), 0x7FFF, false, + false); + + n++; + } + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0 || !m_Stone.IsEmpty) + return; + + Mobile from = sender.Mobile; + + int iSkill = info.ButtonID - 1; + if (iSkill < 0 || iSkill >= from.Skills.Length) + return; + + Skill skill = from.Skills[iSkill]; + if (skill.Base <= 0.0) + return; + + if (!m_Stone.CheckUse(from)) + return; + + from.SendGump(new ConfirmSkillGump(m_Stone, skill)); + } + } - Skill skill = from.Skills[iSkill]; - if ( skill.Base <= 0.0 ) - return; + private class ConfirmSkillGump : Gump + { + private Skill m_Skill; + private SoulStone m_Stone; - if ( !m_Stone.CheckUse( from ) ) - return; + public ConfirmSkillGump(SoulStone stone, Skill skill) : base(50, 50) + { + m_Stone = stone; + m_Skill = skill; - from.SendGump( new ConfirmSkillGump( m_Stone, skill ) ); - } - } + AddBackground(0, 0, 520, 440, 0x13BE); - private class ConfirmSkillGump : Gump - { - private SoulStone m_Stone; - private Skill m_Skill; + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 360, 0xA40); + AddImageTiled(10, 410, 500, 20, 0xA40); - public ConfirmSkillGump( SoulStone stone, Skill skill ) : base( 50, 50 ) - { - m_Stone = stone; - m_Skill = skill; + AddAlphaRegion(10, 10, 500, 420); - AddBackground( 0, 0, 520, 440, 0x13BE ); + AddHtmlLocalized(10, 12, 500, 20, 1070709, 0x7FFF, false, + false); //
Confirm Soulstone Transfer
- AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 360, 0xA40 ); - AddImageTiled( 10, 410, 500, 20, 0xA40 ); + /*
Soulstone

+ * You are using a Soulstone. This powerful artifact allows you to remove skill points + * from your character and store them in the stone for later retrieval. In order to use + * the stone, you must make sure your Skill Lock for the indicated skill is pointed downward. + * Click the "Skills" button on your Paperdoll to access the Skill List, and double-check + * your skill lock.

+ * + * Once you activate the stone, all skill points in the indicated skill will be removed from + * your character. These skill points can later be retrieved. IMPORTANT: When retrieving + * skill points from a Soulstone, the Soulstone WILL REPLACE any existing skill points + * already on your character!

+ * + * This is an Account Bound Soulstone. Skill pointsstored inside can be retrieved by any + * character on the same account as the character who placed them into the stone. + */ + AddHtmlLocalized(10, 42, 500, 110, 1061067, 0x7FFF, false, true); - AddAlphaRegion( 10, 10, 500, 420 ); + AddHtmlLocalized(10, 200, 390, 20, 1062297, 0x7FFF, false, false); // Skill Chosen: + AddHtmlLocalized(210, 200, 390, 20, AosSkillBonuses.GetLabel(skill.SkillName), 0x7FFF, false, false); - AddHtmlLocalized( 10, 12, 500, 20, 1070709, 0x7FFF, false, false ); //
Confirm Soulstone Transfer
+ AddHtmlLocalized(10, 220, 390, 20, 1062298, 0x7FFF, false, false); // Current Value: + AddLabel(210, 220, 0x481, skill.Base.ToString("0.0")); + + AddHtmlLocalized(10, 240, 390, 20, 1062299, 0x7FFF, false, false); // Current Cap: + AddLabel(210, 240, 0x481, skill.Cap.ToString("0.0")); + + AddHtmlLocalized(10, 260, 390, 20, 1062300, 0x7FFF, false, false); // New Value: + AddLabel(210, 260, 0x481, "0.0"); + + AddButton(10, 360, 0xFA5, 0xFA6, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 362, 450, 20, 1070720, 0x7FFF, false, + false); // Activate the stone. I am ready to transfer the skill points to it. + + AddButton(10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 382, 450, 20, 1062279, 0x7FFF, false, false); // No, let me make another selection. + + AddButton(10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 412, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0 || !m_Stone.IsEmpty) + return; - /*
Soulstone

- * You are using a Soulstone. This powerful artifact allows you to remove skill points - * from your character and store them in the stone for later retrieval. In order to use - * the stone, you must make sure your Skill Lock for the indicated skill is pointed downward. - * Click the "Skills" button on your Paperdoll to access the Skill List, and double-check - * your skill lock.

- * - * Once you activate the stone, all skill points in the indicated skill will be removed from - * your character. These skill points can later be retrieved. IMPORTANT: When retrieving - * skill points from a Soulstone, the Soulstone WILL REPLACE any existing skill points - * already on your character!

- * - * This is an Account Bound Soulstone. Skill pointsstored inside can be retrieved by any - * character on the same account as the character who placed them into the stone. - */ - AddHtmlLocalized( 10, 42, 500, 110, 1061067, 0x7FFF, false, true ); + Mobile from = sender.Mobile; - AddHtmlLocalized( 10, 200, 390, 20, 1062297, 0x7FFF, false, false ); // Skill Chosen: - AddHtmlLocalized( 210, 200, 390, 20, AosSkillBonuses.GetLabel( skill.SkillName ), 0x7FFF, false, false ); + if (!m_Stone.CheckUse(from)) + return; - AddHtmlLocalized( 10, 220, 390, 20, 1062298, 0x7FFF, false, false ); // Current Value: - AddLabel( 210, 220, 0x481, skill.Base.ToString( "0.0" ) ); + if (info.ButtonID == 1) // Is asking for another selection + { + from.SendGump(new SelectSkillGump(m_Stone, from)); + return; + } - AddHtmlLocalized( 10, 240, 390, 20, 1062299, 0x7FFF, false, false ); // Current Cap: - AddLabel( 210, 240, 0x481, skill.Cap.ToString( "0.0" ) ); + if (m_Skill.Base <= 0.0) + return; - AddHtmlLocalized( 10, 260, 390, 20, 1062300, 0x7FFF, false, false ); // New Value: - AddLabel( 210, 260, 0x481, "0.0" ); + if (m_Skill.Lock != SkillLock.Down) + { + //
Unable to Transfer Selected Skill to Soulstone
- AddButton( 10, 360, 0xFA5, 0xFA6, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 362, 450, 20, 1070720, 0x7FFF, false, false ); // Activate the stone. I am ready to transfer the skill points to it. + /* You cannot transfer the selected skill to the Soulstone at this time. The selected + * skill may be locked or set to raise in your skill menu. Click on "Skills" in your + * paperdoll menu to check your raise/locked/lower settings and your total skills. + * Make any needed adjustments, then click "Continue". If you do not wish to transfer + * the selected skill at this time, click "Cancel". + */ - AddButton( 10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 382, 450, 20, 1062279, 0x7FFF, false, false ); // No, let me make another selection. + from.SendGump(new ErrorGump(m_Stone, 1070710, 1070711)); + return; + } - AddButton( 10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 412, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - } + m_Stone.Skill = m_Skill.SkillName; + m_Stone.SkillValue = m_Skill.Base; + + m_Skill.Base = 0.0; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 || !m_Stone.IsEmpty ) - return; + from.SendLocalizedMessage( + 1070712); // You have successfully transferred your skill points into the Soulstone. + + m_Stone.LastUserName = from.Name; - Mobile from = sender.Mobile; + Effects.SendLocationParticles(EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration), 0, 0, + 0, 0, 0, 5060, 0); + Effects.PlaySound(from.Location, from.Map, 0x243); - if ( !m_Stone.CheckUse( from ) ) - return; + Effects.SendMovingParticles( + new Entity(Server.Serial.Zero, new Point3D(from.X - 6, from.Y - 6, from.Z + 15), from.Map), from, 0x36D4, + 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + + Effects.SendTargetParticles(from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); + } + } + + private class ConfirmTransferGump : Gump + { + private SoulStone m_Stone; + + public ConfirmTransferGump(SoulStone stone, Mobile from) : base(50, 50) + { + m_Stone = stone; + + AddBackground(0, 0, 520, 440, 0x13BE); + + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 360, 0xA40); + AddImageTiled(10, 410, 500, 20, 0xA40); - if ( info.ButtonID == 1 ) // Is asking for another selection - { - from.SendGump( new SelectSkillGump( m_Stone, from ) ); - return; - } + AddAlphaRegion(10, 10, 500, 420); - if ( m_Skill.Base <= 0.0 ) - return; + AddHtmlLocalized(10, 12, 500, 20, 1070709, 0x7FFF, false, + false); //
Confirm Soulstone Transfer
- if ( m_Skill.Lock != SkillLock.Down ) - { - //
Unable to Transfer Selected Skill to Soulstone
+ /*
Soulstone

+ * You are using a Soulstone. This powerful artifact allows you to remove skill points + * from your character and store them in the stone for later retrieval. In order to use + * the stone, you must make sure your Skill Lock for the indicated skill is pointed downward. + * Click the "Skills" button on your Paperdoll to access the Skill List, and double-check + * your skill lock.

+ * + * Once you activate the stone, all skill points in the indicated skill will be removed from + * your character. These skill points can later be retrieved. IMPORTANT: When retrieving + * skill points from a Soulstone, the Soulstone WILL REPLACE any existing skill points + * already on your character!

+ * + * This is an Account Bound Soulstone. Skill pointsstored inside can be retrieved by any + * character on the same account as the character who placed them into the stone. + */ + AddHtmlLocalized(10, 42, 500, 110, 1061067, 0x7FFF, false, true); + + AddHtmlLocalized(10, 200, 390, 20, 1070718, 0x7FFF, false, false); // Skill Stored: + AddHtmlLocalized(210, 200, 390, 20, AosSkillBonuses.GetLabel(stone.Skill), 0x7FFF, false, false); + + Skill fromSkill = from.Skills[stone.Skill]; + + AddHtmlLocalized(10, 220, 390, 20, 1062298, 0x7FFF, false, false); // Current Value: + AddLabel(210, 220, 0x481, fromSkill.Base.ToString("0.0")); + + AddHtmlLocalized(10, 240, 390, 20, 1062299, 0x7FFF, false, false); // Current Cap: + AddLabel(210, 240, 0x481, fromSkill.Cap.ToString("0.0")); + + AddHtmlLocalized(10, 260, 390, 20, 1062300, 0x7FFF, false, false); // New Value: + AddLabel(210, 260, 0x481, stone.SkillValue.ToString("0.0")); + + AddButton(10, 360, 0xFA5, 0xFA6, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 362, 450, 20, 1070719, 0x7FFF, false, + false); // Activate the stone. I am ready to retrieve the skill points from it. + + AddButton(10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 382, 450, 20, 1070723, 0x7FFF, false, + false); // Remove all skill points from this stone and DO NOT absorb them. + + AddButton(10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 412, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0 || m_Stone.IsEmpty) + return; - /* You cannot transfer the selected skill to the Soulstone at this time. The selected - * skill may be locked or set to raise in your skill menu. Click on "Skills" in your - * paperdoll menu to check your raise/locked/lower settings and your total skills. - * Make any needed adjustments, then click "Continue". If you do not wish to transfer - * the selected skill at this time, click "Cancel". - */ + Mobile from = sender.Mobile; - from.SendGump( new ErrorGump( m_Stone, 1070710, 1070711 ) ); - return; - } + if (!m_Stone.CheckUse(from)) + return; - m_Stone.Skill = m_Skill.SkillName; - m_Stone.SkillValue = m_Skill.Base; + if (info.ButtonID == 1) // Remove skill points + { + from.SendGump(new ConfirmRemovalGump(m_Stone)); + return; + } - m_Skill.Base = 0.0; + SkillName skill = m_Stone.Skill; + double skillValue = m_Stone.SkillValue; + Skill fromSkill = from.Skills[m_Stone.Skill]; + + /* If we have, say, 88.4 in our skill and the stone holds 100, we need + * 11.6 free points. Also, if we're below our skillcap by, say, 8.2 points, + * we only need 11.6 - 8.2 = 3.4 points. + */ + int requiredAmount = (int)(skillValue * 10) - fromSkill.BaseFixedPoint - (from.SkillsCap - from.SkillsTotal); + + bool cannotAbsorb = false; + + if (fromSkill.Lock != SkillLock.Up) + { + cannotAbsorb = true; + } + else if (requiredAmount > 0) + { + int available = 0; + + for (int i = 0; i < from.Skills.Length; ++i) + { + if (from.Skills[i].Lock != SkillLock.Down) + continue; + + available += from.Skills[i].BaseFixedPoint; + } + + if (requiredAmount > available) + cannotAbsorb = true; + } + + if (cannotAbsorb) + { + //
Unable to Absorb Selected Skill from Soulstone
+ + /* You cannot absorb the selected skill from the Soulstone at this time. The selected + * skill may be locked or set to lower in your skill menu. You may also be at your + * total skill cap. Click on "Skills" in your paperdoll menu to check your + * raise/locked/lower settings and your total skills. Make any needed adjustments, + * then click "Continue". If you do not wish to transfer the selected skill at this + * time, click "Cancel". + */ + + from.SendGump(new ErrorGump(m_Stone, 1070717, 1070716)); + return; + } + + if (skillValue > fromSkill.Cap) + { + //
Unable to Absorb Selected Skill from Soulstone
- from.SendLocalizedMessage( 1070712 ); // You have successfully transferred your skill points into the Soulstone. + /* The amount of skill stored in this stone exceeds your individual skill cap for + * that skill. In order to retrieve the skill points stored in this stone, you must + * obtain a Power Scroll of the appropriate type and level in order to increase your + * skill cap. You cannot currently retrieve the skill points stored in this stone. + */ - m_Stone.LastUserName = from.Name; + from.SendGump(new ErrorGump(m_Stone, 1070717, 1070715)); + return; + } - Effects.SendLocationParticles( EffectItem.Create( from.Location, from.Map, EffectItem.DefaultDuration ), 0, 0, 0, 0, 0, 5060, 0 ); - Effects.PlaySound( from.Location, from.Map, 0x243 ); + if (fromSkill.Base >= skillValue) + { + //
Unable to Absorb Selected Skill from Soulstone
- Effects.SendMovingParticles( new Entity( Server.Serial.Zero, new Point3D( from.X - 6, from.Y - 6, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); + /* You cannot transfer the selected skill to the Soulstone at this time. The selected + * skill has a skill level higher than what is stored in the Soulstone. + */ + + // Wrong message?! + + from.SendGump(new ErrorGump(m_Stone, 1070717, 1070802)); + return; + } - Effects.SendTargetParticles( from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); - } - } + #region Scroll of ALacrity + + PlayerMobile pm = from as PlayerMobile; + if (pm.AcceleratedStart > DateTime.UtcNow) + { + //
Unable to Absorb Selected Skill from Soulstone
+ + /*You may not use a soulstone while your character is under the effects of a Scroll of Alacrity.*/ + + // Wrong message?! + + from.SendGump(new ErrorGump(m_Stone, 1070717, 1078115)); + return; + } + + #endregion + + if (requiredAmount > 0) + for (int i = 0; i < from.Skills.Length; ++i) + { + if (from.Skills[i].Lock != SkillLock.Down) + continue; - private class ConfirmTransferGump : Gump - { - private SoulStone m_Stone; + if (requiredAmount >= from.Skills[i].BaseFixedPoint) + { + requiredAmount -= from.Skills[i].BaseFixedPoint; + from.Skills[i].Base = 0.0; + } + else + { + from.Skills[i].BaseFixedPoint -= requiredAmount; + break; + } + } - public ConfirmTransferGump( SoulStone stone, Mobile from ) : base( 50, 50 ) - { - m_Stone = stone; + fromSkill.Base = skillValue; + m_Stone.SkillValue = 0.0; - AddBackground( 0, 0, 520, 440, 0x13BE ); - - AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 360, 0xA40 ); - AddImageTiled( 10, 410, 500, 20, 0xA40 ); + from.SendLocalizedMessage(1070713); // You have successfully absorbed the Soulstone's skill points. - AddAlphaRegion( 10, 10, 500, 420 ); + m_Stone.LastUserName = from.Name; - AddHtmlLocalized( 10, 12, 500, 20, 1070709, 0x7FFF, false, false ); //
Confirm Soulstone Transfer
+ Effects.SendLocationParticles(EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration), 0, 0, + 0, 0, 0, 5060, 0); + Effects.PlaySound(from.Location, from.Map, 0x243); - /*
Soulstone

- * You are using a Soulstone. This powerful artifact allows you to remove skill points - * from your character and store them in the stone for later retrieval. In order to use - * the stone, you must make sure your Skill Lock for the indicated skill is pointed downward. - * Click the "Skills" button on your Paperdoll to access the Skill List, and double-check - * your skill lock.

- * - * Once you activate the stone, all skill points in the indicated skill will be removed from - * your character. These skill points can later be retrieved. IMPORTANT: When retrieving - * skill points from a Soulstone, the Soulstone WILL REPLACE any existing skill points - * already on your character!

- * - * This is an Account Bound Soulstone. Skill pointsstored inside can be retrieved by any - * character on the same account as the character who placed them into the stone. - */ - AddHtmlLocalized( 10, 42, 500, 110, 1061067, 0x7FFF, false, true ); + Effects.SendMovingParticles( + new Entity(Server.Serial.Zero, new Point3D(from.X - 6, from.Y - 6, from.Z + 15), from.Map), from, 0x36D4, + 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); - AddHtmlLocalized( 10, 200, 390, 20, 1070718, 0x7FFF, false, false ); // Skill Stored: - AddHtmlLocalized( 210, 200, 390, 20, AosSkillBonuses.GetLabel( stone.Skill ), 0x7FFF, false, false ); + Effects.SendTargetParticles(from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); - Skill fromSkill = from.Skills[stone.Skill]; + if (m_Stone is SoulstoneFragment frag) + if (--frag.UsesRemaining <= 0) + from.SendLocalizedMessage(1070974); // You have used up your soulstone fragment. + } + } - AddHtmlLocalized( 10, 220, 390, 20, 1062298, 0x7FFF, false, false ); // Current Value: - AddLabel( 210, 220, 0x481, fromSkill.Base.ToString( "0.0" ) ); + private class ConfirmRemovalGump : Gump + { + private SoulStone m_Stone; - AddHtmlLocalized( 10, 240, 390, 20, 1062299, 0x7FFF, false, false ); // Current Cap: - AddLabel( 210, 240, 0x481, fromSkill.Cap.ToString( "0.0" ) ); + public ConfirmRemovalGump(SoulStone stone) : base(50, 50) + { + m_Stone = stone; - AddHtmlLocalized( 10, 260, 390, 20, 1062300, 0x7FFF, false, false ); // New Value: - AddLabel( 210, 260, 0x481, stone.SkillValue.ToString( "0.0" ) ); + AddBackground(0, 0, 520, 440, 0x13BE); - AddButton( 10, 360, 0xFA5, 0xFA6, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 362, 450, 20, 1070719, 0x7FFF, false, false ); // Activate the stone. I am ready to retrieve the skill points from it. + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 360, 0xA40); + AddImageTiled(10, 410, 500, 20, 0xA40); - AddButton( 10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 382, 450, 20, 1070723, 0x7FFF, false, false ); // Remove all skill points from this stone and DO NOT absorb them. + AddAlphaRegion(10, 10, 500, 420); - AddButton( 10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 412, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - } + AddHtmlLocalized(10, 12, 500, 20, 1070725, 0x7FFF, false, + false); //
Confirm Soulstone Skill Removal
- public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 || m_Stone.IsEmpty ) - return; + /* WARNING!

+ * + * You are about to permanently remove all skill points stored in this Soulstone. + * You WILL NOT absorb these skill points. They will be DELETED.

+ * + * Are you sure you wish to do this? If not, press the Cancel button. + */ + AddHtmlLocalized(10, 42, 500, 110, 1070724, 0x7FFF, false, true); - Mobile from = sender.Mobile; + AddButton(10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 382, 450, 20, 1052072, 0x7FFF, false, false); // Continue - if ( !m_Stone.CheckUse( from ) ) - return; + AddButton(10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 412, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + } - if ( info.ButtonID == 1 ) // Remove skill points - { - from.SendGump( new ConfirmRemovalGump( m_Stone ) ); - return; - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0 || m_Stone.IsEmpty) + return; - SkillName skill = m_Stone.Skill; - double skillValue = m_Stone.SkillValue; - Skill fromSkill = from.Skills[m_Stone.Skill]; - - /* If we have, say, 88.4 in our skill and the stone holds 100, we need - * 11.6 free points. Also, if we're below our skillcap by, say, 8.2 points, - * we only need 11.6 - 8.2 = 3.4 points. - */ - int requiredAmount = (int)(skillValue * 10) - fromSkill.BaseFixedPoint - (from.SkillsCap - from.SkillsTotal); - - bool cannotAbsorb = false; - - if ( fromSkill.Lock != SkillLock.Up ) - { - cannotAbsorb = true; - } - else if ( requiredAmount > 0 ) - { - int available = 0; - - for ( int i = 0; i < from.Skills.Length; ++i ) - { - if ( from.Skills[i].Lock != SkillLock.Down ) - continue; - - available += from.Skills[i].BaseFixedPoint; - } - - if ( requiredAmount > available ) - cannotAbsorb = true; - } - - if ( cannotAbsorb ) - { - //
Unable to Absorb Selected Skill from Soulstone
- - /* You cannot absorb the selected skill from the Soulstone at this time. The selected - * skill may be locked or set to lower in your skill menu. You may also be at your - * total skill cap. Click on "Skills" in your paperdoll menu to check your - * raise/locked/lower settings and your total skills. Make any needed adjustments, - * then click "Continue". If you do not wish to transfer the selected skill at this - * time, click "Cancel". - */ - - from.SendGump( new ErrorGump( m_Stone, 1070717, 1070716 ) ); - return; - } - - if ( skillValue > fromSkill.Cap ) - { - //
Unable to Absorb Selected Skill from Soulstone
- - /* The amount of skill stored in this stone exceeds your individual skill cap for - * that skill. In order to retrieve the skill points stored in this stone, you must - * obtain a Power Scroll of the appropriate type and level in order to increase your - * skill cap. You cannot currently retrieve the skill points stored in this stone. - */ - - from.SendGump( new ErrorGump( m_Stone, 1070717, 1070715 ) ); - return; - } - - if ( fromSkill.Base >= skillValue ) - { - //
Unable to Absorb Selected Skill from Soulstone
- - /* You cannot transfer the selected skill to the Soulstone at this time. The selected - * skill has a skill level higher than what is stored in the Soulstone. - */ - - // Wrong message?! - - from.SendGump( new ErrorGump( m_Stone, 1070717, 1070802 ) ); - return; - } - - #region Scroll of ALacrity - PlayerMobile pm = from as PlayerMobile; - if (pm.AcceleratedStart > DateTime.UtcNow) - { - //
Unable to Absorb Selected Skill from Soulstone
- - /*You may not use a soulstone while your character is under the effects of a Scroll of Alacrity.*/ - - // Wrong message?! - - from.SendGump(new ErrorGump(m_Stone, 1070717, 1078115)); - return; - } - #endregion - - if ( requiredAmount > 0 ) - { - for ( int i = 0; i < from.Skills.Length; ++i ) - { - if ( from.Skills[i].Lock != SkillLock.Down ) - continue; - - if ( requiredAmount >= from.Skills[i].BaseFixedPoint ) - { - requiredAmount -= from.Skills[i].BaseFixedPoint; - from.Skills[i].Base = 0.0; - } - else - { - from.Skills[i].BaseFixedPoint -= requiredAmount; - break; - } - } - } + Mobile from = sender.Mobile; - fromSkill.Base = skillValue; - m_Stone.SkillValue = 0.0; + if (!m_Stone.CheckUse(from)) + return; - from.SendLocalizedMessage( 1070713 ); // You have successfully absorbed the Soulstone's skill points. + m_Stone.SkillValue = 0.0; + from.SendLocalizedMessage(1070726); // You have successfully deleted the Soulstone's skill points. + } + } - m_Stone.LastUserName = from.Name; + private class ErrorGump : Gump + { + private SoulStone m_Stone; + + public ErrorGump(SoulStone stone, int title, int message) : base(50, 50) + { + m_Stone = stone; - Effects.SendLocationParticles( EffectItem.Create( from.Location, from.Map, EffectItem.DefaultDuration ), 0, 0, 0, 0, 0, 5060, 0 ); - Effects.PlaySound( from.Location, from.Map, 0x243 ); + AddBackground(0, 0, 520, 440, 0x13BE); - Effects.SendMovingParticles( new Entity( Server.Serial.Zero, new Point3D( from.X - 6, from.Y - 6, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 360, 0xA40); + AddImageTiled(10, 410, 500, 20, 0xA40); - Effects.SendTargetParticles( from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); + AddAlphaRegion(10, 10, 500, 420); - if ( m_Stone is SoulstoneFragment frag ) - { - if ( --frag.UsesRemaining <= 0 ) - from.SendLocalizedMessage( 1070974 ); // You have used up your soulstone fragment. - } - } - } + AddHtmlLocalized(10, 12, 500, 20, title, 0x7FFF, false, false); - private class ConfirmRemovalGump : Gump - { - private SoulStone m_Stone; + AddHtmlLocalized(10, 42, 500, 110, message, 0x7FFF, false, true); - public ConfirmRemovalGump( SoulStone stone ) : base( 50, 50 ) - { - m_Stone = stone; + AddButton(10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 382, 450, 20, 1052072, 0x7FFF, false, false); // Continue - AddBackground( 0, 0, 520, 440, 0x13BE ); + AddButton(10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 412, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + } - AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 360, 0xA40 ); - AddImageTiled( 10, 410, 500, 20, 0xA40 ); + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0) + return; - AddAlphaRegion( 10, 10, 500, 420 ); + Mobile from = sender.Mobile; - AddHtmlLocalized( 10, 12, 500, 20, 1070725, 0x7FFF, false, false ); //
Confirm Soulstone Skill Removal
+ if (!m_Stone.CheckUse(from)) + return; - /* WARNING!

- * - * You are about to permanently remove all skill points stored in this Soulstone. - * You WILL NOT absorb these skill points. They will be DELETED.

- * - * Are you sure you wish to do this? If not, press the Cancel button. - */ - AddHtmlLocalized( 10, 42, 500, 110, 1070724, 0x7FFF, false, true ); + if (m_Stone.IsEmpty) + from.SendGump(new SelectSkillGump(m_Stone, from)); + else + from.SendGump(new ConfirmTransferGump(m_Stone, from)); + } + } + } - AddButton( 10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 382, 450, 20, 1052072, 0x7FFF, false, false ); // Continue + public class SoulstoneFragment : SoulStone, IUsesRemaining + { + private int m_UsesRemaining; - AddButton( 10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 412, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - } + [Constructible] + public SoulstoneFragment() : this(5, null) + { + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 || m_Stone.IsEmpty ) - return; - - Mobile from = sender.Mobile; - - if ( !m_Stone.CheckUse( from ) ) - return; - - m_Stone.SkillValue = 0.0; - from.SendLocalizedMessage( 1070726 ); // You have successfully deleted the Soulstone's skill points. - } - } - - private class ErrorGump : Gump - { - private SoulStone m_Stone; - - public ErrorGump( SoulStone stone, int title, int message ) : base( 50, 50 ) - { - m_Stone = stone; - - AddBackground( 0, 0, 520, 440, 0x13BE ); - - AddImageTiled( 10, 10, 500, 20, 0xA40 ); - AddImageTiled( 10, 40, 500, 360, 0xA40 ); - AddImageTiled( 10, 410, 500, 20, 0xA40 ); - - AddAlphaRegion( 10, 10, 500, 420 ); - - AddHtmlLocalized( 10, 12, 500, 20, title, 0x7FFF, false, false ); - - AddHtmlLocalized( 10, 42, 500, 110, message, 0x7FFF, false, true ); - - AddButton( 10, 380, 0xFA5, 0xFA6, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 382, 450, 20, 1052072, 0x7FFF, false, false ); // Continue - - AddButton( 10, 410, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 412, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 ) - return; - - Mobile from = sender.Mobile; - - if ( !m_Stone.CheckUse( from ) ) - return; - - if ( m_Stone.IsEmpty ) - from.SendGump( new SelectSkillGump( m_Stone, from ) ); - else - from.SendGump( new ConfirmTransferGump( m_Stone, from ) ); - } - } - - public SoulStone( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 3 ); // version - - //version 3 - writer.Write( (string) m_LastUserName ); - - //version 2 - writer.Write( (int)Level ); - - writer.Write( m_ActiveItemID ); - writer.Write( m_InactiveItemID ); - - writer.Write( (string) Account ); - writer.Write( (DateTime) m_NextUse ); //TODO: delete it in a harmless way - - writer.WriteEncodedInt( (int) m_Skill ); - writer.Write( (double) m_SkillValue ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - switch( version ) - { - case 3: - { - m_LastUserName = reader.ReadString(); - goto case 2; - } - case 2: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 1; - } - case 1: - { - m_ActiveItemID = reader.ReadInt(); - m_InactiveItemID = reader.ReadInt(); - - goto case 0; - } - case 0: - { - Account = reader.ReadString(); - m_NextUse = reader.ReadDateTime(); //TODO: delete it in a harmless way - - m_Skill = (SkillName)reader.ReadEncodedInt(); - m_SkillValue = reader.ReadDouble(); - break; - } - } - - if ( version == 0 ) - { - m_ActiveItemID = 0x2A94; - m_InactiveItemID = 0x2A93; - } - } - } - - public class SoulstoneFragment : SoulStone, IUsesRemaining - { - private int m_UsesRemaining; - - public override int LabelNumber => 1071000; // soulstone fragment - - [Constructible] - public SoulstoneFragment() : this( 5, null ) - { - } - - [Constructible] - public SoulstoneFragment( int usesRemaining ) : this( usesRemaining, null ) - { - } - - [Constructible] - public SoulstoneFragment( string account ) : this( 5, account ) - { - } - - [Constructible] - public SoulstoneFragment( int usesRemaining, string account ) : base( account, Utility.Random( 0x2AA1, 9 ) ) - { - m_UsesRemaining = usesRemaining; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ - } - - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set - { - m_UsesRemaining = value; InvalidateProperties(); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 2 ); // version - - writer.WriteEncodedInt( m_UsesRemaining ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_UsesRemaining = reader.ReadEncodedInt(); - - if ( version <= 1 ) - { - if ( ItemID == 0x2A93 || ItemID == 0x2A94 ) - { - ActiveItemID = Utility.Random( 0x2AA1, 9 ); - } - else - { - ActiveItemID = ItemID; - } - - InactiveItemID = ActiveItemID; - } - - if ( version == 0 && Weight == 1 ) - Weight = -1; - } - - public SoulstoneFragment( Serial serial ) : base( serial ) - { - } - - protected override bool CheckUse( Mobile from ) - { - bool canUse = base.CheckUse( from ); - - if ( canUse ) - { - if ( m_UsesRemaining <= 0 ) - { - from.SendLocalizedMessage( 1070975 ); // That soulstone fragment has no more uses. - return false; - } - } - - return canUse; - } - - - public bool ShowUsesRemaining{ get => true; - set{} } - } - - [Flippable] - public class BlueSoulstone : SoulStone - { - [Constructible] - public BlueSoulstone() - : this( null ) - { - } - - [Constructible] - public BlueSoulstone( string account ) - : base( account, 0x2ADC, 0x2ADD ) - { - } - - public BlueSoulstone( Serial serial ) - : base( serial ) - { - } - - public void Flip() - { - switch( ItemID ) - { - case 0x2ADC: ItemID = 0x2AEC; break; - case 0x2ADD: ItemID = 0x2AED; break; - case 0x2AEC: ItemID = 0x2ADC; break; - case 0x2AED: ItemID = 0x2ADD; break; - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class RedSoulstone : SoulStone, IRewardItem - { - [Constructible] - public RedSoulstone() - : this( null ) - { - } - - [Constructible] - public RedSoulstone( string account ) - : base( account, 0x32F3, 0x32F4 ) - { - - } - - public RedSoulstone( Serial serial ) - : base( serial ) - { - } - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076217 ); // 1st Year Veteran Reward - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - m_IsRewardItem = reader.ReadBool(); - break; - } - } - } - } -} + [Constructible] + public SoulstoneFragment(int usesRemaining) : this(usesRemaining, null) + { + } + + [Constructible] + public SoulstoneFragment(string account) : this(5, account) + { + } + + [Constructible] + public SoulstoneFragment(int usesRemaining, string account) : base(account, Utility.Random(0x2AA1, 9)) + { + m_UsesRemaining = usesRemaining; + } + + public SoulstoneFragment(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1071000; // soulstone fragment + + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } + + + public bool ShowUsesRemaining + { + get => true; + set { } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(2); // version + + writer.WriteEncodedInt(m_UsesRemaining); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_UsesRemaining = reader.ReadEncodedInt(); + + if (version <= 1) + { + if (ItemID == 0x2A93 || ItemID == 0x2A94) + ActiveItemID = Utility.Random(0x2AA1, 9); + else + ActiveItemID = ItemID; + + InactiveItemID = ActiveItemID; + } + + if (version == 0 && Weight == 1) + Weight = -1; + } + + protected override bool CheckUse(Mobile from) + { + bool canUse = base.CheckUse(from); + + if (canUse) + if (m_UsesRemaining <= 0) + { + from.SendLocalizedMessage(1070975); // That soulstone fragment has no more uses. + return false; + } + + return canUse; + } + } + + [Flippable] + public class BlueSoulstone : SoulStone + { + [Constructible] + public BlueSoulstone() + : this(null) + { + } + + [Constructible] + public BlueSoulstone(string account) + : base(account, 0x2ADC, 0x2ADD) + { + } + + public BlueSoulstone(Serial serial) + : base(serial) + { + } + + public void Flip() + { + switch (ItemID) + { + case 0x2ADC: + ItemID = 0x2AEC; + break; + case 0x2ADD: + ItemID = 0x2AED; + break; + case 0x2AEC: + ItemID = 0x2ADC; + break; + case 0x2AED: + ItemID = 0x2ADD; + break; + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class RedSoulstone : SoulStone, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public RedSoulstone() + : this(null) + { + } + + [Constructible] + public RedSoulstone(string account) + : base(account, 0x32F3, 0x32F4) + { + } + + public RedSoulstone(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076217); // 1st Year Veteran Reward + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_IsRewardItem = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Special Scrolls/PowerScroll.cs b/Scripts/Items/Special/Special Scrolls/PowerScroll.cs index 01f1dffcd..84e89a760 100644 --- a/Scripts/Items/Special/Special Scrolls/PowerScroll.cs +++ b/Scripts/Items/Special/Special Scrolls/PowerScroll.cs @@ -1,248 +1,248 @@ -using System; using System.Collections.Generic; namespace Server.Items { - public class PowerScroll : SpecialScroll - { - public override int Message => 1049469; /* Using a scroll increases the maximum amount of a specific skill or your maximum statistics. + public class PowerScroll : SpecialScroll + { + private static SkillName[] m_Skills = + { + SkillName.Blacksmith, + SkillName.Tailoring, + SkillName.Swords, + SkillName.Fencing, + SkillName.Macing, + SkillName.Archery, + SkillName.Wrestling, + SkillName.Parry, + SkillName.Tactics, + SkillName.Anatomy, + SkillName.Healing, + SkillName.Magery, + SkillName.Meditation, + SkillName.EvalInt, + SkillName.MagicResist, + SkillName.AnimalTaming, + SkillName.AnimalLore, + SkillName.Veterinary, + SkillName.Musicianship, + SkillName.Provocation, + SkillName.Discordance, + SkillName.Peacemaking + }; + + private static SkillName[] m_AOSSkills = + { + SkillName.Chivalry, + SkillName.Focus, + SkillName.Necromancy, + SkillName.Stealing, + SkillName.Stealth, + SkillName.SpiritSpeak + }; + + private static SkillName[] m_SESkills = + { + SkillName.Ninjitsu, + SkillName.Bushido + }; + + private static SkillName[] m_MLSkills = + { + SkillName.Spellweaving + }; + + /* + private static SkillName[] m_SASkills = new SkillName[] + { + SkillName.Throwing, + SkillName.Mysticism, + SkillName.Imbuing + }; + + private static SkillName[] m_HSSkills = new SkillName[] + { + SkillName.Fishing + }; + */ + + private static List _Skills = new List(); + + public PowerScroll() : this(SkillName.Alchemy, 0.0) + { + } + + [Constructible] + public PowerScroll(SkillName skill, double value) : base(skill, value) + { + Hue = 0x481; + + if (Value == 105.0 || skill == SkillName.Blacksmith || skill == SkillName.Tailoring) + LootType = LootType.Regular; + } + + public PowerScroll(Serial serial) : base(serial) + { + } + + public override int Message => + 1049469; /* Using a scroll increases the maximum amount of a specific skill or your maximum statistics. * When used, the effect is not immediately seen without a gain of points with that skill or statistics. * You can view your maximum skill values in your skills window. * You can view your maximum statistic value in your statistics window. */ - public override int Title - { - get - { - double level = ( Value - 105.0 ) / 5.0; - if ( level >= 0.0 && level <= 3.0 && Value % 5.0 == 0.0 ) - return 1049635 + (int)level; /* Wonderous Scroll (105 Skill): OR + public override int Title + { + get + { + double level = (Value - 105.0) / 5.0; + + if (level >= 0.0 && level <= 3.0 && Value % 5.0 == 0.0) + return 1049635 + (int)level; /* Wonderous Scroll (105 Skill): OR * Exalted Scroll (110 Skill): OR * Mythical Scroll (115 Skill): OR * Legendary Scroll (120 Skill): */ - return 0; - } - } + return 0; + } + } - public override string DefaultTitle => $"Power Scroll ({Value} Skill):"; + public override string DefaultTitle => $"Power Scroll ({Value} Skill):"; - private static SkillName[] m_Skills = { - SkillName.Blacksmith, - SkillName.Tailoring, - SkillName.Swords, - SkillName.Fencing, - SkillName.Macing, - SkillName.Archery, - SkillName.Wrestling, - SkillName.Parry, - SkillName.Tactics, - SkillName.Anatomy, - SkillName.Healing, - SkillName.Magery, - SkillName.Meditation, - SkillName.EvalInt, - SkillName.MagicResist, - SkillName.AnimalTaming, - SkillName.AnimalLore, - SkillName.Veterinary, - SkillName.Musicianship, - SkillName.Provocation, - SkillName.Discordance, - SkillName.Peacemaking - }; + public static List Skills + { + get + { + if (_Skills.Count == 0) + { + _Skills.AddRange(m_Skills); + if (Core.AOS) + { + _Skills.AddRange(m_AOSSkills); + if (Core.SE) + { + _Skills.AddRange(m_SESkills); + if (Core.ML) _Skills.AddRange(m_MLSkills); + } + } + } - private static SkillName[] m_AOSSkills = { - SkillName.Chivalry, - SkillName.Focus, - SkillName.Necromancy, - SkillName.Stealing, - SkillName.Stealth, - SkillName.SpiritSpeak - }; + return _Skills; + } + } - private static SkillName[] m_SESkills = { - SkillName.Ninjitsu, - SkillName.Bushido - }; + public static PowerScroll CreateRandom(int min, int max) + { + min /= 5; + max /= 5; - private static SkillName[] m_MLSkills = { - SkillName.Spellweaving - }; + return new PowerScroll(Skills[Utility.Random(Skills.Count)], 100 + Utility.RandomMinMax(min, max) * 5); + } - /* - private static SkillName[] m_SASkills = new SkillName[] - { - SkillName.Throwing, - SkillName.Mysticism, - SkillName.Imbuing - }; + public static PowerScroll CreateRandomNoCraft(int min, int max) + { + min /= 5; + max /= 5; - private static SkillName[] m_HSSkills = new SkillName[] - { - SkillName.Fishing - }; - */ + SkillName skillName; - private static List _Skills = new List(); + do + { + skillName = Skills[Utility.Random(Skills.Count)]; + } while (skillName == SkillName.Blacksmith || skillName == SkillName.Tailoring); - public static List Skills - { - get - { - if ( _Skills.Count == 0 ) - { - _Skills.AddRange( m_Skills ); - if (Core.AOS) - { - _Skills.AddRange( m_AOSSkills ); - if (Core.SE) - { - _Skills.AddRange( m_SESkills ); - if (Core.ML) - { - _Skills.AddRange( m_MLSkills ); - /* - if (Core.SA) - { - _Skills.AddRange( m_SASkills ); - if (Core.HS) - _Skills.AddRange( m_HSSkills ); - } - */ - } - } - } - } - return _Skills; - } - } + return new PowerScroll(skillName, 100 + Utility.RandomMinMax(min, max) * 5); + } - public static PowerScroll CreateRandom( int min, int max ) - { - min /= 5; - max /= 5; + public override void AddNameProperty(ObjectPropertyList list) + { + double level = (Value - 105.0) / 5.0; - return new PowerScroll( Skills[Utility.Random( Skills.Count )], 100 + ( Utility.RandomMinMax( min, max ) * 5 ) ); - } - - public static PowerScroll CreateRandomNoCraft( int min, int max ) - { - min /= 5; - max /= 5; - - SkillName skillName; - - do - { - skillName = Skills[Utility.Random( Skills.Count )]; - } while ( skillName == SkillName.Blacksmith || skillName == SkillName.Tailoring ); - - return new PowerScroll( skillName, 100 + (Utility.RandomMinMax( min, max ) * 5)); - } - - public PowerScroll() : this( SkillName.Alchemy, 0.0 ) - { - } - - [Constructible] - public PowerScroll( SkillName skill, double value ) : base( skill, value ) - { - Hue = 0x481; - - if ( Value == 105.0 || skill == SkillName.Blacksmith || skill == SkillName.Tailoring ) - LootType = LootType.Regular; - } - - public PowerScroll( Serial serial ) : base( serial ) - { - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - double level = ( Value - 105.0 ) / 5.0; - - if ( level >= 0.0 && level <= 3.0 && Value % 5.0 == 0.0 ) - list.Add( 1049639 + (int)level, GetNameLocalized() ); /* a wonderous scroll of ~1_type~ (105 Skill) OR + if (level >= 0.0 && level <= 3.0 && Value % 5.0 == 0.0) + list.Add(1049639 + (int)level, GetNameLocalized()); /* a wonderous scroll of ~1_type~ (105 Skill) OR * an exalted scroll of ~1_type~ (110 Skill) OR * a mythical scroll of ~1_type~ (115 Skill) OR * a legendary scroll of ~1_type~ (120 Skill) */ - else - list.Add( "a power scroll of {0} ({1} Skill)", GetName(), Value ); - } + else + list.Add("a power scroll of {0} ({1} Skill)", GetName(), Value); + } - public override void OnSingleClick( Mobile from ) - { - double level = ( Value - 105.0 ) / 5.0; + public override void OnSingleClick(Mobile from) + { + double level = (Value - 105.0) / 5.0; - if ( level >= 0.0 && level <= 3.0 && Value % 5.0 == 0.0 ) - LabelTo( from, 1049639 + (int)level, GetNameLocalized() ); - else - LabelTo( from, "a power scroll of {0} ({1} Skill)", GetName(), Value ); - } + if (level >= 0.0 && level <= 3.0 && Value % 5.0 == 0.0) + LabelTo(from, 1049639 + (int)level, GetNameLocalized()); + else + LabelTo(from, "a power scroll of {0} ({1} Skill)", GetName(), Value); + } - public override bool CanUse( Mobile from ) - { - if ( !base.CanUse( from ) ) - return false; + public override bool CanUse(Mobile from) + { + if (!base.CanUse(from)) + return false; - Skill skill = from.Skills[Skill]; + Skill skill = from.Skills[Skill]; - if ( skill == null ) - return false; + if (skill == null) + return false; - if ( skill.Cap >= Value ) - { - from.SendLocalizedMessage( 1049511, GetNameLocalized() ); // Your ~1_type~ is too high for this power scroll. - return false; - } + if (skill.Cap >= Value) + { + from.SendLocalizedMessage(1049511, GetNameLocalized()); // Your ~1_type~ is too high for this power scroll. + return false; + } - return true; - } + return true; + } - public override void Use( Mobile from ) - { - if ( !CanUse( from ) ) - return; + public override void Use(Mobile from) + { + if (!CanUse(from)) + return; - from.SendLocalizedMessage( 1049513, GetNameLocalized() ); // You feel a surge of magic as the scroll enhances your ~1_type~! + from.SendLocalizedMessage(1049513, + GetNameLocalized()); // You feel a surge of magic as the scroll enhances your ~1_type~! - from.Skills[Skill].Cap = Value; + from.Skills[Skill].Cap = Value; - Effects.SendLocationParticles( EffectItem.Create( from.Location, from.Map, EffectItem.DefaultDuration ), 0, 0, 0, 0, 0, 5060, 0 ); - Effects.PlaySound( from.Location, from.Map, 0x243 ); + Effects.SendLocationParticles(EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration), 0, 0, 0, 0, + 0, 5060, 0); + Effects.PlaySound(from.Location, from.Map, 0x243); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( from.X - 6, from.Y - 6, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( from.X - 4, from.Y - 6, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( from.X - 6, from.Y - 4, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(from.X - 6, from.Y - 6, from.Z + 15), from.Map), + from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(from.X - 4, from.Y - 6, from.Z + 15), from.Map), + from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(from.X - 6, from.Y - 4, from.Z + 15), from.Map), + from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); - Effects.SendTargetParticles( from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); + Effects.SendTargetParticles(from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); - Delete(); - } + Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = ( InheritsItem ? 0 : reader.ReadInt() ); // Required for SpecialScroll insertion + int version = InheritsItem ? 0 : reader.ReadInt(); // Required for SpecialScroll insertion - if ( Value == 105.0 || Skill == SkillName.Blacksmith || Skill == SkillName.Tailoring ) - { - LootType = LootType.Regular; - } - else - { - LootType = LootType.Cursed; - Insured = false; - } - } - } -} + if (Value == 105.0 || Skill == SkillName.Blacksmith || Skill == SkillName.Tailoring) + { + LootType = LootType.Regular; + } + else + { + LootType = LootType.Cursed; + Insured = false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Special Scrolls/ScrollofAlacrity.cs b/Scripts/Items/Special/Special Scrolls/ScrollofAlacrity.cs index 5c51dbd8f..bd4ba6543 100644 --- a/Scripts/Items/Special/Special Scrolls/ScrollofAlacrity.cs +++ b/Scripts/Items/Special/Special Scrolls/ScrollofAlacrity.cs @@ -19,143 +19,151 @@ ***************************************************************************/ using System; -using Server.Mobiles; using System.Collections; +using Server.Mobiles; namespace Server.Items { - public class ScrollofAlacrity : SpecialScroll - { - public override int LabelNumber => 1078604; // Scroll of Alacrity + public class ScrollofAlacrity : SpecialScroll + { + private static Hashtable m_Table = new Hashtable(); - public override int Message => 1078602; /*Using a Scroll of Transcendence for a given skill will permanently increase your current + public ScrollofAlacrity() : this(SkillName.Alchemy) + { + } + + [Constructible] + public ScrollofAlacrity(SkillName skill) : base(skill, 0.0) + { + ItemID = 0x14EF; + Hue = 0x4AB; + } + + public ScrollofAlacrity(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1078604; // Scroll of Alacrity + + public override int Message => + 1078602; /*Using a Scroll of Transcendence for a given skill will permanently increase your current *level in that skill by the amount of points displayed on the scroll. *As you may not gain skills beyond your maximum skill cap, any excess points will be lost.*/ - public override string DefaultTitle => string.Format( "Scroll of Alacrity:" ); + public override string DefaultTitle => "Scroll of Alacrity:"; - public ScrollofAlacrity() : this( SkillName.Alchemy ) - { - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - [Constructible] - public ScrollofAlacrity( SkillName skill ) : base( skill, 0.0 ) - { - ItemID = 0x14EF; - Hue = 0x4AB; - } + list.Add(1071345, "{0} 15 Minutes", GetName()); // Skill: ~1_val~ + } - public ScrollofAlacrity(Serial serial) : base(serial) - { - } + public override bool CanUse(Mobile from) + { + if (!base.CanUse(from)) + return false; - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); + if (!(from is PlayerMobile pm)) + return false; - list.Add(1071345, "{0} 15 Minutes", GetName()); // Skill: ~1_val~ - } + #region Mondain's Legacy - public override bool CanUse( Mobile from ) - { - if ( !base.CanUse( from ) ) - return false; + /* to add when skillgain quests will be implemented - if ( !(from is PlayerMobile pm) ) - return false; + for (int i = pm.Quests.Count - 1; i >= 0; i--) + { + BaseQuest quest = pm.Quests[i]; - #region Mondain's Legacy - /* to add when skillgain quests will be implemented + for (int j = quest.Objectives.Count - 1; j >= 0; j--) + { + BaseObjective objective = quest.Objectives[j]; - for (int i = pm.Quests.Count - 1; i >= 0; i--) - { - BaseQuest quest = pm.Quests[i]; + if (objective is ApprenticeObjective) + { + from.SendMessage("You are already under the effect of an enhanced skillgain quest."); + return false; + } + } + } - for (int j = quest.Objectives.Count - 1; j >= 0; j--) - { - BaseObjective objective = quest.Objectives[j]; + */ - if (objective is ApprenticeObjective) - { - from.SendMessage("You are already under the effect of an enhanced skillgain quest."); - return false; - } - } - } + #endregion - */ - #endregion + #region Scroll of Alacrity - #region Scroll of Alacrity - if (pm.AcceleratedStart > DateTime.UtcNow) - { - from.SendLocalizedMessage(1077951); // You are already under the effect of an accelerated skillgain scroll. - return false; - } - #endregion + if (pm.AcceleratedStart > DateTime.UtcNow) + { + from.SendLocalizedMessage(1077951); // You are already under the effect of an accelerated skillgain scroll. + return false; + } - return true; - } + #endregion - public override void Use( Mobile from ) - { - if ( !CanUse( from ) ) - return; + return true; + } - if ( !(from is PlayerMobile pm) ) - return; + public override void Use(Mobile from) + { + if (!CanUse(from)) + return; - double tskill = from.Skills[Skill].Base; - double tcap = from.Skills[Skill].Cap; + if (!(from is PlayerMobile pm)) + return; - if ( tskill >= tcap || from.Skills[Skill].Lock != SkillLock.Up ) - { - from.SendLocalizedMessage( 1094935 ); /*You cannot increase this skill at this time. The skill may be locked or set to lower in your skill menu. + double tskill = from.Skills[Skill].Base; + double tcap = from.Skills[Skill].Cap; + + if (tskill >= tcap || from.Skills[Skill].Lock != SkillLock.Up) + { + from.SendLocalizedMessage( + 1094935); /*You cannot increase this skill at this time. The skill may be locked or set to lower in your skill menu. *If you are at your total skill cap, you must use a Powerscroll to increase your current skill cap.*/ - return; - } + return; + } - from.SendLocalizedMessage( 1077956 ); // You are infused with intense energy. You are under the effects of an accelerated skillgain scroll. + from.SendLocalizedMessage( + 1077956); // You are infused with intense energy. You are under the effects of an accelerated skillgain scroll. - Effects.PlaySound( from.Location, from.Map, 0x1E9 ); - Effects.SendTargetParticles( from, 0x373A, 35, 45, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); + Effects.PlaySound(from.Location, from.Map, 0x1E9); + Effects.SendTargetParticles(from, 0x373A, 35, 45, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); - pm.AcceleratedStart = DateTime.UtcNow + TimeSpan.FromMinutes(15); - m_Table[from] = Timer.DelayCall( TimeSpan.FromMinutes( 15 ), new TimerStateCallback( Expire_Callback ), from ); + pm.AcceleratedStart = DateTime.UtcNow + TimeSpan.FromMinutes(15); + m_Table[from] = Timer.DelayCall(TimeSpan.FromMinutes(15), new TimerStateCallback(Expire_Callback), from); - pm.AcceleratedSkill = Skill; + pm.AcceleratedSkill = Skill; - Delete(); - } + Delete(); + } - private static Hashtable m_Table = new Hashtable(); + private static void Expire_Callback(object state) + { + Mobile m = (Mobile)state; - private static void Expire_Callback(object state) - { - Mobile m = (Mobile)state; + m_Table.Remove(m); - m_Table.Remove(m); + m.PlaySound(0x1F8); - m.PlaySound(0x1F8); + m.SendLocalizedMessage( + 1077957); // The intense energy dissipates. You are no longer under the effects of an accelerated skillgain scroll. + } - m.SendLocalizedMessage(1077957);// The intense energy dissipates. You are no longer under the effects of an accelerated skillgain scroll. - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); // version + } - writer.Write((int)0); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + int version = InheritsItem ? 0 : reader.ReadInt(); //Required for SpecialScroll insertion - int version = ( InheritsItem ? 0 : reader.ReadInt() ); //Required for SpecialScroll insertion - - LootType = LootType.Cursed; - Insured = false; - } - } -} + LootType = LootType.Cursed; + Insured = false; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Special Scrolls/ScrollofTranscendence.cs b/Scripts/Items/Special/Special Scrolls/ScrollofTranscendence.cs index db3bb6329..45eef49a6 100644 --- a/Scripts/Items/Special/Special Scrolls/ScrollofTranscendence.cs +++ b/Scripts/Items/Special/Special Scrolls/ScrollofTranscendence.cs @@ -3,161 +3,168 @@ using Server.Mobiles; namespace Server.Items { - public class ScrollofTranscendence : SpecialScroll - { - public override int LabelNumber => 1094934; // Scroll of Transcendence + public class ScrollofTranscendence : SpecialScroll + { + public ScrollofTranscendence() : this(SkillName.Alchemy, 0.0) + { + } - public override int Message => 1094933; /*Using a Scroll of Transcendence for a given skill will permanently increase your current + [Constructible] + public ScrollofTranscendence(SkillName skill, double value) : base(skill, value) + { + ItemID = 0x14EF; + Hue = 0x490; + } + + public ScrollofTranscendence(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1094934; // Scroll of Transcendence + + public override int Message => + 1094933; /*Using a Scroll of Transcendence for a given skill will permanently increase your current *level in that skill by the amount of points displayed on the scroll. *As you may not gain skills beyond your maximum skill cap, any excess points will be lost.*/ - public override string DefaultTitle => - $"Scroll of Transcendence ({Value} Skill):"; + public override string DefaultTitle => + $"Scroll of Transcendence ({Value} Skill):"; - public static ScrollofTranscendence CreateRandom( int min, int max ) - { - SkillName skill = (SkillName)Utility.Random( SkillInfo.Table.Length ); + public static ScrollofTranscendence CreateRandom(int min, int max) + { + SkillName skill = (SkillName)Utility.Random(SkillInfo.Table.Length); - return new ScrollofTranscendence(skill, Utility.RandomMinMax(min, max) * 0.1); - } + return new ScrollofTranscendence(skill, Utility.RandomMinMax(min, max) * 0.1); + } - public ScrollofTranscendence() : this( SkillName.Alchemy, 0.0 ) - { - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - [Constructible] - public ScrollofTranscendence( SkillName skill, double value ) : base( skill, value ) - { - ItemID = 0x14EF; - Hue = 0x490; - } + if (Value == 1) + list.Add(1076759, "{0}\t{1}.0 Skill Points", GetName(), Value); + else + list.Add(1076759, "{0}\t{1} Skill Points", GetName(), Value); + } - public ScrollofTranscendence(Serial serial) : base(serial) - { - } + public override bool CanUse(Mobile from) + { + if (!base.CanUse(from)) + return false; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties(list); + if (!(from is PlayerMobile pm)) + return false; - if ( Value == 1 ) - list.Add(1076759, "{0}\t{1}.0 Skill Points", GetName(), Value); - else - list.Add(1076759, "{0}\t{1} Skill Points", GetName(), Value); - } + #region Mondain's Legacy - public override bool CanUse( Mobile from ) - { - if ( !base.CanUse( from ) ) - return false; + /* to add when skillgain quests will be implemented - if ( !(from is PlayerMobile pm) ) - return false; + for (int i = pm.Quests.Count - 1; i >= 0; i--) + { + BaseQuest quest = pm.Quests[i]; - #region Mondain's Legacy - /* to add when skillgain quests will be implemented + for (int j = quest.Objectives.Count - 1; j >= 0; j--) + { + BaseObjective objective = quest.Objectives[j]; - for (int i = pm.Quests.Count - 1; i >= 0; i--) - { - BaseQuest quest = pm.Quests[i]; + if (objective is ApprenticeObjective) + { + from.SendMessage("You are already under the effect of an enhanced skillgain quest."); + return false; + } + } + } - for (int j = quest.Objectives.Count - 1; j >= 0; j--) - { - BaseObjective objective = quest.Objectives[j]; + */ - if (objective is ApprenticeObjective) - { - from.SendMessage("You are already under the effect of an enhanced skillgain quest."); - return false; - } - } - } + #endregion - */ - #endregion + #region Scroll of Alacrity - #region Scroll of Alacrity - if (pm.AcceleratedStart > DateTime.UtcNow) - { - from.SendLocalizedMessage(1077951); // You are already under the effect of an accelerated skillgain scroll. - return false; - } - #endregion + if (pm.AcceleratedStart > DateTime.UtcNow) + { + from.SendLocalizedMessage(1077951); // You are already under the effect of an accelerated skillgain scroll. + return false; + } - return true; - } + #endregion - public override void Use( Mobile from ) - { - if ( !CanUse( from ) ) - return; + return true; + } - double tskill = from.Skills[Skill].Base; // value of skill without item bonuses etc - double tcap = from.Skills[Skill].Cap; // maximum value permitted - bool canGain = false; + public override void Use(Mobile from) + { + if (!CanUse(from)) + return; - double newValue = Value; + double tskill = from.Skills[Skill].Base; // value of skill without item bonuses etc + double tcap = from.Skills[Skill].Cap; // maximum value permitted + bool canGain = false; - if ( ( tskill + newValue ) > tcap ) - newValue = tcap - tskill; + double newValue = Value; - if ( tskill < tcap && from.Skills[Skill].Lock == SkillLock.Up ) - { - if ( ( from.SkillsTotal + newValue * 10 ) > from.SkillsCap ) - { - int ns = from.Skills.Length; // number of items in from.Skills[] + if (tskill + newValue > tcap) + newValue = tcap - tskill; - for ( int i = 0; i < ns; i++ ) - { - // skill must point down and its value must be enough - if ( from.Skills[i].Lock == SkillLock.Down && from.Skills[i].Base >= newValue ) - { - from.Skills[i].Base -= newValue; - canGain = true; - break; - } - } - } - else - canGain = true; - } + if (tskill < tcap && from.Skills[Skill].Lock == SkillLock.Up) + { + if (from.SkillsTotal + newValue * 10 > from.SkillsCap) + { + int ns = from.Skills.Length; // number of items in from.Skills[] - if ( !canGain ) - { - from.SendLocalizedMessage( 1094935 ); /*You cannot increase this skill at this time. The skill may be locked or set to lower in your skill menu. + for (int i = 0; i < ns; i++) + // skill must point down and its value must be enough + if (from.Skills[i].Lock == SkillLock.Down && from.Skills[i].Base >= newValue) + { + from.Skills[i].Base -= newValue; + canGain = true; + break; + } + } + else + { + canGain = true; + } + } + + if (!canGain) + { + from.SendLocalizedMessage( + 1094935); /*You cannot increase this skill at this time. The skill may be locked or set to lower in your skill menu. *If you are at your total skill cap, you must use a Powerscroll to increase your current skill cap.*/ - return; - } + return; + } - from.SendLocalizedMessage( 1049513, GetNameLocalized() ); // You feel a surge of magic as the scroll enhances your ~1_type~! + from.SendLocalizedMessage(1049513, + GetNameLocalized()); // You feel a surge of magic as the scroll enhances your ~1_type~! - from.Skills[Skill].Base += newValue; + from.Skills[Skill].Base += newValue; - Effects.PlaySound( from.Location, from.Map, 0x1F7 ); - Effects.SendTargetParticles( from, 0x373A, 35, 45, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); - Effects.SendTargetParticles( from, 0x376A, 35, 45, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); + Effects.PlaySound(from.Location, from.Map, 0x1F7); + Effects.SendTargetParticles(from, 0x373A, 35, 45, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); + Effects.SendTargetParticles(from, 0x376A, 35, 45, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); - Delete(); - } + Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = ( InheritsItem ? 0 : reader.ReadInt() ); //Required for SpecialScroll insertion + int version = InheritsItem ? 0 : reader.ReadInt(); //Required for SpecialScroll insertion - LootType = LootType.Cursed; - Insured = false; + LootType = LootType.Cursed; + Insured = false; - if (Hue == 0x7E) - Hue = 0x490; - } - } -} + if (Hue == 0x7E) + Hue = 0x490; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Special Scrolls/SpecialScroll.cs b/Scripts/Items/Special/Special Scrolls/SpecialScroll.cs index de8d8e372..0313e104e 100644 --- a/Scripts/Items/Special/Special Scrolls/SpecialScroll.cs +++ b/Scripts/Items/Special/Special Scrolls/SpecialScroll.cs @@ -1,171 +1,171 @@ -using System; using Server.Gumps; using Server.Network; namespace Server.Items { - public abstract class SpecialScroll : Item - { - #region Old Item Serialization Vars - /* DO NOT USE! Only used in serialization of special scrolls that originally derived from Item */ + public abstract class SpecialScroll : Item + { + public SpecialScroll(SkillName skill, double value) : base(0x14F0) + { + LootType = LootType.Cursed; + Weight = 1.0; - protected bool InheritsItem { get; private set; } + Skill = skill; + Value = value; + } - #endregion + public SpecialScroll(Serial serial) : base(serial) + { + } - public abstract int Message{ get; } - public virtual int Title => 0; - public abstract string DefaultTitle{ get; } + #region Old Item Serialization Vars - public SpecialScroll( SkillName skill, double value ) : base( 0x14F0 ) - { - LootType = LootType.Cursed; - Weight = 1.0; + /* DO NOT USE! Only used in serialization of special scrolls that originally derived from Item */ - Skill = skill; - Value = value; - } + protected bool InheritsItem{ get; private set; } - public SpecialScroll( Serial serial ) : base( serial ) - { - } + #endregion - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill { get; set; } + public abstract int Message{ get; } + public virtual int Title => 0; + public abstract string DefaultTitle{ get; } - [CommandProperty( AccessLevel.GameMaster )] - public double Value { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill{ get; set; } - public virtual string GetNameLocalized() - { - return string.Concat( "#", AosSkillBonuses.GetLabel( Skill ).ToString() ); - } + [CommandProperty(AccessLevel.GameMaster)] + public double Value{ get; set; } - public virtual string GetName() - { - int index = (int)Skill; - SkillInfo[] table = SkillInfo.Table; + public virtual string GetNameLocalized() + { + return string.Concat("#", AosSkillBonuses.GetLabel(Skill).ToString()); + } - if ( index >= 0 && index < table.Length ) - return table[index].Name.ToLower(); - return "???"; - } + public virtual string GetName() + { + int index = (int)Skill; + SkillInfo[] table = SkillInfo.Table; - public virtual bool CanUse( Mobile from ) - { - if ( Deleted ) - return false; + if (index >= 0 && index < table.Length) + return table[index].Name.ToLower(); + return "???"; + } - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. - return false; - } + public virtual bool CanUse(Mobile from) + { + if (Deleted) + return false; - return true; - } + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + return false; + } - public virtual void Use( Mobile from ) - { - } + return true; + } - public override void OnDoubleClick( Mobile from ) - { - if ( !CanUse( from ) ) - return; + public virtual void Use(Mobile from) + { + } - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( from, this ) ); - } + public override void OnDoubleClick(Mobile from) + { + if (!CanUse(from)) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(from, this)); + } - writer.Write( (int) 1 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) Skill ); - writer.Write( (double) Value ); - } + writer.Write(1); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write((int)Skill); + writer.Write(Value); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - { - Skill = (SkillName)reader.ReadInt(); - Value = reader.ReadDouble(); - break; - } - case 0: - { - InheritsItem = true; + int version = reader.ReadInt(); - if ( !(this is StatCapScroll) ) - Skill = (SkillName)reader.ReadInt(); - else - Skill = SkillName.Alchemy; + switch (version) + { + case 1: + { + Skill = (SkillName)reader.ReadInt(); + Value = reader.ReadDouble(); + break; + } + case 0: + { + InheritsItem = true; - if ( this is ScrollofAlacrity ) - Value = 0.0; - else if ( this is StatCapScroll ) - Value = (double)reader.ReadInt(); - else - Value = reader.ReadDouble(); + if (!(this is StatCapScroll)) + Skill = (SkillName)reader.ReadInt(); + else + Skill = SkillName.Alchemy; - break; - } - } - } + if (this is ScrollofAlacrity) + Value = 0.0; + else if (this is StatCapScroll) + Value = reader.ReadInt(); + else + Value = reader.ReadDouble(); - public class InternalGump : Gump - { - private Mobile m_Mobile; - private SpecialScroll m_Scroll; + break; + } + } + } - public InternalGump( Mobile mobile, SpecialScroll scroll ) : base( 25, 50 ) - { - m_Mobile = mobile; - m_Scroll = scroll; + public class InternalGump : Gump + { + private Mobile m_Mobile; + private SpecialScroll m_Scroll; - AddPage( 0 ); + public InternalGump(Mobile mobile, SpecialScroll scroll) : base(25, 50) + { + m_Mobile = mobile; + m_Scroll = scroll; - AddBackground( 25, 10, 420, 200, 5054 ); + AddPage(0); - AddImageTiled( 33, 20, 401, 181, 2624 ); - AddAlphaRegion( 33, 20, 401, 181 ); + AddBackground(25, 10, 420, 200, 5054); - AddHtmlLocalized( 40, 48, 387, 100, m_Scroll.Message, true, true ); + AddImageTiled(33, 20, 401, 181, 2624); + AddAlphaRegion(33, 20, 401, 181); - AddHtmlLocalized( 125, 148, 200, 20, 1049478, 0xFFFFFF, false, false ); // Do you wish to use this scroll? + AddHtmlLocalized(40, 48, 387, 100, m_Scroll.Message, true, true); - AddButton( 100, 172, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 135, 172, 120, 20, 1046362, 0xFFFFFF, false, false ); // Yes + AddHtmlLocalized(125, 148, 200, 20, 1049478, 0xFFFFFF, false, false); // Do you wish to use this scroll? - AddButton( 275, 172, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 310, 172, 120, 20, 1046363, 0xFFFFFF, false, false ); // No + AddButton(100, 172, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(135, 172, 120, 20, 1046362, 0xFFFFFF, false, false); // Yes - if ( m_Scroll.Title != 0 ) - AddHtmlLocalized( 40, 20, 260, 20, m_Scroll.Title, 0xFFFFFF, false, false ); - else - AddHtml( 40, 20, 260, 20, m_Scroll.DefaultTitle, false, false ); + AddButton(275, 172, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(310, 172, 120, 20, 1046363, 0xFFFFFF, false, false); // No - if ( m_Scroll is StatCapScroll ) - AddHtmlLocalized( 310, 20, 120, 20, 1038019, 0xFFFFFF, false, false ); // Power - else - AddHtmlLocalized( 310, 20, 120, 20, AosSkillBonuses.GetLabel( m_Scroll.Skill ), 0xFFFFFF, false, false ); - } + if (m_Scroll.Title != 0) + AddHtmlLocalized(40, 20, 260, 20, m_Scroll.Title, 0xFFFFFF, false, false); + else + AddHtml(40, 20, 260, 20, m_Scroll.DefaultTitle, false, false); - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Scroll.Use( m_Mobile ); - } - } - } -} + if (m_Scroll is StatCapScroll) + AddHtmlLocalized(310, 20, 120, 20, 1038019, 0xFFFFFF, false, false); // Power + else + AddHtmlLocalized(310, 20, 120, 20, AosSkillBonuses.GetLabel(m_Scroll.Skill), 0xFFFFFF, false, false); + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 1) + m_Scroll.Use(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Special Scrolls/StatScroll.cs b/Scripts/Items/Special/Special Scrolls/StatScroll.cs index 599d103a4..8edbe31f6 100644 --- a/Scripts/Items/Special/Special Scrolls/StatScroll.cs +++ b/Scripts/Items/Special/Special Scrolls/StatScroll.cs @@ -1,130 +1,135 @@ -using System; using Server.Mobiles; namespace Server.Items { - public class StatCapScroll : SpecialScroll - { - public override int Message => 1049469; /* Using a scroll increases the maximum amount of a specific skill or your maximum statistics. + public class StatCapScroll : SpecialScroll + { + public StatCapScroll() : this(105) + { + } + + [Constructible] + public StatCapScroll(int value) : base(SkillName.Alchemy, value) + { + Hue = 0x481; + } + + public StatCapScroll(Serial serial) : base(serial) + { + } + + public override int Message => + 1049469; /* Using a scroll increases the maximum amount of a specific skill or your maximum statistics. * When used, the effect is not immediately seen without a gain of points with that skill or statistics. * You can view your maximum skill values in your skills window. * You can view your maximum statistic value in your statistics window. */ - public override int Title - { - get - { - int level = ( (int)Value - 230 ) / 5; - if ( level >= 0 && level <= 4 && Value % 5 == 0 ) - return 1049458 + level; /* Wonderous Scroll (+5 Maximum Stats): OR + public override int Title + { + get + { + int level = ((int)Value - 230) / 5; + + if (level >= 0 && level <= 4 && Value % 5 == 0) + return 1049458 + level; /* Wonderous Scroll (+5 Maximum Stats): OR * Exalted Scroll (+10 Maximum Stats): OR * Mythical Scroll (+15 Maximum Stats): OR * Legendary Scroll (+20 Maximum Stats): OR * Ultimate Scroll (+25 Maximum Stats): */ - return 0; - } - } + return 0; + } + } - public override string DefaultTitle => - $"Power Scroll ({(((int) Value - 225) >= 0 ? "+" : "")}{(int) Value - 225} Maximum Stats):"; + public override string DefaultTitle => + $"Power Scroll ({((int)Value - 225 >= 0 ? "+" : "")}{(int)Value - 225} Maximum Stats):"; - public StatCapScroll() : this( 105 ) - { - } + public override void AddNameProperty(ObjectPropertyList list) + { + int level = ((int)Value - 230) / 5; - [Constructible] - public StatCapScroll( int value ) : base( SkillName.Alchemy, value ) - { - Hue = 0x481; - } - - public StatCapScroll( Serial serial ) : base( serial ) - { - } - - public override void AddNameProperty(ObjectPropertyList list) - { - int level = ( (int)Value - 230 ) / 5; - - if ( level >= 0 && level <= 4 && (int)Value % 5 == 0 ) - list.Add( 1049463 + level, "#1049476" ); /* a wonderous scroll of ~1_type~ (+5 Maximum Stats) OR + if (level >= 0 && level <= 4 && (int)Value % 5 == 0) + list.Add(1049463 + level, "#1049476"); /* a wonderous scroll of ~1_type~ (+5 Maximum Stats) OR * an exalted scroll of ~1_type~ (+10 Maximum Stats) OR * a mythical scroll of ~1_type~ (+15 Maximum Stats) OR * a legendary scroll of ~1_type~ (+20 Maximum Stats) OR * an ultimate scroll of ~1_type~ (+25 Maximum Stats) */ - else - list.Add( "a scroll of power ({0}{1} Maximum Stats)", (Value - 225) >= 0 ? "+" : "", Value - 225 ); - } + else + list.Add("a scroll of power ({0}{1} Maximum Stats)", Value - 225 >= 0 ? "+" : "", Value - 225); + } - public override void OnSingleClick( Mobile from ) - { - int level = ( (int)Value - 230 ) / 5; + public override void OnSingleClick(Mobile from) + { + int level = ((int)Value - 230) / 5; - if ( level >= 0 && level <= 4 && (int)Value % 5 == 0 ) - LabelTo( from, 1049463 + level, "#1049476" ); - else - LabelTo( from, "a scroll of power ({0}{1} Maximum Stats)", (Value - 225) >= 0 ? "+" : "", Value - 225 ); - } + if (level >= 0 && level <= 4 && (int)Value % 5 == 0) + LabelTo(from, 1049463 + level, "#1049476"); + else + LabelTo(from, "a scroll of power ({0}{1} Maximum Stats)", Value - 225 >= 0 ? "+" : "", Value - 225); + } - public override bool CanUse( Mobile from ) - { - if ( !base.CanUse( from ) ) - return false; + public override bool CanUse(Mobile from) + { + if (!base.CanUse(from)) + return false; - int newValue = (int)Value; + int newValue = (int)Value; - if ( from is PlayerMobile mobile && mobile.HasStatReward ) - newValue += 5; + if (from is PlayerMobile mobile && mobile.HasStatReward) + newValue += 5; - if ( from.StatCap >= newValue ) - { - from.SendLocalizedMessage( 1049510 ); // Your stats are too high for this power scroll. - return false; - } + if (from.StatCap >= newValue) + { + from.SendLocalizedMessage(1049510); // Your stats are too high for this power scroll. + return false; + } - return true; - } + return true; + } - public override void Use( Mobile from ) - { - if ( !CanUse( from ) ) - return; + public override void Use(Mobile from) + { + if (!CanUse(from)) + return; - from.SendLocalizedMessage( 1049512 ); // You feel a surge of magic as the scroll enhances your powers! + from.SendLocalizedMessage(1049512); // You feel a surge of magic as the scroll enhances your powers! - if ( from is PlayerMobile mobile && mobile.HasStatReward ) - mobile.StatCap = (int)Value + 5; - else - from.StatCap = (int)Value; + if (from is PlayerMobile mobile && mobile.HasStatReward) + mobile.StatCap = (int)Value + 5; + else + from.StatCap = (int)Value; - Effects.SendLocationParticles( EffectItem.Create( from.Location, from.Map, EffectItem.DefaultDuration ), 0, 0, 0, 0, 0, 5060, 0 ); - Effects.PlaySound( from.Location, from.Map, 0x243 ); + Effects.SendLocationParticles(EffectItem.Create(from.Location, from.Map, EffectItem.DefaultDuration), 0, 0, 0, 0, + 0, 5060, 0); + Effects.PlaySound(from.Location, from.Map, 0x243); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( from.X - 6, from.Y - 6, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( from.X - 4, from.Y - 6, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( from.X - 6, from.Y - 4, from.Z + 15 ), from.Map ), from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100 ); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(from.X - 6, from.Y - 6, from.Z + 15), from.Map), + from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(from.X - 4, from.Y - 6, from.Z + 15), from.Map), + from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); + Effects.SendMovingParticles(new Entity(Serial.Zero, new Point3D(from.X - 6, from.Y - 4, from.Z + 15), from.Map), + from, 0x36D4, 7, 0, false, true, 0x497, 0, 9502, 1, 0, (EffectLayer)255, 0x100); - Effects.SendTargetParticles( from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100 ); + Effects.SendTargetParticles(from, 0x375A, 35, 90, 0x00, 0x00, 9502, (EffectLayer)255, 0x100); - Delete(); - } + Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = ( InheritsItem ? 0 : reader.ReadInt() ); //Required for SpecialScroll insertion + int version = InheritsItem ? 0 : reader.ReadInt(); //Required for SpecialScroll insertion - LootType = LootType.Cursed; - Insured = false; - } - } -} + LootType = LootType.Cursed; + Insured = false; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Valentines/2007/RedVelvetGiftBox.cs b/Scripts/Items/Special/Valentines/2007/RedVelvetGiftBox.cs index 63a81b89d..0e581e3c3 100644 --- a/Scripts/Items/Special/Valentines/2007/RedVelvetGiftBox.cs +++ b/Scripts/Items/Special/Valentines/2007/RedVelvetGiftBox.cs @@ -1,5 +1,3 @@ - - /* * Simply add this box with param true to create the entire valentine's 2007 package. * Adding it with no params or false will create an empty box. @@ -7,58 +5,59 @@ namespace Server.Items { - public class RedVelvetGiftBox : BaseContainer - { - public override int DefaultGumpID => 0x3f; - public override int LabelNumber => 1077596; // A Red Velvet Box + public class RedVelvetGiftBox : BaseContainer + { + [Constructible] + public RedVelvetGiftBox() + : this(false) + { + } - [Constructible] - public RedVelvetGiftBox() - : this( false ) - { - } + [Constructible] + public RedVelvetGiftBox(bool fill) + : base(0xE7A) + { + Hue = 0x20; - [Constructible] - public RedVelvetGiftBox( bool fill ) - : base( 0xE7A ) - { - Hue = 0x20; + if (fill) + { + for (int i = 0; i < 5; i++) + { + AddToBox(new ValentinesCardSouth(), new Point3D(60 + i * 10, 47, 0)); + AddToBox(new ValentinesCardEast(), new Point3D(20 + i * 10, 72, 0)); + } - if (fill) - { - for (int i = 0; i < 5; i++) - { - AddToBox(new ValentinesCardSouth(), new Point3D(60 + (i * 10), 47, 0)); - AddToBox(new ValentinesCardEast(), new Point3D(20 + (i * 10), 72, 0)); - } - AddToBox(new Bacon(), new Point3D(90, 85, 0)); - AddToBox(new RoseInAVase(), new Point3D(130, 55, 0)); - } - } + AddToBox(new Bacon(), new Point3D(90, 85, 0)); + AddToBox(new RoseInAVase(), new Point3D(130, 55, 0)); + } + } - public virtual void AddToBox(Item item, Point3D loc) - { - DropItem(item); - item.Location = loc; - } + public RedVelvetGiftBox(Serial serial) + : base(serial) + { + } - public RedVelvetGiftBox( Serial serial ) - : base( serial ) - { - } + public override int DefaultGumpID => 0x3f; + public override int LabelNumber => 1077596; // A Red Velvet Box - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public virtual void AddToBox(Item item, Point3D loc) + { + DropItem(item); + item.Location = loc; + } - writer.Write( (int)0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Valentines/2007/RoseInAVase.cs b/Scripts/Items/Special/Valentines/2007/RoseInAVase.cs index 5bc94d906..32fab937e 100644 --- a/Scripts/Items/Special/Valentines/2007/RoseInAVase.cs +++ b/Scripts/Items/Special/Valentines/2007/RoseInAVase.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public class RoseInAVase : Item /* TODO: when dye tub changes are implemented, furny dyable this */ - { - public override int LabelNumber => 1023760; // A Rose in a Vase 1023760 + public class RoseInAVase : Item /* TODO: when dye tub changes are implemented, furny dyable this */ + { + [Constructible] + public RoseInAVase() + : base(0x0EB0) + { + Hue = 0x20; + LootType = LootType.Blessed; + } - [Constructible] - public RoseInAVase( ) - : base( 0x0EB0 ) - { - Hue = 0x20; - LootType = LootType.Blessed; - } + public RoseInAVase(Serial serial) + : base(serial) + { + } - public RoseInAVase( Serial serial ) - : base( serial ) - { - } + public override int LabelNumber => 1023760; // A Rose in a Vase 1023760 - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Valentines/2007/ValentinesCard.cs b/Scripts/Items/Special/Valentines/2007/ValentinesCard.cs index 1a2b04e13..0e064bf50 100644 --- a/Scripts/Items/Special/Valentines/2007/ValentinesCard.cs +++ b/Scripts/Items/Special/Valentines/2007/ValentinesCard.cs @@ -1,193 +1,197 @@ -using System; -using Server.Mobiles; +using Server.Mobiles; using Server.Targeting; namespace Server.Items { - public class ValentinesCard : Item - { - public override string DefaultName => "a Valentine's card"; + public class ValentinesCard : Item + { + private static string Unsigned = "___"; + private string m_From; - [CommandProperty(AccessLevel.GameMaster)] - public virtual string From { get => m_From; - set => m_From = value; - } + private int m_LabelNumber; + private string m_To; - [CommandProperty(AccessLevel.GameMaster)] - public virtual string To { get => m_To; - set => m_To = value; - } + [Constructible] + public ValentinesCard(int itemid) + : base(itemid) + { + LootType = LootType.Blessed; + Hue = Utility.RandomDouble() < .001 ? 0x47E : 0xE8; + m_LabelNumber = Utility.Random(1077589, 5); + } - private static string Unsigned = "___"; + public ValentinesCard(Serial serial) + : base(serial) + { + } - private int m_LabelNumber; - private string m_From; - private string m_To; + public override string DefaultName => "a Valentine's card"; - [Constructible] - public ValentinesCard( int itemid ) - : base(itemid) - { - LootType = LootType.Blessed; - Hue = Utility.RandomDouble() < .001 ? 0x47E : 0xE8; - m_LabelNumber = Utility.Random(1077589, 5); - } + [CommandProperty(AccessLevel.GameMaster)] + public virtual string From + { + get => m_From; + set => m_From = value; + } - /* - * Five possible messages to be signed: - * - * To my one true love, ~1_target_player~. Signed: ~2_player~ 1077589 - * You’ve pwnd my heart, ~1_target_player~. Signed: ~2_player~ 1077590 - * Happy Valentine’s Day, ~1_target_player~. Signed: ~2_player~ 1077591 - * Blackrock has driven me crazy... for ~1_target_player~! Signed: ~2_player~ 1077592 - * You light my Candle of Love, ~1_target_player~! Signed: ~2_player~ 1077593 - * - */ + [CommandProperty(AccessLevel.GameMaster)] + public virtual string To + { + get => m_To; + set => m_To = value; + } - public override void AddNameProperty(ObjectPropertyList list) - { - list.Add(m_LabelNumber, $"{m_To ?? Unsigned}\t{m_From ?? Unsigned}"); - } + /* + * Five possible messages to be signed: + * + * To my one true love, ~1_target_player~. Signed: ~2_player~ 1077589 + * You’ve pwnd my heart, ~1_target_player~. Signed: ~2_player~ 1077590 + * Happy Valentine’s Day, ~1_target_player~. Signed: ~2_player~ 1077591 + * Blackrock has driven me crazy... for ~1_target_player~! Signed: ~2_player~ 1077592 + * You light my Candle of Love, ~1_target_player~! Signed: ~2_player~ 1077593 + * + */ - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(m_LabelNumber, $"{m_To ?? Unsigned}\t{m_From ?? Unsigned}"); + } - LabelTo( from, m_LabelNumber, - $"{m_To ?? Unsigned}\t{m_From ?? Unsigned}"); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - public override void OnDoubleClick(Mobile from) - { - if (m_To == null) - { - if (IsChildOf(from)) - { - from.BeginTarget(10, false, TargetFlags.None, OnTarget); + LabelTo(from, m_LabelNumber, + $"{m_To ?? Unsigned}\t{m_From ?? Unsigned}"); + } - from.SendLocalizedMessage(1077497); //To whom do you wish to give this card? - } - else - { - from.SendLocalizedMessage(1080063); // This must be in your backpack to use it. - } - } - } + public override void OnDoubleClick(Mobile from) + { + if (m_To == null) + { + if (IsChildOf(from)) + { + from.BeginTarget(10, false, TargetFlags.None, OnTarget); - public virtual void OnTarget(Mobile from, object targeted) - { - if (!Deleted) - { - if (targeted != null && targeted is Mobile to) - { - if (to is PlayerMobile) - { - if (to != from) - { - m_From = from.Name; - m_To = to.Name; - from.SendLocalizedMessage(1077498); //You fill out the card. Hopefully the other person actually likes you... - InvalidateProperties(); - } - else - { - from.SendLocalizedMessage(1077495); //You can't give yourself a card, silly! - } - } - else - { - from.SendLocalizedMessage(1077496); //You can't possibly be THAT lonely! - } - } - else - { - from.SendLocalizedMessage(1077488); //That's not another player! - } - } - } + from.SendLocalizedMessage(1077497); //To whom do you wish to give this card? + } + else + { + from.SendLocalizedMessage(1080063); // This must be in your backpack to use it. + } + } + } - public ValentinesCard(Serial serial) - : base( serial ) - { - } + public virtual void OnTarget(Mobile from, object targeted) + { + if (!Deleted) + { + if (targeted != null && targeted is Mobile to) + { + if (to is PlayerMobile) + { + if (to != from) + { + m_From = from.Name; + m_To = to.Name; + from.SendLocalizedMessage( + 1077498); //You fill out the card. Hopefully the other person actually likes you... + InvalidateProperties(); + } + else + { + from.SendLocalizedMessage(1077495); //You can't give yourself a card, silly! + } + } + else + { + from.SendLocalizedMessage(1077496); //You can't possibly be THAT lonely! + } + } + else + { + from.SendLocalizedMessage(1077488); //That's not another player! + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version - writer.Write((int)m_LabelNumber); - writer.Write((string)m_From); - writer.Write((string)m_To); - } + writer.Write(0); // version + writer.Write(m_LabelNumber); + writer.Write(m_From); + writer.Write(m_To); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - m_LabelNumber = reader.ReadInt(); - m_From = reader.ReadString(); - m_To = reader.ReadString(); + int version = reader.ReadInt(); + m_LabelNumber = reader.ReadInt(); + m_From = reader.ReadString(); + m_To = reader.ReadString(); - Utility.Intern(ref m_From); - Utility.Intern(ref m_To); - } - } + Utility.Intern(ref m_From); + Utility.Intern(ref m_To); + } + } - public class ValentinesCardSouth : ValentinesCard - { - [Constructible] - public ValentinesCardSouth() - : base(0x0EBD) - { - } + public class ValentinesCardSouth : ValentinesCard + { + [Constructible] + public ValentinesCardSouth() + : base(0x0EBD) + { + } - public ValentinesCardSouth(Serial serial) - : base(serial) - { - } + public ValentinesCardSouth(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } - public class ValentinesCardEast : ValentinesCard - { - [Constructible] - public ValentinesCardEast() - : base(0x0EBE) - { - } + public class ValentinesCardEast : ValentinesCard + { + [Constructible] + public ValentinesCardEast() + : base(0x0EBE) + { + } - public ValentinesCardEast(Serial serial) - : base(serial) - { - } + public ValentinesCardEast(Serial serial) + : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/AnkhOfSacrifice.cs b/Scripts/Items/Special/Veteran Rewards/AnkhOfSacrifice.cs index 3b07625bd..89392930e 100644 --- a/Scripts/Items/Special/Veteran Rewards/AnkhOfSacrifice.cs +++ b/Scripts/Items/Special/Veteran Rewards/AnkhOfSacrifice.cs @@ -1,328 +1,348 @@ using System; using System.Collections.Generic; +using Server.ContextMenus; +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Mobiles; using Server.Network; -using Server.ContextMenus; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class AnkhOfSacrificeComponent : AddonComponent - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override int LabelNumber => 1027772; // Ankh of Sacrifice + public class AnkhOfSacrificeComponent : AddonComponent + { + public AnkhOfSacrificeComponent(int itemID) : base(itemID) + { + } - public AnkhOfSacrificeComponent( int itemID ) : base( itemID ) - { - } + public AnkhOfSacrificeComponent(Serial serial) : base(serial) + { + } - public AnkhOfSacrificeComponent( Serial serial ) : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public override int LabelNumber => 1027772; // Ankh of Sacrifice - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - if ( from is PlayerMobile mobile ) - list.Add( new LockKarmaEntry( mobile, Addon as AnkhOfSacrificeAddon ) ); + if (from is PlayerMobile mobile) + list.Add(new LockKarmaEntry(mobile, Addon as AnkhOfSacrificeAddon)); - list.Add( new ResurrectEntry( from, Addon as AnkhOfSacrificeAddon ) ); - } + list.Add(new ResurrectEntry(from, Addon as AnkhOfSacrificeAddon)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public static void Resurrect( PlayerMobile m, AnkhOfSacrificeAddon ankh ) - { - if ( m == null ) - { - } - else if ( !m.InRange( ankh.GetWorldLocation(), 2 ) ) - { - m.SendLocalizedMessage( 500446 ); // That is too far away. - } - else if ( m.Alive ) - { - m.SendLocalizedMessage( 1060197 ); // You are not dead, and thus cannot be resurrected! - } - else if ( m.AnkhNextUse > DateTime.UtcNow ) - { - TimeSpan delay = m.AnkhNextUse - DateTime.UtcNow; + public static void Resurrect(PlayerMobile m, AnkhOfSacrificeAddon ankh) + { + if (m == null) + { + } + else if (!m.InRange(ankh.GetWorldLocation(), 2)) + { + m.SendLocalizedMessage(500446); // That is too far away. + } + else if (m.Alive) + { + m.SendLocalizedMessage(1060197); // You are not dead, and thus cannot be resurrected! + } + else if (m.AnkhNextUse > DateTime.UtcNow) + { + TimeSpan delay = m.AnkhNextUse - DateTime.UtcNow; - if ( delay.TotalMinutes > 0 ) - m.SendLocalizedMessage( 1079265, Math.Round( delay.TotalMinutes ).ToString() ); // You must wait ~1_minutes~ minutes before you can use this item. - else - m.SendLocalizedMessage( 1079263, Math.Round( delay.TotalSeconds ).ToString() ); // You must wait ~1_seconds~ seconds before you can use this item. - } - else - { - m.CloseGump( typeof( AnkhResurrectGump ) ); - m.SendGump( new AnkhResurrectGump( m, ResurrectMessage.VirtueShrine ) ); - } - } + if (delay.TotalMinutes > 0) + m.SendLocalizedMessage(1079265, + Math.Round(delay.TotalMinutes) + .ToString()); // You must wait ~1_minutes~ minutes before you can use this item. + else + m.SendLocalizedMessage(1079263, + Math.Round(delay.TotalSeconds) + .ToString()); // You must wait ~1_seconds~ seconds before you can use this item. + } + else + { + m.CloseGump(typeof(AnkhResurrectGump)); + m.SendGump(new AnkhResurrectGump(m, ResurrectMessage.VirtueShrine)); + } + } - private class ResurrectEntry : ContextMenuEntry - { - private Mobile m_Mobile; - private AnkhOfSacrificeAddon m_Ankh; + private class ResurrectEntry : ContextMenuEntry + { + private AnkhOfSacrificeAddon m_Ankh; + private Mobile m_Mobile; - public ResurrectEntry( Mobile mobile, AnkhOfSacrificeAddon ankh ) : base( 6195, 2 ) - { - m_Mobile = mobile; - m_Ankh = ankh; - } + public ResurrectEntry(Mobile mobile, AnkhOfSacrificeAddon ankh) : base(6195, 2) + { + m_Mobile = mobile; + m_Ankh = ankh; + } - public override void OnClick() - { - if ( m_Ankh == null || m_Ankh.Deleted ) - return; + public override void OnClick() + { + if (m_Ankh == null || m_Ankh.Deleted) + return; - Resurrect( m_Mobile as PlayerMobile, m_Ankh ); - } - } + Resurrect(m_Mobile as PlayerMobile, m_Ankh); + } + } - private class LockKarmaEntry : ContextMenuEntry - { - private PlayerMobile m_Mobile; - private AnkhOfSacrificeAddon m_Ankh; + private class LockKarmaEntry : ContextMenuEntry + { + private AnkhOfSacrificeAddon m_Ankh; + private PlayerMobile m_Mobile; - public LockKarmaEntry( PlayerMobile mobile, AnkhOfSacrificeAddon ankh ) : base( mobile.KarmaLocked ? 6197 : 6196, 2 ) - { - m_Mobile = mobile; - m_Ankh = ankh; - } + public LockKarmaEntry(PlayerMobile mobile, AnkhOfSacrificeAddon ankh) : base(mobile.KarmaLocked ? 6197 : 6196, 2) + { + m_Mobile = mobile; + m_Ankh = ankh; + } - public override void OnClick() - { - if ( !m_Mobile.InRange( m_Ankh.GetWorldLocation(), 2 ) ) - m_Mobile.SendLocalizedMessage( 500446 ); // That is too far away. - else - { - m_Mobile.KarmaLocked = !m_Mobile.KarmaLocked; + public override void OnClick() + { + if (!m_Mobile.InRange(m_Ankh.GetWorldLocation(), 2)) + { + m_Mobile.SendLocalizedMessage(500446); // That is too far away. + } + else + { + m_Mobile.KarmaLocked = !m_Mobile.KarmaLocked; - if ( m_Mobile.KarmaLocked ) - m_Mobile.SendLocalizedMessage( 1060192 ); // Your karma has been locked. Your karma can no longer be raised. - else - m_Mobile.SendLocalizedMessage( 1060191 ); // Your karma has been unlocked. Your karma can be raised again. - } - } - } + if (m_Mobile.KarmaLocked) + m_Mobile.SendLocalizedMessage( + 1060192); // Your karma has been locked. Your karma can no longer be raised. + else + m_Mobile.SendLocalizedMessage( + 1060191); // Your karma has been unlocked. Your karma can be raised again. + } + } + } - private class AnkhResurrectGump : ResurrectGump - { - public AnkhResurrectGump( Mobile owner, ResurrectMessage msg ) : base( owner, owner, msg, false ) - { - } + private class AnkhResurrectGump : ResurrectGump + { + public AnkhResurrectGump(Mobile owner, ResurrectMessage msg) : base(owner, owner, msg, false) + { + } - public override void OnResponse( NetState state, RelayInfo info ) - { - Mobile from = state.Mobile; + public override void OnResponse(NetState state, RelayInfo info) + { + Mobile from = state.Mobile; - if ( info.ButtonID == 1 || info.ButtonID == 2 ) - { - if ( from.Map == null || !from.Map.CanFit( from.Location, 16, false, false ) ) - { - from.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - return; - } + if (info.ButtonID == 1 || info.ButtonID == 2) + { + if (from.Map == null || !from.Map.CanFit(from.Location, 16, false, false)) + { + from.SendLocalizedMessage(502391); // Thou can not be resurrected there! + return; + } - if ( from is PlayerMobile mobile ) - { - mobile.AnkhNextUse = DateTime.UtcNow + TimeSpan.FromHours( 1 ); - } + if (from is PlayerMobile mobile) mobile.AnkhNextUse = DateTime.UtcNow + TimeSpan.FromHours(1); - base.OnResponse( state, info ); - } - } - } - } - public class AnkhOfSacrificeAddon : BaseAddon, IRewardItem - { - public override bool HandlesOnMovement => true; + base.OnResponse(state, info); + } + } + } + } - public override BaseAddonDeed Deed - { - get - { - AnkhOfSacrificeDeed deed = new AnkhOfSacrificeDeed(); - deed.IsRewardItem = m_IsRewardItem; + public class AnkhOfSacrificeAddon : BaseAddon, IRewardItem + { + private bool m_IsRewardItem; - return deed; - } - } + [Constructible] + public AnkhOfSacrificeAddon(bool east) + { + if (east) + { + AddComponent(new AnkhOfSacrificeComponent(0x1D98), 0, 0, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1D97), 0, 1, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CD6), 1, 0, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CD4), 1, 1, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CD0), 2, 0, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CCE), 2, 1, 0); + } + else + { + AddComponent(new AnkhOfSacrificeComponent(0x1E5D), 0, 0, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1E5C), 1, 0, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CD2), 0, 1, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CD8), 1, 1, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CCD), 0, 2, 0); + AddComponent(new AnkhOfSacrificeComponent(0x1CCE), 1, 2, 0); + } + } - private bool m_IsRewardItem; + public AnkhOfSacrificeAddon(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public override bool HandlesOnMovement => true; - [Constructible] - public AnkhOfSacrificeAddon( bool east ) - { - if ( east ) - { - AddComponent( new AnkhOfSacrificeComponent( 0x1D98 ), 0, 0, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1D97 ), 0, 1, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CD6 ), 1, 0, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CD4 ), 1, 1, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CD0 ), 2, 0, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CCE ), 2, 1, 0 ); - } - else - { - AddComponent( new AnkhOfSacrificeComponent( 0x1E5D ), 0, 0, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1E5C ), 1, 0, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CD2 ), 0, 1, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CD8 ), 1, 1, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CCD ), 0, 2, 0 ); - AddComponent( new AnkhOfSacrificeComponent( 0x1CCE ), 1, 2, 0 ); - } - } + public override BaseAddonDeed Deed + { + get + { + AnkhOfSacrificeDeed deed = new AnkhOfSacrificeDeed(); + deed.IsRewardItem = m_IsRewardItem; - public AnkhOfSacrificeAddon( Serial serial ) : base( serial ) - { - } + return deed; + } + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( !m.Alive && Utility.InRange( Location, m.Location, 1 ) && !Utility.InRange( Location, oldLocation, 1 ) ) - AnkhOfSacrificeComponent.Resurrect( m as PlayerMobile, this ); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (!m.Alive && Utility.InRange(Location, m.Location, 1) && !Utility.InRange(Location, oldLocation, 1)) + AnkhOfSacrificeComponent.Resurrect(m as PlayerMobile, this); + } - writer.WriteEncodedInt( 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (bool) m_IsRewardItem ); - } + writer.WriteEncodedInt(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_IsRewardItem); + } - int version = reader.ReadEncodedInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_IsRewardItem = reader.ReadBool(); - } - } + int version = reader.ReadEncodedInt(); - public class AnkhOfSacrificeDeed : BaseAddonDeed, IRewardItem, IRewardOption - { - public override int LabelNumber => 1080397; // Deed For An Ankh Of Sacrifice + m_IsRewardItem = reader.ReadBool(); + } + } - public override BaseAddon Addon - { - get - { - AnkhOfSacrificeAddon addon = new AnkhOfSacrificeAddon( m_East ); - addon.IsRewardItem = m_IsRewardItem; + public class AnkhOfSacrificeDeed : BaseAddonDeed, IRewardItem, IRewardOption + { + private bool m_East; + private bool m_IsRewardItem; - return addon; - } - } + [Constructible] + public AnkhOfSacrificeDeed() : this(false) + { + } - private bool m_East; - private bool m_IsRewardItem; + [Constructible] + public AnkhOfSacrificeDeed(bool isRewardItem) + { + LootType = LootType.Blessed; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + m_IsRewardItem = isRewardItem; + } - [Constructible] - public AnkhOfSacrificeDeed() : this( false ) - { - } + public AnkhOfSacrificeDeed(Serial serial) : base(serial) + { + } - [Constructible] - public AnkhOfSacrificeDeed( bool isRewardItem ) - { - LootType = LootType.Blessed; + public override int LabelNumber => 1080397; // Deed For An Ankh Of Sacrifice - m_IsRewardItem = isRewardItem; - } + public override BaseAddon Addon + { + get + { + AnkhOfSacrificeAddon addon = new AnkhOfSacrificeAddon(m_East); + addon.IsRewardItem = m_IsRewardItem; - public AnkhOfSacrificeDeed( Serial serial ) : base( serial ) - { - } + return addon; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( RewardOptionGump ) ); - from.SendGump( new RewardOptionGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public void GetOptions(RewardOptionList list) + { + list.Add(1, 1080398); // Ankh of Sacrifice South + list.Add(2, 1080399); // Ankh of Sacrifice East + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public void OnOptionSelected(Mobile from, int option) + { + switch (option) + { + case 1: + m_East = false; + break; + case 2: + m_East = true; + break; + } - if ( m_IsRewardItem ) - list.Add( 1080457 ); // 10th Year Veteran Reward - } + if (!Deleted) + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - writer.WriteEncodedInt( 0 ); // version + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(RewardOptionGump)); + from.SendGump(new RewardOptionGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - writer.Write( (bool) m_IsRewardItem ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (m_IsRewardItem) + list.Add(1080457); // 10th Year Veteran Reward + } - int version = reader.ReadEncodedInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_IsRewardItem = reader.ReadBool(); - } + writer.WriteEncodedInt(0); // version - public void GetOptions( RewardOptionList list ) - { - list.Add( 1, 1080398 ); // Ankh of Sacrifice South - list.Add( 2, 1080399 ); // Ankh of Sacrifice East - } + writer.Write(m_IsRewardItem); + } - public void OnOptionSelected( Mobile from, int option ) - { - switch ( option ) - { - case 1: m_East = false; break; - case 2: m_East = true; break; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( !Deleted ) - base.OnDoubleClick( from ); - } - } -} + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/Banner.cs b/Scripts/Items/Special/Veteran Rewards/Banner.cs index 8ddc6c841..92b8bccfd 100644 --- a/Scripts/Items/Special/Veteran Rewards/Banner.cs +++ b/Scripts/Items/Special/Veteran Rewards/Banner.cs @@ -1,380 +1,406 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Multis; using Server.Network; using Server.Targeting; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class Banner : Item, IAddon, IDyable, IRewardItem - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public Item Deed - { - get - { - BannerDeed deed = new BannerDeed(); - deed.IsRewardItem = m_IsRewardItem; - - return deed; - } - } - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - public bool FacingSouth => ( ItemID & 0x1 ) == 0; - - [Constructible] - public Banner( int itemID ) : base( itemID ) - { - LootType = LootType.Blessed; - Movable = false; - } - - public Banner( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Core.ML && m_IsRewardItem ) - list.Add( 1076218 ); // 2nd Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( RewardDemolitionGump ) ); - from.SendGump( new RewardDemolitionGump( this, 1018318 ) ); // Do you wish to re-deed this banner? - } - else - from.SendLocalizedMessage( 1018330 ); // You can only re-deed a banner if you placed it or you are the owner of the house. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; - - Hue = sender.DyedHue; - - return true; - } - - public bool CouldFit( IPoint3D p, Map map ) - { - if ( map == null || !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; - - if ( FacingSouth ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // north wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // west wall - } - } - - public class BannerDeed : Item, IRewardItem - { - public override int LabelNumber => 1041007; // a banner deed - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - [Constructible] - public BannerDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } - - public BannerDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076218 ); // 2nd Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - private class InternalGump : Gump - { - public const int Start = 0x15AE; - public const int End = 0x15F4; - - private BannerDeed m_Banner; - - public InternalGump( BannerDeed banner ) : base( 100, 200 ) - { - m_Banner = banner; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddBackground( 25, 0, 520, 230, 0xA28 ); - AddLabel( 70, 12, 0x3E3, "Choose a Banner:" ); - - - int itemID = Start; - - for ( int i = 1; i <= 4; i++ ) - { - AddPage( i ); - - for ( int j = 0; j < 8; j++, itemID += 2 ) - { - AddItem( 50 + 60 * j, 70, itemID ); - AddButton( 50 + 60 * j, 50, 0x845, 0x846, itemID, GumpButtonType.Reply, 0 ); - } - - if ( i > 1 ) - AddButton( 75, 198, 0x8AF, 0x8AF, 0, GumpButtonType.Page, i - 1 ); - - if ( i < 4 ) - AddButton( 475, 198, 0x8B0, 0x8B0, 0, GumpButtonType.Page, i + 1 ); - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Banner == null | m_Banner.Deleted ) - return; - - Mobile m = sender.Mobile; - - if ( info.ButtonID >= Start && info.ButtonID <= End ) - { - if ( ( info.ButtonID & 0x1 ) == 0 ) - { - m.SendLocalizedMessage( 1042037 ); // Where would you like to place this banner? - m.Target = new InternalTarget( m_Banner, info.ButtonID ); - } - } - } - } - - private class InternalTarget : Target - { - private BannerDeed m_Banner; - private int m_ItemID; - - public InternalTarget( BannerDeed banner, int itemID ) : base( -1, true, TargetFlags.None ) - { - m_Banner = banner; - m_ItemID = itemID; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Banner == null || m_Banner.Deleted ) - return; - - if ( m_Banner.IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsOwner( from ) ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; - - if ( p == null || map == null ) - return; - - Point3D p3d = new Point3D( p ); - ItemData id = TileData.ItemTable[ m_ItemID & TileData.MaxItemValue ]; - - if ( map.CanFit( p3d, id.Height ) ) - { - house = BaseHouse.FindHouseAt( p3d, map, id.Height ); - - if ( house != null && house.IsOwner( from ) ) - { - bool north = BaseAddon.IsWall( p3d.X, p3d.Y - 1, p3d.Z, map ); - bool west = BaseAddon.IsWall( p3d.X - 1, p3d.Y, p3d.Z, map ); - - if ( north && west ) - { - from.CloseGump( typeof( FacingGump ) ); - from.SendGump( new FacingGump( m_Banner, m_ItemID, p3d, house ) ); - } - else if ( north || west ) - { - Banner banner = null; - - if ( north ) - banner = new Banner( m_ItemID ); - else if ( west ) - banner = new Banner( m_ItemID + 1 ); - - house.Addons.Add( banner ); - - banner.IsRewardItem = m_Banner.IsRewardItem; - banner.MoveToWorld( p3d, map ); - - m_Banner.Delete(); - } - else - from.SendLocalizedMessage( 1042039 ); // The banner must be placed next to a wall. - } - else - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - else - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - private class FacingGump : Gump - { - private BannerDeed m_Banner; - private int m_ItemID; - private Point3D m_Location; - private BaseHouse m_House; - - private enum Buttons - { - Cancel, - East, - South - } - - public FacingGump( BannerDeed banner, int itemID, Point3D location, BaseHouse house ) : base( 150, 50 ) - { - m_Banner = banner; - m_ItemID = itemID; - m_Location = location; - m_House = house; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddBackground( 0, 0, 300, 150, 0xA28 ); - - AddItem( 90, 30, itemID + 1 ); - AddItem( 180, 30, itemID ); - - AddButton( 50, 35, 0x868, 0x869, (int) Buttons.East, GumpButtonType.Reply, 0 ); - AddButton( 145, 35, 0x868, 0x869, (int) Buttons.South, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Banner == null || m_Banner.Deleted || m_House == null ) - return; - - Banner banner = null; - - if ( info.ButtonID == (int) Buttons.East ) - banner = new Banner( m_ItemID + 1 ); - if ( info.ButtonID == (int) Buttons.South ) - banner = new Banner( m_ItemID ); - - if ( banner != null ) - { - m_House.Addons.Add( banner ); - - banner.IsRewardItem = m_Banner.IsRewardItem; - banner.MoveToWorld( m_Location, sender.Mobile.Map ); - - m_Banner.Delete(); - } - } - } - } - } -} + public class Banner : Item, IAddon, IDyable, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public Banner(int itemID) : base(itemID) + { + LootType = LootType.Blessed; + Movable = false; + } + + public Banner(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public bool FacingSouth => (ItemID & 0x1) == 0; + + public Item Deed + { + get + { + BannerDeed deed = new BannerDeed(); + deed.IsRewardItem = m_IsRewardItem; + + return deed; + } + } + + public bool CouldFit(IPoint3D p, Map map) + { + if (map == null || !map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; + + if (FacingSouth) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // north wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // west wall + } + + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; + + Hue = sender.DyedHue; + + return true; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Core.ML && m_IsRewardItem) + list.Add(1076218); // 2nd Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(Location, 2)) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(RewardDemolitionGump)); + from.SendGump(new RewardDemolitionGump(this, 1018318)); // Do you wish to re-deed this banner? + } + else + { + from.SendLocalizedMessage( + 1018330); // You can only re-deed a banner if you placed it or you are the owner of the house. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + } + + public class BannerDeed : Item, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public BannerDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } + + public BannerDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041007; // a banner deed + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076218); // 2nd Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; + + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + + private class InternalGump : Gump + { + public const int Start = 0x15AE; + public const int End = 0x15F4; + + private BannerDeed m_Banner; + + public InternalGump(BannerDeed banner) : base(100, 200) + { + m_Banner = banner; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + + AddBackground(25, 0, 520, 230, 0xA28); + AddLabel(70, 12, 0x3E3, "Choose a Banner:"); + + + int itemID = Start; + + for (int i = 1; i <= 4; i++) + { + AddPage(i); + + for (int j = 0; j < 8; j++, itemID += 2) + { + AddItem(50 + 60 * j, 70, itemID); + AddButton(50 + 60 * j, 50, 0x845, 0x846, itemID, GumpButtonType.Reply, 0); + } + + if (i > 1) + AddButton(75, 198, 0x8AF, 0x8AF, 0, GumpButtonType.Page, i - 1); + + if (i < 4) + AddButton(475, 198, 0x8B0, 0x8B0, 0, GumpButtonType.Page, i + 1); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if ((m_Banner == null) | m_Banner.Deleted) + return; + + Mobile m = sender.Mobile; + + if (info.ButtonID >= Start && info.ButtonID <= End) + if ((info.ButtonID & 0x1) == 0) + { + m.SendLocalizedMessage(1042037); // Where would you like to place this banner? + m.Target = new InternalTarget(m_Banner, info.ButtonID); + } + } + } + + private class InternalTarget : Target + { + private BannerDeed m_Banner; + private int m_ItemID; + + public InternalTarget(BannerDeed banner, int itemID) : base(-1, true, TargetFlags.None) + { + m_Banner = banner; + m_ItemID = itemID; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Banner == null || m_Banner.Deleted) + return; + + if (m_Banner.IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsOwner(from)) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; + + if (p == null || map == null) + return; + + Point3D p3d = new Point3D(p); + ItemData id = TileData.ItemTable[m_ItemID & TileData.MaxItemValue]; + + if (map.CanFit(p3d, id.Height)) + { + house = BaseHouse.FindHouseAt(p3d, map, id.Height); + + if (house != null && house.IsOwner(from)) + { + bool north = BaseAddon.IsWall(p3d.X, p3d.Y - 1, p3d.Z, map); + bool west = BaseAddon.IsWall(p3d.X - 1, p3d.Y, p3d.Z, map); + + if (north && west) + { + from.CloseGump(typeof(FacingGump)); + from.SendGump(new FacingGump(m_Banner, m_ItemID, p3d, house)); + } + else if (north || west) + { + Banner banner = null; + + if (north) + banner = new Banner(m_ItemID); + else if (west) + banner = new Banner(m_ItemID + 1); + + house.Addons.Add(banner); + + banner.IsRewardItem = m_Banner.IsRewardItem; + banner.MoveToWorld(p3d, map); + + m_Banner.Delete(); + } + else + { + from.SendLocalizedMessage(1042039); // The banner must be placed next to a wall. + } + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } + else + { + from.SendLocalizedMessage(500269); // You cannot build that there. + } + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + private class FacingGump : Gump + { + private BannerDeed m_Banner; + private BaseHouse m_House; + private int m_ItemID; + private Point3D m_Location; + + public FacingGump(BannerDeed banner, int itemID, Point3D location, BaseHouse house) : base(150, 50) + { + m_Banner = banner; + m_ItemID = itemID; + m_Location = location; + m_House = house; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + + AddBackground(0, 0, 300, 150, 0xA28); + + AddItem(90, 30, itemID + 1); + AddItem(180, 30, itemID); + + AddButton(50, 35, 0x868, 0x869, (int)Buttons.East, GumpButtonType.Reply, 0); + AddButton(145, 35, 0x868, 0x869, (int)Buttons.South, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Banner == null || m_Banner.Deleted || m_House == null) + return; + + Banner banner = null; + + if (info.ButtonID == (int)Buttons.East) + banner = new Banner(m_ItemID + 1); + if (info.ButtonID == (int)Buttons.South) + banner = new Banner(m_ItemID); + + if (banner != null) + { + m_House.Addons.Add(banner); + + banner.IsRewardItem = m_Banner.IsRewardItem; + banner.MoveToWorld(m_Location, sender.Mobile.Map); + + m_Banner.Delete(); + } + } + + private enum Buttons + { + Cancel, + East, + South + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/BloodyPentagram.cs b/Scripts/Items/Special/Veteran Rewards/BloodyPentagram.cs index a6f760f93..7d713d286 100644 --- a/Scripts/Items/Special/Veteran Rewards/BloodyPentagram.cs +++ b/Scripts/Items/Special/Veteran Rewards/BloodyPentagram.cs @@ -2,189 +2,197 @@ using Server.Engines.VeteranRewards; namespace Server.Items { - public class BloodyPentagramComponent : AddonComponent - { - public override bool DisplayWeight => false; - public override int LabelNumber => 1080279; // Bloody Pentagram + public class BloodyPentagramComponent : AddonComponent + { + public BloodyPentagramComponent(int itemID) : base(itemID) + { + } - public BloodyPentagramComponent( int itemID ) : base( itemID ) - { - } + public BloodyPentagramComponent(Serial serial) : base(serial) + { + } - public BloodyPentagramComponent( Serial serial ) : base( serial ) - { - } + public override bool DisplayWeight => false; + public override int LabelNumber => 1080279; // Bloody Pentagram - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class BloodyPentagramAddon : BaseAddon, IRewardItem - { - public override BaseAddonDeed Deed - { - get - { - BloodyPentagramDeed deed = new BloodyPentagramDeed(); - deed.IsRewardItem = m_IsRewardItem; + public class BloodyPentagramAddon : BaseAddon, IRewardItem + { + private bool m_IsRewardItem; - return deed; - } - } + [Constructible] + public BloodyPentagramAddon() + { + AddComponent(new BloodyPentagramComponent(0x1CF9), 0, 1, 0); + AddComponent(new BloodyPentagramComponent(0x1CF8), 0, 2, 0); + AddComponent(new BloodyPentagramComponent(0x1CF7), 0, 3, 0); + AddComponent(new BloodyPentagramComponent(0x1CF6), 0, 4, 0); + AddComponent(new BloodyPentagramComponent(0x1CF5), 0, 5, 0); - private bool m_IsRewardItem; + AddComponent(new BloodyPentagramComponent(0x1CFB), 1, 0, 0); + AddComponent(new BloodyPentagramComponent(0x1CFA), 1, 1, 0); + AddComponent(new BloodyPentagramComponent(0x1D09), 1, 2, 0); + AddComponent(new BloodyPentagramComponent(0x1D08), 1, 3, 0); + AddComponent(new BloodyPentagramComponent(0x1D07), 1, 4, 0); + AddComponent(new BloodyPentagramComponent(0x1CF4), 1, 5, 0); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + AddComponent(new BloodyPentagramComponent(0x1CFC), 2, 0, 0); + AddComponent(new BloodyPentagramComponent(0x1D0A), 2, 1, 0); + AddComponent(new BloodyPentagramComponent(0x1D11), 2, 2, 0); + AddComponent(new BloodyPentagramComponent(0x1D10), 2, 3, 0); + AddComponent(new BloodyPentagramComponent(0x1D06), 2, 4, 0); + AddComponent(new BloodyPentagramComponent(0x1CF3), 2, 5, 0); - [Constructible] - public BloodyPentagramAddon() - { - AddComponent( new BloodyPentagramComponent( 0x1CF9 ), 0, 1, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF8 ), 0, 2, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF7 ), 0, 3, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF6 ), 0, 4, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF5 ), 0, 5, 0 ); + AddComponent(new BloodyPentagramComponent(0x1CFD), 3, 0, 0); + AddComponent(new BloodyPentagramComponent(0x1D0B), 3, 1, 0); + AddComponent(new BloodyPentagramComponent(0x1D12), 3, 2, 0); + AddComponent(new BloodyPentagramComponent(0x1D0F), 3, 3, 0); + AddComponent(new BloodyPentagramComponent(0x1D05), 3, 4, 0); + AddComponent(new BloodyPentagramComponent(0x1CF2), 3, 5, 0); - AddComponent( new BloodyPentagramComponent( 0x1CFB ), 1, 0, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CFA ), 1, 1, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D09 ), 1, 2, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D08 ), 1, 3, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D07 ), 1, 4, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF4 ), 1, 5, 0 ); + AddComponent(new BloodyPentagramComponent(0x1CFE), 4, 0, 0); + AddComponent(new BloodyPentagramComponent(0x1D0C), 4, 1, 0); + AddComponent(new BloodyPentagramComponent(0x1D0D), 4, 2, 0); + AddComponent(new BloodyPentagramComponent(0x1D0E), 4, 3, 0); + AddComponent(new BloodyPentagramComponent(0x1D04), 4, 4, 0); + AddComponent(new BloodyPentagramComponent(0x1CF1), 4, 5, 0); - AddComponent( new BloodyPentagramComponent( 0x1CFC ), 2, 0, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D0A ), 2, 1, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D11 ), 2, 2, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D10 ), 2, 3, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D06 ), 2, 4, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF3 ), 2, 5, 0 ); + AddComponent(new BloodyPentagramComponent(0x1CFF), 5, 0, 0); + AddComponent(new BloodyPentagramComponent(0x1D00), 5, 1, 0); + AddComponent(new BloodyPentagramComponent(0x1D01), 5, 2, 0); + AddComponent(new BloodyPentagramComponent(0x1D02), 5, 3, 0); + AddComponent(new BloodyPentagramComponent(0x1D03), 5, 4, 0); + } - AddComponent( new BloodyPentagramComponent( 0x1CFD ), 3, 0, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D0B ), 3, 1, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D12 ), 3, 2, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D0F ), 3, 3, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D05 ), 3, 4, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF2 ), 3, 5, 0 ); + public BloodyPentagramAddon(Serial serial) : base(serial) + { + } - AddComponent( new BloodyPentagramComponent( 0x1CFE ), 4, 0, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D0C ), 4, 1, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D0D ), 4, 2, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D0E ), 4, 3, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D04 ), 4, 4, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1CF1 ), 4, 5, 0 ); + public override BaseAddonDeed Deed + { + get + { + BloodyPentagramDeed deed = new BloodyPentagramDeed(); + deed.IsRewardItem = m_IsRewardItem; - AddComponent( new BloodyPentagramComponent( 0x1CFF ), 5, 0, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D00 ), 5, 1, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D01 ), 5, 2, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D02 ), 5, 3, 0 ); - AddComponent( new BloodyPentagramComponent( 0x1D03 ), 5, 4, 0 ); - } + return deed; + } + } - public BloodyPentagramAddon( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } - } + m_IsRewardItem = reader.ReadBool(); + } + } - public class BloodyPentagramDeed : BaseAddonDeed, IRewardItem - { - public override int LabelNumber => 1080384; // Bloody Pentagram + public class BloodyPentagramDeed : BaseAddonDeed, IRewardItem + { + private bool m_IsRewardItem; - public override BaseAddon Addon - { - get - { - BloodyPentagramAddon addon = new BloodyPentagramAddon(); - addon.IsRewardItem = m_IsRewardItem; + [Constructible] + public BloodyPentagramDeed() + { + LootType = LootType.Blessed; + } - return addon; - } - } + public BloodyPentagramDeed(Serial serial) : base(serial) + { + } - private bool m_IsRewardItem; + public override int LabelNumber => 1080384; // Bloody Pentagram - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public override BaseAddon Addon + { + get + { + BloodyPentagramAddon addon = new BloodyPentagramAddon(); + addon.IsRewardItem = m_IsRewardItem; - [Constructible] - public BloodyPentagramDeed() - { - LootType = LootType.Blessed; - } + return addon; + } + } - public BloodyPentagramDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - base.OnDoubleClick( from ); - } + base.OnDoubleClick(from); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076221 ); // 5th Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076221); // 5th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } - } -} + m_IsRewardItem = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/Brazier.cs b/Scripts/Items/Special/Veteran Rewards/Brazier.cs index 01739934c..9ffb87013 100644 --- a/Scripts/Items/Special/Veteran Rewards/Brazier.cs +++ b/Scripts/Items/Special/Veteran Rewards/Brazier.cs @@ -1,240 +1,257 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Multis; using Server.Network; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class RewardBrazier : Item, IRewardItem - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public class RewardBrazier : Item, IRewardItem + { + private static int[] m_Art = + { + 0x19AA, 0x19BB + }; - private bool m_IsRewardItem; + private Item m_Fire; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + private bool m_IsRewardItem; - private Item m_Fire; + [Constructible] + public RewardBrazier() : this(Utility.RandomList(m_Art)) + { + } - public override void OnDelete() - { - TurnOff(); + [Constructible] + public RewardBrazier(int itemID) : base(itemID) + { + LootType = LootType.Blessed; + Weight = 10.0; + } - base.OnDelete(); - } + public RewardBrazier(Serial serial) : base(serial) + { + } - private static int[] m_Art = { - 0x19AA, 0x19BB - }; + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - [Constructible] - public RewardBrazier() : this( Utility.RandomList( m_Art ) ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - [Constructible] - public RewardBrazier( int itemID ) : base( itemID ) - { - LootType = LootType.Blessed; - Weight = 10.0; - } + public override void OnDelete() + { + TurnOff(); - public RewardBrazier( Serial serial ) : base( serial ) - { - } + base.OnDelete(); + } - public void TurnOff() - { - if ( m_Fire != null ) - { - m_Fire.Delete(); - m_Fire = null; - } - } + public void TurnOff() + { + if (m_Fire != null) + { + m_Fire.Delete(); + m_Fire = null; + } + } - public void TurnOn() - { - if ( m_Fire == null ) - m_Fire = new Item(); + public void TurnOn() + { + if (m_Fire == null) + m_Fire = new Item(); - m_Fire.ItemID = 0x19AB; - m_Fire.Movable = false; - m_Fire.MoveToWorld( new Point3D( X, Y, Z + ItemData.Height + 2 ), Map ); - } + m_Fire.ItemID = 0x19AB; + m_Fire.Movable = false; + m_Fire.MoveToWorld(new Point3D(X, Y, Z + ItemData.Height + 2), Map); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.InRange( GetWorldLocation(), 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - else if ( IsLockedDown ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + public override void OnDoubleClick(Mobile from) + { + if (!from.InRange(GetWorldLocation(), 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + else if (IsLockedDown) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house != null && house.IsCoOwner( from ) ) - { - if ( m_Fire != null ) - TurnOff(); - else - TurnOn(); - } - else - from.SendLocalizedMessage( 502436 ); // That is not accessible. - } - else - from.SendLocalizedMessage( 502692 ); // This must be in a house and be locked down to work. - } + if (house != null && house.IsCoOwner(from)) + { + if (m_Fire != null) + TurnOff(); + else + TurnOn(); + } + else + { + from.SendLocalizedMessage(502436); // That is not accessible. + } + } + else + { + from.SendLocalizedMessage(502692); // This must be in a house and be locked down to work. + } + } - public override void OnLocationChange( Point3D old ) - { - m_Fire?.MoveToWorld( new Point3D( X, Y, Z + ItemData.Height ), Map ); - } + public override void OnLocationChange(Point3D old) + { + m_Fire?.MoveToWorld(new Point3D(X, Y, Z + ItemData.Height), Map); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076222 ); // 6th Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076222); // 6th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - writer.Write( (Item) m_Fire ); - } + writer.Write(m_IsRewardItem); + writer.Write(m_Fire); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - m_Fire = reader.ReadItem(); - } - } + m_IsRewardItem = reader.ReadBool(); + m_Fire = reader.ReadItem(); + } + } - public class RewardBrazierDeed : Item, IRewardItem - { - public override int LabelNumber => 1080527; // Brazier Deed + public class RewardBrazierDeed : Item, IRewardItem + { + private bool m_IsRewardItem; - private bool m_IsRewardItem; + [Constructible] + public RewardBrazierDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public RewardBrazierDeed(Serial serial) : base(serial) + { + } - [Constructible] - public RewardBrazierDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } + public override int LabelNumber => 1080527; // Brazier Deed - public RewardBrazierDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076222 ); // 6th Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076222); // 6th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } + m_IsRewardItem = reader.ReadBool(); + } - private class InternalGump : Gump - { - private RewardBrazierDeed m_Brazier; + private class InternalGump : Gump + { + private RewardBrazierDeed m_Brazier; - public InternalGump( RewardBrazierDeed brazier ) : base( 100, 200 ) - { - m_Brazier = brazier; + public InternalGump(RewardBrazierDeed brazier) : base(100, 200) + { + m_Brazier = brazier; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); - AddBackground( 0, 0, 200, 200, 2600 ); + AddPage(0); + AddBackground(0, 0, 200, 200, 2600); - AddPage( 1 ); - AddLabel( 45, 15, 0, "Choose a Brazier:" ); + AddPage(1); + AddLabel(45, 15, 0, "Choose a Brazier:"); - AddItem( 40, 75, 0x19AA ); - AddButton( 55, 50, 0x845, 0x846, 0x19AA, GumpButtonType.Reply, 0 ); + AddItem(40, 75, 0x19AA); + AddButton(55, 50, 0x845, 0x846, 0x19AA, GumpButtonType.Reply, 0); - AddItem( 100, 75, 0x19BB ); - AddButton( 115, 50, 0x845, 0x846, 0x19BB, GumpButtonType.Reply, 0 ); - } + AddItem(100, 75, 0x19BB); + AddButton(115, 50, 0x845, 0x846, 0x19BB, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Brazier == null | m_Brazier.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if ((m_Brazier == null) | m_Brazier.Deleted) + return; - Mobile m = sender.Mobile; + Mobile m = sender.Mobile; - if ( info.ButtonID == 0x19AA || info.ButtonID == 0x19BB ) - { - RewardBrazier brazier = new RewardBrazier( info.ButtonID ); - brazier.IsRewardItem = m_Brazier.IsRewardItem; + if (info.ButtonID == 0x19AA || info.ButtonID == 0x19BB) + { + RewardBrazier brazier = new RewardBrazier(info.ButtonID); + brazier.IsRewardItem = m_Brazier.IsRewardItem; - if ( !m.PlaceInBackpack( brazier ) ) - { - brazier.Delete(); - m.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - m_Brazier.Delete(); - } - } - } - } -} + if (!m.PlaceInBackpack(brazier)) + { + brazier.Delete(); + m.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + m_Brazier.Delete(); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/Cannon.cs b/Scripts/Items/Special/Veteran Rewards/Cannon.cs index 6d1d717bc..11215654f 100644 --- a/Scripts/Items/Special/Veteran Rewards/Cannon.cs +++ b/Scripts/Items/Special/Veteran Rewards/Cannon.cs @@ -1,460 +1,484 @@ using System; -using Server.Gumps; -using Server.Targeting; -using Server.Network; using Server.Engines.Quests.Haven; using Server.Engines.VeteranRewards; +using Server.Gumps; +using Server.Network; +using Server.Targeting; namespace Server.Items { - public class CannonAddonComponent : AddonComponent - { - public override int LabelNumber => 1076157; // Decorative Cannon - - public CannonAddonComponent( int itemID ) : base( itemID ) - { - LootType = LootType.Blessed; - } - - public CannonAddonComponent( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Addon is CannonAddon addon ) - { - if ( addon.IsRewardItem ) - list.Add( 1076223 ); // 7th Year Veteran Reward - - list.Add( 1076207, addon.Charges.ToString() ); // Remaining Charges: ~1_val~ - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CannonAddon : BaseAddon - { - public override BaseAddonDeed Deed - { - get - { - CannonDeed deed = new CannonDeed(); - deed.Charges = m_Charges; - deed.IsRewardItem = m_IsRewardItem; - - return deed; - } - } - - private int m_Charges; - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public CannonDirection CannonDirection { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set - { - m_Charges = value; - - foreach ( AddonComponent c in Components ) - c.InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set - { - m_IsRewardItem = value; - - foreach ( AddonComponent c in Components ) - c.InvalidateProperties(); - } - } - - [Constructible] - public CannonAddon( CannonDirection direction ) - { - CannonDirection = direction; - - switch ( direction ) - { - case CannonDirection.North: - { - AddComponent( new CannonAddonComponent( 0xE8D ), 0, 0, 0 ); - AddComponent( new CannonAddonComponent( 0xE8C ), 0, 1, 0 ); - AddComponent( new CannonAddonComponent( 0xE8B ), 0, 2, 0 ); - - break; - } - case CannonDirection.East: - { - AddComponent( new CannonAddonComponent( 0xE96 ), 0, 0, 0 ); - AddComponent( new CannonAddonComponent( 0xE95 ), -1, 0, 0 ); - AddComponent( new CannonAddonComponent( 0xE94 ), -2, 0, 0 ); - - break; - } - case CannonDirection.South: - { - AddComponent( new CannonAddonComponent( 0xE91 ), 0, 0, 0 ); - AddComponent( new CannonAddonComponent( 0xE92 ), 0, -1, 0 ); - AddComponent( new CannonAddonComponent( 0xE93 ), 0, -2, 0 ); - - break; - } - default: - { - AddComponent( new CannonAddonComponent( 0xE8E ), 0, 0, 0 ); - AddComponent( new CannonAddonComponent( 0xE8F ), 1, 0, 0 ); - AddComponent( new CannonAddonComponent( 0xE90 ), 2, 0, 0 ); - - break; - } - } - } - - public CannonAddon( Serial serial ) : base( serial ) - { - } - - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - if ( m_Charges > 0 ) - { - from.Target = new InternalTarget( this ); - } - else - { - if ( from.Backpack != null ) - { - PotionKeg keg = from.Backpack.FindItemByType( typeof( PotionKeg ) ) as PotionKeg; - - if ( Validate( keg ) > 0 ) - from.SendGump( new InternalGump( this, keg ) ); - else - from.SendLocalizedMessage( 1076198 ); // You do not have a full keg of explosion potions needed to recharge the cannon. - } - } - } - else - from.SendLocalizedMessage( 1076766 ); // That is too far away. - } - - public int Validate( PotionKeg keg ) - { - if ( keg != null && !keg.Deleted && keg.Held == 100 ) - { - if ( keg.Type == PotionEffect.ExplosionLesser ) - return 5; - if ( keg.Type == PotionEffect.Explosion ) - return 10; - if ( keg.Type == PotionEffect.ExplosionGreater ) - return 15; - } - - return 0; - } - - public void Fill( Mobile from, PotionKeg keg ) - { - Charges = Validate( keg ); - - if ( Charges > 0 ) - { - keg.Delete(); - from.SendLocalizedMessage( 1076199 ); // Your cannon is recharged. - } - else - from.SendLocalizedMessage( 1076198 ); // You do not have a full keg of explosion potions needed to recharge the cannon. - } - - private static int[] m_Effects = { - 0x36B0, 0x3728, 0x3709, 0x36FE - }; - - public void DoFireEffect( IPoint3D target ) - { - Map map = Map; - - if ( target == null || map == null ) - return; - - Effects.PlaySound( target, map, Utility.RandomList( 0x11B, 0x11C, 0x11D ) ); - Effects.SendLocationEffect( target, map, Utility.RandomList( m_Effects ), 16, 1 ); - - for ( int count = Utility.Random( 3 ); count > 0; count-- ) - { - IPoint3D location = new Point3D( target.X + Utility.RandomMinMax( -1, 1 ), target.Y + Utility.RandomMinMax( -1, 1 ), target.Z ); - int effect = Utility.RandomList( m_Effects ); - Effects.SendLocationEffect( location, map, effect, 16, 1 ); - } - - Charges -= 1; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (int) CannonDirection ); - writer.Write( (int) m_Charges ); - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - CannonDirection = (CannonDirection) reader.ReadInt(); - m_Charges = reader.ReadInt(); - m_IsRewardItem = reader.ReadBool(); - } - - private class InternalTarget : Target - { - private CannonAddon m_Cannon; - - public InternalTarget( CannonAddon cannon ) : base( 12, true, TargetFlags.None ) - { - m_Cannon = cannon; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Cannon == null || m_Cannon.Deleted ) - return; - - if ( !(targeted is IPoint3D p) ) - return; - - if ( from.InLOS( new Point3D( p ) ) ) - { - if ( !Utility.InRange( new Point3D( p ), m_Cannon.Location, 2 ) ) - { - bool allow = false; - - int x = p.X - m_Cannon.X; - int y = p.Y - m_Cannon.Y; - - switch ( m_Cannon.CannonDirection ) - { - case CannonDirection.North: - if ( y < 0 && Math.Abs( x ) <= -y / 3 ) - allow = true; - - break; - case CannonDirection.East: - if ( x > 0 && Math.Abs( y ) <= x / 3 ) - allow = true; - - break; - case CannonDirection.South: - if ( y > 0 && Math.Abs( x ) <= y / 3 ) - allow = true; - - break; - case CannonDirection.West: - if ( x < 0 && Math.Abs( y ) <= -x / 3 ) - allow = true; - - break; - } - - if ( allow && Utility.InRange( new Point3D( p ), m_Cannon.Location, 14 ) ) - m_Cannon.DoFireEffect( p ); - else - from.SendLocalizedMessage( 1076203 ); // Target out of range. - } - else - from.SendLocalizedMessage( 1076215 ); // Cannon must be aimed farther away. - } - else - from.SendLocalizedMessage( 1049630 ); // You cannot see that target! - } - - protected override void OnTargetOutOfRange( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 1076203 ); // Target out of range. - } - } - - private class InternalGump : Gump - { - private CannonAddon m_Cannon; - private PotionKeg m_Keg; - - private enum Buttons - { - Cancel, - Recharge - } - - public InternalGump( CannonAddon cannon, PotionKeg keg ) : base( 50, 50 ) - { - m_Cannon = cannon; - m_Keg = keg; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddBackground( 0, 0, 291, 133, 0x13BE ); - AddImageTiled( 5, 5, 280, 100, 0xA40 ); - - AddHtmlLocalized( 9, 9, 272, 100, 1076196, cannon.Validate( keg ).ToString(), 0x7FFF, false, false ); // You will need a full keg of explosion potions to recharge the cannon. Your keg will provide ~1_CHARGES~ charges. - - AddButton( 5, 107, 0xFB1, 0xFB2, (int) Buttons.Cancel, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 109, 100, 20, 1060051, 0x7FFF, false, false ); // CANCEL - - AddButton( 160, 107, 0xFB7, 0xFB8, (int) Buttons.Recharge, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 109, 120, 20, 1076197, 0x7FFF, false, false ); // Recharge - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( m_Cannon == null || m_Cannon.Deleted ) - return; - - if ( info.ButtonID == (int) Buttons.Recharge ) - m_Cannon.Fill( state.Mobile, m_Keg ); - } - } - } - - public class CannonDeed : BaseAddonDeed, IRewardItem, IRewardOption - { - public override int LabelNumber => 1076195; // A deed for a cannon - - public override BaseAddon Addon - { - get - { - CannonAddon addon = new CannonAddon( m_Direction ); - addon.Charges = m_Charges; - addon.IsRewardItem = m_IsRewardItem; - - return addon; - } - } - - private CannonDirection m_Direction; - private int m_Charges; - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set{ m_Charges = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - [Constructible] - public CannonDeed() - { - LootType = LootType.Blessed; - } - - public CannonDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076223 ); // 7th Year Veteran Reward - - list.Add( 1076207, m_Charges.ToString() ); // Remaining Charges: ~1_val~ - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( RewardOptionGump ) ); - from.SendGump( new RewardOptionGump( this ) ); - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (int) m_Charges ); - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_Charges = reader.ReadInt(); - m_IsRewardItem = reader.ReadBool(); - } - - public void GetOptions( RewardOptionList list ) - { - list.Add( (int) CannonDirection.South, 1075386 ); // South - list.Add( (int) CannonDirection.East, 1075387 ); // East - list.Add( (int) CannonDirection.North, 1075389 ); // North - list.Add( (int) CannonDirection.West, 1075390 ); // West - } - - public void OnOptionSelected( Mobile from, int option ) - { - m_Direction = (CannonDirection) option; - - if ( !Deleted ) - base.OnDoubleClick( from ); - } - } -} + public class CannonAddonComponent : AddonComponent + { + public CannonAddonComponent(int itemID) : base(itemID) + { + LootType = LootType.Blessed; + } + + public CannonAddonComponent(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1076157; // Decorative Cannon + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Addon is CannonAddon addon) + { + if (addon.IsRewardItem) + list.Add(1076223); // 7th Year Veteran Reward + + list.Add(1076207, addon.Charges.ToString()); // Remaining Charges: ~1_val~ + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CannonAddon : BaseAddon + { + private static int[] m_Effects = + { + 0x36B0, 0x3728, 0x3709, 0x36FE + }; + + private int m_Charges; + private bool m_IsRewardItem; + + [Constructible] + public CannonAddon(CannonDirection direction) + { + CannonDirection = direction; + + switch (direction) + { + case CannonDirection.North: + { + AddComponent(new CannonAddonComponent(0xE8D), 0, 0, 0); + AddComponent(new CannonAddonComponent(0xE8C), 0, 1, 0); + AddComponent(new CannonAddonComponent(0xE8B), 0, 2, 0); + + break; + } + case CannonDirection.East: + { + AddComponent(new CannonAddonComponent(0xE96), 0, 0, 0); + AddComponent(new CannonAddonComponent(0xE95), -1, 0, 0); + AddComponent(new CannonAddonComponent(0xE94), -2, 0, 0); + + break; + } + case CannonDirection.South: + { + AddComponent(new CannonAddonComponent(0xE91), 0, 0, 0); + AddComponent(new CannonAddonComponent(0xE92), 0, -1, 0); + AddComponent(new CannonAddonComponent(0xE93), 0, -2, 0); + + break; + } + default: + { + AddComponent(new CannonAddonComponent(0xE8E), 0, 0, 0); + AddComponent(new CannonAddonComponent(0xE8F), 1, 0, 0); + AddComponent(new CannonAddonComponent(0xE90), 2, 0, 0); + + break; + } + } + } + + public CannonAddon(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed + { + get + { + CannonDeed deed = new CannonDeed(); + deed.Charges = m_Charges; + deed.IsRewardItem = m_IsRewardItem; + + return deed; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CannonDirection CannonDirection{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + + foreach (AddonComponent c in Components) + c.InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + + foreach (AddonComponent c in Components) + c.InvalidateProperties(); + } + } + + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (from.InRange(Location, 2)) + { + if (m_Charges > 0) + { + from.Target = new InternalTarget(this); + } + else + { + if (from.Backpack != null) + { + PotionKeg keg = from.Backpack.FindItemByType(typeof(PotionKeg)) as PotionKeg; + + if (Validate(keg) > 0) + from.SendGump(new InternalGump(this, keg)); + else + from.SendLocalizedMessage( + 1076198); // You do not have a full keg of explosion potions needed to recharge the cannon. + } + } + } + else + { + from.SendLocalizedMessage(1076766); // That is too far away. + } + } + + public int Validate(PotionKeg keg) + { + if (keg != null && !keg.Deleted && keg.Held == 100) + { + if (keg.Type == PotionEffect.ExplosionLesser) + return 5; + if (keg.Type == PotionEffect.Explosion) + return 10; + if (keg.Type == PotionEffect.ExplosionGreater) + return 15; + } + + return 0; + } + + public void Fill(Mobile from, PotionKeg keg) + { + Charges = Validate(keg); + + if (Charges > 0) + { + keg.Delete(); + from.SendLocalizedMessage(1076199); // Your cannon is recharged. + } + else + { + from.SendLocalizedMessage( + 1076198); // You do not have a full keg of explosion potions needed to recharge the cannon. + } + } + + public void DoFireEffect(IPoint3D target) + { + Map map = Map; + + if (target == null || map == null) + return; + + Effects.PlaySound(target, map, Utility.RandomList(0x11B, 0x11C, 0x11D)); + Effects.SendLocationEffect(target, map, Utility.RandomList(m_Effects), 16, 1); + + for (int count = Utility.Random(3); count > 0; count--) + { + IPoint3D location = new Point3D(target.X + Utility.RandomMinMax(-1, 1), + target.Y + Utility.RandomMinMax(-1, 1), target.Z); + int effect = Utility.RandomList(m_Effects); + Effects.SendLocationEffect(location, map, effect, 16, 1); + } + + Charges -= 1; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write((int)CannonDirection); + writer.Write(m_Charges); + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + CannonDirection = (CannonDirection)reader.ReadInt(); + m_Charges = reader.ReadInt(); + m_IsRewardItem = reader.ReadBool(); + } + + private class InternalTarget : Target + { + private CannonAddon m_Cannon; + + public InternalTarget(CannonAddon cannon) : base(12, true, TargetFlags.None) + { + m_Cannon = cannon; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Cannon == null || m_Cannon.Deleted) + return; + + if (!(targeted is IPoint3D p)) + return; + + if (from.InLOS(new Point3D(p))) + { + if (!Utility.InRange(new Point3D(p), m_Cannon.Location, 2)) + { + bool allow = false; + + int x = p.X - m_Cannon.X; + int y = p.Y - m_Cannon.Y; + + switch (m_Cannon.CannonDirection) + { + case CannonDirection.North: + if (y < 0 && Math.Abs(x) <= -y / 3) + allow = true; + + break; + case CannonDirection.East: + if (x > 0 && Math.Abs(y) <= x / 3) + allow = true; + + break; + case CannonDirection.South: + if (y > 0 && Math.Abs(x) <= y / 3) + allow = true; + + break; + case CannonDirection.West: + if (x < 0 && Math.Abs(y) <= -x / 3) + allow = true; + + break; + } + + if (allow && Utility.InRange(new Point3D(p), m_Cannon.Location, 14)) + m_Cannon.DoFireEffect(p); + else + from.SendLocalizedMessage(1076203); // Target out of range. + } + else + { + from.SendLocalizedMessage(1076215); // Cannon must be aimed farther away. + } + } + else + { + from.SendLocalizedMessage(1049630); // You cannot see that target! + } + } + + protected override void OnTargetOutOfRange(Mobile from, object targeted) + { + from.SendLocalizedMessage(1076203); // Target out of range. + } + } + + private class InternalGump : Gump + { + private CannonAddon m_Cannon; + private PotionKeg m_Keg; + + public InternalGump(CannonAddon cannon, PotionKeg keg) : base(50, 50) + { + m_Cannon = cannon; + m_Keg = keg; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + + AddBackground(0, 0, 291, 133, 0x13BE); + AddImageTiled(5, 5, 280, 100, 0xA40); + + AddHtmlLocalized(9, 9, 272, 100, 1076196, cannon.Validate(keg).ToString(), 0x7FFF, false, + false); // You will need a full keg of explosion potions to recharge the cannon. Your keg will provide ~1_CHARGES~ charges. + + AddButton(5, 107, 0xFB1, 0xFB2, (int)Buttons.Cancel, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 109, 100, 20, 1060051, 0x7FFF, false, false); // CANCEL + + AddButton(160, 107, 0xFB7, 0xFB8, (int)Buttons.Recharge, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 109, 120, 20, 1076197, 0x7FFF, false, false); // Recharge + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Cannon == null || m_Cannon.Deleted) + return; + + if (info.ButtonID == (int)Buttons.Recharge) + m_Cannon.Fill(state.Mobile, m_Keg); + } + + private enum Buttons + { + Cancel, + Recharge + } + } + } + + public class CannonDeed : BaseAddonDeed, IRewardItem, IRewardOption + { + private int m_Charges; + + private CannonDirection m_Direction; + private bool m_IsRewardItem; + + [Constructible] + public CannonDeed() + { + LootType = LootType.Blessed; + } + + public CannonDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1076195; // A deed for a cannon + + public override BaseAddon Addon + { + get + { + CannonAddon addon = new CannonAddon(m_Direction); + addon.Charges = m_Charges; + addon.IsRewardItem = m_IsRewardItem; + + return addon; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public void GetOptions(RewardOptionList list) + { + list.Add((int)CannonDirection.South, 1075386); // South + list.Add((int)CannonDirection.East, 1075387); // East + list.Add((int)CannonDirection.North, 1075389); // North + list.Add((int)CannonDirection.West, 1075390); // West + } + + public void OnOptionSelected(Mobile from, int option) + { + m_Direction = (CannonDirection)option; + + if (!Deleted) + base.OnDoubleClick(from); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076223); // 7th Year Veteran Reward + + list.Add(1076207, m_Charges.ToString()); // Remaining Charges: ~1_val~ + } + + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; + + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(RewardOptionGump)); + from.SendGump(new RewardOptionGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_Charges); + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_Charges = reader.ReadInt(); + m_IsRewardItem = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/CommodityDeedBox.cs b/Scripts/Items/Special/Veteran Rewards/CommodityDeedBox.cs index 81c9051cf..2a6d36f45 100644 --- a/Scripts/Items/Special/Veteran Rewards/CommodityDeedBox.cs +++ b/Scripts/Items/Special/Veteran Rewards/CommodityDeedBox.cs @@ -2,66 +2,70 @@ using Server.Engines.VeteranRewards; namespace Server.Items { - [Furniture] - public class CommodityDeedBox : BaseContainer, IRewardItem - { - public override int LabelNumber => 1080523; // Commodity Deed Box - public override int DefaultGumpID => 0x43; + [Furniture] + public class CommodityDeedBox : BaseContainer, IRewardItem + { + private bool m_IsRewardItem; - private bool m_IsRewardItem; + [Constructible] + public CommodityDeedBox() : base(0x9AA) + { + Hue = 0x47; + Weight = 4.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public CommodityDeedBox(Serial serial) : base(serial) + { + } - [Constructible] - public CommodityDeedBox() : base( 0x9AA ) - { - Hue = 0x47; - Weight = 4.0; - } + public override int LabelNumber => 1080523; // Commodity Deed Box + public override int DefaultGumpID => 0x43; - public CommodityDeedBox( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076217 ); // 1st Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076217); // 1st Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } + m_IsRewardItem = reader.ReadBool(); + } - public static CommodityDeedBox Find( Item deed ) - { - Item parent = deed; + public static CommodityDeedBox Find(Item deed) + { + Item parent = deed; - while ( parent != null && !( parent is CommodityDeedBox ) ) - parent = parent.Parent as Item; + while (parent != null && !(parent is CommodityDeedBox)) + parent = parent.Parent as Item; - return parent as CommodityDeedBox; - } - } -} + return parent as CommodityDeedBox; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/ContestMiniHouse.cs b/Scripts/Items/Special/Veteran Rewards/ContestMiniHouse.cs index 4045c0213..1cd1839b1 100644 --- a/Scripts/Items/Special/Veteran Rewards/ContestMiniHouse.cs +++ b/Scripts/Items/Special/Veteran Rewards/ContestMiniHouse.cs @@ -2,129 +2,137 @@ using Server.Engines.VeteranRewards; namespace Server.Items { - public class ContestMiniHouse : MiniHouseAddon - { - public override BaseAddonDeed Deed - { - get - { - ContestMiniHouseDeed deed = new ContestMiniHouseDeed( Type ); - deed.IsRewardItem = m_IsRewardItem; + public class ContestMiniHouse : MiniHouseAddon + { + private bool m_IsRewardItem; - return deed; - } - } + [Constructible] + public ContestMiniHouse() : base(MiniHouseType.MalasMountainPass) + { + } - private bool m_IsRewardItem; + [Constructible] + public ContestMiniHouse(MiniHouseType type) : base(type) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public ContestMiniHouse(Serial serial) : base(serial) + { + } - [Constructible] - public ContestMiniHouse() : base( MiniHouseType.MalasMountainPass ) - { - } + public override BaseAddonDeed Deed + { + get + { + ContestMiniHouseDeed deed = new ContestMiniHouseDeed(Type); + deed.IsRewardItem = m_IsRewardItem; - [Constructible] - public ContestMiniHouse( MiniHouseType type ) : base( type ) - { - } + return deed; + } + } - public ContestMiniHouse( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - } + int version = reader.ReadEncodedInt(); - public class ContestMiniHouseDeed : MiniHouseDeed, IRewardItem - { - public override BaseAddon Addon - { - get - { - ContestMiniHouse addon = new ContestMiniHouse( Type ); - addon.IsRewardItem = m_IsRewardItem; + m_IsRewardItem = reader.ReadBool(); + } + } - return addon; - } - } - - private bool m_IsRewardItem; + public class ContestMiniHouseDeed : MiniHouseDeed, IRewardItem + { + private bool m_IsRewardItem; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - [Constructible] - public ContestMiniHouseDeed() : base( MiniHouseType.MalasMountainPass ) - { - } + [Constructible] + public ContestMiniHouseDeed() : base(MiniHouseType.MalasMountainPass) + { + } - [Constructible] - public ContestMiniHouseDeed( MiniHouseType type ) : base( type ) - { - } + [Constructible] + public ContestMiniHouseDeed(MiniHouseType type) : base(type) + { + } - public ContestMiniHouseDeed( Serial serial ) : base( serial ) - { - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, new object[] { Type } ) ) - return; + public ContestMiniHouseDeed(Serial serial) : base(serial) + { + } - base.OnDoubleClick( from ); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Core.ML && m_IsRewardItem ) - list.Add( 1076217 ); // 1st Year Veteran Reward - } + public override BaseAddon Addon + { + get + { + ContestMiniHouse addon = new ContestMiniHouse(Type); + addon.IsRewardItem = m_IsRewardItem; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return addon; + } + } - writer.WriteEncodedInt( 0 ); // version + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - writer.Write( (bool) m_IsRewardItem ); - } + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, new object[] { Type })) + return; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + base.OnDoubleClick(from); + } - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - } -} + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Core.ML && m_IsRewardItem) + list.Add(1076217); // 1st Year Veteran Reward + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/DecorativeShield.cs b/Scripts/Items/Special/Veteran Rewards/DecorativeShield.cs index abd5cea3b..7e7d27c30 100644 --- a/Scripts/Items/Special/Veteran Rewards/DecorativeShield.cs +++ b/Scripts/Items/Special/Veteran Rewards/DecorativeShield.cs @@ -1,397 +1,425 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Multis; using Server.Network; using Server.Targeting; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class DecorativeShield : Item, IAddon, IRewardItem - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public Item Deed - { - get - { - DecorativeShieldDeed deed = new DecorativeShieldDeed(); - deed.IsRewardItem = m_IsRewardItem; - - return deed; - } - } - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - public bool FacingSouth - { - get - { - if ( ItemID < 0x1582 ) - return ( ItemID & 0x1 ) == 0; - - return ItemID <= 0x1585; - } - } - - [Constructible] - public DecorativeShield() : this( 0x156C ) - { - } - - [Constructible] - public DecorativeShield( int itemID ) : base( itemID ) - { - Movable = false; - } - - public DecorativeShield( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Core.ML && m_IsRewardItem ) - list.Add( 1076220 ); // 4th Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( RewardDemolitionGump ) ); - from.SendGump( new RewardDemolitionGump( this, 1049783 ) ); // Do you wish to re-deed this decoration? - } - else - from.SendLocalizedMessage( 1049784 ); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - public bool CouldFit( IPoint3D p, Map map ) - { - if ( map == null || !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; - - if ( FacingSouth ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // north wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // west wall - } - } - - public class DecorativeShieldDeed : Item, IRewardItem - { - public override int LabelNumber => 1049771; // deed for a decorative shield wall hanging - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - [Constructible] - public DecorativeShieldDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } - - public DecorativeShieldDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076220 ); // 4th Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - public static int GetWestItemID( int east ) - { - switch ( east ) - { - case 0x1582: return 0x1635; - case 0x1583: return 0x1634; - case 0x1584: return 0x1637; - case 0x1585: return 0x1636; - default: return east + 1; - } - } - - private class InternalGump : Gump - { - public const int Start = 0x156C; - public const int End = 0x1585; - - private DecorativeShieldDeed m_Shield; - private int m_Page; - - public InternalGump( DecorativeShieldDeed shield ) : this( shield, 1 ) - { - } - - public InternalGump( DecorativeShieldDeed shield, int page ) : base( 150, 50 ) - { - m_Shield = shield; - m_Page = page; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddBackground( 25, 0, 500, 230, 0xA28 ); - - int itemID = Start; - - for ( int i = 1; i <= 2; i++ ) - { - AddPage( i ); - - for ( int j = 0; j < 9 - i; j++ ) - { - AddItem( 40 + j * 60, 70, itemID ); - AddButton( 60 + j * 60, 50, 0x845, 0x846, itemID, GumpButtonType.Reply, 0 ); - - if ( itemID < 0x1582 ) - itemID += 2; - else - itemID += 1; - } - - switch ( i ) - { - case 1: AddButton( 455, 198, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 2 ); break; - case 2: AddButton( 70, 198, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 1 ); break; - } - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Shield == null | m_Shield.Deleted ) - return; - - Mobile m = sender.Mobile; - - if ( info.ButtonID >= Start && info.ButtonID <= End ) - { - if ( ( info.ButtonID & 0x1 ) == 0 && info.ButtonID < 0x1582 || info.ButtonID >= 0x1582 && info.ButtonID <= 0x1585 ) - { - m.SendLocalizedMessage( 1049780 ); // Where would you like to place this decoration? - m.Target = new InternalTarget( m_Shield, info.ButtonID ); - } - } - } - } - - private class InternalTarget : Target - { - private DecorativeShieldDeed m_Shield; - private int m_ItemID; - - public InternalTarget( DecorativeShieldDeed shield, int itemID ) : base( -1, true, TargetFlags.None ) - { - m_Shield = shield; - m_ItemID = itemID; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Shield == null || m_Shield.Deleted ) - return; - - if ( m_Shield.IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsOwner( from ) ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; - - if ( p == null || map == null ) - return; - - Point3D p3d = new Point3D( p ); - ItemData id = TileData.ItemTable[ m_ItemID & TileData.MaxItemValue ]; - - if ( map.CanFit( p3d, id.Height ) ) - { - house = BaseHouse.FindHouseAt( p3d, map, id.Height ); - - if ( house != null && house.IsOwner( from ) ) - { - bool north = BaseAddon.IsWall( p3d.X, p3d.Y - 1, p3d.Z, map ); - bool west = BaseAddon.IsWall( p3d.X - 1, p3d.Y, p3d.Z, map ); - - if ( north && west ) - { - from.CloseGump( typeof( FacingGump ) ); - from.SendGump( new FacingGump( m_Shield, m_ItemID, p3d, house ) ); - } - else if ( north || west ) - { - DecorativeShield shield = null; - - if ( north ) - shield = new DecorativeShield( m_ItemID ); - else if ( west ) - shield = new DecorativeShield( GetWestItemID( m_ItemID ) ); - - house.Addons.Add( shield ); - - shield.IsRewardItem = m_Shield.IsRewardItem; - shield.MoveToWorld( p3d, map ); - - m_Shield.Delete(); - } - else - from.SendLocalizedMessage( 1049781 ); // This decoration must be placed next to a wall. - } - else - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - else - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - private class FacingGump : Gump - { - private DecorativeShieldDeed m_Shield; - private int m_ItemID; - private Point3D m_Location; - private BaseHouse m_House; - - private enum Buttons - { - Cancel, - South, - East - } - - public FacingGump( DecorativeShieldDeed shield, int itemID, Point3D location, BaseHouse house ) : base( 150, 50 ) - { - m_Shield = shield; - m_ItemID = itemID; - m_Location = location; - m_House = house; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - AddBackground( 0, 0, 300, 150, 0xA28 ); - - AddItem( 90, 30, GetWestItemID( itemID ) ); - AddItem( 180, 30, itemID ); - - AddButton( 50, 35, 0x867, 0x869, (int) Buttons.East, GumpButtonType.Reply, 0 ); - AddButton( 145, 35, 0x867, 0x869, (int) Buttons.South, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Shield == null || m_Shield.Deleted || m_House == null ) - return; - - DecorativeShield shield = null; - - if ( info.ButtonID == (int) Buttons.East ) - shield = new DecorativeShield( GetWestItemID( m_ItemID ) ); - if ( info.ButtonID == (int) Buttons.South ) - shield = new DecorativeShield( m_ItemID ); - - if ( shield != null ) - { - m_House.Addons.Add( shield ); - - shield.IsRewardItem = m_Shield.IsRewardItem; - shield.MoveToWorld( m_Location, sender.Mobile.Map ); - - m_Shield.Delete(); - } - } - } - } - } -} + public class DecorativeShield : Item, IAddon, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public DecorativeShield() : this(0x156C) + { + } + + [Constructible] + public DecorativeShield(int itemID) : base(itemID) + { + Movable = false; + } + + public DecorativeShield(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public bool FacingSouth + { + get + { + if (ItemID < 0x1582) + return (ItemID & 0x1) == 0; + + return ItemID <= 0x1585; + } + } + + public Item Deed + { + get + { + DecorativeShieldDeed deed = new DecorativeShieldDeed(); + deed.IsRewardItem = m_IsRewardItem; + + return deed; + } + } + + public bool CouldFit(IPoint3D p, Map map) + { + if (map == null || !map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; + + if (FacingSouth) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // north wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // west wall + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Core.ML && m_IsRewardItem) + list.Add(1076220); // 4th Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(Location, 2)) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(RewardDemolitionGump)); + from.SendGump(new RewardDemolitionGump(this, 1049783)); // Do you wish to re-deed this decoration? + } + else + { + from.SendLocalizedMessage( + 1049784); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + } + + public class DecorativeShieldDeed : Item, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public DecorativeShieldDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } + + public DecorativeShieldDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1049771; // deed for a decorative shield wall hanging + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076220); // 4th Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; + + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + + public static int GetWestItemID(int east) + { + switch (east) + { + case 0x1582: return 0x1635; + case 0x1583: return 0x1634; + case 0x1584: return 0x1637; + case 0x1585: return 0x1636; + default: return east + 1; + } + } + + private class InternalGump : Gump + { + public const int Start = 0x156C; + public const int End = 0x1585; + private int m_Page; + + private DecorativeShieldDeed m_Shield; + + public InternalGump(DecorativeShieldDeed shield) : this(shield, 1) + { + } + + public InternalGump(DecorativeShieldDeed shield, int page) : base(150, 50) + { + m_Shield = shield; + m_Page = page; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + + AddBackground(25, 0, 500, 230, 0xA28); + + int itemID = Start; + + for (int i = 1; i <= 2; i++) + { + AddPage(i); + + for (int j = 0; j < 9 - i; j++) + { + AddItem(40 + j * 60, 70, itemID); + AddButton(60 + j * 60, 50, 0x845, 0x846, itemID, GumpButtonType.Reply, 0); + + if (itemID < 0x1582) + itemID += 2; + else + itemID += 1; + } + + switch (i) + { + case 1: + AddButton(455, 198, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 2); + break; + case 2: + AddButton(70, 198, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 1); + break; + } + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if ((m_Shield == null) | m_Shield.Deleted) + return; + + Mobile m = sender.Mobile; + + if (info.ButtonID >= Start && info.ButtonID <= End) + if ((info.ButtonID & 0x1) == 0 && info.ButtonID < 0x1582 || + info.ButtonID >= 0x1582 && info.ButtonID <= 0x1585) + { + m.SendLocalizedMessage(1049780); // Where would you like to place this decoration? + m.Target = new InternalTarget(m_Shield, info.ButtonID); + } + } + } + + private class InternalTarget : Target + { + private int m_ItemID; + private DecorativeShieldDeed m_Shield; + + public InternalTarget(DecorativeShieldDeed shield, int itemID) : base(-1, true, TargetFlags.None) + { + m_Shield = shield; + m_ItemID = itemID; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Shield == null || m_Shield.Deleted) + return; + + if (m_Shield.IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsOwner(from)) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; + + if (p == null || map == null) + return; + + Point3D p3d = new Point3D(p); + ItemData id = TileData.ItemTable[m_ItemID & TileData.MaxItemValue]; + + if (map.CanFit(p3d, id.Height)) + { + house = BaseHouse.FindHouseAt(p3d, map, id.Height); + + if (house != null && house.IsOwner(from)) + { + bool north = BaseAddon.IsWall(p3d.X, p3d.Y - 1, p3d.Z, map); + bool west = BaseAddon.IsWall(p3d.X - 1, p3d.Y, p3d.Z, map); + + if (north && west) + { + from.CloseGump(typeof(FacingGump)); + from.SendGump(new FacingGump(m_Shield, m_ItemID, p3d, house)); + } + else if (north || west) + { + DecorativeShield shield = null; + + if (north) + shield = new DecorativeShield(m_ItemID); + else if (west) + shield = new DecorativeShield(GetWestItemID(m_ItemID)); + + house.Addons.Add(shield); + + shield.IsRewardItem = m_Shield.IsRewardItem; + shield.MoveToWorld(p3d, map); + + m_Shield.Delete(); + } + else + { + from.SendLocalizedMessage(1049781); // This decoration must be placed next to a wall. + } + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } + else + { + from.SendLocalizedMessage(500269); // You cannot build that there. + } + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + private class FacingGump : Gump + { + private BaseHouse m_House; + private int m_ItemID; + private Point3D m_Location; + private DecorativeShieldDeed m_Shield; + + public FacingGump(DecorativeShieldDeed shield, int itemID, Point3D location, BaseHouse house) : base(150, 50) + { + m_Shield = shield; + m_ItemID = itemID; + m_Location = location; + m_House = house; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + AddBackground(0, 0, 300, 150, 0xA28); + + AddItem(90, 30, GetWestItemID(itemID)); + AddItem(180, 30, itemID); + + AddButton(50, 35, 0x867, 0x869, (int)Buttons.East, GumpButtonType.Reply, 0); + AddButton(145, 35, 0x867, 0x869, (int)Buttons.South, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Shield == null || m_Shield.Deleted || m_House == null) + return; + + DecorativeShield shield = null; + + if (info.ButtonID == (int)Buttons.East) + shield = new DecorativeShield(GetWestItemID(m_ItemID)); + if (info.ButtonID == (int)Buttons.South) + shield = new DecorativeShield(m_ItemID); + + if (shield != null) + { + m_House.Addons.Add(shield); + + shield.IsRewardItem = m_Shield.IsRewardItem; + shield.MoveToWorld(m_Location, sender.Mobile.Map); + + m_Shield.Delete(); + } + } + + private enum Buttons + { + Cancel, + South, + East + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/FlamingHead.cs b/Scripts/Items/Special/Veteran Rewards/FlamingHead.cs index e2dbf4f1b..a6451bb21 100644 --- a/Scripts/Items/Special/Veteran Rewards/FlamingHead.cs +++ b/Scripts/Items/Special/Veteran Rewards/FlamingHead.cs @@ -1,255 +1,283 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Multis; using Server.Network; using Server.Targeting; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class FlamingHead : StoneFaceTrapNoDamage, IAddon, IRewardItem - { - public override int LabelNumber => 1041266; // Flaming Head - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public class FlamingHead : StoneFaceTrapNoDamage, IAddon, IRewardItem + { + private bool m_IsRewardItem; - public Item Deed - { - get - { - FlamingHeadDeed deed = new FlamingHeadDeed(); - deed.IsRewardItem = m_IsRewardItem; + [Constructible] + public FlamingHead() : this(StoneFaceTrapType.NorthWall) + { + } - return deed; - } - } + [Constructible] + public FlamingHead(StoneFaceTrapType type) + { + LootType = LootType.Blessed; + Movable = false; + Type = type; + } - private bool m_IsRewardItem; + public FlamingHead(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public override int LabelNumber => 1041266; // Flaming Head + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - [Constructible] - public FlamingHead() : this( StoneFaceTrapType.NorthWall ) - { - } + public Item Deed + { + get + { + FlamingHeadDeed deed = new FlamingHeadDeed(); + deed.IsRewardItem = m_IsRewardItem; - [Constructible] - public FlamingHead( StoneFaceTrapType type ) - { - LootType = LootType.Blessed; - Movable = false; - Type = type; - } + return deed; + } + } - public FlamingHead( Serial serial ) : base( serial ) - { - } + public bool CouldFit(IPoint3D p, Map map) + { + if (map == null || !map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (Type == StoneFaceTrapType.NorthWestWall) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map) && + BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // north and west wall + if (Type == StoneFaceTrapType.NorthWall) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // north wall + if (Type == StoneFaceTrapType.WestWall) + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // west wall - if ( Core.ML && m_IsRewardItem ) - list.Add( 1076218 ); // 2nd Year Veteran Reward - } + return false; + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( RewardDemolitionGump ) ); - from.SendGump( new RewardDemolitionGump( this, 1018329 ) ); // Do you wish to re-deed this skull? - } - else - from.SendLocalizedMessage( 1018328 ); // You can only re-deed a skull if you placed it or you are the owner of the house. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (Core.ML && m_IsRewardItem) + list.Add(1076218); // 2nd Year Veteran Reward + } - writer.WriteEncodedInt( 0 ); // version + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(Location, 2)) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - writer.Write( (bool) m_IsRewardItem ); - } + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(RewardDemolitionGump)); + from.SendGump(new RewardDemolitionGump(this, 1018329)); // Do you wish to re-deed this skull? + } + else + { + from.SendLocalizedMessage( + 1018328); // You can only re-deed a skull if you placed it or you are the owner of the house. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadEncodedInt(); + writer.WriteEncodedInt(0); // version - m_IsRewardItem = reader.ReadBool(); - } + writer.Write(m_IsRewardItem); + } - public bool CouldFit( IPoint3D p, Map map ) - { - if ( map == null || !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Type == StoneFaceTrapType.NorthWestWall ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ) && BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // north and west wall - if ( Type == StoneFaceTrapType.NorthWall ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // north wall - if ( Type == StoneFaceTrapType.WestWall ) - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // west wall + int version = reader.ReadEncodedInt(); - return false; - } - } + m_IsRewardItem = reader.ReadBool(); + } + } - public class FlamingHeadDeed : Item, IRewardItem - { - public override int LabelNumber => 1041050; // a flaming head deed + public class FlamingHeadDeed : Item, IRewardItem + { + private bool m_IsRewardItem; - private bool m_IsRewardItem; + [Constructible] + public FlamingHeadDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public FlamingHeadDeed(Serial serial) : base(serial) + { + } - [Constructible] - public FlamingHeadDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } + public override int LabelNumber => 1041050; // a flaming head deed - public FlamingHeadDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076218 ); // 2nd Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076218); // 2nd Year Veteran Reward + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house != null && house.IsOwner( from ) ) - { - from.SendLocalizedMessage( 1042264 ); // Where would you like to place this head? - from.Target = new InternalTarget( this ); - } - else - from.SendLocalizedMessage( 502115 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } + if (house != null && house.IsOwner(from)) + { + from.SendLocalizedMessage(1042264); // Where would you like to place this head? + from.Target = new InternalTarget(this); + } + else + { + from.SendLocalizedMessage(502115); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } + m_IsRewardItem = reader.ReadBool(); + } - private class InternalTarget : Target - { - private FlamingHeadDeed m_Head; + private class InternalTarget : Target + { + private FlamingHeadDeed m_Head; - public InternalTarget( FlamingHeadDeed head ) : base( -1, true, TargetFlags.None ) - { - m_Head = head; - } + public InternalTarget(FlamingHeadDeed head) : base(-1, true, TargetFlags.None) + { + m_Head = head; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Head == null || m_Head.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Head == null || m_Head.Deleted) + return; - if ( m_Head.IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + if (m_Head.IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house != null && house.IsOwner( from ) ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; + if (house != null && house.IsOwner(from)) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; - if ( p == null || map == null ) - return; + if (p == null || map == null) + return; - Point3D p3d = new Point3D( p ); - ItemData id = TileData.ItemTable[ 0x10F5 ]; + Point3D p3d = new Point3D(p); + ItemData id = TileData.ItemTable[0x10F5]; - house = BaseHouse.FindHouseAt( p3d, map, id.Height ); + house = BaseHouse.FindHouseAt(p3d, map, id.Height); - if ( house != null && house.IsOwner( from ) ) - { - if ( map.CanFit( p3d, id.Height ) ) - { - bool north = BaseAddon.IsWall( p3d.X, p3d.Y - 1, p3d.Z, map ); - bool west = BaseAddon.IsWall( p3d.X - 1, p3d.Y, p3d.Z, map ); + if (house != null && house.IsOwner(from)) + { + if (map.CanFit(p3d, id.Height)) + { + bool north = BaseAddon.IsWall(p3d.X, p3d.Y - 1, p3d.Z, map); + bool west = BaseAddon.IsWall(p3d.X - 1, p3d.Y, p3d.Z, map); - FlamingHead head = null; + FlamingHead head = null; - if ( north && west ) - head = new FlamingHead( StoneFaceTrapType.NorthWestWall ); - else if ( north ) - head = new FlamingHead( StoneFaceTrapType.NorthWall ); - else if ( west ) - head = new FlamingHead( StoneFaceTrapType.WestWall ); + if (north && west) + head = new FlamingHead(StoneFaceTrapType.NorthWestWall); + else if (north) + head = new FlamingHead(StoneFaceTrapType.NorthWall); + else if (west) + head = new FlamingHead(StoneFaceTrapType.WestWall); - if ( north || west ) - { - house.Addons.Add( head ); + if (north || west) + { + house.Addons.Add(head); - head.IsRewardItem = m_Head.IsRewardItem; - head.MoveToWorld( p3d, map ); + head.IsRewardItem = m_Head.IsRewardItem; + head.MoveToWorld(p3d, map); - m_Head.Delete(); - } - else - from.SendLocalizedMessage( 1042266 ); // The head must be placed next to a wall. - } - else - from.SendLocalizedMessage( 1042266 ); // The head must be placed next to a wall. - } - else - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - else - from.SendLocalizedMessage( 502115 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - } - } -} + m_Head.Delete(); + } + else + { + from.SendLocalizedMessage(1042266); // The head must be placed next to a wall. + } + } + else + { + from.SendLocalizedMessage(1042266); // The head must be placed next to a wall. + } + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } + else + { + from.SendLocalizedMessage(502115); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/HangingSkeleton.cs b/Scripts/Items/Special/Veteran Rewards/HangingSkeleton.cs index 4d7ae61dd..41e7385b9 100644 --- a/Scripts/Items/Special/Veteran Rewards/HangingSkeleton.cs +++ b/Scripts/Items/Special/Veteran Rewards/HangingSkeleton.cs @@ -1,387 +1,414 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Multis; using Server.Network; using Server.Targeting; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class HangingSkeleton : Item, IAddon, IRewardItem - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; - - public Item Deed - { - get - { - HangingSkeletonDeed deed = new HangingSkeletonDeed(); - deed.IsRewardItem = m_IsRewardItem; - - return deed; - } - } - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - public bool FacingSouth - { - get - { - if ( ItemID == 0x1A03 || ItemID == 0x1A05 || ItemID == 0x1A09 || - ItemID == 0x1B1E || ItemID == 0x1B7F ) - return true; - - return false; - } - } - - [Constructible] - public HangingSkeleton() : this( 0x1596 ) - { - } - - [Constructible] - public HangingSkeleton( int itemID ) : base( itemID ) - { - LootType = LootType.Blessed; - Movable = false; - } - - public HangingSkeleton( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Core.ML && m_IsRewardItem ) - list.Add( 1076220 ); // 4th Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.InRange( Location, 3 ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( RewardDemolitionGump ) ); - from.SendGump( new RewardDemolitionGump( this, 1049783 ) ); // Do you wish to re-deed this decoration? - } - else - from.SendLocalizedMessage( 1049784 ); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - public bool CouldFit( IPoint3D p, Map map ) - { - if ( map == null || !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; - - if ( FacingSouth ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // north wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // west wall - } - } - - public class HangingSkeletonDeed : Item, IRewardItem - { - public override int LabelNumber => 1049772; // deed for a hanging skeleton decoration - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - [Constructible] - public HangingSkeletonDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } - - public HangingSkeletonDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076220 ); // 4th Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - public static int GetWestItemID( int south ) - { - switch ( south ) - { - case 0x1B1E: return 0x1B1D; - case 0x1B7F: return 0x1B7C; - default: return south + 1; - } - } - - private class InternalGump : Gump - { - private HangingSkeletonDeed m_Skeleton; - - public InternalGump( HangingSkeletonDeed skeleton ) : base( 100, 200 ) - { - m_Skeleton = skeleton; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddBackground( 25, 0, 500, 230, 0xA28 ); - - AddPage( 1 ); - - AddItem( 130, 70, 0x1A03 ); - AddButton( 150, 50, 0x845, 0x846, 0x1A03, GumpButtonType.Reply, 0 ); - - AddItem( 190, 70, 0x1A05 ); - AddButton( 210, 50, 0x845, 0x846, 0x1A05, GumpButtonType.Reply, 0 ); - - AddItem( 250, 70, 0x1A09 ); - AddButton( 270, 50, 0x845, 0x846, 0x1A09, GumpButtonType.Reply, 0 ); - - AddItem( 310, 70, 0x1B1E ); - AddButton( 330, 50, 0x845, 0x846, 0x1B1E, GumpButtonType.Reply, 0 ); - - AddItem( 370, 70, 0x1B7F ); - AddButton( 390, 50, 0x845, 0x846, 0x1B7F, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Skeleton == null | m_Skeleton.Deleted ) - return; - - Mobile m = sender.Mobile; - - if ( info.ButtonID == 0x1A03 || info.ButtonID == 0x1A05 || info.ButtonID == 0x1A09 || - info.ButtonID == 0x1B1E || info.ButtonID == 0x1B7F ) - { - m.SendLocalizedMessage( 1049780 ); // Where would you like to place this decoration? - m.Target = new InternalTarget( m_Skeleton, info.ButtonID ); - } - } - } - - private class InternalTarget : Target - { - private HangingSkeletonDeed m_Skeleton; - private int m_ItemID; - - public InternalTarget( HangingSkeletonDeed banner, int itemID ) : base( -1, true, TargetFlags.None ) - { - m_Skeleton = banner; - m_ItemID = itemID; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Skeleton == null || m_Skeleton.Deleted ) - return; - - if ( m_Skeleton.IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); - - if ( house != null && house.IsOwner( from ) ) - { - IPoint3D p = targeted as IPoint3D; - Map map = from.Map; - - if ( p == null || map == null ) - return; - - Point3D p3d = new Point3D( p ); - ItemData id = TileData.ItemTable[ m_ItemID & TileData.MaxItemValue ]; - - if ( map.CanFit( p3d, id.Height ) ) - { - house = BaseHouse.FindHouseAt( p3d, map, id.Height ); - - if ( house != null && house.IsOwner( from ) ) - { - bool north = BaseAddon.IsWall( p3d.X, p3d.Y - 1, p3d.Z, map ); - bool west = BaseAddon.IsWall( p3d.X - 1, p3d.Y, p3d.Z, map ); - - if ( north && west ) - { - from.CloseGump( typeof( FacingGump ) ); - from.SendGump( new FacingGump( m_Skeleton, m_ItemID, p3d, house ) ); - } - else if ( north || west ) - { - HangingSkeleton banner = null; - - if ( north ) - banner = new HangingSkeleton( m_ItemID ); - else if ( west ) - banner = new HangingSkeleton( GetWestItemID( m_ItemID ) ); - - house.Addons.Add( banner ); - - banner.IsRewardItem = m_Skeleton.IsRewardItem; - banner.MoveToWorld( p3d, map ); - - m_Skeleton.Delete(); - } - else - from.SendLocalizedMessage( 1042039 ); // The banner must be placed next to a wall. - } - else - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - else - from.SendLocalizedMessage( 500269 ); // You cannot build that there. - } - else - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - private class FacingGump : Gump - { - private HangingSkeletonDeed m_Skeleton; - private int m_ItemID; - private Point3D m_Location; - private BaseHouse m_House; - - private enum Buttons - { - Cancel, - South, - East - } - - public FacingGump( HangingSkeletonDeed banner, int itemID, Point3D location, BaseHouse house ) : base( 150, 50 ) - { - m_Skeleton = banner; - m_ItemID = itemID; - m_Location = location; - m_House = house; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddPage( 0 ); - - AddBackground( 0, 0, 300, 150, 0xA28 ); - - AddItem( 90, 30, GetWestItemID( itemID ) ); - AddItem( 180, 30, itemID ); - - AddButton( 50, 35, 0x868, 0x869, (int) Buttons.East, GumpButtonType.Reply, 0 ); - AddButton( 145, 35, 0x868, 0x869, (int) Buttons.South, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Skeleton == null || m_Skeleton.Deleted || m_House == null ) - return; - - HangingSkeleton banner = null; - - if ( info.ButtonID == (int) Buttons.East ) - banner = new HangingSkeleton( GetWestItemID( m_ItemID ) ); - if ( info.ButtonID == (int) Buttons.South ) - banner = new HangingSkeleton( m_ItemID ); - - if ( banner != null ) - { - m_House.Addons.Add( banner ); - - banner.IsRewardItem = m_Skeleton.IsRewardItem; - banner.MoveToWorld( m_Location, sender.Mobile.Map ); - - m_Skeleton.Delete(); - } - } - } - } - } -} + public class HangingSkeleton : Item, IAddon, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public HangingSkeleton() : this(0x1596) + { + } + + [Constructible] + public HangingSkeleton(int itemID) : base(itemID) + { + LootType = LootType.Blessed; + Movable = false; + } + + public HangingSkeleton(Serial serial) : base(serial) + { + } + + public override bool ForceShowProperties => ObjectPropertyList.Enabled; + + public bool FacingSouth + { + get + { + if (ItemID == 0x1A03 || ItemID == 0x1A05 || ItemID == 0x1A09 || + ItemID == 0x1B1E || ItemID == 0x1B7F) + return true; + + return false; + } + } + + public Item Deed + { + get + { + HangingSkeletonDeed deed = new HangingSkeletonDeed(); + deed.IsRewardItem = m_IsRewardItem; + + return deed; + } + } + + public bool CouldFit(IPoint3D p, Map map) + { + if (map == null || !map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; + + if (FacingSouth) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // north wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // west wall + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Core.ML && m_IsRewardItem) + list.Add(1076220); // 4th Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (from.InRange(Location, 3)) + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(RewardDemolitionGump)); + from.SendGump(new RewardDemolitionGump(this, 1049783)); // Do you wish to re-deed this decoration? + } + else + { + from.SendLocalizedMessage( + 1049784); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + } + + public class HangingSkeletonDeed : Item, IRewardItem + { + private bool m_IsRewardItem; + + [Constructible] + public HangingSkeletonDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } + + public HangingSkeletonDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1049772; // deed for a hanging skeleton decoration + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076220); // 4th Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; + + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + + public static int GetWestItemID(int south) + { + switch (south) + { + case 0x1B1E: return 0x1B1D; + case 0x1B7F: return 0x1B7C; + default: return south + 1; + } + } + + private class InternalGump : Gump + { + private HangingSkeletonDeed m_Skeleton; + + public InternalGump(HangingSkeletonDeed skeleton) : base(100, 200) + { + m_Skeleton = skeleton; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + + AddBackground(25, 0, 500, 230, 0xA28); + + AddPage(1); + + AddItem(130, 70, 0x1A03); + AddButton(150, 50, 0x845, 0x846, 0x1A03, GumpButtonType.Reply, 0); + + AddItem(190, 70, 0x1A05); + AddButton(210, 50, 0x845, 0x846, 0x1A05, GumpButtonType.Reply, 0); + + AddItem(250, 70, 0x1A09); + AddButton(270, 50, 0x845, 0x846, 0x1A09, GumpButtonType.Reply, 0); + + AddItem(310, 70, 0x1B1E); + AddButton(330, 50, 0x845, 0x846, 0x1B1E, GumpButtonType.Reply, 0); + + AddItem(370, 70, 0x1B7F); + AddButton(390, 50, 0x845, 0x846, 0x1B7F, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if ((m_Skeleton == null) | m_Skeleton.Deleted) + return; + + Mobile m = sender.Mobile; + + if (info.ButtonID == 0x1A03 || info.ButtonID == 0x1A05 || info.ButtonID == 0x1A09 || + info.ButtonID == 0x1B1E || info.ButtonID == 0x1B7F) + { + m.SendLocalizedMessage(1049780); // Where would you like to place this decoration? + m.Target = new InternalTarget(m_Skeleton, info.ButtonID); + } + } + } + + private class InternalTarget : Target + { + private int m_ItemID; + private HangingSkeletonDeed m_Skeleton; + + public InternalTarget(HangingSkeletonDeed banner, int itemID) : base(-1, true, TargetFlags.None) + { + m_Skeleton = banner; + m_ItemID = itemID; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Skeleton == null || m_Skeleton.Deleted) + return; + + if (m_Skeleton.IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); + + if (house != null && house.IsOwner(from)) + { + IPoint3D p = targeted as IPoint3D; + Map map = from.Map; + + if (p == null || map == null) + return; + + Point3D p3d = new Point3D(p); + ItemData id = TileData.ItemTable[m_ItemID & TileData.MaxItemValue]; + + if (map.CanFit(p3d, id.Height)) + { + house = BaseHouse.FindHouseAt(p3d, map, id.Height); + + if (house != null && house.IsOwner(from)) + { + bool north = BaseAddon.IsWall(p3d.X, p3d.Y - 1, p3d.Z, map); + bool west = BaseAddon.IsWall(p3d.X - 1, p3d.Y, p3d.Z, map); + + if (north && west) + { + from.CloseGump(typeof(FacingGump)); + from.SendGump(new FacingGump(m_Skeleton, m_ItemID, p3d, house)); + } + else if (north || west) + { + HangingSkeleton banner = null; + + if (north) + banner = new HangingSkeleton(m_ItemID); + else if (west) + banner = new HangingSkeleton(GetWestItemID(m_ItemID)); + + house.Addons.Add(banner); + + banner.IsRewardItem = m_Skeleton.IsRewardItem; + banner.MoveToWorld(p3d, map); + + m_Skeleton.Delete(); + } + else + { + from.SendLocalizedMessage(1042039); // The banner must be placed next to a wall. + } + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } + else + { + from.SendLocalizedMessage(500269); // You cannot build that there. + } + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + private class FacingGump : Gump + { + private BaseHouse m_House; + private int m_ItemID; + private Point3D m_Location; + private HangingSkeletonDeed m_Skeleton; + + public FacingGump(HangingSkeletonDeed banner, int itemID, Point3D location, BaseHouse house) : base(150, 50) + { + m_Skeleton = banner; + m_ItemID = itemID; + m_Location = location; + m_House = house; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddPage(0); + + AddBackground(0, 0, 300, 150, 0xA28); + + AddItem(90, 30, GetWestItemID(itemID)); + AddItem(180, 30, itemID); + + AddButton(50, 35, 0x868, 0x869, (int)Buttons.East, GumpButtonType.Reply, 0); + AddButton(145, 35, 0x868, 0x869, (int)Buttons.South, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Skeleton == null || m_Skeleton.Deleted || m_House == null) + return; + + HangingSkeleton banner = null; + + if (info.ButtonID == (int)Buttons.East) + banner = new HangingSkeleton(GetWestItemID(m_ItemID)); + if (info.ButtonID == (int)Buttons.South) + banner = new HangingSkeleton(m_ItemID); + + if (banner != null) + { + m_House.Addons.Add(banner); + + banner.IsRewardItem = m_Skeleton.IsRewardItem; + banner.MoveToWorld(m_Location, sender.Mobile.Map); + + m_Skeleton.Delete(); + } + } + + private enum Buttons + { + Cancel, + South, + East + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/MiningCart.cs b/Scripts/Items/Special/Veteran Rewards/MiningCart.cs index 63b7850d4..0e4b6d36d 100644 --- a/Scripts/Items/Special/Veteran Rewards/MiningCart.cs +++ b/Scripts/Items/Special/Veteran Rewards/MiningCart.cs @@ -6,382 +6,438 @@ using Server.Network; namespace Server.Items { - public enum MiningCartType - { - OreSouth = 100, - OreEast = 101, - GemSouth = 102, - GemEast = 103 - } + public enum MiningCartType + { + OreSouth = 100, + OreEast = 101, + GemSouth = 102, + GemEast = 103 + } - public class MiningCart : BaseAddon, IRewardItem - { - public override BaseAddonDeed Deed - { - get - { - MiningCartDeed deed = new MiningCartDeed(); - deed.IsRewardItem = IsRewardItem; - deed.Gems = Gems; - deed.Ore = Ore; + public class MiningCart : BaseAddon, IRewardItem + { + private Timer m_Timer; - return deed; - } - } + [Constructible] + public MiningCart(MiningCartType type) + { + CartType = type; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } + switch (type) + { + case MiningCartType.OreSouth: + AddComponent(new AddonComponent(0x1A83), 0, 0, 0); + AddComponent(new AddonComponent(0x1A82), 0, 1, 0); + AddComponent(new AddonComponent(0x1A86), 0, -1, 0); + break; + case MiningCartType.OreEast: + AddComponent(new AddonComponent(0x1A88), 0, 0, 0); + AddComponent(new AddonComponent(0x1A87), 1, 0, 0); + AddComponent(new AddonComponent(0x1A8B), -1, 0, 0); + break; + case MiningCartType.GemSouth: + AddComponent(new LocalizedAddonComponent(0x1A83, 1080388), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1A82, 1080388), 0, 1, 0); + AddComponent(new LocalizedAddonComponent(0x1A86, 1080388), 0, -1, 0); - [CommandProperty( AccessLevel.GameMaster )] - public MiningCartType CartType { get; private set; } + AddComponent(new AddonComponent(0xF2C), 0, 0, 6); + AddComponent(new AddonComponent(0xF1D), 0, 0, 5); + AddComponent(new AddonComponent(0xF2B), 0, 0, 2); + AddComponent(new AddonComponent(0xF21), 0, 0, 1); + AddComponent(new AddonComponent(0xF22), 0, 0, 4); + AddComponent(new AddonComponent(0xF2F), 0, 0, 5); + AddComponent(new AddonComponent(0xF26), 0, 0, 6); + AddComponent(new AddonComponent(0xF27), 0, 0, 3); + AddComponent(new AddonComponent(0xF29), 0, 0, 0); + break; + case MiningCartType.GemEast: + AddComponent(new LocalizedAddonComponent(0x1A88, 1080388), 0, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1A87, 1080388), 1, 0, 0); + AddComponent(new LocalizedAddonComponent(0x1A8B, 1080388), -1, 0, 0); - [CommandProperty( AccessLevel.GameMaster )] - public int Gems { get; set; } + AddComponent(new AddonComponent(0xF2E), 0, 0, 6); + AddComponent(new AddonComponent(0xF12), 0, 0, 3); + AddComponent(new AddonComponent(0xF29), 0, 0, 1); + AddComponent(new AddonComponent(0xF24), 0, 0, 5); + AddComponent(new AddonComponent(0xF21), 0, 0, 1); + AddComponent(new AddonComponent(0xF2B), 0, 0, 3); + AddComponent(new AddonComponent(0xF2F), 0, 0, 4); + AddComponent(new AddonComponent(0xF23), 0, 0, 3); + AddComponent(new AddonComponent(0xF27), 0, 0, 3); + break; + } - [CommandProperty( AccessLevel.GameMaster )] - public int Ore { get; set; } + m_Timer = Timer.DelayCall(TimeSpan.FromDays(1), TimeSpan.FromDays(1), GiveResources); + } - private Timer m_Timer; + public MiningCart(Serial serial) : base(serial) + { + } - [Constructible] - public MiningCart( MiningCartType type ) - { - CartType = type; + public override BaseAddonDeed Deed + { + get + { + MiningCartDeed deed = new MiningCartDeed(); + deed.IsRewardItem = IsRewardItem; + deed.Gems = Gems; + deed.Ore = Ore; - switch ( type ) - { - case MiningCartType.OreSouth: - AddComponent( new AddonComponent( 0x1A83 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1A82 ), 0, 1, 0 ); - AddComponent( new AddonComponent( 0x1A86 ), 0, -1, 0 ); - break; - case MiningCartType.OreEast: - AddComponent( new AddonComponent( 0x1A88 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x1A87 ), 1, 0, 0 ); - AddComponent( new AddonComponent( 0x1A8B ), -1, 0, 0 ); - break; - case MiningCartType.GemSouth: - AddComponent( new LocalizedAddonComponent( 0x1A83, 1080388 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1A82, 1080388 ), 0, 1, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1A86, 1080388 ), 0, -1, 0 ); + return deed; + } + } - AddComponent( new AddonComponent( 0xF2C ), 0, 0, 6 ); - AddComponent( new AddonComponent( 0xF1D ), 0, 0, 5 ); - AddComponent( new AddonComponent( 0xF2B ), 0, 0, 2 ); - AddComponent( new AddonComponent( 0xF21 ), 0, 0, 1 ); - AddComponent( new AddonComponent( 0xF22 ), 0, 0, 4 ); - AddComponent( new AddonComponent( 0xF2F ), 0, 0, 5 ); - AddComponent( new AddonComponent( 0xF26 ), 0, 0, 6 ); - AddComponent( new AddonComponent( 0xF27 ), 0, 0, 3 ); - AddComponent( new AddonComponent( 0xF29 ), 0, 0, 0 ); - break; - case MiningCartType.GemEast: - AddComponent( new LocalizedAddonComponent( 0x1A88, 1080388 ), 0, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1A87, 1080388 ), 1, 0, 0 ); - AddComponent( new LocalizedAddonComponent( 0x1A8B, 1080388 ), -1, 0, 0 ); + [CommandProperty(AccessLevel.GameMaster)] + public MiningCartType CartType{ get; private set; } - AddComponent( new AddonComponent( 0xF2E ), 0, 0, 6 ); - AddComponent( new AddonComponent( 0xF12 ), 0, 0, 3 ); - AddComponent( new AddonComponent( 0xF29 ), 0, 0, 1 ); - AddComponent( new AddonComponent( 0xF24 ), 0, 0, 5 ); - AddComponent( new AddonComponent( 0xF21 ), 0, 0, 1 ); - AddComponent( new AddonComponent( 0xF2B ), 0, 0, 3 ); - AddComponent( new AddonComponent( 0xF2F ), 0, 0, 4 ); - AddComponent( new AddonComponent( 0xF23 ), 0, 0, 3 ); - AddComponent( new AddonComponent( 0xF27 ), 0, 0, 3 ); - break; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Gems{ get; set; } - m_Timer = Timer.DelayCall( TimeSpan.FromDays( 1 ), TimeSpan.FromDays( 1 ), GiveResources ); - } + [CommandProperty(AccessLevel.GameMaster)] + public int Ore{ get; set; } - public MiningCart( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } - private void GiveResources() - { - switch ( CartType ) - { - case MiningCartType.OreSouth: - case MiningCartType.OreEast: - Ore = Math.Min( 100, Ore + 10 ); - break; - case MiningCartType.GemSouth: - case MiningCartType.GemEast: - Gems = Math.Min( 50, Gems + 5 ); - break; - } - } + private void GiveResources() + { + switch (CartType) + { + case MiningCartType.OreSouth: + case MiningCartType.OreEast: + Ore = Math.Min(100, Ore + 10); + break; + case MiningCartType.GemSouth: + case MiningCartType.GemEast: + Gems = Math.Min(50, Gems + 5); + break; + } + } - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - /* - * Unique problems have unique solutions. OSI does not have a problem with 1000s of mining carts - * due to the fact that they have only a miniscule fraction of the number of 10 year vets that a - * typical RunUO shard will have (RunUO's scaled down account aging system makes this a unique problem), - * and the "freeness" of free accounts. We also dont have mitigating factors like inactive (unpaid) - * accounts not gaining veteran time. - * - * The lack of high end vets and vet rewards on OSI has made testing the *exact* ranging/stacking - * behavior of these things all but impossible, so either way its just an estimation. - * - * If youd like your shard's carts/stumps to work the way they did before, simply replace the check - * below with this line of code: - * - * if (!from.InRange(GetWorldLocation(), 2) - * - * However, I am sure these checks are more accurate to OSI than the former version was. - * - */ + /* + * Unique problems have unique solutions. OSI does not have a problem with 1000s of mining carts + * due to the fact that they have only a miniscule fraction of the number of 10 year vets that a + * typical RunUO shard will have (RunUO's scaled down account aging system makes this a unique problem), + * and the "freeness" of free accounts. We also dont have mitigating factors like inactive (unpaid) + * accounts not gaining veteran time. + * + * The lack of high end vets and vet rewards on OSI has made testing the *exact* ranging/stacking + * behavior of these things all but impossible, so either way its just an estimation. + * + * If youd like your shard's carts/stumps to work the way they did before, simply replace the check + * below with this line of code: + * + * if (!from.InRange(GetWorldLocation(), 2) + * + * However, I am sure these checks are more accurate to OSI than the former version was. + * + */ - if (!from.InRange(GetWorldLocation(), 2) || !from.InLOS(this) || !((from.Z - Z) > -3 && (from.Z - Z) < 3)) - { - from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. - } - else if ( house != null && house.HasSecureAccess( from, SecureLevel.Friends ) ) - { - switch ( CartType ) - { - case MiningCartType.OreSouth: - case MiningCartType.OreEast: - if ( Ore > 0 ) - { - Item ingots = null; + if (!from.InRange(GetWorldLocation(), 2) || !from.InLOS(this) || !(from.Z - Z > -3 && from.Z - Z < 3)) + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + else if (house != null && house.HasSecureAccess(from, SecureLevel.Friends)) + switch (CartType) + { + case MiningCartType.OreSouth: + case MiningCartType.OreEast: + if (Ore > 0) + { + Item ingots = null; - switch ( Utility.Random( 9 ) ) - { - case 0: ingots = new IronIngot(); break; - case 1: ingots = new DullCopperIngot(); break; - case 2: ingots = new ShadowIronIngot(); break; - case 3: ingots = new CopperIngot(); break; - case 4: ingots = new BronzeIngot(); break; - case 5: ingots = new GoldIngot(); break; - case 6: ingots = new AgapiteIngot(); break; - case 7: ingots = new VeriteIngot(); break; - case 8: ingots = new ValoriteIngot(); break; - } + switch (Utility.Random(9)) + { + case 0: + ingots = new IronIngot(); + break; + case 1: + ingots = new DullCopperIngot(); + break; + case 2: + ingots = new ShadowIronIngot(); + break; + case 3: + ingots = new CopperIngot(); + break; + case 4: + ingots = new BronzeIngot(); + break; + case 5: + ingots = new GoldIngot(); + break; + case 6: + ingots = new AgapiteIngot(); + break; + case 7: + ingots = new VeriteIngot(); + break; + case 8: + ingots = new ValoriteIngot(); + break; + } - int amount = Math.Min( 10, Ore ); - ingots.Amount = amount; + int amount = Math.Min(10, Ore); + ingots.Amount = amount; - if ( !from.PlaceInBackpack( ingots ) ) - { - ingots.Delete(); - from.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - { - PublicOverheadMessage(MessageType.Regular, 0, 1094724, amount.ToString() ); // Ore: ~1_COUNT~ - Ore -= amount; - } - } - else - from.SendLocalizedMessage( 1094725 ); // There are no more resources available at this time. + if (!from.PlaceInBackpack(ingots)) + { + ingots.Delete(); + from.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + PublicOverheadMessage(MessageType.Regular, 0, 1094724, amount.ToString()); // Ore: ~1_COUNT~ + Ore -= amount; + } + } + else + { + from.SendLocalizedMessage(1094725); // There are no more resources available at this time. + } - break; - case MiningCartType.GemSouth: - case MiningCartType.GemEast: - if ( Gems > 0 ) - { - Item gems = null; + break; + case MiningCartType.GemSouth: + case MiningCartType.GemEast: + if (Gems > 0) + { + Item gems = null; - switch ( Utility.Random( 15 ) ) - { - case 0: gems = new Amber(); break; - case 1: gems = new Amethyst(); break; - case 2: gems = new Citrine(); break; - case 3: gems = new Diamond(); break; - case 4: gems = new Emerald(); break; - case 5: gems = new Ruby(); break; - case 6: gems = new Sapphire(); break; - case 7: gems = new StarSapphire(); break; - case 8: gems = new Tourmaline(); break; + switch (Utility.Random(15)) + { + case 0: + gems = new Amber(); + break; + case 1: + gems = new Amethyst(); + break; + case 2: + gems = new Citrine(); + break; + case 3: + gems = new Diamond(); + break; + case 4: + gems = new Emerald(); + break; + case 5: + gems = new Ruby(); + break; + case 6: + gems = new Sapphire(); + break; + case 7: + gems = new StarSapphire(); + break; + case 8: + gems = new Tourmaline(); + break; - // Mondain's Legacy gems - case 9: gems = new PerfectEmerald(); break; - case 10: gems = new DarkSapphire(); break; - case 11: gems = new Turquoise(); break; - case 12: gems = new EcruCitrine(); break; - case 13: gems = new FireRuby(); break; - case 14: gems = new BlueDiamond(); break; - } + // Mondain's Legacy gems + case 9: + gems = new PerfectEmerald(); + break; + case 10: + gems = new DarkSapphire(); + break; + case 11: + gems = new Turquoise(); + break; + case 12: + gems = new EcruCitrine(); + break; + case 13: + gems = new FireRuby(); + break; + case 14: + gems = new BlueDiamond(); + break; + } - int amount = Math.Min( 5, Gems ); - gems.Amount = amount; + int amount = Math.Min(5, Gems); + gems.Amount = amount; - if ( !from.PlaceInBackpack( gems ) ) - { - gems.Delete(); - from.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - { - PublicOverheadMessage( MessageType.Regular, 0, 1094723, amount.ToString() ); // Gems: ~1_COUNT~ - Gems -= amount; - } - } - else - from.SendLocalizedMessage( 1094725 ); // There are no more resources available at this time. + if (!from.PlaceInBackpack(gems)) + { + gems.Delete(); + from.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + PublicOverheadMessage(MessageType.Regular, 0, 1094723, amount.ToString()); // Gems: ~1_COUNT~ + Gems -= amount; + } + } + else + { + from.SendLocalizedMessage(1094725); // There are no more resources available at this time. + } - break; - } - } - else - from.SendLocalizedMessage( 1061637 ); // You are not allowed to access this. - } + break; + } + else + from.SendLocalizedMessage(1061637); // You are not allowed to access this. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version + writer.WriteEncodedInt(1); // version - #region version 1 - writer.Write( (int) CartType ); - #endregion + #region version 1 - writer.Write( (bool) IsRewardItem ); - writer.Write( (int) Gems ); - writer.Write( (int) Ore ); + writer.Write((int)CartType); - if ( m_Timer != null ) - writer.Write( (DateTime) m_Timer.Next ); - else - writer.Write( (DateTime) DateTime.UtcNow + TimeSpan.FromDays( 1 ) ); - } + #endregion - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(IsRewardItem); + writer.Write(Gems); + writer.Write(Ore); - int version = reader.ReadEncodedInt(); + if (m_Timer != null) + writer.Write(m_Timer.Next); + else + writer.Write(DateTime.UtcNow + TimeSpan.FromDays(1)); + } - switch ( version ) - { - case 1: - CartType = (MiningCartType) reader.ReadInt(); - goto case 0; - case 0: - IsRewardItem = reader.ReadBool(); - Gems = reader.ReadInt(); - Ore = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - DateTime next = reader.ReadDateTime(); + int version = reader.ReadEncodedInt(); - if ( next < DateTime.UtcNow ) - next = DateTime.UtcNow; + switch (version) + { + case 1: + CartType = (MiningCartType)reader.ReadInt(); + goto case 0; + case 0: + IsRewardItem = reader.ReadBool(); + Gems = reader.ReadInt(); + Ore = reader.ReadInt(); - m_Timer = Timer.DelayCall( next - DateTime.UtcNow, TimeSpan.FromDays( 1 ), GiveResources ); - break; - } - } - } + DateTime next = reader.ReadDateTime(); - public class MiningCartDeed : BaseAddonDeed, IRewardItem, IRewardOption - { - public override int LabelNumber => 1080385; // deed for a mining cart decoration + if (next < DateTime.UtcNow) + next = DateTime.UtcNow; - public override BaseAddon Addon - { - get - { - MiningCart addon = new MiningCart( m_CartType ); - addon.IsRewardItem = m_IsRewardItem; - addon.Gems = Gems; - addon.Ore = Ore; + m_Timer = Timer.DelayCall(next - DateTime.UtcNow, TimeSpan.FromDays(1), GiveResources); + break; + } + } + } - return addon; - } - } + public class MiningCartDeed : BaseAddonDeed, IRewardItem, IRewardOption + { + private MiningCartType m_CartType; - private MiningCartType m_CartType; + private bool m_IsRewardItem; - private bool m_IsRewardItem; + [Constructible] + public MiningCartDeed() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public MiningCartDeed(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Gems { get; set; } + public override int LabelNumber => 1080385; // deed for a mining cart decoration - [CommandProperty( AccessLevel.GameMaster )] - public int Ore { get; set; } + public override BaseAddon Addon + { + get + { + MiningCart addon = new MiningCart(m_CartType); + addon.IsRewardItem = m_IsRewardItem; + addon.Gems = Gems; + addon.Ore = Ore; - [Constructible] - public MiningCartDeed() - { - LootType = LootType.Blessed; - } + return addon; + } + } - public MiningCartDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Gems{ get; set; } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public int Ore{ get; set; } - if ( m_IsRewardItem ) - list.Add( 1080457 ); // 10th Year Veteran Reward - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public void GetOptions(RewardOptionList list) + { + list.Add((int)MiningCartType.OreSouth, 1080391); + list.Add((int)MiningCartType.OreEast, 1080390); + list.Add((int)MiningCartType.GemSouth, 1080500); + list.Add((int)MiningCartType.GemEast, 1080499); + } - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( RewardOptionGump ) ); - from.SendGump( new RewardOptionGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public void OnOptionSelected(Mobile from, int choice) + { + m_CartType = (MiningCartType)choice; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (!Deleted) + base.OnDoubleClick(from); + } - writer.WriteEncodedInt( 0 ); // version + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - writer.Write( (bool) m_IsRewardItem ); - writer.Write( (int) Gems ); - writer.Write( (int) Ore ); - } + if (m_IsRewardItem) + list.Add(1080457); // 10th Year Veteran Reward + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - int version = reader.ReadEncodedInt(); + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(RewardOptionGump)); + from.SendGump(new RewardOptionGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - m_IsRewardItem = reader.ReadBool(); - Gems = reader.ReadInt(); - Ore = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void GetOptions( RewardOptionList list ) - { - list.Add( (int) MiningCartType.OreSouth, 1080391 ); - list.Add( (int) MiningCartType.OreEast, 1080390 ); - list.Add( (int) MiningCartType.GemSouth, 1080500 ); - list.Add( (int) MiningCartType.GemEast, 1080499 ); - } + writer.WriteEncodedInt(0); // version - public void OnOptionSelected( Mobile from, int choice ) - { - m_CartType = (MiningCartType) choice; + writer.Write(m_IsRewardItem); + writer.Write(Gems); + writer.Write(Ore); + } - if ( !Deleted ) - base.OnDoubleClick( from ); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + Gems = reader.ReadInt(); + Ore = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/MinotaurStatue.cs b/Scripts/Items/Special/Veteran Rewards/MinotaurStatue.cs index 5e0ede3e7..9386e8b38 100644 --- a/Scripts/Items/Special/Veteran Rewards/MinotaurStatue.cs +++ b/Scripts/Items/Special/Veteran Rewards/MinotaurStatue.cs @@ -1,177 +1,188 @@ -using Server.Gumps; using Server.Engines.VeteranRewards; +using Server.Gumps; namespace Server.Items { - public enum MinotaurStatueType - { - AttackSouth = 100, - AttackEast = 101, - DefendSouth = 102, - DefendEast = 103 - } + public enum MinotaurStatueType + { + AttackSouth = 100, + AttackEast = 101, + DefendSouth = 102, + DefendEast = 103 + } - public class MinotaurStatue : BaseAddon, IRewardItem - { - public override BaseAddonDeed Deed - { - get - { - MinotaurStatueDeed deed = new MinotaurStatueDeed(); - deed.IsRewardItem = m_IsRewardItem; + public class MinotaurStatue : BaseAddon, IRewardItem + { + private bool m_IsRewardItem; - return deed; - } - } + [Constructible] + public MinotaurStatue(MinotaurStatueType type) + { + switch (type) + { + case MinotaurStatueType.AttackSouth: + AddComponent(new AddonComponent(0x306C), 0, 0, 0); + AddComponent(new AddonComponent(0x306D), -1, 0, 0); + AddComponent(new AddonComponent(0x306E), 0, -1, 0); + break; + case MinotaurStatueType.AttackEast: + AddComponent(new AddonComponent(0x3074), 0, 0, 0); + AddComponent(new AddonComponent(0x3075), -1, 0, 0); + AddComponent(new AddonComponent(0x3076), 0, -1, 0); + break; + case MinotaurStatueType.DefendSouth: + AddComponent(new AddonComponent(0x3072), 0, 0, 0); + AddComponent(new AddonComponent(0x3073), 0, -1, 0); + break; + case MinotaurStatueType.DefendEast: + AddComponent(new AddonComponent(0x306F), 0, 0, 0); + AddComponent(new AddonComponent(0x3070), -1, 0, 0); + AddComponent(new AddonComponent(0x3071), 0, -1, 0); + break; + } + } - private bool m_IsRewardItem; + public MinotaurStatue(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public override BaseAddonDeed Deed + { + get + { + MinotaurStatueDeed deed = new MinotaurStatueDeed(); + deed.IsRewardItem = m_IsRewardItem; - [Constructible] - public MinotaurStatue( MinotaurStatueType type ) - { - switch ( type ) - { - case MinotaurStatueType.AttackSouth: - AddComponent( new AddonComponent( 0x306C ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x306D ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x306E ), 0, -1, 0 ); - break; - case MinotaurStatueType.AttackEast: - AddComponent( new AddonComponent( 0x3074 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3075 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x3076 ), 0, -1, 0 ); - break; - case MinotaurStatueType.DefendSouth: - AddComponent( new AddonComponent( 0x3072 ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3073 ), 0, -1, 0 ); - break; - case MinotaurStatueType.DefendEast: - AddComponent( new AddonComponent( 0x306F ), 0, 0, 0 ); - AddComponent( new AddonComponent( 0x3070 ), -1, 0, 0 ); - AddComponent( new AddonComponent( 0x3071 ), 0, -1, 0 ); - break; - } - } + return deed; + } + } - public MinotaurStatue( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } - } + m_IsRewardItem = reader.ReadBool(); + } + } - public class MinotaurStatueDeed : BaseAddonDeed, IRewardItem, IRewardOption - { - public override int LabelNumber => 1080409; // Minotaur Statue Deed + public class MinotaurStatueDeed : BaseAddonDeed, IRewardItem, IRewardOption + { + private bool m_IsRewardItem; - public override BaseAddon Addon - { - get - { - MinotaurStatue addon = new MinotaurStatue( m_StatueType ); - addon.IsRewardItem = m_IsRewardItem; + private MinotaurStatueType m_StatueType; - return addon; - } - } + [Constructible] + public MinotaurStatueDeed() + { + LootType = LootType.Blessed; + } - private MinotaurStatueType m_StatueType; - private bool m_IsRewardItem; + public MinotaurStatueDeed(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public override int LabelNumber => 1080409; // Minotaur Statue Deed - [Constructible] - public MinotaurStatueDeed() - { - LootType = LootType.Blessed; - } + public override BaseAddon Addon + { + get + { + MinotaurStatue addon = new MinotaurStatue(m_StatueType); + addon.IsRewardItem = m_IsRewardItem; - public MinotaurStatueDeed( Serial serial ) : base( serial ) - { - } + return addon; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( RewardOptionGump ) ); - from.SendGump( new RewardOptionGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + public void GetOptions(RewardOptionList list) + { + list.Add((int)MinotaurStatueType.AttackSouth, 1080410); // Minotaur Attack South + list.Add((int)MinotaurStatueType.AttackEast, 1080411); // Minotaur Attack East + list.Add((int)MinotaurStatueType.DefendSouth, 1080412); // Minotaur Defend South + list.Add((int)MinotaurStatueType.DefendEast, 1080413); // Minotaur Defend East + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public void OnOptionSelected(Mobile from, int option) + { + m_StatueType = (MinotaurStatueType)option; - if ( m_IsRewardItem ) - list.Add( 1076218 ); // 2nd Year Veteran Reward - } + if (!Deleted) + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - writer.WriteEncodedInt( 0 ); // version + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(RewardOptionGump)); + from.SendGump(new RewardOptionGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - writer.Write( (bool) m_IsRewardItem ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (m_IsRewardItem) + list.Add(1076218); // 2nd Year Veteran Reward + } - int version = reader.ReadEncodedInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_IsRewardItem = reader.ReadBool(); - } + writer.WriteEncodedInt(0); // version - public void GetOptions( RewardOptionList list ) - { - list.Add( (int) MinotaurStatueType.AttackSouth, 1080410 ); // Minotaur Attack South - list.Add( (int) MinotaurStatueType.AttackEast, 1080411 ); // Minotaur Attack East - list.Add( (int) MinotaurStatueType.DefendSouth, 1080412 ); // Minotaur Defend South - list.Add( (int) MinotaurStatueType.DefendEast, 1080413 ); // Minotaur Defend East - } + writer.Write(m_IsRewardItem); + } - public void OnOptionSelected( Mobile from, int option ) - { - m_StatueType = (MinotaurStatueType) option; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( !Deleted ) - base.OnDoubleClick( from ); - } - } -} + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/PottedCactus.cs b/Scripts/Items/Special/Veteran Rewards/PottedCactus.cs index 423806758..9884cacac 100644 --- a/Scripts/Items/Special/Veteran Rewards/PottedCactus.cs +++ b/Scripts/Items/Special/Veteran Rewards/PottedCactus.cs @@ -1,186 +1,197 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Network; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class RewardPottedCactus : Item, IRewardItem - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public class RewardPottedCactus : Item, IRewardItem + { + private bool m_IsRewardItem; - private bool m_IsRewardItem; + [Constructible] + public RewardPottedCactus() : this(Utility.RandomMinMax(0x1E0F, 0x1E14)) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set { m_IsRewardItem = value; InvalidateProperties(); } - } + [Constructible] + public RewardPottedCactus(int itemID) : base(itemID) + { + Weight = 5.0; + } - [Constructible] - public RewardPottedCactus() : this( Utility.RandomMinMax( 0x1E0F, 0x1E14 ) ) - { - } + public RewardPottedCactus(Serial serial) : base(serial) + { + } - [Constructible] - public RewardPottedCactus( int itemID ) : base( itemID ) - { - Weight = 5.0; - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public RewardPottedCactus( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 1 ); // version + writer.WriteEncodedInt(1); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - switch ( version ) - { - case 1: - m_IsRewardItem = reader.ReadBool(); - break; - } + switch (version) + { + case 1: + m_IsRewardItem = reader.ReadBool(); + break; + } + } + } - } - } + public class PottedCactusDeed : Item, IRewardItem + { + private bool m_IsRewardItem; - public class PottedCactusDeed : Item, IRewardItem - { - public override int LabelNumber => 1080407; // Potted Cactus Deed + [Constructible] + public PottedCactusDeed() : base(0x14F0) + { + LootType = LootType.Blessed; + Weight = 1.0; + } - private bool m_IsRewardItem; + public PottedCactusDeed(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public override int LabelNumber => 1080407; // Potted Cactus Deed - [Constructible] - public PottedCactusDeed() : base( 0x14F0 ) - { - LootType = LootType.Blessed; - Weight = 1.0; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public PottedCactusDeed( Serial serial ) : base( serial ) - { - } + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076219 ); // 3rd Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076219); // 3rd Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } + m_IsRewardItem = reader.ReadBool(); + } - private class InternalGump : Gump - { - private PottedCactusDeed m_Cactus; + private class InternalGump : Gump + { + private PottedCactusDeed m_Cactus; - public InternalGump( PottedCactusDeed cactus ) : base( 100, 200 ) - { - m_Cactus = cactus; + public InternalGump(PottedCactusDeed cactus) : base(100, 200) + { + m_Cactus = cactus; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); - AddBackground( 0, 0, 425, 250, 0xA28 ); + AddPage(0); + AddBackground(0, 0, 425, 250, 0xA28); - AddPage( 1 ); - AddLabel( 45, 15, 0, "Choose a Potted Cactus:" ); + AddPage(1); + AddLabel(45, 15, 0, "Choose a Potted Cactus:"); - AddItem( 45, 75, 0x1E0F ); - AddButton( 55, 50, 0x845, 0x846, 0x1E0F, GumpButtonType.Reply, 0 ); + AddItem(45, 75, 0x1E0F); + AddButton(55, 50, 0x845, 0x846, 0x1E0F, GumpButtonType.Reply, 0); - AddItem( 105, 75, 0x1E10 ); - AddButton( 115, 50, 0x845, 0x846, 0x1E10, GumpButtonType.Reply, 0 ); + AddItem(105, 75, 0x1E10); + AddButton(115, 50, 0x845, 0x846, 0x1E10, GumpButtonType.Reply, 0); - AddItem( 160, 75, 0x1E14 ); - AddButton( 175, 50, 0x845, 0x846, 0x1E14, GumpButtonType.Reply, 0 ); + AddItem(160, 75, 0x1E14); + AddButton(175, 50, 0x845, 0x846, 0x1E14, GumpButtonType.Reply, 0); - AddItem( 220, 75, 0x1E11 ); - AddButton( 235, 50, 0x845, 0x846, 0x1E11, GumpButtonType.Reply, 0 ); + AddItem(220, 75, 0x1E11); + AddButton(235, 50, 0x845, 0x846, 0x1E11, GumpButtonType.Reply, 0); - AddItem( 280, 75, 0x1E12 ); - AddButton( 295, 50, 0x845, 0x846, 0x1E12, GumpButtonType.Reply, 0 ); + AddItem(280, 75, 0x1E12); + AddButton(295, 50, 0x845, 0x846, 0x1E12, GumpButtonType.Reply, 0); - AddItem( 340, 75, 0x1E13 ); - AddButton( 355, 50, 0x845, 0x846, 0x1E13, GumpButtonType.Reply, 0 ); - } + AddItem(340, 75, 0x1E13); + AddButton(355, 50, 0x845, 0x846, 0x1E13, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Cactus == null | m_Cactus.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if ((m_Cactus == null) | m_Cactus.Deleted) + return; - Mobile m = sender.Mobile; + Mobile m = sender.Mobile; - if ( info.ButtonID >= 0x1E0F && info.ButtonID <= 0x1E14 ) - { - RewardPottedCactus cactus = new RewardPottedCactus( info.ButtonID ); - cactus.IsRewardItem = m_Cactus.IsRewardItem; + if (info.ButtonID >= 0x1E0F && info.ButtonID <= 0x1E14) + { + RewardPottedCactus cactus = new RewardPottedCactus(info.ButtonID); + cactus.IsRewardItem = m_Cactus.IsRewardItem; - if ( !m.PlaceInBackpack( cactus ) ) - { - cactus.Delete(); - m.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - m_Cactus.Delete(); - } - } - } - } -} + if (!m.PlaceInBackpack(cactus)) + { + cactus.Delete(); + m.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + m_Cactus.Delete(); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/StoneAnkh.cs b/Scripts/Items/Special/Veteran Rewards/StoneAnkh.cs index 8bf32f37c..e26a9ab32 100644 --- a/Scripts/Items/Special/Veteran Rewards/StoneAnkh.cs +++ b/Scripts/Items/Special/Veteran Rewards/StoneAnkh.cs @@ -1,266 +1,281 @@ -using Server.Multis; -using Server.Gumps; -using Server.Network; using Server.Engines.VeteranRewards; +using Server.Gumps; +using Server.Multis; +using Server.Network; namespace Server.Items { - public class StoneAnkhComponent : AddonComponent - { - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + public class StoneAnkhComponent : AddonComponent + { + public StoneAnkhComponent(int itemID) : base(itemID) + { + Weight = 1.0; + } - public StoneAnkhComponent( int itemID ) : base( itemID ) - { - Weight = 1.0; - } + public StoneAnkhComponent(Serial serial) : base(serial) + { + } - public StoneAnkhComponent( Serial serial ) : base( serial ) - { - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Addon is StoneAnkh ankh && ankh.IsRewardItem ) - list.Add( 1076221 ); // 5th Year Veteran Reward - } + if (Addon is StoneAnkh ankh && ankh.IsRewardItem) + list.Add(1076221); // 5th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } + int version = reader.ReadEncodedInt(); + } + } - public class StoneAnkh : BaseAddon, IRewardItem - { - public override BaseAddonDeed Deed - { - get - { - StoneAnkhDeed deed = new StoneAnkhDeed(); - deed.IsRewardItem = m_IsRewardItem; + public class StoneAnkh : BaseAddon, IRewardItem + { + private bool m_IsRewardItem; - return deed; - } - } + [Constructible] + public StoneAnkh() : this(true) + { + } - private bool m_IsRewardItem; + [Constructible] + public StoneAnkh(bool east) + { + if (east) + { + AddComponent(new StoneAnkhComponent(0x2), 0, 0, 0); + AddComponent(new StoneAnkhComponent(0x3), 0, -1, 0); + } + else + { + AddComponent(new StoneAnkhComponent(0x5), 0, 0, 0); + AddComponent(new StoneAnkhComponent(0x4), -1, 0, 0); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public StoneAnkh(Serial serial) : base(serial) + { + } - [Constructible] - public StoneAnkh() : this( true ) - { - } + public override BaseAddonDeed Deed + { + get + { + StoneAnkhDeed deed = new StoneAnkhDeed(); + deed.IsRewardItem = m_IsRewardItem; - [Constructible] - public StoneAnkh( bool east ) - { - if ( east ) - { - AddComponent( new StoneAnkhComponent( 0x2 ), 0, 0, 0 ); - AddComponent( new StoneAnkhComponent( 0x3 ), 0, -1, 0 ); - } - else - { - AddComponent( new StoneAnkhComponent( 0x5 ), 0, 0, 0 ); - AddComponent( new StoneAnkhComponent( 0x4 ), -1, 0, 0 ); - } - } + return deed; + } + } - public StoneAnkh( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void OnChop( Mobile from ) - { - from.SendLocalizedMessage( 500489 ); // You can't use an axe on that. - } + public override void OnChop(Mobile from) + { + from.SendLocalizedMessage(500489); // You can't use an axe on that. + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( Core.ML && m_IsRewardItem ) - list.Add( 1076221 ); // 5th Year Veteran Reward - } + if (Core.ML && m_IsRewardItem) + list.Add(1076221); // 5th Year Veteran Reward + } - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + if (from.InRange(Location, 2)) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - if ( house != null && house.IsOwner( from ) ) - { - from.CloseGump( typeof( RewardDemolitionGump ) ); - from.SendGump( new RewardDemolitionGump( this, 1049783 ) ); // Do you wish to re-deed this decoration? - } - else - from.SendLocalizedMessage( 1049784 ); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } + if (house != null && house.IsOwner(from)) + { + from.CloseGump(typeof(RewardDemolitionGump)); + from.SendGump(new RewardDemolitionGump(this, 1049783)); // Do you wish to re-deed this decoration? + } + else + { + from.SendLocalizedMessage( + 1049784); // You can only re-deed this decoration if you are the house owner or originally placed the decoration. + } + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } - } + m_IsRewardItem = reader.ReadBool(); + } + } - public class StoneAnkhDeed : BaseAddonDeed, IRewardItem - { - public override int LabelNumber => 1049773; // deed for a stone ankh + public class StoneAnkhDeed : BaseAddonDeed, IRewardItem + { + private bool m_East; + private bool m_IsRewardItem; - private bool m_East; - private bool m_IsRewardItem; + [Constructible] + public StoneAnkhDeed() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public StoneAnkhDeed(Serial serial) : base(serial) + { + } - public override BaseAddon Addon - { - get - { - StoneAnkh addon = new StoneAnkh( m_East ); - addon.IsRewardItem = m_IsRewardItem; + public override int LabelNumber => 1049773; // deed for a stone ankh - return addon; - } - } + public override BaseAddon Addon + { + get + { + StoneAnkh addon = new StoneAnkh(m_East); + addon.IsRewardItem = m_IsRewardItem; - [Constructible] - public StoneAnkhDeed() - { - LootType = LootType.Blessed; - } + return addon; + } + } - public StoneAnkhDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } - private void SendTarget( Mobile m ) - { - base.OnDoubleClick( m ); - } + private void SendTarget(Mobile m) + { + base.OnDoubleClick(m); + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( m_IsRewardItem ) - list.Add( 1076221 ); // 5th Year Veteran Reward - } + if (m_IsRewardItem) + list.Add(1076221); // 5th Year Veteran Reward + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(m_IsRewardItem); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - } + m_IsRewardItem = reader.ReadBool(); + } - private class InternalGump : Gump - { - private StoneAnkhDeed m_Deed; + private class InternalGump : Gump + { + private StoneAnkhDeed m_Deed; - private enum Buttons - { - Cancel, - South, - East - } + public InternalGump(StoneAnkhDeed deed) : base(150, 50) + { + m_Deed = deed; - public InternalGump( StoneAnkhDeed deed ) : base( 150, 50 ) - { - m_Deed = deed; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + AddPage(0); - AddPage( 0 ); + AddBackground(0, 0, 300, 150, 0xA28); - AddBackground( 0, 0, 300, 150, 0xA28 ); + AddItem(90, 30, 0x4); + AddItem(112, 30, 0x5); + AddButton(50, 35, 0x867, 0x869, (int)Buttons.South, GumpButtonType.Reply, 0); // South - AddItem( 90, 30, 0x4 ); - AddItem( 112, 30, 0x5 ); - AddButton( 50, 35, 0x867, 0x869, (int) Buttons.South, GumpButtonType.Reply, 0 ); // South + AddItem(170, 30, 0x2); + AddItem(192, 30, 0x3); + AddButton(145, 35, 0x867, 0x869, (int)Buttons.East, GumpButtonType.Reply, 0); // East + } - AddItem( 170, 30, 0x2 ); - AddItem( 192, 30, 0x3 ); - AddButton( 145, 35, 0x867, 0x869, (int) Buttons.East, GumpButtonType.Reply, 0 ); // East - } + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed == null || m_Deed.Deleted) + return; - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed == null || m_Deed.Deleted ) - return; + if (info.ButtonID != (int)Buttons.Cancel) + { + m_Deed.m_East = info.ButtonID == (int)Buttons.East; + m_Deed.SendTarget(sender.Mobile); + } + } - if ( info.ButtonID != (int) Buttons.Cancel ) - { - m_Deed.m_East = ( info.ButtonID == (int) Buttons.East ); - m_Deed.SendTarget( sender.Mobile ); - } - } - } - } -} + private enum Buttons + { + Cancel, + South, + East + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/TreeStump.cs b/Scripts/Items/Special/Veteran Rewards/TreeStump.cs index 62ea5cff2..cc72e9796 100644 --- a/Scripts/Items/Special/Veteran Rewards/TreeStump.cs +++ b/Scripts/Items/Special/Veteran Rewards/TreeStump.cs @@ -6,262 +6,307 @@ using Server.Network; namespace Server.Items { - public class TreeStump : BaseAddon, IRewardItem - { - public override BaseAddonDeed Deed - { - get - { - TreeStumpDeed deed = new TreeStumpDeed(); - deed.IsRewardItem = m_IsRewardItem; - deed.Logs = m_Logs; + public class TreeStump : BaseAddon, IRewardItem + { + private bool m_IsRewardItem; - return deed; - } - } + private int m_Logs; - private bool m_IsRewardItem; + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + [Constructible] + public TreeStump(int itemID) + { + AddComponent(new AddonComponent(itemID), 0, 0, 0); - private int m_Logs; + m_Timer = Timer.DelayCall(TimeSpan.FromDays(1), TimeSpan.FromDays(1), GiveLogs); + } - [CommandProperty( AccessLevel.GameMaster )] - public int Logs - { - get => m_Logs; - set{ m_Logs = value; InvalidateProperties(); } - } + public TreeStump(Serial serial) : base(serial) + { + } - private Timer m_Timer; + public override BaseAddonDeed Deed + { + get + { + TreeStumpDeed deed = new TreeStumpDeed(); + deed.IsRewardItem = m_IsRewardItem; + deed.Logs = m_Logs; - [Constructible] - public TreeStump( int itemID ) - { - AddComponent( new AddonComponent( itemID ), 0, 0, 0 ); + return deed; + } + } - m_Timer = Timer.DelayCall( TimeSpan.FromDays( 1 ), TimeSpan.FromDays( 1 ), GiveLogs ); - } + [CommandProperty(AccessLevel.GameMaster)] + public int Logs + { + get => m_Logs; + set + { + m_Logs = value; + InvalidateProperties(); + } + } - public TreeStump( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - private void GiveLogs() - { - m_Logs = Math.Min( 100, m_Logs + 10 ); - } + private void GiveLogs() + { + m_Logs = Math.Min(100, m_Logs + 10); + } - public override void OnComponentUsed( AddonComponent c, Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + public override void OnComponentUsed(AddonComponent c, Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - /* - * Unique problems have unique solutions. OSI does not have a problem with 1000s of mining carts - * due to the fact that they have only a miniscule fraction of the number of 10 year vets that a - * typical RunUO shard will have (RunUO's scaled down account aging system makes this a unique problem), - * and the "freeness" of free accounts. We also dont have mitigating factors like inactive (unpaid) - * accounts not gaining veteran time. - * - * The lack of high end vets and vet rewards on OSI has made testing the *exact* ranging/stacking - * behavior of these things all but impossible, so either way its just an estimation. - * - * If youd like your shard's carts/stumps to work the way they did before, simply replace the check - * below with this line of code: - * - * if (!from.InRange(GetWorldLocation(), 2) - * - * However, I am sure these checks are more accurate to OSI than the former version was. - * - */ + /* + * Unique problems have unique solutions. OSI does not have a problem with 1000s of mining carts + * due to the fact that they have only a miniscule fraction of the number of 10 year vets that a + * typical RunUO shard will have (RunUO's scaled down account aging system makes this a unique problem), + * and the "freeness" of free accounts. We also dont have mitigating factors like inactive (unpaid) + * accounts not gaining veteran time. + * + * The lack of high end vets and vet rewards on OSI has made testing the *exact* ranging/stacking + * behavior of these things all but impossible, so either way its just an estimation. + * + * If youd like your shard's carts/stumps to work the way they did before, simply replace the check + * below with this line of code: + * + * if (!from.InRange(GetWorldLocation(), 2) + * + * However, I am sure these checks are more accurate to OSI than the former version was. + * + */ - if (!from.InRange(GetWorldLocation(), 2) || !from.InLOS(this) || !((from.Z - Z) > -3 && (from.Z - Z) < 3)) - { - from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. - } - else if ( house != null && house.HasSecureAccess( from, SecureLevel.Friends ) ) - { - if ( m_Logs > 0 ) - { - Item logs = null; + if (!from.InRange(GetWorldLocation(), 2) || !from.InLOS(this) || !(from.Z - Z > -3 && from.Z - Z < 3)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + else if (house != null && house.HasSecureAccess(from, SecureLevel.Friends)) + { + if (m_Logs > 0) + { + Item logs = null; - switch ( Utility.Random( 7 ) ) - { - case 0: logs = new Log(); break; - case 1: logs = new AshLog(); break; - case 2: logs = new OakLog(); break; - case 3: logs = new YewLog(); break; - case 4: logs = new HeartwoodLog(); break; - case 5: logs = new BloodwoodLog(); break; - case 6: logs = new FrostwoodLog(); break; - } + switch (Utility.Random(7)) + { + case 0: + logs = new Log(); + break; + case 1: + logs = new AshLog(); + break; + case 2: + logs = new OakLog(); + break; + case 3: + logs = new YewLog(); + break; + case 4: + logs = new HeartwoodLog(); + break; + case 5: + logs = new BloodwoodLog(); + break; + case 6: + logs = new FrostwoodLog(); + break; + } - int amount = Math.Min( 10, m_Logs ); - logs.Amount = amount; + int amount = Math.Min(10, m_Logs); + logs.Amount = amount; - if ( !from.PlaceInBackpack( logs ) ) - { - logs.Delete(); - from.SendLocalizedMessage( 1078837 ); // Your backpack is full! Please make room and try again. - } - else - { - m_Logs -= amount; - PublicOverheadMessage( MessageType.Regular, 0, 1094719, m_Logs.ToString() ); // Logs: ~1_COUNT~ - } - } - else - from.SendLocalizedMessage( 1094720 ); // There are no more logs available. - } - else - from.SendLocalizedMessage( 1061637 ); // You are not allowed to access this. - } + if (!from.PlaceInBackpack(logs)) + { + logs.Delete(); + from.SendLocalizedMessage(1078837); // Your backpack is full! Please make room and try again. + } + else + { + m_Logs -= amount; + PublicOverheadMessage(MessageType.Regular, 0, 1094719, m_Logs.ToString()); // Logs: ~1_COUNT~ + } + } + else + { + from.SendLocalizedMessage(1094720); // There are no more logs available. + } + } + else + { + from.SendLocalizedMessage(1061637); // You are not allowed to access this. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (bool) m_IsRewardItem ); - writer.Write( (int) m_Logs ); + writer.Write(m_IsRewardItem); + writer.Write(m_Logs); - if ( m_Timer != null ) - writer.Write( (DateTime) m_Timer.Next ); - else - writer.Write( (DateTime) DateTime.UtcNow + TimeSpan.FromDays( 1 ) ); - } + if (m_Timer != null) + writer.Write(m_Timer.Next); + else + writer.Write(DateTime.UtcNow + TimeSpan.FromDays(1)); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_IsRewardItem = reader.ReadBool(); - m_Logs = reader.ReadInt(); + m_IsRewardItem = reader.ReadBool(); + m_Logs = reader.ReadInt(); - DateTime next = reader.ReadDateTime(); + DateTime next = reader.ReadDateTime(); - if ( next < DateTime.UtcNow ) - next = DateTime.UtcNow; + if (next < DateTime.UtcNow) + next = DateTime.UtcNow; - m_Timer = Timer.DelayCall( next - DateTime.UtcNow, TimeSpan.FromDays( 1 ), GiveLogs ); - } - } + m_Timer = Timer.DelayCall(next - DateTime.UtcNow, TimeSpan.FromDays(1), GiveLogs); + } + } - public class TreeStumpDeed : BaseAddonDeed, IRewardItem, IRewardOption - { - public override int LabelNumber => 1080406; // a deed for a tree stump decoration + public class TreeStumpDeed : BaseAddonDeed, IRewardItem, IRewardOption + { + private bool m_IsRewardItem; - public override BaseAddon Addon - { - get - { - TreeStump addon = new TreeStump( m_ItemID ); - addon.IsRewardItem = m_IsRewardItem; - addon.Logs = m_Logs; + private int m_ItemID; - return addon; - } - } + private int m_Logs; - private int m_ItemID; - private bool m_IsRewardItem; + [Constructible] + public TreeStumpDeed() + { + LootType = LootType.Blessed; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + public TreeStumpDeed(Serial serial) : base(serial) + { + } - private int m_Logs; + public override int LabelNumber => 1080406; // a deed for a tree stump decoration - [CommandProperty( AccessLevel.GameMaster )] - public int Logs - { - get => m_Logs; - set{ m_Logs = value; InvalidateProperties(); } - } + public override BaseAddon Addon + { + get + { + TreeStump addon = new TreeStump(m_ItemID); + addon.IsRewardItem = m_IsRewardItem; + addon.Logs = m_Logs; - [Constructible] - public TreeStumpDeed() - { - LootType = LootType.Blessed; - } + return addon; + } + } - public TreeStumpDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Logs + { + get => m_Logs; + set + { + m_Logs = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - if ( m_IsRewardItem ) - list.Add( 1076223 ); // 7th Year Veteran Reward - } + public void GetOptions(RewardOptionList list) + { + list.Add(1, 1080403); // Tree Stump with Axe West + list.Add(2, 1080404); // Tree Stump with Axe North + list.Add(3, 1080401); // Tree Stump East + list.Add(4, 1080402); // Tree Stump South + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public void OnOptionSelected(Mobile from, int option) + { + switch (option) + { + case 1: + m_ItemID = 0xE56; + break; + case 2: + m_ItemID = 0xE58; + break; + case 3: + m_ItemID = 0xE57; + break; + case 4: + m_ItemID = 0xE59; + break; + } - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( RewardOptionGump ) ); - from.SendGump( new RewardOptionGump( this ) ); - } - else - from.SendLocalizedMessage( 1062334 ); // This item must be in your backpack to be used. - } + if (!Deleted) + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - writer.WriteEncodedInt( 0 ); // version + if (m_IsRewardItem) + list.Add(1076223); // 7th Year Veteran Reward + } - writer.Write( (bool) m_IsRewardItem ); - writer.Write( (int) m_Logs ); - } + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(RewardOptionGump)); + from.SendGump(new RewardOptionGump(this)); + } + else + { + from.SendLocalizedMessage(1062334); // This item must be in your backpack to be used. + } + } - int version = reader.ReadEncodedInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - m_IsRewardItem = reader.ReadBool(); - m_Logs = reader.ReadInt(); - } + writer.WriteEncodedInt(0); // version - public void GetOptions( RewardOptionList list ) - { - list.Add( 1, 1080403 ); // Tree Stump with Axe West - list.Add( 2, 1080404 ); // Tree Stump with Axe North - list.Add( 3, 1080401 ); // Tree Stump East - list.Add( 4, 1080402 ); // Tree Stump South - } + writer.Write(m_IsRewardItem); + writer.Write(m_Logs); + } - public void OnOptionSelected( Mobile from, int option ) - { - switch ( option ) - { - case 1: m_ItemID = 0xE56; break; - case 2: m_ItemID = 0xE58; break; - case 3: m_ItemID = 0xE57; break; - case 4: m_ItemID = 0xE59; break; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( !Deleted ) - base.OnDoubleClick( from ); - } - } -} + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + m_Logs = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/WallBanner.cs b/Scripts/Items/Special/Veteran Rewards/WallBanner.cs index aacc78c42..b1a01a789 100644 --- a/Scripts/Items/Special/Veteran Rewards/WallBanner.cs +++ b/Scripts/Items/Special/Veteran Rewards/WallBanner.cs @@ -1,496 +1,510 @@ +using Server.Engines.VeteranRewards; using Server.Gumps; using Server.Network; -using Server.Engines.VeteranRewards; namespace Server.Items { - public class WallBannerComponent : AddonComponent, IDyable - { - public override bool NeedsWall => true; - public override Point3D WallPosition => East ? new Point3D( -1, 0, 0 ) : new Point3D( 0, -1, 0 ); - - public bool East => ((WallBanner)Addon).East; - - public WallBannerComponent( int itemID ) : base( itemID ) - { - } - - public WallBannerComponent( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - - public bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; - - if ( Addon != null ) - Addon.Hue = sender.DyedHue; - - return true; - } - } - - public class WallBanner : BaseAddon, IRewardItem - { - public override BaseAddonDeed Deed - { - get - { - WallBannerDeed deed = new WallBannerDeed(); - deed.IsRewardItem = m_IsRewardItem; - - return deed; - } - } - - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - private bool m_East; - - [CommandProperty( AccessLevel.GameMaster )] - public bool East - { - get => m_East; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - [Constructible] - public WallBanner( int bannerID ) - { - m_East = ((bannerID % 2) == 1 ); - - switch ( bannerID ) - { - case 1: - AddComponent( new WallBannerComponent( 0x161F ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x161E ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x161D ), 0, 2, 0 ); - break; - case 2: - AddComponent( new WallBannerComponent( 0x1586 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1587 ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1588 ), 2, 0, 0 ); - break; - case 3: - AddComponent( new WallBannerComponent( 0x1622 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1621 ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x1620 ), 0, 2, 0 ); - break; - case 4: - AddComponent( new WallBannerComponent( 0x1589 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x158A ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x158B ), 2, 0, 0 ); - break; - case 5: - AddComponent( new WallBannerComponent( 0x1625 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1624 ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x1623 ), 0, 2, 0 ); - break; - case 6: - AddComponent( new WallBannerComponent( 0x158C ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x158D ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x158E ), 2, 0, 0 ); - break; - case 7: - AddComponent( new WallBannerComponent( 0x1628 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1627 ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x1626 ), 0, 2, 0 ); - break; - case 8: - AddComponent( new WallBannerComponent( 0x1590 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1591 ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x158F ), 2, 0, 0 ); - break; - case 9: - AddComponent( new WallBannerComponent( 0x162A ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1629 ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x1626 ), 0, 2, 0 ); - break; - case 10: - AddComponent( new WallBannerComponent( 0x1592 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1593 ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x158F ), 2, 0, 0 ); - break; - case 11: - AddComponent( new WallBannerComponent( 0x162D ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x162C ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x162B ), 0, 2, 0 ); - break; - case 12: - AddComponent( new WallBannerComponent( 0x1594 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1595 ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1596 ), 2, 0, 0 ); - break; - case 13: - AddComponent( new WallBannerComponent( 0x1632 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1631 ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x162E ), 0, 2, 0 ); - break; - case 14: - AddComponent( new WallBannerComponent( 0x1598 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x159B ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x159C ), 2, 0, 0 ); - break; - case 15: - AddComponent( new WallBannerComponent( 0x1633 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1630 ), 0, 1, 0 ); - AddComponent( new WallBannerComponent( 0x162F ), 0, 2, 0 ); - break; - case 16: - AddComponent( new WallBannerComponent( 0x1599 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x159A ), 1, 0, 0 ); - AddComponent( new WallBannerComponent( 0x159D ), 2, 0, 0 ); - break; - - - case 17: - AddComponent( new WallBannerComponent( 0x1610 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x160F ), 0, 1, 0 ); - break; - case 18: - AddComponent( new WallBannerComponent( 0x15A0 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15A1 ), 1, 0, 0 ); - break; - - case 19: - AddComponent( new WallBannerComponent( 0x1612 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1611 ), 0, 1, 0 ); - break; - case 20: - AddComponent( new WallBannerComponent( 0x15A2 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15A3 ), 1, 0, 0 ); - break; - - case 21: - AddComponent( new WallBannerComponent( 0x1614 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1613 ), 0, 1, 0 ); - break; - case 22: - AddComponent( new WallBannerComponent( 0x15A4 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15A5 ), 1, 0, 0 ); - break; - - case 23: - AddComponent( new WallBannerComponent( 0x1616 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1615 ), 0, 1, 0 ); - break; - case 24: - AddComponent( new WallBannerComponent( 0x15A6 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15A7 ), 1, 0, 0 ); - break; - - case 25: - AddComponent( new WallBannerComponent( 0x1618 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1617 ), 0, 1, 0 ); - break; - case 26: - AddComponent( new WallBannerComponent( 0x15A8 ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15A9 ), 1, 0, 0 ); - break; - - case 27: - AddComponent( new WallBannerComponent( 0x161A ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x1619 ), 0, 1, 0 ); - break; - case 28: - AddComponent( new WallBannerComponent( 0x15AA ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15AB ), 1, 0, 0 ); - break; - - case 29: - AddComponent( new WallBannerComponent( 0x161C ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x161B ), 0, 1, 0 ); - break; - case 30: - AddComponent( new WallBannerComponent( 0x15AC ), 0, 0, 0 ); - AddComponent( new WallBannerComponent( 0x15AD ), 1, 0, 0 ); - break; - } - } - - public WallBanner( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_East ); - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_East = reader.ReadBool(); - m_IsRewardItem = reader.ReadBool(); - } - } - - public class WallBannerDeed : BaseAddonDeed, IRewardItem - { - public override int LabelNumber => 1080549; // Wall Banner Deed - - public override BaseAddon Addon - { - get - { - WallBanner addon = new WallBanner( m_BannerID ); - addon.IsRewardItem = m_IsRewardItem; - - return addon; - } - } - - private int m_BannerID; - private bool m_IsRewardItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } - - [Constructible] - public WallBannerDeed() - { - LootType = LootType.Blessed; - } - - public WallBannerDeed( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsRewardItem ) - list.Add( 1076225 ); // 9th Year Veteran Reward - } - - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; - - if ( IsChildOf( from.Backpack ) ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( this ) ); - } - else - from.SendLocalizedMessage( 1042038 ); // You must have the object in your backpack to use it. - } - - public void Use( Mobile m, int bannerID ) - { - m_BannerID = bannerID; - - base.OnDoubleClick( m ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( (bool) m_IsRewardItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - m_IsRewardItem = reader.ReadBool(); - } - - private class InternalGump : Gump - { - private WallBannerDeed m_WallBanner; - - public InternalGump( WallBannerDeed WallBanner ) : base( 150, 50 ) - { - m_WallBanner = WallBanner; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - AddBackground( 25, 0, 500, 265, 0xA28 ); - AddLabel( 70, 12, 0x3E3, "Choose a Wall Banner:" ); - - AddPage( 1 ); - - AddItem( 55, 110, 0x161D ); - AddItem( 75, 90, 0x161E ); - AddItem( 95, 70, 0x161F ); - AddButton( 70, 50, 0x845, 0x846, 1, GumpButtonType.Reply, 0 ); - AddItem( 105, 70, 0x1586 ); - AddItem( 125, 90, 0x1587 ); - AddItem( 145, 110, 0x1588 ); - AddButton( 145, 50, 0x845, 0x846, 2, GumpButtonType.Reply, 0 ); - AddItem( 200, 110, 0x1620 ); - AddItem( 220, 90, 0x1621 ); - AddItem( 240, 70, 0x1622 ); - AddButton( 220, 50, 0x845, 0x846, 3, GumpButtonType.Reply, 0 ); - AddItem( 250, 70, 0x1589 ); - AddItem( 270, 90, 0x158A ); - AddItem( 290, 110, 0x158B ); - AddButton( 300, 50, 0x845, 0x846, 4, GumpButtonType.Reply, 0 ); - AddItem( 350, 110, 0x1623 ); - AddItem( 370, 90, 0x1624 ); - AddItem( 390, 70, 0x1625 ); - AddButton( 365, 50, 0x845, 0x846, 5, GumpButtonType.Reply, 0 ); - AddItem( 400, 70, 0x158C ); - AddItem( 420, 90, 0x158D ); - AddItem( 440, 110, 0x158E ); - AddButton( 445, 50, 0x845, 0x846, 6, GumpButtonType.Reply, 0 ); - AddButton( 455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 2 ); - - AddPage( 2 ); - - AddItem( 52, 110, 0x1626 ); - AddItem( 72, 90, 0x1627 ); - AddItem( 95, 70, 0x1628 ); - AddButton( 70, 50, 0x845, 0x846, 7, GumpButtonType.Reply, 0 ); - AddItem( 105, 70, 0x1590 ); - AddItem( 125, 90, 0x1591 ); - AddItem( 145, 110, 0x158F ); - AddButton( 145, 50, 0x845, 0x846, 8, GumpButtonType.Reply, 0 ); - AddItem( 197, 110, 0x1626 ); - AddItem( 217, 90, 0x1629 ); - AddItem( 240, 70, 0x162A ); - AddButton( 220, 50, 0x845, 0x846, 9, GumpButtonType.Reply, 0 ); - AddItem( 250, 70, 0x1592 ); - AddItem( 270, 90, 0x1593 ); - AddItem( 290, 110, 0x158F ); - AddButton( 300, 50, 0x845, 0x846, 10, GumpButtonType.Reply, 0 ); - AddItem( 340, 110, 0x162B ); - AddItem( 363, 90, 0x162C ); - AddItem( 385, 70, 0x162D ); - AddButton( 365, 50, 0x845, 0x846, 11, GumpButtonType.Reply, 0 ); - AddItem( 395, 70, 0x1594 ); - AddItem( 417, 90, 0x1595 ); - AddItem( 439, 111, 0x1596 ); - AddButton( 445, 50, 0x845, 0x846, 12, GumpButtonType.Reply, 0 ); - AddButton( 70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 1 ); - AddButton( 455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 3 ); - - AddPage( 3 ); - - AddItem( 55, 110, 0x162E ); - AddItem( 75, 93, 0x1631 ); - AddItem( 95, 70, 0x1632 ); - AddButton( 70, 50, 0x845, 0x846, 13, GumpButtonType.Reply, 0 ); - AddItem( 118, 70, 0x1598 ); - AddItem( 138, 94, 0x159B ); - AddItem( 159, 113, 0x159C ); - AddButton( 160, 50, 0x845, 0x846, 14, GumpButtonType.Reply, 0 ); - AddItem( 219, 111, 0x162F ); - AddItem( 238, 94, 0x1630 ); - AddItem( 258, 70, 0x1633 ); - AddButton( 240, 50, 0x845, 0x846, 15, GumpButtonType.Reply, 0 ); - AddItem( 279, 70, 0x1599 ); - AddItem( 298, 93, 0x159A ); - AddItem( 319, 113, 0x159D ); - AddButton( 320, 50, 0x845, 0x846, 16, GumpButtonType.Reply, 0 ); - AddItem( 380, 90, 0x160F ); - AddItem( 400, 70, 0x1610 ); - AddButton( 390, 50, 0x845, 0x846, 17, GumpButtonType.Reply, 0 ); - AddItem( 420, 70, 0x15A0 ); - AddItem( 440, 90, 0x15A1 ); - AddButton( 455, 50, 0x845, 0x846, 18, GumpButtonType.Reply, 0 ); - AddButton( 70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 2 ); - AddButton( 455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 4 ); - - AddPage( 4 ); - - AddItem( 55, 90, 0x1611 ); - AddItem( 75, 70, 0x1612 ); - AddButton( 70, 50, 0x845, 0x846, 19, GumpButtonType.Reply, 0 ); - AddItem( 105, 70, 0x15A2 ); - AddItem( 125, 90, 0x15A3 ); - AddButton( 145, 50, 0x845, 0x846, 20, GumpButtonType.Reply, 0 ); - AddItem( 200, 84, 0x1613 ); - AddItem( 220, 70, 0x1614 ); - AddButton( 215, 50, 0x845, 0x846, 21, GumpButtonType.Reply, 0 ); - AddItem( 250, 70, 0x15A4 ); - AddItem( 270, 84, 0x15A5 ); - AddButton( 290, 50, 0x845, 0x846, 22, GumpButtonType.Reply, 0 ); - AddItem( 350, 90, 0x1615 ); - AddItem( 370, 70, 0x1616 ); - AddButton( 365, 50, 0x845, 0x846, 23, GumpButtonType.Reply, 0 ); - AddItem( 400, 70, 0x15A6 ); - AddItem( 420, 90, 0x15A7 ); - AddButton( 445, 50, 0x845, 0x846, 24, GumpButtonType.Reply, 0 ); - AddButton( 70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 3 ); - AddButton( 455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 5 ); - - AddPage( 5 ); - - AddItem( 55, 90, 0x1617 ); - AddItem( 77, 70, 0x1618 ); - AddButton( 70, 50, 0x845, 0x846, 25, GumpButtonType.Reply, 0 ); - AddItem( 105, 70, 0x15A8 ); - AddItem( 127, 90, 0x15A9 ); - AddButton( 145, 50, 0x845, 0x846, 26, GumpButtonType.Reply, 0 ); - AddItem( 200, 90, 0x1619 ); - AddItem( 222, 70, 0x161A ); - AddButton( 220, 50, 0x845, 0x846, 27, GumpButtonType.Reply, 0 ); - AddItem( 250, 70, 0x15AA ); - AddItem( 272, 90, 0x15AB ); - AddButton( 300, 50, 0x845, 0x846, 28, GumpButtonType.Reply, 0 ); - AddItem( 350, 90, 0x161B ); - AddItem( 372, 70, 0x161C ); - AddButton( 365, 50, 0x845, 0x846, 29, GumpButtonType.Reply, 0 ); - AddItem( 400, 70, 0x15AC ); - AddItem( 422, 90, 0x15AD ); - AddButton( 445, 50, 0x845, 0x846, 30, GumpButtonType.Reply, 0 ); - AddButton( 70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 4 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_WallBanner == null || m_WallBanner.Deleted ) - return; - - if ( info.ButtonID > 0 && info.ButtonID < 31 ) - m_WallBanner.Use( sender.Mobile, info.ButtonID ); - } - } - } -} + public class WallBannerComponent : AddonComponent, IDyable + { + public WallBannerComponent(int itemID) : base(itemID) + { + } + + public WallBannerComponent(Serial serial) : base(serial) + { + } + + public override bool NeedsWall => true; + public override Point3D WallPosition => East ? new Point3D(-1, 0, 0) : new Point3D(0, -1, 0); + + public bool East => ((WallBanner)Addon).East; + + public bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; + + if (Addon != null) + Addon.Hue = sender.DyedHue; + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class WallBanner : BaseAddon, IRewardItem + { + private bool m_East; + + private bool m_IsRewardItem; + + [Constructible] + public WallBanner(int bannerID) + { + m_East = bannerID % 2 == 1; + + switch (bannerID) + { + case 1: + AddComponent(new WallBannerComponent(0x161F), 0, 0, 0); + AddComponent(new WallBannerComponent(0x161E), 0, 1, 0); + AddComponent(new WallBannerComponent(0x161D), 0, 2, 0); + break; + case 2: + AddComponent(new WallBannerComponent(0x1586), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1587), 1, 0, 0); + AddComponent(new WallBannerComponent(0x1588), 2, 0, 0); + break; + case 3: + AddComponent(new WallBannerComponent(0x1622), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1621), 0, 1, 0); + AddComponent(new WallBannerComponent(0x1620), 0, 2, 0); + break; + case 4: + AddComponent(new WallBannerComponent(0x1589), 0, 0, 0); + AddComponent(new WallBannerComponent(0x158A), 1, 0, 0); + AddComponent(new WallBannerComponent(0x158B), 2, 0, 0); + break; + case 5: + AddComponent(new WallBannerComponent(0x1625), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1624), 0, 1, 0); + AddComponent(new WallBannerComponent(0x1623), 0, 2, 0); + break; + case 6: + AddComponent(new WallBannerComponent(0x158C), 0, 0, 0); + AddComponent(new WallBannerComponent(0x158D), 1, 0, 0); + AddComponent(new WallBannerComponent(0x158E), 2, 0, 0); + break; + case 7: + AddComponent(new WallBannerComponent(0x1628), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1627), 0, 1, 0); + AddComponent(new WallBannerComponent(0x1626), 0, 2, 0); + break; + case 8: + AddComponent(new WallBannerComponent(0x1590), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1591), 1, 0, 0); + AddComponent(new WallBannerComponent(0x158F), 2, 0, 0); + break; + case 9: + AddComponent(new WallBannerComponent(0x162A), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1629), 0, 1, 0); + AddComponent(new WallBannerComponent(0x1626), 0, 2, 0); + break; + case 10: + AddComponent(new WallBannerComponent(0x1592), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1593), 1, 0, 0); + AddComponent(new WallBannerComponent(0x158F), 2, 0, 0); + break; + case 11: + AddComponent(new WallBannerComponent(0x162D), 0, 0, 0); + AddComponent(new WallBannerComponent(0x162C), 0, 1, 0); + AddComponent(new WallBannerComponent(0x162B), 0, 2, 0); + break; + case 12: + AddComponent(new WallBannerComponent(0x1594), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1595), 1, 0, 0); + AddComponent(new WallBannerComponent(0x1596), 2, 0, 0); + break; + case 13: + AddComponent(new WallBannerComponent(0x1632), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1631), 0, 1, 0); + AddComponent(new WallBannerComponent(0x162E), 0, 2, 0); + break; + case 14: + AddComponent(new WallBannerComponent(0x1598), 0, 0, 0); + AddComponent(new WallBannerComponent(0x159B), 1, 0, 0); + AddComponent(new WallBannerComponent(0x159C), 2, 0, 0); + break; + case 15: + AddComponent(new WallBannerComponent(0x1633), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1630), 0, 1, 0); + AddComponent(new WallBannerComponent(0x162F), 0, 2, 0); + break; + case 16: + AddComponent(new WallBannerComponent(0x1599), 0, 0, 0); + AddComponent(new WallBannerComponent(0x159A), 1, 0, 0); + AddComponent(new WallBannerComponent(0x159D), 2, 0, 0); + break; + + + case 17: + AddComponent(new WallBannerComponent(0x1610), 0, 0, 0); + AddComponent(new WallBannerComponent(0x160F), 0, 1, 0); + break; + case 18: + AddComponent(new WallBannerComponent(0x15A0), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15A1), 1, 0, 0); + break; + + case 19: + AddComponent(new WallBannerComponent(0x1612), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1611), 0, 1, 0); + break; + case 20: + AddComponent(new WallBannerComponent(0x15A2), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15A3), 1, 0, 0); + break; + + case 21: + AddComponent(new WallBannerComponent(0x1614), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1613), 0, 1, 0); + break; + case 22: + AddComponent(new WallBannerComponent(0x15A4), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15A5), 1, 0, 0); + break; + + case 23: + AddComponent(new WallBannerComponent(0x1616), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1615), 0, 1, 0); + break; + case 24: + AddComponent(new WallBannerComponent(0x15A6), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15A7), 1, 0, 0); + break; + + case 25: + AddComponent(new WallBannerComponent(0x1618), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1617), 0, 1, 0); + break; + case 26: + AddComponent(new WallBannerComponent(0x15A8), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15A9), 1, 0, 0); + break; + + case 27: + AddComponent(new WallBannerComponent(0x161A), 0, 0, 0); + AddComponent(new WallBannerComponent(0x1619), 0, 1, 0); + break; + case 28: + AddComponent(new WallBannerComponent(0x15AA), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15AB), 1, 0, 0); + break; + + case 29: + AddComponent(new WallBannerComponent(0x161C), 0, 0, 0); + AddComponent(new WallBannerComponent(0x161B), 0, 1, 0); + break; + case 30: + AddComponent(new WallBannerComponent(0x15AC), 0, 0, 0); + AddComponent(new WallBannerComponent(0x15AD), 1, 0, 0); + break; + } + } + + public WallBanner(Serial serial) : base(serial) + { + } + + public override BaseAddonDeed Deed + { + get + { + WallBannerDeed deed = new WallBannerDeed(); + deed.IsRewardItem = m_IsRewardItem; + + return deed; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool East + { + get => m_East; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_East); + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_East = reader.ReadBool(); + m_IsRewardItem = reader.ReadBool(); + } + } + + public class WallBannerDeed : BaseAddonDeed, IRewardItem + { + private int m_BannerID; + private bool m_IsRewardItem; + + [Constructible] + public WallBannerDeed() + { + LootType = LootType.Blessed; + } + + public WallBannerDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1080549; // Wall Banner Deed + + public override BaseAddon Addon + { + get + { + WallBanner addon = new WallBanner(m_BannerID); + addon.IsRewardItem = m_IsRewardItem; + + return addon; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsRewardItem) + list.Add(1076225); // 9th Year Veteran Reward + } + + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; + + if (IsChildOf(from.Backpack)) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(this)); + } + else + { + from.SendLocalizedMessage(1042038); // You must have the object in your backpack to use it. + } + } + + public void Use(Mobile m, int bannerID) + { + m_BannerID = bannerID; + + base.OnDoubleClick(m); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(m_IsRewardItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + m_IsRewardItem = reader.ReadBool(); + } + + private class InternalGump : Gump + { + private WallBannerDeed m_WallBanner; + + public InternalGump(WallBannerDeed WallBanner) : base(150, 50) + { + m_WallBanner = WallBanner; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + AddBackground(25, 0, 500, 265, 0xA28); + AddLabel(70, 12, 0x3E3, "Choose a Wall Banner:"); + + AddPage(1); + + AddItem(55, 110, 0x161D); + AddItem(75, 90, 0x161E); + AddItem(95, 70, 0x161F); + AddButton(70, 50, 0x845, 0x846, 1, GumpButtonType.Reply, 0); + AddItem(105, 70, 0x1586); + AddItem(125, 90, 0x1587); + AddItem(145, 110, 0x1588); + AddButton(145, 50, 0x845, 0x846, 2, GumpButtonType.Reply, 0); + AddItem(200, 110, 0x1620); + AddItem(220, 90, 0x1621); + AddItem(240, 70, 0x1622); + AddButton(220, 50, 0x845, 0x846, 3, GumpButtonType.Reply, 0); + AddItem(250, 70, 0x1589); + AddItem(270, 90, 0x158A); + AddItem(290, 110, 0x158B); + AddButton(300, 50, 0x845, 0x846, 4, GumpButtonType.Reply, 0); + AddItem(350, 110, 0x1623); + AddItem(370, 90, 0x1624); + AddItem(390, 70, 0x1625); + AddButton(365, 50, 0x845, 0x846, 5, GumpButtonType.Reply, 0); + AddItem(400, 70, 0x158C); + AddItem(420, 90, 0x158D); + AddItem(440, 110, 0x158E); + AddButton(445, 50, 0x845, 0x846, 6, GumpButtonType.Reply, 0); + AddButton(455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 2); + + AddPage(2); + + AddItem(52, 110, 0x1626); + AddItem(72, 90, 0x1627); + AddItem(95, 70, 0x1628); + AddButton(70, 50, 0x845, 0x846, 7, GumpButtonType.Reply, 0); + AddItem(105, 70, 0x1590); + AddItem(125, 90, 0x1591); + AddItem(145, 110, 0x158F); + AddButton(145, 50, 0x845, 0x846, 8, GumpButtonType.Reply, 0); + AddItem(197, 110, 0x1626); + AddItem(217, 90, 0x1629); + AddItem(240, 70, 0x162A); + AddButton(220, 50, 0x845, 0x846, 9, GumpButtonType.Reply, 0); + AddItem(250, 70, 0x1592); + AddItem(270, 90, 0x1593); + AddItem(290, 110, 0x158F); + AddButton(300, 50, 0x845, 0x846, 10, GumpButtonType.Reply, 0); + AddItem(340, 110, 0x162B); + AddItem(363, 90, 0x162C); + AddItem(385, 70, 0x162D); + AddButton(365, 50, 0x845, 0x846, 11, GumpButtonType.Reply, 0); + AddItem(395, 70, 0x1594); + AddItem(417, 90, 0x1595); + AddItem(439, 111, 0x1596); + AddButton(445, 50, 0x845, 0x846, 12, GumpButtonType.Reply, 0); + AddButton(70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 1); + AddButton(455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 3); + + AddPage(3); + + AddItem(55, 110, 0x162E); + AddItem(75, 93, 0x1631); + AddItem(95, 70, 0x1632); + AddButton(70, 50, 0x845, 0x846, 13, GumpButtonType.Reply, 0); + AddItem(118, 70, 0x1598); + AddItem(138, 94, 0x159B); + AddItem(159, 113, 0x159C); + AddButton(160, 50, 0x845, 0x846, 14, GumpButtonType.Reply, 0); + AddItem(219, 111, 0x162F); + AddItem(238, 94, 0x1630); + AddItem(258, 70, 0x1633); + AddButton(240, 50, 0x845, 0x846, 15, GumpButtonType.Reply, 0); + AddItem(279, 70, 0x1599); + AddItem(298, 93, 0x159A); + AddItem(319, 113, 0x159D); + AddButton(320, 50, 0x845, 0x846, 16, GumpButtonType.Reply, 0); + AddItem(380, 90, 0x160F); + AddItem(400, 70, 0x1610); + AddButton(390, 50, 0x845, 0x846, 17, GumpButtonType.Reply, 0); + AddItem(420, 70, 0x15A0); + AddItem(440, 90, 0x15A1); + AddButton(455, 50, 0x845, 0x846, 18, GumpButtonType.Reply, 0); + AddButton(70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 2); + AddButton(455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 4); + + AddPage(4); + + AddItem(55, 90, 0x1611); + AddItem(75, 70, 0x1612); + AddButton(70, 50, 0x845, 0x846, 19, GumpButtonType.Reply, 0); + AddItem(105, 70, 0x15A2); + AddItem(125, 90, 0x15A3); + AddButton(145, 50, 0x845, 0x846, 20, GumpButtonType.Reply, 0); + AddItem(200, 84, 0x1613); + AddItem(220, 70, 0x1614); + AddButton(215, 50, 0x845, 0x846, 21, GumpButtonType.Reply, 0); + AddItem(250, 70, 0x15A4); + AddItem(270, 84, 0x15A5); + AddButton(290, 50, 0x845, 0x846, 22, GumpButtonType.Reply, 0); + AddItem(350, 90, 0x1615); + AddItem(370, 70, 0x1616); + AddButton(365, 50, 0x845, 0x846, 23, GumpButtonType.Reply, 0); + AddItem(400, 70, 0x15A6); + AddItem(420, 90, 0x15A7); + AddButton(445, 50, 0x845, 0x846, 24, GumpButtonType.Reply, 0); + AddButton(70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 3); + AddButton(455, 205, 0x8B0, 0x8B0, 0, GumpButtonType.Page, 5); + + AddPage(5); + + AddItem(55, 90, 0x1617); + AddItem(77, 70, 0x1618); + AddButton(70, 50, 0x845, 0x846, 25, GumpButtonType.Reply, 0); + AddItem(105, 70, 0x15A8); + AddItem(127, 90, 0x15A9); + AddButton(145, 50, 0x845, 0x846, 26, GumpButtonType.Reply, 0); + AddItem(200, 90, 0x1619); + AddItem(222, 70, 0x161A); + AddButton(220, 50, 0x845, 0x846, 27, GumpButtonType.Reply, 0); + AddItem(250, 70, 0x15AA); + AddItem(272, 90, 0x15AB); + AddButton(300, 50, 0x845, 0x846, 28, GumpButtonType.Reply, 0); + AddItem(350, 90, 0x161B); + AddItem(372, 70, 0x161C); + AddButton(365, 50, 0x845, 0x846, 29, GumpButtonType.Reply, 0); + AddItem(400, 70, 0x15AC); + AddItem(422, 90, 0x15AD); + AddButton(445, 50, 0x845, 0x846, 30, GumpButtonType.Reply, 0); + AddButton(70, 205, 0x8AF, 0x8AF, 0, GumpButtonType.Page, 4); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_WallBanner == null || m_WallBanner.Deleted) + return; + + if (info.ButtonID > 0 && info.ButtonID < 31) + m_WallBanner.Use(sender.Mobile, info.ButtonID); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Special/Veteran Rewards/WeaponEngravingTool.cs b/Scripts/Items/Special/Veteran Rewards/WeaponEngravingTool.cs index ce9256246..4a600067d 100644 --- a/Scripts/Items/Special/Veteran Rewards/WeaponEngravingTool.cs +++ b/Scripts/Items/Special/Veteran Rewards/WeaponEngravingTool.cs @@ -1,324 +1,357 @@ -using System; -using Server.Mobiles; -using Server.Targeting; -using Server.Gumps; using Server.Engines.VeteranRewards; +using Server.Gumps; +using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Items { - public class WeaponEngravingTool : Item, IUsesRemaining, IRewardItem - { - public override int LabelNumber => 1076158; // Weapon Engraving Tool + public class WeaponEngravingTool : Item, IUsesRemaining, IRewardItem + { + private bool m_IsRewardItem; - private int m_UsesRemaining; - private bool m_IsRewardItem; + private int m_UsesRemaining; - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set{ m_UsesRemaining = value; InvalidateProperties(); } - } + [Constructible] + public WeaponEngravingTool() : this(10) + { + } - public virtual bool ShowUsesRemaining - { - get => true; - set{} - } + [Constructible] + public WeaponEngravingTool(int uses) : base(0x32F8) + { + LootType = LootType.Blessed; + Weight = 1.0; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem - { - get => m_IsRewardItem; - set{ m_IsRewardItem = value; InvalidateProperties(); } - } + m_UsesRemaining = uses; + } - [Constructible] - public WeaponEngravingTool() : this( 10 ) - { - } + public WeaponEngravingTool(Serial serial) : base(serial) + { + } - [Constructible] - public WeaponEngravingTool( int uses ) : base( 0x32F8 ) - { - LootType = LootType.Blessed; - Weight = 1.0; + public override int LabelNumber => 1076158; // Weapon Engraving Tool - m_UsesRemaining = uses; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem + { + get => m_IsRewardItem; + set + { + m_IsRewardItem = value; + InvalidateProperties(); + } + } - public WeaponEngravingTool( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - return; + public virtual bool ShowUsesRemaining + { + get => true; + set { } + } - if ( m_UsesRemaining > 0 ) - { - from.SendLocalizedMessage( 1072357 ); // Select an object to engrave. - from.Target = new TargetWeapon( this ); - } - else - { - if ( from.Skills.Tinkering.Value == 0 ) - { - from.SendLocalizedMessage( 1076179 ); // Since you have no tinkering skill, you will need to find an NPC tinkerer to repair this for you. - } - else if ( from.Skills.Tinkering.Value < 75.0 ) - { - from.SendLocalizedMessage( 1076178 ); // Your tinkering skill is too low to fix this yourself. An NPC tinkerer can help you repair this for a fee. - } - else - { - Item diamond = from.Backpack.FindItemByType( typeof( BlueDiamond ) ); + public override void OnDoubleClick(Mobile from) + { + if (m_IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) + return; - if ( diamond != null ) - from.SendGump( new ConfirmGump( this, null ) ); - else - from.SendLocalizedMessage( 1076166 ); // You do not have a blue diamond needed to recharge the engraving tool. - } + if (m_UsesRemaining > 0) + { + from.SendLocalizedMessage(1072357); // Select an object to engrave. + from.Target = new TargetWeapon(this); + } + else + { + if (from.Skills.Tinkering.Value == 0) + { + from.SendLocalizedMessage( + 1076179); // Since you have no tinkering skill, you will need to find an NPC tinkerer to repair this for you. + } + else if (from.Skills.Tinkering.Value < 75.0) + { + from.SendLocalizedMessage( + 1076178); // Your tinkering skill is too low to fix this yourself. An NPC tinkerer can help you repair this for a fee. + } + else + { + Item diamond = from.Backpack.FindItemByType(typeof(BlueDiamond)); - from.SendLocalizedMessage( 1076163 ); // There are no charges left on this engraving tool. - } - } + if (diamond != null) + from.SendGump(new ConfirmGump(this, null)); + else + from.SendLocalizedMessage( + 1076166); // You do not have a blue diamond needed to recharge the engraving tool. + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + from.SendLocalizedMessage(1076163); // There are no charges left on this engraving tool. + } + } - if ( m_IsRewardItem ) - list.Add( 1076224 ); // 8th Year Veteran Reward + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - if ( ShowUsesRemaining ) - list.Add( 1060584, m_UsesRemaining.ToString() ); // uses remaining: ~1_val~ - } + if (m_IsRewardItem) + list.Add(1076224); // 8th Year Veteran Reward - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (ShowUsesRemaining) + list.Add(1060584, m_UsesRemaining.ToString()); // uses remaining: ~1_val~ + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) m_UsesRemaining ); - writer.Write( (bool) m_IsRewardItem ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_UsesRemaining); + writer.Write(m_IsRewardItem); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_UsesRemaining = reader.ReadInt(); - m_IsRewardItem = reader.ReadBool(); - } + int version = reader.ReadInt(); - public virtual void Recharge( Mobile from, Mobile guildmaster ) - { - if ( from.Backpack != null ) - { - Item diamond = from.Backpack.FindItemByType( typeof( BlueDiamond ) ); + m_UsesRemaining = reader.ReadInt(); + m_IsRewardItem = reader.ReadBool(); + } - if ( guildmaster != null ) - { - if ( m_UsesRemaining <= 0 ) - { - if ( diamond != null && Banker.Withdraw( from, 100000 ) ) - { - diamond.Consume(); - UsesRemaining = 10; - guildmaster.Say( 1076165 ); // Your weapon engraver should be good as new! - } - else - guildmaster.Say( 1076167 ); // You need a 100,000 gold and a blue diamond to recharge the weapon engraver. - } - else - guildmaster.Say( 1076164 ); // I can only help with this if you are carrying an engraving tool that needs repair. - } - else - { - if ( from.Skills.Tinkering.Value == 0 ) - { - from.SendLocalizedMessage( 1076179 ); // Since you have no tinkering skill, you will need to find an NPC tinkerer to repair this for you. - } - else if ( from.Skills.Tinkering.Value < 75.0 ) - { - from.SendLocalizedMessage( 1076178 ); // Your tinkering skill is too low to fix this yourself. An NPC tinkerer can help you repair this for a fee. - } - else if ( diamond != null ) - { - diamond.Consume(); + public virtual void Recharge(Mobile from, Mobile guildmaster) + { + if (from.Backpack != null) + { + Item diamond = from.Backpack.FindItemByType(typeof(BlueDiamond)); - if ( Utility.RandomDouble() < from.Skills.Tinkering.Value / 100 ) - { - UsesRemaining = 10; - from.SendLocalizedMessage( 1076165 ); // Your weapon engraver should be good as new! ????? - } - else - from.SendLocalizedMessage( 1076175 ); // You cracked the diamond attempting to fix the weapon engraver. - } - else - from.SendLocalizedMessage( 1076166 ); // You do not have a blue diamond needed to recharge the engraving tool. - } - } - } + if (guildmaster != null) + { + if (m_UsesRemaining <= 0) + { + if (diamond != null && Banker.Withdraw(from, 100000)) + { + diamond.Consume(); + UsesRemaining = 10; + guildmaster.Say(1076165); // Your weapon engraver should be good as new! + } + else + { + guildmaster.Say( + 1076167); // You need a 100,000 gold and a blue diamond to recharge the weapon engraver. + } + } + else + { + guildmaster.Say( + 1076164); // I can only help with this if you are carrying an engraving tool that needs repair. + } + } + else + { + if (from.Skills.Tinkering.Value == 0) + { + from.SendLocalizedMessage( + 1076179); // Since you have no tinkering skill, you will need to find an NPC tinkerer to repair this for you. + } + else if (from.Skills.Tinkering.Value < 75.0) + { + from.SendLocalizedMessage( + 1076178); // Your tinkering skill is too low to fix this yourself. An NPC tinkerer can help you repair this for a fee. + } + else if (diamond != null) + { + diamond.Consume(); - public static WeaponEngravingTool Find( Mobile from ) - { - return from.Backpack?.FindItemByType( typeof( WeaponEngravingTool ) ) as WeaponEngravingTool; - } + if (Utility.RandomDouble() < from.Skills.Tinkering.Value / 100) + { + UsesRemaining = 10; + from.SendLocalizedMessage(1076165); // Your weapon engraver should be good as new! ????? + } + else + { + from.SendLocalizedMessage( + 1076175); // You cracked the diamond attempting to fix the weapon engraver. + } + } + else + { + from.SendLocalizedMessage( + 1076166); // You do not have a blue diamond needed to recharge the engraving tool. + } + } + } + } - private class TargetWeapon : Target - { - private WeaponEngravingTool m_Tool; + public static WeaponEngravingTool Find(Mobile from) + { + return from.Backpack?.FindItemByType(typeof(WeaponEngravingTool)) as WeaponEngravingTool; + } - public TargetWeapon( WeaponEngravingTool tool ) : base( -1, true, TargetFlags.None ) - { - m_Tool = tool; - } + private class TargetWeapon : Target + { + private WeaponEngravingTool m_Tool; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Tool == null || m_Tool.Deleted ) - return; + public TargetWeapon(WeaponEngravingTool tool) : base(-1, true, TargetFlags.None) + { + m_Tool = tool; + } - if ( targeted is BaseWeapon item ) - { - from.CloseGump( typeof( InternalGump ) ); - from.SendGump( new InternalGump( m_Tool, item ) ); - } - else - from.SendLocalizedMessage( 1072309 ); // The selected item cannot be engraved by this engraving tool. - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Tool == null || m_Tool.Deleted) + return; - private class InternalGump : Gump - { - private WeaponEngravingTool m_Tool; - private BaseWeapon m_Target; + if (targeted is BaseWeapon item) + { + from.CloseGump(typeof(InternalGump)); + from.SendGump(new InternalGump(m_Tool, item)); + } + else + { + from.SendLocalizedMessage(1072309); // The selected item cannot be engraved by this engraving tool. + } + } + } - private enum Buttons - { - Cancel, - Okay, - Text - } + private class InternalGump : Gump + { + private BaseWeapon m_Target; + private WeaponEngravingTool m_Tool; - public InternalGump( WeaponEngravingTool tool, BaseWeapon target ) : base( 0, 0 ) - { - m_Tool = tool; - m_Target = target; + public InternalGump(WeaponEngravingTool tool, BaseWeapon target) : base(0, 0) + { + m_Tool = tool; + m_Target = target; - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; - AddBackground( 50, 50, 400, 300, 0xA28 ); + AddBackground(50, 50, 400, 300, 0xA28); - AddPage( 0 ); + AddPage(0); - AddHtmlLocalized( 50, 70, 400, 20, 1072359, 0x0, false, false ); //
Engraving Tool
- AddHtmlLocalized( 75, 95, 350, 145, 1076229, 0x0, true, true ); // Please enter the text to add to the selected object. Leave the text area blank to remove any existing text. Removing text does not use a charge. - AddButton( 125, 300, 0x81A, 0x81B, (int) Buttons.Okay, GumpButtonType.Reply, 0 ); - AddButton( 320, 300, 0x819, 0x818, (int) Buttons.Cancel, GumpButtonType.Reply, 0 ); - AddImageTiled( 75, 245, 350, 40, 0xDB0 ); - AddImageTiled( 76, 245, 350, 2, 0x23C5 ); - AddImageTiled( 75, 245, 2, 40, 0x23C3 ); - AddImageTiled( 75, 285, 350, 2, 0x23C5 ); - AddImageTiled( 425, 245, 2, 42, 0x23C3 ); + AddHtmlLocalized(50, 70, 400, 20, 1072359, 0x0, false, false); //
Engraving Tool
+ AddHtmlLocalized(75, 95, 350, 145, 1076229, 0x0, true, + true); // Please enter the text to add to the selected object. Leave the text area blank to remove any existing text. Removing text does not use a charge. + AddButton(125, 300, 0x81A, 0x81B, (int)Buttons.Okay, GumpButtonType.Reply, 0); + AddButton(320, 300, 0x819, 0x818, (int)Buttons.Cancel, GumpButtonType.Reply, 0); + AddImageTiled(75, 245, 350, 40, 0xDB0); + AddImageTiled(76, 245, 350, 2, 0x23C5); + AddImageTiled(75, 245, 2, 40, 0x23C3); + AddImageTiled(75, 285, 350, 2, 0x23C5); + AddImageTiled(425, 245, 2, 42, 0x23C3); - AddTextEntry( 75, 245, 350, 40, 0x0, (int) Buttons.Text, "" ); - } + AddTextEntry(75, 245, 350, 40, 0x0, (int)Buttons.Text, ""); + } - public override void OnResponse( Network.NetState state, RelayInfo info ) - { - if ( m_Tool == null || m_Tool.Deleted || m_Target == null || m_Target.Deleted ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Tool == null || m_Tool.Deleted || m_Target == null || m_Target.Deleted) + return; - if ( info.ButtonID == (int) Buttons.Okay ) - { - TextRelay relay = info.GetTextEntry( (int) Buttons.Text ); + if (info.ButtonID == (int)Buttons.Okay) + { + TextRelay relay = info.GetTextEntry((int)Buttons.Text); - if ( relay != null ) - { - if ( string.IsNullOrEmpty( relay.Text ) ) - { - m_Target.EngravedText = null; - state.Mobile.SendLocalizedMessage( 1072362 ); // You remove the engraving from the object. - } - else - { - if ( relay.Text.Length > 64 ) - m_Target.EngravedText = Utility.FixHtml( relay.Text.Substring( 0, 64 ) ); - else - m_Target.EngravedText = Utility.FixHtml( relay.Text ); + if (relay != null) + { + if (string.IsNullOrEmpty(relay.Text)) + { + m_Target.EngravedText = null; + state.Mobile.SendLocalizedMessage(1072362); // You remove the engraving from the object. + } + else + { + if (relay.Text.Length > 64) + m_Target.EngravedText = Utility.FixHtml(relay.Text.Substring(0, 64)); + else + m_Target.EngravedText = Utility.FixHtml(relay.Text); - state.Mobile.SendLocalizedMessage( 1072361 ); // You engraved the object. - m_Target.InvalidateProperties(); - m_Tool.UsesRemaining -= 1; - m_Tool.InvalidateProperties(); - } - } - } - else - state.Mobile.SendLocalizedMessage( 1072363 ); // The object was not engraved. - } - } + state.Mobile.SendLocalizedMessage(1072361); // You engraved the object. + m_Target.InvalidateProperties(); + m_Tool.UsesRemaining -= 1; + m_Tool.InvalidateProperties(); + } + } + } + else + { + state.Mobile.SendLocalizedMessage(1072363); // The object was not engraved. + } + } - public class ConfirmGump : Gump - { - private WeaponEngravingTool m_Engraver; - private Mobile m_Guildmaster; + private enum Buttons + { + Cancel, + Okay, + Text + } + } - private enum Buttons - { - Cancel, - Confirm - } + public class ConfirmGump : Gump + { + private WeaponEngravingTool m_Engraver; + private Mobile m_Guildmaster; - public ConfirmGump( WeaponEngravingTool engraver, Mobile guildmaster ) : base( 200, 200 ) - { - m_Engraver = engraver; - m_Guildmaster = guildmaster; + public ConfirmGump(WeaponEngravingTool engraver, Mobile guildmaster) : base(200, 200) + { + m_Engraver = engraver; + m_Guildmaster = guildmaster; - Closable = false; - Disposable = true; - Dragable = true; - Resizable = false; + Closable = false; + Disposable = true; + Dragable = true; + Resizable = false; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 291, 133, 0x13BE ); - AddImageTiled( 5, 5, 280, 100, 0xA40 ); + AddBackground(0, 0, 291, 133, 0x13BE); + AddImageTiled(5, 5, 280, 100, 0xA40); - if ( guildmaster != null ) - { - AddHtmlLocalized( 9, 9, 272, 100, 1076169, 0x7FFF, false, false ); // It will cost you 100,000 gold and a blue diamond to recharge your weapon engraver with 10 charges. - AddHtmlLocalized( 195, 109, 120, 20, 1076172, 0x7FFF, false, false ); // Recharge it - } - else - { - AddHtmlLocalized( 9, 9, 272, 100, 1076176, 0x7FFF, false, false ); // You will need a blue diamond to repair the tip of the engraver. A successful repair will give the engraver 10 charges. - AddHtmlLocalized( 195, 109, 120, 20, 1076177, 0x7FFF, false, false ); // Replace the tip. - } + if (guildmaster != null) + { + AddHtmlLocalized(9, 9, 272, 100, 1076169, 0x7FFF, false, + false); // It will cost you 100,000 gold and a blue diamond to recharge your weapon engraver with 10 charges. + AddHtmlLocalized(195, 109, 120, 20, 1076172, 0x7FFF, false, false); // Recharge it + } + else + { + AddHtmlLocalized(9, 9, 272, 100, 1076176, 0x7FFF, false, + false); // You will need a blue diamond to repair the tip of the engraver. A successful repair will give the engraver 10 charges. + AddHtmlLocalized(195, 109, 120, 20, 1076177, 0x7FFF, false, false); // Replace the tip. + } - AddButton( 160, 107, 0xFB7, 0xFB8, (int) Buttons.Confirm, GumpButtonType.Reply, 0 ); - AddButton( 5, 107, 0xFB1, 0xFB2, (int) Buttons.Cancel, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 109, 100, 20, 1060051, 0x7FFF, false, false ); // CANCEL - } + AddButton(160, 107, 0xFB7, 0xFB8, (int)Buttons.Confirm, GumpButtonType.Reply, 0); + AddButton(5, 107, 0xFB1, 0xFB2, (int)Buttons.Cancel, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 109, 100, 20, 1060051, 0x7FFF, false, false); // CANCEL + } - public override void OnResponse( Network.NetState state, RelayInfo info ) - { - if ( m_Engraver == null || m_Engraver.Deleted ) - return; + public override void OnResponse(NetState state, RelayInfo info) + { + if (m_Engraver == null || m_Engraver.Deleted) + return; - if ( info.ButtonID == (int) Buttons.Confirm ) - m_Engraver.Recharge( state.Mobile, m_Guildmaster ); - } - } - } -} + if (info.ButtonID == (int)Buttons.Confirm) + m_Engraver.Recharge(state.Mobile, m_Guildmaster); + } + + private enum Buttons + { + Cancel, + Confirm + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Suits/AdminRobe.cs b/Scripts/Items/Suits/AdminRobe.cs index db544396a..22d83aa5d 100644 --- a/Scripts/Items/Suits/AdminRobe.cs +++ b/Scripts/Items/Suits/AdminRobe.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class AdminRobe : BaseSuit - { - [Constructible] - public AdminRobe() : base( AccessLevel.Administrator, 0x0, 0x204F ) // Blank hue - { - } + public class AdminRobe : BaseSuit + { + [Constructible] + public AdminRobe() : base(AccessLevel.Administrator, 0x0, 0x204F) // Blank hue + { + } - public AdminRobe( Serial serial ) : base( serial ) - { - } + public AdminRobe(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/BaseSuit.cs b/Scripts/Items/Suits/BaseSuit.cs index 1dd05fba3..63ecdf70b 100644 --- a/Scripts/Items/Suits/BaseSuit.cs +++ b/Scripts/Items/Suits/BaseSuit.cs @@ -1,86 +1,86 @@ namespace Server.Items { - public abstract class BaseSuit : Item - { - [CommandProperty( AccessLevel.Administrator )] - public AccessLevel AccessLevel { get; set; } + public abstract class BaseSuit : Item + { + public BaseSuit(AccessLevel level, int hue, int itemID) : base(itemID) + { + Hue = hue; + Weight = 1.0; + Movable = false; + LootType = LootType.Newbied; + Layer = Layer.OuterTorso; - public BaseSuit( AccessLevel level, int hue, int itemID ) : base( itemID ) - { - Hue = hue; - Weight = 1.0; - Movable = false; - LootType = LootType.Newbied; - Layer = Layer.OuterTorso; + AccessLevel = level; + } - AccessLevel = level; - } + public BaseSuit(Serial serial) : base(serial) + { + } - public BaseSuit( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.Administrator)] + public AccessLevel AccessLevel{ get; set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) AccessLevel ); - } + writer.Write((int)AccessLevel); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - AccessLevel = (AccessLevel)reader.ReadInt(); - break; - } - } - } + switch (version) + { + case 0: + { + AccessLevel = (AccessLevel)reader.ReadInt(); + break; + } + } + } - public bool Validate() - { - object root = RootParent; + public bool Validate() + { + object root = RootParent; - if ( root is Mobile mobile && mobile.AccessLevel < AccessLevel ) - { - Delete(); - return false; - } + if (root is Mobile mobile && mobile.AccessLevel < AccessLevel) + { + Delete(); + return false; + } - return true; - } + return true; + } - public override void OnSingleClick( Mobile from ) - { - if ( Validate() ) - base.OnSingleClick( from ); - } + public override void OnSingleClick(Mobile from) + { + if (Validate()) + base.OnSingleClick(from); + } - public override void OnDoubleClick( Mobile from ) - { - if ( Validate() ) - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (Validate()) + base.OnDoubleClick(from); + } - public override bool VerifyMove( Mobile from ) - { - return ( from.AccessLevel >= AccessLevel ); - } + public override bool VerifyMove(Mobile from) + { + return from.AccessLevel >= AccessLevel; + } - public override bool OnEquip( Mobile from ) - { - if ( from.AccessLevel < AccessLevel ) - from.SendMessage( "You may not wear this." ); + public override bool OnEquip(Mobile from) + { + if (from.AccessLevel < AccessLevel) + from.SendMessage("You may not wear this."); - return ( from.AccessLevel >= AccessLevel ); - } - } -} + return from.AccessLevel >= AccessLevel; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Suits/CounselorRobe.cs b/Scripts/Items/Suits/CounselorRobe.cs index 89e85ec05..999acd9c5 100644 --- a/Scripts/Items/Suits/CounselorRobe.cs +++ b/Scripts/Items/Suits/CounselorRobe.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class CounselorRobe : BaseSuit - { - [Constructible] - public CounselorRobe() : base( AccessLevel.Counselor, 0x3, 0x204F ) - { - } + public class CounselorRobe : BaseSuit + { + [Constructible] + public CounselorRobe() : base(AccessLevel.Counselor, 0x3, 0x204F) + { + } - public CounselorRobe( Serial serial ) : base( serial ) - { - } + public CounselorRobe(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/DeathShroud.cs b/Scripts/Items/Suits/DeathShroud.cs index e65817a38..9e032c515 100644 --- a/Scripts/Items/Suits/DeathShroud.cs +++ b/Scripts/Items/Suits/DeathShroud.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class DeathShroud : BaseSuit - { - [Constructible] - public DeathShroud() : base( AccessLevel.GameMaster, 0x0, 0x204E ) - { - } + public class DeathShroud : BaseSuit + { + [Constructible] + public DeathShroud() : base(AccessLevel.GameMaster, 0x0, 0x204E) + { + } - public DeathShroud( Serial serial ) : base( serial ) - { - } + public DeathShroud(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/DupreSuit.cs b/Scripts/Items/Suits/DupreSuit.cs index 70a1c41b0..be979fccf 100644 --- a/Scripts/Items/Suits/DupreSuit.cs +++ b/Scripts/Items/Suits/DupreSuit.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class DupreSuit : BaseSuit - { - [Constructible] - public DupreSuit() : base( AccessLevel.GameMaster, 0x0, 0x2050 ) - { - } + public class DupreSuit : BaseSuit + { + [Constructible] + public DupreSuit() : base(AccessLevel.GameMaster, 0x0, 0x2050) + { + } - public DupreSuit( Serial serial ) : base( serial ) - { - } + public DupreSuit(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/GMRobe.cs b/Scripts/Items/Suits/GMRobe.cs index 4823951e6..479de61ae 100644 --- a/Scripts/Items/Suits/GMRobe.cs +++ b/Scripts/Items/Suits/GMRobe.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class GMRobe : BaseSuit - { - [Constructible] - public GMRobe() : base( AccessLevel.GameMaster, 0x26, 0x204F ) - { - } + public class GMRobe : BaseSuit + { + [Constructible] + public GMRobe() : base(AccessLevel.GameMaster, 0x26, 0x204F) + { + } - public GMRobe( Serial serial ) : base( serial ) - { - } + public GMRobe(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/LordBlackthorneSuit.cs b/Scripts/Items/Suits/LordBlackthorneSuit.cs index 4d56ed498..1aa941bcd 100644 --- a/Scripts/Items/Suits/LordBlackthorneSuit.cs +++ b/Scripts/Items/Suits/LordBlackthorneSuit.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class LordBlackthorneSuit : BaseSuit - { - [Constructible] - public LordBlackthorneSuit() : base( AccessLevel.GameMaster, 0x0, 0x2043 ) - { - } + public class LordBlackthorneSuit : BaseSuit + { + [Constructible] + public LordBlackthorneSuit() : base(AccessLevel.GameMaster, 0x0, 0x2043) + { + } - public LordBlackthorneSuit( Serial serial ) : base( serial ) - { - } + public LordBlackthorneSuit(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/LordBritishSuit.cs b/Scripts/Items/Suits/LordBritishSuit.cs index f534ca3e3..2b4d93724 100644 --- a/Scripts/Items/Suits/LordBritishSuit.cs +++ b/Scripts/Items/Suits/LordBritishSuit.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class LordBritishSuit : BaseSuit - { - [Constructible] - public LordBritishSuit() : base( AccessLevel.GameMaster, 0x0, 0x2042 ) - { - } + public class LordBritishSuit : BaseSuit + { + [Constructible] + public LordBritishSuit() : base(AccessLevel.GameMaster, 0x0, 0x2042) + { + } - public LordBritishSuit( Serial serial ) : base( serial ) - { - } + public LordBritishSuit(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Suits/SeerRobe.cs b/Scripts/Items/Suits/SeerRobe.cs index 76f3c8dff..3068236dc 100644 --- a/Scripts/Items/Suits/SeerRobe.cs +++ b/Scripts/Items/Suits/SeerRobe.cs @@ -1,28 +1,28 @@ namespace Server.Items { - public class SeerRobe : BaseSuit - { - [Constructible] - public SeerRobe() : base( AccessLevel.Seer, 0x1D3, 0x204F ) - { - } + public class SeerRobe : BaseSuit + { + [Constructible] + public SeerRobe() : base(AccessLevel.Seer, 0x1D3, 0x204F) + { + } - public SeerRobe( Serial serial ) : base( serial ) - { - } + public SeerRobe(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Talismans/BaseTalisman.cs b/Scripts/Items/Talismans/BaseTalisman.cs index 9096aa6cd..579091b0f 100644 --- a/Scripts/Items/Talismans/BaseTalisman.cs +++ b/Scripts/Items/Talismans/BaseTalisman.cs @@ -10,1065 +10,1168 @@ using Server.Targeting; namespace Server.Items { - public enum TalismanRemoval - { - None = 0, - Ward = 390, - Damage = 404, - Curse = 407, - Wildfire = 2843 - } - - public class BaseTalisman : Item - { - public static void Initialize() - { - CommandSystem.Register("RandomTalisman", AccessLevel.GameMaster, RandomTalisman_OnCommand); - } - - [Usage("RandomTalisman ")] - [Description("Generates random talismans in your backpack.")] - public static void RandomTalisman_OnCommand(CommandEventArgs e) - { - Mobile m = e.Mobile; - int count = e.GetInt32(0); - - for (int i = 0; i < count; i++) - { - m.AddToBackpack(Loot.RandomTalisman()); - } - } - - public override int LabelNumber => 1071023; // Talisman - public virtual bool ForceShowName => false; // used to override default summoner/removal name - - private int m_MaxCharges; - private int m_Charges; - private int m_MaxChargeTime; - private int m_ChargeTime; - private bool m_Blessed; - - [CommandProperty(AccessLevel.GameMaster)] - public int MaxCharges - { - get => m_MaxCharges; - set { m_MaxCharges = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int Charges - { - get => m_Charges; - set - { - m_Charges = value; - - if (m_ChargeTime > 0) - StartTimer(); - - InvalidateProperties(); - } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int MaxChargeTime - { - get => m_MaxChargeTime; - set { m_MaxChargeTime = value; InvalidateProperties(); } - } - - public int ChargeTime - { - get => m_ChargeTime; - set { m_ChargeTime = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public bool Blessed - { - get => m_Blessed; - set { m_Blessed = value; InvalidateProperties(); } - } - - #region Slayer - private TalismanSlayerName m_Slayer; - - [CommandProperty(AccessLevel.GameMaster)] - public TalismanSlayerName Slayer - { - get => m_Slayer; - set { m_Slayer = value; InvalidateProperties(); } - } - #endregion - - #region Summoner/Removal - private TalismanAttribute m_Summoner; - private TalismanRemoval m_Removal; - private Mobile m_Creature; - - [CommandProperty(AccessLevel.GameMaster)] - public TalismanAttribute Summoner - { - get => m_Summoner; - set { m_Summoner = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public TalismanRemoval Removal - { - get => m_Removal; - set { m_Removal = value; InvalidateProperties(); } - } - #endregion - - #region Protection/Killer - private TalismanAttribute m_Protection; - private TalismanAttribute m_Killer; - - [CommandProperty(AccessLevel.GameMaster)] - public TalismanAttribute Protection - { - get => m_Protection; - set { m_Protection = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public TalismanAttribute Killer - { - get => m_Killer; - set { m_Killer = value; InvalidateProperties(); } - } - #endregion - - #region Craft bonuses - private SkillName m_Skill; - private int m_SuccessBonus; - private int m_ExceptionalBonus; - - [CommandProperty(AccessLevel.GameMaster)] - public SkillName Skill - { - get => m_Skill; - set { m_Skill = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int SuccessBonus - { - get => m_SuccessBonus; - set { m_SuccessBonus = value; InvalidateProperties(); } - } - - [CommandProperty(AccessLevel.GameMaster)] - public int ExceptionalBonus - { - get => m_ExceptionalBonus; - set { m_ExceptionalBonus = value; InvalidateProperties(); } - } - #endregion - - #region AOS bonuses - private AosAttributes m_AosAttributes; - private AosSkillBonuses m_AosSkillBonuses; - - [CommandProperty(AccessLevel.GameMaster)] - public AosAttributes Attributes - { - get => m_AosAttributes; - set { } - } - - [CommandProperty(AccessLevel.GameMaster)] - public AosSkillBonuses SkillBonuses - { - get => m_AosSkillBonuses; - set { } - } - #endregion - - public BaseTalisman() - : this(GetRandomItemID()) - { - } - - public BaseTalisman(int itemID) - : base(itemID) - { - Layer = Layer.Talisman; - Weight = 1.0; - - m_Protection = new TalismanAttribute(); - m_Killer = new TalismanAttribute(); - m_Summoner = new TalismanAttribute(); - m_AosAttributes = new AosAttributes(this); - m_AosSkillBonuses = new AosSkillBonuses(this); - } - - public BaseTalisman(Serial serial) - : base(serial) - { - } - - public override void OnAfterDuped(Item newItem) - { - if (!(newItem is BaseTalisman talisman)) - return; - - talisman.m_Summoner = new TalismanAttribute(m_Summoner); - talisman.m_Protection = new TalismanAttribute(m_Protection); - talisman.m_Killer = new TalismanAttribute(m_Killer); - talisman.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); - talisman.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); - } - - public override bool CanEquip( Mobile from ) - { - if ( BlessedFor != null && BlessedFor != from ) - { - from.SendLocalizedMessage( 1010437 ); // You are not the owner. - return false; - } - - return base.CanEquip( from ); - } - - public override void OnAdded(IEntity parent) - { - if (parent is Mobile from) - { - m_AosSkillBonuses.AddTo(from); - m_AosAttributes.AddStatBonuses(from); - - if (m_Blessed && BlessedFor == null) - { - BlessedFor = from; - LootType = LootType.Blessed; - } - - if (m_ChargeTime > 0) - { - m_ChargeTime = m_MaxChargeTime; - StartTimer(); - } - } - - InvalidateProperties(); - } - - public override void OnRemoved(IEntity parent) - { - if (parent is Mobile from) - { - m_AosSkillBonuses.Remove(); - m_AosAttributes.RemoveStatBonuses(from); - - if (m_Creature != null && !m_Creature.Deleted) - { - Effects.SendLocationParticles(EffectItem.Create(m_Creature.Location, m_Creature.Map, EffectItem.DefaultDuration), 0x3728, 8, 20, 5042); - Effects.PlaySound(m_Creature, m_Creature.Map, 0x201); - - m_Creature.Delete(); - } - - StopTimer(); - } - - InvalidateProperties(); - } - - public override void OnDoubleClick(Mobile from) - { - if (from.Talisman != this) - from.SendLocalizedMessage(502641); // You must equip this item to use it. - else if (m_ChargeTime > 0) - from.SendLocalizedMessage(1074882, m_ChargeTime.ToString()); // You must wait ~1_val~ seconds for this to recharge. - else if (m_Charges == 0 && m_MaxCharges > 0) - from.SendLocalizedMessage(1042544); // This item is out of charges. - else - { - Type type = GetSummoner(); - - if (m_Summoner != null && !m_Summoner.IsEmpty) - type = m_Summoner.Type; - - if (type != null) - { - object obj; - - try { obj = Activator.CreateInstance(type); } - catch { obj = null; } - - if (obj is Item item) - { - int count = 1; - - if (m_Summoner != null && m_Summoner.Amount > 1) - { - if (item.Stackable) - item.Amount = m_Summoner.Amount; - else - count = m_Summoner.Amount; - } - - if (from.Backpack == null || count * item.Weight > from.Backpack.MaxWeight || - from.Backpack.Items.Count + count > from.Backpack.MaxItems) - { - from.SendLocalizedMessage(500720); // You don't have enough room in your backpack! - item.Delete(); - item = null; - return; - } - - for (int i = 0; i < count; i++) - { - from.PlaceInBackpack(item); - - if (i + 1 < count) - item = Activator.CreateInstance(type) as Item; - } - - if (item is Board) - from.SendLocalizedMessage(1075000); // You have been given some wooden boards. - else if (item is IronIngot) - from.SendLocalizedMessage(1075001); // You have been given some ingots. - else if (item is Bandage) - from.SendLocalizedMessage(1075002); // You have been given some clean bandages. - else if (m_Summoner?.Name != null) - from.SendLocalizedMessage(1074853, m_Summoner.Name.ToString()); // You have been given ~1_name~ - } - else if (obj is BaseCreature mob) - { - if ((m_Creature != null && !m_Creature.Deleted) || from.Followers + mob.ControlSlots > from.FollowersMax) - { - from.SendLocalizedMessage(1074270); // You have too many followers to summon another one. - mob.Delete(); - return; - } - - BaseCreature.Summon(mob, from, from.Location, mob.BaseSoundID, TimeSpan.FromMinutes(10)); - Effects.SendLocationParticles(EffectItem.Create(mob.Location, mob.Map, EffectItem.DefaultDuration), 0x3728, 1, 10, 0x26B6); - - mob.Summoned = false; - mob.ControlOrder = OrderType.Friend; - - m_Creature = mob; - } - - OnAfterUse(from); - } - - if (m_Removal != TalismanRemoval.None) - { - from.Target = new TalismanTarget(this); - } - } - } - - public override void AddNameProperty(ObjectPropertyList list) - { - if (ForceShowName) - base.AddNameProperty(list); - else if (m_Summoner != null && !m_Summoner.IsEmpty) - list.Add(1072400, m_Summoner.Name != null ? m_Summoner.Name.ToString() : "Unknown"); // Talisman of ~1_name~ Summoning - else if (m_Removal != TalismanRemoval.None) - list.Add(1072389, "#" + (1072000 + (int)m_Removal)); // Talisman of ~1_name~ - else - base.AddNameProperty(list); - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - if (Blessed) - { - if (BlessedFor != null) - list.Add(1072304, !string.IsNullOrEmpty(BlessedFor.Name) ? BlessedFor.Name : "Unnamed Warrior"); // Owned by ~1_name~ - else - list.Add(1072304, "Nobody"); // Owned by ~1_name~ - } + public enum TalismanRemoval + { + None = 0, + Ward = 390, + Damage = 404, + Curse = 407, + Wildfire = 2843 + } + + public class BaseTalisman : Item + { + private bool m_Blessed; + private int m_Charges; + private int m_ChargeTime; + + private int m_MaxCharges; + private int m_MaxChargeTime; + + public BaseTalisman() + : this(GetRandomItemID()) + { + } + + public BaseTalisman(int itemID) + : base(itemID) + { + Layer = Layer.Talisman; + Weight = 1.0; + + m_Protection = new TalismanAttribute(); + m_Killer = new TalismanAttribute(); + m_Summoner = new TalismanAttribute(); + m_AosAttributes = new AosAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + } + + public BaseTalisman(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1071023; // Talisman + public virtual bool ForceShowName => false; // used to override default summoner/removal name + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxCharges + { + get => m_MaxCharges; + set + { + m_MaxCharges = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + + if (m_ChargeTime > 0) + StartTimer(); + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxChargeTime + { + get => m_MaxChargeTime; + set + { + m_MaxChargeTime = value; + InvalidateProperties(); + } + } + + public int ChargeTime + { + get => m_ChargeTime; + set + { + m_ChargeTime = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Blessed + { + get => m_Blessed; + set + { + m_Blessed = value; + InvalidateProperties(); + } + } + + public static void Initialize() + { + CommandSystem.Register("RandomTalisman", AccessLevel.GameMaster, RandomTalisman_OnCommand); + } + + [Usage("RandomTalisman ")] + [Description("Generates random talismans in your backpack.")] + public static void RandomTalisman_OnCommand(CommandEventArgs e) + { + Mobile m = e.Mobile; + int count = e.GetInt32(0); + + for (int i = 0; i < count; i++) m.AddToBackpack(Loot.RandomTalisman()); + } + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is BaseTalisman talisman)) + return; + + talisman.m_Summoner = new TalismanAttribute(m_Summoner); + talisman.m_Protection = new TalismanAttribute(m_Protection); + talisman.m_Killer = new TalismanAttribute(m_Killer); + talisman.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); + talisman.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); + } + + public override bool CanEquip(Mobile from) + { + if (BlessedFor != null && BlessedFor != from) + { + from.SendLocalizedMessage(1010437); // You are not the owner. + return false; + } + + return base.CanEquip(from); + } + + public override void OnAdded(IEntity parent) + { + if (parent is Mobile from) + { + m_AosSkillBonuses.AddTo(from); + m_AosAttributes.AddStatBonuses(from); + + if (m_Blessed && BlessedFor == null) + { + BlessedFor = from; + LootType = LootType.Blessed; + } + + if (m_ChargeTime > 0) + { + m_ChargeTime = m_MaxChargeTime; + StartTimer(); + } + } + + InvalidateProperties(); + } + + public override void OnRemoved(IEntity parent) + { + if (parent is Mobile from) + { + m_AosSkillBonuses.Remove(); + m_AosAttributes.RemoveStatBonuses(from); + + if (m_Creature != null && !m_Creature.Deleted) + { + Effects.SendLocationParticles( + EffectItem.Create(m_Creature.Location, m_Creature.Map, EffectItem.DefaultDuration), 0x3728, 8, 20, + 5042); + Effects.PlaySound(m_Creature, m_Creature.Map, 0x201); + + m_Creature.Delete(); + } + + StopTimer(); + } + + InvalidateProperties(); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.Talisman != this) + { + from.SendLocalizedMessage(502641); // You must equip this item to use it. + } + else if (m_ChargeTime > 0) + { + from.SendLocalizedMessage(1074882, + m_ChargeTime.ToString()); // You must wait ~1_val~ seconds for this to recharge. + } + else if (m_Charges == 0 && m_MaxCharges > 0) + { + from.SendLocalizedMessage(1042544); // This item is out of charges. + } + else + { + Type type = GetSummoner(); + + if (m_Summoner != null && !m_Summoner.IsEmpty) + type = m_Summoner.Type; + + if (type != null) + { + object obj; + + try + { + obj = Activator.CreateInstance(type); + } + catch + { + obj = null; + } + + if (obj is Item item) + { + int count = 1; + + if (m_Summoner != null && m_Summoner.Amount > 1) + { + if (item.Stackable) + item.Amount = m_Summoner.Amount; + else + count = m_Summoner.Amount; + } + + if (from.Backpack == null || count * item.Weight > from.Backpack.MaxWeight || + from.Backpack.Items.Count + count > from.Backpack.MaxItems) + { + from.SendLocalizedMessage(500720); // You don't have enough room in your backpack! + item.Delete(); + item = null; + return; + } + + for (int i = 0; i < count; i++) + { + from.PlaceInBackpack(item); + + if (i + 1 < count) + item = Activator.CreateInstance(type) as Item; + } + + if (item is Board) + from.SendLocalizedMessage(1075000); // You have been given some wooden boards. + else if (item is IronIngot) + from.SendLocalizedMessage(1075001); // You have been given some ingots. + else if (item is Bandage) + from.SendLocalizedMessage(1075002); // You have been given some clean bandages. + else if (m_Summoner?.Name != null) + from.SendLocalizedMessage(1074853, m_Summoner.Name.ToString()); // You have been given ~1_name~ + } + else if (obj is BaseCreature mob) + { + if (m_Creature != null && !m_Creature.Deleted || + from.Followers + mob.ControlSlots > from.FollowersMax) + { + from.SendLocalizedMessage(1074270); // You have too many followers to summon another one. + mob.Delete(); + return; + } + + BaseCreature.Summon(mob, from, from.Location, mob.BaseSoundID, TimeSpan.FromMinutes(10)); + Effects.SendLocationParticles(EffectItem.Create(mob.Location, mob.Map, EffectItem.DefaultDuration), + 0x3728, 1, 10, 0x26B6); + + mob.Summoned = false; + mob.ControlOrder = OrderType.Friend; + + m_Creature = mob; + } + + OnAfterUse(from); + } + + if (m_Removal != TalismanRemoval.None) from.Target = new TalismanTarget(this); + } + } + + public override void AddNameProperty(ObjectPropertyList list) + { + if (ForceShowName) + base.AddNameProperty(list); + else if (m_Summoner != null && !m_Summoner.IsEmpty) + list.Add(1072400, + m_Summoner.Name != null ? m_Summoner.Name.ToString() : "Unknown"); // Talisman of ~1_name~ Summoning + else if (m_Removal != TalismanRemoval.None) + list.Add(1072389, "#" + (1072000 + (int)m_Removal)); // Talisman of ~1_name~ + else + base.AddNameProperty(list); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Blessed) + { + if (BlessedFor != null) + list.Add(1072304, + !string.IsNullOrEmpty(BlessedFor.Name) ? BlessedFor.Name : "Unnamed Warrior"); // Owned by ~1_name~ + else + list.Add(1072304, "Nobody"); // Owned by ~1_name~ + } + + if (Parent is Mobile && m_MaxChargeTime > 0) + { + if (m_ChargeTime > 0) + list.Add(1074884, m_ChargeTime.ToString()); // Charge time left: ~1_val~ + else + list.Add(1074883); // Fully Charged + } + + list.Add(1075085); // Requirement: Mondain's Legacy + + if (m_Killer != null && !m_Killer.IsEmpty && m_Killer.Amount > 0) + list.Add(1072388, "{0}\t{1}", m_Killer.Name != null ? m_Killer.Name.ToString() : "Unknown", + m_Killer.Amount); // ~1_NAME~ Killer: +~2_val~% + + if (m_Protection != null && !m_Protection.IsEmpty && m_Protection.Amount > 0) + list.Add(1072387, "{0}\t{1}", m_Protection.Name != null ? m_Protection.Name.ToString() : "Unknown", + m_Protection.Amount); // ~1_NAME~ Protection: +~2_val~% + + if (m_ExceptionalBonus != 0) + list.Add(1072395, "#{0}\t{1}", AosSkillBonuses.GetLabel(m_Skill), + m_ExceptionalBonus); // ~1_NAME~ Exceptional Bonus: ~2_val~% + + if (m_SuccessBonus != 0) + list.Add(1072394, "#{0}\t{1}", AosSkillBonuses.GetLabel(m_Skill), + m_SuccessBonus); // ~1_NAME~ Bonus: ~2_val~% - if (Parent is Mobile && m_MaxChargeTime > 0) - { - if (m_ChargeTime > 0) - list.Add(1074884, m_ChargeTime.ToString()); // Charge time left: ~1_val~ - else - list.Add(1074883); // Fully Charged - } - - list.Add(1075085); // Requirement: Mondain's Legacy - - if (m_Killer != null && !m_Killer.IsEmpty && m_Killer.Amount > 0) - list.Add(1072388, "{0}\t{1}", m_Killer.Name != null ? m_Killer.Name.ToString() : "Unknown", m_Killer.Amount); // ~1_NAME~ Killer: +~2_val~% - - if (m_Protection != null && !m_Protection.IsEmpty && m_Protection.Amount > 0) - list.Add(1072387, "{0}\t{1}", m_Protection.Name != null ? m_Protection.Name.ToString() : "Unknown", m_Protection.Amount); // ~1_NAME~ Protection: +~2_val~% - - if (m_ExceptionalBonus != 0) - list.Add(1072395, "#{0}\t{1}", AosSkillBonuses.GetLabel( m_Skill ), m_ExceptionalBonus); // ~1_NAME~ Exceptional Bonus: ~2_val~% - - if (m_SuccessBonus != 0) - list.Add(1072394, "#{0}\t{1}", AosSkillBonuses.GetLabel( m_Skill ), m_SuccessBonus); // ~1_NAME~ Bonus: ~2_val~% - - m_AosSkillBonuses.GetProperties(list); - - int prop; - - if ((prop = m_AosAttributes.WeaponDamage) != 0) - list.Add(1060401, prop.ToString()); // damage increase ~1_val~% - - if ((prop = m_AosAttributes.DefendChance) != 0) - list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% - - if ((prop = m_AosAttributes.BonusDex) != 0) - list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ - - if ((prop = m_AosAttributes.EnhancePotions) != 0) - list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% - - if ((prop = m_AosAttributes.CastRecovery) != 0) - list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ - - if ((prop = m_AosAttributes.CastSpeed) != 0) - list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - - if ((prop = m_AosAttributes.AttackChance) != 0) - list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - - if ((prop = m_AosAttributes.BonusHits) != 0) - list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - - if ((prop = m_AosAttributes.BonusInt) != 0) - list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - - if ((prop = m_AosAttributes.LowerManaCost) != 0) - list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - - if ((prop = m_AosAttributes.LowerRegCost) != 0) - list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - - if ((prop = m_AosAttributes.Luck) != 0) - list.Add(1060436, prop.ToString()); // luck ~1_val~ - - if ((prop = m_AosAttributes.BonusMana) != 0) - list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - - if ((prop = m_AosAttributes.RegenMana) != 0) - list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - - if ((prop = m_AosAttributes.NightSight) != 0) - list.Add(1060441); // night sight - - if ((prop = m_AosAttributes.ReflectPhysical) != 0) - list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - - if ((prop = m_AosAttributes.RegenStam) != 0) - list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - - if ((prop = m_AosAttributes.RegenHits) != 0) - list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ + m_AosSkillBonuses.GetProperties(list); - if ((prop = m_AosAttributes.SpellChanneling) != 0) - list.Add(1060482); // spell channeling + int prop; - if ((prop = m_AosAttributes.SpellDamage) != 0) - list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% + if ((prop = m_AosAttributes.WeaponDamage) != 0) + list.Add(1060401, prop.ToString()); // damage increase ~1_val~% - if ((prop = m_AosAttributes.BonusStam) != 0) - list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ + if ((prop = m_AosAttributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% + + if ((prop = m_AosAttributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ + + if ((prop = m_AosAttributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% + + if ((prop = m_AosAttributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ + + if ((prop = m_AosAttributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - if ((prop = m_AosAttributes.BonusStr) != 0) - list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ + if ((prop = m_AosAttributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - if ((prop = m_AosAttributes.WeaponSpeed) != 0) - list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% + if ((prop = m_AosAttributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) - list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% + if ((prop = m_AosAttributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - if (m_MaxCharges > 0) - list.Add(1060741, m_Charges.ToString()); // charges: ~1_val~ + if ((prop = m_AosAttributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if (m_Slayer != TalismanSlayerName.None) - list.Add(1072503 + (int)m_Slayer); - } + if ((prop = m_AosAttributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) - { - if (setIf) - flags |= toSet; - } + if ((prop = m_AosAttributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) - { - return ((flags & toGet) != 0); - } + if ((prop = m_AosAttributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - [Flags] - private enum SaveFlag - { - None = 0x00000000, - Attributes = 0x00000001, - SkillBonuses = 0x00000002, - Owner = 0x00000004, - Protection = 0x00000008, - Killer = 0x00000010, - Summoner = 0x00000020, - Removal = 0x00000040, - OldKarmaLoss = 0x00000080, - Skill = 0x00000100, - SuccessBonus = 0x00000200, - ExceptionalBonus = 0x00000400, - MaxCharges = 0x00000800, - Charges = 0x00001000, - MaxChargeTime = 0x00002000, - ChargeTime = 0x00004000, - Blessed = 0x00008000, - Slayer = 0x00010000, - } + if ((prop = m_AosAttributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + if ((prop = m_AosAttributes.NightSight) != 0) + list.Add(1060441); // night sight - writer.Write((int)0); // version + if ((prop = m_AosAttributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - SaveFlag flags = SaveFlag.None; + if ((prop = m_AosAttributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - SetSaveFlag(ref flags, SaveFlag.Attributes, !m_AosAttributes.IsEmpty); - SetSaveFlag(ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty); - SetSaveFlag(ref flags, SaveFlag.Protection, m_Protection != null && !m_Protection.IsEmpty); - SetSaveFlag(ref flags, SaveFlag.Killer, m_Killer != null && !m_Killer.IsEmpty); - SetSaveFlag(ref flags, SaveFlag.Summoner, m_Summoner != null && !m_Summoner.IsEmpty); - SetSaveFlag(ref flags, SaveFlag.Removal, m_Removal != TalismanRemoval.None); - SetSaveFlag(ref flags, SaveFlag.Skill, (int)m_Skill != 0); - SetSaveFlag(ref flags, SaveFlag.SuccessBonus, m_SuccessBonus != 0); - SetSaveFlag(ref flags, SaveFlag.ExceptionalBonus, m_ExceptionalBonus != 0); - SetSaveFlag(ref flags, SaveFlag.MaxCharges, m_MaxCharges != 0); - SetSaveFlag(ref flags, SaveFlag.Charges, m_Charges != 0); - SetSaveFlag(ref flags, SaveFlag.MaxChargeTime, m_MaxChargeTime != 0); - SetSaveFlag(ref flags, SaveFlag.ChargeTime, m_ChargeTime != 0); - SetSaveFlag(ref flags, SaveFlag.Blessed, m_Blessed); - SetSaveFlag(ref flags, SaveFlag.Slayer, m_Slayer != TalismanSlayerName.None); - - writer.WriteEncodedInt((int)flags); + if ((prop = m_AosAttributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if (GetSaveFlag(flags, SaveFlag.Attributes)) - m_AosAttributes.Serialize(writer); + if ((prop = m_AosAttributes.SpellChanneling) != 0) + list.Add(1060482); // spell channeling - if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) - m_AosSkillBonuses.Serialize(writer); + if ((prop = m_AosAttributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - if (GetSaveFlag(flags, SaveFlag.Protection)) - m_Protection.Serialize(writer); + if ((prop = m_AosAttributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - if (GetSaveFlag(flags, SaveFlag.Killer)) - m_Killer.Serialize(writer); + if ((prop = m_AosAttributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - if (GetSaveFlag(flags, SaveFlag.Summoner)) - m_Summoner.Serialize(writer); + if ((prop = m_AosAttributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - if (GetSaveFlag(flags, SaveFlag.Removal)) - writer.WriteEncodedInt((int)m_Removal); + if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) + list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% - if (GetSaveFlag(flags, SaveFlag.Skill)) - writer.WriteEncodedInt((int)m_Skill); + if (m_MaxCharges > 0) + list.Add(1060741, m_Charges.ToString()); // charges: ~1_val~ - if (GetSaveFlag(flags, SaveFlag.SuccessBonus)) - writer.WriteEncodedInt(m_SuccessBonus); - - if (GetSaveFlag(flags, SaveFlag.ExceptionalBonus)) - writer.WriteEncodedInt(m_ExceptionalBonus); - - if (GetSaveFlag(flags, SaveFlag.MaxCharges)) - writer.WriteEncodedInt(m_MaxCharges); - - if (GetSaveFlag(flags, SaveFlag.Charges)) - writer.WriteEncodedInt(m_Charges); - - if (GetSaveFlag(flags, SaveFlag.MaxChargeTime)) - writer.WriteEncodedInt(m_MaxChargeTime); - - if (GetSaveFlag(flags, SaveFlag.ChargeTime)) - writer.WriteEncodedInt(m_ChargeTime); - - if (GetSaveFlag(flags, SaveFlag.Slayer)) - writer.WriteEncodedInt((int)m_Slayer); - } - - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - - switch (version) - { - case 0: - { - SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); - - if (GetSaveFlag(flags, SaveFlag.Attributes)) - m_AosAttributes = new AosAttributes(this, reader); - else - m_AosAttributes = new AosAttributes(this); + if (m_Slayer != TalismanSlayerName.None) + list.Add(1072503 + (int)m_Slayer); + } - if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) - m_AosSkillBonuses = new AosSkillBonuses(this, reader); - else - m_AosSkillBonuses = new AosSkillBonuses(this); + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } - // Backward compatibility - if (GetSaveFlag(flags, SaveFlag.Owner)) - BlessedFor = reader.ReadMobile(); + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } - if (GetSaveFlag(flags, SaveFlag.Protection)) - m_Protection = new TalismanAttribute(reader); - else - m_Protection = new TalismanAttribute(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if (GetSaveFlag(flags, SaveFlag.Killer)) - m_Killer = new TalismanAttribute(reader); - else - m_Killer = new TalismanAttribute(); + writer.Write(0); // version - if (GetSaveFlag(flags, SaveFlag.Summoner)) - m_Summoner = new TalismanAttribute(reader); - else - m_Summoner = new TalismanAttribute(); + SaveFlag flags = SaveFlag.None; - if (GetSaveFlag(flags, SaveFlag.Removal)) - m_Removal = (TalismanRemoval)reader.ReadEncodedInt(); + SetSaveFlag(ref flags, SaveFlag.Attributes, !m_AosAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.Protection, m_Protection != null && !m_Protection.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.Killer, m_Killer != null && !m_Killer.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.Summoner, m_Summoner != null && !m_Summoner.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.Removal, m_Removal != TalismanRemoval.None); + SetSaveFlag(ref flags, SaveFlag.Skill, (int)m_Skill != 0); + SetSaveFlag(ref flags, SaveFlag.SuccessBonus, m_SuccessBonus != 0); + SetSaveFlag(ref flags, SaveFlag.ExceptionalBonus, m_ExceptionalBonus != 0); + SetSaveFlag(ref flags, SaveFlag.MaxCharges, m_MaxCharges != 0); + SetSaveFlag(ref flags, SaveFlag.Charges, m_Charges != 0); + SetSaveFlag(ref flags, SaveFlag.MaxChargeTime, m_MaxChargeTime != 0); + SetSaveFlag(ref flags, SaveFlag.ChargeTime, m_ChargeTime != 0); + SetSaveFlag(ref flags, SaveFlag.Blessed, m_Blessed); + SetSaveFlag(ref flags, SaveFlag.Slayer, m_Slayer != TalismanSlayerName.None); - if (GetSaveFlag(flags, SaveFlag.OldKarmaLoss)) - m_AosAttributes.IncreasedKarmaLoss = reader.ReadEncodedInt(); + writer.WriteEncodedInt((int)flags); - if (GetSaveFlag(flags, SaveFlag.Skill)) - m_Skill = (SkillName)reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_AosAttributes.Serialize(writer); - if (GetSaveFlag(flags, SaveFlag.SuccessBonus)) - m_SuccessBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses.Serialize(writer); - if (GetSaveFlag(flags, SaveFlag.ExceptionalBonus)) - m_ExceptionalBonus = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Protection)) + m_Protection.Serialize(writer); - if (GetSaveFlag(flags, SaveFlag.MaxCharges)) - m_MaxCharges = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Killer)) + m_Killer.Serialize(writer); - if (GetSaveFlag(flags, SaveFlag.Charges)) - m_Charges = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Summoner)) + m_Summoner.Serialize(writer); - if (GetSaveFlag(flags, SaveFlag.MaxChargeTime)) - m_MaxChargeTime = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Removal)) + writer.WriteEncodedInt((int)m_Removal); - if (GetSaveFlag(flags, SaveFlag.ChargeTime)) - m_ChargeTime = reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.Skill)) + writer.WriteEncodedInt((int)m_Skill); - if (GetSaveFlag(flags, SaveFlag.Slayer)) - m_Slayer = (TalismanSlayerName)reader.ReadEncodedInt(); + if (GetSaveFlag(flags, SaveFlag.SuccessBonus)) + writer.WriteEncodedInt(m_SuccessBonus); - m_Blessed = GetSaveFlag(flags, SaveFlag.Blessed); - - break; - } - } - - if (Parent is Mobile m) - { - m_AosAttributes.AddStatBonuses(m); - m_AosSkillBonuses.AddTo(m); - - if (m_ChargeTime > 0) - StartTimer(); - } - } - - public virtual void OnAfterUse(Mobile m) - { - m_ChargeTime = m_MaxChargeTime; - - if (m_Charges > 0 && m_MaxCharges > 0) - m_Charges -= 1; - - if (m_ChargeTime > 0) - StartTimer(); - - InvalidateProperties(); - } - - public virtual Type GetSummoner() - { - return null; - } - - public virtual void SetSummoner(Type type, TextDefinition name) - { - m_Summoner = new TalismanAttribute(type, name); - } - - public virtual void SetProtection(Type type, TextDefinition name, int amount) - { - m_Protection = new TalismanAttribute(type, name, amount); - } - - public virtual void SetKiller(Type type, TextDefinition name, int amount) - { - m_Killer = new TalismanAttribute(type, name, amount); - } - - #region Timer - private Timer m_Timer; - - public virtual void StartTimer() - { - if (m_Timer == null || !m_Timer.Running) - m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(10), TimeSpan.FromSeconds(10), Slice); - } - - public virtual void StopTimer() - { - m_Timer?.Stop(); - - m_Timer = null; - } - - public virtual void Slice() - { - if (m_ChargeTime - 10 > 0) - m_ChargeTime -= 10; - else - { - m_ChargeTime = 0; - - StopTimer(); - } - - InvalidateProperties(); - } - #endregion - - #region Randomize - private static int[] m_ItemIDs = { - 0x2F58, 0x2F59, 0x2F5A, 0x2F5B - }; - - public static int GetRandomItemID() - { - return Utility.RandomList(m_ItemIDs); - } - - private static Type[] m_Summons = { - typeof( SummonedAntLion ), - typeof( SummonedCow ), - typeof( SummonedLavaSerpent ), - typeof( SummonedOrcBrute ), - typeof( SummonedFrostSpider ), - typeof( SummonedPanther ), - typeof( SummonedDoppleganger ), - typeof( SummonedGreatHart ), - typeof( SummonedBullFrog ), - typeof( SummonedArcticOgreLord ), - typeof( SummonedBogling ), - typeof( SummonedBakeKitsune ), - typeof( SummonedSheep ), - typeof( SummonedSkeletalKnight ), - typeof( SummonedWailingBanshee ), - typeof( SummonedChicken ), - typeof( SummonedVorpalBunny ), - - typeof( Board ), - typeof( IronIngot ), - typeof( Bandage ), - }; - - private static int[] m_SummonLabels = { - 1075211, // Ant Lion - 1072494, // Cow - 1072434, // Lava Serpent - 1072414, // Orc Brute - 1072476, // Frost Spider - 1029653, // Panther - 1029741, // Doppleganger - 1018292, // great hart - 1028496, // bullfrog - 1018227, // arctic ogre lord - 1029735, // Bogling - 1030083, // bake-kitsune - 1018285, // sheep - 1018239, // skeletal knight - 1072399, // Wailing Banshee - 1072459, // Chicken - 1072401, // Vorpal Bunny - - 1015101, // Boards - 1044036, // Ingots - 1023817, // clean bandage - }; - - public static Type GetRandomSummonType() - { - return m_Summons[Utility.Random(m_Summons.Length)]; - } - - public static TalismanAttribute GetRandomSummoner() - { - if (0.025 > Utility.RandomDouble()) - { - int num = Utility.Random(m_Summons.Length); - - if (num > 14) - return new TalismanAttribute(m_Summons[num], m_SummonLabels[num], 10); - return new TalismanAttribute(m_Summons[num], m_SummonLabels[num]); - } - - return new TalismanAttribute(); - } - - public static TalismanRemoval GetRandomRemoval() - { - if (0.65 > Utility.RandomDouble()) - return (TalismanRemoval)Utility.RandomList(390, 404, 407); - - return TalismanRemoval.None; - } - - private static Type[] m_Killers = { - typeof( OrcBomber ), typeof( OrcBrute ), typeof( SewerRat ), typeof( Rat ), typeof( GiantRat ), - typeof( Ratman ), typeof( RatmanArcher ), typeof( GiantSpider ), typeof( FrostSpider ), typeof( GiantBlackWidow ), - typeof( DreadSpider ), typeof( SilverSerpent ), typeof( DeepSeaSerpent ), typeof( GiantSerpent ), typeof( Snake ), - typeof( IceSnake ), typeof( IceSerpent ), typeof( LavaSerpent ), typeof( LavaSnake ), typeof( Yamandon ), - typeof( StrongMongbat ),typeof( Mongbat ), typeof( VampireBat ), typeof( Lich ), typeof( EvilMage ), - typeof( LichLord ), typeof( EvilMageLord ), typeof( SkeletalMage ), typeof( KhaldunZealot ), typeof( AncientLich ), - typeof( JukaMage ), typeof( MeerMage ), typeof( Beetle ), typeof( DeathwatchBeetle ), typeof( RuneBeetle ), - typeof( FireBeetle ), typeof( DeathwatchBeetleHatchling), typeof( Bird ), typeof( Chicken ), typeof( Eagle ), - typeof( TropicalBird ), typeof( Phoenix ), typeof( DesertOstard ), typeof( FrenziedOstard ), typeof( ForestOstard ), - typeof( Crane ), typeof( SnowLeopard ), typeof( IceFiend ), typeof( FrostOoze ), typeof( FrostTroll ), - typeof( IceElemental ), typeof( SnowElemental ), typeof( GiantIceWorm ), typeof( LadyOfTheSnow ), typeof( FireElemental ), - typeof( FireSteed ), typeof( HellHound ), typeof( HellCat ), typeof( PredatorHellCat ), typeof( LavaLizard ), - typeof( FireBeetle ), typeof( Cow ), typeof( Bull ), typeof( Gaman )//, typeof( Minotaur) - // TODO Meraktus, Tormented Minotaur, Minotaur - }; - - private static int[] m_KillerLabels = { - 1072413, 1072414, 1072418, 1072419, 1072420, - 1072421, 1072423, 1072424, 1072425, 1072426, - 1072427, 1072428, 1072429, 1072430, 1072431, - 1072432, 1072433, 1072434, 1072435, 1072438, - 1072440, 1072441, 1072443, 1072444, 1072445, - 1072446, 1072447, 1072448, 1072449, 1072450, - 1072451, 1072452, 1072453, 1072454, 1072455, - 1072456, 1072457, 1072458, 1072459, 1072461, - 1072462, 1072465, 1072468, 1072469, 1072470, - 1072473, 1072474, 1072477, 1072478, 1072479, - 1072480, 1072481, 1072483, 1072485, 1072486, - 1072487, 1072489, 1072490, 1072491, 1072492, - 1072493, 1072494, 1072495, 1072498, - }; - - public static TalismanAttribute GetRandomKiller() - { - return GetRandomKiller( true ); - } - - public static TalismanAttribute GetRandomKiller( bool includingNone ) - { - if ( includingNone && Utility.RandomBool() ) - return new TalismanAttribute(); - - int num = Utility.Random(m_Killers.Length); - - return new TalismanAttribute(m_Killers[num], m_KillerLabels[num], Utility.RandomMinMax(10, 100)); - } - - public static TalismanAttribute GetRandomProtection() - { - return GetRandomProtection( true ); - } - - public static TalismanAttribute GetRandomProtection( bool includingNone ) - { - if ( includingNone && Utility.RandomBool() ) - return new TalismanAttribute(); - - int num = Utility.Random(m_Killers.Length); - - return new TalismanAttribute(m_Killers[num], m_KillerLabels[num], Utility.RandomMinMax(5, 60)); - } - - private static SkillName[] m_Skills = { - SkillName.Alchemy, - SkillName.Blacksmith, - SkillName.Carpentry, - SkillName.Cartography, - SkillName.Cooking, - SkillName.Fletching, - SkillName.Inscribe, - SkillName.Tailoring, - SkillName.Tinkering, - }; - - public static SkillName GetRandomSkill() - { - return m_Skills[Utility.Random(m_Skills.Length)]; - } - - public static int GetRandomExceptional() - { - if (0.3 > Utility.RandomDouble()) - { - double num = 40 - Math.Log(Utility.RandomMinMax(7, 403)) * 5; - - return (int)Math.Round(num); - } - - return 0; - } - - public static int GetRandomSuccessful() - { - if (0.75 > Utility.RandomDouble()) - { - double num = 40 - Math.Log(Utility.RandomMinMax(7, 403)) * 5; - - return (int)Math.Round(num); - } - - return 0; - } - - public static bool GetRandomBlessed() - { - if (0.02 > Utility.RandomDouble()) - return true; - - return false; - } - - public static TalismanSlayerName GetRandomSlayer() - { - if (0.01 > Utility.RandomDouble()) - return (TalismanSlayerName)Utility.RandomMinMax(1, 9); - - return TalismanSlayerName.None; - } - - public static int GetRandomCharges() - { - if (0.5 > Utility.RandomDouble()) - return Utility.RandomMinMax(10, 50); - - return 0; - } - #endregion - - private class TalismanTarget : Target - { - private BaseTalisman m_Talisman; - - public TalismanTarget(BaseTalisman talisman) - : base(12, false, TargetFlags.Beneficial) - { - m_Talisman = talisman; - } - - protected override void OnTarget(Mobile from, object o) - { - if (m_Talisman == null || m_Talisman.Deleted) - return; - - Mobile target = o as Mobile; - - if (from.Talisman != m_Talisman) - from.SendLocalizedMessage(502641); // You must equip this item to use it. - else if (target == null) - from.SendLocalizedMessage(1046439); // That is not a valid target. - else if (m_Talisman.ChargeTime > 0) - from.SendLocalizedMessage(1074882, m_Talisman.ChargeTime.ToString()); // You must wait ~1_val~ seconds for this to recharge. - else if (m_Talisman.Charges == 0 && m_Talisman.MaxCharges > 0) - from.SendLocalizedMessage(1042544); // This item is out of charges. - else - { - switch (m_Talisman.Removal) - { - case TalismanRemoval.Curse: - target.PlaySound(0xF6); - target.PlaySound(0x1F7); - target.FixedParticles(0x3709, 1, 30, 9963, 13, 3, EffectLayer.Head); - - IEntity mfrom = new Entity(Serial.Zero, new Point3D(target.X, target.Y, target.Z - 10), from.Map); - IEntity mto = new Entity(Serial.Zero, new Point3D(target.X, target.Y, target.Z + 50), from.Map); - Effects.SendMovingParticles(mfrom, mto, 0x2255, 1, 0, false, false, 13, 3, 9501, 1, 0, EffectLayer.Head, 0x100); - - StatMod mod; - - mod = target.GetStatMod("[Magic] Str Offset"); - if (mod != null && mod.Offset < 0) - target.RemoveStatMod("[Magic] Str Offset"); - - mod = target.GetStatMod("[Magic] Dex Offset"); - if (mod != null && mod.Offset < 0) - target.RemoveStatMod("[Magic] Dex Offset"); - - mod = target.GetStatMod("[Magic] Int Offset"); - if (mod != null && mod.Offset < 0) - target.RemoveStatMod("[Magic] Int Offset"); - - target.Paralyzed = false; - - EvilOmenSpell.TryEndEffect(target); - StrangleSpell.RemoveCurse(target); - CorpseSkinSpell.RemoveCurse(target); - CurseSpell.RemoveEffect(target); - - BuffInfo.RemoveBuff(target, BuffIcon.Clumsy); - BuffInfo.RemoveBuff(target, BuffIcon.FeebleMind); - BuffInfo.RemoveBuff(target, BuffIcon.Weaken); - BuffInfo.RemoveBuff(target, BuffIcon.MassCurse); - - target.SendLocalizedMessage(1072408); // Any curses on you have been lifted - - if (target != from) - from.SendLocalizedMessage(1072409); // Your targets curses have been lifted - - break; - case TalismanRemoval.Damage: - target.PlaySound(0x201); - Effects.SendLocationParticles(EffectItem.Create(target.Location, target.Map, EffectItem.DefaultDuration), 0x3728, 1, 13, 0x834, 0, 0x13B2, 0); - - BleedAttack.EndBleed(target, true); - MortalStrike.EndWound(target); - - BuffInfo.RemoveBuff(target, BuffIcon.Bleed); - BuffInfo.RemoveBuff(target, BuffIcon.MortalStrike); - - target.SendLocalizedMessage(1072405); // Your lasting damage effects have been removed! - - if (target != from) - from.SendLocalizedMessage(1072406); // Your Targets lasting damage effects have been removed! - - break; - case TalismanRemoval.Ward: - target.PlaySound(0x201); - Effects.SendLocationParticles(EffectItem.Create(target.Location, target.Map, EffectItem.DefaultDuration), 0x3728, 1, 13, 0x834, 0, 0x13B2, 0); - - MagicReflectSpell.EndReflect(target); - ReactiveArmorSpell.EndArmor(target); - ProtectionSpell.EndProtection(target); - - target.SendLocalizedMessage(1072402); // Your wards have been removed! - - if (target != from) - from.SendLocalizedMessage(1072403); // Your target's wards have been removed! - - break; - case TalismanRemoval.Wildfire: - // TODO - break; - } - - m_Talisman.OnAfterUse(from); - } - } - } - } -} + if (GetSaveFlag(flags, SaveFlag.ExceptionalBonus)) + writer.WriteEncodedInt(m_ExceptionalBonus); + + if (GetSaveFlag(flags, SaveFlag.MaxCharges)) + writer.WriteEncodedInt(m_MaxCharges); + + if (GetSaveFlag(flags, SaveFlag.Charges)) + writer.WriteEncodedInt(m_Charges); + + if (GetSaveFlag(flags, SaveFlag.MaxChargeTime)) + writer.WriteEncodedInt(m_MaxChargeTime); + + if (GetSaveFlag(flags, SaveFlag.ChargeTime)) + writer.WriteEncodedInt(m_ChargeTime); + + if (GetSaveFlag(flags, SaveFlag.Slayer)) + writer.WriteEncodedInt((int)m_Slayer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Attributes)) + m_AosAttributes = new AosAttributes(this, reader); + else + m_AosAttributes = new AosAttributes(this); + + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses = new AosSkillBonuses(this, reader); + else + m_AosSkillBonuses = new AosSkillBonuses(this); + + // Backward compatibility + if (GetSaveFlag(flags, SaveFlag.Owner)) + BlessedFor = reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.Protection)) + m_Protection = new TalismanAttribute(reader); + else + m_Protection = new TalismanAttribute(); + + if (GetSaveFlag(flags, SaveFlag.Killer)) + m_Killer = new TalismanAttribute(reader); + else + m_Killer = new TalismanAttribute(); + + if (GetSaveFlag(flags, SaveFlag.Summoner)) + m_Summoner = new TalismanAttribute(reader); + else + m_Summoner = new TalismanAttribute(); + + if (GetSaveFlag(flags, SaveFlag.Removal)) + m_Removal = (TalismanRemoval)reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.OldKarmaLoss)) + m_AosAttributes.IncreasedKarmaLoss = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Skill)) + m_Skill = (SkillName)reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.SuccessBonus)) + m_SuccessBonus = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.ExceptionalBonus)) + m_ExceptionalBonus = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.MaxCharges)) + m_MaxCharges = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Charges)) + m_Charges = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.MaxChargeTime)) + m_MaxChargeTime = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.ChargeTime)) + m_ChargeTime = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Slayer)) + m_Slayer = (TalismanSlayerName)reader.ReadEncodedInt(); + + m_Blessed = GetSaveFlag(flags, SaveFlag.Blessed); + + break; + } + } + + if (Parent is Mobile m) + { + m_AosAttributes.AddStatBonuses(m); + m_AosSkillBonuses.AddTo(m); + + if (m_ChargeTime > 0) + StartTimer(); + } + } + + public virtual void OnAfterUse(Mobile m) + { + m_ChargeTime = m_MaxChargeTime; + + if (m_Charges > 0 && m_MaxCharges > 0) + m_Charges -= 1; + + if (m_ChargeTime > 0) + StartTimer(); + + InvalidateProperties(); + } + + public virtual Type GetSummoner() + { + return null; + } + + public virtual void SetSummoner(Type type, TextDefinition name) + { + m_Summoner = new TalismanAttribute(type, name); + } + + public virtual void SetProtection(Type type, TextDefinition name, int amount) + { + m_Protection = new TalismanAttribute(type, name, amount); + } + + public virtual void SetKiller(Type type, TextDefinition name, int amount) + { + m_Killer = new TalismanAttribute(type, name, amount); + } + + [Flags] + private enum SaveFlag + { + None = 0x00000000, + Attributes = 0x00000001, + SkillBonuses = 0x00000002, + Owner = 0x00000004, + Protection = 0x00000008, + Killer = 0x00000010, + Summoner = 0x00000020, + Removal = 0x00000040, + OldKarmaLoss = 0x00000080, + Skill = 0x00000100, + SuccessBonus = 0x00000200, + ExceptionalBonus = 0x00000400, + MaxCharges = 0x00000800, + Charges = 0x00001000, + MaxChargeTime = 0x00002000, + ChargeTime = 0x00004000, + Blessed = 0x00008000, + Slayer = 0x00010000 + } + + private class TalismanTarget : Target + { + private BaseTalisman m_Talisman; + + public TalismanTarget(BaseTalisman talisman) + : base(12, false, TargetFlags.Beneficial) + { + m_Talisman = talisman; + } + + protected override void OnTarget(Mobile from, object o) + { + if (m_Talisman == null || m_Talisman.Deleted) + return; + + Mobile target = o as Mobile; + + if (from.Talisman != m_Talisman) + { + from.SendLocalizedMessage(502641); // You must equip this item to use it. + } + else if (target == null) + { + from.SendLocalizedMessage(1046439); // That is not a valid target. + } + else if (m_Talisman.ChargeTime > 0) + { + from.SendLocalizedMessage(1074882, + m_Talisman.ChargeTime.ToString()); // You must wait ~1_val~ seconds for this to recharge. + } + else if (m_Talisman.Charges == 0 && m_Talisman.MaxCharges > 0) + { + from.SendLocalizedMessage(1042544); // This item is out of charges. + } + else + { + switch (m_Talisman.Removal) + { + case TalismanRemoval.Curse: + target.PlaySound(0xF6); + target.PlaySound(0x1F7); + target.FixedParticles(0x3709, 1, 30, 9963, 13, 3, EffectLayer.Head); + + IEntity mfrom = new Entity(Serial.Zero, new Point3D(target.X, target.Y, target.Z - 10), + from.Map); + IEntity mto = new Entity(Serial.Zero, new Point3D(target.X, target.Y, target.Z + 50), from.Map); + Effects.SendMovingParticles(mfrom, mto, 0x2255, 1, 0, false, false, 13, 3, 9501, 1, 0, + EffectLayer.Head, 0x100); + + StatMod mod; + + mod = target.GetStatMod("[Magic] Str Offset"); + if (mod != null && mod.Offset < 0) + target.RemoveStatMod("[Magic] Str Offset"); + + mod = target.GetStatMod("[Magic] Dex Offset"); + if (mod != null && mod.Offset < 0) + target.RemoveStatMod("[Magic] Dex Offset"); + + mod = target.GetStatMod("[Magic] Int Offset"); + if (mod != null && mod.Offset < 0) + target.RemoveStatMod("[Magic] Int Offset"); + + target.Paralyzed = false; + + EvilOmenSpell.TryEndEffect(target); + StrangleSpell.RemoveCurse(target); + CorpseSkinSpell.RemoveCurse(target); + CurseSpell.RemoveEffect(target); + + BuffInfo.RemoveBuff(target, BuffIcon.Clumsy); + BuffInfo.RemoveBuff(target, BuffIcon.FeebleMind); + BuffInfo.RemoveBuff(target, BuffIcon.Weaken); + BuffInfo.RemoveBuff(target, BuffIcon.MassCurse); + + target.SendLocalizedMessage(1072408); // Any curses on you have been lifted + + if (target != from) + from.SendLocalizedMessage(1072409); // Your targets curses have been lifted + + break; + case TalismanRemoval.Damage: + target.PlaySound(0x201); + Effects.SendLocationParticles( + EffectItem.Create(target.Location, target.Map, EffectItem.DefaultDuration), 0x3728, 1, 13, + 0x834, 0, 0x13B2, 0); + + BleedAttack.EndBleed(target, true); + MortalStrike.EndWound(target); + + BuffInfo.RemoveBuff(target, BuffIcon.Bleed); + BuffInfo.RemoveBuff(target, BuffIcon.MortalStrike); + + target.SendLocalizedMessage(1072405); // Your lasting damage effects have been removed! + + if (target != from) + from.SendLocalizedMessage(1072406); // Your Targets lasting damage effects have been removed! + + break; + case TalismanRemoval.Ward: + target.PlaySound(0x201); + Effects.SendLocationParticles( + EffectItem.Create(target.Location, target.Map, EffectItem.DefaultDuration), 0x3728, 1, 13, + 0x834, 0, 0x13B2, 0); + + MagicReflectSpell.EndReflect(target); + ReactiveArmorSpell.EndArmor(target); + ProtectionSpell.EndProtection(target); + + target.SendLocalizedMessage(1072402); // Your wards have been removed! + + if (target != from) + from.SendLocalizedMessage(1072403); // Your target's wards have been removed! + + break; + case TalismanRemoval.Wildfire: + // TODO + break; + } + + m_Talisman.OnAfterUse(from); + } + } + } + + #region Slayer + + private TalismanSlayerName m_Slayer; + + [CommandProperty(AccessLevel.GameMaster)] + public TalismanSlayerName Slayer + { + get => m_Slayer; + set + { + m_Slayer = value; + InvalidateProperties(); + } + } + + #endregion + + #region Summoner/Removal + + private TalismanAttribute m_Summoner; + private TalismanRemoval m_Removal; + private Mobile m_Creature; + + [CommandProperty(AccessLevel.GameMaster)] + public TalismanAttribute Summoner + { + get => m_Summoner; + set + { + m_Summoner = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TalismanRemoval Removal + { + get => m_Removal; + set + { + m_Removal = value; + InvalidateProperties(); + } + } + + #endregion + + #region Protection/Killer + + private TalismanAttribute m_Protection; + private TalismanAttribute m_Killer; + + [CommandProperty(AccessLevel.GameMaster)] + public TalismanAttribute Protection + { + get => m_Protection; + set + { + m_Protection = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TalismanAttribute Killer + { + get => m_Killer; + set + { + m_Killer = value; + InvalidateProperties(); + } + } + + #endregion + + #region Craft bonuses + + private SkillName m_Skill; + private int m_SuccessBonus; + private int m_ExceptionalBonus; + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill + { + get => m_Skill; + set + { + m_Skill = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SuccessBonus + { + get => m_SuccessBonus; + set + { + m_SuccessBonus = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ExceptionalBonus + { + get => m_ExceptionalBonus; + set + { + m_ExceptionalBonus = value; + InvalidateProperties(); + } + } + + #endregion + + #region AOS bonuses + + private AosAttributes m_AosAttributes; + private AosSkillBonuses m_AosSkillBonuses; + + [CommandProperty(AccessLevel.GameMaster)] + public AosAttributes Attributes + { + get => m_AosAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosSkillBonuses SkillBonuses + { + get => m_AosSkillBonuses; + set { } + } + + #endregion + + #region Timer + + private Timer m_Timer; + + public virtual void StartTimer() + { + if (m_Timer == null || !m_Timer.Running) + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(10), TimeSpan.FromSeconds(10), Slice); + } + + public virtual void StopTimer() + { + m_Timer?.Stop(); + + m_Timer = null; + } + + public virtual void Slice() + { + if (m_ChargeTime - 10 > 0) + { + m_ChargeTime -= 10; + } + else + { + m_ChargeTime = 0; + + StopTimer(); + } + + InvalidateProperties(); + } + + #endregion + + #region Randomize + + private static int[] m_ItemIDs = + { + 0x2F58, 0x2F59, 0x2F5A, 0x2F5B + }; + + public static int GetRandomItemID() + { + return Utility.RandomList(m_ItemIDs); + } + + private static Type[] m_Summons = + { + typeof(SummonedAntLion), + typeof(SummonedCow), + typeof(SummonedLavaSerpent), + typeof(SummonedOrcBrute), + typeof(SummonedFrostSpider), + typeof(SummonedPanther), + typeof(SummonedDoppleganger), + typeof(SummonedGreatHart), + typeof(SummonedBullFrog), + typeof(SummonedArcticOgreLord), + typeof(SummonedBogling), + typeof(SummonedBakeKitsune), + typeof(SummonedSheep), + typeof(SummonedSkeletalKnight), + typeof(SummonedWailingBanshee), + typeof(SummonedChicken), + typeof(SummonedVorpalBunny), + + typeof(Board), + typeof(IronIngot), + typeof(Bandage) + }; + + private static int[] m_SummonLabels = + { + 1075211, // Ant Lion + 1072494, // Cow + 1072434, // Lava Serpent + 1072414, // Orc Brute + 1072476, // Frost Spider + 1029653, // Panther + 1029741, // Doppleganger + 1018292, // great hart + 1028496, // bullfrog + 1018227, // arctic ogre lord + 1029735, // Bogling + 1030083, // bake-kitsune + 1018285, // sheep + 1018239, // skeletal knight + 1072399, // Wailing Banshee + 1072459, // Chicken + 1072401, // Vorpal Bunny + + 1015101, // Boards + 1044036, // Ingots + 1023817 // clean bandage + }; + + public static Type GetRandomSummonType() + { + return m_Summons[Utility.Random(m_Summons.Length)]; + } + + public static TalismanAttribute GetRandomSummoner() + { + if (0.025 > Utility.RandomDouble()) + { + int num = Utility.Random(m_Summons.Length); + + if (num > 14) + return new TalismanAttribute(m_Summons[num], m_SummonLabels[num], 10); + return new TalismanAttribute(m_Summons[num], m_SummonLabels[num]); + } + + return new TalismanAttribute(); + } + + public static TalismanRemoval GetRandomRemoval() + { + if (0.65 > Utility.RandomDouble()) + return (TalismanRemoval)Utility.RandomList(390, 404, 407); + + return TalismanRemoval.None; + } + + private static Type[] m_Killers = + { + typeof(OrcBomber), typeof(OrcBrute), typeof(SewerRat), typeof(Rat), typeof(GiantRat), + typeof(Ratman), typeof(RatmanArcher), typeof(GiantSpider), typeof(FrostSpider), typeof(GiantBlackWidow), + typeof(DreadSpider), typeof(SilverSerpent), typeof(DeepSeaSerpent), typeof(GiantSerpent), typeof(Snake), + typeof(IceSnake), typeof(IceSerpent), typeof(LavaSerpent), typeof(LavaSnake), typeof(Yamandon), + typeof(StrongMongbat), typeof(Mongbat), typeof(VampireBat), typeof(Lich), typeof(EvilMage), + typeof(LichLord), typeof(EvilMageLord), typeof(SkeletalMage), typeof(KhaldunZealot), typeof(AncientLich), + typeof(JukaMage), typeof(MeerMage), typeof(Beetle), typeof(DeathwatchBeetle), typeof(RuneBeetle), + typeof(FireBeetle), typeof(DeathwatchBeetleHatchling), typeof(Bird), typeof(Chicken), typeof(Eagle), + typeof(TropicalBird), typeof(Phoenix), typeof(DesertOstard), typeof(FrenziedOstard), typeof(ForestOstard), + typeof(Crane), typeof(SnowLeopard), typeof(IceFiend), typeof(FrostOoze), typeof(FrostTroll), + typeof(IceElemental), typeof(SnowElemental), typeof(GiantIceWorm), typeof(LadyOfTheSnow), typeof(FireElemental), + typeof(FireSteed), typeof(HellHound), typeof(HellCat), typeof(PredatorHellCat), typeof(LavaLizard), + typeof(FireBeetle), typeof(Cow), typeof(Bull), typeof(Gaman) //, typeof( Minotaur) + // TODO Meraktus, Tormented Minotaur, Minotaur + }; + + private static int[] m_KillerLabels = + { + 1072413, 1072414, 1072418, 1072419, 1072420, + 1072421, 1072423, 1072424, 1072425, 1072426, + 1072427, 1072428, 1072429, 1072430, 1072431, + 1072432, 1072433, 1072434, 1072435, 1072438, + 1072440, 1072441, 1072443, 1072444, 1072445, + 1072446, 1072447, 1072448, 1072449, 1072450, + 1072451, 1072452, 1072453, 1072454, 1072455, + 1072456, 1072457, 1072458, 1072459, 1072461, + 1072462, 1072465, 1072468, 1072469, 1072470, + 1072473, 1072474, 1072477, 1072478, 1072479, + 1072480, 1072481, 1072483, 1072485, 1072486, + 1072487, 1072489, 1072490, 1072491, 1072492, + 1072493, 1072494, 1072495, 1072498 + }; + + public static TalismanAttribute GetRandomKiller() + { + return GetRandomKiller(true); + } + + public static TalismanAttribute GetRandomKiller(bool includingNone) + { + if (includingNone && Utility.RandomBool()) + return new TalismanAttribute(); + + int num = Utility.Random(m_Killers.Length); + + return new TalismanAttribute(m_Killers[num], m_KillerLabels[num], Utility.RandomMinMax(10, 100)); + } + + public static TalismanAttribute GetRandomProtection() + { + return GetRandomProtection(true); + } + + public static TalismanAttribute GetRandomProtection(bool includingNone) + { + if (includingNone && Utility.RandomBool()) + return new TalismanAttribute(); + + int num = Utility.Random(m_Killers.Length); + + return new TalismanAttribute(m_Killers[num], m_KillerLabels[num], Utility.RandomMinMax(5, 60)); + } + + private static SkillName[] m_Skills = + { + SkillName.Alchemy, + SkillName.Blacksmith, + SkillName.Carpentry, + SkillName.Cartography, + SkillName.Cooking, + SkillName.Fletching, + SkillName.Inscribe, + SkillName.Tailoring, + SkillName.Tinkering + }; + + public static SkillName GetRandomSkill() + { + return m_Skills[Utility.Random(m_Skills.Length)]; + } + + public static int GetRandomExceptional() + { + if (0.3 > Utility.RandomDouble()) + { + double num = 40 - Math.Log(Utility.RandomMinMax(7, 403)) * 5; + + return (int)Math.Round(num); + } + + return 0; + } + + public static int GetRandomSuccessful() + { + if (0.75 > Utility.RandomDouble()) + { + double num = 40 - Math.Log(Utility.RandomMinMax(7, 403)) * 5; + + return (int)Math.Round(num); + } + + return 0; + } + + public static bool GetRandomBlessed() + { + if (0.02 > Utility.RandomDouble()) + return true; + + return false; + } + + public static TalismanSlayerName GetRandomSlayer() + { + if (0.01 > Utility.RandomDouble()) + return (TalismanSlayerName)Utility.RandomMinMax(1, 9); + + return TalismanSlayerName.None; + } + + public static int GetRandomCharges() + { + if (0.5 > Utility.RandomDouble()) + return Utility.RandomMinMax(10, 50); + + return 0; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/Items/EnchantedSwitch.cs b/Scripts/Items/Talismans/Items/EnchantedSwitch.cs index 92d06a056..24e0498bf 100644 --- a/Scripts/Items/Talismans/Items/EnchantedSwitch.cs +++ b/Scripts/Items/Talismans/Items/EnchantedSwitch.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class EnchantedSwitch : Item - { - public override int LabelNumber => 1072893; // enchanted switch + public class EnchantedSwitch : Item + { + [Constructible] + public EnchantedSwitch() : base(0x2F5C) + { + Weight = 1.0; + } - [Constructible] - public EnchantedSwitch() : base( 0x2F5C ) - { - Weight = 1.0; - } + public EnchantedSwitch(Serial serial) : base(serial) + { + } - public EnchantedSwitch( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072893; // enchanted switch - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/Items/HollowPrism.cs b/Scripts/Items/Talismans/Items/HollowPrism.cs index f5f6e4321..accf931af 100644 --- a/Scripts/Items/Talismans/Items/HollowPrism.cs +++ b/Scripts/Items/Talismans/Items/HollowPrism.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class HollowPrism : Item - { - public override int LabelNumber => 1072895; // hollow prism + public class HollowPrism : Item + { + [Constructible] + public HollowPrism() : base(0x2F5D) + { + Weight = 1.0; + } - [Constructible] - public HollowPrism() : base( 0x2F5D ) - { - Weight = 1.0; - } + public HollowPrism(Serial serial) : base(serial) + { + } - public HollowPrism( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072895; // hollow prism - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/Items/JeweledFiligree.cs b/Scripts/Items/Talismans/Items/JeweledFiligree.cs index c491b5dc4..3141ffb00 100644 --- a/Scripts/Items/Talismans/Items/JeweledFiligree.cs +++ b/Scripts/Items/Talismans/Items/JeweledFiligree.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class JeweledFiligree : Item - { - public override int LabelNumber => 1072894; // jeweled filigree + public class JeweledFiligree : Item + { + [Constructible] + public JeweledFiligree() : base(0x2F5E) + { + Weight = 1.0; + } - [Constructible] - public JeweledFiligree() : base( 0x2F5E ) - { - Weight = 1.0; - } + public JeweledFiligree(Serial serial) : base(serial) + { + } - public JeweledFiligree( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072894; // jeweled filigree - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/Items/RunedPrism.cs b/Scripts/Items/Talismans/Items/RunedPrism.cs index 5634d48fd..79542f684 100644 --- a/Scripts/Items/Talismans/Items/RunedPrism.cs +++ b/Scripts/Items/Talismans/Items/RunedPrism.cs @@ -1,32 +1,31 @@ namespace Server.Items { - public class RunedPrism : Item - { - public override int LabelNumber => 1073465; // runed prism + public class RunedPrism : Item + { + [Constructible] + public RunedPrism() : base(0x2F57) + { + Weight = 1.0; + } - [Constructible] - public RunedPrism() : base( 0x2F57 ) - { - Weight = 1.0; - } + public RunedPrism(Serial serial) : base(serial) + { + } - public RunedPrism( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073465; // runed prism - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/Items/RunedSwitch.cs b/Scripts/Items/Talismans/Items/RunedSwitch.cs index 775fde06a..647233ce6 100644 --- a/Scripts/Items/Talismans/Items/RunedSwitch.cs +++ b/Scripts/Items/Talismans/Items/RunedSwitch.cs @@ -2,74 +2,80 @@ using Server.Targeting; namespace Server.Items { - public class RunedSwitch : Item - { - public override int LabelNumber => 1072896; // runed switch + public class RunedSwitch : Item + { + [Constructible] + public RunedSwitch() : base(0x2F61) + { + Weight = 1.0; + } - [Constructible] - public RunedSwitch() : base( 0x2F61 ) - { - Weight = 1.0; - } + public RunedSwitch(Serial serial) : base(serial) + { + } - public RunedSwitch( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072896; // runed switch - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1075101 ); // Please select an item to recharge. - from.Target = new InternalTarget( this ); - } - else - from.SendLocalizedMessage( 1060640 ); // The item must be in your backpack to use it. - } + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1075101); // Please select an item to recharge. + from.Target = new InternalTarget(this); + } + else + { + from.SendLocalizedMessage(1060640); // The item must be in your backpack to use it. + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - private class InternalTarget : Target - { - private RunedSwitch m_Item; + private class InternalTarget : Target + { + private RunedSwitch m_Item; - public InternalTarget( RunedSwitch item ) : base( 0, false, TargetFlags.None ) - { - m_Item = item; - } + public InternalTarget(RunedSwitch item) : base(0, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( m_Item == null || m_Item.Deleted ) - return; - - if ( o is BaseTalisman talisman ) - { - if ( talisman.Charges == 0 ) - { - talisman.Charges = talisman.MaxCharges; - m_Item.Delete(); - from.SendLocalizedMessage( 1075100 ); // The item has been recharged. - } - else - from.SendLocalizedMessage( 1075099 ); // You cannot recharge that item until all of its current charges have been used. - } - else - from.SendLocalizedMessage( 1046439 ); // That is not a valid target. - } - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (m_Item == null || m_Item.Deleted) + return; + if (o is BaseTalisman talisman) + { + if (talisman.Charges == 0) + { + talisman.Charges = talisman.MaxCharges; + m_Item.Delete(); + from.SendLocalizedMessage(1075100); // The item has been recharged. + } + else + { + from.SendLocalizedMessage( + 1075099); // You cannot recharge that item until all of its current charges have been used. + } + } + else + { + from.SendLocalizedMessage(1046439); // That is not a valid target. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/RandomTalisman.cs b/Scripts/Items/Talismans/RandomTalisman.cs index c60baefb8..a45fce10e 100644 --- a/Scripts/Items/Talismans/RandomTalisman.cs +++ b/Scripts/Items/Talismans/RandomTalisman.cs @@ -1,58 +1,58 @@ namespace Server.Items { - public class RandomTalisman : BaseTalisman - { - [Constructible] - public RandomTalisman() : base( GetRandomItemID() ) - { - Summoner = GetRandomSummoner(); + public class RandomTalisman : BaseTalisman + { + [Constructible] + public RandomTalisman() : base(GetRandomItemID()) + { + Summoner = GetRandomSummoner(); - if ( Summoner.IsEmpty ) - { - Removal = GetRandomRemoval(); + if (Summoner.IsEmpty) + { + Removal = GetRandomRemoval(); - if ( Removal != TalismanRemoval.None ) - { - MaxCharges = GetRandomCharges(); - MaxChargeTime = 1200; - } - } - else - { - MaxCharges = Utility.RandomMinMax( 10, 50 ); + if (Removal != TalismanRemoval.None) + { + MaxCharges = GetRandomCharges(); + MaxChargeTime = 1200; + } + } + else + { + MaxCharges = Utility.RandomMinMax(10, 50); - if ( Summoner.IsItem ) - MaxChargeTime = 60; - else - MaxChargeTime = 1800; - } + if (Summoner.IsItem) + MaxChargeTime = 60; + else + MaxChargeTime = 1800; + } - Blessed = GetRandomBlessed(); - Slayer = GetRandomSlayer(); - Protection = GetRandomProtection(); - Killer = GetRandomKiller(); - Skill = GetRandomSkill(); - ExceptionalBonus = GetRandomExceptional(); - SuccessBonus = GetRandomSuccessful(); - Charges = MaxCharges; - } + Blessed = GetRandomBlessed(); + Slayer = GetRandomSlayer(); + Protection = GetRandomProtection(); + Killer = GetRandomKiller(); + Skill = GetRandomSkill(); + ExceptionalBonus = GetRandomExceptional(); + SuccessBonus = GetRandomSuccessful(); + Charges = MaxCharges; + } - public RandomTalisman( Serial serial ) : base( serial ) - { - } + public RandomTalisman(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/TalismanAttribute.cs b/Scripts/Items/Talismans/TalismanAttribute.cs index 19ff251c0..87321e1b5 100644 --- a/Scripts/Items/Talismans/TalismanAttribute.cs +++ b/Scripts/Items/Talismans/TalismanAttribute.cs @@ -2,121 +2,121 @@ using System; namespace Server.Items { - [PropertyObject] - public class TalismanAttribute - { - [CommandProperty( AccessLevel.GameMaster )] - public Type Type { get; set; } + [PropertyObject] + public class TalismanAttribute + { + public TalismanAttribute() : this(null, 0, 0) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public TextDefinition Name { get; set; } + public TalismanAttribute(TalismanAttribute copy) + { + if (copy != null) + { + Type = copy.Type; + Name = copy.Name; + Amount = copy.Amount; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public int Amount { get; set; } + public TalismanAttribute(Type type, TextDefinition name) : this(type, name, 0) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsEmpty => Type == null; + public TalismanAttribute(Type type, TextDefinition name, int amount) + { + Type = type; + Name = name; + Amount = amount; + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsItem => Type != null && Type.Namespace.Equals( "Server.Items" ); + public TalismanAttribute(GenericReader reader) + { + int version = reader.ReadInt(); - public TalismanAttribute() : this( null, 0, 0 ) - { - } + SaveFlag flags = (SaveFlag)reader.ReadEncodedInt(); - public TalismanAttribute( TalismanAttribute copy ) - { - if ( copy != null ) - { - Type = copy.Type; - Name = copy.Name; - Amount = copy.Amount; - } - } + if (GetSaveFlag(flags, SaveFlag.Type)) + Type = ScriptCompiler.FindTypeByFullName(reader.ReadString(), false); - public TalismanAttribute( Type type, TextDefinition name ) : this( type, name, 0 ) - { - } + if (GetSaveFlag(flags, SaveFlag.Name)) + Name = TextDefinition.Deserialize(reader); - public TalismanAttribute( Type type, TextDefinition name, int amount ) - { - Type = type; - Name = name; - Amount = amount; - } + if (GetSaveFlag(flags, SaveFlag.Amount)) + Amount = reader.ReadEncodedInt(); + } - public TalismanAttribute( GenericReader reader ) - { - int version = reader.ReadInt(); + [CommandProperty(AccessLevel.GameMaster)] + public Type Type{ get; set; } - SaveFlag flags = (SaveFlag) reader.ReadEncodedInt(); + [CommandProperty(AccessLevel.GameMaster)] + public TextDefinition Name{ get; set; } - if ( GetSaveFlag( flags, SaveFlag.Type ) ) - Type = ScriptCompiler.FindTypeByFullName( reader.ReadString(), false ); + [CommandProperty(AccessLevel.GameMaster)] + public int Amount{ get; set; } - if ( GetSaveFlag( flags, SaveFlag.Name ) ) - Name = TextDefinition.Deserialize( reader ); + [CommandProperty(AccessLevel.GameMaster)] + public bool IsEmpty => Type == null; - if ( GetSaveFlag( flags, SaveFlag.Amount ) ) - Amount = reader.ReadEncodedInt(); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsItem => Type != null && Type.Namespace.Equals("Server.Items"); - public override string ToString() - { - if ( Type != null ) - return Type.Name; + public override string ToString() + { + if (Type != null) + return Type.Name; - return "None"; - } + return "None"; + } - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } - [Flags] - private enum SaveFlag - { - None = 0x00000000, - Type = 0x00000001, - Name = 0x00000002, - Amount = 0x00000004, - } + public virtual void Serialize(GenericWriter writer) + { + writer.Write(0); // version - public virtual void Serialize( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version + SaveFlag flags = SaveFlag.None; - SaveFlag flags = SaveFlag.None; + SetSaveFlag(ref flags, SaveFlag.Type, Type != null); + SetSaveFlag(ref flags, SaveFlag.Name, Name != null); + SetSaveFlag(ref flags, SaveFlag.Amount, Amount != 0); - SetSaveFlag( ref flags, SaveFlag.Type, Type != null ); - SetSaveFlag( ref flags, SaveFlag.Name, Name != null ); - SetSaveFlag( ref flags, SaveFlag.Amount, Amount != 0 ); + writer.WriteEncodedInt((int)flags); - writer.WriteEncodedInt( (int) flags ); + if (GetSaveFlag(flags, SaveFlag.Type)) + writer.Write(Type.FullName); - if ( GetSaveFlag( flags, SaveFlag.Type ) ) - writer.Write( Type.FullName ); + if (GetSaveFlag(flags, SaveFlag.Name)) + TextDefinition.Serialize(writer, Name); - if ( GetSaveFlag( flags, SaveFlag.Name ) ) - TextDefinition.Serialize( writer, Name ); + if (GetSaveFlag(flags, SaveFlag.Amount)) + writer.WriteEncodedInt(Amount); + } - if ( GetSaveFlag( flags, SaveFlag.Amount ) ) - writer.WriteEncodedInt( Amount ); - } + public int DamageBonus(Mobile to) + { + if (to != null && to.GetType() == Type) // Verified: only works on the exact type + return Amount; - public int DamageBonus( Mobile to ) - { - if ( to != null && to.GetType() == Type ) // Verified: only works on the exact type - return Amount; + return 0; + } - return 0; - } - } -} + [Flags] + private enum SaveFlag + { + None = 0x00000000, + Type = 0x00000001, + Name = 0x00000002, + Amount = 0x00000004 + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/TalismanSlayer.cs b/Scripts/Items/Talismans/TalismanSlayer.cs index c7311925f..c9684080d 100644 --- a/Scripts/Items/Talismans/TalismanSlayer.cs +++ b/Scripts/Items/Talismans/TalismanSlayer.cs @@ -4,110 +4,108 @@ using Server.Mobiles; namespace Server.Items { - public enum TalismanSlayerName - { - None, - Bear, - Vermin, - Bat, - Mage, - Beetle, - Bird, - Ice, - Flame, - Bovine - } + public enum TalismanSlayerName + { + None, + Bear, + Vermin, + Bat, + Mage, + Beetle, + Bird, + Ice, + Flame, + Bovine + } - public static class TalismanSlayer - { - private static Dictionary m_Table = new Dictionary(); + public static class TalismanSlayer + { + private static Dictionary m_Table = new Dictionary(); - public static void Initialize() - { - m_Table[ TalismanSlayerName.Bear ] = new[] - { - typeof( GrizzlyBear ), typeof( BlackBear ), typeof( BrownBear ), typeof( PolarBear ) //, typeof( Grobu ) - }; + public static void Initialize() + { + m_Table[TalismanSlayerName.Bear] = new[] + { + typeof(GrizzlyBear), typeof(BlackBear), typeof(BrownBear), typeof(PolarBear) //, typeof( Grobu ) + }; - m_Table[ TalismanSlayerName.Vermin ] = new[] - { - typeof( RatmanMage ), typeof( RatmanMage ), typeof( RatmanArcher ), typeof( Barracoon), - typeof( Ratman ), typeof( SewerRat ), typeof( Rat ), typeof( GiantRat ) //, typeof( Chiikkaha ) - }; + m_Table[TalismanSlayerName.Vermin] = new[] + { + typeof(RatmanMage), typeof(RatmanMage), typeof(RatmanArcher), typeof(Barracoon), + typeof(Ratman), typeof(SewerRat), typeof(Rat), typeof(GiantRat) //, typeof( Chiikkaha ) + }; - m_Table[ TalismanSlayerName.Bat ] = new[] - { - typeof( Mongbat ), typeof( StrongMongbat ), typeof( VampireBat ) - }; + m_Table[TalismanSlayerName.Bat] = new[] + { + typeof(Mongbat), typeof(StrongMongbat), typeof(VampireBat) + }; - m_Table[ TalismanSlayerName.Mage ] = new[] - { - typeof( EvilMage ), typeof( EvilMageLord ), typeof( AncientLich ), typeof( Lich ), typeof( LichLord ), - typeof( SkeletalMage ), typeof( BoneMagi ), typeof( OrcishMage ), typeof( KhaldunZealot ), typeof( JukaMage ), - }; + m_Table[TalismanSlayerName.Mage] = new[] + { + typeof(EvilMage), typeof(EvilMageLord), typeof(AncientLich), typeof(Lich), typeof(LichLord), + typeof(SkeletalMage), typeof(BoneMagi), typeof(OrcishMage), typeof(KhaldunZealot), typeof(JukaMage) + }; - m_Table[ TalismanSlayerName.Beetle ] = new[] - { - typeof( Beetle ), typeof( RuneBeetle ), typeof( FireBeetle ), typeof( DeathwatchBeetle ), - typeof( DeathwatchBeetleHatchling ) - }; + m_Table[TalismanSlayerName.Beetle] = new[] + { + typeof(Beetle), typeof(RuneBeetle), typeof(FireBeetle), typeof(DeathwatchBeetle), + typeof(DeathwatchBeetleHatchling) + }; - m_Table[ TalismanSlayerName.Bird ] = new[] - { - typeof( Bird ), typeof( TropicalBird ), typeof( Chicken ), typeof( Crane ), - typeof( DesertOstard ), typeof( Eagle ), typeof( ForestOstard ), typeof( FrenziedOstard ), - typeof( Phoenix ), /*typeof( Pyre ), typeof( Swoop ), typeof( Saliva ),*/ typeof( Harpy ), - typeof( StoneHarpy ) // ????? - }; + m_Table[TalismanSlayerName.Bird] = new[] + { + typeof(Bird), typeof(TropicalBird), typeof(Chicken), typeof(Crane), + typeof(DesertOstard), typeof(Eagle), typeof(ForestOstard), typeof(FrenziedOstard), + typeof(Phoenix), /*typeof( Pyre ), typeof( Swoop ), typeof( Saliva ),*/ typeof(Harpy), + typeof(StoneHarpy) // ????? + }; - m_Table[ TalismanSlayerName.Ice ] = new[] - { - typeof( ArcticOgreLord ), typeof( IceElemental ), typeof( SnowElemental ), typeof( FrostOoze ), - typeof( IceFiend ), /*typeof( UnfrozenMummy ),*/ typeof( FrostSpider ), typeof( LadyOfTheSnow ), - typeof( FrostTroll ), + m_Table[TalismanSlayerName.Ice] = new[] + { + typeof(ArcticOgreLord), typeof(IceElemental), typeof(SnowElemental), typeof(FrostOoze), + typeof(IceFiend), /*typeof( UnfrozenMummy ),*/ typeof(FrostSpider), typeof(LadyOfTheSnow), + typeof(FrostTroll), - // TODO WinterReaper, check - typeof( IceSnake ), typeof( SnowLeopard ), typeof( PolarBear ), typeof( IceSerpent ), typeof( GiantIceWorm ) - }; + // TODO WinterReaper, check + typeof(IceSnake), typeof(SnowLeopard), typeof(PolarBear), typeof(IceSerpent), typeof(GiantIceWorm) + }; - m_Table[ TalismanSlayerName.Flame ] = new[] - { - typeof( FireBeetle ), typeof( HellHound ), typeof( LavaSerpent ), typeof( FireElemental ), - typeof( PredatorHellCat ), typeof( Phoenix ), typeof( FireGargoyle ), typeof( HellCat ), - /*typeof( Pyre ),*/ typeof( FireSteed ), typeof( LavaLizard ), + m_Table[TalismanSlayerName.Flame] = new[] + { + typeof(FireBeetle), typeof(HellHound), typeof(LavaSerpent), typeof(FireElemental), + typeof(PredatorHellCat), typeof(Phoenix), typeof(FireGargoyle), typeof(HellCat), + /*typeof( Pyre ),*/ typeof(FireSteed), typeof(LavaLizard), - // TODO check - typeof( LavaSnake ), - }; + // TODO check + typeof(LavaSnake) + }; - m_Table[ TalismanSlayerName.Bovine ] = new[] - { - typeof( Cow ), typeof( Bull ), typeof( Gaman ) /*, typeof( MinotaurCaptain ), + m_Table[TalismanSlayerName.Bovine] = new[] + { + typeof(Cow), typeof(Bull), typeof(Gaman) /*, typeof( MinotaurCaptain ), typeof( MinotaurScout ), typeof( Minotaur )*/ - // TODO TormentedMinotaur - }; - } + // TODO TormentedMinotaur + }; + } - public static bool Slays( TalismanSlayerName name, Mobile m ) - { - if ( !m_Table.ContainsKey( name ) ) - return false; + public static bool Slays(TalismanSlayerName name, Mobile m) + { + if (!m_Table.ContainsKey(name)) + return false; - Type[] types = m_Table[ name ]; + Type[] types = m_Table[name]; - if ( types == null || m == null ) - return false; + if (types == null || m == null) + return false; - Type type = m.GetType(); + Type type = m.GetType(); - for ( int i = 0; i < types.Length; i++ ) - { - if ( types[ i ].IsAssignableFrom( type ) ) - return true; - } + for (int i = 0; i < types.Length; i++) + if (types[i].IsAssignableFrom(type)) + return true; - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Talismans/TalismanSummons.cs b/Scripts/Items/Talismans/TalismanSummons.cs index 510d9f8cf..259c7186e 100644 --- a/Scripts/Items/Talismans/TalismanSummons.cs +++ b/Scripts/Items/Talismans/TalismanSummons.cs @@ -1,637 +1,637 @@ using System; using System.Collections.Generic; - using Server.ContextMenus; using Server.Items; -using BunnyHole = Server.Mobiles.VorpalBunny.BunnyHole; - namespace Server.Mobiles { - public class BaseTalismanSummon : BaseCreature - { - public override bool Commandable => false; - public override bool InitialInnocent => true; - //public override bool IsInvulnerable => true; // TODO: Wailing banshees are NOT invulnerable, are any of the others? - - public BaseTalismanSummon() : base( AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4 ) - { - // TODO: Stats/skills - } - - public BaseTalismanSummon( Serial serial ) : base( serial ) - { - } - - public override void AddCustomContextEntries( Mobile from, List list ) - { - if ( from.Alive && ControlMaster == from ) - list.Add( new TalismanReleaseEntry( this ) ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - - private class TalismanReleaseEntry : ContextMenuEntry - { - private Mobile m_Mobile; - - public TalismanReleaseEntry( Mobile m ) : base( 6118, 3 ) - { - m_Mobile = m; - } - - public override void OnClick() - { - Effects.SendLocationParticles( EffectItem.Create( m_Mobile.Location, m_Mobile.Map, EffectItem.DefaultDuration ), 0x3728, 8, 20, 5042 ); - Effects.PlaySound( m_Mobile, m_Mobile.Map, 0x201 ); - - m_Mobile.Delete(); - } - } - } - - public class SummonedAntLion : BaseTalismanSummon - { - public override string DefaultName => "an ant lion"; - - [Constructible] - public SummonedAntLion() - { - Body = 787; - BaseSoundID = 1006; - } - - public SummonedAntLion( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedArcticOgreLord : BaseTalismanSummon - { - public override string DefaultName => "an arctic ogre lord"; - - [Constructible] - public SummonedArcticOgreLord() : base() - { - Body = 135; - BaseSoundID = 427; - } - - public SummonedArcticOgreLord( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedBakeKitsune : BaseTalismanSummon - { - public override string DefaultName => "a bake kitsune"; - - [Constructible] - public SummonedBakeKitsune() - { - Body = 246; - BaseSoundID = 0x4DD; - } - - public SummonedBakeKitsune( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedBogling : BaseTalismanSummon - { - public override string DefaultName => "a bogling"; - - [Constructible] - public SummonedBogling() - { - Body = 779; - BaseSoundID = 422; - } - - public SummonedBogling( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedBullFrog : BaseTalismanSummon - { - public override string DefaultName => "a bull frog"; - - [Constructible] - public SummonedBullFrog() - { - Body = 81; - Hue = Utility.RandomList( 0x5AC, 0x5A3, 0x59A, 0x591, 0x588, 0x57F ); - BaseSoundID = 0x266; - } - - public SummonedBullFrog( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedChicken : BaseTalismanSummon - { - public override string DefaultName => "a chicken"; - - [Constructible] - public SummonedChicken() - { - Body = 0xD0; - BaseSoundID = 0x6E; - } - - public SummonedChicken( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedCow : BaseTalismanSummon - { - public override string DefaultName => "a cow"; - - [Constructible] - public SummonedCow() - { - Body = Utility.RandomList( 0xD8, 0xE7 ); - BaseSoundID = 0x78; - } - - public SummonedCow( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - public class SummonedDoppleganger : BaseTalismanSummon - { - public override string DefaultName => "a doppleganger"; - - [Constructible] - public SummonedDoppleganger() - { - Body = 0x309; - BaseSoundID = 0x451; - } - - public SummonedDoppleganger( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedFrostSpider : BaseTalismanSummon - { - public override string DefaultName => "a frost spider"; - - [Constructible] - public SummonedFrostSpider() - { - Body = 20; - BaseSoundID = 0x388; - } - - public SummonedFrostSpider( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedGreatHart : BaseTalismanSummon - { - public override string DefaultName => "a great hart"; - - [Constructible] - public SummonedGreatHart() - { - Body = 0xEA; - BaseSoundID = 0x82; - } - - public SummonedGreatHart( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedLavaSerpent : BaseTalismanSummon - { - public override string DefaultName => "a lava serpent"; - - [Constructible] - public SummonedLavaSerpent() - { - Body = 90; - BaseSoundID = 219; - } - - public SummonedLavaSerpent( Serial serial ) : base( serial ) - { - } - - public override void OnThink() - { - /* - if ( m_NextWave < DateTime.UtcNow ) - AreaHeatDamage(); - */ - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - - /* - // An area attack that only damages staff, wtf? - - private DateTime m_NextWave; - - public void AreaHeatDamage() - { - Mobile mob = ControlMaster; - - if ( mob != null ) - { - if ( mob.InRange( Location, 2 ) ) - { - if ( mob.AccessLevel != AccessLevel.Player ) - { - AOS.Damage( mob, Utility.Random( 2, 3 ), 0, 100, 0, 0, 0 ); - mob.SendLocalizedMessage( 1008112 ); // The intense heat is damaging you! - } - } - - GuardedRegion r = Region as GuardedRegion; - - if ( r != null && mob.Alive ) - { - foreach ( Mobile m in GetMobilesInRange( 2 ) ) - { - if ( !mob.CanBeHarmful( m ) ) - mob.CriminalAction( false ); - } - } - } - - m_NextWave = DateTime.UtcNow + TimeSpan.FromSeconds( 3 ); - } - */ - } - - public class SummonedOrcBrute : BaseTalismanSummon - { - public override string DefaultName => "an orc brute"; - - [Constructible] - public SummonedOrcBrute() - { - Body = 189; - BaseSoundID = 0x45A; - } - - public SummonedOrcBrute( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedPanther : BaseTalismanSummon - { - public override string DefaultName => "a panther"; - - [Constructible] - public SummonedPanther() - { - Body = 0xD6; - Hue = 0x901; - BaseSoundID = 0x462; - } - - public SummonedPanther( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedSheep : BaseTalismanSummon - { - public override string DefaultName => "a sheep"; - - [Constructible] - public SummonedSheep() - { - Body = 0xCF; - BaseSoundID = 0xD6; - } - - public SummonedSheep( Serial serial ) : base( serial ) - { - } - - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedSkeletalKnight : BaseTalismanSummon - { - public override string DefaultName => "a skeletal knight"; - - [Constructible] - public SummonedSkeletalKnight() - { - Body = 147; - BaseSoundID = 451; - } - - public SummonedSkeletalKnight( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class SummonedVorpalBunny : BaseTalismanSummon - { - public override string DefaultName => "a vorpal bunny"; - - [Constructible] - public SummonedVorpalBunny() - { - Body = 205; - Hue = 0x480; - BaseSoundID = 0xC9; - - Timer.DelayCall( TimeSpan.FromMinutes( 30.0 ), BeginTunnel ); - } - - public SummonedVorpalBunny( Serial serial ) : base( serial ) - { - } - - public virtual void BeginTunnel() - { - if ( Deleted ) - return; + public class BaseTalismanSummon : BaseCreature + { + //public override bool IsInvulnerable => true; // TODO: Wailing banshees are NOT invulnerable, are any of the others? + + public BaseTalismanSummon() : base(AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4) + { + // TODO: Stats/skills + } + + public BaseTalismanSummon(Serial serial) : base(serial) + { + } + + public override bool Commandable => false; + public override bool InitialInnocent => true; + + public override void AddCustomContextEntries(Mobile from, List list) + { + if (from.Alive && ControlMaster == from) + list.Add(new TalismanReleaseEntry(this)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + + private class TalismanReleaseEntry : ContextMenuEntry + { + private Mobile m_Mobile; + + public TalismanReleaseEntry(Mobile m) : base(6118, 3) + { + m_Mobile = m; + } + + public override void OnClick() + { + Effects.SendLocationParticles(EffectItem.Create(m_Mobile.Location, m_Mobile.Map, EffectItem.DefaultDuration), + 0x3728, 8, 20, 5042); + Effects.PlaySound(m_Mobile, m_Mobile.Map, 0x201); + + m_Mobile.Delete(); + } + } + } + + public class SummonedAntLion : BaseTalismanSummon + { + [Constructible] + public SummonedAntLion() + { + Body = 787; + BaseSoundID = 1006; + } + + public SummonedAntLion(Serial serial) : base(serial) + { + } + + public override string DefaultName => "an ant lion"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedArcticOgreLord : BaseTalismanSummon + { + [Constructible] + public SummonedArcticOgreLord() + { + Body = 135; + BaseSoundID = 427; + } + + public SummonedArcticOgreLord(Serial serial) : base(serial) + { + } + + public override string DefaultName => "an arctic ogre lord"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedBakeKitsune : BaseTalismanSummon + { + [Constructible] + public SummonedBakeKitsune() + { + Body = 246; + BaseSoundID = 0x4DD; + } + + public SummonedBakeKitsune(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a bake kitsune"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedBogling : BaseTalismanSummon + { + [Constructible] + public SummonedBogling() + { + Body = 779; + BaseSoundID = 422; + } + + public SummonedBogling(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a bogling"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedBullFrog : BaseTalismanSummon + { + [Constructible] + public SummonedBullFrog() + { + Body = 81; + Hue = Utility.RandomList(0x5AC, 0x5A3, 0x59A, 0x591, 0x588, 0x57F); + BaseSoundID = 0x266; + } + + public SummonedBullFrog(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a bull frog"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedChicken : BaseTalismanSummon + { + [Constructible] + public SummonedChicken() + { + Body = 0xD0; + BaseSoundID = 0x6E; + } + + public SummonedChicken(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a chicken"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedCow : BaseTalismanSummon + { + [Constructible] + public SummonedCow() + { + Body = Utility.RandomList(0xD8, 0xE7); + BaseSoundID = 0x78; + } + + public SummonedCow(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a cow"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedDoppleganger : BaseTalismanSummon + { + [Constructible] + public SummonedDoppleganger() + { + Body = 0x309; + BaseSoundID = 0x451; + } + + public SummonedDoppleganger(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a doppleganger"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedFrostSpider : BaseTalismanSummon + { + [Constructible] + public SummonedFrostSpider() + { + Body = 20; + BaseSoundID = 0x388; + } + + public SummonedFrostSpider(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a frost spider"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedGreatHart : BaseTalismanSummon + { + [Constructible] + public SummonedGreatHart() + { + Body = 0xEA; + BaseSoundID = 0x82; + } + + public SummonedGreatHart(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a great hart"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedLavaSerpent : BaseTalismanSummon + { + [Constructible] + public SummonedLavaSerpent() + { + Body = 90; + BaseSoundID = 219; + } + + public SummonedLavaSerpent(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a lava serpent"; + + public override void OnThink() + { + /* + if ( m_NextWave < DateTime.UtcNow ) + AreaHeatDamage(); + */ + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + + /* + // An area attack that only damages staff, wtf? + + private DateTime m_NextWave; + + public void AreaHeatDamage() + { + Mobile mob = ControlMaster; + + if ( mob != null ) + { + if ( mob.InRange( Location, 2 ) ) + { + if ( mob.AccessLevel != AccessLevel.Player ) + { + AOS.Damage( mob, Utility.Random( 2, 3 ), 0, 100, 0, 0, 0 ); + mob.SendLocalizedMessage( 1008112 ); // The intense heat is damaging you! + } + } + + GuardedRegion r = Region as GuardedRegion; + + if ( r != null && mob.Alive ) + { + foreach ( Mobile m in GetMobilesInRange( 2 ) ) + { + if ( !mob.CanBeHarmful( m ) ) + mob.CriminalAction( false ); + } + } + } + + m_NextWave = DateTime.UtcNow + TimeSpan.FromSeconds( 3 ); + } + */ + } + + public class SummonedOrcBrute : BaseTalismanSummon + { + [Constructible] + public SummonedOrcBrute() + { + Body = 189; + BaseSoundID = 0x45A; + } + + public SummonedOrcBrute(Serial serial) : base(serial) + { + } + + public override string DefaultName => "an orc brute"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedPanther : BaseTalismanSummon + { + [Constructible] + public SummonedPanther() + { + Body = 0xD6; + Hue = 0x901; + BaseSoundID = 0x462; + } + + public SummonedPanther(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a panther"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedSheep : BaseTalismanSummon + { + [Constructible] + public SummonedSheep() + { + Body = 0xCF; + BaseSoundID = 0xD6; + } + + public SummonedSheep(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a sheep"; + + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedSkeletalKnight : BaseTalismanSummon + { + [Constructible] + public SummonedSkeletalKnight() + { + Body = 147; + BaseSoundID = 451; + } + + public SummonedSkeletalKnight(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a skeletal knight"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedVorpalBunny : BaseTalismanSummon + { + [Constructible] + public SummonedVorpalBunny() + { + Body = 205; + Hue = 0x480; + BaseSoundID = 0xC9; + + Timer.DelayCall(TimeSpan.FromMinutes(30.0), BeginTunnel); + } + + public SummonedVorpalBunny(Serial serial) : base(serial) + { + } - new BunnyHole().MoveToWorld( Location, Map ); - - Frozen = true; - Say( "* The bunny begins to dig a tunnel back to its underground lair *" ); - PlaySound( 0x247 ); - - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), Delete ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } + public override string DefaultName => "a vorpal bunny"; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public virtual void BeginTunnel() + { + if (Deleted) + return; - int version = reader.ReadEncodedInt(); - } - } + new VorpalBunny.BunnyHole().MoveToWorld(Location, Map); + + Frozen = true; + Say("* The bunny begins to dig a tunnel back to its underground lair *"); + PlaySound(0x247); + + Timer.DelayCall(TimeSpan.FromSeconds(5.0), Delete); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } - public class SummonedWailingBanshee : BaseTalismanSummon - { - public override string DefaultName => "a wailing banshee"; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [Constructible] - public SummonedWailingBanshee() - { - Body = 310; - BaseSoundID = 0x482; - } - - public SummonedWailingBanshee( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } + + public class SummonedWailingBanshee : BaseTalismanSummon + { + [Constructible] + public SummonedWailingBanshee() + { + Body = 310; + BaseSoundID = 0x482; + } + + public SummonedWailingBanshee(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a wailing banshee"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/BaseTrap.cs b/Scripts/Items/Traps/BaseTrap.cs index 729b73657..5465c84e4 100644 --- a/Scripts/Items/Traps/BaseTrap.cs +++ b/Scripts/Items/Traps/BaseTrap.cs @@ -2,84 +2,85 @@ using System; namespace Server.Items { - public abstract class BaseTrap : Item - { - public virtual bool PassivelyTriggered => false; - public virtual TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public virtual int PassiveTriggerRange => -1; - public virtual TimeSpan ResetDelay => TimeSpan.Zero; + public abstract class BaseTrap : Item + { + private DateTime m_NextPassiveTrigger, m_NextActiveTrigger; - private DateTime m_NextPassiveTrigger, m_NextActiveTrigger; + public BaseTrap(int itemID) : base(itemID) + { + Movable = false; + } - public virtual void OnTrigger( Mobile from ) - { - } + public BaseTrap(Serial serial) : base(serial) + { + } - public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement + public virtual bool PassivelyTriggered => false; + public virtual TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public virtual int PassiveTriggerRange => -1; + public virtual TimeSpan ResetDelay => TimeSpan.Zero; - public virtual int GetEffectHue() - { - int hue = Hue & 0x3FFF; + public override bool HandlesOnMovement => true; // Tell the core that we implement OnMovement - if ( hue < 2 ) - return 0; + public virtual void OnTrigger(Mobile from) + { + } - return hue - 1; - } + public virtual int GetEffectHue() + { + int hue = Hue & 0x3FFF; - public bool CheckRange( Point3D loc, Point3D oldLoc, int range ) - { - return CheckRange( loc, range ) && !CheckRange( oldLoc, range ); - } + if (hue < 2) + return 0; - public bool CheckRange( Point3D loc, int range ) - { - return ( (Z + 8) >= loc.Z && (loc.Z + 16) > Z ) - && Utility.InRange( GetWorldLocation(), loc, range ); - } + return hue - 1; + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + public bool CheckRange(Point3D loc, Point3D oldLoc, int range) + { + return CheckRange(loc, range) && !CheckRange(oldLoc, range); + } - if ( m.Location == oldLocation ) - return; + public bool CheckRange(Point3D loc, int range) + { + return Z + 8 >= loc.Z && loc.Z + 16 > Z + && Utility.InRange(GetWorldLocation(), loc, range); + } - if ( CheckRange( m.Location, oldLocation, 0 ) && DateTime.UtcNow >= m_NextActiveTrigger ) - { - m_NextActiveTrigger = m_NextPassiveTrigger = DateTime.UtcNow + ResetDelay; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - OnTrigger( m ); - } - else if ( PassivelyTriggered && CheckRange( m.Location, oldLocation, PassiveTriggerRange ) && DateTime.UtcNow >= m_NextPassiveTrigger ) - { - m_NextPassiveTrigger = DateTime.UtcNow + PassiveTriggerDelay; + if (m.Location == oldLocation) + return; - OnTrigger( m ); - } - } + if (CheckRange(m.Location, oldLocation, 0) && DateTime.UtcNow >= m_NextActiveTrigger) + { + m_NextActiveTrigger = m_NextPassiveTrigger = DateTime.UtcNow + ResetDelay; - public BaseTrap( int itemID ) : base( itemID ) - { - Movable = false; - } + OnTrigger(m); + } + else if (PassivelyTriggered && CheckRange(m.Location, oldLocation, PassiveTriggerRange) && + DateTime.UtcNow >= m_NextPassiveTrigger) + { + m_NextPassiveTrigger = DateTime.UtcNow + PassiveTriggerDelay; - public BaseTrap( Serial serial ) : base( serial ) - { - } + OnTrigger(m); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/FireColumnTrap.cs b/Scripts/Items/Traps/FireColumnTrap.cs index 23960516c..415839939 100644 --- a/Scripts/Items/Traps/FireColumnTrap.cs +++ b/Scripts/Items/Traps/FireColumnTrap.cs @@ -1,111 +1,114 @@ using System; +using Server.Spells; namespace Server.Items { - public class FireColumnTrap : BaseTrap - { - [Constructible] - public FireColumnTrap() : base( 0x1B71 ) - { - m_MinDamage = 10; - m_MaxDamage = 40; + public class FireColumnTrap : BaseTrap + { + private int m_MaxDamage; - m_WarningFlame = true; - } + private int m_MinDamage; - public override bool PassivelyTriggered => true; - public override TimeSpan PassiveTriggerDelay => TimeSpan.FromSeconds( 2.0 ); - public override int PassiveTriggerRange => 3; - public override TimeSpan ResetDelay => TimeSpan.FromSeconds( 0.5 ); + private bool m_WarningFlame; - private int m_MinDamage; + [Constructible] + public FireColumnTrap() : base(0x1B71) + { + m_MinDamage = 10; + m_MaxDamage = 40; - [CommandProperty( AccessLevel.GameMaster )] - public virtual int MinDamage - { - get => m_MinDamage; - set => m_MinDamage = value; - } + m_WarningFlame = true; + } - private int m_MaxDamage; + public FireColumnTrap(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public virtual int MaxDamage - { - get => m_MaxDamage; - set => m_MaxDamage = value; - } + public override bool PassivelyTriggered => true; + public override TimeSpan PassiveTriggerDelay => TimeSpan.FromSeconds(2.0); + public override int PassiveTriggerRange => 3; + public override TimeSpan ResetDelay => TimeSpan.FromSeconds(0.5); - private bool m_WarningFlame; + [CommandProperty(AccessLevel.GameMaster)] + public virtual int MinDamage + { + get => m_MinDamage; + set => m_MinDamage = value; + } - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool WarningFlame - { - get => m_WarningFlame; - set => m_WarningFlame = value; - } + [CommandProperty(AccessLevel.GameMaster)] + public virtual int MaxDamage + { + get => m_MaxDamage; + set => m_MaxDamage = value; + } - public override void OnTrigger( Mobile from ) - { - if ( from.AccessLevel > AccessLevel.Player ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool WarningFlame + { + get => m_WarningFlame; + set => m_WarningFlame = value; + } - if ( WarningFlame ) - DoEffect(); + public override void OnTrigger(Mobile from) + { + if (from.AccessLevel > AccessLevel.Player) + return; - if ( from.Alive && CheckRange( from.Location, 0 ) ) - { - Spells.SpellHelper.Damage( TimeSpan.FromSeconds( 0.5 ), from, from, Utility.RandomMinMax( MinDamage, MaxDamage ), 0, 100, 0, 0, 0 ); + if (WarningFlame) + DoEffect(); - if ( !WarningFlame ) - DoEffect(); - } - } + if (from.Alive && CheckRange(from.Location, 0)) + { + SpellHelper.Damage(TimeSpan.FromSeconds(0.5), from, from, Utility.RandomMinMax(MinDamage, MaxDamage), 0, 100, + 0, 0, 0); - private void DoEffect() - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3709, 10, 30, 5052 ); - Effects.PlaySound( Location, Map, 0x225 ); - } + if (!WarningFlame) + DoEffect(); + } + } - public FireColumnTrap( Serial serial ) : base( serial ) - { - } + private void DoEffect() + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3709, 10, 30, + 5052); + Effects.PlaySound(Location, Map, 0x225); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( m_WarningFlame ); - writer.Write( m_MinDamage ); - writer.Write( m_MaxDamage ); - } + writer.Write(m_WarningFlame); + writer.Write(m_MinDamage); + writer.Write(m_MaxDamage); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_WarningFlame = reader.ReadBool(); - m_MinDamage = reader.ReadInt(); - m_MaxDamage = reader.ReadInt(); - break; - } - } + switch (version) + { + case 1: + { + m_WarningFlame = reader.ReadBool(); + m_MinDamage = reader.ReadInt(); + m_MaxDamage = reader.ReadInt(); + break; + } + } - if ( version == 0 ) - { - m_WarningFlame = true; - m_MinDamage = 10; - m_MaxDamage = 40; - } - } - } -} + if (version == 0) + { + m_WarningFlame = true; + m_MinDamage = 10; + m_MaxDamage = 40; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/FlameSpurtTrap.cs b/Scripts/Items/Traps/FlameSpurtTrap.cs index 2e2fbb13e..95021c258 100644 --- a/Scripts/Items/Traps/FlameSpurtTrap.cs +++ b/Scripts/Items/Traps/FlameSpurtTrap.cs @@ -1,177 +1,178 @@ using System; +using Server.Spells; namespace Server.Items { - public class FlameSpurtTrap : BaseTrap - { - private Item m_Spurt; - private Timer m_Timer; + public class FlameSpurtTrap : BaseTrap + { + private Item m_Spurt; + private Timer m_Timer; - [Constructible] - public FlameSpurtTrap() : base( 0x1B71 ) - { - Visible = false; - } + [Constructible] + public FlameSpurtTrap() : base(0x1B71) + { + Visible = false; + } - public virtual void StartTimer() - { - if ( m_Timer == null ) - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ), Refresh ); - } + public FlameSpurtTrap(Serial serial) : base(serial) + { + } - public virtual void StopTimer() - { - m_Timer?.Stop(); + public virtual void StartTimer() + { + if (m_Timer == null) + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0), Refresh); + } - m_Timer = null; - } + public virtual void StopTimer() + { + m_Timer?.Stop(); - public virtual void CheckTimer() - { - Map map = Map; + m_Timer = null; + } - if ( map != null && map.GetSector( GetWorldLocation() ).Active ) - StartTimer(); - else - StopTimer(); - } + public virtual void CheckTimer() + { + Map map = Map; - public override void OnLocationChange( Point3D oldLocation ) - { - base.OnLocationChange( oldLocation ); + if (map != null && map.GetSector(GetWorldLocation()).Active) + StartTimer(); + else + StopTimer(); + } - CheckTimer(); - } + public override void OnLocationChange(Point3D oldLocation) + { + base.OnLocationChange(oldLocation); - public override void OnMapChange() - { - base.OnMapChange(); + CheckTimer(); + } - CheckTimer(); - } + public override void OnMapChange() + { + base.OnMapChange(); - public override void OnSectorActivate() - { - base.OnSectorActivate(); + CheckTimer(); + } - StartTimer(); - } + public override void OnSectorActivate() + { + base.OnSectorActivate(); - public override void OnSectorDeactivate() - { - base.OnSectorDeactivate(); + StartTimer(); + } - StopTimer(); - } + public override void OnSectorDeactivate() + { + base.OnSectorDeactivate(); - public override void OnDelete() - { - base.OnDelete(); + StopTimer(); + } - m_Spurt?.Delete(); - } + public override void OnDelete() + { + base.OnDelete(); - public virtual void Refresh() - { - if ( Deleted ) - return; + m_Spurt?.Delete(); + } - bool foundPlayer = false; + public virtual void Refresh() + { + if (Deleted) + return; - foreach ( Mobile mob in GetMobilesInRange( 3 ) ) - { - if ( !mob.Player || !mob.Alive || mob.AccessLevel > AccessLevel.Player ) - continue; + bool foundPlayer = false; - if ( ( (Z + 8) >= mob.Z && (mob.Z + 16) > Z ) ) - { - foundPlayer = true; - break; - } - } + foreach (Mobile mob in GetMobilesInRange(3)) + { + if (!mob.Player || !mob.Alive || mob.AccessLevel > AccessLevel.Player) + continue; - if ( !foundPlayer ) - { - m_Spurt?.Delete(); + if (Z + 8 >= mob.Z && mob.Z + 16 > Z) + { + foundPlayer = true; + break; + } + } - m_Spurt = null; - } - else if ( m_Spurt == null || m_Spurt.Deleted ) - { - m_Spurt = new Static( 0x3709 ); - m_Spurt.MoveToWorld( Location, Map ); + if (!foundPlayer) + { + m_Spurt?.Delete(); - Effects.PlaySound( GetWorldLocation(), Map, 0x309 ); - } - } + m_Spurt = null; + } + else if (m_Spurt == null || m_Spurt.Deleted) + { + m_Spurt = new Static(0x3709); + m_Spurt.MoveToWorld(Location, Map); - public override bool OnMoveOver( Mobile m ) - { - if ( m.AccessLevel > AccessLevel.Player ) - return true; + Effects.PlaySound(GetWorldLocation(), Map, 0x309); + } + } - if ( m.Player && m.Alive ) - { - CheckTimer(); + public override bool OnMoveOver(Mobile m) + { + if (m.AccessLevel > AccessLevel.Player) + return true; - Spells.SpellHelper.Damage( TimeSpan.FromTicks( 1 ), m, m, Utility.RandomMinMax( 1, 30 ) ); - m.PlaySound( m.Female ? 0x327 : 0x437 ); - } + if (m.Player && m.Alive) + { + CheckTimer(); - return false; - } + SpellHelper.Damage(TimeSpan.FromTicks(1), m, m, Utility.RandomMinMax(1, 30)); + m.PlaySound(m.Female ? 0x327 : 0x437); + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + return false; + } - if ( m.Location == oldLocation || !m.Player || !m.Alive || m.AccessLevel > AccessLevel.Player ) - return; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - if ( CheckRange( m.Location, oldLocation, 1 ) ) - { - CheckTimer(); + if (m.Location == oldLocation || !m.Player || !m.Alive || m.AccessLevel > AccessLevel.Player) + return; - Spells.SpellHelper.Damage( TimeSpan.FromTicks( 1 ), m, m, Utility.RandomMinMax( 1, 10 ) ); - m.PlaySound( m.Female ? 0x327 : 0x437 ); + if (CheckRange(m.Location, oldLocation, 1)) + { + CheckTimer(); - if ( m.Body.IsHuman ) - m.Animate( 20, 1, 1, true, false, 0 ); - } - } + SpellHelper.Damage(TimeSpan.FromTicks(1), m, m, Utility.RandomMinMax(1, 10)); + m.PlaySound(m.Female ? 0x327 : 0x437); - public FlameSpurtTrap( Serial serial ) : base( serial ) - { - } + if (m.Body.IsHuman) + m.Animate(20, 1, 1, true, false, 0); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (Item) m_Spurt ); - } + writer.Write(m_Spurt); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Item item = reader.ReadItem(); + switch (version) + { + case 0: + { + Item item = reader.ReadItem(); - item?.Delete(); + item?.Delete(); - CheckTimer(); + CheckTimer(); - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/GasTrap.cs b/Scripts/Items/Traps/GasTrap.cs index 6ae3ba0d0..d7967ac8e 100644 --- a/Scripts/Items/Traps/GasTrap.cs +++ b/Scripts/Items/Traps/GasTrap.cs @@ -3,113 +3,113 @@ using Server.Network; namespace Server.Items { - public enum GasTrapType - { - NorthWall, - WestWall, - Floor - } + public enum GasTrapType + { + NorthWall, + WestWall, + Floor + } - public class GasTrap : BaseTrap - { - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison { get; set; } + public class GasTrap : BaseTrap + { + [Constructible] + public GasTrap() : this(GasTrapType.Floor) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public GasTrapType Type - { - get - { - switch ( ItemID ) - { - case 0x113C: return GasTrapType.NorthWall; - case 0x1147: return GasTrapType.WestWall; - case 0x11A8: return GasTrapType.Floor; - } + [Constructible] + public GasTrap(GasTrapType type) : this(type, Poison.Lesser) + { + } - return GasTrapType.WestWall; - } - set => ItemID = GetBaseID( value ); - } + [Constructible] + public GasTrap(Poison poison) : this(GasTrapType.Floor, Poison.Lesser) + { + } - public static int GetBaseID( GasTrapType type ) - { - switch ( type ) - { - case GasTrapType.NorthWall: return 0x113C; - case GasTrapType.WestWall: return 0x1147; - case GasTrapType.Floor: return 0x11A8; - } + [Constructible] + public GasTrap(GasTrapType type, Poison poison) : base(GetBaseID(type)) + { + Poison = poison; + } - return 0; - } + public GasTrap(Serial serial) : base(serial) + { + } - [Constructible] - public GasTrap() : this( GasTrapType.Floor ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison{ get; set; } - [Constructible] - public GasTrap( GasTrapType type ) : this( type, Poison.Lesser ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public GasTrapType Type + { + get + { + switch (ItemID) + { + case 0x113C: return GasTrapType.NorthWall; + case 0x1147: return GasTrapType.WestWall; + case 0x11A8: return GasTrapType.Floor; + } - [Constructible] - public GasTrap( Poison poison ) : this( GasTrapType.Floor, Poison.Lesser ) - { - } + return GasTrapType.WestWall; + } + set => ItemID = GetBaseID(value); + } - [Constructible] - public GasTrap( GasTrapType type, Poison poison ) : base( GetBaseID( type ) ) - { - Poison = poison; - } + public override bool PassivelyTriggered => false; + public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public override int PassiveTriggerRange => 0; + public override TimeSpan ResetDelay => TimeSpan.FromSeconds(0.0); - public override bool PassivelyTriggered => false; - public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public override int PassiveTriggerRange => 0; - public override TimeSpan ResetDelay => TimeSpan.FromSeconds( 0.0 ); + public static int GetBaseID(GasTrapType type) + { + switch (type) + { + case GasTrapType.NorthWall: return 0x113C; + case GasTrapType.WestWall: return 0x1147; + case GasTrapType.Floor: return 0x11A8; + } - public override void OnTrigger( Mobile from ) - { - if ( Poison == null || !from.Player || !from.Alive || from.AccessLevel > AccessLevel.Player ) - return; + return 0; + } - Effects.SendLocationEffect( Location, Map, GetBaseID( Type ) - 2, 16, 3, GetEffectHue(), 0 ); - Effects.PlaySound( Location, Map, 0x231 ); + public override void OnTrigger(Mobile from) + { + if (Poison == null || !from.Player || !from.Alive || from.AccessLevel > AccessLevel.Player) + return; - from.ApplyPoison( from, Poison ); + Effects.SendLocationEffect(Location, Map, GetBaseID(Type) - 2, 16, 3, GetEffectHue(), 0); + Effects.PlaySound(Location, Map, 0x231); - from.LocalOverheadMessage( MessageType.Regular, 0x22, 500855 ); // You are enveloped by a noxious gas cloud! - } + from.ApplyPoison(from, Poison); - public GasTrap( Serial serial ) : base( serial ) - { - } + from.LocalOverheadMessage(MessageType.Regular, 0x22, 500855); // You are enveloped by a noxious gas cloud! + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - Poison.Serialize( Poison, writer ); - } + Poison.Serialize(Poison, writer); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Poison = Poison.Deserialize( reader ); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Poison = Poison.Deserialize(reader); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/GiantSpikeTrap.cs b/Scripts/Items/Traps/GiantSpikeTrap.cs index c296383aa..f5425d39e 100644 --- a/Scripts/Items/Traps/GiantSpikeTrap.cs +++ b/Scripts/Items/Traps/GiantSpikeTrap.cs @@ -1,46 +1,47 @@ using System; +using Server.Spells; namespace Server.Items { - public class GiantSpikeTrap : BaseTrap - { - [Constructible] - public GiantSpikeTrap() : base( 1 ) - { - } + public class GiantSpikeTrap : BaseTrap + { + [Constructible] + public GiantSpikeTrap() : base(1) + { + } - public override bool PassivelyTriggered => true; - public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public override int PassiveTriggerRange => 3; - public override TimeSpan ResetDelay => TimeSpan.FromSeconds( 0.0 ); + public GiantSpikeTrap(Serial serial) : base(serial) + { + } - public override void OnTrigger( Mobile from ) - { - if ( from.AccessLevel > AccessLevel.Player ) - return; + public override bool PassivelyTriggered => true; + public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public override int PassiveTriggerRange => 3; + public override TimeSpan ResetDelay => TimeSpan.FromSeconds(0.0); - Effects.SendLocationEffect( Location, Map, 0x1D99, 48, 2, GetEffectHue(), 0 ); + public override void OnTrigger(Mobile from) + { + if (from.AccessLevel > AccessLevel.Player) + return; - if ( from.Alive && CheckRange( from.Location, 0 ) ) - Spells.SpellHelper.Damage( TimeSpan.FromTicks( 1 ), from, from, Utility.Dice( 10, 7, 0 ) ); - } + Effects.SendLocationEffect(Location, Map, 0x1D99, 48, 2, GetEffectHue(), 0); - public GiantSpikeTrap( Serial serial ) : base( serial ) - { - } + if (from.Alive && CheckRange(from.Location, 0)) + SpellHelper.Damage(TimeSpan.FromTicks(1), from, from, Utility.Dice(10, 7, 0)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/MushroomTrap.cs b/Scripts/Items/Traps/MushroomTrap.cs index 90ce01dac..568c65a5f 100644 --- a/Scripts/Items/Traps/MushroomTrap.cs +++ b/Scripts/Items/Traps/MushroomTrap.cs @@ -1,60 +1,61 @@ using System; using Server.Regions; +using Server.Spells; namespace Server.Items { - public class MushroomTrap : BaseTrap - { - [Constructible] - public MushroomTrap() : base( 0x1125 ) - { - } + public class MushroomTrap : BaseTrap + { + [Constructible] + public MushroomTrap() : base(0x1125) + { + } - public override bool PassivelyTriggered => true; - public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public override int PassiveTriggerRange => 2; - public override TimeSpan ResetDelay => TimeSpan.Zero; + public MushroomTrap(Serial serial) : base(serial) + { + } - public override void OnTrigger( Mobile from ) - { - if ( !from.Alive || ItemID != 0x1125 || from.AccessLevel > AccessLevel.Player ) - return; + public override bool PassivelyTriggered => true; + public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public override int PassiveTriggerRange => 2; + public override TimeSpan ResetDelay => TimeSpan.Zero; - ItemID = 0x1126; - Effects.PlaySound( Location, Map, 0x306 ); + public override void OnTrigger(Mobile from) + { + if (!from.Alive || ItemID != 0x1125 || from.AccessLevel > AccessLevel.Player) + return; - Spells.SpellHelper.Damage( TimeSpan.FromSeconds( 0.5 ), from, from, Utility.Dice( 2, 4, 0 ) ); + ItemID = 0x1126; + Effects.PlaySound(Location, Map, 0x306); - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), OnMushroomReset ); - } + SpellHelper.Damage(TimeSpan.FromSeconds(0.5), from, from, Utility.Dice(2, 4, 0)); - public virtual void OnMushroomReset() - { - if ( Region.Find( Location, Map ).IsPartOf( typeof( DungeonRegion ) ) ) - ItemID = 0x1125; // reset - else - Delete(); - } + Timer.DelayCall(TimeSpan.FromSeconds(2.0), OnMushroomReset); + } - public MushroomTrap( Serial serial ) : base( serial ) - { - } + public virtual void OnMushroomReset() + { + if (Region.Find(Location, Map).IsPartOf(typeof(DungeonRegion))) + ItemID = 0x1125; // reset + else + Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( ItemID == 0x1126 ) - OnMushroomReset(); - } - } -} + if (ItemID == 0x1126) + OnMushroomReset(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/SawTrap.cs b/Scripts/Items/Traps/SawTrap.cs index caa9c681b..3d10165f0 100644 --- a/Scripts/Items/Traps/SawTrap.cs +++ b/Scripts/Items/Traps/SawTrap.cs @@ -1,93 +1,94 @@ using System; using Server.Network; +using Server.Spells; namespace Server.Items { - public enum SawTrapType - { - WestWall, - NorthWall, - WestFloor, - NorthFloor - } + public enum SawTrapType + { + WestWall, + NorthWall, + WestFloor, + NorthFloor + } - public class SawTrap : BaseTrap - { - [CommandProperty( AccessLevel.GameMaster )] - public SawTrapType Type - { - get - { - switch ( ItemID ) - { - case 0x1103: return SawTrapType.NorthWall; - case 0x1116: return SawTrapType.WestWall; - case 0x11AC: return SawTrapType.NorthFloor; - case 0x11B1: return SawTrapType.WestFloor; - } + public class SawTrap : BaseTrap + { + [Constructible] + public SawTrap() : this(SawTrapType.NorthFloor) + { + } - return SawTrapType.NorthWall; - } - set => ItemID = GetBaseID( value ); - } + [Constructible] + public SawTrap(SawTrapType type) : base(GetBaseID(type)) + { + } - public static int GetBaseID( SawTrapType type ) - { - switch ( type ) - { - case SawTrapType.NorthWall: return 0x1103; - case SawTrapType.WestWall: return 0x1116; - case SawTrapType.NorthFloor: return 0x11AC; - case SawTrapType.WestFloor: return 0x11B1; - } + public SawTrap(Serial serial) : base(serial) + { + } - return 0; - } + [CommandProperty(AccessLevel.GameMaster)] + public SawTrapType Type + { + get + { + switch (ItemID) + { + case 0x1103: return SawTrapType.NorthWall; + case 0x1116: return SawTrapType.WestWall; + case 0x11AC: return SawTrapType.NorthFloor; + case 0x11B1: return SawTrapType.WestFloor; + } - [Constructible] - public SawTrap() : this( SawTrapType.NorthFloor ) - { - } + return SawTrapType.NorthWall; + } + set => ItemID = GetBaseID(value); + } - [Constructible] - public SawTrap( SawTrapType type ) : base( GetBaseID( type ) ) - { - } + public override bool PassivelyTriggered => false; + public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public override int PassiveTriggerRange => 0; + public override TimeSpan ResetDelay => TimeSpan.FromSeconds(0.0); - public override bool PassivelyTriggered => false; - public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public override int PassiveTriggerRange => 0; - public override TimeSpan ResetDelay => TimeSpan.FromSeconds( 0.0 ); + public static int GetBaseID(SawTrapType type) + { + switch (type) + { + case SawTrapType.NorthWall: return 0x1103; + case SawTrapType.WestWall: return 0x1116; + case SawTrapType.NorthFloor: return 0x11AC; + case SawTrapType.WestFloor: return 0x11B1; + } - public override void OnTrigger( Mobile from ) - { - if ( !from.Alive || from.AccessLevel > AccessLevel.Player ) - return; + return 0; + } - Effects.SendLocationEffect( Location, Map, GetBaseID( Type ) + 1, 6, 3, GetEffectHue(), 0 ); - Effects.PlaySound( Location, Map, 0x21C ); + public override void OnTrigger(Mobile from) + { + if (!from.Alive || from.AccessLevel > AccessLevel.Player) + return; - Spells.SpellHelper.Damage( TimeSpan.FromTicks( 1 ), from, from, Utility.RandomMinMax( 5, 15 ) ); + Effects.SendLocationEffect(Location, Map, GetBaseID(Type) + 1, 6, 3, GetEffectHue(), 0); + Effects.PlaySound(Location, Map, 0x21C); - from.LocalOverheadMessage( MessageType.Regular, 0x22, 500853 ); // You stepped onto a blade trap! - } + SpellHelper.Damage(TimeSpan.FromTicks(1), from, from, Utility.RandomMinMax(5, 15)); - public SawTrap( Serial serial ) : base( serial ) - { - } + from.LocalOverheadMessage(MessageType.Regular, 0x22, 500853); // You stepped onto a blade trap! + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/SpikeTrap.cs b/Scripts/Items/Traps/SpikeTrap.cs index 1feda9100..cb7811e38 100644 --- a/Scripts/Items/Traps/SpikeTrap.cs +++ b/Scripts/Items/Traps/SpikeTrap.cs @@ -1,149 +1,156 @@ using System; using Server.Network; +using Server.Spells; namespace Server.Items { - public enum SpikeTrapType - { - WestWall, - NorthWall, - WestFloor, - NorthFloor - } + public enum SpikeTrapType + { + WestWall, + NorthWall, + WestFloor, + NorthFloor + } - public class SpikeTrap : BaseTrap - { - [CommandProperty( AccessLevel.GameMaster )] - public SpikeTrapType Type - { - get - { - switch ( ItemID ) - { - case 4360: case 4361: case 4366: return SpikeTrapType.WestWall; - case 4379: case 4380: case 4385: return SpikeTrapType.NorthWall; - case 4506: case 4507: case 4511: return SpikeTrapType.WestFloor; - case 4512: case 4513: case 4517: return SpikeTrapType.NorthFloor; - } + public class SpikeTrap : BaseTrap + { + [Constructible] + public SpikeTrap() : this(SpikeTrapType.WestFloor) + { + } - return SpikeTrapType.WestWall; - } - set - { - bool extended = Extended; + [Constructible] + public SpikeTrap(SpikeTrapType type) : base(GetBaseID(type)) + { + } - ItemID = ( extended ? GetExtendedID( value ) : GetBaseID( value ) ); - } - } + public SpikeTrap(Serial serial) : base(serial) + { + } - public bool Extended - { - get => ( ItemID == GetExtendedID( Type ) ); - set - { - if ( value ) - ItemID = GetExtendedID( Type ); - else - ItemID = GetBaseID( Type ); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public SpikeTrapType Type + { + get + { + switch (ItemID) + { + case 4360: + case 4361: + case 4366: return SpikeTrapType.WestWall; + case 4379: + case 4380: + case 4385: return SpikeTrapType.NorthWall; + case 4506: + case 4507: + case 4511: return SpikeTrapType.WestFloor; + case 4512: + case 4513: + case 4517: return SpikeTrapType.NorthFloor; + } - public static int GetBaseID( SpikeTrapType type ) - { - switch ( type ) - { - case SpikeTrapType.WestWall: return 4360; - case SpikeTrapType.NorthWall: return 4379; - case SpikeTrapType.WestFloor: return 4506; - case SpikeTrapType.NorthFloor: return 4512; - } + return SpikeTrapType.WestWall; + } + set + { + bool extended = Extended; - return 0; - } + ItemID = extended ? GetExtendedID(value) : GetBaseID(value); + } + } - public static int GetExtendedID( SpikeTrapType type ) - { - return GetBaseID( type ) + GetExtendedOffset( type ); - } + public bool Extended + { + get => ItemID == GetExtendedID(Type); + set + { + if (value) + ItemID = GetExtendedID(Type); + else + ItemID = GetBaseID(Type); + } + } - public static int GetExtendedOffset( SpikeTrapType type ) - { - switch ( type ) - { - case SpikeTrapType.WestWall: return 6; - case SpikeTrapType.NorthWall: return 6; + public override bool PassivelyTriggered => false; + public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public override int PassiveTriggerRange => 0; + public override TimeSpan ResetDelay => TimeSpan.FromSeconds(6.0); - case SpikeTrapType.WestFloor: return 5; - case SpikeTrapType.NorthFloor: return 5; - } + public static int GetBaseID(SpikeTrapType type) + { + switch (type) + { + case SpikeTrapType.WestWall: return 4360; + case SpikeTrapType.NorthWall: return 4379; + case SpikeTrapType.WestFloor: return 4506; + case SpikeTrapType.NorthFloor: return 4512; + } - return 0; - } + return 0; + } - [Constructible] - public SpikeTrap() : this( SpikeTrapType.WestFloor ) - { - } + public static int GetExtendedID(SpikeTrapType type) + { + return GetBaseID(type) + GetExtendedOffset(type); + } - [Constructible] - public SpikeTrap( SpikeTrapType type ) : base( GetBaseID( type ) ) - { - } + public static int GetExtendedOffset(SpikeTrapType type) + { + switch (type) + { + case SpikeTrapType.WestWall: return 6; + case SpikeTrapType.NorthWall: return 6; - public override bool PassivelyTriggered => false; - public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public override int PassiveTriggerRange => 0; - public override TimeSpan ResetDelay => TimeSpan.FromSeconds( 6.0 ); + case SpikeTrapType.WestFloor: return 5; + case SpikeTrapType.NorthFloor: return 5; + } - public override void OnTrigger( Mobile from ) - { - if ( !from.Alive || from.AccessLevel > AccessLevel.Player ) - return; + return 0; + } - Effects.SendLocationEffect( Location, Map, GetBaseID( Type ) + 1, 18, 3, GetEffectHue(), 0 ); - Effects.PlaySound( Location, Map, 0x22C ); + public override void OnTrigger(Mobile from) + { + if (!from.Alive || from.AccessLevel > AccessLevel.Player) + return; - foreach ( Mobile mob in GetMobilesInRange( 0 ) ) - { - if ( mob.Alive && !mob.IsDeadBondedPet ) - Spells.SpellHelper.Damage( TimeSpan.FromTicks( 1 ), mob, mob, Utility.RandomMinMax( 1, 6 ) * 6 ); - } + Effects.SendLocationEffect(Location, Map, GetBaseID(Type) + 1, 18, 3, GetEffectHue(), 0); + Effects.PlaySound(Location, Map, 0x22C); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), OnSpikeExtended ); + foreach (Mobile mob in GetMobilesInRange(0)) + if (mob.Alive && !mob.IsDeadBondedPet) + SpellHelper.Damage(TimeSpan.FromTicks(1), mob, mob, Utility.RandomMinMax(1, 6) * 6); - from.LocalOverheadMessage( MessageType.Regular, 0x22, 500852 ); // You stepped onto a spike trap! - } + Timer.DelayCall(TimeSpan.FromSeconds(1.0), OnSpikeExtended); - public virtual void OnSpikeExtended() - { - Extended = true; - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), OnSpikeRetracted ); - } + from.LocalOverheadMessage(MessageType.Regular, 0x22, 500852); // You stepped onto a spike trap! + } - public virtual void OnSpikeRetracted() - { - Extended = false; - Effects.SendLocationEffect( Location, Map, GetExtendedID( Type ) - 1, 6, 3, GetEffectHue(), 0 ); - } + public virtual void OnSpikeExtended() + { + Extended = true; + Timer.DelayCall(TimeSpan.FromSeconds(5.0), OnSpikeRetracted); + } - public SpikeTrap( Serial serial ) : base( serial ) - { - } + public virtual void OnSpikeRetracted() + { + Extended = false; + Effects.SendLocationEffect(Location, Map, GetExtendedID(Type) - 1, 6, 3, GetEffectHue(), 0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Extended = false; - } - } -} + Extended = false; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Traps/StoneFaceTrap.cs b/Scripts/Items/Traps/StoneFaceTrap.cs index 88d5cc0db..d7c4443d0 100644 --- a/Scripts/Items/Traps/StoneFaceTrap.cs +++ b/Scripts/Items/Traps/StoneFaceTrap.cs @@ -1,161 +1,166 @@ using System; +using Server.Spells; namespace Server.Items { - public enum StoneFaceTrapType - { - NorthWestWall, - NorthWall, - WestWall - } + public enum StoneFaceTrapType + { + NorthWestWall, + NorthWall, + WestWall + } - public class StoneFaceTrap : BaseTrap - { - [CommandProperty( AccessLevel.GameMaster )] - public StoneFaceTrapType Type - { - get - { - switch ( ItemID ) - { - case 0x10F5: case 0x10F6: case 0x10F7: return StoneFaceTrapType.NorthWestWall; - case 0x10FC: case 0x10FD: case 0x10FE: return StoneFaceTrapType.NorthWall; - case 0x110F: case 0x1110: case 0x1111: return StoneFaceTrapType.WestWall; - } + public class StoneFaceTrap : BaseTrap + { + [Constructible] + public StoneFaceTrap() : base(0x10FC) + { + Light = LightType.Circle225; + } - return StoneFaceTrapType.NorthWestWall; - } - set - { - bool breathing = Breathing; + public StoneFaceTrap(Serial serial) : base(serial) + { + } - ItemID = ( breathing ? GetFireID( value ) : GetBaseID( value ) ); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public StoneFaceTrapType Type + { + get + { + switch (ItemID) + { + case 0x10F5: + case 0x10F6: + case 0x10F7: return StoneFaceTrapType.NorthWestWall; + case 0x10FC: + case 0x10FD: + case 0x10FE: return StoneFaceTrapType.NorthWall; + case 0x110F: + case 0x1110: + case 0x1111: return StoneFaceTrapType.WestWall; + } - public bool Breathing - { - get => ( ItemID == GetFireID( Type ) ); - set - { - if ( value ) - ItemID = GetFireID( Type ); - else - ItemID = GetBaseID( Type ); - } - } + return StoneFaceTrapType.NorthWestWall; + } + set + { + bool breathing = Breathing; - public static int GetBaseID( StoneFaceTrapType type ) - { - switch ( type ) - { - case StoneFaceTrapType.NorthWestWall: return 0x10F5; - case StoneFaceTrapType.NorthWall: return 0x10FC; - case StoneFaceTrapType.WestWall: return 0x110F; - } + ItemID = breathing ? GetFireID(value) : GetBaseID(value); + } + } - return 0; - } + public bool Breathing + { + get => ItemID == GetFireID(Type); + set + { + if (value) + ItemID = GetFireID(Type); + else + ItemID = GetBaseID(Type); + } + } - public static int GetFireID( StoneFaceTrapType type ) - { - switch ( type ) - { - case StoneFaceTrapType.NorthWestWall: return 0x10F7; - case StoneFaceTrapType.NorthWall: return 0x10FE; - case StoneFaceTrapType.WestWall: return 0x1111; - } + public override bool PassivelyTriggered => true; + public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; + public override int PassiveTriggerRange => 2; + public override TimeSpan ResetDelay => TimeSpan.Zero; - return 0; - } + public static int GetBaseID(StoneFaceTrapType type) + { + switch (type) + { + case StoneFaceTrapType.NorthWestWall: return 0x10F5; + case StoneFaceTrapType.NorthWall: return 0x10FC; + case StoneFaceTrapType.WestWall: return 0x110F; + } - [Constructible] - public StoneFaceTrap() : base( 0x10FC ) - { - Light = LightType.Circle225; - } + return 0; + } - public override bool PassivelyTriggered => true; - public override TimeSpan PassiveTriggerDelay => TimeSpan.Zero; - public override int PassiveTriggerRange => 2; - public override TimeSpan ResetDelay => TimeSpan.Zero; + public static int GetFireID(StoneFaceTrapType type) + { + switch (type) + { + case StoneFaceTrapType.NorthWestWall: return 0x10F7; + case StoneFaceTrapType.NorthWall: return 0x10FE; + case StoneFaceTrapType.WestWall: return 0x1111; + } - public override void OnTrigger( Mobile from ) - { - if ( !from.Alive || from.AccessLevel > AccessLevel.Player ) - return; + return 0; + } - Effects.PlaySound( Location, Map, 0x359 ); + public override void OnTrigger(Mobile from) + { + if (!from.Alive || from.AccessLevel > AccessLevel.Player) + return; - Breathing = true; + Effects.PlaySound(Location, Map, 0x359); - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), FinishBreath ); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TriggerDamage ); - } + Breathing = true; - public virtual void FinishBreath() - { - Breathing = false; - } + Timer.DelayCall(TimeSpan.FromSeconds(2.0), FinishBreath); + Timer.DelayCall(TimeSpan.FromSeconds(1.0), TriggerDamage); + } - public virtual void TriggerDamage() - { - foreach ( Mobile mob in GetMobilesInRange( 1 ) ) - { - if ( mob.Alive && !mob.IsDeadBondedPet && mob.AccessLevel == AccessLevel.Player ) - Spells.SpellHelper.Damage( TimeSpan.FromTicks( 1 ), mob, mob, Utility.Dice( 3, 15, 0 ) ); - } - } + public virtual void FinishBreath() + { + Breathing = false; + } - public StoneFaceTrap( Serial serial ) : base( serial ) - { - } + public virtual void TriggerDamage() + { + foreach (Mobile mob in GetMobilesInRange(1)) + if (mob.Alive && !mob.IsDeadBondedPet && mob.AccessLevel == AccessLevel.Player) + SpellHelper.Damage(TimeSpan.FromTicks(1), mob, mob, Utility.Dice(3, 15, 0)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Breathing = false; - } - } + Breathing = false; + } + } - public class StoneFaceTrapNoDamage : StoneFaceTrap - { - [Constructible] - public StoneFaceTrapNoDamage() - { - } + public class StoneFaceTrapNoDamage : StoneFaceTrap + { + [Constructible] + public StoneFaceTrapNoDamage() + { + } - public StoneFaceTrapNoDamage( Serial serial ) : base( serial ) - { - } + public StoneFaceTrapNoDamage(Serial serial) : base(serial) + { + } - public override void TriggerDamage() - { - // nothing.. - } + public override void TriggerDamage() + { + // nothing.. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/TreasureChests/TreasureChestLevel1.cs b/Scripts/Items/TreasureChests/TreasureChestLevel1.cs index 8e2f26970..a4bad125d 100644 --- a/Scripts/Items/TreasureChests/TreasureChestLevel1.cs +++ b/Scripts/Items/TreasureChests/TreasureChestLevel1.cs @@ -2,115 +2,115 @@ using System; namespace Server.Items { - public class TreasureChestLevel1 : LockableContainer - { - private const int m_Level = 1; + public class TreasureChestLevel1 : LockableContainer + { + private const int m_Level = 1; - public override bool Decays => true; + [Constructible] + public TreasureChestLevel1() + : base(0xE41) + { + SetChestAppearance(); + Movable = false; - public override bool IsDecoContainer => false; + TrapType = TrapType.DartTrap; + TrapPower = m_Level * Utility.Random(1, 25); + Locked = true; - public override TimeSpan DecayTime => TimeSpan.FromMinutes( Utility.Random( 15, 60 ) ); + RequiredSkill = 57; + LockLevel = RequiredSkill - Utility.Random(1, 10); + MaxLockLevel = RequiredSkill + Utility.Random(1, 10); - private void SetChestAppearance() - { - bool UseFirstItemId = Utility.RandomBool(); + // According to OSI, loot in level 1 chest is: + // Gold 25 - 50 + // Bolts 10 + // Gems + // Normal weapon + // Normal armour + // Normal clothing + // Normal jewelry - switch( Utility.RandomList( 0, 1, 2 ) ) - { - case 0:// Large Crate - ItemID = ( UseFirstItemId ? 0xe3c : 0xe3d ); - GumpID = 0x44; - break; + // Gold + DropItem(new Gold(Utility.Random(30, 100))); - case 1:// Medium Crate - ItemID = ( UseFirstItemId ? 0xe3e : 0xe3f ); - GumpID = 0x44; - break; + // Drop bolts + //DropItem( new Bolt( 10 ) ); - case 2:// Small Crate - ItemID = ( UseFirstItemId ? 0x9a9 : 0xe7e ); - GumpID = 0x44; - break; - } - } + // Gems + if (Utility.RandomBool()) + { + Item GemLoot = Loot.RandomGem(); + GemLoot.Amount = Utility.Random(1, 3); + DropItem(GemLoot); + } - public override int DefaultGumpID => 0x42; + // Weapon + if (Utility.RandomBool()) + DropItem(Loot.RandomWeapon()); - public override int DefaultDropSound => 0x42; + // Armour + if (Utility.RandomBool()) + DropItem(Loot.RandomArmorOrShield()); - public override Rectangle2D Bounds => new Rectangle2D( 18, 105, 144, 73 ); + // Clothing + if (Utility.RandomBool()) + DropItem(Loot.RandomClothing()); - [Constructible] - public TreasureChestLevel1() - : base( 0xE41 ) - { - SetChestAppearance(); - Movable = false; + // Jewelry + if (Utility.RandomBool()) + DropItem(Loot.RandomJewelry()); + } - TrapType = TrapType.DartTrap; - TrapPower = m_Level * Utility.Random( 1, 25 ); - Locked = true; + public TreasureChestLevel1(Serial serial) + : base(serial) + { + } - RequiredSkill = 57; - LockLevel = RequiredSkill - Utility.Random( 1, 10 ); - MaxLockLevel = RequiredSkill + Utility.Random( 1, 10 ); + public override bool Decays => true; - // According to OSI, loot in level 1 chest is: - // Gold 25 - 50 - // Bolts 10 - // Gems - // Normal weapon - // Normal armour - // Normal clothing - // Normal jewelry + public override bool IsDecoContainer => false; - // Gold - DropItem( new Gold( Utility.Random( 30, 100 ) ) ); + public override TimeSpan DecayTime => TimeSpan.FromMinutes(Utility.Random(15, 60)); - // Drop bolts - //DropItem( new Bolt( 10 ) ); + public override int DefaultGumpID => 0x42; - // Gems - if ( Utility.RandomBool() == true ) - { - Item GemLoot = Loot.RandomGem(); - GemLoot.Amount = Utility.Random( 1, 3 ); - DropItem( GemLoot ); - } + public override int DefaultDropSound => 0x42; - // Weapon - if ( Utility.RandomBool() == true ) - DropItem( Loot.RandomWeapon() ); + public override Rectangle2D Bounds => new Rectangle2D(18, 105, 144, 73); - // Armour - if ( Utility.RandomBool() == true ) - DropItem( Loot.RandomArmorOrShield() ); + private void SetChestAppearance() + { + bool UseFirstItemId = Utility.RandomBool(); - // Clothing - if ( Utility.RandomBool() == true ) - DropItem( Loot.RandomClothing() ); + switch (Utility.RandomList(0, 1, 2)) + { + case 0: // Large Crate + ItemID = UseFirstItemId ? 0xe3c : 0xe3d; + GumpID = 0x44; + break; - // Jewelry - if ( Utility.RandomBool() == true ) - DropItem( Loot.RandomJewelry() ); - } + case 1: // Medium Crate + ItemID = UseFirstItemId ? 0xe3e : 0xe3f; + GumpID = 0x44; + break; - public TreasureChestLevel1( Serial serial ) - : base( serial ) - { - } + case 2: // Small Crate + ItemID = UseFirstItemId ? 0x9a9 : 0xe7e; + GumpID = 0x44; + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( ( int )1 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/TreasureChests/TreasureChestLevel2.cs b/Scripts/Items/TreasureChests/TreasureChestLevel2.cs index a3f33dab4..b607d7d19 100644 --- a/Scripts/Items/TreasureChests/TreasureChestLevel2.cs +++ b/Scripts/Items/TreasureChests/TreasureChestLevel2.cs @@ -2,146 +2,147 @@ using System; namespace Server.Items { - public class TreasureChestLevel2 : LockableContainer - { - private const int m_Level = 2; + public class TreasureChestLevel2 : LockableContainer + { + private const int m_Level = 2; - public override bool Decays => true; + [Constructible] + public TreasureChestLevel2() + : base(0xE41) + { + SetChestAppearance(); + Movable = false; - public override bool IsDecoContainer => false; + TrapType = TrapType.ExplosionTrap; + TrapPower = m_Level * Utility.Random(1, 25); + Locked = true; - public override TimeSpan DecayTime => TimeSpan.FromMinutes( Utility.Random( 15, 60 ) ); + RequiredSkill = 72; + LockLevel = RequiredSkill - Utility.Random(1, 10); + MaxLockLevel = RequiredSkill + Utility.Random(1, 10); + ; - private void SetChestAppearance() - { - bool UseFirstItemId = Utility.RandomBool(); + // According to OSI, loot in level 2 chest is: + // Gold 80 - 150 + // Arrows 10 + // Reagents + // Scrolls + // Potions + // Gems - switch( Utility.RandomList( 0, 1, 2, 3, 4, 5, 6, 7 ) ) - { - case 0:// Large Crate - ItemID = ( UseFirstItemId ? 0xe3c : 0xe3d ); - GumpID = 0x44; - break; + // Gold + DropItem(new Gold(Utility.Random(70, 100))); - case 1:// Medium Crate - ItemID = ( UseFirstItemId ? 0xe3e : 0xe3f ); - GumpID = 0x44; - break; + // Drop bolts + //DropItem( new Arrow( 10 ) ); - case 2:// Small Crate - ItemID = ( UseFirstItemId ? 0x9a9 : 0xe7e ); - GumpID = 0x44; - break; + // Reagents + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item ReagentLoot = Loot.RandomReagent(); + ReagentLoot.Amount = Utility.Random(1, m_Level); + DropItem(ReagentLoot); + } - case 3:// Wooden Chest - ItemID = ( UseFirstItemId ? 0xe42 : 0xe43 ); - GumpID = 0x49; - break; + // Scrolls + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item ScrollLoot = Loot.RandomScroll(0, 39, SpellbookType.Regular); + ScrollLoot.Amount = Utility.Random(1, 8); + DropItem(ScrollLoot); + } - case 4:// Metal Chest - ItemID = ( UseFirstItemId ? 0x9ab : 0xe7c ); - GumpID = 0x4A; - break; + // Potions + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item PotionLoot = Loot.RandomPotion(); + DropItem(PotionLoot); + } - case 5:// Metal Golden Chest - ItemID = ( UseFirstItemId ? 0xe40 : 0xe41 ); - GumpID = 0x42; - break; + // Gems + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item GemLoot = Loot.RandomGem(); + GemLoot.Amount = Utility.Random(1, 6); + DropItem(GemLoot); + } + } - case 6:// Keg - ItemID = ( UseFirstItemId ? 0xe7f : 0xe7f ); - GumpID = 0x3e; - break; + public TreasureChestLevel2(Serial serial) + : base(serial) + { + } - case 7:// Barrel - ItemID = ( UseFirstItemId ? 0xe77 : 0xe77 ); - GumpID = 0x3e; - break; - } - } + public override bool Decays => true; - public override int DefaultGumpID => 0x42; + public override bool IsDecoContainer => false; - public override int DefaultDropSound => 0x42; + public override TimeSpan DecayTime => TimeSpan.FromMinutes(Utility.Random(15, 60)); - public override Rectangle2D Bounds => new Rectangle2D( 18, 105, 144, 73 ); + public override int DefaultGumpID => 0x42; - [Constructible] - public TreasureChestLevel2() - : base( 0xE41 ) - { - SetChestAppearance(); - Movable = false; + public override int DefaultDropSound => 0x42; - TrapType = TrapType.ExplosionTrap; - TrapPower = m_Level * Utility.Random( 1, 25 ); - Locked = true; + public override Rectangle2D Bounds => new Rectangle2D(18, 105, 144, 73); - RequiredSkill = 72; - LockLevel = RequiredSkill - Utility.Random( 1, 10 ); - MaxLockLevel = RequiredSkill + Utility.Random( 1, 10 ); ; + private void SetChestAppearance() + { + bool UseFirstItemId = Utility.RandomBool(); - // According to OSI, loot in level 2 chest is: - // Gold 80 - 150 - // Arrows 10 - // Reagents - // Scrolls - // Potions - // Gems + switch (Utility.RandomList(0, 1, 2, 3, 4, 5, 6, 7)) + { + case 0: // Large Crate + ItemID = UseFirstItemId ? 0xe3c : 0xe3d; + GumpID = 0x44; + break; - // Gold - DropItem( new Gold( Utility.Random( 70, 100 ) ) ); + case 1: // Medium Crate + ItemID = UseFirstItemId ? 0xe3e : 0xe3f; + GumpID = 0x44; + break; - // Drop bolts - //DropItem( new Arrow( 10 ) ); + case 2: // Small Crate + ItemID = UseFirstItemId ? 0x9a9 : 0xe7e; + GumpID = 0x44; + break; - // Reagents - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item ReagentLoot = Loot.RandomReagent(); - ReagentLoot.Amount = Utility.Random( 1, m_Level ); - DropItem( ReagentLoot ); - } + case 3: // Wooden Chest + ItemID = UseFirstItemId ? 0xe42 : 0xe43; + GumpID = 0x49; + break; - // Scrolls - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item ScrollLoot = Loot.RandomScroll( 0, 39, SpellbookType.Regular ); - ScrollLoot.Amount = Utility.Random( 1, 8 ); - DropItem( ScrollLoot ); - } + case 4: // Metal Chest + ItemID = UseFirstItemId ? 0x9ab : 0xe7c; + GumpID = 0x4A; + break; - // Potions - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item PotionLoot = Loot.RandomPotion(); - DropItem( PotionLoot ); - } + case 5: // Metal Golden Chest + ItemID = UseFirstItemId ? 0xe40 : 0xe41; + GumpID = 0x42; + break; - // Gems - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item GemLoot = Loot.RandomGem(); - GemLoot.Amount = Utility.Random( 1, 6 ); - DropItem( GemLoot ); - } - } + case 6: // Keg + ItemID = UseFirstItemId ? 0xe7f : 0xe7f; + GumpID = 0x3e; + break; - public TreasureChestLevel2( Serial serial ) - : base( serial ) - { - } + case 7: // Barrel + ItemID = UseFirstItemId ? 0xe77 : 0xe77; + GumpID = 0x3e; + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( ( int )1 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/TreasureChests/TreasureChestLevel3.cs b/Scripts/Items/TreasureChests/TreasureChestLevel3.cs index 772ecadd0..a11d41e75 100644 --- a/Scripts/Items/TreasureChests/TreasureChestLevel3.cs +++ b/Scripts/Items/TreasureChests/TreasureChestLevel3.cs @@ -2,159 +2,160 @@ using System; namespace Server.Items { - public class TreasureChestLevel3 : LockableContainer - { - private const int m_Level = 3; + public class TreasureChestLevel3 : LockableContainer + { + private const int m_Level = 3; - public override bool Decays => true; + [Constructible] + public TreasureChestLevel3() + : base(0xE41) + { + SetChestAppearance(); + Movable = false; - public override bool IsDecoContainer => false; + TrapType = TrapType.PoisonTrap; + TrapPower = m_Level * Utility.Random(1, 25); + Locked = true; - public override TimeSpan DecayTime => TimeSpan.FromMinutes( Utility.Random( 15, 60 ) ); + RequiredSkill = 84; + LockLevel = RequiredSkill - Utility.Random(1, 10); + MaxLockLevel = RequiredSkill + Utility.Random(1, 10); + ; - private void SetChestAppearance() - { - bool UseFirstItemId = Utility.RandomBool(); - switch( Utility.RandomList( 0, 1, 2 ) ) - { - case 0:// Wooden Chest - ItemID = ( UseFirstItemId ? 0xe42 : 0xe43 ); - GumpID = 0x49; - break; + // According to OSI, loot in level 3 chest is: + // Gold 250 - 350 + // Arrows 10 + // Reagents + // Scrolls + // Potions + // Gems + // Magic Wand + // Magic weapon + // Magic armour + // Magic clothing (not implemented) + // Magic jewelry (not implemented) - case 1:// Metal Chest - ItemID = ( UseFirstItemId ? 0x9ab : 0xe7c ); - GumpID = 0x4A; - break; + // Gold + DropItem(new Gold(Utility.Random(180, 240))); - case 2:// Metal Golden Chest - ItemID = ( UseFirstItemId ? 0xe40 : 0xe41 ); - GumpID = 0x42; - break; - } - } + // Drop bolts + //DropItem( new Arrow( 10 ) ); - public override int DefaultGumpID => 0x42; + // Reagents + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item ReagentLoot = Loot.RandomReagent(); + ReagentLoot.Amount = Utility.Random(1, 9); + DropItem(ReagentLoot); + } - public override int DefaultDropSound => 0x42; + // Scrolls + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item ScrollLoot = Loot.RandomScroll(0, 47, SpellbookType.Regular); + ScrollLoot.Amount = Utility.Random(1, 12); + DropItem(ScrollLoot); + } - public override Rectangle2D Bounds => new Rectangle2D( 18, 105, 144, 73 ); + // Potions + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item PotionLoot = Loot.RandomPotion(); + DropItem(PotionLoot); + } - [Constructible] - public TreasureChestLevel3() - : base( 0xE41 ) - { - SetChestAppearance(); - Movable = false; + // Gems + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item GemLoot = Loot.RandomGem(); + GemLoot.Amount = Utility.Random(1, 9); + DropItem(GemLoot); + } - TrapType = TrapType.PoisonTrap; - TrapPower = m_Level * Utility.Random( 1, 25 ); - Locked = true; + // Magic Wand + for (int i = Utility.Random(1, m_Level); i > 1; i--) + DropItem(Loot.RandomWand()); - RequiredSkill = 84; - LockLevel = RequiredSkill - Utility.Random( 1, 10 ); - MaxLockLevel = RequiredSkill + Utility.Random( 1, 10 ); ; + // Equipment + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item item = Loot.RandomArmorOrShieldOrWeapon(); - // According to OSI, loot in level 3 chest is: - // Gold 250 - 350 - // Arrows 10 - // Reagents - // Scrolls - // Potions - // Gems - // Magic Wand - // Magic weapon - // Magic armour - // Magic clothing (not implemented) - // Magic jewelry (not implemented) + if (item is BaseWeapon weapon) + { + weapon.DamageLevel = (WeaponDamageLevel)Utility.Random(m_Level); + weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random(m_Level); + weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random(m_Level); + weapon.Quality = WeaponQuality.Regular; + } + else if (item is BaseArmor armor) + { + armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random(m_Level); + armor.Durability = (ArmorDurabilityLevel)Utility.Random(m_Level); + armor.Quality = ArmorQuality.Regular; + } - // Gold - DropItem( new Gold( Utility.Random( 180, 240 ) ) ); + DropItem(item); + } - // Drop bolts - //DropItem( new Arrow( 10 ) ); + // Clothing + for (int i = Utility.Random(1, 2); i > 1; i--) + DropItem(Loot.RandomClothing()); - // Reagents - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item ReagentLoot = Loot.RandomReagent(); - ReagentLoot.Amount = Utility.Random( 1, 9 ); - DropItem( ReagentLoot ); - } + // Jewelry + for (int i = Utility.Random(1, 2); i > 1; i--) + DropItem(Loot.RandomJewelry()); + } - // Scrolls - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item ScrollLoot = Loot.RandomScroll( 0, 47, SpellbookType.Regular ); - ScrollLoot.Amount = Utility.Random( 1, 12 ); - DropItem( ScrollLoot ); - } + public TreasureChestLevel3(Serial serial) + : base(serial) + { + } - // Potions - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item PotionLoot = Loot.RandomPotion(); - DropItem( PotionLoot ); - } + public override bool Decays => true; - // Gems - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item GemLoot = Loot.RandomGem(); - GemLoot.Amount = Utility.Random( 1, 9 ); - DropItem( GemLoot ); - } + public override bool IsDecoContainer => false; - // Magic Wand - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - DropItem( Loot.RandomWand() ); + public override TimeSpan DecayTime => TimeSpan.FromMinutes(Utility.Random(15, 60)); - // Equipment - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item item = Loot.RandomArmorOrShieldOrWeapon(); + public override int DefaultGumpID => 0x42; - if ( item is BaseWeapon weapon ) - { - weapon.DamageLevel = ( WeaponDamageLevel )Utility.Random( m_Level ); - weapon.AccuracyLevel = ( WeaponAccuracyLevel )Utility.Random( m_Level ); - weapon.DurabilityLevel = ( WeaponDurabilityLevel )Utility.Random( m_Level ); - weapon.Quality = WeaponQuality.Regular; - } - else if ( item is BaseArmor armor ) - { - armor.ProtectionLevel = ( ArmorProtectionLevel )Utility.Random( m_Level ); - armor.Durability = ( ArmorDurabilityLevel )Utility.Random( m_Level ); - armor.Quality = ArmorQuality.Regular; - } + public override int DefaultDropSound => 0x42; - DropItem( item ); - } + public override Rectangle2D Bounds => new Rectangle2D(18, 105, 144, 73); - // Clothing - for( int i = Utility.Random( 1, 2 ); i > 1; i-- ) - DropItem( Loot.RandomClothing() ); + private void SetChestAppearance() + { + bool UseFirstItemId = Utility.RandomBool(); + switch (Utility.RandomList(0, 1, 2)) + { + case 0: // Wooden Chest + ItemID = UseFirstItemId ? 0xe42 : 0xe43; + GumpID = 0x49; + break; - // Jewelry - for( int i = Utility.Random( 1, 2 ); i > 1; i-- ) - DropItem( Loot.RandomJewelry() ); - } + case 1: // Metal Chest + ItemID = UseFirstItemId ? 0x9ab : 0xe7c; + GumpID = 0x4A; + break; - public TreasureChestLevel3( Serial serial ) - : base( serial ) - { - } + case 2: // Metal Golden Chest + ItemID = UseFirstItemId ? 0xe40 : 0xe41; + GumpID = 0x42; + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( ( int )1 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/TreasureChests/TreasureChestLevel4.cs b/Scripts/Items/TreasureChests/TreasureChestLevel4.cs index e8e7aef99..11616eed2 100644 --- a/Scripts/Items/TreasureChests/TreasureChestLevel4.cs +++ b/Scripts/Items/TreasureChests/TreasureChestLevel4.cs @@ -2,168 +2,169 @@ using System; namespace Server.Items { - public class TreasureChestLevel4 : LockableContainer - { - private const int m_Level = 4; + public class TreasureChestLevel4 : LockableContainer + { + private const int m_Level = 4; - public override bool Decays => true; + [Constructible] + public TreasureChestLevel4() + : base(0xE41) + { + SetChestAppearance(); + Movable = false; - public override bool IsDecoContainer => false; + TrapType = TrapType.ExplosionTrap; + TrapPower = m_Level * Utility.Random(10, 25); + Locked = true; - public override TimeSpan DecayTime => TimeSpan.FromMinutes( Utility.Random( 15, 60 ) ); + RequiredSkill = 92; + LockLevel = RequiredSkill - Utility.Random(1, 10); + MaxLockLevel = RequiredSkill + Utility.Random(1, 10); + ; - private void SetChestAppearance() - { - bool UseFirstItemId = Utility.RandomBool(); + // According to OSI, loot in level 4 chest is: + // Gold 500 - 900 + // Reagents + // Scrolls + // Blank scrolls + // Potions + // Gems + // Magic Wand + // Magic weapon + // Magic armour + // Magic clothing (not implemented) + // Magic jewelry (not implemented) + // Crystal ball (not implemented) - switch( Utility.Random( 4 ) ) - { - case 0:// Wooden Chest - ItemID = ( UseFirstItemId ? 0xe42 : 0xe43 ); - GumpID = 0x49; - break; + // Gold + DropItem(new Gold(Utility.Random(200, 400))); - case 1:// Metal Chest - ItemID = ( UseFirstItemId ? 0x9ab : 0xe7c ); - GumpID = 0x4A; - break; + // Reagents + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item ReagentLoot = Loot.RandomReagent(); + ReagentLoot.Amount = 12; + DropItem(ReagentLoot); + } - case 2:// Metal Golden Chest - ItemID = ( UseFirstItemId ? 0xe40 : 0xe41 ); - GumpID = 0x42; - break; + // Scrolls + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item ScrollLoot = Loot.RandomScroll(0, 47, SpellbookType.Regular); + ScrollLoot.Amount = 16; + DropItem(ScrollLoot); + } - case 3:// Keg - ItemID = 0xe7f; - GumpID = 0x3e; - break; - } - } + // Drop blank scrolls + DropItem(new BlankScroll(Utility.Random(1, m_Level))); - public override int DefaultGumpID => 0x42; + // Potions + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item PotionLoot = Loot.RandomPotion(); + DropItem(PotionLoot); + } - public override int DefaultDropSound => 0x42; + // Gems + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item GemLoot = Loot.RandomGem(); + GemLoot.Amount = 12; + DropItem(GemLoot); + } - public override Rectangle2D Bounds => new Rectangle2D( 18, 105, 144, 73 ); + // Magic Wand + for (int i = Utility.Random(1, m_Level); i > 1; i--) + DropItem(Loot.RandomWand()); - [Constructible] - public TreasureChestLevel4() - : base( 0xE41 ) - { - SetChestAppearance(); - Movable = false; + // Equipment + for (int i = Utility.Random(1, m_Level); i > 1; i--) + { + Item item = Loot.RandomArmorOrShieldOrWeapon(); - TrapType = TrapType.ExplosionTrap; - TrapPower = m_Level * Utility.Random( 10, 25 ); - Locked = true; + if (item is BaseWeapon weapon) + { + weapon.DamageLevel = (WeaponDamageLevel)Utility.Random(m_Level); + weapon.AccuracyLevel = (WeaponAccuracyLevel)Utility.Random(m_Level); + weapon.DurabilityLevel = (WeaponDurabilityLevel)Utility.Random(m_Level); + weapon.Quality = WeaponQuality.Regular; + } + else if (item is BaseArmor armor) + { + armor.ProtectionLevel = (ArmorProtectionLevel)Utility.Random(m_Level); + armor.Durability = (ArmorDurabilityLevel)Utility.Random(m_Level); + armor.Quality = ArmorQuality.Regular; + } - RequiredSkill = 92; - LockLevel = RequiredSkill - Utility.Random( 1, 10 ); - MaxLockLevel = RequiredSkill + Utility.Random( 1, 10 ); ; + DropItem(item); + } - // According to OSI, loot in level 4 chest is: - // Gold 500 - 900 - // Reagents - // Scrolls - // Blank scrolls - // Potions - // Gems - // Magic Wand - // Magic weapon - // Magic armour - // Magic clothing (not implemented) - // Magic jewelry (not implemented) - // Crystal ball (not implemented) + // Clothing + for (int i = Utility.Random(1, 2); i > 1; i--) + DropItem(Loot.RandomClothing()); - // Gold - DropItem( new Gold( Utility.Random( 200, 400 ) ) ); + // Jewelry + for (int i = Utility.Random(1, 2); i > 1; i--) + DropItem(Loot.RandomJewelry()); - // Reagents - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item ReagentLoot = Loot.RandomReagent(); - ReagentLoot.Amount = 12; - DropItem( ReagentLoot ); - } + // Crystal ball (not implemented) + } - // Scrolls - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item ScrollLoot = Loot.RandomScroll( 0, 47, SpellbookType.Regular ); - ScrollLoot.Amount = 16; - DropItem( ScrollLoot ); - } + public TreasureChestLevel4(Serial serial) + : base(serial) + { + } - // Drop blank scrolls - DropItem( new BlankScroll( Utility.Random( 1, m_Level ) ) ); + public override bool Decays => true; - // Potions - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item PotionLoot = Loot.RandomPotion(); - DropItem( PotionLoot ); - } + public override bool IsDecoContainer => false; - // Gems - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item GemLoot = Loot.RandomGem(); - GemLoot.Amount = 12; - DropItem( GemLoot ); - } + public override TimeSpan DecayTime => TimeSpan.FromMinutes(Utility.Random(15, 60)); - // Magic Wand - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - DropItem( Loot.RandomWand() ); + public override int DefaultGumpID => 0x42; - // Equipment - for( int i = Utility.Random( 1, m_Level ); i > 1; i-- ) - { - Item item = Loot.RandomArmorOrShieldOrWeapon(); + public override int DefaultDropSound => 0x42; - if ( item is BaseWeapon weapon ) - { - weapon.DamageLevel = ( WeaponDamageLevel )Utility.Random( m_Level ); - weapon.AccuracyLevel = ( WeaponAccuracyLevel )Utility.Random( m_Level ); - weapon.DurabilityLevel = ( WeaponDurabilityLevel )Utility.Random( m_Level ); - weapon.Quality = WeaponQuality.Regular; - } - else if ( item is BaseArmor armor ) - { - armor.ProtectionLevel = ( ArmorProtectionLevel )Utility.Random( m_Level ); - armor.Durability = ( ArmorDurabilityLevel )Utility.Random( m_Level ); - armor.Quality = ArmorQuality.Regular; - } + public override Rectangle2D Bounds => new Rectangle2D(18, 105, 144, 73); - DropItem( item ); - } + private void SetChestAppearance() + { + bool UseFirstItemId = Utility.RandomBool(); - // Clothing - for( int i = Utility.Random( 1, 2 ); i > 1; i-- ) - DropItem( Loot.RandomClothing() ); + switch (Utility.Random(4)) + { + case 0: // Wooden Chest + ItemID = UseFirstItemId ? 0xe42 : 0xe43; + GumpID = 0x49; + break; - // Jewelry - for( int i = Utility.Random( 1, 2 ); i > 1; i-- ) - DropItem( Loot.RandomJewelry() ); + case 1: // Metal Chest + ItemID = UseFirstItemId ? 0x9ab : 0xe7c; + GumpID = 0x4A; + break; - // Crystal ball (not implemented) - } + case 2: // Metal Golden Chest + ItemID = UseFirstItemId ? 0xe40 : 0xe41; + GumpID = 0x42; + break; - public TreasureChestLevel4( Serial serial ) - : base( serial ) - { - } + case 3: // Keg + ItemID = 0xe7f; + GumpID = 0x3e; + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( ( int )1 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Wands/BaseWand.cs b/Scripts/Items/Wands/BaseWand.cs index 41ba4ee45..bcca61469 100644 --- a/Scripts/Items/Wands/BaseWand.cs +++ b/Scripts/Items/Wands/BaseWand.cs @@ -1,253 +1,308 @@ using System; using System.Collections; using Server.Network; -using Server.Targeting; using Server.Spells; +using Server.Targeting; namespace Server.Items { - public enum WandEffect - { - Clumsiness, - Identification, - Healing, - Feeblemindedness, - Weakness, - MagicArrow, - Harming, - Fireball, - GreaterHealing, - Lightning, - ManaDraining - } + public enum WandEffect + { + Clumsiness, + Identification, + Healing, + Feeblemindedness, + Weakness, + MagicArrow, + Harming, + Fireball, + GreaterHealing, + Lightning, + ManaDraining + } - public abstract class BaseWand : BaseBashing, ITokunoDyable - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Dismount; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + public abstract class BaseWand : BaseBashing, ITokunoDyable + { + private int m_Charges; - public override int AosStrengthReq => 5; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 40; - public override float MlSpeed => 2.75f; + private WandEffect m_WandEffect; - public override int OldStrengthReq => 0; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 6; - public override int OldSpeed => 35; + public BaseWand(WandEffect effect, int minCharges, int maxCharges) : base(Utility.RandomList(0xDF2, 0xDF3, 0xDF4, + 0xDF5)) + { + Weight = 1.0; + Effect = effect; + Charges = Utility.RandomMinMax(minCharges, maxCharges); + Attributes.SpellChanneling = 1; + Attributes.CastSpeed = -1; + WeaponAttributes.MageWeapon = Utility.RandomMinMax(1, 10); + } - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public BaseWand(Serial serial) : base(serial) + { + } - private WandEffect m_WandEffect; - private int m_Charges; + public override WeaponAbility PrimaryAbility => WeaponAbility.Dismount; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public virtual TimeSpan GetUseDelay => TimeSpan.FromSeconds( 4.0 ); + public override int AosStrengthReq => 5; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 40; + public override float MlSpeed => 2.75f; - [CommandProperty( AccessLevel.GameMaster )] - public WandEffect Effect - { - get => m_WandEffect; - set{ m_WandEffect = value; InvalidateProperties(); } - } + public override int OldStrengthReq => 0; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 6; + public override int OldSpeed => 35; - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set{ m_Charges = value; InvalidateProperties(); } - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public BaseWand( WandEffect effect, int minCharges, int maxCharges ) : base( Utility.RandomList( 0xDF2, 0xDF3, 0xDF4, 0xDF5 ) ) - { - Weight = 1.0; - Effect = effect; - Charges = Utility.RandomMinMax( minCharges, maxCharges ); - Attributes.SpellChanneling = 1; - Attributes.CastSpeed = -1; - WeaponAttributes.MageWeapon = Utility.RandomMinMax( 1, 10 ); - } + public virtual TimeSpan GetUseDelay => TimeSpan.FromSeconds(4.0); - public void ConsumeCharge( Mobile from ) - { - --Charges; + [CommandProperty(AccessLevel.GameMaster)] + public WandEffect Effect + { + get => m_WandEffect; + set + { + m_WandEffect = value; + InvalidateProperties(); + } + } - if ( Charges == 0 ) - from.SendLocalizedMessage( 1019073 ); // This item is out of charges. + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + InvalidateProperties(); + } + } - ApplyDelayTo( from ); - } + public void ConsumeCharge(Mobile from) + { + --Charges; - public BaseWand( Serial serial ) : base( serial ) - { - } + if (Charges == 0) + from.SendLocalizedMessage(1019073); // This item is out of charges. - public virtual void ApplyDelayTo( Mobile from ) - { - from.BeginAction( typeof( BaseWand ) ); - Timer.DelayCall(GetUseDelay, ReleaseWandLock_Callback, from); - } + ApplyDelayTo(from); + } - public virtual void ReleaseWandLock_Callback(Mobile state) - { - state.EndAction(typeof(BaseWand)); - } + public virtual void ApplyDelayTo(Mobile from) + { + from.BeginAction(typeof(BaseWand)); + Timer.DelayCall(GetUseDelay, ReleaseWandLock_Callback, from); + } - public override void OnDoubleClick( Mobile from ) - { - if ( !from.CanBeginAction( typeof( BaseWand ) ) ) - { - from.SendLocalizedMessage( 1070860 ); // You must wait a moment for the wand to recharge. - return; - } + public virtual void ReleaseWandLock_Callback(Mobile state) + { + state.EndAction(typeof(BaseWand)); + } - if ( Parent == from ) - { - if ( Charges > 0 ) - OnWandUse( from ); - else - from.SendLocalizedMessage( 1019073 ); // This item is out of charges. - } - else - { - from.SendLocalizedMessage( 502641 ); // You must equip this item to use it. - } - } + public override void OnDoubleClick(Mobile from) + { + if (!from.CanBeginAction(typeof(BaseWand))) + { + from.SendLocalizedMessage(1070860); // You must wait a moment for the wand to recharge. + return; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (Parent == from) + { + if (Charges > 0) + OnWandUse(from); + else + from.SendLocalizedMessage(1019073); // This item is out of charges. + } + else + { + from.SendLocalizedMessage(502641); // You must equip this item to use it. + } + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) m_WandEffect ); - writer.Write( (int) m_Charges ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write((int)m_WandEffect); + writer.Write(m_Charges); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - m_WandEffect = (WandEffect)reader.ReadInt(); - m_Charges = (int)reader.ReadInt(); + int version = reader.ReadInt(); - break; - } - } - } + switch (version) + { + case 0: + { + m_WandEffect = (WandEffect)reader.ReadInt(); + m_Charges = reader.ReadInt(); - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + break; + } + } + } - switch ( m_WandEffect ) - { - case WandEffect.Clumsiness: list.Add( 1017326, m_Charges.ToString() ); break; // clumsiness charges: ~1_val~ - case WandEffect.Identification: list.Add( 1017350, m_Charges.ToString() ); break; // identification charges: ~1_val~ - case WandEffect.Healing: list.Add( 1017329, m_Charges.ToString() ); break; // healing charges: ~1_val~ - case WandEffect.Feeblemindedness: list.Add( 1017327, m_Charges.ToString() ); break; // feeblemind charges: ~1_val~ - case WandEffect.Weakness: list.Add( 1017328, m_Charges.ToString() ); break; // weakness charges: ~1_val~ - case WandEffect.MagicArrow: list.Add( 1060492, m_Charges.ToString() ); break; // magic arrow charges: ~1_val~ - case WandEffect.Harming: list.Add( 1017334, m_Charges.ToString() ); break; // harm charges: ~1_val~ - case WandEffect.Fireball: list.Add( 1060487, m_Charges.ToString() ); break; // fireball charges: ~1_val~ - case WandEffect.GreaterHealing: list.Add( 1017330, m_Charges.ToString() ); break; // greater healing charges: ~1_val~ - case WandEffect.Lightning: list.Add( 1060491, m_Charges.ToString() ); break; // lightning charges: ~1_val~ - case WandEffect.ManaDraining: list.Add( 1017339, m_Charges.ToString() ); break; // mana drain charges: ~1_val~ - } - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnSingleClick( Mobile from ) - { - ArrayList attrs = new ArrayList(); + switch (m_WandEffect) + { + case WandEffect.Clumsiness: + list.Add(1017326, m_Charges.ToString()); + break; // clumsiness charges: ~1_val~ + case WandEffect.Identification: + list.Add(1017350, m_Charges.ToString()); + break; // identification charges: ~1_val~ + case WandEffect.Healing: + list.Add(1017329, m_Charges.ToString()); + break; // healing charges: ~1_val~ + case WandEffect.Feeblemindedness: + list.Add(1017327, m_Charges.ToString()); + break; // feeblemind charges: ~1_val~ + case WandEffect.Weakness: + list.Add(1017328, m_Charges.ToString()); + break; // weakness charges: ~1_val~ + case WandEffect.MagicArrow: + list.Add(1060492, m_Charges.ToString()); + break; // magic arrow charges: ~1_val~ + case WandEffect.Harming: + list.Add(1017334, m_Charges.ToString()); + break; // harm charges: ~1_val~ + case WandEffect.Fireball: + list.Add(1060487, m_Charges.ToString()); + break; // fireball charges: ~1_val~ + case WandEffect.GreaterHealing: + list.Add(1017330, m_Charges.ToString()); + break; // greater healing charges: ~1_val~ + case WandEffect.Lightning: + list.Add(1060491, m_Charges.ToString()); + break; // lightning charges: ~1_val~ + case WandEffect.ManaDraining: + list.Add(1017339, m_Charges.ToString()); + break; // mana drain charges: ~1_val~ + } + } - if ( DisplayLootType ) - { - if ( LootType == LootType.Blessed ) - attrs.Add( new EquipInfoAttribute( 1038021 ) ); // blessed - else if ( LootType == LootType.Cursed ) - attrs.Add( new EquipInfoAttribute( 1049643 ) ); // cursed - } + public override void OnSingleClick(Mobile from) + { + ArrayList attrs = new ArrayList(); - if ( !Identified ) - { - attrs.Add( new EquipInfoAttribute( 1038000 ) ); // Unidentified - } - else - { - int num = 0; + if (DisplayLootType) + { + if (LootType == LootType.Blessed) + attrs.Add(new EquipInfoAttribute(1038021)); // blessed + else if (LootType == LootType.Cursed) + attrs.Add(new EquipInfoAttribute(1049643)); // cursed + } - switch ( m_WandEffect ) - { - case WandEffect.Clumsiness: num = 3002011; break; - case WandEffect.Identification: num = 1044063; break; - case WandEffect.Healing: num = 3002014; break; - case WandEffect.Feeblemindedness: num = 3002013; break; - case WandEffect.Weakness: num = 3002018; break; - case WandEffect.MagicArrow: num = 3002015; break; - case WandEffect.Harming: num = 3002022; break; - case WandEffect.Fireball: num = 3002028; break; - case WandEffect.GreaterHealing: num = 3002039; break; - case WandEffect.Lightning: num = 3002040; break; - case WandEffect.ManaDraining: num = 3002041; break; - } + if (!Identified) + { + attrs.Add(new EquipInfoAttribute(1038000)); // Unidentified + } + else + { + int num = 0; - if ( num > 0 ) - attrs.Add( new EquipInfoAttribute( num, m_Charges ) ); - } + switch (m_WandEffect) + { + case WandEffect.Clumsiness: + num = 3002011; + break; + case WandEffect.Identification: + num = 1044063; + break; + case WandEffect.Healing: + num = 3002014; + break; + case WandEffect.Feeblemindedness: + num = 3002013; + break; + case WandEffect.Weakness: + num = 3002018; + break; + case WandEffect.MagicArrow: + num = 3002015; + break; + case WandEffect.Harming: + num = 3002022; + break; + case WandEffect.Fireball: + num = 3002028; + break; + case WandEffect.GreaterHealing: + num = 3002039; + break; + case WandEffect.Lightning: + num = 3002040; + break; + case WandEffect.ManaDraining: + num = 3002041; + break; + } - int number; + if (num > 0) + attrs.Add(new EquipInfoAttribute(num, m_Charges)); + } - if ( Name == null ) - { - number = 1017085; - } - else - { - LabelTo( from, Name ); - number = 1041000; - } + int number; - if ( attrs.Count == 0 && Crafter == null && Name != null ) - return; + if (Name == null) + { + number = 1017085; + } + else + { + LabelTo(from, Name); + number = 1041000; + } - EquipmentInfo eqInfo = new EquipmentInfo( number, Crafter, false, (EquipInfoAttribute[])attrs.ToArray( typeof( EquipInfoAttribute ) ) ); + if (attrs.Count == 0 && Crafter == null && Name != null) + return; - from.Send( new DisplayEquipmentInfo( this, eqInfo ) ); - } + EquipmentInfo eqInfo = new EquipmentInfo(number, Crafter, false, + (EquipInfoAttribute[])attrs.ToArray(typeof(EquipInfoAttribute))); - public void Cast( Spell spell ) - { - bool m = Movable; + from.Send(new DisplayEquipmentInfo(this, eqInfo)); + } - Movable = false; - spell.Cast(); - Movable = m; - } + public void Cast(Spell spell) + { + bool m = Movable; - public virtual void OnWandUse( Mobile from ) - { - from.Target = new WandTarget( this ); - } + Movable = false; + spell.Cast(); + Movable = m; + } - public virtual void DoWandTarget( Mobile from, object o ) - { - if ( Deleted || Charges <= 0 || Parent != from || o is StaticTarget || o is LandTarget ) - return; + public virtual void OnWandUse(Mobile from) + { + from.Target = new WandTarget(this); + } - if ( OnWandTarget( from, o ) ) - ConsumeCharge( from ); - } + public virtual void DoWandTarget(Mobile from, object o) + { + if (Deleted || Charges <= 0 || Parent != from || o is StaticTarget || o is LandTarget) + return; - public virtual bool OnWandTarget( Mobile from, object o ) - { - return true; - } - } -} + if (OnWandTarget(from, o)) + ConsumeCharge(from); + } + + public virtual bool OnWandTarget(Mobile from, object o) + { + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Wands/ClumsyWand.cs b/Scripts/Items/Wands/ClumsyWand.cs index 4fff24c42..987e41c6b 100644 --- a/Scripts/Items/Wands/ClumsyWand.cs +++ b/Scripts/Items/Wands/ClumsyWand.cs @@ -2,34 +2,34 @@ using Server.Spells.First; namespace Server.Items { - public class ClumsyWand : BaseWand - { - [Constructible] - public ClumsyWand() : base( WandEffect.Clumsiness, 5, 30 ) - { - } + public class ClumsyWand : BaseWand + { + [Constructible] + public ClumsyWand() : base(WandEffect.Clumsiness, 5, 30) + { + } - public ClumsyWand( Serial serial ) : base( serial ) - { - } + public ClumsyWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new ClumsySpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new ClumsySpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/FeebleWand.cs b/Scripts/Items/Wands/FeebleWand.cs index 78b106b4b..157d61ecb 100644 --- a/Scripts/Items/Wands/FeebleWand.cs +++ b/Scripts/Items/Wands/FeebleWand.cs @@ -2,34 +2,34 @@ using Server.Spells.First; namespace Server.Items { - public class FeebleWand : BaseWand - { - [Constructible] - public FeebleWand() : base( WandEffect.Feeblemindedness, 5, 30 ) - { - } + public class FeebleWand : BaseWand + { + [Constructible] + public FeebleWand() : base(WandEffect.Feeblemindedness, 5, 30) + { + } - public FeebleWand( Serial serial ) : base( serial ) - { - } + public FeebleWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new FeeblemindSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new FeeblemindSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/FireballWand.cs b/Scripts/Items/Wands/FireballWand.cs index adbffcf7e..d2aa2533e 100644 --- a/Scripts/Items/Wands/FireballWand.cs +++ b/Scripts/Items/Wands/FireballWand.cs @@ -2,34 +2,34 @@ using Server.Spells.Third; namespace Server.Items { - public class FireballWand : BaseWand - { - [Constructible] - public FireballWand() : base( WandEffect.Fireball, 5, Core.ML ? 109 : 15 ) - { - } + public class FireballWand : BaseWand + { + [Constructible] + public FireballWand() : base(WandEffect.Fireball, 5, Core.ML ? 109 : 15) + { + } - public FireballWand( Serial serial ) : base( serial ) - { - } + public FireballWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new FireballSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new FireballSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/GreaterHealWand.cs b/Scripts/Items/Wands/GreaterHealWand.cs index 4db60ea62..2a1f42741 100644 --- a/Scripts/Items/Wands/GreaterHealWand.cs +++ b/Scripts/Items/Wands/GreaterHealWand.cs @@ -2,34 +2,34 @@ using Server.Spells.Fourth; namespace Server.Items { - public class GreaterHealWand : BaseWand - { - [Constructible] - public GreaterHealWand() : base( WandEffect.GreaterHealing, 1, Core.ML ? 109 : 5 ) - { - } + public class GreaterHealWand : BaseWand + { + [Constructible] + public GreaterHealWand() : base(WandEffect.GreaterHealing, 1, Core.ML ? 109 : 5) + { + } - public GreaterHealWand( Serial serial ) : base( serial ) - { - } + public GreaterHealWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new GreaterHealSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new GreaterHealSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/HarmWand.cs b/Scripts/Items/Wands/HarmWand.cs index bb4931c66..61bb15962 100644 --- a/Scripts/Items/Wands/HarmWand.cs +++ b/Scripts/Items/Wands/HarmWand.cs @@ -2,34 +2,34 @@ using Server.Spells.Second; namespace Server.Items { - public class HarmWand : BaseWand - { - [Constructible] - public HarmWand() : base( WandEffect.Harming, 5, Core.ML ? 109 : 30 ) - { - } + public class HarmWand : BaseWand + { + [Constructible] + public HarmWand() : base(WandEffect.Harming, 5, Core.ML ? 109 : 30) + { + } - public HarmWand( Serial serial ) : base( serial ) - { - } + public HarmWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new HarmSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new HarmSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/HealWand.cs b/Scripts/Items/Wands/HealWand.cs index 65d0ab707..adbc9bcc4 100644 --- a/Scripts/Items/Wands/HealWand.cs +++ b/Scripts/Items/Wands/HealWand.cs @@ -2,34 +2,34 @@ using Server.Spells.First; namespace Server.Items { - public class HealWand : BaseWand - { - [Constructible] - public HealWand() : base( WandEffect.Healing, 10, Core.ML ? 109 : 25 ) - { - } + public class HealWand : BaseWand + { + [Constructible] + public HealWand() : base(WandEffect.Healing, 10, Core.ML ? 109 : 25) + { + } - public HealWand( Serial serial ) : base( serial ) - { - } + public HealWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new HealSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new HealSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/IDWand.cs b/Scripts/Items/Wands/IDWand.cs index f2eebc8d3..95af6b3ea 100644 --- a/Scripts/Items/Wands/IDWand.cs +++ b/Scripts/Items/Wands/IDWand.cs @@ -2,49 +2,49 @@ using System; namespace Server.Items { - public class IDWand : BaseWand - { - public override TimeSpan GetUseDelay => TimeSpan.Zero; + public class IDWand : BaseWand + { + [Constructible] + public IDWand() : base(WandEffect.Identification, 25, 175) + { + } - [Constructible] - public IDWand() : base( WandEffect.Identification, 25, 175 ) - { - } + public IDWand(Serial serial) : base(serial) + { + } - public IDWand( Serial serial ) : base( serial ) - { - } + public override TimeSpan GetUseDelay => TimeSpan.Zero; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override bool OnWandTarget( Mobile from, object o ) - { - if (o is Item item) - { - if ( item is BaseWeapon weapon ) - weapon.Identified = true; - else if ( item is BaseArmor armor ) - armor.Identified = true; + public override bool OnWandTarget(Mobile from, object o) + { + if (o is Item item) + { + if (item is BaseWeapon weapon) + weapon.Identified = true; + else if (item is BaseArmor armor) + armor.Identified = true; - if (!Core.AOS) - item.OnSingleClick( from ); + if (!Core.AOS) + item.OnSingleClick(from); - return true; - } + return true; + } - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Wands/LightningWand.cs b/Scripts/Items/Wands/LightningWand.cs index 0b517ad96..c3b6f90b8 100644 --- a/Scripts/Items/Wands/LightningWand.cs +++ b/Scripts/Items/Wands/LightningWand.cs @@ -2,34 +2,34 @@ using Server.Spells.Fourth; namespace Server.Items { - public class LightningWand : BaseWand - { - [Constructible] - public LightningWand() : base( WandEffect.Lightning, 5, Core.ML ? 109 : 20 ) - { - } + public class LightningWand : BaseWand + { + [Constructible] + public LightningWand() : base(WandEffect.Lightning, 5, Core.ML ? 109 : 20) + { + } - public LightningWand( Serial serial ) : base( serial ) - { - } + public LightningWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new LightningSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new LightningSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/MagicArrowWand.cs b/Scripts/Items/Wands/MagicArrowWand.cs index 5fd85e23a..7d0578844 100644 --- a/Scripts/Items/Wands/MagicArrowWand.cs +++ b/Scripts/Items/Wands/MagicArrowWand.cs @@ -2,34 +2,34 @@ using Server.Spells.First; namespace Server.Items { - public class MagicArrowWand : BaseWand - { - [Constructible] - public MagicArrowWand() : base( WandEffect.MagicArrow, 5, Core.ML ? 109 : 30 ) - { - } + public class MagicArrowWand : BaseWand + { + [Constructible] + public MagicArrowWand() : base(WandEffect.MagicArrow, 5, Core.ML ? 109 : 30) + { + } - public MagicArrowWand( Serial serial ) : base( serial ) - { - } + public MagicArrowWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new MagicArrowSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new MagicArrowSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/ManaDrainWand.cs b/Scripts/Items/Wands/ManaDrainWand.cs index 9d1f94c5a..62819a876 100644 --- a/Scripts/Items/Wands/ManaDrainWand.cs +++ b/Scripts/Items/Wands/ManaDrainWand.cs @@ -2,34 +2,34 @@ using Server.Spells.Fourth; namespace Server.Items { - public class ManaDrainWand : BaseWand - { - [Constructible] - public ManaDrainWand() : base( WandEffect.ManaDraining, 5, 30 ) - { - } + public class ManaDrainWand : BaseWand + { + [Constructible] + public ManaDrainWand() : base(WandEffect.ManaDraining, 5, 30) + { + } - public ManaDrainWand( Serial serial ) : base( serial ) - { - } + public ManaDrainWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new ManaDrainSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new ManaDrainSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/RandomWand.cs b/Scripts/Items/Wands/RandomWand.cs index a5f904d64..10db0d613 100644 --- a/Scripts/Items/Wands/RandomWand.cs +++ b/Scripts/Items/Wands/RandomWand.cs @@ -1,33 +1,33 @@ namespace Server.Items { - public class RandomWand - { - public static BaseWand CreateWand() - { - return CreateRandomWand(); - } + public class RandomWand + { + public static BaseWand CreateWand() + { + return CreateRandomWand(); + } - public static BaseWand CreateRandomWand() - { - return Loot.RandomWand(); + public static BaseWand CreateRandomWand() + { + return Loot.RandomWand(); - /* - switch ( Utility.Random( 11 ) ) - { - default: - case 0: return new ClumsyWand(); - case 1: return new FeebleWand(); - case 2: return new FireballWand(); - case 3: return new GreaterHealWand(); - case 4: return new HarmWand(); - case 5: return new HealWand(); - case 6: return new IDWand(); - case 7: return new LightningWand(); - case 8: return new MagicArrowWand(); - case 9: return new ManaDrainWand(); - case 10: return new WeaknessWand(); - } - */ - } - } + /* + switch ( Utility.Random( 11 ) ) + { + default: + case 0: return new ClumsyWand(); + case 1: return new FeebleWand(); + case 2: return new FireballWand(); + case 3: return new GreaterHealWand(); + case 4: return new HarmWand(); + case 5: return new HealWand(); + case 6: return new IDWand(); + case 7: return new LightningWand(); + case 8: return new MagicArrowWand(); + case 9: return new ManaDrainWand(); + case 10: return new WeaknessWand(); + } + */ + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/WandTarget.cs b/Scripts/Items/Wands/WandTarget.cs index 24780225f..cdb675e96 100644 --- a/Scripts/Items/Wands/WandTarget.cs +++ b/Scripts/Items/Wands/WandTarget.cs @@ -2,23 +2,23 @@ using Server.Items; namespace Server.Targeting { - public class WandTarget : Target - { - private BaseWand m_Item; + public class WandTarget : Target + { + private BaseWand m_Item; - public WandTarget( BaseWand item ) : base( 6, false, TargetFlags.None ) - { - m_Item = item; - } + public WandTarget(BaseWand item) : base(6, false, TargetFlags.None) + { + m_Item = item; + } - private static int GetOffset( Mobile caster ) - { - return 5 + (int)(caster.Skills[SkillName.Magery].Value * 0.02 ); - } + private static int GetOffset(Mobile caster) + { + return 5 + (int)(caster.Skills[SkillName.Magery].Value * 0.02); + } - protected override void OnTarget( Mobile from, object targeted ) - { - m_Item.DoWandTarget( from, targeted ); - } - } + protected override void OnTarget(Mobile from, object targeted) + { + m_Item.DoWandTarget(from, targeted); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Wands/WeaknessWand.cs b/Scripts/Items/Wands/WeaknessWand.cs index 45b53c1ad..8f33ac865 100644 --- a/Scripts/Items/Wands/WeaknessWand.cs +++ b/Scripts/Items/Wands/WeaknessWand.cs @@ -2,34 +2,34 @@ using Server.Spells.First; namespace Server.Items { - public class WeaknessWand : BaseWand - { - [Constructible] - public WeaknessWand() : base( WandEffect.Weakness, 5, 30 ) - { - } + public class WeaknessWand : BaseWand + { + [Constructible] + public WeaknessWand() : base(WandEffect.Weakness, 5, 30) + { + } - public WeaknessWand( Serial serial ) : base( serial ) - { - } + public WeaknessWand(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnWandUse( Mobile from ) - { - Cast( new WeakenSpell( from, this ) ); - } - } + public override void OnWandUse(Mobile from) + { + Cast(new WeakenSpell(from, this)); + } + } } \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/ArmorIgnore.cs b/Scripts/Items/Weapons/Abilities/ArmorIgnore.cs index de677dbf6..ce270af94 100644 --- a/Scripts/Items/Weapons/Abilities/ArmorIgnore.cs +++ b/Scripts/Items/Weapons/Abilities/ArmorIgnore.cs @@ -1,31 +1,28 @@ namespace Server.Items { - /// - /// This special move allows the skilled warrior to bypass his target's physical resistance, for one shot only. - /// The Armor Ignore shot does slightly less damage than normal. - /// Against a heavily armored opponent, this ability is a big win, but when used against a very lightly armored foe, it might be better to use a standard strike! - /// - public class ArmorIgnore : WeaponAbility - { - public ArmorIgnore() - { - } + /// + /// This special move allows the skilled warrior to bypass his target's physical resistance, for one shot only. + /// The Armor Ignore shot does slightly less damage than normal. + /// Against a heavily armored opponent, this ability is a big win, but when used against a very lightly armored foe, it might + /// be better to use a standard strike! + /// + public class ArmorIgnore : WeaponAbility + { + public override int BaseMana => 30; + public override double DamageScalar => 0.9; - public override int BaseMana => 30; - public override double DamageScalar => 0.9; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1060076); // Your attack penetrates their armor! + defender.SendLocalizedMessage(1060077); // The blow penetrated your armor! - attacker.SendLocalizedMessage( 1060076 ); // Your attack penetrates their armor! - defender.SendLocalizedMessage( 1060077 ); // The blow penetrated your armor! - - defender.PlaySound( 0x56 ); - defender.FixedParticles( 0x3728, 200, 25, 9942, EffectLayer.Waist ); - } - } -} + defender.PlaySound(0x56); + defender.FixedParticles(0x3728, 200, 25, 9942, EffectLayer.Waist); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/ArmorPierce.cs b/Scripts/Items/Weapons/Abilities/ArmorPierce.cs index 1517c91bf..d3ca4967a 100644 --- a/Scripts/Items/Weapons/Abilities/ArmorPierce.cs +++ b/Scripts/Items/Weapons/Abilities/ArmorPierce.cs @@ -1,41 +1,39 @@ namespace Server.Items { - /// - /// Strike your opponent with great force, partially bypassing their armor and inflicting greater damage. Requires either Bushido or Ninjitsu skill - /// - public class ArmorPierce : WeaponAbility - { - public ArmorPierce() - { - } + /// + /// Strike your opponent with great force, partially bypassing their armor and inflicting greater damage. Requires either + /// Bushido or Ninjitsu skill + /// + public class ArmorPierce : WeaponAbility + { + public override int BaseMana => 30; + public override double DamageScalar => 1.5; - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 && GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1063347, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! - return false; - } + public override bool RequiresSE => true; - return base.CheckSkills( from ); - } + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0 && GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1063347, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! + return false; + } - public override int BaseMana => 30; - public override double DamageScalar => 1.5; + return base.CheckSkills(from); + } - public override bool RequiresSE => true; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1063350); // You pierce your opponent's armor! + defender.SendLocalizedMessage(1063351); // Your attacker pierced your armor! - attacker.SendLocalizedMessage( 1063350 ); // You pierce your opponent's armor! - defender.SendLocalizedMessage( 1063351 ); // Your attacker pierced your armor! - - defender.FixedParticles( 0x3728, 1, 26, 0x26D6, 0, 0, EffectLayer.Waist ); - } - } -} + defender.FixedParticles(0x3728, 1, 26, 0x26D6, 0, 0, EffectLayer.Waist); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/BleedAttack.cs b/Scripts/Items/Weapons/Abilities/BleedAttack.cs index 571a5578f..12cb1af16 100644 --- a/Scripts/Items/Weapons/Abilities/BleedAttack.cs +++ b/Scripts/Items/Weapons/Abilities/BleedAttack.cs @@ -1,134 +1,131 @@ using System; using System.Collections; using Server.Mobiles; -using Server.Spells.Necromancy; using Server.Network; using Server.Spells; +using Server.Spells.Necromancy; namespace Server.Items { - /// - /// Make your opponent bleed profusely with this wicked use of your weapon. - /// When successful, the target will bleed for several seconds, taking damage as time passes for up to ten seconds. - /// The rate of damage slows down as time passes, and the blood loss can be completely staunched with the use of bandages. - /// - public class BleedAttack : WeaponAbility - { - public BleedAttack() - { - } + /// + /// Make your opponent bleed profusely with this wicked use of your weapon. + /// When successful, the target will bleed for several seconds, taking damage as time passes for up to ten seconds. + /// The rate of damage slows down as time passes, and the blood loss can be completely staunched with the use of bandages. + /// + public class BleedAttack : WeaponAbility + { + private static Hashtable m_Table = new Hashtable(); - public override int BaseMana => 30; + public override int BaseMana => 30; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - // Necromancers under Lich or Wraith Form are immune to Bleed Attacks. - TransformContext context = TransformationSpellHelper.GetContext( defender ); + // Necromancers under Lich or Wraith Form are immune to Bleed Attacks. + TransformContext context = TransformationSpellHelper.GetContext(defender); - if ( (context != null && ( context.Type == typeof( LichFormSpell ) || context.Type == typeof( WraithFormSpell ))) || - (defender is BaseCreature creature && creature.BleedImmune) ) - { - attacker.SendLocalizedMessage( 1062052 ); // Your target is not affected by the bleed attack! - return; - } + if (context != null && (context.Type == typeof(LichFormSpell) || context.Type == typeof(WraithFormSpell)) || + defender is BaseCreature creature && creature.BleedImmune) + { + attacker.SendLocalizedMessage(1062052); // Your target is not affected by the bleed attack! + return; + } - attacker.SendLocalizedMessage( 1060159 ); // Your target is bleeding! - defender.SendLocalizedMessage( 1060160 ); // You are bleeding! + attacker.SendLocalizedMessage(1060159); // Your target is bleeding! + defender.SendLocalizedMessage(1060160); // You are bleeding! - if ( defender is PlayerMobile ) - { - defender.LocalOverheadMessage( MessageType.Regular, 0x21, 1060757 ); // You are bleeding profusely - defender.NonlocalOverheadMessage( MessageType.Regular, 0x21, 1060758, defender.Name ); // ~1_NAME~ is bleeding profusely - } + if (defender is PlayerMobile) + { + defender.LocalOverheadMessage(MessageType.Regular, 0x21, 1060757); // You are bleeding profusely + defender.NonlocalOverheadMessage(MessageType.Regular, 0x21, 1060758, + defender.Name); // ~1_NAME~ is bleeding profusely + } - defender.PlaySound( 0x133 ); - defender.FixedParticles( 0x377A, 244, 25, 9950, 31, 0, EffectLayer.Waist ); + defender.PlaySound(0x133); + defender.FixedParticles(0x377A, 244, 25, 9950, 31, 0, EffectLayer.Waist); - BeginBleed( defender, attacker ); - } + BeginBleed(defender, attacker); + } - private static Hashtable m_Table = new Hashtable(); + public static bool IsBleeding(Mobile m) + { + return m_Table.Contains(m); + } - public static bool IsBleeding( Mobile m ) - { - return m_Table.Contains( m ); - } + public static void BeginBleed(Mobile m, Mobile from) + { + Timer t = (Timer)m_Table[m]; - public static void BeginBleed( Mobile m, Mobile from ) - { - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + t = new InternalTimer(from, m); + m_Table[m] = t; - t = new InternalTimer( from, m ); - m_Table[m] = t; + t.Start(); + } - t.Start(); - } + public static void DoBleed(Mobile m, Mobile from, int level) + { + if (m.Alive) + { + int damage = Utility.RandomMinMax(level, level * 2); - public static void DoBleed( Mobile m, Mobile from, int level ) - { - if ( m.Alive ) - { - int damage = Utility.RandomMinMax( level, level * 2 ); + if (!m.Player) + damage *= 2; - if ( !m.Player ) - damage *= 2; + m.PlaySound(0x133); + m.Damage(damage, from); - m.PlaySound( 0x133 ); - m.Damage( damage, from ); + Blood blood = new Blood(); - Blood blood = new Blood(); + blood.ItemID = Utility.Random(0x122A, 5); - blood.ItemID = Utility.Random( 0x122A, 5 ); + blood.MoveToWorld(m.Location, m.Map); + } + else + { + EndBleed(m, false); + } + } - blood.MoveToWorld( m.Location, m.Map ); - } - else - { - EndBleed( m, false ); - } - } + public static void EndBleed(Mobile m, bool message) + { + Timer t = (Timer)m_Table[m]; - public static void EndBleed( Mobile m, bool message ) - { - Timer t = (Timer)m_Table[m]; + if (t == null) + return; - if ( t == null ) - return; + t.Stop(); + m_Table.Remove(m); - t.Stop(); - m_Table.Remove( m ); + if (message) + m.SendLocalizedMessage(1060167); // The bleeding wounds have healed, you are no longer bleeding! + } - if ( message ) - m.SendLocalizedMessage( 1060167 ); // The bleeding wounds have healed, you are no longer bleeding! - } + private class InternalTimer : Timer + { + private int m_Count; + private Mobile m_From; + private Mobile m_Mobile; - private class InternalTimer : Timer - { - private Mobile m_From; - private Mobile m_Mobile; - private int m_Count; + public InternalTimer(Mobile from, Mobile m) : base(TimeSpan.FromSeconds(2.0), TimeSpan.FromSeconds(2.0)) + { + m_From = from; + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - public InternalTimer( Mobile from, Mobile m ) : base( TimeSpan.FromSeconds( 2.0 ), TimeSpan.FromSeconds( 2.0 ) ) - { - m_From = from; - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } + protected override void OnTick() + { + DoBleed(m_Mobile, m_From, 5 - m_Count); - protected override void OnTick() - { - DoBleed( m_Mobile, m_From, 5 - m_Count ); - - if ( ++m_Count == 5 ) - EndBleed( m_Mobile, true ); - } - } - } -} + if (++m_Count == 5) + EndBleed(m_Mobile, true); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/Block.cs b/Scripts/Items/Weapons/Abilities/Block.cs index 23e9ecde6..a7b672e1e 100644 --- a/Scripts/Items/Weapons/Abilities/Block.cs +++ b/Scripts/Items/Weapons/Abilities/Block.cs @@ -3,103 +3,101 @@ using System.Collections; namespace Server.Items { - /// - /// Raises your defenses for a short time. Requires Bushido or Ninjitsu skill. - /// - public class Block : WeaponAbility - { - public Block() - { - } + /// + /// Raises your defenses for a short time. Requires Bushido or Ninjitsu skill. + /// + public class Block : WeaponAbility + { + private static Hashtable m_Table = new Hashtable(); - public override int BaseMana => 30; + public override int BaseMana => 30; - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 && GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1063347, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! - return false; - } + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0 && GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1063347, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! + return false; + } - return base.CheckSkills( from ); - } + return base.CheckSkills(from); + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - attacker.SendLocalizedMessage( 1063345 ); // You block an attack! - defender.SendLocalizedMessage( 1063346 ); // Your attack was blocked! + attacker.SendLocalizedMessage(1063345); // You block an attack! + defender.SendLocalizedMessage(1063346); // Your attack was blocked! - attacker.FixedParticles( 0x37C4, 1, 16, 0x251D, 0x39D, 0x3, EffectLayer.RightHand ); + attacker.FixedParticles(0x37C4, 1, 16, 0x251D, 0x39D, 0x3, EffectLayer.RightHand); - int bonus = (int)(10.0 * ((Math.Max( attacker.Skills[SkillName.Bushido].Value, attacker.Skills[SkillName.Ninjitsu].Value ) - 50.0) / 70.0 + 5)); + int bonus = (int)(10.0 * ((Math.Max(attacker.Skills[SkillName.Bushido].Value, + attacker.Skills[SkillName.Ninjitsu].Value) - 50.0) / 70.0 + 5)); - BeginBlock( attacker, bonus ); - } + BeginBlock(attacker, bonus); + } - private class BlockInfo - { - public Mobile m_Target; - public Timer m_Timer; - public int m_Bonus; + public static bool GetBonus(Mobile targ, ref int bonus) + { + if (!(m_Table[targ] is BlockInfo info)) + return false; - public BlockInfo( Mobile target, int bonus ) - { - m_Target = target; - m_Bonus = bonus; - } - } + bonus = info.m_Bonus; + return true; + } - private static Hashtable m_Table = new Hashtable(); + public static void BeginBlock(Mobile m, int bonus) + { + EndBlock(m); - public static bool GetBonus( Mobile targ, ref int bonus ) - { - if ( !(m_Table[targ] is BlockInfo info) ) - return false; + BlockInfo info = new BlockInfo(m, bonus); + info.m_Timer = new InternalTimer(m); - bonus = info.m_Bonus; - return true; - } + m_Table[m] = info; + } - public static void BeginBlock( Mobile m, int bonus ) - { - EndBlock( m ); + public static void EndBlock(Mobile m) + { + if (m_Table[m] is BlockInfo info) + { + info.m_Timer?.Stop(); - BlockInfo info = new BlockInfo( m, bonus ); - info.m_Timer = new InternalTimer( m ); + m_Table.Remove(m); + } + } - m_Table[m] = info; - } + private class BlockInfo + { + public int m_Bonus; + public Mobile m_Target; + public Timer m_Timer; - public static void EndBlock( Mobile m ) - { - if ( m_Table[m] is BlockInfo info ) - { - info.m_Timer?.Stop(); + public BlockInfo(Mobile target, int bonus) + { + m_Target = target; + m_Bonus = bonus; + } + } - m_Table.Remove( m ); - } - } + private class InternalTimer : Timer + { + private Mobile m_Mobile; - private class InternalTimer : Timer - { - private Mobile m_Mobile; + public InternalTimer(Mobile m) : base(TimeSpan.FromSeconds(6.0)) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - public InternalTimer( Mobile m ) : base( TimeSpan.FromSeconds( 6.0 ) ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - EndBlock( m_Mobile ); - } - } - } -} + protected override void OnTick() + { + EndBlock(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/ConcussionBlow.cs b/Scripts/Items/Weapons/Abilities/ConcussionBlow.cs index ce4aa718e..285e89332 100644 --- a/Scripts/Items/Weapons/Abilities/ConcussionBlow.cs +++ b/Scripts/Items/Weapons/Abilities/ConcussionBlow.cs @@ -2,51 +2,51 @@ using System; namespace Server.Items { - /// - /// This devastating strike is most effective against those who are in good health and whose reserves of mana are low, or vice versa. - /// - public class ConcussionBlow : WeaponAbility - { - public ConcussionBlow() - { - } + /// + /// This devastating strike is most effective against those who are in good health and whose reserves of mana are low, or vice + /// versa. + /// + public class ConcussionBlow : WeaponAbility + { + public override int BaseMana => 25; - public override int BaseMana => 25; + public override bool OnBeforeDamage(Mobile attacker, Mobile defender) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return false; - public override bool OnBeforeDamage( Mobile attacker, Mobile defender ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return false; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1060165); // You have delivered a concussion! + defender.SendLocalizedMessage(1060166); // You feel disoriented! - attacker.SendLocalizedMessage( 1060165 ); // You have delivered a concussion! - defender.SendLocalizedMessage( 1060166 ); // You feel disoriented! + defender.PlaySound(0x213); + defender.FixedParticles(0x377A, 1, 32, 9949, 1153, 0, EffectLayer.Head); - defender.PlaySound( 0x213 ); - defender.FixedParticles( 0x377A, 1, 32, 9949, 1153, 0, EffectLayer.Head ); + Effects.SendMovingParticles( + new Entity(Serial.Zero, new Point3D(defender.X, defender.Y, defender.Z + 10), defender.Map), + new Entity(Serial.Zero, new Point3D(defender.X, defender.Y, defender.Z + 20), defender.Map), 0x36FE, 1, 0, + false, false, 1133, 3, 9501, 1, 0, EffectLayer.Waist, 0x100); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( defender.X, defender.Y, defender.Z + 10 ), defender.Map ), new Entity( Serial.Zero, new Point3D( defender.X, defender.Y, defender.Z + 20 ), defender.Map ), 0x36FE, 1, 0, false, false, 1133, 3, 9501, 1, 0, EffectLayer.Waist, 0x100 ); + int damage = 10; // Base damage is 10. - int damage = 10; // Base damage is 10. + if (defender.HitsMax > 0) + { + double hitsPercent = defender.Hits / (double)defender.HitsMax * 100.0; - if ( defender.HitsMax > 0 ) - { - double hitsPercent = ( (double)defender.Hits / (double)defender.HitsMax ) * 100.0; + double manaPercent = 0; - double manaPercent = 0; + if (defender.ManaMax > 0) + manaPercent = defender.Mana / (double)defender.ManaMax * 100.0; - if ( defender.ManaMax > 0 ) - manaPercent = ( (double)defender.Mana / (double)defender.ManaMax ) * 100.0; + damage += Math.Min((int)(Math.Abs(hitsPercent - manaPercent) / 4), 20); + } - damage += Math.Min( (int)(Math.Abs( hitsPercent - manaPercent ) / 4), 20 ); - } + // Total damage is 10 + (0~20) = 10~30, physical, non-resistable. - // Total damage is 10 + (0~20) = 10~30, physical, non-resistable. + defender.Damage(damage, attacker); - defender.Damage( damage, attacker ); - - return true; - } - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/CrushingBlow.cs b/Scripts/Items/Weapons/Abilities/CrushingBlow.cs index 6c0b17092..d45108a82 100644 --- a/Scripts/Items/Weapons/Abilities/CrushingBlow.cs +++ b/Scripts/Items/Weapons/Abilities/CrushingBlow.cs @@ -1,32 +1,31 @@ namespace Server.Items { - /// - /// Also known as the Haymaker, this attack dramatically increases the damage done by a weapon reaching its mark. - /// - public class CrushingBlow : WeaponAbility - { - public CrushingBlow() - { - } - - public override int BaseMana => 25; - public override double DamageScalar => 1.5; + /// + /// Also known as the Haymaker, this attack dramatically increases the damage done by a weapon reaching its mark. + /// + public class CrushingBlow : WeaponAbility + { + public override int BaseMana => 25; + public override double DamageScalar => 1.5; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - attacker.SendLocalizedMessage( 1060090 ); // You have delivered a crushing blow! - defender.SendLocalizedMessage( 1060091 ); // You take extra damage from the crushing attack! + attacker.SendLocalizedMessage(1060090); // You have delivered a crushing blow! + defender.SendLocalizedMessage(1060091); // You take extra damage from the crushing attack! - defender.PlaySound( 0x1E1 ); - defender.FixedParticles( 0, 1, 0, 9946, EffectLayer.Head ); + defender.PlaySound(0x1E1); + defender.FixedParticles(0, 1, 0, 9946, EffectLayer.Head); - Effects.SendMovingParticles( new Entity( Serial.Zero, new Point3D( defender.X, defender.Y, defender.Z + 50 ), defender.Map ), new Entity( Serial.Zero, new Point3D( defender.X, defender.Y, defender.Z + 20 ), defender.Map ), 0xFB4, 1, 0, false, false, 0, 3, 9501, 1, 0, EffectLayer.Head, 0x100 ); - } - } -} + Effects.SendMovingParticles( + new Entity(Serial.Zero, new Point3D(defender.X, defender.Y, defender.Z + 50), defender.Map), + new Entity(Serial.Zero, new Point3D(defender.X, defender.Y, defender.Z + 20), defender.Map), 0xFB4, 1, 0, + false, false, 0, 3, 9501, 1, 0, EffectLayer.Head, 0x100); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/DefenseMastery.cs b/Scripts/Items/Weapons/Abilities/DefenseMastery.cs index 08671c827..0a2695618 100644 --- a/Scripts/Items/Weapons/Abilities/DefenseMastery.cs +++ b/Scripts/Items/Weapons/Abilities/DefenseMastery.cs @@ -3,95 +3,96 @@ using System.Collections; namespace Server.Items { - /// - /// Raises your physical resistance for a short time while lowering your ability to inflict damage. Requires Bushido or Ninjitsu skill. - /// - public class DefenseMastery : WeaponAbility - { - public DefenseMastery() - { - } + /// + /// Raises your physical resistance for a short time while lowering your ability to inflict damage. Requires Bushido or + /// Ninjitsu skill. + /// + public class DefenseMastery : WeaponAbility + { + private static Hashtable m_Table = new Hashtable(); - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 && GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1063347, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! - return false; - } + public override int BaseMana => 30; - return base.CheckSkills( from ); - } + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0 && GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1063347, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! + return false; + } - public override int BaseMana => 30; + return base.CheckSkills(from); + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - attacker.SendLocalizedMessage( 1063353 ); // You perform a masterful defense! + attacker.SendLocalizedMessage(1063353); // You perform a masterful defense! - attacker.FixedParticles( 0x375A, 1, 17, 0x7F2, 0x3E8, 0x3, EffectLayer.Waist ); + attacker.FixedParticles(0x375A, 1, 17, 0x7F2, 0x3E8, 0x3, EffectLayer.Waist); - int modifier = (int)(30.0 * ((Math.Max( attacker.Skills[SkillName.Bushido].Value, attacker.Skills[SkillName.Ninjitsu].Value ) - 50.0) / 70.0)); + int modifier = + (int)(30.0 * + ((Math.Max(attacker.Skills[SkillName.Bushido].Value, attacker.Skills[SkillName.Ninjitsu].Value) - + 50.0) / 70.0)); - if ( m_Table[attacker] is DefenseMasteryInfo info ) - EndDefense( (object)info ); + if (m_Table[attacker] is DefenseMasteryInfo info) + EndDefense(info); - ResistanceMod mod = new ResistanceMod( ResistanceType.Physical, 50 + modifier ); - attacker.AddResistanceMod( mod ); + ResistanceMod mod = new ResistanceMod(ResistanceType.Physical, 50 + modifier); + attacker.AddResistanceMod(mod); - info = new DefenseMasteryInfo( attacker, 80 - modifier, mod ); - info.m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 3.0 ), new TimerStateCallback( EndDefense ), info ); + info = new DefenseMasteryInfo(attacker, 80 - modifier, mod); + info.m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(3.0), new TimerStateCallback(EndDefense), info); - m_Table[attacker] = info; + m_Table[attacker] = info; - attacker.Delta( MobileDelta.WeaponDamage ); - } + attacker.Delta(MobileDelta.WeaponDamage); + } - private class DefenseMasteryInfo - { - public Mobile m_From; - public Timer m_Timer; - public int m_DamageMalus; - public ResistanceMod m_Mod; + public static bool GetMalus(Mobile targ, ref int damageMalus) + { + if (!(m_Table[targ] is DefenseMasteryInfo info)) + return false; - public DefenseMasteryInfo( Mobile from, int damageMalus, ResistanceMod mod ) - { - m_From = from; - m_DamageMalus = damageMalus; - m_Mod = mod; - } - } + damageMalus = info.m_DamageMalus; + return true; + } - private static Hashtable m_Table = new Hashtable(); + private static void EndDefense(object state) + { + DefenseMasteryInfo info = (DefenseMasteryInfo)state; - public static bool GetMalus( Mobile targ, ref int damageMalus ) - { - if ( !(m_Table[targ] is DefenseMasteryInfo info) ) - return false; + if (info.m_Mod != null) + info.m_From.RemoveResistanceMod(info.m_Mod); - damageMalus = info.m_DamageMalus; - return true; - } + info.m_Timer?.Stop(); - private static void EndDefense( object state ) - { - DefenseMasteryInfo info = (DefenseMasteryInfo)state; + // No message is sent to the player. - if ( info.m_Mod != null ) - info.m_From.RemoveResistanceMod( info.m_Mod ); + m_Table.Remove(info.m_From); - info.m_Timer?.Stop(); + info.m_From.Delta(MobileDelta.WeaponDamage); + } - // No message is sent to the player. + private class DefenseMasteryInfo + { + public int m_DamageMalus; + public Mobile m_From; + public ResistanceMod m_Mod; + public Timer m_Timer; - m_Table.Remove( info.m_From ); - - info.m_From.Delta( MobileDelta.WeaponDamage ); - } - } -} + public DefenseMasteryInfo(Mobile from, int damageMalus, ResistanceMod mod) + { + m_From = from; + m_DamageMalus = damageMalus; + m_Mod = mod; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/Disarm.cs b/Scripts/Items/Weapons/Abilities/Disarm.cs index f2ab34f5f..1efaa9e5a 100644 --- a/Scripts/Items/Weapons/Abilities/Disarm.cs +++ b/Scripts/Items/Weapons/Abilities/Disarm.cs @@ -2,81 +2,77 @@ using System; namespace Server.Items { - /// - /// This attack allows you to disarm your foe. - /// Now in Age of Shadows, a successful Disarm leaves the victim unable to re-arm another weapon for several seconds. - /// - public class Disarm : WeaponAbility - { - public Disarm() - { - } + /// + /// This attack allows you to disarm your foe. + /// Now in Age of Shadows, a successful Disarm leaves the victim unable to re-arm another weapon for several seconds. + /// + public class Disarm : WeaponAbility + { + public static readonly TimeSpan BlockEquipDuration = TimeSpan.FromSeconds(5.0); - public override int BaseMana => 20; + public override int BaseMana => 20; - // No longer active in pub21: - /*public override bool CheckSkills( Mobile from ) - { - if ( !base.CheckSkills( from ) ) - return false; + // No longer active in pub21: + /*public override bool CheckSkills( Mobile from ) + { + if ( !base.CheckSkills( from ) ) + return false; - if ( !(from.Weapon is Fists) ) - return true; + if ( !(from.Weapon is Fists) ) + return true; - Skill skill = from.Skills[SkillName.ArmsLore]; + Skill skill = from.Skills[SkillName.ArmsLore]; - if ( skill != null && skill.Base >= 80.0 ) - return true; + if ( skill != null && skill.Base >= 80.0 ) + return true; - from.SendLocalizedMessage( 1061812 ); // You lack the required skill in armslore to perform that attack! + from.SendLocalizedMessage( 1061812 ); // You lack the required skill in armslore to perform that attack! - return false; - }*/ + return false; + }*/ - public override bool RequiresTactics( Mobile from ) - { - if ( !(from.Weapon is BaseWeapon weapon) ) - return false; + public override bool RequiresTactics(Mobile from) + { + if (!(from.Weapon is BaseWeapon weapon)) + return false; - return weapon.Skill != SkillName.Wrestling; - } + return weapon.Skill != SkillName.Wrestling; + } - public static readonly TimeSpan BlockEquipDuration = TimeSpan.FromSeconds( 5.0 ); + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + Item toDisarm = defender.FindItemOnLayer(Layer.OneHanded); - Item toDisarm = defender.FindItemOnLayer( Layer.OneHanded ); + if (toDisarm == null || !toDisarm.Movable) + toDisarm = defender.FindItemOnLayer(Layer.TwoHanded); - if ( toDisarm == null || !toDisarm.Movable ) - toDisarm = defender.FindItemOnLayer( Layer.TwoHanded ); + Container pack = defender.Backpack; - Container pack = defender.Backpack; + if (pack == null || toDisarm != null && !toDisarm.Movable) + { + attacker.SendLocalizedMessage(1004001); // You cannot disarm your opponent. + } + else if (toDisarm == null || toDisarm is BaseShield || toDisarm is Spellbook && !Core.ML) + { + attacker.SendLocalizedMessage(1060849); // Your target is already unarmed! + } + else if (CheckMana(attacker, true)) + { + attacker.SendLocalizedMessage(1060092); // You disarm their weapon! + defender.SendLocalizedMessage(1060093); // Your weapon has been disarmed! - if ( pack == null || (toDisarm != null && !toDisarm.Movable) ) - { - attacker.SendLocalizedMessage( 1004001 ); // You cannot disarm your opponent. - } - else if (toDisarm == null || toDisarm is BaseShield || toDisarm is Spellbook && !Core.ML ) - { - attacker.SendLocalizedMessage( 1060849 ); // Your target is already unarmed! - } - else if ( CheckMana( attacker, true ) ) - { - attacker.SendLocalizedMessage( 1060092 ); // You disarm their weapon! - defender.SendLocalizedMessage( 1060093 ); // Your weapon has been disarmed! + defender.PlaySound(0x3B9); + defender.FixedParticles(0x37BE, 232, 25, 9948, EffectLayer.LeftHand); - defender.PlaySound( 0x3B9 ); - defender.FixedParticles( 0x37BE, 232, 25, 9948, EffectLayer.LeftHand ); + pack.DropItem(toDisarm); - pack.DropItem( toDisarm ); - - BaseWeapon.BlockEquip( defender, BlockEquipDuration ); - } - } - } -} + BaseWeapon.BlockEquip(defender, BlockEquipDuration); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/Dismount.cs b/Scripts/Items/Weapons/Abilities/Dismount.cs index 6b015900d..8b3dd43cf 100644 --- a/Scripts/Items/Weapons/Abilities/Dismount.cs +++ b/Scripts/Items/Weapons/Abilities/Dismount.cs @@ -1,109 +1,94 @@ using System; using Server.Mobiles; +using Server.Spells.Ninjitsu; namespace Server.Items { - /// - /// Perfect for the foot-soldier, the Dismount special attack can unseat a mounted opponent. - /// The fighter using this ability must be on his own two feet and not in the saddle of a steed - /// (with one exception: players may use a lance to dismount other players while mounted). - /// If it works, the target will be knocked off his own mount and will take some extra damage from the fall! - /// - public class Dismount : WeaponAbility - { - public Dismount() - { - } + /// + /// Perfect for the foot-soldier, the Dismount special attack can unseat a mounted opponent. + /// The fighter using this ability must be on his own two feet and not in the saddle of a steed + /// (with one exception: players may use a lance to dismount other players while mounted). + /// If it works, the target will be knocked off his own mount and will take some extra damage from the fall! + /// + public class Dismount : WeaponAbility + { + public static readonly TimeSpan RemountDelay = TimeSpan.FromSeconds(10.0); - public override int BaseMana => 20; + public override int BaseMana => 20; - public override bool Validate( Mobile from ) - { - if ( !base.Validate( from ) ) - return false; + public override bool Validate(Mobile from) + { + if (!base.Validate(from)) + return false; - if ( from.Mounted && !(from.Weapon is Lance) ) - { - from.SendLocalizedMessage( 1061283 ); // You cannot perform that attack while mounted! - return false; - } + if (from.Mounted && !(from.Weapon is Lance)) + { + from.SendLocalizedMessage(1061283); // You cannot perform that attack while mounted! + return false; + } - return true; - } + return true; + } - public static readonly TimeSpan RemountDelay = TimeSpan.FromSeconds( 10.0 ); + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) ) - return; + if (defender is ChaosDragoon || defender is ChaosDragoonElite) + return; - if ( defender is ChaosDragoon || defender is ChaosDragoonElite ) - return; + if (attacker.Mounted && (!(attacker.Weapon is Lance) || !(defender.Weapon is Lance)) + ) // TODO: Should there be a message here? + return; - if ( attacker.Mounted && ( !(attacker.Weapon is Lance) || !(defender.Weapon is Lance) ) ) // TODO: Should there be a message here? - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + IMount mount = defender.Mount; - IMount mount = defender.Mount; + if (mount == null && !AnimalForm.UnderTransformation(defender)) + { + attacker.SendLocalizedMessage(1060848); // This attack only works on mounted targets + return; + } - if (mount == null && !Spells.Ninjitsu.AnimalForm.UnderTransformation( defender ) ) - { - attacker.SendLocalizedMessage( 1060848 ); // This attack only works on mounted targets - return; - } + if (!CheckMana(attacker, true)) + return; - if ( !CheckMana( attacker, true ) ) - return; + if (Core.ML && attacker is LesserHiryu && 0.8 >= Utility.RandomDouble()) + return; //Lesser Hiryu have an 80% chance of missing this attack - if ( Core.ML && attacker is LesserHiryu && 0.8 >= Utility.RandomDouble() ) - { - return; //Lesser Hiryu have an 80% chance of missing this attack - } + attacker.SendLocalizedMessage(1060082); // The force of your attack has dislodged them from their mount! - attacker.SendLocalizedMessage( 1060082 ); // The force of your attack has dislodged them from their mount! + if (attacker.Mounted) + defender.SendLocalizedMessage(1062315); // You fall off your mount! + else + defender.SendLocalizedMessage(1060083); // You fall off of your mount and take damage! - if ( attacker.Mounted ) - defender.SendLocalizedMessage( 1062315 ); // You fall off your mount! - else - defender.SendLocalizedMessage( 1060083 ); // You fall off of your mount and take damage! + defender.PlaySound(0x140); + defender.FixedParticles(0x3728, 10, 15, 9955, EffectLayer.Waist); - defender.PlaySound( 0x140 ); - defender.FixedParticles( 0x3728, 10, 15, 9955, EffectLayer.Waist ); + if (defender is PlayerMobile mobile) + { + if (AnimalForm.UnderTransformation(mobile)) + mobile.SendLocalizedMessage(1114066, attacker.Name); // ~1_NAME~ knocked you out of animal form! + else if (mobile.Mounted) mobile.SendLocalizedMessage(1040023); // You have been knocked off of your mount! - if (defender is PlayerMobile mobile) - { - if (Spells.Ninjitsu.AnimalForm.UnderTransformation(mobile)) - { - mobile.SendLocalizedMessage(1114066, attacker.Name); // ~1_NAME~ knocked you out of animal form! - } - else if (mobile.Mounted) - { - mobile.SendLocalizedMessage(1040023); // You have been knocked off of your mount! - } + mobile.SetMountBlock(BlockMountType.Dazed, TimeSpan.FromSeconds(10), true); + } + else + { + defender.Mount.Rider = null; + } - mobile.SetMountBlock(BlockMountType.Dazed, TimeSpan.FromSeconds(10), true); - } - else - { - defender.Mount.Rider = null; - } + if (attacker is PlayerMobile playerMobile) + playerMobile.SetMountBlock(BlockMountType.DismountRecovery, RemountDelay, true); + else if (Core.ML && attacker is BaseCreature bc) + if (bc.ControlMaster is PlayerMobile pm) + pm.SetMountBlock(BlockMountType.DismountRecovery, RemountDelay, false); - if ( attacker is PlayerMobile playerMobile ) - { - playerMobile.SetMountBlock(BlockMountType.DismountRecovery, RemountDelay, true ); - } - else if ( Core.ML && attacker is BaseCreature bc ) - { - if ( bc.ControlMaster is PlayerMobile pm ) - { - pm.SetMountBlock(BlockMountType.DismountRecovery, RemountDelay, false ); - } - } - - if ( !attacker.Mounted ) - AOS.Damage( defender, attacker, Utility.RandomMinMax( 15, 25 ), 100, 0, 0, 0, 0 ); - } - } -} + if (!attacker.Mounted) + AOS.Damage(defender, attacker, Utility.RandomMinMax(15, 25), 100, 0, 0, 0, 0); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/Disrobe.cs b/Scripts/Items/Weapons/Abilities/Disrobe.cs index 7c2680f72..2baaf5952 100644 --- a/Scripts/Items/Weapons/Abilities/Disrobe.cs +++ b/Scripts/Items/Weapons/Abilities/Disrobe.cs @@ -2,48 +2,44 @@ using System; namespace Server.Items { - /// - /// This attack allows you to disrobe your foe. - /// - public class Disrobe : WeaponAbility - { - public Disrobe() - { - } + /// + /// This attack allows you to disrobe your foe. + /// + public class Disrobe : WeaponAbility + { + public static readonly TimeSpan BlockEquipDuration = TimeSpan.FromSeconds(5.0); - public override int BaseMana => 20; // Not Sure what amount of mana a creature uses. + public override int BaseMana => 20; // Not Sure what amount of mana a creature uses. - public static readonly TimeSpan BlockEquipDuration = TimeSpan.FromSeconds( 5.0 ); + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) ) - return; + ClearCurrentAbility(attacker); + Item toDisrobe = defender.FindItemOnLayer(Layer.InnerTorso); - ClearCurrentAbility( attacker ); - Item toDisrobe = defender.FindItemOnLayer(Layer.InnerTorso); + if (toDisrobe == null || !toDisrobe.Movable) + toDisrobe = defender.FindItemOnLayer(Layer.OuterTorso); - if ( toDisrobe == null || !toDisrobe.Movable ) - toDisrobe = defender.FindItemOnLayer( Layer.OuterTorso ); + Container pack = defender.Backpack; - Container pack = defender.Backpack; + if (pack == null || toDisrobe == null || !toDisrobe.Movable) + { + attacker.SendLocalizedMessage(1004001); // You cannot disarm your opponent. + } + else if (CheckMana(attacker, true)) + { + //attacker.SendLocalizedMessage( 1060092 ); // You disarm their weapon! + defender.SendLocalizedMessage(1062002); // You can no longer wear your ~1_ARMOR~ - if ( pack == null || toDisrobe == null || !toDisrobe.Movable ) - { - attacker.SendLocalizedMessage(1004001); // You cannot disarm your opponent. - } - else if ( CheckMana( attacker, true ) ) - { - //attacker.SendLocalizedMessage( 1060092 ); // You disarm their weapon! - defender.SendLocalizedMessage(1062002); // You can no longer wear your ~1_ARMOR~ + defender.PlaySound(0x3B9); + //defender.FixedParticles( 0x37BE, 232, 25, 9948, EffectLayer.InnerTorso ); - defender.PlaySound( 0x3B9 ); - //defender.FixedParticles( 0x37BE, 232, 25, 9948, EffectLayer.InnerTorso ); + pack.DropItem(toDisrobe); - pack.DropItem( toDisrobe ); - - BaseWeapon.BlockEquip( defender, BlockEquipDuration ); - } - } - } -} + BaseWeapon.BlockEquip(defender, BlockEquipDuration); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/DoubleShot.cs b/Scripts/Items/Weapons/Abilities/DoubleShot.cs index 42ce7ccda..973f8219d 100644 --- a/Scripts/Items/Weapons/Abilities/DoubleShot.cs +++ b/Scripts/Items/Weapons/Abilities/DoubleShot.cs @@ -1,63 +1,60 @@ namespace Server.Items { - /// - /// Send two arrows flying at your opponent if you're mounted. Requires Bushido or Ninjitsu skill. - /// - public class DoubleShot : WeaponAbility - { - public DoubleShot() - { - } + /// + /// Send two arrows flying at your opponent if you're mounted. Requires Bushido or Ninjitsu skill. + /// + public class DoubleShot : WeaponAbility + { + public override int BaseMana => 30; - public override int BaseMana => 30; + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0 && GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1063347, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! + return false; + } - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 && GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1063347, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! - return false; - } + return base.CheckSkills(from); + } - return base.CheckSkills( from ); - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + Use(attacker, defender); + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - Use( attacker, defender ); - } + public override void OnMiss(Mobile attacker, Mobile defender) + { + Use(attacker, defender); + } - public override void OnMiss( Mobile attacker, Mobile defender ) - { - Use( attacker, defender ); - } + public override bool Validate(Mobile from) + { + if (base.Validate(from)) + { + if (from.Mounted) + return true; + from.SendLocalizedMessage(1070770); // You can only execute this attack while mounted! + ClearCurrentAbility(from); + } - public override bool Validate( Mobile from ) - { - if ( base.Validate( from ) ) - { - if ( from.Mounted ) - return true; - from.SendLocalizedMessage( 1070770 ); // You can only execute this attack while mounted! - ClearCurrentAbility( from ); - } + return false; + } - return false; - } + public void Use(Mobile attacker, Mobile defender) + { + if (!Validate(attacker) || !CheckMana(attacker, true) || attacker.Weapon == null) //sanity + return; - public void Use( Mobile attacker, Mobile defender ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) || attacker.Weapon == null ) //sanity - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1063348); // You launch two shots at once! + defender.SendLocalizedMessage(1063349); // You're attacked with a barrage of shots! - attacker.SendLocalizedMessage( 1063348 ); // You launch two shots at once! - defender.SendLocalizedMessage( 1063349 ); // You're attacked with a barrage of shots! + defender.FixedParticles(0x37B9, 1, 19, 0x251D, EffectLayer.Waist); - defender.FixedParticles( 0x37B9, 1, 19, 0x251D, EffectLayer.Waist ); - - attacker.Weapon.OnSwing( attacker, defender ); - } - } -} + attacker.Weapon.OnSwing(attacker, defender); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/DoubleStrike.cs b/Scripts/Items/Weapons/Abilities/DoubleStrike.cs index 1c0a8d5de..a9e25450d 100644 --- a/Scripts/Items/Weapons/Abilities/DoubleStrike.cs +++ b/Scripts/Items/Weapons/Abilities/DoubleStrike.cs @@ -1,55 +1,52 @@ namespace Server.Items { - /// - /// The highly skilled warrior can use this special attack to make two quick swings in succession. - /// Landing both blows would be devastating! - /// - public class DoubleStrike : WeaponAbility - { - public DoubleStrike() - { - } + /// + /// The highly skilled warrior can use this special attack to make two quick swings in succession. + /// Landing both blows would be devastating! + /// + public class DoubleStrike : WeaponAbility + { + public override int BaseMana => 30; + public override double DamageScalar => 0.9; - public override int BaseMana => 30; - public override double DamageScalar => 0.9; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1060084); // You attack with lightning speed! + defender.SendLocalizedMessage(1060085); // Your attacker strikes with lightning speed! - attacker.SendLocalizedMessage( 1060084 ); // You attack with lightning speed! - defender.SendLocalizedMessage( 1060085 ); // Your attacker strikes with lightning speed! + defender.PlaySound(0x3BB); + defender.FixedEffect(0x37B9, 244, 25); - defender.PlaySound( 0x3BB ); - defender.FixedEffect( 0x37B9, 244, 25 ); + // Swing again: - // Swing again: + // If no combatant, wrong map, one of us is a ghost, or cannot see, or deleted, then stop combat + if (defender == null || defender.Deleted || attacker.Deleted || defender.Map != attacker.Map || + !defender.Alive || !attacker.Alive || !attacker.CanSee(defender)) + { + attacker.Combatant = null; + return; + } - // If no combatant, wrong map, one of us is a ghost, or cannot see, or deleted, then stop combat - if ( defender == null || defender.Deleted || attacker.Deleted || defender.Map != attacker.Map || !defender.Alive || !attacker.Alive || !attacker.CanSee( defender ) ) - { - attacker.Combatant = null; - return; - } + IWeapon weapon = attacker.Weapon; - IWeapon weapon = attacker.Weapon; + if (weapon == null) + return; - if ( weapon == null ) - return; + if (!attacker.InRange(defender, weapon.MaxRange)) + return; - if ( !attacker.InRange( defender, weapon.MaxRange ) ) - return; - - if ( attacker.InLOS( defender ) ) - { - BaseWeapon.InDoubleStrike = true; - attacker.RevealingAction(); - attacker.NextCombatTime = Core.TickCount + (int)weapon.OnSwing(attacker, defender).TotalMilliseconds; - BaseWeapon.InDoubleStrike = false; - } - } - } -} + if (attacker.InLOS(defender)) + { + BaseWeapon.InDoubleStrike = true; + attacker.RevealingAction(); + attacker.NextCombatTime = Core.TickCount + (int)weapon.OnSwing(attacker, defender).TotalMilliseconds; + BaseWeapon.InDoubleStrike = false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/DualWield.cs b/Scripts/Items/Weapons/Abilities/DualWield.cs index 6a66abc5b..551425b5f 100644 --- a/Scripts/Items/Weapons/Abilities/DualWield.cs +++ b/Scripts/Items/Weapons/Abilities/DualWield.cs @@ -1,75 +1,72 @@ - using System; using System.Collections; namespace Server.Items { - /// - /// Attack faster as you swing with both weapons. - /// - public class DualWield : WeaponAbility - { - public static Hashtable Registry { get; } = new Hashtable(); + /// + /// Attack faster as you swing with both weapons. + /// + public class DualWield : WeaponAbility + { + public static Hashtable Registry{ get; } = new Hashtable(); - public DualWield() - { - } + public override int BaseMana => 30; - public override int BaseMana => 30; + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0) + { + from.SendLocalizedMessage(1063352, + "50"); // You need ~1_SKILL_REQUIREMENT~ Ninjitsu skill to perform that attack! + return false; + } - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 ) - { - from.SendLocalizedMessage( 1063352, "50" ); // You need ~1_SKILL_REQUIREMENT~ Ninjitsu skill to perform that attack! - return false; - } + return base.CheckSkills(from); + } - return base.CheckSkills( from ); - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + if (Registry.Contains(attacker)) + { + DualWieldTimer existingtimer = (DualWieldTimer)Registry[attacker]; + existingtimer.Stop(); + Registry.Remove(attacker); + } - if ( Registry.Contains( attacker ) ) - { - DualWieldTimer existingtimer = (DualWieldTimer)Registry[attacker]; - existingtimer.Stop(); - Registry.Remove( attacker ); - } + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1063362); // You dually wield for increased speed! - attacker.SendLocalizedMessage( 1063362 ); // You dually wield for increased speed! + attacker.FixedParticles(0x3779, 1, 15, 0x7F6, 0x3E8, 3, EffectLayer.LeftHand); - attacker.FixedParticles( 0x3779, 1, 15, 0x7F6, 0x3E8, 3, EffectLayer.LeftHand ); + Timer t = new DualWieldTimer(attacker, + (int)(20.0 + 3.0 * (attacker.Skills[SkillName.Ninjitsu].Value - 50.0) / 7.0)); //20-50 % increase - Timer t = new DualWieldTimer( attacker, (int)(20.0 + 3.0 * (attacker.Skills[SkillName.Ninjitsu].Value - 50.0) / 7.0) ); //20-50 % increase + t.Start(); + Registry.Add(attacker, t); + } - t.Start(); - Registry.Add( attacker, t ); - } + public class DualWieldTimer : Timer + { + private Mobile m_Owner; - public class DualWieldTimer : Timer - { - private Mobile m_Owner; + public DualWieldTimer(Mobile owner, int bonusSwingSpeed) + : base(TimeSpan.FromSeconds(6.0)) + { + m_Owner = owner; + BonusSwingSpeed = bonusSwingSpeed; + Priority = TimerPriority.FiftyMS; + } - public int BonusSwingSpeed { get; } + public int BonusSwingSpeed{ get; } - public DualWieldTimer( Mobile owner, int bonusSwingSpeed ) - : base( TimeSpan.FromSeconds( 6.0 ) ) - { - m_Owner = owner; - BonusSwingSpeed = bonusSwingSpeed; - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - Registry.Remove( m_Owner ); - } - } - } -} + protected override void OnTick() + { + Registry.Remove(m_Owner); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/Feint.cs b/Scripts/Items/Weapons/Abilities/Feint.cs index 86aa26bb2..771353201 100644 --- a/Scripts/Items/Weapons/Abilities/Feint.cs +++ b/Scripts/Items/Weapons/Abilities/Feint.cs @@ -1,76 +1,74 @@ - using System; using System.Collections; namespace Server.Items { - /// - /// Gain a defensive advantage over your primary opponent for a short time. - /// - public class Feint : WeaponAbility - { - public static Hashtable Registry { get; } = new Hashtable(); + /// + /// Gain a defensive advantage over your primary opponent for a short time. + /// + public class Feint : WeaponAbility + { + public static Hashtable Registry{ get; } = new Hashtable(); - public Feint() - { - } + public override int BaseMana => 30; - public override int BaseMana => 30; + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0 && GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1063347, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! + return false; + } - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 && GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1063347, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! - return false; - } + return base.CheckSkills(from); + } - return base.CheckSkills( from ); - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + if (Registry.Contains(defender)) + { + FeintTimer existingtimer = (FeintTimer)Registry[defender]; + existingtimer.Stop(); + Registry.Remove(defender); + } - if ( Registry.Contains( defender ) ) - { - FeintTimer existingtimer = (FeintTimer)Registry[defender]; - existingtimer.Stop(); - Registry.Remove( defender ); - } + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1063360); // You baffle your target with a feint! + defender.SendLocalizedMessage(1063361); // You were deceived by an attacker's feint! - attacker.SendLocalizedMessage( 1063360 ); // You baffle your target with a feint! - defender.SendLocalizedMessage( 1063361 ); // You were deceived by an attacker's feint! + attacker.FixedParticles(0x3728, 1, 13, 0x7F3, 0x962, 0, EffectLayer.Waist); - attacker.FixedParticles( 0x3728, 1, 13, 0x7F3, 0x962, 0, EffectLayer.Waist ); + Timer t = new FeintTimer(defender, + (int)(20.0 + 3.0 * (Math.Max(attacker.Skills[SkillName.Ninjitsu].Value, + attacker.Skills[SkillName.Bushido].Value) - 50.0) / 7.0)); //20-50 % decrease - Timer t = new FeintTimer( defender, (int)(20.0 + 3.0 * (Math.Max( attacker.Skills[SkillName.Ninjitsu].Value, attacker.Skills[SkillName.Bushido].Value ) - 50.0) / 7.0) ); //20-50 % decrease + t.Start(); + Registry.Add(defender, t); + } - t.Start(); - Registry.Add( defender, t ); - } + public class FeintTimer : Timer + { + private Mobile m_Defender; - public class FeintTimer : Timer - { - private Mobile m_Defender; + public FeintTimer(Mobile defender, int swingSpeedReduction) + : base(TimeSpan.FromSeconds(6.0)) + { + m_Defender = defender; + SwingSpeedReduction = swingSpeedReduction; + Priority = TimerPriority.FiftyMS; + } - public int SwingSpeedReduction { get; } + public int SwingSpeedReduction{ get; } - public FeintTimer( Mobile defender, int swingSpeedReduction ) - : base( TimeSpan.FromSeconds( 6.0 ) ) - { - m_Defender = defender; - SwingSpeedReduction = swingSpeedReduction; - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - Registry.Remove( m_Defender ); - } - } - } -} + protected override void OnTick() + { + Registry.Remove(m_Defender); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/FrenziedWhirlwind.cs b/Scripts/Items/Weapons/Abilities/FrenziedWhirlwind.cs index d3b8ef581..246a98c91 100644 --- a/Scripts/Items/Weapons/Abilities/FrenziedWhirlwind.cs +++ b/Scripts/Items/Weapons/Abilities/FrenziedWhirlwind.cs @@ -4,158 +4,157 @@ using Server.Spells; namespace Server.Items { - /// - /// A quick attack to all enemies in range of your weapon that causes damage over time. Requires Bushido or Ninjitsu skill. - /// - public class FrenziedWhirlwind : WeaponAbility - { - public FrenziedWhirlwind() - { - } + /// + /// A quick attack to all enemies in range of your weapon that causes damage over time. Requires Bushido or Ninjitsu skill. + /// + public class FrenziedWhirlwind : WeaponAbility + { + public override int BaseMana => 30; - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 && GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1063347, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! - return false; - } + public static Hashtable Registry{ get; } = new Hashtable(); - return base.CheckSkills( from ); - } + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0 && GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1063347, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido or Ninjitsu skill to perform that attack! + return false; + } - public override int BaseMana => 30; + return base.CheckSkills(from); + } - public static Hashtable Registry { get; } = new Hashtable(); + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker)) //Mana check after check that there are targets + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) ) //Mana check after check that there are targets - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + Map map = attacker.Map; - Map map = attacker.Map; + if (map == null) + return; - if ( map == null ) - return; + if (!(attacker.Weapon is BaseWeapon weapon)) + return; - if ( !(attacker.Weapon is BaseWeapon weapon) ) - return; + ArrayList list = new ArrayList(); - ArrayList list = new ArrayList(); + foreach (Mobile m in attacker.GetMobilesInRange(1)) + list.Add(m); - foreach( Mobile m in attacker.GetMobilesInRange( 1 ) ) - list.Add( m ); + ArrayList targets = new ArrayList(); - ArrayList targets = new ArrayList(); + for (int i = 0; i < list.Count; ++i) + { + Mobile m = (Mobile)list[i]; - for( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; + if (m != defender && m != attacker && SpellHelper.ValidIndirectTarget(attacker, m)) + { + if (m == null || m.Deleted || m.Map != attacker.Map || !m.Alive || !attacker.CanSee(m) || + !attacker.CanBeHarmful(m)) + continue; - if ( m != defender && m != attacker && SpellHelper.ValidIndirectTarget( attacker, m ) ) - { - if ( m == null || m.Deleted || m.Map != attacker.Map || !m.Alive || !attacker.CanSee( m ) || !attacker.CanBeHarmful( m ) ) - continue; + if (!attacker.InRange(m, weapon.MaxRange)) + continue; - if ( !attacker.InRange( m, weapon.MaxRange ) ) - continue; + if (attacker.InLOS(m)) + targets.Add(m); + } + } - if ( attacker.InLOS( m ) ) - targets.Add( m ); - } - } + if (targets.Count > 0) + { + if (!CheckMana(attacker, true)) + return; - if ( targets.Count > 0 ) - { - if ( !CheckMana( attacker, true ) ) - return; + attacker.FixedEffect(0x3728, 10, 15); + attacker.PlaySound(0x2A1); - attacker.FixedEffect( 0x3728, 10, 15 ); - attacker.PlaySound( 0x2A1 ); + // 5-15 damage + int amount = (int)(10.0 * ((Math.Max(attacker.Skills[SkillName.Bushido].Value, + attacker.Skills[SkillName.Ninjitsu].Value) - 50.0) / 70.0 + 5)); - // 5-15 damage - int amount = (int)(10.0 * ((Math.Max( attacker.Skills[SkillName.Bushido].Value, attacker.Skills[SkillName.Ninjitsu].Value ) - 50.0) / 70.0 + 5)); + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = (Mobile)targets[i]; + attacker.DoHarmful(m, true); - for( int i = 0; i < targets.Count; ++i ) - { - Mobile m = (Mobile)targets[i]; - attacker.DoHarmful( m, true ); + if (Registry[m] is Timer t) + { + t.Stop(); + Registry.Remove(m); + } - if ( Registry[m] is Timer t ) - { - t.Stop(); - Registry.Remove( m ); - } + t = new InternalTimer(attacker, m, amount); + t.Start(); + Registry.Add(m, t); + } - t = new InternalTimer( attacker, m, amount ); - t.Start(); - Registry.Add( m, t ); - } + Timer.DelayCall(TimeSpan.FromSeconds(2.0), new TimerStateCallback(RepeatEffect), attacker); + } + } - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), new TimerStateCallback( RepeatEffect ), attacker ); - } - } + private void RepeatEffect(object state) + { + Mobile attacker = (Mobile)state; - private void RepeatEffect( object state ) - { - Mobile attacker = (Mobile)state; + attacker.FixedEffect(0x3728, 10, 15); + attacker.PlaySound(0x2A1); + } - attacker.FixedEffect( 0x3728, 10, 15 ); - attacker.PlaySound( 0x2A1 ); - } + private class InternalTimer : Timer + { + private readonly double DamagePerTick; + private Mobile m_Attacker; + private double m_DamageRemaining; + private double m_DamageToDo; + private Mobile m_Defender; - private class InternalTimer : Timer - { - private Mobile m_Attacker; - private Mobile m_Defender; - private double m_DamageRemaining; - private double m_DamageToDo; + public InternalTimer(Mobile attacker, Mobile defender, int totalDamage) + : base(TimeSpan.Zero, TimeSpan.FromSeconds(0.25), + 12) // 3 seconds at .25 seconds apart = 12. Confirm delay inbetween of .25 each. + { + m_Attacker = attacker; + m_Defender = defender; - private readonly double DamagePerTick; + m_DamageRemaining = totalDamage; + DamagePerTick = (double)totalDamage / 12 + 0.01; - public InternalTimer( Mobile attacker, Mobile defender, int totalDamage ) - : base( TimeSpan.Zero, TimeSpan.FromSeconds( 0.25 ), 12 ) // 3 seconds at .25 seconds apart = 12. Confirm delay inbetween of .25 each. - { - m_Attacker = attacker; - m_Defender = defender; + Priority = TimerPriority.TwentyFiveMS; + } - m_DamageRemaining = (double)totalDamage; - DamagePerTick = (double)totalDamage / 12 + 0.01; + protected override void OnTick() + { + if (!m_Defender.Alive || m_DamageRemaining <= 0) + { + Stop(); + Registry.Remove(m_Defender); + return; + } - Priority = TimerPriority.TwentyFiveMS; - } + m_DamageRemaining -= DamagePerTick; + m_DamageToDo += DamagePerTick; - protected override void OnTick() - { - if ( !m_Defender.Alive || m_DamageRemaining <= 0 ) - { - Stop(); - Registry.Remove( m_Defender ); - return; - } + if (m_DamageRemaining <= 0 && m_DamageToDo < 1) + m_DamageToDo = 1.0; //Confirm this 'round up' at the end - m_DamageRemaining -= DamagePerTick; - m_DamageToDo += DamagePerTick; + int damage = (int)m_DamageToDo; - if ( m_DamageRemaining <= 0 && m_DamageToDo < 1 ) - m_DamageToDo = 1.0; //Confirm this 'round up' at the end + if (damage > 0) + { + m_Defender.Damage(damage, m_Attacker); + m_DamageToDo -= damage; + } - int damage = (int)m_DamageToDo; - - if ( damage > 0 ) - { - m_Defender.Damage( damage, m_Attacker ); - m_DamageToDo -= damage; - } - - if ( !m_Defender.Alive || m_DamageRemaining <= 0 ) - { - Stop(); - Registry.Remove( m_Defender ); - } - } - } - } -} + if (!m_Defender.Alive || m_DamageRemaining <= 0) + { + Stop(); + Registry.Remove(m_Defender); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/InfectiousStrike.cs b/Scripts/Items/Weapons/Abilities/InfectiousStrike.cs index 28956d5ce..b73922459 100644 --- a/Scripts/Items/Weapons/Abilities/InfectiousStrike.cs +++ b/Scripts/Items/Weapons/Abilities/InfectiousStrike.cs @@ -1,78 +1,78 @@ namespace Server.Items { - /// - /// This special move represents a significant change to the use of poisons in Age of Shadows. - /// Now, only certain weapon types � those that have Infectious Strike as an available special move � will be able to be poisoned. - /// Targets will no longer be poisoned at random when hit by poisoned weapons. - /// Instead, the wielder must use this ability to deliver the venom. - /// While no skill in Poisoning is directly required to use this ability, being knowledgeable in the application and use of toxins - /// will allow a character to use Infectious Strike at reduced mana cost and with a chance to inflict more deadly poison on his victim. - /// With this change, weapons will no longer be corroded by poison. - /// Level 5 poison will be possible when using this special move. - /// - public class InfectiousStrike : WeaponAbility - { - public InfectiousStrike() - { - } + /// + /// This special move represents a significant change to the use of poisons in Age of Shadows. + /// Now, only certain weapon types � those that have Infectious Strike as an available special move � will be able to be + /// poisoned. + /// Targets will no longer be poisoned at random when hit by poisoned weapons. + /// Instead, the wielder must use this ability to deliver the venom. + /// While no skill in Poisoning is directly required to use this ability, being knowledgeable in the application and use of + /// toxins + /// will allow a character to use Infectious Strike at reduced mana cost and with a chance to inflict more deadly poison on + /// his victim. + /// With this change, weapons will no longer be corroded by poison. + /// Level 5 poison will be possible when using this special move. + /// + public class InfectiousStrike : WeaponAbility + { + public override int BaseMana => 15; - public override int BaseMana => 15; + public override bool RequiresTactics(Mobile from) + { + return false; + } - public override bool RequiresTactics( Mobile from ) - { - return false; - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + if (!(attacker.Weapon is BaseWeapon weapon)) + return; - if ( !(attacker.Weapon is BaseWeapon weapon) ) - return; + Poison p = weapon.Poison; - Poison p = weapon.Poison; + if (p == null || weapon.PoisonCharges <= 0) + { + attacker.SendLocalizedMessage( + 1061141); // Your weapon must have a dose of poison to perform an infectious strike! + return; + } - if ( p == null || weapon.PoisonCharges <= 0 ) - { - attacker.SendLocalizedMessage( 1061141 ); // Your weapon must have a dose of poison to perform an infectious strike! - return; - } + if (!CheckMana(attacker, true)) + return; - if ( !CheckMana( attacker, true ) ) - return; + --weapon.PoisonCharges; - --weapon.PoisonCharges; + // Infectious strike special move now uses poisoning skill to help determine potency + int maxLevel = attacker.Skills[SkillName.Poisoning].Fixed / 200; + if (maxLevel < 0) maxLevel = 0; + if (p.Level > maxLevel) p = Poison.GetPoison(maxLevel); - // Infectious strike special move now uses poisoning skill to help determine potency - int maxLevel = attacker.Skills[SkillName.Poisoning].Fixed / 200; - if ( maxLevel < 0 ) maxLevel = 0; - if ( p.Level > maxLevel ) p = Poison.GetPoison( maxLevel ); + if (attacker.Skills[SkillName.Poisoning].Value / 100.0 > Utility.RandomDouble()) + { + int level = p.Level + 1; + Poison newPoison = Poison.GetPoison(level); - if ( (attacker.Skills[SkillName.Poisoning].Value / 100.0) > Utility.RandomDouble() ) - { - int level = p.Level + 1; - Poison newPoison = Poison.GetPoison( level ); + if (newPoison != null) + { + p = newPoison; - if ( newPoison != null ) - { - p = newPoison; + attacker.SendLocalizedMessage(1060080); // Your precise strike has increased the level of the poison by 1 + defender.SendLocalizedMessage(1060081); // The poison seems extra effective! + } + } - attacker.SendLocalizedMessage( 1060080 ); // Your precise strike has increased the level of the poison by 1 - defender.SendLocalizedMessage( 1060081 ); // The poison seems extra effective! - } - } + defender.PlaySound(0xDD); + defender.FixedParticles(0x3728, 244, 25, 9941, 1266, 0, EffectLayer.Waist); - defender.PlaySound( 0xDD ); - defender.FixedParticles( 0x3728, 244, 25, 9941, 1266, 0, EffectLayer.Waist ); - - if ( defender.ApplyPoison( attacker, p ) != ApplyPoisonResult.Immune ) - { - attacker.SendLocalizedMessage( 1008096, true, defender.Name ); // You have poisoned your target : - defender.SendLocalizedMessage( 1008097, false, attacker.Name ); // : poisoned you! - } - } - } -} + if (defender.ApplyPoison(attacker, p) != ApplyPoisonResult.Immune) + { + attacker.SendLocalizedMessage(1008096, true, defender.Name); // You have poisoned your target : + defender.SendLocalizedMessage(1008097, false, attacker.Name); // : poisoned you! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/MortalStrike.cs b/Scripts/Items/Weapons/Abilities/MortalStrike.cs index 4c48b438d..5e004a313 100644 --- a/Scripts/Items/Weapons/Abilities/MortalStrike.cs +++ b/Scripts/Items/Weapons/Abilities/MortalStrike.cs @@ -3,92 +3,85 @@ using System.Collections; namespace Server.Items { - /// - /// The assassin's friend. - /// A successful Mortal Strike will render its victim unable to heal any damage for several seconds. - /// Use a gruesome follow-up to finish off your foe. - /// - public class MortalStrike : WeaponAbility - { - public MortalStrike() - { - } + /// + /// The assassin's friend. + /// A successful Mortal Strike will render its victim unable to heal any damage for several seconds. + /// Use a gruesome follow-up to finish off your foe. + /// + public class MortalStrike : WeaponAbility + { + public static readonly TimeSpan PlayerDuration = TimeSpan.FromSeconds(6.0); + public static readonly TimeSpan NPCDuration = TimeSpan.FromSeconds(12.0); - public override int BaseMana => 30; + private static Hashtable m_Table = new Hashtable(); - public static readonly TimeSpan PlayerDuration = TimeSpan.FromSeconds( 6.0 ); - public static readonly TimeSpan NPCDuration = TimeSpan.FromSeconds( 12.0 ); + public override int BaseMana => 30; - public override void OnHit(Mobile attacker, Mobile defender, int damage) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - { - return; - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) return; - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - attacker.SendLocalizedMessage( 1060086 ); // You deliver a mortal wound! - defender.SendLocalizedMessage( 1060087 ); // You have been mortally wounded! + attacker.SendLocalizedMessage(1060086); // You deliver a mortal wound! + defender.SendLocalizedMessage(1060087); // You have been mortally wounded! - defender.PlaySound( 0x1E1 ); - defender.FixedParticles( 0x37B9, 244, 25, 9944, 31, 0, EffectLayer.Waist ); + defender.PlaySound(0x1E1); + defender.FixedParticles(0x37B9, 244, 25, 9944, 31, 0, EffectLayer.Waist); - // Do not reset timer if one is already in place. - if ( !IsWounded( defender ) ) - BeginWound( defender, defender.Player ? PlayerDuration : NPCDuration ); - } + // Do not reset timer if one is already in place. + if (!IsWounded(defender)) + BeginWound(defender, defender.Player ? PlayerDuration : NPCDuration); + } - private static Hashtable m_Table = new Hashtable(); + public static bool IsWounded(Mobile m) + { + return m_Table.Contains(m); + } - public static bool IsWounded( Mobile m ) - { - return m_Table.Contains( m ); - } + public static void BeginWound(Mobile m, TimeSpan duration) + { + Timer t = (Timer)m_Table[m]; - public static void BeginWound( Mobile m, TimeSpan duration ) - { - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + t = new InternalTimer(m, duration); + m_Table[m] = t; - t = new InternalTimer( m, duration ); - m_Table[m] = t; + t.Start(); - t.Start(); + m.YellowHealthbar = true; + } - m.YellowHealthbar = true; - } + public static void EndWound(Mobile m) + { + if (!IsWounded(m)) + return; - public static void EndWound( Mobile m ) - { - if ( !IsWounded( m ) ) - return; + Timer t = (Timer)m_Table[m]; - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + m_Table.Remove(m); - m_Table.Remove( m ); + m.YellowHealthbar = false; + m.SendLocalizedMessage(1060208); // You are no longer mortally wounded. + } - m.YellowHealthbar = false; - m.SendLocalizedMessage( 1060208 ); // You are no longer mortally wounded. - } + private class InternalTimer : Timer + { + private Mobile m_Mobile; - private class InternalTimer : Timer - { - private Mobile m_Mobile; + public InternalTimer(Mobile m, TimeSpan duration) : base(duration) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - public InternalTimer( Mobile m, TimeSpan duration ) : base( duration ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - EndWound( m_Mobile ); - } - } - } -} + protected override void OnTick() + { + EndWound(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/MovingShot.cs b/Scripts/Items/Weapons/Abilities/MovingShot.cs index 4fc044a40..5912ac572 100644 --- a/Scripts/Items/Weapons/Abilities/MovingShot.cs +++ b/Scripts/Items/Weapons/Abilities/MovingShot.cs @@ -1,41 +1,37 @@ namespace Server.Items { - /// - /// Available on some crossbows, this special move allows archers to fire while on the move. - /// This shot is somewhat less accurate than normal, but the ability to fire while running is a clear advantage. - /// - public class MovingShot : WeaponAbility - { - public MovingShot() - { - } + /// + /// Available on some crossbows, this special move allows archers to fire while on the move. + /// This shot is somewhat less accurate than normal, but the ability to fire while running is a clear advantage. + /// + public class MovingShot : WeaponAbility + { + public override int BaseMana => 15; + public override int AccuracyBonus => -25; - public override int BaseMana => 15; - public override int AccuracyBonus => -25; + public override bool ValidatesDuringHit => false; - public override bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - return ( Validate( attacker ) && CheckMana( attacker, true ) ); - } + public override bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + return Validate(attacker) && CheckMana(attacker, true); + } - public override void OnMiss( Mobile attacker, Mobile defender ) - { - //Validates in OnSwing for accuracy scalar + public override void OnMiss(Mobile attacker, Mobile defender) + { + //Validates in OnSwing for accuracy scalar - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - attacker.SendLocalizedMessage( 1060089 ); // You fail to execute your special move - } + attacker.SendLocalizedMessage(1060089); // You fail to execute your special move + } - public override bool ValidatesDuringHit => false; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + //Validates in OnSwing for accuracy scalar - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - //Validates in OnSwing for accuracy scalar + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); - - attacker.SendLocalizedMessage( 1060216 ); // Your shot was successful - } - } -} + attacker.SendLocalizedMessage(1060216); // Your shot was successful + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/NerveStrike.cs b/Scripts/Items/Weapons/Abilities/NerveStrike.cs index 0ed8e77de..ccf737ac8 100644 --- a/Scripts/Items/Weapons/Abilities/NerveStrike.cs +++ b/Scripts/Items/Weapons/Abilities/NerveStrike.cs @@ -2,79 +2,80 @@ using System; namespace Server.Items { - /// - /// Does damage and paralyses your opponent for a short time. - /// - public class NerveStrike : WeaponAbility - { - public NerveStrike() - { - } + /// + /// Does damage and paralyses your opponent for a short time. + /// + public class NerveStrike : WeaponAbility + { + public override int BaseMana => 30; - public override int BaseMana => 30; + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1070768, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido skill to perform that attack! + return false; + } - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1070768, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido skill to perform that attack! - return false; - } + return base.CheckSkills(from); + } - return base.CheckSkills( from ); - } + public override bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + if (defender.Paralyzed) + { + attacker.SendLocalizedMessage(1061923); // The target is already frozen. + return false; + } - public override bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - if ( defender.Paralyzed ) - { - attacker.SendLocalizedMessage( 1061923 ); // The target is already frozen. - return false; - } + return true; + } - return true; - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + bool cantpara = Items.ParalyzingBlow.IsImmune(defender); - bool cantpara = Server.Items.ParalyzingBlow.IsImmune(defender); + if (cantpara) + { + attacker.SendLocalizedMessage(1070804); // Your target resists paralysis. + defender.SendLocalizedMessage(1070813); // You resist paralysis. + } + else + { + attacker.SendLocalizedMessage(1063356); // You cripple your target with a nerve strike! + defender.SendLocalizedMessage(1063357); // Your attacker dealt a crippling nerve strike! + } - if ( cantpara ) - { - attacker.SendLocalizedMessage(1070804); // Your target resists paralysis. - defender.SendLocalizedMessage(1070813); // You resist paralysis. - } - else - { - attacker.SendLocalizedMessage(1063356); // You cripple your target with a nerve strike! - defender.SendLocalizedMessage(1063357); // Your attacker dealt a crippling nerve strike! - } + attacker.PlaySound(0x204); + defender.FixedEffect(0x376A, 9, 32); + defender.FixedParticles(0x37C4, 1, 8, 0x13AF, 0, 0, EffectLayer.Waist); - attacker.PlaySound(0x204); - defender.FixedEffect(0x376A, 9, 32); - defender.FixedParticles(0x37C4, 1, 8, 0x13AF, 0, 0, EffectLayer.Waist); + if (Core.ML) + { + AOS.Damage(defender, attacker, + (int)(15.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + Utility.Random(10)), true, 100, + 0, 0, 0, 0); //0-25 - if ( Core.ML ) - { - AOS.Damage( defender, attacker, (int)( 15.0 * ( attacker.Skills[SkillName.Bushido].Value - 50.0 ) / 70.0 + Utility.Random( 10 ) ), true, 100, 0, 0, 0, 0 ); //0-25 - - if (!cantpara && ((150.0 / 7.0 + (4.0 * attacker.Skills[SkillName.Bushido].Value) / 7.0) / 100.0) > Utility.RandomDouble()) - { - defender.Paralyze( TimeSpan.FromSeconds( 2.0 ) ); - Server.Items.ParalyzingBlow.BeginImmunity( defender, Server.Items.ParalyzingBlow.FreezeDelayDuration ); - } - } - else if ( !cantpara ) - { - AOS.Damage( defender, attacker, (int)(15.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + 10), true, 100, 0, 0, 0, 0 ); //10-25 - defender.Freeze(TimeSpan.FromSeconds(2.0)); - Server.Items.ParalyzingBlow.BeginImmunity(defender, Server.Items.ParalyzingBlow.FreezeDelayDuration); - } - } - } -} + if (!cantpara && (150.0 / 7.0 + 4.0 * attacker.Skills[SkillName.Bushido].Value / 7.0) / 100.0 > + Utility.RandomDouble()) + { + defender.Paralyze(TimeSpan.FromSeconds(2.0)); + Items.ParalyzingBlow.BeginImmunity(defender, Items.ParalyzingBlow.FreezeDelayDuration); + } + } + else if (!cantpara) + { + AOS.Damage(defender, attacker, (int)(15.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + 10), + true, 100, 0, 0, 0, 0); //10-25 + defender.Freeze(TimeSpan.FromSeconds(2.0)); + Items.ParalyzingBlow.BeginImmunity(defender, Items.ParalyzingBlow.FreezeDelayDuration); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/ParalyzingBlow.cs b/Scripts/Items/Weapons/Abilities/ParalyzingBlow.cs index 37c01487b..50fe0c5b2 100644 --- a/Scripts/Items/Weapons/Abilities/ParalyzingBlow.cs +++ b/Scripts/Items/Weapons/Abilities/ParalyzingBlow.cs @@ -3,130 +3,126 @@ using System.Collections; namespace Server.Items { - /// - /// A successful Paralyzing Blow will leave the target stunned, unable to move, attack, or cast spells, for a few seconds. - /// - public class ParalyzingBlow : WeaponAbility - { - public ParalyzingBlow() - { - } + /// + /// A successful Paralyzing Blow will leave the target stunned, unable to move, attack, or cast spells, for a few seconds. + /// + public class ParalyzingBlow : WeaponAbility + { + public static readonly TimeSpan PlayerFreezeDuration = TimeSpan.FromSeconds(3.0); + public static readonly TimeSpan NPCFreezeDuration = TimeSpan.FromSeconds(6.0); - public override int BaseMana => 30; + public static readonly TimeSpan FreezeDelayDuration = TimeSpan.FromSeconds(8.0); - public static readonly TimeSpan PlayerFreezeDuration = TimeSpan.FromSeconds( 3.0 ); - public static readonly TimeSpan NPCFreezeDuration = TimeSpan.FromSeconds( 6.0 ); + private static Hashtable m_Table = new Hashtable(); - public static readonly TimeSpan FreezeDelayDuration = TimeSpan.FromSeconds( 8.0 ); + public override int BaseMana => 30; - // No longer active in pub21: - /*public override bool CheckSkills( Mobile from ) - { - if ( !base.CheckSkills( from ) ) - return false; + // No longer active in pub21: + /*public override bool CheckSkills( Mobile from ) + { + if ( !base.CheckSkills( from ) ) + return false; - if ( !(from.Weapon is Fists) ) - return true; + if ( !(from.Weapon is Fists) ) + return true; - Skill skill = from.Skills[SkillName.Anatomy]; + Skill skill = from.Skills[SkillName.Anatomy]; - if ( skill != null && skill.Base >= 80.0 ) - return true; + if ( skill != null && skill.Base >= 80.0 ) + return true; - from.SendLocalizedMessage( 1061811 ); // You lack the required anatomy skill to perform that attack! + from.SendLocalizedMessage( 1061811 ); // You lack the required anatomy skill to perform that attack! - return false; - }*/ + return false; + }*/ - public override bool RequiresTactics( Mobile from ) - { - if ( !(from.Weapon is BaseWeapon weapon) ) - return true; + public override bool RequiresTactics(Mobile from) + { + if (!(from.Weapon is BaseWeapon weapon)) + return true; - return weapon.Skill != SkillName.Wrestling; - } + return weapon.Skill != SkillName.Wrestling; + } - public override bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - if ( defender.Paralyzed ) - { - attacker.SendLocalizedMessage( 1061923 ); // The target is already frozen. - return false; - } + public override bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + if (defender.Paralyzed) + { + attacker.SendLocalizedMessage(1061923); // The target is already frozen. + return false; + } - return true; - } + return true; + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentAbility( attacker ); + ClearCurrentAbility(attacker); - if ( IsImmune( defender ) ) //Intentionally going after Mana consumption - { - attacker.SendLocalizedMessage( 1070804 ); // Your target resists paralysis. - defender.SendLocalizedMessage( 1070813 ); // You resist paralysis. - return; - } + if (IsImmune(defender)) //Intentionally going after Mana consumption + { + attacker.SendLocalizedMessage(1070804); // Your target resists paralysis. + defender.SendLocalizedMessage(1070813); // You resist paralysis. + return; + } - defender.FixedEffect( 0x376A, 9, 32 ); - defender.PlaySound( 0x204 ); + defender.FixedEffect(0x376A, 9, 32); + defender.PlaySound(0x204); - attacker.SendLocalizedMessage( 1060163 ); // You deliver a paralyzing blow! - defender.SendLocalizedMessage( 1060164 ); // The attack has temporarily paralyzed you! + attacker.SendLocalizedMessage(1060163); // You deliver a paralyzing blow! + defender.SendLocalizedMessage(1060164); // The attack has temporarily paralyzed you! - TimeSpan duration = defender.Player ? PlayerFreezeDuration : NPCFreezeDuration; + TimeSpan duration = defender.Player ? PlayerFreezeDuration : NPCFreezeDuration; - // Treat it as paralyze not as freeze, effect must be removed when damaged. - defender.Paralyze( duration ); + // Treat it as paralyze not as freeze, effect must be removed when damaged. + defender.Paralyze(duration); - BeginImmunity( defender, duration + FreezeDelayDuration ); - } + BeginImmunity(defender, duration + FreezeDelayDuration); + } - private static Hashtable m_Table = new Hashtable(); + public static bool IsImmune(Mobile m) + { + return m_Table.Contains(m); + } - public static bool IsImmune( Mobile m ) - { - return m_Table.Contains( m ); - } + public static void BeginImmunity(Mobile m, TimeSpan duration) + { + Timer t = (Timer)m_Table[m]; - public static void BeginImmunity( Mobile m, TimeSpan duration ) - { - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + t = new InternalTimer(m, duration); + m_Table[m] = t; - t = new InternalTimer( m, duration ); - m_Table[m] = t; + t.Start(); + } - t.Start(); - } + public static void EndImmunity(Mobile m) + { + Timer t = (Timer)m_Table[m]; - public static void EndImmunity( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + m_Table.Remove(m); + } - m_Table.Remove( m ); - } + private class InternalTimer : Timer + { + private Mobile m_Mobile; - private class InternalTimer : Timer - { - private Mobile m_Mobile; + public InternalTimer(Mobile m, TimeSpan duration) : base(duration) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - public InternalTimer( Mobile m, TimeSpan duration ) : base( duration ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - EndImmunity( m_Mobile ); - } - } - } -} + protected override void OnTick() + { + EndImmunity(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/RidingSwipe.cs b/Scripts/Items/Weapons/Abilities/RidingSwipe.cs index 7d3a8faef..4a2bb1e17 100644 --- a/Scripts/Items/Weapons/Abilities/RidingSwipe.cs +++ b/Scripts/Items/Weapons/Abilities/RidingSwipe.cs @@ -1,80 +1,77 @@ - using System; using Server.Mobiles; namespace Server.Items { - /// - /// If you are on foot, dismounts your opponent and damage the ethereal's rider or the - /// living mount(which must be healed before ridden again). If you are mounted, damages - /// and stuns the mounted opponent. - /// - public class RidingSwipe : WeaponAbility - { - public RidingSwipe() - { - } + /// + /// If you are on foot, dismounts your opponent and damage the ethereal's rider or the + /// living mount(which must be healed before ridden again). If you are mounted, damages + /// and stuns the mounted opponent. + /// + public class RidingSwipe : WeaponAbility + { + public override int BaseMana => 30; - public override int BaseMana => 30; + public override bool RequiresSE => true; - public override bool RequiresSE => true; + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Bushido) < 50.0) + { + from.SendLocalizedMessage(1070768, + "50"); // You need ~1_SKILL_REQUIREMENT~ Bushido skill to perform that attack! + return false; + } - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Bushido ) < 50.0 ) - { - from.SendLocalizedMessage( 1070768, "50" ); // You need ~1_SKILL_REQUIREMENT~ Bushido skill to perform that attack! - return false; - } + return base.CheckSkills(from); + } - return base.CheckSkills( from ); - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!defender.Mounted) + { + attacker.SendLocalizedMessage(1060848); // This attack only works on mounted targets + ClearCurrentAbility(attacker); + return; + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !defender.Mounted ) - { - attacker.SendLocalizedMessage( 1060848 ); // This attack only works on mounted targets - ClearCurrentAbility( attacker ); - return; - } + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + if (!attacker.Mounted) + { + Mobile mount = defender.Mount as Mobile; + BaseMount.Dismount(defender); - if ( !attacker.Mounted ) - { - Mobile mount = defender.Mount as Mobile; - BaseMount.Dismount( defender ); + if (mount != null) //Ethy mounts don't take damage + { + int amount = 10 + (int)(10.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + 5); - if ( mount != null ) //Ethy mounts don't take damage - { - int amount = 10 + (int)(10.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + 5); + AOS.Damage(mount, null, amount, 100, 0, 0, 0, + 0); //The mount just takes damage, there's no flagging as if it was attacking the mount directly - AOS.Damage( mount, null, amount, 100, 0, 0, 0, 0 ); //The mount just takes damage, there's no flagging as if it was attacking the mount directly + //TODO: Mount prevention until mount healed + } + } + else + { + int amount = 10 + (int)(10.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + 5); - //TODO: Mount prevention until mount healed - } - } - else - { - int amount = 10 + (int)(10.0 * (attacker.Skills[SkillName.Bushido].Value - 50.0) / 70.0 + 5); + AOS.Damage(defender, attacker, amount, 100, 0, 0, 0, 0); - AOS.Damage( defender, attacker, amount, 100, 0, 0, 0, 0 ); - - if ( Server.Items.ParalyzingBlow.IsImmune( defender ) ) //Does it still do damage? - { - attacker.SendLocalizedMessage( 1070804 ); // Your target resists paralysis. - defender.SendLocalizedMessage( 1070813 ); // You resist paralysis. - } - else - { - defender.Paralyze( TimeSpan.FromSeconds( 3.0 ) ); - Server.Items.ParalyzingBlow.BeginImmunity( defender, Server.Items.ParalyzingBlow.FreezeDelayDuration ); - } - } - } - } -} + if (Items.ParalyzingBlow.IsImmune(defender)) //Does it still do damage? + { + attacker.SendLocalizedMessage(1070804); // Your target resists paralysis. + defender.SendLocalizedMessage(1070813); // You resist paralysis. + } + else + { + defender.Paralyze(TimeSpan.FromSeconds(3.0)); + Items.ParalyzingBlow.BeginImmunity(defender, Items.ParalyzingBlow.FreezeDelayDuration); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/ShadowStrike.cs b/Scripts/Items/Weapons/Abilities/ShadowStrike.cs index f88dfb25a..872841fc7 100644 --- a/Scripts/Items/Weapons/Abilities/ShadowStrike.cs +++ b/Scripts/Items/Weapons/Abilities/ShadowStrike.cs @@ -1,57 +1,54 @@ namespace Server.Items { - /// - /// This powerful ability requires secondary skills to activate. - /// Successful use of Shadowstrike deals extra damage to the target � and renders the attacker invisible! - /// Only those who are adept at the art of stealth will be able to use this ability. - /// - public class ShadowStrike : WeaponAbility - { - public ShadowStrike() - { - } + /// + /// This powerful ability requires secondary skills to activate. + /// Successful use of Shadowstrike deals extra damage to the target � and renders the attacker invisible! + /// Only those who are adept at the art of stealth will be able to use this ability. + /// + public class ShadowStrike : WeaponAbility + { + public override int BaseMana => 20; + public override double DamageScalar => 1.25; - public override int BaseMana => 20; - public override double DamageScalar => 1.25; + public override bool RequiresTactics(Mobile from) + { + return false; + } - public override bool RequiresTactics( Mobile from ) - { - return false; - } + public override bool CheckSkills(Mobile from) + { + if (!base.CheckSkills(from)) + return false; - public override bool CheckSkills( Mobile from ) - { - if ( !base.CheckSkills( from ) ) - return false; + Skill skill = from.Skills[SkillName.Stealth]; - Skill skill = from.Skills[SkillName.Stealth]; + if (skill != null && skill.Value >= 80.0) + return true; - if ( skill != null && skill.Value >= 80.0 ) - return true; + from.SendLocalizedMessage(1060183); // You lack the required stealth to perform that attack - from.SendLocalizedMessage( 1060183 ); // You lack the required stealth to perform that attack + return false; + } - return false; - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1060078); // You strike and hide in the shadows! + defender.SendLocalizedMessage(1060079); // You are dazed by the attack and your attacker vanishes! - attacker.SendLocalizedMessage( 1060078 ); // You strike and hide in the shadows! - defender.SendLocalizedMessage( 1060079 ); // You are dazed by the attack and your attacker vanishes! + Effects.SendLocationParticles(EffectItem.Create(attacker.Location, attacker.Map, EffectItem.DefaultDuration), + 0x376A, 8, 12, 9943); + attacker.PlaySound(0x482); - Effects.SendLocationParticles( EffectItem.Create( attacker.Location, attacker.Map, EffectItem.DefaultDuration ), 0x376A, 8, 12, 9943 ); - attacker.PlaySound( 0x482 ); + defender.FixedEffect(0x37BE, 20, 25); - defender.FixedEffect( 0x37BE, 20, 25 ); - - attacker.Combatant = null; - attacker.Warmode = false; - attacker.Hidden = true; - } - } -} + attacker.Combatant = null; + attacker.Warmode = false; + attacker.Hidden = true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/TalonStrike.cs b/Scripts/Items/Weapons/Abilities/TalonStrike.cs index 614a91a42..08c7d17e0 100644 --- a/Scripts/Items/Weapons/Abilities/TalonStrike.cs +++ b/Scripts/Items/Weapons/Abilities/TalonStrike.cs @@ -1,104 +1,101 @@ - using System; using System.Collections; namespace Server.Items { - /// - /// Attack with increased damage with additional damage over time. - /// - public class TalonStrike : WeaponAbility - { - public static Hashtable Registry { get; } = new Hashtable(); + /// + /// Attack with increased damage with additional damage over time. + /// + public class TalonStrike : WeaponAbility + { + public static Hashtable Registry{ get; } = new Hashtable(); - public TalonStrike() - { - } + public override int BaseMana => 30; + public override double DamageScalar => 1.2; - public override int BaseMana => 30; - public override double DamageScalar => 1.2; + public override bool CheckSkills(Mobile from) + { + if (GetSkill(from, SkillName.Ninjitsu) < 50.0) + { + from.SendLocalizedMessage(1063352, + "50"); // You need ~1_SKILL_REQUIREMENT~ Ninjitsu skill to perform that attack! + return false; + } - public override bool CheckSkills( Mobile from ) - { - if ( GetSkill( from, SkillName.Ninjitsu ) < 50.0 ) - { - from.SendLocalizedMessage( 1063352, "50" ); // You need ~1_SKILL_REQUIREMENT~ Ninjitsu skill to perform that attack! - return false; - } + return base.CheckSkills(from); + } - return base.CheckSkills( from ); - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (Registry.Contains(defender) || !Validate(attacker) || !CheckMana(attacker, true)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( Registry.Contains( defender ) || !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + attacker.SendLocalizedMessage(1063358); // You deliver a talon strike! + defender.SendLocalizedMessage(1063359); // Your attacker delivers a talon strike! - attacker.SendLocalizedMessage( 1063358 ); // You deliver a talon strike! - defender.SendLocalizedMessage( 1063359 ); // Your attacker delivers a talon strike! + defender.FixedParticles(0x373A, 1, 17, 0x26BC, 0x662, 0, EffectLayer.Waist); - defender.FixedParticles( 0x373A, 1, 17, 0x26BC, 0x662, 0, EffectLayer.Waist ); + Timer t = new InternalTimer(defender, + (int)(10.0 * (attacker.Skills[SkillName.Ninjitsu].Value - 50.0) / 70.0 + 5), attacker); //5 - 15 damage - Timer t = new InternalTimer( defender, (int)(10.0 * (attacker.Skills[SkillName.Ninjitsu].Value - 50.0) / 70.0 + 5), attacker ); //5 - 15 damage + t.Start(); - t.Start(); + Registry.Add(defender, t); + } - Registry.Add( defender, t ); - } + private class InternalTimer : Timer + { + private readonly double DamagePerTick; + private Mobile m_Attacker; + private double m_DamageRemaining; + private double m_DamageToDo; + private Mobile m_Defender; - private class InternalTimer : Timer - { - private Mobile m_Defender; - private double m_DamageRemaining; - private double m_DamageToDo; - private Mobile m_Attacker; + public InternalTimer(Mobile defender, int totalDamage, Mobile attacker) + : base(TimeSpan.Zero, TimeSpan.FromSeconds(0.25), + 12) // 3 seconds at .25 seconds apart = 12. Confirm delay inbetween of .25 each. + { + m_Defender = defender; + m_DamageRemaining = totalDamage; + Priority = TimerPriority.TwentyFiveMS; - private readonly double DamagePerTick; + m_Attacker = attacker; - public InternalTimer( Mobile defender, int totalDamage, Mobile attacker ) - : base( TimeSpan.Zero, TimeSpan.FromSeconds( 0.25 ), 12 ) // 3 seconds at .25 seconds apart = 12. Confirm delay inbetween of .25 each. - { - m_Defender = defender; - m_DamageRemaining = (double)totalDamage; - Priority = TimerPriority.TwentyFiveMS; + DamagePerTick = (double)totalDamage / 12 + .01; + } - m_Attacker = attacker; + protected override void OnTick() + { + if (!m_Defender.Alive || m_DamageRemaining <= 0) + { + Stop(); + Registry.Remove(m_Defender); + return; + } - DamagePerTick = (double)totalDamage / 12+.01; - } + m_DamageRemaining -= DamagePerTick; + m_DamageToDo += DamagePerTick; - protected override void OnTick() - { - if ( !m_Defender.Alive || m_DamageRemaining <= 0 ) - { - Stop(); - Registry.Remove( m_Defender ); - return; - } + if (m_DamageRemaining <= 0 && m_DamageToDo < 1) + m_DamageToDo = 1.0; //Confirm this 'round up' at the end - m_DamageRemaining -= DamagePerTick; - m_DamageToDo += DamagePerTick; + int damage = (int)m_DamageToDo; - if ( m_DamageRemaining <= 0 && m_DamageToDo < 1 ) - m_DamageToDo = 1.0; //Confirm this 'round up' at the end + if (damage > 0) + { + //m_Defender.Damage( damage, m_Attacker, false ); + m_Defender.Hits -= damage; //Don't show damage, don't disrupt + m_DamageToDo -= damage; + } - int damage = (int)m_DamageToDo; - - if ( damage > 0 ) - { - //m_Defender.Damage( damage, m_Attacker, false ); - m_Defender.Hits -= damage; //Don't show damage, don't disrupt - m_DamageToDo -= damage; - } - - if ( !m_Defender.Alive || m_DamageRemaining <= 0 ) - { - Stop(); - Registry.Remove( m_Defender ); - } - } - } - } -} + if (!m_Defender.Alive || m_DamageRemaining <= 0) + { + Stop(); + Registry.Remove(m_Defender); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/WeaponAbility.cs b/Scripts/Items/Weapons/Abilities/WeaponAbility.cs index 061251d82..f3a967999 100644 --- a/Scripts/Items/Weapons/Abilities/WeaponAbility.cs +++ b/Scripts/Items/Weapons/Abilities/WeaponAbility.cs @@ -1,478 +1,484 @@ using System; using System.Collections; +using Server.Engines.ConPVP; +using Server.Mobiles; using Server.Network; using Server.Spells; -using Server.Mobiles; +using Server.Spells.Bushido; +using Server.Spells.Necromancy; +using Server.Spells.Ninjitsu; namespace Server.Items { - public abstract class WeaponAbility - { - public virtual int BaseMana => 0; - - public virtual int AccuracyBonus => 0; - public virtual double DamageScalar => 1.0; - - public virtual bool RequiresSE => false; - - public virtual void OnHit( Mobile attacker, Mobile defender, int damage ) - { - } - - public virtual void OnMiss( Mobile attacker, Mobile defender ) - { - } - - public virtual bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - // Here because you must be sure you can use the skill before calling CheckHit if the ability has a HCI bonus for example - return true; - } - - public virtual bool OnBeforeDamage( Mobile attacker, Mobile defender ) - { - return true; - } - - public virtual bool RequiresTactics( Mobile from ) - { - return true; - } - - public virtual double GetRequiredSkill( Mobile from ) - { - BaseWeapon weapon = from.Weapon as BaseWeapon; - - if ( weapon != null && weapon.PrimaryAbility == this ) - return 70.0; - if ( weapon != null && weapon.SecondaryAbility == this ) - return 90.0; - - return 200.0; - } - - public virtual int CalculateMana( Mobile from ) - { - int mana = BaseMana; - - double skillTotal = GetSkill( from, SkillName.Swords ) + GetSkill( from, SkillName.Macing ) - + GetSkill( from, SkillName.Fencing ) + GetSkill( from, SkillName.Archery ) + GetSkill( from, SkillName.Parry ) - + GetSkill( from, SkillName.Lumberjacking ) + GetSkill( from, SkillName.Stealth ) - + GetSkill( from, SkillName.Poisoning ) + GetSkill( from, SkillName.Bushido ) + GetSkill( from, SkillName.Ninjitsu ); - - if ( skillTotal >= 300.0 ) - mana -= 10; - else if ( skillTotal >= 200.0 ) - mana -= 5; - - double scalar = 1.0; - if ( !Spells.Necromancy.MindRotSpell.GetMindRotScalar( from, ref scalar ) ) - scalar = 1.0; - - // Lower Mana Cost = 40% - int lmc = Math.Min( AosAttributes.GetValue( from, AosAttribute.LowerManaCost ), 40 ); - - scalar -= (double)lmc / 100; - mana = (int)(mana * scalar); - - // Using a special move within 3 seconds of the previous special move costs double mana - if ( GetContext( from ) != null ) - mana *= 2; - - return mana; - } - - public virtual bool CheckWeaponSkill( Mobile from ) - { - if ( !(from.Weapon is BaseWeapon weapon) ) - return false; - - Skill skill = from.Skills[weapon.Skill]; - double reqSkill = GetRequiredSkill( from ); - bool reqTactics = Core.ML && RequiresTactics( from ); - - if ( Core.ML && reqTactics && from.Skills[SkillName.Tactics].Base < reqSkill ) - { - from.SendLocalizedMessage( 1079308, reqSkill.ToString() ); // You need ~1_SKILL_REQUIREMENT~ weapon and tactics skill to perform that attack - return false; - } - - if ( skill != null && skill.Base >= reqSkill ) - return true; - - /* */ - if ( weapon.WeaponAttributes.UseBestSkill > 0 && (from.Skills[SkillName.Swords].Base >= reqSkill || from.Skills[SkillName.Macing].Base >= reqSkill || from.Skills[SkillName.Fencing].Base >= reqSkill) ) - return true; - /* */ - - if ( reqTactics ) - { - from.SendLocalizedMessage( 1079308, reqSkill.ToString() ); // You need ~1_SKILL_REQUIREMENT~ weapon and tactics skill to perform that attack - } - else - { - from.SendLocalizedMessage( 1060182, reqSkill.ToString() ); // You need ~1_SKILL_REQUIREMENT~ weapon skill to perform that attack - } - - return false; - } - - public virtual bool CheckSkills( Mobile from ) - { - return CheckWeaponSkill( from ); - } - - public virtual double GetSkill( Mobile from, SkillName skillName ) - { - Skill skill = from.Skills[skillName]; - - if ( skill == null ) - return 0.0; - - return skill.Value; - } - - public virtual bool CheckMana( Mobile from, bool consume ) - { - int mana = CalculateMana( from ); - - if ( from.Mana < mana ) - { - if ( from is BaseCreature creature && creature.HasManaOveride ) - { - return true; - } - - from.SendLocalizedMessage( 1060181, mana.ToString() ); // You need ~1_MANA_REQUIREMENT~ mana to perform that attack - return false; - } - - if ( consume ) - { - if ( GetContext( from ) == null ) - { - Timer timer = new WeaponAbilityTimer( from ); - timer.Start(); - - AddContext( from, new WeaponAbilityContext( timer ) ); - } - - from.Mana -= mana; - } - - return true; - } - - public virtual bool Validate( Mobile from ) - { - if ( !from.Player ) - return true; - - NetState state = from.NetState; - - if ( state == null ) - return false; - - if ( RequiresSE && !state.SupportsExpansion( Expansion.SE ) ) - { - from.SendLocalizedMessage( 1063456 ); // You must upgrade to Samurai Empire in order to use that ability. - return false; - } - - if ( Spells.Bushido.HonorableExecution.IsUnderPenalty( from ) || Spells.Ninjitsu.AnimalForm.UnderTransformation( from ) ) - { - from.SendLocalizedMessage( 1063024 ); // You cannot perform this special move right now. - return false; - } - - if ( Core.ML && from.Spell != null ) - { - from.SendLocalizedMessage( 1063024 ); // You cannot perform this special move right now. - return false; - } - - #region Dueling - string option = null; - - if ( this is ArmorIgnore ) - option = "Armor Ignore"; - else if ( this is BleedAttack ) - option = "Bleed Attack"; - else if ( this is ConcussionBlow ) - option = "Concussion Blow"; - else if ( this is CrushingBlow ) - option = "Crushing Blow"; - else if ( this is Disarm ) - option = "Disarm"; - else if ( this is Dismount ) - option = "Dismount"; - else if ( this is DoubleStrike ) - option = "Double Strike"; - else if ( this is InfectiousStrike ) - option = "Infectious Strike"; - else if ( this is MortalStrike ) - option = "Mortal Strike"; - else if ( this is MovingShot ) - option = "Moving Shot"; - else if ( this is ParalyzingBlow ) - option = "Paralyzing Blow"; - else if ( this is ShadowStrike ) - option = "Shadow Strike"; - else if ( this is WhirlwindAttack ) - option = "Whirlwind Attack"; - else if ( this is RidingSwipe ) - option = "Riding Swipe"; - else if ( this is FrenziedWhirlwind ) - option = "Frenzied Whirlwind"; - else if ( this is Block ) - option = "Block"; - else if ( this is DefenseMastery ) - option = "Defense Mastery"; - else if ( this is NerveStrike ) - option = "Nerve Strike"; - else if ( this is TalonStrike ) - option = "Talon Strike"; - else if ( this is Feint ) - option = "Feint"; - else if ( this is DualWield ) - option = "Dual Wield"; - else if ( this is DoubleShot ) - option = "Double Shot"; - else if ( this is ArmorPierce ) - option = "Armor Pierce"; - - - if ( option != null && !Engines.ConPVP.DuelContext.AllowSpecialAbility( from, option, true ) ) - return false; - #endregion - - return CheckSkills( from ) && CheckMana( from, false ); - } - - public static WeaponAbility[] Abilities { get; } = new WeaponAbility[31] - { - null, - new ArmorIgnore(), - new BleedAttack(), - new ConcussionBlow(), - new CrushingBlow(), - new Disarm(), - new Dismount(), - new DoubleStrike(), - new InfectiousStrike(), - new MortalStrike(), - new MovingShot(), - new ParalyzingBlow(), - new ShadowStrike(), - new WhirlwindAttack(), - - new RidingSwipe(), - new FrenziedWhirlwind(), - new Block(), - new DefenseMastery(), - new NerveStrike(), - new TalonStrike(), - new Feint(), - new DualWield(), - new DoubleShot(), - new ArmorPierce(), - null, - null, - null, - null, - null, - null, - new Disrobe() - }; - - public static Hashtable Table { get; } = new Hashtable(); - - public static readonly WeaponAbility ArmorIgnore = Abilities[ 1]; - public static readonly WeaponAbility BleedAttack = Abilities[ 2]; - public static readonly WeaponAbility ConcussionBlow = Abilities[ 3]; - public static readonly WeaponAbility CrushingBlow = Abilities[ 4]; - public static readonly WeaponAbility Disarm = Abilities[ 5]; - public static readonly WeaponAbility Dismount = Abilities[ 6]; - public static readonly WeaponAbility DoubleStrike = Abilities[ 7]; - public static readonly WeaponAbility InfectiousStrike = Abilities[ 8]; - public static readonly WeaponAbility MortalStrike = Abilities[ 9]; - public static readonly WeaponAbility MovingShot = Abilities[10]; - public static readonly WeaponAbility ParalyzingBlow = Abilities[11]; - public static readonly WeaponAbility ShadowStrike = Abilities[12]; - public static readonly WeaponAbility WhirlwindAttack = Abilities[13]; - - public static readonly WeaponAbility RidingSwipe = Abilities[14]; - public static readonly WeaponAbility FrenziedWhirlwind = Abilities[15]; - public static readonly WeaponAbility Block = Abilities[16]; - public static readonly WeaponAbility DefenseMastery = Abilities[17]; - public static readonly WeaponAbility NerveStrike = Abilities[18]; - public static readonly WeaponAbility TalonStrike = Abilities[19]; - public static readonly WeaponAbility Feint = Abilities[20]; - public static readonly WeaponAbility DualWield = Abilities[21]; - public static readonly WeaponAbility DoubleShot = Abilities[22]; - public static readonly WeaponAbility ArmorPierce = Abilities[23]; - - public static readonly WeaponAbility Bladeweave = Abilities[24]; - public static readonly WeaponAbility ForceArrow = Abilities[25]; - public static readonly WeaponAbility LightningArrow = Abilities[26]; - public static readonly WeaponAbility PsychicAttack = Abilities[27]; - public static readonly WeaponAbility SerpentArrow = Abilities[28]; - public static readonly WeaponAbility ForceOfNature = Abilities[29]; - - public static readonly WeaponAbility Disrobe = Abilities[30]; - - public static bool IsWeaponAbility( Mobile m, WeaponAbility a ) - { - if ( a == null ) - return true; - - if ( !m.Player ) - return true; - - return ( m.Weapon is BaseWeapon weapon && (weapon.PrimaryAbility == a || weapon.SecondaryAbility == a) ); - } - - public virtual bool ValidatesDuringHit => true; - - public static WeaponAbility GetCurrentAbility( Mobile m ) - { - if ( !Core.AOS ) - { - ClearCurrentAbility( m ); - return null; - } - - WeaponAbility a = (WeaponAbility)Table[m]; - - if ( !IsWeaponAbility( m, a ) ) - { - ClearCurrentAbility( m ); - return null; - } - - if ( a != null && a.ValidatesDuringHit && !a.Validate( m ) ) - { - ClearCurrentAbility( m ); - return null; - } - - return a; - } - - public static bool SetCurrentAbility( Mobile m, WeaponAbility a ) - { - if ( !Core.AOS ) - { - ClearCurrentAbility( m ); - return false; - } - - if ( !IsWeaponAbility( m, a ) ) - { - ClearCurrentAbility( m ); - return false; - } - - if ( a != null && !a.Validate( m ) ) - { - ClearCurrentAbility( m ); - return false; - } - - if ( a == null ) - { - Table.Remove( m ); - } - else - { - SpecialMove.ClearCurrentMove( m ); - - Table[m] = a; - } - - return true; - } - - public static void ClearCurrentAbility( Mobile m ) - { - Table.Remove( m ); - - if ( Core.AOS && m.NetState != null ) - m.Send( ClearWeaponAbility.Instance ); - } - - public static void Initialize() - { - EventSink.SetAbility += EventSink_SetAbility; - } - - public WeaponAbility() - { - } - - private static void EventSink_SetAbility( SetAbilityEventArgs e ) - { - int index = e.Index; - - if ( index == 0 ) - ClearCurrentAbility( e.Mobile ); - else if ( index >= 1 && index < Abilities.Length ) - SetCurrentAbility( e.Mobile, Abilities[index] ); - } - - - private static Hashtable m_PlayersTable = new Hashtable(); - - private static void AddContext( Mobile m, WeaponAbilityContext context ) - { - m_PlayersTable[m] = context; - } - - private static void RemoveContext( Mobile m ) - { - WeaponAbilityContext context = GetContext( m ); - - if ( context != null ) - RemoveContext( m, context ); - } - - private static void RemoveContext( Mobile m, WeaponAbilityContext context ) - { - m_PlayersTable.Remove( m ); - - context.Timer.Stop(); - } - - private static WeaponAbilityContext GetContext( Mobile m ) - { - return ( m_PlayersTable[m] as WeaponAbilityContext ); - } - - private class WeaponAbilityTimer : Timer - { - private Mobile m_Mobile; - - public WeaponAbilityTimer( Mobile from ) : base ( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Mobile = from; - - Priority = TimerPriority.TwentyFiveMS; - } - - protected override void OnTick() - { - RemoveContext( m_Mobile ); - } - } - - private class WeaponAbilityContext - { - public Timer Timer { get; } - - public WeaponAbilityContext( Timer timer ) - { - Timer = timer; - } - } - } -} + public abstract class WeaponAbility + { + public static readonly WeaponAbility ArmorIgnore = Abilities[1]; + public static readonly WeaponAbility BleedAttack = Abilities[2]; + public static readonly WeaponAbility ConcussionBlow = Abilities[3]; + public static readonly WeaponAbility CrushingBlow = Abilities[4]; + public static readonly WeaponAbility Disarm = Abilities[5]; + public static readonly WeaponAbility Dismount = Abilities[6]; + public static readonly WeaponAbility DoubleStrike = Abilities[7]; + public static readonly WeaponAbility InfectiousStrike = Abilities[8]; + public static readonly WeaponAbility MortalStrike = Abilities[9]; + public static readonly WeaponAbility MovingShot = Abilities[10]; + public static readonly WeaponAbility ParalyzingBlow = Abilities[11]; + public static readonly WeaponAbility ShadowStrike = Abilities[12]; + public static readonly WeaponAbility WhirlwindAttack = Abilities[13]; + + public static readonly WeaponAbility RidingSwipe = Abilities[14]; + public static readonly WeaponAbility FrenziedWhirlwind = Abilities[15]; + public static readonly WeaponAbility Block = Abilities[16]; + public static readonly WeaponAbility DefenseMastery = Abilities[17]; + public static readonly WeaponAbility NerveStrike = Abilities[18]; + public static readonly WeaponAbility TalonStrike = Abilities[19]; + public static readonly WeaponAbility Feint = Abilities[20]; + public static readonly WeaponAbility DualWield = Abilities[21]; + public static readonly WeaponAbility DoubleShot = Abilities[22]; + public static readonly WeaponAbility ArmorPierce = Abilities[23]; + + public static readonly WeaponAbility Bladeweave = Abilities[24]; + public static readonly WeaponAbility ForceArrow = Abilities[25]; + public static readonly WeaponAbility LightningArrow = Abilities[26]; + public static readonly WeaponAbility PsychicAttack = Abilities[27]; + public static readonly WeaponAbility SerpentArrow = Abilities[28]; + public static readonly WeaponAbility ForceOfNature = Abilities[29]; + + public static readonly WeaponAbility Disrobe = Abilities[30]; + + + private static Hashtable m_PlayersTable = new Hashtable(); + + public virtual int BaseMana => 0; + + public virtual int AccuracyBonus => 0; + public virtual double DamageScalar => 1.0; + + public virtual bool RequiresSE => false; + + public static WeaponAbility[] Abilities{ get; } = new WeaponAbility[31] + { + null, + new ArmorIgnore(), + new BleedAttack(), + new ConcussionBlow(), + new CrushingBlow(), + new Disarm(), + new Dismount(), + new DoubleStrike(), + new InfectiousStrike(), + new MortalStrike(), + new MovingShot(), + new ParalyzingBlow(), + new ShadowStrike(), + new WhirlwindAttack(), + + new RidingSwipe(), + new FrenziedWhirlwind(), + new Block(), + new DefenseMastery(), + new NerveStrike(), + new TalonStrike(), + new Feint(), + new DualWield(), + new DoubleShot(), + new ArmorPierce(), + null, + null, + null, + null, + null, + null, + new Disrobe() + }; + + public static Hashtable Table{ get; } = new Hashtable(); + + public virtual bool ValidatesDuringHit => true; + + public virtual void OnHit(Mobile attacker, Mobile defender, int damage) + { + } + + public virtual void OnMiss(Mobile attacker, Mobile defender) + { + } + + public virtual bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + // Here because you must be sure you can use the skill before calling CheckHit if the ability has a HCI bonus for example + return true; + } + + public virtual bool OnBeforeDamage(Mobile attacker, Mobile defender) + { + return true; + } + + public virtual bool RequiresTactics(Mobile from) + { + return true; + } + + public virtual double GetRequiredSkill(Mobile from) + { + BaseWeapon weapon = from.Weapon as BaseWeapon; + + if (weapon != null && weapon.PrimaryAbility == this) + return 70.0; + if (weapon != null && weapon.SecondaryAbility == this) + return 90.0; + + return 200.0; + } + + public virtual int CalculateMana(Mobile from) + { + int mana = BaseMana; + + double skillTotal = GetSkill(from, SkillName.Swords) + GetSkill(from, SkillName.Macing) + + GetSkill(from, SkillName.Fencing) + + GetSkill(from, SkillName.Archery) + + GetSkill(from, SkillName.Parry) + + GetSkill(from, SkillName.Lumberjacking) + + GetSkill(from, SkillName.Stealth) + + GetSkill(from, SkillName.Poisoning) + + GetSkill(from, SkillName.Bushido) + + GetSkill(from, SkillName.Ninjitsu); + + if (skillTotal >= 300.0) + mana -= 10; + else if (skillTotal >= 200.0) + mana -= 5; + + double scalar = 1.0; + if (!MindRotSpell.GetMindRotScalar(from, ref scalar)) + scalar = 1.0; + + // Lower Mana Cost = 40% + int lmc = Math.Min(AosAttributes.GetValue(from, AosAttribute.LowerManaCost), 40); + + scalar -= (double)lmc / 100; + mana = (int)(mana * scalar); + + // Using a special move within 3 seconds of the previous special move costs double mana + if (GetContext(from) != null) + mana *= 2; + + return mana; + } + + public virtual bool CheckWeaponSkill(Mobile from) + { + if (!(from.Weapon is BaseWeapon weapon)) + return false; + + Skill skill = from.Skills[weapon.Skill]; + double reqSkill = GetRequiredSkill(from); + bool reqTactics = Core.ML && RequiresTactics(from); + + if (Core.ML && reqTactics && from.Skills[SkillName.Tactics].Base < reqSkill) + { + from.SendLocalizedMessage(1079308, + reqSkill.ToString()); // You need ~1_SKILL_REQUIREMENT~ weapon and tactics skill to perform that attack + return false; + } + + if (skill != null && skill.Base >= reqSkill) + return true; + + /* */ + if (weapon.WeaponAttributes.UseBestSkill > 0 && (from.Skills[SkillName.Swords].Base >= reqSkill || + from.Skills[SkillName.Macing].Base >= reqSkill || + from.Skills[SkillName.Fencing].Base >= reqSkill)) + return true; + /* */ + + if (reqTactics) + from.SendLocalizedMessage(1079308, + reqSkill.ToString()); // You need ~1_SKILL_REQUIREMENT~ weapon and tactics skill to perform that attack + else + from.SendLocalizedMessage(1060182, + reqSkill.ToString()); // You need ~1_SKILL_REQUIREMENT~ weapon skill to perform that attack + + return false; + } + + public virtual bool CheckSkills(Mobile from) + { + return CheckWeaponSkill(from); + } + + public virtual double GetSkill(Mobile from, SkillName skillName) + { + Skill skill = from.Skills[skillName]; + + if (skill == null) + return 0.0; + + return skill.Value; + } + + public virtual bool CheckMana(Mobile from, bool consume) + { + int mana = CalculateMana(from); + + if (from.Mana < mana) + { + if (from is BaseCreature creature && creature.HasManaOveride) return true; + + from.SendLocalizedMessage(1060181, + mana.ToString()); // You need ~1_MANA_REQUIREMENT~ mana to perform that attack + return false; + } + + if (consume) + { + if (GetContext(from) == null) + { + Timer timer = new WeaponAbilityTimer(from); + timer.Start(); + + AddContext(from, new WeaponAbilityContext(timer)); + } + + from.Mana -= mana; + } + + return true; + } + + public virtual bool Validate(Mobile from) + { + if (!from.Player) + return true; + + NetState state = from.NetState; + + if (state == null) + return false; + + if (RequiresSE && !state.SupportsExpansion(Expansion.SE)) + { + from.SendLocalizedMessage(1063456); // You must upgrade to Samurai Empire in order to use that ability. + return false; + } + + if (HonorableExecution.IsUnderPenalty(from) || AnimalForm.UnderTransformation(from)) + { + from.SendLocalizedMessage(1063024); // You cannot perform this special move right now. + return false; + } + + if (Core.ML && from.Spell != null) + { + from.SendLocalizedMessage(1063024); // You cannot perform this special move right now. + return false; + } + + #region Dueling + + string option = null; + + if (this is ArmorIgnore) + option = "Armor Ignore"; + else if (this is BleedAttack) + option = "Bleed Attack"; + else if (this is ConcussionBlow) + option = "Concussion Blow"; + else if (this is CrushingBlow) + option = "Crushing Blow"; + else if (this is Disarm) + option = "Disarm"; + else if (this is Dismount) + option = "Dismount"; + else if (this is DoubleStrike) + option = "Double Strike"; + else if (this is InfectiousStrike) + option = "Infectious Strike"; + else if (this is MortalStrike) + option = "Mortal Strike"; + else if (this is MovingShot) + option = "Moving Shot"; + else if (this is ParalyzingBlow) + option = "Paralyzing Blow"; + else if (this is ShadowStrike) + option = "Shadow Strike"; + else if (this is WhirlwindAttack) + option = "Whirlwind Attack"; + else if (this is RidingSwipe) + option = "Riding Swipe"; + else if (this is FrenziedWhirlwind) + option = "Frenzied Whirlwind"; + else if (this is Block) + option = "Block"; + else if (this is DefenseMastery) + option = "Defense Mastery"; + else if (this is NerveStrike) + option = "Nerve Strike"; + else if (this is TalonStrike) + option = "Talon Strike"; + else if (this is Feint) + option = "Feint"; + else if (this is DualWield) + option = "Dual Wield"; + else if (this is DoubleShot) + option = "Double Shot"; + else if (this is ArmorPierce) + option = "Armor Pierce"; + + + if (option != null && !DuelContext.AllowSpecialAbility(from, option, true)) + return false; + + #endregion + + return CheckSkills(from) && CheckMana(from, false); + } + + public static bool IsWeaponAbility(Mobile m, WeaponAbility a) + { + if (a == null) + return true; + + if (!m.Player) + return true; + + return m.Weapon is BaseWeapon weapon && (weapon.PrimaryAbility == a || weapon.SecondaryAbility == a); + } + + public static WeaponAbility GetCurrentAbility(Mobile m) + { + if (!Core.AOS) + { + ClearCurrentAbility(m); + return null; + } + + WeaponAbility a = (WeaponAbility)Table[m]; + + if (!IsWeaponAbility(m, a)) + { + ClearCurrentAbility(m); + return null; + } + + if (a != null && a.ValidatesDuringHit && !a.Validate(m)) + { + ClearCurrentAbility(m); + return null; + } + + return a; + } + + public static bool SetCurrentAbility(Mobile m, WeaponAbility a) + { + if (!Core.AOS) + { + ClearCurrentAbility(m); + return false; + } + + if (!IsWeaponAbility(m, a)) + { + ClearCurrentAbility(m); + return false; + } + + if (a != null && !a.Validate(m)) + { + ClearCurrentAbility(m); + return false; + } + + if (a == null) + { + Table.Remove(m); + } + else + { + SpecialMove.ClearCurrentMove(m); + + Table[m] = a; + } + + return true; + } + + public static void ClearCurrentAbility(Mobile m) + { + Table.Remove(m); + + if (Core.AOS && m.NetState != null) + m.Send(ClearWeaponAbility.Instance); + } + + public static void Initialize() + { + EventSink.SetAbility += EventSink_SetAbility; + } + + private static void EventSink_SetAbility(SetAbilityEventArgs e) + { + int index = e.Index; + + if (index == 0) + ClearCurrentAbility(e.Mobile); + else if (index >= 1 && index < Abilities.Length) + SetCurrentAbility(e.Mobile, Abilities[index]); + } + + private static void AddContext(Mobile m, WeaponAbilityContext context) + { + m_PlayersTable[m] = context; + } + + private static void RemoveContext(Mobile m) + { + WeaponAbilityContext context = GetContext(m); + + if (context != null) + RemoveContext(m, context); + } + + private static void RemoveContext(Mobile m, WeaponAbilityContext context) + { + m_PlayersTable.Remove(m); + + context.Timer.Stop(); + } + + private static WeaponAbilityContext GetContext(Mobile m) + { + return m_PlayersTable[m] as WeaponAbilityContext; + } + + private class WeaponAbilityTimer : Timer + { + private Mobile m_Mobile; + + public WeaponAbilityTimer(Mobile from) : base(TimeSpan.FromSeconds(3.0)) + { + m_Mobile = from; + + Priority = TimerPriority.TwentyFiveMS; + } + + protected override void OnTick() + { + RemoveContext(m_Mobile); + } + } + + private class WeaponAbilityContext + { + public WeaponAbilityContext(Timer timer) + { + Timer = timer; + } + + public Timer Timer{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Abilities/WhirlwindAttack.cs b/Scripts/Items/Weapons/Abilities/WhirlwindAttack.cs index 954ff76d7..085eda9e0 100644 --- a/Scripts/Items/Weapons/Abilities/WhirlwindAttack.cs +++ b/Scripts/Items/Weapons/Abilities/WhirlwindAttack.cs @@ -4,82 +4,80 @@ using Server.Spells; namespace Server.Items { - /// - /// A godsend to a warrior surrounded, the Whirlwind Attack allows the fighter to strike at all nearby targets in one mighty spinning swing. - /// - public class WhirlwindAttack : WeaponAbility - { - public WhirlwindAttack() - { - } + /// + /// A godsend to a warrior surrounded, the Whirlwind Attack allows the fighter to strike at all nearby targets in one mighty + /// spinning swing. + /// + public class WhirlwindAttack : WeaponAbility + { + public override int BaseMana => 15; - public override int BaseMana => 15; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) ) - return; + ClearCurrentAbility(attacker); - ClearCurrentAbility( attacker ); + Map map = attacker.Map; - Map map = attacker.Map; + if (map == null) + return; - if ( map == null ) - return; + if (!(attacker.Weapon is BaseWeapon weapon)) + return; - if ( !(attacker.Weapon is BaseWeapon weapon) ) - return; + if (!CheckMana(attacker, true)) + return; - if ( !CheckMana( attacker, true ) ) - return; + attacker.FixedEffect(0x3728, 10, 15); + attacker.PlaySound(0x2A1); - attacker.FixedEffect( 0x3728, 10, 15 ); - attacker.PlaySound( 0x2A1 ); + ArrayList list = new ArrayList(); - ArrayList list = new ArrayList(); + foreach (Mobile m in attacker.GetMobilesInRange(1)) + list.Add(m); - foreach ( Mobile m in attacker.GetMobilesInRange( 1 ) ) - list.Add( m ); + ArrayList targets = new ArrayList(); - ArrayList targets = new ArrayList(); + for (int i = 0; i < list.Count; ++i) + { + Mobile m = (Mobile)list[i]; - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; + if (m != defender && m != attacker && SpellHelper.ValidIndirectTarget(attacker, m)) + { + if (m == null || m.Deleted || m.Map != attacker.Map || !m.Alive || !attacker.CanSee(m) || + !attacker.CanBeHarmful(m)) + continue; - if ( m != defender && m != attacker && SpellHelper.ValidIndirectTarget( attacker, m ) ) - { - if ( m == null || m.Deleted || m.Map != attacker.Map || !m.Alive || !attacker.CanSee( m ) || !attacker.CanBeHarmful( m ) ) - continue; + if (!attacker.InRange(m, weapon.MaxRange)) + continue; - if ( !attacker.InRange( m, weapon.MaxRange ) ) - continue; + if (attacker.InLOS(m)) + targets.Add(m); + } + } - if ( attacker.InLOS( m ) ) - targets.Add( m ); - } - } + if (targets.Count > 0) + { + double bushido = attacker.Skills.Bushido.Value; + double damageBonus = 1.0 + Math.Pow(targets.Count * bushido / 60, 2) / 100; - if ( targets.Count > 0 ) - { - double bushido = attacker.Skills.Bushido.Value; - double damageBonus = 1.0 + Math.Pow( (targets.Count * bushido) / 60, 2 ) / 100; + if (damageBonus > 2.0) + damageBonus = 2.0; - if ( damageBonus > 2.0 ) - damageBonus = 2.0; + attacker.RevealingAction(); - attacker.RevealingAction(); + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = (Mobile)targets[i]; - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = (Mobile)targets[i]; + attacker.SendLocalizedMessage(1060161); // The whirling attack strikes a target! + m.SendLocalizedMessage(1060162); // You are struck by the whirling attack and take damage! - attacker.SendLocalizedMessage( 1060161 ); // The whirling attack strikes a target! - m.SendLocalizedMessage( 1060162 ); // You are struck by the whirling attack and take damage! - - weapon.OnHit( attacker, m, damageBonus ); - } - } - } - } -} + weapon.OnHit(attacker, m, damageBonus); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/AxeOfTheHeavens.cs b/Scripts/Items/Weapons/Artifacts/AxeOfTheHeavens.cs index d5ded4513..5842d5cd1 100644 --- a/Scripts/Items/Weapons/Artifacts/AxeOfTheHeavens.cs +++ b/Scripts/Items/Weapons/Artifacts/AxeOfTheHeavens.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class AxeOfTheHeavens : DoubleAxe - { - public override int LabelNumber => 1061106; // Axe of the Heavens - public override int ArtifactRarity => 11; + public class AxeOfTheHeavens : DoubleAxe + { + [Constructible] + public AxeOfTheHeavens() + { + Hue = 0x4D5; + WeaponAttributes.HitLightning = 50; + Attributes.AttackChance = 15; + Attributes.DefendChance = 15; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public AxeOfTheHeavens(Serial serial) : base(serial) + { + } - [Constructible] - public AxeOfTheHeavens() - { - Hue = 0x4D5; - WeaponAttributes.HitLightning = 50; - Attributes.AttackChance = 15; - Attributes.DefendChance = 15; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061106; // Axe of the Heavens + public override int ArtifactRarity => 11; - public AxeOfTheHeavens( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/BladeOfInsanity.cs b/Scripts/Items/Weapons/Artifacts/BladeOfInsanity.cs index 193b13562..e1f6fb67f 100644 --- a/Scripts/Items/Weapons/Artifacts/BladeOfInsanity.cs +++ b/Scripts/Items/Weapons/Artifacts/BladeOfInsanity.cs @@ -1,42 +1,42 @@ namespace Server.Items { - public class BladeOfInsanity : Katana - { - public override int LabelNumber => 1061088; // Blade of Insanity - public override int ArtifactRarity => 11; + public class BladeOfInsanity : Katana + { + [Constructible] + public BladeOfInsanity() + { + Hue = 0x76D; + WeaponAttributes.HitLeechStam = 100; + Attributes.RegenStam = 2; + Attributes.WeaponSpeed = 30; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public BladeOfInsanity(Serial serial) : base(serial) + { + } - [Constructible] - public BladeOfInsanity() - { - Hue = 0x76D; - WeaponAttributes.HitLeechStam = 100; - Attributes.RegenStam = 2; - Attributes.WeaponSpeed = 30; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061088; // Blade of Insanity + public override int ArtifactRarity => 11; - public BladeOfInsanity( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 0x44F ) - Hue = 0x76D; - } - } -} + if (Hue == 0x44F) + Hue = 0x76D; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/BladeOfTheRighteous.cs b/Scripts/Items/Weapons/Artifacts/BladeOfTheRighteous.cs index 989baf74e..de98d3d1f 100644 --- a/Scripts/Items/Weapons/Artifacts/BladeOfTheRighteous.cs +++ b/Scripts/Items/Weapons/Artifacts/BladeOfTheRighteous.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class BladeOfTheRighteous : Longsword - { - public override int LabelNumber => 1061107; // Blade of the Righteous - public override int ArtifactRarity => 10; + public class BladeOfTheRighteous : Longsword + { + [Constructible] + public BladeOfTheRighteous() + { + Hue = 0x47E; + //Slayer = SlayerName.DaemonDismissal; + Slayer = SlayerName.Exorcism; + WeaponAttributes.HitLeechHits = 50; + WeaponAttributes.UseBestSkill = 1; + Attributes.BonusHits = 10; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public BladeOfTheRighteous(Serial serial) : base(serial) + { + } - [Constructible] - public BladeOfTheRighteous() - { - Hue = 0x47E; - //Slayer = SlayerName.DaemonDismissal; - Slayer = SlayerName.Exorcism; - WeaponAttributes.HitLeechHits = 50; - WeaponAttributes.UseBestSkill = 1; - Attributes.BonusHits = 10; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061107; // Blade of the Righteous + public override int ArtifactRarity => 10; - public BladeOfTheRighteous( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Slayer == SlayerName.None ) - Slayer = SlayerName.Exorcism; - } - } -} + if (Slayer == SlayerName.None) + Slayer = SlayerName.Exorcism; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/BoneCrusher.cs b/Scripts/Items/Weapons/Artifacts/BoneCrusher.cs index 188320eba..5c2f81104 100644 --- a/Scripts/Items/Weapons/Artifacts/BoneCrusher.cs +++ b/Scripts/Items/Weapons/Artifacts/BoneCrusher.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class BoneCrusher : WarMace - { - public override int LabelNumber => 1061596; // Bone Crusher - public override int ArtifactRarity => 11; + public class BoneCrusher : WarMace + { + [Constructible] + public BoneCrusher() + { + ItemID = 0x1406; + Hue = 0x60C; + WeaponAttributes.HitLowerDefend = 50; + Attributes.BonusStr = 10; + Attributes.WeaponDamage = 75; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public BoneCrusher(Serial serial) : base(serial) + { + } - [Constructible] - public BoneCrusher() - { - ItemID = 0x1406; - Hue = 0x60C; - WeaponAttributes.HitLowerDefend = 50; - Attributes.BonusStr = 10; - Attributes.WeaponDamage = 75; - } + public override int LabelNumber => 1061596; // Bone Crusher + public override int ArtifactRarity => 11; - public BoneCrusher( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Hue == 0x604 ) - Hue = 0x60C; + if (Hue == 0x604) + Hue = 0x60C; - if ( ItemID == 0x1407 ) - ItemID = 0x1406; - } - } -} + if (ItemID == 0x1407) + ItemID = 0x1406; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/BreathOfTheDead.cs b/Scripts/Items/Weapons/Artifacts/BreathOfTheDead.cs index f00766b63..47c060de8 100644 --- a/Scripts/Items/Weapons/Artifacts/BreathOfTheDead.cs +++ b/Scripts/Items/Weapons/Artifacts/BreathOfTheDead.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class BreathOfTheDead : BoneHarvester - { - public override int LabelNumber => 1061109; // Breath of the Dead - public override int ArtifactRarity => 11; + public class BreathOfTheDead : BoneHarvester + { + [Constructible] + public BreathOfTheDead() + { + Hue = 0x455; + WeaponAttributes.HitLeechHits = 100; + WeaponAttributes.HitHarm = 25; + Attributes.SpellDamage = 5; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public BreathOfTheDead(Serial serial) : base(serial) + { + } - [Constructible] - public BreathOfTheDead() - { - Hue = 0x455; - WeaponAttributes.HitLeechHits = 100; - WeaponAttributes.HitHarm = 25; - Attributes.SpellDamage = 5; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061109; // Breath of the Dead + public override int ArtifactRarity => 11; - public BreathOfTheDead( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/Frostbringer.cs b/Scripts/Items/Weapons/Artifacts/Frostbringer.cs index 89bdc5ac8..fa5ec1f3d 100644 --- a/Scripts/Items/Weapons/Artifacts/Frostbringer.cs +++ b/Scripts/Items/Weapons/Artifacts/Frostbringer.cs @@ -1,44 +1,45 @@ namespace Server.Items { - public class Frostbringer : Bow - { - public override int LabelNumber => 1061111; // Frostbringer - public override int ArtifactRarity => 11; + public class Frostbringer : Bow + { + [Constructible] + public Frostbringer() + { + Hue = 0x4F2; + WeaponAttributes.HitDispel = 50; + Attributes.RegenStam = 10; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public Frostbringer(Serial serial) : base(serial) + { + } - [Constructible] - public Frostbringer() - { - Hue = 0x4F2; - WeaponAttributes.HitDispel = 50; - Attributes.RegenStam = 10; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061111; // Frostbringer + public override int ArtifactRarity => 11; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = pois = nrgy = chaos = direct = 0; - cold = 100; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public Frostbringer( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = pois = nrgy = chaos = direct = 0; + cold = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/LegacyOfTheDreadLord.cs b/Scripts/Items/Weapons/Artifacts/LegacyOfTheDreadLord.cs index 34a64e852..079394948 100644 --- a/Scripts/Items/Weapons/Artifacts/LegacyOfTheDreadLord.cs +++ b/Scripts/Items/Weapons/Artifacts/LegacyOfTheDreadLord.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class LegacyOfTheDreadLord : Bardiche - { - public override int LabelNumber => 1060860; // Legacy of the Dread Lord - public override int ArtifactRarity => 10; + public class LegacyOfTheDreadLord : Bardiche + { + [Constructible] + public LegacyOfTheDreadLord() + { + Hue = 0x676; + Attributes.SpellChanneling = 1; + Attributes.CastRecovery = 3; + Attributes.WeaponSpeed = 30; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public LegacyOfTheDreadLord(Serial serial) : base(serial) + { + } - [Constructible] - public LegacyOfTheDreadLord() - { - Hue = 0x676; - Attributes.SpellChanneling = 1; - Attributes.CastRecovery = 3; - Attributes.WeaponSpeed = 30; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1060860; // Legacy of the Dread Lord + public override int ArtifactRarity => 10; - public LegacyOfTheDreadLord( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Attributes.CastSpeed == 3 ) - Attributes.CastRecovery = 3; + if (Attributes.CastSpeed == 3) + Attributes.CastRecovery = 3; - if ( Hue == 0x4B9 ) - Hue = 0x676; - } - } -} + if (Hue == 0x4B9) + Hue = 0x676; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/SerpentsFang.cs b/Scripts/Items/Weapons/Artifacts/SerpentsFang.cs index 9f56d3303..825bd2e26 100644 --- a/Scripts/Items/Weapons/Artifacts/SerpentsFang.cs +++ b/Scripts/Items/Weapons/Artifacts/SerpentsFang.cs @@ -1,50 +1,51 @@ namespace Server.Items { - public class SerpentsFang : Kryss - { - public override int LabelNumber => 1061601; // Serpent's Fang - public override int ArtifactRarity => 11; + public class SerpentsFang : Kryss + { + [Constructible] + public SerpentsFang() + { + ItemID = 0x1400; + Hue = 0x488; + WeaponAttributes.HitPoisonArea = 100; + WeaponAttributes.ResistPoisonBonus = 20; + Attributes.AttackChance = 15; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public SerpentsFang(Serial serial) : base(serial) + { + } - [Constructible] - public SerpentsFang() - { - ItemID = 0x1400; - Hue = 0x488; - WeaponAttributes.HitPoisonArea = 100; - WeaponAttributes.ResistPoisonBonus = 20; - Attributes.AttackChance = 15; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061601; // Serpent's Fang + public override int ArtifactRarity => 11; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - fire = cold = nrgy = chaos = direct = 0; - phys = 25; - pois = 75; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public SerpentsFang( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + fire = cold = nrgy = chaos = direct = 0; + phys = 25; + pois = 75; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( ItemID == 0x1401 ) - ItemID = 0x1400; - } - } -} + if (ItemID == 0x1401) + ItemID = 0x1400; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/StaffOfTheMagi.cs b/Scripts/Items/Weapons/Artifacts/StaffOfTheMagi.cs index 5166f7bc3..13430aaf8 100644 --- a/Scripts/Items/Weapons/Artifacts/StaffOfTheMagi.cs +++ b/Scripts/Items/Weapons/Artifacts/StaffOfTheMagi.cs @@ -1,51 +1,52 @@ namespace Server.Items { - public class StaffOfTheMagi : BlackStaff - { - public override int LabelNumber => 1061600; // Staff of the Magi - public override int ArtifactRarity => 11; + public class StaffOfTheMagi : BlackStaff + { + [Constructible] + public StaffOfTheMagi() + { + Hue = 0x481; + WeaponAttributes.MageWeapon = 30; + Attributes.SpellChanneling = 1; + Attributes.CastSpeed = 1; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public StaffOfTheMagi(Serial serial) : base(serial) + { + } - [Constructible] - public StaffOfTheMagi() - { - Hue = 0x481; - WeaponAttributes.MageWeapon = 30; - Attributes.SpellChanneling = 1; - Attributes.CastSpeed = 1; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061600; // Staff of the Magi + public override int ArtifactRarity => 11; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = chaos = direct = 0; - nrgy = 100; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public StaffOfTheMagi( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = chaos = direct = 0; + nrgy = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( WeaponAttributes.MageWeapon == 0 ) - WeaponAttributes.MageWeapon = 30; + if (WeaponAttributes.MageWeapon == 0) + WeaponAttributes.MageWeapon = 30; - if ( ItemID == 0xDF1 ) - ItemID = 0xDF0; - } - } -} + if (ItemID == 0xDF1) + ItemID = 0xDF0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/TheBeserkersMaul.cs b/Scripts/Items/Weapons/Artifacts/TheBeserkersMaul.cs index 1f2e2179f..b93ea530c 100644 --- a/Scripts/Items/Weapons/Artifacts/TheBeserkersMaul.cs +++ b/Scripts/Items/Weapons/Artifacts/TheBeserkersMaul.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class TheBeserkersMaul : Maul - { - public override int LabelNumber => 1061108; // The Berserker's Maul - public override int ArtifactRarity => 11; + public class TheBeserkersMaul : Maul + { + [Constructible] + public TheBeserkersMaul() + { + Hue = 0x21; + Attributes.WeaponSpeed = 75; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public TheBeserkersMaul(Serial serial) : base(serial) + { + } - [Constructible] - public TheBeserkersMaul() - { - Hue = 0x21; - Attributes.WeaponSpeed = 75; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061108; // The Berserker's Maul + public override int ArtifactRarity => 11; - public TheBeserkersMaul( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/TheDragonSlayer.cs b/Scripts/Items/Weapons/Artifacts/TheDragonSlayer.cs index 364388d16..760d04bc0 100644 --- a/Scripts/Items/Weapons/Artifacts/TheDragonSlayer.cs +++ b/Scripts/Items/Weapons/Artifacts/TheDragonSlayer.cs @@ -1,49 +1,50 @@ namespace Server.Items { - public class TheDragonSlayer : Lance - { - public override int LabelNumber => 1061248; // The Dragon Slayer - public override int ArtifactRarity => 11; + public class TheDragonSlayer : Lance + { + [Constructible] + public TheDragonSlayer() + { + Hue = 0x530; + Slayer = SlayerName.DragonSlaying; + Attributes.Luck = 110; + Attributes.WeaponDamage = 50; + WeaponAttributes.ResistFireBonus = 20; + WeaponAttributes.UseBestSkill = 1; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public TheDragonSlayer(Serial serial) : base(serial) + { + } - [Constructible] - public TheDragonSlayer() - { - Hue = 0x530; - Slayer = SlayerName.DragonSlaying; - Attributes.Luck = 110; - Attributes.WeaponDamage = 50; - WeaponAttributes.ResistFireBonus = 20; - WeaponAttributes.UseBestSkill = 1; - } + public override int LabelNumber => 1061248; // The Dragon Slayer + public override int ArtifactRarity => 11; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = chaos = direct = 0; - nrgy = 100; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public TheDragonSlayer( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = chaos = direct = 0; + nrgy = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Slayer == SlayerName.None ) - Slayer = SlayerName.DragonSlaying; - } - } -} + if (Slayer == SlayerName.None) + Slayer = SlayerName.DragonSlaying; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/TheDryadBow.cs b/Scripts/Items/Weapons/Artifacts/TheDryadBow.cs index cea761d26..58985690e 100644 --- a/Scripts/Items/Weapons/Artifacts/TheDryadBow.cs +++ b/Scripts/Items/Weapons/Artifacts/TheDryadBow.cs @@ -1,53 +1,56 @@ namespace Server.Items { - public class TheDryadBow : Bow - { - public override int LabelNumber => 1061090; // The Dryad Bow - public override int ArtifactRarity => 11; + public class TheDryadBow : Bow + { + private static SkillName[] m_PossibleBonusSkills = + { + SkillName.Archery, + SkillName.Healing, + SkillName.MagicResist, + SkillName.Peacemaking, + SkillName.Chivalry, + SkillName.Ninjitsu + }; - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + [Constructible] + public TheDryadBow() + { + ItemID = 0x13B1; + Hue = 0x48F; + SkillBonuses.SetValues(0, m_PossibleBonusSkills[Utility.Random(m_PossibleBonusSkills.Length)], + Utility.Random(4) == 0 ? 10.0 : 5.0); + WeaponAttributes.SelfRepair = 5; + Attributes.WeaponSpeed = 50; + Attributes.WeaponDamage = 35; + WeaponAttributes.ResistPoisonBonus = 15; + } - [Constructible] - public TheDryadBow() - { - ItemID = 0x13B1; - Hue = 0x48F; - SkillBonuses.SetValues( 0, m_PossibleBonusSkills[Utility.Random(m_PossibleBonusSkills.Length)], (Utility.Random( 4 ) == 0 ? 10.0 : 5.0) ); - WeaponAttributes.SelfRepair = 5; - Attributes.WeaponSpeed = 50; - Attributes.WeaponDamage = 35; - WeaponAttributes.ResistPoisonBonus = 15; - } + public TheDryadBow(Serial serial) : base(serial) + { + } - private static SkillName[] m_PossibleBonusSkills = { - SkillName.Archery, - SkillName.Healing, - SkillName.MagicResist, - SkillName.Peacemaking, - SkillName.Chivalry, - SkillName.Ninjitsu - }; + public override int LabelNumber => 1061090; // The Dryad Bow + public override int ArtifactRarity => 11; - public TheDryadBow( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 ) - SkillBonuses.SetValues( 0, m_PossibleBonusSkills[Utility.Random(m_PossibleBonusSkills.Length)], (Utility.Random( 4 ) == 0 ? 10.0 : 5.0) ); - } - } -} + if (version < 1) + SkillBonuses.SetValues(0, m_PossibleBonusSkills[Utility.Random(m_PossibleBonusSkills.Length)], + Utility.Random(4) == 0 ? 10.0 : 5.0); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/TheTaskmaster.cs b/Scripts/Items/Weapons/Artifacts/TheTaskmaster.cs index 974029410..13ee8b416 100644 --- a/Scripts/Items/Weapons/Artifacts/TheTaskmaster.cs +++ b/Scripts/Items/Weapons/Artifacts/TheTaskmaster.cs @@ -1,45 +1,46 @@ namespace Server.Items { - public class TheTaskmaster : WarFork - { - public override int LabelNumber => 1061110; // The Taskmaster - public override int ArtifactRarity => 10; + public class TheTaskmaster : WarFork + { + [Constructible] + public TheTaskmaster() + { + Hue = 0x4F8; + WeaponAttributes.HitPoisonArea = 100; + Attributes.BonusDex = 5; + Attributes.AttackChance = 15; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public TheTaskmaster(Serial serial) : base(serial) + { + } - [Constructible] - public TheTaskmaster() - { - Hue = 0x4F8; - WeaponAttributes.HitPoisonArea = 100; - Attributes.BonusDex = 5; - Attributes.AttackChance = 15; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061110; // The Taskmaster + public override int ArtifactRarity => 10; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = nrgy = chaos = direct = 0; - pois = 100; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public TheTaskmaster( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = nrgy = chaos = direct = 0; + pois = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/TitansHammer.cs b/Scripts/Items/Weapons/Artifacts/TitansHammer.cs index 297cf9647..f4a26a015 100644 --- a/Scripts/Items/Weapons/Artifacts/TitansHammer.cs +++ b/Scripts/Items/Weapons/Artifacts/TitansHammer.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class TitansHammer : WarHammer - { - public override int LabelNumber => 1060024; // Titan's Hammer - public override int ArtifactRarity => 10; + public class TitansHammer : WarHammer + { + [Constructible] + public TitansHammer() + { + Hue = 0x482; + WeaponAttributes.HitEnergyArea = 100; + Attributes.BonusStr = 15; + Attributes.AttackChance = 15; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public TitansHammer(Serial serial) : base(serial) + { + } - [Constructible] - public TitansHammer() - { - Hue = 0x482; - WeaponAttributes.HitEnergyArea = 100; - Attributes.BonusStr = 15; - Attributes.AttackChance = 15; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1060024; // Titan's Hammer + public override int ArtifactRarity => 10; - public TitansHammer( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Artifacts/ZyronicClaw.cs b/Scripts/Items/Weapons/Artifacts/ZyronicClaw.cs index 9c8843f68..f13671925 100644 --- a/Scripts/Items/Weapons/Artifacts/ZyronicClaw.cs +++ b/Scripts/Items/Weapons/Artifacts/ZyronicClaw.cs @@ -1,48 +1,49 @@ namespace Server.Items { - public class ZyronicClaw : ExecutionersAxe - { - public override int LabelNumber => 1061593; // Zyronic Claw - public override int ArtifactRarity => 10; + public class ZyronicClaw : ExecutionersAxe + { + [Constructible] + public ZyronicClaw() + { + Hue = 0x485; + Slayer = SlayerName.ElementalBan; + WeaponAttributes.HitLeechMana = 50; + Attributes.AttackChance = 30; + Attributes.WeaponDamage = 50; + } - public override int InitMinHits => 255; - public override int InitMaxHits => 255; + public ZyronicClaw(Serial serial) : base(serial) + { + } - [Constructible] - public ZyronicClaw() - { - Hue = 0x485; - Slayer = SlayerName.ElementalBan; - WeaponAttributes.HitLeechMana = 50; - Attributes.AttackChance = 30; - Attributes.WeaponDamage = 50; - } + public override int LabelNumber => 1061593; // Zyronic Claw + public override int ArtifactRarity => 10; - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - chaos = direct = 0; - phys = fire = cold = pois = nrgy = 20; - } + public override int InitMinHits => 255; + public override int InitMaxHits => 255; - public ZyronicClaw( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + chaos = direct = 0; + phys = fire = cold = pois = nrgy = 20; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Slayer == SlayerName.None ) - Slayer = SlayerName.ElementalBan; - } - } -} + if (Slayer == SlayerName.None) + Slayer = SlayerName.ElementalBan; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/Axe.cs b/Scripts/Items/Weapons/Axes/Axe.cs index 290bc0581..50af8f4c6 100644 --- a/Scripts/Items/Weapons/Axes/Axe.cs +++ b/Scripts/Items/Weapons/Axes/Axe.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xF49, 0xF4a )] - public class Axe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; + [Flippable(0xF49, 0xF4a)] + public class Axe : BaseAxe + { + [Constructible] + public Axe() : base(0xF49) + { + Weight = 4.0; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 16; - public override int AosSpeed => 37; - public override float MlSpeed => 3.00f; + public Axe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 33; - public override int OldSpeed => 37; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 16; + public override int AosSpeed => 37; + public override float MlSpeed => 3.00f; - [Constructible] - public Axe() : base( 0xF49 ) - { - Weight = 4.0; - } + public override int OldStrengthReq => 35; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 33; + public override int OldSpeed => 37; - public Axe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/BaseAxe.cs b/Scripts/Items/Weapons/Axes/BaseAxe.cs index 712c9c650..26efe7e93 100644 --- a/Scripts/Items/Weapons/Axes/BaseAxe.cs +++ b/Scripts/Items/Weapons/Axes/BaseAxe.cs @@ -1,170 +1,184 @@ using System; using System.Collections.Generic; -using Server.Engines.Harvest; using Server.ContextMenus; +using Server.Engines.ConPVP; +using Server.Engines.Harvest; using Server.Network; namespace Server.Items { - public interface IAxe - { - bool Axe( Mobile from, BaseAxe axe ); - } + public interface IAxe + { + bool Axe(Mobile from, BaseAxe axe); + } - public abstract class BaseAxe : BaseMeleeWeapon - { - public override int DefHitSound => 0x232; - public override int DefMissSound => 0x23A; + public abstract class BaseAxe : BaseMeleeWeapon + { + private bool m_ShowUsesRemaining; - public override SkillName DefSkill => SkillName.Swords; - public override WeaponType DefType => WeaponType.Axe; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash2H; + private int m_UsesRemaining; - public virtual HarvestSystem HarvestSystem => Lumberjacking.System; + public BaseAxe(int itemID) : base(itemID) + { + m_UsesRemaining = 150; + } - private int m_UsesRemaining; - private bool m_ShowUsesRemaining; + public BaseAxe(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + public override int DefHitSound => 0x232; + public override int DefMissSound => 0x23A; - [CommandProperty( AccessLevel.GameMaster )] - public bool ShowUsesRemaining - { - get => m_ShowUsesRemaining; - set { m_ShowUsesRemaining = value; InvalidateProperties(); } - } + public override SkillName DefSkill => SkillName.Swords; + public override WeaponType DefType => WeaponType.Axe; + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash2H; - public virtual int GetUsesScalar() - { - if ( Quality == WeaponQuality.Exceptional ) - return 200; + public virtual HarvestSystem HarvestSystem => Lumberjacking.System; - return 100; - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public override void UnscaleDurability() - { - base.UnscaleDurability(); + [CommandProperty(AccessLevel.GameMaster)] + public bool ShowUsesRemaining + { + get => m_ShowUsesRemaining; + set + { + m_ShowUsesRemaining = value; + InvalidateProperties(); + } + } - int scale = GetUsesScalar(); + public virtual int GetUsesScalar() + { + if (Quality == WeaponQuality.Exceptional) + return 200; - m_UsesRemaining = ((m_UsesRemaining * 100) + (scale - 1)) / scale; - InvalidateProperties(); - } + return 100; + } - public override void ScaleDurability() - { - base.ScaleDurability(); + public override void UnscaleDurability() + { + base.UnscaleDurability(); - int scale = GetUsesScalar(); + int scale = GetUsesScalar(); - m_UsesRemaining = ((m_UsesRemaining * scale) + 99) / 100; - InvalidateProperties(); - } + m_UsesRemaining = (m_UsesRemaining * 100 + (scale - 1)) / scale; + InvalidateProperties(); + } - public BaseAxe( int itemID ) : base( itemID ) - { - m_UsesRemaining = 150; - } + public override void ScaleDurability() + { + base.ScaleDurability(); - public BaseAxe( Serial serial ) : base( serial ) - { - } + int scale = GetUsesScalar(); - public override void OnDoubleClick( Mobile from ) - { - if ( HarvestSystem == null || Deleted ) - return; + m_UsesRemaining = (m_UsesRemaining * scale + 99) / 100; + InvalidateProperties(); + } - Point3D loc = GetWorldLocation(); + public override void OnDoubleClick(Mobile from) + { + if (HarvestSystem == null || Deleted) + return; - if ( !from.InLOS( loc ) || !from.InRange( loc, 2 ) ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 1019045 ); // I can't reach that - return; - } + Point3D loc = GetWorldLocation(); - if ( !IsAccessibleTo( from ) ) - { - PublicOverheadMessage( MessageType.Regular, 0x3E9, 1061637 ); // You are not allowed to access this. - return; - } + if (!from.InLOS(loc) || !from.InRange(loc, 2)) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 1019045); // I can't reach that + return; + } - if ( !(HarvestSystem is Mining) ) - from.SendLocalizedMessage( 1010018 ); // What do you want to use this item on? + if (!IsAccessibleTo(from)) + { + PublicOverheadMessage(MessageType.Regular, 0x3E9, 1061637); // You are not allowed to access this. + return; + } - HarvestSystem.BeginHarvesting( from, this ); - } + if (!(HarvestSystem is Mining)) + from.SendLocalizedMessage(1010018); // What do you want to use this item on? - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + HarvestSystem.BeginHarvesting(from, this); + } - if ( HarvestSystem != null ) - BaseHarvestTool.AddContextMenuEntries( from, this, list, HarvestSystem ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (HarvestSystem != null) + BaseHarvestTool.AddContextMenuEntries(from, this, list, HarvestSystem); + } - writer.Write( (int) 2 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (bool) m_ShowUsesRemaining ); + writer.Write(2); // version - writer.Write( (int) m_UsesRemaining ); - } + writer.Write(m_ShowUsesRemaining); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_UsesRemaining); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 2: - { - m_ShowUsesRemaining = reader.ReadBool(); - goto case 1; - } - case 1: - { - m_UsesRemaining = reader.ReadInt(); - goto case 0; - } - case 0: - { - if ( m_UsesRemaining < 1 ) - m_UsesRemaining = 150; + int version = reader.ReadInt(); - break; - } - } - } + switch (version) + { + case 2: + { + m_ShowUsesRemaining = reader.ReadBool(); + goto case 1; + } + case 1: + { + m_UsesRemaining = reader.ReadInt(); + goto case 0; + } + case 0: + { + if (m_UsesRemaining < 1) + m_UsesRemaining = 150; - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + break; + } + } + } - if (!Core.AOS && (attacker.Player || attacker.Body.IsHuman) && Layer == Layer.TwoHanded && attacker.Skills[SkillName.Anatomy].Value >= 80 && (attacker.Skills[SkillName.Anatomy].Value / 400.0) >= Utility.RandomDouble() && Engines.ConPVP.DuelContext.AllowSpecialAbility(attacker, "Concussion Blow", false)) - { - StatMod mod = defender.GetStatMod( "Concussion" ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - if ( mod == null ) - { - defender.SendMessage( "You receive a concussion blow!" ); - defender.AddStatMod( new StatMod( StatType.Int, "Concussion", -(defender.RawInt / 2), TimeSpan.FromSeconds( 30.0 ) ) ); + if (!Core.AOS && (attacker.Player || attacker.Body.IsHuman) && Layer == Layer.TwoHanded && + attacker.Skills[SkillName.Anatomy].Value >= 80 && + attacker.Skills[SkillName.Anatomy].Value / 400.0 >= Utility.RandomDouble() && + DuelContext.AllowSpecialAbility(attacker, "Concussion Blow", false)) + { + StatMod mod = defender.GetStatMod("Concussion"); - attacker.SendMessage( "You deliver a concussion blow!" ); - attacker.PlaySound( 0x308 ); - } - } - } - } -} + if (mod == null) + { + defender.SendMessage("You receive a concussion blow!"); + defender.AddStatMod(new StatMod(StatType.Int, "Concussion", -(defender.RawInt / 2), + TimeSpan.FromSeconds(30.0))); + + attacker.SendMessage("You deliver a concussion blow!"); + attacker.PlaySound(0x308); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/BattleAxe.cs b/Scripts/Items/Weapons/Axes/BattleAxe.cs index 4d30cff04..53f1b6586 100644 --- a/Scripts/Items/Weapons/Axes/BattleAxe.cs +++ b/Scripts/Items/Weapons/Axes/BattleAxe.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0xF47, 0xF48 )] - public class BattleAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; + [Flippable(0xF47, 0xF48)] + public class BattleAxe : BaseAxe + { + [Constructible] + public BattleAxe() : base(0xF47) + { + Weight = 4.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 31; - public override float MlSpeed => 3.50f; + public BattleAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 38; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 31; + public override float MlSpeed => 3.50f; - [Constructible] - public BattleAxe() : base( 0xF47 ) - { - Weight = 4.0; - Layer = Layer.TwoHanded; - } + public override int OldStrengthReq => 40; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 38; + public override int OldSpeed => 30; - public BattleAxe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/DoubleAxe.cs b/Scripts/Items/Weapons/Axes/DoubleAxe.cs index d8752dafb..794bacc3f 100644 --- a/Scripts/Items/Weapons/Axes/DoubleAxe.cs +++ b/Scripts/Items/Weapons/Axes/DoubleAxe.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xf4b, 0xf4c )] - public class DoubleAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.WhirlwindAttack; + [Flippable(0xf4b, 0xf4c)] + public class DoubleAxe : BaseAxe + { + [Constructible] + public DoubleAxe() : base(0xF4B) + { + Weight = 8.0; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 33; - public override float MlSpeed => 3.25f; + public DoubleAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 45; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 35; - public override int OldSpeed => 37; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.WhirlwindAttack; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 33; + public override float MlSpeed => 3.25f; - [Constructible] - public DoubleAxe() : base( 0xF4B ) - { - Weight = 8.0; - } + public override int OldStrengthReq => 45; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 35; + public override int OldSpeed => 37; - public DoubleAxe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/ExecutionersAxe.cs b/Scripts/Items/Weapons/Axes/ExecutionersAxe.cs index abc30b790..1d63c0515 100644 --- a/Scripts/Items/Weapons/Axes/ExecutionersAxe.cs +++ b/Scripts/Items/Weapons/Axes/ExecutionersAxe.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xf45, 0xf46 )] - public class ExecutionersAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0xf45, 0xf46)] + public class ExecutionersAxe : BaseAxe + { + [Constructible] + public ExecutionersAxe() : base(0xF45) + { + Weight = 8.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 33; - public override float MlSpeed => 3.25f; + public ExecutionersAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 33; - public override int OldSpeed => 37; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 33; + public override float MlSpeed => 3.25f; - [Constructible] - public ExecutionersAxe() : base( 0xF45 ) - { - Weight = 8.0; - } + public override int OldStrengthReq => 35; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 33; + public override int OldSpeed => 37; - public ExecutionersAxe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/GuardianAxe.cs b/Scripts/Items/Weapons/Axes/GuardianAxe.cs index 3b3bb73b6..2dbaac0ce 100644 --- a/Scripts/Items/Weapons/Axes/GuardianAxe.cs +++ b/Scripts/Items/Weapons/Axes/GuardianAxe.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class GuardianAxe : OrnateAxe - { - public override int LabelNumber => 1073545; // guardian axe + public class GuardianAxe : OrnateAxe + { + [Constructible] + public GuardianAxe() + { + Attributes.BonusHits = 4; + Attributes.RegenHits = 1; + } - [Constructible] - public GuardianAxe() - { - Attributes.BonusHits = 4; - Attributes.RegenHits = 1; - } + public GuardianAxe(Serial serial) : base(serial) + { + } - public GuardianAxe( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073545; // guardian axe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/Hatchet.cs b/Scripts/Items/Weapons/Axes/Hatchet.cs index 9d1d96470..e88d88a91 100644 --- a/Scripts/Items/Weapons/Axes/Hatchet.cs +++ b/Scripts/Items/Weapons/Axes/Hatchet.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xF43, 0xF44 )] - public class Hatchet : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Flippable(0xF43, 0xF44)] + public class Hatchet : BaseAxe + { + [Constructible] + public Hatchet() : base(0xF43) + { + Weight = 4.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 41; - public override float MlSpeed => 2.75f; + public Hatchet(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 17; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 41; + public override float MlSpeed => 2.75f; - [Constructible] - public Hatchet() : base( 0xF43 ) - { - Weight = 4.0; - } + public override int OldStrengthReq => 15; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 17; + public override int OldSpeed => 40; - public Hatchet( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/HeavyOrnateAxe.cs b/Scripts/Items/Weapons/Axes/HeavyOrnateAxe.cs index 808a0dffe..258a10915 100644 --- a/Scripts/Items/Weapons/Axes/HeavyOrnateAxe.cs +++ b/Scripts/Items/Weapons/Axes/HeavyOrnateAxe.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class HeavyOrnateAxe : OrnateAxe - { - public override int LabelNumber => 1073548; // heavy ornate axe + public class HeavyOrnateAxe : OrnateAxe + { + [Constructible] + public HeavyOrnateAxe() + { + Attributes.WeaponDamage = 8; + } - [Constructible] - public HeavyOrnateAxe() - { - Attributes.WeaponDamage = 8; - } + public HeavyOrnateAxe(Serial serial) : base(serial) + { + } - public HeavyOrnateAxe( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073548; // heavy ornate axe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/LargeBattleAxe.cs b/Scripts/Items/Weapons/Axes/LargeBattleAxe.cs index c9456d163..372f83e53 100644 --- a/Scripts/Items/Weapons/Axes/LargeBattleAxe.cs +++ b/Scripts/Items/Weapons/Axes/LargeBattleAxe.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x13FB, 0x13FA )] - public class LargeBattleAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.BleedAttack; + [Flippable(0x13FB, 0x13FA)] + public class LargeBattleAxe : BaseAxe + { + [Constructible] + public LargeBattleAxe() : base(0x13FB) + { + Weight = 6.0; + } - public override int AosStrengthReq => 80; - public override int AosMinDamage => 16; - public override int AosMaxDamage => 17; - public override int AosSpeed => 29; - public override float MlSpeed => 3.75f; + public LargeBattleAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 38; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.BleedAttack; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 80; + public override int AosMinDamage => 16; + public override int AosMaxDamage => 17; + public override int AosSpeed => 29; + public override float MlSpeed => 3.75f; - [Constructible] - public LargeBattleAxe() : base( 0x13FB ) - { - Weight = 6.0; - } + public override int OldStrengthReq => 40; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 38; + public override int OldSpeed => 30; - public LargeBattleAxe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/Pickaxe.cs b/Scripts/Items/Weapons/Axes/Pickaxe.cs index 8d8b0c23e..a9db334c0 100644 --- a/Scripts/Items/Weapons/Axes/Pickaxe.cs +++ b/Scripts/Items/Weapons/Axes/Pickaxe.cs @@ -2,55 +2,55 @@ using Server.Engines.Harvest; namespace Server.Items { - [FlippableAttribute( 0xE86, 0xE85 )] - public class Pickaxe : BaseAxe, IUsesRemaining - { - public override HarvestSystem HarvestSystem => Mining.System; + [Flippable(0xE86, 0xE85)] + public class Pickaxe : BaseAxe, IUsesRemaining + { + [Constructible] + public Pickaxe() : base(0xE86) + { + Weight = 11.0; + UsesRemaining = 50; + ShowUsesRemaining = true; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + public Pickaxe(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 35; - public override float MlSpeed => 3.00f; + public override HarvestSystem HarvestSystem => Mining.System; - public override int OldStrengthReq => 25; - public override int OldMinDamage => 1; - public override int OldMaxDamage => 15; - public override int OldSpeed => 35; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 60; + public override int AosStrengthReq => 50; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 35; + public override float MlSpeed => 3.00f; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; + public override int OldStrengthReq => 25; + public override int OldMinDamage => 1; + public override int OldMaxDamage => 15; + public override int OldSpeed => 35; - [Constructible] - public Pickaxe() : base( 0xE86 ) - { - Weight = 11.0; - UsesRemaining = 50; - ShowUsesRemaining = true; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 60; - public Pickaxe( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - ShowUsesRemaining = true; - } - } -} + int version = reader.ReadInt(); + ShowUsesRemaining = true; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/SingingAxe.cs b/Scripts/Items/Weapons/Axes/SingingAxe.cs index 73a0c6bc8..eb0e1a05b 100644 --- a/Scripts/Items/Weapons/Axes/SingingAxe.cs +++ b/Scripts/Items/Weapons/Axes/SingingAxe.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SingingAxe : OrnateAxe - { - public override int LabelNumber => 1073546; // singing axe + public class SingingAxe : OrnateAxe + { + [Constructible] + public SingingAxe() + { + SkillBonuses.SetValues(0, SkillName.Musicianship, 5); + } - [Constructible] - public SingingAxe() - { - SkillBonuses.SetValues( 0, SkillName.Musicianship, 5 ); - } + public SingingAxe(Serial serial) : base(serial) + { + } - public SingingAxe( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073546; // singing axe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/ThunderingAxe.cs b/Scripts/Items/Weapons/Axes/ThunderingAxe.cs index d10594a92..45acbb1c8 100644 --- a/Scripts/Items/Weapons/Axes/ThunderingAxe.cs +++ b/Scripts/Items/Weapons/Axes/ThunderingAxe.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class ThunderingAxe : OrnateAxe - { - public override int LabelNumber => 1073547; // thundering axe + public class ThunderingAxe : OrnateAxe + { + [Constructible] + public ThunderingAxe() + { + WeaponAttributes.HitLightning = 10; + } - [Constructible] - public ThunderingAxe() - { - WeaponAttributes.HitLightning = 10; - } + public ThunderingAxe(Serial serial) : base(serial) + { + } - public ThunderingAxe( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073547; // thundering axe - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/TwoHandedAxe.cs b/Scripts/Items/Weapons/Axes/TwoHandedAxe.cs index 2345874f4..ae901f270 100644 --- a/Scripts/Items/Weapons/Axes/TwoHandedAxe.cs +++ b/Scripts/Items/Weapons/Axes/TwoHandedAxe.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x1443, 0x1442 )] - public class TwoHandedAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; + [Flippable(0x1443, 0x1442)] + public class TwoHandedAxe : BaseAxe + { + [Constructible] + public TwoHandedAxe() : base(0x1443) + { + Weight = 8.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 16; - public override int AosMaxDamage => 17; - public override int AosSpeed => 31; - public override float MlSpeed => 3.50f; + public TwoHandedAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 39; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 90; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 16; + public override int AosMaxDamage => 17; + public override int AosSpeed => 31; + public override float MlSpeed => 3.50f; - [Constructible] - public TwoHandedAxe() : base( 0x1443 ) - { - Weight = 8.0; - } + public override int OldStrengthReq => 35; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 39; + public override int OldSpeed => 30; - public TwoHandedAxe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 90; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Axes/WarAxe.cs b/Scripts/Items/Weapons/Axes/WarAxe.cs index 41f36a22e..fb73c5726 100644 --- a/Scripts/Items/Weapons/Axes/WarAxe.cs +++ b/Scripts/Items/Weapons/Axes/WarAxe.cs @@ -2,57 +2,57 @@ using Server.Engines.Harvest; namespace Server.Items { - [FlippableAttribute( 0x13B0, 0x13AF )] - public class WarAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.BleedAttack; + [Flippable(0x13B0, 0x13AF)] + public class WarAxe : BaseAxe + { + [Constructible] + public WarAxe() : base(0x13B0) + { + Weight = 8.0; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 15; - public override int AosSpeed => 33; - public override float MlSpeed => 3.25f; + public WarAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 27; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.BleedAttack; - public override int DefHitSound => 0x233; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 15; + public override int AosSpeed => 33; + public override float MlSpeed => 3.25f; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int OldStrengthReq => 35; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 27; + public override int OldSpeed => 40; - public override SkillName DefSkill => SkillName.Macing; - public override WeaponType DefType => WeaponType.Bashing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Bash1H; + public override int DefHitSound => 0x233; + public override int DefMissSound => 0x239; - public override HarvestSystem HarvestSystem => null; + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - [Constructible] - public WarAxe() : base( 0x13B0 ) - { - Weight = 8.0; - } + public override SkillName DefSkill => SkillName.Macing; + public override WeaponType DefType => WeaponType.Bashing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Bash1H; - public WarAxe( Serial serial ) : base( serial ) - { - } + public override HarvestSystem HarvestSystem => null; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/BaseMeleeWeapon.cs b/Scripts/Items/Weapons/BaseMeleeWeapon.cs index f5894537a..75912b33e 100644 --- a/Scripts/Items/Weapons/BaseMeleeWeapon.cs +++ b/Scripts/Items/Weapons/BaseMeleeWeapon.cs @@ -2,63 +2,63 @@ using Server.Spells.Spellweaving; namespace Server.Items { - public abstract class BaseMeleeWeapon : BaseWeapon - { - public BaseMeleeWeapon( int itemID ) : base( itemID ) - { - } + public abstract class BaseMeleeWeapon : BaseWeapon + { + public BaseMeleeWeapon(int itemID) : base(itemID) + { + } - public BaseMeleeWeapon( Serial serial ) : base( serial ) - { - } + public BaseMeleeWeapon(Serial serial) : base(serial) + { + } - public override int AbsorbDamage( Mobile attacker, Mobile defender, int damage ) - { - damage = base.AbsorbDamage( attacker, defender, damage ); + public override int AbsorbDamage(Mobile attacker, Mobile defender, int damage) + { + damage = base.AbsorbDamage(attacker, defender, damage); - AttuneWeaponSpell.TryAbsorb( defender, ref damage ); + AttuneWeaponSpell.TryAbsorb(defender, ref damage); - if ( Core.AOS ) - return damage; + if (Core.AOS) + return damage; - int absorb = defender.MeleeDamageAbsorb; + int absorb = defender.MeleeDamageAbsorb; - if ( absorb > 0 ) - { - if ( absorb > damage ) - { - int react = damage / 5; + if (absorb > 0) + { + if (absorb > damage) + { + int react = damage / 5; - if ( react <= 0 ) - react = 1; + if (react <= 0) + react = 1; - defender.MeleeDamageAbsorb -= damage; - damage = 0; + defender.MeleeDamageAbsorb -= damage; + damage = 0; - attacker.Damage( react, defender ); + attacker.Damage(react, defender); - attacker.PlaySound( 0x1F1 ); - attacker.FixedEffect( 0x374A, 10, 16 ); - } - else - { - defender.MeleeDamageAbsorb = 0; - defender.SendLocalizedMessage( 1005556 ); // Your reactive armor spell has been nullified. - DefensiveSpell.Nullify( defender ); - } - } + attacker.PlaySound(0x1F1); + attacker.FixedEffect(0x374A, 10, 16); + } + else + { + defender.MeleeDamageAbsorb = 0; + defender.SendLocalizedMessage(1005556); // Your reactive armor spell has been nullified. + DefensiveSpell.Nullify(defender); + } + } - return damage; - } + return damage; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/BaseWeapon.cs b/Scripts/Items/Weapons/BaseWeapon.cs index 06e4da34b..2c4db1d55 100644 --- a/Scripts/Items/Weapons/BaseWeapon.cs +++ b/Scripts/Items/Weapons/BaseWeapon.cs @@ -1,3476 +1,3689 @@ using System; -using Server.Network; -using Server.Mobiles; -using Server.Spells; -using Server.Spells.Necromancy; -using Server.Spells.Bushido; -using Server.Spells.Ninjitsu; -using Server.Factions; -using Server.Engines.Craft; using System.Collections.Generic; +using Server.Engines.Craft; +using Server.Ethics; +using Server.Factions; +using Server.Mobiles; +using Server.Network; +using Server.SkillHandlers; +using Server.Spells; +using Server.Spells.Bushido; +using Server.Spells.Chivalry; +using Server.Spells.Necromancy; +using Server.Spells.Ninjitsu; +using Server.Spells.Sixth; using Server.Spells.Spellweaving; namespace Server.Items { - public interface ISlayer - { - SlayerName Slayer { get; set; } - SlayerName Slayer2 { get; set; } - } - - public abstract class BaseWeapon : Item, IWeapon, IFactionItem, ICraftable, ISlayer, IDurability - { - private string m_EngravedText; - - [CommandProperty( AccessLevel.GameMaster )] - public string EngravedText - { - get => m_EngravedText; - set{ m_EngravedText = value; InvalidateProperties(); } - } - - #region Factions - private FactionItem m_FactionState; - - public FactionItem FactionItemState - { - get => m_FactionState; - set - { - m_FactionState = value; - - if ( m_FactionState == null ) - Hue = CraftResources.GetHue( Resource ); - - LootType = ( m_FactionState == null ? LootType.Regular : LootType.Blessed ); - } - } - #endregion - - /* Weapon internals work differently now (Mar 13 2003) - * - * The attributes defined below default to -1. - * If the value is -1, the corresponding virtual 'Aos/Old' property is used. - * If not, the attribute value itself is used. Here's the list: - * - MinDamage - * - MaxDamage - * - Speed - * - HitSound - * - MissSound - * - StrRequirement, DexRequirement, IntRequirement - * - WeaponType - * - WeaponAnimation - * - MaxRange - */ - - #region Var declarations - - // Instance values. These values are unique to each weapon. - private WeaponDamageLevel m_DamageLevel; - private WeaponAccuracyLevel m_AccuracyLevel; - private WeaponDurabilityLevel m_DurabilityLevel; - private WeaponQuality m_Quality; - private Mobile m_Crafter; - private Poison m_Poison; - private int m_PoisonCharges; - private bool m_Identified; - private int m_Hits; - private int m_MaxHits; - private SlayerName m_Slayer; - private SlayerName m_Slayer2; - private SkillMod m_SkillMod, m_MageMod; - private CraftResource m_Resource; - - private AosAttributes m_AosAttributes; - private AosWeaponAttributes m_AosWeaponAttributes; - private AosSkillBonuses m_AosSkillBonuses; - private AosElementAttributes m_AosElementDamages; - - // Overridable values. These values are provided to override the defaults which get defined in the individual weapon scripts. - private int m_StrReq, m_DexReq, m_IntReq; - private int m_MinDamage, m_MaxDamage; - private int m_HitSound, m_MissSound; - private float m_Speed; - private int m_MaxRange; - private SkillName m_Skill; - private WeaponType m_Type; - private WeaponAnimation m_Animation; - #endregion - - #region Virtual Properties - public virtual WeaponAbility PrimaryAbility => null; - public virtual WeaponAbility SecondaryAbility => null; - - public virtual int DefMaxRange => 1; - public virtual int DefHitSound => 0; - public virtual int DefMissSound => 0; - public virtual SkillName DefSkill => SkillName.Swords; - public virtual WeaponType DefType => WeaponType.Slashing; - public virtual WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; - - public virtual int AosStrengthReq => 0; - public virtual int AosDexterityReq => 0; - public virtual int AosIntelligenceReq => 0; - public virtual int AosMinDamage => 0; - public virtual int AosMaxDamage => 0; - public virtual int AosSpeed => 0; - public virtual float MlSpeed => 0.0f; - public virtual int AosMaxRange => DefMaxRange; - public virtual int AosHitSound => DefHitSound; - public virtual int AosMissSound => DefMissSound; - public virtual SkillName AosSkill => DefSkill; - public virtual WeaponType AosType => DefType; - public virtual WeaponAnimation AosAnimation => DefAnimation; - - public virtual int OldStrengthReq => 0; - public virtual int OldDexterityReq => 0; - public virtual int OldIntelligenceReq => 0; - public virtual int OldMinDamage => 0; - public virtual int OldMaxDamage => 0; - public virtual int OldSpeed => 0; - public virtual int OldMaxRange => DefMaxRange; - public virtual int OldHitSound => DefHitSound; - public virtual int OldMissSound => DefMissSound; - public virtual SkillName OldSkill => DefSkill; - public virtual WeaponType OldType => DefType; - public virtual WeaponAnimation OldAnimation => DefAnimation; - - public virtual int InitMinHits => 0; - public virtual int InitMaxHits => 0; - - public virtual bool CanFortify => true; - - public override int PhysicalResistance => m_AosWeaponAttributes.ResistPhysicalBonus; - public override int FireResistance => m_AosWeaponAttributes.ResistFireBonus; - public override int ColdResistance => m_AosWeaponAttributes.ResistColdBonus; - public override int PoisonResistance => m_AosWeaponAttributes.ResistPoisonBonus; - public override int EnergyResistance => m_AosWeaponAttributes.ResistEnergyBonus; - - public virtual SkillName AccuracySkill => SkillName.Tactics; - #endregion - - #region Getters & Setters - [CommandProperty( AccessLevel.GameMaster )] - public AosAttributes Attributes - { - get => m_AosAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosWeaponAttributes WeaponAttributes - { - get => m_AosWeaponAttributes; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosSkillBonuses SkillBonuses - { - get => m_AosSkillBonuses; - set{} - } - - [CommandProperty( AccessLevel.GameMaster )] - public AosElementAttributes AosElementDamages - { - get => m_AosElementDamages; - set { } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Cursed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Consecrated { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Identified - { - get => m_Identified; - set{ m_Identified = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitPoints - { - get => m_Hits; - set - { - if ( m_Hits == value ) - return; - - if ( value > m_MaxHits ) - value = m_MaxHits; - - m_Hits = value; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxHitPoints - { - get => m_MaxHits; - set{ m_MaxHits = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonCharges - { - get => m_PoisonCharges; - set{ m_PoisonCharges = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison - { - get => m_Poison; - set{ m_Poison = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public WeaponQuality Quality - { - get => m_Quality; - set{ UnscaleDurability(); m_Quality = value; ScaleDurability(); InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Crafter - { - get => m_Crafter; - set{ m_Crafter = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public SlayerName Slayer - { - get => m_Slayer; - set{ m_Slayer = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public SlayerName Slayer2 - { - get => m_Slayer2; - set { m_Slayer2 = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource Resource - { - get => m_Resource; - set{ UnscaleDurability(); m_Resource = value; Hue = CraftResources.GetHue( m_Resource ); InvalidateProperties(); ScaleDurability(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public WeaponDamageLevel DamageLevel - { - get => m_DamageLevel; - set{ m_DamageLevel = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public WeaponDurabilityLevel DurabilityLevel - { - get => m_DurabilityLevel; - set{ UnscaleDurability(); m_DurabilityLevel = value; InvalidateProperties(); ScaleDurability(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool PlayerConstructed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxRange - { - get => ( m_MaxRange == -1 ? Core.AOS ? AosMaxRange : OldMaxRange : m_MaxRange ); - set{ m_MaxRange = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public WeaponAnimation Animation - { - get => ( m_Animation == (WeaponAnimation)(-1) ? Core.AOS ? AosAnimation : OldAnimation : m_Animation ); - set => m_Animation = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public WeaponType Type - { - get => ( m_Type == (WeaponType)(-1) ? Core.AOS ? AosType : OldType : m_Type ); - set => m_Type = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill - { - get => ( m_Skill == (SkillName)(-1) ? Core.AOS ? AosSkill : OldSkill : m_Skill ); - set{ m_Skill = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitSound - { - get => ( m_HitSound == -1 ? Core.AOS ? AosHitSound : OldHitSound : m_HitSound ); - set => m_HitSound = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MissSound - { - get => ( m_MissSound == -1 ? Core.AOS ? AosMissSound : OldMissSound : m_MissSound ); - set => m_MissSound = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MinDamage - { - get => ( m_MinDamage == -1 ? Core.AOS ? AosMinDamage : OldMinDamage : m_MinDamage ); - set{ m_MinDamage = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxDamage - { - get => ( m_MaxDamage == -1 ? Core.AOS ? AosMaxDamage : OldMaxDamage : m_MaxDamage ); - set{ m_MaxDamage = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public float Speed - { - get - { - if ( m_Speed != -1 ) - return m_Speed; - - if ( Core.ML ) - return MlSpeed; - if ( Core.AOS ) - return AosSpeed; - - return OldSpeed; - } - set{ m_Speed = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int StrRequirement - { - get => ( m_StrReq == -1 ? Core.AOS ? AosStrengthReq : OldStrengthReq : m_StrReq ); - set{ m_StrReq = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DexRequirement - { - get => ( m_DexReq == -1 ? Core.AOS ? AosDexterityReq : OldDexterityReq : m_DexReq ); - set => m_DexReq = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int IntRequirement - { - get => ( m_IntReq == -1 ? Core.AOS ? AosIntelligenceReq : OldIntelligenceReq : m_IntReq ); - set => m_IntReq = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public WeaponAccuracyLevel AccuracyLevel - { - get => m_AccuracyLevel; - set - { - if ( m_AccuracyLevel != value ) - { - m_AccuracyLevel = value; - - if ( UseSkillMod ) - { - if ( m_AccuracyLevel == WeaponAccuracyLevel.Regular ) - { - m_SkillMod?.Remove(); - - m_SkillMod = null; - } - else if ( m_SkillMod == null && Parent is Mobile mobile ) - { - m_SkillMod = new DefaultSkillMod( AccuracySkill, true, (int)m_AccuracyLevel * 5 ); - mobile.AddSkillMod( m_SkillMod ); - } - else if ( m_SkillMod != null ) - { - m_SkillMod.Value = (int)m_AccuracyLevel * 5; - } - } - - InvalidateProperties(); - } - } - } - - #endregion - - public override void OnAfterDuped( Item newItem ) - { - if ( !(newItem is BaseWeapon weap) ) - return; - - weap.m_AosAttributes = new AosAttributes( newItem, m_AosAttributes ); - weap.m_AosElementDamages = new AosElementAttributes( newItem, m_AosElementDamages ); - weap.m_AosSkillBonuses = new AosSkillBonuses( newItem, m_AosSkillBonuses ); - weap.m_AosWeaponAttributes = new AosWeaponAttributes( newItem, m_AosWeaponAttributes ); - } - - public virtual void UnscaleDurability() - { - int scale = 100 + GetDurabilityBonus(); - - m_Hits = ((m_Hits * 100) + (scale - 1)) / scale; - m_MaxHits = ((m_MaxHits * 100) + (scale - 1)) / scale; - InvalidateProperties(); - } - - public virtual void ScaleDurability() - { - int scale = 100 + GetDurabilityBonus(); - - m_Hits = ((m_Hits * scale) + 99) / 100; - m_MaxHits = ((m_MaxHits * scale) + 99) / 100; - InvalidateProperties(); - } - - public int GetDurabilityBonus() - { - int bonus = 0; - - if ( m_Quality == WeaponQuality.Exceptional ) - bonus += 20; - - switch ( m_DurabilityLevel ) - { - case WeaponDurabilityLevel.Durable: bonus += 20; break; - case WeaponDurabilityLevel.Substantial: bonus += 50; break; - case WeaponDurabilityLevel.Massive: bonus += 70; break; - case WeaponDurabilityLevel.Fortified: bonus += 100; break; - case WeaponDurabilityLevel.Indestructible: bonus += 120; break; - } - - if ( Core.AOS ) - { - bonus += m_AosWeaponAttributes.DurabilityBonus; - - CraftResourceInfo resInfo = CraftResources.GetInfo( m_Resource ); - CraftAttributeInfo attrInfo = null; - - if ( resInfo != null ) - attrInfo = resInfo.AttributeInfo; - - if ( attrInfo != null ) - bonus += attrInfo.WeaponDurability; - } - - return bonus; - } - - public int GetLowerStatReq() - { - if ( !Core.AOS ) - return 0; - - int v = m_AosWeaponAttributes.LowerStatReq; - - CraftAttributeInfo attrInfo = CraftResources.GetInfo( m_Resource )?.AttributeInfo; - - if ( attrInfo != null ) - v += attrInfo.WeaponLowerRequirements; - - if ( v > 100 ) - v = 100; - - return v; - } - - public static void BlockEquip( Mobile m, TimeSpan duration ) - { - if ( m.BeginAction( typeof( BaseWeapon ) ) ) - new ResetEquipTimer( m, duration ).Start(); - } - - private class ResetEquipTimer : Timer - { - private Mobile m_Mobile; - - public ResetEquipTimer( Mobile m, TimeSpan duration ) : base( duration ) - { - m_Mobile = m; - } - - protected override void OnTick() - { - m_Mobile.EndAction( typeof( BaseWeapon ) ); - } - } - - public override bool CheckConflictingLayer( Mobile m, Item item, Layer layer ) - { - if ( base.CheckConflictingLayer( m, item, layer ) ) - return true; - - if ( Layer == Layer.TwoHanded && layer == Layer.OneHanded ) - { - m.SendLocalizedMessage( 500214 ); // You already have something in both hands. - return true; - } - - if ( Layer == Layer.OneHanded && layer == Layer.TwoHanded && !(item is BaseShield) && !(item is BaseEquipableLight) ) - { - m.SendLocalizedMessage( 500215 ); // You can only wield one weapon at a time. - return true; - } - - return false; - } - - public override bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - if ( !Ethics.Ethic.CheckTrade( from, to, newOwner, this ) ) - return false; - - return base.AllowSecureTrade( from, to, newOwner, accepted ); - } - - public virtual Race RequiredRace => null; //On OSI, there are no weapons with race requirements, this is for custom stuff - - public override bool CanEquip( Mobile from ) - { - if ( !Ethics.Ethic.CheckEquip( from, this ) ) - return false; - - if ( RequiredRace != null && from.Race != RequiredRace ) - { - if ( RequiredRace == Race.Elf ) - from.SendLocalizedMessage( 1072203 ); // Only Elves may use this. - else - from.SendMessage( "Only {0} may use this.", RequiredRace.PluralName ); - - return false; - } - if ( from.Dex < DexRequirement ) - { - from.SendMessage( "You are not nimble enough to equip that." ); - return false; - } - if ( from.Str < AOS.Scale( StrRequirement, 100 - GetLowerStatReq() ) ) - { - from.SendLocalizedMessage( 500213 ); // You are not strong enough to equip that. - return false; - } - if ( from.Int < IntRequirement ) - { - from.SendMessage( "You are not smart enough to equip that." ); - return false; - } - if ( !from.CanBeginAction( typeof( BaseWeapon ) ) ) - { - return false; - } - - return base.CanEquip( from ); - } - - public virtual bool UseSkillMod => !Core.AOS; - - public override bool OnEquip( Mobile from ) - { - int strBonus = m_AosAttributes.BonusStr; - int dexBonus = m_AosAttributes.BonusDex; - int intBonus = m_AosAttributes.BonusInt; - - if ( (strBonus != 0 || dexBonus != 0 || intBonus != 0) ) - { - Mobile m = from; - - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - m.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - from.NextCombatTime = Core.TickCount + (int)GetDelay( from ).TotalMilliseconds; - - if ( UseSkillMod && m_AccuracyLevel != WeaponAccuracyLevel.Regular ) - { - m_SkillMod?.Remove(); - - m_SkillMod = new DefaultSkillMod( AccuracySkill, true, (int)m_AccuracyLevel * 5 ); - from.AddSkillMod( m_SkillMod ); - } - - if ( Core.AOS && m_AosWeaponAttributes.MageWeapon != 0 && m_AosWeaponAttributes.MageWeapon != 30 ) - { - m_MageMod?.Remove(); - - m_MageMod = new DefaultSkillMod( SkillName.Magery, true, -30 + m_AosWeaponAttributes.MageWeapon ); - from.AddSkillMod( m_MageMod ); - } - - return true; - } - - public override void OnAdded(IEntity parent) - { - base.OnAdded( parent ); - - if ( parent is Mobile from ) - { - if ( Core.AOS ) - m_AosSkillBonuses.AddTo( from ); - - from.CheckStatTimers(); - from.Delta( MobileDelta.WeaponDamage ); - } - } - - public override void OnRemoved(IEntity parent) - { - if ( parent is Mobile m ) - { - BaseWeapon weapon = m.Weapon as BaseWeapon; - - string modName = Serial.ToString(); - - m.RemoveStatMod( modName + "Str" ); - m.RemoveStatMod( modName + "Dex" ); - m.RemoveStatMod( modName + "Int" ); - - if ( weapon != null ) - m.NextCombatTime = Core.TickCount + (int)weapon.GetDelay(m).TotalMilliseconds; - - if ( UseSkillMod && m_SkillMod != null ) - { - m_SkillMod.Remove(); - m_SkillMod = null; - } - - if ( m_MageMod != null ) - { - m_MageMod.Remove(); - m_MageMod = null; - } + public interface ISlayer + { + SlayerName Slayer{ get; set; } + SlayerName Slayer2{ get; set; } + } + + public abstract class BaseWeapon : Item, IWeapon, IFactionItem, ICraftable, ISlayer, IDurability + { + private string m_EngravedText; + + public BaseWeapon(int itemID) : base(itemID) + { + Layer = (Layer)ItemData.Quality; + + m_Quality = WeaponQuality.Regular; + m_StrReq = -1; + m_DexReq = -1; + m_IntReq = -1; + m_MinDamage = -1; + m_MaxDamage = -1; + m_HitSound = -1; + m_MissSound = -1; + m_Speed = -1; + m_MaxRange = -1; + m_Skill = (SkillName)(-1); + m_Type = (WeaponType)(-1); + m_Animation = (WeaponAnimation)(-1); + + m_Hits = m_MaxHits = Utility.RandomMinMax(InitMinHits, InitMaxHits); + + m_Resource = CraftResource.Iron; + + m_AosAttributes = new AosAttributes(this); + m_AosWeaponAttributes = new AosWeaponAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + m_AosElementDamages = new AosElementAttributes(this); + } + + public BaseWeapon(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public string EngravedText + { + get => m_EngravedText; + set + { + m_EngravedText = value; + InvalidateProperties(); + } + } + + public virtual Race RequiredRace => + null; //On OSI, there are no weapons with race requirements, this is for custom stuff + + public virtual bool UseSkillMod => !Core.AOS; + + public static bool InDoubleStrike{ get; set; } + + public virtual int VirtualDamageBonus => 0; + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + InvalidateProperties(); + } + } + + public virtual int ArtifactRarity => 0; + + public static BaseWeapon Fists{ get; set; } + + #region ICraftable Members + + public int OnCraft(int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, + CraftItem craftItem, int resHue) + { + Quality = (WeaponQuality)quality; + + if (makersMark) + Crafter = from; + + PlayerConstructed = true; + + Type resourceType = typeRes; + + if (resourceType == null) + resourceType = craftItem.Resources.GetAt(0).ItemType; + + if (Core.AOS) + { + Resource = CraftResources.GetFromType(resourceType); + + CraftContext context = craftSystem.GetContext(from); + + if (context != null && context.DoNotColor) + Hue = 0; + + if (tool is BaseRunicTool runicTool) + runicTool.ApplyAttributesTo(this); + + if (Quality == WeaponQuality.Exceptional) + { + if (Attributes.WeaponDamage > 35) + Attributes.WeaponDamage -= 20; + else + Attributes.WeaponDamage = 15; + + if (Core.ML) + { + Attributes.WeaponDamage += (int)(from.Skills.ArmsLore.Value / 20); + + if (Attributes.WeaponDamage > 50) + Attributes.WeaponDamage = 50; + + from.CheckSkill(SkillName.ArmsLore, 0, 100); + } + } + } + else if (tool is BaseRunicTool runicTool) + { + CraftResource thisResource = CraftResources.GetFromType(resourceType); + + if (thisResource == runicTool.Resource) + { + Resource = thisResource; + + CraftContext context = craftSystem.GetContext(from); + + if (context != null && context.DoNotColor) + Hue = 0; + + switch (thisResource) + { + case CraftResource.DullCopper: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Durable; + AccuracyLevel = WeaponAccuracyLevel.Accurate; + break; + } + case CraftResource.ShadowIron: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Durable; + DamageLevel = WeaponDamageLevel.Ruin; + break; + } + case CraftResource.Copper: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Fortified; + DamageLevel = WeaponDamageLevel.Ruin; + AccuracyLevel = WeaponAccuracyLevel.Surpassingly; + break; + } + case CraftResource.Bronze: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Fortified; + DamageLevel = WeaponDamageLevel.Might; + AccuracyLevel = WeaponAccuracyLevel.Surpassingly; + break; + } + case CraftResource.Gold: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Indestructible; + DamageLevel = WeaponDamageLevel.Force; + AccuracyLevel = WeaponAccuracyLevel.Eminently; + break; + } + case CraftResource.Agapite: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Indestructible; + DamageLevel = WeaponDamageLevel.Power; + AccuracyLevel = WeaponAccuracyLevel.Eminently; + break; + } + case CraftResource.Verite: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Indestructible; + DamageLevel = WeaponDamageLevel.Power; + AccuracyLevel = WeaponAccuracyLevel.Exceedingly; + break; + } + case CraftResource.Valorite: + { + Identified = true; + DurabilityLevel = WeaponDurabilityLevel.Indestructible; + DamageLevel = WeaponDamageLevel.Vanq; + AccuracyLevel = WeaponAccuracyLevel.Supremely; + break; + } + } + } + } + + return quality; + } + + #endregion + + public virtual void UnscaleDurability() + { + int scale = 100 + GetDurabilityBonus(); + + m_Hits = (m_Hits * 100 + (scale - 1)) / scale; + m_MaxHits = (m_MaxHits * 100 + (scale - 1)) / scale; + InvalidateProperties(); + } + + public virtual void ScaleDurability() + { + int scale = 100 + GetDurabilityBonus(); + + m_Hits = (m_Hits * scale + 99) / 100; + m_MaxHits = (m_MaxHits * scale + 99) / 100; + InvalidateProperties(); + } + + public virtual void OnBeforeSwing(Mobile attacker, Mobile defender) + { + WeaponAbility a = WeaponAbility.GetCurrentAbility(attacker); + + if (a != null && !a.OnBeforeSwing(attacker, defender)) + WeaponAbility.ClearCurrentAbility(attacker); + + SpecialMove move = SpecialMove.GetCurrentMove(attacker); + + if (move != null && !move.OnBeforeSwing(attacker, defender)) + SpecialMove.ClearCurrentMove(attacker); + } + + public virtual TimeSpan OnSwing(Mobile attacker, Mobile defender) + { + return OnSwing(attacker, defender, 1.0); + } + + public virtual void GetStatusDamage(Mobile from, out int min, out int max) + { + GetBaseDamageRange(from, out int baseMin, out int baseMax); + + if (Core.AOS) + { + min = Math.Max((int)ScaleDamageAOS(from, baseMin, false), 1); + max = Math.Max((int)ScaleDamageAOS(from, baseMax, false), 1); + } + else + { + min = Math.Max((int)ScaleDamageOld(from, baseMin, false), 1); + max = Math.Max((int)ScaleDamageOld(from, baseMax, false), 1); + } + } + + public override void OnAfterDuped(Item newItem) + { + if (!(newItem is BaseWeapon weap)) + return; + + weap.m_AosAttributes = new AosAttributes(newItem, m_AosAttributes); + weap.m_AosElementDamages = new AosElementAttributes(newItem, m_AosElementDamages); + weap.m_AosSkillBonuses = new AosSkillBonuses(newItem, m_AosSkillBonuses); + weap.m_AosWeaponAttributes = new AosWeaponAttributes(newItem, m_AosWeaponAttributes); + } + + public int GetDurabilityBonus() + { + int bonus = 0; + + if (m_Quality == WeaponQuality.Exceptional) + bonus += 20; + + switch (m_DurabilityLevel) + { + case WeaponDurabilityLevel.Durable: + bonus += 20; + break; + case WeaponDurabilityLevel.Substantial: + bonus += 50; + break; + case WeaponDurabilityLevel.Massive: + bonus += 70; + break; + case WeaponDurabilityLevel.Fortified: + bonus += 100; + break; + case WeaponDurabilityLevel.Indestructible: + bonus += 120; + break; + } + + if (Core.AOS) + { + bonus += m_AosWeaponAttributes.DurabilityBonus; + + CraftResourceInfo resInfo = CraftResources.GetInfo(m_Resource); + CraftAttributeInfo attrInfo = null; + + if (resInfo != null) + attrInfo = resInfo.AttributeInfo; + + if (attrInfo != null) + bonus += attrInfo.WeaponDurability; + } + + return bonus; + } + + public int GetLowerStatReq() + { + if (!Core.AOS) + return 0; + + int v = m_AosWeaponAttributes.LowerStatReq; + + CraftAttributeInfo attrInfo = CraftResources.GetInfo(m_Resource)?.AttributeInfo; + + if (attrInfo != null) + v += attrInfo.WeaponLowerRequirements; + + if (v > 100) + v = 100; + + return v; + } + + public static void BlockEquip(Mobile m, TimeSpan duration) + { + if (m.BeginAction(typeof(BaseWeapon))) + new ResetEquipTimer(m, duration).Start(); + } + + public override bool CheckConflictingLayer(Mobile m, Item item, Layer layer) + { + if (base.CheckConflictingLayer(m, item, layer)) + return true; + + if (Layer == Layer.TwoHanded && layer == Layer.OneHanded) + { + m.SendLocalizedMessage(500214); // You already have something in both hands. + return true; + } + + if (Layer == Layer.OneHanded && layer == Layer.TwoHanded && !(item is BaseShield) && + !(item is BaseEquipableLight)) + { + m.SendLocalizedMessage(500215); // You can only wield one weapon at a time. + return true; + } + + return false; + } + + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (!Ethic.CheckTrade(from, to, newOwner, this)) + return false; + + return base.AllowSecureTrade(from, to, newOwner, accepted); + } + + public override bool CanEquip(Mobile from) + { + if (!Ethic.CheckEquip(from, this)) + return false; + + if (RequiredRace != null && from.Race != RequiredRace) + { + if (RequiredRace == Race.Elf) + from.SendLocalizedMessage(1072203); // Only Elves may use this. + else + from.SendMessage("Only {0} may use this.", RequiredRace.PluralName); + + return false; + } + + if (from.Dex < DexRequirement) + { + from.SendMessage("You are not nimble enough to equip that."); + return false; + } + + if (from.Str < AOS.Scale(StrRequirement, 100 - GetLowerStatReq())) + { + from.SendLocalizedMessage(500213); // You are not strong enough to equip that. + return false; + } - if ( Core.AOS ) - m_AosSkillBonuses.Remove(); + if (from.Int < IntRequirement) + { + from.SendMessage("You are not smart enough to equip that."); + return false; + } - ImmolatingWeaponSpell.StopImmolating( this ); + if (!from.CanBeginAction(typeof(BaseWeapon))) return false; - m.CheckStatTimers(); + return base.CanEquip(from); + } - m.Delta( MobileDelta.WeaponDamage ); - } - } + public override bool OnEquip(Mobile from) + { + int strBonus = m_AosAttributes.BonusStr; + int dexBonus = m_AosAttributes.BonusDex; + int intBonus = m_AosAttributes.BonusInt; - public virtual SkillName GetUsedSkill( Mobile m, bool checkSkillAttrs ) - { - SkillName sk; + if (strBonus != 0 || dexBonus != 0 || intBonus != 0) + { + Mobile m = from; + + string modName = Serial.ToString(); + + if (strBonus != 0) + m.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + m.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + m.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + from.NextCombatTime = Core.TickCount + (int)GetDelay(from).TotalMilliseconds; + + if (UseSkillMod && m_AccuracyLevel != WeaponAccuracyLevel.Regular) + { + m_SkillMod?.Remove(); + + m_SkillMod = new DefaultSkillMod(AccuracySkill, true, (int)m_AccuracyLevel * 5); + from.AddSkillMod(m_SkillMod); + } + + if (Core.AOS && m_AosWeaponAttributes.MageWeapon != 0 && m_AosWeaponAttributes.MageWeapon != 30) + { + m_MageMod?.Remove(); + + m_MageMod = new DefaultSkillMod(SkillName.Magery, true, -30 + m_AosWeaponAttributes.MageWeapon); + from.AddSkillMod(m_MageMod); + } + + return true; + } + + public override void OnAdded(IEntity parent) + { + base.OnAdded(parent); + + if (parent is Mobile from) + { + if (Core.AOS) + m_AosSkillBonuses.AddTo(from); + + from.CheckStatTimers(); + from.Delta(MobileDelta.WeaponDamage); + } + } + + public override void OnRemoved(IEntity parent) + { + if (parent is Mobile m) + { + BaseWeapon weapon = m.Weapon as BaseWeapon; + + string modName = Serial.ToString(); + + m.RemoveStatMod(modName + "Str"); + m.RemoveStatMod(modName + "Dex"); + m.RemoveStatMod(modName + "Int"); + + if (weapon != null) + m.NextCombatTime = Core.TickCount + (int)weapon.GetDelay(m).TotalMilliseconds; + + if (UseSkillMod && m_SkillMod != null) + { + m_SkillMod.Remove(); + m_SkillMod = null; + } + + if (m_MageMod != null) + { + m_MageMod.Remove(); + m_MageMod = null; + } + + if (Core.AOS) + m_AosSkillBonuses.Remove(); - if ( checkSkillAttrs && m_AosWeaponAttributes.UseBestSkill != 0 ) - { - double swrd = m.Skills[SkillName.Swords].Value; - double fenc = m.Skills[SkillName.Fencing].Value; - double mcng = m.Skills[SkillName.Macing].Value; - double val; + ImmolatingWeaponSpell.StopImmolating(this); - sk = SkillName.Swords; - val = swrd; + m.CheckStatTimers(); - if ( fenc > val ){ sk = SkillName.Fencing; val = fenc; } - if ( mcng > val ){ sk = SkillName.Macing; } - } - else if ( m_AosWeaponAttributes.MageWeapon != 0 ) - { - if ( m.Skills[SkillName.Magery].Value > m.Skills[Skill].Value ) - sk = SkillName.Magery; - else - sk = Skill; - } - else - { - sk = Skill; + m.Delta(MobileDelta.WeaponDamage); + } + } - if ( sk != SkillName.Wrestling && !m.Player && !m.Body.IsHuman && m.Skills[SkillName.Wrestling].Value > m.Skills[sk].Value ) - sk = SkillName.Wrestling; - } + public virtual SkillName GetUsedSkill(Mobile m, bool checkSkillAttrs) + { + SkillName sk; - return sk; - } + if (checkSkillAttrs && m_AosWeaponAttributes.UseBestSkill != 0) + { + double swrd = m.Skills[SkillName.Swords].Value; + double fenc = m.Skills[SkillName.Fencing].Value; + double mcng = m.Skills[SkillName.Macing].Value; + double val; - public virtual double GetAttackSkillValue( Mobile attacker, Mobile defender ) - { - return attacker.Skills[GetUsedSkill( attacker, true )].Value; - } + sk = SkillName.Swords; + val = swrd; - public virtual double GetDefendSkillValue( Mobile attacker, Mobile defender ) - { - return defender.Skills[GetUsedSkill( defender, true )].Value; - } + if (fenc > val) + { + sk = SkillName.Fencing; + val = fenc; + } - private static bool CheckAnimal( Mobile m, Type type ) - { - return AnimalForm.UnderTransformation( m, type ); - } + if (mcng > val) sk = SkillName.Macing; + } + else if (m_AosWeaponAttributes.MageWeapon != 0) + { + if (m.Skills[SkillName.Magery].Value > m.Skills[Skill].Value) + sk = SkillName.Magery; + else + sk = Skill; + } + else + { + sk = Skill; - public virtual bool CheckHit( Mobile attacker, Mobile defender ) - { - BaseWeapon atkWeapon = attacker.Weapon as BaseWeapon; - BaseWeapon defWeapon = defender.Weapon as BaseWeapon; + if (sk != SkillName.Wrestling && !m.Player && !m.Body.IsHuman && + m.Skills[SkillName.Wrestling].Value > m.Skills[sk].Value) + sk = SkillName.Wrestling; + } - Skill atkSkill = attacker.Skills[atkWeapon.Skill]; - // Skill defSkill = defender.Skills[defWeapon.Skill]; + return sk; + } - double atkValue = atkWeapon.GetAttackSkillValue( attacker, defender ); - double defValue = defWeapon.GetDefendSkillValue( attacker, defender ); + public virtual double GetAttackSkillValue(Mobile attacker, Mobile defender) + { + return attacker.Skills[GetUsedSkill(attacker, true)].Value; + } - double ourValue, theirValue; + public virtual double GetDefendSkillValue(Mobile attacker, Mobile defender) + { + return defender.Skills[GetUsedSkill(defender, true)].Value; + } - int bonus = GetHitChanceBonus(); + private static bool CheckAnimal(Mobile m, Type type) + { + return AnimalForm.UnderTransformation(m, type); + } - if ( Core.AOS ) - { - if ( atkValue <= -20.0 ) - atkValue = -19.9; + public virtual bool CheckHit(Mobile attacker, Mobile defender) + { + BaseWeapon atkWeapon = attacker.Weapon as BaseWeapon; + BaseWeapon defWeapon = defender.Weapon as BaseWeapon; - if ( defValue <= -20.0 ) - defValue = -19.9; + Skill atkSkill = attacker.Skills[atkWeapon.Skill]; + // Skill defSkill = defender.Skills[defWeapon.Skill]; - bonus += AosAttributes.GetValue( attacker, AosAttribute.AttackChance ); + double atkValue = atkWeapon.GetAttackSkillValue(attacker, defender); + double defValue = defWeapon.GetDefendSkillValue(attacker, defender); - if ( Spells.Chivalry.DivineFurySpell.UnderEffect( attacker ) ) - bonus += 10; // attacker gets 10% bonus when they're under divine fury + double ourValue, theirValue; - if ( CheckAnimal( attacker, typeof( GreyWolf ) ) || CheckAnimal( attacker, typeof( BakeKitsune ) ) ) - bonus += 20; // attacker gets 20% bonus when under Wolf or Bake Kitsune form + int bonus = GetHitChanceBonus(); - if ( HitLower.IsUnderAttackEffect( attacker ) ) - bonus -= 25; // Under Hit Lower Attack effect -> 25% malus + if (Core.AOS) + { + if (atkValue <= -20.0) + atkValue = -19.9; - WeaponAbility ability = WeaponAbility.GetCurrentAbility( attacker ); + if (defValue <= -20.0) + defValue = -19.9; - if ( ability != null ) - bonus += ability.AccuracyBonus; + bonus += AosAttributes.GetValue(attacker, AosAttribute.AttackChance); - SpecialMove move = SpecialMove.GetCurrentMove( attacker ); + if (DivineFurySpell.UnderEffect(attacker)) + bonus += 10; // attacker gets 10% bonus when they're under divine fury - if ( move != null ) - bonus += move.GetAccuracyBonus( attacker ); + if (CheckAnimal(attacker, typeof(GreyWolf)) || CheckAnimal(attacker, typeof(BakeKitsune))) + bonus += 20; // attacker gets 20% bonus when under Wolf or Bake Kitsune form - // Max Hit Chance Increase = 45% - if ( bonus > 45 ) - bonus = 45; + if (HitLower.IsUnderAttackEffect(attacker)) + bonus -= 25; // Under Hit Lower Attack effect -> 25% malus - ourValue = (atkValue + 20.0) * (100 + bonus); + WeaponAbility ability = WeaponAbility.GetCurrentAbility(attacker); - bonus = AosAttributes.GetValue( defender, AosAttribute.DefendChance ); + if (ability != null) + bonus += ability.AccuracyBonus; - if ( Spells.Chivalry.DivineFurySpell.UnderEffect( defender ) ) - bonus -= 20; // defender loses 20% bonus when they're under divine fury + SpecialMove move = SpecialMove.GetCurrentMove(attacker); - if ( HitLower.IsUnderDefenseEffect( defender ) ) - bonus -= 25; // Under Hit Lower Defense effect -> 25% malus + if (move != null) + bonus += move.GetAccuracyBonus(attacker); - int blockBonus = 0; + // Max Hit Chance Increase = 45% + if (bonus > 45) + bonus = 45; - if ( Block.GetBonus( defender, ref blockBonus ) ) - bonus += blockBonus; + ourValue = (atkValue + 20.0) * (100 + bonus); - int surpriseMalus = 0; + bonus = AosAttributes.GetValue(defender, AosAttribute.DefendChance); - if ( SurpriseAttack.GetMalus( defender, ref surpriseMalus ) ) - bonus -= surpriseMalus; + if (DivineFurySpell.UnderEffect(defender)) + bonus -= 20; // defender loses 20% bonus when they're under divine fury - int discordanceEffect = 0; + if (HitLower.IsUnderDefenseEffect(defender)) + bonus -= 25; // Under Hit Lower Defense effect -> 25% malus - // Defender loses -0/-28% if under the effect of Discordance. - if ( SkillHandlers.Discordance.GetEffect( attacker, ref discordanceEffect ) ) - bonus -= discordanceEffect; + int blockBonus = 0; - // Defense Chance Increase = 45% - if ( bonus > 45 ) - bonus = 45; + if (Block.GetBonus(defender, ref blockBonus)) + bonus += blockBonus; - theirValue = (defValue + 20.0) * (100 + bonus); + int surpriseMalus = 0; - bonus = 0; - } - else - { - if ( atkValue <= -50.0 ) - atkValue = -49.9; + if (SurpriseAttack.GetMalus(defender, ref surpriseMalus)) + bonus -= surpriseMalus; - if ( defValue <= -50.0 ) - defValue = -49.9; + int discordanceEffect = 0; - ourValue = (atkValue + 50.0); - theirValue = (defValue + 50.0); - } + // Defender loses -0/-28% if under the effect of Discordance. + if (Discordance.GetEffect(attacker, ref discordanceEffect)) + bonus -= discordanceEffect; - double chance = ourValue / (theirValue * 2.0); + // Defense Chance Increase = 45% + if (bonus > 45) + bonus = 45; - chance *= 1.0 + ((double)bonus / 100); + theirValue = (defValue + 20.0) * (100 + bonus); - if ( Core.AOS && chance < 0.02 ) - chance = 0.02; + bonus = 0; + } + else + { + if (atkValue <= -50.0) + atkValue = -49.9; - return attacker.CheckSkill( atkSkill.SkillName, chance ); - } + if (defValue <= -50.0) + defValue = -49.9; - public virtual TimeSpan GetDelay( Mobile m ) - { - double speed = Speed; + ourValue = atkValue + 50.0; + theirValue = defValue + 50.0; + } - if ( speed == 0 ) - return TimeSpan.FromHours( 1.0 ); + double chance = ourValue / (theirValue * 2.0); - double delayInSeconds; + chance *= 1.0 + (double)bonus / 100; - if ( Core.SE ) - { - /* - * This is likely true for Core.AOS as well... both guides report the same - * formula, and both are wrong. - * The old formula left in for AOS for legacy & because we aren't quite 100% - * Sure that AOS has THIS formula - */ - int bonus = AosAttributes.GetValue( m, AosAttribute.WeaponSpeed ); + if (Core.AOS && chance < 0.02) + chance = 0.02; - if ( Spells.Chivalry.DivineFurySpell.UnderEffect( m ) ) - bonus += 10; + return attacker.CheckSkill(atkSkill.SkillName, chance); + } - // Bonus granted by successful use of Honorable Execution. - bonus += HonorableExecution.GetSwingBonus( m ); + public virtual TimeSpan GetDelay(Mobile m) + { + double speed = Speed; - if ( DualWield.Registry.Contains( m ) ) - bonus += ((DualWield.DualWieldTimer)DualWield.Registry[m]).BonusSwingSpeed; + if (speed == 0) + return TimeSpan.FromHours(1.0); - if ( Feint.Registry.Contains( m ) ) - bonus -= ((Feint.FeintTimer)Feint.Registry[m]).SwingSpeedReduction; + double delayInSeconds; - TransformContext context = TransformationSpellHelper.GetContext( m ); + if (Core.SE) + { + /* + * This is likely true for Core.AOS as well... both guides report the same + * formula, and both are wrong. + * The old formula left in for AOS for legacy & because we aren't quite 100% + * Sure that AOS has THIS formula + */ + int bonus = AosAttributes.GetValue(m, AosAttribute.WeaponSpeed); - if ( context?.Spell is ReaperFormSpell spell ) - bonus += spell.SwingSpeedBonus; + if (DivineFurySpell.UnderEffect(m)) + bonus += 10; - int discordanceEffect = 0; + // Bonus granted by successful use of Honorable Execution. + bonus += HonorableExecution.GetSwingBonus(m); - // Discordance gives a malus of -0/-28% to swing speed. - if ( SkillHandlers.Discordance.GetEffect( m, ref discordanceEffect ) ) - bonus -= discordanceEffect; + if (DualWield.Registry.Contains(m)) + bonus += ((DualWield.DualWieldTimer)DualWield.Registry[m]).BonusSwingSpeed; - if ( EssenceOfWindSpell.IsDebuffed( m ) ) - bonus -= EssenceOfWindSpell.GetSSIMalus( m ); + if (Feint.Registry.Contains(m)) + bonus -= ((Feint.FeintTimer)Feint.Registry[m]).SwingSpeedReduction; - if ( bonus > 60 ) - bonus = 60; + TransformContext context = TransformationSpellHelper.GetContext(m); - double ticks; + if (context?.Spell is ReaperFormSpell spell) + bonus += spell.SwingSpeedBonus; - if ( Core.ML ) - { - int stamTicks = m.Stam / 30; + int discordanceEffect = 0; - ticks = speed * 4; - ticks = Math.Floor( ( ticks - stamTicks ) * ( 100.0 / ( 100 + bonus ) ) ); - } - else - { - speed = Math.Floor( speed * ( bonus + 100.0 ) / 100.0 ); + // Discordance gives a malus of -0/-28% to swing speed. + if (Discordance.GetEffect(m, ref discordanceEffect)) + bonus -= discordanceEffect; - if ( speed <= 0 ) - speed = 1; + if (EssenceOfWindSpell.IsDebuffed(m)) + bonus -= EssenceOfWindSpell.GetSSIMalus(m); - ticks = Math.Floor( ( 80000.0 / ( ( m.Stam + 100 ) * speed ) ) - 2 ); - } + if (bonus > 60) + bonus = 60; - // Swing speed currently capped at one swing every 1.25 seconds (5 ticks). - if ( ticks < 5 ) - ticks = 5; + double ticks; - delayInSeconds = ticks * 0.25; - } - else if ( Core.AOS ) - { - int v = (m.Stam + 100) * (int) speed; + if (Core.ML) + { + int stamTicks = m.Stam / 30; - int bonus = AosAttributes.GetValue( m, AosAttribute.WeaponSpeed ); + ticks = speed * 4; + ticks = Math.Floor((ticks - stamTicks) * (100.0 / (100 + bonus))); + } + else + { + speed = Math.Floor(speed * (bonus + 100.0) / 100.0); - if ( Spells.Chivalry.DivineFurySpell.UnderEffect( m ) ) - bonus += 10; + if (speed <= 0) + speed = 1; - int discordanceEffect = 0; + ticks = Math.Floor(80000.0 / ((m.Stam + 100) * speed) - 2); + } - // Discordance gives a malus of -0/-28% to swing speed. - if ( SkillHandlers.Discordance.GetEffect( m, ref discordanceEffect ) ) - bonus -= discordanceEffect; + // Swing speed currently capped at one swing every 1.25 seconds (5 ticks). + if (ticks < 5) + ticks = 5; - v += AOS.Scale( v, bonus ); + delayInSeconds = ticks * 0.25; + } + else if (Core.AOS) + { + int v = (m.Stam + 100) * (int)speed; - if ( v <= 0 ) - v = 1; + int bonus = AosAttributes.GetValue(m, AosAttribute.WeaponSpeed); - delayInSeconds = Math.Floor( 40000.0 / v ) * 0.5; + if (DivineFurySpell.UnderEffect(m)) + bonus += 10; - // Maximum swing rate capped at one swing per second - // OSI dev said that it has and is supposed to be 1.25 - if ( delayInSeconds < 1.25 ) - delayInSeconds = 1.25; - } - else - { - int v = (m.Stam + 100) * (int) speed; + int discordanceEffect = 0; - if ( v <= 0 ) - v = 1; + // Discordance gives a malus of -0/-28% to swing speed. + if (Discordance.GetEffect(m, ref discordanceEffect)) + bonus -= discordanceEffect; - delayInSeconds = 15000.0 / v; - } + v += AOS.Scale(v, bonus); - return TimeSpan.FromSeconds( delayInSeconds ); - } + if (v <= 0) + v = 1; - public virtual void OnBeforeSwing( Mobile attacker, Mobile defender ) - { - WeaponAbility a = WeaponAbility.GetCurrentAbility( attacker ); + delayInSeconds = Math.Floor(40000.0 / v) * 0.5; - if ( a != null && !a.OnBeforeSwing( attacker, defender ) ) - WeaponAbility.ClearCurrentAbility( attacker ); + // Maximum swing rate capped at one swing per second + // OSI dev said that it has and is supposed to be 1.25 + if (delayInSeconds < 1.25) + delayInSeconds = 1.25; + } + else + { + int v = (m.Stam + 100) * (int)speed; - SpecialMove move = SpecialMove.GetCurrentMove( attacker ); + if (v <= 0) + v = 1; - if ( move != null && !move.OnBeforeSwing( attacker, defender ) ) - SpecialMove.ClearCurrentMove( attacker ); - } + delayInSeconds = 15000.0 / v; + } - public virtual TimeSpan OnSwing( Mobile attacker, Mobile defender ) - { - return OnSwing( attacker, defender, 1.0 ); - } + return TimeSpan.FromSeconds(delayInSeconds); + } - public virtual TimeSpan OnSwing( Mobile attacker, Mobile defender, double damageBonus ) - { - bool canSwing = true; + public virtual TimeSpan OnSwing(Mobile attacker, Mobile defender, double damageBonus) + { + bool canSwing = true; - if ( Core.AOS ) - { - canSwing = ( !attacker.Paralyzed && !attacker.Frozen ); - - if ( canSwing ) - { - canSwing = ( !(attacker.Spell is Spell sp) || !sp.IsCasting || !sp.BlocksMovement ); - } + if (Core.AOS) + { + canSwing = !attacker.Paralyzed && !attacker.Frozen; - if ( canSwing ) - { - canSwing = ( !(attacker is PlayerMobile p) || p.PeacedUntil <= DateTime.UtcNow ); - } - } - - #region Dueling - if ( attacker is PlayerMobile pm ) - { - if ( pm.DuelContext != null && !pm.DuelContext.CheckItemEquip( attacker, this ) ) - canSwing = false; - } - #endregion + if (canSwing) canSwing = !(attacker.Spell is Spell sp) || !sp.IsCasting || !sp.BlocksMovement; - if ( canSwing && attacker.HarmfulCheck( defender ) ) - { - attacker.DisruptiveAction(); - - if ( attacker.NetState != null ) - attacker.Send( new Swing( 0, attacker, defender ) ); - - if ( attacker is BaseCreature bc ) - { - WeaponAbility ab = bc.GetWeaponAbility(); - - if ( ab != null ) - { - if ( bc.WeaponAbilityChance > Utility.RandomDouble() ) - WeaponAbility.SetCurrentAbility( bc, ab ); - else - WeaponAbility.ClearCurrentAbility( bc ); - } - } - - if ( CheckHit( attacker, defender ) ) - OnHit( attacker, defender, damageBonus ); - else - OnMiss( attacker, defender ); - } - - return GetDelay( attacker ); - } - - #region Sounds - public virtual int GetHitAttackSound( Mobile attacker, Mobile defender ) - { - int sound = attacker.GetAttackSound(); - - if ( sound == -1 ) - sound = HitSound; - - return sound; - } - - public virtual int GetHitDefendSound( Mobile attacker, Mobile defender ) - { - return defender.GetHurtSound(); - } - - public virtual int GetMissAttackSound( Mobile attacker, Mobile defender ) - { - return attacker.GetAttackSound() == -1 ? MissSound : -1; - } - - public virtual int GetMissDefendSound( Mobile attacker, Mobile defender ) - { - return -1; - } - #endregion - - public static bool CheckParry( Mobile defender ) - { - if ( defender == null ) - return false; - - BaseShield shield = defender.FindItemOnLayer( Layer.TwoHanded ) as BaseShield; - - double parry = defender.Skills[SkillName.Parry].Value; - double bushidoNonRacial = defender.Skills[SkillName.Bushido].NonRacialValue; - double bushido = defender.Skills[SkillName.Bushido].Value; - - if ( shield != null ) - { - double chance = (parry - bushidoNonRacial) / 400.0; // As per OSI, no genitive effect from the Racial stuffs, ie, 120 parry and '0' bushido with humans - - if ( chance < 0 ) // chance shouldn't go below 0 - chance = 0; - - // Parry/Bushido over 100 grants a 5% bonus. - if ( parry >= 100.0 || bushido >= 100.0) - chance += 0.05; - - // Evasion grants a variable bonus post ML. 50% prior. - if ( Evasion.IsEvading( defender ) ) - chance *= Evasion.GetParryScalar( defender ); - - // Low dexterity lowers the chance. - if ( defender.Dex < 80 ) - chance = chance * (20 + defender.Dex) / 100; - - return defender.CheckSkill( SkillName.Parry, chance ); - } - if ( !(defender.Weapon is Fists) && !(defender.Weapon is BaseRanged) ) - { - BaseWeapon weapon = defender.Weapon as BaseWeapon; - - double divisor = (weapon.Layer == Layer.OneHanded) ? 48000.0 : 41140.0; - - double chance = (parry * bushido) / divisor; - - double aosChance = parry / 800.0; - - // Parry or Bushido over 100 grant a 5% bonus. - if ( parry >= 100.0 ) - { - chance += 0.05; - aosChance += 0.05; - } - else if ( bushido >= 100.0 ) - { - chance += 0.05; - } - - // Evasion grants a variable bonus post ML. 50% prior. - if ( Evasion.IsEvading( defender ) ) - chance *= Evasion.GetParryScalar( defender ); - - // Low dexterity lowers the chance. - if ( defender.Dex < 80 ) - chance = chance * (20 + defender.Dex) / 100; - - if ( chance > aosChance ) - return defender.CheckSkill( SkillName.Parry, chance ); - - return (aosChance > Utility.RandomDouble()); // Only skillcheck if wielding a shield & there's no effect from Bushido - } - - return false; - } - - public virtual int AbsorbDamageAOS( Mobile attacker, Mobile defender, int damage ) - { - bool blocked = false; - - if ( defender.Player || defender.Body.IsHuman ) - { - blocked = CheckParry( defender ); - - if ( blocked ) - { - defender.FixedEffect( 0x37B9, 10, 16 ); - damage = 0; - - // Successful block removes the Honorable Execution penalty. - HonorableExecution.RemovePenalty( defender ); - - if ( CounterAttack.IsCountering( defender ) ) - { - if ( defender.Weapon is BaseWeapon weapon ) - { - defender.FixedParticles(0x3779, 1, 15, 0x158B, 0x0, 0x3, EffectLayer.Waist); - weapon.OnSwing( defender, attacker ); - } - - CounterAttack.StopCountering( defender ); - } - - if ( Confidence.IsConfident( defender ) ) - { - defender.SendLocalizedMessage( 1063117 ); // Your confidence reassures you as you successfully block your opponent's blow. - - double bushido = defender.Skills.Bushido.Value; - - defender.Hits += Utility.RandomMinMax( 1, (int)(bushido / 12) ); - defender.Stam += Utility.RandomMinMax( 1, (int)(bushido / 5) ); - } - - BaseShield shield = defender.FindItemOnLayer( Layer.TwoHanded ) as BaseShield; - - shield?.OnHit( this, damage ); - } - } - - if ( !blocked ) - { - double positionChance = Utility.RandomDouble(); - - Item armorItem; - - if ( positionChance < 0.07 ) - armorItem = defender.NeckArmor; - else if ( positionChance < 0.14 ) - armorItem = defender.HandArmor; - else if ( positionChance < 0.28 ) - armorItem = defender.ArmsArmor; - else if ( positionChance < 0.43 ) - armorItem = defender.HeadArmor; - else if ( positionChance < 0.65 ) - armorItem = defender.LegsArmor; - else - armorItem = defender.ChestArmor; - - if ( armorItem is IWearableDurability armor ) - armor.OnHit( this, damage ); // call OnHit to lose durability - } - - return damage; - } - - public virtual int AbsorbDamage( Mobile attacker, Mobile defender, int damage ) - { - if ( Core.AOS ) - return AbsorbDamageAOS( attacker, defender, damage ); - - if ( defender.FindItemOnLayer( Layer.TwoHanded ) is BaseShield shield ) - damage = shield.OnHit( this, damage ); - - double chance = Utility.RandomDouble(); - - Item armorItem; - - if ( chance < 0.07 ) - armorItem = defender.NeckArmor; - else if ( chance < 0.14 ) - armorItem = defender.HandArmor; - else if ( chance < 0.28 ) - armorItem = defender.ArmsArmor; - else if ( chance < 0.43 ) - armorItem = defender.HeadArmor; - else if ( chance < 0.65 ) - armorItem = defender.LegsArmor; - else - armorItem = defender.ChestArmor; - - if ( armorItem is IWearableDurability armor ) - damage = armor.OnHit( this, damage ); - - int virtualArmor = defender.VirtualArmor + defender.VirtualArmorMod; - - if ( virtualArmor > 0 ) - { - double scalar; - - if ( chance < 0.14 ) - scalar = 0.07; - else if ( chance < 0.28 ) - scalar = 0.14; - else if ( chance < 0.43 ) - scalar = 0.15; - else if ( chance < 0.65 ) - scalar = 0.22; - else - scalar = 0.35; - - int from = (int)(virtualArmor * scalar) / 2; - int to = (int)(virtualArmor * scalar); - - damage -= Utility.Random( from, (to - from) + 1 ); - } - - return damage; - } - - public virtual int GetPackInstinctBonus( Mobile attacker, Mobile defender ) - { - if ( attacker.Player || defender.Player ) - return 0; - - if ( !(attacker is BaseCreature bc) || bc.PackInstinct == PackInstinct.None || (!bc.Controlled && !bc.Summoned) ) - return 0; - - Mobile master = bc.ControlMaster; - - if ( master == null ) - master = bc.SummonMaster; - - if ( master == null ) - return 0; - - int inPack = 1; - - IPooledEnumerable eable = defender.GetMobilesInRange( 1 ); - foreach ( BaseCreature m in eable ) - { - if ( m != attacker ) - { - if ( (m.PackInstinct & bc.PackInstinct) == 0 || (!m.Controlled && !m.Summoned) ) - continue; - - Mobile theirMaster = m.ControlMaster; - - if ( theirMaster == null ) - theirMaster = m.SummonMaster; - - if ( master == theirMaster && m.Combatant == defender ) - ++inPack; - } - } - eable.Free(); - - if ( inPack >= 5 ) - return 100; - if ( inPack >= 4 ) - return 75; - if ( inPack >= 3 ) - return 50; - if ( inPack >= 2 ) - return 25; - - return 0; - } - - public static bool InDoubleStrike { get; set; } - - public virtual void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1.0) - { - if ( MirrorImage.HasClone( defender ) && (defender.Skills.Ninjitsu.Value / 150.0) > Utility.RandomDouble() ) - { - IPooledEnumerable eable = defender.GetMobilesInRange( 4 ); - foreach ( Clone m in eable ) - { - if ( m != null && m.Summoned && m.SummonMaster == defender ) - { - attacker.SendLocalizedMessage( 1063141 ); // Your attack has been diverted to a nearby mirror image of your target! - defender.SendLocalizedMessage( 1063140 ); // You manage to divert the attack onto one of your nearby mirror images. - - /* - * TODO: What happens if the Clone parries a blow? - * And what about if the attacker is using Honorable Execution - * and kills it? - */ - - defender = m; - break; - } - } - eable.Free(); - } - - PlaySwingAnimation( attacker ); - PlayHurtAnimation( defender ); - - attacker.PlaySound( GetHitAttackSound( attacker, defender ) ); - defender.PlaySound( GetHitDefendSound( attacker, defender ) ); - - int damage = ComputeDamage( attacker, defender ); - - #region Damage Multipliers - /* - * The following damage bonuses multiply damage by a factor. - * Capped at x3 (300%). - */ - int percentageBonus = 0; - - WeaponAbility a = WeaponAbility.GetCurrentAbility( attacker ); - SpecialMove move = SpecialMove.GetCurrentMove( attacker ); - - if ( a != null ) - { - percentageBonus += (int)(a.DamageScalar * 100) - 100; - } - - if ( move != null ) - { - percentageBonus += (int)(move.GetDamageScalar( attacker, defender ) * 100) - 100; - } - - percentageBonus += (int)(damageBonus * 100) - 100; - - CheckSlayerResult cs = CheckSlayers( attacker, defender ); - - if ( cs != CheckSlayerResult.None ) - { - if ( cs == CheckSlayerResult.Slayer ) - defender.FixedEffect( 0x37B9, 10, 5 ); - - percentageBonus += 100; - } - - if ( !attacker.Player ) - { - if ( defender is PlayerMobile pm ) - { - if ( pm.EnemyOfOneType != null && pm.EnemyOfOneType != attacker.GetType() ) - { - percentageBonus += 100; - } - } - } - else if ( !defender.Player ) - { - if ( attacker is PlayerMobile pm ) - { - if ( pm.WaitingForEnemy ) - { - pm.EnemyOfOneType = defender.GetType(); - pm.WaitingForEnemy = false; - } - - if ( pm.EnemyOfOneType == defender.GetType() ) - { - defender.FixedEffect( 0x37B9, 10, 5, 1160, 0 ); - - percentageBonus += 50; - } - } - } - - int packInstinctBonus = GetPackInstinctBonus( attacker, defender ); - - if ( packInstinctBonus != 0 ) - { - percentageBonus += packInstinctBonus; - } - - if ( InDoubleStrike ) - { - percentageBonus -= 10; - } - - TransformContext context = TransformationSpellHelper.GetContext( defender ); - - if ( (m_Slayer == SlayerName.Silver || m_Slayer2 == SlayerName.Silver) && context?.Spell is NecromancerSpell && context.Type != typeof( HorrificBeastSpell ) ) - { - // Every necromancer transformation other than horrific beast takes an additional 25% damage - percentageBonus += 25; - } - - if ( attacker is PlayerMobile pmAttacker && !(Core.ML && defender is PlayerMobile )) - { - if ( pmAttacker.HonorActive && pmAttacker.InRange( defender, 1 ) ) - { - percentageBonus += 25; - } - - if ( pmAttacker.SentHonorContext != null && pmAttacker.SentHonorContext.Target == defender ) - { - percentageBonus += pmAttacker.SentHonorContext.PerfectionDamageBonus; - } - } - - if ( attacker.Talisman is BaseTalisman talisman && talisman.Killer != null ) - percentageBonus += talisman.Killer.DamageBonus( defender ); - - percentageBonus = Math.Min( percentageBonus, 300 ); - - damage = AOS.Scale( damage, 100 + percentageBonus ); - #endregion - - BaseCreature bcAtt = attacker as BaseCreature; - BaseCreature bcDef = defender as BaseCreature; - - bcAtt?.AlterMeleeDamageTo( defender, ref damage ); - bcDef?.AlterMeleeDamageFrom( attacker, ref damage ); - - damage = AbsorbDamage( attacker, defender, damage ); - - if ( !Core.AOS && damage < 1 ) - damage = 1; - else if ( Core.AOS && damage == 0 ) // parried - { - if ( a != null && a.Validate( attacker ) /*&& a.CheckMana( attacker, true )*/ ) // Parried special moves have no mana cost - { - a = null; - WeaponAbility.ClearCurrentAbility( attacker ); - - attacker.SendLocalizedMessage( 1061140 ); // Your attack was parried! - } - } - - AddBlood( attacker, defender, damage ); - - int phys, fire, cold, pois, nrgy, chaos, direct; - - GetDamageTypes( attacker, out phys, out fire, out cold, out pois, out nrgy, out chaos, out direct ); - - if ( Core.ML && this is BaseRanged ) - { - if ( attacker.FindItemOnLayer( Layer.Cloak ) is BaseQuiver quiver ) - quiver.AlterBowDamage( ref phys, ref fire, ref cold, ref pois, ref nrgy, ref chaos, ref direct ); - } - - if ( Consecrated ) - { - phys = defender.PhysicalResistance; - fire = defender.FireResistance; - cold = defender.ColdResistance; - pois = defender.PoisonResistance; - nrgy = defender.EnergyResistance; - - int low = phys, type = 0; - - if ( fire < low ){ low = fire; type = 1; } - if ( cold < low ){ low = cold; type = 2; } - if ( pois < low ){ low = pois; type = 3; } - if ( nrgy < low ){ low = nrgy; type = 4; } + if (canSwing) canSwing = !(attacker is PlayerMobile p) || p.PeacedUntil <= DateTime.UtcNow; + } - phys = fire = cold = pois = nrgy = chaos = direct = 0; + #region Dueling - if ( type == 0 ) phys = 100; - else if ( type == 1 ) fire = 100; - else if ( type == 2 ) cold = 100; - else if ( type == 3 ) pois = 100; - else if ( type == 4 ) nrgy = 100; - } - - // TODO: Scale damage, alongside the leech effects below, to weapon speed. - if ( ImmolatingWeaponSpell.IsImmolating( this ) && damage > 0 ) - ImmolatingWeaponSpell.DoEffect( this, defender ); - - int damageGiven = damage; - - if ( a != null && !a.OnBeforeDamage( attacker, defender ) ) - { - WeaponAbility.ClearCurrentAbility( attacker ); - a = null; - } - - if ( move != null && !move.OnBeforeDamage( attacker, defender ) ) - { - SpecialMove.ClearCurrentMove( attacker ); - move = null; - } - - bool ignoreArmor = ( a is ArmorIgnore || (move != null && move.IgnoreArmor( attacker )) ); - - damageGiven = AOS.Damage( defender, attacker, damage, ignoreArmor, phys, fire, cold, pois, nrgy, chaos, direct, false, this is BaseRanged, false ); - - double propertyBonus = move?.GetPropertyBonus( attacker ) ?? 1.0; - - if ( Core.AOS ) - { - int lifeLeech = 0; - int stamLeech = 0; - int manaLeech = 0; - int wraithLeech = 0; - - if ( (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitLeechHits ) * propertyBonus) > Utility.Random( 100 ) ) - lifeLeech += 30; // HitLeechHits% chance to leech 30% of damage as hit points + if (attacker is PlayerMobile pm) + if (pm.DuelContext != null && !pm.DuelContext.CheckItemEquip(attacker, this)) + canSwing = false; - if ( (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitLeechStam ) * propertyBonus) > Utility.Random( 100 ) ) - stamLeech += 100; // HitLeechStam% chance to leech 100% of damage as stamina - - if ( (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitLeechMana ) * propertyBonus) > Utility.Random( 100 ) ) - manaLeech += 40; // HitLeechMana% chance to leech 40% of damage as mana - - if ( Cursed ) - lifeLeech += 50; // Additional 50% life leech for cursed weapons (necro spell) - - context = TransformationSpellHelper.GetContext( attacker ); - - if ( context != null && context.Type == typeof( VampiricEmbraceSpell ) ) - lifeLeech += 20; // Vampiric embrace gives an additional 20% life leech - - if ( context != null && context.Type == typeof( WraithFormSpell ) ) - { - wraithLeech = (5 + (int)((15 * attacker.Skills.SpiritSpeak.Value) / 100)); // Wraith form gives an additional 5-20% mana leech - - // Mana leeched by the Wraith Form spell is actually stolen, not just leeched. - defender.Mana -= AOS.Scale( damageGiven, wraithLeech ); - - manaLeech += wraithLeech; - } + #endregion - if ( lifeLeech != 0 ) - attacker.Hits += AOS.Scale( damageGiven, lifeLeech ); + if (canSwing && attacker.HarmfulCheck(defender)) + { + attacker.DisruptiveAction(); - if ( stamLeech != 0 ) - attacker.Stam += AOS.Scale( damageGiven, stamLeech ); + if (attacker.NetState != null) + attacker.Send(new Swing(0, attacker, defender)); - if ( manaLeech != 0 ) - attacker.Mana += AOS.Scale( damageGiven, manaLeech ); + if (attacker is BaseCreature bc) + { + WeaponAbility ab = bc.GetWeaponAbility(); - if ( lifeLeech != 0 || stamLeech != 0 || manaLeech != 0 ) - attacker.PlaySound( 0x44D ); - } - - if ( m_MaxHits > 0 && ((MaxRange <= 1 && (defender is Slime || defender is AcidElemental)) || Utility.RandomDouble() < .04) ) // Stratics says 50% chance, seems more like 4%.. - { - if ( MaxRange <= 1 && (defender is Slime || defender is AcidElemental) ) - attacker.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500263 ); // *Acid blood scars your weapon!* + if (ab != null) + { + if (bc.WeaponAbilityChance > Utility.RandomDouble()) + WeaponAbility.SetCurrentAbility(bc, ab); + else + WeaponAbility.ClearCurrentAbility(bc); + } + } - if ( Core.AOS && m_AosWeaponAttributes.SelfRepair > Utility.Random( 10 ) ) - { - HitPoints += 2; - } - else - { - if ( m_Hits > 0 ) - { - --HitPoints; - } - else if ( m_MaxHits > 1 ) - { - --MaxHitPoints; + if (CheckHit(attacker, defender)) + OnHit(attacker, defender, damageBonus); + else + OnMiss(attacker, defender); + } - if ( Parent is Mobile mobile ) - mobile.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1061121 ); // Your equipment is severely damaged. - } - else - { - Delete(); - } - } - } + return GetDelay(attacker); + } - if ( attacker is VampireBatFamiliar bc ) - { - Mobile caster = bc.ControlMaster ?? bc.SummonMaster; + public static bool CheckParry(Mobile defender) + { + if (defender == null) + return false; - if ( caster != null && caster.Map == bc.Map && caster.InRange( bc, 2 ) ) - caster.Hits += damage; - else - bc.Hits += damage; - } + BaseShield shield = defender.FindItemOnLayer(Layer.TwoHanded) as BaseShield; - if ( Core.AOS ) - { - int physChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitPhysicalArea ) * propertyBonus); - int fireChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitFireArea ) * propertyBonus); - int coldChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitColdArea ) * propertyBonus); - int poisChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitPoisonArea ) * propertyBonus); - int nrgyChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitEnergyArea ) * propertyBonus); + double parry = defender.Skills[SkillName.Parry].Value; + double bushidoNonRacial = defender.Skills[SkillName.Bushido].NonRacialValue; + double bushido = defender.Skills[SkillName.Bushido].Value; - if ( physChance != 0 && physChance > Utility.Random( 100 ) ) - DoAreaAttack( attacker, defender, 0x10E, 50, 100, 0, 0, 0, 0 ); + if (shield != null) + { + double + chance = (parry - bushidoNonRacial) / + 400.0; // As per OSI, no genitive effect from the Racial stuffs, ie, 120 parry and '0' bushido with humans - if ( fireChance != 0 && fireChance > Utility.Random( 100 ) ) - DoAreaAttack( attacker, defender, 0x11D, 1160, 0, 100, 0, 0, 0 ); + if (chance < 0) // chance shouldn't go below 0 + chance = 0; - if ( coldChance != 0 && coldChance > Utility.Random( 100 ) ) - DoAreaAttack( attacker, defender, 0x0FC, 2100, 0, 0, 100, 0, 0 ); + // Parry/Bushido over 100 grants a 5% bonus. + if (parry >= 100.0 || bushido >= 100.0) + chance += 0.05; - if ( poisChance != 0 && poisChance > Utility.Random( 100 ) ) - DoAreaAttack( attacker, defender, 0x205, 1166, 0, 0, 0, 100, 0 ); + // Evasion grants a variable bonus post ML. 50% prior. + if (Evasion.IsEvading(defender)) + chance *= Evasion.GetParryScalar(defender); - if ( nrgyChance != 0 && nrgyChance > Utility.Random( 100 ) ) - DoAreaAttack( attacker, defender, 0x1F1, 120, 0, 0, 0, 0, 100 ); + // Low dexterity lowers the chance. + if (defender.Dex < 80) + chance = chance * (20 + defender.Dex) / 100; - int maChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitMagicArrow ) * propertyBonus); - int harmChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitHarm ) * propertyBonus); - int fireballChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitFireball ) * propertyBonus); - int lightningChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitLightning ) * propertyBonus); - int dispelChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitDispel ) * propertyBonus); + return defender.CheckSkill(SkillName.Parry, chance); + } + + if (!(defender.Weapon is Fists) && !(defender.Weapon is BaseRanged)) + { + BaseWeapon weapon = defender.Weapon as BaseWeapon; - if ( maChance != 0 && maChance > Utility.Random( 100 ) ) - DoMagicArrow( attacker, defender ); + double divisor = weapon.Layer == Layer.OneHanded ? 48000.0 : 41140.0; - if ( harmChance != 0 && harmChance > Utility.Random( 100 ) ) - DoHarm( attacker, defender ); + double chance = parry * bushido / divisor; - if ( fireballChance != 0 && fireballChance > Utility.Random( 100 ) ) - DoFireball( attacker, defender ); + double aosChance = parry / 800.0; - if ( lightningChance != 0 && lightningChance > Utility.Random( 100 ) ) - DoLightning( attacker, defender ); + // Parry or Bushido over 100 grant a 5% bonus. + if (parry >= 100.0) + { + chance += 0.05; + aosChance += 0.05; + } + else if (bushido >= 100.0) + { + chance += 0.05; + } - if ( dispelChance != 0 && dispelChance > Utility.Random( 100 ) ) - DoDispel( attacker, defender ); + // Evasion grants a variable bonus post ML. 50% prior. + if (Evasion.IsEvading(defender)) + chance *= Evasion.GetParryScalar(defender); - int laChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitLowerAttack ) * propertyBonus); - int ldChance = (int)(AosWeaponAttributes.GetValue( attacker, AosWeaponAttribute.HitLowerDefend ) * propertyBonus); + // Low dexterity lowers the chance. + if (defender.Dex < 80) + chance = chance * (20 + defender.Dex) / 100; + + if (chance > aosChance) + return defender.CheckSkill(SkillName.Parry, chance); + + return + aosChance > Utility + .RandomDouble(); // Only skillcheck if wielding a shield & there's no effect from Bushido + } + + return false; + } + + public virtual int AbsorbDamageAOS(Mobile attacker, Mobile defender, int damage) + { + bool blocked = false; + + if (defender.Player || defender.Body.IsHuman) + { + blocked = CheckParry(defender); + + if (blocked) + { + defender.FixedEffect(0x37B9, 10, 16); + damage = 0; + + // Successful block removes the Honorable Execution penalty. + HonorableExecution.RemovePenalty(defender); + + if (CounterAttack.IsCountering(defender)) + { + if (defender.Weapon is BaseWeapon weapon) + { + defender.FixedParticles(0x3779, 1, 15, 0x158B, 0x0, 0x3, EffectLayer.Waist); + weapon.OnSwing(defender, attacker); + } + + CounterAttack.StopCountering(defender); + } + + if (Confidence.IsConfident(defender)) + { + defender.SendLocalizedMessage( + 1063117); // Your confidence reassures you as you successfully block your opponent's blow. + + double bushido = defender.Skills.Bushido.Value; + + defender.Hits += Utility.RandomMinMax(1, (int)(bushido / 12)); + defender.Stam += Utility.RandomMinMax(1, (int)(bushido / 5)); + } + + BaseShield shield = defender.FindItemOnLayer(Layer.TwoHanded) as BaseShield; + + shield?.OnHit(this, damage); + } + } + + if (!blocked) + { + double positionChance = Utility.RandomDouble(); + + Item armorItem; + + if (positionChance < 0.07) + armorItem = defender.NeckArmor; + else if (positionChance < 0.14) + armorItem = defender.HandArmor; + else if (positionChance < 0.28) + armorItem = defender.ArmsArmor; + else if (positionChance < 0.43) + armorItem = defender.HeadArmor; + else if (positionChance < 0.65) + armorItem = defender.LegsArmor; + else + armorItem = defender.ChestArmor; + + if (armorItem is IWearableDurability armor) + armor.OnHit(this, damage); // call OnHit to lose durability + } + + return damage; + } + + public virtual int AbsorbDamage(Mobile attacker, Mobile defender, int damage) + { + if (Core.AOS) + return AbsorbDamageAOS(attacker, defender, damage); + + if (defender.FindItemOnLayer(Layer.TwoHanded) is BaseShield shield) + damage = shield.OnHit(this, damage); + + double chance = Utility.RandomDouble(); + + Item armorItem; + + if (chance < 0.07) + armorItem = defender.NeckArmor; + else if (chance < 0.14) + armorItem = defender.HandArmor; + else if (chance < 0.28) + armorItem = defender.ArmsArmor; + else if (chance < 0.43) + armorItem = defender.HeadArmor; + else if (chance < 0.65) + armorItem = defender.LegsArmor; + else + armorItem = defender.ChestArmor; + + if (armorItem is IWearableDurability armor) + damage = armor.OnHit(this, damage); + + int virtualArmor = defender.VirtualArmor + defender.VirtualArmorMod; + + if (virtualArmor > 0) + { + double scalar; + + if (chance < 0.14) + scalar = 0.07; + else if (chance < 0.28) + scalar = 0.14; + else if (chance < 0.43) + scalar = 0.15; + else if (chance < 0.65) + scalar = 0.22; + else + scalar = 0.35; + + int from = (int)(virtualArmor * scalar) / 2; + int to = (int)(virtualArmor * scalar); + + damage -= Utility.Random(from, to - from + 1); + } + + return damage; + } - if ( laChance != 0 && laChance > Utility.Random( 100 ) ) - DoLowerAttack( attacker, defender ); + public virtual int GetPackInstinctBonus(Mobile attacker, Mobile defender) + { + if (attacker.Player || defender.Player) + return 0; + + if (!(attacker is BaseCreature bc) || bc.PackInstinct == PackInstinct.None || !bc.Controlled && !bc.Summoned) + return 0; - if ( ldChance != 0 && ldChance > Utility.Random( 100 ) ) - DoLowerDefense( attacker, defender ); - } + Mobile master = bc.ControlMaster; - bcAtt?.OnGaveMeleeAttack( defender ); - bcDef?.OnGotMeleeAttack( attacker ); + if (master == null) + master = bc.SummonMaster; + + if (master == null) + return 0; + + int inPack = 1; + + IPooledEnumerable eable = defender.GetMobilesInRange(1); + foreach (BaseCreature m in eable) + if (m != attacker) + { + if ((m.PackInstinct & bc.PackInstinct) == 0 || !m.Controlled && !m.Summoned) + continue; + + Mobile theirMaster = m.ControlMaster; + + if (theirMaster == null) + theirMaster = m.SummonMaster; + + if (master == theirMaster && m.Combatant == defender) + ++inPack; + } + + eable.Free(); + + if (inPack >= 5) + return 100; + if (inPack >= 4) + return 75; + if (inPack >= 3) + return 50; + if (inPack >= 2) + return 25; - a?.OnHit( attacker, defender, damage ); - move?.OnHit( attacker, defender, damage ); + return 0; + } + + public virtual void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1.0) + { + if (MirrorImage.HasClone(defender) && defender.Skills.Ninjitsu.Value / 150.0 > Utility.RandomDouble()) + { + IPooledEnumerable eable = defender.GetMobilesInRange(4); + foreach (Clone m in eable) + if (m != null && m.Summoned && m.SummonMaster == defender) + { + attacker.SendLocalizedMessage( + 1063141); // Your attack has been diverted to a nearby mirror image of your target! + defender.SendLocalizedMessage( + 1063140); // You manage to divert the attack onto one of your nearby mirror images. - if ( defender is IHonorTarget it ) - it.ReceivedHonorContext?.OnTargetHit( attacker ); + /* + * TODO: What happens if the Clone parries a blow? + * And what about if the attacker is using Honorable Execution + * and kills it? + */ - if ( !(this is BaseRanged) ) - { - if ( AnimalForm.UnderTransformation( attacker, typeof( GiantSerpent ) ) ) - defender.ApplyPoison( attacker, Poison.Lesser ); + defender = m; + break; + } - if ( AnimalForm.UnderTransformation( defender, typeof( BullFrog ) ) ) - attacker.ApplyPoison( defender, Poison.Regular ); - } - } + eable.Free(); + } - public virtual double GetAosDamage( Mobile attacker, int bonus, int dice, int sides ) - { - int damage = Utility.Dice( dice, sides, bonus ) * 100; - int damageBonus = 0; + PlaySwingAnimation(attacker); + PlayHurtAnimation(defender); - // Inscription bonus - int inscribeSkill = attacker.Skills[SkillName.Inscribe].Fixed; + attacker.PlaySound(GetHitAttackSound(attacker, defender)); + defender.PlaySound(GetHitDefendSound(attacker, defender)); - damageBonus += inscribeSkill / 200; + int damage = ComputeDamage(attacker, defender); - if ( inscribeSkill >= 1000 ) - damageBonus += 5; + #region Damage Multipliers - if ( attacker.Player ) - { - // Int bonus - damageBonus += (attacker.Int / 10); + /* + * The following damage bonuses multiply damage by a factor. + * Capped at x3 (300%). + */ + int percentageBonus = 0; - // SDI bonus - damageBonus += AosAttributes.GetValue( attacker, AosAttribute.SpellDamage ); + WeaponAbility a = WeaponAbility.GetCurrentAbility(attacker); + SpecialMove move = SpecialMove.GetCurrentMove(attacker); - TransformContext context = TransformationSpellHelper.GetContext( attacker ); + if (a != null) percentageBonus += (int)(a.DamageScalar * 100) - 100; - if ( context?.Spell is ReaperFormSpell spell ) - damageBonus += spell.SpellDamageBonus; - } + if (move != null) percentageBonus += (int)(move.GetDamageScalar(attacker, defender) * 100) - 100; - damage = AOS.Scale( damage, 100 + damageBonus ); + percentageBonus += (int)(damageBonus * 100) - 100; - return damage / 100; - } + CheckSlayerResult cs = CheckSlayers(attacker, defender); - #region Do - public virtual void DoMagicArrow( Mobile attacker, Mobile defender ) - { - if ( !attacker.CanBeHarmful( defender, false ) ) - return; + if (cs != CheckSlayerResult.None) + { + if (cs == CheckSlayerResult.Slayer) + defender.FixedEffect(0x37B9, 10, 5); - attacker.DoHarmful( defender ); + percentageBonus += 100; + } - double damage = GetAosDamage( attacker, 10, 1, 4 ); + if (!attacker.Player) + { + if (defender is PlayerMobile pm) + if (pm.EnemyOfOneType != null && pm.EnemyOfOneType != attacker.GetType()) + percentageBonus += 100; + } + else if (!defender.Player) + { + if (attacker is PlayerMobile pm) + { + if (pm.WaitingForEnemy) + { + pm.EnemyOfOneType = defender.GetType(); + pm.WaitingForEnemy = false; + } - attacker.MovingParticles( defender, 0x36E4, 5, 0, false, true, 3006, 4006, 0 ); - attacker.PlaySound( 0x1E5 ); + if (pm.EnemyOfOneType == defender.GetType()) + { + defender.FixedEffect(0x37B9, 10, 5, 1160, 0); - SpellHelper.Damage( TimeSpan.FromSeconds( 1.0 ), defender, attacker, damage, 0, 100, 0, 0, 0 ); - } + percentageBonus += 50; + } + } + } - public virtual void DoHarm( Mobile attacker, Mobile defender ) - { - if ( !attacker.CanBeHarmful( defender, false ) ) - return; + int packInstinctBonus = GetPackInstinctBonus(attacker, defender); - attacker.DoHarmful( defender ); + if (packInstinctBonus != 0) percentageBonus += packInstinctBonus; + + if (InDoubleStrike) percentageBonus -= 10; - double damage = GetAosDamage( attacker, 17, 1, 5 ); + TransformContext context = TransformationSpellHelper.GetContext(defender); - if ( !defender.InRange( attacker, 2 ) ) - damage *= 0.25; // 1/4 damage at > 2 tile range - else if ( !defender.InRange( attacker, 1 ) ) - damage *= 0.50; // 1/2 damage at 2 tile range + if ((m_Slayer == SlayerName.Silver || m_Slayer2 == SlayerName.Silver) && context?.Spell is NecromancerSpell && + context.Type != typeof(HorrificBeastSpell)) percentageBonus += 25; - defender.FixedParticles( 0x374A, 10, 30, 5013, 1153, 2, EffectLayer.Waist ); - defender.PlaySound( 0x0FC ); + if (attacker is PlayerMobile pmAttacker && !(Core.ML && defender is PlayerMobile)) + { + if (pmAttacker.HonorActive && pmAttacker.InRange(defender, 1)) percentageBonus += 25; - SpellHelper.Damage( TimeSpan.Zero, defender, attacker, damage, 0, 0, 100, 0, 0 ); - } + if (pmAttacker.SentHonorContext != null && pmAttacker.SentHonorContext.Target == defender) + percentageBonus += pmAttacker.SentHonorContext.PerfectionDamageBonus; + } - public virtual void DoFireball( Mobile attacker, Mobile defender ) - { - if ( !attacker.CanBeHarmful( defender, false ) ) - return; + if (attacker.Talisman is BaseTalisman talisman && talisman.Killer != null) + percentageBonus += talisman.Killer.DamageBonus(defender); - attacker.DoHarmful( defender ); + percentageBonus = Math.Min(percentageBonus, 300); - double damage = GetAosDamage( attacker, 19, 1, 5 ); + damage = AOS.Scale(damage, 100 + percentageBonus); - attacker.MovingParticles( defender, 0x36D4, 7, 0, false, true, 9502, 4019, 0x160 ); - attacker.PlaySound( 0x15E ); + #endregion - SpellHelper.Damage( TimeSpan.FromSeconds( 1.0 ), defender, attacker, damage, 0, 100, 0, 0, 0 ); - } + BaseCreature bcAtt = attacker as BaseCreature; + BaseCreature bcDef = defender as BaseCreature; - public virtual void DoLightning( Mobile attacker, Mobile defender ) - { - if ( !attacker.CanBeHarmful( defender, false ) ) - return; + bcAtt?.AlterMeleeDamageTo(defender, ref damage); + bcDef?.AlterMeleeDamageFrom(attacker, ref damage); - attacker.DoHarmful( defender ); + damage = AbsorbDamage(attacker, defender, damage); - double damage = GetAosDamage( attacker, 23, 1, 4 ); + if (!Core.AOS && damage < 1) + damage = 1; + else if (Core.AOS && damage == 0) // parried + if (a != null && a.Validate(attacker) /*&& a.CheckMana( attacker, true )*/ + ) // Parried special moves have no mana cost + { + a = null; + WeaponAbility.ClearCurrentAbility(attacker); - defender.BoltEffect( 0 ); + attacker.SendLocalizedMessage(1061140); // Your attack was parried! + } - SpellHelper.Damage( TimeSpan.Zero, defender, attacker, damage, 0, 0, 0, 0, 100 ); - } + AddBlood(attacker, defender, damage); - public virtual void DoDispel( Mobile attacker, Mobile defender ) - { - bool dispellable = false; + int phys, fire, cold, pois, nrgy, chaos, direct; - if ( defender is BaseCreature creature ) - dispellable = creature.Summoned && !creature.IsAnimatedDead; + GetDamageTypes(attacker, out phys, out fire, out cold, out pois, out nrgy, out chaos, out direct); - if ( !dispellable ) - return; + if (Core.ML && this is BaseRanged) + if (attacker.FindItemOnLayer(Layer.Cloak) is BaseQuiver quiver) + quiver.AlterBowDamage(ref phys, ref fire, ref cold, ref pois, ref nrgy, ref chaos, ref direct); - if ( !attacker.CanBeHarmful( defender, false ) ) - return; + if (Consecrated) + { + phys = defender.PhysicalResistance; + fire = defender.FireResistance; + cold = defender.ColdResistance; + pois = defender.PoisonResistance; + nrgy = defender.EnergyResistance; - attacker.DoHarmful( defender ); + int low = phys, type = 0; - MagerySpell sp = new Spells.Sixth.DispelSpell( attacker, null ); + if (fire < low) + { + low = fire; + type = 1; + } - if ( sp.CheckResisted( defender ) ) - { - defender.FixedEffect( 0x3779, 10, 20 ); - } - else - { - Effects.SendLocationParticles( EffectItem.Create( defender.Location, defender.Map, EffectItem.DefaultDuration ), 0x3728, 8, 20, 5042 ); - Effects.PlaySound( defender, defender.Map, 0x201 ); + if (cold < low) + { + low = cold; + type = 2; + } - defender.Delete(); - } - } + if (pois < low) + { + low = pois; + type = 3; + } - public virtual void DoLowerAttack( Mobile from, Mobile defender ) - { - if ( HitLower.ApplyAttack( defender ) ) - { - defender.PlaySound( 0x28E ); - Effects.SendTargetEffect( defender, 0x37BE, 1, 4, 0xA, 3 ); - } - } + if (nrgy < low) + { + low = nrgy; + type = 4; + } - public virtual void DoLowerDefense( Mobile from, Mobile defender ) - { - if ( HitLower.ApplyDefense( defender ) ) - { - defender.PlaySound( 0x28E ); - Effects.SendTargetEffect( defender, 0x37BE, 1, 4, 0x23, 3 ); - } - } + phys = fire = cold = pois = nrgy = chaos = direct = 0; - public virtual void DoAreaAttack( Mobile from, Mobile defender, int sound, int hue, int phys, int fire, int cold, int pois, int nrgy ) - { - Map map = from.Map; + if (type == 0) phys = 100; + else if (type == 1) fire = 100; + else if (type == 2) cold = 100; + else if (type == 3) pois = 100; + else if (type == 4) nrgy = 100; + } - if ( map == null ) - return; + // TODO: Scale damage, alongside the leech effects below, to weapon speed. + if (ImmolatingWeaponSpell.IsImmolating(this) && damage > 0) + ImmolatingWeaponSpell.DoEffect(this, defender); + + int damageGiven = damage; + + if (a != null && !a.OnBeforeDamage(attacker, defender)) + { + WeaponAbility.ClearCurrentAbility(attacker); + a = null; + } + + if (move != null && !move.OnBeforeDamage(attacker, defender)) + { + SpecialMove.ClearCurrentMove(attacker); + move = null; + } + + bool ignoreArmor = a is ArmorIgnore || move != null && move.IgnoreArmor(attacker); + + damageGiven = AOS.Damage(defender, attacker, damage, ignoreArmor, phys, fire, cold, pois, nrgy, chaos, direct, + false, this is BaseRanged, false); + + double propertyBonus = move?.GetPropertyBonus(attacker) ?? 1.0; + + if (Core.AOS) + { + int lifeLeech = 0; + int stamLeech = 0; + int manaLeech = 0; + int wraithLeech = 0; + + if ((int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitLeechHits) * propertyBonus) > + Utility.Random(100)) + lifeLeech += 30; // HitLeechHits% chance to leech 30% of damage as hit points + + if ((int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitLeechStam) * propertyBonus) > + Utility.Random(100)) + stamLeech += 100; // HitLeechStam% chance to leech 100% of damage as stamina + + if ((int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitLeechMana) * propertyBonus) > + Utility.Random(100)) + manaLeech += 40; // HitLeechMana% chance to leech 40% of damage as mana + + if (Cursed) + lifeLeech += 50; // Additional 50% life leech for cursed weapons (necro spell) + + context = TransformationSpellHelper.GetContext(attacker); + + if (context != null && context.Type == typeof(VampiricEmbraceSpell)) + lifeLeech += 20; // Vampiric embrace gives an additional 20% life leech + + if (context != null && context.Type == typeof(WraithFormSpell)) + { + wraithLeech = + 5 + (int)(15 * attacker.Skills.SpiritSpeak.Value / + 100); // Wraith form gives an additional 5-20% mana leech + + // Mana leeched by the Wraith Form spell is actually stolen, not just leeched. + defender.Mana -= AOS.Scale(damageGiven, wraithLeech); + + manaLeech += wraithLeech; + } + + if (lifeLeech != 0) + attacker.Hits += AOS.Scale(damageGiven, lifeLeech); + + if (stamLeech != 0) + attacker.Stam += AOS.Scale(damageGiven, stamLeech); + + if (manaLeech != 0) + attacker.Mana += AOS.Scale(damageGiven, manaLeech); + + if (lifeLeech != 0 || stamLeech != 0 || manaLeech != 0) + attacker.PlaySound(0x44D); + } + + if (m_MaxHits > 0 && (MaxRange <= 1 && (defender is Slime || defender is AcidElemental) || + Utility.RandomDouble() < .04)) // Stratics says 50% chance, seems more like 4%.. + { + if (MaxRange <= 1 && (defender is Slime || defender is AcidElemental)) + attacker.LocalOverheadMessage(MessageType.Regular, 0x3B2, 500263); // *Acid blood scars your weapon!* + + if (Core.AOS && m_AosWeaponAttributes.SelfRepair > Utility.Random(10)) + { + HitPoints += 2; + } + else + { + if (m_Hits > 0) + { + --HitPoints; + } + else if (m_MaxHits > 1) + { + --MaxHitPoints; + + if (Parent is Mobile mobile) + mobile.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1061121); // Your equipment is severely damaged. + } + else + { + Delete(); + } + } + } + + if (attacker is VampireBatFamiliar bc) + { + Mobile caster = bc.ControlMaster ?? bc.SummonMaster; + + if (caster != null && caster.Map == bc.Map && caster.InRange(bc, 2)) + caster.Hits += damage; + else + bc.Hits += damage; + } + + if (Core.AOS) + { + int physChance = (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitPhysicalArea) * + propertyBonus); + int fireChance = + (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitFireArea) * propertyBonus); + int coldChance = + (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitColdArea) * propertyBonus); + int poisChance = (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitPoisonArea) * + propertyBonus); + int nrgyChance = (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitEnergyArea) * + propertyBonus); + + if (physChance != 0 && physChance > Utility.Random(100)) + DoAreaAttack(attacker, defender, 0x10E, 50, 100, 0, 0, 0, 0); + + if (fireChance != 0 && fireChance > Utility.Random(100)) + DoAreaAttack(attacker, defender, 0x11D, 1160, 0, 100, 0, 0, 0); + + if (coldChance != 0 && coldChance > Utility.Random(100)) + DoAreaAttack(attacker, defender, 0x0FC, 2100, 0, 0, 100, 0, 0); + + if (poisChance != 0 && poisChance > Utility.Random(100)) + DoAreaAttack(attacker, defender, 0x205, 1166, 0, 0, 0, 100, 0); + + if (nrgyChance != 0 && nrgyChance > Utility.Random(100)) + DoAreaAttack(attacker, defender, 0x1F1, 120, 0, 0, 0, 0, 100); + + int maChance = + (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitMagicArrow) * propertyBonus); + int harmChance = (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitHarm) * propertyBonus); + int fireballChance = + (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitFireball) * propertyBonus); + int lightningChance = + (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitLightning) * propertyBonus); + int dispelChance = + (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitDispel) * propertyBonus); + + if (maChance != 0 && maChance > Utility.Random(100)) + DoMagicArrow(attacker, defender); + + if (harmChance != 0 && harmChance > Utility.Random(100)) + DoHarm(attacker, defender); + + if (fireballChance != 0 && fireballChance > Utility.Random(100)) + DoFireball(attacker, defender); + + if (lightningChance != 0 && lightningChance > Utility.Random(100)) + DoLightning(attacker, defender); + + if (dispelChance != 0 && dispelChance > Utility.Random(100)) + DoDispel(attacker, defender); + + int laChance = (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitLowerAttack) * + propertyBonus); + int ldChance = (int)(AosWeaponAttributes.GetValue(attacker, AosWeaponAttribute.HitLowerDefend) * + propertyBonus); + + if (laChance != 0 && laChance > Utility.Random(100)) + DoLowerAttack(attacker, defender); + + if (ldChance != 0 && ldChance > Utility.Random(100)) + DoLowerDefense(attacker, defender); + } + + bcAtt?.OnGaveMeleeAttack(defender); + bcDef?.OnGotMeleeAttack(attacker); + + a?.OnHit(attacker, defender, damage); + move?.OnHit(attacker, defender, damage); + + if (defender is IHonorTarget it) + it.ReceivedHonorContext?.OnTargetHit(attacker); + + if (!(this is BaseRanged)) + { + if (AnimalForm.UnderTransformation(attacker, typeof(GiantSerpent))) + defender.ApplyPoison(attacker, Poison.Lesser); + + if (AnimalForm.UnderTransformation(defender, typeof(BullFrog))) + attacker.ApplyPoison(defender, Poison.Regular); + } + } + + public virtual double GetAosDamage(Mobile attacker, int bonus, int dice, int sides) + { + int damage = Utility.Dice(dice, sides, bonus) * 100; + int damageBonus = 0; + + // Inscription bonus + int inscribeSkill = attacker.Skills[SkillName.Inscribe].Fixed; + + damageBonus += inscribeSkill / 200; + + if (inscribeSkill >= 1000) + damageBonus += 5; + + if (attacker.Player) + { + // Int bonus + damageBonus += attacker.Int / 10; + + // SDI bonus + damageBonus += AosAttributes.GetValue(attacker, AosAttribute.SpellDamage); + + TransformContext context = TransformationSpellHelper.GetContext(attacker); + + if (context?.Spell is ReaperFormSpell spell) + damageBonus += spell.SpellDamageBonus; + } + + damage = AOS.Scale(damage, 100 + damageBonus); + + return damage / 100; + } + + public virtual CheckSlayerResult CheckSlayers(Mobile attacker, Mobile defender) + { + BaseWeapon atkWeapon = attacker.Weapon as BaseWeapon; + SlayerEntry atkSlayer = SlayerGroup.GetEntryByName(atkWeapon.Slayer); + SlayerEntry atkSlayer2 = SlayerGroup.GetEntryByName(atkWeapon.Slayer2); + + if (atkWeapon is ButchersWarCleaver && TalismanSlayer.Slays(TalismanSlayerName.Bovine, defender)) + return CheckSlayerResult.Slayer; + + if (atkSlayer != null && atkSlayer.Slays(defender) || atkSlayer2 != null && atkSlayer2.Slays(defender)) + return CheckSlayerResult.Slayer; + + if (attacker.Talisman is BaseTalisman talisman && TalismanSlayer.Slays(talisman.Slayer, defender)) + return CheckSlayerResult.Slayer; + + if (!Core.SE) + { + ISlayer defISlayer = Spellbook.FindEquippedSpellbook(defender); + + if (defISlayer == null) + defISlayer = defender.Weapon as ISlayer; - List list = new List(); - - int range = Core.ML ? 5 : 10; - - IPooledEnumerable eable = from.GetMobilesInRange(range); - foreach ( Mobile m in eable ) - { - if ( from != m && defender != m && SpellHelper.ValidIndirectTarget( from, m ) && from.CanBeHarmful( m, false ) && ( !Core.ML || from.InLOS( m ) ) ) - list.Add( m ); - } - eable.Free(); - - if ( list.Count == 0 ) - return; - - Effects.PlaySound( from.Location, map, sound ); - - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = list[i]; - - double scalar = Core.ML ? 1.0 : ( 11 - from.GetDistanceToSqrt( m ) ) / 10; - double damage = GetBaseDamage( from ); - - if (scalar <= 0) - { - continue; - } - - if ( scalar < 1.0 ) - { - damage *= ( 11 - from.GetDistanceToSqrt( m ) ) / 10; - } - - from.DoHarmful( m, true ); - m.FixedEffect( 0x3779, 1, 15, hue, 0 ); - AOS.Damage(m, from, (int)damage, phys, fire, cold, pois, nrgy); - } - } - #endregion - - public virtual CheckSlayerResult CheckSlayers( Mobile attacker, Mobile defender ) - { - BaseWeapon atkWeapon = attacker.Weapon as BaseWeapon; - SlayerEntry atkSlayer = SlayerGroup.GetEntryByName( atkWeapon.Slayer ); - SlayerEntry atkSlayer2 = SlayerGroup.GetEntryByName( atkWeapon.Slayer2 ); - - if ( atkWeapon is ButchersWarCleaver && TalismanSlayer.Slays( TalismanSlayerName.Bovine, defender ) ) - return CheckSlayerResult.Slayer; - - if ( atkSlayer != null && atkSlayer.Slays( defender ) || atkSlayer2 != null && atkSlayer2.Slays( defender ) ) - return CheckSlayerResult.Slayer; - - if ( attacker.Talisman is BaseTalisman talisman && TalismanSlayer.Slays( talisman.Slayer, defender ) ) - return CheckSlayerResult.Slayer; - - if ( !Core.SE ) - { - ISlayer defISlayer = Spellbook.FindEquippedSpellbook( defender ); - - if ( defISlayer == null ) - defISlayer = defender.Weapon as ISlayer; - - if ( defISlayer != null ) - { - SlayerEntry defSlayer = SlayerGroup.GetEntryByName( defISlayer.Slayer ); - SlayerEntry defSlayer2 = SlayerGroup.GetEntryByName( defISlayer.Slayer2 ); - - if ( defSlayer != null && defSlayer.Group.OppositionSuperSlays( attacker ) || defSlayer2 != null && defSlayer2.Group.OppositionSuperSlays( attacker ) ) - return CheckSlayerResult.Opposition; - } - } - - return CheckSlayerResult.None; - } - - public virtual void AddBlood( Mobile attacker, Mobile defender, int damage ) - { - if ( damage > 0 ) - { - new Blood().MoveToWorld( defender.Location, defender.Map ); - - int extraBlood = (Core.SE ? Utility.RandomMinMax( 3, 4 ) : Utility.RandomMinMax( 0, 1 ) ); - - for( int i = 0; i < extraBlood; i++ ) - { - new Blood().MoveToWorld( new Point3D( - defender.X + Utility.RandomMinMax( -1, 1 ), - defender.Y + Utility.RandomMinMax( -1, 1 ), - defender.Z ), defender.Map ); - } - } - } - - public virtual void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - if ( wielder is BaseCreature bc ) - { - phys = bc.PhysicalDamage; - fire = bc.FireDamage; - cold = bc.ColdDamage; - pois = bc.PoisonDamage; - nrgy = bc.EnergyDamage; - chaos = bc.ChaosDamage; - direct = bc.DirectDamage; - } - else - { - fire = m_AosElementDamages.Fire; - cold = m_AosElementDamages.Cold; - pois = m_AosElementDamages.Poison; - nrgy = m_AosElementDamages.Energy; - chaos = m_AosElementDamages.Chaos; - direct = m_AosElementDamages.Direct; - - phys = 100 - fire - cold - pois - nrgy - chaos - direct; - - CraftAttributeInfo attrInfo = CraftResources.GetInfo( m_Resource )?.AttributeInfo; - - if ( attrInfo != null ) - { - int left = phys; - - left = ApplyCraftAttributeElementDamage( attrInfo.WeaponColdDamage, ref cold, left ); - left = ApplyCraftAttributeElementDamage( attrInfo.WeaponEnergyDamage, ref nrgy, left ); - left = ApplyCraftAttributeElementDamage( attrInfo.WeaponFireDamage, ref fire, left ); - left = ApplyCraftAttributeElementDamage( attrInfo.WeaponPoisonDamage, ref pois, left ); - left = ApplyCraftAttributeElementDamage( attrInfo.WeaponChaosDamage, ref chaos, left ); - left = ApplyCraftAttributeElementDamage( attrInfo.WeaponDirectDamage, ref direct, left ); - - phys = left; - } - } - } - - private int ApplyCraftAttributeElementDamage( int attrDamage, ref int element, int totalRemaining ) - { - if ( totalRemaining <= 0 ) - return 0; - - if ( attrDamage <= 0 ) - return totalRemaining; - - int appliedDamage = attrDamage; - - if ( (appliedDamage + element) > 100 ) - appliedDamage = 100 - element; - - if ( appliedDamage > totalRemaining ) - appliedDamage = totalRemaining; - - element += appliedDamage; - - return totalRemaining - appliedDamage; - } - - public virtual void OnMiss( Mobile attacker, Mobile defender ) - { - PlaySwingAnimation( attacker ); - attacker.PlaySound( GetMissAttackSound( attacker, defender ) ); - defender.PlaySound( GetMissDefendSound( attacker, defender ) ); - - WeaponAbility ability = WeaponAbility.GetCurrentAbility( attacker ); - - ability?.OnMiss( attacker, defender ); - - SpecialMove move = SpecialMove.GetCurrentMove( attacker ); - - move?.OnMiss( attacker, defender ); - - if ( defender is IHonorTarget target ) - { - target.ReceivedHonorContext?.OnTargetMissed( attacker ); - } - } - - public virtual void GetBaseDamageRange( Mobile attacker, out int min, out int max ) - { - if ( attacker is BaseCreature c ) - { - if ( c.DamageMin >= 0 ) - { - min = c.DamageMin; - max = c.DamageMax; - return; - } - - if ( this is Fists && !c.Body.IsHuman ) - { - min = c.Str / 28; - max = c.Str / 28; - return; - } - } - - min = MinDamage; - max = MaxDamage; - } - - public virtual double GetBaseDamage( Mobile attacker ) - { - GetBaseDamageRange( attacker, out int min, out int max ); - - int damage = Utility.RandomMinMax( min, max ); - - if ( Core.AOS ) return damage; - - /* Apply damage level offset - * : Regular : 0 - * : Ruin : 1 - * : Might : 3 - * : Force : 5 - * : Power : 7 - * : Vanq : 9 - */ - if ( m_DamageLevel != WeaponDamageLevel.Regular ) - damage += (2 * (int)m_DamageLevel) - 1; - - return damage; - } - - public virtual double GetBonus( double value, double scalar, double threshold, double offset ) - { - double bonus = value * scalar; - - if ( value >= threshold ) - bonus += offset; - - return bonus / 100; - } - - public virtual int GetHitChanceBonus() - { - if ( !Core.AOS ) - return 0; - - int bonus = 0; - - switch ( m_AccuracyLevel ) - { - case WeaponAccuracyLevel.Accurate: bonus += 02; break; - case WeaponAccuracyLevel.Surpassingly: bonus += 04; break; - case WeaponAccuracyLevel.Eminently: bonus += 06; break; - case WeaponAccuracyLevel.Exceedingly: bonus += 08; break; - case WeaponAccuracyLevel.Supremely: bonus += 10; break; - } - - return bonus; - } - - public virtual int GetDamageBonus() - { - int bonus = VirtualDamageBonus; - - switch ( m_Quality ) - { - case WeaponQuality.Low: bonus -= 20; break; - case WeaponQuality.Exceptional: bonus += 20; break; - } - - switch ( m_DamageLevel ) - { - case WeaponDamageLevel.Ruin: bonus += 15; break; - case WeaponDamageLevel.Might: bonus += 20; break; - case WeaponDamageLevel.Force: bonus += 25; break; - case WeaponDamageLevel.Power: bonus += 30; break; - case WeaponDamageLevel.Vanq: bonus += 35; break; - } - - return bonus; - } - - public virtual void GetStatusDamage( Mobile from, out int min, out int max ) - { - GetBaseDamageRange( from, out int baseMin, out int baseMax ); - - if ( Core.AOS ) - { - min = Math.Max( (int)ScaleDamageAOS( from, baseMin, false ), 1 ); - max = Math.Max( (int)ScaleDamageAOS( from, baseMax, false ), 1 ); - } - else - { - min = Math.Max( (int)ScaleDamageOld( from, baseMin, false ), 1 ); - max = Math.Max( (int)ScaleDamageOld( from, baseMax, false ), 1 ); - } - } - - public virtual double ScaleDamageAOS( Mobile attacker, double damage, bool checkSkills ) - { - if ( checkSkills ) - { - attacker.CheckSkill( SkillName.Tactics, 0.0, attacker.Skills[SkillName.Tactics].Cap ); // Passively check tactics for gain - attacker.CheckSkill( SkillName.Anatomy, 0.0, attacker.Skills[SkillName.Anatomy].Cap ); // Passively check Anatomy for gain - - if ( Type == WeaponType.Axe ) - attacker.CheckSkill( SkillName.Lumberjacking, 0.0, 100.0 ); // Passively check Lumberjacking for gain - } - - #region Physical bonuses - /* - * These are the bonuses given by the physical characteristics of the mobile. - * No caps apply. - */ - double strengthBonus = GetBonus( attacker.Str, 0.300, 100.0, 5.00 ); - double anatomyBonus = GetBonus( attacker.Skills[SkillName.Anatomy].Value, 0.500, 100.0, 5.00 ); - double tacticsBonus = GetBonus( attacker.Skills[SkillName.Tactics].Value, 0.625, 100.0, 6.25 ); - double lumberBonus = GetBonus( attacker.Skills[SkillName.Lumberjacking].Value, 0.200, 100.0, 10.00 ); - - if ( Type != WeaponType.Axe ) - lumberBonus = 0.0; - #endregion - - #region Modifiers - /* - * The following are damage modifiers whose effect shows on the status bar. - * Capped at 100% total. - */ - int damageBonus = AosAttributes.GetValue( attacker, AosAttribute.WeaponDamage ); - - // Horrific Beast transformation gives a +25% bonus to damage. - if ( TransformationSpellHelper.UnderTransformation( attacker, typeof( HorrificBeastSpell ) ) ) - damageBonus += 25; - - // Divine Fury gives a +10% bonus to damage. - if ( Spells.Chivalry.DivineFurySpell.UnderEffect( attacker ) ) - damageBonus += 10; - - int defenseMasteryMalus = 0; - - // Defense Mastery gives a -50%/-80% malus to damage. - if ( DefenseMastery.GetMalus( attacker, ref defenseMasteryMalus ) ) - damageBonus -= defenseMasteryMalus; - - int discordanceEffect = 0; - - // Discordance gives a -2%/-48% malus to damage. - if ( SkillHandlers.Discordance.GetEffect( attacker, ref discordanceEffect ) ) - damageBonus -= discordanceEffect * 2; - - if ( damageBonus > 100 ) - damageBonus = 100; - #endregion - - double totalBonus = strengthBonus + anatomyBonus + tacticsBonus + lumberBonus + ((double)(GetDamageBonus() + damageBonus) / 100.0); - - return damage + (int)(damage * totalBonus); - } - - public virtual int VirtualDamageBonus => 0; - - public virtual int ComputeDamageAOS( Mobile attacker, Mobile defender ) - { - return (int)ScaleDamageAOS( attacker, GetBaseDamage( attacker ), true ); - } - - public virtual double ScaleDamageOld( Mobile attacker, double damage, bool checkSkills ) - { - if ( checkSkills ) - { - attacker.CheckSkill( SkillName.Tactics, 0.0, attacker.Skills[SkillName.Tactics].Cap ); // Passively check tactics for gain - attacker.CheckSkill( SkillName.Anatomy, 0.0, attacker.Skills[SkillName.Anatomy].Cap ); // Passively check Anatomy for gain - - if ( Type == WeaponType.Axe ) - attacker.CheckSkill( SkillName.Lumberjacking, 0.0, 100.0 ); // Passively check Lumberjacking for gain - } - - /* Compute tactics modifier - * : 0.0 = 50% loss - * : 50.0 = unchanged - * : 100.0 = 50% bonus - */ - damage += ( damage * ( ( attacker.Skills[SkillName.Tactics].Value - 50.0 ) / 100.0 ) ); - - - /* Compute strength modifier - * : 1% bonus for every 5 strength - */ - double modifiers = ( attacker.Str / 5.0 ) / 100.0; - - /* Compute anatomy modifier - * : 1% bonus for every 5 points of anatomy - * : +10% bonus at Grandmaster or higher - */ - double anatomyValue = attacker.Skills[SkillName.Anatomy].Value; - modifiers += ( ( anatomyValue / 5.0 ) / 100.0 ); - - if ( anatomyValue >= 100.0 ) - modifiers += 0.1; - - /* Compute lumberjacking bonus - * : 1% bonus for every 5 points of lumberjacking - * : +10% bonus at Grandmaster or higher - */ - if ( Type == WeaponType.Axe ) - { - double lumberValue = attacker.Skills[SkillName.Lumberjacking].Value; - - modifiers += ( ( lumberValue / 5.0 ) / 100.0 ); - - if ( lumberValue >= 100.0 ) - modifiers += 0.1; - } - - // New quality bonus: - if ( m_Quality != WeaponQuality.Regular ) - modifiers += ( ( (int)m_Quality - 1 ) * 0.2 ); - - // Virtual damage bonus: - if ( VirtualDamageBonus != 0 ) - modifiers += ( VirtualDamageBonus / 100.0 ); - - // Apply bonuses - damage += ( damage * modifiers ); - - return ScaleDamageByDurability( (int)damage ); - } - - public virtual int ScaleDamageByDurability( int damage ) - { - int scale = 100; - - if ( m_MaxHits > 0 && m_Hits < m_MaxHits ) - scale = 50 + ((50 * m_Hits) / m_MaxHits); - - return AOS.Scale( damage, scale ); - } - - public virtual int ComputeDamage( Mobile attacker, Mobile defender ) - { - if ( Core.AOS ) - return ComputeDamageAOS( attacker, defender ); - - int damage = (int)ScaleDamageOld( attacker, GetBaseDamage( attacker ), true ); - - // pre-AOS, halve damage if the defender is a player or the attacker is not a player - if ( defender is PlayerMobile || !( attacker is PlayerMobile ) ) - damage = (int)(damage / 2.0); - - return damage; - } - - public virtual void PlayHurtAnimation( Mobile from ) - { - int action; - int frames; - - switch ( from.Body.Type ) - { - case BodyType.Sea: - case BodyType.Animal: - { - action = 7; - frames = 5; - break; - } - case BodyType.Monster: - { - action = 10; - frames = 4; - break; - } - case BodyType.Human: - { - action = 20; - frames = 5; - break; - } - default: return; - } - - if ( from.Mounted ) - return; - - from.Animate( action, frames, 1, true, false, 0 ); - } - - public virtual void PlaySwingAnimation( Mobile from ) - { - int action; - - switch ( from.Body.Type ) - { - case BodyType.Sea: - case BodyType.Animal: - { - action = Utility.Random( 5, 2 ); - break; - } - case BodyType.Monster: - { - switch ( Animation ) - { - default: - case WeaponAnimation.Wrestle: - case WeaponAnimation.Bash1H: - case WeaponAnimation.Pierce1H: - case WeaponAnimation.Slash1H: - case WeaponAnimation.Bash2H: - case WeaponAnimation.Pierce2H: - case WeaponAnimation.Slash2H: action = Utility.Random( 4, 3 ); break; - case WeaponAnimation.ShootBow: return; // 7 - case WeaponAnimation.ShootXBow: return; // 8 - } - - break; - } - case BodyType.Human: - { - if ( !from.Mounted ) - { - action = (int)Animation; - } - else - { - switch ( Animation ) - { - default: - case WeaponAnimation.Wrestle: - case WeaponAnimation.Bash1H: - case WeaponAnimation.Pierce1H: - case WeaponAnimation.Slash1H: action = 26; break; - case WeaponAnimation.Bash2H: - case WeaponAnimation.Pierce2H: - case WeaponAnimation.Slash2H: action = 29; break; - case WeaponAnimation.ShootBow: action = 27; break; - case WeaponAnimation.ShootXBow: action = 28; break; - } - } - - break; - } - default: return; - } - - from.Animate( action, 7, 1, true, false, 0 ); - } - - #region Serialization/Deserialization - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } - - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 9 ); // version - - SaveFlag flags = SaveFlag.None; - - SetSaveFlag( ref flags, SaveFlag.DamageLevel, m_DamageLevel != WeaponDamageLevel.Regular ); - SetSaveFlag( ref flags, SaveFlag.AccuracyLevel, m_AccuracyLevel != WeaponAccuracyLevel.Regular ); - SetSaveFlag( ref flags, SaveFlag.DurabilityLevel, m_DurabilityLevel != WeaponDurabilityLevel.Regular ); - SetSaveFlag( ref flags, SaveFlag.Quality, m_Quality != WeaponQuality.Regular ); - SetSaveFlag( ref flags, SaveFlag.Hits, m_Hits != 0 ); - SetSaveFlag( ref flags, SaveFlag.MaxHits, m_MaxHits != 0 ); - SetSaveFlag( ref flags, SaveFlag.Slayer, m_Slayer != SlayerName.None ); - SetSaveFlag( ref flags, SaveFlag.Poison, m_Poison != null ); - SetSaveFlag( ref flags, SaveFlag.PoisonCharges, m_PoisonCharges != 0 ); - SetSaveFlag( ref flags, SaveFlag.Crafter, m_Crafter != null ); - SetSaveFlag( ref flags, SaveFlag.Identified, m_Identified ); - SetSaveFlag( ref flags, SaveFlag.StrReq, m_StrReq != -1 ); - SetSaveFlag( ref flags, SaveFlag.DexReq, m_DexReq != -1 ); - SetSaveFlag( ref flags, SaveFlag.IntReq, m_IntReq != -1 ); - SetSaveFlag( ref flags, SaveFlag.MinDamage, m_MinDamage != -1 ); - SetSaveFlag( ref flags, SaveFlag.MaxDamage, m_MaxDamage != -1 ); - SetSaveFlag( ref flags, SaveFlag.HitSound, m_HitSound != -1 ); - SetSaveFlag( ref flags, SaveFlag.MissSound, m_MissSound != -1 ); - SetSaveFlag( ref flags, SaveFlag.Speed, m_Speed != -1 ); - SetSaveFlag( ref flags, SaveFlag.MaxRange, m_MaxRange != -1 ); - SetSaveFlag( ref flags, SaveFlag.Skill, m_Skill != (SkillName)(-1) ); - SetSaveFlag( ref flags, SaveFlag.Type, m_Type != (WeaponType)(-1) ); - SetSaveFlag( ref flags, SaveFlag.Animation, m_Animation != (WeaponAnimation)(-1) ); - SetSaveFlag( ref flags, SaveFlag.Resource, m_Resource != CraftResource.Iron ); - SetSaveFlag( ref flags, SaveFlag.xAttributes, !m_AosAttributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.xWeaponAttributes, !m_AosWeaponAttributes.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.PlayerConstructed, PlayerConstructed ); - SetSaveFlag( ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.Slayer2, m_Slayer2 != SlayerName.None ); - SetSaveFlag( ref flags, SaveFlag.ElementalDamages, !m_AosElementDamages.IsEmpty ); - SetSaveFlag( ref flags, SaveFlag.EngravedText, !string.IsNullOrEmpty( m_EngravedText ) ); - - writer.Write( (int) flags ); - - if ( GetSaveFlag( flags, SaveFlag.DamageLevel ) ) - writer.Write( (int) m_DamageLevel ); - - if ( GetSaveFlag( flags, SaveFlag.AccuracyLevel ) ) - writer.Write( (int) m_AccuracyLevel ); - - if ( GetSaveFlag( flags, SaveFlag.DurabilityLevel ) ) - writer.Write( (int) m_DurabilityLevel ); - - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - writer.Write( (int) m_Quality ); - - if ( GetSaveFlag( flags, SaveFlag.Hits ) ) - writer.Write( (int) m_Hits ); - - if ( GetSaveFlag( flags, SaveFlag.MaxHits ) ) - writer.Write( (int) m_MaxHits ); - - if ( GetSaveFlag( flags, SaveFlag.Slayer ) ) - writer.Write( (int) m_Slayer ); - - if ( GetSaveFlag( flags, SaveFlag.Poison ) ) - Poison.Serialize( m_Poison, writer ); - - if ( GetSaveFlag( flags, SaveFlag.PoisonCharges ) ) - writer.Write( (int) m_PoisonCharges ); - - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - writer.Write( (Mobile) m_Crafter ); - - if ( GetSaveFlag( flags, SaveFlag.StrReq ) ) - writer.Write( (int) m_StrReq ); - - if ( GetSaveFlag( flags, SaveFlag.DexReq ) ) - writer.Write( (int) m_DexReq ); - - if ( GetSaveFlag( flags, SaveFlag.IntReq ) ) - writer.Write( (int) m_IntReq ); - - if ( GetSaveFlag( flags, SaveFlag.MinDamage ) ) - writer.Write( (int) m_MinDamage ); - - if ( GetSaveFlag( flags, SaveFlag.MaxDamage ) ) - writer.Write( (int) m_MaxDamage ); - - if ( GetSaveFlag( flags, SaveFlag.HitSound ) ) - writer.Write( (int) m_HitSound ); - - if ( GetSaveFlag( flags, SaveFlag.MissSound ) ) - writer.Write( (int) m_MissSound ); - - if ( GetSaveFlag( flags, SaveFlag.Speed ) ) - writer.Write( (float) m_Speed ); - - if ( GetSaveFlag( flags, SaveFlag.MaxRange ) ) - writer.Write( (int) m_MaxRange ); - - if ( GetSaveFlag( flags, SaveFlag.Skill ) ) - writer.Write( (int) m_Skill ); - - if ( GetSaveFlag( flags, SaveFlag.Type ) ) - writer.Write( (int) m_Type ); - - if ( GetSaveFlag( flags, SaveFlag.Animation ) ) - writer.Write( (int) m_Animation ); - - if ( GetSaveFlag( flags, SaveFlag.Resource ) ) - writer.Write( (int) m_Resource ); - - if ( GetSaveFlag( flags, SaveFlag.xAttributes ) ) - m_AosAttributes.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.xWeaponAttributes ) ) - m_AosWeaponAttributes.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.SkillBonuses ) ) - m_AosSkillBonuses.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.Slayer2 ) ) - writer.Write( (int)m_Slayer2 ); - - if ( GetSaveFlag( flags, SaveFlag.ElementalDamages ) ) - m_AosElementDamages.Serialize( writer ); - - if ( GetSaveFlag( flags, SaveFlag.EngravedText ) ) - writer.Write( (string) m_EngravedText ); - } - - [Flags] - private enum SaveFlag - { - None = 0x00000000, - DamageLevel = 0x00000001, - AccuracyLevel = 0x00000002, - DurabilityLevel = 0x00000004, - Quality = 0x00000008, - Hits = 0x00000010, - MaxHits = 0x00000020, - Slayer = 0x00000040, - Poison = 0x00000080, - PoisonCharges = 0x00000100, - Crafter = 0x00000200, - Identified = 0x00000400, - StrReq = 0x00000800, - DexReq = 0x00001000, - IntReq = 0x00002000, - MinDamage = 0x00004000, - MaxDamage = 0x00008000, - HitSound = 0x00010000, - MissSound = 0x00020000, - Speed = 0x00040000, - MaxRange = 0x00080000, - Skill = 0x00100000, - Type = 0x00200000, - Animation = 0x00400000, - Resource = 0x00800000, - xAttributes = 0x01000000, - xWeaponAttributes = 0x02000000, - PlayerConstructed = 0x04000000, - SkillBonuses = 0x08000000, - Slayer2 = 0x10000000, - ElementalDamages = 0x20000000, - EngravedText = 0x40000000 - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Mobile parentMobile = Parent as Mobile; - - switch ( version ) - { - case 9: - case 8: - case 7: - case 6: - case 5: - { - SaveFlag flags = (SaveFlag)reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.DamageLevel ) ) - { - m_DamageLevel = (WeaponDamageLevel)reader.ReadInt(); - - if ( m_DamageLevel > WeaponDamageLevel.Vanq ) - m_DamageLevel = WeaponDamageLevel.Ruin; - } - - if ( GetSaveFlag( flags, SaveFlag.AccuracyLevel ) ) - { - m_AccuracyLevel = (WeaponAccuracyLevel)reader.ReadInt(); - - if ( m_AccuracyLevel > WeaponAccuracyLevel.Supremely ) - m_AccuracyLevel = WeaponAccuracyLevel.Accurate; - } - - if ( GetSaveFlag( flags, SaveFlag.DurabilityLevel ) ) - { - m_DurabilityLevel = (WeaponDurabilityLevel)reader.ReadInt(); - - if ( m_DurabilityLevel > WeaponDurabilityLevel.Indestructible ) - m_DurabilityLevel = WeaponDurabilityLevel.Durable; - } - - if ( GetSaveFlag( flags, SaveFlag.Quality ) ) - m_Quality = (WeaponQuality)reader.ReadInt(); - else - m_Quality = WeaponQuality.Regular; - - if ( GetSaveFlag( flags, SaveFlag.Hits ) ) - m_Hits = reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.MaxHits ) ) - m_MaxHits = reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.Slayer ) ) - m_Slayer = (SlayerName)reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.Poison ) ) - m_Poison = Poison.Deserialize( reader ); - - if ( GetSaveFlag( flags, SaveFlag.PoisonCharges ) ) - m_PoisonCharges = reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.Crafter ) ) - m_Crafter = reader.ReadMobile(); - - if ( GetSaveFlag( flags, SaveFlag.Identified ) ) - m_Identified = ( version >= 6 || reader.ReadBool() ); - - if ( GetSaveFlag( flags, SaveFlag.StrReq ) ) - m_StrReq = reader.ReadInt(); - else - m_StrReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.DexReq ) ) - m_DexReq = reader.ReadInt(); - else - m_DexReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.IntReq ) ) - m_IntReq = reader.ReadInt(); - else - m_IntReq = -1; - - if ( GetSaveFlag( flags, SaveFlag.MinDamage ) ) - m_MinDamage = reader.ReadInt(); - else - m_MinDamage = -1; - - if ( GetSaveFlag( flags, SaveFlag.MaxDamage ) ) - m_MaxDamage = reader.ReadInt(); - else - m_MaxDamage = -1; - - if ( GetSaveFlag( flags, SaveFlag.HitSound ) ) - m_HitSound = reader.ReadInt(); - else - m_HitSound = -1; - - if ( GetSaveFlag( flags, SaveFlag.MissSound ) ) - m_MissSound = reader.ReadInt(); - else - m_MissSound = -1; - - if ( GetSaveFlag( flags, SaveFlag.Speed ) ) - { - if ( version < 9 ) - m_Speed = reader.ReadInt(); - else - m_Speed = reader.ReadFloat(); - } - else - m_Speed = -1; - - if ( GetSaveFlag( flags, SaveFlag.MaxRange ) ) - m_MaxRange = reader.ReadInt(); - else - m_MaxRange = -1; - - if ( GetSaveFlag( flags, SaveFlag.Skill ) ) - m_Skill = (SkillName)reader.ReadInt(); - else - m_Skill = (SkillName)(-1); - - if ( GetSaveFlag( flags, SaveFlag.Type ) ) - m_Type = (WeaponType)reader.ReadInt(); - else - m_Type = (WeaponType)(-1); - - if ( GetSaveFlag( flags, SaveFlag.Animation ) ) - m_Animation = (WeaponAnimation)reader.ReadInt(); - else - m_Animation = (WeaponAnimation)(-1); - - if ( GetSaveFlag( flags, SaveFlag.Resource ) ) - m_Resource = (CraftResource)reader.ReadInt(); - else - m_Resource = CraftResource.Iron; - - if ( GetSaveFlag( flags, SaveFlag.xAttributes ) ) - m_AosAttributes = new AosAttributes( this, reader ); - else - m_AosAttributes = new AosAttributes( this ); - - if ( GetSaveFlag( flags, SaveFlag.xWeaponAttributes ) ) - m_AosWeaponAttributes = new AosWeaponAttributes( this, reader ); - else - m_AosWeaponAttributes = new AosWeaponAttributes( this ); - - if ( UseSkillMod && m_AccuracyLevel != WeaponAccuracyLevel.Regular && parentMobile != null ) - { - m_SkillMod = new DefaultSkillMod( AccuracySkill, true, (int)m_AccuracyLevel * 5 ); - parentMobile.AddSkillMod( m_SkillMod ); - } - - if ( version < 7 && m_AosWeaponAttributes.MageWeapon != 0 ) - m_AosWeaponAttributes.MageWeapon = 30 - m_AosWeaponAttributes.MageWeapon; - - if ( Core.AOS && m_AosWeaponAttributes.MageWeapon != 0 && m_AosWeaponAttributes.MageWeapon != 30 && parentMobile != null ) - { - m_MageMod = new DefaultSkillMod( SkillName.Magery, true, -30 + m_AosWeaponAttributes.MageWeapon ); - parentMobile.AddSkillMod( m_MageMod ); - } - - if ( GetSaveFlag( flags, SaveFlag.PlayerConstructed ) ) - PlayerConstructed = true; - - if ( GetSaveFlag( flags, SaveFlag.SkillBonuses ) ) - m_AosSkillBonuses = new AosSkillBonuses( this, reader ); - else - m_AosSkillBonuses = new AosSkillBonuses( this ); - - if ( GetSaveFlag( flags, SaveFlag.Slayer2 ) ) - m_Slayer2 = (SlayerName)reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.ElementalDamages ) ) - m_AosElementDamages = new AosElementAttributes( this, reader ); - else - m_AosElementDamages = new AosElementAttributes( this ); - - if ( GetSaveFlag( flags, SaveFlag.EngravedText ) ) - m_EngravedText = reader.ReadString(); - - break; - } - case 4: - { - m_Slayer = (SlayerName)reader.ReadInt(); - - goto case 3; - } - case 3: - { - m_StrReq = reader.ReadInt(); - m_DexReq = reader.ReadInt(); - m_IntReq = reader.ReadInt(); - - goto case 2; - } - case 2: - { - m_Identified = reader.ReadBool(); - - goto case 1; - } - case 1: - { - m_MaxRange = reader.ReadInt(); - - goto case 0; - } - case 0: - { - if ( version == 0 ) - m_MaxRange = 1; // default - - if ( version < 5 ) - { - m_Resource = CraftResource.Iron; - m_AosAttributes = new AosAttributes( this ); - m_AosWeaponAttributes = new AosWeaponAttributes( this ); - m_AosElementDamages = new AosElementAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - } - - m_MinDamage = reader.ReadInt(); - m_MaxDamage = reader.ReadInt(); - - m_Speed = reader.ReadInt(); - - m_HitSound = reader.ReadInt(); - m_MissSound = reader.ReadInt(); - - m_Skill = (SkillName)reader.ReadInt(); - m_Type = (WeaponType)reader.ReadInt(); - m_Animation = (WeaponAnimation)reader.ReadInt(); - m_DamageLevel = (WeaponDamageLevel)reader.ReadInt(); - m_AccuracyLevel = (WeaponAccuracyLevel)reader.ReadInt(); - m_DurabilityLevel = (WeaponDurabilityLevel)reader.ReadInt(); - m_Quality = (WeaponQuality)reader.ReadInt(); - - m_Crafter = reader.ReadMobile(); - - m_Poison = Poison.Deserialize( reader ); - m_PoisonCharges = reader.ReadInt(); - - if ( m_StrReq == OldStrengthReq ) - m_StrReq = -1; - - if ( m_DexReq == OldDexterityReq ) - m_DexReq = -1; - - if ( m_IntReq == OldIntelligenceReq ) - m_IntReq = -1; - - if ( m_MinDamage == OldMinDamage ) - m_MinDamage = -1; - - if ( m_MaxDamage == OldMaxDamage ) - m_MaxDamage = -1; - - if ( m_HitSound == OldHitSound ) - m_HitSound = -1; - - if ( m_MissSound == OldMissSound ) - m_MissSound = -1; - - if ( m_Speed == OldSpeed ) - m_Speed = -1; - - if ( m_MaxRange == OldMaxRange ) - m_MaxRange = -1; - - if ( m_Skill == OldSkill ) - m_Skill = (SkillName)(-1); - - if ( m_Type == OldType ) - m_Type = (WeaponType)(-1); - - if ( m_Animation == OldAnimation ) - m_Animation = (WeaponAnimation)(-1); - - if ( UseSkillMod && m_AccuracyLevel != WeaponAccuracyLevel.Regular && parentMobile != null ) - { - m_SkillMod = new DefaultSkillMod( AccuracySkill, true, (int)m_AccuracyLevel * 5); - parentMobile.AddSkillMod( m_SkillMod ); - } - - break; - } - } - - if ( Core.AOS && parentMobile != null ) - m_AosSkillBonuses.AddTo( parentMobile ); - - int strBonus = m_AosAttributes.BonusStr; - int dexBonus = m_AosAttributes.BonusDex; - int intBonus = m_AosAttributes.BonusInt; - - if ( parentMobile != null && (strBonus != 0 || dexBonus != 0 || intBonus != 0) ) - { - string modName = Serial.ToString(); - - if ( strBonus != 0 ) - parentMobile.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - parentMobile.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - parentMobile.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - parentMobile?.CheckStatTimers(); - - if ( m_Hits <= 0 && m_MaxHits <= 0 ) - { - m_Hits = m_MaxHits = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - } - - if ( version < 6 ) - PlayerConstructed = true; // we don't know, so, assume it's crafted - } - #endregion - - public BaseWeapon( int itemID ) : base( itemID ) - { - Layer = (Layer)ItemData.Quality; - - m_Quality = WeaponQuality.Regular; - m_StrReq = -1; - m_DexReq = -1; - m_IntReq = -1; - m_MinDamage = -1; - m_MaxDamage = -1; - m_HitSound = -1; - m_MissSound = -1; - m_Speed = -1; - m_MaxRange = -1; - m_Skill = (SkillName)(-1); - m_Type = (WeaponType)(-1); - m_Animation = (WeaponAnimation)(-1); - - m_Hits = m_MaxHits = Utility.RandomMinMax( InitMinHits, InitMaxHits ); - - m_Resource = CraftResource.Iron; - - m_AosAttributes = new AosAttributes( this ); - m_AosWeaponAttributes = new AosWeaponAttributes( this ); - m_AosSkillBonuses = new AosSkillBonuses( this ); - m_AosElementDamages = new AosElementAttributes( this ); - } - - public BaseWeapon( Serial serial ) : base( serial ) - { - } - - private string GetNameString() - { - string name = Name; - - if ( name == null ) - name = $"#{LabelNumber}"; - - return name; - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set{ base.Hue = value; InvalidateProperties(); } - } - - public int GetElementalDamageHue() - { - GetDamageTypes( null, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ); - //Order is Cold, Energy, Fire, Poison, Physical left - - int currentMax = 50; - int hue = 0; - - if ( pois >= currentMax ) - { - hue = 1267 + (pois - 50) / 10; - currentMax = pois; - } - - if ( fire >= currentMax ) - { - hue = 1255 + (fire - 50) / 10; - currentMax = fire; - } - - if ( nrgy >= currentMax ) - { - hue = 1273 + (nrgy - 50) / 10; - currentMax = nrgy; - } - - if ( cold >= currentMax ) - { - hue = 1261 + (cold - 50) / 10; - } - - return hue; - } - - public override void AddNameProperty( ObjectPropertyList list ) - { - int oreType; - - switch ( m_Resource ) - { - case CraftResource.DullCopper: oreType = 1053108; break; // dull copper - case CraftResource.ShadowIron: oreType = 1053107; break; // shadow iron - case CraftResource.Copper: oreType = 1053106; break; // copper - case CraftResource.Bronze: oreType = 1053105; break; // bronze - case CraftResource.Gold: oreType = 1053104; break; // golden - case CraftResource.Agapite: oreType = 1053103; break; // agapite - case CraftResource.Verite: oreType = 1053102; break; // verite - case CraftResource.Valorite: oreType = 1053101; break; // valorite - case CraftResource.SpinedLeather: oreType = 1061118; break; // spined - case CraftResource.HornedLeather: oreType = 1061117; break; // horned - case CraftResource.BarbedLeather: oreType = 1061116; break; // barbed - case CraftResource.RedScales: oreType = 1060814; break; // red - case CraftResource.YellowScales: oreType = 1060818; break; // yellow - case CraftResource.BlackScales: oreType = 1060820; break; // black - case CraftResource.GreenScales: oreType = 1060819; break; // green - case CraftResource.WhiteScales: oreType = 1060821; break; // white - case CraftResource.BlueScales: oreType = 1060815; break; // blue - default: oreType = 0; break; - } - - if ( oreType != 0 ) - list.Add( 1053099, "#{0}\t{1}", oreType, GetNameString() ); // ~1_oretype~ ~2_armortype~ - else if ( Name == null ) - list.Add( LabelNumber ); - else - list.Add( Name ); - - /* - * Want to move this to the engraving tool, let the non-harmful - * formatting show, and remove CLILOCs embedded: more like OSI - * did with the books that had markup, etc. - * - * This will have a negative effect on a few event things imgame - * as is. - * - * If we cant find a more OSI-ish way to clean it up, we can - * easily put this back, and use it in the deserialize - * method and engraving tool, to make it perm cleaned up. - */ - - if ( !string.IsNullOrEmpty( m_EngravedText ) ) - list.Add( 1062613, m_EngravedText ); - - /* list.Add( 1062613, Utility.FixHtml( m_EngravedText ) ); */ - } - - public override bool AllowEquippedCast( Mobile from ) - { - if ( base.AllowEquippedCast( from ) ) - return true; - - return ( m_AosAttributes.SpellChanneling != 0 ); - } - - public virtual int ArtifactRarity => 0; - - public virtual int GetLuckBonus() - { - CraftResourceInfo resInfo = CraftResources.GetInfo( m_Resource ); + if (defISlayer != null) + { + SlayerEntry defSlayer = SlayerGroup.GetEntryByName(defISlayer.Slayer); + SlayerEntry defSlayer2 = SlayerGroup.GetEntryByName(defISlayer.Slayer2); - CraftAttributeInfo attrInfo = resInfo?.AttributeInfo; - - if ( attrInfo == null ) - return 0; + if (defSlayer != null && defSlayer.Group.OppositionSuperSlays(attacker) || + defSlayer2 != null && defSlayer2.Group.OppositionSuperSlays(attacker)) + return CheckSlayerResult.Opposition; + } + } - return attrInfo.WeaponLuck; - } + return CheckSlayerResult.None; + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public virtual void AddBlood(Mobile attacker, Mobile defender, int damage) + { + if (damage > 0) + { + new Blood().MoveToWorld(defender.Location, defender.Map); + + int extraBlood = Core.SE ? Utility.RandomMinMax(3, 4) : Utility.RandomMinMax(0, 1); + + for (int i = 0; i < extraBlood; i++) + new Blood().MoveToWorld(new Point3D( + defender.X + Utility.RandomMinMax(-1, 1), + defender.Y + Utility.RandomMinMax(-1, 1), + defender.Z), defender.Map); + } + } + + public virtual void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + if (wielder is BaseCreature bc) + { + phys = bc.PhysicalDamage; + fire = bc.FireDamage; + cold = bc.ColdDamage; + pois = bc.PoisonDamage; + nrgy = bc.EnergyDamage; + chaos = bc.ChaosDamage; + direct = bc.DirectDamage; + } + else + { + fire = m_AosElementDamages.Fire; + cold = m_AosElementDamages.Cold; + pois = m_AosElementDamages.Poison; + nrgy = m_AosElementDamages.Energy; + chaos = m_AosElementDamages.Chaos; + direct = m_AosElementDamages.Direct; + + phys = 100 - fire - cold - pois - nrgy - chaos - direct; + + CraftAttributeInfo attrInfo = CraftResources.GetInfo(m_Resource)?.AttributeInfo; + + if (attrInfo != null) + { + int left = phys; + + left = ApplyCraftAttributeElementDamage(attrInfo.WeaponColdDamage, ref cold, left); + left = ApplyCraftAttributeElementDamage(attrInfo.WeaponEnergyDamage, ref nrgy, left); + left = ApplyCraftAttributeElementDamage(attrInfo.WeaponFireDamage, ref fire, left); + left = ApplyCraftAttributeElementDamage(attrInfo.WeaponPoisonDamage, ref pois, left); + left = ApplyCraftAttributeElementDamage(attrInfo.WeaponChaosDamage, ref chaos, left); + left = ApplyCraftAttributeElementDamage(attrInfo.WeaponDirectDamage, ref direct, left); + + phys = left; + } + } + } + + private int ApplyCraftAttributeElementDamage(int attrDamage, ref int element, int totalRemaining) + { + if (totalRemaining <= 0) + return 0; + + if (attrDamage <= 0) + return totalRemaining; + + int appliedDamage = attrDamage; + + if (appliedDamage + element > 100) + appliedDamage = 100 - element; + + if (appliedDamage > totalRemaining) + appliedDamage = totalRemaining; + + element += appliedDamage; + + return totalRemaining - appliedDamage; + } + + public virtual void OnMiss(Mobile attacker, Mobile defender) + { + PlaySwingAnimation(attacker); + attacker.PlaySound(GetMissAttackSound(attacker, defender)); + defender.PlaySound(GetMissDefendSound(attacker, defender)); + + WeaponAbility ability = WeaponAbility.GetCurrentAbility(attacker); + + ability?.OnMiss(attacker, defender); + + SpecialMove move = SpecialMove.GetCurrentMove(attacker); + + move?.OnMiss(attacker, defender); + + if (defender is IHonorTarget target) target.ReceivedHonorContext?.OnTargetMissed(attacker); + } + + public virtual void GetBaseDamageRange(Mobile attacker, out int min, out int max) + { + if (attacker is BaseCreature c) + { + if (c.DamageMin >= 0) + { + min = c.DamageMin; + max = c.DamageMax; + return; + } + + if (this is Fists && !c.Body.IsHuman) + { + min = c.Str / 28; + max = c.Str / 28; + return; + } + } + + min = MinDamage; + max = MaxDamage; + } + + public virtual double GetBaseDamage(Mobile attacker) + { + GetBaseDamageRange(attacker, out int min, out int max); + + int damage = Utility.RandomMinMax(min, max); + + if (Core.AOS) return damage; + + /* Apply damage level offset + * : Regular : 0 + * : Ruin : 1 + * : Might : 3 + * : Force : 5 + * : Power : 7 + * : Vanq : 9 + */ + if (m_DamageLevel != WeaponDamageLevel.Regular) + damage += 2 * (int)m_DamageLevel - 1; + + return damage; + } + + public virtual double GetBonus(double value, double scalar, double threshold, double offset) + { + double bonus = value * scalar; + + if (value >= threshold) + bonus += offset; + + return bonus / 100; + } + + public virtual int GetHitChanceBonus() + { + if (!Core.AOS) + return 0; + + int bonus = 0; + + switch (m_AccuracyLevel) + { + case WeaponAccuracyLevel.Accurate: + bonus += 02; + break; + case WeaponAccuracyLevel.Surpassingly: + bonus += 04; + break; + case WeaponAccuracyLevel.Eminently: + bonus += 06; + break; + case WeaponAccuracyLevel.Exceedingly: + bonus += 08; + break; + case WeaponAccuracyLevel.Supremely: + bonus += 10; + break; + } + + return bonus; + } + + public virtual int GetDamageBonus() + { + int bonus = VirtualDamageBonus; + + switch (m_Quality) + { + case WeaponQuality.Low: + bonus -= 20; + break; + case WeaponQuality.Exceptional: + bonus += 20; + break; + } + + switch (m_DamageLevel) + { + case WeaponDamageLevel.Ruin: + bonus += 15; + break; + case WeaponDamageLevel.Might: + bonus += 20; + break; + case WeaponDamageLevel.Force: + bonus += 25; + break; + case WeaponDamageLevel.Power: + bonus += 30; + break; + case WeaponDamageLevel.Vanq: + bonus += 35; + break; + } + + return bonus; + } + + public virtual double ScaleDamageAOS(Mobile attacker, double damage, bool checkSkills) + { + if (checkSkills) + { + attacker.CheckSkill(SkillName.Tactics, 0.0, + attacker.Skills[SkillName.Tactics].Cap); // Passively check tactics for gain + attacker.CheckSkill(SkillName.Anatomy, 0.0, + attacker.Skills[SkillName.Anatomy].Cap); // Passively check Anatomy for gain + + if (Type == WeaponType.Axe) + attacker.CheckSkill(SkillName.Lumberjacking, 0.0, 100.0); // Passively check Lumberjacking for gain + } + + #region Physical bonuses + + /* + * These are the bonuses given by the physical characteristics of the mobile. + * No caps apply. + */ + double strengthBonus = GetBonus(attacker.Str, 0.300, 100.0, 5.00); + double anatomyBonus = GetBonus(attacker.Skills[SkillName.Anatomy].Value, 0.500, 100.0, 5.00); + double tacticsBonus = GetBonus(attacker.Skills[SkillName.Tactics].Value, 0.625, 100.0, 6.25); + double lumberBonus = GetBonus(attacker.Skills[SkillName.Lumberjacking].Value, 0.200, 100.0, 10.00); + + if (Type != WeaponType.Axe) + lumberBonus = 0.0; + + #endregion + + #region Modifiers + + /* + * The following are damage modifiers whose effect shows on the status bar. + * Capped at 100% total. + */ + int damageBonus = AosAttributes.GetValue(attacker, AosAttribute.WeaponDamage); + + // Horrific Beast transformation gives a +25% bonus to damage. + if (TransformationSpellHelper.UnderTransformation(attacker, typeof(HorrificBeastSpell))) + damageBonus += 25; + + // Divine Fury gives a +10% bonus to damage. + if (DivineFurySpell.UnderEffect(attacker)) + damageBonus += 10; + + int defenseMasteryMalus = 0; + + // Defense Mastery gives a -50%/-80% malus to damage. + if (DefenseMastery.GetMalus(attacker, ref defenseMasteryMalus)) + damageBonus -= defenseMasteryMalus; + + int discordanceEffect = 0; + + // Discordance gives a -2%/-48% malus to damage. + if (Discordance.GetEffect(attacker, ref discordanceEffect)) + damageBonus -= discordanceEffect * 2; + + if (damageBonus > 100) + damageBonus = 100; + + #endregion + + double totalBonus = strengthBonus + anatomyBonus + tacticsBonus + lumberBonus + + (GetDamageBonus() + damageBonus) / 100.0; + + return damage + (int)(damage * totalBonus); + } + + public virtual int ComputeDamageAOS(Mobile attacker, Mobile defender) + { + return (int)ScaleDamageAOS(attacker, GetBaseDamage(attacker), true); + } + + public virtual double ScaleDamageOld(Mobile attacker, double damage, bool checkSkills) + { + if (checkSkills) + { + attacker.CheckSkill(SkillName.Tactics, 0.0, + attacker.Skills[SkillName.Tactics].Cap); // Passively check tactics for gain + attacker.CheckSkill(SkillName.Anatomy, 0.0, + attacker.Skills[SkillName.Anatomy].Cap); // Passively check Anatomy for gain + + if (Type == WeaponType.Axe) + attacker.CheckSkill(SkillName.Lumberjacking, 0.0, 100.0); // Passively check Lumberjacking for gain + } + + /* Compute tactics modifier + * : 0.0 = 50% loss + * : 50.0 = unchanged + * : 100.0 = 50% bonus + */ + damage += damage * ((attacker.Skills[SkillName.Tactics].Value - 50.0) / 100.0); + + + /* Compute strength modifier + * : 1% bonus for every 5 strength + */ + double modifiers = attacker.Str / 5.0 / 100.0; + + /* Compute anatomy modifier + * : 1% bonus for every 5 points of anatomy + * : +10% bonus at Grandmaster or higher + */ + double anatomyValue = attacker.Skills[SkillName.Anatomy].Value; + modifiers += anatomyValue / 5.0 / 100.0; + + if (anatomyValue >= 100.0) + modifiers += 0.1; + + /* Compute lumberjacking bonus + * : 1% bonus for every 5 points of lumberjacking + * : +10% bonus at Grandmaster or higher + */ + if (Type == WeaponType.Axe) + { + double lumberValue = attacker.Skills[SkillName.Lumberjacking].Value; + + modifiers += lumberValue / 5.0 / 100.0; + + if (lumberValue >= 100.0) + modifiers += 0.1; + } + + // New quality bonus: + if (m_Quality != WeaponQuality.Regular) + modifiers += ((int)m_Quality - 1) * 0.2; + + // Virtual damage bonus: + if (VirtualDamageBonus != 0) + modifiers += VirtualDamageBonus / 100.0; + + // Apply bonuses + damage += damage * modifiers; + + return ScaleDamageByDurability((int)damage); + } + + public virtual int ScaleDamageByDurability(int damage) + { + int scale = 100; + + if (m_MaxHits > 0 && m_Hits < m_MaxHits) + scale = 50 + 50 * m_Hits / m_MaxHits; + + return AOS.Scale(damage, scale); + } + + public virtual int ComputeDamage(Mobile attacker, Mobile defender) + { + if (Core.AOS) + return ComputeDamageAOS(attacker, defender); + + int damage = (int)ScaleDamageOld(attacker, GetBaseDamage(attacker), true); + + // pre-AOS, halve damage if the defender is a player or the attacker is not a player + if (defender is PlayerMobile || !(attacker is PlayerMobile)) + damage = (int)(damage / 2.0); + + return damage; + } + + public virtual void PlayHurtAnimation(Mobile from) + { + int action; + int frames; + + switch (from.Body.Type) + { + case BodyType.Sea: + case BodyType.Animal: + { + action = 7; + frames = 5; + break; + } + case BodyType.Monster: + { + action = 10; + frames = 4; + break; + } + case BodyType.Human: + { + action = 20; + frames = 5; + break; + } + default: return; + } + + if (from.Mounted) + return; + + from.Animate(action, frames, 1, true, false, 0); + } + + public virtual void PlaySwingAnimation(Mobile from) + { + int action; + + switch (from.Body.Type) + { + case BodyType.Sea: + case BodyType.Animal: + { + action = Utility.Random(5, 2); + break; + } + case BodyType.Monster: + { + switch (Animation) + { + default: + case WeaponAnimation.Wrestle: + case WeaponAnimation.Bash1H: + case WeaponAnimation.Pierce1H: + case WeaponAnimation.Slash1H: + case WeaponAnimation.Bash2H: + case WeaponAnimation.Pierce2H: + case WeaponAnimation.Slash2H: + action = Utility.Random(4, 3); + break; + case WeaponAnimation.ShootBow: return; // 7 + case WeaponAnimation.ShootXBow: return; // 8 + } + + break; + } + case BodyType.Human: + { + if (!from.Mounted) + action = (int)Animation; + else + switch (Animation) + { + default: + case WeaponAnimation.Wrestle: + case WeaponAnimation.Bash1H: + case WeaponAnimation.Pierce1H: + case WeaponAnimation.Slash1H: + action = 26; + break; + case WeaponAnimation.Bash2H: + case WeaponAnimation.Pierce2H: + case WeaponAnimation.Slash2H: + action = 29; + break; + case WeaponAnimation.ShootBow: + action = 27; + break; + case WeaponAnimation.ShootXBow: + action = 28; + break; + } + + break; + } + default: return; + } + + from.Animate(action, 7, 1, true, false, 0); + } + + private string GetNameString() + { + string name = Name; + + if (name == null) + name = $"#{LabelNumber}"; + + return name; + } + + public int GetElementalDamageHue() + { + GetDamageTypes(null, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, + out int direct); + //Order is Cold, Energy, Fire, Poison, Physical left + + int currentMax = 50; + int hue = 0; + + if (pois >= currentMax) + { + hue = 1267 + (pois - 50) / 10; + currentMax = pois; + } + + if (fire >= currentMax) + { + hue = 1255 + (fire - 50) / 10; + currentMax = fire; + } + + if (nrgy >= currentMax) + { + hue = 1273 + (nrgy - 50) / 10; + currentMax = nrgy; + } + + if (cold >= currentMax) hue = 1261 + (cold - 50) / 10; + + return hue; + } + + public override void AddNameProperty(ObjectPropertyList list) + { + int oreType; + + switch (m_Resource) + { + case CraftResource.DullCopper: + oreType = 1053108; + break; // dull copper + case CraftResource.ShadowIron: + oreType = 1053107; + break; // shadow iron + case CraftResource.Copper: + oreType = 1053106; + break; // copper + case CraftResource.Bronze: + oreType = 1053105; + break; // bronze + case CraftResource.Gold: + oreType = 1053104; + break; // golden + case CraftResource.Agapite: + oreType = 1053103; + break; // agapite + case CraftResource.Verite: + oreType = 1053102; + break; // verite + case CraftResource.Valorite: + oreType = 1053101; + break; // valorite + case CraftResource.SpinedLeather: + oreType = 1061118; + break; // spined + case CraftResource.HornedLeather: + oreType = 1061117; + break; // horned + case CraftResource.BarbedLeather: + oreType = 1061116; + break; // barbed + case CraftResource.RedScales: + oreType = 1060814; + break; // red + case CraftResource.YellowScales: + oreType = 1060818; + break; // yellow + case CraftResource.BlackScales: + oreType = 1060820; + break; // black + case CraftResource.GreenScales: + oreType = 1060819; + break; // green + case CraftResource.WhiteScales: + oreType = 1060821; + break; // white + case CraftResource.BlueScales: + oreType = 1060815; + break; // blue + default: + oreType = 0; + break; + } + + if (oreType != 0) + list.Add(1053099, "#{0}\t{1}", oreType, GetNameString()); // ~1_oretype~ ~2_armortype~ + else if (Name == null) + list.Add(LabelNumber); + else + list.Add(Name); + + /* + * Want to move this to the engraving tool, let the non-harmful + * formatting show, and remove CLILOCs embedded: more like OSI + * did with the books that had markup, etc. + * + * This will have a negative effect on a few event things imgame + * as is. + * + * If we cant find a more OSI-ish way to clean it up, we can + * easily put this back, and use it in the deserialize + * method and engraving tool, to make it perm cleaned up. + */ + + if (!string.IsNullOrEmpty(m_EngravedText)) + list.Add(1062613, m_EngravedText); + + /* list.Add( 1062613, Utility.FixHtml( m_EngravedText ) ); */ + } + + public override bool AllowEquippedCast(Mobile from) + { + if (base.AllowEquippedCast(from)) + return true; + + return m_AosAttributes.SpellChanneling != 0; + } + + public virtual int GetLuckBonus() + { + CraftResourceInfo resInfo = CraftResources.GetInfo(m_Resource); + + CraftAttributeInfo attrInfo = resInfo?.AttributeInfo; + + if (attrInfo == null) + return 0; + + return attrInfo.WeaponLuck; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_Crafter != null) + list.Add(1050043, m_Crafter.Name); // crafted by ~1_NAME~ + + #region Factions + + if (m_FactionState != null) + list.Add(1041350); // faction item + + #endregion + + m_AosSkillBonuses?.GetProperties(list); + + if (m_Quality == WeaponQuality.Exceptional) + list.Add(1060636); // exceptional - if ( m_Crafter != null ) - list.Add( 1050043, m_Crafter.Name ); // crafted by ~1_NAME~ + if (RequiredRace == Race.Elf) + list.Add(1075086); // Elves Only - #region Factions - if ( m_FactionState != null ) - list.Add( 1041350 ); // faction item - #endregion + if (ArtifactRarity > 0) + list.Add(1061078, ArtifactRarity.ToString()); // artifact rarity ~1_val~ - m_AosSkillBonuses?.GetProperties( list ); + if (this is IUsesRemaining usesRemaining && usesRemaining.ShowUsesRemaining) + list.Add(1060584, usesRemaining.UsesRemaining.ToString()); // uses remaining: ~1_val~ - if ( m_Quality == WeaponQuality.Exceptional ) - list.Add( 1060636 ); // exceptional + if (m_Poison != null && m_PoisonCharges > 0) + list.Add(1062412 + m_Poison.Level, m_PoisonCharges.ToString()); - if ( RequiredRace == Race.Elf ) - list.Add( 1075086 ); // Elves Only + if (m_Slayer != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer); + if (entry != null) + list.Add(entry.Title); + } - if ( ArtifactRarity > 0 ) - list.Add( 1061078, ArtifactRarity.ToString() ); // artifact rarity ~1_val~ + if (m_Slayer2 != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer2); + if (entry != null) + list.Add(entry.Title); + } - if ( this is IUsesRemaining usesRemaining && usesRemaining.ShowUsesRemaining ) - list.Add( 1060584, usesRemaining.UsesRemaining.ToString() ); // uses remaining: ~1_val~ - if ( m_Poison != null && m_PoisonCharges > 0 ) - list.Add( 1062412 + m_Poison.Level, m_PoisonCharges.ToString() ); + base.AddResistanceProperties(list); - if ( m_Slayer != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer ); - if ( entry != null ) - list.Add( entry.Title ); - } + int prop; - if ( m_Slayer2 != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer2 ); - if ( entry != null ) - list.Add( entry.Title ); - } + BaseRanged ranged = this as BaseRanged; + if (Core.ML && ranged?.Balanced == true) + list.Add(1072792); // Balanced - base.AddResistanceProperties( list ); + if ((prop = m_AosWeaponAttributes.UseBestSkill) != 0) + list.Add(1060400); // use best weapon skill - int prop; + if ((prop = GetDamageBonus() + m_AosAttributes.WeaponDamage) != 0) + list.Add(1060401, prop.ToString()); // damage increase ~1_val~% - BaseRanged ranged = this as BaseRanged; + if ((prop = m_AosAttributes.DefendChance) != 0) + list.Add(1060408, prop.ToString()); // defense chance increase ~1_val~% - if ( Core.ML && ranged?.Balanced == true ) - list.Add( 1072792 ); // Balanced + if ((prop = m_AosAttributes.EnhancePotions) != 0) + list.Add(1060411, prop.ToString()); // enhance potions ~1_val~% - if ( (prop = m_AosWeaponAttributes.UseBestSkill) != 0 ) - list.Add( 1060400 ); // use best weapon skill + if ((prop = m_AosAttributes.CastRecovery) != 0) + list.Add(1060412, prop.ToString()); // faster cast recovery ~1_val~ - if ( (prop = (GetDamageBonus() + m_AosAttributes.WeaponDamage)) != 0 ) - list.Add( 1060401, prop.ToString() ); // damage increase ~1_val~% + if ((prop = m_AosAttributes.CastSpeed) != 0) + list.Add(1060413, prop.ToString()); // faster casting ~1_val~ - if ( (prop = m_AosAttributes.DefendChance) != 0 ) - list.Add( 1060408, prop.ToString() ); // defense chance increase ~1_val~% + if ((prop = GetHitChanceBonus() + m_AosAttributes.AttackChance) != 0) + list.Add(1060415, prop.ToString()); // hit chance increase ~1_val~% - if ( (prop = m_AosAttributes.EnhancePotions) != 0 ) - list.Add( 1060411, prop.ToString() ); // enhance potions ~1_val~% + if ((prop = m_AosWeaponAttributes.HitColdArea) != 0) + list.Add(1060416, prop.ToString()); // hit cold area ~1_val~% - if ( (prop = m_AosAttributes.CastRecovery) != 0 ) - list.Add( 1060412, prop.ToString() ); // faster cast recovery ~1_val~ + if ((prop = m_AosWeaponAttributes.HitDispel) != 0) + list.Add(1060417, prop.ToString()); // hit dispel ~1_val~% - if ( (prop = m_AosAttributes.CastSpeed) != 0 ) - list.Add( 1060413, prop.ToString() ); // faster casting ~1_val~ + if ((prop = m_AosWeaponAttributes.HitEnergyArea) != 0) + list.Add(1060418, prop.ToString()); // hit energy area ~1_val~% - if ( (prop = (GetHitChanceBonus() + m_AosAttributes.AttackChance)) != 0 ) - list.Add( 1060415, prop.ToString() ); // hit chance increase ~1_val~% + if ((prop = m_AosWeaponAttributes.HitFireArea) != 0) + list.Add(1060419, prop.ToString()); // hit fire area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitColdArea) != 0 ) - list.Add( 1060416, prop.ToString() ); // hit cold area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitFireball) != 0) + list.Add(1060420, prop.ToString()); // hit fireball ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitDispel) != 0 ) - list.Add( 1060417, prop.ToString() ); // hit dispel ~1_val~% + if ((prop = m_AosWeaponAttributes.HitHarm) != 0) + list.Add(1060421, prop.ToString()); // hit harm ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitEnergyArea) != 0 ) - list.Add( 1060418, prop.ToString() ); // hit energy area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLeechHits) != 0) + list.Add(1060422, prop.ToString()); // hit life leech ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitFireArea) != 0 ) - list.Add( 1060419, prop.ToString() ); // hit fire area ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLightning) != 0) + list.Add(1060423, prop.ToString()); // hit lightning ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitFireball) != 0 ) - list.Add( 1060420, prop.ToString() ); // hit fireball ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLowerAttack) != 0) + list.Add(1060424, prop.ToString()); // hit lower attack ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitHarm) != 0 ) - list.Add( 1060421, prop.ToString() ); // hit harm ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLowerDefend) != 0) + list.Add(1060425, prop.ToString()); // hit lower defense ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLeechHits) != 0 ) - list.Add( 1060422, prop.ToString() ); // hit life leech ~1_val~% + if ((prop = m_AosWeaponAttributes.HitMagicArrow) != 0) + list.Add(1060426, prop.ToString()); // hit magic arrow ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLightning) != 0 ) - list.Add( 1060423, prop.ToString() ); // hit lightning ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLeechMana) != 0) + list.Add(1060427, prop.ToString()); // hit mana leech ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLowerAttack) != 0 ) - list.Add( 1060424, prop.ToString() ); // hit lower attack ~1_val~% + if ((prop = m_AosWeaponAttributes.HitPhysicalArea) != 0) + list.Add(1060428, prop.ToString()); // hit physical area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLowerDefend) != 0 ) - list.Add( 1060425, prop.ToString() ); // hit lower defense ~1_val~% + if ((prop = m_AosWeaponAttributes.HitPoisonArea) != 0) + list.Add(1060429, prop.ToString()); // hit poison area ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitMagicArrow) != 0 ) - list.Add( 1060426, prop.ToString() ); // hit magic arrow ~1_val~% + if ((prop = m_AosWeaponAttributes.HitLeechStam) != 0) + list.Add(1060430, prop.ToString()); // hit stamina leech ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitLeechMana) != 0 ) - list.Add( 1060427, prop.ToString() ); // hit mana leech ~1_val~% + if (ImmolatingWeaponSpell.IsImmolating(this)) + list.Add(1111917); // Immolated - if ( (prop = m_AosWeaponAttributes.HitPhysicalArea) != 0 ) - list.Add( 1060428, prop.ToString() ); // hit physical area ~1_val~% + if (Core.ML && (ranged?.Velocity ?? 0) != 0) + list.Add(1072793, prop.ToString()); // Velocity ~1_val~% - if ( (prop = m_AosWeaponAttributes.HitPoisonArea) != 0 ) - list.Add( 1060429, prop.ToString() ); // hit poison area ~1_val~% + if ((prop = m_AosAttributes.BonusDex) != 0) + list.Add(1060409, prop.ToString()); // dexterity bonus ~1_val~ - if ( (prop = m_AosWeaponAttributes.HitLeechStam) != 0 ) - list.Add( 1060430, prop.ToString() ); // hit stamina leech ~1_val~% + if ((prop = m_AosAttributes.BonusHits) != 0) + list.Add(1060431, prop.ToString()); // hit point increase ~1_val~ - if ( ImmolatingWeaponSpell.IsImmolating( this ) ) - list.Add( 1111917 ); // Immolated + if ((prop = m_AosAttributes.BonusInt) != 0) + list.Add(1060432, prop.ToString()); // intelligence bonus ~1_val~ - if ( Core.ML && (ranged?.Velocity ?? 0) != 0 ) - list.Add( 1072793, prop.ToString() ); // Velocity ~1_val~% + if ((prop = m_AosAttributes.LowerManaCost) != 0) + list.Add(1060433, prop.ToString()); // lower mana cost ~1_val~% - if ( (prop = m_AosAttributes.BonusDex) != 0 ) - list.Add( 1060409, prop.ToString() ); // dexterity bonus ~1_val~ + if ((prop = m_AosAttributes.LowerRegCost) != 0) + list.Add(1060434, prop.ToString()); // lower reagent cost ~1_val~% - if ( (prop = m_AosAttributes.BonusHits) != 0 ) - list.Add( 1060431, prop.ToString() ); // hit point increase ~1_val~ + if ((prop = GetLowerStatReq()) != 0) + list.Add(1060435, prop.ToString()); // lower requirements ~1_val~% - if ( (prop = m_AosAttributes.BonusInt) != 0 ) - list.Add( 1060432, prop.ToString() ); // intelligence bonus ~1_val~ + if ((prop = GetLuckBonus() + m_AosAttributes.Luck) != 0) + list.Add(1060436, prop.ToString()); // luck ~1_val~ - if ( (prop = m_AosAttributes.LowerManaCost) != 0 ) - list.Add( 1060433, prop.ToString() ); // lower mana cost ~1_val~% + if ((prop = m_AosWeaponAttributes.MageWeapon) != 0) + list.Add(1060438, (30 - prop).ToString()); // mage weapon -~1_val~ skill - if ( (prop = m_AosAttributes.LowerRegCost) != 0 ) - list.Add( 1060434, prop.ToString() ); // lower reagent cost ~1_val~% + if ((prop = m_AosAttributes.BonusMana) != 0) + list.Add(1060439, prop.ToString()); // mana increase ~1_val~ - if ( (prop = GetLowerStatReq()) != 0 ) - list.Add( 1060435, prop.ToString() ); // lower requirements ~1_val~% + if ((prop = m_AosAttributes.RegenMana) != 0) + list.Add(1060440, prop.ToString()); // mana regeneration ~1_val~ - if ( (prop = (GetLuckBonus() + m_AosAttributes.Luck)) != 0 ) - list.Add( 1060436, prop.ToString() ); // luck ~1_val~ + if ((prop = m_AosAttributes.NightSight) != 0) + list.Add(1060441); // night sight - if ( (prop = m_AosWeaponAttributes.MageWeapon) != 0 ) - list.Add( 1060438, (30 - prop).ToString() ); // mage weapon -~1_val~ skill + if ((prop = m_AosAttributes.ReflectPhysical) != 0) + list.Add(1060442, prop.ToString()); // reflect physical damage ~1_val~% - if ( (prop = m_AosAttributes.BonusMana) != 0 ) - list.Add( 1060439, prop.ToString() ); // mana increase ~1_val~ + if ((prop = m_AosAttributes.RegenStam) != 0) + list.Add(1060443, prop.ToString()); // stamina regeneration ~1_val~ - if ( (prop = m_AosAttributes.RegenMana) != 0 ) - list.Add( 1060440, prop.ToString() ); // mana regeneration ~1_val~ + if ((prop = m_AosAttributes.RegenHits) != 0) + list.Add(1060444, prop.ToString()); // hit point regeneration ~1_val~ - if ( (prop = m_AosAttributes.NightSight) != 0 ) - list.Add( 1060441 ); // night sight + if ((prop = m_AosWeaponAttributes.SelfRepair) != 0) + list.Add(1060450, prop.ToString()); // self repair ~1_val~ - if ( (prop = m_AosAttributes.ReflectPhysical) != 0 ) - list.Add( 1060442, prop.ToString() ); // reflect physical damage ~1_val~% + if ((prop = m_AosAttributes.SpellChanneling) != 0) + list.Add(1060482); // spell channeling - if ( (prop = m_AosAttributes.RegenStam) != 0 ) - list.Add( 1060443, prop.ToString() ); // stamina regeneration ~1_val~ + if ((prop = m_AosAttributes.SpellDamage) != 0) + list.Add(1060483, prop.ToString()); // spell damage increase ~1_val~% - if ( (prop = m_AosAttributes.RegenHits) != 0 ) - list.Add( 1060444, prop.ToString() ); // hit point regeneration ~1_val~ + if ((prop = m_AosAttributes.BonusStam) != 0) + list.Add(1060484, prop.ToString()); // stamina increase ~1_val~ - if ( (prop = m_AosWeaponAttributes.SelfRepair) != 0 ) - list.Add( 1060450, prop.ToString() ); // self repair ~1_val~ + if ((prop = m_AosAttributes.BonusStr) != 0) + list.Add(1060485, prop.ToString()); // strength bonus ~1_val~ - if ( (prop = m_AosAttributes.SpellChanneling) != 0 ) - list.Add( 1060482 ); // spell channeling + if ((prop = m_AosAttributes.WeaponSpeed) != 0) + list.Add(1060486, prop.ToString()); // swing speed increase ~1_val~% - if ( (prop = m_AosAttributes.SpellDamage) != 0 ) - list.Add( 1060483, prop.ToString() ); // spell damage increase ~1_val~% + if (Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0) + list.Add(1075210, prop.ToString()); // Increased Karma Loss ~1val~% - if ( (prop = m_AosAttributes.BonusStam) != 0 ) - list.Add( 1060484, prop.ToString() ); // stamina increase ~1_val~ + GetDamageTypes(null, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, + out int direct); - if ( (prop = m_AosAttributes.BonusStr) != 0 ) - list.Add( 1060485, prop.ToString() ); // strength bonus ~1_val~ + if (phys != 0) + list.Add(1060403, phys.ToString()); // physical damage ~1_val~% - if ( (prop = m_AosAttributes.WeaponSpeed) != 0 ) - list.Add( 1060486, prop.ToString() ); // swing speed increase ~1_val~% + if (fire != 0) + list.Add(1060405, fire.ToString()); // fire damage ~1_val~% - if ( Core.ML && (prop = m_AosAttributes.IncreasedKarmaLoss) != 0 ) - list.Add( 1075210, prop.ToString() ); // Increased Karma Loss ~1val~% + if (cold != 0) + list.Add(1060404, cold.ToString()); // cold damage ~1_val~% - GetDamageTypes( null, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ); + if (pois != 0) + list.Add(1060406, pois.ToString()); // poison damage ~1_val~% - if ( phys != 0 ) - list.Add( 1060403, phys.ToString() ); // physical damage ~1_val~% + if (nrgy != 0) + list.Add(1060407, nrgy.ToString()); // energy damage ~1_val - if ( fire != 0 ) - list.Add( 1060405, fire.ToString() ); // fire damage ~1_val~% + if (Core.ML && chaos != 0) + list.Add(1072846, chaos.ToString()); // chaos damage ~1_val~% - if ( cold != 0 ) - list.Add( 1060404, cold.ToString() ); // cold damage ~1_val~% + if (Core.ML && direct != 0) + list.Add(1079978, direct.ToString()); // Direct Damage: ~1_PERCENT~% - if ( pois != 0 ) - list.Add( 1060406, pois.ToString() ); // poison damage ~1_val~% + list.Add(1061168, "{0}\t{1}", MinDamage.ToString(), MaxDamage.ToString()); // weapon damage ~1_val~ - ~2_val~ - if ( nrgy != 0 ) - list.Add( 1060407, nrgy.ToString() ); // energy damage ~1_val + if (Core.ML) + list.Add(1061167, $"{Speed}s"); // weapon speed ~1_val~ + else + list.Add(1061167, Speed.ToString()); - if ( Core.ML && chaos != 0 ) - list.Add( 1072846, chaos.ToString() ); // chaos damage ~1_val~% + if (MaxRange > 1) + list.Add(1061169, MaxRange.ToString()); // range ~1_val~ - if ( Core.ML && direct != 0 ) - list.Add( 1079978, direct.ToString() ); // Direct Damage: ~1_PERCENT~% + int strReq = AOS.Scale(StrRequirement, 100 - GetLowerStatReq()); - list.Add( 1061168, "{0}\t{1}", MinDamage.ToString(), MaxDamage.ToString() ); // weapon damage ~1_val~ - ~2_val~ + if (strReq > 0) + list.Add(1061170, strReq.ToString()); // strength requirement ~1_val~ - if ( Core.ML ) - list.Add( 1061167, $"{Speed}s"); // weapon speed ~1_val~ - else - list.Add( 1061167, Speed.ToString() ); + if (Layer == Layer.TwoHanded) + list.Add(1061171); // two-handed weapon + else + list.Add(1061824); // one-handed weapon - if ( MaxRange > 1 ) - list.Add( 1061169, MaxRange.ToString() ); // range ~1_val~ + if (Core.SE || m_AosWeaponAttributes.UseBestSkill == 0) + switch (Skill) + { + case SkillName.Swords: + list.Add(1061172); + break; // skill required: swordsmanship + case SkillName.Macing: + list.Add(1061173); + break; // skill required: mace fighting + case SkillName.Fencing: + list.Add(1061174); + break; // skill required: fencing + case SkillName.Archery: + list.Add(1061175); + break; // skill required: archery + } - int strReq = AOS.Scale( StrRequirement, 100 - GetLowerStatReq() ); + if (m_Hits >= 0 && m_MaxHits > 0) + list.Add(1060639, "{0}\t{1}", m_Hits, m_MaxHits); // durability ~1_val~ / ~2_val~ + } - if ( strReq > 0 ) - list.Add( 1061170, strReq.ToString() ); // strength requirement ~1_val~ + public override void OnSingleClick(Mobile from) + { + List attrs = new List(); - if ( Layer == Layer.TwoHanded ) - list.Add( 1061171 ); // two-handed weapon - else - list.Add( 1061824 ); // one-handed weapon + if (DisplayLootType) + { + if (LootType == LootType.Blessed) + attrs.Add(new EquipInfoAttribute(1038021)); // blessed + else if (LootType == LootType.Cursed) + attrs.Add(new EquipInfoAttribute(1049643)); // cursed + } - if ( Core.SE || m_AosWeaponAttributes.UseBestSkill == 0 ) - { - switch ( Skill ) - { - case SkillName.Swords: list.Add( 1061172 ); break; // skill required: swordsmanship - case SkillName.Macing: list.Add( 1061173 ); break; // skill required: mace fighting - case SkillName.Fencing: list.Add( 1061174 ); break; // skill required: fencing - case SkillName.Archery: list.Add( 1061175 ); break; // skill required: archery - } - } + #region Factions - if ( m_Hits >= 0 && m_MaxHits > 0 ) - list.Add( 1060639, "{0}\t{1}", m_Hits, m_MaxHits ); // durability ~1_val~ / ~2_val~ - } + if (m_FactionState != null) + attrs.Add(new EquipInfoAttribute(1041350)); // faction item + + #endregion + + if (m_Quality == WeaponQuality.Exceptional) + attrs.Add(new EquipInfoAttribute(1018305 - (int)m_Quality)); + + if (m_Identified || from.AccessLevel >= AccessLevel.GameMaster) + { + if (m_Slayer != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer); + if (entry != null) + attrs.Add(new EquipInfoAttribute(entry.Title)); + } + + if (m_Slayer2 != SlayerName.None) + { + SlayerEntry entry = SlayerGroup.GetEntryByName(m_Slayer2); + if (entry != null) + attrs.Add(new EquipInfoAttribute(entry.Title)); + } + + if (m_DurabilityLevel != WeaponDurabilityLevel.Regular) + attrs.Add(new EquipInfoAttribute(1038000 + (int)m_DurabilityLevel)); + + if (m_DamageLevel != WeaponDamageLevel.Regular) + attrs.Add(new EquipInfoAttribute(1038015 + (int)m_DamageLevel)); + + if (m_AccuracyLevel != WeaponAccuracyLevel.Regular) + attrs.Add(new EquipInfoAttribute(1038010 + (int)m_AccuracyLevel)); + } + else if (m_Slayer != SlayerName.None || m_Slayer2 != SlayerName.None || + m_DurabilityLevel != WeaponDurabilityLevel.Regular || m_DamageLevel != WeaponDamageLevel.Regular || + m_AccuracyLevel != WeaponAccuracyLevel.Regular) + { + attrs.Add(new EquipInfoAttribute(1038000)); // Unidentified + } + + if (m_Poison != null && m_PoisonCharges > 0) + attrs.Add(new EquipInfoAttribute(1017383, m_PoisonCharges)); + + int number; + + if (Name == null) + { + number = LabelNumber; + } + else + { + LabelTo(from, Name); + number = 1041000; + } + + if (attrs.Count == 0 && Crafter == null && Name != null) + return; + + EquipmentInfo eqInfo = new EquipmentInfo(number, m_Crafter, false, attrs.ToArray()); + + from.Send(new DisplayEquipmentInfo(this, eqInfo)); + } + + private class ResetEquipTimer : Timer + { + private Mobile m_Mobile; + + public ResetEquipTimer(Mobile m, TimeSpan duration) : base(duration) + { + m_Mobile = m; + } + + protected override void OnTick() + { + m_Mobile.EndAction(typeof(BaseWeapon)); + } + } + + #region Factions + + private FactionItem m_FactionState; + + public FactionItem FactionItemState + { + get => m_FactionState; + set + { + m_FactionState = value; + + if (m_FactionState == null) + Hue = CraftResources.GetHue(Resource); + + LootType = m_FactionState == null ? LootType.Regular : LootType.Blessed; + } + } + + #endregion + + /* Weapon internals work differently now (Mar 13 2003) + * + * The attributes defined below default to -1. + * If the value is -1, the corresponding virtual 'Aos/Old' property is used. + * If not, the attribute value itself is used. Here's the list: + * - MinDamage + * - MaxDamage + * - Speed + * - HitSound + * - MissSound + * - StrRequirement, DexRequirement, IntRequirement + * - WeaponType + * - WeaponAnimation + * - MaxRange + */ + + #region Var declarations + + // Instance values. These values are unique to each weapon. + private WeaponDamageLevel m_DamageLevel; + private WeaponAccuracyLevel m_AccuracyLevel; + private WeaponDurabilityLevel m_DurabilityLevel; + private WeaponQuality m_Quality; + private Mobile m_Crafter; + private Poison m_Poison; + private int m_PoisonCharges; + private bool m_Identified; + private int m_Hits; + private int m_MaxHits; + private SlayerName m_Slayer; + private SlayerName m_Slayer2; + private SkillMod m_SkillMod, m_MageMod; + private CraftResource m_Resource; + + private AosAttributes m_AosAttributes; + private AosWeaponAttributes m_AosWeaponAttributes; + private AosSkillBonuses m_AosSkillBonuses; + private AosElementAttributes m_AosElementDamages; + + // Overridable values. These values are provided to override the defaults which get defined in the individual weapon scripts. + private int m_StrReq, m_DexReq, m_IntReq; + private int m_MinDamage, m_MaxDamage; + private int m_HitSound, m_MissSound; + private float m_Speed; + private int m_MaxRange; + private SkillName m_Skill; + private WeaponType m_Type; + private WeaponAnimation m_Animation; + + #endregion + + #region Virtual Properties + + public virtual WeaponAbility PrimaryAbility => null; + public virtual WeaponAbility SecondaryAbility => null; + + public virtual int DefMaxRange => 1; + public virtual int DefHitSound => 0; + public virtual int DefMissSound => 0; + public virtual SkillName DefSkill => SkillName.Swords; + public virtual WeaponType DefType => WeaponType.Slashing; + public virtual WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; + + public virtual int AosStrengthReq => 0; + public virtual int AosDexterityReq => 0; + public virtual int AosIntelligenceReq => 0; + public virtual int AosMinDamage => 0; + public virtual int AosMaxDamage => 0; + public virtual int AosSpeed => 0; + public virtual float MlSpeed => 0.0f; + public virtual int AosMaxRange => DefMaxRange; + public virtual int AosHitSound => DefHitSound; + public virtual int AosMissSound => DefMissSound; + public virtual SkillName AosSkill => DefSkill; + public virtual WeaponType AosType => DefType; + public virtual WeaponAnimation AosAnimation => DefAnimation; + + public virtual int OldStrengthReq => 0; + public virtual int OldDexterityReq => 0; + public virtual int OldIntelligenceReq => 0; + public virtual int OldMinDamage => 0; + public virtual int OldMaxDamage => 0; + public virtual int OldSpeed => 0; + public virtual int OldMaxRange => DefMaxRange; + public virtual int OldHitSound => DefHitSound; + public virtual int OldMissSound => DefMissSound; + public virtual SkillName OldSkill => DefSkill; + public virtual WeaponType OldType => DefType; + public virtual WeaponAnimation OldAnimation => DefAnimation; + + public virtual int InitMinHits => 0; + public virtual int InitMaxHits => 0; + + public virtual bool CanFortify => true; + + public override int PhysicalResistance => m_AosWeaponAttributes.ResistPhysicalBonus; + public override int FireResistance => m_AosWeaponAttributes.ResistFireBonus; + public override int ColdResistance => m_AosWeaponAttributes.ResistColdBonus; + public override int PoisonResistance => m_AosWeaponAttributes.ResistPoisonBonus; + public override int EnergyResistance => m_AosWeaponAttributes.ResistEnergyBonus; + + public virtual SkillName AccuracySkill => SkillName.Tactics; + + #endregion + + #region Getters & Setters + + [CommandProperty(AccessLevel.GameMaster)] + public AosAttributes Attributes + { + get => m_AosAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosWeaponAttributes WeaponAttributes + { + get => m_AosWeaponAttributes; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosSkillBonuses SkillBonuses + { + get => m_AosSkillBonuses; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public AosElementAttributes AosElementDamages + { + get => m_AosElementDamages; + set { } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Cursed{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Consecrated{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Identified + { + get => m_Identified; + set + { + m_Identified = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitPoints + { + get => m_Hits; + set + { + if (m_Hits == value) + return; + + if (value > m_MaxHits) + value = m_MaxHits; + + m_Hits = value; + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxHitPoints + { + get => m_MaxHits; + set + { + m_MaxHits = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonCharges + { + get => m_PoisonCharges; + set + { + m_PoisonCharges = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison + { + get => m_Poison; + set + { + m_Poison = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public WeaponQuality Quality + { + get => m_Quality; + set + { + UnscaleDurability(); + m_Quality = value; + ScaleDurability(); + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Crafter + { + get => m_Crafter; + set + { + m_Crafter = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public SlayerName Slayer + { + get => m_Slayer; + set + { + m_Slayer = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public SlayerName Slayer2 + { + get => m_Slayer2; + set + { + m_Slayer2 = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource Resource + { + get => m_Resource; + set + { + UnscaleDurability(); + m_Resource = value; + Hue = CraftResources.GetHue(m_Resource); + InvalidateProperties(); + ScaleDurability(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public WeaponDamageLevel DamageLevel + { + get => m_DamageLevel; + set + { + m_DamageLevel = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public WeaponDurabilityLevel DurabilityLevel + { + get => m_DurabilityLevel; + set + { + UnscaleDurability(); + m_DurabilityLevel = value; + InvalidateProperties(); + ScaleDurability(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool PlayerConstructed{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxRange + { + get => m_MaxRange == -1 ? Core.AOS ? AosMaxRange : OldMaxRange : m_MaxRange; + set + { + m_MaxRange = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public WeaponAnimation Animation + { + get => m_Animation == (WeaponAnimation)(-1) ? Core.AOS ? AosAnimation : OldAnimation : m_Animation; + set => m_Animation = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public WeaponType Type + { + get => m_Type == (WeaponType)(-1) ? Core.AOS ? AosType : OldType : m_Type; + set => m_Type = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill + { + get => m_Skill == (SkillName)(-1) ? Core.AOS ? AosSkill : OldSkill : m_Skill; + set + { + m_Skill = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitSound + { + get => m_HitSound == -1 ? Core.AOS ? AosHitSound : OldHitSound : m_HitSound; + set => m_HitSound = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MissSound + { + get => m_MissSound == -1 ? Core.AOS ? AosMissSound : OldMissSound : m_MissSound; + set => m_MissSound = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MinDamage + { + get => m_MinDamage == -1 ? Core.AOS ? AosMinDamage : OldMinDamage : m_MinDamage; + set + { + m_MinDamage = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxDamage + { + get => m_MaxDamage == -1 ? Core.AOS ? AosMaxDamage : OldMaxDamage : m_MaxDamage; + set + { + m_MaxDamage = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public float Speed + { + get + { + if (m_Speed != -1) + return m_Speed; + + if (Core.ML) + return MlSpeed; + if (Core.AOS) + return AosSpeed; + + return OldSpeed; + } + set + { + m_Speed = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int StrRequirement + { + get => m_StrReq == -1 ? Core.AOS ? AosStrengthReq : OldStrengthReq : m_StrReq; + set + { + m_StrReq = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DexRequirement + { + get => m_DexReq == -1 ? Core.AOS ? AosDexterityReq : OldDexterityReq : m_DexReq; + set => m_DexReq = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int IntRequirement + { + get => m_IntReq == -1 ? Core.AOS ? AosIntelligenceReq : OldIntelligenceReq : m_IntReq; + set => m_IntReq = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public WeaponAccuracyLevel AccuracyLevel + { + get => m_AccuracyLevel; + set + { + if (m_AccuracyLevel != value) + { + m_AccuracyLevel = value; + + if (UseSkillMod) + { + if (m_AccuracyLevel == WeaponAccuracyLevel.Regular) + { + m_SkillMod?.Remove(); + + m_SkillMod = null; + } + else if (m_SkillMod == null && Parent is Mobile mobile) + { + m_SkillMod = new DefaultSkillMod(AccuracySkill, true, (int)m_AccuracyLevel * 5); + mobile.AddSkillMod(m_SkillMod); + } + else if (m_SkillMod != null) + { + m_SkillMod.Value = (int)m_AccuracyLevel * 5; + } + } + + InvalidateProperties(); + } + } + } + + #endregion + + #region Sounds + + public virtual int GetHitAttackSound(Mobile attacker, Mobile defender) + { + int sound = attacker.GetAttackSound(); + + if (sound == -1) + sound = HitSound; + + return sound; + } + + public virtual int GetHitDefendSound(Mobile attacker, Mobile defender) + { + return defender.GetHurtSound(); + } + + public virtual int GetMissAttackSound(Mobile attacker, Mobile defender) + { + return attacker.GetAttackSound() == -1 ? MissSound : -1; + } + + public virtual int GetMissDefendSound(Mobile attacker, Mobile defender) + { + return -1; + } + + #endregion + + #region Do + + public virtual void DoMagicArrow(Mobile attacker, Mobile defender) + { + if (!attacker.CanBeHarmful(defender, false)) + return; + + attacker.DoHarmful(defender); + + double damage = GetAosDamage(attacker, 10, 1, 4); + + attacker.MovingParticles(defender, 0x36E4, 5, 0, false, true, 3006, 4006, 0); + attacker.PlaySound(0x1E5); + + SpellHelper.Damage(TimeSpan.FromSeconds(1.0), defender, attacker, damage, 0, 100, 0, 0, 0); + } + + public virtual void DoHarm(Mobile attacker, Mobile defender) + { + if (!attacker.CanBeHarmful(defender, false)) + return; + + attacker.DoHarmful(defender); + + double damage = GetAosDamage(attacker, 17, 1, 5); - public override void OnSingleClick( Mobile from ) - { - List attrs = new List(); + if (!defender.InRange(attacker, 2)) + damage *= 0.25; // 1/4 damage at > 2 tile range + else if (!defender.InRange(attacker, 1)) + damage *= 0.50; // 1/2 damage at 2 tile range - if ( DisplayLootType ) - { - if ( LootType == LootType.Blessed ) - attrs.Add( new EquipInfoAttribute( 1038021 ) ); // blessed - else if ( LootType == LootType.Cursed ) - attrs.Add( new EquipInfoAttribute( 1049643 ) ); // cursed - } + defender.FixedParticles(0x374A, 10, 30, 5013, 1153, 2, EffectLayer.Waist); + defender.PlaySound(0x0FC); - #region Factions - if ( m_FactionState != null ) - attrs.Add( new EquipInfoAttribute( 1041350 ) ); // faction item - #endregion + SpellHelper.Damage(TimeSpan.Zero, defender, attacker, damage, 0, 0, 100, 0, 0); + } - if ( m_Quality == WeaponQuality.Exceptional ) - attrs.Add( new EquipInfoAttribute( 1018305 - (int)m_Quality ) ); + public virtual void DoFireball(Mobile attacker, Mobile defender) + { + if (!attacker.CanBeHarmful(defender, false)) + return; - if ( m_Identified || from.AccessLevel >= AccessLevel.GameMaster ) - { - if ( m_Slayer != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer ); - if ( entry != null ) - attrs.Add( new EquipInfoAttribute( entry.Title ) ); - } + attacker.DoHarmful(defender); - if ( m_Slayer2 != SlayerName.None ) - { - SlayerEntry entry = SlayerGroup.GetEntryByName( m_Slayer2 ); - if ( entry != null ) - attrs.Add( new EquipInfoAttribute( entry.Title ) ); - } + double damage = GetAosDamage(attacker, 19, 1, 5); - if ( m_DurabilityLevel != WeaponDurabilityLevel.Regular ) - attrs.Add( new EquipInfoAttribute( 1038000 + (int)m_DurabilityLevel ) ); + attacker.MovingParticles(defender, 0x36D4, 7, 0, false, true, 9502, 4019, 0x160); + attacker.PlaySound(0x15E); - if ( m_DamageLevel != WeaponDamageLevel.Regular ) - attrs.Add( new EquipInfoAttribute( 1038015 + (int)m_DamageLevel ) ); + SpellHelper.Damage(TimeSpan.FromSeconds(1.0), defender, attacker, damage, 0, 100, 0, 0, 0); + } - if ( m_AccuracyLevel != WeaponAccuracyLevel.Regular ) - attrs.Add( new EquipInfoAttribute( 1038010 + (int)m_AccuracyLevel ) ); - } - else if ( m_Slayer != SlayerName.None || m_Slayer2 != SlayerName.None || m_DurabilityLevel != WeaponDurabilityLevel.Regular || m_DamageLevel != WeaponDamageLevel.Regular || m_AccuracyLevel != WeaponAccuracyLevel.Regular ) - attrs.Add( new EquipInfoAttribute( 1038000 ) ); // Unidentified - - if ( m_Poison != null && m_PoisonCharges > 0 ) - attrs.Add( new EquipInfoAttribute( 1017383, m_PoisonCharges ) ); - - int number; - - if ( Name == null ) - { - number = LabelNumber; - } - else - { - LabelTo( from, Name ); - number = 1041000; - } - - if ( attrs.Count == 0 && Crafter == null && Name != null ) - return; - - EquipmentInfo eqInfo = new EquipmentInfo( number, m_Crafter, false, attrs.ToArray() ); - - from.Send( new DisplayEquipmentInfo( this, eqInfo ) ); - } - - public static BaseWeapon Fists { get; set; } - - #region ICraftable Members - - public int OnCraft( int quality, bool makersMark, Mobile from, CraftSystem craftSystem, Type typeRes, BaseTool tool, CraftItem craftItem, int resHue ) - { - Quality = (WeaponQuality)quality; - - if ( makersMark ) - Crafter = from; - - PlayerConstructed = true; - - Type resourceType = typeRes; - - if ( resourceType == null ) - resourceType = craftItem.Resources.GetAt( 0 ).ItemType; - - if ( Core.AOS ) - { - Resource = CraftResources.GetFromType( resourceType ); - - CraftContext context = craftSystem.GetContext( from ); - - if ( context != null && context.DoNotColor ) - Hue = 0; - - if ( tool is BaseRunicTool runicTool ) - runicTool.ApplyAttributesTo( this ); - - if ( Quality == WeaponQuality.Exceptional ) - { - if ( Attributes.WeaponDamage > 35 ) - Attributes.WeaponDamage -= 20; - else - Attributes.WeaponDamage = 15; - - if ( Core.ML ) - { - Attributes.WeaponDamage += (int)(from.Skills.ArmsLore.Value / 20); - - if ( Attributes.WeaponDamage > 50 ) - Attributes.WeaponDamage = 50; - - from.CheckSkill( SkillName.ArmsLore, 0, 100 ); - } - } - } - else if ( tool is BaseRunicTool runicTool ) - { - CraftResource thisResource = CraftResources.GetFromType( resourceType ); - - if ( thisResource == runicTool.Resource ) - { - Resource = thisResource; - - CraftContext context = craftSystem.GetContext( from ); - - if ( context != null && context.DoNotColor ) - Hue = 0; - - switch ( thisResource ) - { - case CraftResource.DullCopper: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Durable; - AccuracyLevel = WeaponAccuracyLevel.Accurate; - break; - } - case CraftResource.ShadowIron: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Durable; - DamageLevel = WeaponDamageLevel.Ruin; - break; - } - case CraftResource.Copper: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Fortified; - DamageLevel = WeaponDamageLevel.Ruin; - AccuracyLevel = WeaponAccuracyLevel.Surpassingly; - break; - } - case CraftResource.Bronze: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Fortified; - DamageLevel = WeaponDamageLevel.Might; - AccuracyLevel = WeaponAccuracyLevel.Surpassingly; - break; - } - case CraftResource.Gold: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Indestructible; - DamageLevel = WeaponDamageLevel.Force; - AccuracyLevel = WeaponAccuracyLevel.Eminently; - break; - } - case CraftResource.Agapite: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Indestructible; - DamageLevel = WeaponDamageLevel.Power; - AccuracyLevel = WeaponAccuracyLevel.Eminently; - break; - } - case CraftResource.Verite: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Indestructible; - DamageLevel = WeaponDamageLevel.Power; - AccuracyLevel = WeaponAccuracyLevel.Exceedingly; - break; - } - case CraftResource.Valorite: - { - Identified = true; - DurabilityLevel = WeaponDurabilityLevel.Indestructible; - DamageLevel = WeaponDamageLevel.Vanq; - AccuracyLevel = WeaponAccuracyLevel.Supremely; - break; - } - } - } - } - - return quality; - } - - #endregion - } - - public enum CheckSlayerResult - { - None, - Slayer, - Opposition - } -} + public virtual void DoLightning(Mobile attacker, Mobile defender) + { + if (!attacker.CanBeHarmful(defender, false)) + return; + + attacker.DoHarmful(defender); + + double damage = GetAosDamage(attacker, 23, 1, 4); + + defender.BoltEffect(0); + + SpellHelper.Damage(TimeSpan.Zero, defender, attacker, damage, 0, 0, 0, 0, 100); + } + + public virtual void DoDispel(Mobile attacker, Mobile defender) + { + bool dispellable = false; + + if (defender is BaseCreature creature) + dispellable = creature.Summoned && !creature.IsAnimatedDead; + + if (!dispellable) + return; + + if (!attacker.CanBeHarmful(defender, false)) + return; + + attacker.DoHarmful(defender); + + MagerySpell sp = new DispelSpell(attacker, null); + + if (sp.CheckResisted(defender)) + { + defender.FixedEffect(0x3779, 10, 20); + } + else + { + Effects.SendLocationParticles(EffectItem.Create(defender.Location, defender.Map, EffectItem.DefaultDuration), + 0x3728, 8, 20, 5042); + Effects.PlaySound(defender, defender.Map, 0x201); + + defender.Delete(); + } + } + + public virtual void DoLowerAttack(Mobile from, Mobile defender) + { + if (HitLower.ApplyAttack(defender)) + { + defender.PlaySound(0x28E); + Effects.SendTargetEffect(defender, 0x37BE, 1, 4, 0xA, 3); + } + } + + public virtual void DoLowerDefense(Mobile from, Mobile defender) + { + if (HitLower.ApplyDefense(defender)) + { + defender.PlaySound(0x28E); + Effects.SendTargetEffect(defender, 0x37BE, 1, 4, 0x23, 3); + } + } + + public virtual void DoAreaAttack(Mobile from, Mobile defender, int sound, int hue, int phys, int fire, int cold, + int pois, int nrgy) + { + Map map = from.Map; + + if (map == null) + return; + + List list = new List(); + + int range = Core.ML ? 5 : 10; + + IPooledEnumerable eable = from.GetMobilesInRange(range); + foreach (Mobile m in eable) + if (from != m && defender != m && SpellHelper.ValidIndirectTarget(from, m) && from.CanBeHarmful(m, false) && + (!Core.ML || from.InLOS(m))) + list.Add(m); + eable.Free(); + + if (list.Count == 0) + return; + + Effects.PlaySound(from.Location, map, sound); + + for (int i = 0; i < list.Count; ++i) + { + Mobile m = list[i]; + + double scalar = Core.ML ? 1.0 : (11 - from.GetDistanceToSqrt(m)) / 10; + double damage = GetBaseDamage(from); + + if (scalar <= 0) continue; + + if (scalar < 1.0) damage *= (11 - from.GetDistanceToSqrt(m)) / 10; + + from.DoHarmful(m, true); + m.FixedEffect(0x3779, 1, 15, hue, 0); + AOS.Damage(m, from, (int)damage, phys, fire, cold, pois, nrgy); + } + } + + #endregion + + #region Serialization/Deserialization + + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } + + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(9); // version + + SaveFlag flags = SaveFlag.None; + + SetSaveFlag(ref flags, SaveFlag.DamageLevel, m_DamageLevel != WeaponDamageLevel.Regular); + SetSaveFlag(ref flags, SaveFlag.AccuracyLevel, m_AccuracyLevel != WeaponAccuracyLevel.Regular); + SetSaveFlag(ref flags, SaveFlag.DurabilityLevel, m_DurabilityLevel != WeaponDurabilityLevel.Regular); + SetSaveFlag(ref flags, SaveFlag.Quality, m_Quality != WeaponQuality.Regular); + SetSaveFlag(ref flags, SaveFlag.Hits, m_Hits != 0); + SetSaveFlag(ref flags, SaveFlag.MaxHits, m_MaxHits != 0); + SetSaveFlag(ref flags, SaveFlag.Slayer, m_Slayer != SlayerName.None); + SetSaveFlag(ref flags, SaveFlag.Poison, m_Poison != null); + SetSaveFlag(ref flags, SaveFlag.PoisonCharges, m_PoisonCharges != 0); + SetSaveFlag(ref flags, SaveFlag.Crafter, m_Crafter != null); + SetSaveFlag(ref flags, SaveFlag.Identified, m_Identified); + SetSaveFlag(ref flags, SaveFlag.StrReq, m_StrReq != -1); + SetSaveFlag(ref flags, SaveFlag.DexReq, m_DexReq != -1); + SetSaveFlag(ref flags, SaveFlag.IntReq, m_IntReq != -1); + SetSaveFlag(ref flags, SaveFlag.MinDamage, m_MinDamage != -1); + SetSaveFlag(ref flags, SaveFlag.MaxDamage, m_MaxDamage != -1); + SetSaveFlag(ref flags, SaveFlag.HitSound, m_HitSound != -1); + SetSaveFlag(ref flags, SaveFlag.MissSound, m_MissSound != -1); + SetSaveFlag(ref flags, SaveFlag.Speed, m_Speed != -1); + SetSaveFlag(ref flags, SaveFlag.MaxRange, m_MaxRange != -1); + SetSaveFlag(ref flags, SaveFlag.Skill, m_Skill != (SkillName)(-1)); + SetSaveFlag(ref flags, SaveFlag.Type, m_Type != (WeaponType)(-1)); + SetSaveFlag(ref flags, SaveFlag.Animation, m_Animation != (WeaponAnimation)(-1)); + SetSaveFlag(ref flags, SaveFlag.Resource, m_Resource != CraftResource.Iron); + SetSaveFlag(ref flags, SaveFlag.xAttributes, !m_AosAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.xWeaponAttributes, !m_AosWeaponAttributes.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.PlayerConstructed, PlayerConstructed); + SetSaveFlag(ref flags, SaveFlag.SkillBonuses, !m_AosSkillBonuses.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.Slayer2, m_Slayer2 != SlayerName.None); + SetSaveFlag(ref flags, SaveFlag.ElementalDamages, !m_AosElementDamages.IsEmpty); + SetSaveFlag(ref flags, SaveFlag.EngravedText, !string.IsNullOrEmpty(m_EngravedText)); + + writer.Write((int)flags); + + if (GetSaveFlag(flags, SaveFlag.DamageLevel)) + writer.Write((int)m_DamageLevel); + + if (GetSaveFlag(flags, SaveFlag.AccuracyLevel)) + writer.Write((int)m_AccuracyLevel); + + if (GetSaveFlag(flags, SaveFlag.DurabilityLevel)) + writer.Write((int)m_DurabilityLevel); + + if (GetSaveFlag(flags, SaveFlag.Quality)) + writer.Write((int)m_Quality); + + if (GetSaveFlag(flags, SaveFlag.Hits)) + writer.Write(m_Hits); + + if (GetSaveFlag(flags, SaveFlag.MaxHits)) + writer.Write(m_MaxHits); + + if (GetSaveFlag(flags, SaveFlag.Slayer)) + writer.Write((int)m_Slayer); + + if (GetSaveFlag(flags, SaveFlag.Poison)) + Poison.Serialize(m_Poison, writer); + + if (GetSaveFlag(flags, SaveFlag.PoisonCharges)) + writer.Write(m_PoisonCharges); + + if (GetSaveFlag(flags, SaveFlag.Crafter)) + writer.Write(m_Crafter); + + if (GetSaveFlag(flags, SaveFlag.StrReq)) + writer.Write(m_StrReq); + + if (GetSaveFlag(flags, SaveFlag.DexReq)) + writer.Write(m_DexReq); + + if (GetSaveFlag(flags, SaveFlag.IntReq)) + writer.Write(m_IntReq); + + if (GetSaveFlag(flags, SaveFlag.MinDamage)) + writer.Write(m_MinDamage); + + if (GetSaveFlag(flags, SaveFlag.MaxDamage)) + writer.Write(m_MaxDamage); + + if (GetSaveFlag(flags, SaveFlag.HitSound)) + writer.Write(m_HitSound); + + if (GetSaveFlag(flags, SaveFlag.MissSound)) + writer.Write(m_MissSound); + + if (GetSaveFlag(flags, SaveFlag.Speed)) + writer.Write(m_Speed); + + if (GetSaveFlag(flags, SaveFlag.MaxRange)) + writer.Write(m_MaxRange); + + if (GetSaveFlag(flags, SaveFlag.Skill)) + writer.Write((int)m_Skill); + + if (GetSaveFlag(flags, SaveFlag.Type)) + writer.Write((int)m_Type); + + if (GetSaveFlag(flags, SaveFlag.Animation)) + writer.Write((int)m_Animation); + + if (GetSaveFlag(flags, SaveFlag.Resource)) + writer.Write((int)m_Resource); + + if (GetSaveFlag(flags, SaveFlag.xAttributes)) + m_AosAttributes.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.xWeaponAttributes)) + m_AosWeaponAttributes.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.Slayer2)) + writer.Write((int)m_Slayer2); + + if (GetSaveFlag(flags, SaveFlag.ElementalDamages)) + m_AosElementDamages.Serialize(writer); + + if (GetSaveFlag(flags, SaveFlag.EngravedText)) + writer.Write(m_EngravedText); + } + + [Flags] + private enum SaveFlag + { + None = 0x00000000, + DamageLevel = 0x00000001, + AccuracyLevel = 0x00000002, + DurabilityLevel = 0x00000004, + Quality = 0x00000008, + Hits = 0x00000010, + MaxHits = 0x00000020, + Slayer = 0x00000040, + Poison = 0x00000080, + PoisonCharges = 0x00000100, + Crafter = 0x00000200, + Identified = 0x00000400, + StrReq = 0x00000800, + DexReq = 0x00001000, + IntReq = 0x00002000, + MinDamage = 0x00004000, + MaxDamage = 0x00008000, + HitSound = 0x00010000, + MissSound = 0x00020000, + Speed = 0x00040000, + MaxRange = 0x00080000, + Skill = 0x00100000, + Type = 0x00200000, + Animation = 0x00400000, + Resource = 0x00800000, + xAttributes = 0x01000000, + xWeaponAttributes = 0x02000000, + PlayerConstructed = 0x04000000, + SkillBonuses = 0x08000000, + Slayer2 = 0x10000000, + ElementalDamages = 0x20000000, + EngravedText = 0x40000000 + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Mobile parentMobile = Parent as Mobile; + + switch (version) + { + case 9: + case 8: + case 7: + case 6: + case 5: + { + SaveFlag flags = (SaveFlag)reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.DamageLevel)) + { + m_DamageLevel = (WeaponDamageLevel)reader.ReadInt(); + + if (m_DamageLevel > WeaponDamageLevel.Vanq) + m_DamageLevel = WeaponDamageLevel.Ruin; + } + + if (GetSaveFlag(flags, SaveFlag.AccuracyLevel)) + { + m_AccuracyLevel = (WeaponAccuracyLevel)reader.ReadInt(); + + if (m_AccuracyLevel > WeaponAccuracyLevel.Supremely) + m_AccuracyLevel = WeaponAccuracyLevel.Accurate; + } + + if (GetSaveFlag(flags, SaveFlag.DurabilityLevel)) + { + m_DurabilityLevel = (WeaponDurabilityLevel)reader.ReadInt(); + + if (m_DurabilityLevel > WeaponDurabilityLevel.Indestructible) + m_DurabilityLevel = WeaponDurabilityLevel.Durable; + } + + if (GetSaveFlag(flags, SaveFlag.Quality)) + m_Quality = (WeaponQuality)reader.ReadInt(); + else + m_Quality = WeaponQuality.Regular; + + if (GetSaveFlag(flags, SaveFlag.Hits)) + m_Hits = reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.MaxHits)) + m_MaxHits = reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.Slayer)) + m_Slayer = (SlayerName)reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.Poison)) + m_Poison = Poison.Deserialize(reader); + + if (GetSaveFlag(flags, SaveFlag.PoisonCharges)) + m_PoisonCharges = reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.Crafter)) + m_Crafter = reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.Identified)) + m_Identified = version >= 6 || reader.ReadBool(); + + if (GetSaveFlag(flags, SaveFlag.StrReq)) + m_StrReq = reader.ReadInt(); + else + m_StrReq = -1; + + if (GetSaveFlag(flags, SaveFlag.DexReq)) + m_DexReq = reader.ReadInt(); + else + m_DexReq = -1; + + if (GetSaveFlag(flags, SaveFlag.IntReq)) + m_IntReq = reader.ReadInt(); + else + m_IntReq = -1; + + if (GetSaveFlag(flags, SaveFlag.MinDamage)) + m_MinDamage = reader.ReadInt(); + else + m_MinDamage = -1; + + if (GetSaveFlag(flags, SaveFlag.MaxDamage)) + m_MaxDamage = reader.ReadInt(); + else + m_MaxDamage = -1; + + if (GetSaveFlag(flags, SaveFlag.HitSound)) + m_HitSound = reader.ReadInt(); + else + m_HitSound = -1; + + if (GetSaveFlag(flags, SaveFlag.MissSound)) + m_MissSound = reader.ReadInt(); + else + m_MissSound = -1; + + if (GetSaveFlag(flags, SaveFlag.Speed)) + { + if (version < 9) + m_Speed = reader.ReadInt(); + else + m_Speed = reader.ReadFloat(); + } + else + { + m_Speed = -1; + } + + if (GetSaveFlag(flags, SaveFlag.MaxRange)) + m_MaxRange = reader.ReadInt(); + else + m_MaxRange = -1; + + if (GetSaveFlag(flags, SaveFlag.Skill)) + m_Skill = (SkillName)reader.ReadInt(); + else + m_Skill = (SkillName)(-1); + + if (GetSaveFlag(flags, SaveFlag.Type)) + m_Type = (WeaponType)reader.ReadInt(); + else + m_Type = (WeaponType)(-1); + + if (GetSaveFlag(flags, SaveFlag.Animation)) + m_Animation = (WeaponAnimation)reader.ReadInt(); + else + m_Animation = (WeaponAnimation)(-1); + + if (GetSaveFlag(flags, SaveFlag.Resource)) + m_Resource = (CraftResource)reader.ReadInt(); + else + m_Resource = CraftResource.Iron; + + if (GetSaveFlag(flags, SaveFlag.xAttributes)) + m_AosAttributes = new AosAttributes(this, reader); + else + m_AosAttributes = new AosAttributes(this); + + if (GetSaveFlag(flags, SaveFlag.xWeaponAttributes)) + m_AosWeaponAttributes = new AosWeaponAttributes(this, reader); + else + m_AosWeaponAttributes = new AosWeaponAttributes(this); + + if (UseSkillMod && m_AccuracyLevel != WeaponAccuracyLevel.Regular && parentMobile != null) + { + m_SkillMod = new DefaultSkillMod(AccuracySkill, true, (int)m_AccuracyLevel * 5); + parentMobile.AddSkillMod(m_SkillMod); + } + + if (version < 7 && m_AosWeaponAttributes.MageWeapon != 0) + m_AosWeaponAttributes.MageWeapon = 30 - m_AosWeaponAttributes.MageWeapon; + + if (Core.AOS && m_AosWeaponAttributes.MageWeapon != 0 && m_AosWeaponAttributes.MageWeapon != 30 && + parentMobile != null) + { + m_MageMod = new DefaultSkillMod(SkillName.Magery, true, -30 + m_AosWeaponAttributes.MageWeapon); + parentMobile.AddSkillMod(m_MageMod); + } + + if (GetSaveFlag(flags, SaveFlag.PlayerConstructed)) + PlayerConstructed = true; + + if (GetSaveFlag(flags, SaveFlag.SkillBonuses)) + m_AosSkillBonuses = new AosSkillBonuses(this, reader); + else + m_AosSkillBonuses = new AosSkillBonuses(this); + + if (GetSaveFlag(flags, SaveFlag.Slayer2)) + m_Slayer2 = (SlayerName)reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.ElementalDamages)) + m_AosElementDamages = new AosElementAttributes(this, reader); + else + m_AosElementDamages = new AosElementAttributes(this); + + if (GetSaveFlag(flags, SaveFlag.EngravedText)) + m_EngravedText = reader.ReadString(); + + break; + } + case 4: + { + m_Slayer = (SlayerName)reader.ReadInt(); + + goto case 3; + } + case 3: + { + m_StrReq = reader.ReadInt(); + m_DexReq = reader.ReadInt(); + m_IntReq = reader.ReadInt(); + + goto case 2; + } + case 2: + { + m_Identified = reader.ReadBool(); + + goto case 1; + } + case 1: + { + m_MaxRange = reader.ReadInt(); + + goto case 0; + } + case 0: + { + if (version == 0) + m_MaxRange = 1; // default + + if (version < 5) + { + m_Resource = CraftResource.Iron; + m_AosAttributes = new AosAttributes(this); + m_AosWeaponAttributes = new AosWeaponAttributes(this); + m_AosElementDamages = new AosElementAttributes(this); + m_AosSkillBonuses = new AosSkillBonuses(this); + } + + m_MinDamage = reader.ReadInt(); + m_MaxDamage = reader.ReadInt(); + + m_Speed = reader.ReadInt(); + + m_HitSound = reader.ReadInt(); + m_MissSound = reader.ReadInt(); + + m_Skill = (SkillName)reader.ReadInt(); + m_Type = (WeaponType)reader.ReadInt(); + m_Animation = (WeaponAnimation)reader.ReadInt(); + m_DamageLevel = (WeaponDamageLevel)reader.ReadInt(); + m_AccuracyLevel = (WeaponAccuracyLevel)reader.ReadInt(); + m_DurabilityLevel = (WeaponDurabilityLevel)reader.ReadInt(); + m_Quality = (WeaponQuality)reader.ReadInt(); + + m_Crafter = reader.ReadMobile(); + + m_Poison = Poison.Deserialize(reader); + m_PoisonCharges = reader.ReadInt(); + + if (m_StrReq == OldStrengthReq) + m_StrReq = -1; + + if (m_DexReq == OldDexterityReq) + m_DexReq = -1; + + if (m_IntReq == OldIntelligenceReq) + m_IntReq = -1; + + if (m_MinDamage == OldMinDamage) + m_MinDamage = -1; + + if (m_MaxDamage == OldMaxDamage) + m_MaxDamage = -1; + + if (m_HitSound == OldHitSound) + m_HitSound = -1; + + if (m_MissSound == OldMissSound) + m_MissSound = -1; + + if (m_Speed == OldSpeed) + m_Speed = -1; + + if (m_MaxRange == OldMaxRange) + m_MaxRange = -1; + + if (m_Skill == OldSkill) + m_Skill = (SkillName)(-1); + + if (m_Type == OldType) + m_Type = (WeaponType)(-1); + + if (m_Animation == OldAnimation) + m_Animation = (WeaponAnimation)(-1); + + if (UseSkillMod && m_AccuracyLevel != WeaponAccuracyLevel.Regular && parentMobile != null) + { + m_SkillMod = new DefaultSkillMod(AccuracySkill, true, (int)m_AccuracyLevel * 5); + parentMobile.AddSkillMod(m_SkillMod); + } + + break; + } + } + + if (Core.AOS && parentMobile != null) + m_AosSkillBonuses.AddTo(parentMobile); + + int strBonus = m_AosAttributes.BonusStr; + int dexBonus = m_AosAttributes.BonusDex; + int intBonus = m_AosAttributes.BonusInt; + + if (parentMobile != null && (strBonus != 0 || dexBonus != 0 || intBonus != 0)) + { + string modName = Serial.ToString(); + + if (strBonus != 0) + parentMobile.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + parentMobile.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + parentMobile.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + parentMobile?.CheckStatTimers(); + + if (m_Hits <= 0 && m_MaxHits <= 0) m_Hits = m_MaxHits = Utility.RandomMinMax(InitMinHits, InitMaxHits); + + if (version < 6) + PlayerConstructed = true; // we don't know, so, assume it's crafted + } + + #endregion + } + + public enum CheckSlayerResult + { + None, + Slayer, + Opposition + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Fists.cs b/Scripts/Items/Weapons/Fists.cs index 841168e0a..9f84c3f31 100644 --- a/Scripts/Items/Weapons/Fists.cs +++ b/Scripts/Items/Weapons/Fists.cs @@ -1,309 +1,316 @@ using System; +using Server.Engines.ConPVP; namespace Server.Items { - public class Fists : BaseMeleeWeapon - { - public static void Initialize() - { - Mobile.DefaultWeapon = new Fists(); + public class Fists : BaseMeleeWeapon + { + public Fists() : base(0) + { + Visible = false; + Movable = false; + Quality = WeaponQuality.Regular; + } - EventSink.DisarmRequest += EventSink_DisarmRequest; - EventSink.StunRequest += EventSink_StunRequest; - } + public Fists(Serial serial) : base(serial) + { + } - public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int AosStrengthReq => 0; - public override int AosMinDamage => 1; - public override int AosMaxDamage => 4; - public override int AosSpeed => 50; - public override float MlSpeed => 2.50f; + public override int AosStrengthReq => 0; + public override int AosMinDamage => 1; + public override int AosMaxDamage => 4; + public override int AosSpeed => 50; + public override float MlSpeed => 2.50f; - public override int OldStrengthReq => 0; - public override int OldMinDamage => 1; - public override int OldMaxDamage => 8; - public override int OldSpeed => 30; + public override int OldStrengthReq => 0; + public override int OldMinDamage => 1; + public override int OldMaxDamage => 8; + public override int OldSpeed => 30; - public override int DefHitSound => -1; - public override int DefMissSound => -1; + public override int DefHitSound => -1; + public override int DefMissSound => -1; - public override SkillName DefSkill => SkillName.Wrestling; - public override WeaponType DefType => WeaponType.Fists; - public override WeaponAnimation DefAnimation => WeaponAnimation.Wrestle; + public override SkillName DefSkill => SkillName.Wrestling; + public override WeaponType DefType => WeaponType.Fists; + public override WeaponAnimation DefAnimation => WeaponAnimation.Wrestle; - public Fists() : base( 0 ) - { - Visible = false; - Movable = false; - Quality = WeaponQuality.Regular; - } + public static void Initialize() + { + Mobile.DefaultWeapon = new Fists(); - public Fists( Serial serial ) : base( serial ) - { - } + EventSink.DisarmRequest += EventSink_DisarmRequest; + EventSink.StunRequest += EventSink_StunRequest; + } - public override double GetDefendSkillValue( Mobile attacker, Mobile defender ) - { - double wresValue = defender.Skills[SkillName.Wrestling].Value; - double anatValue = defender.Skills[SkillName.Anatomy].Value; - double evalValue = defender.Skills[SkillName.EvalInt].Value; - double incrValue = (anatValue + evalValue + 20.0) * 0.5; + public override double GetDefendSkillValue(Mobile attacker, Mobile defender) + { + double wresValue = defender.Skills[SkillName.Wrestling].Value; + double anatValue = defender.Skills[SkillName.Anatomy].Value; + double evalValue = defender.Skills[SkillName.EvalInt].Value; + double incrValue = (anatValue + evalValue + 20.0) * 0.5; - if ( incrValue > 120.0 ) - incrValue = 120.0; + if (incrValue > 120.0) + incrValue = 120.0; - if ( wresValue > incrValue ) - return wresValue; - return incrValue; - } + if (wresValue > incrValue) + return wresValue; + return incrValue; + } - private void CheckPreAOSMoves( Mobile attacker, Mobile defender ) - { - if ( attacker.StunReady ) - { - if ( attacker.CanBeginAction( typeof( Fists ) ) ) - { - if ( attacker.Skills[SkillName.Anatomy].Value >= 80.0 && attacker.Skills[SkillName.Wrestling].Value >= 80.0 ) - { - if ( attacker.Stam >= 15 ) - { - attacker.Stam -= 15; + private void CheckPreAOSMoves(Mobile attacker, Mobile defender) + { + if (attacker.StunReady) + { + if (attacker.CanBeginAction(typeof(Fists))) + { + if (attacker.Skills[SkillName.Anatomy].Value >= 80.0 && + attacker.Skills[SkillName.Wrestling].Value >= 80.0) + { + if (attacker.Stam >= 15) + { + attacker.Stam -= 15; - if ( CheckMove( attacker, SkillName.Anatomy ) ) - { - StartMoveDelay( attacker ); + if (CheckMove(attacker, SkillName.Anatomy)) + { + StartMoveDelay(attacker); - attacker.StunReady = false; + attacker.StunReady = false; - attacker.SendLocalizedMessage( 1004013 ); // You successfully stun your opponent! - defender.SendLocalizedMessage( 1004014 ); // You have been stunned! + attacker.SendLocalizedMessage(1004013); // You successfully stun your opponent! + defender.SendLocalizedMessage(1004014); // You have been stunned! - defender.Freeze( TimeSpan.FromSeconds( 4.0 ) ); - } - else - { - attacker.SendLocalizedMessage( 1004010 ); // You failed in your attempt to stun. - defender.SendLocalizedMessage( 1004011 ); // Your opponent tried to stun you and failed. - } - } - else - { - attacker.SendLocalizedMessage( 1004009 ); // You are too fatigued to attempt anything. - } - } - else - { - attacker.SendLocalizedMessage( 1004008 ); // You are not skilled enough to stun your opponent. - attacker.StunReady = false; - } - } - } - else if ( attacker.DisarmReady ) - { - if ( attacker.CanBeginAction( typeof( Fists ) ) ) - { - if ( defender.Player || defender.Body.IsHuman ) - { - if ( attacker.Skills[SkillName.ArmsLore].Value >= 80.0 && attacker.Skills[SkillName.Wrestling].Value >= 80.0 ) - { - if ( attacker.Stam >= 15 ) - { - Item toDisarm = defender.FindItemOnLayer( Layer.OneHanded ); + defender.Freeze(TimeSpan.FromSeconds(4.0)); + } + else + { + attacker.SendLocalizedMessage(1004010); // You failed in your attempt to stun. + defender.SendLocalizedMessage(1004011); // Your opponent tried to stun you and failed. + } + } + else + { + attacker.SendLocalizedMessage(1004009); // You are too fatigued to attempt anything. + } + } + else + { + attacker.SendLocalizedMessage(1004008); // You are not skilled enough to stun your opponent. + attacker.StunReady = false; + } + } + } + else if (attacker.DisarmReady) + { + if (attacker.CanBeginAction(typeof(Fists))) + { + if (defender.Player || defender.Body.IsHuman) + { + if (attacker.Skills[SkillName.ArmsLore].Value >= 80.0 && + attacker.Skills[SkillName.Wrestling].Value >= 80.0) + { + if (attacker.Stam >= 15) + { + Item toDisarm = defender.FindItemOnLayer(Layer.OneHanded); - if ( toDisarm == null || !toDisarm.Movable ) - toDisarm = defender.FindItemOnLayer( Layer.TwoHanded ); + if (toDisarm == null || !toDisarm.Movable) + toDisarm = defender.FindItemOnLayer(Layer.TwoHanded); - Container pack = defender.Backpack; + Container pack = defender.Backpack; - if ( pack == null || toDisarm == null || !toDisarm.Movable ) - { - attacker.SendLocalizedMessage( 1004001 ); // You cannot disarm your opponent. - } - else if ( CheckMove( attacker, SkillName.ArmsLore ) ) - { - StartMoveDelay( attacker ); + if (pack == null || toDisarm == null || !toDisarm.Movable) + { + attacker.SendLocalizedMessage(1004001); // You cannot disarm your opponent. + } + else if (CheckMove(attacker, SkillName.ArmsLore)) + { + StartMoveDelay(attacker); - attacker.Stam -= 15; - attacker.DisarmReady = false; + attacker.Stam -= 15; + attacker.DisarmReady = false; - attacker.SendLocalizedMessage( 1004006 ); // You successfully disarm your opponent! - defender.SendLocalizedMessage( 1004007 ); // You have been disarmed! + attacker.SendLocalizedMessage(1004006); // You successfully disarm your opponent! + defender.SendLocalizedMessage(1004007); // You have been disarmed! - pack.DropItem( toDisarm ); - } - else - { - attacker.Stam -= 15; + pack.DropItem(toDisarm); + } + else + { + attacker.Stam -= 15; - attacker.SendLocalizedMessage( 1004004 ); // You failed in your attempt to disarm. - defender.SendLocalizedMessage( 1004005 ); // Your opponent tried to disarm you but failed. - } - } - else - { - attacker.SendLocalizedMessage( 1004003 ); // You are too fatigued to attempt anything. - } - } - else - { - attacker.SendLocalizedMessage( 1004002 ); // You are not skilled enough to disarm your opponent. - attacker.DisarmReady = false; - } - } - else - { - attacker.SendLocalizedMessage( 1004001 ); // You cannot disarm your opponent. - } - } - } - } + attacker.SendLocalizedMessage(1004004); // You failed in your attempt to disarm. + defender.SendLocalizedMessage(1004005); // Your opponent tried to disarm you but failed. + } + } + else + { + attacker.SendLocalizedMessage(1004003); // You are too fatigued to attempt anything. + } + } + else + { + attacker.SendLocalizedMessage(1004002); // You are not skilled enough to disarm your opponent. + attacker.DisarmReady = false; + } + } + else + { + attacker.SendLocalizedMessage(1004001); // You cannot disarm your opponent. + } + } + } + } - public override TimeSpan OnSwing( Mobile attacker, Mobile defender ) - { - if ( !Core.AOS ) - CheckPreAOSMoves( attacker, defender ); + public override TimeSpan OnSwing(Mobile attacker, Mobile defender) + { + if (!Core.AOS) + CheckPreAOSMoves(attacker, defender); - return base.OnSwing( attacker, defender ); - } + return base.OnSwing(attacker, defender); + } - /*public override void OnMiss( Mobile attacker, Mobile defender ) - { - base.PlaySwingAnimation( attacker ); - }*/ + /*public override void OnMiss( Mobile attacker, Mobile defender ) + { + base.PlaySwingAnimation( attacker ); + }*/ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } + Delete(); + } - /* Wrestling moves */ + /* Wrestling moves */ - private static bool CheckMove( Mobile m, SkillName other ) - { - double wresValue = m.Skills[SkillName.Wrestling].Value; - double scndValue = m.Skills[other].Value; + private static bool CheckMove(Mobile m, SkillName other) + { + double wresValue = m.Skills[SkillName.Wrestling].Value; + double scndValue = m.Skills[other].Value; - /* 40% chance at 80, 80 - * 50% chance at 100, 100 - * 60% chance at 120, 120 - */ + /* 40% chance at 80, 80 + * 50% chance at 100, 100 + * 60% chance at 120, 120 + */ - double chance = (wresValue + scndValue) / 400.0; + double chance = (wresValue + scndValue) / 400.0; - return ( chance >= Utility.RandomDouble() ); - } + return chance >= Utility.RandomDouble(); + } - private static bool HasFreeHands( Mobile m ) - { - Item item = m.FindItemOnLayer( Layer.OneHanded ); + private static bool HasFreeHands(Mobile m) + { + Item item = m.FindItemOnLayer(Layer.OneHanded); - if ( item != null && !(item is Spellbook) ) - return false; + if (item != null && !(item is Spellbook)) + return false; - return m.FindItemOnLayer( Layer.TwoHanded ) == null; - } + return m.FindItemOnLayer(Layer.TwoHanded) == null; + } - private static void EventSink_DisarmRequest( DisarmRequestEventArgs e ) - { - if ( Core.AOS ) - return; + private static void EventSink_DisarmRequest(DisarmRequestEventArgs e) + { + if (Core.AOS) + return; - Mobile m = e.Mobile; + Mobile m = e.Mobile; - #region Dueling - if ( !Engines.ConPVP.DuelContext.AllowSpecialAbility( m, "Disarm", true ) ) - return; - #endregion + #region Dueling - double armsValue = m.Skills[SkillName.ArmsLore].Value; - double wresValue = m.Skills[SkillName.Wrestling].Value; + if (!DuelContext.AllowSpecialAbility(m, "Disarm", true)) + return; - if ( !HasFreeHands( m ) ) - { - m.SendLocalizedMessage( 1004029 ); // You must have your hands free to attempt to disarm your opponent. - m.DisarmReady = false; - } - else if ( armsValue >= 80.0 && wresValue >= 80.0 ) - { - m.DisruptiveAction(); - m.DisarmReady = !m.DisarmReady; - m.SendLocalizedMessage( m.DisarmReady ? 1019013 : 1019014 ); - } - else - { - m.SendLocalizedMessage( 1004002 ); // You are not skilled enough to disarm your opponent. - m.DisarmReady = false; - } - } + #endregion - private static void EventSink_StunRequest( StunRequestEventArgs e ) - { - if ( Core.AOS ) - return; + double armsValue = m.Skills[SkillName.ArmsLore].Value; + double wresValue = m.Skills[SkillName.Wrestling].Value; - Mobile m = e.Mobile; + if (!HasFreeHands(m)) + { + m.SendLocalizedMessage(1004029); // You must have your hands free to attempt to disarm your opponent. + m.DisarmReady = false; + } + else if (armsValue >= 80.0 && wresValue >= 80.0) + { + m.DisruptiveAction(); + m.DisarmReady = !m.DisarmReady; + m.SendLocalizedMessage(m.DisarmReady ? 1019013 : 1019014); + } + else + { + m.SendLocalizedMessage(1004002); // You are not skilled enough to disarm your opponent. + m.DisarmReady = false; + } + } - #region Dueling - if ( !Engines.ConPVP.DuelContext.AllowSpecialAbility( m, "Stun", true ) ) - return; - #endregion + private static void EventSink_StunRequest(StunRequestEventArgs e) + { + if (Core.AOS) + return; - double anatValue = m.Skills[SkillName.Anatomy].Value; - double wresValue = m.Skills[SkillName.Wrestling].Value; + Mobile m = e.Mobile; - if ( !HasFreeHands( m ) ) - { - m.SendLocalizedMessage( 1004031 ); // You must have your hands free to attempt to stun your opponent. - m.StunReady = false; - } - else if ( anatValue >= 80.0 && wresValue >= 80.0 ) - { - m.DisruptiveAction(); - m.StunReady = !m.StunReady; - m.SendLocalizedMessage( m.StunReady ? 1019011 : 1019012 ); - } - else - { - m.SendLocalizedMessage( 1004008 ); // You are not skilled enough to stun your opponent. - m.StunReady = false; - } - } + #region Dueling - private class MoveDelayTimer : Timer - { - private Mobile m_Mobile; + if (!DuelContext.AllowSpecialAbility(m, "Stun", true)) + return; - public MoveDelayTimer( Mobile m ) : base( TimeSpan.FromSeconds( 10.0 ) ) - { - m_Mobile = m; + #endregion - Priority = TimerPriority.TwoFiftyMS; + double anatValue = m.Skills[SkillName.Anatomy].Value; + double wresValue = m.Skills[SkillName.Wrestling].Value; - m_Mobile.BeginAction( typeof( Fists ) ); - } + if (!HasFreeHands(m)) + { + m.SendLocalizedMessage(1004031); // You must have your hands free to attempt to stun your opponent. + m.StunReady = false; + } + else if (anatValue >= 80.0 && wresValue >= 80.0) + { + m.DisruptiveAction(); + m.StunReady = !m.StunReady; + m.SendLocalizedMessage(m.StunReady ? 1019011 : 1019012); + } + else + { + m.SendLocalizedMessage(1004008); // You are not skilled enough to stun your opponent. + m.StunReady = false; + } + } - protected override void OnTick() - { - m_Mobile.EndAction( typeof( Fists ) ); - } - } + private static void StartMoveDelay(Mobile m) + { + new MoveDelayTimer(m).Start(); + } - private static void StartMoveDelay( Mobile m ) - { - new MoveDelayTimer( m ).Start(); - } - } -} + private class MoveDelayTimer : Timer + { + private Mobile m_Mobile; + + public MoveDelayTimer(Mobile m) : base(TimeSpan.FromSeconds(10.0)) + { + m_Mobile = m; + + Priority = TimerPriority.TwoFiftyMS; + + m_Mobile.BeginAction(typeof(Fists)); + } + + protected override void OnTick() + { + m_Mobile.EndAction(typeof(Fists)); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/HitLower.cs b/Scripts/Items/Weapons/HitLower.cs index acd5c733d..a8cc9386f 100644 --- a/Scripts/Items/Weapons/HitLower.cs +++ b/Scripts/Items/Weapons/HitLower.cs @@ -3,93 +3,93 @@ using System.Collections; namespace Server.Items { - public class HitLower - { - public static readonly TimeSpan AttackEffectDuration = TimeSpan.FromSeconds( 10.0 ); - public static readonly TimeSpan DefenseEffectDuration = TimeSpan.FromSeconds( 8.0 ); + public class HitLower + { + public static readonly TimeSpan AttackEffectDuration = TimeSpan.FromSeconds(10.0); + public static readonly TimeSpan DefenseEffectDuration = TimeSpan.FromSeconds(8.0); - private static Hashtable m_AttackTable = new Hashtable(); + private static Hashtable m_AttackTable = new Hashtable(); - public static bool IsUnderAttackEffect( Mobile m ) - { - return m_AttackTable.Contains( m ); - } + private static Hashtable m_DefenseTable = new Hashtable(); - public static bool ApplyAttack( Mobile m ) - { - if ( IsUnderAttackEffect( m ) ) - return false; + public static bool IsUnderAttackEffect(Mobile m) + { + return m_AttackTable.Contains(m); + } - m_AttackTable[m] = new AttackTimer( m ); - m.SendLocalizedMessage( 1062319 ); // Your attack chance has been reduced! - return true; - } + public static bool ApplyAttack(Mobile m) + { + if (IsUnderAttackEffect(m)) + return false; - private static void RemoveAttack( Mobile m ) - { - m_AttackTable.Remove( m ); - m.SendLocalizedMessage( 1062320 ); // Your attack chance has returned to normal. - } + m_AttackTable[m] = new AttackTimer(m); + m.SendLocalizedMessage(1062319); // Your attack chance has been reduced! + return true; + } - private class AttackTimer : Timer - { - private Mobile m_Player; + private static void RemoveAttack(Mobile m) + { + m_AttackTable.Remove(m); + m.SendLocalizedMessage(1062320); // Your attack chance has returned to normal. + } - public AttackTimer( Mobile player ) : base( AttackEffectDuration ) - { - m_Player = player; + public static bool IsUnderDefenseEffect(Mobile m) + { + return m_DefenseTable.Contains(m); + } - Priority = TimerPriority.TwoFiftyMS; + public static bool ApplyDefense(Mobile m) + { + if (IsUnderDefenseEffect(m)) + return false; - Start(); - } + m_DefenseTable[m] = new DefenseTimer(m); + m.SendLocalizedMessage(1062318); // Your defense chance has been reduced! + return true; + } - protected override void OnTick() - { - RemoveAttack( m_Player ); - } - } + private static void RemoveDefense(Mobile m) + { + m_DefenseTable.Remove(m); + m.SendLocalizedMessage(1062321); // Your defense chance has returned to normal. + } - private static Hashtable m_DefenseTable = new Hashtable(); + private class AttackTimer : Timer + { + private Mobile m_Player; - public static bool IsUnderDefenseEffect( Mobile m ) - { - return m_DefenseTable.Contains( m ); - } + public AttackTimer(Mobile player) : base(AttackEffectDuration) + { + m_Player = player; - public static bool ApplyDefense( Mobile m ) - { - if ( IsUnderDefenseEffect( m ) ) - return false; + Priority = TimerPriority.TwoFiftyMS; - m_DefenseTable[m] = new DefenseTimer( m ); - m.SendLocalizedMessage( 1062318 ); // Your defense chance has been reduced! - return true; - } + Start(); + } - private static void RemoveDefense( Mobile m ) - { - m_DefenseTable.Remove( m ); - m.SendLocalizedMessage( 1062321 ); // Your defense chance has returned to normal. - } + protected override void OnTick() + { + RemoveAttack(m_Player); + } + } - private class DefenseTimer : Timer - { - private Mobile m_Player; + private class DefenseTimer : Timer + { + private Mobile m_Player; - public DefenseTimer( Mobile player ) : base( DefenseEffectDuration ) - { - m_Player = player; + public DefenseTimer(Mobile player) : base(DefenseEffectDuration) + { + m_Player = player; - Priority = TimerPriority.TwoFiftyMS; + Priority = TimerPriority.TwoFiftyMS; - Start(); - } + Start(); + } - protected override void OnTick() - { - RemoveDefense( m_Player ); - } - } - } + protected override void OnTick() + { + RemoveDefense(m_Player); + } + } + } } \ No newline at end of file diff --git a/Scripts/Items/Weapons/Knives/BaseKnife.cs b/Scripts/Items/Weapons/Knives/BaseKnife.cs index 33dcb76c0..6b6675ac6 100644 --- a/Scripts/Items/Weapons/Knives/BaseKnife.cs +++ b/Scripts/Items/Weapons/Knives/BaseKnife.cs @@ -2,55 +2,55 @@ using Server.Targets; namespace Server.Items { - public abstract class BaseKnife : BaseMeleeWeapon - { - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x238; + public abstract class BaseKnife : BaseMeleeWeapon + { + public BaseKnife(int itemID) : base(itemID) + { + } - public override SkillName DefSkill => SkillName.Swords; - public override WeaponType DefType => WeaponType.Slashing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; + public BaseKnife(Serial serial) : base(serial) + { + } - public BaseKnife( int itemID ) : base( itemID ) - { - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x238; - public BaseKnife( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Swords; + public override WeaponType DefType => WeaponType.Slashing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 1010018 ); // What do you want to use this item on? + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(1010018); // What do you want to use this item on? - from.Target = new BladedItemTarget( this ); - } + from.Target = new BladedItemTarget(this); + } - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - if ( !Core.AOS && Poison != null && PoisonCharges > 0 ) - { - --PoisonCharges; + if (!Core.AOS && Poison != null && PoisonCharges > 0) + { + --PoisonCharges; - if ( Utility.RandomDouble() >= 0.5 ) // 50% chance to poison - defender.ApplyPoison( attacker, Poison ); - } - } - } -} + if (Utility.RandomDouble() >= 0.5) // 50% chance to poison + defender.ApplyPoison(attacker, Poison); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Knives/ButcherKnife.cs b/Scripts/Items/Weapons/Knives/ButcherKnife.cs index e5320a706..4dd097708 100644 --- a/Scripts/Items/Weapons/Knives/ButcherKnife.cs +++ b/Scripts/Items/Weapons/Knives/ButcherKnife.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x13F6, 0x13F7 )] - public class ButcherKnife : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.InfectiousStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Flippable(0x13F6, 0x13F7)] + public class ButcherKnife : BaseKnife + { + [Constructible] + public ButcherKnife() : base(0x13F6) + { + Weight = 1.0; + } - public override int AosStrengthReq => 5; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 49; - public override float MlSpeed => 2.25f; + public ButcherKnife(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 5; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 14; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.InfectiousStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 40; + public override int AosStrengthReq => 5; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 49; + public override float MlSpeed => 2.25f; - [Constructible] - public ButcherKnife() : base( 0x13F6 ) - { - Weight = 1.0; - } + public override int OldStrengthReq => 5; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 14; + public override int OldSpeed => 40; - public ButcherKnife( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 40; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Knives/Cleaver.cs b/Scripts/Items/Weapons/Knives/Cleaver.cs index 4dd280776..3811ac40f 100644 --- a/Scripts/Items/Weapons/Knives/Cleaver.cs +++ b/Scripts/Items/Weapons/Knives/Cleaver.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0xEC3, 0xEC2 )] - public class Cleaver : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; + [Flippable(0xEC3, 0xEC2)] + public class Cleaver : BaseKnife + { + [Constructible] + public Cleaver() : base(0xEC3) + { + Weight = 2.0; + } - public override int AosStrengthReq => 10; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 13; - public override int AosSpeed => 46; - public override float MlSpeed => 2.50f; + public Cleaver(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 13; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 50; + public override int AosStrengthReq => 10; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 13; + public override int AosSpeed => 46; + public override float MlSpeed => 2.50f; - [Constructible] - public Cleaver() : base( 0xEC3 ) - { - Weight = 2.0; - } + public override int OldStrengthReq => 10; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 13; + public override int OldSpeed => 40; - public Cleaver( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 50; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Knives/Dagger.cs b/Scripts/Items/Weapons/Knives/Dagger.cs index 864c3d1ac..37cfade1c 100644 --- a/Scripts/Items/Weapons/Knives/Dagger.cs +++ b/Scripts/Items/Weapons/Knives/Dagger.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0xF52, 0xF51 )] - public class Dagger : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.InfectiousStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; + [Flippable(0xF52, 0xF51)] + public class Dagger : BaseKnife + { + [Constructible] + public Dagger() : base(0xF52) + { + Weight = 1.0; + } - public override int AosStrengthReq => 10; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 11; - public override int AosSpeed => 56; - public override float MlSpeed => 2.00f; + public Dagger(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 1; - public override int OldMinDamage => 3; - public override int OldMaxDamage => 15; - public override int OldSpeed => 55; + public override WeaponAbility PrimaryAbility => WeaponAbility.InfectiousStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 40; + public override int AosStrengthReq => 10; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 11; + public override int AosSpeed => 56; + public override float MlSpeed => 2.00f; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int OldStrengthReq => 1; + public override int OldMinDamage => 3; + public override int OldMaxDamage => 15; + public override int OldSpeed => 55; - [Constructible] - public Dagger() : base( 0xF52 ) - { - Weight = 1.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 40; - public Dagger( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Knives/SkinningKnife.cs b/Scripts/Items/Weapons/Knives/SkinningKnife.cs index 4db86f9da..353fac536 100644 --- a/Scripts/Items/Weapons/Knives/SkinningKnife.cs +++ b/Scripts/Items/Weapons/Knives/SkinningKnife.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xEC4, 0xEC5 )] - public class SkinningKnife : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ShadowStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Flippable(0xEC4, 0xEC5)] + public class SkinningKnife : BaseKnife + { + [Constructible] + public SkinningKnife() : base(0xEC4) + { + Weight = 1.0; + } - public override int AosStrengthReq => 5; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 49; - public override float MlSpeed => 2.25f; + public SkinningKnife(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 5; - public override int OldMinDamage => 1; - public override int OldMaxDamage => 10; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.ShadowStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 40; + public override int AosStrengthReq => 5; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 49; + public override float MlSpeed => 2.25f; - [Constructible] - public SkinningKnife() : base( 0xEC4 ) - { - Weight = 1.0; - } + public override int OldStrengthReq => 5; + public override int OldMinDamage => 1; + public override int OldMaxDamage => 10; + public override int OldSpeed => 40; - public SkinningKnife( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 40; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Knives/ThrowingDagger.cs b/Scripts/Items/Weapons/Knives/ThrowingDagger.cs index b41d29485..df6ec41d6 100644 --- a/Scripts/Items/Weapons/Knives/ThrowingDagger.cs +++ b/Scripts/Items/Weapons/Knives/ThrowingDagger.cs @@ -3,118 +3,131 @@ using Server.Targeting; namespace Server.Items { - [FlippableAttribute( 0xF52, 0xF51 )] - public class ThrowingDagger : Item - { - public override string DefaultName => "a throwing dagger"; + [Flippable(0xF52, 0xF51)] + public class ThrowingDagger : Item + { + [Constructible] + public ThrowingDagger() : base(0xF52) + { + Weight = 1.0; + Layer = Layer.OneHanded; + } - [Constructible] - public ThrowingDagger() : base( 0xF52 ) - { - Weight = 1.0; - Layer = Layer.OneHanded; - } + public ThrowingDagger(Serial serial) : base(serial) + { + } - public ThrowingDagger( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a throwing dagger"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.Items.Contains( this ) ) - { - InternalTarget t = new InternalTarget( this ); - from.Target = t; - } - else - { - from.SendMessage( "You must be holding that weapon to use it." ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (from.Items.Contains(this)) + { + InternalTarget t = new InternalTarget(this); + from.Target = t; + } + else + { + from.SendMessage("You must be holding that weapon to use it."); + } + } - private class InternalTarget : Target - { - private ThrowingDagger m_Dagger; + private class InternalTarget : Target + { + private ThrowingDagger m_Dagger; - public InternalTarget( ThrowingDagger dagger ) : base( 10, false, TargetFlags.Harmful ) - { - m_Dagger = dagger; - } + public InternalTarget(ThrowingDagger dagger) : base(10, false, TargetFlags.Harmful) + { + m_Dagger = dagger; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Dagger.Deleted ) - { - return; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Dagger.Deleted) return; - if ( !from.Items.Contains( m_Dagger ) ) - { - from.SendMessage( "You must be holding that weapon to use it." ); - } - else if ( targeted is Mobile m ) - { - if ( m != from && from.HarmfulCheck( m ) ) - { - Direction to = from.GetDirectionTo( m ); + if (!from.Items.Contains(m_Dagger)) + from.SendMessage("You must be holding that weapon to use it."); + else if (targeted is Mobile m) + if (m != from && from.HarmfulCheck(m)) + { + Direction to = from.GetDirectionTo(m); - from.Direction = to; + from.Direction = to; - from.Animate( from.Mounted ? 26 : 9, 7, 1, true, false, 0 ); + from.Animate(from.Mounted ? 26 : 9, 7, 1, true, false, 0); - if ( Utility.RandomDouble() >= (Math.Sqrt( m.Dex / 100.0 ) * 0.8) ) - { - from.MovingEffect( m, 0x1BFE, 7, 1, false, false, 0x481, 0 ); + if (Utility.RandomDouble() >= Math.Sqrt(m.Dex / 100.0) * 0.8) + { + from.MovingEffect(m, 0x1BFE, 7, 1, false, false, 0x481, 0); - AOS.Damage( m, from, Utility.Random( 5, from.Str / 10 ), 100, 0, 0, 0, 0 ); + AOS.Damage(m, from, Utility.Random(5, from.Str / 10), 100, 0, 0, 0, 0); - m_Dagger.MoveToWorld( m.Location, m.Map ); - } - else - { - int x = 0, y = 0; + m_Dagger.MoveToWorld(m.Location, m.Map); + } + else + { + int x = 0, y = 0; - switch ( to & Direction.Mask ) - { - case Direction.North: --y; break; - case Direction.South: ++y; break; - case Direction.West: --x; break; - case Direction.East: ++x; break; - case Direction.Up: --x; --y; break; - case Direction.Down: ++x; ++y; break; - case Direction.Left: --x; ++y; break; - case Direction.Right: ++x; --y; break; - } + switch (to & Direction.Mask) + { + case Direction.North: + --y; + break; + case Direction.South: + ++y; + break; + case Direction.West: + --x; + break; + case Direction.East: + ++x; + break; + case Direction.Up: + --x; + --y; + break; + case Direction.Down: + ++x; + ++y; + break; + case Direction.Left: + --x; + ++y; + break; + case Direction.Right: + ++x; + --y; + break; + } - x += Utility.Random( -1, 3 ); - y += Utility.Random( -1, 3 ); + x += Utility.Random(-1, 3); + y += Utility.Random(-1, 3); - x += m.X; - y += m.Y; + x += m.X; + y += m.Y; - m_Dagger.MoveToWorld( new Point3D( x, y, m.Z ), m.Map ); + m_Dagger.MoveToWorld(new Point3D(x, y, m.Z), m.Map); - from.MovingEffect( m_Dagger, 0x1BFE, 7, 1, false, false, 0x481, 0 ); + from.MovingEffect(m_Dagger, 0x1BFE, 7, 1, false, false, 0x481, 0); - from.SendMessage( "You miss." ); - } - } - } - } - } - } -} + from.SendMessage("You miss."); + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/BlightGrippedLongbow.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/BlightGrippedLongbow.cs index 69a9ef028..9934fff92 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/BlightGrippedLongbow.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/BlightGrippedLongbow.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class BlightGrippedLongbow : ElvenCompositeLongbow - { - public override int LabelNumber => 1072907; // Blight Gripped Longbow + public class BlightGrippedLongbow : ElvenCompositeLongbow + { + [Constructible] + public BlightGrippedLongbow() + { + Hue = 0x8A4; - [Constructible] - public BlightGrippedLongbow() - { - Hue = 0x8A4; + WeaponAttributes.HitPoisonArea = 20; + Attributes.RegenStam = 3; + Attributes.NightSight = 1; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 35; + } - WeaponAttributes.HitPoisonArea = 20; - Attributes.RegenStam = 3; - Attributes.NightSight = 1; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 35; - } + public BlightGrippedLongbow(Serial serial) : base(serial) + { + } - public BlightGrippedLongbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072907; // Blight Gripped Longbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/ColdForgedBlade.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/ColdForgedBlade.cs index 8af7ea4b6..e74627ee9 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/ColdForgedBlade.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/ColdForgedBlade.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class ColdForgedBlade : ElvenSpellblade - { - public override int LabelNumber => 1072916; // Cold Forged Blade + public class ColdForgedBlade : ElvenSpellblade + { + [Constructible] + public ColdForgedBlade() + { + WeaponAttributes.HitHarm = 40; + Attributes.SpellChanneling = 1; + Attributes.NightSight = 1; + Attributes.WeaponSpeed = 25; + Attributes.WeaponDamage = 50; - [Constructible] - public ColdForgedBlade() - { - WeaponAttributes.HitHarm = 40; - Attributes.SpellChanneling = 1; - Attributes.NightSight = 1; - Attributes.WeaponSpeed = 25; - Attributes.WeaponDamage = 50; + Hue = GetElementalDamageHue(); + } - Hue = GetElementalDamageHue(); - } + public ColdForgedBlade(Serial serial) : base(serial) + { + } - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = pois = nrgy = chaos = direct = 0; - cold = 100; - } + public override int LabelNumber => 1072916; // Cold Forged Blade - public ColdForgedBlade( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = pois = nrgy = chaos = direct = 0; + cold = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/LuminousRuneBlade.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/LuminousRuneBlade.cs index e2069a2ec..541ae26de 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/LuminousRuneBlade.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/LuminousRuneBlade.cs @@ -1,43 +1,44 @@ namespace Server.Items { - public class LuminousRuneBlade : RuneBlade - { - public override int LabelNumber => 1072922; // Luminous Rune Blade + public class LuminousRuneBlade : RuneBlade + { + [Constructible] + public LuminousRuneBlade() + { + WeaponAttributes.HitLightning = 40; + WeaponAttributes.SelfRepair = 5; + Attributes.NightSight = 1; + Attributes.WeaponSpeed = 25; + Attributes.WeaponDamage = 55; - [Constructible] - public LuminousRuneBlade() - { - WeaponAttributes.HitLightning = 40; - WeaponAttributes.SelfRepair = 5; - Attributes.NightSight = 1; - Attributes.WeaponSpeed = 25; - Attributes.WeaponDamage = 55; + Hue = GetElementalDamageHue(); + } - Hue = GetElementalDamageHue(); - } + public LuminousRuneBlade(Serial serial) : base(serial) + { + } - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = chaos = direct = 0; - nrgy = 100; - } + public override int LabelNumber => 1072922; // Luminous Rune Blade - public LuminousRuneBlade( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = chaos = direct = 0; + nrgy = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/OverseerSunderedBlade.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/OverseerSunderedBlade.cs index 42655b308..84859fefe 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/OverseerSunderedBlade.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/OverseerSunderedBlade.cs @@ -1,45 +1,46 @@ namespace Server.Items { - public class OverseerSunderedBlade : RadiantScimitar - { - public override int LabelNumber => 1072920; // Overseer Sundered Blade + public class OverseerSunderedBlade : RadiantScimitar + { + [Constructible] + public OverseerSunderedBlade() + { + ItemID = 0x2D27; + Hue = 0x485; - [Constructible] - public OverseerSunderedBlade() - { - ItemID = 0x2D27; - Hue = 0x485; + Attributes.RegenStam = 2; + Attributes.AttackChance = 10; + Attributes.WeaponSpeed = 35; + Attributes.WeaponDamage = 45; - Attributes.RegenStam = 2; - Attributes.AttackChance = 10; - Attributes.WeaponSpeed = 35; - Attributes.WeaponDamage = 45; + Hue = GetElementalDamageHue(); + } - Hue = GetElementalDamageHue(); - } + public OverseerSunderedBlade(Serial serial) : base(serial) + { + } - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = cold = pois = nrgy = chaos = direct = 0; - fire = 100; - } + public override int LabelNumber => 1072920; // Overseer Sundered Blade - public OverseerSunderedBlade( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = cold = pois = nrgy = chaos = direct = 0; + fire = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/PhantomStaff.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/PhantomStaff.cs index 2b7434ee0..2aa7ede82 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/PhantomStaff.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/PhantomStaff.cs @@ -1,41 +1,42 @@ namespace Server.Items { - public class PhantomStaff : WildStaff - { - public override int LabelNumber => 1072919; // Phantom Staff + public class PhantomStaff : WildStaff + { + [Constructible] + public PhantomStaff() + { + Hue = 0x1; + Attributes.RegenHits = 2; + Attributes.NightSight = 1; + Attributes.WeaponSpeed = 20; + Attributes.WeaponDamage = 60; + } - [Constructible] - public PhantomStaff() - { - Hue = 0x1; - Attributes.RegenHits = 2; - Attributes.NightSight = 1; - Attributes.WeaponSpeed = 20; - Attributes.WeaponDamage = 60; - } + public PhantomStaff(Serial serial) : base(serial) + { + } - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = nrgy = chaos = direct = 0; - cold = pois = 50; - } + public override int LabelNumber => 1072919; // Phantom Staff - public PhantomStaff( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = nrgy = chaos = direct = 0; + cold = pois = 50; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/RuneCarvingKnife.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/RuneCarvingKnife.cs index 72469832d..bd7f2de16 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/RuneCarvingKnife.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/RuneCarvingKnife.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class RuneCarvingKnife : AssassinSpike - { - public override int LabelNumber => 1072915; // Rune Carving Knife + public class RuneCarvingKnife : AssassinSpike + { + [Constructible] + public RuneCarvingKnife() + { + Hue = 0x48D; - [Constructible] - public RuneCarvingKnife() - { - Hue = 0x48D; + WeaponAttributes.HitLeechMana = 40; + Attributes.RegenStam = 2; + Attributes.LowerManaCost = 10; + Attributes.WeaponSpeed = 35; + Attributes.WeaponDamage = 30; + } - WeaponAttributes.HitLeechMana = 40; - Attributes.RegenStam = 2; - Attributes.LowerManaCost = 10; - Attributes.WeaponSpeed = 35; - Attributes.WeaponDamage = 30; - } + public RuneCarvingKnife(Serial serial) : base(serial) + { + } - public RuneCarvingKnife( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072915; // Rune Carving Knife - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/ShardTrasher.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/ShardTrasher.cs index 568c06a7b..5d8f1f541 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/ShardTrasher.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/ShardTrasher.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class ShardThrasher : DiamondMace - { - public override int LabelNumber => 1072918; // Shard Thrasher + public class ShardThrasher : DiamondMace + { + [Constructible] + public ShardThrasher() + { + Hue = 0x4F2; - [Constructible] - public ShardThrasher() - { - Hue = 0x4F2; + WeaponAttributes.HitPhysicalArea = 30; + Attributes.BonusStam = 8; + Attributes.AttackChance = 10; + Attributes.WeaponSpeed = 35; + Attributes.WeaponDamage = 40; + } - WeaponAttributes.HitPhysicalArea = 30; - Attributes.BonusStam = 8; - Attributes.AttackChance = 10; - Attributes.WeaponSpeed = 35; - Attributes.WeaponDamage = 40; - } + public ShardThrasher(Serial serial) : base(serial) + { + } - public ShardThrasher( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072918; // Shard Thrasher - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/SilvanisFeywoodBow.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/SilvanisFeywoodBow.cs index 40091e566..9bfa6fdb8 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/SilvanisFeywoodBow.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/SilvanisFeywoodBow.cs @@ -1,42 +1,43 @@ namespace Server.Items { - public class SilvanisFeywoodBow : ElvenCompositeLongbow - { - public override int LabelNumber => 1072955; // Silvani's Feywood Bow + public class SilvanisFeywoodBow : ElvenCompositeLongbow + { + [Constructible] + public SilvanisFeywoodBow() + { + Hue = 0x1A; - [Constructible] - public SilvanisFeywoodBow() - { - Hue = 0x1A; + Attributes.SpellChanneling = 1; + Attributes.AttackChance = 12; + Attributes.WeaponSpeed = 30; + Attributes.WeaponDamage = 35; + } - Attributes.SpellChanneling = 1; - Attributes.AttackChance = 12; - Attributes.WeaponSpeed = 30; - Attributes.WeaponDamage = 35; - } + public SilvanisFeywoodBow(Serial serial) : base(serial) + { + } - public override void GetDamageTypes( Mobile wielder, out int phys, out int fire, out int cold, out int pois, out int nrgy, out int chaos, out int direct ) - { - phys = fire = cold = pois = chaos = direct = 0; - nrgy = 100; - } + public override int LabelNumber => 1072955; // Silvani's Feywood Bow - public SilvanisFeywoodBow( Serial serial ) : base( serial ) - { - } + public override void GetDamageTypes(Mobile wielder, out int phys, out int fire, out int cold, out int pois, + out int nrgy, out int chaos, out int direct) + { + phys = fire = cold = pois = chaos = direct = 0; + nrgy = 100; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Artifacts/TheNightReaper.cs b/Scripts/Items/Weapons/ML Weapons/Artifacts/TheNightReaper.cs index bcbbf3e11..99d1252dd 100644 --- a/Scripts/Items/Weapons/ML Weapons/Artifacts/TheNightReaper.cs +++ b/Scripts/Items/Weapons/ML Weapons/Artifacts/TheNightReaper.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class TheNightReaper : RepeatingCrossbow - { - public override int LabelNumber => 1072912; // The Night Reaper + public class TheNightReaper : RepeatingCrossbow + { + [Constructible] + public TheNightReaper() + { + ItemID = 0x26CD; + Hue = 0x41C; - [Constructible] - public TheNightReaper() - { - ItemID = 0x26CD; - Hue = 0x41C; + Slayer = SlayerName.Exorcism; + Attributes.NightSight = 1; + Attributes.WeaponSpeed = 25; + Attributes.WeaponDamage = 55; + } - Slayer = SlayerName.Exorcism; - Attributes.NightSight = 1; - Attributes.WeaponSpeed = 25; - Attributes.WeaponDamage = 55; - } + public TheNightReaper(Serial serial) : base(serial) + { + } - public TheNightReaper( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1072912; // The Night Reaper - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/AssassinSpike.cs b/Scripts/Items/Weapons/ML Weapons/AssassinSpike.cs index cd9938b01..0a4d99c25 100644 --- a/Scripts/Items/Weapons/ML Weapons/AssassinSpike.cs +++ b/Scripts/Items/Weapons/ML Weapons/AssassinSpike.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2D21, 0x2D2D )] - public class AssassinSpike : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.InfectiousStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; + [Flippable(0x2D21, 0x2D2D)] + public class AssassinSpike : BaseKnife + { + [Constructible] + public AssassinSpike() : base(0x2D21) + { + Weight = 4.0; + } - public override int AosStrengthReq => 15; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 12; - public override int AosSpeed => 50; - public override float MlSpeed => 2.00f; + public AssassinSpike(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 12; - public override int OldSpeed => 50; + public override WeaponAbility PrimaryAbility => WeaponAbility.InfectiousStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; - public override int DefMissSound => 0x239; - public override SkillName DefSkill => SkillName.Fencing; + public override int AosStrengthReq => 15; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 12; + public override int AosSpeed => 50; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 30; // TODO - public override int InitMaxHits => 60; // TODO + public override int OldStrengthReq => 15; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 12; + public override int OldSpeed => 50; - [Constructible] - public AssassinSpike() : base( 0x2D21 ) - { - Weight = 4.0; - } + public override int DefMissSound => 0x239; + public override SkillName DefSkill => SkillName.Fencing; - public AssassinSpike( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; // TODO + public override int InitMaxHits => 60; // TODO - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/ButchersWarCleaver.cs b/Scripts/Items/Weapons/ML Weapons/ButchersWarCleaver.cs index dd7f34f76..6adbec2c1 100644 --- a/Scripts/Items/Weapons/ML Weapons/ButchersWarCleaver.cs +++ b/Scripts/Items/Weapons/ML Weapons/ButchersWarCleaver.cs @@ -1,37 +1,37 @@ namespace Server.Items { - public class ButchersWarCleaver : WarCleaver - { - public override int LabelNumber => 1073526; // butcher's war cleaver + public class ButchersWarCleaver : WarCleaver + { + [Constructible] + public ButchersWarCleaver() + { + } - [Constructible] - public ButchersWarCleaver() - { - } + public ButchersWarCleaver(Serial serial) : base(serial) + { + } - public ButchersWarCleaver( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073526; // butcher's war cleaver - public override void AppendChildNameProperties( ObjectPropertyList list ) - { - base.AppendChildNameProperties( list ); + public override void AppendChildNameProperties(ObjectPropertyList list) + { + base.AppendChildNameProperties(list); - list.Add( 1072512 ); // Bovine Slayer - } + list.Add(1072512); // Bovine Slayer + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/DiamondMace.cs b/Scripts/Items/Weapons/ML Weapons/DiamondMace.cs index fd0d900f1..c031b0f79 100644 --- a/Scripts/Items/Weapons/ML Weapons/DiamondMace.cs +++ b/Scripts/Items/Weapons/ML Weapons/DiamondMace.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2D24, 0x2D30 )] - public class DiamondMace : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; + [Flippable(0x2D24, 0x2D30)] + public class DiamondMace : BaseBashing + { + [Constructible] + public DiamondMace() : base(0x2D24) + { + Weight = 10.0; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 17; - public override int AosSpeed => 37; - public override float MlSpeed => 3.00f; + public DiamondMace(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 14; - public override int OldMaxDamage => 17; - public override int OldSpeed => 37; + public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; - public override int InitMinHits => 30; // TODO - public override int InitMaxHits => 60; // TODO + public override int AosStrengthReq => 35; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 17; + public override int AosSpeed => 37; + public override float MlSpeed => 3.00f; - [Constructible] - public DiamondMace() : base( 0x2D24 ) - { - Weight = 10.0; - } + public override int OldStrengthReq => 35; + public override int OldMinDamage => 14; + public override int OldMaxDamage => 17; + public override int OldSpeed => 37; - public DiamondMace( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; // TODO + public override int InitMaxHits => 60; // TODO - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/ElvenCompositeLongbow.cs b/Scripts/Items/Weapons/ML Weapons/ElvenCompositeLongbow.cs index 6897e4b3d..83961ec2c 100644 --- a/Scripts/Items/Weapons/ML Weapons/ElvenCompositeLongbow.cs +++ b/Scripts/Items/Weapons/ML Weapons/ElvenCompositeLongbow.cs @@ -2,56 +2,56 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x2D1E, 0x2D2A )] - public class ElvenCompositeLongbow : BaseRanged - { - public override int EffectID => 0xF42; - public override Type AmmoType => typeof( Arrow ); - public override Item Ammo => new Arrow(); + [Flippable(0x2D1E, 0x2D2A)] + public class ElvenCompositeLongbow : BaseRanged + { + [Constructible] + public ElvenCompositeLongbow() : base(0x2D1E) + { + Weight = 8.0; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.ForceArrow; - public override WeaponAbility SecondaryAbility => WeaponAbility.SerpentArrow; + public ElvenCompositeLongbow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 16; - public override int AosSpeed => 27; - public override float MlSpeed => 4.00f; + public override int EffectID => 0xF42; + public override Type AmmoType => typeof(Arrow); + public override Item Ammo => new Arrow(); - public override int OldStrengthReq => 45; - public override int OldMinDamage => 12; - public override int OldMaxDamage => 16; - public override int OldSpeed => 27; + public override WeaponAbility PrimaryAbility => WeaponAbility.ForceArrow; + public override WeaponAbility SecondaryAbility => WeaponAbility.SerpentArrow; - public override int DefMaxRange => 10; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 16; + public override int AosSpeed => 27; + public override float MlSpeed => 4.00f; - public override int InitMinHits => 41; - public override int InitMaxHits => 90; + public override int OldStrengthReq => 45; + public override int OldMinDamage => 12; + public override int OldMaxDamage => 16; + public override int OldSpeed => 27; - public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; + public override int DefMaxRange => 10; - [Constructible] - public ElvenCompositeLongbow() : base( 0x2D1E ) - { - Weight = 8.0; - } + public override int InitMinHits => 41; + public override int InitMaxHits => 90; - public ElvenCompositeLongbow( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/ElvenMachete.cs b/Scripts/Items/Weapons/ML Weapons/ElvenMachete.cs index ef0aa3e70..ba861a8aa 100644 --- a/Scripts/Items/Weapons/ML Weapons/ElvenMachete.cs +++ b/Scripts/Items/Weapons/ML Weapons/ElvenMachete.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2D35, 0x2D29 )] - public class ElvenMachete : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DefenseMastery; - public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; + [Flippable(0x2D35, 0x2D29)] + public class ElvenMachete : BaseSword + { + [Constructible] + public ElvenMachete() : base(0x2D35) + { + Weight = 6.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 41; - public override float MlSpeed => 2.75f; + public ElvenMachete(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 13; - public override int OldMaxDamage => 15; - public override int OldSpeed => 41; + public override WeaponAbility PrimaryAbility => WeaponAbility.DefenseMastery; + public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 41; + public override float MlSpeed => 2.75f; - public override int InitMinHits => 30; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 20; + public override int OldMinDamage => 13; + public override int OldMaxDamage => 15; + public override int OldSpeed => 41; - [Constructible] - public ElvenMachete() : base( 0x2D35 ) - { - Weight = 6.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x239; - public ElvenMachete( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/ElvenSpellblade.cs b/Scripts/Items/Weapons/ML Weapons/ElvenSpellblade.cs index 6be3616cd..8260c9c8a 100644 --- a/Scripts/Items/Weapons/ML Weapons/ElvenSpellblade.cs +++ b/Scripts/Items/Weapons/ML Weapons/ElvenSpellblade.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2D20, 0x2D2C )] - public class ElvenSpellblade : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.PsychicAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.BleedAttack; + [Flippable(0x2D20, 0x2D2C)] + public class ElvenSpellblade : BaseKnife + { + [Constructible] + public ElvenSpellblade() : base(0x2D20) + { + Weight = 5.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 14; - public override int AosSpeed => 44; - public override float MlSpeed => 2.50f; + public ElvenSpellblade(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 12; - public override int OldMaxDamage => 14; - public override int OldSpeed => 44; + public override WeaponAbility PrimaryAbility => WeaponAbility.PsychicAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.BleedAttack; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 14; + public override int AosSpeed => 44; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 30; // TODO - public override int InitMaxHits => 60; // TODO + public override int OldStrengthReq => 35; + public override int OldMinDamage => 12; + public override int OldMaxDamage => 14; + public override int OldSpeed => 44; - [Constructible] - public ElvenSpellblade() : base( 0x2D20 ) - { - Weight = 5.0; - Layer = Layer.TwoHanded; - } + public override int DefMissSound => 0x239; - public ElvenSpellblade( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; // TODO + public override int InitMaxHits => 60; // TODO - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/Leafblade.cs b/Scripts/Items/Weapons/ML Weapons/Leafblade.cs index f51155912..cc5e29ad2 100644 --- a/Scripts/Items/Weapons/ML Weapons/Leafblade.cs +++ b/Scripts/Items/Weapons/ML Weapons/Leafblade.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2D22, 0x2D2E )] - public class Leafblade : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; - public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorIgnore; + [Flippable(0x2D22, 0x2D2E)] + public class Leafblade : BaseKnife + { + [Constructible] + public Leafblade() : base(0x2D22) + { + Weight = 8.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 42; - public override float MlSpeed => 2.75f; + public Leafblade(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 13; - public override int OldMaxDamage => 15; - public override int OldSpeed => 42; + public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; + public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorIgnore; - public override int DefMissSound => 0x239; - public override SkillName DefSkill => SkillName.Fencing; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 42; + public override float MlSpeed => 2.75f; - public override int InitMinHits => 30; // TODO - public override int InitMaxHits => 60; // TODO + public override int OldStrengthReq => 20; + public override int OldMinDamage => 13; + public override int OldMaxDamage => 15; + public override int OldSpeed => 42; - [Constructible] - public Leafblade() : base( 0x2D22 ) - { - Weight = 8.0; - } + public override int DefMissSound => 0x239; + public override SkillName DefSkill => SkillName.Fencing; - public Leafblade( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; // TODO + public override int InitMaxHits => 60; // TODO - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/MagicalShortbow.cs b/Scripts/Items/Weapons/ML Weapons/MagicalShortbow.cs index 5620f075a..f2cf0412d 100644 --- a/Scripts/Items/Weapons/ML Weapons/MagicalShortbow.cs +++ b/Scripts/Items/Weapons/ML Weapons/MagicalShortbow.cs @@ -2,54 +2,54 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x2D2B, 0x2D1F )] - public class MagicalShortbow : BaseRanged - { - public override int EffectID => 0xF42; - public override Type AmmoType => typeof( Arrow ); - public override Item Ammo => new Arrow(); + [Flippable(0x2D2B, 0x2D1F)] + public class MagicalShortbow : BaseRanged + { + [Constructible] + public MagicalShortbow() : base(0x2D2B) + { + Weight = 6.0; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.LightningArrow; - public override WeaponAbility SecondaryAbility => WeaponAbility.PsychicAttack; + public MagicalShortbow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 13; - public override int AosSpeed => 38; - public override float MlSpeed => 3.00f; + public override int EffectID => 0xF42; + public override Type AmmoType => typeof(Arrow); + public override Item Ammo => new Arrow(); - public override int OldStrengthReq => 45; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 13; - public override int OldSpeed => 38; + public override WeaponAbility PrimaryAbility => WeaponAbility.LightningArrow; + public override WeaponAbility SecondaryAbility => WeaponAbility.PsychicAttack; - public override int DefMaxRange => 10; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 13; + public override int AosSpeed => 38; + public override float MlSpeed => 3.00f; - public override int InitMinHits => 41; - public override int InitMaxHits => 90; + public override int OldStrengthReq => 45; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 13; + public override int OldSpeed => 38; - [Constructible] - public MagicalShortbow() : base( 0x2D2B ) - { - Weight = 6.0; - } + public override int DefMaxRange => 10; - public MagicalShortbow( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 41; + public override int InitMaxHits => 90; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/OrnateAxe.cs b/Scripts/Items/Weapons/ML Weapons/OrnateAxe.cs index 9408395e1..4f7dd1dbb 100644 --- a/Scripts/Items/Weapons/ML Weapons/OrnateAxe.cs +++ b/Scripts/Items/Weapons/ML Weapons/OrnateAxe.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2D28, 0x2D34 )] - public class OrnateAxe : BaseAxe - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; - public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; + [Flippable(0x2D28, 0x2D34)] + public class OrnateAxe : BaseAxe + { + [Constructible] + public OrnateAxe() : base(0x2D28) + { + Weight = 12.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 18; - public override int AosMaxDamage => 20; - public override int AosSpeed => 26; - public override float MlSpeed => 3.50f; + public OrnateAxe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 45; - public override int OldMinDamage => 18; - public override int OldMaxDamage => 20; - public override int OldSpeed => 26; + public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; + public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 18; + public override int AosMaxDamage => 20; + public override int AosSpeed => 26; + public override float MlSpeed => 3.50f; - public override int InitMinHits => 30; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 45; + public override int OldMinDamage => 18; + public override int OldMaxDamage => 20; + public override int OldSpeed => 26; - [Constructible] - public OrnateAxe() : base( 0x2D28 ) - { - Weight = 12.0; - Layer = Layer.TwoHanded; - } + public override int DefMissSound => 0x239; - public OrnateAxe( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/RadiantScimitar.cs b/Scripts/Items/Weapons/ML Weapons/RadiantScimitar.cs index 27bd66082..0f43415bf 100644 --- a/Scripts/Items/Weapons/ML Weapons/RadiantScimitar.cs +++ b/Scripts/Items/Weapons/ML Weapons/RadiantScimitar.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x2D33, 0x2D27 )] - public class RadiantScimitar : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; + [Flippable(0x2D33, 0x2D27)] + public class RadiantScimitar : BaseSword + { + [Constructible] + public RadiantScimitar() : base(0x2D33) + { + Weight = 9.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 14; - public override int AosSpeed => 43; - public override float MlSpeed => 2.50f; + public RadiantScimitar(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 12; - public override int OldMaxDamage => 14; - public override int OldSpeed => 43; + public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 14; + public override int AosSpeed => 43; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 30; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 20; + public override int OldMinDamage => 12; + public override int OldMaxDamage => 14; + public override int OldSpeed => 43; - [Constructible] - public RadiantScimitar() : base( 0x2D33 ) - { - Weight = 9.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x239; - public RadiantScimitar( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/RuneBlade.cs b/Scripts/Items/Weapons/ML Weapons/RuneBlade.cs index adcbb8eb4..2cd3b24d7 100644 --- a/Scripts/Items/Weapons/ML Weapons/RuneBlade.cs +++ b/Scripts/Items/Weapons/ML Weapons/RuneBlade.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x2D32, 0x2D26 )] - public class RuneBlade : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; - public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; + [Flippable(0x2D32, 0x2D26)] + public class RuneBlade : BaseSword + { + [Constructible] + public RuneBlade() : base(0x2D32) + { + Weight = 7.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 30; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 35; - public override float MlSpeed => 3.00f; + public RuneBlade(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 30; - public override int OldMinDamage => 15; - public override int OldMaxDamage => 17; - public override int OldSpeed => 35; + public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; + public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 30; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 35; + public override float MlSpeed => 3.00f; - public override int InitMinHits => 30; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 30; + public override int OldMinDamage => 15; + public override int OldMaxDamage => 17; + public override int OldSpeed => 35; - [Constructible] - public RuneBlade() : base( 0x2D32 ) - { - Weight = 7.0; - Layer = Layer.TwoHanded; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x239; - public RuneBlade( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/WarCleaver.cs b/Scripts/Items/Weapons/ML Weapons/WarCleaver.cs index f0ccfb5ff..0941e1dd3 100644 --- a/Scripts/Items/Weapons/ML Weapons/WarCleaver.cs +++ b/Scripts/Items/Weapons/ML Weapons/WarCleaver.cs @@ -1,54 +1,54 @@ namespace Server.Items { - [FlippableAttribute( 0x2D2F, 0x2D23 )] - public class WarCleaver : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; - public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; + [Flippable(0x2D2F, 0x2D23)] + public class WarCleaver : BaseKnife + { + [Constructible] + public WarCleaver() : base(0x2D2F) + { + Weight = 10.0; + } - public override int AosStrengthReq => 15; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 48; - public override float MlSpeed => 2.25f; + public WarCleaver(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 11; - public override int OldSpeed => 48; + public override WeaponAbility PrimaryAbility => WeaponAbility.Disarm; + public override WeaponAbility SecondaryAbility => WeaponAbility.Bladeweave; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 15; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 48; + public override float MlSpeed => 2.25f; - public override int InitMinHits => 30; // TODO - public override int InitMaxHits => 60; // TODO + public override int OldStrengthReq => 15; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 11; + public override int OldSpeed => 48; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x239; - [Constructible] - public WarCleaver() : base( 0x2D2F ) - { - Weight = 10.0; - } + public override int InitMinHits => 30; // TODO + public override int InitMaxHits => 60; // TODO - public WarCleaver( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/ML Weapons/WildStaff.cs b/Scripts/Items/Weapons/ML Weapons/WildStaff.cs index 0c6caf9f0..ae81740a7 100644 --- a/Scripts/Items/Weapons/ML Weapons/WildStaff.cs +++ b/Scripts/Items/Weapons/ML Weapons/WildStaff.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x2D25, 0x2D31 )] - public class WildStaff : BaseStaff - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Block; - public override WeaponAbility SecondaryAbility => WeaponAbility.ForceOfNature; + [Flippable(0x2D25, 0x2D31)] + public class WildStaff : BaseStaff + { + [Constructible] + public WildStaff() : base(0x2D25) + { + Weight = 8.0; + } - public override int AosStrengthReq => 15; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 12; - public override int AosSpeed => 48; - public override float MlSpeed => 2.25f; + public WildStaff(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 12; - public override int OldSpeed => 48; + public override WeaponAbility PrimaryAbility => WeaponAbility.Block; + public override WeaponAbility SecondaryAbility => WeaponAbility.ForceOfNature; - public override int InitMinHits => 30; - public override int InitMaxHits => 60; + public override int AosStrengthReq => 15; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 12; + public override int AosSpeed => 48; + public override float MlSpeed => 2.25f; - [Constructible] - public WildStaff() : base( 0x2D25 ) - { - Weight = 8.0; - } + public override int OldStrengthReq => 15; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 12; + public override int OldSpeed => 48; - public WildStaff( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 30; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/BaseBashing.cs b/Scripts/Items/Weapons/Maces/BaseBashing.cs index 2294a67f8..612a69819 100644 --- a/Scripts/Items/Weapons/Maces/BaseBashing.cs +++ b/Scripts/Items/Weapons/Maces/BaseBashing.cs @@ -1,56 +1,61 @@ +using Server.Engines.ConPVP; + namespace Server.Items { - public abstract class BaseBashing : BaseMeleeWeapon - { - public override int DefHitSound => 0x233; - public override int DefMissSound => 0x239; + public abstract class BaseBashing : BaseMeleeWeapon + { + public BaseBashing(int itemID) : base(itemID) + { + } - public override SkillName DefSkill => SkillName.Macing; - public override WeaponType DefType => WeaponType.Bashing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Bash1H; + public BaseBashing(Serial serial) : base(serial) + { + } - public BaseBashing( int itemID ) : base( itemID ) - { - } + public override int DefHitSound => 0x233; + public override int DefMissSound => 0x239; - public BaseBashing( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Macing; + public override WeaponType DefType => WeaponType.Bashing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Bash1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - defender.Stam -= Utility.Random( 3, 3 ); // 3-5 points of stamina loss - } + defender.Stam -= Utility.Random(3, 3); // 3-5 points of stamina loss + } - public override double GetBaseDamage( Mobile attacker ) - { - double damage = base.GetBaseDamage( attacker ); + public override double GetBaseDamage(Mobile attacker) + { + double damage = base.GetBaseDamage(attacker); - if (!Core.AOS && (attacker.Player || attacker.Body.IsHuman) && Layer == Layer.TwoHanded && attacker.Skills[SkillName.Anatomy].Value >= 80 && (attacker.Skills[SkillName.Anatomy].Value / 400.0) >= Utility.RandomDouble() && Engines.ConPVP.DuelContext.AllowSpecialAbility(attacker, "Crushing Blow", false)) - { - damage *= 1.5; + if (!Core.AOS && (attacker.Player || attacker.Body.IsHuman) && Layer == Layer.TwoHanded && + attacker.Skills[SkillName.Anatomy].Value >= 80 && + attacker.Skills[SkillName.Anatomy].Value / 400.0 >= Utility.RandomDouble() && + DuelContext.AllowSpecialAbility(attacker, "Crushing Blow", false)) + { + damage *= 1.5; - attacker.SendMessage( "You deliver a crushing blow!" ); // Is this not localized? - attacker.PlaySound( 0x11C ); - } + attacker.SendMessage("You deliver a crushing blow!"); // Is this not localized? + attacker.PlaySound(0x11C); + } - return damage; - } - } -} + return damage; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/Club.cs b/Scripts/Items/Weapons/Maces/Club.cs index a5ca32534..54f22cb79 100644 --- a/Scripts/Items/Weapons/Maces/Club.cs +++ b/Scripts/Items/Weapons/Maces/Club.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x13b4, 0x13b3 )] - public class Club : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ShadowStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; + [Flippable(0x13b4, 0x13b3)] + public class Club : BaseBashing + { + [Constructible] + public Club() : base(0x13B4) + { + Weight = 9.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 13; - public override int AosSpeed => 44; - public override float MlSpeed => 2.50f; + public Club(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 8; - public override int OldMaxDamage => 24; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.ShadowStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; - public override int InitMinHits => 31; - public override int InitMaxHits => 40; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 13; + public override int AosSpeed => 44; + public override float MlSpeed => 2.50f; - [Constructible] - public Club() : base( 0x13B4 ) - { - Weight = 9.0; - } + public override int OldStrengthReq => 10; + public override int OldMinDamage => 8; + public override int OldMaxDamage => 24; + public override int OldSpeed => 40; - public Club( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 40; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/EmeraldMace.cs b/Scripts/Items/Weapons/Maces/EmeraldMace.cs index f35ead1b3..2826c5a88 100644 --- a/Scripts/Items/Weapons/Maces/EmeraldMace.cs +++ b/Scripts/Items/Weapons/Maces/EmeraldMace.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class EmeraldMace : DiamondMace - { - public override int LabelNumber => 1073530; // emerald mace + public class EmeraldMace : DiamondMace + { + [Constructible] + public EmeraldMace() + { + WeaponAttributes.ResistPoisonBonus = 5; + } - [Constructible] - public EmeraldMace() - { - WeaponAttributes.ResistPoisonBonus = 5; - } + public EmeraldMace(Serial serial) : base(serial) + { + } - public EmeraldMace( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073530; // emerald mace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/FireworksWand.cs b/Scripts/Items/Weapons/Maces/FireworksWand.cs index b4d1be517..2946c633a 100644 --- a/Scripts/Items/Weapons/Maces/FireworksWand.cs +++ b/Scripts/Items/Weapons/Maces/FireworksWand.cs @@ -2,135 +2,141 @@ using System; namespace Server.Items { - public class FireworksWand : MagicWand - { - public override int LabelNumber => 1041424; // a fireworks wand + public class FireworksWand : MagicWand + { + private int m_Charges; - private int m_Charges; + [Constructible] + public FireworksWand() : this(100) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Charges - { - get => m_Charges; - set{ m_Charges = value; InvalidateProperties(); } - } + [Constructible] + public FireworksWand(int charges) + { + m_Charges = charges; + LootType = LootType.Blessed; + } - [Constructible] - public FireworksWand() : this( 100 ) - { - } + public FireworksWand(Serial serial) : base(serial) + { + } - [Constructible] - public FireworksWand( int charges ) - { - m_Charges = charges; - LootType = LootType.Blessed; - } + public override int LabelNumber => 1041424; // a fireworks wand - public FireworksWand( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int Charges + { + get => m_Charges; + set + { + m_Charges = value; + InvalidateProperties(); + } + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - list.Add( 1060741, m_Charges.ToString() ); // charges: ~1_val~ - } + list.Add(1060741, m_Charges.ToString()); // charges: ~1_val~ + } - public override void OnDoubleClick( Mobile from ) - { - BeginLaunch( from, true ); - } + public override void OnDoubleClick(Mobile from) + { + BeginLaunch(from, true); + } - public void BeginLaunch( Mobile from, bool useCharges ) - { - Map map = from.Map; + public void BeginLaunch(Mobile from, bool useCharges) + { + Map map = from.Map; - if ( map == null || map == Map.Internal ) - return; + if (map == null || map == Map.Internal) + return; - if ( useCharges ) - { - if ( Charges > 0 ) - { - --Charges; - } - else - { - from.SendLocalizedMessage( 502412 ); // There are no charges left on that item. - return; - } - } + if (useCharges) + { + if (Charges > 0) + { + --Charges; + } + else + { + from.SendLocalizedMessage(502412); // There are no charges left on that item. + return; + } + } - from.SendLocalizedMessage( 502615 ); // You launch a firework! + from.SendLocalizedMessage(502615); // You launch a firework! - Point3D ourLoc = GetWorldLocation(); + Point3D ourLoc = GetWorldLocation(); - Point3D startLoc = new Point3D( ourLoc.X, ourLoc.Y, ourLoc.Z + 10 ); - Point3D endLoc = new Point3D( startLoc.X + Utility.RandomMinMax( -2, 2 ), startLoc.Y + Utility.RandomMinMax( -2, 2 ), startLoc.Z + 32 ); + Point3D startLoc = new Point3D(ourLoc.X, ourLoc.Y, ourLoc.Z + 10); + Point3D endLoc = new Point3D(startLoc.X + Utility.RandomMinMax(-2, 2), startLoc.Y + Utility.RandomMinMax(-2, 2), + startLoc.Z + 32); - Effects.SendMovingEffect( new Entity( Serial.Zero, startLoc, map ), new Entity( Serial.Zero, endLoc, map ), - 0x36E4, 5, 0, false, false ); + Effects.SendMovingEffect(new Entity(Serial.Zero, startLoc, map), new Entity(Serial.Zero, endLoc, map), + 0x36E4, 5, 0, false, false); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( FinishLaunch ), new object[]{ from, endLoc, map } ); - } + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(FinishLaunch), + new object[] { from, endLoc, map }); + } - private void FinishLaunch( object state ) - { - object[] states = (object[])state; + private void FinishLaunch(object state) + { + object[] states = (object[])state; - Mobile from = (Mobile)states[0]; - Point3D endLoc = (Point3D)states[1]; - Map map = (Map)states[2]; + Mobile from = (Mobile)states[0]; + Point3D endLoc = (Point3D)states[1]; + Map map = (Map)states[2]; - int hue = Utility.Random( 40 ); + int hue = Utility.Random(40); - if ( hue < 8 ) - hue = 0x66D; - else if ( hue < 10 ) - hue = 0x482; - else if ( hue < 12 ) - hue = 0x47E; - else if ( hue < 16 ) - hue = 0x480; - else if ( hue < 20 ) - hue = 0x47F; - else - hue = 0; + if (hue < 8) + hue = 0x66D; + else if (hue < 10) + hue = 0x482; + else if (hue < 12) + hue = 0x47E; + else if (hue < 16) + hue = 0x480; + else if (hue < 20) + hue = 0x47F; + else + hue = 0; - if ( Utility.RandomBool() ) - hue = Utility.RandomList( 0x47E, 0x47F, 0x480, 0x482, 0x66D ); + if (Utility.RandomBool()) + hue = Utility.RandomList(0x47E, 0x47F, 0x480, 0x482, 0x66D); - int renderMode = Utility.RandomList( 0, 2, 3, 4, 5, 7 ); + int renderMode = Utility.RandomList(0, 2, 3, 4, 5, 7); - Effects.PlaySound( endLoc, map, Utility.Random( 0x11B, 4 ) ); - Effects.SendLocationEffect( endLoc, map, 0x373A + (0x10 * Utility.Random( 4 )), 16, 10, hue, renderMode ); - } + Effects.PlaySound(endLoc, map, Utility.Random(0x11B, 4)); + Effects.SendLocationEffect(endLoc, map, 0x373A + 0x10 * Utility.Random(4), 16, 10, hue, renderMode); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) m_Charges ); - } + writer.Write(m_Charges); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Charges = reader.ReadInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + m_Charges = reader.ReadInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/HammerPick.cs b/Scripts/Items/Weapons/Maces/HammerPick.cs index 1f839fa75..11fa948dc 100644 --- a/Scripts/Items/Weapons/Maces/HammerPick.cs +++ b/Scripts/Items/Weapons/Maces/HammerPick.cs @@ -1,48 +1,48 @@ namespace Server.Items { - [FlippableAttribute( 0x143D, 0x143C )] - public class HammerPick : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0x143D, 0x143C)] + public class HammerPick : BaseBashing + { + [Constructible] + public HammerPick() : base(0x143D) + { + Weight = 9.0; + Layer = Layer.OneHanded; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 28; - public override float MlSpeed => 3.75f; + public HammerPick(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 33; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 28; + public override float MlSpeed => 3.75f; - [Constructible] - public HammerPick() : base( 0x143D ) - { - Weight = 9.0; - Layer = Layer.OneHanded; - } + public override int OldStrengthReq => 35; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 33; + public override int OldSpeed => 30; - public HammerPick( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/Mace.cs b/Scripts/Items/Weapons/Maces/Mace.cs index 98ba4fc5a..97c556ba8 100644 --- a/Scripts/Items/Weapons/Maces/Mace.cs +++ b/Scripts/Items/Weapons/Maces/Mace.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xF5C, 0xF5D )] - public class Mace : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Flippable(0xF5C, 0xF5D)] + public class Mace : BaseBashing + { + [Constructible] + public Mace() : base(0xF5C) + { + Weight = 14.0; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 14; - public override int AosSpeed => 40; - public override float MlSpeed => 2.75f; + public Mace(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 8; - public override int OldMaxDamage => 32; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 14; + public override int AosSpeed => 40; + public override float MlSpeed => 2.75f; - [Constructible] - public Mace() : base( 0xF5C ) - { - Weight = 14.0; - } + public override int OldStrengthReq => 20; + public override int OldMinDamage => 8; + public override int OldMaxDamage => 32; + public override int OldSpeed => 30; - public Mace( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/MagicWand.cs b/Scripts/Items/Weapons/Maces/MagicWand.cs index 875ac77a8..aa2e79192 100644 --- a/Scripts/Items/Weapons/Maces/MagicWand.cs +++ b/Scripts/Items/Weapons/Maces/MagicWand.cs @@ -1,46 +1,46 @@ namespace Server.Items { - public class MagicWand : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Dismount; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + public class MagicWand : BaseBashing + { + [Constructible] + public MagicWand() : base(0xDF2) + { + Weight = 1.0; + } - public override int AosStrengthReq => 5; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 40; - public override float MlSpeed => 2.75f; + public MagicWand(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 0; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 6; - public override int OldSpeed => 35; + public override WeaponAbility PrimaryAbility => WeaponAbility.Dismount; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 5; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 40; + public override float MlSpeed => 2.75f; - [Constructible] - public MagicWand() : base( 0xDF2 ) - { - Weight = 1.0; - } + public override int OldStrengthReq => 0; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 6; + public override int OldSpeed => 35; - public MagicWand( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/Maul.cs b/Scripts/Items/Weapons/Maces/Maul.cs index 7c3b4536e..7bddd8241 100644 --- a/Scripts/Items/Weapons/Maces/Maul.cs +++ b/Scripts/Items/Weapons/Maces/Maul.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x143B, 0x143A )] - public class Maul : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; + [Flippable(0x143B, 0x143A)] + public class Maul : BaseBashing + { + [Constructible] + public Maul() : base(0x143B) + { + Weight = 10.0; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 16; - public override int AosSpeed => 32; - public override float MlSpeed => 3.50f; + public Maul(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 30; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 16; + public override int AosSpeed => 32; + public override float MlSpeed => 3.50f; - [Constructible] - public Maul() : base( 0x143B ) - { - Weight = 10.0; - } + public override int OldStrengthReq => 20; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 30; + public override int OldSpeed => 30; - public Maul( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 14.0 ) - Weight = 10.0; - } - } -} + if (Weight == 14.0) + Weight = 10.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/RubyMace.cs b/Scripts/Items/Weapons/Maces/RubyMace.cs index 931eea6ae..7b3881752 100644 --- a/Scripts/Items/Weapons/Maces/RubyMace.cs +++ b/Scripts/Items/Weapons/Maces/RubyMace.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class RubyMace : DiamondMace - { - public override int LabelNumber => 1073529; // ruby mace + public class RubyMace : DiamondMace + { + [Constructible] + public RubyMace() + { + Attributes.WeaponDamage = 5; + } - [Constructible] - public RubyMace() - { - Attributes.WeaponDamage = 5; - } + public RubyMace(Serial serial) : base(serial) + { + } - public RubyMace( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073529; // ruby mace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/SapphireMace.cs b/Scripts/Items/Weapons/Maces/SapphireMace.cs index 32d76e33b..bfca7746b 100644 --- a/Scripts/Items/Weapons/Maces/SapphireMace.cs +++ b/Scripts/Items/Weapons/Maces/SapphireMace.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SapphireMace : DiamondMace - { - public override int LabelNumber => 1073531; // sapphire mace + public class SapphireMace : DiamondMace + { + [Constructible] + public SapphireMace() + { + WeaponAttributes.ResistEnergyBonus = 5; + } - [Constructible] - public SapphireMace() - { - WeaponAttributes.ResistEnergyBonus = 5; - } + public SapphireMace(Serial serial) : base(serial) + { + } - public SapphireMace( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073531; // sapphire mace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/Scepter.cs b/Scripts/Items/Weapons/Maces/Scepter.cs index ed0344dce..65fe9eea1 100644 --- a/Scripts/Items/Weapons/Maces/Scepter.cs +++ b/Scripts/Items/Weapons/Maces/Scepter.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x26BC, 0x26C6 )] - public class Scepter : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0x26BC, 0x26C6)] + public class Scepter : BaseBashing + { + [Constructible] + public Scepter() : base(0x26BC) + { + Weight = 8.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 17; - public override int AosSpeed => 30; - public override float MlSpeed => 3.50f; + public Scepter(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 14; - public override int OldMaxDamage => 17; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 17; + public override int AosSpeed => 30; + public override float MlSpeed => 3.50f; - [Constructible] - public Scepter() : base( 0x26BC ) - { - Weight = 8.0; - } + public override int OldStrengthReq => 40; + public override int OldMinDamage => 14; + public override int OldMaxDamage => 17; + public override int OldSpeed => 30; - public Scepter( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/SilverEtchedMace.cs b/Scripts/Items/Weapons/Maces/SilverEtchedMace.cs index d0d608f36..1cfa4a8e8 100644 --- a/Scripts/Items/Weapons/Maces/SilverEtchedMace.cs +++ b/Scripts/Items/Weapons/Maces/SilverEtchedMace.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SilverEtchedMace : DiamondMace - { - public override int LabelNumber => 1073532; // silver-etched mace + public class SilverEtchedMace : DiamondMace + { + [Constructible] + public SilverEtchedMace() + { + Slayer = SlayerName.Exorcism; + } - [Constructible] - public SilverEtchedMace() - { - Slayer = SlayerName.Exorcism; - } + public SilverEtchedMace(Serial serial) : base(serial) + { + } - public SilverEtchedMace( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073532; // silver-etched mace - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/WarHammer.cs b/Scripts/Items/Weapons/Maces/WarHammer.cs index 7f32b8ceb..828da75ed 100644 --- a/Scripts/Items/Weapons/Maces/WarHammer.cs +++ b/Scripts/Items/Weapons/Maces/WarHammer.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x1439, 0x1438 )] - public class WarHammer : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; + [Flippable(0x1439, 0x1438)] + public class WarHammer : BaseBashing + { + [Constructible] + public WarHammer() : base(0x1439) + { + Weight = 10.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 95; - public override int AosMinDamage => 17; - public override int AosMaxDamage => 18; - public override int AosSpeed => 28; - public override float MlSpeed => 3.75f; + public WarHammer(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 8; - public override int OldMaxDamage => 36; - public override int OldSpeed => 31; + public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 95; + public override int AosMinDamage => 17; + public override int AosMaxDamage => 18; + public override int AosSpeed => 28; + public override float MlSpeed => 3.75f; - public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; + public override int OldStrengthReq => 40; + public override int OldMinDamage => 8; + public override int OldMaxDamage => 36; + public override int OldSpeed => 31; - [Constructible] - public WarHammer() : base( 0x1439 ) - { - Weight = 10.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public WarHammer( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Maces/WarMace.cs b/Scripts/Items/Weapons/Maces/WarMace.cs index ef0deba33..ca568b671 100644 --- a/Scripts/Items/Weapons/Maces/WarMace.cs +++ b/Scripts/Items/Weapons/Maces/WarMace.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x1407, 0x1406 )] - public class WarMace : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0x1407, 0x1406)] + public class WarMace : BaseBashing + { + [Constructible] + public WarMace() : base(0x1407) + { + Weight = 17.0; + } - public override int AosStrengthReq => 80; - public override int AosMinDamage => 16; - public override int AosMaxDamage => 17; - public override int AosSpeed => 26; - public override float MlSpeed => 4.00f; + public WarMace(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 30; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 30; - public override int OldSpeed => 32; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 80; + public override int AosMinDamage => 16; + public override int AosMaxDamage => 17; + public override int AosSpeed => 26; + public override float MlSpeed => 4.00f; - [Constructible] - public WarMace() : base( 0x1407 ) - { - Weight = 17.0; - } + public override int OldStrengthReq => 30; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 30; + public override int OldSpeed => 32; - public WarMace( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/PoleArms/Bardiche.cs b/Scripts/Items/Weapons/PoleArms/Bardiche.cs index 9130616d6..7ec70cfec 100644 --- a/Scripts/Items/Weapons/PoleArms/Bardiche.cs +++ b/Scripts/Items/Weapons/PoleArms/Bardiche.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xF4D, 0xF4E )] - public class Bardiche : BasePoleArm - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; + [Flippable(0xF4D, 0xF4E)] + public class Bardiche : BasePoleArm + { + [Constructible] + public Bardiche() : base(0xF4D) + { + Weight = 7.0; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 17; - public override int AosMaxDamage => 18; - public override int AosSpeed => 28; - public override float MlSpeed => 3.75f; + public Bardiche(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 43; - public override int OldSpeed => 26; + public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; - public override int InitMinHits => 31; - public override int InitMaxHits => 100; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 17; + public override int AosMaxDamage => 18; + public override int AosSpeed => 28; + public override float MlSpeed => 3.75f; - [Constructible] - public Bardiche() : base( 0xF4D ) - { - Weight = 7.0; - } + public override int OldStrengthReq => 40; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 43; + public override int OldSpeed => 26; - public Bardiche( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 100; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/PoleArms/BasePoleArm.cs b/Scripts/Items/Weapons/PoleArms/BasePoleArm.cs index 308e53c0c..e7628763a 100644 --- a/Scripts/Items/Weapons/PoleArms/BasePoleArm.cs +++ b/Scripts/Items/Weapons/PoleArms/BasePoleArm.cs @@ -1,122 +1,136 @@ using System; using System.Collections.Generic; -using Server.Engines.Harvest; using Server.ContextMenus; +using Server.Engines.ConPVP; +using Server.Engines.Harvest; namespace Server.Items { - public abstract class BasePoleArm : BaseMeleeWeapon, IUsesRemaining - { - public override int DefHitSound => 0x237; - public override int DefMissSound => 0x238; + public abstract class BasePoleArm : BaseMeleeWeapon, IUsesRemaining + { + private bool m_ShowUsesRemaining; - public override SkillName DefSkill => SkillName.Swords; - public override WeaponType DefType => WeaponType.Polearm; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash2H; + private int m_UsesRemaining; - public virtual HarvestSystem HarvestSystem => Lumberjacking.System; + public BasePoleArm(int itemID) : base(itemID) + { + m_UsesRemaining = 150; + } - private int m_UsesRemaining; - private bool m_ShowUsesRemaining; + public BasePoleArm(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int UsesRemaining - { - get => m_UsesRemaining; - set { m_UsesRemaining = value; InvalidateProperties(); } - } + public override int DefHitSound => 0x237; + public override int DefMissSound => 0x238; - [CommandProperty( AccessLevel.GameMaster )] - public bool ShowUsesRemaining - { - get => m_ShowUsesRemaining; - set { m_ShowUsesRemaining = value; InvalidateProperties(); } - } + public override SkillName DefSkill => SkillName.Swords; + public override WeaponType DefType => WeaponType.Polearm; + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash2H; - public BasePoleArm( int itemID ) : base( itemID ) - { - m_UsesRemaining = 150; - } + public virtual HarvestSystem HarvestSystem => Lumberjacking.System; - public BasePoleArm( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int UsesRemaining + { + get => m_UsesRemaining; + set + { + m_UsesRemaining = value; + InvalidateProperties(); + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( HarvestSystem == null ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public bool ShowUsesRemaining + { + get => m_ShowUsesRemaining; + set + { + m_ShowUsesRemaining = value; + InvalidateProperties(); + } + } - if ( IsChildOf( from.Backpack ) || Parent == from ) - HarvestSystem.BeginHarvesting( from, this ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } + public override void OnDoubleClick(Mobile from) + { + if (HarvestSystem == null) + return; - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (IsChildOf(from.Backpack) || Parent == from) + HarvestSystem.BeginHarvesting(from, this); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } - if ( HarvestSystem != null ) - BaseHarvestTool.AddContextMenuEntries( from, this, list, HarvestSystem ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (HarvestSystem != null) + BaseHarvestTool.AddContextMenuEntries(from, this, list, HarvestSystem); + } - writer.Write( (int) 2 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (bool) m_ShowUsesRemaining ); + writer.Write(2); // version - writer.Write( (int) m_UsesRemaining ); - } + writer.Write(m_ShowUsesRemaining); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_UsesRemaining); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 2: - { - m_ShowUsesRemaining = reader.ReadBool(); - goto case 1; - } - case 1: - { - m_UsesRemaining = reader.ReadInt(); - goto case 0; - } - case 0: - { - if ( m_UsesRemaining < 1 ) - m_UsesRemaining = 150; + int version = reader.ReadInt(); - break; - } - } - } + switch (version) + { + case 2: + { + m_ShowUsesRemaining = reader.ReadBool(); + goto case 1; + } + case 1: + { + m_UsesRemaining = reader.ReadInt(); + goto case 0; + } + case 0: + { + if (m_UsesRemaining < 1) + m_UsesRemaining = 150; - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + break; + } + } + } - if (!Core.AOS && (attacker.Player || attacker.Body.IsHuman) && Layer == Layer.TwoHanded && attacker.Skills[SkillName.Anatomy].Value >= 80 && (attacker.Skills[SkillName.Anatomy].Value / 400.0) >= Utility.RandomDouble() && Engines.ConPVP.DuelContext.AllowSpecialAbility(attacker, "Concussion Blow", false)) - { - StatMod mod = defender.GetStatMod( "Concussion" ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - if ( mod == null ) - { - defender.SendMessage( "You receive a concussion blow!" ); - defender.AddStatMod( new StatMod( StatType.Int, "Concussion", -(defender.RawInt / 2), TimeSpan.FromSeconds( 30.0 ) ) ); + if (!Core.AOS && (attacker.Player || attacker.Body.IsHuman) && Layer == Layer.TwoHanded && + attacker.Skills[SkillName.Anatomy].Value >= 80 && + attacker.Skills[SkillName.Anatomy].Value / 400.0 >= Utility.RandomDouble() && + DuelContext.AllowSpecialAbility(attacker, "Concussion Blow", false)) + { + StatMod mod = defender.GetStatMod("Concussion"); - attacker.SendMessage( "You deliver a concussion blow!" ); - attacker.PlaySound( 0x11C ); - } - } - } - } -} + if (mod == null) + { + defender.SendMessage("You receive a concussion blow!"); + defender.AddStatMod(new StatMod(StatType.Int, "Concussion", -(defender.RawInt / 2), + TimeSpan.FromSeconds(30.0))); + + attacker.SendMessage("You deliver a concussion blow!"); + attacker.PlaySound(0x11C); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/PoleArms/Halberd.cs b/Scripts/Items/Weapons/PoleArms/Halberd.cs index 78bef57af..dcb7dbb3c 100644 --- a/Scripts/Items/Weapons/PoleArms/Halberd.cs +++ b/Scripts/Items/Weapons/PoleArms/Halberd.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x143E, 0x143F )] - public class Halberd : BasePoleArm - { - public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; + [Flippable(0x143E, 0x143F)] + public class Halberd : BasePoleArm + { + [Constructible] + public Halberd() : base(0x143E) + { + Weight = 16.0; + } - public override int AosStrengthReq => 95; - public override int AosMinDamage => 18; - public override int AosMaxDamage => 19; - public override int AosSpeed => 25; - public override float MlSpeed => 4.25f; + public Halberd(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 45; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 49; - public override int OldSpeed => 25; + public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int AosStrengthReq => 95; + public override int AosMinDamage => 18; + public override int AosMaxDamage => 19; + public override int AosSpeed => 25; + public override float MlSpeed => 4.25f; - [Constructible] - public Halberd() : base( 0x143E ) - { - Weight = 16.0; - } + public override int OldStrengthReq => 45; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 49; + public override int OldSpeed => 25; - public Halberd( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/PoleArms/Scythe.cs b/Scripts/Items/Weapons/PoleArms/Scythe.cs index db35aec87..0787f8b46 100644 --- a/Scripts/Items/Weapons/PoleArms/Scythe.cs +++ b/Scripts/Items/Weapons/PoleArms/Scythe.cs @@ -2,53 +2,53 @@ using Server.Engines.Harvest; namespace Server.Items { - [FlippableAttribute( 0x26BA, 0x26C4 )] - public class Scythe : BasePoleArm - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0x26BA, 0x26C4)] + public class Scythe : BasePoleArm + { + [Constructible] + public Scythe() : base(0x26BA) + { + Weight = 5.0; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 18; - public override int AosSpeed => 32; - public override float MlSpeed => 3.50f; + public Scythe(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 45; - public override int OldMinDamage => 15; - public override int OldMaxDamage => 18; - public override int OldSpeed => 32; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 100; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 18; + public override int AosSpeed => 32; + public override float MlSpeed => 3.50f; - public override HarvestSystem HarvestSystem => null; + public override int OldStrengthReq => 45; + public override int OldMinDamage => 15; + public override int OldMaxDamage => 18; + public override int OldSpeed => 32; - [Constructible] - public Scythe() : base( 0x26BA ) - { - Weight = 5.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 100; - public Scythe( Serial serial ) : base( serial ) - { - } + public override HarvestSystem HarvestSystem => null; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 15.0 ) - Weight = 5.0; - } - } -} + if (Weight == 15.0) + Weight = 5.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/AssassinsShortbow.cs b/Scripts/Items/Weapons/Ranged/AssassinsShortbow.cs index 1cd228967..7ca373bd2 100644 --- a/Scripts/Items/Weapons/Ranged/AssassinsShortbow.cs +++ b/Scripts/Items/Weapons/Ranged/AssassinsShortbow.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class AssassinsShortbow : MagicalShortbow - { - public override int LabelNumber => 1073512; // assassin's shortbow + public class AssassinsShortbow : MagicalShortbow + { + [Constructible] + public AssassinsShortbow() + { + Attributes.AttackChance = 3; + Attributes.WeaponDamage = 4; + } - [Constructible] - public AssassinsShortbow() - { - Attributes.AttackChance = 3; - Attributes.WeaponDamage = 4; - } + public AssassinsShortbow(Serial serial) : base(serial) + { + } - public AssassinsShortbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073512; // assassin's shortbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/BarbedLongbow.cs b/Scripts/Items/Weapons/Ranged/BarbedLongbow.cs index 5f606557a..fe17943d0 100644 --- a/Scripts/Items/Weapons/Ranged/BarbedLongbow.cs +++ b/Scripts/Items/Weapons/Ranged/BarbedLongbow.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class BarbedLongbow : ElvenCompositeLongbow - { - public override int LabelNumber => 1073505; // barbed longbow + public class BarbedLongbow : ElvenCompositeLongbow + { + [Constructible] + public BarbedLongbow() + { + Attributes.ReflectPhysical = 12; + } - [Constructible] - public BarbedLongbow() - { - Attributes.ReflectPhysical = 12; - } + public BarbedLongbow(Serial serial) : base(serial) + { + } - public BarbedLongbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073505; // barbed longbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/BaseRanged.cs b/Scripts/Items/Weapons/Ranged/BaseRanged.cs index 371076216..9a9298f1a 100644 --- a/Scripts/Items/Weapons/Ranged/BaseRanged.cs +++ b/Scripts/Items/Weapons/Ranged/BaseRanged.cs @@ -1,227 +1,240 @@ using System; +using Server.Mobiles; using Server.Network; using Server.Spells; -using Server.Mobiles; namespace Server.Items { - public abstract class BaseRanged : BaseMeleeWeapon - { - public abstract int EffectID{ get; } - public abstract Type AmmoType{ get; } - public abstract Item Ammo{ get; } + public abstract class BaseRanged : BaseMeleeWeapon + { + private bool m_Balanced; - public override int DefHitSound => 0x234; - public override int DefMissSound => 0x238; + private Timer m_RecoveryTimer; // so we don't start too many timers + private int m_Velocity; - public override SkillName DefSkill => SkillName.Archery; - public override WeaponType DefType => WeaponType.Ranged; - public override WeaponAnimation DefAnimation => WeaponAnimation.ShootXBow; + public BaseRanged(int itemID) : base(itemID) + { + } - public override SkillName AccuracySkill => SkillName.Archery; + public BaseRanged(Serial serial) : base(serial) + { + } - private Timer m_RecoveryTimer; // so we don't start too many timers - private bool m_Balanced; - private int m_Velocity; + public abstract int EffectID{ get; } + public abstract Type AmmoType{ get; } + public abstract Item Ammo{ get; } - [CommandProperty( AccessLevel.GameMaster )] - public bool Balanced - { - get => m_Balanced; - set{ m_Balanced = value; InvalidateProperties(); } - } + public override int DefHitSound => 0x234; + public override int DefMissSound => 0x238; - [CommandProperty( AccessLevel.GameMaster )] - public int Velocity - { - get => m_Velocity; - set{ m_Velocity = value; InvalidateProperties(); } - } + public override SkillName DefSkill => SkillName.Archery; + public override WeaponType DefType => WeaponType.Ranged; + public override WeaponAnimation DefAnimation => WeaponAnimation.ShootXBow; - public BaseRanged( int itemID ) : base( itemID ) - { - } + public override SkillName AccuracySkill => SkillName.Archery; - public BaseRanged( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Balanced + { + get => m_Balanced; + set + { + m_Balanced = value; + InvalidateProperties(); + } + } - public override TimeSpan OnSwing( Mobile attacker, Mobile defender ) - { - // WeaponAbility a = WeaponAbility.GetCurrentAbility( attacker ); + [CommandProperty(AccessLevel.GameMaster)] + public int Velocity + { + get => m_Velocity; + set + { + m_Velocity = value; + InvalidateProperties(); + } + } - // Make sure we've been standing still for .25/.5/1 second depending on Era - if (Core.TickCount - attacker.LastMoveTime >= (Core.SE ? 250 : Core.AOS ? 500 : 1000) || (Core.AOS && WeaponAbility.GetCurrentAbility(attacker) is MovingShot)) - { - bool canSwing = true; + public override TimeSpan OnSwing(Mobile attacker, Mobile defender) + { + // WeaponAbility a = WeaponAbility.GetCurrentAbility( attacker ); - if ( Core.AOS ) - { - canSwing = ( !attacker.Paralyzed && !attacker.Frozen ); + // Make sure we've been standing still for .25/.5/1 second depending on Era + if (Core.TickCount - attacker.LastMoveTime >= (Core.SE ? 250 : Core.AOS ? 500 : 1000) || + Core.AOS && WeaponAbility.GetCurrentAbility(attacker) is MovingShot) + { + bool canSwing = true; - if ( canSwing ) - { - canSwing = ( !(attacker.Spell is Spell sp) || !sp.IsCasting || !sp.BlocksMovement ); - } - } + if (Core.AOS) + { + canSwing = !attacker.Paralyzed && !attacker.Frozen; - #region Dueling - if ( attacker is PlayerMobile pm ) - { - if ( pm.DuelContext != null && !pm.DuelContext.CheckItemEquip( attacker, this ) ) - canSwing = false; - } - #endregion + if (canSwing) canSwing = !(attacker.Spell is Spell sp) || !sp.IsCasting || !sp.BlocksMovement; + } - if ( canSwing && attacker.HarmfulCheck( defender ) ) - { - attacker.DisruptiveAction(); - attacker.Send( new Swing( 0, attacker, defender ) ); + #region Dueling - if ( OnFired( attacker, defender ) ) - { - if ( CheckHit( attacker, defender ) ) - OnHit( attacker, defender ); - else - OnMiss( attacker, defender ); - } - } + if (attacker is PlayerMobile pm) + if (pm.DuelContext != null && !pm.DuelContext.CheckItemEquip(attacker, this)) + canSwing = false; - attacker.RevealingAction(); + #endregion - return GetDelay( attacker ); - } + if (canSwing && attacker.HarmfulCheck(defender)) + { + attacker.DisruptiveAction(); + attacker.Send(new Swing(0, attacker, defender)); - attacker.RevealingAction(); + if (OnFired(attacker, defender)) + { + if (CheckHit(attacker, defender)) + OnHit(attacker, defender); + else + OnMiss(attacker, defender); + } + } - return TimeSpan.FromSeconds( 0.25 ); - } + attacker.RevealingAction(); - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1) - { - if ( attacker.Player && !defender.Player && (defender.Body.IsAnimal || defender.Body.IsMonster) && 0.4 >= Utility.RandomDouble() ) - defender.AddToBackpack( Ammo ); + return GetDelay(attacker); + } - if ( Core.ML && m_Velocity > 0 ) - { - int bonus = (int) attacker.GetDistanceToSqrt( defender ); + attacker.RevealingAction(); - if ( bonus > 0 && m_Velocity > Utility.Random( 100 ) ) - { - AOS.Damage( defender, attacker, bonus * 3, 100, 0, 0, 0, 0 ); + return TimeSpan.FromSeconds(0.25); + } - if ( attacker.Player ) - attacker.SendLocalizedMessage( 1072794 ); // Your arrow hits its mark with velocity! + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + if (attacker.Player && !defender.Player && (defender.Body.IsAnimal || defender.Body.IsMonster) && + 0.4 >= Utility.RandomDouble()) + defender.AddToBackpack(Ammo); - if ( defender.Player ) - defender.SendLocalizedMessage( 1072795 ); // You have been hit by an arrow with velocity! - } - } + if (Core.ML && m_Velocity > 0) + { + int bonus = (int)attacker.GetDistanceToSqrt(defender); - base.OnHit( attacker, defender, damageBonus ); - } + if (bonus > 0 && m_Velocity > Utility.Random(100)) + { + AOS.Damage(defender, attacker, bonus * 3, 100, 0, 0, 0, 0); - public override void OnMiss( Mobile attacker, Mobile defender ) - { - if ( attacker.Player && 0.4 >= Utility.RandomDouble() ) - { - if ( Core.SE ) - { - if ( attacker is PlayerMobile pm ) - { - Type ammo = AmmoType; + if (attacker.Player) + attacker.SendLocalizedMessage(1072794); // Your arrow hits its mark with velocity! - if ( pm.RecoverableAmmo.ContainsKey( ammo ) ) - pm.RecoverableAmmo[ ammo ]++; - else - pm.RecoverableAmmo.Add( ammo, 1 ); + if (defender.Player) + defender.SendLocalizedMessage(1072795); // You have been hit by an arrow with velocity! + } + } - if ( !pm.Warmode ) - { - if ( m_RecoveryTimer == null ) - m_RecoveryTimer = Timer.DelayCall( TimeSpan.FromSeconds( 10 ), pm.RecoverAmmo ); + base.OnHit(attacker, defender, damageBonus); + } - if ( !m_RecoveryTimer.Running ) - m_RecoveryTimer.Start(); - } - } - } else { - Ammo.MoveToWorld( new Point3D( defender.X + Utility.RandomMinMax( -1, 1 ), defender.Y + Utility.RandomMinMax( -1, 1 ), defender.Z ), defender.Map ); - } - } + public override void OnMiss(Mobile attacker, Mobile defender) + { + if (attacker.Player && 0.4 >= Utility.RandomDouble()) + { + if (Core.SE) + { + if (attacker is PlayerMobile pm) + { + Type ammo = AmmoType; - base.OnMiss( attacker, defender ); - } + if (pm.RecoverableAmmo.ContainsKey(ammo)) + pm.RecoverableAmmo[ammo]++; + else + pm.RecoverableAmmo.Add(ammo, 1); - public virtual bool OnFired( Mobile attacker, Mobile defender ) - { - if ( attacker.Player ) - { - BaseQuiver quiver = attacker.FindItemOnLayer( Layer.Cloak ) as BaseQuiver; - Container pack = attacker.Backpack; + if (!pm.Warmode) + { + if (m_RecoveryTimer == null) + m_RecoveryTimer = Timer.DelayCall(TimeSpan.FromSeconds(10), pm.RecoverAmmo); - if ( quiver == null || Utility.Random( 100 ) >= quiver.LowerAmmoCost ) - { - // consume ammo - if ( quiver != null && quiver.ConsumeTotal( AmmoType, 1 ) ) - quiver.InvalidateWeight(); - else if ( pack == null || !pack.ConsumeTotal( AmmoType, 1 ) ) - return false; - } - else if ( quiver.FindItemByType( AmmoType ) == null && ( pack?.FindItemByType( AmmoType ) == null ) ) - { - // lower ammo cost should not work when we have no ammo at all - return false; - } - } + if (!m_RecoveryTimer.Running) + m_RecoveryTimer.Start(); + } + } + } + else + { + Ammo.MoveToWorld( + new Point3D(defender.X + Utility.RandomMinMax(-1, 1), defender.Y + Utility.RandomMinMax(-1, 1), + defender.Z), defender.Map); + } + } - attacker.MovingEffect( defender, EffectID, 18, 1, false, false ); + base.OnMiss(attacker, defender); + } - return true; - } + public virtual bool OnFired(Mobile attacker, Mobile defender) + { + if (attacker.Player) + { + BaseQuiver quiver = attacker.FindItemOnLayer(Layer.Cloak) as BaseQuiver; + Container pack = attacker.Backpack; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (quiver == null || Utility.Random(100) >= quiver.LowerAmmoCost) + { + // consume ammo + if (quiver != null && quiver.ConsumeTotal(AmmoType, 1)) + quiver.InvalidateWeight(); + else if (pack == null || !pack.ConsumeTotal(AmmoType, 1)) + return false; + } + else if (quiver.FindItemByType(AmmoType) == null && pack?.FindItemByType(AmmoType) == null) + { + // lower ammo cost should not work when we have no ammo at all + return false; + } + } - writer.Write( (int) 3 ); // version + attacker.MovingEffect(defender, EffectID, 18, 1, false, false); - writer.Write( (bool) m_Balanced ); - writer.Write( (int) m_Velocity ); - } + return true; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); + writer.Write(3); // version - switch ( version ) - { - case 3: - { - m_Balanced = reader.ReadBool(); - m_Velocity = reader.ReadInt(); + writer.Write(m_Balanced); + writer.Write(m_Velocity); + } - goto case 2; - } - case 2: - case 1: - { - break; - } - case 0: - { - /*m_EffectID =*/ reader.ReadInt(); - break; - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( version < 2 ) - { - WeaponAttributes.MageWeapon = 0; - WeaponAttributes.UseBestSkill = 0; - } - } - } -} + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + m_Balanced = reader.ReadBool(); + m_Velocity = reader.ReadInt(); + + goto case 2; + } + case 2: + case 1: + { + break; + } + case 0: + { + /*m_EffectID =*/ + reader.ReadInt(); + break; + } + } + + if (version < 2) + { + WeaponAttributes.MageWeapon = 0; + WeaponAttributes.UseBestSkill = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/Bow.cs b/Scripts/Items/Weapons/Ranged/Bow.cs index a582a39e5..2421412db 100644 --- a/Scripts/Items/Weapons/Ranged/Bow.cs +++ b/Scripts/Items/Weapons/Ranged/Bow.cs @@ -2,60 +2,60 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x13B2, 0x13B1 )] - public class Bow : BaseRanged - { - public override int EffectID => 0xF42; - public override Type AmmoType => typeof( Arrow ); - public override Item Ammo => new Arrow(); + [Flippable(0x13B2, 0x13B1)] + public class Bow : BaseRanged + { + [Constructible] + public Bow() : base(0x13B2) + { + Weight = 6.0; + Layer = Layer.TwoHanded; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + public Bow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 30; - public override int AosMinDamage => Core.ML ? 15 : 16; - public override int AosMaxDamage => Core.ML ? 19 : 18; - public override int AosSpeed => 25; - public override float MlSpeed => 4.25f; + public override int EffectID => 0xF42; + public override Type AmmoType => typeof(Arrow); + public override Item Ammo => new Arrow(); - public override int OldStrengthReq => 20; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 41; - public override int OldSpeed => 20; + public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int DefMaxRange => 10; + public override int AosStrengthReq => 30; + public override int AosMinDamage => Core.ML ? 15 : 16; + public override int AosMaxDamage => Core.ML ? 19 : 18; + public override int AosSpeed => 25; + public override float MlSpeed => 4.25f; - public override int InitMinHits => 31; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 20; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 41; + public override int OldSpeed => 20; - public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; + public override int DefMaxRange => 10; - [Constructible] - public Bow() : base( 0x13B2 ) - { - Weight = 6.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 60; - public Bow( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 7.0 ) - Weight = 6.0; - } - } -} + if (Weight == 7.0) + Weight = 6.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/CompositeBow.cs b/Scripts/Items/Weapons/Ranged/CompositeBow.cs index f84a88298..4f6ac1a79 100644 --- a/Scripts/Items/Weapons/Ranged/CompositeBow.cs +++ b/Scripts/Items/Weapons/Ranged/CompositeBow.cs @@ -2,56 +2,56 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x26C2, 0x26CC )] - public class CompositeBow : BaseRanged - { - public override int EffectID => 0xF42; - public override Type AmmoType => typeof( Arrow ); - public override Item Ammo => new Arrow(); + [Flippable(0x26C2, 0x26CC)] + public class CompositeBow : BaseRanged + { + [Constructible] + public CompositeBow() : base(0x26C2) + { + Weight = 5.0; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.MovingShot; + public CompositeBow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => Core.ML ? 13 : 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 25; - public override float MlSpeed => 4.00f; + public override int EffectID => 0xF42; + public override Type AmmoType => typeof(Arrow); + public override Item Ammo => new Arrow(); - public override int OldStrengthReq => 45; - public override int OldMinDamage => 15; - public override int OldMaxDamage => 17; - public override int OldSpeed => 25; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.MovingShot; - public override int DefMaxRange => 10; + public override int AosStrengthReq => 45; + public override int AosMinDamage => Core.ML ? 13 : 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 25; + public override float MlSpeed => 4.00f; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int OldStrengthReq => 45; + public override int OldMinDamage => 15; + public override int OldMaxDamage => 17; + public override int OldSpeed => 25; - public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; + public override int DefMaxRange => 10; - [Constructible] - public CompositeBow() : base( 0x26C2 ) - { - Weight = 5.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public CompositeBow( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/Crossbow.cs b/Scripts/Items/Weapons/Ranged/Crossbow.cs index 992571ffe..350e301d1 100644 --- a/Scripts/Items/Weapons/Ranged/Crossbow.cs +++ b/Scripts/Items/Weapons/Ranged/Crossbow.cs @@ -2,55 +2,55 @@ using System; namespace Server.Items { - [FlippableAttribute( 0xF50, 0xF4F )] - public class Crossbow : BaseRanged - { - public override int EffectID => 0x1BFE; - public override Type AmmoType => typeof( Bolt ); - public override Item Ammo => new Bolt(); + [Flippable(0xF50, 0xF4F)] + public class Crossbow : BaseRanged + { + [Constructible] + public Crossbow() : base(0xF50) + { + Weight = 7.0; + Layer = Layer.TwoHanded; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + public Crossbow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 18; - public override int AosMaxDamage => Core.ML ? 22 : 20; - public override int AosSpeed => 24; - public override float MlSpeed => 4.50f; + public override int EffectID => 0x1BFE; + public override Type AmmoType => typeof(Bolt); + public override Item Ammo => new Bolt(); - public override int OldStrengthReq => 30; - public override int OldMinDamage => 8; - public override int OldMaxDamage => 43; - public override int OldSpeed => 18; + public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int DefMaxRange => 8; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 18; + public override int AosMaxDamage => Core.ML ? 22 : 20; + public override int AosSpeed => 24; + public override float MlSpeed => 4.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int OldStrengthReq => 30; + public override int OldMinDamage => 8; + public override int OldMaxDamage => 43; + public override int OldSpeed => 18; - [Constructible] - public Crossbow() : base( 0xF50 ) - { - Weight = 7.0; - Layer = Layer.TwoHanded; - } + public override int DefMaxRange => 8; - public Crossbow( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/FrozenLongbow.cs b/Scripts/Items/Weapons/Ranged/FrozenLongbow.cs index 69ac803e1..f1e1490da 100644 --- a/Scripts/Items/Weapons/Ranged/FrozenLongbow.cs +++ b/Scripts/Items/Weapons/Ranged/FrozenLongbow.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class FrozenLongbow : ElvenCompositeLongbow - { - public override int LabelNumber => 1073507; // frozen longbow + public class FrozenLongbow : ElvenCompositeLongbow + { + [Constructible] + public FrozenLongbow() + { + Attributes.WeaponSpeed = -5; + Attributes.DefendChance = 10; + } - [Constructible] - public FrozenLongbow() - { - Attributes.WeaponSpeed = -5; - Attributes.DefendChance = 10; - } + public FrozenLongbow(Serial serial) : base(serial) + { + } - public FrozenLongbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073507; // frozen longbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/HeavyCrossbow.cs b/Scripts/Items/Weapons/Ranged/HeavyCrossbow.cs index c4573b215..ce075eeff 100644 --- a/Scripts/Items/Weapons/Ranged/HeavyCrossbow.cs +++ b/Scripts/Items/Weapons/Ranged/HeavyCrossbow.cs @@ -2,55 +2,55 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x13FD, 0x13FC )] - public class HeavyCrossbow : BaseRanged - { - public override int EffectID => 0x1BFE; - public override Type AmmoType => typeof( Bolt ); - public override Item Ammo => new Bolt(); + [Flippable(0x13FD, 0x13FC)] + public class HeavyCrossbow : BaseRanged + { + [Constructible] + public HeavyCrossbow() : base(0x13FD) + { + Weight = 9.0; + Layer = Layer.TwoHanded; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.MovingShot; - public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; + public HeavyCrossbow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 80; - public override int AosMinDamage => Core.ML ? 20 : 19; - public override int AosMaxDamage => Core.ML ? 24 : 20; - public override int AosSpeed => 22; - public override float MlSpeed => 5.00f; + public override int EffectID => 0x1BFE; + public override Type AmmoType => typeof(Bolt); + public override Item Ammo => new Bolt(); - public override int OldStrengthReq => 40; - public override int OldMinDamage => 11; - public override int OldMaxDamage => 56; - public override int OldSpeed => 10; + public override WeaponAbility PrimaryAbility => WeaponAbility.MovingShot; + public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; - public override int DefMaxRange => 8; + public override int AosStrengthReq => 80; + public override int AosMinDamage => Core.ML ? 20 : 19; + public override int AosMaxDamage => Core.ML ? 24 : 20; + public override int AosSpeed => 22; + public override float MlSpeed => 5.00f; - public override int InitMinHits => 31; - public override int InitMaxHits => 100; + public override int OldStrengthReq => 40; + public override int OldMinDamage => 11; + public override int OldMaxDamage => 56; + public override int OldSpeed => 10; - [Constructible] - public HeavyCrossbow() : base( 0x13FD ) - { - Weight = 9.0; - Layer = Layer.TwoHanded; - } + public override int DefMaxRange => 8; - public HeavyCrossbow( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 100; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/JukaBow.cs b/Scripts/Items/Weapons/Ranged/JukaBow.cs index 8d19ff132..bba29c71f 100644 --- a/Scripts/Items/Weapons/Ranged/JukaBow.cs +++ b/Scripts/Items/Weapons/Ranged/JukaBow.cs @@ -1,88 +1,91 @@ +using Server.Targeting; + namespace Server.Items { - [FlippableAttribute( 0x13B2, 0x13B1 )] - public class JukaBow : Bow - { - public override int AosStrengthReq => 80; - public override int AosDexterityReq => 80; + [Flippable(0x13B2, 0x13B1)] + public class JukaBow : Bow + { + [Constructible] + public JukaBow() + { + } - public override int OldStrengthReq => 80; - public override int OldDexterityReq => 80; + public JukaBow(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool IsModified => ( Hue == 0x453 ); + public override int AosStrengthReq => 80; + public override int AosDexterityReq => 80; - [Constructible] - public JukaBow() - { - } + public override int OldStrengthReq => 80; + public override int OldDexterityReq => 80; - public override void OnDoubleClick( Mobile from ) - { - if ( IsModified ) - { - from.SendMessage( "That has already been modified." ); - } - else if ( !IsChildOf( from.Backpack ) ) - { - from.SendMessage( "This must be in your backpack to modify it." ); - } - else if ( from.Skills[SkillName.Fletching].Base < 100.0 ) - { - from.SendMessage( "Only a grandmaster bowcrafter can modify this weapon." ); - } - else - { - from.BeginTarget( 2, false, Targeting.TargetFlags.None, OnTargetGears ); - from.SendMessage( "Select the gears you wish to use." ); - } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsModified => Hue == 0x453; - public void OnTargetGears( Mobile from, object targ ) - { - if ( !(targ is Gears g) || !g.IsChildOf( from.Backpack ) ) - { - from.SendMessage( "Those are not gears." ); // Apparently gears that aren't in your backpack aren't really gears at all. :-( - } - else if ( IsModified ) - { - from.SendMessage( "That has already been modified." ); - } - else if ( !IsChildOf( from.Backpack ) ) - { - from.SendMessage( "This must be in your backpack to modify it." ); - } - else if ( from.Skills[SkillName.Fletching].Base < 100.0 ) - { - from.SendMessage( "Only a grandmaster bowcrafter can modify this weapon." ); - } - else - { - g.Consume(); + public override void OnDoubleClick(Mobile from) + { + if (IsModified) + { + from.SendMessage("That has already been modified."); + } + else if (!IsChildOf(from.Backpack)) + { + from.SendMessage("This must be in your backpack to modify it."); + } + else if (from.Skills[SkillName.Fletching].Base < 100.0) + { + from.SendMessage("Only a grandmaster bowcrafter can modify this weapon."); + } + else + { + from.BeginTarget(2, false, TargetFlags.None, OnTargetGears); + from.SendMessage("Select the gears you wish to use."); + } + } - Hue = 0x453; - Slayer = (SlayerName)Utility.Random( 2, 25 ); + public void OnTargetGears(Mobile from, object targ) + { + if (!(targ is Gears g) || !g.IsChildOf(from.Backpack)) + { + from.SendMessage( + "Those are not gears."); // Apparently gears that aren't in your backpack aren't really gears at all. :-( + } + else if (IsModified) + { + from.SendMessage("That has already been modified."); + } + else if (!IsChildOf(from.Backpack)) + { + from.SendMessage("This must be in your backpack to modify it."); + } + else if (from.Skills[SkillName.Fletching].Base < 100.0) + { + from.SendMessage("Only a grandmaster bowcrafter can modify this weapon."); + } + else + { + g.Consume(); - from.SendMessage( "You modify it." ); - } - } + Hue = 0x453; + Slayer = (SlayerName)Utility.Random(2, 25); - public JukaBow( Serial serial ) : base( serial ) - { - } + from.SendMessage("You modify it."); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/LightweightShortbow.cs b/Scripts/Items/Weapons/Ranged/LightweightShortbow.cs index a392d1e4b..b79dcb08d 100644 --- a/Scripts/Items/Weapons/Ranged/LightweightShortbow.cs +++ b/Scripts/Items/Weapons/Ranged/LightweightShortbow.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class LightweightShortbow : MagicalShortbow - { - public override int LabelNumber => 1073510; // lightweight shortbow + public class LightweightShortbow : MagicalShortbow + { + [Constructible] + public LightweightShortbow() + { + Balanced = true; + } - [Constructible] - public LightweightShortbow() - { - Balanced = true; - } + public LightweightShortbow(Serial serial) : base(serial) + { + } - public LightweightShortbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073510; // lightweight shortbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/LongbowOfMight.cs b/Scripts/Items/Weapons/Ranged/LongbowOfMight.cs index 531f542b5..d6dcef563 100644 --- a/Scripts/Items/Weapons/Ranged/LongbowOfMight.cs +++ b/Scripts/Items/Weapons/Ranged/LongbowOfMight.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class LongbowOfMight : ElvenCompositeLongbow - { - public override int LabelNumber => 1073508; // longbow of might + public class LongbowOfMight : ElvenCompositeLongbow + { + [Constructible] + public LongbowOfMight() + { + Attributes.WeaponDamage = 5; + } - [Constructible] - public LongbowOfMight() - { - Attributes.WeaponDamage = 5; - } + public LongbowOfMight(Serial serial) : base(serial) + { + } - public LongbowOfMight( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073508; // longbow of might - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/MysticalShortbow.cs b/Scripts/Items/Weapons/Ranged/MysticalShortbow.cs index d4cfdf690..6dcadc3c7 100644 --- a/Scripts/Items/Weapons/Ranged/MysticalShortbow.cs +++ b/Scripts/Items/Weapons/Ranged/MysticalShortbow.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class MysticalShortbow : MagicalShortbow - { - public override int LabelNumber => 1073511; // mystical shortbow + public class MysticalShortbow : MagicalShortbow + { + [Constructible] + public MysticalShortbow() + { + Attributes.SpellChanneling = 1; + Attributes.CastSpeed = -1; + } - [Constructible] - public MysticalShortbow() - { - Attributes.SpellChanneling = 1; - Attributes.CastSpeed = -1; - } + public MysticalShortbow(Serial serial) : base(serial) + { + } - public MysticalShortbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073511; // mystical shortbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/RangersShortbow.cs b/Scripts/Items/Weapons/Ranged/RangersShortbow.cs index 5b5e14d90..8e0c1ef59 100644 --- a/Scripts/Items/Weapons/Ranged/RangersShortbow.cs +++ b/Scripts/Items/Weapons/Ranged/RangersShortbow.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class RangersShortbow : MagicalShortbow - { - public override int LabelNumber => 1073509; // ranger's shortbow + public class RangersShortbow : MagicalShortbow + { + [Constructible] + public RangersShortbow() + { + Attributes.WeaponSpeed = 5; + } - [Constructible] - public RangersShortbow() - { - Attributes.WeaponSpeed = 5; - } + public RangersShortbow(Serial serial) : base(serial) + { + } - public RangersShortbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073509; // ranger's shortbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/RepeatingCrossbow.cs b/Scripts/Items/Weapons/Ranged/RepeatingCrossbow.cs index d0744f419..6ad769d9d 100644 --- a/Scripts/Items/Weapons/Ranged/RepeatingCrossbow.cs +++ b/Scripts/Items/Weapons/Ranged/RepeatingCrossbow.cs @@ -2,54 +2,54 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x26C3, 0x26CD )] - public class RepeatingCrossbow : BaseRanged - { - public override int EffectID => 0x1BFE; - public override Type AmmoType => typeof( Bolt ); - public override Item Ammo => new Bolt(); + [Flippable(0x26C3, 0x26CD)] + public class RepeatingCrossbow : BaseRanged + { + [Constructible] + public RepeatingCrossbow() : base(0x26C3) + { + Weight = 6.0; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.MovingShot; + public RepeatingCrossbow(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 30; - public override int AosMinDamage => Core.ML ? 8 : 10; - public override int AosMaxDamage => 12; - public override int AosSpeed => 41; - public override float MlSpeed => 2.75f; + public override int EffectID => 0x1BFE; + public override Type AmmoType => typeof(Bolt); + public override Item Ammo => new Bolt(); - public override int OldStrengthReq => 30; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 12; - public override int OldSpeed => 41; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.MovingShot; - public override int DefMaxRange => 7; + public override int AosStrengthReq => 30; + public override int AosMinDamage => Core.ML ? 8 : 10; + public override int AosMaxDamage => 12; + public override int AosSpeed => 41; + public override float MlSpeed => 2.75f; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int OldStrengthReq => 30; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 12; + public override int OldSpeed => 41; - [Constructible] - public RepeatingCrossbow() : base( 0x26C3 ) - { - Weight = 6.0; - } + public override int DefMaxRange => 7; - public RepeatingCrossbow( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Ranged/SlayerLongbow.cs b/Scripts/Items/Weapons/Ranged/SlayerLongbow.cs index 09a7f14b3..0ea51d838 100644 --- a/Scripts/Items/Weapons/Ranged/SlayerLongbow.cs +++ b/Scripts/Items/Weapons/Ranged/SlayerLongbow.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SlayerLongbow : ElvenCompositeLongbow - { - public override int LabelNumber => 1073506; // slayer longbow + public class SlayerLongbow : ElvenCompositeLongbow + { + [Constructible] + public SlayerLongbow() + { + Slayer2 = (SlayerName)Utility.RandomMinMax(1, 27); + } - [Constructible] - public SlayerLongbow() - { - Slayer2 = (SlayerName) Utility.RandomMinMax( 1, 27 ); - } + public SlayerLongbow(Serial serial) : base(serial) + { + } - public SlayerLongbow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073506; // slayer longbow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Bokuto.cs b/Scripts/Items/Weapons/SE Weapons/Bokuto.cs index 50dbc9375..f1a44879e 100644 --- a/Scripts/Items/Weapons/SE Weapons/Bokuto.cs +++ b/Scripts/Items/Weapons/SE Weapons/Bokuto.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x27A8, 0x27F3 )] - public class Bokuto : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; - public override WeaponAbility SecondaryAbility => WeaponAbility.NerveStrike; + [Flippable(0x27A8, 0x27F3)] + public class Bokuto : BaseSword + { + [Constructible] + public Bokuto() : base(0x27A8) + { + Weight = 7.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 53; - public override float MlSpeed => 2.00f; + public Bokuto(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 11; - public override int OldSpeed => 53; + public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; + public override WeaponAbility SecondaryAbility => WeaponAbility.NerveStrike; - public override int DefHitSound => 0x536; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 53; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 25; - public override int InitMaxHits => 50; + public override int OldStrengthReq => 20; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 11; + public override int OldSpeed => 53; - [Constructible] - public Bokuto() : base( 0x27A8 ) - { - Weight = 7.0; - } + public override int DefHitSound => 0x536; + public override int DefMissSound => 0x23A; - public Bokuto( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 25; + public override int InitMaxHits => 50; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Daisho.cs b/Scripts/Items/Weapons/SE Weapons/Daisho.cs index 52036adb9..12ef2fed7 100644 --- a/Scripts/Items/Weapons/SE Weapons/Daisho.cs +++ b/Scripts/Items/Weapons/SE Weapons/Daisho.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x27A9, 0x27F4 )] - public class Daisho : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; - public override WeaponAbility SecondaryAbility => WeaponAbility.DoubleStrike; + [Flippable(0x27A9, 0x27F4)] + public class Daisho : BaseSword + { + [Constructible] + public Daisho() : base(0x27A9) + { + Weight = 8.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 40; - public override float MlSpeed => 2.75f; + public Daisho(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 13; - public override int OldMaxDamage => 15; - public override int OldSpeed => 40; + public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; + public override WeaponAbility SecondaryAbility => WeaponAbility.DoubleStrike; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 40; + public override float MlSpeed => 2.75f; - public override int InitMinHits => 45; - public override int InitMaxHits => 65; + public override int OldStrengthReq => 40; + public override int OldMinDamage => 13; + public override int OldMaxDamage => 15; + public override int OldSpeed => 40; - [Constructible] - public Daisho() : base( 0x27A9 ) - { - Weight = 8.0; - Layer = Layer.TwoHanded; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public Daisho( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 45; + public override int InitMaxHits => 65; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Kama.cs b/Scripts/Items/Weapons/SE Weapons/Kama.cs index 2fc64dda0..4b8a63361 100644 --- a/Scripts/Items/Weapons/SE Weapons/Kama.cs +++ b/Scripts/Items/Weapons/SE Weapons/Kama.cs @@ -1,55 +1,55 @@ namespace Server.Items { - [FlippableAttribute( 0x27AD, 0x27F8 )] - public class Kama : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.DefenseMastery; + [Flippable(0x27AD, 0x27F8)] + public class Kama : BaseKnife + { + [Constructible] + public Kama() : base(0x27AD) + { + Weight = 7.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 15; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 55; - public override float MlSpeed => 2.00f; + public Kama(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 11; - public override int OldSpeed => 55; + public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.DefenseMastery; - public override int DefHitSound => 0x232; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 15; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 55; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 35; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 15; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 11; + public override int OldSpeed => 55; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x232; + public override int DefMissSound => 0x238; - [Constructible] - public Kama() : base( 0x27AD ) - { - Weight = 7.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 35; + public override int InitMaxHits => 60; - public Kama( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Lajatang.cs b/Scripts/Items/Weapons/SE Weapons/Lajatang.cs index c6afcbb0d..46cc22617 100644 --- a/Scripts/Items/Weapons/SE Weapons/Lajatang.cs +++ b/Scripts/Items/Weapons/SE Weapons/Lajatang.cs @@ -1,55 +1,55 @@ namespace Server.Items { - [FlippableAttribute( 0x27A7, 0x27F2 )] - public class Lajatang : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DefenseMastery; - public override WeaponAbility SecondaryAbility => WeaponAbility.FrenziedWhirlwind; + [Flippable(0x27A7, 0x27F2)] + public class Lajatang : BaseKnife + { + [Constructible] + public Lajatang() : base(0x27A7) + { + Weight = 12.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 65; - public override int AosMinDamage => 16; - public override int AosMaxDamage => 18; - public override int AosSpeed => 32; - public override float MlSpeed => 3.50f; + public Lajatang(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 65; - public override int OldMinDamage => 16; - public override int OldMaxDamage => 18; - public override int OldSpeed => 55; + public override WeaponAbility PrimaryAbility => WeaponAbility.DefenseMastery; + public override WeaponAbility SecondaryAbility => WeaponAbility.FrenziedWhirlwind; - public override int DefHitSound => 0x232; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 65; + public override int AosMinDamage => 16; + public override int AosMaxDamage => 18; + public override int AosSpeed => 32; + public override float MlSpeed => 3.50f; - public override int InitMinHits => 90; - public override int InitMaxHits => 95; + public override int OldStrengthReq => 65; + public override int OldMinDamage => 16; + public override int OldMaxDamage => 18; + public override int OldSpeed => 55; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x232; + public override int DefMissSound => 0x238; - [Constructible] - public Lajatang() : base( 0x27A7 ) - { - Weight = 12.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 90; + public override int InitMaxHits => 95; - public Lajatang( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/NoDachi.cs b/Scripts/Items/Weapons/SE Weapons/NoDachi.cs index d4870ac44..c9e28af37 100644 --- a/Scripts/Items/Weapons/SE Weapons/NoDachi.cs +++ b/Scripts/Items/Weapons/SE Weapons/NoDachi.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x27A2, 0x27ED )] - public class NoDachi : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.RidingSwipe; + [Flippable(0x27A2, 0x27ED)] + public class NoDachi : BaseSword + { + [Constructible] + public NoDachi() : base(0x27A2) + { + Weight = 10.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 16; - public override int AosMaxDamage => 18; - public override int AosSpeed => 35; - public override float MlSpeed => 3.50f; + public NoDachi(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 16; - public override int OldMaxDamage => 18; - public override int OldSpeed => 35; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.RidingSwipe; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 16; + public override int AosMaxDamage => 18; + public override int AosSpeed => 35; + public override float MlSpeed => 3.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 90; + public override int OldStrengthReq => 40; + public override int OldMinDamage => 16; + public override int OldMaxDamage => 18; + public override int OldSpeed => 35; - [Constructible] - public NoDachi() : base( 0x27A2 ) - { - Weight = 10.0; - Layer = Layer.TwoHanded; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public NoDachi( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 90; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Nunchaku.cs b/Scripts/Items/Weapons/SE Weapons/Nunchaku.cs index 345ad54c7..3d95ee61f 100644 --- a/Scripts/Items/Weapons/SE Weapons/Nunchaku.cs +++ b/Scripts/Items/Weapons/SE Weapons/Nunchaku.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x27AE, 0x27F9 )] - public class Nunchaku : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Block; - public override WeaponAbility SecondaryAbility => WeaponAbility.Feint; + [Flippable(0x27AE, 0x27F9)] + public class Nunchaku : BaseBashing + { + [Constructible] + public Nunchaku() : base(0x27AE) + { + Weight = 5.0; + } - public override int AosStrengthReq => 15; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 13; - public override int AosSpeed => 47; - public override float MlSpeed => 2.50f; + public Nunchaku(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 11; - public override int OldMaxDamage => 13; - public override int OldSpeed => 47; + public override WeaponAbility PrimaryAbility => WeaponAbility.Block; + public override WeaponAbility SecondaryAbility => WeaponAbility.Feint; - public override int DefHitSound => 0x535; - public override int DefMissSound => 0x239; + public override int AosStrengthReq => 15; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 13; + public override int AosSpeed => 47; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 40; - public override int InitMaxHits => 55; + public override int OldStrengthReq => 15; + public override int OldMinDamage => 11; + public override int OldMaxDamage => 13; + public override int OldSpeed => 47; - [Constructible] - public Nunchaku() : base( 0x27AE ) - { - Weight = 5.0; - } + public override int DefHitSound => 0x535; + public override int DefMissSound => 0x239; - public Nunchaku( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 40; + public override int InitMaxHits => 55; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Sai.cs b/Scripts/Items/Weapons/SE Weapons/Sai.cs index 597c85599..bf68f6cd1 100644 --- a/Scripts/Items/Weapons/SE Weapons/Sai.cs +++ b/Scripts/Items/Weapons/SE Weapons/Sai.cs @@ -1,55 +1,55 @@ namespace Server.Items { - [FlippableAttribute( 0x27AF, 0x27FA )] - public class Sai : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Block; - public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorPierce; + [Flippable(0x27AF, 0x27FA)] + public class Sai : BaseKnife + { + [Constructible] + public Sai() : base(0x27AF) + { + Weight = 7.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 15; - public override int AosMinDamage => 9; - public override int AosMaxDamage => 11; - public override int AosSpeed => 55; - public override float MlSpeed => 2.00f; + public Sai(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 9; - public override int OldMaxDamage => 11; - public override int OldSpeed => 55; + public override WeaponAbility PrimaryAbility => WeaponAbility.Block; + public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorPierce; - public override int DefHitSound => 0x23C; - public override int DefMissSound => 0x232; + public override int AosStrengthReq => 15; + public override int AosMinDamage => 9; + public override int AosMaxDamage => 11; + public override int AosSpeed => 55; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 55; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 15; + public override int OldMinDamage => 9; + public override int OldMaxDamage => 11; + public override int OldSpeed => 55; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x23C; + public override int DefMissSound => 0x232; - [Constructible] - public Sai() : base( 0x27AF ) - { - Weight = 7.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 55; + public override int InitMaxHits => 60; - public Sai( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Tekagi.cs b/Scripts/Items/Weapons/SE Weapons/Tekagi.cs index 73b94cde7..d107cc2db 100644 --- a/Scripts/Items/Weapons/SE Weapons/Tekagi.cs +++ b/Scripts/Items/Weapons/SE Weapons/Tekagi.cs @@ -1,55 +1,55 @@ namespace Server.Items { - [FlippableAttribute( 0x27Ab, 0x27F6 )] - public class Tekagi : BaseKnife - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DualWield; - public override WeaponAbility SecondaryAbility => WeaponAbility.TalonStrike; + [Flippable(0x27Ab, 0x27F6)] + public class Tekagi : BaseKnife + { + [Constructible] + public Tekagi() : base(0x27AB) + { + Weight = 5.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 10; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 12; - public override int AosSpeed => 53; - public override float MlSpeed => 2.00f; + public Tekagi(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 12; - public override int OldSpeed => 53; + public override WeaponAbility PrimaryAbility => WeaponAbility.DualWield; + public override WeaponAbility SecondaryAbility => WeaponAbility.TalonStrike; - public override int DefHitSound => 0x238; - public override int DefMissSound => 0x232; + public override int AosStrengthReq => 10; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 12; + public override int AosSpeed => 53; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 35; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 12; + public override int OldSpeed => 53; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x238; + public override int DefMissSound => 0x232; - [Constructible] - public Tekagi() : base( 0x27AB ) - { - Weight = 5.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 35; + public override int InitMaxHits => 60; - public Tekagi( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Tessen.cs b/Scripts/Items/Weapons/SE Weapons/Tessen.cs index 531fef5d7..707eec206 100644 --- a/Scripts/Items/Weapons/SE Weapons/Tessen.cs +++ b/Scripts/Items/Weapons/SE Weapons/Tessen.cs @@ -1,53 +1,53 @@ namespace Server.Items { - [FlippableAttribute( 0x27A3, 0x27EE )] - public class Tessen : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; - public override WeaponAbility SecondaryAbility => WeaponAbility.Block; + [Flippable(0x27A3, 0x27EE)] + public class Tessen : BaseBashing + { + [Constructible] + public Tessen() : base(0x27A3) + { + Weight = 6.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 10; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 12; - public override int AosSpeed => 50; - public override float MlSpeed => 2.00f; + public Tessen(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 12; - public override int OldSpeed => 50; + public override WeaponAbility PrimaryAbility => WeaponAbility.Feint; + public override WeaponAbility SecondaryAbility => WeaponAbility.Block; - public override int DefHitSound => 0x232; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 10; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 12; + public override int AosSpeed => 50; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 55; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 12; + public override int OldSpeed => 50; - public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; + public override int DefHitSound => 0x232; + public override int DefMissSound => 0x238; - [Constructible] - public Tessen() : base( 0x27A3 ) - { - Weight = 6.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 55; + public override int InitMaxHits => 60; - public Tessen( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Tetsubo.cs b/Scripts/Items/Weapons/SE Weapons/Tetsubo.cs index 747d4a1ab..03029b081 100644 --- a/Scripts/Items/Weapons/SE Weapons/Tetsubo.cs +++ b/Scripts/Items/Weapons/SE Weapons/Tetsubo.cs @@ -1,53 +1,53 @@ namespace Server.Items { - [FlippableAttribute( 0x27A6, 0x27F1 )] - public class Tetsubo : BaseBashing - { - public override WeaponAbility PrimaryAbility => WeaponAbility.FrenziedWhirlwind; - public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; + [Flippable(0x27A6, 0x27F1)] + public class Tetsubo : BaseBashing + { + [Constructible] + public Tetsubo() : base(0x27A6) + { + Weight = 8.0; + Layer = Layer.TwoHanded; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 14; - public override int AosSpeed => 45; - public override float MlSpeed => 2.50f; + public Tetsubo(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 12; - public override int OldMaxDamage => 14; - public override int OldSpeed => 45; + public override WeaponAbility PrimaryAbility => WeaponAbility.FrenziedWhirlwind; + public override WeaponAbility SecondaryAbility => WeaponAbility.CrushingBlow; - public override int DefHitSound => 0x233; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 14; + public override int AosSpeed => 45; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 60; - public override int InitMaxHits => 65; + public override int OldStrengthReq => 35; + public override int OldMinDamage => 12; + public override int OldMaxDamage => 14; + public override int OldSpeed => 45; - public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; + public override int DefHitSound => 0x233; + public override int DefMissSound => 0x238; - [Constructible] - public Tetsubo() : base( 0x27A6 ) - { - Weight = 8.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 60; + public override int InitMaxHits => 65; - public Tetsubo( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Wakizashi.cs b/Scripts/Items/Weapons/SE Weapons/Wakizashi.cs index 7a9f1b80b..3a34687e8 100644 --- a/Scripts/Items/Weapons/SE Weapons/Wakizashi.cs +++ b/Scripts/Items/Weapons/SE Weapons/Wakizashi.cs @@ -1,51 +1,51 @@ namespace Server.Items { - [FlippableAttribute( 0x27A4, 0x27EF )] - public class Wakizashi : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.FrenziedWhirlwind; - public override WeaponAbility SecondaryAbility => WeaponAbility.DoubleStrike; + [Flippable(0x27A4, 0x27EF)] + public class Wakizashi : BaseSword + { + [Constructible] + public Wakizashi() : base(0x27A4) + { + Weight = 5.0; + Layer = Layer.OneHanded; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 13; - public override int AosSpeed => 44; - public override float MlSpeed => 2.50f; + public Wakizashi(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 11; - public override int OldMaxDamage => 13; - public override int OldSpeed => 44; + public override WeaponAbility PrimaryAbility => WeaponAbility.FrenziedWhirlwind; + public override WeaponAbility SecondaryAbility => WeaponAbility.DoubleStrike; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 13; + public override int AosSpeed => 44; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 45; - public override int InitMaxHits => 50; + public override int OldStrengthReq => 20; + public override int OldMinDamage => 11; + public override int OldMaxDamage => 13; + public override int OldSpeed => 44; - [Constructible] - public Wakizashi() : base( 0x27A4 ) - { - Weight = 5.0; - Layer = Layer.OneHanded; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public Wakizashi( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 45; + public override int InitMaxHits => 50; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SE Weapons/Yumi.cs b/Scripts/Items/Weapons/SE Weapons/Yumi.cs index 39564fa51..b813f41d5 100644 --- a/Scripts/Items/Weapons/SE Weapons/Yumi.cs +++ b/Scripts/Items/Weapons/SE Weapons/Yumi.cs @@ -2,60 +2,60 @@ using System; namespace Server.Items { - [FlippableAttribute( 0x27A5, 0x27F0 )] - public class Yumi : BaseRanged - { - public override int EffectID => 0xF42; - public override Type AmmoType => typeof( Arrow ); - public override Item Ammo => new Arrow(); + [Flippable(0x27A5, 0x27F0)] + public class Yumi : BaseRanged + { + [Constructible] + public Yumi() : base(0x27A5) + { + Weight = 9.0; + Layer = Layer.TwoHanded; + } - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorPierce; - public override WeaponAbility SecondaryAbility => WeaponAbility.DoubleShot; + public Yumi(Serial serial) : base(serial) + { + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => Core.ML ? 16 : 18; - public override int AosMaxDamage => 20; - public override int AosSpeed => 25; - public override float MlSpeed => 4.5f; + public override int EffectID => 0xF42; + public override Type AmmoType => typeof(Arrow); + public override Item Ammo => new Arrow(); - public override int OldStrengthReq => 35; - public override int OldMinDamage => 18; - public override int OldMaxDamage => 20; - public override int OldSpeed => 25; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorPierce; + public override WeaponAbility SecondaryAbility => WeaponAbility.DoubleShot; - public override int DefMaxRange => 10; + public override int AosStrengthReq => 35; + public override int AosMinDamage => Core.ML ? 16 : 18; + public override int AosMaxDamage => 20; + public override int AosSpeed => 25; + public override float MlSpeed => 4.5f; - public override int InitMinHits => 55; - public override int InitMaxHits => 60; + public override int OldStrengthReq => 35; + public override int OldMinDamage => 18; + public override int OldMaxDamage => 20; + public override int OldSpeed => 25; - public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; + public override int DefMaxRange => 10; - [Constructible] - public Yumi() : base( 0x27A5 ) - { - Weight = 9.0; - Layer = Layer.TwoHanded; - } + public override int InitMinHits => 55; + public override int InitMaxHits => 60; - public Yumi( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.ShootBow; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 7.0 ) - Weight = 6.0; - } - } -} + if (Weight == 7.0) + Weight = 6.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SlayerEntry.cs b/Scripts/Items/Weapons/SlayerEntry.cs index 756105b67..ac6caf0ff 100644 --- a/Scripts/Items/Weapons/SlayerEntry.cs +++ b/Scripts/Items/Weapons/SlayerEntry.cs @@ -2,101 +2,101 @@ using System; namespace Server.Items { - public class SlayerEntry - { - public SlayerGroup Group { get; set; } + public class SlayerEntry + { + private static int[] m_AosTitles = + { + 1060479, // undead slayer + 1060470, // orc slayer + 1060480, // troll slayer + 1060468, // ogre slayer + 1060472, // repond slayer + 1060462, // dragon slayer + 1060478, // terathan slayer + 1060475, // snake slayer + 1060467, // lizardman slayer + 1060473, // reptile slayer + 1060460, // demon slayer + 1060466, // gargoyle slayer + 1017396, // Balron Damnation + 1060461, // demon slayer + 1060469, // ophidian slayer + 1060477, // spider slayer + 1060474, // scorpion slayer + 1060458, // arachnid slayer + 1060465, // fire elemental slayer + 1060481, // water elemental slayer + 1060457, // air elemental slayer + 1060471, // poison elemental slayer + 1060463, // earth elemental slayer + 1060459, // blood elemental slayer + 1060476, // snow elemental slayer + 1060464, // elemental slayer + 1070855 // fey slayer + }; - public SlayerName Name { get; } + private static int[] m_OldTitles = + { + 1017384, // Silver + 1017385, // Orc Slaying + 1017386, // Troll Slaughter + 1017387, // Ogre Thrashing + 1017388, // Repond + 1017389, // Dragon Slaying + 1017390, // Terathan + 1017391, // Snake's Bane + 1017392, // Lizardman Slaughter + 1017393, // Reptilian Death + 1017394, // Daemon Dismissal + 1017395, // Gargoyle's Foe + 1017396, // Balron Damnation + 1017397, // Exorcism + 1017398, // Ophidian + 1017399, // Spider's Death + 1017400, // Scorpion's Bane + 1017401, // Arachnid Doom + 1017402, // Flame Dousing + 1017403, // Water Dissipation + 1017404, // Vacuum + 1017405, // Elemental Health + 1017406, // Earth Shatter + 1017407, // Blood Drinking + 1017408, // Summer Wind + 1017409, // Elemental Ban + 1070855 // fey slayer + }; - public Type[] Types { get; } + public SlayerEntry(SlayerName name, params Type[] types) + { + Name = name; + Types = types; + } - private static int[] m_AosTitles = { - 1060479, // undead slayer - 1060470, // orc slayer - 1060480, // troll slayer - 1060468, // ogre slayer - 1060472, // repond slayer - 1060462, // dragon slayer - 1060478, // terathan slayer - 1060475, // snake slayer - 1060467, // lizardman slayer - 1060473, // reptile slayer - 1060460, // demon slayer - 1060466, // gargoyle slayer - 1017396, // Balron Damnation - 1060461, // demon slayer - 1060469, // ophidian slayer - 1060477, // spider slayer - 1060474, // scorpion slayer - 1060458, // arachnid slayer - 1060465, // fire elemental slayer - 1060481, // water elemental slayer - 1060457, // air elemental slayer - 1060471, // poison elemental slayer - 1060463, // earth elemental slayer - 1060459, // blood elemental slayer - 1060476, // snow elemental slayer - 1060464, // elemental slayer - 1070855 // fey slayer - }; + public SlayerGroup Group{ get; set; } - private static int[] m_OldTitles = { - 1017384, // Silver - 1017385, // Orc Slaying - 1017386, // Troll Slaughter - 1017387, // Ogre Thrashing - 1017388, // Repond - 1017389, // Dragon Slaying - 1017390, // Terathan - 1017391, // Snake's Bane - 1017392, // Lizardman Slaughter - 1017393, // Reptilian Death - 1017394, // Daemon Dismissal - 1017395, // Gargoyle's Foe - 1017396, // Balron Damnation - 1017397, // Exorcism - 1017398, // Ophidian - 1017399, // Spider's Death - 1017400, // Scorpion's Bane - 1017401, // Arachnid Doom - 1017402, // Flame Dousing - 1017403, // Water Dissipation - 1017404, // Vacuum - 1017405, // Elemental Health - 1017406, // Earth Shatter - 1017407, // Blood Drinking - 1017408, // Summer Wind - 1017409, // Elemental Ban - 1070855 // fey slayer - }; + public SlayerName Name{ get; } - public int Title - { - get - { - int[] titles = ( Core.AOS ? m_AosTitles : m_OldTitles ); + public Type[] Types{ get; } - return titles[(int)Name - 1]; - } - } + public int Title + { + get + { + int[] titles = Core.AOS ? m_AosTitles : m_OldTitles; - public SlayerEntry( SlayerName name, params Type[] types ) - { - Name = name; - Types = types; - } + return titles[(int)Name - 1]; + } + } - public bool Slays( Mobile m ) - { - Type t = m.GetType(); + public bool Slays(Mobile m) + { + Type t = m.GetType(); - for ( int i = 0; i < Types.Length; ++i ) - { - if ( Types[i].IsAssignableFrom( t ) ) - return true; - } + for (int i = 0; i < Types.Length; ++i) + if (Types[i].IsAssignableFrom(t)) + return true; - return false; - } - } + return false; + } + } } \ No newline at end of file diff --git a/Scripts/Items/Weapons/SlayerGroup.cs b/Scripts/Items/Weapons/SlayerGroup.cs index dc1763d0b..1f33b7279 100644 --- a/Scripts/Items/Weapons/SlayerGroup.cs +++ b/Scripts/Items/Weapons/SlayerGroup.cs @@ -3,193 +3,243 @@ using Server.Mobiles; namespace Server.Items { - public class SlayerGroup - { - public static SlayerEntry[] TotalEntries { get; } + public class SlayerGroup + { + static SlayerGroup() + { + SlayerGroup humanoid = new SlayerGroup(); + SlayerGroup undead = new SlayerGroup(); + SlayerGroup elemental = new SlayerGroup(); + SlayerGroup abyss = new SlayerGroup(); + SlayerGroup arachnid = new SlayerGroup(); + SlayerGroup reptilian = new SlayerGroup(); + SlayerGroup fey = new SlayerGroup(); - public static SlayerGroup[] Groups { get; } + humanoid.Opposition = new[] { undead }; + humanoid.FoundOn = new[] { typeof(BoneKnight), typeof(Lich), typeof(LichLord) }; + humanoid.Super = new SlayerEntry(SlayerName.Repond, typeof(ArcticOgreLord), typeof(Cyclops), typeof(Ettin), + typeof(EvilMage), typeof(EvilMageLord), typeof(FrostTroll), typeof(MeerCaptain), typeof(MeerEternal), + typeof(MeerMage), typeof(MeerWarrior), typeof(Ogre), typeof(OgreLord), typeof(Orc), typeof(OrcBomber), + typeof(OrcBrute), typeof(OrcCaptain), /*typeof( OrcChopper ), typeof( OrcScout ),*/ typeof(OrcishLord), + typeof(OrcishMage), typeof(Ratman), typeof(RatmanArcher), typeof(RatmanMage), typeof(SavageRider), + typeof(SavageShaman), typeof(Savage), typeof(Titan), typeof(Troglodyte), typeof(Troll)); + humanoid.Entries = new[] + { + new SlayerEntry(SlayerName.OgreTrashing, typeof(Ogre), typeof(OgreLord), typeof(ArcticOgreLord)), + new SlayerEntry(SlayerName.OrcSlaying, typeof(Orc), typeof(OrcBomber), typeof(OrcBrute), + typeof(OrcCaptain), /* typeof( OrcChopper ), typeof( OrcScout ),*/ typeof(OrcishLord), + typeof(OrcishMage)), + new SlayerEntry(SlayerName.TrollSlaughter, typeof(Troll), typeof(FrostTroll)) + }; - public static SlayerEntry GetEntryByName( SlayerName name ) - { - int v = (int)name; + undead.Opposition = new[] { humanoid }; + undead.Super = new SlayerEntry(SlayerName.Silver, typeof(AncientLich), typeof(Bogle), typeof(BoneKnight), + typeof(BoneMagi), /* typeof( DarkGuardian ), */typeof(DarknightCreeper), typeof(FleshGolem), typeof(Ghoul), + typeof(GoreFiend), typeof(HellSteed), typeof(LadyOfTheSnow), typeof(Lich), typeof(LichLord), typeof(Mummy), + typeof(PestilentBandage), typeof(Revenant), typeof(RevenantLion), typeof(RottingCorpse), typeof(Shade), + typeof(ShadowKnight), typeof(SkeletalKnight), typeof(SkeletalMage), typeof(SkeletalMount), typeof(Skeleton), + typeof(Spectre), typeof(Wraith), typeof(Zombie)); + undead.Entries = new SlayerEntry[0]; - if ( v >= 0 && v < TotalEntries.Length ) - return TotalEntries[v]; + fey.Opposition = new[] { abyss }; + fey.Super = new SlayerEntry(SlayerName.Fey, typeof(Centaur), typeof(CuSidhe), typeof(EtherealWarrior), + typeof(Kirin), typeof(LordOaks), typeof(Pixie), typeof(Silvani), typeof(Treefellow), typeof(Unicorn), + typeof(Wisp), typeof(MLDryad), typeof(Satyr)); + fey.Entries = new SlayerEntry[0]; - return null; - } + elemental.Opposition = new[] { abyss }; + elemental.FoundOn = new[] { typeof(Balron), typeof(Daemon) }; + elemental.Super = new SlayerEntry(SlayerName.ElementalBan, typeof(AcidElemental), typeof(AgapiteElemental), + typeof(AirElemental), typeof(SummonedAirElemental), typeof(BloodElemental), typeof(BronzeElemental), + typeof(CopperElemental), typeof(CrystalElemental), typeof(DullCopperElemental), typeof(EarthElemental), + typeof(SummonedEarthElemental), typeof(Efreet), typeof(FireElemental), typeof(SummonedFireElemental), + typeof(GoldenElemental), typeof(IceElemental), typeof(KazeKemono), typeof(PoisonElemental), typeof(RaiJu), + typeof(SandVortex), typeof(ShadowIronElemental), typeof(SnowElemental), typeof(ValoriteElemental), + typeof(VeriteElemental), typeof(WaterElemental), typeof(SummonedWaterElemental)); + elemental.Entries = new[] + { + new SlayerEntry(SlayerName.BloodDrinking, typeof(BloodElemental)), + new SlayerEntry(SlayerName.EarthShatter, typeof(AgapiteElemental), typeof(BronzeElemental), + typeof(CopperElemental), typeof(DullCopperElemental), typeof(EarthElemental), + typeof(SummonedEarthElemental), typeof(GoldenElemental), typeof(ShadowIronElemental), + typeof(ValoriteElemental), typeof(VeriteElemental)), + new SlayerEntry(SlayerName.ElementalHealth, typeof(PoisonElemental)), + new SlayerEntry(SlayerName.FlameDousing, typeof(FireElemental), typeof(SummonedFireElemental)), + new SlayerEntry(SlayerName.SummerWind, typeof(SnowElemental), typeof(IceElemental)), + new SlayerEntry(SlayerName.Vacuum, typeof(AirElemental), typeof(SummonedAirElemental)), + new SlayerEntry(SlayerName.WaterDissipation, typeof(WaterElemental), typeof(SummonedWaterElemental)) + }; - public static SlayerName GetLootSlayerType( Type type ) - { - for ( int i = 0; i < Groups.Length; ++i ) - { - SlayerGroup group = Groups[i]; - Type[] foundOn = group.FoundOn; + abyss.Opposition = new[] { elemental, fey }; + abyss.FoundOn = new[] { typeof(BloodElemental) }; - bool inGroup = false; + if (Core.AOS) + { + abyss.Super = new SlayerEntry(SlayerName.Exorcism, typeof(AbysmalHorror), typeof(ArcaneDaemon), + typeof(Balron), typeof(BoneDemon), typeof(ChaosDaemon), typeof(Daemon), typeof(SummonedDaemon), + typeof(DemonKnight), typeof(Devourer), typeof(EnslavedGargoyle), typeof(FanDancer), typeof(FireGargoyle), + typeof(Gargoyle), typeof(GargoyleDestroyer), typeof(GargoyleEnforcer), typeof(Gibberling), + typeof(HordeMinion), typeof(IceFiend), typeof(Imp), typeof(Impaler), typeof(Moloch), typeof(Oni), + typeof(Ravager), typeof(Semidar), typeof(StoneGargoyle), typeof(Succubus), typeof(TsukiWolf)); - for ( int j = 0; foundOn != null && !inGroup && j < foundOn.Length; ++j ) - inGroup = ( foundOn[j] == type ); + abyss.Entries = new[] + { + // Daemon Dismissal & Balron Damnation have been removed and moved up to super slayer on OSI. + new SlayerEntry(SlayerName.GargoylesFoe, typeof(EnslavedGargoyle), typeof(FireGargoyle), + typeof(Gargoyle), typeof(GargoyleDestroyer), typeof(GargoyleEnforcer), typeof(StoneGargoyle)) + }; + } + else + { + abyss.Super = new SlayerEntry(SlayerName.Exorcism, typeof(AbysmalHorror), typeof(Balron), typeof(BoneDemon), + typeof(ChaosDaemon), typeof(Daemon), typeof(SummonedDaemon), typeof(DemonKnight), typeof(Devourer), + typeof(Gargoyle), typeof(FireGargoyle), typeof(Gibberling), typeof(HordeMinion), typeof(IceFiend), + typeof(Imp), typeof(Impaler), typeof(Ravager), typeof(StoneGargoyle), typeof(ArcaneDaemon), + typeof(EnslavedGargoyle), typeof(GargoyleDestroyer), typeof(GargoyleEnforcer), typeof(Moloch)); - if ( inGroup ) - { - int index = Utility.Random( 1 + group.Entries.Length ); + abyss.Entries = new[] + { + new SlayerEntry(SlayerName.DaemonDismissal, typeof(AbysmalHorror), typeof(Balron), typeof(BoneDemon), + typeof(ChaosDaemon), typeof(Daemon), typeof(SummonedDaemon), typeof(DemonKnight), typeof(Devourer), + typeof(Gibberling), typeof(HordeMinion), typeof(IceFiend), typeof(Imp), typeof(Impaler), + typeof(Ravager), typeof(ArcaneDaemon), typeof(Moloch)), + new SlayerEntry(SlayerName.GargoylesFoe, typeof(FireGargoyle), typeof(Gargoyle), typeof(StoneGargoyle), + typeof(EnslavedGargoyle), typeof(GargoyleDestroyer), typeof(GargoyleEnforcer)), + new SlayerEntry(SlayerName.BalronDamnation, typeof(Balron)) + }; + } - if ( index == 0 ) - return group.Super.Name; + arachnid.Opposition = new[] { reptilian }; + arachnid.FoundOn = new[] + { + typeof(AncientWyrm), typeof(GreaterDragon), typeof(Dragon), typeof(OphidianMatriarch), typeof(ShadowWyrm) + }; + arachnid.Super = new SlayerEntry(SlayerName.ArachnidDoom, typeof(DreadSpider), typeof(FrostSpider), + typeof(GiantBlackWidow), typeof(GiantSpider), typeof(Mephitis), typeof(Scorpion), typeof(TerathanAvenger), + typeof(TerathanDrone), typeof(TerathanMatriarch), typeof(TerathanWarrior)); + arachnid.Entries = new[] + { + new SlayerEntry(SlayerName.ScorpionsBane, typeof(Scorpion)), + new SlayerEntry(SlayerName.SpidersDeath, typeof(DreadSpider), typeof(FrostSpider), typeof(GiantBlackWidow), + typeof(GiantSpider), typeof(Mephitis)), + new SlayerEntry(SlayerName.Terathan, typeof(TerathanAvenger), typeof(TerathanDrone), + typeof(TerathanMatriarch), typeof(TerathanWarrior)) + }; - return group.Entries[index - 1].Name; - } - } + reptilian.Opposition = new[] { arachnid }; + reptilian.FoundOn = new[] { typeof(TerathanAvenger), typeof(TerathanMatriarch) }; + reptilian.Super = new SlayerEntry(SlayerName.ReptilianDeath, typeof(AncientWyrm), typeof(DeepSeaSerpent), + typeof(GreaterDragon), typeof(Dragon), typeof(Drake), typeof(GiantIceWorm), typeof(IceSerpent), + typeof(GiantSerpent), typeof(Hiryu), typeof(IceSnake), typeof(JukaLord), typeof(JukaMage), + typeof(JukaWarrior), typeof(LavaSerpent), typeof(LavaSnake), typeof(LesserHiryu), typeof(Lizardman), + typeof(OphidianArchmage), typeof(OphidianKnight), typeof(OphidianMage), typeof(OphidianMatriarch), + typeof(OphidianWarrior), typeof(Reptalon), typeof(SeaSerpent), typeof(Serado), typeof(SerpentineDragon), + typeof(ShadowWyrm), typeof(SilverSerpent), typeof(SkeletalDragon), typeof(Snake), typeof(SwampDragon), + typeof(WhiteWyrm), typeof(Wyvern), typeof(Yamandon)); + reptilian.Entries = new[] + { + new SlayerEntry(SlayerName.DragonSlaying, typeof(AncientWyrm), typeof(GreaterDragon), typeof(Dragon), + typeof(Drake), typeof(Hiryu), typeof(LesserHiryu), typeof(Reptalon), typeof(SerpentineDragon), + typeof(ShadowWyrm), typeof(SkeletalDragon), typeof(SwampDragon), typeof(WhiteWyrm), typeof(Wyvern)), + new SlayerEntry(SlayerName.LizardmanSlaughter, typeof(Lizardman)), + new SlayerEntry(SlayerName.Ophidian, typeof(OphidianArchmage), typeof(OphidianKnight), typeof(OphidianMage), + typeof(OphidianMatriarch), typeof(OphidianWarrior)), + new SlayerEntry(SlayerName.SnakesBane, typeof(DeepSeaSerpent), typeof(GiantIceWorm), typeof(GiantSerpent), + typeof(IceSerpent), typeof(IceSnake), typeof(LavaSerpent), typeof(LavaSnake), typeof(SeaSerpent), + typeof(Serado), typeof(SilverSerpent), typeof(Snake), typeof(Yamandon)) + }; - return SlayerName.Silver; - } + Groups = new[] + { + humanoid, + undead, + elemental, + abyss, + arachnid, + reptilian, + fey + }; - static SlayerGroup() - { - SlayerGroup humanoid = new SlayerGroup(); - SlayerGroup undead = new SlayerGroup(); - SlayerGroup elemental = new SlayerGroup(); - SlayerGroup abyss = new SlayerGroup(); - SlayerGroup arachnid = new SlayerGroup(); - SlayerGroup reptilian = new SlayerGroup(); - SlayerGroup fey = new SlayerGroup(); + TotalEntries = CompileEntries(Groups); + } - humanoid.Opposition = new[]{ undead }; - humanoid.FoundOn = new[]{ typeof( BoneKnight ), typeof( Lich ), typeof( LichLord ) }; - humanoid.Super = new SlayerEntry( SlayerName.Repond, typeof( ArcticOgreLord ), typeof( Cyclops ), typeof( Ettin ), typeof( EvilMage ), typeof( EvilMageLord ), typeof( FrostTroll ), typeof( MeerCaptain ), typeof( MeerEternal ), typeof( MeerMage ), typeof( MeerWarrior ), typeof( Ogre ), typeof( OgreLord ), typeof( Orc ), typeof( OrcBomber ), typeof( OrcBrute ), typeof( OrcCaptain ), /*typeof( OrcChopper ), typeof( OrcScout ),*/ typeof( OrcishLord ), typeof( OrcishMage ), typeof( Ratman ), typeof( RatmanArcher ), typeof( RatmanMage ), typeof( SavageRider ), typeof( SavageShaman ), typeof( Savage ), typeof( Titan ), typeof( Troglodyte ), typeof( Troll ) ); - humanoid.Entries = new[] - { - new SlayerEntry( SlayerName.OgreTrashing, typeof( Ogre ), typeof( OgreLord ), typeof( ArcticOgreLord ) ), - new SlayerEntry( SlayerName.OrcSlaying, typeof( Orc ), typeof( OrcBomber ), typeof( OrcBrute ), typeof( OrcCaptain ),/* typeof( OrcChopper ), typeof( OrcScout ),*/ typeof( OrcishLord ), typeof( OrcishMage ) ), - new SlayerEntry( SlayerName.TrollSlaughter, typeof( Troll ), typeof( FrostTroll ) ) - }; + public static SlayerEntry[] TotalEntries{ get; } - undead.Opposition = new[]{ humanoid }; - undead.Super = new SlayerEntry( SlayerName.Silver, typeof( AncientLich ), typeof( Bogle ), typeof( BoneKnight ), typeof( BoneMagi ),/* typeof( DarkGuardian ), */typeof( DarknightCreeper ), typeof( FleshGolem ), typeof( Ghoul ), typeof( GoreFiend ), typeof( HellSteed ), typeof( LadyOfTheSnow ), typeof( Lich ), typeof( LichLord ), typeof( Mummy ), typeof( PestilentBandage ), typeof( Revenant ), typeof( RevenantLion ), typeof( RottingCorpse ), typeof( Shade ), typeof( ShadowKnight ), typeof( SkeletalKnight ), typeof( SkeletalMage ), typeof( SkeletalMount ), typeof( Skeleton ), typeof( Spectre ), typeof( Wraith ), typeof( Zombie ) ); - undead.Entries = new SlayerEntry[0]; + public static SlayerGroup[] Groups{ get; } - fey.Opposition = new[]{ abyss }; - fey.Super = new SlayerEntry( SlayerName.Fey, typeof( Centaur ), typeof( CuSidhe ), typeof( EtherealWarrior ), typeof( Kirin ), typeof( LordOaks ), typeof( Pixie ), typeof( Silvani ), typeof( Treefellow ), typeof( Unicorn ), typeof( Wisp ), typeof( MLDryad ), typeof( Satyr ) ); - fey.Entries = new SlayerEntry[0]; + public SlayerGroup[] Opposition{ get; set; } - elemental.Opposition = new[]{ abyss }; - elemental.FoundOn = new[]{ typeof( Balron ), typeof( Daemon ) }; - elemental.Super = new SlayerEntry( SlayerName.ElementalBan, typeof( AcidElemental ), typeof( AgapiteElemental ), typeof( AirElemental ), typeof( SummonedAirElemental ), typeof( BloodElemental ), typeof( BronzeElemental ), typeof( CopperElemental ), typeof( CrystalElemental ), typeof( DullCopperElemental ), typeof( EarthElemental ), typeof( SummonedEarthElemental ), typeof( Efreet ), typeof( FireElemental ), typeof( SummonedFireElemental ), typeof( GoldenElemental ), typeof( IceElemental ), typeof( KazeKemono ), typeof( PoisonElemental ), typeof( RaiJu ), typeof( SandVortex ), typeof( ShadowIronElemental ), typeof( SnowElemental ), typeof( ValoriteElemental ), typeof( VeriteElemental ), typeof( WaterElemental ), typeof( SummonedWaterElemental ) ); - elemental.Entries = new[] - { - new SlayerEntry( SlayerName.BloodDrinking, typeof( BloodElemental ) ), - new SlayerEntry( SlayerName.EarthShatter, typeof( AgapiteElemental ), typeof( BronzeElemental ), typeof( CopperElemental ), typeof( DullCopperElemental ), typeof( EarthElemental ), typeof( SummonedEarthElemental ), typeof( GoldenElemental ), typeof( ShadowIronElemental ), typeof( ValoriteElemental ), typeof( VeriteElemental ) ), - new SlayerEntry( SlayerName.ElementalHealth, typeof( PoisonElemental ) ), - new SlayerEntry( SlayerName.FlameDousing, typeof( FireElemental ), typeof( SummonedFireElemental ) ), - new SlayerEntry( SlayerName.SummerWind, typeof( SnowElemental ), typeof( IceElemental ) ), - new SlayerEntry( SlayerName.Vacuum, typeof( AirElemental ), typeof( SummonedAirElemental ) ), - new SlayerEntry( SlayerName.WaterDissipation, typeof( WaterElemental ), typeof( SummonedWaterElemental ) ) - }; + public SlayerEntry Super{ get; set; } - abyss.Opposition = new[]{ elemental, fey }; - abyss.FoundOn = new[]{ typeof( BloodElemental ) }; + public SlayerEntry[] Entries{ get; set; } - if ( Core.AOS ) - { - abyss.Super = new SlayerEntry( SlayerName.Exorcism, typeof( AbysmalHorror ), typeof( ArcaneDaemon ), typeof( Balron ), typeof( BoneDemon ), typeof( ChaosDaemon ), typeof( Daemon ), typeof( SummonedDaemon ), typeof( DemonKnight ), typeof( Devourer ), typeof( EnslavedGargoyle ), typeof( FanDancer ), typeof( FireGargoyle ), typeof( Gargoyle ), typeof( GargoyleDestroyer ), typeof( GargoyleEnforcer ), typeof( Gibberling ), typeof( HordeMinion ), typeof( IceFiend ), typeof( Imp ), typeof( Impaler ), typeof( Moloch ), typeof( Oni ), typeof( Ravager ), typeof( Semidar ), typeof( StoneGargoyle ), typeof( Succubus ), typeof( TsukiWolf ) ); + public Type[] FoundOn{ get; set; } - abyss.Entries = new[] - { - // Daemon Dismissal & Balron Damnation have been removed and moved up to super slayer on OSI. - new SlayerEntry( SlayerName.GargoylesFoe, typeof( EnslavedGargoyle ), typeof( FireGargoyle ), typeof( Gargoyle ), typeof( GargoyleDestroyer ), typeof( GargoyleEnforcer ), typeof( StoneGargoyle ) ), - }; - } - else - { - abyss.Super = new SlayerEntry( SlayerName.Exorcism, typeof( AbysmalHorror ), typeof( Balron ), typeof( BoneDemon ), typeof( ChaosDaemon ), typeof( Daemon ), typeof( SummonedDaemon ), typeof( DemonKnight ), typeof( Devourer ), typeof( Gargoyle ), typeof( FireGargoyle ), typeof( Gibberling ), typeof( HordeMinion ), typeof( IceFiend ), typeof( Imp ), typeof( Impaler ), typeof( Ravager ), typeof( StoneGargoyle ), typeof( ArcaneDaemon ), typeof( EnslavedGargoyle ), typeof( GargoyleDestroyer ), typeof( GargoyleEnforcer ), typeof( Moloch ) ); + public static SlayerEntry GetEntryByName(SlayerName name) + { + int v = (int)name; - abyss.Entries = new[] - { - new SlayerEntry( SlayerName.DaemonDismissal, typeof( AbysmalHorror ), typeof( Balron ), typeof( BoneDemon ), typeof( ChaosDaemon ), typeof( Daemon ), typeof( SummonedDaemon ), typeof( DemonKnight ), typeof( Devourer ), typeof( Gibberling ), typeof( HordeMinion ), typeof( IceFiend ), typeof( Imp ), typeof( Impaler ), typeof( Ravager ), typeof( ArcaneDaemon ), typeof( Moloch ) ), - new SlayerEntry( SlayerName.GargoylesFoe, typeof( FireGargoyle ), typeof( Gargoyle ), typeof( StoneGargoyle ), typeof( EnslavedGargoyle ), typeof( GargoyleDestroyer ), typeof( GargoyleEnforcer ) ), - new SlayerEntry( SlayerName.BalronDamnation, typeof( Balron ) ) - }; - } + if (v >= 0 && v < TotalEntries.Length) + return TotalEntries[v]; - arachnid.Opposition = new[]{ reptilian }; - arachnid.FoundOn = new[]{ typeof( AncientWyrm ), typeof( GreaterDragon ), typeof( Dragon ), typeof( OphidianMatriarch ), typeof( ShadowWyrm ) }; - arachnid.Super = new SlayerEntry( SlayerName.ArachnidDoom, typeof( DreadSpider ), typeof( FrostSpider ), typeof( GiantBlackWidow ), typeof( GiantSpider ), typeof( Mephitis ), typeof( Scorpion ), typeof( TerathanAvenger ), typeof( TerathanDrone ), typeof( TerathanMatriarch ), typeof( TerathanWarrior ) ); - arachnid.Entries = new[] - { - new SlayerEntry( SlayerName.ScorpionsBane, typeof( Scorpion ) ), - new SlayerEntry( SlayerName.SpidersDeath, typeof( DreadSpider ), typeof( FrostSpider ), typeof( GiantBlackWidow ), typeof( GiantSpider ), typeof( Mephitis ) ), - new SlayerEntry( SlayerName.Terathan, typeof( TerathanAvenger ), typeof( TerathanDrone ), typeof( TerathanMatriarch ), typeof( TerathanWarrior ) ) - }; + return null; + } - reptilian.Opposition = new[]{ arachnid }; - reptilian.FoundOn = new[]{ typeof( TerathanAvenger ), typeof( TerathanMatriarch ) }; - reptilian.Super = new SlayerEntry( SlayerName.ReptilianDeath, typeof( AncientWyrm ), typeof( DeepSeaSerpent ), typeof( GreaterDragon ), typeof( Dragon ), typeof( Drake ), typeof( GiantIceWorm ), typeof( IceSerpent ), typeof( GiantSerpent ), typeof( Hiryu ), typeof( IceSnake ), typeof( JukaLord ), typeof( JukaMage ), typeof( JukaWarrior ), typeof( LavaSerpent ), typeof( LavaSnake ), typeof( LesserHiryu ), typeof( Lizardman ), typeof( OphidianArchmage ), typeof( OphidianKnight ), typeof( OphidianMage ), typeof( OphidianMatriarch ), typeof( OphidianWarrior ), typeof( Reptalon ), typeof( SeaSerpent ), typeof( Serado ), typeof( SerpentineDragon ), typeof( ShadowWyrm ), typeof( SilverSerpent ), typeof( SkeletalDragon ), typeof( Snake ), typeof( SwampDragon ), typeof( WhiteWyrm ), typeof( Wyvern ), typeof( Yamandon ) ); - reptilian.Entries = new[] - { - new SlayerEntry( SlayerName.DragonSlaying, typeof( AncientWyrm ), typeof( GreaterDragon ), typeof( Dragon ), typeof( Drake ), typeof( Hiryu ), typeof( LesserHiryu ), typeof( Reptalon ), typeof( SerpentineDragon ), typeof( ShadowWyrm ), typeof( SkeletalDragon ), typeof( SwampDragon ), typeof( WhiteWyrm ), typeof( Wyvern ) ), - new SlayerEntry( SlayerName.LizardmanSlaughter, typeof( Lizardman ) ), - new SlayerEntry( SlayerName.Ophidian, typeof( OphidianArchmage ), typeof( OphidianKnight ), typeof( OphidianMage ), typeof( OphidianMatriarch ), typeof( OphidianWarrior ) ), - new SlayerEntry( SlayerName.SnakesBane, typeof( DeepSeaSerpent ), typeof( GiantIceWorm ), typeof( GiantSerpent ), typeof( IceSerpent ), typeof( IceSnake ), typeof( LavaSerpent ), typeof( LavaSnake ), typeof( SeaSerpent ), typeof( Serado ), typeof( SilverSerpent ), typeof( Snake ), typeof( Yamandon ) ) - }; + public static SlayerName GetLootSlayerType(Type type) + { + for (int i = 0; i < Groups.Length; ++i) + { + SlayerGroup group = Groups[i]; + Type[] foundOn = group.FoundOn; - Groups = new[] - { - humanoid, - undead, - elemental, - abyss, - arachnid, - reptilian, - fey - }; + bool inGroup = false; - TotalEntries = CompileEntries( Groups ); - } + for (int j = 0; foundOn != null && !inGroup && j < foundOn.Length; ++j) + inGroup = foundOn[j] == type; - private static SlayerEntry[] CompileEntries( SlayerGroup[] groups ) - { - SlayerEntry[] entries = new SlayerEntry[28]; + if (inGroup) + { + int index = Utility.Random(1 + group.Entries.Length); - for ( int i = 0; i < groups.Length; ++i ) - { - SlayerGroup g = groups[i]; + if (index == 0) + return group.Super.Name; - g.Super.Group = g; + return group.Entries[index - 1].Name; + } + } - entries[(int)g.Super.Name] = g.Super; + return SlayerName.Silver; + } - for ( int j = 0; j < g.Entries.Length; ++j ) - { - g.Entries[j].Group = g; - entries[(int)g.Entries[j].Name] = g.Entries[j]; - } - } + private static SlayerEntry[] CompileEntries(SlayerGroup[] groups) + { + SlayerEntry[] entries = new SlayerEntry[28]; - return entries; - } + for (int i = 0; i < groups.Length; ++i) + { + SlayerGroup g = groups[i]; - public SlayerGroup[] Opposition { get; set; } + g.Super.Group = g; - public SlayerEntry Super { get; set; } + entries[(int)g.Super.Name] = g.Super; - public SlayerEntry[] Entries { get; set; } + for (int j = 0; j < g.Entries.Length; ++j) + { + g.Entries[j].Group = g; + entries[(int)g.Entries[j].Name] = g.Entries[j]; + } + } - public Type[] FoundOn { get; set; } + return entries; + } - public bool OppositionSuperSlays( Mobile m ) - { - for( int i = 0; i < Opposition.Length; i++ ) - { - if ( Opposition[i].Super.Slays( m ) ) - return true; - } + public bool OppositionSuperSlays(Mobile m) + { + for (int i = 0; i < Opposition.Length; i++) + if (Opposition[i].Super.Slays(m)) + return true; - return false; - } - - public SlayerGroup() - { - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SlayerName.cs b/Scripts/Items/Weapons/SlayerName.cs index f2456d4ba..c1a56bf25 100644 --- a/Scripts/Items/Weapons/SlayerName.cs +++ b/Scripts/Items/Weapons/SlayerName.cs @@ -1,34 +1,34 @@ namespace Server.Items { - public enum SlayerName - { - None, - Silver, - OrcSlaying, - TrollSlaughter, - OgreTrashing, - Repond, - DragonSlaying, - Terathan, - SnakesBane, - LizardmanSlaughter, - ReptilianDeath, - DaemonDismissal, - GargoylesFoe, - BalronDamnation, - Exorcism, - Ophidian, - SpidersDeath, - ScorpionsBane, - ArachnidDoom, - FlameDousing, - WaterDissipation, - Vacuum, - ElementalHealth, - EarthShatter, - BloodDrinking, - SummerWind, - ElementalBan, // Bane? - Fey - } + public enum SlayerName + { + None, + Silver, + OrcSlaying, + TrollSlaughter, + OgreTrashing, + Repond, + DragonSlaying, + Terathan, + SnakesBane, + LizardmanSlaughter, + ReptilianDeath, + DaemonDismissal, + GargoylesFoe, + BalronDamnation, + Exorcism, + Ophidian, + SpidersDeath, + ScorpionsBane, + ArachnidDoom, + FlameDousing, + WaterDissipation, + Vacuum, + ElementalHealth, + EarthShatter, + BloodDrinking, + SummerWind, + ElementalBan, // Bane? + Fey + } } \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/BaseSpear.cs b/Scripts/Items/Weapons/SpearsAndForks/BaseSpear.cs index 04936bd1a..3bc11185e 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/BaseSpear.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/BaseSpear.cs @@ -1,58 +1,61 @@ using System; +using Server.Engines.ConPVP; namespace Server.Items { - public abstract class BaseSpear : BaseMeleeWeapon - { - public override int DefHitSound => 0x23C; - public override int DefMissSound => 0x238; + public abstract class BaseSpear : BaseMeleeWeapon + { + public BaseSpear(int itemID) : base(itemID) + { + } - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce2H; + public BaseSpear(Serial serial) : base(serial) + { + } - public BaseSpear( int itemID ) : base( itemID ) - { - } + public override int DefHitSound => 0x23C; + public override int DefMissSound => 0x238; - public BaseSpear( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce2H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - if ( !Core.AOS && Layer == Layer.TwoHanded && (attacker.Skills[SkillName.Anatomy].Value / 400.0) >= Utility.RandomDouble() && Engines.ConPVP.DuelContext.AllowSpecialAbility( attacker, "Paralyzing Blow", false ) ) - { - defender.SendMessage( "You receive a paralyzing blow!" ); // Is this not localized? - defender.Freeze( TimeSpan.FromSeconds( 2.0 ) ); + if (!Core.AOS && Layer == Layer.TwoHanded && + attacker.Skills[SkillName.Anatomy].Value / 400.0 >= Utility.RandomDouble() && + DuelContext.AllowSpecialAbility(attacker, "Paralyzing Blow", false)) + { + defender.SendMessage("You receive a paralyzing blow!"); // Is this not localized? + defender.Freeze(TimeSpan.FromSeconds(2.0)); - attacker.SendMessage( "You deliver a paralyzing blow!" ); // Is this not localized? - attacker.PlaySound( 0x11C ); - } + attacker.SendMessage("You deliver a paralyzing blow!"); // Is this not localized? + attacker.PlaySound(0x11C); + } - if ( !Core.AOS && Poison != null && PoisonCharges > 0 ) - { - --PoisonCharges; + if (!Core.AOS && Poison != null && PoisonCharges > 0) + { + --PoisonCharges; - if ( Utility.RandomDouble() >= 0.5 ) // 50% chance to poison - defender.ApplyPoison( attacker, Poison ); - } - } - } -} + if (Utility.RandomDouble() >= 0.5) // 50% chance to poison + defender.ApplyPoison(attacker, Poison); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/BladedStaff.cs b/Scripts/Items/Weapons/SpearsAndForks/BladedStaff.cs index 1cccf2079..9a3193224 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/BladedStaff.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/BladedStaff.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x26BD, 0x26C7 )] - public class BladedStaff : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; + [Flippable(0x26BD, 0x26C7)] + public class BladedStaff : BaseSpear + { + [Constructible] + public BladedStaff() : base(0x26BD) + { + Weight = 4.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 16; - public override int AosSpeed => 37; - public override float MlSpeed => 3.00f; + public BladedStaff(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 14; - public override int OldMaxDamage => 16; - public override int OldSpeed => 37; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; - public override int InitMinHits => 21; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 16; + public override int AosSpeed => 37; + public override float MlSpeed => 3.00f; - public override SkillName DefSkill => SkillName.Swords; + public override int OldStrengthReq => 40; + public override int OldMinDamage => 14; + public override int OldMaxDamage => 16; + public override int OldSpeed => 37; - [Constructible] - public BladedStaff() : base( 0x26BD ) - { - Weight = 4.0; - } + public override int InitMinHits => 21; + public override int InitMaxHits => 110; - public BladedStaff( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Swords; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/DoubleBladedStaff.cs b/Scripts/Items/Weapons/SpearsAndForks/DoubleBladedStaff.cs index 4f0481f22..b094bb0d4 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/DoubleBladedStaff.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/DoubleBladedStaff.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x26BF, 0x26C9 )] - public class DoubleBladedStaff : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; + [Flippable(0x26BF, 0x26C9)] + public class DoubleBladedStaff : BaseSpear + { + [Constructible] + public DoubleBladedStaff() : base(0x26BF) + { + Weight = 2.0; + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 13; - public override int AosSpeed => 49; - public override float MlSpeed => 2.25f; + public DoubleBladedStaff(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 50; - public override int OldMinDamage => 12; - public override int OldMaxDamage => 13; - public override int OldSpeed => 49; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int AosStrengthReq => 50; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 13; + public override int AosSpeed => 49; + public override float MlSpeed => 2.25f; - [Constructible] - public DoubleBladedStaff() : base( 0x26BF ) - { - Weight = 2.0; - } + public override int OldStrengthReq => 50; + public override int OldMinDamage => 12; + public override int OldMaxDamage => 13; + public override int OldSpeed => 49; - public DoubleBladedStaff( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/Pike.cs b/Scripts/Items/Weapons/SpearsAndForks/Pike.cs index fa6db0654..7a215b95d 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/Pike.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/Pike.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x26BE, 0x26C8 )] - public class Pike : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; + [Flippable(0x26BE, 0x26C8)] + public class Pike : BaseSpear + { + [Constructible] + public Pike() : base(0x26BE) + { + Weight = 8.0; + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 16; - public override int AosSpeed => 37; - public override float MlSpeed => 3.00f; + public Pike(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 50; - public override int OldMinDamage => 14; - public override int OldMaxDamage => 16; - public override int OldSpeed => 37; + public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int AosStrengthReq => 50; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 16; + public override int AosSpeed => 37; + public override float MlSpeed => 3.00f; - [Constructible] - public Pike() : base( 0x26BE ) - { - Weight = 8.0; - } + public override int OldStrengthReq => 50; + public override int OldMinDamage => 14; + public override int OldMaxDamage => 16; + public override int OldSpeed => 37; - public Pike( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/Pitchfork.cs b/Scripts/Items/Weapons/SpearsAndForks/Pitchfork.cs index 46feb6f6c..01f857eb9 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/Pitchfork.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/Pitchfork.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0xE87, 0xE88 )] - public class Pitchfork : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; + [Flippable(0xE87, 0xE88)] + public class Pitchfork : BaseSpear + { + [Constructible] + public Pitchfork() : base(0xE87) + { + Weight = 11.0; + } - public override int AosStrengthReq => 55; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 14; - public override int AosSpeed => 43; - public override float MlSpeed => 2.50f; + public Pitchfork(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 4; - public override int OldMaxDamage => 16; - public override int OldSpeed => 45; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.Dismount; - public override int InitMinHits => 31; - public override int InitMaxHits => 60; + public override int AosStrengthReq => 55; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 14; + public override int AosSpeed => 43; + public override float MlSpeed => 2.50f; - [Constructible] - public Pitchfork() : base( 0xE87 ) - { - Weight = 11.0; - } + public override int OldStrengthReq => 15; + public override int OldMinDamage => 4; + public override int OldMaxDamage => 16; + public override int OldSpeed => 45; - public Pitchfork( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 10.0 ) - Weight = 11.0; - } - } -} + if (Weight == 10.0) + Weight = 11.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/ShortSpear.cs b/Scripts/Items/Weapons/SpearsAndForks/ShortSpear.cs index 10ff0d732..4c18525c8 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/ShortSpear.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/ShortSpear.cs @@ -1,49 +1,49 @@ namespace Server.Items { - [FlippableAttribute( 0x1403, 0x1402 )] - public class ShortSpear : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ShadowStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0x1403, 0x1402)] + public class ShortSpear : BaseSpear + { + [Constructible] + public ShortSpear() : base(0x1403) + { + Weight = 4.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 13; - public override int AosSpeed => 55; - public override float MlSpeed => 2.00f; + public ShortSpear(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 15; - public override int OldMinDamage => 4; - public override int OldMaxDamage => 32; - public override int OldSpeed => 50; + public override WeaponAbility PrimaryAbility => WeaponAbility.ShadowStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 13; + public override int AosSpeed => 55; + public override float MlSpeed => 2.00f; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int OldStrengthReq => 15; + public override int OldMinDamage => 4; + public override int OldMaxDamage => 32; + public override int OldSpeed => 50; - [Constructible] - public ShortSpear() : base( 0x1403 ) - { - Weight = 4.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public ShortSpear( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/Spear.cs b/Scripts/Items/Weapons/SpearsAndForks/Spear.cs index 8f411432c..8dd62b6df 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/Spear.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/Spear.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xF62, 0xF63 )] - public class Spear : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0xF62, 0xF63)] + public class Spear : BaseSpear + { + [Constructible] + public Spear() : base(0xF62) + { + Weight = 7.0; + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 42; - public override float MlSpeed => 2.75f; + public Spear(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 30; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 36; - public override int OldSpeed => 46; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int AosStrengthReq => 50; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 42; + public override float MlSpeed => 2.75f; - [Constructible] - public Spear() : base( 0xF62 ) - { - Weight = 7.0; - } + public override int OldStrengthReq => 30; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 36; + public override int OldSpeed => 46; - public Spear( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/TribalSpear.cs b/Scripts/Items/Weapons/SpearsAndForks/TribalSpear.cs index 930af368b..f80211c6a 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/TribalSpear.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/TribalSpear.cs @@ -1,52 +1,52 @@ namespace Server.Items { - [FlippableAttribute( 0xF62, 0xF63 )] - public class TribalSpear : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0xF62, 0xF63)] + public class TribalSpear : BaseSpear + { + [Constructible] + public TribalSpear() : base(0xF62) + { + Weight = 7.0; + Hue = 837; + } - public override int AosStrengthReq => 50; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 42; - public override float MlSpeed => 2.75f; + public TribalSpear(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 30; - public override int OldMinDamage => 2; - public override int OldMaxDamage => 36; - public override int OldSpeed => 46; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 80; + public override int AosStrengthReq => 50; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 42; + public override float MlSpeed => 2.75f; - public override int VirtualDamageBonus => 25; + public override int OldStrengthReq => 30; + public override int OldMinDamage => 2; + public override int OldMaxDamage => 36; + public override int OldSpeed => 46; - public override string DefaultName => "a tribal spear"; + public override int InitMinHits => 31; + public override int InitMaxHits => 80; - [Constructible] - public TribalSpear() : base( 0xF62 ) - { - Weight = 7.0; - Hue = 837; - } + public override int VirtualDamageBonus => 25; - public TribalSpear( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a tribal spear"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/SpearsAndForks/WarFork.cs b/Scripts/Items/Weapons/SpearsAndForks/WarFork.cs index 8abc45080..4d7692f4c 100644 --- a/Scripts/Items/Weapons/SpearsAndForks/WarFork.cs +++ b/Scripts/Items/Weapons/SpearsAndForks/WarFork.cs @@ -1,52 +1,52 @@ namespace Server.Items { - [FlippableAttribute( 0x1405, 0x1404 )] - public class WarFork : BaseSpear - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Flippable(0x1405, 0x1404)] + public class WarFork : BaseSpear + { + [Constructible] + public WarFork() : base(0x1405) + { + Weight = 9.0; + } - public override int AosStrengthReq => 45; - public override int AosMinDamage => 12; - public override int AosMaxDamage => 13; - public override int AosSpeed => 43; - public override float MlSpeed => 2.50f; + public WarFork(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 4; - public override int OldMaxDamage => 32; - public override int OldSpeed => 45; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int DefHitSound => 0x236; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 45; + public override int AosMinDamage => 12; + public override int AosMaxDamage => 13; + public override int AosSpeed => 43; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int OldStrengthReq => 35; + public override int OldMinDamage => 4; + public override int OldMaxDamage => 32; + public override int OldSpeed => 45; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x236; + public override int DefMissSound => 0x238; - [Constructible] - public WarFork() : base( 0x1405 ) - { - Weight = 9.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public WarFork( Serial serial ) : base( serial ) - { - } + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Staves/BaseStaff.cs b/Scripts/Items/Weapons/Staves/BaseStaff.cs index e148ccb13..6c5a58d30 100644 --- a/Scripts/Items/Weapons/Staves/BaseStaff.cs +++ b/Scripts/Items/Weapons/Staves/BaseStaff.cs @@ -1,41 +1,41 @@ namespace Server.Items { - public abstract class BaseStaff : BaseMeleeWeapon - { - public override int DefHitSound => 0x233; - public override int DefMissSound => 0x239; + public abstract class BaseStaff : BaseMeleeWeapon + { + public BaseStaff(int itemID) : base(itemID) + { + } - public override SkillName DefSkill => SkillName.Macing; - public override WeaponType DefType => WeaponType.Staff; - public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; + public BaseStaff(Serial serial) : base(serial) + { + } - public BaseStaff( int itemID ) : base( itemID ) - { - } + public override int DefHitSound => 0x233; + public override int DefMissSound => 0x239; - public BaseStaff( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Macing; + public override WeaponType DefType => WeaponType.Staff; + public override WeaponAnimation DefAnimation => WeaponAnimation.Bash2H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - defender.Stam -= Utility.Random( 3, 3 ); // 3-5 points of stamina loss - } - } -} + defender.Stam -= Utility.Random(3, 3); // 3-5 points of stamina loss + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Staves/BlackStaff.cs b/Scripts/Items/Weapons/Staves/BlackStaff.cs index 988556c44..9714b9ca7 100644 --- a/Scripts/Items/Weapons/Staves/BlackStaff.cs +++ b/Scripts/Items/Weapons/Staves/BlackStaff.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xDF1, 0xDF0 )] - public class BlackStaff : BaseStaff - { - public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0xDF1, 0xDF0)] + public class BlackStaff : BaseStaff + { + [Constructible] + public BlackStaff() : base(0xDF0) + { + Weight = 6.0; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 16; - public override int AosSpeed => 39; - public override float MlSpeed => 2.75f; + public BlackStaff(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 35; - public override int OldMinDamage => 8; - public override int OldMaxDamage => 33; - public override int OldSpeed => 35; + public override WeaponAbility PrimaryAbility => WeaponAbility.WhirlwindAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 16; + public override int AosSpeed => 39; + public override float MlSpeed => 2.75f; - [Constructible] - public BlackStaff() : base( 0xDF0 ) - { - Weight = 6.0; - } + public override int OldStrengthReq => 35; + public override int OldMinDamage => 8; + public override int OldMaxDamage => 33; + public override int OldSpeed => 35; - public BlackStaff( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Staves/GlacialStaff.cs b/Scripts/Items/Weapons/Staves/GlacialStaff.cs index e731dba3e..92b293440 100644 --- a/Scripts/Items/Weapons/Staves/GlacialStaff.cs +++ b/Scripts/Items/Weapons/Staves/GlacialStaff.cs @@ -1,37 +1,36 @@ namespace Server.Items { - public class GlacialStaff : BlackStaff - { - //TODO: Pre-AoS stuff - public override int LabelNumber => 1017413; // Glacial Staff + public class GlacialStaff : BlackStaff + { + [Constructible] + public GlacialStaff() + { + Hue = 0x480; + WeaponAttributes.HitHarm = 5 * Utility.RandomMinMax(1, 5); + WeaponAttributes.MageWeapon = Utility.RandomMinMax(5, 10); - [Constructible] - public GlacialStaff() - { - Hue = 0x480; - WeaponAttributes.HitHarm = 5 * Utility.RandomMinMax( 1, 5 ); - WeaponAttributes.MageWeapon = Utility.RandomMinMax( 5, 10 ); + AosElementDamages[AosElementAttribute.Cold] = 20 + 5 * Utility.RandomMinMax(0, 6); + } - AosElementDamages[AosElementAttribute.Cold] = 20 + (5 * Utility.RandomMinMax( 0, 6 )); + public GlacialStaff(Serial serial) : base(serial) + { + } - } + //TODO: Pre-AoS stuff + public override int LabelNumber => 1017413; // Glacial Staff - public GlacialStaff( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Staves/GnarledStaff.cs b/Scripts/Items/Weapons/Staves/GnarledStaff.cs index 72f1faa5b..03cb5cbb9 100644 --- a/Scripts/Items/Weapons/Staves/GnarledStaff.cs +++ b/Scripts/Items/Weapons/Staves/GnarledStaff.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x13F8, 0x13F9 )] - public class GnarledStaff : BaseStaff - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0x13F8, 0x13F9)] + public class GnarledStaff : BaseStaff + { + [Constructible] + public GnarledStaff() : base(0x13F8) + { + Weight = 3.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 33; - public override float MlSpeed => 3.25f; + public GnarledStaff(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 20; - public override int OldMinDamage => 10; - public override int OldMaxDamage => 30; - public override int OldSpeed => 33; + public override WeaponAbility PrimaryAbility => WeaponAbility.ConcussionBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 50; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 33; + public override float MlSpeed => 3.25f; - [Constructible] - public GnarledStaff() : base( 0x13F8 ) - { - Weight = 3.0; - } + public override int OldStrengthReq => 20; + public override int OldMinDamage => 10; + public override int OldMaxDamage => 30; + public override int OldSpeed => 33; - public GnarledStaff( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 50; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Staves/QuarterStaff.cs b/Scripts/Items/Weapons/Staves/QuarterStaff.cs index c8532db08..0d1500e28 100644 --- a/Scripts/Items/Weapons/Staves/QuarterStaff.cs +++ b/Scripts/Items/Weapons/Staves/QuarterStaff.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0xE89, 0xE8a )] - public class QuarterStaff : BaseStaff - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; + [Flippable(0xE89, 0xE8a)] + public class QuarterStaff : BaseStaff + { + [Constructible] + public QuarterStaff() : base(0xE89) + { + Weight = 4.0; + } - public override int AosStrengthReq => 30; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 14; - public override int AosSpeed => 48; - public override float MlSpeed => 2.25f; + public QuarterStaff(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 30; - public override int OldMinDamage => 8; - public override int OldMaxDamage => 28; - public override int OldSpeed => 48; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; - public override int InitMinHits => 31; - public override int InitMaxHits => 60; + public override int AosStrengthReq => 30; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 14; + public override int AosSpeed => 48; + public override float MlSpeed => 2.25f; - [Constructible] - public QuarterStaff() : base( 0xE89 ) - { - Weight = 4.0; - } + public override int OldStrengthReq => 30; + public override int OldMinDamage => 8; + public override int OldMaxDamage => 28; + public override int OldSpeed => 48; - public QuarterStaff( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 60; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Staves/ShepherdsCrook.cs b/Scripts/Items/Weapons/Staves/ShepherdsCrook.cs index 892cc470d..aebf9be52 100644 --- a/Scripts/Items/Weapons/Staves/ShepherdsCrook.cs +++ b/Scripts/Items/Weapons/Staves/ShepherdsCrook.cs @@ -1,166 +1,169 @@ using System; +using Server.Engines.CannedEvil; +using Server.Mobiles; using Server.Network; using Server.Targeting; -using Server.Mobiles; -using Server.Engines.CannedEvil; namespace Server.Items { - [FlippableAttribute( 0xE81, 0xE82 )] - public class ShepherdsCrook : BaseStaff - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; + [Flippable(0xE81, 0xE82)] + public class ShepherdsCrook : BaseStaff + { + [Constructible] + public ShepherdsCrook() : base(0xE81) + { + Weight = 4.0; + } - public override int AosStrengthReq => 20; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 40; - public override float MlSpeed => 2.75f; + public ShepherdsCrook(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 3; - public override int OldMaxDamage => 12; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.Disarm; - public override int InitMinHits => 31; - public override int InitMaxHits => 50; + public override int AosStrengthReq => 20; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 40; + public override float MlSpeed => 2.75f; - [Constructible] - public ShepherdsCrook() : base( 0xE81 ) - { - Weight = 4.0; - } + public override int OldStrengthReq => 10; + public override int OldMinDamage => 3; + public override int OldMaxDamage => 12; + public override int OldSpeed => 30; - public ShepherdsCrook( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 50; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 2.0 ) - Weight = 4.0; - } + if (Weight == 2.0) + Weight = 4.0; + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 502464 ); // Target the animal you wish to herd. - from.Target = new HerdingTarget(); - } + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(502464); // Target the animal you wish to herd. + from.Target = new HerdingTarget(); + } - private class HerdingTarget : Target - { - public HerdingTarget() : base( 10, false, TargetFlags.None ) - { - } + private class HerdingTarget : Target + { + private static Type[] m_ChampTamables = + { + typeof(StrongMongbat), typeof(Imp), typeof(Scorpion), typeof(GiantSpider), + typeof(Snake), typeof(LavaLizard), typeof(Drake), typeof(Dragon), + typeof(Kirin), typeof(Unicorn), typeof(GiantRat), typeof(Slime), + typeof(DireWolf), typeof(HellHound), typeof(DeathwatchBeetle), + typeof(LesserHiryu), typeof(Hiryu) + }; - protected override void OnTarget( Mobile from, object targ ) - { - if ( targ is BaseCreature bc ) - { - if ( IsHerdable( bc ) ) - { - if ( bc.Controlled ) - { - bc.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502467, from.NetState ); // That animal looks tame already. - } - else - { - from.SendLocalizedMessage( 502475 ); // Click where you wish the animal to go. - from.Target = new InternalTarget( bc ); - } - } - else - { - from.SendLocalizedMessage( 502468 ); // That is not a herdable animal. - } - } - else - { - from.SendLocalizedMessage( 502472 ); // You don't seem to be able to persuade that to move. - } - } + public HerdingTarget() : base(10, false, TargetFlags.None) + { + } - private static Type[] m_ChampTamables = { - typeof( StrongMongbat ), typeof( Imp ), typeof( Scorpion ), typeof( GiantSpider ), - typeof( Snake ), typeof( LavaLizard ), typeof( Drake ), typeof( Dragon ), - typeof( Kirin ), typeof( Unicorn ), typeof( GiantRat ), typeof( Slime ), - typeof( DireWolf ), typeof( HellHound ), typeof( DeathwatchBeetle ), - typeof( LesserHiryu ), typeof( Hiryu ) - }; + protected override void OnTarget(Mobile from, object targ) + { + if (targ is BaseCreature bc) + { + if (IsHerdable(bc)) + { + if (bc.Controlled) + { + bc.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502467, + from.NetState); // That animal looks tame already. + } + else + { + from.SendLocalizedMessage(502475); // Click where you wish the animal to go. + from.Target = new InternalTarget(bc); + } + } + else + { + from.SendLocalizedMessage(502468); // That is not a herdable animal. + } + } + else + { + from.SendLocalizedMessage(502472); // You don't seem to be able to persuade that to move. + } + } - private bool IsHerdable( BaseCreature bc ) - { - if ( bc.IsParagon ) - return false; + private bool IsHerdable(BaseCreature bc) + { + if (bc.IsParagon) + return false; - if ( bc.Tamable ) - return true; + if (bc.Tamable) + return true; - Map map = bc.Map; + Map map = bc.Map; - if ( Region.Find( bc.Home, map ) is ChampionSpawnRegion region ) - { - ChampionSpawn spawn = region.ChampionSpawn; + if (Region.Find(bc.Home, map) is ChampionSpawnRegion region) + { + ChampionSpawn spawn = region.ChampionSpawn; - if ( spawn != null && spawn.IsChampionSpawn( bc ) ) - { - Type t = bc.GetType(); + if (spawn != null && spawn.IsChampionSpawn(bc)) + { + Type t = bc.GetType(); - foreach ( Type type in m_ChampTamables ) - if ( type == t ) - return true; - } - } + foreach (Type type in m_ChampTamables) + if (type == t) + return true; + } + } - return false; - } + return false; + } - private class InternalTarget : Target - { - private BaseCreature m_Creature; + private class InternalTarget : Target + { + private BaseCreature m_Creature; - public InternalTarget( BaseCreature c ) : base( 10, true, TargetFlags.None ) - { - m_Creature = c; - } + public InternalTarget(BaseCreature c) : base(10, true, TargetFlags.None) + { + m_Creature = c; + } - protected override void OnTarget( Mobile from, object targ ) - { - if ( targ is IPoint2D p ) - { - double min = m_Creature.MinTameSkill - 30; - double max = m_Creature.MinTameSkill + 30 + Utility.Random( 10 ); + protected override void OnTarget(Mobile from, object targ) + { + if (targ is IPoint2D p) + { + double min = m_Creature.MinTameSkill - 30; + double max = m_Creature.MinTameSkill + 30 + Utility.Random(10); - if ( max <= from.Skills[ SkillName.Herding ].Value ) - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502471, from.NetState ); // That wasn't even challenging. + if (max <= from.Skills[SkillName.Herding].Value) + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502471, + from.NetState); // That wasn't even challenging. - if ( from.CheckTargetSkill( SkillName.Herding, m_Creature, min, max ) ) - { - if ( p != from ) - p = new Point2D( p.X, p.Y ); + if (from.CheckTargetSkill(SkillName.Herding, m_Creature, min, max)) + { + if (p != from) + p = new Point2D(p.X, p.Y); - m_Creature.TargetLocation = p; - from.SendLocalizedMessage( 502479 ); // The animal walks where it was instructed to. - } - else - { - from.SendLocalizedMessage( 502472 ); // You don't seem to be able to persuade that to move. - } - } - } - } - } - } -} + m_Creature.TargetLocation = p; + from.SendLocalizedMessage(502479); // The animal walks where it was instructed to. + } + else + { + from.SendLocalizedMessage(502472); // You don't seem to be able to persuade that to move. + } + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/AdventurersMachete.cs b/Scripts/Items/Weapons/Swords/AdventurersMachete.cs index a7b0eb343..78417929c 100644 --- a/Scripts/Items/Weapons/Swords/AdventurersMachete.cs +++ b/Scripts/Items/Weapons/Swords/AdventurersMachete.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AdventurersMachete : ElvenMachete - { - public override int LabelNumber => 1073533; // adventurer's machete + public class AdventurersMachete : ElvenMachete + { + [Constructible] + public AdventurersMachete() + { + Attributes.Luck = 20; + } - [Constructible] - public AdventurersMachete() - { - Attributes.Luck = 20; - } + public AdventurersMachete(Serial serial) : base(serial) + { + } - public AdventurersMachete( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073533; // adventurer's machete - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/BaseSword.cs b/Scripts/Items/Weapons/Swords/BaseSword.cs index 2ee18c841..d4c19f37e 100644 --- a/Scripts/Items/Weapons/Swords/BaseSword.cs +++ b/Scripts/Items/Weapons/Swords/BaseSword.cs @@ -2,52 +2,52 @@ using Server.Targets; namespace Server.Items { - public abstract class BaseSword : BaseMeleeWeapon - { - public override SkillName DefSkill => SkillName.Swords; - public override WeaponType DefType => WeaponType.Slashing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; + public abstract class BaseSword : BaseMeleeWeapon + { + public BaseSword(int itemID) : base(itemID) + { + } - public BaseSword( int itemID ) : base( itemID ) - { - } + public BaseSword(Serial serial) : base(serial) + { + } - public BaseSword( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Swords; + public override WeaponType DefType => WeaponType.Slashing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Slash1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnDoubleClick( Mobile from ) - { - from.SendLocalizedMessage( 1010018 ); // What do you want to use this item on? + public override void OnDoubleClick(Mobile from) + { + from.SendLocalizedMessage(1010018); // What do you want to use this item on? - from.Target = new BladedItemTarget( this ); - } + from.Target = new BladedItemTarget(this); + } - public override void OnHit( Mobile attacker, Mobile defender, double damageBonus = 1 ) - { - base.OnHit( attacker, defender, damageBonus ); + public override void OnHit(Mobile attacker, Mobile defender, double damageBonus = 1) + { + base.OnHit(attacker, defender, damageBonus); - if ( !Core.AOS && Poison != null && PoisonCharges > 0 ) - { - --PoisonCharges; + if (!Core.AOS && Poison != null && PoisonCharges > 0) + { + --PoisonCharges; - if ( Utility.RandomDouble() >= 0.5 ) // 50% chance to poison - defender.ApplyPoison( attacker, Poison ); - } - } - } -} + if (Utility.RandomDouble() >= 0.5) // 50% chance to poison + defender.ApplyPoison(attacker, Poison); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/BoneHarvester.cs b/Scripts/Items/Weapons/Swords/BoneHarvester.cs index 9b7a54482..5a7c97070 100644 --- a/Scripts/Items/Weapons/Swords/BoneHarvester.cs +++ b/Scripts/Items/Weapons/Swords/BoneHarvester.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x26BB, 0x26C5 )] - public class BoneHarvester : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0x26BB, 0x26C5)] + public class BoneHarvester : BaseSword + { + [Constructible] + public BoneHarvester() : base(0x26BB) + { + Weight = 3.0; + } - public override int AosStrengthReq => 25; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 36; - public override float MlSpeed => 3.00f; + public BoneHarvester(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 25; - public override int OldMinDamage => 13; - public override int OldMaxDamage => 15; - public override int OldSpeed => 36; + public override WeaponAbility PrimaryAbility => WeaponAbility.ParalyzingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 25; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 36; + public override float MlSpeed => 3.00f; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int OldStrengthReq => 25; + public override int OldMinDamage => 13; + public override int OldMaxDamage => 15; + public override int OldSpeed => 36; - [Constructible] - public BoneHarvester() : base( 0x26BB ) - { - Weight = 3.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public BoneHarvester( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/BoneMachete.cs b/Scripts/Items/Weapons/Swords/BoneMachete.cs index 94261ff4e..161a4ae13 100644 --- a/Scripts/Items/Weapons/Swords/BoneMachete.cs +++ b/Scripts/Items/Weapons/Swords/BoneMachete.cs @@ -2,60 +2,62 @@ using Server.Engines.MLQuests.Items; namespace Server.Items { - public class BoneMachete : ElvenMachete, ITicket - { - public override WeaponAbility PrimaryAbility => null; - public override WeaponAbility SecondaryAbility => null; + public class BoneMachete : ElvenMachete, ITicket + { + [Constructible] + public BoneMachete() + { + ItemID = 0x20E; + } - public override int PhysicalResistance => 1; - public override int FireResistance => 1; - public override int ColdResistance => 1; - public override int PoisonResistance => 1; - public override int EnergyResistance => 1; + public BoneMachete(Serial serial) + : base(serial) + { + } - public override int InitMinHits => 5; - public override int InitMaxHits => 5; + public override WeaponAbility PrimaryAbility => null; + public override WeaponAbility SecondaryAbility => null; - [Constructible] - public BoneMachete() - { - ItemID = 0x20E; - } + public override int PhysicalResistance => 1; + public override int FireResistance => 1; + public override int ColdResistance => 1; + public override int PoisonResistance => 1; + public override int EnergyResistance => 1; - public BoneMachete( Serial serial ) - : base( serial ) - { - } + public override int InitMinHits => 5; + public override int InitMaxHits => 5; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + #region ITicket Members - writer.WriteEncodedInt( 0 ); // version - } + public void OnTicketUsed(Mobile from) + { + if (Utility.RandomDouble() < 0.25) + { + from.SendLocalizedMessage( + 1075007); // Your bone handled machete snaps in half as you force your way through the poisonous undergrowth. + Delete(); + } + else + { + from.SendLocalizedMessage( + 1075008); // Your bone handled machete has grown dull but you still manage to force your way past the venomous branches. + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + #endregion - int version = reader.ReadEncodedInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - #region ITicket Members + writer.WriteEncodedInt(0); // version + } - public void OnTicketUsed( Mobile from ) - { - if ( Utility.RandomDouble() < 0.25 ) - { - from.SendLocalizedMessage( 1075007 ); // Your bone handled machete snaps in half as you force your way through the poisonous undergrowth. - Delete(); - } - else - { - from.SendLocalizedMessage( 1075008 ); // Your bone handled machete has grown dull but you still manage to force your way past the venomous branches. - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #endregion - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Broadsword.cs b/Scripts/Items/Weapons/Swords/Broadsword.cs index b4753ed28..25873490e 100644 --- a/Scripts/Items/Weapons/Swords/Broadsword.cs +++ b/Scripts/Items/Weapons/Swords/Broadsword.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0xF5E, 0xF5F )] - public class Broadsword : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorIgnore; + [Flippable(0xF5E, 0xF5F)] + public class Broadsword : BaseSword + { + [Constructible] + public Broadsword() : base(0xF5E) + { + Weight = 6.0; + } - public override int AosStrengthReq => 30; - public override int AosMinDamage => 14; - public override int AosMaxDamage => 15; - public override int AosSpeed => 33; - public override float MlSpeed => 3.25f; + public Broadsword(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 25; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 29; - public override int OldSpeed => 45; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorIgnore; - public override int DefHitSound => 0x237; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 30; + public override int AosMinDamage => 14; + public override int AosMaxDamage => 15; + public override int AosSpeed => 33; + public override float MlSpeed => 3.25f; - public override int InitMinHits => 31; - public override int InitMaxHits => 100; + public override int OldStrengthReq => 25; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 29; + public override int OldSpeed => 45; - [Constructible] - public Broadsword() : base( 0xF5E ) - { - Weight = 6.0; - } + public override int DefHitSound => 0x237; + public override int DefMissSound => 0x23A; - public Broadsword( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 100; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/ChargedAssassinSpike.cs b/Scripts/Items/Weapons/Swords/ChargedAssassinSpike.cs index 286024e3d..c82eeb40c 100644 --- a/Scripts/Items/Weapons/Swords/ChargedAssassinSpike.cs +++ b/Scripts/Items/Weapons/Swords/ChargedAssassinSpike.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class ChargedAssassinSpike : AssassinSpike - { - public override int LabelNumber => 1073518; // charged assassin spike + public class ChargedAssassinSpike : AssassinSpike + { + [Constructible] + public ChargedAssassinSpike() + { + WeaponAttributes.HitLightning = 10; + } - [Constructible] - public ChargedAssassinSpike() - { - WeaponAttributes.HitLightning = 10; - } + public ChargedAssassinSpike(Serial serial) : base(serial) + { + } - public ChargedAssassinSpike( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073518; // charged assassin spike - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/CorruptedRuneBlade.cs b/Scripts/Items/Weapons/Swords/CorruptedRuneBlade.cs index 547733fce..9d44ab073 100644 --- a/Scripts/Items/Weapons/Swords/CorruptedRuneBlade.cs +++ b/Scripts/Items/Weapons/Swords/CorruptedRuneBlade.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class CorruptedRuneBlade : RuneBlade - { - public override int LabelNumber => 1073540; // Corrupted Rune Blade + public class CorruptedRuneBlade : RuneBlade + { + [Constructible] + public CorruptedRuneBlade() + { + WeaponAttributes.ResistPhysicalBonus = -5; + WeaponAttributes.ResistPoisonBonus = 12; + } - [Constructible] - public CorruptedRuneBlade() - { - WeaponAttributes.ResistPhysicalBonus = -5; - WeaponAttributes.ResistPoisonBonus = 12; - } + public CorruptedRuneBlade(Serial serial) : base(serial) + { + } - public CorruptedRuneBlade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073540; // Corrupted Rune Blade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/CrescentBlade.cs b/Scripts/Items/Weapons/Swords/CrescentBlade.cs index 35172bd4c..badc76c16 100644 --- a/Scripts/Items/Weapons/Swords/CrescentBlade.cs +++ b/Scripts/Items/Weapons/Swords/CrescentBlade.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x26C1, 0x26CB )] - public class CrescentBlade : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; + [Flippable(0x26C1, 0x26CB)] + public class CrescentBlade : BaseSword + { + [Constructible] + public CrescentBlade() : base(0x26C1) + { + Weight = 1.0; + } - public override int AosStrengthReq => 55; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 14; - public override int AosSpeed => 47; - public override float MlSpeed => 2.50f; + public CrescentBlade(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 55; - public override int OldMinDamage => 11; - public override int OldMaxDamage => 14; - public override int OldSpeed => 47; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.MortalStrike; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 55; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 14; + public override int AosSpeed => 47; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 51; - public override int InitMaxHits => 80; + public override int OldStrengthReq => 55; + public override int OldMinDamage => 11; + public override int OldMaxDamage => 14; + public override int OldSpeed => 47; - [Constructible] - public CrescentBlade() : base( 0x26C1 ) - { - Weight = 1.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public CrescentBlade( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 51; + public override int InitMaxHits => 80; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Cutlass.cs b/Scripts/Items/Weapons/Swords/Cutlass.cs index dcfb08514..0a26665e1 100644 --- a/Scripts/Items/Weapons/Swords/Cutlass.cs +++ b/Scripts/Items/Weapons/Swords/Cutlass.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x1441, 0x1440 )] - public class Cutlass : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; - public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; + [Flippable(0x1441, 0x1440)] + public class Cutlass : BaseSword + { + [Constructible] + public Cutlass() : base(0x1441) + { + Weight = 8.0; + } - public override int AosStrengthReq => 25; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 13; - public override int AosSpeed => 44; - public override float MlSpeed => 2.50f; + public Cutlass(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 28; - public override int OldSpeed => 45; + public override WeaponAbility PrimaryAbility => WeaponAbility.BleedAttack; + public override WeaponAbility SecondaryAbility => WeaponAbility.ShadowStrike; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 25; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 13; + public override int AosSpeed => 44; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 70; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 28; + public override int OldSpeed => 45; - [Constructible] - public Cutlass() : base( 0x1441 ) - { - Weight = 8.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public Cutlass( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 70; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/DarkglowScimitar.cs b/Scripts/Items/Weapons/Swords/DarkglowScimitar.cs index 8efb0b63e..8cf5dc523 100644 --- a/Scripts/Items/Weapons/Swords/DarkglowScimitar.cs +++ b/Scripts/Items/Weapons/Swords/DarkglowScimitar.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class DarkglowScimitar : RadiantScimitar - { - public override int LabelNumber => 1073542; // darkglow scimitar + public class DarkglowScimitar : RadiantScimitar + { + [Constructible] + public DarkglowScimitar() + { + WeaponAttributes.HitDispel = 10; + } - [Constructible] - public DarkglowScimitar() - { - WeaponAttributes.HitDispel = 10; - } + public DarkglowScimitar(Serial serial) : base(serial) + { + } - public DarkglowScimitar( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073542; // darkglow scimitar - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/DiseasedMachete.cs b/Scripts/Items/Weapons/Swords/DiseasedMachete.cs index 917e98aad..b01ffc5fa 100644 --- a/Scripts/Items/Weapons/Swords/DiseasedMachete.cs +++ b/Scripts/Items/Weapons/Swords/DiseasedMachete.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class DiseasedMachete : ElvenMachete - { - public override int LabelNumber => 1073536; // Diseased Machete + public class DiseasedMachete : ElvenMachete + { + [Constructible] + public DiseasedMachete() + { + WeaponAttributes.HitPoisonArea = 25; + } - [Constructible] - public DiseasedMachete() - { - WeaponAttributes.HitPoisonArea = 25; - } + public DiseasedMachete(Serial serial) : base(serial) + { + } - public DiseasedMachete( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073536; // Diseased Machete - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/FierySpellblade.cs b/Scripts/Items/Weapons/Swords/FierySpellblade.cs index 83aa8b4d0..ebda09d81 100644 --- a/Scripts/Items/Weapons/Swords/FierySpellblade.cs +++ b/Scripts/Items/Weapons/Swords/FierySpellblade.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class FierySpellblade : ElvenSpellblade - { - public override int LabelNumber => 1073515; // fiery spellblade + public class FierySpellblade : ElvenSpellblade + { + [Constructible] + public FierySpellblade() + { + WeaponAttributes.ResistFireBonus = 5; + } - [Constructible] - public FierySpellblade() - { - WeaponAttributes.ResistFireBonus = 5; - } + public FierySpellblade(Serial serial) : base(serial) + { + } - public FierySpellblade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073515; // fiery spellblade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/IcyScimitar.cs b/Scripts/Items/Weapons/Swords/IcyScimitar.cs index 631deff17..7ff484692 100644 --- a/Scripts/Items/Weapons/Swords/IcyScimitar.cs +++ b/Scripts/Items/Weapons/Swords/IcyScimitar.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class IcyScimitar : RadiantScimitar - { - public override int LabelNumber => 1073543; // icy scimitar + public class IcyScimitar : RadiantScimitar + { + [Constructible] + public IcyScimitar() + { + WeaponAttributes.HitHarm = 15; + } - [Constructible] - public IcyScimitar() - { - WeaponAttributes.HitHarm = 15; - } + public IcyScimitar(Serial serial) : base(serial) + { + } - public IcyScimitar( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073543; // icy scimitar - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/IcySpellblade.cs b/Scripts/Items/Weapons/Swords/IcySpellblade.cs index cb823416c..c889b1b07 100644 --- a/Scripts/Items/Weapons/Swords/IcySpellblade.cs +++ b/Scripts/Items/Weapons/Swords/IcySpellblade.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class IcySpellblade : ElvenSpellblade - { - public override int LabelNumber => 1073514; // icy spellblade + public class IcySpellblade : ElvenSpellblade + { + [Constructible] + public IcySpellblade() + { + WeaponAttributes.ResistColdBonus = 5; + } - [Constructible] - public IcySpellblade() - { - WeaponAttributes.ResistColdBonus = 5; - } + public IcySpellblade(Serial serial) : base(serial) + { + } - public IcySpellblade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073514; // icy spellblade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Katana.cs b/Scripts/Items/Weapons/Swords/Katana.cs index 032081af2..ad2b6d1e4 100644 --- a/Scripts/Items/Weapons/Swords/Katana.cs +++ b/Scripts/Items/Weapons/Swords/Katana.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13FF, 0x13FE )] - public class Katana : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorIgnore; + [Flippable(0x13FF, 0x13FE)] + public class Katana : BaseSword + { + [Constructible] + public Katana() : base(0x13FF) + { + Weight = 6.0; + } - public override int AosStrengthReq => 25; - public override int AosMinDamage => 11; - public override int AosMaxDamage => 13; - public override int AosSpeed => 46; - public override float MlSpeed => 2.50f; + public Katana(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 26; - public override int OldSpeed => 58; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.ArmorIgnore; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 25; + public override int AosMinDamage => 11; + public override int AosMaxDamage => 13; + public override int AosSpeed => 46; + public override float MlSpeed => 2.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 90; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 26; + public override int OldSpeed => 58; - [Constructible] - public Katana() : base( 0x13FF ) - { - Weight = 6.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public Katana( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 90; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/KnightsWarCleaver.cs b/Scripts/Items/Weapons/Swords/KnightsWarCleaver.cs index 60ae7d557..fab35ce5a 100644 --- a/Scripts/Items/Weapons/Swords/KnightsWarCleaver.cs +++ b/Scripts/Items/Weapons/Swords/KnightsWarCleaver.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class KnightsWarCleaver : WarCleaver - { - public override int LabelNumber => 1073525; // knight's war cleaver + public class KnightsWarCleaver : WarCleaver + { + [Constructible] + public KnightsWarCleaver() + { + Attributes.RegenHits = 3; + } - [Constructible] - public KnightsWarCleaver() - { - Attributes.RegenHits = 3; - } + public KnightsWarCleaver(Serial serial) : base(serial) + { + } - public KnightsWarCleaver( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073525; // knight's war cleaver - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Kryss.cs b/Scripts/Items/Weapons/Swords/Kryss.cs index 289be8bd9..b63f00b9a 100644 --- a/Scripts/Items/Weapons/Swords/Kryss.cs +++ b/Scripts/Items/Weapons/Swords/Kryss.cs @@ -1,57 +1,57 @@ namespace Server.Items { - [FlippableAttribute( 0x1401, 0x1400 )] - public class Kryss : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; + [Flippable(0x1401, 0x1400)] + public class Kryss : BaseSword + { + [Constructible] + public Kryss() : base(0x1401) + { + Weight = 2.0; + } - public override int AosStrengthReq => 10; - public override int AosMinDamage => 10; - public override int AosMaxDamage => 12; - public override int AosSpeed => 53; - public override float MlSpeed => 2.00f; + public Kryss(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 3; - public override int OldMaxDamage => 28; - public override int OldSpeed => 53; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.InfectiousStrike; - public override int DefHitSound => 0x23C; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 10; + public override int AosMinDamage => 10; + public override int AosMaxDamage => 12; + public override int AosSpeed => 53; + public override float MlSpeed => 2.00f; - public override int InitMinHits => 31; - public override int InitMaxHits => 90; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 3; + public override int OldMaxDamage => 28; + public override int OldSpeed => 53; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x23C; + public override int DefMissSound => 0x238; - [Constructible] - public Kryss() : base( 0x1401 ) - { - Weight = 2.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 90; - public Kryss( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( Weight == 1.0 ) - Weight = 2.0; - } - } -} + if (Weight == 1.0) + Weight = 2.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Lance.cs b/Scripts/Items/Weapons/Swords/Lance.cs index 73c4425b9..16c6c578b 100644 --- a/Scripts/Items/Weapons/Swords/Lance.cs +++ b/Scripts/Items/Weapons/Swords/Lance.cs @@ -1,54 +1,54 @@ namespace Server.Items { - [FlippableAttribute( 0x26C0, 0x26CA )] - public class Lance : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.Dismount; - public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; + [Flippable(0x26C0, 0x26CA)] + public class Lance : BaseSword + { + [Constructible] + public Lance() : base(0x26C0) + { + Weight = 12.0; + } - public override int AosStrengthReq => 95; - public override int AosMinDamage => 17; - public override int AosMaxDamage => 18; - public override int AosSpeed => 24; - public override float MlSpeed => 4.50f; + public Lance(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 95; - public override int OldMinDamage => 17; - public override int OldMaxDamage => 18; - public override int OldSpeed => 24; + public override WeaponAbility PrimaryAbility => WeaponAbility.Dismount; + public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; - public override int DefHitSound => 0x23C; - public override int DefMissSound => 0x238; + public override int AosStrengthReq => 95; + public override int AosMinDamage => 17; + public override int AosMaxDamage => 18; + public override int AosSpeed => 24; + public override float MlSpeed => 4.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int OldStrengthReq => 95; + public override int OldMinDamage => 17; + public override int OldMaxDamage => 18; + public override int OldSpeed => 24; - public override SkillName DefSkill => SkillName.Fencing; - public override WeaponType DefType => WeaponType.Piercing; - public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; + public override int DefHitSound => 0x23C; + public override int DefMissSound => 0x238; - [Constructible] - public Lance() : base( 0x26C0 ) - { - Weight = 12.0; - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public Lance( Serial serial ) : base( serial ) - { - } + public override SkillName DefSkill => SkillName.Fencing; + public override WeaponType DefType => WeaponType.Piercing; + public override WeaponAnimation DefAnimation => WeaponAnimation.Pierce1H; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/LeafbladeOfEase.cs b/Scripts/Items/Weapons/Swords/LeafbladeOfEase.cs index 923852799..5699c5b25 100644 --- a/Scripts/Items/Weapons/Swords/LeafbladeOfEase.cs +++ b/Scripts/Items/Weapons/Swords/LeafbladeOfEase.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class LeafbladeOfEase : Leafblade - { - public override int LabelNumber => 1073524; // leafblade of ease + public class LeafbladeOfEase : Leafblade + { + [Constructible] + public LeafbladeOfEase() + { + WeaponAttributes.UseBestSkill = 1; + } - [Constructible] - public LeafbladeOfEase() - { - WeaponAttributes.UseBestSkill = 1; - } + public LeafbladeOfEase(Serial serial) : base(serial) + { + } - public LeafbladeOfEase( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073524; // leafblade of ease - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Longsword.cs b/Scripts/Items/Weapons/Swords/Longsword.cs index e72043acd..64b315d5e 100644 --- a/Scripts/Items/Weapons/Swords/Longsword.cs +++ b/Scripts/Items/Weapons/Swords/Longsword.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0xF61, 0xF60 )] - public class Longsword : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; - public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; + [Flippable(0xF61, 0xF60)] + public class Longsword : BaseSword + { + [Constructible] + public Longsword() : base(0xF61) + { + Weight = 7.0; + } - public override int AosStrengthReq => 35; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 16; - public override int AosSpeed => 30; - public override float MlSpeed => 3.50f; + public Longsword(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 25; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 33; - public override int OldSpeed => 35; + public override WeaponAbility PrimaryAbility => WeaponAbility.ArmorIgnore; + public override WeaponAbility SecondaryAbility => WeaponAbility.ConcussionBlow; - public override int DefHitSound => 0x237; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 16; + public override int AosSpeed => 30; + public override float MlSpeed => 3.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int OldStrengthReq => 25; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 33; + public override int OldSpeed => 35; - [Constructible] - public Longsword() : base( 0xF61 ) - { - Weight = 7.0; - } + public override int DefHitSound => 0x237; + public override int DefMissSound => 0x23A; - public Longsword( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Luckblade.cs b/Scripts/Items/Weapons/Swords/Luckblade.cs index f2a56c131..8bc842a42 100644 --- a/Scripts/Items/Weapons/Swords/Luckblade.cs +++ b/Scripts/Items/Weapons/Swords/Luckblade.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class Luckblade : Leafblade - { - public override int LabelNumber => 1073522; // luckblade + public class Luckblade : Leafblade + { + [Constructible] + public Luckblade() + { + Attributes.Luck = 20; + } - [Constructible] - public Luckblade() - { - Attributes.Luck = 20; - } + public Luckblade(Serial serial) : base(serial) + { + } - public Luckblade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073522; // luckblade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/MacheteOfDefense.cs b/Scripts/Items/Weapons/Swords/MacheteOfDefense.cs index ccad2f2a4..16c4f8033 100644 --- a/Scripts/Items/Weapons/Swords/MacheteOfDefense.cs +++ b/Scripts/Items/Weapons/Swords/MacheteOfDefense.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class MacheteOfDefense : ElvenMachete - { - public override int LabelNumber => 1073535; // machete of defense + public class MacheteOfDefense : ElvenMachete + { + [Constructible] + public MacheteOfDefense() + { + Attributes.DefendChance = 5; + } - [Constructible] - public MacheteOfDefense() - { - Attributes.DefendChance = 5; - } + public MacheteOfDefense(Serial serial) : base(serial) + { + } - public MacheteOfDefense( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073535; // machete of defense - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/MagekillerAssassinSpike.cs b/Scripts/Items/Weapons/Swords/MagekillerAssassinSpike.cs index b835fb586..3e922e6c4 100644 --- a/Scripts/Items/Weapons/Swords/MagekillerAssassinSpike.cs +++ b/Scripts/Items/Weapons/Swords/MagekillerAssassinSpike.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class MagekillerAssassinSpike : AssassinSpike - { - public override int LabelNumber => 1073519; // magekiller assassin spike + public class MagekillerAssassinSpike : AssassinSpike + { + [Constructible] + public MagekillerAssassinSpike() + { + WeaponAttributes.HitLeechMana = 16; + } - [Constructible] - public MagekillerAssassinSpike() - { - WeaponAttributes.HitLeechMana = 16; - } + public MagekillerAssassinSpike(Serial serial) : base(serial) + { + } - public MagekillerAssassinSpike( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073519; // magekiller assassin spike - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/MagekillerLeafblade.cs b/Scripts/Items/Weapons/Swords/MagekillerLeafblade.cs index afd83849e..1962eba43 100644 --- a/Scripts/Items/Weapons/Swords/MagekillerLeafblade.cs +++ b/Scripts/Items/Weapons/Swords/MagekillerLeafblade.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class MagekillerLeafblade : Leafblade - { - public override int LabelNumber => 1073523; // maagekiller leafblade + public class MagekillerLeafblade : Leafblade + { + [Constructible] + public MagekillerLeafblade() + { + WeaponAttributes.HitLeechMana = 16; + } - [Constructible] - public MagekillerLeafblade() - { - WeaponAttributes.HitLeechMana = 16; - } + public MagekillerLeafblade(Serial serial) : base(serial) + { + } - public MagekillerLeafblade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073523; // maagekiller leafblade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/MagesRuneBlade.cs b/Scripts/Items/Weapons/Swords/MagesRuneBlade.cs index bee766c7e..c97416ad5 100644 --- a/Scripts/Items/Weapons/Swords/MagesRuneBlade.cs +++ b/Scripts/Items/Weapons/Swords/MagesRuneBlade.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class MagesRuneBlade : RuneBlade - { - public override int LabelNumber => 1073538; // mage's rune blade + public class MagesRuneBlade : RuneBlade + { + [Constructible] + public MagesRuneBlade() + { + Attributes.CastSpeed = 1; + } - [Constructible] - public MagesRuneBlade() - { - Attributes.CastSpeed = 1; - } + public MagesRuneBlade(Serial serial) : base(serial) + { + } - public MagesRuneBlade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073538; // mage's rune blade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/OrcishMachete.cs b/Scripts/Items/Weapons/Swords/OrcishMachete.cs index 7b6780bb6..625890560 100644 --- a/Scripts/Items/Weapons/Swords/OrcishMachete.cs +++ b/Scripts/Items/Weapons/Swords/OrcishMachete.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class OrcishMachete : ElvenMachete - { - public override int LabelNumber => 1073534; // Orcish Machete + public class OrcishMachete : ElvenMachete + { + [Constructible] + public OrcishMachete() + { + Attributes.BonusInt = -5; + Attributes.WeaponDamage = 10; + } - [Constructible] - public OrcishMachete() - { - Attributes.BonusInt = -5; - Attributes.WeaponDamage = 10; - } + public OrcishMachete(Serial serial) : base(serial) + { + } - public OrcishMachete( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073534; // Orcish Machete - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/RuneBladeOfKnowledge.cs b/Scripts/Items/Weapons/Swords/RuneBladeOfKnowledge.cs index 12c6c532c..f6c00e314 100644 --- a/Scripts/Items/Weapons/Swords/RuneBladeOfKnowledge.cs +++ b/Scripts/Items/Weapons/Swords/RuneBladeOfKnowledge.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class RuneBladeOfKnowledge : RuneBlade - { - public override int LabelNumber => 1073539; // rune blade of knowledge + public class RuneBladeOfKnowledge : RuneBlade + { + [Constructible] + public RuneBladeOfKnowledge() + { + Attributes.SpellDamage = 5; + } - [Constructible] - public RuneBladeOfKnowledge() - { - Attributes.SpellDamage = 5; - } + public RuneBladeOfKnowledge(Serial serial) : base(serial) + { + } - public RuneBladeOfKnowledge( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073539; // rune blade of knowledge - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Runesabre.cs b/Scripts/Items/Weapons/Swords/Runesabre.cs index aab6577c6..84ad5f061 100644 --- a/Scripts/Items/Weapons/Swords/Runesabre.cs +++ b/Scripts/Items/Weapons/Swords/Runesabre.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class Runesabre : RuneBlade - { - public override int LabelNumber => 1073537; // runesabre + public class Runesabre : RuneBlade + { + [Constructible] + public Runesabre() + { + SkillBonuses.SetValues(0, SkillName.MagicResist, 5.0); + WeaponAttributes.MageWeapon = -29; + } - [Constructible] - public Runesabre() - { - SkillBonuses.SetValues( 0, SkillName.MagicResist, 5.0 ); - WeaponAttributes.MageWeapon = -29; - } + public Runesabre(Serial serial) : base(serial) + { + } - public Runesabre( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073537; // runesabre - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/Scimitar.cs b/Scripts/Items/Weapons/Swords/Scimitar.cs index 9cb68ff5f..aee828f4e 100644 --- a/Scripts/Items/Weapons/Swords/Scimitar.cs +++ b/Scripts/Items/Weapons/Swords/Scimitar.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13B6, 0x13B5 )] - public class Scimitar : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0x13B6, 0x13B5)] + public class Scimitar : BaseSword + { + [Constructible] + public Scimitar() : base(0x13B6) + { + Weight = 5.0; + } - public override int AosStrengthReq => 25; - public override int AosMinDamage => 13; - public override int AosMaxDamage => 15; - public override int AosSpeed => 37; - public override float MlSpeed => 3.00f; + public Scimitar(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 10; - public override int OldMinDamage => 4; - public override int OldMaxDamage => 30; - public override int OldSpeed => 43; + public override WeaponAbility PrimaryAbility => WeaponAbility.DoubleStrike; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int DefHitSound => 0x23B; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 25; + public override int AosMinDamage => 13; + public override int AosMaxDamage => 15; + public override int AosSpeed => 37; + public override float MlSpeed => 3.00f; - public override int InitMinHits => 31; - public override int InitMaxHits => 90; + public override int OldStrengthReq => 10; + public override int OldMinDamage => 4; + public override int OldMaxDamage => 30; + public override int OldSpeed => 43; - [Constructible] - public Scimitar() : base( 0x13B6 ) - { - Weight = 5.0; - } + public override int DefHitSound => 0x23B; + public override int DefMissSound => 0x23A; - public Scimitar( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 90; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/SerratedWarCleaver.cs b/Scripts/Items/Weapons/Swords/SerratedWarCleaver.cs index eb9dc220a..e07a65ca5 100644 --- a/Scripts/Items/Weapons/Swords/SerratedWarCleaver.cs +++ b/Scripts/Items/Weapons/Swords/SerratedWarCleaver.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SerratedWarCleaver : WarCleaver - { - public override int LabelNumber => 1073527; // serrated war cleaver + public class SerratedWarCleaver : WarCleaver + { + [Constructible] + public SerratedWarCleaver() + { + Attributes.WeaponDamage = 7; + } - [Constructible] - public SerratedWarCleaver() - { - Attributes.WeaponDamage = 7; - } + public SerratedWarCleaver(Serial serial) : base(serial) + { + } - public SerratedWarCleaver( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073527; // serrated war cleaver - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/SpellbladeOfDefense.cs b/Scripts/Items/Weapons/Swords/SpellbladeOfDefense.cs index 4c87e0cc1..abf724196 100644 --- a/Scripts/Items/Weapons/Swords/SpellbladeOfDefense.cs +++ b/Scripts/Items/Weapons/Swords/SpellbladeOfDefense.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class SpellbladeOfDefense : ElvenSpellblade - { - public override int LabelNumber => 1073516; // spellblade of defense + public class SpellbladeOfDefense : ElvenSpellblade + { + [Constructible] + public SpellbladeOfDefense() + { + Attributes.DefendChance = 5; + } - [Constructible] - public SpellbladeOfDefense() - { - Attributes.DefendChance = 5; - } + public SpellbladeOfDefense(Serial serial) : base(serial) + { + } - public SpellbladeOfDefense( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073516; // spellblade of defense - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/ThinLongsword.cs b/Scripts/Items/Weapons/Swords/ThinLongsword.cs index 526243d14..d9a6d8113 100644 --- a/Scripts/Items/Weapons/Swords/ThinLongsword.cs +++ b/Scripts/Items/Weapons/Swords/ThinLongsword.cs @@ -1,47 +1,47 @@ namespace Server.Items { - [FlippableAttribute( 0x13B8, 0x13B7 )] - public class ThinLongsword : BaseSword - { - public override int AosStrengthReq => 35; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 16; - public override int AosSpeed => 30; - public override float MlSpeed => 3.50f; + [Flippable(0x13B8, 0x13B7)] + public class ThinLongsword : BaseSword + { + [Constructible] + public ThinLongsword() : base(0x13B8) + { + Weight = 1.0; + } - public override int OldStrengthReq => 25; - public override int OldMinDamage => 5; - public override int OldMaxDamage => 33; - public override int OldSpeed => 35; + public ThinLongsword(Serial serial) : base(serial) + { + } - public override int DefHitSound => 0x237; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 35; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 16; + public override int AosSpeed => 30; + public override float MlSpeed => 3.50f; - public override int InitMinHits => 31; - public override int InitMaxHits => 110; + public override int OldStrengthReq => 25; + public override int OldMinDamage => 5; + public override int OldMaxDamage => 33; + public override int OldSpeed => 35; - [Constructible] - public ThinLongsword() : base( 0x13B8 ) - { - Weight = 1.0; - } + public override int DefHitSound => 0x237; + public override int DefMissSound => 0x23A; - public ThinLongsword( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 110; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/TrueAssassinSpike.cs b/Scripts/Items/Weapons/Swords/TrueAssassinSpike.cs index ad38bca1f..e29d2360f 100644 --- a/Scripts/Items/Weapons/Swords/TrueAssassinSpike.cs +++ b/Scripts/Items/Weapons/Swords/TrueAssassinSpike.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class TrueAssassinSpike : AssassinSpike - { - public override int LabelNumber => 1073517; // true assassin spike + public class TrueAssassinSpike : AssassinSpike + { + [Constructible] + public TrueAssassinSpike() + { + Attributes.AttackChance = 4; + Attributes.WeaponDamage = 4; + } - [Constructible] - public TrueAssassinSpike() - { - Attributes.AttackChance = 4; - Attributes.WeaponDamage = 4; - } + public TrueAssassinSpike(Serial serial) : base(serial) + { + } - public TrueAssassinSpike( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073517; // true assassin spike - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/TrueLeafblade.cs b/Scripts/Items/Weapons/Swords/TrueLeafblade.cs index 94d9efc70..bf4f5c269 100644 --- a/Scripts/Items/Weapons/Swords/TrueLeafblade.cs +++ b/Scripts/Items/Weapons/Swords/TrueLeafblade.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class TrueLeafblade : Leafblade - { - public override int LabelNumber => 1073521; // true leafblade + public class TrueLeafblade : Leafblade + { + [Constructible] + public TrueLeafblade() + { + WeaponAttributes.ResistPoisonBonus = 5; + } - [Constructible] - public TrueLeafblade() - { - WeaponAttributes.ResistPoisonBonus = 5; - } + public TrueLeafblade(Serial serial) : base(serial) + { + } - public TrueLeafblade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073521; // true leafblade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/TrueRadiantScimitar.cs b/Scripts/Items/Weapons/Swords/TrueRadiantScimitar.cs index a3ffe41ed..6de73eaca 100644 --- a/Scripts/Items/Weapons/Swords/TrueRadiantScimitar.cs +++ b/Scripts/Items/Weapons/Swords/TrueRadiantScimitar.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class TrueRadiantScimitar : RadiantScimitar - { - public override int LabelNumber => 1073541; // true radiant scimitar + public class TrueRadiantScimitar : RadiantScimitar + { + [Constructible] + public TrueRadiantScimitar() + { + Attributes.NightSight = 1; + } - [Constructible] - public TrueRadiantScimitar() - { - Attributes.NightSight = 1; - } + public TrueRadiantScimitar(Serial serial) : base(serial) + { + } - public TrueRadiantScimitar( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073541; // true radiant scimitar - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/TrueSpellblade.cs b/Scripts/Items/Weapons/Swords/TrueSpellblade.cs index fd57d3a07..f7f06c556 100644 --- a/Scripts/Items/Weapons/Swords/TrueSpellblade.cs +++ b/Scripts/Items/Weapons/Swords/TrueSpellblade.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class TrueSpellblade : ElvenSpellblade - { - public override int LabelNumber => 1073513; // true spellblade + public class TrueSpellblade : ElvenSpellblade + { + [Constructible] + public TrueSpellblade() + { + Attributes.SpellChanneling = 1; + Attributes.CastSpeed = -1; + } - [Constructible] - public TrueSpellblade() - { - Attributes.SpellChanneling = 1; - Attributes.CastSpeed = -1; - } + public TrueSpellblade(Serial serial) : base(serial) + { + } - public TrueSpellblade( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073513; // true spellblade - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/TrueWarCleaver.cs b/Scripts/Items/Weapons/Swords/TrueWarCleaver.cs index 5168f97d7..5eea3ecef 100644 --- a/Scripts/Items/Weapons/Swords/TrueWarCleaver.cs +++ b/Scripts/Items/Weapons/Swords/TrueWarCleaver.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class TrueWarCleaver : WarCleaver - { - public override int LabelNumber => 1073528; // true war cleaver + public class TrueWarCleaver : WarCleaver + { + [Constructible] + public TrueWarCleaver() + { + Attributes.WeaponDamage = 4; + Attributes.RegenHits = 2; + } - [Constructible] - public TrueWarCleaver() - { - Attributes.WeaponDamage = 4; - Attributes.RegenHits = 2; - } + public TrueWarCleaver(Serial serial) : base(serial) + { + } - public TrueWarCleaver( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073528; // true war cleaver - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/TwinklingScimitar.cs b/Scripts/Items/Weapons/Swords/TwinklingScimitar.cs index a3ff81f1a..99f21e10c 100644 --- a/Scripts/Items/Weapons/Swords/TwinklingScimitar.cs +++ b/Scripts/Items/Weapons/Swords/TwinklingScimitar.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class TwinklingScimitar : RadiantScimitar - { - public override int LabelNumber => 1073544; // twinkling scimitar + public class TwinklingScimitar : RadiantScimitar + { + [Constructible] + public TwinklingScimitar() + { + Attributes.DefendChance = 6; + } - [Constructible] - public TwinklingScimitar() - { - Attributes.DefendChance = 6; - } + public TwinklingScimitar(Serial serial) : base(serial) + { + } - public TwinklingScimitar( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073544; // twinkling scimitar - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/VikingSword.cs b/Scripts/Items/Weapons/Swords/VikingSword.cs index 06b296d80..5e490c228 100644 --- a/Scripts/Items/Weapons/Swords/VikingSword.cs +++ b/Scripts/Items/Weapons/Swords/VikingSword.cs @@ -1,50 +1,50 @@ namespace Server.Items { - [FlippableAttribute( 0x13B9, 0x13Ba )] - public class VikingSword : BaseSword - { - public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; - public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; + [Flippable(0x13B9, 0x13Ba)] + public class VikingSword : BaseSword + { + [Constructible] + public VikingSword() : base(0x13B9) + { + Weight = 6.0; + } - public override int AosStrengthReq => 40; - public override int AosMinDamage => 15; - public override int AosMaxDamage => 17; - public override int AosSpeed => 28; - public override float MlSpeed => 3.75f; + public VikingSword(Serial serial) : base(serial) + { + } - public override int OldStrengthReq => 40; - public override int OldMinDamage => 6; - public override int OldMaxDamage => 34; - public override int OldSpeed => 30; + public override WeaponAbility PrimaryAbility => WeaponAbility.CrushingBlow; + public override WeaponAbility SecondaryAbility => WeaponAbility.ParalyzingBlow; - public override int DefHitSound => 0x237; - public override int DefMissSound => 0x23A; + public override int AosStrengthReq => 40; + public override int AosMinDamage => 15; + public override int AosMaxDamage => 17; + public override int AosSpeed => 28; + public override float MlSpeed => 3.75f; - public override int InitMinHits => 31; - public override int InitMaxHits => 100; + public override int OldStrengthReq => 40; + public override int OldMinDamage => 6; + public override int OldMaxDamage => 34; + public override int OldSpeed => 30; - [Constructible] - public VikingSword() : base( 0x13B9 ) - { - Weight = 6.0; - } + public override int DefHitSound => 0x237; + public override int DefMissSound => 0x23A; - public VikingSword( Serial serial ) : base( serial ) - { - } + public override int InitMinHits => 31; + public override int InitMaxHits => 100; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Swords/WoundingAssassinSpike.cs b/Scripts/Items/Weapons/Swords/WoundingAssassinSpike.cs index 8839984d7..69c7ab8cd 100644 --- a/Scripts/Items/Weapons/Swords/WoundingAssassinSpike.cs +++ b/Scripts/Items/Weapons/Swords/WoundingAssassinSpike.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class WoundingAssassinSpike : AssassinSpike - { - public override int LabelNumber => 1073520; // wounding assassin spike + public class WoundingAssassinSpike : AssassinSpike + { + [Constructible] + public WoundingAssassinSpike() + { + WeaponAttributes.HitHarm = 15; + } - [Constructible] - public WoundingAssassinSpike() - { - WeaponAttributes.HitHarm = 15; - } + public WoundingAssassinSpike(Serial serial) : base(serial) + { + } - public WoundingAssassinSpike( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073520; // wounding assassin spike - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/WeaponEnums.cs b/Scripts/Items/Weapons/WeaponEnums.cs index ea76fc5ec..dd102c5e0 100644 --- a/Scripts/Items/Weapons/WeaponEnums.cs +++ b/Scripts/Items/Weapons/WeaponEnums.cs @@ -1,64 +1,64 @@ namespace Server.Items { - public enum WeaponQuality - { - Low, - Regular, - Exceptional - } + public enum WeaponQuality + { + Low, + Regular, + Exceptional + } - public enum WeaponType - { - Axe, // Axes, Hatches, etc. These can give concussion blows - Slashing, // Katana, Broadsword, Longsword, etc. Slashing weapons are poisonable - Staff, // Staves - Bashing, // War Hammers, Maces, Mauls, etc. Two-handed bashing delivers crushing blows - Piercing, // Spears, Warforks, Daggers, etc. Two-handed piercing delivers paralyzing blows - Polearm, // Halberd, Bardiche - Ranged, // Bow, Crossbows - Fists // Fists - } + public enum WeaponType + { + Axe, // Axes, Hatches, etc. These can give concussion blows + Slashing, // Katana, Broadsword, Longsword, etc. Slashing weapons are poisonable + Staff, // Staves + Bashing, // War Hammers, Maces, Mauls, etc. Two-handed bashing delivers crushing blows + Piercing, // Spears, Warforks, Daggers, etc. Two-handed piercing delivers paralyzing blows + Polearm, // Halberd, Bardiche + Ranged, // Bow, Crossbows + Fists // Fists + } - public enum WeaponDamageLevel - { - Regular, - Ruin, - Might, - Force, - Power, - Vanq - } + public enum WeaponDamageLevel + { + Regular, + Ruin, + Might, + Force, + Power, + Vanq + } - public enum WeaponAccuracyLevel - { - Regular, - Accurate, - Surpassingly, - Eminently, - Exceedingly, - Supremely - } + public enum WeaponAccuracyLevel + { + Regular, + Accurate, + Surpassingly, + Eminently, + Exceedingly, + Supremely + } - public enum WeaponDurabilityLevel - { - Regular, - Durable, - Substantial, - Massive, - Fortified, - Indestructible - } + public enum WeaponDurabilityLevel + { + Regular, + Durable, + Substantial, + Massive, + Fortified, + Indestructible + } - public enum WeaponAnimation - { - Slash1H = 9, - Pierce1H = 10, - Bash1H = 11, - Bash2H = 12, - Slash2H = 13, - Pierce2H = 14, - ShootBow = 18, - ShootXBow = 19, - Wrestle = 31 - } + public enum WeaponAnimation + { + Slash1H = 9, + Pierce1H = 10, + Bash1H = 11, + Bash2H = 12, + Slash2H = 13, + Pierce2H = 14, + ShootBow = 18, + ShootXBow = 19, + Wrestle = 31 + } } \ No newline at end of file diff --git a/Scripts/Items/Weapons/Wooden/AncientWildStaff.cs b/Scripts/Items/Weapons/Wooden/AncientWildStaff.cs index 641915537..a2b9f6e95 100644 --- a/Scripts/Items/Weapons/Wooden/AncientWildStaff.cs +++ b/Scripts/Items/Weapons/Wooden/AncientWildStaff.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class AncientWildStaff : WildStaff - { - public override int LabelNumber => 1073550; // ancient wild staff + public class AncientWildStaff : WildStaff + { + [Constructible] + public AncientWildStaff() + { + WeaponAttributes.ResistPoisonBonus = 5; + } - [Constructible] - public AncientWildStaff() - { - WeaponAttributes.ResistPoisonBonus = 5; - } + public AncientWildStaff(Serial serial) : base(serial) + { + } - public AncientWildStaff( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073550; // ancient wild staff - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Wooden/ArcanistsWildStaff.cs b/Scripts/Items/Weapons/Wooden/ArcanistsWildStaff.cs index 89c89fa18..89dc445b8 100644 --- a/Scripts/Items/Weapons/Wooden/ArcanistsWildStaff.cs +++ b/Scripts/Items/Weapons/Wooden/ArcanistsWildStaff.cs @@ -1,32 +1,32 @@ namespace Server.Items { - public class ArcanistsWildStaff : WildStaff - { - public override int LabelNumber => 1073549; // arcanist's wild staff + public class ArcanistsWildStaff : WildStaff + { + [Constructible] + public ArcanistsWildStaff() + { + Attributes.BonusMana = 3; + Attributes.WeaponDamage = 3; + } - [Constructible] - public ArcanistsWildStaff() - { - Attributes.BonusMana = 3; - Attributes.WeaponDamage = 3; - } + public ArcanistsWildStaff(Serial serial) : base(serial) + { + } - public ArcanistsWildStaff( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073549; // arcanist's wild staff - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Wooden/HardenedWildStaff.cs b/Scripts/Items/Weapons/Wooden/HardenedWildStaff.cs index 636bf166d..9a985ed61 100644 --- a/Scripts/Items/Weapons/Wooden/HardenedWildStaff.cs +++ b/Scripts/Items/Weapons/Wooden/HardenedWildStaff.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class HardenedWildStaff : WildStaff - { - public override int LabelNumber => 1073552; // hardened wild staff + public class HardenedWildStaff : WildStaff + { + [Constructible] + public HardenedWildStaff() + { + Attributes.WeaponDamage = 5; + } - [Constructible] - public HardenedWildStaff() - { - Attributes.WeaponDamage = 5; - } + public HardenedWildStaff(Serial serial) : base(serial) + { + } - public HardenedWildStaff( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073552; // hardened wild staff - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Items/Weapons/Wooden/ThornedWildStaff.cs b/Scripts/Items/Weapons/Wooden/ThornedWildStaff.cs index d19acc3b2..ea01f95fe 100644 --- a/Scripts/Items/Weapons/Wooden/ThornedWildStaff.cs +++ b/Scripts/Items/Weapons/Wooden/ThornedWildStaff.cs @@ -1,31 +1,31 @@ namespace Server.Items { - public class ThornedWildStaff : WildStaff - { - public override int LabelNumber => 1073551; // thorned wild staff + public class ThornedWildStaff : WildStaff + { + [Constructible] + public ThornedWildStaff() + { + Attributes.ReflectPhysical = 12; + } - [Constructible] - public ThornedWildStaff() - { - Attributes.ReflectPhysical = 12; - } + public ThornedWildStaff(Serial serial) : base(serial) + { + } - public ThornedWildStaff( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1073551; // thorned wild staff - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/AOS.cs b/Scripts/Misc/AOS.cs index 2c2373b4a..23c8fce1a 100644 --- a/Scripts/Misc/AOS.cs +++ b/Scripts/Misc/AOS.cs @@ -4,1350 +4,1512 @@ using Server.Items; using Server.Mobiles; using Server.Spells; using Server.Spells.Fifth; -using Server.Spells.Seventh; using Server.Spells.Ninjitsu; +using Server.Spells.Seventh; namespace Server { - public class AOS - { - public static void DisableStatInfluences() - { - for( int i = 0; i < SkillInfo.Table.Length; ++i ) - { - SkillInfo info = SkillInfo.Table[i]; - - info.StrScale = 0.0; - info.DexScale = 0.0; - info.IntScale = 0.0; - info.StatTotal = 0.0; - } - } - - public static int Damage( Mobile m, int damage, bool ignoreArmor, int phys, int fire, int cold, int pois, int nrgy ) - { - return Damage( m, null, damage, ignoreArmor, phys, fire, cold, pois, nrgy ); - } - - public static int Damage( Mobile m, int damage, int phys, int fire, int cold, int pois, int nrgy ) - { - return Damage( m, null, damage, phys, fire, cold, pois, nrgy ); - } - - public static int Damage( Mobile m, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy ) - { - return Damage( m, from, damage, false, phys, fire, cold, pois, nrgy, 0, 0, false, false, false ); - } - - public static int Damage( Mobile m, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy, int chaos ) - { - return Damage( m, from, damage, false, phys, fire, cold, pois, nrgy, chaos, 0, false, false, false ); - } - - public static int Damage( Mobile m, Mobile from, int damage, bool ignoreArmor, int phys, int fire, int cold, int pois, int nrgy ) - { - return Damage( m, from, damage, ignoreArmor, phys, fire, cold, pois, nrgy, 0, 0, false, false, false ); - } - - public static int Damage( Mobile m, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy, bool keepAlive ) - { - return Damage( m, from, damage, false, phys, fire, cold, pois, nrgy, 0, 0, keepAlive, false, false ); - } - - public static int Damage( Mobile m, Mobile from, int damage, bool ignoreArmor, int phys, int fire, int cold, int pois, int nrgy, int chaos, int direct, bool keepAlive, bool archer, bool deathStrike ) - { - if ( m == null || m.Deleted || !m.Alive || damage <= 0 ) - return 0; - - if ( phys == 0 && fire == 100 && cold == 0 && pois == 0 && nrgy == 0 ) - MeerMage.StopEffect( m, true ); - - if ( !Core.AOS ) - { - m.Damage( damage, from ); - return damage; - } - - Fix( ref phys ); - Fix( ref fire ); - Fix( ref cold ); - Fix( ref pois ); - Fix( ref nrgy ); - Fix( ref chaos ); - Fix( ref direct ); - - if ( Core.ML && chaos > 0 ) - { - switch ( Utility.Random( 5 ) ) - { - case 0: phys += chaos; break; - case 1: fire += chaos; break; - case 2: cold += chaos; break; - case 3: pois += chaos; break; - case 4: nrgy += chaos; break; - } - } - - BaseQuiver quiver = null; - - if ( archer && from != null ) - quiver = from.FindItemOnLayer( Layer.Cloak ) as BaseQuiver; - - int totalDamage; - - if ( !ignoreArmor ) - { - // Armor Ignore on OSI ignores all defenses, not just physical. - int resPhys = m.PhysicalResistance; - int resFire = m.FireResistance; - int resCold = m.ColdResistance; - int resPois = m.PoisonResistance; - int resNrgy = m.EnergyResistance; - - totalDamage = damage * phys * (100 - resPhys); - totalDamage += damage * fire * (100 - resFire); - totalDamage += damage * cold * (100 - resCold); - totalDamage += damage * pois * (100 - resPois); - totalDamage += damage * nrgy * (100 - resNrgy); - - totalDamage /= 10000; - - if ( Core.ML ) - { - totalDamage += damage * direct / 100; - - if ( quiver != null ) - totalDamage += totalDamage * quiver.DamageIncrease / 100; - } - - if ( totalDamage < 1 ) - totalDamage = 1; - } - else if ( Core.ML && m is PlayerMobile && from is PlayerMobile ) - { - if ( quiver != null ) - damage += damage * quiver.DamageIncrease / 100; - - if ( !deathStrike ) - totalDamage = Math.Min( damage, 35 ); // Direct Damage cap of 35 - else - totalDamage = Math.Min( damage, 70 ); // Direct Damage cap of 70 - } - else - { - totalDamage = damage; - - if ( Core.ML && quiver != null ) - totalDamage += totalDamage * quiver.DamageIncrease / 100; - } - - #region Dragon Barding - if ( (from == null || !from.Player) && m.Player && m.Mount is SwampDragon pet ) - { - if ( pet.HasBarding ) - { - int percent = (pet.BardingExceptional ? 20 : 10); - int absorbed = Scale( totalDamage, percent ); - - totalDamage -= absorbed; - pet.BardingHP -= absorbed; - - if ( pet.BardingHP < 0 ) - { - pet.HasBarding = false; - pet.BardingHP = 0; - - m.SendLocalizedMessage( 1053031 ); // Your dragon's barding has been destroyed! - } - } - } - #endregion - - if ( keepAlive && totalDamage > m.Hits ) - totalDamage = m.Hits; - - if ( from != null && !from.Deleted && from.Alive ) - { - int reflectPhys = AosAttributes.GetValue( m, AosAttribute.ReflectPhysical ); - - if ( reflectPhys != 0 ) - { - if ( from is ExodusMinion minion && minion.FieldActive || from is ExodusOverseer overseer && overseer.FieldActive ) - { - from.FixedParticles( 0x376A, 20, 10, 0x2530, EffectLayer.Waist ); - from.PlaySound( 0x2F4 ); - m.SendAsciiMessage( "Your weapon cannot penetrate the creature's magical barrier" ); - } - else - { - from.Damage( Scale( (damage * phys * (100 - (ignoreArmor ? 0 : m.PhysicalResistance))) / 10000, reflectPhys ), m ); - } - } - } - - m.Damage( totalDamage, from ); - return totalDamage; - } - - public static void Fix( ref int val ) - { - if ( val < 0 ) - val = 0; - } - - public static int Scale( int input, int percent ) - { - return (input * percent) / 100; - } - - public static int GetStatus( Mobile from, int index ) - { - switch ( index ) - { - // TODO: Account for buffs/debuffs - case 0: return from.GetMaxResistance( ResistanceType.Physical ); - case 1: return from.GetMaxResistance( ResistanceType.Fire ); - case 2: return from.GetMaxResistance( ResistanceType.Cold ); - case 3: return from.GetMaxResistance( ResistanceType.Poison ); - case 4: return from.GetMaxResistance( ResistanceType.Energy ); - case 5: return AosAttributes.GetValue( from, AosAttribute.DefendChance ); - case 6: return 45; - case 7: return AosAttributes.GetValue( from, AosAttribute.AttackChance ); - case 8: return AosAttributes.GetValue( from, AosAttribute.WeaponSpeed ); - case 9: return AosAttributes.GetValue( from, AosAttribute.WeaponDamage ); - case 10: return AosAttributes.GetValue( from, AosAttribute.LowerRegCost ); - case 11: return AosAttributes.GetValue( from, AosAttribute.SpellDamage ); - case 12: return AosAttributes.GetValue( from, AosAttribute.CastRecovery ); - case 13: return AosAttributes.GetValue( from, AosAttribute.CastSpeed ); - case 14: return AosAttributes.GetValue( from, AosAttribute.LowerManaCost ); - default: return 0; - } - } - } - - [Flags] - public enum AosAttribute - { - RegenHits=0x00000001, - RegenStam=0x00000002, - RegenMana=0x00000004, - DefendChance=0x00000008, - AttackChance=0x00000010, - BonusStr=0x00000020, - BonusDex=0x00000040, - BonusInt=0x00000080, - BonusHits=0x00000100, - BonusStam=0x00000200, - BonusMana=0x00000400, - WeaponDamage=0x00000800, - WeaponSpeed=0x00001000, - SpellDamage=0x00002000, - CastRecovery=0x00004000, - CastSpeed=0x00008000, - LowerManaCost=0x00010000, - LowerRegCost=0x00020000, - ReflectPhysical=0x00040000, - EnhancePotions=0x00080000, - Luck=0x00100000, - SpellChanneling=0x00200000, - NightSight=0x00400000, - IncreasedKarmaLoss=0x00800000 - } - - public sealed class AosAttributes : BaseAttributes - { - public AosAttributes( Item owner ) - : base( owner ) - { - } - - public AosAttributes( Item owner, AosAttributes other ) - : base( owner, other ) - { - } - - public AosAttributes( Item owner, GenericReader reader ) - : base( owner, reader ) - { - } - - public static int GetValue( Mobile m, AosAttribute attribute ) - { - if ( !Core.AOS ) - return 0; - - List items = m.Items; - int value = 0; - - for( int i = 0; i < items.Count; ++i ) - { - Item obj = items[i]; - - if ( obj is BaseWeapon weapon ) - { - AosAttributes attrs = weapon.Attributes; - - if ( attrs != null ) - value += attrs[attribute]; - - if ( attribute == AosAttribute.Luck ) - value += weapon.GetLuckBonus(); - } - else if ( obj is BaseArmor armor ) - { - AosAttributes attrs = armor.Attributes; - - if ( attrs != null ) - value += attrs[attribute]; - - if ( attribute == AosAttribute.Luck ) - value += armor.GetLuckBonus(); - } - else if ( obj is BaseJewel jewel ) - { - AosAttributes attrs = jewel.Attributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - else if ( obj is BaseClothing clothing ) - { - AosAttributes attrs = clothing.Attributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - else if ( obj is Spellbook spellbook ) - { - AosAttributes attrs = spellbook.Attributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - else if ( obj is BaseQuiver quiver ) - { - AosAttributes attrs = quiver.Attributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - else if ( obj is BaseTalisman talisman ) - { - AosAttributes attrs = talisman.Attributes; - - if (attrs != null) - value += attrs[attribute]; - } - } - - return value; - } - - public int this[AosAttribute attribute] - { - get => GetValue( (int)attribute ); - set => SetValue( (int)attribute, value ); - } - - public override string ToString() - { - return "..."; - } - - public void AddStatBonuses( Mobile to ) - { - int strBonus = BonusStr; - int dexBonus = BonusDex; - int intBonus = BonusInt; - - if ( strBonus != 0 || dexBonus != 0 || intBonus != 0 ) - { - string modName = Owner.Serial.ToString(); - - if ( strBonus != 0 ) - to.AddStatMod( new StatMod( StatType.Str, modName + "Str", strBonus, TimeSpan.Zero ) ); - - if ( dexBonus != 0 ) - to.AddStatMod( new StatMod( StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero ) ); - - if ( intBonus != 0 ) - to.AddStatMod( new StatMod( StatType.Int, modName + "Int", intBonus, TimeSpan.Zero ) ); - } - - to.CheckStatTimers(); - } - - public void RemoveStatBonuses( Mobile from ) - { - string modName = Owner.Serial.ToString(); - - from.RemoveStatMod( modName + "Str" ); - from.RemoveStatMod( modName + "Dex" ); - from.RemoveStatMod( modName + "Int" ); - - from.CheckStatTimers(); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int RegenHits { get => this[AosAttribute.RegenHits]; - set => this[AosAttribute.RegenHits] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int RegenStam { get => this[AosAttribute.RegenStam]; - set => this[AosAttribute.RegenStam] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int RegenMana { get => this[AosAttribute.RegenMana]; - set => this[AosAttribute.RegenMana] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DefendChance { get => this[AosAttribute.DefendChance]; - set => this[AosAttribute.DefendChance] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int AttackChance { get => this[AosAttribute.AttackChance]; - set => this[AosAttribute.AttackChance] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BonusStr { get => this[AosAttribute.BonusStr]; - set => this[AosAttribute.BonusStr] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BonusDex { get => this[AosAttribute.BonusDex]; - set => this[AosAttribute.BonusDex] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BonusInt { get => this[AosAttribute.BonusInt]; - set => this[AosAttribute.BonusInt] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BonusHits { get => this[AosAttribute.BonusHits]; - set => this[AosAttribute.BonusHits] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BonusStam { get => this[AosAttribute.BonusStam]; - set => this[AosAttribute.BonusStam] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BonusMana { get => this[AosAttribute.BonusMana]; - set => this[AosAttribute.BonusMana] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int WeaponDamage { get => this[AosAttribute.WeaponDamage]; - set => this[AosAttribute.WeaponDamage] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int WeaponSpeed { get => this[AosAttribute.WeaponSpeed]; - set => this[AosAttribute.WeaponSpeed] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SpellDamage { get => this[AosAttribute.SpellDamage]; - set => this[AosAttribute.SpellDamage] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int CastRecovery { get => this[AosAttribute.CastRecovery]; - set => this[AosAttribute.CastRecovery] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int CastSpeed { get => this[AosAttribute.CastSpeed]; - set => this[AosAttribute.CastSpeed] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int LowerManaCost { get => this[AosAttribute.LowerManaCost]; - set => this[AosAttribute.LowerManaCost] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int LowerRegCost { get => this[AosAttribute.LowerRegCost]; - set => this[AosAttribute.LowerRegCost] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ReflectPhysical { get => this[AosAttribute.ReflectPhysical]; - set => this[AosAttribute.ReflectPhysical] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int EnhancePotions { get => this[AosAttribute.EnhancePotions]; - set => this[AosAttribute.EnhancePotions] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Luck { get => this[AosAttribute.Luck]; - set => this[AosAttribute.Luck] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SpellChanneling { get => this[AosAttribute.SpellChanneling]; - set => this[AosAttribute.SpellChanneling] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int NightSight { get => this[AosAttribute.NightSight]; - set => this[AosAttribute.NightSight] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int IncreasedKarmaLoss { get => this[AosAttribute.IncreasedKarmaLoss]; - set => this[AosAttribute.IncreasedKarmaLoss] = value; - } - } - - [Flags] - public enum AosWeaponAttribute - { - LowerStatReq=0x00000001, - SelfRepair=0x00000002, - HitLeechHits=0x00000004, - HitLeechStam=0x00000008, - HitLeechMana=0x00000010, - HitLowerAttack=0x00000020, - HitLowerDefend=0x00000040, - HitMagicArrow=0x00000080, - HitHarm=0x00000100, - HitFireball=0x00000200, - HitLightning=0x00000400, - HitDispel=0x00000800, - HitColdArea=0x00001000, - HitFireArea=0x00002000, - HitPoisonArea=0x00004000, - HitEnergyArea=0x00008000, - HitPhysicalArea=0x00010000, - ResistPhysicalBonus=0x00020000, - ResistFireBonus=0x00040000, - ResistColdBonus=0x00080000, - ResistPoisonBonus=0x00100000, - ResistEnergyBonus=0x00200000, - UseBestSkill=0x00400000, - MageWeapon=0x00800000, - DurabilityBonus=0x01000000 - } - - public sealed class AosWeaponAttributes : BaseAttributes - { - public AosWeaponAttributes( Item owner ) - : base( owner ) - { - } - - public AosWeaponAttributes( Item owner, AosWeaponAttributes other ) - : base( owner, other ) - { - } - - public AosWeaponAttributes( Item owner, GenericReader reader ) - : base( owner, reader ) - { - } - - public static int GetValue( Mobile m, AosWeaponAttribute attribute ) - { - if ( !Core.AOS ) - return 0; - - List items = m.Items; - int value = 0; - - for( int i = 0; i < items.Count; ++i ) - { - Item obj = items[i]; - - if ( obj is BaseWeapon weapon ) - { - AosWeaponAttributes attrs = weapon.WeaponAttributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - else if ( obj is ElvenGlasses glasses ) - { - AosWeaponAttributes attrs = glasses.WeaponAttributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - } - - return value; - } - - public int this[AosWeaponAttribute attribute] - { - get => GetValue( (int)attribute ); - set => SetValue( (int)attribute, value ); - } - - public override string ToString() - { - return "..."; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int LowerStatReq { get => this[AosWeaponAttribute.LowerStatReq]; - set => this[AosWeaponAttribute.LowerStatReq] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SelfRepair { get => this[AosWeaponAttribute.SelfRepair]; - set => this[AosWeaponAttribute.SelfRepair] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitLeechHits { get => this[AosWeaponAttribute.HitLeechHits]; - set => this[AosWeaponAttribute.HitLeechHits] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitLeechStam { get => this[AosWeaponAttribute.HitLeechStam]; - set => this[AosWeaponAttribute.HitLeechStam] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitLeechMana { get => this[AosWeaponAttribute.HitLeechMana]; - set => this[AosWeaponAttribute.HitLeechMana] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitLowerAttack { get => this[AosWeaponAttribute.HitLowerAttack]; - set => this[AosWeaponAttribute.HitLowerAttack] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitLowerDefend { get => this[AosWeaponAttribute.HitLowerDefend]; - set => this[AosWeaponAttribute.HitLowerDefend] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitMagicArrow { get => this[AosWeaponAttribute.HitMagicArrow]; - set => this[AosWeaponAttribute.HitMagicArrow] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitHarm { get => this[AosWeaponAttribute.HitHarm]; - set => this[AosWeaponAttribute.HitHarm] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitFireball { get => this[AosWeaponAttribute.HitFireball]; - set => this[AosWeaponAttribute.HitFireball] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitLightning { get => this[AosWeaponAttribute.HitLightning]; - set => this[AosWeaponAttribute.HitLightning] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitDispel { get => this[AosWeaponAttribute.HitDispel]; - set => this[AosWeaponAttribute.HitDispel] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitColdArea { get => this[AosWeaponAttribute.HitColdArea]; - set => this[AosWeaponAttribute.HitColdArea] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitFireArea { get => this[AosWeaponAttribute.HitFireArea]; - set => this[AosWeaponAttribute.HitFireArea] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitPoisonArea { get => this[AosWeaponAttribute.HitPoisonArea]; - set => this[AosWeaponAttribute.HitPoisonArea] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitEnergyArea { get => this[AosWeaponAttribute.HitEnergyArea]; - set => this[AosWeaponAttribute.HitEnergyArea] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int HitPhysicalArea { get => this[AosWeaponAttribute.HitPhysicalArea]; - set => this[AosWeaponAttribute.HitPhysicalArea] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ResistPhysicalBonus { get => this[AosWeaponAttribute.ResistPhysicalBonus]; - set => this[AosWeaponAttribute.ResistPhysicalBonus] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ResistFireBonus { get => this[AosWeaponAttribute.ResistFireBonus]; - set => this[AosWeaponAttribute.ResistFireBonus] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ResistColdBonus { get => this[AosWeaponAttribute.ResistColdBonus]; - set => this[AosWeaponAttribute.ResistColdBonus] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ResistPoisonBonus { get => this[AosWeaponAttribute.ResistPoisonBonus]; - set => this[AosWeaponAttribute.ResistPoisonBonus] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ResistEnergyBonus { get => this[AosWeaponAttribute.ResistEnergyBonus]; - set => this[AosWeaponAttribute.ResistEnergyBonus] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int UseBestSkill { get => this[AosWeaponAttribute.UseBestSkill]; - set => this[AosWeaponAttribute.UseBestSkill] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MageWeapon { get => this[AosWeaponAttribute.MageWeapon]; - set => this[AosWeaponAttribute.MageWeapon] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DurabilityBonus { get => this[AosWeaponAttribute.DurabilityBonus]; - set => this[AosWeaponAttribute.DurabilityBonus] = value; - } - } - - [Flags] - public enum AosArmorAttribute - { - LowerStatReq=0x00000001, - SelfRepair=0x00000002, - MageArmor=0x00000004, - DurabilityBonus=0x00000008 - } - - public sealed class AosArmorAttributes : BaseAttributes - { - public AosArmorAttributes( Item owner ) - : base( owner ) - { - } - - public AosArmorAttributes( Item owner, GenericReader reader ) - : base( owner, reader ) - { - } - - public AosArmorAttributes( Item owner, AosArmorAttributes other ) - : base( owner, other ) - { - } - - public static int GetValue( Mobile m, AosArmorAttribute attribute ) - { - if ( !Core.AOS ) - return 0; - - List items = m.Items; - int value = 0; - - for( int i = 0; i < items.Count; ++i ) - { - Item obj = items[i]; - - if ( obj is BaseArmor armor ) - { - AosArmorAttributes attrs = armor.ArmorAttributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - else if ( obj is BaseClothing clothing ) - { - AosArmorAttributes attrs = clothing.ClothingAttributes; - - if ( attrs != null ) - value += attrs[attribute]; - } - } - - return value; - } - - public int this[AosArmorAttribute attribute] - { - get => GetValue( (int)attribute ); - set => SetValue( (int)attribute, value ); - } - - public override string ToString() - { - return "..."; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int LowerStatReq { get => this[AosArmorAttribute.LowerStatReq]; - set => this[AosArmorAttribute.LowerStatReq] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SelfRepair { get => this[AosArmorAttribute.SelfRepair]; - set => this[AosArmorAttribute.SelfRepair] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MageArmor { get => this[AosArmorAttribute.MageArmor]; - set => this[AosArmorAttribute.MageArmor] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DurabilityBonus { get => this[AosArmorAttribute.DurabilityBonus]; - set => this[AosArmorAttribute.DurabilityBonus] = value; - } - } - - public sealed class AosSkillBonuses : BaseAttributes - { - private List m_Mods; - - public AosSkillBonuses( Item owner ) - : base( owner ) - { - } - - public AosSkillBonuses( Item owner, GenericReader reader ) - : base( owner, reader ) - { - } - - public AosSkillBonuses( Item owner, AosSkillBonuses other ) - : base( owner, other ) - { - } - - public void GetProperties( ObjectPropertyList list ) - { - for( int i = 0; i < 5; ++i ) - { - SkillName skill; - double bonus; - - if ( !GetValues( i, out skill, out bonus ) ) - continue; - - list.Add( 1060451 + i, "#{0}\t{1}", GetLabel( skill ), bonus ); - } - } - - public static int GetLabel( SkillName skill ) - { - switch ( skill ) - { - case SkillName.EvalInt: return 1002070; // Evaluate Intelligence - case SkillName.Forensics: return 1002078; // Forensic Evaluation - case SkillName.Lockpicking: return 1002097; // Lockpicking - default: return 1044060 + (int)skill; - } - } - - public void AddTo( Mobile m ) - { - Remove(); - - for( int i = 0; i < 5; ++i ) - { - if ( !GetValues( i, out SkillName skill, out double bonus ) ) - continue; - - if ( m_Mods == null ) - m_Mods = new List(); - - SkillMod sk = new DefaultSkillMod( skill, true, bonus ); - sk.ObeyCap = true; - m.AddSkillMod( sk ); - m_Mods.Add( sk ); - } - } - - public void Remove() - { - if ( m_Mods == null ) - return; - - for( int i = 0; i < m_Mods.Count; ++i ) { - - Mobile m = m_Mods[i].Owner; - m_Mods[i].Remove(); - - if ( Core.ML ) - CheckCancelMorph ( m ); - } - m_Mods = null; - } - - public bool GetValues( int index, out SkillName skill, out double bonus ) - { - int v = GetValue( 1 << index ); - int vSkill = 0; - int vBonus = 0; - - for( int i = 0; i < 16; ++i ) - { - vSkill <<= 1; - vSkill |= (v & 1); - v >>= 1; - - vBonus <<= 1; - vBonus |= (v & 1); - v >>= 1; - } - - skill = (SkillName)vSkill; - bonus = (double)vBonus / 10; - - return (bonus != 0); - } - - public void SetValues( int index, SkillName skill, double bonus ) - { - int v = 0; - int vSkill = (int)skill; - int vBonus = (int)(bonus * 10); - - for( int i = 0; i < 16; ++i ) - { - v <<= 1; - v |= (vBonus & 1); - vBonus >>= 1; - - v <<= 1; - v |= (vSkill & 1); - vSkill >>= 1; - } - - SetValue( 1 << index, v ); - } - - public SkillName GetSkill( int index ) - { - SkillName skill; - double bonus; - - GetValues( index, out skill, out bonus ); - - return skill; - } - - public void SetSkill( int index, SkillName skill ) - { - SetValues( index, skill, GetBonus( index ) ); - } - - public double GetBonus( int index ) - { - SkillName skill; - double bonus; - - GetValues( index, out skill, out bonus ); - - return bonus; - } - - public void SetBonus( int index, double bonus ) - { - SetValues( index, GetSkill( index ), bonus ); - } - - public override string ToString() - { - return "..."; - } - - public void CheckCancelMorph ( Mobile m ) - { - if ( m == null ) - return; - - double minSkill, maxSkill; - - AnimalFormContext acontext = AnimalForm.GetContext( m ); - TransformContext context = TransformationSpellHelper.GetContext( m ); - - if ( context != null ) { - Spell spell = context.Spell as Spell; - spell.GetCastSkills ( out minSkill, out maxSkill ); - if ( m.Skills[spell.CastSkill].Value < minSkill ) - TransformationSpellHelper.RemoveContext( m, context, true ); - } - if ( acontext != null ) { - int i; - for ( i = 0; i < AnimalForm.Entries.Length; ++i ) - if ( AnimalForm.Entries[i].Type == acontext.Type ) - break; - if ( m.Skills[SkillName.Ninjitsu].Value < AnimalForm.Entries[i].ReqSkill ) - AnimalForm.RemoveContext( m, true ); - } - if ( !m.CanBeginAction ( typeof ( PolymorphSpell ) ) && m.Skills[SkillName.Magery].Value < 66.1 ) { - m.BodyMod = 0; - m.HueMod = -1; - m.NameMod = null; - m.EndAction( typeof( PolymorphSpell ) ); - BaseArmor.ValidateMobile( m ); - BaseClothing.ValidateMobile( m ); - } - if ( !m.CanBeginAction ( typeof ( IncognitoSpell ) ) && m.Skills[SkillName.Magery].Value < 38.1 ) { - if ( m is PlayerMobile mobile ) - mobile.SetHairMods( -1, -1 ); - m.BodyMod = 0; - m.HueMod = -1; - m.NameMod = null; - m.EndAction( typeof( IncognitoSpell ) ); - BaseArmor.ValidateMobile( m ); - BaseClothing.ValidateMobile( m ); - BuffInfo.RemoveBuff( m, BuffIcon.Incognito ); - } - } - - - [CommandProperty( AccessLevel.GameMaster )] - public double Skill_1_Value { get => GetBonus( 0 ); - set => SetBonus( 0, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill_1_Name { get => GetSkill( 0 ); - set => SetSkill( 0, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public double Skill_2_Value { get => GetBonus( 1 ); - set => SetBonus( 1, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill_2_Name { get => GetSkill( 1 ); - set => SetSkill( 1, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public double Skill_3_Value { get => GetBonus( 2 ); - set => SetBonus( 2, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill_3_Name { get => GetSkill( 2 ); - set => SetSkill( 2, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public double Skill_4_Value { get => GetBonus( 3 ); - set => SetBonus( 3, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill_4_Name { get => GetSkill( 3 ); - set => SetSkill( 3, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public double Skill_5_Value { get => GetBonus( 4 ); - set => SetBonus( 4, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public SkillName Skill_5_Name { get => GetSkill( 4 ); - set => SetSkill( 4, value ); - } - } - - [Flags] - public enum AosElementAttribute - { - Physical=0x00000001, - Fire=0x00000002, - Cold=0x00000004, - Poison=0x00000008, - Energy=0x00000010, - Chaos=0x00000020, - Direct=0x00000040 - } - - public sealed class AosElementAttributes : BaseAttributes - { - public AosElementAttributes( Item owner ) - : base( owner ) - { - } - - public AosElementAttributes( Item owner, AosElementAttributes other ) - : base( owner, other ) - { - } - - public AosElementAttributes( Item owner, GenericReader reader ) - : base( owner, reader ) - { - } - - public int this[AosElementAttribute attribute] - { - get => GetValue( (int)attribute ); - set => SetValue( (int)attribute, value ); - } - - public override string ToString() - { - return "..."; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Physical { get => this[AosElementAttribute.Physical]; - set => this[AosElementAttribute.Physical] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Fire { get => this[AosElementAttribute.Fire]; - set => this[AosElementAttribute.Fire] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Cold { get => this[AosElementAttribute.Cold]; - set => this[AosElementAttribute.Cold] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Poison { get => this[AosElementAttribute.Poison]; - set => this[AosElementAttribute.Poison] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Energy { get => this[AosElementAttribute.Energy]; - set => this[AosElementAttribute.Energy] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Chaos { get => this[AosElementAttribute.Chaos]; - set => this[AosElementAttribute.Chaos] = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Direct { get => this[AosElementAttribute.Direct]; - set => this[AosElementAttribute.Direct] = value; - } - } - - [PropertyObject] - public abstract class BaseAttributes - { - private uint m_Names; - private int[] m_Values; - - private static int[] m_Empty = new int[0]; - - public bool IsEmpty => (m_Names == 0); - public Item Owner { get; } - - public BaseAttributes( Item owner ) - { - Owner = owner; - m_Values = m_Empty; - } - - public BaseAttributes( Item owner, BaseAttributes other ) - { - Owner = owner; - m_Values = new int[other.m_Values.Length]; - other.m_Values.CopyTo( m_Values, 0 ); - m_Names = other.m_Names; - } - - public BaseAttributes( Item owner, GenericReader reader ) - { - Owner = owner; - - int version = reader.ReadByte(); - - switch( version ) - { - case 1: - { - m_Names = reader.ReadUInt(); - m_Values = new int[reader.ReadEncodedInt()]; - - for( int i = 0; i < m_Values.Length; ++i ) - m_Values[i] = reader.ReadEncodedInt(); - - break; - } - case 0: - { - m_Names = reader.ReadUInt(); - m_Values = new int[reader.ReadInt()]; - - for( int i = 0; i < m_Values.Length; ++i ) - m_Values[i] = reader.ReadInt(); - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (byte)1 ); // version; - - writer.Write( (uint)m_Names ); - writer.WriteEncodedInt( (int)m_Values.Length ); - - for( int i = 0; i < m_Values.Length; ++i ) - writer.WriteEncodedInt( (int)m_Values[i] ); - } - - public int GetValue( int bitmask ) - { - if ( !Core.AOS ) - return 0; - - uint mask = (uint)bitmask; - - if ( (m_Names & mask) == 0 ) - return 0; - - int index = GetIndex( mask ); - - if ( index >= 0 && index < m_Values.Length ) - return m_Values[index]; - - return 0; - } - - public void SetValue( int bitmask, int value ) - { - if ( (bitmask == (int)AosWeaponAttribute.DurabilityBonus) && (this is AosWeaponAttributes) ) - { - if ( Owner is BaseWeapon weapon ) - weapon.UnscaleDurability(); - } - else if ( (bitmask == (int)AosArmorAttribute.DurabilityBonus) && (this is AosArmorAttributes) ) - { - if ( Owner is BaseArmor armor ) - armor.UnscaleDurability(); - else if ( Owner is BaseClothing clothing ) - clothing.UnscaleDurability(); - } - - uint mask = (uint)bitmask; - - if ( value != 0 ) - { - if ( (m_Names & mask) != 0 ) - { - int index = GetIndex( mask ); - - if ( index >= 0 && index < m_Values.Length ) - m_Values[index] = value; - } - else - { - int index = GetIndex( mask ); - - if ( index >= 0 && index <= m_Values.Length ) - { - int[] old = m_Values; - m_Values = new int[old.Length + 1]; - - for( int i = 0; i < index; ++i ) - m_Values[i] = old[i]; - - m_Values[index] = value; - - for( int i = index; i < old.Length; ++i ) - m_Values[i + 1] = old[i]; - - m_Names |= mask; - } - } - } - else if ( (m_Names & mask) != 0 ) - { - int index = GetIndex( mask ); - - if ( index >= 0 && index < m_Values.Length ) - { - m_Names &= ~mask; - - if ( m_Values.Length == 1 ) - { - m_Values = m_Empty; - } - else - { - int[] old = m_Values; - m_Values = new int[old.Length - 1]; - - for( int i = 0; i < index; ++i ) - m_Values[i] = old[i]; - - for( int i = index + 1; i < old.Length; ++i ) - m_Values[i - 1] = old[i]; - } - } - } - - if ( (bitmask == (int)AosWeaponAttribute.DurabilityBonus) && (this is AosWeaponAttributes) ) - { - if ( Owner is BaseWeapon weapon ) - weapon.ScaleDurability(); - } - else if ( (bitmask == (int)AosArmorAttribute.DurabilityBonus) && (this is AosArmorAttributes) ) - { - if ( Owner is BaseArmor armor ) - armor.ScaleDurability(); - else if ( Owner is BaseClothing clothing ) - clothing.ScaleDurability(); - } - - if ( Owner.Parent is Mobile m ) - { - m.CheckStatTimers(); - m.UpdateResistances(); - m.Delta( MobileDelta.Stat | MobileDelta.WeaponDamage | MobileDelta.Hits | MobileDelta.Stam | MobileDelta.Mana ); - - if ( this is AosSkillBonuses ) - { - ((AosSkillBonuses)this).Remove(); - ((AosSkillBonuses)this).AddTo( m ); - } - } - - Owner.InvalidateProperties(); - } - - private int GetIndex( uint mask ) - { - int index = 0; - uint ourNames = m_Names; - uint currentBit = 1; - - while( currentBit != mask ) - { - if ( (ourNames & currentBit) != 0 ) - ++index; - - if ( currentBit == 0x80000000 ) - return -1; - - currentBit <<= 1; - } - - return index; - } - } -} + public class AOS + { + public static void DisableStatInfluences() + { + for (int i = 0; i < SkillInfo.Table.Length; ++i) + { + SkillInfo info = SkillInfo.Table[i]; + + info.StrScale = 0.0; + info.DexScale = 0.0; + info.IntScale = 0.0; + info.StatTotal = 0.0; + } + } + + public static int Damage(Mobile m, int damage, bool ignoreArmor, int phys, int fire, int cold, int pois, int nrgy) + { + return Damage(m, null, damage, ignoreArmor, phys, fire, cold, pois, nrgy); + } + + public static int Damage(Mobile m, int damage, int phys, int fire, int cold, int pois, int nrgy) + { + return Damage(m, null, damage, phys, fire, cold, pois, nrgy); + } + + public static int Damage(Mobile m, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy) + { + return Damage(m, from, damage, false, phys, fire, cold, pois, nrgy, 0, 0, false, false, false); + } + + public static int Damage(Mobile m, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy, + int chaos) + { + return Damage(m, from, damage, false, phys, fire, cold, pois, nrgy, chaos, 0, false, false, false); + } + + public static int Damage(Mobile m, Mobile from, int damage, bool ignoreArmor, int phys, int fire, int cold, int pois, + int nrgy) + { + return Damage(m, from, damage, ignoreArmor, phys, fire, cold, pois, nrgy, 0, 0, false, false, false); + } + + public static int Damage(Mobile m, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy, + bool keepAlive) + { + return Damage(m, from, damage, false, phys, fire, cold, pois, nrgy, 0, 0, keepAlive, false, false); + } + + public static int Damage(Mobile m, Mobile from, int damage, bool ignoreArmor, int phys, int fire, int cold, int pois, + int nrgy, int chaos, int direct, bool keepAlive, bool archer, bool deathStrike) + { + if (m == null || m.Deleted || !m.Alive || damage <= 0) + return 0; + + if (phys == 0 && fire == 100 && cold == 0 && pois == 0 && nrgy == 0) + MeerMage.StopEffect(m, true); + + if (!Core.AOS) + { + m.Damage(damage, from); + return damage; + } + + Fix(ref phys); + Fix(ref fire); + Fix(ref cold); + Fix(ref pois); + Fix(ref nrgy); + Fix(ref chaos); + Fix(ref direct); + + if (Core.ML && chaos > 0) + switch (Utility.Random(5)) + { + case 0: + phys += chaos; + break; + case 1: + fire += chaos; + break; + case 2: + cold += chaos; + break; + case 3: + pois += chaos; + break; + case 4: + nrgy += chaos; + break; + } + + BaseQuiver quiver = null; + + if (archer && from != null) + quiver = from.FindItemOnLayer(Layer.Cloak) as BaseQuiver; + + int totalDamage; + + if (!ignoreArmor) + { + // Armor Ignore on OSI ignores all defenses, not just physical. + int resPhys = m.PhysicalResistance; + int resFire = m.FireResistance; + int resCold = m.ColdResistance; + int resPois = m.PoisonResistance; + int resNrgy = m.EnergyResistance; + + totalDamage = damage * phys * (100 - resPhys); + totalDamage += damage * fire * (100 - resFire); + totalDamage += damage * cold * (100 - resCold); + totalDamage += damage * pois * (100 - resPois); + totalDamage += damage * nrgy * (100 - resNrgy); + + totalDamage /= 10000; + + if (Core.ML) + { + totalDamage += damage * direct / 100; + + if (quiver != null) + totalDamage += totalDamage * quiver.DamageIncrease / 100; + } + + if (totalDamage < 1) + totalDamage = 1; + } + else if (Core.ML && m is PlayerMobile && from is PlayerMobile) + { + if (quiver != null) + damage += damage * quiver.DamageIncrease / 100; + + if (!deathStrike) + totalDamage = Math.Min(damage, 35); // Direct Damage cap of 35 + else + totalDamage = Math.Min(damage, 70); // Direct Damage cap of 70 + } + else + { + totalDamage = damage; + + if (Core.ML && quiver != null) + totalDamage += totalDamage * quiver.DamageIncrease / 100; + } + + #region Dragon Barding + + if ((from == null || !from.Player) && m.Player && m.Mount is SwampDragon pet) + if (pet.HasBarding) + { + int percent = pet.BardingExceptional ? 20 : 10; + int absorbed = Scale(totalDamage, percent); + + totalDamage -= absorbed; + pet.BardingHP -= absorbed; + + if (pet.BardingHP < 0) + { + pet.HasBarding = false; + pet.BardingHP = 0; + + m.SendLocalizedMessage(1053031); // Your dragon's barding has been destroyed! + } + } + + #endregion + + if (keepAlive && totalDamage > m.Hits) + totalDamage = m.Hits; + + if (from != null && !from.Deleted && from.Alive) + { + int reflectPhys = AosAttributes.GetValue(m, AosAttribute.ReflectPhysical); + + if (reflectPhys != 0) + { + if (from is ExodusMinion minion && minion.FieldActive || + from is ExodusOverseer overseer && overseer.FieldActive) + { + from.FixedParticles(0x376A, 20, 10, 0x2530, EffectLayer.Waist); + from.PlaySound(0x2F4); + m.SendAsciiMessage("Your weapon cannot penetrate the creature's magical barrier"); + } + else + { + from.Damage( + Scale(damage * phys * (100 - (ignoreArmor ? 0 : m.PhysicalResistance)) / 10000, reflectPhys), m); + } + } + } + + m.Damage(totalDamage, from); + return totalDamage; + } + + public static void Fix(ref int val) + { + if (val < 0) + val = 0; + } + + public static int Scale(int input, int percent) + { + return input * percent / 100; + } + + public static int GetStatus(Mobile from, int index) + { + switch (index) + { + // TODO: Account for buffs/debuffs + case 0: return from.GetMaxResistance(ResistanceType.Physical); + case 1: return from.GetMaxResistance(ResistanceType.Fire); + case 2: return from.GetMaxResistance(ResistanceType.Cold); + case 3: return from.GetMaxResistance(ResistanceType.Poison); + case 4: return from.GetMaxResistance(ResistanceType.Energy); + case 5: return AosAttributes.GetValue(from, AosAttribute.DefendChance); + case 6: return 45; + case 7: return AosAttributes.GetValue(from, AosAttribute.AttackChance); + case 8: return AosAttributes.GetValue(from, AosAttribute.WeaponSpeed); + case 9: return AosAttributes.GetValue(from, AosAttribute.WeaponDamage); + case 10: return AosAttributes.GetValue(from, AosAttribute.LowerRegCost); + case 11: return AosAttributes.GetValue(from, AosAttribute.SpellDamage); + case 12: return AosAttributes.GetValue(from, AosAttribute.CastRecovery); + case 13: return AosAttributes.GetValue(from, AosAttribute.CastSpeed); + case 14: return AosAttributes.GetValue(from, AosAttribute.LowerManaCost); + default: return 0; + } + } + } + + [Flags] + public enum AosAttribute + { + RegenHits = 0x00000001, + RegenStam = 0x00000002, + RegenMana = 0x00000004, + DefendChance = 0x00000008, + AttackChance = 0x00000010, + BonusStr = 0x00000020, + BonusDex = 0x00000040, + BonusInt = 0x00000080, + BonusHits = 0x00000100, + BonusStam = 0x00000200, + BonusMana = 0x00000400, + WeaponDamage = 0x00000800, + WeaponSpeed = 0x00001000, + SpellDamage = 0x00002000, + CastRecovery = 0x00004000, + CastSpeed = 0x00008000, + LowerManaCost = 0x00010000, + LowerRegCost = 0x00020000, + ReflectPhysical = 0x00040000, + EnhancePotions = 0x00080000, + Luck = 0x00100000, + SpellChanneling = 0x00200000, + NightSight = 0x00400000, + IncreasedKarmaLoss = 0x00800000 + } + + public sealed class AosAttributes : BaseAttributes + { + public AosAttributes(Item owner) + : base(owner) + { + } + + public AosAttributes(Item owner, AosAttributes other) + : base(owner, other) + { + } + + public AosAttributes(Item owner, GenericReader reader) + : base(owner, reader) + { + } + + public int this[AosAttribute attribute] + { + get => GetValue((int)attribute); + set => SetValue((int)attribute, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int RegenHits + { + get => this[AosAttribute.RegenHits]; + set => this[AosAttribute.RegenHits] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int RegenStam + { + get => this[AosAttribute.RegenStam]; + set => this[AosAttribute.RegenStam] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int RegenMana + { + get => this[AosAttribute.RegenMana]; + set => this[AosAttribute.RegenMana] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DefendChance + { + get => this[AosAttribute.DefendChance]; + set => this[AosAttribute.DefendChance] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int AttackChance + { + get => this[AosAttribute.AttackChance]; + set => this[AosAttribute.AttackChance] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BonusStr + { + get => this[AosAttribute.BonusStr]; + set => this[AosAttribute.BonusStr] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BonusDex + { + get => this[AosAttribute.BonusDex]; + set => this[AosAttribute.BonusDex] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BonusInt + { + get => this[AosAttribute.BonusInt]; + set => this[AosAttribute.BonusInt] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BonusHits + { + get => this[AosAttribute.BonusHits]; + set => this[AosAttribute.BonusHits] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BonusStam + { + get => this[AosAttribute.BonusStam]; + set => this[AosAttribute.BonusStam] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BonusMana + { + get => this[AosAttribute.BonusMana]; + set => this[AosAttribute.BonusMana] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int WeaponDamage + { + get => this[AosAttribute.WeaponDamage]; + set => this[AosAttribute.WeaponDamage] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int WeaponSpeed + { + get => this[AosAttribute.WeaponSpeed]; + set => this[AosAttribute.WeaponSpeed] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SpellDamage + { + get => this[AosAttribute.SpellDamage]; + set => this[AosAttribute.SpellDamage] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int CastRecovery + { + get => this[AosAttribute.CastRecovery]; + set => this[AosAttribute.CastRecovery] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int CastSpeed + { + get => this[AosAttribute.CastSpeed]; + set => this[AosAttribute.CastSpeed] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int LowerManaCost + { + get => this[AosAttribute.LowerManaCost]; + set => this[AosAttribute.LowerManaCost] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int LowerRegCost + { + get => this[AosAttribute.LowerRegCost]; + set => this[AosAttribute.LowerRegCost] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ReflectPhysical + { + get => this[AosAttribute.ReflectPhysical]; + set => this[AosAttribute.ReflectPhysical] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int EnhancePotions + { + get => this[AosAttribute.EnhancePotions]; + set => this[AosAttribute.EnhancePotions] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Luck + { + get => this[AosAttribute.Luck]; + set => this[AosAttribute.Luck] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SpellChanneling + { + get => this[AosAttribute.SpellChanneling]; + set => this[AosAttribute.SpellChanneling] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int NightSight + { + get => this[AosAttribute.NightSight]; + set => this[AosAttribute.NightSight] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int IncreasedKarmaLoss + { + get => this[AosAttribute.IncreasedKarmaLoss]; + set => this[AosAttribute.IncreasedKarmaLoss] = value; + } + + public static int GetValue(Mobile m, AosAttribute attribute) + { + if (!Core.AOS) + return 0; + + List items = m.Items; + int value = 0; + + for (int i = 0; i < items.Count; ++i) + { + Item obj = items[i]; + + if (obj is BaseWeapon weapon) + { + AosAttributes attrs = weapon.Attributes; + + if (attrs != null) + value += attrs[attribute]; + + if (attribute == AosAttribute.Luck) + value += weapon.GetLuckBonus(); + } + else if (obj is BaseArmor armor) + { + AosAttributes attrs = armor.Attributes; + + if (attrs != null) + value += attrs[attribute]; + + if (attribute == AosAttribute.Luck) + value += armor.GetLuckBonus(); + } + else if (obj is BaseJewel jewel) + { + AosAttributes attrs = jewel.Attributes; + + if (attrs != null) + value += attrs[attribute]; + } + else if (obj is BaseClothing clothing) + { + AosAttributes attrs = clothing.Attributes; + + if (attrs != null) + value += attrs[attribute]; + } + else if (obj is Spellbook spellbook) + { + AosAttributes attrs = spellbook.Attributes; + + if (attrs != null) + value += attrs[attribute]; + } + else if (obj is BaseQuiver quiver) + { + AosAttributes attrs = quiver.Attributes; + + if (attrs != null) + value += attrs[attribute]; + } + else if (obj is BaseTalisman talisman) + { + AosAttributes attrs = talisman.Attributes; + + if (attrs != null) + value += attrs[attribute]; + } + } + + return value; + } + + public override string ToString() + { + return "..."; + } + + public void AddStatBonuses(Mobile to) + { + int strBonus = BonusStr; + int dexBonus = BonusDex; + int intBonus = BonusInt; + + if (strBonus != 0 || dexBonus != 0 || intBonus != 0) + { + string modName = Owner.Serial.ToString(); + + if (strBonus != 0) + to.AddStatMod(new StatMod(StatType.Str, modName + "Str", strBonus, TimeSpan.Zero)); + + if (dexBonus != 0) + to.AddStatMod(new StatMod(StatType.Dex, modName + "Dex", dexBonus, TimeSpan.Zero)); + + if (intBonus != 0) + to.AddStatMod(new StatMod(StatType.Int, modName + "Int", intBonus, TimeSpan.Zero)); + } + + to.CheckStatTimers(); + } + + public void RemoveStatBonuses(Mobile from) + { + string modName = Owner.Serial.ToString(); + + from.RemoveStatMod(modName + "Str"); + from.RemoveStatMod(modName + "Dex"); + from.RemoveStatMod(modName + "Int"); + + from.CheckStatTimers(); + } + } + + [Flags] + public enum AosWeaponAttribute + { + LowerStatReq = 0x00000001, + SelfRepair = 0x00000002, + HitLeechHits = 0x00000004, + HitLeechStam = 0x00000008, + HitLeechMana = 0x00000010, + HitLowerAttack = 0x00000020, + HitLowerDefend = 0x00000040, + HitMagicArrow = 0x00000080, + HitHarm = 0x00000100, + HitFireball = 0x00000200, + HitLightning = 0x00000400, + HitDispel = 0x00000800, + HitColdArea = 0x00001000, + HitFireArea = 0x00002000, + HitPoisonArea = 0x00004000, + HitEnergyArea = 0x00008000, + HitPhysicalArea = 0x00010000, + ResistPhysicalBonus = 0x00020000, + ResistFireBonus = 0x00040000, + ResistColdBonus = 0x00080000, + ResistPoisonBonus = 0x00100000, + ResistEnergyBonus = 0x00200000, + UseBestSkill = 0x00400000, + MageWeapon = 0x00800000, + DurabilityBonus = 0x01000000 + } + + public sealed class AosWeaponAttributes : BaseAttributes + { + public AosWeaponAttributes(Item owner) + : base(owner) + { + } + + public AosWeaponAttributes(Item owner, AosWeaponAttributes other) + : base(owner, other) + { + } + + public AosWeaponAttributes(Item owner, GenericReader reader) + : base(owner, reader) + { + } + + public int this[AosWeaponAttribute attribute] + { + get => GetValue((int)attribute); + set => SetValue((int)attribute, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int LowerStatReq + { + get => this[AosWeaponAttribute.LowerStatReq]; + set => this[AosWeaponAttribute.LowerStatReq] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SelfRepair + { + get => this[AosWeaponAttribute.SelfRepair]; + set => this[AosWeaponAttribute.SelfRepair] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitLeechHits + { + get => this[AosWeaponAttribute.HitLeechHits]; + set => this[AosWeaponAttribute.HitLeechHits] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitLeechStam + { + get => this[AosWeaponAttribute.HitLeechStam]; + set => this[AosWeaponAttribute.HitLeechStam] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitLeechMana + { + get => this[AosWeaponAttribute.HitLeechMana]; + set => this[AosWeaponAttribute.HitLeechMana] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitLowerAttack + { + get => this[AosWeaponAttribute.HitLowerAttack]; + set => this[AosWeaponAttribute.HitLowerAttack] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitLowerDefend + { + get => this[AosWeaponAttribute.HitLowerDefend]; + set => this[AosWeaponAttribute.HitLowerDefend] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitMagicArrow + { + get => this[AosWeaponAttribute.HitMagicArrow]; + set => this[AosWeaponAttribute.HitMagicArrow] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitHarm + { + get => this[AosWeaponAttribute.HitHarm]; + set => this[AosWeaponAttribute.HitHarm] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitFireball + { + get => this[AosWeaponAttribute.HitFireball]; + set => this[AosWeaponAttribute.HitFireball] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitLightning + { + get => this[AosWeaponAttribute.HitLightning]; + set => this[AosWeaponAttribute.HitLightning] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitDispel + { + get => this[AosWeaponAttribute.HitDispel]; + set => this[AosWeaponAttribute.HitDispel] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitColdArea + { + get => this[AosWeaponAttribute.HitColdArea]; + set => this[AosWeaponAttribute.HitColdArea] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitFireArea + { + get => this[AosWeaponAttribute.HitFireArea]; + set => this[AosWeaponAttribute.HitFireArea] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitPoisonArea + { + get => this[AosWeaponAttribute.HitPoisonArea]; + set => this[AosWeaponAttribute.HitPoisonArea] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitEnergyArea + { + get => this[AosWeaponAttribute.HitEnergyArea]; + set => this[AosWeaponAttribute.HitEnergyArea] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int HitPhysicalArea + { + get => this[AosWeaponAttribute.HitPhysicalArea]; + set => this[AosWeaponAttribute.HitPhysicalArea] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ResistPhysicalBonus + { + get => this[AosWeaponAttribute.ResistPhysicalBonus]; + set => this[AosWeaponAttribute.ResistPhysicalBonus] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ResistFireBonus + { + get => this[AosWeaponAttribute.ResistFireBonus]; + set => this[AosWeaponAttribute.ResistFireBonus] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ResistColdBonus + { + get => this[AosWeaponAttribute.ResistColdBonus]; + set => this[AosWeaponAttribute.ResistColdBonus] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ResistPoisonBonus + { + get => this[AosWeaponAttribute.ResistPoisonBonus]; + set => this[AosWeaponAttribute.ResistPoisonBonus] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ResistEnergyBonus + { + get => this[AosWeaponAttribute.ResistEnergyBonus]; + set => this[AosWeaponAttribute.ResistEnergyBonus] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int UseBestSkill + { + get => this[AosWeaponAttribute.UseBestSkill]; + set => this[AosWeaponAttribute.UseBestSkill] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MageWeapon + { + get => this[AosWeaponAttribute.MageWeapon]; + set => this[AosWeaponAttribute.MageWeapon] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DurabilityBonus + { + get => this[AosWeaponAttribute.DurabilityBonus]; + set => this[AosWeaponAttribute.DurabilityBonus] = value; + } + + public static int GetValue(Mobile m, AosWeaponAttribute attribute) + { + if (!Core.AOS) + return 0; + + List items = m.Items; + int value = 0; + + for (int i = 0; i < items.Count; ++i) + { + Item obj = items[i]; + + if (obj is BaseWeapon weapon) + { + AosWeaponAttributes attrs = weapon.WeaponAttributes; + + if (attrs != null) + value += attrs[attribute]; + } + else if (obj is ElvenGlasses glasses) + { + AosWeaponAttributes attrs = glasses.WeaponAttributes; + + if (attrs != null) + value += attrs[attribute]; + } + } + + return value; + } + + public override string ToString() + { + return "..."; + } + } + + [Flags] + public enum AosArmorAttribute + { + LowerStatReq = 0x00000001, + SelfRepair = 0x00000002, + MageArmor = 0x00000004, + DurabilityBonus = 0x00000008 + } + + public sealed class AosArmorAttributes : BaseAttributes + { + public AosArmorAttributes(Item owner) + : base(owner) + { + } + + public AosArmorAttributes(Item owner, GenericReader reader) + : base(owner, reader) + { + } + + public AosArmorAttributes(Item owner, AosArmorAttributes other) + : base(owner, other) + { + } + + public int this[AosArmorAttribute attribute] + { + get => GetValue((int)attribute); + set => SetValue((int)attribute, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int LowerStatReq + { + get => this[AosArmorAttribute.LowerStatReq]; + set => this[AosArmorAttribute.LowerStatReq] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SelfRepair + { + get => this[AosArmorAttribute.SelfRepair]; + set => this[AosArmorAttribute.SelfRepair] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MageArmor + { + get => this[AosArmorAttribute.MageArmor]; + set => this[AosArmorAttribute.MageArmor] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int DurabilityBonus + { + get => this[AosArmorAttribute.DurabilityBonus]; + set => this[AosArmorAttribute.DurabilityBonus] = value; + } + + public static int GetValue(Mobile m, AosArmorAttribute attribute) + { + if (!Core.AOS) + return 0; + + List items = m.Items; + int value = 0; + + for (int i = 0; i < items.Count; ++i) + { + Item obj = items[i]; + + if (obj is BaseArmor armor) + { + AosArmorAttributes attrs = armor.ArmorAttributes; + + if (attrs != null) + value += attrs[attribute]; + } + else if (obj is BaseClothing clothing) + { + AosArmorAttributes attrs = clothing.ClothingAttributes; + + if (attrs != null) + value += attrs[attribute]; + } + } + + return value; + } + + public override string ToString() + { + return "..."; + } + } + + public sealed class AosSkillBonuses : BaseAttributes + { + private List m_Mods; + + public AosSkillBonuses(Item owner) + : base(owner) + { + } + + public AosSkillBonuses(Item owner, GenericReader reader) + : base(owner, reader) + { + } + + public AosSkillBonuses(Item owner, AosSkillBonuses other) + : base(owner, other) + { + } + + + [CommandProperty(AccessLevel.GameMaster)] + public double Skill_1_Value + { + get => GetBonus(0); + set => SetBonus(0, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill_1_Name + { + get => GetSkill(0); + set => SetSkill(0, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public double Skill_2_Value + { + get => GetBonus(1); + set => SetBonus(1, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill_2_Name + { + get => GetSkill(1); + set => SetSkill(1, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public double Skill_3_Value + { + get => GetBonus(2); + set => SetBonus(2, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill_3_Name + { + get => GetSkill(2); + set => SetSkill(2, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public double Skill_4_Value + { + get => GetBonus(3); + set => SetBonus(3, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill_4_Name + { + get => GetSkill(3); + set => SetSkill(3, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public double Skill_5_Value + { + get => GetBonus(4); + set => SetBonus(4, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName Skill_5_Name + { + get => GetSkill(4); + set => SetSkill(4, value); + } + + public void GetProperties(ObjectPropertyList list) + { + for (int i = 0; i < 5; ++i) + { + SkillName skill; + double bonus; + + if (!GetValues(i, out skill, out bonus)) + continue; + + list.Add(1060451 + i, "#{0}\t{1}", GetLabel(skill), bonus); + } + } + + public static int GetLabel(SkillName skill) + { + switch (skill) + { + case SkillName.EvalInt: return 1002070; // Evaluate Intelligence + case SkillName.Forensics: return 1002078; // Forensic Evaluation + case SkillName.Lockpicking: return 1002097; // Lockpicking + default: return 1044060 + (int)skill; + } + } + + public void AddTo(Mobile m) + { + Remove(); + + for (int i = 0; i < 5; ++i) + { + if (!GetValues(i, out SkillName skill, out double bonus)) + continue; + + if (m_Mods == null) + m_Mods = new List(); + + SkillMod sk = new DefaultSkillMod(skill, true, bonus); + sk.ObeyCap = true; + m.AddSkillMod(sk); + m_Mods.Add(sk); + } + } + + public void Remove() + { + if (m_Mods == null) + return; + + for (int i = 0; i < m_Mods.Count; ++i) + { + Mobile m = m_Mods[i].Owner; + m_Mods[i].Remove(); + + if (Core.ML) + CheckCancelMorph(m); + } + + m_Mods = null; + } + + public bool GetValues(int index, out SkillName skill, out double bonus) + { + int v = GetValue(1 << index); + int vSkill = 0; + int vBonus = 0; + + for (int i = 0; i < 16; ++i) + { + vSkill <<= 1; + vSkill |= v & 1; + v >>= 1; + + vBonus <<= 1; + vBonus |= v & 1; + v >>= 1; + } + + skill = (SkillName)vSkill; + bonus = (double)vBonus / 10; + + return bonus != 0; + } + + public void SetValues(int index, SkillName skill, double bonus) + { + int v = 0; + int vSkill = (int)skill; + int vBonus = (int)(bonus * 10); + + for (int i = 0; i < 16; ++i) + { + v <<= 1; + v |= vBonus & 1; + vBonus >>= 1; + + v <<= 1; + v |= vSkill & 1; + vSkill >>= 1; + } + + SetValue(1 << index, v); + } + + public SkillName GetSkill(int index) + { + SkillName skill; + double bonus; + + GetValues(index, out skill, out bonus); + + return skill; + } + + public void SetSkill(int index, SkillName skill) + { + SetValues(index, skill, GetBonus(index)); + } + + public double GetBonus(int index) + { + SkillName skill; + double bonus; + + GetValues(index, out skill, out bonus); + + return bonus; + } + + public void SetBonus(int index, double bonus) + { + SetValues(index, GetSkill(index), bonus); + } + + public override string ToString() + { + return "..."; + } + + public void CheckCancelMorph(Mobile m) + { + if (m == null) + return; + + double minSkill, maxSkill; + + AnimalFormContext acontext = AnimalForm.GetContext(m); + TransformContext context = TransformationSpellHelper.GetContext(m); + + if (context != null) + { + Spell spell = context.Spell as Spell; + spell.GetCastSkills(out minSkill, out maxSkill); + if (m.Skills[spell.CastSkill].Value < minSkill) + TransformationSpellHelper.RemoveContext(m, context, true); + } + + if (acontext != null) + { + int i; + for (i = 0; i < AnimalForm.Entries.Length; ++i) + if (AnimalForm.Entries[i].Type == acontext.Type) + break; + if (m.Skills[SkillName.Ninjitsu].Value < AnimalForm.Entries[i].ReqSkill) + AnimalForm.RemoveContext(m, true); + } + + if (!m.CanBeginAction(typeof(PolymorphSpell)) && m.Skills[SkillName.Magery].Value < 66.1) + { + m.BodyMod = 0; + m.HueMod = -1; + m.NameMod = null; + m.EndAction(typeof(PolymorphSpell)); + BaseArmor.ValidateMobile(m); + BaseClothing.ValidateMobile(m); + } + + if (!m.CanBeginAction(typeof(IncognitoSpell)) && m.Skills[SkillName.Magery].Value < 38.1) + { + if (m is PlayerMobile mobile) + mobile.SetHairMods(-1, -1); + m.BodyMod = 0; + m.HueMod = -1; + m.NameMod = null; + m.EndAction(typeof(IncognitoSpell)); + BaseArmor.ValidateMobile(m); + BaseClothing.ValidateMobile(m); + BuffInfo.RemoveBuff(m, BuffIcon.Incognito); + } + } + } + + [Flags] + public enum AosElementAttribute + { + Physical = 0x00000001, + Fire = 0x00000002, + Cold = 0x00000004, + Poison = 0x00000008, + Energy = 0x00000010, + Chaos = 0x00000020, + Direct = 0x00000040 + } + + public sealed class AosElementAttributes : BaseAttributes + { + public AosElementAttributes(Item owner) + : base(owner) + { + } + + public AosElementAttributes(Item owner, AosElementAttributes other) + : base(owner, other) + { + } + + public AosElementAttributes(Item owner, GenericReader reader) + : base(owner, reader) + { + } + + public int this[AosElementAttribute attribute] + { + get => GetValue((int)attribute); + set => SetValue((int)attribute, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Physical + { + get => this[AosElementAttribute.Physical]; + set => this[AosElementAttribute.Physical] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Fire + { + get => this[AosElementAttribute.Fire]; + set => this[AosElementAttribute.Fire] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Cold + { + get => this[AosElementAttribute.Cold]; + set => this[AosElementAttribute.Cold] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Poison + { + get => this[AosElementAttribute.Poison]; + set => this[AosElementAttribute.Poison] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Energy + { + get => this[AosElementAttribute.Energy]; + set => this[AosElementAttribute.Energy] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Chaos + { + get => this[AosElementAttribute.Chaos]; + set => this[AosElementAttribute.Chaos] = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Direct + { + get => this[AosElementAttribute.Direct]; + set => this[AosElementAttribute.Direct] = value; + } + + public override string ToString() + { + return "..."; + } + } + + [PropertyObject] + public abstract class BaseAttributes + { + private static int[] m_Empty = new int[0]; + private uint m_Names; + private int[] m_Values; + + public BaseAttributes(Item owner) + { + Owner = owner; + m_Values = m_Empty; + } + + public BaseAttributes(Item owner, BaseAttributes other) + { + Owner = owner; + m_Values = new int[other.m_Values.Length]; + other.m_Values.CopyTo(m_Values, 0); + m_Names = other.m_Names; + } + + public BaseAttributes(Item owner, GenericReader reader) + { + Owner = owner; + + int version = reader.ReadByte(); + + switch (version) + { + case 1: + { + m_Names = reader.ReadUInt(); + m_Values = new int[reader.ReadEncodedInt()]; + + for (int i = 0; i < m_Values.Length; ++i) + m_Values[i] = reader.ReadEncodedInt(); + + break; + } + case 0: + { + m_Names = reader.ReadUInt(); + m_Values = new int[reader.ReadInt()]; + + for (int i = 0; i < m_Values.Length; ++i) + m_Values[i] = reader.ReadInt(); + + break; + } + } + } + + public bool IsEmpty => m_Names == 0; + public Item Owner{ get; } + + public void Serialize(GenericWriter writer) + { + writer.Write((byte)1); // version; + + writer.Write(m_Names); + writer.WriteEncodedInt(m_Values.Length); + + for (int i = 0; i < m_Values.Length; ++i) + writer.WriteEncodedInt(m_Values[i]); + } + + public int GetValue(int bitmask) + { + if (!Core.AOS) + return 0; + + uint mask = (uint)bitmask; + + if ((m_Names & mask) == 0) + return 0; + + int index = GetIndex(mask); + + if (index >= 0 && index < m_Values.Length) + return m_Values[index]; + + return 0; + } + + public void SetValue(int bitmask, int value) + { + if (bitmask == (int)AosWeaponAttribute.DurabilityBonus && this is AosWeaponAttributes) + { + if (Owner is BaseWeapon weapon) + weapon.UnscaleDurability(); + } + else if (bitmask == (int)AosArmorAttribute.DurabilityBonus && this is AosArmorAttributes) + { + if (Owner is BaseArmor armor) + armor.UnscaleDurability(); + else if (Owner is BaseClothing clothing) + clothing.UnscaleDurability(); + } + + uint mask = (uint)bitmask; + + if (value != 0) + { + if ((m_Names & mask) != 0) + { + int index = GetIndex(mask); + + if (index >= 0 && index < m_Values.Length) + m_Values[index] = value; + } + else + { + int index = GetIndex(mask); + + if (index >= 0 && index <= m_Values.Length) + { + int[] old = m_Values; + m_Values = new int[old.Length + 1]; + + for (int i = 0; i < index; ++i) + m_Values[i] = old[i]; + + m_Values[index] = value; + + for (int i = index; i < old.Length; ++i) + m_Values[i + 1] = old[i]; + + m_Names |= mask; + } + } + } + else if ((m_Names & mask) != 0) + { + int index = GetIndex(mask); + + if (index >= 0 && index < m_Values.Length) + { + m_Names &= ~mask; + + if (m_Values.Length == 1) + { + m_Values = m_Empty; + } + else + { + int[] old = m_Values; + m_Values = new int[old.Length - 1]; + + for (int i = 0; i < index; ++i) + m_Values[i] = old[i]; + + for (int i = index + 1; i < old.Length; ++i) + m_Values[i - 1] = old[i]; + } + } + } + + if (bitmask == (int)AosWeaponAttribute.DurabilityBonus && this is AosWeaponAttributes) + { + if (Owner is BaseWeapon weapon) + weapon.ScaleDurability(); + } + else if (bitmask == (int)AosArmorAttribute.DurabilityBonus && this is AosArmorAttributes) + { + if (Owner is BaseArmor armor) + armor.ScaleDurability(); + else if (Owner is BaseClothing clothing) + clothing.ScaleDurability(); + } + + if (Owner.Parent is Mobile m) + { + m.CheckStatTimers(); + m.UpdateResistances(); + m.Delta(MobileDelta.Stat | MobileDelta.WeaponDamage | MobileDelta.Hits | MobileDelta.Stam | + MobileDelta.Mana); + + if (this is AosSkillBonuses) + { + ((AosSkillBonuses)this).Remove(); + ((AosSkillBonuses)this).AddTo(m); + } + } + + Owner.InvalidateProperties(); + } + + private int GetIndex(uint mask) + { + int index = 0; + uint ourNames = m_Names; + uint currentBit = 1; + + while (currentBit != mask) + { + if ((ourNames & currentBit) != 0) + ++index; + + if (currentBit == 0x80000000) + return -1; + + currentBit <<= 1; + } + + return index; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/AccountPrompt.cs b/Scripts/Misc/AccountPrompt.cs index 454e46bd6..1c5df4dab 100644 --- a/Scripts/Misc/AccountPrompt.cs +++ b/Scripts/Misc/AccountPrompt.cs @@ -3,37 +3,37 @@ using Server.Accounting; namespace Server.Misc { - public class AccountPrompt - { - public static void Initialize() - { - if ( Accounts.Count == 0 && !Core.Service ) - { - Console.WriteLine( "This server has no accounts." ); - Console.Write( "Do you want to create the owner account now? (y/n)" ); + public class AccountPrompt + { + public static void Initialize() + { + if (Accounts.Count == 0 && !Core.Service) + { + Console.WriteLine("This server has no accounts."); + Console.Write("Do you want to create the owner account now? (y/n)"); - if ( Console.ReadKey( true ).Key == ConsoleKey.Y ) - { - Console.WriteLine(); + if (Console.ReadKey(true).Key == ConsoleKey.Y) + { + Console.WriteLine(); - Console.Write( "Username: " ); - string username = Console.ReadLine(); + Console.Write("Username: "); + string username = Console.ReadLine(); - Console.Write( "Password: " ); - string password = Console.ReadLine(); + Console.Write("Password: "); + string password = Console.ReadLine(); - Account a = new Account( username, password ); - a.AccessLevel = AccessLevel.Owner; + Account a = new Account(username, password); + a.AccessLevel = AccessLevel.Owner; - Console.WriteLine( "Account created." ); - } - else - { - Console.WriteLine(); + Console.WriteLine("Account created."); + } + else + { + Console.WriteLine(); - Console.WriteLine( "Account not created." ); - } - } - } - } -} + Console.WriteLine("Account not created."); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Animations.cs b/Scripts/Misc/Animations.cs index 581404e74..d4515e671 100644 --- a/Scripts/Misc/Animations.cs +++ b/Scripts/Misc/Animations.cs @@ -1,27 +1,31 @@ namespace Server.Misc { - public class Animations - { - public static void Initialize() - { - EventSink.AnimateRequest += EventSink_AnimateRequest; - } + public class Animations + { + public static void Initialize() + { + EventSink.AnimateRequest += EventSink_AnimateRequest; + } - private static void EventSink_AnimateRequest( AnimateRequestEventArgs e ) - { - Mobile from = e.Mobile; + private static void EventSink_AnimateRequest(AnimateRequestEventArgs e) + { + Mobile from = e.Mobile; - int action; + int action; - switch ( e.Action ) - { - case "bow": action = 32; break; - case "salute": action = 33; break; - default: return; - } + switch (e.Action) + { + case "bow": + action = 32; + break; + case "salute": + action = 33; + break; + default: return; + } - if ( from.Alive && !from.Mounted && from.Body.IsHuman ) - from.Animate( action, 5, 1, true, false, 0 ); - } - } + if (from.Alive && !from.Mounted && from.Body.IsHuman) + from.Animate(action, 5, 1, true, false, 0); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Assistants.cs b/Scripts/Misc/Assistants.cs index fe9a6405f..b18b97e34 100644 --- a/Scripts/Misc/Assistants.cs +++ b/Scripts/Misc/Assistants.cs @@ -1,184 +1,185 @@ using System; using System.Collections.Generic; +using Server.Gumps; using Server.Network; namespace Server.Misc { - public static partial class Assistants - { - private static class Settings - { - public const bool Enabled = false; - public const bool KickOnFailure = true; // It will also kick clients running without assistants + public static class Assistants + { + private static class Settings + { + [Flags] + public enum Features : ulong + { + None = 0, - public static readonly TimeSpan HandshakeTimeout = TimeSpan.FromSeconds(30.0); - public static readonly TimeSpan DisconnectDelay = TimeSpan.FromSeconds(15.0); + FilterWeather = 1 << 0, // Weather Filter + FilterLight = 1 << 1, // Light Filter + SmartTarget = 1 << 2, // Smart Last Target + RangedTarget = 1 << 3, // Range Check Last Target + AutoOpenDoors = 1 << 4, // Automatically Open Doors + DequipOnCast = 1 << 5, // Unequip Weapon on spell cast + AutoPotionEquip = 1 << 6, // Un/re-equip weapon on potion use + PoisonedChecks = 1 << 7, // Block heal If poisoned/Macro If Poisoned condition/Heal or Cure self + LoopedMacros = 1 << 8, // Disallow looping or recursive macros + UseOnceAgent = 1 << 9, // The use once agent + RestockAgent = 1 << 10, // The restock agent + SellAgent = 1 << 11, // The sell agent + BuyAgent = 1 << 12, // The buy agent + PotionHotkeys = 1 << 13, // All potion hotkeys + RandomTargets = 1 << 14, // All random target hotkeys (not target next, last target, target self) + ClosestTargets = 1 << 15, // All closest target hotkeys + OverheadHealth = 1 << 16, // Health and Mana/Stam messages shown over player's heads + AutolootAgent = 1 << 17, // The autoloot agent + BoneCutterAgent = 1 << 18, // The bone cutter agent + AdvancedMacros = 1 << 19, // Advanced macro engine + AutoRemount = 1 << 20, // Auto remount after dismount + AutoBandage = 1 << 21, // Auto bandage friends, self, last and mount option + EnemyTargetShare = 1 << 22, // Enemy target share on guild, party or alliance chat + FilterSeason = 1 << 23, // Season Filter + SpellTargetShare = 1 << 24, // Spell target share on guild, party or alliance chat - public const string WarningMessage = "The server was unable to negotiate features with your assistant. " - + "You must download and run an updated version of UOSteam" - + " or Razor." - + "

Make sure you've checked the option Negotiate features with server, " - + "once you have this box checked you may log in and play normally." - + "

You will be disconnected shortly."; + All = ulong.MaxValue + } - public static void Configure() - { - //DisallowFeature( Features.FilterWeather ); - } + public const bool Enabled = false; + public const bool KickOnFailure = true; // It will also kick clients running without assistants - [Flags] - public enum Features : ulong - { - None = 0, + public const string WarningMessage = "The server was unable to negotiate features with your assistant. " + + "You must download and run an updated version of UOSteam" + + " or Razor." + + "

Make sure you've checked the option Negotiate features with server, " + + "once you have this box checked you may log in and play normally." + + "

You will be disconnected shortly."; - FilterWeather = 1 << 0, // Weather Filter - FilterLight = 1 << 1, // Light Filter - SmartTarget = 1 << 2, // Smart Last Target - RangedTarget = 1 << 3, // Range Check Last Target - AutoOpenDoors = 1 << 4, // Automatically Open Doors - DequipOnCast = 1 << 5, // Unequip Weapon on spell cast - AutoPotionEquip = 1 << 6, // Un/re-equip weapon on potion use - PoisonedChecks = 1 << 7, // Block heal If poisoned/Macro If Poisoned condition/Heal or Cure self - LoopedMacros = 1 << 8, // Disallow looping or recursive macros - UseOnceAgent = 1 << 9, // The use once agent - RestockAgent = 1 << 10, // The restock agent - SellAgent = 1 << 11, // The sell agent - BuyAgent = 1 << 12, // The buy agent - PotionHotkeys = 1 << 13, // All potion hotkeys - RandomTargets = 1 << 14, // All random target hotkeys (not target next, last target, target self) - ClosestTargets = 1 << 15, // All closest target hotkeys - OverheadHealth = 1 << 16, // Health and Mana/Stam messages shown over player's heads - AutolootAgent = 1 << 17, // The autoloot agent - BoneCutterAgent = 1 << 18, // The bone cutter agent - AdvancedMacros = 1 << 19, // Advanced macro engine - AutoRemount = 1 << 20, // Auto remount after dismount - AutoBandage = 1 << 21, // Auto bandage friends, self, last and mount option - EnemyTargetShare = 1 << 22, // Enemy target share on guild, party or alliance chat - FilterSeason = 1 << 23, // Season Filter - SpellTargetShare = 1 << 24, // Spell target share on guild, party or alliance chat + public static readonly TimeSpan HandshakeTimeout = TimeSpan.FromSeconds(30.0); + public static readonly TimeSpan DisconnectDelay = TimeSpan.FromSeconds(15.0); - All = ulong.MaxValue - } + public static Features DisallowedFeatures{ get; private set; } = Features.None; - public static void DisallowFeature(Features feature) - { - SetDisallowed(feature, true); - } + public static void Configure() + { + //DisallowFeature( Features.FilterWeather ); + } - public static void AllowFeature(Features feature) - { - SetDisallowed(feature, false); - } + public static void DisallowFeature(Features feature) + { + SetDisallowed(feature, true); + } - public static void SetDisallowed(Features feature, bool value) - { - if (value) - DisallowedFeatures |= feature; - else - DisallowedFeatures &= ~feature; - } + public static void AllowFeature(Features feature) + { + SetDisallowed(feature, false); + } - public static Features DisallowedFeatures { get; private set; } = Features.None; - } + public static void SetDisallowed(Features feature, bool value) + { + if (value) + DisallowedFeatures |= feature; + else + DisallowedFeatures &= ~feature; + } + } - private static class Negotiator - { - private static Dictionary m_Dictionary = new Dictionary(); + private static class Negotiator + { + private static Dictionary m_Dictionary = new Dictionary(); - private static TimerStateCallback OnHandshakeTimeout_Callback = OnHandshakeTimeout; - private static TimerStateCallback OnForceDisconnect_Callback = OnForceDisconnect; + private static TimerStateCallback OnHandshakeTimeout_Callback = OnHandshakeTimeout; + private static TimerStateCallback OnForceDisconnect_Callback = OnForceDisconnect; - public static void Initialize() - { - if (Settings.Enabled) - { - EventSink.Login += EventSink_Login; - ProtocolExtensions.Register(0xFF, true, OnHandshakeResponse); - } - } + public static void Initialize() + { + if (Settings.Enabled) + { + EventSink.Login += EventSink_Login; + ProtocolExtensions.Register(0xFF, true, OnHandshakeResponse); + } + } - private static void EventSink_Login(LoginEventArgs e) - { - Mobile m = e.Mobile; + private static void EventSink_Login(LoginEventArgs e) + { + Mobile m = e.Mobile; - if (m?.NetState != null && m.NetState.Running) - { - m.Send(new BeginHandshake()); + if (m?.NetState != null && m.NetState.Running) + { + m.Send(new BeginHandshake()); - if (Settings.KickOnFailure) - m.Send(new BeginHandshake()); + if (Settings.KickOnFailure) + m.Send(new BeginHandshake()); - if (m_Dictionary.TryGetValue(m, out Timer t)) - t?.Stop(); + if (m_Dictionary.TryGetValue(m, out Timer t)) + t?.Stop(); - m_Dictionary[m] = t = Timer.DelayCall(Settings.HandshakeTimeout, OnHandshakeTimeout_Callback, m); - t.Start(); - } - } + m_Dictionary[m] = t = Timer.DelayCall(Settings.HandshakeTimeout, OnHandshakeTimeout_Callback, m); + t.Start(); + } + } - private static void OnHandshakeResponse(NetState state, PacketReader pvSrc) - { - pvSrc.Trace(state); + private static void OnHandshakeResponse(NetState state, PacketReader pvSrc) + { + pvSrc.Trace(state); - if (state?.Mobile == null || !state.Running) - return; + if (state?.Mobile == null || !state.Running) + return; - Mobile m = state.Mobile; - if (m_Dictionary.TryGetValue( m, out Timer t )) - { - t?.Stop(); + Mobile m = state.Mobile; + if (m_Dictionary.TryGetValue(m, out Timer t)) + { + t?.Stop(); - m_Dictionary.Remove(m); - } - } + m_Dictionary.Remove(m); + } + } - private static void OnHandshakeTimeout(object state) - { - if (!(state is Mobile m)) - return; + private static void OnHandshakeTimeout(object state) + { + if (!(state is Mobile m)) + return; - m_Dictionary.Remove(m); + m_Dictionary.Remove(m); // if (!Settings.KickOnFailure) // { // Console.WriteLine("Player '{0}' failed to negotiate features.", m); // } - if (m.NetState != null && m.NetState.Running) - { - m.SendGump(new Gumps.WarningGump(1060635, 30720, Settings.WarningMessage, 0xFFC000, 420, 250, null, null)); + if (m.NetState != null && m.NetState.Running) + { + m.SendGump(new WarningGump(1060635, 30720, Settings.WarningMessage, 0xFFC000, 420, 250, null, null)); - if (m.AccessLevel <= AccessLevel.Player) - { - Timer t; - m_Dictionary[m] = t = Timer.DelayCall(Settings.DisconnectDelay, OnForceDisconnect_Callback, m); - t.Start(); - } - } - } + if (m.AccessLevel <= AccessLevel.Player) + { + Timer t; + m_Dictionary[m] = t = Timer.DelayCall(Settings.DisconnectDelay, OnForceDisconnect_Callback, m); + t.Start(); + } + } + } - private static void OnForceDisconnect(object state) - { - if (state is Mobile m) - { - if (m.NetState != null && m.NetState.Running) - m.NetState.Dispose(); + private static void OnForceDisconnect(object state) + { + if (state is Mobile m) + { + if (m.NetState != null && m.NetState.Running) + m.NetState.Dispose(); - m_Dictionary.Remove(m); + m_Dictionary.Remove(m); - Console.WriteLine("Player {0} kicked (Failed assistant handshake)", m); - } - } + Console.WriteLine("Player {0} kicked (Failed assistant handshake)", m); + } + } - private sealed class BeginHandshake : ProtocolExtension - { - public BeginHandshake() - : base(0xFE, 8) - { - m_Stream.Write((uint)((ulong)Settings.DisallowedFeatures >> 32)); - m_Stream.Write((uint)((ulong)Settings.DisallowedFeatures & 0xFFFFFFFF)); - } - } - } - } -} + private sealed class BeginHandshake : ProtocolExtension + { + public BeginHandshake() + : base(0xFE, 8) + { + m_Stream.Write((uint)((ulong)Settings.DisallowedFeatures >> 32)); + m_Stream.Write((uint)((ulong)Settings.DisallowedFeatures & 0xFFFFFFFF)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/AttackMessage.cs b/Scripts/Misc/AttackMessage.cs index 5f5cb21d9..0687281f7 100644 --- a/Scripts/Misc/AttackMessage.cs +++ b/Scripts/Misc/AttackMessage.cs @@ -4,57 +4,59 @@ using Server.Network; namespace Server.Misc { - public class AttackMessage - { - private const string AggressorFormat = "You are attacking {0}!"; - private const string AggressedFormat = "{0} is attacking you!"; - private const int Hue = 0x22; + public class AttackMessage + { + private const string AggressorFormat = "You are attacking {0}!"; + private const string AggressedFormat = "{0} is attacking you!"; + private const int Hue = 0x22; - private static TimeSpan Delay = TimeSpan.FromMinutes( 1.0 ); + private static TimeSpan Delay = TimeSpan.FromMinutes(1.0); - public static void Initialize() - { - EventSink.AggressiveAction += EventSink_AggressiveAction; - } + public static void Initialize() + { + EventSink.AggressiveAction += EventSink_AggressiveAction; + } - public static void EventSink_AggressiveAction( AggressiveActionEventArgs e ) - { - Mobile aggressor = e.Aggressor; - Mobile aggressed = e.Aggressed; + public static void EventSink_AggressiveAction(AggressiveActionEventArgs e) + { + Mobile aggressor = e.Aggressor; + Mobile aggressed = e.Aggressed; - if ( !aggressor.Player || !aggressed.Player ) - return; + if (!aggressor.Player || !aggressed.Player) + return; - if ( !CheckAggressions( aggressor, aggressed ) ) - { - aggressor.LocalOverheadMessage( MessageType.Regular, Hue, true, string.Format( AggressorFormat, aggressed.Name ) ); - aggressed.LocalOverheadMessage( MessageType.Regular, Hue, true, string.Format( AggressedFormat, aggressor.Name ) ); - } - } + if (!CheckAggressions(aggressor, aggressed)) + { + aggressor.LocalOverheadMessage(MessageType.Regular, Hue, true, + string.Format(AggressorFormat, aggressed.Name)); + aggressed.LocalOverheadMessage(MessageType.Regular, Hue, true, + string.Format(AggressedFormat, aggressor.Name)); + } + } - public static bool CheckAggressions( Mobile m1, Mobile m2 ) - { - List list = m1.Aggressors; + public static bool CheckAggressions(Mobile m1, Mobile m2) + { + List list = m1.Aggressors; - for ( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - if ( info.Attacker == m2 && DateTime.UtcNow < (info.LastCombatTime + Delay) ) - return true; - } + if (info.Attacker == m2 && DateTime.UtcNow < info.LastCombatTime + Delay) + return true; + } - list = m2.Aggressors; + list = m2.Aggressors; - for ( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - if ( info.Attacker == m1 && DateTime.UtcNow < (info.LastCombatTime + Delay) ) - return true; - } + if (info.Attacker == m1 && DateTime.UtcNow < info.LastCombatTime + Delay) + return true; + } - return false; - } - } + return false; + } + } } \ No newline at end of file diff --git a/Scripts/Misc/AutoRestart.cs b/Scripts/Misc/AutoRestart.cs index edf6f7d24..2ee1f6b6b 100644 --- a/Scripts/Misc/AutoRestart.cs +++ b/Scripts/Misc/AutoRestart.cs @@ -3,78 +3,82 @@ using Server.Commands; namespace Server.Misc { - public class AutoRestart : Timer - { - public static bool Enabled; // is the script enabled? + public class AutoRestart : Timer + { + public static bool Enabled; // is the script enabled? - private static TimeSpan RestartTime = TimeSpan.FromHours( 2.0 ); // time of day at which to restart - private static TimeSpan RestartDelay = TimeSpan.Zero; // how long the server should remain active before restart (period of 'server wars') + private static TimeSpan RestartTime = TimeSpan.FromHours(2.0); // time of day at which to restart - private static TimeSpan WarningDelay = TimeSpan.FromMinutes( 1.0 ); // at what interval should the shutdown message be displayed? + private static TimeSpan + RestartDelay = + TimeSpan.Zero; // how long the server should remain active before restart (period of 'server wars') - private static DateTime m_RestartTime; + private static TimeSpan + WarningDelay = TimeSpan.FromMinutes(1.0); // at what interval should the shutdown message be displayed? - public static bool Restarting { get; private set; } + private static DateTime m_RestartTime; - public static void Initialize() - { - CommandSystem.Register( "Restart", AccessLevel.Administrator, Restart_OnCommand ); - new AutoRestart().Start(); - } + public AutoRestart() : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + Priority = TimerPriority.FiveSeconds; - public static void Restart_OnCommand( CommandEventArgs e ) - { - if ( Restarting ) - { - e.Mobile.SendMessage( "The server is already restarting." ); - } - else - { - e.Mobile.SendMessage( "You have initiated server shutdown." ); - Enabled = true; - m_RestartTime = DateTime.UtcNow; - } - } + m_RestartTime = DateTime.UtcNow.Date + RestartTime; - public AutoRestart() : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - Priority = TimerPriority.FiveSeconds; + if (m_RestartTime < DateTime.UtcNow) + m_RestartTime += TimeSpan.FromDays(1.0); + } - m_RestartTime = DateTime.UtcNow.Date + RestartTime; + public static bool Restarting{ get; private set; } - if ( m_RestartTime < DateTime.UtcNow ) - m_RestartTime += TimeSpan.FromDays( 1.0 ); - } + public static void Initialize() + { + CommandSystem.Register("Restart", AccessLevel.Administrator, Restart_OnCommand); + new AutoRestart().Start(); + } - private void Warning_Callback() - { - World.Broadcast( 0x22, true, "The server is going down shortly." ); - } + public static void Restart_OnCommand(CommandEventArgs e) + { + if (Restarting) + { + e.Mobile.SendMessage("The server is already restarting."); + } + else + { + e.Mobile.SendMessage("You have initiated server shutdown."); + Enabled = true; + m_RestartTime = DateTime.UtcNow; + } + } - private void Restart_Callback() - { - Core.Kill( true ); - } + private void Warning_Callback() + { + World.Broadcast(0x22, true, "The server is going down shortly."); + } - protected override void OnTick() - { - if ( Restarting || !Enabled ) - return; + private void Restart_Callback() + { + Core.Kill(true); + } - if ( DateTime.UtcNow < m_RestartTime ) - return; + protected override void OnTick() + { + if (Restarting || !Enabled) + return; - if ( WarningDelay > TimeSpan.Zero ) - { - Warning_Callback(); - DelayCall( WarningDelay, WarningDelay, Warning_Callback ); - } + if (DateTime.UtcNow < m_RestartTime) + return; - AutoSave.Save(); + if (WarningDelay > TimeSpan.Zero) + { + Warning_Callback(); + DelayCall(WarningDelay, WarningDelay, Warning_Callback); + } - Restarting = true; + AutoSave.Save(); - DelayCall( RestartDelay, Restart_Callback ); - } - } + Restarting = true; + + DelayCall(RestartDelay, Restart_Callback); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/AutoSave.cs b/Scripts/Misc/AutoSave.cs index cdedfbbfb..ebb44ca9a 100644 --- a/Scripts/Misc/AutoSave.cs +++ b/Scripts/Misc/AutoSave.cs @@ -4,170 +4,186 @@ using Server.Commands; namespace Server.Misc { - public class AutoSave : Timer - { - private static TimeSpan m_Delay = TimeSpan.FromMinutes( 5.0 ); - private static TimeSpan m_Warning = TimeSpan.Zero; - //private static TimeSpan m_Warning = TimeSpan.FromSeconds( 15.0 ); + public class AutoSave : Timer + { + private static TimeSpan m_Delay = TimeSpan.FromMinutes(5.0); + private static TimeSpan m_Warning = TimeSpan.Zero; - public static void Initialize() - { - new AutoSave().Start(); - CommandSystem.Register( "SetSaves", AccessLevel.Administrator, SetSaves_OnCommand ); - } + private static string[] m_Backups = + { + "Third Backup", + "Second Backup", + "Most Recent" + }; - public static bool SavesEnabled { get; set; } = true; + public AutoSave() : base(m_Delay - m_Warning, m_Delay) + { + Priority = TimerPriority.OneMinute; + } - [Usage( "SetSaves " )] - [Description( "Enables or disables automatic shard saving." )] - public static void SetSaves_OnCommand( CommandEventArgs e ) - { - if ( e.Length == 1 ) - { - SavesEnabled = e.GetBoolean( 0 ); - e.Mobile.SendMessage( "Saves have been {0}.", SavesEnabled ? "enabled" : "disabled" ); - } - else - { - e.Mobile.SendMessage( "Format: SetSaves " ); - } - } + public static bool SavesEnabled{ get; set; } = true; + //private static TimeSpan m_Warning = TimeSpan.FromSeconds( 15.0 ); - public AutoSave() : base( m_Delay - m_Warning, m_Delay ) - { - Priority = TimerPriority.OneMinute; - } + public static void Initialize() + { + new AutoSave().Start(); + CommandSystem.Register("SetSaves", AccessLevel.Administrator, SetSaves_OnCommand); + } - protected override void OnTick() - { - if ( !SavesEnabled || AutoRestart.Restarting ) - return; + [Usage("SetSaves ")] + [Description("Enables or disables automatic shard saving.")] + public static void SetSaves_OnCommand(CommandEventArgs e) + { + if (e.Length == 1) + { + SavesEnabled = e.GetBoolean(0); + e.Mobile.SendMessage("Saves have been {0}.", SavesEnabled ? "enabled" : "disabled"); + } + else + { + e.Mobile.SendMessage("Format: SetSaves "); + } + } - if ( m_Warning == TimeSpan.Zero ) - { - Save( true ); - } - else - { - int s = (int)m_Warning.TotalSeconds; - int m = s / 60; - s %= 60; + protected override void OnTick() + { + if (!SavesEnabled || AutoRestart.Restarting) + return; - if ( m > 0 && s > 0 ) - World.Broadcast( 0x35, true, "The world will save in {0} minute{1} and {2} second{3}.", m, m != 1 ? "s" : "", s, s != 1 ? "s" : "" ); - else if ( m > 0 ) - World.Broadcast( 0x35, true, "The world will save in {0} minute{1}.", m, m != 1 ? "s" : "" ); - else - World.Broadcast( 0x35, true, "The world will save in {0} second{1}.", s, s != 1 ? "s" : "" ); + if (m_Warning == TimeSpan.Zero) + { + Save(true); + } + else + { + int s = (int)m_Warning.TotalSeconds; + int m = s / 60; + s %= 60; - DelayCall( m_Warning, Save ); - } - } + if (m > 0 && s > 0) + World.Broadcast(0x35, true, "The world will save in {0} minute{1} and {2} second{3}.", m, + m != 1 ? "s" : "", s, s != 1 ? "s" : ""); + else if (m > 0) + World.Broadcast(0x35, true, "The world will save in {0} minute{1}.", m, m != 1 ? "s" : ""); + else + World.Broadcast(0x35, true, "The world will save in {0} second{1}.", s, s != 1 ? "s" : ""); - public static void Save() - { - Save( false ); - } + DelayCall(m_Warning, Save); + } + } - public static void Save( bool permitBackgroundWrite ) - { - if ( AutoRestart.Restarting ) - return; + public static void Save() + { + Save(false); + } - World.WaitForWriteCompletion(); + public static void Save(bool permitBackgroundWrite) + { + if (AutoRestart.Restarting) + return; - try{ Backup(); } - catch ( Exception e ) { Console.WriteLine("WARNING: Automatic backup FAILED: {0}", e); } + World.WaitForWriteCompletion(); - World.Save( true, permitBackgroundWrite ); - } + try + { + Backup(); + } + catch (Exception e) + { + Console.WriteLine("WARNING: Automatic backup FAILED: {0}", e); + } - private static string[] m_Backups = { - "Third Backup", - "Second Backup", - "Most Recent" - }; + World.Save(true, permitBackgroundWrite); + } - private static void Backup() - { - if ( m_Backups.Length == 0 ) - return; + private static void Backup() + { + if (m_Backups.Length == 0) + return; - string root = Path.Combine( Core.BaseDirectory, "Backups/Automatic" ); + string root = Path.Combine(Core.BaseDirectory, "Backups/Automatic"); - if ( !Directory.Exists( root ) ) - Directory.CreateDirectory( root ); + if (!Directory.Exists(root)) + Directory.CreateDirectory(root); - string[] existing = Directory.GetDirectories( root ); + string[] existing = Directory.GetDirectories(root); - for ( int i = 0; i < m_Backups.Length; ++i ) - { - DirectoryInfo dir = Match( existing, m_Backups[i] ); + for (int i = 0; i < m_Backups.Length; ++i) + { + DirectoryInfo dir = Match(existing, m_Backups[i]); - if ( dir == null ) - continue; + if (dir == null) + continue; - if ( i > 0 ) - { - string timeStamp = FindTimeStamp( dir.Name ); + if (i > 0) + { + string timeStamp = FindTimeStamp(dir.Name); - if ( timeStamp != null ) - { - try{ dir.MoveTo( FormatDirectory( root, m_Backups[i - 1], timeStamp ) ); } - catch{} - } - } - else - { - try{ dir.Delete( true ); } - catch{} - } - } + if (timeStamp != null) + try + { + dir.MoveTo(FormatDirectory(root, m_Backups[i - 1], timeStamp)); + } + catch + { + } + } + else + { + try + { + dir.Delete(true); + } + catch + { + } + } + } - string saves = Path.Combine( Core.BaseDirectory, "Saves" ); + string saves = Path.Combine(Core.BaseDirectory, "Saves"); - if ( Directory.Exists( saves ) ) - Directory.Move( saves, FormatDirectory( root, m_Backups[m_Backups.Length - 1], GetTimeStamp() ) ); - } + if (Directory.Exists(saves)) + Directory.Move(saves, FormatDirectory(root, m_Backups[m_Backups.Length - 1], GetTimeStamp())); + } - private static DirectoryInfo Match( string[] paths, string match ) - { - for ( int i = 0; i < paths.Length; ++i ) - { - DirectoryInfo info = new DirectoryInfo( paths[i] ); + private static DirectoryInfo Match(string[] paths, string match) + { + for (int i = 0; i < paths.Length; ++i) + { + DirectoryInfo info = new DirectoryInfo(paths[i]); - if ( info.Name.StartsWith( match ) ) - return info; - } + if (info.Name.StartsWith(match)) + return info; + } - return null; - } + return null; + } - private static string FormatDirectory( string root, string name, string timeStamp ) - { - return Path.Combine( root, $"{name} ({timeStamp})"); - } + private static string FormatDirectory(string root, string name, string timeStamp) + { + return Path.Combine(root, $"{name} ({timeStamp})"); + } - private static string FindTimeStamp( string input ) - { - int start = input.IndexOf( '(' ); + private static string FindTimeStamp(string input) + { + int start = input.IndexOf('('); - if ( start >= 0 ) - { - int end = input.IndexOf( ')', ++start ); + if (start >= 0) + { + int end = input.IndexOf(')', ++start); - if ( end >= start ) - return input.Substring( start, end-start ); - } + if (end >= start) + return input.Substring(start, end - start); + } - return null; - } + return null; + } - private static string GetTimeStamp() - { - DateTime now = DateTime.UtcNow; + private static string GetTimeStamp() + { + DateTime now = DateTime.UtcNow; - return $"{now.Day}-{now.Month}-{now.Year} {now.Hour}-{now.Minute:D2}-{now.Second:D2}"; - } - } + return $"{now.Day}-{now.Month}-{now.Year} {now.Hour}-{now.Minute:D2}-{now.Second:D2}"; + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Broadcasts.cs b/Scripts/Misc/Broadcasts.cs index de7c69a8b..2286a385d 100644 --- a/Scripts/Misc/Broadcasts.cs +++ b/Scripts/Misc/Broadcasts.cs @@ -1,33 +1,33 @@ namespace Server.Misc { - public class Broadcasts - { - public static void Initialize() - { - EventSink.Crashed += EventSink_Crashed; - EventSink.Shutdown += EventSink_Shutdown; - } + public class Broadcasts + { + public static void Initialize() + { + EventSink.Crashed += EventSink_Crashed; + EventSink.Shutdown += EventSink_Shutdown; + } - public static void EventSink_Crashed( CrashedEventArgs e ) - { - try - { - World.Broadcast( 0x35, true, "The server has crashed." ); - } - catch - { - } - } + public static void EventSink_Crashed(CrashedEventArgs e) + { + try + { + World.Broadcast(0x35, true, "The server has crashed."); + } + catch + { + } + } - public static void EventSink_Shutdown( ShutdownEventArgs e ) - { - try - { - World.Broadcast( 0x35, true, "The server has shut down." ); - } - catch - { - } - } - } + public static void EventSink_Shutdown(ShutdownEventArgs e) + { + try + { + World.Broadcast(0x35, true, "The server has shut down."); + } + catch + { + } + } + } } \ No newline at end of file diff --git a/Scripts/Misc/BuffIcons.cs b/Scripts/Misc/BuffIcons.cs index d05a92191..daffd1f35 100644 --- a/Scripts/Misc/BuffIcons.cs +++ b/Scripts/Misc/BuffIcons.cs @@ -4,285 +4,292 @@ using Server.Network; namespace Server { - public class BuffInfo - { - public static bool Enabled => Core.ML; + public class BuffInfo + { + public static bool Enabled => Core.ML; - public static void Initialize() - { - if ( Enabled ) - { - EventSink.ClientVersionReceived += delegate( ClientVersionReceivedArgs args ) - { - if ( args.State.Mobile is PlayerMobile pm ) - Timer.DelayCall( TimeSpan.Zero, pm.ResendBuffs ); - }; - } - } + public static void Initialize() + { + if (Enabled) + EventSink.ClientVersionReceived += delegate(ClientVersionReceivedArgs args) + { + if (args.State.Mobile is PlayerMobile pm) + Timer.DelayCall(TimeSpan.Zero, pm.ResendBuffs); + }; + } - #region Properties + #region Properties - public BuffIcon ID { get; } + public BuffIcon ID{ get; } - public int TitleCliloc { get; } + public int TitleCliloc{ get; } - public int SecondaryCliloc { get; } + public int SecondaryCliloc{ get; } - public TimeSpan TimeLength { get; } + public TimeSpan TimeLength{ get; } - public DateTime TimeStart { get; } + public DateTime TimeStart{ get; } - public Timer Timer { get; } + public Timer Timer{ get; } - public bool RetainThroughDeath { get; } + public bool RetainThroughDeath{ get; } - public TextDefinition Args { get; } + public TextDefinition Args{ get; } - #endregion + #endregion - #region Constructors - public BuffInfo( BuffIcon iconID, int titleCliloc ) - : this( iconID, titleCliloc, titleCliloc + 1 ) - { - } + #region Constructors - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc ) - { - ID = iconID; - TitleCliloc = titleCliloc; - SecondaryCliloc = secondaryCliloc; - } + public BuffInfo(BuffIcon iconID, int titleCliloc) + : this(iconID, titleCliloc, titleCliloc + 1) + { + } - public BuffInfo( BuffIcon iconID, int titleCliloc, TimeSpan length, Mobile m ) - : this( iconID, titleCliloc, titleCliloc + 1, length, m ) - { - } + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc) + { + ID = iconID; + TitleCliloc = titleCliloc; + SecondaryCliloc = secondaryCliloc; + } - //Only the timed one needs to Mobile to know when to automagically remove it. - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc, TimeSpan length, Mobile m ) - : this( iconID, titleCliloc, secondaryCliloc ) - { - TimeLength = length; - TimeStart = DateTime.UtcNow; + public BuffInfo(BuffIcon iconID, int titleCliloc, TimeSpan length, Mobile m) + : this(iconID, titleCliloc, titleCliloc + 1, length, m) + { + } - Timer = Timer.DelayCall( length, delegate - { - if ( !(m is PlayerMobile pm) ) - return; + //Only the timed one needs to Mobile to know when to automagically remove it. + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc, TimeSpan length, Mobile m) + : this(iconID, titleCliloc, secondaryCliloc) + { + TimeLength = length; + TimeStart = DateTime.UtcNow; - pm.RemoveBuff( this ); - } ); - } + Timer = Timer.DelayCall(length, delegate + { + if (!(m is PlayerMobile pm)) + return; + + pm.RemoveBuff(this); + }); + } - public BuffInfo( BuffIcon iconID, int titleCliloc, TextDefinition args ) - : this( iconID, titleCliloc, titleCliloc + 1, args ) - { - } + public BuffInfo(BuffIcon iconID, int titleCliloc, TextDefinition args) + : this(iconID, titleCliloc, titleCliloc + 1, args) + { + } - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc, TextDefinition args ) - : this( iconID, titleCliloc, secondaryCliloc ) - { - Args = args; - } + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc, TextDefinition args) + : this(iconID, titleCliloc, secondaryCliloc) + { + Args = args; + } - public BuffInfo( BuffIcon iconID, int titleCliloc, bool retainThroughDeath ) - : this( iconID, titleCliloc, titleCliloc + 1, retainThroughDeath ) - { - } + public BuffInfo(BuffIcon iconID, int titleCliloc, bool retainThroughDeath) + : this(iconID, titleCliloc, titleCliloc + 1, retainThroughDeath) + { + } - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc, bool retainThroughDeath ) - : this( iconID, titleCliloc, secondaryCliloc ) - { - RetainThroughDeath = retainThroughDeath; - } + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc, bool retainThroughDeath) + : this(iconID, titleCliloc, secondaryCliloc) + { + RetainThroughDeath = retainThroughDeath; + } - public BuffInfo( BuffIcon iconID, int titleCliloc, TextDefinition args, bool retainThroughDeath ) - : this( iconID, titleCliloc, titleCliloc + 1, args, retainThroughDeath ) - { - } + public BuffInfo(BuffIcon iconID, int titleCliloc, TextDefinition args, bool retainThroughDeath) + : this(iconID, titleCliloc, titleCliloc + 1, args, retainThroughDeath) + { + } - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc, TextDefinition args, bool retainThroughDeath ) - : this( iconID, titleCliloc, secondaryCliloc, args ) - { - RetainThroughDeath = retainThroughDeath; - } + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc, TextDefinition args, bool retainThroughDeath) + : this(iconID, titleCliloc, secondaryCliloc, args) + { + RetainThroughDeath = retainThroughDeath; + } - public BuffInfo( BuffIcon iconID, int titleCliloc, TimeSpan length, Mobile m, TextDefinition args ) - : this( iconID, titleCliloc, titleCliloc + 1, length, m, args ) - { - } + public BuffInfo(BuffIcon iconID, int titleCliloc, TimeSpan length, Mobile m, TextDefinition args) + : this(iconID, titleCliloc, titleCliloc + 1, length, m, args) + { + } - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc, TimeSpan length, Mobile m, TextDefinition args ) - : this( iconID, titleCliloc, secondaryCliloc, length, m ) - { - Args = args; - } + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc, TimeSpan length, Mobile m, + TextDefinition args) + : this(iconID, titleCliloc, secondaryCliloc, length, m) + { + Args = args; + } - public BuffInfo( BuffIcon iconID, int titleCliloc, TimeSpan length, Mobile m, TextDefinition args, bool retainThroughDeath ) - : this( iconID, titleCliloc, titleCliloc + 1, length, m, args, retainThroughDeath ) - { - } + public BuffInfo(BuffIcon iconID, int titleCliloc, TimeSpan length, Mobile m, TextDefinition args, + bool retainThroughDeath) + : this(iconID, titleCliloc, titleCliloc + 1, length, m, args, retainThroughDeath) + { + } - public BuffInfo( BuffIcon iconID, int titleCliloc, int secondaryCliloc, TimeSpan length, Mobile m, TextDefinition args, bool retainThroughDeath ) - : this( iconID, titleCliloc, secondaryCliloc, length, m ) - { - Args = args; - RetainThroughDeath = retainThroughDeath; - } + public BuffInfo(BuffIcon iconID, int titleCliloc, int secondaryCliloc, TimeSpan length, Mobile m, + TextDefinition args, bool retainThroughDeath) + : this(iconID, titleCliloc, secondaryCliloc, length, m) + { + Args = args; + RetainThroughDeath = retainThroughDeath; + } - #endregion + #endregion - #region Convenience Methods - public static void AddBuff( Mobile m, BuffInfo b ) - { - if ( m is PlayerMobile pm ) - pm.AddBuff( b ); - } + #region Convenience Methods - public static void RemoveBuff( Mobile m, BuffInfo b ) - { - if ( m is PlayerMobile pm ) - pm.RemoveBuff( b ); - } + public static void AddBuff(Mobile m, BuffInfo b) + { + if (m is PlayerMobile pm) + pm.AddBuff(b); + } - public static void RemoveBuff( Mobile m, BuffIcon b ) - { - if ( m is PlayerMobile pm ) - pm.RemoveBuff( b ); - } - #endregion - } + public static void RemoveBuff(Mobile m, BuffInfo b) + { + if (m is PlayerMobile pm) + pm.RemoveBuff(b); + } - public enum BuffIcon : short - { - DismountPrevention=0x3E9, - NoRearm=0x3EA, - //Currently, no 0x3EB or 0x3EC - NightSight=0x3ED, //* - DeathStrike, - EvilOmen, - UnknownStandingSwirl, //Which is healing throttle & Stamina throttle? - UnknownKneelingSword, - DivineFury, //* - EnemyOfOne, //* - HidingAndOrStealth, //* - ActiveMeditation, //* - BloodOathCaster, //* - BloodOathCurse, //* - CorpseSkin, //* - Mindrot, //* - PainSpike, //* - Strangle, - GiftOfRenewal, //* - AttuneWeapon, //* - Thunderstorm, //* - EssenceOfWind, //* - EtherealVoyage, //* - GiftOfLife, //* - ArcaneEmpowerment, //* - MortalStrike, - ReactiveArmor, //* - Protection, //* - ArchProtection, - MagicReflection, //* - Incognito, //* - Disguised, - AnimalForm, - Polymorph, - Invisibility, //* - Paralyze, //* - Poison, - Bleed, - Clumsy, //* - FeebleMind, //* - Weaken, //* - Curse, //* - MassCurse, - Agility, //* - Cunning, //* - Strength, //* - Bless, //* - Sleep, - StoneForm, - SpellPlague, - SpellTrigger, - NetherBolt, - Fly - } + public static void RemoveBuff(Mobile m, BuffIcon b) + { + if (m is PlayerMobile pm) + pm.RemoveBuff(b); + } - public sealed class AddBuffPacket : Packet - { - public AddBuffPacket( Mobile m, BuffInfo info ) - : this( m, info.ID, info.TitleCliloc, info.SecondaryCliloc, info.Args, (info.TimeStart != DateTime.MinValue) ? ((info.TimeStart + info.TimeLength) - DateTime.UtcNow) : TimeSpan.Zero ) - { - } + #endregion + } - public AddBuffPacket( Mobile mob, BuffIcon iconID, int titleCliloc, int secondaryCliloc, TextDefinition args, TimeSpan length ) - : base( 0xDF ) - { - bool hasArgs = (args != null); + public enum BuffIcon : short + { + DismountPrevention = 0x3E9, + NoRearm = 0x3EA, - EnsureCapacity( (hasArgs ? (48 + args.ToString().Length * 2): 44) ); - m_Stream.Write( (int)mob.Serial ); + //Currently, no 0x3EB or 0x3EC + NightSight = 0x3ED, //* + DeathStrike, + EvilOmen, + UnknownStandingSwirl, //Which is healing throttle & Stamina throttle? + UnknownKneelingSword, + DivineFury, //* + EnemyOfOne, //* + HidingAndOrStealth, //* + ActiveMeditation, //* + BloodOathCaster, //* + BloodOathCurse, //* + CorpseSkin, //* + Mindrot, //* + PainSpike, //* + Strangle, + GiftOfRenewal, //* + AttuneWeapon, //* + Thunderstorm, //* + EssenceOfWind, //* + EtherealVoyage, //* + GiftOfLife, //* + ArcaneEmpowerment, //* + MortalStrike, + ReactiveArmor, //* + Protection, //* + ArchProtection, + MagicReflection, //* + Incognito, //* + Disguised, + AnimalForm, + Polymorph, + Invisibility, //* + Paralyze, //* + Poison, + Bleed, + Clumsy, //* + FeebleMind, //* + Weaken, //* + Curse, //* + MassCurse, + Agility, //* + Cunning, //* + Strength, //* + Bless, //* + Sleep, + StoneForm, + SpellPlague, + SpellTrigger, + NetherBolt, + Fly + } + + public sealed class AddBuffPacket : Packet + { + public AddBuffPacket(Mobile m, BuffInfo info) + : this(m, info.ID, info.TitleCliloc, info.SecondaryCliloc, info.Args, + info.TimeStart != DateTime.MinValue ? info.TimeStart + info.TimeLength - DateTime.UtcNow : TimeSpan.Zero) + { + } + + public AddBuffPacket(Mobile mob, BuffIcon iconID, int titleCliloc, int secondaryCliloc, TextDefinition args, + TimeSpan length) + : base(0xDF) + { + bool hasArgs = args != null; + + EnsureCapacity(hasArgs ? 48 + args.ToString().Length * 2 : 44); + m_Stream.Write(mob.Serial); - m_Stream.Write( (short)iconID ); //ID - m_Stream.Write( (short)0x1 ); //Type 0 for removal. 1 for add 2 for Data + m_Stream.Write((short)iconID); //ID + m_Stream.Write((short)0x1); //Type 0 for removal. 1 for add 2 for Data - m_Stream.Fill( 4 ); + m_Stream.Fill(4); - m_Stream.Write( (short)iconID ); //ID - m_Stream.Write( (short)0x01 ); //Type 0 for removal. 1 for add 2 for Data + m_Stream.Write((short)iconID); //ID + m_Stream.Write((short)0x01); //Type 0 for removal. 1 for add 2 for Data - m_Stream.Fill( 4 ); + m_Stream.Fill(4); - if ( length < TimeSpan.Zero ) - length = TimeSpan.Zero; + if (length < TimeSpan.Zero) + length = TimeSpan.Zero; - m_Stream.Write( (short)length.TotalSeconds ); //Time in seconds + m_Stream.Write((short)length.TotalSeconds); //Time in seconds - m_Stream.Fill( 3 ); - m_Stream.Write( (int)titleCliloc ); - m_Stream.Write( (int)secondaryCliloc ); + m_Stream.Fill(3); + m_Stream.Write(titleCliloc); + m_Stream.Write(secondaryCliloc); - if ( !hasArgs ) - { - //m_Stream.Fill( 2 ); - m_Stream.Fill( 10 ); - } - else - { - m_Stream.Fill( 4 ); - m_Stream.Write( (short)0x1 ); //Unknown -> Possibly something saying 'hey, I have more data!'? - m_Stream.Fill( 2 ); + if (!hasArgs) + { + //m_Stream.Fill( 2 ); + m_Stream.Fill(10); + } + else + { + m_Stream.Fill(4); + m_Stream.Write((short)0x1); //Unknown -> Possibly something saying 'hey, I have more data!'? + m_Stream.Fill(2); - //m_Stream.WriteLittleUniNull( "\t#1018280" ); - m_Stream.WriteLittleUniNull($"\t{args.ToString()}"); + //m_Stream.WriteLittleUniNull( "\t#1018280" ); + m_Stream.WriteLittleUniNull($"\t{args}"); - m_Stream.Write( (short)0x1 ); //Even more Unknown -> Possibly something saying 'hey, I have more data!'? - m_Stream.Fill( 2 ); - } - } - } + m_Stream.Write((short)0x1); //Even more Unknown -> Possibly something saying 'hey, I have more data!'? + m_Stream.Fill(2); + } + } + } - public sealed class RemoveBuffPacket : Packet - { - public RemoveBuffPacket( Mobile mob, BuffInfo info ) - : this( mob, info.ID ) - { - } + public sealed class RemoveBuffPacket : Packet + { + public RemoveBuffPacket(Mobile mob, BuffInfo info) + : this(mob, info.ID) + { + } - public RemoveBuffPacket( Mobile mob, BuffIcon iconID ) - : base( 0xDF ) - { - EnsureCapacity( 13 ); - m_Stream.Write( (int)mob.Serial ); + public RemoveBuffPacket(Mobile mob, BuffIcon iconID) + : base(0xDF) + { + EnsureCapacity(13); + m_Stream.Write(mob.Serial); - m_Stream.Write( (short)iconID ); //ID - m_Stream.Write( (short)0x0 ); //Type 0 for removal. 1 for add 2 for Data + m_Stream.Write((short)iconID); //ID + m_Stream.Write((short)0x0); //Type 0 for removal. 1 for add 2 for Data - m_Stream.Fill( 4 ); - } - } -} + m_Stream.Fill(4); + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/CharacterCreation.cs b/Scripts/Misc/CharacterCreation.cs index 959eaad1e..baf8bc17b 100644 --- a/Scripts/Misc/CharacterCreation.cs +++ b/Scripts/Misc/CharacterCreation.cs @@ -1,1690 +1,1751 @@ using System; +using Server.Accounting; +using Server.Factions; using Server.Items; using Server.Mobiles; using Server.Network; -using Server.Accounting; namespace Server.Misc { - public class CharacterCreation - { - public static void Initialize() - { - // Register our event handler - EventSink.CharacterCreated += EventSink_CharacterCreated; - } + public class CharacterCreation + { + private static readonly CityInfo m_NewHavenInfo = + new CityInfo("New Haven", "The Bountiful Harvest Inn", 3503, 2574, 14, Map.Trammel); - private static void AddBackpack( Mobile m ) - { - Container pack = m.Backpack; + private static Mobile m_Mobile; - if ( pack == null ) - { - pack = new Backpack(); - pack.Movable = false; + public static void Initialize() + { + // Register our event handler + EventSink.CharacterCreated += EventSink_CharacterCreated; + } - m.AddItem( pack ); - } + private static void AddBackpack(Mobile m) + { + Container pack = m.Backpack; - PackItem( new RedBook( "a book", m.Name, 20, true ) ); - PackItem( new Gold( 1000 ) ); // Starting gold can be customized here - PackItem( new Dagger() ); - PackItem( new Candle() ); - } + if (pack == null) + { + pack = new Backpack(); + pack.Movable = false; - private static Item MakeNewbie( Item item ) - { - if ( !Core.AOS ) - item.LootType = LootType.Newbied; + m.AddItem(pack); + } - return item; - } + PackItem(new RedBook("a book", m.Name, 20, true)); + PackItem(new Gold(1000)); // Starting gold can be customized here + PackItem(new Dagger()); + PackItem(new Candle()); + } - private static void PlaceItemIn( Container parent, int x, int y, Item item ) - { - parent.AddItem( item ); - item.Location = new Point3D( x, y, 0 ); - } + private static Item MakeNewbie(Item item) + { + if (!Core.AOS) + item.LootType = LootType.Newbied; - private static Item MakePotionKeg( PotionEffect type, int hue ) - { - PotionKeg keg = new PotionKeg(); + return item; + } - keg.Held = 100; - keg.Type = type; - keg.Hue = hue; + private static void PlaceItemIn(Container parent, int x, int y, Item item) + { + parent.AddItem(item); + item.Location = new Point3D(x, y, 0); + } - return MakeNewbie( keg ); - } + private static Item MakePotionKeg(PotionEffect type, int hue) + { + PotionKeg keg = new PotionKeg(); - private static void FillBankAOS( Mobile m ) - { - BankBox bank = m.BankBox; + keg.Held = 100; + keg.Type = type; + keg.Hue = hue; - // The new AOS bankboxes don't have powerscrolls, they are automatically 'applied': + return MakeNewbie(keg); + } - for ( int i = 0; i < PowerScroll.Skills.Count; ++i ) - m.Skills[PowerScroll.Skills[ i ]].Cap = 120.0; + private static void FillBankAOS(Mobile m) + { + BankBox bank = m.BankBox; - m.StatCap = 250; + // The new AOS bankboxes don't have powerscrolls, they are automatically 'applied': + for (int i = 0; i < PowerScroll.Skills.Count; ++i) + m.Skills[PowerScroll.Skills[i]].Cap = 120.0; - Container cont; + m.StatCap = 250; - // Begin box of money - cont = new WoodenBox(); - cont.ItemID = 0xE7D; - cont.Hue = 0x489; + Container cont; - PlaceItemIn( cont, 16, 51, new BankCheck( 500000 ) ); - PlaceItemIn( cont, 28, 51, new BankCheck( 250000 ) ); - PlaceItemIn( cont, 40, 51, new BankCheck( 100000 ) ); - PlaceItemIn( cont, 52, 51, new BankCheck( 100000 ) ); - PlaceItemIn( cont, 64, 51, new BankCheck( 50000 ) ); - PlaceItemIn( cont, 16, 115, new Factions.Silver( 9000 ) ); - PlaceItemIn( cont, 34, 115, new Gold( 60000 ) ); + // Begin box of money + cont = new WoodenBox(); + cont.ItemID = 0xE7D; + cont.Hue = 0x489; - PlaceItemIn( bank, 18, 169, cont ); - // End box of money + PlaceItemIn(cont, 16, 51, new BankCheck(500000)); + PlaceItemIn(cont, 28, 51, new BankCheck(250000)); + PlaceItemIn(cont, 40, 51, new BankCheck(100000)); + PlaceItemIn(cont, 52, 51, new BankCheck(100000)); + PlaceItemIn(cont, 64, 51, new BankCheck(50000)); + PlaceItemIn(cont, 16, 115, new Silver(9000)); + PlaceItemIn(cont, 34, 115, new Gold(60000)); - // Begin bag of potion kegs - cont = new Backpack(); - cont.Name = "Various Potion Kegs"; + PlaceItemIn(bank, 18, 169, cont); + // End box of money - PlaceItemIn( cont, 45, 149, MakePotionKeg( PotionEffect.CureGreater, 0x2D ) ); - PlaceItemIn( cont, 69, 149, MakePotionKeg( PotionEffect.HealGreater, 0x499 ) ); - PlaceItemIn( cont, 93, 149, MakePotionKeg( PotionEffect.PoisonDeadly, 0x46 ) ); - PlaceItemIn( cont, 117, 149, MakePotionKeg( PotionEffect.RefreshTotal, 0x21 ) ); - PlaceItemIn( cont, 141, 149, MakePotionKeg( PotionEffect.ExplosionGreater, 0x74 ) ); - PlaceItemIn( cont, 93, 82, new Bottle( 1000 ) ); - - PlaceItemIn( bank, 53, 169, cont ); - // End bag of potion kegs + // Begin bag of potion kegs + cont = new Backpack(); + cont.Name = "Various Potion Kegs"; + PlaceItemIn(cont, 45, 149, MakePotionKeg(PotionEffect.CureGreater, 0x2D)); + PlaceItemIn(cont, 69, 149, MakePotionKeg(PotionEffect.HealGreater, 0x499)); + PlaceItemIn(cont, 93, 149, MakePotionKeg(PotionEffect.PoisonDeadly, 0x46)); + PlaceItemIn(cont, 117, 149, MakePotionKeg(PotionEffect.RefreshTotal, 0x21)); + PlaceItemIn(cont, 141, 149, MakePotionKeg(PotionEffect.ExplosionGreater, 0x74)); - // Begin bag of tools - cont = new Bag(); - cont.Name = "Tool Bag"; - - PlaceItemIn( cont, 30, 35, new TinkerTools( 1000 ) ); - PlaceItemIn( cont, 60, 35, new HousePlacementTool() ); - PlaceItemIn( cont, 90, 35, new DovetailSaw( 1000 ) ); - PlaceItemIn( cont, 30, 68, new Scissors() ); - PlaceItemIn( cont, 45, 68, new MortarPestle( 1000 ) ); - PlaceItemIn( cont, 75, 68, new ScribesPen( 1000 ) ); - PlaceItemIn( cont, 90, 68, new SmithHammer( 1000 ) ); - PlaceItemIn( cont, 30, 118, new TwoHandedAxe() ); - PlaceItemIn( cont, 60, 118, new FletcherTools( 1000 ) ); - PlaceItemIn( cont, 90, 118, new SewingKit( 1000 ) ); + PlaceItemIn(cont, 93, 82, new Bottle(1000)); - PlaceItemIn( cont, 36, 51, new RunicHammer( CraftResource.DullCopper, 1000 ) ); - PlaceItemIn( cont, 42, 51, new RunicHammer( CraftResource.ShadowIron, 1000 ) ); - PlaceItemIn( cont, 48, 51, new RunicHammer( CraftResource.Copper, 1000 ) ); - PlaceItemIn( cont, 54, 51, new RunicHammer( CraftResource.Bronze, 1000 ) ); - PlaceItemIn( cont, 61, 51, new RunicHammer( CraftResource.Gold, 1000 ) ); - PlaceItemIn( cont, 67, 51, new RunicHammer( CraftResource.Agapite, 1000 ) ); - PlaceItemIn( cont, 73, 51, new RunicHammer( CraftResource.Verite, 1000 ) ); - PlaceItemIn( cont, 79, 51, new RunicHammer( CraftResource.Valorite, 1000 ) ); + PlaceItemIn(bank, 53, 169, cont); + // End bag of potion kegs - PlaceItemIn( cont, 36, 55, new RunicSewingKit( CraftResource.SpinedLeather, 1000 ) ); - PlaceItemIn( cont, 42, 55, new RunicSewingKit( CraftResource.HornedLeather, 1000 ) ); - PlaceItemIn( cont, 48, 55, new RunicSewingKit( CraftResource.BarbedLeather, 1000 ) ); - PlaceItemIn( bank, 118, 169, cont ); - // End bag of tools + // Begin bag of tools + cont = new Bag(); + cont.Name = "Tool Bag"; + PlaceItemIn(cont, 30, 35, new TinkerTools(1000)); + PlaceItemIn(cont, 60, 35, new HousePlacementTool()); + PlaceItemIn(cont, 90, 35, new DovetailSaw(1000)); + PlaceItemIn(cont, 30, 68, new Scissors()); + PlaceItemIn(cont, 45, 68, new MortarPestle(1000)); + PlaceItemIn(cont, 75, 68, new ScribesPen(1000)); + PlaceItemIn(cont, 90, 68, new SmithHammer(1000)); + PlaceItemIn(cont, 30, 118, new TwoHandedAxe()); + PlaceItemIn(cont, 60, 118, new FletcherTools(1000)); + PlaceItemIn(cont, 90, 118, new SewingKit(1000)); - // Begin bag of archery ammo - cont = new Bag(); - cont.Name = "Bag Of Archery Ammo"; + PlaceItemIn(cont, 36, 51, new RunicHammer(CraftResource.DullCopper, 1000)); + PlaceItemIn(cont, 42, 51, new RunicHammer(CraftResource.ShadowIron, 1000)); + PlaceItemIn(cont, 48, 51, new RunicHammer(CraftResource.Copper, 1000)); + PlaceItemIn(cont, 54, 51, new RunicHammer(CraftResource.Bronze, 1000)); + PlaceItemIn(cont, 61, 51, new RunicHammer(CraftResource.Gold, 1000)); + PlaceItemIn(cont, 67, 51, new RunicHammer(CraftResource.Agapite, 1000)); + PlaceItemIn(cont, 73, 51, new RunicHammer(CraftResource.Verite, 1000)); + PlaceItemIn(cont, 79, 51, new RunicHammer(CraftResource.Valorite, 1000)); - PlaceItemIn( cont, 48, 76, new Arrow( 5000 ) ); - PlaceItemIn( cont, 72, 76, new Bolt( 5000 ) ); + PlaceItemIn(cont, 36, 55, new RunicSewingKit(CraftResource.SpinedLeather, 1000)); + PlaceItemIn(cont, 42, 55, new RunicSewingKit(CraftResource.HornedLeather, 1000)); + PlaceItemIn(cont, 48, 55, new RunicSewingKit(CraftResource.BarbedLeather, 1000)); - PlaceItemIn( bank, 118, 124, cont ); - // End bag of archery ammo + PlaceItemIn(bank, 118, 169, cont); + // End bag of tools - // Begin bag of treasure maps - cont = new Bag(); - cont.Name = "Bag Of Treasure Maps"; + // Begin bag of archery ammo + cont = new Bag(); + cont.Name = "Bag Of Archery Ammo"; - PlaceItemIn( cont, 30, 35, new TreasureMap( 1, Map.Trammel ) ); - PlaceItemIn( cont, 45, 35, new TreasureMap( 2, Map.Trammel ) ); - PlaceItemIn( cont, 60, 35, new TreasureMap( 3, Map.Trammel ) ); - PlaceItemIn( cont, 75, 35, new TreasureMap( 4, Map.Trammel ) ); - PlaceItemIn( cont, 90, 35, new TreasureMap( 5, Map.Trammel ) ); - PlaceItemIn( cont, 90, 35, new TreasureMap( 6, Map.Trammel ) ); + PlaceItemIn(cont, 48, 76, new Arrow(5000)); + PlaceItemIn(cont, 72, 76, new Bolt(5000)); - PlaceItemIn( cont, 30, 50, new TreasureMap( 1, Map.Trammel ) ); - PlaceItemIn( cont, 45, 50, new TreasureMap( 2, Map.Trammel ) ); - PlaceItemIn( cont, 60, 50, new TreasureMap( 3, Map.Trammel ) ); - PlaceItemIn( cont, 75, 50, new TreasureMap( 4, Map.Trammel ) ); - PlaceItemIn( cont, 90, 50, new TreasureMap( 5, Map.Trammel ) ); - PlaceItemIn( cont, 90, 50, new TreasureMap( 6, Map.Trammel ) ); + PlaceItemIn(bank, 118, 124, cont); + // End bag of archery ammo - PlaceItemIn( cont, 55, 100, new Lockpick( 30 ) ); - PlaceItemIn( cont, 60, 100, new Pickaxe() ); - - PlaceItemIn( bank, 98, 124, cont ); - // End bag of treasure maps + // Begin bag of treasure maps + cont = new Bag(); + cont.Name = "Bag Of Treasure Maps"; - // Begin bag of raw materials - cont = new Bag(); - cont.Hue = 0x835; - cont.Name = "Raw Materials Bag"; + PlaceItemIn(cont, 30, 35, new TreasureMap(1, Map.Trammel)); + PlaceItemIn(cont, 45, 35, new TreasureMap(2, Map.Trammel)); + PlaceItemIn(cont, 60, 35, new TreasureMap(3, Map.Trammel)); + PlaceItemIn(cont, 75, 35, new TreasureMap(4, Map.Trammel)); + PlaceItemIn(cont, 90, 35, new TreasureMap(5, Map.Trammel)); + PlaceItemIn(cont, 90, 35, new TreasureMap(6, Map.Trammel)); - PlaceItemIn( cont, 92, 60, new BarbedLeather( 5000 ) ); - PlaceItemIn( cont, 92, 68, new HornedLeather( 5000 ) ); - PlaceItemIn( cont, 92, 76, new SpinedLeather( 5000 ) ); - PlaceItemIn( cont, 92, 84, new Leather( 5000 ) ); + PlaceItemIn(cont, 30, 50, new TreasureMap(1, Map.Trammel)); + PlaceItemIn(cont, 45, 50, new TreasureMap(2, Map.Trammel)); + PlaceItemIn(cont, 60, 50, new TreasureMap(3, Map.Trammel)); + PlaceItemIn(cont, 75, 50, new TreasureMap(4, Map.Trammel)); + PlaceItemIn(cont, 90, 50, new TreasureMap(5, Map.Trammel)); + PlaceItemIn(cont, 90, 50, new TreasureMap(6, Map.Trammel)); - PlaceItemIn( cont, 30, 118, new Cloth( 5000 ) ); - PlaceItemIn( cont, 30, 84, new Board( 5000 ) ); - PlaceItemIn( cont, 57, 80, new BlankScroll( 500 ) ); - - PlaceItemIn( cont, 30, 35, new DullCopperIngot( 5000 ) ); - PlaceItemIn( cont, 37, 35, new ShadowIronIngot( 5000 ) ); - PlaceItemIn( cont, 44, 35, new CopperIngot( 5000 ) ); - PlaceItemIn( cont, 51, 35, new BronzeIngot( 5000 ) ); - PlaceItemIn( cont, 58, 35, new GoldIngot( 5000 ) ); - PlaceItemIn( cont, 65, 35, new AgapiteIngot( 5000 ) ); - PlaceItemIn( cont, 72, 35, new VeriteIngot( 5000 ) ); - PlaceItemIn( cont, 79, 35, new ValoriteIngot( 5000 ) ); - PlaceItemIn( cont, 86, 35, new IronIngot( 5000 ) ); - - PlaceItemIn( cont, 30, 59, new RedScales( 5000 ) ); - PlaceItemIn( cont, 36, 59, new YellowScales( 5000 ) ); - PlaceItemIn( cont, 42, 59, new BlackScales( 5000 ) ); - PlaceItemIn( cont, 48, 59, new GreenScales( 5000 ) ); - PlaceItemIn( cont, 54, 59, new WhiteScales( 5000 ) ); - PlaceItemIn( cont, 60, 59, new BlueScales( 5000 ) ); - - PlaceItemIn( bank, 98, 169, cont ); - // End bag of raw materials - - - // Begin bag of spell casting stuff - cont = new Backpack(); - cont.Hue = 0x480; - cont.Name = "Spell Casting Stuff"; - - PlaceItemIn( cont, 45, 105, new Spellbook( ulong.MaxValue ) ); - PlaceItemIn( cont, 65, 105, new NecromancerSpellbook( (ulong)0xFFFF ) ); - PlaceItemIn( cont, 85, 105, new BookOfChivalry( (ulong)0x3FF ) ); - PlaceItemIn( cont, 105, 105, new BookOfBushido() ); //Default ctor = full - PlaceItemIn( cont, 125, 105, new BookOfNinjitsu() ); //Default ctor = full - - Runebook runebook = new Runebook( 10 ); - runebook.CurCharges = runebook.MaxCharges; - PlaceItemIn( cont, 145, 105, runebook ); - - Item toHue = new BagOfReagents( 150 ); - toHue.Hue = 0x2D; - PlaceItemIn( cont, 45, 150, toHue ); - - toHue = new BagOfNecroReagents( 150 ); - toHue.Hue = 0x488; - PlaceItemIn( cont, 65, 150, toHue ); - - PlaceItemIn( cont, 140, 150, new BagOfAllReagents( 500 ) ); - - for ( int i = 0; i < 9; ++i ) - PlaceItemIn( cont, 45 + (i * 10), 75, new RecallRune() ); - - PlaceItemIn( cont, 141, 74, new FireHorn() ); - - PlaceItemIn( bank, 78, 169, cont ); - // End bag of spell casting stuff - - - // Begin bag of ethereals - cont = new Backpack(); - cont.Hue = 0x490; - cont.Name = "Bag Of Ethy's!"; - - PlaceItemIn( cont, 45, 66, new EtherealHorse() ); - PlaceItemIn( cont, 69, 82, new EtherealOstard() ); - PlaceItemIn( cont, 93, 99, new EtherealLlama() ); - PlaceItemIn( cont, 117, 115, new EtherealKirin() ); - PlaceItemIn( cont, 45, 132, new EtherealUnicorn() ); - PlaceItemIn( cont, 69, 66, new EtherealRidgeback() ); - PlaceItemIn( cont, 93, 82, new EtherealSwampDragon() ); - PlaceItemIn( cont, 117, 99, new EtherealBeetle() ); - - PlaceItemIn( bank, 38, 124, cont ); - // End bag of ethereals - - - // Begin first bag of artifacts - cont = new Backpack(); - cont.Hue = 0x48F; - cont.Name = "Bag of Artifacts"; - - PlaceItemIn( cont, 45, 66, new TitansHammer() ); - PlaceItemIn( cont, 69, 82, new InquisitorsResolution() ); - PlaceItemIn( cont, 93, 99, new BladeOfTheRighteous() ); - PlaceItemIn( cont, 117, 115, new ZyronicClaw() ); - - PlaceItemIn( bank, 58, 124, cont ); - // End first bag of artifacts - - - // Begin second bag of artifacts - cont = new Backpack(); - cont.Hue = 0x48F; - cont.Name = "Bag of Artifacts"; - - PlaceItemIn( cont, 45, 66, new GauntletsOfNobility() ); - PlaceItemIn( cont, 69, 82, new MidnightBracers() ); - PlaceItemIn( cont, 93, 99, new VoiceOfTheFallenKing() ); - PlaceItemIn( cont, 117, 115, new OrnateCrownOfTheHarrower() ); - PlaceItemIn( cont, 45, 132, new HelmOfInsight() ); - PlaceItemIn( cont, 69, 66, new HolyKnightsBreastplate() ); - PlaceItemIn( cont, 93, 82, new ArmorOfFortune() ); - PlaceItemIn( cont, 117, 99, new TunicOfFire() ); - PlaceItemIn( cont, 45, 115, new LeggingsOfBane() ); - PlaceItemIn( cont, 69, 132, new ArcaneShield() ); - PlaceItemIn( cont, 93, 66, new Aegis() ); - PlaceItemIn( cont, 117, 82, new RingOfTheVile() ); - PlaceItemIn( cont, 45, 99, new BraceletOfHealth() ); - PlaceItemIn( cont, 69, 115, new RingOfTheElements() ); - PlaceItemIn( cont, 93, 132, new OrnamentOfTheMagician() ); - PlaceItemIn( cont, 117, 66, new DivineCountenance() ); - PlaceItemIn( cont, 45, 82, new JackalsCollar() ); - PlaceItemIn( cont, 69, 99, new HuntersHeaddress() ); - PlaceItemIn( cont, 93, 115, new HatOfTheMagi() ); - PlaceItemIn( cont, 117, 132, new ShadowDancerLeggings() ); - PlaceItemIn( cont, 45, 66, new SpiritOfTheTotem() ); - PlaceItemIn( cont, 69, 82, new BladeOfInsanity() ); - PlaceItemIn( cont, 93, 99, new AxeOfTheHeavens() ); - PlaceItemIn( cont, 117, 115, new TheBeserkersMaul() ); - PlaceItemIn( cont, 45, 132, new Frostbringer() ); - PlaceItemIn( cont, 69, 66, new BreathOfTheDead() ); - PlaceItemIn( cont, 93, 82, new TheDragonSlayer() ); - PlaceItemIn( cont, 117, 99, new BoneCrusher() ); - PlaceItemIn( cont, 45, 115, new StaffOfTheMagi() ); - PlaceItemIn( cont, 69, 132, new SerpentsFang() ); - PlaceItemIn( cont, 93, 66, new LegacyOfTheDreadLord() ); - PlaceItemIn( cont, 117, 82, new TheTaskmaster() ); - PlaceItemIn( cont, 45, 99, new TheDryadBow() ); - - PlaceItemIn( bank, 78, 124, cont ); - // End second bag of artifacts - - // Begin bag of minor artifacts - cont = new Backpack(); - cont.Hue = 0x48F; - cont.Name = "Bag of Minor Artifacts"; - - - PlaceItemIn( cont, 45, 66, new LunaLance() ); - PlaceItemIn( cont, 69, 82, new VioletCourage() ); - PlaceItemIn( cont, 93, 99, new CavortingClub() ); - PlaceItemIn( cont, 117, 115, new CaptainQuacklebushsCutlass() ); - PlaceItemIn( cont, 45, 132, new NightsKiss() ); - PlaceItemIn( cont, 69, 66, new ShipModelOfTheHMSCape() ); - PlaceItemIn( cont, 93, 82, new AdmiralsHeartyRum() ); - PlaceItemIn( cont, 117, 99, new CandelabraOfSouls() ); - PlaceItemIn( cont, 45, 115, new IolosLute() ); - PlaceItemIn( cont, 69, 132, new GwennosHarp() ); - PlaceItemIn( cont, 93, 66, new ArcticDeathDealer() ); - PlaceItemIn( cont, 117, 82, new EnchantedTitanLegBone() ); - PlaceItemIn( cont, 45, 99, new NoxRangersHeavyCrossbow() ); - PlaceItemIn( cont, 69, 115, new BlazeOfDeath() ); - PlaceItemIn( cont, 93, 132, new DreadPirateHat() ); - PlaceItemIn( cont, 117, 66, new BurglarsBandana() ); - PlaceItemIn( cont, 45, 82, new GoldBricks() ); - PlaceItemIn( cont, 69, 99, new AlchemistsBauble() ); - PlaceItemIn( cont, 93, 115, new PhillipsWoodenSteed() ); - PlaceItemIn( cont, 117, 132, new PolarBearMask() ); - PlaceItemIn( cont, 45, 66, new BowOfTheJukaKing() ); - PlaceItemIn( cont, 69, 82, new GlovesOfThePugilist() ); - PlaceItemIn( cont, 93, 99, new OrcishVisage() ); - PlaceItemIn( cont, 117, 115, new StaffOfPower() ); - PlaceItemIn( cont, 45, 132, new ShieldOfInvulnerability() ); - PlaceItemIn( cont, 69, 66, new HeartOfTheLion() ); - PlaceItemIn( cont, 93, 82, new ColdBlood() ); - PlaceItemIn( cont, 117, 99, new GhostShipAnchor() ); - PlaceItemIn( cont, 45, 115, new SeahorseStatuette() ); - PlaceItemIn( cont, 69, 132, new WrathOfTheDryad() ); - PlaceItemIn( cont, 93, 66, new PixieSwatter() ); - - for( int i = 0; i < 10; i++ ) - PlaceItemIn( cont, 117, 128, new MessageInABottle( Utility.RandomBool() ? Map.Trammel : Map.Felucca, 4 ) ); - - PlaceItemIn( bank, 18, 124, cont ); - - if ( Core.SE ) - { - cont = new Bag(); - cont.Hue = 0x501; - cont.Name = "Tokuno Minor Artifacts"; - - PlaceItemIn( cont, 42, 70, new Exiler() ); - PlaceItemIn( cont, 38, 53, new HanzosBow() ); - PlaceItemIn( cont, 45, 40, new TheDestroyer() ); - PlaceItemIn( cont, 92, 80, new DragonNunchaku() ); - PlaceItemIn( cont, 42, 56, new PeasantsBokuto() ); - PlaceItemIn( cont, 44, 71, new TomeOfEnlightenment() ); - PlaceItemIn( cont, 35, 35, new ChestOfHeirlooms() ); - PlaceItemIn( cont, 29, 0, new HonorableSwords() ); - PlaceItemIn( cont, 49, 85, new AncientUrn() ); - PlaceItemIn( cont, 51, 58, new FluteOfRenewal() ); - PlaceItemIn( cont, 70, 51, new PigmentsOfTokuno() ); - PlaceItemIn( cont, 40, 79, new AncientSamuraiDo() ); - PlaceItemIn( cont, 51, 61, new LegsOfStability() ); - PlaceItemIn( cont, 88, 78, new GlovesOfTheSun() ); - PlaceItemIn( cont, 55, 62, new AncientFarmersKasa() ); - PlaceItemIn( cont, 55, 83, new ArmsOfTacticalExcellence() ); - PlaceItemIn( cont, 50, 85, new DaimyosHelm() ); - PlaceItemIn( cont, 52, 78, new BlackLotusHood() ); - PlaceItemIn( cont, 52, 79, new DemonForks() ); - PlaceItemIn( cont, 33, 49, new PilferedDancerFans() ); - - PlaceItemIn( bank, 58, 124, cont ); - } - - if ( Core.SE ) //This bag came only after SE. - { - cont = new Bag(); - cont.Name = "Bag of Bows"; - - PlaceItemIn( cont, 31, 84, new Bow() ); - PlaceItemIn( cont, 78, 74, new CompositeBow() ); - PlaceItemIn( cont, 53, 71, new Crossbow() ); - PlaceItemIn( cont, 56, 39, new HeavyCrossbow() ); - PlaceItemIn( cont, 82, 72, new RepeatingCrossbow() ); - PlaceItemIn( cont, 49, 45, new Yumi() ); - - for( int i = 0; i < cont.Items.Count; i++ ) - { - if ( cont.Items[i] is BaseRanged bow ) - { - bow.Attributes.WeaponSpeed = 35; - bow.Attributes.WeaponDamage = 35; - } - } - - PlaceItemIn( bank, 108, 135, cont ); - } - } - - private static void FillBankbox( Mobile m ) - { - if ( Core.AOS ) - { - FillBankAOS( m ); - return; - } - - BankBox bank = m.BankBox; - - bank.DropItem( new BankCheck( 1000000 ) ); - - // Full spellbook - Spellbook book = new Spellbook(); - - book.Content = ulong.MaxValue; - - bank.DropItem( book ); - - Bag bag = new Bag(); - - for ( int i = 0; i < 5; ++i ) - bag.DropItem( new Moonstone( MoonstoneType.Felucca ) ); - - // Felucca moonstones - bank.DropItem( bag ); - - bag = new Bag(); - - for ( int i = 0; i < 5; ++i ) - bag.DropItem( new Moonstone( MoonstoneType.Trammel ) ); - - // Trammel moonstones - bank.DropItem( bag ); - - // Treasure maps - bank.DropItem( new TreasureMap( 1, Map.Trammel ) ); - bank.DropItem( new TreasureMap( 2, Map.Trammel ) ); - bank.DropItem( new TreasureMap( 3, Map.Trammel ) ); - bank.DropItem( new TreasureMap( 4, Map.Trammel ) ); - bank.DropItem( new TreasureMap( 5, Map.Trammel ) ); - - // Bag containing 50 of each reagent - bank.DropItem( new BagOfReagents( 50 ) ); - - // Craft tools - bank.DropItem( MakeNewbie( new Scissors() ) ); - bank.DropItem( MakeNewbie( new SewingKit( 1000 ) ) ); - bank.DropItem( MakeNewbie( new SmithHammer( 1000 ) ) ); - bank.DropItem( MakeNewbie( new FletcherTools( 1000 ) ) ); - bank.DropItem( MakeNewbie( new DovetailSaw( 1000 ) ) ); - bank.DropItem( MakeNewbie( new MortarPestle( 1000 ) ) ); - bank.DropItem( MakeNewbie( new ScribesPen( 1000 ) ) ); - bank.DropItem( MakeNewbie( new TinkerTools( 1000 ) ) ); - - // A few dye tubs - bank.DropItem( new Dyes() ); - bank.DropItem( new DyeTub() ); - bank.DropItem( new DyeTub() ); - bank.DropItem( new BlackDyeTub() ); - - DyeTub darkRedTub = new DyeTub(); - - darkRedTub.DyedHue = 0x485; - darkRedTub.Redyable = false; - - bank.DropItem( darkRedTub ); - - // Some food - bank.DropItem( MakeNewbie( new Apple( 1000 ) ) ); - - // Resources - bank.DropItem( MakeNewbie( new Feather( 1000 ) ) ); - bank.DropItem( MakeNewbie( new BoltOfCloth( 1000 ) ) ); - bank.DropItem( MakeNewbie( new BlankScroll( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Hides( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Bandage( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Bottle( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Log( 1000 ) ) ); - - bank.DropItem( MakeNewbie( new IronIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new DullCopperIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new ShadowIronIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new CopperIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new BronzeIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new GoldIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new AgapiteIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new VeriteIngot( 5000 ) ) ); - bank.DropItem( MakeNewbie( new ValoriteIngot( 5000 ) ) ); - - // Reagents - bank.DropItem( MakeNewbie( new BlackPearl( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Bloodmoss( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Garlic( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Ginseng( 1000 ) ) ); - bank.DropItem( MakeNewbie( new MandrakeRoot( 1000 ) ) ); - bank.DropItem( MakeNewbie( new Nightshade( 1000 ) ) ); - bank.DropItem( MakeNewbie( new SulfurousAsh( 1000 ) ) ); - bank.DropItem( MakeNewbie( new SpidersSilk( 1000 ) ) ); - - // Some extra starting gold - bank.DropItem( MakeNewbie( new Gold( 9000 ) ) ); - - // 5 blank recall runes - for ( int i = 0; i < 5; ++i ) - bank.DropItem( MakeNewbie( new RecallRune() ) ); - - AddPowerScrolls( bank ); - } - - private static void AddPowerScrolls( BankBox bank ) - { - Bag bag = new Bag(); - - for ( int i = 0; i < PowerScroll.Skills.Count; ++i ) - bag.DropItem( new PowerScroll( PowerScroll.Skills[i], 120.0 ) ); - - bag.DropItem( new StatCapScroll( 250 ) ); - - bank.DropItem( bag ); - } - - private static void AddShirt( Mobile m, int shirtHue ) - { - int hue = Utility.ClipDyedHue( shirtHue & 0x3FFF ); - - if ( m.Race == Race.Elf ) - { - EquipItem( new ElvenShirt( hue ), true ); - } - else - { - switch ( Utility.Random( 3 ) ) - { - case 0: EquipItem( new Shirt( hue ), true ); break; - case 1: EquipItem( new FancyShirt( hue ), true ); break; - case 2: EquipItem( new Doublet( hue ), true ); break; - } - } - } - - private static void AddPants( Mobile m, int pantsHue ) - { - int hue = Utility.ClipDyedHue( pantsHue & 0x3FFF ); - - if ( m.Race == Race.Elf ) - { - EquipItem( new ElvenPants( hue ), true ); - } - else - { - if ( m.Female ) - { - switch ( Utility.Random( 2 ) ) - { - case 0: EquipItem( new Skirt( hue ), true ); break; - case 1: EquipItem( new Kilt( hue ), true ); break; - } - } - else - { - switch ( Utility.Random( 2 ) ) - { - case 0: EquipItem( new LongPants( hue ), true ); break; - case 1: EquipItem( new ShortPants( hue ), true ); break; - } - } - } - } - - private static void AddShoes( Mobile m ) - { - if ( m.Race == Race.Elf ) - EquipItem( new ElvenBoots(), true ); - else - EquipItem( new Shoes( Utility.RandomYellowHue() ), true ); - } - - private static Mobile CreateMobile( Account a ) - { - if ( a.Count >= a.Limit ) - return null; - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] == null ) - return (a[i] = new PlayerMobile()); - } - - return null; - } - - private static void EventSink_CharacterCreated( CharacterCreatedEventArgs args ) - { - if ( !VerifyProfession( args.Profession ) ) - args.Profession = 0; - - NetState state = args.State; - - if ( state == null ) - return; - - Mobile newChar = CreateMobile( args.Account as Account ); - - if ( newChar == null ) - { - Console.WriteLine( "Login: {0}: Character creation failed, account full", state ); - return; - } - - args.Mobile = newChar; - m_Mobile = newChar; - - newChar.Player = true; - newChar.AccessLevel = args.Account.AccessLevel; - newChar.Female = args.Female; - //newChar.Body = newChar.Female ? 0x191 : 0x190; - - if ( Core.Expansion >= args.Race.RequiredExpansion ) - newChar.Race = args.Race; //Sets body - else - newChar.Race = Race.DefaultRace; - - //newChar.Hue = Utility.ClipSkinHue( args.Hue & 0x3FFF ) | 0x8000; - newChar.Hue = newChar.Race.ClipSkinHue( args.Hue & 0x3FFF ) | 0x8000; - - newChar.Hunger = 20; - - bool young = false; - - if ( newChar is PlayerMobile pm ) - { - pm.Profession = args.Profession; - - if ( pm.AccessLevel == AccessLevel.Player && ((Account)pm.Account).Young ) - young = pm.Young = true; - } - - SetName( newChar, args.Name ); - - AddBackpack( newChar ); - - SetStats( newChar, state, args.Str, args.Dex, args.Int ); - SetSkills( newChar, args.Skills, args.Profession ); - - Race race = newChar.Race; - - if ( race.ValidateHair( newChar, args.HairID ) ) - { - newChar.HairItemID = args.HairID; - newChar.HairHue = race.ClipHairHue( args.HairHue & 0x3FFF ); - } - - if ( race.ValidateFacialHair( newChar, args.BeardID ) ) - { - newChar.FacialHairItemID = args.BeardID; - newChar.FacialHairHue = race.ClipHairHue( args.BeardHue & 0x3FFF ); - } - - if ( args.Profession <= 3 ) - { - AddShirt( newChar, args.ShirtHue ); - AddPants( newChar, args.PantsHue ); - AddShoes( newChar ); - } - - if ( TestCenter.Enabled ) - FillBankbox( newChar ); - - if ( young ) - { - NewPlayerTicket ticket = new NewPlayerTicket(); - ticket.Owner = newChar; - newChar.BankBox.DropItem( ticket ); - } - - CityInfo city = GetStartLocation( args, young ); - - newChar.MoveToWorld( city.Location, city.Map ); - - Console.WriteLine( "Login: {0}: New character being created (account={1})", state, args.Account.Username ); - Console.WriteLine( " - Character: {0} (serial={1})", newChar.Name, newChar.Serial ); - Console.WriteLine( " - Started: {0} {1} in {2}", city.City, city.Location, city.Map.ToString() ); - - new WelcomeTimer( newChar ).Start(); - } - - public static bool VerifyProfession( int profession ) - { - if ( profession < 0 ) - return false; - if ( profession < 4 ) - return true; - if ( Core.AOS && profession < 6 ) - return true; - if ( Core.SE && profession < 8 ) - return true; - - return false; - } - - private class BadStartMessage : Timer - { - Mobile m_Mobile; - int m_Message; - public BadStartMessage( Mobile m, int message ) : base( TimeSpan.FromSeconds ( 3.5 ) ) - { - m_Mobile = m; - m_Message = message; - Start(); - } - - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( m_Message ); - } - } - - private static readonly CityInfo m_NewHavenInfo = new CityInfo( "New Haven", "The Bountiful Harvest Inn", 3503, 2574, 14, Map.Trammel ); - - private static CityInfo GetStartLocation( CharacterCreatedEventArgs args, bool isYoung ) - { - if ( Core.ML ) - { - //if ( args.State != null && args.State.NewHaven ) - return m_NewHavenInfo; //We don't get the client Version until AFTER Character creation - - //return args.City; TODO: Uncomment when the old quest system is actually phased out - } - - bool useHaven = isYoung; - - ClientFlags flags = args.State?.Flags ?? ClientFlags.None; - Mobile m = args.Mobile; - - switch ( args.Profession ) - { - case 4: //Necro - { - if ( (flags & ClientFlags.Malas) != 0 ) - { - return new CityInfo( "Umbra", "Mardoth's Tower", 2114, 1301, -50, Map.Malas ); - } - - useHaven = true; - - new BadStartMessage( m, 1062205 ); - /* - * Unfortunately you are playing on a *NON-Age-Of-Shadows* game - * installation and cannot be transported to Malas. - * You will not be able to take your new player quest in Malas - * without an AOS client. You are now being taken to the city of - * Haven on the Trammel facet. - * */ - - break; - } - case 5: //Paladin - { - return m_NewHavenInfo; - } - case 6: //Samurai - { - if ( (flags & ClientFlags.Tokuno) != 0 ) - { - return new CityInfo( "Samurai DE", "Haoti's Grounds", 368, 780, -1, Map.Malas ); - } - - useHaven = true; - - new BadStartMessage( m, 1063487 ); - /* - * Unfortunately you are playing on a *NON-Samurai-Empire* game - * installation and cannot be transported to Tokuno. - * You will not be able to take your new player quest in Tokuno - * without an SE client. You are now being taken to the city of - * Haven on the Trammel facet. - * */ - - break; - } - case 7: //Ninja - { - if ( (flags & ClientFlags.Tokuno) != 0 ) - { - return new CityInfo( "Ninja DE", "Enimo's Residence", 414, 823, -1, Map.Malas ); - } - - useHaven = true; - - new BadStartMessage( m, 1063487 ); - /* - * Unfortunately you are playing on a *NON-Samurai-Empire* game - * installation and cannot be transported to Tokuno. - * You will not be able to take your new player quest in Tokuno - * without an SE client. You are now being taken to the city of - * Haven on the Trammel facet. - * */ - - break; - } - } - - if ( useHaven ) - return m_NewHavenInfo; - - return args.City; - } - - private static void FixStats( ref int str, ref int dex, ref int intel, int max ) - { - int vMax = max - 30; - - int vStr = str - 10; - int vDex = dex - 10; - int vInt = intel - 10; - - if ( vStr < 0 ) - vStr = 0; - - if ( vDex < 0 ) - vDex = 0; - - if ( vInt < 0 ) - vInt = 0; - - int total = vStr + vDex + vInt; - - if ( total == 0 || total == vMax ) - return; - - double scalar = vMax / (double)total; - - vStr = (int)(vStr * scalar); - vDex = (int)(vDex * scalar); - vInt = (int)(vInt * scalar); - - FixStat( ref vStr, (vStr + vDex + vInt) - vMax, vMax ); - FixStat( ref vDex, (vStr + vDex + vInt) - vMax, vMax ); - FixStat( ref vInt, (vStr + vDex + vInt) - vMax, vMax ); - - str = vStr + 10; - dex = vDex + 10; - intel = vInt + 10; - } - - private static void FixStat( ref int stat, int diff, int max ) - { - stat += diff; - - if ( stat < 0 ) - stat = 0; - else if ( stat > max ) - stat = max; - } - - private static void SetStats( Mobile m, NetState state, int str, int dex, int intel ) - { - int max = state.NewCharacterCreation ? 90 : 80; - - FixStats( ref str, ref dex, ref intel, max ); - - if ( str < 10 || str > 60 || dex < 10 || dex > 60 || intel < 10 || intel > 60 || (str + dex + intel) != max ) - { - str = 10; - dex = 10; - intel = 10; - } - - m.InitStats( str, dex, intel ); - } - - private static void SetName( Mobile m, string name ) - { - name = name.Trim(); - - if ( !NameVerification.Validate( name, 2, 16, true, false, true, 1, NameVerification.SpaceDashPeriodQuote ) ) - name = "Generic Player"; - - m.Name = name; - } - - private static bool ValidSkills( SkillNameValue[] skills ) - { - int total = 0; - - for ( int i = 0; i < skills.Length; ++i ) - { - if ( skills[i].Value < 0 || skills[i].Value > 50 ) - return false; - - total += skills[i].Value; - - for ( int j = i + 1; j < skills.Length; ++j ) - { - if ( skills[j].Value > 0 && skills[j].Name == skills[i].Name ) - return false; - } - } - - return ( total == 100 || total == 120 ); - } - - private static Mobile m_Mobile; - - private static void SetSkills( Mobile m, SkillNameValue[] skills, int prof ) - { - switch ( prof ) - { - case 1: // Warrior - { - skills = new[] - { - new SkillNameValue( SkillName.Anatomy, 30 ), - new SkillNameValue( SkillName.Healing, 45 ), - new SkillNameValue( SkillName.Swords, 35 ), - new SkillNameValue( SkillName.Tactics, 50 ) - }; - - break; - } - case 2: // Magician - { - skills = new[] - { - new SkillNameValue( SkillName.EvalInt, 30 ), - new SkillNameValue( SkillName.Wrestling, 30 ), - new SkillNameValue( SkillName.Magery, 50 ), - new SkillNameValue( SkillName.Meditation, 50 ) - }; - - break; - } - case 3: // Blacksmith - { - skills = new[] - { - new SkillNameValue( SkillName.Mining, 30 ), - new SkillNameValue( SkillName.ArmsLore, 30 ), - new SkillNameValue( SkillName.Blacksmith, 50 ), - new SkillNameValue( SkillName.Tinkering, 50 ) - }; - - break; - } - case 4: // Necromancer - { - skills = new[] - { - new SkillNameValue( SkillName.Necromancy, 50 ), - new SkillNameValue( SkillName.Focus, 30 ), - new SkillNameValue( SkillName.SpiritSpeak, 30 ), - new SkillNameValue( SkillName.Swords, 30 ), - new SkillNameValue( SkillName.Tactics, 20 ) - }; - - break; - } - case 5: // Paladin - { - skills = new[] - { - new SkillNameValue( SkillName.Chivalry, 51 ), - new SkillNameValue( SkillName.Swords, 49 ), - new SkillNameValue( SkillName.Focus, 30 ), - new SkillNameValue( SkillName.Tactics, 30 ) - }; - - break; - } - case 6: //Samurai - { - skills = new[] - { - new SkillNameValue( SkillName.Bushido, 50 ), - new SkillNameValue( SkillName.Swords, 50 ), - new SkillNameValue( SkillName.Anatomy, 30 ), - new SkillNameValue( SkillName.Healing, 30 ) - }; - break; - } - case 7: //Ninja - { - skills = new[] - { - new SkillNameValue( SkillName.Ninjitsu, 50 ), - new SkillNameValue( SkillName.Hiding, 50 ), - new SkillNameValue( SkillName.Fencing, 30 ), - new SkillNameValue( SkillName.Stealth, 30 ) - }; - break; - } - default: - { - if ( !ValidSkills( skills ) ) - return; - - break; - } - } - - bool addSkillItems = true; - bool elf = (m.Race == Race.Elf); - - switch ( prof ) - { - case 1: // Warrior - { - if ( elf ) - EquipItem( new LeafChest() ); - else - EquipItem( new LeatherChest() ); - break; - } - case 4: // Necromancer - { - Container regs = new BagOfNecroReagents( 50 ); - - if ( !Core.AOS ) - { - foreach ( Item item in regs.Items ) - item.LootType = LootType.Newbied; - } - - PackItem( regs ); - - regs.LootType = LootType.Regular; - - EquipItem( new BoneHelm() ); - - if ( elf ) - { - EquipItem( new ElvenMachete() ); - EquipItem( NecroHue( new LeafChest() ) ); - EquipItem( NecroHue( new LeafArms() ) ); - EquipItem( NecroHue( new LeafGloves() ) ); - EquipItem( NecroHue( new LeafGorget() ) ); - EquipItem( NecroHue( new LeafGorget() ) ); - EquipItem( NecroHue( new ElvenPants() ) ); //TODO: Verify the pants - EquipItem( new ElvenBoots() ); - } - else - { - EquipItem( new BoneHarvester() ); - EquipItem( NecroHue( new LeatherChest() ) ); - EquipItem( NecroHue( new LeatherArms() ) ); - EquipItem( NecroHue( new LeatherGloves() ) ); - EquipItem( NecroHue( new LeatherGorget() ) ); - EquipItem( NecroHue( new LeatherLegs() ) ); - EquipItem( NecroHue( new Skirt() ) ); - EquipItem( new Sandals( 0x8FD ) ); - } - - Spellbook book = new NecromancerSpellbook( (ulong)0x8981 ); // animate dead, evil omen, pain spike, summon familiar, wraith form - - PackItem( book ); - - book.LootType = LootType.Blessed; - - addSkillItems = false; - - break; - } - case 5: // Paladin - { - if ( elf ) - { - EquipItem( new ElvenMachete() ); - EquipItem( new WingedHelm() ); - EquipItem( new LeafGorget() ); - EquipItem( new LeafArms() ); - EquipItem( new LeafChest() ); - EquipItem( new LeafLegs() ); - EquipItem( new ElvenBoots() ); //Verify hue - } - else - { - EquipItem( new Broadsword() ); - EquipItem( new Helmet() ); - EquipItem( new PlateGorget() ); - EquipItem( new RingmailArms() ); - EquipItem( new RingmailChest() ); - EquipItem( new RingmailLegs() ); - EquipItem( new ThighBoots( 0x748 ) ); - EquipItem( new Cloak( 0xCF ) ); - EquipItem( new BodySash( 0xCF ) ); - } - - Spellbook book = new BookOfChivalry( (ulong)0x3FF ); - - PackItem( book ); - - book.LootType = LootType.Blessed; - - addSkillItems = false; - - break; - } - - case 6: // Samurai - { - addSkillItems = false; - EquipItem( new HakamaShita( 0x2C3 ) ); - EquipItem( new Hakama( 0x2C3 ) ); - EquipItem( new SamuraiTabi( 0x2C3 ) ); - EquipItem( new TattsukeHakama( 0x22D ) ); - EquipItem( new Bokuto() ); - - if ( elf ) - EquipItem( new RavenHelm() ); - else - EquipItem( new LeatherJingasa() ); - - PackItem( new Scissors() ); - PackItem( new Bandage( 50 ) ); - - Spellbook book = new BookOfBushido(); - PackItem( book ); - - break; - } - case 7: // Ninja - { - addSkillItems = false; - EquipItem( new Kasa() ); - - int[] hues = { 0x1A8, 0xEC, 0x99, 0x90, 0xB5, 0x336, 0x89 }; - //TODO: Verify that's ALL the hues for that above. - - EquipItem( new TattsukeHakama( hues[Utility.Random(hues.Length)] ) ); - - EquipItem( new HakamaShita( 0x2C3 ) ); - EquipItem( new NinjaTabi( 0x2C3 ) ); - - if ( elf ) - EquipItem( new AssassinSpike() ); - else - EquipItem( new Tekagi() ); - - PackItem( new SmokeBomb() ); - - Spellbook book = new BookOfNinjitsu(); - PackItem( book ); - - break; - } - } - - for ( int i = 0; i < skills.Length; ++i ) - { - SkillNameValue snv = skills[i]; - - if ( snv.Value > 0 && ( snv.Name != SkillName.Stealth || prof == 7 ) && snv.Name != SkillName.RemoveTrap && snv.Name != SkillName.Spellweaving ) - { - Skill skill = m.Skills[snv.Name]; - - if ( skill != null ) - { - skill.BaseFixedPoint = snv.Value * 10; - - if ( addSkillItems ) - AddSkillItems( snv.Name, m ); - } - } - } - } - - private static void EquipItem( Item item, bool mustEquip = false) - { - if ( !Core.AOS ) - item.LootType = LootType.Newbied; - - if ( m_Mobile != null && m_Mobile.EquipItem( item ) ) - return; - - Container pack = m_Mobile.Backpack; - - if ( !mustEquip && pack != null ) - pack.DropItem( item ); - else - item.Delete(); - } - - private static void PackItem( Item item ) - { - if ( !Core.AOS ) - item.LootType = LootType.Newbied; - - Container pack = m_Mobile.Backpack; - - if ( pack != null ) - pack.DropItem( item ); - else - item.Delete(); - } - - private static void PackInstrument() - { - switch ( Utility.Random( 6 ) ) - { - case 0: PackItem( new Drums() ); break; - case 1: PackItem( new Harp() ); break; - case 2: PackItem( new LapHarp() ); break; - case 3: PackItem( new Lute() ); break; - case 4: PackItem( new Tambourine() ); break; - case 5: PackItem( new TambourineTassel() ); break; - } - } - - private static void PackScroll( int circle ) - { - switch ( Utility.Random( 8 ) * ( circle + 1 ) ) - { - case 0: PackItem( new ClumsyScroll() ); break; - case 1: PackItem( new CreateFoodScroll() ); break; - case 2: PackItem( new FeeblemindScroll() ); break; - case 3: PackItem( new HealScroll() ); break; - case 4: PackItem( new MagicArrowScroll() ); break; - case 5: PackItem( new NightSightScroll() ); break; - case 6: PackItem( new ReactiveArmorScroll() ); break; - case 7: PackItem( new WeakenScroll() ); break; - case 8: PackItem( new AgilityScroll() ); break; - case 9: PackItem( new CunningScroll() ); break; - case 10: PackItem( new CureScroll() ); break; - case 11: PackItem( new HarmScroll() ); break; - case 12: PackItem( new MagicTrapScroll() ); break; - case 13: PackItem( new MagicUnTrapScroll() ); break; - case 14: PackItem( new ProtectionScroll() ); break; - case 15: PackItem( new StrengthScroll() ); break; - case 16: PackItem( new BlessScroll() ); break; - case 17: PackItem( new FireballScroll() ); break; - case 18: PackItem( new MagicLockScroll() ); break; - case 19: PackItem( new PoisonScroll() ); break; - case 20: PackItem( new TelekinisisScroll() ); break; - case 21: PackItem( new TeleportScroll() ); break; - case 22: PackItem( new UnlockScroll() ); break; - case 23: PackItem( new WallOfStoneScroll() ); break; - } - } - - private static Item NecroHue( Item item ) - { - item.Hue = 0x2C3; - - return item; - } - - private static void AddSkillItems( SkillName skill, Mobile m ) - { - bool elf = (m.Race == Race.Elf); - - switch ( skill ) - { - case SkillName.Alchemy: - { - PackItem( new Bottle( 4 ) ); - PackItem( new MortarPestle() ); - - int hue = Utility.RandomPinkHue(); - - if ( elf ) - { - if ( m.Female ) - EquipItem( new FemaleElvenRobe( hue ) ); - else - EquipItem( new MaleElvenRobe( hue ) ); - } - else - { - EquipItem( new Robe( Utility.RandomPinkHue() ) ); - } - break; - } - case SkillName.Anatomy: - { - PackItem( new Bandage( 3 ) ); - - int hue = Utility.RandomYellowHue(); - - if ( elf ) - { - if ( m.Female ) - EquipItem( new FemaleElvenRobe( hue ) ); - else - EquipItem( new MaleElvenRobe( hue ) ); - } - else - { - EquipItem( new Robe( hue ) ); - } - break; - } - case SkillName.AnimalLore: - { - int hue = Utility.RandomBlueHue(); - - if ( elf ) - { - EquipItem( new WildStaff() ); - - if ( m.Female ) - EquipItem( new FemaleElvenRobe( hue ) ); - else - EquipItem( new MaleElvenRobe( hue ) ); - } - else - { - EquipItem( new ShepherdsCrook() ); - EquipItem( new Robe( hue ) ); - } - break; - } - case SkillName.Archery: - { - PackItem( new Arrow( 25 ) ); - - if ( elf ) - EquipItem( new ElvenCompositeLongbow() ); - else - EquipItem( new Bow() ); - - break; - } - case SkillName.ArmsLore: - { - if ( elf ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: EquipItem( new Leafblade() ); break; - case 1: EquipItem( new RuneBlade() ); break; - case 2: EquipItem( new DiamondMace() ); break; - } - } - else - { - switch ( Utility.Random( 3 ) ) - { - case 0: EquipItem( new Kryss() ); break; - case 1: EquipItem( new Katana() ); break; - case 2: EquipItem( new Club() ); break; - } - } - - break; - } - case SkillName.Begging: - { - if ( elf ) - EquipItem( new WildStaff() ); - else - EquipItem( new GnarledStaff() ); - break; - } - case SkillName.Blacksmith: - { - PackItem( new Tongs() ); - PackItem( new Pickaxe() ); - PackItem( new Pickaxe() ); - PackItem( new IronIngot( 50 ) ); - EquipItem( new HalfApron( Utility.RandomYellowHue() ) ); - break; - } - case SkillName.Bushido: - { - EquipItem( new Hakama() ); - EquipItem( new Kasa() ); - EquipItem( new BookOfBushido() ); - break; - } - case SkillName.Fletching: - { - PackItem( new Board( 14 ) ); - PackItem( new Feather( 5 ) ); - PackItem( new Shaft( 5 ) ); - break; - } - case SkillName.Camping: - { - PackItem( new Bedroll() ); - PackItem( new Kindling( 5 ) ); - break; - } - case SkillName.Carpentry: - { - PackItem( new Board( 10 ) ); - PackItem( new Saw() ); - EquipItem( new HalfApron( Utility.RandomYellowHue() ) ); - break; - } - case SkillName.Cartography: - { - PackItem( new BlankMap() ); - PackItem( new BlankMap() ); - PackItem( new BlankMap() ); - PackItem( new BlankMap() ); - PackItem( new Sextant() ); - break; - } - case SkillName.Cooking: - { - PackItem( new Kindling( 2 ) ); - PackItem( new RawLambLeg() ); - PackItem( new RawChickenLeg() ); - PackItem( new RawFishSteak() ); - PackItem( new SackFlour() ); - PackItem( new Pitcher( BeverageType.Water ) ); - break; - } - case SkillName.Chivalry: - { - if ( Core.ML ) - PackItem( new BookOfChivalry( (ulong)0x3FF ) ); - - break; - } - case SkillName.DetectHidden: - { - EquipItem( new Cloak( 0x455 ) ); - break; - } - case SkillName.Discordance: - { - PackInstrument(); - break; - } - case SkillName.Fencing: - { - if ( elf ) - EquipItem( new Leafblade() ); - else - EquipItem( new Kryss() ); - - break; - } - case SkillName.Fishing: - { - EquipItem( new FishingPole() ); - - int hue = Utility.RandomYellowHue(); - - if ( elf ) - { - Item i = new Circlet(); - i.Hue = hue; - EquipItem( i ); - } - else - { - EquipItem( new FloppyHat( hue ) ); - } - - break; - } - case SkillName.Healing: - { - PackItem( new Bandage( 50 ) ); - PackItem( new Scissors() ); - break; - } - case SkillName.Herding: - { - if ( elf ) - EquipItem( new WildStaff() ); - else - EquipItem( new ShepherdsCrook() ); - - break; - } - case SkillName.Hiding: - { - EquipItem( new Cloak( 0x455 ) ); - break; - } - case SkillName.Inscribe: - { - PackItem( new BlankScroll( 2 ) ); - PackItem( new BlueBook() ); - break; - } - case SkillName.ItemID: - { - if ( elf ) - EquipItem( new WildStaff() ); - else - EquipItem( new GnarledStaff() ); - break; - } - case SkillName.Lockpicking: - { - PackItem( new Lockpick( 20 ) ); - break; - } - case SkillName.Lumberjacking: - { - EquipItem( new Hatchet() ); - break; - } - case SkillName.Macing: - { - if ( elf ) - EquipItem( new DiamondMace() ); - else - EquipItem( new Club() ); - - break; - } - case SkillName.Magery: - { - BagOfReagents regs = new BagOfReagents( 30 ); - - if ( !Core.AOS ) - { - foreach ( Item item in regs.Items ) - item.LootType = LootType.Newbied; - } - - PackItem( regs ); - - regs.LootType = LootType.Regular; - - PackScroll( 0 ); - PackScroll( 1 ); - PackScroll( 2 ); - - Spellbook book = new Spellbook( (ulong)0x382A8C38 ); - - EquipItem( book ); - - book.LootType = LootType.Blessed; - - if ( elf ) - { - EquipItem( new Circlet() ); - - if ( m.Female ) - EquipItem( new FemaleElvenRobe( Utility.RandomBlueHue() ) ); - else - EquipItem( new MaleElvenRobe( Utility.RandomBlueHue() ) ); - } - else - { - EquipItem( new WizardsHat() ); - EquipItem( new Robe( Utility.RandomBlueHue() ) ); - } - - break; - } - case SkillName.Mining: - { - PackItem( new Pickaxe() ); - break; - } - case SkillName.Musicianship: - { - PackInstrument(); - break; - } - case SkillName.Necromancy: - { - if ( Core.ML ) - { - Container regs = new BagOfNecroReagents( 50 ); - - PackItem( regs ); - - regs.LootType = LootType.Regular; - } - - break; - } - case SkillName.Ninjitsu: - { - EquipItem( new Hakama( 0x2C3 ) ); //Only ninjas get the hued one. - EquipItem( new Kasa() ); - EquipItem( new BookOfNinjitsu() ); - break; - } - case SkillName.Parry: - { - EquipItem( new WoodenShield() ); - break; - } - case SkillName.Peacemaking: - { - PackInstrument(); - break; - } - case SkillName.Poisoning: - { - PackItem( new LesserPoisonPotion() ); - PackItem( new LesserPoisonPotion() ); - break; - } - case SkillName.Provocation: - { - PackInstrument(); - break; - } - case SkillName.Snooping: - { - PackItem( new Lockpick( 20 ) ); - break; - } - case SkillName.SpiritSpeak: - { - EquipItem( new Cloak( 0x455 ) ); - break; - } - case SkillName.Stealing: - { - PackItem( new Lockpick( 20 ) ); - break; - } - case SkillName.Swords: - { - if ( elf ) - EquipItem( new RuneBlade() ); - else - EquipItem( new Katana() ); - - break; - } - case SkillName.Tactics: - { - if ( elf ) - EquipItem( new RuneBlade() ); - else - EquipItem( new Katana() ); - - break; - } - case SkillName.Tailoring: - { - PackItem( new BoltOfCloth() ); - PackItem( new SewingKit() ); - break; - } - case SkillName.Tracking: - { - Item shoes = m_Mobile?.FindItemOnLayer( Layer.Shoes ); - - shoes?.Delete(); - - int hue = Utility.RandomYellowHue(); - - if ( elf ) - EquipItem( new ElvenBoots( hue ) ); - else - EquipItem( new Boots( hue ) ); - - EquipItem( new SkinningKnife() ); - break; - } - case SkillName.Veterinary: - { - PackItem( new Bandage( 5 ) ); - PackItem( new Scissors() ); - break; - } - case SkillName.Wrestling: - { - if ( elf ) - EquipItem( new LeafGloves() ); - else - EquipItem( new LeatherGloves() ); - - break; - } - } - } - } -} + PlaceItemIn(cont, 55, 100, new Lockpick(30)); + PlaceItemIn(cont, 60, 100, new Pickaxe()); + + PlaceItemIn(bank, 98, 124, cont); + // End bag of treasure maps + + + // Begin bag of raw materials + cont = new Bag(); + cont.Hue = 0x835; + cont.Name = "Raw Materials Bag"; + + PlaceItemIn(cont, 92, 60, new BarbedLeather(5000)); + PlaceItemIn(cont, 92, 68, new HornedLeather(5000)); + PlaceItemIn(cont, 92, 76, new SpinedLeather(5000)); + PlaceItemIn(cont, 92, 84, new Leather(5000)); + + PlaceItemIn(cont, 30, 118, new Cloth(5000)); + PlaceItemIn(cont, 30, 84, new Board(5000)); + PlaceItemIn(cont, 57, 80, new BlankScroll(500)); + + PlaceItemIn(cont, 30, 35, new DullCopperIngot(5000)); + PlaceItemIn(cont, 37, 35, new ShadowIronIngot(5000)); + PlaceItemIn(cont, 44, 35, new CopperIngot(5000)); + PlaceItemIn(cont, 51, 35, new BronzeIngot(5000)); + PlaceItemIn(cont, 58, 35, new GoldIngot(5000)); + PlaceItemIn(cont, 65, 35, new AgapiteIngot(5000)); + PlaceItemIn(cont, 72, 35, new VeriteIngot(5000)); + PlaceItemIn(cont, 79, 35, new ValoriteIngot(5000)); + PlaceItemIn(cont, 86, 35, new IronIngot(5000)); + + PlaceItemIn(cont, 30, 59, new RedScales(5000)); + PlaceItemIn(cont, 36, 59, new YellowScales(5000)); + PlaceItemIn(cont, 42, 59, new BlackScales(5000)); + PlaceItemIn(cont, 48, 59, new GreenScales(5000)); + PlaceItemIn(cont, 54, 59, new WhiteScales(5000)); + PlaceItemIn(cont, 60, 59, new BlueScales(5000)); + + PlaceItemIn(bank, 98, 169, cont); + // End bag of raw materials + + + // Begin bag of spell casting stuff + cont = new Backpack(); + cont.Hue = 0x480; + cont.Name = "Spell Casting Stuff"; + + PlaceItemIn(cont, 45, 105, new Spellbook(ulong.MaxValue)); + PlaceItemIn(cont, 65, 105, new NecromancerSpellbook((ulong)0xFFFF)); + PlaceItemIn(cont, 85, 105, new BookOfChivalry((ulong)0x3FF)); + PlaceItemIn(cont, 105, 105, new BookOfBushido()); //Default ctor = full + PlaceItemIn(cont, 125, 105, new BookOfNinjitsu()); //Default ctor = full + + Runebook runebook = new Runebook(10); + runebook.CurCharges = runebook.MaxCharges; + PlaceItemIn(cont, 145, 105, runebook); + + Item toHue = new BagOfReagents(150); + toHue.Hue = 0x2D; + PlaceItemIn(cont, 45, 150, toHue); + + toHue = new BagOfNecroReagents(150); + toHue.Hue = 0x488; + PlaceItemIn(cont, 65, 150, toHue); + + PlaceItemIn(cont, 140, 150, new BagOfAllReagents(500)); + + for (int i = 0; i < 9; ++i) + PlaceItemIn(cont, 45 + i * 10, 75, new RecallRune()); + + PlaceItemIn(cont, 141, 74, new FireHorn()); + + PlaceItemIn(bank, 78, 169, cont); + // End bag of spell casting stuff + + + // Begin bag of ethereals + cont = new Backpack(); + cont.Hue = 0x490; + cont.Name = "Bag Of Ethy's!"; + + PlaceItemIn(cont, 45, 66, new EtherealHorse()); + PlaceItemIn(cont, 69, 82, new EtherealOstard()); + PlaceItemIn(cont, 93, 99, new EtherealLlama()); + PlaceItemIn(cont, 117, 115, new EtherealKirin()); + PlaceItemIn(cont, 45, 132, new EtherealUnicorn()); + PlaceItemIn(cont, 69, 66, new EtherealRidgeback()); + PlaceItemIn(cont, 93, 82, new EtherealSwampDragon()); + PlaceItemIn(cont, 117, 99, new EtherealBeetle()); + + PlaceItemIn(bank, 38, 124, cont); + // End bag of ethereals + + + // Begin first bag of artifacts + cont = new Backpack(); + cont.Hue = 0x48F; + cont.Name = "Bag of Artifacts"; + + PlaceItemIn(cont, 45, 66, new TitansHammer()); + PlaceItemIn(cont, 69, 82, new InquisitorsResolution()); + PlaceItemIn(cont, 93, 99, new BladeOfTheRighteous()); + PlaceItemIn(cont, 117, 115, new ZyronicClaw()); + + PlaceItemIn(bank, 58, 124, cont); + // End first bag of artifacts + + + // Begin second bag of artifacts + cont = new Backpack(); + cont.Hue = 0x48F; + cont.Name = "Bag of Artifacts"; + + PlaceItemIn(cont, 45, 66, new GauntletsOfNobility()); + PlaceItemIn(cont, 69, 82, new MidnightBracers()); + PlaceItemIn(cont, 93, 99, new VoiceOfTheFallenKing()); + PlaceItemIn(cont, 117, 115, new OrnateCrownOfTheHarrower()); + PlaceItemIn(cont, 45, 132, new HelmOfInsight()); + PlaceItemIn(cont, 69, 66, new HolyKnightsBreastplate()); + PlaceItemIn(cont, 93, 82, new ArmorOfFortune()); + PlaceItemIn(cont, 117, 99, new TunicOfFire()); + PlaceItemIn(cont, 45, 115, new LeggingsOfBane()); + PlaceItemIn(cont, 69, 132, new ArcaneShield()); + PlaceItemIn(cont, 93, 66, new Aegis()); + PlaceItemIn(cont, 117, 82, new RingOfTheVile()); + PlaceItemIn(cont, 45, 99, new BraceletOfHealth()); + PlaceItemIn(cont, 69, 115, new RingOfTheElements()); + PlaceItemIn(cont, 93, 132, new OrnamentOfTheMagician()); + PlaceItemIn(cont, 117, 66, new DivineCountenance()); + PlaceItemIn(cont, 45, 82, new JackalsCollar()); + PlaceItemIn(cont, 69, 99, new HuntersHeaddress()); + PlaceItemIn(cont, 93, 115, new HatOfTheMagi()); + PlaceItemIn(cont, 117, 132, new ShadowDancerLeggings()); + PlaceItemIn(cont, 45, 66, new SpiritOfTheTotem()); + PlaceItemIn(cont, 69, 82, new BladeOfInsanity()); + PlaceItemIn(cont, 93, 99, new AxeOfTheHeavens()); + PlaceItemIn(cont, 117, 115, new TheBeserkersMaul()); + PlaceItemIn(cont, 45, 132, new Frostbringer()); + PlaceItemIn(cont, 69, 66, new BreathOfTheDead()); + PlaceItemIn(cont, 93, 82, new TheDragonSlayer()); + PlaceItemIn(cont, 117, 99, new BoneCrusher()); + PlaceItemIn(cont, 45, 115, new StaffOfTheMagi()); + PlaceItemIn(cont, 69, 132, new SerpentsFang()); + PlaceItemIn(cont, 93, 66, new LegacyOfTheDreadLord()); + PlaceItemIn(cont, 117, 82, new TheTaskmaster()); + PlaceItemIn(cont, 45, 99, new TheDryadBow()); + + PlaceItemIn(bank, 78, 124, cont); + // End second bag of artifacts + + // Begin bag of minor artifacts + cont = new Backpack(); + cont.Hue = 0x48F; + cont.Name = "Bag of Minor Artifacts"; + + + PlaceItemIn(cont, 45, 66, new LunaLance()); + PlaceItemIn(cont, 69, 82, new VioletCourage()); + PlaceItemIn(cont, 93, 99, new CavortingClub()); + PlaceItemIn(cont, 117, 115, new CaptainQuacklebushsCutlass()); + PlaceItemIn(cont, 45, 132, new NightsKiss()); + PlaceItemIn(cont, 69, 66, new ShipModelOfTheHMSCape()); + PlaceItemIn(cont, 93, 82, new AdmiralsHeartyRum()); + PlaceItemIn(cont, 117, 99, new CandelabraOfSouls()); + PlaceItemIn(cont, 45, 115, new IolosLute()); + PlaceItemIn(cont, 69, 132, new GwennosHarp()); + PlaceItemIn(cont, 93, 66, new ArcticDeathDealer()); + PlaceItemIn(cont, 117, 82, new EnchantedTitanLegBone()); + PlaceItemIn(cont, 45, 99, new NoxRangersHeavyCrossbow()); + PlaceItemIn(cont, 69, 115, new BlazeOfDeath()); + PlaceItemIn(cont, 93, 132, new DreadPirateHat()); + PlaceItemIn(cont, 117, 66, new BurglarsBandana()); + PlaceItemIn(cont, 45, 82, new GoldBricks()); + PlaceItemIn(cont, 69, 99, new AlchemistsBauble()); + PlaceItemIn(cont, 93, 115, new PhillipsWoodenSteed()); + PlaceItemIn(cont, 117, 132, new PolarBearMask()); + PlaceItemIn(cont, 45, 66, new BowOfTheJukaKing()); + PlaceItemIn(cont, 69, 82, new GlovesOfThePugilist()); + PlaceItemIn(cont, 93, 99, new OrcishVisage()); + PlaceItemIn(cont, 117, 115, new StaffOfPower()); + PlaceItemIn(cont, 45, 132, new ShieldOfInvulnerability()); + PlaceItemIn(cont, 69, 66, new HeartOfTheLion()); + PlaceItemIn(cont, 93, 82, new ColdBlood()); + PlaceItemIn(cont, 117, 99, new GhostShipAnchor()); + PlaceItemIn(cont, 45, 115, new SeahorseStatuette()); + PlaceItemIn(cont, 69, 132, new WrathOfTheDryad()); + PlaceItemIn(cont, 93, 66, new PixieSwatter()); + + for (int i = 0; i < 10; i++) + PlaceItemIn(cont, 117, 128, new MessageInABottle(Utility.RandomBool() ? Map.Trammel : Map.Felucca, 4)); + + PlaceItemIn(bank, 18, 124, cont); + + if (Core.SE) + { + cont = new Bag(); + cont.Hue = 0x501; + cont.Name = "Tokuno Minor Artifacts"; + + PlaceItemIn(cont, 42, 70, new Exiler()); + PlaceItemIn(cont, 38, 53, new HanzosBow()); + PlaceItemIn(cont, 45, 40, new TheDestroyer()); + PlaceItemIn(cont, 92, 80, new DragonNunchaku()); + PlaceItemIn(cont, 42, 56, new PeasantsBokuto()); + PlaceItemIn(cont, 44, 71, new TomeOfEnlightenment()); + PlaceItemIn(cont, 35, 35, new ChestOfHeirlooms()); + PlaceItemIn(cont, 29, 0, new HonorableSwords()); + PlaceItemIn(cont, 49, 85, new AncientUrn()); + PlaceItemIn(cont, 51, 58, new FluteOfRenewal()); + PlaceItemIn(cont, 70, 51, new PigmentsOfTokuno()); + PlaceItemIn(cont, 40, 79, new AncientSamuraiDo()); + PlaceItemIn(cont, 51, 61, new LegsOfStability()); + PlaceItemIn(cont, 88, 78, new GlovesOfTheSun()); + PlaceItemIn(cont, 55, 62, new AncientFarmersKasa()); + PlaceItemIn(cont, 55, 83, new ArmsOfTacticalExcellence()); + PlaceItemIn(cont, 50, 85, new DaimyosHelm()); + PlaceItemIn(cont, 52, 78, new BlackLotusHood()); + PlaceItemIn(cont, 52, 79, new DemonForks()); + PlaceItemIn(cont, 33, 49, new PilferedDancerFans()); + + PlaceItemIn(bank, 58, 124, cont); + } + + if (Core.SE) //This bag came only after SE. + { + cont = new Bag(); + cont.Name = "Bag of Bows"; + + PlaceItemIn(cont, 31, 84, new Bow()); + PlaceItemIn(cont, 78, 74, new CompositeBow()); + PlaceItemIn(cont, 53, 71, new Crossbow()); + PlaceItemIn(cont, 56, 39, new HeavyCrossbow()); + PlaceItemIn(cont, 82, 72, new RepeatingCrossbow()); + PlaceItemIn(cont, 49, 45, new Yumi()); + + for (int i = 0; i < cont.Items.Count; i++) + if (cont.Items[i] is BaseRanged bow) + { + bow.Attributes.WeaponSpeed = 35; + bow.Attributes.WeaponDamage = 35; + } + + PlaceItemIn(bank, 108, 135, cont); + } + } + + private static void FillBankbox(Mobile m) + { + if (Core.AOS) + { + FillBankAOS(m); + return; + } + + BankBox bank = m.BankBox; + + bank.DropItem(new BankCheck(1000000)); + + // Full spellbook + Spellbook book = new Spellbook(); + + book.Content = ulong.MaxValue; + + bank.DropItem(book); + + Bag bag = new Bag(); + + for (int i = 0; i < 5; ++i) + bag.DropItem(new Moonstone(MoonstoneType.Felucca)); + + // Felucca moonstones + bank.DropItem(bag); + + bag = new Bag(); + + for (int i = 0; i < 5; ++i) + bag.DropItem(new Moonstone(MoonstoneType.Trammel)); + + // Trammel moonstones + bank.DropItem(bag); + + // Treasure maps + bank.DropItem(new TreasureMap(1, Map.Trammel)); + bank.DropItem(new TreasureMap(2, Map.Trammel)); + bank.DropItem(new TreasureMap(3, Map.Trammel)); + bank.DropItem(new TreasureMap(4, Map.Trammel)); + bank.DropItem(new TreasureMap(5, Map.Trammel)); + + // Bag containing 50 of each reagent + bank.DropItem(new BagOfReagents(50)); + + // Craft tools + bank.DropItem(MakeNewbie(new Scissors())); + bank.DropItem(MakeNewbie(new SewingKit(1000))); + bank.DropItem(MakeNewbie(new SmithHammer(1000))); + bank.DropItem(MakeNewbie(new FletcherTools(1000))); + bank.DropItem(MakeNewbie(new DovetailSaw(1000))); + bank.DropItem(MakeNewbie(new MortarPestle(1000))); + bank.DropItem(MakeNewbie(new ScribesPen(1000))); + bank.DropItem(MakeNewbie(new TinkerTools(1000))); + + // A few dye tubs + bank.DropItem(new Dyes()); + bank.DropItem(new DyeTub()); + bank.DropItem(new DyeTub()); + bank.DropItem(new BlackDyeTub()); + + DyeTub darkRedTub = new DyeTub(); + + darkRedTub.DyedHue = 0x485; + darkRedTub.Redyable = false; + + bank.DropItem(darkRedTub); + + // Some food + bank.DropItem(MakeNewbie(new Apple(1000))); + + // Resources + bank.DropItem(MakeNewbie(new Feather(1000))); + bank.DropItem(MakeNewbie(new BoltOfCloth(1000))); + bank.DropItem(MakeNewbie(new BlankScroll(1000))); + bank.DropItem(MakeNewbie(new Hides(1000))); + bank.DropItem(MakeNewbie(new Bandage(1000))); + bank.DropItem(MakeNewbie(new Bottle(1000))); + bank.DropItem(MakeNewbie(new Log(1000))); + + bank.DropItem(MakeNewbie(new IronIngot(5000))); + bank.DropItem(MakeNewbie(new DullCopperIngot(5000))); + bank.DropItem(MakeNewbie(new ShadowIronIngot(5000))); + bank.DropItem(MakeNewbie(new CopperIngot(5000))); + bank.DropItem(MakeNewbie(new BronzeIngot(5000))); + bank.DropItem(MakeNewbie(new GoldIngot(5000))); + bank.DropItem(MakeNewbie(new AgapiteIngot(5000))); + bank.DropItem(MakeNewbie(new VeriteIngot(5000))); + bank.DropItem(MakeNewbie(new ValoriteIngot(5000))); + + // Reagents + bank.DropItem(MakeNewbie(new BlackPearl(1000))); + bank.DropItem(MakeNewbie(new Bloodmoss(1000))); + bank.DropItem(MakeNewbie(new Garlic(1000))); + bank.DropItem(MakeNewbie(new Ginseng(1000))); + bank.DropItem(MakeNewbie(new MandrakeRoot(1000))); + bank.DropItem(MakeNewbie(new Nightshade(1000))); + bank.DropItem(MakeNewbie(new SulfurousAsh(1000))); + bank.DropItem(MakeNewbie(new SpidersSilk(1000))); + + // Some extra starting gold + bank.DropItem(MakeNewbie(new Gold(9000))); + + // 5 blank recall runes + for (int i = 0; i < 5; ++i) + bank.DropItem(MakeNewbie(new RecallRune())); + + AddPowerScrolls(bank); + } + + private static void AddPowerScrolls(BankBox bank) + { + Bag bag = new Bag(); + + for (int i = 0; i < PowerScroll.Skills.Count; ++i) + bag.DropItem(new PowerScroll(PowerScroll.Skills[i], 120.0)); + + bag.DropItem(new StatCapScroll(250)); + + bank.DropItem(bag); + } + + private static void AddShirt(Mobile m, int shirtHue) + { + int hue = Utility.ClipDyedHue(shirtHue & 0x3FFF); + + if (m.Race == Race.Elf) + EquipItem(new ElvenShirt(hue), true); + else + switch (Utility.Random(3)) + { + case 0: + EquipItem(new Shirt(hue), true); + break; + case 1: + EquipItem(new FancyShirt(hue), true); + break; + case 2: + EquipItem(new Doublet(hue), true); + break; + } + } + + private static void AddPants(Mobile m, int pantsHue) + { + int hue = Utility.ClipDyedHue(pantsHue & 0x3FFF); + + if (m.Race == Race.Elf) + { + EquipItem(new ElvenPants(hue), true); + } + else + { + if (m.Female) + switch (Utility.Random(2)) + { + case 0: + EquipItem(new Skirt(hue), true); + break; + case 1: + EquipItem(new Kilt(hue), true); + break; + } + else + switch (Utility.Random(2)) + { + case 0: + EquipItem(new LongPants(hue), true); + break; + case 1: + EquipItem(new ShortPants(hue), true); + break; + } + } + } + + private static void AddShoes(Mobile m) + { + if (m.Race == Race.Elf) + EquipItem(new ElvenBoots(), true); + else + EquipItem(new Shoes(Utility.RandomYellowHue()), true); + } + + private static Mobile CreateMobile(Account a) + { + if (a.Count >= a.Limit) + return null; + + for (int i = 0; i < a.Length; ++i) + if (a[i] == null) + return a[i] = new PlayerMobile(); + + return null; + } + + private static void EventSink_CharacterCreated(CharacterCreatedEventArgs args) + { + if (!VerifyProfession(args.Profession)) + args.Profession = 0; + + NetState state = args.State; + + if (state == null) + return; + + Mobile newChar = CreateMobile(args.Account as Account); + + if (newChar == null) + { + Console.WriteLine("Login: {0}: Character creation failed, account full", state); + return; + } + + args.Mobile = newChar; + m_Mobile = newChar; + + newChar.Player = true; + newChar.AccessLevel = args.Account.AccessLevel; + newChar.Female = args.Female; + //newChar.Body = newChar.Female ? 0x191 : 0x190; + + if (Core.Expansion >= args.Race.RequiredExpansion) + newChar.Race = args.Race; //Sets body + else + newChar.Race = Race.DefaultRace; + + //newChar.Hue = Utility.ClipSkinHue( args.Hue & 0x3FFF ) | 0x8000; + newChar.Hue = newChar.Race.ClipSkinHue(args.Hue & 0x3FFF) | 0x8000; + + newChar.Hunger = 20; + + bool young = false; + + if (newChar is PlayerMobile pm) + { + pm.Profession = args.Profession; + + if (pm.AccessLevel == AccessLevel.Player && ((Account)pm.Account).Young) + young = pm.Young = true; + } + + SetName(newChar, args.Name); + + AddBackpack(newChar); + + SetStats(newChar, state, args.Str, args.Dex, args.Int); + SetSkills(newChar, args.Skills, args.Profession); + + Race race = newChar.Race; + + if (race.ValidateHair(newChar, args.HairID)) + { + newChar.HairItemID = args.HairID; + newChar.HairHue = race.ClipHairHue(args.HairHue & 0x3FFF); + } + + if (race.ValidateFacialHair(newChar, args.BeardID)) + { + newChar.FacialHairItemID = args.BeardID; + newChar.FacialHairHue = race.ClipHairHue(args.BeardHue & 0x3FFF); + } + + if (args.Profession <= 3) + { + AddShirt(newChar, args.ShirtHue); + AddPants(newChar, args.PantsHue); + AddShoes(newChar); + } + + if (TestCenter.Enabled) + FillBankbox(newChar); + + if (young) + { + NewPlayerTicket ticket = new NewPlayerTicket(); + ticket.Owner = newChar; + newChar.BankBox.DropItem(ticket); + } + + CityInfo city = GetStartLocation(args, young); + + newChar.MoveToWorld(city.Location, city.Map); + + Console.WriteLine("Login: {0}: New character being created (account={1})", state, args.Account.Username); + Console.WriteLine(" - Character: {0} (serial={1})", newChar.Name, newChar.Serial); + Console.WriteLine(" - Started: {0} {1} in {2}", city.City, city.Location, city.Map); + + new WelcomeTimer(newChar).Start(); + } + + public static bool VerifyProfession(int profession) + { + if (profession < 0) + return false; + if (profession < 4) + return true; + if (Core.AOS && profession < 6) + return true; + if (Core.SE && profession < 8) + return true; + + return false; + } + + private static CityInfo GetStartLocation(CharacterCreatedEventArgs args, bool isYoung) + { + if (Core.ML) return m_NewHavenInfo; //We don't get the client Version until AFTER Character creation + + bool useHaven = isYoung; + + ClientFlags flags = args.State?.Flags ?? ClientFlags.None; + Mobile m = args.Mobile; + + switch (args.Profession) + { + case 4: //Necro + { + if ((flags & ClientFlags.Malas) != 0) + return new CityInfo("Umbra", "Mardoth's Tower", 2114, 1301, -50, Map.Malas); + + useHaven = true; + + new BadStartMessage(m, 1062205); + /* + * Unfortunately you are playing on a *NON-Age-Of-Shadows* game + * installation and cannot be transported to Malas. + * You will not be able to take your new player quest in Malas + * without an AOS client. You are now being taken to the city of + * Haven on the Trammel facet. + * */ + + break; + } + case 5: //Paladin + { + return m_NewHavenInfo; + } + case 6: //Samurai + { + if ((flags & ClientFlags.Tokuno) != 0) + return new CityInfo("Samurai DE", "Haoti's Grounds", 368, 780, -1, Map.Malas); + + useHaven = true; + + new BadStartMessage(m, 1063487); + /* + * Unfortunately you are playing on a *NON-Samurai-Empire* game + * installation and cannot be transported to Tokuno. + * You will not be able to take your new player quest in Tokuno + * without an SE client. You are now being taken to the city of + * Haven on the Trammel facet. + * */ + + break; + } + case 7: //Ninja + { + if ((flags & ClientFlags.Tokuno) != 0) + return new CityInfo("Ninja DE", "Enimo's Residence", 414, 823, -1, Map.Malas); + + useHaven = true; + + new BadStartMessage(m, 1063487); + /* + * Unfortunately you are playing on a *NON-Samurai-Empire* game + * installation and cannot be transported to Tokuno. + * You will not be able to take your new player quest in Tokuno + * without an SE client. You are now being taken to the city of + * Haven on the Trammel facet. + * */ + + break; + } + } + + if (useHaven) + return m_NewHavenInfo; + + return args.City; + } + + private static void FixStats(ref int str, ref int dex, ref int intel, int max) + { + int vMax = max - 30; + + int vStr = str - 10; + int vDex = dex - 10; + int vInt = intel - 10; + + if (vStr < 0) + vStr = 0; + + if (vDex < 0) + vDex = 0; + + if (vInt < 0) + vInt = 0; + + int total = vStr + vDex + vInt; + + if (total == 0 || total == vMax) + return; + + double scalar = vMax / (double)total; + + vStr = (int)(vStr * scalar); + vDex = (int)(vDex * scalar); + vInt = (int)(vInt * scalar); + + FixStat(ref vStr, vStr + vDex + vInt - vMax, vMax); + FixStat(ref vDex, vStr + vDex + vInt - vMax, vMax); + FixStat(ref vInt, vStr + vDex + vInt - vMax, vMax); + + str = vStr + 10; + dex = vDex + 10; + intel = vInt + 10; + } + + private static void FixStat(ref int stat, int diff, int max) + { + stat += diff; + + if (stat < 0) + stat = 0; + else if (stat > max) + stat = max; + } + + private static void SetStats(Mobile m, NetState state, int str, int dex, int intel) + { + int max = state.NewCharacterCreation ? 90 : 80; + + FixStats(ref str, ref dex, ref intel, max); + + if (str < 10 || str > 60 || dex < 10 || dex > 60 || intel < 10 || intel > 60 || str + dex + intel != max) + { + str = 10; + dex = 10; + intel = 10; + } + + m.InitStats(str, dex, intel); + } + + private static void SetName(Mobile m, string name) + { + name = name.Trim(); + + if (!NameVerification.Validate(name, 2, 16, true, false, true, 1, NameVerification.SpaceDashPeriodQuote)) + name = "Generic Player"; + + m.Name = name; + } + + private static bool ValidSkills(SkillNameValue[] skills) + { + int total = 0; + + for (int i = 0; i < skills.Length; ++i) + { + if (skills[i].Value < 0 || skills[i].Value > 50) + return false; + + total += skills[i].Value; + + for (int j = i + 1; j < skills.Length; ++j) + if (skills[j].Value > 0 && skills[j].Name == skills[i].Name) + return false; + } + + return total == 100 || total == 120; + } + + private static void SetSkills(Mobile m, SkillNameValue[] skills, int prof) + { + switch (prof) + { + case 1: // Warrior + { + skills = new[] + { + new SkillNameValue(SkillName.Anatomy, 30), + new SkillNameValue(SkillName.Healing, 45), + new SkillNameValue(SkillName.Swords, 35), + new SkillNameValue(SkillName.Tactics, 50) + }; + + break; + } + case 2: // Magician + { + skills = new[] + { + new SkillNameValue(SkillName.EvalInt, 30), + new SkillNameValue(SkillName.Wrestling, 30), + new SkillNameValue(SkillName.Magery, 50), + new SkillNameValue(SkillName.Meditation, 50) + }; + + break; + } + case 3: // Blacksmith + { + skills = new[] + { + new SkillNameValue(SkillName.Mining, 30), + new SkillNameValue(SkillName.ArmsLore, 30), + new SkillNameValue(SkillName.Blacksmith, 50), + new SkillNameValue(SkillName.Tinkering, 50) + }; + + break; + } + case 4: // Necromancer + { + skills = new[] + { + new SkillNameValue(SkillName.Necromancy, 50), + new SkillNameValue(SkillName.Focus, 30), + new SkillNameValue(SkillName.SpiritSpeak, 30), + new SkillNameValue(SkillName.Swords, 30), + new SkillNameValue(SkillName.Tactics, 20) + }; + + break; + } + case 5: // Paladin + { + skills = new[] + { + new SkillNameValue(SkillName.Chivalry, 51), + new SkillNameValue(SkillName.Swords, 49), + new SkillNameValue(SkillName.Focus, 30), + new SkillNameValue(SkillName.Tactics, 30) + }; + + break; + } + case 6: //Samurai + { + skills = new[] + { + new SkillNameValue(SkillName.Bushido, 50), + new SkillNameValue(SkillName.Swords, 50), + new SkillNameValue(SkillName.Anatomy, 30), + new SkillNameValue(SkillName.Healing, 30) + }; + break; + } + case 7: //Ninja + { + skills = new[] + { + new SkillNameValue(SkillName.Ninjitsu, 50), + new SkillNameValue(SkillName.Hiding, 50), + new SkillNameValue(SkillName.Fencing, 30), + new SkillNameValue(SkillName.Stealth, 30) + }; + break; + } + default: + { + if (!ValidSkills(skills)) + return; + + break; + } + } + + bool addSkillItems = true; + bool elf = m.Race == Race.Elf; + + switch (prof) + { + case 1: // Warrior + { + if (elf) + EquipItem(new LeafChest()); + else + EquipItem(new LeatherChest()); + break; + } + case 4: // Necromancer + { + Container regs = new BagOfNecroReagents(50); + + if (!Core.AOS) + foreach (Item item in regs.Items) + item.LootType = LootType.Newbied; + + PackItem(regs); + + regs.LootType = LootType.Regular; + + EquipItem(new BoneHelm()); + + if (elf) + { + EquipItem(new ElvenMachete()); + EquipItem(NecroHue(new LeafChest())); + EquipItem(NecroHue(new LeafArms())); + EquipItem(NecroHue(new LeafGloves())); + EquipItem(NecroHue(new LeafGorget())); + EquipItem(NecroHue(new LeafGorget())); + EquipItem(NecroHue(new ElvenPants())); //TODO: Verify the pants + EquipItem(new ElvenBoots()); + } + else + { + EquipItem(new BoneHarvester()); + EquipItem(NecroHue(new LeatherChest())); + EquipItem(NecroHue(new LeatherArms())); + EquipItem(NecroHue(new LeatherGloves())); + EquipItem(NecroHue(new LeatherGorget())); + EquipItem(NecroHue(new LeatherLegs())); + EquipItem(NecroHue(new Skirt())); + EquipItem(new Sandals(0x8FD)); + } + + Spellbook + book = new NecromancerSpellbook( + (ulong)0x8981); // animate dead, evil omen, pain spike, summon familiar, wraith form + + PackItem(book); + + book.LootType = LootType.Blessed; + + addSkillItems = false; + + break; + } + case 5: // Paladin + { + if (elf) + { + EquipItem(new ElvenMachete()); + EquipItem(new WingedHelm()); + EquipItem(new LeafGorget()); + EquipItem(new LeafArms()); + EquipItem(new LeafChest()); + EquipItem(new LeafLegs()); + EquipItem(new ElvenBoots()); //Verify hue + } + else + { + EquipItem(new Broadsword()); + EquipItem(new Helmet()); + EquipItem(new PlateGorget()); + EquipItem(new RingmailArms()); + EquipItem(new RingmailChest()); + EquipItem(new RingmailLegs()); + EquipItem(new ThighBoots(0x748)); + EquipItem(new Cloak(0xCF)); + EquipItem(new BodySash(0xCF)); + } + + Spellbook book = new BookOfChivalry((ulong)0x3FF); + + PackItem(book); + + book.LootType = LootType.Blessed; + + addSkillItems = false; + + break; + } + + case 6: // Samurai + { + addSkillItems = false; + EquipItem(new HakamaShita(0x2C3)); + EquipItem(new Hakama(0x2C3)); + EquipItem(new SamuraiTabi(0x2C3)); + EquipItem(new TattsukeHakama(0x22D)); + EquipItem(new Bokuto()); + + if (elf) + EquipItem(new RavenHelm()); + else + EquipItem(new LeatherJingasa()); + + PackItem(new Scissors()); + PackItem(new Bandage(50)); + + Spellbook book = new BookOfBushido(); + PackItem(book); + + break; + } + case 7: // Ninja + { + addSkillItems = false; + EquipItem(new Kasa()); + + int[] hues = { 0x1A8, 0xEC, 0x99, 0x90, 0xB5, 0x336, 0x89 }; + //TODO: Verify that's ALL the hues for that above. + + EquipItem(new TattsukeHakama(hues[Utility.Random(hues.Length)])); + + EquipItem(new HakamaShita(0x2C3)); + EquipItem(new NinjaTabi(0x2C3)); + + if (elf) + EquipItem(new AssassinSpike()); + else + EquipItem(new Tekagi()); + + PackItem(new SmokeBomb()); + + Spellbook book = new BookOfNinjitsu(); + PackItem(book); + + break; + } + } + + for (int i = 0; i < skills.Length; ++i) + { + SkillNameValue snv = skills[i]; + + if (snv.Value > 0 && (snv.Name != SkillName.Stealth || prof == 7) && snv.Name != SkillName.RemoveTrap && + snv.Name != SkillName.Spellweaving) + { + Skill skill = m.Skills[snv.Name]; + + if (skill != null) + { + skill.BaseFixedPoint = snv.Value * 10; + + if (addSkillItems) + AddSkillItems(snv.Name, m); + } + } + } + } + + private static void EquipItem(Item item, bool mustEquip = false) + { + if (!Core.AOS) + item.LootType = LootType.Newbied; + + if (m_Mobile != null && m_Mobile.EquipItem(item)) + return; + + Container pack = m_Mobile.Backpack; + + if (!mustEquip && pack != null) + pack.DropItem(item); + else + item.Delete(); + } + + private static void PackItem(Item item) + { + if (!Core.AOS) + item.LootType = LootType.Newbied; + + Container pack = m_Mobile.Backpack; + + if (pack != null) + pack.DropItem(item); + else + item.Delete(); + } + + private static void PackInstrument() + { + switch (Utility.Random(6)) + { + case 0: + PackItem(new Drums()); + break; + case 1: + PackItem(new Harp()); + break; + case 2: + PackItem(new LapHarp()); + break; + case 3: + PackItem(new Lute()); + break; + case 4: + PackItem(new Tambourine()); + break; + case 5: + PackItem(new TambourineTassel()); + break; + } + } + + private static void PackScroll(int circle) + { + switch (Utility.Random(8) * (circle + 1)) + { + case 0: + PackItem(new ClumsyScroll()); + break; + case 1: + PackItem(new CreateFoodScroll()); + break; + case 2: + PackItem(new FeeblemindScroll()); + break; + case 3: + PackItem(new HealScroll()); + break; + case 4: + PackItem(new MagicArrowScroll()); + break; + case 5: + PackItem(new NightSightScroll()); + break; + case 6: + PackItem(new ReactiveArmorScroll()); + break; + case 7: + PackItem(new WeakenScroll()); + break; + case 8: + PackItem(new AgilityScroll()); + break; + case 9: + PackItem(new CunningScroll()); + break; + case 10: + PackItem(new CureScroll()); + break; + case 11: + PackItem(new HarmScroll()); + break; + case 12: + PackItem(new MagicTrapScroll()); + break; + case 13: + PackItem(new MagicUnTrapScroll()); + break; + case 14: + PackItem(new ProtectionScroll()); + break; + case 15: + PackItem(new StrengthScroll()); + break; + case 16: + PackItem(new BlessScroll()); + break; + case 17: + PackItem(new FireballScroll()); + break; + case 18: + PackItem(new MagicLockScroll()); + break; + case 19: + PackItem(new PoisonScroll()); + break; + case 20: + PackItem(new TelekinisisScroll()); + break; + case 21: + PackItem(new TeleportScroll()); + break; + case 22: + PackItem(new UnlockScroll()); + break; + case 23: + PackItem(new WallOfStoneScroll()); + break; + } + } + + private static Item NecroHue(Item item) + { + item.Hue = 0x2C3; + + return item; + } + + private static void AddSkillItems(SkillName skill, Mobile m) + { + bool elf = m.Race == Race.Elf; + + switch (skill) + { + case SkillName.Alchemy: + { + PackItem(new Bottle(4)); + PackItem(new MortarPestle()); + + int hue = Utility.RandomPinkHue(); + + if (elf) + { + if (m.Female) + EquipItem(new FemaleElvenRobe(hue)); + else + EquipItem(new MaleElvenRobe(hue)); + } + else + { + EquipItem(new Robe(Utility.RandomPinkHue())); + } + + break; + } + case SkillName.Anatomy: + { + PackItem(new Bandage(3)); + + int hue = Utility.RandomYellowHue(); + + if (elf) + { + if (m.Female) + EquipItem(new FemaleElvenRobe(hue)); + else + EquipItem(new MaleElvenRobe(hue)); + } + else + { + EquipItem(new Robe(hue)); + } + + break; + } + case SkillName.AnimalLore: + { + int hue = Utility.RandomBlueHue(); + + if (elf) + { + EquipItem(new WildStaff()); + + if (m.Female) + EquipItem(new FemaleElvenRobe(hue)); + else + EquipItem(new MaleElvenRobe(hue)); + } + else + { + EquipItem(new ShepherdsCrook()); + EquipItem(new Robe(hue)); + } + + break; + } + case SkillName.Archery: + { + PackItem(new Arrow(25)); + + if (elf) + EquipItem(new ElvenCompositeLongbow()); + else + EquipItem(new Bow()); + + break; + } + case SkillName.ArmsLore: + { + if (elf) + switch (Utility.Random(3)) + { + case 0: + EquipItem(new Leafblade()); + break; + case 1: + EquipItem(new RuneBlade()); + break; + case 2: + EquipItem(new DiamondMace()); + break; + } + else + switch (Utility.Random(3)) + { + case 0: + EquipItem(new Kryss()); + break; + case 1: + EquipItem(new Katana()); + break; + case 2: + EquipItem(new Club()); + break; + } + + break; + } + case SkillName.Begging: + { + if (elf) + EquipItem(new WildStaff()); + else + EquipItem(new GnarledStaff()); + break; + } + case SkillName.Blacksmith: + { + PackItem(new Tongs()); + PackItem(new Pickaxe()); + PackItem(new Pickaxe()); + PackItem(new IronIngot(50)); + EquipItem(new HalfApron(Utility.RandomYellowHue())); + break; + } + case SkillName.Bushido: + { + EquipItem(new Hakama()); + EquipItem(new Kasa()); + EquipItem(new BookOfBushido()); + break; + } + case SkillName.Fletching: + { + PackItem(new Board(14)); + PackItem(new Feather(5)); + PackItem(new Shaft(5)); + break; + } + case SkillName.Camping: + { + PackItem(new Bedroll()); + PackItem(new Kindling(5)); + break; + } + case SkillName.Carpentry: + { + PackItem(new Board(10)); + PackItem(new Saw()); + EquipItem(new HalfApron(Utility.RandomYellowHue())); + break; + } + case SkillName.Cartography: + { + PackItem(new BlankMap()); + PackItem(new BlankMap()); + PackItem(new BlankMap()); + PackItem(new BlankMap()); + PackItem(new Sextant()); + break; + } + case SkillName.Cooking: + { + PackItem(new Kindling(2)); + PackItem(new RawLambLeg()); + PackItem(new RawChickenLeg()); + PackItem(new RawFishSteak()); + PackItem(new SackFlour()); + PackItem(new Pitcher(BeverageType.Water)); + break; + } + case SkillName.Chivalry: + { + if (Core.ML) + PackItem(new BookOfChivalry((ulong)0x3FF)); + + break; + } + case SkillName.DetectHidden: + { + EquipItem(new Cloak(0x455)); + break; + } + case SkillName.Discordance: + { + PackInstrument(); + break; + } + case SkillName.Fencing: + { + if (elf) + EquipItem(new Leafblade()); + else + EquipItem(new Kryss()); + + break; + } + case SkillName.Fishing: + { + EquipItem(new FishingPole()); + + int hue = Utility.RandomYellowHue(); + + if (elf) + { + Item i = new Circlet(); + i.Hue = hue; + EquipItem(i); + } + else + { + EquipItem(new FloppyHat(hue)); + } + + break; + } + case SkillName.Healing: + { + PackItem(new Bandage(50)); + PackItem(new Scissors()); + break; + } + case SkillName.Herding: + { + if (elf) + EquipItem(new WildStaff()); + else + EquipItem(new ShepherdsCrook()); + + break; + } + case SkillName.Hiding: + { + EquipItem(new Cloak(0x455)); + break; + } + case SkillName.Inscribe: + { + PackItem(new BlankScroll(2)); + PackItem(new BlueBook()); + break; + } + case SkillName.ItemID: + { + if (elf) + EquipItem(new WildStaff()); + else + EquipItem(new GnarledStaff()); + break; + } + case SkillName.Lockpicking: + { + PackItem(new Lockpick(20)); + break; + } + case SkillName.Lumberjacking: + { + EquipItem(new Hatchet()); + break; + } + case SkillName.Macing: + { + if (elf) + EquipItem(new DiamondMace()); + else + EquipItem(new Club()); + + break; + } + case SkillName.Magery: + { + BagOfReagents regs = new BagOfReagents(30); + + if (!Core.AOS) + foreach (Item item in regs.Items) + item.LootType = LootType.Newbied; + + PackItem(regs); + + regs.LootType = LootType.Regular; + + PackScroll(0); + PackScroll(1); + PackScroll(2); + + Spellbook book = new Spellbook((ulong)0x382A8C38); + + EquipItem(book); + + book.LootType = LootType.Blessed; + + if (elf) + { + EquipItem(new Circlet()); + + if (m.Female) + EquipItem(new FemaleElvenRobe(Utility.RandomBlueHue())); + else + EquipItem(new MaleElvenRobe(Utility.RandomBlueHue())); + } + else + { + EquipItem(new WizardsHat()); + EquipItem(new Robe(Utility.RandomBlueHue())); + } + + break; + } + case SkillName.Mining: + { + PackItem(new Pickaxe()); + break; + } + case SkillName.Musicianship: + { + PackInstrument(); + break; + } + case SkillName.Necromancy: + { + if (Core.ML) + { + Container regs = new BagOfNecroReagents(50); + + PackItem(regs); + + regs.LootType = LootType.Regular; + } + + break; + } + case SkillName.Ninjitsu: + { + EquipItem(new Hakama(0x2C3)); //Only ninjas get the hued one. + EquipItem(new Kasa()); + EquipItem(new BookOfNinjitsu()); + break; + } + case SkillName.Parry: + { + EquipItem(new WoodenShield()); + break; + } + case SkillName.Peacemaking: + { + PackInstrument(); + break; + } + case SkillName.Poisoning: + { + PackItem(new LesserPoisonPotion()); + PackItem(new LesserPoisonPotion()); + break; + } + case SkillName.Provocation: + { + PackInstrument(); + break; + } + case SkillName.Snooping: + { + PackItem(new Lockpick(20)); + break; + } + case SkillName.SpiritSpeak: + { + EquipItem(new Cloak(0x455)); + break; + } + case SkillName.Stealing: + { + PackItem(new Lockpick(20)); + break; + } + case SkillName.Swords: + { + if (elf) + EquipItem(new RuneBlade()); + else + EquipItem(new Katana()); + + break; + } + case SkillName.Tactics: + { + if (elf) + EquipItem(new RuneBlade()); + else + EquipItem(new Katana()); + + break; + } + case SkillName.Tailoring: + { + PackItem(new BoltOfCloth()); + PackItem(new SewingKit()); + break; + } + case SkillName.Tracking: + { + Item shoes = m_Mobile?.FindItemOnLayer(Layer.Shoes); + + shoes?.Delete(); + + int hue = Utility.RandomYellowHue(); + + if (elf) + EquipItem(new ElvenBoots(hue)); + else + EquipItem(new Boots(hue)); + + EquipItem(new SkinningKnife()); + break; + } + case SkillName.Veterinary: + { + PackItem(new Bandage(5)); + PackItem(new Scissors()); + break; + } + case SkillName.Wrestling: + { + if (elf) + EquipItem(new LeafGloves()); + else + EquipItem(new LeatherGloves()); + + break; + } + } + } + + private class BadStartMessage : Timer + { + private int m_Message; + private Mobile m_Mobile; + + public BadStartMessage(Mobile m, int message) : base(TimeSpan.FromSeconds(3.5)) + { + m_Mobile = m; + m_Message = message; + Start(); + } + + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(m_Message); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Cleanup.cs b/Scripts/Misc/Cleanup.cs index 760da1c95..f552380f0 100644 --- a/Scripts/Misc/Cleanup.cs +++ b/Scripts/Misc/Cleanup.cs @@ -1,163 +1,169 @@ using System; using System.Collections.Generic; using Server.Items; -using Server.Multis; using Server.Mobiles; +using Server.Multis; namespace Server.Misc { - public class Cleanup - { - public static void Initialize() - { - Timer.DelayCall( TimeSpan.FromSeconds( 2.5 ), Run ); - } + public class Cleanup + { + public static void Initialize() + { + Timer.DelayCall(TimeSpan.FromSeconds(2.5), Run); + } - public static void Run() - { - List items = new List(); - List validItems = new List(); - List hairCleanup = new List(); + public static void Run() + { + List items = new List(); + List validItems = new List(); + List hairCleanup = new List(); - int boxes = 0; + int boxes = 0; - foreach ( Item item in World.Items.Values ) - { - if ( item.Map == null ) - { - items.Add( item ); - continue; - } - if ( item is CommodityDeed deed ) - { - if ( deed.Commodity != null ) - validItems.Add( deed.Commodity ); + foreach (Item item in World.Items.Values) + { + if (item.Map == null) + { + items.Add(item); + continue; + } - continue; - } - if ( item is BaseHouse house ) - { - foreach ( RelocatedEntity relEntity in house.RelocatedEntities ) - { - if ( relEntity.Entity is Item item1 ) - validItems.Add( item1 ); - } + if (item is CommodityDeed deed) + { + if (deed.Commodity != null) + validItems.Add(deed.Commodity); - foreach ( VendorInventory inventory in house.VendorInventories ) - { - foreach ( Item subItem in inventory.Items ) - validItems.Add( subItem ); - } - } - else if ( item is BankBox box ) - { - Mobile owner = box.Owner; + continue; + } - if ( owner == null ) - { - items.Add( box ); - ++boxes; - } - else if ( box.Items.Count == 0 ) - { - items.Add( box ); - ++boxes; - } + if (item is BaseHouse house) + { + foreach (RelocatedEntity relEntity in house.RelocatedEntities) + if (relEntity.Entity is Item item1) + validItems.Add(item1); - continue; - } - else if ( (item.Layer == Layer.Hair || item.Layer == Layer.FacialHair) ) - { - object rootParent = item.RootParent; + foreach (VendorInventory inventory in house.VendorInventories) + foreach (Item subItem in inventory.Items) + validItems.Add(subItem); + } + else if (item is BankBox box) + { + Mobile owner = box.Owner; - if ( rootParent is Mobile rootMobile ) - { - if ( item.Parent != rootMobile && rootMobile.AccessLevel == AccessLevel.Player ) - { - items.Add( item ); - continue; - } - if ( item.Parent == rootMobile ) - { - hairCleanup.Add( rootMobile ); - continue; - } - } - } + if (owner == null) + { + items.Add(box); + ++boxes; + } + else if (box.Items.Count == 0) + { + items.Add(box); + ++boxes; + } - if ( item.Parent != null || item.Map != Map.Internal || item.HeldBy != null ) - continue; + continue; + } + else if (item.Layer == Layer.Hair || item.Layer == Layer.FacialHair) + { + object rootParent = item.RootParent; - if ( item.Location != Point3D.Zero ) - continue; + if (rootParent is Mobile rootMobile) + { + if (item.Parent != rootMobile && rootMobile.AccessLevel == AccessLevel.Player) + { + items.Add(item); + continue; + } - if ( !IsBuggable( item ) ) - continue; + if (item.Parent == rootMobile) + { + hairCleanup.Add(rootMobile); + continue; + } + } + } - items.Add( item ); - } + if (item.Parent != null || item.Map != Map.Internal || item.HeldBy != null) + continue; - for ( int i = 0; i < validItems.Count; ++i ) - items.Remove( validItems[i] ); + if (item.Location != Point3D.Zero) + continue; - if ( items.Count > 0 ) - { - if ( boxes > 0 ) - Console.WriteLine( "Cleanup: Detected {0} inaccessible items, including {1} bank boxes, removing..", items.Count, boxes ); - else - Console.WriteLine( "Cleanup: Detected {0} inaccessible items, removing..", items.Count ); + if (!IsBuggable(item)) + continue; - for ( int i = 0; i < items.Count; ++i ) - items[i].Delete(); - } + items.Add(item); + } - if ( hairCleanup.Count > 0 ) - { - Console.WriteLine( "Cleanup: Detected {0} hair and facial hair items being worn, converting to their virtual counterparts..", hairCleanup.Count ); + for (int i = 0; i < validItems.Count; ++i) + items.Remove(validItems[i]); - for ( int i = 0; i < hairCleanup.Count; i++ ) - hairCleanup[i].ConvertHair(); - } - } + if (items.Count > 0) + { + if (boxes > 0) + Console.WriteLine("Cleanup: Detected {0} inaccessible items, including {1} bank boxes, removing..", + items.Count, boxes); + else + Console.WriteLine("Cleanup: Detected {0} inaccessible items, removing..", items.Count); - public static bool IsBuggable( Item item ) - { - if ( item is Fists ) - return false; + for (int i = 0; i < items.Count; ++i) + items[i].Delete(); + } - if ( item is ICommodity || item is BaseBoat - || item is Fish || item is BigFish - || item is BasePotion || item is Food || item is CookableFood - || item is SpecialFishingNet || item is BaseMagicFish - || item is Shoes || item is Sandals - || item is Boots || item is ThighBoots - || item is TreasureMap || item is MessageInABottle - || item is BaseArmor || item is BaseWeapon - || item is BaseClothing - || ( item is BaseJewel && Core.AOS ) - || ( item is BasePotion && Core.ML ) - #region Champion artifacts - || item is SkullPole - || item is EvilIdolSkull - || item is MonsterStatuette - || item is Pier - || item is ArtifactLargeVase - || item is ArtifactVase - || item is MinotaurStatueDeed - || item is SwampTile - || item is WallBlood - || item is TatteredAncientMummyWrapping - || item is LavaTile - || item is DemonSkull - || item is Web - || item is WaterTile - || item is WindSpirit - || item is DirtPatch - || item is Futon ) - #endregion - return true; + if (hairCleanup.Count > 0) + { + Console.WriteLine( + "Cleanup: Detected {0} hair and facial hair items being worn, converting to their virtual counterparts..", + hairCleanup.Count); - return false; - } - } -} + for (int i = 0; i < hairCleanup.Count; i++) + hairCleanup[i].ConvertHair(); + } + } + + public static bool IsBuggable(Item item) + { + if (item is Fists) + return false; + + if (item is ICommodity || item is BaseBoat + || item is Fish || item is BigFish + || item is BasePotion || item is Food || item is CookableFood + || item is SpecialFishingNet || item is BaseMagicFish + || item is Shoes || item is Sandals + || item is Boots || item is ThighBoots + || item is TreasureMap || item is MessageInABottle + || item is BaseArmor || item is BaseWeapon + || item is BaseClothing + || item is BaseJewel && Core.AOS + || item is BasePotion && Core.ML + + #region Champion artifacts + + || item is SkullPole + || item is EvilIdolSkull + || item is MonsterStatuette + || item is Pier + || item is ArtifactLargeVase + || item is ArtifactVase + || item is MinotaurStatueDeed + || item is SwampTile + || item is WallBlood + || item is TatteredAncientMummyWrapping + || item is LavaTile + || item is DemonSkull + || item is Web + || item is WaterTile + || item is WindSpirit + || item is DirtPatch + || item is Futon) + + #endregion + + return true; + + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/ClientVerification.cs b/Scripts/Misc/ClientVerification.cs index b5c1a2968..f7d1050b9 100644 --- a/Scripts/Misc/ClientVerification.cs +++ b/Scripts/Misc/ClientVerification.cs @@ -1,166 +1,175 @@ using System; using System.Diagnostics; using System.IO; -using Server.Network; using Server.Gumps; using Server.Mobiles; +using Server.Network; namespace Server.Misc { - public class ClientVerification - { - private enum OldClientResponse - { - Ignore, - Warn, - Annoy, - LenientKick, - Kick - } + public class ClientVerification + { + private static bool m_DetectClientRequirement = true; + private static OldClientResponse m_OldClientResponse = OldClientResponse.LenientKick; - private static bool m_DetectClientRequirement = true; - private static OldClientResponse m_OldClientResponse = OldClientResponse.LenientKick; + private static TimeSpan m_AgeLeniency = TimeSpan.FromDays(10); + private static TimeSpan m_GameTimeLeniency = TimeSpan.FromHours(25); - private static TimeSpan m_AgeLeniency = TimeSpan.FromDays( 10 ); - private static TimeSpan m_GameTimeLeniency = TimeSpan.FromHours( 25 ); + public static ClientVersion Required{ get; set; } - public static ClientVersion Required { get; set; } + public static bool AllowRegular{ get; set; } = true; - public static bool AllowRegular { get; set; } = true; + public static bool AllowUOTD{ get; set; } = true; - public static bool AllowUOTD { get; set; } = true; + public static bool AllowGod{ get; set; } = true; - public static bool AllowGod { get; set; } = true; + public static TimeSpan KickDelay{ get; set; } = TimeSpan.FromSeconds(20.0); - public static TimeSpan KickDelay { get; set; } = TimeSpan.FromSeconds( 20.0 ); + public static void Initialize() + { + EventSink.ClientVersionReceived += EventSink_ClientVersionReceived; - public static void Initialize() - { - EventSink.ClientVersionReceived += EventSink_ClientVersionReceived; + //ClientVersion.Required = null; + //Required = new ClientVersion( "6.0.0.0" ); - //ClientVersion.Required = null; - //Required = new ClientVersion( "6.0.0.0" ); + if (m_DetectClientRequirement) + { + string path = Core.FindDataFile("client.exe"); - if ( m_DetectClientRequirement ) - { - string path = Core.FindDataFile( "client.exe" ); + if (File.Exists(path)) + { + FileVersionInfo info = FileVersionInfo.GetVersionInfo(path); - if ( File.Exists( path ) ) - { - FileVersionInfo info = FileVersionInfo.GetVersionInfo( path ); + if (info.FileMajorPart != 0 || info.FileMinorPart != 0 || info.FileBuildPart != 0 || + info.FilePrivatePart != 0) + Required = new ClientVersion(info.FileMajorPart, info.FileMinorPart, info.FileBuildPart, + info.FilePrivatePart); + } + } - if ( info.FileMajorPart != 0 || info.FileMinorPart != 0 || info.FileBuildPart != 0 || info.FilePrivatePart != 0 ) - { - Required = new ClientVersion( info.FileMajorPart, info.FileMinorPart, info.FileBuildPart, info.FilePrivatePart ); - } - } - } + if (Required != null) + { + Utility.PushColor(ConsoleColor.White); + Console.WriteLine("Restricting client version to {0}. Action to be taken: {1}", Required, + m_OldClientResponse); + Utility.PopColor(); + } + } - if ( Required != null ) - { - Utility.PushColor( ConsoleColor.White ); - Console.WriteLine( "Restricting client version to {0}. Action to be taken: {1}", Required, m_OldClientResponse ); - Utility.PopColor(); - } - } + private static void EventSink_ClientVersionReceived(ClientVersionReceivedArgs e) + { + string kickMessage = null; + NetState state = e.State; + ClientVersion version = e.Version; - private static void EventSink_ClientVersionReceived( ClientVersionReceivedArgs e ) - { - string kickMessage = null; - NetState state = e.State; - ClientVersion version = e.Version; + if (state.Mobile == null || state.Mobile.AccessLevel > AccessLevel.Player) + return; - if ( state.Mobile == null || state.Mobile.AccessLevel > AccessLevel.Player ) - return; + if (Required != null && version < Required && (m_OldClientResponse == OldClientResponse.Kick || + m_OldClientResponse == OldClientResponse.LenientKick && + DateTime.UtcNow - state.Mobile.CreationTime > m_AgeLeniency && + state.Mobile is PlayerMobile mobile && + mobile.GameTime > m_GameTimeLeniency)) + { + kickMessage = $"This server requires your client version be at least {Required}."; + } + else if (!AllowGod || !AllowRegular || !AllowUOTD) + { + if (!AllowGod && version.Type == ClientType.God) + kickMessage = "This server does not allow god clients to connect."; + else if (!AllowRegular && version.Type == ClientType.Regular) + kickMessage = "This server does not allow regular clients to connect."; + else if (!AllowUOTD && state.IsUOTDClient) + kickMessage = "This server does not allow UO:TD clients to connect."; - if ( Required != null && version < Required && ( m_OldClientResponse == OldClientResponse.Kick ||( m_OldClientResponse == OldClientResponse.LenientKick && (DateTime.UtcNow - state.Mobile.CreationTime) > m_AgeLeniency && state.Mobile is PlayerMobile mobile && mobile.GameTime > m_GameTimeLeniency ))) - { - kickMessage = $"This server requires your client version be at least {Required}."; - } - else if ( !AllowGod || !AllowRegular || !AllowUOTD ) - { - if ( !AllowGod && version.Type == ClientType.God ) - kickMessage = "This server does not allow god clients to connect."; - else if ( !AllowRegular && version.Type == ClientType.Regular ) - kickMessage = "This server does not allow regular clients to connect."; - else if ( !AllowUOTD && state.IsUOTDClient ) - kickMessage = "This server does not allow UO:TD clients to connect."; + if (!AllowGod && !AllowRegular && !AllowUOTD) + { + kickMessage = "This server does not allow any clients to connect."; + } + else if (AllowGod && !AllowRegular && !AllowUOTD && version.Type != ClientType.God) + { + kickMessage = "This server requires you to use the god client."; + } + else if (kickMessage != null) + { + if (AllowRegular && AllowUOTD) + kickMessage += " You can use regular or UO:TD clients."; + else if (AllowRegular) + kickMessage += " You can use regular clients."; + else if (AllowUOTD) + kickMessage += " You can use UO:TD clients."; + } + } - if ( !AllowGod && !AllowRegular && !AllowUOTD ) - { - kickMessage = "This server does not allow any clients to connect."; - } - else if ( AllowGod && !AllowRegular && !AllowUOTD && version.Type != ClientType.God ) - { - kickMessage = "This server requires you to use the god client."; - } - else if ( kickMessage != null ) - { - if ( AllowRegular && AllowUOTD ) - kickMessage += " You can use regular or UO:TD clients."; - else if ( AllowRegular ) - kickMessage += " You can use regular clients."; - else if ( AllowUOTD ) - kickMessage += " You can use UO:TD clients."; - } - } + if (kickMessage != null) + { + state.Mobile.SendMessage(0x22, kickMessage); + state.Mobile.SendMessage(0x22, "You will be disconnected in {0} seconds.", KickDelay.TotalSeconds); - if ( kickMessage != null ) - { - state.Mobile.SendMessage( 0x22, kickMessage ); - state.Mobile.SendMessage( 0x22, "You will be disconnected in {0} seconds.", KickDelay.TotalSeconds ); + Timer.DelayCall(KickDelay, delegate + { + if (state.Socket != null) + { + Console.WriteLine("Client: {0}: Disconnecting, bad version", state); + state.Dispose(); + } + }); + } + else if (Required != null && version < Required) + { + switch (m_OldClientResponse) + { + case OldClientResponse.Warn: + { + state.Mobile.SendMessage(0x22, "Your client is out of date. Please update your client.", Required); + state.Mobile.SendMessage(0x22, "This server recommends that your client version be at least {0}.", + Required); + break; + } + case OldClientResponse.LenientKick: + case OldClientResponse.Annoy: + { + SendAnnoyGump(state.Mobile); + break; + } + } + } + } - Timer.DelayCall( KickDelay, delegate - { - if ( state.Socket != null ) - { - Console.WriteLine( "Client: {0}: Disconnecting, bad version", state ); - state.Dispose(); - } - } ); - } - else if ( Required != null && version < Required ) - { - switch( m_OldClientResponse ) - { - case OldClientResponse.Warn: - { - state.Mobile.SendMessage( 0x22, "Your client is out of date. Please update your client.", Required ); - state.Mobile.SendMessage( 0x22, "This server recommends that your client version be at least {0}.", Required ); - break; - } - case OldClientResponse.LenientKick: - case OldClientResponse.Annoy: - { - SendAnnoyGump( state.Mobile ); - break; - } - } - } - } + private static void SendAnnoyGump(Mobile m) + { + if (m.NetState != null && m.NetState.Version < Required) + { + Gump g = new WarningGump(1060637, 30720, + $"Your client is out of date. Please update your client.
This server recommends that your client version be at least {Required}.

You are currently using version {m.NetState.Version}.

To patch, run UOPatch.exe inside your Ultima Online folder.", + 0xFFC000, 480, 360, + delegate + { + m.SendMessage("You will be reminded of this again."); - private static void SendAnnoyGump( Mobile m ) - { - if ( m.NetState != null && m.NetState.Version < Required ) - { - Gump g = new WarningGump( 1060637, 30720, - $"Your client is out of date. Please update your client.
This server recommends that your client version be at least {Required}.

You are currently using version {m.NetState.Version}.

To patch, run UOPatch.exe inside your Ultima Online folder.", 0xFFC000, 480, 360, - delegate( Mobile mob, bool selection, object o ) - { - m.SendMessage( "You will be reminded of this again." ); + if (m_OldClientResponse == OldClientResponse.LenientKick) + m.SendMessage( + "Old clients will be kicked after {0} days of character age and {1} hours of play time", + m_AgeLeniency, m_GameTimeLeniency); - if ( m_OldClientResponse == OldClientResponse.LenientKick ) - m.SendMessage( "Old clients will be kicked after {0} days of character age and {1} hours of play time", m_AgeLeniency, m_GameTimeLeniency ); + Timer.DelayCall(TimeSpan.FromMinutes(Utility.Random(5, 15)), delegate { SendAnnoyGump(m); }); + }, null, false); - Timer.DelayCall( TimeSpan.FromMinutes( Utility.Random( 5, 15 ) ), delegate { SendAnnoyGump( m ); } ); - }, null, false ); + g.Dragable = false; + g.Closable = false; + g.Resizable = false; - g.Dragable = false; - g.Closable = false; - g.Resizable = false; + m.SendGump(g); + } + } - m.SendGump( g ); - } - } - } -} + private enum OldClientResponse + { + Ignore, + Warn, + Annoy, + LenientKick, + Kick + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/CrashGuard.cs b/Scripts/Misc/CrashGuard.cs index 8fab0ac06..b397b9577 100644 --- a/Scripts/Misc/CrashGuard.cs +++ b/Scripts/Misc/CrashGuard.cs @@ -8,245 +8,256 @@ using Server.Network; namespace Server.Misc { - public class CrashGuard - { - private static bool Enabled = true; - private static bool SaveBackup = true; - private static bool RestartServer = true; - private static bool GenerateReport = true; + public class CrashGuard + { + private static bool Enabled = true; + private static bool SaveBackup = true; + private static bool RestartServer = true; + private static bool GenerateReport = true; - public static void Initialize() - { - if ( Enabled ) // If enabled, register our crash event handler - EventSink.Crashed += CrashGuard_OnCrash; - } + public static void Initialize() + { + if (Enabled) // If enabled, register our crash event handler + EventSink.Crashed += CrashGuard_OnCrash; + } - public static void CrashGuard_OnCrash( CrashedEventArgs e ) - { - if ( GenerateReport ) - GenerateCrashReport( e ); + public static void CrashGuard_OnCrash(CrashedEventArgs e) + { + if (GenerateReport) + GenerateCrashReport(e); - World.WaitForWriteCompletion(); + World.WaitForWriteCompletion(); - if ( SaveBackup ) - Backup(); + if (SaveBackup) + Backup(); - /*if ( Core.Service ) - e.Close = true; - else */ if ( RestartServer ) - Restart( e ); - } + /*if ( Core.Service ) + e.Close = true; + else */ + if (RestartServer) + Restart(e); + } - private static void SendEmail( string filePath ) - { - Console.Write( "Crash: Sending email..." ); + private static void SendEmail(string filePath) + { + Console.Write("Crash: Sending email..."); - MailMessage message = new MailMessage( Email.FromAddress, Email.CrashAddresses ); + MailMessage message = new MailMessage(Email.FromAddress, Email.CrashAddresses); - message.Subject = "Automated RunUO Crash Report"; + message.Subject = "Automated RunUO Crash Report"; - message.Body = "Automated RunUO Crash Report. See attachment for details."; + message.Body = "Automated RunUO Crash Report. See attachment for details."; - message.Attachments.Add( new Attachment( filePath ) ); + message.Attachments.Add(new Attachment(filePath)); - if ( Email.Send( message ) ) - Console.WriteLine( "done" ); - else - Console.WriteLine( "failed" ); - } + if (Email.Send(message)) + Console.WriteLine("done"); + else + Console.WriteLine("failed"); + } - private static string GetRoot() - { - try - { - return Path.GetDirectoryName( Environment.GetCommandLineArgs()[0] ); - } - catch - { - return ""; - } - } + private static string GetRoot() + { + try + { + return Path.GetDirectoryName(Environment.GetCommandLineArgs()[0]); + } + catch + { + return ""; + } + } - private static string Combine( string path1, string path2 ) - { - if ( path1.Length == 0 ) - return path2; + private static string Combine(string path1, string path2) + { + if (path1.Length == 0) + return path2; - return Path.Combine( path1, path2 ); - } + return Path.Combine(path1, path2); + } - private static void Restart( CrashedEventArgs e ) - { - string root = GetRoot(); + private static void Restart(CrashedEventArgs e) + { + string root = GetRoot(); - Console.Write( "Crash: Restarting..." ); + Console.Write("Crash: Restarting..."); - try - { - Process.Start( Core.ExePath, Core.Arguments ); - Console.WriteLine( "done" ); + try + { + Process.Start(Core.ExePath, Core.Arguments); + Console.WriteLine("done"); - e.Close = true; - } - catch - { - Console.WriteLine( "failed" ); - } - } + e.Close = true; + } + catch + { + Console.WriteLine("failed"); + } + } - private static void CreateDirectory( string path ) - { - if ( !Directory.Exists( path ) ) - Directory.CreateDirectory( path ); - } + private static void CreateDirectory(string path) + { + if (!Directory.Exists(path)) + Directory.CreateDirectory(path); + } - private static void CreateDirectory( string path1, string path2 ) - { - CreateDirectory( Combine( path1, path2 ) ); - } + private static void CreateDirectory(string path1, string path2) + { + CreateDirectory(Combine(path1, path2)); + } - private static void CopyFile( string rootOrigin, string rootBackup, string path ) - { - string originPath = Combine( rootOrigin, path ); - string backupPath = Combine( rootBackup, path ); + private static void CopyFile(string rootOrigin, string rootBackup, string path) + { + string originPath = Combine(rootOrigin, path); + string backupPath = Combine(rootBackup, path); - try - { - if ( File.Exists( originPath ) ) - File.Copy( originPath, backupPath ); - } - catch - { - } - } + try + { + if (File.Exists(originPath)) + File.Copy(originPath, backupPath); + } + catch + { + } + } - private static void Backup() - { - Console.Write( "Crash: Backing up..." ); + private static void Backup() + { + Console.Write("Crash: Backing up..."); - try - { - string timeStamp = GetTimeStamp(); + try + { + string timeStamp = GetTimeStamp(); - string root = GetRoot(); - string rootBackup = Combine( root, $"Backups/Crashed/{timeStamp}/"); - string rootOrigin = Combine( root, string.Format( "Saves/" ) ); + string root = GetRoot(); + string rootBackup = Combine(root, $"Backups/Crashed/{timeStamp}/"); + string rootOrigin = Combine(root, "Saves/"); - // Create new directories - CreateDirectory( rootBackup ); - CreateDirectory( rootBackup, "Accounts/" ); - CreateDirectory( rootBackup, "Items/" ); - CreateDirectory( rootBackup, "Mobiles/" ); - CreateDirectory( rootBackup, "Guilds/" ); - CreateDirectory( rootBackup, "Regions/" ); + // Create new directories + CreateDirectory(rootBackup); + CreateDirectory(rootBackup, "Accounts/"); + CreateDirectory(rootBackup, "Items/"); + CreateDirectory(rootBackup, "Mobiles/"); + CreateDirectory(rootBackup, "Guilds/"); + CreateDirectory(rootBackup, "Regions/"); - // Copy files - CopyFile( rootOrigin, rootBackup, "Accounts/Accounts.xml" ); + // Copy files + CopyFile(rootOrigin, rootBackup, "Accounts/Accounts.xml"); - CopyFile( rootOrigin, rootBackup, "Items/Items.bin" ); - CopyFile( rootOrigin, rootBackup, "Items/Items.idx" ); - CopyFile( rootOrigin, rootBackup, "Items/Items.tdb" ); + CopyFile(rootOrigin, rootBackup, "Items/Items.bin"); + CopyFile(rootOrigin, rootBackup, "Items/Items.idx"); + CopyFile(rootOrigin, rootBackup, "Items/Items.tdb"); - CopyFile( rootOrigin, rootBackup, "Mobiles/Mobiles.bin" ); - CopyFile( rootOrigin, rootBackup, "Mobiles/Mobiles.idx" ); - CopyFile( rootOrigin, rootBackup, "Mobiles/Mobiles.tdb" ); + CopyFile(rootOrigin, rootBackup, "Mobiles/Mobiles.bin"); + CopyFile(rootOrigin, rootBackup, "Mobiles/Mobiles.idx"); + CopyFile(rootOrigin, rootBackup, "Mobiles/Mobiles.tdb"); - CopyFile( rootOrigin, rootBackup, "Guilds/Guilds.bin" ); - CopyFile( rootOrigin, rootBackup, "Guilds/Guilds.idx" ); + CopyFile(rootOrigin, rootBackup, "Guilds/Guilds.bin"); + CopyFile(rootOrigin, rootBackup, "Guilds/Guilds.idx"); - CopyFile( rootOrigin, rootBackup, "Regions/Regions.bin" ); - CopyFile( rootOrigin, rootBackup, "Regions/Regions.idx" ); + CopyFile(rootOrigin, rootBackup, "Regions/Regions.bin"); + CopyFile(rootOrigin, rootBackup, "Regions/Regions.idx"); - Console.WriteLine( "done" ); - } - catch - { - Console.WriteLine( "failed" ); - } - } + Console.WriteLine("done"); + } + catch + { + Console.WriteLine("failed"); + } + } - private static void GenerateCrashReport( CrashedEventArgs e ) - { - Console.Write( "Crash: Generating report..." ); + private static void GenerateCrashReport(CrashedEventArgs e) + { + Console.Write("Crash: Generating report..."); - try - { - string timeStamp = GetTimeStamp(); - string fileName = $"Crash {timeStamp}.log"; + try + { + string timeStamp = GetTimeStamp(); + string fileName = $"Crash {timeStamp}.log"; - string root = GetRoot(); - string filePath = Combine( root, fileName ); + string root = GetRoot(); + string filePath = Combine(root, fileName); - using ( StreamWriter op = new StreamWriter( filePath ) ) - { - Version ver = Core.Assembly.GetName().Version; + using (StreamWriter op = new StreamWriter(filePath)) + { + Version ver = Core.Assembly.GetName().Version; - op.WriteLine( "Server Crash Report" ); - op.WriteLine( "===================" ); - op.WriteLine(); - op.WriteLine( "RunUO Version {0}.{1}, Build {2}.{3}", ver.Major, ver.Minor, ver.Build, ver.Revision ); - op.WriteLine( "Operating System: {0}", Environment.OSVersion ); - op.WriteLine( ".NET Framework: {0}", Environment.Version ); - op.WriteLine( "Time: {0}", DateTime.UtcNow ); + op.WriteLine("Server Crash Report"); + op.WriteLine("==================="); + op.WriteLine(); + op.WriteLine("RunUO Version {0}.{1}, Build {2}.{3}", ver.Major, ver.Minor, ver.Build, ver.Revision); + op.WriteLine("Operating System: {0}", Environment.OSVersion); + op.WriteLine(".NET Framework: {0}", Environment.Version); + op.WriteLine("Time: {0}", DateTime.UtcNow); - try { op.WriteLine( "Mobiles: {0}", World.Mobiles.Count ); } - catch {} + try + { + op.WriteLine("Mobiles: {0}", World.Mobiles.Count); + } + catch + { + } - try { op.WriteLine( "Items: {0}", World.Items.Count ); } - catch {} + try + { + op.WriteLine("Items: {0}", World.Items.Count); + } + catch + { + } - op.WriteLine( "Exception:" ); - op.WriteLine( e.Exception ); - op.WriteLine(); + op.WriteLine("Exception:"); + op.WriteLine(e.Exception); + op.WriteLine(); - op.WriteLine( "Clients:" ); + op.WriteLine("Clients:"); - try - { - List states = NetState.Instances; + try + { + List states = NetState.Instances; - op.WriteLine( "- Count: {0}", states.Count ); + op.WriteLine("- Count: {0}", states.Count); - for ( int i = 0; i < states.Count; ++i ) - { - NetState state = states[i]; + for (int i = 0; i < states.Count; ++i) + { + NetState state = states[i]; - op.Write( "+ {0}:", state ); + op.Write("+ {0}:", state); - if ( state.Account is Account a ) - op.Write( " (account = {0})", a.Username ); + if (state.Account is Account a) + op.Write(" (account = {0})", a.Username); - Mobile m = state.Mobile; + Mobile m = state.Mobile; - if ( m != null ) - op.Write( " (mobile = 0x{0:X} '{1}')", m.Serial.Value, m.Name ); + if (m != null) + op.Write(" (mobile = 0x{0:X} '{1}')", m.Serial.Value, m.Name); - op.WriteLine(); - } - } - catch - { - op.WriteLine( "- Failed" ); - } - } + op.WriteLine(); + } + } + catch + { + op.WriteLine("- Failed"); + } + } - Console.WriteLine( "done" ); + Console.WriteLine("done"); - if ( Email.FromAddress != null && Email.CrashAddresses != null ) - SendEmail( filePath ); - } - catch - { - Console.WriteLine( "failed" ); - } - } + if (Email.FromAddress != null && Email.CrashAddresses != null) + SendEmail(filePath); + } + catch + { + Console.WriteLine("failed"); + } + } - private static string GetTimeStamp() - { - DateTime now = DateTime.UtcNow; + private static string GetTimeStamp() + { + DateTime now = DateTime.UtcNow; - return $"{now.Day}-{now.Month}-{now.Year}-{now.Hour}-{now.Minute}-{now.Second}"; - } - } -} + return $"{now.Day}-{now.Month}-{now.Year}-{now.Hour}-{now.Minute}-{now.Second}"; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/CurrentExpansion.cs b/Scripts/Misc/CurrentExpansion.cs index 43c31ca61..3ff96d7ed 100644 --- a/Scripts/Misc/CurrentExpansion.cs +++ b/Scripts/Misc/CurrentExpansion.cs @@ -3,37 +3,38 @@ using Server.Network; namespace Server { - public class CurrentExpansion - { - private static readonly Expansion Expansion = Expansion.TOL; + public class CurrentExpansion + { + private static readonly Expansion Expansion = Expansion.TOL; - public static void Configure() - { - Core.Expansion = Expansion; + public static void Configure() + { + Core.Expansion = Expansion; - AccountGold.Enabled = Core.TOL; - AccountGold.ConvertOnBank = true; - AccountGold.ConvertOnTrade = false; - VirtualCheck.UseEditGump = true; + AccountGold.Enabled = Core.TOL; + AccountGold.ConvertOnBank = true; + AccountGold.ConvertOnTrade = false; + VirtualCheck.UseEditGump = true; - bool Enabled = Core.AOS; + bool Enabled = Core.AOS; - Mobile.InsuranceEnabled = Enabled; - ObjectPropertyList.Enabled = Enabled; - Mobile.VisibleDamageType = Enabled ? VisibleDamageType.Related : VisibleDamageType.None; - Mobile.GuildClickMessage = !Enabled; - Mobile.AsciiClickMessage = !Enabled; + Mobile.InsuranceEnabled = Enabled; + ObjectPropertyList.Enabled = Enabled; + Mobile.VisibleDamageType = Enabled ? VisibleDamageType.Related : VisibleDamageType.None; + Mobile.GuildClickMessage = !Enabled; + Mobile.AsciiClickMessage = !Enabled; - if ( Enabled ) - { - AOS.DisableStatInfluences(); + if (Enabled) + { + AOS.DisableStatInfluences(); - if ( ObjectPropertyList.Enabled ) - PacketHandlers.SingleClickProps = true; // single click for everything is overridden to check object property list + if (ObjectPropertyList.Enabled) + PacketHandlers.SingleClickProps = + true; // single click for everything is overridden to check object property list - Mobile.ActionDelay = 1000; - Mobile.AOSStatusHandler = AOS.GetStatus; - } - } - } -} + Mobile.ActionDelay = 1000; + Mobile.AOSStatusHandler = AOS.GetStatus; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/DataPath.cs b/Scripts/Misc/DataPath.cs index 84a918d75..2914455b7 100644 --- a/Scripts/Misc/DataPath.cs +++ b/Scripts/Misc/DataPath.cs @@ -4,103 +4,105 @@ using Microsoft.Win32; namespace Server.Misc { - public class DataPath - { - /* If you have not installed Ultima Online, - * or wish the server to use a separate set of datafiles, - * change the 'CustomPath' value. - * Example: - * private static string CustomPath = @"C:\Program Files\Ultima Online"; - */ - private static string CustomPath = null; + public class DataPath + { + /* If you have not installed Ultima Online, + * or wish the server to use a separate set of datafiles, + * change the 'CustomPath' value. + * Example: + * private static string CustomPath = @"C:\Program Files\Ultima Online"; + */ + private static string CustomPath = null; - /* The following is a list of files which a required for proper execution: - * - * Multi.idx - * Multi.mul - * VerData.mul - * TileData.mul - * Map*.mul or Map*LegacyMUL.uop - * StaIdx*.mul - * Statics*.mul - * MapDif*.mul - * MapDifL*.mul - * StaDif*.mul - * StaDifL*.mul - * StaDifI*.mul - */ + /* The following is a list of files which a required for proper execution: + * + * Multi.idx + * Multi.mul + * VerData.mul + * TileData.mul + * Map*.mul or Map*LegacyMUL.uop + * StaIdx*.mul + * Statics*.mul + * MapDif*.mul + * MapDifL*.mul + * StaDif*.mul + * StaDifL*.mul + * StaDifI*.mul + */ - public static void Configure() - { - string pathUO = GetPath( @"Origin Worlds Online\Ultima Online\1.0", "ExePath" ); - string pathTD = GetPath( @"Origin Worlds Online\Ultima Online Third Dawn\1.0", "ExePath" ); //These refer to 2D & 3D, not the Third Dawn expansion - string pathKR = GetPath( @"Origin Worlds Online\Ultima Online\KR Legacy Beta", "ExePath" ); //After KR, This is the new registry key for the 2D client - string pathSA = GetPath( @"Electronic Arts\EA Games\Ultima Online Stygian Abyss Classic", "InstallDir" ); - string pathHS = GetPath( @"Electronic Arts\EA Games\Ultima Online Classic", "InstallDir" ); + public static void Configure() + { + string pathUO = GetPath(@"Origin Worlds Online\Ultima Online\1.0", "ExePath"); + string pathTD = GetPath(@"Origin Worlds Online\Ultima Online Third Dawn\1.0", + "ExePath"); //These refer to 2D & 3D, not the Third Dawn expansion + string pathKR = GetPath(@"Origin Worlds Online\Ultima Online\KR Legacy Beta", + "ExePath"); //After KR, This is the new registry key for the 2D client + string pathSA = GetPath(@"Electronic Arts\EA Games\Ultima Online Stygian Abyss Classic", "InstallDir"); + string pathHS = GetPath(@"Electronic Arts\EA Games\Ultima Online Classic", "InstallDir"); - if ( CustomPath != null ) - Core.DataDirectories.Add( CustomPath ); + if (CustomPath != null) + Core.DataDirectories.Add(CustomPath); - if ( pathUO != null ) - Core.DataDirectories.Add( pathUO ); + if (pathUO != null) + Core.DataDirectories.Add(pathUO); - if ( pathTD != null ) - Core.DataDirectories.Add( pathTD ); + if (pathTD != null) + Core.DataDirectories.Add(pathTD); - if ( pathKR != null ) - Core.DataDirectories.Add( pathKR ); + if (pathKR != null) + Core.DataDirectories.Add(pathKR); - if ( pathSA != null ) - Core.DataDirectories.Add( pathSA ); + if (pathSA != null) + Core.DataDirectories.Add(pathSA); - if ( pathHS != null ) - Core.DataDirectories.Add( pathHS ); + if (pathHS != null) + Core.DataDirectories.Add(pathHS); - if ( Core.DataDirectories.Count == 0 && !Core.Service ) - { - Console.WriteLine( "Enter the Ultima Online directory:" ); - Console.Write( "> " ); + if (Core.DataDirectories.Count == 0 && !Core.Service) + { + Console.WriteLine("Enter the Ultima Online directory:"); + Console.Write("> "); - Core.DataDirectories.Add( Console.ReadLine() ); - } - } + Core.DataDirectories.Add(Console.ReadLine()); + } + } - private static string GetPath( string subName, string keyName ) - { - try - { - string keyString; + private static string GetPath(string subName, string keyName) + { + try + { + string keyString; - if ( Core.Is64Bit ) - keyString = @"SOFTWARE\Wow6432Node\{0}"; - else - keyString = @"SOFTWARE\{0}"; + if (Core.Is64Bit) + keyString = @"SOFTWARE\Wow6432Node\{0}"; + else + keyString = @"SOFTWARE\{0}"; - using( RegistryKey key = Registry.LocalMachine.OpenSubKey( string.Format( keyString, subName ) ) ) - { - if ( key == null ) - return null; + using (RegistryKey key = Registry.LocalMachine.OpenSubKey(string.Format(keyString, subName))) + { + if (key == null) + return null; - string v = key.GetValue( keyName ) as string; + string v = key.GetValue(keyName) as string; - if ( string.IsNullOrEmpty( v ) ) - return null; + if (string.IsNullOrEmpty(v)) + return null; - if ( keyName == "InstallDir" ) - v = v + @"\"; + if (keyName == "InstallDir") + v = v + @"\"; - v = Path.GetDirectoryName( v ); + v = Path.GetDirectoryName(v); - if ( string.IsNullOrEmpty( v ) ) - return null; + if (string.IsNullOrEmpty(v)) + return null; - return v; - } - } - catch - { - return null; - } - } - } -} + return v; + } + } + catch + { + return null; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/DispellableAttribute.cs b/Scripts/Misc/DispellableAttribute.cs index 262621608..a9526c282 100644 --- a/Scripts/Misc/DispellableAttribute.cs +++ b/Scripts/Misc/DispellableAttribute.cs @@ -2,8 +2,8 @@ using System; namespace Server.Misc { - [AttributeUsage( AttributeTargets.Class )] - public class DispellableAttribute : Attribute - { - } + [AttributeUsage(AttributeTargets.Class)] + public class DispellableAttribute : Attribute + { + } } \ No newline at end of file diff --git a/Scripts/Misc/DispellableFieldAttribute.cs b/Scripts/Misc/DispellableFieldAttribute.cs index 688eb4eee..896c8d8e4 100644 --- a/Scripts/Misc/DispellableFieldAttribute.cs +++ b/Scripts/Misc/DispellableFieldAttribute.cs @@ -2,8 +2,8 @@ using System; namespace Server.Misc { - [AttributeUsage( AttributeTargets.Class )] - public class DispellableFieldAttribute : Attribute - { - } + [AttributeUsage(AttributeTargets.Class)] + public class DispellableFieldAttribute : Attribute + { + } } \ No newline at end of file diff --git a/Scripts/Misc/DoorGenerator.cs b/Scripts/Misc/DoorGenerator.cs index 3d96c1742..a0cf69ea4 100644 --- a/Scripts/Misc/DoorGenerator.cs +++ b/Scripts/Misc/DoorGenerator.cs @@ -1,551 +1,558 @@ -using Server.Items; using Server.Commands; +using Server.Items; +using Server.Network; namespace Server { - public class DoorGenerator - { - private static Rectangle2D[] m_BritRegions = { - new Rectangle2D( new Point2D( 250, 750 ), new Point2D( 775, 1330 ) ), - new Rectangle2D( new Point2D( 525, 2095 ), new Point2D( 925, 2430 ) ), - new Rectangle2D( new Point2D( 1025, 2155 ), new Point2D( 1265, 2310 ) ), - new Rectangle2D( new Point2D( 1635, 2430 ), new Point2D( 1705, 2508 ) ), - new Rectangle2D( new Point2D( 1775, 2605 ), new Point2D( 2165, 2975 ) ), - new Rectangle2D( new Point2D( 1055, 3520 ), new Point2D( 1570, 4075 ) ), - new Rectangle2D( new Point2D( 2860, 3310 ), new Point2D( 3120, 3630 ) ), - new Rectangle2D( new Point2D( 2470, 1855 ), new Point2D( 3950, 3045 ) ), - new Rectangle2D( new Point2D( 3425, 990 ), new Point2D( 3900, 1455 ) ), - new Rectangle2D( new Point2D( 4175, 735 ), new Point2D( 4840, 1600 ) ), - new Rectangle2D( new Point2D( 2375, 330 ), new Point2D( 3100, 1045 ) ), - new Rectangle2D( new Point2D( 2100, 1090 ), new Point2D( 2310, 1450 ) ), - new Rectangle2D( new Point2D( 1495, 1400 ), new Point2D( 1550, 1475 ) ), - new Rectangle2D( new Point2D( 1085, 1520 ), new Point2D( 1415, 1910 ) ), - new Rectangle2D( new Point2D( 1410, 1500 ), new Point2D( 1745, 1795 ) ), - new Rectangle2D( new Point2D( 5120, 2300 ), new Point2D( 6143, 4095 ) ) - }; + public class DoorGenerator + { + private static Rectangle2D[] m_BritRegions = + { + new Rectangle2D(new Point2D(250, 750), new Point2D(775, 1330)), + new Rectangle2D(new Point2D(525, 2095), new Point2D(925, 2430)), + new Rectangle2D(new Point2D(1025, 2155), new Point2D(1265, 2310)), + new Rectangle2D(new Point2D(1635, 2430), new Point2D(1705, 2508)), + new Rectangle2D(new Point2D(1775, 2605), new Point2D(2165, 2975)), + new Rectangle2D(new Point2D(1055, 3520), new Point2D(1570, 4075)), + new Rectangle2D(new Point2D(2860, 3310), new Point2D(3120, 3630)), + new Rectangle2D(new Point2D(2470, 1855), new Point2D(3950, 3045)), + new Rectangle2D(new Point2D(3425, 990), new Point2D(3900, 1455)), + new Rectangle2D(new Point2D(4175, 735), new Point2D(4840, 1600)), + new Rectangle2D(new Point2D(2375, 330), new Point2D(3100, 1045)), + new Rectangle2D(new Point2D(2100, 1090), new Point2D(2310, 1450)), + new Rectangle2D(new Point2D(1495, 1400), new Point2D(1550, 1475)), + new Rectangle2D(new Point2D(1085, 1520), new Point2D(1415, 1910)), + new Rectangle2D(new Point2D(1410, 1500), new Point2D(1745, 1795)), + new Rectangle2D(new Point2D(5120, 2300), new Point2D(6143, 4095)) + }; - private static Rectangle2D[] m_IlshRegions = { - new Rectangle2D( new Point2D( 0, 0 ), new Point2D( 288*8, 200*8 ) ) - }; + private static Rectangle2D[] m_IlshRegions = + { + new Rectangle2D(new Point2D(0, 0), new Point2D(288 * 8, 200 * 8)) + }; - private static Rectangle2D[] m_MalasRegions = { - new Rectangle2D( new Point2D( 0, 0 ), new Point2D( 320*8, 256*8 ) ) - }; + private static Rectangle2D[] m_MalasRegions = + { + new Rectangle2D(new Point2D(0, 0), new Point2D(320 * 8, 256 * 8)) + }; - private static int[] m_SouthFrames = { - 0x0006, - 0x0008, - 0x000B, - 0x001A, - 0x001B, - 0x001F, - 0x0038, - 0x0057, - 0x0059, - 0x005B, - 0x005D, - 0x0080, - 0x0081, - 0x0082, - 0x0084, - 0x0090, - 0x0091, - 0x0094, - 0x0096, - 0x0099, - 0x00A6, - 0x00A7, - 0x00AA, - 0x00AE, - 0x00B0, - 0x00B3, - 0x00C7, - 0x00C9, - 0x00F8, - 0x00FA, - 0x00FD, - 0x00FE, - 0x0100, - 0x0103, - 0x0104, - 0x0106, - 0x0109, - 0x0127, - 0x0129, - 0x012B, - 0x012D, - 0x012F, - 0x0131, - 0x0132, - 0x0134, - 0x0135, - 0x0137, - 0x0139, - 0x013B, - 0x014C, - 0x014E, - 0x014F, - 0x0151, - 0x0153, - 0x0155, - 0x0157, - 0x0158, - 0x015A, - 0x015D, - 0x015E, - 0x015F, - 0x0162, - 0x01CF, - 0x01D1, - 0x01D4, - 0x01FF, - 0x0204, - 0x0206, - 0x0208, - 0x020A - }; + private static int[] m_SouthFrames = + { + 0x0006, + 0x0008, + 0x000B, + 0x001A, + 0x001B, + 0x001F, + 0x0038, + 0x0057, + 0x0059, + 0x005B, + 0x005D, + 0x0080, + 0x0081, + 0x0082, + 0x0084, + 0x0090, + 0x0091, + 0x0094, + 0x0096, + 0x0099, + 0x00A6, + 0x00A7, + 0x00AA, + 0x00AE, + 0x00B0, + 0x00B3, + 0x00C7, + 0x00C9, + 0x00F8, + 0x00FA, + 0x00FD, + 0x00FE, + 0x0100, + 0x0103, + 0x0104, + 0x0106, + 0x0109, + 0x0127, + 0x0129, + 0x012B, + 0x012D, + 0x012F, + 0x0131, + 0x0132, + 0x0134, + 0x0135, + 0x0137, + 0x0139, + 0x013B, + 0x014C, + 0x014E, + 0x014F, + 0x0151, + 0x0153, + 0x0155, + 0x0157, + 0x0158, + 0x015A, + 0x015D, + 0x015E, + 0x015F, + 0x0162, + 0x01CF, + 0x01D1, + 0x01D4, + 0x01FF, + 0x0204, + 0x0206, + 0x0208, + 0x020A + }; - private static int[] m_NorthFrames = { - 0x0006, - 0x0008, - 0x000D, - 0x001A, - 0x001B, - 0x0020, - 0x003A, - 0x0057, - 0x0059, - 0x005B, - 0x005D, - 0x0080, - 0x0081, - 0x0082, - 0x0084, - 0x0090, - 0x0091, - 0x0094, - 0x0096, - 0x0099, - 0x00A6, - 0x00A7, - 0x00AC, - 0x00AE, - 0x00B0, - 0x00C7, - 0x00C9, - 0x00F8, - 0x00FA, - 0x00FD, - 0x00FE, - 0x0100, - 0x0103, - 0x0104, - 0x0106, - 0x0109, - 0x0127, - 0x0129, - 0x012B, - 0x012D, - 0x012F, - 0x0131, - 0x0132, - 0x0134, - 0x0135, - 0x0137, - 0x0139, - 0x013B, - 0x014C, - 0x014E, - 0x014F, - 0x0151, - 0x0153, - 0x0155, - 0x0157, - 0x0158, - 0x015A, - 0x015D, - 0x015E, - 0x015F, - 0x0162, - 0x01CF, - 0x01D1, - 0x01D4, - 0x01FF, - 0x0201, - 0x0204, - 0x0208, - 0x020A - }; + private static int[] m_NorthFrames = + { + 0x0006, + 0x0008, + 0x000D, + 0x001A, + 0x001B, + 0x0020, + 0x003A, + 0x0057, + 0x0059, + 0x005B, + 0x005D, + 0x0080, + 0x0081, + 0x0082, + 0x0084, + 0x0090, + 0x0091, + 0x0094, + 0x0096, + 0x0099, + 0x00A6, + 0x00A7, + 0x00AC, + 0x00AE, + 0x00B0, + 0x00C7, + 0x00C9, + 0x00F8, + 0x00FA, + 0x00FD, + 0x00FE, + 0x0100, + 0x0103, + 0x0104, + 0x0106, + 0x0109, + 0x0127, + 0x0129, + 0x012B, + 0x012D, + 0x012F, + 0x0131, + 0x0132, + 0x0134, + 0x0135, + 0x0137, + 0x0139, + 0x013B, + 0x014C, + 0x014E, + 0x014F, + 0x0151, + 0x0153, + 0x0155, + 0x0157, + 0x0158, + 0x015A, + 0x015D, + 0x015E, + 0x015F, + 0x0162, + 0x01CF, + 0x01D1, + 0x01D4, + 0x01FF, + 0x0201, + 0x0204, + 0x0208, + 0x020A + }; - private static int[] m_EastFrames = { - 0x0007, - 0x000A, - 0x001A, - 0x001C, - 0x001E, - 0x0037, - 0x0058, - 0x0059, - 0x005C, - 0x005E, - 0x0080, - 0x0081, - 0x0082, - 0x0084, - 0x0090, - 0x0092, - 0x0095, - 0x0097, - 0x0098, - 0x00A6, - 0x00A8, - 0x00AB, - 0x00AE, - 0x00AF, - 0x00B2, - 0x00C7, - 0x00C8, - 0x00EA, - 0x00F8, - 0x00F9, - 0x00FC, - 0x00FE, - 0x00FF, - 0x0102, - 0x0104, - 0x0105, - 0x0108, - 0x0127, - 0x0128, - 0x012B, - 0x012C, - 0x012E, - 0x0130, - 0x0132, - 0x0133, - 0x0135, - 0x0136, - 0x0138, - 0x013A, - 0x014C, - 0x014D, - 0x014F, - 0x0150, - 0x0152, - 0x0154, - 0x0156, - 0x0158, - 0x0159, - 0x015C, - 0x015E, - 0x0160, - 0x0163, - 0x01CF, - 0x01D0, - 0x01D3, - 0x01FF, - 0x0203, - 0x0205, - 0x0207, - 0x0209 - }; + private static int[] m_EastFrames = + { + 0x0007, + 0x000A, + 0x001A, + 0x001C, + 0x001E, + 0x0037, + 0x0058, + 0x0059, + 0x005C, + 0x005E, + 0x0080, + 0x0081, + 0x0082, + 0x0084, + 0x0090, + 0x0092, + 0x0095, + 0x0097, + 0x0098, + 0x00A6, + 0x00A8, + 0x00AB, + 0x00AE, + 0x00AF, + 0x00B2, + 0x00C7, + 0x00C8, + 0x00EA, + 0x00F8, + 0x00F9, + 0x00FC, + 0x00FE, + 0x00FF, + 0x0102, + 0x0104, + 0x0105, + 0x0108, + 0x0127, + 0x0128, + 0x012B, + 0x012C, + 0x012E, + 0x0130, + 0x0132, + 0x0133, + 0x0135, + 0x0136, + 0x0138, + 0x013A, + 0x014C, + 0x014D, + 0x014F, + 0x0150, + 0x0152, + 0x0154, + 0x0156, + 0x0158, + 0x0159, + 0x015C, + 0x015E, + 0x0160, + 0x0163, + 0x01CF, + 0x01D0, + 0x01D3, + 0x01FF, + 0x0203, + 0x0205, + 0x0207, + 0x0209 + }; - private static int[] m_WestFrames = { - 0x0007, - 0x000C, - 0x001A, - 0x001C, - 0x0021, - 0x0039, - 0x0058, - 0x0059, - 0x005C, - 0x005E, - 0x0080, - 0x0081, - 0x0082, - 0x0084, - 0x0090, - 0x0092, - 0x0095, - 0x0097, - 0x0098, - 0x00A6, - 0x00A8, - 0x00AD, - 0x00AE, - 0x00AF, - 0x00B5, - 0x00C7, - 0x00C8, - 0x00EA, - 0x00F8, - 0x00F9, - 0x00FC, - 0x00FE, - 0x00FF, - 0x0102, - 0x0104, - 0x0105, - 0x0108, - 0x0127, - 0x0128, - 0x012C, - 0x012E, - 0x0130, - 0x0132, - 0x0133, - 0x0135, - 0x0136, - 0x0138, - 0x013A, - 0x014C, - 0x014D, - 0x014F, - 0x0150, - 0x0152, - 0x0154, - 0x0156, - 0x0158, - 0x0159, - 0x015C, - 0x015E, - 0x0160, - 0x0163, - 0x01CF, - 0x01D0, - 0x01D3, - 0x01FF, - 0x0200, - 0x0203, - 0x0207, - 0x0209 - }; + private static int[] m_WestFrames = + { + 0x0007, + 0x000C, + 0x001A, + 0x001C, + 0x0021, + 0x0039, + 0x0058, + 0x0059, + 0x005C, + 0x005E, + 0x0080, + 0x0081, + 0x0082, + 0x0084, + 0x0090, + 0x0092, + 0x0095, + 0x0097, + 0x0098, + 0x00A6, + 0x00A8, + 0x00AD, + 0x00AE, + 0x00AF, + 0x00B5, + 0x00C7, + 0x00C8, + 0x00EA, + 0x00F8, + 0x00F9, + 0x00FC, + 0x00FE, + 0x00FF, + 0x0102, + 0x0104, + 0x0105, + 0x0108, + 0x0127, + 0x0128, + 0x012C, + 0x012E, + 0x0130, + 0x0132, + 0x0133, + 0x0135, + 0x0136, + 0x0138, + 0x013A, + 0x014C, + 0x014D, + 0x014F, + 0x0150, + 0x0152, + 0x0154, + 0x0156, + 0x0158, + 0x0159, + 0x015C, + 0x015E, + 0x0160, + 0x0163, + 0x01CF, + 0x01D0, + 0x01D3, + 0x01FF, + 0x0200, + 0x0203, + 0x0207, + 0x0209 + }; - public static void Initialize() - { - CommandSystem.Register( "DoorGen", AccessLevel.Administrator, DoorGen_OnCommand ); - } + private static Map m_Map; + private static int m_Count; - [Usage( "DoorGen" )] - [Description( "Generates doors by analyzing the map. Slow." )] - public static void DoorGen_OnCommand( CommandEventArgs e ) - { - Generate(); - } + public static void Initialize() + { + CommandSystem.Register("DoorGen", AccessLevel.Administrator, DoorGen_OnCommand); + } - private static Map m_Map; - private static int m_Count; + [Usage("DoorGen")] + [Description("Generates doors by analyzing the map. Slow.")] + public static void DoorGen_OnCommand(CommandEventArgs e) + { + Generate(); + } - public static void Generate() - { - World.Broadcast( 0x35, true, "Generating doors, please wait." ); + public static void Generate() + { + World.Broadcast(0x35, true, "Generating doors, please wait."); - Network.NetState.FlushAll(); - Network.NetState.Pause(); + NetState.FlushAll(); + NetState.Pause(); - m_Map = Map.Trammel; - m_Count = 0; + m_Map = Map.Trammel; + m_Count = 0; - for ( int i = 0; i < m_BritRegions.Length; ++i ) - Generate( m_BritRegions[i] ); + for (int i = 0; i < m_BritRegions.Length; ++i) + Generate(m_BritRegions[i]); - int trammelCount = m_Count; + int trammelCount = m_Count; - m_Map = Map.Felucca; - m_Count = 0; + m_Map = Map.Felucca; + m_Count = 0; - for ( int i = 0; i < m_BritRegions.Length; ++i ) - Generate( m_BritRegions[i] ); + for (int i = 0; i < m_BritRegions.Length; ++i) + Generate(m_BritRegions[i]); - int feluccaCount = m_Count; + int feluccaCount = m_Count; - m_Map = Map.Ilshenar; - m_Count = 0; + m_Map = Map.Ilshenar; + m_Count = 0; - for ( int i = 0; i < m_IlshRegions.Length; ++i ) - Generate( m_IlshRegions[i] ); + for (int i = 0; i < m_IlshRegions.Length; ++i) + Generate(m_IlshRegions[i]); - int ilshenarCount = m_Count; + int ilshenarCount = m_Count; - m_Map = Map.Malas; - m_Count = 0; + m_Map = Map.Malas; + m_Count = 0; - for ( int i = 0; i < m_MalasRegions.Length; ++i ) - Generate( m_MalasRegions[i] ); + for (int i = 0; i < m_MalasRegions.Length; ++i) + Generate(m_MalasRegions[i]); - int malasCount = m_Count; + int malasCount = m_Count; - Network.NetState.Resume(); + NetState.Resume(); - World.Broadcast( 0x35, true, "Door generation complete. Trammel: {0}; Felucca: {1}; Ilshenar: {2}; Malas: {3};", trammelCount, feluccaCount, ilshenarCount, malasCount ); - } + World.Broadcast(0x35, true, "Door generation complete. Trammel: {0}; Felucca: {1}; Ilshenar: {2}; Malas: {3};", + trammelCount, feluccaCount, ilshenarCount, malasCount); + } - public static bool IsFrame( int id, int[] list ) - { - if ( id > list[list.Length - 1] ) - return false; + public static bool IsFrame(int id, int[] list) + { + if (id > list[list.Length - 1]) + return false; - for ( int i = 0; i < list.Length; ++i ) - { - int delta = id - list[i]; + for (int i = 0; i < list.Length; ++i) + { + int delta = id - list[i]; - if ( delta < 0 ) - return false; - if ( delta == 0 ) - return true; - } + if (delta < 0) + return false; + if (delta == 0) + return true; + } - return false; - } + return false; + } - public static bool IsNorthFrame( int id ) - { - return IsFrame( id, m_NorthFrames ); - } + public static bool IsNorthFrame(int id) + { + return IsFrame(id, m_NorthFrames); + } - public static bool IsSouthFrame( int id ) - { - return IsFrame( id, m_SouthFrames ); - } + public static bool IsSouthFrame(int id) + { + return IsFrame(id, m_SouthFrames); + } - public static bool IsWestFrame( int id ) - { - return IsFrame( id, m_WestFrames ); - } + public static bool IsWestFrame(int id) + { + return IsFrame(id, m_WestFrames); + } - public static bool IsEastFrame( int id ) - { - return IsFrame( id, m_EastFrames ); - } + public static bool IsEastFrame(int id) + { + return IsFrame(id, m_EastFrames); + } - public static bool IsEastFrame( int x, int y, int z ) - { - StaticTile[] tiles = m_Map.Tiles.GetStaticTiles( x, y ); + public static bool IsEastFrame(int x, int y, int z) + { + StaticTile[] tiles = m_Map.Tiles.GetStaticTiles(x, y); - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; - if ( tile.Z == z && IsEastFrame( tile.ID ) ) - return true; - } + if (tile.Z == z && IsEastFrame(tile.ID)) + return true; + } - return false; - } + return false; + } - public static bool IsSouthFrame( int x, int y, int z ) - { - StaticTile[] tiles = m_Map.Tiles.GetStaticTiles( x, y ); + public static bool IsSouthFrame(int x, int y, int z) + { + StaticTile[] tiles = m_Map.Tiles.GetStaticTiles(x, y); - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; - if ( tile.Z == z && IsSouthFrame( tile.ID ) ) - return true; - } + if (tile.Z == z && IsSouthFrame(tile.ID)) + return true; + } - return false; - } + return false; + } - public static BaseDoor AddDoor( int x, int y, int z, DoorFacing facing ) - { - int doorZ = z; - int doorTop = doorZ + 20; + public static BaseDoor AddDoor(int x, int y, int z, DoorFacing facing) + { + int doorZ = z; + int doorTop = doorZ + 20; - if ( !m_Map.CanFit( x, y, z, 16, false, false ) ) - return null; + if (!m_Map.CanFit(x, y, z, 16, false, false)) + return null; - if ( y == 1743 && x >= 1343 && x <= 1344 ) - return null; + if (y == 1743 && x >= 1343 && x <= 1344) + return null; - if ( y == 1679 && x >= 1392 && x <= 1393 ) - return null; + if (y == 1679 && x >= 1392 && x <= 1393) + return null; - if ( x == 1320 && y >= 1618 && y <= 1640 ) - return null; + if (x == 1320 && y >= 1618 && y <= 1640) + return null; - if ( x == 1383 && y >= 1642 && y <= 1643 ) - return null; + if (x == 1383 && y >= 1642 && y <= 1643) + return null; - BaseDoor door = new DarkWoodDoor( facing ); - door.MoveToWorld( new Point3D( x, y, z ), m_Map ); + BaseDoor door = new DarkWoodDoor(facing); + door.MoveToWorld(new Point3D(x, y, z), m_Map); - ++m_Count; + ++m_Count; - return door; - } + return door; + } - public static void Generate( Rectangle2D region ) - { - for ( int rx = 0; rx < region.Width; ++rx ) - { - for ( int ry = 0; ry < region.Height; ++ry ) - { - int vx = rx + region.X; - int vy = ry + region.Y; + public static void Generate(Rectangle2D region) + { + for (int rx = 0; rx < region.Width; ++rx) + for (int ry = 0; ry < region.Height; ++ry) + { + int vx = rx + region.X; + int vy = ry + region.Y; - StaticTile[] tiles = m_Map.Tiles.GetStaticTiles( vx, vy ); + StaticTile[] tiles = m_Map.Tiles.GetStaticTiles(vx, vy); - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; - int id = tile.ID; - int z = tile.Z; + int id = tile.ID; + int z = tile.Z; - if ( IsWestFrame( id ) ) - { - if ( IsEastFrame( vx + 2, vy, z ) ) - { - AddDoor( vx + 1, vy, z, DoorFacing.WestCW ); - } - else if ( IsEastFrame( vx + 3, vy, z ) ) - { - BaseDoor first = AddDoor( vx + 1, vy, z, DoorFacing.WestCW ); - BaseDoor second = AddDoor( vx + 2, vy, z, DoorFacing.EastCCW ); + if (IsWestFrame(id)) + { + if (IsEastFrame(vx + 2, vy, z)) + { + AddDoor(vx + 1, vy, z, DoorFacing.WestCW); + } + else if (IsEastFrame(vx + 3, vy, z)) + { + BaseDoor first = AddDoor(vx + 1, vy, z, DoorFacing.WestCW); + BaseDoor second = AddDoor(vx + 2, vy, z, DoorFacing.EastCCW); - if ( first != null && second != null ) - { - first.Link = second; - second.Link = first; - } - else - { - first?.Delete(); + if (first != null && second != null) + { + first.Link = second; + second.Link = first; + } + else + { + first?.Delete(); - second?.Delete(); - } - } - } - else if ( IsNorthFrame( id ) ) - { - if ( IsSouthFrame( vx, vy + 2, z ) ) - { - AddDoor( vx, vy + 1, z, DoorFacing.SouthCW ); - } - else if ( IsSouthFrame( vx, vy + 3, z ) ) - { - BaseDoor first = AddDoor( vx, vy + 1, z, DoorFacing.NorthCCW ); - BaseDoor second = AddDoor( vx, vy + 2, z, DoorFacing.SouthCW ); + second?.Delete(); + } + } + } + else if (IsNorthFrame(id)) + { + if (IsSouthFrame(vx, vy + 2, z)) + { + AddDoor(vx, vy + 1, z, DoorFacing.SouthCW); + } + else if (IsSouthFrame(vx, vy + 3, z)) + { + BaseDoor first = AddDoor(vx, vy + 1, z, DoorFacing.NorthCCW); + BaseDoor second = AddDoor(vx, vy + 2, z, DoorFacing.SouthCW); - if ( first != null && second != null ) - { - first.Link = second; - second.Link = first; - } - else - { - first?.Delete(); + if (first != null && second != null) + { + first.Link = second; + second.Link = first; + } + else + { + first?.Delete(); - second?.Delete(); - } - } - } - } - } - } - } - } + second?.Delete(); + } + } + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Email.cs b/Scripts/Misc/Email.cs index 2ab8f6e8c..43d1d99c9 100644 --- a/Scripts/Misc/Email.cs +++ b/Scripts/Misc/Email.cs @@ -1,98 +1,98 @@ using System; +using System.Net; using System.Net.Mail; using System.Text.RegularExpressions; using System.Threading; namespace Server.Misc { - public class Email - { - /* In order to support emailing, fill in EmailServer and FromAddress: - * Example: - * public static readonly string EmailServer = "mail.domain.com"; - * public static readonly string FromAddress = "runuo@domain.com"; - * - * If you want to add crash reporting emailing, fill in CrashAddresses: - * Example: - * public static readonly string CrashAddresses = "first@email.here,second@email.here,third@email.here"; - * - * If you want to add speech log page emailing, fill in SpeechLogPageAddresses: - * Example: - * public static readonly string SpeechLogPageAddresses = "first@email.here,second@email.here,third@email.here"; - */ + public class Email + { + /* In order to support emailing, fill in EmailServer and FromAddress: + * Example: + * public static readonly string EmailServer = "mail.domain.com"; + * public static readonly string FromAddress = "runuo@domain.com"; + * + * If you want to add crash reporting emailing, fill in CrashAddresses: + * Example: + * public static readonly string CrashAddresses = "first@email.here,second@email.here,third@email.here"; + * + * If you want to add speech log page emailing, fill in SpeechLogPageAddresses: + * Example: + * public static readonly string SpeechLogPageAddresses = "first@email.here,second@email.here,third@email.here"; + */ - public static readonly string EmailServer = null; - public static readonly int EmailPort = 25; + public static readonly string EmailServer = null; + public static readonly int EmailPort = 25; - public static readonly string FromAddress = null; - public static readonly string EmailUsername = null; - public static readonly string EmailPassword = null; + public static readonly string FromAddress = null; + public static readonly string EmailUsername = null; + public static readonly string EmailPassword = null; - public static readonly string CrashAddresses = null; - public static readonly string SpeechLogPageAddresses = null; + public static readonly string CrashAddresses = null; + public static readonly string SpeechLogPageAddresses = null; - private static Regex _pattern = new Regex( @"^[a-z0-9.+_-]+@([a-z0-9-]+\.)+[a-z]+$", RegexOptions.Compiled | RegexOptions.IgnoreCase ); + private static Regex _pattern = new Regex(@"^[a-z0-9.+_-]+@([a-z0-9-]+\.)+[a-z]+$", + RegexOptions.Compiled | RegexOptions.IgnoreCase); - public static bool IsValid( string address ) - { - if ( address == null || address.Length > 320 ) - return false; + private static SmtpClient _Client; - return _pattern.IsMatch( address ); - } + public static bool IsValid(string address) + { + if (address == null || address.Length > 320) + return false; - private static SmtpClient _Client; + return _pattern.IsMatch(address); + } - public static void Configure() - { - if ( EmailServer != null ) - { - _Client = new SmtpClient( EmailServer, EmailPort ); - if ( EmailUsername != null ) - { - _Client.Credentials = new System.Net.NetworkCredential( EmailUsername, EmailPassword ); - } - } - } + public static void Configure() + { + if (EmailServer != null) + { + _Client = new SmtpClient(EmailServer, EmailPort); + if (EmailUsername != null) _Client.Credentials = new NetworkCredential(EmailUsername, EmailPassword); + } + } - public static bool Send( MailMessage message ) - { - try - { - // .NET relies on the MTA to generate Message-ID header. Not all MTAs will add this header. + public static bool Send(MailMessage message) + { + try + { + // .NET relies on the MTA to generate Message-ID header. Not all MTAs will add this header. - DateTime now = DateTime.UtcNow; - string messageID = $"<{now.ToString("yyyyMMdd")}.{now.ToString("HHmmssff")}@{EmailServer}>"; - message.Headers.Add("Message-ID", messageID ); + DateTime now = DateTime.UtcNow; + string messageID = $"<{now.ToString("yyyyMMdd")}.{now.ToString("HHmmssff")}@{EmailServer}>"; + message.Headers.Add("Message-ID", messageID); - message.Headers.Add("X-Mailer", "RunUO"); + message.Headers.Add("X-Mailer", "RunUO"); - lock ( _Client ) { - _Client.Send( message ); - } - } - catch - { - return false; - } + lock (_Client) + { + _Client.Send(message); + } + } + catch + { + return false; + } - return true; - } + return true; + } - public static void AsyncSend( MailMessage message ) - { - ThreadPool.QueueUserWorkItem( SendCallback, message ); - } + public static void AsyncSend(MailMessage message) + { + ThreadPool.QueueUserWorkItem(SendCallback, message); + } - private static void SendCallback( object state ) - { - MailMessage message = (MailMessage) state; + private static void SendCallback(object state) + { + MailMessage message = (MailMessage)state; - if ( Send( message ) ) - Console.WriteLine( "Sent e-mail '{0}' to '{1}'.", message.Subject, message.To ); - else - Console.WriteLine( "Failure sending e-mail '{0}' to '{1}'.", message.Subject, message.To ); - } - } -} + if (Send(message)) + Console.WriteLine("Sent e-mail '{0}' to '{1}'.", message.Subject, message.To); + else + Console.WriteLine("Failure sending e-mail '{0}' to '{1}'.", message.Subject, message.To); + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Fastwalk.cs b/Scripts/Misc/Fastwalk.cs index d6928e9fc..232986b7a 100644 --- a/Scripts/Misc/Fastwalk.cs +++ b/Scripts/Misc/Fastwalk.cs @@ -2,30 +2,32 @@ using System; namespace Server.Misc { - // This fastwalk detection is no longer required - // As of B36 PlayerMobile implements movement packet throttling which more reliably controls movement speeds - public class Fastwalk - { - private static int MaxSteps = 4; // Maximum number of queued steps until fastwalk is detected - private static bool Enabled = false; // Is fastwalk detection enabled? - private static bool UOTDOverride = false; // Should UO:TD clients not be checked for fastwalk? - private static AccessLevel AccessOverride = AccessLevel.GameMaster; // Anyone with this or higher access level is not checked for fastwalk + // This fastwalk detection is no longer required + // As of B36 PlayerMobile implements movement packet throttling which more reliably controls movement speeds + public class Fastwalk + { + private static int MaxSteps = 4; // Maximum number of queued steps until fastwalk is detected + private static bool Enabled = false; // Is fastwalk detection enabled? + private static bool UOTDOverride = false; // Should UO:TD clients not be checked for fastwalk? - public static void Initialize() - { - Mobile.FwdMaxSteps = MaxSteps; - Mobile.FwdEnabled = Enabled; - Mobile.FwdUOTDOverride = UOTDOverride; - Mobile.FwdAccessOverride = AccessOverride; + private static AccessLevel + AccessOverride = AccessLevel.GameMaster; // Anyone with this or higher access level is not checked for fastwalk - if ( Enabled ) - EventSink.FastWalk += OnFastWalk; - } + public static void Initialize() + { + Mobile.FwdMaxSteps = MaxSteps; + Mobile.FwdEnabled = Enabled; + Mobile.FwdUOTDOverride = UOTDOverride; + Mobile.FwdAccessOverride = AccessOverride; - public static void OnFastWalk( FastWalkEventArgs e ) - { - e.Blocked = true;//disallow this fastwalk - Console.WriteLine( "Client: {0}: Fast movement detected (name={1})", e.NetState, e.NetState.Mobile.Name ); - } - } -} + if (Enabled) + EventSink.FastWalk += OnFastWalk; + } + + public static void OnFastWalk(FastWalkEventArgs e) + { + e.Blocked = true; //disallow this fastwalk + Console.WriteLine("Client: {0}: Fast movement detected (name={1})", e.NetState, e.NetState.Mobile.Name); + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/FoodDecay.cs b/Scripts/Misc/FoodDecay.cs index 59d8fef13..709141d29 100644 --- a/Scripts/Misc/FoodDecay.cs +++ b/Scripts/Misc/FoodDecay.cs @@ -3,42 +3,42 @@ using Server.Network; namespace Server.Misc { - public class FoodDecayTimer : Timer - { - public static void Initialize() - { - new FoodDecayTimer().Start(); - } + public class FoodDecayTimer : Timer + { + public FoodDecayTimer() : base(TimeSpan.FromMinutes(5), TimeSpan.FromMinutes(5)) + { + Priority = TimerPriority.OneMinute; + } - public FoodDecayTimer() : base( TimeSpan.FromMinutes( 5 ), TimeSpan.FromMinutes( 5 ) ) - { - Priority = TimerPriority.OneMinute; - } + public static void Initialize() + { + new FoodDecayTimer().Start(); + } - protected override void OnTick() - { - FoodDecay(); - } + protected override void OnTick() + { + FoodDecay(); + } - public static void FoodDecay() - { - foreach ( NetState state in NetState.Instances ) - { - HungerDecay( state.Mobile ); - ThirstDecay( state.Mobile ); - } - } + public static void FoodDecay() + { + foreach (NetState state in NetState.Instances) + { + HungerDecay(state.Mobile); + ThirstDecay(state.Mobile); + } + } - public static void HungerDecay( Mobile m ) - { - if ( m != null && m.Hunger >= 1 ) - m.Hunger -= 1; - } + public static void HungerDecay(Mobile m) + { + if (m != null && m.Hunger >= 1) + m.Hunger -= 1; + } - public static void ThirstDecay( Mobile m ) - { - if ( m != null && m.Thirst >= 1 ) - m.Thirst -= 1; - } - } + public static void ThirstDecay(Mobile m) + { + if (m != null && m.Thirst >= 1) + m.Thirst -= 1; + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Geometry.cs b/Scripts/Misc/Geometry.cs index faff955e0..f5374c516 100644 --- a/Scripts/Misc/Geometry.cs +++ b/Scripts/Misc/Geometry.cs @@ -2,220 +2,226 @@ using System; namespace Server.Misc { - public delegate void DoEffect_Callback( Point3D p, Map map ); - - public static class Geometry - { - public static void Swap( ref T a, ref T b ) - { - T temp = a; - a = b; - b = temp; - } - - public static double RadiansToDegrees( double angle ) - { - return angle * (180.0 / Math.PI); - } - - public static double DegreesToRadians( double angle ) - { - return angle * ( Math.PI / 180.0 ); - } - - public class CirclePoint - { - public Point2D Point { get; } + public delegate void DoEffect_Callback(Point3D p, Map map); - public int Angle { get; } + public static class Geometry + { + public static void Swap(ref T a, ref T b) + { + T temp = a; + a = b; + b = temp; + } - public int Quadrant { get; } + public static double RadiansToDegrees(double angle) + { + return angle * (180.0 / Math.PI); + } - public CirclePoint( Point2D point, int angle, int quadrant ) - { - this.Point = point; - this.Angle = angle; - this.Quadrant = quadrant; - } - } + public static double DegreesToRadians(double angle) + { + return angle * (Math.PI / 180.0); + } - public static Point2D ArcPoint( Point3D loc, int radius, int angle ) - { - int sideA, sideB; - - if ( angle < 0 ) - angle = 0; - - if ( angle > 90 ) - angle = 90; - - sideA = (int) Math.Round( radius * Math.Sin( DegreesToRadians( angle ) ) ); - sideB = (int) Math.Round( radius * Math.Cos( DegreesToRadians( angle ) ) ); - - return new Point2D( loc.X - sideB, loc.Y - sideA ); - } - - public static void Circle2D( Point3D loc, Map map, int radius, DoEffect_Callback effect ) - { - Circle2D( loc, map, radius, effect, 0, 360 ); - } - - public static void Circle2D( Point3D loc, Map map, int radius, DoEffect_Callback effect, int angleStart, int angleEnd ) - { - if ( angleStart < 0 || angleStart > 360 ) - angleStart = 0; - - if ( angleEnd > 360 || angleEnd < 0 ) - angleEnd = 360; - - if ( angleStart == angleEnd ) - return; + public static Point2D ArcPoint(Point3D loc, int radius, int angle) + { + int sideA, sideB; - bool opposite = angleStart > angleEnd; - - int startQuadrant = angleStart / 90; - int endQuadrant = angleEnd / 90; - - Point2D start = ArcPoint( loc, radius, angleStart % 90 ); - Point2D end = ArcPoint( loc, radius, angleEnd % 90 ); - - if ( opposite ) - { - Swap( ref start, ref end ); - Swap( ref startQuadrant, ref endQuadrant ); - } - - CirclePoint startPoint = new CirclePoint( start, angleStart, startQuadrant ); - CirclePoint endPoint = new CirclePoint( end, angleEnd, endQuadrant ); - - int error = -radius; - int x = radius; - int y = 0; - - while (x > y) - { - plot4points( loc, map, x, y, startPoint, endPoint, effect, opposite ); - plot4points( loc, map, y, x, startPoint, endPoint, effect, opposite ); - - error += ( y * 2 ) + 1; - ++y; - - if (error >= 0) - { - --x; - error -= x * 2; - } - } - - plot4points( loc, map, x, y, startPoint, endPoint, effect, opposite ); - } - - public static void plot4points( Point3D loc, Map map, int x, int y, CirclePoint start, CirclePoint end, DoEffect_Callback effect, bool opposite ) - { - Point2D pointA = new Point2D( loc.X - x, loc.Y - y ); - Point2D pointB = new Point2D( loc.X - y, loc.Y - x ); - - int quadrant = 2; - - if ( x == 0 && start.Quadrant == 3 ) - quadrant = 3; - - if ( WithinCircleBounds( quadrant == 3 ? pointB : pointA, quadrant, loc, start, end, opposite ) ) - effect( new Point3D( loc.X + x, loc.Y + y, loc.Z ), map ); - - quadrant = 3; - - if ( y == 0 && start.Quadrant == 0 ) - quadrant = 0; - - if ( x != 0 && WithinCircleBounds( quadrant == 0 ? pointA : pointB, quadrant, loc, start, end, opposite ) ) - effect( new Point3D( loc.X - x, loc.Y + y, loc.Z ), map ); - if ( y != 0 && WithinCircleBounds( pointB, 1, loc, start, end, opposite ) ) - effect( new Point3D( loc.X + x, loc.Y - y, loc.Z ), map ); - if ( x != 0 && y != 0 && WithinCircleBounds( pointA, 0, loc, start, end, opposite ) ) - effect( new Point3D( loc.X - x, loc.Y - y, loc.Z ), map ); - } - - public static bool WithinCircleBounds( Point2D pointLoc, int pointQuadrant, Point3D center, CirclePoint start, CirclePoint end, bool opposite ) - { - if ( start.Angle == 0 && end.Angle == 360 ) - return true; + if (angle < 0) + angle = 0; - int startX = start.Point.X; - int startY = start.Point.Y; - int endX = end.Point.X; - int endY = end.Point.Y; - - int x = pointLoc.X; - int y = pointLoc.Y; + if (angle > 90) + angle = 90; - if ( pointQuadrant < start.Quadrant || pointQuadrant > end.Quadrant ) - return opposite; - - if ( pointQuadrant > start.Quadrant && pointQuadrant < end.Quadrant ) - return !opposite; + sideA = (int)Math.Round(radius * Math.Sin(DegreesToRadians(angle))); + sideB = (int)Math.Round(radius * Math.Cos(DegreesToRadians(angle))); - bool withinBounds = true; - - if ( start.Quadrant == end.Quadrant ) - { - if ( startX == endX && ( x > startX || y > startY || y < endY ) ) - withinBounds = false; - else if ( startY == endY && ( y < startY || x < startX || x > endX ) ) - withinBounds = false; - else if ( x < startX || x > endX || y > startY || y < endY ) - withinBounds = false; - } - else if ( pointQuadrant == start.Quadrant && ( x < startX || y > startY ) ) - withinBounds = false; - else if ( pointQuadrant == end.Quadrant && ( x > endX || y < endY ) ) - withinBounds = false; - - return opposite ? !withinBounds : withinBounds; - } + return new Point2D(loc.X - sideB, loc.Y - sideA); + } - public static void Line2D( Point3D start, Point3D end, Map map, DoEffect_Callback effect ) - { - bool steep = Math.Abs( end.Y - start.Y ) > Math.Abs( end.X - start.X ); - - int x0 = start.X; - int x1 = end.X; - int y0 = start.Y; - int y1 = end.Y; - - if ( steep ) - { - Swap( ref x0, ref y0 ); - Swap( ref x1, ref y1 ); - } - - if ( x0 > x1 ) - { - Swap( ref x0, ref x1 ); - Swap( ref y0, ref y1 ); - } - - int deltax = x1 - x0; - int deltay = Math.Abs( y1 - y0 ); - int error = deltax / 2; - int ystep = y0 < y1 ? 1 : -1; - int y = y0; - - for ( int x = x0; x <= x1; x++ ) - { - if ( steep ) - effect( new Point3D( y, x, start.Z ), map ); - else - effect( new Point3D( x, y, start.Z ), map ); - - error -= deltay; - - if ( error < 0 ) - { - y += ystep; - error += deltax; - } - } - } - } -} + public static void Circle2D(Point3D loc, Map map, int radius, DoEffect_Callback effect) + { + Circle2D(loc, map, radius, effect, 0, 360); + } + + public static void Circle2D(Point3D loc, Map map, int radius, DoEffect_Callback effect, int angleStart, int angleEnd) + { + if (angleStart < 0 || angleStart > 360) + angleStart = 0; + + if (angleEnd > 360 || angleEnd < 0) + angleEnd = 360; + + if (angleStart == angleEnd) + return; + + bool opposite = angleStart > angleEnd; + + int startQuadrant = angleStart / 90; + int endQuadrant = angleEnd / 90; + + Point2D start = ArcPoint(loc, radius, angleStart % 90); + Point2D end = ArcPoint(loc, radius, angleEnd % 90); + + if (opposite) + { + Swap(ref start, ref end); + Swap(ref startQuadrant, ref endQuadrant); + } + + CirclePoint startPoint = new CirclePoint(start, angleStart, startQuadrant); + CirclePoint endPoint = new CirclePoint(end, angleEnd, endQuadrant); + + int error = -radius; + int x = radius; + int y = 0; + + while (x > y) + { + plot4points(loc, map, x, y, startPoint, endPoint, effect, opposite); + plot4points(loc, map, y, x, startPoint, endPoint, effect, opposite); + + error += y * 2 + 1; + ++y; + + if (error >= 0) + { + --x; + error -= x * 2; + } + } + + plot4points(loc, map, x, y, startPoint, endPoint, effect, opposite); + } + + public static void plot4points(Point3D loc, Map map, int x, int y, CirclePoint start, CirclePoint end, + DoEffect_Callback effect, bool opposite) + { + Point2D pointA = new Point2D(loc.X - x, loc.Y - y); + Point2D pointB = new Point2D(loc.X - y, loc.Y - x); + + int quadrant = 2; + + if (x == 0 && start.Quadrant == 3) + quadrant = 3; + + if (WithinCircleBounds(quadrant == 3 ? pointB : pointA, quadrant, loc, start, end, opposite)) + effect(new Point3D(loc.X + x, loc.Y + y, loc.Z), map); + + quadrant = 3; + + if (y == 0 && start.Quadrant == 0) + quadrant = 0; + + if (x != 0 && WithinCircleBounds(quadrant == 0 ? pointA : pointB, quadrant, loc, start, end, opposite)) + effect(new Point3D(loc.X - x, loc.Y + y, loc.Z), map); + if (y != 0 && WithinCircleBounds(pointB, 1, loc, start, end, opposite)) + effect(new Point3D(loc.X + x, loc.Y - y, loc.Z), map); + if (x != 0 && y != 0 && WithinCircleBounds(pointA, 0, loc, start, end, opposite)) + effect(new Point3D(loc.X - x, loc.Y - y, loc.Z), map); + } + + public static bool WithinCircleBounds(Point2D pointLoc, int pointQuadrant, Point3D center, CirclePoint start, + CirclePoint end, bool opposite) + { + if (start.Angle == 0 && end.Angle == 360) + return true; + + int startX = start.Point.X; + int startY = start.Point.Y; + int endX = end.Point.X; + int endY = end.Point.Y; + + int x = pointLoc.X; + int y = pointLoc.Y; + + if (pointQuadrant < start.Quadrant || pointQuadrant > end.Quadrant) + return opposite; + + if (pointQuadrant > start.Quadrant && pointQuadrant < end.Quadrant) + return !opposite; + + bool withinBounds = true; + + if (start.Quadrant == end.Quadrant) + { + if (startX == endX && (x > startX || y > startY || y < endY)) + withinBounds = false; + else if (startY == endY && (y < startY || x < startX || x > endX)) + withinBounds = false; + else if (x < startX || x > endX || y > startY || y < endY) + withinBounds = false; + } + else if (pointQuadrant == start.Quadrant && (x < startX || y > startY)) + { + withinBounds = false; + } + else if (pointQuadrant == end.Quadrant && (x > endX || y < endY)) + { + withinBounds = false; + } + + return opposite ? !withinBounds : withinBounds; + } + + public static void Line2D(Point3D start, Point3D end, Map map, DoEffect_Callback effect) + { + bool steep = Math.Abs(end.Y - start.Y) > Math.Abs(end.X - start.X); + + int x0 = start.X; + int x1 = end.X; + int y0 = start.Y; + int y1 = end.Y; + + if (steep) + { + Swap(ref x0, ref y0); + Swap(ref x1, ref y1); + } + + if (x0 > x1) + { + Swap(ref x0, ref x1); + Swap(ref y0, ref y1); + } + + int deltax = x1 - x0; + int deltay = Math.Abs(y1 - y0); + int error = deltax / 2; + int ystep = y0 < y1 ? 1 : -1; + int y = y0; + + for (int x = x0; x <= x1; x++) + { + if (steep) + effect(new Point3D(y, x, start.Z), map); + else + effect(new Point3D(x, y, start.Z), map); + + error -= deltay; + + if (error < 0) + { + y += ystep; + error += deltax; + } + } + } + + public class CirclePoint + { + public CirclePoint(Point2D point, int angle, int quadrant) + { + Point = point; + Angle = angle; + Quadrant = quadrant; + } + + public Point2D Point{ get; } + + public int Angle{ get; } + + public int Quadrant{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/DecorativeTopiary.cs b/Scripts/Misc/Gifts/Winter2004/DecorativeTopiary.cs index 540a3f1a2..363ce2b3b 100644 --- a/Scripts/Misc/Gifts/Winter2004/DecorativeTopiary.cs +++ b/Scripts/Misc/Gifts/Winter2004/DecorativeTopiary.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class DecorativeTopiary : Item - { - [Constructible] - public DecorativeTopiary() : base( 0x2378 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class DecorativeTopiary : Item + { + [Constructible] + public DecorativeTopiary() : base(0x2378) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public DecorativeTopiary( Serial serial ) : base( serial ) - { - } + public DecorativeTopiary(Serial serial) : base(serial) + { + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - LabelTo( from, 1070880 ); // Winter 2004 - } + LabelTo(from, 1070880); // Winter 2004 + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070880 ); // Winter 2004 - } + list.Add(1070880); // Winter 2004 + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/FestiveCactus.cs b/Scripts/Misc/Gifts/Winter2004/FestiveCactus.cs index c1361a442..79a065b32 100644 --- a/Scripts/Misc/Gifts/Winter2004/FestiveCactus.cs +++ b/Scripts/Misc/Gifts/Winter2004/FestiveCactus.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class FestiveCactus : Item - { - [Constructible] - public FestiveCactus() : base( 0x2376 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class FestiveCactus : Item + { + [Constructible] + public FestiveCactus() : base(0x2376) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public FestiveCactus( Serial serial ) : base( serial ) - { - } + public FestiveCactus(Serial serial) : base(serial) + { + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - LabelTo( from, 1070880 ); // Winter 2004 - } + LabelTo(from, 1070880); // Winter 2004 + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070880 ); // Winter 2004 - } + list.Add(1070880); // Winter 2004 + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/LightOfTheWinterSolstice.cs b/Scripts/Misc/Gifts/Winter2004/LightOfTheWinterSolstice.cs index 26816bffc..8f70bcd35 100644 --- a/Scripts/Misc/Gifts/Winter2004/LightOfTheWinterSolstice.cs +++ b/Scripts/Misc/Gifts/Winter2004/LightOfTheWinterSolstice.cs @@ -1,99 +1,98 @@ -using System; - namespace Server.Items { - [FlippableAttribute( 0x236E, 0x2371 )] - public class LightOfTheWinterSolstice : Item - { - private static string[] m_StaffNames = { - "Aenima", - "Alkiser", - "ASayre", - "David", - "Krrios", - "Mark", - "Merlin", - "Merlix", //LordMerlix - "Phantom", - "Phenos", - "psz", - "Ryan", - "Quantos", - "Outkast", //TheOutkastDev - "V", //Admin_V - "Zippy" - }; + [Flippable(0x236E, 0x2371)] + public class LightOfTheWinterSolstice : Item + { + private static string[] m_StaffNames = + { + "Aenima", + "Alkiser", + "ASayre", + "David", + "Krrios", + "Mark", + "Merlin", + "Merlix", //LordMerlix + "Phantom", + "Phenos", + "psz", + "Ryan", + "Quantos", + "Outkast", //TheOutkastDev + "V", //Admin_V + "Zippy" + }; - [CommandProperty( AccessLevel.GameMaster )] - public string Dipper { get; set; } + [Constructible] + public LightOfTheWinterSolstice() : this(m_StaffNames[Utility.Random(m_StaffNames.Length)]) + { + } - [Constructible] - public LightOfTheWinterSolstice() : this( m_StaffNames[Utility.Random( m_StaffNames.Length )] ) - { - } + [Constructible] + public LightOfTheWinterSolstice(string dipper) : base(0x236E) + { + Dipper = dipper; - [Constructible] - public LightOfTheWinterSolstice( string dipper ) : base( 0x236E ) - { - Dipper = dipper; + Weight = 1.0; + LootType = LootType.Blessed; + Light = LightType.Circle300; + Hue = Utility.RandomDyedHue(); + } - Weight = 1.0; - LootType = LootType.Blessed; - Light = LightType.Circle300; - Hue = Utility.RandomDyedHue(); - } + public LightOfTheWinterSolstice(Serial serial) : base(serial) + { + } - public LightOfTheWinterSolstice( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public string Dipper{ get; set; } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - LabelTo( from, 1070881, Dipper ); // Hand Dipped by ~1_name~ - LabelTo( from, 1070880 ); // Winter 2004 - } + LabelTo(from, 1070881, Dipper); // Hand Dipped by ~1_name~ + LabelTo(from, 1070880); // Winter 2004 + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070881, Dipper ); // Hand Dipped by ~1_name~ - list.Add( 1070880 ); // Winter 2004 - } + list.Add(1070881, Dipper); // Hand Dipped by ~1_name~ + list.Add(1070880); // Winter 2004 + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (string) Dipper ); - } + writer.Write(Dipper); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Dipper = reader.ReadString(); - break; - } - case 0: - { - Dipper = m_StaffNames[Utility.Random( m_StaffNames.Length )]; - break; - } - } + switch (version) + { + case 1: + { + Dipper = reader.ReadString(); + break; + } + case 0: + { + Dipper = m_StaffNames[Utility.Random(m_StaffNames.Length)]; + break; + } + } - if ( Dipper != null ) - Dipper = string.Intern( Dipper ); - } - } + if (Dipper != null) + Dipper = string.Intern(Dipper); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/Mistletoe.cs b/Scripts/Misc/Gifts/Winter2004/Mistletoe.cs index e01e3c57b..b451de605 100644 --- a/Scripts/Misc/Gifts/Winter2004/Mistletoe.cs +++ b/Scripts/Misc/Gifts/Winter2004/Mistletoe.cs @@ -6,325 +6,325 @@ using Server.Targeting; namespace Server.Items { - public class MistletoeAddon : Item, IDyable, IAddon - { - [Constructible] - public MistletoeAddon() : this( Utility.RandomDyedHue() ) - { - } + public class MistletoeAddon : Item, IDyable, IAddon + { + [Constructible] + public MistletoeAddon() : this(Utility.RandomDyedHue()) + { + } - [Constructible] - public MistletoeAddon( int hue ) : base( 0x2375 ) - { - Hue = hue; - Movable = false; - } + [Constructible] + public MistletoeAddon(int hue) : base(0x2375) + { + Hue = hue; + Movable = false; + } - public MistletoeAddon( Serial serial ) : base( serial ) - { - } + public MistletoeAddon(Serial serial) : base(serial) + { + } - public bool CouldFit( IPoint3D p, Map map ) - { - if ( !map.CanFit( p.X, p.Y, p.Z, ItemData.Height ) ) - return false; + public bool CouldFit(IPoint3D p, Map map) + { + if (!map.CanFit(p.X, p.Y, p.Z, ItemData.Height)) + return false; - if ( ItemID == 0x2375 ) - return BaseAddon.IsWall( p.X, p.Y - 1, p.Z, map ); // North wall - return BaseAddon.IsWall( p.X - 1, p.Y, p.Z, map ); // West wall - } + if (ItemID == 0x2375) + return BaseAddon.IsWall(p.X, p.Y - 1, p.Z, map); // North wall + return BaseAddon.IsWall(p.X - 1, p.Y, p.Z, map); // West wall + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public Item Deed => new MistletoeDeed(Hue); - writer.Write( (int) 0 ); // version - } + public virtual bool Dye(Mobile from, DyeTub sender) + { + if (Deleted) + return false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + BaseHouse house = BaseHouse.FindHouseAt(this); - int version = reader.ReadInt(); + if (house != null && house.IsCoOwner(from)) + { + if (from.InRange(GetWorldLocation(), 1)) + { + Hue = sender.DyedHue; + return true; + } - Timer.DelayCall( TimeSpan.Zero, FixMovingCrate ); - } + from.SendLocalizedMessage(500295); // You are too far away to do that. + return false; + } - private void FixMovingCrate() - { - if ( Deleted ) - return; + return false; + } - if ( Movable || IsLockedDown ) - { - Item deed = Deed; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( Parent is Item item ) - { - item.AddItem( deed ); - deed.Location = Location; - } - else - { - deed.MoveToWorld( Location, Map ); - } + writer.Write(0); // version + } - Delete(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public Item Deed => new MistletoeDeed( Hue ); + int version = reader.ReadInt(); - public override void OnDoubleClick( Mobile from ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + Timer.DelayCall(TimeSpan.Zero, FixMovingCrate); + } - if ( house != null && house.IsCoOwner( from ) ) - { - if ( from.InRange( GetWorldLocation(), 3 ) ) - { - from.CloseGump( typeof( MistletoeAddonGump ) ); - from.SendGump( new MistletoeAddonGump( from, this ) ); - } - else - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - } - } - } + private void FixMovingCrate() + { + if (Deleted) + return; - public virtual bool Dye( Mobile from, DyeTub sender ) - { - if ( Deleted ) - return false; + if (Movable || IsLockedDown) + { + Item deed = Deed; - BaseHouse house = BaseHouse.FindHouseAt( this ); + if (Parent is Item item) + { + item.AddItem(deed); + deed.Location = Location; + } + else + { + deed.MoveToWorld(Location, Map); + } - if ( house != null && house.IsCoOwner( from ) ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - { - Hue = sender.DyedHue; - return true; - } + Delete(); + } + } - from.SendLocalizedMessage( 500295 ); // You are too far away to do that. - return false; - } + public override void OnDoubleClick(Mobile from) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - return false; - } + if (house != null && house.IsCoOwner(from)) + { + if (from.InRange(GetWorldLocation(), 3)) + { + from.CloseGump(typeof(MistletoeAddonGump)); + from.SendGump(new MistletoeAddonGump(from, this)); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + } + } + } - private class MistletoeAddonGump : Gump - { - private Mobile m_From; - private MistletoeAddon m_Addon; + private class MistletoeAddonGump : Gump + { + private MistletoeAddon m_Addon; + private Mobile m_From; - public MistletoeAddonGump( Mobile from, MistletoeAddon addon ) : base( 150, 50 ) - { - m_From = from; - m_Addon = addon; + public MistletoeAddonGump(Mobile from, MistletoeAddon addon) : base(150, 50) + { + m_From = from; + m_Addon = addon; - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 220, 170, 0x13BE ); - AddBackground( 10, 10, 200, 150, 0xBB8 ); - AddHtmlLocalized( 20, 30, 180, 60, 1062839, false, false ); // Do you wish to re-deed this decoration? - AddHtmlLocalized( 55, 100, 160, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 100, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 55, 125, 160, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 125, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0 ); - } + AddBackground(0, 0, 220, 170, 0x13BE); + AddBackground(10, 10, 200, 150, 0xBB8); + AddHtmlLocalized(20, 30, 180, 60, 1062839, false, false); // Do you wish to re-deed this decoration? + AddHtmlLocalized(55, 100, 160, 25, 1011011, false, false); // CONTINUE + AddButton(20, 100, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(55, 125, 160, 25, 1011012, false, false); // CANCEL + AddButton(20, 125, 0xFA5, 0xFA7, 0, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Addon.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Addon.Deleted) + return; - if ( info.ButtonID == 1 ) - { - if ( m_From.InRange( m_Addon.GetWorldLocation(), 3 ) ) - { - m_From.AddToBackpack( m_Addon.Deed ); - m_Addon.Delete(); - } - else - { - m_From.SendLocalizedMessage( 500295 ); // You are too far away to do that. - } - } - } - } - } + if (info.ButtonID == 1) + { + if (m_From.InRange(m_Addon.GetWorldLocation(), 3)) + { + m_From.AddToBackpack(m_Addon.Deed); + m_Addon.Delete(); + } + else + { + m_From.SendLocalizedMessage(500295); // You are too far away to do that. + } + } + } + } + } - [Flippable( 0x14F0, 0x14EF )] - public class MistletoeDeed : Item - { - public override int LabelNumber => 1070882; // Mistletoe Deed + [Flippable(0x14F0, 0x14EF)] + public class MistletoeDeed : Item + { + [Constructible] + public MistletoeDeed() : this(0) + { + } - [Constructible] - public MistletoeDeed() : this( 0 ) - { - } + [Constructible] + public MistletoeDeed(int hue) : base(0x14F0) + { + Hue = hue; + Weight = 1.0; + LootType = LootType.Blessed; + } - [Constructible] - public MistletoeDeed( int hue ) : base( 0x14F0 ) - { - Hue = hue; - Weight = 1.0; - LootType = LootType.Blessed; - } + public MistletoeDeed(Serial serial) : base(serial) + { + } - public MistletoeDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1070882; // Mistletoe Deed - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - LabelTo( from, 1070880 ); // Winter 2004 - } + LabelTo(from, 1070880); // Winter 2004 + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070880 ); // Winter 2004 - } + list.Add(1070880); // Winter 2004 + } - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - { - BaseHouse house = BaseHouse.FindHouseAt( from ); + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + { + BaseHouse house = BaseHouse.FindHouseAt(from); - if ( house != null && house.IsCoOwner( from ) ) - { - from.SendLocalizedMessage( 1062838 ); // Where would you like to place this decoration? - from.BeginTarget( -1, true, TargetFlags.None, Placement_OnTarget, null ); - } - else - { - from.SendLocalizedMessage( 502092 ); // You must be in your house to do this. - } - } - else - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - } + if (house != null && house.IsCoOwner(from)) + { + from.SendLocalizedMessage(1062838); // Where would you like to place this decoration? + from.BeginTarget(-1, true, TargetFlags.None, Placement_OnTarget, null); + } + else + { + from.SendLocalizedMessage(502092); // You must be in your house to do this. + } + } + else + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + } - public void Placement_OnTarget( Mobile from, object targeted, object state ) - { - if ( !(targeted is IPoint3D p) ) - return; + public void Placement_OnTarget(Mobile from, object targeted, object state) + { + if (!(targeted is IPoint3D p)) + return; - Point3D loc = new Point3D( p ); + Point3D loc = new Point3D(p); - BaseHouse house = BaseHouse.FindHouseAt( loc, from.Map, 16 ); + BaseHouse house = BaseHouse.FindHouseAt(loc, from.Map, 16); - if ( house != null && house.IsCoOwner( from ) ) - { - bool northWall = BaseAddon.IsWall( loc.X, loc.Y - 1, loc.Z, from.Map ); - bool westWall = BaseAddon.IsWall( loc.X - 1, loc.Y, loc.Z, from.Map ); + if (house != null && house.IsCoOwner(from)) + { + bool northWall = BaseAddon.IsWall(loc.X, loc.Y - 1, loc.Z, from.Map); + bool westWall = BaseAddon.IsWall(loc.X - 1, loc.Y, loc.Z, from.Map); - if ( northWall && westWall ) - from.SendGump( new MistletoeDeedGump( from, loc, this ) ); - else - PlaceAddon( from, loc, northWall, westWall ); - } - else - { - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - } - } + if (northWall && westWall) + from.SendGump(new MistletoeDeedGump(from, loc, this)); + else + PlaceAddon(from, loc, northWall, westWall); + } + else + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + } + } - private void PlaceAddon( Mobile from, Point3D loc, bool northWall, bool westWall ) - { - if ( Deleted ) - return; + private void PlaceAddon(Mobile from, Point3D loc, bool northWall, bool westWall) + { + if (Deleted) + return; - BaseHouse house = BaseHouse.FindHouseAt( loc, from.Map, 16 ); + BaseHouse house = BaseHouse.FindHouseAt(loc, from.Map, 16); - if ( house == null || !house.IsCoOwner( from ) ) - { - from.SendLocalizedMessage( 1042036 ); // That location is not in your house. - return; - } + if (house == null || !house.IsCoOwner(from)) + { + from.SendLocalizedMessage(1042036); // That location is not in your house. + return; + } - int itemID = 0; + int itemID = 0; - if ( northWall ) - itemID = 0x2374; - else if ( westWall ) - itemID = 0x2375; - else - from.SendLocalizedMessage( 1070883 ); // The mistletoe must be placed next to a wall. + if (northWall) + itemID = 0x2374; + else if (westWall) + itemID = 0x2375; + else + from.SendLocalizedMessage(1070883); // The mistletoe must be placed next to a wall. - if ( itemID > 0 ) - { - Item addon = new MistletoeAddon( Hue ); + if (itemID > 0) + { + Item addon = new MistletoeAddon(Hue); - addon.ItemID = itemID; - addon.MoveToWorld( loc, from.Map ); + addon.ItemID = itemID; + addon.MoveToWorld(loc, from.Map); - house.Addons.Add( addon ); - Delete(); - } - } + house.Addons.Add(addon); + Delete(); + } + } - private class MistletoeDeedGump : Gump - { - private Mobile m_From; - private Point3D m_Loc; - private MistletoeDeed m_Deed; + private class MistletoeDeedGump : Gump + { + private MistletoeDeed m_Deed; + private Mobile m_From; + private Point3D m_Loc; - public MistletoeDeedGump( Mobile from, Point3D loc, MistletoeDeed deed ) : base( 150, 50 ) - { - m_From = from; - m_Loc = loc; - m_Deed = deed; + public MistletoeDeedGump(Mobile from, Point3D loc, MistletoeDeed deed) : base(150, 50) + { + m_From = from; + m_Loc = loc; + m_Deed = deed; - AddBackground( 0, 0, 300, 150, 0xA28 ); + AddBackground(0, 0, 300, 150, 0xA28); - AddPage( 0 ); + AddPage(0); - AddItem( 90, 30, 0x2375 ); - AddItem( 180, 30, 0x2374 ); - AddButton( 50, 35, 0x868, 0x869, 1, GumpButtonType.Reply, 0 ); - AddButton( 145, 35, 0x868, 0x869, 2, GumpButtonType.Reply, 0 ); - } + AddItem(90, 30, 0x2375); + AddItem(180, 30, 0x2374); + AddButton(50, 35, 0x868, 0x869, 1, GumpButtonType.Reply, 0); + AddButton(145, 35, 0x868, 0x869, 2, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Deed.Deleted ) - return; + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Deed.Deleted) + return; - switch( info.ButtonID ) - { - case 1: - m_Deed.PlaceAddon( m_From, m_Loc, false, true ); - break; - case 2: - m_Deed.PlaceAddon( m_From, m_Loc, true, false ); - break; - } - } - } - } -} + switch (info.ButtonID) + { + case 1: + m_Deed.PlaceAddon(m_From, m_Loc, false, true); + break; + case 2: + m_Deed.PlaceAddon(m_From, m_Loc, true, false); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/PileOfGlacialSnow.cs b/Scripts/Misc/Gifts/Winter2004/PileOfGlacialSnow.cs index c77e63106..b4883b1d3 100644 --- a/Scripts/Misc/Gifts/Winter2004/PileOfGlacialSnow.cs +++ b/Scripts/Misc/Gifts/Winter2004/PileOfGlacialSnow.cs @@ -1,148 +1,153 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Items { - public class PileOfGlacialSnow : Item - { - [Constructible] - public PileOfGlacialSnow() : base( 0x913 ) - { - Hue = 0x480; - Weight = 1.0; - LootType = LootType.Blessed; - } + public class PileOfGlacialSnow : Item + { + [Constructible] + public PileOfGlacialSnow() : base(0x913) + { + Hue = 0x480; + Weight = 1.0; + LootType = LootType.Blessed; + } - public override int LabelNumber => 1070874; // a Pile of Glacial Snow + public PileOfGlacialSnow(Serial serial) : base(serial) + { + } - public PileOfGlacialSnow( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1070874; // a Pile of Glacial Snow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } - } + if (version == 0) + { + Weight = 1.0; + LootType = LootType.Blessed; + } + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - LabelTo( from, 1070880 ); // Winter 2004 - } + LabelTo(from, 1070880); // Winter 2004 + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1070880 ); // Winter 2004 - } + list.Add(1070880); // Winter 2004 + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042010 ); // You must have the object in your backpack to use it. - } - else if ( from.Mounted ) - from.SendLocalizedMessage ( 1010097 ); // You cannot use this while mounted. + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042010); // You must have the object in your backpack to use it. + } + else if (from.Mounted) + { + from.SendLocalizedMessage(1010097); // You cannot use this while mounted. + } - else if ( from.CanBeginAction( typeof( SnowPile ) ) ) - { - from.SendLocalizedMessage( 1005575 ); // You carefully pack the snow into a ball... - from.Target = new SnowTarget( from, this ); - } - else - { - from.SendLocalizedMessage( 1005574 ); // The snow is not ready to be packed yet. Keep trying. - } - } + else if (from.CanBeginAction(typeof(SnowPile))) + { + from.SendLocalizedMessage(1005575); // You carefully pack the snow into a ball... + from.Target = new SnowTarget(from, this); + } + else + { + from.SendLocalizedMessage(1005574); // The snow is not ready to be packed yet. Keep trying. + } + } - private class InternalTimer : Timer - { - private Mobile m_From; + private class InternalTimer : Timer + { + private Mobile m_From; - public InternalTimer( Mobile from ) : base( TimeSpan.FromSeconds( 5.0 ) ) - { - m_From = from; - } + public InternalTimer(Mobile from) : base(TimeSpan.FromSeconds(5.0)) + { + m_From = from; + } - protected override void OnTick() - { - m_From.EndAction( typeof( SnowPile ) ); - } - } + protected override void OnTick() + { + m_From.EndAction(typeof(SnowPile)); + } + } - private class SnowTarget : Target - { - private Mobile m_Thrower; - private Item m_Snow; + private class SnowTarget : Target + { + private Item m_Snow; + private Mobile m_Thrower; - public SnowTarget( Mobile thrower, Item snow ) : base ( 10, false, TargetFlags.None ) - { - m_Thrower = thrower; - m_Snow = snow; - } + public SnowTarget(Mobile thrower, Item snow) : base(10, false, TargetFlags.None) + { + m_Thrower = thrower; + m_Snow = snow; + } - protected override void OnTarget( Mobile from, object target ) - { - if ( target == from ) - { - from.SendLocalizedMessage( 1005576 ); // You can't throw this at yourself. - } - else if ( target is Mobile targ ) - { - Container pack = targ.Backpack; + protected override void OnTarget(Mobile from, object target) + { + if (target == from) + { + from.SendLocalizedMessage(1005576); // You can't throw this at yourself. + } + else if (target is Mobile targ) + { + Container pack = targ.Backpack; - if ( from.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) || targ.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - from.SendMessage( "You may not throw snow here." ); - } - else if ( pack?.FindItemByType( new[]{ typeof( SnowPile ), typeof( PileOfGlacialSnow ) } ) != null ) - { - if ( from.BeginAction( typeof( SnowPile ) ) ) - { - new InternalTimer( from ).Start(); + if (from.Region.IsPartOf(typeof(SafeZone)) || targ.Region.IsPartOf(typeof(SafeZone))) + { + from.SendMessage("You may not throw snow here."); + } + else if (pack?.FindItemByType(new[] { typeof(SnowPile), typeof(PileOfGlacialSnow) }) != null) + { + if (from.BeginAction(typeof(SnowPile))) + { + new InternalTimer(from).Start(); - from.PlaySound( 0x145 ); + from.PlaySound(0x145); - from.Animate( 9, 1, 1, true, false, 0 ); + from.Animate(9, 1, 1, true, false, 0); - targ.SendLocalizedMessage( 1010572 ); // You have just been hit by a snowball! - from.SendLocalizedMessage( 1010573 ); // You throw the snowball and hit the target! + targ.SendLocalizedMessage(1010572); // You have just been hit by a snowball! + from.SendLocalizedMessage(1010573); // You throw the snowball and hit the target! - Effects.SendMovingEffect( from, targ, 0x36E4, 7, 0, false, true, 0x47F, 0 ); - } - else - { - from.SendLocalizedMessage( 1005574 ); // The snow is not ready to be packed yet. Keep trying. - } - } - else - { - from.SendLocalizedMessage( 1005577 ); // You can only throw a snowball at something that can throw one back. - } - } - else - { - from.SendLocalizedMessage( 1005577 ); // You can only throw a snowball at something that can throw one back. - } - } - } - } -} + Effects.SendMovingEffect(from, targ, 0x36E4, 7, 0, false, true, 0x47F, 0); + } + else + { + from.SendLocalizedMessage(1005574); // The snow is not ready to be packed yet. Keep trying. + } + } + else + { + from.SendLocalizedMessage( + 1005577); // You can only throw a snowball at something that can throw one back. + } + } + else + { + from.SendLocalizedMessage( + 1005577); // You can only throw a snowball at something that can throw one back. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/SnowPile.cs b/Scripts/Misc/Gifts/Winter2004/SnowPile.cs index 8ec8fbf5e..c6efeacdc 100644 --- a/Scripts/Misc/Gifts/Winter2004/SnowPile.cs +++ b/Scripts/Misc/Gifts/Winter2004/SnowPile.cs @@ -1,134 +1,139 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Items { - public class SnowPile : Item - { - [Constructible] - public SnowPile() : base( 0x913 ) - { - Hue = 0x481; - Weight = 1.0; - LootType = LootType.Blessed; - } + public class SnowPile : Item + { + [Constructible] + public SnowPile() : base(0x913) + { + Hue = 0x481; + Weight = 1.0; + LootType = LootType.Blessed; + } - public override int LabelNumber => 1005578; // a pile of snow + public SnowPile(Serial serial) : base(serial) + { + } - public SnowPile( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1005578; // a pile of snow - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } - } + if (version == 0) + { + Weight = 1.0; + LootType = LootType.Blessed; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042010 ); // You must have the object in your backpack to use it. - } - else if ( from.Mounted ) - from.SendLocalizedMessage ( 1010097 ); // You cannot use this while mounted. + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042010); // You must have the object in your backpack to use it. + } + else if (from.Mounted) + { + from.SendLocalizedMessage(1010097); // You cannot use this while mounted. + } - else if ( from.CanBeginAction( typeof( SnowPile ) ) ) - { - from.SendLocalizedMessage( 1005575 ); // You carefully pack the snow into a ball... - from.Target = new SnowTarget( from, this ); - } - else - { - from.SendLocalizedMessage( 1005574 ); // The snow is not ready to be packed yet. Keep trying. - } - } + else if (from.CanBeginAction(typeof(SnowPile))) + { + from.SendLocalizedMessage(1005575); // You carefully pack the snow into a ball... + from.Target = new SnowTarget(from, this); + } + else + { + from.SendLocalizedMessage(1005574); // The snow is not ready to be packed yet. Keep trying. + } + } - private class InternalTimer : Timer - { - private Mobile m_From; + private class InternalTimer : Timer + { + private Mobile m_From; - public InternalTimer( Mobile from ) : base( TimeSpan.FromSeconds( 5.0 ) ) - { - m_From = from; - } + public InternalTimer(Mobile from) : base(TimeSpan.FromSeconds(5.0)) + { + m_From = from; + } - protected override void OnTick() - { - m_From.EndAction( typeof( SnowPile ) ); - } - } + protected override void OnTick() + { + m_From.EndAction(typeof(SnowPile)); + } + } - private class SnowTarget : Target - { - private Mobile m_Thrower; - private Item m_Snow; + private class SnowTarget : Target + { + private Item m_Snow; + private Mobile m_Thrower; - public SnowTarget( Mobile thrower, Item snow ) : base ( 10, false, TargetFlags.None ) - { - m_Thrower = thrower; - m_Snow = snow; - } + public SnowTarget(Mobile thrower, Item snow) : base(10, false, TargetFlags.None) + { + m_Thrower = thrower; + m_Snow = snow; + } - protected override void OnTarget( Mobile from, object target ) - { - if ( target == from ) - { - from.SendLocalizedMessage( 1005576 ); // You can't throw this at yourself. - } - else if ( target is Mobile targ ) - { - Container pack = targ.Backpack; + protected override void OnTarget(Mobile from, object target) + { + if (target == from) + { + from.SendLocalizedMessage(1005576); // You can't throw this at yourself. + } + else if (target is Mobile targ) + { + Container pack = targ.Backpack; - if ( from.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) || targ.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - from.SendMessage( "You may not throw snow here." ); - } - else if ( pack?.FindItemByType( new[]{ typeof( SnowPile ), typeof( PileOfGlacialSnow ) } ) != null ) - { - if ( from.BeginAction( typeof( SnowPile ) ) ) - { - new InternalTimer( from ).Start(); + if (from.Region.IsPartOf(typeof(SafeZone)) || targ.Region.IsPartOf(typeof(SafeZone))) + { + from.SendMessage("You may not throw snow here."); + } + else if (pack?.FindItemByType(new[] { typeof(SnowPile), typeof(PileOfGlacialSnow) }) != null) + { + if (from.BeginAction(typeof(SnowPile))) + { + new InternalTimer(from).Start(); - from.PlaySound( 0x145 ); + from.PlaySound(0x145); - from.Animate( 9, 1, 1, true, false, 0 ); + from.Animate(9, 1, 1, true, false, 0); - targ.SendLocalizedMessage( 1010572 ); // You have just been hit by a snowball! - from.SendLocalizedMessage( 1010573 ); // You throw the snowball and hit the target! + targ.SendLocalizedMessage(1010572); // You have just been hit by a snowball! + from.SendLocalizedMessage(1010573); // You throw the snowball and hit the target! - Effects.SendMovingEffect( from, targ, 0x36E4, 7, 0, false, true, 0x480, 0 ); - } - else - { - from.SendLocalizedMessage( 1005574 ); // The snow is not ready to be packed yet. Keep trying. - } - } - else - { - from.SendLocalizedMessage( 1005577 ); // You can only throw a snowball at something that can throw one back. - } - } - else - { - from.SendLocalizedMessage( 1005577 ); // You can only throw a snowball at something that can throw one back. - } - } - } - } -} + Effects.SendMovingEffect(from, targ, 0x36E4, 7, 0, false, true, 0x480, 0); + } + else + { + from.SendLocalizedMessage(1005574); // The snow is not ready to be packed yet. Keep trying. + } + } + else + { + from.SendLocalizedMessage( + 1005577); // You can only throw a snowball at something that can throw one back. + } + } + else + { + from.SendLocalizedMessage( + 1005577); // You can only throw a snowball at something that can throw one back. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/SnowyTree.cs b/Scripts/Misc/Gifts/Winter2004/SnowyTree.cs index 9cfe730b5..13177cdb6 100644 --- a/Scripts/Misc/Gifts/Winter2004/SnowyTree.cs +++ b/Scripts/Misc/Gifts/Winter2004/SnowyTree.cs @@ -1,44 +1,44 @@ namespace Server.Items { - public class SnowyTree : Item - { - [Constructible] - public SnowyTree() : base( 0x2377 ) - { - Weight = 1.0; - LootType = LootType.Blessed; - } + public class SnowyTree : Item + { + [Constructible] + public SnowyTree() : base(0x2377) + { + Weight = 1.0; + LootType = LootType.Blessed; + } - public SnowyTree( Serial serial ) : base( serial ) - { - } + public SnowyTree(Serial serial) : base(serial) + { + } - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); - LabelTo( from, 1070880 ); // Winter 2004 - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + LabelTo(from, 1070880); // Winter 2004 + } - list.Add( 1070880 ); // Winter 2004 - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + list.Add(1070880); // Winter 2004 + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Gifts/Winter2004/Winter2004.cs b/Scripts/Misc/Gifts/Winter2004/Winter2004.cs index 59b17f1d5..c1588587e 100644 --- a/Scripts/Misc/Gifts/Winter2004/Winter2004.cs +++ b/Scripts/Misc/Gifts/Winter2004/Winter2004.cs @@ -3,42 +3,42 @@ using Server.Items; namespace Server.Misc { - public class WinterGiftGiver2004 : GiftGiver - { - public static void Initialize() - { - GiftGiving.Register( new WinterGiftGiver2004() ); - } + public class WinterGiftGiver2004 : GiftGiver + { + public override DateTime Start => new DateTime(2004, 12, 24); + public override DateTime Finish => new DateTime(2005, 1, 1); - public override DateTime Start => new DateTime( 2004, 12, 24 ); - public override DateTime Finish => new DateTime( 2005, 1, 1 ); + public static void Initialize() + { + GiftGiving.Register(new WinterGiftGiver2004()); + } - public override void GiveGift( Mobile mob ) - { - GiftBox box = new GiftBox(); + public override void GiveGift(Mobile mob) + { + GiftBox box = new GiftBox(); - box.DropItem( new MistletoeDeed() ); - box.DropItem( new PileOfGlacialSnow() ); - box.DropItem( new LightOfTheWinterSolstice() ); + box.DropItem(new MistletoeDeed()); + box.DropItem(new PileOfGlacialSnow()); + box.DropItem(new LightOfTheWinterSolstice()); - int random = Utility.Random( 100 ); + int random = Utility.Random(100); - if ( random < 60 ) - box.DropItem( new DecorativeTopiary() ); - else if ( random < 84 ) - box.DropItem( new FestiveCactus() ); - else - box.DropItem( new SnowyTree() ); + if (random < 60) + box.DropItem(new DecorativeTopiary()); + else if (random < 84) + box.DropItem(new FestiveCactus()); + else + box.DropItem(new SnowyTree()); - switch ( GiveGift( mob, box ) ) - { - case GiftResult.Backpack: - mob.SendMessage( 0x482, "Happy Holidays from the team! Gift items have been placed in your backpack." ); - break; - case GiftResult.BankBox: - mob.SendMessage( 0x482, "Happy Holidays from the team! Gift items have been placed in your bank box." ); - break; - } - } - } -} + switch (GiveGift(mob, box)) + { + case GiftResult.Backpack: + mob.SendMessage(0x482, "Happy Holidays from the team! Gift items have been placed in your backpack."); + break; + case GiftResult.BankBox: + mob.SendMessage(0x482, "Happy Holidays from the team! Gift items have been placed in your bank box."); + break; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Guild.cs b/Scripts/Misc/Guild.cs index dff9dc63f..5ecba0867 100644 --- a/Scripts/Misc/Guild.cs +++ b/Scripts/Misc/Guild.cs @@ -1,1583 +1,1602 @@ using System; using System.Collections.Generic; -using Server.Items; -using Server.Mobiles; -using Server.Gumps; -using Server.Network; -using Server.Targeting; using Server.Commands; using Server.Commands.Generic; +using Server.Gumps; +using Server.Items; +using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Guilds { - #region Ranks - [Flags] - public enum RankFlags - { - None = 0x00000000, - CanInvitePlayer = 0x00000001, - AccessGuildItems = 0x00000002, - RemoveLowestRank = 0x00000004, - RemovePlayers = 0x00000008, - CanPromoteDemote = 0x00000010, - ControlWarStatus = 0x00000020, - AllianceControl = 0x00000040, - CanSetGuildTitle = 0x00000080, - CanVote = 0x00000100, - - All = Member | CanInvitePlayer | RemovePlayers | CanPromoteDemote | ControlWarStatus | AllianceControl | CanSetGuildTitle, - Member = RemoveLowestRank | AccessGuildItems | CanVote - } - - public class RankDefinition - { - public static RankDefinition[] Ranks = { - new RankDefinition( 1062963, 0, RankFlags.None ), //Ronin - new RankDefinition( 1062962, 1, RankFlags.Member ), //Member - new RankDefinition( 1062961, 2, RankFlags.Member | RankFlags.RemovePlayers | RankFlags.CanInvitePlayer | RankFlags.CanSetGuildTitle | RankFlags.CanPromoteDemote ), //Emmissary - new RankDefinition( 1062960, 3, RankFlags.Member | RankFlags.ControlWarStatus ), //Warlord - new RankDefinition( 1062959, 4, RankFlags.All ) //Leader - }; - public static RankDefinition Leader => Ranks[4]; - public static RankDefinition Member => Ranks[1]; - public static RankDefinition Lowest => Ranks[0]; - - public TextDefinition Name { get; } - - public int Rank { get; } - - public RankFlags Flags { get; private set; } - - public RankDefinition( TextDefinition name, int rank, RankFlags flags ) - { - Name = name; - Rank = rank; - Flags = flags; - } - - public bool GetFlag( RankFlags flag ) - { - return ( (Flags & flag) != 0 ); - } - - public void SetFlag( RankFlags flag, bool value ) - { - if ( value ) - Flags |= flag; - else - Flags &= ~flag; - } - } - - #endregion - - #region Alliances - public class AllianceInfo - { - public static Dictionary Alliances { get; } = new Dictionary(); - - private Guild m_Leader; - private List m_Members; - private List m_PendingMembers; - - public string Name { get; } - - public void CalculateAllianceLeader() - { - m_Leader = ((m_Members.Count >= 2) ? m_Members[Utility.Random( m_Members.Count )] : null); - } - - public void CheckLeader() - { - if ( m_Leader == null || m_Leader.Disbanded ) - { - CalculateAllianceLeader(); - - if ( m_Leader == null ) - Disband(); - } - } - - public Guild Leader - { - get - { - CheckLeader(); - return m_Leader; - } - set - { - if ( m_Leader != value && value != null ) - AllianceMessage( 1070765, value.Name ); // Your Alliance is now led by ~1_GUILDNAME~ - - m_Leader = value; - - if ( m_Leader == null ) - CalculateAllianceLeader(); - } - } - - public bool IsPendingMember( Guild g ) - { - if ( g.Alliance != this ) - return false; - - return m_PendingMembers.Contains( g ); - } - - public bool IsMember( Guild g ) - { - if ( g.Alliance != this ) - return false; - - return m_Members.Contains( g ); - } - - public AllianceInfo( Guild leader, string name, Guild partner ) - { - m_Leader = leader; - Name = name; - - m_Members = new List(); - m_PendingMembers = new List(); - - leader.Alliance = this; - partner.Alliance = this; - - if ( !Alliances.ContainsKey( Name.ToLower() ) ) - Alliances.Add( Name.ToLower(), this ); - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (int)0 ); //Version - - writer.Write( Name ); - writer.Write( m_Leader ); - - writer.WriteGuildList( m_Members, true ); - writer.WriteGuildList( m_PendingMembers, true ); - - if ( !Alliances.ContainsKey( Name.ToLower() ) ) - Alliances.Add( Name.ToLower(), this ); - } - - public AllianceInfo( GenericReader reader ) - { - int version = reader.ReadInt(); - - switch( version ) - { - case 0: - { - Name = reader.ReadString(); - m_Leader = reader.ReadGuild() as Guild; - - m_Members = reader.ReadStrongGuildList(); - m_PendingMembers = reader.ReadStrongGuildList(); - - break; - } - } - } - - public void AddPendingGuild( Guild g ) - { - if ( g.Alliance != this || m_PendingMembers.Contains( g ) || m_Members.Contains( g ) ) - return; - - m_PendingMembers.Add( g ); - } - - public void TurnToMember( Guild g ) - { - if ( g.Alliance != this || !m_PendingMembers.Contains( g ) || m_Members.Contains( g ) ) - return; - - g.GuildMessage( 1070760, Name ); // Your Guild has joined the ~1_ALLIANCENAME~ Alliance. - AllianceMessage( 1070761, g.Name ); // A new Guild has joined your Alliance: ~1_GUILDNAME~ - - m_PendingMembers.Remove( g ); - m_Members.Add( g ); - g.Alliance.InvalidateMemberProperties(); - } - - public void RemoveGuild( Guild g ) - { - if ( m_PendingMembers.Contains( g ) ) - { - m_PendingMembers.Remove( g ); - } - - if ( m_Members.Contains( g ) ) //Sanity, just incase someone with a custom script adds a character to BOTH arrays - { - m_Members.Remove( g ); - g.InvalidateMemberProperties(); - - g.GuildMessage( 1070763, Name ); // Your Guild has been removed from the ~1_ALLIANCENAME~ Alliance. - AllianceMessage( 1070764, g.Name ); // A Guild has left your Alliance: ~1_GUILDNAME~ - } - - //g.Alliance = null; //NO G.Alliance call here. Set the Guild's Alliance to null, if you JUST use RemoveGuild, it removes it from the alliance, but doesn't remove the link from the guild to the alliance. setting g.Alliance will call this method. - //to check on OSI: have 3 guilds, make 2 of them a member, one pending. remove one of the memebers. alliance still exist? - //ANSWER: NO - - if ( g == m_Leader ) - { - CalculateAllianceLeader(); - - /* - if ( m_Leader == null ) //only when m_members.count < 2 - Disband(); - else - AllianceMessage( 1070765, m_Leader.Name ); // Your Alliance is now led by ~1_GUILDNAME~ - */ - } - - if ( m_Members.Count < 2 ) - Disband(); - } - - public void Disband() - { - AllianceMessage( 1070762 ); // Your Alliance has dissolved. - - for( int i = 0; i < m_PendingMembers.Count; i++ ) - m_PendingMembers[i].Alliance = null; - - for( int i = 0; i < m_Members.Count; i++ ) - m_Members[i].Alliance = null; - - Alliances.TryGetValue( Name.ToLower(), out AllianceInfo aInfo ); - - if ( aInfo == this ) - Alliances.Remove( Name.ToLower() ); - } - - public void InvalidateMemberProperties() - { - InvalidateMemberProperties( false ); - } - - public void InvalidateMemberProperties( bool onlyOPL ) - { - for ( int i = 0; i < m_Members.Count; i++ ) - { - Guild g = m_Members[i]; - - g.InvalidateMemberProperties( onlyOPL ); - } - } - - public void InvalidateMemberNotoriety() - { - for ( int i = 0; i < m_Members.Count; i++ ) - m_Members[i].InvalidateMemberNotoriety(); - } - - #region Alliance[Text]Message(...) - public void AllianceMessage( int num, bool append, string format, params object[] args ) - { - AllianceMessage( num, append, string.Format( format, args) ); - } - public void AllianceMessage( int number ) - { - for ( int i = 0; i < m_Members.Count; ++i ) - m_Members[i].GuildMessage( number ); - } - public void AllianceMessage( int number, string args ) - { - AllianceMessage( number, args, 0x3B2 ); - } - public void AllianceMessage( int number, string args, int hue ) - { - for ( int i = 0; i < m_Members.Count; ++i ) - m_Members[i].GuildMessage( number, args, hue ); - } - public void AllianceMessage( int number, bool append, string affix ) - { - AllianceMessage( number, append, affix, "", 0x3B2 ); - } - public void AllianceMessage( int number, bool append, string affix, string args ) - { - AllianceMessage( number, append, affix, args, 0x3B2 ); - } - public void AllianceMessage( int number, bool append, string affix, string args, int hue ) - { - for ( int i = 0; i < m_Members.Count; ++i ) - m_Members[i].GuildMessage( number, append, affix, args, hue ); - } - - public void AllianceTextMessage( string text ) - { - AllianceTextMessage( 0x3B2, text ); - } - public void AllianceTextMessage( string format, params object[] args ) - { - AllianceTextMessage( 0x3B2, string.Format( format, args ) ); - } - public void AllianceTextMessage( int hue, string text ) - { - for( int i = 0; i < m_Members.Count; ++i ) - m_Members[i].GuildTextMessage( hue, text ); - } - public void AllianceTextMessage( int hue, string format, params object[] args ) - { - AllianceTextMessage( hue, string.Format( format, args ) ); - } - - public void AllianceChat( Mobile from, int hue, string text ) - { - Packet p = null; - for( int i = 0; i < m_Members.Count; i++ ) - { - Guild g = m_Members[i]; - - for( int j = 0; j < g.Members.Count; j++ ) - { - Mobile m = g.Members[j]; - - NetState state = m.NetState; - - if ( state != null ) - { - if ( p == null ) - p = Packet.Acquire( new UnicodeMessage( from.Serial, from.Body, MessageType.Alliance, hue, 3, from.Language, from.Name, text ) ); - - state.Send( p ); - } - } - } - - Packet.Release( p ); - } - - public void AllianceChat( Mobile from, string text ) - { - PlayerMobile pm = from as PlayerMobile; - - AllianceChat( from, pm?.AllianceMessageHue ?? 0x3B2, text ); - } - #endregion - - public class AllianceRosterGump : GuildDiplomacyGump - { - protected override bool AllowAdvancedSearch => false; - - private AllianceInfo m_Alliance; - - public AllianceRosterGump( PlayerMobile pm, Guild g, AllianceInfo alliance ): base( pm, g, true, "", 0, alliance.m_Members, alliance.Name ) - { - m_Alliance = alliance; - } - - public AllianceRosterGump( PlayerMobile pm, Guild g, AllianceInfo alliance, IComparer currentComparer, bool ascending, string filter, int startNumber ) : base( pm, g, currentComparer, ascending, filter, startNumber, alliance.m_Members, alliance.Name ) - { - m_Alliance = alliance; - } - - public override Gump GetResentGump( PlayerMobile pm, Guild g, IComparer comparer, bool ascending, string filter, int startNumber ) - { - return new AllianceRosterGump( pm, g, m_Alliance, comparer, ascending, filter, startNumber ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID != 8 ) //So that they can't get to the AdvancedSearch button - base.OnResponse( sender, info ); - } - } - } - #endregion - - #region Wars - public enum WarStatus - { - InProgress = -1, - Win, - Lose, - Draw, - Pending - } - - public class WarDeclaration - { - public int Kills { get; set; } - - public int MaxKills { get; set; } - - public TimeSpan WarLength { get; set; } - - public Guild Opponent { get; } - - public Guild Guild { get; } - - public DateTime WarBeginning { get; set; } - - public bool WarRequester { get; set; } - - public WarDeclaration( Guild g, Guild opponent, int maxKills, TimeSpan warLength, bool warRequester ) - { - Guild = g; - MaxKills = maxKills; - Opponent = opponent; - WarLength = warLength; - WarRequester = warRequester; - } - - public WarDeclaration( GenericReader reader ) - { - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - Kills = reader.ReadInt(); - MaxKills = reader.ReadInt(); - - WarLength = reader.ReadTimeSpan(); - WarBeginning = reader.ReadDateTime(); - - Guild = reader.ReadGuild() as Guild; - Opponent = reader.ReadGuild() as Guild; - - WarRequester = reader.ReadBool(); - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (int)0 ); //version - - writer.Write( Kills ); - writer.Write( MaxKills ); - - writer.Write( WarLength ); - writer.Write( WarBeginning ); - - writer.Write( Guild ); - writer.Write( Opponent ); - - writer.Write( WarRequester ); - } - - public WarStatus Status - { - get - { - if ( Opponent == null || Opponent.Disbanded ) - return WarStatus.Win; - - if ( Guild == null || Guild.Disbanded ) - return WarStatus.Lose; - - WarDeclaration w = Opponent.FindActiveWar( Guild ); - - if ( Opponent.FindPendingWar( Guild ) != null && Guild.FindPendingWar( Opponent ) != null ) - return WarStatus.Pending; - - if ( w == null ) - return WarStatus.Win; - - if ( WarLength != TimeSpan.Zero && (WarBeginning + WarLength) < DateTime.UtcNow ) - { - if ( Kills > w.Kills ) - return WarStatus.Win; - if ( Kills < w.Kills ) - return WarStatus.Lose; - return WarStatus.Draw; - } - - if ( MaxKills > 0 ) - { - if ( Kills >= MaxKills ) - return WarStatus.Win; - if ( w.Kills >= w.MaxKills ) - return WarStatus.Lose; - } - - return WarStatus.InProgress; - } - } - } - - public class WarTimer : Timer - { - private static TimeSpan InternalDelay = TimeSpan.FromMinutes( 1.0 ); - - public static void Initialize() - { - if ( Guild.NewGuildSystem ) - new WarTimer().Start(); - } - - public WarTimer() : base( InternalDelay, InternalDelay ) - { - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - foreach( Guild g in BaseGuild.List.Values ) - g.CheckExpiredWars(); - } - } - - #endregion - - public class Guild : BaseGuild - { - public static void Configure() - { - EventSink.CreateGuild += EventSink_CreateGuild; - EventSink.GuildGumpRequest += EventSink_GuildGumpRequest; - - CommandSystem.Register( "GuildProps", AccessLevel.Counselor, GuildProps_OnCommand ); - } - - #region GuildProps - [Usage( "GuildProps" )] - [Description( "Opens a menu where you can view and edit guild properties of a targeted player or guild stone. If the new Guild system is active, also brings up the guild gump." )] - private static void GuildProps_OnCommand( CommandEventArgs e ) - { - string arg = e.ArgString.Trim(); - Mobile from = e.Mobile; - - if ( arg.Length == 0 ) - { - e.Mobile.Target = new GuildPropsTarget(); - } - else - { - Guild g = int.TryParse( arg, out int id ) ? Find( id ) as Guild : - FindByAbbrev( arg ) as Guild ?? FindByName( arg ) as Guild; - - if ( g != null ) - { - from.SendGump( new PropertiesGump( from, g ) ); - - if ( NewGuildSystem && from.AccessLevel >= AccessLevel.GameMaster && from is PlayerMobile mobile ) - mobile.SendGump( new GuildInfoGump( mobile, g ) ); - } - } - - } - - private class GuildPropsTarget : Target - { - public GuildPropsTarget() : base( -1, true, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object o ) - { - if ( !BaseCommand.IsAccessible( from, o ) ) - { - from.SendMessage( "That is not accessible." ); - return; - } - - Guild g = null; - - if ( o is Guildstone stone ) - { - if ( stone.Guild == null || stone.Guild.Disbanded ) - { - from.SendMessage( "The guild associated with that Guildstone no longer exists" ); - return; - } - - g = stone.Guild; - } - else if ( o is Mobile mobile ) - { - g = mobile.Guild as Guild; - } - - if (g == null) - { - from.SendMessage("That is not in a guild!"); - return; - } - - from.SendGump( new PropertiesGump( from, g ) ); - - if ( NewGuildSystem && from.AccessLevel >= AccessLevel.GameMaster && from is PlayerMobile pm ) - pm.SendGump( new GuildInfoGump( pm, g ) ); - } - } - #endregion - - #region EventSinks - public static void EventSink_GuildGumpRequest( GuildGumpRequestArgs args ) - { - if ( !NewGuildSystem || !(args.Mobile is PlayerMobile pm) ) - return; - - if ( pm.Guild == null ) - pm.SendGump( new CreateGuildGump( pm ) ); - else - pm.SendGump( new GuildInfoGump( pm, pm.Guild as Guild ) ); - } - - public static void EventSink_CreateGuild(CreateGuildEventArgs args) - { - args.Guild = new Guild(args.Id); - } - #endregion - - public static bool NewGuildSystem => Core.SE; - public static bool OrderChaos => !Core.SE; - - public static readonly int RegistrationFee = 25000; - public static readonly int AbbrevLimit = 4; - public static readonly int NameLimit = 40; - public static readonly int MajorityPercentage = 66; - public static readonly TimeSpan InactiveTime = TimeSpan.FromDays( 30 ); - - - #region New Alliances - - public AllianceInfo Alliance - { - get{ - if ( m_AllianceInfo != null ) - return m_AllianceInfo; - - return m_AllianceLeader?.m_AllianceInfo; - } - set - { - AllianceInfo current = Alliance; - - if ( value == current ) - return; - - current?.RemoveGuild( this ); - - if ( value != null ) - { - - if ( value.Leader == this ) - m_AllianceInfo = value; - else - m_AllianceLeader = value.Leader; - - value.AddPendingGuild( this ); - } - else - { - m_AllianceInfo = null; - m_AllianceLeader = null; - } - } - } - - [CommandProperty( AccessLevel.Counselor )] - public string AllianceName => Alliance?.Name; - - [CommandProperty( AccessLevel.Counselor )] - public Guild AllianceLeader => Alliance?.Leader; - - [CommandProperty( AccessLevel.Counselor )] - public bool IsAllianceMember => Alliance?.IsMember( this ) == true; - - [CommandProperty( AccessLevel.Counselor )] - public bool IsAlliancePendingMember => Alliance?.IsPendingMember( this ) == true; - - public static Guild GetAllianceLeader( Guild g ) - { - AllianceInfo alliance = g.Alliance; - - if ( alliance?.Leader != null && alliance.IsMember( g ) ) - return alliance.Leader; - - return g; - } - - #endregion - - #region New Wars - - public List PendingWars { get; private set; } - - public List AcceptedWars { get; private set; } - - - public WarDeclaration FindPendingWar( Guild g ) - { - for( int i = 0; i < PendingWars.Count; i++ ) - { - WarDeclaration w = PendingWars[i]; - - if ( w.Opponent == g ) - return w; - } - - return null; - } - - public WarDeclaration FindActiveWar( Guild g ) - { - for( int i = 0; i < AcceptedWars.Count; i++ ) - { - WarDeclaration w = AcceptedWars[i]; + #region Ranks + + [Flags] + public enum RankFlags + { + None = 0x00000000, + CanInvitePlayer = 0x00000001, + AccessGuildItems = 0x00000002, + RemoveLowestRank = 0x00000004, + RemovePlayers = 0x00000008, + CanPromoteDemote = 0x00000010, + ControlWarStatus = 0x00000020, + AllianceControl = 0x00000040, + CanSetGuildTitle = 0x00000080, + CanVote = 0x00000100, + + All = Member | CanInvitePlayer | RemovePlayers | CanPromoteDemote | ControlWarStatus | AllianceControl | + CanSetGuildTitle, + Member = RemoveLowestRank | AccessGuildItems | CanVote + } + + public class RankDefinition + { + public static RankDefinition[] Ranks = + { + new RankDefinition(1062963, 0, RankFlags.None), //Ronin + new RankDefinition(1062962, 1, RankFlags.Member), //Member + new RankDefinition(1062961, 2, + RankFlags.Member | RankFlags.RemovePlayers | RankFlags.CanInvitePlayer | RankFlags.CanSetGuildTitle | + RankFlags.CanPromoteDemote), //Emmissary + new RankDefinition(1062960, 3, RankFlags.Member | RankFlags.ControlWarStatus), //Warlord + new RankDefinition(1062959, 4, RankFlags.All) //Leader + }; + + public RankDefinition(TextDefinition name, int rank, RankFlags flags) + { + Name = name; + Rank = rank; + Flags = flags; + } + + public static RankDefinition Leader => Ranks[4]; + public static RankDefinition Member => Ranks[1]; + public static RankDefinition Lowest => Ranks[0]; + + public TextDefinition Name{ get; } + + public int Rank{ get; } + + public RankFlags Flags{ get; private set; } + + public bool GetFlag(RankFlags flag) + { + return (Flags & flag) != 0; + } + + public void SetFlag(RankFlags flag, bool value) + { + if (value) + Flags |= flag; + else + Flags &= ~flag; + } + } + + #endregion + + #region Alliances + + public class AllianceInfo + { + private Guild m_Leader; + private List m_Members; + private List m_PendingMembers; + + public AllianceInfo(Guild leader, string name, Guild partner) + { + m_Leader = leader; + Name = name; + + m_Members = new List(); + m_PendingMembers = new List(); + + leader.Alliance = this; + partner.Alliance = this; + + if (!Alliances.ContainsKey(Name.ToLower())) + Alliances.Add(Name.ToLower(), this); + } + + public AllianceInfo(GenericReader reader) + { + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Name = reader.ReadString(); + m_Leader = reader.ReadGuild() as Guild; + + m_Members = reader.ReadStrongGuildList(); + m_PendingMembers = reader.ReadStrongGuildList(); + + break; + } + } + } + + public static Dictionary Alliances{ get; } = new Dictionary(); + + public string Name{ get; } + + public Guild Leader + { + get + { + CheckLeader(); + return m_Leader; + } + set + { + if (m_Leader != value && value != null) + AllianceMessage(1070765, value.Name); // Your Alliance is now led by ~1_GUILDNAME~ + + m_Leader = value; + + if (m_Leader == null) + CalculateAllianceLeader(); + } + } + + public void CalculateAllianceLeader() + { + m_Leader = m_Members.Count >= 2 ? m_Members[Utility.Random(m_Members.Count)] : null; + } + + public void CheckLeader() + { + if (m_Leader == null || m_Leader.Disbanded) + { + CalculateAllianceLeader(); - if ( w.Opponent == g ) - return w; - } - - return null; - } - - public void CheckExpiredWars() - { - for( int i = 0; i < AcceptedWars.Count; i++ ) - { - WarDeclaration w = AcceptedWars[i]; - Guild g = w.Opponent; + if (m_Leader == null) + Disband(); + } + } + + public bool IsPendingMember(Guild g) + { + if (g.Alliance != this) + return false; + + return m_PendingMembers.Contains(g); + } + + public bool IsMember(Guild g) + { + if (g.Alliance != this) + return false; + + return m_Members.Contains(g); + } + + public void Serialize(GenericWriter writer) + { + writer.Write(0); //Version + + writer.Write(Name); + writer.Write(m_Leader); + + writer.WriteGuildList(m_Members, true); + writer.WriteGuildList(m_PendingMembers, true); + + if (!Alliances.ContainsKey(Name.ToLower())) + Alliances.Add(Name.ToLower(), this); + } + + public void AddPendingGuild(Guild g) + { + if (g.Alliance != this || m_PendingMembers.Contains(g) || m_Members.Contains(g)) + return; + + m_PendingMembers.Add(g); + } + + public void TurnToMember(Guild g) + { + if (g.Alliance != this || !m_PendingMembers.Contains(g) || m_Members.Contains(g)) + return; + + g.GuildMessage(1070760, Name); // Your Guild has joined the ~1_ALLIANCENAME~ Alliance. + AllianceMessage(1070761, g.Name); // A new Guild has joined your Alliance: ~1_GUILDNAME~ + + m_PendingMembers.Remove(g); + m_Members.Add(g); + g.Alliance.InvalidateMemberProperties(); + } + + public void RemoveGuild(Guild g) + { + if (m_PendingMembers.Contains(g)) m_PendingMembers.Remove(g); + + if (m_Members.Contains(g)) //Sanity, just incase someone with a custom script adds a character to BOTH arrays + { + m_Members.Remove(g); + g.InvalidateMemberProperties(); + + g.GuildMessage(1070763, Name); // Your Guild has been removed from the ~1_ALLIANCENAME~ Alliance. + AllianceMessage(1070764, g.Name); // A Guild has left your Alliance: ~1_GUILDNAME~ + } + + //g.Alliance = null; //NO G.Alliance call here. Set the Guild's Alliance to null, if you JUST use RemoveGuild, it removes it from the alliance, but doesn't remove the link from the guild to the alliance. setting g.Alliance will call this method. + //to check on OSI: have 3 guilds, make 2 of them a member, one pending. remove one of the memebers. alliance still exist? + //ANSWER: NO + + if (g == m_Leader) CalculateAllianceLeader(); + + if (m_Members.Count < 2) + Disband(); + } + + public void Disband() + { + AllianceMessage(1070762); // Your Alliance has dissolved. + + for (int i = 0; i < m_PendingMembers.Count; i++) + m_PendingMembers[i].Alliance = null; + + for (int i = 0; i < m_Members.Count; i++) + m_Members[i].Alliance = null; + + Alliances.TryGetValue(Name.ToLower(), out AllianceInfo aInfo); + + if (aInfo == this) + Alliances.Remove(Name.ToLower()); + } + + public void InvalidateMemberProperties() + { + InvalidateMemberProperties(false); + } + + public void InvalidateMemberProperties(bool onlyOPL) + { + for (int i = 0; i < m_Members.Count; i++) + { + Guild g = m_Members[i]; + + g.InvalidateMemberProperties(onlyOPL); + } + } + + public void InvalidateMemberNotoriety() + { + for (int i = 0; i < m_Members.Count; i++) + m_Members[i].InvalidateMemberNotoriety(); + } + + public class AllianceRosterGump : GuildDiplomacyGump + { + private AllianceInfo m_Alliance; + + public AllianceRosterGump(PlayerMobile pm, Guild g, AllianceInfo alliance) : base(pm, g, true, "", 0, + alliance.m_Members, alliance.Name) + { + m_Alliance = alliance; + } + + public AllianceRosterGump(PlayerMobile pm, Guild g, AllianceInfo alliance, IComparer currentComparer, + bool ascending, string filter, int startNumber) : base(pm, g, currentComparer, ascending, filter, + startNumber, alliance.m_Members, alliance.Name) + { + m_Alliance = alliance; + } + + protected override bool AllowAdvancedSearch => false; + + public override Gump GetResentGump(PlayerMobile pm, Guild g, IComparer comparer, bool ascending, + string filter, int startNumber) + { + return new AllianceRosterGump(pm, g, m_Alliance, comparer, ascending, filter, startNumber); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID != 8) //So that they can't get to the AdvancedSearch button + base.OnResponse(sender, info); + } + } + + #region Alliance[Text]Message(...) + + public void AllianceMessage(int num, bool append, string format, params object[] args) + { + AllianceMessage(num, append, string.Format(format, args)); + } + + public void AllianceMessage(int number) + { + for (int i = 0; i < m_Members.Count; ++i) + m_Members[i].GuildMessage(number); + } + + public void AllianceMessage(int number, string args) + { + AllianceMessage(number, args, 0x3B2); + } + + public void AllianceMessage(int number, string args, int hue) + { + for (int i = 0; i < m_Members.Count; ++i) + m_Members[i].GuildMessage(number, args, hue); + } + + public void AllianceMessage(int number, bool append, string affix) + { + AllianceMessage(number, append, affix, "", 0x3B2); + } + + public void AllianceMessage(int number, bool append, string affix, string args) + { + AllianceMessage(number, append, affix, args, 0x3B2); + } + + public void AllianceMessage(int number, bool append, string affix, string args, int hue) + { + for (int i = 0; i < m_Members.Count; ++i) + m_Members[i].GuildMessage(number, append, affix, args, hue); + } + + public void AllianceTextMessage(string text) + { + AllianceTextMessage(0x3B2, text); + } + + public void AllianceTextMessage(string format, params object[] args) + { + AllianceTextMessage(0x3B2, string.Format(format, args)); + } + + public void AllianceTextMessage(int hue, string text) + { + for (int i = 0; i < m_Members.Count; ++i) + m_Members[i].GuildTextMessage(hue, text); + } + + public void AllianceTextMessage(int hue, string format, params object[] args) + { + AllianceTextMessage(hue, string.Format(format, args)); + } + + public void AllianceChat(Mobile from, int hue, string text) + { + Packet p = null; + for (int i = 0; i < m_Members.Count; i++) + { + Guild g = m_Members[i]; + + for (int j = 0; j < g.Members.Count; j++) + { + Mobile m = g.Members[j]; + + NetState state = m.NetState; + + if (state != null) + { + if (p == null) + p = Packet.Acquire(new UnicodeMessage(from.Serial, from.Body, MessageType.Alliance, hue, 3, + from.Language, from.Name, text)); + + state.Send(p); + } + } + } + + Packet.Release(p); + } + + public void AllianceChat(Mobile from, string text) + { + PlayerMobile pm = from as PlayerMobile; + + AllianceChat(from, pm?.AllianceMessageHue ?? 0x3B2, text); + } + + #endregion + } + + #endregion + + #region Wars + + public enum WarStatus + { + InProgress = -1, + Win, + Lose, + Draw, + Pending + } + + public class WarDeclaration + { + public WarDeclaration(Guild g, Guild opponent, int maxKills, TimeSpan warLength, bool warRequester) + { + Guild = g; + MaxKills = maxKills; + Opponent = opponent; + WarLength = warLength; + WarRequester = warRequester; + } + + public WarDeclaration(GenericReader reader) + { + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Kills = reader.ReadInt(); + MaxKills = reader.ReadInt(); + + WarLength = reader.ReadTimeSpan(); + WarBeginning = reader.ReadDateTime(); + + Guild = reader.ReadGuild() as Guild; + Opponent = reader.ReadGuild() as Guild; + + WarRequester = reader.ReadBool(); + + break; + } + } + } + + public int Kills{ get; set; } + + public int MaxKills{ get; set; } + + public TimeSpan WarLength{ get; set; } + + public Guild Opponent{ get; } + + public Guild Guild{ get; } + + public DateTime WarBeginning{ get; set; } + + public bool WarRequester{ get; set; } + + public WarStatus Status + { + get + { + if (Opponent == null || Opponent.Disbanded) + return WarStatus.Win; + + if (Guild == null || Guild.Disbanded) + return WarStatus.Lose; + + WarDeclaration w = Opponent.FindActiveWar(Guild); - WarStatus status = w.Status; - - if ( status != WarStatus.InProgress ) - { - AllianceInfo myAlliance = Alliance; - bool inAlliance = myAlliance?.IsMember( this ) == true; + if (Opponent.FindPendingWar(Guild) != null && Guild.FindPendingWar(Opponent) != null) + return WarStatus.Pending; + + if (w == null) + return WarStatus.Win; - AllianceInfo otherAlliance = g?.Alliance; - bool otherInAlliance = ( otherAlliance != null && otherAlliance.IsMember( this ) ); + if (WarLength != TimeSpan.Zero && WarBeginning + WarLength < DateTime.UtcNow) + { + if (Kills > w.Kills) + return WarStatus.Win; + if (Kills < w.Kills) + return WarStatus.Lose; + return WarStatus.Draw; + } - if ( inAlliance ) - { - myAlliance.AllianceMessage( 1070739 + (int)status, (g == null) ? "a deleted opponent" : (otherInAlliance ? otherAlliance.Name : g.Name) ); - myAlliance.InvalidateMemberProperties(); - } - else - { - GuildMessage( 1070739 + (int)status, (g == null) ? "a deleted opponent" : (otherInAlliance ? otherAlliance.Name : g.Name) ); - InvalidateMemberProperties(); - } - - AcceptedWars.Remove( w ); - - if ( g != null ) - { - if ( status != WarStatus.Draw ) - status = (WarStatus)((int)status + 1 % 2); + if (MaxKills > 0) + { + if (Kills >= MaxKills) + return WarStatus.Win; + if (w.Kills >= w.MaxKills) + return WarStatus.Lose; + } - if ( otherInAlliance ) - { - otherAlliance.AllianceMessage( 1070739 + (int)status, ( inAlliance ? Alliance.Name : Name ) ); - otherAlliance.InvalidateMemberProperties(); - } - else - { - g.GuildMessage( 1070739 + (int)status, (inAlliance ? Alliance.Name : Name) ); - g.InvalidateMemberProperties(); - } + return WarStatus.InProgress; + } + } + + public void Serialize(GenericWriter writer) + { + writer.Write(0); //version + + writer.Write(Kills); + writer.Write(MaxKills); + + writer.Write(WarLength); + writer.Write(WarBeginning); - g.AcceptedWars.Remove( g.FindActiveWar( this ) ); - } - } - } + writer.Write(Guild); + writer.Write(Opponent); + + writer.Write(WarRequester); + } + } - for( int i = 0; i < PendingWars.Count; i++ ) - { - WarDeclaration w = PendingWars[i]; - Guild g = w.Opponent; - - if ( w.Status != WarStatus.Pending ) - { - //All sanity in here - PendingWars.Remove( w ); - - g?.PendingWars.Remove( g.FindPendingWar( this ) ); - } - } - } - - public static void HandleDeath( Mobile victim ) - { - HandleDeath( victim, null ); - } - - public static void HandleDeath( Mobile victim, Mobile killer ) - { - if ( !NewGuildSystem ) - return; - - if ( killer == null ) - killer = victim.FindMostRecentDamager( false ); - - if ( killer == null || victim.Guild == null || killer.Guild == null ) - return; - - Guild victimGuild = GetAllianceLeader( victim.Guild as Guild ); - Guild killerGuild = GetAllianceLeader( killer.Guild as Guild ); - - WarDeclaration war = killerGuild.FindActiveWar( victimGuild ); - - if ( war == null ) - return; - - war.Kills++; - - if ( war.Opponent == victimGuild ) - killerGuild.CheckExpiredWars(); - else - victimGuild.CheckExpiredWars(); - } - #endregion - - #region Var declarations - private Mobile m_Leader; - - private string m_Name; - private string m_Abbreviation; - - private GuildType m_Type; - - private AllianceInfo m_AllianceInfo; - private Guild m_AllianceLeader; - #endregion - - public Guild( Mobile leader, string name, string abbreviation ) - { - #region Ctor mumbo-jumbo - m_Leader = leader; - - Members = new List(); - Allies = new List(); - Enemies = new List(); - WarDeclarations = new List(); - WarInvitations = new List(); - AllyDeclarations = new List(); - AllyInvitations = new List(); - Candidates = new List(); - Accepted = new List(); - - LastFealty = DateTime.UtcNow; - - m_Name = name; - m_Abbreviation = abbreviation; - - TypeLastChange = DateTime.MinValue; - - AddMember( m_Leader ); - - if ( m_Leader is PlayerMobile mobile ) - mobile.GuildRank = RankDefinition.Leader; - - AcceptedWars = new List(); - PendingWars = new List(); - #endregion - } - - public Guild( int id ) : base( id )//serialization ctor - { - } - - public void InvalidateMemberProperties( bool onlyOPL = false) - { - if ( Members != null ) - { - for ( int i = 0; i < Members.Count; i++ ) - { - Mobile m = Members[i]; - m.InvalidateProperties(); + public class WarTimer : Timer + { + private static TimeSpan InternalDelay = TimeSpan.FromMinutes(1.0); - if ( !onlyOPL ) - m.Delta( MobileDelta.Noto ); - } - } - } + public WarTimer() : base(InternalDelay, InternalDelay) + { + Priority = TimerPriority.FiveSeconds; + } - public void InvalidateMemberNotoriety() - { - if ( Members != null ) - { - for (int i=0; i < Members.Count; i++) - Members[i].Delta( MobileDelta.Noto ); - } - } + public static void Initialize() + { + if (Guild.NewGuildSystem) + new WarTimer().Start(); + } - public void InvalidateWarNotoriety() - { - Guild g = GetAllianceLeader( this ); + protected override void OnTick() + { + foreach (Guild g in BaseGuild.List.Values) + g.CheckExpiredWars(); + } + } - if ( g.Alliance != null ) - g.Alliance.InvalidateMemberNotoriety(); - else - g.InvalidateMemberNotoriety(); + #endregion - if ( g.AcceptedWars == null ) - return; + public class Guild : BaseGuild + { + public static readonly int RegistrationFee = 25000; + public static readonly int AbbrevLimit = 4; + public static readonly int NameLimit = 40; + public static readonly int MajorityPercentage = 66; + public static readonly TimeSpan InactiveTime = TimeSpan.FromDays(30); - foreach ( WarDeclaration warDec in g.AcceptedWars ) - { - Guild opponent = warDec.Opponent; + public Guild(Mobile leader, string name, string abbreviation) + { + #region Ctor mumbo-jumbo + + m_Leader = leader; + + Members = new List(); + Allies = new List(); + Enemies = new List(); + WarDeclarations = new List(); + WarInvitations = new List(); + AllyDeclarations = new List(); + AllyInvitations = new List(); + Candidates = new List(); + Accepted = new List(); + + LastFealty = DateTime.UtcNow; + + m_Name = name; + m_Abbreviation = abbreviation; + + TypeLastChange = DateTime.MinValue; + + AddMember(m_Leader); + + if (m_Leader is PlayerMobile mobile) + mobile.GuildRank = RankDefinition.Leader; + + AcceptedWars = new List(); + PendingWars = new List(); + + #endregion + } + + public Guild(int id) : base(id) //serialization ctor + { + } + + public static bool NewGuildSystem => Core.SE; + public static bool OrderChaos => !Core.SE; + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Leader + { + get + { + if (m_Leader == null || m_Leader.Deleted || m_Leader.Guild != this) + CalculateGuildmaster(); - if ( opponent.Alliance != null ) - opponent.Alliance.InvalidateMemberNotoriety(); - else - opponent.InvalidateMemberNotoriety(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Leader - { - get - { - if ( m_Leader == null || m_Leader.Deleted || m_Leader.Guild != this ) - CalculateGuildmaster(); + return m_Leader; + } + set + { + if (value != null) + AddMember(value); //Also removes from old guild. - return m_Leader; - } - set - { - if ( value != null ) - AddMember( value ); //Also removes from old guild. - - if ( m_Leader is PlayerMobile leader && leader?.Guild == this ) - leader.GuildRank = RankDefinition.Member; - - m_Leader = value; - - if ( m_Leader is PlayerMobile mobile ) - mobile.GuildRank = RankDefinition.Leader; - } - } + if (m_Leader is PlayerMobile leader && leader?.Guild == this) + leader.GuildRank = RankDefinition.Member; + m_Leader = value; - public override bool Disbanded => ( m_Leader == null || m_Leader.Deleted ); + if (m_Leader is PlayerMobile mobile) + mobile.GuildRank = RankDefinition.Leader; + } + } - public override void OnDelete( Mobile mob ) - { - RemoveMember( mob ); - } + public override bool Disbanded => m_Leader == null || m_Leader.Deleted; - public void Disband() - { - m_Leader = null; + public static void Configure() + { + EventSink.CreateGuild += EventSink_CreateGuild; + EventSink.GuildGumpRequest += EventSink_GuildGumpRequest; - List.Remove( Id ); + CommandSystem.Register("GuildProps", AccessLevel.Counselor, GuildProps_OnCommand); + } - foreach ( Mobile m in Members ) - { - m.SendLocalizedMessage( 502131 ); // Your guild has disbanded. + public void InvalidateMemberProperties(bool onlyOPL = false) + { + if (Members != null) + for (int i = 0; i < Members.Count; i++) + { + Mobile m = Members[i]; + m.InvalidateProperties(); + + if (!onlyOPL) + m.Delta(MobileDelta.Noto); + } + } - if ( m is PlayerMobile mobile ) - mobile.GuildRank = RankDefinition.Lowest; + public void InvalidateMemberNotoriety() + { + if (Members != null) + for (int i = 0; i < Members.Count; i++) + Members[i].Delta(MobileDelta.Noto); + } + + public void InvalidateWarNotoriety() + { + Guild g = GetAllianceLeader(this); + + if (g.Alliance != null) + g.Alliance.InvalidateMemberNotoriety(); + else + g.InvalidateMemberNotoriety(); + + if (g.AcceptedWars == null) + return; + + foreach (WarDeclaration warDec in g.AcceptedWars) + { + Guild opponent = warDec.Opponent; + + if (opponent.Alliance != null) + opponent.Alliance.InvalidateMemberNotoriety(); + else + opponent.InvalidateMemberNotoriety(); + } + } + + public override void OnDelete(Mobile mob) + { + RemoveMember(mob); + } + + + public void Disband() + { + m_Leader = null; + + List.Remove(Id); + + foreach (Mobile m in Members) + { + m.SendLocalizedMessage(502131); // Your guild has disbanded. + + if (m is PlayerMobile mobile) + mobile.GuildRank = RankDefinition.Lowest; + + m.Guild = null; + } + + Members.Clear(); + + for (int i = Allies.Count - 1; i >= 0; --i) + if (i < Allies.Count) + RemoveAlly(Allies[i]); + + for (int i = Enemies.Count - 1; i >= 0; --i) + if (i < Enemies.Count) + RemoveEnemy(Enemies[i]); + + if (!NewGuildSystem) + Guildstone?.Delete(); + + Guildstone = null; + + CheckExpiredWars(); + + Alliance = null; + } + + #region GuildProps + + [Usage("GuildProps")] + [Description( + "Opens a menu where you can view and edit guild properties of a targeted player or guild stone. If the new Guild system is active, also brings up the guild gump.")] + private static void GuildProps_OnCommand(CommandEventArgs e) + { + string arg = e.ArgString.Trim(); + Mobile from = e.Mobile; + + if (arg.Length == 0) + { + e.Mobile.Target = new GuildPropsTarget(); + } + else + { + Guild g = int.TryParse(arg, out int id) + ? Find(id) as Guild + : FindByAbbrev(arg) as Guild ?? FindByName(arg) as Guild; + + if (g != null) + { + from.SendGump(new PropertiesGump(from, g)); + + if (NewGuildSystem && from.AccessLevel >= AccessLevel.GameMaster && from is PlayerMobile mobile) + mobile.SendGump(new GuildInfoGump(mobile, g)); + } + } + } + + private class GuildPropsTarget : Target + { + public GuildPropsTarget() : base(-1, true, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object o) + { + if (!BaseCommand.IsAccessible(from, o)) + { + from.SendMessage("That is not accessible."); + return; + } + + Guild g = null; + + if (o is Guildstone stone) + { + if (stone.Guild == null || stone.Guild.Disbanded) + { + from.SendMessage("The guild associated with that Guildstone no longer exists"); + return; + } + + g = stone.Guild; + } + else if (o is Mobile mobile) + { + g = mobile.Guild as Guild; + } - m.Guild = null; - } + if (g == null) + { + from.SendMessage("That is not in a guild!"); + return; + } - Members.Clear(); + from.SendGump(new PropertiesGump(from, g)); - for ( int i = Allies.Count - 1; i >= 0; --i ) - if ( i < Allies.Count ) - RemoveAlly( Allies[i] ); + if (NewGuildSystem && from.AccessLevel >= AccessLevel.GameMaster && from is PlayerMobile pm) + pm.SendGump(new GuildInfoGump(pm, g)); + } + } - for ( int i = Enemies.Count - 1; i >= 0; --i ) - if ( i < Enemies.Count ) - RemoveEnemy( Enemies[i] ); + #endregion - if ( !NewGuildSystem ) - Guildstone?.Delete(); + #region EventSinks - Guildstone = null; + public static void EventSink_GuildGumpRequest(GuildGumpRequestArgs args) + { + if (!NewGuildSystem || !(args.Mobile is PlayerMobile pm)) + return; + + if (pm.Guild == null) + pm.SendGump(new CreateGuildGump(pm)); + else + pm.SendGump(new GuildInfoGump(pm, pm.Guild as Guild)); + } + + public static void EventSink_CreateGuild(CreateGuildEventArgs args) + { + args.Guild = new Guild(args.Id); + } + + #endregion + + + #region New Alliances + + public AllianceInfo Alliance + { + get + { + if (m_AllianceInfo != null) + return m_AllianceInfo; + + return m_AllianceLeader?.m_AllianceInfo; + } + set + { + AllianceInfo current = Alliance; + + if (value == current) + return; + + current?.RemoveGuild(this); + + if (value != null) + { + if (value.Leader == this) + m_AllianceInfo = value; + else + m_AllianceLeader = value.Leader; + + value.AddPendingGuild(this); + } + else + { + m_AllianceInfo = null; + m_AllianceLeader = null; + } + } + } + + [CommandProperty(AccessLevel.Counselor)] + public string AllianceName => Alliance?.Name; + + [CommandProperty(AccessLevel.Counselor)] + public Guild AllianceLeader => Alliance?.Leader; + + [CommandProperty(AccessLevel.Counselor)] + public bool IsAllianceMember => Alliance?.IsMember(this) == true; + + [CommandProperty(AccessLevel.Counselor)] + public bool IsAlliancePendingMember => Alliance?.IsPendingMember(this) == true; + + public static Guild GetAllianceLeader(Guild g) + { + AllianceInfo alliance = g.Alliance; + + if (alliance?.Leader != null && alliance.IsMember(g)) + return alliance.Leader; + + return g; + } + + #endregion + + #region New Wars + + public List PendingWars{ get; private set; } + + public List AcceptedWars{ get; private set; } + + + public WarDeclaration FindPendingWar(Guild g) + { + for (int i = 0; i < PendingWars.Count; i++) + { + WarDeclaration w = PendingWars[i]; + + if (w.Opponent == g) + return w; + } + + return null; + } + + public WarDeclaration FindActiveWar(Guild g) + { + for (int i = 0; i < AcceptedWars.Count; i++) + { + WarDeclaration w = AcceptedWars[i]; + + if (w.Opponent == g) + return w; + } + + return null; + } + + public void CheckExpiredWars() + { + for (int i = 0; i < AcceptedWars.Count; i++) + { + WarDeclaration w = AcceptedWars[i]; + Guild g = w.Opponent; + + WarStatus status = w.Status; + + if (status != WarStatus.InProgress) + { + AllianceInfo myAlliance = Alliance; + bool inAlliance = myAlliance?.IsMember(this) == true; - CheckExpiredWars(); + AllianceInfo otherAlliance = g?.Alliance; + bool otherInAlliance = otherAlliance != null && otherAlliance.IsMember(this); - Alliance = null; - } + if (inAlliance) + { + myAlliance.AllianceMessage(1070739 + (int)status, + g == null ? "a deleted opponent" : otherInAlliance ? otherAlliance.Name : g.Name); + myAlliance.InvalidateMemberProperties(); + } + else + { + GuildMessage(1070739 + (int)status, + g == null ? "a deleted opponent" : otherInAlliance ? otherAlliance.Name : g.Name); + InvalidateMemberProperties(); + } - #region Is(...) - public bool IsMember( Mobile m ) - { - return Members.Contains( m ); - } + AcceptedWars.Remove(w); - public bool IsAlly( Guild g ) - { - if ( NewGuildSystem ) - { - return (Alliance != null && Alliance.IsMember( this ) && Alliance.IsMember( g )); - } + if (g != null) + { + if (status != WarStatus.Draw) + status = (WarStatus)((int)status + 1 % 2); - return Allies.Contains( g ); - } + if (otherInAlliance) + { + otherAlliance.AllianceMessage(1070739 + (int)status, inAlliance ? Alliance.Name : Name); + otherAlliance.InvalidateMemberProperties(); + } + else + { + g.GuildMessage(1070739 + (int)status, inAlliance ? Alliance.Name : Name); + g.InvalidateMemberProperties(); + } - public bool IsEnemy( Guild g ) - { - if ( Type != GuildType.Regular && g.Type != GuildType.Regular && Type != g.Type ) - return true; + g.AcceptedWars.Remove(g.FindActiveWar(this)); + } + } + } - return IsWar( g ); - } + for (int i = 0; i < PendingWars.Count; i++) + { + WarDeclaration w = PendingWars[i]; + Guild g = w.Opponent; - public bool IsWar( Guild g ) - { - if ( g == null ) - return false; + if (w.Status != WarStatus.Pending) + { + //All sanity in here + PendingWars.Remove(w); - if ( NewGuildSystem ) - { - Guild guild = GetAllianceLeader( this ); - Guild otherGuild = GetAllianceLeader( g ); + g?.PendingWars.Remove(g.FindPendingWar(this)); + } + } + } - if ( guild.FindActiveWar( otherGuild ) != null ) - return true; + public static void HandleDeath(Mobile victim) + { + HandleDeath(victim, null); + } - return false; - } + public static void HandleDeath(Mobile victim, Mobile killer) + { + if (!NewGuildSystem) + return; - return Enemies.Contains( g ); - } - #endregion + if (killer == null) + killer = victim.FindMostRecentDamager(false); - #region Serialization - public override void Serialize( GenericWriter writer ) - { - if ( LastFealty+TimeSpan.FromDays( 1.0 ) < DateTime.UtcNow ) - CalculateGuildmaster(); + if (killer == null || victim.Guild == null || killer.Guild == null) + return; - CheckExpiredWars(); + Guild victimGuild = GetAllianceLeader(victim.Guild as Guild); + Guild killerGuild = GetAllianceLeader(killer.Guild as Guild); - Alliance?.CheckLeader(); + WarDeclaration war = killerGuild.FindActiveWar(victimGuild); - writer.Write( (int) 5 );//version + if (war == null) + return; - #region War Serialization - writer.Write( PendingWars.Count ); + war.Kills++; - for( int i = 0; i < PendingWars.Count; i++ ) - { - PendingWars[i].Serialize( writer ); - } + if (war.Opponent == victimGuild) + killerGuild.CheckExpiredWars(); + else + victimGuild.CheckExpiredWars(); + } - writer.Write( AcceptedWars.Count ); + #endregion - for( int i = 0; i < AcceptedWars.Count; i++ ) - { - AcceptedWars[i].Serialize( writer ); - } - #endregion + #region Var declarations - #region Alliances + private Mobile m_Leader; - bool isAllianceLeader = (m_AllianceLeader == null && m_AllianceInfo != null ); - writer.Write( isAllianceLeader ); + private string m_Name; + private string m_Abbreviation; - if ( isAllianceLeader ) - m_AllianceInfo.Serialize( writer ); - else - writer.Write( m_AllianceLeader ); + private GuildType m_Type; - #endregion + private AllianceInfo m_AllianceInfo; + private Guild m_AllianceLeader; - // + #endregion - writer.WriteGuildList( AllyDeclarations, true ); - writer.WriteGuildList( AllyInvitations, true ); + #region Is(...) - writer.Write( TypeLastChange ); + public bool IsMember(Mobile m) + { + return Members.Contains(m); + } - writer.Write( (int)m_Type ); + public bool IsAlly(Guild g) + { + if (NewGuildSystem) return Alliance != null && Alliance.IsMember(this) && Alliance.IsMember(g); - writer.Write( LastFealty ); + return Allies.Contains(g); + } - writer.Write( m_Leader ); - writer.Write( m_Name ); - writer.Write( m_Abbreviation ); + public bool IsEnemy(Guild g) + { + if (Type != GuildType.Regular && g.Type != GuildType.Regular && Type != g.Type) + return true; - writer.WriteGuildList( Allies, true ); - writer.WriteGuildList( Enemies, true ); - writer.WriteGuildList( WarDeclarations, true ); - writer.WriteGuildList( WarInvitations, true ); + return IsWar(g); + } - writer.Write( Members, true ); - writer.Write( Candidates, true ); - writer.Write( Accepted, true ); + public bool IsWar(Guild g) + { + if (g == null) + return false; - writer.Write( Guildstone ); - writer.Write( Teleporter ); + if (NewGuildSystem) + { + Guild guild = GetAllianceLeader(this); + Guild otherGuild = GetAllianceLeader(g); - writer.Write( Charter ); - writer.Write( Website ); - } + if (guild.FindActiveWar(otherGuild) != null) + return true; - public override void Deserialize( GenericReader reader ) - { - int version = reader.ReadInt(); + return false; + } - switch ( version ) - { - case 5: - { - int count = reader.ReadInt(); + return Enemies.Contains(g); + } - PendingWars = new List(); - for( int i = 0; i < count; i++ ) - { - PendingWars.Add( new WarDeclaration( reader ) ); - } + #endregion - count = reader.ReadInt(); - AcceptedWars = new List(); - for( int i = 0; i < count; i++ ) - { - AcceptedWars.Add( new WarDeclaration( reader ) ); - } + #region Serialization - bool isAllianceLeader = reader.ReadBool(); + public override void Serialize(GenericWriter writer) + { + if (LastFealty + TimeSpan.FromDays(1.0) < DateTime.UtcNow) + CalculateGuildmaster(); - if ( isAllianceLeader ) - m_AllianceInfo = new AllianceInfo( reader ); - else - m_AllianceLeader = reader.ReadGuild() as Guild; + CheckExpiredWars(); + Alliance?.CheckLeader(); - goto case 4; - } - case 4: - { - AllyDeclarations = reader.ReadStrongGuildList(); - AllyInvitations = reader.ReadStrongGuildList(); + writer.Write(5); //version - goto case 3; - } - case 3: - { - TypeLastChange = reader.ReadDateTime(); + #region War Serialization - goto case 2; - } - case 2: - { - m_Type = (GuildType)reader.ReadInt(); + writer.Write(PendingWars.Count); - goto case 1; - } - case 1: - { - LastFealty = reader.ReadDateTime(); + for (int i = 0; i < PendingWars.Count; i++) PendingWars[i].Serialize(writer); - goto case 0; - } - case 0: - { - m_Leader = reader.ReadMobile(); + writer.Write(AcceptedWars.Count); - if ( m_Leader is PlayerMobile mobile ) - mobile.GuildRank = RankDefinition.Leader; + for (int i = 0; i < AcceptedWars.Count; i++) AcceptedWars[i].Serialize(writer); - m_Name = reader.ReadString(); - m_Abbreviation = reader.ReadString(); + #endregion - Allies = reader.ReadStrongGuildList(); - Enemies = reader.ReadStrongGuildList(); - WarDeclarations = reader.ReadStrongGuildList(); - WarInvitations = reader.ReadStrongGuildList(); + #region Alliances - Members = reader.ReadStrongMobileList(); - Candidates = reader.ReadStrongMobileList(); - Accepted = reader.ReadStrongMobileList(); + bool isAllianceLeader = m_AllianceLeader == null && m_AllianceInfo != null; + writer.Write(isAllianceLeader); - Guildstone = reader.ReadItem(); - Teleporter = reader.ReadItem(); + if (isAllianceLeader) + m_AllianceInfo.Serialize(writer); + else + writer.Write(m_AllianceLeader); - Charter = reader.ReadString(); - Website = reader.ReadString(); + #endregion - break; - } - } + // - if ( AllyDeclarations == null ) - AllyDeclarations = new List(); + writer.WriteGuildList(AllyDeclarations, true); + writer.WriteGuildList(AllyInvitations, true); - if ( AllyInvitations == null ) - AllyInvitations = new List(); + writer.Write(TypeLastChange); + writer.Write((int)m_Type); - if ( AcceptedWars == null ) - AcceptedWars = new List(); + writer.Write(LastFealty); - if ( PendingWars == null ) - PendingWars = new List(); + writer.Write(m_Leader); + writer.Write(m_Name); + writer.Write(m_Abbreviation); + writer.WriteGuildList(Allies, true); + writer.WriteGuildList(Enemies, true); + writer.WriteGuildList(WarDeclarations, true); + writer.WriteGuildList(WarInvitations, true); - /* - if ( ( !NewGuildSystem && m_Guildstone == null )|| m_Members.Count == 0 ) - Disband(); - */ + writer.Write(Members, true); + writer.Write(Candidates, true); + writer.Write(Accepted, true); - Timer.DelayCall( TimeSpan.Zero, VerifyGuild_Callback ); - } + writer.Write(Guildstone); + writer.Write(Teleporter); - private void VerifyGuild_Callback() - { - if ( (!NewGuildSystem && Guildstone == null) || Members.Count == 0 ) - Disband(); + writer.Write(Charter); + writer.Write(Website); + } - CheckExpiredWars(); + public override void Deserialize(GenericReader reader) + { + int version = reader.ReadInt(); - AllianceInfo alliance = Alliance; + switch (version) + { + case 5: + { + int count = reader.ReadInt(); - alliance?.CheckLeader(); + PendingWars = new List(); + for (int i = 0; i < count; i++) PendingWars.Add(new WarDeclaration(reader)); - alliance = Alliance; //CheckLeader could possibly change the value of this.Alliance + count = reader.ReadInt(); + AcceptedWars = new List(); + for (int i = 0; i < count; i++) AcceptedWars.Add(new WarDeclaration(reader)); - if ( alliance != null && !alliance.IsMember( this ) && !alliance.IsPendingMember( this ) ) //This block is there to fix a bug in the code in an older version. - Alliance = null; //Will call Alliance.RemoveGuild which will set it null & perform all the pertient checks as far as alliacne disbanding + bool isAllianceLeader = reader.ReadBool(); - } + if (isAllianceLeader) + m_AllianceInfo = new AllianceInfo(reader); + else + m_AllianceLeader = reader.ReadGuild() as Guild; - #endregion - #region Add/Remove Member/Old Ally/Old Enemy - public void AddMember( Mobile m ) - { - if ( !Members.Contains( m ) ) - { - if ( m.Guild != null && m.Guild != this ) - ((Guild)m.Guild).RemoveMember( m ); + goto case 4; + } + case 4: + { + AllyDeclarations = reader.ReadStrongGuildList(); + AllyInvitations = reader.ReadStrongGuildList(); - Members.Add( m ); - m.Guild = this; + goto case 3; + } + case 3: + { + TypeLastChange = reader.ReadDateTime(); - if ( !NewGuildSystem ) - m.GuildFealty = m_Leader; - else - m.GuildFealty = null; + goto case 2; + } + case 2: + { + m_Type = (GuildType)reader.ReadInt(); - if ( m is PlayerMobile mobile ) - mobile.GuildRank = RankDefinition.Lowest; + goto case 1; + } + case 1: + { + LastFealty = reader.ReadDateTime(); - ((Guild)m.Guild).InvalidateWarNotoriety(); - } - } + goto case 0; + } + case 0: + { + m_Leader = reader.ReadMobile(); - public void RemoveMember( Mobile m ) - { - RemoveMember( m, 1018028 ); // You have been dismissed from your guild. - } - public void RemoveMember( Mobile m, int message ) - { - if ( Members.Contains( m ) ) - { - Members.Remove( m ); + if (m_Leader is PlayerMobile mobile) + mobile.GuildRank = RankDefinition.Leader; - Guild guild = m.Guild as Guild; + m_Name = reader.ReadString(); + m_Abbreviation = reader.ReadString(); - m.Guild = null; - - if ( m is PlayerMobile mobile ) - mobile.GuildRank = RankDefinition.Lowest; - - if ( message > 0 ) - m.SendLocalizedMessage( message ); - - if ( m == m_Leader ) - { - CalculateGuildmaster(); - - if ( m_Leader == null ) - Disband(); - } - - if ( Members.Count == 0 ) - Disband(); - - guild?.InvalidateWarNotoriety(); - - m.Delta( MobileDelta.Noto ); - } - } - - public void AddAlly( Guild g ) - { - if ( !Allies.Contains( g ) ) - { - Allies.Add( g ); - - g.AddAlly( this ); - } - } - - public void RemoveAlly( Guild g ) - { - if ( Allies.Contains( g ) ) - { - Allies.Remove( g ); - - g.RemoveAlly( this ); - } - } - - public void AddEnemy( Guild g ) - { - if ( !Enemies.Contains( g ) ) - { - Enemies.Add( g ); - - g.AddEnemy( this ); - } - } - - public void RemoveEnemy( Guild g ) - { - if ( Enemies != null && Enemies.Contains( g ) ) - { - Enemies.Remove( g ); - - g.RemoveEnemy( this ); - } - } - - #endregion - - #region Guild[Text]Message(...) - public void GuildMessage( int num, bool append, string format, params object[] args ) - { - GuildMessage( num, append, string.Format( format, args) ); - } - public void GuildMessage( int number ) - { - for ( int i = 0; i < Members.Count; ++i ) - Members[i].SendLocalizedMessage( number ); - } - - public void GuildMessage( int number, string args, int hue = 0x3B2) - { - for ( int i = 0; i < Members.Count; ++i ) - Members[i].SendLocalizedMessage( number, args, hue ); - } - - public void GuildMessage( int number, bool append, string affix, string args = "", int hue = 0x3B2) - { - for ( int i = 0; i < Members.Count; ++i ) - Members[i].SendLocalizedMessage( number, append, affix, args, hue ); - } - - public void GuildTextMessage( string text ) - { - GuildTextMessage( 0x3B2, text ); - } - public void GuildTextMessage( string format, params object[] args ) - { - GuildTextMessage( 0x3B2, string.Format( format, args ) ); - } - public void GuildTextMessage( int hue, string text ) - { - for( int i = 0; i < Members.Count; ++i ) - Members[i].SendMessage( hue, text ); - } - public void GuildTextMessage( int hue, string format, params object[] args ) - { - GuildTextMessage( hue, string.Format( format, args ) ); - } - - public void GuildChat( Mobile from, int hue, string text ) - { - Packet p = null; - for ( int i = 0; i < Members.Count; i++ ) - { - Mobile m = Members[i]; - - NetState state = m.NetState; - - if ( state != null ) - { - if ( p == null ) - p = Packet.Acquire( new UnicodeMessage( from.Serial, from.Body, MessageType.Guild, hue, 3, from.Language, from.Name, text ) ); - - state.Send( p ); - } - } - - Packet.Release( p ); - } - - public void GuildChat( Mobile from, string text ) - { - PlayerMobile pm = from as PlayerMobile; - - GuildChat( from, pm?.GuildMessageHue ?? 0x3B2, text ); - } - #endregion - - #region Voting - public bool CanVote( Mobile m ) - { - if ( NewGuildSystem ) - { - if ( !(m is PlayerMobile pm) || !pm.GuildRank.GetFlag( RankFlags.CanVote ) ) - return false; - } - - return ( m != null && !m.Deleted && m.Guild == this ); - } - public bool CanBeVotedFor( Mobile m ) - { - if ( NewGuildSystem ) - { - if ( !(m is PlayerMobile pm) || pm.LastOnline + InactiveTime < DateTime.UtcNow ) - return false; - } - - return ( m != null && !m.Deleted && m.Guild == this ); - } - - public void CalculateGuildmaster() - { - Dictionary votes = new Dictionary(); - - int votingMembers = 0; - - for ( int i = 0; Members != null && i < Members.Count; ++i ) - { - Mobile memb = Members[i]; - - if ( !CanVote( memb ) ) - continue; - - Mobile m = memb.GuildFealty; - - if ( !CanBeVotedFor( m ) ) - { - if ( m_Leader != null && !m_Leader.Deleted && m_Leader.Guild == this ) - m = m_Leader; - else - m = memb; - } - - if ( m == null ) - continue; - - if ( !votes.TryGetValue( m, out int v ) ) - votes[m] = 1; - else - votes[m] = v + 1; - - votingMembers++; - } - - Mobile winner = null; - int highVotes = 0; - - foreach ( KeyValuePair kvp in votes ) - { - Mobile m = kvp.Key; - int val = kvp.Value; + Allies = reader.ReadStrongGuildList(); + Enemies = reader.ReadStrongGuildList(); + WarDeclarations = reader.ReadStrongGuildList(); + WarInvitations = reader.ReadStrongGuildList(); - if ( winner == null || val > highVotes ) - { - winner = m; - highVotes = val; - } - } + Members = reader.ReadStrongMobileList(); + Candidates = reader.ReadStrongMobileList(); + Accepted = reader.ReadStrongMobileList(); - if ( NewGuildSystem && (highVotes * 100) / Math.Max( votingMembers, 1 ) < MajorityPercentage && m_Leader != null && winner != m_Leader && !m_Leader.Deleted && m_Leader.Guild == this ) - winner = m_Leader; + Guildstone = reader.ReadItem(); + Teleporter = reader.ReadItem(); - if ( m_Leader != winner && winner != null ) - GuildMessage( 1018015, true, winner.Name ); // Guild Message: Guildmaster changed to: + Charter = reader.ReadString(); + Website = reader.ReadString(); - Leader = winner; - LastFealty = DateTime.UtcNow; - } + break; + } + } - #endregion + if (AllyDeclarations == null) + AllyDeclarations = new List(); - #region Getters & Setters - [CommandProperty( AccessLevel.GameMaster )] - public Item Guildstone { get; set; } + if (AllyInvitations == null) + AllyInvitations = new List(); - [CommandProperty( AccessLevel.GameMaster )] - public Item Teleporter { get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public override string Name - { - get => m_Name; - set - { - m_Name = value; + if (AcceptedWars == null) + AcceptedWars = new List(); - InvalidateMemberProperties( true ); + if (PendingWars == null) + PendingWars = new List(); - Guildstone?.InvalidateProperties(); - } - } - [CommandProperty( AccessLevel.GameMaster )] - public string Website { get; set; } + /* + if ( ( !NewGuildSystem && m_Guildstone == null )|| m_Members.Count == 0 ) + Disband(); + */ - [CommandProperty( AccessLevel.GameMaster )] - public override string Abbreviation - { - get => m_Abbreviation; - set - { - m_Abbreviation = value; + Timer.DelayCall(TimeSpan.Zero, VerifyGuild_Callback); + } - InvalidateMemberProperties( true ); + private void VerifyGuild_Callback() + { + if (!NewGuildSystem && Guildstone == null || Members.Count == 0) + Disband(); - Guildstone?.InvalidateProperties(); - } - } + CheckExpiredWars(); - [CommandProperty( AccessLevel.GameMaster )] - public string Charter { get; set; } + AllianceInfo alliance = Alliance; - [CommandProperty( AccessLevel.GameMaster )] - public override GuildType Type - { - get => OrderChaos ? m_Type : GuildType.Regular; - set - { - if ( m_Type != value ) - { - m_Type = value; - TypeLastChange = DateTime.UtcNow; + alliance?.CheckLeader(); - InvalidateMemberProperties(); - } - } - } + alliance = Alliance; //CheckLeader could possibly change the value of this.Alliance - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastFealty { get; set; } + if (alliance != null && !alliance.IsMember(this) && !alliance.IsPendingMember(this) + ) //This block is there to fix a bug in the code in an older version. + Alliance = null; //Will call Alliance.RemoveGuild which will set it null & perform all the pertient checks as far as alliacne disbanding + } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime TypeLastChange { get; private set; } + #endregion - public List Allies { get; private set; } + #region Add/Remove Member/Old Ally/Old Enemy - public List Enemies { get; private set; } + public void AddMember(Mobile m) + { + if (!Members.Contains(m)) + { + if (m.Guild != null && m.Guild != this) + ((Guild)m.Guild).RemoveMember(m); - public List AllyDeclarations { get; private set; } + Members.Add(m); + m.Guild = this; - public List AllyInvitations { get; private set; } + if (!NewGuildSystem) + m.GuildFealty = m_Leader; + else + m.GuildFealty = null; - public List WarDeclarations { get; private set; } + if (m is PlayerMobile mobile) + mobile.GuildRank = RankDefinition.Lowest; - public List WarInvitations { get; private set; } + ((Guild)m.Guild).InvalidateWarNotoriety(); + } + } - public List Candidates { get; private set; } + public void RemoveMember(Mobile m) + { + RemoveMember(m, 1018028); // You have been dismissed from your guild. + } - public List Accepted { get; private set; } + public void RemoveMember(Mobile m, int message) + { + if (Members.Contains(m)) + { + Members.Remove(m); - public List Members { get; private set; } + Guild guild = m.Guild as Guild; - #endregion - } -} + m.Guild = null; + + if (m is PlayerMobile mobile) + mobile.GuildRank = RankDefinition.Lowest; + + if (message > 0) + m.SendLocalizedMessage(message); + + if (m == m_Leader) + { + CalculateGuildmaster(); + + if (m_Leader == null) + Disband(); + } + + if (Members.Count == 0) + Disband(); + + guild?.InvalidateWarNotoriety(); + + m.Delta(MobileDelta.Noto); + } + } + + public void AddAlly(Guild g) + { + if (!Allies.Contains(g)) + { + Allies.Add(g); + + g.AddAlly(this); + } + } + + public void RemoveAlly(Guild g) + { + if (Allies.Contains(g)) + { + Allies.Remove(g); + + g.RemoveAlly(this); + } + } + + public void AddEnemy(Guild g) + { + if (!Enemies.Contains(g)) + { + Enemies.Add(g); + + g.AddEnemy(this); + } + } + + public void RemoveEnemy(Guild g) + { + if (Enemies != null && Enemies.Contains(g)) + { + Enemies.Remove(g); + + g.RemoveEnemy(this); + } + } + + #endregion + + #region Guild[Text]Message(...) + + public void GuildMessage(int num, bool append, string format, params object[] args) + { + GuildMessage(num, append, string.Format(format, args)); + } + + public void GuildMessage(int number) + { + for (int i = 0; i < Members.Count; ++i) + Members[i].SendLocalizedMessage(number); + } + + public void GuildMessage(int number, string args, int hue = 0x3B2) + { + for (int i = 0; i < Members.Count; ++i) + Members[i].SendLocalizedMessage(number, args, hue); + } + + public void GuildMessage(int number, bool append, string affix, string args = "", int hue = 0x3B2) + { + for (int i = 0; i < Members.Count; ++i) + Members[i].SendLocalizedMessage(number, append, affix, args, hue); + } + + public void GuildTextMessage(string text) + { + GuildTextMessage(0x3B2, text); + } + + public void GuildTextMessage(string format, params object[] args) + { + GuildTextMessage(0x3B2, string.Format(format, args)); + } + + public void GuildTextMessage(int hue, string text) + { + for (int i = 0; i < Members.Count; ++i) + Members[i].SendMessage(hue, text); + } + + public void GuildTextMessage(int hue, string format, params object[] args) + { + GuildTextMessage(hue, string.Format(format, args)); + } + + public void GuildChat(Mobile from, int hue, string text) + { + Packet p = null; + for (int i = 0; i < Members.Count; i++) + { + Mobile m = Members[i]; + + NetState state = m.NetState; + + if (state != null) + { + if (p == null) + p = Packet.Acquire(new UnicodeMessage(from.Serial, from.Body, MessageType.Guild, hue, 3, + from.Language, from.Name, text)); + + state.Send(p); + } + } + + Packet.Release(p); + } + + public void GuildChat(Mobile from, string text) + { + PlayerMobile pm = from as PlayerMobile; + + GuildChat(from, pm?.GuildMessageHue ?? 0x3B2, text); + } + + #endregion + + #region Voting + + public bool CanVote(Mobile m) + { + if (NewGuildSystem) + if (!(m is PlayerMobile pm) || !pm.GuildRank.GetFlag(RankFlags.CanVote)) + return false; + + return m != null && !m.Deleted && m.Guild == this; + } + + public bool CanBeVotedFor(Mobile m) + { + if (NewGuildSystem) + if (!(m is PlayerMobile pm) || pm.LastOnline + InactiveTime < DateTime.UtcNow) + return false; + + return m != null && !m.Deleted && m.Guild == this; + } + + public void CalculateGuildmaster() + { + Dictionary votes = new Dictionary(); + + int votingMembers = 0; + + for (int i = 0; Members != null && i < Members.Count; ++i) + { + Mobile memb = Members[i]; + + if (!CanVote(memb)) + continue; + + Mobile m = memb.GuildFealty; + + if (!CanBeVotedFor(m)) + { + if (m_Leader != null && !m_Leader.Deleted && m_Leader.Guild == this) + m = m_Leader; + else + m = memb; + } + + if (m == null) + continue; + + if (!votes.TryGetValue(m, out int v)) + votes[m] = 1; + else + votes[m] = v + 1; + + votingMembers++; + } + + Mobile winner = null; + int highVotes = 0; + + foreach (KeyValuePair kvp in votes) + { + Mobile m = kvp.Key; + int val = kvp.Value; + + if (winner == null || val > highVotes) + { + winner = m; + highVotes = val; + } + } + + if (NewGuildSystem && highVotes * 100 / Math.Max(votingMembers, 1) < MajorityPercentage && m_Leader != null && + winner != m_Leader && !m_Leader.Deleted && m_Leader.Guild == this) + winner = m_Leader; + + if (m_Leader != winner && winner != null) + GuildMessage(1018015, true, winner.Name); // Guild Message: Guildmaster changed to: + + Leader = winner; + LastFealty = DateTime.UtcNow; + } + + #endregion + + #region Getters & Setters + + [CommandProperty(AccessLevel.GameMaster)] + public Item Guildstone{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Item Teleporter{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public override string Name + { + get => m_Name; + set + { + m_Name = value; + + InvalidateMemberProperties(true); + + Guildstone?.InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Website{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public override string Abbreviation + { + get => m_Abbreviation; + set + { + m_Abbreviation = value; + + InvalidateMemberProperties(true); + + Guildstone?.InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Charter{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public override GuildType Type + { + get => OrderChaos ? m_Type : GuildType.Regular; + set + { + if (m_Type != value) + { + m_Type = value; + TypeLastChange = DateTime.UtcNow; + + InvalidateMemberProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastFealty{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime TypeLastChange{ get; private set; } + + public List Allies{ get; private set; } + + public List Enemies{ get; private set; } + + public List AllyDeclarations{ get; private set; } + + public List AllyInvitations{ get; private set; } + + public List WarDeclarations{ get; private set; } + + public List WarInvitations{ get; private set; } + + public List Candidates{ get; private set; } + + public List Accepted{ get; private set; } + + public List Members{ get; private set; } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Misc/HardwareInfo.cs b/Scripts/Misc/HardwareInfo.cs index db055ea02..c0fb29bbb 100644 --- a/Scripts/Misc/HardwareInfo.cs +++ b/Scripts/Misc/HardwareInfo.cs @@ -1,170 +1,172 @@ using System; -using Server.Commands; using Server.Accounting; +using Server.Commands; +using Server.Gumps; using Server.Network; using Server.Targeting; namespace Server { - public class HardwareInfo - { - [CommandProperty( AccessLevel.GameMaster )] - public int CpuModel { get; private set; } + public class HardwareInfo + { + [CommandProperty(AccessLevel.GameMaster)] + public int CpuModel{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int CpuClockSpeed { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int CpuClockSpeed{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int CpuQuantity { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int CpuQuantity{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int OSMajor { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int OSMajor{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int OSMinor { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int OSMinor{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int OSRevision { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int OSRevision{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int InstanceID { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int InstanceID{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ScreenWidth { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int ScreenWidth{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ScreenHeight { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int ScreenHeight{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ScreenDepth { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int ScreenDepth{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int PhysicalMemory { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int PhysicalMemory{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int CpuManufacturer { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int CpuManufacturer{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int CpuFamily { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int CpuFamily{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int VCVendorID { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int VCVendorID{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int VCDeviceID { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int VCDeviceID{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int VCMemory { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int VCMemory{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int DXMajor { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int DXMajor{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int DXMinor { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int DXMinor{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public string VCDescription { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public string VCDescription{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public string Language { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public string Language{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int Distribution { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int Distribution{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ClientsRunning { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int ClientsRunning{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ClientsInstalled { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int ClientsInstalled{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int PartialInstalled { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public int PartialInstalled{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public string Unknown { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public string Unknown{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime TimeReceived { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public DateTime TimeReceived{ get; private set; } - public static void Initialize() - { - PacketHandlers.Register( 0xD9, 0x10C, false, OnReceive ); + public static void Initialize() + { + PacketHandlers.Register(0xD9, 0x10C, false, OnReceive); - CommandSystem.Register( "HWInfo", AccessLevel.GameMaster, HWInfo_OnCommand ); - } + CommandSystem.Register("HWInfo", AccessLevel.GameMaster, HWInfo_OnCommand); + } - [Usage( "HWInfo" )] - [Description( "Displays information about a targeted player's hardware." )] - public static void HWInfo_OnCommand( CommandEventArgs e ) - { - e.Mobile.BeginTarget( -1, false, TargetFlags.None, HWInfo_OnTarget ); - e.Mobile.SendMessage( "Target a player to view their hardware information." ); - } + [Usage("HWInfo")] + [Description("Displays information about a targeted player's hardware.")] + public static void HWInfo_OnCommand(CommandEventArgs e) + { + e.Mobile.BeginTarget(-1, false, TargetFlags.None, HWInfo_OnTarget); + e.Mobile.SendMessage("Target a player to view their hardware information."); + } - public static void HWInfo_OnTarget( Mobile from, object obj ) - { - if ( obj is Mobile m && m.Player ) - { - if ( m.Account is Account acct ) - { - HardwareInfo hwInfo = acct.HardwareInfo; + public static void HWInfo_OnTarget(Mobile from, object obj) + { + if (obj is Mobile m && m.Player) + { + if (m.Account is Account acct) + { + HardwareInfo hwInfo = acct.HardwareInfo; - if ( hwInfo != null ) - CommandLogging.WriteLine( from, "{0} {1} viewing hardware info of {2}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( m ) ); + if (hwInfo != null) + CommandLogging.WriteLine(from, "{0} {1} viewing hardware info of {2}", from.AccessLevel, + CommandLogging.Format(from), CommandLogging.Format(m)); - if ( hwInfo != null ) - from.SendGump( new Gumps.PropertiesGump( from, hwInfo ) ); - else - from.SendMessage( "No hardware information for that account was found." ); - } - else - { - from.SendMessage( "No account has been attached to that player." ); - } - } - else - { - from.BeginTarget( -1, false, TargetFlags.None, HWInfo_OnTarget ); - from.SendMessage( "That is not a player. Try again." ); - } - } + if (hwInfo != null) + from.SendGump(new PropertiesGump(from, hwInfo)); + else + from.SendMessage("No hardware information for that account was found."); + } + else + { + from.SendMessage("No account has been attached to that player."); + } + } + else + { + from.BeginTarget(-1, false, TargetFlags.None, HWInfo_OnTarget); + from.SendMessage("That is not a player. Try again."); + } + } - public static void OnReceive( NetState state, PacketReader pvSrc ) - { - pvSrc.ReadByte(); // 1: <4.0.1a, 2>=4.0.1a + public static void OnReceive(NetState state, PacketReader pvSrc) + { + pvSrc.ReadByte(); // 1: <4.0.1a, 2>=4.0.1a - HardwareInfo info = new HardwareInfo(); + HardwareInfo info = new HardwareInfo(); - info.InstanceID = pvSrc.ReadInt32(); - info.OSMajor = pvSrc.ReadInt32(); - info.OSMinor = pvSrc.ReadInt32(); - info.OSRevision = pvSrc.ReadInt32(); - info.CpuManufacturer = pvSrc.ReadByte(); - info.CpuFamily = pvSrc.ReadInt32(); - info.CpuModel = pvSrc.ReadInt32(); - info.CpuClockSpeed = pvSrc.ReadInt32(); - info.CpuQuantity = pvSrc.ReadByte(); - info.PhysicalMemory = pvSrc.ReadInt32(); - info.ScreenWidth = pvSrc.ReadInt32(); - info.ScreenHeight = pvSrc.ReadInt32(); - info.ScreenDepth = pvSrc.ReadInt32(); - info.DXMajor = pvSrc.ReadInt16(); - info.DXMinor = pvSrc.ReadInt16(); - info.VCDescription = pvSrc.ReadUnicodeStringLESafe( 64 ); - info.VCVendorID = pvSrc.ReadInt32(); - info.VCDeviceID = pvSrc.ReadInt32(); - info.VCMemory = pvSrc.ReadInt32(); - info.Distribution = pvSrc.ReadByte(); - info.ClientsRunning = pvSrc.ReadByte(); - info.ClientsInstalled = pvSrc.ReadByte(); - info.PartialInstalled = pvSrc.ReadByte(); - info.Language = pvSrc.ReadUnicodeStringLESafe( 4 ); - info.Unknown = pvSrc.ReadStringSafe( 64 ); + info.InstanceID = pvSrc.ReadInt32(); + info.OSMajor = pvSrc.ReadInt32(); + info.OSMinor = pvSrc.ReadInt32(); + info.OSRevision = pvSrc.ReadInt32(); + info.CpuManufacturer = pvSrc.ReadByte(); + info.CpuFamily = pvSrc.ReadInt32(); + info.CpuModel = pvSrc.ReadInt32(); + info.CpuClockSpeed = pvSrc.ReadInt32(); + info.CpuQuantity = pvSrc.ReadByte(); + info.PhysicalMemory = pvSrc.ReadInt32(); + info.ScreenWidth = pvSrc.ReadInt32(); + info.ScreenHeight = pvSrc.ReadInt32(); + info.ScreenDepth = pvSrc.ReadInt32(); + info.DXMajor = pvSrc.ReadInt16(); + info.DXMinor = pvSrc.ReadInt16(); + info.VCDescription = pvSrc.ReadUnicodeStringLESafe(64); + info.VCVendorID = pvSrc.ReadInt32(); + info.VCDeviceID = pvSrc.ReadInt32(); + info.VCMemory = pvSrc.ReadInt32(); + info.Distribution = pvSrc.ReadByte(); + info.ClientsRunning = pvSrc.ReadByte(); + info.ClientsInstalled = pvSrc.ReadByte(); + info.PartialInstalled = pvSrc.ReadByte(); + info.Language = pvSrc.ReadUnicodeStringLESafe(4); + info.Unknown = pvSrc.ReadStringSafe(64); - info.TimeReceived = DateTime.UtcNow; + info.TimeReceived = DateTime.UtcNow; - if ( state.Account is Account acct ) - acct.HardwareInfo = info; - } - } -} + if (state.Account is Account acct) + acct.HardwareInfo = info; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Keywords.cs b/Scripts/Misc/Keywords.cs index ca15f8353..5f0fc9554 100644 --- a/Scripts/Misc/Keywords.cs +++ b/Scripts/Misc/Keywords.cs @@ -1,56 +1,54 @@ using Server.Guilds; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; namespace Server.Misc { - public class Keywords - { - public static void Initialize() - { - // Register our speech handler - EventSink.Speech += EventSink_Speech; - } + public class Keywords + { + public static void Initialize() + { + // Register our speech handler + EventSink.Speech += EventSink_Speech; + } - public static void EventSink_Speech( SpeechEventArgs args ) - { - Mobile from = args.Mobile; - int[] keywords = args.Keywords; + public static void EventSink_Speech(SpeechEventArgs args) + { + Mobile from = args.Mobile; + int[] keywords = args.Keywords; - for ( int i = 0; i < keywords.Length; ++i ) - { - switch ( keywords[i] ) - { - case 0x002A: // *i resign from my guild* - { - ((Guild)from.Guild)?.RemoveMember( from ); + for (int i = 0; i < keywords.Length; ++i) + switch (keywords[i]) + { + case 0x002A: // *i resign from my guild* + { + ((Guild)from.Guild)?.RemoveMember(from); - break; - } - case 0x0032: // *i must consider my sins* - { - if ( !Core.SE ) - { - from.SendMessage( "Short Term Murders : {0}", from.ShortTermMurders ); - from.SendMessage( "Long Term Murders : {0}", from.Kills ); - } - else - { - from.SendMessage( 0x3B2, "Short Term Murders: {0} Long Term Murders: {1}", from.ShortTermMurders, from.Kills ); - } - break; - } - case 0x0035: // i renounce my young player status* - { - if ( from is PlayerMobile mobile && mobile.Young && !mobile.HasGump( typeof( RenounceYoungGump ) ) ) - { - mobile.SendGump( new RenounceYoungGump() ); - } + break; + } + case 0x0032: // *i must consider my sins* + { + if (!Core.SE) + { + from.SendMessage("Short Term Murders : {0}", from.ShortTermMurders); + from.SendMessage("Long Term Murders : {0}", from.Kills); + } + else + { + from.SendMessage(0x3B2, "Short Term Murders: {0} Long Term Murders: {1}", from.ShortTermMurders, + from.Kills); + } - break; - } - } - } - } - } -} + break; + } + case 0x0035: // i renounce my young player status* + { + if (from is PlayerMobile mobile && mobile.Young && !mobile.HasGump(typeof(RenounceYoungGump))) + mobile.SendGump(new RenounceYoungGump()); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/LanguageStatistics.cs b/Scripts/Misc/LanguageStatistics.cs index ac7e2d1f2..b01c00c24 100644 --- a/Scripts/Misc/LanguageStatistics.cs +++ b/Scripts/Misc/LanguageStatistics.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Generic; using System.IO; using Server.Accounting; @@ -6,364 +5,349 @@ using Server.Commands; namespace Server.Misc { - /** - * This file requires to be saved in a Unicode - * compatible format. - * - * Warning: if you change String.Format methods, - * please note that the following character - * is suggested before any left-to-right text - * in order to prevent undesired formatting - * resulting from mixing LR and RL text: ‎ - * - * Use this one if you need to force RL: ‏ - * - * If you do not see the above chars, please - * enable showing of unicode control chars - **/ + /** + * This file requires to be saved in a Unicode + * compatible format. + * + * Warning: if you change String.Format methods, + * please note that the following character + * is suggested before any left-to-right text + * in order to prevent undesired formatting + * resulting from mixing LR and RL text: ‎ + * + * Use this one if you need to force RL: ‏ + * + * If you do not see the above chars, please + * enable showing of unicode control chars + **/ - public class LanguageStatistics - { - struct InternationalCode - { - bool m_HasLocalInfo; + public class LanguageStatistics + { + private static InternationalCode[] InternationalCodes = + { + new InternationalCode("ARA", "Arabic", "Saudi Arabia", "العربية", "السعودية"), + new InternationalCode("ARI", "Arabic", "Iraq", "العربية", "العراق"), + new InternationalCode("ARE", "Arabic", "Egypt", "العربية", "مصر"), + new InternationalCode("ARL", "Arabic", "Libya", "العربية", "ليبيا"), + new InternationalCode("ARG", "Arabic", "Algeria", "العربية", "الجزائر"), + new InternationalCode("ARM", "Arabic", "Morocco", "العربية", "المغرب"), + new InternationalCode("ART", "Arabic", "Tunisia", "العربية", "تونس"), + new InternationalCode("ARO", "Arabic", "Oman", "العربية", "عمان"), + new InternationalCode("ARY", "Arabic", "Yemen", "العربية", "اليمن"), + new InternationalCode("ARS", "Arabic", "Syria", "العربية", "سورية"), + new InternationalCode("ARJ", "Arabic", "Jordan", "العربية", "الأردن"), + new InternationalCode("ARB", "Arabic", "Lebanon", "العربية", "لبنان"), + new InternationalCode("ARK", "Arabic", "Kuwait", "العربية", "الكويت"), + new InternationalCode("ARU", "Arabic", "U.A.E.", "العربية", "الامارات"), + new InternationalCode("ARH", "Arabic", "Bahrain", "العربية", "البحرين"), + new InternationalCode("ARQ", "Arabic", "Qatar", "العربية", "قطر"), + new InternationalCode("BGR", "Bulgarian", "Bulgaria", "Български", "България"), + new InternationalCode("CAT", "Catalan", "Spain", "Català", "Espanya"), + new InternationalCode("CHT", "Chinese", "Taiwan", "台語", "臺灣"), + new InternationalCode("CHS", "Chinese", "PRC", "中文", "中国"), + new InternationalCode("ZHH", "Chinese", "Hong Kong", "中文", "香港"), + new InternationalCode("ZHI", "Chinese", "Singapore", "中文", "新加坡"), + new InternationalCode("ZHM", "Chinese", "Macau", "中文", "澳門"), + new InternationalCode("CSY", "Czech", "Czech Republic", "Čeština", "Česká republika"), + new InternationalCode("DAN", "Danish", "Denmark", "Dansk", "Danmark"), + new InternationalCode("DEU", "German", "Germany", "Deutsch", "Deutschland"), + new InternationalCode("DES", "German", "Switzerland", "Deutsch", "der Schweiz"), + new InternationalCode("DEA", "German", "Austria", "Deutsch", "Österreich"), + new InternationalCode("DEL", "German", "Luxembourg", "Deutsch", "Luxembourg"), + new InternationalCode("DEC", "German", "Liechtenstein", "Deutsch", "Liechtenstein"), + new InternationalCode("ELL", "Greek", "Greece", "Ελληνικά", "Ελλάδα"), + new InternationalCode("ENU", "English", "United States"), + new InternationalCode("ENG", "English", "United Kingdom"), + new InternationalCode("ENA", "English", "Australia"), + new InternationalCode("ENC", "English", "Canada"), + new InternationalCode("ENZ", "English", "New Zealand"), + new InternationalCode("ENI", "English", "Ireland"), + new InternationalCode("ENS", "English", "South Africa"), + new InternationalCode("ENJ", "English", "Jamaica"), + new InternationalCode("ENB", "English", "Caribbean"), + new InternationalCode("ENL", "English", "Belize"), + new InternationalCode("ENT", "English", "Trinidad"), + new InternationalCode("ENW", "English", "Zimbabwe"), + new InternationalCode("ENP", "English", "Philippines"), + new InternationalCode("ESP", "Spanish", "Spain (Traditional Sort)", "Español", "España (tipo tradicional)"), + new InternationalCode("ESM", "Spanish", "Mexico", "Español", "México"), + new InternationalCode("ESN", "Spanish", "Spain (International Sort)", "Español", "España (tipo internacional)"), + new InternationalCode("ESG", "Spanish", "Guatemala", "Español", "Guatemala"), + new InternationalCode("ESC", "Spanish", "Costa Rica", "Español", "Costa Rica"), + new InternationalCode("ESA", "Spanish", "Panama", "Español", "Panama"), + new InternationalCode("ESD", "Spanish", "Dominican Republic", "Español", "Republica Dominicana"), + new InternationalCode("ESV", "Spanish", "Venezuela", "Español", "Venezuela"), + new InternationalCode("ESO", "Spanish", "Colombia", "Español", "Colombia"), + new InternationalCode("ESR", "Spanish", "Peru", "Español", "Peru"), + new InternationalCode("ESS", "Spanish", "Argentina", "Español", "Argentina"), + new InternationalCode("ESF", "Spanish", "Ecuador", "Español", "Ecuador"), + new InternationalCode("ESL", "Spanish", "Chile", "Español", "Chile"), + new InternationalCode("ESY", "Spanish", "Uruguay", "Español", "Uruguay"), + new InternationalCode("ESZ", "Spanish", "Paraguay", "Español", "Paraguay"), + new InternationalCode("ESB", "Spanish", "Bolivia", "Español", "Bolivia"), + new InternationalCode("ESE", "Spanish", "El Salvador", "Español", "El Salvador"), + new InternationalCode("ESH", "Spanish", "Honduras", "Español", "Honduras"), + new InternationalCode("ESI", "Spanish", "Nicaragua", "Español", "Nicaragua"), + new InternationalCode("ESU", "Spanish", "Puerto Rico", "Español", "Puerto Rico"), + new InternationalCode("FIN", "Finnish", "Finland", "Suomi", "Suomi"), + new InternationalCode("FRA", "French", "France", "Français", "France"), + new InternationalCode("FRB", "French", "Belgium", "Français", "Belgique"), + new InternationalCode("FRC", "French", "Canada", "Français", "Canada"), + new InternationalCode("FRS", "French", "Switzerland", "Français", "Suisse"), + new InternationalCode("FRL", "French", "Luxembourg", "Français", "Luxembourg"), + new InternationalCode("FRM", "French", "Monaco", "Français", "Monaco"), + new InternationalCode("HEB", "Hebrew", "Israel", "עִבְרִית", "ישׂראל"), + new InternationalCode("HUN", "Hungarian", "Hungary", "Magyar", "Magyarország"), + new InternationalCode("ISL", "Icelandic", "Iceland", "Íslenska", "Ísland"), + new InternationalCode("ITA", "Italian", "Italy", "Italiano", "Italia"), + new InternationalCode("ITS", "Italian", "Switzerland", "Italiano", "Svizzera"), + new InternationalCode("JPN", "Japanese", "Japan", "日本語", "日本"), + new InternationalCode("KOR", "Korean (Extended Wansung)", "Korea", "한국어", "한국"), + new InternationalCode("NLD", "Dutch", "Netherlands", "Nederlands", "Nederland"), + new InternationalCode("NLB", "Dutch", "Belgium", "Nederlands", "België"), + new InternationalCode("NOR", "Norwegian", "Norway (Bokmål)", "Norsk", "Norge (Bokmål)"), + new InternationalCode("NON", "Norwegian", "Norway (Nynorsk)", "Norsk", "Norge (Nynorsk)"), + new InternationalCode("PLK", "Polish", "Poland", "Polski", "Polska"), + new InternationalCode("PTB", "Portuguese", "Brazil", "Português", "Brasil"), + new InternationalCode("PTG", "Portuguese", "Portugal", "Português", "Brasil"), + new InternationalCode("ROM", "Romanian", "Romania", "Limba Română", "România"), + new InternationalCode("RUS", "Russian", "Russia", "Русский", "Россия"), + new InternationalCode("HRV", "Croatian", "Croatia", "Hrvatski", "Hrvatska"), + new InternationalCode("SRL", "Serbian", "Serbia (Latin)", "Srpski", "Srbija i Crna Gora"), + new InternationalCode("SRB", "Serbian", "Serbia (Cyrillic)", "Српски", "Србија и Црна Гора"), + new InternationalCode("SKY", "Slovak", "Slovakia", "Slovenčina", "Slovensko"), + new InternationalCode("SQI", "Albanian", "Albania", "Shqip", "Shqipëria"), + new InternationalCode("SVE", "Swedish", "Sweden", "Svenska", "Sverige"), + new InternationalCode("SVF", "Swedish", "Finland", "Svenska", "Finland"), + new InternationalCode("THA", "Thai", "Thailand", "ภาษาไทย", "ประเทศไทย"), + new InternationalCode("TRK", "Turkish", "Turkey", "Türkçe", "Türkiye"), + new InternationalCode("URP", "Urdu", "Pakistan", "اردو", "پاکستان"), + new InternationalCode("IND", "Indonesian", "Indonesia", "Bahasa Indonesia", "Indonesia"), + new InternationalCode("UKR", "Ukrainian", "Ukraine", "Українська", "Украина"), + new InternationalCode("BEL", "Belarusian", "Belarus", "Беларускі", "Беларусь"), + new InternationalCode("SLV", "Slovene", "Slovenia", "Slovenščina", "Slovenija"), + new InternationalCode("ETI", "Estonian", "Estonia", "Eesti", "Eesti"), + new InternationalCode("LVI", "Latvian", "Latvia", "Latviešu", "Latvija"), + new InternationalCode("LTH", "Lithuanian", "Lithuania", "Lietuvių", "Lietuva"), + new InternationalCode("LTC", "Classic Lithuanian", "Lithuania", "Lietuviškai", "Lietuva"), + new InternationalCode("FAR", "Farsi", "Iran", "فارسى", "ايران"), + new InternationalCode("VIT", "Vietnamese", "Viet Nam", "tiếng Việt", "Việt Nam"), + new InternationalCode("HYE", "Armenian", "Armenia", "Հայերէն", "Հայաստան"), + new InternationalCode("AZE", "Azeri", "Azerbaijan (Latin)", "Azərbaycanca", "Azərbaycan"), + new InternationalCode("AZE", "Azeri", "Azerbaijan (Cyrillic)", "Азәрбајҹанҹа", "Азәрбајҹан"), + new InternationalCode("EUQ", "Basque", "Spain", "Euskera", "Espainia"), + new InternationalCode("MKI", "Macedonian", "Macedonia", "Македонски", "Македонија"), + new InternationalCode("AFK", "Afrikaans", "South Africa", "Afrikaans", "Republiek van Suid-Afrika"), + new InternationalCode("KAT", "Georgian", "Georgia", "ქართული", "საკარტველო"), + new InternationalCode("FOS", "Faeroese", "Faeroe Islands", "Føroyska", "Føroya"), + new InternationalCode("HIN", "Hindi", "India", "हिन्दी", "भारत"), + new InternationalCode("MSL", "Malay", "Malaysia", "Bahasa melayu", "Malaysia"), + new InternationalCode("MSB", "Malay", "Brunei Darussalam", "Bahasa melayu", "Negara Brunei Darussalam"), + new InternationalCode("KAZ", "Kazak", "Kazakstan", "Қазақ", "Қазақстан"), + new InternationalCode("SWK", "Swahili", "Kenya", "Kiswahili", "Kenya"), + new InternationalCode("UZB", "Uzbek", "Uzbekistan (Latin)", "O'zbek", "O'zbekiston"), + new InternationalCode("UZB", "Uzbek", "Uzbekistan (Cyrillic)", "Ўзбек", "Ўзбекистон"), + new InternationalCode("TAT", "Tatar", "Tatarstan", "Татарча", "Татарстан"), + new InternationalCode("BEN", "Bengali", "India", "বাংলা", "ভারত"), + new InternationalCode("PAN", "Punjabi", "India", "ਪੰਜਾਬੀ", "ਭਾਰਤ"), + new InternationalCode("GUJ", "Gujarati", "India", "ગુજરાતી", "ભારત"), + new InternationalCode("ORI", "Oriya", "India", "ଓଡ଼ିଆ", "ଭାରତ"), + new InternationalCode("TAM", "Tamil", "India", "தமிழ்", "இந்தியா"), + new InternationalCode("TEL", "Telugu", "India", "తెలుగు", "భారత"), + new InternationalCode("KAN", "Kannada", "India", "ಕನ್ನಡ", "ಭಾರತ"), + new InternationalCode("MAL", "Malayalam", "India", "മലയാളം", "ഭാരത"), + new InternationalCode("ASM", "Assamese", "India", "অসমিয়া", "Bhārat"), // missing correct country name + new InternationalCode("MAR", "Marathi", "India", "मराठी", "भारत"), + new InternationalCode("SAN", "Sanskrit", "India", "संस्कृत", "भारतम्"), + new InternationalCode("KOK", "Konkani", "India", "कोंकणी", "भारत") + }; - public string Code { get; } + private static bool DefaultLocalNames = false; + private static bool ShowAlternatives = true; + private static bool CountAccounts = true; // will consider only first character's valid language - public string Language { get; } + private static string GetFormattedInfo(string code) + { + if (code == null || code.Length != 3) + return $"Unknown code {code}"; - public string Country { get; } + for (int i = 0; i < InternationalCodes.Length; i++) + if (code == InternationalCodes[i].Code) + return $"{InternationalCodes[i].GetName()}"; - public string Language_LocalName { get; } + return $"Unknown code {code}"; + } - public string Country_LocalName { get; } + public static void Initialize() + { + CommandSystem.Register("LanguageStatistics", AccessLevel.Administrator, LanguageStatistics_OnCommand); + } - public InternationalCode( string code, string language, string country ) : this( code, language, country, null, null ) - { - m_HasLocalInfo = false; - } + [Usage("LanguageStatistics")] + [Description("Generate a file containing the list of languages for each PlayerMobile.")] + public static void LanguageStatistics_OnCommand(CommandEventArgs e) + { + Dictionary ht = new Dictionary(); - public InternationalCode( string code, string language, string country, string language_localname, string country_localname ) - { - Code = code; - Language = language; - Country = country; - Language_LocalName = language_localname; - Country_LocalName = country_localname; - m_HasLocalInfo = true; - } + using (StreamWriter writer = new StreamWriter("languages.txt")) + { + if (CountAccounts) + foreach (Account acc in Accounts.GetAccounts()) + for (int i = 0; i < acc.Length; i++) + { + Mobile mob = acc[i]; - public string GetName() - { - string s; + string lang = mob?.Language; - if ( m_HasLocalInfo ) - { - s = - $"{(DefaultLocalNames ? Language_LocalName : Language)}‎ - {(DefaultLocalNames ? Country_LocalName : Country)}"; + if (lang != null) + { + lang = lang.ToUpper(); - if ( ShowAlternatives ) - s += - $"‎ 【{(DefaultLocalNames ? Language : Language_LocalName)}‎ - {(DefaultLocalNames ? Country : Country_LocalName)}‎】"; - } - else - { - s = $"{Language}‎ - {Country}"; - } + if (!ht.ContainsKey(lang)) + ht[lang] = new InternationalCodeCounter(lang); + else + ht[lang].Increase(); - return s; - } - } + break; + } + } + else + foreach (Mobile mob in World.Mobiles.Values) + if (mob.Player) + { + string lang = mob.Language; - private static InternationalCode[] InternationalCodes = - { - new InternationalCode( "ARA", "Arabic", "Saudi Arabia", "العربية", "السعودية" ), - new InternationalCode( "ARI", "Arabic", "Iraq", "العربية", "العراق" ), - new InternationalCode( "ARE", "Arabic", "Egypt", "العربية", "مصر" ), - new InternationalCode( "ARL", "Arabic", "Libya", "العربية", "ليبيا" ), - new InternationalCode( "ARG", "Arabic", "Algeria", "العربية", "الجزائر" ), - new InternationalCode( "ARM", "Arabic", "Morocco", "العربية", "المغرب" ), - new InternationalCode( "ART", "Arabic", "Tunisia", "العربية", "تونس" ), - new InternationalCode( "ARO", "Arabic", "Oman", "العربية", "عمان" ), - new InternationalCode( "ARY", "Arabic", "Yemen", "العربية", "اليمن" ), - new InternationalCode( "ARS", "Arabic", "Syria", "العربية", "سورية" ), - new InternationalCode( "ARJ", "Arabic", "Jordan", "العربية", "الأردن" ), - new InternationalCode( "ARB", "Arabic", "Lebanon", "العربية", "لبنان" ), - new InternationalCode( "ARK", "Arabic", "Kuwait", "العربية", "الكويت" ), - new InternationalCode( "ARU", "Arabic", "U.A.E.", "العربية", "الامارات" ), - new InternationalCode( "ARH", "Arabic", "Bahrain", "العربية", "البحرين" ), - new InternationalCode( "ARQ", "Arabic", "Qatar", "العربية", "قطر" ), - new InternationalCode( "BGR", "Bulgarian", "Bulgaria", "Български", "България" ), - new InternationalCode( "CAT", "Catalan", "Spain", "Català", "Espanya" ), - new InternationalCode( "CHT", "Chinese", "Taiwan", "台語", "臺灣" ), - new InternationalCode( "CHS", "Chinese", "PRC", "中文", "中国" ), - new InternationalCode( "ZHH", "Chinese", "Hong Kong", "中文", "香港" ), - new InternationalCode( "ZHI", "Chinese", "Singapore", "中文", "新加坡" ), - new InternationalCode( "ZHM", "Chinese", "Macau", "中文", "澳門" ), - new InternationalCode( "CSY", "Czech", "Czech Republic", "Čeština", "Česká republika" ), - new InternationalCode( "DAN", "Danish", "Denmark", "Dansk", "Danmark" ), - new InternationalCode( "DEU", "German", "Germany", "Deutsch", "Deutschland" ), - new InternationalCode( "DES", "German", "Switzerland", "Deutsch", "der Schweiz" ), - new InternationalCode( "DEA", "German", "Austria", "Deutsch", "Österreich" ), - new InternationalCode( "DEL", "German", "Luxembourg", "Deutsch", "Luxembourg" ), - new InternationalCode( "DEC", "German", "Liechtenstein", "Deutsch", "Liechtenstein" ), - new InternationalCode( "ELL", "Greek", "Greece", "Ελληνικά", "Ελλάδα" ), - new InternationalCode( "ENU", "English", "United States" ), - new InternationalCode( "ENG", "English", "United Kingdom" ), - new InternationalCode( "ENA", "English", "Australia" ), - new InternationalCode( "ENC", "English", "Canada" ), - new InternationalCode( "ENZ", "English", "New Zealand" ), - new InternationalCode( "ENI", "English", "Ireland" ), - new InternationalCode( "ENS", "English", "South Africa" ), - new InternationalCode( "ENJ", "English", "Jamaica" ), - new InternationalCode( "ENB", "English", "Caribbean" ), - new InternationalCode( "ENL", "English", "Belize" ), - new InternationalCode( "ENT", "English", "Trinidad" ), - new InternationalCode( "ENW", "English", "Zimbabwe" ), - new InternationalCode( "ENP", "English", "Philippines" ), - new InternationalCode( "ESP", "Spanish", "Spain (Traditional Sort)", "Español", "España (tipo tradicional)" ), - new InternationalCode( "ESM", "Spanish", "Mexico", "Español", "México" ), - new InternationalCode( "ESN", "Spanish", "Spain (International Sort)", "Español", "España (tipo internacional)" ), - new InternationalCode( "ESG", "Spanish", "Guatemala", "Español", "Guatemala" ), - new InternationalCode( "ESC", "Spanish", "Costa Rica", "Español", "Costa Rica" ), - new InternationalCode( "ESA", "Spanish", "Panama", "Español", "Panama" ), - new InternationalCode( "ESD", "Spanish", "Dominican Republic", "Español", "Republica Dominicana" ), - new InternationalCode( "ESV", "Spanish", "Venezuela", "Español", "Venezuela" ), - new InternationalCode( "ESO", "Spanish", "Colombia", "Español", "Colombia" ), - new InternationalCode( "ESR", "Spanish", "Peru", "Español", "Peru" ), - new InternationalCode( "ESS", "Spanish", "Argentina", "Español", "Argentina" ), - new InternationalCode( "ESF", "Spanish", "Ecuador", "Español", "Ecuador" ), - new InternationalCode( "ESL", "Spanish", "Chile", "Español", "Chile" ), - new InternationalCode( "ESY", "Spanish", "Uruguay", "Español", "Uruguay" ), - new InternationalCode( "ESZ", "Spanish", "Paraguay", "Español", "Paraguay" ), - new InternationalCode( "ESB", "Spanish", "Bolivia", "Español", "Bolivia" ), - new InternationalCode( "ESE", "Spanish", "El Salvador", "Español", "El Salvador" ), - new InternationalCode( "ESH", "Spanish", "Honduras", "Español", "Honduras" ), - new InternationalCode( "ESI", "Spanish", "Nicaragua", "Español", "Nicaragua" ), - new InternationalCode( "ESU", "Spanish", "Puerto Rico", "Español", "Puerto Rico" ), - new InternationalCode( "FIN", "Finnish", "Finland", "Suomi", "Suomi" ), - new InternationalCode( "FRA", "French", "France", "Français", "France" ), - new InternationalCode( "FRB", "French", "Belgium", "Français", "Belgique" ), - new InternationalCode( "FRC", "French", "Canada", "Français", "Canada" ), - new InternationalCode( "FRS", "French", "Switzerland", "Français", "Suisse" ), - new InternationalCode( "FRL", "French", "Luxembourg", "Français", "Luxembourg" ), - new InternationalCode( "FRM", "French", "Monaco", "Français", "Monaco" ), - new InternationalCode( "HEB", "Hebrew", "Israel", "עִבְרִית", "ישׂראל" ), - new InternationalCode( "HUN", "Hungarian", "Hungary", "Magyar", "Magyarország" ), - new InternationalCode( "ISL", "Icelandic", "Iceland", "Íslenska", "Ísland" ), - new InternationalCode( "ITA", "Italian", "Italy", "Italiano", "Italia" ), - new InternationalCode( "ITS", "Italian", "Switzerland", "Italiano", "Svizzera" ), - new InternationalCode( "JPN", "Japanese", "Japan", "日本語", "日本" ), - new InternationalCode( "KOR", "Korean (Extended Wansung)", "Korea", "한국어", "한국" ), - new InternationalCode( "NLD", "Dutch", "Netherlands", "Nederlands", "Nederland" ), - new InternationalCode( "NLB", "Dutch", "Belgium", "Nederlands", "België" ), - new InternationalCode( "NOR", "Norwegian", "Norway (Bokmål)", "Norsk", "Norge (Bokmål)" ), - new InternationalCode( "NON", "Norwegian", "Norway (Nynorsk)", "Norsk", "Norge (Nynorsk)" ), - new InternationalCode( "PLK", "Polish", "Poland", "Polski", "Polska" ), - new InternationalCode( "PTB", "Portuguese", "Brazil", "Português", "Brasil" ), - new InternationalCode( "PTG", "Portuguese", "Portugal", "Português", "Brasil" ), - new InternationalCode( "ROM", "Romanian", "Romania", "Limba Română", "România" ), - new InternationalCode( "RUS", "Russian", "Russia", "Русский", "Россия" ), - new InternationalCode( "HRV", "Croatian", "Croatia", "Hrvatski", "Hrvatska" ), - new InternationalCode( "SRL", "Serbian", "Serbia (Latin)", "Srpski", "Srbija i Crna Gora" ), - new InternationalCode( "SRB", "Serbian", "Serbia (Cyrillic)", "Српски", "Србија и Црна Гора" ), - new InternationalCode( "SKY", "Slovak", "Slovakia", "Slovenčina", "Slovensko" ), - new InternationalCode( "SQI", "Albanian", "Albania", "Shqip", "Shqipëria" ), - new InternationalCode( "SVE", "Swedish", "Sweden", "Svenska", "Sverige" ), - new InternationalCode( "SVF", "Swedish", "Finland", "Svenska", "Finland" ), - new InternationalCode( "THA", "Thai", "Thailand", "ภาษาไทย", "ประเทศไทย" ), - new InternationalCode( "TRK", "Turkish", "Turkey", "Türkçe", "Türkiye" ), - new InternationalCode( "URP", "Urdu", "Pakistan", "اردو", "پاکستان" ), - new InternationalCode( "IND", "Indonesian", "Indonesia", "Bahasa Indonesia", "Indonesia" ), - new InternationalCode( "UKR", "Ukrainian", "Ukraine", "Українська", "Украина" ), - new InternationalCode( "BEL", "Belarusian", "Belarus", "Беларускі", "Беларусь" ), - new InternationalCode( "SLV", "Slovene", "Slovenia", "Slovenščina", "Slovenija" ), - new InternationalCode( "ETI", "Estonian", "Estonia", "Eesti", "Eesti" ), - new InternationalCode( "LVI", "Latvian", "Latvia", "Latviešu", "Latvija" ), - new InternationalCode( "LTH", "Lithuanian", "Lithuania", "Lietuvių", "Lietuva" ), - new InternationalCode( "LTC", "Classic Lithuanian", "Lithuania", "Lietuviškai", "Lietuva" ), - new InternationalCode( "FAR", "Farsi", "Iran", "فارسى", "ايران" ), - new InternationalCode( "VIT", "Vietnamese", "Viet Nam", "tiếng Việt", "Việt Nam" ), - new InternationalCode( "HYE", "Armenian", "Armenia", "Հայերէն", "Հայաստան" ), - new InternationalCode( "AZE", "Azeri", "Azerbaijan (Latin)", "Azərbaycanca", "Azərbaycan" ), - new InternationalCode( "AZE", "Azeri", "Azerbaijan (Cyrillic)", "Азәрбајҹанҹа", "Азәрбајҹан" ), - new InternationalCode( "EUQ", "Basque", "Spain", "Euskera", "Espainia" ), - new InternationalCode( "MKI", "Macedonian", "Macedonia", "Македонски", "Македонија" ), - new InternationalCode( "AFK", "Afrikaans", "South Africa", "Afrikaans", "Republiek van Suid-Afrika" ), - new InternationalCode( "KAT", "Georgian", "Georgia", "ქართული", "საკარტველო" ), - new InternationalCode( "FOS", "Faeroese", "Faeroe Islands", "Føroyska", "Føroya" ), - new InternationalCode( "HIN", "Hindi", "India", "हिन्दी", "भारत" ), - new InternationalCode( "MSL", "Malay", "Malaysia", "Bahasa melayu", "Malaysia" ), - new InternationalCode( "MSB", "Malay", "Brunei Darussalam", "Bahasa melayu", "Negara Brunei Darussalam" ), - new InternationalCode( "KAZ", "Kazak", "Kazakstan", "Қазақ", "Қазақстан" ), - new InternationalCode( "SWK", "Swahili", "Kenya", "Kiswahili", "Kenya" ), - new InternationalCode( "UZB", "Uzbek", "Uzbekistan (Latin)", "O'zbek", "O'zbekiston" ), - new InternationalCode( "UZB", "Uzbek", "Uzbekistan (Cyrillic)", "Ўзбек", "Ўзбекистон" ), - new InternationalCode( "TAT", "Tatar", "Tatarstan", "Татарча", "Татарстан" ), - new InternationalCode( "BEN", "Bengali", "India", "বাংলা", "ভারত" ), - new InternationalCode( "PAN", "Punjabi", "India", "ਪੰਜਾਬੀ", "ਭਾਰਤ" ), - new InternationalCode( "GUJ", "Gujarati", "India", "ગુજરાતી", "ભારત" ), - new InternationalCode( "ORI", "Oriya", "India", "ଓଡ଼ିଆ", "ଭାରତ" ), - new InternationalCode( "TAM", "Tamil", "India", "தமிழ்", "இந்தியா" ), - new InternationalCode( "TEL", "Telugu", "India", "తెలుగు", "భారత" ), - new InternationalCode( "KAN", "Kannada", "India", "ಕನ್ನಡ", "ಭಾರತ" ), - new InternationalCode( "MAL", "Malayalam", "India", "മലയാളം", "ഭാരത" ), - new InternationalCode( "ASM", "Assamese", "India", "অসমিয়া", "Bhārat" ), // missing correct country name - new InternationalCode( "MAR", "Marathi", "India", "मराठी", "भारत" ), - new InternationalCode( "SAN", "Sanskrit", "India", "संस्कृत", "भारतम्" ), - new InternationalCode( "KOK", "Konkani", "India", "कोंकणी", "भारत" ) - }; + if (lang != null) + { + lang = lang.ToUpper(); - private static string GetFormattedInfo( string code ) - { - if ( code == null || code.Length != 3 ) - return $"Unknown code {code}"; + if (!ht.ContainsKey(lang)) + ht[lang] = new InternationalCodeCounter(lang); + else + ht[lang].Increase(); + } + } - for ( int i = 0; i < InternationalCodes.Length; i++ ) - { - if ( code == InternationalCodes[i].Code ) - { - return $"{InternationalCodes[i].GetName()}"; - } - } + writer.WriteLine( + $"Language statistics. Numbers show how many {(CountAccounts ? "accounts" : "playermobile")} use the specified language."); + writer.WriteLine( + "===================================================================================================="); + writer.WriteLine(); - return $"Unknown code {code}"; - } + // sort the list + List list = new List(ht.Values); + list.Sort(InternationalCodeComparer.Instance); - private static bool DefaultLocalNames = false; - private static bool ShowAlternatives = true; - private static bool CountAccounts = true; // will consider only first character's valid language + foreach (InternationalCodeCounter c in list) + writer.WriteLine($"{GetFormattedInfo(c.Code)}‎ : {c.Count}"); - public static void Initialize() - { - CommandSystem.Register( "LanguageStatistics", AccessLevel.Administrator, LanguageStatistics_OnCommand ); - } + e.Mobile.SendMessage("Languages list generated."); + } + } - [Usage( "LanguageStatistics" )] - [Description( "Generate a file containing the list of languages for each PlayerMobile." )] - public static void LanguageStatistics_OnCommand( CommandEventArgs e ) - { - Dictionary ht = new Dictionary(); + private struct InternationalCode + { + private bool m_HasLocalInfo; - using ( StreamWriter writer = new StreamWriter( "languages.txt" ) ) - { - if ( CountAccounts ) - { - // count accounts - foreach ( Account acc in Accounts.GetAccounts() ) - { - for ( int i = 0; i < acc.Length; i++ ) - { - Mobile mob = acc[i]; + public string Code{ get; } - string lang = mob?.Language; + public string Language{ get; } - if ( lang != null ) - { - lang = lang.ToUpper(); + public string Country{ get; } - if ( !ht.ContainsKey( lang ) ) - ht[lang] = new InternationalCodeCounter( lang ); - else - ht[lang].Increase(); + public string Language_LocalName{ get; } - break; - } - } - } - } - else - { - // count playermobiles - foreach( Mobile mob in World.Mobiles.Values ) - { - if ( mob.Player ) - { - string lang = mob.Language; + public string Country_LocalName{ get; } - if ( lang != null ) - { - lang = lang.ToUpper(); + public InternationalCode(string code, string language, string country) : this(code, language, country, null, + null) + { + m_HasLocalInfo = false; + } - if ( !ht.ContainsKey( lang ) ) - ht[lang] = new InternationalCodeCounter( lang ); - else - ht[lang].Increase(); - } - } - } - } + public InternationalCode(string code, string language, string country, string language_localname, + string country_localname) + { + Code = code; + Language = language; + Country = country; + Language_LocalName = language_localname; + Country_LocalName = country_localname; + m_HasLocalInfo = true; + } - writer.WriteLine( - $"Language statistics. Numbers show how many {(CountAccounts ? "accounts" : "playermobile")} use the specified language."); - writer.WriteLine( "====================================================================================================" ); - writer.WriteLine(); + public string GetName() + { + string s; - // sort the list - List list = new List( ht.Values ); - list.Sort( InternationalCodeComparer.Instance ); + if (m_HasLocalInfo) + { + s = + $"{(DefaultLocalNames ? Language_LocalName : Language)}‎ - {(DefaultLocalNames ? Country_LocalName : Country)}"; - foreach ( InternationalCodeCounter c in list ) - writer.WriteLine($"{GetFormattedInfo(c.Code)}‎ : {c.Count}"); + if (ShowAlternatives) + s += + $"‎ 【{(DefaultLocalNames ? Language : Language_LocalName)}‎ - {(DefaultLocalNames ? Country : Country_LocalName)}‎】"; + } + else + { + s = $"{Language}‎ - {Country}"; + } - e.Mobile.SendMessage( "Languages list generated." ); - } - } + return s; + } + } - private class InternationalCodeCounter - { - public string Code { get; } + private class InternationalCodeCounter + { + public InternationalCodeCounter(string code) + { + Code = code; + Count = 1; + } - public int Count { get; private set; } + public string Code{ get; } - public InternationalCodeCounter( string code ) - { - Code = code; - Count = 1; - } + public int Count{ get; private set; } - public void Increase() - { - Count++; - } - } + public void Increase() + { + Count++; + } + } - private class InternationalCodeComparer : IComparer - { - public static readonly InternationalCodeComparer Instance = new InternationalCodeComparer(); + private class InternationalCodeComparer : IComparer + { + public static readonly InternationalCodeComparer Instance = new InternationalCodeComparer(); - public InternationalCodeComparer() - { - } + public int Compare(InternationalCodeCounter x, InternationalCodeCounter y) + { + string a = null, b = null; + int ca = 0, cb = 0; - public int Compare( InternationalCodeCounter x, InternationalCodeCounter y ) - { - string a = null, b = null; - int ca = 0, cb = 0; - - a = x.Code; - ca = x.Count; - b = y.Code; - cb = y.Count; + a = x.Code; + ca = x.Count; + b = y.Code; + cb = y.Count; - if ( ca > cb ) - return -1; + if (ca > cb) + return -1; - if ( ca < cb ) - return 1; + if (ca < cb) + return 1; - if ( a == null && b == null ) - return 0; + if (a == null && b == null) + return 0; - if ( a == null ) - return 1; + if (a == null) + return 1; - if ( b == null ) - return -1; + if (b == null) + return -1; - return a.CompareTo( b ); - } - } - } + return a.CompareTo(b); + } + } + } } \ No newline at end of file diff --git a/Scripts/Misc/LightCycle.cs b/Scripts/Misc/LightCycle.cs index 321ea1c96..8b815b234 100644 --- a/Scripts/Misc/LightCycle.cs +++ b/Scripts/Misc/LightCycle.cs @@ -1,138 +1,139 @@ using System; -using Server.Network; using Server.Commands; +using Server.Items; +using Server.Network; namespace Server { - public class LightCycle - { - public const int DayLevel = 0; - public const int NightLevel = 12; - public const int DungeonLevel = 26; - public const int JailLevel = 9; + public class LightCycle + { + public const int DayLevel = 0; + public const int NightLevel = 12; + public const int DungeonLevel = 26; + public const int JailLevel = 9; - private static int m_LevelOverride = int.MinValue; + private static int m_LevelOverride = int.MinValue; - public static int LevelOverride - { - get => m_LevelOverride; - set - { - m_LevelOverride = value; + public static int LevelOverride + { + get => m_LevelOverride; + set + { + m_LevelOverride = value; - for ( int i = 0; i < NetState.Instances.Count; ++i ) - { - NetState ns = NetState.Instances[i]; - Mobile m = ns.Mobile; + for (int i = 0; i < NetState.Instances.Count; ++i) + { + NetState ns = NetState.Instances[i]; + Mobile m = ns.Mobile; - m?.CheckLightLevels( false ); - } - } - } + m?.CheckLightLevels(false); + } + } + } - public static void Initialize() - { - new LightCycleTimer().Start(); - EventSink.Login += OnLogin; + public static void Initialize() + { + new LightCycleTimer().Start(); + EventSink.Login += OnLogin; - CommandSystem.Register( "GlobalLight", AccessLevel.GameMaster, Light_OnCommand ); - } + CommandSystem.Register("GlobalLight", AccessLevel.GameMaster, Light_OnCommand); + } - [Usage( "GlobalLight " )] - [Description( "Sets the current global light level." )] - private static void Light_OnCommand( CommandEventArgs e ) - { - if ( e.Length >= 1 ) - { - LevelOverride = e.GetInt32( 0 ); - e.Mobile.SendMessage( "Global light level override has been changed to {0}.", m_LevelOverride ); - } - else - { - LevelOverride = int.MinValue; - e.Mobile.SendMessage( "Global light level override has been cleared." ); - } - } + [Usage("GlobalLight ")] + [Description("Sets the current global light level.")] + private static void Light_OnCommand(CommandEventArgs e) + { + if (e.Length >= 1) + { + LevelOverride = e.GetInt32(0); + e.Mobile.SendMessage("Global light level override has been changed to {0}.", m_LevelOverride); + } + else + { + LevelOverride = int.MinValue; + e.Mobile.SendMessage("Global light level override has been cleared."); + } + } - public static void OnLogin( LoginEventArgs args ) - { - Mobile m = args.Mobile; + public static void OnLogin(LoginEventArgs args) + { + Mobile m = args.Mobile; - m.CheckLightLevels( true ); - } + m.CheckLightLevels(true); + } - public static int ComputeLevelFor( Mobile from ) - { - if ( m_LevelOverride > int.MinValue ) - return m_LevelOverride; + public static int ComputeLevelFor(Mobile from) + { + if (m_LevelOverride > int.MinValue) + return m_LevelOverride; - int hours, minutes; + int hours, minutes; - Items.Clock.GetTime( from.Map, from.X, from.Y, out hours, out minutes ); + Clock.GetTime(from.Map, from.X, from.Y, out hours, out minutes); - /* OSI times: - * - * Midnight -> 3:59 AM : Night - * 4:00 AM -> 11:59 PM : Day - * - * RunUO times: - * - * 10:00 PM -> 11:59 PM : Scale to night - * Midnight -> 3:59 AM : Night - * 4:00 AM -> 5:59 AM : Scale to day - * 6:00 AM -> 9:59 PM : Day - */ + /* OSI times: + * + * Midnight -> 3:59 AM : Night + * 4:00 AM -> 11:59 PM : Day + * + * RunUO times: + * + * 10:00 PM -> 11:59 PM : Scale to night + * Midnight -> 3:59 AM : Night + * 4:00 AM -> 5:59 AM : Scale to day + * 6:00 AM -> 9:59 PM : Day + */ - if ( hours < 4 ) - return NightLevel; + if (hours < 4) + return NightLevel; - if ( hours < 6 ) - return NightLevel + (((((hours - 4) * 60) + minutes) * (DayLevel - NightLevel)) / 120); + if (hours < 6) + return NightLevel + ((hours - 4) * 60 + minutes) * (DayLevel - NightLevel) / 120; - if ( hours < 22 ) - return DayLevel; + if (hours < 22) + return DayLevel; - if ( hours < 24 ) - return DayLevel + (((((hours - 22) * 60) + minutes) * (NightLevel - DayLevel)) / 120); + if (hours < 24) + return DayLevel + ((hours - 22) * 60 + minutes) * (NightLevel - DayLevel) / 120; - return NightLevel; // should never be - } + return NightLevel; // should never be + } - private class LightCycleTimer : Timer - { - public LightCycleTimer() : base( TimeSpan.FromSeconds( 0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - Priority = TimerPriority.FiveSeconds; - } + private class LightCycleTimer : Timer + { + public LightCycleTimer() : base(TimeSpan.FromSeconds(0), TimeSpan.FromSeconds(5.0)) + { + Priority = TimerPriority.FiveSeconds; + } - protected override void OnTick() - { - for ( int i = 0; i < NetState.Instances.Count; ++i ) - { - NetState ns = NetState.Instances[i]; - Mobile m = ns.Mobile; + protected override void OnTick() + { + for (int i = 0; i < NetState.Instances.Count; ++i) + { + NetState ns = NetState.Instances[i]; + Mobile m = ns.Mobile; - m?.CheckLightLevels( false ); - } - } - } + m?.CheckLightLevels(false); + } + } + } - public class NightSightTimer : Timer - { - private Mobile m_Owner; + public class NightSightTimer : Timer + { + private Mobile m_Owner; - public NightSightTimer( Mobile owner ) : base( TimeSpan.FromMinutes( Utility.Random( 15, 25 ) ) ) - { - m_Owner = owner; - Priority = TimerPriority.OneMinute; - } + public NightSightTimer(Mobile owner) : base(TimeSpan.FromMinutes(Utility.Random(15, 25))) + { + m_Owner = owner; + Priority = TimerPriority.OneMinute; + } - protected override void OnTick() - { - m_Owner.EndAction( typeof( LightCycle ) ); - m_Owner.LightLevel = 0; - BuffInfo.RemoveBuff( m_Owner, BuffIcon.NightSight ); - } - } - } -} + protected override void OnTick() + { + m_Owner.EndAction(typeof(LightCycle)); + m_Owner.LightLevel = 0; + BuffInfo.RemoveBuff(m_Owner, BuffIcon.NightSight); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/LoginStats.cs b/Scripts/Misc/LoginStats.cs index bc166a124..69985c921 100644 --- a/Scripts/Misc/LoginStats.cs +++ b/Scripts/Misc/LoginStats.cs @@ -2,28 +2,29 @@ using Server.Network; namespace Server.Misc { - public class LoginStats - { - public static void Initialize() - { - // Register our event handler - EventSink.Login += EventSink_Login; - } + public class LoginStats + { + public static void Initialize() + { + // Register our event handler + EventSink.Login += EventSink_Login; + } - private static void EventSink_Login( LoginEventArgs args ) - { - int userCount = NetState.Instances.Count; - int itemCount = World.Items.Count; - int mobileCount = World.Mobiles.Count; + private static void EventSink_Login(LoginEventArgs args) + { + int userCount = NetState.Instances.Count; + int itemCount = World.Items.Count; + int mobileCount = World.Mobiles.Count; - Mobile m = args.Mobile; + Mobile m = args.Mobile; - m.SendMessage( "Welcome, {0}! There {1} currently {2} user{3} online, with {4} item{5} and {6} mobile{7} in the world.", - args.Mobile.Name, - userCount == 1 ? "is" : "are", - userCount, userCount == 1 ? "" : "s", - itemCount, itemCount == 1 ? "" : "s", - mobileCount, mobileCount == 1 ? "" : "s" ); - } - } + m.SendMessage( + "Welcome, {0}! There {1} currently {2} user{3} online, with {4} item{5} and {6} mobile{7} in the world.", + args.Mobile.Name, + userCount == 1 ? "is" : "are", + userCount, userCount == 1 ? "" : "s", + itemCount, itemCount == 1 ? "" : "s", + mobileCount, mobileCount == 1 ? "" : "s"); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Loot.cs b/Scripts/Misc/Loot.cs index fad2eba1e..4ffc7b06e 100644 --- a/Scripts/Misc/Loot.cs +++ b/Scripts/Misc/Loot.cs @@ -3,765 +3,815 @@ using Server.Items; namespace Server { - public class Loot - { - #region List definitions - - #region Mondain's Legacy - - public static Type[] MLWeaponTypes { get; } = - { - typeof( AssassinSpike ), typeof( DiamondMace ), typeof( ElvenMachete ), - typeof( ElvenSpellblade ), typeof( Leafblade ), typeof( OrnateAxe ), - typeof( RadiantScimitar ), typeof( RuneBlade ), typeof( WarCleaver ), - typeof( WildStaff ) - }; - - public static Type[] MLRangedWeaponTypes { get; } = - { - typeof( ElvenCompositeLongbow ), typeof( MagicalShortbow ) - }; - - public static Type[] MLArmorTypes { get; } = - { - typeof( Circlet ), typeof( GemmedCirclet ), typeof( LeafTonlet ), - typeof( RavenHelm ), typeof( RoyalCirclet ), typeof( VultureHelm ), - typeof( WingedHelm ), typeof( LeafArms ), typeof( LeafChest ), - typeof( LeafGloves ), typeof( LeafGorget ), typeof( LeafLegs ), - typeof( WoodlandArms ), typeof( WoodlandChest ), typeof( WoodlandGloves ), - typeof( WoodlandGorget ), typeof( WoodlandLegs ), typeof( HideChest ), - typeof( HideGloves ), typeof( HideGorget ), typeof( HidePants ), - typeof( HidePauldrons ) - }; - - public static Type[] MLClothingTypes { get; } = - { - typeof( MaleElvenRobe ), typeof( FemaleElvenRobe ), typeof( ElvenPants ), - typeof( ElvenShirt ), typeof( ElvenDarkShirt ), typeof( ElvenBoots ), - typeof( VultureHelm ), typeof( WoodlandBelt ) - }; - - #endregion - - public static Type[] SEWeaponTypes { get; } = - { - typeof( Bokuto ), typeof( Daisho ), typeof( Kama ), - typeof( Lajatang ), typeof( NoDachi ), typeof( Nunchaku ), - typeof( Sai ), typeof( Tekagi ), typeof( Tessen ), - typeof( Tetsubo ), typeof( Wakizashi ) - }; - - public static Type[] AosWeaponTypes { get; } = - { - typeof( Scythe ), typeof( BoneHarvester ), typeof( Scepter ), - typeof( BladedStaff ), typeof( Pike ), typeof( DoubleBladedStaff ), - typeof( Lance ), typeof( CrescentBlade ) - }; - - public static Type[] WeaponTypes { get; } = - { - typeof( Axe ), typeof( BattleAxe ), typeof( DoubleAxe ), - typeof( ExecutionersAxe ), typeof( Hatchet ), typeof( LargeBattleAxe ), - typeof( TwoHandedAxe ), typeof( WarAxe ), typeof( Club ), - typeof( Mace ), typeof( Maul ), typeof( WarHammer ), - typeof( WarMace ), typeof( Bardiche ), typeof( Halberd ), - typeof( Spear ), typeof( ShortSpear ), typeof( Pitchfork ), - typeof( WarFork ), typeof( BlackStaff ), typeof( GnarledStaff ), - typeof( QuarterStaff ), typeof( Broadsword ), typeof( Cutlass ), - typeof( Katana ), typeof( Kryss ), typeof( Longsword ), - typeof( Scimitar ), typeof( VikingSword ), typeof( Pickaxe ), - typeof( HammerPick ), typeof( ButcherKnife ), typeof( Cleaver ), - typeof( Dagger ), typeof( SkinningKnife ), typeof( ShepherdsCrook ) - }; - - public static Type[] SERangedWeaponTypes { get; } = - { - typeof( Yumi ) - }; - - public static Type[] AosRangedWeaponTypes { get; } = - { - typeof( CompositeBow ), typeof( RepeatingCrossbow ) - }; - - public static Type[] RangedWeaponTypes { get; } = - { - typeof( Bow ), typeof( Crossbow ), typeof( HeavyCrossbow ) - }; - - public static Type[] SEArmorTypes { get; } = - { - typeof( ChainHatsuburi ), typeof( LeatherDo ), typeof( LeatherHaidate ), - typeof( LeatherHiroSode ), typeof( LeatherJingasa ), typeof( LeatherMempo ), - typeof( LeatherNinjaHood ), typeof( LeatherNinjaJacket ), typeof( LeatherNinjaMitts ), - typeof( LeatherNinjaPants ), typeof( LeatherSuneate ), typeof( DecorativePlateKabuto ), - typeof( HeavyPlateJingasa ), typeof( LightPlateJingasa ), typeof( PlateBattleKabuto ), - typeof( PlateDo ), typeof( PlateHaidate ), typeof( PlateHatsuburi ), - typeof( PlateHiroSode ), typeof( PlateMempo ), typeof( PlateSuneate ), - typeof( SmallPlateJingasa ), typeof( StandardPlateKabuto ), typeof( StuddedDo ), - typeof( StuddedHaidate ), typeof( StuddedHiroSode ), typeof( StuddedMempo ), - typeof( StuddedSuneate ) - }; - - public static Type[] ArmorTypes { get; } = - { - typeof( BoneArms ), typeof( BoneChest ), typeof( BoneGloves ), - typeof( BoneLegs ), typeof( BoneHelm ), typeof( ChainChest ), - typeof( ChainLegs ), typeof( ChainCoif ), typeof( Bascinet ), - typeof( CloseHelm ), typeof( Helmet ), typeof( NorseHelm ), - typeof( OrcHelm ), typeof( FemaleLeatherChest ), typeof( LeatherArms ), - typeof( LeatherBustierArms ), typeof( LeatherChest ), typeof( LeatherGloves ), - typeof( LeatherGorget ), typeof( LeatherLegs ), typeof( LeatherShorts ), - typeof( LeatherSkirt ), typeof( LeatherCap ), typeof( FemalePlateChest ), - typeof( PlateArms ), typeof( PlateChest ), typeof( PlateGloves ), - typeof( PlateGorget ), typeof( PlateHelm ), typeof( PlateLegs ), - typeof( RingmailArms ), typeof( RingmailChest ), typeof( RingmailGloves ), - typeof( RingmailLegs ), typeof( FemaleStuddedChest ), typeof( StuddedArms ), - typeof( StuddedBustierArms ), typeof( StuddedChest ), typeof( StuddedGloves ), - typeof( StuddedGorget ), typeof( StuddedLegs ) - }; - - public static Type[] AosShieldTypes { get; } = - { - typeof( ChaosShield ), typeof( OrderShield ) - }; - - public static Type[] ShieldTypes { get; } = - { - typeof( BronzeShield ), typeof( Buckler ), typeof( HeaterShield ), - typeof( MetalShield ), typeof( MetalKiteShield ), typeof( WoodenKiteShield ), - typeof( WoodenShield ) - }; - - public static Type[] GemTypes { get; } = - { - typeof( Amber ), typeof( Amethyst ), typeof( Citrine ), - typeof( Diamond ), typeof( Emerald ), typeof( Ruby ), - typeof( Sapphire ), typeof( StarSapphire ), typeof( Tourmaline ) - }; - - public static Type[] JewelryTypes { get; } = - { - typeof( GoldRing ), typeof( GoldBracelet ), - typeof( SilverRing ), typeof( SilverBracelet ) - }; - - public static Type[] RegTypes { get; } = - { - typeof( BlackPearl ), typeof( Bloodmoss ), typeof( Garlic ), - typeof( Ginseng ), typeof( MandrakeRoot ), typeof( Nightshade ), - typeof( SulfurousAsh ), typeof( SpidersSilk ) - }; - - public static Type[] NecroRegTypes { get; } = - { - typeof( BatWing ), typeof( GraveDust ), typeof( DaemonBlood ), - typeof( NoxCrystal ), typeof( PigIron ) - }; - - public static Type[] PotionTypes { get; } = - { - typeof( AgilityPotion ), typeof( StrengthPotion ), typeof( RefreshPotion ), - typeof( LesserCurePotion ), typeof( LesserHealPotion ), typeof( LesserPoisonPotion ) - }; - - public static Type[] SEInstrumentTypes { get; } = - { - typeof( BambooFlute ) - }; - - public static Type[] InstrumentTypes { get; } = - { - typeof( Drums ), typeof( Harp ), typeof( LapHarp ), - typeof( Lute ), typeof( Tambourine ), typeof( TambourineTassel ) - }; - - public static Type[] StatueTypes { get; } = - { - typeof( StatueSouth ), typeof( StatueSouth2 ), typeof( StatueNorth ), - typeof( StatueWest ), typeof( StatueEast ), typeof( StatueEast2 ), - typeof( StatueSouthEast ), typeof( BustSouth ), typeof( BustEast ) - }; - - #region Mondain's Legacy - - #endregion - - public static Type[] RegularScrollTypes { get; } = - { - typeof( ReactiveArmorScroll ), typeof( ClumsyScroll ), typeof( CreateFoodScroll ), typeof( FeeblemindScroll ), - typeof( HealScroll ), typeof( MagicArrowScroll ), typeof( NightSightScroll ), typeof( WeakenScroll ), - typeof( AgilityScroll ), typeof( CunningScroll ), typeof( CureScroll ), typeof( HarmScroll ), - typeof( MagicTrapScroll ), typeof( MagicUnTrapScroll ), typeof( ProtectionScroll ), typeof( StrengthScroll ), - typeof( BlessScroll ), typeof( FireballScroll ), typeof( MagicLockScroll ), typeof( PoisonScroll ), - typeof( TelekinisisScroll ), typeof( TeleportScroll ), typeof( UnlockScroll ), typeof( WallOfStoneScroll ), - typeof( ArchCureScroll ), typeof( ArchProtectionScroll ), typeof( CurseScroll ), typeof( FireFieldScroll ), - typeof( GreaterHealScroll ), typeof( LightningScroll ), typeof( ManaDrainScroll ), typeof( RecallScroll ), - typeof( BladeSpiritsScroll ), typeof( DispelFieldScroll ), typeof( IncognitoScroll ), typeof( MagicReflectScroll ), - typeof( MindBlastScroll ), typeof( ParalyzeScroll ), typeof( PoisonFieldScroll ), typeof( SummonCreatureScroll ), - typeof( DispelScroll ), typeof( EnergyBoltScroll ), typeof( ExplosionScroll ), typeof( InvisibilityScroll ), - typeof( MarkScroll ), typeof( MassCurseScroll ), typeof( ParalyzeFieldScroll ), typeof( RevealScroll ), - typeof( ChainLightningScroll ), typeof( EnergyFieldScroll ), typeof( FlamestrikeScroll ), typeof( GateTravelScroll ), - typeof( ManaVampireScroll ), typeof( MassDispelScroll ), typeof( MeteorSwarmScroll ), typeof( PolymorphScroll ), - typeof( EarthquakeScroll ), typeof( EnergyVortexScroll ), typeof( ResurrectionScroll ), typeof( SummonAirElementalScroll ), - typeof( SummonDaemonScroll ), typeof( SummonEarthElementalScroll ), typeof( SummonFireElementalScroll ), typeof( SummonWaterElementalScroll ) - }; - - public static Type[] NecromancyScrollTypes { get; } = - { - typeof( AnimateDeadScroll ), typeof( BloodOathScroll ), typeof( CorpseSkinScroll ), typeof( CurseWeaponScroll ), - typeof( EvilOmenScroll ), typeof( HorrificBeastScroll ), typeof( LichFormScroll ), typeof( MindRotScroll ), - typeof( PainSpikeScroll ), typeof( PoisonStrikeScroll ), typeof( StrangleScroll ), typeof( SummonFamiliarScroll ), - typeof( VampiricEmbraceScroll ), typeof( VengefulSpiritScroll ), typeof( WitherScroll ), typeof( WraithFormScroll ) - }; - - public static Type[] SENecromancyScrollTypes { get; } = - { - typeof( AnimateDeadScroll ), typeof( BloodOathScroll ), typeof( CorpseSkinScroll ), typeof( CurseWeaponScroll ), - typeof( EvilOmenScroll ), typeof( HorrificBeastScroll ), typeof( LichFormScroll ), typeof( MindRotScroll ), - typeof( PainSpikeScroll ), typeof( PoisonStrikeScroll ), typeof( StrangleScroll ), typeof( SummonFamiliarScroll ), - typeof( VampiricEmbraceScroll ), typeof( VengefulSpiritScroll ), typeof( WitherScroll ), typeof( WraithFormScroll ), - typeof( ExorcismScroll ) - }; - - public static Type[] PaladinScrollTypes { get; } = new Type[0]; - - #region Mondain's Legacy - public static Type[] ArcanistScrollTypes { get; } = - { - typeof( ArcaneCircleScroll ), typeof( GiftOfRenewalScroll ), typeof( ImmolatingWeaponScroll ), typeof( AttuneWeaponScroll ), - typeof( ThunderstormScroll ), typeof( NatureFuryScroll ), /*typeof( SummonFeyScroll ), typeof( SummonFiendScroll ),*/ - typeof( ReaperFormScroll ), typeof( WildfireScroll ), typeof( EssenceOfWindScroll ), typeof( DryadAllureScroll ), - typeof( EtherealVoyageScroll ), typeof( WordOfDeathScroll ), typeof( GiftOfLifeScroll ), typeof( ArcaneEmpowermentScroll ) - }; - - #endregion - - public static Type[] GrimmochJournalTypes { get; } = - { - typeof( GrimmochJournal1 ), typeof( GrimmochJournal2 ), typeof( GrimmochJournal3 ), - typeof( GrimmochJournal6 ), typeof( GrimmochJournal7 ), typeof( GrimmochJournal11 ), - typeof( GrimmochJournal14 ), typeof( GrimmochJournal17 ), typeof( GrimmochJournal23 ) - }; - - public static Type[] LysanderNotebookTypes { get; } = - { - typeof( LysanderNotebook1 ), typeof( LysanderNotebook2 ), typeof( LysanderNotebook3 ), - typeof( LysanderNotebook7 ), typeof( LysanderNotebook8 ), typeof( LysanderNotebook11 ) - }; - - public static Type[] TavarasJournalTypes { get; } = - { - typeof( TavarasJournal1 ), typeof( TavarasJournal2 ), typeof( TavarasJournal3 ), - typeof( TavarasJournal6 ), typeof( TavarasJournal7 ), typeof( TavarasJournal8 ), - typeof( TavarasJournal9 ), typeof( TavarasJournal11 ), typeof( TavarasJournal14 ), - typeof( TavarasJournal16 ), typeof( TavarasJournal16b ), typeof( TavarasJournal17 ), - typeof( TavarasJournal19 ) - }; - - - public static Type[] NewWandTypes { get; } = - { - typeof( FireballWand ), typeof( LightningWand ), typeof( MagicArrowWand ), - typeof( GreaterHealWand ), typeof( HarmWand ), typeof( HealWand ) - }; - - public static Type[] WandTypes { get; } = - { - typeof( ClumsyWand ), typeof( FeebleWand ), - typeof( ManaDrainWand ), typeof( WeaknessWand ) - }; - - public static Type[] OldWandTypes { get; } = - { - typeof( IDWand ) - }; - - public static Type[] SEClothingTypes { get; } = - { - typeof( ClothNinjaJacket ), typeof( FemaleKimono ), typeof( Hakama ), - typeof( HakamaShita ), typeof( JinBaori ), typeof( Kamishimo ), - typeof( MaleKimono ), typeof( NinjaTabi ), typeof( Obi ), - typeof( SamuraiTabi ), typeof( TattsukeHakama ), typeof( Waraji ) - }; - - public static Type[] AosClothingTypes { get; } = - { - typeof( FurSarong ), typeof( FurCape ), typeof( FlowerGarland ), - typeof( GildedDress ), typeof( FurBoots ), typeof( FormalShirt ), - }; - - public static Type[] ClothingTypes { get; } = - { - typeof( Cloak ), - typeof( Bonnet ), typeof( Cap ), typeof( FeatheredHat ), - typeof( FloppyHat ), typeof( JesterHat ), typeof( Surcoat ), - typeof( SkullCap ), typeof( StrawHat ), typeof( TallStrawHat ), - typeof( TricorneHat ), typeof( WideBrimHat ), typeof( WizardsHat ), - typeof( BodySash ), typeof( Doublet ), typeof( Boots ), - typeof( FullApron ), typeof( JesterSuit ), typeof( Sandals ), - typeof( Tunic ), typeof( Shoes ), typeof( Shirt ), - typeof( Kilt ), typeof( Skirt ), typeof( FancyShirt ), - typeof( FancyDress ), typeof( ThighBoots ), typeof( LongPants ), - typeof( PlainDress ), typeof( Robe ), typeof( ShortPants ), - typeof( HalfApron ) - }; - - public static Type[] SEHatTypes { get; } = - { - typeof( ClothNinjaHood ), typeof( Kasa ) - }; - - public static Type[] AosHatTypes { get; } = - { - typeof( FlowerGarland ), typeof( BearMask ), typeof( DeerMask ) //Are Bear& Deer mask inside the Pre-AoS loottables too? - }; - - public static Type[] HatTypes { get; } = - { - typeof( SkullCap ), typeof( Bandana ), typeof( FloppyHat ), - typeof( Cap ), typeof( WideBrimHat ), typeof( StrawHat ), - typeof( TallStrawHat ), typeof( WizardsHat ), typeof( Bonnet ), - typeof( FeatheredHat ), typeof( TricorneHat ), typeof( JesterHat ) - }; - - public static Type[] LibraryBookTypes { get; } = - { - typeof( GrammarOfOrcish ), typeof( CallToAnarchy ), typeof( ArmsAndWeaponsPrimer ), - typeof( SongOfSamlethe ), typeof( TaleOfThreeTribes ), typeof( GuideToGuilds ), - typeof( BirdsOfBritannia ), typeof( BritannianFlora ), typeof( ChildrenTalesVol2 ), - typeof( TalesOfVesperVol1 ), typeof( DeceitDungeonOfHorror ), typeof( DimensionalTravel ), - typeof( EthicalHedonism ), typeof( MyStory ), typeof( DiversityOfOurLand ), - typeof( QuestOfVirtues ), typeof( RegardingLlamas ), typeof( TalkingToWisps ), - typeof( TamingDragons ), typeof( BoldStranger ), typeof( BurningOfTrinsic ), - typeof( TheFight ), typeof( LifeOfATravellingMinstrel ), typeof( MajorTradeAssociation ), - typeof( RankingsOfTrades ), typeof( WildGirlOfTheForest ), typeof( TreatiseOnAlchemy ), - typeof( VirtueBook ) - }; - - #endregion - - #region Accessors - - public static BaseWand RandomWand() - { - if ( Core.ML ) - return Construct( NewWandTypes ) as BaseWand; - if ( Core.AOS ) - return Construct( WandTypes, NewWandTypes ) as BaseWand; - return Construct( OldWandTypes, WandTypes, NewWandTypes ) as BaseWand; - } - - public static BaseClothing RandomClothing() - { - return RandomClothing( false, false ); - } - - public static BaseClothing RandomClothing( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLClothingTypes, AosClothingTypes, ClothingTypes ) as BaseClothing; - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEClothingTypes, AosClothingTypes, ClothingTypes ) as BaseClothing; - - if ( Core.AOS ) - return Construct( AosClothingTypes, ClothingTypes ) as BaseClothing; - - return Construct( ClothingTypes ) as BaseClothing; - } - - public static BaseWeapon RandomRangedWeapon() - { - return RandomRangedWeapon( false, false ); - } - - public static BaseWeapon RandomRangedWeapon( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLRangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes ) as BaseWeapon; - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SERangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes ) as BaseWeapon; - - if ( Core.AOS ) - return Construct( AosRangedWeaponTypes, RangedWeaponTypes ) as BaseWeapon; - - return Construct( RangedWeaponTypes ) as BaseWeapon; - } - - public static BaseWeapon RandomWeapon() - { - return RandomWeapon( false, false ); - } - - public static BaseWeapon RandomWeapon( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLWeaponTypes, AosWeaponTypes, WeaponTypes ) as BaseWeapon; - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEWeaponTypes, AosWeaponTypes, WeaponTypes ) as BaseWeapon; - - if ( Core.AOS ) - return Construct( AosWeaponTypes, WeaponTypes ) as BaseWeapon; - - return Construct( WeaponTypes ) as BaseWeapon; - } - - public static Item RandomWeaponOrJewelry() - { - return RandomWeaponOrJewelry( false, false ); - } - - public static Item RandomWeaponOrJewelry( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLWeaponTypes, AosWeaponTypes, WeaponTypes, JewelryTypes ); - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEWeaponTypes, AosWeaponTypes, WeaponTypes, JewelryTypes ); - - if ( Core.AOS ) - return Construct( AosWeaponTypes, WeaponTypes, JewelryTypes ); - - return Construct( WeaponTypes, JewelryTypes ); - } - - public static BaseJewel RandomJewelry() - { - return Construct( JewelryTypes ) as BaseJewel; - } - - public static BaseArmor RandomArmor() - { - return RandomArmor( false, false ); - } - - public static BaseArmor RandomArmor( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLArmorTypes, ArmorTypes ) as BaseArmor; - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEArmorTypes, ArmorTypes ) as BaseArmor; - - return Construct( ArmorTypes ) as BaseArmor; - } - - public static BaseHat RandomHat() - { - return RandomHat( false ); - } - - public static BaseHat RandomHat( bool inTokuno ) - { - if ( Core.SE && inTokuno ) - return Construct( SEHatTypes, AosHatTypes, HatTypes ) as BaseHat; - - if ( Core.AOS ) - return Construct( AosHatTypes, HatTypes ) as BaseHat; - - return Construct( HatTypes ) as BaseHat; - } - - public static Item RandomArmorOrHat() - { - return RandomArmorOrHat( false, false ); - } - - public static Item RandomArmorOrHat( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes ); - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes ); - - if ( Core.AOS ) - return Construct( ArmorTypes, AosHatTypes, HatTypes ); - - return Construct( ArmorTypes, HatTypes ); - } - - public static BaseShield RandomShield() - { - if ( Core.AOS ) - return Construct( AosShieldTypes, ShieldTypes ) as BaseShield; - - return Construct( ShieldTypes ) as BaseShield; - } - - public static BaseArmor RandomArmorOrShield() - { - return RandomArmorOrShield( false, false ); - } - - public static BaseArmor RandomArmorOrShield( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLArmorTypes, ArmorTypes, AosShieldTypes, ShieldTypes ) as BaseArmor; - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEArmorTypes, ArmorTypes, AosShieldTypes, ShieldTypes ) as BaseArmor; - - if ( Core.AOS ) - return Construct( ArmorTypes, AosShieldTypes, ShieldTypes ) as BaseArmor; - - return Construct( ArmorTypes, ShieldTypes ) as BaseArmor; - } - - public static Item RandomArmorOrShieldOrJewelry() - { - return RandomArmorOrShieldOrJewelry( false, false ); - } - - public static Item RandomArmorOrShieldOrJewelry( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes ); - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes ); - - if ( Core.AOS ) - return Construct( ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes ); - - return Construct( ArmorTypes, HatTypes, ShieldTypes, JewelryTypes ); - } - - public static Item RandomArmorOrShieldOrWeapon() - { - return RandomArmorOrShieldOrWeapon( false, false ); - } - - public static Item RandomArmorOrShieldOrWeapon( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLWeaponTypes, AosWeaponTypes, WeaponTypes, MLRangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes ); - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEWeaponTypes, AosWeaponTypes, WeaponTypes, SERangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes ); - - if ( Core.AOS ) - return Construct( AosWeaponTypes, WeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes ); - - return Construct( WeaponTypes, RangedWeaponTypes, ArmorTypes, HatTypes, ShieldTypes ); - } - - public static Item RandomArmorOrShieldOrWeaponOrJewelry() - { - return RandomArmorOrShieldOrWeaponOrJewelry( false, false ); - } - - public static Item RandomArmorOrShieldOrWeaponOrJewelry( bool inTokuno, bool isMondain ) - { - #region Mondain's Legacy - if ( Core.ML && isMondain ) - return Construct( MLWeaponTypes, AosWeaponTypes, WeaponTypes, MLRangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes ); - #endregion - - if ( Core.SE && inTokuno ) - return Construct( SEWeaponTypes, AosWeaponTypes, WeaponTypes, SERangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes ); - - if ( Core.AOS ) - return Construct( AosWeaponTypes, WeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes ); - - return Construct( WeaponTypes, RangedWeaponTypes, ArmorTypes, HatTypes, ShieldTypes, JewelryTypes ); - } - - #region Chest of Heirlooms - public static Item ChestOfHeirloomsContains() - { - return Construct( SEArmorTypes, SEHatTypes, SEWeaponTypes, SERangedWeaponTypes, JewelryTypes ); - } - #endregion - - public static Item RandomGem() - { - return Construct( GemTypes ); - } - - public static Item RandomReagent() - { - return Construct( RegTypes ); - } - - public static Item RandomNecromancyReagent() - { - return Construct( NecroRegTypes ); - } - - public static Item RandomPossibleReagent() - { - if ( Core.AOS ) - return Construct( RegTypes, NecroRegTypes ); - - return Construct( RegTypes ); - } - - public static Item RandomPotion() - { - return Construct( PotionTypes ); - } - - public static BaseInstrument RandomInstrument() - { - if ( Core.SE ) - return Construct( InstrumentTypes, SEInstrumentTypes ) as BaseInstrument; - - return Construct( InstrumentTypes ) as BaseInstrument; - } - - public static Item RandomStatue() - { - return Construct( StatueTypes ); - } - - public static SpellScroll RandomScroll( int minIndex, int maxIndex, SpellbookType type ) - { - Type[] types; - - switch ( type ) - { - default: - case SpellbookType.Regular: types = RegularScrollTypes; break; - case SpellbookType.Necromancer: types = (Core.SE ? SENecromancyScrollTypes : NecromancyScrollTypes ); break; - case SpellbookType.Paladin: types = PaladinScrollTypes; break; - case SpellbookType.Arcanist: types = ArcanistScrollTypes; break; - } - - return Construct( types, Utility.RandomMinMax( minIndex, maxIndex ) ) as SpellScroll; - } - - public static BaseBook RandomGrimmochJournal() - { - return Construct( GrimmochJournalTypes ) as BaseBook; - } - - public static BaseBook RandomLysanderNotebook() - { - return Construct( LysanderNotebookTypes ) as BaseBook; - } - - public static BaseBook RandomTavarasJournal() - { - return Construct( TavarasJournalTypes ) as BaseBook; - } - - public static BaseBook RandomLibraryBook() - { - return Construct( LibraryBookTypes ) as BaseBook; - } - - public static BaseTalisman RandomTalisman() - { - BaseTalisman talisman = new BaseTalisman( BaseTalisman.GetRandomItemID() ); - - talisman.Summoner = BaseTalisman.GetRandomSummoner(); - - if ( talisman.Summoner.IsEmpty ) - { - talisman.Removal = BaseTalisman.GetRandomRemoval(); - - if ( talisman.Removal != TalismanRemoval.None ) - { - talisman.MaxCharges = BaseTalisman.GetRandomCharges(); - talisman.MaxChargeTime = 1200; - } - } - else - { - talisman.MaxCharges = Utility.RandomMinMax( 10, 50 ); - - if ( talisman.Summoner.IsItem ) - talisman.MaxChargeTime = 60; - else - talisman.MaxChargeTime = 1800; - } - - talisman.Blessed = BaseTalisman.GetRandomBlessed(); - talisman.Slayer = BaseTalisman.GetRandomSlayer(); - talisman.Protection = BaseTalisman.GetRandomProtection(); - talisman.Killer = BaseTalisman.GetRandomKiller(); - talisman.Skill = BaseTalisman.GetRandomSkill(); - talisman.ExceptionalBonus = BaseTalisman.GetRandomExceptional(); - talisman.SuccessBonus = BaseTalisman.GetRandomSuccessful(); - talisman.Charges = talisman.MaxCharges; - - return talisman; - } - #endregion - - #region Construction methods - public static Item Construct( Type type ) - { - try - { - return Activator.CreateInstance( type ) as Item; - } - catch - { - return null; - } - } - - public static Item Construct( Type[] types ) - { - if ( types.Length > 0 ) - return Construct( types, Utility.Random( types.Length ) ); - - return null; - } - - public static Item Construct( Type[] types, int index ) - { - if ( index >= 0 && index < types.Length ) - return Construct( types[index] ); - - return null; - } - - public static Item Construct( params Type[][] types ) - { - int totalLength = 0; - - for ( int i = 0; i < types.Length; ++i ) - totalLength += types[i].Length; - - if ( totalLength > 0 ) - { - int index = Utility.Random( totalLength ); - - for ( int i = 0; i < types.Length; ++i ) - { - if ( index >= 0 && index < types[i].Length ) - return Construct( types[i][index] ); - - index -= types[i].Length; - } - } - - return null; - } - #endregion - } + public class Loot + { + #region List definitions + + #region Mondain's Legacy + + public static Type[] MLWeaponTypes{ get; } = + { + typeof(AssassinSpike), typeof(DiamondMace), typeof(ElvenMachete), + typeof(ElvenSpellblade), typeof(Leafblade), typeof(OrnateAxe), + typeof(RadiantScimitar), typeof(RuneBlade), typeof(WarCleaver), + typeof(WildStaff) + }; + + public static Type[] MLRangedWeaponTypes{ get; } = + { + typeof(ElvenCompositeLongbow), typeof(MagicalShortbow) + }; + + public static Type[] MLArmorTypes{ get; } = + { + typeof(Circlet), typeof(GemmedCirclet), typeof(LeafTonlet), + typeof(RavenHelm), typeof(RoyalCirclet), typeof(VultureHelm), + typeof(WingedHelm), typeof(LeafArms), typeof(LeafChest), + typeof(LeafGloves), typeof(LeafGorget), typeof(LeafLegs), + typeof(WoodlandArms), typeof(WoodlandChest), typeof(WoodlandGloves), + typeof(WoodlandGorget), typeof(WoodlandLegs), typeof(HideChest), + typeof(HideGloves), typeof(HideGorget), typeof(HidePants), + typeof(HidePauldrons) + }; + + public static Type[] MLClothingTypes{ get; } = + { + typeof(MaleElvenRobe), typeof(FemaleElvenRobe), typeof(ElvenPants), + typeof(ElvenShirt), typeof(ElvenDarkShirt), typeof(ElvenBoots), + typeof(VultureHelm), typeof(WoodlandBelt) + }; + + #endregion + + public static Type[] SEWeaponTypes{ get; } = + { + typeof(Bokuto), typeof(Daisho), typeof(Kama), + typeof(Lajatang), typeof(NoDachi), typeof(Nunchaku), + typeof(Sai), typeof(Tekagi), typeof(Tessen), + typeof(Tetsubo), typeof(Wakizashi) + }; + + public static Type[] AosWeaponTypes{ get; } = + { + typeof(Scythe), typeof(BoneHarvester), typeof(Scepter), + typeof(BladedStaff), typeof(Pike), typeof(DoubleBladedStaff), + typeof(Lance), typeof(CrescentBlade) + }; + + public static Type[] WeaponTypes{ get; } = + { + typeof(Axe), typeof(BattleAxe), typeof(DoubleAxe), + typeof(ExecutionersAxe), typeof(Hatchet), typeof(LargeBattleAxe), + typeof(TwoHandedAxe), typeof(WarAxe), typeof(Club), + typeof(Mace), typeof(Maul), typeof(WarHammer), + typeof(WarMace), typeof(Bardiche), typeof(Halberd), + typeof(Spear), typeof(ShortSpear), typeof(Pitchfork), + typeof(WarFork), typeof(BlackStaff), typeof(GnarledStaff), + typeof(QuarterStaff), typeof(Broadsword), typeof(Cutlass), + typeof(Katana), typeof(Kryss), typeof(Longsword), + typeof(Scimitar), typeof(VikingSword), typeof(Pickaxe), + typeof(HammerPick), typeof(ButcherKnife), typeof(Cleaver), + typeof(Dagger), typeof(SkinningKnife), typeof(ShepherdsCrook) + }; + + public static Type[] SERangedWeaponTypes{ get; } = + { + typeof(Yumi) + }; + + public static Type[] AosRangedWeaponTypes{ get; } = + { + typeof(CompositeBow), typeof(RepeatingCrossbow) + }; + + public static Type[] RangedWeaponTypes{ get; } = + { + typeof(Bow), typeof(Crossbow), typeof(HeavyCrossbow) + }; + + public static Type[] SEArmorTypes{ get; } = + { + typeof(ChainHatsuburi), typeof(LeatherDo), typeof(LeatherHaidate), + typeof(LeatherHiroSode), typeof(LeatherJingasa), typeof(LeatherMempo), + typeof(LeatherNinjaHood), typeof(LeatherNinjaJacket), typeof(LeatherNinjaMitts), + typeof(LeatherNinjaPants), typeof(LeatherSuneate), typeof(DecorativePlateKabuto), + typeof(HeavyPlateJingasa), typeof(LightPlateJingasa), typeof(PlateBattleKabuto), + typeof(PlateDo), typeof(PlateHaidate), typeof(PlateHatsuburi), + typeof(PlateHiroSode), typeof(PlateMempo), typeof(PlateSuneate), + typeof(SmallPlateJingasa), typeof(StandardPlateKabuto), typeof(StuddedDo), + typeof(StuddedHaidate), typeof(StuddedHiroSode), typeof(StuddedMempo), + typeof(StuddedSuneate) + }; + + public static Type[] ArmorTypes{ get; } = + { + typeof(BoneArms), typeof(BoneChest), typeof(BoneGloves), + typeof(BoneLegs), typeof(BoneHelm), typeof(ChainChest), + typeof(ChainLegs), typeof(ChainCoif), typeof(Bascinet), + typeof(CloseHelm), typeof(Helmet), typeof(NorseHelm), + typeof(OrcHelm), typeof(FemaleLeatherChest), typeof(LeatherArms), + typeof(LeatherBustierArms), typeof(LeatherChest), typeof(LeatherGloves), + typeof(LeatherGorget), typeof(LeatherLegs), typeof(LeatherShorts), + typeof(LeatherSkirt), typeof(LeatherCap), typeof(FemalePlateChest), + typeof(PlateArms), typeof(PlateChest), typeof(PlateGloves), + typeof(PlateGorget), typeof(PlateHelm), typeof(PlateLegs), + typeof(RingmailArms), typeof(RingmailChest), typeof(RingmailGloves), + typeof(RingmailLegs), typeof(FemaleStuddedChest), typeof(StuddedArms), + typeof(StuddedBustierArms), typeof(StuddedChest), typeof(StuddedGloves), + typeof(StuddedGorget), typeof(StuddedLegs) + }; + + public static Type[] AosShieldTypes{ get; } = + { + typeof(ChaosShield), typeof(OrderShield) + }; + + public static Type[] ShieldTypes{ get; } = + { + typeof(BronzeShield), typeof(Buckler), typeof(HeaterShield), + typeof(MetalShield), typeof(MetalKiteShield), typeof(WoodenKiteShield), + typeof(WoodenShield) + }; + + public static Type[] GemTypes{ get; } = + { + typeof(Amber), typeof(Amethyst), typeof(Citrine), + typeof(Diamond), typeof(Emerald), typeof(Ruby), + typeof(Sapphire), typeof(StarSapphire), typeof(Tourmaline) + }; + + public static Type[] JewelryTypes{ get; } = + { + typeof(GoldRing), typeof(GoldBracelet), + typeof(SilverRing), typeof(SilverBracelet) + }; + + public static Type[] RegTypes{ get; } = + { + typeof(BlackPearl), typeof(Bloodmoss), typeof(Garlic), + typeof(Ginseng), typeof(MandrakeRoot), typeof(Nightshade), + typeof(SulfurousAsh), typeof(SpidersSilk) + }; + + public static Type[] NecroRegTypes{ get; } = + { + typeof(BatWing), typeof(GraveDust), typeof(DaemonBlood), + typeof(NoxCrystal), typeof(PigIron) + }; + + public static Type[] PotionTypes{ get; } = + { + typeof(AgilityPotion), typeof(StrengthPotion), typeof(RefreshPotion), + typeof(LesserCurePotion), typeof(LesserHealPotion), typeof(LesserPoisonPotion) + }; + + public static Type[] SEInstrumentTypes{ get; } = + { + typeof(BambooFlute) + }; + + public static Type[] InstrumentTypes{ get; } = + { + typeof(Drums), typeof(Harp), typeof(LapHarp), + typeof(Lute), typeof(Tambourine), typeof(TambourineTassel) + }; + + public static Type[] StatueTypes{ get; } = + { + typeof(StatueSouth), typeof(StatueSouth2), typeof(StatueNorth), + typeof(StatueWest), typeof(StatueEast), typeof(StatueEast2), + typeof(StatueSouthEast), typeof(BustSouth), typeof(BustEast) + }; + + #region Mondain's Legacy + + #endregion + + public static Type[] RegularScrollTypes{ get; } = + { + typeof(ReactiveArmorScroll), typeof(ClumsyScroll), typeof(CreateFoodScroll), typeof(FeeblemindScroll), + typeof(HealScroll), typeof(MagicArrowScroll), typeof(NightSightScroll), typeof(WeakenScroll), + typeof(AgilityScroll), typeof(CunningScroll), typeof(CureScroll), typeof(HarmScroll), + typeof(MagicTrapScroll), typeof(MagicUnTrapScroll), typeof(ProtectionScroll), typeof(StrengthScroll), + typeof(BlessScroll), typeof(FireballScroll), typeof(MagicLockScroll), typeof(PoisonScroll), + typeof(TelekinisisScroll), typeof(TeleportScroll), typeof(UnlockScroll), typeof(WallOfStoneScroll), + typeof(ArchCureScroll), typeof(ArchProtectionScroll), typeof(CurseScroll), typeof(FireFieldScroll), + typeof(GreaterHealScroll), typeof(LightningScroll), typeof(ManaDrainScroll), typeof(RecallScroll), + typeof(BladeSpiritsScroll), typeof(DispelFieldScroll), typeof(IncognitoScroll), typeof(MagicReflectScroll), + typeof(MindBlastScroll), typeof(ParalyzeScroll), typeof(PoisonFieldScroll), typeof(SummonCreatureScroll), + typeof(DispelScroll), typeof(EnergyBoltScroll), typeof(ExplosionScroll), typeof(InvisibilityScroll), + typeof(MarkScroll), typeof(MassCurseScroll), typeof(ParalyzeFieldScroll), typeof(RevealScroll), + typeof(ChainLightningScroll), typeof(EnergyFieldScroll), typeof(FlamestrikeScroll), typeof(GateTravelScroll), + typeof(ManaVampireScroll), typeof(MassDispelScroll), typeof(MeteorSwarmScroll), typeof(PolymorphScroll), + typeof(EarthquakeScroll), typeof(EnergyVortexScroll), typeof(ResurrectionScroll), + typeof(SummonAirElementalScroll), + typeof(SummonDaemonScroll), typeof(SummonEarthElementalScroll), typeof(SummonFireElementalScroll), + typeof(SummonWaterElementalScroll) + }; + + public static Type[] NecromancyScrollTypes{ get; } = + { + typeof(AnimateDeadScroll), typeof(BloodOathScroll), typeof(CorpseSkinScroll), typeof(CurseWeaponScroll), + typeof(EvilOmenScroll), typeof(HorrificBeastScroll), typeof(LichFormScroll), typeof(MindRotScroll), + typeof(PainSpikeScroll), typeof(PoisonStrikeScroll), typeof(StrangleScroll), typeof(SummonFamiliarScroll), + typeof(VampiricEmbraceScroll), typeof(VengefulSpiritScroll), typeof(WitherScroll), typeof(WraithFormScroll) + }; + + public static Type[] SENecromancyScrollTypes{ get; } = + { + typeof(AnimateDeadScroll), typeof(BloodOathScroll), typeof(CorpseSkinScroll), typeof(CurseWeaponScroll), + typeof(EvilOmenScroll), typeof(HorrificBeastScroll), typeof(LichFormScroll), typeof(MindRotScroll), + typeof(PainSpikeScroll), typeof(PoisonStrikeScroll), typeof(StrangleScroll), typeof(SummonFamiliarScroll), + typeof(VampiricEmbraceScroll), typeof(VengefulSpiritScroll), typeof(WitherScroll), typeof(WraithFormScroll), + typeof(ExorcismScroll) + }; + + public static Type[] PaladinScrollTypes{ get; } = new Type[0]; + + #region Mondain's Legacy + + public static Type[] ArcanistScrollTypes{ get; } = + { + typeof(ArcaneCircleScroll), typeof(GiftOfRenewalScroll), typeof(ImmolatingWeaponScroll), + typeof(AttuneWeaponScroll), + typeof(ThunderstormScroll), + typeof(NatureFuryScroll), /*typeof( SummonFeyScroll ), typeof( SummonFiendScroll ),*/ + typeof(ReaperFormScroll), typeof(WildfireScroll), typeof(EssenceOfWindScroll), typeof(DryadAllureScroll), + typeof(EtherealVoyageScroll), typeof(WordOfDeathScroll), typeof(GiftOfLifeScroll), + typeof(ArcaneEmpowermentScroll) + }; + + #endregion + + public static Type[] GrimmochJournalTypes{ get; } = + { + typeof(GrimmochJournal1), typeof(GrimmochJournal2), typeof(GrimmochJournal3), + typeof(GrimmochJournal6), typeof(GrimmochJournal7), typeof(GrimmochJournal11), + typeof(GrimmochJournal14), typeof(GrimmochJournal17), typeof(GrimmochJournal23) + }; + + public static Type[] LysanderNotebookTypes{ get; } = + { + typeof(LysanderNotebook1), typeof(LysanderNotebook2), typeof(LysanderNotebook3), + typeof(LysanderNotebook7), typeof(LysanderNotebook8), typeof(LysanderNotebook11) + }; + + public static Type[] TavarasJournalTypes{ get; } = + { + typeof(TavarasJournal1), typeof(TavarasJournal2), typeof(TavarasJournal3), + typeof(TavarasJournal6), typeof(TavarasJournal7), typeof(TavarasJournal8), + typeof(TavarasJournal9), typeof(TavarasJournal11), typeof(TavarasJournal14), + typeof(TavarasJournal16), typeof(TavarasJournal16b), typeof(TavarasJournal17), + typeof(TavarasJournal19) + }; + + + public static Type[] NewWandTypes{ get; } = + { + typeof(FireballWand), typeof(LightningWand), typeof(MagicArrowWand), + typeof(GreaterHealWand), typeof(HarmWand), typeof(HealWand) + }; + + public static Type[] WandTypes{ get; } = + { + typeof(ClumsyWand), typeof(FeebleWand), + typeof(ManaDrainWand), typeof(WeaknessWand) + }; + + public static Type[] OldWandTypes{ get; } = + { + typeof(IDWand) + }; + + public static Type[] SEClothingTypes{ get; } = + { + typeof(ClothNinjaJacket), typeof(FemaleKimono), typeof(Hakama), + typeof(HakamaShita), typeof(JinBaori), typeof(Kamishimo), + typeof(MaleKimono), typeof(NinjaTabi), typeof(Obi), + typeof(SamuraiTabi), typeof(TattsukeHakama), typeof(Waraji) + }; + + public static Type[] AosClothingTypes{ get; } = + { + typeof(FurSarong), typeof(FurCape), typeof(FlowerGarland), + typeof(GildedDress), typeof(FurBoots), typeof(FormalShirt) + }; + + public static Type[] ClothingTypes{ get; } = + { + typeof(Cloak), + typeof(Bonnet), typeof(Cap), typeof(FeatheredHat), + typeof(FloppyHat), typeof(JesterHat), typeof(Surcoat), + typeof(SkullCap), typeof(StrawHat), typeof(TallStrawHat), + typeof(TricorneHat), typeof(WideBrimHat), typeof(WizardsHat), + typeof(BodySash), typeof(Doublet), typeof(Boots), + typeof(FullApron), typeof(JesterSuit), typeof(Sandals), + typeof(Tunic), typeof(Shoes), typeof(Shirt), + typeof(Kilt), typeof(Skirt), typeof(FancyShirt), + typeof(FancyDress), typeof(ThighBoots), typeof(LongPants), + typeof(PlainDress), typeof(Robe), typeof(ShortPants), + typeof(HalfApron) + }; + + public static Type[] SEHatTypes{ get; } = + { + typeof(ClothNinjaHood), typeof(Kasa) + }; + + public static Type[] AosHatTypes{ get; } = + { + typeof(FlowerGarland), typeof(BearMask), + typeof(DeerMask) //Are Bear& Deer mask inside the Pre-AoS loottables too? + }; + + public static Type[] HatTypes{ get; } = + { + typeof(SkullCap), typeof(Bandana), typeof(FloppyHat), + typeof(Cap), typeof(WideBrimHat), typeof(StrawHat), + typeof(TallStrawHat), typeof(WizardsHat), typeof(Bonnet), + typeof(FeatheredHat), typeof(TricorneHat), typeof(JesterHat) + }; + + public static Type[] LibraryBookTypes{ get; } = + { + typeof(GrammarOfOrcish), typeof(CallToAnarchy), typeof(ArmsAndWeaponsPrimer), + typeof(SongOfSamlethe), typeof(TaleOfThreeTribes), typeof(GuideToGuilds), + typeof(BirdsOfBritannia), typeof(BritannianFlora), typeof(ChildrenTalesVol2), + typeof(TalesOfVesperVol1), typeof(DeceitDungeonOfHorror), typeof(DimensionalTravel), + typeof(EthicalHedonism), typeof(MyStory), typeof(DiversityOfOurLand), + typeof(QuestOfVirtues), typeof(RegardingLlamas), typeof(TalkingToWisps), + typeof(TamingDragons), typeof(BoldStranger), typeof(BurningOfTrinsic), + typeof(TheFight), typeof(LifeOfATravellingMinstrel), typeof(MajorTradeAssociation), + typeof(RankingsOfTrades), typeof(WildGirlOfTheForest), typeof(TreatiseOnAlchemy), + typeof(VirtueBook) + }; + + #endregion + + #region Accessors + + public static BaseWand RandomWand() + { + if (Core.ML) + return Construct(NewWandTypes) as BaseWand; + if (Core.AOS) + return Construct(WandTypes, NewWandTypes) as BaseWand; + return Construct(OldWandTypes, WandTypes, NewWandTypes) as BaseWand; + } + + public static BaseClothing RandomClothing() + { + return RandomClothing(false, false); + } + + public static BaseClothing RandomClothing(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLClothingTypes, AosClothingTypes, ClothingTypes) as BaseClothing; + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEClothingTypes, AosClothingTypes, ClothingTypes) as BaseClothing; + + if (Core.AOS) + return Construct(AosClothingTypes, ClothingTypes) as BaseClothing; + + return Construct(ClothingTypes) as BaseClothing; + } + + public static BaseWeapon RandomRangedWeapon() + { + return RandomRangedWeapon(false, false); + } + + public static BaseWeapon RandomRangedWeapon(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLRangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes) as BaseWeapon; + + #endregion + + if (Core.SE && inTokuno) + return Construct(SERangedWeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes) as BaseWeapon; + + if (Core.AOS) + return Construct(AosRangedWeaponTypes, RangedWeaponTypes) as BaseWeapon; + + return Construct(RangedWeaponTypes) as BaseWeapon; + } + + public static BaseWeapon RandomWeapon() + { + return RandomWeapon(false, false); + } + + public static BaseWeapon RandomWeapon(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLWeaponTypes, AosWeaponTypes, WeaponTypes) as BaseWeapon; + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEWeaponTypes, AosWeaponTypes, WeaponTypes) as BaseWeapon; + + if (Core.AOS) + return Construct(AosWeaponTypes, WeaponTypes) as BaseWeapon; + + return Construct(WeaponTypes) as BaseWeapon; + } + + public static Item RandomWeaponOrJewelry() + { + return RandomWeaponOrJewelry(false, false); + } + + public static Item RandomWeaponOrJewelry(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLWeaponTypes, AosWeaponTypes, WeaponTypes, JewelryTypes); + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEWeaponTypes, AosWeaponTypes, WeaponTypes, JewelryTypes); + + if (Core.AOS) + return Construct(AosWeaponTypes, WeaponTypes, JewelryTypes); + + return Construct(WeaponTypes, JewelryTypes); + } + + public static BaseJewel RandomJewelry() + { + return Construct(JewelryTypes) as BaseJewel; + } + + public static BaseArmor RandomArmor() + { + return RandomArmor(false, false); + } + + public static BaseArmor RandomArmor(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLArmorTypes, ArmorTypes) as BaseArmor; + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEArmorTypes, ArmorTypes) as BaseArmor; + + return Construct(ArmorTypes) as BaseArmor; + } + + public static BaseHat RandomHat() + { + return RandomHat(false); + } + + public static BaseHat RandomHat(bool inTokuno) + { + if (Core.SE && inTokuno) + return Construct(SEHatTypes, AosHatTypes, HatTypes) as BaseHat; + + if (Core.AOS) + return Construct(AosHatTypes, HatTypes) as BaseHat; + + return Construct(HatTypes) as BaseHat; + } + + public static Item RandomArmorOrHat() + { + return RandomArmorOrHat(false, false); + } + + public static Item RandomArmorOrHat(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes); + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes); + + if (Core.AOS) + return Construct(ArmorTypes, AosHatTypes, HatTypes); + + return Construct(ArmorTypes, HatTypes); + } + + public static BaseShield RandomShield() + { + if (Core.AOS) + return Construct(AosShieldTypes, ShieldTypes) as BaseShield; + + return Construct(ShieldTypes) as BaseShield; + } + + public static BaseArmor RandomArmorOrShield() + { + return RandomArmorOrShield(false, false); + } + + public static BaseArmor RandomArmorOrShield(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLArmorTypes, ArmorTypes, AosShieldTypes, ShieldTypes) as BaseArmor; + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEArmorTypes, ArmorTypes, AosShieldTypes, ShieldTypes) as BaseArmor; + + if (Core.AOS) + return Construct(ArmorTypes, AosShieldTypes, ShieldTypes) as BaseArmor; + + return Construct(ArmorTypes, ShieldTypes) as BaseArmor; + } + + public static Item RandomArmorOrShieldOrJewelry() + { + return RandomArmorOrShieldOrJewelry(false, false); + } + + public static Item RandomArmorOrShieldOrJewelry(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes); + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, + JewelryTypes); + + if (Core.AOS) + return Construct(ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes); + + return Construct(ArmorTypes, HatTypes, ShieldTypes, JewelryTypes); + } + + public static Item RandomArmorOrShieldOrWeapon() + { + return RandomArmorOrShieldOrWeapon(false, false); + } + + public static Item RandomArmorOrShieldOrWeapon(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLWeaponTypes, AosWeaponTypes, WeaponTypes, MLRangedWeaponTypes, AosRangedWeaponTypes, + RangedWeaponTypes, MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes); + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEWeaponTypes, AosWeaponTypes, WeaponTypes, SERangedWeaponTypes, AosRangedWeaponTypes, + RangedWeaponTypes, SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes, AosShieldTypes, + ShieldTypes); + + if (Core.AOS) + return Construct(AosWeaponTypes, WeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, ArmorTypes, + AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes); + + return Construct(WeaponTypes, RangedWeaponTypes, ArmorTypes, HatTypes, ShieldTypes); + } + + public static Item RandomArmorOrShieldOrWeaponOrJewelry() + { + return RandomArmorOrShieldOrWeaponOrJewelry(false, false); + } + + public static Item RandomArmorOrShieldOrWeaponOrJewelry(bool inTokuno, bool isMondain) + { + #region Mondain's Legacy + + if (Core.ML && isMondain) + return Construct(MLWeaponTypes, AosWeaponTypes, WeaponTypes, MLRangedWeaponTypes, AosRangedWeaponTypes, + RangedWeaponTypes, MLArmorTypes, ArmorTypes, AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, + JewelryTypes); + + #endregion + + if (Core.SE && inTokuno) + return Construct(SEWeaponTypes, AosWeaponTypes, WeaponTypes, SERangedWeaponTypes, AosRangedWeaponTypes, + RangedWeaponTypes, SEArmorTypes, ArmorTypes, SEHatTypes, AosHatTypes, HatTypes, AosShieldTypes, + ShieldTypes, JewelryTypes); + + if (Core.AOS) + return Construct(AosWeaponTypes, WeaponTypes, AosRangedWeaponTypes, RangedWeaponTypes, ArmorTypes, + AosHatTypes, HatTypes, AosShieldTypes, ShieldTypes, JewelryTypes); + + return Construct(WeaponTypes, RangedWeaponTypes, ArmorTypes, HatTypes, ShieldTypes, JewelryTypes); + } + + #region Chest of Heirlooms + + public static Item ChestOfHeirloomsContains() + { + return Construct(SEArmorTypes, SEHatTypes, SEWeaponTypes, SERangedWeaponTypes, JewelryTypes); + } + + #endregion + + public static Item RandomGem() + { + return Construct(GemTypes); + } + + public static Item RandomReagent() + { + return Construct(RegTypes); + } + + public static Item RandomNecromancyReagent() + { + return Construct(NecroRegTypes); + } + + public static Item RandomPossibleReagent() + { + if (Core.AOS) + return Construct(RegTypes, NecroRegTypes); + + return Construct(RegTypes); + } + + public static Item RandomPotion() + { + return Construct(PotionTypes); + } + + public static BaseInstrument RandomInstrument() + { + if (Core.SE) + return Construct(InstrumentTypes, SEInstrumentTypes) as BaseInstrument; + + return Construct(InstrumentTypes) as BaseInstrument; + } + + public static Item RandomStatue() + { + return Construct(StatueTypes); + } + + public static SpellScroll RandomScroll(int minIndex, int maxIndex, SpellbookType type) + { + Type[] types; + + switch (type) + { + default: + case SpellbookType.Regular: + types = RegularScrollTypes; + break; + case SpellbookType.Necromancer: + types = Core.SE ? SENecromancyScrollTypes : NecromancyScrollTypes; + break; + case SpellbookType.Paladin: + types = PaladinScrollTypes; + break; + case SpellbookType.Arcanist: + types = ArcanistScrollTypes; + break; + } + + return Construct(types, Utility.RandomMinMax(minIndex, maxIndex)) as SpellScroll; + } + + public static BaseBook RandomGrimmochJournal() + { + return Construct(GrimmochJournalTypes) as BaseBook; + } + + public static BaseBook RandomLysanderNotebook() + { + return Construct(LysanderNotebookTypes) as BaseBook; + } + + public static BaseBook RandomTavarasJournal() + { + return Construct(TavarasJournalTypes) as BaseBook; + } + + public static BaseBook RandomLibraryBook() + { + return Construct(LibraryBookTypes) as BaseBook; + } + + public static BaseTalisman RandomTalisman() + { + BaseTalisman talisman = new BaseTalisman(BaseTalisman.GetRandomItemID()); + + talisman.Summoner = BaseTalisman.GetRandomSummoner(); + + if (talisman.Summoner.IsEmpty) + { + talisman.Removal = BaseTalisman.GetRandomRemoval(); + + if (talisman.Removal != TalismanRemoval.None) + { + talisman.MaxCharges = BaseTalisman.GetRandomCharges(); + talisman.MaxChargeTime = 1200; + } + } + else + { + talisman.MaxCharges = Utility.RandomMinMax(10, 50); + + if (talisman.Summoner.IsItem) + talisman.MaxChargeTime = 60; + else + talisman.MaxChargeTime = 1800; + } + + talisman.Blessed = BaseTalisman.GetRandomBlessed(); + talisman.Slayer = BaseTalisman.GetRandomSlayer(); + talisman.Protection = BaseTalisman.GetRandomProtection(); + talisman.Killer = BaseTalisman.GetRandomKiller(); + talisman.Skill = BaseTalisman.GetRandomSkill(); + talisman.ExceptionalBonus = BaseTalisman.GetRandomExceptional(); + talisman.SuccessBonus = BaseTalisman.GetRandomSuccessful(); + talisman.Charges = talisman.MaxCharges; + + return talisman; + } + + #endregion + + #region Construction methods + + public static Item Construct(Type type) + { + try + { + return Activator.CreateInstance(type) as Item; + } + catch + { + return null; + } + } + + public static Item Construct(Type[] types) + { + if (types.Length > 0) + return Construct(types, Utility.Random(types.Length)); + + return null; + } + + public static Item Construct(Type[] types, int index) + { + if (index >= 0 && index < types.Length) + return Construct(types[index]); + + return null; + } + + public static Item Construct(params Type[][] types) + { + int totalLength = 0; + + for (int i = 0; i < types.Length; ++i) + totalLength += types[i].Length; + + if (totalLength > 0) + { + int index = Utility.Random(totalLength); + + for (int i = 0; i < types.Length; ++i) + { + if (index >= 0 && index < types[i].Length) + return Construct(types[i][index]); + + index -= types[i].Length; + } + } + + return null; + } + + #endregion + } } \ No newline at end of file diff --git a/Scripts/Misc/LootPack.cs b/Scripts/Misc/LootPack.cs index 7e49c716e..826a5b0d5 100644 --- a/Scripts/Misc/LootPack.cs +++ b/Scripts/Misc/LootPack.cs @@ -5,897 +5,966 @@ using Server.Mobiles; namespace Server { - public class LootPack - { - public static int GetLuckChance( Mobile killer, Mobile victim ) - { - if ( !Core.AOS ) - return 0; + public class LootPack + { + public static readonly LootPackItem[] Gold = + { + new LootPackItem(typeof(Gold), 1) + }; + + public static readonly LootPackItem[] Instruments = + { + new LootPackItem(typeof(BaseInstrument), 1) + }; + + + public static readonly LootPackItem[] LowScrollItems = + { + new LootPackItem(typeof(ClumsyScroll), 1) + }; + + public static readonly LootPackItem[] MedScrollItems = + { + new LootPackItem(typeof(ArchCureScroll), 1) + }; + + public static readonly LootPackItem[] HighScrollItems = + { + new LootPackItem(typeof(SummonAirElementalScroll), 1) + }; + + public static readonly LootPackItem[] GemItems = + { + new LootPackItem(typeof(Amber), 1) + }; + + public static readonly LootPackItem[] PotionItems = + { + new LootPackItem(typeof(AgilityPotion), 1), + new LootPackItem(typeof(StrengthPotion), 1), + new LootPackItem(typeof(RefreshPotion), 1), + new LootPackItem(typeof(LesserCurePotion), 1), + new LootPackItem(typeof(LesserHealPotion), 1), + new LootPackItem(typeof(LesserPoisonPotion), 1) + }; + + #region Old Magic Items + + public static readonly LootPackItem[] OldMagicItems = + { + new LootPackItem(typeof(BaseJewel), 1), + new LootPackItem(typeof(BaseArmor), 4), + new LootPackItem(typeof(BaseWeapon), 3), + new LootPackItem(typeof(BaseRanged), 1), + new LootPackItem(typeof(BaseShield), 1) + }; + + #endregion + + public static readonly LootPack LowScrolls = new LootPack(new[] + { + new LootPackEntry(false, LowScrollItems, 100.00, 1) + }); + + public static readonly LootPack MedScrolls = new LootPack(new[] + { + new LootPackEntry(false, MedScrollItems, 100.00, 1) + }); + + public static readonly LootPack HighScrolls = new LootPack(new[] + { + new LootPackEntry(false, HighScrollItems, 100.00, 1) + }); + + public static readonly LootPack Gems = new LootPack(new[] + { + new LootPackEntry(false, GemItems, 100.00, 1) + }); + + public static readonly LootPack Potions = new LootPack(new[] + { + new LootPackEntry(false, PotionItems, 100.00, 1) + }); + + private LootPackEntry[] m_Entries; + + public LootPack(LootPackEntry[] entries) + { + m_Entries = entries; + } + + public static int GetLuckChance(Mobile killer, Mobile victim) + { + if (!Core.AOS) + return 0; + + int luck = killer.Luck; + + if (killer is PlayerMobile pmKiller && pmKiller.SentHonorContext != null && + pmKiller.SentHonorContext.Target == victim) + luck += pmKiller.SentHonorContext.PerfectionLuckBonus; + + if (luck < 0) + return 0; + + if (!Core.SE && luck > 1200) + luck = 1200; + + return (int)(Math.Pow(luck, 1 / 1.8) * 100); + } + + public static int GetLuckChanceForKiller(Mobile dead) + { + List list = BaseCreature.GetLootingRights(dead.DamageEntries, dead.HitsMax); + + DamageStore highest = null; + + for (int i = 0; i < list.Count; ++i) + { + DamageStore ds = list[i]; + + if (ds.m_HasRight && (highest == null || ds.m_Damage > highest.m_Damage)) + highest = ds; + } + + if (highest == null) + return 0; + + return GetLuckChance(highest.m_Mobile, dead); + } + + public static bool CheckLuck(int chance) + { + return chance > Utility.Random(10000); + } + + public void Generate(Mobile from, Container cont, bool spawning, int luckChance) + { + if (cont == null) + return; + + bool checkLuck = Core.AOS; + + for (int i = 0; i < m_Entries.Length; ++i) + { + LootPackEntry entry = m_Entries[i]; + + bool shouldAdd = entry.Chance > Utility.Random(10000); + + if (!shouldAdd && checkLuck) + { + checkLuck = false; + + if (CheckLuck(luckChance)) + shouldAdd = entry.Chance > Utility.Random(10000); + } + + if (!shouldAdd) + continue; + + Item item = entry.Construct(from, luckChance, spawning); + + if (item != null) + if (!item.Stackable || !cont.TryDropItem(from, item, false)) + cont.DropItem(item); + } + } + + #region ML definitions + + public static readonly LootPackItem[] AosMagicItemsRichType1 = + { + new LootPackItem(typeof(BaseWeapon), 211), + new LootPackItem(typeof(BaseRanged), 53), + new LootPackItem(typeof(BaseArmor), 303), + new LootPackItem(typeof(BaseShield), 39), + new LootPackItem(typeof(BaseJewel), 158) + }; + + public static readonly LootPack MlRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "4d50+450"), + new LootPackEntry(false, AosMagicItemsRichType1, 100.00, 1, 3, 0, 75), + new LootPackEntry(false, AosMagicItemsRichType1, 80.00, 1, 3, 0, 75), + new LootPackEntry(false, AosMagicItemsRichType1, 60.00, 1, 5, 0, 100), + new LootPackEntry(false, Instruments, 1.00, 1) + }); + + #endregion + + #region AOS Magic Items + + public static readonly LootPackItem[] AosMagicItemsPoor = + { + new LootPackItem(typeof(BaseWeapon), 3), + new LootPackItem(typeof(BaseRanged), 1), + new LootPackItem(typeof(BaseArmor), 4), + new LootPackItem(typeof(BaseShield), 1), + new LootPackItem(typeof(BaseJewel), 2) + }; + + public static readonly LootPackItem[] AosMagicItemsMeagerType1 = + { + new LootPackItem(typeof(BaseWeapon), 56), + new LootPackItem(typeof(BaseRanged), 14), + new LootPackItem(typeof(BaseArmor), 81), + new LootPackItem(typeof(BaseShield), 11), + new LootPackItem(typeof(BaseJewel), 42) + }; + + public static readonly LootPackItem[] AosMagicItemsMeagerType2 = + { + new LootPackItem(typeof(BaseWeapon), 28), + new LootPackItem(typeof(BaseRanged), 7), + new LootPackItem(typeof(BaseArmor), 40), + new LootPackItem(typeof(BaseShield), 5), + new LootPackItem(typeof(BaseJewel), 21) + }; + + public static readonly LootPackItem[] AosMagicItemsAverageType1 = + { + new LootPackItem(typeof(BaseWeapon), 90), + new LootPackItem(typeof(BaseRanged), 23), + new LootPackItem(typeof(BaseArmor), 130), + new LootPackItem(typeof(BaseShield), 17), + new LootPackItem(typeof(BaseJewel), 68) + }; + + public static readonly LootPackItem[] AosMagicItemsAverageType2 = + { + new LootPackItem(typeof(BaseWeapon), 54), + new LootPackItem(typeof(BaseRanged), 13), + new LootPackItem(typeof(BaseArmor), 77), + new LootPackItem(typeof(BaseShield), 10), + new LootPackItem(typeof(BaseJewel), 40) + }; + + + public static readonly LootPackItem[] AosMagicItemsRichType2 = + { + new LootPackItem(typeof(BaseWeapon), 170), + new LootPackItem(typeof(BaseRanged), 43), + new LootPackItem(typeof(BaseArmor), 245), + new LootPackItem(typeof(BaseShield), 32), + new LootPackItem(typeof(BaseJewel), 128) + }; + + public static readonly LootPackItem[] AosMagicItemsFilthyRichType1 = + { + new LootPackItem(typeof(BaseWeapon), 219), + new LootPackItem(typeof(BaseRanged), 55), + new LootPackItem(typeof(BaseArmor), 315), + new LootPackItem(typeof(BaseShield), 41), + new LootPackItem(typeof(BaseJewel), 164) + }; + + public static readonly LootPackItem[] AosMagicItemsFilthyRichType2 = + { + new LootPackItem(typeof(BaseWeapon), 239), + new LootPackItem(typeof(BaseRanged), 60), + new LootPackItem(typeof(BaseArmor), 343), + new LootPackItem(typeof(BaseShield), 90), + new LootPackItem(typeof(BaseJewel), 45) + }; + + public static readonly LootPackItem[] AosMagicItemsUltraRich = + { + new LootPackItem(typeof(BaseWeapon), 276), + new LootPackItem(typeof(BaseRanged), 69), + new LootPackItem(typeof(BaseArmor), 397), + new LootPackItem(typeof(BaseShield), 52), + new LootPackItem(typeof(BaseJewel), 207) + }; + + #endregion + + #region SE definitions + + public static readonly LootPack SePoor = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "2d10+20"), + new LootPackEntry(false, AosMagicItemsPoor, 1.00, 1, 5, 0, 100), + new LootPackEntry(false, Instruments, 0.02, 1) + }); + + public static readonly LootPack SeMeager = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "4d10+40"), + new LootPackEntry(false, AosMagicItemsMeagerType1, 20.40, 1, 2, 0, 50), + new LootPackEntry(false, AosMagicItemsMeagerType2, 10.20, 1, 5, 0, 100), + new LootPackEntry(false, Instruments, 0.10, 1) + }); + + public static readonly LootPack SeAverage = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "8d10+100"), + new LootPackEntry(false, AosMagicItemsAverageType1, 32.80, 1, 3, 0, 50), + new LootPackEntry(false, AosMagicItemsAverageType1, 32.80, 1, 4, 0, 75), + new LootPackEntry(false, AosMagicItemsAverageType2, 19.50, 1, 5, 0, 100), + new LootPackEntry(false, Instruments, 0.40, 1) + }); + + public static readonly LootPack SeRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "15d10+225"), + new LootPackEntry(false, AosMagicItemsRichType1, 76.30, 1, 4, 0, 75), + new LootPackEntry(false, AosMagicItemsRichType1, 76.30, 1, 4, 0, 75), + new LootPackEntry(false, AosMagicItemsRichType2, 61.70, 1, 5, 0, 100), + new LootPackEntry(false, Instruments, 1.00, 1) + }); + + public static readonly LootPack SeFilthyRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "3d100+400"), + new LootPackEntry(false, AosMagicItemsFilthyRichType1, 79.50, 1, 5, 0, 100), + new LootPackEntry(false, AosMagicItemsFilthyRichType1, 79.50, 1, 5, 0, 100), + new LootPackEntry(false, AosMagicItemsFilthyRichType2, 77.60, 1, 5, 25, 100), + new LootPackEntry(false, Instruments, 2.00, 1) + }); + + public static readonly LootPack SeUltraRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "6d100+600"), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, Instruments, 2.00, 1) + }); + + public static readonly LootPack SeSuperBoss = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "10d100+800"), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100), + new LootPackEntry(false, Instruments, 2.00, 1) + }); + + #endregion + + #region AOS definitions + + public static readonly LootPack AosPoor = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "1d10+10"), + new LootPackEntry(false, AosMagicItemsPoor, 0.02, 1, 5, 0, 90), + new LootPackEntry(false, Instruments, 0.02, 1) + }); + + public static readonly LootPack AosMeager = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "3d10+20"), + new LootPackEntry(false, AosMagicItemsMeagerType1, 1.00, 1, 2, 0, 10), + new LootPackEntry(false, AosMagicItemsMeagerType2, 0.20, 1, 5, 0, 90), + new LootPackEntry(false, Instruments, 0.10, 1) + }); + + public static readonly LootPack AosAverage = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "5d10+50"), + new LootPackEntry(false, AosMagicItemsAverageType1, 5.00, 1, 4, 0, 20), + new LootPackEntry(false, AosMagicItemsAverageType1, 2.00, 1, 3, 0, 50), + new LootPackEntry(false, AosMagicItemsAverageType2, 0.50, 1, 5, 0, 90), + new LootPackEntry(false, Instruments, 0.40, 1) + }); + + public static readonly LootPack AosRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "10d10+150"), + new LootPackEntry(false, AosMagicItemsRichType1, 20.00, 1, 4, 0, 40), + new LootPackEntry(false, AosMagicItemsRichType1, 10.00, 1, 5, 0, 60), + new LootPackEntry(false, AosMagicItemsRichType2, 1.00, 1, 5, 0, 90), + new LootPackEntry(false, Instruments, 1.00, 1) + }); + + public static readonly LootPack AosFilthyRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "2d100+200"), + new LootPackEntry(false, AosMagicItemsFilthyRichType1, 33.00, 1, 4, 0, 50), + new LootPackEntry(false, AosMagicItemsFilthyRichType1, 33.00, 1, 4, 0, 60), + new LootPackEntry(false, AosMagicItemsFilthyRichType2, 20.00, 1, 5, 0, 75), + new LootPackEntry(false, AosMagicItemsFilthyRichType2, 5.00, 1, 5, 0, 100), + new LootPackEntry(false, Instruments, 2.00, 1) + }); + + public static readonly LootPack AosUltraRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "5d100+500"), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 35, 100), + new LootPackEntry(false, Instruments, 2.00, 1) + }); + + public static readonly LootPack AosSuperBoss = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "5d100+500"), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100), + new LootPackEntry(false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100), + new LootPackEntry(false, Instruments, 2.00, 1) + }); + + #endregion + + #region Pre-AOS definitions + + public static readonly LootPack OldPoor = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "1d25"), + new LootPackEntry(false, Instruments, 0.02, 1) + }); + + public static readonly LootPack OldMeager = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "5d10+25"), + new LootPackEntry(false, Instruments, 0.10, 1), + new LootPackEntry(false, OldMagicItems, 1.00, 1, 1, 0, 60), + new LootPackEntry(false, OldMagicItems, 0.20, 1, 1, 10, 70) + }); + + public static readonly LootPack OldAverage = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "10d10+50"), + new LootPackEntry(false, Instruments, 0.40, 1), + new LootPackEntry(false, OldMagicItems, 5.00, 1, 1, 20, 80), + new LootPackEntry(false, OldMagicItems, 2.00, 1, 1, 30, 90), + new LootPackEntry(false, OldMagicItems, 0.50, 1, 1, 40, 100) + }); + + public static readonly LootPack OldRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "10d10+250"), + new LootPackEntry(false, Instruments, 1.00, 1), + new LootPackEntry(false, OldMagicItems, 20.00, 1, 1, 60, 100), + new LootPackEntry(false, OldMagicItems, 10.00, 1, 1, 65, 100), + new LootPackEntry(false, OldMagicItems, 1.00, 1, 1, 70, 100) + }); + + public static readonly LootPack OldFilthyRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "2d125+400"), + new LootPackEntry(false, Instruments, 2.00, 1), + new LootPackEntry(false, OldMagicItems, 33.00, 1, 1, 50, 100), + new LootPackEntry(false, OldMagicItems, 33.00, 1, 1, 60, 100), + new LootPackEntry(false, OldMagicItems, 20.00, 1, 1, 70, 100), + new LootPackEntry(false, OldMagicItems, 5.00, 1, 1, 80, 100) + }); + + public static readonly LootPack OldUltraRich = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "5d100+500"), + new LootPackEntry(false, Instruments, 2.00, 1), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 40, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 40, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 50, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 50, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 60, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 60, 100) + }); + + public static readonly LootPack OldSuperBoss = new LootPack(new[] + { + new LootPackEntry(true, Gold, 100.00, "5d100+500"), + new LootPackEntry(false, Instruments, 2.00, 1), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 40, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 40, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 40, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 50, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 50, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 50, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 60, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 60, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 60, 100), + new LootPackEntry(false, OldMagicItems, 100.00, 1, 1, 70, 100) + }); + + #endregion + + #region Generic accessors + + public static LootPack Poor => Core.SE ? SePoor : Core.AOS ? AosPoor : OldPoor; + public static LootPack Meager => Core.SE ? SeMeager : Core.AOS ? AosMeager : OldMeager; + public static LootPack Average => Core.SE ? SeAverage : Core.AOS ? AosAverage : OldAverage; + public static LootPack Rich => Core.SE ? SeRich : Core.AOS ? AosRich : OldRich; + public static LootPack FilthyRich => Core.SE ? SeFilthyRich : Core.AOS ? AosFilthyRich : OldFilthyRich; + public static LootPack UltraRich => Core.SE ? SeUltraRich : Core.AOS ? AosUltraRich : OldUltraRich; + public static LootPack SuperBoss => Core.SE ? SeSuperBoss : Core.AOS ? AosSuperBoss : OldSuperBoss; + + #endregion + + /* + // TODO: Uncomment once added + #region Mondain's Legacy + public static readonly LootPackItem[] ParrotItem = new LootPackItem[] + { + new LootPackItem( typeof( ParrotItem ), 1 ) + }; + + public static readonly LootPack Parrot = new LootPack( new LootPackEntry[] + { + new LootPackEntry( false, ParrotItem, 10.00, 1 ) + } ); + #endregion + */ + } + + public class LootPackEntry + { + private bool m_AtSpawnTime; + + public LootPackEntry(bool atSpawnTime, LootPackItem[] items, double chance, string quantity) : this(atSpawnTime, + items, chance, new LootPackDice(quantity), 0, 0, 0) + { + } + + public LootPackEntry(bool atSpawnTime, LootPackItem[] items, double chance, int quantity) : this(atSpawnTime, items, + chance, new LootPackDice(0, 0, quantity), 0, 0, 0) + { + } + + public LootPackEntry(bool atSpawnTime, LootPackItem[] items, double chance, string quantity, int maxProps, + int minIntensity, int maxIntensity) : this(atSpawnTime, items, chance, new LootPackDice(quantity), maxProps, + minIntensity, maxIntensity) + { + } + + public LootPackEntry(bool atSpawnTime, LootPackItem[] items, double chance, int quantity, int maxProps, + int minIntensity, int maxIntensity) : this(atSpawnTime, items, chance, new LootPackDice(0, 0, quantity), + maxProps, minIntensity, maxIntensity) + { + } + + public LootPackEntry(bool atSpawnTime, LootPackItem[] items, double chance, LootPackDice quantity, int maxProps, + int minIntensity, int maxIntensity) + { + m_AtSpawnTime = atSpawnTime; + Items = items; + Chance = (int)(100 * chance); + Quantity = quantity; + MaxProps = maxProps; + MinIntensity = minIntensity; + MaxIntensity = maxIntensity; + } + + public int Chance{ get; set; } + + public LootPackDice Quantity{ get; set; } + + public int MaxProps{ get; set; } + + public int MinIntensity{ get; set; } + + public int MaxIntensity{ get; set; } + + public LootPackItem[] Items{ get; set; } + + private static bool IsInTokuno(Mobile m) + { + if (m.Region.IsPartOf("Fan Dancer's Dojo")) + return true; + + if (m.Region.IsPartOf("Yomotsu Mines")) + return true; + + return m.Map == Map.Tokuno; + } + + #region Mondain's Legacy + + private static bool IsMondain(Mobile m) + { + return MondainsLegacy.IsMLRegion(m.Region); + } + + #endregion + + public Item Construct(Mobile from, int luckChance, bool spawning) + { + if (m_AtSpawnTime != spawning) + return null; + + int totalChance = 0; + + for (int i = 0; i < Items.Length; ++i) + totalChance += Items[i].Chance; + + int rnd = Utility.Random(totalChance); + + for (int i = 0; i < Items.Length; ++i) + { + LootPackItem item = Items[i]; + + if (rnd < item.Chance) + return Mutate(from, luckChance, item.Construct(IsInTokuno(from), IsMondain(from))); + + rnd -= item.Chance; + } + + return null; + } + + private int GetRandomOldBonus() + { + int rnd = Utility.RandomMinMax(MinIntensity, MaxIntensity); + + if (50 > rnd) + return 1; + rnd -= 50; + + if (25 > rnd) + return 2; + rnd -= 25; + + if (14 > rnd) + return 3; + rnd -= 14; + + if (8 > rnd) + return 4; + + return 5; + } + + public Item Mutate(Mobile from, int luckChance, Item item) + { + if (item != null) + { + if (item is BaseWeapon && 1 > Utility.Random(100)) + { + item.Delete(); + item = new FireHorn(); + return item; + } + + if (item is BaseWeapon || item is BaseArmor || item is BaseJewel || item is BaseHat) + { + if (Core.AOS) + { + int bonusProps = GetBonusProperties(); + int min = MinIntensity; + int max = MaxIntensity; + + if (bonusProps < MaxProps && LootPack.CheckLuck(luckChance)) + ++bonusProps; + + int props = 1 + bonusProps; + + // Make sure we're not spawning items with 6 properties. + if (props > MaxProps) + props = MaxProps; + + if (item is BaseWeapon weapon) + BaseRunicTool.ApplyAttributesTo(weapon, false, luckChance, props, MinIntensity, MaxIntensity); + else if (item is BaseArmor armor) + BaseRunicTool.ApplyAttributesTo(armor, false, luckChance, props, MinIntensity, MaxIntensity); + else if (item is BaseJewel jewel) + BaseRunicTool.ApplyAttributesTo(jewel, false, luckChance, props, MinIntensity, MaxIntensity); + else + BaseRunicTool.ApplyAttributesTo((BaseHat)item, false, luckChance, props, MinIntensity, + MaxIntensity); + } + else // not aos + { + if (item is BaseWeapon weapon) + { + if (80 > Utility.Random(100)) + weapon.AccuracyLevel = (WeaponAccuracyLevel)GetRandomOldBonus(); + + if (60 > Utility.Random(100)) + weapon.DamageLevel = (WeaponDamageLevel)GetRandomOldBonus(); + + if (40 > Utility.Random(100)) + weapon.DurabilityLevel = (WeaponDurabilityLevel)GetRandomOldBonus(); + + if (5 > Utility.Random(100)) + weapon.Slayer = SlayerName.Silver; + + if (from != null && weapon.AccuracyLevel == 0 && weapon.DamageLevel == 0 && + weapon.DurabilityLevel == 0 && weapon.Slayer == SlayerName.None && 5 > Utility.Random(100)) + weapon.Slayer = SlayerGroup.GetLootSlayerType(from.GetType()); + } + else if (item is BaseArmor armor) + { + if (80 > Utility.Random(100)) + armor.ProtectionLevel = (ArmorProtectionLevel)GetRandomOldBonus(); + + if (40 > Utility.Random(100)) + armor.Durability = (ArmorDurabilityLevel)GetRandomOldBonus(); + } + } + } + else if (item is BaseInstrument instr) + { + SlayerName slayer = SlayerName.None; + + if (Core.AOS) + slayer = BaseRunicTool.GetRandomSlayer(); + else + slayer = SlayerGroup.GetLootSlayerType(from.GetType()); + + if (slayer == SlayerName.None) + { + instr.Delete(); + return null; + } + + instr.Quality = InstrumentQuality.Regular; + instr.Slayer = slayer; + } + + if (item.Stackable) + item.Amount = Quantity.Roll(); + } + + return item; + } + + public int GetBonusProperties() + { + int p0 = 0, p1 = 0, p2 = 0, p3 = 0, p4 = 0, p5 = 0; + + switch (MaxProps) + { + case 1: + p0 = 3; + p1 = 1; + break; + case 2: + p0 = 6; + p1 = 3; + p2 = 1; + break; + case 3: + p0 = 10; + p1 = 6; + p2 = 3; + p3 = 1; + break; + case 4: + p0 = 16; + p1 = 12; + p2 = 6; + p3 = 5; + p4 = 1; + break; + case 5: + p0 = 30; + p1 = 25; + p2 = 20; + p3 = 15; + p4 = 9; + p5 = 1; + break; + } + + int pc = p0 + p1 + p2 + p3 + p4 + p5; + + int rnd = Utility.Random(pc); + + if (rnd < p5) + return 5; + + rnd -= p5; + + if (rnd < p4) + return 4; + + rnd -= p4; + + if (rnd < p3) + return 3; + + rnd -= p3; + + if (rnd < p2) + return 2; + + return rnd - p2 < p1 ? 1 : 0; + } + } + + public class LootPackItem + { + private static Type[] m_BlankTypes = { typeof(BlankScroll) }; + + private static Type[][] m_NecroTypes = + { + new[] // low + { + typeof(AnimateDeadScroll), typeof(BloodOathScroll), typeof(CorpseSkinScroll), typeof(CurseWeaponScroll), + typeof(EvilOmenScroll), typeof(HorrificBeastScroll), typeof(MindRotScroll), typeof(PainSpikeScroll), + typeof(SummonFamiliarScroll), typeof(WraithFormScroll) + }, + new[] // med + { + typeof(LichFormScroll), typeof(PoisonStrikeScroll), typeof(StrangleScroll), typeof(WitherScroll) + }, + + Core.SE + ? new[] // high + { + typeof(VengefulSpiritScroll), typeof(VampiricEmbraceScroll), typeof(ExorcismScroll) + } + : new[] // high + { + typeof(VengefulSpiritScroll), typeof(VampiricEmbraceScroll) + } + }; + + public LootPackItem(Type type, int chance) + { + Type = type; + Chance = chance; + } + + public Type Type{ get; set; } + + public int Chance{ get; set; } + + public static Item RandomScroll(int index, int minCircle, int maxCircle) + { + --minCircle; + --maxCircle; + + int scrollCount = (maxCircle - minCircle + 1) * 8; + + if (index == 0) + scrollCount += m_BlankTypes.Length; + + if (Core.AOS) + scrollCount += m_NecroTypes[index].Length; + + int rnd = Utility.Random(scrollCount); + + if (index == 0 && rnd < m_BlankTypes.Length) + return Loot.Construct(m_BlankTypes); + if (index == 0) + rnd -= m_BlankTypes.Length; + + if (Core.AOS && rnd < m_NecroTypes.Length) + return Loot.Construct(m_NecroTypes[index]); + + return Loot.RandomScroll(minCircle * 8, maxCircle * 8 + 7, SpellbookType.Regular); + } + + public Item Construct(bool inTokuno, bool isMondain) + { + try + { + Item item; + + if (Type == typeof(BaseRanged)) + item = Loot.RandomRangedWeapon(inTokuno, isMondain); + else if (Type == typeof(BaseWeapon)) + item = Loot.RandomWeapon(inTokuno, isMondain); + else if (Type == typeof(BaseArmor)) + item = Loot.RandomArmorOrHat(inTokuno, isMondain); + else if (Type == typeof(BaseShield)) + item = Loot.RandomShield(); + else if (Type == typeof(BaseJewel)) + item = Core.AOS ? Loot.RandomJewelry() : Loot.RandomArmorOrShieldOrWeapon(); + else if (Type == typeof(BaseInstrument)) + item = Loot.RandomInstrument(); + else if (Type == typeof(Amber)) // gem + item = Loot.RandomGem(); + else if (Type == typeof(ClumsyScroll)) // low scroll + item = RandomScroll(0, 1, 3); + else if (Type == typeof(ArchCureScroll)) // med scroll + item = RandomScroll(1, 4, 7); + else if (Type == typeof(SummonAirElementalScroll)) // high scroll + item = RandomScroll(2, 8, 8); + else + item = Activator.CreateInstance(Type) as Item; + + return item; + } + catch + { + } + + return null; + } + } + + public class LootPackDice + { + public LootPackDice(string str) + { + int start = 0; + int index = str.IndexOf('d', start); + + if (index < start) + return; + + Count = Utility.ToInt32(str.Substring(start, index - start)); + + start = index + 1; + index = str.IndexOf('+', start); + + bool negative = index < start; + + if (negative) + index = str.IndexOf('-', start); + + if (index < start) + index = str.Length; - int luck = killer.Luck; + Sides = Utility.ToInt32(str.Substring(start, index - start)); - if ( killer is PlayerMobile pmKiller && pmKiller.SentHonorContext != null && pmKiller.SentHonorContext.Target == victim ) - luck += pmKiller.SentHonorContext.PerfectionLuckBonus; + if (index == str.Length) + return; - if ( luck < 0 ) - return 0; + start = index + 1; + index = str.Length; - if ( !Core.SE && luck > 1200 ) - luck = 1200; + Bonus = Utility.ToInt32(str.Substring(start, index - start)); - return (int)(Math.Pow( luck, 1 / 1.8 ) * 100); - } - - public static int GetLuckChanceForKiller( Mobile dead ) - { - List list = BaseCreature.GetLootingRights( dead.DamageEntries, dead.HitsMax ); - - DamageStore highest = null; - - for ( int i = 0; i < list.Count; ++i ) - { - DamageStore ds = list[i]; - - if ( ds.m_HasRight && (highest == null || ds.m_Damage > highest.m_Damage) ) - highest = ds; - } - - if ( highest == null ) - return 0; - - return GetLuckChance( highest.m_Mobile, dead ); - } - - public static bool CheckLuck( int chance ) - { - return ( chance > Utility.Random( 10000 ) ); - } - - private LootPackEntry[] m_Entries; - - public LootPack( LootPackEntry[] entries ) - { - m_Entries = entries; - } - - public void Generate( Mobile from, Container cont, bool spawning, int luckChance ) - { - if ( cont == null ) - return; - - bool checkLuck = Core.AOS; - - for ( int i = 0; i < m_Entries.Length; ++i ) - { - LootPackEntry entry = m_Entries[i]; - - bool shouldAdd = ( entry.Chance > Utility.Random( 10000 ) ); - - if ( !shouldAdd && checkLuck ) - { - checkLuck = false; - - if ( CheckLuck( luckChance ) ) - shouldAdd = ( entry.Chance > Utility.Random( 10000 ) ); - } - - if ( !shouldAdd ) - continue; - - Item item = entry.Construct( from, luckChance, spawning ); - - if ( item != null ) - { - if ( !item.Stackable || !cont.TryDropItem( from, item, false ) ) - cont.DropItem( item ); - } - } - } - - public static readonly LootPackItem[] Gold = { - new LootPackItem( typeof( Gold ), 1 ) - }; - - public static readonly LootPackItem[] Instruments = { - new LootPackItem( typeof( BaseInstrument ), 1 ) - }; - - - public static readonly LootPackItem[] LowScrollItems = { - new LootPackItem( typeof( ClumsyScroll ), 1 ) - }; - - public static readonly LootPackItem[] MedScrollItems = { - new LootPackItem( typeof( ArchCureScroll ), 1 ) - }; - - public static readonly LootPackItem[] HighScrollItems = { - new LootPackItem( typeof( SummonAirElementalScroll ), 1 ) - }; - - public static readonly LootPackItem[] GemItems = { - new LootPackItem( typeof( Amber ), 1 ) - }; - - public static readonly LootPackItem[] PotionItems = { - new LootPackItem( typeof( AgilityPotion ), 1 ), - new LootPackItem( typeof( StrengthPotion ), 1 ), - new LootPackItem( typeof( RefreshPotion ), 1 ), - new LootPackItem( typeof( LesserCurePotion ), 1 ), - new LootPackItem( typeof( LesserHealPotion ), 1 ), - new LootPackItem( typeof( LesserPoisonPotion ), 1 ) - }; - - #region Old Magic Items - public static readonly LootPackItem[] OldMagicItems = { - new LootPackItem( typeof( BaseJewel ), 1 ), - new LootPackItem( typeof( BaseArmor ), 4 ), - new LootPackItem( typeof( BaseWeapon ), 3 ), - new LootPackItem( typeof( BaseRanged ), 1 ), - new LootPackItem( typeof( BaseShield ), 1 ) - }; - #endregion - - #region AOS Magic Items - public static readonly LootPackItem[] AosMagicItemsPoor = { - new LootPackItem( typeof( BaseWeapon ), 3 ), - new LootPackItem( typeof( BaseRanged ), 1 ), - new LootPackItem( typeof( BaseArmor ), 4 ), - new LootPackItem( typeof( BaseShield ), 1 ), - new LootPackItem( typeof( BaseJewel ), 2 ) - }; - - public static readonly LootPackItem[] AosMagicItemsMeagerType1 = { - new LootPackItem( typeof( BaseWeapon ), 56 ), - new LootPackItem( typeof( BaseRanged ), 14 ), - new LootPackItem( typeof( BaseArmor ), 81 ), - new LootPackItem( typeof( BaseShield ), 11 ), - new LootPackItem( typeof( BaseJewel ), 42 ) - }; - - public static readonly LootPackItem[] AosMagicItemsMeagerType2 = { - new LootPackItem( typeof( BaseWeapon ), 28 ), - new LootPackItem( typeof( BaseRanged ), 7 ), - new LootPackItem( typeof( BaseArmor ), 40 ), - new LootPackItem( typeof( BaseShield ), 5 ), - new LootPackItem( typeof( BaseJewel ), 21 ) - }; - - public static readonly LootPackItem[] AosMagicItemsAverageType1 = { - new LootPackItem( typeof( BaseWeapon ), 90 ), - new LootPackItem( typeof( BaseRanged ), 23 ), - new LootPackItem( typeof( BaseArmor ), 130 ), - new LootPackItem( typeof( BaseShield ), 17 ), - new LootPackItem( typeof( BaseJewel ), 68 ) - }; - - public static readonly LootPackItem[] AosMagicItemsAverageType2 = { - new LootPackItem( typeof( BaseWeapon ), 54 ), - new LootPackItem( typeof( BaseRanged ), 13 ), - new LootPackItem( typeof( BaseArmor ), 77 ), - new LootPackItem( typeof( BaseShield ), 10 ), - new LootPackItem( typeof( BaseJewel ), 40 ) - }; - - public static readonly LootPackItem[] AosMagicItemsRichType1 = { - new LootPackItem( typeof( BaseWeapon ), 211 ), - new LootPackItem( typeof( BaseRanged ), 53 ), - new LootPackItem( typeof( BaseArmor ), 303 ), - new LootPackItem( typeof( BaseShield ), 39 ), - new LootPackItem( typeof( BaseJewel ), 158 ) - }; - - public static readonly LootPackItem[] AosMagicItemsRichType2 = { - new LootPackItem( typeof( BaseWeapon ), 170 ), - new LootPackItem( typeof( BaseRanged ), 43 ), - new LootPackItem( typeof( BaseArmor ), 245 ), - new LootPackItem( typeof( BaseShield ), 32 ), - new LootPackItem( typeof( BaseJewel ), 128 ) - }; - - public static readonly LootPackItem[] AosMagicItemsFilthyRichType1 = { - new LootPackItem( typeof( BaseWeapon ), 219 ), - new LootPackItem( typeof( BaseRanged ), 55 ), - new LootPackItem( typeof( BaseArmor ), 315 ), - new LootPackItem( typeof( BaseShield ), 41 ), - new LootPackItem( typeof( BaseJewel ), 164 ) - }; - - public static readonly LootPackItem[] AosMagicItemsFilthyRichType2 = { - new LootPackItem( typeof( BaseWeapon ), 239 ), - new LootPackItem( typeof( BaseRanged ), 60 ), - new LootPackItem( typeof( BaseArmor ), 343 ), - new LootPackItem( typeof( BaseShield ), 90 ), - new LootPackItem( typeof( BaseJewel ), 45 ) - }; - - public static readonly LootPackItem[] AosMagicItemsUltraRich = { - new LootPackItem( typeof( BaseWeapon ), 276 ), - new LootPackItem( typeof( BaseRanged ), 69 ), - new LootPackItem( typeof( BaseArmor ), 397 ), - new LootPackItem( typeof( BaseShield ), 52 ), - new LootPackItem( typeof( BaseJewel ), 207 ) - }; - #endregion - - #region ML definitions - public static readonly LootPack MlRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "4d50+450" ), - new LootPackEntry( false, AosMagicItemsRichType1, 100.00, 1, 3, 0, 75 ), - new LootPackEntry( false, AosMagicItemsRichType1, 80.00, 1, 3, 0, 75 ), - new LootPackEntry( false, AosMagicItemsRichType1, 60.00, 1, 5, 0, 100 ), - new LootPackEntry( false, Instruments, 1.00, 1 ) - } ); - #endregion - - #region SE definitions - public static readonly LootPack SePoor = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "2d10+20" ), - new LootPackEntry( false, AosMagicItemsPoor, 1.00, 1, 5, 0, 100 ), - new LootPackEntry( false, Instruments, 0.02, 1 ) - } ); - - public static readonly LootPack SeMeager = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "4d10+40" ), - new LootPackEntry( false, AosMagicItemsMeagerType1, 20.40, 1, 2, 0, 50 ), - new LootPackEntry( false, AosMagicItemsMeagerType2, 10.20, 1, 5, 0, 100 ), - new LootPackEntry( false, Instruments, 0.10, 1 ) - } ); - - public static readonly LootPack SeAverage = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "8d10+100" ), - new LootPackEntry( false, AosMagicItemsAverageType1, 32.80, 1, 3, 0, 50 ), - new LootPackEntry( false, AosMagicItemsAverageType1, 32.80, 1, 4, 0, 75 ), - new LootPackEntry( false, AosMagicItemsAverageType2, 19.50, 1, 5, 0, 100 ), - new LootPackEntry( false, Instruments, 0.40, 1 ) - } ); - - public static readonly LootPack SeRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "15d10+225" ), - new LootPackEntry( false, AosMagicItemsRichType1, 76.30, 1, 4, 0, 75 ), - new LootPackEntry( false, AosMagicItemsRichType1, 76.30, 1, 4, 0, 75 ), - new LootPackEntry( false, AosMagicItemsRichType2, 61.70, 1, 5, 0, 100 ), - new LootPackEntry( false, Instruments, 1.00, 1 ) - } ); - - public static readonly LootPack SeFilthyRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "3d100+400" ), - new LootPackEntry( false, AosMagicItemsFilthyRichType1, 79.50, 1, 5, 0, 100 ), - new LootPackEntry( false, AosMagicItemsFilthyRichType1, 79.50, 1, 5, 0, 100 ), - new LootPackEntry( false, AosMagicItemsFilthyRichType2, 77.60, 1, 5, 25, 100 ), - new LootPackEntry( false, Instruments, 2.00, 1 ) - } ); - - public static readonly LootPack SeUltraRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "6d100+600" ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, Instruments, 2.00, 1 ) - } ); - - public static readonly LootPack SeSuperBoss = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "10d100+800" ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100 ), - new LootPackEntry( false, Instruments, 2.00, 1 ) - } ); - #endregion - - #region AOS definitions - public static readonly LootPack AosPoor = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "1d10+10" ), - new LootPackEntry( false, AosMagicItemsPoor, 0.02, 1, 5, 0, 90 ), - new LootPackEntry( false, Instruments, 0.02, 1 ) - } ); - - public static readonly LootPack AosMeager = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "3d10+20" ), - new LootPackEntry( false, AosMagicItemsMeagerType1, 1.00, 1, 2, 0, 10 ), - new LootPackEntry( false, AosMagicItemsMeagerType2, 0.20, 1, 5, 0, 90 ), - new LootPackEntry( false, Instruments, 0.10, 1 ) - } ); - - public static readonly LootPack AosAverage = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "5d10+50" ), - new LootPackEntry( false, AosMagicItemsAverageType1, 5.00, 1, 4, 0, 20 ), - new LootPackEntry( false, AosMagicItemsAverageType1, 2.00, 1, 3, 0, 50 ), - new LootPackEntry( false, AosMagicItemsAverageType2, 0.50, 1, 5, 0, 90 ), - new LootPackEntry( false, Instruments, 0.40, 1 ) - } ); - - public static readonly LootPack AosRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "10d10+150" ), - new LootPackEntry( false, AosMagicItemsRichType1, 20.00, 1, 4, 0, 40 ), - new LootPackEntry( false, AosMagicItemsRichType1, 10.00, 1, 5, 0, 60 ), - new LootPackEntry( false, AosMagicItemsRichType2, 1.00, 1, 5, 0, 90 ), - new LootPackEntry( false, Instruments, 1.00, 1 ) - } ); - - public static readonly LootPack AosFilthyRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "2d100+200" ), - new LootPackEntry( false, AosMagicItemsFilthyRichType1, 33.00, 1, 4, 0, 50 ), - new LootPackEntry( false, AosMagicItemsFilthyRichType1, 33.00, 1, 4, 0, 60 ), - new LootPackEntry( false, AosMagicItemsFilthyRichType2, 20.00, 1, 5, 0, 75 ), - new LootPackEntry( false, AosMagicItemsFilthyRichType2, 5.00, 1, 5, 0, 100 ), - new LootPackEntry( false, Instruments, 2.00, 1 ) - } ); - - public static readonly LootPack AosUltraRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "5d100+500" ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 35, 100 ), - new LootPackEntry( false, Instruments, 2.00, 1 ) - } ); - - public static readonly LootPack AosSuperBoss = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "5d100+500" ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 25, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 33, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100 ), - new LootPackEntry( false, AosMagicItemsUltraRich, 100.00, 1, 5, 50, 100 ), - new LootPackEntry( false, Instruments, 2.00, 1 ) - } ); - #endregion - - #region Pre-AOS definitions - public static readonly LootPack OldPoor = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "1d25" ), - new LootPackEntry( false, Instruments, 0.02, 1 ) - } ); - - public static readonly LootPack OldMeager = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "5d10+25" ), - new LootPackEntry( false, Instruments, 0.10, 1 ), - new LootPackEntry( false, OldMagicItems, 1.00, 1, 1, 0, 60 ), - new LootPackEntry( false, OldMagicItems, 0.20, 1, 1, 10, 70 ) - } ); - - public static readonly LootPack OldAverage = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "10d10+50" ), - new LootPackEntry( false, Instruments, 0.40, 1 ), - new LootPackEntry( false, OldMagicItems, 5.00, 1, 1, 20, 80 ), - new LootPackEntry( false, OldMagicItems, 2.00, 1, 1, 30, 90 ), - new LootPackEntry( false, OldMagicItems, 0.50, 1, 1, 40, 100 ) - } ); - - public static readonly LootPack OldRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "10d10+250" ), - new LootPackEntry( false, Instruments, 1.00, 1 ), - new LootPackEntry( false, OldMagicItems, 20.00, 1, 1, 60, 100 ), - new LootPackEntry( false, OldMagicItems, 10.00, 1, 1, 65, 100 ), - new LootPackEntry( false, OldMagicItems, 1.00, 1, 1, 70, 100 ) - } ); - - public static readonly LootPack OldFilthyRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "2d125+400" ), - new LootPackEntry( false, Instruments, 2.00, 1 ), - new LootPackEntry( false, OldMagicItems, 33.00, 1, 1, 50, 100 ), - new LootPackEntry( false, OldMagicItems, 33.00, 1, 1, 60, 100 ), - new LootPackEntry( false, OldMagicItems, 20.00, 1, 1, 70, 100 ), - new LootPackEntry( false, OldMagicItems, 5.00, 1, 1, 80, 100 ) - } ); - - public static readonly LootPack OldUltraRich = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "5d100+500" ), - new LootPackEntry( false, Instruments, 2.00, 1 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 40, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 40, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 50, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 50, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 60, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 60, 100 ) - } ); - - public static readonly LootPack OldSuperBoss = new LootPack( new[] - { - new LootPackEntry( true, Gold, 100.00, "5d100+500" ), - new LootPackEntry( false, Instruments, 2.00, 1 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 40, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 40, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 40, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 50, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 50, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 50, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 60, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 60, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 60, 100 ), - new LootPackEntry( false, OldMagicItems, 100.00, 1, 1, 70, 100 ) - } ); - #endregion - - #region Generic accessors - public static LootPack Poor => Core.SE ? SePoor : Core.AOS ? AosPoor : OldPoor; - public static LootPack Meager => Core.SE ? SeMeager : Core.AOS ? AosMeager : OldMeager; - public static LootPack Average => Core.SE ? SeAverage : Core.AOS ? AosAverage : OldAverage; - public static LootPack Rich => Core.SE ? SeRich : Core.AOS ? AosRich : OldRich; - public static LootPack FilthyRich => Core.SE ? SeFilthyRich : Core.AOS ? AosFilthyRich : OldFilthyRich; - public static LootPack UltraRich => Core.SE ? SeUltraRich : Core.AOS ? AosUltraRich : OldUltraRich; - public static LootPack SuperBoss => Core.SE ? SeSuperBoss : Core.AOS ? AosSuperBoss : OldSuperBoss; - - #endregion - - public static readonly LootPack LowScrolls = new LootPack( new[] - { - new LootPackEntry( false, LowScrollItems, 100.00, 1 ) - } ); - - public static readonly LootPack MedScrolls = new LootPack( new[] - { - new LootPackEntry( false, MedScrollItems, 100.00, 1 ) - } ); - - public static readonly LootPack HighScrolls = new LootPack( new[] - { - new LootPackEntry( false, HighScrollItems, 100.00, 1 ) - } ); - - public static readonly LootPack Gems = new LootPack( new[] - { - new LootPackEntry( false, GemItems, 100.00, 1 ) - } ); - - public static readonly LootPack Potions = new LootPack( new[] - { - new LootPackEntry( false, PotionItems, 100.00, 1 ) - } ); - - /* - // TODO: Uncomment once added - #region Mondain's Legacy - public static readonly LootPackItem[] ParrotItem = new LootPackItem[] - { - new LootPackItem( typeof( ParrotItem ), 1 ) - }; - - public static readonly LootPack Parrot = new LootPack( new LootPackEntry[] - { - new LootPackEntry( false, ParrotItem, 10.00, 1 ) - } ); - #endregion - */ - } - - public class LootPackEntry - { - private bool m_AtSpawnTime; - - public int Chance { get; set; } - - public LootPackDice Quantity { get; set; } - - public int MaxProps { get; set; } - - public int MinIntensity { get; set; } - - public int MaxIntensity { get; set; } - - public LootPackItem[] Items { get; set; } - - private static bool IsInTokuno( Mobile m ) - { - if ( m.Region.IsPartOf( "Fan Dancer's Dojo" ) ) - return true; - - if ( m.Region.IsPartOf( "Yomotsu Mines" ) ) - return true; - - return ( m.Map == Map.Tokuno ); - } - - #region Mondain's Legacy - private static bool IsMondain( Mobile m ) - { - return MondainsLegacy.IsMLRegion( m.Region ); - } - #endregion - - public Item Construct( Mobile from, int luckChance, bool spawning ) - { - if ( m_AtSpawnTime != spawning ) - return null; - - int totalChance = 0; - - for ( int i = 0; i < Items.Length; ++i ) - totalChance += Items[i].Chance; - - int rnd = Utility.Random( totalChance ); - - for ( int i = 0; i < Items.Length; ++i ) - { - LootPackItem item = Items[i]; - - if ( rnd < item.Chance ) - return Mutate( from, luckChance, item.Construct( IsInTokuno( from ), IsMondain( from ) ) ); - - rnd -= item.Chance; - } - - return null; - } - - private int GetRandomOldBonus() - { - int rnd = Utility.RandomMinMax( MinIntensity, MaxIntensity ); - - if ( 50 > rnd ) - return 1; - rnd -= 50; - - if ( 25 > rnd ) - return 2; - rnd -= 25; - - if ( 14 > rnd ) - return 3; - rnd -= 14; - - if ( 8 > rnd ) - return 4; - - return 5; - } - - public Item Mutate( Mobile from, int luckChance, Item item ) - { - if ( item != null ) - { - if ( item is BaseWeapon && 1 > Utility.Random( 100 ) ) - { - item.Delete(); - item = new FireHorn(); - return item; - } - - if ( item is BaseWeapon || item is BaseArmor || item is BaseJewel || item is BaseHat ) - { - if ( Core.AOS ) - { - int bonusProps = GetBonusProperties(); - int min = MinIntensity; - int max = MaxIntensity; - - if ( bonusProps < MaxProps && LootPack.CheckLuck( luckChance ) ) - ++bonusProps; - - int props = 1 + bonusProps; - - // Make sure we're not spawning items with 6 properties. - if ( props > MaxProps ) - props = MaxProps; - - if ( item is BaseWeapon weapon ) - BaseRunicTool.ApplyAttributesTo( weapon, false, luckChance, props, MinIntensity, MaxIntensity ); - else if ( item is BaseArmor armor ) - BaseRunicTool.ApplyAttributesTo( armor, false, luckChance, props, MinIntensity, MaxIntensity ); - else if ( item is BaseJewel jewel ) - BaseRunicTool.ApplyAttributesTo( jewel, false, luckChance, props, MinIntensity, MaxIntensity ); - else - BaseRunicTool.ApplyAttributesTo( (BaseHat)item, false, luckChance, props, MinIntensity, MaxIntensity ); - } - else // not aos - { - if ( item is BaseWeapon weapon ) - { - if ( 80 > Utility.Random( 100 ) ) - weapon.AccuracyLevel = (WeaponAccuracyLevel)GetRandomOldBonus(); - - if ( 60 > Utility.Random( 100 ) ) - weapon.DamageLevel = (WeaponDamageLevel)GetRandomOldBonus(); - - if ( 40 > Utility.Random( 100 ) ) - weapon.DurabilityLevel = (WeaponDurabilityLevel)GetRandomOldBonus(); - - if ( 5 > Utility.Random( 100 ) ) - weapon.Slayer = SlayerName.Silver; - - if ( from != null && weapon.AccuracyLevel == 0 && weapon.DamageLevel == 0 && weapon.DurabilityLevel == 0 && weapon.Slayer == SlayerName.None && 5 > Utility.Random( 100 ) ) - weapon.Slayer = SlayerGroup.GetLootSlayerType( from.GetType() ); - } - else if ( item is BaseArmor armor ) - { - if ( 80 > Utility.Random( 100 ) ) - armor.ProtectionLevel = (ArmorProtectionLevel)GetRandomOldBonus(); - - if ( 40 > Utility.Random( 100 ) ) - armor.Durability = (ArmorDurabilityLevel)GetRandomOldBonus(); - } - } - } - else if ( item is BaseInstrument instr ) - { - SlayerName slayer = SlayerName.None; - - if ( Core.AOS ) - slayer = BaseRunicTool.GetRandomSlayer(); - else - slayer = SlayerGroup.GetLootSlayerType( from.GetType() ); - - if ( slayer == SlayerName.None ) - { - instr.Delete(); - return null; - } - - instr.Quality = InstrumentQuality.Regular; - instr.Slayer = slayer; - } - - if ( item.Stackable ) - item.Amount = Quantity.Roll(); - } - - return item; - } - - public LootPackEntry( bool atSpawnTime, LootPackItem[] items, double chance, string quantity ) : this( atSpawnTime, items, chance, new LootPackDice( quantity ), 0, 0, 0 ) - { - } - - public LootPackEntry( bool atSpawnTime, LootPackItem[] items, double chance, int quantity ) : this( atSpawnTime, items, chance, new LootPackDice( 0, 0, quantity ), 0, 0, 0 ) - { - } - - public LootPackEntry( bool atSpawnTime, LootPackItem[] items, double chance, string quantity, int maxProps, int minIntensity, int maxIntensity ) : this( atSpawnTime, items, chance, new LootPackDice( quantity ), maxProps, minIntensity, maxIntensity ) - { - } - - public LootPackEntry( bool atSpawnTime, LootPackItem[] items, double chance, int quantity, int maxProps, int minIntensity, int maxIntensity ) : this( atSpawnTime, items, chance, new LootPackDice( 0, 0, quantity ), maxProps, minIntensity, maxIntensity ) - { - } - - public LootPackEntry( bool atSpawnTime, LootPackItem[] items, double chance, LootPackDice quantity, int maxProps, int minIntensity, int maxIntensity ) - { - m_AtSpawnTime = atSpawnTime; - Items = items; - Chance = (int)(100 * chance); - Quantity = quantity; - MaxProps = maxProps; - MinIntensity = minIntensity; - MaxIntensity = maxIntensity; - } - - public int GetBonusProperties() - { - int p0=0, p1=0, p2=0, p3=0, p4=0, p5=0; - - switch ( MaxProps ) - { - case 1: p0= 3; p1= 1; break; - case 2: p0= 6; p1= 3; p2= 1; break; - case 3: p0=10; p1= 6; p2= 3; p3= 1; break; - case 4: p0=16; p1=12; p2= 6; p3= 5; p4=1; break; - case 5: p0=30; p1=25; p2=20; p3=15; p4=9; p5=1; break; - } - - int pc = p0+p1+p2+p3+p4+p5; - - int rnd = Utility.Random( pc ); - - if ( rnd < p5 ) - return 5; - - rnd -= p5; - - if ( rnd < p4 ) - return 4; - - rnd -= p4; - - if ( rnd < p3 ) - return 3; - - rnd -= p3; - - if ( rnd < p2 ) - return 2; - - return rnd - p2 < p1 ? 1 : 0; - } - } - - public class LootPackItem - { - public Type Type { get; set; } - - public int Chance { get; set; } - - private static Type[] m_BlankTypes = { typeof( BlankScroll ) }; - private static Type[][] m_NecroTypes = { - new[] // low - { - typeof( AnimateDeadScroll ), typeof( BloodOathScroll ), typeof( CorpseSkinScroll ), typeof( CurseWeaponScroll ), - typeof( EvilOmenScroll ), typeof( HorrificBeastScroll ), typeof( MindRotScroll ), typeof( PainSpikeScroll ), - typeof( SummonFamiliarScroll ), typeof( WraithFormScroll ) - }, - new[] // med - { - typeof( LichFormScroll ), typeof( PoisonStrikeScroll ), typeof( StrangleScroll ), typeof( WitherScroll ) - }, - - ((Core.SE) ? - new[] // high - { - typeof( VengefulSpiritScroll ), typeof( VampiricEmbraceScroll ), typeof( ExorcismScroll ) - } : - new[] // high - { - typeof( VengefulSpiritScroll ), typeof( VampiricEmbraceScroll ) - }) - }; - - public static Item RandomScroll( int index, int minCircle, int maxCircle ) - { - --minCircle; - --maxCircle; - - int scrollCount = ((maxCircle - minCircle) + 1) * 8; - - if ( index == 0 ) - scrollCount += m_BlankTypes.Length; - - if ( Core.AOS ) - scrollCount += m_NecroTypes[index].Length; - - int rnd = Utility.Random( scrollCount ); - - if ( index == 0 && rnd < m_BlankTypes.Length ) - return Loot.Construct( m_BlankTypes ); - if ( index == 0 ) - rnd -= m_BlankTypes.Length; - - if ( Core.AOS && rnd < m_NecroTypes.Length ) - return Loot.Construct( m_NecroTypes[index] ); - - return Loot.RandomScroll( minCircle * 8, (maxCircle * 8) + 7, SpellbookType.Regular ); - } - - public Item Construct( bool inTokuno, bool isMondain ) - { - try - { - Item item; - - if ( Type == typeof( BaseRanged ) ) - item = Loot.RandomRangedWeapon( inTokuno, isMondain ); - else if ( Type == typeof( BaseWeapon ) ) - item = Loot.RandomWeapon( inTokuno, isMondain ); - else if ( Type == typeof( BaseArmor ) ) - item = Loot.RandomArmorOrHat( inTokuno, isMondain ); - else if ( Type == typeof( BaseShield ) ) - item = Loot.RandomShield(); - else if ( Type == typeof( BaseJewel ) ) - item = Core.AOS ? Loot.RandomJewelry() : Loot.RandomArmorOrShieldOrWeapon(); - else if ( Type == typeof( BaseInstrument ) ) - item = Loot.RandomInstrument(); - else if ( Type == typeof( Amber ) ) // gem - item = Loot.RandomGem(); - else if ( Type == typeof( ClumsyScroll ) ) // low scroll - item = RandomScroll( 0, 1, 3 ); - else if ( Type == typeof( ArchCureScroll ) ) // med scroll - item = RandomScroll( 1, 4, 7 ); - else if ( Type == typeof( SummonAirElementalScroll ) ) // high scroll - item = RandomScroll( 2, 8, 8 ); - else - item = Activator.CreateInstance( Type ) as Item; - - return item; - } - catch - { - } - - return null; - } - - public LootPackItem( Type type, int chance ) - { - Type = type; - Chance = chance; - } - } - - public class LootPackDice - { - public int Count { get; set; } - - public int Sides { get; set; } - - public int Bonus { get; set; } - - public int Roll() - { - int v = Bonus; - - for ( int i = 0; i < Count; ++i ) - v += Utility.Random( 1, Sides ); - - return v; - } - - public LootPackDice( string str ) - { - int start = 0; - int index = str.IndexOf( 'd', start ); - - if ( index < start ) - return; - - Count = Utility.ToInt32( str.Substring( start, index-start ) ); - - start = index + 1; - index = str.IndexOf( '+', start ); - - bool negative = index < start; - - if ( negative ) - index = str.IndexOf( '-', start ); - - if ( index < start ) - index = str.Length; - - Sides = Utility.ToInt32( str.Substring( start, index-start ) ); - - if ( index == str.Length ) - return; - - start = index + 1; - index = str.Length; - - Bonus = Utility.ToInt32( str.Substring( start, index-start ) ); - - if ( negative ) - Bonus *= -1; - } - - public LootPackDice( int count, int sides, int bonus ) - { - Count = count; - Sides = sides; - Bonus = bonus; - } - } -} + if (negative) + Bonus *= -1; + } + + public LootPackDice(int count, int sides, int bonus) + { + Count = count; + Sides = sides; + Bonus = bonus; + } + + public int Count{ get; set; } + + public int Sides{ get; set; } + + public int Bonus{ get; set; } + + public int Roll() + { + int v = Bonus; + + for (int i = 0; i < Count; ++i) + v += Utility.Random(1, Sides); + + return v; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/MapDefinitions.cs b/Scripts/Misc/MapDefinitions.cs index ab9231a9b..f0558527a 100644 --- a/Scripts/Misc/MapDefinitions.cs +++ b/Scripts/Misc/MapDefinitions.cs @@ -1,51 +1,52 @@ namespace Server.Misc { - public class MapDefinitions - { - public static void Configure() - { - /* Here we configure all maps. Some notes: - * - * 1) The first 32 maps are reserved for core use. - * 2) Map 0x7F is reserved for core use. - * 3) Map 0xFF is reserved for core use. - * 4) Changing or removing any predefined maps may cause server instability. - */ + public class MapDefinitions + { + public static void Configure() + { + /* Here we configure all maps. Some notes: + * + * 1) The first 32 maps are reserved for core use. + * 2) Map 0x7F is reserved for core use. + * 3) Map 0xFF is reserved for core use. + * 4) Changing or removing any predefined maps may cause server instability. + */ - RegisterMap( 0, 0, 0, 7168, 4096, 4, "Felucca", MapRules.FeluccaRules ); - RegisterMap( 1, 1, 1, 7168, 4096, 0, "Trammel", MapRules.TrammelRules ); - RegisterMap( 2, 2, 2, 2304, 1600, 1, "Ilshenar", MapRules.TrammelRules ); - RegisterMap( 3, 3, 3, 2560, 2048, 1, "Malas", MapRules.TrammelRules ); - RegisterMap( 4, 4, 4, 1448, 1448, 1, "Tokuno", MapRules.TrammelRules ); - RegisterMap( 5, 5, 5, 1280, 4096, 1, "TerMur", MapRules.TrammelRules ); + RegisterMap(0, 0, 0, 7168, 4096, 4, "Felucca", MapRules.FeluccaRules); + RegisterMap(1, 1, 1, 7168, 4096, 0, "Trammel", MapRules.TrammelRules); + RegisterMap(2, 2, 2, 2304, 1600, 1, "Ilshenar", MapRules.TrammelRules); + RegisterMap(3, 3, 3, 2560, 2048, 1, "Malas", MapRules.TrammelRules); + RegisterMap(4, 4, 4, 1448, 1448, 1, "Tokuno", MapRules.TrammelRules); + RegisterMap(5, 5, 5, 1280, 4096, 1, "TerMur", MapRules.TrammelRules); - RegisterMap( 0x7F, 0x7F, 0x7F, Map.SectorSize, Map.SectorSize, 1, "Internal", MapRules.Internal ); + RegisterMap(0x7F, 0x7F, 0x7F, Map.SectorSize, Map.SectorSize, 1, "Internal", MapRules.Internal); - /* Example of registering a custom map: - * RegisterMap( 32, 0, 0, 6144, 4096, 3, "Iceland", MapRules.FeluccaRules ); - * - * Defined: - * RegisterMap( , , , , , , , ); - * - : An unreserved unique index for this map - * - : An identification number used in client communications. For any visible maps, this value must be from 0-5 - * - : A file identification number. For any visible maps, this value must be from 0-5 - * - , : Size of the map (in tiles) - * - : Season of the map. 0 = Spring, 1 = Summer, 2 = Fall, 3 = Winter, 4 = Desolation - * - : Reference name for the map, used in props gump, get/set commands, region loading, etc - * - : Rules and restrictions associated with the map. See documentation for details - */ + /* Example of registering a custom map: + * RegisterMap( 32, 0, 0, 6144, 4096, 3, "Iceland", MapRules.FeluccaRules ); + * + * Defined: + * RegisterMap( , , , , , , , ); + * - : An unreserved unique index for this map + * - : An identification number used in client communications. For any visible maps, this value must be from 0-5 + * - : A file identification number. For any visible maps, this value must be from 0-5 + * - , : Size of the map (in tiles) + * - : Season of the map. 0 = Spring, 1 = Summer, 2 = Fall, 3 = Winter, 4 = Desolation + * - : Reference name for the map, used in props gump, get/set commands, region loading, etc + * - : Rules and restrictions associated with the map. See documentation for details + */ - TileMatrixPatch.Enabled = false; // OSI Client Patch 6.0.0.0 + TileMatrixPatch.Enabled = false; // OSI Client Patch 6.0.0.0 - MultiComponentList.PostHSFormat = true; // OSI Client Patch 7.0.9.0 - } + MultiComponentList.PostHSFormat = true; // OSI Client Patch 7.0.9.0 + } - public static void RegisterMap( int mapIndex, int mapID, int fileIndex, int width, int height, int season, string name, MapRules rules ) - { - Map newMap = new Map( mapID, mapIndex, fileIndex, width, height, season, name, rules ); + public static void RegisterMap(int mapIndex, int mapID, int fileIndex, int width, int height, int season, + string name, MapRules rules) + { + Map newMap = new Map(mapID, mapIndex, fileIndex, width, height, season, name, rules); - Map.Maps[mapIndex] = newMap; - Map.AllMaps.Add( newMap ); - } - } + Map.Maps[mapIndex] = newMap; + Map.AllMaps.Add(newMap); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/MapUO.cs b/Scripts/Misc/MapUO.cs index 30630d329..7263c6530 100644 --- a/Scripts/Misc/MapUO.cs +++ b/Scripts/Misc/MapUO.cs @@ -1,127 +1,130 @@ using System; -using Server.Network; using Server.Engines.PartySystem; using Server.Guilds; +using Server.Network; namespace Server.Misc { - public static partial class MapUO - { - private static class Settings - { - public const bool PartyTrack = true; - public const bool GuildTrack = true; - public const bool GuildHitsPercent = true; - } + public static class MapUO + { + public static void Initialize() + { + if (Settings.PartyTrack) + ProtocolExtensions.Register(0x00, true, OnPartyTrack); - public static void Initialize() - { - if ( Settings.PartyTrack ) - ProtocolExtensions.Register( 0x00, true, OnPartyTrack ); + if (Settings.GuildTrack) + ProtocolExtensions.Register(0x01, true, OnGuildTrack); + } - if ( Settings.GuildTrack ) - ProtocolExtensions.Register( 0x01, true, OnGuildTrack ); - } + private static void OnPartyTrack(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + Party party = Party.Get(from); - private static void OnPartyTrack( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - Party party = Party.Get( from ); + if (party != null) + { + Packets.PartyTrack packet = new Packets.PartyTrack(from, party); - if ( party != null ) - { - Packets.PartyTrack packet = new Packets.PartyTrack( from, party ); + if (packet.UnderlyingStream.Length > 8) + state.Send(packet); + } + } - if ( packet.UnderlyingStream.Length > 8 ) - state.Send( packet ); - } - } + private static void OnGuildTrack(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; - private static void OnGuildTrack( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; + if (from.Guild is Guild guild) + { + bool locations = pvSrc.ReadByte() != 0; - if ( from.Guild is Guild guild ) - { - bool locations = pvSrc.ReadByte() != 0; + Packets.GuildTrack packet = new Packets.GuildTrack(from, guild, locations); - Packets.GuildTrack packet = new Packets.GuildTrack( from, guild, locations ); + if (packet.UnderlyingStream.Length > (locations ? 9 : 5)) + state.Send(packet); + } + else + { + state.Send(new Packets.GuildTrack()); + } + } - if ( packet.UnderlyingStream.Length > ( locations ? 9 : 5 ) ) - state.Send( packet ); - } - else - state.Send( new Packets.GuildTrack() ); - } + private static class Settings + { + public const bool PartyTrack = true; + public const bool GuildTrack = true; + public const bool GuildHitsPercent = true; + } - private static class Packets - { - public sealed class PartyTrack : ProtocolExtension - { - public PartyTrack( Mobile from, Party party ) : base( 0x01, ( ( party.Members.Count - 1 ) * 9 ) + 4 ) - { - for ( int i = 0; i < party.Members.Count; ++i ) - { - PartyMemberInfo pmi = (PartyMemberInfo)party.Members[i]; + private static class Packets + { + public sealed class PartyTrack : ProtocolExtension + { + public PartyTrack(Mobile from, Party party) : base(0x01, (party.Members.Count - 1) * 9 + 4) + { + for (int i = 0; i < party.Members.Count; ++i) + { + PartyMemberInfo pmi = party.Members[i]; - if ( pmi == null || pmi.Mobile == from ) - continue; + if (pmi == null || pmi.Mobile == from) + continue; - Mobile mob = pmi.Mobile; + Mobile mob = pmi.Mobile; - if ( Utility.InUpdateRange( from, mob ) && from.CanSee( mob ) ) - continue; + if (Utility.InUpdateRange(from, mob) && from.CanSee(mob)) + continue; - m_Stream.Write( (int) mob.Serial ); - m_Stream.Write( (short) mob.X ); - m_Stream.Write( (short) mob.Y ); - m_Stream.Write( (byte) (mob.Map?.MapID ?? 0) ); - } + m_Stream.Write(mob.Serial); + m_Stream.Write((short)mob.X); + m_Stream.Write((short)mob.Y); + m_Stream.Write((byte)(mob.Map?.MapID ?? 0)); + } - m_Stream.Write( (int) 0 ); - } - } + m_Stream.Write(0); + } + } - public sealed class GuildTrack : ProtocolExtension - { - public GuildTrack() : base( 0x02, 5 ) - { - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (int) 0 ); - } + public sealed class GuildTrack : ProtocolExtension + { + public GuildTrack() : base(0x02, 5) + { + m_Stream.Write((byte)0); + m_Stream.Write(0); + } - public GuildTrack( Mobile from, Guild guild, bool locations ) : base( 0x02, ( ( guild.Members.Count - 1 ) * ( locations ? 10 : 4 ) ) + 5 ) - { - m_Stream.Write( (byte) ( locations ? 1 : 0 ) ); + public GuildTrack(Mobile from, Guild guild, bool locations) : base(0x02, + (guild.Members.Count - 1) * (locations ? 10 : 4) + 5) + { + m_Stream.Write((byte)(locations ? 1 : 0)); - for ( int i = 0; i < guild.Members.Count; ++i ) - { - Mobile mob = guild.Members[i]; + for (int i = 0; i < guild.Members.Count; ++i) + { + Mobile mob = guild.Members[i]; - if ( mob == null || mob == from || mob.NetState == null ) - continue; + if (mob == null || mob == from || mob.NetState == null) + continue; - if ( locations && Utility.InUpdateRange( from, mob ) && from.CanSee( mob ) ) - continue; + if (locations && Utility.InUpdateRange(from, mob) && from.CanSee(mob)) + continue; - m_Stream.Write( (int) mob.Serial ); + m_Stream.Write(mob.Serial); - if ( locations ) - { - m_Stream.Write( (short) mob.X ); - m_Stream.Write( (short) mob.Y ); - m_Stream.Write( (byte) (mob.Map?.MapID ?? 0) ); + if (locations) + { + m_Stream.Write((short)mob.X); + m_Stream.Write((short)mob.Y); + m_Stream.Write((byte)(mob.Map?.MapID ?? 0)); - if ( Settings.GuildHitsPercent && mob.Alive ) - m_Stream.Write( (byte) ( mob.Hits / Math.Max( mob.HitsMax, 1.0 ) * 100 ) ); - else - m_Stream.Write( (byte) 0 ); - } - } + if (Settings.GuildHitsPercent && mob.Alive) + m_Stream.Write((byte)(mob.Hits / Math.Max(mob.HitsMax, 1.0) * 100)); + else + m_Stream.Write((byte)0); + } + } - m_Stream.Write( (int) 0 ); - } - } - } - } -} + m_Stream.Write(0); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/MondainsLegacy.cs b/Scripts/Misc/MondainsLegacy.cs index dc5347625..213dc69a2 100644 --- a/Scripts/Misc/MondainsLegacy.cs +++ b/Scripts/Misc/MondainsLegacy.cs @@ -4,73 +4,75 @@ using Server.Mobiles; namespace Server { - public static class MondainsLegacy - { - public static Type[] Artifacts { get; } = - { - typeof( AegisOfGrace ), typeof( BladeDance ), typeof( BloodwoodSpirit ), typeof( Bonesmasher ), - typeof( Boomstick ), typeof( BrightsightLenses ), typeof( FeyLeggings ), typeof( FleshRipper ), - typeof( HelmOfSwiftness ), typeof( PadsOfTheCuSidhe ), typeof( QuiverOfRage ), typeof( QuiverOfElements ), - typeof( RaedsGlory ), typeof( RighteousAnger ), typeof( RobeOfTheEclipse ), typeof( RobeOfTheEquinox ), - typeof( SoulSeeker ), typeof( TalonBite ), typeof( TotemOfVoid ), typeof( WildfireBow ), - typeof( Windsong ) - }; + public static class MondainsLegacy + { + public static Type[] Artifacts{ get; } = + { + typeof(AegisOfGrace), typeof(BladeDance), typeof(BloodwoodSpirit), typeof(Bonesmasher), + typeof(Boomstick), typeof(BrightsightLenses), typeof(FeyLeggings), typeof(FleshRipper), + typeof(HelmOfSwiftness), typeof(PadsOfTheCuSidhe), typeof(QuiverOfRage), typeof(QuiverOfElements), + typeof(RaedsGlory), typeof(RighteousAnger), typeof(RobeOfTheEclipse), typeof(RobeOfTheEquinox), + typeof(SoulSeeker), typeof(TalonBite), typeof(TotemOfVoid), typeof(WildfireBow), + typeof(Windsong) + }; - public static bool CheckArtifactChance( Mobile m, BaseCreature bc ) - { - if ( !Core.ML ) - return false; + public static bool CheckArtifactChance(Mobile m, BaseCreature bc) + { + if (!Core.ML) + return false; - return Paragon.CheckArtifactChance( m, bc ); - } + return Paragon.CheckArtifactChance(m, bc); + } - public static void GiveArtifactTo( Mobile m ) - { - if ( !(Activator.CreateInstance( Artifacts[Utility.Random( Artifacts.Length )] ) is Item item) ) - return; + public static void GiveArtifactTo(Mobile m) + { + if (!(Activator.CreateInstance(Artifacts[Utility.Random(Artifacts.Length)]) is Item item)) + return; - if ( m.AddToBackpack( item ) ) - { - m.SendLocalizedMessage( 1072223 ); // An item has been placed in your backpack. - m.SendLocalizedMessage( 1062317 ); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. - } - else if ( m.BankBox.TryDropItem( m, item, false ) ) - { - m.SendLocalizedMessage( 1072224 ); // An item has been placed in your bank box. - m.SendLocalizedMessage( 1062317 ); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. - } - else - { - // Item was placed at feet by m.AddToBackpack - m.SendLocalizedMessage( 1072523 ); // You find an artifact, but your backpack and bank are too full to hold it. - } - } + if (m.AddToBackpack(item)) + { + m.SendLocalizedMessage(1072223); // An item has been placed in your backpack. + m.SendLocalizedMessage( + 1062317); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. + } + else if (m.BankBox.TryDropItem(m, item, false)) + { + m.SendLocalizedMessage(1072224); // An item has been placed in your bank box. + m.SendLocalizedMessage( + 1062317); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. + } + else + { + // Item was placed at feet by m.AddToBackpack + m.SendLocalizedMessage(1072523); // You find an artifact, but your backpack and bank are too full to hold it. + } + } - public static bool CheckML( Mobile from, bool message = true) - { - if ( from?.NetState == null ) - return false; + public static bool CheckML(Mobile from, bool message = true) + { + if (from?.NetState == null) + return false; - if ( from.NetState.SupportsExpansion( Expansion.ML ) ) - return true; + if (from.NetState.SupportsExpansion(Expansion.ML)) + return true; - if ( message ) - from.SendLocalizedMessage( 1072791 ); // You must upgrade to Mondain's Legacy in order to use that item. + if (message) + from.SendLocalizedMessage(1072791); // You must upgrade to Mondain's Legacy in order to use that item. - return false; - } + return false; + } - public static bool IsMLRegion( Region region ) - { - return region.IsPartOf( "Twisted Weald" ) - || region.IsPartOf( "Sanctuary" ) - || region.IsPartOf( "The Prism of Light" ) - || region.IsPartOf( "The Citadel" ) - || region.IsPartOf( "Bedlam" ) - || region.IsPartOf( "Blighted Grove" ) - || region.IsPartOf( "The Painted Caves" ) - || region.IsPartOf( "The Palace of Paroxysmus" ) - || region.IsPartOf( "Labyrinth" ); - } - } -} + public static bool IsMLRegion(Region region) + { + return region.IsPartOf("Twisted Weald") + || region.IsPartOf("Sanctuary") + || region.IsPartOf("The Prism of Light") + || region.IsPartOf("The Citadel") + || region.IsPartOf("Bedlam") + || region.IsPartOf("Blighted Grove") + || region.IsPartOf("The Painted Caves") + || region.IsPartOf("The Palace of Paroxysmus") + || region.IsPartOf("Labyrinth"); + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/NameVerification.cs b/Scripts/Misc/NameVerification.cs index dd09f8c6b..5684626fb 100644 --- a/Scripts/Misc/NameVerification.cs +++ b/Scripts/Misc/NameVerification.cs @@ -2,200 +2,201 @@ using Server.Commands; namespace Server.Misc { - public class NameVerification - { - public static readonly char[] SpaceDashPeriodQuote = { - ' ', '-', '.', '\'' - }; + public class NameVerification + { + public static readonly char[] SpaceDashPeriodQuote = + { + ' ', '-', '.', '\'' + }; - public static readonly char[] Empty = new char[0]; + public static readonly char[] Empty = new char[0]; - public static void Initialize() - { - CommandSystem.Register( "ValidateName", AccessLevel.Administrator, ValidateName_OnCommand ); - } + public static string[] StartDisallowed{ get; } = + { + "seer", + "counselor", + "gm", + "admin", + "lady", + "lord" + }; - [Usage( "ValidateName" )] - [Description( "Checks the result of NameValidation on the specified name." )] - public static void ValidateName_OnCommand( CommandEventArgs e ) - { - if ( Validate( e.ArgString, 2, 16, true, false, true, 1, SpaceDashPeriodQuote ) ) - e.Mobile.SendMessage( 0x59, "That name is considered valid." ); - else - e.Mobile.SendMessage( 0x22, "That name is considered invalid." ); - } + public static string[] Disallowed{ get; } = + { + "jigaboo", + "chigaboo", + "wop", + "kyke", + "kike", + "tit", + "spic", + "prick", + "piss", + "lezbo", + "lesbo", + "felatio", + "dyke", + "dildo", + "chinc", + "chink", + "cunnilingus", + "cum", + "cocksucker", + "cock", + "clitoris", + "clit", + "ass", + "hitler", + "penis", + "nigga", + "nigger", + "klit", + "kunt", + "jiz", + "jism", + "jerkoff", + "jackoff", + "goddamn", + "fag", + "blowjob", + "bitch", + "asshole", + "dick", + "pussy", + "snatch", + "cunt", + "twat", + "shit", + "fuck", + "tailor", + "smith", + "scholar", + "rogue", + "novice", + "neophyte", + "merchant", + "medium", + "master", + "mage", + "lb", + "journeyman", + "grandmaster", + "fisherman", + "expert", + "chef", + "carpenter", + "british", + "blackthorne", + "blackthorn", + "beggar", + "archer", + "apprentice", + "adept", + "gamemaster", + "frozen", + "squelched", + "invulnerable", + "osi", + "origin" + }; - public static bool Validate( string name, int minLength, int maxLength, bool allowLetters, bool allowDigits, bool noExceptionsAtStart, int maxExceptions, char[] exceptions ) - { - return Validate( name, minLength, maxLength, allowLetters, allowDigits, noExceptionsAtStart, maxExceptions, exceptions, Disallowed, StartDisallowed ); - } + public static void Initialize() + { + CommandSystem.Register("ValidateName", AccessLevel.Administrator, ValidateName_OnCommand); + } - public static bool Validate( string name, int minLength, int maxLength, bool allowLetters, bool allowDigits, bool noExceptionsAtStart, int maxExceptions, char[] exceptions, string[] disallowed, string[] startDisallowed ) - { - if ( name == null || name.Length < minLength || name.Length > maxLength ) - return false; + [Usage("ValidateName")] + [Description("Checks the result of NameValidation on the specified name.")] + public static void ValidateName_OnCommand(CommandEventArgs e) + { + if (Validate(e.ArgString, 2, 16, true, false, true, 1, SpaceDashPeriodQuote)) + e.Mobile.SendMessage(0x59, "That name is considered valid."); + else + e.Mobile.SendMessage(0x22, "That name is considered invalid."); + } - int exceptCount = 0; + public static bool Validate(string name, int minLength, int maxLength, bool allowLetters, bool allowDigits, + bool noExceptionsAtStart, int maxExceptions, char[] exceptions) + { + return Validate(name, minLength, maxLength, allowLetters, allowDigits, noExceptionsAtStart, maxExceptions, + exceptions, Disallowed, StartDisallowed); + } - name = name.ToLower(); + public static bool Validate(string name, int minLength, int maxLength, bool allowLetters, bool allowDigits, + bool noExceptionsAtStart, int maxExceptions, char[] exceptions, string[] disallowed, string[] startDisallowed) + { + if (name == null || name.Length < minLength || name.Length > maxLength) + return false; - if ( !allowLetters || !allowDigits || (exceptions.Length > 0 && (noExceptionsAtStart || maxExceptions < int.MaxValue)) ) - { - for ( int i = 0; i < name.Length; ++i ) - { - char c = name[i]; + int exceptCount = 0; - if ( c >= 'a' && c <= 'z' ) - { - if ( !allowLetters ) - return false; + name = name.ToLower(); - exceptCount = 0; - } - else if ( c >= '0' && c <= '9' ) - { - if ( !allowDigits ) - return false; + if (!allowLetters || !allowDigits || + exceptions.Length > 0 && (noExceptionsAtStart || maxExceptions < int.MaxValue)) + for (int i = 0; i < name.Length; ++i) + { + char c = name[i]; - exceptCount = 0; - } - else - { - bool except = false; + if (c >= 'a' && c <= 'z') + { + if (!allowLetters) + return false; - for ( int j = 0; !except && j < exceptions.Length; ++j ) - if ( c == exceptions[j] ) - except = true; + exceptCount = 0; + } + else if (c >= '0' && c <= '9') + { + if (!allowDigits) + return false; - if ( !except || (i == 0 && noExceptionsAtStart) ) - return false; + exceptCount = 0; + } + else + { + bool except = false; - if ( exceptCount++ == maxExceptions ) - return false; - } - } - } + for (int j = 0; !except && j < exceptions.Length; ++j) + if (c == exceptions[j]) + except = true; - for ( int i = 0; i < disallowed.Length; ++i ) - { - int indexOf = name.IndexOf( disallowed[i] ); + if (!except || i == 0 && noExceptionsAtStart) + return false; - if ( indexOf == -1 ) - continue; + if (exceptCount++ == maxExceptions) + return false; + } + } - bool badPrefix = ( indexOf == 0 ); + for (int i = 0; i < disallowed.Length; ++i) + { + int indexOf = name.IndexOf(disallowed[i]); - for ( int j = 0; !badPrefix && j < exceptions.Length; ++j ) - badPrefix = ( name[indexOf - 1] == exceptions[j] ); + if (indexOf == -1) + continue; - if ( !badPrefix ) - continue; + bool badPrefix = indexOf == 0; - bool badSuffix = ( (indexOf + disallowed[i].Length) >= name.Length ); + for (int j = 0; !badPrefix && j < exceptions.Length; ++j) + badPrefix = name[indexOf - 1] == exceptions[j]; - for ( int j = 0; !badSuffix && j < exceptions.Length; ++j ) - badSuffix = ( name[indexOf + disallowed[i].Length] == exceptions[j] ); + if (!badPrefix) + continue; - if ( badSuffix ) - return false; - } + bool badSuffix = indexOf + disallowed[i].Length >= name.Length; - for ( int i = 0; i < startDisallowed.Length; ++i ) - { - if ( name.StartsWith( startDisallowed[i] ) ) - return false; - } + for (int j = 0; !badSuffix && j < exceptions.Length; ++j) + badSuffix = name[indexOf + disallowed[i].Length] == exceptions[j]; - return true; - } + if (badSuffix) + return false; + } - public static string[] StartDisallowed { get; } = - { - "seer", - "counselor", - "gm", - "admin", - "lady", - "lord" - }; + for (int i = 0; i < startDisallowed.Length; ++i) + if (name.StartsWith(startDisallowed[i])) + return false; - public static string[] Disallowed { get; } = - { - "jigaboo", - "chigaboo", - "wop", - "kyke", - "kike", - "tit", - "spic", - "prick", - "piss", - "lezbo", - "lesbo", - "felatio", - "dyke", - "dildo", - "chinc", - "chink", - "cunnilingus", - "cum", - "cocksucker", - "cock", - "clitoris", - "clit", - "ass", - "hitler", - "penis", - "nigga", - "nigger", - "klit", - "kunt", - "jiz", - "jism", - "jerkoff", - "jackoff", - "goddamn", - "fag", - "blowjob", - "bitch", - "asshole", - "dick", - "pussy", - "snatch", - "cunt", - "twat", - "shit", - "fuck", - "tailor", - "smith", - "scholar", - "rogue", - "novice", - "neophyte", - "merchant", - "medium", - "master", - "mage", - "lb", - "journeyman", - "grandmaster", - "fisherman", - "expert", - "chef", - "carpenter", - "british", - "blackthorne", - "blackthorn", - "beggar", - "archer", - "apprentice", - "adept", - "gamemaster", - "frozen", - "squelched", - "invulnerable", - "osi", - "origin" - }; - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Notoriety.cs b/Scripts/Misc/Notoriety.cs index f77d11201..634839762 100644 --- a/Scripts/Misc/Notoriety.cs +++ b/Scripts/Misc/Notoriety.cs @@ -1,463 +1,491 @@ using System; using System.Collections.Generic; using Server.Engines.ConPVP; -using Server.Items; -using Server.Guilds; -using Server.Multis; -using Server.Mobiles; using Server.Engines.PartySystem; using Server.Factions; +using Server.Guilds; +using Server.Items; +using Server.Mobiles; +using Server.Multis; +using Server.SkillHandlers; +using Server.Spells.Seventh; namespace Server.Misc { - public class NotorietyHandlers - { - public static void Initialize() - { - Notoriety.Hues[Notoriety.Innocent] = 0x59; - Notoriety.Hues[Notoriety.Ally] = 0x3F; - Notoriety.Hues[Notoriety.CanBeAttacked] = 0x3B2; - Notoriety.Hues[Notoriety.Criminal] = 0x3B2; - Notoriety.Hues[Notoriety.Enemy] = 0x90; - Notoriety.Hues[Notoriety.Murderer] = 0x22; - Notoriety.Hues[Notoriety.Invulnerable] = 0x35; - - Notoriety.Handler = MobileNotoriety; + public class NotorietyHandlers + { + public static void Initialize() + { + Notoriety.Hues[Notoriety.Innocent] = 0x59; + Notoriety.Hues[Notoriety.Ally] = 0x3F; + Notoriety.Hues[Notoriety.CanBeAttacked] = 0x3B2; + Notoriety.Hues[Notoriety.Criminal] = 0x3B2; + Notoriety.Hues[Notoriety.Enemy] = 0x90; + Notoriety.Hues[Notoriety.Murderer] = 0x22; + Notoriety.Hues[Notoriety.Invulnerable] = 0x35; + + Notoriety.Handler = MobileNotoriety; - Mobile.AllowBeneficialHandler = Mobile_AllowBeneficial; - Mobile.AllowHarmfulHandler = Mobile_AllowHarmful; - } + Mobile.AllowBeneficialHandler = Mobile_AllowBeneficial; + Mobile.AllowHarmfulHandler = Mobile_AllowHarmful; + } - private enum GuildStatus { None, Peaceful, Waring } + private static GuildStatus GetGuildStatus(Mobile m) + { + if (m.Guild == null) + return GuildStatus.None; + if (((Guild)m.Guild).Enemies.Count == 0 && m.Guild.Type == GuildType.Regular) + return GuildStatus.Peaceful; - private static GuildStatus GetGuildStatus( Mobile m ) - { - if ( m.Guild == null ) - return GuildStatus.None; - if ( ((Guild)m.Guild).Enemies.Count == 0 && m.Guild.Type == GuildType.Regular ) - return GuildStatus.Peaceful; + return GuildStatus.Waring; + } - return GuildStatus.Waring; - } + private static bool CheckBeneficialStatus(GuildStatus from, GuildStatus target) + { + if (from == GuildStatus.Waring || target == GuildStatus.Waring) + return false; - private static bool CheckBeneficialStatus( GuildStatus from, GuildStatus target ) - { - if ( from == GuildStatus.Waring || target == GuildStatus.Waring ) - return false; + return true; + } - return true; - } + /*private static bool CheckHarmfulStatus( GuildStatus from, GuildStatus target ) + { + if ( from == GuildStatus.Waring && target == GuildStatus.Waring ) + return true; - /*private static bool CheckHarmfulStatus( GuildStatus from, GuildStatus target ) - { - if ( from == GuildStatus.Waring && target == GuildStatus.Waring ) - return true; + return false; + }*/ - return false; - }*/ + public static bool Mobile_AllowBeneficial(Mobile from, Mobile target) + { + if (from == null || target == null || from.AccessLevel > AccessLevel.Player || + target.AccessLevel > AccessLevel.Player) + return true; - public static bool Mobile_AllowBeneficial( Mobile from, Mobile target ) - { - if ( from == null || target == null || from.AccessLevel > AccessLevel.Player || target.AccessLevel > AccessLevel.Player ) - return true; + #region Dueling - #region Dueling - PlayerMobile pmFrom = from as PlayerMobile; - PlayerMobile pmTarg = target as PlayerMobile; + PlayerMobile pmFrom = from as PlayerMobile; + PlayerMobile pmTarg = target as PlayerMobile; - if ( pmFrom == null && from is BaseCreature bcFrom ) - { - if ( bcFrom.Summoned ) - pmFrom = bcFrom.SummonMaster as PlayerMobile; - } + if (pmFrom == null && from is BaseCreature bcFrom) + if (bcFrom.Summoned) + pmFrom = bcFrom.SummonMaster as PlayerMobile; - if ( pmTarg == null && target is BaseCreature bcTarg ) - { - if ( bcTarg.Summoned ) - pmTarg = bcTarg.SummonMaster as PlayerMobile; - } + if (pmTarg == null && target is BaseCreature bcTarg) + if (bcTarg.Summoned) + pmTarg = bcTarg.SummonMaster as PlayerMobile; - if ( pmFrom != null && pmTarg != null ) - { - if ( pmFrom.DuelContext != pmTarg.DuelContext && ((pmFrom.DuelContext != null && pmFrom.DuelContext.Started) || (pmTarg.DuelContext != null && pmTarg.DuelContext.Started)) ) - return false; + if (pmFrom != null && pmTarg != null) + { + if (pmFrom.DuelContext != pmTarg.DuelContext && + (pmFrom.DuelContext != null && pmFrom.DuelContext.Started || + pmTarg.DuelContext != null && pmTarg.DuelContext.Started)) + return false; - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && ((pmFrom.DuelContext.StartedReadyCountdown && !pmFrom.DuelContext.Started) || pmFrom.DuelContext.Tied || pmFrom.DuelPlayer.Eliminated || pmTarg.DuelPlayer.Eliminated) ) - return false; + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && + (pmFrom.DuelContext.StartedReadyCountdown && !pmFrom.DuelContext.Started || pmFrom.DuelContext.Tied || + pmFrom.DuelPlayer.Eliminated || pmTarg.DuelPlayer.Eliminated)) + return false; - if ( pmFrom.DuelPlayer != null && !pmFrom.DuelPlayer.Eliminated && pmFrom.DuelContext != null && pmFrom.DuelContext.IsSuddenDeath ) - return false; + if (pmFrom.DuelPlayer != null && !pmFrom.DuelPlayer.Eliminated && pmFrom.DuelContext != null && + pmFrom.DuelContext.IsSuddenDeath) + return false; - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.m_Tournament != null && pmFrom.DuelContext.m_Tournament.IsNotoRestricted && pmFrom.DuelPlayer != null && pmTarg.DuelPlayer != null && pmFrom.DuelPlayer.Participant != pmTarg.DuelPlayer.Participant ) - return false; + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && + pmFrom.DuelContext.m_Tournament != null && pmFrom.DuelContext.m_Tournament.IsNotoRestricted && + pmFrom.DuelPlayer != null && pmTarg.DuelPlayer != null && + pmFrom.DuelPlayer.Participant != pmTarg.DuelPlayer.Participant) + return false; - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.Started ) - return true; - } + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.Started) + return true; + } - if ( (pmFrom?.DuelContext != null && pmFrom.DuelContext.Started) || (pmTarg?.DuelContext != null && pmTarg.DuelContext.Started) ) - return false; + if (pmFrom?.DuelContext != null && pmFrom.DuelContext.Started || + pmTarg?.DuelContext != null && pmTarg.DuelContext.Started) + return false; - if ( from.Region.GetRegion( typeof( SafeZone ) ) is SafeZone sz /*&& sz.IsDisabled()*/ ) - return false; + if (from.Region.GetRegion(typeof(SafeZone)) is SafeZone sz /*&& sz.IsDisabled()*/) + return false; - sz = target.Region.GetRegion( typeof( SafeZone ) ) as SafeZone; + sz = target.Region.GetRegion(typeof(SafeZone)) as SafeZone; - if ( sz != null /*&& sz.IsDisabled()*/ ) - return false; - #endregion + if (sz != null /*&& sz.IsDisabled()*/) + return false; - Map map = from.Map; + #endregion - #region Factions - Faction targetFaction = Faction.Find( target, true ); + Map map = from.Map; - if ( (!Core.ML || map == Faction.Facet) && targetFaction != null ) - { - if ( Faction.Find( from, true ) != targetFaction ) - return false; - } - #endregion + #region Factions + Faction targetFaction = Faction.Find(target, true); - if ( map != null && (map.Rules & MapRules.BeneficialRestrictions) == 0 ) - return true; // In felucca, anything goes + if ((!Core.ML || map == Faction.Facet) && targetFaction != null) + if (Faction.Find(from, true) != targetFaction) + return false; - if ( !from.Player ) - return true; // NPCs have no restrictions + #endregion - if ( target is BaseCreature creature && !creature.Controlled ) - return false; // Players cannot heal uncontrolled mobiles - if ( pmFrom?.Young == true || pmTarg?.Young == true ) - return false; // Young players cannot perform beneficial actions towards older players + if (map != null && (map.Rules & MapRules.BeneficialRestrictions) == 0) + return true; // In felucca, anything goes - if ( from.Guild is Guild fromGuild && target.Guild is Guild targetGuild && (targetGuild == fromGuild || fromGuild.IsAlly( targetGuild )) ) - return true; // Guild members can be beneficial + if (!from.Player) + return true; // NPCs have no restrictions - return CheckBeneficialStatus( GetGuildStatus( from ), GetGuildStatus( target ) ); - } + if (target is BaseCreature creature && !creature.Controlled) + return false; // Players cannot heal uncontrolled mobiles - public static bool Mobile_AllowHarmful( Mobile from, Mobile target ) - { - if ( from == null || target == null || from.AccessLevel > AccessLevel.Player || target.AccessLevel > AccessLevel.Player ) - return true; + if (pmFrom?.Young == true || pmTarg?.Young == true) + return false; // Young players cannot perform beneficial actions towards older players - #region Dueling - PlayerMobile pmFrom = from as PlayerMobile; - PlayerMobile pmTarg = target as PlayerMobile; - BaseCreature bcTarg = target as BaseCreature; + if (from.Guild is Guild fromGuild && target.Guild is Guild targetGuild && + (targetGuild == fromGuild || fromGuild.IsAlly(targetGuild))) + return true; // Guild members can be beneficial - if ( pmFrom == null && from is BaseCreature bcFrom && bcFrom.Summoned ) - pmFrom = bcFrom.SummonMaster as PlayerMobile; + return CheckBeneficialStatus(GetGuildStatus(from), GetGuildStatus(target)); + } - if ( pmTarg == null && bcTarg?.Summoned == true ) - pmTarg = bcTarg.SummonMaster as PlayerMobile; + public static bool Mobile_AllowHarmful(Mobile from, Mobile target) + { + if (from == null || target == null || from.AccessLevel > AccessLevel.Player || + target.AccessLevel > AccessLevel.Player) + return true; - if ( pmFrom != null && pmTarg != null ) - { - if ( pmFrom.DuelContext != pmTarg.DuelContext && ((pmFrom.DuelContext != null && pmFrom.DuelContext.Started) || (pmTarg.DuelContext != null && pmTarg.DuelContext.Started)) ) - return false; + #region Dueling - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && ((pmFrom.DuelContext.StartedReadyCountdown && !pmFrom.DuelContext.Started) || pmFrom.DuelContext.Tied || pmFrom.DuelPlayer.Eliminated || pmTarg.DuelPlayer.Eliminated) ) - return false; + PlayerMobile pmFrom = from as PlayerMobile; + PlayerMobile pmTarg = target as PlayerMobile; + BaseCreature bcTarg = target as BaseCreature; - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.m_Tournament != null && pmFrom.DuelContext.m_Tournament.IsNotoRestricted && pmFrom.DuelPlayer != null && pmTarg.DuelPlayer != null && pmFrom.DuelPlayer.Participant == pmTarg.DuelPlayer.Participant ) - return false; + if (pmFrom == null && from is BaseCreature bcFrom && bcFrom.Summoned) + pmFrom = bcFrom.SummonMaster as PlayerMobile; - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.Started ) - return true; - } + if (pmTarg == null && bcTarg?.Summoned == true) + pmTarg = bcTarg.SummonMaster as PlayerMobile; - if ( (pmFrom?.DuelContext != null && pmFrom.DuelContext.Started) || (pmTarg?.DuelContext != null && pmTarg.DuelContext.Started) ) - return false; + if (pmFrom != null && pmTarg != null) + { + if (pmFrom.DuelContext != pmTarg.DuelContext && + (pmFrom.DuelContext != null && pmFrom.DuelContext.Started || + pmTarg.DuelContext != null && pmTarg.DuelContext.Started)) + return false; - if ( from.Region.GetRegion( typeof( SafeZone ) ) is SafeZone sz /*&& sz.IsDisabled()*/ ) - return false; + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && + (pmFrom.DuelContext.StartedReadyCountdown && !pmFrom.DuelContext.Started || pmFrom.DuelContext.Tied || + pmFrom.DuelPlayer.Eliminated || pmTarg.DuelPlayer.Eliminated)) + return false; - sz = target.Region.GetRegion( typeof( SafeZone ) ) as SafeZone; + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && + pmFrom.DuelContext.m_Tournament != null && pmFrom.DuelContext.m_Tournament.IsNotoRestricted && + pmFrom.DuelPlayer != null && pmTarg.DuelPlayer != null && + pmFrom.DuelPlayer.Participant == pmTarg.DuelPlayer.Participant) + return false; - if ( sz != null /*&& sz.IsDisabled()*/ ) - return false; - #endregion + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.Started) + return true; + } - Map map = from.Map; + if (pmFrom?.DuelContext != null && pmFrom.DuelContext.Started || + pmTarg?.DuelContext != null && pmTarg.DuelContext.Started) + return false; - if ( map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0 ) - return true; // In felucca, anything goes + if (from.Region.GetRegion(typeof(SafeZone)) is SafeZone sz /*&& sz.IsDisabled()*/) + return false; - if ( !from.Player && !(from is BaseCreature bc && bc.GetMaster() != null && bc.GetMaster().AccessLevel == AccessLevel.Player ) ) - { - if ( !CheckAggressor( from.Aggressors, target ) && !CheckAggressed( from.Aggressed, target ) && pmTarg?.CheckYoungProtection( from ) == true ) - return false; + sz = target.Region.GetRegion(typeof(SafeZone)) as SafeZone; - return true; // Uncontrolled NPCs are only restricted by the young system - } + if (sz != null /*&& sz.IsDisabled()*/) + return false; - Guild fromGuild = GetGuildFor( from.Guild as Guild, from ); - Guild targetGuild = GetGuildFor( target.Guild as Guild, target ); + #endregion - if ( fromGuild != null && targetGuild != null && (fromGuild == targetGuild || fromGuild.IsAlly( targetGuild ) || fromGuild.IsEnemy( targetGuild )) ) - return true; // Guild allies or enemies can be harmful + Map map = from.Map; - if ( bcTarg?.Controlled == true || bcTarg?.Summoned == true && bcTarg?.SummonMaster != from ) - return false; // Cannot harm other controlled mobiles + if (map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0) + return true; // In felucca, anything goes - if ( target.Player ) - return false; // Cannot harm other players + if (!from.Player && !(from is BaseCreature bc && bc.GetMaster() != null && + bc.GetMaster().AccessLevel == AccessLevel.Player)) + { + if (!CheckAggressor(from.Aggressors, target) && !CheckAggressed(from.Aggressed, target) && + pmTarg?.CheckYoungProtection(from) == true) + return false; - if ( bcTarg?.InitialInnocent != true ) - { - if ( Notoriety.Compute( from, target ) == Notoriety.Innocent ) - return false; // Cannot harm innocent mobiles - } + return true; // Uncontrolled NPCs are only restricted by the young system + } - return true; - } + Guild fromGuild = GetGuildFor(from.Guild as Guild, from); + Guild targetGuild = GetGuildFor(target.Guild as Guild, target); - public static Guild GetGuildFor( Guild def, Mobile m ) - { - Guild g = def; + if (fromGuild != null && targetGuild != null && + (fromGuild == targetGuild || fromGuild.IsAlly(targetGuild) || fromGuild.IsEnemy(targetGuild))) + return true; // Guild allies or enemies can be harmful - if ( m is BaseCreature c && c.Controlled && c.ControlMaster != null ) - { - c.DisplayGuildTitle = false; + if (bcTarg?.Controlled == true || bcTarg?.Summoned == true && bcTarg?.SummonMaster != from) + return false; // Cannot harm other controlled mobiles - if ( c.Map != Map.Internal && (Core.AOS || Guild.NewGuildSystem || c.ControlOrder == OrderType.Attack || c.ControlOrder == OrderType.Guard) ) - g = (Guild)(c.Guild = c.ControlMaster.Guild); - else if ( c.Map == Map.Internal || c.ControlMaster.Guild == null ) - g = (Guild)(c.Guild = null); - } + if (target.Player) + return false; // Cannot harm other players - return g; - } + if (bcTarg?.InitialInnocent != true) + if (Notoriety.Compute(from, target) == Notoriety.Innocent) + return false; // Cannot harm innocent mobiles - public static int CorpseNotoriety( Mobile source, Corpse target ) - { - if ( target.AccessLevel > AccessLevel.Player ) - return Notoriety.CanBeAttacked; + return true; + } - Body body = target.Amount; + public static Guild GetGuildFor(Guild def, Mobile m) + { + Guild g = def; - Guild sourceGuild = GetGuildFor( source.Guild as Guild, source ); - Guild targetGuild = GetGuildFor( target.Guild, target.Owner ); + if (m is BaseCreature c && c.Controlled && c.ControlMaster != null) + { + c.DisplayGuildTitle = false; - Faction srcFaction = Faction.Find( source, true, true ); - Faction trgFaction = Faction.Find( target.Owner, true, true ); - List list = target.Aggressors; + if (c.Map != Map.Internal && (Core.AOS || Guild.NewGuildSystem || c.ControlOrder == OrderType.Attack || + c.ControlOrder == OrderType.Guard)) + g = (Guild)(c.Guild = c.ControlMaster.Guild); + else if (c.Map == Map.Internal || c.ControlMaster.Guild == null) + g = (Guild)(c.Guild = null); + } - if ( sourceGuild != null && targetGuild != null ) - { - if ( sourceGuild == targetGuild || sourceGuild.IsAlly( targetGuild ) ) - return Notoriety.Ally; - if ( sourceGuild.IsEnemy( targetGuild ) ) - return Notoriety.Enemy; - } + return g; + } - if ( target.Owner is BaseCreature creature ) - { - if ( srcFaction != null && trgFaction != null && srcFaction != trgFaction && source.Map == Faction.Facet ) - return Notoriety.Enemy; + public static int CorpseNotoriety(Mobile source, Corpse target) + { + if (target.AccessLevel > AccessLevel.Player) + return Notoriety.CanBeAttacked; - if ( CheckHouseFlag( source, creature, target.Location, target.Map ) ) - return Notoriety.CanBeAttacked; + Body body = target.Amount; - int actual = Notoriety.CanBeAttacked; + Guild sourceGuild = GetGuildFor(source.Guild as Guild, source); + Guild targetGuild = GetGuildFor(target.Guild, target.Owner); - if ( target.Kills >= 5 || body.IsMonster && IsSummoned( creature ) || creature.AlwaysMurderer || creature.IsAnimatedDead ) - actual = Notoriety.Murderer; + Faction srcFaction = Faction.Find(source, true, true); + Faction trgFaction = Faction.Find(target.Owner, true, true); + List list = target.Aggressors; - if ( DateTime.UtcNow >= target.TimeOfDeath + Corpse.MonsterLootRightSacrifice ) - return actual; + if (sourceGuild != null && targetGuild != null) + { + if (sourceGuild == targetGuild || sourceGuild.IsAlly(targetGuild)) + return Notoriety.Ally; + if (sourceGuild.IsEnemy(targetGuild)) + return Notoriety.Enemy; + } - Party sourceParty = Party.Get( source ); + if (target.Owner is BaseCreature creature) + { + if (srcFaction != null && trgFaction != null && srcFaction != trgFaction && source.Map == Faction.Facet) + return Notoriety.Enemy; - for( int i = 0; i < list.Count; ++i ) - { - if ( list[i] == source || sourceParty != null && Party.Get( list[i] ) == sourceParty ) - return actual; - } + if (CheckHouseFlag(source, creature, target.Location, target.Map)) + return Notoriety.CanBeAttacked; - return Notoriety.Innocent; - } + int actual = Notoriety.CanBeAttacked; - if ( target.Kills >= 5 || body.IsMonster ) - return Notoriety.Murderer; + if (target.Kills >= 5 || body.IsMonster && IsSummoned(creature) || creature.AlwaysMurderer || + creature.IsAnimatedDead) + actual = Notoriety.Murderer; - if (target.Criminal && target.Map != null && (target.Map.Rules & MapRules.HarmfulRestrictions) == 0) - return Notoriety.Criminal; + if (DateTime.UtcNow >= target.TimeOfDeath + Corpse.MonsterLootRightSacrifice) + return actual; - if ( srcFaction != null && trgFaction != null && srcFaction != trgFaction && source.Map == Faction.Facet ) - { - for ( int i = 0; i < list.Count; ++i ) - { - if ( list[i] == source || list[i] is BaseFactionGuard ) - return Notoriety.Enemy; - } - } + Party sourceParty = Party.Get(source); - if ( CheckHouseFlag( source, target.Owner, target.Location, target.Map ) ) - return Notoriety.CanBeAttacked; + for (int i = 0; i < list.Count; ++i) + if (list[i] == source || sourceParty != null && Party.Get(list[i]) == sourceParty) + return actual; - if ( !(target.Owner is PlayerMobile) ) - return Notoriety.CanBeAttacked; + return Notoriety.Innocent; + } - for ( int i = 0; i < list.Count; ++i ) - { - if ( list[i] == source ) - return Notoriety.CanBeAttacked; - } + if (target.Kills >= 5 || body.IsMonster) + return Notoriety.Murderer; - return Notoriety.Innocent; - } + if (target.Criminal && target.Map != null && (target.Map.Rules & MapRules.HarmfulRestrictions) == 0) + return Notoriety.Criminal; - /* Must be thread-safe */ - public static int MobileNotoriety( Mobile source, Mobile target ) - { - BaseCreature bcTarg = target as BaseCreature; + if (srcFaction != null && trgFaction != null && srcFaction != trgFaction && source.Map == Faction.Facet) + for (int i = 0; i < list.Count; ++i) + if (list[i] == source || list[i] is BaseFactionGuard) + return Notoriety.Enemy; - if ( Core.AOS && ( target.Blessed || bcTarg?.IsInvulnerable == true || target is PlayerVendor || target is TownCrier ) ) - return Notoriety.Invulnerable; + if (CheckHouseFlag(source, target.Owner, target.Location, target.Map)) + return Notoriety.CanBeAttacked; - PlayerMobile pmFrom = source as PlayerMobile; - PlayerMobile pmTarg = target as PlayerMobile; + if (!(target.Owner is PlayerMobile)) + return Notoriety.CanBeAttacked; - #region Dueling - if ( pmFrom != null && pmTarg != null ) - { - if ( pmFrom.DuelContext != null && pmFrom.DuelContext.StartedBeginCountdown && !pmFrom.DuelContext.Finished && pmFrom.DuelContext == pmTarg.DuelContext ) - return pmFrom.DuelContext.IsAlly( pmFrom, pmTarg ) ? Notoriety.Ally : Notoriety.Enemy; - } - #endregion + for (int i = 0; i < list.Count; ++i) + if (list[i] == source) + return Notoriety.CanBeAttacked; - if ( target.AccessLevel > AccessLevel.Player ) - return Notoriety.CanBeAttacked; + return Notoriety.Innocent; + } - if ( source.Player && !target.Player && pmFrom != null && bcTarg != null ) - { - Mobile master = bcTarg.GetMaster(); + /* Must be thread-safe */ + public static int MobileNotoriety(Mobile source, Mobile target) + { + BaseCreature bcTarg = target as BaseCreature; - if ( master != null && master.AccessLevel > AccessLevel.Player ) - return Notoriety.CanBeAttacked; + if (Core.AOS && (target.Blessed || bcTarg?.IsInvulnerable == true || target is PlayerVendor || + target is TownCrier)) + return Notoriety.Invulnerable; - master = bcTarg.ControlMaster; + PlayerMobile pmFrom = source as PlayerMobile; + PlayerMobile pmTarg = target as PlayerMobile; - if ( Core.ML && master != null ) - { - if ( ( source == master && CheckAggressor( bcTarg.Aggressors, source ) ) || ( CheckAggressor( source.Aggressors, bcTarg ) ) ) - return Notoriety.CanBeAttacked; + #region Dueling - return MobileNotoriety( source, master ); - } + if (pmFrom != null && pmTarg != null) + if (pmFrom.DuelContext != null && pmFrom.DuelContext.StartedBeginCountdown && !pmFrom.DuelContext.Finished && + pmFrom.DuelContext == pmTarg.DuelContext) + return pmFrom.DuelContext.IsAlly(pmFrom, pmTarg) ? Notoriety.Ally : Notoriety.Enemy; - if ( !bcTarg.Summoned && !bcTarg.Controlled && pmFrom.EnemyOfOneType == bcTarg.GetType() ) - return Notoriety.Enemy; - } + #endregion - if ( target.Kills >= 5 || target.Body.IsMonster && IsSummoned( bcTarg ) && !( target is BaseFamiliar ) && !( target is ArcaneFey ) && !( target is Golem ) || bcTarg?.AlwaysMurderer == true || bcTarg?.IsAnimatedDead == true ) - return Notoriety.Murderer; + if (target.AccessLevel > AccessLevel.Player) + return Notoriety.CanBeAttacked; - if ( target.Criminal ) - return Notoriety.Criminal; + if (source.Player && !target.Player && pmFrom != null && bcTarg != null) + { + Mobile master = bcTarg.GetMaster(); - Guild sourceGuild = GetGuildFor( source.Guild as Guild, source ); - Guild targetGuild = GetGuildFor( target.Guild as Guild, target ); + if (master != null && master.AccessLevel > AccessLevel.Player) + return Notoriety.CanBeAttacked; - if ( sourceGuild != null && targetGuild != null ) - { - if ( sourceGuild == targetGuild || sourceGuild.IsAlly( targetGuild ) ) - return Notoriety.Ally; - if ( sourceGuild.IsEnemy( targetGuild ) ) - return Notoriety.Enemy; - } + master = bcTarg.ControlMaster; - Faction srcFaction = Faction.Find( source, true, true ); - Faction trgFaction = Faction.Find( target, true, true ); + if (Core.ML && master != null) + { + if (source == master && CheckAggressor(bcTarg.Aggressors, source) || + CheckAggressor(source.Aggressors, bcTarg)) + return Notoriety.CanBeAttacked; - if ( srcFaction != null && trgFaction != null && srcFaction != trgFaction && source.Map == Faction.Facet ) - return Notoriety.Enemy; + return MobileNotoriety(source, master); + } - if ( SkillHandlers.Stealing.ClassicMode && pmTarg?.PermaFlags.Contains( source ) == true ) - return Notoriety.CanBeAttacked; + if (!bcTarg.Summoned && !bcTarg.Controlled && pmFrom.EnemyOfOneType == bcTarg.GetType()) + return Notoriety.Enemy; + } - if ( bcTarg?.AlwaysAttackable == true ) - return Notoriety.CanBeAttacked; + if (target.Kills >= 5 || + target.Body.IsMonster && IsSummoned(bcTarg) && !(target is BaseFamiliar) && !(target is ArcaneFey) && + !(target is Golem) || bcTarg?.AlwaysMurderer == true || bcTarg?.IsAnimatedDead == true) + return Notoriety.Murderer; - if ( CheckHouseFlag( source, target, target.Location, target.Map ) ) - return Notoriety.CanBeAttacked; + if (target.Criminal) + return Notoriety.Criminal; - if ( bcTarg?.InitialInnocent != true ) - { - if ( !target.Body.IsHuman && !target.Body.IsGhost && !IsPet( bcTarg ) && pmTarg == null || !Core.ML && !target.CanBeginAction( typeof( Spells.Seventh.PolymorphSpell ) ) ) - return Notoriety.CanBeAttacked; - } + Guild sourceGuild = GetGuildFor(source.Guild as Guild, source); + Guild targetGuild = GetGuildFor(target.Guild as Guild, target); - if ( CheckAggressor( source.Aggressors, target ) ) - return Notoriety.CanBeAttacked; + if (sourceGuild != null && targetGuild != null) + { + if (sourceGuild == targetGuild || sourceGuild.IsAlly(targetGuild)) + return Notoriety.Ally; + if (sourceGuild.IsEnemy(targetGuild)) + return Notoriety.Enemy; + } - if ( CheckAggressed( source.Aggressed, target ) ) - return Notoriety.CanBeAttacked; + Faction srcFaction = Faction.Find(source, true, true); + Faction trgFaction = Faction.Find(target, true, true); - if ( bcTarg != null && bcTarg.Controlled && bcTarg.ControlOrder == OrderType.Guard && bcTarg.ControlTarget == source ) - return Notoriety.CanBeAttacked; + if (srcFaction != null && trgFaction != null && srcFaction != trgFaction && source.Map == Faction.Facet) + return Notoriety.Enemy; - if ( source is BaseCreature bc ) - { - Mobile master = bc.GetMaster(); + if (Stealing.ClassicMode && pmTarg?.PermaFlags.Contains(source) == true) + return Notoriety.CanBeAttacked; - if ( master != null && CheckAggressor( master.Aggressors, target ) || MobileNotoriety( master, target ) == Notoriety.CanBeAttacked || bcTarg != null ) - return Notoriety.CanBeAttacked; - } + if (bcTarg?.AlwaysAttackable == true) + return Notoriety.CanBeAttacked; - return Notoriety.Innocent; - } + if (CheckHouseFlag(source, target, target.Location, target.Map)) + return Notoriety.CanBeAttacked; - public static bool CheckHouseFlag( Mobile from, Mobile m, Point3D p, Map map ) - { - BaseHouse house = BaseHouse.FindHouseAt( p, map, 16 ); + if (bcTarg?.InitialInnocent != true) + if (!target.Body.IsHuman && !target.Body.IsGhost && !IsPet(bcTarg) && pmTarg == null || + !Core.ML && !target.CanBeginAction(typeof(PolymorphSpell))) + return Notoriety.CanBeAttacked; - if ( house == null || house.Public || !house.IsFriend( from ) ) - return false; + if (CheckAggressor(source.Aggressors, target)) + return Notoriety.CanBeAttacked; - if ( m != null && house.IsFriend( m ) ) - return false; + if (CheckAggressed(source.Aggressed, target)) + return Notoriety.CanBeAttacked; - if ( m is BaseCreature c && !c.Deleted && c.Controlled && c.ControlMaster != null ) - return !house.IsFriend( c.ControlMaster ); + if (bcTarg != null && bcTarg.Controlled && bcTarg.ControlOrder == OrderType.Guard && + bcTarg.ControlTarget == source) + return Notoriety.CanBeAttacked; - return true; - } + if (source is BaseCreature bc) + { + Mobile master = bc.GetMaster(); - public static bool IsPet( BaseCreature c ) - { - return (c != null && c.Controlled); - } + if (master != null && CheckAggressor(master.Aggressors, target) || + MobileNotoriety(master, target) == Notoriety.CanBeAttacked || bcTarg != null) + return Notoriety.CanBeAttacked; + } - public static bool IsSummoned( BaseCreature c ) - { - return (c != null && /*c.Controlled &&*/ c.Summoned); - } + return Notoriety.Innocent; + } - public static bool CheckAggressor( List list, Mobile target ) - { - for( int i = 0; i < list.Count; ++i ) - if ( list[i].Attacker == target ) - return true; + public static bool CheckHouseFlag(Mobile from, Mobile m, Point3D p, Map map) + { + BaseHouse house = BaseHouse.FindHouseAt(p, map, 16); - return false; - } + if (house == null || house.Public || !house.IsFriend(from)) + return false; - public static bool CheckAggressed( List list, Mobile target ) - { - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + if (m != null && house.IsFriend(m)) + return false; - if ( !info.CriminalAggression && info.Defender == target ) - return true; - } + if (m is BaseCreature c && !c.Deleted && c.Controlled && c.ControlMaster != null) + return !house.IsFriend(c.ControlMaster); - return false; - } - } -} + return true; + } + + public static bool IsPet(BaseCreature c) + { + return c != null && c.Controlled; + } + + public static bool IsSummoned(BaseCreature c) + { + return c != null && /*c.Controlled &&*/ c.Summoned; + } + + public static bool CheckAggressor(List list, Mobile target) + { + for (int i = 0; i < list.Count; ++i) + if (list[i].Attacker == target) + return true; + + return false; + } + + public static bool CheckAggressed(List list, Mobile target) + { + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; + + if (!info.CriminalAggression && info.Defender == target) + return true; + } + + return false; + } + + private enum GuildStatus + { + None, + Peaceful, + Waring + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Paperdoll.cs b/Scripts/Misc/Paperdoll.cs index 414bf497e..4ba425c74 100644 --- a/Scripts/Misc/Paperdoll.cs +++ b/Scripts/Misc/Paperdoll.cs @@ -3,30 +3,31 @@ using Server.Network; namespace Server.Misc { - public class Paperdoll - { - public static void Initialize() - { - EventSink.PaperdollRequest += EventSink_PaperdollRequest; - } + public class Paperdoll + { + public static void Initialize() + { + EventSink.PaperdollRequest += EventSink_PaperdollRequest; + } - public static void EventSink_PaperdollRequest( PaperdollRequestEventArgs e ) - { - Mobile beholder = e.Beholder; - Mobile beheld = e.Beheld; + public static void EventSink_PaperdollRequest(PaperdollRequestEventArgs e) + { + Mobile beholder = e.Beholder; + Mobile beheld = e.Beheld; - beholder.Send( new DisplayPaperdoll( beheld, Titles.ComputeTitle( beholder, beheld ), beheld.AllowEquipFrom( beholder ) ) ); + beholder.Send(new DisplayPaperdoll(beheld, Titles.ComputeTitle(beholder, beheld), + beheld.AllowEquipFrom(beholder))); - if ( ObjectPropertyList.Enabled ) - { - List items = beheld.Items; + if (ObjectPropertyList.Enabled) + { + List items = beheld.Items; - for ( int i = 0; i < items.Count; ++i ) - beholder.Send( items[i].OPLPacket ); + for (int i = 0; i < items.Count; ++i) + beholder.Send(items[i].OPLPacket); - // NOTE: OSI sends MobileUpdate when opening your own paperdoll. - // It has a very bad rubber-banding affect. What positive affects does it have? - } - } - } + // NOTE: OSI sends MobileUpdate when opening your own paperdoll. + // It has a very bad rubber-banding affect. What positive affects does it have? + } + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Poison.cs b/Scripts/Misc/Poison.cs index fb5d980fb..7dd39920e 100644 --- a/Scripts/Misc/Poison.cs +++ b/Scripts/Misc/Poison.cs @@ -1,151 +1,153 @@ using System; using Server.Items; -using Server.Network; using Server.Mobiles; +using Server.Network; using Server.Spells; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; namespace Server { - public class PoisonImpl : Poison - { - [CallPriority( 10 )] - public static void Configure() - { - if ( Core.AOS ) - { - Register( new PoisonImpl( "Lesser", 0, 4, 16, 7.5, 3.0, 2.25, 10, 4 ) ); - Register( new PoisonImpl( "Regular", 1, 8, 18, 10.0, 3.0, 3.25, 10, 3 ) ); - Register( new PoisonImpl( "Greater", 2, 12, 20, 15.0, 3.0, 4.25, 10, 2 ) ); - Register( new PoisonImpl( "Deadly", 3, 16, 30, 30.0, 3.0, 5.25, 15, 2 ) ); - Register( new PoisonImpl( "Lethal", 4, 20, 50, 35.0, 3.0, 5.25, 20, 2 ) ); - } - else - { - Register( new PoisonImpl( "Lesser", 0, 4, 26, 2.500, 3.5, 3.0, 10, 2 ) ); - Register( new PoisonImpl( "Regular", 1, 5, 26, 3.125, 3.5, 3.0, 10, 2 ) ); - Register( new PoisonImpl( "Greater", 2, 6, 26, 6.250, 3.5, 3.0, 10, 2 ) ); - Register( new PoisonImpl( "Deadly", 3, 7, 26, 12.500, 3.5, 4.0, 10, 2 ) ); - Register( new PoisonImpl( "Lethal", 4, 9, 26, 25.000, 3.5, 5.0, 10, 2 ) ); - } - } + public class PoisonImpl : Poison + { + private int m_Count, m_MessageInterval; - public static Poison IncreaseLevel( Poison oldPoison ) - { - Poison newPoison = ( oldPoison == null ? null : GetPoison( oldPoison.Level + 1 ) ); + // Timers + private TimeSpan m_Delay; + private TimeSpan m_Interval; - return newPoison ?? oldPoison; - } + // Info - // Info + // Damage + private int m_Minimum, m_Maximum; + private double m_Scalar; - // Damage - private int m_Minimum, m_Maximum; - private double m_Scalar; + public PoisonImpl(string name, int level, int min, int max, double percent, double delay, double interval, int count, + int messageInterval) + { + Name = name; + Level = level; + m_Minimum = min; + m_Maximum = max; + m_Scalar = percent * 0.01; + m_Delay = TimeSpan.FromSeconds(delay); + m_Interval = TimeSpan.FromSeconds(interval); + m_Count = count; + m_MessageInterval = messageInterval; + } - // Timers - private TimeSpan m_Delay; - private TimeSpan m_Interval; - private int m_Count, m_MessageInterval; + public override string Name{ get; } - public PoisonImpl( string name, int level, int min, int max, double percent, double delay, double interval, int count, int messageInterval ) - { - Name = name; - Level = level; - m_Minimum = min; - m_Maximum = max; - m_Scalar = percent * 0.01; - m_Delay = TimeSpan.FromSeconds( delay ); - m_Interval = TimeSpan.FromSeconds( interval ); - m_Count = count; - m_MessageInterval = messageInterval; - } + public override int Level{ get; } - public override string Name { get; } + [CallPriority(10)] + public static void Configure() + { + if (Core.AOS) + { + Register(new PoisonImpl("Lesser", 0, 4, 16, 7.5, 3.0, 2.25, 10, 4)); + Register(new PoisonImpl("Regular", 1, 8, 18, 10.0, 3.0, 3.25, 10, 3)); + Register(new PoisonImpl("Greater", 2, 12, 20, 15.0, 3.0, 4.25, 10, 2)); + Register(new PoisonImpl("Deadly", 3, 16, 30, 30.0, 3.0, 5.25, 15, 2)); + Register(new PoisonImpl("Lethal", 4, 20, 50, 35.0, 3.0, 5.25, 20, 2)); + } + else + { + Register(new PoisonImpl("Lesser", 0, 4, 26, 2.500, 3.5, 3.0, 10, 2)); + Register(new PoisonImpl("Regular", 1, 5, 26, 3.125, 3.5, 3.0, 10, 2)); + Register(new PoisonImpl("Greater", 2, 6, 26, 6.250, 3.5, 3.0, 10, 2)); + Register(new PoisonImpl("Deadly", 3, 7, 26, 12.500, 3.5, 4.0, 10, 2)); + Register(new PoisonImpl("Lethal", 4, 9, 26, 25.000, 3.5, 5.0, 10, 2)); + } + } - public override int Level { get; } + public static Poison IncreaseLevel(Poison oldPoison) + { + Poison newPoison = oldPoison == null ? null : GetPoison(oldPoison.Level + 1); - public class PoisonTimer : Timer - { - private PoisonImpl m_Poison; - private Mobile m_Mobile; - private int m_LastDamage; - private int m_Index; + return newPoison ?? oldPoison; + } - public Mobile From { get; set; } + public override Timer ConstructTimer(Mobile m) + { + return new PoisonTimer(m, this); + } - public PoisonTimer( Mobile m, PoisonImpl p ) : base( p.m_Delay, p.m_Interval ) - { - From = m; - m_Mobile = m; - m_Poison = p; - } + public class PoisonTimer : Timer + { + private int m_Index; + private int m_LastDamage; + private Mobile m_Mobile; + private PoisonImpl m_Poison; - protected override void OnTick() - { - if ( (Core.AOS && m_Poison.Level < 4 && TransformationSpellHelper.UnderTransformation( m_Mobile, typeof( VampiricEmbraceSpell ) )) || - (m_Poison.Level < 3 && OrangePetals.UnderEffect( m_Mobile )) || - AnimalForm.UnderTransformation( m_Mobile, typeof( Unicorn ) ) ) - { - if ( m_Mobile.CurePoison( m_Mobile ) ) - { - m_Mobile.LocalOverheadMessage( MessageType.Emote, 0x3F, true, - "* You feel yourself resisting the effects of the poison *" ); + public PoisonTimer(Mobile m, PoisonImpl p) : base(p.m_Delay, p.m_Interval) + { + From = m; + m_Mobile = m; + m_Poison = p; + } - m_Mobile.NonlocalOverheadMessage( MessageType.Emote, 0x3F, true, - $"* {m_Mobile.Name} seems resistant to the poison *"); + public Mobile From{ get; set; } - Stop(); - return; - } - } + protected override void OnTick() + { + if (Core.AOS && m_Poison.Level < 4 && + TransformationSpellHelper.UnderTransformation(m_Mobile, typeof(VampiricEmbraceSpell)) || + m_Poison.Level < 3 && OrangePetals.UnderEffect(m_Mobile) || + AnimalForm.UnderTransformation(m_Mobile, typeof(Unicorn))) + if (m_Mobile.CurePoison(m_Mobile)) + { + m_Mobile.LocalOverheadMessage(MessageType.Emote, 0x3F, true, + "* You feel yourself resisting the effects of the poison *"); - if ( m_Index++ == m_Poison.m_Count ) - { - m_Mobile.SendLocalizedMessage( 502136 ); // The poison seems to have worn off. - m_Mobile.Poison = null; + m_Mobile.NonlocalOverheadMessage(MessageType.Emote, 0x3F, true, + $"* {m_Mobile.Name} seems resistant to the poison *"); - Stop(); - return; - } + Stop(); + return; + } - int damage; + if (m_Index++ == m_Poison.m_Count) + { + m_Mobile.SendLocalizedMessage(502136); // The poison seems to have worn off. + m_Mobile.Poison = null; - if ( !Core.AOS && m_LastDamage != 0 && Utility.RandomBool() ) - { - damage = m_LastDamage; - } - else - { - damage = 1 + (int)(m_Mobile.Hits * m_Poison.m_Scalar); + Stop(); + return; + } - if ( damage < m_Poison.m_Minimum ) - damage = m_Poison.m_Minimum; - else if ( damage > m_Poison.m_Maximum ) - damage = m_Poison.m_Maximum; + int damage; - m_LastDamage = damage; - } + if (!Core.AOS && m_LastDamage != 0 && Utility.RandomBool()) + { + damage = m_LastDamage; + } + else + { + damage = 1 + (int)(m_Mobile.Hits * m_Poison.m_Scalar); - From?.DoHarmful( m_Mobile, true ); + if (damage < m_Poison.m_Minimum) + damage = m_Poison.m_Minimum; + else if (damage > m_Poison.m_Maximum) + damage = m_Poison.m_Maximum; - if ( m_Mobile is IHonorTarget honorTarget ) - honorTarget.ReceivedHonorContext?.OnTargetPoisoned(); + m_LastDamage = damage; + } - AOS.Damage( m_Mobile, From, damage, 0, 0, 0, 100, 0 ); + From?.DoHarmful(m_Mobile, true); - if ( 0.60 <= Utility.RandomDouble() ) // OSI: randomly revealed between first and third damage tick, guessing 60% chance - m_Mobile.RevealingAction(); + if (m_Mobile is IHonorTarget honorTarget) + honorTarget.ReceivedHonorContext?.OnTargetPoisoned(); - if ( (m_Index % m_Poison.m_MessageInterval) == 0 ) - m_Mobile.OnPoisoned( From, m_Poison, m_Poison ); - } - } + AOS.Damage(m_Mobile, From, damage, 0, 0, 0, 100, 0); - public override Timer ConstructTimer( Mobile m ) - { - return new PoisonTimer( m, this ); - } - } -} + if (0.60 <= Utility.RandomDouble() + ) // OSI: randomly revealed between first and third damage tick, guessing 60% chance + m_Mobile.RevealingAction(); + + if (m_Index % m_Poison.m_MessageInterval == 0) + m_Mobile.OnPoisoned(From, m_Poison, m_Poison); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/ProfanityProtection.cs b/Scripts/Misc/ProfanityProtection.cs index 9f7b5df02..57c47db75 100644 --- a/Scripts/Misc/ProfanityProtection.cs +++ b/Scripts/Misc/ProfanityProtection.cs @@ -2,116 +2,124 @@ using Server.Network; namespace Server.Misc { - public enum ProfanityAction - { - None, // no action taken - Disallow, // speech is not displayed - Criminal, // makes the player criminal, not killable by guards - CriminalAction, // makes the player criminal, can be killed by guards - Disconnect, // player is kicked - Other // some other implementation - } + public enum ProfanityAction + { + None, // no action taken + Disallow, // speech is not displayed + Criminal, // makes the player criminal, not killable by guards + CriminalAction, // makes the player criminal, can be killed by guards + Disconnect, // player is kicked + Other // some other implementation + } - public class ProfanityProtection - { - private static bool Enabled = false; - private static ProfanityAction Action = ProfanityAction.Disallow; // change here what to do when profanity is detected + public class ProfanityProtection + { + private static bool Enabled = false; - public static void Initialize() - { - if ( Enabled ) - EventSink.Speech += EventSink_Speech; - } + private static ProfanityAction + Action = ProfanityAction.Disallow; // change here what to do when profanity is detected - private static bool OnProfanityDetected( Mobile from, string speech ) - { - switch ( Action ) - { - case ProfanityAction.None: return true; - case ProfanityAction.Disallow: return false; - case ProfanityAction.Criminal: from.Criminal = true; return true; - case ProfanityAction.CriminalAction: from.CriminalAction( false ); return true; - case ProfanityAction.Disconnect: - { - NetState ns = from.NetState; + public static char[] Exceptions{ get; } = + { + ' ', '-', '.', '\'', '"', ',', '_', '+', '=', '~', '`', '!', '^', '*', '\\', '/', ';', ':', '<', '>', '[', ']', + '{', '}', '?', '|', '(', ')', '%', '$', '&', '#', '@' + }; - ns?.Dispose(); + public static string[] StartDisallowed{ get; } = { }; - return false; - } - default: - case ProfanityAction.Other: // TODO: Provide custom implementation if this is chosen - { - return true; - } - } - } + public static string[] Disallowed{ get; } = + { + "jigaboo", + "chigaboo", + "wop", + "kyke", + "kike", + "tit", + "spic", + "prick", + "piss", + "lezbo", + "lesbo", + "felatio", + "dyke", + "dildo", + "chinc", + "chink", + "cunnilingus", + "cum", + "cocksucker", + "cock", + "clitoris", + "clit", + "ass", + "hitler", + "penis", + "nigga", + "nigger", + "klit", + "kunt", + "jiz", + "jism", + "jerkoff", + "jackoff", + "goddamn", + "fag", + "blowjob", + "bitch", + "asshole", + "dick", + "pussy", + "snatch", + "cunt", + "twat", + "shit", + "fuck" + }; - private static void EventSink_Speech( SpeechEventArgs e ) - { - Mobile from = e.Mobile; + public static void Initialize() + { + if (Enabled) + EventSink.Speech += EventSink_Speech; + } - if ( from.AccessLevel > AccessLevel.Player ) - return; + private static bool OnProfanityDetected(Mobile from, string speech) + { + switch (Action) + { + case ProfanityAction.None: return true; + case ProfanityAction.Disallow: return false; + case ProfanityAction.Criminal: + from.Criminal = true; + return true; + case ProfanityAction.CriminalAction: + from.CriminalAction(false); + return true; + case ProfanityAction.Disconnect: + { + NetState ns = from.NetState; - if ( !NameVerification.Validate( e.Speech, 0, int.MaxValue, true, true, false, int.MaxValue, Exceptions, Disallowed, StartDisallowed ) ) - e.Blocked = !OnProfanityDetected( from, e.Speech ); - } + ns?.Dispose(); - public static char[] Exceptions { get; } = - { - ' ', '-', '.', '\'', '"', ',', '_', '+', '=', '~', '`', '!', '^', '*', '\\', '/', ';', ':', '<', '>', '[', ']', '{', '}', '?', '|', '(', ')', '%', '$', '&', '#', '@' - }; + return false; + } + default: + case ProfanityAction.Other: // TODO: Provide custom implementation if this is chosen + { + return true; + } + } + } - public static string[] StartDisallowed { get; } = {}; + private static void EventSink_Speech(SpeechEventArgs e) + { + Mobile from = e.Mobile; - public static string[] Disallowed { get; } = - { - "jigaboo", - "chigaboo", - "wop", - "kyke", - "kike", - "tit", - "spic", - "prick", - "piss", - "lezbo", - "lesbo", - "felatio", - "dyke", - "dildo", - "chinc", - "chink", - "cunnilingus", - "cum", - "cocksucker", - "cock", - "clitoris", - "clit", - "ass", - "hitler", - "penis", - "nigga", - "nigger", - "klit", - "kunt", - "jiz", - "jism", - "jerkoff", - "jackoff", - "goddamn", - "fag", - "blowjob", - "bitch", - "asshole", - "dick", - "pussy", - "snatch", - "cunt", - "twat", - "shit", - "fuck" - }; - } + if (from.AccessLevel > AccessLevel.Player) + return; + + if (!NameVerification.Validate(e.Speech, 0, int.MaxValue, true, true, false, int.MaxValue, Exceptions, + Disallowed, StartDisallowed)) + e.Blocked = !OnProfanityDetected(from, e.Speech); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/Profile.cs b/Scripts/Misc/Profile.cs index 87fc18061..5967995c1 100644 --- a/Scripts/Misc/Profile.cs +++ b/Scripts/Misc/Profile.cs @@ -1,95 +1,95 @@ using System; -using Server.Network; using Server.Accounting; +using Server.Network; namespace Server.Misc { - public class Profile - { - public static void Initialize() - { - EventSink.ProfileRequest += EventSink_ProfileRequest; - EventSink.ChangeProfileRequest += EventSink_ChangeProfileRequest; - } + public class Profile + { + public static void Initialize() + { + EventSink.ProfileRequest += EventSink_ProfileRequest; + EventSink.ChangeProfileRequest += EventSink_ChangeProfileRequest; + } - public static void EventSink_ChangeProfileRequest( ChangeProfileRequestEventArgs e ) - { - Mobile from = e.Beholder; + public static void EventSink_ChangeProfileRequest(ChangeProfileRequestEventArgs e) + { + Mobile from = e.Beholder; - if ( from.ProfileLocked ) - from.SendMessage( "Your profile is locked. You may not change it." ); - else - from.Profile = e.Text; - } + if (from.ProfileLocked) + from.SendMessage("Your profile is locked. You may not change it."); + else + from.Profile = e.Text; + } - public static void EventSink_ProfileRequest( ProfileRequestEventArgs e ) - { - Mobile beholder = e.Beholder; - Mobile beheld = e.Beheld; + public static void EventSink_ProfileRequest(ProfileRequestEventArgs e) + { + Mobile beholder = e.Beholder; + Mobile beheld = e.Beheld; - if ( !beheld.Player ) - return; + if (!beheld.Player) + return; - if ( beholder.Map != beheld.Map || !beholder.InRange( beheld, 12 ) || !beholder.CanSee( beheld ) ) - return; + if (beholder.Map != beheld.Map || !beholder.InRange(beheld, 12) || !beholder.CanSee(beheld)) + return; - string header = Titles.ComputeTitle( beholder, beheld ); + string header = Titles.ComputeTitle(beholder, beheld); - string footer = ""; + string footer = ""; - if ( beheld.ProfileLocked ) - { - if ( beholder == beheld ) - footer = "Your profile has been locked."; - else if ( beholder.AccessLevel >= AccessLevel.Counselor ) - footer = "This profile has been locked."; - } + if (beheld.ProfileLocked) + { + if (beholder == beheld) + footer = "Your profile has been locked."; + else if (beholder.AccessLevel >= AccessLevel.Counselor) + footer = "This profile has been locked."; + } - if ( footer.Length == 0 && beholder == beheld ) - footer = GetAccountDuration( beheld ); + if (footer.Length == 0 && beholder == beheld) + footer = GetAccountDuration(beheld); - string body = beheld.Profile; + string body = beheld.Profile; - if ( body == null || body.Length <= 0 ) - body = ""; + if (body == null || body.Length <= 0) + body = ""; - beholder.Send( new DisplayProfile( beholder != beheld || !beheld.ProfileLocked, beheld, header, body, footer ) ); - } + beholder.Send(new DisplayProfile(beholder != beheld || !beheld.ProfileLocked, beheld, header, body, footer)); + } - private static string GetAccountDuration( Mobile m ) - { - if ( !(m.Account is Account a) ) - return ""; + private static string GetAccountDuration(Mobile m) + { + if (!(m.Account is Account a)) + return ""; - TimeSpan ts = DateTime.UtcNow - a.Created; + TimeSpan ts = DateTime.UtcNow - a.Created; - string v; + string v; - if ( Format( ts.TotalDays, "This account is {0} day{1} old.", out v ) ) - return v; + if (Format(ts.TotalDays, "This account is {0} day{1} old.", out v)) + return v; - if ( Format( ts.TotalHours, "This account is {0} hour{1} old.", out v ) ) - return v; + if (Format(ts.TotalHours, "This account is {0} hour{1} old.", out v)) + return v; - if ( Format( ts.TotalMinutes, "This account is {0} minute{1} old.", out v ) ) - return v; + if (Format(ts.TotalMinutes, "This account is {0} minute{1} old.", out v)) + return v; - if ( Format( ts.TotalSeconds, "This account is {0} second{1} old.", out v ) ) - return v; + if (Format(ts.TotalSeconds, "This account is {0} second{1} old.", out v)) + return v; - return ""; - } + return ""; + } - public static bool Format( double value, string format, out string op ) - { - if ( value >= 1.0 ) - { - op = string.Format( format, (int)value, (int)value != 1 ? "s" : "" ); - return true; - } + public static bool Format(double value, string format, out string op) + { + if (value >= 1.0) + { + op = string.Format(format, (int)value, (int)value != 1 ? "s" : ""); + return true; + } - op = null; - return false; - } - } -} + op = null; + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/ProtocolExtensions.cs b/Scripts/Misc/ProtocolExtensions.cs index 312d18224..5aeee0a96 100644 --- a/Scripts/Misc/ProtocolExtensions.cs +++ b/Scripts/Misc/ProtocolExtensions.cs @@ -3,60 +3,62 @@ using Server.Network; namespace Server.Misc { - public class ProtocolExtensions - { - private static PacketHandler[] m_Handlers = new PacketHandler[0x100]; + public class ProtocolExtensions + { + private static PacketHandler[] m_Handlers = new PacketHandler[0x100]; - public static void Initialize() - { - PacketHandlers.Register( 0xF0, 0, false, DecodeBundledPacket ); - } + public static void Initialize() + { + PacketHandlers.Register(0xF0, 0, false, DecodeBundledPacket); + } - public static void Register( int packetID, bool ingame, OnPacketReceive onReceive ) - { - m_Handlers[packetID] = new PacketHandler( packetID, 0, ingame, onReceive ); - } + public static void Register(int packetID, bool ingame, OnPacketReceive onReceive) + { + m_Handlers[packetID] = new PacketHandler(packetID, 0, ingame, onReceive); + } - public static PacketHandler GetHandler( int packetID ) - { - if ( packetID >= 0 && packetID < m_Handlers.Length ) - return m_Handlers[packetID]; + public static PacketHandler GetHandler(int packetID) + { + if (packetID >= 0 && packetID < m_Handlers.Length) + return m_Handlers[packetID]; - return null; - } + return null; + } - public static void DecodeBundledPacket( NetState state, PacketReader pvSrc ) - { - int packetID = pvSrc.ReadByte(); + public static void DecodeBundledPacket(NetState state, PacketReader pvSrc) + { + int packetID = pvSrc.ReadByte(); - PacketHandler ph = GetHandler( packetID ); + PacketHandler ph = GetHandler(packetID); - if ( ph != null ) - { - if ( ph.Ingame && state.Mobile == null ) - { - Console.WriteLine( "Client: {0}: Sent ingame packet (0xF0x{1:X2}) before having been attached to a mobile", state, packetID ); - state.Dispose(); - } - else if ( ph.Ingame && state.Mobile.Deleted ) - { - state.Dispose(); - } - else - { - ph.OnReceive( state, pvSrc ); - } - } - } - } + if (ph != null) + { + if (ph.Ingame && state.Mobile == null) + { + Console.WriteLine( + "Client: {0}: Sent ingame packet (0xF0x{1:X2}) before having been attached to a mobile", state, + packetID); + state.Dispose(); + } + else if (ph.Ingame && state.Mobile.Deleted) + { + state.Dispose(); + } + else + { + ph.OnReceive(state, pvSrc); + } + } + } + } - public abstract class ProtocolExtension : Packet - { - public ProtocolExtension( int packetID, int capacity ) : base( 0xF0 ) - { - EnsureCapacity( 4 + capacity ); + public abstract class ProtocolExtension : Packet + { + public ProtocolExtension(int packetID, int capacity) : base(0xF0) + { + EnsureCapacity(4 + capacity); - m_Stream.Write( (byte) packetID ); - } - } + m_Stream.Write((byte)packetID); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/RaceDefinitions.cs b/Scripts/Misc/RaceDefinitions.cs index a66c6f483..a686169b6 100644 --- a/Scripts/Misc/RaceDefinitions.cs +++ b/Scripts/Misc/RaceDefinitions.cs @@ -1,321 +1,326 @@ namespace Server.Misc { - public class RaceDefinitions - { - public static void Configure() - { - /* Here we configure all races. Some notes: - * - * 1) The first 32 races are reserved for core use. - * 2) Race 0x7F is reserved for core use. - * 3) Race 0xFF is reserved for core use. - * 4) Changing or removing any predefined races may cause server instability. - */ + public class RaceDefinitions + { + public static void Configure() + { + /* Here we configure all races. Some notes: + * + * 1) The first 32 races are reserved for core use. + * 2) Race 0x7F is reserved for core use. + * 3) Race 0xFF is reserved for core use. + * 4) Changing or removing any predefined races may cause server instability. + */ - RegisterRace( new Human( 0, 0 ) ); - RegisterRace( new Elf( 1, 1 ) ); - RegisterRace( new Gargoyle( 2, 2 ) ); - } + RegisterRace(new Human(0, 0)); + RegisterRace(new Elf(1, 1)); + RegisterRace(new Gargoyle(2, 2)); + } - public static void RegisterRace( Race race ) - { - Race.Races[race.RaceIndex] = race; - Race.AllRaces.Add( race ); - } + public static void RegisterRace(Race race) + { + Race.Races[race.RaceIndex] = race; + Race.AllRaces.Add(race); + } - private class Human : Race - { - public Human( int raceID, int raceIndex ) - : base( raceID, raceIndex, "Human", "Humans", 400, 401, 402, 403, Expansion.None ) - { - } + private class Human : Race + { + public Human(int raceID, int raceIndex) + : base(raceID, raceIndex, "Human", "Humans", 400, 401, 402, 403, Expansion.None) + { + } - public override bool ValidateHair( bool female, int itemID ) - { - if ( itemID == 0 ) - return true; + public override bool ValidateHair(bool female, int itemID) + { + if (itemID == 0) + return true; - if ( (female && itemID == 0x2048) || (!female && itemID == 0x2046 ) ) - return false; //Buns & Receeding Hair + if (female && itemID == 0x2048 || !female && itemID == 0x2046) + return false; //Buns & Receeding Hair - if ( itemID >= 0x203B && itemID <= 0x203D ) - return true; + if (itemID >= 0x203B && itemID <= 0x203D) + return true; - if ( itemID >= 0x2044 && itemID <= 0x204A ) - return true; + if (itemID >= 0x2044 && itemID <= 0x204A) + return true; - return false; - } + return false; + } - public override int RandomHair( bool female ) //Random hair doesn't include baldness - { - switch( Utility.Random( 9 ) ) - { - case 0: return 0x203B; //Short - case 1: return 0x203C; //Long - case 2: return 0x203D; //Pony Tail - case 3: return 0x2044; //Mohawk - case 4: return 0x2045; //Pageboy - case 5: return 0x2047; //Afro - case 6: return 0x2049; //Pig tails - case 7: return 0x204A; //Krisna - default: return (female ? 0x2046 : 0x2048); //Buns or Receeding Hair - } - } - - public override bool ValidateFacialHair( bool female, int itemID ) - { - if ( itemID == 0 ) - return true; - - if ( female ) - return false; - - if ( itemID >= 0x203E && itemID <= 0x2041 ) - return true; - - if ( itemID >= 0x204B && itemID <= 0x204D ) - return true; - - return false; - } - - public override int RandomFacialHair( bool female ) - { - if ( female ) - return 0; - - int rand = Utility.Random( 7 ); - - return ((rand < 4) ? 0x203E : 0x2047) + rand; - } - - public override int ClipSkinHue( int hue ) - { - if ( hue < 1002 ) - return 1002; - if ( hue > 1058 ) - return 1058; - return hue; - } - - public override int RandomSkinHue() - { - return Utility.Random( 1002, 57 ) | 0x8000; - } - - public override int ClipHairHue( int hue ) - { - if ( hue < 1102 ) - return 1102; - if ( hue > 1149 ) - return 1149; - return hue; - } - - public override int RandomHairHue() - { - return Utility.Random( 1102, 48 ); - } - } - - private class Elf : Race - { - private static int[] m_SkinHues = { - 0x0BF, 0x24D, 0x24E, 0x24F, 0x353, 0x361, 0x367, 0x374, - 0x375, 0x376, 0x381, 0x382, 0x383, 0x384, 0x385, 0x389, - 0x3DE, 0x3E5, 0x3E6, 0x3E8, 0x3E9, 0x430, 0x4A7, 0x4DE, - 0x51D, 0x53F, 0x579, 0x76B, 0x76C, 0x76D, 0x835, 0x903 - }; - - private static int[] m_HairHues = { - 0x034, 0x035, 0x036, 0x037, 0x038, 0x039, 0x058, 0x08E, - 0x08F, 0x090, 0x091, 0x092, 0x101, 0x159, 0x15A, 0x15B, - 0x15C, 0x15D, 0x15E, 0x128, 0x12F, 0x1BD, 0x1E4, 0x1F3, - 0x207, 0x211, 0x239, 0x251, 0x26C, 0x2C3, 0x2C9, 0x31D, - 0x31E, 0x31F, 0x320, 0x321, 0x322, 0x323, 0x324, 0x325, - 0x326, 0x369, 0x386, 0x387, 0x388, 0x389, 0x38A, 0x59D, - 0x6B8, 0x725, 0x853 - }; - - public Elf( int raceID, int raceIndex ) - : base( raceID, raceIndex, "Elf", "Elves", 605, 606, 607, 608, Expansion.ML ) - { - } - - public override bool ValidateHair( bool female, int itemID ) - { - if ( itemID == 0 ) - return true; - - if ( (female && (itemID == 0x2FCD || itemID == 0x2FBF)) || (!female && (itemID == 0x2FCC || itemID == 0x2FD0)) ) - return false; - - if ( itemID >= 0x2FBF && itemID <= 0x2FC2 ) - return true; - - if ( itemID >= 0x2FCC && itemID <= 0x2FD1 ) - return true; - - return false; - } - - public override int RandomHair( bool female ) //Random hair doesn't include baldness - { - switch( Utility.Random( 8 ) ) - { - case 0: return 0x2FC0; //Long Feather - case 1: return 0x2FC1; //Short - case 2: return 0x2FC2; //Mullet - case 3: return 0x2FCE; //Knob - case 4: return 0x2FCF; //Braided - case 5: return 0x2FD1; //Spiked - case 6: return (female ? 0x2FCC : 0x2FBF); //Flower or Mid-long - default: return (female ? 0x2FD0 : 0x2FCD); //Bun or Long - } - } - - public override bool ValidateFacialHair( bool female, int itemID ) - { - return (itemID == 0); - } - - public override int RandomFacialHair( bool female ) - { - return 0; - } - - public override int ClipSkinHue( int hue ) - { - for( int i = 0; i < m_SkinHues.Length; i++ ) - if ( m_SkinHues[i] == hue ) - return hue; - - return m_SkinHues[0]; - } - - public override int RandomSkinHue() - { - return m_SkinHues[Utility.Random( m_SkinHues.Length )] | 0x8000; - } - - public override int ClipHairHue( int hue ) - { - for( int i = 0; i < m_HairHues.Length; i++ ) - if ( m_HairHues[i] == hue ) - return hue; - - return m_HairHues[0]; - } - - public override int RandomHairHue() - { - return m_HairHues[Utility.Random( m_HairHues.Length )]; - } - } - - #region SA - private class Gargoyle : Race + public override int RandomHair(bool female) //Random hair doesn't include baldness + { + switch (Utility.Random(9)) { - public Gargoyle(int raceID, int raceIndex) - : base(raceID, raceIndex, "Gargoyle", "Gargoyles", 666, 667, 402, 403, Expansion.SA) - { - } - - public override bool ValidateHair(bool female, int itemID) - { - if (female == false) - { - return itemID >= 0x4258 && itemID <= 0x425F; - } - - return ((itemID == 0x4261 || itemID == 0x4262) || (itemID >= 0x4273 && itemID <= 0x4275) || (itemID == 0x42B0 || itemID == 0x42B1) || (itemID == 0x42AA || itemID == 0x42AB)); - } - - public override int RandomHair(bool female) - { - if (Utility.Random(9) == 0) - return 0; - if (!female) - return 0x4258 + Utility.Random(8); - switch (Utility.Random(9)) - { - case 0: - return 0x4261; - case 1: - return 0x4262; - case 2: - return 0x4273; - case 3: - return 0x4274; - case 4: - return 0x4275; - case 5: - return 0x42B0; - case 6: - return 0x42B1; - case 7: - return 0x42AA; - case 8: - return 0x42AB; - } - return 0; - } - - public override bool ValidateFacialHair(bool female, int itemID) - { - if (female) - return false; - return itemID >= 0x42AD && itemID <= 0x42B0; - } - - public override int RandomFacialHair(bool female) - { - if (female) - return 0; - return Utility.RandomList(0, 0x42AD, 0x42AE, 0x42AF, 0x42B0); - } - - // Todo Finish body hues - private static readonly int[] m_BodyHues = { - 0x86DB, 0x86DC, 0x86DD, 0x86DE, - 0x86DF, 0x86E0, 0x86E1, 0x86E2, - 0x86E3, 0x86E4, 0x86E5, 0x86E6 - // 0x, 0x, 0x, 0x, // 86E7/86E8/86E9/86EA? - // 0x, 0x, 0x, 0x, // 86EB/86EC/86ED/86EE? - // 0x86F3, 0x86DB, 0x86DC, 0x86DD - }; - - public override int ClipSkinHue(int hue) - { - return hue; // for hue information gathering - } - - public override int RandomSkinHue() - { - return m_BodyHues[Utility.Random(m_BodyHues.Length)] | 0x8000; - } - - private static readonly int[] m_HornHues = { - 0x709, 0x70B, 0x70D, 0x70F, 0x711, 0x763, - 0x765, 0x768, 0x76B, 0x6F3, 0x6F1, 0x6EF, - 0x6E4, 0x6E2, 0x6E0, 0x709, 0x70B, 0x70D - }; - - public override int ClipHairHue(int hue) - { - for (int i = 0; i < m_HornHues.Length; i++) - if (m_HornHues[i] == hue) - return hue; - - return m_HornHues[0]; - } - - public override int RandomHairHue() - { - return m_HornHues[Utility.Random(m_HornHues.Length)]; - } + case 0: return 0x203B; //Short + case 1: return 0x203C; //Long + case 2: return 0x203D; //Pony Tail + case 3: return 0x2044; //Mohawk + case 4: return 0x2045; //Pageboy + case 5: return 0x2047; //Afro + case 6: return 0x2049; //Pig tails + case 7: return 0x204A; //Krisna + default: return female ? 0x2046 : 0x2048; //Buns or Receeding Hair } - #endregion - } -} + } + + public override bool ValidateFacialHair(bool female, int itemID) + { + if (itemID == 0) + return true; + + if (female) + return false; + + if (itemID >= 0x203E && itemID <= 0x2041) + return true; + + if (itemID >= 0x204B && itemID <= 0x204D) + return true; + + return false; + } + + public override int RandomFacialHair(bool female) + { + if (female) + return 0; + + int rand = Utility.Random(7); + + return (rand < 4 ? 0x203E : 0x2047) + rand; + } + + public override int ClipSkinHue(int hue) + { + if (hue < 1002) + return 1002; + if (hue > 1058) + return 1058; + return hue; + } + + public override int RandomSkinHue() + { + return Utility.Random(1002, 57) | 0x8000; + } + + public override int ClipHairHue(int hue) + { + if (hue < 1102) + return 1102; + if (hue > 1149) + return 1149; + return hue; + } + + public override int RandomHairHue() + { + return Utility.Random(1102, 48); + } + } + + private class Elf : Race + { + private static int[] m_SkinHues = + { + 0x0BF, 0x24D, 0x24E, 0x24F, 0x353, 0x361, 0x367, 0x374, + 0x375, 0x376, 0x381, 0x382, 0x383, 0x384, 0x385, 0x389, + 0x3DE, 0x3E5, 0x3E6, 0x3E8, 0x3E9, 0x430, 0x4A7, 0x4DE, + 0x51D, 0x53F, 0x579, 0x76B, 0x76C, 0x76D, 0x835, 0x903 + }; + + private static int[] m_HairHues = + { + 0x034, 0x035, 0x036, 0x037, 0x038, 0x039, 0x058, 0x08E, + 0x08F, 0x090, 0x091, 0x092, 0x101, 0x159, 0x15A, 0x15B, + 0x15C, 0x15D, 0x15E, 0x128, 0x12F, 0x1BD, 0x1E4, 0x1F3, + 0x207, 0x211, 0x239, 0x251, 0x26C, 0x2C3, 0x2C9, 0x31D, + 0x31E, 0x31F, 0x320, 0x321, 0x322, 0x323, 0x324, 0x325, + 0x326, 0x369, 0x386, 0x387, 0x388, 0x389, 0x38A, 0x59D, + 0x6B8, 0x725, 0x853 + }; + + public Elf(int raceID, int raceIndex) + : base(raceID, raceIndex, "Elf", "Elves", 605, 606, 607, 608, Expansion.ML) + { + } + + public override bool ValidateHair(bool female, int itemID) + { + if (itemID == 0) + return true; + + if (female && (itemID == 0x2FCD || itemID == 0x2FBF) || !female && (itemID == 0x2FCC || itemID == 0x2FD0)) + return false; + + if (itemID >= 0x2FBF && itemID <= 0x2FC2) + return true; + + if (itemID >= 0x2FCC && itemID <= 0x2FD1) + return true; + + return false; + } + + public override int RandomHair(bool female) //Random hair doesn't include baldness + { + switch (Utility.Random(8)) + { + case 0: return 0x2FC0; //Long Feather + case 1: return 0x2FC1; //Short + case 2: return 0x2FC2; //Mullet + case 3: return 0x2FCE; //Knob + case 4: return 0x2FCF; //Braided + case 5: return 0x2FD1; //Spiked + case 6: return female ? 0x2FCC : 0x2FBF; //Flower or Mid-long + default: return female ? 0x2FD0 : 0x2FCD; //Bun or Long + } + } + + public override bool ValidateFacialHair(bool female, int itemID) + { + return itemID == 0; + } + + public override int RandomFacialHair(bool female) + { + return 0; + } + + public override int ClipSkinHue(int hue) + { + for (int i = 0; i < m_SkinHues.Length; i++) + if (m_SkinHues[i] == hue) + return hue; + + return m_SkinHues[0]; + } + + public override int RandomSkinHue() + { + return m_SkinHues[Utility.Random(m_SkinHues.Length)] | 0x8000; + } + + public override int ClipHairHue(int hue) + { + for (int i = 0; i < m_HairHues.Length; i++) + if (m_HairHues[i] == hue) + return hue; + + return m_HairHues[0]; + } + + public override int RandomHairHue() + { + return m_HairHues[Utility.Random(m_HairHues.Length)]; + } + } + + #region SA + + private class Gargoyle : Race + { + // Todo Finish body hues + private static readonly int[] m_BodyHues = + { + 0x86DB, 0x86DC, 0x86DD, 0x86DE, + 0x86DF, 0x86E0, 0x86E1, 0x86E2, + 0x86E3, 0x86E4, 0x86E5, 0x86E6 + // 0x, 0x, 0x, 0x, // 86E7/86E8/86E9/86EA? + // 0x, 0x, 0x, 0x, // 86EB/86EC/86ED/86EE? + // 0x86F3, 0x86DB, 0x86DC, 0x86DD + }; + + private static readonly int[] m_HornHues = + { + 0x709, 0x70B, 0x70D, 0x70F, 0x711, 0x763, + 0x765, 0x768, 0x76B, 0x6F3, 0x6F1, 0x6EF, + 0x6E4, 0x6E2, 0x6E0, 0x709, 0x70B, 0x70D + }; + + public Gargoyle(int raceID, int raceIndex) + : base(raceID, raceIndex, "Gargoyle", "Gargoyles", 666, 667, 402, 403, Expansion.SA) + { + } + + public override bool ValidateHair(bool female, int itemID) + { + if (female == false) return itemID >= 0x4258 && itemID <= 0x425F; + + return itemID == 0x4261 || itemID == 0x4262 || itemID >= 0x4273 && itemID <= 0x4275 || itemID == 0x42B0 || + itemID == 0x42B1 || itemID == 0x42AA || itemID == 0x42AB; + } + + public override int RandomHair(bool female) + { + if (Utility.Random(9) == 0) + return 0; + if (!female) + return 0x4258 + Utility.Random(8); + switch (Utility.Random(9)) + { + case 0: + return 0x4261; + case 1: + return 0x4262; + case 2: + return 0x4273; + case 3: + return 0x4274; + case 4: + return 0x4275; + case 5: + return 0x42B0; + case 6: + return 0x42B1; + case 7: + return 0x42AA; + case 8: + return 0x42AB; + } + + return 0; + } + + public override bool ValidateFacialHair(bool female, int itemID) + { + if (female) + return false; + return itemID >= 0x42AD && itemID <= 0x42B0; + } + + public override int RandomFacialHair(bool female) + { + if (female) + return 0; + return Utility.RandomList(0, 0x42AD, 0x42AE, 0x42AF, 0x42B0); + } + + public override int ClipSkinHue(int hue) + { + return hue; // for hue information gathering + } + + public override int RandomSkinHue() + { + return m_BodyHues[Utility.Random(m_BodyHues.Length)] | 0x8000; + } + + public override int ClipHairHue(int hue) + { + for (int i = 0; i < m_HornHues.Length; i++) + if (m_HornHues[i] == hue) + return hue; + + return m_HornHues[0]; + } + + public override int RandomHairHue() + { + return m_HornHues[Utility.Random(m_HornHues.Length)]; + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Misc/RegenRates.cs b/Scripts/Misc/RegenRates.cs index 5c46b5b80..66662164d 100644 --- a/Scripts/Misc/RegenRates.cs +++ b/Scripts/Misc/RegenRates.cs @@ -1,220 +1,220 @@ using System; using Server.Items; +using Server.Mobiles; using Server.Spells; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; -using Server.Mobiles; namespace Server.Misc { - public class RegenRates - { - [CallPriority( 10 )] - public static void Configure() - { - Mobile.DefaultHitsRate = TimeSpan.FromSeconds( 11.0 ); - Mobile.DefaultStamRate = TimeSpan.FromSeconds( 7.0 ); - Mobile.DefaultManaRate = TimeSpan.FromSeconds( 7.0 ); + public class RegenRates + { + [CallPriority(10)] + public static void Configure() + { + Mobile.DefaultHitsRate = TimeSpan.FromSeconds(11.0); + Mobile.DefaultStamRate = TimeSpan.FromSeconds(7.0); + Mobile.DefaultManaRate = TimeSpan.FromSeconds(7.0); - Mobile.ManaRegenRateHandler = Mobile_ManaRegenRate; + Mobile.ManaRegenRateHandler = Mobile_ManaRegenRate; - if ( Core.AOS ) - { - Mobile.StamRegenRateHandler = Mobile_StamRegenRate; - Mobile.HitsRegenRateHandler = Mobile_HitsRegenRate; - } - } + if (Core.AOS) + { + Mobile.StamRegenRateHandler = Mobile_StamRegenRate; + Mobile.HitsRegenRateHandler = Mobile_HitsRegenRate; + } + } - private static void CheckBonusSkill( Mobile m, int cur, int max, SkillName skill ) - { - if ( !m.Alive ) - return; + private static void CheckBonusSkill(Mobile m, int cur, int max, SkillName skill) + { + if (!m.Alive) + return; - double n = (double)cur / max; - double v = Math.Sqrt( m.Skills[skill].Value * 0.005 ); + double n = (double)cur / max; + double v = Math.Sqrt(m.Skills[skill].Value * 0.005); - n *= (1.0 - v); - n += v; + n *= 1.0 - v; + n += v; - m.CheckSkill( skill, n ); - } + m.CheckSkill(skill, n); + } - private static bool CheckTransform( Mobile m, Type type ) - { - return TransformationSpellHelper.UnderTransformation( m, type ); - } + private static bool CheckTransform(Mobile m, Type type) + { + return TransformationSpellHelper.UnderTransformation(m, type); + } - private static bool CheckAnimal( Mobile m, Type type ) - { - return AnimalForm.UnderTransformation( m, type ); - } + private static bool CheckAnimal(Mobile m, Type type) + { + return AnimalForm.UnderTransformation(m, type); + } - private static TimeSpan Mobile_HitsRegenRate( Mobile from ) - { - int points = AosAttributes.GetValue( from, AosAttribute.RegenHits ); + private static TimeSpan Mobile_HitsRegenRate(Mobile from) + { + int points = AosAttributes.GetValue(from, AosAttribute.RegenHits); - BaseCreature bc = from as BaseCreature; + BaseCreature bc = from as BaseCreature; - if ( bc != null && !bc.IsAnimatedDead ) - points += 4; + if (bc != null && !bc.IsAnimatedDead) + points += 4; - if ( bc?.IsParagon == true || from is Leviathan ) - points += 40; + if (bc?.IsParagon == true || from is Leviathan) + points += 40; - if ( Core.ML && from.Race == Race.Human ) //Is this affected by the cap? - points += 2; + if (Core.ML && from.Race == Race.Human) //Is this affected by the cap? + points += 2; - if ( points < 0 ) - points = 0; + if (points < 0) + points = 0; - if ( Core.ML && from is PlayerMobile ) //does racial bonus go before/after? - points = Math.Min( points, 18 ); + if (Core.ML && from is PlayerMobile) //does racial bonus go before/after? + points = Math.Min(points, 18); - if ( CheckTransform( from, typeof( HorrificBeastSpell ) ) ) - points += 20; + if (CheckTransform(from, typeof(HorrificBeastSpell))) + points += 20; - if ( CheckAnimal( from, typeof( Dog ) ) || CheckAnimal( from, typeof( Cat ) ) ) - points += from.Skills[SkillName.Ninjitsu].Fixed / 30; + if (CheckAnimal(from, typeof(Dog)) || CheckAnimal(from, typeof(Cat))) + points += from.Skills[SkillName.Ninjitsu].Fixed / 30; - return TimeSpan.FromSeconds( 1.0 / (0.1 * (1 + points)) ); - } + return TimeSpan.FromSeconds(1.0 / (0.1 * (1 + points))); + } - private static TimeSpan Mobile_StamRegenRate( Mobile from ) - { - if ( from.Skills == null ) - return Mobile.DefaultStamRate; + private static TimeSpan Mobile_StamRegenRate(Mobile from) + { + if (from.Skills == null) + return Mobile.DefaultStamRate; - CheckBonusSkill( from, from.Stam, from.StamMax, SkillName.Focus ); + CheckBonusSkill(from, from.Stam, from.StamMax, SkillName.Focus); - int points =(int)(from.Skills[SkillName.Focus].Value * 0.1); + int points = (int)(from.Skills[SkillName.Focus].Value * 0.1); - if ( (from is BaseCreature creature && creature.IsParagon) || from is Leviathan ) - points += 40; + if (from is BaseCreature creature && creature.IsParagon || from is Leviathan) + points += 40; - int cappedPoints = AosAttributes.GetValue( from, AosAttribute.RegenStam ); + int cappedPoints = AosAttributes.GetValue(from, AosAttribute.RegenStam); - if ( CheckTransform( from, typeof( VampiricEmbraceSpell ) ) ) - cappedPoints += 15; + if (CheckTransform(from, typeof(VampiricEmbraceSpell))) + cappedPoints += 15; - if ( CheckAnimal( from, typeof( Kirin ) ) ) - cappedPoints += 20; + if (CheckAnimal(from, typeof(Kirin))) + cappedPoints += 20; - if ( Core.ML && from is PlayerMobile ) - cappedPoints = Math.Min( cappedPoints, 24 ); + if (Core.ML && from is PlayerMobile) + cappedPoints = Math.Min(cappedPoints, 24); - points += cappedPoints; + points += cappedPoints; - if ( points < -1 ) - points = -1; + if (points < -1) + points = -1; - return TimeSpan.FromSeconds( 1.0 / (0.1 * (2 + points)) ); - } + return TimeSpan.FromSeconds(1.0 / (0.1 * (2 + points))); + } - private static TimeSpan Mobile_ManaRegenRate( Mobile from ) - { - if ( from.Skills == null ) - return Mobile.DefaultManaRate; + private static TimeSpan Mobile_ManaRegenRate(Mobile from) + { + if (from.Skills == null) + return Mobile.DefaultManaRate; - if ( !from.Meditating ) - CheckBonusSkill( from, from.Mana, from.ManaMax, SkillName.Meditation ); + if (!from.Meditating) + CheckBonusSkill(from, from.Mana, from.ManaMax, SkillName.Meditation); - double rate; - double armorPenalty = GetArmorOffset( from ); + double rate; + double armorPenalty = GetArmorOffset(from); - if ( Core.AOS ) - { - double medPoints = from.Int + (from.Skills[SkillName.Meditation].Value * 3); + if (Core.AOS) + { + double medPoints = from.Int + from.Skills[SkillName.Meditation].Value * 3; - medPoints *= ( from.Skills[SkillName.Meditation].Value < 100.0 ) ? 0.025 : 0.0275; + medPoints *= from.Skills[SkillName.Meditation].Value < 100.0 ? 0.025 : 0.0275; - CheckBonusSkill( from, from.Mana, from.ManaMax, SkillName.Focus ); + CheckBonusSkill(from, from.Mana, from.ManaMax, SkillName.Focus); - double focusPoints = (from.Skills[SkillName.Focus].Value * 0.05); + double focusPoints = from.Skills[SkillName.Focus].Value * 0.05; - if ( armorPenalty > 0 ) - medPoints = 0; // In AOS, wearing any meditation-blocking armor completely removes meditation bonus + if (armorPenalty > 0) + medPoints = 0; // In AOS, wearing any meditation-blocking armor completely removes meditation bonus - double totalPoints = focusPoints + medPoints + (from.Meditating ? (medPoints > 13.0 ? 13.0 : medPoints) : 0.0); + double totalPoints = focusPoints + medPoints + (from.Meditating ? medPoints > 13.0 ? 13.0 : medPoints : 0.0); - if ( (from is BaseCreature creature && creature.IsParagon) || from is Leviathan ) - totalPoints += 40; + if (from is BaseCreature creature && creature.IsParagon || from is Leviathan) + totalPoints += 40; - int cappedPoints = AosAttributes.GetValue( from, AosAttribute.RegenMana ); + int cappedPoints = AosAttributes.GetValue(from, AosAttribute.RegenMana); - if ( CheckTransform( from, typeof( VampiricEmbraceSpell ) ) ) - cappedPoints += 3; - else if ( CheckTransform( from, typeof( LichFormSpell ) ) ) - cappedPoints += 13; + if (CheckTransform(from, typeof(VampiricEmbraceSpell))) + cappedPoints += 3; + else if (CheckTransform(from, typeof(LichFormSpell))) + cappedPoints += 13; - if ( Core.ML && from is PlayerMobile ) - cappedPoints = Math.Min( cappedPoints, 18 ); + if (Core.ML && from is PlayerMobile) + cappedPoints = Math.Min(cappedPoints, 18); - totalPoints += cappedPoints; + totalPoints += cappedPoints; - if ( totalPoints < -1 ) - totalPoints = -1; + if (totalPoints < -1) + totalPoints = -1; - if ( Core.ML ) - totalPoints = Math.Floor( totalPoints ); + if (Core.ML) + totalPoints = Math.Floor(totalPoints); - rate = 1.0 / (0.1 * (2 + totalPoints)); - } - else - { - double medPoints = (from.Int + from.Skills[SkillName.Meditation].Value) * 0.5; + rate = 1.0 / (0.1 * (2 + totalPoints)); + } + else + { + double medPoints = (from.Int + from.Skills[SkillName.Meditation].Value) * 0.5; - if ( medPoints <= 0 ) - rate = 7.0; - else if ( medPoints <= 100 ) - rate = 7.0 - (239*medPoints/2400) + (19*medPoints*medPoints/48000); - else if ( medPoints < 120 ) - rate = 1.0; - else - rate = 0.75; + if (medPoints <= 0) + rate = 7.0; + else if (medPoints <= 100) + rate = 7.0 - 239 * medPoints / 2400 + 19 * medPoints * medPoints / 48000; + else if (medPoints < 120) + rate = 1.0; + else + rate = 0.75; - rate += armorPenalty; + rate += armorPenalty; - if ( from.Meditating ) - rate *= 0.5; + if (from.Meditating) + rate *= 0.5; - if ( rate < 0.5 ) - rate = 0.5; - else if ( rate > 7.0 ) - rate = 7.0; - } + if (rate < 0.5) + rate = 0.5; + else if (rate > 7.0) + rate = 7.0; + } - return TimeSpan.FromSeconds( rate ); - } + return TimeSpan.FromSeconds(rate); + } - public static double GetArmorOffset( Mobile from ) - { - double rating = 0.0; + public static double GetArmorOffset(Mobile from) + { + double rating = 0.0; - if ( !Core.AOS ) - rating += GetArmorMeditationValue( from.ShieldArmor as BaseArmor ); + if (!Core.AOS) + rating += GetArmorMeditationValue(from.ShieldArmor as BaseArmor); - rating += GetArmorMeditationValue( from.NeckArmor as BaseArmor ); - rating += GetArmorMeditationValue( from.HandArmor as BaseArmor ); - rating += GetArmorMeditationValue( from.HeadArmor as BaseArmor ); - rating += GetArmorMeditationValue( from.ArmsArmor as BaseArmor ); - rating += GetArmorMeditationValue( from.LegsArmor as BaseArmor ); - rating += GetArmorMeditationValue( from.ChestArmor as BaseArmor ); + rating += GetArmorMeditationValue(from.NeckArmor as BaseArmor); + rating += GetArmorMeditationValue(from.HandArmor as BaseArmor); + rating += GetArmorMeditationValue(from.HeadArmor as BaseArmor); + rating += GetArmorMeditationValue(from.ArmsArmor as BaseArmor); + rating += GetArmorMeditationValue(from.LegsArmor as BaseArmor); + rating += GetArmorMeditationValue(from.ChestArmor as BaseArmor); - return rating / 4; - } + return rating / 4; + } - private static double GetArmorMeditationValue( BaseArmor ar ) - { - if ( ar == null || ar.ArmorAttributes.MageArmor != 0 || ar.Attributes.SpellChanneling != 0 ) - return 0.0; + private static double GetArmorMeditationValue(BaseArmor ar) + { + if (ar == null || ar.ArmorAttributes.MageArmor != 0 || ar.Attributes.SpellChanneling != 0) + return 0.0; - switch ( ar.MeditationAllowance ) - { - default: - case ArmorMeditationAllowance.None: return ar.BaseArmorRatingScaled; - case ArmorMeditationAllowance.Half: return ar.BaseArmorRatingScaled / 2.0; - case ArmorMeditationAllowance.All: return 0.0; - } - } - } -} + switch (ar.MeditationAllowance) + { + default: + case ArmorMeditationAllowance.None: return ar.BaseArmorRatingScaled; + case ArmorMeditationAllowance.Half: return ar.BaseArmorRatingScaled / 2.0; + case ArmorMeditationAllowance.All: return 0.0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/RenameRequests.cs b/Scripts/Misc/RenameRequests.cs index aacbe151e..02028eb0a 100644 --- a/Scripts/Misc/RenameRequests.cs +++ b/Scripts/Misc/RenameRequests.cs @@ -1,50 +1,47 @@ -using System; - namespace Server.Misc { - public class RenameRequests - { - public static void Initialize() - { - EventSink.RenameRequest += EventSink_RenameRequest; - } + public class RenameRequests + { + public static void Initialize() + { + EventSink.RenameRequest += EventSink_RenameRequest; + } - private static void EventSink_RenameRequest( RenameRequestEventArgs e ) - { - Mobile from = e.From; - Mobile targ = e.Target; - string name = e.Name; + private static void EventSink_RenameRequest(RenameRequestEventArgs e) + { + Mobile from = e.From; + Mobile targ = e.Target; + string name = e.Name; - if ( from.CanSee( targ ) && from.InRange( targ, 12 ) && targ.CanBeRenamedBy( from ) ) - { - name = name.Trim(); + if (from.CanSee(targ) && from.InRange(targ, 12) && targ.CanBeRenamedBy(from)) + { + name = name.Trim(); - if ( NameVerification.Validate( name, 1, 16, true, false, true, 0, NameVerification.Empty, NameVerification.StartDisallowed, ( Core.ML ? NameVerification.Disallowed : new string[]{} ) ) ) - { + if (NameVerification.Validate(name, 1, 16, true, false, true, 0, NameVerification.Empty, + NameVerification.StartDisallowed, Core.ML ? NameVerification.Disallowed : new string[] { })) + { + if (Core.ML) + { + string[] disallowed = ProfanityProtection.Disallowed; - if ( Core.ML ) - { - string[] disallowed = ProfanityProtection.Disallowed; + for (int i = 0; i < disallowed.Length; i++) + if (name.IndexOf(disallowed[i]) != -1) + { + from.SendLocalizedMessage(1072622); // That name isn't very polite. + return; + } - for( int i = 0; i < disallowed.Length; i++ ) - { - if ( name.IndexOf( disallowed[i] ) != -1 ) - { - from.SendLocalizedMessage( 1072622 ); // That name isn't very polite. - return; - } - } + from.SendLocalizedMessage(1072623, + $"{targ.Name}\t{name}"); // Pet ~1_OLDPETNAME~ renamed to ~2_NEWPETNAME~. + } - from.SendLocalizedMessage( 1072623, $"{targ.Name}\t{name}"); // Pet ~1_OLDPETNAME~ renamed to ~2_NEWPETNAME~. - } - - targ.Name = name; - } - else - { - from.SendMessage( "That name is unacceptable." ); - } - } - } - } -} + targ.Name = name; + } + else + { + from.SendMessage("That name is unacceptable."); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/ServerList.cs b/Scripts/Misc/ServerList.cs index f31bf0021..b251642c0 100644 --- a/Scripts/Misc/ServerList.cs +++ b/Scripts/Misc/ServerList.cs @@ -7,190 +7,202 @@ using Server.Network; namespace Server.Misc { - public class ServerList - { - /* - * The default setting for Address, a value of 'null', will use your local IP address. If all of your local IP addresses - * are private network addresses and AutoDetect is 'true' then RunUO will attempt to discover your public IP address - * for you automatically. - * - * If you do not plan on allowing clients outside of your LAN to connect, you can set AutoDetect to 'false' and leave - * Address set to 'null'. - * - * If your public IP address cannot be determined, you must change the value of Address to your public IP address - * manually to allow clients outside of your LAN to connect to your server. Address can be either an IP address or - * a hostname that will be resolved when RunUO starts. - * - * If you want players outside your LAN to be able to connect to your server and you are behind a router, you must also - * forward TCP port 2593 to your private IP address. The procedure for doing this varies by manufacturer but generally - * involves configuration of the router through your web browser. - * - * ServerList will direct connecting clients depending on both the address they are connecting from and the address and - * port they are connecting to. If it is determined that both ends of a connection are private IP addresses, ServerList - * will direct the client to the local private IP address. If a client is connecting to a local public IP address, they - * will be directed to whichever address and port they initially connected to. This allows multihomed servers to function - * properly and fully supports listening on multiple ports. If a client with a public IP address is connecting to a - * locally private address, the server will direct the client to either the AutoDetected IP address or the manually entered - * IP address or hostname, whichever is applicable. Loopback clients will be directed to loopback. - * - * If you would like to listen on additional ports (i.e. 22, 23, 80, for clients behind highly restrictive egress - * firewalls) or specific IP adddresses you can do so by modifying the file SocketOptions.cs found in this directory. - */ + public class ServerList + { + /* + * The default setting for Address, a value of 'null', will use your local IP address. If all of your local IP addresses + * are private network addresses and AutoDetect is 'true' then RunUO will attempt to discover your public IP address + * for you automatically. + * + * If you do not plan on allowing clients outside of your LAN to connect, you can set AutoDetect to 'false' and leave + * Address set to 'null'. + * + * If your public IP address cannot be determined, you must change the value of Address to your public IP address + * manually to allow clients outside of your LAN to connect to your server. Address can be either an IP address or + * a hostname that will be resolved when RunUO starts. + * + * If you want players outside your LAN to be able to connect to your server and you are behind a router, you must also + * forward TCP port 2593 to your private IP address. The procedure for doing this varies by manufacturer but generally + * involves configuration of the router through your web browser. + * + * ServerList will direct connecting clients depending on both the address they are connecting from and the address and + * port they are connecting to. If it is determined that both ends of a connection are private IP addresses, ServerList + * will direct the client to the local private IP address. If a client is connecting to a local public IP address, they + * will be directed to whichever address and port they initially connected to. This allows multihomed servers to function + * properly and fully supports listening on multiple ports. If a client with a public IP address is connecting to a + * locally private address, the server will direct the client to either the AutoDetected IP address or the manually entered + * IP address or hostname, whichever is applicable. Loopback clients will be directed to loopback. + * + * If you would like to listen on additional ports (i.e. 22, 23, 80, for clients behind highly restrictive egress + * firewalls) or specific IP adddresses you can do so by modifying the file SocketOptions.cs found in this directory. + */ - public static readonly string Address = null; - public static readonly string ServerName = "RunUO TC"; + public static readonly string Address = null; + public static readonly string ServerName = "RunUO TC"; - public static readonly bool AutoDetect = true; + public static readonly bool AutoDetect = true; - public static void Initialize() - { - if ( Address == null ) { - if ( AutoDetect ) - AutoDetection(); - } - else { - Resolve( Address, out m_PublicAddress ); - } + private static IPAddress m_PublicAddress; - EventSink.ServerList += EventSink_ServerList; - } + public static void Initialize() + { + if (Address == null) + { + if (AutoDetect) + AutoDetection(); + } + else + { + Resolve(Address, out m_PublicAddress); + } - private static IPAddress m_PublicAddress; + EventSink.ServerList += EventSink_ServerList; + } - private static void EventSink_ServerList( ServerListEventArgs e ) - { - try - { - NetState ns = e.State; - Socket s = ns.Socket; + private static void EventSink_ServerList(ServerListEventArgs e) + { + try + { + NetState ns = e.State; + Socket s = ns.Socket; - IPEndPoint ipep = (IPEndPoint)s.LocalEndPoint; + IPEndPoint ipep = (IPEndPoint)s.LocalEndPoint; - IPAddress localAddress = ipep.Address; - int localPort = ipep.Port; + IPAddress localAddress = ipep.Address; + int localPort = ipep.Port; - if ( IsPrivateNetwork( localAddress ) ) { - ipep = (IPEndPoint)s.RemoteEndPoint; - if ( !IsPrivateNetwork( ipep.Address ) && m_PublicAddress != null ) - localAddress = m_PublicAddress; - } + if (IsPrivateNetwork(localAddress)) + { + ipep = (IPEndPoint)s.RemoteEndPoint; + if (!IsPrivateNetwork(ipep.Address) && m_PublicAddress != null) + localAddress = m_PublicAddress; + } - e.AddServer( ServerName, new IPEndPoint( localAddress, localPort ) ); - } - catch - { - e.Rejected = true; - } - } + e.AddServer(ServerName, new IPEndPoint(localAddress, localPort)); + } + catch + { + e.Rejected = true; + } + } - private static void AutoDetection() - { - if ( !HasPublicIPAddress() ) { - Console.Write( "ServerList: Auto-detecting public IP address..." ); - m_PublicAddress = FindPublicAddress(); + private static void AutoDetection() + { + if (!HasPublicIPAddress()) + { + Console.Write("ServerList: Auto-detecting public IP address..."); + m_PublicAddress = FindPublicAddress(); - if ( m_PublicAddress != null ) - Console.WriteLine( "done ({0})", m_PublicAddress.ToString() ); - else - Console.WriteLine( "failed" ); - } - } + if (m_PublicAddress != null) + Console.WriteLine("done ({0})", m_PublicAddress); + else + Console.WriteLine("failed"); + } + } - private static void Resolve( string addr, out IPAddress outValue ) - { - if ( IPAddress.TryParse( addr, out outValue ) ) - return; + private static void Resolve(string addr, out IPAddress outValue) + { + if (IPAddress.TryParse(addr, out outValue)) + return; - try { - IPHostEntry iphe = Dns.GetHostEntry( addr ); + try + { + IPHostEntry iphe = Dns.GetHostEntry(addr); - if ( iphe.AddressList.Length > 0 ) - outValue = iphe.AddressList[iphe.AddressList.Length - 1]; - } - catch { - } - } + if (iphe.AddressList.Length > 0) + outValue = iphe.AddressList[iphe.AddressList.Length - 1]; + } + catch + { + } + } - private static bool HasPublicIPAddress() - { - NetworkInterface[] adapters = NetworkInterface.GetAllNetworkInterfaces(); + private static bool HasPublicIPAddress() + { + NetworkInterface[] adapters = NetworkInterface.GetAllNetworkInterfaces(); - foreach ( NetworkInterface adapter in adapters ) { - IPInterfaceProperties properties = adapter.GetIPProperties(); + foreach (NetworkInterface adapter in adapters) + { + IPInterfaceProperties properties = adapter.GetIPProperties(); - foreach ( IPAddressInformation unicast in properties.UnicastAddresses ) { - IPAddress ip = unicast.Address; + foreach (IPAddressInformation unicast in properties.UnicastAddresses) + { + IPAddress ip = unicast.Address; - if ( !IPAddress.IsLoopback( ip ) && ip.AddressFamily != AddressFamily.InterNetworkV6 && !IsPrivateNetwork( ip ) ) - return true; - } - } + if (!IPAddress.IsLoopback(ip) && ip.AddressFamily != AddressFamily.InterNetworkV6 && + !IsPrivateNetwork(ip)) + return true; + } + } - return false; + return false; - /* - IPHostEntry iphe = Dns.GetHostEntry( Dns.GetHostName() ); + /* + IPHostEntry iphe = Dns.GetHostEntry( Dns.GetHostName() ); - IPAddress[] ips = iphe.AddressList; + IPAddress[] ips = iphe.AddressList; - for ( int i = 0; i < ips.Length; ++i ) - { - if ( ips[i].AddressFamily != AddressFamily.InterNetworkV6 && !IsPrivateNetwork( ips[i] ) ) - return true; - } + for ( int i = 0; i < ips.Length; ++i ) + { + if ( ips[i].AddressFamily != AddressFamily.InterNetworkV6 && !IsPrivateNetwork( ips[i] ) ) + return true; + } - return false; - */ - } + return false; + */ + } - private static bool IsPrivateNetwork( IPAddress ip ) - { - // 10.0.0.0/8 - // 172.16.0.0/12 - // 192.168.0.0/16 - // 169.254.0.0/16 - // 100.64.0.0/10 RFC 6598 + private static bool IsPrivateNetwork(IPAddress ip) + { + // 10.0.0.0/8 + // 172.16.0.0/12 + // 192.168.0.0/16 + // 169.254.0.0/16 + // 100.64.0.0/10 RFC 6598 - if ( ip.AddressFamily == AddressFamily.InterNetworkV6 ) - return false; + if (ip.AddressFamily == AddressFamily.InterNetworkV6) + return false; - if ( Utility.IPMatch( "192.168.*", ip ) ) - return true; - if ( Utility.IPMatch( "10.*", ip ) ) - return true; - if ( Utility.IPMatch( "172.16-31.*", ip ) ) - return true; - if ( Utility.IPMatch( "169.254.*", ip ) ) - return true; - if ( Utility.IPMatch( "100.64-127.*", ip ) ) - return true; - return false; - } + if (Utility.IPMatch("192.168.*", ip)) + return true; + if (Utility.IPMatch("10.*", ip)) + return true; + if (Utility.IPMatch("172.16-31.*", ip)) + return true; + if (Utility.IPMatch("169.254.*", ip)) + return true; + if (Utility.IPMatch("100.64-127.*", ip)) + return true; + return false; + } - private static IPAddress FindPublicAddress() - { - try { - WebRequest req = WebRequest.Create( "https://api.ipify.org" ); + private static IPAddress FindPublicAddress() + { + try + { + WebRequest req = WebRequest.Create("https://api.ipify.org"); - req.Timeout = 15000; + req.Timeout = 15000; - WebResponse res = req.GetResponse(); + WebResponse res = req.GetResponse(); - Stream s = res.GetResponseStream(); + Stream s = res.GetResponseStream(); - StreamReader sr = new StreamReader( s ); + StreamReader sr = new StreamReader(s); - IPAddress ip = IPAddress.Parse( sr.ReadLine() ); + IPAddress ip = IPAddress.Parse(sr.ReadLine()); - sr.Close(); - s.Close(); - res.Close(); + sr.Close(); + s.Close(); + res.Close(); - return ip; - } catch { - return null; - } - } - } -} + return ip; + } + catch + { + return null; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/ShardPoller.cs b/Scripts/Misc/ShardPoller.cs index 5d12b392b..6bb1ea099 100644 --- a/Scripts/Misc/ShardPoller.cs +++ b/Scripts/Misc/ShardPoller.cs @@ -1,6 +1,6 @@ using System; -using System.Net; using System.Collections.Generic; +using System.Net; using System.Text.RegularExpressions; using Server.Gumps; using Server.Network; @@ -8,607 +8,612 @@ using Server.Prompts; namespace Server.Misc { - public class ShardPoller : Item - { - private string m_Title; - - private bool m_Active; - - public ShardPollOption[] Options { get; set; } - - public IPAddress[] Addresses { get; set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public string Title - { - get => m_Title; - set => m_Title = ShardPollPrompt.UrlToHref( value ); - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public TimeSpan Duration { get; set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public DateTime StartTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public TimeSpan TimeRemaining - { - get - { - if ( StartTime == DateTime.MinValue || !m_Active ) - return TimeSpan.Zero; - - try - { - TimeSpan ts = (StartTime + Duration) - DateTime.UtcNow; - - if ( ts < TimeSpan.Zero ) - return TimeSpan.Zero; - - return ts; - } - catch - { - return TimeSpan.Zero; - } - } - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public bool Active - { - get => m_Active; - set - { - if ( m_Active == value ) - return; - - m_Active = value; - - if ( m_Active ) - { - StartTime = DateTime.UtcNow; - m_ActivePollers.Add( this ); - } - else - { - m_ActivePollers.Remove( this ); - } - } - } - - public bool HasAlreadyVoted( NetState ns ) - { - for ( int i = 0; i < Options.Length; ++i ) - { - if ( Options[i].HasAlreadyVoted( ns ) ) - return true; - } - - return false; - } - - public void AddVote( NetState ns, ShardPollOption option ) - { - option.AddVote( ns ); - } - - public void RemoveOption( ShardPollOption option ) - { - int index = Array.IndexOf( Options, option ); - - if ( index < 0 ) - return; - - ShardPollOption[] old = Options; - Options = new ShardPollOption[old.Length - 1]; - - for ( int i = 0; i < index; ++i ) - Options[i] = old[i]; - - for ( int i = index; i < Options.Length; ++i ) - Options[i] = old[i + 1]; - } - - public void AddOption( ShardPollOption option ) - { - ShardPollOption[] old = Options; - Options = new ShardPollOption[old.Length + 1]; - - for ( int i = 0; i < old.Length; ++i ) - Options[i] = old[i]; - - Options[old.Length] = option; - } - - public override string DefaultName => "shard poller"; - - [Constructible( AccessLevel.Administrator )] - public ShardPoller() : base( 0x1047 ) - { - Duration = TimeSpan.FromHours( 24.0 ); - Options = new ShardPollOption[0]; - Addresses = new IPAddress[0]; - - Movable = false; - } - - public static void Initialize() - { - EventSink.Login += EventSink_Login; - } - - private static List m_ActivePollers = new List(); - - private static void EventSink_Login( LoginEventArgs e ) - { - if ( m_ActivePollers.Count == 0 ) - return; - - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( EventSink_Login_Callback ), e.Mobile ); - } - - private static void EventSink_Login_Callback( object state ) - { - Mobile from = (Mobile)state; - NetState ns = from.NetState; - - if ( ns == null ) - return; - - ShardPollGump spg = null; - - for ( int i = 0; i < m_ActivePollers.Count; ++i ) - { - ShardPoller poller = m_ActivePollers[i]; - - if ( poller.Deleted || !poller.Active ) - continue; - - if ( poller.TimeRemaining > TimeSpan.Zero ) - { - if ( poller.HasAlreadyVoted( ns ) ) - continue; - - if ( spg == null ) - { - spg = new ShardPollGump( from, poller, false, null ); - from.SendGump( spg ); - } - else - { - spg.QueuePoll( poller ); - } - } - else - { - poller.Active = false; - } - } - } - - public void SendQueuedPoll_Callback( object state ) - { - object[] states = (object[])state; - Mobile from = (Mobile)states[0]; - Queue queue = (Queue)states[1]; - - from.SendGump( new ShardPollGump( from, this, false, queue ) ); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.Administrator ) - from.SendGump( new ShardPollGump( from, this, true, null ) ); - } - - public ShardPoller( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Title ); - writer.Write( Duration ); - writer.Write( StartTime ); - writer.Write( m_Active ); - - writer.Write( Options.Length ); - - for ( int i = 0; i < Options.Length; ++i ) - Options[i].Serialize( writer ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Title = reader.ReadString(); - Duration = reader.ReadTimeSpan(); - StartTime = reader.ReadDateTime(); - m_Active = reader.ReadBool(); - - Options = new ShardPollOption[reader.ReadInt()]; - - for ( int i = 0; i < Options.Length; ++i ) - Options[i] = new ShardPollOption( reader ); - - if ( m_Active ) - m_ActivePollers.Add( this ); - - break; - } - } - } - - public override void OnDelete() - { - base.OnDelete(); - - Active = false; - } - } - - public class ShardPollOption - { - private string m_Title; - - public string Title{ get => m_Title; - set{ m_Title = value; LineBreaks = GetBreaks( m_Title ); } } - public int LineBreaks { get; private set; } - - public int Votes => Voters.Length; - public IPAddress[] Voters { get; set; } - - public ShardPollOption( string title ) - { - m_Title = title; - LineBreaks = GetBreaks( m_Title ); - Voters = new IPAddress[0]; - } - - public bool HasAlreadyVoted( NetState ns ) - { - if ( ns == null ) - return false; + public class ShardPoller : Item + { + private static List m_ActivePollers = new List(); + + private bool m_Active; + private string m_Title; + + [Constructible(AccessLevel.Administrator)] + public ShardPoller() : base(0x1047) + { + Duration = TimeSpan.FromHours(24.0); + Options = new ShardPollOption[0]; + Addresses = new IPAddress[0]; + + Movable = false; + } + + public ShardPoller(Serial serial) : base(serial) + { + } + + public ShardPollOption[] Options{ get; set; } + + public IPAddress[] Addresses{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public string Title + { + get => m_Title; + set => m_Title = ShardPollPrompt.UrlToHref(value); + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public TimeSpan Duration{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public DateTime StartTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public TimeSpan TimeRemaining + { + get + { + if (StartTime == DateTime.MinValue || !m_Active) + return TimeSpan.Zero; + + try + { + TimeSpan ts = StartTime + Duration - DateTime.UtcNow; + + if (ts < TimeSpan.Zero) + return TimeSpan.Zero; + + return ts; + } + catch + { + return TimeSpan.Zero; + } + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public bool Active + { + get => m_Active; + set + { + if (m_Active == value) + return; + + m_Active = value; + + if (m_Active) + { + StartTime = DateTime.UtcNow; + m_ActivePollers.Add(this); + } + else + { + m_ActivePollers.Remove(this); + } + } + } + + public override string DefaultName => "shard poller"; + + public bool HasAlreadyVoted(NetState ns) + { + for (int i = 0; i < Options.Length; ++i) + if (Options[i].HasAlreadyVoted(ns)) + return true; + + return false; + } + + public void AddVote(NetState ns, ShardPollOption option) + { + option.AddVote(ns); + } + + public void RemoveOption(ShardPollOption option) + { + int index = Array.IndexOf(Options, option); + + if (index < 0) + return; + + ShardPollOption[] old = Options; + Options = new ShardPollOption[old.Length - 1]; + + for (int i = 0; i < index; ++i) + Options[i] = old[i]; + + for (int i = index; i < Options.Length; ++i) + Options[i] = old[i + 1]; + } + + public void AddOption(ShardPollOption option) + { + ShardPollOption[] old = Options; + Options = new ShardPollOption[old.Length + 1]; + + for (int i = 0; i < old.Length; ++i) + Options[i] = old[i]; + + Options[old.Length] = option; + } + + public static void Initialize() + { + EventSink.Login += EventSink_Login; + } + + private static void EventSink_Login(LoginEventArgs e) + { + if (m_ActivePollers.Count == 0) + return; + + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(EventSink_Login_Callback), e.Mobile); + } + + private static void EventSink_Login_Callback(object state) + { + Mobile from = (Mobile)state; + NetState ns = from.NetState; + + if (ns == null) + return; + + ShardPollGump spg = null; + + for (int i = 0; i < m_ActivePollers.Count; ++i) + { + ShardPoller poller = m_ActivePollers[i]; + + if (poller.Deleted || !poller.Active) + continue; + + if (poller.TimeRemaining > TimeSpan.Zero) + { + if (poller.HasAlreadyVoted(ns)) + continue; + + if (spg == null) + { + spg = new ShardPollGump(from, poller, false, null); + from.SendGump(spg); + } + else + { + spg.QueuePoll(poller); + } + } + else + { + poller.Active = false; + } + } + } + + public void SendQueuedPoll_Callback(object state) + { + object[] states = (object[])state; + Mobile from = (Mobile)states[0]; + Queue queue = (Queue)states[1]; + + from.SendGump(new ShardPollGump(from, this, false, queue)); + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.Administrator) + from.SendGump(new ShardPollGump(from, this, true, null)); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Title); + writer.Write(Duration); + writer.Write(StartTime); + writer.Write(m_Active); + + writer.Write(Options.Length); + + for (int i = 0; i < Options.Length; ++i) + Options[i].Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Title = reader.ReadString(); + Duration = reader.ReadTimeSpan(); + StartTime = reader.ReadDateTime(); + m_Active = reader.ReadBool(); + + Options = new ShardPollOption[reader.ReadInt()]; + + for (int i = 0; i < Options.Length; ++i) + Options[i] = new ShardPollOption(reader); + + if (m_Active) + m_ActivePollers.Add(this); + + break; + } + } + } + + public override void OnDelete() + { + base.OnDelete(); + + Active = false; + } + } + + public class ShardPollOption + { + private string m_Title; + + public ShardPollOption(string title) + { + m_Title = title; + LineBreaks = GetBreaks(m_Title); + Voters = new IPAddress[0]; + } + + public ShardPollOption(GenericReader reader) + { + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Title = reader.ReadString(); + LineBreaks = GetBreaks(m_Title); + + Voters = new IPAddress[reader.ReadInt()]; + + for (int i = 0; i < Voters.Length; ++i) + Voters[i] = Utility.Intern(reader.ReadIPAddress()); + + break; + } + } + } - IPAddress ipAddress = ns.Address; + public string Title + { + get => m_Title; + set + { + m_Title = value; + LineBreaks = GetBreaks(m_Title); + } + } - for ( int i = 0; i < Voters.Length; ++i ) - { - if ( Utility.IPMatchClassC( Voters[i], ipAddress ) ) - return true; - } + public int LineBreaks{ get; private set; } - return false; - } + public int Votes => Voters.Length; + public IPAddress[] Voters{ get; set; } - public void AddVote( NetState ns ) - { - if ( ns == null ) - return; + public bool HasAlreadyVoted(NetState ns) + { + if (ns == null) + return false; - IPAddress[] old = Voters; - Voters = new IPAddress[old.Length + 1]; + IPAddress ipAddress = ns.Address; - for ( int i = 0; i < old.Length; ++i ) - Voters[i] = old[i]; + for (int i = 0; i < Voters.Length; ++i) + if (Utility.IPMatchClassC(Voters[i], ipAddress)) + return true; - Voters[old.Length] = ns.Address; - } + return false; + } - public int ComputeHeight() - { - int height = LineBreaks * 18; + public void AddVote(NetState ns) + { + if (ns == null) + return; - if ( height > 30 ) - return height; + IPAddress[] old = Voters; + Voters = new IPAddress[old.Length + 1]; - return 30; - } + for (int i = 0; i < old.Length; ++i) + Voters[i] = old[i]; - public int GetBreaks( string title ) - { - if ( title == null ) - return 1; + Voters[old.Length] = ns.Address; + } - int count = 0; - int index = -1; + public int ComputeHeight() + { + int height = LineBreaks * 18; - do - { - ++count; - index = title.IndexOf( "
", index + 1 ); - } while ( index >= 0 ); + if (height > 30) + return height; - return count; - } + return 30; + } - public ShardPollOption( GenericReader reader ) - { - int version = reader.ReadInt(); + public int GetBreaks(string title) + { + if (title == null) + return 1; - switch ( version ) - { - case 0: - { - m_Title = reader.ReadString(); - LineBreaks = GetBreaks( m_Title ); + int count = 0; + int index = -1; - Voters = new IPAddress[reader.ReadInt()]; + do + { + ++count; + index = title.IndexOf("
", index + 1); + } while (index >= 0); - for ( int i = 0; i < Voters.Length; ++i ) - Voters[i] = Utility.Intern( reader.ReadIPAddress() ); + return count; + } - break; - } - } - } + public void Serialize(GenericWriter writer) + { + writer.Write(0); // version - public void Serialize( GenericWriter writer ) - { - writer.Write( (int) 0 ); // version + writer.Write(m_Title); - writer.Write( m_Title ); + writer.Write(Voters.Length); - writer.Write( Voters.Length ); + for (int i = 0; i < Voters.Length; ++i) + writer.Write(Voters[i]); + } + } - for ( int i = 0; i < Voters.Length; ++i ) - writer.Write( Voters[i] ); - } - } + public class ShardPollGump : Gump + { + private const int LabelColor32 = 0xFFFFFF; + private Mobile m_From; + private ShardPoller m_Poller; + private Queue m_Polls; - public class ShardPollGump : Gump - { - private Mobile m_From; - private ShardPoller m_Poller; - private Queue m_Polls; + public ShardPollGump(Mobile from, ShardPoller poller, bool editing, Queue polls) : base(50, 50) + { + m_From = from; + m_Poller = poller; + Editing = editing; + m_Polls = polls; - public bool Editing { get; } + Closable = false; - public void QueuePoll( ShardPoller poller ) - { - if ( m_Polls == null ) - m_Polls = new Queue( 4 ); + AddPage(0); - m_Polls.Enqueue( poller ); - } + int totalVotes = 0; + int totalOptionHeight = 0; - public string Center( string text ) - { - return $"
{text}
"; - } + for (int i = 0; i < poller.Options.Length; ++i) + { + totalVotes += poller.Options[i].Votes; + totalOptionHeight += poller.Options[i].ComputeHeight() + 5; + } - public string Color( string text, int color ) - { - return $"{text}"; - } + bool isViewingResults = editing && poller.Active; + bool isCompleted = totalVotes > 0 && !poller.Active; - private const int LabelColor32 = 0xFFFFFF; + if (editing && !isViewingResults) + totalOptionHeight += 35; - public ShardPollGump( Mobile from, ShardPoller poller, bool editing, Queue polls ) : base( 50, 50 ) - { - m_From = from; - m_Poller = poller; - Editing = editing; - m_Polls = polls; + int height = 115 + totalOptionHeight; - Closable = false; + AddBackground(1, 1, 398, height - 2, 3600); + AddAlphaRegion(16, 15, 369, height - 31); - AddPage( 0 ); + AddItem(308, 30, 0x1E5E); - int totalVotes = 0; - int totalOptionHeight = 0; + string title; - for ( int i = 0; i < poller.Options.Length; ++i ) - { - totalVotes += poller.Options[i].Votes; - totalOptionHeight += poller.Options[i].ComputeHeight() + 5; - } + if (editing) + title = isCompleted ? "Poll Completed" : "Poll Editor"; + else + title = "Shard Poll"; - bool isViewingResults = editing && poller.Active; - bool isCompleted = totalVotes > 0 && !poller.Active; + AddHtml(22, 22, 294, 20, Color(Center(title), LabelColor32), false, false); - if ( editing && !isViewingResults ) - totalOptionHeight += 35; + if (editing) + { + AddHtml(22, 22, 294, 20, Color($"{totalVotes} total", LabelColor32), false, false); + AddButton(287, 23, 0x2622, 0x2623, 2, GumpButtonType.Reply, 0); + } - int height = 115 + totalOptionHeight; + AddHtml(22, 50, 294, 40, Color(poller.Title, 0x99CC66), false, false); - AddBackground( 1, 1, 398, height - 2, 3600 ); - AddAlphaRegion( 16, 15, 369, height - 31 ); + AddImageTiled(32, 88, 264, 1, 9107); + AddImageTiled(42, 90, 264, 1, 9157); - AddItem( 308, 30, 0x1E5E ); + int y = 100; - string title; + for (int i = 0; i < poller.Options.Length; ++i) + { + ShardPollOption option = poller.Options[i]; + string text = option.Title; - if ( editing ) - title = ( isCompleted ? "Poll Completed" : "Poll Editor" ); - else - title = "Shard Poll"; - - AddHtml( 22, 22, 294, 20, Color( Center( title ), LabelColor32 ), false, false ); - - if ( editing ) - { - AddHtml( 22, 22, 294, 20, Color($"{totalVotes} total", LabelColor32 ), false, false ); - AddButton( 287, 23, 0x2622, 0x2623, 2, GumpButtonType.Reply, 0 ); - } - - AddHtml( 22, 50, 294, 40, Color( poller.Title, 0x99CC66 ), false, false ); - - AddImageTiled( 32, 88, 264, 1, 9107 ); - AddImageTiled( 42, 90, 264, 1, 9157 ); - - int y = 100; - - for ( int i = 0; i < poller.Options.Length; ++i ) - { - ShardPollOption option = poller.Options[i]; - string text = option.Title; - - if ( editing && totalVotes > 0 ) - { - double perc = option.Votes / (double)totalVotes; - - text = string.Format( "[{1}: {2}%] {0}", text, option.Votes, (int)(perc*100) ); - } - - int optHeight = option.ComputeHeight(); - - y += optHeight/2; - - if ( isViewingResults ) - AddImage( 24, y - 15, 0x25FE ); - else - AddRadio( 24, y - 15, 0x25F9, 0x25FC, false, 1 + i ); - - AddHtml( 60, y - (9 * option.LineBreaks), 250, 18 * option.LineBreaks, Color( text, LabelColor32 ), false, false ); - - y += optHeight/2; - y += 5; - } - - if ( editing && !isViewingResults ) - { - AddRadio( 24, y + 15 - 15, 0x25F9, 0x25FC, false, 1 + poller.Options.Length ); - AddHtml( 60, y + 15 - 9, 250, 18, Color( "Create new option.", 0x99CC66 ), false, false ); - } - - AddButton( 314, height - 73, 247, 248, 1, GumpButtonType.Reply, 0 ); - AddButton( 314, height - 47, 242, 241, 0, GumpButtonType.Reply, 0 ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_Polls != null && m_Polls.Count > 0 ) - { - ShardPoller poller = m_Polls.Dequeue(); - - if ( poller != null ) - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( poller.SendQueuedPoll_Callback ), new object[]{ m_From, m_Polls } ); - } - - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; - - if ( switches.Length == 0 ) - return; - - int switched = switches[0] - 1; - ShardPollOption opt = null; - - if ( switched >= 0 && switched < m_Poller.Options.Length ) - opt = m_Poller.Options[switched]; - - if ( opt == null && !Editing ) - return; - - if ( Editing ) - { - if ( !m_Poller.Active ) - { - m_From.SendMessage( "Enter a title for the option. Escape to cancel.{0}", opt == null ? "" : " Use \"DEL\" to delete." ); - m_From.Prompt = new ShardPollPrompt( m_Poller, opt ); - } - else - { - m_From.SendMessage( "You may not edit an active poll. Deactivate it first." ); - m_From.SendGump( new ShardPollGump( m_From, m_Poller, Editing, m_Polls ) ); - } - } - else - { - if ( !m_Poller.Active ) - m_From.SendMessage( "The poll has been deactivated." ); - else if ( m_Poller.HasAlreadyVoted( sender ) ) - m_From.SendMessage( "You have already voted on this poll." ); - else - m_Poller.AddVote( sender, opt ); - } - } - else if ( info.ButtonID == 2 && Editing ) - { - m_From.SendGump( new ShardPollGump( m_From, m_Poller, Editing, m_Polls ) ); - m_From.SendGump( new PropertiesGump( m_From, m_Poller ) ); - } - } - } - - public class ShardPollPrompt : Prompt - { - private ShardPoller m_Poller; - private ShardPollOption m_Option; - - public ShardPollPrompt( ShardPoller poller, ShardPollOption opt ) - { - m_Poller = poller; - m_Option = opt; - } - - public override void OnCancel( Mobile from ) - { - from.SendGump( new ShardPollGump( from, m_Poller, true, null ) ); - } - - private static Regex m_UrlRegex = new Regex( @"\[url(?:=(.*?))?\](.*?)\[/url\]", RegexOptions.IgnoreCase | RegexOptions.Compiled ); - - private static string UrlRegex_Match( Match m ) - { - if ( m.Groups[1].Success ) - { - if ( m.Groups[2].Success ) - return $"{m.Groups[2].Value}"; - } - else if ( m.Groups[2].Success ) - { - return string.Format( "{0}", m.Groups[2].Value ); - } - - return m.Value; - } - - public static string UrlToHref( string text ) - { - if ( text == null ) - return null; - - return m_UrlRegex.Replace( text, UrlRegex_Match ); - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Poller.Active ) - { - from.SendMessage( "You may not edit an active poll. Deactivate it first." ); - } - else if ( text == "DEL" ) - { - if ( m_Option != null ) - m_Poller.RemoveOption( m_Option ); - } - else - { - text = UrlToHref( text ); - - if ( m_Option == null ) - m_Poller.AddOption( new ShardPollOption( text ) ); - else - m_Option.Title = text; - } - - from.SendGump( new ShardPollGump( from, m_Poller, true, null ) ); - } - } + if (editing && totalVotes > 0) + { + double perc = option.Votes / (double)totalVotes; + + text = string.Format("[{1}: {2}%] {0}", text, option.Votes, (int)(perc * 100)); + } + + int optHeight = option.ComputeHeight(); + + y += optHeight / 2; + + if (isViewingResults) + AddImage(24, y - 15, 0x25FE); + else + AddRadio(24, y - 15, 0x25F9, 0x25FC, false, 1 + i); + + AddHtml(60, y - 9 * option.LineBreaks, 250, 18 * option.LineBreaks, Color(text, LabelColor32), false, false); + + y += optHeight / 2; + y += 5; + } + + if (editing && !isViewingResults) + { + AddRadio(24, y + 15 - 15, 0x25F9, 0x25FC, false, 1 + poller.Options.Length); + AddHtml(60, y + 15 - 9, 250, 18, Color("Create new option.", 0x99CC66), false, false); + } + + AddButton(314, height - 73, 247, 248, 1, GumpButtonType.Reply, 0); + AddButton(314, height - 47, 242, 241, 0, GumpButtonType.Reply, 0); + } + + public bool Editing{ get; } + + public void QueuePoll(ShardPoller poller) + { + if (m_Polls == null) + m_Polls = new Queue(4); + + m_Polls.Enqueue(poller); + } + + public string Center(string text) + { + return $"
{text}
"; + } + + public string Color(string text, int color) + { + return $"{text}"; + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_Polls != null && m_Polls.Count > 0) + { + ShardPoller poller = m_Polls.Dequeue(); + + if (poller != null) + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(poller.SendQueuedPoll_Callback), + new object[] { m_From, m_Polls }); + } + + if (info.ButtonID == 1) + { + int[] switches = info.Switches; + + if (switches.Length == 0) + return; + + int switched = switches[0] - 1; + ShardPollOption opt = null; + + if (switched >= 0 && switched < m_Poller.Options.Length) + opt = m_Poller.Options[switched]; + + if (opt == null && !Editing) + return; + + if (Editing) + { + if (!m_Poller.Active) + { + m_From.SendMessage("Enter a title for the option. Escape to cancel.{0}", + opt == null ? "" : " Use \"DEL\" to delete."); + m_From.Prompt = new ShardPollPrompt(m_Poller, opt); + } + else + { + m_From.SendMessage("You may not edit an active poll. Deactivate it first."); + m_From.SendGump(new ShardPollGump(m_From, m_Poller, Editing, m_Polls)); + } + } + else + { + if (!m_Poller.Active) + m_From.SendMessage("The poll has been deactivated."); + else if (m_Poller.HasAlreadyVoted(sender)) + m_From.SendMessage("You have already voted on this poll."); + else + m_Poller.AddVote(sender, opt); + } + } + else if (info.ButtonID == 2 && Editing) + { + m_From.SendGump(new ShardPollGump(m_From, m_Poller, Editing, m_Polls)); + m_From.SendGump(new PropertiesGump(m_From, m_Poller)); + } + } + } + + public class ShardPollPrompt : Prompt + { + private static Regex m_UrlRegex = + new Regex(@"\[url(?:=(.*?))?\](.*?)\[/url\]", RegexOptions.IgnoreCase | RegexOptions.Compiled); + + private ShardPollOption m_Option; + private ShardPoller m_Poller; + + public ShardPollPrompt(ShardPoller poller, ShardPollOption opt) + { + m_Poller = poller; + m_Option = opt; + } + + public override void OnCancel(Mobile from) + { + from.SendGump(new ShardPollGump(from, m_Poller, true, null)); + } + + private static string UrlRegex_Match(Match m) + { + if (m.Groups[1].Success) + { + if (m.Groups[2].Success) + return $"{m.Groups[2].Value}"; + } + else if (m.Groups[2].Success) + { + return string.Format("{0}", m.Groups[2].Value); + } + + return m.Value; + } + + public static string UrlToHref(string text) + { + if (text == null) + return null; + + return m_UrlRegex.Replace(text, UrlRegex_Match); + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Poller.Active) + { + from.SendMessage("You may not edit an active poll. Deactivate it first."); + } + else if (text == "DEL") + { + if (m_Option != null) + m_Poller.RemoveOption(m_Option); + } + else + { + text = UrlToHref(text); + + if (m_Option == null) + m_Poller.AddOption(new ShardPollOption(text)); + else + m_Option.Title = text; + } + + from.SendGump(new ShardPollGump(from, m_Poller, true, null)); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/ShrinkTable.cs b/Scripts/Misc/ShrinkTable.cs index 0de200297..3876d2401 100644 --- a/Scripts/Misc/ShrinkTable.cs +++ b/Scripts/Misc/ShrinkTable.cs @@ -2,84 +2,84 @@ using System.IO; namespace Server { - public class ShrinkTable - { - public const int DefaultItemID = 0x1870; // Yellow virtue stone + public class ShrinkTable + { + public const int DefaultItemID = 0x1870; // Yellow virtue stone - private static int[] m_Table; + private static int[] m_Table; - public static int Lookup( Mobile m ) - { - return Lookup( m.Body.BodyID, DefaultItemID ); - } + public static int Lookup(Mobile m) + { + return Lookup(m.Body.BodyID, DefaultItemID); + } - public static int Lookup( int body ) - { - return Lookup( body, DefaultItemID ); - } + public static int Lookup(int body) + { + return Lookup(body, DefaultItemID); + } - public static int Lookup( Mobile m, int defaultValue ) - { - return Lookup( m.Body.BodyID, defaultValue ); - } + public static int Lookup(Mobile m, int defaultValue) + { + return Lookup(m.Body.BodyID, defaultValue); + } - public static int Lookup( int body, int defaultValue ) - { - if ( m_Table == null ) - Load(); + public static int Lookup(int body, int defaultValue) + { + if (m_Table == null) + Load(); - int val = 0; + int val = 0; - if ( body >= 0 && body < m_Table.Length ) - val = m_Table[body]; + if (body >= 0 && body < m_Table.Length) + val = m_Table[body]; - if ( val == 0 ) - val = defaultValue; + if (val == 0) + val = defaultValue; - return val; - } + return val; + } - private static void Load() - { - string path = Path.Combine( Core.BaseDirectory, "Data/shrink.cfg" ); + private static void Load() + { + string path = Path.Combine(Core.BaseDirectory, "Data/shrink.cfg"); - if ( !File.Exists( path ) ) - { - m_Table = new int[0]; - return; - } + if (!File.Exists(path)) + { + m_Table = new int[0]; + return; + } - m_Table = new int[1000]; + m_Table = new int[1000]; - using ( StreamReader ip = new StreamReader( path ) ) - { - string line; + using (StreamReader ip = new StreamReader(path)) + { + string line; - while ( (line = ip.ReadLine()) != null ) - { - line = line.Trim(); + while ((line = ip.ReadLine()) != null) + { + line = line.Trim(); - if ( line.Length == 0 || line.StartsWith( "#" ) ) - continue; + if (line.Length == 0 || line.StartsWith("#")) + continue; - try - { - string[] split = line.Split( '\t' ); + try + { + string[] split = line.Split('\t'); - if ( split.Length >= 2 ) - { - int body = Utility.ToInt32( split[0] ); - int item = Utility.ToInt32( split[1] ); + if (split.Length >= 2) + { + int body = Utility.ToInt32(split[0]); + int item = Utility.ToInt32(split[1]); - if ( body >= 0 && body < m_Table.Length ) - m_Table[body] = item; - } - } - catch - { - } - } - } - } - } + if (body >= 0 && body < m_Table.Length) + m_Table[body] = item; + } + } + catch + { + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Misc/SkillCheck.cs b/Scripts/Misc/SkillCheck.cs index 91da3637f..482750c38 100644 --- a/Scripts/Misc/SkillCheck.cs +++ b/Scripts/Misc/SkillCheck.cs @@ -1,386 +1,402 @@ using System; -using Server.Mobiles; using Server.Factions; +using Server.Mobiles; +using Server.Regions; namespace Server.Misc { - public class SkillCheck - { - private static readonly bool AntiMacroCode = !Core.ML; //Change this to false to disable anti-macro code - - public static TimeSpan AntiMacroExpire = TimeSpan.FromMinutes( 5.0 ); //How long do we remember targets/locations? - public const int Allowance = 3; //How many times may we use the same location/target for gain - private const int LocationSize = 5; //The size of eeach location, make this smaller so players dont have to move as far - private static bool[] UseAntiMacro = { - // true if this skill uses the anti-macro code, false if it does not - false,// Alchemy = 0, - true,// Anatomy = 1, - true,// AnimalLore = 2, - true,// ItemID = 3, - true,// ArmsLore = 4, - false,// Parry = 5, - true,// Begging = 6, - false,// Blacksmith = 7, - false,// Fletching = 8, - true,// Peacemaking = 9, - true,// Camping = 10, - false,// Carpentry = 11, - false,// Cartography = 12, - false,// Cooking = 13, - true,// DetectHidden = 14, - true,// Discordance = 15, - true,// EvalInt = 16, - true,// Healing = 17, - true,// Fishing = 18, - true,// Forensics = 19, - true,// Herding = 20, - true,// Hiding = 21, - true,// Provocation = 22, - false,// Inscribe = 23, - true,// Lockpicking = 24, - true,// Magery = 25, - true,// MagicResist = 26, - false,// Tactics = 27, - true,// Snooping = 28, - true,// Musicianship = 29, - true,// Poisoning = 30, - false,// Archery = 31, - true,// SpiritSpeak = 32, - true,// Stealing = 33, - false,// Tailoring = 34, - true,// AnimalTaming = 35, - true,// TasteID = 36, - false,// Tinkering = 37, - true,// Tracking = 38, - true,// Veterinary = 39, - false,// Swords = 40, - false,// Macing = 41, - false,// Fencing = 42, - false,// Wrestling = 43, - true,// Lumberjacking = 44, - true,// Mining = 45, - true,// Meditation = 46, - true,// Stealth = 47, - true,// RemoveTrap = 48, - true,// Necromancy = 49, - false,// Focus = 50, - true,// Chivalry = 51 - true,// Bushido = 52 - true,//Ninjitsu = 53 - true // Spellweaving - }; - - public static void Initialize() - { - Mobile.SkillCheckLocationHandler = Mobile_SkillCheckLocation; - Mobile.SkillCheckDirectLocationHandler = Mobile_SkillCheckDirectLocation; - - Mobile.SkillCheckTargetHandler = Mobile_SkillCheckTarget; - Mobile.SkillCheckDirectTargetHandler = Mobile_SkillCheckDirectTarget; - } - - public static bool Mobile_SkillCheckLocation( Mobile from, SkillName skillName, double minSkill, double maxSkill ) - { - Skill skill = from.Skills[skillName]; - - if ( skill == null ) - return false; - - double value = skill.Value; - - if ( value < minSkill ) - return false; // Too difficult - if ( value >= maxSkill ) - return true; // No challenge - - double chance = (value - minSkill) / (maxSkill - minSkill); - - Point2D loc = new Point2D( from.Location.X / LocationSize, from.Location.Y / LocationSize ); - return CheckSkill( from, skill, loc, chance ); - } - - public static bool Mobile_SkillCheckDirectLocation( Mobile from, SkillName skillName, double chance ) - { - Skill skill = from.Skills[skillName]; - - if ( skill == null ) - return false; - - if ( chance < 0.0 ) - return false; // Too difficult - if ( chance >= 1.0 ) - return true; // No challenge - - Point2D loc = new Point2D( from.Location.X / LocationSize, from.Location.Y / LocationSize ); - return CheckSkill( from, skill, loc, chance ); - } - - public static bool CheckSkill( Mobile from, Skill skill, object amObj, double chance ) - { - if ( from.Skills.Cap == 0 ) - return false; - - bool success = ( chance >= Utility.RandomDouble() ); - double gc = (double)(from.Skills.Cap - from.Skills.Total) / from.Skills.Cap; - gc += ( skill.Cap - skill.Base ) / skill.Cap; - gc /= 2; - - gc += ( 1.0 - chance ) * ( success ? 0.5 : (Core.AOS ? 0.0 : 0.2) ); - gc /= 2; - - gc *= skill.Info.GainFactor; - - if ( gc < 0.01 ) - gc = 0.01; - - if ( from is BaseCreature creature && creature.Controlled ) - gc *= 2; - - if ( from.Alive && ( ( gc >= Utility.RandomDouble() && AllowGain( from, skill, amObj ) ) || skill.Base < 10.0 ) ) - Gain( from, skill ); - - return success; - } - - public static bool Mobile_SkillCheckTarget( Mobile from, SkillName skillName, object target, double minSkill, double maxSkill ) - { - Skill skill = from.Skills[skillName]; - - if ( skill == null ) - return false; - - double value = skill.Value; - - if ( value < minSkill ) - return false; // Too difficult - if ( value >= maxSkill ) - return true; // No challenge - - double chance = (value - minSkill) / (maxSkill - minSkill); - - return CheckSkill( from, skill, target, chance ); - } + public class SkillCheck + { + public enum Stat + { + Str, + Dex, + Int + } + + public const int Allowance = 3; //How many times may we use the same location/target for gain + + private const int + LocationSize = 5; //The size of eeach location, make this smaller so players dont have to move as far + + private static readonly bool AntiMacroCode = !Core.ML; //Change this to false to disable anti-macro code + + public static TimeSpan AntiMacroExpire = TimeSpan.FromMinutes(5.0); //How long do we remember targets/locations? + + private static bool[] UseAntiMacro = + { + // true if this skill uses the anti-macro code, false if it does not + false, // Alchemy = 0, + true, // Anatomy = 1, + true, // AnimalLore = 2, + true, // ItemID = 3, + true, // ArmsLore = 4, + false, // Parry = 5, + true, // Begging = 6, + false, // Blacksmith = 7, + false, // Fletching = 8, + true, // Peacemaking = 9, + true, // Camping = 10, + false, // Carpentry = 11, + false, // Cartography = 12, + false, // Cooking = 13, + true, // DetectHidden = 14, + true, // Discordance = 15, + true, // EvalInt = 16, + true, // Healing = 17, + true, // Fishing = 18, + true, // Forensics = 19, + true, // Herding = 20, + true, // Hiding = 21, + true, // Provocation = 22, + false, // Inscribe = 23, + true, // Lockpicking = 24, + true, // Magery = 25, + true, // MagicResist = 26, + false, // Tactics = 27, + true, // Snooping = 28, + true, // Musicianship = 29, + true, // Poisoning = 30, + false, // Archery = 31, + true, // SpiritSpeak = 32, + true, // Stealing = 33, + false, // Tailoring = 34, + true, // AnimalTaming = 35, + true, // TasteID = 36, + false, // Tinkering = 37, + true, // Tracking = 38, + true, // Veterinary = 39, + false, // Swords = 40, + false, // Macing = 41, + false, // Fencing = 42, + false, // Wrestling = 43, + true, // Lumberjacking = 44, + true, // Mining = 45, + true, // Meditation = 46, + true, // Stealth = 47, + true, // RemoveTrap = 48, + true, // Necromancy = 49, + false, // Focus = 50, + true, // Chivalry = 51 + true, // Bushido = 52 + true, //Ninjitsu = 53 + true // Spellweaving + }; + + private static TimeSpan m_StatGainDelay = TimeSpan.FromMinutes(Core.ML ? 0.05 : 15); + private static TimeSpan m_PetStatGainDelay = TimeSpan.FromMinutes(5.0); + + public static void Initialize() + { + Mobile.SkillCheckLocationHandler = Mobile_SkillCheckLocation; + Mobile.SkillCheckDirectLocationHandler = Mobile_SkillCheckDirectLocation; + + Mobile.SkillCheckTargetHandler = Mobile_SkillCheckTarget; + Mobile.SkillCheckDirectTargetHandler = Mobile_SkillCheckDirectTarget; + } + + public static bool Mobile_SkillCheckLocation(Mobile from, SkillName skillName, double minSkill, double maxSkill) + { + Skill skill = from.Skills[skillName]; + + if (skill == null) + return false; + + double value = skill.Value; + + if (value < minSkill) + return false; // Too difficult + if (value >= maxSkill) + return true; // No challenge + + double chance = (value - minSkill) / (maxSkill - minSkill); + + Point2D loc = new Point2D(from.Location.X / LocationSize, from.Location.Y / LocationSize); + return CheckSkill(from, skill, loc, chance); + } + + public static bool Mobile_SkillCheckDirectLocation(Mobile from, SkillName skillName, double chance) + { + Skill skill = from.Skills[skillName]; + + if (skill == null) + return false; + + if (chance < 0.0) + return false; // Too difficult + if (chance >= 1.0) + return true; // No challenge + + Point2D loc = new Point2D(from.Location.X / LocationSize, from.Location.Y / LocationSize); + return CheckSkill(from, skill, loc, chance); + } + + public static bool CheckSkill(Mobile from, Skill skill, object amObj, double chance) + { + if (from.Skills.Cap == 0) + return false; + + bool success = chance >= Utility.RandomDouble(); + double gc = (double)(from.Skills.Cap - from.Skills.Total) / from.Skills.Cap; + gc += (skill.Cap - skill.Base) / skill.Cap; + gc /= 2; + + gc += (1.0 - chance) * (success ? 0.5 : Core.AOS ? 0.0 : 0.2); + gc /= 2; + + gc *= skill.Info.GainFactor; + + if (gc < 0.01) + gc = 0.01; + + if (from is BaseCreature creature && creature.Controlled) + gc *= 2; + + if (from.Alive && (gc >= Utility.RandomDouble() && AllowGain(from, skill, amObj) || skill.Base < 10.0)) + Gain(from, skill); + + return success; + } + + public static bool Mobile_SkillCheckTarget(Mobile from, SkillName skillName, object target, double minSkill, + double maxSkill) + { + Skill skill = from.Skills[skillName]; + + if (skill == null) + return false; + + double value = skill.Value; + + if (value < minSkill) + return false; // Too difficult + if (value >= maxSkill) + return true; // No challenge - public static bool Mobile_SkillCheckDirectTarget( Mobile from, SkillName skillName, object target, double chance ) - { - Skill skill = from.Skills[skillName]; + double chance = (value - minSkill) / (maxSkill - minSkill); - if ( skill == null ) - return false; + return CheckSkill(from, skill, target, chance); + } - if ( chance < 0.0 ) - return false; // Too difficult - if ( chance >= 1.0 ) - return true; // No challenge + public static bool Mobile_SkillCheckDirectTarget(Mobile from, SkillName skillName, object target, double chance) + { + Skill skill = from.Skills[skillName]; - return CheckSkill( from, skill, target, chance ); - } + if (skill == null) + return false; - private static bool AllowGain( Mobile from, Skill skill, object obj ) - { - if ( Core.AOS && Faction.InSkillLoss( from ) ) //Changed some time between the introduction of AoS and SE. - return false; + if (chance < 0.0) + return false; // Too difficult + if (chance >= 1.0) + return true; // No challenge - if ( AntiMacroCode && from is PlayerMobile mobile && UseAntiMacro[skill.Info.SkillID] ) - return mobile.AntiMacroCheck( skill, obj ); + return CheckSkill(from, skill, target, chance); + } - return true; - } - - public enum Stat { Str, Dex, Int } - - public static void Gain( Mobile from, Skill skill ) - { - if ( from.Region.IsPartOf( typeof( Regions.Jail ) ) ) - return; - - if ( from is BaseCreature creature && creature.IsDeadPet ) - return; - - if ( skill.SkillName == SkillName.Focus && from is BaseCreature ) - return; - - if ( skill.Base < skill.Cap && skill.Lock == SkillLock.Up ) - { - int toGain = 1; - - if ( skill.Base <= 10.0 ) - toGain = Utility.Random( 4 ) + 1; - - Skills skills = from.Skills; - - if ( from.Player && ( skills.Total / skills.Cap ) >= Utility.RandomDouble() )//( skills.Total >= skills.Cap ) - { - for ( int i = 0; i < skills.Length; ++i ) - { - Skill toLower = skills[i]; - - if ( toLower != skill && toLower.Lock == SkillLock.Down && toLower.BaseFixedPoint >= toGain ) - { - toLower.BaseFixedPoint -= toGain; - break; - } - } - } - - #region Scroll of Alacrity - - if ( from is PlayerMobile pm && skill.SkillName == pm.AcceleratedSkill && pm.AcceleratedStart > DateTime.UtcNow ) - toGain *= Utility.RandomMinMax(2, 5); - #endregion - - if ( !from.Player || (skills.Total + toGain) <= skills.Cap ) - { - skill.BaseFixedPoint += toGain; - } - } - - if ( skill.Lock == SkillLock.Up ) - { - SkillInfo info = skill.Info; - - if ( from.StrLock == StatLockType.Up && (info.StrGain / 33.3) > Utility.RandomDouble() ) - GainStat( from, Stat.Str ); - else if ( from.DexLock == StatLockType.Up && (info.DexGain / 33.3) > Utility.RandomDouble() ) - GainStat( from, Stat.Dex ); - else if ( from.IntLock == StatLockType.Up && (info.IntGain / 33.3) > Utility.RandomDouble() ) - GainStat( from, Stat.Int ); - } - } - - public static bool CanLower( Mobile from, Stat stat ) - { - switch ( stat ) - { - case Stat.Str: return ( from.StrLock == StatLockType.Down && from.RawStr > 10 ); - case Stat.Dex: return ( from.DexLock == StatLockType.Down && from.RawDex > 10 ); - case Stat.Int: return ( from.IntLock == StatLockType.Down && from.RawInt > 10 ); - } - - return false; - } - - public static bool CanRaise( Mobile from, Stat stat ) - { - if ( !(from is BaseCreature creature && creature.Controlled) ) - { - if ( from.RawStatTotal >= from.StatCap ) - return false; - } - - switch ( stat ) - { - case Stat.Str: return ( from.StrLock == StatLockType.Up && from.RawStr < 125 ); - case Stat.Dex: return ( from.DexLock == StatLockType.Up && from.RawDex < 125 ); - case Stat.Int: return ( from.IntLock == StatLockType.Up && from.RawInt < 125 ); - } - - return false; - } - - public static void IncreaseStat( Mobile from, Stat stat, bool atrophy ) - { - atrophy = atrophy || (from.RawStatTotal >= from.StatCap); - - switch ( stat ) - { - case Stat.Str: - { - if ( atrophy ) - { - if ( CanLower( from, Stat.Dex ) && (from.RawDex < from.RawInt || !CanLower( from, Stat.Int )) ) - --from.RawDex; - else if ( CanLower( from, Stat.Int ) ) - --from.RawInt; - } - - if ( CanRaise( from, Stat.Str ) ) - ++from.RawStr; - - break; - } - case Stat.Dex: - { - if ( atrophy ) - { - if ( CanLower( from, Stat.Str ) && (from.RawStr < from.RawInt || !CanLower( from, Stat.Int )) ) - --from.RawStr; - else if ( CanLower( from, Stat.Int ) ) - --from.RawInt; - } - - if ( CanRaise( from, Stat.Dex ) ) - ++from.RawDex; - - break; - } - case Stat.Int: - { - if ( atrophy ) - { - if ( CanLower( from, Stat.Str ) && (from.RawStr < from.RawDex || !CanLower( from, Stat.Dex )) ) - --from.RawStr; - else if ( CanLower( from, Stat.Dex ) ) - --from.RawDex; - } - - if ( CanRaise( from, Stat.Int ) ) - ++from.RawInt; - - break; - } - } - } - - private static TimeSpan m_StatGainDelay = TimeSpan.FromMinutes( ( Core.ML ) ? 0.05 : 15 ); - private static TimeSpan m_PetStatGainDelay = TimeSpan.FromMinutes( 5.0 ); - - public static void GainStat( Mobile from, Stat stat ) - { - switch( stat ) - { - case Stat.Str: - { - if ( from is BaseCreature creature && creature.Controlled ) { - if ( (creature.LastStrGain + m_PetStatGainDelay) >= DateTime.UtcNow ) - return; - } - else if ( (from.LastStrGain + m_StatGainDelay) >= DateTime.UtcNow ) - return; - - from.LastStrGain = DateTime.UtcNow; - break; - } - case Stat.Dex: - { - if ( from is BaseCreature creature && creature.Controlled ) { - if ( (creature.LastDexGain + m_PetStatGainDelay) >= DateTime.UtcNow ) - return; - } - else if ( (from.LastDexGain + m_StatGainDelay) >= DateTime.UtcNow ) - return; - - from.LastDexGain = DateTime.UtcNow; - break; - } - case Stat.Int: - { - if ( from is BaseCreature creature && creature.Controlled ) { - if ( (creature.LastIntGain + m_PetStatGainDelay) >= DateTime.UtcNow ) - return; - } - - else if ( (from.LastIntGain + m_StatGainDelay) >= DateTime.UtcNow ) - return; - - from.LastIntGain = DateTime.UtcNow; - break; - } - } - - bool atrophy = ( (from.RawStatTotal / (double)from.StatCap) >= Utility.RandomDouble() ); - - IncreaseStat( from, stat, atrophy ); - } - } -} + private static bool AllowGain(Mobile from, Skill skill, object obj) + { + if (Core.AOS && Faction.InSkillLoss(from)) //Changed some time between the introduction of AoS and SE. + return false; + + if (AntiMacroCode && from is PlayerMobile mobile && UseAntiMacro[skill.Info.SkillID]) + return mobile.AntiMacroCheck(skill, obj); + + return true; + } + + public static void Gain(Mobile from, Skill skill) + { + if (from.Region.IsPartOf(typeof(Jail))) + return; + + if (from is BaseCreature creature && creature.IsDeadPet) + return; + + if (skill.SkillName == SkillName.Focus && from is BaseCreature) + return; + + if (skill.Base < skill.Cap && skill.Lock == SkillLock.Up) + { + int toGain = 1; + + if (skill.Base <= 10.0) + toGain = Utility.Random(4) + 1; + + Skills skills = from.Skills; + + if (from.Player && skills.Total / skills.Cap >= Utility.RandomDouble()) //( skills.Total >= skills.Cap ) + for (int i = 0; i < skills.Length; ++i) + { + Skill toLower = skills[i]; + + if (toLower != skill && toLower.Lock == SkillLock.Down && toLower.BaseFixedPoint >= toGain) + { + toLower.BaseFixedPoint -= toGain; + break; + } + } + + #region Scroll of Alacrity + + if (from is PlayerMobile pm && skill.SkillName == pm.AcceleratedSkill && + pm.AcceleratedStart > DateTime.UtcNow) + toGain *= Utility.RandomMinMax(2, 5); + + #endregion + + if (!from.Player || skills.Total + toGain <= skills.Cap) skill.BaseFixedPoint += toGain; + } + + if (skill.Lock == SkillLock.Up) + { + SkillInfo info = skill.Info; + + if (from.StrLock == StatLockType.Up && info.StrGain / 33.3 > Utility.RandomDouble()) + GainStat(from, Stat.Str); + else if (from.DexLock == StatLockType.Up && info.DexGain / 33.3 > Utility.RandomDouble()) + GainStat(from, Stat.Dex); + else if (from.IntLock == StatLockType.Up && info.IntGain / 33.3 > Utility.RandomDouble()) + GainStat(from, Stat.Int); + } + } + + public static bool CanLower(Mobile from, Stat stat) + { + switch (stat) + { + case Stat.Str: return from.StrLock == StatLockType.Down && from.RawStr > 10; + case Stat.Dex: return from.DexLock == StatLockType.Down && from.RawDex > 10; + case Stat.Int: return from.IntLock == StatLockType.Down && from.RawInt > 10; + } + + return false; + } + + public static bool CanRaise(Mobile from, Stat stat) + { + if (!(from is BaseCreature creature && creature.Controlled)) + if (from.RawStatTotal >= from.StatCap) + return false; + + switch (stat) + { + case Stat.Str: return from.StrLock == StatLockType.Up && from.RawStr < 125; + case Stat.Dex: return from.DexLock == StatLockType.Up && from.RawDex < 125; + case Stat.Int: return from.IntLock == StatLockType.Up && from.RawInt < 125; + } + + return false; + } + + public static void IncreaseStat(Mobile from, Stat stat, bool atrophy) + { + atrophy = atrophy || from.RawStatTotal >= from.StatCap; + + switch (stat) + { + case Stat.Str: + { + if (atrophy) + { + if (CanLower(from, Stat.Dex) && (from.RawDex < from.RawInt || !CanLower(from, Stat.Int))) + --from.RawDex; + else if (CanLower(from, Stat.Int)) + --from.RawInt; + } + + if (CanRaise(from, Stat.Str)) + ++from.RawStr; + + break; + } + case Stat.Dex: + { + if (atrophy) + { + if (CanLower(from, Stat.Str) && (from.RawStr < from.RawInt || !CanLower(from, Stat.Int))) + --from.RawStr; + else if (CanLower(from, Stat.Int)) + --from.RawInt; + } + + if (CanRaise(from, Stat.Dex)) + ++from.RawDex; + + break; + } + case Stat.Int: + { + if (atrophy) + { + if (CanLower(from, Stat.Str) && (from.RawStr < from.RawDex || !CanLower(from, Stat.Dex))) + --from.RawStr; + else if (CanLower(from, Stat.Dex)) + --from.RawDex; + } + + if (CanRaise(from, Stat.Int)) + ++from.RawInt; + + break; + } + } + } + + public static void GainStat(Mobile from, Stat stat) + { + switch (stat) + { + case Stat.Str: + { + if (from is BaseCreature creature && creature.Controlled) + { + if (creature.LastStrGain + m_PetStatGainDelay >= DateTime.UtcNow) + return; + } + else if (from.LastStrGain + m_StatGainDelay >= DateTime.UtcNow) + { + return; + } + + from.LastStrGain = DateTime.UtcNow; + break; + } + case Stat.Dex: + { + if (from is BaseCreature creature && creature.Controlled) + { + if (creature.LastDexGain + m_PetStatGainDelay >= DateTime.UtcNow) + return; + } + else if (from.LastDexGain + m_StatGainDelay >= DateTime.UtcNow) + { + return; + } + + from.LastDexGain = DateTime.UtcNow; + break; + } + case Stat.Int: + { + if (from is BaseCreature creature && creature.Controlled) + { + if (creature.LastIntGain + m_PetStatGainDelay >= DateTime.UtcNow) + return; + } + + else if (from.LastIntGain + m_StatGainDelay >= DateTime.UtcNow) + { + return; + } + + from.LastIntGain = DateTime.UtcNow; + break; + } + } + + bool atrophy = from.RawStatTotal / (double)from.StatCap >= Utility.RandomDouble(); + + IncreaseStat(from, stat, atrophy); + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/SocketOptions.cs b/Scripts/Misc/SocketOptions.cs index 2e8b00eb4..8abfebbdb 100644 --- a/Scripts/Misc/SocketOptions.cs +++ b/Scripts/Misc/SocketOptions.cs @@ -4,35 +4,36 @@ using Server.Network; namespace Server { - public class SocketOptions - { - private const bool NagleEnabled = false; // Should the Nagle algorithm be enabled? This may reduce performance - private const int CoalesceBufferSize = 512; // MSS that the core will use when buffering packets + public class SocketOptions + { + private const bool NagleEnabled = false; // Should the Nagle algorithm be enabled? This may reduce performance + private const int CoalesceBufferSize = 512; // MSS that the core will use when buffering packets - private static IPEndPoint[] m_ListenerEndPoints = { - new IPEndPoint( IPAddress.Any, 2593 ), // Default: Listen on port 2593 on all IP addresses - - // Examples: - // new IPEndPoint( IPAddress.Any, 80 ), // Listen on port 80 on all IP addresses - // new IPEndPoint( IPAddress.Parse( "1.2.3.4" ), 2593 ), // Listen on port 2593 on IP address 1.2.3.4 - }; + private static IPEndPoint[] m_ListenerEndPoints = + { + new IPEndPoint(IPAddress.Any, 2593) // Default: Listen on port 2593 on all IP addresses - public static void Initialize() - { - SendQueue.CoalesceBufferSize = CoalesceBufferSize; + // Examples: + // new IPEndPoint( IPAddress.Any, 80 ), // Listen on port 80 on all IP addresses + // new IPEndPoint( IPAddress.Parse( "1.2.3.4" ), 2593 ), // Listen on port 2593 on IP address 1.2.3.4 + }; - EventSink.SocketConnect += EventSink_SocketConnect; + public static void Initialize() + { + SendQueue.CoalesceBufferSize = CoalesceBufferSize; - Listener.EndPoints = m_ListenerEndPoints; - } + EventSink.SocketConnect += EventSink_SocketConnect; - private static void EventSink_SocketConnect( SocketConnectEventArgs e ) - { - if ( !e.AllowConnection ) - return; + Listener.EndPoints = m_ListenerEndPoints; + } - if ( !NagleEnabled ) - e.Socket.SetSocketOption( SocketOptionLevel.Tcp, SocketOptionName.NoDelay, 1 ); // RunUO uses its own algorithm - } - } + private static void EventSink_SocketConnect(SocketConnectEventArgs e) + { + if (!e.AllowConnection) + return; + + if (!NagleEnabled) + e.Socket.SetSocketOption(SocketOptionLevel.Tcp, SocketOptionName.NoDelay, 1); // RunUO uses its own algorithm + } + } } \ No newline at end of file diff --git a/Scripts/Misc/TextDefinition.cs b/Scripts/Misc/TextDefinition.cs index 15b979b57..34f027606 100644 --- a/Scripts/Misc/TextDefinition.cs +++ b/Scripts/Misc/TextDefinition.cs @@ -1,217 +1,219 @@ -using System; using System.Globalization; using Server.Gumps; using Server.Network; namespace Server { - [Parsable] - public class TextDefinition - { - public int Number { get; } + [Parsable] + public class TextDefinition + { + public TextDefinition() : this(0, null) + { + } - public string String { get; } + public TextDefinition(int number) : this(number, null) + { + } - public bool IsEmpty => ( Number <= 0 && String == null ); + public TextDefinition(string text) : this(0, text) + { + } - public TextDefinition() : this( 0, null ) - { - } + public TextDefinition(int number, string text) + { + Number = number; + String = text; + } - public TextDefinition( int number ) : this( number, null ) - { - } + public int Number{ get; } - public TextDefinition( string text ) : this( 0, text ) - { - } + public string String{ get; } - public TextDefinition( int number, string text ) - { - Number = number; - String = text; - } + public bool IsEmpty => Number <= 0 && String == null; - public override string ToString() - { - if ( Number > 0 ) - return string.Concat( "#", Number.ToString() ); - if ( String != null ) - return String; + public override string ToString() + { + if (Number > 0) + return string.Concat("#", Number.ToString()); + if (String != null) + return String; - return ""; - } + return ""; + } - public string Format( bool propsGump ) - { - if ( Number > 0 ) - return string.Format( "{0} (0x{0:X})", Number ); - if ( String != null ) - return $"\"{String}\""; + public string Format(bool propsGump) + { + if (Number > 0) + return string.Format("{0} (0x{0:X})", Number); + if (String != null) + return $"\"{String}\""; - return propsGump ? "-empty-" : "empty"; - } + return propsGump ? "-empty-" : "empty"; + } - public string GetValue() - { - if ( Number > 0 ) - return Number.ToString(); - if ( String != null ) - return String; + public string GetValue() + { + if (Number > 0) + return Number.ToString(); + if (String != null) + return String; - return ""; - } + return ""; + } - public static void Serialize( GenericWriter writer, TextDefinition def ) - { - if ( def == null ) - { - writer.WriteEncodedInt( 3 ); - } - else if ( def.Number > 0 ) - { - writer.WriteEncodedInt( 1 ); - writer.WriteEncodedInt( def.Number ); - } - else if ( def.String != null ) - { - writer.WriteEncodedInt( 2 ); - writer.Write( def.String ); - } - else - { - writer.WriteEncodedInt( 0 ); - } - } + public static void Serialize(GenericWriter writer, TextDefinition def) + { + if (def == null) + { + writer.WriteEncodedInt(3); + } + else if (def.Number > 0) + { + writer.WriteEncodedInt(1); + writer.WriteEncodedInt(def.Number); + } + else if (def.String != null) + { + writer.WriteEncodedInt(2); + writer.Write(def.String); + } + else + { + writer.WriteEncodedInt(0); + } + } - public static TextDefinition Deserialize( GenericReader reader ) - { - int type = reader.ReadEncodedInt(); + public static TextDefinition Deserialize(GenericReader reader) + { + int type = reader.ReadEncodedInt(); - switch ( type ) - { - case 0: return new TextDefinition(); - case 1: return new TextDefinition( reader.ReadEncodedInt() ); - case 2: return new TextDefinition( reader.ReadString() ); - } + switch (type) + { + case 0: return new TextDefinition(); + case 1: return new TextDefinition(reader.ReadEncodedInt()); + case 2: return new TextDefinition(reader.ReadString()); + } - return null; - } + return null; + } - public static void AddTo( ObjectPropertyList list, TextDefinition def ) - { - if ( def == null ) - return; + public static void AddTo(ObjectPropertyList list, TextDefinition def) + { + if (def == null) + return; - if ( def.Number > 0 ) - list.Add( def.Number ); - else if ( def.String != null ) - list.Add( def.String ); - } + if (def.Number > 0) + list.Add(def.Number); + else if (def.String != null) + list.Add(def.String); + } - public static implicit operator TextDefinition( int v ) - { - return new TextDefinition( v ); - } + public static implicit operator TextDefinition(int v) + { + return new TextDefinition(v); + } - public static implicit operator TextDefinition( string s ) - { - return new TextDefinition( s ); - } + public static implicit operator TextDefinition(string s) + { + return new TextDefinition(s); + } - public static implicit operator int( TextDefinition m ) - { - if ( m == null ) - return 0; + public static implicit operator int(TextDefinition m) + { + if (m == null) + return 0; - return m.Number; - } + return m.Number; + } - public static implicit operator string( TextDefinition m ) - { - return m?.String; - } + public static implicit operator string(TextDefinition m) + { + return m?.String; + } - public static void AddHtmlText( Gump g, int x, int y, int width, int height, TextDefinition def, bool back, bool scroll, int numberColor, int stringColor ) - { - if ( def == null ) - return; + public static void AddHtmlText(Gump g, int x, int y, int width, int height, TextDefinition def, bool back, + bool scroll, int numberColor, int stringColor) + { + if (def == null) + return; - if ( def.Number > 0 ) - { - if ( numberColor >= 0 ) // 5 bits per RGB component (15 bit RGB) - g.AddHtmlLocalized( x, y, width, height, def.Number, numberColor, back, scroll ); - else - g.AddHtmlLocalized( x, y, width, height, def.Number, back, scroll ); - } - else if ( def.String != null ) - { - if ( stringColor >= 0 ) // 8 bits per RGB component (24 bit RGB) - g.AddHtml( x, y, width, height, $"{def.String}", back, scroll ); - else - g.AddHtml( x, y, width, height, def.String, back, scroll ); - } - } + if (def.Number > 0) + { + if (numberColor >= 0) // 5 bits per RGB component (15 bit RGB) + g.AddHtmlLocalized(x, y, width, height, def.Number, numberColor, back, scroll); + else + g.AddHtmlLocalized(x, y, width, height, def.Number, back, scroll); + } + else if (def.String != null) + { + if (stringColor >= 0) // 8 bits per RGB component (24 bit RGB) + g.AddHtml(x, y, width, height, $"{def.String}", back, + scroll); + else + g.AddHtml(x, y, width, height, def.String, back, scroll); + } + } - public static void AddHtmlText( Gump g, int x, int y, int width, int height, TextDefinition def, bool back, bool scroll ) - { - AddHtmlText( g, x, y, width, height, def, back, scroll, -1, -1 ); - } + public static void AddHtmlText(Gump g, int x, int y, int width, int height, TextDefinition def, bool back, + bool scroll) + { + AddHtmlText(g, x, y, width, height, def, back, scroll, -1, -1); + } - public static void SendMessageTo( Mobile m, TextDefinition def ) - { - if ( def == null ) - return; + public static void SendMessageTo(Mobile m, TextDefinition def) + { + if (def == null) + return; - if ( def.Number > 0 ) - m.SendLocalizedMessage( def.Number ); - else if ( def.String != null ) - m.SendMessage( def.String ); - } + if (def.Number > 0) + m.SendLocalizedMessage(def.Number); + else if (def.String != null) + m.SendMessage(def.String); + } - public static void SendMessageTo( Mobile m, TextDefinition def, int hue ) - { - if ( def == null ) - return; + public static void SendMessageTo(Mobile m, TextDefinition def, int hue) + { + if (def == null) + return; - if ( def.Number > 0 ) - m.SendLocalizedMessage( def.Number, "", hue ); - else if ( def.String != null ) - m.SendMessage( hue, def.String ); - } + if (def.Number > 0) + m.SendLocalizedMessage(def.Number, "", hue); + else if (def.String != null) + m.SendMessage(hue, def.String); + } - public static void PublicOverheadMessage( Mobile m, MessageType messageType, int hue, TextDefinition def ) - { - if ( def == null ) - return; + public static void PublicOverheadMessage(Mobile m, MessageType messageType, int hue, TextDefinition def) + { + if (def == null) + return; - if ( def.Number > 0 ) - m.PublicOverheadMessage( messageType, hue, def.Number ); - else if ( def.String != null ) - m.PublicOverheadMessage( messageType, hue, false, def.String ); - } + if (def.Number > 0) + m.PublicOverheadMessage(messageType, hue, def.Number); + else if (def.String != null) + m.PublicOverheadMessage(messageType, hue, false, def.String); + } - public static TextDefinition Parse( string value ) - { - if ( value == null ) - return null; + public static TextDefinition Parse(string value) + { + if (value == null) + return null; - int i; - bool isInteger; + int i; + bool isInteger; - if ( value.StartsWith( "0x" ) ) - isInteger = int.TryParse( value.Substring( 2 ), NumberStyles.HexNumber, null, out i ); - else - isInteger = int.TryParse( value, out i ); + if (value.StartsWith("0x")) + isInteger = int.TryParse(value.Substring(2), NumberStyles.HexNumber, null, out i); + else + isInteger = int.TryParse(value, out i); - if ( isInteger ) - return new TextDefinition( i ); - return new TextDefinition( value ); - } + if (isInteger) + return new TextDefinition(i); + return new TextDefinition(value); + } - public static bool IsNullOrEmpty( TextDefinition def ) - { - return ( def == null || def.IsEmpty ); - } - } -} + public static bool IsNullOrEmpty(TextDefinition def) + { + return def == null || def.IsEmpty; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/Titles.cs b/Scripts/Misc/Titles.cs index 46e4feb56..4e7e1dcb3 100644 --- a/Scripts/Misc/Titles.cs +++ b/Scripts/Misc/Titles.cs @@ -1,399 +1,406 @@ using System; using System.Text; -using Server.Mobiles; using Server.Engines.CannedEvil; +using Server.Mobiles; namespace Server.Misc { - public class Titles - { - public const int MinFame = 0; - public const int MaxFame = 15000; + public class Titles + { + public const int MinFame = 0; + public const int MaxFame = 15000; - public static void AwardFame( Mobile m, int offset, bool message ) - { - if ( offset > 0 ) - { - if ( m.Fame >= MaxFame ) - return; + public const int MinKarma = -15000; + public const int MaxKarma = 15000; - offset -= m.Fame / 100; + public static string[] HarrowerTitles = + { + "Spite", "Opponent", "Hunter", "Venom", "Executioner", "Annihilator", "Champion", "Assailant", "Purifier", + "Nullifier" + }; - if ( offset < 0 ) - offset = 0; - } - else if ( offset < 0 ) - { - if ( m.Fame <= MinFame ) - return; + private static string[,] m_Levels = + { + { "Neophyte", "Neophyte", "Neophyte" }, + { "Novice", "Novice", "Novice" }, + { "Apprentice", "Apprentice", "Apprentice" }, + { "Journeyman", "Journeyman", "Journeyman" }, + { "Expert", "Expert", "Expert" }, + { "Adept", "Adept", "Adept" }, + { "Master", "Master", "Master" }, + { "Grandmaster", "Grandmaster", "Grandmaster" }, + { "Elder", "Tatsujin", "Shinobi" }, + { "Legendary", "Kengo", "Ka-ge" } + }; - offset -= m.Fame / 100; + private static FameEntry[] m_FameEntries = + { + new FameEntry(1249, new[] + { + new KarmaEntry(-10000, "The Outcast {0}"), + new KarmaEntry(-5000, "The Despicable {0}"), + new KarmaEntry(-2500, "The Scoundrel {0}"), + new KarmaEntry(-1250, "The Unsavory {0}"), + new KarmaEntry(-625, "The Rude {0}"), + new KarmaEntry(624, "{0}"), + new KarmaEntry(1249, "The Fair {0}"), + new KarmaEntry(2499, "The Kind {0}"), + new KarmaEntry(4999, "The Good {0}"), + new KarmaEntry(9999, "The Honest {0}"), + new KarmaEntry(10000, "The Trustworthy {0}") + }), + new FameEntry(2499, new[] + { + new KarmaEntry(-10000, "The Wretched {0}"), + new KarmaEntry(-5000, "The Dastardly {0}"), + new KarmaEntry(-2500, "The Malicious {0}"), + new KarmaEntry(-1250, "The Dishonorable {0}"), + new KarmaEntry(-625, "The Disreputable {0}"), + new KarmaEntry(624, "The Notable {0}"), + new KarmaEntry(1249, "The Upstanding {0}"), + new KarmaEntry(2499, "The Respectable {0}"), + new KarmaEntry(4999, "The Honorable {0}"), + new KarmaEntry(9999, "The Commendable {0}"), + new KarmaEntry(10000, "The Estimable {0}") + }), + new FameEntry(4999, new[] + { + new KarmaEntry(-10000, "The Nefarious {0}"), + new KarmaEntry(-5000, "The Wicked {0}"), + new KarmaEntry(-2500, "The Vile {0}"), + new KarmaEntry(-1250, "The Ignoble {0}"), + new KarmaEntry(-625, "The Notorious {0}"), + new KarmaEntry(624, "The Prominent {0}"), + new KarmaEntry(1249, "The Reputable {0}"), + new KarmaEntry(2499, "The Proper {0}"), + new KarmaEntry(4999, "The Admirable {0}"), + new KarmaEntry(9999, "The Famed {0}"), + new KarmaEntry(10000, "The Great {0}") + }), + new FameEntry(9999, new[] + { + new KarmaEntry(-10000, "The Dread {0}"), + new KarmaEntry(-5000, "The Evil {0}"), + new KarmaEntry(-2500, "The Villainous {0}"), + new KarmaEntry(-1250, "The Sinister {0}"), + new KarmaEntry(-625, "The Infamous {0}"), + new KarmaEntry(624, "The Renowned {0}"), + new KarmaEntry(1249, "The Distinguished {0}"), + new KarmaEntry(2499, "The Eminent {0}"), + new KarmaEntry(4999, "The Noble {0}"), + new KarmaEntry(9999, "The Illustrious {0}"), + new KarmaEntry(10000, "The Glorious {0}") + }), + new FameEntry(10000, new[] + { + new KarmaEntry(-10000, "The Dread {1} {0}"), + new KarmaEntry(-5000, "The Evil {1} {0}"), + new KarmaEntry(-2500, "The Dark {1} {0}"), + new KarmaEntry(-1250, "The Sinister {1} {0}"), + new KarmaEntry(-625, "The Dishonored {1} {0}"), + new KarmaEntry(624, "{1} {0}"), + new KarmaEntry(1249, "The Distinguished {1} {0}"), + new KarmaEntry(2499, "The Eminent {1} {0}"), + new KarmaEntry(4999, "The Noble {1} {0}"), + new KarmaEntry(9999, "The Illustrious {1} {0}"), + new KarmaEntry(10000, "The Glorious {1} {0}") + }) + }; - if ( offset > 0 ) - offset = 0; - } + public static void AwardFame(Mobile m, int offset, bool message) + { + if (offset > 0) + { + if (m.Fame >= MaxFame) + return; - if ( (m.Fame + offset) > MaxFame ) - offset = MaxFame - m.Fame; - else if ( (m.Fame + offset) < MinFame ) - offset = MinFame - m.Fame; + offset -= m.Fame / 100; - m.Fame += offset; + if (offset < 0) + offset = 0; + } + else if (offset < 0) + { + if (m.Fame <= MinFame) + return; - if ( message ) - { - if ( offset > 40 ) - m.SendLocalizedMessage( 1019054 ); // You have gained a lot of fame. - else if ( offset > 20 ) - m.SendLocalizedMessage( 1019053 ); // You have gained a good amount of fame. - else if ( offset > 10 ) - m.SendLocalizedMessage( 1019052 ); // You have gained some fame. - else if ( offset > 0 ) - m.SendLocalizedMessage( 1019051 ); // You have gained a little fame. - else if ( offset < -40 ) - m.SendLocalizedMessage( 1019058 ); // You have lost a lot of fame. - else if ( offset < -20 ) - m.SendLocalizedMessage( 1019057 ); // You have lost a good amount of fame. - else if ( offset < -10 ) - m.SendLocalizedMessage( 1019056 ); // You have lost some fame. - else if ( offset < 0 ) - m.SendLocalizedMessage( 1019055 ); // You have lost a little fame. - } - } + offset -= m.Fame / 100; - public const int MinKarma = -15000; - public const int MaxKarma = 15000; + if (offset > 0) + offset = 0; + } - public static void AwardKarma( Mobile m, int offset, bool message ) - { - PlayerMobile pm = m as PlayerMobile; + if (m.Fame + offset > MaxFame) + offset = MaxFame - m.Fame; + else if (m.Fame + offset < MinFame) + offset = MinFame - m.Fame; - if ( offset > 0 ) - { - if ( pm?.KarmaLocked == true ) - return; + m.Fame += offset; - if ( m.Karma >= MaxKarma ) - return; + if (message) + { + if (offset > 40) + m.SendLocalizedMessage(1019054); // You have gained a lot of fame. + else if (offset > 20) + m.SendLocalizedMessage(1019053); // You have gained a good amount of fame. + else if (offset > 10) + m.SendLocalizedMessage(1019052); // You have gained some fame. + else if (offset > 0) + m.SendLocalizedMessage(1019051); // You have gained a little fame. + else if (offset < -40) + m.SendLocalizedMessage(1019058); // You have lost a lot of fame. + else if (offset < -20) + m.SendLocalizedMessage(1019057); // You have lost a good amount of fame. + else if (offset < -10) + m.SendLocalizedMessage(1019056); // You have lost some fame. + else if (offset < 0) + m.SendLocalizedMessage(1019055); // You have lost a little fame. + } + } - offset -= m.Karma / 100; + public static void AwardKarma(Mobile m, int offset, bool message) + { + PlayerMobile pm = m as PlayerMobile; - if ( offset < 0 ) - offset = 0; - } - else if ( offset < 0 ) - { - if ( m.Karma <= MinKarma ) - return; + if (offset > 0) + { + if (pm?.KarmaLocked == true) + return; - offset -= m.Karma / 100; + if (m.Karma >= MaxKarma) + return; - if ( offset > 0 ) - offset = 0; - } + offset -= m.Karma / 100; - if ( (m.Karma + offset) > MaxKarma ) - offset = MaxKarma - m.Karma; - else if ( (m.Karma + offset) < MinKarma ) - offset = MinKarma - m.Karma; + if (offset < 0) + offset = 0; + } + else if (offset < 0) + { + if (m.Karma <= MinKarma) + return; - bool wasPositiveKarma = ( m.Karma >= 0 ); + offset -= m.Karma / 100; - m.Karma += offset; + if (offset > 0) + offset = 0; + } - if ( message ) - { - if ( offset > 40 ) - m.SendLocalizedMessage( 1019062 ); // You have gained a lot of karma. - else if ( offset > 20 ) - m.SendLocalizedMessage( 1019061 ); // You have gained a good amount of karma. - else if ( offset > 10 ) - m.SendLocalizedMessage( 1019060 ); // You have gained some karma. - else if ( offset > 0 ) - m.SendLocalizedMessage( 1019059 ); // You have gained a little karma. - else if ( offset < -40 ) - m.SendLocalizedMessage( 1019066 ); // You have lost a lot of karma. - else if ( offset < -20 ) - m.SendLocalizedMessage( 1019065 ); // You have lost a good amount of karma. - else if ( offset < -10 ) - m.SendLocalizedMessage( 1019064 ); // You have lost some karma. - else if ( offset < 0 ) - m.SendLocalizedMessage( 1019063 ); // You have lost a little karma. - } + if (m.Karma + offset > MaxKarma) + offset = MaxKarma - m.Karma; + else if (m.Karma + offset < MinKarma) + offset = MinKarma - m.Karma; - if ( !Core.AOS && wasPositiveKarma && m.Karma < 0 && pm != null && !pm.KarmaLocked ) - { - pm.KarmaLocked = true; - m.SendLocalizedMessage( 1042511, "", 0x22 ); // Karma is locked. A mantra spoken at a shrine will unlock it again. - } - } + bool wasPositiveKarma = m.Karma >= 0; - public static string[] HarrowerTitles = { "Spite", "Opponent", "Hunter", "Venom", "Executioner", "Annihilator", "Champion", "Assailant", "Purifier", "Nullifier" }; + m.Karma += offset; - public static string ComputeTitle( Mobile beholder, Mobile beheld ) - { - StringBuilder title = new StringBuilder(); + if (message) + { + if (offset > 40) + m.SendLocalizedMessage(1019062); // You have gained a lot of karma. + else if (offset > 20) + m.SendLocalizedMessage(1019061); // You have gained a good amount of karma. + else if (offset > 10) + m.SendLocalizedMessage(1019060); // You have gained some karma. + else if (offset > 0) + m.SendLocalizedMessage(1019059); // You have gained a little karma. + else if (offset < -40) + m.SendLocalizedMessage(1019066); // You have lost a lot of karma. + else if (offset < -20) + m.SendLocalizedMessage(1019065); // You have lost a good amount of karma. + else if (offset < -10) + m.SendLocalizedMessage(1019064); // You have lost some karma. + else if (offset < 0) + m.SendLocalizedMessage(1019063); // You have lost a little karma. + } - int fame = beheld.Fame; - int karma = beheld.Karma; + if (!Core.AOS && wasPositiveKarma && m.Karma < 0 && pm != null && !pm.KarmaLocked) + { + pm.KarmaLocked = true; + m.SendLocalizedMessage(1042511, "", + 0x22); // Karma is locked. A mantra spoken at a shrine will unlock it again. + } + } - bool showSkillTitle = beheld.ShowFameTitle && ( (beholder == beheld) || (fame >= 5000) ); + public static string ComputeTitle(Mobile beholder, Mobile beheld) + { + StringBuilder title = new StringBuilder(); - /*if ( beheld.Kills >= 5 ) - { - title.AppendFormat( beheld.Fame >= 10000 ? "The Murderer {1} {0}" : "The Murderer {0}", beheld.Name, beheld.Female ? "Lady" : "Lord" ); - } - else*/if ( beheld.ShowFameTitle || (beholder == beheld) ) - { - for ( int i = 0; i < m_FameEntries.Length; ++i ) - { - FameEntry fe = m_FameEntries[i]; + int fame = beheld.Fame; + int karma = beheld.Karma; - if ( fame <= fe.m_Fame || i == (m_FameEntries.Length - 1) ) - { - KarmaEntry[] karmaEntries = fe.m_Karma; + bool showSkillTitle = beheld.ShowFameTitle && (beholder == beheld || fame >= 5000); - for ( int j = 0; j < karmaEntries.Length; ++j ) - { - KarmaEntry ke = karmaEntries[j]; + /*if ( beheld.Kills >= 5 ) + { + title.AppendFormat( beheld.Fame >= 10000 ? "The Murderer {1} {0}" : "The Murderer {0}", beheld.Name, beheld.Female ? "Lady" : "Lord" ); + } + else*/ + if (beheld.ShowFameTitle || beholder == beheld) + for (int i = 0; i < m_FameEntries.Length; ++i) + { + FameEntry fe = m_FameEntries[i]; - if ( karma <= ke.m_Karma || j == (karmaEntries.Length - 1) ) - { - title.AppendFormat( ke.m_Title, beheld.Name, beheld.Female ? "Lady" : "Lord" ); - break; - } - } + if (fame <= fe.m_Fame || i == m_FameEntries.Length - 1) + { + KarmaEntry[] karmaEntries = fe.m_Karma; - break; - } - } - } - else - { - title.Append( beheld.Name ); - } + for (int j = 0; j < karmaEntries.Length; ++j) + { + KarmaEntry ke = karmaEntries[j]; - if ( beheld is PlayerMobile mobile && mobile.DisplayChampionTitle ) - { - PlayerMobile.ChampionTitleInfo info = mobile.ChampionTitles; + if (karma <= ke.m_Karma || j == karmaEntries.Length - 1) + { + title.AppendFormat(ke.m_Title, beheld.Name, beheld.Female ? "Lady" : "Lord"); + break; + } + } - if ( info.Harrower > 0 ) - title.AppendFormat( ": {0} of Evil", HarrowerTitles[Math.Min( HarrowerTitles.Length, info.Harrower )-1] ); - else - { - int highestValue = 0, highestType = 0; - for( int i = 0; i < ChampionSpawnInfo.Table.Length; i++ ) - { - int v = info.GetValue( i ); + break; + } + } + else + title.Append(beheld.Name); - if ( v > highestValue ) - { - highestValue = v; - highestType = i; - } - } + if (beheld is PlayerMobile mobile && mobile.DisplayChampionTitle) + { + PlayerMobile.ChampionTitleInfo info = mobile.ChampionTitles; - int offset = 0; - if ( highestValue > 800 ) - offset = 3; - else if ( highestValue > 300 ) - offset = (int)(highestValue/300); + if (info.Harrower > 0) + { + title.AppendFormat(": {0} of Evil", HarrowerTitles[Math.Min(HarrowerTitles.Length, info.Harrower) - 1]); + } + else + { + int highestValue = 0, highestType = 0; + for (int i = 0; i < ChampionSpawnInfo.Table.Length; i++) + { + int v = info.GetValue(i); - if ( offset > 0 ) - { - ChampionSpawnInfo champInfo = ChampionSpawnInfo.GetInfo( (ChampionSpawnType)highestType ); - title.AppendFormat( ": {0} of the {1}", champInfo.LevelNames[Math.Min( offset, champInfo.LevelNames.Length ) -1], champInfo.Name ); - } - } - } + if (v > highestValue) + { + highestValue = v; + highestType = i; + } + } - string customTitle = beheld.Title; + int offset = 0; + if (highestValue > 800) + offset = 3; + else if (highestValue > 300) + offset = highestValue / 300; - if ( customTitle != null && (customTitle = customTitle.Trim()).Length > 0 ) - { - title.AppendFormat( " {0}", customTitle ); - } - else if ( showSkillTitle && beheld.Player ) - { - string skillTitle = GetSkillTitle( beheld ); + if (offset > 0) + { + ChampionSpawnInfo champInfo = ChampionSpawnInfo.GetInfo((ChampionSpawnType)highestType); + title.AppendFormat(": {0} of the {1}", + champInfo.LevelNames[Math.Min(offset, champInfo.LevelNames.Length) - 1], champInfo.Name); + } + } + } - if ( skillTitle != null ) { - title.Append( ", " ).Append( skillTitle ); - } - } + string customTitle = beheld.Title; - return title.ToString(); - } + if (customTitle != null && (customTitle = customTitle.Trim()).Length > 0) + { + title.AppendFormat(" {0}", customTitle); + } + else if (showSkillTitle && beheld.Player) + { + string skillTitle = GetSkillTitle(beheld); - public static string GetSkillTitle( Mobile mob ) { - Skill highest = GetHighestSkill( mob );// beheld.Skills.Highest; + if (skillTitle != null) title.Append(", ").Append(skillTitle); + } - if ( highest != null && highest.BaseFixedPoint >= 300 ) - { - string skillLevel = GetSkillLevel( highest ); - string skillTitle = highest.Info.Title; + return title.ToString(); + } - if ( mob.Female && skillTitle.EndsWith( "man" ) ) - skillTitle = skillTitle.Substring( 0, skillTitle.Length - 3 ) + "woman"; + public static string GetSkillTitle(Mobile mob) + { + Skill highest = GetHighestSkill(mob); // beheld.Skills.Highest; - return string.Concat( skillLevel, " ", skillTitle ); - } + if (highest != null && highest.BaseFixedPoint >= 300) + { + string skillLevel = GetSkillLevel(highest); + string skillTitle = highest.Info.Title; - return null; - } + if (mob.Female && skillTitle.EndsWith("man")) + skillTitle = skillTitle.Substring(0, skillTitle.Length - 3) + "woman"; - private static Skill GetHighestSkill( Mobile m ) - { - Skills skills = m.Skills; + return string.Concat(skillLevel, " ", skillTitle); + } - if ( !Core.AOS ) - return skills.Highest; + return null; + } - Skill highest = null; + private static Skill GetHighestSkill(Mobile m) + { + Skills skills = m.Skills; - for ( int i = 0; i < m.Skills.Length; ++i ) - { - Skill check = m.Skills[i]; + if (!Core.AOS) + return skills.Highest; - if ( highest == null || check.BaseFixedPoint > highest.BaseFixedPoint ) - highest = check; - else if ( highest != null && highest.Lock != SkillLock.Up && check.Lock == SkillLock.Up && check.BaseFixedPoint == highest.BaseFixedPoint ) - highest = check; - } + Skill highest = null; - return highest; - } + for (int i = 0; i < m.Skills.Length; ++i) + { + Skill check = m.Skills[i]; - private static string[,] m_Levels = { - { "Neophyte", "Neophyte", "Neophyte" }, - { "Novice", "Novice", "Novice" }, - { "Apprentice", "Apprentice", "Apprentice" }, - { "Journeyman", "Journeyman", "Journeyman" }, - { "Expert", "Expert", "Expert" }, - { "Adept", "Adept", "Adept" }, - { "Master", "Master", "Master" }, - { "Grandmaster", "Grandmaster", "Grandmaster" }, - { "Elder", "Tatsujin", "Shinobi" }, - { "Legendary", "Kengo", "Ka-ge" } - }; + if (highest == null || check.BaseFixedPoint > highest.BaseFixedPoint) + highest = check; + else if (highest != null && highest.Lock != SkillLock.Up && check.Lock == SkillLock.Up && + check.BaseFixedPoint == highest.BaseFixedPoint) + highest = check; + } - private static string GetSkillLevel( Skill skill ) - { - return m_Levels[GetTableIndex( skill ), GetTableType( skill )]; - } + return highest; + } - private static int GetTableType( Skill skill ) - { - switch ( skill.SkillName ) - { - default: return 0; - case SkillName.Bushido: return 1; - case SkillName.Ninjitsu: return 2; - } - } + private static string GetSkillLevel(Skill skill) + { + return m_Levels[GetTableIndex(skill), GetTableType(skill)]; + } - private static int GetTableIndex( Skill skill ) - { - int fp = Math.Min( skill.BaseFixedPoint, 1200 ); + private static int GetTableType(Skill skill) + { + switch (skill.SkillName) + { + default: return 0; + case SkillName.Bushido: return 1; + case SkillName.Ninjitsu: return 2; + } + } - return (fp - 300) / 100; - } + private static int GetTableIndex(Skill skill) + { + int fp = Math.Min(skill.BaseFixedPoint, 1200); - private static FameEntry[] m_FameEntries = { - new FameEntry( 1249, new[] - { - new KarmaEntry( -10000, "The Outcast {0}" ), - new KarmaEntry( -5000, "The Despicable {0}" ), - new KarmaEntry( -2500, "The Scoundrel {0}" ), - new KarmaEntry( -1250, "The Unsavory {0}" ), - new KarmaEntry( -625, "The Rude {0}" ), - new KarmaEntry( 624, "{0}" ), - new KarmaEntry( 1249, "The Fair {0}" ), - new KarmaEntry( 2499, "The Kind {0}" ), - new KarmaEntry( 4999, "The Good {0}" ), - new KarmaEntry( 9999, "The Honest {0}" ), - new KarmaEntry( 10000, "The Trustworthy {0}" ) - } ), - new FameEntry( 2499, new[] - { - new KarmaEntry( -10000, "The Wretched {0}" ), - new KarmaEntry( -5000, "The Dastardly {0}" ), - new KarmaEntry( -2500, "The Malicious {0}" ), - new KarmaEntry( -1250, "The Dishonorable {0}" ), - new KarmaEntry( -625, "The Disreputable {0}" ), - new KarmaEntry( 624, "The Notable {0}" ), - new KarmaEntry( 1249, "The Upstanding {0}" ), - new KarmaEntry( 2499, "The Respectable {0}" ), - new KarmaEntry( 4999, "The Honorable {0}" ), - new KarmaEntry( 9999, "The Commendable {0}" ), - new KarmaEntry( 10000, "The Estimable {0}" ) - } ), - new FameEntry( 4999, new[] - { - new KarmaEntry( -10000, "The Nefarious {0}" ), - new KarmaEntry( -5000, "The Wicked {0}" ), - new KarmaEntry( -2500, "The Vile {0}" ), - new KarmaEntry( -1250, "The Ignoble {0}" ), - new KarmaEntry( -625, "The Notorious {0}" ), - new KarmaEntry( 624, "The Prominent {0}" ), - new KarmaEntry( 1249, "The Reputable {0}" ), - new KarmaEntry( 2499, "The Proper {0}" ), - new KarmaEntry( 4999, "The Admirable {0}" ), - new KarmaEntry( 9999, "The Famed {0}" ), - new KarmaEntry( 10000, "The Great {0}" ) - } ), - new FameEntry( 9999, new[] - { - new KarmaEntry( -10000, "The Dread {0}" ), - new KarmaEntry( -5000, "The Evil {0}" ), - new KarmaEntry( -2500, "The Villainous {0}" ), - new KarmaEntry( -1250, "The Sinister {0}" ), - new KarmaEntry( -625, "The Infamous {0}" ), - new KarmaEntry( 624, "The Renowned {0}" ), - new KarmaEntry( 1249, "The Distinguished {0}" ), - new KarmaEntry( 2499, "The Eminent {0}" ), - new KarmaEntry( 4999, "The Noble {0}" ), - new KarmaEntry( 9999, "The Illustrious {0}" ), - new KarmaEntry( 10000, "The Glorious {0}" ) - } ), - new FameEntry( 10000, new[] - { - new KarmaEntry( -10000, "The Dread {1} {0}" ), - new KarmaEntry( -5000, "The Evil {1} {0}" ), - new KarmaEntry( -2500, "The Dark {1} {0}" ), - new KarmaEntry( -1250, "The Sinister {1} {0}" ), - new KarmaEntry( -625, "The Dishonored {1} {0}" ), - new KarmaEntry( 624, "{1} {0}" ), - new KarmaEntry( 1249, "The Distinguished {1} {0}" ), - new KarmaEntry( 2499, "The Eminent {1} {0}" ), - new KarmaEntry( 4999, "The Noble {1} {0}" ), - new KarmaEntry( 9999, "The Illustrious {1} {0}" ), - new KarmaEntry( 10000, "The Glorious {1} {0}" ) - } ) - }; - } + return (fp - 300) / 100; + } + } - public class FameEntry - { - public int m_Fame; - public KarmaEntry[] m_Karma; + public class FameEntry + { + public int m_Fame; + public KarmaEntry[] m_Karma; - public FameEntry( int fame, KarmaEntry[] karma ) - { - m_Fame = fame; - m_Karma = karma; - } - } + public FameEntry(int fame, KarmaEntry[] karma) + { + m_Fame = fame; + m_Karma = karma; + } + } - public class KarmaEntry - { - public int m_Karma; - public string m_Title; + public class KarmaEntry + { + public int m_Karma; + public string m_Title; - public KarmaEntry( int karma, string title ) - { - m_Karma = karma; - m_Title = title; - } - } -} + public KarmaEntry(int karma, string title) + { + m_Karma = karma; + m_Title = title; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/ToggleItem.cs b/Scripts/Misc/ToggleItem.cs index 0bd25d310..ca6c4592c 100644 --- a/Scripts/Misc/ToggleItem.cs +++ b/Scripts/Misc/ToggleItem.cs @@ -3,105 +3,105 @@ using Server.Commands.Generic; namespace Server.Items { - public class ToggleItem : Item - { - public class ToggleCommand : BaseCommand - { - public ToggleCommand() - { - AccessLevel = AccessLevel.GameMaster; - Supports = CommandSupport.AllItems; - Commands = new[]{ "Toggle" }; - ObjectTypes = ObjectTypes.Items; - Usage = "Toggle"; - Description = "Toggles a targeted ToggleItem."; - } + public class ToggleItem : Item + { + [Constructible] + public ToggleItem(int inactiveItemID, int activeItemID, bool playersCanToggle = false) + : base(inactiveItemID) + { + Movable = false; - public override void Execute( CommandEventArgs e, object obj ) - { - if ( obj is ToggleItem item ) - { - item.Toggle(); - AddResponse( "The item has been toggled." ); - } - else - { - LogFailure( "That is not a ToggleItem." ); - } - } - } + InactiveItemID = inactiveItemID; + ActiveItemID = activeItemID; + PlayersCanToggle = playersCanToggle; + } - public static void Initialize() - { - TargetCommands.Register( new ToggleCommand() ); - } + public ToggleItem(Serial serial) + : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int InactiveItemID { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int InactiveItemID{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ActiveItemID { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public int ActiveItemID{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public bool PlayersCanToggle { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public bool PlayersCanToggle{ get; set; } - [Constructible] - public ToggleItem( int inactiveItemID, int activeItemID, bool playersCanToggle = false) - : base( inactiveItemID ) - { - Movable = false; + public static void Initialize() + { + TargetCommands.Register(new ToggleCommand()); + } - InactiveItemID = inactiveItemID; - ActiveItemID = activeItemID; - PlayersCanToggle = playersCanToggle; - } + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + { + Toggle(); + } + else if (PlayersCanToggle) + { + if (from.InRange(GetWorldLocation(), 1)) + Toggle(); + else + from.SendLocalizedMessage(500446); // That is too far away. + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - Toggle(); - } - else if ( PlayersCanToggle ) - { - if ( from.InRange( GetWorldLocation(), 1 ) ) - Toggle(); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } + public void Toggle() + { + ItemID = ItemID == ActiveItemID ? InactiveItemID : ActiveItemID; + Visible = ItemID != 0x1; + } - public void Toggle() - { - ItemID = ( ItemID == ActiveItemID ) ? InactiveItemID : ActiveItemID; - Visible = ( ItemID != 0x1 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public ToggleItem( Serial serial ) - : base( serial ) - { - } + writer.Write(0); // version - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(InactiveItemID); + writer.Write(ActiveItemID); + writer.Write(PlayersCanToggle); + } - writer.Write( (int) 0 ); // version + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( InactiveItemID ); - writer.Write( ActiveItemID ); - writer.Write( PlayersCanToggle ); - } + int version = reader.ReadInt(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + InactiveItemID = reader.ReadInt(); + ActiveItemID = reader.ReadInt(); + PlayersCanToggle = reader.ReadBool(); + } - int version = reader.ReadInt(); + public class ToggleCommand : BaseCommand + { + public ToggleCommand() + { + AccessLevel = AccessLevel.GameMaster; + Supports = CommandSupport.AllItems; + Commands = new[] { "Toggle" }; + ObjectTypes = ObjectTypes.Items; + Usage = "Toggle"; + Description = "Toggles a targeted ToggleItem."; + } - InactiveItemID = reader.ReadInt(); - ActiveItemID = reader.ReadInt(); - PlayersCanToggle = reader.ReadBool(); - } - } -} + public override void Execute(CommandEventArgs e, object obj) + { + if (obj is ToggleItem item) + { + item.Toggle(); + AddResponse("The item has been toggled."); + } + else + { + LogFailure("That is not a ToggleItem."); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/TreasureMapProtection.cs b/Scripts/Misc/TreasureMapProtection.cs index 55f9d1bf2..5007491f0 100644 --- a/Scripts/Misc/TreasureMapProtection.cs +++ b/Scripts/Misc/TreasureMapProtection.cs @@ -4,73 +4,72 @@ using Server.Regions; namespace Server { - public class TreasureRegion : BaseRegion - { - private const int Range = 5; // No house may be placed within 5 tiles of the treasure + public class TreasureRegion : BaseRegion + { + private const int Range = 5; // No house may be placed within 5 tiles of the treasure - public TreasureRegion( int x, int y, Map map ): base( null, map, DefaultPriority, new Rectangle2D( x - Range, y - Range, 1 + (Range * 2), 1 + (Range * 2) ) ) - { - GoLocation = new Point3D( x, y, map.GetAverageZ( x, y ) ); + public TreasureRegion(int x, int y, Map map) : base(null, map, DefaultPriority, + new Rectangle2D(x - Range, y - Range, 1 + Range * 2, 1 + Range * 2)) + { + GoLocation = new Point3D(x, y, map.GetAverageZ(x, y)); - Register(); - } + Register(); + } - public static void Initialize() - { - string filePath = Path.Combine( Core.BaseDirectory, "Data/treasure.cfg" ); - int i = 0, x = 0, y = 0; + public static void Initialize() + { + string filePath = Path.Combine(Core.BaseDirectory, "Data/treasure.cfg"); + int i = 0, x = 0, y = 0; - if ( File.Exists( filePath ) ) - { - using ( StreamReader ip = new StreamReader( filePath ) ) - { - string line; + if (File.Exists(filePath)) + using (StreamReader ip = new StreamReader(filePath)) + { + string line; - while ( (line = ip.ReadLine()) != null ) - { - i++; + while ((line = ip.ReadLine()) != null) + { + i++; - try - { - string[] split = line.Split( ' ' ); + try + { + string[] split = line.Split(' '); - x = Convert.ToInt32( split[0] ); - y = Convert.ToInt32( split[1] ); + x = Convert.ToInt32(split[0]); + y = Convert.ToInt32(split[1]); - try - { - new TreasureRegion( x, y, Map.Felucca ); - new TreasureRegion( x, y, Map.Trammel ); - } - catch ( Exception e ) - { - Console.WriteLine( "{0} {1} {2} {3}", i, x, y, e ); - } - } - catch - { - Console.WriteLine( "Warning: Error in Line '{0}' of Data/treasure.cfg", line ); - } - } - } - } - } + try + { + new TreasureRegion(x, y, Map.Felucca); + new TreasureRegion(x, y, Map.Trammel); + } + catch (Exception e) + { + Console.WriteLine("{0} {1} {2} {3}", i, x, y, e); + } + } + catch + { + Console.WriteLine("Warning: Error in Line '{0}' of Data/treasure.cfg", line); + } + } + } + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } - public override void OnEnter( Mobile m ) - { - if ( m.AccessLevel > AccessLevel.Player ) - m.SendMessage( "You have entered a protected treasure map area." ); - } + public override void OnEnter(Mobile m) + { + if (m.AccessLevel > AccessLevel.Player) + m.SendMessage("You have entered a protected treasure map area."); + } - public override void OnExit( Mobile m ) - { - if ( m.AccessLevel > AccessLevel.Player ) - m.SendMessage( "You have left a protected treasure map area." ); - } - } + public override void OnExit(Mobile m) + { + if (m.AccessLevel > AccessLevel.Player) + m.SendMessage("You have left a protected treasure map area."); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/ValidationQueue.cs b/Scripts/Misc/ValidationQueue.cs index 67bcd3072..f878d9210 100644 --- a/Scripts/Misc/ValidationQueue.cs +++ b/Scripts/Misc/ValidationQueue.cs @@ -4,52 +4,50 @@ using System.Reflection; namespace Server { - public delegate void ValidationEventHandler(); + public delegate void ValidationEventHandler(); - public static class ValidationQueue - { - public static event ValidationEventHandler StartValidation; + public static class ValidationQueue + { + public static event ValidationEventHandler StartValidation; - public static void Initialize() - { - StartValidation?.Invoke(); + public static void Initialize() + { + StartValidation?.Invoke(); - StartValidation = null; - } - } + StartValidation = null; + } + } - public static class ValidationQueue - { - private static List m_Queue; + public static class ValidationQueue + { + private static List m_Queue; - static ValidationQueue() - { - m_Queue = new List(); - ValidationQueue.StartValidation += ValidateAll; - } + static ValidationQueue() + { + m_Queue = new List(); + ValidationQueue.StartValidation += ValidateAll; + } - public static void Add( T obj ) - { - m_Queue.Add( obj ); - } + public static void Add(T obj) + { + m_Queue.Add(obj); + } - private static void ValidateAll() - { - Type type = typeof( T ); + private static void ValidateAll() + { + Type type = typeof(T); - if ( type != null ) - { - MethodInfo m = type.GetMethod( "Validate", BindingFlags.Instance | BindingFlags.Public ); + if (type != null) + { + MethodInfo m = type.GetMethod("Validate", BindingFlags.Instance | BindingFlags.Public); - if ( m != null ) - { - for ( int i = 0; i < m_Queue.Count; ++i ) - m.Invoke( m_Queue[i], null ); - } - } + if (m != null) + for (int i = 0; i < m_Queue.Count; ++i) + m.Invoke(m_Queue[i], null); + } - m_Queue.Clear(); - m_Queue = null; - } - } -} + m_Queue.Clear(); + m_Queue = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/VendorGenerator.cs b/Scripts/Misc/VendorGenerator.cs index 88e50b860..bf4649989 100644 --- a/Scripts/Misc/VendorGenerator.cs +++ b/Scripts/Misc/VendorGenerator.cs @@ -6,522 +6,519 @@ using Server.Mobiles; namespace Server { - public class VendorGenerator - { - public static void Initialize() - { - CommandSystem.Register( "VendorGen", AccessLevel.Administrator, VendorGen_OnCommand ); - } - - private static Rectangle2D[] m_BritRegions = { - new Rectangle2D( new Point2D( 250, 750 ), new Point2D( 775, 1330 ) ), - new Rectangle2D( new Point2D( 525, 2095 ), new Point2D( 925, 2430 ) ), - new Rectangle2D( new Point2D( 1025, 2155 ), new Point2D( 1265, 2310 ) ), - new Rectangle2D( new Point2D( 1635, 2430 ), new Point2D( 1705, 2508 ) ), - new Rectangle2D( new Point2D( 1775, 2605 ), new Point2D( 2165, 2975 ) ), - new Rectangle2D( new Point2D( 1055, 3520 ), new Point2D( 1570, 4075 ) ), - new Rectangle2D( new Point2D( 2860, 3310 ), new Point2D( 3120, 3630 ) ), - new Rectangle2D( new Point2D( 2470, 1855 ), new Point2D( 3950, 3045 ) ), - new Rectangle2D( new Point2D( 3425, 990 ), new Point2D( 3900, 1455 ) ), - new Rectangle2D( new Point2D( 4175, 735 ), new Point2D( 4840, 1600 ) ), - new Rectangle2D( new Point2D( 2375, 330 ), new Point2D( 3100, 1045 ) ), - new Rectangle2D( new Point2D( 2100, 1090 ), new Point2D( 2310, 1450 ) ), - new Rectangle2D( new Point2D( 1495, 1400 ), new Point2D( 1550, 1475 ) ), - new Rectangle2D( new Point2D( 1085, 1520 ), new Point2D( 1415, 1910 ) ), - new Rectangle2D( new Point2D( 1410, 1500 ), new Point2D( 1745, 1795 ) ), - new Rectangle2D( new Point2D( 5120, 2300 ), new Point2D( 6143, 4095 ) ) - }; - - private static Rectangle2D[] m_IlshRegions = { - new Rectangle2D( new Point2D( 0, 0 ), new Point2D( 288*8, 200*8 ) ) - }; - - [Usage( "VendorGen" )] - [Description( "Generates vendors based on display cases and floor plans. Analyzes the map files, slow." )] - private static void VendorGen_OnCommand( CommandEventArgs e ) - { - Process( Map.Trammel, m_BritRegions ); - Process( Map.Felucca, m_BritRegions ); - Process( Map.Ilshenar, m_IlshRegions ); - } - - private static bool GetFloorZ( Map map, int x, int y, out int z ) - { - LandTile lt = map.Tiles.GetLandTile( x, y ); - - if ( IsFloor( lt.ID ) && map.CanFit( x, y, lt.Z, 16, false, false ) ) - { - z = lt.Z; - return true; - } - - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y ); - - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile t = tiles[i]; - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - - if ( IsStaticFloor( t.ID ) && map.CanFit( x, y, t.Z + (id.Surface ? id.CalcHeight : 0), 16, false, false ) ) - { - z = t.Z + (id.Surface ? id.CalcHeight : 0); - return true; - } - } - - z = 0; - return false; - } - - private static bool IsFloor( Map map, int x, int y, bool canFit ) - { - LandTile lt = map.Tiles.GetLandTile( x, y ); - - if ( IsFloor( lt.ID ) && (canFit||CanFit( map, x, y, lt.Z )) ) - return true; - - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y ); - - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile t = tiles[i]; - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - - if ( IsStaticFloor( t.ID ) && (canFit||CanFit( map, x, y, t.Z + (id.Surface ? id.CalcHeight : 0) )) ) - return true; - } - - return false; - } - - private static bool IsFloor( int itemID ) - { - itemID &= TileData.MaxLandValue; - - return ( itemID >= 0x406 && itemID <= 0x51A ); - } - - private static bool IsStaticFloor( int itemID ) - { - return ( itemID >= 0x495 && itemID <= 0x514 ) - || ( itemID >= 0x519 && itemID <= 0x53A ); - } - - private static bool IsDisplayCase( int itemID ) - { - return ( itemID >= 0xB00 && itemID <= 0xB02 ) - || ( itemID >= 0xB06 && itemID <= 0xB0A ) - || ( itemID >= 0xB0D && itemID <= 0xB17 ); - } - - private static void Process( Map map, Rectangle2D[] regions ) - { - m_ShopTable = new Hashtable(); - m_ShopList = new ArrayList(); - - World.Broadcast( 0x35, true, "Generating vendor spawns for {0}, please wait.", map ); - - for ( int i = 0; i < regions.Length; ++i ) - for ( int x = 0; x < map.Width; ++x ) - for ( int y = 0; y < map.Height; ++y ) - CheckPoint( map, regions[i].X + x, regions[i].Y + y ); - - for ( int i = 0; i < m_ShopList.Count; ++i ) - { - ShopInfo si = (ShopInfo)m_ShopList[i]; - - int xTotal = 0; - int yTotal = 0; - - bool hasSpawner = false; - - for ( int j = 0; !hasSpawner && j < si.m_Floor.Count; ++j ) - { - Point2D fp = (Point2D)si.m_Floor[j]; - - xTotal += fp.X; - yTotal += fp.Y; + public class VendorGenerator + { + private static Rectangle2D[] m_BritRegions = + { + new Rectangle2D(new Point2D(250, 750), new Point2D(775, 1330)), + new Rectangle2D(new Point2D(525, 2095), new Point2D(925, 2430)), + new Rectangle2D(new Point2D(1025, 2155), new Point2D(1265, 2310)), + new Rectangle2D(new Point2D(1635, 2430), new Point2D(1705, 2508)), + new Rectangle2D(new Point2D(1775, 2605), new Point2D(2165, 2975)), + new Rectangle2D(new Point2D(1055, 3520), new Point2D(1570, 4075)), + new Rectangle2D(new Point2D(2860, 3310), new Point2D(3120, 3630)), + new Rectangle2D(new Point2D(2470, 1855), new Point2D(3950, 3045)), + new Rectangle2D(new Point2D(3425, 990), new Point2D(3900, 1455)), + new Rectangle2D(new Point2D(4175, 735), new Point2D(4840, 1600)), + new Rectangle2D(new Point2D(2375, 330), new Point2D(3100, 1045)), + new Rectangle2D(new Point2D(2100, 1090), new Point2D(2310, 1450)), + new Rectangle2D(new Point2D(1495, 1400), new Point2D(1550, 1475)), + new Rectangle2D(new Point2D(1085, 1520), new Point2D(1415, 1910)), + new Rectangle2D(new Point2D(1410, 1500), new Point2D(1745, 1795)), + new Rectangle2D(new Point2D(5120, 2300), new Point2D(6143, 4095)) + }; + + private static Rectangle2D[] m_IlshRegions = + { + new Rectangle2D(new Point2D(0, 0), new Point2D(288 * 8, 200 * 8)) + }; + + private static Hashtable m_ShopTable; + private static ArrayList m_ShopList; + + public static void Initialize() + { + CommandSystem.Register("VendorGen", AccessLevel.Administrator, VendorGen_OnCommand); + } + + [Usage("VendorGen")] + [Description("Generates vendors based on display cases and floor plans. Analyzes the map files, slow.")] + private static void VendorGen_OnCommand(CommandEventArgs e) + { + Process(Map.Trammel, m_BritRegions); + Process(Map.Felucca, m_BritRegions); + Process(Map.Ilshenar, m_IlshRegions); + } + + private static bool GetFloorZ(Map map, int x, int y, out int z) + { + LandTile lt = map.Tiles.GetLandTile(x, y); + + if (IsFloor(lt.ID) && map.CanFit(x, y, lt.Z, 16, false, false)) + { + z = lt.Z; + return true; + } + + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y); + + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile t = tiles[i]; + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + + if (IsStaticFloor(t.ID) && map.CanFit(x, y, t.Z + (id.Surface ? id.CalcHeight : 0), 16, false, false)) + { + z = t.Z + (id.Surface ? id.CalcHeight : 0); + return true; + } + } + + z = 0; + return false; + } + + private static bool IsFloor(Map map, int x, int y, bool canFit) + { + LandTile lt = map.Tiles.GetLandTile(x, y); + + if (IsFloor(lt.ID) && (canFit || CanFit(map, x, y, lt.Z))) + return true; + + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y); + + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile t = tiles[i]; + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + + if (IsStaticFloor(t.ID) && (canFit || CanFit(map, x, y, t.Z + (id.Surface ? id.CalcHeight : 0)))) + return true; + } + + return false; + } + + private static bool IsFloor(int itemID) + { + itemID &= TileData.MaxLandValue; + + return itemID >= 0x406 && itemID <= 0x51A; + } + + private static bool IsStaticFloor(int itemID) + { + return itemID >= 0x495 && itemID <= 0x514 + || itemID >= 0x519 && itemID <= 0x53A; + } + + private static bool IsDisplayCase(int itemID) + { + return itemID >= 0xB00 && itemID <= 0xB02 + || itemID >= 0xB06 && itemID <= 0xB0A + || itemID >= 0xB0D && itemID <= 0xB17; + } + + private static void Process(Map map, Rectangle2D[] regions) + { + m_ShopTable = new Hashtable(); + m_ShopList = new ArrayList(); + + World.Broadcast(0x35, true, "Generating vendor spawns for {0}, please wait.", map); + + for (int i = 0; i < regions.Length; ++i) + for (int x = 0; x < map.Width; ++x) + for (int y = 0; y < map.Height; ++y) + CheckPoint(map, regions[i].X + x, regions[i].Y + y); + + for (int i = 0; i < m_ShopList.Count; ++i) + { + ShopInfo si = (ShopInfo)m_ShopList[i]; + + int xTotal = 0; + int yTotal = 0; + + bool hasSpawner = false; - IPooledEnumerable eable = map.GetItemsInRange( new Point3D( fp.X, fp.Y, 0 ), 0 ); + for (int j = 0; !hasSpawner && j < si.m_Floor.Count; ++j) + { + Point2D fp = (Point2D)si.m_Floor[j]; - foreach ( Spawner item in eable ) - { - hasSpawner = true; - break; - } + xTotal += fp.X; + yTotal += fp.Y; - eable.Free(); + IPooledEnumerable eable = map.GetItemsInRange(new Point3D(fp.X, fp.Y, 0), 0); - if ( hasSpawner ) - break; - } + foreach (Spawner item in eable) + { + hasSpawner = true; + break; + } - if ( hasSpawner ) - continue; - - int xAvg = xTotal / si.m_Floor.Count; - int yAvg = yTotal / si.m_Floor.Count; - - ArrayList names = new ArrayList(); - ShopFlags flags = si.m_Flags; - - if ( (flags & ShopFlags.Armor) != 0 ) - names.Add( "armorer" ); - - if ( (flags & ShopFlags.MetalWeapon) != 0 ) - names.Add( "weaponsmith" ); - - if ( (flags & ShopFlags.ArcheryWeapon) != 0 ) - names.Add( "bowyer" ); - - if ( (flags & ShopFlags.Scroll) != 0 ) - names.Add( "mage" ); - - if ( (flags & ShopFlags.Spellbook) != 0 ) - names.Add( "mage" ); - - if ( (flags & ShopFlags.Bread) != 0 ) - names.Add( "baker" ); - - if ( (flags & ShopFlags.Jewel) != 0 ) - names.Add( "jeweler" ); - - if ( (flags & ShopFlags.Potion) != 0 ) - { - names.Add( "herbalist" ); - names.Add( "alchemist" ); - names.Add( "mage" ); - } - - if ( (flags & ShopFlags.Reagent) != 0 ) - { - names.Add( "mage" ); - names.Add( "herbalist" ); - } - - if ( (flags & ShopFlags.Clothes) != 0 ) - { - names.Add( "tailor" ); - names.Add( "weaver" ); - } - - for ( int j = 0; j < names.Count; ++j ) - { - Point2D cp = Point2D.Zero; - int dist = 100000; - int tz; - - for ( int k = 0; k < si.m_Floor.Count; ++k ) - { - Point2D fp = (Point2D)si.m_Floor[k]; - - int rx = fp.X - xAvg; - int ry = fp.Y - yAvg; - int fd = (int)Math.Sqrt( rx*rx + ry*ry ); - - if ( fd > 0 && fd < 5 ) - fd -= Utility.Random( 10 ); - - if ( fd < dist && GetFloorZ( map, fp.X, fp.Y, out tz ) ) - { - dist = fd; - cp = fp; - } - } + eable.Free(); - if ( cp == Point2D.Zero ) - continue; + if (hasSpawner) + break; + } - int z; + if (hasSpawner) + continue; - if ( !GetFloorZ( map, cp.X, cp.Y, out z ) ) - continue; + int xAvg = xTotal / si.m_Floor.Count; + int yAvg = yTotal / si.m_Floor.Count; - new Spawner( 1, 1, 1, 0, 4, (string)names[j] ).MoveToWorld( new Point3D( cp.X, cp.Y, z ), map ); - } - } + ArrayList names = new ArrayList(); + ShopFlags flags = si.m_Flags; - World.Broadcast( 0x35, true, "Generation complete. {0} spawners generated.", m_ShopList.Count ); - } + if ((flags & ShopFlags.Armor) != 0) + names.Add("armorer"); - private static void CheckPoint( Map map, int x, int y ) - { - if ( IsFloor( map, x, y, true ) ) - CheckFloor( map, x, y ); - } + if ((flags & ShopFlags.MetalWeapon) != 0) + names.Add("weaponsmith"); - private static void CheckFloor( Map map, int x, int y ) - { - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y ); + if ((flags & ShopFlags.ArcheryWeapon) != 0) + names.Add("bowyer"); - for ( int i = 0; i < tiles.Length; ++i ) - { - if ( IsDisplayCase( tiles[i].ID ) ) - { - ProcessDisplayCase( map, tiles, x, y ); - break; - } - } - } + if ((flags & ShopFlags.Scroll) != 0) + names.Add("mage"); - [Flags] - private enum ShopFlags - { - None = 0x000, - Armor = 0x001, - MetalWeapon = 0x002, - Jewel = 0x004, - Reagent = 0x008, - Potion = 0x010, - Bread = 0x020, - Clothes = 0x040, - ArcheryWeapon = 0x080, - Scroll = 0x100, - Spellbook = 0x200 - } - - private static bool IsClothes( int itemID ) - { - if ( itemID >= 0x1515 && itemID <= 0x1518 ) - return true; - - if ( itemID >= 0x152E && itemID <= 0x1531 ) - return true; - - if ( itemID >= 0x1537 && itemID <= 0x154C ) - return true; - - if ( itemID >= 0x1EFD && itemID <= 0x1F04 ) - return true; - - if ( itemID >= 0x170B && itemID <= 0x171C ) - return true; - - return false; - } - - private static bool IsArmor( int itemID ) - { - if ( itemID >= 0x13BB && itemID <= 0x13E2 ) - return true; + if ((flags & ShopFlags.Spellbook) != 0) + names.Add("mage"); - if ( itemID >= 0x13E5 && itemID <= 0x13F2 ) - return true; + if ((flags & ShopFlags.Bread) != 0) + names.Add("baker"); - if ( itemID >= 0x1408 && itemID <= 0x141A ) - return true; + if ((flags & ShopFlags.Jewel) != 0) + names.Add("jeweler"); - if ( itemID >= 0x144E && itemID <= 0x1457 ) - return true; + if ((flags & ShopFlags.Potion) != 0) + { + names.Add("herbalist"); + names.Add("alchemist"); + names.Add("mage"); + } - return false; - } + if ((flags & ShopFlags.Reagent) != 0) + { + names.Add("mage"); + names.Add("herbalist"); + } - private static bool IsMetalWeapon( int itemID ) - { - if ( itemID >= 0xF43 && itemID <= 0xF4E ) - return true; + if ((flags & ShopFlags.Clothes) != 0) + { + names.Add("tailor"); + names.Add("weaver"); + } - if ( itemID >= 0xF51 && itemID <= 0xF52 ) - return true; + for (int j = 0; j < names.Count; ++j) + { + Point2D cp = Point2D.Zero; + int dist = 100000; + int tz; - if ( itemID >= 0xF5C && itemID <= 0xF63 ) - return true; + for (int k = 0; k < si.m_Floor.Count; ++k) + { + Point2D fp = (Point2D)si.m_Floor[k]; - if ( itemID >= 0x13AF && itemID <= 0x13B0 ) - return true; + int rx = fp.X - xAvg; + int ry = fp.Y - yAvg; + int fd = (int)Math.Sqrt(rx * rx + ry * ry); - if ( itemID >= 0x13B5 && itemID <= 0x13BA ) - return true; + if (fd > 0 && fd < 5) + fd -= Utility.Random(10); - if ( itemID >= 0x13FA && itemID <= 0x13FB ) - return true; - - if ( itemID >= 0x13FE && itemID <= 0x1407 ) - return true; - - if ( itemID >= 0x1438 && itemID <= 0x1443 ) - return true; - - return false; - } - - private static bool IsArcheryWeapon( int itemID ) - { - if ( itemID >= 0xF4F && itemID <= 0xF50 ) - return true; - - if ( itemID >= 0x13B1 && itemID <= 0x13B2 ) - return true; + if (fd < dist && GetFloorZ(map, fp.X, fp.Y, out tz)) + { + dist = fd; + cp = fp; + } + } - if ( itemID >= 0x13FC && itemID <= 0x13FD ) - return true; + if (cp == Point2D.Zero) + continue; - return false; - } + int z; - private static ShopFlags ProcessDisplayedItem( int itemID ) - { - itemID &= TileData.MaxItemValue; + if (!GetFloorZ(map, cp.X, cp.Y, out z)) + continue; - ShopFlags res = ShopFlags.None; + new Spawner(1, 1, 1, 0, 4, (string)names[j]).MoveToWorld(new Point3D(cp.X, cp.Y, z), map); + } + } - ItemData id = TileData.ItemTable[itemID]; - TileFlag flags = id.Flags; + World.Broadcast(0x35, true, "Generation complete. {0} spawners generated.", m_ShopList.Count); + } - if ( (flags & TileFlag.Wearable) != 0 ) - { - if ( IsClothes( itemID ) ) - res |= ShopFlags.Clothes; - else if ( IsArmor( itemID ) ) - res |= ShopFlags.Armor; - else if ( IsMetalWeapon( itemID ) ) - res |= ShopFlags.MetalWeapon; - else if ( IsArcheryWeapon( itemID ) ) - res |= ShopFlags.ArcheryWeapon; - } + private static void CheckPoint(Map map, int x, int y) + { + if (IsFloor(map, x, y, true)) + CheckFloor(map, x, y); + } - if ( itemID == 0x98C || itemID == 0x103B || itemID == 0x103C ) - res |= ShopFlags.Bread; + private static void CheckFloor(Map map, int x, int y) + { + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y); - if ( itemID >= 0xF0F && itemID <= 0xF30 ) - res |= ShopFlags.Jewel; + for (int i = 0; i < tiles.Length; ++i) + if (IsDisplayCase(tiles[i].ID)) + { + ProcessDisplayCase(map, tiles, x, y); + break; + } + } - if ( itemID >= 0xEFB && itemID <= 0xF0D ) - res |= ShopFlags.Potion; + private static bool IsClothes(int itemID) + { + if (itemID >= 0x1515 && itemID <= 0x1518) + return true; - if ( itemID >= 0xF78 && itemID <= 0xF91 ) - res |= ShopFlags.Reagent; + if (itemID >= 0x152E && itemID <= 0x1531) + return true; - if ( (itemID >= 0xE35 && itemID <= 0xE3A) || (itemID >= 0xEF4 && itemID <= 0xEF9) || (itemID >= 0x1F2D && itemID <= 0x1F72) ) - res |= ShopFlags.Scroll; + if (itemID >= 0x1537 && itemID <= 0x154C) + return true; - if ( itemID == 0xE38 || itemID == 0xEFA ) - res |= ShopFlags.Spellbook; + if (itemID >= 0x1EFD && itemID <= 0x1F04) + return true; - return res; - } + if (itemID >= 0x170B && itemID <= 0x171C) + return true; - private static void ProcessDisplayCase( Map map, StaticTile[] tiles, int x, int y ) - { - ShopFlags flags = ShopFlags.None; + return false; + } - for ( int i = 0; i < tiles.Length; ++i ) - flags |= ProcessDisplayedItem( tiles[i].ID ); + private static bool IsArmor(int itemID) + { + if (itemID >= 0x13BB && itemID <= 0x13E2) + return true; - if ( flags != ShopFlags.None ) - { - Point2D p = new Point2D( x, y ); - ShopInfo si = (ShopInfo)m_ShopTable[p]; + if (itemID >= 0x13E5 && itemID <= 0x13F2) + return true; - if ( si == null ) - { - ArrayList floor = new ArrayList(); + if (itemID >= 0x1408 && itemID <= 0x141A) + return true; - RecurseFindFloor( map, x, y, floor ); + if (itemID >= 0x144E && itemID <= 0x1457) + return true; - if ( floor.Count == 0 ) - return; + return false; + } - si = new ShopInfo(); - si.m_Flags = flags; - si.m_Floor = floor; - m_ShopList.Add( si ); + private static bool IsMetalWeapon(int itemID) + { + if (itemID >= 0xF43 && itemID <= 0xF4E) + return true; - for ( int i = 0; i < floor.Count; ++i ) - m_ShopTable[(Point2D)floor[i]] = si; - } - else - { - si.m_Flags |= flags; - } - } - } - - private static Hashtable m_ShopTable; - private static ArrayList m_ShopList; - - private class ShopInfo - { - public ShopFlags m_Flags; - public ArrayList m_Floor; - } - - private static bool CanFit( Map map, int x, int y, int z ) - { - bool hasSurface = false; + if (itemID >= 0xF51 && itemID <= 0xF52) + return true; - LandTile lt = map.Tiles.GetLandTile( x, y ); - int lowZ = 0, avgZ = 0, topZ = 0; - - map.GetAverageZ( x, y, ref lowZ, ref avgZ, ref topZ ); - TileFlag landFlags = TileData.LandTable[lt.ID & TileData.MaxLandValue].Flags; - - if ( (landFlags & TileFlag.Impassable) != 0 && topZ > z && (z + 16) > lowZ ) - return false; - if ( (landFlags & TileFlag.Impassable) == 0 && z == avgZ && !lt.Ignored ) - hasSurface = true; - - StaticTile[] staticTiles = map.Tiles.GetStaticTiles( x, y ); - - bool surface, impassable; - - for ( int i = 0; i < staticTiles.Length; ++i ) - { - if ( IsDisplayCase( staticTiles[i].ID ) ) - continue; - - ItemData id = TileData.ItemTable[staticTiles[i].ID & TileData.MaxItemValue]; - - surface = id.Surface; - impassable = id.Impassable; - - if ( (surface || impassable) && (staticTiles[i].Z + id.CalcHeight) > z && (z + 16) > staticTiles[i].Z ) - return false; - if ( surface && !impassable && z == (staticTiles[i].Z + id.CalcHeight) ) - hasSurface = true; - } - - Sector sector = map.GetSector( x, y ); - List items = sector.Items; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( item.AtWorldPoint( x, y ) ) - { - ItemData id = item.ItemData; - surface = id.Surface; - impassable = id.Impassable; - - if ( (surface || impassable) && (item.Z + id.CalcHeight) > z && (z + 16) > item.Z ) - return false; - if ( surface && !impassable && z == (item.Z + id.CalcHeight) ) - hasSurface = true; - } - } - - return hasSurface; - } - - private static void RecurseFindFloor( Map map, int x, int y, ArrayList floor ) - { - Point2D p = new Point2D( x, y ); - - if ( floor.Contains( p ) ) - return; - - floor.Add( p ); - - for ( int xo = -1; xo <= 1; ++xo ) - { - for ( int yo = -1; yo <= 1; ++yo ) - { - if ( (xo != 0 || yo != 0) && IsFloor( map, x + xo, y + yo, false ) ) - RecurseFindFloor( map, x + xo, y + yo, floor ); - } - } - } - } -} + if (itemID >= 0xF5C && itemID <= 0xF63) + return true; + + if (itemID >= 0x13AF && itemID <= 0x13B0) + return true; + + if (itemID >= 0x13B5 && itemID <= 0x13BA) + return true; + + if (itemID >= 0x13FA && itemID <= 0x13FB) + return true; + + if (itemID >= 0x13FE && itemID <= 0x1407) + return true; + + if (itemID >= 0x1438 && itemID <= 0x1443) + return true; + + return false; + } + + private static bool IsArcheryWeapon(int itemID) + { + if (itemID >= 0xF4F && itemID <= 0xF50) + return true; + + if (itemID >= 0x13B1 && itemID <= 0x13B2) + return true; + + if (itemID >= 0x13FC && itemID <= 0x13FD) + return true; + + return false; + } + + private static ShopFlags ProcessDisplayedItem(int itemID) + { + itemID &= TileData.MaxItemValue; + + ShopFlags res = ShopFlags.None; + + ItemData id = TileData.ItemTable[itemID]; + TileFlag flags = id.Flags; + + if ((flags & TileFlag.Wearable) != 0) + { + if (IsClothes(itemID)) + res |= ShopFlags.Clothes; + else if (IsArmor(itemID)) + res |= ShopFlags.Armor; + else if (IsMetalWeapon(itemID)) + res |= ShopFlags.MetalWeapon; + else if (IsArcheryWeapon(itemID)) + res |= ShopFlags.ArcheryWeapon; + } + + if (itemID == 0x98C || itemID == 0x103B || itemID == 0x103C) + res |= ShopFlags.Bread; + + if (itemID >= 0xF0F && itemID <= 0xF30) + res |= ShopFlags.Jewel; + + if (itemID >= 0xEFB && itemID <= 0xF0D) + res |= ShopFlags.Potion; + + if (itemID >= 0xF78 && itemID <= 0xF91) + res |= ShopFlags.Reagent; + + if (itemID >= 0xE35 && itemID <= 0xE3A || itemID >= 0xEF4 && itemID <= 0xEF9 || + itemID >= 0x1F2D && itemID <= 0x1F72) + res |= ShopFlags.Scroll; + + if (itemID == 0xE38 || itemID == 0xEFA) + res |= ShopFlags.Spellbook; + + return res; + } + + private static void ProcessDisplayCase(Map map, StaticTile[] tiles, int x, int y) + { + ShopFlags flags = ShopFlags.None; + + for (int i = 0; i < tiles.Length; ++i) + flags |= ProcessDisplayedItem(tiles[i].ID); + + if (flags != ShopFlags.None) + { + Point2D p = new Point2D(x, y); + ShopInfo si = (ShopInfo)m_ShopTable[p]; + + if (si == null) + { + ArrayList floor = new ArrayList(); + + RecurseFindFloor(map, x, y, floor); + + if (floor.Count == 0) + return; + + si = new ShopInfo(); + si.m_Flags = flags; + si.m_Floor = floor; + m_ShopList.Add(si); + + for (int i = 0; i < floor.Count; ++i) + m_ShopTable[(Point2D)floor[i]] = si; + } + else + { + si.m_Flags |= flags; + } + } + } + + private static bool CanFit(Map map, int x, int y, int z) + { + bool hasSurface = false; + + LandTile lt = map.Tiles.GetLandTile(x, y); + int lowZ = 0, avgZ = 0, topZ = 0; + + map.GetAverageZ(x, y, ref lowZ, ref avgZ, ref topZ); + TileFlag landFlags = TileData.LandTable[lt.ID & TileData.MaxLandValue].Flags; + + if ((landFlags & TileFlag.Impassable) != 0 && topZ > z && z + 16 > lowZ) + return false; + if ((landFlags & TileFlag.Impassable) == 0 && z == avgZ && !lt.Ignored) + hasSurface = true; + + StaticTile[] staticTiles = map.Tiles.GetStaticTiles(x, y); + + bool surface, impassable; + + for (int i = 0; i < staticTiles.Length; ++i) + { + if (IsDisplayCase(staticTiles[i].ID)) + continue; + + ItemData id = TileData.ItemTable[staticTiles[i].ID & TileData.MaxItemValue]; + + surface = id.Surface; + impassable = id.Impassable; + + if ((surface || impassable) && staticTiles[i].Z + id.CalcHeight > z && z + 16 > staticTiles[i].Z) + return false; + if (surface && !impassable && z == staticTiles[i].Z + id.CalcHeight) + hasSurface = true; + } + + Sector sector = map.GetSector(x, y); + List items = sector.Items; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (item.AtWorldPoint(x, y)) + { + ItemData id = item.ItemData; + surface = id.Surface; + impassable = id.Impassable; + + if ((surface || impassable) && item.Z + id.CalcHeight > z && z + 16 > item.Z) + return false; + if (surface && !impassable && z == item.Z + id.CalcHeight) + hasSurface = true; + } + } + + return hasSurface; + } + + private static void RecurseFindFloor(Map map, int x, int y, ArrayList floor) + { + Point2D p = new Point2D(x, y); + + if (floor.Contains(p)) + return; + + floor.Add(p); + + for (int xo = -1; xo <= 1; ++xo) + for (int yo = -1; yo <= 1; ++yo) + if ((xo != 0 || yo != 0) && IsFloor(map, x + xo, y + yo, false)) + RecurseFindFloor(map, x + xo, y + yo, floor); + } + + [Flags] + private enum ShopFlags + { + None = 0x000, + Armor = 0x001, + MetalWeapon = 0x002, + Jewel = 0x004, + Reagent = 0x008, + Potion = 0x010, + Bread = 0x020, + Clothes = 0x040, + ArcheryWeapon = 0x080, + Scroll = 0x100, + Spellbook = 0x200 + } + + private class ShopInfo + { + public ShopFlags m_Flags; + public ArrayList m_Floor; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/WebStatus.cs b/Scripts/Misc/WebStatus.cs index b61435958..891cb0a75 100644 --- a/Scripts/Misc/WebStatus.cs +++ b/Scripts/Misc/WebStatus.cs @@ -1,194 +1,185 @@ #region References + using System; using System.IO; using System.Linq; using System.Net; using System.Text; - using Server.Guilds; using Server.Network; + #endregion namespace Server.Misc { - public class StatusPage : Timer - { - public static readonly bool Enabled = false; + public class StatusPage : Timer + { + public static readonly bool Enabled = false; - private static HttpListener _Listener; + private static HttpListener _Listener; - private static string _StatusPage = string.Empty; - private static byte[] _StatusBuffer = new byte[0]; + private static string _StatusPage = string.Empty; + private static byte[] _StatusBuffer = new byte[0]; - private static readonly object _StatusLock = new object(); + private static readonly object _StatusLock = new object(); - public static void Initialize() - { - if (!Enabled) - { - return; - } + public StatusPage() + : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(60.0)) + { + Priority = TimerPriority.FiveSeconds; + } - new StatusPage().Start(); + public static void Initialize() + { + if (!Enabled) return; - Listen(); - } + new StatusPage().Start(); - private static void Listen() - { - if (!HttpListener.IsSupported) - { - return; - } + Listen(); + } - if (_Listener == null) - { - _Listener = new HttpListener(); - _Listener.Prefixes.Add("http://*:80/status/"); - _Listener.Start(); - } - else if (!_Listener.IsListening) - { - _Listener.Start(); - } + private static void Listen() + { + if (!HttpListener.IsSupported) return; - if (_Listener.IsListening) - { - _Listener.BeginGetContext(ListenerCallback, null); - } - } + if (_Listener == null) + { + _Listener = new HttpListener(); + _Listener.Prefixes.Add("http://*:80/status/"); + _Listener.Start(); + } + else if (!_Listener.IsListening) + { + _Listener.Start(); + } - private static void ListenerCallback(IAsyncResult result) - { - try - { - var context = _Listener.EndGetContext(result); + if (_Listener.IsListening) _Listener.BeginGetContext(ListenerCallback, null); + } - byte[] buffer; + private static void ListenerCallback(IAsyncResult result) + { + try + { + HttpListenerContext context = _Listener.EndGetContext(result); - lock (_StatusLock) - { - buffer = _StatusBuffer; - } + byte[] buffer; - context.Response.ContentLength64 = buffer.Length; - context.Response.OutputStream.Write(buffer, 0, buffer.Length); - context.Response.OutputStream.Close(); - } - catch - { } + lock (_StatusLock) + { + buffer = _StatusBuffer; + } - Listen(); - } + context.Response.ContentLength64 = buffer.Length; + context.Response.OutputStream.Write(buffer, 0, buffer.Length); + context.Response.OutputStream.Close(); + } + catch + { + } - private static string Encode(string input) - { - var sb = new StringBuilder(input); + Listen(); + } - sb.Replace("&", "&"); - sb.Replace("<", "<"); - sb.Replace(">", ">"); - sb.Replace("\"", """); - sb.Replace("'", "'"); + private static string Encode(string input) + { + StringBuilder sb = new StringBuilder(input); - return sb.ToString(); - } + sb.Replace("&", "&"); + sb.Replace("<", "<"); + sb.Replace(">", ">"); + sb.Replace("\"", """); + sb.Replace("'", "'"); - public StatusPage() - : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(60.0)) - { - Priority = TimerPriority.FiveSeconds; - } + return sb.ToString(); + } - protected override void OnTick() - { - if (!Directory.Exists("web")) - { - Directory.CreateDirectory("web"); - } + protected override void OnTick() + { + if (!Directory.Exists("web")) Directory.CreateDirectory("web"); - using (var op = new StreamWriter("web/status.html")) - { - op.WriteLine(""); - op.WriteLine(""); - op.WriteLine(" "); - op.WriteLine(" " + ServerList.ServerName + " Server Status"); - op.WriteLine(" "); - op.WriteLine(" "); - op.WriteLine(" "); - op.WriteLine("

RunUO Server Status

"); - op.WriteLine("

Online clients

"); - op.WriteLine(" "); - op.WriteLine(" "); + using (StreamWriter op = new StreamWriter("web/status.html")) + { + op.WriteLine(""); + op.WriteLine(""); + op.WriteLine(" "); + op.WriteLine(" " + ServerList.ServerName + " Server Status"); + op.WriteLine(" "); + op.WriteLine(" "); + op.WriteLine(" "); + op.WriteLine("

RunUO Server Status

"); + op.WriteLine("

Online clients

"); + op.WriteLine("
NameLocationKillsKarma/Fame
"); + op.WriteLine( + " "); - var index = 0; + int index = 0; - foreach (var m in NetState.Instances.Where(state => state.Mobile != null).Select(state => state.Mobile)) - { - ++index; + foreach (Mobile m in NetState.Instances.Where(state => state.Mobile != null).Select(state => state.Mobile)) + { + ++index; - var g = m.Guild as Guild; + Guild g = m.Guild as Guild; - op.Write(" "); - } + op.Write(""); + } - op.WriteLine(" "); - op.WriteLine("
NameLocationKillsKarma/Fame
"); + op.Write("
"); - if (g != null) - { - op.Write(Encode(m.Name)); - op.Write(" ["); + if (g != null) + { + op.Write(Encode(m.Name)); + op.Write(" ["); - var title = m.GuildTitle; + string title = m.GuildTitle; - title = title != null ? title.Trim() : string.Empty; + title = title != null ? title.Trim() : string.Empty; - if (title.Length > 0) - { - op.Write(Encode(title)); - op.Write(", "); - } + if (title.Length > 0) + { + op.Write(Encode(title)); + op.Write(", "); + } - op.Write(Encode(g.Abbreviation)); + op.Write(Encode(g.Abbreviation)); - op.Write(']'); - } - else - { - op.Write(Encode(m.Name)); - } + op.Write(']'); + } + else + { + op.Write(Encode(m.Name)); + } - op.Write(""); - op.Write(m.X); - op.Write(", "); - op.Write(m.Y); - op.Write(", "); - op.Write(m.Z); - op.Write(" ("); - op.Write(m.Map); - op.Write(")"); - op.Write(m.Kills); - op.Write(""); - op.Write(m.Karma); - op.Write(" / "); - op.Write(m.Fame); - op.WriteLine("
"); + op.Write(m.X); + op.Write(", "); + op.Write(m.Y); + op.Write(", "); + op.Write(m.Z); + op.Write(" ("); + op.Write(m.Map); + op.Write(")"); + op.Write(m.Kills); + op.Write(""); + op.Write(m.Karma); + op.Write(" / "); + op.Write(m.Fame); + op.WriteLine("
"); - op.WriteLine(" "); - op.WriteLine(""); - } + op.WriteLine(" "); + op.WriteLine(" "); + op.WriteLine(" "); + op.WriteLine(""); + } - lock (_StatusLock) - { - _StatusPage = File.ReadAllText("web/status.html"); - _StatusBuffer = Encoding.UTF8.GetBytes(_StatusPage); - } - } - } + lock (_StatusLock) + { + _StatusPage = File.ReadAllText("web/status.html"); + _StatusBuffer = Encoding.UTF8.GetBytes(_StatusPage); + } + } + } } \ No newline at end of file diff --git a/Scripts/Misc/WeightOverloading.cs b/Scripts/Misc/WeightOverloading.cs index 28278565c..bbb9a3d68 100644 --- a/Scripts/Misc/WeightOverloading.cs +++ b/Scripts/Misc/WeightOverloading.cs @@ -1,124 +1,126 @@ using System; using Server.Mobiles; +using Server.Spells.Ninjitsu; namespace Server.Misc { - public enum DFAlgorithm - { - Standard, - PainSpike - } + public enum DFAlgorithm + { + Standard, + PainSpike + } - public class WeightOverloading - { - public static void Initialize() - { - EventSink.Movement += EventSink_Movement; - } + public class WeightOverloading + { + public const int OverloadAllowance = 4; // We can be four stones overweight without getting fatigued - public static DFAlgorithm DFA { get; set; } + public static DFAlgorithm DFA{ get; set; } - public static void FatigueOnDamage( Mobile m, int damage ) - { - double fatigue = 0.0; + public static void Initialize() + { + EventSink.Movement += EventSink_Movement; + } - switch ( DFA ) - { - case DFAlgorithm.Standard: - { - fatigue = (damage * (100.0 / m.Hits) * ((double)m.Stam / 100)) - 5.0; - break; - } - case DFAlgorithm.PainSpike: - { - fatigue = (damage * ((100.0 / m.Hits) + ((50.0 + m.Stam) / 100) - 1.0)) - 5.0; - break; - } - } + public static void FatigueOnDamage(Mobile m, int damage) + { + double fatigue = 0.0; - if ( fatigue > 0 ) - m.Stam -= (int)fatigue; - } + switch (DFA) + { + case DFAlgorithm.Standard: + { + fatigue = damage * (100.0 / m.Hits) * ((double)m.Stam / 100) - 5.0; + break; + } + case DFAlgorithm.PainSpike: + { + fatigue = damage * (100.0 / m.Hits + (50.0 + m.Stam) / 100 - 1.0) - 5.0; + break; + } + } - public const int OverloadAllowance = 4; // We can be four stones overweight without getting fatigued + if (fatigue > 0) + m.Stam -= (int)fatigue; + } - public static int GetMaxWeight( Mobile m ) - { - //return ((( Core.ML && m.Race == Race.Human) ? 100 : 40 ) + (int)(3.5 * m.Str)); - //Moved to core virtual method for use there + public static int GetMaxWeight(Mobile m) + { + //return ((( Core.ML && m.Race == Race.Human) ? 100 : 40 ) + (int)(3.5 * m.Str)); + //Moved to core virtual method for use there - return m.MaxWeight; - } + return m.MaxWeight; + } - public static void EventSink_Movement( MovementEventArgs e ) - { - Mobile from = e.Mobile; + public static void EventSink_Movement(MovementEventArgs e) + { + Mobile from = e.Mobile; - if ( !from.Alive || from.AccessLevel > AccessLevel.Player ) - return; + if (!from.Alive || from.AccessLevel > AccessLevel.Player) + return; - if ( !from.Player ) - { - // Else it won't work on monsters. - Spells.Ninjitsu.DeathStrike.AddStep( from ); - return; - } + if (!from.Player) + { + // Else it won't work on monsters. + DeathStrike.AddStep(from); + return; + } - int maxWeight = GetMaxWeight( from ) + OverloadAllowance; - int overWeight = (Mobile.BodyWeight + from.TotalWeight) - maxWeight; + int maxWeight = GetMaxWeight(from) + OverloadAllowance; + int overWeight = Mobile.BodyWeight + from.TotalWeight - maxWeight; - if ( overWeight > 0 ) - { - from.Stam -= GetStamLoss( from, overWeight, (e.Direction & Direction.Running) != 0 ); + if (overWeight > 0) + { + from.Stam -= GetStamLoss(from, overWeight, (e.Direction & Direction.Running) != 0); - if ( from.Stam == 0 ) - { - from.SendLocalizedMessage( 500109 ); // You are too fatigued to move, because you are carrying too much weight! - e.Blocked = true; - return; - } - } + if (from.Stam == 0) + { + from.SendLocalizedMessage( + 500109); // You are too fatigued to move, because you are carrying too much weight! + e.Blocked = true; + return; + } + } - if ( ((from.Stam * 100) / Math.Max( from.StamMax, 1 )) < 10 ) - --from.Stam; + if (from.Stam * 100 / Math.Max(from.StamMax, 1) < 10) + --from.Stam; - if ( from.Stam == 0 ) - { - from.SendLocalizedMessage( 500110 ); // You are too fatigued to move. - e.Blocked = true; - return; - } + if (from.Stam == 0) + { + from.SendLocalizedMessage(500110); // You are too fatigued to move. + e.Blocked = true; + return; + } - if ( from is PlayerMobile pm ) - { - int amt = ( pm.Mounted ? 48 : 16 ); + if (from is PlayerMobile pm) + { + int amt = pm.Mounted ? 48 : 16; - if ( (++pm.StepsTaken % amt) == 0 ) - --pm.Stam; - } + if (++pm.StepsTaken % amt == 0) + --pm.Stam; + } - Spells.Ninjitsu.DeathStrike.AddStep( from ); - } + DeathStrike.AddStep(from); + } - public static int GetStamLoss( Mobile from, int overWeight, bool running ) - { - int loss = 5 + (overWeight / 25); + public static int GetStamLoss(Mobile from, int overWeight, bool running) + { + int loss = 5 + overWeight / 25; - if ( from.Mounted ) - loss /= 3; + if (from.Mounted) + loss /= 3; - if ( running ) - loss *= 2; + if (running) + loss *= 2; - return loss; - } + return loss; + } - public static bool IsOverloaded( Mobile m ) - { - if ( !m.Player || !m.Alive || m.AccessLevel > AccessLevel.Player ) - return false; + public static bool IsOverloaded(Mobile m) + { + if (!m.Player || !m.Alive || m.AccessLevel > AccessLevel.Player) + return false; - return ( (Mobile.BodyWeight + m.TotalWeight) > (GetMaxWeight( m ) + OverloadAllowance) ); - } - } -} + return Mobile.BodyWeight + m.TotalWeight > GetMaxWeight(m) + OverloadAllowance; + } + } +} \ No newline at end of file diff --git a/Scripts/Misc/WelcomeTimer.cs b/Scripts/Misc/WelcomeTimer.cs index ee8c5334c..24b1fc2bb 100644 --- a/Scripts/Misc/WelcomeTimer.cs +++ b/Scripts/Misc/WelcomeTimer.cs @@ -2,51 +2,52 @@ using System; namespace Server.Misc { - /// - /// This timer spouts some welcome messages to a user at a set interval. It is used on character creation and login. - /// - public class WelcomeTimer : Timer - { - private Mobile m_Mobile; - private int m_State, m_Count; + /// + /// This timer spouts some welcome messages to a user at a set interval. It is used on character creation and login. + /// + public class WelcomeTimer : Timer + { + private static string[] m_Messages = TestCenter.Enabled + ? new[] + { + "Welcome to this test shard. You are able to customize your character's stats and skills at anytime to anything you wish. To see the commands to do this just say 'help'.", + "You will find a bank check worth 1,000,000 gold in your bank!", + "A spellbook and a bag of reagents has been placed into your bank box.", + "Various tools have been placed into your bank.", + "Various raw materials like ingots, logs, feathers, hides, bottles, etc, have been placed into your bank.", + "5 unmarked recall runes, 5 Felucca moonstones and 5 Trammel moonstones have been placed into your bank box.", + "One of each level of treasure map has been placed in your bank box.", + "You will find 9000 silver pieces deposited into your bank box. Spend it as you see fit and enjoy yourself!", + "You will find 9000 gold pieces deposited into your bank box. Spend it as you see fit and enjoy yourself!", + "A bag of PowerScrolls has been placed in your bank box." + } + : new[] + { + //Yes, this message is a pathetic message, It's suggested that you change it. + "Welcome to this shard.", + "Please enjoy your stay." + }; - private static string[] m_Messages = ( TestCenter.Enabled ? - new[] - { - "Welcome to this test shard. You are able to customize your character's stats and skills at anytime to anything you wish. To see the commands to do this just say 'help'.", - "You will find a bank check worth 1,000,000 gold in your bank!", - "A spellbook and a bag of reagents has been placed into your bank box.", - "Various tools have been placed into your bank.", - "Various raw materials like ingots, logs, feathers, hides, bottles, etc, have been placed into your bank.", - "5 unmarked recall runes, 5 Felucca moonstones and 5 Trammel moonstones have been placed into your bank box.", - "One of each level of treasure map has been placed in your bank box.", - "You will find 9000 silver pieces deposited into your bank box. Spend it as you see fit and enjoy yourself!", - "You will find 9000 gold pieces deposited into your bank box. Spend it as you see fit and enjoy yourself!", - "A bag of PowerScrolls has been placed in your bank box." - } : - new[] - { //Yes, this message is a pathetic message, It's suggested that you change it. - "Welcome to this shard.", - "Please enjoy your stay." - } ); + private Mobile m_Mobile; + private int m_State, m_Count; - public WelcomeTimer( Mobile m ) : this( m, m_Messages.Length ) - { - } + public WelcomeTimer(Mobile m) : this(m, m_Messages.Length) + { + } - public WelcomeTimer( Mobile m, int count ) : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 10.0 ) ) - { - m_Mobile = m; - m_Count = count; - } + public WelcomeTimer(Mobile m, int count) : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(10.0)) + { + m_Mobile = m; + m_Count = count; + } - protected override void OnTick() - { - if ( m_State < m_Count ) - m_Mobile.SendMessage( 0x35, m_Messages[m_State++] ); + protected override void OnTick() + { + if (m_State < m_Count) + m_Mobile.SendMessage(0x35, m_Messages[m_State++]); - if ( m_State == m_Count ) - Stop(); - } - } + if (m_State == m_Count) + Stop(); + } + } } \ No newline at end of file diff --git a/Scripts/Misc/uoamVendors.cs b/Scripts/Misc/uoamVendors.cs index 032d4d551..ab6a64645 100644 --- a/Scripts/Misc/uoamVendors.cs +++ b/Scripts/Misc/uoamVendors.cs @@ -1,350 +1,350 @@ using System; using System.Collections.Generic; using System.IO; -using Server.Mobiles; using Server.Commands; +using Server.Mobiles; // Version 0.8 namespace Server { - public class UOAMVendorGenerator - { - private static int m_Count; + public class UOAMVendorGenerator + { + //configuration + private const int + NPCCount = 2; //2 npcs per type (so a mage spawner will spawn 2 npcs, a alchemist and herbalist spawner will spawn 4 npcs total) - //configuration - private const int NPCCount = 2;//2 npcs per type (so a mage spawner will spawn 2 npcs, a alchemist and herbalist spawner will spawn 4 npcs total) - private const int HomeRange = 5;//How far should they wander? - private const bool TotalRespawn = true;//Should we spawn them up right away? - private static TimeSpan MinTime = TimeSpan.FromMinutes( 2.5 );//min spawn time - private static TimeSpan MaxTime = TimeSpan.FromMinutes( 10.0 );//max spawn time - private const int Team = 0;//"team" the npcs are on + private const int HomeRange = 5; //How far should they wander? + private const bool TotalRespawn = true; //Should we spawn them up right away? + private const int Team = 0; //"team" the npcs are on + private static int m_Count; + private static TimeSpan MinTime = TimeSpan.FromMinutes(2.5); //min spawn time + private static TimeSpan MaxTime = TimeSpan.FromMinutes(10.0); //max spawn time - public static void Initialize() - { - CommandSystem.Register( "UOAMVendors", AccessLevel.Administrator, Generate_OnCommand ); - } + public static void Initialize() + { + CommandSystem.Register("UOAMVendors", AccessLevel.Administrator, Generate_OnCommand); + } - [Usage( "UOAMVendors" )] - [Description( "Generates vendor spawners from Data/Common.MAP (taken from UOAutoMap)" )] - private static void Generate_OnCommand( CommandEventArgs e ) - { - Parse( e.Mobile ); - } + [Usage("UOAMVendors")] + [Description("Generates vendor spawners from Data/Common.MAP (taken from UOAutoMap)")] + private static void Generate_OnCommand(CommandEventArgs e) + { + Parse(e.Mobile); + } - public static void Parse( Mobile from ) - { - string vendor_path = Path.Combine( Core.BaseDirectory, "Data/Common.map" ); - m_Count = 0; + public static void Parse(Mobile from) + { + string vendor_path = Path.Combine(Core.BaseDirectory, "Data/Common.map"); + m_Count = 0; - if ( File.Exists( vendor_path ) ) - { - from.SendMessage( "Generating Vendors..." ); + if (File.Exists(vendor_path)) + { + from.SendMessage("Generating Vendors..."); - using ( StreamReader ip = new StreamReader( vendor_path ) ) - { - string line; + using (StreamReader ip = new StreamReader(vendor_path)) + { + string line; - while ( (line = ip.ReadLine()) != null ) - { - int indexOf = line.IndexOf( ':' ); + while ((line = ip.ReadLine()) != null) + { + int indexOf = line.IndexOf(':'); - if ( indexOf == -1 ) - continue; + if (indexOf == -1) + continue; - string type = line.Substring( 0, ++indexOf ).Trim(); - string sub = line.Substring( indexOf ).Trim(); + string type = line.Substring(0, ++indexOf).Trim(); + string sub = line.Substring(indexOf).Trim(); - string[] split = sub.Split( ' ' ); + string[] split = sub.Split(' '); - if ( split.Length < 3 ) - continue; + if (split.Length < 3) + continue; - split = new[]{ type, split[0], split[1], split[2] }; + split = new[] { type, split[0], split[1], split[2] }; - switch(split[0].ToLower()) - { - case "-healer:": - PlaceNPC( split[1], split[2], split[3], "Healer", "HealerGuildmaster" ); - break; - case "-baker:": - PlaceNPC( split[1], split[2], split[3], "Baker" ); - break; - case "-vet:": - PlaceNPC( split[1], split[2], split[3], "Veterinarian" ); - break; - case "-gypsymaiden:": - PlaceNPC( split[1], split[2], split[3], "GypsyMaiden" ); - break; - case "-gypsybank:": - PlaceNPC( split[1], split[2], split[3], "GypsyBanker" ); - break; - case "-bank:": - PlaceNPC( split[1], split[2], split[3], "Banker", "Minter" ); - break; - case "-inn:": - PlaceNPC( split[1], split[2], split[3], "Innkeeper" ); - break; - case "-provisioner:": - PlaceNPC( split[1], split[2], split[3], "Provisioner", "Cobbler" ); - break; - case "-tailor:": - PlaceNPC( split[1], split[2], split[3], "Tailor", "Weaver", "TailorGuildmaster" ); - break; - case "-tavern:": - PlaceNPC( split[1], split[2], split[3], "Tavernkeeper", "Waiter", "Cook", "Barkeeper" ); - break; - case "-reagents:": - PlaceNPC( split[1], split[2], split[3], "Herbalist", "Alchemist", "CustomHairstylist" ); - break; - case "-fortuneteller:": - PlaceNPC( split[1], split[2], split[3], "FortuneTeller" ); - break; - case "-holymage:": - PlaceNPC( split[1], split[2], split[3], "HolyMage" ); - break; - case "-chivalrykeeper:": - PlaceNPC( split[1], split[2], split[3], "KeeperOfChivalry" ); - break; - case "-mage:": - PlaceNPC( split[1], split[2], split[3], "Mage", "Alchemist", "MageGuildmaster" ); - break; - case "-arms:": - PlaceNPC( split[1], split[2], split[3], "Armorer", "Weaponsmith" ); - break; - case "-tinker:": - PlaceNPC( split[1], split[2], split[3], "Tinker", "TinkerGuildmaster" ); - break; - case "-gypsystable:": - PlaceNPC( split[1], split[2], split[3], "GypsyAnimalTrainer" ); - break; - case "-stable:": - PlaceNPC( split[1], split[2], split[3], "AnimalTrainer" ); - break; - case "-blacksmith:": - PlaceNPC( split[1], split[2], split[3], "Blacksmith", "BlacksmithGuildmaster" ); - break; - case "-bowyer:": - case "-fletcher:": - PlaceNPC( split[1], split[2], split[3], "Bowyer" ); - break; - case "-carpenter:": - PlaceNPC( split[1], split[2], split[3], "Carpenter", "Architect", "RealEstateBroker" ); - break; - case "-butcher:": - PlaceNPC( split[1], split[2], split[3], "Butcher" ); - break; - case "-jeweler:": - PlaceNPC( split[1], split[2], split[3], "Jeweler" ); - break; - case "-tanner:": - PlaceNPC( split[1], split[2], split[3], "Tanner", "Furtrader" ); - break; - case "-bard:": - PlaceNPC( split[1], split[2], split[3], "Bard", "BardGuildmaster" ); - break; - case "-market:": - PlaceNPC( split[1], split[2], split[3], "Butcher", "Farmer" ); - break; - case "-library:": - PlaceNPC( split[1], split[2], split[3], "Scribe" ); - break; - case "-shipwright:": - PlaceNPC( split[1], split[2], split[3], "Shipwright", "Mapmaker" ); - break; - case "-docks:": - PlaceNPC( split[1], split[2], split[3], "Fisherman" ); - break; + switch (split[0].ToLower()) + { + case "-healer:": + PlaceNPC(split[1], split[2], split[3], "Healer", "HealerGuildmaster"); + break; + case "-baker:": + PlaceNPC(split[1], split[2], split[3], "Baker"); + break; + case "-vet:": + PlaceNPC(split[1], split[2], split[3], "Veterinarian"); + break; + case "-gypsymaiden:": + PlaceNPC(split[1], split[2], split[3], "GypsyMaiden"); + break; + case "-gypsybank:": + PlaceNPC(split[1], split[2], split[3], "GypsyBanker"); + break; + case "-bank:": + PlaceNPC(split[1], split[2], split[3], "Banker", "Minter"); + break; + case "-inn:": + PlaceNPC(split[1], split[2], split[3], "Innkeeper"); + break; + case "-provisioner:": + PlaceNPC(split[1], split[2], split[3], "Provisioner", "Cobbler"); + break; + case "-tailor:": + PlaceNPC(split[1], split[2], split[3], "Tailor", "Weaver", "TailorGuildmaster"); + break; + case "-tavern:": + PlaceNPC(split[1], split[2], split[3], "Tavernkeeper", "Waiter", "Cook", "Barkeeper"); + break; + case "-reagents:": + PlaceNPC(split[1], split[2], split[3], "Herbalist", "Alchemist", "CustomHairstylist"); + break; + case "-fortuneteller:": + PlaceNPC(split[1], split[2], split[3], "FortuneTeller"); + break; + case "-holymage:": + PlaceNPC(split[1], split[2], split[3], "HolyMage"); + break; + case "-chivalrykeeper:": + PlaceNPC(split[1], split[2], split[3], "KeeperOfChivalry"); + break; + case "-mage:": + PlaceNPC(split[1], split[2], split[3], "Mage", "Alchemist", "MageGuildmaster"); + break; + case "-arms:": + PlaceNPC(split[1], split[2], split[3], "Armorer", "Weaponsmith"); + break; + case "-tinker:": + PlaceNPC(split[1], split[2], split[3], "Tinker", "TinkerGuildmaster"); + break; + case "-gypsystable:": + PlaceNPC(split[1], split[2], split[3], "GypsyAnimalTrainer"); + break; + case "-stable:": + PlaceNPC(split[1], split[2], split[3], "AnimalTrainer"); + break; + case "-blacksmith:": + PlaceNPC(split[1], split[2], split[3], "Blacksmith", "BlacksmithGuildmaster"); + break; + case "-bowyer:": + case "-fletcher:": + PlaceNPC(split[1], split[2], split[3], "Bowyer"); + break; + case "-carpenter:": + PlaceNPC(split[1], split[2], split[3], "Carpenter", "Architect", "RealEstateBroker"); + break; + case "-butcher:": + PlaceNPC(split[1], split[2], split[3], "Butcher"); + break; + case "-jeweler:": + PlaceNPC(split[1], split[2], split[3], "Jeweler"); + break; + case "-tanner:": + PlaceNPC(split[1], split[2], split[3], "Tanner", "Furtrader"); + break; + case "-bard:": + PlaceNPC(split[1], split[2], split[3], "Bard", "BardGuildmaster"); + break; + case "-market:": + PlaceNPC(split[1], split[2], split[3], "Butcher", "Farmer"); + break; + case "-library:": + PlaceNPC(split[1], split[2], split[3], "Scribe"); + break; + case "-shipwright:": + PlaceNPC(split[1], split[2], split[3], "Shipwright", "Mapmaker"); + break; + case "-docks:": + PlaceNPC(split[1], split[2], split[3], "Fisherman"); + break; - case "-beekeeper:": - PlaceNPC( split[1], split[2], split[3], "Beekeeper" ); - break; - - - // Guilds & Misc - case "-tinkers guild:": - PlaceNPC( split[1], split[2], split[3], "TinkerGuildmaster" ); - break; - case "-blacksmiths guild:": - PlaceNPC( split[1], split[2], split[3], "BlacksmithGuildmaster" ); - break; - case "-sorcerors guild:": - PlaceNPC( split[1], split[2], split[3], "MageGuildmaster" ); - break; - case "-customs:": break; - case "-painter:": break; - case "-theater:": break; - case "-warriors guild:": - PlaceNPC( split[1], split[2], split[3], "WarriorGuildmaster" ); - break; - case "-archers guild:": - PlaceNPC( split[1], split[2], split[3], "RangerGuildmaster" ); - break; - case "-thieves guild:": - PlaceNPC( split[1], split[2], split[3], "ThiefGuildmaster" ); - break; - case "-miners guild:": - PlaceNPC( split[1], split[2], split[3], "MinerGuildmaster" ); - break; - case "-fishermans guild:": - PlaceNPC( split[1], split[2], split[3], "FisherGuildmaster" ); - break; - case "-merchants guild:": - PlaceNPC( split[1], split[2], split[3], "MerchantGuildmaster" ); - break; - case "-illusionists guild:": break; - case "-armourers guild:": break; - case "-sorcerers guild:": break; - case "-mages guild:": - PlaceNPC( split[1], split[2], split[3], "MageGuildmaster" ); - break; - case "-weapons guild:": break; - case "-bardic guild:": - PlaceNPC( split[1], split[2], split[3], "BardGuildmaster" ); - break; - case "-rogues guild:": - break; + case "-beekeeper:": + PlaceNPC(split[1], split[2], split[3], "Beekeeper"); + break; - // Skip - case "+landmark:": - case "-point of interest:": - case "+shrine:": - case "+moongate:": - case "+dungeon:": - case "+scenic:": - case "-gate:": - case "+Body of Water:": - case "+ruins:": - case "+teleporter:": - case "+Terrain:": - case "-exit:": - case "-bridge:": - case "-other:": - case "+champion:": - case "-stairs:": - case "-guild:": - case "+graveyard:": - case "+Island:": - case "+town:": - break; - /*default: - Console.WriteLine(split[0]); - break;*/ - } - } - } - from.SendMessage( "Done, added {0} spawners",m_Count ); - } - else - { - from.SendMessage( "{0} not found!", vendor_path ); - } - } - public static void PlaceNPC( string sx, string sy, string sm, params string[] types ) - { - if ( types.Length == 0 ) - return; + // Guilds & Misc + case "-tinkers guild:": + PlaceNPC(split[1], split[2], split[3], "TinkerGuildmaster"); + break; + case "-blacksmiths guild:": + PlaceNPC(split[1], split[2], split[3], "BlacksmithGuildmaster"); + break; + case "-sorcerors guild:": + PlaceNPC(split[1], split[2], split[3], "MageGuildmaster"); + break; + case "-customs:": break; + case "-painter:": break; + case "-theater:": break; + case "-warriors guild:": + PlaceNPC(split[1], split[2], split[3], "WarriorGuildmaster"); + break; + case "-archers guild:": + PlaceNPC(split[1], split[2], split[3], "RangerGuildmaster"); + break; + case "-thieves guild:": + PlaceNPC(split[1], split[2], split[3], "ThiefGuildmaster"); + break; + case "-miners guild:": + PlaceNPC(split[1], split[2], split[3], "MinerGuildmaster"); + break; + case "-fishermans guild:": + PlaceNPC(split[1], split[2], split[3], "FisherGuildmaster"); + break; + case "-merchants guild:": + PlaceNPC(split[1], split[2], split[3], "MerchantGuildmaster"); + break; + case "-illusionists guild:": break; + case "-armourers guild:": break; + case "-sorcerers guild:": break; + case "-mages guild:": + PlaceNPC(split[1], split[2], split[3], "MageGuildmaster"); + break; + case "-weapons guild:": break; + case "-bardic guild:": + PlaceNPC(split[1], split[2], split[3], "BardGuildmaster"); + break; + case "-rogues guild:": + break; - int x = Utility.ToInt32( sx ); - int y = Utility.ToInt32( sy ); - int map = Utility.ToInt32( sm ); + // Skip + case "+landmark:": + case "-point of interest:": + case "+shrine:": + case "+moongate:": + case "+dungeon:": + case "+scenic:": + case "-gate:": + case "+Body of Water:": + case "+ruins:": + case "+teleporter:": + case "+Terrain:": + case "-exit:": + case "-bridge:": + case "-other:": + case "+champion:": + case "-stairs:": + case "-guild:": + case "+graveyard:": + case "+Island:": + case "+town:": + break; + /*default: + Console.WriteLine(split[0]); + break;*/ + } + } + } - switch ( map ) - { - case 0://Trammel and Felucca - MakeSpawner( types, x, y, Map.Felucca ); - MakeSpawner( types, x, y, Map.Trammel ); - break; - case 1://Felucca - MakeSpawner( types, x, y, Map.Felucca ); - break; - case 2: - MakeSpawner( types, x, y, Map.Trammel ); - break; - case 3: - MakeSpawner( types, x, y, Map.Ilshenar ); - break; - case 4: - MakeSpawner( types, x, y, Map.Malas ); - break; - default: - Console.WriteLine( "UOAM Vendor Parser: Warning, unknown map {0}", map ); - break; - } - } + from.SendMessage("Done, added {0} spawners", m_Count); + } + else + { + from.SendMessage("{0} not found!", vendor_path); + } + } - public static int GetSpawnerZ( int x, int y, Map map ) - { - int z = map.GetAverageZ( x, y ); + public static void PlaceNPC(string sx, string sy, string sm, params string[] types) + { + if (types.Length == 0) + return; - if ( map.CanFit( x, y, z, 16, false, false, true ) ) - return z; + int x = Utility.ToInt32(sx); + int y = Utility.ToInt32(sy); + int map = Utility.ToInt32(sm); - for ( int i = 1; i <= 20; ++i ) - { - if ( map.CanFit( x, y, z + i, 16, false, false, true ) ) - return z + i; + switch (map) + { + case 0: //Trammel and Felucca + MakeSpawner(types, x, y, Map.Felucca); + MakeSpawner(types, x, y, Map.Trammel); + break; + case 1: //Felucca + MakeSpawner(types, x, y, Map.Felucca); + break; + case 2: + MakeSpawner(types, x, y, Map.Trammel); + break; + case 3: + MakeSpawner(types, x, y, Map.Ilshenar); + break; + case 4: + MakeSpawner(types, x, y, Map.Malas); + break; + default: + Console.WriteLine("UOAM Vendor Parser: Warning, unknown map {0}", map); + break; + } + } - if ( map.CanFit( x, y, z - i, 16, false, false, true ) ) - return z - i; - } + public static int GetSpawnerZ(int x, int y, Map map) + { + int z = map.GetAverageZ(x, y); - return z; - } + if (map.CanFit(x, y, z, 16, false, false, true)) + return z; - public static void ClearSpawners( int x, int y, int z, Map map ) - { - IPooledEnumerable eable = map.GetItemsInRange( new Point3D( x, y, z ), 0 ); - Queue m_ToDelete = new Queue(); + for (int i = 1; i <= 20; ++i) + { + if (map.CanFit(x, y, z + i, 16, false, false, true)) + return z + i; - foreach ( Spawner item in eable ) - { - if ( item.Z == z ) - m_ToDelete.Enqueue( item ); - } + if (map.CanFit(x, y, z - i, 16, false, false, true)) + return z - i; + } - eable.Free(); + return z; + } - while ( m_ToDelete.Count > 0 ) - ((Item)m_ToDelete.Dequeue()).Delete(); - } + public static void ClearSpawners(int x, int y, int z, Map map) + { + IPooledEnumerable eable = map.GetItemsInRange(new Point3D(x, y, z), 0); + Queue m_ToDelete = new Queue(); - private static void MakeSpawner( string[] types, int x, int y, Map map ) - { - if ( types.Length == 0 ) - return; + foreach (Spawner item in eable) + if (item.Z == z) + m_ToDelete.Enqueue(item); - int z = GetSpawnerZ( x, y, map ); + eable.Free(); - ClearSpawners( x, y, z, map ); + while (m_ToDelete.Count > 0) + m_ToDelete.Dequeue().Delete(); + } - for ( int i = 0; i < types.Length; ++i ) - { - bool isGuildmaster = ( types[i].EndsWith( "Guildmaster" ) ); + private static void MakeSpawner(string[] types, int x, int y, Map map) + { + if (types.Length == 0) + return; - Spawner sp = new Spawner( types[i] ); + int z = GetSpawnerZ(x, y, map); - if ( isGuildmaster ) - sp.Count = 1; - else - sp.Count = NPCCount; + ClearSpawners(x, y, z, map); - sp.MinDelay = MinTime; - sp.MaxDelay = MaxTime; - sp.Team = Team; - sp.HomeRange = HomeRange; + for (int i = 0; i < types.Length; ++i) + { + bool isGuildmaster = types[i].EndsWith("Guildmaster"); - sp.MoveToWorld( new Point3D( x, y, z ), map ); + Spawner sp = new Spawner(types[i]); - if ( TotalRespawn ) - { - sp.Respawn(); - sp.BringToHome(); - } + if (isGuildmaster) + sp.Count = 1; + else + sp.Count = NPCCount; - ++m_Count; - } - } - } -} + sp.MinDelay = MinTime; + sp.MaxDelay = MaxTime; + sp.Team = Team; + sp.HomeRange = HomeRange; + + sp.MoveToWorld(new Point3D(x, y, z), map); + + if (TotalRespawn) + { + sp.Respawn(); + sp.BringToHome(); + } + + ++m_Count; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/AI/AIControlMobileTarget.cs b/Scripts/Mobiles/AI/AIControlMobileTarget.cs index 26befc163..2cbf93a39 100644 --- a/Scripts/Mobiles/AI/AIControlMobileTarget.cs +++ b/Scripts/Mobiles/AI/AIControlMobileTarget.cs @@ -4,33 +4,32 @@ using Server.Targeting; namespace Server.Targets { - public class AIControlMobileTarget : Target - { - private List m_List; + public class AIControlMobileTarget : Target + { + private List m_List; - public OrderType Order { get; } + public AIControlMobileTarget(BaseAI ai, OrderType order) : base(-1, false, + order == OrderType.Attack ? TargetFlags.Harmful : TargetFlags.None) + { + m_List = new List(); + Order = order; - public AIControlMobileTarget( BaseAI ai, OrderType order ) : base( -1, false, ( order == OrderType.Attack ? TargetFlags.Harmful : TargetFlags.None ) ) - { - m_List = new List(); - Order = order; + AddAI(ai); + } - AddAI( ai ); - } + public OrderType Order{ get; } - public void AddAI( BaseAI ai ) - { - if ( !m_List.Contains( ai ) ) - m_List.Add( ai ); - } + public void AddAI(BaseAI ai) + { + if (!m_List.Contains(ai)) + m_List.Add(ai); + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile m ) - { - for ( int i = 0; i < m_List.Count; ++i ) - m_List[i].EndPickTarget( from, m, Order ); - } - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile m) + for (int i = 0; i < m_List.Count; ++i) + m_List[i].EndPickTarget(from, m, Order); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/AI/AnimalAI.cs b/Scripts/Mobiles/AI/AnimalAI.cs index 4ac7ad6cf..b621aef16 100644 --- a/Scripts/Mobiles/AI/AnimalAI.cs +++ b/Scripts/Mobiles/AI/AnimalAI.cs @@ -1,5 +1,3 @@ - - // Ideas // When you run on animals the panic // When if ( distance < 8 && Utility.RandomDouble() * Math.Sqrt( (8 - distance) / 6 ) >= incoming.Skills[SkillName.AnimalTaming].Value ) @@ -7,19 +5,19 @@ /* * AnimalHunterAI, AnimalHidingAI, AnimalDomesticAI... * - */ + */ namespace Server.Mobiles { - public class AnimalAI : BaseAI - { - public AnimalAI(BaseCreature m) : base (m) - { - } + public class AnimalAI : BaseAI + { + public AnimalAI(BaseCreature m) : base(m) + { + } - public override bool DoActionWander() - { - // Old: + public override bool DoActionWander() + { + // Old: #if false if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, true, false, true)) { @@ -39,114 +37,114 @@ namespace Server.Mobiles return true; #endif - // New, only flee @ 10% + // New, only flee @ 10% - double hitPercent = (double)m_Mobile.Hits / m_Mobile.HitsMax; + double hitPercent = (double)m_Mobile.Hits / m_Mobile.HitsMax; - if ( !m_Mobile.Summoned && !m_Mobile.Controlled && hitPercent < 0.1 && m_Mobile.CanFlee ) // Less than 10% health - { - m_Mobile.DebugSay( "I am low on health!" ); - Action = ActionType.Flee; - } - else if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + if (!m_Mobile.Summoned && !m_Mobile.Controlled && hitPercent < 0.1 && m_Mobile.CanFlee) // Less than 10% health + { + m_Mobile.DebugSay("I am low on health!"); + Action = ActionType.Flee; + } + else if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionWander(); - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionWander(); + } - return true; - } + return true; + } - public override bool DoActionCombat() - { - Mobile combatant = m_Mobile.Combatant; + public override bool DoActionCombat() + { + Mobile combatant = m_Mobile.Combatant; - if ( combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map ) - { - m_Mobile.DebugSay( "My combatant is gone.." ); + if (combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map) + { + m_Mobile.DebugSay("My combatant is gone.."); - Action = ActionType.Wander; + Action = ActionType.Wander; - return true; - } + return true; + } - if ( WalkMobileRange( combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight ) ) - { - m_Mobile.Direction = m_Mobile.GetDirectionTo( combatant ); - } - else - { - if ( m_Mobile.GetDistanceToSqrt( combatant ) > m_Mobile.RangePerception + 1 ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I cannot find {0}", combatant.Name ); + if (WalkMobileRange(combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight)) + { + m_Mobile.Direction = m_Mobile.GetDirectionTo(combatant); + } + else + { + if (m_Mobile.GetDistanceToSqrt(combatant) > m_Mobile.RangePerception + 1) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I cannot find {0}", combatant.Name); - Action = ActionType.Wander; + Action = ActionType.Wander; - return true; - } + return true; + } - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I should be closer to {0}", combatant.Name ); - } + if (m_Mobile.Debug) + m_Mobile.DebugSay("I should be closer to {0}", combatant.Name); + } - if ( !m_Mobile.Controlled && !m_Mobile.Summoned && m_Mobile.CanFlee ) - { - double hitPercent = (double)m_Mobile.Hits / m_Mobile.HitsMax; + if (!m_Mobile.Controlled && !m_Mobile.Summoned && m_Mobile.CanFlee) + { + double hitPercent = (double)m_Mobile.Hits / m_Mobile.HitsMax; - if ( hitPercent < 0.1 ) - { - m_Mobile.DebugSay( "I am low on health!" ); - Action = ActionType.Flee; - } - } + if (hitPercent < 0.1) + { + m_Mobile.DebugSay("I am low on health!"); + Action = ActionType.Flee; + } + } - return true; - } + return true; + } - public override bool DoActionBackoff() - { - double hitPercent = (double)m_Mobile.Hits / m_Mobile.HitsMax; + public override bool DoActionBackoff() + { + double hitPercent = (double)m_Mobile.Hits / m_Mobile.HitsMax; - if ( !m_Mobile.Summoned && !m_Mobile.Controlled && hitPercent < 0.1 && m_Mobile.CanFlee ) // Less than 10% health - { - Action = ActionType.Flee; - } - else - { - if (AcquireFocusMob(m_Mobile.RangePerception * 2, FightMode.Closest, true, false , true)) - { - if ( WalkMobileRange(m_Mobile.FocusMob, 1, false, m_Mobile.RangePerception, m_Mobile.RangePerception * 2) ) - { - m_Mobile.DebugSay( "Well, here I am safe" ); - Action = ActionType.Wander; - } - } - else - { - m_Mobile.DebugSay( "I have lost my focus, lets relax" ); - Action = ActionType.Wander; - } - } + if (!m_Mobile.Summoned && !m_Mobile.Controlled && hitPercent < 0.1 && m_Mobile.CanFlee) // Less than 10% health + { + Action = ActionType.Flee; + } + else + { + if (AcquireFocusMob(m_Mobile.RangePerception * 2, FightMode.Closest, true, false, true)) + { + if (WalkMobileRange(m_Mobile.FocusMob, 1, false, m_Mobile.RangePerception, m_Mobile.RangePerception * 2)) + { + m_Mobile.DebugSay("Well, here I am safe"); + Action = ActionType.Wander; + } + } + else + { + m_Mobile.DebugSay("I have lost my focus, lets relax"); + Action = ActionType.Wander; + } + } - return true; - } + return true; + } - public override bool DoActionFlee() - { - AcquireFocusMob(m_Mobile.RangePerception * 2, m_Mobile.FightMode, true, false, true); + public override bool DoActionFlee() + { + AcquireFocusMob(m_Mobile.RangePerception * 2, m_Mobile.FightMode, true, false, true); - if ( m_Mobile.FocusMob == null ) - m_Mobile.FocusMob = m_Mobile.Combatant; + if (m_Mobile.FocusMob == null) + m_Mobile.FocusMob = m_Mobile.Combatant; - return base.DoActionFlee(); - } - } + return base.DoActionFlee(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/ArcherAI.cs b/Scripts/Mobiles/AI/ArcherAI.cs index 21a61f0f8..3783ef2ff 100644 --- a/Scripts/Mobiles/AI/ArcherAI.cs +++ b/Scripts/Mobiles/AI/ArcherAI.cs @@ -2,125 +2,119 @@ using Server.Items; namespace Server.Mobiles { - public class ArcherAI : BaseAI - { - public ArcherAI(BaseCreature m) : base (m) - { - } + public class ArcherAI : BaseAI + { + public ArcherAI(BaseCreature m) : base(m) + { + } - public override bool DoActionWander() - { - m_Mobile.DebugSay( "I have no combatant" ); + public override bool DoActionWander() + { + m_Mobile.DebugSay("I have no combatant"); - if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected {0} and I will attack", m_Mobile.FocusMob.Name ); + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected {0} and I will attack", m_Mobile.FocusMob.Name); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - return base.DoActionWander(); - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + return base.DoActionWander(); + } - return true; - } + return true; + } - public override bool DoActionCombat() - { - if ( m_Mobile.Combatant == null || m_Mobile.Combatant.Deleted || !m_Mobile.Combatant.Alive || m_Mobile.Combatant.IsDeadBondedPet ) - { - m_Mobile.DebugSay("My combatant is deleted"); - Action = ActionType.Guard; - return true; - } + public override bool DoActionCombat() + { + if (m_Mobile.Combatant == null || m_Mobile.Combatant.Deleted || !m_Mobile.Combatant.Alive || + m_Mobile.Combatant.IsDeadBondedPet) + { + m_Mobile.DebugSay("My combatant is deleted"); + Action = ActionType.Guard; + return true; + } - if (Core.TickCount - m_Mobile.LastMoveTime > 1000) - { - if (WalkMobileRange(m_Mobile.Combatant, 1, true, m_Mobile.RangeFight, m_Mobile.Weapon.MaxRange)) - { - // Be sure to face the combatant - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant.Location); - } - else - { - if ( m_Mobile.Combatant != null ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I am still not in range of {0}", m_Mobile.Combatant.Name); + if (Core.TickCount - m_Mobile.LastMoveTime > 1000) + { + if (WalkMobileRange(m_Mobile.Combatant, 1, true, m_Mobile.RangeFight, m_Mobile.Weapon.MaxRange)) + { + // Be sure to face the combatant + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant.Location); + } + else + { + if (m_Mobile.Combatant != null) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I am still not in range of {0}", m_Mobile.Combatant.Name); - if ( (int) m_Mobile.GetDistanceToSqrt( m_Mobile.Combatant ) > m_Mobile.RangePerception + 1 ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have lost {0}", m_Mobile.Combatant.Name); + if ((int)m_Mobile.GetDistanceToSqrt(m_Mobile.Combatant) > m_Mobile.RangePerception + 1) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have lost {0}", m_Mobile.Combatant.Name); - m_Mobile.Combatant = null; - Action = ActionType.Guard; - return true; - } - } - } - } + m_Mobile.Combatant = null; + Action = ActionType.Guard; + return true; + } + } + } + } - // When we have no ammo, we flee - Container pack = m_Mobile.Backpack; + // When we have no ammo, we flee + Container pack = m_Mobile.Backpack; - if ( pack?.FindItemByType( typeof( Arrow ) ) == null ) - { - Action = ActionType.Flee; - return true; - } + if (pack?.FindItemByType(typeof(Arrow)) == null) + { + Action = ActionType.Flee; + return true; + } - - // At 20% we should check if we must leave - if ( m_Mobile.Hits < m_Mobile.HitsMax*20/100 && m_Mobile.CanFlee ) - { - bool bFlee = false; - // if my current hits are more than my opponent, i don't care - if ( m_Mobile.Combatant != null && m_Mobile.Hits < m_Mobile.Combatant.Hits) - { - int iDiff = m_Mobile.Combatant.Hits - m_Mobile.Hits; - if ( Utility.Random(0, 100) > 10 + iDiff) // 10% to flee + the diff of hits - { - bFlee = true; - } - } - else if ( m_Mobile.Combatant != null && m_Mobile.Hits >= m_Mobile.Combatant.Hits) - { - if ( Utility.Random(0, 100) > 10 ) // 10% to flee - { - bFlee = true; - } - } - - if (bFlee) - { - Action = ActionType.Flee; - } - } + // At 20% we should check if we must leave + if (m_Mobile.Hits < m_Mobile.HitsMax * 20 / 100 && m_Mobile.CanFlee) + { + bool bFlee = false; + // if my current hits are more than my opponent, i don't care + if (m_Mobile.Combatant != null && m_Mobile.Hits < m_Mobile.Combatant.Hits) + { + int iDiff = m_Mobile.Combatant.Hits - m_Mobile.Hits; - return true; - } + if (Utility.Random(0, 100) > 10 + iDiff) // 10% to flee + the diff of hits + bFlee = true; + } + else if (m_Mobile.Combatant != null && m_Mobile.Hits >= m_Mobile.Combatant.Hits) + { + if (Utility.Random(0, 100) > 10) // 10% to flee + bFlee = true; + } - public override bool DoActionGuard() - { - if ( AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + if (bFlee) Action = ActionType.Flee; + } - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionGuard(); - } + return true; + } - return true; - } - } + public override bool DoActionGuard() + { + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionGuard(); + } + + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/BaseAI.cs b/Scripts/Mobiles/AI/BaseAI.cs index 9ed2cea9e..95c353ef6 100644 --- a/Scripts/Mobiles/AI/BaseAI.cs +++ b/Scripts/Mobiles/AI/BaseAI.cs @@ -1,2789 +1,2798 @@ using System; using System.Collections.Generic; using System.IO; -using Server.Items; -using Server.Targets; -using Server.Network; -using Server.Regions; using Server.ContextMenus; using Server.Engines.Quests; using Server.Engines.Quests.Necro; -using MoveImpl = Server.Movement.MovementImpl; +using Server.Factions; +using Server.Gumps; +using Server.Items; +using Server.Network; +using Server.Regions; using Server.Spells; using Server.Spells.Spellweaving; +using Server.Targets; +using MoveImpl = Server.Movement.MovementImpl; namespace Server.Mobiles { - public enum AIType - { - AI_Use_Default, - AI_Melee, - AI_Animal, - AI_Archer, - AI_Healer, - AI_Vendor, - AI_Mage, - AI_Berserk, - AI_Predator, - AI_Thief - } - - public enum ActionType - { - Wander, - Combat, - Guard, - Flee, - Backoff, - Interact - } - - public abstract class BaseAI - { - public Timer m_Timer; - protected ActionType m_Action; - private long m_NextStopGuard; - - public BaseCreature m_Mobile; - - public BaseAI(BaseCreature m) - { - m_Mobile = m; - - m_Timer = new AITimer(this); - - bool activate; - - if (!m.PlayerRangeSensitive) - activate = true; - else if (World.Loading) - activate = false; - else if (m.Map == null || m.Map == Map.Internal || !m.Map.GetSector(m).Active) - activate = false; - else - activate = true; - - if (activate) - m_Timer.Start(); - - Action = ActionType.Wander; - } - - public ActionType Action - { - get => m_Action; - set - { - m_Action = value; - OnActionChanged(); - } - } - - public virtual bool WasNamed(string speech) - { - string name = m_Mobile.Name; - - return (name != null && Insensitive.StartsWith(speech, name)); - } - - private class InternalEntry : ContextMenuEntry - { - private Mobile m_From; - private BaseCreature m_Mobile; - private BaseAI m_AI; - private OrderType m_Order; - - public InternalEntry(Mobile from, int number, int range, BaseCreature mobile, BaseAI ai, OrderType order) - : base(number, range) - { - m_From = from; - m_Mobile = mobile; - m_AI = ai; - m_Order = order; - - if (mobile.IsDeadPet && (order == OrderType.Guard || order == OrderType.Attack || order == OrderType.Transfer || order == OrderType.Drop)) - Enabled = false; - } - - public override void OnClick() - { - if (!m_Mobile.Deleted && m_Mobile.Controlled && m_From.CheckAlive()) - { - if (m_Mobile.IsDeadPet && (m_Order == OrderType.Guard || m_Order == OrderType.Attack || m_Order == OrderType.Transfer || m_Order == OrderType.Drop)) - return; - - bool isOwner = (m_From == m_Mobile.ControlMaster); - bool isFriend = (!isOwner && m_Mobile.IsPetFriend(m_From)); - - if (!isOwner && !isFriend) - return; - if (isFriend && m_Order != OrderType.Follow && m_Order != OrderType.Stay && m_Order != OrderType.Stop) - return; - - switch (m_Order) - { - case OrderType.Follow: - case OrderType.Attack: - case OrderType.Transfer: - case OrderType.Friend: - case OrderType.Unfriend: - { - if (m_Order == OrderType.Transfer && m_From.HasTrade) - m_From.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending - else if (m_Order == OrderType.Friend && m_From.HasTrade) - m_From.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending - else - m_AI.BeginPickTarget(m_From, m_Order); - - break; - } - case OrderType.Release: - { - if (m_Mobile.Summoned) - goto default; - m_From.SendGump(new Gumps.ConfirmReleaseGump(m_From, m_Mobile)); - - break; - } - default: - { - if (m_Mobile.CheckControlChance(m_From)) - m_Mobile.ControlOrder = m_Order; - - break; - } - } - } - } - } - - public virtual void GetContextMenuEntries(Mobile from, List list) - { - if (from.Alive && m_Mobile.Controlled && from.InRange(m_Mobile, 14)) - { - if (from == m_Mobile.ControlMaster) - { - list.Add(new InternalEntry(from, 6107, 14, m_Mobile, this, OrderType.Guard)); // Command: Guard - list.Add(new InternalEntry(from, 6108, 14, m_Mobile, this, OrderType.Follow)); // Command: Follow - - if (m_Mobile.CanDrop) - list.Add(new InternalEntry(from, 6109, 14, m_Mobile, this, OrderType.Drop)); // Command: Drop - - list.Add(new InternalEntry(from, 6111, 14, m_Mobile, this, OrderType.Attack)); // Command: Kill - - list.Add(new InternalEntry(from, 6112, 14, m_Mobile, this, OrderType.Stop)); // Command: Stop - list.Add(new InternalEntry(from, 6114, 14, m_Mobile, this, OrderType.Stay)); // Command: Stay - - if (!m_Mobile.Summoned && !(m_Mobile is GrizzledMare)) - { - list.Add(new InternalEntry(from, 6110, 14, m_Mobile, this, OrderType.Friend)); // Add Friend - list.Add(new InternalEntry(from, 6099, 14, m_Mobile, this, OrderType.Unfriend)); // Remove Friend - list.Add(new InternalEntry(from, 6113, 14, m_Mobile, this, OrderType.Transfer)); // Transfer - } - - list.Add(new InternalEntry(from, 6118, 14, m_Mobile, this, OrderType.Release)); // Release - } - else if (m_Mobile.IsPetFriend(from)) - { - list.Add(new InternalEntry(from, 6108, 14, m_Mobile, this, OrderType.Follow)); // Command: Follow - list.Add(new InternalEntry(from, 6112, 14, m_Mobile, this, OrderType.Stop)); // Command: Stop - list.Add(new InternalEntry(from, 6114, 14, m_Mobile, this, OrderType.Stay)); // Command: Stay - } - } - } - - public virtual void BeginPickTarget(Mobile from, OrderType order) - { - if (m_Mobile.Deleted || !m_Mobile.Controlled || !from.InRange(m_Mobile, 14) || from.Map != m_Mobile.Map) - return; - - bool isOwner = (from == m_Mobile.ControlMaster); - bool isFriend = (!isOwner && m_Mobile.IsPetFriend(from)); - - if (!isOwner && !isFriend) - return; - if (isFriend && order != OrderType.Follow && order != OrderType.Stay && order != OrderType.Stop) - return; - - if (from.Target == null) - { - if (order == OrderType.Transfer) - from.SendLocalizedMessage(502038); // Click on the person to transfer ownership to. - else if (order == OrderType.Friend) - from.SendLocalizedMessage(502020); // Click on the player whom you wish to make a co-owner. - else if (order == OrderType.Unfriend) - from.SendLocalizedMessage(1070948); // Click on the player whom you wish to remove as a co-owner. - - from.Target = new AIControlMobileTarget(this, order); - } - else if (from.Target is AIControlMobileTarget t) - { - if (t.Order == order) - t.AddAI(this); - } - } - - public virtual void OnAggressiveAction(Mobile aggressor) - { - Mobile currentCombat = m_Mobile.Combatant; - - if (currentCombat != null && !aggressor.Hidden && currentCombat != aggressor && m_Mobile.GetDistanceToSqrt(currentCombat) > m_Mobile.GetDistanceToSqrt(aggressor)) - m_Mobile.Combatant = aggressor; - } - - public virtual void EndPickTarget(Mobile from, Mobile target, OrderType order) - { - if (m_Mobile.Deleted || !m_Mobile.Controlled || !from.InRange(m_Mobile, 14) || from.Map != m_Mobile.Map || !from.CheckAlive()) - return; - - bool isOwner = (from == m_Mobile.ControlMaster); - bool isFriend = (!isOwner && m_Mobile.IsPetFriend(from)); - - if (!isOwner && !isFriend) - return; - if (isFriend && order != OrderType.Follow && order != OrderType.Stay && order != OrderType.Stop) - return; - - if (order == OrderType.Attack) - { - if (target is BaseCreature creature && creature.IsScaryToPets && m_Mobile.IsScaredOfScaryThings) - { - m_Mobile.SayTo(from, "Your pet refuses to attack this creature!"); - return; - } - - if ((SolenHelper.CheckRedFriendship(from) && - (target is RedSolenInfiltratorQueen - || target is RedSolenInfiltratorWarrior - || target is RedSolenQueen - || target is RedSolenWarrior - || target is RedSolenWorker)) - || (SolenHelper.CheckBlackFriendship(from) && - (target is BlackSolenInfiltratorQueen - || target is BlackSolenInfiltratorWarrior - || target is BlackSolenQueen - || target is BlackSolenWarrior - || target is BlackSolenWorker))) - { - from.SendAsciiMessage("You can not force your pet to attack a creature you are protected from."); - return; - } - - if (target is Factions.BaseFactionGuard) - { - m_Mobile.SayTo(from, "Your pet refuses to attack the guard."); - return; - } - } - - if (m_Mobile.CheckControlChance(from)) - { - m_Mobile.ControlTarget = target; - m_Mobile.ControlOrder = order; - } - } - - public virtual bool HandlesOnSpeech(Mobile from) - { - if (from.AccessLevel >= AccessLevel.GameMaster) - return true; - - if (from.Alive && m_Mobile.Controlled && m_Mobile.Commandable && (from == m_Mobile.ControlMaster || m_Mobile.IsPetFriend(from))) - return true; - - return (from.Alive && from.InRange(m_Mobile.Location, 3) && m_Mobile.IsHumanInTown()); - } - - private static SkillName[] m_KeywordTable = { - SkillName.Parry, - SkillName.Healing, - SkillName.Hiding, - SkillName.Stealing, - SkillName.Alchemy, - SkillName.AnimalLore, - SkillName.ItemID, - SkillName.ArmsLore, - SkillName.Begging, - SkillName.Blacksmith, - SkillName.Fletching, - SkillName.Peacemaking, - SkillName.Camping, - SkillName.Carpentry, - SkillName.Cartography, - SkillName.Cooking, - SkillName.DetectHidden, - SkillName.Discordance,//?? - SkillName.EvalInt, - SkillName.Fishing, - SkillName.Provocation, - SkillName.Lockpicking, - SkillName.Magery, - SkillName.MagicResist, - SkillName.Tactics, - SkillName.Snooping, - SkillName.RemoveTrap, - SkillName.Musicianship, - SkillName.Poisoning, - SkillName.Archery, - SkillName.SpiritSpeak, - SkillName.Tailoring, - SkillName.AnimalTaming, - SkillName.TasteID, - SkillName.Tinkering, - SkillName.Veterinary, - SkillName.Forensics, - SkillName.Herding, - SkillName.Tracking, - SkillName.Stealth, - SkillName.Inscribe, - SkillName.Swords, - SkillName.Macing, - SkillName.Fencing, - SkillName.Wrestling, - SkillName.Lumberjacking, - SkillName.Mining, - SkillName.Meditation - }; - - public virtual void OnSpeech(SpeechEventArgs e) - { - if (e.Mobile.Alive && e.Mobile.InRange(m_Mobile.Location, 3) && m_Mobile.IsHumanInTown()) - { - if (e.HasKeyword(0x9D) && WasNamed(e.Speech)) // *move* - { - if (m_Mobile.Combatant != null) - { - // I am too busy fighting to deal with thee! - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); - } - else - { - // Excuse me? - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501516); - WalkRandomInHome(2, 2, 1); - } - } - else if (e.HasKeyword(0x9E) && WasNamed(e.Speech)) // *time* - { - if (m_Mobile.Combatant != null) - { - // I am too busy fighting to deal with thee! - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); - } - else - { - Clock.GetTime(m_Mobile, out int generalNumber, out _); - - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, generalNumber); - } - } - else if (e.HasKeyword(0x6C) && WasNamed(e.Speech)) // *train - { - if (m_Mobile.Combatant != null) - { - // I am too busy fighting to deal with thee! - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); - } - else - { - bool foundSomething = false; - - Skills ourSkills = m_Mobile.Skills; - Skills theirSkills = e.Mobile.Skills; - - for (int i = 0; i < ourSkills.Length && i < theirSkills.Length; ++i) - { - Skill skill = ourSkills[i]; - Skill theirSkill = theirSkills[i]; - - if (skill != null && theirSkill != null && skill.Base >= 60.0 && m_Mobile.CheckTeach(skill.SkillName, e.Mobile)) - { - double toTeach = skill.Base / 3.0; - - if (toTeach > 42.0) - toTeach = 42.0; - - if (toTeach > theirSkill.Base) - { - int number = 1043059 + i; - - if (number > 1043107) - continue; - - if (!foundSomething) - m_Mobile.Say(1043058); // I can train the following: - - m_Mobile.Say(number); - - foundSomething = true; - } - } - } - - if (!foundSomething) - m_Mobile.Say(501505); // Alas, I cannot teach thee anything. - } - } - else - { - SkillName toTrain = (SkillName)(-1); - - for (int i = 0; toTrain == (SkillName)(-1) && i < e.Keywords.Length; ++i) - { - int keyword = e.Keywords[i]; - - if (keyword == 0x154) - { - toTrain = SkillName.Anatomy; - } - else if (keyword >= 0x6D && keyword <= 0x9C) - { - int index = keyword - 0x6D; - - if (index >= 0 && index < m_KeywordTable.Length) - toTrain = m_KeywordTable[index]; - } - } - - if (toTrain != (SkillName)(-1) && WasNamed(e.Speech)) - { - if (m_Mobile.Combatant != null) - { - // I am too busy fighting to deal with thee! - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); - } - else - { - Skills skills = m_Mobile.Skills; - Skill skill = skills[toTrain]; - - if (skill == null || skill.Base < 60.0 || !m_Mobile.CheckTeach(toTrain, e.Mobile)) - { - m_Mobile.Say(501507); // 'Tis not something I can teach thee of. - } - else - { - m_Mobile.Teach(toTrain, e.Mobile, 0, false); - } - } - } - } - } - - if (m_Mobile.Controlled && m_Mobile.Commandable) - { - m_Mobile.DebugSay("Listening..."); - - bool isOwner = (e.Mobile == m_Mobile.ControlMaster); - bool isFriend = (!isOwner && m_Mobile.IsPetFriend(e.Mobile)); - - if (e.Mobile.Alive && (isOwner || isFriend)) - { - m_Mobile.DebugSay("It's from my master"); - - int[] keywords = e.Keywords; - string speech = e.Speech; - - // First, check the all* - for (int i = 0; i < keywords.Length; ++i) - { - int keyword = keywords[i]; - - switch (keyword) - { - case 0x164: // all come - { - if (!isOwner) - break; - - if (m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Come; - } - - return; - } - case 0x165: // all follow - { - BeginPickTarget(e.Mobile, OrderType.Follow); - return; - } - case 0x166: // all guard - case 0x16B: // all guard me - { - if (!isOwner) - break; - - if (m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Guard; - } - return; - } - case 0x167: // all stop - { - if (m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Stop; - } - return; - } - case 0x168: // all kill - case 0x169: // all attack - { - if (!isOwner) - break; - - BeginPickTarget(e.Mobile, OrderType.Attack); - return; - } - case 0x16C: // all follow me - { - if (m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = e.Mobile; - m_Mobile.ControlOrder = OrderType.Follow; - } - return; - } - case 0x170: // all stay - { - if (m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Stay; - } - return; - } - } - } - - // No all*, so check *command - for (int i = 0; i < keywords.Length; ++i) - { - int keyword = keywords[i]; - - switch (keyword) - { - case 0x155: // *come - { - if (!isOwner) - break; - - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Come; - } - - return; - } - case 0x156: // *drop - { - if (!isOwner) - break; - - if (!m_Mobile.IsDeadPet && !m_Mobile.Summoned && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Drop; - } - - return; - } - case 0x15A: // *follow - { - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - BeginPickTarget(e.Mobile, OrderType.Follow); - - return; - } - case 0x15B: // *friend - { - if (!isOwner) - break; - - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - if (m_Mobile.Summoned || (m_Mobile is GrizzledMare)) - e.Mobile.SendLocalizedMessage(1005481); // Summoned creatures are loyal only to their summoners. - else if (e.Mobile.HasTrade) - e.Mobile.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending - else - BeginPickTarget(e.Mobile, OrderType.Friend); - } - - return; - } - case 0x15C: // *guard - { - if (!isOwner) - break; - - if (!m_Mobile.IsDeadPet && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Guard; - } - - return; - } - case 0x15D: // *kill - case 0x15E: // *attack - { - if (!isOwner) - break; - - if (!m_Mobile.IsDeadPet && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - BeginPickTarget(e.Mobile, OrderType.Attack); - - return; - } - case 0x15F: // *patrol - { - if (!isOwner) - break; - - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Patrol; - } - - return; - } - case 0x161: // *stop - { - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Stop; - } - - return; - } - case 0x163: // *follow me - { - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = e.Mobile; - m_Mobile.ControlOrder = OrderType.Follow; - } - - return; - } - case 0x16D: // *release - { - if (!isOwner) - break; - - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - if (!m_Mobile.Summoned) - { - e.Mobile.SendGump(new Gumps.ConfirmReleaseGump(e.Mobile, m_Mobile)); - } - else - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Release; - } - } - - return; - } - case 0x16E: // *transfer - { - if (!isOwner) - break; - - if (!m_Mobile.IsDeadPet && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - if (m_Mobile.Summoned || (m_Mobile is GrizzledMare)) - e.Mobile.SendLocalizedMessage(1005487); // You cannot transfer ownership of a summoned creature. - else if (e.Mobile.HasTrade) - e.Mobile.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending - else - BeginPickTarget(e.Mobile, OrderType.Transfer); - } - - return; - } - case 0x16F: // *stay - { - if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Stay; - } - - return; - } - } - } - } - } - else - { - if (e.Mobile.AccessLevel >= AccessLevel.GameMaster) - { - m_Mobile.DebugSay("It's from a GM"); - - if (m_Mobile.FindMyName(e.Speech, true)) - { - string[] str = e.Speech.Split(' '); - int i; - - for (i = 0; i < str.Length; i++) - { - string word = str[i]; - - if (Insensitive.Equals(word, "obey")) - { - m_Mobile.SetControlMaster(e.Mobile); - - if (m_Mobile.Summoned) - m_Mobile.SummonMaster = e.Mobile; - - return; - } - } - } - } - } - } - - public virtual bool Think() - { - if (m_Mobile.Deleted) - return false; - - if (CheckFlee()) - return true; - - switch (Action) - { - case ActionType.Wander: - m_Mobile.OnActionWander(); - return DoActionWander(); - - case ActionType.Combat: - m_Mobile.OnActionCombat(); - return DoActionCombat(); - - case ActionType.Guard: - m_Mobile.OnActionGuard(); - return DoActionGuard(); - - case ActionType.Flee: - m_Mobile.OnActionFlee(); - return DoActionFlee(); - - case ActionType.Interact: - m_Mobile.OnActionInteract(); - return DoActionInteract(); - - case ActionType.Backoff: - m_Mobile.OnActionBackoff(); - return DoActionBackoff(); - - default: - return false; - } - } - - public virtual void OnActionChanged() - { - switch (Action) - { - case ActionType.Wander: - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - m_Mobile.FocusMob = null; - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - break; - - case ActionType.Combat: - m_Mobile.Warmode = true; - m_Mobile.FocusMob = null; - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - break; - - case ActionType.Guard: - m_Mobile.Warmode = true; - m_Mobile.FocusMob = null; - m_Mobile.Combatant = null; - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - m_NextStopGuard = Core.TickCount + (int)TimeSpan.FromSeconds(10).TotalMilliseconds; - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - break; - - case ActionType.Flee: - m_Mobile.Warmode = true; - m_Mobile.FocusMob = null; - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - break; - - case ActionType.Interact: - m_Mobile.Warmode = false; - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - break; - - case ActionType.Backoff: - m_Mobile.Warmode = false; - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - break; - } - } - - public virtual bool OnAtWayPoint() - { - return true; - } - - public virtual bool DoActionWander() - { - if (CheckHerding()) - { - m_Mobile.DebugSay("Praise the shepherd!"); - } - else if (m_Mobile.CurrentWayPoint != null) - { - WayPoint point = m_Mobile.CurrentWayPoint; - if ((point.X != m_Mobile.Location.X || point.Y != m_Mobile.Location.Y) && point.Map == m_Mobile.Map && point.Parent == null && !point.Deleted) - { - m_Mobile.DebugSay("I will move towards my waypoint."); - DoMove(m_Mobile.GetDirectionTo(m_Mobile.CurrentWayPoint)); - } - else if (OnAtWayPoint()) - { - m_Mobile.DebugSay("I will go to the next waypoint"); - m_Mobile.CurrentWayPoint = point.NextPoint; - if (point.NextPoint != null && point.NextPoint.Deleted) - m_Mobile.CurrentWayPoint = point.NextPoint = point.NextPoint.NextPoint; - } - } - else if (m_Mobile.IsAnimatedDead) - { - // animated dead follow their master - Mobile master = m_Mobile.SummonMaster; - - if (master != null && master.Map == m_Mobile.Map && master.InRange(m_Mobile, m_Mobile.RangePerception)) - MoveTo(master, false, 1); - else - WalkRandomInHome(2, 2, 1); - } - else if (CheckMove()) - { - if (!m_Mobile.CheckIdle()) - WalkRandomInHome(2, 2, 1); - } - - if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && !m_Mobile.Combatant.IsDeadBondedPet) - { - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); - } - - return true; - } - - public virtual bool DoActionCombat() - { - if (Core.AOS && CheckHerding()) - { - m_Mobile.DebugSay("Praise the shepherd!"); - } - else - { - Mobile c = m_Mobile.Combatant; - - if (c == null || c.Deleted || c.Map != m_Mobile.Map || !c.Alive || c.IsDeadBondedPet) - Action = ActionType.Wander; - else - m_Mobile.Direction = m_Mobile.GetDirectionTo(c); - } - - return true; - } - - public virtual bool DoActionGuard() - { - if (Core.AOS && CheckHerding()) - { - m_Mobile.DebugSay("Praise the shepherd!"); - } - else if (Core.TickCount - m_NextStopGuard < 0) - { - m_Mobile.DebugSay("I am on guard"); - //m_Mobile.Turn( Utility.Random(0, 2) - 1 ); - } - else - { - m_Mobile.DebugSay("I stopped being on guard"); - Action = ActionType.Wander; - } - - return true; - } - - public virtual bool DoActionFlee() - { - Mobile from = m_Mobile.FocusMob; - - if (from == null || from.Deleted || from.Map != m_Mobile.Map) - { - m_Mobile.DebugSay("I have lost him"); - Action = ActionType.Guard; - return true; - } - - if (WalkMobileRange(from, 1, true, m_Mobile.RangePerception * 2, m_Mobile.RangePerception * 3)) - { - m_Mobile.DebugSay("I have fled"); - Action = ActionType.Guard; - return true; - } - - m_Mobile.DebugSay("I am fleeing!"); - - return true; - } - - public virtual bool DoActionInteract() - { - return true; - } - - public virtual bool DoActionBackoff() - { - return true; - } - - public virtual bool Obey() - { - if (m_Mobile.Deleted) - return false; - - switch (m_Mobile.ControlOrder) - { - case OrderType.None: - return DoOrderNone(); - - case OrderType.Come: - return DoOrderCome(); - - case OrderType.Drop: - return DoOrderDrop(); - - case OrderType.Friend: - return DoOrderFriend(); - - case OrderType.Unfriend: - return DoOrderUnfriend(); - - case OrderType.Guard: - return DoOrderGuard(); - - case OrderType.Attack: - return DoOrderAttack(); - - case OrderType.Patrol: - return DoOrderPatrol(); - - case OrderType.Release: - return DoOrderRelease(); - - case OrderType.Stay: - return DoOrderStay(); - - case OrderType.Stop: - return DoOrderStop(); - - case OrderType.Follow: - return DoOrderFollow(); - - case OrderType.Transfer: - return DoOrderTransfer(); - - default: - return false; - } - } - - public virtual void OnCurrentOrderChanged() - { - if (m_Mobile.Deleted || m_Mobile.ControlMaster == null || m_Mobile.ControlMaster.Deleted) - return; - - switch (m_Mobile.ControlOrder) - { - case OrderType.None: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.Home = m_Mobile.Location; - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Come: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Drop: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = true; - m_Mobile.Combatant = null; - break; - - case OrderType.Friend: - case OrderType.Unfriend: - m_Mobile.ControlMaster.RevealingAction(); - break; - - case OrderType.Guard: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = true; - m_Mobile.Combatant = null; - string petname = $"{m_Mobile.Name}"; - m_Mobile.ControlMaster.SendLocalizedMessage(1049671, petname); //~1_PETNAME~ is now guarding you. - break; - - case OrderType.Attack: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - - m_Mobile.Warmode = true; - m_Mobile.Combatant = null; - break; - - case OrderType.Patrol: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Release: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Stay: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Stop: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.Home = m_Mobile.Location; - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Follow: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - - case OrderType.Transfer: - m_Mobile.ControlMaster.RevealingAction(); - m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; - m_Mobile.PlaySound(m_Mobile.GetIdleSound()); - - m_Mobile.Warmode = false; - m_Mobile.Combatant = null; - break; - } - } - - public virtual bool DoOrderNone() - { - m_Mobile.DebugSay("I have no order"); - - WalkRandomInHome(3, 2, 1); - - if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && !m_Mobile.Combatant.IsDeadBondedPet) - { - m_Mobile.Warmode = true; - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); - } - else - { - m_Mobile.Warmode = false; - } - - return true; - } - - public virtual bool DoOrderCome() - { - if (m_Mobile.ControlMaster != null && !m_Mobile.ControlMaster.Deleted) - { - int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m_Mobile.ControlMaster); - - if (iCurrDist > m_Mobile.RangePerception) - { - m_Mobile.DebugSay("I have lost my master. I stay here"); - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.None; - } - else - { - m_Mobile.DebugSay("My master told me come"); - - // Not exactly OSI style, but better than nothing. - bool bRun = (iCurrDist > 5); - - if (WalkMobileRange(m_Mobile.ControlMaster, 1, bRun, 0, 1)) - { - if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && !m_Mobile.Combatant.IsDeadBondedPet) - { - m_Mobile.Warmode = true; - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); - } - else - { - m_Mobile.Warmode = false; - } - } - } - } - - return true; - } - - public virtual bool DoOrderDrop() - { - if (m_Mobile.IsDeadPet || !m_Mobile.CanDrop) - return true; - - m_Mobile.DebugSay("I drop my stuff for my master"); - - Container pack = m_Mobile.Backpack; - - if (pack != null) - { - List list = pack.Items; - - for (int i = list.Count - 1; i >= 0; --i) - if (i < list.Count) - list[i].MoveToWorld(m_Mobile.Location, m_Mobile.Map); - } - - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.None; - - return true; - } - - public virtual bool CheckHerding() - { - IPoint2D target = m_Mobile.TargetLocation; - - if (target == null) - return false; // Creature is not being herded - - double distance = m_Mobile.GetDistanceToSqrt(target); - - if (distance < 1 || distance > 15) - { - if (distance < 1 && target.X == 1076 && target.Y == 450 && (m_Mobile is HordeMinionFamiliar)) - { - if (m_Mobile.ControlMaster is PlayerMobile pm) - { - QuestSystem qs = pm.Quest; - - if (qs is DarkTidesQuest) - { - QuestObjective obj = qs.FindObjective(typeof(FetchAbraxusScrollObjective)); - - if (obj != null && !obj.Completed) - { - m_Mobile.AddToBackpack(new ScrollOfAbraxus()); - obj.Complete(); - } - } - } - } - - m_Mobile.TargetLocation = null; - return false; // At the target or too far away - } - - DoMove(m_Mobile.GetDirectionTo(target)); - - return true; - } - - public virtual bool DoOrderFollow() - { - if (CheckHerding()) - { - m_Mobile.DebugSay("Praise the shepherd!"); - } - else if (m_Mobile.ControlTarget != null && !m_Mobile.ControlTarget.Deleted && m_Mobile.ControlTarget != m_Mobile) - { - int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m_Mobile.ControlTarget); - - if (iCurrDist > m_Mobile.RangePerception) - { - m_Mobile.DebugSay("I have lost the one to follow. I stay here"); - - if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && !m_Mobile.Combatant.IsDeadBondedPet) - { - m_Mobile.Warmode = true; - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); - } - else - { - m_Mobile.Warmode = false; - } - } - else - { - m_Mobile.DebugSay("My master told me to follow: {0}", m_Mobile.ControlTarget.Name); - - // Not exactly OSI style, but better than nothing. - bool bRun = (iCurrDist > 5); - - if (WalkMobileRange(m_Mobile.ControlTarget, 1, bRun, 0, 1)) - { - if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && !m_Mobile.Combatant.IsDeadBondedPet) - { - m_Mobile.Warmode = true; - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); - } - else - { - m_Mobile.Warmode = false; - if (Core.AOS) - m_Mobile.CurrentSpeed = 0.1; - } - } - } - } - else - { - m_Mobile.DebugSay("I have nobody to follow"); - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.None; - } - - return true; - } - - public virtual bool DoOrderFriend() - { - Mobile from = m_Mobile.ControlMaster; - Mobile to = m_Mobile.ControlTarget; - - if (from == null || to == null || from == to || from.Deleted || to.Deleted || !to.Player) - { - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 502039); // *looks confused* - } - else - { - bool youngFrom = from is PlayerMobile mobile && mobile.Young; - bool youngTo = to is PlayerMobile playerMobile && playerMobile.Young; - - if (youngFrom && !youngTo) - { - from.SendLocalizedMessage(502040); // As a young player, you may not friend pets to older players. - } - else if (!youngFrom && youngTo) - { - from.SendLocalizedMessage(502041); // As an older player, you may not friend pets to young players. - } - else if (from.CanBeBeneficial(to, true)) - { - NetState fromState = from.NetState, toState = to.NetState; - - if (fromState != null && toState != null) - { - if (from.HasTrade) - { - from.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending - } - else if (to.HasTrade) - { - to.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending - } - else if (m_Mobile.IsPetFriend(to)) - { - from.SendLocalizedMessage(1049691); // That person is already a friend. - } - else if (!m_Mobile.AllowNewPetFriend) - { - from.SendLocalizedMessage(1005482); // Your pet does not seem to be interested in making new friends right now. - } - else - { - // ~1_NAME~ will now accept movement commands from ~2_NAME~. - from.SendLocalizedMessage(1049676, $"{m_Mobile.Name}\t{to.Name}"); - - /* ~1_NAME~ has granted you the ability to give orders to their pet ~2_PET_NAME~. - * This creature will now consider you as a friend. - */ - to.SendLocalizedMessage(1043246, $"{from.Name}\t{m_Mobile.Name}"); - - m_Mobile.AddPetFriend(to); - - m_Mobile.ControlTarget = to; - m_Mobile.ControlOrder = OrderType.Follow; - - return true; - } - } - } - } - - m_Mobile.ControlTarget = from; - m_Mobile.ControlOrder = OrderType.Follow; - - return true; - } - - public virtual bool DoOrderUnfriend() - { - Mobile from = m_Mobile.ControlMaster; - Mobile to = m_Mobile.ControlTarget; - - if (from == null || to == null || from == to || from.Deleted || to.Deleted || !to.Player) - { - m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 502039); // *looks confused* - } - else if (!m_Mobile.IsPetFriend(to)) - { - from.SendLocalizedMessage(1070953); // That person is not a friend. - } - else - { - // ~1_NAME~ will no longer accept movement commands from ~2_NAME~. - from.SendLocalizedMessage(1070951, $"{m_Mobile.Name}\t{to.Name}"); - - /* ~1_NAME~ has no longer granted you the ability to give orders to their pet ~2_PET_NAME~. - * This creature will no longer consider you as a friend. - */ - to.SendLocalizedMessage(1070952, $"{from.Name}\t{m_Mobile.Name}"); - - m_Mobile.RemovePetFriend(to); - } - - m_Mobile.ControlTarget = from; - m_Mobile.ControlOrder = OrderType.Follow; - - return true; - } - - public virtual bool DoOrderGuard() - { - if (m_Mobile.IsDeadPet) - return true; - - Mobile controlMaster = m_Mobile.ControlMaster; - - if (controlMaster == null || controlMaster.Deleted) - return true; - - Mobile combatant = m_Mobile.Combatant; - - List aggressors = controlMaster.Aggressors; - - if (aggressors.Count > 0) - { - for (int i = 0; i < aggressors.Count; ++i) - { - AggressorInfo info = aggressors[i]; - Mobile attacker = info.Attacker; - - if (attacker != null && !attacker.Deleted && attacker.GetDistanceToSqrt(m_Mobile) <= m_Mobile.RangePerception) - { - if (combatant == null || attacker.GetDistanceToSqrt(controlMaster) < combatant.GetDistanceToSqrt(controlMaster)) - combatant = attacker; - } - } - - if (combatant != null) - m_Mobile.DebugSay("Crap, my master has been attacked! I will attack one of those bastards!"); - } - - if (combatant != null && combatant != m_Mobile && combatant != m_Mobile.ControlMaster && !combatant.Deleted && combatant.Alive && !combatant.IsDeadBondedPet && m_Mobile.CanSee(combatant) && m_Mobile.CanBeHarmful(combatant, false) && combatant.Map == m_Mobile.Map) - { - m_Mobile.DebugSay("Guarding from target..."); - - m_Mobile.Combatant = combatant; - m_Mobile.FocusMob = combatant; - Action = ActionType.Combat; - - /* - * We need to call Think() here or spell casting monsters will not use - * spells when guarding because their target is never processed. - */ - Think(); - } - else - { - m_Mobile.DebugSay("Nothing to guard from"); - - m_Mobile.Warmode = false; - if (Core.AOS) - m_Mobile.CurrentSpeed = 0.1; - - WalkMobileRange(controlMaster, 1, false, 0, 1); - } - - return true; - } - - public virtual bool DoOrderAttack() - { - if (m_Mobile.IsDeadPet) - return true; - - if (m_Mobile.ControlTarget == null || m_Mobile.ControlTarget.Deleted || m_Mobile.ControlTarget.Map != m_Mobile.Map || !m_Mobile.ControlTarget.Alive || m_Mobile.ControlTarget.IsDeadBondedPet) - { - m_Mobile.DebugSay("I think he might be dead. He's not anywhere around here at least. That's cool. I'm glad he's dead."); - - if (Core.AOS) - { - m_Mobile.ControlTarget = m_Mobile.ControlMaster; - m_Mobile.ControlOrder = OrderType.Follow; - } - else - { - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.None; - } - - if (m_Mobile.FightMode == FightMode.Closest || m_Mobile.FightMode == FightMode.Aggressor) - { - Mobile newCombatant = null; - double newScore = 0.0; - - foreach (Mobile aggr in m_Mobile.GetMobilesInRange(m_Mobile.RangePerception)) - { - if (!m_Mobile.CanSee(aggr) || aggr.Combatant != m_Mobile) - continue; - - if (aggr.IsDeadBondedPet || !aggr.Alive) - continue; - - double aggrScore = m_Mobile.GetFightModeRanking(aggr, FightMode.Closest, false); - - if ((newCombatant == null || aggrScore > newScore) && m_Mobile.InLOS(aggr)) - { - newCombatant = aggr; - newScore = aggrScore; - } - } - - if (newCombatant != null) - { - m_Mobile.ControlTarget = newCombatant; - m_Mobile.ControlOrder = OrderType.Attack; - m_Mobile.Combatant = newCombatant; - m_Mobile.DebugSay("But -that- is not dead. Here we go again..."); - Think(); - } - } - } - else - { - m_Mobile.DebugSay("Attacking target..."); - Think(); - } - - return true; - } - - public virtual bool DoOrderPatrol() - { - m_Mobile.DebugSay("This order is not yet coded"); - return true; - } - - public virtual bool DoOrderRelease() - { - m_Mobile.DebugSay("I have been released"); - - m_Mobile.PlaySound(m_Mobile.GetAngerSound()); - - m_Mobile.SetControlMaster(null); - m_Mobile.SummonMaster = null; - - m_Mobile.BondingBegin = DateTime.MinValue; - m_Mobile.OwnerAbandonTime = DateTime.MinValue; - m_Mobile.IsBonded = false; - - if (m_Mobile.Spawner is SpawnEntry se && se.HomeLocation != Point3D.Zero) - { - m_Mobile.Home = se.HomeLocation; - m_Mobile.RangeHome = se.HomeRange; - } - - if (m_Mobile.DeleteOnRelease || m_Mobile.IsDeadPet) - m_Mobile.Delete(); - - m_Mobile.BeginDeleteTimer(); - m_Mobile.DropBackpack(); - - return true; - } - - public virtual bool DoOrderStay() - { - if (CheckHerding()) - m_Mobile.DebugSay("Praise the shepherd!"); - else - m_Mobile.DebugSay("My master told me to stay"); - - //m_Mobile.Direction = m_Mobile.GetDirectionTo( m_Mobile.ControlMaster ); - - return true; - } - - public virtual bool DoOrderStop() - { - if (m_Mobile.ControlMaster == null || m_Mobile.ControlMaster.Deleted) - return true; - - m_Mobile.DebugSay("My master told me to stop."); - - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.ControlMaster); - m_Mobile.Home = m_Mobile.Location; - - m_Mobile.ControlTarget = null; - - if (Core.ML) - { - WalkRandomInHome(3, 2, 1); - } - else - { - m_Mobile.ControlOrder = OrderType.None; - } - - return true; - } - - private class TransferItem : Item - { - public static bool IsInCombat(BaseCreature creature) - { - return (creature != null && (creature.Aggressors.Count > 0 || creature.Aggressed.Count > 0)); - } - - private BaseCreature m_Creature; - - public TransferItem(BaseCreature creature) - : base(ShrinkTable.Lookup(creature)) - { - m_Creature = creature; - - Movable = false; - - if (!Core.AOS) - { - Name = creature.Name; - } - else if (ItemID == ShrinkTable.DefaultItemID || creature.GetType().IsDefined(typeof(FriendlyNameAttribute), false) || creature is Reptalon) - Name = FriendlyNameAttribute.GetFriendlyNameFor(creature.GetType()).ToString(); - - //(As Per OSI)No name. Normally, set by the ItemID of the Shrink Item unless we either explicitly set it with an Attribute, or, no lookup found + public enum AIType + { + AI_Use_Default, + AI_Melee, + AI_Animal, + AI_Archer, + AI_Healer, + AI_Vendor, + AI_Mage, + AI_Berserk, + AI_Predator, + AI_Thief + } + + public enum ActionType + { + Wander, + Combat, + Guard, + Flee, + Backoff, + Interact + } + + public abstract class BaseAI + { + private static SkillName[] m_KeywordTable = + { + SkillName.Parry, + SkillName.Healing, + SkillName.Hiding, + SkillName.Stealing, + SkillName.Alchemy, + SkillName.AnimalLore, + SkillName.ItemID, + SkillName.ArmsLore, + SkillName.Begging, + SkillName.Blacksmith, + SkillName.Fletching, + SkillName.Peacemaking, + SkillName.Camping, + SkillName.Carpentry, + SkillName.Cartography, + SkillName.Cooking, + SkillName.DetectHidden, + SkillName.Discordance, //?? + SkillName.EvalInt, + SkillName.Fishing, + SkillName.Provocation, + SkillName.Lockpicking, + SkillName.Magery, + SkillName.MagicResist, + SkillName.Tactics, + SkillName.Snooping, + SkillName.RemoveTrap, + SkillName.Musicianship, + SkillName.Poisoning, + SkillName.Archery, + SkillName.SpiritSpeak, + SkillName.Tailoring, + SkillName.AnimalTaming, + SkillName.TasteID, + SkillName.Tinkering, + SkillName.Veterinary, + SkillName.Forensics, + SkillName.Herding, + SkillName.Tracking, + SkillName.Stealth, + SkillName.Inscribe, + SkillName.Swords, + SkillName.Macing, + SkillName.Fencing, + SkillName.Wrestling, + SkillName.Lumberjacking, + SkillName.Mining, + SkillName.Meditation + }; + + private static Queue m_Obstacles = new Queue(); + protected ActionType m_Action; + + public BaseCreature m_Mobile; + + private long m_NextDetectHidden; + private long m_NextStopGuard; + + protected PathFollower m_Path; + public Timer m_Timer; + + public BaseAI(BaseCreature m) + { + m_Mobile = m; + + m_Timer = new AITimer(this); + + bool activate; + + if (!m.PlayerRangeSensitive) + activate = true; + else if (World.Loading) + activate = false; + else if (m.Map == null || m.Map == Map.Internal || !m.Map.GetSector(m).Active) + activate = false; + else + activate = true; + + if (activate) + m_Timer.Start(); + + Action = ActionType.Wander; + } + + public ActionType Action + { + get => m_Action; + set + { + m_Action = value; + OnActionChanged(); + } + } + + public long NextMove{ get; set; } + + public virtual bool CanDetectHidden => m_Mobile.Skills[SkillName.DetectHidden].Value > 0; + + public virtual bool WasNamed(string speech) + { + string name = m_Mobile.Name; + + return name != null && Insensitive.StartsWith(speech, name); + } + + public virtual void GetContextMenuEntries(Mobile from, List list) + { + if (from.Alive && m_Mobile.Controlled && from.InRange(m_Mobile, 14)) + { + if (from == m_Mobile.ControlMaster) + { + list.Add(new InternalEntry(from, 6107, 14, m_Mobile, this, OrderType.Guard)); // Command: Guard + list.Add(new InternalEntry(from, 6108, 14, m_Mobile, this, OrderType.Follow)); // Command: Follow + + if (m_Mobile.CanDrop) + list.Add(new InternalEntry(from, 6109, 14, m_Mobile, this, OrderType.Drop)); // Command: Drop + + list.Add(new InternalEntry(from, 6111, 14, m_Mobile, this, OrderType.Attack)); // Command: Kill + + list.Add(new InternalEntry(from, 6112, 14, m_Mobile, this, OrderType.Stop)); // Command: Stop + list.Add(new InternalEntry(from, 6114, 14, m_Mobile, this, OrderType.Stay)); // Command: Stay + + if (!m_Mobile.Summoned && !(m_Mobile is GrizzledMare)) + { + list.Add(new InternalEntry(from, 6110, 14, m_Mobile, this, OrderType.Friend)); // Add Friend + list.Add(new InternalEntry(from, 6099, 14, m_Mobile, this, OrderType.Unfriend)); // Remove Friend + list.Add(new InternalEntry(from, 6113, 14, m_Mobile, this, OrderType.Transfer)); // Transfer + } + + list.Add(new InternalEntry(from, 6118, 14, m_Mobile, this, OrderType.Release)); // Release + } + else if (m_Mobile.IsPetFriend(from)) + { + list.Add(new InternalEntry(from, 6108, 14, m_Mobile, this, OrderType.Follow)); // Command: Follow + list.Add(new InternalEntry(from, 6112, 14, m_Mobile, this, OrderType.Stop)); // Command: Stop + list.Add(new InternalEntry(from, 6114, 14, m_Mobile, this, OrderType.Stay)); // Command: Stay + } + } + } + + public virtual void BeginPickTarget(Mobile from, OrderType order) + { + if (m_Mobile.Deleted || !m_Mobile.Controlled || !from.InRange(m_Mobile, 14) || from.Map != m_Mobile.Map) + return; + + bool isOwner = from == m_Mobile.ControlMaster; + bool isFriend = !isOwner && m_Mobile.IsPetFriend(from); + + if (!isOwner && !isFriend) + return; + if (isFriend && order != OrderType.Follow && order != OrderType.Stay && order != OrderType.Stop) + return; + + if (from.Target == null) + { + if (order == OrderType.Transfer) + from.SendLocalizedMessage(502038); // Click on the person to transfer ownership to. + else if (order == OrderType.Friend) + from.SendLocalizedMessage(502020); // Click on the player whom you wish to make a co-owner. + else if (order == OrderType.Unfriend) + from.SendLocalizedMessage(1070948); // Click on the player whom you wish to remove as a co-owner. + + from.Target = new AIControlMobileTarget(this, order); + } + else if (from.Target is AIControlMobileTarget t) + { + if (t.Order == order) + t.AddAI(this); + } + } + + public virtual void OnAggressiveAction(Mobile aggressor) + { + Mobile currentCombat = m_Mobile.Combatant; + + if (currentCombat != null && !aggressor.Hidden && currentCombat != aggressor && + m_Mobile.GetDistanceToSqrt(currentCombat) > m_Mobile.GetDistanceToSqrt(aggressor)) + m_Mobile.Combatant = aggressor; + } + + public virtual void EndPickTarget(Mobile from, Mobile target, OrderType order) + { + if (m_Mobile.Deleted || !m_Mobile.Controlled || !from.InRange(m_Mobile, 14) || from.Map != m_Mobile.Map || + !from.CheckAlive()) + return; + + bool isOwner = from == m_Mobile.ControlMaster; + bool isFriend = !isOwner && m_Mobile.IsPetFriend(from); + + if (!isOwner && !isFriend) + return; + if (isFriend && order != OrderType.Follow && order != OrderType.Stay && order != OrderType.Stop) + return; + + if (order == OrderType.Attack) + { + if (target is BaseCreature creature && creature.IsScaryToPets && m_Mobile.IsScaredOfScaryThings) + { + m_Mobile.SayTo(from, "Your pet refuses to attack this creature!"); + return; + } + + if (SolenHelper.CheckRedFriendship(from) && + (target is RedSolenInfiltratorQueen + || target is RedSolenInfiltratorWarrior + || target is RedSolenQueen + || target is RedSolenWarrior + || target is RedSolenWorker) + || SolenHelper.CheckBlackFriendship(from) && + (target is BlackSolenInfiltratorQueen + || target is BlackSolenInfiltratorWarrior + || target is BlackSolenQueen + || target is BlackSolenWarrior + || target is BlackSolenWorker)) + { + from.SendAsciiMessage("You can not force your pet to attack a creature you are protected from."); + return; + } + + if (target is BaseFactionGuard) + { + m_Mobile.SayTo(from, "Your pet refuses to attack the guard."); + return; + } + } + + if (m_Mobile.CheckControlChance(from)) + { + m_Mobile.ControlTarget = target; + m_Mobile.ControlOrder = order; + } + } + + public virtual bool HandlesOnSpeech(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + + if (from.Alive && m_Mobile.Controlled && m_Mobile.Commandable && + (from == m_Mobile.ControlMaster || m_Mobile.IsPetFriend(from))) + return true; + + return from.Alive && from.InRange(m_Mobile.Location, 3) && m_Mobile.IsHumanInTown(); + } + + public virtual void OnSpeech(SpeechEventArgs e) + { + if (e.Mobile.Alive && e.Mobile.InRange(m_Mobile.Location, 3) && m_Mobile.IsHumanInTown()) + { + if (e.HasKeyword(0x9D) && WasNamed(e.Speech)) // *move* + { + if (m_Mobile.Combatant != null) + { + // I am too busy fighting to deal with thee! + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); + } + else + { + // Excuse me? + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501516); + WalkRandomInHome(2, 2, 1); + } + } + else if (e.HasKeyword(0x9E) && WasNamed(e.Speech)) // *time* + { + if (m_Mobile.Combatant != null) + { + // I am too busy fighting to deal with thee! + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); + } + else + { + Clock.GetTime(m_Mobile, out int generalNumber, out _); + + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, generalNumber); + } + } + else if (e.HasKeyword(0x6C) && WasNamed(e.Speech)) // *train + { + if (m_Mobile.Combatant != null) + { + // I am too busy fighting to deal with thee! + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); + } + else + { + bool foundSomething = false; + + Skills ourSkills = m_Mobile.Skills; + Skills theirSkills = e.Mobile.Skills; + + for (int i = 0; i < ourSkills.Length && i < theirSkills.Length; ++i) + { + Skill skill = ourSkills[i]; + Skill theirSkill = theirSkills[i]; + + if (skill != null && theirSkill != null && skill.Base >= 60.0 && + m_Mobile.CheckTeach(skill.SkillName, e.Mobile)) + { + double toTeach = skill.Base / 3.0; + + if (toTeach > 42.0) + toTeach = 42.0; + + if (toTeach > theirSkill.Base) + { + int number = 1043059 + i; + + if (number > 1043107) + continue; + + if (!foundSomething) + m_Mobile.Say(1043058); // I can train the following: + + m_Mobile.Say(number); + + foundSomething = true; + } + } + } + + if (!foundSomething) + m_Mobile.Say(501505); // Alas, I cannot teach thee anything. + } + } + else + { + SkillName toTrain = (SkillName)(-1); + + for (int i = 0; toTrain == (SkillName)(-1) && i < e.Keywords.Length; ++i) + { + int keyword = e.Keywords[i]; + + if (keyword == 0x154) + { + toTrain = SkillName.Anatomy; + } + else if (keyword >= 0x6D && keyword <= 0x9C) + { + int index = keyword - 0x6D; + + if (index >= 0 && index < m_KeywordTable.Length) + toTrain = m_KeywordTable[index]; + } + } + + if (toTrain != (SkillName)(-1) && WasNamed(e.Speech)) + { + if (m_Mobile.Combatant != null) + { + // I am too busy fighting to deal with thee! + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 501482); + } + else + { + Skills skills = m_Mobile.Skills; + Skill skill = skills[toTrain]; + + if (skill == null || skill.Base < 60.0 || !m_Mobile.CheckTeach(toTrain, e.Mobile)) + m_Mobile.Say(501507); // 'Tis not something I can teach thee of. + else + m_Mobile.Teach(toTrain, e.Mobile, 0, false); + } + } + } + } + + if (m_Mobile.Controlled && m_Mobile.Commandable) + { + m_Mobile.DebugSay("Listening..."); + + bool isOwner = e.Mobile == m_Mobile.ControlMaster; + bool isFriend = !isOwner && m_Mobile.IsPetFriend(e.Mobile); + + if (e.Mobile.Alive && (isOwner || isFriend)) + { + m_Mobile.DebugSay("It's from my master"); + + int[] keywords = e.Keywords; + string speech = e.Speech; + + // First, check the all* + for (int i = 0; i < keywords.Length; ++i) + { + int keyword = keywords[i]; + + switch (keyword) + { + case 0x164: // all come + { + if (!isOwner) + break; + + if (m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Come; + } + + return; + } + case 0x165: // all follow + { + BeginPickTarget(e.Mobile, OrderType.Follow); + return; + } + case 0x166: // all guard + case 0x16B: // all guard me + { + if (!isOwner) + break; + + if (m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Guard; + } + + return; + } + case 0x167: // all stop + { + if (m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Stop; + } + + return; + } + case 0x168: // all kill + case 0x169: // all attack + { + if (!isOwner) + break; + + BeginPickTarget(e.Mobile, OrderType.Attack); + return; + } + case 0x16C: // all follow me + { + if (m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = e.Mobile; + m_Mobile.ControlOrder = OrderType.Follow; + } + + return; + } + case 0x170: // all stay + { + if (m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Stay; + } + + return; + } + } + } + + // No all*, so check *command + for (int i = 0; i < keywords.Length; ++i) + { + int keyword = keywords[i]; + + switch (keyword) + { + case 0x155: // *come + { + if (!isOwner) + break; + + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Come; + } + + return; + } + case 0x156: // *drop + { + if (!isOwner) + break; + + if (!m_Mobile.IsDeadPet && !m_Mobile.Summoned && WasNamed(speech) && + m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Drop; + } + + return; + } + case 0x15A: // *follow + { + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + BeginPickTarget(e.Mobile, OrderType.Follow); + + return; + } + case 0x15B: // *friend + { + if (!isOwner) + break; + + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + if (m_Mobile.Summoned || m_Mobile is GrizzledMare) + e.Mobile.SendLocalizedMessage( + 1005481); // Summoned creatures are loyal only to their summoners. + else if (e.Mobile.HasTrade) + e.Mobile.SendLocalizedMessage( + 1070947); // You cannot friend a pet with a trade pending + else + BeginPickTarget(e.Mobile, OrderType.Friend); + } + + return; + } + case 0x15C: // *guard + { + if (!isOwner) + break; + + if (!m_Mobile.IsDeadPet && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Guard; + } + + return; + } + case 0x15D: // *kill + case 0x15E: // *attack + { + if (!isOwner) + break; + + if (!m_Mobile.IsDeadPet && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + BeginPickTarget(e.Mobile, OrderType.Attack); + + return; + } + case 0x15F: // *patrol + { + if (!isOwner) + break; + + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Patrol; + } + + return; + } + case 0x161: // *stop + { + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Stop; + } + + return; + } + case 0x163: // *follow me + { + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = e.Mobile; + m_Mobile.ControlOrder = OrderType.Follow; + } + + return; + } + case 0x16D: // *release + { + if (!isOwner) + break; + + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + if (!m_Mobile.Summoned) + { + e.Mobile.SendGump(new ConfirmReleaseGump(e.Mobile, m_Mobile)); + } + else + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Release; + } + } + + return; + } + case 0x16E: // *transfer + { + if (!isOwner) + break; + + if (!m_Mobile.IsDeadPet && WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + if (m_Mobile.Summoned || m_Mobile is GrizzledMare) + e.Mobile.SendLocalizedMessage( + 1005487); // You cannot transfer ownership of a summoned creature. + else if (e.Mobile.HasTrade) + e.Mobile.SendLocalizedMessage( + 1010507); // You cannot transfer a pet with a trade pending + else + BeginPickTarget(e.Mobile, OrderType.Transfer); + } + + return; + } + case 0x16F: // *stay + { + if (WasNamed(speech) && m_Mobile.CheckControlChance(e.Mobile)) + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Stay; + } + + return; + } + } + } + } + } + else + { + if (e.Mobile.AccessLevel >= AccessLevel.GameMaster) + { + m_Mobile.DebugSay("It's from a GM"); + + if (m_Mobile.FindMyName(e.Speech, true)) + { + string[] str = e.Speech.Split(' '); + int i; + + for (i = 0; i < str.Length; i++) + { + string word = str[i]; + + if (Insensitive.Equals(word, "obey")) + { + m_Mobile.SetControlMaster(e.Mobile); + + if (m_Mobile.Summoned) + m_Mobile.SummonMaster = e.Mobile; + + return; + } + } + } + } + } + } + + public virtual bool Think() + { + if (m_Mobile.Deleted) + return false; + + if (CheckFlee()) + return true; + + switch (Action) + { + case ActionType.Wander: + m_Mobile.OnActionWander(); + return DoActionWander(); + + case ActionType.Combat: + m_Mobile.OnActionCombat(); + return DoActionCombat(); + + case ActionType.Guard: + m_Mobile.OnActionGuard(); + return DoActionGuard(); + + case ActionType.Flee: + m_Mobile.OnActionFlee(); + return DoActionFlee(); + + case ActionType.Interact: + m_Mobile.OnActionInteract(); + return DoActionInteract(); + + case ActionType.Backoff: + m_Mobile.OnActionBackoff(); + return DoActionBackoff(); + + default: + return false; + } + } + + public virtual void OnActionChanged() + { + switch (Action) + { + case ActionType.Wander: + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + m_Mobile.FocusMob = null; + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + break; + + case ActionType.Combat: + m_Mobile.Warmode = true; + m_Mobile.FocusMob = null; + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + break; + + case ActionType.Guard: + m_Mobile.Warmode = true; + m_Mobile.FocusMob = null; + m_Mobile.Combatant = null; + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + m_NextStopGuard = Core.TickCount + (int)TimeSpan.FromSeconds(10).TotalMilliseconds; + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + break; + + case ActionType.Flee: + m_Mobile.Warmode = true; + m_Mobile.FocusMob = null; + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + break; + + case ActionType.Interact: + m_Mobile.Warmode = false; + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + break; + + case ActionType.Backoff: + m_Mobile.Warmode = false; + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + break; + } + } + + public virtual bool OnAtWayPoint() + { + return true; + } + + public virtual bool DoActionWander() + { + if (CheckHerding()) + { + m_Mobile.DebugSay("Praise the shepherd!"); + } + else if (m_Mobile.CurrentWayPoint != null) + { + WayPoint point = m_Mobile.CurrentWayPoint; + if ((point.X != m_Mobile.Location.X || point.Y != m_Mobile.Location.Y) && point.Map == m_Mobile.Map && + point.Parent == null && !point.Deleted) + { + m_Mobile.DebugSay("I will move towards my waypoint."); + DoMove(m_Mobile.GetDirectionTo(m_Mobile.CurrentWayPoint)); + } + else if (OnAtWayPoint()) + { + m_Mobile.DebugSay("I will go to the next waypoint"); + m_Mobile.CurrentWayPoint = point.NextPoint; + if (point.NextPoint != null && point.NextPoint.Deleted) + m_Mobile.CurrentWayPoint = point.NextPoint = point.NextPoint.NextPoint; + } + } + else if (m_Mobile.IsAnimatedDead) + { + // animated dead follow their master + Mobile master = m_Mobile.SummonMaster; + + if (master != null && master.Map == m_Mobile.Map && master.InRange(m_Mobile, m_Mobile.RangePerception)) + MoveTo(master, false, 1); + else + WalkRandomInHome(2, 2, 1); + } + else if (CheckMove()) + { + if (!m_Mobile.CheckIdle()) + WalkRandomInHome(2, 2, 1); + } + + if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && + !m_Mobile.Combatant.IsDeadBondedPet) m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); + + return true; + } + + public virtual bool DoActionCombat() + { + if (Core.AOS && CheckHerding()) + { + m_Mobile.DebugSay("Praise the shepherd!"); + } + else + { + Mobile c = m_Mobile.Combatant; + + if (c == null || c.Deleted || c.Map != m_Mobile.Map || !c.Alive || c.IsDeadBondedPet) + Action = ActionType.Wander; + else + m_Mobile.Direction = m_Mobile.GetDirectionTo(c); + } + + return true; + } + + public virtual bool DoActionGuard() + { + if (Core.AOS && CheckHerding()) + { + m_Mobile.DebugSay("Praise the shepherd!"); + } + else if (Core.TickCount - m_NextStopGuard < 0) + { + m_Mobile.DebugSay("I am on guard"); + //m_Mobile.Turn( Utility.Random(0, 2) - 1 ); + } + else + { + m_Mobile.DebugSay("I stopped being on guard"); + Action = ActionType.Wander; + } + + return true; + } + + public virtual bool DoActionFlee() + { + Mobile from = m_Mobile.FocusMob; + + if (from == null || from.Deleted || from.Map != m_Mobile.Map) + { + m_Mobile.DebugSay("I have lost him"); + Action = ActionType.Guard; + return true; + } + + if (WalkMobileRange(from, 1, true, m_Mobile.RangePerception * 2, m_Mobile.RangePerception * 3)) + { + m_Mobile.DebugSay("I have fled"); + Action = ActionType.Guard; + return true; + } + + m_Mobile.DebugSay("I am fleeing!"); + + return true; + } + + public virtual bool DoActionInteract() + { + return true; + } + + public virtual bool DoActionBackoff() + { + return true; + } + + public virtual bool Obey() + { + if (m_Mobile.Deleted) + return false; + + switch (m_Mobile.ControlOrder) + { + case OrderType.None: + return DoOrderNone(); + + case OrderType.Come: + return DoOrderCome(); + + case OrderType.Drop: + return DoOrderDrop(); + + case OrderType.Friend: + return DoOrderFriend(); + + case OrderType.Unfriend: + return DoOrderUnfriend(); + + case OrderType.Guard: + return DoOrderGuard(); + + case OrderType.Attack: + return DoOrderAttack(); + + case OrderType.Patrol: + return DoOrderPatrol(); + + case OrderType.Release: + return DoOrderRelease(); + + case OrderType.Stay: + return DoOrderStay(); + + case OrderType.Stop: + return DoOrderStop(); + + case OrderType.Follow: + return DoOrderFollow(); + + case OrderType.Transfer: + return DoOrderTransfer(); + + default: + return false; + } + } + + public virtual void OnCurrentOrderChanged() + { + if (m_Mobile.Deleted || m_Mobile.ControlMaster == null || m_Mobile.ControlMaster.Deleted) + return; + + switch (m_Mobile.ControlOrder) + { + case OrderType.None: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.Home = m_Mobile.Location; + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Come: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Drop: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = true; + m_Mobile.Combatant = null; + break; + + case OrderType.Friend: + case OrderType.Unfriend: + m_Mobile.ControlMaster.RevealingAction(); + break; + + case OrderType.Guard: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = true; + m_Mobile.Combatant = null; + string petname = $"{m_Mobile.Name}"; + m_Mobile.ControlMaster.SendLocalizedMessage(1049671, petname); //~1_PETNAME~ is now guarding you. + break; + + case OrderType.Attack: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + + m_Mobile.Warmode = true; + m_Mobile.Combatant = null; + break; + + case OrderType.Patrol: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Release: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Stay: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Stop: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.Home = m_Mobile.Location; + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Follow: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.ActiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + + case OrderType.Transfer: + m_Mobile.ControlMaster.RevealingAction(); + m_Mobile.CurrentSpeed = m_Mobile.PassiveSpeed; + m_Mobile.PlaySound(m_Mobile.GetIdleSound()); + + m_Mobile.Warmode = false; + m_Mobile.Combatant = null; + break; + } + } + + public virtual bool DoOrderNone() + { + m_Mobile.DebugSay("I have no order"); + + WalkRandomInHome(3, 2, 1); + + if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && + !m_Mobile.Combatant.IsDeadBondedPet) + { + m_Mobile.Warmode = true; + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); + } + else + { + m_Mobile.Warmode = false; + } + + return true; + } + + public virtual bool DoOrderCome() + { + if (m_Mobile.ControlMaster != null && !m_Mobile.ControlMaster.Deleted) + { + int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m_Mobile.ControlMaster); + + if (iCurrDist > m_Mobile.RangePerception) + { + m_Mobile.DebugSay("I have lost my master. I stay here"); + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.None; + } + else + { + m_Mobile.DebugSay("My master told me come"); + + // Not exactly OSI style, but better than nothing. + bool bRun = iCurrDist > 5; + + if (WalkMobileRange(m_Mobile.ControlMaster, 1, bRun, 0, 1)) + { + if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && + !m_Mobile.Combatant.IsDeadBondedPet) + { + m_Mobile.Warmode = true; + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); + } + else + { + m_Mobile.Warmode = false; + } + } + } + } + + return true; + } + + public virtual bool DoOrderDrop() + { + if (m_Mobile.IsDeadPet || !m_Mobile.CanDrop) + return true; + + m_Mobile.DebugSay("I drop my stuff for my master"); + + Container pack = m_Mobile.Backpack; + + if (pack != null) + { + List list = pack.Items; + + for (int i = list.Count - 1; i >= 0; --i) + if (i < list.Count) + list[i].MoveToWorld(m_Mobile.Location, m_Mobile.Map); + } + + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.None; + + return true; + } + + public virtual bool CheckHerding() + { + IPoint2D target = m_Mobile.TargetLocation; + + if (target == null) + return false; // Creature is not being herded + + double distance = m_Mobile.GetDistanceToSqrt(target); + + if (distance < 1 || distance > 15) + { + if (distance < 1 && target.X == 1076 && target.Y == 450 && m_Mobile is HordeMinionFamiliar) + if (m_Mobile.ControlMaster is PlayerMobile pm) + { + QuestSystem qs = pm.Quest; + + if (qs is DarkTidesQuest) + { + QuestObjective obj = qs.FindObjective(typeof(FetchAbraxusScrollObjective)); + + if (obj != null && !obj.Completed) + { + m_Mobile.AddToBackpack(new ScrollOfAbraxus()); + obj.Complete(); + } + } + } + + m_Mobile.TargetLocation = null; + return false; // At the target or too far away + } + + DoMove(m_Mobile.GetDirectionTo(target)); + + return true; + } + + public virtual bool DoOrderFollow() + { + if (CheckHerding()) + { + m_Mobile.DebugSay("Praise the shepherd!"); + } + else if (m_Mobile.ControlTarget != null && !m_Mobile.ControlTarget.Deleted && m_Mobile.ControlTarget != m_Mobile) + { + int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m_Mobile.ControlTarget); + + if (iCurrDist > m_Mobile.RangePerception) + { + m_Mobile.DebugSay("I have lost the one to follow. I stay here"); + + if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && + !m_Mobile.Combatant.IsDeadBondedPet) + { + m_Mobile.Warmode = true; + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); + } + else + { + m_Mobile.Warmode = false; + } + } + else + { + m_Mobile.DebugSay("My master told me to follow: {0}", m_Mobile.ControlTarget.Name); + + // Not exactly OSI style, but better than nothing. + bool bRun = iCurrDist > 5; + + if (WalkMobileRange(m_Mobile.ControlTarget, 1, bRun, 0, 1)) + { + if (m_Mobile.Combatant != null && !m_Mobile.Combatant.Deleted && m_Mobile.Combatant.Alive && + !m_Mobile.Combatant.IsDeadBondedPet) + { + m_Mobile.Warmode = true; + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant); + } + else + { + m_Mobile.Warmode = false; + if (Core.AOS) + m_Mobile.CurrentSpeed = 0.1; + } + } + } + } + else + { + m_Mobile.DebugSay("I have nobody to follow"); + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.None; + } + + return true; + } + + public virtual bool DoOrderFriend() + { + Mobile from = m_Mobile.ControlMaster; + Mobile to = m_Mobile.ControlTarget; + + if (from == null || to == null || from == to || from.Deleted || to.Deleted || !to.Player) + { + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 502039); // *looks confused* + } + else + { + bool youngFrom = from is PlayerMobile mobile && mobile.Young; + bool youngTo = to is PlayerMobile playerMobile && playerMobile.Young; + + if (youngFrom && !youngTo) + { + from.SendLocalizedMessage(502040); // As a young player, you may not friend pets to older players. + } + else if (!youngFrom && youngTo) + { + from.SendLocalizedMessage(502041); // As an older player, you may not friend pets to young players. + } + else if (from.CanBeBeneficial(to, true)) + { + NetState fromState = from.NetState, toState = to.NetState; + + if (fromState != null && toState != null) + { + if (from.HasTrade) + { + from.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending + } + else if (to.HasTrade) + { + to.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending + } + else if (m_Mobile.IsPetFriend(to)) + { + from.SendLocalizedMessage(1049691); // That person is already a friend. + } + else if (!m_Mobile.AllowNewPetFriend) + { + from.SendLocalizedMessage( + 1005482); // Your pet does not seem to be interested in making new friends right now. + } + else + { + // ~1_NAME~ will now accept movement commands from ~2_NAME~. + from.SendLocalizedMessage(1049676, $"{m_Mobile.Name}\t{to.Name}"); + + /* ~1_NAME~ has granted you the ability to give orders to their pet ~2_PET_NAME~. + * This creature will now consider you as a friend. + */ + to.SendLocalizedMessage(1043246, $"{from.Name}\t{m_Mobile.Name}"); + + m_Mobile.AddPetFriend(to); + + m_Mobile.ControlTarget = to; + m_Mobile.ControlOrder = OrderType.Follow; + + return true; + } + } + } + } + + m_Mobile.ControlTarget = from; + m_Mobile.ControlOrder = OrderType.Follow; + + return true; + } + + public virtual bool DoOrderUnfriend() + { + Mobile from = m_Mobile.ControlMaster; + Mobile to = m_Mobile.ControlTarget; + + if (from == null || to == null || from == to || from.Deleted || to.Deleted || !to.Player) + { + m_Mobile.PublicOverheadMessage(MessageType.Regular, 0x3B2, 502039); // *looks confused* + } + else if (!m_Mobile.IsPetFriend(to)) + { + from.SendLocalizedMessage(1070953); // That person is not a friend. + } + else + { + // ~1_NAME~ will no longer accept movement commands from ~2_NAME~. + from.SendLocalizedMessage(1070951, $"{m_Mobile.Name}\t{to.Name}"); + + /* ~1_NAME~ has no longer granted you the ability to give orders to their pet ~2_PET_NAME~. + * This creature will no longer consider you as a friend. + */ + to.SendLocalizedMessage(1070952, $"{from.Name}\t{m_Mobile.Name}"); + + m_Mobile.RemovePetFriend(to); + } + + m_Mobile.ControlTarget = from; + m_Mobile.ControlOrder = OrderType.Follow; + + return true; + } + + public virtual bool DoOrderGuard() + { + if (m_Mobile.IsDeadPet) + return true; + + Mobile controlMaster = m_Mobile.ControlMaster; + + if (controlMaster == null || controlMaster.Deleted) + return true; + + Mobile combatant = m_Mobile.Combatant; + + List aggressors = controlMaster.Aggressors; + + if (aggressors.Count > 0) + { + for (int i = 0; i < aggressors.Count; ++i) + { + AggressorInfo info = aggressors[i]; + Mobile attacker = info.Attacker; + + if (attacker != null && !attacker.Deleted && + attacker.GetDistanceToSqrt(m_Mobile) <= m_Mobile.RangePerception) + if (combatant == null || attacker.GetDistanceToSqrt(controlMaster) < + combatant.GetDistanceToSqrt(controlMaster)) + combatant = attacker; + } + + if (combatant != null) + m_Mobile.DebugSay("Crap, my master has been attacked! I will attack one of those bastards!"); + } + + if (combatant != null && combatant != m_Mobile && combatant != m_Mobile.ControlMaster && !combatant.Deleted && + combatant.Alive && !combatant.IsDeadBondedPet && m_Mobile.CanSee(combatant) && + m_Mobile.CanBeHarmful(combatant, false) && combatant.Map == m_Mobile.Map) + { + m_Mobile.DebugSay("Guarding from target..."); + + m_Mobile.Combatant = combatant; + m_Mobile.FocusMob = combatant; + Action = ActionType.Combat; + + /* + * We need to call Think() here or spell casting monsters will not use + * spells when guarding because their target is never processed. + */ + Think(); + } + else + { + m_Mobile.DebugSay("Nothing to guard from"); + + m_Mobile.Warmode = false; + if (Core.AOS) + m_Mobile.CurrentSpeed = 0.1; + + WalkMobileRange(controlMaster, 1, false, 0, 1); + } + + return true; + } + + public virtual bool DoOrderAttack() + { + if (m_Mobile.IsDeadPet) + return true; + + if (m_Mobile.ControlTarget == null || m_Mobile.ControlTarget.Deleted || + m_Mobile.ControlTarget.Map != m_Mobile.Map || !m_Mobile.ControlTarget.Alive || + m_Mobile.ControlTarget.IsDeadBondedPet) + { + m_Mobile.DebugSay( + "I think he might be dead. He's not anywhere around here at least. That's cool. I'm glad he's dead."); + + if (Core.AOS) + { + m_Mobile.ControlTarget = m_Mobile.ControlMaster; + m_Mobile.ControlOrder = OrderType.Follow; + } + else + { + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.None; + } + + if (m_Mobile.FightMode == FightMode.Closest || m_Mobile.FightMode == FightMode.Aggressor) + { + Mobile newCombatant = null; + double newScore = 0.0; + + foreach (Mobile aggr in m_Mobile.GetMobilesInRange(m_Mobile.RangePerception)) + { + if (!m_Mobile.CanSee(aggr) || aggr.Combatant != m_Mobile) + continue; + + if (aggr.IsDeadBondedPet || !aggr.Alive) + continue; + + double aggrScore = m_Mobile.GetFightModeRanking(aggr, FightMode.Closest, false); + + if ((newCombatant == null || aggrScore > newScore) && m_Mobile.InLOS(aggr)) + { + newCombatant = aggr; + newScore = aggrScore; + } + } + + if (newCombatant != null) + { + m_Mobile.ControlTarget = newCombatant; + m_Mobile.ControlOrder = OrderType.Attack; + m_Mobile.Combatant = newCombatant; + m_Mobile.DebugSay("But -that- is not dead. Here we go again..."); + Think(); + } + } + } + else + { + m_Mobile.DebugSay("Attacking target..."); + Think(); + } + + return true; + } + + public virtual bool DoOrderPatrol() + { + m_Mobile.DebugSay("This order is not yet coded"); + return true; + } + + public virtual bool DoOrderRelease() + { + m_Mobile.DebugSay("I have been released"); + + m_Mobile.PlaySound(m_Mobile.GetAngerSound()); + + m_Mobile.SetControlMaster(null); + m_Mobile.SummonMaster = null; + + m_Mobile.BondingBegin = DateTime.MinValue; + m_Mobile.OwnerAbandonTime = DateTime.MinValue; + m_Mobile.IsBonded = false; + + if (m_Mobile.Spawner is SpawnEntry se && se.HomeLocation != Point3D.Zero) + { + m_Mobile.Home = se.HomeLocation; + m_Mobile.RangeHome = se.HomeRange; + } + + if (m_Mobile.DeleteOnRelease || m_Mobile.IsDeadPet) + m_Mobile.Delete(); + + m_Mobile.BeginDeleteTimer(); + m_Mobile.DropBackpack(); + + return true; + } + + public virtual bool DoOrderStay() + { + if (CheckHerding()) + m_Mobile.DebugSay("Praise the shepherd!"); + else + m_Mobile.DebugSay("My master told me to stay"); + + //m_Mobile.Direction = m_Mobile.GetDirectionTo( m_Mobile.ControlMaster ); + + return true; + } + + public virtual bool DoOrderStop() + { + if (m_Mobile.ControlMaster == null || m_Mobile.ControlMaster.Deleted) + return true; + + m_Mobile.DebugSay("My master told me to stop."); + + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.ControlMaster); + m_Mobile.Home = m_Mobile.Location; + + m_Mobile.ControlTarget = null; + + if (Core.ML) + WalkRandomInHome(3, 2, 1); + else + m_Mobile.ControlOrder = OrderType.None; + + return true; + } + + public virtual bool DoOrderTransfer() + { + if (m_Mobile.IsDeadPet) + return true; + + Mobile from = m_Mobile.ControlMaster; + Mobile to = m_Mobile.ControlTarget; + + if (from != to && from != null && !from.Deleted && to != null && !to.Deleted && to.Player) + { + m_Mobile.DebugSay("Begin transfer with {0}", to.Name); + + bool youngFrom = from is PlayerMobile mobile && mobile.Young; + bool youngTo = to is PlayerMobile playerMobile && playerMobile.Young; + + if (youngFrom && !youngTo) + { + from.SendLocalizedMessage(502051); // As a young player, you may not transfer pets to older players. + } + else if (!youngFrom && youngTo) + { + from.SendLocalizedMessage(502052); // As an older player, you may not transfer pets to young players. + } + else if (!m_Mobile.CanBeControlledBy(to)) + { + string args = $"{to.Name}\t{from.Name}\t "; + + from.SendLocalizedMessage(1043248, + args); // The pet refuses to be transferred because it will not obey ~1_NAME~.~3_BLANK~ + to.SendLocalizedMessage(1043249, + args); // The pet will not accept you as a master because it does not trust you.~3_BLANK~ + } + else if (!m_Mobile.CanBeControlledBy(from)) + { + string args = $"{to.Name}\t{from.Name}\t "; + + from.SendLocalizedMessage(1043250, + args); // The pet refuses to be transferred because it will not obey you sufficiently.~3_BLANK~ + to.SendLocalizedMessage(1043251, + args); // The pet will not accept you as a master because it does not trust ~2_NAME~.~3_BLANK~ + } + else if (TransferItem.IsInCombat(m_Mobile)) + { + from.SendMessage("You may not transfer a pet that has recently been in combat."); + to.SendMessage("The pet may not be transfered to you because it has recently been in combat."); + } + else + { + NetState fromState = from.NetState, toState = to.NetState; + + if (fromState != null && toState != null) + { + if (from.HasTrade) + { + from.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending + } + else if (to.HasTrade) + { + to.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending + } + else + { + Container c = fromState.AddTrade(toState); + c.DropItem(new TransferItem(m_Mobile)); + } + } + } + } + + m_Mobile.ControlTarget = null; + m_Mobile.ControlOrder = OrderType.Stay; + + return true; + } + + public virtual bool DoBardPacified() + { + if (DateTime.UtcNow < m_Mobile.BardEndTime) + { + m_Mobile.DebugSay("I am pacified, I wait"); + m_Mobile.Combatant = null; + m_Mobile.Warmode = false; + } + else + { + m_Mobile.DebugSay("I'm not pacified any longer"); + m_Mobile.BardPacified = false; + } + + return true; + } + + public virtual bool DoBardProvoked() + { + if (DateTime.UtcNow >= m_Mobile.BardEndTime && (m_Mobile.BardMaster == null || m_Mobile.BardMaster.Deleted || + m_Mobile.BardMaster.Map != m_Mobile.Map || + m_Mobile.GetDistanceToSqrt(m_Mobile.BardMaster) > + m_Mobile.RangePerception)) + { + m_Mobile.DebugSay("I have lost my provoker"); + m_Mobile.BardProvoked = false; + m_Mobile.BardMaster = null; + m_Mobile.BardTarget = null; + + m_Mobile.Combatant = null; + m_Mobile.Warmode = false; + } + else + { + if (m_Mobile.BardTarget == null || m_Mobile.BardTarget.Deleted || m_Mobile.BardTarget.Map != m_Mobile.Map || + m_Mobile.GetDistanceToSqrt(m_Mobile.BardTarget) > m_Mobile.RangePerception) + { + m_Mobile.DebugSay("I have lost my provoke target"); + m_Mobile.BardProvoked = false; + m_Mobile.BardMaster = null; + m_Mobile.BardTarget = null; + + m_Mobile.Combatant = null; + m_Mobile.Warmode = false; + } + else + { + m_Mobile.Combatant = m_Mobile.BardTarget; + m_Action = ActionType.Combat; + + m_Mobile.OnThink(); + Think(); + } + } + + return true; + } + + public virtual void WalkRandom(int iChanceToNotMove, int iChanceToDir, int iSteps) + { + if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves) + return; + + for (int i = 0; i < iSteps; i++) + if (Utility.Random(8 * iChanceToNotMove) <= 8) + { + int iRndMove = Utility.Random(0, 8 + 9 * iChanceToDir); + + switch (iRndMove) + { + case 0: + DoMove(Direction.Up); + break; + case 1: + DoMove(Direction.North); + break; + case 2: + DoMove(Direction.Left); + break; + case 3: + DoMove(Direction.West); + break; + case 5: + DoMove(Direction.Down); + break; + case 6: + DoMove(Direction.South); + break; + case 7: + DoMove(Direction.Right); + break; + case 8: + DoMove(Direction.East); + break; + default: + DoMove(m_Mobile.Direction); + break; + } + } + } + + public double TransformMoveDelay(double delay) + { + bool isPassive = delay == m_Mobile.PassiveSpeed; + bool isControlled = m_Mobile.Controlled || m_Mobile.Summoned; + + if (delay == 0.2) + delay = 0.3; + else if (delay == 0.25) + delay = 0.45; + else if (delay == 0.3) + delay = 0.6; + else if (delay == 0.4) + delay = 0.9; + else if (delay == 0.5) + delay = 1.05; + else if (delay == 0.6) + delay = 1.2; + else if (delay == 0.8) + delay = 1.5; + + if (isPassive) + delay += 0.2; + + if (!isControlled) + { + delay += 0.1; + } + else if (m_Mobile.Controlled) + { + if (m_Mobile.ControlOrder == OrderType.Follow && m_Mobile.ControlTarget == m_Mobile.ControlMaster) + delay *= 0.5; + + delay -= 0.075; + } + + if (m_Mobile.ReduceSpeedWithDamage || m_Mobile.IsSubdued) + { + double offset = (double)m_Mobile.Hits / m_Mobile.HitsMax; + + if (offset < 0.0) + offset = 0.0; + else if (offset > 1.0) + offset = 1.0; + + offset = 1.0 - offset; + + delay += offset * 0.8; + } + + if (delay < 0.0) + delay = 0.0; + + if (double.IsNaN(delay)) + { + using (StreamWriter op = new StreamWriter("nan_transform.txt", true)) + { + op.WriteLine( + $"NaN in TransformMoveDelay: {DateTime.UtcNow}, {GetType()}, {(m_Mobile == null ? "null" : m_Mobile.GetType().ToString())}, {m_Mobile.HitsMax}"); + } + + return 1.0; + } + + return delay; + } + + public virtual bool CheckMove() + { + return Core.TickCount - NextMove >= 0; + } + + public virtual bool DoMove(Direction d) + { + return DoMove(d, false); + } + + public virtual bool DoMove(Direction d, bool badStateOk) + { + MoveResult res = DoMoveImpl(d); + + return res == MoveResult.Success || res == MoveResult.SuccessAutoTurn || + badStateOk && res == MoveResult.BadState; + } + + public virtual MoveResult DoMoveImpl(Direction d) + { + if (m_Mobile.Deleted || m_Mobile.Frozen || m_Mobile.Paralyzed || + m_Mobile.Spell != null && m_Mobile.Spell.IsCasting || m_Mobile.DisallowAllMoves) + return MoveResult.BadState; + if (!CheckMove()) + return MoveResult.BadState; + + // This makes them always move one step, never any direction changes + m_Mobile.Direction = d; + + int delay = (int)(TransformMoveDelay(m_Mobile.CurrentSpeed) * 1000); + + NextMove += delay; + + if (Core.TickCount - NextMove > 0) + NextMove = Core.TickCount; + + m_Mobile.Pushing = false; + + MoveImpl.IgnoreMovableImpassables = m_Mobile.CanMoveOverObstacles && !m_Mobile.CanDestroyObstacles; + + if ((m_Mobile.Direction & Direction.Mask) != (d & Direction.Mask)) + { + bool v = m_Mobile.Move(d); + + MoveImpl.IgnoreMovableImpassables = false; + return v ? MoveResult.Success : MoveResult.Blocked; + } + + if (!m_Mobile.Move(d)) + { + bool wasPushing = m_Mobile.Pushing; + + bool blocked = true; + + bool canOpenDoors = m_Mobile.CanOpenDoors; + bool canDestroyObstacles = m_Mobile.CanDestroyObstacles; + + if (canOpenDoors || canDestroyObstacles) + { + m_Mobile.DebugSay("My movement was blocked, I will try to clear some obstacles."); + + Map map = m_Mobile.Map; + + if (map != null) + { + int x = m_Mobile.X, y = m_Mobile.Y; + Movement.Movement.Offset(d, ref x, ref y); + + int destroyables = 0; + + IPooledEnumerable eable = map.GetItemsInRange(new Point3D(x, y, m_Mobile.Location.Z), 1); + + foreach (Item item in eable) + if (canOpenDoors && item is BaseDoor door && door.Z + door.ItemData.Height > m_Mobile.Z && + m_Mobile.Z + 16 > door.Z) + { + if (door.X != x || door.Y != y) + continue; + + if (!door.Locked || !door.UseLocks()) + m_Obstacles.Enqueue(door); + + if (!canDestroyObstacles) + break; + } + else if (canDestroyObstacles && item.Movable && item.ItemData.Impassable && + item.Z + item.ItemData.Height > m_Mobile.Z && m_Mobile.Z + 16 > item.Z) + { + if (!m_Mobile.InRange(item.GetWorldLocation(), 1)) + continue; + + m_Obstacles.Enqueue(item); + ++destroyables; + } + + eable.Free(); + + if (destroyables > 0) + Effects.PlaySound(new Point3D(x, y, m_Mobile.Z), m_Mobile.Map, 0x3B3); + + if (m_Obstacles.Count > 0) + blocked = false; // retry movement + + while (m_Obstacles.Count > 0) + { + Item item = m_Obstacles.Dequeue(); + + if (item is BaseDoor door) + { + m_Mobile.DebugSay( + "Little do they expect, I've learned how to open doors. Didn't they read the script??"); + m_Mobile.DebugSay("*twist*"); + + door.Use(m_Mobile); + } + else + { + m_Mobile.DebugSay("Ugabooga. I'm so big and tough I can destroy it: {0}", + item.GetType().Name); + + if (item is Container cont) + { + for (int i = 0; i < cont.Items.Count; ++i) + { + Item check = cont.Items[i]; + + if (check.Movable && check.ItemData.Impassable && + cont.Z + check.ItemData.Height > m_Mobile.Z) + m_Obstacles.Enqueue(check); + } + + cont.Destroy(); + } + else + { + item.Delete(); + } + } + } + + if (!blocked) + blocked = !m_Mobile.Move(d); + } + } + + if (blocked) + { + int offset = Utility.RandomDouble() >= 0.6 ? 1 : -1; + + for (int i = 0; i < 2; ++i) + { + m_Mobile.TurnInternal(offset); + + if (m_Mobile.Move(m_Mobile.Direction)) + { + MoveImpl.IgnoreMovableImpassables = false; + return MoveResult.SuccessAutoTurn; + } + } + + MoveImpl.IgnoreMovableImpassables = false; + return wasPushing ? MoveResult.BadState : MoveResult.Blocked; + } + + MoveImpl.IgnoreMovableImpassables = false; + return MoveResult.Success; + } + + MoveImpl.IgnoreMovableImpassables = false; + return MoveResult.Success; + } + + public virtual void WalkRandomInHome(int iChanceToNotMove, int iChanceToDir, int iSteps) + { + if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves) + return; + + if (m_Mobile.Home == Point3D.Zero) + { + if (m_Mobile.Spawner is SpawnEntry entry) + { + Region region = entry.Region; + + if (m_Mobile.Region.AcceptsSpawnsFrom(region)) + { + m_Mobile.WalkRegion = region; + WalkRandom(iChanceToNotMove, iChanceToDir, iSteps); + m_Mobile.WalkRegion = null; + } + else + { + if (region.GoLocation != Point3D.Zero && Utility.Random(10) > 5) + DoMove(m_Mobile.GetDirectionTo(region.GoLocation)); + else + WalkRandom(iChanceToNotMove, iChanceToDir, 1); + } + } + else + { + WalkRandom(iChanceToNotMove, iChanceToDir, iSteps); + } + } + else + { + for (int i = 0; i < iSteps; i++) + if (m_Mobile.RangeHome != 0) + { + int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m_Mobile.Home); + + if (iCurrDist < m_Mobile.RangeHome * 2 / 3) + { + WalkRandom(iChanceToNotMove, iChanceToDir, 1); + } + else if (iCurrDist > m_Mobile.RangeHome) + { + DoMove(m_Mobile.GetDirectionTo(m_Mobile.Home)); + } + else + { + if (Utility.Random(10) > 5) + DoMove(m_Mobile.GetDirectionTo(m_Mobile.Home)); + else + WalkRandom(iChanceToNotMove, iChanceToDir, 1); + } + } + else + { + if (m_Mobile.Location != m_Mobile.Home) DoMove(m_Mobile.GetDirectionTo(m_Mobile.Home)); + } + } + } + + public virtual bool CheckFlee() + { + if (m_Mobile.CheckFlee()) + { + Mobile combatant = m_Mobile.Combatant; + + if (combatant == null) + { + WalkRandom(1, 2, 1); + } + else + { + Direction d = combatant.GetDirectionTo(m_Mobile); + + d = (Direction)((int)d + Utility.RandomMinMax(-1, +1)); + + m_Mobile.Direction = d; + m_Mobile.Move(d); + } + + return true; + } + + return false; + } + + public virtual void OnTeleported() + { + if (m_Path != null) + { + m_Mobile.DebugSay("Teleported; repathing"); + m_Path.ForceRepath(); + } + } + + public virtual bool MoveTo(Mobile m, bool run, int range) + { + if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves || m == null || m.Deleted) + return false; + + if (m_Mobile.InRange(m, range)) + { + m_Path = null; + return true; + } + + if (m_Path != null && m_Path.Goal == m) + { + if (m_Path.Follow(run, 1)) + { + m_Path = null; + return true; + } + } + else if (!DoMove(m_Mobile.GetDirectionTo(m), true)) + { + m_Path = new PathFollower(m_Mobile, m); + m_Path.Mover = DoMoveImpl; + + if (m_Path.Follow(run, 1)) + { + m_Path = null; + return true; + } + } + else + { + m_Path = null; + return true; + } + + return false; + } + + /* + * Walk at range distance from mobile + * + * iSteps : Number of steps + * bRun : Do we run + * iWantDistMin : The minimum distance we want to be + * iWantDistMax : The maximum distance we want to be + * + */ + public virtual bool WalkMobileRange(Mobile m, int iSteps, bool bRun, int iWantDistMin, int iWantDistMax) + { + if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves) + return false; + + if (m == null) + return false; + + for (int i = 0; i < iSteps; i++) + { + // Get the current distance + int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m); + + if (iCurrDist < iWantDistMin || iCurrDist > iWantDistMax) + { + bool needCloser = iCurrDist > iWantDistMax; + bool needFurther = !needCloser; + + if (needCloser && m_Path != null && m_Path.Goal == m) + { + if (m_Path.Follow(bRun, 1)) + m_Path = null; + } + else + { + Direction dirTo; + + if (iCurrDist > iWantDistMax) + dirTo = m_Mobile.GetDirectionTo(m); + else + dirTo = m.GetDirectionTo(m_Mobile); + + // Add the run flag + if (bRun) + dirTo = dirTo | Direction.Running; + + if (!DoMove(dirTo, true) && needCloser) + { + m_Path = new PathFollower(m_Mobile, m); + m_Path.Mover = DoMoveImpl; + + if (m_Path.Follow(bRun, 1)) + m_Path = null; + } + else + { + m_Path = null; + } + } + } + else + { + return true; + } + } + + // Get the current distance + int iNewDist = (int)m_Mobile.GetDistanceToSqrt(m); + + if (iNewDist >= iWantDistMin && iNewDist <= iWantDistMax) + return true; + + return false; + } + + /* + * Here we check to acquire a target from our surrounding + * + * iRange : The range + * acqType : A type of acquire we want (closest, strongest, etc) + * bPlayerOnly : Don't bother with other creatures or NPCs, want a player + * bFacFriend : Check people in my faction + * bFacFoe : Check people in other factions + * + */ + public virtual bool AcquireFocusMob(int iRange, FightMode acqType, bool bPlayerOnly, bool bFacFriend, bool bFacFoe) + { + if (m_Mobile.Deleted) + return false; + + if (m_Mobile.BardProvoked) + { + if (m_Mobile.BardTarget == null || m_Mobile.BardTarget.Deleted) + { + m_Mobile.FocusMob = null; + return false; + } + + m_Mobile.FocusMob = m_Mobile.BardTarget; + return m_Mobile.FocusMob != null; + } + + if (m_Mobile.Controlled) + { + if (m_Mobile.ControlTarget == null || m_Mobile.ControlTarget.Deleted || m_Mobile.ControlTarget.Hidden || + !m_Mobile.ControlTarget.Alive || m_Mobile.ControlTarget.IsDeadBondedPet || + !m_Mobile.InRange(m_Mobile.ControlTarget, m_Mobile.RangePerception * 2)) + { + if (m_Mobile.ControlTarget != null && m_Mobile.ControlTarget != m_Mobile.ControlMaster) + m_Mobile.ControlTarget = null; + + m_Mobile.FocusMob = null; + return false; + } + + m_Mobile.FocusMob = m_Mobile.ControlTarget; + return m_Mobile.FocusMob != null; + } + + if (m_Mobile.ConstantFocus != null) + { + m_Mobile.DebugSay("Acquired my constant focus"); + m_Mobile.FocusMob = m_Mobile.ConstantFocus; + return true; + } + + if (acqType == FightMode.None) + { + m_Mobile.FocusMob = null; + return false; + } + + if (acqType == FightMode.Aggressor && m_Mobile.Aggressors.Count == 0 && m_Mobile.Aggressed.Count == 0 && + m_Mobile.FactionAllegiance == null && m_Mobile.EthicAllegiance == null) + { + m_Mobile.FocusMob = null; + return false; + } + + if (Core.TickCount - m_Mobile.NextReacquireTime < 0) + { + m_Mobile.FocusMob = null; + return false; + } + + m_Mobile.NextReacquireTime = Core.TickCount + (int)m_Mobile.ReacquireDelay.TotalMilliseconds; + + m_Mobile.DebugSay("Acquiring..."); + + Map map = m_Mobile.Map; + + if (map != null) + { + Mobile newFocusMob = null; + double val = double.MinValue; + + IPooledEnumerable eable = map.GetMobilesInRange(m_Mobile.Location, iRange); + + foreach (Mobile m in eable) + { + if (m.Deleted || m.Blessed) + continue; + + // Let's not target ourselves... + if (m == m_Mobile || m is BaseFamiliar) + continue; + + // Dead targets are invalid. + if (!m.Alive || m.IsDeadBondedPet) + continue; + + // Staff members cannot be targeted. + if (m.AccessLevel > AccessLevel.Player) + continue; + + // Does it have to be a player? + if (bPlayerOnly && !m.Player) + continue; + + // Can't acquire a target we can't see. + if (!m_Mobile.CanSee(m)) + continue; + + BaseCreature bc = m as BaseCreature; + PlayerMobile pm = m as PlayerMobile; + + if (Core.AOS && bc?.Summoned == true && bc?.Controlled != true) + continue; + + if (m_Mobile.Summoned && m_Mobile.SummonMaster != null) + { + // If this is a summon, it can't target its controller. + if (m == m_Mobile.SummonMaster) + continue; + + // It also must abide by harmful spell rules. + if (!SpellHelper.ValidIndirectTarget(m_Mobile.SummonMaster, m)) + continue; + + // Animated creatures cannot attack players directly. + if (pm != null && m_Mobile.IsAnimatedDead) + continue; + } + + // If we only want faction friends, make sure it's one. + if (bFacFriend && !m_Mobile.IsFriend(m)) + continue; - Hue = creature.Hue & 0x0FFF; - } + //Ignore anyone under EtherealVoyage + if (TransformationSpellHelper.UnderTransformation(m, typeof(EtherealVoyageSpell))) + continue; - public TransferItem(Serial serial) - : base(serial) - { - } - - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - - writer.Write((int)0); // version - } + // Ignore players with activated honor + if (pm?.HonorActive == true && m_Mobile.Combatant != m) + continue; + + if (acqType == FightMode.Aggressor || acqType == FightMode.Evil) + { + bool bValid = IsHostile(m); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + if (!bValid) + bValid = m_Mobile.GetFactionAllegiance(m) == BaseCreature.Allegiance.Enemy || + m_Mobile.GetEthicAllegiance(m) == BaseCreature.Allegiance.Enemy; - int version = reader.ReadInt(); - - Delete(); - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - list.Add(1041603); // This item represents a pet currently in consideration for trade - list.Add(1041601, m_Creature.Name); // Pet Name: ~1_val~ - - if (m_Creature.ControlMaster != null) - list.Add(1041602, m_Creature.ControlMaster.Name); // Owner: ~1_val~ - } - - public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) - { - if (!base.AllowSecureTrade(from, to, newOwner, accepted)) - return false; - - if (Deleted || m_Creature == null || m_Creature.Deleted || m_Creature.ControlMaster != from || !from.CheckAlive() || !to.CheckAlive()) - return false; - - if (from.Map != m_Creature.Map || !from.InRange(m_Creature, 14)) - return false; - - bool youngFrom = from is PlayerMobile mobile && mobile.Young; - bool youngTo = to is PlayerMobile playerMobile && playerMobile.Young; - - if (accepted && youngFrom && !youngTo) - { - from.SendLocalizedMessage(502051); // As a young player, you may not transfer pets to older players. - } - else if (accepted && !youngFrom && youngTo) - { - from.SendLocalizedMessage(502052); // As an older player, you may not transfer pets to young players. - } - else if (accepted && !m_Creature.CanBeControlledBy(to)) - { - string args = $"{to.Name}\t{from.Name}\t "; - - from.SendLocalizedMessage(1043248, args); // The pet refuses to be transferred because it will not obey ~1_NAME~.~3_BLANK~ - to.SendLocalizedMessage(1043249, args); // The pet will not accept you as a master because it does not trust you.~3_BLANK~ - - return false; - } - else if (accepted && !m_Creature.CanBeControlledBy(from)) - { - string args = $"{to.Name}\t{from.Name}\t "; - - from.SendLocalizedMessage(1043250, args); // The pet refuses to be transferred because it will not obey you sufficiently.~3_BLANK~ - to.SendLocalizedMessage(1043251, args); // The pet will not accept you as a master because it does not trust ~2_NAME~.~3_BLANK~ - } - else if (accepted && (to.Followers + m_Creature.ControlSlots) > to.FollowersMax) - { - to.SendLocalizedMessage(1049607); // You have too many followers to control that creature. - - return false; - } - else if (accepted && IsInCombat(m_Creature)) - { - from.SendMessage("You may not transfer a pet that has recently been in combat."); - to.SendMessage("The pet may not be transfered to you because it has recently been in combat."); - - return false; - } - - return true; - } - - public override void OnSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) - { - if (Deleted) - return; - - Delete(); - - if (m_Creature == null || m_Creature.Deleted || m_Creature.ControlMaster != from || !from.CheckAlive() || !to.CheckAlive()) - return; - - if (from.Map != m_Creature.Map || !from.InRange(m_Creature, 14)) - return; - - if (accepted) - { - if (m_Creature.SetControlMaster(to)) - { - if (m_Creature.Summoned) - m_Creature.SummonMaster = to; - - m_Creature.ControlTarget = to; - m_Creature.ControlOrder = OrderType.Follow; - - m_Creature.BondingBegin = DateTime.MinValue; - m_Creature.OwnerAbandonTime = DateTime.MinValue; - m_Creature.IsBonded = false; - - m_Creature.PlaySound(m_Creature.GetIdleSound()); - - string args = $"{from.Name}\t{m_Creature.Name}\t{to.Name}"; - - from.SendLocalizedMessage(1043253, args); // You have transferred your pet to ~3_GETTER~. - to.SendLocalizedMessage(1043252, args); // ~1_NAME~ has transferred the allegiance of ~2_PET_NAME~ to you. - } - } - } - } - - public virtual bool DoOrderTransfer() - { - if (m_Mobile.IsDeadPet) - return true; - - Mobile from = m_Mobile.ControlMaster; - Mobile to = m_Mobile.ControlTarget; - - if (from != to && from != null && !from.Deleted && to != null && !to.Deleted && to.Player) - { - m_Mobile.DebugSay("Begin transfer with {0}", to.Name); - - bool youngFrom = from is PlayerMobile mobile && mobile.Young; - bool youngTo = to is PlayerMobile playerMobile && playerMobile.Young; - - if (youngFrom && !youngTo) - { - from.SendLocalizedMessage(502051); // As a young player, you may not transfer pets to older players. - } - else if (!youngFrom && youngTo) - { - from.SendLocalizedMessage(502052); // As an older player, you may not transfer pets to young players. - } - else if (!m_Mobile.CanBeControlledBy(to)) - { - string args = $"{to.Name}\t{from.Name}\t "; - - from.SendLocalizedMessage(1043248, args); // The pet refuses to be transferred because it will not obey ~1_NAME~.~3_BLANK~ - to.SendLocalizedMessage(1043249, args); // The pet will not accept you as a master because it does not trust you.~3_BLANK~ - } - else if (!m_Mobile.CanBeControlledBy(from)) - { - string args = $"{to.Name}\t{from.Name}\t "; - - from.SendLocalizedMessage(1043250, args); // The pet refuses to be transferred because it will not obey you sufficiently.~3_BLANK~ - to.SendLocalizedMessage(1043251, args); // The pet will not accept you as a master because it does not trust ~2_NAME~.~3_BLANK~ - } - else if (TransferItem.IsInCombat(m_Mobile)) - { - from.SendMessage("You may not transfer a pet that has recently been in combat."); - to.SendMessage("The pet may not be transfered to you because it has recently been in combat."); - } - else - { - NetState fromState = from.NetState, toState = to.NetState; - - if (fromState != null && toState != null) - { - if (from.HasTrade) - { - from.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending - } - else if (to.HasTrade) - { - to.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending - } - else - { - Container c = fromState.AddTrade(toState); - c.DropItem(new TransferItem(m_Mobile)); - } - } - } - } - - m_Mobile.ControlTarget = null; - m_Mobile.ControlOrder = OrderType.Stay; - - return true; - } - - public virtual bool DoBardPacified() - { - if (DateTime.UtcNow < m_Mobile.BardEndTime) - { - m_Mobile.DebugSay("I am pacified, I wait"); - m_Mobile.Combatant = null; - m_Mobile.Warmode = false; - - } - else - { - m_Mobile.DebugSay("I'm not pacified any longer"); - m_Mobile.BardPacified = false; - } - - return true; - } - - public virtual bool DoBardProvoked() - { - if (DateTime.UtcNow >= m_Mobile.BardEndTime && (m_Mobile.BardMaster == null || m_Mobile.BardMaster.Deleted || m_Mobile.BardMaster.Map != m_Mobile.Map || m_Mobile.GetDistanceToSqrt(m_Mobile.BardMaster) > m_Mobile.RangePerception)) - { - m_Mobile.DebugSay("I have lost my provoker"); - m_Mobile.BardProvoked = false; - m_Mobile.BardMaster = null; - m_Mobile.BardTarget = null; - - m_Mobile.Combatant = null; - m_Mobile.Warmode = false; - } - else - { - if (m_Mobile.BardTarget == null || m_Mobile.BardTarget.Deleted || m_Mobile.BardTarget.Map != m_Mobile.Map || m_Mobile.GetDistanceToSqrt(m_Mobile.BardTarget) > m_Mobile.RangePerception) - { - m_Mobile.DebugSay("I have lost my provoke target"); - m_Mobile.BardProvoked = false; - m_Mobile.BardMaster = null; - m_Mobile.BardTarget = null; - - m_Mobile.Combatant = null; - m_Mobile.Warmode = false; - } - else - { - m_Mobile.Combatant = m_Mobile.BardTarget; - m_Action = ActionType.Combat; - - m_Mobile.OnThink(); - Think(); - } - } - - return true; - } - - public virtual void WalkRandom(int iChanceToNotMove, int iChanceToDir, int iSteps) - { - if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves) - return; - - for (int i = 0; i < iSteps; i++) - { - if (Utility.Random(8 * iChanceToNotMove) <= 8) - { - int iRndMove = Utility.Random(0, 8 + (9 * iChanceToDir)); - - switch (iRndMove) - { - case 0: - DoMove(Direction.Up); - break; - case 1: - DoMove(Direction.North); - break; - case 2: - DoMove(Direction.Left); - break; - case 3: - DoMove(Direction.West); - break; - case 5: - DoMove(Direction.Down); - break; - case 6: - DoMove(Direction.South); - break; - case 7: - DoMove(Direction.Right); - break; - case 8: - DoMove(Direction.East); - break; - default: - DoMove(m_Mobile.Direction); - break; - } - } - } - } - - public double TransformMoveDelay(double delay) - { - bool isPassive = (delay == m_Mobile.PassiveSpeed); - bool isControlled = (m_Mobile.Controlled || m_Mobile.Summoned); - - if (delay == 0.2) - delay = 0.3; - else if (delay == 0.25) - delay = 0.45; - else if (delay == 0.3) - delay = 0.6; - else if (delay == 0.4) - delay = 0.9; - else if (delay == 0.5) - delay = 1.05; - else if (delay == 0.6) - delay = 1.2; - else if (delay == 0.8) - delay = 1.5; - - if (isPassive) - delay += 0.2; - - if (!isControlled) - { - delay += 0.1; - } - else if (m_Mobile.Controlled) - { - if (m_Mobile.ControlOrder == OrderType.Follow && m_Mobile.ControlTarget == m_Mobile.ControlMaster) - delay *= 0.5; - - delay -= 0.075; - } - - if (m_Mobile.ReduceSpeedWithDamage || m_Mobile.IsSubdued) - { - double offset = (double)m_Mobile.Hits / m_Mobile.HitsMax; - - if (offset < 0.0) - offset = 0.0; - else if (offset > 1.0) - offset = 1.0; - - offset = 1.0 - offset; - - delay += (offset * 0.8); - } - - if (delay < 0.0) - delay = 0.0; - - if (double.IsNaN(delay)) - { - using (StreamWriter op = new StreamWriter("nan_transform.txt", true)) - { - op.WriteLine( - $"NaN in TransformMoveDelay: {DateTime.UtcNow}, {GetType().ToString()}, {(m_Mobile == null ? "null" : m_Mobile.GetType().ToString())}, {m_Mobile.HitsMax}"); - } - - return 1.0; - } - - return delay; - } - - public long NextMove { get; set; } - - public virtual bool CheckMove() - { - return (Core.TickCount - NextMove >= 0); - } - - public virtual bool DoMove(Direction d) - { - return DoMove(d, false); - } - - public virtual bool DoMove(Direction d, bool badStateOk) - { - MoveResult res = DoMoveImpl(d); - - return (res == MoveResult.Success || res == MoveResult.SuccessAutoTurn || (badStateOk && res == MoveResult.BadState)); - } - - private static Queue m_Obstacles = new Queue(); - - public virtual MoveResult DoMoveImpl(Direction d) - { - if (m_Mobile.Deleted || m_Mobile.Frozen || m_Mobile.Paralyzed || (m_Mobile.Spell != null && m_Mobile.Spell.IsCasting) || m_Mobile.DisallowAllMoves) - return MoveResult.BadState; - if (!CheckMove()) - return MoveResult.BadState; - - // This makes them always move one step, never any direction changes - m_Mobile.Direction = d; - - int delay = (int)(TransformMoveDelay(m_Mobile.CurrentSpeed) * 1000); - - NextMove += delay; - - if (Core.TickCount - NextMove > 0) - NextMove = Core.TickCount; - - m_Mobile.Pushing = false; - - MoveImpl.IgnoreMovableImpassables = (m_Mobile.CanMoveOverObstacles && !m_Mobile.CanDestroyObstacles); - - if ((m_Mobile.Direction & Direction.Mask) != (d & Direction.Mask)) - { - bool v = m_Mobile.Move(d); - - MoveImpl.IgnoreMovableImpassables = false; - return (v ? MoveResult.Success : MoveResult.Blocked); - } - if (!m_Mobile.Move(d)) - { - bool wasPushing = m_Mobile.Pushing; - - bool blocked = true; - - bool canOpenDoors = m_Mobile.CanOpenDoors; - bool canDestroyObstacles = m_Mobile.CanDestroyObstacles; - - if (canOpenDoors || canDestroyObstacles) - { - m_Mobile.DebugSay("My movement was blocked, I will try to clear some obstacles."); - - Map map = m_Mobile.Map; - - if (map != null) - { - int x = m_Mobile.X, y = m_Mobile.Y; - Movement.Movement.Offset(d, ref x, ref y); - - int destroyables = 0; - - IPooledEnumerable eable = map.GetItemsInRange(new Point3D(x, y, m_Mobile.Location.Z), 1); - - foreach (Item item in eable) - { - if (canOpenDoors && item is BaseDoor door && (door.Z + door.ItemData.Height) > m_Mobile.Z && (m_Mobile.Z + 16) > door.Z) - { - if (door.X != x || door.Y != y) - continue; - - if (!door.Locked || !door.UseLocks()) - m_Obstacles.Enqueue(door); - - if (!canDestroyObstacles) - break; - } - else if (canDestroyObstacles && item.Movable && item.ItemData.Impassable && (item.Z + item.ItemData.Height) > m_Mobile.Z && (m_Mobile.Z + 16) > item.Z) - { - if (!m_Mobile.InRange(item.GetWorldLocation(), 1)) - continue; - - m_Obstacles.Enqueue(item); - ++destroyables; - } - } - - eable.Free(); - - if (destroyables > 0) - Effects.PlaySound(new Point3D(x, y, m_Mobile.Z), m_Mobile.Map, 0x3B3); - - if (m_Obstacles.Count > 0) - blocked = false; // retry movement - - while (m_Obstacles.Count > 0) - { - Item item = m_Obstacles.Dequeue(); - - if (item is BaseDoor door) - { - m_Mobile.DebugSay("Little do they expect, I've learned how to open doors. Didn't they read the script??"); - m_Mobile.DebugSay("*twist*"); - - door.Use(m_Mobile); - } - else - { - m_Mobile.DebugSay("Ugabooga. I'm so big and tough I can destroy it: {0}", item.GetType().Name); - - if (item is Container cont) - { - for (int i = 0; i < cont.Items.Count; ++i) - { - Item check = cont.Items[i]; - - if (check.Movable && check.ItemData.Impassable && (cont.Z + check.ItemData.Height) > m_Mobile.Z) - m_Obstacles.Enqueue(check); - } - - cont.Destroy(); - } - else - { - item.Delete(); - } - } - } - - if (!blocked) - blocked = !m_Mobile.Move(d); - } - } - - if (blocked) - { - int offset = (Utility.RandomDouble() >= 0.6 ? 1 : -1); - - for (int i = 0; i < 2; ++i) - { - m_Mobile.TurnInternal(offset); - - if (m_Mobile.Move(m_Mobile.Direction)) - { - MoveImpl.IgnoreMovableImpassables = false; - return MoveResult.SuccessAutoTurn; - } - } - - MoveImpl.IgnoreMovableImpassables = false; - return (wasPushing ? MoveResult.BadState : MoveResult.Blocked); - } - - MoveImpl.IgnoreMovableImpassables = false; - return MoveResult.Success; - } - - MoveImpl.IgnoreMovableImpassables = false; - return MoveResult.Success; - } - - public virtual void WalkRandomInHome(int iChanceToNotMove, int iChanceToDir, int iSteps) - { - if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves) - return; - - if (m_Mobile.Home == Point3D.Zero) - { - if (m_Mobile.Spawner is SpawnEntry entry) - { - Region region = entry.Region; - - if (m_Mobile.Region.AcceptsSpawnsFrom(region)) - { - m_Mobile.WalkRegion = region; - WalkRandom(iChanceToNotMove, iChanceToDir, iSteps); - m_Mobile.WalkRegion = null; - } - else - { - if (region.GoLocation != Point3D.Zero && Utility.Random(10) > 5) - { - DoMove(m_Mobile.GetDirectionTo(region.GoLocation)); - } - else - { - WalkRandom(iChanceToNotMove, iChanceToDir, 1); - } - } - } - else - { - WalkRandom(iChanceToNotMove, iChanceToDir, iSteps); - } - } - else - { - for (int i = 0; i < iSteps; i++) - { - if (m_Mobile.RangeHome != 0) - { - int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m_Mobile.Home); - - if (iCurrDist < m_Mobile.RangeHome * 2 / 3) - { - WalkRandom(iChanceToNotMove, iChanceToDir, 1); - } - else if (iCurrDist > m_Mobile.RangeHome) - { - DoMove(m_Mobile.GetDirectionTo(m_Mobile.Home)); - } - else - { - if (Utility.Random(10) > 5) - { - DoMove(m_Mobile.GetDirectionTo(m_Mobile.Home)); - } - else - { - WalkRandom(iChanceToNotMove, iChanceToDir, 1); - } - } - } - else - { - if (m_Mobile.Location != m_Mobile.Home) - { - DoMove(m_Mobile.GetDirectionTo(m_Mobile.Home)); - } - } - } - } - } - - public virtual bool CheckFlee() - { - if (m_Mobile.CheckFlee()) - { - Mobile combatant = m_Mobile.Combatant; - - if (combatant == null) - { - WalkRandom(1, 2, 1); - } - else - { - Direction d = combatant.GetDirectionTo(m_Mobile); - - d = (Direction)((int)d + Utility.RandomMinMax(-1, +1)); - - m_Mobile.Direction = d; - m_Mobile.Move(d); - } - - return true; - } - - return false; - } - - protected PathFollower m_Path; - - public virtual void OnTeleported() - { - if (m_Path != null) - { - m_Mobile.DebugSay("Teleported; repathing"); - m_Path.ForceRepath(); - } - } - - public virtual bool MoveTo(Mobile m, bool run, int range) - { - if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves || m == null || m.Deleted) - return false; - - if (m_Mobile.InRange(m, range)) - { - m_Path = null; - return true; - } - - if (m_Path != null && m_Path.Goal == m) - { - if (m_Path.Follow(run, 1)) - { - m_Path = null; - return true; - } - } - else if (!DoMove(m_Mobile.GetDirectionTo(m), true)) - { - m_Path = new PathFollower(m_Mobile, m); - m_Path.Mover = DoMoveImpl; - - if (m_Path.Follow(run, 1)) - { - m_Path = null; - return true; - } - } - else - { - m_Path = null; - return true; - } - - return false; - } - - /* - * Walk at range distance from mobile - * - * iSteps : Number of steps - * bRun : Do we run - * iWantDistMin : The minimum distance we want to be - * iWantDistMax : The maximum distance we want to be - * - */ - public virtual bool WalkMobileRange(Mobile m, int iSteps, bool bRun, int iWantDistMin, int iWantDistMax) - { - if (m_Mobile.Deleted || m_Mobile.DisallowAllMoves) - return false; - - if (m == null) - return false; - - for (int i = 0; i < iSteps; i++) - { - // Get the current distance - int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(m); - - if (iCurrDist < iWantDistMin || iCurrDist > iWantDistMax) - { - bool needCloser = (iCurrDist > iWantDistMax); - bool needFurther = !needCloser; - - if (needCloser && m_Path != null && m_Path.Goal == m) - { - if (m_Path.Follow(bRun, 1)) - m_Path = null; - } - else - { - Direction dirTo; - - if (iCurrDist > iWantDistMax) - dirTo = m_Mobile.GetDirectionTo(m); - else - dirTo = m.GetDirectionTo(m_Mobile); - - // Add the run flag - if (bRun) - dirTo = dirTo | Direction.Running; - - if (!DoMove(dirTo, true) && needCloser) - { - m_Path = new PathFollower(m_Mobile, m); - m_Path.Mover = DoMoveImpl; - - if (m_Path.Follow(bRun, 1)) - m_Path = null; - } - else - { - m_Path = null; - } - } - } - else - { - return true; - } - } - - // Get the current distance - int iNewDist = (int)m_Mobile.GetDistanceToSqrt(m); - - if (iNewDist >= iWantDistMin && iNewDist <= iWantDistMax) - return true; - - return false; - } - - /* - * Here we check to acquire a target from our surrounding - * - * iRange : The range - * acqType : A type of acquire we want (closest, strongest, etc) - * bPlayerOnly : Don't bother with other creatures or NPCs, want a player - * bFacFriend : Check people in my faction - * bFacFoe : Check people in other factions - * - */ - public virtual bool AcquireFocusMob(int iRange, FightMode acqType, bool bPlayerOnly, bool bFacFriend, bool bFacFoe) - { - if (m_Mobile.Deleted) - return false; - - if (m_Mobile.BardProvoked) - { - if (m_Mobile.BardTarget == null || m_Mobile.BardTarget.Deleted) - { - m_Mobile.FocusMob = null; - return false; - } - - m_Mobile.FocusMob = m_Mobile.BardTarget; - return (m_Mobile.FocusMob != null); - } - - if (m_Mobile.Controlled) - { - if (m_Mobile.ControlTarget == null || m_Mobile.ControlTarget.Deleted || m_Mobile.ControlTarget.Hidden || !m_Mobile.ControlTarget.Alive || m_Mobile.ControlTarget.IsDeadBondedPet || !m_Mobile.InRange(m_Mobile.ControlTarget, m_Mobile.RangePerception * 2)) - { - if (m_Mobile.ControlTarget != null && m_Mobile.ControlTarget != m_Mobile.ControlMaster) - m_Mobile.ControlTarget = null; - - m_Mobile.FocusMob = null; - return false; - } - - m_Mobile.FocusMob = m_Mobile.ControlTarget; - return (m_Mobile.FocusMob != null); - } - - if (m_Mobile.ConstantFocus != null) - { - m_Mobile.DebugSay("Acquired my constant focus"); - m_Mobile.FocusMob = m_Mobile.ConstantFocus; - return true; - } - - if (acqType == FightMode.None) - { - m_Mobile.FocusMob = null; - return false; - } - - if (acqType == FightMode.Aggressor && m_Mobile.Aggressors.Count == 0 && m_Mobile.Aggressed.Count == 0 && m_Mobile.FactionAllegiance == null && m_Mobile.EthicAllegiance == null) - { - m_Mobile.FocusMob = null; - return false; - } - - if (Core.TickCount - m_Mobile.NextReacquireTime < 0) - { - m_Mobile.FocusMob = null; - return false; - } - - m_Mobile.NextReacquireTime = Core.TickCount + (int)m_Mobile.ReacquireDelay.TotalMilliseconds; - - m_Mobile.DebugSay("Acquiring..."); - - Map map = m_Mobile.Map; - - if (map != null) - { - Mobile newFocusMob = null; - double val = double.MinValue; - - IPooledEnumerable eable = map.GetMobilesInRange(m_Mobile.Location, iRange); - - foreach (Mobile m in eable) - { - if (m.Deleted || m.Blessed) - continue; - - // Let's not target ourselves... - if (m == m_Mobile || m is BaseFamiliar) - continue; - - // Dead targets are invalid. - if (!m.Alive || m.IsDeadBondedPet) - continue; - - // Staff members cannot be targeted. - if (m.AccessLevel > AccessLevel.Player) - continue; - - // Does it have to be a player? - if (bPlayerOnly && !m.Player) - continue; - - // Can't acquire a target we can't see. - if (!m_Mobile.CanSee(m)) - continue; - - BaseCreature bc = m as BaseCreature; - PlayerMobile pm = m as PlayerMobile; - - if (Core.AOS && bc?.Summoned == true && bc?.Controlled != true) - continue; - - if (m_Mobile.Summoned && m_Mobile.SummonMaster != null) - { - // If this is a summon, it can't target its controller. - if (m == m_Mobile.SummonMaster) - continue; - - // It also must abide by harmful spell rules. - if (!SpellHelper.ValidIndirectTarget(m_Mobile.SummonMaster, m)) - continue; - - // Animated creatures cannot attack players directly. - if (pm != null && m_Mobile.IsAnimatedDead) - continue; - } - - // If we only want faction friends, make sure it's one. - if (bFacFriend && !m_Mobile.IsFriend(m)) - continue; - - //Ignore anyone under EtherealVoyage - if (TransformationSpellHelper.UnderTransformation(m, typeof(EtherealVoyageSpell))) - continue; - - // Ignore players with activated honor - if (pm?.HonorActive == true && m_Mobile.Combatant != m) - continue; - - if (acqType == FightMode.Aggressor || acqType == FightMode.Evil) - { - bool bValid = IsHostile(m); - - if (!bValid) - bValid = (m_Mobile.GetFactionAllegiance(m) == BaseCreature.Allegiance.Enemy || m_Mobile.GetEthicAllegiance(m) == BaseCreature.Allegiance.Enemy); - - if (acqType == FightMode.Evil && !bValid) - { - if (bc?.Controlled == true && bc?.ControlMaster != null) - bValid = bc.ControlMaster.Karma < 0; - else - bValid = (m.Karma < 0); - } - - if (!bValid) - continue; - } - else - { - // Same goes for faction enemies. - if (bFacFoe && !m_Mobile.IsEnemy(m)) - continue; - - // If it's an enemy factioned mobile, make sure we can be harmful to it. - if (bFacFoe && !bFacFriend && !m_Mobile.CanBeHarmful(m, false)) - continue; - } - - var theirVal = m_Mobile.GetFightModeRanking(m, acqType, bPlayerOnly); - - if (theirVal > val && m_Mobile.InLOS(m)) - { - newFocusMob = m; - val = theirVal; - } - } - - eable.Free(); - - m_Mobile.FocusMob = newFocusMob; - } - - return (m_Mobile.FocusMob != null); - } - - private bool IsHostile(Mobile from) - { - int count = Math.Max(m_Mobile.Aggressors.Count, m_Mobile.Aggressed.Count); - - if (m_Mobile.Combatant == from || from.Combatant == m_Mobile) - { - return true; - } - - if (count > 0) - { - for (int a = 0; a < count; ++a) - { - if (a < m_Mobile.Aggressed.Count && m_Mobile.Aggressed[a].Attacker == from) - { - return true; - } - - if (a < m_Mobile.Aggressors.Count && m_Mobile.Aggressors[a].Defender == from) - { - return true; - } - } - } - - return false; - } - - - public virtual void DetectHidden() - { - if (m_Mobile.Deleted || m_Mobile.Map == null) - return; - - m_Mobile.DebugSay("Checking for hidden players"); - - double srcSkill = m_Mobile.Skills[SkillName.DetectHidden].Value; - - if (srcSkill <= 0) - return; - - IPooledEnumerable eable = m_Mobile.GetMobilesInRange(m_Mobile.RangePerception); - foreach (Mobile trg in eable) - { - if (trg != m_Mobile && trg.Player && trg.Alive && trg.Hidden && trg.AccessLevel == AccessLevel.Player && m_Mobile.InLOS(trg)) - { - m_Mobile.DebugSay("Trying to detect {0}", trg.Name); - - double trgHiding = trg.Skills[SkillName.Hiding].Value / 2.9; - double trgStealth = trg.Skills[SkillName.Stealth].Value / 1.8; - - double chance = srcSkill / 1.2 - Math.Min(trgHiding, trgStealth); - - if (chance < srcSkill / 10) - chance = srcSkill / 10; - - chance /= 100; - - if (chance > Utility.RandomDouble()) - { - trg.RevealingAction(); - trg.SendLocalizedMessage(500814); // You have been revealed! - } - } - } - eable.Free(); - } - - public virtual void Deactivate() - { - if (m_Mobile.PlayerRangeSensitive) - { - m_Timer.Stop(); - - if (m_Mobile.Spawner is SpawnEntry se && se.ReturnOnDeactivate && !m_Mobile.Controlled) - { - if (se.HomeLocation == Point3D.Zero) - { - if (!m_Mobile.Region.AcceptsSpawnsFrom(se.Region)) - { - Timer.DelayCall(TimeSpan.Zero, ReturnToHome); - } - } - else if (!m_Mobile.InRange(se.HomeLocation, se.HomeRange)) - { - Timer.DelayCall(TimeSpan.Zero, ReturnToHome); - } - } - } - } - - private void ReturnToHome() - { - if (m_Mobile.Spawner is SpawnEntry se) - { - Point3D loc = se.RandomSpawnLocation(16, !m_Mobile.CantWalk, m_Mobile.CanSwim); - - if (loc != Point3D.Zero) - { - m_Mobile.MoveToWorld(loc, se.Region.Map); - } - } - } - - public virtual void Activate() - { - if (!m_Timer.Running) - { - m_Timer.Delay = TimeSpan.Zero; - m_Timer.Start(); - } - } - - /* - * The mobile changed it speed, we must adjust the timer - */ - public virtual void OnCurrentSpeedChanged() - { - m_Timer.Stop(); - m_Timer.Delay = TimeSpan.FromSeconds(Utility.RandomDouble()); - m_Timer.Interval = TimeSpan.FromSeconds(Math.Max(0.0, m_Mobile.CurrentSpeed)); - m_Timer.Start(); - } - - private long m_NextDetectHidden; - - public virtual bool CanDetectHidden => m_Mobile.Skills[SkillName.DetectHidden].Value > 0; - - /* - * The Timer object - */ - private class AITimer : Timer - { - private BaseAI m_Owner; - - public AITimer(BaseAI owner) - : base(TimeSpan.FromSeconds(Utility.RandomDouble()), TimeSpan.FromSeconds(Math.Max(0.0, owner.m_Mobile.CurrentSpeed))) - { - m_Owner = owner; - - m_Owner.m_NextDetectHidden = Core.TickCount; - - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - if (m_Owner.m_Mobile.Deleted) - { - Stop(); - return; - } - if (m_Owner.m_Mobile.Map == null || m_Owner.m_Mobile.Map == Map.Internal) - { - m_Owner.Deactivate(); - return; - } - if (m_Owner.m_Mobile.PlayerRangeSensitive)//have to check this in the timer.... - { - Sector sect = m_Owner.m_Mobile.Map.GetSector(m_Owner.m_Mobile); - if (!sect.Active) - { - m_Owner.Deactivate(); - return; - } - } - - m_Owner.m_Mobile.OnThink(); - - if (m_Owner.m_Mobile.Deleted) - { - Stop(); - return; - } - if (m_Owner.m_Mobile.Map == null || m_Owner.m_Mobile.Map == Map.Internal) - { - m_Owner.Deactivate(); - return; - } - - if (m_Owner.m_Mobile.BardPacified) - { - m_Owner.DoBardPacified(); - } - else if (m_Owner.m_Mobile.BardProvoked) - { - m_Owner.DoBardProvoked(); - } - else - { - if (!m_Owner.m_Mobile.Controlled) - { - if (!m_Owner.Think()) - { - Stop(); - return; - } - } - else - { - if (!m_Owner.Obey()) - { - Stop(); - return; - } - } - } - - if (m_Owner.CanDetectHidden && Core.TickCount - m_Owner.m_NextDetectHidden >= 0) - { - m_Owner.DetectHidden(); - - // Not exactly OSI style, approximation. - int delay = (15000 / m_Owner.m_Mobile.Int); - - if (delay > 60) - delay = 60; - - int min = delay * (9 / 10); // 13s at 1000 int, 33s at 400 int, 54s at <250 int - int max = delay * (10 / 9); // 16s at 1000 int, 41s at 400 int, 66s at <250 int - - m_Owner.m_NextDetectHidden = Core.TickCount + (int)TimeSpan.FromSeconds(Utility.RandomMinMax(min, max)).TotalMilliseconds; - } - } - } - } -} + if (acqType == FightMode.Evil && !bValid) + { + if (bc?.Controlled == true && bc?.ControlMaster != null) + bValid = bc.ControlMaster.Karma < 0; + else + bValid = m.Karma < 0; + } + if (!bValid) + continue; + } + else + { + // Same goes for faction enemies. + if (bFacFoe && !m_Mobile.IsEnemy(m)) + continue; + + // If it's an enemy factioned mobile, make sure we can be harmful to it. + if (bFacFoe && !bFacFriend && !m_Mobile.CanBeHarmful(m, false)) + continue; + } + + double theirVal = m_Mobile.GetFightModeRanking(m, acqType, bPlayerOnly); + + if (theirVal > val && m_Mobile.InLOS(m)) + { + newFocusMob = m; + val = theirVal; + } + } + + eable.Free(); + + m_Mobile.FocusMob = newFocusMob; + } + + return m_Mobile.FocusMob != null; + } + + private bool IsHostile(Mobile from) + { + int count = Math.Max(m_Mobile.Aggressors.Count, m_Mobile.Aggressed.Count); + + if (m_Mobile.Combatant == from || from.Combatant == m_Mobile) return true; + + if (count > 0) + for (int a = 0; a < count; ++a) + { + if (a < m_Mobile.Aggressed.Count && m_Mobile.Aggressed[a].Attacker == from) return true; + + if (a < m_Mobile.Aggressors.Count && m_Mobile.Aggressors[a].Defender == from) return true; + } + + return false; + } + + + public virtual void DetectHidden() + { + if (m_Mobile.Deleted || m_Mobile.Map == null) + return; + + m_Mobile.DebugSay("Checking for hidden players"); + + double srcSkill = m_Mobile.Skills[SkillName.DetectHidden].Value; + + if (srcSkill <= 0) + return; + + IPooledEnumerable eable = m_Mobile.GetMobilesInRange(m_Mobile.RangePerception); + foreach (Mobile trg in eable) + if (trg != m_Mobile && trg.Player && trg.Alive && trg.Hidden && trg.AccessLevel == AccessLevel.Player && + m_Mobile.InLOS(trg)) + { + m_Mobile.DebugSay("Trying to detect {0}", trg.Name); + + double trgHiding = trg.Skills[SkillName.Hiding].Value / 2.9; + double trgStealth = trg.Skills[SkillName.Stealth].Value / 1.8; + + double chance = srcSkill / 1.2 - Math.Min(trgHiding, trgStealth); + + if (chance < srcSkill / 10) + chance = srcSkill / 10; + + chance /= 100; + + if (chance > Utility.RandomDouble()) + { + trg.RevealingAction(); + trg.SendLocalizedMessage(500814); // You have been revealed! + } + } + + eable.Free(); + } + + public virtual void Deactivate() + { + if (m_Mobile.PlayerRangeSensitive) + { + m_Timer.Stop(); + + if (m_Mobile.Spawner is SpawnEntry se && se.ReturnOnDeactivate && !m_Mobile.Controlled) + { + if (se.HomeLocation == Point3D.Zero) + { + if (!m_Mobile.Region.AcceptsSpawnsFrom(se.Region)) Timer.DelayCall(TimeSpan.Zero, ReturnToHome); + } + else if (!m_Mobile.InRange(se.HomeLocation, se.HomeRange)) + { + Timer.DelayCall(TimeSpan.Zero, ReturnToHome); + } + } + } + } + + private void ReturnToHome() + { + if (m_Mobile.Spawner is SpawnEntry se) + { + Point3D loc = se.RandomSpawnLocation(16, !m_Mobile.CantWalk, m_Mobile.CanSwim); + + if (loc != Point3D.Zero) m_Mobile.MoveToWorld(loc, se.Region.Map); + } + } + + public virtual void Activate() + { + if (!m_Timer.Running) + { + m_Timer.Delay = TimeSpan.Zero; + m_Timer.Start(); + } + } + + /* + * The mobile changed it speed, we must adjust the timer + */ + public virtual void OnCurrentSpeedChanged() + { + m_Timer.Stop(); + m_Timer.Delay = TimeSpan.FromSeconds(Utility.RandomDouble()); + m_Timer.Interval = TimeSpan.FromSeconds(Math.Max(0.0, m_Mobile.CurrentSpeed)); + m_Timer.Start(); + } + + private class InternalEntry : ContextMenuEntry + { + private BaseAI m_AI; + private Mobile m_From; + private BaseCreature m_Mobile; + private OrderType m_Order; + + public InternalEntry(Mobile from, int number, int range, BaseCreature mobile, BaseAI ai, OrderType order) + : base(number, range) + { + m_From = from; + m_Mobile = mobile; + m_AI = ai; + m_Order = order; + + if (mobile.IsDeadPet && (order == OrderType.Guard || order == OrderType.Attack || + order == OrderType.Transfer || order == OrderType.Drop)) + Enabled = false; + } + + public override void OnClick() + { + if (!m_Mobile.Deleted && m_Mobile.Controlled && m_From.CheckAlive()) + { + if (m_Mobile.IsDeadPet && (m_Order == OrderType.Guard || m_Order == OrderType.Attack || + m_Order == OrderType.Transfer || m_Order == OrderType.Drop)) + return; + + bool isOwner = m_From == m_Mobile.ControlMaster; + bool isFriend = !isOwner && m_Mobile.IsPetFriend(m_From); + + if (!isOwner && !isFriend) + return; + if (isFriend && m_Order != OrderType.Follow && m_Order != OrderType.Stay && m_Order != OrderType.Stop) + return; + + switch (m_Order) + { + case OrderType.Follow: + case OrderType.Attack: + case OrderType.Transfer: + case OrderType.Friend: + case OrderType.Unfriend: + { + if (m_Order == OrderType.Transfer && m_From.HasTrade) + m_From.SendLocalizedMessage(1010507); // You cannot transfer a pet with a trade pending + else if (m_Order == OrderType.Friend && m_From.HasTrade) + m_From.SendLocalizedMessage(1070947); // You cannot friend a pet with a trade pending + else + m_AI.BeginPickTarget(m_From, m_Order); + + break; + } + case OrderType.Release: + { + if (m_Mobile.Summoned) + goto default; + m_From.SendGump(new ConfirmReleaseGump(m_From, m_Mobile)); + + break; + } + default: + { + if (m_Mobile.CheckControlChance(m_From)) + m_Mobile.ControlOrder = m_Order; + + break; + } + } + } + } + } + + private class TransferItem : Item + { + private BaseCreature m_Creature; + + public TransferItem(BaseCreature creature) + : base(ShrinkTable.Lookup(creature)) + { + m_Creature = creature; + + Movable = false; + + if (!Core.AOS) + Name = creature.Name; + else if (ItemID == ShrinkTable.DefaultItemID || + creature.GetType().IsDefined(typeof(FriendlyNameAttribute), false) || creature is Reptalon) + Name = FriendlyNameAttribute.GetFriendlyNameFor(creature.GetType()).ToString(); + + //(As Per OSI)No name. Normally, set by the ItemID of the Shrink Item unless we either explicitly set it with an Attribute, or, no lookup found + + Hue = creature.Hue & 0x0FFF; + } + + public TransferItem(Serial serial) + : base(serial) + { + } + + public static bool IsInCombat(BaseCreature creature) + { + return creature != null && (creature.Aggressors.Count > 0 || creature.Aggressed.Count > 0); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Delete(); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(1041603); // This item represents a pet currently in consideration for trade + list.Add(1041601, m_Creature.Name); // Pet Name: ~1_val~ + + if (m_Creature.ControlMaster != null) + list.Add(1041602, m_Creature.ControlMaster.Name); // Owner: ~1_val~ + } + + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (!base.AllowSecureTrade(from, to, newOwner, accepted)) + return false; + + if (Deleted || m_Creature == null || m_Creature.Deleted || m_Creature.ControlMaster != from || + !from.CheckAlive() || !to.CheckAlive()) + return false; + + if (from.Map != m_Creature.Map || !from.InRange(m_Creature, 14)) + return false; + + bool youngFrom = from is PlayerMobile mobile && mobile.Young; + bool youngTo = to is PlayerMobile playerMobile && playerMobile.Young; + + if (accepted && youngFrom && !youngTo) + { + from.SendLocalizedMessage(502051); // As a young player, you may not transfer pets to older players. + } + else if (accepted && !youngFrom && youngTo) + { + from.SendLocalizedMessage(502052); // As an older player, you may not transfer pets to young players. + } + else if (accepted && !m_Creature.CanBeControlledBy(to)) + { + string args = $"{to.Name}\t{from.Name}\t "; + + from.SendLocalizedMessage(1043248, + args); // The pet refuses to be transferred because it will not obey ~1_NAME~.~3_BLANK~ + to.SendLocalizedMessage(1043249, + args); // The pet will not accept you as a master because it does not trust you.~3_BLANK~ + + return false; + } + else if (accepted && !m_Creature.CanBeControlledBy(from)) + { + string args = $"{to.Name}\t{from.Name}\t "; + + from.SendLocalizedMessage(1043250, + args); // The pet refuses to be transferred because it will not obey you sufficiently.~3_BLANK~ + to.SendLocalizedMessage(1043251, + args); // The pet will not accept you as a master because it does not trust ~2_NAME~.~3_BLANK~ + } + else if (accepted && to.Followers + m_Creature.ControlSlots > to.FollowersMax) + { + to.SendLocalizedMessage(1049607); // You have too many followers to control that creature. + + return false; + } + else if (accepted && IsInCombat(m_Creature)) + { + from.SendMessage("You may not transfer a pet that has recently been in combat."); + to.SendMessage("The pet may not be transfered to you because it has recently been in combat."); + + return false; + } + + return true; + } + + public override void OnSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (Deleted) + return; + + Delete(); + + if (m_Creature == null || m_Creature.Deleted || m_Creature.ControlMaster != from || !from.CheckAlive() || + !to.CheckAlive()) + return; + + if (from.Map != m_Creature.Map || !from.InRange(m_Creature, 14)) + return; + + if (accepted) + if (m_Creature.SetControlMaster(to)) + { + if (m_Creature.Summoned) + m_Creature.SummonMaster = to; + + m_Creature.ControlTarget = to; + m_Creature.ControlOrder = OrderType.Follow; + + m_Creature.BondingBegin = DateTime.MinValue; + m_Creature.OwnerAbandonTime = DateTime.MinValue; + m_Creature.IsBonded = false; + + m_Creature.PlaySound(m_Creature.GetIdleSound()); + + string args = $"{from.Name}\t{m_Creature.Name}\t{to.Name}"; + + from.SendLocalizedMessage(1043253, args); // You have transferred your pet to ~3_GETTER~. + to.SendLocalizedMessage(1043252, + args); // ~1_NAME~ has transferred the allegiance of ~2_PET_NAME~ to you. + } + } + } + + /* + * The Timer object + */ + private class AITimer : Timer + { + private BaseAI m_Owner; + + public AITimer(BaseAI owner) + : base(TimeSpan.FromSeconds(Utility.RandomDouble()), + TimeSpan.FromSeconds(Math.Max(0.0, owner.m_Mobile.CurrentSpeed))) + { + m_Owner = owner; + + m_Owner.m_NextDetectHidden = Core.TickCount; + + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + if (m_Owner.m_Mobile.Deleted) + { + Stop(); + return; + } + + if (m_Owner.m_Mobile.Map == null || m_Owner.m_Mobile.Map == Map.Internal) + { + m_Owner.Deactivate(); + return; + } + + if (m_Owner.m_Mobile.PlayerRangeSensitive) //have to check this in the timer.... + { + Sector sect = m_Owner.m_Mobile.Map.GetSector(m_Owner.m_Mobile); + if (!sect.Active) + { + m_Owner.Deactivate(); + return; + } + } + + m_Owner.m_Mobile.OnThink(); + + if (m_Owner.m_Mobile.Deleted) + { + Stop(); + return; + } + + if (m_Owner.m_Mobile.Map == null || m_Owner.m_Mobile.Map == Map.Internal) + { + m_Owner.Deactivate(); + return; + } + + if (m_Owner.m_Mobile.BardPacified) + { + m_Owner.DoBardPacified(); + } + else if (m_Owner.m_Mobile.BardProvoked) + { + m_Owner.DoBardProvoked(); + } + else + { + if (!m_Owner.m_Mobile.Controlled) + { + if (!m_Owner.Think()) + { + Stop(); + return; + } + } + else + { + if (!m_Owner.Obey()) + { + Stop(); + return; + } + } + } + + if (m_Owner.CanDetectHidden && Core.TickCount - m_Owner.m_NextDetectHidden >= 0) + { + m_Owner.DetectHidden(); + + // Not exactly OSI style, approximation. + int delay = 15000 / m_Owner.m_Mobile.Int; + + if (delay > 60) + delay = 60; + + int min = delay * (9 / 10); // 13s at 1000 int, 33s at 400 int, 54s at <250 int + int max = delay * (10 / 9); // 16s at 1000 int, 41s at 400 int, 66s at <250 int + + m_Owner.m_NextDetectHidden = Core.TickCount + + (int)TimeSpan.FromSeconds(Utility.RandomMinMax(min, max)).TotalMilliseconds; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/AI/BerserkAI.cs b/Scripts/Mobiles/AI/BerserkAI.cs index 8e554ae9f..f81a704a5 100644 --- a/Scripts/Mobiles/AI/BerserkAI.cs +++ b/Scripts/Mobiles/AI/BerserkAI.cs @@ -1,82 +1,82 @@ namespace Server.Mobiles { - public class BerserkAI : BaseAI - { - public BerserkAI(BaseCreature m) : base (m) - { - } + public class BerserkAI : BaseAI + { + public BerserkAI(BaseCreature m) : base(m) + { + } - public override bool DoActionWander() - { - m_Mobile.DebugSay( "I have No Combatant" ); + public override bool DoActionWander() + { + m_Mobile.DebugSay("I have No Combatant"); - if ( AcquireFocusMob( m_Mobile.RangePerception, FightMode.Closest, false, true, true) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected " + m_Mobile.FocusMob.Name + " and I will attack" ); + if (AcquireFocusMob(m_Mobile.RangePerception, FightMode.Closest, false, true, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected " + m_Mobile.FocusMob.Name + " and I will attack"); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionWander(); - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionWander(); + } - return true; - } + return true; + } - public override bool DoActionCombat() - { - if ( m_Mobile.Combatant == null || m_Mobile.Combatant.Deleted ) - { - m_Mobile.DebugSay("My combatant is deleted"); - Action = ActionType.Guard; - return true; - } + public override bool DoActionCombat() + { + if (m_Mobile.Combatant == null || m_Mobile.Combatant.Deleted) + { + m_Mobile.DebugSay("My combatant is deleted"); + Action = ActionType.Guard; + return true; + } - if ( WalkMobileRange( m_Mobile.Combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight ) ) - { - // Be sure to face the combatant - m_Mobile.Direction = m_Mobile.GetDirectionTo( m_Mobile.Combatant.Location ); - } - else - { - if ( m_Mobile.Combatant != null ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay("I am still not in range of " + m_Mobile.Combatant.Name); + if (WalkMobileRange(m_Mobile.Combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight)) + { + // Be sure to face the combatant + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_Mobile.Combatant.Location); + } + else + { + if (m_Mobile.Combatant != null) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I am still not in range of " + m_Mobile.Combatant.Name); - if ( (int) m_Mobile.GetDistanceToSqrt( m_Mobile.Combatant ) > m_Mobile.RangePerception + 1 ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have lost " + m_Mobile.Combatant.Name ); + if ((int)m_Mobile.GetDistanceToSqrt(m_Mobile.Combatant) > m_Mobile.RangePerception + 1) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have lost " + m_Mobile.Combatant.Name); - Action = ActionType.Guard; - return true; - } - } - } + Action = ActionType.Guard; + return true; + } + } + } - return true; - } + return true; + } - public override bool DoActionGuard() - { - if ( AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, true, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + public override bool DoActionGuard() + { + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, true, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionGuard(); - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionGuard(); + } - return true; - } - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/AI/HealerAI.cs b/Scripts/Mobiles/AI/HealerAI.cs index 2dfa49f73..e05638eb9 100644 --- a/Scripts/Mobiles/AI/HealerAI.cs +++ b/Scripts/Mobiles/AI/HealerAI.cs @@ -1,172 +1,154 @@ -using Server.Targeting; using Server.Spells.First; -using Server.Spells.Second; using Server.Spells.Fourth; +using Server.Spells.Second; +using Server.Targeting; namespace Server.Mobiles { - public class HealerAI : BaseAI - { - private static NeedDelegate m_Cure = NeedCure; - private static NeedDelegate m_GHeal = NeedGHeal; - private static NeedDelegate m_LHeal = NeedLHeal; - private static NeedDelegate[] m_ACure = { m_Cure }; - private static NeedDelegate[] m_AGHeal = { m_GHeal }; - private static NeedDelegate[] m_ALHeal = { m_LHeal }; - private static NeedDelegate[] m_All = { m_Cure, m_GHeal, m_LHeal }; + public class HealerAI : BaseAI + { + private static NeedDelegate m_Cure = NeedCure; + private static NeedDelegate m_GHeal = NeedGHeal; + private static NeedDelegate m_LHeal = NeedLHeal; + private static NeedDelegate[] m_ACure = { m_Cure }; + private static NeedDelegate[] m_AGHeal = { m_GHeal }; + private static NeedDelegate[] m_ALHeal = { m_LHeal }; + private static NeedDelegate[] m_All = { m_Cure, m_GHeal, m_LHeal }; - public HealerAI( BaseCreature m ) : base( m ) - { - } + public HealerAI(BaseCreature m) : base(m) + { + } - public override bool Think() - { - if ( m_Mobile.Deleted ) - return false; + public override bool Think() + { + if (m_Mobile.Deleted) + return false; - Target targ = m_Mobile.Target; + Target targ = m_Mobile.Target; - if ( targ != null ) - { - if ( targ is CureSpell.InternalTarget ) - { - ProcessTarget( targ, m_ACure ); - } - else if ( targ is GreaterHealSpell.InternalTarget ) - { - ProcessTarget( targ, m_AGHeal ); - } - else if ( targ is HealSpell.InternalTarget ) - { - ProcessTarget( targ, m_ALHeal ); - } - else - { - targ.Cancel( m_Mobile, TargetCancelType.Canceled ); - } - } - else - { - Mobile toHelp = Find( m_All ); + if (targ != null) + { + if (targ is CureSpell.InternalTarget) + ProcessTarget(targ, m_ACure); + else if (targ is GreaterHealSpell.InternalTarget) + ProcessTarget(targ, m_AGHeal); + else if (targ is HealSpell.InternalTarget) + ProcessTarget(targ, m_ALHeal); + else + targ.Cancel(m_Mobile, TargetCancelType.Canceled); + } + else + { + Mobile toHelp = Find(m_All); - if ( toHelp != null ) - { - if ( NeedCure( toHelp ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} needs a cure", toHelp.Name ); + if (toHelp != null) + { + if (NeedCure(toHelp)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} needs a cure", toHelp.Name); - if ( !(new CureSpell( m_Mobile, null )).Cast() ) - new CureSpell( m_Mobile, null ).Cast(); - } - else if ( NeedGHeal( toHelp ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} needs a greater heal", toHelp.Name ); + if (!new CureSpell(m_Mobile, null).Cast()) + new CureSpell(m_Mobile, null).Cast(); + } + else if (NeedGHeal(toHelp)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} needs a greater heal", toHelp.Name); - if ( !(new GreaterHealSpell( m_Mobile, null )).Cast() ) - new HealSpell( m_Mobile, null ).Cast(); - } - else if ( NeedLHeal( toHelp ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} needs a lesser heal", toHelp.Name ); + if (!new GreaterHealSpell(m_Mobile, null).Cast()) + new HealSpell(m_Mobile, null).Cast(); + } + else if (NeedLHeal(toHelp)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} needs a lesser heal", toHelp.Name); - new HealSpell( m_Mobile, null ).Cast(); - } - } - else - { - if ( AcquireFocusMob( m_Mobile.RangePerception, FightMode.Weakest, false, true, false ) ) - { - WalkMobileRange( m_Mobile.FocusMob, 1, false, 4, 7 ); - } - else - { - WalkRandomInHome( 3, 2, 1 ); - } - } - } + new HealSpell(m_Mobile, null).Cast(); + } + } + else + { + if (AcquireFocusMob(m_Mobile.RangePerception, FightMode.Weakest, false, true, false)) + WalkMobileRange(m_Mobile.FocusMob, 1, false, 4, 7); + else + WalkRandomInHome(3, 2, 1); + } + } - return true; - } + return true; + } - private delegate bool NeedDelegate( Mobile m ); + private void ProcessTarget(Target targ, NeedDelegate[] func) + { + Mobile toHelp = Find(func); - private void ProcessTarget( Target targ, NeedDelegate[] func ) - { - Mobile toHelp = Find( func ); + if (toHelp != null) + { + if (targ.Range != -1 && !m_Mobile.InRange(toHelp, targ.Range)) + DoMove(m_Mobile.GetDirectionTo(toHelp) | Direction.Running); + else + targ.Invoke(m_Mobile, toHelp); + } + else + { + targ.Cancel(m_Mobile, TargetCancelType.Canceled); + } + } - if ( toHelp != null ) - { - if ( targ.Range != -1 && !m_Mobile.InRange( toHelp, targ.Range ) ) - { - DoMove( m_Mobile.GetDirectionTo( toHelp ) | Direction.Running ); - } - else - { - targ.Invoke( m_Mobile, toHelp ); - } - } - else - { - targ.Cancel( m_Mobile, TargetCancelType.Canceled ); - } - } + private Mobile Find(params NeedDelegate[] funcs) + { + if (m_Mobile.Deleted) + return null; - private Mobile Find( params NeedDelegate[] funcs ) - { - if ( m_Mobile.Deleted ) - return null; + Map map = m_Mobile.Map; - Map map = m_Mobile.Map; + if (map != null) + { + double prio = 0.0; + Mobile found = null; - if ( map != null ) - { - double prio = 0.0; - Mobile found = null; + foreach (Mobile m in m_Mobile.GetMobilesInRange(m_Mobile.RangePerception)) + { + if (!m_Mobile.CanSee(m) || !(m is BaseCreature) || ((BaseCreature)m).Team != m_Mobile.Team) + continue; - foreach ( Mobile m in m_Mobile.GetMobilesInRange( m_Mobile.RangePerception ) ) - { - if ( !m_Mobile.CanSee( m ) || !(m is BaseCreature) || ((BaseCreature)m).Team != m_Mobile.Team ) - continue; + for (int i = 0; i < funcs.Length; ++i) + if (funcs[i](m)) + { + double val = -m_Mobile.GetDistanceToSqrt(m); - for ( int i = 0; i < funcs.Length; ++i ) - { - if ( funcs[i]( m ) ) - { - double val = -m_Mobile.GetDistanceToSqrt( m ); + if (found == null || val > prio) + { + prio = val; + found = m; + } - if ( found == null || val > prio ) - { - prio = val; - found = m; - } + break; + } + } - break; - } - } - } + return found; + } - return found; - } + return null; + } - return null; - } + private static bool NeedCure(Mobile m) + { + return m.Poisoned; + } - private static bool NeedCure( Mobile m ) - { - return m.Poisoned; - } + private static bool NeedGHeal(Mobile m) + { + return m.Hits < m.HitsMax - 40; + } - private static bool NeedGHeal( Mobile m ) - { - return m.Hits < m.HitsMax - 40; - } + private static bool NeedLHeal(Mobile m) + { + return m.Hits < m.HitsMax - 10; + } - private static bool NeedLHeal( Mobile m ) - { - return m.Hits < m.HitsMax - 10; - } - } + private delegate bool NeedDelegate(Mobile m); + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/MageAI.cs b/Scripts/Mobiles/AI/MageAI.cs index 94a6c00ed..1e8633c0b 100644 --- a/Scripts/Mobiles/AI/MageAI.cs +++ b/Scripts/Mobiles/AI/MageAI.cs @@ -13,1075 +13,1096 @@ using Server.Targeting; namespace Server.Mobiles { - public class MageAI : BaseAI - { - private long m_NextCastTime; - private long m_NextHealTime; - - public MageAI( BaseCreature m ) - : base( m ) - { - } - - public override bool Think() - { - if ( m_Mobile.Deleted ) - return false; - - if ( ProcessTarget() ) - return true; - return base.Think(); - } - - public virtual bool SmartAI => ( m_Mobile is BaseVendor || m_Mobile is BaseEscortable || m_Mobile is Changeling ); - - public virtual bool IsNecromancer => ( Core.AOS && m_Mobile.Skills[ SkillName.Necromancy ].Value > 50 ); - - private const double HealChance = 0.10; // 10% chance to heal at gm magery - private const double TeleportChance = 0.05; // 5% chance to teleport at gm magery - private const double DispelChance = 0.75; // 75% chance to dispel at gm magery - - public virtual double ScaleBySkill( double v, SkillName skill ) - { - return v * m_Mobile.Skills[ skill ].Value / 100; - } - - public override bool DoActionWander() - { - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "I am going to attack {0}", m_Mobile.FocusMob.Name ); - - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - m_NextCastTime = Core.TickCount; - } - else if ( SmartAI && m_Mobile.Mana < m_Mobile.ManaMax && !m_Mobile.Meditating ) - { - m_Mobile.DebugSay( "I am going to meditate" ); - - m_Mobile.UseSkill( SkillName.Meditation ); - } - else - { - m_Mobile.DebugSay( "I am wandering" ); - - m_Mobile.Warmode = false; - - base.DoActionWander(); - - if ( Utility.RandomDouble() < 0.05 ) - { - Spell spell = CheckCastHealingSpell(); - - spell?.Cast(); - } - } - - return true; - } - - private Spell CheckCastHealingSpell() - { - // If I'm poisoned, always attempt to cure. - if ( m_Mobile.Poisoned ) - return new CureSpell( m_Mobile, null ); - - // Summoned creatures never heal themselves. - if ( m_Mobile.Summoned ) - return null; - - if ( m_Mobile.Controlled ) - { - if (Core.TickCount - m_NextHealTime < 0) - return null; - } - - if ( !SmartAI ) - { - if ( ScaleBySkill( HealChance, SkillName.Magery ) < Utility.RandomDouble() ) - return null; - } - else - { - if ( Utility.Random( 0, 4 + ( m_Mobile.Hits == 0 ? m_Mobile.HitsMax : ( m_Mobile.HitsMax / m_Mobile.Hits ) ) ) < 3 ) - return null; - } - - Spell spell = null; - - if ( m_Mobile.Hits < ( m_Mobile.HitsMax - 50 ) ) - { - if ( UseNecromancy() ) - { - m_Mobile.UseSkill( SkillName.SpiritSpeak ); - } - else - { - spell = new GreaterHealSpell( m_Mobile, null ); - - if ( spell == null ) - spell = new HealSpell( m_Mobile, null ); - } - } - else if ( m_Mobile.Hits < ( m_Mobile.HitsMax - 10 ) ) - { - spell = new HealSpell( m_Mobile, null ); - } - - double delay; - - if ( m_Mobile.Int >= 500 ) - delay = Utility.RandomMinMax( 7, 10 ); - else - delay = Math.Sqrt( 600 - m_Mobile.Int ); - - m_NextHealTime = Core.TickCount + (int)TimeSpan.FromSeconds(delay).TotalMilliseconds; - - return spell; - } - - public void RunTo( Mobile m ) - { - if ( !SmartAI ) - { - if ( !MoveTo( m, true, m_Mobile.RangeFight ) ) - OnFailedMove(); - - return; - } - - if ( m.Paralyzed || m.Frozen ) - { - if ( m_Mobile.InRange( m, 1 ) ) - RunFrom( m ); - else if ( !m_Mobile.InRange( m, m_Mobile.RangeFight > 2 ? m_Mobile.RangeFight : 2 ) && !MoveTo( m, true, 1 ) ) - OnFailedMove(); - } - else - { - if ( !m_Mobile.InRange( m, m_Mobile.RangeFight ) ) - { - if ( !MoveTo( m, true, 1 ) ) - OnFailedMove(); - } - else if ( m_Mobile.InRange( m, m_Mobile.RangeFight - 1 ) ) - { - RunFrom( m ); - } - } - } - - public void RunFrom( Mobile m ) - { - Run( ( m_Mobile.GetDirectionTo( m ) - 4 ) & Direction.Mask ); - } - - public void OnFailedMove() - { - if ( !m_Mobile.DisallowAllMoves && ( SmartAI ? Utility.Random( 4 ) == 0 : ScaleBySkill( TeleportChance, SkillName.Magery ) > Utility.RandomDouble() ) ) - { - m_Mobile.Target?.Cancel( m_Mobile, TargetCancelType.Canceled ); - - new TeleportSpell( m_Mobile, null ).Cast(); - - m_Mobile.DebugSay( "I am stuck, I'm going to try teleporting away" ); - } - else if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "My move is blocked, so I am going to attack {0}", m_Mobile.FocusMob.Name ); - - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - m_Mobile.DebugSay( "I am stuck" ); - } - } - - public void Run( Direction d ) - { - if ( ( m_Mobile.Spell != null && m_Mobile.Spell.IsCasting ) || m_Mobile.Paralyzed || m_Mobile.Frozen || m_Mobile.DisallowAllMoves ) - return; - - m_Mobile.Direction = d | Direction.Running; - - if ( !DoMove( m_Mobile.Direction, true ) ) - OnFailedMove(); - } - - public virtual bool UseNecromancy() - { - if ( IsNecromancer ) - return ( Utility.Random( m_Mobile.Skills[ SkillName.Magery ].BaseFixedPoint + m_Mobile.Skills[ SkillName.Necromancy ].BaseFixedPoint ) >= m_Mobile.Skills[ SkillName.Magery ].BaseFixedPoint ); - - return false; - } - - public virtual Spell GetRandomDamageSpell() - { - return UseNecromancy() ? GetRandomDamageSpellNecro() : GetRandomDamageSpellMage(); - } - - public virtual Spell GetRandomDamageSpellNecro() - { - int bound = ( m_Mobile.Skills[ SkillName.Necromancy ].Value >= 100 ) ? 5 : 3; - - switch( Utility.Random( bound ) ) - { - case 0: m_Mobile.DebugSay( "Pain Spike" ); return new PainSpikeSpell( m_Mobile, null ); - case 1: m_Mobile.DebugSay( "Poison Strike" ); return new PoisonStrikeSpell( m_Mobile, null ); - case 2: m_Mobile.DebugSay( "Strangle" ); return new StrangleSpell( m_Mobile, null ); - case 3: m_Mobile.DebugSay( "Wither" ); return new WitherSpell( m_Mobile, null ); - default: m_Mobile.DebugSay( "Vengeful Spirit" ); return new VengefulSpiritSpell( m_Mobile, null ); - } - } - - public virtual Spell GetRandomDamageSpellMage() - { - int maxCircle = (int)( ( m_Mobile.Skills[ SkillName.Magery ].Value + 20.0 ) / ( 100.0 / 7.0 ) ); - - if ( maxCircle < 1 ) - maxCircle = 1; - else if ( maxCircle > 8 ) - maxCircle = 8; - - switch( Utility.Random( maxCircle * 2 ) ) - { - case 0: - case 1: return new MagicArrowSpell( m_Mobile, null ); - case 2: - case 3: return new HarmSpell( m_Mobile, null ); - case 4: - case 5: return new FireballSpell( m_Mobile, null ); - case 6: - case 7: return new LightningSpell( m_Mobile, null ); - case 8: - case 9: return new MindBlastSpell( m_Mobile, null ); - case 10: return new EnergyBoltSpell( m_Mobile, null ); - case 11: return new ExplosionSpell( m_Mobile, null ); - default: return new FlameStrikeSpell( m_Mobile, null ); - } - } - - public virtual Spell GetRandomCurseSpell() - { - return UseNecromancy() ? GetRandomCurseSpellNecro() : GetRandomCurseSpellMage(); - } - - public virtual Spell GetRandomCurseSpellNecro() - { - switch( Utility.Random( 4 ) ) - { - case 0: m_Mobile.DebugSay( "Blood Oath" ); return new BloodOathSpell( m_Mobile, null ); - case 1: m_Mobile.DebugSay( "Corpse Skin" ); return new CorpseSkinSpell( m_Mobile, null ); - case 2: m_Mobile.DebugSay( "Evil Omen" ); return new EvilOmenSpell( m_Mobile, null ); - default: m_Mobile.DebugSay( "Mind Rot" ); return new MindRotSpell( m_Mobile, null ); - } - } - - public virtual Spell GetRandomCurseSpellMage() - { - if ( m_Mobile.Skills[ SkillName.Magery ].Value >= 40.0 && Utility.Random( 4 ) == 0 ) - return new CurseSpell( m_Mobile, null ); - - switch( Utility.Random( 3 ) ) - { - case 0: return new WeakenSpell( m_Mobile, null ); - case 1: return new ClumsySpell( m_Mobile, null ); - default: return new FeeblemindSpell( m_Mobile, null ); - } - } - - public virtual Spell GetRandomManaDrainSpell() - { - if ( m_Mobile.Skills[ SkillName.Magery ].Value >= 80.0 && Utility.RandomBool() ) - return new ManaVampireSpell( m_Mobile, null ); - - return new ManaDrainSpell( m_Mobile, null ); - } - - public virtual Spell DoDispel( Mobile toDispel ) - { - if ( !SmartAI ) - { - if ( ScaleBySkill( DispelChance, SkillName.Magery ) > Utility.RandomDouble() ) - return new DispelSpell( m_Mobile, null ); - - return ChooseSpell( toDispel ); - } - - Spell spell = CheckCastHealingSpell(); - - if ( spell == null ) - { - if ( !m_Mobile.DisallowAllMoves && Utility.Random( (int)m_Mobile.GetDistanceToSqrt( toDispel ) ) == 0 ) - spell = new TeleportSpell( m_Mobile, null ); - else if ( Utility.Random( 3 ) == 0 && !m_Mobile.InRange( toDispel, 3 ) && !toDispel.Paralyzed && !toDispel.Frozen ) - spell = new ParalyzeSpell( m_Mobile, null ); - else - spell = new DispelSpell( m_Mobile, null ); - } - - return spell; - } - - public virtual Spell ChooseSpell( Mobile c ) - { - Spell spell = null; - - if ( !SmartAI ) - { - spell = CheckCastHealingSpell(); - - if ( spell != null ) - return spell; - - if ( IsNecromancer ) - { - double psDamage = ( ( m_Mobile.Skills[ SkillName.SpiritSpeak ].Value - c.Skills[ SkillName.MagicResist ].Value ) / 10 ) + ( c.Player ? 18 : 30 ); - - if ( psDamage > c.Hits ) - return new PainSpikeSpell( m_Mobile, null ); - } - - switch (Utility.Random(16)) - { - case 0: - case 1: // Poison them - { - if (c.Poisoned) - goto default; - - m_Mobile.DebugSay( "Attempting to poison" ); - - spell = new PoisonSpell(m_Mobile, null); - break; - } - case 2: // Bless ourselves - { - m_Mobile.DebugSay( "Blessing myself" ); - - spell = new BlessSpell(m_Mobile, null); - break; - } - case 3: - case 4: // Curse them - { - m_Mobile.DebugSay( "Attempting to curse" ); - - spell = GetRandomCurseSpell(); - break; - } - case 5: // Paralyze them - { - if (c.Paralyzed || m_Mobile.Skills[ SkillName.Magery ].Value <= 50.0) - goto default; - - m_Mobile.DebugSay( "Attempting to paralyze" ); - - spell = new ParalyzeSpell(m_Mobile, null); - break; - } - case 6: // Drain mana - { - m_Mobile.DebugSay( "Attempting to drain mana" ); - - spell = GetRandomManaDrainSpell(); - break; - } - case 7: // Invis ourselves - { - if (Utility.RandomBool()) - goto default; - - m_Mobile.DebugSay( "Attempting to invis myself" ); - - spell = new InvisibilitySpell(m_Mobile, null); - break; - } - default: // Damage them - { - m_Mobile.DebugSay( "Just doing damage" ); - - spell = GetRandomDamageSpell(); - break; - } - } - - return spell; - } - - spell = CheckCastHealingSpell(); - - if ( spell != null ) - return spell; - - switch( Utility.Random( 3 ) ) - { - case 0: // Poison them - { - if ( c.Poisoned ) - goto case 1; - - spell = new PoisonSpell( m_Mobile, null ); - break; - } - case 1: // Deal some damage - { - spell = GetRandomDamageSpell(); - - break; - } - default: // Set up a combo - { - if ( m_Mobile.Mana > 15 && m_Mobile.Mana < 40 ) - { - if ( c.Paralyzed && !c.Poisoned && !m_Mobile.Meditating ) - { - m_Mobile.DebugSay( "I am going to meditate" ); - - m_Mobile.UseSkill( SkillName.Meditation ); - } - else if ( !c.Poisoned ) - { - spell = new ParalyzeSpell( m_Mobile, null ); - } - } - else if ( m_Mobile.Mana > 60 ) - { - if ( Utility.RandomBool() && !c.Paralyzed && !c.Frozen && !c.Poisoned ) - { - m_Combo = 0; - spell = new ParalyzeSpell( m_Mobile, null ); - } - else - { - m_Combo = 1; - spell = new ExplosionSpell( m_Mobile, null ); - } - } - - break; - } - } - - return spell; - } - - protected int m_Combo = -1; - - public virtual Spell DoCombo( Mobile c ) - { - Spell spell = null; - - if ( m_Combo == 0 ) - { - spell = new ExplosionSpell( m_Mobile, null ); - ++m_Combo; // Move to next spell - } - else if ( m_Combo == 1 ) - { - spell = new WeakenSpell( m_Mobile, null ); - ++m_Combo; // Move to next spell - } - else if ( m_Combo == 2 ) - { - if ( !c.Poisoned ) - spell = new PoisonSpell( m_Mobile, null ); - else if ( IsNecromancer ) - spell = new StrangleSpell( m_Mobile, null ); - - ++m_Combo; // Move to next spell - } - - if ( m_Combo == 3 && spell == null ) - { - switch( Utility.Random( IsNecromancer ? 4 : 3 ) ) - { - case 0: - { - if ( c.Int < c.Dex ) - spell = new FeeblemindSpell( m_Mobile, null ); - else - spell = new ClumsySpell( m_Mobile, null ); - - ++m_Combo; // Move to next spell - - break; - } - case 1: - { - spell = new EnergyBoltSpell( m_Mobile, null ); - m_Combo = -1; // Reset combo state - break; - } - case 2: - { - spell = new FlameStrikeSpell( m_Mobile, null ); - m_Combo = -1; // Reset combo state - break; - } - default: - { - spell = new PainSpikeSpell( m_Mobile, null ); - m_Combo = -1; // Reset combo state - break; - } - } - } - else if ( m_Combo == 4 && spell == null ) - { - spell = new MindBlastSpell( m_Mobile, null ); - m_Combo = -1; - } - - return spell; - } - - private TimeSpan GetDelay( Spell spell ) - { - if ( SmartAI || ( spell is DispelSpell ) ) - { - return TimeSpan.FromSeconds( m_Mobile.ActiveSpeed ); - } - - double del = ScaleBySkill( 3.0, SkillName.Magery ); - double min = 6.0 - ( del * 0.75 ); - double max = 6.0 - ( del * 1.25 ); - - return TimeSpan.FromSeconds( min + ( ( max - min ) * Utility.RandomDouble() ) ); - } - - private Mobile m_LastTarget; - private Point3D m_LastTargetLoc; - - public override bool DoActionCombat() - { - Mobile c = m_Mobile.Combatant; - m_Mobile.Warmode = true; - - if ( c == null || c.Deleted || !c.Alive || c.IsDeadBondedPet || !m_Mobile.CanSee( c ) || !m_Mobile.CanBeHarmful( c, false ) || c.Map != m_Mobile.Map ) - { - // Our combatant is deleted, dead, hidden, or we cannot hurt them - // Try to find another combatant - - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "Something happened to my combatant, so I am going to fight {0}", m_Mobile.FocusMob.Name ); - - m_Mobile.Combatant = c = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - else - { - m_Mobile.DebugSay( "Something happened to my combatant, and nothing is around. I am on guard." ); - Action = ActionType.Guard; - return true; - } - } - - if ( !m_Mobile.InLOS( c ) ) - { - m_Mobile.DebugSay( "I can't see my target" ); - - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "I will switch to {0}", m_Mobile.FocusMob.Name ); - m_Mobile.Combatant = c = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - } - - if ( !Core.AOS && SmartAI && !m_Mobile.StunReady && m_Mobile.Skills[ SkillName.Wrestling ].Value >= 80.0 && m_Mobile.Skills[ SkillName.Anatomy ].Value >= 80.0 ) - EventSink.InvokeStunRequest( new StunRequestEventArgs( m_Mobile ) ); - - if ( !m_Mobile.InRange( c, m_Mobile.RangePerception ) ) - { - // They are somewhat far away, can we find something else? - - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.Combatant = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - else if ( !m_Mobile.InRange( c, m_Mobile.RangePerception * 3 ) ) - { - m_Mobile.Combatant = null; - } - - c = m_Mobile.Combatant; - - if ( c == null ) - { - m_Mobile.DebugSay( "My combatant has fled, so I am on guard" ); - Action = ActionType.Guard; - - return true; - } - } - - if ( !m_Mobile.Controlled && !m_Mobile.Summoned && m_Mobile.CanFlee ) - { - if ( m_Mobile.Hits < m_Mobile.HitsMax * 20 / 100 ) - { - // We are low on health, should we flee? - - bool flee = false; - - if ( m_Mobile.Hits < c.Hits ) - { - // We are more hurt than them - - int diff = c.Hits - m_Mobile.Hits; - - flee = ( Utility.Random( 0, 100 ) > ( 10 + diff ) ); // (10 + diff)% chance to flee - } - else - { - flee = Utility.Random( 0, 100 ) > 10; // 10% chance to flee - } - - if ( flee ) - { - m_Mobile.DebugSay( "I am going to flee from {0}", c.Name ); - - Action = ActionType.Flee; - return true; - } - } - } - - if (m_Mobile.Spell == null && Core.TickCount - m_NextCastTime >= 0 && m_Mobile.InRange(c, Core.ML ? 10 : 12)) - { - // We are ready to cast a spell - - Spell spell = null; - Mobile toDispel = FindDispelTarget( true ); - - if ( m_Mobile.Poisoned ) // Top cast priority is cure - { - m_Mobile.DebugSay( "I am going to cure myself" ); - - spell = new CureSpell( m_Mobile, null ); - } - else if ( toDispel != null ) // Something dispellable is attacking us - { - m_Mobile.DebugSay( "I am going to dispel {0}", toDispel ); - - spell = DoDispel( toDispel ); - } - else if ( SmartAI && m_Combo != -1 ) // We are doing a spell combo - { - spell = DoCombo( c ); - } - else if ( SmartAI && ( c.Spell is HealSpell || c.Spell is GreaterHealSpell ) && !c.Poisoned ) // They have a heal spell out - { - spell = new PoisonSpell( m_Mobile, null ); - } - else - { - spell = ChooseSpell( c ); - } - - // Now we have a spell picked - // Move first before casting - - if ( SmartAI && toDispel != null ) - { - if ( m_Mobile.InRange( toDispel, 10 ) ) - RunFrom( toDispel ); - else if ( !m_Mobile.InRange( toDispel, Core.ML ? 10 : 12 ) ) - RunTo( toDispel ); - } - else - { - RunTo( c ); - } - - spell?.Cast(); - - m_NextCastTime = Core.TickCount + (int)GetDelay(spell).TotalMilliseconds; - } - else if ( m_Mobile.Spell == null || !m_Mobile.Spell.IsCasting ) - { - RunTo( c ); - } - - m_LastTarget = c; - m_LastTargetLoc = c.Location; - - return true; - } - - private LandTarget m_RevealTarget; - - public override bool DoActionGuard() - { - if ( m_LastTarget != null && m_LastTarget.Hidden ) - { - Map map = m_Mobile.Map; - - if ( map == null || !m_Mobile.InRange( m_LastTargetLoc, Core.ML ? 10 : 12 ) ) - { - m_LastTarget = null; - } - else if ( m_Mobile.Spell == null && Core.TickCount - m_NextCastTime >= 0 ) - { - m_Mobile.DebugSay( "I am going to reveal my last target" ); - - m_RevealTarget = new LandTarget( m_LastTargetLoc, map ); - Spell spell = new RevealSpell( m_Mobile, null ); - - if ( spell.Cast() ) - m_LastTarget = null; // only do it once - - m_NextCastTime = Core.TickCount + (int)GetDelay(spell).TotalMilliseconds; - } - } - - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "I am going to attack {0}", m_Mobile.FocusMob.Name ); - - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - if ( !m_Mobile.Controlled ) - { - ProcessTarget(); - - Spell spell = CheckCastHealingSpell(); - - spell?.Cast(); - } - - base.DoActionGuard(); - } - - return true; - } - - public override bool DoActionFlee() - { - Mobile c = m_Mobile.Combatant; - - if ( ( m_Mobile.Mana > 20 || m_Mobile.Mana == m_Mobile.ManaMax ) && m_Mobile.Hits > ( m_Mobile.HitsMax / 2 ) ) - { - m_Mobile.DebugSay( "I am stronger now, my guard is up" ); - Action = ActionType.Guard; - } - else if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "I am scared of {0}", m_Mobile.FocusMob.Name ); - - RunFrom( m_Mobile.FocusMob ); - m_Mobile.FocusMob = null; - - if ( m_Mobile.Poisoned && Utility.Random( 0, 5 ) == 0 ) - new CureSpell( m_Mobile, null ).Cast(); - } - else - { - m_Mobile.DebugSay( "Area seems clear, but my guard is up" ); - - Action = ActionType.Guard; - m_Mobile.Warmode = true; - } - - return true; - } - - public Mobile FindDispelTarget( bool activeOnly ) - { - if ( m_Mobile.Deleted || m_Mobile.Int < 95 || CanDispel( m_Mobile ) || m_Mobile.AutoDispel ) - return null; - - if ( activeOnly ) - { - List aggressed = m_Mobile.Aggressed; - List aggressors = m_Mobile.Aggressors; - - Mobile active = null; - double activePrio = 0.0; - - Mobile comb = m_Mobile.Combatant; - - if ( comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && m_Mobile.InRange( comb, Core.ML ? 10 : 12 ) && CanDispel( comb ) ) - { - active = comb; - activePrio = m_Mobile.GetDistanceToSqrt( comb ); - - if ( activePrio <= 2 ) - return active; - } - - for( int i = 0; i < aggressed.Count; ++i ) - { - AggressorInfo info = aggressed[ i ]; - Mobile m = info.Defender; - - if ( m != comb && m.Combatant == m_Mobile && m_Mobile.InRange( m, Core.ML ? 10 : 12 ) && CanDispel( m ) ) - { - double prio = m_Mobile.GetDistanceToSqrt( m ); - - if ( active == null || prio < activePrio ) - { - active = m; - activePrio = prio; - - if ( activePrio <= 2 ) - return active; - } - } - } - - for( int i = 0; i < aggressors.Count; ++i ) - { - AggressorInfo info = aggressors[ i ]; - Mobile m = info.Attacker; - - if ( m != comb && m.Combatant == m_Mobile && m_Mobile.InRange( m, Core.ML ? 10 : 12 ) && CanDispel( m ) ) - { - double prio = m_Mobile.GetDistanceToSqrt( m ); - - if ( active == null || prio < activePrio ) - { - active = m; - activePrio = prio; - - if ( activePrio <= 2 ) - return active; - } - } - } - - return active; - } - - Map map = m_Mobile.Map; - - if ( map != null ) - { - Mobile active = null, inactive = null; - double actPrio = 0.0, inactPrio = 0.0; - - Mobile comb = m_Mobile.Combatant; - - if ( comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && CanDispel( comb ) ) - { - active = inactive = comb; - actPrio = inactPrio = m_Mobile.GetDistanceToSqrt( comb ); - } - - foreach( Mobile m in m_Mobile.GetMobilesInRange( Core.ML ? 10 : 12 ) ) - { - if ( m != m_Mobile && CanDispel( m ) ) - { - double prio = m_Mobile.GetDistanceToSqrt( m ); - - if ( !activeOnly && ( inactive == null || prio < inactPrio ) ) - { - inactive = m; - inactPrio = prio; - } - - if ( ( m_Mobile.Combatant == m || m.Combatant == m_Mobile ) && ( active == null || prio < actPrio ) ) - { - active = m; - actPrio = prio; - } - } - } - - return active ?? inactive; - } - - return null; - } - - public bool CanDispel( Mobile m ) - { - return ( m is BaseCreature creature && creature.Summoned && m_Mobile.CanBeHarmful( creature, false ) && !creature.IsAnimatedDead ); - } - - private static int[] m_Offsets = { - -1, -1, - -1, 0, - -1, 1, - 0, -1, - 0, 1, - 1, -1, - 1, 0, - 1, 1, - - -2, -2, - -2, -1, - -2, 0, - -2, 1, - -2, 2, - -1, -2, - -1, 2, - 0, -2, - 0, 2, - 1, -2, - 1, 2, - 2, -2, - 2, -1, - 2, 0, - 2, 1, - 2, 2 - }; - - private bool ProcessTarget() - { - Target targ = m_Mobile.Target; - - if ( targ == null ) - return false; - - bool isReveal = ( targ is RevealSpell.InternalTarget ); - bool isDispel = ( targ is DispelSpell.InternalTarget ); - bool isParalyze = ( targ is ParalyzeSpell.InternalTarget ); - bool isTeleport = ( targ is TeleportSpell.InternalTarget ); - bool isInvisible = ( targ is InvisibilitySpell.InternalTarget ); - bool teleportAway = false; - - Mobile toTarget; - - if ( isInvisible ) - { - toTarget = m_Mobile; - } - else if ( isDispel ) - { - toTarget = FindDispelTarget( false ); - - if ( !SmartAI && toTarget != null ) - RunTo( toTarget ); - else if ( toTarget != null && m_Mobile.InRange( toTarget, 10 ) ) - RunFrom( toTarget ); - } - else if ( SmartAI && ( isParalyze || isTeleport ) ) - { - toTarget = FindDispelTarget( true ); - - if ( toTarget == null ) - { - toTarget = m_Mobile.Combatant; - - if ( toTarget != null ) - RunTo( toTarget ); - } - else if ( m_Mobile.InRange( toTarget, 10 ) ) - { - RunFrom( toTarget ); - teleportAway = true; - } - else - { - teleportAway = true; - } - } - else - { - toTarget = m_Mobile.Combatant; - - if ( toTarget != null ) - RunTo( toTarget ); - } - - if ( ( targ.Flags & TargetFlags.Harmful ) != 0 && toTarget != null ) - { - if ( ( targ.Range == -1 || m_Mobile.InRange( toTarget, targ.Range ) ) && m_Mobile.CanSee( toTarget ) && m_Mobile.InLOS( toTarget ) ) - { - targ.Invoke( m_Mobile, toTarget ); - } - else if ( isDispel ) - { - targ.Cancel( m_Mobile, TargetCancelType.Canceled ); - } - } - else if ( ( targ.Flags & TargetFlags.Beneficial ) != 0 ) - { - targ.Invoke( m_Mobile, m_Mobile ); - } - else if ( isReveal && m_RevealTarget != null ) - { - targ.Invoke( m_Mobile, m_RevealTarget ); - } - else if ( isTeleport && toTarget != null ) - { - Map map = m_Mobile.Map; - - if ( map == null ) - { - targ.Cancel( m_Mobile, TargetCancelType.Canceled ); - return true; - } - - int px, py; - - if ( teleportAway ) - { - int rx = m_Mobile.X - toTarget.X; - int ry = m_Mobile.Y - toTarget.Y; - - double d = m_Mobile.GetDistanceToSqrt( toTarget ); - - px = toTarget.X + (int)( rx * ( 10 / d ) ); - py = toTarget.Y + (int)( ry * ( 10 / d ) ); - } - else - { - px = toTarget.X; - py = toTarget.Y; - } - - for( int i = 0; i < m_Offsets.Length; i += 2 ) - { - int x = m_Offsets[ i ], y = m_Offsets[ i + 1 ]; - - Point3D p = new Point3D( px + x, py + y, 0 ); - - LandTarget lt = new LandTarget( p, map ); - - if ( ( targ.Range == -1 || m_Mobile.InRange( p, targ.Range ) ) && m_Mobile.InLOS( lt ) && map.CanSpawnMobile( px + x, py + y, lt.Z ) && !SpellHelper.CheckMulti( p, map ) ) - { - targ.Invoke( m_Mobile, lt ); - return true; - } - } - - int teleRange = targ.Range; - - if ( teleRange < 0 ) - teleRange = Core.ML ? 11 : 12; - - for( int i = 0; i < 10; ++i ) - { - Point3D randomPoint = new Point3D( m_Mobile.X - teleRange + Utility.Random( teleRange * 2 + 1 ), m_Mobile.Y - teleRange + Utility.Random( teleRange * 2 + 1 ), 0 ); - - LandTarget lt = new LandTarget( randomPoint, map ); - - if ( m_Mobile.InLOS( lt ) && map.CanSpawnMobile( lt.X, lt.Y, lt.Z ) && !SpellHelper.CheckMulti( randomPoint, map ) ) - { - targ.Invoke( m_Mobile, new LandTarget( randomPoint, map ) ); - return true; - } - } - - targ.Cancel( m_Mobile, TargetCancelType.Canceled ); - } - else - { - targ.Cancel( m_Mobile, TargetCancelType.Canceled ); - } - - return true; - } - } -} + public class MageAI : BaseAI + { + private const double HealChance = 0.10; // 10% chance to heal at gm magery + private const double TeleportChance = 0.05; // 5% chance to teleport at gm magery + private const double DispelChance = 0.75; // 75% chance to dispel at gm magery + + private static int[] m_Offsets = + { + -1, -1, + -1, 0, + -1, 1, + 0, -1, + 0, 1, + 1, -1, + 1, 0, + 1, 1, + + -2, -2, + -2, -1, + -2, 0, + -2, 1, + -2, 2, + -1, -2, + -1, 2, + 0, -2, + 0, 2, + 1, -2, + 1, 2, + 2, -2, + 2, -1, + 2, 0, + 2, 1, + 2, 2 + }; + + protected int m_Combo = -1; + + private Mobile m_LastTarget; + private Point3D m_LastTargetLoc; + private long m_NextCastTime; + private long m_NextHealTime; + + private LandTarget m_RevealTarget; + + public MageAI(BaseCreature m) + : base(m) + { + } + + public virtual bool SmartAI => m_Mobile is BaseVendor || m_Mobile is BaseEscortable || m_Mobile is Changeling; + + public virtual bool IsNecromancer => Core.AOS && m_Mobile.Skills[SkillName.Necromancy].Value > 50; + + public override bool Think() + { + if (m_Mobile.Deleted) + return false; + + if (ProcessTarget()) + return true; + return base.Think(); + } + + public virtual double ScaleBySkill(double v, SkillName skill) + { + return v * m_Mobile.Skills[skill].Value / 100; + } + + public override bool DoActionWander() + { + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("I am going to attack {0}", m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + m_NextCastTime = Core.TickCount; + } + else if (SmartAI && m_Mobile.Mana < m_Mobile.ManaMax && !m_Mobile.Meditating) + { + m_Mobile.DebugSay("I am going to meditate"); + + m_Mobile.UseSkill(SkillName.Meditation); + } + else + { + m_Mobile.DebugSay("I am wandering"); + + m_Mobile.Warmode = false; + + base.DoActionWander(); + + if (Utility.RandomDouble() < 0.05) + { + Spell spell = CheckCastHealingSpell(); + + spell?.Cast(); + } + } + + return true; + } + + private Spell CheckCastHealingSpell() + { + // If I'm poisoned, always attempt to cure. + if (m_Mobile.Poisoned) + return new CureSpell(m_Mobile, null); + + // Summoned creatures never heal themselves. + if (m_Mobile.Summoned) + return null; + + if (m_Mobile.Controlled) + if (Core.TickCount - m_NextHealTime < 0) + return null; + + if (!SmartAI) + { + if (ScaleBySkill(HealChance, SkillName.Magery) < Utility.RandomDouble()) + return null; + } + else + { + if (Utility.Random(0, 4 + (m_Mobile.Hits == 0 ? m_Mobile.HitsMax : m_Mobile.HitsMax / m_Mobile.Hits)) < 3) + return null; + } + + Spell spell = null; + + if (m_Mobile.Hits < m_Mobile.HitsMax - 50) + { + if (UseNecromancy()) + { + m_Mobile.UseSkill(SkillName.SpiritSpeak); + } + else + { + spell = new GreaterHealSpell(m_Mobile, null); + + if (spell == null) + spell = new HealSpell(m_Mobile, null); + } + } + else if (m_Mobile.Hits < m_Mobile.HitsMax - 10) + { + spell = new HealSpell(m_Mobile, null); + } + + double delay; + + if (m_Mobile.Int >= 500) + delay = Utility.RandomMinMax(7, 10); + else + delay = Math.Sqrt(600 - m_Mobile.Int); + + m_NextHealTime = Core.TickCount + (int)TimeSpan.FromSeconds(delay).TotalMilliseconds; + + return spell; + } + + public void RunTo(Mobile m) + { + if (!SmartAI) + { + if (!MoveTo(m, true, m_Mobile.RangeFight)) + OnFailedMove(); + + return; + } + + if (m.Paralyzed || m.Frozen) + { + if (m_Mobile.InRange(m, 1)) + RunFrom(m); + else if (!m_Mobile.InRange(m, m_Mobile.RangeFight > 2 ? m_Mobile.RangeFight : 2) && !MoveTo(m, true, 1)) + OnFailedMove(); + } + else + { + if (!m_Mobile.InRange(m, m_Mobile.RangeFight)) + { + if (!MoveTo(m, true, 1)) + OnFailedMove(); + } + else if (m_Mobile.InRange(m, m_Mobile.RangeFight - 1)) + { + RunFrom(m); + } + } + } + + public void RunFrom(Mobile m) + { + Run((m_Mobile.GetDirectionTo(m) - 4) & Direction.Mask); + } + + public void OnFailedMove() + { + if (!m_Mobile.DisallowAllMoves && (SmartAI + ? Utility.Random(4) == 0 + : ScaleBySkill(TeleportChance, SkillName.Magery) > Utility.RandomDouble())) + { + m_Mobile.Target?.Cancel(m_Mobile, TargetCancelType.Canceled); + + new TeleportSpell(m_Mobile, null).Cast(); + + m_Mobile.DebugSay("I am stuck, I'm going to try teleporting away"); + } + else if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("My move is blocked, so I am going to attack {0}", m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + m_Mobile.DebugSay("I am stuck"); + } + } + + public void Run(Direction d) + { + if (m_Mobile.Spell != null && m_Mobile.Spell.IsCasting || m_Mobile.Paralyzed || m_Mobile.Frozen || + m_Mobile.DisallowAllMoves) + return; + + m_Mobile.Direction = d | Direction.Running; + + if (!DoMove(m_Mobile.Direction, true)) + OnFailedMove(); + } + + public virtual bool UseNecromancy() + { + if (IsNecromancer) + return Utility.Random(m_Mobile.Skills[SkillName.Magery].BaseFixedPoint + + m_Mobile.Skills[SkillName.Necromancy].BaseFixedPoint) >= + m_Mobile.Skills[SkillName.Magery].BaseFixedPoint; + + return false; + } + + public virtual Spell GetRandomDamageSpell() + { + return UseNecromancy() ? GetRandomDamageSpellNecro() : GetRandomDamageSpellMage(); + } + + public virtual Spell GetRandomDamageSpellNecro() + { + int bound = m_Mobile.Skills[SkillName.Necromancy].Value >= 100 ? 5 : 3; + + switch (Utility.Random(bound)) + { + case 0: + m_Mobile.DebugSay("Pain Spike"); + return new PainSpikeSpell(m_Mobile, null); + case 1: + m_Mobile.DebugSay("Poison Strike"); + return new PoisonStrikeSpell(m_Mobile, null); + case 2: + m_Mobile.DebugSay("Strangle"); + return new StrangleSpell(m_Mobile, null); + case 3: + m_Mobile.DebugSay("Wither"); + return new WitherSpell(m_Mobile, null); + default: + m_Mobile.DebugSay("Vengeful Spirit"); + return new VengefulSpiritSpell(m_Mobile, null); + } + } + + public virtual Spell GetRandomDamageSpellMage() + { + int maxCircle = (int)((m_Mobile.Skills[SkillName.Magery].Value + 20.0) / (100.0 / 7.0)); + + if (maxCircle < 1) + maxCircle = 1; + else if (maxCircle > 8) + maxCircle = 8; + + switch (Utility.Random(maxCircle * 2)) + { + case 0: + case 1: return new MagicArrowSpell(m_Mobile, null); + case 2: + case 3: return new HarmSpell(m_Mobile, null); + case 4: + case 5: return new FireballSpell(m_Mobile, null); + case 6: + case 7: return new LightningSpell(m_Mobile, null); + case 8: + case 9: return new MindBlastSpell(m_Mobile, null); + case 10: return new EnergyBoltSpell(m_Mobile, null); + case 11: return new ExplosionSpell(m_Mobile, null); + default: return new FlameStrikeSpell(m_Mobile, null); + } + } + + public virtual Spell GetRandomCurseSpell() + { + return UseNecromancy() ? GetRandomCurseSpellNecro() : GetRandomCurseSpellMage(); + } + + public virtual Spell GetRandomCurseSpellNecro() + { + switch (Utility.Random(4)) + { + case 0: + m_Mobile.DebugSay("Blood Oath"); + return new BloodOathSpell(m_Mobile, null); + case 1: + m_Mobile.DebugSay("Corpse Skin"); + return new CorpseSkinSpell(m_Mobile, null); + case 2: + m_Mobile.DebugSay("Evil Omen"); + return new EvilOmenSpell(m_Mobile, null); + default: + m_Mobile.DebugSay("Mind Rot"); + return new MindRotSpell(m_Mobile, null); + } + } + + public virtual Spell GetRandomCurseSpellMage() + { + if (m_Mobile.Skills[SkillName.Magery].Value >= 40.0 && Utility.Random(4) == 0) + return new CurseSpell(m_Mobile, null); + + switch (Utility.Random(3)) + { + case 0: return new WeakenSpell(m_Mobile, null); + case 1: return new ClumsySpell(m_Mobile, null); + default: return new FeeblemindSpell(m_Mobile, null); + } + } + + public virtual Spell GetRandomManaDrainSpell() + { + if (m_Mobile.Skills[SkillName.Magery].Value >= 80.0 && Utility.RandomBool()) + return new ManaVampireSpell(m_Mobile, null); + + return new ManaDrainSpell(m_Mobile, null); + } + + public virtual Spell DoDispel(Mobile toDispel) + { + if (!SmartAI) + { + if (ScaleBySkill(DispelChance, SkillName.Magery) > Utility.RandomDouble()) + return new DispelSpell(m_Mobile, null); + + return ChooseSpell(toDispel); + } + + Spell spell = CheckCastHealingSpell(); + + if (spell == null) + { + if (!m_Mobile.DisallowAllMoves && Utility.Random((int)m_Mobile.GetDistanceToSqrt(toDispel)) == 0) + spell = new TeleportSpell(m_Mobile, null); + else if (Utility.Random(3) == 0 && !m_Mobile.InRange(toDispel, 3) && !toDispel.Paralyzed && !toDispel.Frozen) + spell = new ParalyzeSpell(m_Mobile, null); + else + spell = new DispelSpell(m_Mobile, null); + } + + return spell; + } + + public virtual Spell ChooseSpell(Mobile c) + { + Spell spell = null; + + if (!SmartAI) + { + spell = CheckCastHealingSpell(); + + if (spell != null) + return spell; + + if (IsNecromancer) + { + double psDamage = + (m_Mobile.Skills[SkillName.SpiritSpeak].Value - c.Skills[SkillName.MagicResist].Value) / 10 + + (c.Player ? 18 : 30); + + if (psDamage > c.Hits) + return new PainSpikeSpell(m_Mobile, null); + } + + switch (Utility.Random(16)) + { + case 0: + case 1: // Poison them + { + if (c.Poisoned) + goto default; + + m_Mobile.DebugSay("Attempting to poison"); + + spell = new PoisonSpell(m_Mobile, null); + break; + } + case 2: // Bless ourselves + { + m_Mobile.DebugSay("Blessing myself"); + + spell = new BlessSpell(m_Mobile, null); + break; + } + case 3: + case 4: // Curse them + { + m_Mobile.DebugSay("Attempting to curse"); + + spell = GetRandomCurseSpell(); + break; + } + case 5: // Paralyze them + { + if (c.Paralyzed || m_Mobile.Skills[SkillName.Magery].Value <= 50.0) + goto default; + + m_Mobile.DebugSay("Attempting to paralyze"); + + spell = new ParalyzeSpell(m_Mobile, null); + break; + } + case 6: // Drain mana + { + m_Mobile.DebugSay("Attempting to drain mana"); + + spell = GetRandomManaDrainSpell(); + break; + } + case 7: // Invis ourselves + { + if (Utility.RandomBool()) + goto default; + + m_Mobile.DebugSay("Attempting to invis myself"); + + spell = new InvisibilitySpell(m_Mobile, null); + break; + } + default: // Damage them + { + m_Mobile.DebugSay("Just doing damage"); + + spell = GetRandomDamageSpell(); + break; + } + } + + return spell; + } + + spell = CheckCastHealingSpell(); + + if (spell != null) + return spell; + + switch (Utility.Random(3)) + { + case 0: // Poison them + { + if (c.Poisoned) + goto case 1; + + spell = new PoisonSpell(m_Mobile, null); + break; + } + case 1: // Deal some damage + { + spell = GetRandomDamageSpell(); + + break; + } + default: // Set up a combo + { + if (m_Mobile.Mana > 15 && m_Mobile.Mana < 40) + { + if (c.Paralyzed && !c.Poisoned && !m_Mobile.Meditating) + { + m_Mobile.DebugSay("I am going to meditate"); + + m_Mobile.UseSkill(SkillName.Meditation); + } + else if (!c.Poisoned) + { + spell = new ParalyzeSpell(m_Mobile, null); + } + } + else if (m_Mobile.Mana > 60) + { + if (Utility.RandomBool() && !c.Paralyzed && !c.Frozen && !c.Poisoned) + { + m_Combo = 0; + spell = new ParalyzeSpell(m_Mobile, null); + } + else + { + m_Combo = 1; + spell = new ExplosionSpell(m_Mobile, null); + } + } + + break; + } + } + + return spell; + } + + public virtual Spell DoCombo(Mobile c) + { + Spell spell = null; + + if (m_Combo == 0) + { + spell = new ExplosionSpell(m_Mobile, null); + ++m_Combo; // Move to next spell + } + else if (m_Combo == 1) + { + spell = new WeakenSpell(m_Mobile, null); + ++m_Combo; // Move to next spell + } + else if (m_Combo == 2) + { + if (!c.Poisoned) + spell = new PoisonSpell(m_Mobile, null); + else if (IsNecromancer) + spell = new StrangleSpell(m_Mobile, null); + + ++m_Combo; // Move to next spell + } + + if (m_Combo == 3 && spell == null) + { + switch (Utility.Random(IsNecromancer ? 4 : 3)) + { + case 0: + { + if (c.Int < c.Dex) + spell = new FeeblemindSpell(m_Mobile, null); + else + spell = new ClumsySpell(m_Mobile, null); + + ++m_Combo; // Move to next spell + + break; + } + case 1: + { + spell = new EnergyBoltSpell(m_Mobile, null); + m_Combo = -1; // Reset combo state + break; + } + case 2: + { + spell = new FlameStrikeSpell(m_Mobile, null); + m_Combo = -1; // Reset combo state + break; + } + default: + { + spell = new PainSpikeSpell(m_Mobile, null); + m_Combo = -1; // Reset combo state + break; + } + } + } + else if (m_Combo == 4 && spell == null) + { + spell = new MindBlastSpell(m_Mobile, null); + m_Combo = -1; + } + + return spell; + } + + private TimeSpan GetDelay(Spell spell) + { + if (SmartAI || spell is DispelSpell) return TimeSpan.FromSeconds(m_Mobile.ActiveSpeed); + + double del = ScaleBySkill(3.0, SkillName.Magery); + double min = 6.0 - del * 0.75; + double max = 6.0 - del * 1.25; + + return TimeSpan.FromSeconds(min + (max - min) * Utility.RandomDouble()); + } + + public override bool DoActionCombat() + { + Mobile c = m_Mobile.Combatant; + m_Mobile.Warmode = true; + + if (c == null || c.Deleted || !c.Alive || c.IsDeadBondedPet || !m_Mobile.CanSee(c) || + !m_Mobile.CanBeHarmful(c, false) || c.Map != m_Mobile.Map) + { + // Our combatant is deleted, dead, hidden, or we cannot hurt them + // Try to find another combatant + + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("Something happened to my combatant, so I am going to fight {0}", + m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = c = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + else + { + m_Mobile.DebugSay("Something happened to my combatant, and nothing is around. I am on guard."); + Action = ActionType.Guard; + return true; + } + } + + if (!m_Mobile.InLOS(c)) + { + m_Mobile.DebugSay("I can't see my target"); + + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("I will switch to {0}", m_Mobile.FocusMob.Name); + m_Mobile.Combatant = c = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + } + + if (!Core.AOS && SmartAI && !m_Mobile.StunReady && m_Mobile.Skills[SkillName.Wrestling].Value >= 80.0 && + m_Mobile.Skills[SkillName.Anatomy].Value >= 80.0) + EventSink.InvokeStunRequest(new StunRequestEventArgs(m_Mobile)); + + if (!m_Mobile.InRange(c, m_Mobile.RangePerception)) + { + // They are somewhat far away, can we find something else? + + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.Combatant = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + else if (!m_Mobile.InRange(c, m_Mobile.RangePerception * 3)) + { + m_Mobile.Combatant = null; + } + + c = m_Mobile.Combatant; + + if (c == null) + { + m_Mobile.DebugSay("My combatant has fled, so I am on guard"); + Action = ActionType.Guard; + + return true; + } + } + + if (!m_Mobile.Controlled && !m_Mobile.Summoned && m_Mobile.CanFlee) + if (m_Mobile.Hits < m_Mobile.HitsMax * 20 / 100) + { + // We are low on health, should we flee? + + bool flee = false; + + if (m_Mobile.Hits < c.Hits) + { + // We are more hurt than them + + int diff = c.Hits - m_Mobile.Hits; + + flee = Utility.Random(0, 100) > 10 + diff; // (10 + diff)% chance to flee + } + else + { + flee = Utility.Random(0, 100) > 10; // 10% chance to flee + } + + if (flee) + { + m_Mobile.DebugSay("I am going to flee from {0}", c.Name); + + Action = ActionType.Flee; + return true; + } + } + + if (m_Mobile.Spell == null && Core.TickCount - m_NextCastTime >= 0 && m_Mobile.InRange(c, Core.ML ? 10 : 12)) + { + // We are ready to cast a spell + + Spell spell = null; + Mobile toDispel = FindDispelTarget(true); + + if (m_Mobile.Poisoned) // Top cast priority is cure + { + m_Mobile.DebugSay("I am going to cure myself"); + + spell = new CureSpell(m_Mobile, null); + } + else if (toDispel != null) // Something dispellable is attacking us + { + m_Mobile.DebugSay("I am going to dispel {0}", toDispel); + + spell = DoDispel(toDispel); + } + else if (SmartAI && m_Combo != -1) // We are doing a spell combo + { + spell = DoCombo(c); + } + else if (SmartAI && (c.Spell is HealSpell || c.Spell is GreaterHealSpell) && !c.Poisoned + ) // They have a heal spell out + { + spell = new PoisonSpell(m_Mobile, null); + } + else + { + spell = ChooseSpell(c); + } + + // Now we have a spell picked + // Move first before casting + + if (SmartAI && toDispel != null) + { + if (m_Mobile.InRange(toDispel, 10)) + RunFrom(toDispel); + else if (!m_Mobile.InRange(toDispel, Core.ML ? 10 : 12)) + RunTo(toDispel); + } + else + { + RunTo(c); + } + + spell?.Cast(); + + m_NextCastTime = Core.TickCount + (int)GetDelay(spell).TotalMilliseconds; + } + else if (m_Mobile.Spell == null || !m_Mobile.Spell.IsCasting) + { + RunTo(c); + } + + m_LastTarget = c; + m_LastTargetLoc = c.Location; + + return true; + } + + public override bool DoActionGuard() + { + if (m_LastTarget != null && m_LastTarget.Hidden) + { + Map map = m_Mobile.Map; + + if (map == null || !m_Mobile.InRange(m_LastTargetLoc, Core.ML ? 10 : 12)) + { + m_LastTarget = null; + } + else if (m_Mobile.Spell == null && Core.TickCount - m_NextCastTime >= 0) + { + m_Mobile.DebugSay("I am going to reveal my last target"); + + m_RevealTarget = new LandTarget(m_LastTargetLoc, map); + Spell spell = new RevealSpell(m_Mobile, null); + + if (spell.Cast()) + m_LastTarget = null; // only do it once + + m_NextCastTime = Core.TickCount + (int)GetDelay(spell).TotalMilliseconds; + } + } + + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("I am going to attack {0}", m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + if (!m_Mobile.Controlled) + { + ProcessTarget(); + + Spell spell = CheckCastHealingSpell(); + + spell?.Cast(); + } + + base.DoActionGuard(); + } + + return true; + } + + public override bool DoActionFlee() + { + Mobile c = m_Mobile.Combatant; + + if ((m_Mobile.Mana > 20 || m_Mobile.Mana == m_Mobile.ManaMax) && m_Mobile.Hits > m_Mobile.HitsMax / 2) + { + m_Mobile.DebugSay("I am stronger now, my guard is up"); + Action = ActionType.Guard; + } + else if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("I am scared of {0}", m_Mobile.FocusMob.Name); + + RunFrom(m_Mobile.FocusMob); + m_Mobile.FocusMob = null; + + if (m_Mobile.Poisoned && Utility.Random(0, 5) == 0) + new CureSpell(m_Mobile, null).Cast(); + } + else + { + m_Mobile.DebugSay("Area seems clear, but my guard is up"); + + Action = ActionType.Guard; + m_Mobile.Warmode = true; + } + + return true; + } + + public Mobile FindDispelTarget(bool activeOnly) + { + if (m_Mobile.Deleted || m_Mobile.Int < 95 || CanDispel(m_Mobile) || m_Mobile.AutoDispel) + return null; + + if (activeOnly) + { + List aggressed = m_Mobile.Aggressed; + List aggressors = m_Mobile.Aggressors; + + Mobile active = null; + double activePrio = 0.0; + + Mobile comb = m_Mobile.Combatant; + + if (comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && + m_Mobile.InRange(comb, Core.ML ? 10 : 12) && CanDispel(comb)) + { + active = comb; + activePrio = m_Mobile.GetDistanceToSqrt(comb); + + if (activePrio <= 2) + return active; + } + + for (int i = 0; i < aggressed.Count; ++i) + { + AggressorInfo info = aggressed[i]; + Mobile m = info.Defender; + + if (m != comb && m.Combatant == m_Mobile && m_Mobile.InRange(m, Core.ML ? 10 : 12) && CanDispel(m)) + { + double prio = m_Mobile.GetDistanceToSqrt(m); + + if (active == null || prio < activePrio) + { + active = m; + activePrio = prio; + + if (activePrio <= 2) + return active; + } + } + } + + for (int i = 0; i < aggressors.Count; ++i) + { + AggressorInfo info = aggressors[i]; + Mobile m = info.Attacker; + + if (m != comb && m.Combatant == m_Mobile && m_Mobile.InRange(m, Core.ML ? 10 : 12) && CanDispel(m)) + { + double prio = m_Mobile.GetDistanceToSqrt(m); + + if (active == null || prio < activePrio) + { + active = m; + activePrio = prio; + + if (activePrio <= 2) + return active; + } + } + } + + return active; + } + + Map map = m_Mobile.Map; + + if (map != null) + { + Mobile active = null, inactive = null; + double actPrio = 0.0, inactPrio = 0.0; + + Mobile comb = m_Mobile.Combatant; + + if (comb != null && !comb.Deleted && comb.Alive && !comb.IsDeadBondedPet && CanDispel(comb)) + { + active = inactive = comb; + actPrio = inactPrio = m_Mobile.GetDistanceToSqrt(comb); + } + + foreach (Mobile m in m_Mobile.GetMobilesInRange(Core.ML ? 10 : 12)) + if (m != m_Mobile && CanDispel(m)) + { + double prio = m_Mobile.GetDistanceToSqrt(m); + + if (!activeOnly && (inactive == null || prio < inactPrio)) + { + inactive = m; + inactPrio = prio; + } + + if ((m_Mobile.Combatant == m || m.Combatant == m_Mobile) && (active == null || prio < actPrio)) + { + active = m; + actPrio = prio; + } + } + + return active ?? inactive; + } + + return null; + } + + public bool CanDispel(Mobile m) + { + return m is BaseCreature creature && creature.Summoned && m_Mobile.CanBeHarmful(creature, false) && + !creature.IsAnimatedDead; + } + + private bool ProcessTarget() + { + Target targ = m_Mobile.Target; + + if (targ == null) + return false; + + bool isReveal = targ is RevealSpell.InternalTarget; + bool isDispel = targ is DispelSpell.InternalTarget; + bool isParalyze = targ is ParalyzeSpell.InternalTarget; + bool isTeleport = targ is TeleportSpell.InternalTarget; + bool isInvisible = targ is InvisibilitySpell.InternalTarget; + bool teleportAway = false; + + Mobile toTarget; + + if (isInvisible) + { + toTarget = m_Mobile; + } + else if (isDispel) + { + toTarget = FindDispelTarget(false); + + if (!SmartAI && toTarget != null) + RunTo(toTarget); + else if (toTarget != null && m_Mobile.InRange(toTarget, 10)) + RunFrom(toTarget); + } + else if (SmartAI && (isParalyze || isTeleport)) + { + toTarget = FindDispelTarget(true); + + if (toTarget == null) + { + toTarget = m_Mobile.Combatant; + + if (toTarget != null) + RunTo(toTarget); + } + else if (m_Mobile.InRange(toTarget, 10)) + { + RunFrom(toTarget); + teleportAway = true; + } + else + { + teleportAway = true; + } + } + else + { + toTarget = m_Mobile.Combatant; + + if (toTarget != null) + RunTo(toTarget); + } + + if ((targ.Flags & TargetFlags.Harmful) != 0 && toTarget != null) + { + if ((targ.Range == -1 || m_Mobile.InRange(toTarget, targ.Range)) && m_Mobile.CanSee(toTarget) && + m_Mobile.InLOS(toTarget)) + targ.Invoke(m_Mobile, toTarget); + else if (isDispel) targ.Cancel(m_Mobile, TargetCancelType.Canceled); + } + else if ((targ.Flags & TargetFlags.Beneficial) != 0) + { + targ.Invoke(m_Mobile, m_Mobile); + } + else if (isReveal && m_RevealTarget != null) + { + targ.Invoke(m_Mobile, m_RevealTarget); + } + else if (isTeleport && toTarget != null) + { + Map map = m_Mobile.Map; + + if (map == null) + { + targ.Cancel(m_Mobile, TargetCancelType.Canceled); + return true; + } + + int px, py; + + if (teleportAway) + { + int rx = m_Mobile.X - toTarget.X; + int ry = m_Mobile.Y - toTarget.Y; + + double d = m_Mobile.GetDistanceToSqrt(toTarget); + + px = toTarget.X + (int)(rx * (10 / d)); + py = toTarget.Y + (int)(ry * (10 / d)); + } + else + { + px = toTarget.X; + py = toTarget.Y; + } + + for (int i = 0; i < m_Offsets.Length; i += 2) + { + int x = m_Offsets[i], y = m_Offsets[i + 1]; + + Point3D p = new Point3D(px + x, py + y, 0); + + LandTarget lt = new LandTarget(p, map); + + if ((targ.Range == -1 || m_Mobile.InRange(p, targ.Range)) && m_Mobile.InLOS(lt) && + map.CanSpawnMobile(px + x, py + y, lt.Z) && !SpellHelper.CheckMulti(p, map)) + { + targ.Invoke(m_Mobile, lt); + return true; + } + } + + int teleRange = targ.Range; + + if (teleRange < 0) + teleRange = Core.ML ? 11 : 12; + + for (int i = 0; i < 10; ++i) + { + Point3D randomPoint = new Point3D(m_Mobile.X - teleRange + Utility.Random(teleRange * 2 + 1), + m_Mobile.Y - teleRange + Utility.Random(teleRange * 2 + 1), 0); + + LandTarget lt = new LandTarget(randomPoint, map); + + if (m_Mobile.InLOS(lt) && map.CanSpawnMobile(lt.X, lt.Y, lt.Z) && + !SpellHelper.CheckMulti(randomPoint, map)) + { + targ.Invoke(m_Mobile, new LandTarget(randomPoint, map)); + return true; + } + } + + targ.Cancel(m_Mobile, TargetCancelType.Canceled); + } + else + { + targ.Cancel(m_Mobile, TargetCancelType.Canceled); + } + + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/AI/MeleeAI.cs b/Scripts/Mobiles/AI/MeleeAI.cs index 3295bd89a..ebf0b3f54 100644 --- a/Scripts/Mobiles/AI/MeleeAI.cs +++ b/Scripts/Mobiles/AI/MeleeAI.cs @@ -1,5 +1,3 @@ - - // // This is a first simple AI // @@ -7,174 +5,173 @@ namespace Server.Mobiles { - public class MeleeAI : BaseAI - { - public MeleeAI(BaseCreature m) : base (m) - { - } + public class MeleeAI : BaseAI + { + public MeleeAI(BaseCreature m) : base(m) + { + } - public override bool DoActionWander() - { - m_Mobile.DebugSay( "I have no combatant" ); + public override bool DoActionWander() + { + m_Mobile.DebugSay("I have no combatant"); - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionWander(); - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionWander(); + } - return true; - } + return true; + } - public override bool DoActionCombat() - { - Mobile combatant = m_Mobile.Combatant; + public override bool DoActionCombat() + { + Mobile combatant = m_Mobile.Combatant; - if ( combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map || !combatant.Alive || combatant.IsDeadBondedPet ) - { - m_Mobile.DebugSay( "My combatant is gone, so my guard is up" ); + if (combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map || !combatant.Alive || + combatant.IsDeadBondedPet) + { + m_Mobile.DebugSay("My combatant is gone, so my guard is up"); - Action = ActionType.Guard; + Action = ActionType.Guard; - return true; - } + return true; + } - if ( !m_Mobile.InRange( combatant, m_Mobile.RangePerception ) ) - { - // They are somewhat far away, can we find something else? + if (!m_Mobile.InRange(combatant, m_Mobile.RangePerception)) + { + // They are somewhat far away, can we find something else? - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.Combatant = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - else if ( !m_Mobile.InRange( combatant, m_Mobile.RangePerception * 3 ) ) - { - m_Mobile.Combatant = null; - } + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.Combatant = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + else if (!m_Mobile.InRange(combatant, m_Mobile.RangePerception * 3)) + { + m_Mobile.Combatant = null; + } - combatant = m_Mobile.Combatant; + combatant = m_Mobile.Combatant; - if ( combatant == null ) - { - m_Mobile.DebugSay( "My combatant has fled, so I am on guard" ); - Action = ActionType.Guard; + if (combatant == null) + { + m_Mobile.DebugSay("My combatant has fled, so I am on guard"); + Action = ActionType.Guard; - return true; - } - } + return true; + } + } - /*if ( !m_Mobile.InLOS( combatant ) ) - { - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.Combatant = combatant = m_Mobile.FocusMob; - m_Mobile.FocusMob = null; - } - }*/ + /*if ( !m_Mobile.InLOS( combatant ) ) + { + if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) + { + m_Mobile.Combatant = combatant = m_Mobile.FocusMob; + m_Mobile.FocusMob = null; + } + }*/ - if ( MoveTo( combatant, true, m_Mobile.RangeFight ) ) - { - m_Mobile.Direction = m_Mobile.GetDirectionTo( combatant ); - } - else if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "My move is blocked, so I am going to attack {0}", m_Mobile.FocusMob.Name ); + if (MoveTo(combatant, true, m_Mobile.RangeFight)) + { + m_Mobile.Direction = m_Mobile.GetDirectionTo(combatant); + } + else if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("My move is blocked, so I am going to attack {0}", m_Mobile.FocusMob.Name); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; - return true; - } - else if ( m_Mobile.GetDistanceToSqrt( combatant ) > m_Mobile.RangePerception + 1 ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I cannot find {0}, so my guard is up", combatant.Name ); + return true; + } + else if (m_Mobile.GetDistanceToSqrt(combatant) > m_Mobile.RangePerception + 1) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I cannot find {0}, so my guard is up", combatant.Name); - Action = ActionType.Guard; + Action = ActionType.Guard; - return true; - } - else - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I should be closer to {0}", combatant.Name ); - } + return true; + } + else + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I should be closer to {0}", combatant.Name); + } - if ( !m_Mobile.Controlled && !m_Mobile.Summoned && m_Mobile.CanFlee ) - { - if ( m_Mobile.Hits < m_Mobile.HitsMax * 20/100 ) - { - // We are low on health, should we flee? + if (!m_Mobile.Controlled && !m_Mobile.Summoned && m_Mobile.CanFlee) + if (m_Mobile.Hits < m_Mobile.HitsMax * 20 / 100) + { + // We are low on health, should we flee? - bool flee = false; + bool flee = false; - if ( m_Mobile.Hits < combatant.Hits ) - { - // We are more hurt than them + if (m_Mobile.Hits < combatant.Hits) + { + // We are more hurt than them - int diff = combatant.Hits - m_Mobile.Hits; + int diff = combatant.Hits - m_Mobile.Hits; - flee = ( Utility.Random( 0, 100 ) < (10 + diff) ); // (10 + diff)% chance to flee - } - else - { - flee = Utility.Random( 0, 100 ) < 10; // 10% chance to flee - } + flee = Utility.Random(0, 100) < 10 + diff; // (10 + diff)% chance to flee + } + else + { + flee = Utility.Random(0, 100) < 10; // 10% chance to flee + } - if ( flee ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I am going to flee from {0}", combatant.Name ); + if (flee) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I am going to flee from {0}", combatant.Name); - Action = ActionType.Flee; - } - } - } + Action = ActionType.Flee; + } + } - return true; - } + return true; + } - public override bool DoActionGuard() - { - if ( AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + public override bool DoActionGuard() + { + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionGuard(); - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionGuard(); + } - return true; - } + return true; + } - public override bool DoActionFlee() - { - if ( m_Mobile.Hits > m_Mobile.HitsMax/2 ) - { - m_Mobile.DebugSay( "I am stronger now, so I will continue fighting" ); - Action = ActionType.Combat; - } - else - { - m_Mobile.FocusMob = m_Mobile.Combatant; - base.DoActionFlee(); - } + public override bool DoActionFlee() + { + if (m_Mobile.Hits > m_Mobile.HitsMax / 2) + { + m_Mobile.DebugSay("I am stronger now, so I will continue fighting"); + Action = ActionType.Combat; + } + else + { + m_Mobile.FocusMob = m_Mobile.Combatant; + base.DoActionFlee(); + } - return true; - } - } + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/OppositionGroup.cs b/Scripts/Mobiles/AI/OppositionGroup.cs index 25cea3314..dfc7e1180 100644 --- a/Scripts/Mobiles/AI/OppositionGroup.cs +++ b/Scripts/Mobiles/AI/OppositionGroup.cs @@ -3,124 +3,124 @@ using Server.Mobiles; namespace Server { - public class OppositionGroup - { - private Type[][] m_Types; + public class OppositionGroup + { + private Type[][] m_Types; - public OppositionGroup( Type[][] types ) - { - m_Types = types; - } + public OppositionGroup(Type[][] types) + { + m_Types = types; + } - public bool IsEnemy( object from, object target ) - { - int fromGroup = IndexOf( from ); - int targGroup = IndexOf( target ); + public static OppositionGroup TerathansAndOphidians{ get; } = new OppositionGroup(new[] + { + new[] + { + typeof(TerathanAvenger), + typeof(TerathanDrone), + typeof(TerathanMatriarch), + typeof(TerathanWarrior) + }, + new[] + { + typeof(OphidianArchmage), + typeof(OphidianKnight), + typeof(OphidianMage), + typeof(OphidianMatriarch), + typeof(OphidianWarrior) + } + }); - return ( fromGroup != -1 && targGroup != -1 && fromGroup != targGroup ); - } + public static OppositionGroup SavagesAndOrcs{ get; } = new OppositionGroup(new[] + { + new[] + { + typeof(Orc), + typeof(OrcBomber), + typeof(OrcBrute), + typeof(OrcCaptain), + typeof(OrcishLord), + typeof(OrcishMage), + typeof(SpawnedOrcishLord) + }, + new[] + { + typeof(Savage), + typeof(SavageRider), + typeof(SavageRidgeback), + typeof(SavageShaman) + } + }); - public int IndexOf( object obj ) - { - if ( obj == null ) - return -1; + public static OppositionGroup FeyAndUndead{ get; } = new OppositionGroup(new[] + { + new[] + { + typeof(Centaur), + typeof(EtherealWarrior), + typeof(Kirin), + typeof(LordOaks), + typeof(Pixie), + typeof(Silvani), + typeof(Unicorn), + typeof(Wisp), + typeof(Treefellow), + typeof(MLDryad), + typeof(Satyr) + }, + new[] + { + typeof(AncientLich), + typeof(Bogle), + typeof(LichLord), + typeof(Shade), + typeof(Spectre), + typeof(Wraith), + typeof(BoneKnight), + typeof(Ghoul), + typeof(Mummy), + typeof(SkeletalKnight), + typeof(Skeleton), + typeof(Zombie), + typeof(ShadowKnight), + typeof(DarknightCreeper), + typeof(RevenantLion), + typeof(LadyOfTheSnow), + typeof(RottingCorpse), + typeof(SkeletalDragon), + typeof(Lich) + } + }); - Type type = obj.GetType(); + public bool IsEnemy(object from, object target) + { + int fromGroup = IndexOf(from); + int targGroup = IndexOf(target); - for ( int i = 0; i < m_Types.Length; ++i ) - { - Type[] group = m_Types[i]; + return fromGroup != -1 && targGroup != -1 && fromGroup != targGroup; + } - bool contains = false; + public int IndexOf(object obj) + { + if (obj == null) + return -1; - for ( int j = 0; !contains && j < group.Length; ++j ) - contains = group[j].IsAssignableFrom( type ); + Type type = obj.GetType(); - if ( contains ) - return i; - } + for (int i = 0; i < m_Types.Length; ++i) + { + Type[] group = m_Types[i]; - return -1; - } + bool contains = false; - public static OppositionGroup TerathansAndOphidians { get; } = new OppositionGroup( new[] - { - new[] - { - typeof( TerathanAvenger ), - typeof( TerathanDrone ), - typeof( TerathanMatriarch ), - typeof( TerathanWarrior ) - }, - new[] - { - typeof( OphidianArchmage ), - typeof( OphidianKnight ), - typeof( OphidianMage ), - typeof( OphidianMatriarch ), - typeof( OphidianWarrior ) - } - } ); + for (int j = 0; !contains && j < group.Length; ++j) + contains = group[j].IsAssignableFrom(type); - public static OppositionGroup SavagesAndOrcs { get; } = new OppositionGroup( new[] - { - new[] - { - typeof( Orc ), - typeof( OrcBomber ), - typeof( OrcBrute ), - typeof( OrcCaptain ), - typeof( OrcishLord ), - typeof( OrcishMage ), - typeof( SpawnedOrcishLord ) - }, - new[] - { - typeof( Savage ), - typeof( SavageRider ), - typeof( SavageRidgeback ), - typeof( SavageShaman ) - } - } ); + if (contains) + return i; + } - public static OppositionGroup FeyAndUndead { get; } = new OppositionGroup( new[] - { - new[] - { - typeof( Centaur ), - typeof( EtherealWarrior ), - typeof( Kirin ), - typeof( LordOaks ), - typeof( Pixie ), - typeof( Silvani ), - typeof( Unicorn ), - typeof( Wisp ), - typeof( Treefellow ), - typeof( MLDryad ), - typeof( Satyr ) - }, - new[] - { - typeof( AncientLich ), - typeof( Bogle ), - typeof( LichLord ), - typeof( Shade ), - typeof( Spectre ), - typeof( Wraith ), - typeof( BoneKnight ), - typeof( Ghoul ), - typeof( Mummy ), - typeof( SkeletalKnight ), - typeof( Skeleton ), - typeof( Zombie ), - typeof( ShadowKnight ), - typeof( DarknightCreeper ), - typeof( RevenantLion ), - typeof( LadyOfTheSnow ), - typeof( RottingCorpse ), - typeof( SkeletalDragon ), - typeof( Lich ) - } - } ); - } + return -1; + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/PredatorAI.cs b/Scripts/Mobiles/AI/PredatorAI.cs index 961917a30..6b382c623 100644 --- a/Scripts/Mobiles/AI/PredatorAI.cs +++ b/Scripts/Mobiles/AI/PredatorAI.cs @@ -1,95 +1,92 @@ - - - /* * PredatorAI, its an animal that can attack * Dont flee but dont attack if not hurt or attacked * - */ + */ namespace Server.Mobiles { - public class PredatorAI : BaseAI - { - public PredatorAI(BaseCreature m) : base (m) - { - } + public class PredatorAI : BaseAI + { + public PredatorAI(BaseCreature m) : base(m) + { + } - public override bool DoActionWander() - { - if ( m_Mobile.Combatant != null ) - { - m_Mobile.DebugSay( "I am hurt or being attacked, I kill him" ); - Action = ActionType.Combat; - } - else if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, true, false, true)) - { - m_Mobile.DebugSay( "There is something near, I go away" ); - Action = ActionType.Backoff; - } - else - { - base.DoActionWander(); - } + public override bool DoActionWander() + { + if (m_Mobile.Combatant != null) + { + m_Mobile.DebugSay("I am hurt or being attacked, I kill him"); + Action = ActionType.Combat; + } + else if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, true, false, true)) + { + m_Mobile.DebugSay("There is something near, I go away"); + Action = ActionType.Backoff; + } + else + { + base.DoActionWander(); + } - return true; - } + return true; + } - public override bool DoActionCombat() - { - Mobile combatant = m_Mobile.Combatant; + public override bool DoActionCombat() + { + Mobile combatant = m_Mobile.Combatant; - if ( combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map ) - { - m_Mobile.DebugSay( "My combatant is gone, so my guard is up" ); - Action = ActionType.Wander; - return true; - } + if (combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map) + { + m_Mobile.DebugSay("My combatant is gone, so my guard is up"); + Action = ActionType.Wander; + return true; + } - if ( WalkMobileRange( combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight ) ) - { - m_Mobile.Direction = m_Mobile.GetDirectionTo( combatant ); - } - else - { - if ( m_Mobile.GetDistanceToSqrt( combatant ) > m_Mobile.RangePerception + 1 ) - { - m_Mobile.DebugSay( "I cannot find {0}", combatant.Name ); + if (WalkMobileRange(combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight)) + { + m_Mobile.Direction = m_Mobile.GetDirectionTo(combatant); + } + else + { + if (m_Mobile.GetDistanceToSqrt(combatant) > m_Mobile.RangePerception + 1) + { + m_Mobile.DebugSay("I cannot find {0}", combatant.Name); - Action = ActionType.Wander; - return true; - } + Action = ActionType.Wander; + return true; + } - m_Mobile.DebugSay( "I should be closer to {0}", combatant.Name ); - } + m_Mobile.DebugSay("I should be closer to {0}", combatant.Name); + } - return true; - } + return true; + } - public override bool DoActionBackoff() - { - if ( m_Mobile.IsHurt() || m_Mobile.Combatant != null ) - { - Action = ActionType.Combat; - } - else - { - if (AcquireFocusMob(m_Mobile.RangePerception * 2, FightMode.Closest, true, false , true)) - { - if ( WalkMobileRange(m_Mobile.FocusMob, 1, false, m_Mobile.RangePerception, m_Mobile.RangePerception * 2) ) - { - m_Mobile.DebugSay( "Well, here I am safe" ); - Action = ActionType.Wander; - } - } - else - { - m_Mobile.DebugSay( "I have lost my focus, lets relax" ); - Action = ActionType.Wander; - } - } + public override bool DoActionBackoff() + { + if (m_Mobile.IsHurt() || m_Mobile.Combatant != null) + { + Action = ActionType.Combat; + } + else + { + if (AcquireFocusMob(m_Mobile.RangePerception * 2, FightMode.Closest, true, false, true)) + { + if (WalkMobileRange(m_Mobile.FocusMob, 1, false, m_Mobile.RangePerception, m_Mobile.RangePerception * 2)) + { + m_Mobile.DebugSay("Well, here I am safe"); + Action = ActionType.Wander; + } + } + else + { + m_Mobile.DebugSay("I have lost my focus, lets relax"); + Action = ActionType.Wander; + } + } - return true; - } - } + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/SpeedInfo.cs b/Scripts/Mobiles/AI/SpeedInfo.cs index 129fcef7f..29be32361 100644 --- a/Scripts/Mobiles/AI/SpeedInfo.cs +++ b/Scripts/Mobiles/AI/SpeedInfo.cs @@ -1,206 +1,210 @@ using System; using System.Collections.Generic; -using Server.Mobiles; using Server.Factions; +using Server.Mobiles; namespace Server { - public class SpeedInfo - { - // Should we use the new method of speeds? - private static bool Enabled = true; + public class SpeedInfo + { + // Should we use the new method of speeds? + private static bool Enabled = true; - public double ActiveSpeed { get; set; } + private static Dictionary m_Table; - public double PassiveSpeed { get; set; } + private static SpeedInfo[] m_Speeds = + { + /* Slow */ + new SpeedInfo(0.3, 0.6, new[] + { + typeof(AntLion), typeof(ArcticOgreLord), typeof(BogThing), + typeof(Bogle), typeof(BoneKnight), typeof(EarthElemental), + typeof(Ettin), typeof(FrostOoze), typeof(FrostTroll), + typeof(GazerLarva), typeof(Ghoul), typeof(Golem), + typeof(HeadlessOne), typeof(Jwilson), typeof(Mummy), + typeof(Ogre), typeof(OgreLord), typeof(PlagueBeast), + typeof(Quagmire), typeof(Rat), typeof(RottingCorpse), + typeof(SewerRat), typeof(Skeleton), typeof(Slime), + typeof(Zombie), typeof(Walrus), typeof(RestlessSoul), + typeof(CrystalElemental), typeof(DarknightCreeper), typeof(MoundOfMaggots), + typeof(Juggernaut), typeof(Yamandon), typeof(Serado) + }), + /* Fast */ + new SpeedInfo(0.2, 0.4, new[] + { + typeof(LordOaks), typeof(Silvani), typeof(AirElemental), + typeof(AncientWyrm), typeof(Balron), typeof(BladeSpirits), + typeof(DreadSpider), typeof(Efreet), typeof(EtherealWarrior), + typeof(Lich), typeof(Nightmare), typeof(OphidianArchmage), + typeof(OphidianMage), typeof(OphidianWarrior), typeof(OphidianMatriarch), + typeof(OphidianKnight), typeof(PoisonElemental), typeof(Revenant), + typeof(SandVortex), typeof(SavageRider), typeof(SavageShaman), + typeof(SnowElemental), typeof(WhiteWyrm), typeof(Wisp), + typeof(DemonKnight), typeof(GiantBlackWidow), typeof(SummonedAirElemental), + typeof(LesserHiryu), typeof(Hiryu), typeof(LadyOfTheSnow), + typeof(RaiJu), typeof(Ronin), typeof(RuneBeetle), + typeof(Changeling), - public Type[] Types { get; set; } + #region ML named mobs - before Paragon speedboost - public SpeedInfo( double activeSpeed, double passiveSpeed, Type[] types ) - { - ActiveSpeed = activeSpeed; - PassiveSpeed = passiveSpeed; - Types = types; - } + typeof(LadyJennifyr), typeof(LadyMarai), typeof(MasterJonath), + typeof(MasterMikael), typeof(MasterTheophilus), typeof(RedDeath), + typeof(SirPatrick), typeof(Miasma), typeof(Rend), + typeof(Grobu), typeof(Gnaw), typeof(Guile), + typeof(Irk), typeof(Spite), typeof(LadyLissith), + typeof(LadySabrix), typeof(Malefic), typeof(Silk), + typeof(Virulent) + // TODO: Where to put Lurg, Putrefier, Swoop and Pyre? They seem slower. - public static bool Contains( object obj ) - { - if ( !Enabled ) - return false; + #endregion + }), + /* Very Fast */ + new SpeedInfo(0.175, 0.350, new[] + { + typeof(Barracoon), typeof(Mephitis), typeof(Neira), + typeof(Rikktor), typeof(Semidar), typeof(EnergyVortex), + typeof(EliteNinja), typeof(Pixie), typeof(SilverSerpent), + typeof(VorpalBunny), typeof(FleshRenderer), typeof(KhaldunRevenant), + typeof(FactionDragoon), typeof(FactionKnight), typeof(FactionPaladin), + typeof(FactionHenchman), typeof(FactionMercenary), typeof(FactionNecromancer), + typeof(FactionSorceress), typeof(FactionWizard), typeof(FactionBerserker), + typeof(FactionPaladin), typeof(Leviathan), typeof(FireBeetle), + typeof(FanDancer), typeof(FactionDeathKnight) + }), + /* Medium */ + new SpeedInfo(0.25, 0.5, new[] + { + typeof(AcidElemental), typeof(AgapiteElemental), typeof(Alligator), + typeof(AncientLich), typeof(Betrayer), typeof(Bird), + typeof(BlackBear), typeof(BlackSolenInfiltratorQueen), typeof(BlackSolenInfiltratorWarrior), + typeof(BlackSolenQueen), typeof(BlackSolenWarrior), typeof(BlackSolenWorker), + typeof(BloodElemental), typeof(Boar), typeof(Bogling), + typeof(BoneMagi), typeof(Brigand), typeof(BronzeElemental), + typeof(BrownBear), typeof(Bull), typeof(BullFrog), + typeof(Cat), typeof(Centaur), typeof(ChaosDaemon), + typeof(Chicken), typeof(GolemController), typeof(CopperElemental), + typeof(CopperElemental), typeof(Cougar), typeof(Cow), + typeof(Cyclops), typeof(Daemon), typeof(DeepSeaSerpent), + typeof(DesertOstard), typeof(DireWolf), typeof(Dog), + typeof(Dolphin), typeof(Dragon), typeof(Drake), + typeof(DullCopperElemental), typeof(Eagle), typeof(ElderGazer), + typeof(EvilMage), typeof(EvilMageLord), typeof(Executioner), + typeof(Savage), typeof(FireElemental), typeof(FireGargoyle), + typeof(FireSteed), typeof(ForestOstard), typeof(FrenziedOstard), + typeof(FrostSpider), typeof(Gargoyle), typeof(Gazer), + typeof(IceSerpent), typeof(GiantRat), typeof(GiantSerpent), + typeof(GiantSpider), typeof(GiantToad), typeof(Goat), + typeof(GoldenElemental), typeof(Gorilla), typeof(GreatHart), + typeof(GreyWolf), typeof(GrizzlyBear), typeof(Guardian), + typeof(Harpy), typeof(Harrower), typeof(HellHound), + typeof(Hind), typeof(HordeMinion), typeof(Horse), + typeof(Horse), typeof(IceElemental), typeof(IceFiend), + typeof(IceSnake), typeof(Imp), typeof(JackRabbit), + typeof(Kirin), typeof(Kraken), typeof(PredatorHellCat), + typeof(LavaLizard), typeof(LavaSerpent), typeof(LavaSnake), + typeof(Lizardman), typeof(Llama), typeof(Mongbat), + typeof(StrongMongbat), typeof(MountainGoat), typeof(Orc), + typeof(OrcBomber), typeof(OrcBrute), typeof(OrcCaptain), + typeof(OrcishLord), typeof(OrcishMage), typeof(PackHorse), + typeof(PackLlama), typeof(Panther), typeof(Pig), + typeof(PlagueSpawn), typeof(PolarBear), typeof(Rabbit), + typeof(Ratman), typeof(RatmanArcher), typeof(RatmanMage), + typeof(RedSolenInfiltratorQueen), typeof(RedSolenInfiltratorWarrior), typeof(RedSolenQueen), + typeof(RedSolenWarrior), typeof(RedSolenWorker), typeof(RidableLlama), + typeof(Ridgeback), typeof(Scorpion), typeof(SeaSerpent), + typeof(SerpentineDragon), typeof(Shade), typeof(ShadowIronElemental), + typeof(ShadowWisp), typeof(ShadowWyrm), typeof(Sheep), + typeof(SilverSteed), typeof(SkeletalDragon), typeof(SkeletalMage), + typeof(SkeletalMount), typeof(HellCat), typeof(Snake), + typeof(SnowLeopard), typeof(SpectralArmour), typeof(Spectre), + typeof(StoneGargoyle), typeof(StoneHarpy), typeof(SwampDragon), + typeof(ScaledSwampDragon), typeof(SwampTentacle), typeof(TerathanAvenger), + typeof(TerathanDrone), typeof(TerathanMatriarch), typeof(TerathanWarrior), + typeof(TimberWolf), typeof(Titan), typeof(Troll), + typeof(Unicorn), typeof(ValoriteElemental), typeof(VeriteElemental), + typeof(CoMWarHorse), typeof(MinaxWarHorse), typeof(SLWarHorse), + typeof(TBWarHorse), typeof(WaterElemental), typeof(WhippingVine), + typeof(WhiteWolf), typeof(Wraith), typeof(Wyvern), + typeof(KhaldunZealot), typeof(KhaldunSummoner), typeof(SavageRidgeback), + typeof(LichLord), typeof(SkeletalKnight), typeof(SummonedDaemon), + typeof(SummonedEarthElemental), typeof(SummonedWaterElemental), typeof(SummonedFireElemental), + typeof(MeerWarrior), typeof(MeerEternal), typeof(MeerMage), + typeof(MeerCaptain), typeof(JukaLord), typeof(JukaMage), + typeof(JukaWarrior), typeof(AbysmalHorror), typeof(BoneDemon), + typeof(Devourer), typeof(FleshGolem), typeof(Gibberling), + typeof(GoreFiend), typeof(Impaler), typeof(PatchworkSkeleton), + typeof(Ravager), typeof(ShadowKnight), typeof(SkitteringHopper), + typeof(Treefellow), typeof(VampireBat), typeof(WailingBanshee), + typeof(WandererOfTheVoid), typeof(Cursed), typeof(GrimmochDrummel), + typeof(LysanderGathenwale), typeof(MorgBergen), typeof(ShadowFiend), + typeof(SpectralArmour), typeof(TavaraSewel), typeof(ArcaneDaemon), + typeof(Doppleganger), typeof(EnslavedGargoyle), typeof(ExodusMinion), + typeof(ExodusOverseer), typeof(GargoyleDestroyer), typeof(GargoyleEnforcer), + typeof(Moloch), typeof(BakeKitsune), typeof(DeathwatchBeetleHatchling), + typeof(Kappa), typeof(KazeKemono), typeof(DeathwatchBeetle), + typeof(TsukiWolf), typeof(YomotsuElder), typeof(YomotsuPriest), + typeof(YomotsuWarrior), typeof(RevenantLion), typeof(Oni), + typeof(Gaman), typeof(Crane), typeof(Beetle) + }) + }; - if ( m_Table == null ) - LoadTable(); + public SpeedInfo(double activeSpeed, double passiveSpeed, Type[] types) + { + ActiveSpeed = activeSpeed; + PassiveSpeed = passiveSpeed; + Types = types; + } - m_Table.TryGetValue( obj.GetType(), out SpeedInfo sp ); + public double ActiveSpeed{ get; set; } - return ( sp != null ); - } + public double PassiveSpeed{ get; set; } - public static bool GetSpeeds( object obj, ref double activeSpeed, ref double passiveSpeed ) - { - if ( !Enabled ) - return false; + public Type[] Types{ get; set; } - if ( m_Table == null ) - LoadTable(); + public static bool Contains(object obj) + { + if (!Enabled) + return false; - m_Table.TryGetValue( obj.GetType(), out SpeedInfo sp ); + if (m_Table == null) + LoadTable(); - if ( sp == null ) - return false; + m_Table.TryGetValue(obj.GetType(), out SpeedInfo sp); - activeSpeed = sp.ActiveSpeed; - passiveSpeed = sp.PassiveSpeed; + return sp != null; + } - return true; - } + public static bool GetSpeeds(object obj, ref double activeSpeed, ref double passiveSpeed) + { + if (!Enabled) + return false; - private static void LoadTable() - { - m_Table = new Dictionary(); + if (m_Table == null) + LoadTable(); - for ( int i = 0; i < m_Speeds.Length; ++i ) - { - SpeedInfo info = m_Speeds[i]; - Type[] types = info.Types; + m_Table.TryGetValue(obj.GetType(), out SpeedInfo sp); - for ( int j = 0; j < types.Length; ++j ) - m_Table[types[j]] = info; - } - } + if (sp == null) + return false; - private static Dictionary m_Table; + activeSpeed = sp.ActiveSpeed; + passiveSpeed = sp.PassiveSpeed; - private static SpeedInfo[] m_Speeds = { - /* Slow */ - new SpeedInfo( 0.3, 0.6, new[] - { - typeof( AntLion ), typeof( ArcticOgreLord ), typeof( BogThing ), - typeof( Bogle ), typeof( BoneKnight ), typeof( EarthElemental ), - typeof( Ettin ), typeof( FrostOoze ), typeof( FrostTroll ), - typeof( GazerLarva ), typeof( Ghoul ), typeof( Golem ), - typeof( HeadlessOne ), typeof( Jwilson ), typeof( Mummy ), - typeof( Ogre ), typeof( OgreLord ), typeof( PlagueBeast ), - typeof( Quagmire ), typeof( Rat ), typeof( RottingCorpse ), - typeof( SewerRat ), typeof( Skeleton ), typeof( Slime ), - typeof( Zombie ), typeof( Walrus ), typeof( RestlessSoul ), - typeof( CrystalElemental ), typeof( DarknightCreeper ), typeof( MoundOfMaggots ), - typeof( Juggernaut ), typeof( Yamandon ), typeof( Serado ) - } ), - /* Fast */ - new SpeedInfo( 0.2, 0.4, new[] - { - typeof( LordOaks ), typeof( Silvani ), typeof( AirElemental ), - typeof( AncientWyrm ), typeof( Balron ), typeof( BladeSpirits ), - typeof( DreadSpider ), typeof( Efreet ), typeof( EtherealWarrior ), - typeof( Lich ), typeof( Nightmare ), typeof( OphidianArchmage ), - typeof( OphidianMage ), typeof( OphidianWarrior ), typeof( OphidianMatriarch ), - typeof( OphidianKnight ), typeof( PoisonElemental ), typeof( Revenant ), - typeof( SandVortex ), typeof( SavageRider ), typeof( SavageShaman ), - typeof( SnowElemental ), typeof( WhiteWyrm ), typeof( Wisp ), - typeof( DemonKnight ), typeof( GiantBlackWidow ), typeof( SummonedAirElemental ), - typeof( LesserHiryu ), typeof( Hiryu ), typeof( LadyOfTheSnow ), - typeof( RaiJu ), typeof( Ronin ), typeof( RuneBeetle ), - typeof( Changeling ), - #region ML named mobs - before Paragon speedboost - typeof( LadyJennifyr ), typeof( LadyMarai ), typeof( MasterJonath ), - typeof( MasterMikael ), typeof( MasterTheophilus ), typeof( RedDeath ), - typeof( SirPatrick ), typeof( Miasma ), typeof( Rend ), - typeof( Grobu ), typeof( Gnaw ), typeof( Guile ), - typeof( Irk ), typeof( Spite ), typeof( LadyLissith ), - typeof( LadySabrix ), typeof( Malefic ), typeof( Silk ), - typeof( Virulent ) - // TODO: Where to put Lurg, Putrefier, Swoop and Pyre? They seem slower. - #endregion - } ), - /* Very Fast */ - new SpeedInfo( 0.175, 0.350, new[] - { - typeof( Barracoon ), typeof( Mephitis ), typeof( Neira ), - typeof( Rikktor ), typeof( Semidar ), typeof( EnergyVortex ), - typeof( EliteNinja ), typeof( Pixie ), typeof( SilverSerpent ), - typeof( VorpalBunny ), typeof( FleshRenderer ), typeof( KhaldunRevenant ), - typeof( FactionDragoon ), typeof( FactionKnight ), typeof( FactionPaladin ), - typeof( FactionHenchman ), typeof( FactionMercenary ), typeof( FactionNecromancer ), - typeof( FactionSorceress ), typeof( FactionWizard ), typeof( FactionBerserker ), - typeof( FactionPaladin ), typeof( Leviathan ), typeof( FireBeetle ), - typeof( FanDancer ), typeof( FactionDeathKnight ) - } ), - /* Medium */ - new SpeedInfo( 0.25, 0.5, new[] - { - typeof( AcidElemental ), typeof( AgapiteElemental ), typeof( Alligator ), - typeof( AncientLich ), typeof( Betrayer ), typeof( Bird ), - typeof( BlackBear ), typeof( BlackSolenInfiltratorQueen ), typeof( BlackSolenInfiltratorWarrior ), - typeof( BlackSolenQueen ), typeof( BlackSolenWarrior ), typeof( BlackSolenWorker ), - typeof( BloodElemental ), typeof( Boar ), typeof( Bogling ), - typeof( BoneMagi ), typeof( Brigand ), typeof( BronzeElemental ), - typeof( BrownBear ), typeof( Bull ), typeof( BullFrog ), - typeof( Cat ), typeof( Centaur ), typeof( ChaosDaemon ), - typeof( Chicken ), typeof( GolemController ), typeof( CopperElemental ), - typeof( CopperElemental ), typeof( Cougar ), typeof( Cow ), - typeof( Cyclops ), typeof( Daemon ), typeof( DeepSeaSerpent ), - typeof( DesertOstard ), typeof( DireWolf ), typeof( Dog ), - typeof( Dolphin ), typeof( Dragon ), typeof( Drake ), - typeof( DullCopperElemental ), typeof( Eagle ), typeof( ElderGazer ), - typeof( EvilMage ), typeof( EvilMageLord ), typeof( Executioner ), - typeof( Savage ), typeof( FireElemental ), typeof( FireGargoyle ), - typeof( FireSteed ), typeof( ForestOstard ), typeof( FrenziedOstard ), - typeof( FrostSpider ), typeof( Gargoyle ), typeof( Gazer ), - typeof( IceSerpent ), typeof( GiantRat ), typeof( GiantSerpent ), - typeof( GiantSpider ), typeof( GiantToad ), typeof( Goat ), - typeof( GoldenElemental ), typeof( Gorilla ), typeof( GreatHart ), - typeof( GreyWolf ), typeof( GrizzlyBear ), typeof( Guardian ), - typeof( Harpy ), typeof( Harrower ), typeof( HellHound ), - typeof( Hind ), typeof( HordeMinion ), typeof( Horse ), - typeof( Horse ), typeof( IceElemental ), typeof( IceFiend ), - typeof( IceSnake ), typeof( Imp ), typeof( JackRabbit ), - typeof( Kirin ), typeof( Kraken ), typeof( PredatorHellCat ), - typeof( LavaLizard ), typeof( LavaSerpent ), typeof( LavaSnake ), - typeof( Lizardman ), typeof( Llama ), typeof( Mongbat ), - typeof( StrongMongbat ), typeof( MountainGoat ), typeof( Orc ), - typeof( OrcBomber ), typeof( OrcBrute ), typeof( OrcCaptain ), - typeof( OrcishLord ), typeof( OrcishMage ), typeof( PackHorse ), - typeof( PackLlama ), typeof( Panther ), typeof( Pig ), - typeof( PlagueSpawn ), typeof( PolarBear ), typeof( Rabbit ), - typeof( Ratman ), typeof( RatmanArcher ), typeof( RatmanMage ), - typeof( RedSolenInfiltratorQueen ), typeof( RedSolenInfiltratorWarrior ), typeof( RedSolenQueen ), - typeof( RedSolenWarrior ), typeof( RedSolenWorker ), typeof( RidableLlama ), - typeof( Ridgeback ), typeof( Scorpion ), typeof( SeaSerpent ), - typeof( SerpentineDragon ), typeof( Shade ), typeof( ShadowIronElemental ), - typeof( ShadowWisp ), typeof( ShadowWyrm ), typeof( Sheep ), - typeof( SilverSteed ), typeof( SkeletalDragon ), typeof( SkeletalMage ), - typeof( SkeletalMount ), typeof( HellCat ), typeof( Snake ), - typeof( SnowLeopard ), typeof( SpectralArmour ), typeof( Spectre ), - typeof( StoneGargoyle ), typeof( StoneHarpy ), typeof( SwampDragon ), - typeof( ScaledSwampDragon ), typeof( SwampTentacle ), typeof( TerathanAvenger ), - typeof( TerathanDrone ), typeof( TerathanMatriarch ), typeof( TerathanWarrior ), - typeof( TimberWolf ), typeof( Titan ), typeof( Troll ), - typeof( Unicorn ), typeof( ValoriteElemental ), typeof( VeriteElemental ), - typeof( CoMWarHorse ), typeof( MinaxWarHorse ), typeof( SLWarHorse ), - typeof( TBWarHorse ), typeof( WaterElemental ), typeof( WhippingVine ), - typeof( WhiteWolf ), typeof( Wraith ), typeof( Wyvern ), - typeof( KhaldunZealot ), typeof( KhaldunSummoner ), typeof( SavageRidgeback ), - typeof( LichLord ), typeof( SkeletalKnight ), typeof( SummonedDaemon ), - typeof( SummonedEarthElemental ), typeof( SummonedWaterElemental ), typeof( SummonedFireElemental ), - typeof( MeerWarrior ), typeof( MeerEternal ), typeof( MeerMage ), - typeof( MeerCaptain ), typeof( JukaLord ), typeof( JukaMage ), - typeof( JukaWarrior ), typeof( AbysmalHorror ), typeof( BoneDemon ), - typeof( Devourer ), typeof( FleshGolem ), typeof( Gibberling ), - typeof( GoreFiend ), typeof( Impaler ), typeof( PatchworkSkeleton ), - typeof( Ravager ), typeof( ShadowKnight ), typeof( SkitteringHopper ), - typeof( Treefellow ), typeof( VampireBat ), typeof( WailingBanshee ), - typeof( WandererOfTheVoid ), typeof( Cursed ), typeof( GrimmochDrummel ), - typeof( LysanderGathenwale ), typeof( MorgBergen ), typeof( ShadowFiend ), - typeof( SpectralArmour ), typeof( TavaraSewel ), typeof( ArcaneDaemon ), - typeof( Doppleganger ), typeof( EnslavedGargoyle ), typeof( ExodusMinion ), - typeof( ExodusOverseer ), typeof( GargoyleDestroyer ), typeof( GargoyleEnforcer ), - typeof( Moloch ), typeof( BakeKitsune ), typeof( DeathwatchBeetleHatchling ), - typeof( Kappa ), typeof( KazeKemono ), typeof( DeathwatchBeetle ), - typeof( TsukiWolf ), typeof( YomotsuElder ), typeof( YomotsuPriest ), - typeof( YomotsuWarrior ), typeof( RevenantLion ), typeof( Oni ), - typeof( Gaman ), typeof( Crane ), typeof( Beetle ) - } ) - }; - } -} + return true; + } + + private static void LoadTable() + { + m_Table = new Dictionary(); + + for (int i = 0; i < m_Speeds.Length; ++i) + { + SpeedInfo info = m_Speeds[i]; + Type[] types = info.Types; + + for (int j = 0; j < types.Length; ++j) + m_Table[types[j]] = info; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/AI/ThiefAI.cs b/Scripts/Mobiles/AI/ThiefAI.cs index 4e553ed44..b6547700f 100644 --- a/Scripts/Mobiles/AI/ThiefAI.cs +++ b/Scripts/Mobiles/AI/ThiefAI.cs @@ -7,179 +7,186 @@ using Server.Items; namespace Server.Mobiles { - public class ThiefAI : BaseAI - { - public ThiefAI(BaseCreature m) : base (m) - { - } + public class ThiefAI : BaseAI + { + private Item m_toDisarm; - private Item m_toDisarm; - public override bool DoActionWander() - { - m_Mobile.DebugSay( "I have no combatant" ); + public ThiefAI(BaseCreature m) : base(m) + { + } - if ( AcquireFocusMob( m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + public override bool DoActionWander() + { + m_Mobile.DebugSay("I have no combatant"); - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionWander(); - } + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); - return true; - } + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionWander(); + } - public override bool DoActionCombat() - { - Mobile combatant = m_Mobile.Combatant; + return true; + } - if ( combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map ) - { - m_Mobile.DebugSay( "My combatant is gone, so my guard is up" ); + public override bool DoActionCombat() + { + Mobile combatant = m_Mobile.Combatant; - Action = ActionType.Guard; + if (combatant == null || combatant.Deleted || combatant.Map != m_Mobile.Map) + { + m_Mobile.DebugSay("My combatant is gone, so my guard is up"); - return true; - } + Action = ActionType.Guard; - if ( WalkMobileRange( combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight ) ) - { - m_Mobile.Direction = m_Mobile.GetDirectionTo( combatant ); - if ( m_toDisarm == null ) - m_toDisarm = combatant.FindItemOnLayer( Layer.OneHanded ); + return true; + } - if ( m_toDisarm == null ) - m_toDisarm = combatant.FindItemOnLayer( Layer.TwoHanded ); + if (WalkMobileRange(combatant, 1, true, m_Mobile.RangeFight, m_Mobile.RangeFight)) + { + m_Mobile.Direction = m_Mobile.GetDirectionTo(combatant); + if (m_toDisarm == null) + m_toDisarm = combatant.FindItemOnLayer(Layer.OneHanded); - if ( m_toDisarm != null && m_toDisarm.IsChildOf( m_Mobile.Backpack ) ) - { - m_toDisarm = combatant.FindItemOnLayer( Layer.OneHanded ); - if ( m_toDisarm == null ) - m_toDisarm = combatant.FindItemOnLayer( Layer.TwoHanded ); - } - if ( !Core.AOS && !m_Mobile.DisarmReady && m_Mobile.Skills[SkillName.Wrestling].Value >= 80.0 && m_Mobile.Skills[SkillName.ArmsLore].Value >= 80.0 && m_toDisarm != null ) - EventSink.InvokeDisarmRequest( new DisarmRequestEventArgs( m_Mobile ) ); + if (m_toDisarm == null) + m_toDisarm = combatant.FindItemOnLayer(Layer.TwoHanded); - if (m_toDisarm != null && m_toDisarm.IsChildOf(combatant.Backpack) && Core.TickCount - m_Mobile.NextSkillTime >= 0 && (m_toDisarm.LootType != LootType.Blessed && m_toDisarm.LootType != LootType.Newbied)) - { - m_Mobile.DebugSay( "Trying to steal from combatant." ); - m_Mobile.UseSkill( SkillName.Stealing ); - m_Mobile.Target?.Invoke( m_Mobile, m_toDisarm ); - } - else if (m_toDisarm == null && Core.TickCount - m_Mobile.NextSkillTime >= 0) - { - Container cpack = combatant.Backpack; + if (m_toDisarm != null && m_toDisarm.IsChildOf(m_Mobile.Backpack)) + { + m_toDisarm = combatant.FindItemOnLayer(Layer.OneHanded); + if (m_toDisarm == null) + m_toDisarm = combatant.FindItemOnLayer(Layer.TwoHanded); + } - if ( cpack != null ) - { - Item steala = cpack.FindItemByType( typeof ( Bandage ) ); - if ( steala != null ) - { - m_Mobile.DebugSay( "Trying to steal from combatant." ); - m_Mobile.UseSkill( SkillName.Stealing ); - m_Mobile.Target?.Invoke( m_Mobile, steala ); - } - Item stealb = cpack.FindItemByType( typeof ( Nightshade ) ); - if ( stealb != null ) - { - m_Mobile.DebugSay( "Trying to steal from combatant." ); - m_Mobile.UseSkill( SkillName.Stealing ); - m_Mobile.Target?.Invoke( m_Mobile, stealb ); - } - Item stealc = cpack.FindItemByType( typeof ( BlackPearl ) ); - if ( stealc != null ) - { - m_Mobile.DebugSay( "Trying to steal from combatant." ); - m_Mobile.UseSkill( SkillName.Stealing ); - m_Mobile.Target?.Invoke( m_Mobile, stealc ); - } + if (!Core.AOS && !m_Mobile.DisarmReady && m_Mobile.Skills[SkillName.Wrestling].Value >= 80.0 && + m_Mobile.Skills[SkillName.ArmsLore].Value >= 80.0 && m_toDisarm != null) + EventSink.InvokeDisarmRequest(new DisarmRequestEventArgs(m_Mobile)); - Item steald = cpack.FindItemByType( typeof ( MandrakeRoot ) ); - if ( steald != null ) - { - m_Mobile.DebugSay( "Trying to steal from combatant." ); - m_Mobile.UseSkill( SkillName.Stealing ); - m_Mobile.Target?.Invoke( m_Mobile, steald ); - } - else if ( steala == null && stealb == null && stealc == null && steald == null ) - { - m_Mobile.DebugSay( "I am going to flee from {0}", combatant.Name ); + if (m_toDisarm != null && m_toDisarm.IsChildOf(combatant.Backpack) && + Core.TickCount - m_Mobile.NextSkillTime >= 0 && m_toDisarm.LootType != LootType.Blessed && + m_toDisarm.LootType != LootType.Newbied) + { + m_Mobile.DebugSay("Trying to steal from combatant."); + m_Mobile.UseSkill(SkillName.Stealing); + m_Mobile.Target?.Invoke(m_Mobile, m_toDisarm); + } + else if (m_toDisarm == null && Core.TickCount - m_Mobile.NextSkillTime >= 0) + { + Container cpack = combatant.Backpack; - Action = ActionType.Flee; - } - } - } - } - else - { - m_Mobile.DebugSay( "I should be closer to {0}", combatant.Name ); - } + if (cpack != null) + { + Item steala = cpack.FindItemByType(typeof(Bandage)); + if (steala != null) + { + m_Mobile.DebugSay("Trying to steal from combatant."); + m_Mobile.UseSkill(SkillName.Stealing); + m_Mobile.Target?.Invoke(m_Mobile, steala); + } - if ( m_Mobile.Hits < m_Mobile.HitsMax * 20/100 && m_Mobile.CanFlee ) - { - // We are low on health, should we flee? + Item stealb = cpack.FindItemByType(typeof(Nightshade)); + if (stealb != null) + { + m_Mobile.DebugSay("Trying to steal from combatant."); + m_Mobile.UseSkill(SkillName.Stealing); + m_Mobile.Target?.Invoke(m_Mobile, stealb); + } - bool flee = false; + Item stealc = cpack.FindItemByType(typeof(BlackPearl)); + if (stealc != null) + { + m_Mobile.DebugSay("Trying to steal from combatant."); + m_Mobile.UseSkill(SkillName.Stealing); + m_Mobile.Target?.Invoke(m_Mobile, stealc); + } - if ( m_Mobile.Hits < combatant.Hits ) - { - // We are more hurt than them + Item steald = cpack.FindItemByType(typeof(MandrakeRoot)); + if (steald != null) + { + m_Mobile.DebugSay("Trying to steal from combatant."); + m_Mobile.UseSkill(SkillName.Stealing); + m_Mobile.Target?.Invoke(m_Mobile, steald); + } + else if (steala == null && stealb == null && stealc == null && steald == null) + { + m_Mobile.DebugSay("I am going to flee from {0}", combatant.Name); - int diff = combatant.Hits - m_Mobile.Hits; + Action = ActionType.Flee; + } + } + } + } + else + { + m_Mobile.DebugSay("I should be closer to {0}", combatant.Name); + } - flee = ( Utility.Random( 0, 100 ) > (10 + diff) ); // (10 + diff)% chance to flee - } - else - { - flee = Utility.Random( 0, 100 ) > 10; // 10% chance to flee - } + if (m_Mobile.Hits < m_Mobile.HitsMax * 20 / 100 && m_Mobile.CanFlee) + { + // We are low on health, should we flee? - if ( flee ) - { - m_Mobile.DebugSay( "I am going to flee from {0}", combatant.Name ); + bool flee = false; - Action = ActionType.Flee; - } - } + if (m_Mobile.Hits < combatant.Hits) + { + // We are more hurt than them - return true; - } + int diff = combatant.Hits - m_Mobile.Hits; - public override bool DoActionGuard() - { - if ( AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true ) ) - { - m_Mobile.DebugSay( "I have detected {0}, attacking", m_Mobile.FocusMob.Name ); + flee = Utility.Random(0, 100) > 10 + diff; // (10 + diff)% chance to flee + } + else + { + flee = Utility.Random(0, 100) > 10; // 10% chance to flee + } - m_Mobile.Combatant = m_Mobile.FocusMob; - Action = ActionType.Combat; - } - else - { - base.DoActionGuard(); - } + if (flee) + { + m_Mobile.DebugSay("I am going to flee from {0}", combatant.Name); - return true; - } + Action = ActionType.Flee; + } + } - public override bool DoActionFlee() - { - if ( m_Mobile.Hits > m_Mobile.HitsMax/2 ) - { - m_Mobile.DebugSay( "I am stronger now, so I will continue fighting" ); - Action = ActionType.Combat; - } - else - { - m_Mobile.FocusMob = m_Mobile.Combatant; - base.DoActionFlee(); - } + return true; + } - return true; - } - } + public override bool DoActionGuard() + { + if (AcquireFocusMob(m_Mobile.RangePerception, m_Mobile.FightMode, false, false, true)) + { + m_Mobile.DebugSay("I have detected {0}, attacking", m_Mobile.FocusMob.Name); + + m_Mobile.Combatant = m_Mobile.FocusMob; + Action = ActionType.Combat; + } + else + { + base.DoActionGuard(); + } + + return true; + } + + public override bool DoActionFlee() + { + if (m_Mobile.Hits > m_Mobile.HitsMax / 2) + { + m_Mobile.DebugSay("I am stronger now, so I will continue fighting"); + Action = ActionType.Combat; + } + else + { + m_Mobile.FocusMob = m_Mobile.Combatant; + base.DoActionFlee(); + } + + return true; + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/AI/VendorAI.cs b/Scripts/Mobiles/AI/VendorAI.cs index 5406100b7..7ad649015 100644 --- a/Scripts/Mobiles/AI/VendorAI.cs +++ b/Scripts/Mobiles/AI/VendorAI.cs @@ -1,5 +1,3 @@ - - // // This is a first simple AI // @@ -7,146 +5,146 @@ namespace Server.Mobiles { - public class VendorAI : BaseAI - { - public VendorAI(BaseCreature m) : base (m) - { - } + public class VendorAI : BaseAI + { + public VendorAI(BaseCreature m) : base(m) + { + } - public override bool DoActionWander() - { - m_Mobile.DebugSay( "I'm fine" ); + public override bool DoActionWander() + { + m_Mobile.DebugSay("I'm fine"); - if ( m_Mobile.Combatant != null ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} is attacking me", m_Mobile.Combatant.Name ); + if (m_Mobile.Combatant != null) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} is attacking me", m_Mobile.Combatant.Name); - m_Mobile.Say( Utility.RandomList( 1005305, 501603 ) ); + m_Mobile.Say(Utility.RandomList(1005305, 501603)); - Action = ActionType.Flee; - } - else - { - if ( m_Mobile.FocusMob != null ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} has talked to me", m_Mobile.FocusMob.Name ); + Action = ActionType.Flee; + } + else + { + if (m_Mobile.FocusMob != null) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} has talked to me", m_Mobile.FocusMob.Name); - Action = ActionType.Interact; - } - else - { - m_Mobile.Warmode = false; + Action = ActionType.Interact; + } + else + { + m_Mobile.Warmode = false; - base.DoActionWander(); - } - } + base.DoActionWander(); + } + } - return true; - } + return true; + } - public override bool DoActionInteract() - { - Mobile customer = m_Mobile.FocusMob; + public override bool DoActionInteract() + { + Mobile customer = m_Mobile.FocusMob; - if ( m_Mobile.Combatant != null ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} is attacking me", m_Mobile.Combatant.Name ); + if (m_Mobile.Combatant != null) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} is attacking me", m_Mobile.Combatant.Name); - m_Mobile.Say( Utility.RandomList( 1005305, 501603 ) ); + m_Mobile.Say(Utility.RandomList(1005305, 501603)); - Action = ActionType.Flee; + Action = ActionType.Flee; - return true; - } + return true; + } - if ( customer == null || customer.Deleted || customer.Map != m_Mobile.Map ) - { - m_Mobile.DebugSay( "My customer have disapeared" ); - m_Mobile.FocusMob = null; + if (customer == null || customer.Deleted || customer.Map != m_Mobile.Map) + { + m_Mobile.DebugSay("My customer have disapeared"); + m_Mobile.FocusMob = null; - Action = ActionType.Wander; - } - else - { - if ( customer.InRange( m_Mobile, m_Mobile.RangeFight ) ) - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "I am with {0}", customer.Name ); + Action = ActionType.Wander; + } + else + { + if (customer.InRange(m_Mobile, m_Mobile.RangeFight)) + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("I am with {0}", customer.Name); - m_Mobile.Direction = m_Mobile.GetDirectionTo( customer ); - } - else - { - if ( m_Mobile.Debug ) - m_Mobile.DebugSay( "{0} is gone", customer.Name ); + m_Mobile.Direction = m_Mobile.GetDirectionTo(customer); + } + else + { + if (m_Mobile.Debug) + m_Mobile.DebugSay("{0} is gone", customer.Name); - m_Mobile.FocusMob = null; + m_Mobile.FocusMob = null; - Action = ActionType.Wander; - } - } + Action = ActionType.Wander; + } + } - return true; - } + return true; + } - public override bool DoActionGuard() - { - m_Mobile.FocusMob = m_Mobile.Combatant; - return base.DoActionGuard(); - } + public override bool DoActionGuard() + { + m_Mobile.FocusMob = m_Mobile.Combatant; + return base.DoActionGuard(); + } - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.InRange( m_Mobile, 4 ) ) - return true; + public override bool HandlesOnSpeech(Mobile from) + { + if (from.InRange(m_Mobile, 4)) + return true; - return base.HandlesOnSpeech( from ); - } + return base.HandlesOnSpeech(from); + } - // Temporary - public override void OnSpeech( SpeechEventArgs e ) - { - base.OnSpeech( e ); + // Temporary + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); - Mobile from = e.Mobile; + Mobile from = e.Mobile; - if ( m_Mobile is BaseVendor vendor && from.InRange( m_Mobile, Core.AOS ? 1 : 4 ) && !e.Handled ) - { - if ( e.HasKeyword( 0x14D ) ) // *vendor sell* - { - e.Handled = true; + if (m_Mobile is BaseVendor vendor && from.InRange(m_Mobile, Core.AOS ? 1 : 4) && !e.Handled) + { + if (e.HasKeyword(0x14D)) // *vendor sell* + { + e.Handled = true; - vendor.VendorSell( from ); - vendor.FocusMob = from; - } - else if ( e.HasKeyword( 0x3C ) ) // *vendor buy* - { - e.Handled = true; + vendor.VendorSell(from); + vendor.FocusMob = from; + } + else if (e.HasKeyword(0x3C)) // *vendor buy* + { + e.Handled = true; - vendor.VendorBuy( from ); - vendor.FocusMob = from; - } - else if ( WasNamed( e.Speech ) ) - { - if ( e.HasKeyword( 0x177 ) ) // *sell* - { - e.Handled = true; + vendor.VendorBuy(from); + vendor.FocusMob = from; + } + else if (WasNamed(e.Speech)) + { + if (e.HasKeyword(0x177)) // *sell* + { + e.Handled = true; - vendor.VendorSell( from ); - } - else if ( e.HasKeyword( 0x171 ) ) // *buy* - { - e.Handled = true; + vendor.VendorSell(from); + } + else if (e.HasKeyword(0x171)) // *buy* + { + e.Handled = true; - vendor.VendorBuy( from ); - } + vendor.VendorBuy(from); + } - vendor.FocusMob = from; - } - } - } - } -} + vendor.FocusMob = from; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Bears/BlackBear.cs b/Scripts/Mobiles/Animals/Bears/BlackBear.cs index 8b178efff..3b17696e1 100644 --- a/Scripts/Mobiles/Animals/Bears/BlackBear.cs +++ b/Scripts/Mobiles/Animals/Bears/BlackBear.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Bear" )] - public class BlackBear : BaseCreature - { - public override string CorpseName => "a bear corpse"; - public override string DefaultName => "a black bear"; + [TypeAlias("Server.Mobiles.Bear")] + public class BlackBear : BaseCreature + { + [Constructible] + public BlackBear() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 211; + BaseSoundID = 0xA3; - [Constructible] - public BlackBear() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 211; - BaseSoundID = 0xA3; + SetStr(76, 100); + SetDex(56, 75); + SetInt(11, 14); - SetStr( 76, 100 ); - SetDex( 56, 75 ); - SetInt( 11, 14 ); + SetHits(46, 60); + SetMana(0); - SetHits( 46, 60 ); - SetMana( 0 ); + SetDamage(4, 10); - SetDamage( 4, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 20.1, 40.0); + SetSkill(SkillName.Tactics, 40.1, 60.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 20.1, 40.0 ); - SetSkill( SkillName.Tactics, 40.1, 60.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 35.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 35.1; - } + public BlackBear(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat | FoodType.FruitsAndVegies; - public override PackInstinct PackInstinct => PackInstinct.Bear; + public override string CorpseName => "a bear corpse"; + public override string DefaultName => "a black bear"; - public BlackBear( Serial serial ) : base( serial ) - { - } + public override int Meat => 1; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat | FoodType.FruitsAndVegies; + public override PackInstinct PackInstinct => PackInstinct.Bear; - public override void Serialize(GenericWriter writer) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Bears/BrownBear.cs b/Scripts/Mobiles/Animals/Bears/BrownBear.cs index 8e3e750fb..01226b5ed 100644 --- a/Scripts/Mobiles/Animals/Bears/BrownBear.cs +++ b/Scripts/Mobiles/Animals/Bears/BrownBear.cs @@ -1,66 +1,66 @@ namespace Server.Mobiles { - public class BrownBear : BaseCreature - { - public override string CorpseName => "a bear corpse"; - public override string DefaultName => "a brown bear"; + public class BrownBear : BaseCreature + { + [Constructible] + public BrownBear() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 167; + BaseSoundID = 0xA3; - [Constructible] - public BrownBear() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 167; - BaseSoundID = 0xA3; + SetStr(76, 100); + SetDex(26, 45); + SetInt(23, 47); - SetStr( 76, 100 ); - SetDex( 26, 45 ); - SetInt( 23, 47 ); + SetHits(46, 60); + SetMana(0); - SetHits( 46, 60 ); - SetMana( 0 ); + SetDamage(6, 12); - SetDamage( 6, 12 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 30); + SetResistance(ResistanceType.Cold, 15, 20); + SetResistance(ResistanceType.Poison, 10, 15); - SetResistance( ResistanceType.Physical, 20, 30 ); - SetResistance( ResistanceType.Cold, 15, 20 ); - SetResistance( ResistanceType.Poison, 10, 15 ); + SetSkill(SkillName.MagicResist, 25.1, 35.0); + SetSkill(SkillName.Tactics, 40.1, 60.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 25.1, 35.0 ); - SetSkill( SkillName.Tactics, 40.1, 60.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 41.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 41.1; - } + public BrownBear(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.FruitsAndVegies | FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Bear; + public override string CorpseName => "a bear corpse"; + public override string DefaultName => "a brown bear"; - public BrownBear( Serial serial ) : base( serial ) - { - } + public override int Meat => 1; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.FruitsAndVegies | FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Bear; - public override void Serialize(GenericWriter writer) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Bears/GrizzlyBear.cs b/Scripts/Mobiles/Animals/Bears/GrizzlyBear.cs index c29773e10..1a61a0b85 100644 --- a/Scripts/Mobiles/Animals/Bears/GrizzlyBear.cs +++ b/Scripts/Mobiles/Animals/Bears/GrizzlyBear.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Grizzlybear" )] - public class GrizzlyBear : BaseCreature - { - public override string CorpseName => "a grizzly bear corpse"; - public override string DefaultName => "a grizzly bear"; + [TypeAlias("Server.Mobiles.Grizzlybear")] + public class GrizzlyBear : BaseCreature + { + [Constructible] + public GrizzlyBear() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 212; + BaseSoundID = 0xA3; - [Constructible] - public GrizzlyBear() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 212; - BaseSoundID = 0xA3; + SetStr(126, 155); + SetDex(81, 105); + SetInt(16, 40); - SetStr( 126, 155 ); - SetDex( 81, 105 ); - SetInt( 16, 40 ); + SetHits(76, 93); + SetMana(0); - SetHits( 76, 93 ); - SetMana( 0 ); + SetDamage(8, 13); - SetDamage( 8, 13 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 70.1, 100.0); + SetSkill(SkillName.Wrestling, 45.1, 70.0); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 70.1, 100.0 ); - SetSkill( SkillName.Wrestling, 45.1, 70.0 ); + Fame = 1000; + Karma = 0; - Fame = 1000; - Karma = 0; + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 59.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 59.1; - } + public GrizzlyBear(Serial serial) : base(serial) + { + } - public override int Meat => 2; - public override int Hides => 16; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.FruitsAndVegies | FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Bear; + public override string CorpseName => "a grizzly bear corpse"; + public override string DefaultName => "a grizzly bear"; - public GrizzlyBear( Serial serial ) : base( serial ) - { - } + public override int Meat => 2; + public override int Hides => 16; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.FruitsAndVegies | FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Bear; - public override void Serialize(GenericWriter writer) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Bears/PolarBear.cs b/Scripts/Mobiles/Animals/Bears/PolarBear.cs index 551dc4dc3..c8582470f 100644 --- a/Scripts/Mobiles/Animals/Bears/PolarBear.cs +++ b/Scripts/Mobiles/Animals/Bears/PolarBear.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Polarbear" )] - public class PolarBear : BaseCreature - { - public override string CorpseName => "a polar bear corpse"; - public override string DefaultName => "a polar bear"; + [TypeAlias("Server.Mobiles.Polarbear")] + public class PolarBear : BaseCreature + { + [Constructible] + public PolarBear() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 213; + BaseSoundID = 0xA3; - [Constructible] - public PolarBear() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 213; - BaseSoundID = 0xA3; + SetStr(116, 140); + SetDex(81, 105); + SetInt(26, 50); - SetStr( 116, 140 ); - SetDex( 81, 105 ); - SetInt( 26, 50 ); + SetHits(70, 84); + SetMana(0); - SetHits( 70, 84 ); - SetMana( 0 ); + SetDamage(7, 12); - SetDamage( 7, 12 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Cold, 60, 80); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Cold, 60, 80 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 60.1, 90.0); + SetSkill(SkillName.Wrestling, 45.1, 70.0); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 60.1, 90.0 ); - SetSkill( SkillName.Wrestling, 45.1, 70.0 ); + Fame = 1500; + Karma = 0; - Fame = 1500; - Karma = 0; + VirtualArmor = 18; - VirtualArmor = 18; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 35.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 35.1; - } + public PolarBear(Serial serial) : base(serial) + { + } - public override int Meat => 2; - public override int Hides => 16; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.FruitsAndVegies | FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Bear; + public override string CorpseName => "a polar bear corpse"; + public override string DefaultName => "a polar bear"; - public PolarBear( Serial serial ) : base( serial ) - { - } + public override int Meat => 2; + public override int Hides => 16; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.FruitsAndVegies | FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Bear; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Birds/Chicken.cs b/Scripts/Mobiles/Animals/Birds/Chicken.cs index 2675ff304..d4353af2a 100644 --- a/Scripts/Mobiles/Animals/Birds/Chicken.cs +++ b/Scripts/Mobiles/Animals/Birds/Chicken.cs @@ -1,66 +1,66 @@ namespace Server.Mobiles { - public class Chicken : BaseCreature - { - public override string CorpseName => "a chicken corpse"; - public override string DefaultName => "a chicken"; + public class Chicken : BaseCreature + { + [Constructible] + public Chicken() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xD0; + BaseSoundID = 0x6E; - [Constructible] - public Chicken() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xD0; - BaseSoundID = 0x6E; + SetStr(5); + SetDex(15); + SetInt(5); - SetStr( 5 ); - SetDex( 15 ); - SetInt( 5 ); + SetHits(3); + SetMana(0); - SetHits( 3 ); - SetMana( 0 ); + SetDamage(1); - SetDamage( 1 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 1, 5); - SetResistance( ResistanceType.Physical, 1, 5 ); + SetSkill(SkillName.MagicResist, 4.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 4.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 150; + Karma = 0; - Fame = 150; - Karma = 0; + VirtualArmor = 2; - VirtualArmor = 2; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -0.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -0.9; - } + public Chicken(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override MeatType MeatType => MeatType.Bird; - public override FoodType FavoriteFood => FoodType.GrainsAndHay; - public override bool CanFly => true; + public override string CorpseName => "a chicken corpse"; + public override string DefaultName => "a chicken"; - public override int Feathers => 25; + public override int Meat => 1; + public override MeatType MeatType => MeatType.Bird; + public override FoodType FavoriteFood => FoodType.GrainsAndHay; + public override bool CanFly => true; - public Chicken(Serial serial) : base(serial) - { - } + public override int Feathers => 25; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Birds/Crane.cs b/Scripts/Mobiles/Animals/Birds/Crane.cs index a2be68ef7..ad85aba59 100644 --- a/Scripts/Mobiles/Animals/Birds/Crane.cs +++ b/Scripts/Mobiles/Animals/Birds/Crane.cs @@ -1,84 +1,84 @@ namespace Server.Mobiles { - public class Crane : BaseCreature - { - public override string CorpseName => "a bird corpse"; - public override string DefaultName => "a crane"; + public class Crane : BaseCreature + { + [Constructible] + public Crane() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 254; + BaseSoundID = 0x4D7; - [Constructible] - public Crane() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 254; - BaseSoundID = 0x4D7; + SetStr(26, 35); + SetDex(16, 25); + SetInt(11, 15); - SetStr( 26, 35 ); - SetDex( 16, 25 ); - SetInt( 11, 15 ); + SetHits(26, 35); + SetMana(0); - SetHits( 26, 35 ); - SetMana( 0 ); + SetDamage(1, 1); - SetDamage( 1, 1 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 5); - SetResistance( ResistanceType.Physical, 5, 5 ); + SetSkill(SkillName.MagicResist, 4.1, 5.0); + SetSkill(SkillName.Tactics, 10.1, 11.0); + SetSkill(SkillName.Wrestling, 10.1, 11.0); - SetSkill( SkillName.MagicResist, 4.1, 5.0 ); - SetSkill( SkillName.Tactics, 10.1, 11.0 ); - SetSkill( SkillName.Wrestling, 10.1, 11.0 ); + Fame = 0; + Karma = 200; - Fame = 0; - Karma = 200; + VirtualArmor = 5; + } - VirtualArmor = 5; - } + public Crane(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Feathers => 25; + public override string CorpseName => "a bird corpse"; + public override string DefaultName => "a crane"; + + public override int Meat => 1; + public override int Feathers => 25; - public override int GetAngerSound() - { - return 0x4D9; - } + public override int GetAngerSound() + { + return 0x4D9; + } - public override int GetIdleSound() - { - return 0x4D8; - } + public override int GetIdleSound() + { + return 0x4D8; + } - public override int GetAttackSound() - { - return 0x4D7; - } + public override int GetAttackSound() + { + return 0x4D7; + } - public override int GetHurtSound() - { - return 0x4DA; - } + public override int GetHurtSound() + { + return 0x4DA; + } - public override int GetDeathSound() - { - return 0x4D6; - } + public override int GetDeathSound() + { + return 0x4D6; + } - public Crane(Serial serial) : base(serial) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + writer.Write(0); + } - writer.Write((int) 0); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Birds/Eagle.cs b/Scripts/Mobiles/Animals/Birds/Eagle.cs index bca158f6f..1f886a4e6 100644 --- a/Scripts/Mobiles/Animals/Birds/Eagle.cs +++ b/Scripts/Mobiles/Animals/Birds/Eagle.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - public class Eagle : BaseCreature - { - public override string CorpseName => "a bird corpse"; - public override string DefaultName => "an eagle"; + public class Eagle : BaseCreature + { + [Constructible] + public Eagle() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 5; + BaseSoundID = 0x2EE; - [Constructible] - public Eagle() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 5; - BaseSoundID = 0x2EE; + SetStr(31, 47); + SetDex(36, 60); + SetInt(8, 20); - SetStr( 31, 47 ); - SetDex( 36, 60 ); - SetInt( 8, 20 ); + SetHits(20, 27); + SetMana(0); - SetHits( 20, 27 ); - SetMana( 0 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 20, 25); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 20, 25 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 15.3, 30.0); + SetSkill(SkillName.Tactics, 18.1, 37.0); + SetSkill(SkillName.Wrestling, 20.1, 30.0); - SetSkill( SkillName.MagicResist, 15.3, 30.0 ); - SetSkill( SkillName.Tactics, 18.1, 37.0 ); - SetSkill( SkillName.Wrestling, 20.1, 30.0 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + VirtualArmor = 22; - VirtualArmor = 22; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 17.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 17.1; - } + public Eagle(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override MeatType MeatType => MeatType.Bird; - public override int Feathers => 36; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; - public override bool CanFly => true; + public override string CorpseName => "a bird corpse"; + public override string DefaultName => "an eagle"; - public Eagle(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override MeatType MeatType => MeatType.Bird; + public override int Feathers => 36; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; + public override bool CanFly => true; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Birds/Phoenix.cs b/Scripts/Mobiles/Animals/Birds/Phoenix.cs index 9fce782eb..13479e0c5 100644 --- a/Scripts/Mobiles/Animals/Birds/Phoenix.cs +++ b/Scripts/Mobiles/Animals/Birds/Phoenix.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class Phoenix : BaseCreature - { - public override string CorpseName => "a phoenix corpse"; - public override string DefaultName => "a phoenix"; + public class Phoenix : BaseCreature + { + [Constructible] + public Phoenix() : base(AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 5; + Hue = 0x674; + BaseSoundID = 0x8F; - [Constructible] - public Phoenix() : base( AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 5; - Hue = 0x674; - BaseSoundID = 0x8F; + SetStr(504, 700); + SetDex(202, 300); + SetInt(504, 700); - SetStr( 504, 700 ); - SetDex( 202, 300 ); - SetInt( 504, 700 ); + SetHits(340, 383); - SetHits( 340, 383 ); + SetDamage(25); - SetDamage( 25 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Fire, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Fire, 50 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 90.2, 100.0); + SetSkill(SkillName.Magery, 90.2, 100.0); + SetSkill(SkillName.Meditation, 75.1, 100.0); + SetSkill(SkillName.MagicResist, 86.0, 135.0); + SetSkill(SkillName.Tactics, 80.1, 90.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.EvalInt, 90.2, 100.0 ); - SetSkill( SkillName.Magery, 90.2, 100.0 ); - SetSkill( SkillName.Meditation, 75.1, 100.0 ); - SetSkill( SkillName.MagicResist, 86.0, 135.0 ); - SetSkill( SkillName.Tactics, 80.1, 90.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 15000; + Karma = 0; - Fame = 15000; - Karma = 0; + VirtualArmor = 60; + } - VirtualArmor = 60; - } + public Phoenix(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a phoenix corpse"; + public override string DefaultName => "a phoenix"; - public override int Meat => 1; - public override MeatType MeatType => MeatType.Bird; - public override int Feathers => 36; - public override bool CanFly => true; + public override int Meat => 1; + public override MeatType MeatType => MeatType.Bird; + public override int Feathers => 36; + public override bool CanFly => true; - public Phoenix( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Canines/DireWolf.cs b/Scripts/Mobiles/Animals/Canines/DireWolf.cs index 54f5d2ccb..b73e82876 100644 --- a/Scripts/Mobiles/Animals/Canines/DireWolf.cs +++ b/Scripts/Mobiles/Animals/Canines/DireWolf.cs @@ -1,70 +1,70 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Direwolf" )] - public class DireWolf : BaseCreature - { - public override string CorpseName => "a dire wolf corpse"; - public override string DefaultName => "a dire wolf"; + [TypeAlias("Server.Mobiles.Direwolf")] + public class DireWolf : BaseCreature + { + [Constructible] + public DireWolf() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 23; + BaseSoundID = 0xE5; - [Constructible] - public DireWolf() : base( AIType.AI_Melee,FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 23; - BaseSoundID = 0xE5; + SetStr(96, 120); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(58, 72); + SetMana(0); - SetHits( 58, 72 ); - SetMana( 0 ); + SetDamage(11, 17); - SetDamage( 11, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 57.6, 75.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.MagicResist, 57.6, 75.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 22; - VirtualArmor = 22; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 83.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 83.1; - } + public DireWolf(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 7; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string CorpseName => "a dire wolf corpse"; + public override string DefaultName => "a dire wolf"; - public DireWolf(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 7; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Canines/GreyWolf.cs b/Scripts/Mobiles/Animals/Canines/GreyWolf.cs index 9a2a1d432..eb5f7d08a 100644 --- a/Scripts/Mobiles/Animals/Canines/GreyWolf.cs +++ b/Scripts/Mobiles/Animals/Canines/GreyWolf.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Greywolf" )] - public class GreyWolf : BaseCreature - { - public override string CorpseName => "a grey wolf corpse"; - public override string DefaultName => "a grey wolf"; + [TypeAlias("Server.Mobiles.Greywolf")] + public class GreyWolf : BaseCreature + { + [Constructible] + public GreyWolf() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(25, 27); + BaseSoundID = 0xE5; - [Constructible] - public GreyWolf() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 25, 27 ); - BaseSoundID = 0xE5; + SetStr(56, 80); + SetDex(56, 75); + SetInt(31, 55); - SetStr( 56, 80 ); - SetDex( 56, 75 ); - SetInt( 31, 55 ); + SetHits(34, 48); + SetMana(0); - SetHits( 34, 48 ); - SetMana( 0 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 20, 25); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 20, 25 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 20.1, 35.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 60.0); - SetSkill( SkillName.MagicResist, 20.1, 35.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 60.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 53.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 53.1; - } + public GreyWolf(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 6; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string CorpseName => "a grey wolf corpse"; + public override string DefaultName => "a grey wolf"; - public GreyWolf(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 6; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Canines/TimberWolf.cs b/Scripts/Mobiles/Animals/Canines/TimberWolf.cs index a5fcae1ac..621812b8e 100644 --- a/Scripts/Mobiles/Animals/Canines/TimberWolf.cs +++ b/Scripts/Mobiles/Animals/Canines/TimberWolf.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Timberwolf" )] - public class TimberWolf : BaseCreature - { - public override string CorpseName => "a timber wolf corpse"; - public override string DefaultName => "a timber wolf"; + [TypeAlias("Server.Mobiles.Timberwolf")] + public class TimberWolf : BaseCreature + { + [Constructible] + public TimberWolf() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 225; + BaseSoundID = 0xE5; - [Constructible] - public TimberWolf() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 225; - BaseSoundID = 0xE5; + SetStr(56, 80); + SetDex(56, 75); + SetInt(11, 25); - SetStr( 56, 80 ); - SetDex( 56, 75 ); - SetInt( 11, 25 ); + SetHits(34, 48); + SetMana(0); - SetHits( 34, 48 ); - SetMana( 0 ); + SetDamage(5, 9); - SetDamage( 5, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 27.6, 45.0); + SetSkill(SkillName.Tactics, 30.1, 50.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 27.6, 45.0 ); - SetSkill( SkillName.Tactics, 30.1, 50.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 23.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 23.1; - } + public TimberWolf(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 5; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string CorpseName => "a timber wolf corpse"; + public override string DefaultName => "a timber wolf"; - public TimberWolf(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 5; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Canines/WhiteWolf.cs b/Scripts/Mobiles/Animals/Canines/WhiteWolf.cs index 724fa01f0..6f76e425f 100644 --- a/Scripts/Mobiles/Animals/Canines/WhiteWolf.cs +++ b/Scripts/Mobiles/Animals/Canines/WhiteWolf.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Whitewolf" )] - public class WhiteWolf : BaseCreature - { - public override string CorpseName => "a white wolf corpse"; - public override string DefaultName => "a white wolf"; + [TypeAlias("Server.Mobiles.Whitewolf")] + public class WhiteWolf : BaseCreature + { + [Constructible] + public WhiteWolf() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(34, 37); + BaseSoundID = 0xE5; - [Constructible] - public WhiteWolf() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 34, 37 ); - BaseSoundID = 0xE5; + SetStr(56, 80); + SetDex(56, 75); + SetInt(31, 55); - SetStr( 56, 80 ); - SetDex( 56, 75 ); - SetInt( 31, 55 ); + SetHits(34, 48); + SetMana(0); - SetHits( 34, 48 ); - SetMana( 0 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 20, 25); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 20, 25 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 20.1, 35.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 60.0); - SetSkill( SkillName.MagicResist, 20.1, 35.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 60.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 65.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 65.1; - } + public WhiteWolf(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 6; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string CorpseName => "a white wolf corpse"; + public override string DefaultName => "a white wolf"; - public WhiteWolf( Serial serial ) : base( serial ) - { - } + public override int Meat => 1; + public override int Hides => 6; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Cows/Bull.cs b/Scripts/Mobiles/Animals/Cows/Bull.cs index 7a1022cea..093e92a56 100644 --- a/Scripts/Mobiles/Animals/Cows/Bull.cs +++ b/Scripts/Mobiles/Animals/Cows/Bull.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - public class Bull : BaseCreature - { - public override string CorpseName => "a bull corpse"; - public override string DefaultName => "a bull"; + public class Bull : BaseCreature + { + [Constructible] + public Bull() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(0xE8, 0xE9); + BaseSoundID = 0x64; - [Constructible] - public Bull() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 0xE8, 0xE9 ); - BaseSoundID = 0x64; + if (0.5 >= Utility.RandomDouble()) + Hue = 0x901; - if ( 0.5 >= Utility.RandomDouble() ) - Hue = 0x901; + SetStr(77, 111); + SetDex(56, 75); + SetInt(47, 75); - SetStr( 77, 111 ); - SetDex( 56, 75 ); - SetInt( 47, 75 ); + SetHits(50, 64); + SetMana(0); - SetHits( 50, 64 ); - SetMana( 0 ); + SetDamage(4, 9); - SetDamage( 4, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Cold, 10, 15); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Cold, 10, 15 ); + SetSkill(SkillName.MagicResist, 17.6, 25.0); + SetSkill(SkillName.Tactics, 67.6, 85.0); + SetSkill(SkillName.Wrestling, 40.1, 57.5); - SetSkill( SkillName.MagicResist, 17.6, 25.0 ); - SetSkill( SkillName.Tactics, 67.6, 85.0 ); - SetSkill( SkillName.Wrestling, 40.1, 57.5 ); + Fame = 600; + Karma = 0; - Fame = 600; - Karma = 0; + VirtualArmor = 28; - VirtualArmor = 28; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 71.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 71.1; - } + public Bull(Serial serial) : base(serial) + { + } - public override int Meat => 10; - public override int Hides => 15; - public override FoodType FavoriteFood => FoodType.GrainsAndHay; - public override PackInstinct PackInstinct => PackInstinct.Bull; + public override string CorpseName => "a bull corpse"; + public override string DefaultName => "a bull"; - public Bull(Serial serial) : base(serial) - { - } + public override int Meat => 10; + public override int Hides => 15; + public override FoodType FavoriteFood => FoodType.GrainsAndHay; + public override PackInstinct PackInstinct => PackInstinct.Bull; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Cows/Cow.cs b/Scripts/Mobiles/Animals/Cows/Cow.cs index f2af4649c..43d354bcf 100644 --- a/Scripts/Mobiles/Animals/Cows/Cow.cs +++ b/Scripts/Mobiles/Animals/Cows/Cow.cs @@ -2,127 +2,129 @@ using System; namespace Server.Mobiles { - public class Cow : BaseCreature - { - public override string CorpseName => "a cow corpse"; + public class Cow : BaseCreature + { + [Constructible] + public Cow() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(0xD8, 0xE7); + BaseSoundID = 0x78; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime MilkedOn { get; set; } + SetStr(30); + SetDex(15); + SetInt(5); - [CommandProperty( AccessLevel.GameMaster )] - public int Milk { get; set; } + SetHits(18); + SetMana(0); - public override string DefaultName => "a cow"; + SetDamage(1, 4); - [Constructible] - public Cow() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 0xD8, 0xE7 ); - BaseSoundID = 0x78; + SetDamage(1, 4); - SetStr( 30 ); - SetDex( 15 ); - SetInt( 5 ); + SetDamageType(ResistanceType.Physical, 100); - SetHits( 18 ); - SetMana( 0 ); + SetResistance(ResistanceType.Physical, 5, 15); - SetDamage( 1, 4 ); + SetSkill(SkillName.MagicResist, 5.5); + SetSkill(SkillName.Tactics, 5.5); + SetSkill(SkillName.Wrestling, 5.5); - SetDamage( 1, 4 ); + Fame = 300; + Karma = 0; - SetDamageType( ResistanceType.Physical, 100 ); + VirtualArmor = 10; - SetResistance( ResistanceType.Physical, 5, 15 ); + Tamable = true; + ControlSlots = 1; + MinTameSkill = 11.1; - SetSkill( SkillName.MagicResist, 5.5 ); - SetSkill( SkillName.Tactics, 5.5 ); - SetSkill( SkillName.Wrestling, 5.5 ); + if (Core.AOS && Utility.Random(1000) == 0) // 0.1% chance to have mad cows + FightMode = FightMode.Closest; + } - Fame = 300; - Karma = 0; + public Cow(Serial serial) : base(serial) + { + } - VirtualArmor = 10; + public override string CorpseName => "a cow corpse"; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 11.1; + [CommandProperty(AccessLevel.GameMaster)] + public DateTime MilkedOn{ get; set; } - if ( Core.AOS && Utility.Random( 1000 ) == 0 ) // 0.1% chance to have mad cows - FightMode = FightMode.Closest; - } + [CommandProperty(AccessLevel.GameMaster)] + public int Milk{ get; set; } - public override int Meat => 8; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string DefaultName => "a cow"; - public override void OnDoubleClick( Mobile from ) - { - base.OnDoubleClick( from ); + public override int Meat => 8; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - int random = Utility.Random( 100 ); + public override void OnDoubleClick(Mobile from) + { + base.OnDoubleClick(from); - if ( random < 5 ) - Tip(); - else if ( random < 20 ) - PlaySound( 120 ); - else if ( random < 40 ) - PlaySound( 121 ); - } + int random = Utility.Random(100); - public void Tip() - { - PlaySound( 121 ); - Animate( 8, 0, 3, true, false, 0 ); - } + if (random < 5) + Tip(); + else if (random < 20) + PlaySound(120); + else if (random < 40) + PlaySound(121); + } - public bool TryMilk( Mobile from ) - { - if ( !from.InLOS( this ) || !from.InRange( Location, 2 ) ) - from.SendLocalizedMessage( 1080400 ); // You can not milk the cow from this location. - if ( Controlled && ControlMaster != from ) - from.SendLocalizedMessage( 1071182 ); // The cow nimbly escapes your attempts to milk it. - if ( Milk == 0 && MilkedOn + TimeSpan.FromDays( 1 ) > DateTime.UtcNow ) - from.SendLocalizedMessage( 1080198 ); // This cow can not be milked now. Please wait for some time. - else - { - if ( Milk == 0 ) - Milk = 4; + public void Tip() + { + PlaySound(121); + Animate(8, 0, 3, true, false, 0); + } - MilkedOn = DateTime.UtcNow; - Milk--; + public bool TryMilk(Mobile from) + { + if (!from.InLOS(this) || !from.InRange(Location, 2)) + from.SendLocalizedMessage(1080400); // You can not milk the cow from this location. + if (Controlled && ControlMaster != from) + from.SendLocalizedMessage(1071182); // The cow nimbly escapes your attempts to milk it. + if (Milk == 0 && MilkedOn + TimeSpan.FromDays(1) > DateTime.UtcNow) + { + from.SendLocalizedMessage(1080198); // This cow can not be milked now. Please wait for some time. + } + else + { + if (Milk == 0) + Milk = 4; - return true; - } + MilkedOn = DateTime.UtcNow; + Milk--; - return false; - } + return true; + } - public Cow( Serial serial ) : base( serial ) - { - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); + writer.Write(1); - writer.Write( (DateTime) MilkedOn ); - writer.Write( (int) Milk ); - } + writer.Write(MilkedOn); + writer.Write(Milk); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version > 0 ) - { - MilkedOn = reader.ReadDateTime(); - Milk = reader.ReadInt(); - } - } - } -} + if (version > 0) + { + MilkedOn = reader.ReadDateTime(); + Milk = reader.ReadInt(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Felines/Cougar.cs b/Scripts/Mobiles/Animals/Felines/Cougar.cs index 816a9e89b..0a270af43 100644 --- a/Scripts/Mobiles/Animals/Felines/Cougar.cs +++ b/Scripts/Mobiles/Animals/Felines/Cougar.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class Cougar : BaseCreature - { - public override string CorpseName => "a cougar corpse"; - public override string DefaultName => "a cougar"; + public class Cougar : BaseCreature + { + [Constructible] + public Cougar() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 63; + BaseSoundID = 0x73; - [Constructible] - public Cougar() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 63; - BaseSoundID = 0x73; + SetStr(56, 80); + SetDex(66, 85); + SetInt(26, 50); - SetStr( 56, 80 ); - SetDex( 66, 85 ); - SetInt( 26, 50 ); + SetHits(34, 48); + SetMana(0); - SetHits( 34, 48 ); - SetMana( 0 ); + SetDamage(4, 10); - SetDamage( 4, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 15.1, 30.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 60.0); - SetSkill( SkillName.MagicResist, 15.1, 30.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 60.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 41.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 41.1; - } + public Cougar(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 10; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Feline; + public override string CorpseName => "a cougar corpse"; + public override string DefaultName => "a cougar"; - public Cougar(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 10; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Feline; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Felines/HellCat.cs b/Scripts/Mobiles/Animals/Felines/HellCat.cs index 846feddd0..cba563b2e 100644 --- a/Scripts/Mobiles/Animals/Felines/HellCat.cs +++ b/Scripts/Mobiles/Animals/Felines/HellCat.cs @@ -1,74 +1,74 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Hellcat" )] - public class HellCat : BaseCreature - { - public override string CorpseName => "a hell cat corpse"; - public override string DefaultName => "a hell cat"; + [TypeAlias("Server.Mobiles.Hellcat")] + public class HellCat : BaseCreature + { + [Constructible] + public HellCat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0xC9; + Hue = Utility.RandomList(0x647, 0x650, 0x659, 0x662, 0x66B, 0x674); + BaseSoundID = 0x69; - [Constructible] - public HellCat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0xC9; - Hue = Utility.RandomList( 0x647, 0x650, 0x659, 0x662, 0x66B, 0x674); - BaseSoundID = 0x69; + SetStr(51, 100); + SetDex(52, 150); + SetInt(13, 85); - SetStr( 51, 100 ); - SetDex( 52, 150 ); - SetInt( 13, 85 ); + SetHits(48, 67); - SetHits( 48, 67 ); + SetDamage(6, 12); - SetDamage( 6, 12 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Fire, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Fire, 60 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 80, 90); + SetResistance(ResistanceType.Energy, 15, 20); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 80, 90 ); - SetResistance( ResistanceType.Energy, 15, 20 ); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 40.1, 55.0); + SetSkill(SkillName.Wrestling, 30.1, 40.0); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 40.1, 55.0 ); - SetSkill( SkillName.Wrestling, 30.1, 40.0 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + VirtualArmor = 30; - VirtualArmor = 30; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 71.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 71.1; - } + public HellCat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a hell cat corpse"; + public override string DefaultName => "a hell cat"; - public override bool HasBreath => true; // fire breath enabled - public override int Hides => 10; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Feline; + public override bool HasBreath => true; // fire breath enabled + public override int Hides => 10; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Feline; - public HellCat(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Felines/Panther.cs b/Scripts/Mobiles/Animals/Felines/Panther.cs index f51a41fa0..6b0137afd 100644 --- a/Scripts/Mobiles/Animals/Felines/Panther.cs +++ b/Scripts/Mobiles/Animals/Felines/Panther.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - public class Panther : BaseCreature - { - public override string CorpseName => "a panther corpse"; - public override string DefaultName => "a panther"; + public class Panther : BaseCreature + { + [Constructible] + public Panther() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xD6; + Hue = 0x901; + BaseSoundID = 0x462; - [Constructible] - public Panther() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xD6; - Hue = 0x901; - BaseSoundID = 0x462; + SetStr(61, 85); + SetDex(86, 105); + SetInt(26, 50); - SetStr( 61, 85 ); - SetDex( 86, 105 ); - SetInt( 26, 50 ); + SetHits(37, 51); + SetMana(0); - SetHits( 37, 51 ); - SetMana( 0 ); + SetDamage(4, 12); - SetDamage( 4, 12 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 15.1, 30.0); + SetSkill(SkillName.Tactics, 50.1, 65.0); + SetSkill(SkillName.Wrestling, 50.1, 65.0); - SetSkill( SkillName.MagicResist, 15.1, 30.0 ); - SetSkill( SkillName.Tactics, 50.1, 65.0 ); - SetSkill( SkillName.Wrestling, 50.1, 65.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 53.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 53.1; - } + public Panther(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 10; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; - public override PackInstinct PackInstinct => PackInstinct.Feline; + public override string CorpseName => "a panther corpse"; + public override string DefaultName => "a panther"; - public Panther(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 10; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; + public override PackInstinct PackInstinct => PackInstinct.Feline; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Felines/PredatorHellCat.cs b/Scripts/Mobiles/Animals/Felines/PredatorHellCat.cs index 2d9f16030..3c88c9ff5 100644 --- a/Scripts/Mobiles/Animals/Felines/PredatorHellCat.cs +++ b/Scripts/Mobiles/Animals/Felines/PredatorHellCat.cs @@ -1,73 +1,73 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Preditorhellcat" )] - public class PredatorHellCat : BaseCreature - { - public override string CorpseName => "a hell cat corpse"; - public override string DefaultName => "a hell cat"; + [TypeAlias("Server.Mobiles.Preditorhellcat")] + public class PredatorHellCat : BaseCreature + { + [Constructible] + public PredatorHellCat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 127; + BaseSoundID = 0xBA; - [Constructible] - public PredatorHellCat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 127; - BaseSoundID = 0xBA; + SetStr(161, 185); + SetDex(96, 115); + SetInt(76, 100); - SetStr( 161, 185 ); - SetDex( 96, 115 ); - SetInt( 76, 100 ); + SetHits(97, 131); - SetHits( 97, 131 ); + SetDamage(5, 17); - SetDamage( 5, 17 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Fire, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Fire, 25 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Energy, 5, 15); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Energy, 5, 15 ); + SetSkill(SkillName.MagicResist, 75.1, 90.0); + SetSkill(SkillName.Tactics, 50.1, 65.0); + SetSkill(SkillName.Wrestling, 50.1, 65.0); - SetSkill( SkillName.MagicResist, 75.1, 90.0 ); - SetSkill( SkillName.Tactics, 50.1, 65.0 ); - SetSkill( SkillName.Wrestling, 50.1, 65.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 30; - VirtualArmor = 30; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 89.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 89.1; - } + public PredatorHellCat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a hell cat corpse"; + public override string DefaultName => "a hell cat"; - public override bool HasBreath => true; // fire breath enabled - public override int Hides => 10; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Feline; + public override bool HasBreath => true; // fire breath enabled + public override int Hides => 10; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Feline; - public PredatorHellCat(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Felines/SnowLeopard.cs b/Scripts/Mobiles/Animals/Felines/SnowLeopard.cs index a537672c6..732020e99 100644 --- a/Scripts/Mobiles/Animals/Felines/SnowLeopard.cs +++ b/Scripts/Mobiles/Animals/Felines/SnowLeopard.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Snowleopard" )] - public class SnowLeopard : BaseCreature - { - public override string CorpseName => "a leopard corpse"; - public override string DefaultName => "a snow leopard"; + [TypeAlias("Server.Mobiles.Snowleopard")] + public class SnowLeopard : BaseCreature + { + [Constructible] + public SnowLeopard() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(64, 65); + BaseSoundID = 0x73; - [Constructible] - public SnowLeopard() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 64, 65 ); - BaseSoundID = 0x73; + SetStr(56, 80); + SetDex(66, 85); + SetInt(26, 50); - SetStr( 56, 80 ); - SetDex( 66, 85 ); - SetInt( 26, 50 ); + SetHits(34, 48); + SetMana(0); - SetHits( 34, 48 ); - SetMana( 0 ); + SetDamage(3, 9); - SetDamage( 3, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 25.1, 35.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 40.1, 50.0); - SetSkill( SkillName.MagicResist, 25.1, 35.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 40.1, 50.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 53.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 53.1; - } + public SnowLeopard(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 8; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; - public override PackInstinct PackInstinct => PackInstinct.Feline; + public override string CorpseName => "a leopard corpse"; + public override string DefaultName => "a snow leopard"; - public SnowLeopard(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 8; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; + public override PackInstinct PackInstinct => PackInstinct.Feline; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Boar.cs b/Scripts/Mobiles/Animals/Misc/Boar.cs index 01dd7bc14..f40a6cdf1 100644 --- a/Scripts/Mobiles/Animals/Misc/Boar.cs +++ b/Scripts/Mobiles/Animals/Misc/Boar.cs @@ -1,64 +1,64 @@ namespace Server.Mobiles { - public class Boar : BaseCreature - { - public override string CorpseName => "a pig corpse"; - public override string DefaultName => "a boar"; + public class Boar : BaseCreature + { + [Constructible] + public Boar() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0x122; + BaseSoundID = 0xC4; - [Constructible] - public Boar() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0x122; - BaseSoundID = 0xC4; + SetStr(25); + SetDex(15); + SetInt(5); - SetStr( 25 ); - SetDex( 15 ); - SetInt( 5 ); + SetHits(15); + SetMana(0); - SetHits( 15 ); - SetMana( 0 ); + SetDamage(3, 6); - SetDamage( 3, 6 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 10, 15); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 10, 15 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 9.0); + SetSkill(SkillName.Tactics, 9.0); + SetSkill(SkillName.Wrestling, 9.0); - SetSkill( SkillName.MagicResist, 9.0 ); - SetSkill( SkillName.Tactics, 9.0 ); - SetSkill( SkillName.Wrestling, 9.0 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + VirtualArmor = 10; - VirtualArmor = 10; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + public Boar(Serial serial) : base(serial) + { + } - public override int Meat => 2; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a pig corpse"; + public override string DefaultName => "a boar"; - public Boar(Serial serial) : base(serial) - { - } + public override int Meat => 2; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/BullFrog.cs b/Scripts/Mobiles/Animals/Misc/BullFrog.cs index 844df3e28..4986e3b22 100644 --- a/Scripts/Mobiles/Animals/Misc/BullFrog.cs +++ b/Scripts/Mobiles/Animals/Misc/BullFrog.cs @@ -1,70 +1,70 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Bullfrog" )] - public class BullFrog : BaseCreature - { - public override string CorpseName => "a bull frog corpse"; - public override string DefaultName => "a bull frog"; + [TypeAlias("Server.Mobiles.Bullfrog")] + public class BullFrog : BaseCreature + { + [Constructible] + public BullFrog() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 81; + Hue = Utility.RandomList(0x5AC, 0x5A3, 0x59A, 0x591, 0x588, 0x57F); + BaseSoundID = 0x266; - [Constructible] - public BullFrog() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 81; - Hue = Utility.RandomList( 0x5AC,0x5A3,0x59A,0x591,0x588,0x57F ); - BaseSoundID = 0x266; + SetStr(46, 70); + SetDex(6, 25); + SetInt(11, 20); - SetStr( 46, 70 ); - SetDex( 6, 25 ); - SetInt( 11, 20 ); + SetHits(28, 42); + SetMana(0); - SetHits( 28, 42 ); - SetMana( 0 ); + SetDamage(1, 2); - SetDamage( 1, 2 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 40.1, 60.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 40.1, 60.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 350; + Karma = 0; - Fame = 350; - Karma = 0; + VirtualArmor = 6; - VirtualArmor = 6; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 23.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 23.1; - } + public BullFrog(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a bull frog corpse"; + public override string DefaultName => "a bull frog"; - public override int Meat => 1; - public override int Hides => 4; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat; + public override int Meat => 1; + public override int Hides => 4; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat; - public BullFrog(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Dolphin.cs b/Scripts/Mobiles/Animals/Misc/Dolphin.cs index 826b4e1e5..e8280f1d5 100644 --- a/Scripts/Mobiles/Animals/Misc/Dolphin.cs +++ b/Scripts/Mobiles/Animals/Misc/Dolphin.cs @@ -1,86 +1,86 @@ namespace Server.Mobiles { - public class Dolphin : BaseCreature - { - public override string CorpseName => "a dolphin corpse"; - public override string DefaultName => "a dolphin"; + public class Dolphin : BaseCreature + { + [Constructible] + public Dolphin() + : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0x97; + BaseSoundID = 0x8A; - [Constructible] - public Dolphin() - : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0x97; - BaseSoundID = 0x8A; + SetStr(21, 49); + SetDex(66, 85); + SetInt(96, 110); - SetStr( 21, 49 ); - SetDex( 66, 85 ); - SetInt( 96, 110 ); + SetHits(15, 27); - SetHits( 15, 27 ); + SetDamage(3, 6); - SetDamage( 3, 6 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 25, 30); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 25, 30 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.2, 29.0); + SetSkill(SkillName.Wrestling, 19.2, 29.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.2, 29.0 ); - SetSkill( SkillName.Wrestling, 19.2, 29.0 ); + Fame = 500; + Karma = 2000; - Fame = 500; - Karma = 2000; + VirtualArmor = 16; + CanSwim = true; + CantWalk = true; + } - VirtualArmor = 16; - CanSwim = true; - CantWalk = true; - } + public Dolphin(Serial serial) + : base(serial) + { + } - public override int Meat => 1; + public override string CorpseName => "a dolphin corpse"; + public override string DefaultName => "a dolphin"; - public Dolphin( Serial serial ) - : base( serial ) - { - } + public override int Meat => 1; - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - Jump(); - } + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + Jump(); + } - public virtual void Jump() - { - if ( Utility.RandomBool() ) - Animate( 3, 16, 1, true, false, 0 ); - else - Animate( 4, 20, 1, true, false, 0 ); - } + public virtual void Jump() + { + if (Utility.RandomBool()) + Animate(3, 16, 1, true, false, 0); + else + Animate(4, 20, 1, true, false, 0); + } - public override void OnThink() - { - if ( Utility.RandomDouble() < .005 ) // slim chance to jump - Jump(); + public override void OnThink() + { + if (Utility.RandomDouble() < .005) // slim chance to jump + Jump(); - base.OnThink(); - } + base.OnThink(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Gaman.cs b/Scripts/Mobiles/Animals/Misc/Gaman.cs index 78e411972..c2e761e92 100644 --- a/Scripts/Mobiles/Animals/Misc/Gaman.cs +++ b/Scripts/Mobiles/Animals/Misc/Gaman.cs @@ -2,94 +2,94 @@ using Server.Items; namespace Server.Mobiles { - public class Gaman : BaseCreature - { - public override string CorpseName => "a gaman corpse"; - public override string DefaultName => "a gaman"; + public class Gaman : BaseCreature + { + [Constructible] + public Gaman() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 248; - [Constructible] - public Gaman() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 248; + SetStr(146, 175); + SetDex(111, 150); + SetInt(46, 60); - SetStr( 146, 175 ); - SetDex( 111, 150 ); - SetInt( 46, 60 ); + SetHits(131, 160); + SetMana(0); - SetHits( 131, 160 ); - SetMana( 0 ); + SetDamage(6, 11); - SetDamage( 6, 11 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 50, 70); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 30, 50); + SetResistance(ResistanceType.Poison, 40, 60); + SetResistance(ResistanceType.Energy, 30, 50); - SetResistance( ResistanceType.Physical, 50, 70 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 30, 50 ); - SetResistance( ResistanceType.Poison, 40, 60 ); - SetResistance( ResistanceType.Energy, 30, 50 ); + SetSkill(SkillName.MagicResist, 37.6, 42.5); + SetSkill(SkillName.Tactics, 70.6, 83.0); + SetSkill(SkillName.Wrestling, 50.1, 57.5); - SetSkill( SkillName.MagicResist, 37.6, 42.5 ); - SetSkill( SkillName.Tactics, 70.6, 83.0 ); - SetSkill( SkillName.Wrestling, 50.1, 57.5 ); + Fame = 2000; + Karma = -2000; - Fame = 2000; - Karma = -2000; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 68.7; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 68.7; - } + public Gaman(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x4F8; - } + public override string CorpseName => "a gaman corpse"; + public override string DefaultName => "a gaman"; - public override int GetIdleSound() - { - return 0x4F7; - } + public override int Meat => 10; + public override int Hides => 15; + public override FoodType FavoriteFood => FoodType.GrainsAndHay; - public override int GetAttackSound() - { - return 0x4F6; - } + public override int GetAngerSound() + { + return 0x4F8; + } - public override int GetHurtSound() - { - return 0x4F9; - } + public override int GetIdleSound() + { + return 0x4F7; + } - public override int GetDeathSound() - { - return 0x4F5; - } + public override int GetAttackSound() + { + return 0x4F6; + } - public override int Meat => 10; - public override int Hides => 15; - public override FoodType FavoriteFood => FoodType.GrainsAndHay; + public override int GetHurtSound() + { + return 0x4F9; + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); - c.DropItem( new GamanHorns( Utility.RandomBool() ? 1 : 2 ) ); - } + public override int GetDeathSound() + { + return 0x4F5; + } - public Gaman( Serial serial ) : base( serial ) - { - } + public override void OnDeath(Container c) + { + base.OnDeath(c); + c.DropItem(new GamanHorns(Utility.RandomBool() ? 1 : 2)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/GiantToad.cs b/Scripts/Mobiles/Animals/Misc/GiantToad.cs index 1e1048d25..b473dc6ac 100644 --- a/Scripts/Mobiles/Animals/Misc/GiantToad.cs +++ b/Scripts/Mobiles/Animals/Misc/GiantToad.cs @@ -1,76 +1,76 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Gianttoad" )] - public class GiantToad : BaseCreature - { - public override string CorpseName => "a giant toad corpse"; - public override string DefaultName => "a giant toad"; + [TypeAlias("Server.Mobiles.Gianttoad")] + public class GiantToad : BaseCreature + { + [Constructible] + public GiantToad() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 80; + BaseSoundID = 0x26B; - [Constructible] - public GiantToad() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 80; - BaseSoundID = 0x26B; + SetStr(76, 100); + SetDex(6, 25); + SetInt(11, 20); - SetStr( 76, 100 ); - SetDex( 6, 25 ); - SetInt( 11, 20 ); + SetHits(46, 60); + SetMana(0); - SetHits( 46, 60 ); - SetMana( 0 ); + SetDamage(5, 17); - SetDamage( 5, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 40.1, 60.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 40.1, 60.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 750; + Karma = -750; - Fame = 750; - Karma = -750; + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 77.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 77.1; - } + public GiantToad(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a giant toad corpse"; + public override string DefaultName => "a giant toad"; - public override int Hides => 12; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat; + public override int Hides => 12; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat; - public GiantToad(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 1); - } + writer.Write(1); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - if ( version < 1 ) - { - AI = AIType.AI_Melee; - FightMode = FightMode.Closest; - } - } - } -} + int version = reader.ReadInt(); + if (version < 1) + { + AI = AIType.AI_Melee; + FightMode = FightMode.Closest; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Goat.cs b/Scripts/Mobiles/Animals/Misc/Goat.cs index 5477e7af1..0c8958322 100644 --- a/Scripts/Mobiles/Animals/Misc/Goat.cs +++ b/Scripts/Mobiles/Animals/Misc/Goat.cs @@ -1,63 +1,63 @@ namespace Server.Mobiles { - public class Goat : BaseCreature - { - public override string CorpseName => "a goat corpse"; - public override string DefaultName => "a goat"; + public class Goat : BaseCreature + { + [Constructible] + public Goat() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xD1; + BaseSoundID = 0x99; - [Constructible] - public Goat() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xD1; - BaseSoundID = 0x99; + SetStr(19); + SetDex(15); + SetInt(5); - SetStr( 19 ); - SetDex( 15 ); - SetInt( 5 ); + SetHits(12); + SetMana(0); - SetHits( 12 ); - SetMana( 0 ); + SetDamage(3, 4); - SetDamage( 3, 4 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 15); - SetResistance( ResistanceType.Physical, 5, 15 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 150; + Karma = 0; - Fame = 150; - Karma = 0; + VirtualArmor = 10; - VirtualArmor = 10; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 11.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 11.1; - } + public Goat(Serial serial) : base(serial) + { + } - public override int Meat => 2; - public override int Hides => 8; - public override FoodType FavoriteFood => FoodType.GrainsAndHay | FoodType.FruitsAndVegies; + public override string CorpseName => "a goat corpse"; + public override string DefaultName => "a goat"; - public Goat(Serial serial) : base(serial) - { - } + public override int Meat => 2; + public override int Hides => 8; + public override FoodType FavoriteFood => FoodType.GrainsAndHay | FoodType.FruitsAndVegies; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Gorilla.cs b/Scripts/Mobiles/Animals/Misc/Gorilla.cs index b23d606ac..216a76446 100644 --- a/Scripts/Mobiles/Animals/Misc/Gorilla.cs +++ b/Scripts/Mobiles/Animals/Misc/Gorilla.cs @@ -1,65 +1,65 @@ namespace Server.Mobiles { - public class Gorilla : BaseCreature - { - public override string CorpseName => "a gorilla corpse"; - public override string DefaultName => "a gorilla"; + public class Gorilla : BaseCreature + { + [Constructible] + public Gorilla() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0x1D; + BaseSoundID = 0x9E; - [Constructible] - public Gorilla() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0x1D; - BaseSoundID = 0x9E; + SetStr(53, 95); + SetDex(36, 55); + SetInt(36, 60); - SetStr( 53, 95 ); - SetDex( 36, 55 ); - SetInt( 36, 60 ); + SetHits(38, 51); + SetMana(0); - SetHits( 38, 51 ); - SetMana( 0 ); + SetDamage(4, 10); - SetDamage( 4, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 10, 15); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 15 ); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 43.3, 58.0); + SetSkill(SkillName.Wrestling, 43.3, 58.0); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 43.3, 58.0 ); - SetSkill( SkillName.Wrestling, 43.3, 58.0 ); + Fame = 450; + Karma = 0; - Fame = 450; - Karma = 0; + VirtualArmor = 20; - VirtualArmor = 20; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -18.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -18.9; - } + public Gorilla(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 6; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a gorilla corpse"; + public override string DefaultName => "a gorilla"; - public Gorilla(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 6; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/GreatHart.cs b/Scripts/Mobiles/Animals/Misc/GreatHart.cs index 76885dfee..a7756ffd0 100644 --- a/Scripts/Mobiles/Animals/Misc/GreatHart.cs +++ b/Scripts/Mobiles/Animals/Misc/GreatHart.cs @@ -1,79 +1,79 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Greathart" )] - public class GreatHart : BaseCreature - { - public override string CorpseName => "a deer corpse"; - public override string DefaultName => "a great hart"; + [TypeAlias("Server.Mobiles.Greathart")] + public class GreatHart : BaseCreature + { + [Constructible] + public GreatHart() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xEA; - [Constructible] - public GreatHart() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xEA; + SetStr(41, 71); + SetDex(47, 77); + SetInt(27, 57); - SetStr( 41, 71 ); - SetDex( 47, 77 ); - SetInt( 27, 57 ); + SetHits(27, 41); + SetMana(0); - SetHits( 27, 41 ); - SetMana( 0 ); + SetDamage(5, 9); - SetDamage( 5, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Cold, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Cold, 5, 10 ); + SetSkill(SkillName.MagicResist, 26.8, 44.5); + SetSkill(SkillName.Tactics, 29.8, 47.5); + SetSkill(SkillName.Wrestling, 29.8, 47.5); - SetSkill( SkillName.MagicResist, 26.8, 44.5 ); - SetSkill( SkillName.Tactics, 29.8, 47.5 ); - SetSkill( SkillName.Wrestling, 29.8, 47.5 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 59.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 59.1; - } + public GreatHart(Serial serial) : base(serial) + { + } - public override int Meat => 6; - public override int Hides => 15; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a deer corpse"; + public override string DefaultName => "a great hart"; - public GreatHart(Serial serial) : base(serial) - { - } + public override int Meat => 6; + public override int Hides => 15; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override int GetAttackSound() - { - return 0x82; - } + public override int GetAttackSound() + { + return 0x82; + } - public override int GetHurtSound() - { - return 0x83; - } + public override int GetHurtSound() + { + return 0x83; + } - public override int GetDeathSound() - { - return 0x84; - } + public override int GetDeathSound() + { + return 0x84; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Hind.cs b/Scripts/Mobiles/Animals/Misc/Hind.cs index f56fe5a3c..55a604cc4 100644 --- a/Scripts/Mobiles/Animals/Misc/Hind.cs +++ b/Scripts/Mobiles/Animals/Misc/Hind.cs @@ -1,78 +1,78 @@ namespace Server.Mobiles { - public class Hind : BaseCreature - { - public override string CorpseName => "a deer corpse"; - public override string DefaultName => "a hind"; + public class Hind : BaseCreature + { + [Constructible] + public Hind() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xED; - [Constructible] - public Hind() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xED; + SetStr(21, 51); + SetDex(47, 77); + SetInt(17, 47); - SetStr( 21, 51 ); - SetDex( 47, 77 ); - SetInt( 17, 47 ); + SetHits(15, 29); + SetMana(0); - SetHits( 15, 29 ); - SetMana( 0 ); + SetDamage(4); - SetDamage( 4 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 15); + SetResistance(ResistanceType.Cold, 5); - SetResistance( ResistanceType.Physical, 5, 15 ); - SetResistance( ResistanceType.Cold, 5 ); + SetSkill(SkillName.MagicResist, 15.0); + SetSkill(SkillName.Tactics, 19.0); + SetSkill(SkillName.Wrestling, 26.0); - SetSkill( SkillName.MagicResist, 15.0 ); - SetSkill( SkillName.Tactics, 19.0 ); - SetSkill( SkillName.Wrestling, 26.0 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + VirtualArmor = 8; - VirtualArmor = 8; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 23.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 23.1; - } + public Hind(Serial serial) : base(serial) + { + } - public override int Meat => 5; - public override int Hides => 8; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a deer corpse"; + public override string DefaultName => "a hind"; - public Hind(Serial serial) : base(serial) - { - } + public override int Meat => 5; + public override int Hides => 8; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override int GetAttackSound() - { - return 0x82; - } + public override int GetAttackSound() + { + return 0x82; + } - public override int GetHurtSound() - { - return 0x83; - } + public override int GetHurtSound() + { + return 0x83; + } - public override int GetDeathSound() - { - return 0x84; - } + public override int GetDeathSound() + { + return 0x84; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Llama.cs b/Scripts/Mobiles/Animals/Misc/Llama.cs index 0eda4349c..609c9e02d 100644 --- a/Scripts/Mobiles/Animals/Misc/Llama.cs +++ b/Scripts/Mobiles/Animals/Misc/Llama.cs @@ -1,63 +1,63 @@ namespace Server.Mobiles { - public class Llama : BaseCreature - { - public override string CorpseName => "a llama corpse"; - public override string DefaultName => "a llama"; + public class Llama : BaseCreature + { + [Constructible] + public Llama() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xDC; + BaseSoundID = 0x3F3; - [Constructible] - public Llama() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xDC; - BaseSoundID = 0x3F3; + SetStr(21, 49); + SetDex(36, 55); + SetInt(16, 30); - SetStr( 21, 49 ); - SetDex( 36, 55 ); - SetInt( 16, 30 ); + SetHits(15, 27); + SetMana(0); - SetHits( 15, 27 ); - SetMana( 0 ); + SetDamage(3, 5); - SetDamage( 3, 5 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); - SetResistance( ResistanceType.Physical, 15, 20 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.2, 29.0); + SetSkill(SkillName.Wrestling, 19.2, 29.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.2, 29.0 ); - SetSkill( SkillName.Wrestling, 19.2, 29.0 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 35.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 35.1; - } + public Llama(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a llama corpse"; + public override string DefaultName => "a llama"; - public Llama(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/MountainGoat.cs b/Scripts/Mobiles/Animals/Misc/MountainGoat.cs index a5b546490..8f5ef1e04 100644 --- a/Scripts/Mobiles/Animals/Misc/MountainGoat.cs +++ b/Scripts/Mobiles/Animals/Misc/MountainGoat.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class MountainGoat : BaseCreature - { - public override string CorpseName => "a mountain goat corpse"; - public override string DefaultName => "a mountain goat"; + public class MountainGoat : BaseCreature + { + [Constructible] + public MountainGoat() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 88; + BaseSoundID = 0x99; - [Constructible] - public MountainGoat() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 88; - BaseSoundID = 0x99; + SetStr(22, 64); + SetDex(56, 75); + SetInt(16, 30); - SetStr( 22, 64 ); - SetDex( 56, 75 ); - SetInt( 16, 30 ); + SetHits(20, 33); + SetMana(0); - SetHits( 20, 33 ); - SetMana( 0 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 10, 20); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 10, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + VirtualArmor = 10; - VirtualArmor = 10; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -0.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -0.9; - } + public MountainGoat(Serial serial) : base(serial) + { + } - public override int Meat => 2; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.GrainsAndHay | FoodType.FruitsAndVegies; + public override string CorpseName => "a mountain goat corpse"; + public override string DefaultName => "a mountain goat"; - public MountainGoat(Serial serial) : base(serial) - { - } + public override int Meat => 2; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.GrainsAndHay | FoodType.FruitsAndVegies; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/PackHorse.cs b/Scripts/Mobiles/Animals/Misc/PackHorse.cs index 3d499a5fc..e6d7c0f12 100644 --- a/Scripts/Mobiles/Animals/Misc/PackHorse.cs +++ b/Scripts/Mobiles/Animals/Misc/PackHorse.cs @@ -1,219 +1,222 @@ using System.Collections.Generic; -using Server.Items; using Server.ContextMenus; +using Server.Items; namespace Server.Mobiles { - public class PackHorse : BaseCreature - { - public override string CorpseName => "a horse corpse"; - public override string DefaultName => "a pack horse"; + public class PackHorse : BaseCreature + { + [Constructible] + public PackHorse() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 291; + BaseSoundID = 0xA8; - [Constructible] - public PackHorse() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 291; - BaseSoundID = 0xA8; + SetStr(44, 120); + SetDex(36, 55); + SetInt(6, 10); - SetStr( 44, 120 ); - SetDex( 36, 55 ); - SetInt( 6, 10 ); + SetHits(61, 80); + SetStam(81, 100); + SetMana(0); - SetHits( 61, 80 ); - SetStam( 81, 100 ); - SetMana( 0 ); + SetDamage(5, 11); - SetDamage( 5, 11 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 20, 25); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 20, 25 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + Fame = 0; + Karma = 200; - Fame = 0; - Karma = 200; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 11.1; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 11.1; + Container pack = Backpack; - Container pack = Backpack; + pack?.Delete(); - pack?.Delete(); + pack = new StrongBackpack(); + pack.Movable = false; - pack = new StrongBackpack(); - pack.Movable = false; + AddItem(pack); + } - AddItem( pack ); - } + public PackHorse(Serial serial) : base(serial) + { + } - public override int Meat => 3; - public override int Hides => 10; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a horse corpse"; + public override string DefaultName => "a pack horse"; - public PackHorse( Serial serial ) : base( serial ) - { - } + public override int Meat => 3; + public override int Hides => 10; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - #region Pack Animal Methods - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - PackAnimal.CombineBackpacks( this ); + writer.Write(0); + } - return true; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override DeathMoveResult GetInventoryMoveResultFor( Item item ) - { - return DeathMoveResult.MoveToCorpse; - } + int version = reader.ReadInt(); + } - public override bool IsSnoop( Mobile from ) - { - if ( PackAnimal.CheckAccess( this, from ) ) - return false; + #region Pack Animal Methods - return base.IsSnoop( from ); - } + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - public override bool OnDragDrop( Mobile from, Item item ) - { - if ( CheckFeed( from, item ) ) - return true; + PackAnimal.CombineBackpacks(this); - if ( PackAnimal.CheckAccess( this, from ) ) - { - AddToBackpack( item ); - return true; - } + return true; + } - return base.OnDragDrop( from, item ); - } + public override DeathMoveResult GetInventoryMoveResultFor(Item item) + { + return DeathMoveResult.MoveToCorpse; + } - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - return PackAnimal.CheckAccess( this, from ); - } + public override bool IsSnoop(Mobile from) + { + if (PackAnimal.CheckAccess(this, from)) + return false; - public override bool CheckNonlocalLift( Mobile from, Item item ) - { - return PackAnimal.CheckAccess( this, from ); - } + return base.IsSnoop(from); + } - public override void OnDoubleClick( Mobile from ) - { - PackAnimal.TryPackOpen( this, from ); - } + public override bool OnDragDrop(Mobile from, Item item) + { + if (CheckFeed(from, item)) + return true; - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (PackAnimal.CheckAccess(this, from)) + { + AddToBackpack(item); + return true; + } - PackAnimal.GetContextMenuEntries( this, from, list ); - } - #endregion + return base.OnDragDrop(from, item); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + return PackAnimal.CheckAccess(this, from); + } - writer.Write( (int) 0 ); - } + public override bool CheckNonlocalLift(Mobile from, Item item) + { + return PackAnimal.CheckAccess(this, from); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnDoubleClick(Mobile from) + { + PackAnimal.TryPackOpen(this, from); + } - int version = reader.ReadInt(); - } - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public class PackAnimalBackpackEntry : ContextMenuEntry - { - private BaseCreature m_Animal; - private Mobile m_From; + PackAnimal.GetContextMenuEntries(this, from, list); + } - public PackAnimalBackpackEntry( BaseCreature animal, Mobile from ) : base( 6145, 3 ) - { - m_Animal = animal; - m_From = from; + #endregion + } - if ( animal.IsDeadPet ) - Enabled = false; - } + public class PackAnimalBackpackEntry : ContextMenuEntry + { + private BaseCreature m_Animal; + private Mobile m_From; - public override void OnClick() - { - PackAnimal.TryPackOpen( m_Animal, m_From ); - } - } + public PackAnimalBackpackEntry(BaseCreature animal, Mobile from) : base(6145, 3) + { + m_Animal = animal; + m_From = from; - public class PackAnimal - { - public static void GetContextMenuEntries( BaseCreature animal, Mobile from, List list ) - { - if ( CheckAccess( animal, from ) ) - list.Add( new PackAnimalBackpackEntry( animal, from ) ); - } + if (animal.IsDeadPet) + Enabled = false; + } - public static bool CheckAccess( BaseCreature animal, Mobile from ) - { - if ( from == animal || from.AccessLevel >= AccessLevel.GameMaster ) - return true; + public override void OnClick() + { + PackAnimal.TryPackOpen(m_Animal, m_From); + } + } - if ( from.Alive && animal.Controlled && !animal.IsDeadPet && ( from == animal.ControlMaster || from == animal.SummonMaster || animal.IsPetFriend( from ) ) ) - return true; + public class PackAnimal + { + public static void GetContextMenuEntries(BaseCreature animal, Mobile from, List list) + { + if (CheckAccess(animal, from)) + list.Add(new PackAnimalBackpackEntry(animal, from)); + } - return false; - } + public static bool CheckAccess(BaseCreature animal, Mobile from) + { + if (from == animal || from.AccessLevel >= AccessLevel.GameMaster) + return true; - public static void CombineBackpacks( BaseCreature animal ) - { - if ( Core.AOS ) - return; + if (from.Alive && animal.Controlled && !animal.IsDeadPet && + (from == animal.ControlMaster || from == animal.SummonMaster || animal.IsPetFriend(from))) + return true; - if ( animal.IsBonded || animal.IsDeadPet ) - return; + return false; + } - Container pack = animal.Backpack; + public static void CombineBackpacks(BaseCreature animal) + { + if (Core.AOS) + return; - if ( pack != null ) - { - Container newPack = new Backpack(); + if (animal.IsBonded || animal.IsDeadPet) + return; - for ( int i = pack.Items.Count - 1; i >= 0; --i ) - { - if ( i >= pack.Items.Count ) - continue; + Container pack = animal.Backpack; - newPack.DropItem( pack.Items[i] ); - } + if (pack != null) + { + Container newPack = new Backpack(); - pack.DropItem( newPack ); - } - } + for (int i = pack.Items.Count - 1; i >= 0; --i) + { + if (i >= pack.Items.Count) + continue; - public static void TryPackOpen( BaseCreature animal, Mobile from ) - { - if ( animal.IsDeadPet ) - return; + newPack.DropItem(pack.Items[i]); + } - Container item = animal.Backpack; + pack.DropItem(newPack); + } + } - if ( item != null ) - from.Use( item ); - } - } -} + public static void TryPackOpen(BaseCreature animal, Mobile from) + { + if (animal.IsDeadPet) + return; + + Container item = animal.Backpack; + + if (item != null) + from.Use(item); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/PackLlama.cs b/Scripts/Mobiles/Animals/Misc/PackLlama.cs index 8e0f3058c..8239aedc4 100644 --- a/Scripts/Mobiles/Animals/Misc/PackLlama.cs +++ b/Scripts/Mobiles/Animals/Misc/PackLlama.cs @@ -1,141 +1,143 @@ using System.Collections.Generic; -using Server.Items; using Server.ContextMenus; +using Server.Items; namespace Server.Mobiles { - public class PackLlama : BaseCreature - { - public override string CorpseName => "a llama corpse"; - public override string DefaultName => "a pack llama"; + public class PackLlama : BaseCreature + { + [Constructible] + public PackLlama() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 292; + BaseSoundID = 0x3F3; - [Constructible] - public PackLlama() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 292; - BaseSoundID = 0x3F3; + SetStr(52, 80); + SetDex(36, 55); + SetInt(16, 30); - SetStr( 52, 80 ); - SetDex( 36, 55 ); - SetInt( 16, 30 ); + SetHits(50); + SetStam(86, 105); + SetMana(0); - SetHits( 50 ); - SetStam( 86, 105 ); - SetMana( 0 ); + SetDamage(2, 6); - SetDamage( 2, 6 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.2, 29.0); + SetSkill(SkillName.Wrestling, 19.2, 29.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.2, 29.0 ); - SetSkill( SkillName.Wrestling, 19.2, 29.0 ); + Fame = 0; + Karma = 200; - Fame = 0; - Karma = 200; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 11.1; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 11.1; + Container pack = Backpack; - Container pack = Backpack; + pack?.Delete(); - pack?.Delete(); + pack = new StrongBackpack(); + pack.Movable = false; - pack = new StrongBackpack(); - pack.Movable = false; + AddItem(pack); + } - AddItem( pack ); - } + public PackLlama(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a llama corpse"; + public override string DefaultName => "a pack llama"; - public PackLlama( Serial serial ) : base( serial ) - { - } + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - #region Pack Animal Methods - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - PackAnimal.CombineBackpacks( this ); + writer.Write(0); + } - return true; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override DeathMoveResult GetInventoryMoveResultFor( Item item ) - { - return DeathMoveResult.MoveToCorpse; - } + int version = reader.ReadInt(); + } - public override bool IsSnoop( Mobile from ) - { - if ( PackAnimal.CheckAccess( this, from ) ) - return false; + #region Pack Animal Methods - return base.IsSnoop( from ); - } + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - public override bool OnDragDrop( Mobile from, Item item ) - { - if ( CheckFeed( from, item ) ) - return true; + PackAnimal.CombineBackpacks(this); - if ( PackAnimal.CheckAccess( this, from ) ) - { - AddToBackpack( item ); - return true; - } + return true; + } - return base.OnDragDrop( from, item ); - } + public override DeathMoveResult GetInventoryMoveResultFor(Item item) + { + return DeathMoveResult.MoveToCorpse; + } - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - return PackAnimal.CheckAccess( this, from ); - } + public override bool IsSnoop(Mobile from) + { + if (PackAnimal.CheckAccess(this, from)) + return false; - public override bool CheckNonlocalLift( Mobile from, Item item ) - { - return PackAnimal.CheckAccess( this, from ); - } + return base.IsSnoop(from); + } - public override void OnDoubleClick( Mobile from ) - { - PackAnimal.TryPackOpen( this, from ); - } + public override bool OnDragDrop(Mobile from, Item item) + { + if (CheckFeed(from, item)) + return true; - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (PackAnimal.CheckAccess(this, from)) + { + AddToBackpack(item); + return true; + } - PackAnimal.GetContextMenuEntries( this, from, list ); - } - #endregion + return base.OnDragDrop(from, item); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + return PackAnimal.CheckAccess(this, from); + } - writer.Write( (int) 0 ); - } + public override bool CheckNonlocalLift(Mobile from, Item item) + { + return PackAnimal.CheckAccess(this, from); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnDoubleClick(Mobile from) + { + PackAnimal.TryPackOpen(this, from); + } - int version = reader.ReadInt(); - } - } -} + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + PackAnimal.GetContextMenuEntries(this, from, list); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Pig.cs b/Scripts/Mobiles/Animals/Misc/Pig.cs index c802cc698..ccc38dfeb 100644 --- a/Scripts/Mobiles/Animals/Misc/Pig.cs +++ b/Scripts/Mobiles/Animals/Misc/Pig.cs @@ -1,62 +1,62 @@ namespace Server.Mobiles { - public class Pig : BaseCreature - { - public override string CorpseName => "a pig corpse"; - public override string DefaultName => "a pig"; + public class Pig : BaseCreature + { + [Constructible] + public Pig() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xCB; + BaseSoundID = 0xC4; - [Constructible] - public Pig() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xCB; - BaseSoundID = 0xC4; + SetStr(20); + SetDex(20); + SetInt(5); - SetStr( 20 ); - SetDex( 20 ); - SetInt( 5 ); + SetHits(12); + SetMana(0); - SetHits( 12 ); - SetMana( 0 ); + SetDamage(2, 4); - SetDamage( 2, 4 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 10, 15); - SetResistance( ResistanceType.Physical, 10, 15 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 150; + Karma = 0; - Fame = 150; - Karma = 0; + VirtualArmor = 12; - VirtualArmor = 12; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 11.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 11.1; - } + public Pig(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a pig corpse"; + public override string DefaultName => "a pig"; - public Pig(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Sheep.cs b/Scripts/Mobiles/Animals/Misc/Sheep.cs index 378d13b00..98afa212e 100644 --- a/Scripts/Mobiles/Animals/Misc/Sheep.cs +++ b/Scripts/Mobiles/Animals/Misc/Sheep.cs @@ -4,107 +4,112 @@ using Server.Network; namespace Server.Mobiles { - public class Sheep : BaseCreature, ICarvable - { - public override string CorpseName => "a sheep corpse"; - private DateTime m_NextWoolTime; + public class Sheep : BaseCreature, ICarvable + { + private DateTime m_NextWoolTime; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextWoolTime - { - get => m_NextWoolTime; - set{ m_NextWoolTime = value; Body = ( DateTime.UtcNow >= m_NextWoolTime ) ? 0xCF : 0xDF; } - } + [Constructible] + public Sheep() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xCF; + BaseSoundID = 0xD6; - public void Carve( Mobile from, Item item ) - { - if ( DateTime.UtcNow < m_NextWoolTime ) - { - // This sheep is not yet ready to be shorn. - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500449, from.NetState ); - return; - } + SetStr(19); + SetDex(25); + SetInt(5); - from.SendLocalizedMessage( 500452 ); // You place the gathered wool into your backpack. - from.AddToBackpack( new Wool( Map == Map.Felucca ? 2 : 1 ) ); + SetHits(12); + SetMana(0); - NextWoolTime = DateTime.UtcNow + TimeSpan.FromHours( 3.0 ); // TODO: Proper time delay - } + SetDamage(1, 2); - public override void OnThink() - { - base.OnThink(); - Body = ( DateTime.UtcNow >= m_NextWoolTime ) ? 0xCF : 0xDF; - } + SetDamageType(ResistanceType.Physical, 100); - public override string DefaultName => "a sheep"; + SetResistance(ResistanceType.Physical, 5, 10); - [Constructible] - public Sheep() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xCF; - BaseSoundID = 0xD6; + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 6.0); + SetSkill(SkillName.Wrestling, 5.0); - SetStr( 19 ); - SetDex( 25 ); - SetInt( 5 ); + Fame = 300; + Karma = 0; - SetHits( 12 ); - SetMana( 0 ); + VirtualArmor = 6; - SetDamage( 1, 2 ); + Tamable = true; + ControlSlots = 1; + MinTameSkill = 11.1; + } - SetDamageType( ResistanceType.Physical, 100 ); + public Sheep(Serial serial) : base(serial) + { + } - SetResistance( ResistanceType.Physical, 5, 10 ); + public override string CorpseName => "a sheep corpse"; - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 6.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextWoolTime + { + get => m_NextWoolTime; + set + { + m_NextWoolTime = value; + Body = DateTime.UtcNow >= m_NextWoolTime ? 0xCF : 0xDF; + } + } - Fame = 300; - Karma = 0; + public override string DefaultName => "a sheep"; - VirtualArmor = 6; + public override int Meat => 3; + public override MeatType MeatType => MeatType.LambLeg; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 11.1; - } + public override int Wool => Body == 0xCF ? 3 : 0; - public override int Meat => 3; - public override MeatType MeatType => MeatType.LambLeg; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public void Carve(Mobile from, Item item) + { + if (DateTime.UtcNow < m_NextWoolTime) + { + // This sheep is not yet ready to be shorn. + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500449, from.NetState); + return; + } - public override int Wool => (Body == 0xCF ? 3 : 0); + from.SendLocalizedMessage(500452); // You place the gathered wool into your backpack. + from.AddToBackpack(new Wool(Map == Map.Felucca ? 2 : 1)); - public Sheep( Serial serial ) : base( serial ) - { - } + NextWoolTime = DateTime.UtcNow + TimeSpan.FromHours(3.0); // TODO: Proper time delay + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnThink() + { + base.OnThink(); + Body = DateTime.UtcNow >= m_NextWoolTime ? 0xCF : 0xDF; + } - writer.Write( (int) 1 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteDeltaTime( m_NextWoolTime ); - } + writer.Write(1); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteDeltaTime(m_NextWoolTime); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - { - NextWoolTime = reader.ReadDeltaTime(); - break; - } - } - } - } -} + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + NextWoolTime = reader.ReadDeltaTime(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Misc/Walrus.cs b/Scripts/Mobiles/Animals/Misc/Walrus.cs index 23107aefa..55661e020 100644 --- a/Scripts/Mobiles/Animals/Misc/Walrus.cs +++ b/Scripts/Mobiles/Animals/Misc/Walrus.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class Walrus : BaseCreature - { - public override string CorpseName => "a walrus corpse"; - public override string DefaultName => "a walrus"; + public class Walrus : BaseCreature + { + [Constructible] + public Walrus() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xDD; + BaseSoundID = 0xE0; - [Constructible] - public Walrus() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xDD; - BaseSoundID = 0xE0; + SetStr(21, 29); + SetDex(46, 55); + SetInt(16, 20); - SetStr( 21, 29 ); - SetDex( 46, 55 ); - SetInt( 16, 20 ); + SetHits(14, 17); + SetMana(0); - SetHits( 14, 17 ); - SetMana( 0 ); + SetDamage(4, 10); - SetDamage( 4, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 20, 25); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 20, 25 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.2, 29.0); + SetSkill(SkillName.Wrestling, 19.2, 29.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.2, 29.0 ); - SetSkill( SkillName.Wrestling, 19.2, 29.0 ); + Fame = 150; + Karma = 0; - Fame = 150; - Karma = 0; + VirtualArmor = 18; - VirtualArmor = 18; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 35.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 35.1; - } + public Walrus(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.Fish; + public override string CorpseName => "a walrus corpse"; + public override string DefaultName => "a walrus"; - public Walrus(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.Fish; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/BaseMount.cs b/Scripts/Mobiles/Animals/Mounts/BaseMount.cs index 97a4c959b..d5deaa511 100644 --- a/Scripts/Mobiles/Animals/Mounts/BaseMount.cs +++ b/Scripts/Mobiles/Animals/Mounts/BaseMount.cs @@ -1,358 +1,354 @@ using System; using Server.Items; +using Server.Multis; +using Server.Network; using Server.Targeting; namespace Server.Mobiles { - public abstract class BaseMount : BaseCreature, IMount - { - private Mobile m_Rider; - - public virtual TimeSpan MountAbilityDelay => TimeSpan.Zero; - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextMountAbility { get; set; } - - protected Item InternalItem { get; private set; } - - public virtual bool AllowMaleRider => true; - public virtual bool AllowFemaleRider => true; - - public BaseMount( string name, int bodyID, int itemID, AIType aiType, FightMode fightMode, int rangePerception, int rangeFight, double activeSpeed, double passiveSpeed ) : base ( aiType, fightMode, rangePerception, rangeFight, activeSpeed, passiveSpeed ) - { - Name = name; - Body = bodyID; - - InternalItem = new MountItem( this, itemID ); - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public override int Hue - { - get => base.Hue; - set - { - base.Hue = value; - - if ( InternalItem != null ) - InternalItem.Hue = value; - } - } - - public override bool OnBeforeDeath() - { - Rider = null; - - return base.OnBeforeDeath(); - } - - public override void OnAfterDelete() - { - InternalItem?.Delete(); - InternalItem = null; - - base.OnAfterDelete(); - } - - public override void OnDelete() - { - Rider = null; - - base.OnDelete(); - } - - public BaseMount( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( ( int )1 ); // version - - writer.Write( NextMountAbility ); - - writer.Write( m_Rider ); - writer.Write( InternalItem ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - NextMountAbility = reader.ReadDateTime(); - goto case 0; - } - case 0: - { - m_Rider = reader.ReadMobile(); - InternalItem = reader.ReadItem(); - - if ( InternalItem == null ) - Delete(); - - break; - } - } - } - - public virtual void OnDisallowedRider( Mobile m ) - { - m.SendMessage( "You may not ride this creature." ); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsDeadPet ) - return; - - if ( from.IsBodyMod && !from.Body.IsHuman ) - { - if ( Core.AOS ) // You cannot ride a mount in your current form. - PrivateOverheadMessage( Network.MessageType.Regular, 0x3B2, 1062061, from.NetState ); - else - from.SendLocalizedMessage( 1061628 ); // You can't do that while polymorphed. - - return; - } - - if ( !CheckMountAllowed( from ) ) - return; - - if ( from.Mounted ) - { - from.SendLocalizedMessage( 1005583 ); // Please dismount first. - return; - } - - if ( from.Female ? !AllowFemaleRider : !AllowMaleRider ) - { - OnDisallowedRider( from ); - return; - } - - if ( !Multis.DesignContext.Check( from ) ) - return; - - if ( from.HasTrade ) - { - from.SendLocalizedMessage( 1042317, "", 0x41 ); // You may not ride at this time - return; - } - - if ( from.InRange( this, 1 ) ) - { - bool canAccess = ( from.AccessLevel >= AccessLevel.GameMaster ) - || ( Controlled && ControlMaster == from ) - || ( Summoned && SummonMaster == from ); - - if ( canAccess ) - { - if ( Poisoned ) - PrivateOverheadMessage( Network.MessageType.Regular, 0x3B2, 1049692, from.NetState ); // This mount is too ill to ride. - else - Rider = from; - } - else if ( !Controlled && !Summoned ) - { - // That mount does not look broken! You would have to tame it to ride it. - PrivateOverheadMessage( Network.MessageType.Regular, 0x3B2, 501263, from.NetState ); - } - else - { - // This isn't your mount; it refuses to let you ride. - PrivateOverheadMessage( Network.MessageType.Regular, 0x3B2, 501264, from.NetState ); - } - } - else - { - from.SendLocalizedMessage( 500206 ); // That is too far away to ride. - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ItemID - { - get => InternalItem?.ItemID ?? 0; - set - { - if ( InternalItem != null ) - InternalItem.ItemID = value; - } - } - - public static void Dismount( Mobile m ) - { - IMount mount = m.Mount; - - if ( mount != null ) - mount.Rider = null; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Rider - { - get => m_Rider; - set - { - if ( m_Rider != value ) - { - if ( value == null ) - { - Point3D loc = m_Rider.Location; - Map map = m_Rider.Map; - - if ( map == null || map == Map.Internal ) - { - loc = m_Rider.LogoutLocation; - map = m_Rider.LogoutMap; - } - - Direction = m_Rider.Direction; - Location = loc; - Map = map; - - InternalItem?.Internalize(); - } - else - { - if ( m_Rider != null ) - { - Dismount( m_Rider ); - } - - Dismount( value ); - - if ( InternalItem != null ) - value.AddItem( InternalItem ); - - value.Direction = Direction; - - Internalize(); - - if ( value.Target is Bola.BolaTarget ) - { - Target.Cancel( value ); - } - } - - m_Rider = value; - } - } - } - - // 1040024 You are still too dazed from being knocked off your mount to ride! - // 1062910 You cannot mount while recovering from a bola throw. - // 1070859 You cannot mount while recovering from a dismount special maneuver. - - public static bool CheckMountAllowed( Mobile mob ) - { - bool result = true; - - if ((mob is PlayerMobile mobile) && mobile.MountBlockReason != BlockMountType.None) - { - mobile.SendLocalizedMessage((int)mobile.MountBlockReason); - result = false; - } - - return result; - } - - public virtual void OnRiderDamaged( int amount, Mobile from, bool willKill ) - { - if ( m_Rider == null ) - return; - - Mobile attacker = from; - if ( attacker == null ) - attacker = m_Rider.FindMostRecentDamager( true ); - - if ( !(attacker == this || attacker == m_Rider || willKill || DateTime.UtcNow < NextMountAbility) ) - { - if ( DoMountAbility( amount, from ) ) - NextMountAbility = DateTime.UtcNow + MountAbilityDelay; - - } - } - - public virtual bool DoMountAbility( int damage, Mobile attacker ) - { - return false; - } - } - - public class MountItem : Item, IMountItem - { - private BaseMount m_Mount; - - public override double DefaultWeight => 0; - - public MountItem( BaseMount mount, int itemID ) : base( itemID ) - { - Layer = Layer.Mount; - Movable = false; - - m_Mount = mount; - } - - public MountItem( Serial serial ) : base( serial ) - { - } - - public override void OnAfterDelete() - { - m_Mount?.Delete(); - m_Mount = null; - - base.OnAfterDelete(); - } - - public override DeathMoveResult OnParentDeath(Mobile parent) - { - if ( m_Mount != null ) - m_Mount.Rider = null; - - return DeathMoveResult.RemainEquipped; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Mount ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Mount = reader.ReadMobile() as BaseMount; - - if ( m_Mount == null ) - Delete(); - - break; - } - } - } - - public IMount Mount => m_Mount; - } -} - + public abstract class BaseMount : BaseCreature, IMount + { + private Mobile m_Rider; + + public BaseMount(string name, int bodyID, int itemID, AIType aiType, FightMode fightMode, int rangePerception, + int rangeFight, double activeSpeed, double passiveSpeed) : base(aiType, fightMode, rangePerception, rangeFight, + activeSpeed, passiveSpeed) + { + Name = name; + Body = bodyID; + + InternalItem = new MountItem(this, itemID); + } + + public BaseMount(Serial serial) + : base(serial) + { + } + + public virtual TimeSpan MountAbilityDelay => TimeSpan.Zero; + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextMountAbility{ get; set; } + + protected Item InternalItem{ get; private set; } + + public virtual bool AllowMaleRider => true; + public virtual bool AllowFemaleRider => true; + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public override int Hue + { + get => base.Hue; + set + { + base.Hue = value; + + if (InternalItem != null) + InternalItem.Hue = value; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ItemID + { + get => InternalItem?.ItemID ?? 0; + set + { + if (InternalItem != null) + InternalItem.ItemID = value; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Rider + { + get => m_Rider; + set + { + if (m_Rider != value) + { + if (value == null) + { + Point3D loc = m_Rider.Location; + Map map = m_Rider.Map; + + if (map == null || map == Map.Internal) + { + loc = m_Rider.LogoutLocation; + map = m_Rider.LogoutMap; + } + + Direction = m_Rider.Direction; + Location = loc; + Map = map; + + InternalItem?.Internalize(); + } + else + { + if (m_Rider != null) Dismount(m_Rider); + + Dismount(value); + + if (InternalItem != null) + value.AddItem(InternalItem); + + value.Direction = Direction; + + Internalize(); + + if (value.Target is Bola.BolaTarget) Target.Cancel(value); + } + + m_Rider = value; + } + } + } + + public virtual void OnRiderDamaged(int amount, Mobile from, bool willKill) + { + if (m_Rider == null) + return; + + Mobile attacker = from; + if (attacker == null) + attacker = m_Rider.FindMostRecentDamager(true); + + if (!(attacker == this || attacker == m_Rider || willKill || DateTime.UtcNow < NextMountAbility)) + if (DoMountAbility(amount, from)) + NextMountAbility = DateTime.UtcNow + MountAbilityDelay; + } + + public override bool OnBeforeDeath() + { + Rider = null; + + return base.OnBeforeDeath(); + } + + public override void OnAfterDelete() + { + InternalItem?.Delete(); + InternalItem = null; + + base.OnAfterDelete(); + } + + public override void OnDelete() + { + Rider = null; + + base.OnDelete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(NextMountAbility); + + writer.Write(m_Rider); + writer.Write(InternalItem); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + NextMountAbility = reader.ReadDateTime(); + goto case 0; + } + case 0: + { + m_Rider = reader.ReadMobile(); + InternalItem = reader.ReadItem(); + + if (InternalItem == null) + Delete(); + + break; + } + } + } + + public virtual void OnDisallowedRider(Mobile m) + { + m.SendMessage("You may not ride this creature."); + } + + public override void OnDoubleClick(Mobile from) + { + if (IsDeadPet) + return; + + if (from.IsBodyMod && !from.Body.IsHuman) + { + if (Core.AOS) // You cannot ride a mount in your current form. + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1062061, from.NetState); + else + from.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + + return; + } + + if (!CheckMountAllowed(from)) + return; + + if (from.Mounted) + { + from.SendLocalizedMessage(1005583); // Please dismount first. + return; + } + + if (from.Female ? !AllowFemaleRider : !AllowMaleRider) + { + OnDisallowedRider(from); + return; + } + + if (!DesignContext.Check(from)) + return; + + if (from.HasTrade) + { + from.SendLocalizedMessage(1042317, "", 0x41); // You may not ride at this time + return; + } + + if (from.InRange(this, 1)) + { + bool canAccess = from.AccessLevel >= AccessLevel.GameMaster + || Controlled && ControlMaster == from + || Summoned && SummonMaster == from; + + if (canAccess) + { + if (Poisoned) + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1049692, + from.NetState); // This mount is too ill to ride. + else + Rider = from; + } + else if (!Controlled && !Summoned) + { + // That mount does not look broken! You would have to tame it to ride it. + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 501263, from.NetState); + } + else + { + // This isn't your mount; it refuses to let you ride. + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 501264, from.NetState); + } + } + else + { + from.SendLocalizedMessage(500206); // That is too far away to ride. + } + } + + public static void Dismount(Mobile m) + { + IMount mount = m.Mount; + + if (mount != null) + mount.Rider = null; + } + + // 1040024 You are still too dazed from being knocked off your mount to ride! + // 1062910 You cannot mount while recovering from a bola throw. + // 1070859 You cannot mount while recovering from a dismount special maneuver. + + public static bool CheckMountAllowed(Mobile mob) + { + bool result = true; + + if (mob is PlayerMobile mobile && mobile.MountBlockReason != BlockMountType.None) + { + mobile.SendLocalizedMessage((int)mobile.MountBlockReason); + result = false; + } + + return result; + } + + public virtual bool DoMountAbility(int damage, Mobile attacker) + { + return false; + } + } + + public class MountItem : Item, IMountItem + { + private BaseMount m_Mount; + + public MountItem(BaseMount mount, int itemID) : base(itemID) + { + Layer = Layer.Mount; + Movable = false; + + m_Mount = mount; + } + + public MountItem(Serial serial) : base(serial) + { + } + + public override double DefaultWeight => 0; + + public IMount Mount => m_Mount; + + public override void OnAfterDelete() + { + m_Mount?.Delete(); + m_Mount = null; + + base.OnAfterDelete(); + } + + public override DeathMoveResult OnParentDeath(Mobile parent) + { + if (m_Mount != null) + m_Mount.Rider = null; + + return DeathMoveResult.RemainEquipped; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Mount); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Mount = reader.ReadMobile() as BaseMount; + + if (m_Mount == null) + Delete(); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Beetle.cs b/Scripts/Mobiles/Animals/Mounts/Beetle.cs index 0154e0452..9133993f3 100644 --- a/Scripts/Mobiles/Animals/Mounts/Beetle.cs +++ b/Scripts/Mobiles/Animals/Mounts/Beetle.cs @@ -1,173 +1,175 @@ using System.Collections.Generic; -using Server.Items; using Server.ContextMenus; +using Server.Items; namespace Server.Mobiles { - public class Beetle : BaseMount - { - public override string CorpseName => "a giant beetle corpse"; - public virtual double BoostedSpeed => 0.1; + public class Beetle : BaseMount + { + [Constructible] + public Beetle() : this("a giant beetle") + { + } - [Constructible] - public Beetle() : this( "a giant beetle" ) - { - } + [Constructible] + public Beetle(string name) : base(name, 0x317, 0x3EBC, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.25, 0.5) + { + SetStr(300); + SetDex(100); + SetInt(500); - public override bool SubdueBeforeTame => true; // Must be beaten into submission - public override bool ReduceSpeedWithDamage => false; + SetHits(200); - [Constructible] - public Beetle( string name ) : base( name, 0x317, 0x3EBC, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.25, 0.5 ) - { - SetStr( 300 ); - SetDex( 100 ); - SetInt( 500 ); + SetDamage(7, 20); - SetHits( 200 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 7, 20 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 80.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 4000; + Karma = -4000; - SetSkill( SkillName.MagicResist, 80.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + Tamable = true; + ControlSlots = 3; + MinTameSkill = 29.1; - Fame = 4000; - Karma = -4000; + Container pack = Backpack; - Tamable = true; - ControlSlots = 3; - MinTameSkill = 29.1; + pack?.Delete(); - Container pack = Backpack; + pack = new StrongBackpack(); + pack.Movable = false; - pack?.Delete(); + AddItem(pack); + } - pack = new StrongBackpack(); - pack.Movable = false; + public Beetle(Serial serial) : base(serial) + { + } - AddItem( pack ); - } + public override string CorpseName => "a giant beetle corpse"; + public virtual double BoostedSpeed => 0.1; - public override int GetAngerSound() - { - return 0x21D; - } + public override bool SubdueBeforeTame => true; // Must be beaten into submission + public override bool ReduceSpeedWithDamage => false; - public override int GetIdleSound() - { - return 0x21D; - } + public override FoodType FavoriteFood => FoodType.Meat; - public override int GetAttackSound() - { - return 0x162; - } + public override int GetAngerSound() + { + return 0x21D; + } - public override int GetHurtSound() - { - return 0x163; - } + public override int GetIdleSound() + { + return 0x21D; + } - public override int GetDeathSound() - { - return 0x21D; - } + public override int GetAttackSound() + { + return 0x162; + } - public override FoodType FavoriteFood => FoodType.Meat; + public override int GetHurtSound() + { + return 0x163; + } - public Beetle( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 0x21D; + } - public override void OnHarmfulSpell( Mobile from ) - { - if ( !Controlled && ControlMaster == null ) - CurrentSpeed = BoostedSpeed; - } + public override void OnHarmfulSpell(Mobile from) + { + if (!Controlled && ControlMaster == null) + CurrentSpeed = BoostedSpeed; + } - public override void OnCombatantChange() - { - if ( Combatant == null && !Controlled && ControlMaster == null ) - CurrentSpeed = PassiveSpeed; - } + public override void OnCombatantChange() + { + if (Combatant == null && !Controlled && ControlMaster == null) + CurrentSpeed = PassiveSpeed; + } - #region Pack Animal Methods - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - PackAnimal.CombineBackpacks( this ); + writer.Write(0); // version + } - return true; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override DeathMoveResult GetInventoryMoveResultFor( Item item ) - { - return DeathMoveResult.MoveToCorpse; - } + int version = reader.ReadInt(); + } - public override bool IsSnoop( Mobile from ) - { - if ( PackAnimal.CheckAccess( this, from ) ) - return false; + #region Pack Animal Methods - return base.IsSnoop( from ); - } + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - public override bool OnDragDrop( Mobile from, Item item ) - { - if ( CheckFeed( from, item ) ) - return true; + PackAnimal.CombineBackpacks(this); - if ( PackAnimal.CheckAccess( this, from ) ) - { - AddToBackpack( item ); - return true; - } + return true; + } - return base.OnDragDrop( from, item ); - } + public override DeathMoveResult GetInventoryMoveResultFor(Item item) + { + return DeathMoveResult.MoveToCorpse; + } - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - return PackAnimal.CheckAccess( this, from ); - } + public override bool IsSnoop(Mobile from) + { + if (PackAnimal.CheckAccess(this, from)) + return false; - public override bool CheckNonlocalLift( Mobile from, Item item ) - { - return PackAnimal.CheckAccess( this, from ); - } + return base.IsSnoop(from); + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override bool OnDragDrop(Mobile from, Item item) + { + if (CheckFeed(from, item)) + return true; - PackAnimal.GetContextMenuEntries( this, from, list ); - } - #endregion + if (PackAnimal.CheckAccess(this, from)) + { + AddToBackpack(item); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return base.OnDragDrop(from, item); + } - writer.Write( (int) 0 ); // version - } + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + return PackAnimal.CheckAccess(this, from); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool CheckNonlocalLift(Mobile from, Item item) + { + return PackAnimal.CheckAccess(this, from); + } - int version = reader.ReadInt(); - } - } -} + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + PackAnimal.GetContextMenuEntries(this, from, list); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/DesertOstard.cs b/Scripts/Mobiles/Animals/Mounts/DesertOstard.cs index 47f7322c8..49a44a60a 100644 --- a/Scripts/Mobiles/Animals/Mounts/DesertOstard.cs +++ b/Scripts/Mobiles/Animals/Mounts/DesertOstard.cs @@ -1,64 +1,65 @@ namespace Server.Mobiles { - public class DesertOstard : BaseMount - { - public override string CorpseName => "an ostard corpse"; - [Constructible] - public DesertOstard() : this( "a desert ostard" ) - { - } + public class DesertOstard : BaseMount + { + [Constructible] + public DesertOstard() : this("a desert ostard") + { + } - [Constructible] - public DesertOstard( string name ) : base( name, 0xD2, 0x3EA3, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x270; + [Constructible] + public DesertOstard(string name) : base(name, 0xD2, 0x3EA3, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x270; - SetStr( 94, 170 ); - SetDex( 56, 75 ); - SetInt( 6, 10 ); + SetStr(94, 170); + SetDex(56, 75); + SetInt(6, 10); - SetHits( 71, 88 ); - SetMana( 0 ); + SetHits(71, 88); + SetMana(0); - SetDamage( 5, 11 ); + SetDamage(5, 11); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 15 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 15); - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 25.3, 40.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 25.3, 40.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - Fame = 450; - Karma = 0; + Fame = 450; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - public override int Meat => 3; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override PackInstinct PackInstinct => PackInstinct.Ostard; + public DesertOstard(Serial serial) : base(serial) + { + } - public DesertOstard( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "an ostard corpse"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int Meat => 3; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override PackInstinct PackInstinct => PackInstinct.Ostard; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Ethereals.cs b/Scripts/Mobiles/Animals/Mounts/Ethereals.cs index 7844e9160..51c01a23d 100644 --- a/Scripts/Mobiles/Animals/Mounts/Ethereals.cs +++ b/Scripts/Mobiles/Animals/Mounts/Ethereals.cs @@ -1,843 +1,843 @@ using System; -using Server.Items; -using Server.Spells; using Server.Engines.VeteranRewards; +using Server.Items; +using Server.Multis; +using Server.Spells; namespace Server.Mobiles { - public class EtherealMount : Item, IMount, IMountItem, IRewardItem - { - private int m_MountedID; - private int m_RegularID; - private Mobile m_Rider; - private bool m_IsDonationItem; - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsRewardItem { get; set; } - - public override double DefaultWeight => 1.0; - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public bool IsDonationItem - { - get => m_IsDonationItem; - set { m_IsDonationItem = value; InvalidateProperties(); } - } - - [Constructible] - public EtherealMount( int itemID, int mountID ) - : base( itemID ) - { - m_MountedID = mountID; - m_RegularID = itemID; - m_Rider = null; - - Layer = Layer.Invalid; - - LootType = LootType.Blessed; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( m_IsDonationItem ) - { - list.Add( "Donation Ethereal" ); - list.Add( "7.5 sec slower cast time if not a 9mo. Veteran" ); - } - if ( Core.ML && IsRewardItem ) - list.Add( RewardSystem.GetRewardYearLabel( this, new object[] { } ) ); // X Year Veteran Reward - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MountedID - { - get => m_MountedID; - set - { - if ( m_MountedID != value ) - { - m_MountedID = value; - - if ( m_Rider != null ) - ItemID = value; - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int RegularID - { - get => m_RegularID; - set - { - if ( m_RegularID != value ) - { - m_RegularID = value; - - if ( m_Rider == null ) - ItemID = value; - } - } - } - - public EtherealMount( Serial serial ) - : base( serial ) - { - } - - public override bool DisplayLootType => false; - - public virtual int FollowerSlots => 1; - - public void RemoveFollowers() - { - if ( m_Rider != null ) - m_Rider.Followers -= FollowerSlots; - - if ( m_Rider != null && m_Rider.Followers < 0 ) - m_Rider.Followers = 0; - } - - public void AddFollowers() - { - if ( m_Rider != null ) - m_Rider.Followers += FollowerSlots; - } - - public virtual bool Validate( Mobile from ) - { - if ( Parent == null ) - { - from.SayTo( from, 1010095 ); // This must be on your person to use. - return false; - } - - if ( IsRewardItem && !RewardSystem.CheckIsUsableBy( from, this, null ) ) - { - // CheckIsUsableBy sends the message - return false; - } - if ( !BaseMount.CheckMountAllowed( from ) ) - { - // CheckMountAllowed sends the message - return false; - } - if ( from.Mounted ) - { - from.SendLocalizedMessage( 1005583 ); // Please dismount first. - return false; - } - if ( from.IsBodyMod && !from.Body.IsHuman ) - { - from.SendLocalizedMessage( 1061628 ); // You can't do that while polymorphed. - return false; - } - if ( from.HasTrade ) - { - from.SendLocalizedMessage( 1042317, "", 0x41 ); // You may not ride at this time - return false; - } - if ( ( from.Followers + FollowerSlots ) > from.FollowersMax ) - { - from.SendLocalizedMessage( 1049679 ); // You have too many followers to summon your mount. - return false; - } - if ( !Multis.DesignContext.Check( from ) ) - { - // Check sends the message - return false; - } - - return true; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( Validate( from ) ) - new EtherealSpell( this, from ).Cast(); - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( m_IsDonationItem ) - LabelTo( from, "Donation Ethereal" ); - else - LabelTo( from, "Veteran Reward" ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)3 ); // version - - writer.Write( m_IsDonationItem ); - writer.Write( IsRewardItem ); - - writer.Write( (int)m_MountedID ); - writer.Write( (int)m_RegularID ); - writer.Write( m_Rider ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - LootType = LootType.Blessed; - - int version = reader.ReadInt(); - - switch( version ) - { - case 3: - { - m_IsDonationItem = reader.ReadBool(); - goto case 2; - } - case 2: - { - IsRewardItem = reader.ReadBool(); - goto case 0; - } - case 1: reader.ReadInt(); goto case 0; - case 0: - { - m_MountedID = reader.ReadInt(); - m_RegularID = reader.ReadInt(); - m_Rider = reader.ReadMobile(); - - if ( m_MountedID == 0x3EA2 ) - m_MountedID = 0x3EAA; - - break; - } - } - - AddFollowers(); - - if ( version < 3 && Weight == 0 ) - Weight = -1; - } - - public override DeathMoveResult OnParentDeath( Mobile parent ) - { - Rider = null;//get off, move to pack - - return DeathMoveResult.RemainEquipped; - } - - public static void Dismount( Mobile m ) - { - IMount mount = m.Mount; - - if ( mount != null ) - mount.Rider = null; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Rider - { - get => m_Rider; - set - { - if ( value != m_Rider ) - { - if ( value == null ) - { - Internalize(); - UnmountMe(); - - RemoveFollowers(); - m_Rider = value; - } - else - { - if ( m_Rider != null ) - Dismount( m_Rider ); - - Dismount( value ); - - RemoveFollowers(); - m_Rider = value; - AddFollowers(); - - MountMe(); - } - } - } - } - - public virtual int EtherealHue => 0x4001; - - public void UnmountMe() - { - Container bp = m_Rider.Backpack; - - ItemID = m_RegularID; - Layer = Layer.Invalid; - Movable = true; - - if ( Hue == EtherealHue ) - Hue = 0; - - if ( bp != null ) - { - bp.DropItem( this ); - } - else - { - Point3D loc = m_Rider.Location; - Map map = m_Rider.Map; - - if ( map == null || map == Map.Internal ) - { - loc = m_Rider.LogoutLocation; - map = m_Rider.LogoutMap; - } - - MoveToWorld( loc, map ); - } - } - - public void MountMe() - { - ItemID = m_MountedID; - Layer = Layer.Mount; - Movable = false; - - if ( Hue == 0 ) - Hue = EtherealHue; - - ProcessDelta(); - m_Rider.ProcessDelta(); - m_Rider.EquipItem( this ); - m_Rider.ProcessDelta(); - ProcessDelta(); - } - - public IMount Mount => this; - - public static void StopMounting( Mobile mob ) - { - (mob.Spell as EtherealSpell)?.Stop(); - } - - public void OnRiderDamaged( int amount, Mobile from, bool willKill ) - { - } - - private class EtherealSpell : Spell - { - private static SpellInfo m_Info = new SpellInfo( "Ethereal Mount", "", 230 ); - - private EtherealMount m_Mount; - private Mobile m_Rider; - - public EtherealSpell( EtherealMount mount, Mobile rider ) - : base( rider, null, m_Info ) - { - m_Rider = rider; - m_Mount = mount; - } - - public override bool ClearHandsOnCast => false; - public override bool RevealOnCast => false; - - public override TimeSpan GetCastRecovery() - { - return TimeSpan.Zero; - } - - public override double CastDelayFastScalar => 0; - - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( ( ( m_Mount.IsDonationItem && RewardSystem.GetRewardLevel( m_Rider ) < 3 ) ? ( 7.5 + ( Core.AOS ? 3.0 : 2.0 ) ) : ( Core.AOS ? 3.0 : 2.0 ) ) ); - - public override int GetMana() - { - return 0; - } - - public override bool ConsumeReagents() - { - return true; - } - - public override bool CheckFizzle() - { - return true; - } - - private bool m_Stop; - - public void Stop() - { - m_Stop = true; - Disturb( DisturbType.Hurt, false, false ); - } - - public override bool CheckDisturb( DisturbType type, bool checkFirst, bool resistable ) - { - if ( type == DisturbType.EquipRequest || type == DisturbType.UseRequest/* || type == DisturbType.Hurt*/ ) - return false; - - return true; - } - - public override void DoHurtFizzle() - { - if ( !m_Stop ) - base.DoHurtFizzle(); - } - - public override void DoFizzle() - { - if ( !m_Stop ) - base.DoFizzle(); - } - - public override void OnDisturb( DisturbType type, bool message ) - { - if ( message && !m_Stop ) - Caster.SendLocalizedMessage( 1049455 ); // You have been disrupted while attempting to summon your ethereal mount! - - //m_Mount.UnmountMe(); - } - - public override void OnCast() - { - if ( !m_Mount.Deleted && m_Mount.Rider == null && m_Mount.Validate( m_Rider ) ) - m_Mount.Rider = m_Rider; - - FinishSequence(); - } - } - } - - public class EtherealHorse : EtherealMount - { - public override int LabelNumber => 1041298; // Ethereal Horse Statuette - - [Constructible] - public EtherealHorse() - : base( 0x20DD, 0x3EAA ) - { - } - - public EtherealHorse( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal horse" ) - Name = null; - - if ( ItemID == 0x2124 ) - ItemID = 0x20DD; - } - } - - public class EtherealLlama : EtherealMount - { - public override int LabelNumber => 1041300; // Ethereal Llama Statuette - - [Constructible] - public EtherealLlama() - : base( 0x20F6, 0x3EAB ) - { - } - - public EtherealLlama( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal llama" ) - Name = null; - } - } - - public class EtherealOstard : EtherealMount - { - public override int LabelNumber => 1041299; // Ethereal Ostard Statuette - - [Constructible] - public EtherealOstard() - : base( 0x2135, 0x3EAC ) - { - } - - public EtherealOstard( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal ostard" ) - Name = null; - } - } - - public class EtherealRidgeback : EtherealMount - { - public override int LabelNumber => 1049747; // Ethereal Ridgeback Statuette - - [Constructible] - public EtherealRidgeback() - : base( 0x2615, 0x3E9A ) - { - } - - public EtherealRidgeback( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal ridgeback" ) - Name = null; - } - } - - public class EtherealUnicorn : EtherealMount - { - public override int LabelNumber => 1049745; // Ethereal Unicorn Statuette - - [Constructible] - public EtherealUnicorn() - : base( 0x25CE, 0x3E9B ) - { - } - - public EtherealUnicorn( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal unicorn" ) - Name = null; - } - } - - public class EtherealBeetle : EtherealMount - { - public override int LabelNumber => 1049748; // Ethereal Beetle Statuette - - [Constructible] - public EtherealBeetle() - : base( 0x260F, 0x3E97 ) - { - } - - public EtherealBeetle( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal beetle" ) - Name = null; - } - } - - public class EtherealKirin : EtherealMount - { - public override int LabelNumber => 1049746; // Ethereal Ki-Rin Statuette - - [Constructible] - public EtherealKirin() - : base( 0x25A0, 0x3E9C ) - { - } - - public EtherealKirin( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal kirin" ) - Name = null; - } - } - - public class EtherealSwampDragon : EtherealMount - { - public override int LabelNumber => 1049749; // Ethereal Swamp Dragon Statuette - - [Constructible] - public EtherealSwampDragon() - : base( 0x2619, 0x3E98 ) - { - } - - public EtherealSwampDragon( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Name == "an ethereal swamp dragon" ) - Name = null; - } - } - - public class RideablePolarBear : EtherealMount - { - public override int LabelNumber => 1076159; // Rideable Polar Bear - public override int EtherealHue => 0; - - [Constructible] - public RideablePolarBear() - : base( 0x20E1, 0x3EC5 ) - { - } - - public RideablePolarBear( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class EtherealCuSidhe : EtherealMount - { - public override int LabelNumber => 1080386; // Ethereal Cu Sidhe Statuette - - [Constructible] - public EtherealCuSidhe() - : base( 0x2D96, 0x3E91 ) - { - } - - public EtherealCuSidhe( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class EtherealHiryu : EtherealMount - { - public override int LabelNumber => 1113813; // Ethereal Hiryu Statuette - - [Constructible] - public EtherealHiryu() - : base( 0x276A, 0x3E94 ) - { - } - - public EtherealHiryu( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class EtherealReptalon : EtherealMount - { - public override int LabelNumber => 1113812; // Ethereal Reptalon Statuette - - [Constructible] - public EtherealReptalon() - : base( 0x2d95, 0x3e90 ) - { - } - - public EtherealReptalon( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } - - public class ChargerOfTheFallen : EtherealMount - { - public override int LabelNumber => 1074816; // Charger of the Fallen Statuette - - [Constructible] - public ChargerOfTheFallen() - : base( 0x2D9C, 0x3E92 ) - { - } - - public override int EtherealHue => 0; - - public ChargerOfTheFallen( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( version <= 1 && Hue != 0 ) - { - Hue = 0; - } - } - } -} + public class EtherealMount : Item, IMount, IMountItem, IRewardItem + { + private bool m_IsDonationItem; + private int m_MountedID; + private int m_RegularID; + private Mobile m_Rider; + + [Constructible] + public EtherealMount(int itemID, int mountID) + : base(itemID) + { + m_MountedID = mountID; + m_RegularID = itemID; + m_Rider = null; + + Layer = Layer.Invalid; + + LootType = LootType.Blessed; + } + + public EtherealMount(Serial serial) + : base(serial) + { + } + + public override double DefaultWeight => 1.0; + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public bool IsDonationItem + { + get => m_IsDonationItem; + set + { + m_IsDonationItem = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MountedID + { + get => m_MountedID; + set + { + if (m_MountedID != value) + { + m_MountedID = value; + + if (m_Rider != null) + ItemID = value; + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int RegularID + { + get => m_RegularID; + set + { + if (m_RegularID != value) + { + m_RegularID = value; + + if (m_Rider == null) + ItemID = value; + } + } + } + + public override bool DisplayLootType => false; + + public virtual int FollowerSlots => 1; + + public virtual int EtherealHue => 0x4001; + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Rider + { + get => m_Rider; + set + { + if (value != m_Rider) + { + if (value == null) + { + Internalize(); + UnmountMe(); + + RemoveFollowers(); + m_Rider = value; + } + else + { + if (m_Rider != null) + Dismount(m_Rider); + + Dismount(value); + + RemoveFollowers(); + m_Rider = value; + AddFollowers(); + + MountMe(); + } + } + } + } + + public void OnRiderDamaged(int amount, Mobile from, bool willKill) + { + } + + public IMount Mount => this; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsRewardItem{ get; set; } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (m_IsDonationItem) + { + list.Add("Donation Ethereal"); + list.Add("7.5 sec slower cast time if not a 9mo. Veteran"); + } + + if (Core.ML && IsRewardItem) + list.Add(RewardSystem.GetRewardYearLabel(this, new object[] { })); // X Year Veteran Reward + } + + public void RemoveFollowers() + { + if (m_Rider != null) + m_Rider.Followers -= FollowerSlots; + + if (m_Rider != null && m_Rider.Followers < 0) + m_Rider.Followers = 0; + } + + public void AddFollowers() + { + if (m_Rider != null) + m_Rider.Followers += FollowerSlots; + } + + public virtual bool Validate(Mobile from) + { + if (Parent == null) + { + from.SayTo(from, 1010095); // This must be on your person to use. + return false; + } + + if (IsRewardItem && !RewardSystem.CheckIsUsableBy(from, this, null)) return false; + if (!BaseMount.CheckMountAllowed(from)) return false; + if (from.Mounted) + { + from.SendLocalizedMessage(1005583); // Please dismount first. + return false; + } + + if (from.IsBodyMod && !from.Body.IsHuman) + { + from.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + return false; + } + + if (from.HasTrade) + { + from.SendLocalizedMessage(1042317, "", 0x41); // You may not ride at this time + return false; + } + + if (from.Followers + FollowerSlots > from.FollowersMax) + { + from.SendLocalizedMessage(1049679); // You have too many followers to summon your mount. + return false; + } + + if (!DesignContext.Check(from)) return false; + + return true; + } + + public override void OnDoubleClick(Mobile from) + { + if (Validate(from)) + new EtherealSpell(this, from).Cast(); + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (m_IsDonationItem) + LabelTo(from, "Donation Ethereal"); + else + LabelTo(from, "Veteran Reward"); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(3); // version + + writer.Write(m_IsDonationItem); + writer.Write(IsRewardItem); + + writer.Write(m_MountedID); + writer.Write(m_RegularID); + writer.Write(m_Rider); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + LootType = LootType.Blessed; + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + m_IsDonationItem = reader.ReadBool(); + goto case 2; + } + case 2: + { + IsRewardItem = reader.ReadBool(); + goto case 0; + } + case 1: + reader.ReadInt(); + goto case 0; + case 0: + { + m_MountedID = reader.ReadInt(); + m_RegularID = reader.ReadInt(); + m_Rider = reader.ReadMobile(); + + if (m_MountedID == 0x3EA2) + m_MountedID = 0x3EAA; + + break; + } + } + + AddFollowers(); + + if (version < 3 && Weight == 0) + Weight = -1; + } + + public override DeathMoveResult OnParentDeath(Mobile parent) + { + Rider = null; //get off, move to pack + + return DeathMoveResult.RemainEquipped; + } + + public static void Dismount(Mobile m) + { + IMount mount = m.Mount; + + if (mount != null) + mount.Rider = null; + } + + public void UnmountMe() + { + Container bp = m_Rider.Backpack; + + ItemID = m_RegularID; + Layer = Layer.Invalid; + Movable = true; + + if (Hue == EtherealHue) + Hue = 0; + + if (bp != null) + { + bp.DropItem(this); + } + else + { + Point3D loc = m_Rider.Location; + Map map = m_Rider.Map; + + if (map == null || map == Map.Internal) + { + loc = m_Rider.LogoutLocation; + map = m_Rider.LogoutMap; + } + + MoveToWorld(loc, map); + } + } + + public void MountMe() + { + ItemID = m_MountedID; + Layer = Layer.Mount; + Movable = false; + + if (Hue == 0) + Hue = EtherealHue; + + ProcessDelta(); + m_Rider.ProcessDelta(); + m_Rider.EquipItem(this); + m_Rider.ProcessDelta(); + ProcessDelta(); + } + + public static void StopMounting(Mobile mob) + { + (mob.Spell as EtherealSpell)?.Stop(); + } + + private class EtherealSpell : Spell + { + private static SpellInfo m_Info = new SpellInfo("Ethereal Mount", "", 230); + + private EtherealMount m_Mount; + private Mobile m_Rider; + + private bool m_Stop; + + public EtherealSpell(EtherealMount mount, Mobile rider) + : base(rider, null, m_Info) + { + m_Rider = rider; + m_Mount = mount; + } + + public override bool ClearHandsOnCast => false; + public override bool RevealOnCast => false; + + public override double CastDelayFastScalar => 0; + + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( + m_Mount.IsDonationItem && RewardSystem.GetRewardLevel(m_Rider) < 3 ? 7.5 + (Core.AOS ? 3.0 : 2.0) : + Core.AOS ? 3.0 : 2.0); + + public override TimeSpan GetCastRecovery() + { + return TimeSpan.Zero; + } + + public override int GetMana() + { + return 0; + } + + public override bool ConsumeReagents() + { + return true; + } + + public override bool CheckFizzle() + { + return true; + } + + public void Stop() + { + m_Stop = true; + Disturb(DisturbType.Hurt, false, false); + } + + public override bool CheckDisturb(DisturbType type, bool checkFirst, bool resistable) + { + if (type == DisturbType.EquipRequest || type == DisturbType.UseRequest /* || type == DisturbType.Hurt*/) + return false; + + return true; + } + + public override void DoHurtFizzle() + { + if (!m_Stop) + base.DoHurtFizzle(); + } + + public override void DoFizzle() + { + if (!m_Stop) + base.DoFizzle(); + } + + public override void OnDisturb(DisturbType type, bool message) + { + if (message && !m_Stop) + Caster.SendLocalizedMessage( + 1049455); // You have been disrupted while attempting to summon your ethereal mount! + + //m_Mount.UnmountMe(); + } + + public override void OnCast() + { + if (!m_Mount.Deleted && m_Mount.Rider == null && m_Mount.Validate(m_Rider)) + m_Mount.Rider = m_Rider; + + FinishSequence(); + } + } + } + + public class EtherealHorse : EtherealMount + { + [Constructible] + public EtherealHorse() + : base(0x20DD, 0x3EAA) + { + } + + public EtherealHorse(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1041298; // Ethereal Horse Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal horse") + Name = null; + + if (ItemID == 0x2124) + ItemID = 0x20DD; + } + } + + public class EtherealLlama : EtherealMount + { + [Constructible] + public EtherealLlama() + : base(0x20F6, 0x3EAB) + { + } + + public EtherealLlama(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1041300; // Ethereal Llama Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal llama") + Name = null; + } + } + + public class EtherealOstard : EtherealMount + { + [Constructible] + public EtherealOstard() + : base(0x2135, 0x3EAC) + { + } + + public EtherealOstard(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1041299; // Ethereal Ostard Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal ostard") + Name = null; + } + } + + public class EtherealRidgeback : EtherealMount + { + [Constructible] + public EtherealRidgeback() + : base(0x2615, 0x3E9A) + { + } + + public EtherealRidgeback(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1049747; // Ethereal Ridgeback Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal ridgeback") + Name = null; + } + } + + public class EtherealUnicorn : EtherealMount + { + [Constructible] + public EtherealUnicorn() + : base(0x25CE, 0x3E9B) + { + } + + public EtherealUnicorn(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1049745; // Ethereal Unicorn Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal unicorn") + Name = null; + } + } + + public class EtherealBeetle : EtherealMount + { + [Constructible] + public EtherealBeetle() + : base(0x260F, 0x3E97) + { + } + + public EtherealBeetle(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1049748; // Ethereal Beetle Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal beetle") + Name = null; + } + } + + public class EtherealKirin : EtherealMount + { + [Constructible] + public EtherealKirin() + : base(0x25A0, 0x3E9C) + { + } + + public EtherealKirin(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1049746; // Ethereal Ki-Rin Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal kirin") + Name = null; + } + } + + public class EtherealSwampDragon : EtherealMount + { + [Constructible] + public EtherealSwampDragon() + : base(0x2619, 0x3E98) + { + } + + public EtherealSwampDragon(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1049749; // Ethereal Swamp Dragon Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Name == "an ethereal swamp dragon") + Name = null; + } + } + + public class RideablePolarBear : EtherealMount + { + [Constructible] + public RideablePolarBear() + : base(0x20E1, 0x3EC5) + { + } + + public RideablePolarBear(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1076159; // Rideable Polar Bear + public override int EtherealHue => 0; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class EtherealCuSidhe : EtherealMount + { + [Constructible] + public EtherealCuSidhe() + : base(0x2D96, 0x3E91) + { + } + + public EtherealCuSidhe(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1080386; // Ethereal Cu Sidhe Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class EtherealHiryu : EtherealMount + { + [Constructible] + public EtherealHiryu() + : base(0x276A, 0x3E94) + { + } + + public EtherealHiryu(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1113813; // Ethereal Hiryu Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class EtherealReptalon : EtherealMount + { + [Constructible] + public EtherealReptalon() + : base(0x2d95, 0x3e90) + { + } + + public EtherealReptalon(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1113812; // Ethereal Reptalon Statuette + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } + + public class ChargerOfTheFallen : EtherealMount + { + [Constructible] + public ChargerOfTheFallen() + : base(0x2D9C, 0x3E92) + { + } + + public ChargerOfTheFallen(Serial serial) + : base(serial) + { + } + + public override int LabelNumber => 1074816; // Charger of the Fallen Statuette + + public override int EtherealHue => 0; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version <= 1 && Hue != 0) Hue = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/FireSteed.cs b/Scripts/Mobiles/Animals/Mounts/FireSteed.cs index 68e528b59..707f5385e 100644 --- a/Scripts/Mobiles/Animals/Mounts/FireSteed.cs +++ b/Scripts/Mobiles/Animals/Mounts/FireSteed.cs @@ -3,90 +3,86 @@ using Server.Items; namespace Server.Mobiles { - public class FireSteed : BaseMount - { - public override string CorpseName => "a fire steed corpse"; - [Constructible] - public FireSteed() : this( "a fire steed" ) - { - } + public class FireSteed : BaseMount + { + [Constructible] + public FireSteed() : this("a fire steed") + { + } - [Constructible] - public FireSteed( string name ) : base( name, 0xBE, 0x3E9E, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0xA8; + [Constructible] + public FireSteed(string name) : base(name, 0xBE, 0x3E9E, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0xA8; - SetStr( 376, 400 ); - SetDex( 91, 120 ); - SetInt( 291, 300 ); + SetStr(376, 400); + SetDex(91, 120); + SetInt(291, 300); - SetHits( 226, 240 ); + SetHits(226, 240); - SetDamage( 11, 30 ); + SetDamage(11, 30); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Fire, 80 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Fire, 80); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetSkill( SkillName.MagicResist, 100.0, 120.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + SetSkill(SkillName.MagicResist, 100.0, 120.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - Fame = 20000; - Karma = -20000; + Fame = 20000; + Karma = -20000; - Tamable = true; - ControlSlots = 2; - MinTameSkill = 106.0; - } + Tamable = true; + ControlSlots = 2; + MinTameSkill = 106.0; + } - public override void GenerateLoot() - { - PackItem( new SulfurousAsh( Utility.RandomMinMax( 151, 300 ) ) ); - PackItem( new Ruby( Utility.RandomMinMax( 16, 30 ) ) ); - } + public FireSteed(Serial serial) : base(serial) + { + } - public override bool HasBreath => true; // fire breath enabled - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Daemon | PackInstinct.Equine; + public override string CorpseName => "a fire steed corpse"; - public FireSteed( Serial serial ) : base( serial ) - { - } + public override bool HasBreath => true; // fire breath enabled + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Daemon | PackInstinct.Equine; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void GenerateLoot() + { + PackItem(new SulfurousAsh(Utility.RandomMinMax(151, 300))); + PackItem(new Ruby(Utility.RandomMinMax(16, 30))); + } - writer.Write( (int) 1 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(1); // version + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( BaseSoundID <= 0 ) - BaseSoundID = 0xA8; + int version = reader.ReadInt(); - if ( version < 1 ) - { - for ( int i = 0; i < Skills.Length; ++i ) - { - Skills[i].Cap = Math.Max( 100.0, Skills[i].Cap * 0.9 ); + if (BaseSoundID <= 0) + BaseSoundID = 0xA8; - if ( Skills[i].Base > Skills[i].Cap ) - { - Skills[i].Base = Skills[i].Cap; - } - } - } - } - } -} + if (version < 1) + for (int i = 0; i < Skills.Length; ++i) + { + Skills[i].Cap = Math.Max(100.0, Skills[i].Cap * 0.9); + + if (Skills[i].Base > Skills[i].Cap) Skills[i].Base = Skills[i].Cap; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/ForestOstard.cs b/Scripts/Mobiles/Animals/Mounts/ForestOstard.cs index 369f3ccd7..af7b8da22 100644 --- a/Scripts/Mobiles/Animals/Mounts/ForestOstard.cs +++ b/Scripts/Mobiles/Animals/Mounts/ForestOstard.cs @@ -1,65 +1,66 @@ namespace Server.Mobiles { - public class ForestOstard : BaseMount - { - public override string CorpseName => "an ostard corpse"; - [Constructible] - public ForestOstard() : this( "a forest ostard" ) - { - } + public class ForestOstard : BaseMount + { + [Constructible] + public ForestOstard() : this("a forest ostard") + { + } - [Constructible] - public ForestOstard( string name ) : base( name, 0xDB, 0x3EA5, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Hue = Utility.RandomSlimeHue() | 0x8000; + [Constructible] + public ForestOstard(string name) : base(name, 0xDB, 0x3EA5, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Hue = Utility.RandomSlimeHue() | 0x8000; - BaseSoundID = 0x270; + BaseSoundID = 0x270; - SetStr( 94, 170 ); - SetDex( 56, 75 ); - SetInt( 6, 10 ); + SetStr(94, 170); + SetDex(56, 75); + SetInt(6, 10); - SetHits( 71, 88 ); - SetMana( 0 ); + SetHits(71, 88); + SetMana(0); - SetDamage( 8, 14 ); + SetDamage(8, 14); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 15, 20 ); + SetResistance(ResistanceType.Physical, 15, 20); - SetSkill( SkillName.MagicResist, 27.1, 32.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + SetSkill(SkillName.MagicResist, 27.1, 32.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - Fame = 450; - Karma = 0; + Fame = 450; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - public override int Meat => 3; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override PackInstinct PackInstinct => PackInstinct.Ostard; + public ForestOstard(Serial serial) : base(serial) + { + } - public ForestOstard( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "an ostard corpse"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int Meat => 3; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override PackInstinct PackInstinct => PackInstinct.Ostard; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/FrenziedOstard.cs b/Scripts/Mobiles/Animals/Mounts/FrenziedOstard.cs index 6013258f4..51384bc67 100644 --- a/Scripts/Mobiles/Animals/Mounts/FrenziedOstard.cs +++ b/Scripts/Mobiles/Animals/Mounts/FrenziedOstard.cs @@ -1,68 +1,69 @@ namespace Server.Mobiles { - public class FrenziedOstard : BaseMount - { - public override string CorpseName => "an ostard corpse"; - [Constructible] - public FrenziedOstard() : this( "a frenzied ostard" ) - { - } + public class FrenziedOstard : BaseMount + { + [Constructible] + public FrenziedOstard() : this("a frenzied ostard") + { + } - [Constructible] - public FrenziedOstard( string name ) : base( name, 0xDA, 0x3EA4, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Hue = Utility.RandomHairHue() | 0x8000; + [Constructible] + public FrenziedOstard(string name) : base(name, 0xDA, 0x3EA4, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Hue = Utility.RandomHairHue() | 0x8000; - BaseSoundID = 0x275; + BaseSoundID = 0x275; - SetStr( 94, 170 ); - SetDex( 96, 115 ); - SetInt( 6, 10 ); + SetStr(94, 170); + SetDex(96, 115); + SetInt(6, 10); - SetHits( 71, 110 ); - SetMana( 0 ); + SetHits(71, 110); + SetMana(0); - SetDamage( 11, 17 ); + SetDamage(11, 17); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Poison, 20, 25 ); - SetResistance( ResistanceType.Energy, 20, 25 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Poison, 20, 25); + SetResistance(ResistanceType.Energy, 20, 25); - SetSkill( SkillName.MagicResist, 75.1, 80.0 ); - SetSkill( SkillName.Tactics, 79.3, 94.0 ); - SetSkill( SkillName.Wrestling, 79.3, 94.0 ); + SetSkill(SkillName.MagicResist, 75.1, 80.0); + SetSkill(SkillName.Tactics, 79.3, 94.0); + SetSkill(SkillName.Wrestling, 79.3, 94.0); - Fame = 1500; - Karma = -1500; + Fame = 1500; + Karma = -1500; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 77.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 77.1; + } - public override int Meat => 3; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish | FoodType.Eggs | FoodType.FruitsAndVegies; - public override PackInstinct PackInstinct => PackInstinct.Ostard; + public FrenziedOstard(Serial serial) : base(serial) + { + } - public FrenziedOstard( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "an ostard corpse"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int Meat => 3; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish | FoodType.Eggs | FoodType.FruitsAndVegies; + public override PackInstinct PackInstinct => PackInstinct.Ostard; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/HellSteed.cs b/Scripts/Mobiles/Animals/Mounts/HellSteed.cs index 19b8eb346..9a31ca23a 100644 --- a/Scripts/Mobiles/Animals/Mounts/HellSteed.cs +++ b/Scripts/Mobiles/Animals/Mounts/HellSteed.cs @@ -1,64 +1,64 @@ namespace Server.Mobiles { - public class HellSteed : BaseMount - { - public override string CorpseName => "a hellsteed corpse"; - public override bool HasBreath => true; - public override int BreathChaosDamage => 100; - public override Poison PoisonImmune => Poison.Lethal; + public class HellSteed : BaseMount + { + [Constructible] + public HellSteed() : this("a hellsteed") + { + } - [Constructible] - public HellSteed() : this( "a hellsteed" ) - { - } + [Constructible] + public HellSteed(string name) : base(name, 793, 0x3EBB, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + SetStats(this); + } - [Constructible] - public HellSteed( string name ) : base( name, 793, 0x3EBB, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - SetStats( this ); - } + public HellSteed(Serial serial) : base(serial) + { + } - public static void SetStats( BaseCreature steed ) - { - steed.SetStr( 201, 210 ); - steed.SetDex( 101, 110 ); - steed.SetInt( 101, 115 ); + public override string CorpseName => "a hellsteed corpse"; + public override bool HasBreath => true; + public override int BreathChaosDamage => 100; + public override Poison PoisonImmune => Poison.Lethal; - steed.SetHits( 201, 220 ); + public static void SetStats(BaseCreature steed) + { + steed.SetStr(201, 210); + steed.SetDex(101, 110); + steed.SetInt(101, 115); - steed.SetDamage( 20, 24 ); + steed.SetHits(201, 220); - steed.SetDamageType( ResistanceType.Physical, 25 ); - steed.SetDamageType( ResistanceType.Fire, 75 ); + steed.SetDamage(20, 24); - steed.SetResistance( ResistanceType.Physical, 60, 70 ); - steed.SetResistance( ResistanceType.Fire, 90 ); - steed.SetResistance( ResistanceType.Poison, 100 ); + steed.SetDamageType(ResistanceType.Physical, 25); + steed.SetDamageType(ResistanceType.Fire, 75); - steed.SetSkill( SkillName.MagicResist, 90.1, 110.0 ); - steed.SetSkill( SkillName.Tactics, 50.0 ); - steed.SetSkill( SkillName.Wrestling, 90.1, 110.0 ); + steed.SetResistance(ResistanceType.Physical, 60, 70); + steed.SetResistance(ResistanceType.Fire, 90); + steed.SetResistance(ResistanceType.Poison, 100); - steed.Fame = 0; - steed.Karma = 0; - } + steed.SetSkill(SkillName.MagicResist, 90.1, 110.0); + steed.SetSkill(SkillName.Tactics, 50.0); + steed.SetSkill(SkillName.Wrestling, 90.1, 110.0); - public HellSteed( Serial serial ) : base( serial ) - { - } + steed.Fame = 0; + steed.Karma = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Hiryu.cs b/Scripts/Mobiles/Animals/Mounts/Hiryu.cs index 62ff8399e..53b663966 100644 --- a/Scripts/Mobiles/Animals/Mounts/Hiryu.cs +++ b/Scripts/Mobiles/Animals/Mounts/Hiryu.cs @@ -1,255 +1,260 @@ using System; using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class Hiryu : BaseMount - { - public override string CorpseName => "a hiryu corpse"; - public override double WeaponAbilityChance => 0.07; /* 1 in 15 chance of using per landed hit */ + public class Hiryu : BaseMount + { + private static Hashtable m_Table = new Hashtable(); - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + [Constructible] + public Hiryu() + : base("a hiryu", 243, 0x3E94, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Hue = GetHue(); - public override bool StatLossAfterTame => true; + SetStr(1201, 1410); + SetDex(171, 270); + SetInt(301, 325); - private static int GetHue() - { - int rand = Utility.Random( 1075 ); + SetHits(901, 1100); + SetMana(60); - /* - 1000 1075 No Hue Color 93.02% 0x0 - * - 10 1075 Ice Green 0.93% 0x847F - 10 1075 Light Blue 0.93% 0x848D - 10 1075 Strong Cyan 0.93% 0x8495 - 10 1075 Agapite 0.93% 0x8899 - 10 1075 Gold 0.93% 0x8032 - * - 8 1075 Blue and Yellow 0.74% 0x8487 - * - 5 1075 Ice Blue 0.47% 0x8482 - * - 3 1075 Cyan 0.28% 0x8123 - 3 1075 Light Green 0.28% 0x8295 - * - 2 1075 Strong Yellow 0.19% 0x8037 - 2 1075 Green 0.19% 0x8030 //this one is an approximation - * - 1 1075 Strong Purple 0.09% 0x8490 - 1 1075 Strong Green 0.09% 0x855C - * */ + SetDamage(20, 30); - if ( rand <= 0 ) - return 0x855C; - if ( rand <= 1 ) - return 0x8490; - if ( rand <= 3 ) - return 0x8030; - if ( rand <= 5 ) - return 0x8037; - if ( rand <= 8 ) - return 0x8295; - if ( rand <= 11 ) - return 0x8123; - if ( rand <= 16 ) - return 0x8482; - if ( rand <= 24 ) - return 0x8487; - if ( rand <= 34 ) - return 0x8032; - if ( rand <= 44 ) - return 0x8899; - if ( rand <= 54 ) - return 0x8495; - if ( rand <= 64 ) - return 0x848D; - if ( rand <= 74 ) - return 0x847F; + SetDamageType(ResistanceType.Physical, 100); + + SetResistance(ResistanceType.Physical, 55, 70); + SetResistance(ResistanceType.Fire, 70, 90); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); + + SetSkill(SkillName.Anatomy, 75.1, 80.0); + SetSkill(SkillName.MagicResist, 85.1, 100.0); + SetSkill(SkillName.Tactics, 100.1, 110.0); + SetSkill(SkillName.Wrestling, 100.1, 120.0); + + Fame = 18000; + Karma = -18000; + + Tamable = true; + ControlSlots = 4; + MinTameSkill = 98.7; + + if (Utility.RandomDouble() < .33) + PackItem(Seed.RandomBonsaiSeed()); + + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(3)); + } + + public Hiryu(Serial serial) + : base(serial) + { + } + + public override string CorpseName => "a hiryu corpse"; + public override double WeaponAbilityChance => 0.07; /* 1 in 15 chance of using per landed hit */ + + public override bool StatLossAfterTame => true; + + public override int TreasureMapLevel => 5; + public override int Meat => 16; + public override int Hides => 60; + public override FoodType FavoriteFood => FoodType.Meat; + public override bool CanAngerOnTame => true; + + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } + + private static int GetHue() + { + int rand = Utility.Random(1075); + + /* + 1000 1075 No Hue Color 93.02% 0x0 + * + 10 1075 Ice Green 0.93% 0x847F + 10 1075 Light Blue 0.93% 0x848D + 10 1075 Strong Cyan 0.93% 0x8495 + 10 1075 Agapite 0.93% 0x8899 + 10 1075 Gold 0.93% 0x8032 + * + 8 1075 Blue and Yellow 0.74% 0x8487 + * + 5 1075 Ice Blue 0.47% 0x8482 + * + 3 1075 Cyan 0.28% 0x8123 + 3 1075 Light Green 0.28% 0x8295 + * + 2 1075 Strong Yellow 0.19% 0x8037 + 2 1075 Green 0.19% 0x8030 //this one is an approximation + * + 1 1075 Strong Purple 0.09% 0x8490 + 1 1075 Strong Green 0.09% 0x855C + * */ + + if (rand <= 0) + return 0x855C; + if (rand <= 1) + return 0x8490; + if (rand <= 3) + return 0x8030; + if (rand <= 5) + return 0x8037; + if (rand <= 8) + return 0x8295; + if (rand <= 11) + return 0x8123; + if (rand <= 16) + return 0x8482; + if (rand <= 24) + return 0x8487; + if (rand <= 34) + return 0x8032; + if (rand <= 44) + return 0x8899; + if (rand <= 54) + return 0x8495; + if (rand <= 64) + return 0x848D; + if (rand <= 74) + return 0x847F; - return 0; - } - - [Constructible] - public Hiryu() - : base( "a hiryu", 243, 0x3E94, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Hue = GetHue(); - - SetStr( 1201, 1410 ); - SetDex( 171, 270 ); - SetInt( 301, 325 ); - - SetHits( 901, 1100 ); - SetMana( 60 ); - - SetDamage( 20, 30 ); - - SetDamageType( ResistanceType.Physical, 100 ); - - SetResistance( ResistanceType.Physical, 55, 70 ); - SetResistance( ResistanceType.Fire, 70, 90 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); - - SetSkill( SkillName.Anatomy, 75.1, 80.0 ); - SetSkill( SkillName.MagicResist, 85.1, 100.0 ); - SetSkill( SkillName.Tactics, 100.1, 110.0 ); - SetSkill( SkillName.Wrestling, 100.1, 120.0 ); - - Fame = 18000; - Karma = -18000; - - Tamable = true; - ControlSlots = 4; - MinTameSkill = 98.7; - - if ( Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(3) ); - } + return 0; + } - public override int GetAngerSound() - { - return 0x4FE; - } + public override int GetAngerSound() + { + return 0x4FE; + } - public override int GetIdleSound() - { - return 0x4FD; - } + public override int GetIdleSound() + { + return 0x4FD; + } - public override int GetAttackSound() - { - return 0x4FC; - } + public override int GetAttackSound() + { + return 0x4FC; + } - public override int GetHurtSound() - { - return 0x4FF; - } + public override int GetHurtSound() + { + return 0x4FF; + } - public override int GetDeathSound() - { - return 0x4FB; - } + public override int GetDeathSound() + { + return 0x4FB; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - AddLoot( LootPack.Gems, 4 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + AddLoot(LootPack.Gems, 4); + } - public override int TreasureMapLevel => 5; - public override int Meat => 16; - public override int Hides => 60; - public override FoodType FavoriteFood => FoodType.Meat; - public override bool CanAngerOnTame => true; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + if (0.1 > Utility.RandomDouble()) + { + /* Grasping Claw + * Start cliloc: 1070836 + * Effect: Physical resistance -15% for 5 seconds + * End cliloc: 1070838 + * Effect: Type: "3" - From: "0x57D4F5B" (player) - To: "0x0" - ItemId: "0x37B9" - ItemIdName: "glow" - FromLocation: "(1149 808, 32)" - ToLocation: "(1149 808, 32)" - Speed: "10" - Duration: "5" - FixedDirection: "True" - Explode: "False" + */ - if ( 0.1 > Utility.RandomDouble() ) - { - /* Grasping Claw - * Start cliloc: 1070836 - * Effect: Physical resistance -15% for 5 seconds - * End cliloc: 1070838 - * Effect: Type: "3" - From: "0x57D4F5B" (player) - To: "0x0" - ItemId: "0x37B9" - ItemIdName: "glow" - FromLocation: "(1149 808, 32)" - ToLocation: "(1149 808, 32)" - Speed: "10" - Duration: "5" - FixedDirection: "True" - Explode: "False" - */ + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070837); // The creature lands another blow in your weakened state. + } + else + { + defender.SendLocalizedMessage( + 1070836); // The blow from the creature's claws has made you more susceptible to physical attacks. + } - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070837 ); // The creature lands another blow in your weakened state. - } - else - defender.SendLocalizedMessage( 1070836 ); // The blow from the creature's claws has made you more susceptible to physical attacks. + int effect = -(defender.PhysicalResistance * 15 / 100); - int effect = -(defender.PhysicalResistance * 15 / 100); + ResistanceMod mod = new ResistanceMod(ResistanceType.Physical, effect); - ResistanceMod mod = new ResistanceMod( ResistanceType.Physical, effect ); + defender.FixedEffect(0x37B9, 10, 5); + defender.AddResistanceMod(mod); - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.AddResistanceMod( mod ); + timer = new ExpireTimer(defender, mod, TimeSpan.FromSeconds(5.0)); + timer.Start(); + m_Table[defender] = timer; + } + } - timer = new ExpireTimer( defender, mod, TimeSpan.FromSeconds( 5.0 ) ); - timer.Start(); - m_Table[defender] = timer; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(2); + } - private static Hashtable m_Table = new Hashtable(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod m_Mod; + if (version == 0) + Timer.DelayCall(TimeSpan.Zero, delegate { Hue = GetHue(); }); - public ExpireTimer( Mobile m, ResistanceMod mod, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - m_Mod = mod; - Priority = TimerPriority.TwoFiftyMS; - } + if (version <= 1) + Timer.DelayCall(TimeSpan.Zero, delegate + { + if (InternalItem != null) InternalItem.Hue = Hue; + }); - public void DoExpire() - { - m_Mobile.RemoveResistanceMod( m_Mod ); - Stop(); - m_Table.Remove( m_Mobile ); - } + if (version < 2) + for (int i = 0; i < Skills.Length; ++i) + { + Skills[i].Cap = Math.Max(100.0, Skills[i].Cap * 0.9); - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1070838 ); // Your resistance to physical attacks has returned. - DoExpire(); - } - } + if (Skills[i].Base > Skills[i].Cap) Skills[i].Base = Skills[i].Cap; + } + } - public Hiryu( Serial serial ) - : base( serial ) - { - } + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod m_Mod; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)2 ); - } + public ExpireTimer(Mobile m, ResistanceMod mod, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + m_Mod = mod; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public void DoExpire() + { + m_Mobile.RemoveResistanceMod(m_Mod); + Stop(); + m_Table.Remove(m_Mobile); + } - if ( version == 0 ) - Timer.DelayCall( TimeSpan.Zero, delegate { Hue = GetHue(); } ); - - if ( version <= 1 ) - Timer.DelayCall( TimeSpan.Zero, delegate { if ( InternalItem != null ) { InternalItem.Hue = Hue; } } ); - - if ( version < 2 ) - { - for ( int i = 0; i < Skills.Length; ++i ) - { - Skills[i].Cap = Math.Max( 100.0, Skills[i].Cap * 0.9 ); - - if ( Skills[i].Base > Skills[i].Cap ) - { - Skills[i].Base = Skills[i].Cap; - } - } - } - } - } -} + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1070838); // Your resistance to physical attacks has returned. + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Horse.cs b/Scripts/Mobiles/Animals/Mounts/Horse.cs index 7bcfdbb65..e9c9644b0 100644 --- a/Scripts/Mobiles/Animals/Mounts/Horse.cs +++ b/Scripts/Mobiles/Animals/Mounts/Horse.cs @@ -1,75 +1,78 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.BrownHorse", "Server.Mobiles.DirtyHorse", "Server.Mobiles.GrayHorse", "Server.Mobiles.TanHorse" )] - public class Horse : BaseMount - { - public override string CorpseName => "a horse corpse"; - private static int[] m_IDs = { - 0xC8, 0x3E9F, - 0xE2, 0x3EA0, - 0xE4, 0x3EA1, - 0xCC, 0x3EA2 - }; + [TypeAlias("Server.Mobiles.BrownHorse", "Server.Mobiles.DirtyHorse", "Server.Mobiles.GrayHorse", + "Server.Mobiles.TanHorse")] + public class Horse : BaseMount + { + private static int[] m_IDs = + { + 0xC8, 0x3E9F, + 0xE2, 0x3EA0, + 0xE4, 0x3EA1, + 0xCC, 0x3EA2 + }; - [Constructible] - public Horse() : this( "a horse" ) - { - } + [Constructible] + public Horse() : this("a horse") + { + } - [Constructible] - public Horse( string name ) : base( name, 0xE2, 0x3EA0, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - int random = Utility.Random( 4 ); + [Constructible] + public Horse(string name) : base(name, 0xE2, 0x3EA0, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + int random = Utility.Random(4); - Body = m_IDs[random * 2]; - ItemID = m_IDs[random * 2 + 1]; - BaseSoundID = 0xA8; + Body = m_IDs[random * 2]; + ItemID = m_IDs[random * 2 + 1]; + BaseSoundID = 0xA8; - SetStr( 22, 98 ); - SetDex( 56, 75 ); - SetInt( 6, 10 ); + SetStr(22, 98); + SetDex(56, 75); + SetInt(6, 10); - SetHits( 28, 45 ); - SetMana( 0 ); + SetHits(28, 45); + SetMana(0); - SetDamage( 3, 4 ); + SetDamage(3, 4); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 15, 20 ); + SetResistance(ResistanceType.Physical, 15, 20); - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - Fame = 300; - Karma = 300; + Fame = 300; + Karma = 300; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - public override int Meat => 3; - public override int Hides => 10; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public Horse(Serial serial) : base(serial) + { + } - public Horse( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a horse corpse"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int Meat => 3; + public override int Hides => 10; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Kirin.cs b/Scripts/Mobiles/Animals/Mounts/Kirin.cs index 2187fb655..bf4736d8a 100644 --- a/Scripts/Mobiles/Animals/Mounts/Kirin.cs +++ b/Scripts/Mobiles/Animals/Mounts/Kirin.cs @@ -1,129 +1,132 @@ using System; -using Server.Network; using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class Kirin : BaseMount - { - public override string CorpseName => "a ki-rin corpse"; - public override bool AllowFemaleRider => false; - public override bool AllowFemaleTamer => false; + public class Kirin : BaseMount + { + [Constructible] + public Kirin() : this("a ki-rin") + { + } - public override bool InitialInnocent => true; + [Constructible] + public Kirin(string name) : base(name, 132, 0x3EAD, AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x3C5; - public override TimeSpan MountAbilityDelay => TimeSpan.FromHours( 1.0 ); + SetStr(296, 325); + SetDex(86, 105); + SetInt(186, 225); - public override void OnDisallowedRider( Mobile m ) - { - m.SendLocalizedMessage( 1042319 ); // The Ki-Rin refuses your attempts to mount it. - } + SetHits(191, 210); - public override bool DoMountAbility( int damage, Mobile attacker ) - { - if ( Rider == null || attacker == null ) //sanity - return false; + SetDamage(16, 22); - if ( (Rider.Hits - damage) < 30 && Rider.Map == attacker.Map && Rider.InRange( attacker, 18 ) ) //Range and map checked here instead of other base fuction because of abiliites that don't need to check this - { - attacker.BoltEffect( 0 ); - // 35~100 damage, unresistable, by the Ki-rin. - attacker.Damage( Utility.RandomMinMax( 35, 100 ), this, false ); //Don't inform mount about this damage, Still unsure wether or not it's flagged as the mount doing damage or the player. If changed to player, without the extra bool it'd be an infinite loop + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Cold, 10); + SetDamageType(ResistanceType.Energy, 10); - Rider.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1042534 ); // Your mount calls down the forces of nature on your opponent. - Rider.FixedParticles( 0, 0, 0, 0x13A7, EffectLayer.Waist ); - Rider.PlaySound( 0xA9 ); // Ki-rin's whinny. - return true; - } + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - return false; - } + SetSkill(SkillName.EvalInt, 80.1, 90.0); + SetSkill(SkillName.Magery, 60.4, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 85.3, 100.0); + SetSkill(SkillName.Tactics, 20.1, 22.5); + SetSkill(SkillName.Wrestling, 80.5, 92.5); - [Constructible] - public Kirin() : this( "a ki-rin" ) - { - } + Fame = 9000; + Karma = 9000; - [Constructible] - public Kirin( string name ) : base( name, 132, 0x3EAD, AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x3C5; + Tamable = true; + ControlSlots = 2; + MinTameSkill = 95.1; + } - SetStr( 296, 325 ); - SetDex( 86, 105 ); - SetInt( 186, 225 ); + public Kirin(Serial serial) : base(serial) + { + } - SetHits( 191, 210 ); + public override string CorpseName => "a ki-rin corpse"; + public override bool AllowFemaleRider => false; + public override bool AllowFemaleTamer => false; - SetDamage( 16, 22 ); + public override bool InitialInnocent => true; - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Cold, 10 ); - SetDamageType( ResistanceType.Energy, 10 ); + public override TimeSpan MountAbilityDelay => TimeSpan.FromHours(1.0); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - SetSkill( SkillName.EvalInt, 80.1, 90.0 ); - SetSkill( SkillName.Magery, 60.4, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 85.3, 100.0 ); - SetSkill( SkillName.Tactics, 20.1, 22.5 ); - SetSkill( SkillName.Wrestling, 80.5, 92.5 ); + public override int Meat => 3; + public override int Hides => 10; + public override HideType HideType => HideType.Horned; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - Fame = 9000; - Karma = 9000; + public override void OnDisallowedRider(Mobile m) + { + m.SendLocalizedMessage(1042319); // The Ki-Rin refuses your attempts to mount it. + } - Tamable = true; - ControlSlots = 2; - MinTameSkill = 95.1; - } + public override bool DoMountAbility(int damage, Mobile attacker) + { + if (Rider == null || attacker == null) //sanity + return false; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.Potions ); - } + if (Rider.Hits - damage < 30 && Rider.Map == attacker.Map && Rider.InRange(attacker, 18) + ) //Range and map checked here instead of other base fuction because of abiliites that don't need to check this + { + attacker.BoltEffect(0); + // 35~100 damage, unresistable, by the Ki-rin. + attacker.Damage(Utility.RandomMinMax(35, 100), this, + false); //Don't inform mount about this damage, Still unsure wether or not it's flagged as the mount doing damage or the player. If changed to player, without the extra bool it'd be an infinite loop - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + Rider.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1042534); // Your mount calls down the forces of nature on your opponent. + Rider.FixedParticles(0, 0, 0, 0x13A7, EffectLayer.Waist); + Rider.PlaySound(0xA9); // Ki-rin's whinny. + return true; + } - if ( Utility.RandomDouble() < 0.35 ) - c.DropItem( new KirinBrains() ); - } + return false; + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.Potions); + } - public override int Meat => 3; - public override int Hides => 10; - public override HideType HideType => HideType.Horned; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public Kirin( Serial serial ) : base( serial ) - { - } + if (Utility.RandomDouble() < 0.35) + c.DropItem(new KirinBrains()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 ) - AI = AIType.AI_Mage; - } - } -} + if (version == 0) + AI = AIType.AI_Mage; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/LesserHiryu.cs b/Scripts/Mobiles/Animals/Mounts/LesserHiryu.cs index b6334b37d..26233d2ab 100644 --- a/Scripts/Mobiles/Animals/Mounts/LesserHiryu.cs +++ b/Scripts/Mobiles/Animals/Mounts/LesserHiryu.cs @@ -1,255 +1,254 @@ using System; using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class LesserHiryu : BaseMount - { - public override string CorpseName => "a hiryu corpse"; - public override double WeaponAbilityChance => 0.07; /* 1 in 15 chance of using; 1 in 5 chance of success */ + public class LesserHiryu : BaseMount + { + private static Hashtable m_Table = new Hashtable(); - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + [Constructible] + public LesserHiryu() + : base("a lesser hiryu", 243, 0x3E94, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Hue = GetHue(); - public override bool StatLossAfterTame => true; + SetStr(301, 410); + SetDex(171, 270); + SetInt(301, 325); - private static int GetHue() - { - int rand = Utility.Random( 527 ); + SetHits(401, 600); + SetMana(60); - /* + SetDamage(18, 23); - 500 527 No Hue Color 94.88% 0 - 10 527 Green 1.90% 0x8295 - 10 527 Green 1.90% 0x8163 (Very Close to Above Green) //this one is an approximation - 5 527 Dark Green 0.95% 0x87D4 - 1 527 Valorite 0.19% 0x88AB - 1 527 Midnight Blue 0.19% 0x8258 + SetDamageType(ResistanceType.Physical, 100); - * */ + SetResistance(ResistanceType.Physical, 45, 70); + SetResistance(ResistanceType.Fire, 60, 80); + SetResistance(ResistanceType.Cold, 5, 15); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - if ( rand <= 0 ) - return 0x8258; - if ( rand <= 1 ) - return 0x88AB; - if ( rand <= 6 ) - return 0x87D4; - if ( rand <= 16 ) - return 0x8163; - if ( rand <= 26 ) - return 0x8295; + SetSkill(SkillName.Anatomy, 75.1, 80.0); + SetSkill(SkillName.MagicResist, 85.1, 100.0); + SetSkill(SkillName.Tactics, 100.1, 110.0); + SetSkill(SkillName.Wrestling, 100.1, 120.0); + + Fame = 10000; + Karma = -10000; + + Tamable = true; + ControlSlots = 3; + MinTameSkill = 98.7; + + if (Utility.RandomDouble() < .33) + PackItem(Seed.RandomBonsaiSeed()); + } + + public LesserHiryu(Serial serial) + : base(serial) + { + } + + public override string CorpseName => "a hiryu corpse"; + public override double WeaponAbilityChance => 0.07; /* 1 in 15 chance of using; 1 in 5 chance of success */ + + public override bool StatLossAfterTame => true; + + public override int TreasureMapLevel => 3; + public override int Meat => 16; + public override int Hides => 60; + public override FoodType FavoriteFood => FoodType.Meat; + public override bool CanAngerOnTame => true; + + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } + + private static int GetHue() + { + int rand = Utility.Random(527); + + /* + + 500 527 No Hue Color 94.88% 0 + 10 527 Green 1.90% 0x8295 + 10 527 Green 1.90% 0x8163 (Very Close to Above Green) //this one is an approximation + 5 527 Dark Green 0.95% 0x87D4 + 1 527 Valorite 0.19% 0x88AB + 1 527 Midnight Blue 0.19% 0x8258 + + * */ + + if (rand <= 0) + return 0x8258; + if (rand <= 1) + return 0x88AB; + if (rand <= 6) + return 0x87D4; + if (rand <= 16) + return 0x8163; + if (rand <= 26) + return 0x8295; - return 0; - } - - [Constructible] - public LesserHiryu() - : base( "a lesser hiryu", 243, 0x3E94, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Hue = GetHue(); - - SetStr( 301, 410 ); - SetDex( 171, 270 ); - SetInt( 301, 325 ); - - SetHits( 401, 600 ); - SetMana( 60 ); - - SetDamage( 18, 23 ); - - SetDamageType( ResistanceType.Physical, 100 ); - - SetResistance( ResistanceType.Physical, 45, 70 ); - SetResistance( ResistanceType.Fire, 60, 80 ); - SetResistance( ResistanceType.Cold, 5, 15 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); - - SetSkill( SkillName.Anatomy, 75.1, 80.0 ); - SetSkill( SkillName.MagicResist, 85.1, 100.0 ); - SetSkill( SkillName.Tactics, 100.1, 110.0 ); - SetSkill( SkillName.Wrestling, 100.1, 120.0 ); - - Fame = 10000; - Karma = -10000; - - Tamable = true; - ControlSlots = 3; - MinTameSkill = 98.7; - - if ( Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - } + return 0; + } - public override bool OverrideBondingReqs() - { - if ( ControlMaster.Skills[SkillName.Bushido].Base >= 90.0 ) - return true; - return false; - } + public override bool OverrideBondingReqs() + { + if (ControlMaster.Skills[SkillName.Bushido].Base >= 90.0) + return true; + return false; + } - public override int GetAngerSound() - { - return 0x4FE; - } + public override int GetAngerSound() + { + return 0x4FE; + } - public override int GetIdleSound() - { - return 0x4FD; - } + public override int GetIdleSound() + { + return 0x4FD; + } - public override int GetAttackSound() - { - return 0x4FC; - } + public override int GetAttackSound() + { + return 0x4FC; + } - public override int GetHurtSound() - { - return 0x4FF; - } + public override int GetHurtSound() + { + return 0x4FF; + } - public override int GetDeathSound() - { - return 0x4FB; - } + public override int GetDeathSound() + { + return 0x4FB; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.Gems, 4 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.Gems, 4); + } - public override double GetControlChance( Mobile m, bool useBaseSkill ) - { - double tamingChance = base.GetControlChance( m, useBaseSkill ); + public override double GetControlChance(Mobile m, bool useBaseSkill) + { + double tamingChance = base.GetControlChance(m, useBaseSkill); - if ( tamingChance >= 0.95 ) - { - return tamingChance; - } + if (tamingChance >= 0.95) return tamingChance; - double skill = (useBaseSkill? m.Skills.Bushido.Base : m.Skills.Bushido.Value); + double skill = useBaseSkill ? m.Skills.Bushido.Base : m.Skills.Bushido.Value; - if ( skill < 90.0 ) - { - return tamingChance; - } + if (skill < 90.0) return tamingChance; - double bushidoChance = ( skill - 30.0 ) / 100; + double bushidoChance = (skill - 30.0) / 100; - if ( m.Skills.Bushido.Base >= 120 ) - bushidoChance += 0.05; + if (m.Skills.Bushido.Base >= 120) + bushidoChance += 0.05; - return bushidoChance > tamingChance ? bushidoChance : tamingChance; - } + return bushidoChance > tamingChance ? bushidoChance : tamingChance; + } - public override int TreasureMapLevel => 3; - public override int Meat => 16; - public override int Hides => 60; - public override FoodType FavoriteFood => FoodType.Meat; - public override bool CanAngerOnTame => true; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + if (0.1 > Utility.RandomDouble()) + { + /* Grasping Claw + * Start cliloc: 1070836 + * Effect: Physical resistance -15% for 5 seconds + * End cliloc: 1070838 + * Effect: Type: "3" - From: "0x57D4F5B" (player) - To: "0x0" - ItemId: "0x37B9" - ItemIdName: "glow" - FromLocation: "(1149 808, 32)" - ToLocation: "(1149 808, 32)" - Speed: "10" - Duration: "5" - FixedDirection: "True" - Explode: "False" + */ - if ( 0.1 > Utility.RandomDouble() ) - { - /* Grasping Claw - * Start cliloc: 1070836 - * Effect: Physical resistance -15% for 5 seconds - * End cliloc: 1070838 - * Effect: Type: "3" - From: "0x57D4F5B" (player) - To: "0x0" - ItemId: "0x37B9" - ItemIdName: "glow" - FromLocation: "(1149 808, 32)" - ToLocation: "(1149 808, 32)" - Speed: "10" - Duration: "5" - FixedDirection: "True" - Explode: "False" - */ + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070837); // The creature lands another blow in your weakened state. + } + else + { + defender.SendLocalizedMessage( + 1070836); // The blow from the creature's claws has made you more susceptible to physical attacks. + } - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070837 ); // The creature lands another blow in your weakened state. - } - else - defender.SendLocalizedMessage( 1070836 ); // The blow from the creature's claws has made you more susceptible to physical attacks. + int effect = -(defender.PhysicalResistance * 15 / 100); - int effect = -(defender.PhysicalResistance * 15 / 100); + ResistanceMod mod = new ResistanceMod(ResistanceType.Physical, effect); - ResistanceMod mod = new ResistanceMod( ResistanceType.Physical, effect ); + defender.FixedEffect(0x37B9, 10, 5); + defender.AddResistanceMod(mod); - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.AddResistanceMod( mod ); + timer = new ExpireTimer(defender, mod, TimeSpan.FromSeconds(5.0)); + timer.Start(); + m_Table[defender] = timer; + } + } - timer = new ExpireTimer( defender, mod, TimeSpan.FromSeconds( 5.0 ) ); - timer.Start(); - m_Table[defender] = timer; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(2); + } - private static Hashtable m_Table = new Hashtable(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod m_Mod; + if (version == 0) + Timer.DelayCall(TimeSpan.Zero, delegate { Hue = GetHue(); }); - public ExpireTimer( Mobile m, ResistanceMod mod, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - m_Mod = mod; - Priority = TimerPriority.TwoFiftyMS; - } + if (version <= 1) + Timer.DelayCall(TimeSpan.Zero, delegate + { + if (InternalItem != null) InternalItem.Hue = Hue; + }); - public void DoExpire() - { - m_Mobile.RemoveResistanceMod( m_Mod ); - Stop(); - m_Table.Remove( m_Mobile ); - } + if (version < 2) + for (int i = 0; i < Skills.Length; ++i) + { + Skills[i].Cap = Math.Max(100.0, Skills[i].Cap * 0.9); - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1070838 ); // Your resistance to physical attacks has returned. - DoExpire(); - } - } + if (Skills[i].Base > Skills[i].Cap) Skills[i].Base = Skills[i].Cap; + } + } - public LesserHiryu( Serial serial ) - : base( serial ) - { - } + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod m_Mod; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)2 ); - } + public ExpireTimer(Mobile m, ResistanceMod mod, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + m_Mod = mod; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public void DoExpire() + { + m_Mobile.RemoveResistanceMod(m_Mod); + Stop(); + m_Table.Remove(m_Mobile); + } - if ( version == 0 ) - Timer.DelayCall( TimeSpan.Zero, delegate { Hue = GetHue(); } ); - - if ( version <= 1 ) - Timer.DelayCall( TimeSpan.Zero, delegate { if ( InternalItem != null ) { InternalItem.Hue = Hue; } } ); - - if ( version < 2 ) - { - for ( int i = 0; i < Skills.Length; ++i ) - { - Skills[i].Cap = Math.Max( 100.0, Skills[i].Cap * 0.9 ); - - if ( Skills[i].Base > Skills[i].Cap ) - { - Skills[i].Base = Skills[i].Cap; - } - } - } - } - } -} + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1070838); // Your resistance to physical attacks has returned. + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Nightmare.cs b/Scripts/Mobiles/Animals/Mounts/Nightmare.cs index 00ed4c3c9..2093d409d 100644 --- a/Scripts/Mobiles/Animals/Mounts/Nightmare.cs +++ b/Scripts/Mobiles/Animals/Mounts/Nightmare.cs @@ -2,121 +2,122 @@ using Server.Items; namespace Server.Mobiles { - public class Nightmare : BaseMount - { - public override string CorpseName => "a nightmare corpse"; - [Constructible] - public Nightmare() : this( "a nightmare" ) - { - } + public class Nightmare : BaseMount + { + [Constructible] + public Nightmare() : this("a nightmare") + { + } - [Constructible] - public Nightmare( string name ) : base( name, 0x74, 0x3EA7, AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = Core.AOS ? 0xA8 : 0x16A; + [Constructible] + public Nightmare(string name) : base(name, 0x74, 0x3EA7, AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + BaseSoundID = Core.AOS ? 0xA8 : 0x16A; - SetStr( 496, 525 ); - SetDex( 86, 105 ); - SetInt( 86, 125 ); + SetStr(496, 525); + SetDex(86, 105); + SetInt(86, 125); - SetHits( 298, 315 ); + SetHits(298, 315); - SetDamage( 16, 22 ); + SetDamage(16, 22); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Fire, 40 ); - SetDamageType( ResistanceType.Energy, 20 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Fire, 40); + SetDamageType(ResistanceType.Energy, 20); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 30); - SetSkill( SkillName.EvalInt, 10.4, 50.0 ); - SetSkill( SkillName.Magery, 10.4, 50.0 ); - SetSkill( SkillName.MagicResist, 85.3, 100.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 80.5, 92.5 ); + SetSkill(SkillName.EvalInt, 10.4, 50.0); + SetSkill(SkillName.Magery, 10.4, 50.0); + SetSkill(SkillName.MagicResist, 85.3, 100.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 80.5, 92.5); - Fame = 14000; - Karma = -14000; + Fame = 14000; + Karma = -14000; - VirtualArmor = 60; + VirtualArmor = 60; - Tamable = true; - ControlSlots = 2; - MinTameSkill = 95.1; + Tamable = true; + ControlSlots = 2; + MinTameSkill = 95.1; - switch ( Utility.Random( 3 ) ) - { - case 0: - { - BodyValue = 116; - ItemID = 16039; - break; - } - case 1: - { - BodyValue = 178; - ItemID = 16041; - break; - } - case 2: - { - BodyValue = 179; - ItemID = 16055; - break; - } - } + switch (Utility.Random(3)) + { + case 0: + { + BodyValue = 116; + ItemID = 16039; + break; + } + case 1: + { + BodyValue = 178; + ItemID = 16041; + break; + } + case 2: + { + BodyValue = 179; + ItemID = 16055; + break; + } + } - PackItem( new SulfurousAsh( Utility.RandomMinMax( 3, 5 ) ) ); - } + PackItem(new SulfurousAsh(Utility.RandomMinMax(3, 5))); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.Potions ); - } + public Nightmare(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - if ( !Controlled ) - return 0x16A; + public override string CorpseName => "a nightmare corpse"; - return base.GetAngerSound(); - } + public override bool HasBreath => true; // fire breath enabled + public override int Meat => 5; + public override int Hides => 10; + public override HideType HideType => HideType.Barbed; + public override FoodType FavoriteFood => FoodType.Meat; + public override bool CanAngerOnTame => true; - public override bool HasBreath => true; // fire breath enabled - public override int Meat => 5; - public override int Hides => 10; - public override HideType HideType => HideType.Barbed; - public override FoodType FavoriteFood => FoodType.Meat; - public override bool CanAngerOnTame => true; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.Potions); + } - public Nightmare( Serial serial ) : base( serial ) - { - } + public override int GetAngerSound() + { + if (!Controlled) + return 0x16A; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return base.GetAngerSound(); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Core.AOS && BaseSoundID == 0x16A ) - BaseSoundID = 0xA8; - else if ( !Core.AOS && BaseSoundID == 0xA8 ) - BaseSoundID = 0x16A; - } - } -} + int version = reader.ReadInt(); + + if (Core.AOS && BaseSoundID == 0x16A) + BaseSoundID = 0xA8; + else if (!Core.AOS && BaseSoundID == 0xA8) + BaseSoundID = 0x16A; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/RidableLlama.cs b/Scripts/Mobiles/Animals/Mounts/RidableLlama.cs index 01199ef86..9b55f150b 100644 --- a/Scripts/Mobiles/Animals/Mounts/RidableLlama.cs +++ b/Scripts/Mobiles/Animals/Mounts/RidableLlama.cs @@ -1,67 +1,68 @@ namespace Server.Mobiles { - public class RidableLlama : BaseMount - { - public override string CorpseName => "a llama corpse"; - [Constructible] - public RidableLlama() : this( "a ridable llama" ) - { - } + public class RidableLlama : BaseMount + { + [Constructible] + public RidableLlama() : this("a ridable llama") + { + } - [Constructible] - public RidableLlama( string name ) : base( name, 0xDC, 0x3EA6, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x3F3; + [Constructible] + public RidableLlama(string name) : base(name, 0xDC, 0x3EA6, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x3F3; - SetStr( 21, 49 ); - SetDex( 56, 75 ); - SetInt( 16, 30 ); + SetStr(21, 49); + SetDex(56, 75); + SetInt(16, 30); - SetHits( 15, 27 ); - SetMana( 0 ); + SetHits(15, 27); + SetMana(0); - SetDamage( 3, 5 ); + SetDamage(3, 5); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 10, 15 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetResistance(ResistanceType.Physical, 10, 15); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.2, 29.0 ); - SetSkill( SkillName.Wrestling, 19.2, 29.0 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.2, 29.0); + SetSkill(SkillName.Wrestling, 19.2, 29.0); - Fame = 300; - Karma = 0; + Fame = 300; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - public override int Meat => 1; - public override int Hides => 12; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public RidableLlama(Serial serial) : base(serial) + { + } - public RidableLlama( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a llama corpse"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int Meat => 1; + public override int Hides => 12; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Ridgeback.cs b/Scripts/Mobiles/Animals/Mounts/Ridgeback.cs index 1c4fd3b34..cc990bc7f 100644 --- a/Scripts/Mobiles/Animals/Mounts/Ridgeback.cs +++ b/Scripts/Mobiles/Animals/Mounts/Ridgeback.cs @@ -1,78 +1,79 @@ namespace Server.Mobiles { - public class Ridgeback : BaseMount - { - public override string CorpseName => "a ridgeback corpse"; - [Constructible] - public Ridgeback() : this( "a ridgeback" ) - { - } + public class Ridgeback : BaseMount + { + [Constructible] + public Ridgeback() : this("a ridgeback") + { + } - [Constructible] - public Ridgeback( string name ) : base( name, 187, 0x3EBA, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x3F3; + [Constructible] + public Ridgeback(string name) : base(name, 187, 0x3EBA, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x3F3; - SetStr( 58, 100 ); - SetDex( 56, 75 ); - SetInt( 16, 30 ); + SetStr(58, 100); + SetDex(56, 75); + SetInt(16, 30); - SetHits( 41, 54 ); - SetMana( 0 ); + SetHits(41, 54); + SetMana(0); - SetDamage( 3, 5 ); + SetDamage(3, 5); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 15, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetResistance(ResistanceType.Physical, 15, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetSkill( SkillName.MagicResist, 25.3, 40.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 35.1, 45.0 ); + SetSkill(SkillName.MagicResist, 25.3, 40.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 35.1, 45.0); - Fame = 300; - Karma = 0; + Fame = 300; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 83.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 83.1; + } - public override bool OverrideBondingReqs() - { - return true; - } + public Ridgeback(Serial serial) : base(serial) + { + } - public override double GetControlChance( Mobile m, bool useBaseSkill ) - { - return 1.0; - } + public override string CorpseName => "a ridgeback corpse"; - public override int Meat => 1; - public override int Hides => 12; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override int Meat => 1; + public override int Hides => 12; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public Ridgeback( Serial serial ) : base( serial ) - { - } + public override bool OverrideBondingReqs() + { + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override double GetControlChance(Mobile m, bool useBaseSkill) + { + return 1.0; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/SavageRidgeback.cs b/Scripts/Mobiles/Animals/Mounts/SavageRidgeback.cs index 0eed9a623..c66355aa2 100644 --- a/Scripts/Mobiles/Animals/Mounts/SavageRidgeback.cs +++ b/Scripts/Mobiles/Animals/Mounts/SavageRidgeback.cs @@ -1,78 +1,79 @@ namespace Server.Mobiles { - public class SavageRidgeback : BaseMount - { - public override string CorpseName => "a savage ridgeback corpse"; - [Constructible] - public SavageRidgeback() : this( "a savage ridgeback" ) - { - } + public class SavageRidgeback : BaseMount + { + [Constructible] + public SavageRidgeback() : this("a savage ridgeback") + { + } - [Constructible] - public SavageRidgeback( string name ) : base( name, 188, 0x3EB8, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x3F3; + [Constructible] + public SavageRidgeback(string name) : base(name, 188, 0x3EB8, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x3F3; - SetStr( 58, 100 ); - SetDex( 56, 75 ); - SetInt( 16, 30 ); + SetStr(58, 100); + SetDex(56, 75); + SetInt(16, 30); - SetHits( 41, 54 ); - SetMana( 0 ); + SetHits(41, 54); + SetMana(0); - SetDamage( 3, 5 ); + SetDamage(3, 5); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 15, 20 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 15, 20); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetSkill( SkillName.MagicResist, 25.3, 40.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 35.1, 45.0 ); + SetSkill(SkillName.MagicResist, 25.3, 40.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 35.1, 45.0); - Fame = 300; - Karma = 0; + Fame = 300; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 83.1; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 83.1; + } - public override bool OverrideBondingReqs() - { - return true; - } + public SavageRidgeback(Serial serial) : base(serial) + { + } - public override double GetControlChance( Mobile m, bool useBaseSkill ) - { - return 1.0; - } + public override string CorpseName => "a savage ridgeback corpse"; - public override int Meat => 1; - public override int Hides => 12; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override int Meat => 1; + public override int Hides => 12; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public SavageRidgeback( Serial serial ) : base( serial ) - { - } + public override bool OverrideBondingReqs() + { + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override double GetControlChance(Mobile m, bool useBaseSkill) + { + return 1.0; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/ScaledSwampDragon.cs b/Scripts/Mobiles/Animals/Mounts/ScaledSwampDragon.cs index ec6b0a4d6..6931c6e84 100644 --- a/Scripts/Mobiles/Animals/Mounts/ScaledSwampDragon.cs +++ b/Scripts/Mobiles/Animals/Mounts/ScaledSwampDragon.cs @@ -1,75 +1,77 @@ namespace Server.Mobiles { - public class ScaledSwampDragon : BaseMount - { - public override string CorpseName => "a swamp dragon corpse"; - [Constructible] - public ScaledSwampDragon() : this( "a swamp dragon" ) - { - } + public class ScaledSwampDragon : BaseMount + { + [Constructible] + public ScaledSwampDragon() : this("a swamp dragon") + { + } - [Constructible] - public ScaledSwampDragon( string name ) : base( name, 0x31F, 0x3EBE, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - SetStr( 201, 300 ); - SetDex( 66, 85 ); - SetInt( 61, 100 ); + [Constructible] + public ScaledSwampDragon(string name) : base(name, 0x31F, 0x3EBE, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, + 0.4) + { + SetStr(201, 300); + SetDex(66, 85); + SetInt(61, 100); - SetHits( 121, 180 ); + SetHits(121, 180); - SetDamage( 3, 4 ); + SetDamage(3, 4); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Poison, 25 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Poison, 25); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 20, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 20, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetSkill( SkillName.Anatomy, 45.1, 55.0 ); - SetSkill( SkillName.MagicResist, 45.1, 55.0 ); - SetSkill( SkillName.Tactics, 45.1, 55.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + SetSkill(SkillName.Anatomy, 45.1, 55.0); + SetSkill(SkillName.MagicResist, 45.1, 55.0); + SetSkill(SkillName.Tactics, 45.1, 55.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - Fame = 2000; - Karma = -2000; + Fame = 2000; + Karma = -2000; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 93.9; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 93.9; + } - public override bool OverrideBondingReqs() - { - return true; - } + public ScaledSwampDragon(Serial serial) : base(serial) + { + } - public override double GetControlChance( Mobile m, bool useBaseSkill ) - { - return 1.0; - } + public override string CorpseName => "a swamp dragon corpse"; - public override bool AutoDispel => !Controlled; - public override FoodType FavoriteFood => FoodType.Meat; + public override bool AutoDispel => !Controlled; + public override FoodType FavoriteFood => FoodType.Meat; - public ScaledSwampDragon( Serial serial ) : base( serial ) - { - } + public override bool OverrideBondingReqs() + { + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override double GetControlChance(Mobile m, bool useBaseSkill) + { + return 1.0; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/SeaHorse.cs b/Scripts/Mobiles/Animals/Mounts/SeaHorse.cs index c775a9277..5ce90c09b 100644 --- a/Scripts/Mobiles/Animals/Mounts/SeaHorse.cs +++ b/Scripts/Mobiles/Animals/Mounts/SeaHorse.cs @@ -1,38 +1,39 @@ namespace Server.Mobiles { - public class SeaHorse : BaseMount - { - public override string CorpseName => "a sea horse corpse"; - [Constructible] - public SeaHorse() : this( "a sea horse" ) - { - } + public class SeaHorse : BaseMount + { + [Constructible] + public SeaHorse() : this("a sea horse") + { + } - [Constructible] - public SeaHorse( string name ) : base( name, 0x90, 0x3EB3, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - InitStats( Utility.Random( 50, 30 ), Utility.Random( 50, 30 ), 10 ); - Skills[SkillName.MagicResist].Base = 25.0 + (Utility.RandomDouble() * 5.0); - Skills[SkillName.Wrestling].Base = 35.0 + (Utility.RandomDouble() * 10.0); - Skills[SkillName.Tactics].Base = 30.0 + (Utility.RandomDouble() * 15.0); - } + [Constructible] + public SeaHorse(string name) : base(name, 0x90, 0x3EB3, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + InitStats(Utility.Random(50, 30), Utility.Random(50, 30), 10); + Skills[SkillName.MagicResist].Base = 25.0 + Utility.RandomDouble() * 5.0; + Skills[SkillName.Wrestling].Base = 35.0 + Utility.RandomDouble() * 10.0; + Skills[SkillName.Tactics].Base = 30.0 + Utility.RandomDouble() * 15.0; + } - public SeaHorse( Serial serial ) : base( serial ) - { - } + public SeaHorse(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string CorpseName => "a sea horse corpse"; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/SilverSteed.cs b/Scripts/Mobiles/Animals/Mounts/SilverSteed.cs index 0bce9ce3c..fac33d9c6 100644 --- a/Scripts/Mobiles/Animals/Mounts/SilverSteed.cs +++ b/Scripts/Mobiles/Animals/Mounts/SilverSteed.cs @@ -1,42 +1,43 @@ namespace Server.Mobiles { - public class SilverSteed : BaseMount - { - public override string CorpseName => "a silver steed corpse"; - [Constructible] - public SilverSteed() : this( "a silver steed" ) - { - } + public class SilverSteed : BaseMount + { + [Constructible] + public SilverSteed() : this("a silver steed") + { + } - [Constructible] - public SilverSteed( string name ) : base( name, 0x75, 0x3EA8, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - InitStats( Utility.Random( 50, 30 ), Utility.Random( 50, 30 ), 10 ); - Skills[SkillName.MagicResist].Base = 25.0 + (Utility.RandomDouble() * 5.0); - Skills[SkillName.Wrestling].Base = 35.0 + (Utility.RandomDouble() * 10.0); - Skills[SkillName.Tactics].Base = 30.0 + (Utility.RandomDouble() * 15.0); + [Constructible] + public SilverSteed(string name) : base(name, 0x75, 0x3EA8, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + InitStats(Utility.Random(50, 30), Utility.Random(50, 30), 10); + Skills[SkillName.MagicResist].Base = 25.0 + Utility.RandomDouble() * 5.0; + Skills[SkillName.Wrestling].Base = 35.0 + Utility.RandomDouble() * 10.0; + Skills[SkillName.Tactics].Base = 30.0 + Utility.RandomDouble() * 15.0; - ControlSlots = 1; - Tamable = true; - MinTameSkill = 103.1; - } + ControlSlots = 1; + Tamable = true; + MinTameSkill = 103.1; + } - public SilverSteed( Serial serial ) : base( serial ) - { - } + public SilverSteed(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string CorpseName => "a silver steed corpse"; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/SkeletalMount.cs b/Scripts/Mobiles/Animals/Mounts/SkeletalMount.cs index ee3bf1e69..156170c47 100644 --- a/Scripts/Mobiles/Animals/Mounts/SkeletalMount.cs +++ b/Scripts/Mobiles/Animals/Mounts/SkeletalMount.cs @@ -1,72 +1,72 @@ namespace Server.Mobiles { - public class SkeletalMount : BaseMount - { - public override string CorpseName => "an undead horse corpse"; - public override string DefaultName => "a skeletal steed"; + public class SkeletalMount : BaseMount + { + [Constructible] + public SkeletalMount() : this(null) + { + } - [Constructible] - public SkeletalMount() : this( null ) - { - } + [Constructible] + public SkeletalMount(string name) : base(name, 793, 0x3EBB, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + SetStr(91, 100); + SetDex(46, 55); + SetInt(46, 60); - [Constructible] - public SkeletalMount( string name ) : base( name, 793, 0x3EBB, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - SetStr( 91, 100 ); - SetDex( 46, 55 ); - SetInt( 46, 60 ); + SetHits(41, 50); - SetHits( 41, 50 ); + SetDamage(5, 12); - SetDamage( 5, 12 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Cold, 90, 95); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Cold, 90, 95 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.MagicResist, 95.1, 100.0); + SetSkill(SkillName.Tactics, 50.0); + SetSkill(SkillName.Wrestling, 70.1, 80.0); - SetSkill( SkillName.MagicResist, 95.1, 100.0 ); - SetSkill( SkillName.Tactics, 50.0 ); - SetSkill( SkillName.Wrestling, 70.1, 80.0 ); + Fame = 0; + Karma = 0; + } - Fame = 0; - Karma = 0; - } + public SkeletalMount(Serial serial) : base(serial) + { + } - public override Poison PoisonImmune => Poison.Lethal; - public override bool BleedImmune => true; + public override string CorpseName => "an undead horse corpse"; + public override string DefaultName => "a skeletal steed"; - public SkeletalMount( Serial serial ) : base( serial ) - { - } + public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch( version ) - { - case 0: - { - Tamable = false; - MinTameSkill = 0.0; - ControlSlots = 0; - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Tamable = false; + MinTameSkill = 0.0; + ControlSlots = 0; + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/SwampDragon.cs b/Scripts/Mobiles/Animals/Mounts/SwampDragon.cs index cf3f5af4a..e6786bb0c 100644 --- a/Scripts/Mobiles/Animals/Mounts/SwampDragon.cs +++ b/Scripts/Mobiles/Animals/Mounts/SwampDragon.cs @@ -2,209 +2,222 @@ using Server.Items; namespace Server.Mobiles { - public class SwampDragon : BaseMount - { - public override string CorpseName => "a swamp dragon corpse"; - private bool m_BardingExceptional; - private Mobile m_BardingCrafter; - private int m_BardingHP; - private bool m_HasBarding; - private CraftResource m_BardingResource; + public class SwampDragon : BaseMount + { + private Mobile m_BardingCrafter; + private bool m_BardingExceptional; + private int m_BardingHP; + private CraftResource m_BardingResource; + private bool m_HasBarding; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile BardingCrafter - { - get => m_BardingCrafter; - set{ m_BardingCrafter = value; InvalidateProperties(); } - } + [Constructible] + public SwampDragon() : this("a swamp dragon") + { + } - [CommandProperty( AccessLevel.GameMaster )] - public bool BardingExceptional - { - get => m_BardingExceptional; - set{ m_BardingExceptional = value; InvalidateProperties(); } - } + [Constructible] + public SwampDragon(string name) : base(name, 0x31A, 0x3EBD, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x16A; - [CommandProperty( AccessLevel.GameMaster )] - public int BardingHP - { - get => m_BardingHP; - set{ m_BardingHP = value; InvalidateProperties(); } - } + SetStr(201, 300); + SetDex(66, 85); + SetInt(61, 100); - [CommandProperty( AccessLevel.GameMaster )] - public bool HasBarding - { - get => m_HasBarding; - set - { - m_HasBarding = value; + SetHits(121, 180); - if ( m_HasBarding ) - { - Hue = CraftResources.GetHue( m_BardingResource ); - BodyValue = 0x31F; - ItemID = 0x3EBE; - } - else - { - Hue = 0x851; - BodyValue = 0x31A; - ItemID = 0x3EBD; - } + SetDamage(3, 4); - InvalidateProperties(); - } - } + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Poison, 25); - [CommandProperty( AccessLevel.GameMaster )] - public CraftResource BardingResource - { - get => m_BardingResource; - set - { - m_BardingResource = value; + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 20, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - if ( m_HasBarding ) - Hue = CraftResources.GetHue( value ); + SetSkill(SkillName.Anatomy, 45.1, 55.0); + SetSkill(SkillName.MagicResist, 45.1, 55.0); + SetSkill(SkillName.Tactics, 45.1, 55.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - InvalidateProperties(); - } - } + Fame = 2000; + Karma = -2000; - [CommandProperty( AccessLevel.GameMaster )] - public int BardingMaxHP => m_BardingExceptional ? 2500 : 1000; + Hue = 0x851; - [Constructible] - public SwampDragon() : this( "a swamp dragon" ) - { - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = 93.9; + } - [Constructible] - public SwampDragon( string name ) : base( name, 0x31A, 0x3EBD, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x16A; + public SwampDragon(Serial serial) : base(serial) + { + } - SetStr( 201, 300 ); - SetDex( 66, 85 ); - SetInt( 61, 100 ); + public override string CorpseName => "a swamp dragon corpse"; - SetHits( 121, 180 ); + [CommandProperty(AccessLevel.GameMaster)] + public Mobile BardingCrafter + { + get => m_BardingCrafter; + set + { + m_BardingCrafter = value; + InvalidateProperties(); + } + } - SetDamage( 3, 4 ); + [CommandProperty(AccessLevel.GameMaster)] + public bool BardingExceptional + { + get => m_BardingExceptional; + set + { + m_BardingExceptional = value; + InvalidateProperties(); + } + } - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Poison, 25 ); + [CommandProperty(AccessLevel.GameMaster)] + public int BardingHP + { + get => m_BardingHP; + set + { + m_BardingHP = value; + InvalidateProperties(); + } + } - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 20, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + [CommandProperty(AccessLevel.GameMaster)] + public bool HasBarding + { + get => m_HasBarding; + set + { + m_HasBarding = value; - SetSkill( SkillName.Anatomy, 45.1, 55.0 ); - SetSkill( SkillName.MagicResist, 45.1, 55.0 ); - SetSkill( SkillName.Tactics, 45.1, 55.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + if (m_HasBarding) + { + Hue = CraftResources.GetHue(m_BardingResource); + BodyValue = 0x31F; + ItemID = 0x3EBE; + } + else + { + Hue = 0x851; + BodyValue = 0x31A; + ItemID = 0x3EBD; + } - Fame = 2000; - Karma = -2000; + InvalidateProperties(); + } + } - Hue = 0x851; + [CommandProperty(AccessLevel.GameMaster)] + public CraftResource BardingResource + { + get => m_BardingResource; + set + { + m_BardingResource = value; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 93.9; - } + if (m_HasBarding) + Hue = CraftResources.GetHue(value); - public override bool OverrideBondingReqs() - { - return true; - } + InvalidateProperties(); + } + } - public override int GetIdleSound() - { - return 0x2CE; - } + [CommandProperty(AccessLevel.GameMaster)] + public int BardingMaxHP => m_BardingExceptional ? 2500 : 1000; - public override int GetDeathSound() - { - return 0x2CC; - } + public override bool ReacquireOnMovement => true; + public override bool AutoDispel => !Controlled; + public override FoodType FavoriteFood => FoodType.Meat; + public override int Meat => 19; + public override int Hides => 20; + public override int Scales => 5; + public override ScaleType ScaleType => ScaleType.Green; + public override bool CanAngerOnTame => true; - public override int GetHurtSound() - { - return 0x2D1; - } + public override bool OverrideBondingReqs() + { + return true; + } - public override int GetAttackSound() - { - return 0x2C8; - } + public override int GetIdleSound() + { + return 0x2CE; + } - public override double GetControlChance( Mobile m, bool useBaseSkill ) - { - return 1.0; - } + public override int GetDeathSound() + { + return 0x2CC; + } - public override bool ReacquireOnMovement => true; - public override bool AutoDispel => !Controlled; - public override FoodType FavoriteFood => FoodType.Meat; - public override int Meat => 19; - public override int Hides => 20; - public override int Scales => 5; - public override ScaleType ScaleType => ScaleType.Green; - public override bool CanAngerOnTame => true; + public override int GetHurtSound() + { + return 0x2D1; + } - public SwampDragon( Serial serial ) : base( serial ) - { - } + public override int GetAttackSound() + { + return 0x2C8; + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override double GetControlChance(Mobile m, bool useBaseSkill) + { + return 1.0; + } - if ( m_HasBarding && m_BardingExceptional && m_BardingCrafter != null ) - list.Add( 1060853, m_BardingCrafter.Name ); // armor exceptionally crafted by ~1_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (m_HasBarding && m_BardingExceptional && m_BardingCrafter != null) + list.Add(1060853, m_BardingCrafter.Name); // armor exceptionally crafted by ~1_val~ + } - writer.Write( (int) 1 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (bool) m_BardingExceptional ); - writer.Write( (Mobile) m_BardingCrafter ); - writer.Write( (bool) m_HasBarding ); - writer.Write( (int) m_BardingHP ); - writer.Write( (int) m_BardingResource ); - } + writer.Write(1); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_BardingExceptional); + writer.Write(m_BardingCrafter); + writer.Write(m_HasBarding); + writer.Write(m_BardingHP); + writer.Write((int)m_BardingResource); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - { - m_BardingExceptional = reader.ReadBool(); - m_BardingCrafter = reader.ReadMobile(); - m_HasBarding = reader.ReadBool(); - m_BardingHP = reader.ReadInt(); - m_BardingResource = (CraftResource) reader.ReadInt(); - break; - } - } + int version = reader.ReadInt(); - if ( Hue == 0 && !m_HasBarding ) - Hue = 0x851; + switch (version) + { + case 1: + { + m_BardingExceptional = reader.ReadBool(); + m_BardingCrafter = reader.ReadMobile(); + m_HasBarding = reader.ReadBool(); + m_BardingHP = reader.ReadInt(); + m_BardingResource = (CraftResource)reader.ReadInt(); + break; + } + } - if ( BaseSoundID == -1 ) - BaseSoundID = 0x16A; - } - } -} + if (Hue == 0 && !m_HasBarding) + Hue = 0x851; + + if (BaseSoundID == -1) + BaseSoundID = 0x16A; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/Unicorn.cs b/Scripts/Mobiles/Animals/Mounts/Unicorn.cs index 8ea6e7a26..bfbe7d5f7 100644 --- a/Scripts/Mobiles/Animals/Mounts/Unicorn.cs +++ b/Scripts/Mobiles/Animals/Mounts/Unicorn.cs @@ -1,136 +1,137 @@ using System; using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class Unicorn : BaseMount - { - public override string CorpseName => "a unicorn corpse"; - public override bool AllowMaleRider => false; - public override bool AllowMaleTamer => false; + public class Unicorn : BaseMount + { + [Constructible] + public Unicorn() : this("a unicorn") + { + } - public override bool InitialInnocent => true; + [Constructible] + public Unicorn(string name) : base(name, 0x7A, 0x3EB4, AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + BaseSoundID = 0x4BC; - public override TimeSpan MountAbilityDelay => TimeSpan.FromHours( 1.0 ); + SetStr(296, 325); + SetDex(96, 115); + SetInt(186, 225); - public override void OnDisallowedRider( Mobile m ) - { - m.SendLocalizedMessage( 1042318 ); // The unicorn refuses to allow you to ride it. - } + SetHits(191, 210); - public override bool DoMountAbility( int damage, Mobile attacker ) - { - if ( Rider == null || attacker == null ) //sanity - return false; + SetDamage(16, 22); - if ( Rider.Poisoned && ((Rider.Hits - damage) < 40) ) - { - Poison p = Rider.Poison; + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Energy, 25); - if ( p != null ) - { - int chanceToCure = 10000 + (int)(Skills[SkillName.Magery].Value * 75) - ((p.Level + 1) * (Core.AOS ? (p.Level < 4 ? 3300 : 3100) : 1750)); - chanceToCure /= 100; + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 25, 40); + SetResistance(ResistanceType.Cold, 25, 40); + SetResistance(ResistanceType.Poison, 55, 65); + SetResistance(ResistanceType.Energy, 25, 40); - if ( chanceToCure > Utility.Random( 100 ) ) - { - if ( Rider.CurePoison( this ) ) //TODO: Confirm if mount is the one flagged for curing it or the rider is - { - Rider.LocalOverheadMessage( Network.MessageType.Regular, 0x3B2, true, "Your mount senses you are in danger and aids you with magic." ); - Rider.FixedParticles( 0x373A, 10, 15, 5012, EffectLayer.Waist ); - Rider.PlaySound( 0x1E0 ); // Cure spell effect. - Rider.PlaySound( 0xA9 ); // Unicorn's whinny. + SetSkill(SkillName.EvalInt, 80.1, 90.0); + SetSkill(SkillName.Magery, 60.2, 80.0); + SetSkill(SkillName.Meditation, 50.1, 60.0); + SetSkill(SkillName.MagicResist, 75.3, 90.0); + SetSkill(SkillName.Tactics, 20.1, 22.5); + SetSkill(SkillName.Wrestling, 80.5, 92.5); - return true; - } - } - } - } + Fame = 9000; + Karma = 9000; - return false; - } + Tamable = true; + ControlSlots = 2; + MinTameSkill = 95.1; + } - [Constructible] - public Unicorn() : this( "a unicorn" ) - { - } + public Unicorn(Serial serial) : base(serial) + { + } - [Constructible] - public Unicorn( string name ) : base( name, 0x7A, 0x3EB4, AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - BaseSoundID = 0x4BC; + public override string CorpseName => "a unicorn corpse"; + public override bool AllowMaleRider => false; + public override bool AllowMaleTamer => false; - SetStr( 296, 325 ); - SetDex( 96, 115 ); - SetInt( 186, 225 ); + public override bool InitialInnocent => true; - SetHits( 191, 210 ); + public override TimeSpan MountAbilityDelay => TimeSpan.FromHours(1.0); - SetDamage( 16, 22 ); + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Energy, 25 ); + public override Poison PoisonImmune => Poison.Lethal; + public override int Meat => 3; + public override int Hides => 10; + public override HideType HideType => HideType.Horned; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 25, 40 ); - SetResistance( ResistanceType.Cold, 25, 40 ); - SetResistance( ResistanceType.Poison, 55, 65 ); - SetResistance( ResistanceType.Energy, 25, 40 ); + public override void OnDisallowedRider(Mobile m) + { + m.SendLocalizedMessage(1042318); // The unicorn refuses to allow you to ride it. + } - SetSkill( SkillName.EvalInt, 80.1, 90.0 ); - SetSkill( SkillName.Magery, 60.2, 80.0 ); - SetSkill( SkillName.Meditation, 50.1, 60.0 ); - SetSkill( SkillName.MagicResist, 75.3, 90.0 ); - SetSkill( SkillName.Tactics, 20.1, 22.5 ); - SetSkill( SkillName.Wrestling, 80.5, 92.5 ); + public override bool DoMountAbility(int damage, Mobile attacker) + { + if (Rider == null || attacker == null) //sanity + return false; - Fame = 9000; - Karma = 9000; + if (Rider.Poisoned && Rider.Hits - damage < 40) + { + Poison p = Rider.Poison; - Tamable = true; - ControlSlots = 2; - MinTameSkill = 95.1; - } + if (p != null) + { + int chanceToCure = 10000 + (int)(Skills[SkillName.Magery].Value * 75) - + (p.Level + 1) * (Core.AOS ? p.Level < 4 ? 3300 : 3100 : 1750); + chanceToCure /= 100; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.Potions ); - } + if (chanceToCure > Utility.Random(100)) + if (Rider.CurePoison(this)) //TODO: Confirm if mount is the one flagged for curing it or the rider is + { + Rider.LocalOverheadMessage(MessageType.Regular, 0x3B2, true, + "Your mount senses you are in danger and aids you with magic."); + Rider.FixedParticles(0x373A, 10, 15, 5012, EffectLayer.Waist); + Rider.PlaySound(0x1E0); // Cure spell effect. + Rider.PlaySound(0xA9); // Unicorn's whinny. - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + return true; + } + } + } - if ( Utility.RandomDouble() < 0.35 ) - c.DropItem( new UnicornRibs() ); - } + return false; + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.Potions); + } - public override Poison PoisonImmune => Poison.Lethal; - public override int Meat => 3; - public override int Hides => 10; - public override HideType HideType => HideType.Horned; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public Unicorn( Serial serial ) : base( serial ) - { - } + if (Utility.RandomDouble() < 0.35) + c.DropItem(new UnicornRibs()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/War Horses/BaseWarHorse.cs b/Scripts/Mobiles/Animals/Mounts/War Horses/BaseWarHorse.cs index c68462c81..d7f43dcd7 100644 --- a/Scripts/Mobiles/Animals/Mounts/War Horses/BaseWarHorse.cs +++ b/Scripts/Mobiles/Animals/Mounts/War Horses/BaseWarHorse.cs @@ -1,62 +1,64 @@ namespace Server.Mobiles { - public abstract class BaseWarHorse : BaseMount - { - public override string CorpseName => "a war horse corpse"; + public abstract class BaseWarHorse : BaseMount + { + public BaseWarHorse(int bodyID, int itemID, AIType aiType, FightMode fightMode, int rangePerception, int rangeFight, + double activeSpeed, double passiveSpeed) : base("a war horse", bodyID, itemID, aiType, fightMode, + rangePerception, rangeFight, activeSpeed, passiveSpeed) + { + BaseSoundID = 0xA8; - public BaseWarHorse( int bodyID, int itemID, AIType aiType, FightMode fightMode, int rangePerception, int rangeFight, double activeSpeed, double passiveSpeed ) : base ( "a war horse", bodyID, itemID, aiType, fightMode, rangePerception, rangeFight, activeSpeed, passiveSpeed ) - { - BaseSoundID = 0xA8; + InitStats(Utility.Random(300, 100), 125, 60); - InitStats( Utility.Random( 300, 100 ), 125, 60 ); + SetStr(400); + SetDex(125); + SetInt(51, 55); - SetStr( 400 ); - SetDex( 125 ); - SetInt( 51, 55 ); + SetHits(240); + SetMana(0); - SetHits( 240 ); - SetMana( 0 ); + SetDamage(5, 8); - SetDamage( 5, 8 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + Fame = 300; + Karma = 300; - Fame = 300; - Karma = 300; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + public BaseWarHorse(Serial serial) : base(serial) + { + } - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override string CorpseName => "a war horse corpse"; - public BaseWarHorse( Serial serial ) : base( serial ) - { - } + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/War Horses/CoMWarHorse.cs b/Scripts/Mobiles/Animals/Mounts/War Horses/CoMWarHorse.cs index 7cdb9da86..e5a89a4a3 100644 --- a/Scripts/Mobiles/Animals/Mounts/War Horses/CoMWarHorse.cs +++ b/Scripts/Mobiles/Animals/Mounts/War Horses/CoMWarHorse.cs @@ -1,28 +1,28 @@ namespace Server.Mobiles { - public class CoMWarHorse : BaseWarHorse - { - [Constructible] - public CoMWarHorse() : base( 0x77, 0x3EB1, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - } + public class CoMWarHorse : BaseWarHorse + { + [Constructible] + public CoMWarHorse() : base(0x77, 0x3EB1, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + } - public CoMWarHorse( Serial serial ) : base( serial ) - { - } + public CoMWarHorse(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/War Horses/MinaxWarHorse.cs b/Scripts/Mobiles/Animals/Mounts/War Horses/MinaxWarHorse.cs index 6633507ba..7eff35d7a 100644 --- a/Scripts/Mobiles/Animals/Mounts/War Horses/MinaxWarHorse.cs +++ b/Scripts/Mobiles/Animals/Mounts/War Horses/MinaxWarHorse.cs @@ -1,28 +1,28 @@ namespace Server.Mobiles { - public class MinaxWarHorse : BaseWarHorse - { - [Constructible] - public MinaxWarHorse() : base( 0x78, 0x3EAF, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - } + public class MinaxWarHorse : BaseWarHorse + { + [Constructible] + public MinaxWarHorse() : base(0x78, 0x3EAF, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + } - public MinaxWarHorse( Serial serial ) : base( serial ) - { - } + public MinaxWarHorse(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/War Horses/SLWarHorse.cs b/Scripts/Mobiles/Animals/Mounts/War Horses/SLWarHorse.cs index f07cfc168..561e9209a 100644 --- a/Scripts/Mobiles/Animals/Mounts/War Horses/SLWarHorse.cs +++ b/Scripts/Mobiles/Animals/Mounts/War Horses/SLWarHorse.cs @@ -1,28 +1,28 @@ namespace Server.Mobiles { - public class SLWarHorse : BaseWarHorse - { - [Constructible] - public SLWarHorse() : base( 0x79, 0x3EB0, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - } + public class SLWarHorse : BaseWarHorse + { + [Constructible] + public SLWarHorse() : base(0x79, 0x3EB0, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + } - public SLWarHorse( Serial serial ) : base( serial ) - { - } + public SLWarHorse(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Mounts/War Horses/TBWarHorse.cs b/Scripts/Mobiles/Animals/Mounts/War Horses/TBWarHorse.cs index dd4a698b9..2c8881317 100644 --- a/Scripts/Mobiles/Animals/Mounts/War Horses/TBWarHorse.cs +++ b/Scripts/Mobiles/Animals/Mounts/War Horses/TBWarHorse.cs @@ -1,28 +1,28 @@ namespace Server.Mobiles { - public class TBWarHorse : BaseWarHorse - { - [Constructible] - public TBWarHorse() : base( 0x76, 0x3EB2, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - } + public class TBWarHorse : BaseWarHorse + { + [Constructible] + public TBWarHorse() : base(0x76, 0x3EB2, AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + } - public TBWarHorse( Serial serial ) : base( serial ) - { - } + public TBWarHorse(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/Alligator.cs b/Scripts/Mobiles/Animals/Reptiles/Alligator.cs index 94a0d4aec..cf2110f9b 100644 --- a/Scripts/Mobiles/Animals/Reptiles/Alligator.cs +++ b/Scripts/Mobiles/Animals/Reptiles/Alligator.cs @@ -1,70 +1,70 @@ namespace Server.Mobiles { - public class Alligator : BaseCreature - { - public override string CorpseName => "an alligator corpse"; - public override string DefaultName => "an alligator"; + public class Alligator : BaseCreature + { + [Constructible] + public Alligator() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0xCA; + BaseSoundID = 660; - [Constructible] - public Alligator() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0xCA; - BaseSoundID = 660; + SetStr(76, 100); + SetDex(6, 25); + SetInt(11, 20); - SetStr( 76, 100 ); - SetDex( 6, 25 ); - SetInt( 11, 20 ); + SetHits(46, 60); + SetStam(46, 65); + SetMana(0); - SetHits( 46, 60 ); - SetStam( 46, 65 ); - SetMana( 0 ); + SetDamage(5, 15); - SetDamage( 5, 15 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 40.1, 60.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 40.1, 60.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 600; + Karma = -600; - Fame = 600; - Karma = -600; + VirtualArmor = 30; - VirtualArmor = 30; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 47.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 47.1; - } + public Alligator(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 12; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; + public override string CorpseName => "an alligator corpse"; + public override string DefaultName => "an alligator"; - public Alligator(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 12; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( BaseSoundID == 0x5A ) - BaseSoundID = 660; - } - } -} + if (BaseSoundID == 0x5A) + BaseSoundID = 660; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/GiantSerpent.cs b/Scripts/Mobiles/Animals/Reptiles/GiantSerpent.cs index f63cd4792..ff03751fc 100644 --- a/Scripts/Mobiles/Animals/Reptiles/GiantSerpent.cs +++ b/Scripts/Mobiles/Animals/Reptiles/GiantSerpent.cs @@ -2,84 +2,84 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Serpant" )] - public class GiantSerpent : BaseCreature - { - public override string CorpseName => "a giant serpent corpse"; - public override string DefaultName => "a giant snake"; + [TypeAlias("Server.Mobiles.Serpant")] + public class GiantSerpent : BaseCreature + { + [Constructible] + public GiantSerpent() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x15; + Hue = Utility.RandomSnakeHue(); + BaseSoundID = 219; - [Constructible] - public GiantSerpent() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x15; - Hue = Utility.RandomSnakeHue(); - BaseSoundID = 219; + SetStr(186, 215); + SetDex(56, 80); + SetInt(66, 85); - SetStr( 186, 215 ); - SetDex( 56, 80 ); - SetInt( 66, 85 ); + SetHits(112, 129); + SetMana(0); - SetHits( 112, 129 ); - SetMana( 0 ); + SetDamage(7, 17); - SetDamage( 7, 17 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Poison, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Poison, 60 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 70, 90); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 70, 90 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Poisoning, 70.1, 100.0); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 65.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.Poisoning, 70.1, 100.0 ); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 65.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 32; - VirtualArmor = 32; + PackItem(new Bone()); + // TODO: Body parts + } - PackItem( new Bone() ); - // TODO: Body parts - } + public GiantSerpent(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a giant serpent corpse"; + public override string DefaultName => "a giant snake"; - public override Poison PoisonImmune => Poison.Greater; - public override Poison HitPoison => (0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly); + public override Poison PoisonImmune => Poison.Greater; + public override Poison HitPoison => 0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly; - public override bool DeathAdderCharmable => true; + public override bool DeathAdderCharmable => true; - public override int Meat => 4; - public override int Hides => 15; - public override HideType HideType => HideType.Spined; + public override int Meat => 4; + public override int Hides => 15; + public override HideType HideType => HideType.Spined; - public GiantSerpent(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( BaseSoundID == -1 ) - BaseSoundID = 219; - } - } -} + if (BaseSoundID == -1) + BaseSoundID = 219; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/IceSerpent.cs b/Scripts/Mobiles/Animals/Reptiles/IceSerpent.cs index 93a3f6f78..feecb3caf 100644 --- a/Scripts/Mobiles/Animals/Reptiles/IceSerpent.cs +++ b/Scripts/Mobiles/Animals/Reptiles/IceSerpent.cs @@ -2,95 +2,115 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Iceserpant" )] - public class IceSerpent : BaseCreature - { - public override string CorpseName => "an ice serpent corpse"; - public override string DefaultName => "a giant ice serpent"; + [TypeAlias("Server.Mobiles.Iceserpant")] + public class IceSerpent : BaseCreature + { + [Constructible] + public IceSerpent() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 89; + BaseSoundID = 219; - [Constructible] - public IceSerpent() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 89; - BaseSoundID = 219; + SetStr(216, 245); + SetDex(26, 50); + SetInt(66, 85); - SetStr( 216, 245 ); - SetDex( 26, 50 ); - SetInt( 66, 85 ); + SetHits(130, 147); + SetMana(0); - SetHits( 130, 147 ); - SetMana( 0 ); + SetDamage(7, 17); - SetDamage( 7, 17 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Cold, 90); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Cold, 90 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Cold, 80, 90); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Cold, 80, 90 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Anatomy, 27.5, 50.0); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 75.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.Anatomy, 27.5, 50.0 ); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 75.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 32; - VirtualArmor = 32; + PackItem(Loot.RandomArmorOrShieldOrWeapon()); - PackItem( Loot.RandomArmorOrShieldOrWeapon() ); + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } - switch ( Utility.Random( 10 )) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } + if (0.025 > Utility.RandomDouble()) + PackItem(new GlacialStaff()); + } - if ( 0.025 > Utility.RandomDouble() ) - PackItem( new GlacialStaff() ); - } + public IceSerpent(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "an ice serpent corpse"; + public override string DefaultName => "a giant ice serpent"; - public override bool DeathAdderCharmable => true; + public override bool DeathAdderCharmable => true; - public override int Meat => 4; - public override int Hides => 15; - public override HideType HideType => HideType.Spined; + public override int Meat => 4; + public override int Hides => 15; + public override HideType HideType => HideType.Spined; - public IceSerpent(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( BaseSoundID == -1 ) - BaseSoundID = 219; - } - } -} + if (BaseSoundID == -1) + BaseSoundID = 219; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/IceSnake.cs b/Scripts/Mobiles/Animals/Reptiles/IceSnake.cs index fbd84dd6f..71dbe35b6 100644 --- a/Scripts/Mobiles/Animals/Reptiles/IceSnake.cs +++ b/Scripts/Mobiles/Animals/Reptiles/IceSnake.cs @@ -1,70 +1,70 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Icesnake" )] - public class IceSnake : BaseCreature - { - public override string CorpseName => "an ice snake corpse"; - public override string DefaultName => "an ice snake"; + [TypeAlias("Server.Mobiles.Icesnake")] + public class IceSnake : BaseCreature + { + [Constructible] + public IceSnake() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 52; + Hue = 0x480; + BaseSoundID = 0xDB; - [Constructible] - public IceSnake() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 52; - Hue = 0x480; - BaseSoundID = 0xDB; + SetStr(42, 54); + SetDex(36, 45); + SetInt(26, 30); - SetStr( 42, 54 ); - SetDex( 36, 45 ); - SetInt( 26, 30 ); + SetMana(0); - SetMana( 0 ); + SetDamage(4, 12); - SetDamage( 4, 12 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Cold, 25); + SetDamageType(ResistanceType.Poison, 50); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Cold, 25 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Cold, 80, 90); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Cold, 80, 90 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 39.3, 54.0); + SetSkill(SkillName.Wrestling, 39.3, 54.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 39.3, 54.0 ); - SetSkill( SkillName.Wrestling, 39.3, 54.0 ); + Fame = 900; + Karma = -900; - Fame = 900; - Karma = -900; + VirtualArmor = 30; + } - VirtualArmor = 30; - } + public IceSnake(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "an ice snake corpse"; + public override string DefaultName => "an ice snake"; - public override bool DeathAdderCharmable => true; + public override bool DeathAdderCharmable => true; - public override int Meat => 1; + public override int Meat => 1; - public IceSnake(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/LavaLizard.cs b/Scripts/Mobiles/Animals/Reptiles/LavaLizard.cs index 81de67df0..edcc47dec 100644 --- a/Scripts/Mobiles/Animals/Reptiles/LavaLizard.cs +++ b/Scripts/Mobiles/Animals/Reptiles/LavaLizard.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Lavalizard" )] - public class LavaLizard : BaseCreature - { - public override string CorpseName => "a lava lizard corpse"; - public override string DefaultName => "a lava lizard"; + [TypeAlias("Server.Mobiles.Lavalizard")] + public class LavaLizard : BaseCreature + { + [Constructible] + public LavaLizard() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0xCE; + Hue = Utility.RandomList(0x647, 0x650, 0x659, 0x662, 0x66B, 0x674); + BaseSoundID = 0x5A; - [Constructible] - public LavaLizard() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0xCE; - Hue = Utility.RandomList( 0x647, 0x650, 0x659, 0x662, 0x66B, 0x674 ); - BaseSoundID = 0x5A; + SetStr(126, 150); + SetDex(56, 75); + SetInt(11, 20); - SetStr( 126, 150 ); - SetDex( 56, 75 ); - SetInt( 11, 20 ); + SetHits(76, 90); + SetMana(0); - SetHits( 76, 90 ); - SetMana( 0 ); + SetDamage(6, 24); - SetDamage( 6, 24 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 30, 45); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 30, 45 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 60.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 60.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 40; - VirtualArmor = 40; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 80.7; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 80.7; + PackItem(new SulfurousAsh(Utility.Random(4, 10))); + } - PackItem( new SulfurousAsh( Utility.Random( 4, 10 ) ) ); - } + public LavaLizard(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a lava lizard corpse"; + public override string DefaultName => "a lava lizard"; - public override bool HasBreath => true; // fire breath enabled - public override int Hides => 12; - public override HideType HideType => HideType.Spined; + public override bool HasBreath => true; // fire breath enabled + public override int Hides => 12; + public override HideType HideType => HideType.Spined; - public LavaLizard(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/LavaSerpent.cs b/Scripts/Mobiles/Animals/Reptiles/LavaSerpent.cs index bbc33bde7..32d4de04f 100644 --- a/Scripts/Mobiles/Animals/Reptiles/LavaSerpent.cs +++ b/Scripts/Mobiles/Animals/Reptiles/LavaSerpent.cs @@ -2,80 +2,80 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Lavaserpant" )] - public class LavaSerpent : BaseCreature - { - public override string CorpseName => "a lava serpent corpse"; - public override string DefaultName => "a lava serpent"; + [TypeAlias("Server.Mobiles.Lavaserpant")] + public class LavaSerpent : BaseCreature + { + [Constructible] + public LavaSerpent() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 90; + BaseSoundID = 219; - [Constructible] - public LavaSerpent() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 90; - BaseSoundID = 219; + SetStr(386, 415); + SetDex(56, 80); + SetInt(66, 85); - SetStr( 386, 415 ); - SetDex( 56, 80 ); - SetInt( 66, 85 ); + SetHits(232, 249); + SetMana(0); - SetHits( 232, 249 ); - SetMana( 0 ); + SetDamage(10, 22); - SetDamage( 10, 22 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Fire, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Fire, 80 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 25.3, 70.0); + SetSkill(SkillName.Tactics, 65.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.MagicResist, 25.3, 70.0 ); - SetSkill( SkillName.Tactics, 65.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 4500; + Karma = -4500; - Fame = 4500; - Karma = -4500; + VirtualArmor = 40; - VirtualArmor = 40; + PackItem(new SulfurousAsh(3)); + PackItem(new Bone()); + // TODO: body parts, armour + } - PackItem( new SulfurousAsh( 3 ) ); - PackItem( new Bone() ); - // TODO: body parts, armour - } + public LavaSerpent(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a lava serpent corpse"; + public override string DefaultName => "a lava serpent"; - public override bool DeathAdderCharmable => true; + public override bool DeathAdderCharmable => true; - public override bool HasBreath => true; // fire breath enabled - public override int Meat => 4; - public override int Hides => 15; - public override HideType HideType => HideType.Spined; + public override bool HasBreath => true; // fire breath enabled + public override int Meat => 4; + public override int Hides => 15; + public override HideType HideType => HideType.Spined; - public LavaSerpent(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( BaseSoundID == -1 ) - BaseSoundID = 219; - } - } -} + if (BaseSoundID == -1) + BaseSoundID = 219; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/LavaSnake.cs b/Scripts/Mobiles/Animals/Reptiles/LavaSnake.cs index 03ba1eda1..3dde97144 100644 --- a/Scripts/Mobiles/Animals/Reptiles/LavaSnake.cs +++ b/Scripts/Mobiles/Animals/Reptiles/LavaSnake.cs @@ -2,73 +2,73 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Lavasnake" )] - public class LavaSnake : BaseCreature - { - public override string CorpseName => "a lava snake corpse"; - public override string DefaultName => "a lava snake"; + [TypeAlias("Server.Mobiles.Lavasnake")] + public class LavaSnake : BaseCreature + { + [Constructible] + public LavaSnake() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 52; + Hue = Utility.RandomList(0x647, 0x650, 0x659, 0x662, 0x66B, 0x674); + BaseSoundID = 0xDB; - [Constructible] - public LavaSnake() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 52; - Hue = Utility.RandomList( 0x647, 0x650, 0x659, 0x662, 0x66B, 0x674 ); - BaseSoundID = 0xDB; + SetStr(43, 55); + SetDex(16, 25); + SetInt(6, 10); - SetStr( 43, 55 ); - SetDex( 16, 25 ); - SetInt( 6, 10 ); + SetHits(28, 32); + SetMana(0); - SetHits( 28, 32 ); - SetMana( 0 ); + SetDamage(1, 8); - SetDamage( 1, 8 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.3, 34.0); + SetSkill(SkillName.Wrestling, 19.3, 34.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.3, 34.0 ); - SetSkill( SkillName.Wrestling, 19.3, 34.0 ); + Fame = 600; + Karma = -600; - Fame = 600; - Karma = -600; + VirtualArmor = 24; - VirtualArmor = 24; + PackItem(new SulfurousAsh()); + } - PackItem( new SulfurousAsh() ); - } + public LavaSnake(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a lava snake corpse"; + public override string DefaultName => "a lava snake"; - public override bool DeathAdderCharmable => true; + public override bool DeathAdderCharmable => true; - public override bool HasBreath => true; // fire breath enabled - public override int Meat => 1; + public override bool HasBreath => true; // fire breath enabled + public override int Meat => 1; - public LavaSnake(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/SilverSerpent.cs b/Scripts/Mobiles/Animals/Reptiles/SilverSerpent.cs index adbadc0dc..5d545c3de 100644 --- a/Scripts/Mobiles/Animals/Reptiles/SilverSerpent.cs +++ b/Scripts/Mobiles/Animals/Reptiles/SilverSerpent.cs @@ -1,81 +1,82 @@ +using Server.Ethics; using Server.Factions; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Silverserpant" )] - public class SilverSerpent : BaseCreature - { - public override string CorpseName => "a silver serpent corpse"; - public override Faction FactionAllegiance => TrueBritannians.Instance; - public override Ethics.Ethic EthicAllegiance => Ethics.Ethic.Hero; + [TypeAlias("Server.Mobiles.Silverserpant")] + public class SilverSerpent : BaseCreature + { + [Constructible] + public SilverSerpent() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 92; + BaseSoundID = 219; - public override string DefaultName => "a silver serpent"; + SetStr(161, 360); + SetDex(151, 300); + SetInt(21, 40); - [Constructible] - public SilverSerpent() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 92; - BaseSoundID = 219; + SetHits(97, 216); - SetStr( 161, 360 ); - SetDex( 151, 300 ); - SetInt( 21, 40 ); + SetDamage(5, 21); - SetHits( 97, 216 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamage( 5, 21 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 5, 10); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetSkill(SkillName.Poisoning, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 95.1, 100.0); + SetSkill(SkillName.Tactics, 80.1, 95.0); + SetSkill(SkillName.Wrestling, 85.1, 100.0); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + Fame = 7000; + Karma = -7000; - SetSkill( SkillName.Poisoning, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 95.1, 100.0 ); - SetSkill( SkillName.Tactics, 80.1, 95.0 ); - SetSkill( SkillName.Wrestling, 85.1, 100.0 ); + VirtualArmor = 40; + } - Fame = 7000; - Karma = -7000; + public SilverSerpent(Serial serial) : base(serial) + { + } - VirtualArmor = 40; - } + public override string CorpseName => "a silver serpent corpse"; + public override Faction FactionAllegiance => TrueBritannians.Instance; + public override Ethic EthicAllegiance => Ethic.Hero; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string DefaultName => "a silver serpent"; - public override bool DeathAdderCharmable => true; + public override bool DeathAdderCharmable => true; - public override int Meat => 1; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; + public override int Meat => 1; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; - public SilverSerpent(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( BaseSoundID == -1 ) - BaseSoundID = 219; - } - } -} + if (BaseSoundID == -1) + BaseSoundID = 219; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Reptiles/Snake.cs b/Scripts/Mobiles/Animals/Reptiles/Snake.cs index cd85ebab5..530b31c7e 100644 --- a/Scripts/Mobiles/Animals/Reptiles/Snake.cs +++ b/Scripts/Mobiles/Animals/Reptiles/Snake.cs @@ -1,70 +1,70 @@ namespace Server.Mobiles { - public class Snake : BaseCreature - { - public override string CorpseName => "a snake corpse"; - public override string DefaultName => "a snake"; + public class Snake : BaseCreature + { + [Constructible] + public Snake() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 52; + Hue = Utility.RandomSnakeHue(); + BaseSoundID = 0xDB; - [Constructible] - public Snake() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 52; - Hue = Utility.RandomSnakeHue(); - BaseSoundID = 0xDB; + SetStr(22, 34); + SetDex(16, 25); + SetInt(6, 10); - SetStr( 22, 34 ); - SetDex( 16, 25 ); - SetInt( 6, 10 ); + SetHits(15, 19); + SetMana(0); - SetHits( 15, 19 ); - SetMana( 0 ); + SetDamage(1, 4); - SetDamage( 1, 4 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Poison, 20, 30); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Poison, 20, 30 ); + SetSkill(SkillName.Poisoning, 50.1, 70.0); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.3, 34.0); + SetSkill(SkillName.Wrestling, 19.3, 34.0); - SetSkill( SkillName.Poisoning, 50.1, 70.0 ); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.3, 34.0 ); - SetSkill( SkillName.Wrestling, 19.3, 34.0 ); + Fame = 300; + Karma = -300; - Fame = 300; - Karma = -300; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 59.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 59.1; - } + public Snake(Serial serial) : base(serial) + { + } - public override Poison PoisonImmune => Poison.Lesser; - public override Poison HitPoison => Poison.Lesser; + public override string CorpseName => "a snake corpse"; + public override string DefaultName => "a snake"; - public override bool DeathAdderCharmable => true; + public override Poison PoisonImmune => Poison.Lesser; + public override Poison HitPoison => Poison.Lesser; - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Eggs; + public override bool DeathAdderCharmable => true; - public Snake(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Eggs; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Rodents/GiantRat.cs b/Scripts/Mobiles/Animals/Rodents/GiantRat.cs index 3aaf09125..f5094325e 100644 --- a/Scripts/Mobiles/Animals/Rodents/GiantRat.cs +++ b/Scripts/Mobiles/Animals/Rodents/GiantRat.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Giantrat" )] - public class GiantRat : BaseCreature - { - public override string CorpseName => "a giant rat corpse"; - public override string DefaultName => "a giant rat"; + [TypeAlias("Server.Mobiles.Giantrat")] + public class GiantRat : BaseCreature + { + [Constructible] + public GiantRat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0xD7; + BaseSoundID = 0x188; - [Constructible] - public GiantRat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0xD7; - BaseSoundID = 0x188; + SetStr(32, 74); + SetDex(46, 65); + SetInt(16, 30); - SetStr( 32, 74 ); - SetDex( 46, 65 ); - SetInt( 16, 30 ); + SetHits(26, 39); + SetMana(0); - SetHits( 26, 39 ); - SetMana( 0 ); + SetDamage(4, 8); - SetDamage( 4, 8 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Poison, 25, 35); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Poison, 25, 35 ); + SetSkill(SkillName.MagicResist, 25.1, 30.0); + SetSkill(SkillName.Tactics, 29.3, 44.0); + SetSkill(SkillName.Wrestling, 29.3, 44.0); - SetSkill( SkillName.MagicResist, 25.1, 30.0 ); - SetSkill( SkillName.Tactics, 29.3, 44.0 ); - SetSkill( SkillName.Wrestling, 29.3, 44.0 ); + Fame = 300; + Karma = -300; - Fame = 300; - Karma = -300; + VirtualArmor = 18; - VirtualArmor = 18; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 29.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 29.1; - } + public GiantRat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a giant rat corpse"; + public override string DefaultName => "a giant rat"; - public override int Meat => 1; - public override int Hides => 6; - public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat | FoodType.FruitsAndVegies | FoodType.Eggs; + public override int Meat => 1; + public override int Hides => 6; + public override FoodType FavoriteFood => FoodType.Fish | FoodType.Meat | FoodType.FruitsAndVegies | FoodType.Eggs; - public GiantRat(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Rodents/JackRabbit.cs b/Scripts/Mobiles/Animals/Rodents/JackRabbit.cs index 5bcd5acfc..6c480f50d 100644 --- a/Scripts/Mobiles/Animals/Rodents/JackRabbit.cs +++ b/Scripts/Mobiles/Animals/Rodents/JackRabbit.cs @@ -1,79 +1,79 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Jackrabbit" )] - public class JackRabbit : BaseCreature - { - public override string CorpseName => "a jack rabbit corpse"; - public override string DefaultName => "a jack rabbit"; + [TypeAlias("Server.Mobiles.Jackrabbit")] + public class JackRabbit : BaseCreature + { + [Constructible] + public JackRabbit() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xCD; + Hue = 0x1BB; - [Constructible] - public JackRabbit() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xCD; - Hue = 0x1BB; + SetStr(15); + SetDex(25); + SetInt(5); - SetStr( 15 ); - SetDex( 25 ); - SetInt( 5 ); + SetHits(9); + SetMana(0); - SetHits( 9 ); - SetMana( 0 ); + SetDamage(1, 2); - SetDamage( 1, 2 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 2, 5); - SetResistance( ResistanceType.Physical, 2, 5 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 150; + Karma = 0; - Fame = 150; - Karma = 0; + VirtualArmor = 4; - VirtualArmor = 4; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -18.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -18.9; - } + public JackRabbit(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 1; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies; + public override string CorpseName => "a jack rabbit corpse"; + public override string DefaultName => "a jack rabbit"; - public JackRabbit(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 1; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies; - public override int GetAttackSound() - { - return 0xC9; - } + public override int GetAttackSound() + { + return 0xC9; + } - public override int GetHurtSound() - { - return 0xCA; - } + public override int GetHurtSound() + { + return 0xCA; + } - public override int GetDeathSound() - { - return 0xCB; - } + public override int GetDeathSound() + { + return 0xCB; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Rodents/Rabbit.cs b/Scripts/Mobiles/Animals/Rodents/Rabbit.cs index 5b76bcd68..3b94236e4 100644 --- a/Scripts/Mobiles/Animals/Rodents/Rabbit.cs +++ b/Scripts/Mobiles/Animals/Rodents/Rabbit.cs @@ -1,80 +1,80 @@ namespace Server.Mobiles { - public class Rabbit : BaseCreature - { - public override string CorpseName => "a hare corpse"; - public override string DefaultName => "a rabbit"; + public class Rabbit : BaseCreature + { + [Constructible] + public Rabbit() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 205; - [Constructible] - public Rabbit() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 205; + if (Utility.RandomBool()) + Hue = Utility.RandomAnimalHue(); - if ( Utility.RandomBool() ) - Hue = Utility.RandomAnimalHue(); + SetStr(6, 10); + SetDex(26, 38); + SetInt(6, 14); - SetStr( 6, 10 ); - SetDex( 26, 38 ); - SetInt( 6, 14 ); + SetHits(4, 6); + SetMana(0); - SetHits( 4, 6 ); - SetMana( 0 ); + SetDamage(1); - SetDamage( 1 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 150; + Karma = 0; - Fame = 150; - Karma = 0; + VirtualArmor = 6; - VirtualArmor = 6; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -18.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -18.9; - } + public Rabbit(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int Hides => 1; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies; + public override string CorpseName => "a hare corpse"; + public override string DefaultName => "a rabbit"; - public Rabbit(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override int Hides => 1; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies; - public override int GetAttackSound() - { - return 0xC9; - } + public override int GetAttackSound() + { + return 0xC9; + } - public override int GetHurtSound() - { - return 0xCA; - } + public override int GetHurtSound() + { + return 0xCA; + } - public override int GetDeathSound() - { - return 0xCB; - } + public override int GetDeathSound() + { + return 0xCB; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Rodents/SewerRat.cs b/Scripts/Mobiles/Animals/Rodents/SewerRat.cs index 695bc2164..03deb1aca 100644 --- a/Scripts/Mobiles/Animals/Rodents/SewerRat.cs +++ b/Scripts/Mobiles/Animals/Rodents/SewerRat.cs @@ -1,70 +1,70 @@ namespace Server.Mobiles { - [TypeAlias("Server.Mobiles.Sewerrat")] - public class SewerRat : BaseCreature - { - public override string CorpseName => "a rat corpse"; - public override string DefaultName => "a sewer rat"; + [TypeAlias("Server.Mobiles.Sewerrat")] + public class SewerRat : BaseCreature + { + [Constructible] + public SewerRat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 238; + BaseSoundID = 0xCC; - [Constructible] - public SewerRat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 238; - BaseSoundID = 0xCC; + SetStr(9); + SetDex(25); + SetInt(6, 10); - SetStr( 9 ); - SetDex( 25 ); - SetInt( 6, 10 ); + SetHits(6); + SetMana(0); - SetHits( 6 ); - SetMana( 0 ); + SetDamage(1, 2); - SetDamage( 1, 2 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 300; + Karma = -300; - Fame = 300; - Karma = -300; + VirtualArmor = 6; - VirtualArmor = 6; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -0.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -0.9; - } + public SewerRat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a rat corpse"; + public override string DefaultName => "a sewer rat"; - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Eggs | FoodType.FruitsAndVegies; + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Eggs | FoodType.FruitsAndVegies; - public SewerRat(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Slimes/Jwilson.cs b/Scripts/Mobiles/Animals/Slimes/Jwilson.cs index 931b94800..3b3242c26 100644 --- a/Scripts/Mobiles/Animals/Slimes/Jwilson.cs +++ b/Scripts/Mobiles/Animals/Slimes/Jwilson.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - public class Jwilson : BaseCreature - { - public override string CorpseName => "a jwilson corpse"; - public override string DefaultName => "a jwilson"; + public class Jwilson : BaseCreature + { + [Constructible] + public Jwilson() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Hue = Utility.RandomList(0x89C, 0x8A2, 0x8A8, 0x8AE); + Body = 0x33; + VirtualArmor = 8; - [Constructible] - public Jwilson() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Hue = Utility.RandomList(0x89C,0x8A2,0x8A8,0x8AE); - Body = 0x33; - VirtualArmor = 8; + InitStats(Utility.Random(22, 13), Utility.Random(16, 6), Utility.Random(16, 5)); - InitStats(Utility.Random(22,13),Utility.Random(16,6),Utility.Random(16,5)); + Skills[SkillName.Wrestling].Base = Utility.Random(24, 17); + Skills[SkillName.Tactics].Base = Utility.Random(18, 14); + Skills[SkillName.MagicResist].Base = Utility.Random(15, 6); + Skills[SkillName.Poisoning].Base = Utility.Random(31, 20); - Skills[SkillName.Wrestling].Base = Utility.Random(24,17); - Skills[SkillName.Tactics].Base = Utility.Random(18,14); - Skills[SkillName.MagicResist].Base = Utility.Random(15,6); - Skills[SkillName.Poisoning].Base = Utility.Random(31,20); + Fame = Utility.Random(0, 1249); + Karma = Utility.Random(0, -624); + } - Fame = Utility.Random(0,1249); - Karma = Utility.Random(0,-624); - } + public Jwilson(Serial serial) : base(serial) + { + } - public Jwilson(Serial serial) : base(serial) - { - } + public override string CorpseName => "a jwilson corpse"; + public override string DefaultName => "a jwilson"; - public override int GetAngerSound() - { - return 0x1C8; - } + public override int GetAngerSound() + { + return 0x1C8; + } - public override int GetIdleSound() - { - return 0x1C9; - } + public override int GetIdleSound() + { + return 0x1C9; + } - public override int GetAttackSound() - { - return 0x1CA; - } + public override int GetAttackSound() + { + return 0x1CA; + } - public override int GetHurtSound() - { - return 0x1CB; - } + public override int GetHurtSound() + { + return 0x1CB; + } - public override int GetDeathSound() - { - return 0x1CC; - } + public override int GetDeathSound() + { + return 0x1CC; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Town Critters/(UO 3D Only) Parrot.cs b/Scripts/Mobiles/Animals/Town Critters/(UO 3D Only) Parrot.cs index 30c97004a..b8f356b91 100644 --- a/Scripts/Mobiles/Animals/Town Critters/(UO 3D Only) Parrot.cs +++ b/Scripts/Mobiles/Animals/Town Critters/(UO 3D Only) Parrot.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class Parrot : BaseCreature - { - public override string CorpseName => "a parrot corpse"; - public override string DefaultName => "a parrot"; + public class Parrot : BaseCreature + { + [Constructible] + public Parrot() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 831; + VirtualArmor = Utility.Random(0, 6); - [Constructible] - public Parrot() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 831; - VirtualArmor = Utility.Random(0,6); + InitStats(10, Utility.Random(25, 16), 10); - InitStats((10),Utility.Random(25,16),(10)); + Skills[SkillName.Wrestling].Base = 6; + Skills[SkillName.Tactics].Base = 6; + Skills[SkillName.MagicResist].Base = 5; - Skills[SkillName.Wrestling].Base = (6); - Skills[SkillName.Tactics].Base = (6); - Skills[SkillName.MagicResist].Base = (5); + Fame = Utility.Random(0, 1249); + Karma = Utility.Random(0, -624); - Fame = Utility.Random(0,1249); - Karma = Utility.Random(0,-624); + Tamable = true; + ControlSlots = 1; + MinTameSkill = 0.0; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 0.0; - } + public Parrot(Serial serial) : base(serial) + { + } - public Parrot(Serial serial) : base(serial) - { - } + public override string CorpseName => "a parrot corpse"; + public override string DefaultName => "a parrot"; - public override int GetAngerSound() - { - return 0x1B; - } + public override int GetAngerSound() + { + return 0x1B; + } - public override int GetIdleSound() - { - return 0x1C; - } + public override int GetIdleSound() + { + return 0x1C; + } - public override int GetAttackSound() - { - return 0x1D; - } + public override int GetAttackSound() + { + return 0x1D; + } - public override int GetHurtSound() - { - return 0x1E; - } + public override int GetHurtSound() + { + return 0x1E; + } - public override int GetDeathSound() - { - return 0x1F; - } + public override int GetDeathSound() + { + return 0x1F; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Town Critters/Bird.cs b/Scripts/Mobiles/Animals/Town Critters/Bird.cs index a9a769e0d..a9ebb7e1c 100644 --- a/Scripts/Mobiles/Animals/Town Critters/Bird.cs +++ b/Scripts/Mobiles/Animals/Town Critters/Bird.cs @@ -1,136 +1,143 @@ namespace Server.Mobiles { - public class Bird : BaseCreature - { - public override string CorpseName => "a bird corpse"; - [Constructible] - public Bird() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - if ( Utility.RandomBool() ) - { - Hue = 0x901; + public class Bird : BaseCreature + { + [Constructible] + public Bird() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + if (Utility.RandomBool()) + { + Hue = 0x901; - switch ( Utility.Random( 3 ) ) - { - case 0: Name = "a crow"; break; - case 2: Name = "a raven"; break; - case 1: Name = "a magpie"; break; - } - } - else - { - Hue = Utility.RandomBirdHue(); - Name = NameList.RandomName( "bird" ); - } + switch (Utility.Random(3)) + { + case 0: + Name = "a crow"; + break; + case 2: + Name = "a raven"; + break; + case 1: + Name = "a magpie"; + break; + } + } + else + { + Hue = Utility.RandomBirdHue(); + Name = NameList.RandomName("bird"); + } - Body = 6; - BaseSoundID = 0x1B; + Body = 6; + BaseSoundID = 0x1B; - VirtualArmor = Utility.RandomMinMax( 0, 6 ); + VirtualArmor = Utility.RandomMinMax(0, 6); - SetStr( 10 ); - SetDex( 25, 35 ); - SetInt( 10 ); + SetStr(10); + SetDex(25, 35); + SetInt(10); - SetDamage( 0 ); + SetDamage(0); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.Wrestling, 4.2, 6.4 ); - SetSkill( SkillName.Tactics, 4.0, 6.0 ); - SetSkill( SkillName.MagicResist, 4.0, 5.0 ); + SetSkill(SkillName.Wrestling, 4.2, 6.4); + SetSkill(SkillName.Tactics, 4.0, 6.0); + SetSkill(SkillName.MagicResist, 4.0, 5.0); - Fame = 150; - Karma = 0; + Fame = 150; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = -6.9; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = -6.9; + } - public override MeatType MeatType => MeatType.Bird; - public override int Meat => 1; - public override int Feathers => 25; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public Bird(Serial serial) : base(serial) + { + } - public Bird( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a bird corpse"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override MeatType MeatType => MeatType.Bird; + public override int Meat => 1; + public override int Feathers => 25; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Hue == 0 ) - Hue = Utility.RandomBirdHue(); - } - } + int version = reader.ReadInt(); - public class TropicalBird : BaseCreature - { - public override string CorpseName => "a bird corpse"; - public override string DefaultName => "a tropical bird"; + if (Hue == 0) + Hue = Utility.RandomBirdHue(); + } + } - [Constructible] - public TropicalBird() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Hue = Utility.RandomBirdHue(); + public class TropicalBird : BaseCreature + { + [Constructible] + public TropicalBird() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Hue = Utility.RandomBirdHue(); - Body = 6; - BaseSoundID = 0xBF; + Body = 6; + BaseSoundID = 0xBF; - VirtualArmor = Utility.RandomMinMax( 0, 6 ); + VirtualArmor = Utility.RandomMinMax(0, 6); - SetStr( 10 ); - SetDex( 25, 35 ); - SetInt( 10 ); + SetStr(10); + SetDex(25, 35); + SetInt(10); - SetDamage( 0 ); + SetDamage(0); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.Wrestling, 4.2, 6.4 ); - SetSkill( SkillName.Tactics, 4.0, 6.0 ); - SetSkill( SkillName.MagicResist, 4.0, 5.0 ); + SetSkill(SkillName.Wrestling, 4.2, 6.4); + SetSkill(SkillName.Tactics, 4.0, 6.0); + SetSkill(SkillName.MagicResist, 4.0, 5.0); - Fame = 150; - Karma = 0; + Fame = 150; + Karma = 0; - Tamable = true; - ControlSlots = 1; - MinTameSkill = -6.9; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = -6.9; + } - public override MeatType MeatType => MeatType.Bird; - public override int Meat => 1; - public override int Feathers => 25; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public TropicalBird(Serial serial) : base(serial) + { + } - public TropicalBird( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a bird corpse"; + public override string DefaultName => "a tropical bird"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override MeatType MeatType => MeatType.Bird; + public override int Meat => 1; + public override int Feathers => 25; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Town Critters/Cat.cs b/Scripts/Mobiles/Animals/Town Critters/Cat.cs index 7d5160496..f154911d4 100644 --- a/Scripts/Mobiles/Animals/Town Critters/Cat.cs +++ b/Scripts/Mobiles/Animals/Town Critters/Cat.cs @@ -1,65 +1,65 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Housecat" )] - public class Cat : BaseCreature - { - public override string CorpseName => "a cat corpse"; - public override string DefaultName => "a cat"; + [TypeAlias("Server.Mobiles.Housecat")] + public class Cat : BaseCreature + { + [Constructible] + public Cat() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xC9; + Hue = Utility.RandomAnimalHue(); + BaseSoundID = 0x69; - [Constructible] - public Cat() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xC9; - Hue = Utility.RandomAnimalHue(); - BaseSoundID = 0x69; + SetStr(9); + SetDex(35); + SetInt(5); - SetStr( 9 ); - SetDex( 35 ); - SetInt( 5 ); + SetHits(6); + SetMana(0); - SetHits( 6 ); - SetMana( 0 ); + SetDamage(1); - SetDamage( 1 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); + SetSkill(SkillName.MagicResist, 5.0); + SetSkill(SkillName.Tactics, 4.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 5.0 ); - SetSkill( SkillName.Tactics, 4.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 0; + Karma = 150; - Fame = 0; - Karma = 150; + VirtualArmor = 8; - VirtualArmor = 8; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -0.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -0.9; - } + public Cat(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; - public override PackInstinct PackInstinct => PackInstinct.Feline; + public override string CorpseName => "a cat corpse"; + public override string DefaultName => "a cat"; - public Cat(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; + public override PackInstinct PackInstinct => PackInstinct.Feline; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Town Critters/Dog.cs b/Scripts/Mobiles/Animals/Town Critters/Dog.cs index 96e1bf69c..45fc1efaa 100644 --- a/Scripts/Mobiles/Animals/Town Critters/Dog.cs +++ b/Scripts/Mobiles/Animals/Town Critters/Dog.cs @@ -1,64 +1,64 @@ namespace Server.Mobiles { - public class Dog : BaseCreature - { - public override string CorpseName => "a dog corpse"; - public override string DefaultName => "a dog"; + public class Dog : BaseCreature + { + [Constructible] + public Dog() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0xD9; + Hue = Utility.RandomAnimalHue(); + BaseSoundID = 0x85; - [Constructible] - public Dog() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0xD9; - Hue = Utility.RandomAnimalHue(); - BaseSoundID = 0x85; + SetStr(27, 37); + SetDex(28, 43); + SetInt(29, 37); - SetStr( 27, 37 ); - SetDex( 28, 43 ); - SetInt( 29, 37 ); + SetHits(17, 22); + SetMana(0); - SetHits( 17, 22 ); - SetMana( 0 ); + SetDamage(4, 7); - SetDamage( 4, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 10, 15); - SetResistance( ResistanceType.Physical, 10, 15 ); + SetSkill(SkillName.MagicResist, 22.1, 47.0); + SetSkill(SkillName.Tactics, 19.2, 31.0); + SetSkill(SkillName.Wrestling, 19.2, 31.0); - SetSkill( SkillName.MagicResist, 22.1, 47.0 ); - SetSkill( SkillName.Tactics, 19.2, 31.0 ); - SetSkill( SkillName.Wrestling, 19.2, 31.0 ); + Fame = 0; + Karma = 300; - Fame = 0; - Karma = 300; + VirtualArmor = 12; - VirtualArmor = 12; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -15.3; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -15.3; - } + public Dog(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override string CorpseName => "a dog corpse"; + public override string DefaultName => "a dog"; - public Dog(Serial serial) : base(serial) - { - } + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Animals/Town Critters/Rat.cs b/Scripts/Mobiles/Animals/Town Critters/Rat.cs index 00eacceee..7d8c14057 100644 --- a/Scripts/Mobiles/Animals/Town Critters/Rat.cs +++ b/Scripts/Mobiles/Animals/Town Critters/Rat.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - public class Rat : BaseCreature - { - public override string CorpseName => "a rat corpse"; - public override string DefaultName => "a rat"; + public class Rat : BaseCreature + { + [Constructible] + public Rat() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 238; + BaseSoundID = 0xCC; - [Constructible] - public Rat() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 238; - BaseSoundID = 0xCC; + SetStr(9); + SetDex(35); + SetInt(5); - SetStr( 9 ); - SetDex( 35 ); - SetInt( 5 ); + SetHits(6); + SetMana(0); - SetHits( 6 ); - SetMana( 0 ); + SetDamage(1, 2); - SetDamage( 1, 2 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 4.0); + SetSkill(SkillName.Tactics, 4.0); + SetSkill(SkillName.Wrestling, 4.0); - SetSkill( SkillName.MagicResist, 4.0 ); - SetSkill( SkillName.Tactics, 4.0 ); - SetSkill( SkillName.Wrestling, 4.0 ); + Fame = 150; + Karma = -150; - Fame = 150; - Karma = -150; + VirtualArmor = 6; - VirtualArmor = 6; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -0.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -0.9; - } + public Rat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a rat corpse"; + public override string DefaultName => "a rat"; - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish | FoodType.Eggs | FoodType.GrainsAndHay; + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish | FoodType.Eggs | FoodType.GrainsAndHay; - public Rat(Serial serial) : base(serial) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int) 0); - } + writer.Write(0); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/BaseCreature.cs b/Scripts/Mobiles/BaseCreature.cs index f7c8351ec..03f8a8971 100644 --- a/Scripts/Mobiles/BaseCreature.cs +++ b/Scripts/Mobiles/BaseCreature.cs @@ -1,5316 +1,5418 @@ using System; using System.Collections.Generic; using System.Threading.Tasks; -using Server.Regions; -using Server.Targeting; -using Server.Network; -using Server.Multis; -using Server.Spells; -using Server.Misc; -using Server.Items; using Server.ContextMenus; -using Server.Engines.Quests; +using Server.Engines.ConPVP; using Server.Engines.MLQuests; using Server.Engines.PartySystem; +using Server.Engines.Quests; +using Server.Engines.Quests.Doom; +using Server.Engines.Quests.Haven; +using Server.Ethics; using Server.Factions; +using Server.Items; +using Server.Misc; +using Server.Multis; +using Server.Network; +using Server.Regions; using Server.SkillHandlers; +using Server.Spells; using Server.Spells.Bushido; -using Server.Spells.Spellweaving; using Server.Spells.Necromancy; +using Server.Spells.Sixth; +using Server.Spells.Spellweaving; +using Server.Targeting; namespace Server.Mobiles { - #region Enums - /// - /// Summary description for MobileAI. - /// - /// - public enum FightMode - { - None, // Never focus on others - Aggressor, // Only attack aggressors - Strongest, // Attack the strongest - Weakest, // Attack the weakest - Closest, // Attack the closest - Evil // Only attack aggressor -or- negative karma - } - - public enum OrderType - { - None, //When no order, let's roam - Come, //"(All/Name) come" Summons all or one pet to your location. - Drop, //"(Name) drop" Drops its loot to the ground (if it carries any). - Follow, //"(Name) follow" Follows targeted being. - //"(All/Name) follow me" Makes all or one pet follow you. - Friend, //"(Name) friend" Allows targeted player to confirm resurrection. - Unfriend, // Remove a friend - Guard, //"(Name) guard" Makes the specified pet guard you. Pets can only guard their owner. - //"(All/Name) guard me" Makes all or one pet guard you. - Attack, //"(All/Name) kill", - //"(All/Name) attack" All or the specified pet(s) currently under your control attack the target. - Patrol, //"(Name) patrol" Roves between two or more guarded targets. - Release, //"(Name) release" Releases pet back into the wild (removes "tame" status). - Stay, //"(All/Name) stay" All or the specified pet(s) will stop and stay in current spot. - Stop, //"(All/Name) stop Cancels any current orders to attack, guard or follow. - Transfer //"(Name) transfer" Transfers complete ownership to targeted player. - } - - [Flags] - public enum FoodType - { - None = 0x0000, - Meat = 0x0001, - FruitsAndVegies = 0x0002, - GrainsAndHay = 0x0004, - Fish = 0x0008, - Eggs = 0x0010, - Gold = 0x0020 - } - - [Flags] - public enum PackInstinct - { - None = 0x0000, - Canine = 0x0001, - Ostard = 0x0002, - Feline = 0x0004, - Arachnid = 0x0008, - Daemon = 0x0010, - Bear = 0x0020, - Equine = 0x0040, - Bull = 0x0080 - } - - public enum ScaleType - { - Red, - Yellow, - Black, - Green, - White, - Blue, - All - } - - public enum MeatType - { - Ribs, - Bird, - LambLeg - } - - public enum HideType - { - Regular, - Spined, - Horned, - Barbed - } - - #endregion - - public class DamageStore : IComparable - { - public Mobile m_Mobile; - public int m_Damage; - public bool m_HasRight; - - public DamageStore( Mobile m, int damage ) - { - m_Mobile = m; - m_Damage = damage; - } - - public int CompareTo( object obj ) - { - DamageStore ds = (DamageStore)obj; - - return ds.m_Damage - m_Damage; - } - } - - [AttributeUsage( AttributeTargets.Class )] - public class FriendlyNameAttribute : Attribute - { - //future use: Talisman 'Protection/Bonus vs. Specific Creature - - public TextDefinition FriendlyName { get; } - - public FriendlyNameAttribute( TextDefinition friendlyName ) - { - FriendlyName = friendlyName; - } - - public static TextDefinition GetFriendlyNameFor( Type t ) - { - if ( t.IsDefined( typeof( FriendlyNameAttribute ), false ) ) - { - object[] objs = t.GetCustomAttributes( typeof( FriendlyNameAttribute ), false ); - - if ( objs != null && objs.Length > 0 ) - { - FriendlyNameAttribute friendly = objs[0] as FriendlyNameAttribute; - - return friendly.FriendlyName; - } - } - - return t.Name; - } - } - - public partial class BaseCreature : Mobile, IHonorTarget, IQuestGiver - { - public const int MaxLoyalty = 100; - - #region Var declarations - - private AIType m_CurrentAI; // The current AI - private AIType m_DefaultAI; // The default AI - - private int m_Team; // Monster Team - - private double m_CurrentSpeed; // The current speed, lets say it could be changed by something; - - private Point3D m_Home; // The home position of the creature, used by some AI - - List m_SpellAttack; // List of attack spell/power - List m_SpellDefense; // List of defensive spell/power - - private bool m_Controlled; // Is controlled - private Mobile m_ControlMaster; // My master - private OrderType m_ControlOrder; // My order + #region Enums + + /// + /// Summary description for MobileAI. + /// + public enum FightMode + { + None, // Never focus on others + Aggressor, // Only attack aggressors + Strongest, // Attack the strongest + Weakest, // Attack the weakest + Closest, // Attack the closest + Evil // Only attack aggressor -or- negative karma + } + + public enum OrderType + { + None, //When no order, let's roam + Come, //"(All/Name) come" Summons all or one pet to your location. + Drop, //"(Name) drop" Drops its loot to the ground (if it carries any). + Follow, //"(Name) follow" Follows targeted being. + + //"(All/Name) follow me" Makes all or one pet follow you. + Friend, //"(Name) friend" Allows targeted player to confirm resurrection. + Unfriend, // Remove a friend + Guard, //"(Name) guard" Makes the specified pet guard you. Pets can only guard their owner. + + //"(All/Name) guard me" Makes all or one pet guard you. + Attack, //"(All/Name) kill", + + //"(All/Name) attack" All or the specified pet(s) currently under your control attack the target. + Patrol, //"(Name) patrol" Roves between two or more guarded targets. + Release, //"(Name) release" Releases pet back into the wild (removes "tame" status). + Stay, //"(All/Name) stay" All or the specified pet(s) will stop and stay in current spot. + Stop, //"(All/Name) stop Cancels any current orders to attack, guard or follow. + Transfer //"(Name) transfer" Transfers complete ownership to targeted player. + } + + [Flags] + public enum FoodType + { + None = 0x0000, + Meat = 0x0001, + FruitsAndVegies = 0x0002, + GrainsAndHay = 0x0004, + Fish = 0x0008, + Eggs = 0x0010, + Gold = 0x0020 + } + + [Flags] + public enum PackInstinct + { + None = 0x0000, + Canine = 0x0001, + Ostard = 0x0002, + Feline = 0x0004, + Arachnid = 0x0008, + Daemon = 0x0010, + Bear = 0x0020, + Equine = 0x0040, + Bull = 0x0080 + } + + public enum ScaleType + { + Red, + Yellow, + Black, + Green, + White, + Blue, + All + } + + public enum MeatType + { + Ribs, + Bird, + LambLeg + } + + public enum HideType + { + Regular, + Spined, + Horned, + Barbed + } + + #endregion + + public class DamageStore : IComparable + { + public int m_Damage; + public bool m_HasRight; + public Mobile m_Mobile; + + public DamageStore(Mobile m, int damage) + { + m_Mobile = m; + m_Damage = damage; + } + + public int CompareTo(object obj) + { + DamageStore ds = (DamageStore)obj; + + return ds.m_Damage - m_Damage; + } + } + + [AttributeUsage(AttributeTargets.Class)] + public class FriendlyNameAttribute : Attribute + { + public FriendlyNameAttribute(TextDefinition friendlyName) + { + FriendlyName = friendlyName; + } + //future use: Talisman 'Protection/Bonus vs. Specific Creature + + public TextDefinition FriendlyName{ get; } + + public static TextDefinition GetFriendlyNameFor(Type t) + { + if (t.IsDefined(typeof(FriendlyNameAttribute), false)) + { + object[] objs = t.GetCustomAttributes(typeof(FriendlyNameAttribute), false); + + if (objs != null && objs.Length > 0) + { + FriendlyNameAttribute friendly = objs[0] as FriendlyNameAttribute; + + return friendly.FriendlyName; + } + } + + return t.Name; + } + } + + public class BaseCreature : Mobile, IHonorTarget, IQuestGiver + { + public const int MaxLoyalty = 100; + + public const int MaxOwners = 5; - private int m_Loyalty; + public const int DefaultRangePerception = 16; + public const int OldRangePerception = 10; - private bool m_bTamable; + private const double ChanceToRummage = 0.5; // 50% - private bool m_bSummoned; + private const double MinutesToNextRummageMin = 1.0; + private const double MinutesToNextRummageMax = 4.0; - private Mobile m_SummonMaster; + private const double MinutesToNextChanceMin = 0.25; + private const double MinutesToNextChanceMax = 0.75; - private int m_DamageMin = -1; - private int m_DamageMax = -1; + private static Type[] m_AnimateDeadTypes = + { + typeof(MoundOfMaggots), typeof(HellSteed), typeof(SkeletalMount), + typeof(WailingBanshee), typeof(Wraith), typeof(SkeletalDragon), + typeof(LichLord), typeof(FleshGolem), typeof(Lich), + typeof(SkeletalKnight), typeof(BoneKnight), typeof(Mummy), + typeof(SkeletalMage), typeof(BoneMagi), typeof(PatchworkSkeleton) + }; - private int m_PhysicalResistance; - private int m_FireResistance; - private int m_ColdResistance; - private int m_PoisonResistance; - private int m_EnergyResistance; + private static double[] m_StandardActiveSpeeds = + { + 0.175, 0.1, 0.15, 0.2, 0.25, 0.3, 0.4, 0.5, 0.6, 0.8 + }; - private bool m_IsStabled; + private static double[] m_StandardPassiveSpeeds = + { + 0.350, 0.2, 0.4, 0.5, 0.6, 0.8, 1.0, 1.2, 1.6, 2.0 + }; - private bool m_HasGeneratedLoot; // have we generated our loot yet? + private static Mobile m_NoDupeGuards; - private bool m_Paragon; + private static bool EnableRummaging = true; - private int m_FailedReturnHome; /* return to home failure counter */ + private DateTime m_IdleReleaseTime; - #endregion + private long m_NextRummageTime; - public virtual string DefaultName => null; - public virtual string CorpseName => null; + /* until we are sure about who should be getting deleted, move them instead */ + /* On OSI, they despawn */ - [CommandProperty(AccessLevel.GameMaster)] - public override string Name - { - get - { - if (NameMod == null && base.Name == null) - return DefaultName; + private bool m_ReturnQueued; - return base.Name; - } - set - { - if (value == DefaultName) - base.Name = null; - else - base.Name = value; - } - } + public BaseCreature(AIType ai, + FightMode mode, + int iRangePerception, + int iRangeFight, + double dActiveSpeed, + double dPassiveSpeed) + { + if (iRangePerception == OldRangePerception) + iRangePerception = DefaultRangePerception; - public virtual InhumanSpeech SpeechType => null; + m_Loyalty = MaxLoyalty; // Wonderfully Happy - /* Do not serialize this till the code is finalized */ + m_CurrentAI = ai; + m_DefaultAI = ai; - [CommandProperty( AccessLevel.GameMaster )] - public bool SeeksHome { get; set; } + RangePerception = iRangePerception; + RangeFight = iRangeFight; - [CommandProperty( AccessLevel.GameMaster )] - public string CorpseNameOverride { get; set; } + FightMode = mode; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public bool IsStabled - { - get => m_IsStabled; - set - { - m_IsStabled = value; - if ( m_IsStabled ) - StopDeleteTimer(); - } - } + m_Team = 0; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public Mobile StabledBy { get; set; } + SpeedInfo.GetSpeeds(this, ref dActiveSpeed, ref dPassiveSpeed); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsPrisoner { get; set; } + ActiveSpeed = dActiveSpeed; + PassiveSpeed = dPassiveSpeed; + m_CurrentSpeed = dPassiveSpeed; - protected DateTime SummonEnd { get; set; } + Debug = false; - public virtual Faction FactionAllegiance => null; - public virtual int FactionSilverWorth => 30; + m_SpellAttack = new List(); + m_SpellDefense = new List(); - #region ML Quest System + m_Controlled = false; + m_ControlMaster = null; + ControlTarget = null; + m_ControlOrder = OrderType.None; - private List m_MLQuests; + m_bTamable = false; - public List MLQuests - { - get - { - if ( m_MLQuests == null ) - { - if ( StaticMLQuester ) - m_MLQuests = MLQuestSystem.FindQuestList( GetType() ); - else - m_MLQuests = ConstructQuestList(); + Owners = new List(); - if ( m_MLQuests == null ) - return MLQuestSystem.EmptyList; // return EmptyList, but don't cache it (run construction again next time) - } + NextReacquireTime = Core.TickCount + (int)ReacquireDelay.TotalMilliseconds; - return m_MLQuests; - } - } + ChangeAIType(AI); - public virtual bool CanGiveMLQuest => ( MLQuests.Count != 0 ); - public virtual bool StaticMLQuester => true; + InhumanSpeech speechType = SpeechType; - protected virtual List ConstructQuestList() - { - return null; - } + speechType?.OnConstruct(this); - public virtual bool CanShout => false; + if (IsInvulnerable && !Core.AOS) + NameHue = 0x35; - public const int ShoutRange = 8; - public static readonly TimeSpan ShoutDelay = TimeSpan.FromMinutes( 1 ); + GenerateLoot(true); + } - private DateTime m_MLNextShout; + public BaseCreature(Serial serial) : base(serial) + { + m_SpellAttack = new List(); + m_SpellDefense = new List(); - private void CheckShout( PlayerMobile pm, Point3D oldLocation ) - { - if ( m_MLNextShout > DateTime.UtcNow || pm.Hidden || !pm.Alive ) - return; + Debug = false; + } - int shoutRange = ShoutRange; + public virtual string DefaultName => null; + public virtual string CorpseName => null; - if ( !InRange( pm.Location, shoutRange ) || InRange( oldLocation, shoutRange ) || !CanSee( pm ) || !InLOS( pm ) ) - return; + [CommandProperty(AccessLevel.GameMaster)] + public override string Name + { + get + { + if (NameMod == null && base.Name == null) + return DefaultName; - MLQuestContext context = MLQuestSystem.GetContext( pm ); - - if ( context != null && context.IsFull ) - return; + return base.Name; + } + set + { + if (value == DefaultName) + base.Name = null; + else + base.Name = value; + } + } - MLQuest quest = MLQuestSystem.RandomStarterQuest( this, pm, context ); + public virtual InhumanSpeech SpeechType => null; - if ( quest == null || !quest.Activated || ( context != null && context.IsDoingQuest( quest ) ) ) - return; - - Shout( pm ); - m_MLNextShout = DateTime.UtcNow + ShoutDelay; - } + /* Do not serialize this till the code is finalized */ - public virtual void Shout( PlayerMobile pm ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public bool SeeksHome{ get; set; } - #endregion - - #region Bonding - public const bool BondingEnabled = true; - - public virtual bool IsBondable => ( BondingEnabled && !Summoned ); - public virtual TimeSpan BondingDelay => TimeSpan.FromDays( 7.0 ); - public virtual TimeSpan BondingAbandonDelay => TimeSpan.FromDays( 1.0 ); - - public override bool CanRegenHits => !IsDeadPet && base.CanRegenHits; - public override bool CanRegenStam => !IsParagon && !IsDeadPet && base.CanRegenStam; - public override bool CanRegenMana => !IsDeadPet && base.CanRegenMana; - - public override bool IsDeadBondedPet => IsDeadPet; - - private bool m_IsBonded; + [CommandProperty(AccessLevel.GameMaster)] + public string CorpseNameOverride{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public Spawner MySpawner - { - get => Spawner as Spawner; - set - { - } - } + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public bool IsStabled + { + get => m_IsStabled; + set + { + m_IsStabled = value; + if (m_IsStabled) + StopDeleteTimer(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile LastOwner - { - get - { - if ( Owners == null || Owners.Count == 0 ) - return null; + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public Mobile StabledBy{ get; set; } - return Owners[Owners.Count - 1]; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsBonded - { - get => m_IsBonded; - set{ m_IsBonded = value; InvalidateProperties(); } - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsPrisoner{ get; set; } - public bool IsDeadPet { get; set; } + protected DateTime SummonEnd{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime BondingBegin { get; set; } + public virtual Faction FactionAllegiance => null; + public virtual int FactionSilverWorth => 30; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime OwnerAbandonTime { get; set; } + public virtual double WeaponAbilityChance => 0.4; - #endregion + [CommandProperty(AccessLevel.GameMaster)] + public bool IsParagon + { + get => m_Paragon; + set + { + if (m_Paragon == value) + return; + if (value) + Paragon.Convert(this); + else + Paragon.UnConvert(this); - #region Delete Previously Tamed Timer - private DeleteTimer m_DeleteTimer; + m_Paragon = value; - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan DeleteTimeLeft - { - get - { - if ( m_DeleteTimer != null && m_DeleteTimer.Running ) - return m_DeleteTimer.Next - DateTime.UtcNow; + InvalidateProperties(); + } + } - return TimeSpan.Zero; - } - } + public virtual bool HasManaOveride => false; - private class DeleteTimer : Timer - { - private Mobile m; - - public DeleteTimer( Mobile creature, TimeSpan delay ) : base( delay ) - { - m = creature; - Priority = TimerPriority.OneMinute; - } - - protected override void OnTick() - { - m.Delete(); - } - } - - public void BeginDeleteTimer() - { - if ( !(this is BaseEscortable) && !Summoned && !Deleted && !IsStabled ) - { - StopDeleteTimer(); - m_DeleteTimer = new DeleteTimer( this, TimeSpan.FromDays( 3.0 ) ); - m_DeleteTimer.Start(); - } - } - - public void StopDeleteTimer() - { - if ( m_DeleteTimer != null ) - { - m_DeleteTimer.Stop(); - m_DeleteTimer = null; - } - } - - #endregion - - public virtual double WeaponAbilityChance => 0.4; - - public virtual WeaponAbility GetWeaponAbility() - { - return null; - } - - #region Elemental Resistance/Damage - - public override int BasePhysicalResistance => m_PhysicalResistance; - public override int BaseFireResistance => m_FireResistance; - public override int BaseColdResistance => m_ColdResistance; - public override int BasePoisonResistance => m_PoisonResistance; - public override int BaseEnergyResistance => m_EnergyResistance; - - [CommandProperty( AccessLevel.GameMaster )] - public int PhysicalResistanceSeed{ get => m_PhysicalResistance; - set{ m_PhysicalResistance = value; UpdateResistances(); } } + public virtual FoodType FavoriteFood => FoodType.Meat; + public virtual PackInstinct PackInstinct => PackInstinct.None; - [CommandProperty( AccessLevel.GameMaster )] - public int FireResistSeed{ get => m_FireResistance; - set{ m_FireResistance = value; UpdateResistances(); } } + public List Owners{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public int ColdResistSeed{ get => m_ColdResistance; - set{ m_ColdResistance = value; UpdateResistances(); } } + public virtual bool AllowMaleTamer => true; + public virtual bool AllowFemaleTamer => true; + public virtual bool SubdueBeforeTame => false; + public virtual bool StatLossAfterTame => SubdueBeforeTame; + public virtual bool ReduceSpeedWithDamage => true; + public virtual bool IsSubdued => SubdueBeforeTame && Hits < HitsMax / 10; - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonResistSeed{ get => m_PoisonResistance; - set{ m_PoisonResistance = value; UpdateResistances(); } } + public virtual bool Commandable => true; - [CommandProperty( AccessLevel.GameMaster )] - public int EnergyResistSeed{ get => m_EnergyResistance; - set{ m_EnergyResistance = value; UpdateResistances(); } } + public virtual Poison HitPoison => null; + public virtual double HitPoisonChance => 0.5; + public virtual Poison PoisonImmune => null; - [CommandProperty( AccessLevel.GameMaster )] - public int PhysicalDamage { get; set; } = 100; + public virtual bool BardImmune => false; + public virtual bool Unprovokable => BardImmune || IsDeadPet; + public virtual bool Uncalmable => BardImmune || IsDeadPet; + public virtual bool AreaPeaceImmune => BardImmune || IsDeadPet; - [CommandProperty( AccessLevel.GameMaster )] - public int FireDamage { get; set; } + public virtual bool BleedImmune => false; + public virtual double BonusPetDamageScalar => 1.0; - [CommandProperty( AccessLevel.GameMaster )] - public int ColdDamage { get; set; } + public virtual bool DeathAdderCharmable => false; - [CommandProperty( AccessLevel.GameMaster )] - public int PoisonDamage { get; set; } + //TODO: Find the pub 31 tweaks to the DispelDifficulty and apply them of course. + public virtual double DispelDifficulty // at this skill level we dispel 50% chance + => 0.0; - [CommandProperty( AccessLevel.GameMaster )] - public int EnergyDamage { get; set; } + public virtual double DispelFocus // at difficulty - focus we have 0%, at difficulty + focus we have 100% + => 20.0; - [CommandProperty( AccessLevel.GameMaster )] - public int ChaosDamage { get; set; } + public virtual bool DisplayWeight => Backpack is StrongBackpack; - [CommandProperty( AccessLevel.GameMaster )] - public int DirectDamage { get; set; } + public virtual bool CanFly => false; - #endregion + public virtual bool IsInvulnerable => false; - [CommandProperty( AccessLevel.GameMaster )] - public bool IsParagon - { - get => m_Paragon; - set - { - if ( m_Paragon == value ) - return; - if ( value ) - Paragon.Convert( this ); - else - Paragon.UnConvert( this ); + public BaseAI AIObject{ get; private set; } - m_Paragon = value; + public virtual OppositionGroup OppositionGroup => null; - InvalidateProperties(); - } - } + public virtual bool IsAnimatedDead + { + get + { + if (!Summoned) + return false; - public virtual bool HasManaOveride => false; + Type type = GetType(); - public virtual FoodType FavoriteFood => FoodType.Meat; - public virtual PackInstinct PackInstinct => PackInstinct.None; + bool contains = false; - public List Owners { get; private set; } + for (int i = 0; !contains && i < m_AnimateDeadTypes.Length; ++i) + contains = type == m_AnimateDeadTypes[i]; - public virtual bool AllowMaleTamer => true; - public virtual bool AllowFemaleTamer => true; - public virtual bool SubdueBeforeTame => false; - public virtual bool StatLossAfterTame => SubdueBeforeTame; - public virtual bool ReduceSpeedWithDamage => true; - public virtual bool IsSubdued => SubdueBeforeTame && ( Hits < ( HitsMax / 10 ) ); + return contains; + } + } - public virtual bool Commandable => true; + public virtual bool IsNecroFamiliar + { + get + { + if (!Summoned) + return false; - public virtual Poison HitPoison => null; - public virtual double HitPoisonChance => 0.5; - public virtual Poison PoisonImmune => null; + if (m_ControlMaster != null && SummonFamiliarSpell.Table.Contains(m_ControlMaster)) + return SummonFamiliarSpell.Table[m_ControlMaster] == this; - public virtual bool BardImmune => false; - public virtual bool Unprovokable => BardImmune || IsDeadPet; - public virtual bool Uncalmable => BardImmune || IsDeadPet; - public virtual bool AreaPeaceImmune => BardImmune || IsDeadPet; + return false; + } + } - public virtual bool BleedImmune => false; - public virtual double BonusPetDamageScalar => 1.0; + public virtual bool DeleteCorpseOnDeath => !Core.AOS && m_bSummoned; - public virtual bool DeathAdderCharmable => false; + [CommandProperty(AccessLevel.GameMaster)] + public int Loyalty + { + get => m_Loyalty; + set => m_Loyalty = Math.Min(Math.Max(value, 0), MaxLoyalty); + } - //TODO: Find the pub 31 tweaks to the DispelDifficulty and apply them of course. - public virtual double DispelDifficulty // at this skill level we dispel 50% chance - => 0.0; + [CommandProperty(AccessLevel.GameMaster)] + public WayPoint CurrentWayPoint{ get; set; } - public virtual double DispelFocus // at difficulty - focus we have 0%, at difficulty + focus we have 100% - => 20.0; + [CommandProperty(AccessLevel.GameMaster)] + public IPoint2D TargetLocation{ get; set; } - public virtual bool DisplayWeight => Backpack is StrongBackpack; + public virtual Mobile ConstantFocus => null; - #region Breath ability, like dragon fire breath - private long m_NextBreathTime; + public virtual bool DisallowAllMoves => false; - // Must be overridden in subclass to enable - public virtual bool HasBreath => false; + public virtual bool InitialInnocent => false; - // Base damage given is: CurrentHitPoints * BreathDamageScalar - public virtual double BreathDamageScalar => (Core.AOS ? 0.16 : 0.05); + public virtual bool AlwaysMurderer => false; - // Min/max seconds until next breath - public virtual double BreathMinDelay => 30.0; - public virtual double BreathMaxDelay => 45.0; + public virtual bool AlwaysAttackable => false; - // Creature stops moving for 1.0 seconds while breathing - public virtual double BreathStallTime => 1.0; + [CommandProperty(AccessLevel.GameMaster)] + public virtual int DamageMin + { + get => m_DamageMin; + set => m_DamageMin = value; + } - // Effect is sent 1.3 seconds after BreathAngerSound and BreathAngerAnimation is played - public virtual double BreathEffectDelay => 1.3; + [CommandProperty(AccessLevel.GameMaster)] + public virtual int DamageMax + { + get => m_DamageMax; + set => m_DamageMax = value; + } - // Damage is given 1.0 seconds after effect is sent - public virtual double BreathDamageDelay => 1.0; + [CommandProperty(AccessLevel.GameMaster)] + public override int HitsMax + { + get + { + if (HitsMaxSeed > 0) + { + int value = HitsMaxSeed + GetStatOffset(StatType.Str); - public virtual int BreathRange => RangePerception; + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; - // Damage types - public virtual int BreathChaosDamage => 0; - public virtual int BreathPhysicalDamage => 0; - public virtual int BreathFireDamage => 100; - public virtual int BreathColdDamage => 0; - public virtual int BreathPoisonDamage => 0; - public virtual int BreathEnergyDamage => 0; - - // Is immune to breath damages - public virtual bool BreathImmune => false; - - // Effect details and sound - public virtual int BreathEffectItemID => 0x36D4; - public virtual int BreathEffectSpeed => 5; - public virtual int BreathEffectDuration => 0; - public virtual bool BreathEffectExplodes => false; - public virtual bool BreathEffectFixedDir => false; - public virtual int BreathEffectHue => 0; - public virtual int BreathEffectRenderMode => 0; - - public virtual int BreathEffectSound => 0x227; - - // Anger sound/animations - public virtual int BreathAngerSound => GetAngerSound(); - public virtual int BreathAngerAnimation => 12; - - public virtual void BreathStart( Mobile target ) - { - BreathStallMovement(); - BreathPlayAngerSound(); - BreathPlayAngerAnimation(); - - Direction = GetDirectionTo( target ); - - Timer.DelayCall( TimeSpan.FromSeconds( BreathEffectDelay ), new TimerStateCallback( BreathEffect_Callback ), target ); - } - - public virtual void BreathStallMovement() - { - if ( AIObject != null ) - AIObject.NextMove = Core.TickCount + (int)(BreathStallTime * 1000); - } - - public virtual void BreathPlayAngerSound() - { - PlaySound( BreathAngerSound ); - } - - public virtual void BreathPlayAngerAnimation() - { - Animate( BreathAngerAnimation, 5, 1, true, false, 0 ); - } - - public virtual void BreathEffect_Callback( object state ) - { - Mobile target = (Mobile)state; - - if ( !target.Alive || !CanBeHarmful( target ) ) - return; - - BreathPlayEffectSound(); - BreathPlayEffect( target ); - - Timer.DelayCall( TimeSpan.FromSeconds( BreathDamageDelay ), new TimerStateCallback( BreathDamage_Callback ), target ); - } - - public virtual void BreathPlayEffectSound() - { - PlaySound( BreathEffectSound ); - } - - public virtual void BreathPlayEffect( Mobile target ) - { - Effects.SendMovingEffect( this, target, BreathEffectItemID, - BreathEffectSpeed, BreathEffectDuration, BreathEffectFixedDir, - BreathEffectExplodes, BreathEffectHue, BreathEffectRenderMode ); - } - - public virtual void BreathDamage_Callback( object state ) - { - if ( state is BaseCreature creature && creature.BreathImmune ) - return; - - Mobile target = (Mobile)state; - - if ( CanBeHarmful( target ) ) - { - DoHarmful( target ); - BreathDealDamage( target ); - } - } - - public virtual void BreathDealDamage( Mobile target ) - { - if ( !Evasion.CheckSpellEvasion( target ) ) - { - int physDamage = BreathPhysicalDamage; - int fireDamage = BreathFireDamage; - int coldDamage = BreathColdDamage; - int poisDamage = BreathPoisonDamage; - int nrgyDamage = BreathEnergyDamage; - - if ( BreathChaosDamage > 0 ) - { - switch( Utility.Random( 5 )) - { - case 0: physDamage += BreathChaosDamage; break; - case 1: fireDamage += BreathChaosDamage; break; - case 2: coldDamage += BreathChaosDamage; break; - case 3: poisDamage += BreathChaosDamage; break; - case 4: nrgyDamage += BreathChaosDamage; break; - } - } - - if ( physDamage == 0 && fireDamage == 0 && coldDamage == 0 && poisDamage == 0 && nrgyDamage == 0 ) - { - target.Damage( BreathComputeDamage(), this );// Unresistable damage even in AOS - } - else - { - AOS.Damage( target, this, BreathComputeDamage(), physDamage, fireDamage, coldDamage, poisDamage, nrgyDamage ); - } - } - } - - public virtual int BreathComputeDamage() - { - int damage = (int)(Hits * BreathDamageScalar); - - if ( IsParagon ) - damage = (int)(damage / Paragon.HitsBuff); - - if ( damage > 200 ) - damage = 200; - - return damage; - } - - #endregion - - public virtual bool CanFly => false; - - #region Spill Acid - - public void SpillAcid( int Amount ) - { - SpillAcid( null, Amount ); - } - - public void SpillAcid( Mobile target, int Amount ) - { - if ( (target != null && target.Map == null) || Map == null ) - return; - - for ( int i = 0; i < Amount; ++i ) - { - Point3D loc = Location; - Map map = Map; - Item acid = NewHarmfulItem(); - - if ( target?.Map != null && Amount == 1 ) - { - loc = target.Location; - map = target.Map; - } - else - { - bool validLocation = false; - for ( int j = 0; !validLocation && j < 10; ++j ) - { - loc = new Point3D( - loc.X+(Utility.Random(0,3)-2), - loc.Y+(Utility.Random(0,3)-2), - loc.Z ); - loc.Z = map.GetAverageZ( loc.X, loc.Y ); - validLocation = map.CanFit( loc, 16, false, false ) ; - } - } - acid.MoveToWorld( loc, map ); - } - } - - /* - Solen Style, override me for other mobiles/items: - kappa+acidslime, grizzles+whatever, etc. - */ - - public virtual Item NewHarmfulItem() - { - return new PoolOfAcid( TimeSpan.FromSeconds(10), 30, 30 ); - } - - #endregion - - #region Flee!!! - public virtual bool CanFlee => !m_Paragon; - - public DateTime EndFleeTime { get; set; } - - public virtual void StopFlee() - { - EndFleeTime = DateTime.MinValue; - } - - public virtual bool CheckFlee() - { - if ( EndFleeTime == DateTime.MinValue ) - return false; + return value; + } - if ( DateTime.UtcNow >= EndFleeTime ) - { - StopFlee(); - return false; - } + return Str; + } + } - return true; - } + [CommandProperty(AccessLevel.GameMaster)] + public int HitsMaxSeed{ get; set; } = -1; - public virtual void BeginFlee( TimeSpan maxDuration ) - { - EndFleeTime = DateTime.UtcNow + maxDuration; - } + [CommandProperty(AccessLevel.GameMaster)] + public override int StamMax + { + get + { + if (StamMaxSeed > 0) + { + int value = StamMaxSeed + GetStatOffset(StatType.Dex); - #endregion + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; - public virtual bool IsInvulnerable => false; + return value; + } - public BaseAI AIObject { get; private set; } + return Dex; + } + } - public const int MaxOwners = 5; + [CommandProperty(AccessLevel.GameMaster)] + public int StamMaxSeed{ get; set; } = -1; - public virtual OppositionGroup OppositionGroup => null; + [CommandProperty(AccessLevel.GameMaster)] + public override int ManaMax + { + get + { + if (ManaMaxSeed > 0) + { + int value = ManaMaxSeed + GetStatOffset(StatType.Int); - #region Friends - public List Friends { get; private set; } + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; - public virtual bool AllowNewPetFriend => ( Friends == null || Friends.Count < 5 ); + return value; + } - public virtual bool IsPetFriend( Mobile m ) - { - return ( Friends != null && Friends.Contains( m ) ); - } + return Int; + } + } - public virtual void AddPetFriend( Mobile m ) - { - if ( Friends == null ) - Friends = new List(); + [CommandProperty(AccessLevel.GameMaster)] + public int ManaMaxSeed{ get; set; } = -1; - Friends.Add( m ); - } + public virtual bool CanOpenDoors => !Body.IsAnimal && !Body.IsSea; + + public virtual bool CanMoveOverObstacles => Core.AOS || Body.IsMonster; - public virtual void RemovePetFriend( Mobile m ) - { - Friends?.Remove( m ); - } + public virtual bool CanDestroyObstacles => false; - public virtual bool IsFriend( Mobile m ) - { - OppositionGroup g = OppositionGroup; + /* + + Seems this actually was removed on OSI somewhere between the original bug report and now. + We will call it ML, until we can get better information. I suspect it was on the OSI TC when + originally it taken out of RunUO, and not implemented on OSIs production shards until more + recently. Either way, this is, or was, accurate OSI behavior, and just entirely + removing it was incorrect. OSI followers were distracted by being attacked well into + AoS, at very least. + + */ + + public virtual bool CanBeDistracted => !Core.ML; + + public override bool ShouldCheckStatTimers => false; + + public virtual bool CanAngerOnTame => false; + + protected virtual BaseAI ForcedAI => null; + + [CommandProperty(AccessLevel.GameMaster)] + public AIType AI + { + get => m_CurrentAI; + set + { + m_CurrentAI = value; + + if (m_CurrentAI == AIType.AI_Use_Default) m_CurrentAI = m_DefaultAI; + + ChangeAIType(m_CurrentAI); + } + } + + [CommandProperty(AccessLevel.Administrator)] + public bool Debug{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Team + { + get => m_Team; + set + { + m_Team = value; + + OnTeamChange(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile FocusMob{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public FightMode FightMode{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int RangePerception{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int RangeFight{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int RangeHome{ get; set; } = 10; + + [CommandProperty(AccessLevel.GameMaster)] + public double ActiveSpeed{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public double PassiveSpeed{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public double CurrentSpeed + { + get + { + if (TargetLocation != null) + return 0.3; + + return m_CurrentSpeed; + } + set + { + if (m_CurrentSpeed != value) + { + m_CurrentSpeed = value; + + AIObject?.OnCurrentSpeedChanged(); + } + } + } - if ( g != null && g.IsEnemy( this, m ) ) - return false; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Home + { + get => m_Home; + set => m_Home = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public Map HomeMap{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Controlled + { + get => m_Controlled; + set + { + if (m_Controlled == value) + return; + + m_Controlled = value; + Delta(MobileDelta.Noto); + + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile ControlMaster + { + get => m_ControlMaster; + set + { + if (m_ControlMaster == value || this == value) + return; + + RemoveFollowers(); + m_ControlMaster = value; + AddFollowers(); + if (m_ControlMaster != null) + StopDeleteTimer(); + + Delta(MobileDelta.Noto); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile SummonMaster + { + get => m_SummonMaster; + set + { + if (m_SummonMaster == value || this == value) + return; - if ( !(m is BaseCreature c) ) - return false; + RemoveFollowers(); + m_SummonMaster = value; + AddFollowers(); - return ( m_Team == c.m_Team && ( (m_bSummoned || m_Controlled) == (c.m_bSummoned || c.m_Controlled) )/* && c.Combatant != this */); - } + Delta(MobileDelta.Noto); + } + } - #endregion + [CommandProperty(AccessLevel.GameMaster)] + public Mobile ControlTarget{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D ControlDest{ get; set; } - #region Allegiance - public virtual Ethics.Ethic EthicAllegiance => null; + [CommandProperty(AccessLevel.GameMaster)] + public OrderType ControlOrder + { + get => m_ControlOrder; + set + { + m_ControlOrder = value; - public enum Allegiance - { - None, - Ally, - Enemy - } + AIObject?.OnCurrentOrderChanged(); - public virtual Allegiance GetFactionAllegiance( Mobile mob ) - { - if ( mob == null || mob.Map != Faction.Facet || FactionAllegiance == null ) - return Allegiance.None; + InvalidateProperties(); + + m_ControlMaster?.InvalidateProperties(); + } + } - Faction fac = Faction.Find( mob, true ); + [CommandProperty(AccessLevel.GameMaster)] + public bool BardProvoked{ get; set; } - if ( fac == null ) - return Allegiance.None; + [CommandProperty(AccessLevel.GameMaster)] + public bool BardPacified{ get; set; } - return ( fac == FactionAllegiance ? Allegiance.Ally : Allegiance.Enemy ); - } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile BardMaster{ get; set; } - public virtual Allegiance GetEthicAllegiance( Mobile mob ) - { - if ( mob == null || mob.Map != Faction.Facet || EthicAllegiance == null ) - return Allegiance.None; + [CommandProperty(AccessLevel.GameMaster)] + public Mobile BardTarget{ get; set; } - Ethics.Ethic ethic = Ethics.Ethic.Find( mob, true ); + [CommandProperty(AccessLevel.GameMaster)] + public DateTime BardEndTime{ get; set; } - if ( ethic == null ) - return Allegiance.None; + [CommandProperty(AccessLevel.GameMaster)] + public double MinTameSkill{ get; set; } - return ( ethic == EthicAllegiance ? Allegiance.Ally : Allegiance.Enemy ); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool Tamable + { + get => m_bTamable && !m_Paragon; + set => m_bTamable = value; + } - #endregion + [CommandProperty(AccessLevel.Administrator)] + public bool Summoned + { + get => m_bSummoned; + set + { + if (m_bSummoned == value) + return; - public virtual bool IsEnemy( Mobile m ) - { - OppositionGroup g = OppositionGroup; + NextReacquireTime = Core.TickCount; - if ( g != null && g.IsEnemy( this, m ) ) - return true; + m_bSummoned = value; + Delta(MobileDelta.Noto); - if ( m is BaseGuard ) - return false; + InvalidateProperties(); + } + } - if ( GetFactionAllegiance( m ) == Allegiance.Ally ) - return false; + [CommandProperty(AccessLevel.Administrator)] + public int ControlSlots{ get; set; } = 1; - Ethics.Ethic ourEthic = EthicAllegiance; - Ethics.Player pl = Ethics.Player.Find( m, true ); + public virtual bool NoHouseRestrictions => false; + public virtual bool IsHouseSummonable => false; - if ( pl != null && pl.IsShielded && ( ourEthic == null || ourEthic == pl.Ethic ) ) - return false; + public virtual bool AutoDispel => false; + public virtual double AutoDispelChance => Core.SE ? .10 : 1.0; - if ( m is PlayerMobile mobile && mobile.HonorActive ) - return false; + public virtual bool IsScaryToPets => false; + public virtual bool IsScaredOfScaryThings => true; - if ( !(m is BaseCreature c) || m is Engines.Quests.Haven.MilitiaFighter ) - return true; + public virtual bool CanRummageCorpses => false; - if ( TransformationSpellHelper.UnderTransformation( m, typeof( EtherealVoyageSpell ) ) ) - return false; + public virtual bool DeleteOnRelease => m_bSummoned; - if ( ( FightMode == FightMode.Evil && m.Karma < 0 ) || ( c.FightMode == FightMode.Evil && Karma < 0 ) ) - return true; + public virtual bool CanDrop => IsBonded; - return ( m_Team != c.m_Team || ( (m_bSummoned || m_Controlled) != (c.m_bSummoned || c.m_Controlled ) )/* || c.Combatant == this*/ ); - } + public virtual double TreasureMapChance => TreasureMap.LootChance; + public virtual int TreasureMapLevel => -1; - public override string ApplyNameSuffix( string suffix ) - { - if ( IsParagon && !GivesMLMinorArtifact ) - { - if ( suffix.Length == 0 ) - suffix = "(Paragon)"; - else - suffix = string.Concat( suffix, " (Paragon)" ); - } + public virtual bool IgnoreYoungProtection => false; - return base.ApplyNameSuffix( suffix ); - } + public bool NoKillAwards{ get; set; } - public virtual bool CheckControlChance( Mobile m ) - { - if ( GetControlChance( m ) > Utility.RandomDouble() ) - { - Loyalty += 1; - return true; - } + #region Mondain's Legacy - PlaySound( GetAngerSound() ); + public virtual bool GivesMLMinorArtifact => false; - if ( Body.IsAnimal ) - Animate( 10, 5, 1, true, false, 0 ); - else if ( Body.IsMonster ) - Animate( 18, 5, 1, true, false, 0 ); + #endregion - Loyalty -= 3; - return false; - } + /* To save on cpu usage, RunUO creatures only reacquire creatures under the following circumstances: + * - 10 seconds have elapsed since the last time it tried + * - The creature was attacked + * - Some creatures, like dragons, will reacquire when they see someone move + * + * This functionality appears to be implemented on OSI as well + */ - public virtual bool CanBeControlledBy( Mobile m ) - { - return ( GetControlChance( m ) > 0.0 ); - } + public long NextReacquireTime{ get; set; } - public virtual double GetControlChance( Mobile m, bool useBaseSkill = false) - { - if ( MinTameSkill <= 29.1 || m_bSummoned || m.AccessLevel >= AccessLevel.GameMaster ) - return 1.0; + public virtual TimeSpan ReacquireDelay => TimeSpan.FromSeconds(10.0); + public virtual bool ReacquireOnMovement => false; + public virtual bool AcquireOnApproach => m_Paragon; + public virtual int AcquireOnApproachRange => 10; - double dMinTameSkill = MinTameSkill; + public static bool Summoning{ get; set; } - if ( dMinTameSkill > -24.9 && AnimalTaming.CheckMastery( m, this ) ) - dMinTameSkill = -24.9; + public virtual bool CanBreath => HasBreath && !Summoned; + public virtual bool IsDispellable => Summoned && !IsAnimatedDead; - int taming = (int)((useBaseSkill ? m.Skills[SkillName.AnimalTaming].Base : m.Skills[SkillName.AnimalTaming].Value ) * 10); - int lore = (int)((useBaseSkill ? m.Skills[SkillName.AnimalLore].Base : m.Skills[SkillName.AnimalLore].Value )* 10); - int bonus = 0, chance = 700; + public virtual bool + PlayerRangeSensitive //If they are following a waypoint, they'll continue to follow it even if players aren't around + => CurrentWayPoint == null; - if ( Core.ML ) - { - int SkillBonus = taming - (int)(dMinTameSkill * 10); - int LoreBonus = lore - (int)(dMinTameSkill * 10); + public virtual bool ReturnsToHome => + SeeksHome && Home != Point3D.Zero && !m_ReturnQueued && !Controlled && !Summoned; - int SkillMod = 6, LoreMod = 6; + // used for deleting untamed creatures [in houses] - if ( SkillBonus < 0 ) - SkillMod = 28; - if ( LoreBonus < 0 ) - LoreMod = 14; + [CommandProperty(AccessLevel.GameMaster)] + public bool RemoveIfUntamed{ get; set; } - SkillBonus *= SkillMod; - LoreBonus *= LoreMod; + [CommandProperty(AccessLevel.GameMaster)] + public int RemoveStep{ get; set; } - bonus = (SkillBonus + LoreBonus ) / 2; - } - else - { - int difficulty = (int)(dMinTameSkill * 10); - int weighted = ((taming * 4) + lore) / 5; - bonus = weighted - difficulty; + public HonorContext ReceivedHonorContext{ get; set; } - if ( bonus <= 0 ) - bonus *= 14; - else - bonus *= 6; - } - - chance += bonus; + public virtual WeaponAbility GetWeaponAbility() + { + return null; + } - if ( chance >= 0 && chance < 200 ) - chance = 200; - else if ( chance > 990 ) - chance = 990; + public virtual bool IsEnemy(Mobile m) + { + OppositionGroup g = OppositionGroup; - chance -= (MaxLoyalty - m_Loyalty) * 10; - - return ( (double)chance / 1000 ); - } - - private static Type[] m_AnimateDeadTypes = { - typeof( MoundOfMaggots ), typeof( HellSteed ), typeof( SkeletalMount ), - typeof( WailingBanshee ), typeof( Wraith ), typeof( SkeletalDragon ), - typeof( LichLord ), typeof( FleshGolem ), typeof( Lich ), - typeof( SkeletalKnight ), typeof( BoneKnight ), typeof( Mummy ), - typeof( SkeletalMage ), typeof( BoneMagi ), typeof( PatchworkSkeleton ) - }; + if (g != null && g.IsEnemy(this, m)) + return true; - public virtual bool IsAnimatedDead - { - get - { - if ( !Summoned ) - return false; + if (m is BaseGuard) + return false; - Type type = GetType(); + if (GetFactionAllegiance(m) == Allegiance.Ally) + return false; - bool contains = false; + Ethic ourEthic = EthicAllegiance; + Player pl = Ethics.Player.Find(m, true); - for ( int i = 0; !contains && i < m_AnimateDeadTypes.Length; ++i ) - contains = ( type == m_AnimateDeadTypes[i] ); + if (pl != null && pl.IsShielded && (ourEthic == null || ourEthic == pl.Ethic)) + return false; - return contains; - } - } + if (m is PlayerMobile mobile && mobile.HonorActive) + return false; - public virtual bool IsNecroFamiliar - { - get - { - if ( !Summoned ) - return false; + if (!(m is BaseCreature c) || m is MilitiaFighter) + return true; - if ( m_ControlMaster != null && SummonFamiliarSpell.Table.Contains( m_ControlMaster ) ) - return SummonFamiliarSpell.Table[ m_ControlMaster ] == this; + if (TransformationSpellHelper.UnderTransformation(m, typeof(EtherealVoyageSpell))) + return false; - return false; - } - } + if (FightMode == FightMode.Evil && m.Karma < 0 || c.FightMode == FightMode.Evil && Karma < 0) + return true; - public override void Damage( int amount, Mobile from ) - { - int oldHits = Hits; + return m_Team != c.m_Team || (m_bSummoned || m_Controlled) != (c.m_bSummoned || c.m_Controlled); + } - if ( Core.AOS && !Summoned && Controlled && 0.2 > Utility.RandomDouble() ) - amount = (int)(amount * BonusPetDamageScalar); + public override string ApplyNameSuffix(string suffix) + { + if (IsParagon && !GivesMLMinorArtifact) + { + if (suffix.Length == 0) + suffix = "(Paragon)"; + else + suffix = string.Concat(suffix, " (Paragon)"); + } - if ( EvilOmenSpell.TryEndEffect( this ) ) - amount = (int)(amount * 1.25); + return base.ApplyNameSuffix(suffix); + } - Mobile oath = BloodOathSpell.GetBloodOath( from ); + public virtual bool CheckControlChance(Mobile m) + { + if (GetControlChance(m) > Utility.RandomDouble()) + { + Loyalty += 1; + return true; + } - if ( oath == this ) - { - amount = (int)(amount * 1.1); - from.Damage( amount, from ); - } + PlaySound(GetAngerSound()); - base.Damage( amount, from ); + if (Body.IsAnimal) + Animate(10, 5, 1, true, false, 0); + else if (Body.IsMonster) + Animate(18, 5, 1, true, false, 0); - if ( SubdueBeforeTame && !Controlled ) - { - if ( (oldHits > (HitsMax / 10)) && (Hits <= (HitsMax / 10)) ) - PublicOverheadMessage( MessageType.Regular, 0x3B2, false, "* The creature has been beaten into subjugation! *" ); - } - } + Loyalty -= 3; + return false; + } - public virtual bool DeleteCorpseOnDeath => !Core.AOS && m_bSummoned; + public virtual bool CanBeControlledBy(Mobile m) + { + return GetControlChance(m) > 0.0; + } - public override void SetLocation( Point3D newLocation, bool isTeleport ) - { - base.SetLocation( newLocation, isTeleport ); + public virtual double GetControlChance(Mobile m, bool useBaseSkill = false) + { + if (MinTameSkill <= 29.1 || m_bSummoned || m.AccessLevel >= AccessLevel.GameMaster) + return 1.0; - if ( isTeleport ) - AIObject?.OnTeleported(); - } + double dMinTameSkill = MinTameSkill; - public override void OnBeforeSpawn( Point3D location, Map m ) - { - if ( Paragon.CheckConvert( this, location, m ) ) - IsParagon = true; + if (dMinTameSkill > -24.9 && AnimalTaming.CheckMastery(m, this)) + dMinTameSkill = -24.9; - base.OnBeforeSpawn( location, m ); - } + int taming = + (int)((useBaseSkill ? m.Skills[SkillName.AnimalTaming].Base : m.Skills[SkillName.AnimalTaming].Value) * 10); + int lore = + (int)((useBaseSkill ? m.Skills[SkillName.AnimalLore].Base : m.Skills[SkillName.AnimalLore].Value) * 10); + int bonus = 0, chance = 700; - public override ApplyPoisonResult ApplyPoison( Mobile from, Poison poison ) - { - if ( !Alive || IsDeadPet ) - return ApplyPoisonResult.Immune; + if (Core.ML) + { + int SkillBonus = taming - (int)(dMinTameSkill * 10); + int LoreBonus = lore - (int)(dMinTameSkill * 10); - if ( EvilOmenSpell.TryEndEffect( this ) ) - poison = PoisonImpl.IncreaseLevel( poison ); + int SkillMod = 6, LoreMod = 6; - ApplyPoisonResult result = base.ApplyPoison( from, poison ); + if (SkillBonus < 0) + SkillMod = 28; + if (LoreBonus < 0) + LoreMod = 14; - if ( from != null && result == ApplyPoisonResult.Poisoned && PoisonTimer is PoisonImpl.PoisonTimer timer ) - timer.From = from; + SkillBonus *= SkillMod; + LoreBonus *= LoreMod; - return result; - } + bonus = (SkillBonus + LoreBonus) / 2; + } + else + { + int difficulty = (int)(dMinTameSkill * 10); + int weighted = (taming * 4 + lore) / 5; + bonus = weighted - difficulty; - public override bool CheckPoisonImmunity( Mobile from, Poison poison ) - { - if ( base.CheckPoisonImmunity( from, poison ) ) - return true; + if (bonus <= 0) + bonus *= 14; + else + bonus *= 6; + } - Poison p = PoisonImmune; + chance += bonus; + + if (chance >= 0 && chance < 200) + chance = 200; + else if (chance > 990) + chance = 990; + + chance -= (MaxLoyalty - m_Loyalty) * 10; + + return (double)chance / 1000; + } + + public override void Damage(int amount, Mobile from) + { + int oldHits = Hits; + + if (Core.AOS && !Summoned && Controlled && 0.2 > Utility.RandomDouble()) + amount = (int)(amount * BonusPetDamageScalar); + + if (EvilOmenSpell.TryEndEffect(this)) + amount = (int)(amount * 1.25); + + Mobile oath = BloodOathSpell.GetBloodOath(from); + + if (oath == this) + { + amount = (int)(amount * 1.1); + from.Damage(amount, from); + } + + base.Damage(amount, from); + + if (SubdueBeforeTame && !Controlled) + if (oldHits > HitsMax / 10 && Hits <= HitsMax / 10) + PublicOverheadMessage(MessageType.Regular, 0x3B2, false, + "* The creature has been beaten into subjugation! *"); + } - if ( m_Paragon ) - p = PoisonImpl.IncreaseLevel( p ); + public override void SetLocation(Point3D newLocation, bool isTeleport) + { + base.SetLocation(newLocation, isTeleport); + + if (isTeleport) + AIObject?.OnTeleported(); + } - return ( p != null && p.Level >= poison.Level ); - } + public override void OnBeforeSpawn(Point3D location, Map m) + { + if (Paragon.CheckConvert(this, location, m)) + IsParagon = true; + + base.OnBeforeSpawn(location, m); + } - [CommandProperty( AccessLevel.GameMaster )] - public int Loyalty - { - get => m_Loyalty; - set => m_Loyalty = Math.Min( Math.Max( value, 0 ), MaxLoyalty ); - } + public override ApplyPoisonResult ApplyPoison(Mobile from, Poison poison) + { + if (!Alive || IsDeadPet) + return ApplyPoisonResult.Immune; - [CommandProperty( AccessLevel.GameMaster )] - public WayPoint CurrentWayPoint { get; set; } + if (EvilOmenSpell.TryEndEffect(this)) + poison = PoisonImpl.IncreaseLevel(poison); + + ApplyPoisonResult result = base.ApplyPoison(from, poison); + + if (from != null && result == ApplyPoisonResult.Poisoned && PoisonTimer is PoisonImpl.PoisonTimer timer) + timer.From = from; + + return result; + } + + public override bool CheckPoisonImmunity(Mobile from, Poison poison) + { + if (base.CheckPoisonImmunity(from, poison)) + return true; + + Poison p = PoisonImmune; + + if (m_Paragon) + p = PoisonImpl.IncreaseLevel(p); + + return p != null && p.Level >= poison.Level; + } + + public void Unpacify() + { + BardEndTime = DateTime.UtcNow; + BardPacified = false; + } + + public virtual void CheckDistracted(Mobile from) + { + if (Utility.RandomDouble() < .10) + { + ControlTarget = from; + ControlOrder = OrderType.Attack; + Combatant = from; + Warmode = true; + } + } + + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (BardPacified && (HitsMax - Hits) * 0.001 > Utility.RandomDouble()) + Unpacify(); + + int disruptThreshold; + //NPCs can use bandages too! + if (!Core.AOS) + disruptThreshold = 0; + else if (from != null && from.Player) + disruptThreshold = 18; + else + disruptThreshold = 25; + + if (amount > disruptThreshold) + { + BandageContext c = BandageContext.GetContext(this); + + c?.Slip(); + } + + if (Confidence.IsRegenerating(this)) + Confidence.StopRegenerating(this); + + WeightOverloading.FatigueOnDamage(this, amount); + + InhumanSpeech speechType = SpeechType; + + if (speechType != null && !willKill) + speechType.OnDamage(this, amount); + + ReceivedHonorContext?.OnTargetDamaged(from, amount); + + if (!willKill) + { + if (CanBeDistracted && ControlOrder == OrderType.Follow) CheckDistracted(from); + } + else if (from is PlayerMobile mobile) + { + Timer.DelayCall(TimeSpan.FromSeconds(10), mobile.RecoverAmmo); + } + + base.OnDamage(amount, from, willKill); + } + + public virtual void OnDamagedBySpell(Mobile from) + { + if (CanBeDistracted && ControlOrder == OrderType.Follow) CheckDistracted(from); + } + + public virtual void OnHarmfulSpell(Mobile from) + { + } + + public virtual void CheckReflect(Mobile caster, ref bool reflect) + { + } + + public virtual void OnCarve(Mobile from, Corpse corpse, Item with) + { + int feathers = Feathers; + int wool = Wool; + int meat = Meat; + int hides = Hides; + int scales = Scales; + + if (feathers == 0 && wool == 0 && meat == 0 && hides == 0 && scales == 0 || Summoned || IsBonded || + corpse.Animated) + { + if (corpse.Animated) + corpse.SendLocalizedMessageTo(from, 500464); // Use this on corpses to carve away meat and hide + else + from.SendLocalizedMessage(500485); // You see nothing useful to carve from the corpse. + } + else + { + if (Core.ML && from.Race == Race.Human) + hides = (int)Math.Ceiling(hides * 1.1); // 10% bonus only applies to hides, ore & logs + + if (corpse.Map == Map.Felucca) + { + feathers *= 2; + wool *= 2; + hides *= 2; + + if (Core.ML) + { + meat *= 2; + scales *= 2; + } + } + + new Blood(0x122D).MoveToWorld(corpse.Location, corpse.Map); + + if (feathers != 0) + { + corpse.AddCarvedItem(new Feather(feathers), from); + from.SendLocalizedMessage(500479); // You pluck the bird. The feathers are now on the corpse. + } + + if (wool != 0) + { + corpse.AddCarvedItem(new TaintedWool(wool), from); + from.SendLocalizedMessage(500483); // You shear it, and the wool is now on the corpse. + } + + if (meat != 0) + { + if (MeatType == MeatType.Ribs) + corpse.AddCarvedItem(new RawRibs(meat), from); + else if (MeatType == MeatType.Bird) + corpse.AddCarvedItem(new RawBird(meat), from); + else if (MeatType == MeatType.LambLeg) + corpse.AddCarvedItem(new RawLambLeg(meat), from); + + from.SendLocalizedMessage(500467); // You carve some meat, which remains on the corpse. + } + + if (hides != 0) + { + Item holding = from.Weapon as Item; + + if (Core.AOS && holding is SkinningKnife) + { + Item leather = null; + + switch (HideType) + { + case HideType.Regular: + leather = new Leather(hides); + break; + case HideType.Spined: + leather = new SpinedLeather(hides); + break; + case HideType.Horned: + leather = new HornedLeather(hides); + break; + case HideType.Barbed: + leather = new BarbedLeather(hides); + break; + } + + if (leather != null) + { + if (!from.PlaceInBackpack(leather)) + { + corpse.DropItem(leather); + from.SendLocalizedMessage(500471); // You skin it, and the hides are now in the corpse. + } + else + { + from.SendLocalizedMessage( + 1073555); // You skin it and place the cut-up hides in your backpack. + } + } + } + else + { + if (HideType == HideType.Regular) + corpse.DropItem(new Hides(hides)); + else if (HideType == HideType.Spined) + corpse.DropItem(new SpinedHides(hides)); + else if (HideType == HideType.Horned) + corpse.DropItem(new HornedHides(hides)); + else if (HideType == HideType.Barbed) + corpse.DropItem(new BarbedHides(hides)); + + from.SendLocalizedMessage(500471); // You skin it, and the hides are now in the corpse. + } + } + + if (scales != 0) + { + ScaleType sc = ScaleType; + + switch (sc) + { + case ScaleType.Red: + corpse.AddCarvedItem(new RedScales(scales), from); + break; + case ScaleType.Yellow: + corpse.AddCarvedItem(new YellowScales(scales), from); + break; + case ScaleType.Black: + corpse.AddCarvedItem(new BlackScales(scales), from); + break; + case ScaleType.Green: + corpse.AddCarvedItem(new GreenScales(scales), from); + break; + case ScaleType.White: + corpse.AddCarvedItem(new WhiteScales(scales), from); + break; + case ScaleType.Blue: + corpse.AddCarvedItem(new BlueScales(scales), from); + break; + case ScaleType.All: + { + corpse.AddCarvedItem(new RedScales(scales), from); + corpse.AddCarvedItem(new YellowScales(scales), from); + corpse.AddCarvedItem(new BlackScales(scales), from); + corpse.AddCarvedItem(new GreenScales(scales), from); + corpse.AddCarvedItem(new WhiteScales(scales), from); + corpse.AddCarvedItem(new BlueScales(scales), from); + break; + } + } + + from.SendMessage("You cut away some scales, but they remain on the corpse."); + } + + corpse.Carved = true; + + if (corpse.IsCriminalAction(from)) + from.CriminalAction(true); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(19); // version + + writer.Write((int)m_CurrentAI); + writer.Write((int)m_DefaultAI); + + writer.Write(RangePerception); + writer.Write(RangeFight); + + writer.Write(m_Team); + + writer.Write(ActiveSpeed); + writer.Write(PassiveSpeed); + writer.Write(m_CurrentSpeed); + + writer.Write(m_Home.X); + writer.Write(m_Home.Y); + writer.Write(m_Home.Z); + + // Version 1 + writer.Write(RangeHome); + + int i = 0; + + writer.Write(m_SpellAttack.Count); + for (i = 0; i < m_SpellAttack.Count; i++) writer.Write(m_SpellAttack[i].ToString()); + + writer.Write(m_SpellDefense.Count); + for (i = 0; i < m_SpellDefense.Count; i++) writer.Write(m_SpellDefense[i].ToString()); + + // Version 2 + writer.Write((int)FightMode); + + writer.Write(m_Controlled); + writer.Write(m_ControlMaster); + writer.Write(ControlTarget); + writer.Write(ControlDest); + writer.Write((int)m_ControlOrder); + writer.Write(MinTameSkill); + // Removed in version 9 + //writer.Write( (double) m_dMaxTameSkill ); + writer.Write(m_bTamable); + writer.Write(m_bSummoned); + + if (m_bSummoned) + writer.WriteDeltaTime(SummonEnd); + + writer.Write(ControlSlots); + + // Version 3 + writer.Write(m_Loyalty); + + // Version 4 + writer.Write(CurrentWayPoint); + + // Verison 5 + writer.Write(m_SummonMaster); + + // Version 6 + writer.Write(HitsMaxSeed); + writer.Write(StamMaxSeed); + writer.Write(ManaMaxSeed); + writer.Write(m_DamageMin); + writer.Write(m_DamageMax); - [CommandProperty( AccessLevel.GameMaster )] - public IPoint2D TargetLocation { get; set; } + // Version 7 + writer.Write(m_PhysicalResistance); + writer.Write(PhysicalDamage); - public virtual Mobile ConstantFocus => null; + writer.Write(m_FireResistance); + writer.Write(FireDamage); - public virtual bool DisallowAllMoves => false; + writer.Write(m_ColdResistance); + writer.Write(ColdDamage); - public virtual bool InitialInnocent => false; + writer.Write(m_PoisonResistance); + writer.Write(PoisonDamage); - public virtual bool AlwaysMurderer => false; + writer.Write(m_EnergyResistance); + writer.Write(EnergyDamage); - public virtual bool AlwaysAttackable => false; + // Version 8 + writer.Write(Owners, true); - [CommandProperty( AccessLevel.GameMaster )] - public virtual int DamageMin{ get => m_DamageMin; - set => m_DamageMin = value; - } + // Version 10 + writer.Write(IsDeadPet); + writer.Write(m_IsBonded); + writer.Write(BondingBegin); + writer.Write(OwnerAbandonTime); - [CommandProperty( AccessLevel.GameMaster )] - public virtual int DamageMax{ get => m_DamageMax; - set => m_DamageMax = value; - } + // Version 11 + writer.Write(m_HasGeneratedLoot); - [CommandProperty( AccessLevel.GameMaster )] - public override int HitsMax - { - get - { - if ( HitsMaxSeed > 0 ) { - int value = HitsMaxSeed + GetStatOffset( StatType.Str ); + // Version 12 + writer.Write(m_Paragon); - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; + // Version 13 + writer.Write(Friends != null && Friends.Count > 0); - return value; - } + if (Friends != null && Friends.Count > 0) + writer.Write(Friends, true); - return Str; - } - } + // Version 14 + writer.Write(RemoveIfUntamed); + writer.Write(RemoveStep); - [CommandProperty( AccessLevel.GameMaster )] - public int HitsMaxSeed { get; set; } = -1; + // Version 17 + if (IsStabled || Controlled && ControlMaster != null) + writer.Write(TimeSpan.Zero); + else + writer.Write(DeleteTimeLeft); - [CommandProperty( AccessLevel.GameMaster )] - public override int StamMax - { - get - { - if ( StamMaxSeed > 0 ) { - int value = StamMaxSeed + GetStatOffset( StatType.Dex ); + // Version 18 + writer.Write(CorpseNameOverride); - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; + // Version 19 + writer.Write(HomeMap); + } - return value; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return Dex; - } - } + int version = reader.ReadInt(); + + m_CurrentAI = (AIType)reader.ReadInt(); + m_DefaultAI = (AIType)reader.ReadInt(); + + RangePerception = reader.ReadInt(); + RangeFight = reader.ReadInt(); + + m_Team = reader.ReadInt(); + + ActiveSpeed = reader.ReadDouble(); + PassiveSpeed = reader.ReadDouble(); + m_CurrentSpeed = reader.ReadDouble(); + + if (RangePerception == OldRangePerception) + RangePerception = DefaultRangePerception; - [CommandProperty( AccessLevel.GameMaster )] - public int StamMaxSeed { get; set; } = -1; + m_Home.X = reader.ReadInt(); + m_Home.Y = reader.ReadInt(); + m_Home.Z = reader.ReadInt(); - [CommandProperty( AccessLevel.GameMaster )] - public override int ManaMax - { - get - { - if ( ManaMaxSeed > 0 ) { - int value = ManaMaxSeed + GetStatOffset( StatType.Int ); + if (version >= 1) + { + RangeHome = reader.ReadInt(); - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; + int iCount = reader.ReadInt(); + for (int i = 0; i < iCount; i++) + { + string str = reader.ReadString(); + Type type = Type.GetType(str); + + if (type != null) m_SpellAttack.Add(type); + } + + iCount = reader.ReadInt(); + for (int i = 0; i < iCount; i++) + { + string str = reader.ReadString(); + Type type = Type.GetType(str); + + if (type != null) m_SpellDefense.Add(type); + } + } + else + { + RangeHome = 0; + } + + if (version >= 2) + { + FightMode = (FightMode)reader.ReadInt(); + + m_Controlled = reader.ReadBool(); + m_ControlMaster = reader.ReadMobile(); + ControlTarget = reader.ReadMobile(); + ControlDest = reader.ReadPoint3D(); + m_ControlOrder = (OrderType)reader.ReadInt(); + + MinTameSkill = reader.ReadDouble(); + + if (version < 9) + reader.ReadDouble(); + + m_bTamable = reader.ReadBool(); + m_bSummoned = reader.ReadBool(); + + if (m_bSummoned) + { + SummonEnd = reader.ReadDeltaTime(); + new UnsummonTimer(m_ControlMaster, this, SummonEnd - DateTime.UtcNow).Start(); + } + + ControlSlots = reader.ReadInt(); + } + else + { + FightMode = FightMode.Closest; + + m_Controlled = false; + m_ControlMaster = null; + ControlTarget = null; + m_ControlOrder = OrderType.None; + } + + if (version >= 3) + m_Loyalty = reader.ReadInt(); + else + m_Loyalty = MaxLoyalty; // Wonderfully Happy + + if (version >= 4) + CurrentWayPoint = reader.ReadItem() as WayPoint; + + if (version >= 5) + m_SummonMaster = reader.ReadMobile(); + + if (version >= 6) + { + HitsMaxSeed = reader.ReadInt(); + StamMaxSeed = reader.ReadInt(); + ManaMaxSeed = reader.ReadInt(); + m_DamageMin = reader.ReadInt(); + m_DamageMax = reader.ReadInt(); + } + + if (version >= 7) + { + m_PhysicalResistance = reader.ReadInt(); + PhysicalDamage = reader.ReadInt(); + + m_FireResistance = reader.ReadInt(); + FireDamage = reader.ReadInt(); + + m_ColdResistance = reader.ReadInt(); + ColdDamage = reader.ReadInt(); + + m_PoisonResistance = reader.ReadInt(); + PoisonDamage = reader.ReadInt(); + + m_EnergyResistance = reader.ReadInt(); + EnergyDamage = reader.ReadInt(); + } + + if (version >= 8) + Owners = reader.ReadStrongMobileList(); + else + Owners = new List(); + + if (version >= 10) + { + IsDeadPet = reader.ReadBool(); + m_IsBonded = reader.ReadBool(); + BondingBegin = reader.ReadDateTime(); + OwnerAbandonTime = reader.ReadDateTime(); + } + + if (version >= 11) + m_HasGeneratedLoot = reader.ReadBool(); + else + m_HasGeneratedLoot = true; + + if (version >= 12) + m_Paragon = reader.ReadBool(); + else + m_Paragon = false; + + if (version >= 13 && reader.ReadBool()) + Friends = reader.ReadStrongMobileList(); + else if (version < 13 && m_ControlOrder >= OrderType.Unfriend) + ++m_ControlOrder; + + if (version < 16 && Loyalty != MaxLoyalty) + Loyalty *= 10; + + double activeSpeed = ActiveSpeed; + double passiveSpeed = PassiveSpeed; + + SpeedInfo.GetSpeeds(this, ref activeSpeed, ref passiveSpeed); - return value; - } - - return Int; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ManaMaxSeed { get; set; } = -1; - - public virtual bool CanOpenDoors => !Body.IsAnimal && !Body.IsSea; - - public virtual bool CanMoveOverObstacles => Core.AOS || Body.IsMonster; + bool isStandardActive = false; + for (int i = 0; !isStandardActive && i < m_StandardActiveSpeeds.Length; ++i) + isStandardActive = ActiveSpeed == m_StandardActiveSpeeds[i]; + + bool isStandardPassive = false; + for (int i = 0; !isStandardPassive && i < m_StandardPassiveSpeeds.Length; ++i) + isStandardPassive = PassiveSpeed == m_StandardPassiveSpeeds[i]; + + if (isStandardActive && m_CurrentSpeed == ActiveSpeed) + m_CurrentSpeed = activeSpeed; + else if (isStandardPassive && m_CurrentSpeed == PassiveSpeed) + m_CurrentSpeed = passiveSpeed; + + if (isStandardActive && !m_Paragon) + ActiveSpeed = activeSpeed; + + if (isStandardPassive && !m_Paragon) + PassiveSpeed = passiveSpeed; + + if (version >= 14) + { + RemoveIfUntamed = reader.ReadBool(); + RemoveStep = reader.ReadInt(); + } + + TimeSpan deleteTime = TimeSpan.Zero; + + if (version >= 17) + deleteTime = reader.ReadTimeSpan(); + + if (deleteTime > TimeSpan.Zero || LastOwner != null && !Controlled && !IsStabled) + { + if (deleteTime == TimeSpan.Zero) + deleteTime = TimeSpan.FromDays(3.0); + + m_DeleteTimer = new DeleteTimer(this, deleteTime); + m_DeleteTimer.Start(); + } + + if (version >= 18) + CorpseNameOverride = reader.ReadString(); + + if (version >= 19) + HomeMap = reader.ReadMap(); + + if (version <= 14 && m_Paragon && Hue == 0x31) Hue = Paragon.Hue; //Paragon hue fixed, should now be 0x501. + + if (Core.AOS && NameHue == 0x35) + NameHue = -1; + + CheckStatTimers(); + + ChangeAIType(m_CurrentAI); + + AddFollowers(); + + if (IsAnimatedDead) + AnimateDeadSpell.Register(m_SummonMaster, this); + } + + public virtual bool IsHumanInTown() + { + return Body.IsHuman && Region.IsPartOf(typeof(GuardedRegion)); + } + + public virtual bool CheckGold(Mobile from, Item dropped) + { + return dropped is Gold gold && OnGoldGiven(from, gold); + } + + public virtual bool OnGoldGiven(Mobile from, Gold dropped) + { + if (CheckTeachingMatch(from)) + { + if (Teach(m_Teaching, from, dropped.Amount, true)) + { + dropped.Delete(); + return true; + } + } + else if (IsHumanInTown()) + { + Direction = GetDirectionTo(from); + + int oldSpeechHue = SpeechHue; + + SpeechHue = 0x23F; + SayTo(from, "Thou art giving me gold?"); + + if (dropped.Amount >= 400) + SayTo(from, "'Tis a noble gift."); + else + SayTo(from, "Money is always welcome."); + + SpeechHue = 0x3B2; + SayTo(from, 501548); // I thank thee. + + SpeechHue = oldSpeechHue; + + dropped.Delete(); + return true; + } + + return false; + } + + public virtual bool OverrideBondingReqs() + { + return false; + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (CheckFeed(from, dropped)) + return true; + if (CheckGold(from, dropped)) + return true; + + // Note: Yes, this happens for all questers (regardless of type, e.g. escorts), + // even if they can't offer you anything at the moment + if (MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile) + { + MLQuestSystem.Tell(this, mobile, + 1074893); // You need to mark your quest items so I don't take the wrong object. Then speak to me. + return false; + } + + return base.OnDragDrop(from, dropped); + } + + public void ChangeAIType(AIType NewAI) + { + AIObject?.m_Timer.Stop(); + + if (ForcedAI != null) + { + AIObject = ForcedAI; + return; + } + + AIObject = null; + + switch (NewAI) + { + case AIType.AI_Melee: + AIObject = new MeleeAI(this); + break; + case AIType.AI_Animal: + AIObject = new AnimalAI(this); + break; + case AIType.AI_Berserk: + AIObject = new BerserkAI(this); + break; + case AIType.AI_Archer: + AIObject = new ArcherAI(this); + break; + case AIType.AI_Healer: + AIObject = new HealerAI(this); + break; + case AIType.AI_Vendor: + AIObject = new VendorAI(this); + break; + case AIType.AI_Mage: + AIObject = new MageAI(this); + break; + case AIType.AI_Predator: + //m_AI = new PredatorAI(this); + AIObject = new MeleeAI(this); + break; + case AIType.AI_Thief: + AIObject = new ThiefAI(this); + break; + } + } + + public void ChangeAIToDefault() + { + ChangeAIType(m_DefaultAI); + } + + public virtual void OnTeamChange() + { + } + + public override void RevealingAction() + { + InvisibilitySpell.RemoveTimer(this); + + base.RevealingAction(); + } + + public void RemoveFollowers() + { + if (m_ControlMaster != null) + { + m_ControlMaster.Followers -= ControlSlots; + if (m_ControlMaster is PlayerMobile mobile) + { + mobile.AllFollowers.Remove(this); + if (mobile.AutoStabled.Contains(this)) + mobile.AutoStabled.Remove(this); + } + } + else if (m_SummonMaster != null) + { + m_SummonMaster.Followers -= ControlSlots; + if (m_SummonMaster is PlayerMobile mobile) mobile.AllFollowers.Remove(this); + } + + if (m_ControlMaster != null && m_ControlMaster.Followers < 0) + m_ControlMaster.Followers = 0; + + if (m_SummonMaster != null && m_SummonMaster.Followers < 0) + m_SummonMaster.Followers = 0; + } + + public void AddFollowers() + { + if (m_ControlMaster != null) + { + m_ControlMaster.Followers += ControlSlots; + if (m_ControlMaster is PlayerMobile mobile) mobile.AllFollowers.Add(this); + } + else if (m_SummonMaster != null) + { + m_SummonMaster.Followers += ControlSlots; + if (m_SummonMaster is PlayerMobile mobile) mobile.AllFollowers.Add(this); + } + } + + public virtual void OnGotMeleeAttack(Mobile attacker) + { + if (AutoDispel && attacker is BaseCreature creature && creature.IsDispellable && + AutoDispelChance > Utility.RandomDouble()) + Dispel(creature); + } + + public virtual void Dispel(Mobile m) + { + Effects.SendLocationParticles(EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), 0x3728, 8, 20, + 5042); + Effects.PlaySound(m, m.Map, 0x201); + + m.Delete(); + } + + public virtual void OnGaveMeleeAttack(Mobile defender) + { + Poison p = HitPoison; + + if (m_Paragon) + p = PoisonImpl.IncreaseLevel(p); + + if (p != null && HitPoisonChance >= Utility.RandomDouble()) + { + defender.ApplyPoison(this, p); + + if (Controlled) + CheckSkill(SkillName.Poisoning, 0, Skills[SkillName.Poisoning].Cap); + } + + if (AutoDispel && defender is BaseCreature creature && creature.IsDispellable && + AutoDispelChance > Utility.RandomDouble()) + Dispel(creature); + } + + public override void OnAfterDelete() + { + if (AIObject != null) + { + AIObject.m_Timer?.Stop(); + + AIObject = null; + } + + if (m_DeleteTimer != null) + { + m_DeleteTimer.Stop(); + m_DeleteTimer = null; + } + + FocusMob = null; + + if (IsAnimatedDead) + AnimateDeadSpell.Unregister(m_SummonMaster, this); + + if (MLQuestSystem.Enabled) + MLQuestSystem.HandleDeletion(this); + + base.OnAfterDelete(); + } + + public void DebugSay(string text) + { + if (Debug) + PublicOverheadMessage(MessageType.Regular, 41, false, text); + } + + public void DebugSay(string format, params object[] args) + { + if (Debug) + PublicOverheadMessage(MessageType.Regular, 41, false, string.Format(format, args)); + } + + /* + * This function can be overridden.. so a "Strongest" mobile, can have a different definition depending + * on who check for value + * -Could add a FightMode.Prefered + * + */ + + public virtual double GetFightModeRanking(Mobile m, FightMode acqType, bool bPlayerOnly) + { + if (bPlayerOnly && m.Player || !bPlayerOnly) + switch (acqType) + { + case FightMode.Strongest: + return m.Skills[SkillName.Tactics].Value + m.Str; //returns strongest mobile + + case FightMode.Weakest: + return -m.Hits; // returns weakest mobile + + default: + return -GetDistanceToSqrt(m); // returns closest mobile + } + + return double.MinValue; + } + + // Turn, - for left, + for right + // Basic for now, needs work + public virtual void Turn(int iTurnSteps) + { + int v = (int)Direction; + + Direction = (Direction)((((v & 0x7) + iTurnSteps) & 0x7) | (v & 0x80)); + } + + public virtual void TurnInternal(int iTurnSteps) + { + int v = (int)Direction; + + SetDirection((Direction)((((v & 0x7) + iTurnSteps) & 0x7) | (v & 0x80))); + } + + public bool IsHurt() + { + return Hits != HitsMax; + } + + public double GetHomeDistance() + { + return GetDistanceToSqrt(m_Home); + } + + public virtual int GetTeamSize(int iRange) + { + int iCount = 0; + + foreach (Mobile m in GetMobilesInRange(iRange)) + if (m != this && m is BaseCreature creature && !creature.Deleted && creature.Team == Team && + CanSee(creature)) + iCount++; + + return iCount; + } + + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); + + if (ControlMaster != null) + if (NotorietyHandlers.CheckAggressor(ControlMaster.Aggressors, aggressor)) + aggressor.Aggressors.Add(AggressorInfo.Create(this, aggressor, true)); + + OrderType ct = m_ControlOrder; + + if (AIObject != null) + { + if (!Core.ML || ct != OrderType.Follow && ct != OrderType.Stop && ct != OrderType.Stay) + { + AIObject.OnAggressiveAction(aggressor); + } + else + { + DebugSay("I'm being attacked but my master told me not to fight."); + Warmode = false; + return; + } + } + + StopFlee(); + + ForceReacquire(); + + if (!IsEnemy(aggressor)) + { + Player pl = Ethics.Player.Find(aggressor, true); + + if (pl != null && pl.IsShielded) + pl.FinishShield(); + } + + if (aggressor.ChangingCombatant && (m_Controlled || m_bSummoned) && + (ct == OrderType.Come || !Core.ML && ct == OrderType.Stay || ct == OrderType.Stop || ct == OrderType.None || + ct == OrderType.Follow)) + { + ControlTarget = aggressor; + ControlOrder = OrderType.Attack; + } + else if (Combatant == null && !BardPacified) + { + Warmode = true; + Combatant = aggressor; + } + } + + public override bool OnMoveOver(Mobile m) + { + if (m is BaseCreature creature && !creature.Controlled) + return !Alive || !creature.Alive || IsDeadBondedPet || creature.IsDeadBondedPet || + Hidden && AccessLevel > AccessLevel.Player; + + #region Dueling + + if (Region.IsPartOf(typeof(SafeZone)) && m is PlayerMobile pm) + if (pm.DuelContext == null || pm.DuelPlayer == null || !pm.DuelContext.Started || pm.DuelContext.Finished || + pm.DuelPlayer.Eliminated) + return true; + + #endregion + + return base.OnMoveOver(m); + } + + public virtual void AddCustomContextEntries(Mobile from, List list) + { + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (Commandable) + AIObject?.GetContextMenuEntries(from, list); + + if (m_bTamable && !m_Controlled && from.Alive) + list.Add(new TameEntry(from, this)); + + AddCustomContextEntries(from, list); + + if (CanTeach && from.Alive) + { + Skills ourSkills = Skills; + Skills theirSkills = from.Skills; + + for (int i = 0; i < ourSkills.Length && i < theirSkills.Length; ++i) + { + Skill skill = ourSkills[i]; + Skill theirSkill = theirSkills[i]; + + if (skill != null && theirSkill != null && skill.Base >= 60.0 && CheckTeach(skill.SkillName, from)) + { + int toTeach = skill.BaseFixedPoint / 3; + + if (toTeach > 420) + toTeach = 420; + + list.Add(new TeachEntry((SkillName)i, this, from, toTeach > theirSkill.BaseFixedPoint)); + } + } + } + } + + public override bool HandlesOnSpeech(Mobile from) + { + InhumanSpeech speechType = SpeechType; + + if (speechType != null && (speechType.Flags & IHSFlags.OnSpeech) != 0 && from.InRange(this, 3)) + return true; + + return AIObject != null && AIObject.HandlesOnSpeech(from) && from.InRange(this, RangePerception); + } + + public override void OnSpeech(SpeechEventArgs e) + { + InhumanSpeech speechType = SpeechType; + + if (speechType != null && speechType.OnSpeech(this, e.Mobile, e.Speech)) + e.Handled = true; + else if (!e.Handled && AIObject != null && e.Mobile.InRange(this, RangePerception)) + AIObject.OnSpeech(e); + } + + public override bool IsHarmfulCriminal(Mobile target) + { + if (Controlled && target == m_ControlMaster || Summoned && target == m_SummonMaster) + return false; + + if (target is BaseCreature creature && creature.InitialInnocent && !creature.Controlled) + return false; + + if (target is PlayerMobile mobile && mobile.PermaFlags.Count > 0) + return false; + + return base.IsHarmfulCriminal(target); + } + + public override void CriminalAction(bool message) + { + base.CriminalAction(message); + + if (Controlled || Summoned) + { + if (m_ControlMaster != null && m_ControlMaster.Player) + m_ControlMaster.CriminalAction(false); + else if (m_SummonMaster != null && m_SummonMaster.Player) + m_SummonMaster.CriminalAction(false); + } + } + + public override void DoHarmful(Mobile target, bool indirect) + { + base.DoHarmful(target, indirect); + + if (target == this || target == m_ControlMaster || target == m_SummonMaster || !Controlled && !Summoned) + return; + + List list = Aggressors; + + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo ai = list[i]; + + if (ai.Attacker == target) + return; + } + + list = Aggressed; + + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo ai = list[i]; + + if (ai.Defender == target) + { + if (m_ControlMaster != null && m_ControlMaster.Player && m_ControlMaster.CanBeHarmful(target, false)) + m_ControlMaster.DoHarmful(target, true); + else if (m_SummonMaster != null && m_SummonMaster.Player && m_SummonMaster.CanBeHarmful(target, false)) + m_SummonMaster.DoHarmful(target, true); + + return; + } + } + } + + public void ReleaseGuardDupeLock() + { + m_NoDupeGuards = null; + } + + public void ReleaseGuardLock() + { + EndAction(typeof(GuardedRegion)); + } + + public virtual bool CheckIdle() + { + if (Combatant != null) + return false; // in combat.. not idling + + if (m_IdleReleaseTime > DateTime.MinValue) + { + // idling... + + if (DateTime.UtcNow >= m_IdleReleaseTime) + { + m_IdleReleaseTime = DateTime.MinValue; + return false; // idle is over + } + + return true; // still idling + } + + if (95 > Utility.Random(100)) + return false; // not idling, but don't want to enter idle state + + m_IdleReleaseTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(15, 25)); + + if (Body.IsHuman) + switch (Utility.Random(2)) + { + case 0: + CheckedAnimate(5, 5, 1, true, true, 1); + break; + case 1: + CheckedAnimate(6, 5, 1, true, false, 1); + break; + } + else if (Body.IsAnimal) + switch (Utility.Random(3)) + { + case 0: + CheckedAnimate(3, 3, 1, true, false, 1); + break; + case 1: + CheckedAnimate(9, 5, 1, true, false, 1); + break; + case 2: + CheckedAnimate(10, 5, 1, true, false, 1); + break; + } + else if (Body.IsMonster) + switch (Utility.Random(2)) + { + case 0: + CheckedAnimate(17, 5, 1, true, false, 1); + break; + case 1: + CheckedAnimate(18, 5, 1, true, false, 1); + break; + } + + PlaySound(GetIdleSound()); + return true; // entered idle state + } + + /* + this way, due to the huge number of locations this will have to be changed + Perhaps we can change this in the future when fixing game play is not the + major issue. + */ + + public virtual void CheckedAnimate(int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay) + { + if (!Mounted) base.Animate(action, frameCount, repeatCount, forward, repeat, delay); + } + + private void CheckAIActive() + { + Map map = Map; + + if (PlayerRangeSensitive && AIObject != null && map != null && map.GetSector(Location).Active) + AIObject.Activate(); + } + + public override void OnCombatantChange() + { + base.OnCombatantChange(); + + Warmode = Combatant != null && !Combatant.Deleted && Combatant.Alive; + + if (CanFly && Warmode) Flying = false; + } + + protected override void OnMapChange(Map oldMap) + { + CheckAIActive(); + + base.OnMapChange(oldMap); + } + + protected override void OnLocationChange(Point3D oldLocation) + { + CheckAIActive(); + + base.OnLocationChange(oldLocation); + } + + public virtual void ForceReacquire() + { + NextReacquireTime = Core.TickCount; + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (AcquireOnApproach && !Controlled && !Summoned && FightMode != FightMode.Aggressor) + { + if (InRange(m.Location, AcquireOnApproachRange) && !InRange(oldLocation, AcquireOnApproachRange)) + if (CanBeHarmful(m) && IsEnemy(m)) + { + Combatant = FocusMob = m; + + AIObject?.MoveTo(m, true, 1); + + DoHarmful(m); + } + } + else if (ReacquireOnMovement) + { + ForceReacquire(); + } + + InhumanSpeech speechType = SpeechType; + + speechType?.OnMovement(this, m, oldLocation); + + /* Begin notice sound */ + if ((!m.Hidden || m.AccessLevel == AccessLevel.Player) && m.Player && FightMode != FightMode.Aggressor && + FightMode != FightMode.None && Combatant == null && !Controlled && !Summoned) + if (InRange(m.Location, 18) && !InRange(oldLocation, 18)) + { + if (Body.IsMonster) + Animate(11, 5, 1, true, false, 1); + + PlaySound(GetAngerSound()); + } + /* End notice sound */ + + if (MLQuestSystem.Enabled && CanShout && m is PlayerMobile mobile) + CheckShout(mobile, oldLocation); + + if (m_NoDupeGuards == m) + return; + + if (!Body.IsHuman || Kills >= 5 || AlwaysMurderer || AlwaysAttackable || m.Kills < 5 || + !m.InRange(Location, 12) || !m.Alive) + return; + + if (Region.GetRegion(typeof(GuardedRegion)) is GuardedRegion guardedRegion) + if (!guardedRegion.IsDisabled() && guardedRegion.IsGuardCandidate(m) && BeginAction(typeof(GuardedRegion))) + { + Say(1013037 + Utility.Random(16)); + guardedRegion.CallGuards(Location); + + Timer.DelayCall(TimeSpan.FromSeconds(5.0), ReleaseGuardLock); + + m_NoDupeGuards = m; + Timer.DelayCall(TimeSpan.Zero, ReleaseGuardDupeLock); + } + } + + public void AddSpellAttack(Type type) + { + m_SpellAttack.Add(type); + } + + public void AddSpellDefense(Type type) + { + m_SpellDefense.Add(type); + } + + public Spell GetAttackSpellRandom() + { + if (m_SpellAttack.Count == 0) + return null; + + Type type = m_SpellAttack[Utility.Random(m_SpellAttack.Count)]; + return Activator.CreateInstance(type, this, null) as Spell; + } + + public Spell GetDefenseSpellRandom() + { + if (m_SpellDefense.Count == 0) + return null; + + Type type = m_SpellDefense[Utility.Random(m_SpellDefense.Count)]; + return Activator.CreateInstance(type, this, null) as Spell; + } + + public Spell GetSpellSpecific(Type type) + { + int i; + + for (i = 0; i < m_SpellAttack.Count; i++) + if (m_SpellAttack[i] == type) + return Activator.CreateInstance(type, this, null) as Spell; + + for (i = 0; i < m_SpellDefense.Count; i++) + if (m_SpellDefense[i] == type) + return Activator.CreateInstance(type, this, null) as Spell; + + return null; + } + + public static void Cap(ref int val, int min, int max) + { + if (val < min) + val = min; + else if (val > max) + val = max; + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster && !Body.IsHuman) + { + Container pack = Backpack; + + pack?.DisplayTo(from); + } + + if (DeathAdderCharmable && from.CanBeHarmful(this, false)) + if (SummonFamiliarSpell.Table[from] is DeathAdder da && !da.Deleted) + { + from.SendAsciiMessage("You charm the snake. Select a target to attack."); + from.Target = new DeathAdderCharmTarget(this); + } + + if (MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile) + MLQuestSystem.OnDoubleClick(this, mobile); + + base.OnDoubleClick(from); + } + + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + + if (MLQuestSystem.Enabled && CanGiveMLQuest) + list.Add(1072269); // Quest Giver + + if (Core.ML) + { + if (DisplayWeight) + list.Add(TotalWeight == 1 ? 1072788 : 1072789, TotalWeight.ToString()); // Weight: ~1_WEIGHT~ stones + + if (m_ControlOrder == OrderType.Guard) + list.Add(1080078); // guarding + } + + if (Summoned && !IsAnimatedDead && !IsNecroFamiliar && !(this is Clone)) + { + list.Add(1049646); // (summoned) + } + else if (Controlled && Commandable) + { + if (IsBonded) //Intentional difference (showing ONLY bonded when bonded instead of bonded & tame) + list.Add(1049608); // (bonded) + else + list.Add(502006); // (tame) + } + } + + public override void OnSingleClick(Mobile from) + { + if (Controlled && Commandable) + { + int number; + + if (Summoned) + number = 1049646; // (summoned) + else if (IsBonded) + number = 1049608; // (bonded) + else + number = 502006; // (tame) + + PrivateOverheadMessage(MessageType.Regular, 0x3B2, number, from.NetState); + } + + base.OnSingleClick(from); + } + + public override bool OnBeforeDeath() + { + int treasureLevel = TreasureMapLevel; + + if (treasureLevel == 1 && Map == Map.Trammel && TreasureMap.IsInHavenIsland(this)) + { + Mobile killer = LastKiller; + + if (killer is BaseCreature bc) + killer = bc.GetMaster(); + + if (killer is PlayerMobile mobile && mobile.Young) + treasureLevel = 0; + } + + if (!Summoned && !NoKillAwards && !IsBonded) + { + if (treasureLevel >= 0) + { + if (m_Paragon && Paragon.ChestChance > Utility.RandomDouble()) + PackItem(new ParagonChest(Name, treasureLevel)); + else if ((Map == Map.Felucca || Map == Map.Trammel) && TreasureMap.LootChance >= Utility.RandomDouble()) + PackItem(new TreasureMap(treasureLevel, Map)); + } + + if (m_Paragon && Paragon.ChocolateIngredientChance > Utility.RandomDouble()) + switch (Utility.Random(4)) + { + case 0: + PackItem(new CocoaButter()); + break; + case 1: + PackItem(new CocoaLiquor()); + break; + case 2: + PackItem(new SackOfSugar()); + break; + case 3: + PackItem(new Vanilla()); + break; + } + } + + if (!Summoned && !NoKillAwards && !m_HasGeneratedLoot) + { + m_HasGeneratedLoot = true; + GenerateLoot(false); + } + + if (!NoKillAwards && Region.IsPartOf("Doom")) + { + int bones = TheSummoningQuest.GetDaemonBonesFor(this); + + if (bones > 0) + PackItem(new DaemonBone(bones)); + } + + if (IsAnimatedDead) + Effects.SendLocationEffect(Location, Map, 0x3728, 13, 1, 0x461, 4); + + InhumanSpeech speechType = SpeechType; + + speechType?.OnDeath(this); + + ReceivedHonorContext?.OnTargetKilled(); + + return base.OnBeforeDeath(); + } + + public int ComputeBonusDamage(List list, Mobile m) + { + int bonus = 0; + + for (int i = list.Count - 1; i >= 0; --i) + { + DamageEntry de = list[i]; + + if (de.Damager == m || !(de.Damager is BaseCreature bc)) + continue; + + if (bc.GetMaster() == m) + bonus += de.DamageGiven; + } + + return bonus; + } + + public Mobile GetMaster() + { + if (Controlled && ControlMaster != null) + return ControlMaster; + if (Summoned && SummonMaster != null) + return SummonMaster; + + return null; + } + + public static List GetLootingRights(List damageEntries, int hitsMax) + { + List rights = new List(); + + for (int i = damageEntries.Count - 1; i >= 0; --i) + { + if (i >= damageEntries.Count) + continue; + + DamageEntry de = damageEntries[i]; + + if (de.HasExpired) + { + damageEntries.RemoveAt(i); + continue; + } + + int damage = de.DamageGiven; + + List respList = de.Responsible; + + if (respList != null) + for (int j = 0; j < respList.Count; ++j) + { + DamageEntry subEntry = respList[j]; + Mobile master = subEntry.Damager; + + if (master == null || master.Deleted || !master.Player) + continue; + + bool needNewSubEntry = true; + + for (int k = 0; needNewSubEntry && k < rights.Count; ++k) + { + DamageStore ds = rights[k]; + + if (ds.m_Mobile == master) + { + ds.m_Damage += subEntry.DamageGiven; + needNewSubEntry = false; + } + } - public virtual bool CanDestroyObstacles => false; - - public void Unpacify() - { - BardEndTime = DateTime.UtcNow; - BardPacified = false; - } - - public HonorContext ReceivedHonorContext { get; set; } - - /* - - Seems this actually was removed on OSI somewhere between the original bug report and now. - We will call it ML, until we can get better information. I suspect it was on the OSI TC when - originally it taken out of RunUO, and not implemented on OSIs production shards until more - recently. Either way, this is, or was, accurate OSI behavior, and just entirely - removing it was incorrect. OSI followers were distracted by being attacked well into - AoS, at very least. - - */ - - public virtual bool CanBeDistracted => !Core.ML; - - public virtual void CheckDistracted( Mobile from ) - { - if ( Utility.RandomDouble() < .10 ) - { - ControlTarget = from; - ControlOrder = OrderType.Attack; - Combatant = from; - Warmode = true; - } - } - - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( BardPacified && (HitsMax - Hits) * 0.001 > Utility.RandomDouble() ) - Unpacify(); - - int disruptThreshold; - //NPCs can use bandages too! - if ( !Core.AOS ) - disruptThreshold = 0; - else if ( from != null && from.Player ) - disruptThreshold = 18; - else - disruptThreshold = 25; - - if ( amount > disruptThreshold ) - { - BandageContext c = BandageContext.GetContext( this ); - - c?.Slip(); - } - - if ( Confidence.IsRegenerating( this ) ) - Confidence.StopRegenerating( this ); - - WeightOverloading.FatigueOnDamage( this, amount ); - - InhumanSpeech speechType = SpeechType; - - if ( speechType != null && !willKill ) - speechType.OnDamage( this, amount ); - - ReceivedHonorContext?.OnTargetDamaged( from, amount ); - - if ( !willKill ) - { - if ( CanBeDistracted && ControlOrder == OrderType.Follow ) - { - CheckDistracted( from ); - } - } - else if ( from is PlayerMobile mobile ) - { - Timer.DelayCall( TimeSpan.FromSeconds( 10 ), mobile.RecoverAmmo ); - } - - base.OnDamage( amount, from, willKill ); - } - - public virtual void OnDamagedBySpell( Mobile from ) - { - if ( CanBeDistracted && ControlOrder == OrderType.Follow ) - { - CheckDistracted( from ); - } - } - - public virtual void OnHarmfulSpell( Mobile from ) - { - } - - #region Alter[...]Damage From/To - - public virtual void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - } - - public virtual void AlterDamageScalarTo( Mobile target, ref double scalar ) - { - } - - public virtual void AlterSpellDamageFrom( Mobile from, ref int damage ) - { - } - - public virtual void AlterSpellDamageTo( Mobile to, ref int damage ) - { - } - - public virtual void AlterMeleeDamageFrom( Mobile from, ref int damage ) - { - } - - public virtual void AlterMeleeDamageTo( Mobile to, ref int damage ) - { - } - - #endregion - - public virtual void CheckReflect( Mobile caster, ref bool reflect ) - { - } - - public virtual void OnCarve( Mobile from, Corpse corpse, Item with ) - { - int feathers = Feathers; - int wool = Wool; - int meat = Meat; - int hides = Hides; - int scales = Scales; - - if ( ( feathers == 0 && wool == 0 && meat == 0 && hides == 0 && scales == 0 ) || Summoned || IsBonded || corpse.Animated ) - { - if ( corpse.Animated ) - corpse.SendLocalizedMessageTo( from, 500464 ); // Use this on corpses to carve away meat and hide - else - from.SendLocalizedMessage( 500485 ); // You see nothing useful to carve from the corpse. - } - else - { - if ( Core.ML && from.Race == Race.Human ) - hides = (int)Math.Ceiling( hides * 1.1 ); // 10% bonus only applies to hides, ore & logs - - if ( corpse.Map == Map.Felucca ) - { - feathers *= 2; - wool *= 2; - hides *= 2; - - if (Core.ML) - { - meat *= 2; - scales *= 2; - } - } - - new Blood( 0x122D ).MoveToWorld( corpse.Location, corpse.Map ); - - if ( feathers != 0 ) - { - corpse.AddCarvedItem( new Feather( feathers ), from ); - from.SendLocalizedMessage( 500479 ); // You pluck the bird. The feathers are now on the corpse. - } - - if ( wool != 0 ) - { - corpse.AddCarvedItem( new TaintedWool( wool ), from ); - from.SendLocalizedMessage( 500483 ); // You shear it, and the wool is now on the corpse. - } - - if ( meat != 0 ) - { - if ( MeatType == MeatType.Ribs ) - corpse.AddCarvedItem( new RawRibs( meat ), from ); - else if ( MeatType == MeatType.Bird ) - corpse.AddCarvedItem( new RawBird( meat ), from ); - else if ( MeatType == MeatType.LambLeg ) - corpse.AddCarvedItem( new RawLambLeg( meat ), from ); - - from.SendLocalizedMessage( 500467 ); // You carve some meat, which remains on the corpse. - } - - if ( hides != 0 ) - { - Item holding = from.Weapon as Item; - - if ( Core.AOS && ( holding is SkinningKnife /* TODO: || holding is ButcherWarCleaver || with is ButcherWarCleaver */ ) ) - { - Item leather = null; - - switch ( HideType ) - { - case HideType.Regular: leather = new Leather( hides ); break; - case HideType.Spined: leather = new SpinedLeather( hides ); break; - case HideType.Horned: leather = new HornedLeather( hides ); break; - case HideType.Barbed: leather = new BarbedLeather( hides ); break; - } - - if ( leather != null ) - { - if ( !from.PlaceInBackpack( leather ) ) - { - corpse.DropItem( leather ); - from.SendLocalizedMessage( 500471 ); // You skin it, and the hides are now in the corpse. - } - else - { - from.SendLocalizedMessage( 1073555 ); // You skin it and place the cut-up hides in your backpack. - } - } - } - else - { - if ( HideType == HideType.Regular ) - corpse.DropItem( new Hides( hides ) ); - else if ( HideType == HideType.Spined ) - corpse.DropItem( new SpinedHides( hides ) ); - else if ( HideType == HideType.Horned ) - corpse.DropItem( new HornedHides( hides ) ); - else if ( HideType == HideType.Barbed ) - corpse.DropItem( new BarbedHides( hides ) ); - - from.SendLocalizedMessage( 500471 ); // You skin it, and the hides are now in the corpse. - } - } - - if ( scales != 0 ) - { - ScaleType sc = ScaleType; - - switch ( sc ) - { - case ScaleType.Red: corpse.AddCarvedItem( new RedScales( scales ), from ); break; - case ScaleType.Yellow: corpse.AddCarvedItem( new YellowScales( scales ), from ); break; - case ScaleType.Black: corpse.AddCarvedItem( new BlackScales( scales ), from ); break; - case ScaleType.Green: corpse.AddCarvedItem( new GreenScales( scales ), from ); break; - case ScaleType.White: corpse.AddCarvedItem( new WhiteScales( scales ), from ); break; - case ScaleType.Blue: corpse.AddCarvedItem( new BlueScales( scales ), from ); break; - case ScaleType.All: - { - corpse.AddCarvedItem( new RedScales( scales ), from ); - corpse.AddCarvedItem( new YellowScales( scales ), from ); - corpse.AddCarvedItem( new BlackScales( scales ), from ); - corpse.AddCarvedItem( new GreenScales( scales ), from ); - corpse.AddCarvedItem( new WhiteScales( scales ), from ); - corpse.AddCarvedItem( new BlueScales( scales ), from ); - break; - } - } - - from.SendMessage( "You cut away some scales, but they remain on the corpse." ); - } - - corpse.Carved = true; - - if ( corpse.IsCriminalAction( from ) ) - from.CriminalAction( true ); - } - } - - public const int DefaultRangePerception = 16; - public const int OldRangePerception = 10; - - public BaseCreature(AIType ai, - FightMode mode, - int iRangePerception, - int iRangeFight, - double dActiveSpeed, - double dPassiveSpeed) - { - if ( iRangePerception == OldRangePerception ) - iRangePerception = DefaultRangePerception; - - m_Loyalty = MaxLoyalty; // Wonderfully Happy - - m_CurrentAI = ai; - m_DefaultAI = ai; - - RangePerception = iRangePerception; - RangeFight = iRangeFight; - - FightMode = mode; - - m_Team = 0; - - SpeedInfo.GetSpeeds( this, ref dActiveSpeed, ref dPassiveSpeed ); - - ActiveSpeed = dActiveSpeed; - PassiveSpeed = dPassiveSpeed; - m_CurrentSpeed = dPassiveSpeed; - - Debug = false; - - m_SpellAttack = new List(); - m_SpellDefense = new List(); - - m_Controlled = false; - m_ControlMaster = null; - ControlTarget = null; - m_ControlOrder = OrderType.None; - - m_bTamable = false; - - Owners = new List(); - - NextReacquireTime = Core.TickCount + (int)ReacquireDelay.TotalMilliseconds; - - ChangeAIType(AI); + if (needNewSubEntry) + rights.Add(new DamageStore(master, subEntry.DamageGiven)); - InhumanSpeech speechType = SpeechType; + damage -= subEntry.DamageGiven; + } - speechType?.OnConstruct( this ); + Mobile m = de.Damager; - if ( IsInvulnerable && !Core.AOS ) - NameHue = 0x35; + if (m == null || m.Deleted || !m.Player) + continue; - GenerateLoot( true ); - } + if (damage <= 0) + continue; - public BaseCreature( Serial serial ) : base( serial ) - { - m_SpellAttack = new List(); - m_SpellDefense = new List(); + bool needNewEntry = true; - Debug = false; - } + for (int j = 0; needNewEntry && j < rights.Count; ++j) + { + DamageStore ds = rights[j]; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (ds.m_Mobile == m) + { + ds.m_Damage += damage; + needNewEntry = false; + } + } - writer.Write( (int) 19 ); // version + if (needNewEntry) + rights.Add(new DamageStore(m, damage)); + } - writer.Write( (int)m_CurrentAI ); - writer.Write( (int)m_DefaultAI ); + if (rights.Count > 0) + { + rights[0].m_Damage = + (int)(rights[0].m_Damage * + 1.25 + ); //This would be the first valid person attacking it. Gets a 25% bonus. Per 1/19/07 Five on Friday - writer.Write( (int)RangePerception ); - writer.Write( (int)RangeFight ); + if (rights.Count > 1) + rights.Sort(); //Sort by damage - writer.Write( (int)m_Team ); + int topDamage = rights[0].m_Damage; + int minDamage; - writer.Write( (double)ActiveSpeed ); - writer.Write( (double)PassiveSpeed ); - writer.Write( (double)m_CurrentSpeed ); + if (hitsMax >= 3000) + minDamage = topDamage / 16; + else if (hitsMax >= 1000) + minDamage = topDamage / 8; + else if (hitsMax >= 200) + minDamage = topDamage / 4; + else + minDamage = topDamage / 2; - writer.Write( (int) m_Home.X ); - writer.Write( (int) m_Home.Y ); - writer.Write( (int) m_Home.Z ); + for (int i = 0; i < rights.Count; ++i) + { + DamageStore ds = rights[i]; - // Version 1 - writer.Write( (int) RangeHome ); + ds.m_HasRight = ds.m_Damage >= minDamage; + } + } + + return rights; + } + + public virtual void OnKilledBy(Mobile mob) + { + #region Mondain's Legacy + + if (GivesMLMinorArtifact) + { + if (MondainsLegacy.CheckArtifactChance(mob, this)) + MondainsLegacy.GiveArtifactTo(mob); + } + + #endregion + + else if (m_Paragon) + { + if (Paragon.CheckArtifactChance(mob, this)) + Paragon.GiveArtifactTo(mob); + } + } + + public override void OnDeath(Container c) + { + MeerMage.StopEffect(this, false); + + if (IsBonded) + { + int sound = GetDeathSound(); + + if (sound >= 0) + Effects.PlaySound(this, Map, sound); + + Warmode = false; + + Poison = null; + Combatant = null; + + Hits = 0; + Stam = 0; + Mana = 0; + + IsDeadPet = true; + ControlTarget = ControlMaster; + ControlOrder = OrderType.Follow; + + ProcessDeltaQueue(); + SendIncomingPacket(); + SendIncomingPacket(); + + // TODO: This can be done in Parallel if there are lots of them. + List aggressors = Aggressors; + + for (int i = 0; i < aggressors.Count; ++i) + { + AggressorInfo info = aggressors[i]; + + if (info.Attacker.Combatant == this) + info.Attacker.Combatant = null; + } + + List aggressed = Aggressed; + + for (int i = 0; i < aggressed.Count; ++i) + { + AggressorInfo info = aggressed[i]; + + if (info.Defender.Combatant == this) + info.Defender.Combatant = null; + } + + Mobile owner = ControlMaster; + + if (owner == null || owner.Deleted || owner.Map != Map || !owner.InRange(this, 12) || !CanSee(owner) || + !InLOS(owner)) + { + if (OwnerAbandonTime == DateTime.MinValue) + OwnerAbandonTime = DateTime.UtcNow; + } + else + { + OwnerAbandonTime = DateTime.MinValue; + } + + GiftOfLifeSpell.HandleDeath(this); + + CheckStatTimers(); + } + else + { + if (!Summoned && !NoKillAwards) + { + int totalFame = Fame / 100; + int totalKarma = -Karma / 100; + + if (Map == Map.Felucca) + { + totalFame += totalFame / 10 * 3; + totalKarma += totalKarma / 10 * 3; + } + + List list = GetLootingRights(DamageEntries, HitsMax); + List titles = new List(); + List fame = new List(); + List karma = new List(); + + bool givenQuestKill = false; + bool givenFactionKill = false; + bool givenToTKill = false; + + for (int i = 0; i < list.Count; ++i) + { + DamageStore ds = list[i]; + + if (!ds.m_HasRight) + continue; + + Party party = Engines.PartySystem.Party.Get(ds.m_Mobile); + + if (party != null) + { + int divedFame = totalFame / party.Members.Count; + int divedKarma = totalKarma / party.Members.Count; + + for (int j = 0; j < party.Members.Count; ++j) + { + PartyMemberInfo info = party.Members[j]; + + if (info?.Mobile != null) + { + int index = titles.IndexOf(info.Mobile); + + if (index == -1) + { + titles.Add(info.Mobile); + fame.Add(divedFame); + karma.Add(divedKarma); + } + else + { + fame[index] += divedFame; + karma[index] += divedKarma; + } + } + } + } + else + { + titles.Add(ds.m_Mobile); + fame.Add(totalFame); + karma.Add(totalKarma); + } + + OnKilledBy(ds.m_Mobile); + + if (!givenFactionKill) + { + givenFactionKill = true; + Faction.HandleDeath(this, ds.m_Mobile); + } + + Region region = ds.m_Mobile.Region; + + if (!givenToTKill && (Map == Map.Tokuno || region.IsPartOf("Yomotsu Mines") || + region.IsPartOf("Fan Dancer's Dojo"))) + { + givenToTKill = true; + TreasuresOfTokuno.HandleKill(this, ds.m_Mobile); + } + + if (ds.m_Mobile is PlayerMobile pm) + { + if (MLQuestSystem.Enabled) MLQuestSystem.HandleKill(pm, this); + + if (givenQuestKill) + continue; + + QuestSystem qs = pm.Quest; + + if (qs != null) + { + qs.OnKill(this, c); + givenQuestKill = true; + } + } + } + + for (int i = 0; i < titles.Count; ++i) + { + Titles.AwardFame(titles[i], fame[i], true); + Titles.AwardKarma(titles[i], karma[i], true); + } + } + + base.OnDeath(c); + + if (DeleteCorpseOnDeath) + c.Delete(); + } + } + + public override void OnDelete() + { + Mobile m = m_ControlMaster; + + SetControlMaster(null); + SummonMaster = null; + + ReceivedHonorContext?.Cancel(); + + base.OnDelete(); + + m?.InvalidateProperties(); + } + + public override bool CanBeHarmful(Mobile target, bool message, bool ignoreOurBlessedness) + { + if (target is BaseFactionGuard) + return false; + + if (target is BaseCreature creature && creature.IsInvulnerable || target is PlayerVendor || target is TownCrier) + { + if (message) + { + if (target.Title == null) + SendMessage("{0} cannot be harmed.", target.Name); + else + SendMessage("{0} {1} cannot be harmed.", target.Name, target.Title); + } + + return false; + } + + return base.CanBeHarmful(target, message, ignoreOurBlessedness); + } + + public override bool CanBeRenamedBy(Mobile from) + { + return Controlled && from == ControlMaster && !from.Region.IsPartOf(typeof(Jail)) || + base.CanBeRenamedBy(from); + } + + public bool SetControlMaster(Mobile m) + { + if (m == null) + { + ControlMaster = null; + Controlled = false; + ControlTarget = null; + ControlOrder = OrderType.None; + Guild = null; + + Delta(MobileDelta.Noto); + } + else + { + ISpawner se = Spawner; + if (se?.UnlinkOnTaming == true) + { + Spawner.Remove(this); + Spawner = null; + } + + if (m.Followers + ControlSlots > m.FollowersMax) + { + m.SendLocalizedMessage(1049607); // You have too many followers to control that creature. + return false; + } + + CurrentWayPoint = null; //so tamed animals don't try to go back + + Home = Point3D.Zero; + + ControlMaster = m; + Controlled = true; + ControlTarget = null; + ControlOrder = OrderType.Come; + Guild = null; + + if (m_DeleteTimer != null) + { + m_DeleteTimer.Stop(); + m_DeleteTimer = null; + } + + Delta(MobileDelta.Noto); + } + + InvalidateProperties(); + + return true; + } + + public override void OnRegionChange(Region Old, Region New) + { + base.OnRegionChange(Old, New); + + if (Controlled) + if (Spawner is SpawnEntry se && !se.UnlinkOnTaming && (New == null || !New.AcceptsSpawnsFrom(se.Region))) + { + Spawner.Remove(this); + Spawner = null; + } + } + + public static bool Summon(BaseCreature creature, Mobile caster, Point3D p, int sound, TimeSpan duration) + { + return Summon(creature, true, caster, p, sound, duration); + } + + public static bool Summon(BaseCreature creature, bool controlled, Mobile caster, Point3D p, int sound, + TimeSpan duration) + { + if (caster.Followers + creature.ControlSlots > caster.FollowersMax) + { + caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + creature.Delete(); + return false; + } + + Summoning = true; + + if (controlled) + creature.SetControlMaster(caster); + + creature.RangeHome = 10; + creature.Summoned = true; + + creature.SummonMaster = caster; + + Container pack = creature.Backpack; + + if (pack != null) + for (int i = pack.Items.Count - 1; i >= 0; --i) + { + if (i >= pack.Items.Count) + continue; + + pack.Items[i].Delete(); + } + + new UnsummonTimer(caster, creature, duration).Start(); + creature.SummonEnd = DateTime.UtcNow + duration; + + creature.MoveToWorld(p, caster.Map); + + Effects.PlaySound(p, creature.Map, sound); + + Summoning = false; + + return true; + } + + public virtual void OnThink() + { + long tc = Core.TickCount; + + if (EnableRummaging && CanRummageCorpses && !Summoned && !Controlled && tc - m_NextRummageTime >= 0) + { + double min, max; + + if (ChanceToRummage > Utility.RandomDouble() && Rummage()) + { + min = MinutesToNextRummageMin; + max = MinutesToNextRummageMax; + } + else + { + min = MinutesToNextChanceMin; + max = MinutesToNextChanceMax; + } + + double delay = min + Utility.RandomDouble() * (max - min); + m_NextRummageTime = tc + (int)TimeSpan.FromMinutes(delay).TotalMilliseconds; + } + + if (CanBreath && tc - m_NextBreathTime >= 0 + ) // tested: controlled dragons do breath fire, what about summoned skeletal dragons? + { + Mobile target = Combatant; + + if (target != null && target.Alive && !target.IsDeadBondedPet && CanBeHarmful(target) && target.Map == Map && + !IsDeadBondedPet && target.InRange(this, BreathRange) && InLOS(target) && !BardPacified) + { + if (Core.TickCount - m_NextBreathTime < 30000 && Utility.RandomBool()) BreathStart(target); + + m_NextBreathTime = tc + (int)TimeSpan + .FromSeconds(BreathMinDelay + + Utility.RandomDouble() * (BreathMaxDelay - BreathMinDelay)) + .TotalMilliseconds; + } + } + + if ((CanHeal || CanHealOwner) && Alive && !IsHealing && !BardPacified) + { + Mobile owner = ControlMaster; + + if (owner != null && CanHealOwner && tc - m_NextHealOwnerTime >= 0 && CanBeBeneficial(owner, true, true) && + owner.Map == Map && InRange(owner, HealStartRange) && InLOS(owner) && + owner.Hits < HealOwnerTrigger * owner.HitsMax) + { + HealStart(owner); + + m_NextHealOwnerTime = tc + (int)TimeSpan.FromSeconds(HealOwnerInterval).TotalMilliseconds; + } + else if (CanHeal && tc - m_NextHealTime >= 0 && CanBeBeneficial(this) && + (Hits < HealTrigger * HitsMax || Poisoned)) + { + HealStart(this); + + m_NextHealTime = tc + (int)TimeSpan.FromSeconds(HealInterval).TotalMilliseconds; + } + } + + if (ReturnsToHome && IsSpawnerBound() && !InRange(Home, RangeHome)) + { + if (Combatant == null && Warmode == false && Utility.RandomDouble() < .10) /* some throttling */ + { + m_FailedReturnHome = !Move(GetDirectionTo(Home.X, Home.Y)) ? m_FailedReturnHome + 1 : 0; + + if (m_FailedReturnHome > 5) + { + SetLocation(Home, true); + + m_FailedReturnHome = 0; + } + } + } + else + { + m_FailedReturnHome = 0; + } + + if (HasAura && tc - m_NextAura >= 0) + { + AuraDamage(); + m_NextAura = tc + (int)AuraInterval.TotalMilliseconds; + } + } + + public virtual bool Rummage() + { + Corpse toRummage = null; + + IPooledEnumerable eable = GetItemsInRange(2); + foreach (Corpse item in eable) + if (item.Items.Count > 0) + { + toRummage = item; + break; + } + + eable.Free(); + + if (toRummage == null) + return false; + + Container pack = Backpack; + + if (pack == null) + return false; + + List items = toRummage.Items; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[Utility.Random(items.Count)]; + + Lift(item, item.Amount, out bool rejected, out LRReason reason); + + if (!rejected && Drop(this, new Point3D(-1, -1, 0))) + { + // *rummages through a corpse and takes an item* + PublicOverheadMessage(MessageType.Emote, 0x3B2, 1008086); + //TODO: Instancing of Rummaged stuff. + return true; + } + } + + return false; + } + + public void Pacify(Mobile master, DateTime endtime) + { + BardPacified = true; + BardEndTime = endtime; + } + + public override Mobile GetDamageMaster(Mobile damagee) + { + if (BardProvoked && damagee == BardTarget) + return BardMaster; + if (m_Controlled && m_ControlMaster != null) + return m_ControlMaster; + if (m_bSummoned && m_SummonMaster != null) + return m_SummonMaster; + + return base.GetDamageMaster(damagee); + } + + public void Provoke(Mobile master, Mobile target, bool bSuccess) + { + BardProvoked = true; + + if (!Core.ML) PublicOverheadMessage(MessageType.Emote, EmoteHue, false, "*looks furious*"); + + if (bSuccess) + { + PlaySound(GetIdleSound()); + + BardMaster = master; + BardTarget = target; + Combatant = target; + BardEndTime = DateTime.UtcNow + TimeSpan.FromSeconds(30.0); + + if (target is BaseCreature t) + { + if (t.Unprovokable || t.IsParagon && BaseInstrument.GetBaseDifficulty(t) >= 160.0) + return; + + t.BardProvoked = true; + + t.BardMaster = master; + t.BardTarget = this; + t.Combatant = this; + t.BardEndTime = DateTime.UtcNow + TimeSpan.FromSeconds(30.0); + } + } + else + { + PlaySound(GetAngerSound()); - int i=0; + BardMaster = master; + BardTarget = target; + } + } - writer.Write( (int) m_SpellAttack.Count ); - for ( i=0; i< m_SpellAttack.Count; i++ ) - { - writer.Write( m_SpellAttack[i].ToString() ); - } + public bool FindMyName(string str, bool bWithAll) + { + string name = Name; + + if (name == null || str.Length < name.Length) + return false; - writer.Write( (int) m_SpellDefense.Count ); - for ( i=0; i< m_SpellDefense.Count; i++ ) - { - writer.Write( m_SpellDefense[i].ToString() ); - } + string[] wordsString = str.Split(' '); + string[] wordsName = name.Split(' '); + + for (int j = 0; j < wordsName.Length; j++) + { + string wordName = wordsName[j]; - // Version 2 - writer.Write( (int) FightMode ); + bool bFound = false; + for (int i = 0; i < wordsString.Length; i++) + { + string word = wordsString[i]; + + if (Insensitive.Equals(word, wordName)) + bFound = true; + + if (bWithAll && Insensitive.Equals(word, "all")) + return true; + } + + if (!bFound) + return false; + } + + return true; + } + + public static void TeleportPets(Mobile master, Point3D loc, Map map, bool onlyBonded = false) + { + List move = new List(); + + foreach (Mobile m in master.GetMobilesInRange(3)) + if (m is BaseCreature pet) + if (pet.Controlled && pet.ControlMaster == master && !onlyBonded || pet.IsBonded) + if (pet.ControlOrder == OrderType.Guard || pet.ControlOrder == OrderType.Follow || + pet.ControlOrder == OrderType.Come) + move.Add(pet); + + foreach (Mobile m in move) + m.MoveToWorld(loc, map); + } + + public virtual void ResurrectPet() + { + if (!IsDeadPet) + return; + + OnBeforeResurrect(); + + Poison = null; - writer.Write( (bool) m_Controlled ); - writer.Write( (Mobile) m_ControlMaster ); - writer.Write( (Mobile) ControlTarget ); - writer.Write( (Point3D) ControlDest ); - writer.Write( (int) m_ControlOrder ); - writer.Write( (double) MinTameSkill ); - // Removed in version 9 - //writer.Write( (double) m_dMaxTameSkill ); - writer.Write( (bool) m_bTamable ); - writer.Write( (bool) m_bSummoned ); + Warmode = false; - if ( m_bSummoned ) - writer.WriteDeltaTime( SummonEnd ); + Hits = 10; + Stam = StamMax; + Mana = 0; - writer.Write( (int) ControlSlots ); + ProcessDeltaQueue(); - // Version 3 - writer.Write( (int)m_Loyalty ); + IsDeadPet = false; - // Version 4 - writer.Write( CurrentWayPoint ); + Effects.SendPacket(Location, Map, new BondedStatus(0, Serial, 0)); - // Verison 5 - writer.Write( m_SummonMaster ); + SendIncomingPacket(); + SendIncomingPacket(); - // Version 6 - writer.Write( (int) HitsMaxSeed ); - writer.Write( (int) StamMaxSeed ); - writer.Write( (int) ManaMaxSeed ); - writer.Write( (int) m_DamageMin ); - writer.Write( (int) m_DamageMax ); + OnAfterResurrect(); + + Mobile owner = ControlMaster; + + if (owner == null || owner.Deleted || owner.Map != Map || !owner.InRange(this, 12) || !CanSee(owner) || + !InLOS(owner)) + { + if (OwnerAbandonTime == DateTime.MinValue) + OwnerAbandonTime = DateTime.UtcNow; + } + else + { + OwnerAbandonTime = DateTime.MinValue; + } + + CheckStatTimers(); + } - // Version 7 - writer.Write( (int) m_PhysicalResistance ); - writer.Write( (int) PhysicalDamage ); + public override bool CanBeDamaged() + { + if (IsDeadPet || IsInvulnerable) + return false; - writer.Write( (int) m_FireResistance ); - writer.Write( (int) FireDamage ); + return base.CanBeDamaged(); + } - writer.Write( (int) m_ColdResistance ); - writer.Write( (int) ColdDamage ); + private bool IsSpawnerBound() + { + return Map != null && Map != Map.Internal && + FightMode != FightMode.None && RangeHome >= 0 && + !Controlled && !Summoned && Spawner is Spawner spawner && spawner.Map == Map; + } - writer.Write( (int) m_PoisonResistance ); - writer.Write( (int) PoisonDamage ); + public override void OnSectorDeactivate() + { + if (!Deleted && ReturnsToHome && IsSpawnerBound() && !InRange(Home, RangeHome + 5)) + { + Timer.DelayCall(TimeSpan.FromSeconds(Utility.Random(45) + 15), GoHome_Callback); - writer.Write( (int) m_EnergyResistance ); - writer.Write( (int) EnergyDamage ); + m_ReturnQueued = true; + } + else if (PlayerRangeSensitive) + { + AIObject?.Deactivate(); + } - // Version 8 - writer.Write( Owners, true ); + base.OnSectorDeactivate(); + } - // Version 10 - writer.Write( (bool) IsDeadPet ); - writer.Write( (bool) m_IsBonded ); - writer.Write( (DateTime) BondingBegin ); - writer.Write( (DateTime) OwnerAbandonTime ); + public void GoHome_Callback() + { + if (m_ReturnQueued && IsSpawnerBound()) + if (!Map.GetSector(X, Y).Active) + { + SetLocation(Home, true); - // Version 11 - writer.Write( (bool) m_HasGeneratedLoot ); + if (!Map.GetSector(X, Y).Active) AIObject?.Deactivate(); + } - // Version 12 - writer.Write( (bool) m_Paragon ); + m_ReturnQueued = false; + } - // Version 13 - writer.Write( (bool) ( Friends != null && Friends.Count > 0 ) ); + public override void OnSectorActivate() + { + if (PlayerRangeSensitive) AIObject?.Activate(); - if ( Friends != null && Friends.Count > 0 ) - writer.Write( Friends, true ); + base.OnSectorActivate(); + } - // Version 14 - writer.Write( (bool)RemoveIfUntamed ); - writer.Write( (int)RemoveStep ); - - // Version 17 - if ( IsStabled || ( Controlled && ControlMaster != null ) ) - writer.Write( TimeSpan.Zero ); - else - writer.Write( DeleteTimeLeft ); - - // Version 18 - writer.Write( CorpseNameOverride ); - - // Version 19 - writer.Write( HomeMap ); - } - - private static double[] m_StandardActiveSpeeds = { - 0.175, 0.1, 0.15, 0.2, 0.25, 0.3, 0.4, 0.5, 0.6, 0.8 - }; - - private static double[] m_StandardPassiveSpeeds = { - 0.350, 0.2, 0.4, 0.5, 0.6, 0.8, 1.0, 1.2, 1.6, 2.0 - }; - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_CurrentAI = (AIType)reader.ReadInt(); - m_DefaultAI = (AIType)reader.ReadInt(); - - RangePerception = reader.ReadInt(); - RangeFight = reader.ReadInt(); - - m_Team = reader.ReadInt(); - - ActiveSpeed = reader.ReadDouble(); - PassiveSpeed = reader.ReadDouble(); - m_CurrentSpeed = reader.ReadDouble(); - - if ( RangePerception == OldRangePerception ) - RangePerception = DefaultRangePerception; - - m_Home.X = reader.ReadInt(); - m_Home.Y = reader.ReadInt(); - m_Home.Z = reader.ReadInt(); - - if ( version >= 1 ) - { - RangeHome = reader.ReadInt(); - - int iCount = reader.ReadInt(); - for ( int i = 0; i < iCount; i++ ) - { - string str = reader.ReadString(); - Type type = Type.GetType( str ); - - if ( type != null ) - { - m_SpellAttack.Add( type ); - } - } - - iCount = reader.ReadInt(); - for ( int i=0; i < iCount; i++ ) - { - string str = reader.ReadString(); - Type type = Type.GetType( str ); - - if ( type != null ) - { - m_SpellDefense.Add( type ); - } - } - } - else - { - RangeHome = 0; - } - - if ( version >= 2 ) - { - FightMode = ( FightMode )reader.ReadInt(); - - m_Controlled = reader.ReadBool(); - m_ControlMaster = reader.ReadMobile(); - ControlTarget = reader.ReadMobile(); - ControlDest = reader.ReadPoint3D(); - m_ControlOrder = (OrderType) reader.ReadInt(); - - MinTameSkill = reader.ReadDouble(); - - if ( version < 9 ) - reader.ReadDouble(); - - m_bTamable = reader.ReadBool(); - m_bSummoned = reader.ReadBool(); - - if ( m_bSummoned ) - { - SummonEnd = reader.ReadDeltaTime(); - new UnsummonTimer( m_ControlMaster, this, SummonEnd - DateTime.UtcNow ).Start(); - } - - ControlSlots = reader.ReadInt(); - } - else - { - FightMode = FightMode.Closest; - - m_Controlled = false; - m_ControlMaster = null; - ControlTarget = null; - m_ControlOrder = OrderType.None; - } - - if ( version >= 3 ) - m_Loyalty = reader.ReadInt(); - else - m_Loyalty = MaxLoyalty; // Wonderfully Happy - - if ( version >= 4 ) - CurrentWayPoint = reader.ReadItem() as WayPoint; - - if ( version >= 5 ) - m_SummonMaster = reader.ReadMobile(); - - if ( version >= 6 ) - { - HitsMaxSeed = reader.ReadInt(); - StamMaxSeed = reader.ReadInt(); - ManaMaxSeed = reader.ReadInt(); - m_DamageMin = reader.ReadInt(); - m_DamageMax = reader.ReadInt(); - } - - if ( version >= 7 ) - { - m_PhysicalResistance = reader.ReadInt(); - PhysicalDamage = reader.ReadInt(); - - m_FireResistance = reader.ReadInt(); - FireDamage = reader.ReadInt(); - - m_ColdResistance = reader.ReadInt(); - ColdDamage = reader.ReadInt(); - - m_PoisonResistance = reader.ReadInt(); - PoisonDamage = reader.ReadInt(); - - m_EnergyResistance = reader.ReadInt(); - EnergyDamage = reader.ReadInt(); - } - - if ( version >= 8 ) - Owners = reader.ReadStrongMobileList(); - else - Owners = new List(); - - if ( version >= 10 ) - { - IsDeadPet = reader.ReadBool(); - m_IsBonded = reader.ReadBool(); - BondingBegin = reader.ReadDateTime(); - OwnerAbandonTime = reader.ReadDateTime(); - } - - if ( version >= 11 ) - m_HasGeneratedLoot = reader.ReadBool(); - else - m_HasGeneratedLoot = true; - - if ( version >= 12 ) - m_Paragon = reader.ReadBool(); - else - m_Paragon = false; - - if ( version >= 13 && reader.ReadBool() ) - Friends = reader.ReadStrongMobileList(); - else if ( version < 13 && m_ControlOrder >= OrderType.Unfriend ) - ++m_ControlOrder; - - if ( version < 16 && Loyalty != MaxLoyalty ) - Loyalty *= 10; - - double activeSpeed = ActiveSpeed; - double passiveSpeed = PassiveSpeed; - - SpeedInfo.GetSpeeds( this, ref activeSpeed, ref passiveSpeed ); - - bool isStandardActive = false; - for ( int i = 0; !isStandardActive && i < m_StandardActiveSpeeds.Length; ++i ) - isStandardActive = ( ActiveSpeed == m_StandardActiveSpeeds[i] ); - - bool isStandardPassive = false; - for ( int i = 0; !isStandardPassive && i < m_StandardPassiveSpeeds.Length; ++i ) - isStandardPassive = ( PassiveSpeed == m_StandardPassiveSpeeds[i] ); - - if ( isStandardActive && m_CurrentSpeed == ActiveSpeed ) - m_CurrentSpeed = activeSpeed; - else if ( isStandardPassive && m_CurrentSpeed == PassiveSpeed ) - m_CurrentSpeed = passiveSpeed; - - if ( isStandardActive && !m_Paragon ) - ActiveSpeed = activeSpeed; - - if ( isStandardPassive && !m_Paragon ) - PassiveSpeed = passiveSpeed; - - if ( version >= 14 ) - { - RemoveIfUntamed = reader.ReadBool(); - RemoveStep = reader.ReadInt(); - } + private class TameEntry : ContextMenuEntry + { + private BaseCreature m_Mobile; - TimeSpan deleteTime = TimeSpan.Zero; - - if ( version >= 17 ) - deleteTime = reader.ReadTimeSpan(); + public TameEntry(Mobile from, BaseCreature creature) : base(6130, 6) + { + m_Mobile = creature; - if ( deleteTime > TimeSpan.Zero || LastOwner != null && !Controlled && !IsStabled ) - { - if ( deleteTime == TimeSpan.Zero ) - deleteTime = TimeSpan.FromDays( 3.0 ); - - m_DeleteTimer = new DeleteTimer( this, deleteTime ); - m_DeleteTimer.Start(); - } - - if ( version >= 18 ) - CorpseNameOverride = reader.ReadString(); - - if ( version >= 19 ) - HomeMap = reader.ReadMap(); - - if ( version <= 14 && m_Paragon && Hue == 0x31 ) - { - Hue = Paragon.Hue; //Paragon hue fixed, should now be 0x501. - } - - if ( Core.AOS && NameHue == 0x35 ) - NameHue = -1; - - CheckStatTimers(); - - ChangeAIType(m_CurrentAI); - - AddFollowers(); - - if ( IsAnimatedDead ) - AnimateDeadSpell.Register( m_SummonMaster, this ); - } - - public virtual bool IsHumanInTown() - { - return ( Body.IsHuman && Region.IsPartOf( typeof( GuardedRegion ) ) ); - } - - public virtual bool CheckGold( Mobile from, Item dropped ) - { - return dropped is Gold gold && OnGoldGiven(from, gold); - } + Enabled = Enabled && (from.Female ? creature.AllowFemaleTamer : creature.AllowMaleTamer); + } - public virtual bool OnGoldGiven( Mobile from, Gold dropped ) - { - if ( CheckTeachingMatch( from ) ) - { - if ( Teach( m_Teaching, from, dropped.Amount, true ) ) - { - dropped.Delete(); - return true; - } - } - else if ( IsHumanInTown() ) - { - Direction = GetDirectionTo( from ); + public override void OnClick() + { + if (!Owner.From.CheckAlive()) + return; - int oldSpeechHue = SpeechHue; + Owner.From.TargetLocked = true; + AnimalTaming.DisableMessage = true; - SpeechHue = 0x23F; - SayTo( from, "Thou art giving me gold?" ); + if (Owner.From.UseSkill(SkillName.AnimalTaming)) + Owner.From.Target.Invoke(Owner.From, m_Mobile); - if ( dropped.Amount >= 400 ) - SayTo( from, "'Tis a noble gift." ); - else - SayTo( from, "Money is always welcome." ); + AnimalTaming.DisableMessage = false; + Owner.From.TargetLocked = false; + } + } - SpeechHue = 0x3B2; - SayTo( from, 501548 ); // I thank thee. + private class DeathAdderCharmTarget : Target + { + private BaseCreature m_Charmed; - SpeechHue = oldSpeechHue; + public DeathAdderCharmTarget(BaseCreature charmed) : base(-1, false, TargetFlags.Harmful) + { + m_Charmed = charmed; + } - dropped.Delete(); - return true; - } + protected override void OnTarget(Mobile from, object targeted) + { + if (!m_Charmed.DeathAdderCharmable || m_Charmed.Combatant != null || !from.CanBeHarmful(m_Charmed, false)) + return; - return false; - } + if (!(SummonFamiliarSpell.Table[from] is DeathAdder da) || da.Deleted) + return; - public override bool ShouldCheckStatTimers => false; + if (!(targeted is Mobile targ) || !from.CanBeHarmful(targ, false)) + return; - #region Food - private static Type[] m_Eggs = { - typeof( FriedEggs ), typeof( Eggs ) - }; + from.RevealingAction(); + from.DoHarmful(targ, true); - private static Type[] m_Fish = { - typeof( FishSteak ), typeof( RawFishSteak ) - }; - - private static Type[] m_GrainsAndHay = { - typeof( BreadLoaf ), typeof( FrenchBread ), typeof( SheafOfHay ) - }; - - private static Type[] m_Meat = { - /* Cooked */ - typeof( Bacon ), typeof( CookedBird ), typeof( Sausage ), - typeof( Ham ), typeof( Ribs ), typeof( LambLeg ), - typeof( ChickenLeg ), - - /* Uncooked */ - typeof( RawBird ), typeof( RawRibs ), typeof( RawLambLeg ), - typeof( RawChickenLeg ), - - /* Body Parts */ - typeof( Head ), typeof( LeftArm ), typeof( LeftLeg ), - typeof( Torso ), typeof( RightArm ), typeof( RightLeg ) - }; - - private static Type[] m_FruitsAndVegies = { - typeof( HoneydewMelon ), typeof( YellowGourd ), typeof( GreenGourd ), - typeof( Banana ), typeof( Bananas ), typeof( Lemon ), typeof( Lime ), - typeof( Dates ), typeof( Grapes ), typeof( Peach ), typeof( Pear ), - typeof( Apple ), typeof( Watermelon ), typeof( Squash ), - typeof( Cantaloupe ), typeof( Carrot ), typeof( Cabbage ), - typeof( Onion ), typeof( Lettuce ), typeof( Pumpkin ) - }; - - private static Type[] m_Gold = { - // white wyrms eat gold.. - typeof( Gold ) - }; - - public virtual bool CheckFoodPreference( Item f ) - { - if ( CheckFoodPreference( f, FoodType.Eggs, m_Eggs ) ) - return true; - - if ( CheckFoodPreference( f, FoodType.Fish, m_Fish ) ) - return true; - - if ( CheckFoodPreference( f, FoodType.GrainsAndHay, m_GrainsAndHay ) ) - return true; - - if ( CheckFoodPreference( f, FoodType.Meat, m_Meat ) ) - return true; - - if ( CheckFoodPreference( f, FoodType.FruitsAndVegies, m_FruitsAndVegies ) ) - return true; - - if ( CheckFoodPreference( f, FoodType.Gold, m_Gold ) ) - return true; - - return false; - } - - public virtual bool CheckFoodPreference( Item fed, FoodType type, Type[] types ) - { - if ( (FavoriteFood & type) == 0 ) - return false; - - Type fedType = fed.GetType(); - bool contains = false; - - for ( int i = 0; !contains && i < types.Length; ++i ) - contains = ( fedType == types[i] ); - - return contains; - } - - public virtual bool CheckFeed( Mobile from, Item dropped ) - { - if ( !IsDeadPet && Controlled && ( ControlMaster == from || IsPetFriend( from ) ) ) - { - Item f = dropped; - - if ( CheckFoodPreference( f ) ) - { - int amount = f.Amount; - - if ( amount > 0 ) - { - int stamGain; - - if ( f is Gold ) - stamGain = amount - 50; - else - stamGain = (amount * 15) - 50; - - if ( stamGain > 0 ) - Stam += stamGain; - - if ( Core.SE ) - { - if ( m_Loyalty < MaxLoyalty ) - { - m_Loyalty = MaxLoyalty; - } - } - else - { - for ( int i = 0; i < amount; ++i ) - { - if ( m_Loyalty < MaxLoyalty && 0.5 >= Utility.RandomDouble() ) - { - m_Loyalty += 10; - } - } - } - - /* if ( happier )*/ // looks like in OSI pets say they are happier even if they are at maximum loyalty - SayTo( from, 502060 ); // Your pet looks happier. - - if ( Body.IsAnimal ) - Animate( 3, 5, 1, true, false, 0 ); - else if ( Body.IsMonster ) - Animate( 17, 5, 1, true, false, 0 ); - - if ( IsBondable && !IsBonded ) - { - Mobile master = m_ControlMaster; - - if ( master != null && master == from ) //So friends can't start the bonding process - { - if ( MinTameSkill <= 29.1 || master.Skills[SkillName.AnimalTaming].Base >= MinTameSkill || OverrideBondingReqs() || (Core.ML && master.Skills[SkillName.AnimalTaming].Value >= MinTameSkill) ) - { - if ( BondingBegin == DateTime.MinValue ) - { - BondingBegin = DateTime.UtcNow; - } - else if ( (BondingBegin + BondingDelay) <= DateTime.UtcNow ) - { - IsBonded = true; - BondingBegin = DateTime.MinValue; - from.SendLocalizedMessage( 1049666 ); // Your pet has bonded with you! - } - } - else if ( Core.ML ) - { - from.SendLocalizedMessage( 1075268 ); // Your pet cannot form a bond with you until your animal taming ability has risen. - } - } - } - - dropped.Delete(); - return true; - } - } - } - - return false; - } - - #endregion - - public virtual bool OverrideBondingReqs() - { - return false; - } - - public virtual bool CanAngerOnTame => false; - - #region OnAction[...] - - public virtual void OnActionWander() - { - } - - public virtual void OnActionCombat() - { - } - - public virtual void OnActionGuard() - { - } - - public virtual void OnActionFlee() - { - } - - public virtual void OnActionInteract() - { - } - - public virtual void OnActionBackoff() - { - } - - #endregion - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( CheckFeed( from, dropped ) ) - return true; - if ( CheckGold( from, dropped ) ) - return true; - - // Note: Yes, this happens for all questers (regardless of type, e.g. escorts), - // even if they can't offer you anything at the moment - if ( MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile ) - { - MLQuestSystem.Tell( this, mobile, 1074893 ); // You need to mark your quest items so I don't take the wrong object. Then speak to me. - return false; - } - - return base.OnDragDrop( from, dropped ); - } - - protected virtual BaseAI ForcedAI => null; - - public void ChangeAIType( AIType NewAI ) - { - AIObject?.m_Timer.Stop(); - - if ( ForcedAI != null ) - { - AIObject = ForcedAI; - return; - } - - AIObject = null; - - switch ( NewAI ) - { - case AIType.AI_Melee: - AIObject = new MeleeAI(this); - break; - case AIType.AI_Animal: - AIObject = new AnimalAI(this); - break; - case AIType.AI_Berserk: - AIObject = new BerserkAI(this); - break; - case AIType.AI_Archer: - AIObject = new ArcherAI(this); - break; - case AIType.AI_Healer: - AIObject = new HealerAI(this); - break; - case AIType.AI_Vendor: - AIObject = new VendorAI(this); - break; - case AIType.AI_Mage: - AIObject = new MageAI(this); - break; - case AIType.AI_Predator: - //m_AI = new PredatorAI(this); - AIObject = new MeleeAI(this); - break; - case AIType.AI_Thief: - AIObject = new ThiefAI(this); - break; - } - } - - public void ChangeAIToDefault() - { - ChangeAIType(m_DefaultAI); - } - - [CommandProperty( AccessLevel.GameMaster )] - public AIType AI - { - get => m_CurrentAI; - set - { - m_CurrentAI = value; - - if (m_CurrentAI == AIType.AI_Use_Default) - { - m_CurrentAI = m_DefaultAI; - } - - ChangeAIType(m_CurrentAI); - } - } - - [CommandProperty( AccessLevel.Administrator )] - public bool Debug { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Team - { - get => m_Team; - set - { - m_Team = value; - - OnTeamChange(); - } - } - - public virtual void OnTeamChange() - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile FocusMob { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public FightMode FightMode { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RangePerception { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RangeFight { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RangeHome { get; set; } = 10; - - [CommandProperty( AccessLevel.GameMaster )] - public double ActiveSpeed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public double PassiveSpeed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public double CurrentSpeed - { - get - { - if ( TargetLocation != null ) - return 0.3; - - return m_CurrentSpeed; - } - set - { - if ( m_CurrentSpeed != value ) - { - m_CurrentSpeed = value; - - AIObject?.OnCurrentSpeedChanged(); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Home - { - get => m_Home; - set => m_Home = value; - } - - [CommandProperty(AccessLevel.GameMaster)] - public Map HomeMap { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Controlled - { - get => m_Controlled; - set - { - if ( m_Controlled == value ) - return; - - m_Controlled = value; - Delta( MobileDelta.Noto ); - - InvalidateProperties(); - } - } - - public override void RevealingAction() - { - Spells.Sixth.InvisibilitySpell.RemoveTimer( this ); - - base.RevealingAction(); - } - - public void RemoveFollowers() - { - if ( m_ControlMaster != null ) - { - m_ControlMaster.Followers -= ControlSlots; - if ( m_ControlMaster is PlayerMobile mobile ) - { - mobile.AllFollowers.Remove( this ); - if ( mobile.AutoStabled.Contains( this ) ) - mobile.AutoStabled.Remove( this ); - } - } - else if ( m_SummonMaster != null ) - { - m_SummonMaster.Followers -= ControlSlots; - if ( m_SummonMaster is PlayerMobile mobile ) - { - mobile.AllFollowers.Remove( this ); - } - } - - if ( m_ControlMaster != null && m_ControlMaster.Followers < 0 ) - m_ControlMaster.Followers = 0; - - if ( m_SummonMaster != null && m_SummonMaster.Followers < 0 ) - m_SummonMaster.Followers = 0; - } - - public void AddFollowers() - { - if ( m_ControlMaster != null ) - { - m_ControlMaster.Followers += ControlSlots; - if ( m_ControlMaster is PlayerMobile mobile ) - { - mobile.AllFollowers.Add( this ); - } - } - else if ( m_SummonMaster != null ) - { - m_SummonMaster.Followers += ControlSlots; - if ( m_SummonMaster is PlayerMobile mobile ) - { - mobile.AllFollowers.Add( this ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile ControlMaster - { - get => m_ControlMaster; - set - { - if ( m_ControlMaster == value || this == value ) - return; - - RemoveFollowers(); - m_ControlMaster = value; - AddFollowers(); - if ( m_ControlMaster != null ) - StopDeleteTimer(); - - Delta( MobileDelta.Noto ); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile SummonMaster - { - get => m_SummonMaster; - set - { - if ( m_SummonMaster == value || this == value ) - return; - - RemoveFollowers(); - m_SummonMaster = value; - AddFollowers(); - - Delta( MobileDelta.Noto ); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile ControlTarget { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D ControlDest { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public OrderType ControlOrder - { - get => m_ControlOrder; - set - { - m_ControlOrder = value; - - AIObject?.OnCurrentOrderChanged(); - - InvalidateProperties(); - - m_ControlMaster?.InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool BardProvoked { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool BardPacified { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile BardMaster { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile BardTarget { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime BardEndTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public double MinTameSkill { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Tamable - { - get => m_bTamable && !m_Paragon; - set => m_bTamable = value; - } - - [CommandProperty( AccessLevel.Administrator )] - public bool Summoned - { - get => m_bSummoned; - set - { - if ( m_bSummoned == value ) - return; + m_Charmed.Combatant = targ; - NextReacquireTime = Core.TickCount; + if (m_Charmed.AIObject != null) + m_Charmed.AIObject.Action = ActionType.Combat; + } + } - m_bSummoned = value; - Delta( MobileDelta.Noto ); + #region Var declarations - InvalidateProperties(); - } - } + private AIType m_CurrentAI; // The current AI + private AIType m_DefaultAI; // The default AI - [CommandProperty( AccessLevel.Administrator )] - public int ControlSlots { get; set; } = 1; + private int m_Team; // Monster Team - public virtual bool NoHouseRestrictions => false; - public virtual bool IsHouseSummonable => false; + private double m_CurrentSpeed; // The current speed, lets say it could be changed by something; - #region Corpse Resources - public virtual int Feathers => 0; - public virtual int Wool => 0; + private Point3D m_Home; // The home position of the creature, used by some AI - public virtual MeatType MeatType => MeatType.Ribs; - public virtual int Meat => 0; + private List m_SpellAttack; // List of attack spell/power + private List m_SpellDefense; // List of defensive spell/power - public virtual int Hides => 0; - public virtual HideType HideType => HideType.Regular; + private bool m_Controlled; // Is controlled + private Mobile m_ControlMaster; // My master + private OrderType m_ControlOrder; // My order - public virtual int Scales => 0; - public virtual ScaleType ScaleType => ScaleType.Red; + private int m_Loyalty; - #endregion + private bool m_bTamable; - public virtual bool AutoDispel => false; - public virtual double AutoDispelChance => ((Core.SE) ? .10 : 1.0); + private bool m_bSummoned; - public virtual bool IsScaryToPets => false; - public virtual bool IsScaredOfScaryThings => true; + private Mobile m_SummonMaster; - public virtual bool CanRummageCorpses => false; + private int m_DamageMin = -1; + private int m_DamageMax = -1; - public virtual void OnGotMeleeAttack( Mobile attacker ) - { - if ( AutoDispel && attacker is BaseCreature creature && creature.IsDispellable && AutoDispelChance > Utility.RandomDouble() ) - Dispel( creature ); - } + private int m_PhysicalResistance; + private int m_FireResistance; + private int m_ColdResistance; + private int m_PoisonResistance; + private int m_EnergyResistance; - public virtual void Dispel( Mobile m ) - { - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x3728, 8, 20, 5042 ); - Effects.PlaySound( m, m.Map, 0x201 ); + private bool m_IsStabled; - m.Delete(); - } + private bool m_HasGeneratedLoot; // have we generated our loot yet? - public virtual bool DeleteOnRelease => m_bSummoned; + private bool m_Paragon; - public virtual void OnGaveMeleeAttack( Mobile defender ) - { - Poison p = HitPoison; + private int m_FailedReturnHome; /* return to home failure counter */ - if ( m_Paragon ) - p = PoisonImpl.IncreaseLevel( p ); + #endregion - if ( p != null && HitPoisonChance >= Utility.RandomDouble() ) - { - defender.ApplyPoison( this, p ); + #region ML Quest System - if ( Controlled ) - CheckSkill( SkillName.Poisoning, 0, Skills[SkillName.Poisoning].Cap ); - } + private List m_MLQuests; - if ( AutoDispel && defender is BaseCreature creature && creature.IsDispellable && AutoDispelChance > Utility.RandomDouble() ) - Dispel( creature ); - } - - public override void OnAfterDelete() - { - if ( AIObject != null ) - { - AIObject.m_Timer?.Stop(); - - AIObject = null; - } - - if ( m_DeleteTimer != null ) - { - m_DeleteTimer.Stop(); - m_DeleteTimer = null; - } - - FocusMob = null; + public List MLQuests + { + get + { + if (m_MLQuests == null) + { + if (StaticMLQuester) + m_MLQuests = MLQuestSystem.FindQuestList(GetType()); + else + m_MLQuests = ConstructQuestList(); - if ( IsAnimatedDead ) - AnimateDeadSpell.Unregister( m_SummonMaster, this ); - - if ( MLQuestSystem.Enabled ) - MLQuestSystem.HandleDeletion( this ); + if (m_MLQuests == null) + return + MLQuestSystem + .EmptyList; // return EmptyList, but don't cache it (run construction again next time) + } - base.OnAfterDelete(); - } + return m_MLQuests; + } + } - public void DebugSay( string text ) - { - if ( Debug ) - PublicOverheadMessage( MessageType.Regular, 41, false, text ); - } + public virtual bool CanGiveMLQuest => MLQuests.Count != 0; + public virtual bool StaticMLQuester => true; - public void DebugSay( string format, params object[] args ) - { - if ( Debug ) - PublicOverheadMessage( MessageType.Regular, 41, false, string.Format( format, args ) ); - } + protected virtual List ConstructQuestList() + { + return null; + } - /* - * This function can be overridden.. so a "Strongest" mobile, can have a different definition depending - * on who check for value - * -Could add a FightMode.Prefered - * - */ + public virtual bool CanShout => false; - public virtual double GetFightModeRanking( Mobile m, FightMode acqType, bool bPlayerOnly ) - { - if ( ( bPlayerOnly && m.Player ) || !bPlayerOnly ) - { - switch( acqType ) - { - case FightMode.Strongest : - return (m.Skills[SkillName.Tactics].Value + m.Str); //returns strongest mobile + public const int ShoutRange = 8; + public static readonly TimeSpan ShoutDelay = TimeSpan.FromMinutes(1); - case FightMode.Weakest : - return -m.Hits; // returns weakest mobile - - default : - return -GetDistanceToSqrt( m ); // returns closest mobile - } - } - - return double.MinValue; - } - - // Turn, - for left, + for right - // Basic for now, needs work - public virtual void Turn(int iTurnSteps) - { - int v = (int)Direction; - - Direction = (Direction)((((v & 0x7) + iTurnSteps) & 0x7) | (v & 0x80)); - } - - public virtual void TurnInternal(int iTurnSteps) - { - int v = (int)Direction; - - SetDirection( (Direction)((((v & 0x7) + iTurnSteps) & 0x7) | (v & 0x80)) ); - } - - public bool IsHurt() - { - return ( Hits != HitsMax ); - } - - public double GetHomeDistance() - { - return GetDistanceToSqrt( m_Home ); - } - - public virtual int GetTeamSize(int iRange) - { - int iCount = 0; - - foreach ( Mobile m in GetMobilesInRange( iRange ) ) - { - if (m != this && m is BaseCreature creature && !creature.Deleted && creature.Team == Team && CanSee( creature )) - { - iCount++; - } - } - - return iCount; - } - - private class TameEntry : ContextMenuEntry - { - private BaseCreature m_Mobile; - - public TameEntry( Mobile from, BaseCreature creature ) : base( 6130, 6 ) - { - m_Mobile = creature; + private DateTime m_MLNextShout; - Enabled = Enabled && ( from.Female ? creature.AllowFemaleTamer : creature.AllowMaleTamer ); - } + private void CheckShout(PlayerMobile pm, Point3D oldLocation) + { + if (m_MLNextShout > DateTime.UtcNow || pm.Hidden || !pm.Alive) + return; - public override void OnClick() - { - if ( !Owner.From.CheckAlive() ) - return; - - Owner.From.TargetLocked = true; - AnimalTaming.DisableMessage = true; - - if ( Owner.From.UseSkill( SkillName.AnimalTaming ) ) - Owner.From.Target.Invoke( Owner.From, m_Mobile ); - - AnimalTaming.DisableMessage = false; - Owner.From.TargetLocked = false; - } - } - - #region Teaching - public virtual bool CanTeach => false; - - public virtual bool CheckTeach( SkillName skill, Mobile from ) - { - if ( !CanTeach ) - return false; - - if ( skill == SkillName.Stealth && from.Skills[SkillName.Hiding].Base < Stealth.HidingRequirement ) - return false; - - if ( skill == SkillName.RemoveTrap && (from.Skills[SkillName.Lockpicking].Base < 50.0 || from.Skills[SkillName.DetectHidden].Base < 50.0) ) - return false; - - if ( !Core.AOS && (skill == SkillName.Focus || skill == SkillName.Chivalry || skill == SkillName.Necromancy) ) - return false; - - return true; - } + int shoutRange = ShoutRange; - public enum TeachResult - { - Success, - Failure, - KnowsMoreThanMe, - KnowsWhatIKnow, - SkillNotRaisable, - NotEnoughFreePoints - } - - public virtual TeachResult CheckTeachSkills( SkillName skill, Mobile m, int maxPointsToLearn, ref int pointsToLearn, bool doTeach ) - { - if ( !CheckTeach( skill, m ) || !m.CheckAlive() ) - return TeachResult.Failure; + if (!InRange(pm.Location, shoutRange) || InRange(oldLocation, shoutRange) || !CanSee(pm) || !InLOS(pm)) + return; - Skill ourSkill = Skills[skill]; - Skill theirSkill = m.Skills[skill]; + MLQuestContext context = MLQuestSystem.GetContext(pm); - if ( ourSkill == null || theirSkill == null ) - return TeachResult.Failure; + if (context != null && context.IsFull) + return; - int baseToSet = ourSkill.BaseFixedPoint / 3; + MLQuest quest = MLQuestSystem.RandomStarterQuest(this, pm, context); - if ( baseToSet > 420 ) - baseToSet = 420; - else if ( baseToSet < 200 ) - return TeachResult.Failure; + if (quest == null || !quest.Activated || context != null && context.IsDoingQuest(quest)) + return; - if ( baseToSet > theirSkill.CapFixedPoint ) - baseToSet = theirSkill.CapFixedPoint; - - pointsToLearn = baseToSet - theirSkill.BaseFixedPoint; - - if ( maxPointsToLearn > 0 && pointsToLearn > maxPointsToLearn ) - { - pointsToLearn = maxPointsToLearn; - baseToSet = theirSkill.BaseFixedPoint + pointsToLearn; - } - - if ( pointsToLearn < 0 ) - return TeachResult.KnowsMoreThanMe; - - if ( pointsToLearn == 0 ) - return TeachResult.KnowsWhatIKnow; - - if ( theirSkill.Lock != SkillLock.Up ) - return TeachResult.SkillNotRaisable; - - int freePoints = m.Skills.Cap - m.Skills.Total; - int freeablePoints = 0; - - if ( freePoints < 0 ) - freePoints = 0; - - for ( int i = 0; (freePoints + freeablePoints) < pointsToLearn && i < m.Skills.Length; ++i ) - { - Skill sk = m.Skills[i]; - - if ( sk == theirSkill || sk.Lock != SkillLock.Down ) - continue; - - freeablePoints += sk.BaseFixedPoint; - } - - if ( (freePoints + freeablePoints) == 0 ) - return TeachResult.NotEnoughFreePoints; - - if ( (freePoints + freeablePoints) < pointsToLearn ) - { - pointsToLearn = freePoints + freeablePoints; - baseToSet = theirSkill.BaseFixedPoint + pointsToLearn; - } - - if ( doTeach ) - { - int need = pointsToLearn - freePoints; - - for ( int i = 0; need > 0 && i < m.Skills.Length; ++i ) - { - Skill sk = m.Skills[i]; - - if ( sk == theirSkill || sk.Lock != SkillLock.Down ) - continue; - - if ( sk.BaseFixedPoint < need ) - { - need -= sk.BaseFixedPoint; - sk.BaseFixedPoint = 0; - } - else - { - sk.BaseFixedPoint -= need; - need = 0; - } - } - - /* Sanity check */ - if ( baseToSet > theirSkill.CapFixedPoint || (m.Skills.Total - theirSkill.BaseFixedPoint + baseToSet) > m.Skills.Cap ) - return TeachResult.NotEnoughFreePoints; - - theirSkill.BaseFixedPoint = baseToSet; - } - - return TeachResult.Success; - } - - public virtual bool CheckTeachingMatch( Mobile m ) - { - if ( m_Teaching == (SkillName)(-1) ) - return false; - - if ( m is PlayerMobile mobile ) - return ( mobile.Learning == m_Teaching ); - - return true; - } - - private SkillName m_Teaching = (SkillName)(-1); - - public virtual bool Teach( SkillName skill, Mobile m, int maxPointsToLearn, bool doTeach ) - { - int pointsToLearn = 0; - TeachResult res = CheckTeachSkills( skill, m, maxPointsToLearn, ref pointsToLearn, doTeach ); - - switch ( res ) - { - case TeachResult.KnowsMoreThanMe: - { - Say( 501508 ); // I cannot teach thee, for thou knowest more than I! - break; - } - case TeachResult.KnowsWhatIKnow: - { - Say( 501509 ); // I cannot teach thee, for thou knowest all I can teach! - break; - } - case TeachResult.NotEnoughFreePoints: - case TeachResult.SkillNotRaisable: - { - // Make sure this skill is marked to raise. If you are near the skill cap (700 points) you may need to lose some points in another skill first. - m.SendLocalizedMessage( 501510, "", 0x22 ); - break; - } - case TeachResult.Success: - { - if ( doTeach ) - { - Say( 501539 ); // Let me show thee something of how this is done. - m.SendLocalizedMessage( 501540 ); // Your skill level increases. - - m_Teaching = (SkillName)(-1); - - if ( m is PlayerMobile mobile ) - mobile.Learning = (SkillName)(-1); - } - else - { - // I will teach thee all I know, if paid the amount in full. The price is: - Say( 1019077, AffixType.Append, $" {pointsToLearn}", "" ); - Say( 1043108 ); // For less I shall teach thee less. - - m_Teaching = skill; - - if ( m is PlayerMobile mobile ) - mobile.Learning = skill; - } - - return true; - } - } - - return false; - } - - #endregion - - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); - - if ( ControlMaster != null ) - if ( NotorietyHandlers.CheckAggressor( ControlMaster.Aggressors, aggressor ) ) - aggressor.Aggressors.Add( AggressorInfo.Create( this, aggressor, true ) ); - - OrderType ct = m_ControlOrder; - - if ( AIObject != null ) - { - if ( !Core.ML || ( ct != OrderType.Follow && ct != OrderType.Stop && ct != OrderType.Stay ) ) - { - AIObject.OnAggressiveAction( aggressor ); - } - else - { - DebugSay( "I'm being attacked but my master told me not to fight." ); - Warmode = false; - return; - } - } - - StopFlee(); - - ForceReacquire(); - - if ( !IsEnemy( aggressor ) ) - { - Ethics.Player pl = Ethics.Player.Find( aggressor, true ); - - if ( pl != null && pl.IsShielded ) - pl.FinishShield(); - } - - if ( aggressor.ChangingCombatant && (m_Controlled || m_bSummoned) && (ct == OrderType.Come || ( !Core.ML && ct == OrderType.Stay ) || ct == OrderType.Stop || ct == OrderType.None || ct == OrderType.Follow) ) - { - ControlTarget = aggressor; - ControlOrder = OrderType.Attack; - } - else if ( Combatant == null && !BardPacified ) - { - Warmode = true; - Combatant = aggressor; - } - } - - public override bool OnMoveOver( Mobile m ) - { - if ( m is BaseCreature creature && !creature.Controlled ) - return ( !Alive || !creature.Alive || IsDeadBondedPet || creature.IsDeadBondedPet ) || ( Hidden && AccessLevel > AccessLevel.Player ); - #region Dueling - if ( Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) && m is PlayerMobile pm ) - { - if ( pm.DuelContext == null || pm.DuelPlayer == null || !pm.DuelContext.Started || pm.DuelContext.Finished || pm.DuelPlayer.Eliminated ) - return true; - } - #endregion - - return base.OnMoveOver( m ); - } - - public virtual void AddCustomContextEntries( Mobile from, List list ) - { - } - - public virtual bool CanDrop => IsBonded; - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( Commandable ) - AIObject?.GetContextMenuEntries( from, list ); - - if ( m_bTamable && !m_Controlled && from.Alive ) - list.Add( new TameEntry( from, this ) ); - - AddCustomContextEntries( from, list ); - - if ( CanTeach && from.Alive ) - { - Skills ourSkills = Skills; - Skills theirSkills = from.Skills; - - for ( int i = 0; i < ourSkills.Length && i < theirSkills.Length; ++i ) - { - Skill skill = ourSkills[i]; - Skill theirSkill = theirSkills[i]; - - if ( skill != null && theirSkill != null && skill.Base >= 60.0 && CheckTeach( skill.SkillName, from ) ) - { - int toTeach = skill.BaseFixedPoint / 3; - - if ( toTeach > 420 ) - toTeach = 420; - - list.Add( new TeachEntry( (SkillName)i, this, from, ( toTeach > theirSkill.BaseFixedPoint ) ) ); - } - } - } - } - - public override bool HandlesOnSpeech( Mobile from ) - { - InhumanSpeech speechType = SpeechType; - - if ( speechType != null && (speechType.Flags & IHSFlags.OnSpeech) != 0 && from.InRange( this, 3 ) ) - return true; - - return ( AIObject != null && AIObject.HandlesOnSpeech( from ) && from.InRange( this, RangePerception ) ); - } - - public override void OnSpeech( SpeechEventArgs e ) - { - InhumanSpeech speechType = SpeechType; - - if ( speechType != null && speechType.OnSpeech( this, e.Mobile, e.Speech ) ) - e.Handled = true; - else if ( !e.Handled && AIObject != null && e.Mobile.InRange( this, RangePerception ) ) - AIObject.OnSpeech( e ); - } - - public override bool IsHarmfulCriminal( Mobile target ) - { - if ( (Controlled && target == m_ControlMaster) || (Summoned && target == m_SummonMaster) ) - return false; - - if ( target is BaseCreature creature && creature.InitialInnocent && !creature.Controlled ) - return false; - - if ( target is PlayerMobile mobile && mobile.PermaFlags.Count > 0 ) - return false; - - return base.IsHarmfulCriminal( target ); - } - - public override void CriminalAction( bool message ) - { - base.CriminalAction( message ); - - if ( Controlled || Summoned ) - { - if ( m_ControlMaster != null && m_ControlMaster.Player ) - m_ControlMaster.CriminalAction( false ); - else if ( m_SummonMaster != null && m_SummonMaster.Player ) - m_SummonMaster.CriminalAction( false ); - } - } - - public override void DoHarmful( Mobile target, bool indirect ) - { - base.DoHarmful( target, indirect ); - - if ( target == this || target == m_ControlMaster || target == m_SummonMaster || (!Controlled && !Summoned) ) - return; - - List list = Aggressors; - - for ( int i = 0; i < list.Count; ++i ) - { - AggressorInfo ai = list[i]; - - if ( ai.Attacker == target ) - return; - } - - list = Aggressed; - - for ( int i = 0; i < list.Count; ++i ) - { - AggressorInfo ai = list[i]; - - if ( ai.Defender == target ) - { - if ( m_ControlMaster != null && m_ControlMaster.Player && m_ControlMaster.CanBeHarmful( target, false ) ) - m_ControlMaster.DoHarmful( target, true ); - else if ( m_SummonMaster != null && m_SummonMaster.Player && m_SummonMaster.CanBeHarmful( target, false ) ) - m_SummonMaster.DoHarmful( target, true ); - - return; - } - } - } - - private static Mobile m_NoDupeGuards; - - public void ReleaseGuardDupeLock() - { - m_NoDupeGuards = null; - } - - public void ReleaseGuardLock() - { - EndAction( typeof( GuardedRegion ) ); - } - - private DateTime m_IdleReleaseTime; - - public virtual bool CheckIdle() - { - if ( Combatant != null ) - return false; // in combat.. not idling - - if ( m_IdleReleaseTime > DateTime.MinValue ) - { - // idling... - - if ( DateTime.UtcNow >= m_IdleReleaseTime ) - { - m_IdleReleaseTime = DateTime.MinValue; - return false; // idle is over - } - - return true; // still idling - } - - if ( 95 > Utility.Random( 100 ) ) - return false; // not idling, but don't want to enter idle state - - m_IdleReleaseTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 15, 25 ) ); - - if ( Body.IsHuman ) - { - switch ( Utility.Random( 2 ) ) - { - case 0: CheckedAnimate( 5, 5, 1, true, true, 1 ); break; - case 1: CheckedAnimate( 6, 5, 1, true, false, 1 ); break; - } - } - else if ( Body.IsAnimal ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: CheckedAnimate( 3, 3, 1, true, false, 1 ); break; - case 1: CheckedAnimate( 9, 5, 1, true, false, 1 ); break; - case 2: CheckedAnimate( 10, 5, 1, true, false, 1 ); break; - } - } - else if ( Body.IsMonster ) - { - switch ( Utility.Random( 2 ) ) - { - case 0: CheckedAnimate( 17, 5, 1, true, false, 1 ); break; - case 1: CheckedAnimate( 18, 5, 1, true, false, 1 ); break; - } - } - - PlaySound( GetIdleSound() ); - return true; // entered idle state - } - - /* - this way, due to the huge number of locations this will have to be changed - Perhaps we can change this in the future when fixing game play is not the - major issue. - */ - - public virtual void CheckedAnimate( int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay ) - { - if ( !Mounted ) - { - base.Animate( action, frameCount, repeatCount, forward, repeat, delay ); - } - } - - private void CheckAIActive() - { - Map map = Map; - - if ( PlayerRangeSensitive && AIObject != null && map != null && map.GetSector( Location ).Active ) - AIObject.Activate(); - } - - public override void OnCombatantChange() - { - base.OnCombatantChange(); - - Warmode = ( Combatant != null && !Combatant.Deleted && Combatant.Alive ); - - if ( CanFly && Warmode ) - { - Flying = false; - } - } - - protected override void OnMapChange( Map oldMap ) - { - CheckAIActive(); - - base.OnMapChange( oldMap ); - } - - protected override void OnLocationChange( Point3D oldLocation ) - { - CheckAIActive(); - - base.OnLocationChange( oldLocation ); - } - - public virtual void ForceReacquire() - { - NextReacquireTime = Core.TickCount; - } - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( AcquireOnApproach && ( !Controlled && !Summoned ) && FightMode != FightMode.Aggressor ) - { - if ( InRange( m.Location, AcquireOnApproachRange ) && !InRange( oldLocation, AcquireOnApproachRange ) ) - { - if ( CanBeHarmful( m ) && IsEnemy( m )) - { - Combatant = FocusMob = m; - - AIObject?.MoveTo( m, true, 1 ); - - DoHarmful( m ); - } - } - } - else if ( ReacquireOnMovement ) - { - ForceReacquire(); - } - - InhumanSpeech speechType = SpeechType; - - speechType?.OnMovement( this, m, oldLocation ); - - /* Begin notice sound */ - if ( (!m.Hidden || m.AccessLevel == AccessLevel.Player) && m.Player && FightMode != FightMode.Aggressor && FightMode != FightMode.None && Combatant == null && !Controlled && !Summoned ) - { - // If this creature defends itself but doesn't actively attack (animal) or - // doesn't fight at all (vendor) then no notice sounds are played.. - // So, players are only notified of aggressive monsters - - // Monsters that are currently fighting are ignored - - // Controlled or summoned creatures are ignored - - if ( InRange( m.Location, 18 ) && !InRange( oldLocation, 18 ) ) - { - if ( Body.IsMonster ) - Animate( 11, 5, 1, true, false, 1 ); - - PlaySound( GetAngerSound() ); - } - } - /* End notice sound */ - - if ( MLQuestSystem.Enabled && CanShout && m is PlayerMobile mobile ) - CheckShout( mobile, oldLocation ); - - if ( m_NoDupeGuards == m ) - return; - - if ( !Body.IsHuman || Kills >= 5 || AlwaysMurderer || AlwaysAttackable || m.Kills < 5 || !m.InRange( Location, 12 ) || !m.Alive ) - return; - - if ( Region.GetRegion( typeof( GuardedRegion ) ) is GuardedRegion guardedRegion ) - { - if ( !guardedRegion.IsDisabled() && guardedRegion.IsGuardCandidate( m ) && BeginAction( typeof( GuardedRegion ) ) ) - { - Say( 1013037 + Utility.Random( 16 ) ); - guardedRegion.CallGuards( Location ); - - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), ReleaseGuardLock ); - - m_NoDupeGuards = m; - Timer.DelayCall( TimeSpan.Zero, ReleaseGuardDupeLock ); - } - } - } - - public void AddSpellAttack( Type type ) - { - m_SpellAttack.Add ( type ); - } - - public void AddSpellDefense( Type type ) - { - m_SpellDefense.Add ( type ); - } - - public Spell GetAttackSpellRandom() - { - if (m_SpellAttack.Count == 0) - return null; - - Type type = m_SpellAttack[Utility.Random(m_SpellAttack.Count)]; - return Activator.CreateInstance( type, this, null) as Spell; - } - - public Spell GetDefenseSpellRandom() - { - if (m_SpellDefense.Count == 0) - return null; - - Type type = m_SpellDefense[Utility.Random(m_SpellDefense.Count)]; - return Activator.CreateInstance( type, this, null ) as Spell; - } - - public Spell GetSpellSpecific( Type type ) - { - int i; - - for( i=0; i< m_SpellAttack.Count; i++ ) - { - if ( m_SpellAttack[i] == type ) - { - return Activator.CreateInstance( type, this, null ) as Spell; - } - } - - for ( i=0; i< m_SpellDefense.Count; i++ ) - { - if ( m_SpellDefense[i] == type ) - { - return Activator.CreateInstance( type, this, null ) as Spell; - } - } - - return null; - } - - #region Set[...] - - public void SetDamage( int val ) - { - m_DamageMin = val; - m_DamageMax = val; - } - - public void SetDamage( int min, int max ) - { - m_DamageMin = min; - m_DamageMax = max; - } - - public void SetHits( int val ) - { - if ( val < 1000 && !Core.AOS ) - val = (val * 100) / 60; - - HitsMaxSeed = val; - Hits = HitsMax; - } - - public void SetHits( int min, int max ) - { - if ( min < 1000 && !Core.AOS ) - { - min = (min * 100) / 60; - max = (max * 100) / 60; - } - - HitsMaxSeed = Utility.RandomMinMax( min, max ); - Hits = HitsMax; - } - - public void SetStam( int val ) - { - StamMaxSeed = val; - Stam = StamMax; - } - - public void SetStam( int min, int max ) - { - StamMaxSeed = Utility.RandomMinMax( min, max ); - Stam = StamMax; - } - - public void SetMana( int val ) - { - ManaMaxSeed = val; - Mana = ManaMax; - } - - public void SetMana( int min, int max ) - { - ManaMaxSeed = Utility.RandomMinMax( min, max ); - Mana = ManaMax; - } - - public void SetStr( int val ) - { - RawStr = val; - Hits = HitsMax; - } - - public void SetStr( int min, int max ) - { - RawStr = Utility.RandomMinMax( min, max ); - Hits = HitsMax; - } - - public void SetDex( int val ) - { - RawDex = val; - Stam = StamMax; - } - - public void SetDex( int min, int max ) - { - RawDex = Utility.RandomMinMax( min, max ); - Stam = StamMax; - } - - public void SetInt( int val ) - { - RawInt = val; - Mana = ManaMax; - } - - public void SetInt( int min, int max ) - { - RawInt = Utility.RandomMinMax( min, max ); - Mana = ManaMax; - } - - public void SetDamageType( ResistanceType type, int min, int max ) - { - SetDamageType( type, Utility.RandomMinMax( min, max ) ); - } - - public void SetDamageType( ResistanceType type, int val ) - { - switch ( type ) - { - case ResistanceType.Physical: PhysicalDamage = val; break; - case ResistanceType.Fire: FireDamage = val; break; - case ResistanceType.Cold: ColdDamage = val; break; - case ResistanceType.Poison: PoisonDamage = val; break; - case ResistanceType.Energy: EnergyDamage = val; break; - } - } - - public void SetResistance( ResistanceType type, int min, int max ) - { - SetResistance( type, Utility.RandomMinMax( min, max ) ); - } - - public void SetResistance( ResistanceType type, int val ) - { - switch ( type ) - { - case ResistanceType.Physical: m_PhysicalResistance = val; break; - case ResistanceType.Fire: m_FireResistance = val; break; - case ResistanceType.Cold: m_ColdResistance = val; break; - case ResistanceType.Poison: m_PoisonResistance = val; break; - case ResistanceType.Energy: m_EnergyResistance = val; break; - } - - UpdateResistances(); - } - - public void SetSkill( SkillName name, double val ) - { - Skills[name].BaseFixedPoint = (int)(val * 10); - - if ( Skills[name].Base > Skills[name].Cap ) - { - if ( Core.SE ) - SkillsCap += ( Skills[name].BaseFixedPoint - Skills[name].CapFixedPoint ); - - Skills[name].Cap = Skills[name].Base; - } - } - - public void SetSkill( SkillName name, double min, double max ) - { - int minFixed = (int)(min * 10); - int maxFixed = (int)(max * 10); - - Skills[name].BaseFixedPoint = Utility.RandomMinMax( minFixed, maxFixed ); - - if ( Skills[name].Base > Skills[name].Cap ) - { - if ( Core.SE ) - SkillsCap += ( Skills[name].BaseFixedPoint - Skills[name].CapFixedPoint ); - - Skills[name].Cap = Skills[name].Base; - } - } - - public void SetFameLevel( int level ) - { - switch ( level ) - { - case 1: Fame = Utility.RandomMinMax( 0, 1249 ); break; - case 2: Fame = Utility.RandomMinMax( 1250, 2499 ); break; - case 3: Fame = Utility.RandomMinMax( 2500, 4999 ); break; - case 4: Fame = Utility.RandomMinMax( 5000, 9999 ); break; - case 5: Fame = Utility.RandomMinMax( 10000, 10000 ); break; - } - } - - public void SetKarmaLevel( int level ) - { - switch ( level ) - { - case 0: Karma = -Utility.RandomMinMax( 0, 624 ); break; - case 1: Karma = -Utility.RandomMinMax( 625, 1249 ); break; - case 2: Karma = -Utility.RandomMinMax( 1250, 2499 ); break; - case 3: Karma = -Utility.RandomMinMax( 2500, 4999 ); break; - case 4: Karma = -Utility.RandomMinMax( 5000, 9999 ); break; - case 5: Karma = -Utility.RandomMinMax( 10000, 10000 ); break; - } - } - - #endregion - - public static void Cap( ref int val, int min, int max ) - { - if ( val < min ) - val = min; - else if ( val > max ) - val = max; - } - - #region Pack & Loot - - #region Mondain's Legacy - public void PackArcaneScroll( int min, int max ) - { - PackArcaneScroll( Utility.RandomMinMax( min, max ) ); - } - - public void PackArcaneScroll( int amount ) - { - for ( int i = 0; i < amount; ++i ) - PackArcaneScroll(); - } - - public void PackArcaneScroll() - { - if ( !Core.ML ) - return; - - PackItem( Loot.Construct( Loot.ArcanistScrollTypes ) ); - } - #endregion - - public void PackPotion() - { - PackItem( Loot.RandomPotion() ); - } - - public void PackArcanceScroll( double chance ) - { - if ( !Core.ML || chance <= Utility.RandomDouble() ) - return; - - PackItem( Loot.Construct( Loot.ArcanistScrollTypes ) ); - } - - public void PackNecroScroll( int index ) - { - if ( !Core.AOS || 0.05 <= Utility.RandomDouble() ) - return; - - PackItem( Loot.Construct( Loot.NecromancyScrollTypes, index ) ); - } - - public void PackScroll( int minCircle, int maxCircle ) - { - PackScroll( Utility.RandomMinMax( minCircle, maxCircle ) ); - } - - public void PackScroll( int circle ) - { - int min = (circle - 1) * 8; - - PackItem( Loot.RandomScroll( min, min + 7, SpellbookType.Regular ) ); - } - - public void PackMagicItems( int minLevel, int maxLevel ) - { - PackMagicItems( minLevel, maxLevel, 0.30, 0.15 ); - } - - public void PackMagicItems( int minLevel, int maxLevel, double armorChance, double weaponChance ) - { - if ( !PackArmor( minLevel, maxLevel, armorChance ) ) - PackWeapon( minLevel, maxLevel, weaponChance ); - } - - public virtual void DropBackpack() - { - if ( Backpack?.Items.Count > 0 ) - { - Backpack b = new CreatureBackpack( Name ); - - List list = new List( Backpack.Items ); - foreach ( Item item in list ) - { - b.DropItem( item ); - } - - BaseHouse house = BaseHouse.FindHouseAt( this ); - if ( house != null ) - b.MoveToWorld( house.BanLocation, house.Map ); - else - b.MoveToWorld( Location, Map ); - } - } - - protected bool m_Spawning; - protected int m_KillersLuck; - - public virtual void GenerateLoot( bool spawning ) - { - m_Spawning = spawning; - - if ( !spawning ) - m_KillersLuck = LootPack.GetLuckChanceForKiller( this ); - - GenerateLoot(); - - if ( m_Paragon ) - { - if ( Fame < 1250 ) - AddLoot( LootPack.Meager ); - else if ( Fame < 2500 ) - AddLoot( LootPack.Average ); - else if ( Fame < 5000 ) - AddLoot( LootPack.Rich ); - else if ( Fame < 10000 ) - AddLoot( LootPack.FilthyRich ); - else - AddLoot( LootPack.UltraRich ); - } - - m_Spawning = false; - m_KillersLuck = 0; - } - - public virtual void GenerateLoot() - { - } - - public virtual void AddLoot( LootPack pack, int amount ) - { - for ( int i = 0; i < amount; ++i ) - AddLoot( pack ); - } - - public virtual void AddLoot( LootPack pack ) - { - if ( Summoned ) - return; - - Container backpack = Backpack ?? new Backpack{ Movable = false }; - AddItem( backpack ); - - pack.Generate( this, backpack, m_Spawning, m_KillersLuck ); - } - - public bool PackArmor( int minLevel, int maxLevel ) - { - return PackArmor( minLevel, maxLevel, 1.0 ); - } - - public bool PackArmor( int minLevel, int maxLevel, double chance ) - { - if ( chance <= Utility.RandomDouble() ) - return false; - - Cap( ref minLevel, 0, 5 ); - Cap( ref maxLevel, 0, 5 ); - - if ( Core.AOS ) - { - Item item = Loot.RandomArmorOrShieldOrJewelry(); - - if ( item == null ) - return false; - - GetRandomAOSStats( minLevel, maxLevel, out int attributeCount, out int min, out int max ); - - if ( item is BaseArmor armor ) - BaseRunicTool.ApplyAttributesTo( armor, attributeCount, min, max ); - else if ( item is BaseJewel jewel ) - BaseRunicTool.ApplyAttributesTo( jewel, attributeCount, min, max ); - - PackItem( item ); - } - else - { - BaseArmor armor = Loot.RandomArmorOrShield(); - - if ( armor == null ) - return false; - - armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled( minLevel, maxLevel ); - armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled( minLevel, maxLevel ); - - PackItem( armor ); - } - - return true; - } - - public static void GetRandomAOSStats( int minLevel, int maxLevel, out int attributeCount, out int min, out int max ) - { - int v = RandomMinMaxScaled( minLevel, maxLevel ); - - if ( v >= 5 ) - { - attributeCount = Utility.RandomMinMax( 2, 6 ); - min = 20; max = 70; - } - else if ( v == 4 ) - { - attributeCount = Utility.RandomMinMax( 2, 4 ); - min = 20; max = 50; - } - else if ( v == 3 ) - { - attributeCount = Utility.RandomMinMax( 2, 3 ); - min = 20; max = 40; - } - else if ( v == 2 ) - { - attributeCount = Utility.RandomMinMax( 1, 2 ); - min = 10; max = 30; - } - else - { - attributeCount = 1; - min = 10; max = 20; - } - } - - public static int RandomMinMaxScaled( int min, int max ) - { - if ( min == max ) - return min; - - if ( min > max ) - { - int hold = min; - min = max; - max = hold; - } - - /* Example: - * min: 1 - * max: 5 - * count: 5 - * - * total = (5*5) + (4*4) + (3*3) + (2*2) + (1*1) = 25 + 16 + 9 + 4 + 1 = 55 - * - * chance for min+0 : 25/55 : 45.45% - * chance for min+1 : 16/55 : 29.09% - * chance for min+2 : 9/55 : 16.36% - * chance for min+3 : 4/55 : 7.27% - * chance for min+4 : 1/55 : 1.81% - */ - - int count = max - min + 1; - int total = 0, toAdd = count; - - for ( int i = 0; i < count; ++i, --toAdd ) - total += toAdd*toAdd; - - int rand = Utility.Random( total ); - toAdd = count; - - int val = min; - - for ( int i = 0; i < count; ++i, --toAdd, ++val ) - { - rand -= toAdd*toAdd; - - if ( rand < 0 ) - break; - } - - return val; - } - - public bool PackSlayer() - { - return PackSlayer( 0.05 ); - } - - public bool PackSlayer( double chance ) - { - if ( chance <= Utility.RandomDouble() ) - return false; - - if ( Utility.RandomBool() ) - { - BaseInstrument instrument = Loot.RandomInstrument(); - - if ( instrument != null ) - { - instrument.Slayer = SlayerGroup.GetLootSlayerType( GetType() ); - PackItem( instrument ); - } - } - else if ( !Core.AOS ) - { - BaseWeapon weapon = Loot.RandomWeapon(); - - if ( weapon != null ) - { - weapon.Slayer = SlayerGroup.GetLootSlayerType( GetType() ); - PackItem( weapon ); - } - } - - return true; - } - - public bool PackWeapon( int minLevel, int maxLevel ) - { - return PackWeapon( minLevel, maxLevel, 1.0 ); - } - - public bool PackWeapon( int minLevel, int maxLevel, double chance ) - { - if ( chance <= Utility.RandomDouble() ) - return false; - - Cap( ref minLevel, 0, 5 ); - Cap( ref maxLevel, 0, 5 ); - - if ( Core.AOS ) - { - Item item = Loot.RandomWeaponOrJewelry(); - - if ( item == null ) - return false; - - GetRandomAOSStats( minLevel, maxLevel, out int attributeCount, out int min, out int max ); - - if ( item is BaseWeapon weapon ) - BaseRunicTool.ApplyAttributesTo( weapon, attributeCount, min, max ); - else if ( item is BaseJewel jewel ) - BaseRunicTool.ApplyAttributesTo( jewel, attributeCount, min, max ); - - PackItem( item ); - } - else - { - BaseWeapon weapon = Loot.RandomWeapon(); - - if ( weapon == null ) - return false; - - if ( 0.05 > Utility.RandomDouble() ) - weapon.Slayer = SlayerName.Silver; - - weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled( minLevel, maxLevel ); - weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled( minLevel, maxLevel ); - weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled( minLevel, maxLevel ); - - PackItem( weapon ); - } - - return true; - } - - public void PackGold( int amount ) - { - if ( amount > 0 ) - PackItem( new Gold( amount ) ); - } - - public void PackGold( int min, int max ) - { - PackGold( Utility.RandomMinMax( min, max ) ); - } - - public void PackStatue( int min, int max ) - { - PackStatue( Utility.RandomMinMax( min, max ) ); - } - - public void PackStatue( int amount ) - { - for ( int i = 0; i < amount; ++i ) - PackStatue(); - } - - public void PackStatue() - { - PackItem( Loot.RandomStatue() ); - } - - public void PackGem() - { - PackGem( 1 ); - } - - public void PackGem( int min, int max ) - { - PackGem( Utility.RandomMinMax( min, max ) ); - } - - public void PackGem( int amount ) - { - if ( amount <= 0 ) - return; - - Item gem = Loot.RandomGem(); - - gem.Amount = amount; - - PackItem( gem ); - } - - public void PackNecroReg( int min, int max ) - { - PackNecroReg( Utility.RandomMinMax( min, max ) ); - } - - public void PackNecroReg( int amount ) - { - for ( int i = 0; i < amount; ++i ) - PackNecroReg(); - } + Shout(pm); + m_MLNextShout = DateTime.UtcNow + ShoutDelay; + } - public void PackNecroReg() - { - if ( !Core.AOS ) - return; - - PackItem( Loot.RandomNecromancyReagent() ); - } + public virtual void Shout(PlayerMobile pm) + { + } - public void PackReg( int min, int max ) - { - PackReg( Utility.RandomMinMax( min, max ) ); - } - - public void PackReg( int amount ) - { - if ( amount <= 0 ) - return; - - Item reg = Loot.RandomReagent(); - - reg.Amount = amount; - - PackItem( reg ); - } - - public void PackItem( Item item ) - { - if ( Summoned || item == null ) - { - item?.Delete(); - return; - } - - Container pack = Backpack ?? new Backpack{ Movable = false }; - AddItem( pack ); - - if ( !item.Stackable || !pack.TryDropItem( this, item, false ) ) // try stack - pack.DropItem( item ); // failed, drop it anyway - } - - #endregion - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster && !Body.IsHuman ) - { - Container pack = Backpack; - - pack?.DisplayTo( from ); - } - - if ( DeathAdderCharmable && from.CanBeHarmful( this, false ) ) - { - if ( SummonFamiliarSpell.Table[from] is DeathAdder da && !da.Deleted ) - { - from.SendAsciiMessage( "You charm the snake. Select a target to attack." ); - from.Target = new DeathAdderCharmTarget( this ); - } - } - - if ( MLQuestSystem.Enabled && CanGiveMLQuest && from is PlayerMobile mobile ) - MLQuestSystem.OnDoubleClick( this, mobile ); - - base.OnDoubleClick( from ); - } - - private class DeathAdderCharmTarget : Target - { - private BaseCreature m_Charmed; - - public DeathAdderCharmTarget( BaseCreature charmed ) : base( -1, false, TargetFlags.Harmful ) - { - m_Charmed = charmed; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !m_Charmed.DeathAdderCharmable || m_Charmed.Combatant != null || !from.CanBeHarmful( m_Charmed, false ) ) - return; - - if ( !(SummonFamiliarSpell.Table[from] is DeathAdder da) || da.Deleted ) - return; - - if ( !(targeted is Mobile targ) || !from.CanBeHarmful( targ, false ) ) - return; - - from.RevealingAction(); - from.DoHarmful( targ, true ); - - m_Charmed.Combatant = targ; - - if ( m_Charmed.AIObject != null ) - m_Charmed.AIObject.Action = ActionType.Combat; - } - } - - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - - if ( MLQuestSystem.Enabled && CanGiveMLQuest ) - list.Add( 1072269 ); // Quest Giver - - if ( Core.ML ) - { - if ( DisplayWeight ) - list.Add( TotalWeight == 1 ? 1072788 : 1072789, TotalWeight.ToString() ); // Weight: ~1_WEIGHT~ stones - - if ( m_ControlOrder == OrderType.Guard ) - list.Add( 1080078 ); // guarding - } - - if ( Summoned && !IsAnimatedDead && !IsNecroFamiliar && !( this is Clone ) ) - list.Add( 1049646 ); // (summoned) - else if ( Controlled && Commandable ) - { - if ( IsBonded ) //Intentional difference (showing ONLY bonded when bonded instead of bonded & tame) - list.Add( 1049608 ); // (bonded) - else - list.Add( 502006 ); // (tame) - } - } - - public override void OnSingleClick( Mobile from ) - { - if ( Controlled && Commandable ) - { - int number; - - if ( Summoned ) - number = 1049646; // (summoned) - else if ( IsBonded ) - number = 1049608; // (bonded) - else - number = 502006; // (tame) - - PrivateOverheadMessage( MessageType.Regular, 0x3B2, number, from.NetState ); - } - - base.OnSingleClick( from ); - } - - public virtual double TreasureMapChance => TreasureMap.LootChance; - public virtual int TreasureMapLevel => -1; - - public virtual bool IgnoreYoungProtection => false; - - public override bool OnBeforeDeath() - { - int treasureLevel = TreasureMapLevel; - - if ( treasureLevel == 1 && Map == Map.Trammel && TreasureMap.IsInHavenIsland( this ) ) - { - Mobile killer = LastKiller; - - if ( killer is BaseCreature bc ) - killer = bc.GetMaster(); - - if ( killer is PlayerMobile mobile && mobile.Young ) - treasureLevel = 0; - } - - if ( !Summoned && !NoKillAwards && !IsBonded ) - { - if ( treasureLevel >= 0 ) - { - if ( m_Paragon && Paragon.ChestChance > Utility.RandomDouble() ) - PackItem( new ParagonChest( Name, treasureLevel ) ); - else if ( (Map == Map.Felucca || Map == Map.Trammel) && TreasureMap.LootChance >= Utility.RandomDouble() ) - PackItem( new TreasureMap( treasureLevel, Map ) ); - } - - if ( m_Paragon && Paragon.ChocolateIngredientChance > Utility.RandomDouble() ) - { - switch ( Utility.Random( 4 ) ) - { - case 0: PackItem( new CocoaButter() ); break; - case 1: PackItem( new CocoaLiquor() ); break; - case 2: PackItem( new SackOfSugar() ); break; - case 3: PackItem( new Vanilla() ); break; - } - } - } - - if ( !Summoned && !NoKillAwards && !m_HasGeneratedLoot ) - { - m_HasGeneratedLoot = true; - GenerateLoot( false ); - } - - if ( !NoKillAwards && Region.IsPartOf( "Doom" ) ) - { - int bones = Engines.Quests.Doom.TheSummoningQuest.GetDaemonBonesFor( this ); - - if ( bones > 0 ) - PackItem( new DaemonBone( bones ) ); - } - - if ( IsAnimatedDead ) - Effects.SendLocationEffect( Location, Map, 0x3728, 13, 1, 0x461, 4 ); - - InhumanSpeech speechType = SpeechType; - - speechType?.OnDeath( this ); - - ReceivedHonorContext?.OnTargetKilled(); - - return base.OnBeforeDeath(); - } - - public bool NoKillAwards { get; set; } - - public int ComputeBonusDamage( List list, Mobile m ) - { - int bonus = 0; - - for ( int i = list.Count - 1; i >= 0; --i ) - { - DamageEntry de = list[i]; + #endregion - if ( de.Damager == m || !(de.Damager is BaseCreature bc) ) - continue; + #region Bonding - if ( bc.GetMaster() == m ) - bonus += de.DamageGiven; - } + public const bool BondingEnabled = true; - return bonus; - } + public virtual bool IsBondable => BondingEnabled && !Summoned; + public virtual TimeSpan BondingDelay => TimeSpan.FromDays(7.0); + public virtual TimeSpan BondingAbandonDelay => TimeSpan.FromDays(1.0); - public Mobile GetMaster() - { - if ( Controlled && ControlMaster != null ) - return ControlMaster; - if ( Summoned && SummonMaster != null ) - return SummonMaster; + public override bool CanRegenHits => !IsDeadPet && base.CanRegenHits; + public override bool CanRegenStam => !IsParagon && !IsDeadPet && base.CanRegenStam; + public override bool CanRegenMana => !IsDeadPet && base.CanRegenMana; - return null; - } + public override bool IsDeadBondedPet => IsDeadPet; - public static List GetLootingRights( List damageEntries, int hitsMax ) - { - List rights = new List(); + private bool m_IsBonded; - for ( int i = damageEntries.Count - 1; i >= 0; --i ) - { - if ( i >= damageEntries.Count ) - continue; + [CommandProperty(AccessLevel.GameMaster)] + public Spawner MySpawner + { + get => Spawner as Spawner; + set { } + } - DamageEntry de = damageEntries[i]; + [CommandProperty(AccessLevel.GameMaster)] + public Mobile LastOwner + { + get + { + if (Owners == null || Owners.Count == 0) + return null; + + return Owners[Owners.Count - 1]; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsBonded + { + get => m_IsBonded; + set + { + m_IsBonded = value; + InvalidateProperties(); + } + } + + public bool IsDeadPet{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime BondingBegin{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime OwnerAbandonTime{ get; set; } + + #endregion + + #region Delete Previously Tamed Timer + + private DeleteTimer m_DeleteTimer; + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan DeleteTimeLeft + { + get + { + if (m_DeleteTimer != null && m_DeleteTimer.Running) + return m_DeleteTimer.Next - DateTime.UtcNow; + + return TimeSpan.Zero; + } + } + + private class DeleteTimer : Timer + { + private Mobile m; + + public DeleteTimer(Mobile creature, TimeSpan delay) : base(delay) + { + m = creature; + Priority = TimerPriority.OneMinute; + } + + protected override void OnTick() + { + m.Delete(); + } + } + + public void BeginDeleteTimer() + { + if (!(this is BaseEscortable) && !Summoned && !Deleted && !IsStabled) + { + StopDeleteTimer(); + m_DeleteTimer = new DeleteTimer(this, TimeSpan.FromDays(3.0)); + m_DeleteTimer.Start(); + } + } + + public void StopDeleteTimer() + { + if (m_DeleteTimer != null) + { + m_DeleteTimer.Stop(); + m_DeleteTimer = null; + } + } + + #endregion + + #region Elemental Resistance/Damage + + public override int BasePhysicalResistance => m_PhysicalResistance; + public override int BaseFireResistance => m_FireResistance; + public override int BaseColdResistance => m_ColdResistance; + public override int BasePoisonResistance => m_PoisonResistance; + public override int BaseEnergyResistance => m_EnergyResistance; + + [CommandProperty(AccessLevel.GameMaster)] + public int PhysicalResistanceSeed + { + get => m_PhysicalResistance; + set + { + m_PhysicalResistance = value; + UpdateResistances(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int FireResistSeed + { + get => m_FireResistance; + set + { + m_FireResistance = value; + UpdateResistances(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ColdResistSeed + { + get => m_ColdResistance; + set + { + m_ColdResistance = value; + UpdateResistances(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonResistSeed + { + get => m_PoisonResistance; + set + { + m_PoisonResistance = value; + UpdateResistances(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int EnergyResistSeed + { + get => m_EnergyResistance; + set + { + m_EnergyResistance = value; + UpdateResistances(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int PhysicalDamage{ get; set; } = 100; + + [CommandProperty(AccessLevel.GameMaster)] + public int FireDamage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ColdDamage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int PoisonDamage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int EnergyDamage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ChaosDamage{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int DirectDamage{ get; set; } + + #endregion + + #region Breath ability, like dragon fire breath + + private long m_NextBreathTime; + + // Must be overridden in subclass to enable + public virtual bool HasBreath => false; + + // Base damage given is: CurrentHitPoints * BreathDamageScalar + public virtual double BreathDamageScalar => Core.AOS ? 0.16 : 0.05; + + // Min/max seconds until next breath + public virtual double BreathMinDelay => 30.0; + public virtual double BreathMaxDelay => 45.0; + + // Creature stops moving for 1.0 seconds while breathing + public virtual double BreathStallTime => 1.0; + + // Effect is sent 1.3 seconds after BreathAngerSound and BreathAngerAnimation is played + public virtual double BreathEffectDelay => 1.3; + + // Damage is given 1.0 seconds after effect is sent + public virtual double BreathDamageDelay => 1.0; + + public virtual int BreathRange => RangePerception; + + // Damage types + public virtual int BreathChaosDamage => 0; + public virtual int BreathPhysicalDamage => 0; + public virtual int BreathFireDamage => 100; + public virtual int BreathColdDamage => 0; + public virtual int BreathPoisonDamage => 0; + public virtual int BreathEnergyDamage => 0; + + // Is immune to breath damages + public virtual bool BreathImmune => false; + + // Effect details and sound + public virtual int BreathEffectItemID => 0x36D4; + public virtual int BreathEffectSpeed => 5; + public virtual int BreathEffectDuration => 0; + public virtual bool BreathEffectExplodes => false; + public virtual bool BreathEffectFixedDir => false; + public virtual int BreathEffectHue => 0; + public virtual int BreathEffectRenderMode => 0; + + public virtual int BreathEffectSound => 0x227; + + // Anger sound/animations + public virtual int BreathAngerSound => GetAngerSound(); + public virtual int BreathAngerAnimation => 12; + + public virtual void BreathStart(Mobile target) + { + BreathStallMovement(); + BreathPlayAngerSound(); + BreathPlayAngerAnimation(); + + Direction = GetDirectionTo(target); + + Timer.DelayCall(TimeSpan.FromSeconds(BreathEffectDelay), new TimerStateCallback(BreathEffect_Callback), target); + } + + public virtual void BreathStallMovement() + { + if (AIObject != null) + AIObject.NextMove = Core.TickCount + (int)(BreathStallTime * 1000); + } + + public virtual void BreathPlayAngerSound() + { + PlaySound(BreathAngerSound); + } + + public virtual void BreathPlayAngerAnimation() + { + Animate(BreathAngerAnimation, 5, 1, true, false, 0); + } + + public virtual void BreathEffect_Callback(object state) + { + Mobile target = (Mobile)state; + + if (!target.Alive || !CanBeHarmful(target)) + return; + + BreathPlayEffectSound(); + BreathPlayEffect(target); + + Timer.DelayCall(TimeSpan.FromSeconds(BreathDamageDelay), new TimerStateCallback(BreathDamage_Callback), target); + } + + public virtual void BreathPlayEffectSound() + { + PlaySound(BreathEffectSound); + } + + public virtual void BreathPlayEffect(Mobile target) + { + Effects.SendMovingEffect(this, target, BreathEffectItemID, + BreathEffectSpeed, BreathEffectDuration, BreathEffectFixedDir, + BreathEffectExplodes, BreathEffectHue, BreathEffectRenderMode); + } + + public virtual void BreathDamage_Callback(object state) + { + if (state is BaseCreature creature && creature.BreathImmune) + return; + + Mobile target = (Mobile)state; + + if (CanBeHarmful(target)) + { + DoHarmful(target); + BreathDealDamage(target); + } + } + + public virtual void BreathDealDamage(Mobile target) + { + if (!Evasion.CheckSpellEvasion(target)) + { + int physDamage = BreathPhysicalDamage; + int fireDamage = BreathFireDamage; + int coldDamage = BreathColdDamage; + int poisDamage = BreathPoisonDamage; + int nrgyDamage = BreathEnergyDamage; + + if (BreathChaosDamage > 0) + switch (Utility.Random(5)) + { + case 0: + physDamage += BreathChaosDamage; + break; + case 1: + fireDamage += BreathChaosDamage; + break; + case 2: + coldDamage += BreathChaosDamage; + break; + case 3: + poisDamage += BreathChaosDamage; + break; + case 4: + nrgyDamage += BreathChaosDamage; + break; + } + + if (physDamage == 0 && fireDamage == 0 && coldDamage == 0 && poisDamage == 0 && nrgyDamage == 0) + target.Damage(BreathComputeDamage(), this); // Unresistable damage even in AOS + else + AOS.Damage(target, this, BreathComputeDamage(), physDamage, fireDamage, coldDamage, poisDamage, + nrgyDamage); + } + } + + public virtual int BreathComputeDamage() + { + int damage = (int)(Hits * BreathDamageScalar); + + if (IsParagon) + damage = (int)(damage / Paragon.HitsBuff); + + if (damage > 200) + damage = 200; + + return damage; + } + + #endregion + + #region Spill Acid + + public void SpillAcid(int Amount) + { + SpillAcid(null, Amount); + } + + public void SpillAcid(Mobile target, int Amount) + { + if (target != null && target.Map == null || Map == null) + return; + + for (int i = 0; i < Amount; ++i) + { + Point3D loc = Location; + Map map = Map; + Item acid = NewHarmfulItem(); + + if (target?.Map != null && Amount == 1) + { + loc = target.Location; + map = target.Map; + } + else + { + bool validLocation = false; + for (int j = 0; !validLocation && j < 10; ++j) + { + loc = new Point3D( + loc.X + (Utility.Random(0, 3) - 2), + loc.Y + (Utility.Random(0, 3) - 2), + loc.Z); + loc.Z = map.GetAverageZ(loc.X, loc.Y); + validLocation = map.CanFit(loc, 16, false, false); + } + } + + acid.MoveToWorld(loc, map); + } + } + + /* + Solen Style, override me for other mobiles/items: + kappa+acidslime, grizzles+whatever, etc. + */ + + public virtual Item NewHarmfulItem() + { + return new PoolOfAcid(TimeSpan.FromSeconds(10), 30, 30); + } + + #endregion + + #region Flee!!! + + public virtual bool CanFlee => !m_Paragon; + + public DateTime EndFleeTime{ get; set; } + + public virtual void StopFlee() + { + EndFleeTime = DateTime.MinValue; + } + + public virtual bool CheckFlee() + { + if (EndFleeTime == DateTime.MinValue) + return false; - if ( de.HasExpired ) - { - damageEntries.RemoveAt( i ); - continue; - } - - int damage = de.DamageGiven; - - List respList = de.Responsible; - - if ( respList != null ) - { - for ( int j = 0; j < respList.Count; ++j ) - { - DamageEntry subEntry = respList[j]; - Mobile master = subEntry.Damager; - - if ( master == null || master.Deleted || !master.Player ) - continue; - - bool needNewSubEntry = true; - - for ( int k = 0; needNewSubEntry && k < rights.Count; ++k ) - { - DamageStore ds = rights[k]; - - if ( ds.m_Mobile == master ) - { - ds.m_Damage += subEntry.DamageGiven; - needNewSubEntry = false; - } - } + if (DateTime.UtcNow >= EndFleeTime) + { + StopFlee(); + return false; + } - if ( needNewSubEntry ) - rights.Add( new DamageStore( master, subEntry.DamageGiven ) ); + return true; + } - damage -= subEntry.DamageGiven; - } - } + public virtual void BeginFlee(TimeSpan maxDuration) + { + EndFleeTime = DateTime.UtcNow + maxDuration; + } - Mobile m = de.Damager; + #endregion - if ( m == null || m.Deleted || !m.Player ) - continue; + #region Friends - if ( damage <= 0 ) - continue; + public List Friends{ get; private set; } - bool needNewEntry = true; + public virtual bool AllowNewPetFriend => Friends == null || Friends.Count < 5; - for ( int j = 0; needNewEntry && j < rights.Count; ++j ) - { - DamageStore ds = rights[j]; + public virtual bool IsPetFriend(Mobile m) + { + return Friends != null && Friends.Contains(m); + } - if ( ds.m_Mobile == m ) - { - ds.m_Damage += damage; - needNewEntry = false; - } - } + public virtual void AddPetFriend(Mobile m) + { + if (Friends == null) + Friends = new List(); - if ( needNewEntry ) - rights.Add( new DamageStore( m, damage ) ); - } + Friends.Add(m); + } - if ( rights.Count > 0 ) - { - rights[0].m_Damage = (int)(rights[0].m_Damage * 1.25); //This would be the first valid person attacking it. Gets a 25% bonus. Per 1/19/07 Five on Friday + public virtual void RemovePetFriend(Mobile m) + { + Friends?.Remove(m); + } - if ( rights.Count > 1 ) - rights.Sort(); //Sort by damage + public virtual bool IsFriend(Mobile m) + { + OppositionGroup g = OppositionGroup; - int topDamage = rights[0].m_Damage; - int minDamage; - - if ( hitsMax >= 3000 ) - minDamage = topDamage / 16; - else if ( hitsMax >= 1000 ) - minDamage = topDamage / 8; - else if ( hitsMax >= 200 ) - minDamage = topDamage / 4; - else - minDamage = topDamage / 2; - - for ( int i = 0; i < rights.Count; ++i ) - { - DamageStore ds = rights[i]; - - ds.m_HasRight = ( ds.m_Damage >= minDamage ); - } - } - - return rights; - } - - #region Mondain's Legacy - public virtual bool GivesMLMinorArtifact => false; - - #endregion - - public virtual void OnKilledBy( Mobile mob ) - { - #region Mondain's Legacy - if ( GivesMLMinorArtifact ) - { - if ( MondainsLegacy.CheckArtifactChance( mob, this ) ) - MondainsLegacy.GiveArtifactTo( mob ); - } - #endregion - else if ( m_Paragon ) - { - if ( Paragon.CheckArtifactChance( mob, this ) ) - Paragon.GiveArtifactTo( mob ); - } - } - - public override void OnDeath( Container c ) - { - MeerMage.StopEffect( this, false ); - - if ( IsBonded ) - { - int sound = GetDeathSound(); - - if ( sound >= 0 ) - Effects.PlaySound( this, Map, sound ); - - Warmode = false; - - Poison = null; - Combatant = null; - - Hits = 0; - Stam = 0; - Mana = 0; - - IsDeadPet = true; - ControlTarget = ControlMaster; - ControlOrder = OrderType.Follow; - - ProcessDeltaQueue(); - SendIncomingPacket(); - SendIncomingPacket(); - - // TODO: This can be done in Parallel if there are lots of them. - List aggressors = Aggressors; - - for ( int i = 0; i < aggressors.Count; ++i ) - { - AggressorInfo info = aggressors[i]; - - if ( info.Attacker.Combatant == this ) - info.Attacker.Combatant = null; - } - - List aggressed = Aggressed; - - for ( int i = 0; i < aggressed.Count; ++i ) - { - AggressorInfo info = aggressed[i]; - - if ( info.Defender.Combatant == this ) - info.Defender.Combatant = null; - } - - Mobile owner = ControlMaster; - - if ( owner == null || owner.Deleted || owner.Map != Map || !owner.InRange( this, 12 ) || !CanSee( owner ) || !InLOS( owner ) ) - { - if ( OwnerAbandonTime == DateTime.MinValue ) - OwnerAbandonTime = DateTime.UtcNow; - } - else - { - OwnerAbandonTime = DateTime.MinValue; - } - - GiftOfLifeSpell.HandleDeath( this ); - - CheckStatTimers(); - } - else - { - if ( !Summoned && !NoKillAwards ) - { - int totalFame = Fame / 100; - int totalKarma = -Karma / 100; - - if (Map == Map.Felucca) - { - totalFame += ((totalFame/10)*3); - totalKarma += ((totalKarma/10)*3); - } - - List list = GetLootingRights( DamageEntries, HitsMax ); - List titles = new List(); - List fame = new List(); - List karma = new List(); - - bool givenQuestKill = false; - bool givenFactionKill = false; - bool givenToTKill = false; - - for ( int i = 0; i < list.Count; ++i ) - { - DamageStore ds = list[i]; - - if ( !ds.m_HasRight ) - continue; - - Party party = Engines.PartySystem.Party.Get( ds.m_Mobile ); - - if ( party != null ) - { - int divedFame = totalFame / party.Members.Count; - int divedKarma = totalKarma / party.Members.Count; - - for ( int j = 0; j < party.Members.Count; ++j ) - { - PartyMemberInfo info = party.Members[ j ] as PartyMemberInfo; - - if ( info?.Mobile != null ) - { - int index = titles.IndexOf( info.Mobile ); - - if ( index == -1 ) - { - titles.Add( info.Mobile ); - fame.Add( divedFame ); - karma.Add( divedKarma ); - } - else - { - fame[ index ] += divedFame; - karma[ index ] += divedKarma; - } - } - } - } - else - { - titles.Add( ds.m_Mobile ); - fame.Add( totalFame ); - karma.Add( totalKarma ); - } - - OnKilledBy( ds.m_Mobile ); - - if ( !givenFactionKill ) - { - givenFactionKill = true; - Faction.HandleDeath( this, ds.m_Mobile ); - } - - Region region = ds.m_Mobile.Region; - - if ( !givenToTKill && ( Map == Map.Tokuno || region.IsPartOf( "Yomotsu Mines" ) || region.IsPartOf( "Fan Dancer's Dojo" ) )) - { - givenToTKill = true; - TreasuresOfTokuno.HandleKill( this, ds.m_Mobile ); - } - - if ( ds.m_Mobile is PlayerMobile pm ) - { - if ( MLQuestSystem.Enabled ) - { - MLQuestSystem.HandleKill( pm, this ); - - // Kills are given to *everyone* with looting right in the ML quest system - //givenQuestKill = true; - } - - if ( givenQuestKill ) - continue; - - QuestSystem qs = pm.Quest; - - if ( qs != null ) - { - qs.OnKill( this, c ); - givenQuestKill = true; - } - } - } - - for ( int i = 0; i < titles.Count; ++i ) - { - Titles.AwardFame( titles[ i ], fame[ i ], true ); - Titles.AwardKarma( titles[ i ], karma[ i ], true ); - } - } - - base.OnDeath( c ); - - if ( DeleteCorpseOnDeath ) - c.Delete(); - } - } - - /* To save on cpu usage, RunUO creatures only reacquire creatures under the following circumstances: - * - 10 seconds have elapsed since the last time it tried - * - The creature was attacked - * - Some creatures, like dragons, will reacquire when they see someone move - * - * This functionality appears to be implemented on OSI as well - */ - - public long NextReacquireTime { get; set; } - - public virtual TimeSpan ReacquireDelay => TimeSpan.FromSeconds( 10.0 ); - public virtual bool ReacquireOnMovement => false; - public virtual bool AcquireOnApproach => m_Paragon; - public virtual int AcquireOnApproachRange => 10; - - public override void OnDelete() - { - Mobile m = m_ControlMaster; - - SetControlMaster( null ); - SummonMaster = null; - - ReceivedHonorContext?.Cancel(); - - base.OnDelete(); - - m?.InvalidateProperties(); - } - - public override bool CanBeHarmful( Mobile target, bool message, bool ignoreOurBlessedness ) - { - if ( target is BaseFactionGuard ) - return false; - - if ( ( target is BaseCreature creature && creature.IsInvulnerable ) || target is PlayerVendor || target is TownCrier ) - { - if ( message ) - { - if ( target.Title == null ) - SendMessage( "{0} cannot be harmed.", target.Name ); - else - SendMessage( "{0} {1} cannot be harmed.", target.Name, target.Title ); - } - - return false; - } - - return base.CanBeHarmful( target, message, ignoreOurBlessedness ); - } - - public override bool CanBeRenamedBy( Mobile from ) - { - return Controlled && from == ControlMaster && !from.Region.IsPartOf(typeof(Jail)) || - base.CanBeRenamedBy( from ); - } - - public bool SetControlMaster( Mobile m ) - { - if ( m == null ) - { - ControlMaster = null; - Controlled = false; - ControlTarget = null; - ControlOrder = OrderType.None; - Guild = null; - - Delta( MobileDelta.Noto ); - } - else - { - ISpawner se = Spawner; - if ( se?.UnlinkOnTaming == true ) - { - Spawner.Remove( this ); - Spawner = null; - } - - if ( m.Followers + ControlSlots > m.FollowersMax ) - { - m.SendLocalizedMessage( 1049607 ); // You have too many followers to control that creature. - return false; - } - - CurrentWayPoint = null;//so tamed animals don't try to go back - - Home = Point3D.Zero; - - ControlMaster = m; - Controlled = true; - ControlTarget = null; - ControlOrder = OrderType.Come; - Guild = null; + if (g != null && g.IsEnemy(this, m)) + return false; - if ( m_DeleteTimer != null ) - { - m_DeleteTimer.Stop(); - m_DeleteTimer = null; - } - - Delta( MobileDelta.Noto ); - } - - InvalidateProperties(); - - return true; - } - - public override void OnRegionChange( Region Old, Region New ) - { - base.OnRegionChange( Old, New ); - - if ( Controlled ) - { - if ( Spawner is SpawnEntry se && !se.UnlinkOnTaming && ( New == null || !New.AcceptsSpawnsFrom( se.Region ) ) ) - { - Spawner.Remove( this ); - Spawner = null; - } - } - } - - public static bool Summoning { get; set; } - - public static bool Summon( BaseCreature creature, Mobile caster, Point3D p, int sound, TimeSpan duration ) - { - return Summon( creature, true, caster, p, sound, duration ); - } - - public static bool Summon( BaseCreature creature, bool controlled, Mobile caster, Point3D p, int sound, TimeSpan duration ) - { - if ( caster.Followers + creature.ControlSlots > caster.FollowersMax ) - { - caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - creature.Delete(); - return false; - } - - Summoning = true; - - if ( controlled ) - creature.SetControlMaster( caster ); - - creature.RangeHome = 10; - creature.Summoned = true; - - creature.SummonMaster = caster; - - Container pack = creature.Backpack; - - if ( pack != null ) - { - for ( int i = pack.Items.Count - 1; i >= 0; --i ) - { - if ( i >= pack.Items.Count ) - continue; - - pack.Items[i].Delete(); - } - } - - new UnsummonTimer( caster, creature, duration ).Start(); - creature.SummonEnd = DateTime.UtcNow + duration; - - creature.MoveToWorld( p, caster.Map ); - - Effects.PlaySound( p, creature.Map, sound ); - - Summoning = false; - - return true; - } - - private static bool EnableRummaging = true; - - private const double ChanceToRummage = 0.5; // 50% - - private const double MinutesToNextRummageMin = 1.0; - private const double MinutesToNextRummageMax = 4.0; - - private const double MinutesToNextChanceMin = 0.25; - private const double MinutesToNextChanceMax = 0.75; - - private long m_NextRummageTime; - - public virtual bool CanBreath => HasBreath && !Summoned; - public virtual bool IsDispellable => Summoned && !IsAnimatedDead; - - #region Healing - public virtual bool CanHeal => false; - public virtual bool CanHealOwner => false; - public virtual double HealScalar => 1.0; + if (!(m is BaseCreature c)) + return false; - public virtual int HealSound => 0x57; - public virtual int HealStartRange => 2; - public virtual int HealEndRange => RangePerception; - public virtual double HealTrigger => 0.78; - public virtual double HealDelay => 6.5; - public virtual double HealInterval => 0.0; - public virtual bool HealFully => true; - public virtual double HealOwnerTrigger => 0.78; - public virtual double HealOwnerDelay => 6.5; - public virtual double HealOwnerInterval => 30.0; - public virtual bool HealOwnerFully => false; + return m_Team == c.m_Team && (m_bSummoned || m_Controlled) == (c.m_bSummoned || c.m_Controlled); + } - private long m_NextHealTime = Core.TickCount; - private long m_NextHealOwnerTime = Core.TickCount; - private Timer m_HealTimer; - - public bool IsHealing => ( m_HealTimer != null ); + #endregion - public virtual void HealStart( Mobile patient ) - { - bool onSelf = ( patient == this ); + #region Allegiance - //DoBeneficial( patient ); + public virtual Ethic EthicAllegiance => null; - RevealingAction(); + public enum Allegiance + { + None, + Ally, + Enemy + } - if ( !onSelf ) - { - patient.RevealingAction(); - patient.SendLocalizedMessage( 1008078, false, Name ); // : Attempting to heal you. - } + public virtual Allegiance GetFactionAllegiance(Mobile mob) + { + if (mob == null || mob.Map != Faction.Facet || FactionAllegiance == null) + return Allegiance.None; - double seconds = ( onSelf ? HealDelay : HealOwnerDelay ) + ( patient.Alive ? 0.0 : 5.0 ); + Faction fac = Faction.Find(mob, true); - m_HealTimer = Timer.DelayCall( TimeSpan.FromSeconds( seconds ), new TimerStateCallback( Heal_Callback ), patient ); - } + if (fac == null) + return Allegiance.None; - private void Heal_Callback( object state ) - { - if ( state is Mobile mobile ) - Heal( mobile ); - } + return fac == FactionAllegiance ? Allegiance.Ally : Allegiance.Enemy; + } - public virtual void Heal( Mobile patient ) - { - if ( !Alive || Map == Map.Internal || !CanBeBeneficial( patient, true, true ) || patient.Map != Map || !InRange( patient, HealEndRange ) ) - { - StopHeal(); - return; - } + public virtual Allegiance GetEthicAllegiance(Mobile mob) + { + if (mob == null || mob.Map != Faction.Facet || EthicAllegiance == null) + return Allegiance.None; - bool onSelf = ( patient == this ); + Ethic ethic = Ethic.Find(mob, true); - if ( !patient.Alive ) - { - } - else if ( patient.Poisoned ) - { - int poisonLevel = patient.Poison.Level; - - double healing = Skills.Healing.Value; - double anatomy = Skills.Anatomy.Value; - double chance = ( healing - 30.0 ) / 50.0 - poisonLevel * 0.1; - - if ( ( healing >= 60.0 && anatomy >= 60.0 ) && chance > Utility.RandomDouble() ) - { - if ( patient.CurePoison( this ) ) - { - patient.SendLocalizedMessage( 1010059 ); // You have been cured of all poisons. - - CheckSkill( SkillName.Healing, 0.0, 60.0 + poisonLevel * 10.0 ); // TODO: Verify formula - CheckSkill( SkillName.Anatomy, 0.0, 100.0 ); - } - } - } - else if ( BleedAttack.IsBleeding( patient ) ) - { - patient.SendLocalizedMessage( 1060167 ); // The bleeding wounds have healed, you are no longer bleeding! - BleedAttack.EndBleed( patient, false ); - } - else - { - double healing = Skills.Healing.Value; - double anatomy = Skills.Anatomy.Value; - double chance = ( healing + 10.0 ) / 100.0; - - if ( chance > Utility.RandomDouble() ) - { - double min = ( anatomy / 10.0 ) + ( healing / 6.0 ) + 4.0; - double max = ( anatomy / 8.0 ) + ( healing / 3.0 ) + 4.0; - - if ( onSelf ) - max += 10; - - double toHeal = min + ( Utility.RandomDouble() * ( max - min ) ); - - toHeal *= HealScalar; - - patient.Heal( (int)toHeal ); - - CheckSkill( SkillName.Healing, 0.0, 90.0 ); - CheckSkill( SkillName.Anatomy, 0.0, 100.0 ); - } - } - - HealEffect( patient ); - - StopHeal(); - - if ( ( onSelf && HealFully && Hits >= HealTrigger * HitsMax && Hits < HitsMax ) || ( !onSelf && HealOwnerFully && patient.Hits >= HealOwnerTrigger * patient.HitsMax && patient.Hits < patient.HitsMax ) ) - HealStart( patient ); - } - - public virtual void StopHeal() - { - m_HealTimer?.Stop(); - - m_HealTimer = null; - } - - public virtual void HealEffect( Mobile patient ) - { - patient.PlaySound( HealSound ); - } - #endregion - - #region Damaging Aura - private long m_NextAura; - - public virtual bool HasAura => false; - public virtual TimeSpan AuraInterval => TimeSpan.FromSeconds( 5 ); - public virtual int AuraRange => 4; - - public virtual int AuraBaseDamage => 5; - public virtual int AuraPhysicalDamage => 0; - public virtual int AuraFireDamage => 100; - public virtual int AuraColdDamage => 0; - public virtual int AuraPoisonDamage => 0; - public virtual int AuraEnergyDamage => 0; - public virtual int AuraChaosDamage => 0; - - public virtual void AuraDamage() - { - if ( !Alive || IsDeadBondedPet ) - return; - - List list = new List(); - - foreach ( Mobile m in GetMobilesInRange( AuraRange ) ) - { - if ( m == this || !CanBeHarmful( m, false ) || ( Core.AOS && !InLOS( m ) ) ) - continue; - - if ( m is BaseCreature bc ) - { - if ( bc.Controlled || bc.Summoned || bc.Team != Team ) - list.Add( bc ); - } - else if ( m.Player ) - { - list.Add( m ); - } - } - - foreach ( Mobile m in list ) - { - AOS.Damage( m, this, AuraBaseDamage, AuraPhysicalDamage, AuraFireDamage, AuraColdDamage, AuraPoisonDamage, AuraEnergyDamage, AuraChaosDamage ); - AuraEffect( m ); - } - } - - public virtual void AuraEffect( Mobile m ) - { - } - #endregion - - public virtual void OnThink() - { - long tc = Core.TickCount; - - if ( EnableRummaging && CanRummageCorpses && !Summoned && !Controlled && tc - m_NextRummageTime >= 0 ) - { - double min, max; - - if ( ChanceToRummage > Utility.RandomDouble() && Rummage() ) - { - min = MinutesToNextRummageMin; - max = MinutesToNextRummageMax; - } - else - { - min = MinutesToNextChanceMin; - max = MinutesToNextChanceMax; - } - - double delay = min + (Utility.RandomDouble() * (max - min)); - m_NextRummageTime = tc + (int)TimeSpan.FromMinutes(delay).TotalMilliseconds; - } - - if ( CanBreath && tc - m_NextBreathTime >= 0 ) // tested: controlled dragons do breath fire, what about summoned skeletal dragons? - { - Mobile target = Combatant; - - if ( target != null && target.Alive && !target.IsDeadBondedPet && CanBeHarmful( target ) && target.Map == Map && !IsDeadBondedPet && target.InRange( this, BreathRange ) && InLOS( target ) && !BardPacified ) - { - if ( ( Core.TickCount - m_NextBreathTime ) < 30000 && Utility.RandomBool() ) - { - BreathStart( target ); - } - - m_NextBreathTime = tc + (int)TimeSpan.FromSeconds( BreathMinDelay + ( ( Utility.RandomDouble( ) * ( BreathMaxDelay - BreathMinDelay ) ) ) ).TotalMilliseconds; - } - } - - if ( ( CanHeal || CanHealOwner ) && Alive && !IsHealing && !BardPacified ) - { - Mobile owner = ControlMaster; - - if ( owner != null && CanHealOwner && tc - m_NextHealOwnerTime >= 0 && CanBeBeneficial( owner, true, true ) && owner.Map == Map && InRange( owner, HealStartRange ) && InLOS( owner ) && owner.Hits < HealOwnerTrigger * owner.HitsMax ) - { - HealStart( owner ); - - m_NextHealOwnerTime = tc + (int)TimeSpan.FromSeconds( HealOwnerInterval ).TotalMilliseconds; - } - else if ( CanHeal && tc - m_NextHealTime >= 0 && CanBeBeneficial( this ) && ( Hits < HealTrigger * HitsMax || Poisoned ) ) - { - HealStart( this ); - - m_NextHealTime = tc + (int)TimeSpan.FromSeconds( HealInterval ).TotalMilliseconds; - } - } - - if (ReturnsToHome && IsSpawnerBound() && !InRange(Home, RangeHome) ) - { - if ((Combatant == null) && (Warmode == false) && Utility.RandomDouble() < .10) /* some throttling */ - { - m_FailedReturnHome = !Move(GetDirectionTo(Home.X, Home.Y)) ? m_FailedReturnHome + 1 : 0; - - if (m_FailedReturnHome > 5) - { - SetLocation(Home, true); - - m_FailedReturnHome = 0; - } - } - } - else - { - m_FailedReturnHome = 0; - } - - if ( HasAura && tc - m_NextAura >= 0 ) - { - AuraDamage(); - m_NextAura = tc + (int)AuraInterval.TotalMilliseconds; - } - } - - public virtual bool Rummage() - { - Corpse toRummage = null; - - IPooledEnumerable eable = GetItemsInRange(2); - foreach ( Corpse item in eable ) - { - if ( item.Items.Count > 0 ) - { - toRummage = item; - break; - } - } - eable.Free(); - - if ( toRummage == null ) - return false; - - Container pack = Backpack; - - if ( pack == null ) - return false; - - List items = toRummage.Items; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[Utility.Random( items.Count )]; - - Lift( item, item.Amount, out bool rejected, out LRReason reason ); - - if ( !rejected && Drop( this, new Point3D( -1, -1, 0 ) ) ) - { - // *rummages through a corpse and takes an item* - PublicOverheadMessage( MessageType.Emote, 0x3B2, 1008086 ); - //TODO: Instancing of Rummaged stuff. - return true; - } - } - - return false; - } - - public void Pacify( Mobile master, DateTime endtime ) - { - BardPacified = true; - BardEndTime = endtime; - } - - public override Mobile GetDamageMaster( Mobile damagee ) - { - if ( BardProvoked && damagee == BardTarget ) - return BardMaster; - if ( m_Controlled && m_ControlMaster != null ) - return m_ControlMaster; - if ( m_bSummoned && m_SummonMaster != null ) - return m_SummonMaster; - - return base.GetDamageMaster( damagee ); - } - - public void Provoke( Mobile master, Mobile target, bool bSuccess ) - { - BardProvoked = true; - - if ( !Core.ML ) - { - PublicOverheadMessage( MessageType.Emote, EmoteHue, false, "*looks furious*" ); - } - - if ( bSuccess ) - { - PlaySound( GetIdleSound() ); - - BardMaster = master; - BardTarget = target; - Combatant = target; - BardEndTime = DateTime.UtcNow + TimeSpan.FromSeconds( 30.0 ); - - if ( target is BaseCreature t ) - { - if ( t.Unprovokable || (t.IsParagon && BaseInstrument.GetBaseDifficulty( t ) >= 160.0) ) - return; - - t.BardProvoked = true; - - t.BardMaster = master; - t.BardTarget = this; - t.Combatant = this; - t.BardEndTime = DateTime.UtcNow + TimeSpan.FromSeconds( 30.0 ); - } - } - else - { - PlaySound( GetAngerSound() ); - - BardMaster = master; - BardTarget = target; - } - } - - public bool FindMyName( string str, bool bWithAll ) - { - string name = Name; - - if ( name == null || str.Length < name.Length ) - return false; - - string[] wordsString = str.Split(' '); - string[] wordsName = name.Split(' '); + if (ethic == null) + return Allegiance.None; - for ( int j = 0 ; j < wordsName.Length; j++ ) - { - string wordName = wordsName[j]; + return ethic == EthicAllegiance ? Allegiance.Ally : Allegiance.Enemy; + } - bool bFound = false; - for ( int i = 0 ; i < wordsString.Length; i++ ) - { - string word = wordsString[i]; + #endregion - if ( Insensitive.Equals( word, wordName ) ) - bFound = true; - - if ( bWithAll && Insensitive.Equals( word, "all" ) ) - return true; - } - - if ( !bFound ) - return false; - } - - return true; - } - - public static void TeleportPets( Mobile master, Point3D loc, Map map, bool onlyBonded = false ) - { - List move = new List(); - - foreach ( Mobile m in master.GetMobilesInRange( 3 ) ) - { - if ( m is BaseCreature pet ) - { - if ( pet.Controlled && pet.ControlMaster == master && !onlyBonded || pet.IsBonded ) - { - if ( pet.ControlOrder == OrderType.Guard || pet.ControlOrder == OrderType.Follow || pet.ControlOrder == OrderType.Come ) - move.Add( pet ); - } - } - } - - foreach ( Mobile m in move ) - m.MoveToWorld( loc, map ); - } - - public virtual void ResurrectPet() - { - if ( !IsDeadPet ) - return; - - OnBeforeResurrect(); - - Poison = null; - - Warmode = false; - - Hits = 10; - Stam = StamMax; - Mana = 0; - - ProcessDeltaQueue(); - - IsDeadPet = false; - - Effects.SendPacket( Location, Map, new BondedStatus( 0, Serial, 0 ) ); - - SendIncomingPacket(); - SendIncomingPacket(); - - OnAfterResurrect(); - - Mobile owner = ControlMaster; - - if ( owner == null || owner.Deleted || owner.Map != Map || !owner.InRange( this, 12 ) || !CanSee( owner ) || !InLOS( owner ) ) - { - if ( OwnerAbandonTime == DateTime.MinValue ) - OwnerAbandonTime = DateTime.UtcNow; - } - else - { - OwnerAbandonTime = DateTime.MinValue; - } - - CheckStatTimers(); - } - - public override bool CanBeDamaged() - { - if ( IsDeadPet || IsInvulnerable ) - return false; + #region Alter[...]Damage From/To - return base.CanBeDamaged(); - } + public virtual void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + } - public virtual bool PlayerRangeSensitive //If they are following a waypoint, they'll continue to follow it even if players aren't around - => (CurrentWayPoint == null); - - /* until we are sure about who should be getting deleted, move them instead */ - /* On OSI, they despawn */ - - private bool m_ReturnQueued; - - private bool IsSpawnerBound() - { - return Map != null && Map != Map.Internal && - FightMode != FightMode.None && RangeHome >= 0 && - !Controlled && !Summoned && Spawner is Spawner spawner && spawner.Map == Map; - } - - public virtual bool ReturnsToHome => ( SeeksHome && ( Home != Point3D.Zero ) && !m_ReturnQueued && !Controlled && !Summoned ); - - public override void OnSectorDeactivate() - { - if ( !Deleted && ReturnsToHome && IsSpawnerBound() && !InRange( Home, ( RangeHome + 5 ) ) ) - { - Timer.DelayCall( TimeSpan.FromSeconds( ( Utility.Random( 45 ) + 15 ) ), GoHome_Callback ); - - m_ReturnQueued = true; - } - else if ( PlayerRangeSensitive ) - { - AIObject?.Deactivate(); - } - - base.OnSectorDeactivate(); - } - - public void GoHome_Callback() - { - if ( m_ReturnQueued && IsSpawnerBound() ) - { - if ( !( ( Map.GetSector( X, Y ) ).Active ) ) - { - SetLocation( Home, true ); - - if ( !( ( Map.GetSector( X, Y ) ).Active ) ) - { - AIObject?.Deactivate(); - } - } - } - - m_ReturnQueued = false; - } - - public override void OnSectorActivate() - { - if ( PlayerRangeSensitive ) - { - AIObject?.Activate(); - } - - base.OnSectorActivate(); - } - - // used for deleting untamed creatures [in houses] - - [CommandProperty( AccessLevel.GameMaster )] - public bool RemoveIfUntamed { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RemoveStep { get; set; } - } - - public class LoyaltyTimer : Timer - { - private static TimeSpan InternalDelay = TimeSpan.FromMinutes( 5.0 ); - - public static void Initialize() - { - new LoyaltyTimer().Start(); - } - - public LoyaltyTimer() : base( InternalDelay, InternalDelay ) - { - m_NextHourlyCheck = DateTime.UtcNow + TimeSpan.FromHours( 1.0 ); - Priority = TimerPriority.FiveSeconds; - } - - private DateTime m_NextHourlyCheck; - - protected override void OnTick() - { - if (DateTime.UtcNow >= m_NextHourlyCheck) - m_NextHourlyCheck = DateTime.UtcNow + TimeSpan.FromHours(1.0); - else - return; - - List toRelease = new List(); - - // added array for wild creatures in house regions to be removed - List toRemove = new List(); - - Parallel.ForEach(World.Mobiles.Values, m => - { - if (!(m is BaseCreature c)) - return; - - if (c is BaseMount mount && mount.Rider != null) - { - mount.OwnerAbandonTime = DateTime.MinValue; - return; - } - - if (c.IsDeadPet) - { - Mobile owner = c.ControlMaster; - - if (!c.IsStabled && (owner == null || owner.Deleted || owner.Map != c.Map || - !owner.InRange(c, 12) || !c.CanSee(owner) || !c.InLOS(owner))) - { - if (c.OwnerAbandonTime == DateTime.MinValue) - { - c.OwnerAbandonTime = DateTime.UtcNow; - } - else if ((c.OwnerAbandonTime + c.BondingAbandonDelay) <= DateTime.UtcNow) - { - lock(toRemove) - toRemove.Add(c); - } - } - else - { - c.OwnerAbandonTime = DateTime.MinValue; - } - } - else if (c.Controlled && c.Commandable) - { - c.OwnerAbandonTime = DateTime.MinValue; - - if (c.Map != Map.Internal) - { - c.Loyalty -= (BaseCreature.MaxLoyalty / 10); - - if (c.Loyalty < (BaseCreature.MaxLoyalty / 10)) - { - c.Say(1043270, c.Name); // * ~1_NAME~ looks around desperately * - c.PlaySound(c.GetIdleSound()); - } - - if (c.Loyalty <= 0) - lock(toRelease) - toRelease.Add(c); - } - } - - // added lines to check if a wild creature in a house region has to be removed or not - if (!c.Controlled && !c.IsStabled && ((c.Region.IsPartOf(typeof(HouseRegion)) && c.CanBeDamaged()) || - (c.RemoveIfUntamed && c.Spawner == null))) - { - c.RemoveStep++; - - if (c.RemoveStep >= 20) - lock(toRemove) - toRemove.Add(c); - } - else - { - c.RemoveStep = 0; - } - }); - - // TODO: Parallelize this - foreach (BaseCreature c in toRelease) - { - c.Say(1043255, c.Name); // ~1_NAME~ appears to have decided that is better off without a master! - c.Loyalty = BaseCreature.MaxLoyalty; // Wonderfully Happy - c.IsBonded = false; - c.BondingBegin = DateTime.MinValue; - c.OwnerAbandonTime = DateTime.MinValue; - c.ControlTarget = null; - c.AIObject.DoOrderRelease(); // this will prevent no release of creatures left alone with AI disabled (and consequent bug of Followers) - c.DropBackpack(); - } - - foreach (BaseCreature c in toRemove) - c.Delete(); - } - } -} + public virtual void AlterDamageScalarTo(Mobile target, ref double scalar) + { + } + + public virtual void AlterSpellDamageFrom(Mobile from, ref int damage) + { + } + + public virtual void AlterSpellDamageTo(Mobile to, ref int damage) + { + } + + public virtual void AlterMeleeDamageFrom(Mobile from, ref int damage) + { + } + + public virtual void AlterMeleeDamageTo(Mobile to, ref int damage) + { + } + + #endregion + + #region Food + + private static Type[] m_Eggs = + { + typeof(FriedEggs), typeof(Eggs) + }; + + private static Type[] m_Fish = + { + typeof(FishSteak), typeof(RawFishSteak) + }; + + private static Type[] m_GrainsAndHay = + { + typeof(BreadLoaf), typeof(FrenchBread), typeof(SheafOfHay) + }; + + private static Type[] m_Meat = + { + /* Cooked */ + typeof(Bacon), typeof(CookedBird), typeof(Sausage), + typeof(Ham), typeof(Ribs), typeof(LambLeg), + typeof(ChickenLeg), + + /* Uncooked */ + typeof(RawBird), typeof(RawRibs), typeof(RawLambLeg), + typeof(RawChickenLeg), + + /* Body Parts */ + typeof(Head), typeof(LeftArm), typeof(LeftLeg), + typeof(Torso), typeof(RightArm), typeof(RightLeg) + }; + + private static Type[] m_FruitsAndVegies = + { + typeof(HoneydewMelon), typeof(YellowGourd), typeof(GreenGourd), + typeof(Banana), typeof(Bananas), typeof(Lemon), typeof(Lime), + typeof(Dates), typeof(Grapes), typeof(Peach), typeof(Pear), + typeof(Apple), typeof(Watermelon), typeof(Squash), + typeof(Cantaloupe), typeof(Carrot), typeof(Cabbage), + typeof(Onion), typeof(Lettuce), typeof(Pumpkin) + }; + + private static Type[] m_Gold = + { + // white wyrms eat gold.. + typeof(Gold) + }; + + public virtual bool CheckFoodPreference(Item f) + { + if (CheckFoodPreference(f, FoodType.Eggs, m_Eggs)) + return true; + + if (CheckFoodPreference(f, FoodType.Fish, m_Fish)) + return true; + + if (CheckFoodPreference(f, FoodType.GrainsAndHay, m_GrainsAndHay)) + return true; + + if (CheckFoodPreference(f, FoodType.Meat, m_Meat)) + return true; + + if (CheckFoodPreference(f, FoodType.FruitsAndVegies, m_FruitsAndVegies)) + return true; + + if (CheckFoodPreference(f, FoodType.Gold, m_Gold)) + return true; + + return false; + } + + public virtual bool CheckFoodPreference(Item fed, FoodType type, Type[] types) + { + if ((FavoriteFood & type) == 0) + return false; + + Type fedType = fed.GetType(); + bool contains = false; + + for (int i = 0; !contains && i < types.Length; ++i) + contains = fedType == types[i]; + + return contains; + } + + public virtual bool CheckFeed(Mobile from, Item dropped) + { + if (!IsDeadPet && Controlled && (ControlMaster == from || IsPetFriend(from))) + { + Item f = dropped; + + if (CheckFoodPreference(f)) + { + int amount = f.Amount; + + if (amount > 0) + { + int stamGain; + + if (f is Gold) + stamGain = amount - 50; + else + stamGain = amount * 15 - 50; + + if (stamGain > 0) + Stam += stamGain; + + if (Core.SE) + { + if (m_Loyalty < MaxLoyalty) m_Loyalty = MaxLoyalty; + } + else + { + for (int i = 0; i < amount; ++i) + if (m_Loyalty < MaxLoyalty && 0.5 >= Utility.RandomDouble()) + m_Loyalty += 10; + } + + /* if ( happier )*/ + // looks like in OSI pets say they are happier even if they are at maximum loyalty + SayTo(from, 502060); // Your pet looks happier. + + if (Body.IsAnimal) + Animate(3, 5, 1, true, false, 0); + else if (Body.IsMonster) + Animate(17, 5, 1, true, false, 0); + + if (IsBondable && !IsBonded) + { + Mobile master = m_ControlMaster; + + if (master != null && master == from) //So friends can't start the bonding process + { + if (MinTameSkill <= 29.1 || master.Skills[SkillName.AnimalTaming].Base >= MinTameSkill || + OverrideBondingReqs() || + Core.ML && master.Skills[SkillName.AnimalTaming].Value >= MinTameSkill) + { + if (BondingBegin == DateTime.MinValue) + { + BondingBegin = DateTime.UtcNow; + } + else if (BondingBegin + BondingDelay <= DateTime.UtcNow) + { + IsBonded = true; + BondingBegin = DateTime.MinValue; + from.SendLocalizedMessage(1049666); // Your pet has bonded with you! + } + } + else if (Core.ML) + { + from.SendLocalizedMessage( + 1075268); // Your pet cannot form a bond with you until your animal taming ability has risen. + } + } + } + + dropped.Delete(); + return true; + } + } + } + + return false; + } + + #endregion + + #region OnAction[...] + + public virtual void OnActionWander() + { + } + + public virtual void OnActionCombat() + { + } + + public virtual void OnActionGuard() + { + } + + public virtual void OnActionFlee() + { + } + + public virtual void OnActionInteract() + { + } + + public virtual void OnActionBackoff() + { + } + + #endregion + + #region Corpse Resources + + public virtual int Feathers => 0; + public virtual int Wool => 0; + + public virtual MeatType MeatType => MeatType.Ribs; + public virtual int Meat => 0; + + public virtual int Hides => 0; + public virtual HideType HideType => HideType.Regular; + + public virtual int Scales => 0; + public virtual ScaleType ScaleType => ScaleType.Red; + + #endregion + + #region Teaching + + public virtual bool CanTeach => false; + + public virtual bool CheckTeach(SkillName skill, Mobile from) + { + if (!CanTeach) + return false; + + if (skill == SkillName.Stealth && from.Skills[SkillName.Hiding].Base < Stealth.HidingRequirement) + return false; + + if (skill == SkillName.RemoveTrap && (from.Skills[SkillName.Lockpicking].Base < 50.0 || + from.Skills[SkillName.DetectHidden].Base < 50.0)) + return false; + + if (!Core.AOS && (skill == SkillName.Focus || skill == SkillName.Chivalry || skill == SkillName.Necromancy)) + return false; + + return true; + } + + public enum TeachResult + { + Success, + Failure, + KnowsMoreThanMe, + KnowsWhatIKnow, + SkillNotRaisable, + NotEnoughFreePoints + } + + public virtual TeachResult CheckTeachSkills(SkillName skill, Mobile m, int maxPointsToLearn, ref int pointsToLearn, + bool doTeach) + { + if (!CheckTeach(skill, m) || !m.CheckAlive()) + return TeachResult.Failure; + + Skill ourSkill = Skills[skill]; + Skill theirSkill = m.Skills[skill]; + + if (ourSkill == null || theirSkill == null) + return TeachResult.Failure; + + int baseToSet = ourSkill.BaseFixedPoint / 3; + + if (baseToSet > 420) + baseToSet = 420; + else if (baseToSet < 200) + return TeachResult.Failure; + + if (baseToSet > theirSkill.CapFixedPoint) + baseToSet = theirSkill.CapFixedPoint; + + pointsToLearn = baseToSet - theirSkill.BaseFixedPoint; + + if (maxPointsToLearn > 0 && pointsToLearn > maxPointsToLearn) + { + pointsToLearn = maxPointsToLearn; + baseToSet = theirSkill.BaseFixedPoint + pointsToLearn; + } + + if (pointsToLearn < 0) + return TeachResult.KnowsMoreThanMe; + + if (pointsToLearn == 0) + return TeachResult.KnowsWhatIKnow; + + if (theirSkill.Lock != SkillLock.Up) + return TeachResult.SkillNotRaisable; + + int freePoints = m.Skills.Cap - m.Skills.Total; + int freeablePoints = 0; + + if (freePoints < 0) + freePoints = 0; + + for (int i = 0; freePoints + freeablePoints < pointsToLearn && i < m.Skills.Length; ++i) + { + Skill sk = m.Skills[i]; + + if (sk == theirSkill || sk.Lock != SkillLock.Down) + continue; + + freeablePoints += sk.BaseFixedPoint; + } + + if (freePoints + freeablePoints == 0) + return TeachResult.NotEnoughFreePoints; + + if (freePoints + freeablePoints < pointsToLearn) + { + pointsToLearn = freePoints + freeablePoints; + baseToSet = theirSkill.BaseFixedPoint + pointsToLearn; + } + + if (doTeach) + { + int need = pointsToLearn - freePoints; + + for (int i = 0; need > 0 && i < m.Skills.Length; ++i) + { + Skill sk = m.Skills[i]; + + if (sk == theirSkill || sk.Lock != SkillLock.Down) + continue; + + if (sk.BaseFixedPoint < need) + { + need -= sk.BaseFixedPoint; + sk.BaseFixedPoint = 0; + } + else + { + sk.BaseFixedPoint -= need; + need = 0; + } + } + + /* Sanity check */ + if (baseToSet > theirSkill.CapFixedPoint || + m.Skills.Total - theirSkill.BaseFixedPoint + baseToSet > m.Skills.Cap) + return TeachResult.NotEnoughFreePoints; + + theirSkill.BaseFixedPoint = baseToSet; + } + + return TeachResult.Success; + } + + public virtual bool CheckTeachingMatch(Mobile m) + { + if (m_Teaching == (SkillName)(-1)) + return false; + + if (m is PlayerMobile mobile) + return mobile.Learning == m_Teaching; + + return true; + } + + private SkillName m_Teaching = (SkillName)(-1); + + public virtual bool Teach(SkillName skill, Mobile m, int maxPointsToLearn, bool doTeach) + { + int pointsToLearn = 0; + TeachResult res = CheckTeachSkills(skill, m, maxPointsToLearn, ref pointsToLearn, doTeach); + + switch (res) + { + case TeachResult.KnowsMoreThanMe: + { + Say(501508); // I cannot teach thee, for thou knowest more than I! + break; + } + case TeachResult.KnowsWhatIKnow: + { + Say(501509); // I cannot teach thee, for thou knowest all I can teach! + break; + } + case TeachResult.NotEnoughFreePoints: + case TeachResult.SkillNotRaisable: + { + // Make sure this skill is marked to raise. If you are near the skill cap (700 points) you may need to lose some points in another skill first. + m.SendLocalizedMessage(501510, "", 0x22); + break; + } + case TeachResult.Success: + { + if (doTeach) + { + Say(501539); // Let me show thee something of how this is done. + m.SendLocalizedMessage(501540); // Your skill level increases. + + m_Teaching = (SkillName)(-1); + + if (m is PlayerMobile mobile) + mobile.Learning = (SkillName)(-1); + } + else + { + // I will teach thee all I know, if paid the amount in full. The price is: + Say(1019077, AffixType.Append, $" {pointsToLearn}", ""); + Say(1043108); // For less I shall teach thee less. + + m_Teaching = skill; + + if (m is PlayerMobile mobile) + mobile.Learning = skill; + } + + return true; + } + } + + return false; + } + + #endregion + + #region Set[...] + + public void SetDamage(int val) + { + m_DamageMin = val; + m_DamageMax = val; + } + + public void SetDamage(int min, int max) + { + m_DamageMin = min; + m_DamageMax = max; + } + + public void SetHits(int val) + { + if (val < 1000 && !Core.AOS) + val = val * 100 / 60; + + HitsMaxSeed = val; + Hits = HitsMax; + } + + public void SetHits(int min, int max) + { + if (min < 1000 && !Core.AOS) + { + min = min * 100 / 60; + max = max * 100 / 60; + } + + HitsMaxSeed = Utility.RandomMinMax(min, max); + Hits = HitsMax; + } + + public void SetStam(int val) + { + StamMaxSeed = val; + Stam = StamMax; + } + + public void SetStam(int min, int max) + { + StamMaxSeed = Utility.RandomMinMax(min, max); + Stam = StamMax; + } + + public void SetMana(int val) + { + ManaMaxSeed = val; + Mana = ManaMax; + } + + public void SetMana(int min, int max) + { + ManaMaxSeed = Utility.RandomMinMax(min, max); + Mana = ManaMax; + } + + public void SetStr(int val) + { + RawStr = val; + Hits = HitsMax; + } + + public void SetStr(int min, int max) + { + RawStr = Utility.RandomMinMax(min, max); + Hits = HitsMax; + } + + public void SetDex(int val) + { + RawDex = val; + Stam = StamMax; + } + + public void SetDex(int min, int max) + { + RawDex = Utility.RandomMinMax(min, max); + Stam = StamMax; + } + + public void SetInt(int val) + { + RawInt = val; + Mana = ManaMax; + } + + public void SetInt(int min, int max) + { + RawInt = Utility.RandomMinMax(min, max); + Mana = ManaMax; + } + + public void SetDamageType(ResistanceType type, int min, int max) + { + SetDamageType(type, Utility.RandomMinMax(min, max)); + } + + public void SetDamageType(ResistanceType type, int val) + { + switch (type) + { + case ResistanceType.Physical: + PhysicalDamage = val; + break; + case ResistanceType.Fire: + FireDamage = val; + break; + case ResistanceType.Cold: + ColdDamage = val; + break; + case ResistanceType.Poison: + PoisonDamage = val; + break; + case ResistanceType.Energy: + EnergyDamage = val; + break; + } + } + + public void SetResistance(ResistanceType type, int min, int max) + { + SetResistance(type, Utility.RandomMinMax(min, max)); + } + + public void SetResistance(ResistanceType type, int val) + { + switch (type) + { + case ResistanceType.Physical: + m_PhysicalResistance = val; + break; + case ResistanceType.Fire: + m_FireResistance = val; + break; + case ResistanceType.Cold: + m_ColdResistance = val; + break; + case ResistanceType.Poison: + m_PoisonResistance = val; + break; + case ResistanceType.Energy: + m_EnergyResistance = val; + break; + } + + UpdateResistances(); + } + + public void SetSkill(SkillName name, double val) + { + Skills[name].BaseFixedPoint = (int)(val * 10); + + if (Skills[name].Base > Skills[name].Cap) + { + if (Core.SE) + SkillsCap += Skills[name].BaseFixedPoint - Skills[name].CapFixedPoint; + + Skills[name].Cap = Skills[name].Base; + } + } + + public void SetSkill(SkillName name, double min, double max) + { + int minFixed = (int)(min * 10); + int maxFixed = (int)(max * 10); + + Skills[name].BaseFixedPoint = Utility.RandomMinMax(minFixed, maxFixed); + + if (Skills[name].Base > Skills[name].Cap) + { + if (Core.SE) + SkillsCap += Skills[name].BaseFixedPoint - Skills[name].CapFixedPoint; + + Skills[name].Cap = Skills[name].Base; + } + } + + public void SetFameLevel(int level) + { + switch (level) + { + case 1: + Fame = Utility.RandomMinMax(0, 1249); + break; + case 2: + Fame = Utility.RandomMinMax(1250, 2499); + break; + case 3: + Fame = Utility.RandomMinMax(2500, 4999); + break; + case 4: + Fame = Utility.RandomMinMax(5000, 9999); + break; + case 5: + Fame = Utility.RandomMinMax(10000, 10000); + break; + } + } + + public void SetKarmaLevel(int level) + { + switch (level) + { + case 0: + Karma = -Utility.RandomMinMax(0, 624); + break; + case 1: + Karma = -Utility.RandomMinMax(625, 1249); + break; + case 2: + Karma = -Utility.RandomMinMax(1250, 2499); + break; + case 3: + Karma = -Utility.RandomMinMax(2500, 4999); + break; + case 4: + Karma = -Utility.RandomMinMax(5000, 9999); + break; + case 5: + Karma = -Utility.RandomMinMax(10000, 10000); + break; + } + } + + #endregion + + #region Pack & Loot + + #region Mondain's Legacy + + public void PackArcaneScroll(int min, int max) + { + PackArcaneScroll(Utility.RandomMinMax(min, max)); + } + + public void PackArcaneScroll(int amount) + { + for (int i = 0; i < amount; ++i) + PackArcaneScroll(); + } + + public void PackArcaneScroll() + { + if (!Core.ML) + return; + + PackItem(Loot.Construct(Loot.ArcanistScrollTypes)); + } + + #endregion + + public void PackPotion() + { + PackItem(Loot.RandomPotion()); + } + + public void PackArcanceScroll(double chance) + { + if (!Core.ML || chance <= Utility.RandomDouble()) + return; + + PackItem(Loot.Construct(Loot.ArcanistScrollTypes)); + } + + public void PackNecroScroll(int index) + { + if (!Core.AOS || 0.05 <= Utility.RandomDouble()) + return; + + PackItem(Loot.Construct(Loot.NecromancyScrollTypes, index)); + } + + public void PackScroll(int minCircle, int maxCircle) + { + PackScroll(Utility.RandomMinMax(minCircle, maxCircle)); + } + + public void PackScroll(int circle) + { + int min = (circle - 1) * 8; + + PackItem(Loot.RandomScroll(min, min + 7, SpellbookType.Regular)); + } + + public void PackMagicItems(int minLevel, int maxLevel) + { + PackMagicItems(minLevel, maxLevel, 0.30, 0.15); + } + + public void PackMagicItems(int minLevel, int maxLevel, double armorChance, double weaponChance) + { + if (!PackArmor(minLevel, maxLevel, armorChance)) + PackWeapon(minLevel, maxLevel, weaponChance); + } + + public virtual void DropBackpack() + { + if (Backpack?.Items.Count > 0) + { + Backpack b = new CreatureBackpack(Name); + + List list = new List(Backpack.Items); + foreach (Item item in list) b.DropItem(item); + + BaseHouse house = BaseHouse.FindHouseAt(this); + if (house != null) + b.MoveToWorld(house.BanLocation, house.Map); + else + b.MoveToWorld(Location, Map); + } + } + + protected bool m_Spawning; + protected int m_KillersLuck; + + public virtual void GenerateLoot(bool spawning) + { + m_Spawning = spawning; + + if (!spawning) + m_KillersLuck = LootPack.GetLuckChanceForKiller(this); + + GenerateLoot(); + + if (m_Paragon) + { + if (Fame < 1250) + AddLoot(LootPack.Meager); + else if (Fame < 2500) + AddLoot(LootPack.Average); + else if (Fame < 5000) + AddLoot(LootPack.Rich); + else if (Fame < 10000) + AddLoot(LootPack.FilthyRich); + else + AddLoot(LootPack.UltraRich); + } + + m_Spawning = false; + m_KillersLuck = 0; + } + + public virtual void GenerateLoot() + { + } + + public virtual void AddLoot(LootPack pack, int amount) + { + for (int i = 0; i < amount; ++i) + AddLoot(pack); + } + + public virtual void AddLoot(LootPack pack) + { + if (Summoned) + return; + + Container backpack = Backpack ?? new Backpack { Movable = false }; + AddItem(backpack); + + pack.Generate(this, backpack, m_Spawning, m_KillersLuck); + } + + public bool PackArmor(int minLevel, int maxLevel) + { + return PackArmor(minLevel, maxLevel, 1.0); + } + + public bool PackArmor(int minLevel, int maxLevel, double chance) + { + if (chance <= Utility.RandomDouble()) + return false; + + Cap(ref minLevel, 0, 5); + Cap(ref maxLevel, 0, 5); + + if (Core.AOS) + { + Item item = Loot.RandomArmorOrShieldOrJewelry(); + + if (item == null) + return false; + + GetRandomAOSStats(minLevel, maxLevel, out int attributeCount, out int min, out int max); + + if (item is BaseArmor armor) + BaseRunicTool.ApplyAttributesTo(armor, attributeCount, min, max); + else if (item is BaseJewel jewel) + BaseRunicTool.ApplyAttributesTo(jewel, attributeCount, min, max); + + PackItem(item); + } + else + { + BaseArmor armor = Loot.RandomArmorOrShield(); + + if (armor == null) + return false; + + armor.ProtectionLevel = (ArmorProtectionLevel)RandomMinMaxScaled(minLevel, maxLevel); + armor.Durability = (ArmorDurabilityLevel)RandomMinMaxScaled(minLevel, maxLevel); + + PackItem(armor); + } + + return true; + } + + public static void GetRandomAOSStats(int minLevel, int maxLevel, out int attributeCount, out int min, out int max) + { + int v = RandomMinMaxScaled(minLevel, maxLevel); + + if (v >= 5) + { + attributeCount = Utility.RandomMinMax(2, 6); + min = 20; + max = 70; + } + else if (v == 4) + { + attributeCount = Utility.RandomMinMax(2, 4); + min = 20; + max = 50; + } + else if (v == 3) + { + attributeCount = Utility.RandomMinMax(2, 3); + min = 20; + max = 40; + } + else if (v == 2) + { + attributeCount = Utility.RandomMinMax(1, 2); + min = 10; + max = 30; + } + else + { + attributeCount = 1; + min = 10; + max = 20; + } + } + + public static int RandomMinMaxScaled(int min, int max) + { + if (min == max) + return min; + + if (min > max) + { + int hold = min; + min = max; + max = hold; + } + + /* Example: + * min: 1 + * max: 5 + * count: 5 + * + * total = (5*5) + (4*4) + (3*3) + (2*2) + (1*1) = 25 + 16 + 9 + 4 + 1 = 55 + * + * chance for min+0 : 25/55 : 45.45% + * chance for min+1 : 16/55 : 29.09% + * chance for min+2 : 9/55 : 16.36% + * chance for min+3 : 4/55 : 7.27% + * chance for min+4 : 1/55 : 1.81% + */ + + int count = max - min + 1; + int total = 0, toAdd = count; + + for (int i = 0; i < count; ++i, --toAdd) + total += toAdd * toAdd; + + int rand = Utility.Random(total); + toAdd = count; + + int val = min; + + for (int i = 0; i < count; ++i, --toAdd, ++val) + { + rand -= toAdd * toAdd; + + if (rand < 0) + break; + } + + return val; + } + + public bool PackSlayer() + { + return PackSlayer(0.05); + } + + public bool PackSlayer(double chance) + { + if (chance <= Utility.RandomDouble()) + return false; + + if (Utility.RandomBool()) + { + BaseInstrument instrument = Loot.RandomInstrument(); + + if (instrument != null) + { + instrument.Slayer = SlayerGroup.GetLootSlayerType(GetType()); + PackItem(instrument); + } + } + else if (!Core.AOS) + { + BaseWeapon weapon = Loot.RandomWeapon(); + + if (weapon != null) + { + weapon.Slayer = SlayerGroup.GetLootSlayerType(GetType()); + PackItem(weapon); + } + } + + return true; + } + + public bool PackWeapon(int minLevel, int maxLevel) + { + return PackWeapon(minLevel, maxLevel, 1.0); + } + + public bool PackWeapon(int minLevel, int maxLevel, double chance) + { + if (chance <= Utility.RandomDouble()) + return false; + + Cap(ref minLevel, 0, 5); + Cap(ref maxLevel, 0, 5); + + if (Core.AOS) + { + Item item = Loot.RandomWeaponOrJewelry(); + + if (item == null) + return false; + + GetRandomAOSStats(minLevel, maxLevel, out int attributeCount, out int min, out int max); + + if (item is BaseWeapon weapon) + BaseRunicTool.ApplyAttributesTo(weapon, attributeCount, min, max); + else if (item is BaseJewel jewel) + BaseRunicTool.ApplyAttributesTo(jewel, attributeCount, min, max); + + PackItem(item); + } + else + { + BaseWeapon weapon = Loot.RandomWeapon(); + + if (weapon == null) + return false; + + if (0.05 > Utility.RandomDouble()) + weapon.Slayer = SlayerName.Silver; + + weapon.DamageLevel = (WeaponDamageLevel)RandomMinMaxScaled(minLevel, maxLevel); + weapon.AccuracyLevel = (WeaponAccuracyLevel)RandomMinMaxScaled(minLevel, maxLevel); + weapon.DurabilityLevel = (WeaponDurabilityLevel)RandomMinMaxScaled(minLevel, maxLevel); + + PackItem(weapon); + } + + return true; + } + + public void PackGold(int amount) + { + if (amount > 0) + PackItem(new Gold(amount)); + } + + public void PackGold(int min, int max) + { + PackGold(Utility.RandomMinMax(min, max)); + } + + public void PackStatue(int min, int max) + { + PackStatue(Utility.RandomMinMax(min, max)); + } + + public void PackStatue(int amount) + { + for (int i = 0; i < amount; ++i) + PackStatue(); + } + + public void PackStatue() + { + PackItem(Loot.RandomStatue()); + } + + public void PackGem() + { + PackGem(1); + } + + public void PackGem(int min, int max) + { + PackGem(Utility.RandomMinMax(min, max)); + } + + public void PackGem(int amount) + { + if (amount <= 0) + return; + + Item gem = Loot.RandomGem(); + + gem.Amount = amount; + + PackItem(gem); + } + + public void PackNecroReg(int min, int max) + { + PackNecroReg(Utility.RandomMinMax(min, max)); + } + + public void PackNecroReg(int amount) + { + for (int i = 0; i < amount; ++i) + PackNecroReg(); + } + + public void PackNecroReg() + { + if (!Core.AOS) + return; + + PackItem(Loot.RandomNecromancyReagent()); + } + + public void PackReg(int min, int max) + { + PackReg(Utility.RandomMinMax(min, max)); + } + + public void PackReg(int amount) + { + if (amount <= 0) + return; + + Item reg = Loot.RandomReagent(); + + reg.Amount = amount; + + PackItem(reg); + } + + public void PackItem(Item item) + { + if (Summoned || item == null) + { + item?.Delete(); + return; + } + + Container pack = Backpack ?? new Backpack { Movable = false }; + AddItem(pack); + + if (!item.Stackable || !pack.TryDropItem(this, item, false)) // try stack + pack.DropItem(item); // failed, drop it anyway + } + + #endregion + + #region Healing + + public virtual bool CanHeal => false; + public virtual bool CanHealOwner => false; + public virtual double HealScalar => 1.0; + + public virtual int HealSound => 0x57; + public virtual int HealStartRange => 2; + public virtual int HealEndRange => RangePerception; + public virtual double HealTrigger => 0.78; + public virtual double HealDelay => 6.5; + public virtual double HealInterval => 0.0; + public virtual bool HealFully => true; + public virtual double HealOwnerTrigger => 0.78; + public virtual double HealOwnerDelay => 6.5; + public virtual double HealOwnerInterval => 30.0; + public virtual bool HealOwnerFully => false; + + private long m_NextHealTime = Core.TickCount; + private long m_NextHealOwnerTime = Core.TickCount; + private Timer m_HealTimer; + + public bool IsHealing => m_HealTimer != null; + + public virtual void HealStart(Mobile patient) + { + bool onSelf = patient == this; + + //DoBeneficial( patient ); + + RevealingAction(); + + if (!onSelf) + { + patient.RevealingAction(); + patient.SendLocalizedMessage(1008078, false, Name); // : Attempting to heal you. + } + + double seconds = (onSelf ? HealDelay : HealOwnerDelay) + (patient.Alive ? 0.0 : 5.0); + + m_HealTimer = Timer.DelayCall(TimeSpan.FromSeconds(seconds), new TimerStateCallback(Heal_Callback), patient); + } + + private void Heal_Callback(object state) + { + if (state is Mobile mobile) + Heal(mobile); + } + + public virtual void Heal(Mobile patient) + { + if (!Alive || Map == Map.Internal || !CanBeBeneficial(patient, true, true) || patient.Map != Map || + !InRange(patient, HealEndRange)) + { + StopHeal(); + return; + } + + bool onSelf = patient == this; + + if (!patient.Alive) + { + } + else if (patient.Poisoned) + { + int poisonLevel = patient.Poison.Level; + + double healing = Skills.Healing.Value; + double anatomy = Skills.Anatomy.Value; + double chance = (healing - 30.0) / 50.0 - poisonLevel * 0.1; + + if (healing >= 60.0 && anatomy >= 60.0 && chance > Utility.RandomDouble()) + if (patient.CurePoison(this)) + { + patient.SendLocalizedMessage(1010059); // You have been cured of all poisons. + + CheckSkill(SkillName.Healing, 0.0, 60.0 + poisonLevel * 10.0); // TODO: Verify formula + CheckSkill(SkillName.Anatomy, 0.0, 100.0); + } + } + else if (BleedAttack.IsBleeding(patient)) + { + patient.SendLocalizedMessage(1060167); // The bleeding wounds have healed, you are no longer bleeding! + BleedAttack.EndBleed(patient, false); + } + else + { + double healing = Skills.Healing.Value; + double anatomy = Skills.Anatomy.Value; + double chance = (healing + 10.0) / 100.0; + + if (chance > Utility.RandomDouble()) + { + double min = anatomy / 10.0 + healing / 6.0 + 4.0; + double max = anatomy / 8.0 + healing / 3.0 + 4.0; + + if (onSelf) + max += 10; + + double toHeal = min + Utility.RandomDouble() * (max - min); + + toHeal *= HealScalar; + + patient.Heal((int)toHeal); + + CheckSkill(SkillName.Healing, 0.0, 90.0); + CheckSkill(SkillName.Anatomy, 0.0, 100.0); + } + } + + HealEffect(patient); + + StopHeal(); + + if (onSelf && HealFully && Hits >= HealTrigger * HitsMax && Hits < HitsMax || !onSelf && HealOwnerFully && + patient.Hits >= HealOwnerTrigger * patient.HitsMax && patient.Hits < patient.HitsMax) + HealStart(patient); + } + + public virtual void StopHeal() + { + m_HealTimer?.Stop(); + + m_HealTimer = null; + } + + public virtual void HealEffect(Mobile patient) + { + patient.PlaySound(HealSound); + } + + #endregion + + #region Damaging Aura + + private long m_NextAura; + + public virtual bool HasAura => false; + public virtual TimeSpan AuraInterval => TimeSpan.FromSeconds(5); + public virtual int AuraRange => 4; + + public virtual int AuraBaseDamage => 5; + public virtual int AuraPhysicalDamage => 0; + public virtual int AuraFireDamage => 100; + public virtual int AuraColdDamage => 0; + public virtual int AuraPoisonDamage => 0; + public virtual int AuraEnergyDamage => 0; + public virtual int AuraChaosDamage => 0; + + public virtual void AuraDamage() + { + if (!Alive || IsDeadBondedPet) + return; + + List list = new List(); + + foreach (Mobile m in GetMobilesInRange(AuraRange)) + { + if (m == this || !CanBeHarmful(m, false) || Core.AOS && !InLOS(m)) + continue; + + if (m is BaseCreature bc) + { + if (bc.Controlled || bc.Summoned || bc.Team != Team) + list.Add(bc); + } + else if (m.Player) + { + list.Add(m); + } + } + + foreach (Mobile m in list) + { + AOS.Damage(m, this, AuraBaseDamage, AuraPhysicalDamage, AuraFireDamage, AuraColdDamage, AuraPoisonDamage, + AuraEnergyDamage, AuraChaosDamage); + AuraEffect(m); + } + } + + public virtual void AuraEffect(Mobile m) + { + } + + #endregion + } + + public class LoyaltyTimer : Timer + { + private static TimeSpan InternalDelay = TimeSpan.FromMinutes(5.0); + + private DateTime m_NextHourlyCheck; + + public LoyaltyTimer() : base(InternalDelay, InternalDelay) + { + m_NextHourlyCheck = DateTime.UtcNow + TimeSpan.FromHours(1.0); + Priority = TimerPriority.FiveSeconds; + } + + public static void Initialize() + { + new LoyaltyTimer().Start(); + } + + protected override void OnTick() + { + if (DateTime.UtcNow >= m_NextHourlyCheck) + m_NextHourlyCheck = DateTime.UtcNow + TimeSpan.FromHours(1.0); + else + return; + + List toRelease = new List(); + + // added array for wild creatures in house regions to be removed + List toRemove = new List(); + + Parallel.ForEach(World.Mobiles.Values, m => + { + if (!(m is BaseCreature c)) + return; + + if (c is BaseMount mount && mount.Rider != null) + { + mount.OwnerAbandonTime = DateTime.MinValue; + return; + } + + if (c.IsDeadPet) + { + Mobile owner = c.ControlMaster; + + if (!c.IsStabled && (owner == null || owner.Deleted || owner.Map != c.Map || + !owner.InRange(c, 12) || !c.CanSee(owner) || !c.InLOS(owner))) + { + if (c.OwnerAbandonTime == DateTime.MinValue) + c.OwnerAbandonTime = DateTime.UtcNow; + else if (c.OwnerAbandonTime + c.BondingAbandonDelay <= DateTime.UtcNow) + lock (toRemove) + { + toRemove.Add(c); + } + } + else + { + c.OwnerAbandonTime = DateTime.MinValue; + } + } + else if (c.Controlled && c.Commandable) + { + c.OwnerAbandonTime = DateTime.MinValue; + + if (c.Map != Map.Internal) + { + c.Loyalty -= BaseCreature.MaxLoyalty / 10; + + if (c.Loyalty < BaseCreature.MaxLoyalty / 10) + { + c.Say(1043270, c.Name); // * ~1_NAME~ looks around desperately * + c.PlaySound(c.GetIdleSound()); + } + + if (c.Loyalty <= 0) + lock (toRelease) + { + toRelease.Add(c); + } + } + } + + // added lines to check if a wild creature in a house region has to be removed or not + if (!c.Controlled && !c.IsStabled && (c.Region.IsPartOf(typeof(HouseRegion)) && c.CanBeDamaged() || + c.RemoveIfUntamed && c.Spawner == null)) + { + c.RemoveStep++; + + if (c.RemoveStep >= 20) + lock (toRemove) + { + toRemove.Add(c); + } + } + else + { + c.RemoveStep = 0; + } + }); + + // TODO: Parallelize this + foreach (BaseCreature c in toRelease) + { + c.Say(1043255, c.Name); // ~1_NAME~ appears to have decided that is better off without a master! + c.Loyalty = BaseCreature.MaxLoyalty; // Wonderfully Happy + c.IsBonded = false; + c.BondingBegin = DateTime.MinValue; + c.OwnerAbandonTime = DateTime.MinValue; + c.ControlTarget = null; + c.AIObject + .DoOrderRelease(); // this will prevent no release of creatures left alone with AI disabled (and consequent bug of Followers) + c.DropBackpack(); + } + + foreach (BaseCreature c in toRemove) + c.Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Familiars/BaseFamiliar.cs b/Scripts/Mobiles/Familiars/BaseFamiliar.cs index 151834bee..2adf698e7 100644 --- a/Scripts/Mobiles/Familiars/BaseFamiliar.cs +++ b/Scripts/Mobiles/Familiars/BaseFamiliar.cs @@ -1,181 +1,174 @@ using System.Collections.Generic; -using Server.Items; using Server.ContextMenus; +using Server.Items; namespace Server.Mobiles { - public abstract class BaseFamiliar : BaseCreature - { - public BaseFamiliar() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, .1, .1 ) - { - } + public abstract class BaseFamiliar : BaseCreature + { + private bool m_LastHidden; - public override bool BardImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override bool Commandable => false; + public BaseFamiliar() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, .1, .1) + { + } - public override bool PlayerRangeSensitive => false; + public BaseFamiliar(Serial serial) : base(serial) + { + } - private bool m_LastHidden; + public override bool BardImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override bool Commandable => false; - public virtual void RangeCheck() - { - if ( !Deleted && ControlMaster != null && !ControlMaster.Deleted ) - { - int range = ( RangeHome - 2 ); + public override bool PlayerRangeSensitive => false; - if ( !InRange( ControlMaster.Location, RangeHome ) ) - { - Mobile master = ControlMaster; + public virtual void RangeCheck() + { + if (!Deleted && ControlMaster != null && !ControlMaster.Deleted) + { + int range = RangeHome - 2; - Point3D m_Loc = Point3D.Zero; + if (!InRange(ControlMaster.Location, RangeHome)) + { + Mobile master = ControlMaster; - if ( Map == master.Map ) - { - int x = ( X > master.X ) ? ( master.X + range ) : ( master.X - range ); - int y = ( Y > master.Y ) ? ( master.Y + range ) : ( master.Y - range ); + Point3D m_Loc = Point3D.Zero; - for( int i = 0; i < 10; i++ ) - { - m_Loc.X = x + Utility.RandomMinMax( -1, 1 ); - m_Loc.Y = y + Utility.RandomMinMax( -1, 1 ); + if (Map == master.Map) + { + int x = X > master.X ? master.X + range : master.X - range; + int y = Y > master.Y ? master.Y + range : master.Y - range; - m_Loc.Z = Map.GetAverageZ( m_Loc.X, m_Loc.Y ); + for (int i = 0; i < 10; i++) + { + m_Loc.X = x + Utility.RandomMinMax(-1, 1); + m_Loc.Y = y + Utility.RandomMinMax(-1, 1); - if ( Map.CanSpawnMobile( m_Loc ) ) - { - break; - } + m_Loc.Z = Map.GetAverageZ(m_Loc.X, m_Loc.Y); - m_Loc = master.Location; - } + if (Map.CanSpawnMobile(m_Loc)) break; - if ( !Deleted ) - { - SetLocation( m_Loc, true ); - } - } - } - } - } + m_Loc = master.Location; + } - public override void OnThink() - { - Mobile master = ControlMaster; + if (!Deleted) SetLocation(m_Loc, true); + } + } + } + } - if ( Deleted ) - { - return; - } - if ( master == null || master.Deleted ) - { - DropPackContents(); - EndRelease( null ); - return; - } + public override void OnThink() + { + Mobile master = ControlMaster; - RangeCheck(); + if (Deleted) return; + if (master == null || master.Deleted) + { + DropPackContents(); + EndRelease(null); + return; + } - if ( m_LastHidden != master.Hidden ) - Hidden = m_LastHidden = master.Hidden; + RangeCheck(); - if ( AIObject != null && AIObject.WalkMobileRange( master, 5, true, 1, 1 )) - { - Warmode = master.Warmode; - Combatant = master.Combatant; + if (m_LastHidden != master.Hidden) + Hidden = m_LastHidden = master.Hidden; - CurrentSpeed = 0.10; - } - else - { - Warmode = false; - FocusMob = Combatant = null; + if (AIObject != null && AIObject.WalkMobileRange(master, 5, true, 1, 1)) + { + Warmode = master.Warmode; + Combatant = master.Combatant; - CurrentSpeed = .01; - } - } + CurrentSpeed = 0.10; + } + else + { + Warmode = false; + FocusMob = Combatant = null; - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + CurrentSpeed = .01; + } + } - if ( from.Alive && Controlled && from == ControlMaster && from.InRange( this, 14 ) ) - list.Add( new ReleaseEntry( from, this ) ); - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public virtual void BeginRelease( Mobile from ) - { - if ( !Deleted && Controlled && from == ControlMaster && from.CheckAlive() ) - EndRelease( from ); - } + if (from.Alive && Controlled && from == ControlMaster && from.InRange(this, 14)) + list.Add(new ReleaseEntry(from, this)); + } - public virtual void EndRelease( Mobile from ) - { - if ( from == null || (!Deleted && Controlled && from == ControlMaster && from.CheckAlive()) ) - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3728, 1, 13, 2100, 3, 5042, 0 ); - PlaySound( 0x201 ); - Delete(); - } - } + public virtual void BeginRelease(Mobile from) + { + if (!Deleted && Controlled && from == ControlMaster && from.CheckAlive()) + EndRelease(from); + } - public virtual void DropPackContents() - { - Map map = Map; - Container pack = Backpack; + public virtual void EndRelease(Mobile from) + { + if (from == null || !Deleted && Controlled && from == ControlMaster && from.CheckAlive()) + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3728, 1, 13, + 2100, 3, 5042, 0); + PlaySound(0x201); + Delete(); + } + } - if ( map != null && map != Map.Internal && pack != null ) - { - List list = new List( pack.Items ); + public virtual void DropPackContents() + { + Map map = Map; + Container pack = Backpack; - for ( int i = 0; i < list.Count; ++i ) - list[i].MoveToWorld( Location, map ); - } - } + if (map != null && map != Map.Internal && pack != null) + { + List list = new List(pack.Items); - public BaseFamiliar( Serial serial ) : base( serial ) - { - } + for (int i = 0; i < list.Count; ++i) + list[i].MoveToWorld(Location, map); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - ValidationQueue.Add( this ); - } + ValidationQueue.Add(this); + } - public void Validate() - { - DropPackContents(); - Delete(); - } + public void Validate() + { + DropPackContents(); + Delete(); + } - private class ReleaseEntry : ContextMenuEntry - { - private Mobile m_From; - private BaseFamiliar m_Familiar; + private class ReleaseEntry : ContextMenuEntry + { + private BaseFamiliar m_Familiar; + private Mobile m_From; - public ReleaseEntry( Mobile from, BaseFamiliar familiar ) : base( 6118, 14 ) - { - m_From = from; - m_Familiar = familiar; - } + public ReleaseEntry(Mobile from, BaseFamiliar familiar) : base(6118, 14) + { + m_From = from; + m_Familiar = familiar; + } - public override void OnClick() - { - if ( !m_Familiar.Deleted && m_Familiar.Controlled && m_From == m_Familiar.ControlMaster && m_From.CheckAlive() ) - m_Familiar.BeginRelease( m_From ); - } - } - } -} + public override void OnClick() + { + if (!m_Familiar.Deleted && m_Familiar.Controlled && m_From == m_Familiar.ControlMaster && + m_From.CheckAlive()) + m_Familiar.BeginRelease(m_From); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Familiars/DarkWolf.cs b/Scripts/Mobiles/Familiars/DarkWolf.cs index de3a1c33d..4a88e5faf 100644 --- a/Scripts/Mobiles/Familiars/DarkWolf.cs +++ b/Scripts/Mobiles/Familiars/DarkWolf.cs @@ -2,77 +2,77 @@ using System; namespace Server.Mobiles { - public class DarkWolfFamiliar : BaseFamiliar - { - public override string CorpseName => "a dark wolf corpse"; - public override string DefaultName => "a dark wolf"; + public class DarkWolfFamiliar : BaseFamiliar + { + private DateTime m_NextRestore; - public DarkWolfFamiliar() - { - Body = 99; - Hue = 0x901; - BaseSoundID = 0xE5; + public DarkWolfFamiliar() + { + Body = 99; + Hue = 0x901; + BaseSoundID = 0xE5; - SetStr( 100 ); - SetDex( 90 ); - SetInt( 90 ); + SetStr(100); + SetDex(90); + SetInt(90); - SetHits( 60 ); - SetStam( 90 ); - SetMana( 0 ); + SetHits(60); + SetStam(90); + SetMana(0); - SetDamage( 5, 10 ); + SetDamage(5, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 25, 40 ); - SetResistance( ResistanceType.Cold, 25, 40 ); - SetResistance( ResistanceType.Poison, 25, 40 ); - SetResistance( ResistanceType.Energy, 25, 40 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 25, 40); + SetResistance(ResistanceType.Cold, 25, 40); + SetResistance(ResistanceType.Poison, 25, 40); + SetResistance(ResistanceType.Energy, 25, 40); - SetSkill( SkillName.Wrestling, 85.1, 90.0 ); - SetSkill( SkillName.Tactics, 50.0 ); + SetSkill(SkillName.Wrestling, 85.1, 90.0); + SetSkill(SkillName.Tactics, 50.0); - ControlSlots = 1; - } + ControlSlots = 1; + } - private DateTime m_NextRestore; + public DarkWolfFamiliar(Serial serial) : base(serial) + { + } - public override void OnThink() - { - base.OnThink(); + public override string CorpseName => "a dark wolf corpse"; + public override string DefaultName => "a dark wolf"; - if ( DateTime.UtcNow < m_NextRestore ) - return; + public override void OnThink() + { + base.OnThink(); - m_NextRestore = DateTime.UtcNow + TimeSpan.FromSeconds( 2.0 ); + if (DateTime.UtcNow < m_NextRestore) + return; - Mobile caster = ControlMaster; + m_NextRestore = DateTime.UtcNow + TimeSpan.FromSeconds(2.0); - if ( caster == null ) - caster = SummonMaster; + Mobile caster = ControlMaster; - if ( caster != null ) - ++caster.Stam; - } + if (caster == null) + caster = SummonMaster; - public DarkWolfFamiliar( Serial serial ) : base( serial ) - { - } + if (caster != null) + ++caster.Stam; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Familiars/DeathAdder.cs b/Scripts/Mobiles/Familiars/DeathAdder.cs index e26bffa6b..2ac409623 100644 --- a/Scripts/Mobiles/Familiars/DeathAdder.cs +++ b/Scripts/Mobiles/Familiars/DeathAdder.cs @@ -1,56 +1,56 @@ namespace Server.Mobiles { - public class DeathAdder : BaseFamiliar - { - public override string CorpseName => "a death adder corpse"; - public override string DefaultName => "a death adder"; + public class DeathAdder : BaseFamiliar + { + public DeathAdder() + { + Body = 0x15; + Hue = 0x455; + BaseSoundID = 219; - public DeathAdder() - { - Body = 0x15; - Hue = 0x455; - BaseSoundID = 219; + SetStr(70); + SetDex(150); + SetInt(100); - SetStr( 70 ); - SetDex( 150 ); - SetInt( 100 ); + SetHits(50); + SetStam(150); + SetMana(0); - SetHits( 50 ); - SetStam( 150 ); - SetMana( 0 ); + SetDamage(1, 4); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 1, 4 ); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 10); + SetResistance(ResistanceType.Poison, 100); - SetResistance( ResistanceType.Physical, 10 ); - SetResistance( ResistanceType.Poison, 100 ); + SetSkill(SkillName.Wrestling, 90.0); + SetSkill(SkillName.Tactics, 50.0); + SetSkill(SkillName.MagicResist, 100.0); + SetSkill(SkillName.Poisoning, 150.0); - SetSkill( SkillName.Wrestling, 90.0 ); - SetSkill( SkillName.Tactics, 50.0 ); - SetSkill( SkillName.MagicResist, 100.0 ); - SetSkill( SkillName.Poisoning, 150.0 ); + ControlSlots = 1; + } - ControlSlots = 1; - } + public DeathAdder(Serial serial) : base(serial) + { + } - public override Poison HitPoison => (0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly); + public override string CorpseName => "a death adder corpse"; + public override string DefaultName => "a death adder"; - public DeathAdder( Serial serial ) : base( serial ) - { - } + public override Poison HitPoison => 0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Familiars/HordeMinion.cs b/Scripts/Mobiles/Familiars/HordeMinion.cs index 173c4f905..d450b9c26 100644 --- a/Scripts/Mobiles/Familiars/HordeMinion.cs +++ b/Scripts/Mobiles/Familiars/HordeMinion.cs @@ -1,201 +1,201 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Items; -using Server.Gumps; -using Server.Network; using Server.ContextMenus; +using Server.Gumps; +using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class HordeMinionFamiliar : BaseFamiliar - { - public override string CorpseName => "a horde minion corpse"; - public override bool DisplayWeight => true; + public class HordeMinionFamiliar : BaseFamiliar + { + private DateTime m_NextPickup; - public override string DefaultName => "a horde minion"; + public HordeMinionFamiliar() + { + Body = 776; + BaseSoundID = 0x39D; - public HordeMinionFamiliar() - { - Body = 776; - BaseSoundID = 0x39D; + SetStr(100); + SetDex(110); + SetInt(100); - SetStr( 100 ); - SetDex( 110 ); - SetInt( 100 ); + SetHits(70); + SetStam(110); + SetMana(0); - SetHits( 70 ); - SetStam( 110 ); - SetMana( 0 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 50, 55); + SetResistance(ResistanceType.Poison, 25, 30); + SetResistance(ResistanceType.Energy, 25, 30); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 50, 55 ); - SetResistance( ResistanceType.Poison, 25, 30 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + SetSkill(SkillName.Wrestling, 70.1, 75.0); + SetSkill(SkillName.Tactics, 50.0); - SetSkill( SkillName.Wrestling, 70.1, 75.0 ); - SetSkill( SkillName.Tactics, 50.0 ); + ControlSlots = 1; - ControlSlots = 1; + Container pack = Backpack; - Container pack = Backpack; + pack?.Delete(); - pack?.Delete(); + pack = new Backpack(); + pack.Movable = false; + pack.Weight = 13.0; - pack = new Backpack(); - pack.Movable = false; - pack.Weight = 13.0; + AddItem(pack); + } - AddItem( pack ); - } + public HordeMinionFamiliar(Serial serial) : base(serial) + { + } - private DateTime m_NextPickup; + public override string CorpseName => "a horde minion corpse"; + public override bool DisplayWeight => true; - public override void OnThink() - { - base.OnThink(); + public override string DefaultName => "a horde minion"; - if ( DateTime.UtcNow < m_NextPickup ) - return; + public override void OnThink() + { + base.OnThink(); - m_NextPickup = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 5, 10 ) ); + if (DateTime.UtcNow < m_NextPickup) + return; - Container pack = Backpack; + m_NextPickup = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(5, 10)); - if ( pack == null ) - return; + Container pack = Backpack; - ArrayList list = new ArrayList(); + if (pack == null) + return; - foreach ( Item item in GetItemsInRange( 2 ) ) - { - if ( item.Movable && item.Stackable ) - list.Add( item ); - } + ArrayList list = new ArrayList(); - int pickedUp = 0; + foreach (Item item in GetItemsInRange(2)) + if (item.Movable && item.Stackable) + list.Add(item); - for ( int i = 0; i < list.Count; ++i ) - { - Item item = (Item)list[i]; + int pickedUp = 0; - if ( !pack.CheckHold( this, item, false, true ) ) - return; + for (int i = 0; i < list.Count; ++i) + { + Item item = (Item)list[i]; - bool rejected; - LRReason reject; + if (!pack.CheckHold(this, item, false, true)) + return; - NextActionTime = Core.TickCount; + bool rejected; + LRReason reject; - Lift( item, item.Amount, out rejected, out reject ); + NextActionTime = Core.TickCount; - if ( rejected ) - continue; + Lift(item, item.Amount, out rejected, out reject); - Drop( this, Point3D.Zero ); + if (rejected) + continue; - if ( ++pickedUp == 3 ) - break; - } - } + Drop(this, Point3D.Zero); - private void ConfirmRelease_Callback( Mobile from, bool okay, object state ) - { - if ( okay ) - EndRelease( from ); - } + if (++pickedUp == 3) + break; + } + } - public override void BeginRelease( Mobile from ) - { - Container pack = Backpack; + private void ConfirmRelease_Callback(Mobile from, bool okay, object state) + { + if (okay) + EndRelease(from); + } - if ( pack != null && pack.Items.Count > 0 ) - from.SendGump( new WarningGump( 1060635, 30720, 1061672, 32512, 420, 280, ConfirmRelease_Callback, null ) ); - else - EndRelease( from ); - } + public override void BeginRelease(Mobile from) + { + Container pack = Backpack; - #region Pack Animal Methods - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + if (pack != null && pack.Items.Count > 0) + from.SendGump(new WarningGump(1060635, 30720, 1061672, 32512, 420, 280, ConfirmRelease_Callback, null)); + else + EndRelease(from); + } - PackAnimal.CombineBackpacks( this ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - return true; - } + writer.Write(0); + } - public override DeathMoveResult GetInventoryMoveResultFor( Item item ) - { - return DeathMoveResult.MoveToCorpse; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override bool IsSnoop( Mobile from ) - { - if ( PackAnimal.CheckAccess( this, from ) ) - return false; + int version = reader.ReadInt(); + } - return base.IsSnoop( from ); - } + #region Pack Animal Methods - public override bool OnDragDrop( Mobile from, Item item ) - { - if ( CheckFeed( from, item ) ) - return true; + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - if ( PackAnimal.CheckAccess( this, from ) ) - { - AddToBackpack( item ); - return true; - } + PackAnimal.CombineBackpacks(this); - return base.OnDragDrop( from, item ); - } + return true; + } - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - return PackAnimal.CheckAccess( this, from ); - } + public override DeathMoveResult GetInventoryMoveResultFor(Item item) + { + return DeathMoveResult.MoveToCorpse; + } - public override bool CheckNonlocalLift( Mobile from, Item item ) - { - return PackAnimal.CheckAccess( this, from ); - } + public override bool IsSnoop(Mobile from) + { + if (PackAnimal.CheckAccess(this, from)) + return false; - public override void OnDoubleClick( Mobile from ) - { - PackAnimal.TryPackOpen( this, from ); - } + return base.IsSnoop(from); + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override bool OnDragDrop(Mobile from, Item item) + { + if (CheckFeed(from, item)) + return true; - PackAnimal.GetContextMenuEntries( this, from, list ); - } - #endregion + if (PackAnimal.CheckAccess(this, from)) + { + AddToBackpack(item); + return true; + } - public HordeMinionFamiliar( Serial serial ) : base( serial ) - { - } + return base.OnDragDrop(from, item); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + return PackAnimal.CheckAccess(this, from); + } - writer.Write( (int) 0 ); - } + public override bool CheckNonlocalLift(Mobile from, Item item) + { + return PackAnimal.CheckAccess(this, from); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnDoubleClick(Mobile from) + { + PackAnimal.TryPackOpen(this, from); + } - int version = reader.ReadInt(); - } - } -} + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + PackAnimal.GetContextMenuEntries(this, from, list); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Familiars/ShadowWisp.cs b/Scripts/Mobiles/Familiars/ShadowWisp.cs index 341524e9c..4c3dffe56 100644 --- a/Scripts/Mobiles/Familiars/ShadowWisp.cs +++ b/Scripts/Mobiles/Familiars/ShadowWisp.cs @@ -3,111 +3,109 @@ using System.Collections; namespace Server.Mobiles { - public class ShadowWispFamiliar : BaseFamiliar - { - public override string CorpseName => "a shadow wisp corpse"; - public override string DefaultName => "a shadow wisp"; + public class ShadowWispFamiliar : BaseFamiliar + { + private DateTime m_NextFlare; - public ShadowWispFamiliar() - { - Body = 165; - Hue = 0x901; - BaseSoundID = 466; + public ShadowWispFamiliar() + { + Body = 165; + Hue = 0x901; + BaseSoundID = 466; - SetStr( 50 ); - SetDex( 60 ); - SetInt( 100 ); + SetStr(50); + SetDex(60); + SetInt(100); - SetHits( 50 ); - SetStam( 60 ); - SetMana( 0 ); + SetHits(50); + SetStam(60); + SetMana(0); - SetDamage( 5, 10 ); + SetDamage(5, 10); - SetDamageType( ResistanceType.Energy, 100 ); + SetDamageType(ResistanceType.Energy, 100); - SetResistance( ResistanceType.Physical, 10, 15 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 99 ); + SetResistance(ResistanceType.Physical, 10, 15); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 99); - SetSkill( SkillName.Wrestling, 40.0 ); - SetSkill( SkillName.Tactics, 40.0 ); + SetSkill(SkillName.Wrestling, 40.0); + SetSkill(SkillName.Tactics, 40.0); - ControlSlots = 1; - } + ControlSlots = 1; + } - private DateTime m_NextFlare; + public ShadowWispFamiliar(Serial serial) : base(serial) + { + } - public override void OnThink() - { - base.OnThink(); + public override string CorpseName => "a shadow wisp corpse"; + public override string DefaultName => "a shadow wisp"; - if ( DateTime.UtcNow < m_NextFlare ) - return; + public override void OnThink() + { + base.OnThink(); - m_NextFlare = DateTime.UtcNow + TimeSpan.FromSeconds( 5.0 + (25.0 * Utility.RandomDouble()) ); + if (DateTime.UtcNow < m_NextFlare) + return; - FixedEffect( 0x37C4, 1, 12, 1109, 6 ); - PlaySound( 0x1D3 ); + m_NextFlare = DateTime.UtcNow + TimeSpan.FromSeconds(5.0 + 25.0 * Utility.RandomDouble()); - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), Flare ); - } + FixedEffect(0x37C4, 1, 12, 1109, 6); + PlaySound(0x1D3); - private void Flare() - { - Mobile caster = ControlMaster; + Timer.DelayCall(TimeSpan.FromSeconds(0.5), Flare); + } - if ( caster == null ) - caster = SummonMaster; + private void Flare() + { + Mobile caster = ControlMaster; - if ( caster == null ) - return; + if (caster == null) + caster = SummonMaster; - ArrayList list = new ArrayList(); + if (caster == null) + return; - foreach ( Mobile m in GetMobilesInRange( 5 ) ) - { - if ( m.Player && m.Alive && !m.IsDeadBondedPet && m.Karma <= 0 && m.AccessLevel < AccessLevel.Counselor ) - list.Add( m ); - } + ArrayList list = new ArrayList(); - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; - bool friendly = true; + foreach (Mobile m in GetMobilesInRange(5)) + if (m.Player && m.Alive && !m.IsDeadBondedPet && m.Karma <= 0 && m.AccessLevel < AccessLevel.Counselor) + list.Add(m); - for ( int j = 0; friendly && j < caster.Aggressors.Count; ++j ) - friendly = ( caster.Aggressors[j].Attacker != m ); + for (int i = 0; i < list.Count; ++i) + { + Mobile m = (Mobile)list[i]; + bool friendly = true; - for ( int j = 0; friendly && j < caster.Aggressed.Count; ++j ) - friendly = ( caster.Aggressed[j].Defender != m ); + for (int j = 0; friendly && j < caster.Aggressors.Count; ++j) + friendly = caster.Aggressors[j].Attacker != m; - if ( friendly ) - { - m.FixedEffect( 0x37C4, 1, 12, 1109, 3 ); // At player - m.Mana += 1 - (m.Karma / 1000); - } - } - } + for (int j = 0; friendly && j < caster.Aggressed.Count; ++j) + friendly = caster.Aggressed[j].Defender != m; - public ShadowWispFamiliar( Serial serial ) : base( serial ) - { - } + if (friendly) + { + m.FixedEffect(0x37C4, 1, 12, 1109, 3); // At player + m.Mana += 1 - m.Karma / 1000; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Familiars/VampireBat.cs b/Scripts/Mobiles/Familiars/VampireBat.cs index 7a7bd6673..3812168a3 100644 --- a/Scripts/Mobiles/Familiars/VampireBat.cs +++ b/Scripts/Mobiles/Familiars/VampireBat.cs @@ -1,55 +1,55 @@ namespace Server.Mobiles { - public class VampireBatFamiliar : BaseFamiliar - { - public override string CorpseName => "a vampire bat corpse"; - public override string DefaultName => "a vampire bat"; + public class VampireBatFamiliar : BaseFamiliar + { + public VampireBatFamiliar() + { + Body = 317; + BaseSoundID = 0x270; - public VampireBatFamiliar() - { - Body = 317; - BaseSoundID = 0x270; + SetStr(120); + SetDex(120); + SetInt(100); - SetStr( 120 ); - SetDex( 120 ); - SetInt( 100 ); + SetHits(90); + SetStam(120); + SetMana(0); - SetHits( 90 ); - SetStam( 120 ); - SetMana( 0 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 10, 15); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 10, 15); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 10, 15 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 10, 15 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.Wrestling, 95.1, 100.0); + SetSkill(SkillName.Tactics, 50.0); - SetSkill( SkillName.Wrestling, 95.1, 100.0 ); - SetSkill( SkillName.Tactics, 50.0 ); + ControlSlots = 1; + } - ControlSlots = 1; - } + public VampireBatFamiliar(Serial serial) : base(serial) + { + } - public VampireBatFamiliar( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a vampire bat corpse"; + public override string DefaultName => "a vampire bat"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Guards/ArcherGuard.cs b/Scripts/Mobiles/Guards/ArcherGuard.cs index 7a16ad5ab..e6b48682a 100644 --- a/Scripts/Mobiles/Guards/ArcherGuard.cs +++ b/Scripts/Mobiles/Guards/ArcherGuard.cs @@ -3,390 +3,397 @@ using Server.Items; namespace Server.Mobiles { - public class ArcherGuard : BaseGuard - { - private Timer m_AttackTimer, m_IdleTimer; + public class ArcherGuard : BaseGuard + { + private Timer m_AttackTimer, m_IdleTimer; - private Mobile m_Focus; + private Mobile m_Focus; - [Constructible] - public ArcherGuard() : this( null ) - { - } + [Constructible] + public ArcherGuard() : this(null) + { + } - public ArcherGuard( Mobile target ) : base( target ) - { - InitStats( 100, 125, 25 ); - Title = "the guard"; + public ArcherGuard(Mobile target) : base(target) + { + InitStats(100, 125, 25); + Title = "the guard"; - SpeechHue = Utility.RandomDyedHue(); + SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } - - new Horse().Rider = this; - - AddItem( new StuddedChest() ); - AddItem( new StuddedArms() ); - AddItem( new StuddedGloves() ); - AddItem( new StuddedGorget() ); - AddItem( new StuddedLegs() ); - AddItem( new Boots() ); - AddItem( new SkullCap() ); - - Bow bow = new Bow(); - - bow.Movable = false; - bow.Crafter = this; - bow.Quality = WeaponQuality.Exceptional; - - AddItem( bow ); - - Container pack = new Backpack(); - - pack.Movable = false; - - Arrow arrows = new Arrow( 250 ); - - arrows.LootType = LootType.Newbied; - - pack.DropItem( arrows ); - pack.DropItem( new Gold( 10, 25 ) ); - - AddItem( pack ); - - Skills[SkillName.Anatomy].Base = 120.0; - Skills[SkillName.Tactics].Base = 120.0; - Skills[SkillName.Archery].Base = 120.0; - Skills[SkillName.MagicResist].Base = 120.0; - Skills[SkillName.DetectHidden].Base = 100.0; - - NextCombatTime = Core.TickCount + 500; - Focus = target; - } - - public ArcherGuard( Serial serial ) : base( serial ) - { - } - - public override bool OnBeforeDeath() - { - if ( m_Focus != null && m_Focus.Alive ) - new AvengeTimer( m_Focus ).Start(); // If a guard dies, three more guards will spawn - - return base.OnBeforeDeath(); - } - - [CommandProperty( AccessLevel.GameMaster )] - public override Mobile Focus - { - get => m_Focus; - set - { - if ( Deleted ) - return; - - Mobile oldFocus = m_Focus; - - if ( oldFocus != value ) - { - m_Focus = value; - - if ( value != null ) - AggressiveAction( value ); - - Combatant = value; - - if ( oldFocus != null && !oldFocus.Alive ) - Say( "Thou hast suffered thy punishment, scoundrel." ); - - if ( value != null ) - Say( 500131 ); // Thou wilt regret thine actions, swine! - - if ( m_AttackTimer != null ) - { - m_AttackTimer.Stop(); - m_AttackTimer = null; - } - - if ( m_IdleTimer != null ) - { - m_IdleTimer.Stop(); - m_IdleTimer = null; - } - - if ( m_Focus != null ) - { - m_AttackTimer = new AttackTimer( this ); - m_AttackTimer.Start(); - ((AttackTimer)m_AttackTimer).DoOnTick(); - } - else - { - m_IdleTimer = new IdleTimer( this ); - m_IdleTimer.Start(); - } - } - else if ( m_Focus == null && m_IdleTimer == null ) - { - m_IdleTimer = new IdleTimer( this ); - m_IdleTimer.Start(); - } - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Focus ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Focus = reader.ReadMobile(); - - if ( m_Focus != null ) - { - m_AttackTimer = new AttackTimer( this ); - m_AttackTimer.Start(); - } - else - { - m_IdleTimer = new IdleTimer( this ); - m_IdleTimer.Start(); - } - - break; - } - } - } - - public override void OnAfterDelete() - { - if ( m_AttackTimer != null ) - { - m_AttackTimer.Stop(); - m_AttackTimer = null; - } - - if ( m_IdleTimer != null ) - { - m_IdleTimer.Stop(); - m_IdleTimer = null; - } - - base.OnAfterDelete(); - } - - private class AvengeTimer : Timer - { - private Mobile m_Focus; - - public AvengeTimer( Mobile focus ) : base( TimeSpan.FromSeconds( 2.5 ), TimeSpan.FromSeconds( 1.0 ), 3 ) // After 2.5 seconds, one guard will spawn every 1.0 second, three times - { - m_Focus = focus; - } - - protected override void OnTick() - { - Spawn( m_Focus, m_Focus, 1, true ); - } - } - - private class AttackTimer : Timer - { - private ArcherGuard m_Owner; - // private bool m_Shooting; - - public AttackTimer( ArcherGuard owner ) : base( TimeSpan.FromSeconds( 0.25 ), TimeSpan.FromSeconds( 0.1 ) ) - { - m_Owner = owner; - } - - public void DoOnTick() - { - OnTick(); - } - - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } - - m_Owner.Criminal = false; - m_Owner.Kills = 0; - m_Owner.Stam = m_Owner.StamMax; - - Mobile target = m_Owner.Focus; - - if ( target != null && (target.Deleted || !target.Alive || !m_Owner.CanBeHarmful( target )) ) - { - m_Owner.Focus = null; - Stop(); - return; - } - - if ( m_Owner.Weapon is Fists ) - { - m_Owner.Kill(); - Stop(); - return; - } - - if ( target != null && m_Owner.Combatant != target ) - m_Owner.Combatant = target; - - if ( target == null ) - { - Stop(); - } - else - {// - TeleportTo( target ); - target.BoltEffect( 0 ); - - if ( target is BaseCreature creature ) - creature.NoKillAwards = true; - - target.Damage( target.HitsMax, m_Owner ); - target.Kill(); // just in case, maybe Damage is overridden on some shard - - if ( target.Corpse != null && !target.Player ) - target.Corpse.Delete(); - - m_Owner.Focus = null; - Stop(); - }// - /*else if ( !m_Owner.InRange( target, 20 ) ) - { - m_Shooting = false; - m_Owner.Focus = null; - } - else if ( !m_Owner.InLOS( target ) ) - { - m_Shooting = false; - TeleportTo( target ); - } - else if ( !m_Owner.CanSee( target ) ) - { - m_Shooting = false; - - if ( !m_Owner.InRange( target, 2 ) ) - { - if ( !m_Owner.Move( m_Owner.GetDirectionTo( target ) | Direction.Running ) && OutOfMaxDistance( target ) ) - TeleportTo( target ); - } - else - { - if ( !m_Owner.UseSkill( SkillName.DetectHidden ) && Utility.Random( 50 ) == 0 ) - m_Owner.Say( "Reveal!" ); - } - } - else - { - if ( m_Shooting && (TimeToSpare() || OutOfMaxDistance( target )) ) - m_Shooting = false; - else if ( !m_Shooting && InMinDistance( target ) ) - m_Shooting = true; - - if ( !m_Shooting ) - { - if ( m_Owner.InRange( target, 1 ) ) - { - if ( !m_Owner.Move( (Direction)(m_Owner.GetDirectionTo( target ) - 4) | Direction.Running ) && OutOfMaxDistance( target ) ) // Too close, move away - TeleportTo( target ); - } - else if ( !m_Owner.InRange( target, 2 ) ) - { - if ( !m_Owner.Move( m_Owner.GetDirectionTo( target ) | Direction.Running ) && OutOfMaxDistance( target ) ) - TeleportTo( target ); - } - } - }*/ - } - - private bool TimeToSpare() - { - return (m_Owner.NextCombatTime - Core.TickCount) > 1000; - } - - private bool OutOfMaxDistance( Mobile target ) - { - return !m_Owner.InRange( target, m_Owner.Weapon.MaxRange ); - } - - private bool InMinDistance( Mobile target ) - { - return m_Owner.InRange( target, 4 ); - } - - private void TeleportTo( Mobile target ) - { - Point3D from = m_Owner.Location; - Point3D to = target.Location; - - m_Owner.Location = to; - - Effects.SendLocationParticles( EffectItem.Create( from, m_Owner.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( to, m_Owner.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); - - m_Owner.PlaySound( 0x1FE ); - } - } - - private class IdleTimer : Timer - { - private ArcherGuard m_Owner; - private int m_Stage; - - public IdleTimer( ArcherGuard owner ) : base( TimeSpan.FromSeconds( 2.0 ), TimeSpan.FromSeconds( 2.5 ) ) - { - m_Owner = owner; - } - - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } - - if ( (m_Stage++ % 4) == 0 || !m_Owner.Move( m_Owner.Direction ) ) - m_Owner.Direction = (Direction)Utility.Random( 8 ); - - if ( m_Stage > 16 ) - { - Effects.SendLocationParticles( EffectItem.Create( m_Owner.Location, m_Owner.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - m_Owner.PlaySound( 0x1FE ); - - m_Owner.Delete(); - } - } - } - } -} + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } + + new Horse().Rider = this; + + AddItem(new StuddedChest()); + AddItem(new StuddedArms()); + AddItem(new StuddedGloves()); + AddItem(new StuddedGorget()); + AddItem(new StuddedLegs()); + AddItem(new Boots()); + AddItem(new SkullCap()); + + Bow bow = new Bow(); + + bow.Movable = false; + bow.Crafter = this; + bow.Quality = WeaponQuality.Exceptional; + + AddItem(bow); + + Container pack = new Backpack(); + + pack.Movable = false; + + Arrow arrows = new Arrow(250); + + arrows.LootType = LootType.Newbied; + + pack.DropItem(arrows); + pack.DropItem(new Gold(10, 25)); + + AddItem(pack); + + Skills[SkillName.Anatomy].Base = 120.0; + Skills[SkillName.Tactics].Base = 120.0; + Skills[SkillName.Archery].Base = 120.0; + Skills[SkillName.MagicResist].Base = 120.0; + Skills[SkillName.DetectHidden].Base = 100.0; + + NextCombatTime = Core.TickCount + 500; + Focus = target; + } + + public ArcherGuard(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public override Mobile Focus + { + get => m_Focus; + set + { + if (Deleted) + return; + + Mobile oldFocus = m_Focus; + + if (oldFocus != value) + { + m_Focus = value; + + if (value != null) + AggressiveAction(value); + + Combatant = value; + + if (oldFocus != null && !oldFocus.Alive) + Say("Thou hast suffered thy punishment, scoundrel."); + + if (value != null) + Say(500131); // Thou wilt regret thine actions, swine! + + if (m_AttackTimer != null) + { + m_AttackTimer.Stop(); + m_AttackTimer = null; + } + + if (m_IdleTimer != null) + { + m_IdleTimer.Stop(); + m_IdleTimer = null; + } + + if (m_Focus != null) + { + m_AttackTimer = new AttackTimer(this); + m_AttackTimer.Start(); + ((AttackTimer)m_AttackTimer).DoOnTick(); + } + else + { + m_IdleTimer = new IdleTimer(this); + m_IdleTimer.Start(); + } + } + else if (m_Focus == null && m_IdleTimer == null) + { + m_IdleTimer = new IdleTimer(this); + m_IdleTimer.Start(); + } + } + } + + public override bool OnBeforeDeath() + { + if (m_Focus != null && m_Focus.Alive) + new AvengeTimer(m_Focus).Start(); // If a guard dies, three more guards will spawn + + return base.OnBeforeDeath(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Focus); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Focus = reader.ReadMobile(); + + if (m_Focus != null) + { + m_AttackTimer = new AttackTimer(this); + m_AttackTimer.Start(); + } + else + { + m_IdleTimer = new IdleTimer(this); + m_IdleTimer.Start(); + } + + break; + } + } + } + + public override void OnAfterDelete() + { + if (m_AttackTimer != null) + { + m_AttackTimer.Stop(); + m_AttackTimer = null; + } + + if (m_IdleTimer != null) + { + m_IdleTimer.Stop(); + m_IdleTimer = null; + } + + base.OnAfterDelete(); + } + + private class AvengeTimer : Timer + { + private Mobile m_Focus; + + public AvengeTimer(Mobile focus) : + base(TimeSpan.FromSeconds(2.5), TimeSpan.FromSeconds(1.0), + 3) // After 2.5 seconds, one guard will spawn every 1.0 second, three times + { + m_Focus = focus; + } + + protected override void OnTick() + { + Spawn(m_Focus, m_Focus, 1, true); + } + } + + private class AttackTimer : Timer + { + private ArcherGuard m_Owner; + // private bool m_Shooting; + + public AttackTimer(ArcherGuard owner) : base(TimeSpan.FromSeconds(0.25), TimeSpan.FromSeconds(0.1)) + { + m_Owner = owner; + } + + public void DoOnTick() + { + OnTick(); + } + + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } + + m_Owner.Criminal = false; + m_Owner.Kills = 0; + m_Owner.Stam = m_Owner.StamMax; + + Mobile target = m_Owner.Focus; + + if (target != null && (target.Deleted || !target.Alive || !m_Owner.CanBeHarmful(target))) + { + m_Owner.Focus = null; + Stop(); + return; + } + + if (m_Owner.Weapon is Fists) + { + m_Owner.Kill(); + Stop(); + return; + } + + if (target != null && m_Owner.Combatant != target) + m_Owner.Combatant = target; + + if (target == null) + { + Stop(); + } + else + { + // + TeleportTo(target); + target.BoltEffect(0); + + if (target is BaseCreature creature) + creature.NoKillAwards = true; + + target.Damage(target.HitsMax, m_Owner); + target.Kill(); // just in case, maybe Damage is overridden on some shard + + if (target.Corpse != null && !target.Player) + target.Corpse.Delete(); + + m_Owner.Focus = null; + Stop(); + } // + + /*else if ( !m_Owner.InRange( target, 20 ) ) + { + m_Shooting = false; + m_Owner.Focus = null; + } + else if ( !m_Owner.InLOS( target ) ) + { + m_Shooting = false; + TeleportTo( target ); + } + else if ( !m_Owner.CanSee( target ) ) + { + m_Shooting = false; + + if ( !m_Owner.InRange( target, 2 ) ) + { + if ( !m_Owner.Move( m_Owner.GetDirectionTo( target ) | Direction.Running ) && OutOfMaxDistance( target ) ) + TeleportTo( target ); + } + else + { + if ( !m_Owner.UseSkill( SkillName.DetectHidden ) && Utility.Random( 50 ) == 0 ) + m_Owner.Say( "Reveal!" ); + } + } + else + { + if ( m_Shooting && (TimeToSpare() || OutOfMaxDistance( target )) ) + m_Shooting = false; + else if ( !m_Shooting && InMinDistance( target ) ) + m_Shooting = true; + + if ( !m_Shooting ) + { + if ( m_Owner.InRange( target, 1 ) ) + { + if ( !m_Owner.Move( (Direction)(m_Owner.GetDirectionTo( target ) - 4) | Direction.Running ) && OutOfMaxDistance( target ) ) // Too close, move away + TeleportTo( target ); + } + else if ( !m_Owner.InRange( target, 2 ) ) + { + if ( !m_Owner.Move( m_Owner.GetDirectionTo( target ) | Direction.Running ) && OutOfMaxDistance( target ) ) + TeleportTo( target ); + } + } + }*/ + } + + private bool TimeToSpare() + { + return m_Owner.NextCombatTime - Core.TickCount > 1000; + } + + private bool OutOfMaxDistance(Mobile target) + { + return !m_Owner.InRange(target, m_Owner.Weapon.MaxRange); + } + + private bool InMinDistance(Mobile target) + { + return m_Owner.InRange(target, 4); + } + + private void TeleportTo(Mobile target) + { + Point3D from = m_Owner.Location; + Point3D to = target.Location; + + m_Owner.Location = to; + + Effects.SendLocationParticles(EffectItem.Create(from, m_Owner.Map, EffectItem.DefaultDuration), 0x3728, 10, + 10, 2023); + Effects.SendLocationParticles(EffectItem.Create(to, m_Owner.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); + + m_Owner.PlaySound(0x1FE); + } + } + + private class IdleTimer : Timer + { + private ArcherGuard m_Owner; + private int m_Stage; + + public IdleTimer(ArcherGuard owner) : base(TimeSpan.FromSeconds(2.0), TimeSpan.FromSeconds(2.5)) + { + m_Owner = owner; + } + + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } + + if (m_Stage++ % 4 == 0 || !m_Owner.Move(m_Owner.Direction)) + m_Owner.Direction = (Direction)Utility.Random(8); + + if (m_Stage > 16) + { + Effects.SendLocationParticles( + EffectItem.Create(m_Owner.Location, m_Owner.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, 2023); + m_Owner.PlaySound(0x1FE); + + m_Owner.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Guards/BaseGuard.cs b/Scripts/Mobiles/Guards/BaseGuard.cs index a43d46234..c77ebf422 100644 --- a/Scripts/Mobiles/Guards/BaseGuard.cs +++ b/Scripts/Mobiles/Guards/BaseGuard.cs @@ -2,79 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public abstract class BaseGuard : Mobile - { - public static void Spawn( Mobile caller, Mobile target ) - { - Spawn( caller, target, 1, false ); - } + public abstract class BaseGuard : Mobile + { + public BaseGuard(Mobile target) + { + if (target != null) + { + Location = target.Location; + Map = target.Map; - public static void Spawn( Mobile caller, Mobile target, int amount, bool onlyAdditional ) - { - if ( target == null || target.Deleted ) - return; + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); + } + } - foreach ( Mobile m in target.GetMobilesInRange( 15 ) ) - { - if ( m is BaseGuard g ) - { - if ( g.Focus == null ) // idling - { - g.Focus = target; + public BaseGuard(Serial serial) : base(serial) + { + } - --amount; - } - else if ( g.Focus == target && !onlyAdditional ) - { - --amount; - } - } - } + public abstract Mobile Focus{ get; set; } - while ( amount-- > 0 ) - caller.Region.MakeGuard( target ); - } + public static void Spawn(Mobile caller, Mobile target) + { + Spawn(caller, target, 1, false); + } - public BaseGuard( Mobile target ) - { - if ( target != null ) - { - Location = target.Location; - Map = target.Map; + public static void Spawn(Mobile caller, Mobile target, int amount, bool onlyAdditional) + { + if (target == null || target.Deleted) + return; - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); - } - } + foreach (Mobile m in target.GetMobilesInRange(15)) + if (m is BaseGuard g) + { + if (g.Focus == null) // idling + { + g.Focus = target; - public BaseGuard( Serial serial ) : base( serial ) - { - } + --amount; + } + else if (g.Focus == target && !onlyAdditional) + { + --amount; + } + } - public override bool OnBeforeDeath() - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); + while (amount-- > 0) + caller.Region.MakeGuard(target); + } - PlaySound( 0x1FE ); + public override bool OnBeforeDeath() + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 2023); - Delete(); + PlaySound(0x1FE); - return false; - } + Delete(); - public abstract Mobile Focus{ get; set; } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Guards/WarriorGuard.cs b/Scripts/Mobiles/Guards/WarriorGuard.cs index 27f69419f..830c53514 100644 --- a/Scripts/Mobiles/Guards/WarriorGuard.cs +++ b/Scripts/Mobiles/Guards/WarriorGuard.cs @@ -3,361 +3,387 @@ using Server.Items; namespace Server.Mobiles { - public class WarriorGuard : BaseGuard - { - private Timer m_AttackTimer, m_IdleTimer; - - private Mobile m_Focus; - - [Constructible] - public WarriorGuard() : this( null ) - { - } - - public WarriorGuard( Mobile target ) : base( target ) - { - InitStats( 1000, 1000, 1000 ); - Title = "the guard"; - - SpeechHue = Utility.RandomDyedHue(); - - Hue = Utility.RandomSkinHue(); - - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - - switch( Utility.Random( 2 ) ) - { - case 0: AddItem( new LeatherSkirt() ); break; - case 1: AddItem( new LeatherShorts() ); break; - } - - switch( Utility.Random( 5 ) ) - { - case 0: AddItem( new FemaleLeatherChest() ); break; - case 1: AddItem( new FemaleStuddedChest() ); break; - case 2: AddItem( new LeatherBustierArms() ); break; - case 3: AddItem( new StuddedBustierArms() ); break; - case 4: AddItem( new FemalePlateChest() ); break; - } - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - - AddItem( new PlateChest() ); - AddItem( new PlateArms() ); - AddItem( new PlateLegs() ); - - switch( Utility.Random( 3 ) ) - { - case 0: AddItem( new Doublet( Utility.RandomNondyedHue() ) ); break; - case 1: AddItem( new Tunic( Utility.RandomNondyedHue() ) ); break; - case 2: AddItem( new BodySash( Utility.RandomNondyedHue() ) ); break; - } - } - Utility.AssignRandomHair( this ); - - if ( Utility.RandomBool() ) - Utility.AssignRandomFacialHair( this, HairHue ); - - Halberd weapon = new Halberd(); - - weapon.Movable = false; - weapon.Crafter = this; - weapon.Quality = WeaponQuality.Exceptional; - - AddItem( weapon ); - - Container pack = new Backpack(); - - pack.Movable = false; - - pack.DropItem( new Gold( 10, 25 ) ); - - AddItem( pack ); - - Skills[SkillName.Anatomy].Base = 120.0; - Skills[SkillName.Tactics].Base = 120.0; - Skills[SkillName.Swords].Base = 120.0; - Skills[SkillName.MagicResist].Base = 120.0; - Skills[SkillName.DetectHidden].Base = 100.0; - - NextCombatTime = Core.TickCount + 500; - Focus = target; - } - - public WarriorGuard( Serial serial ) : base( serial ) - { - } - - public override bool OnBeforeDeath() - { - if ( m_Focus != null && m_Focus.Alive ) - new AvengeTimer( m_Focus ).Start(); // If a guard dies, three more guards will spawn - - return base.OnBeforeDeath(); - } - - [CommandProperty( AccessLevel.GameMaster )] - public override Mobile Focus - { - get => m_Focus; - set - { - if ( Deleted ) - return; - - Mobile oldFocus = m_Focus; - - if ( oldFocus != value ) - { - m_Focus = value; - - if ( value != null ) - AggressiveAction( value ); - - Combatant = value; - - if ( oldFocus != null && !oldFocus.Alive ) - Say( "Thou hast suffered thy punishment, scoundrel." ); - - if ( value != null ) - Say( 500131 ); // Thou wilt regret thine actions, swine! - - if ( m_AttackTimer != null ) - { - m_AttackTimer.Stop(); - m_AttackTimer = null; - } - - if ( m_IdleTimer != null ) - { - m_IdleTimer.Stop(); - m_IdleTimer = null; - } - - if ( m_Focus != null ) - { - m_AttackTimer = new AttackTimer( this ); - m_AttackTimer.Start(); - ((AttackTimer)m_AttackTimer).DoOnTick(); - } - else - { - m_IdleTimer = new IdleTimer( this ); - m_IdleTimer.Start(); - } - } - else if ( m_Focus == null && m_IdleTimer == null ) - { - m_IdleTimer = new IdleTimer( this ); - m_IdleTimer.Start(); - } - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_Focus ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_Focus = reader.ReadMobile(); - - if ( m_Focus != null ) - { - m_AttackTimer = new AttackTimer( this ); - m_AttackTimer.Start(); - } - else - { - m_IdleTimer = new IdleTimer( this ); - m_IdleTimer.Start(); - } - - break; - } - } - } - - public override void OnAfterDelete() - { - if ( m_AttackTimer != null ) - { - m_AttackTimer.Stop(); - m_AttackTimer = null; - } - - if ( m_IdleTimer != null ) - { - m_IdleTimer.Stop(); - m_IdleTimer = null; - } - - base.OnAfterDelete(); - } - - private class AvengeTimer : Timer - { - private Mobile m_Focus; - - public AvengeTimer( Mobile focus ) : base( TimeSpan.FromSeconds( 2.5 ), TimeSpan.FromSeconds( 1.0 ), 3 ) - { - m_Focus = focus; - } - - protected override void OnTick() - { - Spawn( m_Focus, m_Focus, 1, true ); - } - } - - private class AttackTimer : Timer - { - private WarriorGuard m_Owner; - - public AttackTimer( WarriorGuard owner ) : base( TimeSpan.FromSeconds( 0.25 ), TimeSpan.FromSeconds( 0.1 ) ) - { - m_Owner = owner; - } - - public void DoOnTick() - { - OnTick(); - } - - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } - - m_Owner.Criminal = false; - m_Owner.Kills = 0; - m_Owner.Stam = m_Owner.StamMax; - - Mobile target = m_Owner.Focus; - - if ( target != null && (target.Deleted || !target.Alive || !m_Owner.CanBeHarmful( target )) ) - { - m_Owner.Focus = null; - Stop(); - return; - } - - if ( m_Owner.Weapon is Fists ) - { - m_Owner.Kill(); - Stop(); - return; - } - - if ( target != null && m_Owner.Combatant != target ) - m_Owner.Combatant = target; - - if ( target == null ) - { - Stop(); - } - else - {// - TeleportTo( target ); - target.BoltEffect( 0 ); - - if ( target is BaseCreature creature ) - creature.NoKillAwards = true; - - target.Damage( target.HitsMax, m_Owner ); - target.Kill(); // just in case, maybe Damage is overridden on some shard - - if ( target.Corpse != null && !target.Player ) - target.Corpse.Delete(); - - m_Owner.Focus = null; - Stop(); - }// - /*else if ( !m_Owner.InRange( target, 20 ) ) - { - m_Owner.Focus = null; - } - else if ( !m_Owner.InRange( target, 10 ) || !m_Owner.InLOS( target ) ) - { - TeleportTo( target ); - } - else if ( !m_Owner.InRange( target, 1 ) ) - { - if ( !m_Owner.Move( m_Owner.GetDirectionTo( target ) | Direction.Running ) ) - TeleportTo( target ); - } - else if ( !m_Owner.CanSee( target ) ) - { - if ( !m_Owner.UseSkill( SkillName.DetectHidden ) && Utility.Random( 50 ) == 0 ) - m_Owner.Say( "Reveal!" ); - }*/ - } - - private void TeleportTo( Mobile target ) - { - Point3D from = m_Owner.Location; - Point3D to = target.Location; - - m_Owner.Location = to; - - Effects.SendLocationParticles( EffectItem.Create( from, m_Owner.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( to, m_Owner.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); - - m_Owner.PlaySound( 0x1FE ); - } - } - - private class IdleTimer : Timer - { - private WarriorGuard m_Owner; - private int m_Stage; - - public IdleTimer( WarriorGuard owner ) : base( TimeSpan.FromSeconds( 2.0 ), TimeSpan.FromSeconds( 2.5 ) ) - { - m_Owner = owner; - } - - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } - - if ( (m_Stage++ % 4) == 0 || !m_Owner.Move( m_Owner.Direction ) ) - m_Owner.Direction = (Direction)Utility.Random( 8 ); - - if ( m_Stage > 16 ) - { - Effects.SendLocationParticles( EffectItem.Create( m_Owner.Location, m_Owner.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - m_Owner.PlaySound( 0x1FE ); - - m_Owner.Delete(); - } - } - } - } -} + public class WarriorGuard : BaseGuard + { + private Timer m_AttackTimer, m_IdleTimer; + + private Mobile m_Focus; + + [Constructible] + public WarriorGuard() : this(null) + { + } + + public WarriorGuard(Mobile target) : base(target) + { + InitStats(1000, 1000, 1000); + Title = "the guard"; + + SpeechHue = Utility.RandomDyedHue(); + + Hue = Utility.RandomSkinHue(); + + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + + switch (Utility.Random(2)) + { + case 0: + AddItem(new LeatherSkirt()); + break; + case 1: + AddItem(new LeatherShorts()); + break; + } + + switch (Utility.Random(5)) + { + case 0: + AddItem(new FemaleLeatherChest()); + break; + case 1: + AddItem(new FemaleStuddedChest()); + break; + case 2: + AddItem(new LeatherBustierArms()); + break; + case 3: + AddItem(new StuddedBustierArms()); + break; + case 4: + AddItem(new FemalePlateChest()); + break; + } + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + + AddItem(new PlateChest()); + AddItem(new PlateArms()); + AddItem(new PlateLegs()); + + switch (Utility.Random(3)) + { + case 0: + AddItem(new Doublet(Utility.RandomNondyedHue())); + break; + case 1: + AddItem(new Tunic(Utility.RandomNondyedHue())); + break; + case 2: + AddItem(new BodySash(Utility.RandomNondyedHue())); + break; + } + } + + Utility.AssignRandomHair(this); + + if (Utility.RandomBool()) + Utility.AssignRandomFacialHair(this, HairHue); + + Halberd weapon = new Halberd(); + + weapon.Movable = false; + weapon.Crafter = this; + weapon.Quality = WeaponQuality.Exceptional; + + AddItem(weapon); + + Container pack = new Backpack(); + + pack.Movable = false; + + pack.DropItem(new Gold(10, 25)); + + AddItem(pack); + + Skills[SkillName.Anatomy].Base = 120.0; + Skills[SkillName.Tactics].Base = 120.0; + Skills[SkillName.Swords].Base = 120.0; + Skills[SkillName.MagicResist].Base = 120.0; + Skills[SkillName.DetectHidden].Base = 100.0; + + NextCombatTime = Core.TickCount + 500; + Focus = target; + } + + public WarriorGuard(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public override Mobile Focus + { + get => m_Focus; + set + { + if (Deleted) + return; + + Mobile oldFocus = m_Focus; + + if (oldFocus != value) + { + m_Focus = value; + + if (value != null) + AggressiveAction(value); + + Combatant = value; + + if (oldFocus != null && !oldFocus.Alive) + Say("Thou hast suffered thy punishment, scoundrel."); + + if (value != null) + Say(500131); // Thou wilt regret thine actions, swine! + + if (m_AttackTimer != null) + { + m_AttackTimer.Stop(); + m_AttackTimer = null; + } + + if (m_IdleTimer != null) + { + m_IdleTimer.Stop(); + m_IdleTimer = null; + } + + if (m_Focus != null) + { + m_AttackTimer = new AttackTimer(this); + m_AttackTimer.Start(); + ((AttackTimer)m_AttackTimer).DoOnTick(); + } + else + { + m_IdleTimer = new IdleTimer(this); + m_IdleTimer.Start(); + } + } + else if (m_Focus == null && m_IdleTimer == null) + { + m_IdleTimer = new IdleTimer(this); + m_IdleTimer.Start(); + } + } + } + + public override bool OnBeforeDeath() + { + if (m_Focus != null && m_Focus.Alive) + new AvengeTimer(m_Focus).Start(); // If a guard dies, three more guards will spawn + + return base.OnBeforeDeath(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Focus); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Focus = reader.ReadMobile(); + + if (m_Focus != null) + { + m_AttackTimer = new AttackTimer(this); + m_AttackTimer.Start(); + } + else + { + m_IdleTimer = new IdleTimer(this); + m_IdleTimer.Start(); + } + + break; + } + } + } + + public override void OnAfterDelete() + { + if (m_AttackTimer != null) + { + m_AttackTimer.Stop(); + m_AttackTimer = null; + } + + if (m_IdleTimer != null) + { + m_IdleTimer.Stop(); + m_IdleTimer = null; + } + + base.OnAfterDelete(); + } + + private class AvengeTimer : Timer + { + private Mobile m_Focus; + + public AvengeTimer(Mobile focus) : base(TimeSpan.FromSeconds(2.5), TimeSpan.FromSeconds(1.0), 3) + { + m_Focus = focus; + } + + protected override void OnTick() + { + Spawn(m_Focus, m_Focus, 1, true); + } + } + + private class AttackTimer : Timer + { + private WarriorGuard m_Owner; + + public AttackTimer(WarriorGuard owner) : base(TimeSpan.FromSeconds(0.25), TimeSpan.FromSeconds(0.1)) + { + m_Owner = owner; + } + + public void DoOnTick() + { + OnTick(); + } + + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } + + m_Owner.Criminal = false; + m_Owner.Kills = 0; + m_Owner.Stam = m_Owner.StamMax; + + Mobile target = m_Owner.Focus; + + if (target != null && (target.Deleted || !target.Alive || !m_Owner.CanBeHarmful(target))) + { + m_Owner.Focus = null; + Stop(); + return; + } + + if (m_Owner.Weapon is Fists) + { + m_Owner.Kill(); + Stop(); + return; + } + + if (target != null && m_Owner.Combatant != target) + m_Owner.Combatant = target; + + if (target == null) + { + Stop(); + } + else + { + // + TeleportTo(target); + target.BoltEffect(0); + + if (target is BaseCreature creature) + creature.NoKillAwards = true; + + target.Damage(target.HitsMax, m_Owner); + target.Kill(); // just in case, maybe Damage is overridden on some shard + + if (target.Corpse != null && !target.Player) + target.Corpse.Delete(); + + m_Owner.Focus = null; + Stop(); + } // + + /*else if ( !m_Owner.InRange( target, 20 ) ) + { + m_Owner.Focus = null; + } + else if ( !m_Owner.InRange( target, 10 ) || !m_Owner.InLOS( target ) ) + { + TeleportTo( target ); + } + else if ( !m_Owner.InRange( target, 1 ) ) + { + if ( !m_Owner.Move( m_Owner.GetDirectionTo( target ) | Direction.Running ) ) + TeleportTo( target ); + } + else if ( !m_Owner.CanSee( target ) ) + { + if ( !m_Owner.UseSkill( SkillName.DetectHidden ) && Utility.Random( 50 ) == 0 ) + m_Owner.Say( "Reveal!" ); + }*/ + } + + private void TeleportTo(Mobile target) + { + Point3D from = m_Owner.Location; + Point3D to = target.Location; + + m_Owner.Location = to; + + Effects.SendLocationParticles(EffectItem.Create(from, m_Owner.Map, EffectItem.DefaultDuration), 0x3728, 10, + 10, 2023); + Effects.SendLocationParticles(EffectItem.Create(to, m_Owner.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); + + m_Owner.PlaySound(0x1FE); + } + } + + private class IdleTimer : Timer + { + private WarriorGuard m_Owner; + private int m_Stage; + + public IdleTimer(WarriorGuard owner) : base(TimeSpan.FromSeconds(2.0), TimeSpan.FromSeconds(2.5)) + { + m_Owner = owner; + } + + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } + + if (m_Stage++ % 4 == 0 || !m_Owner.Move(m_Owner.Direction)) + m_Owner.Direction = (Direction)Utility.Random(8); + + if (m_Stage > 16) + { + Effects.SendLocationParticles( + EffectItem.Create(m_Owner.Location, m_Owner.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, 2023); + m_Owner.PlaySound(0x1FE); + + m_Owner.Delete(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/BaseHealer.cs b/Scripts/Mobiles/Healers/BaseHealer.cs index bc75f2a39..5e0710d1f 100644 --- a/Scripts/Mobiles/Healers/BaseHealer.cs +++ b/Scripts/Mobiles/Healers/BaseHealer.cs @@ -1,162 +1,158 @@ using System; using System.Collections.Generic; -using Server.Items; using Server.Gumps; +using Server.Items; namespace Server.Mobiles { - public abstract class BaseHealer : BaseVendor - { - protected override List SBInfos { get; } = new List(); + public abstract class BaseHealer : BaseVendor + { + private static TimeSpan ResurrectDelay = TimeSpan.FromSeconds(2.0); - public override bool IsActiveVendor => false; - public override bool IsInvulnerable => false; + private DateTime m_NextResurrect; - public override void InitSBInfo() - { - } + public BaseHealer() : base(null) + { + if (!IsInvulnerable) + { + AI = AIType.AI_Mage; + ActiveSpeed = 0.2; + PassiveSpeed = 0.8; + RangePerception = DefaultRangePerception; + FightMode = FightMode.Aggressor; + } - public BaseHealer() : base( null ) - { - if ( !IsInvulnerable ) - { - AI = AIType.AI_Mage; - ActiveSpeed = 0.2; - PassiveSpeed = 0.8; - RangePerception = DefaultRangePerception; - FightMode = FightMode.Aggressor; - } + SpeechHue = 0; - SpeechHue = 0; + SetStr(304, 400); + SetDex(102, 150); + SetInt(204, 300); - SetStr( 304, 400 ); - SetDex( 102, 150 ); - SetInt( 204, 300 ); + SetDamage(10, 23); - SetDamage( 10, 23 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Anatomy, 75.0, 97.5); + SetSkill(SkillName.EvalInt, 82.0, 100.0); + SetSkill(SkillName.Healing, 75.0, 97.5); + SetSkill(SkillName.Magery, 82.0, 100.0); + SetSkill(SkillName.MagicResist, 82.0, 100.0); + SetSkill(SkillName.Tactics, 82.0, 100.0); - SetSkill( SkillName.Anatomy, 75.0, 97.5 ); - SetSkill( SkillName.EvalInt, 82.0, 100.0 ); - SetSkill( SkillName.Healing, 75.0, 97.5 ); - SetSkill( SkillName.Magery, 82.0, 100.0 ); - SetSkill( SkillName.MagicResist, 82.0, 100.0 ); - SetSkill( SkillName.Tactics, 82.0, 100.0 ); + Fame = 1000; + Karma = 10000; - Fame = 1000; - Karma = 10000; + PackItem(new Bandage(Utility.RandomMinMax(5, 10))); + PackItem(new HealPotion()); + PackItem(new CurePotion()); + } - PackItem( new Bandage( Utility.RandomMinMax( 5, 10 ) ) ); - PackItem( new HealPotion() ); - PackItem( new CurePotion() ); - } + public BaseHealer(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => VendorShoeType.Sandals; + protected override List SBInfos{ get; } = new List(); - public virtual int GetRobeColor() - { - return Utility.RandomYellowHue(); - } + public override bool IsActiveVendor => false; + public override bool IsInvulnerable => false; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => VendorShoeType.Sandals; - AddItem( new Robe( GetRobeColor() ) ); - } + public virtual bool HealsYoungPlayers => true; - public virtual bool HealsYoungPlayers => true; + public override void InitSBInfo() + { + } - public virtual bool CheckResurrect( Mobile m ) - { - return true; - } + public virtual int GetRobeColor() + { + return Utility.RandomYellowHue(); + } - private DateTime m_NextResurrect; - private static TimeSpan ResurrectDelay = TimeSpan.FromSeconds( 2.0 ); + public override void InitOutfit() + { + base.InitOutfit(); - public virtual void OfferResurrection( Mobile m ) - { - Direction = GetDirectionTo( m ); + AddItem(new Robe(GetRobeColor())); + } - m.PlaySound(0x1F2); - m.FixedEffect( 0x376A, 10, 16 ); + public virtual bool CheckResurrect(Mobile m) + { + return true; + } - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, ResurrectMessage.Healer ) ); - } + public virtual void OfferResurrection(Mobile m) + { + Direction = GetDirectionTo(m); - public virtual void OfferHeal( PlayerMobile m ) - { - Direction = GetDirectionTo( m ); + m.PlaySound(0x1F2); + m.FixedEffect(0x376A, 10, 16); - if ( m.CheckYoungHealTime() ) - { - Say( 501229 ); // You look like you need some healing my child. + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, ResurrectMessage.Healer)); + } - m.PlaySound( 0x1F2 ); - m.FixedEffect( 0x376A, 9, 32 ); + public virtual void OfferHeal(PlayerMobile m) + { + Direction = GetDirectionTo(m); - m.Hits = m.HitsMax; - } - else - { - Say( 501228 ); // I can do no more for you at this time. - } - } + if (m.CheckYoungHealTime()) + { + Say(501229); // You look like you need some healing my child. - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( !m.Frozen && DateTime.UtcNow >= m_NextResurrect && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && InLOS( m ) ) - { - if ( !m.Alive ) - { - m_NextResurrect = DateTime.UtcNow + ResurrectDelay; + m.PlaySound(0x1F2); + m.FixedEffect(0x376A, 9, 32); - if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else if ( CheckResurrect( m ) ) - { - OfferResurrection( m ); - } - } - else if ( HealsYoungPlayers && m.Hits < m.HitsMax && m is PlayerMobile mobile && mobile.Young ) - { - OfferHeal( mobile ); - } - } - } + m.Hits = m.HitsMax; + } + else + { + Say(501228); // I can do no more for you at this time. + } + } - public BaseHealer( Serial serial ) : base( serial ) - { - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (!m.Frozen && DateTime.UtcNow >= m_NextResurrect && InRange(m, 4) && !InRange(oldLocation, 4) && InLOS(m)) + { + if (!m.Alive) + { + m_NextResurrect = DateTime.UtcNow + ResurrectDelay; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - } + if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + else if (CheckResurrect(m)) OfferResurrection(m); + } + else if (HealsYoungPlayers && m.Hits < m.HitsMax && m is PlayerMobile mobile && mobile.Young) + { + OfferHeal(mobile); + } + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + } - if ( !IsInvulnerable ) - { - AI = AIType.AI_Mage; - ActiveSpeed = 0.2; - PassiveSpeed = 0.8; - RangePerception = DefaultRangePerception; - FightMode = FightMode.Aggressor; - } - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + if (!IsInvulnerable) + { + AI = AIType.AI_Mage; + ActiveSpeed = 0.2; + PassiveSpeed = 0.8; + RangePerception = DefaultRangePerception; + FightMode = FightMode.Aggressor; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/EvilHealer.cs b/Scripts/Mobiles/Healers/EvilHealer.cs index 40387702b..28521b573 100644 --- a/Scripts/Mobiles/Healers/EvilHealer.cs +++ b/Scripts/Mobiles/Healers/EvilHealer.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class EvilHealer : BaseHealer - { - public override bool CanTeach => true; + public class EvilHealer : BaseHealer + { + [Constructible] + public EvilHealer() + { + Title = "the healer"; - public override bool CheckTeach( SkillName skill, Mobile from ) - { - if ( !base.CheckTeach( skill, from ) ) - return false; + Karma = -10000; - return ( skill == SkillName.Forensics ) - || ( skill == SkillName.Healing ) - || ( skill == SkillName.SpiritSpeak ) - || ( skill == SkillName.Swords ); - } + SetSkill(SkillName.Forensics, 80.0, 100.0); + SetSkill(SkillName.SpiritSpeak, 80.0, 100.0); + SetSkill(SkillName.Swords, 80.0, 100.0); + } - [Constructible] - public EvilHealer() - { - Title = "the healer"; + public EvilHealer(Serial serial) : base(serial) + { + } - Karma = -10000; + public override bool CanTeach => true; - SetSkill( SkillName.Forensics, 80.0, 100.0 ); - SetSkill( SkillName.SpiritSpeak, 80.0, 100.0 ); - SetSkill( SkillName.Swords, 80.0, 100.0 ); - } + public override bool AlwaysMurderer => true; + public override bool IsActiveVendor => true; - public override bool AlwaysMurderer => true; - public override bool IsActiveVendor => true; + public override bool CheckTeach(SkillName skill, Mobile from) + { + if (!base.CheckTeach(skill, from)) + return false; - public override void InitSBInfo() - { - SBInfos.Add( new SBHealer() ); - } + return skill == SkillName.Forensics + || skill == SkillName.Healing + || skill == SkillName.SpiritSpeak + || skill == SkillName.Swords; + } - public override bool CheckResurrect( Mobile m ) - { - if ( Core.AOS && m.Criminal ) - { - Say( 501222 ); // Thou art a criminal. I shall not resurrect thee. - return false; - } + public override void InitSBInfo() + { + SBInfos.Add(new SBHealer()); + } - return true; - } + public override bool CheckResurrect(Mobile m) + { + if (Core.AOS && m.Criminal) + { + Say(501222); // Thou art a criminal. I shall not resurrect thee. + return false; + } - public EvilHealer( Serial serial ) : base( serial ) - { - } + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/EvilWanderingHealer.cs b/Scripts/Mobiles/Healers/EvilWanderingHealer.cs index 09a373ddb..1480e43e0 100644 --- a/Scripts/Mobiles/Healers/EvilWanderingHealer.cs +++ b/Scripts/Mobiles/Healers/EvilWanderingHealer.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class EvilWanderingHealer : BaseHealer - { - public override bool CanTeach => true; + public class EvilWanderingHealer : BaseHealer + { + [Constructible] + public EvilWanderingHealer() + { + Title = Core.AOS ? "the Priest Of Mondain" : "the evil wandering healer"; + Karma = -10000; - public override bool CheckTeach( SkillName skill, Mobile from ) - { - if ( !base.CheckTeach( skill, from ) ) - return false; + AddItem(new GnarledStaff()); - return ( skill == SkillName.Anatomy ) - || ( skill == SkillName.Camping ) - || ( skill == SkillName.Forensics ) - || ( skill == SkillName.Healing ) - || ( skill == SkillName.SpiritSpeak ); - } + SetSkill(SkillName.Camping, 80.0, 100.0); + SetSkill(SkillName.Forensics, 80.0, 100.0); + SetSkill(SkillName.SpiritSpeak, 80.0, 100.0); + } - [Constructible] - public EvilWanderingHealer() - { - Title = ( Core.AOS ) ? "the Priest Of Mondain" : "the evil wandering healer"; - Karma = -10000; + public EvilWanderingHealer(Serial serial) : base(serial) + { + } - AddItem( new GnarledStaff() ); + public override bool CanTeach => true; - SetSkill( SkillName.Camping, 80.0, 100.0 ); - SetSkill( SkillName.Forensics, 80.0, 100.0 ); - SetSkill( SkillName.SpiritSpeak, 80.0, 100.0 ); - } + public override bool AlwaysMurderer => true; + public override bool ClickTitle => false; // Do not display title in OnSingleClick - public override bool AlwaysMurderer => true; - public override bool ClickTitle => false; // Do not display title in OnSingleClick + public override bool CheckTeach(SkillName skill, Mobile from) + { + if (!base.CheckTeach(skill, from)) + return false; - public override bool CheckResurrect( Mobile m ) - { - if ( Core.AOS && m.Criminal ) - { - Say( 501222 ); // Thou art a criminal. I shall not resurrect thee. - return false; - } + return skill == SkillName.Anatomy + || skill == SkillName.Camping + || skill == SkillName.Forensics + || skill == SkillName.Healing + || skill == SkillName.SpiritSpeak; + } - return true; - } + public override bool CheckResurrect(Mobile m) + { + if (Core.AOS && m.Criminal) + { + Say(501222); // Thou art a criminal. I shall not resurrect thee. + return false; + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + return true; + } - if ( Utility.RandomDouble() < 0.5 ) - c.DropItem( new FragmentOfAMap() ); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public EvilWanderingHealer( Serial serial ) : base( serial ) - { - } + if (Utility.RandomDouble() < 0.5) + c.DropItem(new FragmentOfAMap()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version < 1 && Title == "the wandering healer" && Core.AOS ) - Title = "the priest of Mondain"; - } - } -} + if (version < 1 && Title == "the wandering healer" && Core.AOS) + Title = "the priest of Mondain"; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/FortuneTeller.cs b/Scripts/Mobiles/Healers/FortuneTeller.cs index 61a55a7f0..7b25759bc 100644 --- a/Scripts/Mobiles/Healers/FortuneTeller.cs +++ b/Scripts/Mobiles/Healers/FortuneTeller.cs @@ -2,76 +2,82 @@ using Server.Items; namespace Server.Mobiles { - public class FortuneTeller : BaseHealer - { - public override bool CanTeach => true; + public class FortuneTeller : BaseHealer + { + [Constructible] + public FortuneTeller() + { + Title = "the fortune teller"; - public override bool CheckTeach( SkillName skill, Mobile from ) - { - if ( !base.CheckTeach( skill, from ) ) - return false; + SetSkill(SkillName.Anatomy, 85.0, 100.0); + SetSkill(SkillName.Healing, 90.0, 100.0); + SetSkill(SkillName.Forensics, 75.0, 98.0); + SetSkill(SkillName.SpiritSpeak, 65.0, 88.0); + } - return ( skill == SkillName.Anatomy ) - || ( skill == SkillName.Healing ) - || ( skill == SkillName.Forensics ) - || ( skill == SkillName.SpiritSpeak ); - } + public FortuneTeller(Serial serial) : base(serial) + { + } - [Constructible] - public FortuneTeller() - { - Title = "the fortune teller"; + public override bool CanTeach => true; - SetSkill( SkillName.Anatomy, 85.0, 100.0 ); - SetSkill( SkillName.Healing, 90.0, 100.0 ); - SetSkill( SkillName.Forensics, 75.0, 98.0 ); - SetSkill( SkillName.SpiritSpeak, 65.0, 88.0 ); - } + public override bool IsActiveVendor => true; + public override bool IsInvulnerable => true; - public override bool IsActiveVendor => true; - public override bool IsInvulnerable => true; + public override bool CheckTeach(SkillName skill, Mobile from) + { + if (!base.CheckTeach(skill, from)) + return false; - public override void InitSBInfo() - { - SBInfos.Add( new SBMage() ); - SBInfos.Add( new SBFortuneTeller() ); - } + return skill == SkillName.Anatomy + || skill == SkillName.Healing + || skill == SkillName.Forensics + || skill == SkillName.SpiritSpeak; + } - public override int GetRobeColor() - { - return Utility.RandomBrightHue(); - } + public override void InitSBInfo() + { + SBInfos.Add(new SBMage()); + SBInfos.Add(new SBFortuneTeller()); + } - public override void InitOutfit() - { - base.InitOutfit(); + public override int GetRobeColor() + { + return Utility.RandomBrightHue(); + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new SkullCap( Utility.RandomBrightHue() ) ); break; - case 1: AddItem( new WizardsHat( Utility.RandomBrightHue() ) ); break; - case 2: AddItem( new Bandana( Utility.RandomBrightHue() ) ); break; - } + public override void InitOutfit() + { + base.InitOutfit(); - AddItem( new Spellbook() ); - } + switch (Utility.Random(3)) + { + case 0: + AddItem(new SkullCap(Utility.RandomBrightHue())); + break; + case 1: + AddItem(new WizardsHat(Utility.RandomBrightHue())); + break; + case 2: + AddItem(new Bandana(Utility.RandomBrightHue())); + break; + } - public FortuneTeller( Serial serial ) : base( serial ) - { - } + AddItem(new Spellbook()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/Healer.cs b/Scripts/Mobiles/Healers/Healer.cs index fd2fe8ab0..c0a4df114 100644 --- a/Scripts/Mobiles/Healers/Healer.cs +++ b/Scripts/Mobiles/Healers/Healer.cs @@ -1,81 +1,80 @@ namespace Server.Mobiles { - public class Healer : BaseHealer - { - public override bool CanTeach => true; + public class Healer : BaseHealer + { + [Constructible] + public Healer() + { + Title = "the healer"; - public override bool CheckTeach( SkillName skill, Mobile from ) - { - if ( !base.CheckTeach( skill, from ) ) - return false; + if (!Core.AOS) + NameHue = 0x35; - return ( skill == SkillName.Forensics ) - || ( skill == SkillName.Healing ) - || ( skill == SkillName.SpiritSpeak ) - || ( skill == SkillName.Swords ); - } + SetSkill(SkillName.Forensics, 80.0, 100.0); + SetSkill(SkillName.SpiritSpeak, 80.0, 100.0); + SetSkill(SkillName.Swords, 80.0, 100.0); + } - [Constructible] - public Healer() - { - Title = "the healer"; + public Healer(Serial serial) : base(serial) + { + } - if ( !Core.AOS ) - NameHue = 0x35; + public override bool CanTeach => true; - SetSkill( SkillName.Forensics, 80.0, 100.0 ); - SetSkill( SkillName.SpiritSpeak, 80.0, 100.0 ); - SetSkill( SkillName.Swords, 80.0, 100.0 ); - } + public override bool IsActiveVendor => true; + public override bool IsInvulnerable => true; - public override bool IsActiveVendor => true; - public override bool IsInvulnerable => true; + public override bool CheckTeach(SkillName skill, Mobile from) + { + if (!base.CheckTeach(skill, from)) + return false; - public override void InitSBInfo() - { - SBInfos.Add( new SBHealer() ); - } + return skill == SkillName.Forensics + || skill == SkillName.Healing + || skill == SkillName.SpiritSpeak + || skill == SkillName.Swords; + } - public override bool CheckResurrect( Mobile m ) - { - if ( m.Criminal ) - { - Say( 501222 ); // Thou art a criminal. I shall not resurrect thee. - return false; - } + public override void InitSBInfo() + { + SBInfos.Add(new SBHealer()); + } - if ( m.Kills >= 5 ) - { - Say( 501223 ); // Thou'rt not a decent and good person. I shall not resurrect thee. - return false; - } - if ( m.Karma < 0 ) - { - Say( 501224 ); // Thou hast strayed from the path of virtue, but thou still deservest a second chance. - } + public override bool CheckResurrect(Mobile m) + { + if (m.Criminal) + { + Say(501222); // Thou art a criminal. I shall not resurrect thee. + return false; + } - return true; - } + if (m.Kills >= 5) + { + Say(501223); // Thou'rt not a decent and good person. I shall not resurrect thee. + return false; + } - public Healer( Serial serial ) : base( serial ) - { - } + if (m.Karma < 0) + Say(501224); // Thou hast strayed from the path of virtue, but thou still deservest a second chance. - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Core.AOS && NameHue == 0x35 ) - NameHue = -1; - } - } -} + int version = reader.ReadInt(); + + if (Core.AOS && NameHue == 0x35) + NameHue = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/PricedHealer.cs b/Scripts/Mobiles/Healers/PricedHealer.cs index cdaa844ed..567912940 100644 --- a/Scripts/Mobiles/Healers/PricedHealer.cs +++ b/Scripts/Mobiles/Healers/PricedHealer.cs @@ -2,76 +2,76 @@ using Server.Gumps; namespace Server.Mobiles { - public class PricedHealer : BaseHealer - { - [CommandProperty( AccessLevel.GameMaster )] - public int Price { get; set; } + public class PricedHealer : BaseHealer + { + [Constructible] + public PricedHealer() : this(5000) + { + } - [Constructible] - public PricedHealer() : this( 5000 ) - { - } + [Constructible] + public PricedHealer(int price) + { + Price = price; - [Constructible] - public PricedHealer( int price ) - { - Price = price; + if (!Core.AOS) + NameHue = 0x35; + } - if ( !Core.AOS ) - NameHue = 0x35; - } + public PricedHealer(Serial serial) : base(serial) + { + } - public override bool IsInvulnerable => true; + [CommandProperty(AccessLevel.GameMaster)] + public int Price{ get; set; } - public override void InitSBInfo() - { - } + public override bool IsInvulnerable => true; - public override bool HealsYoungPlayers => false; + public override bool HealsYoungPlayers => false; - public override void OfferResurrection( Mobile m ) - { - Direction = GetDirectionTo( m ); + public override void InitSBInfo() + { + } - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + public override void OfferResurrection(Mobile m) + { + Direction = GetDirectionTo(m); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, this, Price ) ); - } + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - public override bool CheckResurrect( Mobile m ) - { - return true; - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, this, Price)); + } - public PricedHealer( Serial serial ) : base( serial ) - { - } + public override bool CheckResurrect(Mobile m) + { + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( (int) Price ); - } + writer.Write(Price); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Price = reader.ReadInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + Price = reader.ReadInt(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Healers/WanderingHealer.cs b/Scripts/Mobiles/Healers/WanderingHealer.cs index 72ad34084..2298b8582 100644 --- a/Scripts/Mobiles/Healers/WanderingHealer.cs +++ b/Scripts/Mobiles/Healers/WanderingHealer.cs @@ -2,73 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class WanderingHealer : BaseHealer - { - public override bool CanTeach => true; + public class WanderingHealer : BaseHealer + { + [Constructible] + public WanderingHealer() + { + Title = "the wandering healer"; - public override bool CheckTeach( SkillName skill, Mobile from ) - { - if ( !base.CheckTeach( skill, from ) ) - return false; + AddItem(new GnarledStaff()); - return ( skill == SkillName.Anatomy ) - || ( skill == SkillName.Camping ) - || ( skill == SkillName.Forensics ) - || ( skill == SkillName.Healing ) - || ( skill == SkillName.SpiritSpeak ); - } + SetSkill(SkillName.Camping, 80.0, 100.0); + SetSkill(SkillName.Forensics, 80.0, 100.0); + SetSkill(SkillName.SpiritSpeak, 80.0, 100.0); + } - [Constructible] - public WanderingHealer() - { - Title = "the wandering healer"; + public WanderingHealer(Serial serial) : base(serial) + { + } - AddItem( new GnarledStaff() ); + public override bool CanTeach => true; - SetSkill( SkillName.Camping, 80.0, 100.0 ); - SetSkill( SkillName.Forensics, 80.0, 100.0 ); - SetSkill( SkillName.SpiritSpeak, 80.0, 100.0 ); - } + public override bool ClickTitle => false; // Do not display title in OnSingleClick - public override bool ClickTitle => false; // Do not display title in OnSingleClick + public override bool CheckTeach(SkillName skill, Mobile from) + { + if (!base.CheckTeach(skill, from)) + return false; - public override bool CheckResurrect( Mobile m ) - { - if ( m.Criminal ) - { - Say( 501222 ); // Thou art a criminal. I shall not resurrect thee. - return false; - } + return skill == SkillName.Anatomy + || skill == SkillName.Camping + || skill == SkillName.Forensics + || skill == SkillName.Healing + || skill == SkillName.SpiritSpeak; + } - if ( m.Kills >= 5 ) - { - Say( 501223 ); // Thou'rt not a decent and good person. I shall not resurrect thee. - return false; - } - if ( m.Karma < 0 ) - { - Say( 501224 ); // Thou hast strayed from the path of virtue, but thou still deservest a second chance. - } + public override bool CheckResurrect(Mobile m) + { + if (m.Criminal) + { + Say(501222); // Thou art a criminal. I shall not resurrect thee. + return false; + } - return true; - } + if (m.Kills >= 5) + { + Say(501223); // Thou'rt not a decent and good person. I shall not resurrect thee. + return false; + } - public WanderingHealer( Serial serial ) : base( serial ) - { - } + if (m.Karma < 0) + Say(501224); // Thou hast strayed from the path of virtue, but thou still deservest a second chance. - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return true; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/AbysmalHorror.cs b/Scripts/Mobiles/Monsters/AOS/AbysmalHorror.cs index 183ca312a..28685ab97 100644 --- a/Scripts/Mobiles/Monsters/AOS/AbysmalHorror.cs +++ b/Scripts/Mobiles/Monsters/AOS/AbysmalHorror.cs @@ -2,87 +2,91 @@ using Server.Items; namespace Server.Mobiles { - public class AbysmalHorror : BaseCreature - { - public override string CorpseName => "an abysmal horror corpse"; - public override WeaponAbility GetWeaponAbility() => Utility.RandomBool() ? WeaponAbility.MortalStrike : WeaponAbility.WhirlwindAttack; + public class AbysmalHorror : BaseCreature + { + [Constructible] + public AbysmalHorror() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 312; + BaseSoundID = 0x451; - public override bool IgnoreYoungProtection => Core.ML; + SetStr(401, 420); + SetDex(81, 90); + SetInt(401, 420); - public override string DefaultName => "an abysmal horror"; + SetHits(6000); - [Constructible] - public AbysmalHorror() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 312; - BaseSoundID = 0x451; + SetDamage(13, 17); - SetStr( 401, 420 ); - SetDex( 81, 90 ); - SetInt( 401, 420 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetHits( 6000 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 100); + SetResistance(ResistanceType.Cold, 50, 55); + SetResistance(ResistanceType.Poison, 60, 65); + SetResistance(ResistanceType.Energy, 77, 80); - SetDamage( 13, 17 ); + SetSkill(SkillName.EvalInt, 200.0); + SetSkill(SkillName.Magery, 112.6, 117.5); + SetSkill(SkillName.Meditation, 200.0); + SetSkill(SkillName.MagicResist, 117.6, 120.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 84.1, 88.0); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + Fame = 26000; + Karma = -26000; - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 100 ); - SetResistance( ResistanceType.Cold, 50, 55 ); - SetResistance( ResistanceType.Poison, 60, 65 ); - SetResistance( ResistanceType.Energy, 77, 80 ); + VirtualArmor = 54; + } - SetSkill( SkillName.EvalInt, 200.0 ); - SetSkill( SkillName.Magery, 112.6, 117.5 ); - SetSkill( SkillName.Meditation, 200.0 ); - SetSkill( SkillName.MagicResist, 117.6, 120.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 84.1, 88.0 ); + public AbysmalHorror(Serial serial) : base(serial) + { + } - Fame = 26000; - Karma = -26000; + public override string CorpseName => "an abysmal horror corpse"; - VirtualArmor = 54; - } + public override bool IgnoreYoungProtection => Core.ML; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string DefaultName => "an abysmal horror"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => 1; - if ( !Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance( this ) ) - DemonKnight.DistributeArtifact( this ); - } + public override WeaponAbility GetWeaponAbility() + { + return Utility.RandomBool() ? WeaponAbility.MortalStrike : WeaponAbility.WhirlwindAttack; + } - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 1; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public AbysmalHorror( Serial serial ) : base( serial ) - { - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + if (!Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance(this)) + DemonKnight.DistributeArtifact(this); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - if ( BaseSoundID == 357 ) - BaseSoundID = 0x451; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (BaseSoundID == 357) + BaseSoundID = 0x451; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/BoneDemon.cs b/Scripts/Mobiles/Monsters/AOS/BoneDemon.cs index 3996b7a2f..17f0da7c8 100644 --- a/Scripts/Mobiles/Monsters/AOS/BoneDemon.cs +++ b/Scripts/Mobiles/Monsters/AOS/BoneDemon.cs @@ -1,72 +1,72 @@ namespace Server.Mobiles { - public class BoneDemon : BaseCreature - { - public override string CorpseName => "a bone demon corpse"; - public override string DefaultName => "a bone demon"; + public class BoneDemon : BaseCreature + { + [Constructible] + public BoneDemon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 308; + BaseSoundID = 0x48D; - [Constructible] - public BoneDemon() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 308; - BaseSoundID = 0x48D; + SetStr(1000); + SetDex(151, 175); + SetInt(171, 220); - SetStr( 1000 ); - SetDex( 151, 175 ); - SetInt( 171, 220 ); + SetHits(3600); - SetHits( 3600 ); + SetDamage(34, 36); - SetDamage( 34, 36 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 75); + SetResistance(ResistanceType.Fire, 60); + SetResistance(ResistanceType.Cold, 90); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 60); - SetResistance( ResistanceType.Physical, 75 ); - SetResistance( ResistanceType.Fire, 60 ); - SetResistance( ResistanceType.Cold, 90 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 60 ); + SetSkill(SkillName.DetectHidden, 80.0); + SetSkill(SkillName.EvalInt, 77.6, 87.5); + SetSkill(SkillName.Magery, 77.6, 87.5); + SetSkill(SkillName.Meditation, 100.0); + SetSkill(SkillName.MagicResist, 50.1, 75.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - SetSkill( SkillName.DetectHidden, 80.0 ); - SetSkill( SkillName.EvalInt, 77.6, 87.5 ); - SetSkill( SkillName.Magery, 77.6, 87.5 ); - SetSkill( SkillName.Meditation, 100.0 ); - SetSkill( SkillName.MagicResist, 50.1, 75.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + Fame = 20000; + Karma = -20000; - Fame = 20000; - Karma = -20000; + VirtualArmor = 44; + } - VirtualArmor = 44; - } + public BoneDemon(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 8 ); - } + public override string CorpseName => "a bone demon corpse"; + public override string DefaultName => "a bone demon"; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 1; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => 1; - public BoneDemon( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 8); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/CrystalElemental.cs b/Scripts/Mobiles/Monsters/AOS/CrystalElemental.cs index 95bf9bec4..3e7f2b6c6 100644 --- a/Scripts/Mobiles/Monsters/AOS/CrystalElemental.cs +++ b/Scripts/Mobiles/Monsters/AOS/CrystalElemental.cs @@ -2,73 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class CrystalElemental : BaseCreature - { - public override string CorpseName => "a crystal elemental corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; + public class CrystalElemental : BaseCreature + { + [Constructible] + public CrystalElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 300; + BaseSoundID = 278; - public override string DefaultName => "a crystal elemental"; + SetStr(136, 160); + SetDex(51, 65); + SetInt(86, 110); - [Constructible] - public CrystalElemental() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 300; - BaseSoundID = 278; + SetHits(150); - SetStr( 136, 160 ); - SetDex( 51, 65 ); - SetInt( 86, 110 ); + SetDamage(10, 15); - SetHits( 150 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Energy, 20); - SetDamage( 10, 15 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 55, 70); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Energy, 20 ); + SetSkill(SkillName.EvalInt, 70.1, 75.0); + SetSkill(SkillName.Magery, 70.1, 75.0); + SetSkill(SkillName.Meditation, 65.1, 75.0); + SetSkill(SkillName.MagicResist, 80.1, 90.0); + SetSkill(SkillName.Tactics, 75.1, 85.0); + SetSkill(SkillName.Wrestling, 65.1, 75.0); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 55, 70 ); + Fame = 6500; + Karma = -6500; - SetSkill( SkillName.EvalInt, 70.1, 75.0 ); - SetSkill( SkillName.Magery, 70.1, 75.0 ); - SetSkill( SkillName.Meditation, 65.1, 75.0 ); - SetSkill( SkillName.MagicResist, 80.1, 90.0 ); - SetSkill( SkillName.Tactics, 75.1, 85.0 ); - SetSkill( SkillName.Wrestling, 65.1, 75.0 ); + VirtualArmor = 54; + } - Fame = 6500; - Karma = -6500; + public CrystalElemental(Serial serial) : base(serial) + { + } - VirtualArmor = 54; - } + public override string CorpseName => "a crystal elemental corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - } + public override string DefaultName => "a crystal elemental"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 1; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => 1; - public CrystalElemental( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/DarknightCreeper.cs b/Scripts/Mobiles/Monsters/AOS/DarknightCreeper.cs index 2bf570ea2..f8833d37b 100644 --- a/Scripts/Mobiles/Monsters/AOS/DarknightCreeper.cs +++ b/Scripts/Mobiles/Monsters/AOS/DarknightCreeper.cs @@ -2,91 +2,91 @@ using Server.Items; namespace Server.Mobiles { - public class DarknightCreeper : BaseCreature - { - public override string CorpseName => "a darknight creeper corpse"; - public override bool IgnoreYoungProtection => Core.ML; + public class DarknightCreeper : BaseCreature + { + [Constructible] + public DarknightCreeper() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("darknight creeper"); + Body = 313; + BaseSoundID = 0xE0; - [Constructible] - public DarknightCreeper() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "darknight creeper" ); - Body = 313; - BaseSoundID = 0xE0; + SetStr(301, 330); + SetDex(101, 110); + SetInt(301, 330); - SetStr( 301, 330 ); - SetDex( 101, 110 ); - SetInt( 301, 330 ); + SetHits(4000); - SetHits( 4000 ); + SetDamage(22, 26); - SetDamage( 22, 26 ); + SetDamageType(ResistanceType.Physical, 85); + SetDamageType(ResistanceType.Poison, 15); - SetDamageType( ResistanceType.Physical, 85 ); - SetDamageType( ResistanceType.Poison, 15 ); + SetResistance(ResistanceType.Physical, 60); + SetResistance(ResistanceType.Fire, 60); + SetResistance(ResistanceType.Cold, 100); + SetResistance(ResistanceType.Poison, 90); + SetResistance(ResistanceType.Energy, 75); - SetResistance( ResistanceType.Physical, 60 ); - SetResistance( ResistanceType.Fire, 60 ); - SetResistance( ResistanceType.Cold, 100 ); - SetResistance( ResistanceType.Poison, 90 ); - SetResistance( ResistanceType.Energy, 75 ); + SetSkill(SkillName.DetectHidden, 80.0); + SetSkill(SkillName.EvalInt, 118.1, 120.0); + SetSkill(SkillName.Magery, 112.6, 120.0); + SetSkill(SkillName.Meditation, 150.0); + SetSkill(SkillName.Poisoning, 120.0); + SetSkill(SkillName.MagicResist, 90.1, 90.9); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 90.9); + SetSkill(SkillName.Necromancy, 120.1, 130.0); + SetSkill(SkillName.SpiritSpeak, 120.1, 130.0); - SetSkill( SkillName.DetectHidden, 80.0 ); - SetSkill( SkillName.EvalInt, 118.1, 120.0 ); - SetSkill( SkillName.Magery, 112.6, 120.0 ); - SetSkill( SkillName.Meditation, 150.0 ); - SetSkill( SkillName.Poisoning, 120.0 ); - SetSkill( SkillName.MagicResist, 90.1, 90.9 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 90.9 ); - SetSkill( SkillName.Necromancy, 120.1, 130.0 ); - SetSkill( SkillName.SpiritSpeak, 120.1, 130.0 ); + Fame = 22000; + Karma = -22000; - Fame = 22000; - Karma = -22000; + VirtualArmor = 34; + } - VirtualArmor = 34; - } + public DarknightCreeper(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a darknight creeper corpse"; + public override bool IgnoreYoungProtection => Core.ML; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; - if ( !Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance( this ) ) - DemonKnight.DistributeArtifact( this ); - } + public override int TreasureMapLevel => 1; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public override int TreasureMapLevel => 1; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public DarknightCreeper( Serial serial ) : base( serial ) - { - } + if (!Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance(this)) + DemonKnight.DistributeArtifact(this); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 471 ) - BaseSoundID = 0xE0; - } - } -} + if (BaseSoundID == 471) + BaseSoundID = 0xE0; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/DemonKnight.cs b/Scripts/Mobiles/Monsters/AOS/DemonKnight.cs index 738b75c92..d70295724 100644 --- a/Scripts/Mobiles/Monsters/AOS/DemonKnight.cs +++ b/Scripts/Mobiles/Monsters/AOS/DemonKnight.cs @@ -4,287 +4,288 @@ using Server.Items; namespace Server.Mobiles { - public class DemonKnight : BaseCreature - { - public override string CorpseName => "a demon knight corpse"; - public override bool IgnoreYoungProtection => Core.ML; + public class DemonKnight : BaseCreature + { + private static bool m_InHere; - public static Type[] ArtifactRarity10 { get; } = - { - typeof( LegacyOfTheDreadLord ), - typeof( TheTaskmaster ) - }; + [Constructible] + public DemonKnight() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("demon knight"); + Title = "the Dark Father"; + Body = 318; + BaseSoundID = 0x165; - public static Type[] ArtifactRarity11 { get; } = - { - typeof( TheDragonSlayer ), - typeof( ArmorOfFortune ), - typeof( GauntletsOfNobility ), - typeof( HelmOfInsight ), - typeof( HolyKnightsBreastplate ), - typeof( JackalsCollar ), - typeof( LeggingsOfBane ), - typeof( MidnightBracers ), - typeof( OrnateCrownOfTheHarrower ), - typeof( ShadowDancerLeggings ), - typeof( TunicOfFire ), - typeof( VoiceOfTheFallenKing ), - typeof( BraceletOfHealth ), - typeof( OrnamentOfTheMagician ), - typeof( RingOfTheElements ), - typeof( RingOfTheVile ), - typeof( Aegis ), - typeof( ArcaneShield ), - typeof( AxeOfTheHeavens ), - typeof( BladeOfInsanity ), - typeof( BoneCrusher ), - typeof( BreathOfTheDead ), - typeof( Frostbringer ), - typeof( SerpentsFang ), - typeof( StaffOfTheMagi ), - typeof( TheBeserkersMaul ), - typeof( TheDryadBow ), - typeof( DivineCountenance ), - typeof( HatOfTheMagi ), - typeof( HuntersHeaddress ), - typeof( SpiritOfTheTotem ) - }; + SetStr(500); + SetDex(100); + SetInt(1000); - public static Item CreateRandomArtifact() - { - if ( !Core.AOS ) - return null; + SetHits(30000); + SetMana(5000); - int count = ( ArtifactRarity10.Length * 5 ) + ( ArtifactRarity11.Length * 4 ); - int random = Utility.Random( count ); - Type type; + SetDamage(17, 21); - if ( random < ( ArtifactRarity10.Length * 5 ) ) - { - type = ArtifactRarity10[random / 5]; - } - else - { - random -= ArtifactRarity10.Length * 5; - type = ArtifactRarity11[random / 4]; - } + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Fire, 20); + SetDamageType(ResistanceType.Cold, 20); + SetDamageType(ResistanceType.Poison, 20); + SetDamageType(ResistanceType.Energy, 20); - return Loot.Construct( type ); - } + SetResistance(ResistanceType.Physical, 30); + SetResistance(ResistanceType.Fire, 30); + SetResistance(ResistanceType.Cold, 30); + SetResistance(ResistanceType.Poison, 30); + SetResistance(ResistanceType.Energy, 30); - public static Mobile FindRandomPlayer( BaseCreature creature ) - { - List rights = GetLootingRights( creature.DamageEntries, creature.HitsMax ); + SetSkill(SkillName.Necromancy, 120, 120.0); + SetSkill(SkillName.SpiritSpeak, 120.0, 120.0); - for ( int i = rights.Count - 1; i >= 0; --i ) - { - DamageStore ds = rights[i]; + SetSkill(SkillName.DetectHidden, 80.0); + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Magery, 100.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.MagicResist, 150.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 120.0); - if ( !ds.m_HasRight ) - rights.RemoveAt( i ); - } + Fame = 28000; + Karma = -28000; - if ( rights.Count > 0 ) - return rights[Utility.Random( rights.Count )].m_Mobile; + VirtualArmor = 64; + } - return null; - } + public DemonKnight(Serial serial) : base(serial) + { + } - public static void DistributeArtifact( BaseCreature creature ) - { - DistributeArtifact( creature, CreateRandomArtifact() ); - } + public override string CorpseName => "a demon knight corpse"; + public override bool IgnoreYoungProtection => Core.ML; - public static void DistributeArtifact( BaseCreature creature, Item artifact ) - { - DistributeArtifact( FindRandomPlayer( creature ), artifact ); - } + public static Type[] ArtifactRarity10{ get; } = + { + typeof(LegacyOfTheDreadLord), + typeof(TheTaskmaster) + }; - public static void DistributeArtifact( Mobile to ) - { - DistributeArtifact( to, CreateRandomArtifact() ); - } + public static Type[] ArtifactRarity11{ get; } = + { + typeof(TheDragonSlayer), + typeof(ArmorOfFortune), + typeof(GauntletsOfNobility), + typeof(HelmOfInsight), + typeof(HolyKnightsBreastplate), + typeof(JackalsCollar), + typeof(LeggingsOfBane), + typeof(MidnightBracers), + typeof(OrnateCrownOfTheHarrower), + typeof(ShadowDancerLeggings), + typeof(TunicOfFire), + typeof(VoiceOfTheFallenKing), + typeof(BraceletOfHealth), + typeof(OrnamentOfTheMagician), + typeof(RingOfTheElements), + typeof(RingOfTheVile), + typeof(Aegis), + typeof(ArcaneShield), + typeof(AxeOfTheHeavens), + typeof(BladeOfInsanity), + typeof(BoneCrusher), + typeof(BreathOfTheDead), + typeof(Frostbringer), + typeof(SerpentsFang), + typeof(StaffOfTheMagi), + typeof(TheBeserkersMaul), + typeof(TheDryadBow), + typeof(DivineCountenance), + typeof(HatOfTheMagi), + typeof(HuntersHeaddress), + typeof(SpiritOfTheTotem) + }; - public static void DistributeArtifact( Mobile to, Item artifact ) - { - if ( to == null || artifact == null ) - return; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override Poison PoisonImmune => Poison.Lethal; - Container pack = to.Backpack; + public override int TreasureMapLevel => 1; - if ( pack == null || !pack.TryDropItem( to, artifact, false ) ) - to.BankBox.DropItem( artifact ); + public static Item CreateRandomArtifact() + { + if (!Core.AOS) + return null; - to.SendLocalizedMessage( 1062317 ); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. - } + int count = ArtifactRarity10.Length * 5 + ArtifactRarity11.Length * 4; + int random = Utility.Random(count); + Type type; - public static int GetArtifactChance( Mobile boss ) - { - if ( !Core.AOS ) - return 0; + if (random < ArtifactRarity10.Length * 5) + { + type = ArtifactRarity10[random / 5]; + } + else + { + random -= ArtifactRarity10.Length * 5; + type = ArtifactRarity11[random / 4]; + } - int luck = LootPack.GetLuckChanceForKiller( boss ); - int chance; + return Loot.Construct(type); + } - if ( boss is DemonKnight ) - chance = 1500 + (luck / 5); - else - chance = 750 + (luck / 10); + public static Mobile FindRandomPlayer(BaseCreature creature) + { + List rights = GetLootingRights(creature.DamageEntries, creature.HitsMax); - return chance; - } + for (int i = rights.Count - 1; i >= 0; --i) + { + DamageStore ds = rights[i]; - public static bool CheckArtifactChance( Mobile boss ) - { - return GetArtifactChance( boss ) > Utility.Random( 100000 ); - } + if (!ds.m_HasRight) + rights.RemoveAt(i); + } - public override WeaponAbility GetWeaponAbility() - { - switch ( Utility.Random( 3 ) ) - { - default: - case 0: return WeaponAbility.DoubleStrike; - case 1: return WeaponAbility.WhirlwindAttack; - case 2: return WeaponAbility.CrushingBlow; - } - } + if (rights.Count > 0) + return rights[Utility.Random(rights.Count)].m_Mobile; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + return null; + } - if ( !Summoned && !NoKillAwards && CheckArtifactChance( this ) ) - DistributeArtifact( this ); - } + public static void DistributeArtifact(BaseCreature creature) + { + DistributeArtifact(creature, CreateRandomArtifact()); + } - [Constructible] - public DemonKnight() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "demon knight" ); - Title = "the Dark Father"; - Body = 318; - BaseSoundID = 0x165; + public static void DistributeArtifact(BaseCreature creature, Item artifact) + { + DistributeArtifact(FindRandomPlayer(creature), artifact); + } - SetStr( 500 ); - SetDex( 100 ); - SetInt( 1000 ); + public static void DistributeArtifact(Mobile to) + { + DistributeArtifact(to, CreateRandomArtifact()); + } - SetHits( 30000 ); - SetMana( 5000 ); + public static void DistributeArtifact(Mobile to, Item artifact) + { + if (to == null || artifact == null) + return; - SetDamage( 17, 21 ); + Container pack = to.Backpack; - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Fire, 20 ); - SetDamageType( ResistanceType.Cold, 20 ); - SetDamageType( ResistanceType.Poison, 20 ); - SetDamageType( ResistanceType.Energy, 20 ); + if (pack == null || !pack.TryDropItem(to, artifact, false)) + to.BankBox.DropItem(artifact); - SetResistance( ResistanceType.Physical, 30 ); - SetResistance( ResistanceType.Fire, 30 ); - SetResistance( ResistanceType.Cold, 30 ); - SetResistance( ResistanceType.Poison, 30 ); - SetResistance( ResistanceType.Energy, 30 ); + to.SendLocalizedMessage( + 1062317); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. + } - SetSkill( SkillName.Necromancy, 120, 120.0 ); - SetSkill( SkillName.SpiritSpeak, 120.0, 120.0 ); + public static int GetArtifactChance(Mobile boss) + { + if (!Core.AOS) + return 0; - SetSkill( SkillName.DetectHidden, 80.0 ); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Magery, 100.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.MagicResist, 150.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); + int luck = LootPack.GetLuckChanceForKiller(boss); + int chance; - Fame = 28000; - Karma = -28000; + if (boss is DemonKnight) + chance = 1500 + luck / 5; + else + chance = 750 + luck / 10; - VirtualArmor = 64; - } + return chance; + } - public override void GenerateLoot() - { - AddLoot( LootPack.SuperBoss, 2 ); - AddLoot( LootPack.HighScrolls, Utility.RandomMinMax( 6, 60 ) ); - } + public static bool CheckArtifactChance(Mobile boss) + { + return GetArtifactChance(boss) > Utility.Random(100000); + } - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override Poison PoisonImmune => Poison.Lethal; + public override WeaponAbility GetWeaponAbility() + { + switch (Utility.Random(3)) + { + default: + case 0: return WeaponAbility.DoubleStrike; + case 1: return WeaponAbility.WhirlwindAttack; + case 2: return WeaponAbility.CrushingBlow; + } + } - public override int TreasureMapLevel => 1; + public override void OnDeath(Container c) + { + base.OnDeath(c); - private static bool m_InHere; + if (!Summoned && !NoKillAwards && CheckArtifactChance(this)) + DistributeArtifact(this); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( from != null && from != this && !m_InHere ) - { - m_InHere = true; - AOS.Damage( from, this, Utility.RandomMinMax( 8, 20 ), 100, 0, 0, 0, 0 ); + public override void GenerateLoot() + { + AddLoot(LootPack.SuperBoss, 2); + AddLoot(LootPack.HighScrolls, Utility.RandomMinMax(6, 60)); + } - MovingEffect( from, 0xECA, 10, 0, false, false, 0, 0 ); - PlaySound( 0x491 ); + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (from != null && from != this && !m_InHere) + { + m_InHere = true; + AOS.Damage(from, this, Utility.RandomMinMax(8, 20), 100, 0, 0, 0, 0); - if ( 0.05 > Utility.RandomDouble() ) - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( CreateBones_Callback ), from ); + MovingEffect(from, 0xECA, 10, 0, false, false, 0, 0); + PlaySound(0x491); - m_InHere = false; - } - } + if (0.05 > Utility.RandomDouble()) + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(CreateBones_Callback), from); - public virtual void CreateBones_Callback( object state ) - { - Mobile from = (Mobile)state; - Map map = from.Map; + m_InHere = false; + } + } - if ( map == null ) - return; + public virtual void CreateBones_Callback(object state) + { + Mobile from = (Mobile)state; + Map map = from.Map; - int count = Utility.RandomMinMax( 1, 3 ); + if (map == null) + return; - for ( int i = 0; i < count; ++i ) - { - int x = from.X + Utility.RandomMinMax( -1, 1 ); - int y = from.Y + Utility.RandomMinMax( -1, 1 ); - int z = from.Z; + int count = Utility.RandomMinMax(1, 3); - if ( !map.CanFit( x, y, z, 16, false, true ) ) - { - z = map.GetAverageZ( x, y ); + for (int i = 0; i < count; ++i) + { + int x = from.X + Utility.RandomMinMax(-1, 1); + int y = from.Y + Utility.RandomMinMax(-1, 1); + int z = from.Z; - if ( z == from.Z || !map.CanFit( x, y, z, 16, false, true ) ) - continue; - } + if (!map.CanFit(x, y, z, 16, false, true)) + { + z = map.GetAverageZ(x, y); - UnholyBone bone = new UnholyBone - { - Hue = 0, - Name = "unholy bones", - ItemID = Utility.Random(0xECA, 9), - }; + if (z == from.Z || !map.CanFit(x, y, z, 16, false, true)) + continue; + } - bone.MoveToWorld( new Point3D( x, y, z ), map ); - } - } + UnholyBone bone = new UnholyBone + { + Hue = 0, + Name = "unholy bones", + ItemID = Utility.Random(0xECA, 9) + }; - public DemonKnight( Serial serial ) : base( serial ) - { - } + bone.MoveToWorld(new Point3D(x, y, z), map); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/Devourer.cs b/Scripts/Mobiles/Monsters/AOS/Devourer.cs index fe014f511..71a0b6615 100644 --- a/Scripts/Mobiles/Monsters/AOS/Devourer.cs +++ b/Scripts/Mobiles/Monsters/AOS/Devourer.cs @@ -1,72 +1,72 @@ namespace Server.Mobiles { - public class Devourer : BaseCreature - { - public override string CorpseName => "a devourer of souls corpse"; - public override string DefaultName => "a devourer of souls"; + public class Devourer : BaseCreature + { + [Constructible] + public Devourer() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 303; + BaseSoundID = 357; - [Constructible] - public Devourer() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 303; - BaseSoundID = 357; + SetStr(801, 950); + SetDex(126, 175); + SetInt(201, 250); - SetStr( 801, 950 ); - SetDex( 126, 175 ); - SetInt( 201, 250 ); + SetHits(650); - SetHits( 650 ); + SetDamage(22, 26); - SetDamage( 22, 26 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Cold, 20); + SetDamageType(ResistanceType.Energy, 20); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Cold, 20 ); - SetDamageType( ResistanceType.Energy, 20 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 90.1, 105.0); + SetSkill(SkillName.Tactics, 75.1, 85.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 90.1, 105.0 ); - SetSkill( SkillName.Tactics, 75.1, 85.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); + Fame = 9500; + Karma = -9500; - Fame = 9500; - Karma = -9500; + VirtualArmor = 44; - VirtualArmor = 44; + PackNecroReg(24, 45); + } - PackNecroReg( 24, 45 ); - } + public Devourer(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - } + public override string CorpseName => "a devourer of souls corpse"; + public override string DefaultName => "a devourer of souls"; - public override Poison PoisonImmune => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; - public override int Meat => 3; + public override int Meat => 3; - public Devourer( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/FleshGolem.cs b/Scripts/Mobiles/Monsters/AOS/FleshGolem.cs index 2ebb2ac38..593f7e007 100644 --- a/Scripts/Mobiles/Monsters/AOS/FleshGolem.cs +++ b/Scripts/Mobiles/Monsters/AOS/FleshGolem.cs @@ -2,67 +2,71 @@ using Server.Items; namespace Server.Mobiles { - public class FleshGolem : BaseCreature - { - public override string CorpseName => "a flesh golem corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; + public class FleshGolem : BaseCreature + { + [Constructible] + public FleshGolem() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 304; + BaseSoundID = 684; - public override string DefaultName => "a flesh golem"; + SetStr(176, 200); + SetDex(51, 75); + SetInt(46, 70); - [Constructible] - public FleshGolem() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 304; - BaseSoundID = 684; + SetHits(106, 120); - SetStr( 176, 200 ); - SetDex( 51, 75 ); - SetInt( 46, 70 ); + SetDamage(18, 22); - SetHits( 106, 120 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 18, 22 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 50.1, 75.0); + SetSkill(SkillName.Tactics, 55.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 70.0); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 1000; + Karma = -1800; - SetSkill( SkillName.MagicResist, 50.1, 75.0 ); - SetSkill( SkillName.Tactics, 55.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 70.0 ); + VirtualArmor = 34; + } - Fame = 1000; - Karma = -1800; + public FleshGolem(Serial serial) : base(serial) + { + } - VirtualArmor = 34; - } + public override string CorpseName => "a flesh golem corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string DefaultName => "a flesh golem"; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; - public FleshGolem( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/FleshRenderer.cs b/Scripts/Mobiles/Monsters/AOS/FleshRenderer.cs index d9f715828..84d5784e8 100644 --- a/Scripts/Mobiles/Monsters/AOS/FleshRenderer.cs +++ b/Scripts/Mobiles/Monsters/AOS/FleshRenderer.cs @@ -2,112 +2,116 @@ using Server.Items; namespace Server.Mobiles { - public class FleshRenderer : BaseCreature - { - public override string CorpseName => "a fleshrenderer corpse"; - public override WeaponAbility GetWeaponAbility() => Utility.RandomBool() ? WeaponAbility.Dismount : WeaponAbility.ParalyzingBlow; + public class FleshRenderer : BaseCreature + { + [Constructible] + public FleshRenderer() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 315; - public override bool IgnoreYoungProtection => Core.ML; + SetStr(401, 460); + SetDex(201, 210); + SetInt(221, 260); - public override string DefaultName => "a fleshrenderer"; + SetHits(4500); - [Constructible] - public FleshRenderer() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 315; + SetDamage(16, 20); - SetStr( 401, 460 ); - SetDex( 201, 210 ); - SetInt( 221, 260 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetHits( 4500 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 70, 80); - SetDamage( 16, 20 ); + SetSkill(SkillName.DetectHidden, 80.0); + SetSkill(SkillName.MagicResist, 155.1, 160.0); + SetSkill(SkillName.Meditation, 100.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + Fame = 23000; + Karma = -23000; - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 70, 80 ); + VirtualArmor = 24; + } - SetSkill( SkillName.DetectHidden, 80.0 ); - SetSkill( SkillName.MagicResist, 155.1, 160.0 ); - SetSkill( SkillName.Meditation, 100.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + public FleshRenderer(Serial serial) : base(serial) + { + } - Fame = 23000; - Karma = -23000; + public override string CorpseName => "a fleshrenderer corpse"; - VirtualArmor = 24; - } + public override bool IgnoreYoungProtection => Core.ML; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string DefaultName => "a fleshrenderer"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool AutoDispel => true; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override Poison PoisonImmune => Poison.Lethal; - if ( !Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance( this ) ) - DemonKnight.DistributeArtifact( this ); - } + public override int TreasureMapLevel => 1; - public override bool AutoDispel => true; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override Poison PoisonImmune => Poison.Lethal; + public override WeaponAbility GetWeaponAbility() + { + return Utility.RandomBool() ? WeaponAbility.Dismount : WeaponAbility.ParalyzingBlow; + } - public override int TreasureMapLevel => 1; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public override int GetAttackSound() - { - return 0x34C; - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override int GetHurtSound() - { - return 0x354; - } + if (!Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance(this)) + DemonKnight.DistributeArtifact(this); + } - public override int GetAngerSound() - { - return 0x34C; - } + public override int GetAttackSound() + { + return 0x34C; + } - public override int GetIdleSound() - { - return 0x34C; - } + public override int GetHurtSound() + { + return 0x354; + } - public override int GetDeathSound() - { - return 0x354; - } + public override int GetAngerSound() + { + return 0x34C; + } - public FleshRenderer( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 0x34C; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetDeathSound() + { + return 0x354; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - if ( BaseSoundID == 660 ) - BaseSoundID = -1; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (BaseSoundID == 660) + BaseSoundID = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/Gibberling.cs b/Scripts/Mobiles/Monsters/AOS/Gibberling.cs index 55bff4f2b..e104e507e 100644 --- a/Scripts/Mobiles/Monsters/AOS/Gibberling.cs +++ b/Scripts/Mobiles/Monsters/AOS/Gibberling.cs @@ -2,68 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class Gibberling : BaseCreature - { - public override string CorpseName => "a gibberling corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + public class Gibberling : BaseCreature + { + [Constructible] + public Gibberling() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 307; + BaseSoundID = 422; - public override string DefaultName => "a gibberling"; + SetStr(141, 165); + SetDex(101, 125); + SetInt(56, 80); - [Constructible] - public Gibberling() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 307; - BaseSoundID = 422; + SetHits(85, 99); - SetStr( 141, 165 ); - SetDex( 101, 125 ); - SetInt( 56, 80 ); + SetDamage(12, 17); - SetHits( 85, 99 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Fire, 40); + SetDamageType(ResistanceType.Energy, 60); - SetDamage( 12, 17 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Fire, 40 ); - SetDamageType( ResistanceType.Energy, 60 ); + SetSkill(SkillName.MagicResist, 45.1, 70.0); + SetSkill(SkillName.Tactics, 67.6, 92.5); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 1500; + Karma = -1500; - SetSkill( SkillName.MagicResist, 45.1, 70.0 ); - SetSkill( SkillName.Tactics, 67.6, 92.5 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + VirtualArmor = 27; + } - Fame = 1500; - Karma = -1500; + public Gibberling(Serial serial) : base(serial) + { + } - VirtualArmor = 27; - } + public override string CorpseName => "a gibberling corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string DefaultName => "a gibberling"; - public override int TreasureMapLevel => 1; + public override int TreasureMapLevel => 1; - public Gibberling( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/GoreFiend.cs b/Scripts/Mobiles/Monsters/AOS/GoreFiend.cs index 6f4797348..d1e9bb074 100644 --- a/Scripts/Mobiles/Monsters/AOS/GoreFiend.cs +++ b/Scripts/Mobiles/Monsters/AOS/GoreFiend.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - public class GoreFiend : BaseCreature - { - public override string CorpseName => "a gore fiend corpse"; - public override string DefaultName => "a gore fiend"; + public class GoreFiend : BaseCreature + { + [Constructible] + public GoreFiend() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 305; + BaseSoundID = 224; - [Constructible] - public GoreFiend() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 305; - BaseSoundID = 224; + SetStr(161, 185); + SetDex(41, 65); + SetInt(46, 70); - SetStr( 161, 185 ); - SetDex( 41, 65 ); - SetInt( 46, 70 ); + SetHits(97, 111); - SetHits( 97, 111 ); + SetDamage(15, 21); - SetDamage( 15, 21 ); + SetDamageType(ResistanceType.Physical, 85); + SetDamageType(ResistanceType.Poison, 15); - SetDamageType( ResistanceType.Physical, 85 ); - SetDamageType( ResistanceType.Poison, 15 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 5, 15); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 5, 15 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 40.1, 55.0); + SetSkill(SkillName.Tactics, 45.1, 70.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetSkill( SkillName.MagicResist, 40.1, 55.0 ); - SetSkill( SkillName.Tactics, 45.1, 70.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 24; + } - VirtualArmor = 24; - } + public GoreFiend(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a gore fiend corpse"; + public override string DefaultName => "a gore fiend"; - public override int GetDeathSound() - { - return 1218; - } + public override bool BleedImmune => true; - public override bool BleedImmune => true; + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public GoreFiend( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 1218; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/Impaler.cs b/Scripts/Mobiles/Monsters/AOS/Impaler.cs index b3962f27c..f9a9463b9 100644 --- a/Scripts/Mobiles/Monsters/AOS/Impaler.cs +++ b/Scripts/Mobiles/Monsters/AOS/Impaler.cs @@ -2,88 +2,92 @@ using Server.Items; namespace Server.Mobiles { - public class Impaler : BaseCreature - { - public override string CorpseName => "an impaler corpse"; - public override WeaponAbility GetWeaponAbility() => Utility.RandomBool() ? WeaponAbility.MortalStrike : WeaponAbility.BleedAttack; + public class Impaler : BaseCreature + { + [Constructible] + public Impaler() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("impaler"); + Body = 306; + BaseSoundID = 0x2A7; - public override bool IgnoreYoungProtection => Core.ML; + SetStr(190); + SetDex(45); + SetInt(190); - [Constructible] - public Impaler() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "impaler" ); - Body = 306; - BaseSoundID = 0x2A7; + SetHits(5000); - SetStr( 190 ); - SetDex( 45 ); - SetInt( 190 ); + SetDamage(31, 35); - SetHits( 5000 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 31, 35 ); + SetResistance(ResistanceType.Physical, 90); + SetResistance(ResistanceType.Fire, 60); + SetResistance(ResistanceType.Cold, 75); + SetResistance(ResistanceType.Poison, 60); + SetResistance(ResistanceType.Energy, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.DetectHidden, 80.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.Poisoning, 160.0); + SetSkill(SkillName.MagicResist, 100.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 80.0); - SetResistance( ResistanceType.Physical, 90 ); - SetResistance( ResistanceType.Fire, 60 ); - SetResistance( ResistanceType.Cold, 75 ); - SetResistance( ResistanceType.Poison, 60 ); - SetResistance( ResistanceType.Energy, 100 ); + Fame = 24000; + Karma = -24000; - SetSkill( SkillName.DetectHidden, 80.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.Poisoning, 160.0 ); - SetSkill( SkillName.MagicResist, 100.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + VirtualArmor = 49; + } - Fame = 24000; - Karma = -24000; + public Impaler(Serial serial) : base(serial) + { + } - VirtualArmor = 49; - } + public override string CorpseName => "an impaler corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override bool IgnoreYoungProtection => Core.ML; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool AutoDispel => true; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => 0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly; - if ( !Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance( this ) ) - DemonKnight.DistributeArtifact( this ); - } + public override int TreasureMapLevel => 1; - public override bool AutoDispel => true; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => (0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly); + public override WeaponAbility GetWeaponAbility() + { + return Utility.RandomBool() ? WeaponAbility.MortalStrike : WeaponAbility.BleedAttack; + } - public override int TreasureMapLevel => 1; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public Impaler( Serial serial ) : base( serial ) - { - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + if (!Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance(this)) + DemonKnight.DistributeArtifact(this); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - if ( BaseSoundID == 1200 ) - BaseSoundID = 0x2A7; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (BaseSoundID == 1200) + BaseSoundID = 0x2A7; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/MoundOfMaggots.cs b/Scripts/Mobiles/Monsters/AOS/MoundOfMaggots.cs index 085c971b2..1015eab13 100644 --- a/Scripts/Mobiles/Monsters/AOS/MoundOfMaggots.cs +++ b/Scripts/Mobiles/Monsters/AOS/MoundOfMaggots.cs @@ -1,63 +1,63 @@ namespace Server.Mobiles { - public class MoundOfMaggots : BaseCreature - { - public override string CorpseName => "a maggoty corpse"; - public override string DefaultName => "a mound of maggots"; + public class MoundOfMaggots : BaseCreature + { + [Constructible] + public MoundOfMaggots() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 319; + BaseSoundID = 898; - [Constructible] - public MoundOfMaggots() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 319; - BaseSoundID = 898; + SetStr(61, 70); + SetDex(61, 70); + SetInt(10); - SetStr( 61, 70 ); - SetDex( 61, 70 ); - SetInt( 10 ); + SetMana(0); - SetMana( 0 ); + SetDamage(3, 9); - SetDamage( 3, 9 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetResistance(ResistanceType.Physical, 90); + SetResistance(ResistanceType.Poison, 100); - SetResistance( ResistanceType.Physical, 90 ); - SetResistance( ResistanceType.Poison, 100 ); + SetSkill(SkillName.Tactics, 50.0); + SetSkill(SkillName.Wrestling, 50.1, 60.0); - SetSkill( SkillName.Tactics, 50.0 ); - SetSkill( SkillName.Wrestling, 50.1, 60.0 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + VirtualArmor = 24; + } - VirtualArmor = 24; - } + public MoundOfMaggots(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Gems ); - } + public override string CorpseName => "a maggoty corpse"; + public override string DefaultName => "a mound of maggots"; - public override Poison PoisonImmune => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 1; + public override int TreasureMapLevel => 1; - public MoundOfMaggots( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/PatchworkSkeleton.cs b/Scripts/Mobiles/Monsters/AOS/PatchworkSkeleton.cs index 66af431ea..0b94cbcdd 100644 --- a/Scripts/Mobiles/Monsters/AOS/PatchworkSkeleton.cs +++ b/Scripts/Mobiles/Monsters/AOS/PatchworkSkeleton.cs @@ -2,70 +2,74 @@ using Server.Items; namespace Server.Mobiles { - public class PatchworkSkeleton : BaseCreature - { - public override string CorpseName => "a patchwork skeletal corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + public class PatchworkSkeleton : BaseCreature + { + [Constructible] + public PatchworkSkeleton() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 309; + BaseSoundID = 0x48D; - public override string DefaultName => "a patchwork skeleton"; + SetStr(96, 120); + SetDex(71, 95); + SetInt(16, 40); - [Constructible] - public PatchworkSkeleton() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 309; - BaseSoundID = 0x48D; + SetHits(58, 72); - SetStr( 96, 120 ); - SetDex( 71, 95 ); - SetInt( 16, 40 ); + SetDamage(18, 22); - SetHits( 58, 72 ); + SetDamageType(ResistanceType.Physical, 85); + SetDamageType(ResistanceType.Cold, 15); - SetDamage( 18, 22 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40, 50); - SetDamageType( ResistanceType.Physical, 85 ); - SetDamageType( ResistanceType.Cold, 15 ); + SetSkill(SkillName.MagicResist, 70.1, 95.0); + SetSkill(SkillName.Tactics, 55.1, 80.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + Fame = 500; + Karma = -500; - SetSkill( SkillName.MagicResist, 70.1, 95.0 ); - SetSkill( SkillName.Tactics, 55.1, 80.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + VirtualArmor = 54; + } - Fame = 500; - Karma = -500; + public PatchworkSkeleton(Serial serial) : base(serial) + { + } - VirtualArmor = 54; - } + public override string CorpseName => "a patchwork skeletal corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string DefaultName => "a patchwork skeleton"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 1; + public override int TreasureMapLevel => 1; - public PatchworkSkeleton( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/Ravager.cs b/Scripts/Mobiles/Monsters/AOS/Ravager.cs index 49f2c24cc..bd29a6175 100644 --- a/Scripts/Mobiles/Monsters/AOS/Ravager.cs +++ b/Scripts/Mobiles/Monsters/AOS/Ravager.cs @@ -2,64 +2,68 @@ using Server.Items; namespace Server.Mobiles { - public class Ravager : BaseCreature - { - public override string CorpseName => "a ravager corpse"; - public override WeaponAbility GetWeaponAbility() => Utility.RandomBool() ? WeaponAbility.Dismount : WeaponAbility.CrushingBlow; + public class Ravager : BaseCreature + { + [Constructible] + public Ravager() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 314; + BaseSoundID = 357; - public override string DefaultName => "a ravager"; + SetStr(251, 275); + SetDex(101, 125); + SetInt(66, 90); - [Constructible] - public Ravager() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 314; - BaseSoundID = 357; + SetHits(161, 175); - SetStr( 251, 275 ); - SetDex( 101, 125 ); - SetInt( 66, 90 ); + SetDamage(15, 20); - SetHits( 161, 175 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 15, 20 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 50.1, 75.0); + SetSkill(SkillName.Tactics, 75.1, 100.0); + SetSkill(SkillName.Wrestling, 70.1, 90.0); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 3500; + Karma = -3500; - SetSkill( SkillName.MagicResist, 50.1, 75.0 ); - SetSkill( SkillName.Tactics, 75.1, 100.0 ); - SetSkill( SkillName.Wrestling, 70.1, 90.0 ); + VirtualArmor = 54; + } - Fame = 3500; - Karma = -3500; + public Ravager(Serial serial) : base(serial) + { + } - VirtualArmor = 54; - } + public override string CorpseName => "a ravager corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override string DefaultName => "a ravager"; - public Ravager( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return Utility.RandomBool() ? WeaponAbility.Dismount : WeaponAbility.CrushingBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/Revenant.cs b/Scripts/Mobiles/Monsters/AOS/Revenant.cs index a47ef887c..a0d7174a8 100644 --- a/Scripts/Mobiles/Monsters/AOS/Revenant.cs +++ b/Scripts/Mobiles/Monsters/AOS/Revenant.cs @@ -4,178 +4,181 @@ using Server.Targeting; namespace Server.Mobiles { - public class Revenant : BaseCreature - { - private Mobile m_Target; - private DateTime m_ExpireTime; + public class Revenant : BaseCreature + { + private DateTime m_ExpireTime; + private Mobile m_Target; - public override void DisplayPaperdollTo( Mobile to ) - { - // Do nothing - } + public Revenant(Mobile caster, Mobile target, TimeSpan duration) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, + 0.18, 0.36) + { + Body = 400; + Hue = 1; + // TODO: Sound values? - public override Mobile ConstantFocus => m_Target; - public override bool NoHouseRestrictions => true; + double scalar = caster.Skills[SkillName.SpiritSpeak].Value * 0.01; - public override double DispelDifficulty => 80.0; - public override double DispelFocus => 20.0; + m_Target = target; + m_ExpireTime = DateTime.UtcNow + duration; - public override string DefaultName => "a revenant"; + SetStr(200); + SetDex(150); + SetInt(150); - public Revenant( Mobile caster, Mobile target, TimeSpan duration ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.18, 0.36 ) - { - Body = 400; - Hue = 1; - // TODO: Sound values? + SetDamage(16, 17); - double scalar = caster.Skills[SkillName.SpiritSpeak].Value * 0.01; + // Bestiary says 50 phys 50 cold, animal lore says differently + SetDamageType(ResistanceType.Physical, 100); - m_Target = target; - m_ExpireTime = DateTime.UtcNow + duration; + SetSkill(SkillName.MagicResist, 100.0 * scalar); // magic resist is absolute value of spiritspeak + SetSkill(SkillName.Tactics, 100.0); // always 100 + SetSkill(SkillName.Swords, + 100.0 * scalar); // not displayed in animal lore but tests clearly show this is influenced + SetSkill(SkillName.DetectHidden, 75.0 * scalar); - SetStr( 200 ); - SetDex( 150 ); - SetInt( 150 ); + scalar /= 1.2; - SetDamage( 16, 17 ); + SetResistance(ResistanceType.Physical, 40 + (int)(20 * scalar), 50 + (int)(20 * scalar)); + SetResistance(ResistanceType.Cold, 40 + (int)(20 * scalar), 50 + (int)(20 * scalar)); + SetResistance(ResistanceType.Fire, (int)(20 * scalar)); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40 + (int)(20 * scalar), 50 + (int)(20 * scalar)); - // Bestiary says 50 phys 50 cold, animal lore says differently - SetDamageType( ResistanceType.Physical, 100 ); + Fame = 0; + Karma = 0; - SetSkill( SkillName.MagicResist, 100.0 * scalar ); // magic resist is absolute value of spiritspeak - SetSkill( SkillName.Tactics, 100.0 ); // always 100 - SetSkill( SkillName.Swords, 100.0 * scalar ); // not displayed in animal lore but tests clearly show this is influenced - SetSkill( SkillName.DetectHidden, 75.0 * scalar ); + ControlSlots = 3; - scalar /= 1.2; + VirtualArmor = 32; - SetResistance( ResistanceType.Physical, 40 + (int)(20 * scalar), 50 + (int)(20 * scalar) ); - SetResistance( ResistanceType.Cold, 40 + (int)(20 * scalar), 50 + (int)(20 * scalar) ); - SetResistance( ResistanceType.Fire, (int)(20 * scalar) ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40 + (int)(20 * scalar), 50 + (int)(20 * scalar) ); + Item shroud = new DeathShroud(); - Fame = 0; - Karma = 0; + shroud.Hue = 0x455; - ControlSlots = 3; + shroud.Movable = false; - VirtualArmor = 32; + AddItem(shroud); - Item shroud = new DeathShroud(); + Halberd weapon = new Halberd(); - shroud.Hue = 0x455; + weapon.Hue = 1; + weapon.Movable = false; - shroud.Movable = false; + AddItem(weapon); + } - AddItem( shroud ); + public Revenant(Serial serial) : base(serial) + { + } - Halberd weapon = new Halberd(); + public override Mobile ConstantFocus => m_Target; + public override bool NoHouseRestrictions => true; - weapon.Hue = 1; - weapon.Movable = false; + public override double DispelDifficulty => 80.0; + public override double DispelFocus => 20.0; - AddItem( weapon ); - } + public override string DefaultName => "a revenant"; - public override bool AlwaysMurderer => true; + public override bool AlwaysMurderer => true; - public override bool BleedImmune => true; - public override bool BardImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override bool BardImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public override void OnThink() - { - if ( !m_Target.Alive || DateTime.UtcNow > m_ExpireTime ) - { - Kill(); - return; - } + public override void DisplayPaperdollTo(Mobile to) + { + // Do nothing + } - if ( Map != m_Target.Map || !InRange( m_Target, 15 ) ) - { - Map fromMap = Map; - Point3D from = Location; + public override void OnThink() + { + if (!m_Target.Alive || DateTime.UtcNow > m_ExpireTime) + { + Kill(); + return; + } - Map toMap = m_Target.Map; - Point3D to = m_Target.Location; + if (Map != m_Target.Map || !InRange(m_Target, 15)) + { + Map fromMap = Map; + Point3D from = Location; - if ( toMap != null ) - { - for ( int i = 0; i < 5; ++i ) - { - Point3D loc = new Point3D( to.X - 4 + Utility.Random( 9 ), to.Y - 4 + Utility.Random( 9 ), to.Z ); + Map toMap = m_Target.Map; + Point3D to = m_Target.Location; - if ( toMap.CanSpawnMobile( loc ) ) - { - to = loc; - break; - } + if (toMap != null) + for (int i = 0; i < 5; ++i) + { + Point3D loc = new Point3D(to.X - 4 + Utility.Random(9), to.Y - 4 + Utility.Random(9), to.Z); - loc.Z = toMap.GetAverageZ( loc.X, loc.Y ); + if (toMap.CanSpawnMobile(loc)) + { + to = loc; + break; + } - if ( toMap.CanSpawnMobile( loc ) ) - { - to = loc; - break; - } - } - } + loc.Z = toMap.GetAverageZ(loc.X, loc.Y); - Map = toMap; - Location = to; + if (toMap.CanSpawnMobile(loc)) + { + to = loc; + break; + } + } - ProcessDelta(); + Map = toMap; + Location = to; - Effects.SendLocationParticles( EffectItem.Create( from, fromMap, EffectItem.DefaultDuration ), 0x3728, 1, 13, 37, 7, 5023, 0 ); - FixedParticles( 0x3728, 1, 13, 5023, 37, 7, EffectLayer.Waist ); + ProcessDelta(); - PlaySound( 0x37D ); - } + Effects.SendLocationParticles(EffectItem.Create(from, fromMap, EffectItem.DefaultDuration), 0x3728, 1, 13, + 37, 7, 5023, 0); + FixedParticles(0x3728, 1, 13, 5023, 37, 7, EffectLayer.Waist); - if (m_Target.Hidden && InRange(m_Target, 3) && Core.TickCount - NextSkillTime >= 0 && UseSkill(SkillName.DetectHidden)) - { - Target targ = Target; + PlaySound(0x37D); + } - targ?.Invoke( this, this ); - } + if (m_Target.Hidden && InRange(m_Target, 3) && Core.TickCount - NextSkillTime >= 0 && + UseSkill(SkillName.DetectHidden)) + { + Target targ = Target; - Combatant = m_Target; - FocusMob = m_Target; + targ?.Invoke(this, this); + } - if ( AIObject != null ) - AIObject.Action = ActionType.Combat; + Combatant = m_Target; + FocusMob = m_Target; - base.OnThink(); - } + if (AIObject != null) + AIObject.Action = ActionType.Combat; - public override bool OnBeforeDeath() - { - Effects.PlaySound( Location, Map, 0x10B ); - Effects.SendLocationParticles( EffectItem.Create( Location, Map, TimeSpan.FromSeconds( 10.0 ) ), 0x37CC, 1, 50, 2101, 7, 9909, 0 ); + base.OnThink(); + } - Delete(); - return false; - } + public override bool OnBeforeDeath() + { + Effects.PlaySound(Location, Map, 0x10B); + Effects.SendLocationParticles(EffectItem.Create(Location, Map, TimeSpan.FromSeconds(10.0)), 0x37CC, 1, 50, 2101, + 7, 9909, 0); - public Revenant( Serial serial ) : base( serial ) - { - } + Delete(); + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } - } -} + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/ShadowKnight.cs b/Scripts/Mobiles/Monsters/AOS/ShadowKnight.cs index a1a079064..bb43140c9 100644 --- a/Scripts/Mobiles/Monsters/AOS/ShadowKnight.cs +++ b/Scripts/Mobiles/Monsters/AOS/ShadowKnight.cs @@ -3,186 +3,191 @@ using Server.Items; namespace Server.Mobiles { - public class ShadowKnight : BaseCreature - { - public override string CorpseName => "a shadow knight corpse"; - public override WeaponAbility GetWeaponAbility() => Utility.RandomBool() ? WeaponAbility.ConcussionBlow : WeaponAbility.CrushingBlow; + public class ShadowKnight : BaseCreature + { + private bool m_HasTeleportedAway; - public override bool IgnoreYoungProtection => Core.ML; + private Timer m_SoundTimer; - [Constructible] - public ShadowKnight() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "shadow knight" ); - Title = "the Shadow Knight"; - Body = 311; + [Constructible] + public ShadowKnight() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("shadow knight"); + Title = "the Shadow Knight"; + Body = 311; - SetStr( 250 ); - SetDex( 100 ); - SetInt( 100 ); + SetStr(250); + SetDex(100); + SetInt(100); - SetHits( 2000 ); + SetHits(2000); - SetDamage( 20, 30 ); + SetDamage(20, 30); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Cold, 40 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Cold, 40); - SetResistance( ResistanceType.Physical, 90 ); - SetResistance( ResistanceType.Fire, 65 ); - SetResistance( ResistanceType.Cold, 75 ); - SetResistance( ResistanceType.Poison, 75 ); - SetResistance( ResistanceType.Energy, 55 ); + SetResistance(ResistanceType.Physical, 90); + SetResistance(ResistanceType.Fire, 65); + SetResistance(ResistanceType.Cold, 75); + SetResistance(ResistanceType.Poison, 75); + SetResistance(ResistanceType.Energy, 55); - SetSkill( SkillName.Chivalry, 120.0 ); - SetSkill( SkillName.DetectHidden, 80.0 ); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Magery, 100.0 ); - SetSkill( SkillName.Meditation, 100.0 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + SetSkill(SkillName.Chivalry, 120.0); + SetSkill(SkillName.DetectHidden, 80.0); + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Magery, 100.0); + SetSkill(SkillName.Meditation, 100.0); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - Fame = 25000; - Karma = -25000; + Fame = 25000; + Karma = -25000; - VirtualArmor = 54; - } + VirtualArmor = 54; + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public ShadowKnight(Serial serial) : base(serial) + { + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string CorpseName => "a shadow knight corpse"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool IgnoreYoungProtection => Core.ML; - if ( !Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance( this ) ) - DemonKnight.DistributeArtifact( this ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override int GetIdleSound() - { - return 0x2CE; - } + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool AreaPeaceImmune => Core.SE; + public override Poison PoisonImmune => Poison.Lethal; - public override int GetDeathSound() - { - return 0x2C1; - } + public override int TreasureMapLevel => 1; - public override int GetHurtSound() - { - return 0x2D1; - } + public override WeaponAbility GetWeaponAbility() + { + return Utility.RandomBool() ? WeaponAbility.ConcussionBlow : WeaponAbility.CrushingBlow; + } - public override int GetAttackSound() - { - return 0x2C8; - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - private Timer m_SoundTimer; - private bool m_HasTeleportedAway; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override void OnCombatantChange() - { - base.OnCombatantChange(); + if (!Summoned && !NoKillAwards && DemonKnight.CheckArtifactChance(this)) + DemonKnight.DistributeArtifact(this); + } - if ( Hidden && Combatant != null ) - Combatant = null; - } + public override int GetIdleSound() + { + return 0x2CE; + } - public virtual void SendTrackingSound() - { - if ( Hidden ) - { - Effects.PlaySound( Location, Map, 0x2C8 ); - Combatant = null; - } - else - { - Frozen = false; + public override int GetDeathSound() + { + return 0x2C1; + } - m_SoundTimer?.Stop(); + public override int GetHurtSound() + { + return 0x2D1; + } - m_SoundTimer = null; - } - } + public override int GetAttackSound() + { + return 0x2C8; + } - public override void OnThink() - { - if ( !m_HasTeleportedAway && Hits < (HitsMax / 2) ) - { - Map map = Map; + public override void OnCombatantChange() + { + base.OnCombatantChange(); - if ( map != null ) - { - // try 10 times to find a teleport spot - for ( int i = 0; i < 10; ++i ) - { - int x = X + (Utility.RandomMinMax( 5, 10 ) * (Utility.RandomBool() ? 1 : -1)); - int y = Y + (Utility.RandomMinMax( 5, 10 ) * (Utility.RandomBool() ? 1 : -1)); - int z = Z; + if (Hidden && Combatant != null) + Combatant = null; + } - if ( !map.CanFit( x, y, z, 16, false, false ) ) - continue; + public virtual void SendTrackingSound() + { + if (Hidden) + { + Effects.PlaySound(Location, Map, 0x2C8); + Combatant = null; + } + else + { + Frozen = false; - Point3D from = Location; - Point3D to = new Point3D( x, y, z ); + m_SoundTimer?.Stop(); - if ( !InLOS( to ) ) - continue; + m_SoundTimer = null; + } + } - Location = to; - ProcessDelta(); - Hidden = true; - Combatant = null; + public override void OnThink() + { + if (!m_HasTeleportedAway && Hits < HitsMax / 2) + { + Map map = Map; - Effects.SendLocationParticles( EffectItem.Create( from, map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( to, map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); + if (map != null) + for (int i = 0; i < 10; ++i) + { + int x = X + Utility.RandomMinMax(5, 10) * (Utility.RandomBool() ? 1 : -1); + int y = Y + Utility.RandomMinMax(5, 10) * (Utility.RandomBool() ? 1 : -1); + int z = Z; - Effects.PlaySound( to, map, 0x1FE ); + if (!map.CanFit(x, y, z, 16, false, false)) + continue; - m_HasTeleportedAway = true; - m_SoundTimer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 2.5 ), SendTrackingSound ); + Point3D from = Location; + Point3D to = new Point3D(x, y, z); - Frozen = true; + if (!InLOS(to)) + continue; - break; - } - } - } + Location = to; + ProcessDelta(); + Hidden = true; + Combatant = null; - base.OnThink(); - } + Effects.SendLocationParticles(EffectItem.Create(from, map, EffectItem.DefaultDuration), 0x3728, 10, + 10, 2023); + Effects.SendLocationParticles(EffectItem.Create(to, map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool AreaPeaceImmune => Core.SE; - public override Poison PoisonImmune => Poison.Lethal; + Effects.PlaySound(to, map, 0x1FE); - public override int TreasureMapLevel => 1; + m_HasTeleportedAway = true; + m_SoundTimer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(2.5), + SendTrackingSound); - public ShadowKnight( Serial serial ) : base( serial ) - { - } + Frozen = true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + break; + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + base.OnThink(); + } - if ( BaseSoundID == 357 ) - BaseSoundID = -1; - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (BaseSoundID == 357) + BaseSoundID = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/SkitteringHopper.cs b/Scripts/Mobiles/Monsters/AOS/SkitteringHopper.cs index dcb87271d..c2ee8e809 100644 --- a/Scripts/Mobiles/Monsters/AOS/SkitteringHopper.cs +++ b/Scripts/Mobiles/Monsters/AOS/SkitteringHopper.cs @@ -1,65 +1,65 @@ namespace Server.Mobiles { - public class SkitteringHopper : BaseCreature - { - public override string CorpseName => "a skittering hopper corpse"; - public override string DefaultName => "a skittering hopper"; + public class SkitteringHopper : BaseCreature + { + [Constructible] + public SkitteringHopper() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 302; + BaseSoundID = 959; - [Constructible] - public SkitteringHopper() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 302; - BaseSoundID = 959; + SetStr(41, 65); + SetDex(91, 115); + SetInt(26, 50); - SetStr( 41, 65 ); - SetDex( 91, 115 ); - SetInt( 26, 50 ); + SetHits(31, 45); - SetHits( 31, 45 ); + SetDamage(3, 5); - SetDamage( 3, 5 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 30.1, 45.0); + SetSkill(SkillName.Tactics, 45.1, 70.0); + SetSkill(SkillName.Wrestling, 40.1, 60.0); - SetSkill( SkillName.MagicResist, 30.1, 45.0 ); - SetSkill( SkillName.Tactics, 45.1, 70.0 ); - SetSkill( SkillName.Wrestling, 40.1, 60.0 ); + Fame = 300; + Karma = 0; - Fame = 300; - Karma = 0; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -12.9; - Tamable = true; - ControlSlots = 1; - MinTameSkill = -12.9; + VirtualArmor = 12; + } - VirtualArmor = 12; - } + public SkitteringHopper(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a skittering hopper corpse"; + public override string DefaultName => "a skittering hopper"; - public override int TreasureMapLevel => 1; + public override int TreasureMapLevel => 1; - public SkitteringHopper( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/Treefellow.cs b/Scripts/Mobiles/Monsters/AOS/Treefellow.cs index 20056d6ea..f853fbf94 100644 --- a/Scripts/Mobiles/Monsters/AOS/Treefellow.cs +++ b/Scripts/Mobiles/Monsters/AOS/Treefellow.cs @@ -2,85 +2,89 @@ using Server.Items; namespace Server.Mobiles { - public class Treefellow : BaseCreature - { - public override string CorpseName => "a treefellow corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + public class Treefellow : BaseCreature + { + [Constructible] + public Treefellow() : base(AIType.AI_Melee, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 301; - public override string DefaultName => "a treefellow"; + SetStr(196, 220); + SetDex(31, 55); + SetInt(66, 90); - [Constructible] - public Treefellow() : base( AIType.AI_Melee, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 301; + SetHits(118, 132); - SetStr( 196, 220 ); - SetDex( 31, 55 ); - SetInt( 66, 90 ); + SetDamage(12, 16); - SetHits( 118, 132 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 12, 16 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 30, 35); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 40.1, 55.0); + SetSkill(SkillName.Tactics, 65.1, 90.0); + SetSkill(SkillName.Wrestling, 65.1, 85.0); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 30, 35 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 500; + Karma = 1500; - SetSkill( SkillName.MagicResist, 40.1, 55.0 ); - SetSkill( SkillName.Tactics, 65.1, 90.0 ); - SetSkill( SkillName.Wrestling, 65.1, 85.0 ); + VirtualArmor = 24; + PackItem(new Log(Utility.RandomMinMax(23, 34))); + } - Fame = 500; - Karma = 1500; + public Treefellow(Serial serial) : base(serial) + { + } - VirtualArmor = 24; - PackItem( new Log( Utility.RandomMinMax( 23, 34 ) ) ); - } + public override string CorpseName => "a treefellow corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string DefaultName => "a treefellow"; - public override int GetIdleSound() - { - return 443; - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override int GetDeathSound() - { - return 31; - } + public override bool BleedImmune => true; - public override int GetAttackSound() - { - return 672; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - public override bool BleedImmune => true; + public override int GetIdleSound() + { + return 443; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override int GetDeathSound() + { + return 31; + } - public Treefellow( Serial serial ) : base( serial ) - { - } + public override int GetAttackSound() + { + return 672; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - if ( BaseSoundID == 442 ) - BaseSoundID = -1; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (BaseSoundID == 442) + BaseSoundID = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/VampireBat.cs b/Scripts/Mobiles/Monsters/AOS/VampireBat.cs index 957bc01ac..f481fe210 100644 --- a/Scripts/Mobiles/Monsters/AOS/VampireBat.cs +++ b/Scripts/Mobiles/Monsters/AOS/VampireBat.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class VampireBat : BaseCreature - { - public override string CorpseName => "a vampire bat corpse"; - public override string DefaultName => "a vampire bat"; + public class VampireBat : BaseCreature + { + [Constructible] + public VampireBat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 317; + BaseSoundID = 0x270; - [Constructible] - public VampireBat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 317; - BaseSoundID = 0x270; + SetStr(91, 110); + SetDex(91, 115); + SetInt(26, 50); - SetStr( 91, 110 ); - SetDex( 91, 115 ); - SetInt( 26, 50 ); + SetHits(55, 66); - SetHits( 55, 66 ); + SetDamage(7, 9); - SetDamage( 7, 9 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.MagicResist, 70.1, 95.0); + SetSkill(SkillName.Tactics, 55.1, 80.0); + SetSkill(SkillName.Wrestling, 30.1, 55.0); - SetSkill( SkillName.MagicResist, 70.1, 95.0 ); - SetSkill( SkillName.Tactics, 55.1, 80.0 ); - SetSkill( SkillName.Wrestling, 30.1, 55.0 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + VirtualArmor = 14; + } - VirtualArmor = 14; - } + public VampireBat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a vampire bat corpse"; + public override string DefaultName => "a vampire bat"; - public override int GetIdleSound() - { - return 0x29B; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public VampireBat( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 0x29B; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/WailingBanshee.cs b/Scripts/Mobiles/Monsters/AOS/WailingBanshee.cs index e0370a40f..1379c2b9c 100644 --- a/Scripts/Mobiles/Monsters/AOS/WailingBanshee.cs +++ b/Scripts/Mobiles/Monsters/AOS/WailingBanshee.cs @@ -2,68 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class WailingBanshee : BaseCreature - { - public override string CorpseName => "a wailing banshee corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.MortalStrike; + public class WailingBanshee : BaseCreature + { + [Constructible] + public WailingBanshee() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 310; + BaseSoundID = 0x482; - public override string DefaultName => "a wailing banshee"; + SetStr(126, 150); + SetDex(76, 100); + SetInt(86, 110); - [Constructible] - public WailingBanshee() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 310; - BaseSoundID = 0x482; + SetHits(76, 90); - SetStr( 126, 150 ); - SetDex( 76, 100 ); - SetInt( 86, 110 ); + SetDamage(10, 14); - SetHits( 76, 90 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 60); + SetDamageType(ResistanceType.Poison, 20); - SetDamage( 10, 14 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 40, 50); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 60 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetSkill(SkillName.MagicResist, 70.1, 95.0); + SetSkill(SkillName.Tactics, 45.1, 70.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + Fame = 1500; + Karma = -1500; - SetSkill( SkillName.MagicResist, 70.1, 95.0 ); - SetSkill( SkillName.Tactics, 45.1, 70.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + VirtualArmor = 19; + } - Fame = 1500; - Karma = -1500; + public WailingBanshee(Serial serial) : base(serial) + { + } - VirtualArmor = 19; - } + public override string CorpseName => "a wailing banshee corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string DefaultName => "a wailing banshee"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public WailingBanshee( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.MortalStrike; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/AOS/WandererOfTheVoid.cs b/Scripts/Mobiles/Monsters/AOS/WandererOfTheVoid.cs index 8fa57a067..84217c13d 100644 --- a/Scripts/Mobiles/Monsters/AOS/WandererOfTheVoid.cs +++ b/Scripts/Mobiles/Monsters/AOS/WandererOfTheVoid.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class WandererOfTheVoid : BaseCreature - { - public override string CorpseName => "a wanderer of the void corpse"; - public override string DefaultName => "a wanderer of the void"; + public class WandererOfTheVoid : BaseCreature + { + [Constructible] + public WandererOfTheVoid() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 316; + BaseSoundID = 377; - [Constructible] - public WandererOfTheVoid() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 316; - BaseSoundID = 377; + SetStr(111, 200); + SetDex(101, 125); + SetInt(301, 390); - SetStr( 111, 200 ); - SetDex( 101, 125 ); - SetInt( 301, 390 ); + SetHits(351, 400); - SetHits( 351, 400 ); + SetDamage(11, 13); - SetDamage( 11, 13 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 15); + SetDamageType(ResistanceType.Energy, 85); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 15 ); - SetDamageType( ResistanceType.Energy, 85 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 50, 75); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 50, 75 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 60.1, 70.0); + SetSkill(SkillName.Magery, 60.1, 70.0); + SetSkill(SkillName.Meditation, 60.1, 70.0); + SetSkill(SkillName.MagicResist, 50.1, 75.0); + SetSkill(SkillName.Tactics, 60.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 70.0); - SetSkill( SkillName.EvalInt, 60.1, 70.0 ); - SetSkill( SkillName.Magery, 60.1, 70.0 ); - SetSkill( SkillName.Meditation, 60.1, 70.0 ); - SetSkill( SkillName.MagicResist, 50.1, 75.0 ); - SetSkill( SkillName.Tactics, 60.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 70.0 ); + Fame = 20000; + Karma = -20000; - Fame = 20000; - Karma = -20000; + VirtualArmor = 44; - VirtualArmor = 44; + int count = Utility.RandomMinMax(2, 3); - int count = Utility.RandomMinMax( 2, 3 ); + for (int i = 0; i < count; ++i) + PackItem(new TreasureMap(3, Map.Trammel)); + } - for ( int i = 0; i < count; ++i ) - PackItem( new TreasureMap( 3, Map.Trammel ) ); - } + public WandererOfTheVoid(Serial serial) : base(serial) + { + } - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => Core.AOS ? 4 : 1; + public override string CorpseName => "a wanderer of the void corpse"; + public override string DefaultName => "a wanderer of the void"; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - } + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => Core.AOS ? 4 : 1; - public WandererOfTheVoid( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/AntLion.cs b/Scripts/Mobiles/Monsters/Ants/AntLion.cs index a5e6066e0..00cb8c534 100644 --- a/Scripts/Mobiles/Monsters/Ants/AntLion.cs +++ b/Scripts/Mobiles/Monsters/Ants/AntLion.cs @@ -1,111 +1,121 @@ +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class AntLion : BaseCreature - { - public override string CorpseName => "an ant lion corpse"; - public override string DefaultName => "an ant lion"; + public class AntLion : BaseCreature + { + [Constructible] + public AntLion() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 787; + BaseSoundID = 1006; - [Constructible] - public AntLion() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 787; - BaseSoundID = 1006; + SetStr(296, 320); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 296, 320 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(151, 162); - SetHits( 151, 162 ); + SetDamage(7, 21); - SetDamage( 7, 21 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 30 ); + SetResistance(ResistanceType.Physical, 45, 60); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 30, 35); - SetResistance( ResistanceType.Physical, 45, 60 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 30, 35 ); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 90.0); + SetSkill(SkillName.Wrestling, 90.0); - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 90.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + Fame = 4500; + Karma = -4500; - Fame = 4500; - Karma = -4500; + VirtualArmor = 45; - VirtualArmor = 45; + PackItem(new Bone(3)); + PackItem(new FertileDirt(Utility.RandomMinMax(1, 5))); - PackItem( new Bone( 3 ) ); - PackItem( new FertileDirt( Utility.RandomMinMax( 1, 5 ) ) ); + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(2)); - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(2) ); + Item orepile = null; /* no trust, no love :( */ - Item orepile = null; /* no trust, no love :( */ + switch (Utility.Random(4)) + { + case 0: + orepile = new DullCopperOre(); + break; + case 1: + orepile = new ShadowIronOre(); + break; + case 2: + orepile = new CopperOre(); + break; + default: + orepile = new BronzeOre(); + break; + } - switch (Utility.Random(4)) - { - case 0: orepile = new DullCopperOre(); break; - case 1: orepile = new ShadowIronOre(); break; - case 2: orepile = new CopperOre(); break; - default: orepile = new BronzeOre(); break; - } - orepile.Amount = Utility.RandomMinMax(1, 10); - orepile.ItemID = 0x19B9; - PackItem(orepile); + orepile.Amount = Utility.RandomMinMax(1, 10); + orepile.ItemID = 0x19B9; + PackItem(orepile); - // TODO: skeleton - } - - public override int GetAngerSound() - { - return 0x5A; - } - - public override int GetIdleSound() - { - return 0x5A; - } - - public override int GetAttackSound() - { - return 0x164; - } - - public override int GetHurtSound() - { - return 0x187; - } - - public override int GetDeathSound() - { - return 0x1BA; - } - - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - } + // TODO: skeleton + } - public AntLion( Serial serial ) : base( serial ) - { - } + public AntLion(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override string CorpseName => "an ant lion corpse"; + public override string DefaultName => "an ant lion"; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override int GetAngerSound() + { + return 0x5A; + } + + public override int GetIdleSound() + { + return 0x5A; + } + + public override int GetAttackSound() + { + return 0x164; + } + + public override int GetHurtSound() + { + return 0x187; + } + + public override int GetDeathSound() + { + return 0x1BA; + } + + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorQueen.cs b/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorQueen.cs index 2a26d908a..51160029d 100644 --- a/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorQueen.cs +++ b/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorQueen.cs @@ -2,107 +2,107 @@ using Server.Items; namespace Server.Mobiles { - public class BlackSolenInfiltratorQueen : BaseCreature - { - public override string CorpseName => "a solen infiltrator corpse"; - public override string DefaultName => "a black solen infiltrator"; + public class BlackSolenInfiltratorQueen : BaseCreature + { + [Constructible] + public BlackSolenInfiltratorQueen() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 807; + BaseSoundID = 959; + Hue = 0x453; - [Constructible] - public BlackSolenInfiltratorQueen() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 807; - BaseSoundID = 959; - Hue = 0x453; + SetStr(326, 350); + SetDex(141, 165); + SetInt(96, 120); - SetStr( 326, 350 ); - SetDex( 141, 165 ); - SetInt( 96, 120 ); + SetHits(151, 162); - SetHits( 151, 162 ); + SetDamage(10, 15); - SetDamage( 10, 15 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 30 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 35); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 40); + SetResistance(ResistanceType.Energy, 25, 30); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 35 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 40 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + SetSkill(SkillName.MagicResist, 90.0); + SetSkill(SkillName.Tactics, 90.0); + SetSkill(SkillName.Wrestling, 90.0); - SetSkill( SkillName.MagicResist, 90.0 ); - SetSkill( SkillName.Tactics, 90.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + Fame = 6500; + Karma = -6500; - Fame = 6500; - Karma = -6500; + VirtualArmor = 50; - VirtualArmor = 50; + SolenHelper.PackPicnicBasket(this); - SolenHelper.PackPicnicBasket( this ); + PackItem(new ZoogiFungus(0.05 > Utility.RandomDouble() ? 16 : 4)); + } - PackItem( new ZoogiFungus( ( 0.05 > Utility.RandomDouble() ) ? 16 : 4 ) ); - } + public BlackSolenInfiltratorQueen(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x259; - } + public override string CorpseName => "a solen infiltrator corpse"; + public override string DefaultName => "a black solen infiltrator"; - public override int GetIdleSound() - { - return 0x259; - } + public override int GetAngerSound() + { + return 0x259; + } - public override int GetAttackSound() - { - return 0x195; - } + public override int GetIdleSound() + { + return 0x259; + } - public override int GetHurtSound() - { - return 0x250; - } + public override int GetAttackSound() + { + return 0x195; + } - public override int GetDeathSound() - { - return 0x25B; - } + public override int GetHurtSound() + { + return 0x250; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override int GetDeathSound() + { + return 0x25B; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckBlackFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnBlackDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckBlackFriendship(m)) + return false; + return base.IsEnemy(m); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnBlackDamage(from); - public BlackSolenInfiltratorQueen( Serial serial ) : base( serial ) - { - } + base.OnDamage(amount, from, willKill); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorWarrior.cs b/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorWarrior.cs index eac8cdf27..882ddab3d 100644 --- a/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorWarrior.cs +++ b/Scripts/Mobiles/Monsters/Ants/BlackSolenInfiltratorWarrior.cs @@ -2,108 +2,108 @@ using Server.Items; namespace Server.Mobiles { - public class BlackSolenInfiltratorWarrior : BaseCreature - { - public override string CorpseName => "a solen infiltrator corpse"; - public override string DefaultName => "a black solen infiltrator"; + public class BlackSolenInfiltratorWarrior : BaseCreature + { + [Constructible] + public BlackSolenInfiltratorWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 806; + BaseSoundID = 959; + Hue = 0x453; - [Constructible] - public BlackSolenInfiltratorWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 806; - BaseSoundID = 959; - Hue = 0x453; + SetStr(206, 230); + SetDex(121, 145); + SetInt(66, 90); - SetStr( 206, 230 ); - SetDex( 121, 145 ); - SetInt( 66, 90 ); + SetHits(96, 107); - SetHits( 96, 107 ); + SetDamage(5, 15); - SetDamage( 5, 15 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetResistance(ResistanceType.Physical, 20, 35); + SetResistance(ResistanceType.Fire, 20, 35); + SetResistance(ResistanceType.Cold, 10, 25); + SetResistance(ResistanceType.Poison, 20, 35); + SetResistance(ResistanceType.Energy, 10, 25); - SetResistance( ResistanceType.Physical, 20, 35 ); - SetResistance( ResistanceType.Fire, 20, 35 ); - SetResistance( ResistanceType.Cold, 10, 25 ); - SetResistance( ResistanceType.Poison, 20, 35 ); - SetResistance( ResistanceType.Energy, 10, 25 ); + SetSkill(SkillName.MagicResist, 80.0); + SetSkill(SkillName.Tactics, 80.0); + SetSkill(SkillName.Wrestling, 80.0); - SetSkill( SkillName.MagicResist, 80.0 ); - SetSkill( SkillName.Tactics, 80.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 40; - VirtualArmor = 40; + SolenHelper.PackPicnicBasket(this); - SolenHelper.PackPicnicBasket( this ); + PackItem(new ZoogiFungus(0.05 > Utility.RandomDouble() ? 13 : 3)); + } - PackItem( new ZoogiFungus( ( 0.05 > Utility.RandomDouble() )? 13 : 3 ) ); - } + public BlackSolenInfiltratorWarrior(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0xB5; - } + public override string CorpseName => "a solen infiltrator corpse"; + public override string DefaultName => "a black solen infiltrator"; - public override int GetIdleSound() - { - return 0xB5; - } + public override int GetAngerSound() + { + return 0xB5; + } - public override int GetAttackSound() - { - return 0x289; - } + public override int GetIdleSound() + { + return 0xB5; + } - public override int GetHurtSound() - { - return 0xBC; - } + public override int GetAttackSound() + { + return 0x289; + } - public override int GetDeathSound() - { - return 0xE4; - } + public override int GetHurtSound() + { + return 0xBC; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 4 ) ); - } + public override int GetDeathSound() + { + return 0xE4; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckBlackFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 4)); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnBlackDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckBlackFriendship(m)) + return false; + return base.IsEnemy(m); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnBlackDamage(from); - public BlackSolenInfiltratorWarrior( Serial serial ) : base( serial ) - { - } + base.OnDamage(amount, from, willKill); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/BlackSolenQueen.cs b/Scripts/Mobiles/Monsters/Ants/BlackSolenQueen.cs index e0b40a131..9d92d542e 100644 --- a/Scripts/Mobiles/Monsters/Ants/BlackSolenQueen.cs +++ b/Scripts/Mobiles/Monsters/Ants/BlackSolenQueen.cs @@ -3,145 +3,145 @@ using Server.Network; namespace Server.Mobiles { - public class BlackSolenQueen : BaseCreature - { - public override string CorpseName => "a solen queen corpse"; - public bool BurstSac { get; private set; } + public class BlackSolenQueen : BaseCreature + { + [Constructible] + public BlackSolenQueen() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 807; + BaseSoundID = 959; + Hue = 0x453; - public override string DefaultName => "a black solen queen"; + SetStr(296, 320); + SetDex(121, 145); + SetInt(76, 100); - [Constructible] - public BlackSolenQueen() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 807; - BaseSoundID = 959; - Hue = 0x453; + SetHits(151, 162); - SetStr( 296, 320 ); - SetDex( 121, 145 ); - SetInt( 76, 100 ); + SetDamage(10, 15); - SetHits( 151, 162 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 30); - SetDamage( 10, 15 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 35); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 40); + SetResistance(ResistanceType.Energy, 25, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 30 ); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 90.0); + SetSkill(SkillName.Wrestling, 90.0); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 35 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 40 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + Fame = 4500; + Karma = -4500; - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 90.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + VirtualArmor = 45; - Fame = 4500; - Karma = -4500; + SolenHelper.PackPicnicBasket(this); - VirtualArmor = 45; + PackItem(new ZoogiFungus(Utility.RandomDouble() > 0.05 ? 5 : 25)); - SolenHelper.PackPicnicBasket( this ); + if (Utility.RandomDouble() < 0.05) + PackItem(new BallOfSummoning()); + } - PackItem( new ZoogiFungus( ( Utility.RandomDouble() > 0.05 )? 5 : 25 ) ); + public BlackSolenQueen(Serial serial) : base(serial) + { + } - if ( Utility.RandomDouble() < 0.05 ) - PackItem( new BallOfSummoning() ); - } + public override string CorpseName => "a solen queen corpse"; + public bool BurstSac{ get; private set; } - public override int GetAngerSound() - { - return 0x259; - } + public override string DefaultName => "a black solen queen"; - public override int GetIdleSound() - { - return 0x259; - } + public override int GetAngerSound() + { + return 0x259; + } - public override int GetAttackSound() - { - return 0x195; - } + public override int GetIdleSound() + { + return 0x259; + } - public override int GetHurtSound() - { - return 0x250; - } + public override int GetAttackSound() + { + return 0x195; + } - public override int GetDeathSound() - { - return 0x25B; - } + public override int GetHurtSound() + { + return 0x250; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override int GetDeathSound() + { + return 0x25B; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckBlackFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnBlackDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckBlackFriendship(m)) + return false; + return base.IsEnemy(m); + } - if ( !willKill ) - { - if ( !BurstSac ) - { - if ( Hits < 50 ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *" ); - BurstSac = true; - } - } - else if ( from != null && from != this && InRange( from, 1 ) ) - { - SpillAcid( from, 1 ); - } - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnBlackDamage(from); - base.OnDamage( amount, from, willKill ); - } + if (!willKill) + { + if (!BurstSac) + { + if (Hits < 50) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *"); + BurstSac = true; + } + } + else if (from != null && from != this && InRange(from, 1)) + { + SpillAcid(from, 1); + } + } - public override bool OnBeforeDeath() - { - SpillAcid( 4 ); + base.OnDamage(amount, from, willKill); + } - return base.OnBeforeDeath(); - } + public override bool OnBeforeDeath() + { + SpillAcid(4); - public BlackSolenQueen( Serial serial ) : base( serial ) - { - } + return base.OnBeforeDeath(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - writer.Write( BurstSac ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + writer.Write(BurstSac); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - switch( version ) - { - case 1: - { - BurstSac = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + BurstSac = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/BlackSolenWarrior.cs b/Scripts/Mobiles/Monsters/Ants/BlackSolenWarrior.cs index f87cf1e69..e007db162 100644 --- a/Scripts/Mobiles/Monsters/Ants/BlackSolenWarrior.cs +++ b/Scripts/Mobiles/Monsters/Ants/BlackSolenWarrior.cs @@ -3,146 +3,146 @@ using Server.Network; namespace Server.Mobiles { - public class BlackSolenWarrior : BaseCreature - { - public override string CorpseName => "a solen warrior corpse"; - public bool BurstSac { get; private set; } + public class BlackSolenWarrior : BaseCreature + { + [Constructible] + public BlackSolenWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 806; + BaseSoundID = 959; + Hue = 0x453; - public override string DefaultName => "a black solen warrior"; + SetStr(196, 220); + SetDex(101, 125); + SetInt(36, 60); - [Constructible] - public BlackSolenWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 806; - BaseSoundID = 959; - Hue = 0x453; + SetHits(96, 107); - SetStr( 196, 220 ); - SetDex( 101, 125 ); - SetInt( 36, 60 ); + SetDamage(5, 15); - SetHits( 96, 107 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetDamage( 5, 15 ); + SetResistance(ResistanceType.Physical, 20, 35); + SetResistance(ResistanceType.Fire, 20, 35); + SetResistance(ResistanceType.Cold, 10, 25); + SetResistance(ResistanceType.Poison, 20, 35); + SetResistance(ResistanceType.Energy, 10, 25); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetSkill(SkillName.MagicResist, 60.0); + SetSkill(SkillName.Tactics, 80.0); + SetSkill(SkillName.Wrestling, 80.0); - SetResistance( ResistanceType.Physical, 20, 35 ); - SetResistance( ResistanceType.Fire, 20, 35 ); - SetResistance( ResistanceType.Cold, 10, 25 ); - SetResistance( ResistanceType.Poison, 20, 35 ); - SetResistance( ResistanceType.Energy, 10, 25 ); + Fame = 3000; + Karma = -3000; - SetSkill( SkillName.MagicResist, 60.0 ); - SetSkill( SkillName.Tactics, 80.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + VirtualArmor = 35; - Fame = 3000; - Karma = -3000; + SolenHelper.PackPicnicBasket(this); - VirtualArmor = 35; + PackItem(new ZoogiFungus(0.05 > Utility.RandomDouble() ? 13 : 3)); - SolenHelper.PackPicnicBasket( this ); + if (Utility.RandomDouble() < 0.05) + PackItem(new BraceletOfBinding()); + } - PackItem( new ZoogiFungus( ( 0.05 > Utility.RandomDouble() )? 13 : 3 ) ); + public BlackSolenWarrior(Serial serial) : base(serial) + { + } - if ( Utility.RandomDouble() < 0.05 ) - PackItem( new BraceletOfBinding() ); - } + public override string CorpseName => "a solen warrior corpse"; + public bool BurstSac{ get; private set; } - public override int GetAngerSound() - { - return 0xB5; - } + public override string DefaultName => "a black solen warrior"; - public override int GetIdleSound() - { - return 0xB5; - } + public override int GetAngerSound() + { + return 0xB5; + } - public override int GetAttackSound() - { - return 0x289; - } + public override int GetIdleSound() + { + return 0xB5; + } - public override int GetHurtSound() - { - return 0xBC; - } + public override int GetAttackSound() + { + return 0x289; + } - public override int GetDeathSound() - { - return 0xE4; - } + public override int GetHurtSound() + { + return 0xBC; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 4 ) ); - } + public override int GetDeathSound() + { + return 0xE4; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckBlackFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 4)); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnBlackDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckBlackFriendship(m)) + return false; + return base.IsEnemy(m); + } - if ( !willKill ) - { - if ( !BurstSac ) - { - if ( Hits < 50 ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *" ); - BurstSac = true; - } - } - else if ( from != null && from != this && InRange( from, 1 ) ) - { - SpillAcid( from, 1 ); - } - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnBlackDamage(from); - base.OnDamage( amount, from, willKill ); - } + if (!willKill) + { + if (!BurstSac) + { + if (Hits < 50) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *"); + BurstSac = true; + } + } + else if (from != null && from != this && InRange(from, 1)) + { + SpillAcid(from, 1); + } + } - public override bool OnBeforeDeath() - { - SpillAcid( 4 ); + base.OnDamage(amount, from, willKill); + } - return base.OnBeforeDeath(); - } + public override bool OnBeforeDeath() + { + SpillAcid(4); - public BlackSolenWarrior( Serial serial ) : base( serial ) - { - } + return base.OnBeforeDeath(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - writer.Write( BurstSac ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + writer.Write(BurstSac); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - switch( version ) - { - case 1: - { - BurstSac = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + BurstSac = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/BlackSolenWorker.cs b/Scripts/Mobiles/Monsters/Ants/BlackSolenWorker.cs index 116f5b64a..915ea5082 100644 --- a/Scripts/Mobiles/Monsters/Ants/BlackSolenWorker.cs +++ b/Scripts/Mobiles/Monsters/Ants/BlackSolenWorker.cs @@ -2,108 +2,108 @@ using Server.Items; namespace Server.Mobiles { - public class BlackSolenWorker : BaseCreature - { - public override string CorpseName => "a solen worker corpse"; - public override string DefaultName => "a black solen worker"; + public class BlackSolenWorker : BaseCreature + { + [Constructible] + public BlackSolenWorker() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 805; + BaseSoundID = 959; + Hue = 0x453; - [Constructible] - public BlackSolenWorker() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 805; - BaseSoundID = 959; - Hue = 0x453; + SetStr(96, 120); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(58, 72); - SetHits( 58, 72 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 60.0); + SetSkill(SkillName.Tactics, 65.0); + SetSkill(SkillName.Wrestling, 60.0); - SetSkill( SkillName.MagicResist, 60.0 ); - SetSkill( SkillName.Tactics, 65.0 ); - SetSkill( SkillName.Wrestling, 60.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 28; - VirtualArmor = 28; + PackGold(Utility.Random(100, 180)); - PackGold( Utility.Random( 100, 180 ) ); + SolenHelper.PackPicnicBasket(this); - SolenHelper.PackPicnicBasket( this ); + PackItem(new ZoogiFungus()); + } - PackItem( new ZoogiFungus() ); - } + public BlackSolenWorker(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x269; - } + public override string CorpseName => "a solen worker corpse"; + public override string DefaultName => "a black solen worker"; - public override int GetIdleSound() - { - return 0x269; - } + public override int GetAngerSound() + { + return 0x269; + } - public override int GetAttackSound() - { - return 0x186; - } + public override int GetIdleSound() + { + return 0x269; + } - public override int GetHurtSound() - { - return 0x1BE; - } + public override int GetAttackSound() + { + return 0x186; + } - public override int GetDeathSound() - { - return 0x8E; - } + public override int GetHurtSound() + { + return 0x1BE; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 2 ) ); - } + public override int GetDeathSound() + { + return 0x8E; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckBlackFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 2)); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnBlackDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckBlackFriendship(m)) + return false; + return base.IsEnemy(m); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnBlackDamage(from); - public BlackSolenWorker( Serial serial ) : base( serial ) - { - } + base.OnDamage(amount, from, willKill); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorQueen.cs b/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorQueen.cs index 70c5fd31e..2b50295b6 100644 --- a/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorQueen.cs +++ b/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorQueen.cs @@ -2,106 +2,106 @@ using Server.Items; namespace Server.Mobiles { - public class RedSolenInfiltratorQueen : BaseCreature - { - public override string CorpseName => "a solen infiltrator corpse"; - public override string DefaultName => "a red solen infiltrator"; + public class RedSolenInfiltratorQueen : BaseCreature + { + [Constructible] + public RedSolenInfiltratorQueen() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 783; + BaseSoundID = 959; - [Constructible] - public RedSolenInfiltratorQueen() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 783; - BaseSoundID = 959; + SetStr(326, 350); + SetDex(141, 165); + SetInt(96, 120); - SetStr( 326, 350 ); - SetDex( 141, 165 ); - SetInt( 96, 120 ); + SetHits(151, 162); - SetHits( 151, 162 ); + SetDamage(10, 15); - SetDamage( 10, 15 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 30 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 35); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 40); + SetResistance(ResistanceType.Energy, 25, 30); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 35 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 40 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + SetSkill(SkillName.MagicResist, 90.0); + SetSkill(SkillName.Tactics, 90.0); + SetSkill(SkillName.Wrestling, 90.0); - SetSkill( SkillName.MagicResist, 90.0 ); - SetSkill( SkillName.Tactics, 90.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + Fame = 6500; + Karma = -6500; - Fame = 6500; - Karma = -6500; + VirtualArmor = 50; - VirtualArmor = 50; + SolenHelper.PackPicnicBasket(this); - SolenHelper.PackPicnicBasket( this ); + PackItem(new ZoogiFungus(0.05 < Utility.RandomDouble() ? 4 : 16)); + } - PackItem( new ZoogiFungus( ( 0.05 < Utility.RandomDouble() )? 4 : 16 ) ); - } + public RedSolenInfiltratorQueen(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x259; - } + public override string CorpseName => "a solen infiltrator corpse"; + public override string DefaultName => "a red solen infiltrator"; - public override int GetIdleSound() - { - return 0x259; - } + public override int GetAngerSound() + { + return 0x259; + } - public override int GetAttackSound() - { - return 0x195; - } + public override int GetIdleSound() + { + return 0x259; + } - public override int GetHurtSound() - { - return 0x250; - } + public override int GetAttackSound() + { + return 0x195; + } - public override int GetDeathSound() - { - return 0x25B; - } + public override int GetHurtSound() + { + return 0x250; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override int GetDeathSound() + { + return 0x25B; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckRedFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnRedDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckRedFriendship(m)) + return false; + return base.IsEnemy(m); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnRedDamage(from); - public RedSolenInfiltratorQueen( Serial serial ) : base( serial ) - { - } + base.OnDamage(amount, from, willKill); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorWarrior.cs b/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorWarrior.cs index e51742e15..0d84604ca 100644 --- a/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorWarrior.cs +++ b/Scripts/Mobiles/Monsters/Ants/RedSolenInfiltratorWarrior.cs @@ -2,108 +2,107 @@ using Server.Items; namespace Server.Mobiles { - public class RedSolenInfiltratorWarrior : BaseCreature - { - public override string CorpseName => "a solen infiltrator corpse"; - public override string DefaultName => "a red solen infiltrator"; + public class RedSolenInfiltratorWarrior : BaseCreature + { + [Constructible] + public RedSolenInfiltratorWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 782; + BaseSoundID = 959; - [Constructible] - public RedSolenInfiltratorWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 782; - BaseSoundID = 959; + SetStr(206, 230); + SetDex(121, 145); + SetInt(66, 90); - SetStr( 206, 230 ); - SetDex( 121, 145 ); - SetInt( 66, 90 ); + SetHits(96, 107); - SetHits( 96, 107 ); + SetDamage(5, 15); - SetDamage( 5, 15 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetResistance(ResistanceType.Physical, 20, 35); + SetResistance(ResistanceType.Fire, 20, 35); + SetResistance(ResistanceType.Cold, 10, 25); + SetResistance(ResistanceType.Poison, 20, 35); + SetResistance(ResistanceType.Energy, 10, 25); - SetResistance( ResistanceType.Physical, 20, 35 ); - SetResistance( ResistanceType.Fire, 20, 35 ); - SetResistance( ResistanceType.Cold, 10, 25 ); - SetResistance( ResistanceType.Poison, 20, 35 ); - SetResistance( ResistanceType.Energy, 10, 25 ); + SetSkill(SkillName.MagicResist, 80.0); + SetSkill(SkillName.Tactics, 80.0); + SetSkill(SkillName.Wrestling, 80.0); - SetSkill( SkillName.MagicResist, 80.0 ); - SetSkill( SkillName.Tactics, 80.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 40; - VirtualArmor = 40; + SolenHelper.PackPicnicBasket(this); - SolenHelper.PackPicnicBasket( this ); + PackItem(new ZoogiFungus(0.05 < Utility.RandomDouble() ? 3 : 13)); + } - PackItem( new ZoogiFungus( ( 0.05 < Utility.RandomDouble() )? 3 : 13 ) ); + public RedSolenInfiltratorWarrior(Serial serial) : base(serial) + { + } - } + public override string CorpseName => "a solen infiltrator corpse"; + public override string DefaultName => "a red solen infiltrator"; - public override int GetAngerSound() - { - return 0xB5; - } + public override int GetAngerSound() + { + return 0xB5; + } - public override int GetIdleSound() - { - return 0xB5; - } + public override int GetIdleSound() + { + return 0xB5; + } - public override int GetAttackSound() - { - return 0x289; - } + public override int GetAttackSound() + { + return 0x289; + } - public override int GetHurtSound() - { - return 0xBC; - } + public override int GetHurtSound() + { + return 0xBC; + } - public override int GetDeathSound() - { - return 0xE4; - } + public override int GetDeathSound() + { + return 0xE4; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 4 ) ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 4)); + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckRedFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckRedFriendship(m)) + return false; + return base.IsEnemy(m); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnRedDamage( from ); + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnRedDamage(from); - base.OnDamage( amount, from, willKill ); - } + base.OnDamage(amount, from, willKill); + } - public RedSolenInfiltratorWarrior( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/RedSolenQueen.cs b/Scripts/Mobiles/Monsters/Ants/RedSolenQueen.cs index 760049cc1..f9994bb20 100644 --- a/Scripts/Mobiles/Monsters/Ants/RedSolenQueen.cs +++ b/Scripts/Mobiles/Monsters/Ants/RedSolenQueen.cs @@ -3,145 +3,145 @@ using Server.Network; namespace Server.Mobiles { - public class RedSolenQueen : BaseCreature - { - public override string CorpseName => "a solen queen corpse"; - public bool BurstSac { get; private set; } + public class RedSolenQueen : BaseCreature + { + [Constructible] + public RedSolenQueen() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 783; + BaseSoundID = 959; - public override string DefaultName => "a red solen queen"; + SetStr(296, 320); + SetDex(121, 145); + SetInt(76, 100); - [Constructible] - public RedSolenQueen() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 783; - BaseSoundID = 959; + SetHits(151, 162); - SetStr( 296, 320 ); - SetDex( 121, 145 ); - SetInt( 76, 100 ); + SetDamage(10, 15); - SetHits( 151, 162 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 30); - SetDamage( 10, 15 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 35); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 40); + SetResistance(ResistanceType.Energy, 25, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 30 ); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 90.0); + SetSkill(SkillName.Wrestling, 90.0); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 35 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 40 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + Fame = 4500; + Karma = -4500; - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 90.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + VirtualArmor = 45; - Fame = 4500; - Karma = -4500; + SolenHelper.PackPicnicBasket(this); - VirtualArmor = 45; + PackItem(new ZoogiFungus(Utility.RandomDouble() > 0.05 ? 5 : 25)); - SolenHelper.PackPicnicBasket( this ); + if (Utility.RandomDouble() < 0.05) + PackItem(new BallOfSummoning()); + } - PackItem( new ZoogiFungus( ( Utility.RandomDouble() > 0.05 )? 5 : 25 ) ); + public RedSolenQueen(Serial serial) : base(serial) + { + } - if ( Utility.RandomDouble() < 0.05 ) - PackItem( new BallOfSummoning() ); - } + public override string CorpseName => "a solen queen corpse"; + public bool BurstSac{ get; private set; } - public override int GetAngerSound() - { - return 0x259; - } + public override string DefaultName => "a red solen queen"; - public override int GetIdleSound() - { - return 0x259; - } + public override int GetAngerSound() + { + return 0x259; + } - public override int GetAttackSound() - { - return 0x195; - } + public override int GetIdleSound() + { + return 0x259; + } - public override int GetHurtSound() - { - return 0x250; - } + public override int GetAttackSound() + { + return 0x195; + } - public override int GetDeathSound() - { - return 0x25B; - } + public override int GetHurtSound() + { + return 0x250; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override int GetDeathSound() + { + return 0x25B; + } + + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckRedFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckRedFriendship(m)) + return false; + return base.IsEnemy(m); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnRedDamage( from ); + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnRedDamage(from); - if ( !willKill ) - { - if ( !BurstSac ) - { - if ( Hits < 50 ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *" ); - BurstSac = true; - } - } - else if ( from != null && from != this && InRange( from, 1 ) ) - { - SpillAcid( from, 1 ); - } - } + if (!willKill) + { + if (!BurstSac) + { + if (Hits < 50) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *"); + BurstSac = true; + } + } + else if (from != null && from != this && InRange(from, 1)) + { + SpillAcid(from, 1); + } + } - base.OnDamage( amount, from, willKill ); - } + base.OnDamage(amount, from, willKill); + } - public override bool OnBeforeDeath() - { - SpillAcid( 4 ); + public override bool OnBeforeDeath() + { + SpillAcid(4); - return base.OnBeforeDeath(); - } + return base.OnBeforeDeath(); + } - public RedSolenQueen( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + writer.Write(BurstSac); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - writer.Write( BurstSac ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - switch( version ) - { - case 1: - { - BurstSac = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + BurstSac = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/RedSolenWarrior.cs b/Scripts/Mobiles/Monsters/Ants/RedSolenWarrior.cs index 7509cff9d..44c542cc4 100644 --- a/Scripts/Mobiles/Monsters/Ants/RedSolenWarrior.cs +++ b/Scripts/Mobiles/Monsters/Ants/RedSolenWarrior.cs @@ -3,145 +3,144 @@ using Server.Network; namespace Server.Mobiles { - public class RedSolenWarrior : BaseCreature - { - public override string CorpseName => "a solen warrior corpse"; - public bool BurstSac { get; private set; } + public class RedSolenWarrior : BaseCreature + { + [Constructible] + public RedSolenWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 782; + BaseSoundID = 959; - public override string DefaultName => "a red solen warrior"; + SetStr(196, 220); + SetDex(101, 125); + SetInt(36, 60); - [Constructible] - public RedSolenWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 782; - BaseSoundID = 959; + SetHits(96, 107); - SetStr( 196, 220 ); - SetDex( 101, 125 ); - SetInt( 36, 60 ); + SetDamage(5, 15); - SetHits( 96, 107 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetDamage( 5, 15 ); + SetResistance(ResistanceType.Physical, 20, 35); + SetResistance(ResistanceType.Fire, 20, 35); + SetResistance(ResistanceType.Cold, 10, 25); + SetResistance(ResistanceType.Poison, 20, 35); + SetResistance(ResistanceType.Energy, 10, 25); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetSkill(SkillName.MagicResist, 60.0); + SetSkill(SkillName.Tactics, 80.0); + SetSkill(SkillName.Wrestling, 80.0); - SetResistance( ResistanceType.Physical, 20, 35 ); - SetResistance( ResistanceType.Fire, 20, 35 ); - SetResistance( ResistanceType.Cold, 10, 25 ); - SetResistance( ResistanceType.Poison, 20, 35 ); - SetResistance( ResistanceType.Energy, 10, 25 ); + Fame = 3000; + Karma = -3000; - SetSkill( SkillName.MagicResist, 60.0 ); - SetSkill( SkillName.Tactics, 80.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + VirtualArmor = 35; - Fame = 3000; - Karma = -3000; + SolenHelper.PackPicnicBasket(this); + PackItem(new ZoogiFungus(0.05 < Utility.RandomDouble() ? 3 : 13)); - VirtualArmor = 35; + if (Utility.RandomDouble() < 0.05) + PackItem(new BraceletOfBinding()); + } - SolenHelper.PackPicnicBasket( this ); - PackItem( new ZoogiFungus( ( 0.05 < Utility.RandomDouble() )? 3 : 13 ) ); + public RedSolenWarrior(Serial serial) : base(serial) + { + } - if ( Utility.RandomDouble() < 0.05 ) - PackItem( new BraceletOfBinding() ); + public override string CorpseName => "a solen warrior corpse"; + public bool BurstSac{ get; private set; } - } + public override string DefaultName => "a red solen warrior"; - public override int GetAngerSound() - { - return 0xB5; - } + public override int GetAngerSound() + { + return 0xB5; + } - public override int GetIdleSound() - { - return 0xB5; - } + public override int GetIdleSound() + { + return 0xB5; + } - public override int GetAttackSound() - { - return 0x289; - } + public override int GetAttackSound() + { + return 0x289; + } - public override int GetHurtSound() - { - return 0xBC; - } + public override int GetHurtSound() + { + return 0xBC; + } - public override int GetDeathSound() - { - return 0xE4; - } + public override int GetDeathSound() + { + return 0xE4; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 4 ) ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 4)); + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckRedFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckRedFriendship(m)) + return false; + return base.IsEnemy(m); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnRedDamage( from ); + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnRedDamage(from); - if ( !willKill ) - { - if ( !BurstSac ) - { - if ( Hits < 50 ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *" ); - BurstSac = true; - } - } - else if ( from != null && from != this && InRange( from, 1 ) ) - { - SpillAcid( from, 1 ); - } - } + if (!willKill) + { + if (!BurstSac) + { + if (Hits < 50) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, true, "* The solen's acid sac is burst open! *"); + BurstSac = true; + } + } + else if (from != null && from != this && InRange(from, 1)) + { + SpillAcid(from, 1); + } + } - base.OnDamage( amount, from, willKill ); - } + base.OnDamage(amount, from, willKill); + } - public override bool OnBeforeDeath() - { - SpillAcid( 4 ); + public override bool OnBeforeDeath() + { + SpillAcid(4); - return base.OnBeforeDeath(); - } + return base.OnBeforeDeath(); + } - public RedSolenWarrior( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + writer.Write(BurstSac); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - writer.Write( BurstSac ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - switch( version ) - { - case 1: - { - BurstSac = reader.ReadBool(); - break; - } - } - } - } -} + switch (version) + { + case 1: + { + BurstSac = reader.ReadBool(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/RedSolenWorker.cs b/Scripts/Mobiles/Monsters/Ants/RedSolenWorker.cs index 8b9a1007f..f72ffcffa 100644 --- a/Scripts/Mobiles/Monsters/Ants/RedSolenWorker.cs +++ b/Scripts/Mobiles/Monsters/Ants/RedSolenWorker.cs @@ -2,107 +2,107 @@ using Server.Items; namespace Server.Mobiles { - public class RedSolenWorker : BaseCreature - { - public override string CorpseName => "a solen worker corpse"; - public override string DefaultName => "a red solen worker"; + public class RedSolenWorker : BaseCreature + { + [Constructible] + public RedSolenWorker() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 781; + BaseSoundID = 959; - [Constructible] - public RedSolenWorker() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 781; - BaseSoundID = 959; + SetStr(96, 120); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(58, 72); - SetHits( 58, 72 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 60.0); + SetSkill(SkillName.Tactics, 65.0); + SetSkill(SkillName.Wrestling, 60.0); - SetSkill( SkillName.MagicResist, 60.0 ); - SetSkill( SkillName.Tactics, 65.0 ); - SetSkill( SkillName.Wrestling, 60.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 28; - VirtualArmor = 28; + PackGold(Utility.Random(100, 180)); - PackGold( Utility.Random( 100, 180 ) ); + SolenHelper.PackPicnicBasket(this); - SolenHelper.PackPicnicBasket( this ); + PackItem(new ZoogiFungus()); + } - PackItem( new ZoogiFungus() ); - } + public RedSolenWorker(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x269; - } + public override string CorpseName => "a solen worker corpse"; + public override string DefaultName => "a red solen worker"; - public override int GetIdleSound() - { - return 0x269; - } + public override int GetAngerSound() + { + return 0x269; + } - public override int GetAttackSound() - { - return 0x186; - } + public override int GetIdleSound() + { + return 0x269; + } - public override int GetHurtSound() - { - return 0x1BE; - } + public override int GetAttackSound() + { + return 0x186; + } - public override int GetDeathSound() - { - return 0x8E; - } + public override int GetHurtSound() + { + return 0x1BE; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 2 ) ); - } + public override int GetDeathSound() + { + return 0x8E; + } - public override bool IsEnemy( Mobile m ) - { - if ( SolenHelper.CheckRedFriendship( m ) ) - return false; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 2)); + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - SolenHelper.OnRedDamage( from ); + public override bool IsEnemy(Mobile m) + { + if (SolenHelper.CheckRedFriendship(m)) + return false; + return base.IsEnemy(m); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + SolenHelper.OnRedDamage(from); - public RedSolenWorker( Serial serial ) : base( serial ) - { - } + base.OnDamage(amount, from, willKill); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ants/SolenHelper.cs b/Scripts/Mobiles/Monsters/Ants/SolenHelper.cs index 159abf524..1f69404d1 100644 --- a/Scripts/Mobiles/Monsters/Ants/SolenHelper.cs +++ b/Scripts/Mobiles/Monsters/Ants/SolenHelper.cs @@ -3,81 +3,83 @@ using Server.Network; namespace Server.Mobiles { - public class SolenHelper - { - public static void PackPicnicBasket( BaseCreature solen ) - { - if ( 1 > Utility.Random( 100 ) ) - { - PicnicBasket basket = new PicnicBasket(); + public class SolenHelper + { + public static void PackPicnicBasket(BaseCreature solen) + { + if (1 > Utility.Random(100)) + { + PicnicBasket basket = new PicnicBasket(); - basket.DropItem( new BeverageBottle( BeverageType.Wine ) ); - basket.DropItem( new CheeseWedge() ); + basket.DropItem(new BeverageBottle(BeverageType.Wine)); + basket.DropItem(new CheeseWedge()); - solen.PackItem( basket ); - } - } + solen.PackItem(basket); + } + } - public static bool CheckRedFriendship( Mobile m ) - { - if ( m is BaseCreature bc ) - { - if ( bc.Controlled && bc.ControlMaster is PlayerMobile ) - return CheckRedFriendship( bc.ControlMaster ); - if ( bc.Summoned && bc.SummonMaster is PlayerMobile ) - return CheckRedFriendship( bc.SummonMaster ); - } + public static bool CheckRedFriendship(Mobile m) + { + if (m is BaseCreature bc) + { + if (bc.Controlled && bc.ControlMaster is PlayerMobile) + return CheckRedFriendship(bc.ControlMaster); + if (bc.Summoned && bc.SummonMaster is PlayerMobile) + return CheckRedFriendship(bc.SummonMaster); + } - return m is PlayerMobile player && player.SolenFriendship == SolenFriendship.Red; - } + return m is PlayerMobile player && player.SolenFriendship == SolenFriendship.Red; + } - public static bool CheckBlackFriendship( Mobile m ) - { - if ( m is BaseCreature bc ) - { - if ( bc.Controlled && bc.ControlMaster is PlayerMobile ) - return CheckBlackFriendship( bc.ControlMaster ); - if ( bc.Summoned && bc.SummonMaster is PlayerMobile ) - return CheckBlackFriendship( bc.SummonMaster ); - } + public static bool CheckBlackFriendship(Mobile m) + { + if (m is BaseCreature bc) + { + if (bc.Controlled && bc.ControlMaster is PlayerMobile) + return CheckBlackFriendship(bc.ControlMaster); + if (bc.Summoned && bc.SummonMaster is PlayerMobile) + return CheckBlackFriendship(bc.SummonMaster); + } - return m is PlayerMobile player && player.SolenFriendship == SolenFriendship.Black; - } + return m is PlayerMobile player && player.SolenFriendship == SolenFriendship.Black; + } - public static void OnRedDamage( Mobile from ) - { - if ( from is BaseCreature bc ) - { - if ( bc.Controlled && bc.ControlMaster is PlayerMobile ) - OnRedDamage( bc.ControlMaster ); - else if ( bc.Summoned && bc.SummonMaster is PlayerMobile ) - OnRedDamage( bc.SummonMaster ); - } + public static void OnRedDamage(Mobile from) + { + if (from is BaseCreature bc) + { + if (bc.Controlled && bc.ControlMaster is PlayerMobile) + OnRedDamage(bc.ControlMaster); + else if (bc.Summoned && bc.SummonMaster is PlayerMobile) + OnRedDamage(bc.SummonMaster); + } - if ( from is PlayerMobile player && player.SolenFriendship == SolenFriendship.Red ) - { - player.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1054103 ); // The solen revoke their friendship. You will now be considered an intruder. + if (from is PlayerMobile player && player.SolenFriendship == SolenFriendship.Red) + { + player.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1054103); // The solen revoke their friendship. You will now be considered an intruder. - player.SolenFriendship = SolenFriendship.None; - } - } + player.SolenFriendship = SolenFriendship.None; + } + } - public static void OnBlackDamage( Mobile from ) - { - if ( from is BaseCreature bc ) - { - if ( bc.Controlled && bc.ControlMaster is PlayerMobile ) - OnBlackDamage( bc.ControlMaster ); - else if ( bc.Summoned && bc.SummonMaster is PlayerMobile ) - OnBlackDamage( bc.SummonMaster ); - } + public static void OnBlackDamage(Mobile from) + { + if (from is BaseCreature bc) + { + if (bc.Controlled && bc.ControlMaster is PlayerMobile) + OnBlackDamage(bc.ControlMaster); + else if (bc.Summoned && bc.SummonMaster is PlayerMobile) + OnBlackDamage(bc.SummonMaster); + } - if ( from is PlayerMobile player && player.SolenFriendship == SolenFriendship.Black ) - { - player.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1054103 ); // The solen revoke their friendship. You will now be considered an intruder. + if (from is PlayerMobile player && player.SolenFriendship == SolenFriendship.Black) + { + player.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1054103); // The solen revoke their friendship. You will now be considered an intruder. - player.SolenFriendship = SolenFriendship.None; - } - } - } -} + player.SolenFriendship = SolenFriendship.None; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Magic/DreadSpider.cs b/Scripts/Mobiles/Monsters/Arachnid/Magic/DreadSpider.cs index fe660a468..e5c4d53ba 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Magic/DreadSpider.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Magic/DreadSpider.cs @@ -2,75 +2,75 @@ using Server.Items; namespace Server.Mobiles { - public class DreadSpider : BaseCreature - { - public override string CorpseName => "a dread spider corpse"; - public override string DefaultName => "a dread spider"; + public class DreadSpider : BaseCreature + { + [Constructible] + public DreadSpider() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 11; + BaseSoundID = 1170; - [Constructible] - public DreadSpider () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 11; - BaseSoundID = 1170; + SetStr(196, 220); + SetDex(126, 145); + SetInt(286, 310); - SetStr( 196, 220 ); - SetDex( 126, 145 ); - SetInt( 286, 310 ); + SetHits(118, 132); - SetHits( 118, 132 ); + SetDamage(5, 17); - SetDamage( 5, 17 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Poison, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Poison, 80 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 90, 100); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 90, 100 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.EvalInt, 65.1, 80.0); + SetSkill(SkillName.Magery, 65.1, 80.0); + SetSkill(SkillName.Meditation, 65.1, 80.0); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 55.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 75.0); - SetSkill( SkillName.EvalInt, 65.1, 80.0 ); - SetSkill( SkillName.Magery, 65.1, 80.0 ); - SetSkill( SkillName.Meditation, 65.1, 80.0 ); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 55.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 75.0 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + VirtualArmor = 36; - VirtualArmor = 36; + PackItem(new SpidersSilk(8)); + } - PackItem( new SpidersSilk( 8 ) ); - } + public DreadSpider(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - } + public override string CorpseName => "a dread spider corpse"; + public override string DefaultName => "a dread spider"; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; - public override int TreasureMapLevel => 3; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; + public override int TreasureMapLevel => 3; - public DreadSpider( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 263 ) - BaseSoundID = 1170; - } - } -} + if (BaseSoundID == 263) + BaseSoundID = 1170; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanAvenger.cs b/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanAvenger.cs index bb1887296..a56d70724 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanAvenger.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanAvenger.cs @@ -1,76 +1,76 @@ namespace Server.Mobiles { - public class TerathanAvenger : BaseCreature - { - public override string CorpseName => "a terathan avenger corpse"; - public override string DefaultName => "a terathan avenger"; + public class TerathanAvenger : BaseCreature + { + [Constructible] + public TerathanAvenger() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 152; + BaseSoundID = 0x24D; - [Constructible] - public TerathanAvenger() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 152; - BaseSoundID = 0x24D; + SetStr(467, 645); + SetDex(77, 95); + SetInt(126, 150); - SetStr( 467, 645 ); - SetDex( 77, 95 ); - SetInt( 126, 150 ); + SetHits(296, 372); + SetMana(46, 70); - SetHits( 296, 372 ); - SetMana( 46, 70 ); + SetDamage(18, 22); - SetDamage( 18, 22 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 90, 100); + SetResistance(ResistanceType.Energy, 35, 45); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 90, 100 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetSkill(SkillName.EvalInt, 70.3, 100.0); + SetSkill(SkillName.Magery, 70.3, 100.0); + SetSkill(SkillName.Poisoning, 60.1, 80.0); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.EvalInt, 70.3, 100.0 ); - SetSkill( SkillName.Magery, 70.3, 100.0 ); - SetSkill( SkillName.Poisoning, 60.1, 80.0 ); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + VirtualArmor = 50; + } - VirtualArmor = 50; - } + public TerathanAvenger(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 2 ); - } + public override string CorpseName => "a terathan avenger corpse"; + public override string DefaultName => "a terathan avenger"; - public override Poison PoisonImmune => Poison.Deadly; - public override Poison HitPoison => Poison.Deadly; - public override int TreasureMapLevel => 3; - public override int Meat => 2; + public override Poison PoisonImmune => Poison.Deadly; + public override Poison HitPoison => Poison.Deadly; + public override int TreasureMapLevel => 3; + public override int Meat => 2; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public TerathanAvenger( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 263 ) - BaseSoundID = 0x24D; - } - } -} + if (BaseSoundID == 263) + BaseSoundID = 0x24D; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanMatriarch.cs b/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanMatriarch.cs index 46e56d653..3f7bcda4e 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanMatriarch.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Magic/TerathanMatriarch.cs @@ -2,72 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class TerathanMatriarch : BaseCreature - { - public override string CorpseName => "a terathan matriarch corpse"; - public override string DefaultName => "a terathan matriarch"; + public class TerathanMatriarch : BaseCreature + { + [Constructible] + public TerathanMatriarch() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 72; + BaseSoundID = 599; - [Constructible] - public TerathanMatriarch() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 72; - BaseSoundID = 599; + SetStr(316, 405); + SetDex(96, 115); + SetInt(366, 455); - SetStr( 316, 405 ); - SetDex( 96, 115 ); - SetInt( 366, 455 ); + SetHits(190, 243); - SetHits( 190, 243 ); + SetDamage(11, 14); - SetDamage( 11, 14 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 35, 45); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 10000; + Karma = -10000; - Fame = 10000; - Karma = -10000; + PackItem(new SpidersSilk(5)); + PackNecroReg(Utility.RandomMinMax(4, 10)); + } - PackItem( new SpidersSilk( 5 ) ); - PackNecroReg( Utility.RandomMinMax( 4, 10 ) ); - } + public TerathanMatriarch(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "a terathan matriarch corpse"; + public override string DefaultName => "a terathan matriarch"; - public override int TreasureMapLevel => 4; + public override int TreasureMapLevel => 4; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public TerathanMatriarch( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.MedScrolls, 2); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Melee/FrostSpider.cs b/Scripts/Mobiles/Monsters/Arachnid/Melee/FrostSpider.cs index e04581c94..d6a279bcb 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Melee/FrostSpider.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Melee/FrostSpider.cs @@ -2,77 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class FrostSpider : BaseCreature - { - public override string CorpseName => "a frost spider corpse"; - public override string DefaultName => "a frost spider"; + public class FrostSpider : BaseCreature + { + [Constructible] + public FrostSpider() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 20; + BaseSoundID = 0x388; - [Constructible] - public FrostSpider() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 20; - BaseSoundID = 0x388; + SetStr(76, 100); + SetDex(126, 145); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 126, 145 ); - SetInt( 36, 60 ); + SetHits(46, 60); + SetMana(0); - SetHits( 46, 60 ); - SetMana( 0 ); + SetDamage(6, 16); - SetDamage( 6, 16 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 80 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 35.1, 50.0); + SetSkill(SkillName.Wrestling, 50.1, 65.0); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 35.1, 50.0 ); - SetSkill( SkillName.Wrestling, 50.1, 65.0 ); + Fame = 775; + Karma = -775; - Fame = 775; - Karma = -775; + VirtualArmor = 28; - VirtualArmor = 28; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 74.7; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 74.7; + PackItem(new SpidersSilk(7)); + } - PackItem( new SpidersSilk( 7 ) ); - } + public FrostSpider(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a frost spider corpse"; + public override string DefaultName => "a frost spider"; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Arachnid; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Arachnid; - public FrostSpider( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 387 ) - BaseSoundID = 0x388; - } - } -} + if (BaseSoundID == 387) + BaseSoundID = 0x388; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantBlackWidow.cs b/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantBlackWidow.cs index 254d02982..f1eaa2fd8 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantBlackWidow.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantBlackWidow.cs @@ -2,72 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class GiantBlackWidow : BaseCreature - { - public override string CorpseName => "a giant black widow spider corpse"; - public override string DefaultName => "a giant black wide"; + public class GiantBlackWidow : BaseCreature + { + [Constructible] + public GiantBlackWidow() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x9D; + BaseSoundID = 0x388; // TODO: validate - [Constructible] - public GiantBlackWidow() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x9D; - BaseSoundID = 0x388; // TODO: validate + SetStr(76, 100); + SetDex(96, 115); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 96, 115 ); - SetInt( 36, 60 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(5, 17); - SetDamage( 5, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 30); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 20, 30 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Anatomy, 30.3, 75.0); + SetSkill(SkillName.Poisoning, 60.1, 80.0); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 65.1, 80.0); + SetSkill(SkillName.Wrestling, 70.1, 85.0); - SetSkill( SkillName.Anatomy, 30.3, 75.0 ); - SetSkill( SkillName.Poisoning, 60.1, 80.0 ); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 65.1, 80.0 ); - SetSkill( SkillName.Wrestling, 70.1, 85.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 24; - VirtualArmor = 24; + PackItem(new SpidersSilk(5)); + PackItem(new LesserPoisonPotion()); + PackItem(new LesserPoisonPotion()); + } - PackItem( new SpidersSilk( 5 ) ); - PackItem( new LesserPoisonPotion() ); - PackItem( new LesserPoisonPotion() ); - } + public GiantBlackWidow(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a giant black widow spider corpse"; + public override string DefaultName => "a giant black wide"; - public override FoodType FavoriteFood => FoodType.Meat; - public override Poison PoisonImmune => Poison.Deadly; - public override Poison HitPoison => Poison.Deadly; + public override FoodType FavoriteFood => FoodType.Meat; + public override Poison PoisonImmune => Poison.Deadly; + public override Poison HitPoison => Poison.Deadly; - public GiantBlackWidow( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantSpider.cs b/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantSpider.cs index a0c2ad6c8..e19ede18c 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantSpider.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Melee/GiantSpider.cs @@ -2,72 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class GiantSpider : BaseCreature - { - public override string CorpseName => "a giant spider corpse"; - public override string DefaultName => "a giant spider"; + public class GiantSpider : BaseCreature + { + [Constructible] + public GiantSpider() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 28; + BaseSoundID = 0x388; - [Constructible] - public GiantSpider() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 28; - BaseSoundID = 0x388; + SetStr(76, 100); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(46, 60); + SetMana(0); - SetHits( 46, 60 ); - SetMana( 0 ); + SetDamage(5, 13); - SetDamage( 5, 13 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Poison, 25, 35); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Poison, 25, 35 ); + SetSkill(SkillName.Poisoning, 60.1, 80.0); + SetSkill(SkillName.MagicResist, 25.1, 40.0); + SetSkill(SkillName.Tactics, 35.1, 50.0); + SetSkill(SkillName.Wrestling, 50.1, 65.0); - SetSkill( SkillName.Poisoning, 60.1, 80.0 ); - SetSkill( SkillName.MagicResist, 25.1, 40.0 ); - SetSkill( SkillName.Tactics, 35.1, 50.0 ); - SetSkill( SkillName.Wrestling, 50.1, 65.0 ); + Fame = 600; + Karma = -600; - Fame = 600; - Karma = -600; + VirtualArmor = 16; - VirtualArmor = 16; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 59.1; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 59.1; + PackItem(new SpidersSilk(5)); + } - PackItem( new SpidersSilk( 5 ) ); - } + public GiantSpider(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a giant spider corpse"; + public override string DefaultName => "a giant spider"; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Arachnid; - public override Poison PoisonImmune => Poison.Regular; - public override Poison HitPoison => Poison.Regular; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Arachnid; + public override Poison PoisonImmune => Poison.Regular; + public override Poison HitPoison => Poison.Regular; - public GiantSpider( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanDrone.cs b/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanDrone.cs index 5c9950091..f1ee8e028 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanDrone.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanDrone.cs @@ -2,74 +2,74 @@ using Server.Items; namespace Server.Mobiles { - public class TerathanDrone : BaseCreature - { - public override string CorpseName => "a terathan drone corpse"; - public override string DefaultName => "a terathan drone"; + public class TerathanDrone : BaseCreature + { + [Constructible] + public TerathanDrone() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 71; + BaseSoundID = 594; - [Constructible] - public TerathanDrone() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 71; - BaseSoundID = 594; + SetStr(36, 65); + SetDex(96, 145); + SetInt(21, 45); - SetStr( 36, 65 ); - SetDex( 96, 145 ); - SetInt( 21, 45 ); + SetHits(22, 39); + SetMana(0); - SetHits( 22, 39 ); - SetMana( 0 ); + SetDamage(6, 12); - SetDamage( 6, 12 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 15, 25); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + SetSkill(SkillName.Poisoning, 40.1, 60.0); + SetSkill(SkillName.MagicResist, 30.1, 45.0); + SetSkill(SkillName.Tactics, 30.1, 50.0); + SetSkill(SkillName.Wrestling, 40.1, 50.0); - SetSkill( SkillName.Poisoning, 40.1, 60.0 ); - SetSkill( SkillName.MagicResist, 30.1, 45.0 ); - SetSkill( SkillName.Tactics, 30.1, 50.0 ); - SetSkill( SkillName.Wrestling, 40.1, 50.0 ); + Fame = 2000; + Karma = -2000; - Fame = 2000; - Karma = -2000; + VirtualArmor = 24; - VirtualArmor = 24; + PackItem(new SpidersSilk(2)); + } - PackItem( new SpidersSilk( 2 ) ); - } + public TerathanDrone(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - // TODO: weapon? - } + public override string CorpseName => "a terathan drone corpse"; + public override string DefaultName => "a terathan drone"; - public override int Meat => 4; + public override int Meat => 4; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public TerathanDrone( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + // TODO: weapon? + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 589 ) - BaseSoundID = 594; - } - } -} + if (BaseSoundID == 589) + BaseSoundID = 594; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanWarrior.cs b/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanWarrior.cs index 2f52527cb..3c00a1cfb 100644 --- a/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanWarrior.cs +++ b/Scripts/Mobiles/Monsters/Arachnid/Melee/TerathanWarrior.cs @@ -1,71 +1,73 @@ +using Server.Engines.Plants; + namespace Server.Mobiles { - public class TerathanWarrior : BaseCreature - { - public override string CorpseName => "a terathan warrior corpse"; - public override string DefaultName => "a terathan warrior"; + public class TerathanWarrior : BaseCreature + { + [Constructible] + public TerathanWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 70; + BaseSoundID = 589; - [Constructible] - public TerathanWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 70; - BaseSoundID = 589; + SetStr(166, 215); + SetDex(96, 145); + SetInt(41, 65); - SetStr( 166, 215 ); - SetDex( 96, 145 ); - SetInt( 41, 65 ); + SetHits(100, 129); + SetMana(0); - SetHits( 100, 129 ); - SetMana( 0 ); + SetDamage(7, 17); - SetDamage( 7, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.Poisoning, 60.1, 80.0); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); - SetSkill( SkillName.Poisoning, 60.1, 80.0 ); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 30; - VirtualArmor = 30; + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(3)); + } - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(3) ); - } + public TerathanWarrior(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a terathan warrior corpse"; + public override string DefaultName => "a terathan warrior"; - public override int TreasureMapLevel => 1; - public override int Meat => 4; + public override int TreasureMapLevel => 1; + public override int Meat => 4; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public TerathanWarrior( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/AcidElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/AcidElemental.cs index 97f324bab..f3b92d71b 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/AcidElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/AcidElemental.cs @@ -1,84 +1,84 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.ToxicElemental" )] - public class AcidElemental : BaseCreature - { - public override string CorpseName => "an acid elemental corpse"; - public override string DefaultName => "an acid elemental"; + [TypeAlias("Server.Mobiles.ToxicElemental")] + public class AcidElemental : BaseCreature + { + [Constructible] + public AcidElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x9E; + BaseSoundID = 278; - [Constructible] - public AcidElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x9E; - BaseSoundID = 278; + SetStr(326, 355); + SetDex(66, 85); + SetInt(271, 295); - SetStr( 326, 355 ); - SetDex( 66, 85 ); - SetInt( 271, 295 ); + SetHits(196, 213); - SetHits( 196, 213 ); + SetDamage(9, 15); - SetDamage( 9, 15 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Fire, 50); + SetDamageType(ResistanceType.Energy, 25); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Fire, 50 ); - SetDamageType( ResistanceType.Energy, 25 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Anatomy, 30.3, 60.0); + SetSkill(SkillName.EvalInt, 70.1, 85.0); + SetSkill(SkillName.Magery, 70.1, 85.0); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 80.1, 90.0); + SetSkill(SkillName.Wrestling, 70.1, 90.0); - SetSkill( SkillName.Anatomy, 30.3, 60.0 ); - SetSkill( SkillName.EvalInt, 70.1, 85.0 ); - SetSkill( SkillName.Magery, 70.1, 85.0 ); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 80.1, 90.0 ); - SetSkill( SkillName.Wrestling, 70.1, 90.0 ); + Fame = 10000; + Karma = -10000; - Fame = 10000; - Karma = -10000; + VirtualArmor = 40; + } - VirtualArmor = 40; - } + public AcidElemental(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - } + public override string CorpseName => "an acid elemental corpse"; + public override string DefaultName => "an acid elemental"; - public override bool BleedImmune => true; - public override Poison HitPoison => Poison.Lethal; - public override double HitPoisonChance => 0.6; + public override bool BleedImmune => true; + public override Poison HitPoison => Poison.Lethal; + public override double HitPoisonChance => 0.6; - public override int TreasureMapLevel => Core.AOS ? 2 : 3; + public override int TreasureMapLevel => Core.AOS ? 2 : 3; - public AcidElemental( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 263 ) - BaseSoundID = 278; + if (BaseSoundID == 263) + BaseSoundID = 278; - if ( Body == 13 ) - Body = 0x9E; + if (Body == 13) + Body = 0x9E; - if ( Hue == 0x4001 ) - Hue = 0; - } - } -} + if (Hue == 0x4001) + Hue = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/AirElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/AirElemental.cs index 121b2f9b2..81536c57c 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/AirElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/AirElemental.cs @@ -1,79 +1,79 @@ namespace Server.Mobiles { - public class AirElemental : BaseCreature - { - public override string CorpseName => "an air elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; + public class AirElemental : BaseCreature + { + [Constructible] + public AirElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 13; + Hue = 0x4001; + BaseSoundID = 655; - public override string DefaultName => "an air elemental"; + SetStr(126, 155); + SetDex(166, 185); + SetInt(101, 125); - [Constructible] - public AirElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 13; - Hue = 0x4001; - BaseSoundID = 655; + SetHits(76, 93); - SetStr( 126, 155 ); - SetDex( 166, 185 ); - SetInt( 101, 125 ); + SetDamage(8, 10); - SetHits( 76, 93 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 40); + SetDamageType(ResistanceType.Energy, 40); - SetDamage( 8, 10 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 25, 35); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 40 ); - SetDamageType( ResistanceType.Energy, 40 ); + SetSkill(SkillName.EvalInt, 60.1, 75.0); + SetSkill(SkillName.Magery, 60.1, 75.0); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 60.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + Fame = 4500; + Karma = -4500; - SetSkill( SkillName.EvalInt, 60.1, 75.0 ); - SetSkill( SkillName.Magery, 60.1, 75.0 ); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 60.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + VirtualArmor = 40; + ControlSlots = 2; + } - Fame = 4500; - Karma = -4500; + public AirElemental(Serial serial) : base(serial) + { + } - VirtualArmor = 40; - ControlSlots = 2; - } + public override string CorpseName => "an air elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.MedScrolls ); - } + public override string DefaultName => "an air elemental"; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 2; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 2; - public AirElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.MedScrolls); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 263 ) - BaseSoundID = 655; - } - } -} + if (BaseSoundID == 263) + BaseSoundID = 655; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/BloodElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/BloodElemental.cs index 40f583231..3c71f2fcf 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/BloodElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/BloodElemental.cs @@ -1,69 +1,69 @@ namespace Server.Mobiles { - public class BloodElemental : BaseCreature - { - public override string CorpseName => "a blood elemental corpse"; - public override string DefaultName => "a blood elemental"; + public class BloodElemental : BaseCreature + { + [Constructible] + public BloodElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 159; + BaseSoundID = 278; - [Constructible] - public BloodElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 159; - BaseSoundID = 278; + SetStr(526, 615); + SetDex(66, 85); + SetInt(226, 350); - SetStr( 526, 615 ); - SetDex( 66, 85 ); - SetInt( 226, 350 ); + SetHits(316, 369); - SetHits( 316, 369 ); + SetDamage(17, 27); - SetDamage( 17, 27 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Poison, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Poison, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 85.1, 100.0); + SetSkill(SkillName.Magery, 85.1, 100.0); + SetSkill(SkillName.Meditation, 10.4, 50.0); + SetSkill(SkillName.MagicResist, 80.1, 95.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); - SetSkill( SkillName.EvalInt, 85.1, 100.0 ); - SetSkill( SkillName.Magery, 85.1, 100.0 ); - SetSkill( SkillName.Meditation, 10.4, 50.0 ); - SetSkill( SkillName.MagicResist, 80.1, 95.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); + Fame = 12500; + Karma = -12500; - Fame = 12500; - Karma = -12500; + VirtualArmor = 60; + } - VirtualArmor = 60; - } + public BloodElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a blood elemental corpse"; + public override string DefaultName => "a blood elemental"; - public override int TreasureMapLevel => 5; + public override int TreasureMapLevel => 5; - public BloodElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/Efreet.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/Efreet.cs index 95d160ab6..620d64b2a 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/Efreet.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/Efreet.cs @@ -2,81 +2,89 @@ using Server.Items; namespace Server.Mobiles { - public class Efreet : BaseCreature - { - public override string CorpseName => "an efreet corpse"; - public override string DefaultName => "an efreet"; + public class Efreet : BaseCreature + { + [Constructible] + public Efreet() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 131; + BaseSoundID = 768; - [Constructible] - public Efreet () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 131; - BaseSoundID = 768; + SetStr(326, 355); + SetDex(266, 285); + SetInt(171, 195); - SetStr( 326, 355 ); - SetDex( 266, 285 ); - SetInt( 171, 195 ); + SetHits(196, 213); - SetHits( 196, 213 ); + SetDamage(11, 13); - SetDamage( 11, 13 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Fire, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Fire, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 60.1, 75.0); + SetSkill(SkillName.Magery, 60.1, 75.0); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 60.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.EvalInt, 60.1, 75.0 ); - SetSkill( SkillName.Magery, 60.1, 75.0 ); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 60.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 10000; + Karma = -10000; - Fame = 10000; - Karma = -10000; + VirtualArmor = 56; + } - VirtualArmor = 56; - } + public Efreet(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems ); + public override string CorpseName => "an efreet corpse"; + public override string DefaultName => "an efreet"; - if ( 0.02 > Utility.RandomDouble() ) - { - switch ( Utility.Random( 5 ) ) - { - case 0: PackItem( new DaemonArms() ); break; - case 1: PackItem( new DaemonChest() ); break; - case 2: PackItem( new DaemonGloves() ); break; - case 3: PackItem( new DaemonLegs() ); break; - case 4: PackItem( new DaemonHelm() ); break; - } - } - } + public override int TreasureMapLevel => Core.AOS ? 4 : 5; - public override int TreasureMapLevel => Core.AOS ? 4 : 5; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems); - public Efreet( Serial serial ) : base( serial ) - { - } + if (0.02 > Utility.RandomDouble()) + switch (Utility.Random(5)) + { + case 0: + PackItem(new DaemonArms()); + break; + case 1: + PackItem(new DaemonChest()); + break; + case 2: + PackItem(new DaemonGloves()); + break; + case 3: + PackItem(new DaemonLegs()); + break; + case 4: + PackItem(new DaemonHelm()); + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/FireElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/FireElemental.cs index 9bab70ee8..dd7ea4d73 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/FireElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/FireElemental.cs @@ -2,81 +2,81 @@ using Server.Items; namespace Server.Mobiles { - public class FireElemental : BaseCreature - { - public override string CorpseName => "a fire elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; + public class FireElemental : BaseCreature + { + [Constructible] + public FireElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 15; + BaseSoundID = 838; - public override string DefaultName => "a fire elemental"; + SetStr(126, 155); + SetDex(166, 185); + SetInt(101, 125); - [Constructible] - public FireElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 15; - BaseSoundID = 838; + SetHits(76, 93); - SetStr( 126, 155 ); - SetDex( 166, 185 ); - SetInt( 101, 125 ); + SetDamage(7, 9); - SetHits( 76, 93 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Fire, 75); - SetDamage( 7, 9 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 60, 80); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Fire, 75 ); + SetSkill(SkillName.EvalInt, 60.1, 75.0); + SetSkill(SkillName.Magery, 60.1, 75.0); + SetSkill(SkillName.MagicResist, 75.2, 105.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 70.1, 100.0); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 60, 80 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 4500; + Karma = -4500; - SetSkill( SkillName.EvalInt, 60.1, 75.0 ); - SetSkill( SkillName.Magery, 60.1, 75.0 ); - SetSkill( SkillName.MagicResist, 75.2, 105.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 70.1, 100.0 ); + VirtualArmor = 40; + ControlSlots = 4; - Fame = 4500; - Karma = -4500; + PackItem(new SulfurousAsh(3)); - VirtualArmor = 40; - ControlSlots = 4; + AddItem(new LightSource()); + } - PackItem( new SulfurousAsh( 3 ) ); + public FireElemental(Serial serial) : base(serial) + { + } - AddItem( new LightSource() ); - } + public override string CorpseName => "a fire elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Gems ); - } + public override string DefaultName => "a fire elemental"; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 2; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 2; - public FireElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 274 ) - BaseSoundID = 838; - } - } -} + if (BaseSoundID == 274) + BaseSoundID = 838; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/IceElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/IceElemental.cs index f13da6f96..29b2afe7a 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/IceElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/IceElemental.cs @@ -2,70 +2,70 @@ using Server.Items; namespace Server.Mobiles { - public class IceElemental : BaseCreature - { - public override string CorpseName => "an ice elemental corpse"; - public override string DefaultName => "an ice elemental"; + public class IceElemental : BaseCreature + { + [Constructible] + public IceElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 161; + BaseSoundID = 268; - [Constructible] - public IceElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 161; - BaseSoundID = 268; + SetStr(156, 185); + SetDex(96, 115); + SetInt(171, 192); - SetStr( 156, 185 ); - SetDex( 96, 115 ); - SetInt( 171, 192 ); + SetHits(94, 111); - SetHits( 94, 111 ); + SetDamage(10, 21); - SetDamage( 10, 21 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Cold, 75); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Cold, 75 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.EvalInt, 10.5, 60.0); + SetSkill(SkillName.Magery, 10.5, 60.0); + SetSkill(SkillName.MagicResist, 30.1, 80.0); + SetSkill(SkillName.Tactics, 70.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.EvalInt, 10.5, 60.0 ); - SetSkill( SkillName.Magery, 10.5, 60.0 ); - SetSkill( SkillName.MagicResist, 30.1, 80.0 ); - SetSkill( SkillName.Tactics, 70.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 40; - VirtualArmor = 40; + PackItem(new BlackPearl()); + PackReg(3); + } - PackItem( new BlackPearl() ); - PackReg( 3 ); - } + public IceElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.Gems, 2 ); - } - public override bool BleedImmune => true; + public override string CorpseName => "an ice elemental corpse"; + public override string DefaultName => "an ice elemental"; + public override bool BleedImmune => true; - public IceElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/PoisonElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/PoisonElemental.cs index c4a9c1d10..46c664ef5 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/PoisonElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/PoisonElemental.cs @@ -2,80 +2,80 @@ using Server.Items; namespace Server.Mobiles { - public class PoisonElemental : BaseCreature - { - public override string CorpseName => "a poison elementals corpse"; - public override string DefaultName => "a poison elemental"; + public class PoisonElemental : BaseCreature + { + [Constructible] + public PoisonElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 162; + BaseSoundID = 263; - [Constructible] - public PoisonElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 162; - BaseSoundID = 263; + SetStr(426, 515); + SetDex(166, 185); + SetInt(361, 435); - SetStr( 426, 515 ); - SetDex( 166, 185 ); - SetInt( 361, 435 ); + SetHits(256, 309); - SetHits( 256, 309 ); + SetDamage(12, 18); - SetDamage( 12, 18 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Poison, 90); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Poison, 90 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 80.1, 95.0); + SetSkill(SkillName.Magery, 80.1, 95.0); + SetSkill(SkillName.Meditation, 80.2, 120.0); + SetSkill(SkillName.Poisoning, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 85.2, 115.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 70.1, 90.0); - SetSkill( SkillName.EvalInt, 80.1, 95.0 ); - SetSkill( SkillName.Magery, 80.1, 95.0 ); - SetSkill( SkillName.Meditation, 80.2, 120.0 ); - SetSkill( SkillName.Poisoning, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 85.2, 115.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 70.1, 90.0 ); + Fame = 12500; + Karma = -12500; - Fame = 12500; - Karma = -12500; + VirtualArmor = 70; - VirtualArmor = 70; + PackItem(new Nightshade(4)); + PackItem(new LesserPoisonPotion()); + } - PackItem( new Nightshade( 4 ) ); - PackItem( new LesserPoisonPotion() ); - } + public PoisonElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls ); - } + public override string CorpseName => "a poison elementals corpse"; + public override string DefaultName => "a poison elemental"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; - public override double HitPoisonChance => 0.75; + public override Poison HitPoison => Poison.Lethal; + public override double HitPoisonChance => 0.75; - public override int TreasureMapLevel => 5; + public override int TreasureMapLevel => 5; - public PoisonElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Magic/WaterElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Magic/WaterElemental.cs index f71ad7704..076f24bd4 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Magic/WaterElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Magic/WaterElemental.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class WaterElemental : BaseCreature - { - public override string CorpseName => "a water elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; + public class WaterElemental : BaseCreature + { + [Constructible] + public WaterElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 16; + BaseSoundID = 278; - public override string DefaultName => "a water elemental"; + SetStr(126, 155); + SetDex(66, 85); + SetInt(101, 125); - [Constructible] - public WaterElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 16; - BaseSoundID = 278; + SetHits(76, 93); - SetStr( 126, 155 ); - SetDex( 66, 85 ); - SetInt( 101, 125 ); + SetDamage(7, 9); - SetHits( 76, 93 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 7, 9 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 10, 25); + SetResistance(ResistanceType.Cold, 10, 25); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 5, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.EvalInt, 60.1, 75.0); + SetSkill(SkillName.Magery, 60.1, 75.0); + SetSkill(SkillName.MagicResist, 100.1, 115.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 10, 25 ); - SetResistance( ResistanceType.Cold, 10, 25 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + Fame = 4500; + Karma = -4500; - SetSkill( SkillName.EvalInt, 60.1, 75.0 ); - SetSkill( SkillName.Magery, 60.1, 75.0 ); - SetSkill( SkillName.MagicResist, 100.1, 115.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + VirtualArmor = 40; + ControlSlots = 3; + CanSwim = true; - Fame = 4500; - Karma = -4500; + PackItem(new BlackPearl(3)); + } - VirtualArmor = 40; - ControlSlots = 3; - CanSwim = true; + public WaterElemental(Serial serial) : base(serial) + { + } - PackItem( new BlackPearl( 3 ) ); - } + public override string CorpseName => "a water elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Potions ); - } + public override string DefaultName => "a water elemental"; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 2; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 2; - public WaterElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Melee/EarthElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Melee/EarthElemental.cs index e2919c5ce..ac8fd3ea1 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Melee/EarthElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Melee/EarthElemental.cs @@ -2,78 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class EarthElemental : BaseCreature - { - public override string CorpseName => "an earth elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; + public class EarthElemental : BaseCreature + { + [Constructible] + public EarthElemental() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 14; + BaseSoundID = 268; - public override string DefaultName => "an earth elemental"; + SetStr(126, 155); + SetDex(66, 85); + SetInt(71, 92); - [Constructible] - public EarthElemental() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 14; - BaseSoundID = 268; + SetHits(76, 93); - SetStr( 126, 155 ); - SetDex( 66, 85 ); - SetInt( 71, 92 ); + SetDamage(9, 16); - SetHits( 76, 93 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 9, 16 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 15, 25); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + Fame = 3500; + Karma = -3500; - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + VirtualArmor = 34; + ControlSlots = 2; - Fame = 3500; - Karma = -3500; + PackItem(new FertileDirt(Utility.RandomMinMax(1, 4))); + PackItem(new MandrakeRoot()); - VirtualArmor = 34; - ControlSlots = 2; + Item ore = new IronOre(5); + ore.ItemID = 0x19B7; + PackItem(ore); + } - PackItem( new FertileDirt( Utility.RandomMinMax( 1, 4 ) ) ); - PackItem( new MandrakeRoot() ); + public EarthElemental(Serial serial) : base(serial) + { + } - Item ore = new IronOre( 5 ); - ore.ItemID = 0x19B7; - PackItem( ore ); - } + public override string CorpseName => "an earth elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Gems ); - } + public override string DefaultName => "an earth elemental"; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; - public EarthElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Elemental/Melee/SnowElemental.cs b/Scripts/Mobiles/Monsters/Elemental/Melee/SnowElemental.cs index fca64d9c1..de1fb9548 100644 --- a/Scripts/Mobiles/Monsters/Elemental/Melee/SnowElemental.cs +++ b/Scripts/Mobiles/Monsters/Elemental/Melee/SnowElemental.cs @@ -2,72 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class SnowElemental : BaseCreature - { - public override string CorpseName => "a snow elemental corpse"; - public override string DefaultName => "a snow elemental"; + public class SnowElemental : BaseCreature + { + [Constructible] + public SnowElemental() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 163; + BaseSoundID = 263; - [Constructible] - public SnowElemental() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 163; - BaseSoundID = 263; + SetStr(326, 355); + SetDex(166, 185); + SetInt(71, 95); - SetStr( 326, 355 ); - SetDex( 166, 185 ); - SetInt( 71, 95 ); + SetHits(196, 213); - SetHits( 196, 213 ); + SetDamage(11, 17); - SetDamage( 11, 17 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 80 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.MagicResist, 50.1, 65.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 65.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + VirtualArmor = 50; - VirtualArmor = 50; + PackItem(new BlackPearl(3)); + Item ore = new IronOre(3); + ore.ItemID = 0x19B8; + PackItem(ore); + } - PackItem( new BlackPearl( 3 ) ); - Item ore = new IronOre( 3 ); - ore.ItemID = 0x19B8; - PackItem( ore ); - } + public SnowElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a snow elemental corpse"; + public override string DefaultName => "a snow elemental"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public override int TreasureMapLevel => Utility.RandomList( 2, 3 ); + public override int TreasureMapLevel => Utility.RandomList(2, 3); - public SnowElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/AncientLich.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/AncientLich.cs index c2112002c..d00543479 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/AncientLich.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/AncientLich.cs @@ -1,103 +1,103 @@ namespace Server.Mobiles { - public class AncientLich : BaseCreature - { - public override string CorpseName => "an ancient lich's corpse"; - [Constructible] - public AncientLich() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "ancient lich" ); - Body = 78; - BaseSoundID = 412; + public class AncientLich : BaseCreature + { + [Constructible] + public AncientLich() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("ancient lich"); + Body = 78; + BaseSoundID = 412; - SetStr( 216, 305 ); - SetDex( 96, 115 ); - SetInt( 966, 1045 ); + SetStr(216, 305); + SetDex(96, 115); + SetInt(966, 1045); - SetHits( 560, 595 ); + SetHits(560, 595); - SetDamage( 15, 27 ); + SetDamage(15, 27); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 40 ); - SetDamageType( ResistanceType.Energy, 40 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 40); + SetDamageType(ResistanceType.Energy, 40); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 25, 30); - SetSkill( SkillName.EvalInt, 120.1, 130.0 ); - SetSkill( SkillName.Magery, 120.1, 130.0 ); - SetSkill( SkillName.Meditation, 100.1, 101.0 ); - SetSkill( SkillName.Poisoning, 100.1, 101.0 ); - SetSkill( SkillName.MagicResist, 175.2, 200.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 75.1, 100.0 ); - SetSkill( SkillName.Necromancy, 120.1, 130.0 ); - SetSkill( SkillName.SpiritSpeak, 120.1, 130.0 ); + SetSkill(SkillName.EvalInt, 120.1, 130.0); + SetSkill(SkillName.Magery, 120.1, 130.0); + SetSkill(SkillName.Meditation, 100.1, 101.0); + SetSkill(SkillName.Poisoning, 100.1, 101.0); + SetSkill(SkillName.MagicResist, 175.2, 200.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 75.1, 100.0); + SetSkill(SkillName.Necromancy, 120.1, 130.0); + SetSkill(SkillName.SpiritSpeak, 120.1, 130.0); - Fame = 23000; - Karma = -23000; + Fame = 23000; + Karma = -23000; - VirtualArmor = 60; - PackNecroReg( 30, 275 ); + VirtualArmor = 60; + PackNecroReg(30, 275); + } - } + public AncientLich(Serial serial) : base(serial) + { + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string CorpseName => "an ancient lich's corpse"; - public override int GetIdleSound() - { - return 0x19D; - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override int GetAngerSound() - { - return 0x175; - } + public override bool Unprovokable => true; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => 5; - public override int GetDeathSound() - { - return 0x108; - } + public override int GetIdleSound() + { + return 0x19D; + } - public override int GetAttackSound() - { - return 0xE2; - } + public override int GetAngerSound() + { + return 0x175; + } - public override int GetHurtSound() - { - return 0x28B; - } + public override int GetDeathSound() + { + return 0x108; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override int GetAttackSound() + { + return 0xE2; + } - public override bool Unprovokable => true; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 5; + public override int GetHurtSound() + { + return 0x28B; + } - public AncientLich( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/ArcaneDaemon.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/ArcaneDaemon.cs index 19ebf1227..0f6b61ba9 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/ArcaneDaemon.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/ArcaneDaemon.cs @@ -2,70 +2,74 @@ using Server.Items; namespace Server.Mobiles { - public class ArcaneDaemon : BaseCreature - { - public override string CorpseName => "an arcane daemon corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ConcussionBlow; + public class ArcaneDaemon : BaseCreature + { + [Constructible] + public ArcaneDaemon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x310; + BaseSoundID = 0x47D; - public override string DefaultName => "an arcane daemon"; + SetStr(131, 150); + SetDex(126, 145); + SetInt(301, 350); - [Constructible] - public ArcaneDaemon() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x310; - BaseSoundID = 0x47D; + SetHits(101, 115); - SetStr( 131, 150 ); - SetDex( 126, 145 ); - SetInt( 301, 350 ); + SetDamage(12, 16); - SetHits( 101, 115 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Fire, 20); - SetDamage( 12, 16 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Fire, 20 ); + SetSkill(SkillName.MagicResist, 85.1, 95.0); + SetSkill(SkillName.Tactics, 70.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); + SetSkill(SkillName.Magery, 80.1, 90.0); + SetSkill(SkillName.EvalInt, 70.1, 80.0); + SetSkill(SkillName.Meditation, 70.1, 80.0); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 7000; + Karma = -10000; - SetSkill( SkillName.MagicResist, 85.1, 95.0 ); - SetSkill( SkillName.Tactics, 70.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); - SetSkill( SkillName.Magery, 80.1, 90.0 ); - SetSkill( SkillName.EvalInt, 70.1, 80.0 ); - SetSkill( SkillName.Meditation, 70.1, 80.0 ); + VirtualArmor = 55; + } - Fame = 7000; - Karma = -10000; + public ArcaneDaemon(Serial serial) : base(serial) + { + } - VirtualArmor = 55; - } + public override string CorpseName => "an arcane daemon corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - } + public override string DefaultName => "an arcane daemon"; - public override Poison PoisonImmune => Poison.Deadly; + public override Poison PoisonImmune => Poison.Deadly; - public ArcaneDaemon( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ConcussionBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Balron.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Balron.cs index af61c5ec3..b480c946a 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Balron.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Balron.cs @@ -2,76 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class Balron : BaseCreature - { - public override string CorpseName => "a balron corpse"; - [Constructible] - public Balron () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "balron" ); - Body = 40; - BaseSoundID = 357; + public class Balron : BaseCreature + { + [Constructible] + public Balron() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("balron"); + Body = 40; + BaseSoundID = 357; - SetStr( 986, 1185 ); - SetDex( 177, 255 ); - SetInt( 151, 250 ); + SetStr(986, 1185); + SetDex(177, 255); + SetInt(151, 250); - SetHits( 592, 711 ); + SetHits(592, 711); - SetDamage( 22, 29 ); + SetDamage(22, 29); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Fire, 25 ); - SetDamageType( ResistanceType.Energy, 25 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Fire, 25); + SetDamageType(ResistanceType.Energy, 25); - SetResistance( ResistanceType.Physical, 65, 80 ); - SetResistance( ResistanceType.Fire, 60, 80 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetResistance(ResistanceType.Physical, 65, 80); + SetResistance(ResistanceType.Fire, 60, 80); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40, 50); - SetSkill( SkillName.Anatomy, 25.1, 50.0 ); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 95.5, 100.0 ); - SetSkill( SkillName.Meditation, 25.1, 50.0 ); - SetSkill( SkillName.MagicResist, 100.5, 150.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + SetSkill(SkillName.Anatomy, 25.1, 50.0); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 95.5, 100.0); + SetSkill(SkillName.Meditation, 25.1, 50.0); + SetSkill(SkillName.MagicResist, 100.5, 150.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - Fame = 24000; - Karma = -24000; + Fame = 24000; + Karma = -24000; - VirtualArmor = 90; + VirtualArmor = 90; - PackItem( new Longsword() ); - } + PackItem(new Longsword()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public Balron(Serial serial) : base(serial) + { + } - public override bool CanRummageCorpses => true; - public override Poison PoisonImmune => Poison.Deadly; - public override int TreasureMapLevel => 5; - public override int Meat => 1; + public override string CorpseName => "a balron corpse"; - public Balron( Serial serial ) : base( serial ) - { - } + public override bool CanRummageCorpses => true; + public override Poison PoisonImmune => Poison.Deadly; + public override int TreasureMapLevel => 5; + public override int Meat => 1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Betrayer.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Betrayer.cs index 8820a9349..f4f2b3240 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Betrayer.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Betrayer.cs @@ -4,180 +4,180 @@ using Server.Network; namespace Server.Mobiles { - public class Betrayer : BaseCreature - { - public override string CorpseName => "a betrayer corpse"; - private bool m_Stunning; + public class Betrayer : BaseCreature + { + private DateTime m_NextAbilityTime; + private bool m_Stunning; - public override string DefaultName => "a betrayer"; + [Constructible] + public Betrayer() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 767; - [Constructible] - public Betrayer() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 767; + SetStr(401, 500); + SetDex(81, 100); + SetInt(151, 200); - SetStr( 401, 500 ); - SetDex( 81, 100 ); - SetInt( 151, 200 ); + SetHits(241, 300); - SetHits( 241, 300 ); + SetDamage(16, 22); - SetDamage( 16, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.Anatomy, 90.1, 100.0); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 50.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 120.1, 130.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.Anatomy, 90.1, 100.0 ); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 50.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 120.1, 130.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + VirtualArmor = 65; + SpeechHue = Utility.RandomDyedHue(); - VirtualArmor = 65; - SpeechHue = Utility.RandomDyedHue(); + PackItem(new PowerCrystal()); - PackItem( new PowerCrystal() ); + if (0.02 > Utility.RandomDouble()) + PackItem(new BlackthornWelcomeBook()); - if ( 0.02 > Utility.RandomDouble() ) - PackItem( new BlackthornWelcomeBook() ); + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(5, 30)); + } - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 5, 30 ) ); - } + public Betrayer(Serial serial) + : base(serial) + { + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override string CorpseName => "a betrayer corpse"; - if ( 0.05 > Utility.RandomDouble() ) - { - if ( !IsParagon ) - { - if ( 0.75 > Utility.RandomDouble() ) - c.DropItem( DawnsMusicGear.RandomCommon ); - else - c.DropItem( DawnsMusicGear.RandomUncommon ); - } - else - c.DropItem( DawnsMusicGear.RandomRare ); - } - } + public override string DefaultName => "a betrayer"; - public override int GetDeathSound() - { - return 0x423; - } + public override bool AlwaysMurderer => true; + public override bool BardImmune => !Core.AOS; + public override Poison PoisonImmune => Poison.Lethal; + public override int Meat => 1; + public override int TreasureMapLevel => 5; - public override int GetAttackSound() - { - return 0x23B; - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override int GetHurtSound() - { - return 0x140; - } + if (0.05 > Utility.RandomDouble()) + { + if (!IsParagon) + { + if (0.75 > Utility.RandomDouble()) + c.DropItem(DawnsMusicGear.RandomCommon); + else + c.DropItem(DawnsMusicGear.RandomUncommon); + } + else + { + c.DropItem(DawnsMusicGear.RandomRare); + } + } + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 1 ); - } + public override int GetDeathSound() + { + return 0x423; + } - public override bool AlwaysMurderer => true; - public override bool BardImmune => !Core.AOS; - public override Poison PoisonImmune => Poison.Lethal; - public override int Meat => 1; - public override int TreasureMapLevel => 5; + public override int GetAttackSound() + { + return 0x23B; + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override int GetHurtSound() + { + return 0x140; + } - if ( !m_Stunning && 0.3 > Utility.RandomDouble() ) - { - m_Stunning = true; + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 1); + } - defender.Animate( 21, 6, 1, true, false, 0 ); - PlaySound( 0xEE ); - defender.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You have been stunned by a colossal blow!" ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( Weapon is BaseWeapon weapon ) - weapon.OnHit( this, defender ); + if (!m_Stunning && 0.3 > Utility.RandomDouble()) + { + m_Stunning = true; - if ( defender.Alive ) - { - defender.Frozen = true; - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( Recover_Callback ), defender ); - } - } - } + defender.Animate(21, 6, 1, true, false, 0); + PlaySound(0xEE); + defender.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You have been stunned by a colossal blow!"); - private void Recover_Callback( object state ) - { - if ( state is Mobile defender ) - { - defender.Frozen = false; - defender.Combatant = null; - defender.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You recover your senses." ); - } + if (Weapon is BaseWeapon weapon) + weapon.OnHit(this, defender); - m_Stunning = false; - } + if (defender.Alive) + { + defender.Frozen = true; + Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(Recover_Callback), defender); + } + } + } - private DateTime m_NextAbilityTime; + private void Recover_Callback(object state) + { + if (state is Mobile defender) + { + defender.Frozen = false; + defender.Combatant = null; + defender.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You recover your senses."); + } - public override void OnActionCombat() - { - Mobile combatant = Combatant; + m_Stunning = false; + } - if ( DateTime.UtcNow < m_NextAbilityTime || combatant == null || combatant.Deleted || combatant.Map != Map || !InRange( combatant, 3 ) || !CanBeHarmful( combatant ) || !InLOS( combatant ) ) - return; + public override void OnActionCombat() + { + Mobile combatant = Combatant; - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 5, 30 ) ); + if (DateTime.UtcNow < m_NextAbilityTime || combatant == null || combatant.Deleted || combatant.Map != Map || + !InRange(combatant, 3) || !CanBeHarmful(combatant) || !InLOS(combatant)) + return; - if ( Utility.RandomBool() ) - { - FixedParticles( 0x376A, 9, 32, 0x2539, EffectLayer.LeftHand ); - PlaySound( 0x1DE ); + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(5, 30)); - foreach ( Mobile m in GetMobilesInRange( 2 ) ) - { - if ( m != this && IsEnemy( m ) ) - { - m.ApplyPoison( this, Poison.Deadly ); - } - } - } - } + if (Utility.RandomBool()) + { + FixedParticles(0x376A, 9, 32, 0x2539, EffectLayer.LeftHand); + PlaySound(0x1DE); - public Betrayer( Serial serial ) - : base( serial ) - { - } + foreach (Mobile m in GetMobilesInRange(2)) + if (m != this && IsEnemy(m)) + m.ApplyPoison(this, Poison.Deadly); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Bogle.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Bogle.cs index a30bf46f4..280c98ec5 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Bogle.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Bogle.cs @@ -2,63 +2,63 @@ using Server.Items; namespace Server.Mobiles { - public class Bogle : BaseCreature - { - public override string CorpseName => "a ghostly corpse"; - public override string DefaultName => "a bogle"; + public class Bogle : BaseCreature + { + [Constructible] + public Bogle() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 153; + BaseSoundID = 0x482; - [Constructible] - public Bogle() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 153; - BaseSoundID = 0x482; + SetStr(76, 100); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(7, 11); - SetDamage( 7, 11 ); + SetSkill(SkillName.EvalInt, 55.1, 70.0); + SetSkill(SkillName.Magery, 55.1, 70.0); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - SetSkill( SkillName.EvalInt, 55.1, 70.0 ); - SetSkill( SkillName.Magery, 55.1, 70.0 ); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 28; + PackItem(Loot.RandomWeapon()); + PackItem(new Bone()); + } - VirtualArmor = 28; - PackItem( Loot.RandomWeapon() ); - PackItem( new Bone() ); - } + public Bogle(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a ghostly corpse"; + public override string DefaultName => "a bogle"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public Bogle( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/BoneMagi.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/BoneMagi.cs index a7d685213..eb0d179af 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/BoneMagi.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/BoneMagi.cs @@ -2,79 +2,79 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias("Server.Mobiles.BoneMage")] - public class BoneMagi : BaseCreature - { - public override string CorpseName => "a skeletal corpse"; - public override string DefaultName => "a bone mage"; + [TypeAlias("Server.Mobiles.BoneMage")] + public class BoneMagi : BaseCreature + { + [Constructible] + public BoneMagi() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 148; + BaseSoundID = 451; - [Constructible] - public BoneMagi() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 148; - BaseSoundID = 451; + SetStr(76, 100); + SetDex(56, 75); + SetInt(186, 210); - SetStr( 76, 100 ); - SetDex( 56, 75 ); - SetInt( 186, 210 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 60.1, 70.0); + SetSkill(SkillName.Magery, 60.1, 70.0); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); + SetSkill(SkillName.Necromancy, 89, 99.1); + SetSkill(SkillName.SpiritSpeak, 90.0, 99.0); - SetSkill( SkillName.EvalInt, 60.1, 70.0 ); - SetSkill( SkillName.Magery, 60.1, 70.0 ); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); - SetSkill( SkillName.Necromancy, 89, 99.1 ); - SetSkill( SkillName.SpiritSpeak, 90.0, 99.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 38; - VirtualArmor = 38; + PackReg(3); + PackNecroReg(3, 10); + PackItem(new Bone()); + } - PackReg( 3 ); - PackNecroReg( 3, 10 ); - PackItem( new Bone() ); - } + public BoneMagi(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "a skeletal corpse"; + public override string DefaultName => "a bone mage"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override Poison PoisonImmune => Poison.Regular; + public override Poison PoisonImmune => Poison.Regular; - public BoneMagi( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Daemon.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Daemon.cs index 5ab813be5..acd71e990 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Daemon.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Daemon.cs @@ -1,79 +1,80 @@ +using Server.Ethics; using Server.Factions; namespace Server.Mobiles { - public class Daemon : BaseCreature - { - public override string CorpseName => "a daemon corpse"; - public override double DispelDifficulty => 125.0; - public override double DispelFocus => 45.0; + public class Daemon : BaseCreature + { + [Constructible] + public Daemon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("daemon"); + Body = 9; + BaseSoundID = 357; - public override Faction FactionAllegiance => Shadowlords.Instance; - public override Ethics.Ethic EthicAllegiance => Ethics.Ethic.Evil; + SetStr(476, 505); + SetDex(76, 95); + SetInt(301, 325); - [Constructible] - public Daemon () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "daemon" ); - Body = 9; - BaseSoundID = 357; + SetHits(286, 303); - SetStr( 476, 505 ); - SetDex( 76, 95 ); - SetInt( 301, 325 ); + SetDamage(7, 14); - SetHits( 286, 303 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 7, 14 ); + SetResistance(ResistanceType.Physical, 45, 60); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.EvalInt, 70.1, 80.0); + SetSkill(SkillName.Magery, 70.1, 80.0); + SetSkill(SkillName.MagicResist, 85.1, 95.0); + SetSkill(SkillName.Tactics, 70.1, 80.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetResistance( ResistanceType.Physical, 45, 60 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 15000; + Karma = -15000; - SetSkill( SkillName.EvalInt, 70.1, 80.0 ); - SetSkill( SkillName.Magery, 70.1, 80.0 ); - SetSkill( SkillName.MagicResist, 85.1, 95.0 ); - SetSkill( SkillName.Tactics, 70.1, 80.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + VirtualArmor = 58; + ControlSlots = Core.SE ? 4 : 5; + } - Fame = 15000; - Karma = -15000; + public Daemon(Serial serial) : base(serial) + { + } - VirtualArmor = 58; - ControlSlots = Core.SE ? 4 : 5; - } + public override string CorpseName => "a daemon corpse"; + public override double DispelDifficulty => 125.0; + public override double DispelFocus => 45.0; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override Faction FactionAllegiance => Shadowlords.Instance; + public override Ethic EthicAllegiance => Ethic.Evil; - public override bool CanRummageCorpses => true; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 4; - public override int Meat => 1; - public override bool CanFly => true; + public override bool CanRummageCorpses => true; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 4; + public override int Meat => 1; + public override bool CanFly => true; - public Daemon( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/ElderGazer.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/ElderGazer.cs index af8b3c9a7..de6be28cf 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/ElderGazer.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/ElderGazer.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class ElderGazer : BaseCreature - { - public override string CorpseName => "an elder gazer corpse"; - public override string DefaultName => "an elder gazer"; + public class ElderGazer : BaseCreature + { + [Constructible] + public ElderGazer() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 22; + BaseSoundID = 377; - [Constructible] - public ElderGazer () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 22; - BaseSoundID = 377; + SetStr(296, 325); + SetDex(86, 105); + SetInt(291, 385); - SetStr( 296, 325 ); - SetDex( 86, 105 ); - SetInt( 291, 385 ); + SetHits(178, 195); - SetHits( 178, 195 ); + SetDamage(8, 19); - SetDamage( 8, 19 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Anatomy, 62.0, 100.0); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 115.1, 130.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); - SetSkill( SkillName.Anatomy, 62.0, 100.0 ); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 115.1, 130.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); + Fame = 12500; + Karma = -12500; - Fame = 12500; - Karma = -12500; + VirtualArmor = 50; + } - VirtualArmor = 50; - } + public ElderGazer(Serial serial) : base(serial) + { + } - public override int TreasureMapLevel => Core.AOS ? 4 : 0; + public override string CorpseName => "an elder gazer corpse"; + public override string DefaultName => "an elder gazer"; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - } + public override int TreasureMapLevel => Core.AOS ? 4 : 0; - public ElderGazer( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMage.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMage.cs index 6e41ec531..e101e2996 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMage.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMage.cs @@ -2,71 +2,72 @@ using Server.Items; namespace Server.Mobiles { - public class EvilMage : BaseCreature - { - public override string CorpseName => "an evil mage corpse"; - [Constructible] - public EvilMage() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "evil mage" ); - Title = "the evil mage"; - Body = 124; + public class EvilMage : BaseCreature + { + [Constructible] + public EvilMage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("evil mage"); + Title = "the evil mage"; + Body = 124; - SetStr( 81, 105 ); - SetDex( 91, 115 ); - SetInt( 96, 120 ); + SetStr(81, 105); + SetDex(91, 115); + SetInt(96, 120); - SetHits( 49, 63 ); + SetHits(49, 63); - SetDamage( 5, 10 ); + SetDamage(5, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetSkill( SkillName.EvalInt, 75.1, 100.0 ); - SetSkill( SkillName.Magery, 75.1, 100.0 ); - SetSkill( SkillName.MagicResist, 75.0, 97.5 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 20.2, 60.0 ); + SetSkill(SkillName.EvalInt, 75.1, 100.0); + SetSkill(SkillName.Magery, 75.1, 100.0); + SetSkill(SkillName.MagicResist, 75.0, 97.5); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 20.2, 60.0); - Fame = 2500; - Karma = -2500; + Fame = 2500; + Karma = -2500; - VirtualArmor = 16; - PackReg( 6 ); - PackItem( new Robe( Utility.RandomNeutralHue() ) ); // TODO: Proper hue - PackItem( new Sandals() ); - } + VirtualArmor = 16; + PackReg(6); + PackItem(new Robe(Utility.RandomNeutralHue())); // TODO: Proper hue + PackItem(new Sandals()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.MedScrolls ); - } + public EvilMage(Serial serial) : base(serial) + { + } - public override bool CanRummageCorpses => true; - public override bool AlwaysMurderer => true; - public override int Meat => 1; - public override int TreasureMapLevel => Core.AOS ? 1 : 0; + public override string CorpseName => "an evil mage corpse"; - public EvilMage( Serial serial ) : base( serial ) - { - } + public override bool CanRummageCorpses => true; + public override bool AlwaysMurderer => true; + public override int Meat => 1; + public override int TreasureMapLevel => Core.AOS ? 1 : 0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.MedScrolls); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMageLord.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMageLord.cs index b6fd5b0a0..4ada940eb 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMageLord.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/EvilMageLord.cs @@ -2,78 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public class EvilMageLord : BaseCreature - { - public override string CorpseName => "an evil mage lord corpse"; - [Constructible] - public EvilMageLord() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "evil mage lord" ); - Body = Utility.RandomList( 125, 126 ); + public class EvilMageLord : BaseCreature + { + [Constructible] + public EvilMageLord() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("evil mage lord"); + Body = Utility.RandomList(125, 126); - PackItem( new Robe( Utility.RandomMetalHue() ) ); - PackItem( new WizardsHat( Utility.RandomMetalHue() ) ); + PackItem(new Robe(Utility.RandomMetalHue())); + PackItem(new WizardsHat(Utility.RandomMetalHue())); - SetStr( 81, 105 ); - SetDex( 191, 215 ); - SetInt( 126, 150 ); + SetStr(81, 105); + SetDex(191, 215); + SetInt(126, 150); - SetHits( 49, 63 ); + SetHits(49, 63); - SetDamage( 5, 10 ); + SetDamage(5, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetSkill( SkillName.EvalInt, 80.2, 100.0 ); - SetSkill( SkillName.Magery, 95.1, 100.0 ); - SetSkill( SkillName.Meditation, 27.5, 50.0 ); - SetSkill( SkillName.MagicResist, 77.5, 100.0 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 20.3, 80.0 ); + SetSkill(SkillName.EvalInt, 80.2, 100.0); + SetSkill(SkillName.Magery, 95.1, 100.0); + SetSkill(SkillName.Meditation, 27.5, 50.0); + SetSkill(SkillName.MagicResist, 77.5, 100.0); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 20.3, 80.0); - Fame = 10500; - Karma = -10500; + Fame = 10500; + Karma = -10500; - VirtualArmor = 16; - PackReg( 23 ); - if ( Utility.RandomBool() ) - PackItem( new Shoes() ); - else - PackItem( new Sandals() ); - } + VirtualArmor = 16; + PackReg(23); + if (Utility.RandomBool()) + PackItem(new Shoes()); + else + PackItem(new Sandals()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public EvilMageLord(Serial serial) : base(serial) + { + } - public override bool CanRummageCorpses => true; - public override bool AlwaysMurderer => true; - public override int Meat => 1; - public override int TreasureMapLevel => Core.AOS ? 2 : 0; + public override string CorpseName => "an evil mage lord corpse"; - public EvilMageLord( Serial serial ) : base( serial ) - { - } + public override bool CanRummageCorpses => true; + public override bool AlwaysMurderer => true; + public override int Meat => 1; + public override int TreasureMapLevel => Core.AOS ? 2 : 0; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/FireGargoyle.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/FireGargoyle.cs index 9ac967804..c6d59ae64 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/FireGargoyle.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/FireGargoyle.cs @@ -1,70 +1,71 @@ namespace Server.Mobiles { - public class FireGargoyle : BaseCreature - { - public override string CorpseName => "a charred corpse"; - [Constructible] - public FireGargoyle() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "fire gargoyle" ); - Body = 130; - BaseSoundID = 0x174; + public class FireGargoyle : BaseCreature + { + [Constructible] + public FireGargoyle() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("fire gargoyle"); + Body = 130; + BaseSoundID = 0x174; - SetStr( 351, 400 ); - SetDex( 126, 145 ); - SetInt( 226, 250 ); + SetStr(351, 400); + SetDex(126, 145); + SetInt(226, 250); - SetHits( 211, 240 ); + SetHits(211, 240); - SetDamage( 7, 14 ); + SetDamage(7, 14); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Fire, 80 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Fire, 80); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetSkill( SkillName.Anatomy, 75.1, 85.0 ); - SetSkill( SkillName.EvalInt, 90.1, 105.0 ); - SetSkill( SkillName.Magery, 90.1, 105.0 ); - SetSkill( SkillName.Meditation, 90.1, 105.0 ); - SetSkill( SkillName.MagicResist, 90.1, 105.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 40.1, 80.0 ); + SetSkill(SkillName.Anatomy, 75.1, 85.0); + SetSkill(SkillName.EvalInt, 90.1, 105.0); + SetSkill(SkillName.Magery, 90.1, 105.0); + SetSkill(SkillName.Meditation, 90.1, 105.0); + SetSkill(SkillName.MagicResist, 90.1, 105.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 40.1, 80.0); - Fame = 3500; - Karma = -3500; + Fame = 3500; + Karma = -3500; - VirtualArmor = 32; - } + VirtualArmor = 32; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems ); - } + public FireGargoyle(Serial serial) : base(serial) + { + } - public override bool HasBreath => true; // fire breath enabled - public override int TreasureMapLevel => 1; - public override int Meat => 1; - public override bool CanFly => true; + public override string CorpseName => "a charred corpse"; - public FireGargoyle( Serial serial ) : base( serial ) - { - } + public override bool HasBreath => true; // fire breath enabled + public override int TreasureMapLevel => 1; + public override int Meat => 1; + public override bool CanFly => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Gargoyle.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Gargoyle.cs index f8c441648..729e58b42 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Gargoyle.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Gargoyle.cs @@ -2,73 +2,73 @@ using Server.Items; namespace Server.Mobiles { - public class Gargoyle : BaseCreature - { - public override string CorpseName => "a gargoyle corpse"; - public override string DefaultName => "a gargoyle"; + public class Gargoyle : BaseCreature + { + [Constructible] + public Gargoyle() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 4; + BaseSoundID = 372; - [Constructible] - public Gargoyle() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 4; - BaseSoundID = 372; + SetStr(146, 175); + SetDex(76, 95); + SetInt(81, 105); - SetStr( 146, 175 ); - SetDex( 76, 95 ); - SetInt( 81, 105 ); + SetHits(88, 105); - SetHits( 88, 105 ); + SetDamage(7, 14); - SetDamage( 7, 14 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 15, 25); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 15, 25 ); + SetSkill(SkillName.EvalInt, 70.1, 85.0); + SetSkill(SkillName.Magery, 70.1, 85.0); + SetSkill(SkillName.MagicResist, 70.1, 85.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 40.1, 80.0); - SetSkill( SkillName.EvalInt, 70.1, 85.0 ); - SetSkill( SkillName.Magery, 70.1, 85.0 ); - SetSkill( SkillName.MagicResist, 70.1, 85.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 40.1, 80.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 32; - VirtualArmor = 32; + if (0.025 > Utility.RandomDouble()) + PackItem(new GargoylesPickaxe()); + } - if ( 0.025 > Utility.RandomDouble() ) - PackItem( new GargoylesPickaxe() ); - } + public Gargoyle(Serial serial) : base(serial) + { + } - public override bool CanFly => true; + public override string CorpseName => "a gargoyle corpse"; + public override string DefaultName => "a gargoyle"; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.MedScrolls ); - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 4 ) ); - } + public override bool CanFly => true; - public override int TreasureMapLevel => 1; - public override int Meat => 1; + public override int TreasureMapLevel => 1; + public override int Meat => 1; - public Gargoyle( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.MedScrolls); + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 4)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleDestroyer.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleDestroyer.cs index 4a4af8b32..8684ed760 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleDestroyer.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleDestroyer.cs @@ -2,103 +2,98 @@ using Server.Items; namespace Server.Mobiles { - public class GargoyleDestroyer : BaseCreature - { - public override string CorpseName => "a gargoyle corpse"; - public override string DefaultName => "a gargoyle destroyer"; + public class GargoyleDestroyer : BaseCreature + { + [Constructible] + public GargoyleDestroyer() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x2F3; + BaseSoundID = 0x174; - [Constructible] - public GargoyleDestroyer() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x2F3; - BaseSoundID = 0x174; + SetStr(760, 850); + SetDex(102, 150); + SetInt(152, 200); - SetStr( 760, 850 ); - SetDex( 102, 150 ); - SetInt( 152, 200 ); + SetHits(482, 485); - SetHits( 482, 485 ); + SetDamage(7, 14); - SetDamage( 7, 14 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 15, 25); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + SetSkill(SkillName.Wrestling, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 120.4, 160.0); + SetSkill(SkillName.Anatomy, 50.5, 100.0); + SetSkill(SkillName.Swords, 90.1, 100.0); + SetSkill(SkillName.Macing, 90.1, 100.0); + SetSkill(SkillName.Fencing, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 120.4, 160.0 ); - SetSkill( SkillName.Anatomy, 50.5, 100.0 ); - SetSkill( SkillName.Swords, 90.1, 100.0 ); - SetSkill( SkillName.Macing, 90.1, 100.0 ); - SetSkill( SkillName.Fencing, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); + Fame = 10000; + Karma = -10000; - Fame = 10000; - Karma = -10000; + VirtualArmor = 50; - VirtualArmor = 50; + if (0.2 > Utility.RandomDouble()) + PackItem(new GargoylesPickaxe()); + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new GargoylesPickaxe() ); - } + public GargoyleDestroyer(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "a gargoyle corpse"; + public override string DefaultName => "a gargoyle destroyer"; - public override bool BardImmune => !Core.AOS; - public override int Meat => 1; - public override bool CanFly => true; + public override bool BardImmune => !Core.AOS; + public override int Meat => 1; + public override bool CanFly => true; - public override void OnDamagedBySpell( Mobile from ) - { - if ( from != null && from.Alive && 0.4 > Utility.RandomDouble() ) - { - ThrowHatchet( from ); - } - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls); + AddLoot(LootPack.Gems, 2); + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnDamagedBySpell(Mobile from) + { + if (from != null && from.Alive && 0.4 > Utility.RandomDouble()) ThrowHatchet(from); + } - if ( attacker != null && attacker.Alive && attacker.Weapon is BaseRanged && 0.4 > Utility.RandomDouble() ) - { - ThrowHatchet( attacker ); - } - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public void ThrowHatchet( Mobile to ) - { - int damage = 50; - MovingEffect( to, 0xF43, 10, 0, false, false ); - DoHarmful( to ); - AOS.Damage( to, this, damage, 100, 0, 0, 0, 0 ); - } + if (attacker != null && attacker.Alive && attacker.Weapon is BaseRanged && 0.4 > Utility.RandomDouble()) + ThrowHatchet(attacker); + } - public GargoyleDestroyer( Serial serial ) : base( serial ) - { - } + public void ThrowHatchet(Mobile to) + { + int damage = 50; + MovingEffect(to, 0xF43, 10, 0, false, false); + DoHarmful(to); + AOS.Damage(to, this, damage, 100, 0, 0, 0, 0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleEnforcer.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleEnforcer.cs index dca526c15..59ca9a8c6 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleEnforcer.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/GargoyleEnforcer.cs @@ -2,75 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public class GargoyleEnforcer : BaseCreature - { - public override string CorpseName => "a gargoyle corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.WhirlwindAttack; + public class GargoyleEnforcer : BaseCreature + { + [Constructible] + public GargoyleEnforcer() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x2F2; + BaseSoundID = 0x174; - public override string DefaultName => "a gargoyle enforcer"; + SetStr(760, 850); + SetDex(102, 150); + SetInt(152, 200); - [Constructible] - public GargoyleEnforcer() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x2F2; - BaseSoundID = 0x174; + SetHits(482, 485); - SetStr( 760, 850 ); - SetDex( 102, 150 ); - SetInt( 152, 200 ); + SetDamage(7, 14); - SetHits( 482, 485 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 15, 25); - SetDamage( 7, 14 ); + SetSkill(SkillName.MagicResist, 120.1, 130.0); + SetSkill(SkillName.Tactics, 70.1, 80.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); + SetSkill(SkillName.Swords, 80.1, 90.0); + SetSkill(SkillName.Anatomy, 70.1, 80.0); + SetSkill(SkillName.Magery, 80.1, 90.0); + SetSkill(SkillName.EvalInt, 70.3, 100.0); + SetSkill(SkillName.Meditation, 70.3, 100.0); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + Fame = 5000; + Karma = -5000; - SetSkill( SkillName.MagicResist, 120.1, 130.0 ); - SetSkill( SkillName.Tactics, 70.1, 80.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); - SetSkill( SkillName.Swords, 80.1, 90.0 ); - SetSkill( SkillName.Anatomy, 70.1, 80.0 ); - SetSkill( SkillName.Magery, 80.1, 90.0 ); - SetSkill( SkillName.EvalInt, 70.3, 100.0 ); - SetSkill( SkillName.Meditation, 70.3, 100.0 ); + VirtualArmor = 50; - Fame = 5000; - Karma = -5000; + if (0.2 > Utility.RandomDouble()) + PackItem(new GargoylesPickaxe()); + } - VirtualArmor = 50; + public GargoyleEnforcer(Serial serial) : base(serial) + { + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new GargoylesPickaxe() ); - } + public override string CorpseName => "a gargoyle corpse"; - public override bool CanFly => true; + public override string DefaultName => "a gargoyle enforcer"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls ); - } + public override bool CanFly => true; - public override int Meat => 1; + public override int Meat => 1; - public GargoyleEnforcer( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.WhirlwindAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Gazer.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Gazer.cs index 966fe6d62..f00c53482 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Gazer.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Gazer.cs @@ -2,70 +2,70 @@ using Server.Items; namespace Server.Mobiles { - public class Gazer : BaseCreature - { - public override string CorpseName => "a gazer corpse"; - public override string DefaultName => "a gazer"; + public class Gazer : BaseCreature + { + [Constructible] + public Gazer() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 22; + BaseSoundID = 377; - [Constructible] - public Gazer () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 22; - BaseSoundID = 377; + SetStr(96, 125); + SetDex(86, 105); + SetInt(141, 165); - SetStr( 96, 125 ); - SetDex( 86, 105 ); - SetInt( 141, 165 ); + SetHits(58, 75); - SetHits( 58, 75 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.EvalInt, 50.1, 65.0); + SetSkill(SkillName.Magery, 50.1, 65.0); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetSkill( SkillName.EvalInt, 50.1, 65.0 ); - SetSkill( SkillName.Magery, 50.1, 65.0 ); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 36; - VirtualArmor = 36; + PackItem(new Nightshade(4)); + } - PackItem( new Nightshade( 4 ) ); - } + public Gazer(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "a gazer corpse"; + public override string DefaultName => "a gazer"; - public override int TreasureMapLevel => 1; - public override int Meat => 1; + public override int TreasureMapLevel => 1; + public override int Meat => 1; - public Gazer( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/GolemController.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/GolemController.cs index a2265afe1..532a686d7 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/GolemController.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/GolemController.cs @@ -2,91 +2,89 @@ using Server.Items; namespace Server.Mobiles { - public class GolemController : BaseCreature - { - public override string CorpseName => "a golem controller corpse"; - [Constructible] - public GolemController() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "golem controller" ); - Title = "the controller"; + public class GolemController : BaseCreature + { + [Constructible] + public GolemController() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("golem controller"); + Title = "the controller"; - Body = 400; - Hue = 0x455; + Body = 400; + Hue = 0x455; - AddArcane( new Robe() ); - AddArcane( new ThighBoots() ); - AddArcane( new LeatherGloves() ); - AddArcane( new Cloak() ); + AddArcane(new Robe()); + AddArcane(new ThighBoots()); + AddArcane(new LeatherGloves()); + AddArcane(new Cloak()); - SetStr( 126, 150 ); - SetDex( 96, 120 ); - SetInt( 151, 175 ); + SetStr(126, 150); + SetDex(96, 120); + SetInt(151, 175); - SetHits( 76, 90 ); + SetHits(76, 90); - SetDamage( 6, 12 ); + SetDamage(6, 12); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 5, 15 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 5, 15); + SetResistance(ResistanceType.Energy, 15, 25); - SetSkill( SkillName.EvalInt, 95.1, 100.0 ); - SetSkill( SkillName.Magery, 95.1, 100.0 ); - SetSkill( SkillName.Meditation, 95.1, 100.0 ); - SetSkill( SkillName.MagicResist, 102.5, 125.0 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 65.0, 87.5 ); + SetSkill(SkillName.EvalInt, 95.1, 100.0); + SetSkill(SkillName.Magery, 95.1, 100.0); + SetSkill(SkillName.Meditation, 95.1, 100.0); + SetSkill(SkillName.MagicResist, 102.5, 125.0); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 65.0, 87.5); - Fame = 4000; - Karma = -4000; + Fame = 4000; + Karma = -4000; - VirtualArmor = 16; + VirtualArmor = 16; - if ( 0.7 > Utility.RandomDouble() ) - PackItem( new ArcaneGem() ); - } + if (0.7 > Utility.RandomDouble()) + PackItem(new ArcaneGem()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public GolemController(Serial serial) : base(serial) + { + } - public void AddArcane( Item item ) - { - if ( item is IArcaneEquip eq ) - { - eq.CurArcaneCharges = eq.MaxArcaneCharges = 20; - } + public override string CorpseName => "a golem controller corpse"; - item.Hue = ArcaneGem.DefaultArcaneHue; - item.LootType = LootType.Newbied; + public override bool ClickTitle => false; + public override bool ShowFameTitle => false; + public override bool AlwaysMurderer => true; - AddItem( item ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override bool ClickTitle => false; - public override bool ShowFameTitle => false; - public override bool AlwaysMurderer => true; + public void AddArcane(Item item) + { + if (item is IArcaneEquip eq) eq.CurArcaneCharges = eq.MaxArcaneCharges = 20; - public GolemController( Serial serial ) : base( serial ) - { - } + item.Hue = ArcaneGem.DefaultArcaneHue; + item.LootType = LootType.Newbied; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + AddItem(item); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/IceFiend.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/IceFiend.cs index cb1f14986..8d52c003b 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/IceFiend.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/IceFiend.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class IceFiend : BaseCreature - { - public override string CorpseName => "an ice fiend corpse"; - public override string DefaultName => "an ice fiend"; + public class IceFiend : BaseCreature + { + [Constructible] + public IceFiend() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 43; + BaseSoundID = 357; - [Constructible] - public IceFiend () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 43; - BaseSoundID = 357; + SetStr(376, 405); + SetDex(176, 195); + SetInt(201, 225); - SetStr( 376, 405 ); - SetDex( 176, 195 ); - SetInt( 201, 225 ); + SetHits(226, 243); - SetHits( 226, 243 ); + SetDamage(8, 19); - SetDamage( 8, 19 ); + SetSkill(SkillName.EvalInt, 80.1, 90.0); + SetSkill(SkillName.Magery, 80.1, 90.0); + SetSkill(SkillName.MagicResist, 75.1, 85.0); + SetSkill(SkillName.Tactics, 80.1, 90.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); - SetSkill( SkillName.EvalInt, 80.1, 90.0 ); - SetSkill( SkillName.Magery, 80.1, 90.0 ); - SetSkill( SkillName.MagicResist, 75.1, 85.0 ); - SetSkill( SkillName.Tactics, 80.1, 90.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 18000; + Karma = -18000; - Fame = 18000; - Karma = -18000; + VirtualArmor = 60; + } - VirtualArmor = 60; - } + public IceFiend(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override string CorpseName => "an ice fiend corpse"; + public override string DefaultName => "an ice fiend"; - public override int TreasureMapLevel => 4; - public override int Meat => 1; - public override bool CanFly => true; + public override int TreasureMapLevel => 4; + public override int Meat => 1; + public override bool CanFly => true; - public IceFiend( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Average); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Imp.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Imp.cs index b7d487b81..4c2ed298c 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Imp.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Imp.cs @@ -1,77 +1,77 @@ namespace Server.Mobiles { - public class Imp : BaseCreature - { - public override string CorpseName => "an imp corpse"; - public override string DefaultName => "an imp"; + public class Imp : BaseCreature + { + [Constructible] + public Imp() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 74; + BaseSoundID = 422; - [Constructible] - public Imp() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 74; - BaseSoundID = 422; + SetStr(91, 115); + SetDex(61, 80); + SetInt(86, 105); - SetStr( 91, 115 ); - SetDex( 61, 80 ); - SetInt( 86, 105 ); + SetHits(55, 70); - SetHits( 55, 70 ); + SetDamage(10, 14); - SetDamage( 10, 14 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Fire, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Fire, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 20.1, 30.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 30.1, 50.0); + SetSkill(SkillName.Tactics, 42.1, 50.0); + SetSkill(SkillName.Wrestling, 40.1, 44.0); - SetSkill( SkillName.EvalInt, 20.1, 30.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 30.1, 50.0 ); - SetSkill( SkillName.Tactics, 42.1, 50.0 ); - SetSkill( SkillName.Wrestling, 40.1, 44.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 30; - VirtualArmor = 30; + Tamable = true; + ControlSlots = 2; + MinTameSkill = 83.1; + } - Tamable = true; - ControlSlots = 2; - MinTameSkill = 83.1; - } + public Imp(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override string CorpseName => "an imp corpse"; + public override string DefaultName => "an imp"; - public override int Meat => 1; - public override int Hides => 6; - public override HideType HideType => HideType.Spined; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Daemon; - public override bool CanFly => true; + public override int Meat => 1; + public override int Hides => 6; + public override HideType HideType => HideType.Spined; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Daemon; + public override bool CanFly => true; - public Imp( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Lich.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Lich.cs index 6b518485b..febe2b0a7 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Lich.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Lich.cs @@ -2,80 +2,80 @@ using Server.Items; namespace Server.Mobiles { - public class Lich : BaseCreature - { - public override string CorpseName => "a lich's corpse"; - public override string DefaultName => "a lich"; + public class Lich : BaseCreature + { + [Constructible] + public Lich() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 24; + BaseSoundID = 0x3E9; - [Constructible] - public Lich() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 24; - BaseSoundID = 0x3E9; + SetStr(171, 200); + SetDex(126, 145); + SetInt(276, 305); - SetStr( 171, 200 ); - SetDex( 126, 145 ); - SetInt( 276, 305 ); + SetHits(103, 120); - SetHits( 103, 120 ); + SetDamage(24, 26); - SetDamage( 24, 26 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Cold, 40); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Cold, 40 ); - SetDamageType( ResistanceType.Energy, 50 ); - - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 55, 65 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 55, 65); + SetResistance(ResistanceType.Energy, 40, 50); - SetSkill( SkillName.Necromancy, 89, 99.1 ); - SetSkill( SkillName.SpiritSpeak, 90.0, 99.0 ); + SetSkill(SkillName.Necromancy, 89, 99.1); + SetSkill(SkillName.SpiritSpeak, 90.0, 99.0); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Magery, 70.1, 80.0 ); - SetSkill( SkillName.Meditation, 85.1, 95.0 ); - SetSkill( SkillName.MagicResist, 80.1, 100.0 ); - SetSkill( SkillName.Tactics, 70.1, 90.0 ); + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Magery, 70.1, 80.0); + SetSkill(SkillName.Meditation, 85.1, 95.0); + SetSkill(SkillName.MagicResist, 80.1, 100.0); + SetSkill(SkillName.Tactics, 70.1, 90.0); - Fame = 8000; - Karma = -8000; + Fame = 8000; + Karma = -8000; - VirtualArmor = 50; - PackItem( new GnarledStaff() ); - PackNecroReg( 17, 24 ); - } + VirtualArmor = 50; + PackItem(new GnarledStaff()); + PackNecroReg(17, 24); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public Lich(Serial serial) : base(serial) + { + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string CorpseName => "a lich's corpse"; + public override string DefaultName => "a lich"; - public override bool CanRummageCorpses => true; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 3; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public Lich( Serial serial ) : base( serial ) - { - } + public override bool CanRummageCorpses => true; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => 3; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/LichLord.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/LichLord.cs index 3af8e5c69..5297352eb 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/LichLord.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/LichLord.cs @@ -2,79 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public class LichLord : BaseCreature - { - public override string CorpseName => "a lich's corpse"; - public override string DefaultName => "a lich lord"; + public class LichLord : BaseCreature + { + [Constructible] + public LichLord() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 79; + BaseSoundID = 412; - [Constructible] - public LichLord() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 79; - BaseSoundID = 412; + SetStr(416, 505); + SetDex(146, 165); + SetInt(566, 655); - SetStr( 416, 505 ); - SetDex( 146, 165 ); - SetInt( 566, 655 ); + SetHits(250, 303); - SetHits( 250, 303 ); + SetDamage(11, 13); - SetDamage( 11, 13 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 60); + SetDamageType(ResistanceType.Energy, 40); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 60 ); - SetDamageType( ResistanceType.Energy, 40 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Necromancy, 90, 110.0); + SetSkill(SkillName.SpiritSpeak, 90.0, 110.0); - SetSkill( SkillName.Necromancy, 90, 110.0 ); - SetSkill( SkillName.SpiritSpeak, 90.0, 110.0 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 150.5, 200.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 150.5, 200.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 18000; + Karma = -18000; - Fame = 18000; - Karma = -18000; + VirtualArmor = 50; + PackItem(new GnarledStaff()); + PackNecroReg(12, 40); + } - VirtualArmor = 50; - PackItem( new GnarledStaff() ); - PackNecroReg( 12, 40 ); - } + public LichLord(Serial serial) : base(serial) + { + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string CorpseName => "a lich's corpse"; + public override string DefaultName => "a lich lord"; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override bool CanRummageCorpses => true; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => 4; + public override bool CanRummageCorpses => true; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => 4; - public LichLord( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/OrcishMage.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/OrcishMage.cs index 8bacd0981..8e98c39cd 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/OrcishMage.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/OrcishMage.cs @@ -1,104 +1,104 @@ -using Server.Misc; using Server.Items; +using Server.Misc; namespace Server.Mobiles { - public class OrcishMage : BaseCreature - { - public override string CorpseName => "a glowing orc corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Orc; + public class OrcishMage : BaseCreature + { + [Constructible] + public OrcishMage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 140; + BaseSoundID = 0x45A; - public override string DefaultName => "an orcish mage"; + SetStr(116, 150); + SetDex(91, 115); + SetInt(161, 185); - [Constructible] - public OrcishMage () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 140; - BaseSoundID = 0x45A; + SetHits(70, 90); - SetStr( 116, 150 ); - SetDex( 91, 115 ); - SetInt( 161, 185 ); + SetDamage(4, 14); - SetHits( 70, 90 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 4, 14 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.EvalInt, 60.1, 72.5); + SetSkill(SkillName.Magery, 60.1, 72.5); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 50.1, 65.0); + SetSkill(SkillName.Wrestling, 40.1, 50.0); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 3000; + Karma = -3000; - SetSkill( SkillName.EvalInt, 60.1, 72.5 ); - SetSkill( SkillName.Magery, 60.1, 72.5 ); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 50.1, 65.0 ); - SetSkill( SkillName.Wrestling, 40.1, 50.0 ); - - Fame = 3000; - Karma = -3000; - - VirtualArmor = 30; + VirtualArmor = 30; - PackReg( 6 ); + PackReg(6); - if ( 0.05 > Utility.RandomDouble() ) - PackItem( new OrcishKinMask() ); - } + if (0.05 > Utility.RandomDouble()) + PackItem(new OrcishKinMask()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.LowScrolls ); - } + public OrcishMage(Serial serial) : base(serial) + { + } - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 1; - public override int Meat => 1; + public override string CorpseName => "a glowing orc corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Orc; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override string DefaultName => "an orcish mage"; - public override bool IsEnemy( Mobile m ) - { - if ( m.Player && m.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - return false; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 1; + public override int Meat => 1; - return base.IsEnemy( m ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.LowScrolls); + } - Item item = aggressor.FindItemOnLayer( Layer.Helm ); + public override bool IsEnemy(Mobile m) + { + if (m.Player && m.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + return false; - if ( item is OrcishKinMask ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - item.Delete(); - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - } - } + return base.IsEnemy(m); + } - public OrcishMage( Serial serial ) : base( serial ) - { - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + Item item = aggressor.FindItemOnLayer(Layer.Helm); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + if (item is OrcishKinMask) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + item.Delete(); + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/RatmanMage.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/RatmanMage.cs index 19106dadc..8b2d83752 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/RatmanMage.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/RatmanMage.cs @@ -2,82 +2,82 @@ using Server.Misc; namespace Server.Mobiles { - public class RatmanMage : BaseCreature - { - public override string CorpseName => "a glowing ratman corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Ratman; + public class RatmanMage : BaseCreature + { + [Constructible] + public RatmanMage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("ratman"); + Body = 0x8F; + BaseSoundID = 437; - [Constructible] - public RatmanMage() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "ratman" ); - Body = 0x8F; - BaseSoundID = 437; + SetStr(146, 180); + SetDex(101, 130); + SetInt(186, 210); - SetStr( 146, 180 ); - SetDex( 101, 130 ); - SetInt( 186, 210 ); + SetHits(88, 108); - SetHits( 88, 108 ); + SetDamage(7, 14); - SetDamage( 7, 14 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 45); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 40, 45 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.EvalInt, 70.1, 80.0); + SetSkill(SkillName.Magery, 70.1, 80.0); + SetSkill(SkillName.MagicResist, 65.1, 90.0); + SetSkill(SkillName.Tactics, 50.1, 75.0); + SetSkill(SkillName.Wrestling, 50.1, 75.0); - SetSkill( SkillName.EvalInt, 70.1, 80.0 ); - SetSkill( SkillName.Magery, 70.1, 80.0 ); - SetSkill( SkillName.MagicResist, 65.1, 90.0 ); - SetSkill( SkillName.Tactics, 50.1, 75.0 ); - SetSkill( SkillName.Wrestling, 50.1, 75.0 ); + Fame = 7500; + Karma = -7500; - Fame = 7500; - Karma = -7500; + VirtualArmor = 44; - VirtualArmor = 44; + PackReg(6); - PackReg( 6 ); + if (0.02 > Utility.RandomDouble()) + PackStatue(); + } - if ( 0.02 > Utility.RandomDouble() ) - PackStatue(); - } + public RatmanMage(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.LowScrolls ); - } + public override string CorpseName => "a glowing ratman corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Ratman; - public override bool CanRummageCorpses => true; - public override int Meat => 1; - public override int Hides => 8; - public override HideType HideType => HideType.Spined; + public override bool CanRummageCorpses => true; + public override int Meat => 1; + public override int Hides => 8; + public override HideType HideType => HideType.Spined; - public RatmanMage( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.LowScrolls); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Body == 42 ) - { - Body = 0x8F; - Hue = 0; - } - } - } -} + if (Body == 42) + { + Body = 0x8F; + Hue = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/SavageShaman.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/SavageShaman.cs index 3f083e5a0..3ce772e06 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/SavageShaman.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/SavageShaman.cs @@ -5,280 +5,277 @@ using Server.Spells; namespace Server.Mobiles { - public class SavageShaman : BaseCreature - { - public override string CorpseName => "a savage corpse"; - [Constructible] - public SavageShaman() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "savage shaman" ); - - if ( Utility.RandomBool() ) - Body = 184; - else - Body = 183; - - SetStr( 126, 145 ); - SetDex( 91, 110 ); - SetInt( 161, 185 ); - - SetDamage( 4, 10 ); - - SetDamageType( ResistanceType.Physical, 100 ); - - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 40, 50 ); - - SetSkill( SkillName.EvalInt, 77.5, 100.0 ); - SetSkill( SkillName.Fencing, 62.5, 85.0 ); - SetSkill( SkillName.Macing, 62.5, 85.0 ); - SetSkill( SkillName.Magery, 72.5, 95.0 ); - SetSkill( SkillName.Meditation, 77.5, 100.0 ); - SetSkill( SkillName.MagicResist, 77.5, 100.0 ); - SetSkill( SkillName.Swords, 62.5, 85.0 ); - SetSkill( SkillName.Tactics, 62.5, 85.0 ); - SetSkill( SkillName.Wrestling, 62.5, 85.0 ); - - Fame = 1000; - Karma = -1000; - - PackReg( 10, 15 ); - PackItem( new Bandage( Utility.RandomMinMax( 1, 15 ) ) ); - - if ( 0.1 > Utility.RandomDouble() ) - PackItem( new TribalBerry() ); - - AddItem( new BoneArms() ); - AddItem( new BoneLegs() ); - AddItem( new DeerMask() ); - } - - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - - } - - public override int Meat => 1; - public override bool AlwaysMurderer => true; - public override bool ShowFameTitle => false; - - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - - public override bool IsEnemy( Mobile m ) - { - if ( m.BodyMod == 183 || m.BodyMod == 184 ) - return false; - - return base.IsEnemy( m ); - } - - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); - - if ( aggressor.BodyMod == 183 || aggressor.BodyMod == 184 ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - aggressor.BodyMod = 0; - aggressor.HueMod = -1; - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - aggressor.SendLocalizedMessage( 1040008 ); // Your skin is scorched as the tribal paint burns away! - - if ( aggressor is PlayerMobile mobile ) - mobile.SavagePaintExpiration = TimeSpan.Zero; - } - } - - public override void AlterMeleeDamageTo( Mobile to, ref int damage ) - { - if ( to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || to is LesserHiryu || to is Daemon ) - damage *= 3; - } + public class SavageShaman : BaseCreature + { + [Constructible] + public SavageShaman() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("savage shaman"); + + if (Utility.RandomBool()) + Body = 184; + else + Body = 183; + + SetStr(126, 145); + SetDex(91, 110); + SetInt(161, 185); + + SetDamage(4, 10); + + SetDamageType(ResistanceType.Physical, 100); + + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 40, 50); + + SetSkill(SkillName.EvalInt, 77.5, 100.0); + SetSkill(SkillName.Fencing, 62.5, 85.0); + SetSkill(SkillName.Macing, 62.5, 85.0); + SetSkill(SkillName.Magery, 72.5, 95.0); + SetSkill(SkillName.Meditation, 77.5, 100.0); + SetSkill(SkillName.MagicResist, 77.5, 100.0); + SetSkill(SkillName.Swords, 62.5, 85.0); + SetSkill(SkillName.Tactics, 62.5, 85.0); + SetSkill(SkillName.Wrestling, 62.5, 85.0); + + Fame = 1000; + Karma = -1000; + + PackReg(10, 15); + PackItem(new Bandage(Utility.RandomMinMax(1, 15))); + + if (0.1 > Utility.RandomDouble()) + PackItem(new TribalBerry()); + + AddItem(new BoneArms()); + AddItem(new BoneLegs()); + AddItem(new DeerMask()); + } + + public SavageShaman(Serial serial) : base(serial) + { + } + + public override string CorpseName => "a savage corpse"; + + public override int Meat => 1; + public override bool AlwaysMurderer => true; + public override bool ShowFameTitle => false; + + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } + + public override bool IsEnemy(Mobile m) + { + if (m.BodyMod == 183 || m.BodyMod == 184) + return false; + + return base.IsEnemy(m); + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - if ( 0.1 > Utility.RandomDouble() ) - BeginSavageDance(); - } - - public void BeginSavageDance() - { - if ( Map == null ) - return; + if (aggressor.BodyMod == 183 || aggressor.BodyMod == 184) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + aggressor.BodyMod = 0; + aggressor.HueMod = -1; + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + aggressor.SendLocalizedMessage(1040008); // Your skin is scorched as the tribal paint burns away! + + if (aggressor is PlayerMobile mobile) + mobile.SavagePaintExpiration = TimeSpan.Zero; + } + } + + public override void AlterMeleeDamageTo(Mobile to, ref int damage) + { + if (to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || + to is LesserHiryu || to is Daemon) + damage *= 3; + } - ArrayList list = new ArrayList(); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - foreach ( Mobile m in GetMobilesInRange( 8 ) ) - { - if ( m != this && m is SavageShaman ) - list.Add( m ); - } + if (0.1 > Utility.RandomDouble()) + BeginSavageDance(); + } - Animate( 111, 5, 1, true, false, 0 ); // Do a little dance... + public void BeginSavageDance() + { + if (Map == null) + return; - if ( AIObject != null ) - AIObject.NextMove = Core.TickCount + 1000; + ArrayList list = new ArrayList(); - if ( list.Count >= 3 ) - { - for ( int i = 0; i < list.Count; ++i ) - { - SavageShaman dancer = (SavageShaman)list[i]; + foreach (Mobile m in GetMobilesInRange(8)) + if (m != this && m is SavageShaman) + list.Add(m); + + Animate(111, 5, 1, true, false, 0); // Do a little dance... + + if (AIObject != null) + AIObject.NextMove = Core.TickCount + 1000; - dancer.Animate( 111, 5, 1, true, false, 0 ); // Get down tonight... + if (list.Count >= 3) + { + for (int i = 0; i < list.Count; ++i) + { + SavageShaman dancer = (SavageShaman)list[i]; - if ( dancer.AIObject != null ) - dancer.AIObject.NextMove = Core.TickCount + 1000; - } + dancer.Animate(111, 5, 1, true, false, 0); // Get down tonight... - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), EndSavageDance ); - } - } + if (dancer.AIObject != null) + dancer.AIObject.NextMove = Core.TickCount + 1000; + } - public void EndSavageDance() - { - if ( Deleted ) - return; + Timer.DelayCall(TimeSpan.FromSeconds(1.0), EndSavageDance); + } + } - ArrayList list = new ArrayList(); + public void EndSavageDance() + { + if (Deleted) + return; - foreach ( Mobile m in GetMobilesInRange( 8 ) ) - list.Add( m ); + ArrayList list = new ArrayList(); - if ( list.Count > 0 ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: /* greater heal */ - { - foreach ( Mobile m in list ) - { - bool isFriendly = ( m is Savage || m is SavageRider || m is SavageShaman || m is SavageRidgeback ); + foreach (Mobile m in GetMobilesInRange(8)) + list.Add(m); - if ( !isFriendly ) - continue; + if (list.Count > 0) + switch (Utility.Random(3)) + { + case 0: /* greater heal */ + { + foreach (Mobile m in list) + { + bool isFriendly = m is Savage || m is SavageRider || m is SavageShaman || m is SavageRidgeback; - if ( m.Poisoned || MortalStrike.IsWounded( m ) || !CanBeBeneficial( m ) ) - continue; + if (!isFriendly) + continue; - DoBeneficial( m ); + if (m.Poisoned || MortalStrike.IsWounded(m) || !CanBeBeneficial(m)) + continue; - // Algorithm: (40% of magery) + (1-10) + DoBeneficial(m); - int toHeal = (int)(Skills[SkillName.Magery].Value * 0.4); - toHeal += Utility.Random( 1, 10 ); + // Algorithm: (40% of magery) + (1-10) - m.Heal( toHeal, this ); + int toHeal = (int)(Skills[SkillName.Magery].Value * 0.4); + toHeal += Utility.Random(1, 10); - m.FixedParticles( 0x376A, 9, 32, 5030, EffectLayer.Waist ); - m.PlaySound( 0x202 ); - } + m.Heal(toHeal, this); - break; - } - case 1: /* lightning */ - { - foreach ( Mobile m in list ) - { - bool isFriendly = ( m is Savage || m is SavageRider || m is SavageShaman || m is SavageRidgeback ); + m.FixedParticles(0x376A, 9, 32, 5030, EffectLayer.Waist); + m.PlaySound(0x202); + } - if ( isFriendly ) - continue; + break; + } + case 1: /* lightning */ + { + foreach (Mobile m in list) + { + bool isFriendly = m is Savage || m is SavageRider || m is SavageShaman || m is SavageRidgeback; - if ( !CanBeHarmful( m ) ) - continue; + if (isFriendly) + continue; - DoHarmful( m ); + if (!CanBeHarmful(m)) + continue; - double damage; + DoHarmful(m); - if ( Core.AOS ) - { - int baseDamage = 6 + (int)(Skills[SkillName.EvalInt].Value / 5.0); + double damage; - damage = Utility.RandomMinMax( baseDamage, baseDamage + 3 ); - } - else - { - damage = Utility.Random( 12, 9 ); - } + if (Core.AOS) + { + int baseDamage = 6 + (int)(Skills[SkillName.EvalInt].Value / 5.0); - m.BoltEffect( 0 ); + damage = Utility.RandomMinMax(baseDamage, baseDamage + 3); + } + else + { + damage = Utility.Random(12, 9); + } - SpellHelper.Damage( TimeSpan.FromSeconds( 0.25 ), m, this, damage, 0, 0, 0, 0, 100 ); - } + m.BoltEffect(0); - break; - } - case 2: /* poison */ - { - foreach ( Mobile m in list ) - { - bool isFriendly = ( m is Savage || m is SavageRider || m is SavageShaman || m is SavageRidgeback ); + SpellHelper.Damage(TimeSpan.FromSeconds(0.25), m, this, damage, 0, 0, 0, 0, 100); + } - if ( isFriendly ) - continue; + break; + } + case 2: /* poison */ + { + foreach (Mobile m in list) + { + bool isFriendly = m is Savage || m is SavageRider || m is SavageShaman || m is SavageRidgeback; - if ( !CanBeHarmful( m ) ) - continue; + if (isFriendly) + continue; - DoHarmful( m ); + if (!CanBeHarmful(m)) + continue; - m.Spell?.OnCasterHurt(); + DoHarmful(m); - m.Paralyzed = false; + m.Spell?.OnCasterHurt(); - double total = Skills[SkillName.Magery].Value + Skills[SkillName.Poisoning].Value; + m.Paralyzed = false; - double dist = GetDistanceToSqrt( m ); + double total = Skills[SkillName.Magery].Value + Skills[SkillName.Poisoning].Value; - if ( dist >= 3.0 ) - total -= (dist - 3.0) * 10.0; + double dist = GetDistanceToSqrt(m); - int level; + if (dist >= 3.0) + total -= (dist - 3.0) * 10.0; - if ( total >= 200.0 && Utility.Random( 1, 100 ) <= 10 ) - level = 3; - else if ( total > 170.0 ) - level = 2; - else if ( total > 130.0 ) - level = 1; - else - level = 0; + int level; - m.ApplyPoison( this, Poison.GetPoison( level ) ); + if (total >= 200.0 && Utility.Random(1, 100) <= 10) + level = 3; + else if (total > 170.0) + level = 2; + else if (total > 130.0) + level = 1; + else + level = 0; - m.FixedParticles( 0x374A, 10, 15, 5021, EffectLayer.Waist ); - m.PlaySound( 0x474 ); - } + m.ApplyPoison(this, Poison.GetPoison(level)); - break; - } - } - } - } + m.FixedParticles(0x374A, 10, 15, 5021, EffectLayer.Waist); + m.PlaySound(0x474); + } - public SavageShaman( Serial serial ) : base( serial ) - { - } + break; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Shade.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Shade.cs index c3d353e20..79787222f 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Shade.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Shade.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class Shade : BaseCreature - { - public override string CorpseName => "a ghostly corpse"; - public override string DefaultName => "a shade"; + public class Shade : BaseCreature + { + [Constructible] + public Shade() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 26; + Hue = 0x4001; + BaseSoundID = 0x482; - [Constructible] - public Shade() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 26; - Hue = 0x4001; - BaseSoundID = 0x482; + SetStr(76, 100); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(7, 11); - SetDamage( 7, 11 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 10, 20 ); + SetSkill(SkillName.EvalInt, 55.1, 70.0); + SetSkill(SkillName.Magery, 55.1, 70.0); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - SetSkill( SkillName.EvalInt, 55.1, 70.0 ); - SetSkill( SkillName.Magery, 55.1, 70.0 ); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 28; - VirtualArmor = 28; + PackReg(10); + } - PackReg( 10 ); - } + public Shade(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a ghostly corpse"; + public override string DefaultName => "a shade"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override Poison PoisonImmune => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; - public Shade( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/SkeletalMage.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/SkeletalMage.cs index 906fcc82d..f92fb868f 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/SkeletalMage.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/SkeletalMage.cs @@ -2,77 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class SkeletalMage : BaseCreature - { - public override string CorpseName => "a skeletal corpse"; - public override string DefaultName => "a skeletal mage"; + public class SkeletalMage : BaseCreature + { + [Constructible] + public SkeletalMage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 148; + BaseSoundID = 451; - [Constructible] - public SkeletalMage() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 148; - BaseSoundID = 451; + SetStr(76, 100); + SetDex(56, 75); + SetInt(186, 210); - SetStr( 76, 100 ); - SetDex( 56, 75 ); - SetInt( 186, 210 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 60.1, 70.0); + SetSkill(SkillName.Magery, 60.1, 70.0); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); + SetSkill(SkillName.Necromancy, 89, 99.1); + SetSkill(SkillName.SpiritSpeak, 90.0, 99.0); - SetSkill( SkillName.EvalInt, 60.1, 70.0 ); - SetSkill( SkillName.Magery, 60.1, 70.0 ); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); - SetSkill( SkillName.Necromancy, 89, 99.1 ); - SetSkill( SkillName.SpiritSpeak, 90.0, 99.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 38; + PackReg(3); + PackNecroReg(3, 10); + PackItem(new Bone()); + } - VirtualArmor = 38; - PackReg( 3 ); - PackNecroReg( 3, 10 ); - PackItem( new Bone() ); - } + public SkeletalMage(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "a skeletal corpse"; + public override string DefaultName => "a skeletal mage"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override Poison PoisonImmune => Poison.Regular; + public override Poison PoisonImmune => Poison.Regular; - public SkeletalMage( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Spectre.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Spectre.cs index fdd615f9b..b963a03e1 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Spectre.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Spectre.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class Spectre : BaseCreature - { - public override string CorpseName => "a ghostly corpse"; - public override string DefaultName => "a spectre"; + public class Spectre : BaseCreature + { + [Constructible] + public Spectre() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 26; + Hue = 0x4001; + BaseSoundID = 0x482; - [Constructible] - public Spectre() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 26; - Hue = 0x4001; - BaseSoundID = 0x482; + SetStr(76, 100); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(7, 11); - SetDamage( 7, 11 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 10, 20 ); + SetSkill(SkillName.EvalInt, 55.1, 70.0); + SetSkill(SkillName.Magery, 55.1, 70.0); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - SetSkill( SkillName.EvalInt, 55.1, 70.0 ); - SetSkill( SkillName.Magery, 55.1, 70.0 ); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 28; - VirtualArmor = 28; + PackReg(10); + } - PackReg( 10 ); - } + public Spectre(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a ghostly corpse"; + public override string DefaultName => "a spectre"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override Poison PoisonImmune => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; - public Spectre( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Succubus.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Succubus.cs index 70a6eb5bd..055a8c521 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Succubus.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Succubus.cs @@ -2,117 +2,117 @@ using System.Collections; namespace Server.Mobiles { - public class Succubus : BaseCreature - { - public override string CorpseName => "a succubus corpse"; - public override string DefaultName => "a succubus"; + public class Succubus : BaseCreature + { + [Constructible] + public Succubus() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 149; + BaseSoundID = 0x4B0; - [Constructible] - public Succubus () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 149; - BaseSoundID = 0x4B0; + SetStr(488, 620); + SetDex(121, 170); + SetInt(498, 657); - SetStr( 488, 620 ); - SetDex( 121, 170 ); - SetInt( 498, 657 ); + SetHits(312, 353); - SetHits( 312, 353 ); + SetDamage(18, 28); - SetDamage( 18, 28 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Energy, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Energy, 25 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 99.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 100.5, 150.0); + SetSkill(SkillName.Tactics, 80.1, 90.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 99.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 100.5, 150.0 ); - SetSkill( SkillName.Tactics, 80.1, 90.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); + Fame = 24000; + Karma = -24000; - Fame = 24000; - Karma = -24000; + VirtualArmor = 80; + } - VirtualArmor = 80; - } + public Succubus(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override string CorpseName => "a succubus corpse"; + public override string DefaultName => "a succubus"; - public override int Meat => 1; - public override int TreasureMapLevel => 5; + public override int Meat => 1; + public override int TreasureMapLevel => 5; - public void DrainLife() - { - ArrayList list = new ArrayList(); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.MedScrolls, 2); + } - foreach ( Mobile m in GetMobilesInRange( 2 ) ) - { - if ( m == this || !CanBeHarmful( m ) ) - continue; + public void DrainLife() + { + ArrayList list = new ArrayList(); - if ( m is BaseCreature creature && (creature.Controlled || creature.Summoned || creature.Team != Team) ) - list.Add( m ); - else if ( m.Player ) - list.Add( m ); - } + foreach (Mobile m in GetMobilesInRange(2)) + { + if (m == this || !CanBeHarmful(m)) + continue; - foreach ( Mobile m in list ) - { - DoHarmful( m ); + if (m is BaseCreature creature && (creature.Controlled || creature.Summoned || creature.Team != Team)) + list.Add(m); + else if (m.Player) + list.Add(m); + } - m.FixedParticles( 0x374A, 10, 15, 5013, 0x496, 0, EffectLayer.Waist ); - m.PlaySound( 0x231 ); + foreach (Mobile m in list) + { + DoHarmful(m); - //m.SendMessage( "You feel the life drain out of you!" ); + m.FixedParticles(0x374A, 10, 15, 5013, 0x496, 0, EffectLayer.Waist); + m.PlaySound(0x231); - int toDrain = Utility.RandomMinMax( 10, 40 ); + //m.SendMessage( "You feel the life drain out of you!" ); - Hits += toDrain; - m.Damage( toDrain, this ); - } - } + int toDrain = Utility.RandomMinMax(10, 40); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + Hits += toDrain; + m.Damage(toDrain, this); + } + } - if ( 0.1 >= Utility.RandomDouble() ) - DrainLife(); - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + if (0.1 >= Utility.RandomDouble()) + DrainLife(); + } - if ( 0.1 >= Utility.RandomDouble() ) - DrainLife(); - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public Succubus( Serial serial ) : base( serial ) - { - } + if (0.1 >= Utility.RandomDouble()) + DrainLife(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Titan.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Titan.cs index 10db23328..5da6706f5 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Titan.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Titan.cs @@ -1,72 +1,74 @@ +using Server.Engines.Plants; + namespace Server.Mobiles { - public class Titan : BaseCreature - { - public override string CorpseName => "a titans corpse"; - public override string DefaultName => "a titan"; + public class Titan : BaseCreature + { + [Constructible] + public Titan() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 76; + BaseSoundID = 609; - [Constructible] - public Titan() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 76; - BaseSoundID = 609; + SetStr(536, 585); + SetDex(126, 145); + SetInt(281, 305); - SetStr( 536, 585 ); - SetDex( 126, 145 ); - SetInt( 281, 305 ); + SetHits(322, 351); - SetHits( 322, 351 ); + SetDamage(13, 16); - SetDamage( 13, 16 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 85.1, 100.0); + SetSkill(SkillName.Magery, 85.1, 100.0); + SetSkill(SkillName.MagicResist, 80.2, 110.0); + SetSkill(SkillName.Tactics, 60.1, 80.0); + SetSkill(SkillName.Wrestling, 40.1, 50.0); - SetSkill( SkillName.EvalInt, 85.1, 100.0 ); - SetSkill( SkillName.Magery, 85.1, 100.0 ); - SetSkill( SkillName.MagicResist, 80.2, 110.0 ); - SetSkill( SkillName.Tactics, 60.1, 80.0 ); - SetSkill( SkillName.Wrestling, 40.1, 50.0 ); + Fame = 11500; + Karma = -11500; - Fame = 11500; - Karma = -11500; + VirtualArmor = 40; - VirtualArmor = 40; + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(1)); + } - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(1) ); - } + public Titan(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.MedScrolls ); - } + public override string CorpseName => "a titans corpse"; + public override string DefaultName => "a titan"; - public override int Meat => 4; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 5; + public override int Meat => 4; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 5; - public Titan( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Average); + AddLoot(LootPack.MedScrolls); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Magic/Wraith.cs b/Scripts/Mobiles/Monsters/Humanoid/Magic/Wraith.cs index dcb0666ac..509793831 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Magic/Wraith.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Magic/Wraith.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class Wraith : BaseCreature - { - public override string CorpseName => "a ghostly corpse"; - public override string DefaultName => "a wraith"; + public class Wraith : BaseCreature + { + [Constructible] + public Wraith() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 26; + Hue = 0x4001; + BaseSoundID = 0x482; - [Constructible] - public Wraith() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 26; - Hue = 0x4001; - BaseSoundID = 0x482; + SetStr(76, 100); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(46, 60); - SetHits( 46, 60 ); + SetDamage(7, 11); - SetDamage( 7, 11 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 10, 20 ); + SetSkill(SkillName.EvalInt, 55.1, 70.0); + SetSkill(SkillName.Magery, 55.1, 70.0); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - SetSkill( SkillName.EvalInt, 55.1, 70.0 ); - SetSkill( SkillName.Magery, 55.1, 70.0 ); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 28; - VirtualArmor = 28; + PackReg(10); + } - PackReg( 10 ); - } + public Wraith(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a ghostly corpse"; + public override string DefaultName => "a wraith"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override Poison PoisonImmune => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; - public Wraith( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/ArcticOgreLord.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/ArcticOgreLord.cs index dd4700405..90fde0c6e 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/ArcticOgreLord.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/ArcticOgreLord.cs @@ -2,69 +2,69 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.ArticOgreLord" )] - public class ArcticOgreLord : BaseCreature - { - public override string CorpseName => "a frozen ogre lord's corpse"; - public override string DefaultName => "an arctic ogre lord"; + [TypeAlias("Server.Mobiles.ArticOgreLord")] + public class ArcticOgreLord : BaseCreature + { + [Constructible] + public ArcticOgreLord() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 135; + BaseSoundID = 427; - [Constructible] - public ArcticOgreLord() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 135; - BaseSoundID = 427; + SetStr(767, 945); + SetDex(66, 75); + SetInt(46, 70); - SetStr( 767, 945 ); - SetDex( 66, 75 ); - SetInt( 46, 70 ); + SetHits(476, 552); - SetHits( 476, 552 ); + SetDamage(20, 25); - SetDamage( 20, 25 ); + SetDamageType(ResistanceType.Physical, 30); + SetDamageType(ResistanceType.Cold, 70); - SetDamageType( ResistanceType.Physical, 30 ); - SetDamageType( ResistanceType.Cold, 70 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.MagicResist, 125.1, 140.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.MagicResist, 125.1, 140.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + VirtualArmor = 50; - VirtualArmor = 50; + PackItem(new Club()); + } - PackItem( new Club() ); - } + public ArcticOgreLord(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a frozen ogre lord's corpse"; + public override string DefaultName => "an arctic ogre lord"; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 3; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 3; - public ArcticOgreLord( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/BoneKnight.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/BoneKnight.cs index 5a9b657b5..df762665d 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/BoneKnight.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/BoneKnight.cs @@ -2,82 +2,94 @@ using Server.Items; namespace Server.Mobiles { - public class BoneKnight : BaseCreature - { - public override string CorpseName => "a skeletal corpse"; - public override string DefaultName => "a bone knight"; + public class BoneKnight : BaseCreature + { + [Constructible] + public BoneKnight() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 57; + BaseSoundID = 451; - [Constructible] - public BoneKnight() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 57; - BaseSoundID = 451; + SetStr(196, 250); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 196, 250 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(118, 150); - SetHits( 118, 150 ); + SetDamage(8, 18); - SetDamage( 8, 18 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 85.1, 100.0); + SetSkill(SkillName.Wrestling, 85.1, 95.0); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 85.1, 100.0 ); - SetSkill( SkillName.Wrestling, 85.1, 95.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 40; - VirtualArmor = 40; + switch (Utility.Random(6)) + { + case 0: + PackItem(new PlateArms()); + break; + case 1: + PackItem(new PlateChest()); + break; + case 2: + PackItem(new PlateGloves()); + break; + case 3: + PackItem(new PlateGorget()); + break; + case 4: + PackItem(new PlateLegs()); + break; + case 5: + PackItem(new PlateHelm()); + break; + } - switch ( Utility.Random( 6 ) ) - { - case 0: PackItem( new PlateArms() ); break; - case 1: PackItem( new PlateChest() ); break; - case 2: PackItem( new PlateGloves() ); break; - case 3: PackItem( new PlateGorget() ); break; - case 4: PackItem( new PlateLegs() ); break; - case 5: PackItem( new PlateHelm() ); break; - } + PackSlayer(); + PackItem(new Scimitar()); + PackItem(new WoodenShield()); + } - PackSlayer(); - PackItem( new Scimitar() ); - PackItem( new WoodenShield() ); - } + public BoneKnight(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a skeletal corpse"; + public override string DefaultName => "a bone knight"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public BoneKnight( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Brigand.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Brigand.cs index f2b65e795..ee73d5b03 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Brigand.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Brigand.cs @@ -2,95 +2,109 @@ using Server.Items; namespace Server.Mobiles { - public class Brigand : BaseCreature - { - public override bool ClickTitle => false; + public class Brigand : BaseCreature + { + [Constructible] + public Brigand() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SpeechHue = Utility.RandomDyedHue(); + Title = "the brigand"; + Hue = Utility.RandomSkinHue(); - [Constructible] - public Brigand() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SpeechHue = Utility.RandomDyedHue(); - Title = "the brigand"; - Hue = Utility.RandomSkinHue(); + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + AddItem(new Skirt(Utility.RandomNeutralHue())); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + AddItem(new ShortPants(Utility.RandomNeutralHue())); + } - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - AddItem( new Skirt( Utility.RandomNeutralHue() ) ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - AddItem( new ShortPants( Utility.RandomNeutralHue() ) ); - } + SetStr(86, 100); + SetDex(81, 95); + SetInt(61, 75); - SetStr( 86, 100 ); - SetDex( 81, 95 ); - SetInt( 61, 75 ); + SetDamage(10, 23); - SetDamage( 10, 23 ); + SetSkill(SkillName.Fencing, 66.0, 97.5); + SetSkill(SkillName.Macing, 65.0, 87.5); + SetSkill(SkillName.MagicResist, 25.0, 47.5); + SetSkill(SkillName.Swords, 65.0, 87.5); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 15.0, 37.5); - SetSkill( SkillName.Fencing, 66.0, 97.5 ); - SetSkill( SkillName.Macing, 65.0, 87.5 ); - SetSkill( SkillName.MagicResist, 25.0, 47.5 ); - SetSkill( SkillName.Swords, 65.0, 87.5 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 15.0, 37.5 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + AddItem(new Boots(Utility.RandomNeutralHue())); + AddItem(new FancyShirt()); + AddItem(new Bandana()); - AddItem( new Boots( Utility.RandomNeutralHue() ) ); - AddItem( new FancyShirt()); - AddItem( new Bandana()); + switch (Utility.Random(7)) + { + case 0: + AddItem(new Longsword()); + break; + case 1: + AddItem(new Cutlass()); + break; + case 2: + AddItem(new Broadsword()); + break; + case 3: + AddItem(new Axe()); + break; + case 4: + AddItem(new Club()); + break; + case 5: + AddItem(new Dagger()); + break; + case 6: + AddItem(new Spear()); + break; + } - switch ( Utility.Random( 7 )) - { - case 0: AddItem( new Longsword() ); break; - case 1: AddItem( new Cutlass() ); break; - case 2: AddItem( new Broadsword() ); break; - case 3: AddItem( new Axe() ); break; - case 4: AddItem( new Club() ); break; - case 5: AddItem( new Dagger() ); break; - case 6: AddItem( new Spear() ); break; - } + Utility.AssignRandomHair(this); + } - Utility.AssignRandomHair( this ); - } + public Brigand(Serial serial) : base(serial) + { + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool ClickTitle => false; - if ( Utility.RandomDouble() < 0.9 ) - c.DropItem( new SeveredHumanEars() ); - } + public override bool AlwaysMurderer => true; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override bool AlwaysMurderer => true; + if (Utility.RandomDouble() < 0.9) + c.DropItem(new SeveredHumanEars()); + } - public Brigand( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/ChaosDaemon.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/ChaosDaemon.cs index e5d81d6bc..c80d14888 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/ChaosDaemon.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/ChaosDaemon.cs @@ -2,66 +2,70 @@ using Server.Items; namespace Server.Mobiles { - public class ChaosDaemon : BaseCreature - { - public override string CorpseName => "a chaos daemon corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.CrushingBlow; + public class ChaosDaemon : BaseCreature + { + [Constructible] + public ChaosDaemon() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 792; + BaseSoundID = 0x3E9; - public override string DefaultName => "a chaos daemon"; + SetStr(106, 130); + SetDex(171, 200); + SetInt(56, 80); - [Constructible] - public ChaosDaemon() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 792; - BaseSoundID = 0x3E9; + SetHits(91, 110); - SetStr( 106, 130 ); - SetDex( 171, 200 ); - SetInt( 56, 80 ); + SetDamage(12, 17); - SetHits( 91, 110 ); + SetDamageType(ResistanceType.Physical, 85); + SetDamageType(ResistanceType.Fire, 15); - SetDamage( 12, 17 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 85 ); - SetDamageType( ResistanceType.Fire, 15 ); + SetSkill(SkillName.MagicResist, 85.1, 95.0); + SetSkill(SkillName.Tactics, 70.1, 80.0); + SetSkill(SkillName.Wrestling, 95.1, 100.0); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 3000; + Karma = -4000; - SetSkill( SkillName.MagicResist, 85.1, 95.0 ); - SetSkill( SkillName.Tactics, 70.1, 80.0 ); - SetSkill( SkillName.Wrestling, 95.1, 100.0 ); + VirtualArmor = 15; + } - Fame = 3000; - Karma = -4000; + public ChaosDaemon(Serial serial) : base(serial) + { + } - VirtualArmor = 15; - } + public override string CorpseName => "a chaos daemon corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - } + public override string DefaultName => "a chaos daemon"; - public ChaosDaemon( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.CrushingBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Cursed.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Cursed.cs index 77c311ff7..7864d60ef 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Cursed.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Cursed.cs @@ -2,83 +2,83 @@ using Server.Items; namespace Server.Mobiles { - public class Cursed : BaseCreature - { - public override string CorpseName => "an inhuman corpse"; - public override bool ClickTitle => false; - public override bool ShowFameTitle => false; + public class Cursed : BaseCreature + { + [Constructible] + public Cursed() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Title = "the Cursed"; - [Constructible] - public Cursed() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Title = "the Cursed"; + Hue = Utility.RandomMinMax(0x8596, 0x8599); + Body = 0x190; + Name = NameList.RandomName("male"); + BaseSoundID = 471; - Hue = Utility.RandomMinMax( 0x8596, 0x8599 ); - Body = 0x190; - Name = NameList.RandomName( "male" ); - BaseSoundID = 471; + AddItem(new ShortPants(Utility.RandomNeutralHue())); + AddItem(new Shirt(Utility.RandomNeutralHue())); - AddItem( new ShortPants( Utility.RandomNeutralHue() ) ); - AddItem( new Shirt( Utility.RandomNeutralHue() ) ); + BaseWeapon weapon = Loot.RandomWeapon(); + weapon.Movable = false; + AddItem(weapon); - BaseWeapon weapon = Loot.RandomWeapon(); - weapon.Movable = false; - AddItem( weapon ); + SetStr(91, 100); + SetDex(86, 95); + SetInt(61, 70); - SetStr( 91, 100 ); - SetDex( 86, 95 ); - SetInt( 61, 70 ); + SetHits(91, 120); - SetHits( 91, 120 ); + SetDamage(5, 13); - SetDamage( 5, 13 ); + SetResistance(ResistanceType.Physical, 15, 25); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 15, 25 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.Fencing, 46.0, 77.5); + SetSkill(SkillName.Macing, 35.0, 57.5); + SetSkill(SkillName.MagicResist, 53.5, 62.5); + SetSkill(SkillName.Swords, 55.0, 77.5); + SetSkill(SkillName.Tactics, 60.0, 82.5); + SetSkill(SkillName.Poisoning, 60.0, 82.5); - SetSkill( SkillName.Fencing, 46.0, 77.5 ); - SetSkill( SkillName.Macing, 35.0, 57.5 ); - SetSkill( SkillName.MagicResist, 53.5, 62.5 ); - SetSkill( SkillName.Swords, 55.0, 77.5 ); - SetSkill( SkillName.Tactics, 60.0, 82.5 ); - SetSkill( SkillName.Poisoning, 60.0, 82.5 ); + Fame = 1000; + Karma = -2000; + } - Fame = 1000; - Karma = -2000; - } + public Cursed(Serial serial) : base(serial) + { + } - public override int GetAttackSound() - { - return -1; - } + public override string CorpseName => "an inhuman corpse"; + public override bool ClickTitle => false; + public override bool ShowFameTitle => false; - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - //AddLoot( LootPack.Miscellaneous ); - } + public override bool AlwaysMurderer => true; - public override bool AlwaysMurderer => true; + public override int GetAttackSound() + { + return -1; + } - public Cursed( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + //AddLoot( LootPack.Miscellaneous ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Cyclops.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Cyclops.cs index 0fc92af7f..80120308e 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Cyclops.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Cyclops.cs @@ -1,66 +1,66 @@ namespace Server.Mobiles { - public class Cyclops : BaseCreature - { - public override string CorpseName => "a cyclopean corpse"; - public override string DefaultName => "a cyclopean warrior"; + public class Cyclops : BaseCreature + { + [Constructible] + public Cyclops() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 75; + BaseSoundID = 604; - [Constructible] - public Cyclops() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 75; - BaseSoundID = 604; + SetStr(336, 385); + SetDex(96, 115); + SetInt(31, 55); - SetStr( 336, 385 ); - SetDex( 96, 115 ); - SetInt( 31, 55 ); + SetHits(202, 231); + SetMana(0); - SetHits( 202, 231 ); - SetMana( 0 ); + SetDamage(7, 23); - SetDamage( 7, 23 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 45, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 45, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 60.3, 105.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); - SetSkill( SkillName.MagicResist, 60.3, 105.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); + Fame = 4500; + Karma = -4500; - Fame = 4500; - Karma = -4500; + VirtualArmor = 48; + } - VirtualArmor = 48; - } + public Cyclops(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a cyclopean corpse"; + public override string DefaultName => "a cyclopean warrior"; - public override int Meat => 4; - public override int TreasureMapLevel => 3; + public override int Meat => 4; + public override int TreasureMapLevel => 3; - public Cyclops( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Doppleganger.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Doppleganger.cs index 4429da2ee..6a76ceb7c 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Doppleganger.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Doppleganger.cs @@ -1,62 +1,62 @@ namespace Server.Mobiles { - public class Doppleganger : BaseCreature - { - public override string CorpseName => "a doppleganger corpse"; - public override string DefaultName => "a doppleganger"; + public class Doppleganger : BaseCreature + { + [Constructible] + public Doppleganger() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x309; + BaseSoundID = 0x451; - [Constructible] - public Doppleganger() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x309; - BaseSoundID = 0x451; + SetStr(81, 110); + SetDex(56, 75); + SetInt(81, 105); - SetStr( 81, 110 ); - SetDex( 56, 75 ); - SetInt( 81, 105 ); + SetHits(101, 120); - SetHits( 101, 120 ); + SetDamage(8, 12); - SetDamage( 8, 12 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 75.1, 85.0); + SetSkill(SkillName.Tactics, 70.1, 80.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); - SetSkill( SkillName.MagicResist, 75.1, 85.0 ); - SetSkill( SkillName.Tactics, 70.1, 80.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + VirtualArmor = 55; + } - VirtualArmor = 55; - } + public Doppleganger(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a doppleganger corpse"; + public override string DefaultName => "a doppleganger"; - public override int Hides => 6; - public override int Meat => 1; + public override int Hides => 6; + public override int Meat => 1; - public Doppleganger( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/ElfBrigand.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/ElfBrigand.cs index f54f1c8d8..fec566b1a 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/ElfBrigand.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/ElfBrigand.cs @@ -2,108 +2,134 @@ using Server.Items; namespace Server.Mobiles { - // TODO: Needs some Spellweaving abilities - public class ElfBrigand : BaseCreature - { - public override bool ClickTitle => false; + // TODO: Needs some Spellweaving abilities + public class ElfBrigand : BaseCreature + { + [Constructible] + public ElfBrigand() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SpeechHue = Utility.RandomDyedHue(); + Title = "the brigand"; + Race = Race.Elf; + Hue = Race.RandomSkinHue(); - [Constructible] - public ElfBrigand() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SpeechHue = Utility.RandomDyedHue(); - Title = "the brigand"; - Race = Race.Elf; - Hue = Race.RandomSkinHue(); + if (Female = Utility.RandomBool()) + { + Body = 0x25E; + Name = NameList.RandomName("female elf brigand"); - if ( Female = Utility.RandomBool() ) - { - Body = 0x25E; - Name = NameList.RandomName( "female elf brigand" ); + switch (Utility.Random(2)) + { + case 0: + AddItem(new Skirt(Utility.RandomNondyedHue())); + break; + case 1: + AddItem(new Kilt(Utility.RandomNondyedHue())); + break; + } + } + else + { + Body = 0x25D; + Name = NameList.RandomName("male elf brigand"); + AddItem(new ShortPants(Utility.RandomNondyedHue())); + } - switch ( Utility.Random( 2 ) ) - { - case 0: AddItem( new Skirt( Utility.RandomNondyedHue() ) ); break; - case 1: AddItem( new Kilt( Utility.RandomNondyedHue() ) ); break; - } - } - else - { - Body = 0x25D; - Name = NameList.RandomName( "male elf brigand" ); - AddItem( new ShortPants( Utility.RandomNondyedHue() ) ); - } + SetStr(86, 100); + SetDex(81, 95); + SetInt(61, 75); - SetStr( 86, 100 ); - SetDex( 81, 95 ); - SetInt( 61, 75 ); + SetDamage(10, 23); - SetDamage( 10, 23 ); + SetSkill(SkillName.Fencing, 66.0, 97.5); + SetSkill(SkillName.Macing, 65.0, 87.5); + SetSkill(SkillName.MagicResist, 25.0, 47.5); + SetSkill(SkillName.Swords, 65.0, 87.5); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 15.0, 37.5); - SetSkill( SkillName.Fencing, 66.0, 97.5 ); - SetSkill( SkillName.Macing, 65.0, 87.5 ); - SetSkill( SkillName.MagicResist, 25.0, 47.5 ); - SetSkill( SkillName.Swords, 65.0, 87.5 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 15.0, 37.5 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + switch (Utility.Random(4)) + { + case 0: + AddItem(new Boots()); + break; + case 1: + AddItem(new ThighBoots()); + break; + case 2: + AddItem(new Sandals()); + break; + case 3: + AddItem(new Shoes()); + break; + } - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new Boots() ); break; - case 1: AddItem( new ThighBoots() ); break; - case 2: AddItem( new Sandals() ); break; - case 3: AddItem( new Shoes() ); break; - } + AddItem(new Shirt(Utility.RandomNondyedHue())); - AddItem( new Shirt( Utility.RandomNondyedHue() ) ); + switch (Utility.Random(7)) + { + case 0: + AddItem(new Longsword()); + break; + case 1: + AddItem(new Cutlass()); + break; + case 2: + AddItem(new Broadsword()); + break; + case 3: + AddItem(new Axe()); + break; + case 4: + AddItem(new Club()); + break; + case 5: + AddItem(new Dagger()); + break; + case 6: + AddItem(new Spear()); + break; + } - switch ( Utility.Random( 7 ) ) - { - case 0: AddItem( new Longsword() ); break; - case 1: AddItem( new Cutlass() ); break; - case 2: AddItem( new Broadsword() ); break; - case 3: AddItem( new Axe() ); break; - case 4: AddItem( new Club() ); break; - case 5: AddItem( new Dagger() ); break; - case 6: AddItem( new Spear() ); break; - } + Utility.AssignRandomHair(this, true); + } - Utility.AssignRandomHair( this, true ); - } + public ElfBrigand(Serial serial) : base(serial) + { + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool ClickTitle => false; - if ( Utility.RandomDouble() < 0.9 ) - c.DropItem( new SeveredElfEars() ); - } + public override bool AlwaysMurderer => true; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override bool AlwaysMurderer => true; + if (Utility.RandomDouble() < 0.9) + c.DropItem(new SeveredElfEars()); + } - public ElfBrigand( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/EnslavedGargoyle.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/EnslavedGargoyle.cs index 84e294f6c..103add859 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/EnslavedGargoyle.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/EnslavedGargoyle.cs @@ -2,67 +2,67 @@ using Server.Items; namespace Server.Mobiles { - public class EnslavedGargoyle : BaseCreature - { - public override string CorpseName => "an enslaved gargoyle corpse"; - public override string DefaultName => "an enslaved gargoyle"; + public class EnslavedGargoyle : BaseCreature + { + [Constructible] + public EnslavedGargoyle() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x2F1; + BaseSoundID = 0x174; - [Constructible] - public EnslavedGargoyle() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x2F1; - BaseSoundID = 0x174; + SetStr(302, 360); + SetDex(76, 95); + SetInt(81, 105); - SetStr( 302, 360 ); - SetDex( 76, 95 ); - SetInt( 81, 105 ); + SetHits(186, 212); - SetHits( 186,212 ); + SetDamage(7, 14); - SetDamage( 7, 14 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 50, 70); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 25, 30); + SetResistance(ResistanceType.Energy, 25, 30); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 50, 70 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 25, 30 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + SetSkill(SkillName.MagicResist, 70.1, 85.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 40.1, 80.0); - SetSkill( SkillName.MagicResist, 70.1, 85.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 40.1, 80.0 ); + Fame = 3500; + Karma = 0; - Fame = 3500; - Karma = 0; + VirtualArmor = 35; - VirtualArmor = 35; + if (0.2 > Utility.RandomDouble()) + PackItem(new GargoylesPickaxe()); + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new GargoylesPickaxe() ); - } + public EnslavedGargoyle(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.Gems ); - } + public override string CorpseName => "an enslaved gargoyle corpse"; + public override string DefaultName => "an enslaved gargoyle"; - public override int Meat => 1; - public override int TreasureMapLevel => 1; + public override int Meat => 1; + public override int TreasureMapLevel => 1; - public EnslavedGargoyle( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ettin.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ettin.cs index 57f633fad..6e2f46d24 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ettin.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ettin.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class Ettin : BaseCreature - { - public override string CorpseName => "an ettins corpse"; - public override string DefaultName => "an ettin"; + public class Ettin : BaseCreature + { + [Constructible] + public Ettin() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 18; + BaseSoundID = 367; - [Constructible] - public Ettin() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 18; - BaseSoundID = 367; + SetStr(136, 165); + SetDex(56, 75); + SetInt(31, 55); - SetStr( 136, 165 ); - SetDex( 56, 75 ); - SetInt( 31, 55 ); + SetHits(82, 99); - SetHits( 82, 99 ); + SetDamage(7, 17); - SetDamage( 7, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 15, 25); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + SetSkill(SkillName.MagicResist, 40.1, 55.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 50.1, 60.0); - SetSkill( SkillName.MagicResist, 40.1, 55.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 50.1, 60.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 38; + } - VirtualArmor = 38; - } + public Ettin(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "an ettins corpse"; + public override string DefaultName => "an ettin"; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 1; - public override int Meat => 4; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 1; + public override int Meat => 4; - public Ettin( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.Average); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Executioner.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Executioner.cs index 77f4bc737..d39c27a4d 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Executioner.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Executioner.cs @@ -2,87 +2,87 @@ using Server.Items; namespace Server.Mobiles { - public class Executioner : BaseCreature - { - [Constructible] - public Executioner() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SpeechHue = Utility.RandomDyedHue(); - Title = "the executioner"; - Hue = Utility.RandomSkinHue(); + public class Executioner : BaseCreature + { + [Constructible] + public Executioner() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SpeechHue = Utility.RandomDyedHue(); + Title = "the executioner"; + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - AddItem( new Skirt( Utility.RandomRedHue() ) ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - AddItem( new ShortPants( Utility.RandomRedHue() ) ); - } + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + AddItem(new Skirt(Utility.RandomRedHue())); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + AddItem(new ShortPants(Utility.RandomRedHue())); + } - SetStr( 386, 400 ); - SetDex( 151, 165 ); - SetInt( 161, 175 ); + SetStr(386, 400); + SetDex(151, 165); + SetInt(161, 175); - SetDamage( 8, 10 ); + SetDamage(8, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 25, 30 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 25, 30); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetSkill( SkillName.Anatomy, 125.0 ); - SetSkill( SkillName.Fencing, 46.0, 77.5 ); - SetSkill( SkillName.Macing, 35.0, 57.5 ); - SetSkill( SkillName.Poisoning, 60.0, 82.5 ); - SetSkill( SkillName.MagicResist, 83.5, 92.5 ); - SetSkill( SkillName.Swords, 125.0 ); - SetSkill( SkillName.Tactics, 125.0 ); - SetSkill( SkillName.Lumberjacking, 125.0 ); + SetSkill(SkillName.Anatomy, 125.0); + SetSkill(SkillName.Fencing, 46.0, 77.5); + SetSkill(SkillName.Macing, 35.0, 57.5); + SetSkill(SkillName.Poisoning, 60.0, 82.5); + SetSkill(SkillName.MagicResist, 83.5, 92.5); + SetSkill(SkillName.Swords, 125.0); + SetSkill(SkillName.Tactics, 125.0); + SetSkill(SkillName.Lumberjacking, 125.0); - Fame = 5000; - Karma = -5000; + Fame = 5000; + Karma = -5000; - VirtualArmor = 40; + VirtualArmor = 40; - AddItem( new ThighBoots( Utility.RandomRedHue() ) ); - AddItem( new Surcoat( Utility.RandomRedHue() ) ); - AddItem( new ExecutionersAxe()); + AddItem(new ThighBoots(Utility.RandomRedHue())); + AddItem(new Surcoat(Utility.RandomRedHue())); + AddItem(new ExecutionersAxe()); - Utility.AssignRandomHair( this ); - } + Utility.AssignRandomHair(this); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Meager ); - } + public Executioner(Serial serial) : base(serial) + { + } - public override bool AlwaysMurderer => true; + public override bool AlwaysMurderer => true; - public Executioner( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/FrostTroll.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/FrostTroll.cs index 1f399c550..db86feb5c 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/FrostTroll.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/FrostTroll.cs @@ -2,68 +2,68 @@ using Server.Items; namespace Server.Mobiles { - public class FrostTroll : BaseCreature - { - public override string CorpseName => "a frost troll corpse"; - public override string DefaultName => "a frost troll"; + public class FrostTroll : BaseCreature + { + [Constructible] + public FrostTroll() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 55; + BaseSoundID = 461; - [Constructible] - public FrostTroll() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 55; - BaseSoundID = 461; + SetStr(227, 265); + SetDex(66, 85); + SetInt(46, 70); - SetStr( 227, 265 ); - SetDex( 66, 85 ); - SetInt( 46, 70 ); + SetHits(140, 156); - SetHits( 140, 156 ); + SetDamage(14, 20); - SetDamage( 14, 20 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Cold, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Cold, 25 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 50; - VirtualArmor = 50; + PackItem(new DoubleAxe()); // TODO: Weapon?? + } - PackItem( new DoubleAxe() ); // TODO: Weapon?? - } + public FrostTroll(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems ); - } + public override string CorpseName => "a frost troll corpse"; + public override string DefaultName => "a frost troll"; - public override int Meat => 2; - public override int TreasureMapLevel => 1; + public override int Meat => 2; + public override int TreasureMapLevel => 1; - public FrostTroll( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/GazerLarva.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/GazerLarva.cs index 447d228ab..0bcb0654c 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/GazerLarva.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/GazerLarva.cs @@ -2,62 +2,62 @@ using Server.Items; namespace Server.Mobiles { - public class GazerLarva : BaseCreature - { - public override string CorpseName => "a gazer larva corpse"; - public override string DefaultName => "a gazer larva"; + public class GazerLarva : BaseCreature + { + [Constructible] + public GazerLarva() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 778; + BaseSoundID = 377; - [Constructible] - public GazerLarva () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 778; - BaseSoundID = 377; + SetStr(76, 100); + SetDex(51, 75); + SetInt(56, 80); - SetStr( 76, 100 ); - SetDex( 51, 75 ); - SetInt( 56, 80 ); + SetHits(36, 47); - SetHits( 36, 47 ); + SetDamage(2, 9); - SetDamage( 2, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 25); - SetResistance( ResistanceType.Physical, 15, 25 ); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 70.0); + SetSkill(SkillName.Wrestling, 70.0); - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 70.0 ); - SetSkill( SkillName.Wrestling, 70.0 ); + Fame = 900; + Karma = -900; - Fame = 900; - Karma = -900; + VirtualArmor = 25; - VirtualArmor = 25; + PackItem(new Nightshade(Utility.RandomMinMax(2, 3))); + } - PackItem( new Nightshade( Utility.RandomMinMax( 2, 3 ) ) ); - } + public GazerLarva(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a gazer larva corpse"; + public override string DefaultName => "a gazer larva"; - public override int Meat => 1; + public override int Meat => 1; - public GazerLarva( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ghoul.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ghoul.cs index 88be9a236..7e0ddaf36 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ghoul.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ghoul.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - public class Ghoul : BaseCreature - { - public override string CorpseName => "a ghostly corpse"; - public override string DefaultName => "a ghoul"; + public class Ghoul : BaseCreature + { + [Constructible] + public Ghoul() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 153; + BaseSoundID = 0x482; - [Constructible] - public Ghoul() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 153; - BaseSoundID = 0x482; + SetStr(76, 100); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 76, 100 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(46, 60); + SetMana(0); - SetHits( 46, 60 ); - SetMana( 0 ); + SetDamage(7, 9); - SetDamage( 7, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 28; - VirtualArmor = 28; + PackItem(Loot.RandomWeapon()); + } - PackItem( Loot.RandomWeapon() ); - } + public Ghoul(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a ghostly corpse"; + public override string DefaultName => "a ghoul"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Regular; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Regular; - public Ghoul( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/GreaterMongbat.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/GreaterMongbat.cs index 3323e1f47..8c8e5d502 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/GreaterMongbat.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/GreaterMongbat.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class GreaterMongbat : BaseCreature - { - public override string CorpseName => "a mongbat corpse"; - public override string DefaultName => "a greater mongbat"; + public class GreaterMongbat : BaseCreature + { + [Constructible] + public GreaterMongbat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 39; + BaseSoundID = 422; - [Constructible] - public GreaterMongbat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 39; - BaseSoundID = 422; + SetStr(56, 80); + SetDex(61, 80); + SetInt(26, 50); - SetStr( 56, 80 ); - SetDex( 61, 80 ); - SetInt( 26, 50 ); + SetHits(34, 48); + SetStam(61, 80); + SetMana(26, 50); - SetHits( 34, 48 ); - SetStam( 61, 80); - SetMana( 26, 50 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 25); - SetResistance( ResistanceType.Physical, 15, 25 ); + SetSkill(SkillName.MagicResist, 15.1, 30.0); + SetSkill(SkillName.Tactics, 35.1, 50.0); + SetSkill(SkillName.Wrestling, 20.1, 35.0); - SetSkill( SkillName.MagicResist, 15.1, 30.0 ); - SetSkill( SkillName.Tactics, 35.1, 50.0 ); - SetSkill( SkillName.Wrestling, 20.1, 35.0 ); + Fame = 450; + Karma = -450; - Fame = 450; - Karma = -450; + VirtualArmor = 10; - VirtualArmor = 10; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 71.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 71.1; - } + public GreaterMongbat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a mongbat corpse"; + public override string DefaultName => "a greater mongbat"; - public override int Meat => 1; - public override int Hides => 6; - public override FoodType FavoriteFood => FoodType.Meat; + public override int Meat => 1; + public override int Hides => 6; + public override FoodType FavoriteFood => FoodType.Meat; - public GreaterMongbat( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Guardian.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Guardian.cs index 7495171c2..9ec7f9379 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Guardian.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Guardian.cs @@ -1,87 +1,86 @@ using Server.Items; -namespace Server.Mobiles -{ - public class Guardian : BaseCreature - { - [Constructible] - public Guardian() : base( AIType.AI_Archer, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - InitStats( 100, 125, 25 ); - Title = "the guardian"; +namespace Server.Mobiles +{ + public class Guardian : BaseCreature + { + [Constructible] + public Guardian() : base(AIType.AI_Archer, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + InitStats(100, 125, 25); + Title = "the guardian"; - SpeechHue = Utility.RandomDyedHue(); + SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } - new ForestOstard().Rider = this; + new ForestOstard().Rider = this; - PlateChest chest = new PlateChest(); - chest.Hue = 0x966; - AddItem( chest ); - PlateArms arms = new PlateArms(); - arms.Hue = 0x966; - AddItem( arms ); - PlateGloves gloves = new PlateGloves(); - gloves.Hue = 0x966; - AddItem( gloves ); - PlateGorget gorget = new PlateGorget(); - gorget.Hue = 0x966; - AddItem( gorget ); - PlateLegs legs = new PlateLegs(); - legs.Hue = 0x966; - AddItem( legs ); - PlateHelm helm = new PlateHelm(); - helm.Hue = 0x966; - AddItem( helm ); + PlateChest chest = new PlateChest(); + chest.Hue = 0x966; + AddItem(chest); + PlateArms arms = new PlateArms(); + arms.Hue = 0x966; + AddItem(arms); + PlateGloves gloves = new PlateGloves(); + gloves.Hue = 0x966; + AddItem(gloves); + PlateGorget gorget = new PlateGorget(); + gorget.Hue = 0x966; + AddItem(gorget); + PlateLegs legs = new PlateLegs(); + legs.Hue = 0x966; + AddItem(legs); + PlateHelm helm = new PlateHelm(); + helm.Hue = 0x966; + AddItem(helm); - Bow bow = new Bow(); + Bow bow = new Bow(); - bow.Movable = false; - bow.Crafter = this; - bow.Quality = WeaponQuality.Exceptional; + bow.Movable = false; + bow.Crafter = this; + bow.Quality = WeaponQuality.Exceptional; - AddItem( bow ); + AddItem(bow); - PackItem( new Arrow( 250 ) ); - PackGold( 250, 500 ); + PackItem(new Arrow(250)); + PackGold(250, 500); - Skills[SkillName.Anatomy].Base = 120.0; - Skills[SkillName.Tactics].Base = 120.0; - Skills[SkillName.Archery].Base = 120.0; - Skills[SkillName.MagicResist].Base = 120.0; - Skills[SkillName.DetectHidden].Base = 100.0; + Skills[SkillName.Anatomy].Base = 120.0; + Skills[SkillName.Tactics].Base = 120.0; + Skills[SkillName.Archery].Base = 120.0; + Skills[SkillName.MagicResist].Base = 120.0; + Skills[SkillName.DetectHidden].Base = 100.0; + } - } + public Guardian(Serial serial) : base(serial) + { + } - public Guardian( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/HeadlessOne.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/HeadlessOne.cs index 104d084b2..f5b4b9e4e 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/HeadlessOne.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/HeadlessOne.cs @@ -1,62 +1,62 @@ namespace Server.Mobiles { - public class HeadlessOne : BaseCreature - { - public override string CorpseName => "a headless corpse"; - public override string DefaultName => "a headless one"; + public class HeadlessOne : BaseCreature + { + [Constructible] + public HeadlessOne() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 31; + Hue = Utility.RandomSkinHue() & 0x7FFF; + BaseSoundID = 0x39D; - [Constructible] - public HeadlessOne() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 31; - Hue = Utility.RandomSkinHue() & 0x7FFF; - BaseSoundID = 0x39D; + SetStr(26, 50); + SetDex(36, 55); + SetInt(16, 30); - SetStr( 26, 50 ); - SetDex( 36, 55 ); - SetInt( 16, 30 ); + SetHits(16, 30); - SetHits( 16, 30 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); - SetResistance( ResistanceType.Physical, 15, 20 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 25.1, 40.0); + SetSkill(SkillName.Wrestling, 25.1, 40.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 25.1, 40.0 ); - SetSkill( SkillName.Wrestling, 25.1, 40.0 ); + Fame = 450; + Karma = -450; - Fame = 450; - Karma = -450; + VirtualArmor = 18; + } - VirtualArmor = 18; - } + public HeadlessOne(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - // TODO: body parts - } + public override string CorpseName => "a headless corpse"; + public override string DefaultName => "a headless one"; - public override bool CanRummageCorpses => true; - public override int Meat => 1; + public override bool CanRummageCorpses => true; + public override int Meat => 1; - public HeadlessOne( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + // TODO: body parts + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/HordeMinion.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/HordeMinion.cs index 600cba0f9..33daeddfd 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/HordeMinion.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/HordeMinion.cs @@ -2,84 +2,84 @@ using Server.Items; namespace Server.Mobiles { - public class HordeMinion : BaseCreature - { - public override string CorpseName => "a horde minion corpse"; - public override string DefaultName => "a horde minion"; + public class HordeMinion : BaseCreature + { + [Constructible] + public HordeMinion() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 776; + BaseSoundID = 357; - [Constructible] - public HordeMinion () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 776; - BaseSoundID = 357; + SetStr(16, 40); + SetDex(31, 60); + SetInt(11, 25); - SetStr( 16, 40 ); - SetDex( 31, 60 ); - SetInt( 11, 25 ); + SetHits(10, 24); - SetHits( 10, 24 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 10); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); + SetSkill(SkillName.MagicResist, 10.0); + SetSkill(SkillName.Tactics, 0.1, 15.0); + SetSkill(SkillName.Wrestling, 25.1, 40.0); - SetSkill( SkillName.MagicResist, 10.0 ); - SetSkill( SkillName.Tactics, 0.1, 15.0 ); - SetSkill( SkillName.Wrestling, 25.1, 40.0 ); + Fame = 500; + Karma = -500; - Fame = 500; - Karma = -500; + VirtualArmor = 18; - VirtualArmor = 18; + AddItem(new LightSource()); - AddItem( new LightSource() ); + PackItem(new Bone(3)); + // TODO: Body parts + } - PackItem( new Bone( 3 ) ); - // TODO: Body parts - } + public HordeMinion(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 338; - } + public override string CorpseName => "a horde minion corpse"; + public override string DefaultName => "a horde minion"; - public override int GetAngerSound() - { - return 338; - } + public override int GetIdleSound() + { + return 338; + } - public override int GetDeathSound() - { - return 338; - } + public override int GetAngerSound() + { + return 338; + } - public override int GetAttackSound() - { - return 406; - } + public override int GetDeathSound() + { + return 338; + } - public override int GetHurtSound() - { - return 194; - } + public override int GetAttackSound() + { + return 406; + } - public HordeMinion( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 194; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Juggernaut.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Juggernaut.cs index 5be10248b..c2b9d66bf 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Juggernaut.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Juggernaut.cs @@ -4,151 +4,155 @@ using Server.Network; namespace Server.Mobiles { - public class Juggernaut : BaseCreature - { - public override string CorpseName => "a juggernaut corpse"; - private bool m_Stunning; + public class Juggernaut : BaseCreature + { + private bool m_Stunning; - public override string DefaultName => "a blackthorn juggernaut"; - - [Constructible] - public Juggernaut() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.3, 0.6 ) - { - Body = 768; + [Constructible] + public Juggernaut() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.3, 0.6) + { + Body = 768; - SetStr( 301, 400 ); - SetDex( 51, 70 ); - SetInt( 51, 100 ); + SetStr(301, 400); + SetDex(51, 70); + SetInt(51, 100); - SetHits( 181, 240 ); + SetHits(181, 240); - SetDamage( 12, 19 ); + SetDamage(12, 19); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Fire, 25 ); - SetDamageType( ResistanceType.Energy, 25 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Fire, 25); + SetDamageType(ResistanceType.Energy, 25); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 10, 20); - SetSkill( SkillName.Anatomy, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 140.1, 150.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + SetSkill(SkillName.Anatomy, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 140.1, 150.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - Fame = 12000; - Karma = -12000; + Fame = 12000; + Karma = -12000; - VirtualArmor = 70; + VirtualArmor = 70; - if ( 0.1 > Utility.RandomDouble() ) - PackItem( new PowerCrystal() ); + if (0.1 > Utility.RandomDouble()) + PackItem(new PowerCrystal()); - if ( 0.4 > Utility.RandomDouble() ) - PackItem( new ClockworkAssembly() ); - } + if (0.4 > Utility.RandomDouble()) + PackItem(new ClockworkAssembly()); + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public Juggernaut(Serial serial) : base(serial) + { + } - if ( 0.05 > Utility.RandomDouble() ) - { - if ( !IsParagon ) - { - if ( 0.75 > Utility.RandomDouble() ) - c.DropItem( DawnsMusicGear.RandomCommon ); - else - c.DropItem( DawnsMusicGear.RandomUncommon ); - } - else - c.DropItem( DawnsMusicGear.RandomRare ); - } - } + public override string CorpseName => "a juggernaut corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 1 ); - } + public override string DefaultName => "a blackthorn juggernaut"; - public override int GetDeathSound() - { - return 0x423; - } + public override bool AlwaysMurderer => true; + public override bool BardImmune => !Core.AOS; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int Meat => 1; + public override int TreasureMapLevel => 5; - public override int GetAttackSound() - { - return 0x23B; - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override int GetHurtSound() - { - return 0x140; - } + if (0.05 > Utility.RandomDouble()) + { + if (!IsParagon) + { + if (0.75 > Utility.RandomDouble()) + c.DropItem(DawnsMusicGear.RandomCommon); + else + c.DropItem(DawnsMusicGear.RandomUncommon); + } + else + { + c.DropItem(DawnsMusicGear.RandomRare); + } + } + } - public override bool AlwaysMurderer => true; - public override bool BardImmune => !Core.AOS; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int Meat => 1; - public override int TreasureMapLevel => 5; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 1); + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override int GetDeathSound() + { + return 0x423; + } - if ( !m_Stunning && 0.3 > Utility.RandomDouble() ) - { - m_Stunning = true; + public override int GetAttackSound() + { + return 0x23B; + } - defender.Animate( 21, 6, 1, true, false, 0 ); - PlaySound( 0xEE ); - defender.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You have been stunned by a colossal blow!" ); + public override int GetHurtSound() + { + return 0x140; + } - if ( Weapon is BaseWeapon weapon ) - weapon.OnHit( this, defender ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( defender.Alive ) - { - defender.Frozen = true; - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( Recover_Callback ), defender ); - } - } - } + if (!m_Stunning && 0.3 > Utility.RandomDouble()) + { + m_Stunning = true; - private void Recover_Callback( object state ) - { - if ( state is Mobile defender ) - { - defender.Frozen = false; - defender.Combatant = null; - defender.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You recover your senses." ); - } + defender.Animate(21, 6, 1, true, false, 0); + PlaySound(0xEE); + defender.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You have been stunned by a colossal blow!"); - m_Stunning = false; - } + if (Weapon is BaseWeapon weapon) + weapon.OnHit(this, defender); - public Juggernaut( Serial serial ) : base( serial ) - { - } + if (defender.Alive) + { + defender.Frozen = true; + Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(Recover_Callback), defender); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private void Recover_Callback(object state) + { + if (state is Mobile defender) + { + defender.Frozen = false; + defender.Combatant = null; + defender.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You recover your senses."); + } - writer.Write( (int) 0 ); // version - } + m_Stunning = false; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunRevenant.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunRevenant.cs index b5612e8cb..b4a1bd55d 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunRevenant.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunRevenant.cs @@ -4,177 +4,173 @@ using Server.Items; namespace Server.Mobiles { - public class KhaldunRevenant : BaseCreature - { - private static Hashtable m_Table = new Hashtable(); + public class KhaldunRevenant : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); + private DateTime m_ExpireTime; - public static void Initialize() - { - EventSink.PlayerDeath += EventSink_PlayerDeath; - } + private Mobile m_Target; - public static void EventSink_PlayerDeath( PlayerDeathEventArgs e ) - { - Mobile m = e.Mobile; - Mobile lastKiller = m.LastKiller; + public KhaldunRevenant(Mobile target) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.18, 0.36) + { + Body = 0x3CA; + Hue = 0x41CE; - if ( lastKiller is BaseCreature ) - lastKiller = ((BaseCreature)lastKiller).GetMaster(); + m_Target = target; + m_ExpireTime = DateTime.UtcNow + TimeSpan.FromMinutes(10.0); - if ( IsInsideKhaldun( m ) && IsInsideKhaldun( lastKiller ) && lastKiller.Player && !m_Table.Contains( lastKiller ) ) - { - foreach ( AggressorInfo ai in m.Aggressors ) - { - if ( ai.Attacker == lastKiller && ai.CanReportMurder ) - { - SummonRevenant( m, lastKiller ); - break; - } - } - } - } + SetStr(401, 500); + SetDex(296, 315); + SetInt(101, 200); - public static void SummonRevenant( Mobile victim, Mobile killer ) - { - KhaldunRevenant revenant = new KhaldunRevenant( killer ); + SetHits(241, 300); + SetStam(242, 280); - revenant.MoveToWorld( victim.Location, victim.Map ); - revenant.Combatant = killer; - revenant.FixedParticles( 0, 0, 0, 0x13A7, EffectLayer.Waist ); - Effects.PlaySound( revenant.Location, revenant.Map, 0x29 ); + SetDamage(20, 30); - m_Table.Add( killer, null ); - } + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - public static bool IsInsideKhaldun( Mobile from ) - { - return from?.Region != null && from.Region.IsPartOf( "Khaldun" ); - } + SetSkill(SkillName.MagicResist, 100.1, 150.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Swords, 140.1, 150.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - private Mobile m_Target; - private DateTime m_ExpireTime; + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - public override bool DeleteCorpseOnDeath => true; + Fame = 0; + Karma = 0; - public override void DisplayPaperdollTo( Mobile to ) - { - } + VirtualArmor = 60; - public override Mobile ConstantFocus => m_Target; - public override bool AlwaysAttackable => true; + Halberd weapon = new Halberd(); + weapon.Hue = 0x41CE; + weapon.Movable = false; - public override string DefaultName => "a revenant"; + AddItem(weapon); + } - public KhaldunRevenant( Mobile target ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.18, 0.36 ) - { - Body = 0x3CA; - Hue = 0x41CE; + public KhaldunRevenant(Serial serial) : base(serial) + { + } - m_Target = target; - m_ExpireTime = DateTime.UtcNow + TimeSpan.FromMinutes( 10.0 ); + public override bool DeleteCorpseOnDeath => true; - SetStr( 401, 500 ); - SetDex( 296, 315 ); - SetInt( 101, 200 ); + public override Mobile ConstantFocus => m_Target; + public override bool AlwaysAttackable => true; - SetHits( 241, 300 ); - SetStam( 242, 280 ); + public override string DefaultName => "a revenant"; - SetDamage( 20, 30 ); + public override bool BardImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + public static void Initialize() + { + EventSink.PlayerDeath += EventSink_PlayerDeath; + } - SetSkill( SkillName.MagicResist, 100.1, 150.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Swords, 140.1, 150.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + public static void EventSink_PlayerDeath(PlayerDeathEventArgs e) + { + Mobile m = e.Mobile; + Mobile lastKiller = m.LastKiller; - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + if (lastKiller is BaseCreature) + lastKiller = ((BaseCreature)lastKiller).GetMaster(); - Fame = 0; - Karma = 0; + if (IsInsideKhaldun(m) && IsInsideKhaldun(lastKiller) && lastKiller.Player && !m_Table.Contains(lastKiller)) + foreach (AggressorInfo ai in m.Aggressors) + if (ai.Attacker == lastKiller && ai.CanReportMurder) + { + SummonRevenant(m, lastKiller); + break; + } + } - VirtualArmor = 60; + public static void SummonRevenant(Mobile victim, Mobile killer) + { + KhaldunRevenant revenant = new KhaldunRevenant(killer); - Halberd weapon = new Halberd(); - weapon.Hue = 0x41CE; - weapon.Movable = false; + revenant.MoveToWorld(victim.Location, victim.Map); + revenant.Combatant = killer; + revenant.FixedParticles(0, 0, 0, 0x13A7, EffectLayer.Waist); + Effects.PlaySound(revenant.Location, revenant.Map, 0x29); - AddItem( weapon ); - } + m_Table.Add(killer, null); + } - public override int GetIdleSound() - { - return 0x1BF; - } + public static bool IsInsideKhaldun(Mobile from) + { + return from?.Region != null && from.Region.IsPartOf("Khaldun"); + } - public override int GetAngerSound() - { - return 0x107; - } + public override void DisplayPaperdollTo(Mobile to) + { + } - public override int GetDeathSound() - { - return 0xFD; - } + public override int GetIdleSound() + { + return 0x1BF; + } - public override bool BardImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override int GetAngerSound() + { + return 0x107; + } - public override void OnThink() - { - if ( !m_Target.Alive || DateTime.UtcNow > m_ExpireTime ) - { - Delete(); - return; - } + public override int GetDeathSound() + { + return 0xFD; + } - //Combatant = m_Target; - //FocusMob = m_Target; + public override void OnThink() + { + if (!m_Target.Alive || DateTime.UtcNow > m_ExpireTime) + { + Delete(); + return; + } - if ( AIObject != null ) - AIObject.Action = ActionType.Combat; + //Combatant = m_Target; + //FocusMob = m_Target; - base.OnThink(); - } + if (AIObject != null) + AIObject.Action = ActionType.Combat; - public override bool OnBeforeDeath() - { - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + base.OnThink(); + } - public override void OnDelete() - { - if ( m_Target != null ) - m_Table.Remove( m_Target ); + public override bool OnBeforeDeath() + { + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - base.OnDelete(); - } + public override void OnDelete() + { + if (m_Target != null) + m_Table.Remove(m_Target); - public KhaldunRevenant( Serial serial ) : base( serial ) - { - } + base.OnDelete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - Delete(); - } - } -} + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunSummoner.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunSummoner.cs index c58d56fa8..5e32fbd40 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunSummoner.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunSummoner.cs @@ -2,139 +2,139 @@ using Server.Items; namespace Server.Mobiles { - public class KhaldunSummoner : BaseCreature - { - public override bool ClickTitle => false; - public override bool ShowFameTitle => false; + public class KhaldunSummoner : BaseCreature + { + [Constructible] + public KhaldunSummoner() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x190; + Title = "the Summoner"; - public override string DefaultName => "Zealot of Khaldun"; + SetStr(351, 400); + SetDex(101, 150); + SetInt(502, 700); - [Constructible] - public KhaldunSummoner():base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x190; - Title = "the Summoner"; + SetHits(421, 480); - SetStr( 351, 400 ); - SetDex( 101, 150 ); - SetInt( 502, 700 ); + SetDamage(5, 15); - SetHits( 421, 480 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Cold, 25); - SetDamage( 5, 15 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Cold, 25 ); + SetSkill(SkillName.Wrestling, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Meditation, 120.1, 130.0); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + VirtualArmor = 36; + Fame = 10000; + Karma = -10000; - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Meditation, 120.1, 130.0 ); + LeatherGloves gloves = new LeatherGloves(); + gloves.Hue = 0x66D; + AddItem(gloves); - VirtualArmor = 36; - Fame = 10000; - Karma = -10000; + BoneHelm helm = new BoneHelm(); + helm.Hue = 0x835; + AddItem(helm); - LeatherGloves gloves = new LeatherGloves(); - gloves.Hue = 0x66D; - AddItem( gloves ); + Necklace necklace = new Necklace(); + necklace.Hue = 0x66D; + AddItem(necklace); - BoneHelm helm = new BoneHelm(); - helm.Hue = 0x835; - AddItem( helm ); + Cloak cloak = new Cloak(); + cloak.Hue = 0x66D; + AddItem(cloak); - Necklace necklace = new Necklace(); - necklace.Hue = 0x66D; - AddItem( necklace ); + Kilt kilt = new Kilt(); + kilt.Hue = 0x66D; + AddItem(kilt); - Cloak cloak = new Cloak(); - cloak.Hue = 0x66D; - AddItem( cloak ); + Sandals sandals = new Sandals(); + sandals.Hue = 0x66D; + AddItem(sandals); + } - Kilt kilt = new Kilt(); - kilt.Hue = 0x66D; - AddItem( kilt ); + public KhaldunSummoner(Serial serial) : base(serial) + { + } - Sandals sandals = new Sandals(); - sandals.Hue = 0x66D; - AddItem( sandals ); - } + public override bool ClickTitle => false; + public override bool ShowFameTitle => false; - public override int GetIdleSound() - { - return 0x184; - } + public override string DefaultName => "Zealot of Khaldun"; - public override int GetAngerSound() - { - return 0x286; - } + public override bool AlwaysMurderer => true; + public override bool Unprovokable => true; - public override int GetDeathSound() - { - return 0x288; - } + public override int GetIdleSound() + { + return 0x184; + } - public override int GetHurtSound() - { - return 0x19F; - } + public override int GetAngerSound() + { + return 0x286; + } - public override bool AlwaysMurderer => true; - public override bool Unprovokable => true; + public override int GetDeathSound() + { + return 0x288; + } - public KhaldunSummoner( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x19F; + } - public override bool OnBeforeDeath() - { - BoneMagi rm = new BoneMagi(); - rm.Team = Team; - rm.Combatant = Combatant; - rm.NoKillAwards = true; + public override bool OnBeforeDeath() + { + BoneMagi rm = new BoneMagi(); + rm.Team = Team; + rm.Combatant = Combatant; + rm.NoKillAwards = true; - if ( rm.Backpack == null ) - { - Backpack pack = new Backpack(); - pack.Movable = false; - rm.AddItem( pack ); - } + if (rm.Backpack == null) + { + Backpack pack = new Backpack(); + pack.Movable = false; + rm.AddItem(pack); + } - for ( int i = 0; i < 2; i++ ) - { - LootPack.FilthyRich.Generate( this, rm.Backpack, true, LootPack.GetLuckChanceForKiller( this ) ); - LootPack.FilthyRich.Generate( this, rm.Backpack, false, LootPack.GetLuckChanceForKiller( this ) ); - } + for (int i = 0; i < 2; i++) + { + LootPack.FilthyRich.Generate(this, rm.Backpack, true, LootPack.GetLuckChanceForKiller(this)); + LootPack.FilthyRich.Generate(this, rm.Backpack, false, LootPack.GetLuckChanceForKiller(this)); + } - Effects.PlaySound(this, Map, GetDeathSound()); - Effects.SendLocationEffect( Location, Map, 0x3709, 30, 10, 0x835, 0 ); - rm.MoveToWorld( Location, Map ); + Effects.PlaySound(this, Map, GetDeathSound()); + Effects.SendLocationEffect(Location, Map, 0x3709, 30, 10, 0x835, 0); + rm.MoveToWorld(Location, Map); - Delete(); - return false; - } + Delete(); + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunZealot.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunZealot.cs index d73ce86c3..f0fc293c4 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunZealot.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/KhaldunZealot.cs @@ -2,148 +2,148 @@ using Server.Items; namespace Server.Mobiles { - public class KhaldunZealot : BaseCreature - { - public override bool ClickTitle => false; - public override bool ShowFameTitle => false; + public class KhaldunZealot : BaseCreature + { + [Constructible] + public KhaldunZealot() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x190; + Title = "the Knight"; + Hue = 0; - public override string DefaultName => "Zealot of Khaldun"; + SetStr(351, 400); + SetDex(151, 165); + SetInt(76, 100); - [Constructible] - public KhaldunZealot(): base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x190; - Title = "the Knight"; - Hue = 0; + SetHits(448, 470); - SetStr( 351, 400 ); - SetDex( 151, 165 ); - SetInt( 76, 100 ); + SetDamage(15, 25); - SetHits( 448, 470 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Cold, 25); - SetDamage( 15, 25 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Cold, 25 ); + SetSkill(SkillName.Wrestling, 70.1, 80.0); + SetSkill(SkillName.Swords, 120.1, 130.0); + SetSkill(SkillName.Anatomy, 120.1, 130.0); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + Fame = 10000; + Karma = -10000; + VirtualArmor = 40; - SetSkill( SkillName.Wrestling, 70.1, 80.0 ); - SetSkill( SkillName.Swords, 120.1, 130.0 ); - SetSkill( SkillName.Anatomy, 120.1, 130.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); + VikingSword weapon = new VikingSword(); + weapon.Hue = 0x835; + weapon.Movable = false; + AddItem(weapon); - Fame = 10000; - Karma = -10000; - VirtualArmor = 40; + MetalShield shield = new MetalShield(); + shield.Hue = 0x835; + shield.Movable = false; + AddItem(shield); - VikingSword weapon = new VikingSword(); - weapon.Hue = 0x835; - weapon.Movable = false; - AddItem( weapon ); + BoneHelm helm = new BoneHelm(); + helm.Hue = 0x835; + AddItem(helm); - MetalShield shield = new MetalShield(); - shield.Hue = 0x835; - shield.Movable = false; - AddItem( shield ); + BoneArms arms = new BoneArms(); + arms.Hue = 0x835; + AddItem(arms); - BoneHelm helm = new BoneHelm(); - helm.Hue = 0x835; - AddItem( helm ); + BoneGloves gloves = new BoneGloves(); + gloves.Hue = 0x835; + AddItem(gloves); - BoneArms arms = new BoneArms(); - arms.Hue = 0x835; - AddItem( arms ); + BoneChest tunic = new BoneChest(); + tunic.Hue = 0x835; + AddItem(tunic); - BoneGloves gloves = new BoneGloves(); - gloves.Hue = 0x835; - AddItem( gloves ); + BoneLegs legs = new BoneLegs(); + legs.Hue = 0x835; + AddItem(legs); - BoneChest tunic = new BoneChest(); - tunic.Hue = 0x835; - AddItem( tunic ); + AddItem(new Boots()); + } - BoneLegs legs = new BoneLegs(); - legs.Hue = 0x835; - AddItem( legs ); + public KhaldunZealot(Serial serial) : base(serial) + { + } - AddItem( new Boots() ); - } + public override bool ClickTitle => false; + public override bool ShowFameTitle => false; - public override int GetIdleSound() - { - return 0x184; - } + public override string DefaultName => "Zealot of Khaldun"; - public override int GetAngerSound() - { - return 0x286; - } + public override bool AlwaysMurderer => true; + public override bool Unprovokable => true; + public override Poison PoisonImmune => Poison.Deadly; - public override int GetDeathSound() - { - return 0x288; - } + public override int GetIdleSound() + { + return 0x184; + } - public override int GetHurtSound() - { - return 0x19F; - } + public override int GetAngerSound() + { + return 0x286; + } - public override bool AlwaysMurderer => true; - public override bool Unprovokable => true; - public override Poison PoisonImmune => Poison.Deadly; + public override int GetDeathSound() + { + return 0x288; + } - public KhaldunZealot( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x19F; + } - public override bool OnBeforeDeath() - { - BoneKnight rm = new BoneKnight(); - rm.Team = Team; - rm.Combatant = Combatant; - rm.NoKillAwards = true; + public override bool OnBeforeDeath() + { + BoneKnight rm = new BoneKnight(); + rm.Team = Team; + rm.Combatant = Combatant; + rm.NoKillAwards = true; - if ( rm.Backpack == null ) - { - Backpack pack = new Backpack(); - pack.Movable = false; - rm.AddItem( pack ); - } + if (rm.Backpack == null) + { + Backpack pack = new Backpack(); + pack.Movable = false; + rm.AddItem(pack); + } - for ( int i = 0; i < 2; i++ ) - { - LootPack.FilthyRich.Generate( this, rm.Backpack, true, LootPack.GetLuckChanceForKiller( this ) ); - LootPack.FilthyRich.Generate( this, rm.Backpack, false, LootPack.GetLuckChanceForKiller( this ) ); - } + for (int i = 0; i < 2; i++) + { + LootPack.FilthyRich.Generate(this, rm.Backpack, true, LootPack.GetLuckChanceForKiller(this)); + LootPack.FilthyRich.Generate(this, rm.Backpack, false, LootPack.GetLuckChanceForKiller(this)); + } - Effects.PlaySound(this, Map, GetDeathSound()); - Effects.SendLocationEffect( Location, Map, 0x3709, 30, 10, 0x835, 0 ); - rm.MoveToWorld( Location, Map ); + Effects.PlaySound(this, Map, GetDeathSound()); + Effects.SendLocationEffect(Location, Map, 0x3709, 30, 10, 0x835, 0); + rm.MoveToWorld(Location, Map); - Delete(); - return false; - } + Delete(); + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Moloch.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Moloch.cs index eec2b47c3..c8887d418 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Moloch.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Moloch.cs @@ -2,64 +2,68 @@ using Server.Items; namespace Server.Mobiles { - public class Moloch : BaseCreature - { - public override string CorpseName => "a moloch corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ConcussionBlow; + public class Moloch : BaseCreature + { + [Constructible] + public Moloch() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x311; + BaseSoundID = 0x300; - public override string DefaultName => "a moloch"; + SetStr(331, 360); + SetDex(66, 85); + SetInt(41, 65); - [Constructible] - public Moloch() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x311; - BaseSoundID = 0x300; + SetHits(171, 200); - SetStr( 331, 360 ); - SetDex( 66, 85 ); - SetInt( 41, 65 ); + SetDamage(15, 23); - SetHits( 171, 200 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamage( 15, 23 ); + SetSkill(SkillName.MagicResist, 65.1, 75.0); + SetSkill(SkillName.Tactics, 75.1, 90.0); + SetSkill(SkillName.Wrestling, 70.1, 90.0); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 7500; + Karma = -7500; - SetSkill( SkillName.MagicResist, 65.1, 75.0 ); - SetSkill( SkillName.Tactics, 75.1, 90.0 ); - SetSkill( SkillName.Wrestling, 70.1, 90.0 ); + VirtualArmor = 32; + } - Fame = 7500; - Karma = -7500; + public Moloch(Serial serial) : base(serial) + { + } - VirtualArmor = 32; - } + public override string CorpseName => "a moloch corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override string DefaultName => "a moloch"; - public override Poison PoisonImmune => Poison.Regular; + public override Poison PoisonImmune => Poison.Regular; - public Moloch( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ConcussionBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Mongbat.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Mongbat.cs index defbc3e09..445ee9258 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Mongbat.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Mongbat.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class Mongbat : BaseCreature - { - public override string CorpseName => "a mongbat corpse"; - public override string DefaultName => "a mongbat"; + public class Mongbat : BaseCreature + { + [Constructible] + public Mongbat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 39; + BaseSoundID = 422; - [Constructible] - public Mongbat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 39; - BaseSoundID = 422; + SetStr(6, 10); + SetDex(26, 38); + SetInt(6, 14); - SetStr( 6, 10 ); - SetDex( 26, 38 ); - SetInt( 6, 14 ); + SetHits(4, 6); + SetMana(0); - SetHits( 4, 6 ); - SetMana( 0 ); + SetDamage(1, 2); - SetDamage( 1, 2 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); - SetResistance( ResistanceType.Physical, 5, 10 ); + SetSkill(SkillName.MagicResist, 5.1, 14.0); + SetSkill(SkillName.Tactics, 5.1, 10.0); + SetSkill(SkillName.Wrestling, 5.1, 10.0); - SetSkill( SkillName.MagicResist, 5.1, 14.0 ); - SetSkill( SkillName.Tactics, 5.1, 10.0 ); - SetSkill( SkillName.Wrestling, 5.1, 10.0 ); + Fame = 150; + Karma = -150; - Fame = 150; - Karma = -150; + VirtualArmor = 10; - VirtualArmor = 10; + Tamable = true; + ControlSlots = 1; + MinTameSkill = -18.9; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -18.9; - } + public Mongbat(Serial serial) : base(serial) + { + } - public override bool CanFly => true; + public override string CorpseName => "a mongbat corpse"; + public override string DefaultName => "a mongbat"; - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override bool CanFly => true; - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat; + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat; - public Mongbat( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Mummy.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Mummy.cs index eeb644745..da2fc0abe 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Mummy.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Mummy.cs @@ -1,77 +1,78 @@ +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class Mummy : BaseCreature - { - public override string CorpseName => "a mummy corpse"; - public override string DefaultName => "a mummy"; + public class Mummy : BaseCreature + { + [Constructible] + public Mummy() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8) + { + Body = 154; + BaseSoundID = 471; - [Constructible] - public Mummy() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8 ) - { - Body = 154; - BaseSoundID = 471; + SetStr(346, 370); + SetDex(71, 90); + SetInt(26, 40); - SetStr( 346, 370 ); - SetDex( 71, 90 ); - SetInt( 26, 40 ); + SetHits(208, 222); - SetHits( 208, 222 ); + SetDamage(13, 23); - SetDamage( 13, 23 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 15.1, 40.0); + SetSkill(SkillName.Tactics, 35.1, 50.0); + SetSkill(SkillName.Wrestling, 35.1, 50.0); - SetSkill( SkillName.MagicResist, 15.1, 40.0 ); - SetSkill( SkillName.Tactics, 35.1, 50.0 ); - SetSkill( SkillName.Wrestling, 35.1, 50.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 50; - VirtualArmor = 50; + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(2)); - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(2) ); + PackItem(new Garlic(5)); + PackItem(new Bandage(10)); + } - PackItem( new Garlic( 5 ) ); - PackItem( new Bandage( 10 ) ); - } + public Mummy(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "a mummy corpse"; + public override string DefaultName => "a mummy"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lesser; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lesser; - public Mummy( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ogre.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ogre.cs index 39d424e30..44ba7b9d1 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ogre.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ogre.cs @@ -2,70 +2,70 @@ using Server.Items; namespace Server.Mobiles { - public class Ogre : BaseCreature - { - public override string CorpseName => "an ogre corpse"; - public override string DefaultName => "an ogre"; + public class Ogre : BaseCreature + { + [Constructible] + public Ogre() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 1; + BaseSoundID = 427; - [Constructible] - public Ogre () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 1; - BaseSoundID = 427; + SetStr(166, 195); + SetDex(46, 65); + SetInt(46, 70); - SetStr( 166, 195 ); - SetDex( 46, 65 ); - SetInt( 46, 70 ); + SetHits(100, 117); + SetMana(0); - SetHits( 100, 117 ); - SetMana( 0 ); + SetDamage(9, 11); - SetDamage( 9, 11 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 25); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 25 ); + SetSkill(SkillName.MagicResist, 55.1, 70.0); + SetSkill(SkillName.Tactics, 60.1, 70.0); + SetSkill(SkillName.Wrestling, 70.1, 80.0); - SetSkill( SkillName.MagicResist, 55.1, 70.0 ); - SetSkill( SkillName.Tactics, 60.1, 70.0 ); - SetSkill( SkillName.Wrestling, 70.1, 80.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 32; - VirtualArmor = 32; + PackItem(new Club()); + } - PackItem( new Club() ); - } + public Ogre(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "an ogre corpse"; + public override string DefaultName => "an ogre"; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 1; - public override int Meat => 2; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 1; + public override int Meat => 2; - public Ogre( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/OgreLord.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/OgreLord.cs index 27cfbe206..8e8484bcb 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/OgreLord.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/OgreLord.cs @@ -1,74 +1,75 @@ -using Server.Items; +using Server.Ethics; using Server.Factions; +using Server.Items; namespace Server.Mobiles { - public class OgreLord : BaseCreature - { - public override string CorpseName => "an ogre lords corpse"; - public override Faction FactionAllegiance => Minax.Instance; - public override Ethics.Ethic EthicAllegiance => Ethics.Ethic.Evil; + public class OgreLord : BaseCreature + { + [Constructible] + public OgreLord() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 83; + BaseSoundID = 427; - public override string DefaultName => "an ogre lord"; + SetStr(767, 945); + SetDex(66, 75); + SetInt(46, 70); - [Constructible] - public OgreLord () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 83; - BaseSoundID = 427; + SetHits(476, 552); - SetStr( 767, 945 ); - SetDex( 66, 75 ); - SetInt( 46, 70 ); + SetDamage(20, 25); - SetHits( 476, 552 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 20, 25 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 125.1, 140.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + Fame = 15000; + Karma = -15000; - SetSkill( SkillName.MagicResist, 125.1, 140.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + VirtualArmor = 50; - Fame = 15000; - Karma = -15000; + PackItem(new Club()); + } - VirtualArmor = 50; + public OgreLord(Serial serial) : base(serial) + { + } - PackItem( new Club() ); - } + public override string CorpseName => "an ogre lords corpse"; + public override Faction FactionAllegiance => Minax.Instance; + public override Ethic EthicAllegiance => Ethic.Evil; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 2 ); - } + public override string DefaultName => "an ogre lord"; - public override bool CanRummageCorpses => true; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 3; - public override int Meat => 2; + public override bool CanRummageCorpses => true; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 3; + public override int Meat => 2; - public OgreLord( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Orc.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Orc.cs index 273b563ff..47210a602 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Orc.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Orc.cs @@ -3,114 +3,132 @@ using Server.Misc; namespace Server.Mobiles { - public class Orc : BaseCreature - { - public override string CorpseName => "an orcish corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Orc; + public class Orc : BaseCreature + { + [Constructible] + public Orc() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("orc"); + Body = 17; + BaseSoundID = 0x45A; - [Constructible] - public Orc() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "orc" ); - Body = 17; - BaseSoundID = 0x45A; + SetStr(96, 120); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(58, 72); - SetHits( 58, 72 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 50.1, 75.0); + SetSkill(SkillName.Tactics, 55.1, 80.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetSkill( SkillName.MagicResist, 50.1, 75.0 ); - SetSkill( SkillName.Tactics, 55.1, 80.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 28; - VirtualArmor = 28; + switch (Utility.Random(20)) + { + case 0: + PackItem(new Scimitar()); + break; + case 1: + PackItem(new Katana()); + break; + case 2: + PackItem(new WarMace()); + break; + case 3: + PackItem(new WarHammer()); + break; + case 4: + PackItem(new Kryss()); + break; + case 5: + PackItem(new Pitchfork()); + break; + } - switch ( Utility.Random( 20 ) ) - { - case 0: PackItem( new Scimitar() ); break; - case 1: PackItem( new Katana() ); break; - case 2: PackItem( new WarMace() ); break; - case 3: PackItem( new WarHammer() ); break; - case 4: PackItem( new Kryss() ); break; - case 5: PackItem( new Pitchfork() ); break; - } + PackItem(new ThighBoots()); - PackItem( new ThighBoots() ); + switch (Utility.Random(3)) + { + case 0: + PackItem(new Ribs()); + break; + case 1: + PackItem(new Shaft()); + break; + case 2: + PackItem(new Candle()); + break; + } - switch ( Utility.Random( 3 ) ) - { - case 0: PackItem( new Ribs() ); break; - case 1: PackItem( new Shaft() ); break; - case 2: PackItem( new Candle() ); break; - } + if (0.2 > Utility.RandomDouble()) + PackItem(new BolaBall()); + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new BolaBall() ); - } + public Orc(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "an orcish corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Orc; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 1; - public override int Meat => 1; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 1; + public override int Meat => 1; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - public override bool IsEnemy( Mobile m ) - { - if ( m.Player && m.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - return false; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - return base.IsEnemy( m ); - } + public override bool IsEnemy(Mobile m) + { + if (m.Player && m.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + return false; - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + return base.IsEnemy(m); + } - Item item = aggressor.FindItemOnLayer( Layer.Helm ); + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - if ( item is OrcishKinMask ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - item.Delete(); - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - } - } + Item item = aggressor.FindItemOnLayer(Layer.Helm); - public Orc( Serial serial ) : base( serial ) - { - } + if (item is OrcishKinMask) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + item.Delete(); + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBomber.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBomber.cs index d6459f609..b769d8c30 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBomber.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBomber.cs @@ -4,153 +4,154 @@ using Server.Misc; namespace Server.Mobiles { - public class OrcBomber : BaseCreature - { - public override string CorpseName => "an orcish corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Orc; + public class OrcBomber : BaseCreature + { + private DateTime m_NextBomb; + private int m_Thrown; - public override string DefaultName => "an orc bomber"; + [Constructible] + public OrcBomber() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 182; + BaseSoundID = 0x45A; - [Constructible] - public OrcBomber() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 182; - BaseSoundID = 0x45A; + SetStr(147, 215); + SetDex(91, 115); + SetInt(61, 85); - SetStr( 147, 215 ); - SetDex( 91, 115 ); - SetInt( 61, 85 ); + SetHits(95, 123); - SetHits( 95, 123 ); + SetDamage(1, 8); - SetDamage( 1, 8 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Fire, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Fire, 25 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 15, 20); + SetResistance(ResistanceType.Energy, 25, 30); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 15, 20 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + SetSkill(SkillName.MagicResist, 70.1, 85.0); + SetSkill(SkillName.Swords, 60.1, 85.0); + SetSkill(SkillName.Tactics, 75.1, 90.0); + SetSkill(SkillName.Wrestling, 60.1, 85.0); - SetSkill( SkillName.MagicResist, 70.1, 85.0 ); - SetSkill( SkillName.Swords, 60.1, 85.0 ); - SetSkill( SkillName.Tactics, 75.1, 90.0 ); - SetSkill( SkillName.Wrestling, 60.1, 85.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 30; - VirtualArmor = 30; + PackItem(new SulfurousAsh(Utility.RandomMinMax(6, 10))); + PackItem(new MandrakeRoot(Utility.RandomMinMax(6, 10))); + PackItem(new BlackPearl(Utility.RandomMinMax(6, 10))); + PackItem(new MortarPestle()); + PackItem(new LesserExplosionPotion()); - PackItem( new SulfurousAsh( Utility.RandomMinMax( 6, 10 ) ) ); - PackItem( new MandrakeRoot( Utility.RandomMinMax( 6, 10 ) ) ); - PackItem( new BlackPearl( Utility.RandomMinMax( 6, 10 ) ) ); - PackItem( new MortarPestle() ); - PackItem( new LesserExplosionPotion() ); + if (0.2 > Utility.RandomDouble()) + PackItem(new BolaBall()); + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new BolaBall() ); - } + public OrcBomber(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "an orcish corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Orc; - public override bool CanRummageCorpses => true; + public override string DefaultName => "an orc bomber"; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override bool CanRummageCorpses => true; - public override bool IsEnemy( Mobile m ) - { - if ( m.Player && m.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - return false; + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + } - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override bool IsEnemy(Mobile m) + { + if (m.Player && m.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + return false; - Item item = aggressor.FindItemOnLayer( Layer.Helm ); + return base.IsEnemy(m); + } - if ( item is OrcishKinMask ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - item.Delete(); - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - } - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - private DateTime m_NextBomb; - private int m_Thrown; + Item item = aggressor.FindItemOnLayer(Layer.Helm); - public override void OnActionCombat() - { - Mobile combatant = Combatant; + if (item is OrcishKinMask) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + item.Delete(); + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + } + } - if ( combatant == null || combatant.Deleted || combatant.Map != Map || !InRange( combatant, 12 ) || !CanBeHarmful( combatant ) || !InLOS( combatant ) ) - return; + public override void OnActionCombat() + { + Mobile combatant = Combatant; - if ( DateTime.UtcNow >= m_NextBomb ) - { - ThrowBomb( combatant ); + if (combatant == null || combatant.Deleted || combatant.Map != Map || !InRange(combatant, 12) || + !CanBeHarmful(combatant) || !InLOS(combatant)) + return; - m_Thrown++; + if (DateTime.UtcNow >= m_NextBomb) + { + ThrowBomb(combatant); - if ( 0.75 >= Utility.RandomDouble() && (m_Thrown % 2) == 1 ) // 75% chance to quickly throw another bomb - m_NextBomb = DateTime.UtcNow + TimeSpan.FromSeconds( 3.0 ); - else - m_NextBomb = DateTime.UtcNow + TimeSpan.FromSeconds( 5.0 + (10.0 * Utility.RandomDouble()) ); // 5-15 seconds - } - } + m_Thrown++; - public void ThrowBomb( Mobile m ) - { - DoHarmful( m ); + if (0.75 >= Utility.RandomDouble() && m_Thrown % 2 == 1) // 75% chance to quickly throw another bomb + m_NextBomb = DateTime.UtcNow + TimeSpan.FromSeconds(3.0); + else + m_NextBomb = DateTime.UtcNow + TimeSpan.FromSeconds(5.0 + 10.0 * Utility.RandomDouble()); // 5-15 seconds + } + } - MovingParticles( m, 0x1C19, 1, 0, false, true, 0, 0, 9502, 6014, 0x11D, EffectLayer.Waist, 0 ); + public void ThrowBomb(Mobile m) + { + DoHarmful(m); - new InternalTimer( m, this ).Start(); - } + MovingParticles(m, 0x1C19, 1, 0, false, true, 0, 0, 9502, 6014, 0x11D, EffectLayer.Waist, 0); - private class InternalTimer : Timer - { - private Mobile m_Mobile, m_From; + new InternalTimer(m, this).Start(); + } - public InternalTimer( Mobile m, Mobile from ) : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_From = from; - Priority = TimerPriority.TwoFiftyMS; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - protected override void OnTick() - { - m_Mobile.PlaySound( 0x11D ); - AOS.Damage( m_Mobile, m_From, Utility.RandomMinMax( 10, 20 ), 0, 100, 0, 0, 0 ); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - public OrcBomber( Serial serial ) : base( serial ) - { - } + private class InternalTimer : Timer + { + private Mobile m_Mobile, m_From; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public InternalTimer(Mobile m, Mobile from) : base(TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_From = from; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + protected override void OnTick() + { + m_Mobile.PlaySound(0x11D); + AOS.Damage(m_Mobile, m_From, Utility.RandomMinMax(10, 20), 0, 100, 0, 0, 0); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBrute.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBrute.cs index e6fdbf625..7e39bc28d 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBrute.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcBrute.cs @@ -2,157 +2,155 @@ using Server.Items; namespace Server.Mobiles { - public class OrcBrute : BaseCreature - { - public override string CorpseName => "an orcish corpse"; - public override string DefaultName => "an orc brute"; + public class OrcBrute : BaseCreature + { + [Constructible] + public OrcBrute() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 189; + BaseSoundID = 0x45A; - [Constructible] - public OrcBrute() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 189; - BaseSoundID = 0x45A; + SetStr(767, 945); + SetDex(66, 75); + SetInt(46, 70); - SetStr( 767, 945 ); - SetDex( 66, 75 ); - SetInt( 46, 70 ); + SetHits(476, 552); - SetHits( 476, 552 ); + SetDamage(20, 25); - SetDamage( 20, 25 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.Macing, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 125.1, 140.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.Macing, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 125.1, 140.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + VirtualArmor = 50; - VirtualArmor = 50; + Item ore = new ShadowIronOre(25); + ore.ItemID = 0x19B9; + PackItem(ore); + PackItem(new IronIngot(10)); - Item ore = new ShadowIronOre( 25 ); - ore.ItemID = 0x19B9; - PackItem( ore ); - PackItem( new IronIngot( 10 ) ); + if (0.05 > Utility.RandomDouble()) + PackItem(new OrcishKinMask()); - if ( 0.05 > Utility.RandomDouble() ) - PackItem( new OrcishKinMask() ); + if (0.2 > Utility.RandomDouble()) + PackItem(new BolaBall()); + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new BolaBall() ); - } + public OrcBrute(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "an orcish corpse"; + public override string DefaultName => "an orc brute"; - public override bool BardImmune => !Core.AOS; - public override Poison PoisonImmune => Poison.Lethal; - public override int Meat => 2; + public override bool BardImmune => !Core.AOS; + public override Poison PoisonImmune => Poison.Lethal; + public override int Meat => 2; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - public override bool IsEnemy( Mobile m ) - { - if ( m.Player && m.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - return false; + public override bool CanRummageCorpses => true; + public override bool AutoDispel => true; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override bool IsEnemy(Mobile m) + { + if (m.Player && m.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + return false; - Item item = aggressor.FindItemOnLayer( Layer.Helm ); + return base.IsEnemy(m); + } - if ( item is OrcishKinMask ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - item.Delete(); - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - } - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - public override bool CanRummageCorpses => true; - public override bool AutoDispel => true; + Item item = aggressor.FindItemOnLayer(Layer.Helm); - public override void OnDamagedBySpell( Mobile caster ) - { - if ( caster == this ) - return; + if (item is OrcishKinMask) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + item.Delete(); + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + } + } - SpawnOrcLord( caster ); - } + public override void OnDamagedBySpell(Mobile caster) + { + if (caster == this) + return; - public void SpawnOrcLord( Mobile target ) - { - Map map = target.Map; + SpawnOrcLord(caster); + } - if ( map == null ) - return; + public void SpawnOrcLord(Mobile target) + { + Map map = target.Map; - int orcs = 0; + if (map == null) + return; - foreach ( Mobile m in GetMobilesInRange( 10 ) ) - { - if ( m is OrcishLord ) - ++orcs; - } + int orcs = 0; - if ( orcs < 10 ) - { - BaseCreature orc = new SpawnedOrcishLord(); + foreach (Mobile m in GetMobilesInRange(10)) + if (m is OrcishLord) + ++orcs; - orc.Team = Team; + if (orcs < 10) + { + BaseCreature orc = new SpawnedOrcishLord(); - Point3D loc = target.Location; - bool validLocation = false; + orc.Team = Team; - for ( int j = 0; !validLocation && j < 10; ++j ) - { - int x = target.X + Utility.Random( 3 ) - 1; - int y = target.Y + Utility.Random( 3 ) - 1; - int z = map.GetAverageZ( x, y ); + Point3D loc = target.Location; + bool validLocation = false; - if ( validLocation = map.CanFit( x, y, Z, 16, false, false ) ) - loc = new Point3D( x, y, Z ); - else if ( validLocation = map.CanFit( x, y, z, 16, false, false ) ) - loc = new Point3D( x, y, z ); - } + for (int j = 0; !validLocation && j < 10; ++j) + { + int x = target.X + Utility.Random(3) - 1; + int y = target.Y + Utility.Random(3) - 1; + int z = map.GetAverageZ(x, y); - orc.MoveToWorld( loc, map ); + if (validLocation = map.CanFit(x, y, Z, 16, false, false)) + loc = new Point3D(x, y, Z); + else if (validLocation = map.CanFit(x, y, z, 16, false, false)) + loc = new Point3D(x, y, z); + } - orc.Combatant = target; - } - } + orc.MoveToWorld(loc, map); - public OrcBrute( Serial serial ) : base( serial ) - { - } + orc.Combatant = target; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcCaptain.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcCaptain.cs index f5840bb9f..cea12c243 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcCaptain.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcCaptain.cs @@ -1,117 +1,131 @@ -using Server.Misc; using Server.Items; +using Server.Misc; namespace Server.Mobiles { - public class OrcCaptain : BaseCreature - { - public override string CorpseName => "an orcish corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Orc; + public class OrcCaptain : BaseCreature + { + [Constructible] + public OrcCaptain() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("orc"); + Body = 7; + BaseSoundID = 0x45A; - [Constructible] - public OrcCaptain() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "orc" ); - Body = 7; - BaseSoundID = 0x45A; + SetStr(111, 145); + SetDex(101, 135); + SetInt(86, 110); - SetStr( 111, 145 ); - SetDex( 101, 135 ); - SetInt( 86, 110 ); + SetHits(67, 87); - SetHits( 67, 87 ); + SetDamage(5, 15); - SetDamage( 5, 15 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 5, 10); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + SetSkill(SkillName.MagicResist, 70.1, 85.0); + SetSkill(SkillName.Swords, 70.1, 95.0); + SetSkill(SkillName.Tactics, 85.1, 100.0); - SetSkill( SkillName.MagicResist, 70.1, 85.0 ); - SetSkill( SkillName.Swords, 70.1, 95.0 ); - SetSkill( SkillName.Tactics, 85.1, 100.0 ); + Fame = 2500; + Karma = -2500; - Fame = 2500; - Karma = -2500; + VirtualArmor = 34; - VirtualArmor = 34; + // TODO: Skull? + switch (Utility.Random(7)) + { + case 0: + PackItem(new Arrow()); + break; + case 1: + PackItem(new Lockpick()); + break; + case 2: + PackItem(new Shaft()); + break; + case 3: + PackItem(new Ribs()); + break; + case 4: + PackItem(new Bandage()); + break; + case 5: + PackItem(new BeverageBottle(BeverageType.Wine)); + break; + case 6: + PackItem(new Jug(BeverageType.Cider)); + break; + } - // TODO: Skull? - switch ( Utility.Random( 7 ) ) - { - case 0: PackItem( new Arrow() ); break; - case 1: PackItem( new Lockpick() ); break; - case 2: PackItem( new Shaft() ); break; - case 3: PackItem( new Ribs() ); break; - case 4: PackItem( new Bandage() ); break; - case 5: PackItem( new BeverageBottle( BeverageType.Wine ) ); break; - case 6: PackItem( new Jug( BeverageType.Cider ) ); break; - } + if (Core.AOS) + PackItem(Loot.RandomNecromancyReagent()); + } - if ( Core.AOS ) - PackItem( Loot.RandomNecromancyReagent() ); - } + public OrcCaptain(Serial serial) : base(serial) + { + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override string CorpseName => "an orcish corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Orc; - // TODO: Check drop rate - if ( Utility.RandomDouble() < 0.05 ) - c.DropItem( new StoutWhip() ); - } + public override bool CanRummageCorpses => true; + public override int Meat => 1; - public override void GenerateLoot() - { - AddLoot( LootPack.Meager, 2 ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - public override bool CanRummageCorpses => true; - public override int Meat => 1; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + // TODO: Check drop rate + if (Utility.RandomDouble() < 0.05) + c.DropItem(new StoutWhip()); + } - public override bool IsEnemy( Mobile m ) - { - if ( m.Player && m.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - return false; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager, 2); + } - return base.IsEnemy( m ); - } + public override bool IsEnemy(Mobile m) + { + if (m.Player && m.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + return false; - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + return base.IsEnemy(m); + } - Item item = aggressor.FindItemOnLayer( Layer.Helm ); + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - if ( item is OrcishKinMask ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - item.Delete(); - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - } - } + Item item = aggressor.FindItemOnLayer(Layer.Helm); - public OrcCaptain( Serial serial ) : base( serial ) - { - } + if (item is OrcishKinMask) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + item.Delete(); + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcishLord.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcishLord.cs index 94633fcc0..86e4bc82c 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcishLord.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/OrcishLord.cs @@ -1,113 +1,123 @@ -using Server.Misc; using Server.Items; +using Server.Misc; namespace Server.Mobiles { - public class OrcishLord : BaseCreature - { - public override string CorpseName => "an orcish corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Orc; + public class OrcishLord : BaseCreature + { + [Constructible] + public OrcishLord() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 138; + BaseSoundID = 0x45A; - public override string DefaultName => "an orcish lord"; + SetStr(147, 215); + SetDex(91, 115); + SetInt(61, 85); - [Constructible] - public OrcishLord() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 138; - BaseSoundID = 0x45A; + SetHits(95, 123); - SetStr( 147, 215 ); - SetDex( 91, 115 ); - SetInt( 61, 85 ); + SetDamage(4, 14); - SetHits( 95, 123 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 4, 14 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 70.1, 85.0); + SetSkill(SkillName.Swords, 60.1, 85.0); + SetSkill(SkillName.Tactics, 75.1, 90.0); + SetSkill(SkillName.Wrestling, 60.1, 85.0); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 2500; + Karma = -2500; - SetSkill( SkillName.MagicResist, 70.1, 85.0 ); - SetSkill( SkillName.Swords, 60.1, 85.0 ); - SetSkill( SkillName.Tactics, 75.1, 90.0 ); - SetSkill( SkillName.Wrestling, 60.1, 85.0 ); + switch (Utility.Random(5)) + { + case 0: + PackItem(new Lockpick()); + break; + case 1: + PackItem(new MortarPestle()); + break; + case 2: + PackItem(new Bottle()); + break; + case 3: + PackItem(new RawRibs()); + break; + case 4: + PackItem(new Shovel()); + break; + } - Fame = 2500; - Karma = -2500; + PackItem(new RingmailChest()); - switch ( Utility.Random( 5 ) ) - { - case 0: PackItem( new Lockpick() ); break; - case 1: PackItem( new MortarPestle() ); break; - case 2: PackItem( new Bottle() ); break; - case 3: PackItem( new RawRibs() ); break; - case 4: PackItem( new Shovel() ); break; - } + if (0.3 > Utility.RandomDouble()) + PackItem(Loot.RandomPossibleReagent()); - PackItem( new RingmailChest() ); + if (0.2 > Utility.RandomDouble()) + PackItem(new BolaBall()); + } - if ( 0.3 > Utility.RandomDouble() ) - PackItem( Loot.RandomPossibleReagent() ); + public OrcishLord(Serial serial) : base(serial) + { + } - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new BolaBall() ); - } + public override string CorpseName => "an orcish corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Orc; - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Average ); - // TODO: evil orc helm - } + public override string DefaultName => "an orcish lord"; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 1; - public override int Meat => 1; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 1; + public override int Meat => 1; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - public override bool IsEnemy( Mobile m ) - { - if ( m.Player && m.FindItemOnLayer( Layer.Helm ) is OrcishKinMask ) - return false; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.Average); + // TODO: evil orc helm + } - return base.IsEnemy( m ); - } + public override bool IsEnemy(Mobile m) + { + if (m.Player && m.FindItemOnLayer(Layer.Helm) is OrcishKinMask) + return false; - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + return base.IsEnemy(m); + } - Item item = aggressor.FindItemOnLayer( Layer.Helm ); + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - if ( item is OrcishKinMask ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - item.Delete(); - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - } - } + Item item = aggressor.FindItemOnLayer(Layer.Helm); - public OrcishLord( Serial serial ) : base( serial ) - { - } + if (item is OrcishKinMask) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + item.Delete(); + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ratman.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ratman.cs index 4da5a130d..01401c880 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Ratman.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Ratman.cs @@ -2,68 +2,68 @@ using Server.Misc; namespace Server.Mobiles { - public class Ratman : BaseCreature - { - public override string CorpseName => "a ratman's corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Ratman; + public class Ratman : BaseCreature + { + [Constructible] + public Ratman() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("ratman"); + Body = 42; + BaseSoundID = 437; - [Constructible] - public Ratman() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "ratman" ); - Body = 42; - BaseSoundID = 437; + SetStr(96, 120); + SetDex(81, 100); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 81, 100 ); - SetInt( 36, 60 ); + SetHits(58, 72); - SetHits( 58, 72 ); + SetDamage(4, 5); - SetDamage( 4, 5 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 35.1, 60.0); + SetSkill(SkillName.Tactics, 50.1, 75.0); + SetSkill(SkillName.Wrestling, 50.1, 75.0); - SetSkill( SkillName.MagicResist, 35.1, 60.0 ); - SetSkill( SkillName.Tactics, 50.1, 75.0 ); - SetSkill( SkillName.Wrestling, 50.1, 75.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 28; + } - VirtualArmor = 28; - } + public Ratman(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - // TODO: weapon, misc - } + public override string CorpseName => "a ratman's corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Ratman; - public override bool CanRummageCorpses => true; - public override int Hides => 8; - public override HideType HideType => HideType.Spined; + public override bool CanRummageCorpses => true; + public override int Hides => 8; + public override HideType HideType => HideType.Spined; - public Ratman( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + // TODO: weapon, misc + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/RatmanArcher.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/RatmanArcher.cs index d8c18422e..ac747a88c 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/RatmanArcher.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/RatmanArcher.cs @@ -1,80 +1,80 @@ -using Server.Misc; using Server.Items; +using Server.Misc; namespace Server.Mobiles { - public class RatmanArcher : BaseCreature - { - public override string CorpseName => "a ratman archer corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Ratman; + public class RatmanArcher : BaseCreature + { + [Constructible] + public RatmanArcher() : base(AIType.AI_Archer, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("ratman"); + Body = 0x8E; + BaseSoundID = 437; - [Constructible] - public RatmanArcher() : base( AIType.AI_Archer, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "ratman" ); - Body = 0x8E; - BaseSoundID = 437; + SetStr(146, 180); + SetDex(101, 130); + SetInt(116, 140); - SetStr( 146, 180 ); - SetDex( 101, 130 ); - SetInt( 116, 140 ); + SetHits(88, 108); - SetHits( 88, 108 ); + SetDamage(4, 10); - SetDamage( 4, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 55); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 40, 55 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Anatomy, 60.2, 100.0); + SetSkill(SkillName.Archery, 80.1, 90.0); + SetSkill(SkillName.MagicResist, 65.1, 90.0); + SetSkill(SkillName.Tactics, 50.1, 75.0); + SetSkill(SkillName.Wrestling, 50.1, 75.0); - SetSkill( SkillName.Anatomy, 60.2, 100.0 ); - SetSkill( SkillName.Archery, 80.1, 90.0 ); - SetSkill( SkillName.MagicResist, 65.1, 90.0 ); - SetSkill( SkillName.Tactics, 50.1, 75.0 ); - SetSkill( SkillName.Wrestling, 50.1, 75.0 ); + Fame = 6500; + Karma = -6500; - Fame = 6500; - Karma = -6500; + VirtualArmor = 56; - VirtualArmor = 56; + AddItem(new Bow()); + PackItem(new Arrow(Utility.RandomMinMax(50, 70))); + } - AddItem( new Bow() ); - PackItem( new Arrow( Utility.RandomMinMax( 50, 70 ) ) ); - } + public RatmanArcher(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a ratman archer corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Ratman; - public override bool CanRummageCorpses => true; - public override int Hides => 8; - public override HideType HideType => HideType.Spined; + public override bool CanRummageCorpses => true; + public override int Hides => 8; + public override HideType HideType => HideType.Spined; - public RatmanArcher( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( Body == 42 ) - { - Body = 0x8E; - Hue = 0; - } - } - } -} + if (Body == 42) + { + Body = 0x8E; + Hue = 0; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/RestlessSoul.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/RestlessSoul.cs index b65ff03ea..e339f1512 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/RestlessSoul.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/RestlessSoul.cs @@ -1,115 +1,111 @@ using System.Collections.Generic; +using Server.ContextMenus; using Server.Engines.Quests; using Server.Engines.Quests.Haven; -using Server.ContextMenus; namespace Server.Mobiles { - public class RestlessSoul : BaseCreature - { - public override string CorpseName => "a ghostly corpse"; - public override string DefaultName => "a restless soul"; + public class RestlessSoul : BaseCreature + { + [Constructible] + public RestlessSoul() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8) + { + Body = 0x3CA; + Hue = 0x453; - [Constructible] - public RestlessSoul() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8 ) - { - Body = 0x3CA; - Hue = 0x453; + SetStr(26, 40); + SetDex(26, 40); + SetInt(26, 40); - SetStr( 26, 40 ); - SetDex( 26, 40 ); - SetInt( 26, 40 ); + SetHits(16, 24); - SetHits( 16, 24 ); + SetDamage(1, 10); - SetDamage( 1, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 25); + SetResistance(ResistanceType.Fire, 5, 15); + SetResistance(ResistanceType.Cold, 25, 40); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 15, 25 ); - SetResistance( ResistanceType.Fire, 5, 15 ); - SetResistance( ResistanceType.Cold, 25, 40 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 20.1, 30.0); + SetSkill(SkillName.Swords, 20.1, 30.0); + SetSkill(SkillName.Tactics, 20.1, 30.0); + SetSkill(SkillName.Wrestling, 20.1, 30.0); - SetSkill( SkillName.MagicResist, 20.1, 30.0 ); - SetSkill( SkillName.Swords, 20.1, 30.0 ); - SetSkill( SkillName.Tactics, 20.1, 30.0 ); - SetSkill( SkillName.Wrestling, 20.1, 30.0 ); + Fame = 500; + Karma = -500; - Fame = 500; - Karma = -500; + VirtualArmor = 6; + } - VirtualArmor = 6; - } + public RestlessSoul(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a ghostly corpse"; + public override string DefaultName => "a restless soul"; - public override bool AlwaysAttackable => true; - public override bool BleedImmune => true; + public override bool AlwaysAttackable => true; + public override bool BleedImmune => true; - public override void DisplayPaperdollTo(Mobile to) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + public override void DisplayPaperdollTo(Mobile to) + { + } - for ( int i = 0; i < list.Count; ++i ) - { - if ( list[i] is PaperdollEntry ) - list.RemoveAt( i-- ); - } - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public override int GetIdleSound() - { - return 0x107; - } + for (int i = 0; i < list.Count; ++i) + if (list[i] is PaperdollEntry) + list.RemoveAt(i--); + } - public override int GetAngerSound() - { - return 0x1BF; - } + public override int GetIdleSound() + { + return 0x107; + } - public override int GetDeathSound() - { - return 0xFD; - } + public override int GetAngerSound() + { + return 0x1BF; + } - public override bool IsEnemy( Mobile m ) - { - if ( m is PlayerMobile player && Map == Map.Trammel && X >= 5199 && X <= 5271 && Y >= 1812 && Y <= 1865 ) // Schmendrick's cave - { - QuestSystem qs = player.Quest; + public override int GetDeathSound() + { + return 0xFD; + } - if ( qs is UzeraanTurmoilQuest && qs.IsObjectiveInProgress( typeof( FindSchmendrickObjective ) ) ) - { - return false; - } - } + public override bool IsEnemy(Mobile m) + { + if (m is PlayerMobile player && Map == Map.Trammel && X >= 5199 && X <= 5271 && Y >= 1812 && Y <= 1865 + ) // Schmendrick's cave + { + QuestSystem qs = player.Quest; - return base.IsEnemy( m ); - } + if (qs is UzeraanTurmoilQuest && qs.IsObjectiveInProgress(typeof(FindSchmendrickObjective))) return false; + } - public RestlessSoul( Serial serial ) : base( serial ) - { - } + return base.IsEnemy(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/RottingCorpse.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/RottingCorpse.cs index 2c4d43591..25a43ac27 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/RottingCorpse.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/RottingCorpse.cs @@ -1,73 +1,73 @@ namespace Server.Mobiles { - public class RottingCorpse : BaseCreature - { - public override string CorpseName => "a rotting corpse"; - public override string DefaultName => "a rotting corpse"; + public class RottingCorpse : BaseCreature + { + [Constructible] + public RottingCorpse() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 155; + BaseSoundID = 471; - [Constructible] - public RottingCorpse() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 155; - BaseSoundID = 471; + SetStr(301, 350); + SetDex(75); + SetInt(151, 200); - SetStr( 301, 350 ); - SetDex( 75 ); - SetInt( 151, 200 ); + SetHits(1200); + SetStam(150); + SetMana(0); - SetHits( 1200 ); - SetStam( 150 ); - SetMana( 0 ); + SetDamage(8, 10); - SetDamage( 8, 10 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 70); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 70 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.Poisoning, 120.0); + SetSkill(SkillName.MagicResist, 250.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.Poisoning, 120.0 ); - SetSkill( SkillName.MagicResist, 250.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 6000; + Karma = -6000; - Fame = 6000; - Karma = -6000; + VirtualArmor = 40; + } - VirtualArmor = 40; - } + public RottingCorpse(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - } + public override string CorpseName => "a rotting corpse"; + public override string DefaultName => "a rotting corpse"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; - public override int TreasureMapLevel => 5; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; + public override int TreasureMapLevel => 5; - public RottingCorpse( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Savage.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Savage.cs index d047f46a7..97893cc16 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Savage.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Savage.cs @@ -3,111 +3,113 @@ using Server.Items; namespace Server.Mobiles { - public class Savage : BaseCreature - { - public override string CorpseName => "a savage corpse"; - [Constructible] - public Savage() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "savage" ); + public class Savage : BaseCreature + { + [Constructible] + public Savage() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("savage"); - if ( Female = Utility.RandomBool() ) - Body = 184; - else - Body = 183; + if (Female = Utility.RandomBool()) + Body = 184; + else + Body = 183; - SetStr( 96, 115 ); - SetDex( 86, 105 ); - SetInt( 51, 65 ); + SetStr(96, 115); + SetDex(86, 105); + SetInt(51, 65); - SetDamage( 23, 27 ); + SetDamage(23, 27); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.Fencing, 60.0, 82.5 ); - SetSkill( SkillName.Macing, 60.0, 82.5 ); - SetSkill( SkillName.Poisoning, 60.0, 82.5 ); - SetSkill( SkillName.MagicResist, 57.5, 80.0 ); - SetSkill( SkillName.Swords, 60.0, 82.5 ); - SetSkill( SkillName.Tactics, 60.0, 82.5 ); + SetSkill(SkillName.Fencing, 60.0, 82.5); + SetSkill(SkillName.Macing, 60.0, 82.5); + SetSkill(SkillName.Poisoning, 60.0, 82.5); + SetSkill(SkillName.MagicResist, 57.5, 80.0); + SetSkill(SkillName.Swords, 60.0, 82.5); + SetSkill(SkillName.Tactics, 60.0, 82.5); - Fame = 1000; - Karma = -1000; + Fame = 1000; + Karma = -1000; - PackItem( new Bandage( Utility.RandomMinMax( 1, 15 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(1, 15))); - if ( Female && 0.1 > Utility.RandomDouble() ) - PackItem( new TribalBerry() ); - else if ( !Female && 0.1 > Utility.RandomDouble() ) - PackItem( new BolaBall() ); + if (Female && 0.1 > Utility.RandomDouble()) + PackItem(new TribalBerry()); + else if (!Female && 0.1 > Utility.RandomDouble()) + PackItem(new BolaBall()); - AddItem( new Spear() ); - AddItem( new BoneArms() ); - AddItem( new BoneLegs() ); + AddItem(new Spear()); + AddItem(new BoneArms()); + AddItem(new BoneLegs()); - if ( 0.5 > Utility.RandomDouble() ) - AddItem( new SavageMask() ); - else if ( 0.1 > Utility.RandomDouble() ) - AddItem( new OrcishKinMask() ); - } + if (0.5 > Utility.RandomDouble()) + AddItem(new SavageMask()); + else if (0.1 > Utility.RandomDouble()) + AddItem(new OrcishKinMask()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public Savage(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override bool AlwaysMurderer => true; - public override bool ShowFameTitle => false; + public override string CorpseName => "a savage corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override int Meat => 1; + public override bool AlwaysMurderer => true; + public override bool ShowFameTitle => false; - public override bool IsEnemy( Mobile m ) - { - if ( m.BodyMod == 183 || m.BodyMod == 184 ) - return false; + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - return base.IsEnemy( m ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override bool IsEnemy(Mobile m) + { + if (m.BodyMod == 183 || m.BodyMod == 184) + return false; - if ( aggressor.BodyMod == 183 || aggressor.BodyMod == 184 ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - aggressor.BodyMod = 0; - aggressor.HueMod = -1; - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - aggressor.SendLocalizedMessage( 1040008 ); // Your skin is scorched as the tribal paint burns away! + return base.IsEnemy(m); + } - if ( aggressor is PlayerMobile mobile ) - mobile.SavagePaintExpiration = TimeSpan.Zero; - } - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - public override void AlterMeleeDamageTo( Mobile to, ref int damage ) - { - if ( to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || to is LesserHiryu || to is Daemon ) - damage *= 3; - } + if (aggressor.BodyMod == 183 || aggressor.BodyMod == 184) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + aggressor.BodyMod = 0; + aggressor.HueMod = -1; + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + aggressor.SendLocalizedMessage(1040008); // Your skin is scorched as the tribal paint burns away! - public Savage( Serial serial ) : base( serial ) - { - } + if (aggressor is PlayerMobile mobile) + mobile.SavagePaintExpiration = TimeSpan.Zero; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void AlterMeleeDamageTo(Mobile to, ref int damage) + { + if (to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || + to is LesserHiryu || to is Daemon) + damage *= 3; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/SavageRider.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/SavageRider.cs index 289c5677d..5d570d714 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/SavageRider.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/SavageRider.cs @@ -3,121 +3,123 @@ using Server.Items; namespace Server.Mobiles { - public class SavageRider : BaseCreature - { - public override string CorpseName => "a savage corpse"; - [Constructible] - public SavageRider() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.15, 0.4 ) - { - Name = NameList.RandomName( "savage rider" ); + public class SavageRider : BaseCreature + { + [Constructible] + public SavageRider() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.15, 0.4) + { + Name = NameList.RandomName("savage rider"); - if ( Female = Utility.RandomBool() ) - Body = 186; - else - Body = 185; + if (Female = Utility.RandomBool()) + Body = 186; + else + Body = 185; - SetStr( 151, 170 ); - SetDex( 92, 130 ); - SetInt( 51, 65 ); + SetStr(151, 170); + SetDex(92, 130); + SetInt(51, 65); - SetDamage( 29, 34 ); + SetDamage(29, 34); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.Fencing, 72.5, 95.0 ); - SetSkill( SkillName.Healing, 60.3, 90.0 ); - SetSkill( SkillName.Macing, 72.5, 95.0 ); - SetSkill( SkillName.Poisoning, 60.0, 82.5 ); - SetSkill( SkillName.MagicResist, 72.5, 95.0 ); - SetSkill( SkillName.Swords, 72.5, 95.0 ); - SetSkill( SkillName.Tactics, 72.5, 95.0 ); + SetSkill(SkillName.Fencing, 72.5, 95.0); + SetSkill(SkillName.Healing, 60.3, 90.0); + SetSkill(SkillName.Macing, 72.5, 95.0); + SetSkill(SkillName.Poisoning, 60.0, 82.5); + SetSkill(SkillName.MagicResist, 72.5, 95.0); + SetSkill(SkillName.Swords, 72.5, 95.0); + SetSkill(SkillName.Tactics, 72.5, 95.0); - Fame = 1000; - Karma = -1000; + Fame = 1000; + Karma = -1000; - PackItem( new Bandage( Utility.RandomMinMax( 1, 15 ) ) ); + PackItem(new Bandage(Utility.RandomMinMax(1, 15))); - if ( 0.1 > Utility.RandomDouble() ) - PackItem( new BolaBall() ); + if (0.1 > Utility.RandomDouble()) + PackItem(new BolaBall()); - AddItem( new TribalSpear() ); - AddItem( new BoneArms() ); - AddItem( new BoneLegs() ); - // TODO: BEAR MASK + AddItem(new TribalSpear()); + AddItem(new BoneArms()); + AddItem(new BoneLegs()); + // TODO: BEAR MASK - new SavageRidgeback().Rider = this; - } + new SavageRidgeback().Rider = this; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public SavageRider(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override bool AlwaysMurderer => true; - public override bool ShowFameTitle => false; + public override string CorpseName => "a savage corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; + public override int Meat => 1; + public override bool AlwaysMurderer => true; + public override bool ShowFameTitle => false; - public override bool OnBeforeDeath() - { - IMount mount = Mount; + public override OppositionGroup OppositionGroup => OppositionGroup.SavagesAndOrcs; - if ( mount != null ) - mount.Rider = null; + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - if ( mount is Mobile mobile ) - mobile.Delete(); + public override bool OnBeforeDeath() + { + IMount mount = Mount; - return base.OnBeforeDeath(); - } + if (mount != null) + mount.Rider = null; - public override bool IsEnemy( Mobile m ) - { - if ( m.BodyMod == 183 || m.BodyMod == 184 ) - return false; + if (mount is Mobile mobile) + mobile.Delete(); - return base.IsEnemy( m ); - } + return base.OnBeforeDeath(); + } - public override void AggressiveAction( Mobile aggressor, bool criminal ) - { - base.AggressiveAction( aggressor, criminal ); + public override bool IsEnemy(Mobile m) + { + if (m.BodyMod == 183 || m.BodyMod == 184) + return false; - if ( aggressor.BodyMod == 183 || aggressor.BodyMod == 184 ) - { - AOS.Damage( aggressor, 50, 0, 100, 0, 0, 0 ); - aggressor.BodyMod = 0; - aggressor.HueMod = -1; - aggressor.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - aggressor.PlaySound( 0x307 ); - aggressor.SendLocalizedMessage( 1040008 ); // Your skin is scorched as the tribal paint burns away! + return base.IsEnemy(m); + } - if ( aggressor is PlayerMobile mobile ) - mobile.SavagePaintExpiration = TimeSpan.Zero; - } - } + public override void AggressiveAction(Mobile aggressor, bool criminal) + { + base.AggressiveAction(aggressor, criminal); - public override void AlterMeleeDamageTo( Mobile to, ref int damage ) - { - if ( to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || to is LesserHiryu || to is Daemon ) - damage *= 3; - } + if (aggressor.BodyMod == 183 || aggressor.BodyMod == 184) + { + AOS.Damage(aggressor, 50, 0, 100, 0, 0, 0); + aggressor.BodyMod = 0; + aggressor.HueMod = -1; + aggressor.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + aggressor.PlaySound(0x307); + aggressor.SendLocalizedMessage(1040008); // Your skin is scorched as the tribal paint burns away! - public SavageRider( Serial serial ) : base( serial ) - { - } + if (aggressor is PlayerMobile mobile) + mobile.SavagePaintExpiration = TimeSpan.Zero; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void AlterMeleeDamageTo(Mobile to, ref int damage) + { + if (to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || + to is LesserHiryu || to is Daemon) + damage *= 3; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/ShadowFiend.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/ShadowFiend.cs index 430d6d214..37d98c82e 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/ShadowFiend.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/ShadowFiend.cs @@ -3,140 +3,139 @@ using Server.Items; namespace Server.Mobiles { - public class ShadowFiend : BaseCreature - { - public override bool DeleteCorpseOnDeath => true; + public class ShadowFiend : BaseCreature + { + private UnhideTimer m_Timer; - private UnhideTimer m_Timer; + [Constructible] + public ShadowFiend() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0xA8; - public override string DefaultName => "a shadow fiend"; + // this to allow shadow fiend to loot from corpses + Backpack backpack = new Backpack(); + backpack.Movable = false; + AddItem(backpack); - [Constructible] - public ShadowFiend() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0xA8; + SetStr(46, 55); + SetDex(121, 130); + SetInt(46, 55); - // this to allow shadow fiend to loot from corpses - Backpack backpack = new Backpack(); - backpack.Movable = false; - AddItem( backpack ); + SetHits(28, 33); + SetStam(46, 55); - SetStr( 46, 55 ); - SetDex( 121, 130 ); - SetInt( 46, 55 ); + SetDamage(10, 22); - SetHits( 28, 33 ); - SetStam( 46, 55 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 80); - SetDamage( 10, 22 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 20, 25); + SetResistance(ResistanceType.Cold, 40, 45); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 5, 10); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 80 ); + SetSkill(SkillName.MagicResist, 20.1, 30.0); + SetSkill(SkillName.Tactics, 20.1, 30.0); + SetSkill(SkillName.Wrestling, 20.1, 30.0); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 20, 25 ); - SetResistance( ResistanceType.Cold, 40, 45 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 5, 10 ); + Fame = 1000; + Karma = -1000; - SetSkill( SkillName.MagicResist, 20.1, 30.0 ); - SetSkill( SkillName.Tactics, 20.1, 30.0 ); - SetSkill( SkillName.Wrestling, 20.1, 30.0 ); + m_Timer = new UnhideTimer(this); + m_Timer.Start(); + } - Fame = 1000; - Karma = -1000; + public ShadowFiend(Serial serial) : base(serial) + { + } - m_Timer = new UnhideTimer( this ); - m_Timer.Start(); - } + public override bool DeleteCorpseOnDeath => true; - public override int GetIdleSound() - { - return 0x37A; - } + public override string DefaultName => "a shadow fiend"; - public override int GetAngerSound() - { - return 0x379; - } + public override bool CanRummageCorpses => true; - public override int GetDeathSound() - { - return 0x381; - } + public override int GetIdleSound() + { + return 0x37A; + } - public override int GetAttackSound() - { - return 0x37F; - } + public override int GetAngerSound() + { + return 0x379; + } - public override int GetHurtSound() - { - return 0x380; - } + public override int GetDeathSound() + { + return 0x381; + } - public override bool CanRummageCorpses => true; + public override int GetAttackSound() + { + return 0x37F; + } - public override bool OnBeforeDeath() - { - Backpack?.Destroy(); + public override int GetHurtSound() + { + return 0x380; + } - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + public override bool OnBeforeDeath() + { + Backpack?.Destroy(); - public ShadowFiend( Serial serial ) : base( serial ) - { - } + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - m_Timer = new UnhideTimer( this ); - m_Timer.Start(); - } + m_Timer = new UnhideTimer(this); + m_Timer.Start(); + } - public override void OnAfterDelete() - { - m_Timer?.Stop(); + public override void OnAfterDelete() + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - base.OnAfterDelete(); - } + base.OnAfterDelete(); + } - private class UnhideTimer : Timer - { - private ShadowFiend m_Owner; + private class UnhideTimer : Timer + { + private ShadowFiend m_Owner; - public UnhideTimer( ShadowFiend owner ) : base( TimeSpan.FromSeconds( 30.0 ) ) - { - m_Owner = owner; - Priority = TimerPriority.OneSecond; - } + public UnhideTimer(ShadowFiend owner) : base(TimeSpan.FromSeconds(30.0)) + { + m_Owner = owner; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } - foreach ( Mobile m in m_Owner.GetMobilesInRange( 3 ) ) - { - if ( m != m_Owner && m.Player && m.Hidden && m_Owner.CanBeHarmful( m ) && m.AccessLevel == AccessLevel.Player ) - m.Hidden = false; - } - } - } - } -} + foreach (Mobile m in m_Owner.GetMobilesInRange(3)) + if (m != m_Owner && m.Player && m.Hidden && m_Owner.CanBeHarmful(m) && + m.AccessLevel == AccessLevel.Player) + m.Hidden = false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/SkeletalKnight.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/SkeletalKnight.cs index ce24ddf3e..11d75bc70 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/SkeletalKnight.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/SkeletalKnight.cs @@ -2,81 +2,93 @@ using Server.Items; namespace Server.Mobiles { - public class SkeletalKnight : BaseCreature - { - public override string CorpseName => "a skeletal corpse"; - public override string DefaultName => "a skeletal knight"; + public class SkeletalKnight : BaseCreature + { + [Constructible] + public SkeletalKnight() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 147; + BaseSoundID = 451; - [Constructible] - public SkeletalKnight() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 147; - BaseSoundID = 451; + SetStr(196, 250); + SetDex(76, 95); + SetInt(36, 60); - SetStr( 196, 250 ); - SetDex( 76, 95 ); - SetInt( 36, 60 ); + SetHits(118, 150); - SetHits( 118, 150 ); + SetDamage(8, 18); - SetDamage( 8, 18 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 85.1, 100.0); + SetSkill(SkillName.Wrestling, 85.1, 95.0); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 85.1, 100.0 ); - SetSkill( SkillName.Wrestling, 85.1, 95.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 40; - VirtualArmor = 40; + switch (Utility.Random(6)) + { + case 0: + PackItem(new PlateArms()); + break; + case 1: + PackItem(new PlateChest()); + break; + case 2: + PackItem(new PlateGloves()); + break; + case 3: + PackItem(new PlateGorget()); + break; + case 4: + PackItem(new PlateLegs()); + break; + case 5: + PackItem(new PlateHelm()); + break; + } - switch ( Utility.Random( 6 ) ) - { - case 0: PackItem( new PlateArms() ); break; - case 1: PackItem( new PlateChest() ); break; - case 2: PackItem( new PlateGloves() ); break; - case 3: PackItem( new PlateGorget() ); break; - case 4: PackItem( new PlateLegs() ); break; - case 5: PackItem( new PlateHelm() ); break; - } + PackItem(new Scimitar()); + PackItem(new WoodenShield()); + } - PackItem( new Scimitar() ); - PackItem( new WoodenShield() ); - } + public SkeletalKnight(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a skeletal corpse"; + public override string DefaultName => "a skeletal knight"; - public override bool BleedImmune => true; + public override bool BleedImmune => true; - public SkeletalKnight( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Skeleton.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Skeleton.cs index 7ef77b08d..14ae71378 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Skeleton.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Skeleton.cs @@ -2,76 +2,86 @@ using Server.Items; namespace Server.Mobiles { - public class Skeleton : BaseCreature - { - public override string CorpseName => "a skeletal corpse"; - public override string DefaultName => "a skeleton"; + public class Skeleton : BaseCreature + { + [Constructible] + public Skeleton() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(50, 56); + BaseSoundID = 0x48D; - [Constructible] - public Skeleton() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 50, 56 ); - BaseSoundID = 0x48D; + SetStr(56, 80); + SetDex(56, 75); + SetInt(16, 40); - SetStr( 56, 80 ); - SetDex( 56, 75 ); - SetInt( 16, 40 ); + SetHits(34, 48); - SetHits( 34, 48 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 25, 40); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 5, 15); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 25, 40 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 5, 15 ); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 55.0); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 55.0 ); + Fame = 450; + Karma = -450; - Fame = 450; - Karma = -450; + VirtualArmor = 16; - VirtualArmor = 16; + switch (Utility.Random(5)) + { + case 0: + PackItem(new BoneArms()); + break; + case 1: + PackItem(new BoneChest()); + break; + case 2: + PackItem(new BoneGloves()); + break; + case 3: + PackItem(new BoneLegs()); + break; + case 4: + PackItem(new BoneHelm()); + break; + } + } - switch ( Utility.Random( 5 )) - { - case 0: PackItem( new BoneArms() ); break; - case 1: PackItem( new BoneChest() ); break; - case 2: PackItem( new BoneGloves() ); break; - case 3: PackItem( new BoneLegs() ); break; - case 4: PackItem( new BoneHelm() ); break; - } - } + public Skeleton(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a skeletal corpse"; + public override string DefaultName => "a skeleton"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lesser; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lesser; - public Skeleton( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/SpawnedOrcishLord.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/SpawnedOrcishLord.cs index 7c269342d..2aaee4310 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/SpawnedOrcishLord.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/SpawnedOrcishLord.cs @@ -2,41 +2,42 @@ using Server.Items; namespace Server.Mobiles { - public class SpawnedOrcishLord : OrcishLord - { - public override string CorpseName => "an orcish corpse"; - [Constructible] - public SpawnedOrcishLord() - { - Container pack = Backpack; + public class SpawnedOrcishLord : OrcishLord + { + [Constructible] + public SpawnedOrcishLord() + { + Container pack = Backpack; - pack?.Delete(); + pack?.Delete(); - NoKillAwards = true; - } + NoKillAwards = true; + } - public SpawnedOrcishLord( Serial serial ) : base( serial ) - { - } + public SpawnedOrcishLord(Serial serial) : base(serial) + { + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override string CorpseName => "an orcish corpse"; - c.Delete(); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + c.Delete(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - NoKillAwards = true; - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + NoKillAwards = true; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/SpectralArmour.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/SpectralArmour.cs index 3030e2317..0e7480460 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/SpectralArmour.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/SpectralArmour.cs @@ -2,96 +2,96 @@ using Server.Items; namespace Server.Mobiles { + public class SpectralArmour : BaseCreature + { + [Constructible] + public SpectralArmour() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 637; + Hue = 0x8026; - public class SpectralArmour : BaseCreature - { - public override bool DeleteCorpseOnDeath => true; + Buckler buckler = new Buckler(); + ChainCoif coif = new ChainCoif(); + PlateGloves gloves = new PlateGloves(); - public override string DefaultName => "a spectral armour"; + buckler.Hue = 0x835; + buckler.Movable = false; + coif.Hue = 0x835; + gloves.Hue = 0x835; - [Constructible] - public SpectralArmour() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 637; - Hue = 0x8026; + AddItem(buckler); + AddItem(coif); + AddItem(gloves); - Buckler buckler = new Buckler(); - ChainCoif coif = new ChainCoif (); - PlateGloves gloves = new PlateGloves(); + SetStr(101, 110); + SetDex(101, 110); + SetInt(101, 110); - buckler.Hue = 0x835; buckler.Movable = false; - coif.Hue = 0x835; - gloves.Hue = 0x835; + SetHits(178, 201); + SetStam(191, 200); - AddItem( buckler ); - AddItem( coif ); - AddItem( gloves ); + SetDamage(10, 22); - SetStr( 101, 110 ); - SetDex( 101, 110 ); - SetInt( 101, 110 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Cold, 25); - SetHits( 178, 201 ); - SetStam( 191, 200 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamage( 10, 22 ); + SetSkill(SkillName.Wrestling, 75.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 90.1, 100); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Cold, 25 ); + VirtualArmor = 40; + Fame = 7000; + Karma = -7000; + } - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + public SpectralArmour(Serial serial) : base(serial) + { + } - SetSkill( SkillName.Wrestling, 75.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100 ); + public override bool DeleteCorpseOnDeath => true; - VirtualArmor = 40; - Fame = 7000; - Karma = -7000; - } + public override string DefaultName => "a spectral armour"; - public override int GetIdleSound() - { - return 0x200; - } + public override Poison PoisonImmune => Poison.Regular; - public override int GetAngerSound() - { - return 0x56; - } + public override int GetIdleSound() + { + return 0x200; + } - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + public override int GetAngerSound() + { + return 0x56; + } - Gold gold = new Gold( Utility.RandomMinMax( 240, 375 ) ); - gold.MoveToWorld( Location, Map ); + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + Gold gold = new Gold(Utility.RandomMinMax(240, 375)); + gold.MoveToWorld(Location, Map); - public override Poison PoisonImmune => Poison.Regular; + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public SpectralArmour( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/StoneGargoyle.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/StoneGargoyle.cs index 2ae8e6410..62e8f3943 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/StoneGargoyle.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/StoneGargoyle.cs @@ -2,71 +2,71 @@ using Server.Items; namespace Server.Mobiles { - public class StoneGargoyle : BaseCreature - { - public override string CorpseName => "a gargoyle corpse"; - public override string DefaultName => "a stone gargoyle"; + public class StoneGargoyle : BaseCreature + { + [Constructible] + public StoneGargoyle() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 67; + BaseSoundID = 0x174; - [Constructible] - public StoneGargoyle() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 67; - BaseSoundID = 0x174; + SetStr(246, 275); + SetDex(76, 95); + SetInt(81, 105); - SetStr( 246, 275 ); - SetDex( 76, 95 ); - SetInt( 81, 105 ); + SetHits(148, 165); - SetHits( 148, 165 ); + SetDamage(11, 17); - SetDamage( 11, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 85.1, 100.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 85.1, 100.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 50; - VirtualArmor = 50; + PackItem(new IronIngot(12)); - PackItem( new IronIngot( 12 ) ); + if (0.05 > Utility.RandomDouble()) + PackItem(new GargoylesPickaxe()); + } - if ( 0.05 > Utility.RandomDouble() ) - PackItem( new GargoylesPickaxe() ); - } + public StoneGargoyle(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.Gems, 1 ); - AddLoot( LootPack.Potions ); - } + public override string CorpseName => "a gargoyle corpse"; + public override string DefaultName => "a stone gargoyle"; - public override int TreasureMapLevel => 2; + public override int TreasureMapLevel => 2; - public StoneGargoyle( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.Gems, 1); + AddLoot(LootPack.Potions); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/StrongMongbat.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/StrongMongbat.cs index 135ac86da..f715d7556 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/StrongMongbat.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/StrongMongbat.cs @@ -1,66 +1,66 @@ namespace Server.Mobiles { - public class StrongMongbat : BaseCreature - { - public override string CorpseName => "a mongbat corpse"; - public override string DefaultName => "a mongbat"; + public class StrongMongbat : BaseCreature + { + [Constructible] + public StrongMongbat() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 39; + BaseSoundID = 422; - [Constructible] - public StrongMongbat() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 39; - BaseSoundID = 422; + SetStr(6, 10); + SetDex(26, 38); + SetInt(6, 14); - SetStr( 6, 10 ); - SetDex( 26, 38 ); - SetInt( 6, 14 ); + SetHits(4, 6); + SetMana(0); - SetHits( 4, 6 ); - SetMana( 0 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 25); - SetResistance( ResistanceType.Physical, 15, 25 ); + SetSkill(SkillName.MagicResist, 15.1, 30.0); + SetSkill(SkillName.Tactics, 35.1, 50.0); + SetSkill(SkillName.Wrestling, 20.1, 35.0); - SetSkill( SkillName.MagicResist, 15.1, 30.0 ); - SetSkill( SkillName.Tactics, 35.1, 50.0 ); - SetSkill( SkillName.Wrestling, 20.1, 35.0 ); + Fame = 150; + Karma = -150; - Fame = 150; - Karma = -150; + VirtualArmor = 10; - VirtualArmor = 10; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 71.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 71.1; - } + public StrongMongbat(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - } + public override string CorpseName => "a mongbat corpse"; + public override string DefaultName => "a mongbat"; - public override int Meat => 1; - public override int Hides => 6; - public override FoodType FavoriteFood => FoodType.Meat; + public override int Meat => 1; + public override int Hides => 6; + public override FoodType FavoriteFood => FoodType.Meat; - public StrongMongbat( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Troll.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Troll.cs index 276a5bdd4..4d060a092 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Troll.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Troll.cs @@ -1,65 +1,65 @@ namespace Server.Mobiles { - public class Troll : BaseCreature - { - public override string CorpseName => "a troll corpse"; - public override string DefaultName => "a troll"; + public class Troll : BaseCreature + { + [Constructible] + public Troll() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(53, 54); + BaseSoundID = 461; - [Constructible] - public Troll () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 53, 54 ); - BaseSoundID = 461; + SetStr(176, 205); + SetDex(46, 65); + SetInt(46, 70); - SetStr( 176, 205 ); - SetDex( 46, 65 ); - SetInt( 46, 70 ); + SetHits(106, 123); - SetHits( 106, 123 ); + SetDamage(8, 14); - SetDamage( 8, 14 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 5, 15); + SetResistance(ResistanceType.Energy, 5, 15); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 5, 15 ); - SetResistance( ResistanceType.Energy, 5, 15 ); + SetSkill(SkillName.MagicResist, 45.1, 60.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetSkill( SkillName.MagicResist, 45.1, 60.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 40; + } - VirtualArmor = 40; - } + public Troll(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a troll corpse"; + public override string DefaultName => "a troll"; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 1; - public override int Meat => 2; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 1; + public override int Meat => 2; - public Troll( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Humanoid/Melee/Zombie.cs b/Scripts/Mobiles/Monsters/Humanoid/Melee/Zombie.cs index d4ed53f71..b67a6cdf5 100644 --- a/Scripts/Mobiles/Monsters/Humanoid/Melee/Zombie.cs +++ b/Scripts/Mobiles/Monsters/Humanoid/Melee/Zombie.cs @@ -2,79 +2,99 @@ using Server.Items; namespace Server.Mobiles { - public class Zombie : BaseCreature - { - public override string CorpseName => "a rotting corpse"; - public override string DefaultName => "a zombie"; + public class Zombie : BaseCreature + { + [Constructible] + public Zombie() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 3; + BaseSoundID = 471; - [Constructible] - public Zombie() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 3; - BaseSoundID = 471; + SetStr(46, 70); + SetDex(31, 50); + SetInt(26, 40); - SetStr( 46, 70 ); - SetDex( 31, 50 ); - SetInt( 26, 40 ); + SetHits(28, 42); - SetHits( 28, 42 ); + SetDamage(3, 7); - SetDamage( 3, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 5, 10); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 5, 10 ); + SetSkill(SkillName.MagicResist, 15.1, 40.0); + SetSkill(SkillName.Tactics, 35.1, 50.0); + SetSkill(SkillName.Wrestling, 35.1, 50.0); - SetSkill( SkillName.MagicResist, 15.1, 40.0 ); - SetSkill( SkillName.Tactics, 35.1, 50.0 ); - SetSkill( SkillName.Wrestling, 35.1, 50.0 ); + Fame = 600; + Karma = -600; - Fame = 600; - Karma = -600; + VirtualArmor = 18; - VirtualArmor = 18; + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } + } - switch ( Utility.Random( 10 )) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } - } + public Zombie(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a rotting corpse"; + public override string DefaultName => "a zombie"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Regular; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Regular; - public Zombie( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusMinion.cs b/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusMinion.cs index ebc457a88..25f412e5c 100644 --- a/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusMinion.cs +++ b/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusMinion.cs @@ -2,193 +2,194 @@ using Server.Items; namespace Server.Mobiles { - public class ExodusMinion : BaseCreature - { - public override string CorpseName => "a minion's corpse"; - public bool FieldActive { get; private set; } + public class ExodusMinion : BaseCreature + { + [Constructible] + public ExodusMinion() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x2F5; - public bool CanUseField // TODO: an OSI bug prevents to verify this - => Hits >= HitsMax * 9 / 10; + SetStr(851, 950); + SetDex(71, 80); + SetInt(61, 90); - public override bool IsScaredOfScaryThings => false; - public override bool IsScaryToPets => true; + SetHits(511, 570); - public override string DefaultName => "an exodus minion"; + SetDamage(16, 22); - [Constructible] - public ExodusMinion() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x2F5; + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 15, 25); - SetStr( 851, 950 ); - SetDex( 71, 80 ); - SetInt( 61, 90 ); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetHits( 511, 570 ); + Fame = 18000; + Karma = -18000; + VirtualArmor = 65; - SetDamage( 16, 22 ); + PackItem(new PowerCrystal()); + PackItem(new ArcaneGem()); + PackItem(new ClockworkAssembly()); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 15, 25); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + switch (Utility.Random(3)) + { + case 0: + PackItem(new PowerCrystal()); + break; + case 1: + PackItem(new ArcaneGem()); + break; + case 2: + PackItem(new ClockworkAssembly()); + break; + } - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + FieldActive = CanUseField; + } - Fame = 18000; - Karma = -18000; - VirtualArmor = 65; + public ExodusMinion(Serial serial) : base(serial) + { + } - PackItem( new PowerCrystal() ); - PackItem( new ArcaneGem() ); - PackItem( new ClockworkAssembly() ); + public override string CorpseName => "a minion's corpse"; + public bool FieldActive{ get; private set; } - switch( Utility.Random( 3 ) ) - { - case 0: PackItem( new PowerCrystal() ); break; - case 1: PackItem( new ArcaneGem() ); break; - case 2: PackItem( new ClockworkAssembly() ); break; - } + public bool CanUseField // TODO: an OSI bug prevents to verify this + => Hits >= HitsMax * 9 / 10; - FieldActive = CanUseField; - } + public override bool IsScaredOfScaryThings => false; + public override bool IsScaryToPets => true; - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Rich ); - } + public override string DefaultName => "an exodus minion"; - public override bool AutoDispel => true; - public override bool BardImmune => !Core.AOS; - public override Poison PoisonImmune => Poison.Lethal; + public override bool AutoDispel => true; + public override bool BardImmune => !Core.AOS; + public override Poison PoisonImmune => Poison.Lethal; - public override int GetIdleSound() - { - return 0x218; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Rich); + } - public override int GetAngerSound() - { - return 0x26C; - } + public override int GetIdleSound() + { + return 0x218; + } - public override int GetDeathSound() - { - return 0x211; - } + public override int GetAngerSound() + { + return 0x26C; + } - public override int GetAttackSound() - { - return 0x232; - } + public override int GetDeathSound() + { + return 0x211; + } - public override int GetHurtSound() - { - return 0x140; - } + public override int GetAttackSound() + { + return 0x232; + } - public override void AlterMeleeDamageFrom( Mobile from, ref int damage ) - { - if ( FieldActive ) - damage = 0; // no melee damage when the field is up - } + public override int GetHurtSound() + { + return 0x140; + } - public override void AlterSpellDamageFrom( Mobile from, ref int damage ) - { - if ( !FieldActive ) - damage = 0; // no spell damage when the field is down - } + public override void AlterMeleeDamageFrom(Mobile from, ref int damage) + { + if (FieldActive) + damage = 0; // no melee damage when the field is up + } - public override void OnDamagedBySpell( Mobile from ) - { - if ( from != null && from.Alive && 0.4 > Utility.RandomDouble() ) - { - SendEBolt( from ); - } + public override void AlterSpellDamageFrom(Mobile from, ref int damage) + { + if (!FieldActive) + damage = 0; // no spell damage when the field is down + } - if ( !FieldActive ) - { - // should there be an effect when spells nullifying is on? - FixedParticles( 0, 10, 0, 0x2522, EffectLayer.Waist ); - } - else if ( FieldActive && !CanUseField ) - { - FieldActive = false; + public override void OnDamagedBySpell(Mobile from) + { + if (from != null && from.Alive && 0.4 > Utility.RandomDouble()) SendEBolt(from); - // TODO: message and effect when field turns down; cannot be verified on OSI due to a bug - FixedParticles( 0x3735, 1, 30, 0x251F, EffectLayer.Waist ); - } - } + if (!FieldActive) + { + // should there be an effect when spells nullifying is on? + FixedParticles(0, 10, 0, 0x2522, EffectLayer.Waist); + } + else if (FieldActive && !CanUseField) + { + FieldActive = false; - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + // TODO: message and effect when field turns down; cannot be verified on OSI due to a bug + FixedParticles(0x3735, 1, 30, 0x251F, EffectLayer.Waist); + } + } - if ( FieldActive ) - { - FixedParticles( 0x376A, 20, 10, 0x2530, EffectLayer.Waist ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - PlaySound( 0x2F4 ); + if (FieldActive) + { + FixedParticles(0x376A, 20, 10, 0x2530, EffectLayer.Waist); - attacker.SendAsciiMessage( "Your weapon cannot penetrate the creature's magical barrier" ); - } + PlaySound(0x2F4); - if ( attacker != null && attacker.Alive && attacker.Weapon is BaseRanged && 0.4 > Utility.RandomDouble() ) - { - SendEBolt( attacker ); - } - } + attacker.SendAsciiMessage("Your weapon cannot penetrate the creature's magical barrier"); + } - public override void OnThink() - { - base.OnThink(); + if (attacker != null && attacker.Alive && attacker.Weapon is BaseRanged && 0.4 > Utility.RandomDouble()) + SendEBolt(attacker); + } - // TODO: an OSI bug prevents to verify if the field can regenerate or not - if ( !FieldActive && !IsHurt() ) - FieldActive = true; - } + public override void OnThink() + { + base.OnThink(); - public override bool Move( Direction d ) - { - bool move = base.Move( d ); + // TODO: an OSI bug prevents to verify if the field can regenerate or not + if (!FieldActive && !IsHurt()) + FieldActive = true; + } - if ( move && FieldActive && Combatant != null ) - FixedParticles( 0, 10, 0, 0x2530, EffectLayer.Waist ); + public override bool Move(Direction d) + { + bool move = base.Move(d); - return move; - } + if (move && FieldActive && Combatant != null) + FixedParticles(0, 10, 0, 0x2530, EffectLayer.Waist); - public void SendEBolt( Mobile to ) - { - MovingParticles( to, 0x379F, 7, 0, false, true, 0xBE3, 0xFCB, 0x211 ); - to.PlaySound( 0x229 ); - DoHarmful( to ); - AOS.Damage( to, this, 50, 0, 0, 0, 0, 100 ); - } + return move; + } - public ExodusMinion( Serial serial ) : base( serial ) - { - } + public void SendEBolt(Mobile to) + { + MovingParticles(to, 0x379F, 7, 0, false, true, 0xBE3, 0xFCB, 0x211); + to.PlaySound(0x229); + DoHarmful(to); + AOS.Damage(to, this, 50, 0, 0, 0, 0, 100); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - FieldActive = CanUseField; + FieldActive = CanUseField; - if ( Name == "Exodus Minion" ) - Name = null; - } - } -} + if (Name == "Exodus Minion") + Name = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusOverseer.cs b/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusOverseer.cs index b7927f79e..096ac5e8f 100644 --- a/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusOverseer.cs +++ b/Scripts/Mobiles/Monsters/LBR/Exodus/ExodusOverseer.cs @@ -2,189 +2,184 @@ using Server.Items; namespace Server.Mobiles { - public class ExodusOverseer : BaseCreature - { - public override string CorpseName => "an overseer's corpse"; - public bool FieldActive { get; private set; } + public class ExodusOverseer : BaseCreature + { + [Constructible] + public ExodusOverseer() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x2F4; - public bool CanUseField // TODO: an OSI bug prevents to verify this - => Hits >= HitsMax * 9 / 10; + SetStr(561, 650); + SetDex(76, 95); + SetInt(61, 90); - public override bool IsScaredOfScaryThings => false; - public override bool IsScaryToPets => true; + SetHits(331, 390); - public override string DefaultName => "an exodus overseer"; + SetDamage(13, 19); - [Constructible] - public ExodusOverseer() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x2F4; + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); - SetStr( 561, 650 ); - SetDex( 76, 95 ); - SetInt( 61, 90 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetHits( 331, 390 ); + SetSkill(SkillName.MagicResist, 80.2, 98.0); + SetSkill(SkillName.Tactics, 80.2, 98.0); + SetSkill(SkillName.Wrestling, 80.2, 98.0); - SetDamage( 13, 19 ); + Fame = 10000; + Karma = -10000; + VirtualArmor = 50; - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + if (Utility.Random(2) == 0) + PackItem(new PowerCrystal()); + else + PackItem(new ArcaneGem()); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + FieldActive = CanUseField; + } - SetSkill( SkillName.MagicResist, 80.2, 98.0 ); - SetSkill( SkillName.Tactics, 80.2, 98.0 ); - SetSkill( SkillName.Wrestling, 80.2, 98.0 ); + public ExodusOverseer(Serial serial) : base(serial) + { + } - Fame = 10000; - Karma = -10000; - VirtualArmor = 50; + public override string CorpseName => "an overseer's corpse"; + public bool FieldActive{ get; private set; } - if ( Utility.Random( 2 ) == 0 ) - PackItem( new PowerCrystal() ); - else - PackItem( new ArcaneGem() ); + public bool CanUseField // TODO: an OSI bug prevents to verify this + => Hits >= HitsMax * 9 / 10; - FieldActive = CanUseField; - } + public override bool IsScaredOfScaryThings => false; + public override bool IsScaryToPets => true; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override string DefaultName => "an exodus overseer"; - public override bool AutoDispel => true; - public override bool BardImmune => !Core.AOS; - public override Poison PoisonImmune => Poison.Lethal; + public override bool AutoDispel => true; + public override bool BardImmune => !Core.AOS; + public override Poison PoisonImmune => Poison.Lethal; - public override int GetIdleSound() - { - return 0xFD; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override int GetAngerSound() - { - return 0x26C; - } + public override int GetIdleSound() + { + return 0xFD; + } - public override int GetDeathSound() - { - return 0x211; - } + public override int GetAngerSound() + { + return 0x26C; + } - public override int GetAttackSound() - { - return 0x23B; - } + public override int GetDeathSound() + { + return 0x211; + } - public override int GetHurtSound() - { - return 0x140; - } + public override int GetAttackSound() + { + return 0x23B; + } - public override void AlterMeleeDamageFrom( Mobile from, ref int damage ) - { - if ( FieldActive ) - damage = 0; // no melee damage when the field is up - } + public override int GetHurtSound() + { + return 0x140; + } - public override void AlterSpellDamageFrom( Mobile caster, ref int damage ) - { - if ( !FieldActive ) - damage = 0; // no spell damage when the field is down - } + public override void AlterMeleeDamageFrom(Mobile from, ref int damage) + { + if (FieldActive) + damage = 0; // no melee damage when the field is up + } - public override void OnDamagedBySpell( Mobile from ) - { - if ( from != null && from.Alive && 0.4 > Utility.RandomDouble() ) - { - SendEBolt( from ); - } + public override void AlterSpellDamageFrom(Mobile caster, ref int damage) + { + if (!FieldActive) + damage = 0; // no spell damage when the field is down + } - if ( !FieldActive ) - { - // should there be an effect when spells nullifying is on? - FixedParticles( 0, 10, 0, 0x2522, EffectLayer.Waist ); - } - else if ( FieldActive && !CanUseField ) - { - FieldActive = false; + public override void OnDamagedBySpell(Mobile from) + { + if (from != null && from.Alive && 0.4 > Utility.RandomDouble()) SendEBolt(from); - // TODO: message and effect when field turns down; cannot be verified on OSI due to a bug - FixedParticles( 0x3735, 1, 30, 0x251F, EffectLayer.Waist ); - } - } + if (!FieldActive) + { + // should there be an effect when spells nullifying is on? + FixedParticles(0, 10, 0, 0x2522, EffectLayer.Waist); + } + else if (FieldActive && !CanUseField) + { + FieldActive = false; - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + // TODO: message and effect when field turns down; cannot be verified on OSI due to a bug + FixedParticles(0x3735, 1, 30, 0x251F, EffectLayer.Waist); + } + } - if ( FieldActive ) - { - FixedParticles( 0x376A, 20, 10, 0x2530, EffectLayer.Waist ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - PlaySound( 0x2F4 ); + if (FieldActive) + { + FixedParticles(0x376A, 20, 10, 0x2530, EffectLayer.Waist); - attacker.SendAsciiMessage( "Your weapon cannot penetrate the creature's magical barrier" ); - } + PlaySound(0x2F4); - if ( attacker != null && attacker.Alive && attacker.Weapon is BaseRanged && 0.4 > Utility.RandomDouble() ) - { - SendEBolt( attacker ); - } - } + attacker.SendAsciiMessage("Your weapon cannot penetrate the creature's magical barrier"); + } - public override void OnThink() - { - base.OnThink(); + if (attacker != null && attacker.Alive && attacker.Weapon is BaseRanged && 0.4 > Utility.RandomDouble()) + SendEBolt(attacker); + } - // TODO: an OSI bug prevents to verify if the field can regenerate or not - if ( !FieldActive && !IsHurt() ) - FieldActive = true; - } + public override void OnThink() + { + base.OnThink(); - public override bool Move( Direction d ) - { - bool move = base.Move( d ); + // TODO: an OSI bug prevents to verify if the field can regenerate or not + if (!FieldActive && !IsHurt()) + FieldActive = true; + } - if ( move && FieldActive && Combatant != null ) - FixedParticles( 0, 10, 0, 0x2530, EffectLayer.Waist ); + public override bool Move(Direction d) + { + bool move = base.Move(d); - return move; - } + if (move && FieldActive && Combatant != null) + FixedParticles(0, 10, 0, 0x2530, EffectLayer.Waist); - public void SendEBolt( Mobile to ) - { - MovingParticles( to, 0x379F, 7, 0, false, true, 0xBE3, 0xFCB, 0x211 ); - to.PlaySound( 0x229 ); - DoHarmful( to ); - AOS.Damage( to, this, 50, 0, 0, 0, 0, 100 ); - } + return move; + } - public ExodusOverseer( Serial serial ) : base( serial ) - { - } + public void SendEBolt(Mobile to) + { + MovingParticles(to, 0x379F, 7, 0, false, true, 0xBE3, 0xFCB, 0x211); + to.PlaySound(0x229); + DoHarmful(to); + AOS.Damage(to, this, 50, 0, 0, 0, 0, 100); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - FieldActive = CanUseField; + FieldActive = CanUseField; - if ( Name == "Exodus Overseer" ) - Name = null; - } - } -} + if (Name == "Exodus Overseer") + Name = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoon.cs b/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoon.cs index 3e4be734a..2afaf18ec 100644 --- a/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoon.cs +++ b/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoon.cs @@ -2,181 +2,212 @@ using Server.Items; namespace Server.Mobiles { - public class ChaosDragoon : BaseCreature - { - public override string CorpseName => "a chaos dragoon corpse"; - public override string DefaultName => "a chaos dragoon"; + public class ChaosDragoon : BaseCreature + { + [Constructible] + public ChaosDragoon() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.15, 0.4) + { + Body = 0x190; + Hue = Utility.RandomSkinHue(); - [Constructible] - public ChaosDragoon() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.15, 0.4 ) - { - Body = 0x190; - Hue = Utility.RandomSkinHue(); + SetStr(176, 225); + SetDex(81, 95); + SetInt(61, 85); - SetStr( 176, 225 ); - SetDex( 81, 95 ); - SetInt( 61, 85 ); + SetHits(176, 225); - SetHits( 176, 225 ); + SetDamage(24, 26); - SetDamage( 24, 26 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Fire, 25); + SetDamageType(ResistanceType.Cold, 25); + SetDamageType(ResistanceType.Energy, 25); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Fire, 25 ); - SetDamageType( ResistanceType.Cold, 25 ); - SetDamageType( ResistanceType.Energy, 25 ); + //SetResistance( ResistanceType.Physical, 25, 38 ); + //SetResistance( ResistanceType.Fire, 25, 38 ); + //SetResistance( ResistanceType.Cold, 25, 38 ); + //SetResistance( ResistanceType.Poison, 25, 38 ); + //SetResistance( ResistanceType.Energy, 25, 38 ); - //SetResistance( ResistanceType.Physical, 25, 38 ); - //SetResistance( ResistanceType.Fire, 25, 38 ); - //SetResistance( ResistanceType.Cold, 25, 38 ); - //SetResistance( ResistanceType.Poison, 25, 38 ); - //SetResistance( ResistanceType.Energy, 25, 38 ); + SetSkill(SkillName.Fencing, 77.6, 92.5); + SetSkill(SkillName.Healing, 60.3, 90.0); + SetSkill(SkillName.Macing, 77.6, 92.5); + SetSkill(SkillName.Anatomy, 77.6, 87.5); + SetSkill(SkillName.MagicResist, 77.6, 97.5); + SetSkill(SkillName.Swords, 77.6, 92.5); + SetSkill(SkillName.Tactics, 77.6, 87.5); - SetSkill( SkillName.Fencing, 77.6, 92.5 ); - SetSkill( SkillName.Healing, 60.3, 90.0 ); - SetSkill( SkillName.Macing, 77.6, 92.5 ); - SetSkill( SkillName.Anatomy, 77.6, 87.5 ); - SetSkill( SkillName.MagicResist, 77.6, 97.5 ); - SetSkill( SkillName.Swords, 77.6, 92.5 ); - SetSkill( SkillName.Tactics, 77.6, 87.5 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + CraftResource res = CraftResource.None; - CraftResource res = CraftResource.None; + switch (Utility.Random(6)) + { + case 0: + res = CraftResource.BlackScales; + break; + case 1: + res = CraftResource.RedScales; + break; + case 2: + res = CraftResource.BlueScales; + break; + case 3: + res = CraftResource.YellowScales; + break; + case 4: + res = CraftResource.GreenScales; + break; + case 5: + res = CraftResource.WhiteScales; + break; + } - switch (Utility.Random( 6 )) - { - case 0: res = CraftResource.BlackScales; break; - case 1: res = CraftResource.RedScales; break; - case 2: res = CraftResource.BlueScales; break; - case 3: res = CraftResource.YellowScales; break; - case 4: res = CraftResource.GreenScales; break; - case 5: res = CraftResource.WhiteScales; break; - } + BaseWeapon melee = null; - BaseWeapon melee = null; + switch (Utility.Random(3)) + { + case 0: + melee = new Kryss(); + break; + case 1: + melee = new Broadsword(); + break; + case 2: + melee = new Katana(); + break; + } - switch (Utility.Random( 3 )) - { - case 0: melee = new Kryss(); break; - case 1: melee = new Broadsword(); break; - case 2: melee = new Katana(); break; - } + melee.Movable = false; + AddItem(melee); - melee.Movable = false; - AddItem( melee ); + DragonHelm helm = new DragonHelm(); + helm.Resource = res; + helm.Movable = false; + AddItem(helm); - DragonHelm helm = new DragonHelm(); - helm.Resource = res; - helm.Movable = false; - AddItem( helm ); + DragonChest chest = new DragonChest(); + chest.Resource = res; + chest.Movable = false; + AddItem(chest); - DragonChest chest = new DragonChest(); - chest.Resource = res; - chest.Movable = false; - AddItem( chest ); + DragonArms arms = new DragonArms(); + arms.Resource = res; + arms.Movable = false; + AddItem(arms); - DragonArms arms = new DragonArms(); - arms.Resource = res; - arms.Movable = false; - AddItem( arms ); + DragonGloves gloves = new DragonGloves(); + gloves.Resource = res; + gloves.Movable = false; + AddItem(gloves); - DragonGloves gloves = new DragonGloves(); - gloves.Resource = res; - gloves.Movable = false; - AddItem( gloves ); + DragonLegs legs = new DragonLegs(); + legs.Resource = res; + legs.Movable = false; + AddItem(legs); - DragonLegs legs = new DragonLegs(); - legs.Resource = res; - legs.Movable = false; - AddItem( legs ); + ChaosShield shield = new ChaosShield(); + shield.Movable = false; + AddItem(shield); - ChaosShield shield = new ChaosShield(); - shield.Movable = false; - AddItem( shield ); + AddItem(new Shirt()); + AddItem(new Boots()); - AddItem( new Shirt() ); - AddItem( new Boots() ); + int amount = Utility.RandomMinMax(1, 3); - int amount = Utility.RandomMinMax( 1, 3 ); + switch (res) + { + case CraftResource.BlackScales: + AddItem(new BlackScales(amount)); + break; + case CraftResource.RedScales: + AddItem(new RedScales(amount)); + break; + case CraftResource.BlueScales: + AddItem(new BlueScales(amount)); + break; + case CraftResource.YellowScales: + AddItem(new YellowScales(amount)); + break; + case CraftResource.GreenScales: + AddItem(new GreenScales(amount)); + break; + case CraftResource.WhiteScales: + AddItem(new WhiteScales(amount)); + break; + } - switch ( res ) - { - case CraftResource.BlackScales: AddItem( new BlackScales( amount ) ); break; - case CraftResource.RedScales: AddItem( new RedScales( amount ) ); break; - case CraftResource.BlueScales: AddItem( new BlueScales( amount ) ); break; - case CraftResource.YellowScales: AddItem( new YellowScales( amount ) ); break; - case CraftResource.GreenScales: AddItem( new GreenScales( amount ) ); break; - case CraftResource.WhiteScales: AddItem( new WhiteScales( amount ) ); break; - } + new SwampDragon().Rider = this; + } - new SwampDragon().Rider = this; - } + public ChaosDragoon(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x2CE; - } + public override string CorpseName => "a chaos dragoon corpse"; + public override string DefaultName => "a chaos dragoon"; - public override int GetDeathSound() - { - return 0x2CC; - } + public override bool HasBreath => true; + public override bool AutoDispel => true; + public override bool BardImmune => !Core.AOS; + public override bool CanRummageCorpses => true; + public override bool AlwaysMurderer => true; + public override bool ShowFameTitle => false; - public override int GetHurtSound() - { - return 0x2D1; - } + public override int GetIdleSound() + { + return 0x2CE; + } - public override int GetAttackSound() - { - return 0x2C8; - } + public override int GetDeathSound() + { + return 0x2CC; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - //AddLoot( LootPack.Gems ); - } + public override int GetHurtSound() + { + return 0x2D1; + } - public override bool HasBreath => true; - public override bool AutoDispel => true; - public override bool BardImmune => !Core.AOS; - public override bool CanRummageCorpses => true; - public override bool AlwaysMurderer => true; - public override bool ShowFameTitle => false; + public override int GetAttackSound() + { + return 0x2C8; + } - public override bool OnBeforeDeath() - { - IMount mount = Mount; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + //AddLoot( LootPack.Gems ); + } - if ( mount != null ) - mount.Rider = null; + public override bool OnBeforeDeath() + { + IMount mount = Mount; - return base.OnBeforeDeath(); - } + if (mount != null) + mount.Rider = null; - public override void AlterMeleeDamageTo( Mobile to, ref int damage ) - { - if ( to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || to is LesserHiryu || to is Daemon ) - damage *= 3; - } + return base.OnBeforeDeath(); + } - public ChaosDragoon( Serial serial ) : base( serial ) - { - } + public override void AlterMeleeDamageTo(Mobile to, ref int damage) + { + if (to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || + to is LesserHiryu || to is Daemon) + damage *= 3; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoonElite.cs b/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoonElite.cs index bd49ca618..1325fd71a 100644 --- a/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoonElite.cs +++ b/Scripts/Mobiles/Monsters/LBR/Jukas/ChaosDragoonElite.cs @@ -2,203 +2,254 @@ using Server.Items; namespace Server.Mobiles { - public class ChaosDragoonElite : BaseCreature - { - public override string CorpseName => "a chaos dragoon elite corpse"; - public override string DefaultName => "a chaos dragoon elite"; + public class ChaosDragoonElite : BaseCreature + { + [Constructible] + public ChaosDragoonElite() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.15, 0.4) + { + Body = 0x190; + Hue = Utility.RandomSkinHue(); - [Constructible] - public ChaosDragoonElite() - : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.15, 0.4) - { - Body = 0x190; - Hue = Utility.RandomSkinHue(); + SetStr(276, 350); + SetDex(66, 90); + SetInt(126, 150); - SetStr(276, 350); - SetDex(66, 90); - SetInt(126, 150); + SetHits(276, 350); - SetHits(276, 350); + SetDamage(29, 34); - SetDamage(29, 34); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType(ResistanceType.Physical, 100); - - /*SetResistance(ResistanceType.Physical, 45, 55); - SetResistance(ResistanceType.Fire, 15, 25); - SetResistance(ResistanceType.Cold, 50); - SetResistance(ResistanceType.Poison, 25, 35); - SetResistance(ResistanceType.Energy, 25, 35);*/ + /*SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 50); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35);*/ - SetSkill(SkillName.Tactics, 80.1, 100.0); - SetSkill(SkillName.MagicResist, 100.1, 110.0); - SetSkill(SkillName.Anatomy, 80.1, 100.0); - SetSkill(SkillName.Magery, 85.1, 100.0); - SetSkill(SkillName.EvalInt, 85.1, 100.0); - SetSkill(SkillName.Swords, 72.5, 95.0); - SetSkill(SkillName.Fencing, 85.1, 100); - SetSkill(SkillName.Macing, 85.1, 100); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.MagicResist, 100.1, 110.0); + SetSkill(SkillName.Anatomy, 80.1, 100.0); + SetSkill(SkillName.Magery, 85.1, 100.0); + SetSkill(SkillName.EvalInt, 85.1, 100.0); + SetSkill(SkillName.Swords, 72.5, 95.0); + SetSkill(SkillName.Fencing, 85.1, 100); + SetSkill(SkillName.Macing, 85.1, 100); - Fame = 8000; - Karma = -8000; + Fame = 8000; + Karma = -8000; - CraftResource res = CraftResource.None;; + CraftResource res = CraftResource.None; + ; - switch (Utility.Random(6)) - { - case 0: res = CraftResource.BlackScales; break; - case 1: res = CraftResource.RedScales; break; - case 2: res = CraftResource.BlueScales; break; - case 3: res = CraftResource.YellowScales; break; - case 4: res = CraftResource.GreenScales; break; - case 5: res = CraftResource.WhiteScales; break; - } + switch (Utility.Random(6)) + { + case 0: + res = CraftResource.BlackScales; + break; + case 1: + res = CraftResource.RedScales; + break; + case 2: + res = CraftResource.BlueScales; + break; + case 3: + res = CraftResource.YellowScales; + break; + case 4: + res = CraftResource.GreenScales; + break; + case 5: + res = CraftResource.WhiteScales; + break; + } - BaseWeapon melee = null; + BaseWeapon melee = null; - switch (Utility.Random(3)) - { - case 0: melee = new Kryss(); break; - case 1: melee = new Broadsword(); break; - case 2: melee = new Katana(); break; - } + switch (Utility.Random(3)) + { + case 0: + melee = new Kryss(); + break; + case 1: + melee = new Broadsword(); + break; + case 2: + melee = new Katana(); + break; + } - melee.Movable = false; - AddItem(melee); + melee.Movable = false; + AddItem(melee); - DragonChest Tunic = new DragonChest(); - Tunic.Resource = res; - Tunic.Movable = false; - AddItem(Tunic); + DragonChest Tunic = new DragonChest(); + Tunic.Resource = res; + Tunic.Movable = false; + AddItem(Tunic); - DragonLegs Legs = new DragonLegs(); - Legs.Resource = res; - Legs.Movable = false; - AddItem(Legs); + DragonLegs Legs = new DragonLegs(); + Legs.Resource = res; + Legs.Movable = false; + AddItem(Legs); - DragonArms Arms = new DragonArms(); - Arms.Resource = res; - Arms.Movable = false; - AddItem(Arms); + DragonArms Arms = new DragonArms(); + Arms.Resource = res; + Arms.Movable = false; + AddItem(Arms); - DragonGloves Gloves = new DragonGloves(); - Gloves.Resource = res; - Gloves.Movable = false; - AddItem(Gloves); + DragonGloves Gloves = new DragonGloves(); + Gloves.Resource = res; + Gloves.Movable = false; + AddItem(Gloves); - DragonHelm Helm = new DragonHelm(); - Helm.Resource = res; - Helm.Movable = false; - AddItem(Helm); + DragonHelm Helm = new DragonHelm(); + Helm.Resource = res; + Helm.Movable = false; + AddItem(Helm); - ChaosShield shield = new ChaosShield(); - shield.Movable = false; - AddItem(shield); + ChaosShield shield = new ChaosShield(); + shield.Movable = false; + AddItem(shield); - AddItem(new Boots(0x455)); - AddItem(new Shirt(Utility.RandomMetalHue())); + AddItem(new Boots(0x455)); + AddItem(new Shirt(Utility.RandomMetalHue())); - int amount = Utility.RandomMinMax(1, 3); + int amount = Utility.RandomMinMax(1, 3); - switch (res) - { - case CraftResource.BlackScales: AddItem(new BlackScales(amount)); break; - case CraftResource.RedScales: AddItem(new RedScales(amount)); break; - case CraftResource.BlueScales: AddItem(new BlueScales(amount)); break; - case CraftResource.YellowScales: AddItem(new YellowScales(amount)); break; - case CraftResource.GreenScales: AddItem(new GreenScales(amount)); break; - case CraftResource.WhiteScales: AddItem(new WhiteScales(amount)); break; - } - switch (Utility.Random(9)) - { - case 0: res = CraftResource.DullCopper; break; - case 1: res = CraftResource.ShadowIron; break; - case 2: res = CraftResource.Copper; break; - case 3: res = CraftResource.Bronze; break; - case 4: res = CraftResource.Gold; break; - case 5: res = CraftResource.Agapite; break; - case 6: res = CraftResource.Verite; break; - case 7: res = CraftResource.Valorite; break; - case 8: res = CraftResource.Iron; break; - } + switch (res) + { + case CraftResource.BlackScales: + AddItem(new BlackScales(amount)); + break; + case CraftResource.RedScales: + AddItem(new RedScales(amount)); + break; + case CraftResource.BlueScales: + AddItem(new BlueScales(amount)); + break; + case CraftResource.YellowScales: + AddItem(new YellowScales(amount)); + break; + case CraftResource.GreenScales: + AddItem(new GreenScales(amount)); + break; + case CraftResource.WhiteScales: + AddItem(new WhiteScales(amount)); + break; + } - SwampDragon mt = new SwampDragon(); - mt.HasBarding = true; - mt.BardingResource = res; - mt.BardingHP = mt.BardingMaxHP; - mt.Rider = this; - } + switch (Utility.Random(9)) + { + case 0: + res = CraftResource.DullCopper; + break; + case 1: + res = CraftResource.ShadowIron; + break; + case 2: + res = CraftResource.Copper; + break; + case 3: + res = CraftResource.Bronze; + break; + case 4: + res = CraftResource.Gold; + break; + case 5: + res = CraftResource.Agapite; + break; + case 6: + res = CraftResource.Verite; + break; + case 7: + res = CraftResource.Valorite; + break; + case 8: + res = CraftResource.Iron; + break; + } - public override int GetIdleSound() - { - return 0x2CE; - } + SwampDragon mt = new SwampDragon(); + mt.HasBarding = true; + mt.BardingResource = res; + mt.BardingHP = mt.BardingMaxHP; + mt.Rider = this; + } - public override int GetDeathSound() - { - return 0x2CC; - } + public ChaosDragoonElite(Serial serial) + : base(serial) + { + } - public override int GetHurtSound() - { - return 0x2D1; - } + public override string CorpseName => "a chaos dragoon elite corpse"; + public override string DefaultName => "a chaos dragoon elite"; - public override int GetAttackSound() - { - return 0x2C8; - } + public override bool HasBreath => true; + public override bool AutoDispel => true; + public override bool BardImmune => !Core.AOS; + public override bool CanRummageCorpses => true; + public override bool AlwaysMurderer => true; + public override bool ShowFameTitle => false; - public override void GenerateLoot() - { - AddLoot(LootPack.Rich); - AddLoot(LootPack.Gems); - } + public override int GetIdleSound() + { + return 0x2CE; + } - public override bool HasBreath => true; - public override bool AutoDispel => true; - public override bool BardImmune => !Core.AOS; - public override bool CanRummageCorpses => true; - public override bool AlwaysMurderer => true; - public override bool ShowFameTitle => false; + public override int GetDeathSound() + { + return 0x2CC; + } - public override bool OnBeforeDeath() - { - IMount mount = Mount; + public override int GetHurtSound() + { + return 0x2D1; + } - if ( mount != null ) - { - if ( mount is SwampDragon dragon ) - dragon.HasBarding = false; + public override int GetAttackSound() + { + return 0x2C8; + } - mount.Rider = null; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems); + } - return base.OnBeforeDeath(); - } + public override bool OnBeforeDeath() + { + IMount mount = Mount; - public override void AlterMeleeDamageTo(Mobile to, ref int damage) - { - if ( to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || to is LesserHiryu || to is Daemon ) - damage *= 3; - } + if (mount != null) + { + if (mount is SwampDragon dragon) + dragon.HasBarding = false; - public ChaosDragoonElite(Serial serial) - : base(serial) - { - } + mount.Rider = null; + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); - } + return base.OnBeforeDeath(); + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + public override void AlterMeleeDamageTo(Mobile to, ref int damage) + { + if (to is Dragon || to is WhiteWyrm || to is SwampDragon || to is Drake || to is Nightmare || to is Hiryu || + to is LesserHiryu || to is Daemon) + damage *= 3; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Jukas/JukaLord.cs b/Scripts/Mobiles/Monsters/LBR/Jukas/JukaLord.cs index 992fa73bb..727412237 100644 --- a/Scripts/Mobiles/Monsters/LBR/Jukas/JukaLord.cs +++ b/Scripts/Mobiles/Monsters/LBR/Jukas/JukaLord.cs @@ -1,125 +1,125 @@ -using System; using Server.Items; namespace Server.Mobiles { - public class JukaLord : BaseCreature - { - public override string CorpseName => "a jukan corpse"; - public override string DefaultName => "a juka lord"; + public class JukaLord : BaseCreature + { + [Constructible] + public JukaLord() : base(AIType.AI_Archer, FightMode.Closest, 10, 3, 0.2, 0.4) + { + Body = 766; - [Constructible] - public JukaLord() : base( AIType.AI_Archer, FightMode.Closest, 10, 3, 0.2, 0.4 ) - { - Body = 766; + SetStr(401, 500); + SetDex(81, 100); + SetInt(151, 200); - SetStr( 401, 500 ); - SetDex( 81, 100 ); - SetInt( 151, 200 ); + SetHits(241, 300); - SetHits( 241, 300 ); + SetDamage(10, 12); - SetDamage( 10, 12 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 45, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 20, 25); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 45, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 20, 25 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Anatomy, 90.1, 100.0); + SetSkill(SkillName.Archery, 95.1, 100.0); + SetSkill(SkillName.Healing, 80.1, 100.0); + SetSkill(SkillName.MagicResist, 120.1, 130.0); + SetSkill(SkillName.Swords, 90.1, 100.0); + SetSkill(SkillName.Tactics, 95.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.Anatomy, 90.1, 100.0 ); - SetSkill( SkillName.Archery, 95.1, 100.0 ); - SetSkill( SkillName.Healing, 80.1, 100.0 ); - SetSkill( SkillName.MagicResist, 120.1, 130.0 ); - SetSkill( SkillName.Swords, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 95.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + VirtualArmor = 28; - VirtualArmor = 28; + Container pack = new Backpack(); - Container pack = new Backpack(); + pack.DropItem(new Arrow(Utility.RandomMinMax(25, 35))); + pack.DropItem(new Arrow(Utility.RandomMinMax(25, 35))); + pack.DropItem(new Bandage(Utility.RandomMinMax(5, 15))); + pack.DropItem(new Bandage(Utility.RandomMinMax(5, 15))); + pack.DropItem(Loot.RandomGem()); + pack.DropItem(new ArcaneGem()); - pack.DropItem( new Arrow( Utility.RandomMinMax( 25, 35 ) ) ); - pack.DropItem( new Arrow( Utility.RandomMinMax( 25, 35 ) ) ); - pack.DropItem( new Bandage( Utility.RandomMinMax( 5, 15 ) ) ); - pack.DropItem( new Bandage( Utility.RandomMinMax( 5, 15 ) ) ); - pack.DropItem( Loot.RandomGem() ); - pack.DropItem( new ArcaneGem() ); + PackItem(pack); - PackItem( pack ); + AddItem(new JukaBow()); - AddItem( new JukaBow() ); + // TODO: Bandage self + } - // TODO: Bandage self - } + public JukaLord(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a jukan corpse"; + public override string DefaultName => "a juka lord"; - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( from != null && !willKill && amount > 5 && from.Player && 5 > Utility.Random( 100 ) ) - { - string[] toSay = { - "{0}!! You will have to do better than that!", - "{0}!! Prepare to meet your doom!", - "{0}!! My armies will crush you!", - "{0}!! You will pay for that!" - }; + public override bool AlwaysMurderer => true; + public override bool BardImmune => !Core.AOS; + public override bool CanRummageCorpses => true; + public override int Meat => 1; - Say( true, string.Format( toSay[Utility.Random( toSay.Length )], from.Name ) ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (from != null && !willKill && amount > 5 && from.Player && 5 > Utility.Random(100)) + { + string[] toSay = + { + "{0}!! You will have to do better than that!", + "{0}!! Prepare to meet your doom!", + "{0}!! My armies will crush you!", + "{0}!! You will pay for that!" + }; - public override int GetIdleSound() - { - return 0x262; - } + Say(true, string.Format(toSay[Utility.Random(toSay.Length)], from.Name)); + } - public override int GetAngerSound() - { - return 0x263; - } + base.OnDamage(amount, from, willKill); + } - public override int GetHurtSound() - { - return 0x1D0; - } + public override int GetIdleSound() + { + return 0x262; + } - public override int GetDeathSound() - { - return 0x28D; - } + public override int GetAngerSound() + { + return 0x263; + } - public override bool AlwaysMurderer => true; - public override bool BardImmune => !Core.AOS; - public override bool CanRummageCorpses => true; - public override int Meat => 1; + public override int GetHurtSound() + { + return 0x1D0; + } - public JukaLord( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 0x28D; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Jukas/JukaMage.cs b/Scripts/Mobiles/Monsters/LBR/Jukas/JukaMage.cs index 6450ec409..e68053647 100644 --- a/Scripts/Mobiles/Monsters/LBR/Jukas/JukaMage.cs +++ b/Scripts/Mobiles/Monsters/LBR/Jukas/JukaMage.cs @@ -1,207 +1,207 @@ using System; +using Server.Engines.Plants; using Server.Items; using Server.Spells; namespace Server.Mobiles { - public class JukaMage : BaseCreature - { - public override string CorpseName => "a jukan corpse"; - public override string DefaultName => "a juka mage"; + public class JukaMage : BaseCreature + { + private DateTime m_NextAbilityTime; - [Constructible] - public JukaMage() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 765; + [Constructible] + public JukaMage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 765; - SetStr( 201, 300 ); - SetDex( 71, 90 ); - SetInt( 451, 500 ); + SetStr(201, 300); + SetDex(71, 90); + SetInt(451, 500); - SetHits( 121, 180 ); + SetHits(121, 180); - SetDamage( 4, 10 ); + SetDamage(4, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 20, 30 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetResistance(ResistanceType.Physical, 20, 30); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 35, 45); - SetSkill( SkillName.Anatomy, 80.1, 90.0 ); - SetSkill( SkillName.EvalInt, 80.2, 100.0 ); - SetSkill( SkillName.Magery, 99.1, 100.0 ); - SetSkill( SkillName.Meditation, 80.2, 100.0 ); - SetSkill( SkillName.MagicResist, 140.1, 150.0 ); - SetSkill( SkillName.Tactics, 80.1, 90.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); + SetSkill(SkillName.Anatomy, 80.1, 90.0); + SetSkill(SkillName.EvalInt, 80.2, 100.0); + SetSkill(SkillName.Magery, 99.1, 100.0); + SetSkill(SkillName.Meditation, 80.2, 100.0); + SetSkill(SkillName.MagicResist, 140.1, 150.0); + SetSkill(SkillName.Tactics, 80.1, 90.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); - Fame = 15000; - Karma = -15000; + Fame = 15000; + Karma = -15000; - VirtualArmor = 16; + VirtualArmor = 16; - Container bag = new Bag(); + Container bag = new Bag(); - int count = Utility.RandomMinMax( 10, 20 ); + int count = Utility.RandomMinMax(10, 20); - for ( int i = 0; i < count; ++i ) - { - Item item = Loot.RandomReagent(); + for (int i = 0; i < count; ++i) + { + Item item = Loot.RandomReagent(); - if ( item == null ) - continue; + if (item == null) + continue; - if ( !bag.TryDropItem( this, item, false ) ) - item.Delete(); - } + if (!bag.TryDropItem(this, item, false)) + item.Delete(); + } - PackItem( bag ); + PackItem(bag); - PackItem( new ArcaneGem() ); + PackItem(new ArcaneGem()); - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(4) ); + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(4)); - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 2, 5 ) ); - } + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(2, 5)); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public JukaMage(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x1AC; - } + public override string CorpseName => "a jukan corpse"; + public override string DefaultName => "a juka mage"; - public override int GetAngerSound() - { - return 0x1CD; - } + public override bool AlwaysMurderer => true; + public override bool CanRummageCorpses => true; + public override int Meat => 1; - public override int GetHurtSound() - { - return 0x1D0; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.MedScrolls, 2); + } - public override int GetDeathSound() - { - return 0x28D; - } + public override int GetIdleSound() + { + return 0x1AC; + } - public override bool AlwaysMurderer => true; - public override bool CanRummageCorpses => true; - public override int Meat => 1; + public override int GetAngerSound() + { + return 0x1CD; + } - private DateTime m_NextAbilityTime; + public override int GetHurtSound() + { + return 0x1D0; + } - public override void OnThink() - { - if ( DateTime.UtcNow >= m_NextAbilityTime ) - { - JukaLord toBuff = null; + public override int GetDeathSound() + { + return 0x28D; + } - foreach ( Mobile m in GetMobilesInRange( 8 ) ) - { - if ( m is JukaLord lord && IsFriend( lord ) && lord.Combatant != null && CanBeBeneficial( lord ) && lord.CanBeginAction( typeof( JukaMage ) ) && InLOS( lord ) ) - { - toBuff = lord; - break; - } - } + public override void OnThink() + { + if (DateTime.UtcNow >= m_NextAbilityTime) + { + JukaLord toBuff = null; - if ( toBuff != null ) - { - if ( CanBeBeneficial( toBuff ) && toBuff.BeginAction( typeof( JukaMage ) ) ) - { - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 30, 60 ) ); + foreach (Mobile m in GetMobilesInRange(8)) + if (m is JukaLord lord && IsFriend(lord) && lord.Combatant != null && CanBeBeneficial(lord) && + lord.CanBeginAction(typeof(JukaMage)) && InLOS(lord)) + { + toBuff = lord; + break; + } - toBuff.Say( true, "Give me the power to destroy my enemies!" ); - Say( true, "Fight well my lord!" ); + if (toBuff != null) + { + if (CanBeBeneficial(toBuff) && toBuff.BeginAction(typeof(JukaMage))) + { + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(30, 60)); - DoBeneficial( toBuff ); + toBuff.Say(true, "Give me the power to destroy my enemies!"); + Say(true, "Fight well my lord!"); - object[] state = { toBuff, toBuff.HitsMaxSeed, toBuff.RawStr, toBuff.RawDex }; + DoBeneficial(toBuff); - SpellHelper.Turn( this, toBuff ); + object[] state = { toBuff, toBuff.HitsMaxSeed, toBuff.RawStr, toBuff.RawDex }; - int toScale = toBuff.HitsMaxSeed; + SpellHelper.Turn(this, toBuff); - if ( toScale > 0 ) - { - toBuff.HitsMaxSeed += AOS.Scale( toScale, 75 ); - toBuff.Hits += AOS.Scale( toScale, 75 ); - } + int toScale = toBuff.HitsMaxSeed; - toScale = toBuff.RawStr; + if (toScale > 0) + { + toBuff.HitsMaxSeed += AOS.Scale(toScale, 75); + toBuff.Hits += AOS.Scale(toScale, 75); + } - if ( toScale > 0 ) - toBuff.RawStr += AOS.Scale( toScale, 50 ); + toScale = toBuff.RawStr; - toScale = toBuff.RawDex; + if (toScale > 0) + toBuff.RawStr += AOS.Scale(toScale, 50); - if ( toScale > 0 ) - { - toBuff.RawDex += AOS.Scale( toScale, 50 ); - toBuff.Stam += AOS.Scale( toScale, 50 ); - } + toScale = toBuff.RawDex; - toBuff.Hits = toBuff.Hits; - toBuff.Stam = toBuff.Stam; + if (toScale > 0) + { + toBuff.RawDex += AOS.Scale(toScale, 50); + toBuff.Stam += AOS.Scale(toScale, 50); + } - toBuff.FixedParticles( 0x375A, 10, 15, 5017, EffectLayer.Waist ); - toBuff.PlaySound( 0x1EE ); + toBuff.Hits = toBuff.Hits; + toBuff.Stam = toBuff.Stam; - Timer.DelayCall( TimeSpan.FromSeconds( 20.0 ), new TimerStateCallback( Unbuff ), state ); - } - } - else - { - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 2, 5 ) ); - } - } + toBuff.FixedParticles(0x375A, 10, 15, 5017, EffectLayer.Waist); + toBuff.PlaySound(0x1EE); - base.OnThink(); - } + Timer.DelayCall(TimeSpan.FromSeconds(20.0), new TimerStateCallback(Unbuff), state); + } + } + else + { + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(2, 5)); + } + } - private void Unbuff( object state ) - { - object[] states = (object[])state; + base.OnThink(); + } - JukaLord toDebuff = (JukaLord)states[0]; + private void Unbuff(object state) + { + object[] states = (object[])state; - toDebuff.EndAction( typeof( JukaMage ) ); + JukaLord toDebuff = (JukaLord)states[0]; - if ( toDebuff.Deleted ) - return; + toDebuff.EndAction(typeof(JukaMage)); - toDebuff.HitsMaxSeed = (int)states[1]; - toDebuff.RawStr = (int)states[2]; - toDebuff.RawDex = (int)states[3]; + if (toDebuff.Deleted) + return; - toDebuff.Hits = toDebuff.Hits; - toDebuff.Stam = toDebuff.Stam; - } + toDebuff.HitsMaxSeed = (int)states[1]; + toDebuff.RawStr = (int)states[2]; + toDebuff.RawDex = (int)states[3]; - public JukaMage( Serial serial ) : base( serial ) - { - } + toDebuff.Hits = toDebuff.Hits; + toDebuff.Stam = toDebuff.Stam; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Jukas/JukaWarrior.cs b/Scripts/Mobiles/Monsters/LBR/Jukas/JukaWarrior.cs index 77539e0c1..5ba4e0be6 100644 --- a/Scripts/Mobiles/Monsters/LBR/Jukas/JukaWarrior.cs +++ b/Scripts/Mobiles/Monsters/LBR/Jukas/JukaWarrior.cs @@ -3,124 +3,124 @@ using Server.Items; namespace Server.Mobiles { - public class JukaWarrior : BaseCreature - { - public override string CorpseName => "a jukan corpse"; - public override string DefaultName => "a juka warrior"; + public class JukaWarrior : BaseCreature + { + [Constructible] + public JukaWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 764; - [Constructible] - public JukaWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 764; + SetStr(251, 350); + SetDex(61, 80); + SetInt(101, 150); - SetStr( 251, 350 ); - SetDex( 61, 80 ); - SetInt( 101, 150 ); + SetHits(151, 210); - SetHits( 151, 210 ); + SetDamage(7, 9); - SetDamage( 7, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Anatomy, 80.1, 90.0); + SetSkill(SkillName.Fencing, 80.1, 90.0); + SetSkill(SkillName.Macing, 80.1, 90.0); + SetSkill(SkillName.MagicResist, 120.1, 130.0); + SetSkill(SkillName.Swords, 80.1, 90.0); + SetSkill(SkillName.Tactics, 80.1, 90.0); + SetSkill(SkillName.Wrestling, 80.1, 90.0); - SetSkill( SkillName.Anatomy, 80.1, 90.0 ); - SetSkill( SkillName.Fencing, 80.1, 90.0 ); - SetSkill( SkillName.Macing, 80.1, 90.0 ); - SetSkill( SkillName.MagicResist, 120.1, 130.0 ); - SetSkill( SkillName.Swords, 80.1, 90.0 ); - SetSkill( SkillName.Tactics, 80.1, 90.0 ); - SetSkill( SkillName.Wrestling, 80.1, 90.0 ); + Fame = 10000; + Karma = -10000; - Fame = 10000; - Karma = -10000; + VirtualArmor = 22; - VirtualArmor = 22; + if (Utility.RandomDouble() < 0.1) + PackItem(new ArcaneGem()); + } - if ( Utility.RandomDouble() < 0.1 ) - PackItem( new ArcaneGem() ); - } + public JukaWarrior(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Gems, 1 ); - } + public override string CorpseName => "a jukan corpse"; + public override string DefaultName => "a juka warrior"; - public override int GetIdleSound() - { - return 0x1AC; - } + public override bool AlwaysMurderer => true; + public override bool CanRummageCorpses => true; + public override int Meat => 1; - public override int GetAngerSound() - { - return 0x1CD; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.Gems, 1); + } - public override int GetHurtSound() - { - return 0x1D0; - } + public override int GetIdleSound() + { + return 0x1AC; + } - public override int GetDeathSound() - { - return 0x28D; - } + public override int GetAngerSound() + { + return 0x1CD; + } - public override bool AlwaysMurderer => true; - public override bool CanRummageCorpses => true; - public override int Meat => 1; + public override int GetHurtSound() + { + return 0x1D0; + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override int GetDeathSound() + { + return 0x28D; + } - if ( 0.2 < Utility.RandomDouble() ) - return; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - switch ( Utility.Random( 3 ) ) - { - case 0: - { - defender.SendLocalizedMessage( 1004014 ); // You have been stunned! - defender.Freeze( TimeSpan.FromSeconds( 4.0 ) ); - break; - } - case 1: - { - defender.SendAsciiMessage( "You have been hit by a paralyzing blow!" ); - defender.Freeze( TimeSpan.FromSeconds( 3.0 ) ); - break; - } - case 2: - { - AOS.Damage( defender, this, Utility.Random( 10, 5 ), 100, 0, 0, 0, 0 ); - defender.SendAsciiMessage( "You have been hit by a critical strike!" ); - break; - } - } - } + if (0.2 < Utility.RandomDouble()) + return; - public JukaWarrior( Serial serial ) : base( serial ) - { - } + switch (Utility.Random(3)) + { + case 0: + { + defender.SendLocalizedMessage(1004014); // You have been stunned! + defender.Freeze(TimeSpan.FromSeconds(4.0)); + break; + } + case 1: + { + defender.SendAsciiMessage("You have been hit by a paralyzing blow!"); + defender.Freeze(TimeSpan.FromSeconds(3.0)); + break; + } + case 2: + { + AOS.Damage(defender, this, Utility.Random(10, 5), 100, 0, 0, 0, 0); + defender.SendAsciiMessage("You have been hit by a critical strike!"); + break; + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Meers/EnragedCreatures.cs b/Scripts/Mobiles/Monsters/LBR/Meers/EnragedCreatures.cs index cf80ed9c5..030aec022 100644 --- a/Scripts/Mobiles/Monsters/LBR/Meers/EnragedCreatures.cs +++ b/Scripts/Mobiles/Monsters/LBR/Meers/EnragedCreatures.cs @@ -2,285 +2,284 @@ using Server.Network; namespace Server.Mobiles { - public class EnragedRabbit : BaseEnraged - { - public override string CorpseName => "a hare corpse"; - public override string DefaultName => "a rabbit"; + public class EnragedRabbit : BaseEnraged + { + public EnragedRabbit(Mobile summoner) : base(summoner) + { + Body = 0xcd; + } - public EnragedRabbit( Mobile summoner ) : base( summoner ) - { - Body = 0xcd; - } + public EnragedRabbit(Serial serial) : base(serial) + { + } - public override int GetAttackSound() - { - return 0xC9; - } + public override string CorpseName => "a hare corpse"; + public override string DefaultName => "a rabbit"; - public override int GetHurtSound() - { - return 0xCA; - } + public override int GetAttackSound() + { + return 0xC9; + } - public override int GetDeathSound() - { - return 0xCB; - } + public override int GetHurtSound() + { + return 0xCA; + } - public EnragedRabbit( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 0xCB; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class EnragedHart : BaseEnraged - { - public override string CorpseName => "a deer corpse"; - public override string DefaultName => "a great hart"; + public class EnragedHart : BaseEnraged + { + public EnragedHart(Mobile summoner) : base(summoner) + { + Body = 0xea; + } - public EnragedHart( Mobile summoner ) : base( summoner ) - { - Body = 0xea; - } + public EnragedHart(Serial serial) : base(serial) + { + } - public override int GetAttackSound() - { - return 0x82; - } + public override string CorpseName => "a deer corpse"; + public override string DefaultName => "a great hart"; - public override int GetHurtSound() - { - return 0x83; - } + public override int GetAttackSound() + { + return 0x82; + } - public override int GetDeathSound() - { - return 0x84; - } + public override int GetHurtSound() + { + return 0x83; + } - public EnragedHart( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 0x84; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class EnragedHind : BaseEnraged - { - public override string CorpseName => "a deer corpse"; - public override string DefaultName => "a hind"; + public class EnragedHind : BaseEnraged + { + public EnragedHind(Mobile summoner) : base(summoner) + { + Body = 0xed; + } - public EnragedHind( Mobile summoner ) : base( summoner ) - { - Body = 0xed; - } - public override int GetAttackSound() - { - return 0x82; - } + public EnragedHind(Serial serial) : base(serial) + { + } - public override int GetHurtSound() - { - return 0x83; - } + public override string CorpseName => "a deer corpse"; + public override string DefaultName => "a hind"; - public override int GetDeathSound() - { - return 0x84; - } + public override int GetAttackSound() + { + return 0x82; + } - public EnragedHind( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x83; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetDeathSound() + { + return 0x84; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public class EnragedBlackBear : BaseEnraged - { - public override string CorpseName => "a bear corpse"; - public override string DefaultName => "a black bear"; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public EnragedBlackBear( Mobile summoner ) : base( summoner ) - { - Body = 0xd3; - BaseSoundID = 0xa3; - } - public EnragedBlackBear( Serial serial ) : base( serial ) - { - } + public class EnragedBlackBear : BaseEnraged + { + public EnragedBlackBear(Mobile summoner) : base(summoner) + { + Body = 0xd3; + BaseSoundID = 0xa3; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public EnragedBlackBear(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override string CorpseName => "a bear corpse"; + public override string DefaultName => "a black bear"; - public class EnragedEagle : BaseEnraged - { - public override string CorpseName => "an eagle corpse"; - public override string DefaultName => "an eagle"; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public EnragedEagle( Mobile summoner ) : base( summoner ) - { - Body = 0x5; - BaseSoundID = 0x2ee; - } - public EnragedEagle( Serial serial ) : base( serial ) - { - } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public class BaseEnraged : BaseCreature - { - public BaseEnraged( Mobile summoner ) - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SetStr( 50, 200 ); - SetDex( 50, 200 ); - SetHits( 50, 200 ); - SetStam( 50, 200 ); + public class EnragedEagle : BaseEnraged + { + public EnragedEagle(Mobile summoner) : base(summoner) + { + Body = 0x5; + BaseSoundID = 0x2ee; + } - /* - On OSI, all stats are random 50-200, but - str is never less than hits, and dex is never - less than stam. - */ + public EnragedEagle(Serial serial) : base(serial) + { + } - if ( Str < Hits ) - Str = Hits; - if ( Dex < Stam ) - Dex = Stam; + public override string CorpseName => "an eagle corpse"; + public override string DefaultName => "an eagle"; - Karma = -1000; - Tamable = false; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - SummonMaster = summoner; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public override void OnThink() - { + public class BaseEnraged : BaseCreature + { + public BaseEnraged(Mobile summoner) + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SetStr(50, 200); + SetDex(50, 200); + SetHits(50, 200); + SetStam(50, 200); - if ( SummonMaster == null || SummonMaster.Deleted ) - { - Delete(); - } + /* + On OSI, all stats are random 50-200, but + str is never less than hits, and dex is never + less than stam. + */ - /* - On OSI, without combatant, they behave as if they have been - given "come" command, ie they wander towards their summoner, - but never actually "follow". - */ + if (Str < Hits) + Str = Hits; + if (Dex < Stam) + Dex = Stam; - else if ( !Combat( this )) - { - AIObject?.MoveTo( SummonMaster, false , 5 ); - } + Karma = -1000; + Tamable = false; - /* - On OSI, if the summon attacks a mobile, the summoner meer also - attacks them, regardless of karma, etc. as long as the combatant - is a player or controlled/summoned, and the summoner is not already - engaged in combat. - */ + SummonMaster = summoner; + } - else if ( !Combat( SummonMaster )) - { - if ( Combatant.Player || ( Combatant is BaseCreature bc && ( bc.Controlled || bc.SummonMaster != null ))) - { - SummonMaster.Combatant = Combatant; - } - } - else - { - base.OnThink(); - } - } + public BaseEnraged(Serial serial) : base(serial) + { + } - private bool Combat( Mobile mobile ) - { - Mobile combatant = mobile.Combatant; - if ( combatant == null || combatant.Deleted || combatant.IsDeadBondedPet || !combatant.Alive ) - return false; + public override void OnThink() + { + if (SummonMaster == null || SummonMaster.Deleted) + { + Delete(); + } + /* + On OSI, without combatant, they behave as if they have been + given "come" command, ie they wander towards their summoner, + but never actually "follow". + */ - return true; - } + else if (!Combat(this)) + { + AIObject?.MoveTo(SummonMaster, false, 5); + } + /* + On OSI, if the summon attacks a mobile, the summoner meer also + attacks them, regardless of karma, etc. as long as the combatant + is a player or controlled/summoned, and the summoner is not already + engaged in combat. + */ - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1060768, from.NetState ); // enraged - } + else if (!Combat(SummonMaster)) + { + if (Combatant.Player || Combatant is BaseCreature bc && (bc.Controlled || bc.SummonMaster != null)) + SummonMaster.Combatant = Combatant; + } + else + { + base.OnThink(); + } + } - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - list.Add( 1060768 ); // enraged - } + private bool Combat(Mobile mobile) + { + Mobile combatant = mobile.Combatant; + if (combatant == null || combatant.Deleted || combatant.IsDeadBondedPet || !combatant.Alive) + return false; - public BaseEnraged( Serial serial ) : base( serial ) - { - } + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1060768, from.NetState); // enraged + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); + list.Add(1060768); // enraged + } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Meers/MeerCaptain.cs b/Scripts/Mobiles/Monsters/LBR/Meers/MeerCaptain.cs index 4dab034eb..352163668 100644 --- a/Scripts/Mobiles/Monsters/LBR/Meers/MeerCaptain.cs +++ b/Scripts/Mobiles/Monsters/LBR/Meers/MeerCaptain.cs @@ -5,163 +5,174 @@ using Server.Spells; namespace Server.Mobiles { - public class MeerCaptain : BaseCreature - { - public override string CorpseName => "a meer corpse"; - public override string DefaultName => "a meer captain"; + public class MeerCaptain : BaseCreature + { + private DateTime m_NextAbilityTime; - [Constructible] - public MeerCaptain() : base( AIType.AI_Archer, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 773; + [Constructible] + public MeerCaptain() : base(AIType.AI_Archer, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 773; - SetStr( 96, 110 ); - SetDex( 186, 200 ); - SetInt( 96, 110 ); + SetStr(96, 110); + SetDex(186, 200); + SetInt(96, 110); - SetHits( 58, 66 ); + SetHits(58, 66); - SetDamage( 5, 15 ); + SetDamage(5, 15); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 35, 45 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 35, 45); + SetResistance(ResistanceType.Energy, 35, 45); - SetSkill( SkillName.Archery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 91.0, 100.0 ); - SetSkill( SkillName.Swords, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 91.0, 100.0 ); - SetSkill( SkillName.Wrestling, 80.9, 89.9 ); + SetSkill(SkillName.Archery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 91.0, 100.0); + SetSkill(SkillName.Swords, 90.1, 100.0); + SetSkill(SkillName.Tactics, 91.0, 100.0); + SetSkill(SkillName.Wrestling, 80.9, 89.9); - Fame = 2000; - Karma = 5000; + Fame = 2000; + Karma = 5000; - VirtualArmor = 28; + VirtualArmor = 28; - Container pack = new Backpack(); + Container pack = new Backpack(); - pack.DropItem( new Bolt( Utility.RandomMinMax( 10, 20 ) ) ); - pack.DropItem( new Bolt( Utility.RandomMinMax( 10, 20 ) ) ); + pack.DropItem(new Bolt(Utility.RandomMinMax(10, 20))); + pack.DropItem(new Bolt(Utility.RandomMinMax(10, 20))); - switch ( Utility.Random( 6 ) ) - { - case 0: pack.DropItem( new Broadsword() ); break; - case 1: pack.DropItem( new Cutlass() ); break; - case 2: pack.DropItem( new Katana() ); break; - case 3: pack.DropItem( new Longsword() ); break; - case 4: pack.DropItem( new Scimitar() ); break; - case 5: pack.DropItem( new VikingSword() ); break; - } + switch (Utility.Random(6)) + { + case 0: + pack.DropItem(new Broadsword()); + break; + case 1: + pack.DropItem(new Cutlass()); + break; + case 2: + pack.DropItem(new Katana()); + break; + case 3: + pack.DropItem(new Longsword()); + break; + case 4: + pack.DropItem(new Scimitar()); + break; + case 5: + pack.DropItem(new VikingSword()); + break; + } - Container bag = new Bag(); + Container bag = new Bag(); - int count = Utility.RandomMinMax( 10, 20 ); + int count = Utility.RandomMinMax(10, 20); - for ( int i = 0; i < count; ++i ) - { - Item item = Loot.RandomReagent(); + for (int i = 0; i < count; ++i) + { + Item item = Loot.RandomReagent(); - if ( item == null ) - continue; + if (item == null) + continue; - if ( !bag.TryDropItem( this, item, false ) ) - item.Delete(); - } + if (!bag.TryDropItem(this, item, false)) + item.Delete(); + } - pack.DropItem( bag ); + pack.DropItem(bag); - AddItem( new Crossbow() ); - PackItem( pack ); + AddItem(new Crossbow()); + PackItem(pack); - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 2, 5 ) ); - } + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(2, 5)); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public MeerCaptain(Serial serial) : base(serial) + { + } - public override bool BardImmune => !Core.AOS; - public override bool CanRummageCorpses => true; + public override string CorpseName => "a meer corpse"; + public override string DefaultName => "a meer captain"; - public override bool InitialInnocent => true; + public override bool BardImmune => !Core.AOS; + public override bool CanRummageCorpses => true; - public override int GetHurtSound() - { - return 0x14D; - } + public override bool InitialInnocent => true; - public override int GetDeathSound() - { - return 0x314; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override int GetAttackSound() - { - return 0x75; - } + public override int GetHurtSound() + { + return 0x14D; + } - private DateTime m_NextAbilityTime; + public override int GetDeathSound() + { + return 0x314; + } - public override void OnThink() - { - if ( Combatant != null && MagicDamageAbsorb < 1 ) - { - MagicDamageAbsorb = Utility.RandomMinMax( 5, 7 ); - FixedParticles( 0x375A, 10, 15, 5037, EffectLayer.Waist ); - PlaySound( 0x1E9 ); - } + public override int GetAttackSound() + { + return 0x75; + } - if ( DateTime.UtcNow >= m_NextAbilityTime ) - { - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 10, 15 ) ); + public override void OnThink() + { + if (Combatant != null && MagicDamageAbsorb < 1) + { + MagicDamageAbsorb = Utility.RandomMinMax(5, 7); + FixedParticles(0x375A, 10, 15, 5037, EffectLayer.Waist); + PlaySound(0x1E9); + } - ArrayList list = new ArrayList(); + if (DateTime.UtcNow >= m_NextAbilityTime) + { + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(10, 15)); - foreach ( Mobile m in GetMobilesInRange( 8 ) ) - { - if ( m is MeerWarrior && IsFriend( m ) && CanBeBeneficial( m ) && m.Hits < m.HitsMax && !m.Poisoned && !MortalStrike.IsWounded( m ) ) - list.Add( m ); - } + ArrayList list = new ArrayList(); - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; + foreach (Mobile m in GetMobilesInRange(8)) + if (m is MeerWarrior && IsFriend(m) && CanBeBeneficial(m) && m.Hits < m.HitsMax && !m.Poisoned && + !MortalStrike.IsWounded(m)) + list.Add(m); - DoBeneficial( m ); + for (int i = 0; i < list.Count; ++i) + { + Mobile m = (Mobile)list[i]; - int toHeal = Utility.RandomMinMax( 20, 30 ); + DoBeneficial(m); - SpellHelper.Turn( this, m ); + int toHeal = Utility.RandomMinMax(20, 30); - m.Heal( toHeal, this ); + SpellHelper.Turn(this, m); - m.FixedParticles( 0x376A, 9, 32, 5030, EffectLayer.Waist ); - m.PlaySound( 0x202 ); - } - } + m.Heal(toHeal, this); - base.OnThink(); - } + m.FixedParticles(0x376A, 9, 32, 5030, EffectLayer.Waist); + m.PlaySound(0x202); + } + } - public MeerCaptain( Serial serial ) : base( serial ) - { - } + base.OnThink(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Meers/MeerEternal.cs b/Scripts/Mobiles/Monsters/LBR/Meers/MeerEternal.cs index 0af3560ae..0e7dc011b 100644 --- a/Scripts/Mobiles/Monsters/LBR/Meers/MeerEternal.cs +++ b/Scripts/Mobiles/Monsters/LBR/Meers/MeerEternal.cs @@ -3,212 +3,219 @@ using System.Collections; namespace Server.Mobiles { - public class MeerEternal : BaseCreature - { - public override string CorpseName => "a meer's corpse"; - public override string DefaultName => "a meer eternal"; + public class MeerEternal : BaseCreature + { + private DateTime m_NextAbilityTime; - [Constructible] - public MeerEternal() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 772; + [Constructible] + public MeerEternal() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 772; - SetStr( 416, 505 ); - SetDex( 146, 165 ); - SetInt( 566, 655 ); + SetStr(416, 505); + SetDex(146, 165); + SetInt(566, 655); - SetHits( 250, 303 ); + SetHits(250, 303); - SetDamage( 11, 13 ); + SetDamage(11, 13); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 45, 55 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 45, 55); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 150.5, 200.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 150.5, 200.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - Fame = 18000; - Karma = 18000; + Fame = 18000; + Karma = 18000; - VirtualArmor = 34; + VirtualArmor = 34; - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 2, 5 ) ); - } + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(2, 5)); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); - AddLoot( LootPack.HighScrolls, 2 ); - } + public MeerEternal(Serial serial) : base(serial) + { + } - public override bool AutoDispel => true; - public override bool BardImmune => !Core.AOS; - public override bool CanRummageCorpses => true; - public override Poison PoisonImmune => Poison.Lethal; - public override int TreasureMapLevel => Core.AOS ? 5 : 4; + public override string CorpseName => "a meer's corpse"; + public override string DefaultName => "a meer eternal"; - public override bool InitialInnocent => true; + public override bool AutoDispel => true; + public override bool BardImmune => !Core.AOS; + public override bool CanRummageCorpses => true; + public override Poison PoisonImmune => Poison.Lethal; + public override int TreasureMapLevel => Core.AOS ? 5 : 4; - public override int GetHurtSound() - { - return 0x167; - } + public override bool InitialInnocent => true; - public override int GetDeathSound() - { - return 0xBC; - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.MedScrolls, 2); + AddLoot(LootPack.HighScrolls, 2); + } - public override int GetAttackSound() - { - return 0x28B; - } + public override int GetHurtSound() + { + return 0x167; + } - private DateTime m_NextAbilityTime; + public override int GetDeathSound() + { + return 0xBC; + } - private void DoAreaLeech() - { - m_NextAbilityTime += TimeSpan.FromSeconds( 2.5 ); + public override int GetAttackSound() + { + return 0x28B; + } - Say( true, "Beware, mortals! You have provoked my wrath!" ); - FixedParticles( 0x376A, 10, 10, 9537, 33, 0, EffectLayer.Waist ); + private void DoAreaLeech() + { + m_NextAbilityTime += TimeSpan.FromSeconds(2.5); - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), DoAreaLeech_Finish ); - } + Say(true, "Beware, mortals! You have provoked my wrath!"); + FixedParticles(0x376A, 10, 10, 9537, 33, 0, EffectLayer.Waist); - private void DoAreaLeech_Finish() - { - ArrayList list = new ArrayList(); + Timer.DelayCall(TimeSpan.FromSeconds(5.0), DoAreaLeech_Finish); + } - foreach ( Mobile m in GetMobilesInRange( 6 ) ) - { - if ( CanBeHarmful( m ) && IsEnemy( m ) ) - list.Add( m ); - } + private void DoAreaLeech_Finish() + { + ArrayList list = new ArrayList(); - if ( list.Count == 0 ) - { - Say( true, "Bah! You have escaped my grasp this time, mortal!" ); - } - else - { - double scalar; + foreach (Mobile m in GetMobilesInRange(6)) + if (CanBeHarmful(m) && IsEnemy(m)) + list.Add(m); - if ( list.Count == 1 ) - scalar = 0.75; - else if ( list.Count == 2 ) - scalar = 0.50; - else - scalar = 0.25; + if (list.Count == 0) + { + Say(true, "Bah! You have escaped my grasp this time, mortal!"); + } + else + { + double scalar; - for ( int i = 0; i < list.Count; ++i ) - { - Mobile m = (Mobile)list[i]; + if (list.Count == 1) + scalar = 0.75; + else if (list.Count == 2) + scalar = 0.50; + else + scalar = 0.25; - int damage = (int)(m.Hits * scalar); + for (int i = 0; i < list.Count; ++i) + { + Mobile m = (Mobile)list[i]; - damage += Utility.RandomMinMax( -5, 5 ); + int damage = (int)(m.Hits * scalar); - if ( damage < 1 ) - damage = 1; + damage += Utility.RandomMinMax(-5, 5); - m.MovingParticles( this, 0x36F4, 1, 0, false, false, 32, 0, 9535, 1, 0, (EffectLayer)255, 0x100 ); - m.MovingParticles( this, 0x0001, 1, 0, false, true, 32, 0, 9535, 9536, 0, (EffectLayer)255, 0 ); + if (damage < 1) + damage = 1; - DoHarmful( m ); - Hits += AOS.Damage( m, this, damage, 100, 0, 0, 0, 0 ); - } + m.MovingParticles(this, 0x36F4, 1, 0, false, false, 32, 0, 9535, 1, 0, (EffectLayer)255, 0x100); + m.MovingParticles(this, 0x0001, 1, 0, false, true, 32, 0, 9535, 9536, 0, (EffectLayer)255, 0); - Say( true, "If I cannot cleanse thy soul, I will destroy it!" ); - } - } + DoHarmful(m); + Hits += AOS.Damage(m, this, damage, 100, 0, 0, 0, 0); + } - private void DoFocusedLeech( Mobile combatant, string message ) - { - Say( true, message ); + Say(true, "If I cannot cleanse thy soul, I will destroy it!"); + } + } - Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), new TimerStateCallback( DoFocusedLeech_Stage1 ), combatant ); - } + private void DoFocusedLeech(Mobile combatant, string message) + { + Say(true, message); - private void DoFocusedLeech_Stage1( object state ) - { - Mobile combatant = (Mobile)state; + Timer.DelayCall(TimeSpan.FromSeconds(0.5), new TimerStateCallback(DoFocusedLeech_Stage1), combatant); + } - if ( CanBeHarmful( combatant ) ) - { - MovingParticles( combatant, 0x36FA, 1, 0, false, false, 1108, 0, 9533, 1, 0, (EffectLayer)255, 0x100 ); - MovingParticles( combatant, 0x0001, 1, 0, false, true, 1108, 0, 9533, 9534, 0, (EffectLayer)255, 0 ); - PlaySound( 0x1FB ); + private void DoFocusedLeech_Stage1(object state) + { + Mobile combatant = (Mobile)state; - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( DoFocusedLeech_Stage2 ), combatant ); - } - } + if (CanBeHarmful(combatant)) + { + MovingParticles(combatant, 0x36FA, 1, 0, false, false, 1108, 0, 9533, 1, 0, (EffectLayer)255, 0x100); + MovingParticles(combatant, 0x0001, 1, 0, false, true, 1108, 0, 9533, 9534, 0, (EffectLayer)255, 0); + PlaySound(0x1FB); - private void DoFocusedLeech_Stage2( object state ) - { - Mobile combatant = (Mobile)state; + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(DoFocusedLeech_Stage2), combatant); + } + } - if ( CanBeHarmful( combatant ) ) - { - combatant.MovingParticles( this, 0x36F4, 1, 0, false, false, 32, 0, 9535, 1, 0, (EffectLayer)255, 0x100 ); - combatant.MovingParticles( this, 0x0001, 1, 0, false, true, 32, 0, 9535, 9536, 0, (EffectLayer)255, 0 ); + private void DoFocusedLeech_Stage2(object state) + { + Mobile combatant = (Mobile)state; - PlaySound( 0x209 ); - DoHarmful( combatant ); - Hits += AOS.Damage( combatant, this, Utility.RandomMinMax( 30, 40 ) - (Core.AOS ? 0 : 10), 100, 0, 0, 0, 0 ); - } - } + if (CanBeHarmful(combatant)) + { + combatant.MovingParticles(this, 0x36F4, 1, 0, false, false, 32, 0, 9535, 1, 0, (EffectLayer)255, 0x100); + combatant.MovingParticles(this, 0x0001, 1, 0, false, true, 32, 0, 9535, 9536, 0, (EffectLayer)255, 0); - public override void OnThink() - { - if ( DateTime.UtcNow >= m_NextAbilityTime ) - { - Mobile combatant = Combatant; + PlaySound(0x209); + DoHarmful(combatant); + Hits += AOS.Damage(combatant, this, Utility.RandomMinMax(30, 40) - (Core.AOS ? 0 : 10), 100, 0, 0, 0, 0); + } + } - if ( combatant != null && combatant.Map == Map && combatant.InRange( this, 12 ) ) - { - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 10, 15 ) ); + public override void OnThink() + { + if (DateTime.UtcNow >= m_NextAbilityTime) + { + Mobile combatant = Combatant; - int ability = Utility.Random( 4 ); + if (combatant != null && combatant.Map == Map && combatant.InRange(this, 12)) + { + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(10, 15)); - switch ( ability ) - { - case 0: DoFocusedLeech( combatant, "Thine essence will fill my withering body with strength!" ); break; - case 1: DoFocusedLeech( combatant, "I rebuke thee, worm, and cleanse thy vile spirit of its tainted blood!" ); break; - case 2: DoFocusedLeech( combatant, "I devour your life's essence to strengthen my resolve!" ); break; - case 3: DoAreaLeech(); break; - // TODO: Resurrect ability - } - } - } + int ability = Utility.Random(4); - base.OnThink(); - } + switch (ability) + { + case 0: + DoFocusedLeech(combatant, "Thine essence will fill my withering body with strength!"); + break; + case 1: + DoFocusedLeech(combatant, + "I rebuke thee, worm, and cleanse thy vile spirit of its tainted blood!"); + break; + case 2: + DoFocusedLeech(combatant, "I devour your life's essence to strengthen my resolve!"); + break; + case 3: + DoAreaLeech(); + break; + // TODO: Resurrect ability + } + } + } - public MeerEternal( Serial serial ) : base( serial ) - { - } + base.OnThink(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Meers/MeerMage.cs b/Scripts/Mobiles/Monsters/LBR/Meers/MeerMage.cs index 018bb3226..6ec494756 100644 --- a/Scripts/Mobiles/Monsters/LBR/Meers/MeerMage.cs +++ b/Scripts/Mobiles/Monsters/LBR/Meers/MeerMage.cs @@ -1,218 +1,229 @@ using System; using System.Collections; using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class MeerMage : BaseCreature - { - public override string CorpseName => "a meer's corpse"; - public override string DefaultName => "a meer mage"; + public class MeerMage : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public MeerMage() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 770; + private DateTime m_NextAbilityTime; - SetStr( 171, 200 ); - SetDex( 126, 145 ); - SetInt( 276, 305 ); + [Constructible] + public MeerMage() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 770; - SetHits( 103, 120 ); + SetStr(171, 200); + SetDex(126, 145); + SetInt(276, 305); - SetDamage( 24, 26 ); + SetHits(103, 120); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamage(24, 26); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 50 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Magery, 70.1, 80.0 ); - SetSkill( SkillName.Meditation, 85.1, 95.0 ); - SetSkill( SkillName.MagicResist, 80.1, 100.0 ); - SetSkill( SkillName.Tactics, 70.1, 90.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 50); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - Fame = 8000; - Karma = 8000; + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Magery, 70.1, 80.0); + SetSkill(SkillName.Meditation, 85.1, 95.0); + SetSkill(SkillName.MagicResist, 80.1, 100.0); + SetSkill(SkillName.Tactics, 70.1, 90.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - VirtualArmor = 16; + Fame = 8000; + Karma = 8000; - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 2, 5 ) ); - } + VirtualArmor = 16; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.MedScrolls, 2 ); - // TODO: Daemon bone ... - } + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(2, 5)); + } - public override bool AutoDispel => true; - public override Poison PoisonImmune => Poison.Lethal; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 3; + public MeerMage(Serial serial) : base(serial) + { + } - public override bool InitialInnocent => true; + public override string CorpseName => "a meer's corpse"; + public override string DefaultName => "a meer mage"; - public override int GetHurtSound() - { - return 0x14D; - } + public override bool AutoDispel => true; + public override Poison PoisonImmune => Poison.Lethal; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 3; - public override int GetDeathSound() - { - return 0x314; - } + public override bool InitialInnocent => true; - public override int GetAttackSound() - { - return 0x75; - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.MedScrolls, 2); + // TODO: Daemon bone ... + } - private DateTime m_NextAbilityTime; + public override int GetHurtSound() + { + return 0x14D; + } - public override void OnThink() - { - if ( DateTime.UtcNow >= m_NextAbilityTime ) - { - Mobile combatant = Combatant; + public override int GetDeathSound() + { + return 0x314; + } - if ( combatant != null && combatant.Map == Map && combatant.InRange( this, 12 ) && IsEnemy( combatant ) && !UnderEffect( combatant ) ) - { - m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds( Utility.RandomMinMax( 20, 30 ) ); + public override int GetAttackSound() + { + return 0x75; + } - if ( combatant is BaseCreature bc ) - { - if ( bc.Controlled && bc.ControlMaster != null && !bc.ControlMaster.Deleted && bc.ControlMaster.Alive ) - { - if ( bc.ControlMaster.Map == Map && bc.ControlMaster.InRange( this, 12 ) && !UnderEffect( bc.ControlMaster ) ) - { - Combatant = combatant = bc.ControlMaster; - } - } - } + public override void OnThink() + { + if (DateTime.UtcNow >= m_NextAbilityTime) + { + Mobile combatant = Combatant; - if ( Utility.RandomDouble() < .1 ) - { - int[][] coord = - { - new[]{-4,-6}, new[]{4,-6}, new[]{0,-8}, new[]{-5,5}, new[]{5,5} - }; + if (combatant != null && combatant.Map == Map && combatant.InRange(this, 12) && IsEnemy(combatant) && + !UnderEffect(combatant)) + { + m_NextAbilityTime = DateTime.UtcNow + TimeSpan.FromSeconds(Utility.RandomMinMax(20, 30)); - for( int i=0; i<5; i++ ) - { - int x = combatant.X + coord[i][0]; - int y = combatant.Y + coord[i][1]; + if (combatant is BaseCreature bc) + if (bc.Controlled && bc.ControlMaster != null && !bc.ControlMaster.Deleted && bc.ControlMaster.Alive) + if (bc.ControlMaster.Map == Map && bc.ControlMaster.InRange(this, 12) && + !UnderEffect(bc.ControlMaster)) + Combatant = combatant = bc.ControlMaster; - Point3D loc = new Point3D( x, y, combatant.Map.GetAverageZ( x, y ) ); + if (Utility.RandomDouble() < .1) + { + int[][] coord = + { + new[] { -4, -6 }, new[] { 4, -6 }, new[] { 0, -8 }, new[] { -5, 5 }, new[] { 5, 5 } + }; - if ( !combatant.Map.CanSpawnMobile( loc ) ) - continue; + for (int i = 0; i < 5; i++) + { + int x = combatant.X + coord[i][0]; + int y = combatant.Y + coord[i][1]; - BaseCreature rabid; - switch ( i ) - { - case 0: rabid = new EnragedRabbit( this ); break; - case 1: rabid = new EnragedHind( this ); break; - case 2: rabid = new EnragedHart( this ); break; - case 3: rabid = new EnragedBlackBear( this ); break; - default: rabid = new EnragedEagle( this ); break; - } + Point3D loc = new Point3D(x, y, combatant.Map.GetAverageZ(x, y)); - rabid.FocusMob = combatant; - rabid.MoveToWorld( loc, combatant.Map ); - } - Say( 1071932 ); //Creatures of the forest, I call to thee! Aid me in the fight against all that is evil! - } - else if ( combatant.Player ) - { - Say( true, "I call a plague of insects to sting your flesh!" ); - m_Table[combatant] = Timer.DelayCall( TimeSpan.FromSeconds( 0.5 ), TimeSpan.FromSeconds( 7.0 ), new TimerStateCallback( DoEffect ), new object[]{ combatant, 0 } ); - } - } - } + if (!combatant.Map.CanSpawnMobile(loc)) + continue; - base.OnThink(); - } + BaseCreature rabid; + switch (i) + { + case 0: + rabid = new EnragedRabbit(this); + break; + case 1: + rabid = new EnragedHind(this); + break; + case 2: + rabid = new EnragedHart(this); + break; + case 3: + rabid = new EnragedBlackBear(this); + break; + default: + rabid = new EnragedEagle(this); + break; + } - private static Hashtable m_Table = new Hashtable(); + rabid.FocusMob = combatant; + rabid.MoveToWorld(loc, combatant.Map); + } - public static bool UnderEffect( Mobile m ) - { - return m_Table.Contains( m ); - } + Say(1071932); //Creatures of the forest, I call to thee! Aid me in the fight against all that is evil! + } + else if (combatant.Player) + { + Say(true, "I call a plague of insects to sting your flesh!"); + m_Table[combatant] = Timer.DelayCall(TimeSpan.FromSeconds(0.5), TimeSpan.FromSeconds(7.0), + new TimerStateCallback(DoEffect), new object[] { combatant, 0 }); + } + } + } - public static void StopEffect( Mobile m, bool message ) - { - if ( m_Table[m] is Timer t ) - { - if ( message ) - m.PublicOverheadMessage( Network.MessageType.Emote, m.SpeechHue, true, "* The open flame begins to scatter the swarm of insects *" ); + base.OnThink(); + } - t.Stop(); - m_Table.Remove( m ); - } - } + public static bool UnderEffect(Mobile m) + { + return m_Table.Contains(m); + } - public void DoEffect( object state ) - { - object[] states = (object[])state; + public static void StopEffect(Mobile m, bool message) + { + if (m_Table[m] is Timer t) + { + if (message) + m.PublicOverheadMessage(MessageType.Emote, m.SpeechHue, true, + "* The open flame begins to scatter the swarm of insects *"); - Mobile m = (Mobile)states[0]; - int count = (int)states[1]; + t.Stop(); + m_Table.Remove(m); + } + } - if ( !m.Alive ) - { - StopEffect( m, false ); - } - else - { - if ( m.FindItemOnLayer( Layer.TwoHanded ) is Torch torch && torch.Burning ) - { - StopEffect( m, true ); - } - else - { - if ( (count % 4) == 0 ) - { - m.LocalOverheadMessage( Network.MessageType.Emote, m.SpeechHue, true, "* The swarm of insects bites and stings your flesh! *" ); - m.NonlocalOverheadMessage( Network.MessageType.Emote, m.SpeechHue, true, - $"* {m.Name} is stung by a swarm of insects *"); - } + public void DoEffect(object state) + { + object[] states = (object[])state; - m.FixedParticles( 0x91C, 10, 180, 9539, EffectLayer.Waist ); - m.PlaySound( 0x00E ); - m.PlaySound( 0x1BC ); + Mobile m = (Mobile)states[0]; + int count = (int)states[1]; - AOS.Damage( m, this, Utility.RandomMinMax( 30, 40 ) - (Core.AOS ? 0 : 10), 100, 0, 0, 0, 0 ); + if (!m.Alive) + { + StopEffect(m, false); + } + else + { + if (m.FindItemOnLayer(Layer.TwoHanded) is Torch torch && torch.Burning) + { + StopEffect(m, true); + } + else + { + if (count % 4 == 0) + { + m.LocalOverheadMessage(MessageType.Emote, m.SpeechHue, true, + "* The swarm of insects bites and stings your flesh! *"); + m.NonlocalOverheadMessage(MessageType.Emote, m.SpeechHue, true, + $"* {m.Name} is stung by a swarm of insects *"); + } - states[1] = count + 1; + m.FixedParticles(0x91C, 10, 180, 9539, EffectLayer.Waist); + m.PlaySound(0x00E); + m.PlaySound(0x1BC); - if ( !m.Alive ) - StopEffect( m, false ); - } - } - } + AOS.Damage(m, this, Utility.RandomMinMax(30, 40) - (Core.AOS ? 0 : 10), 100, 0, 0, 0, 0); - public MeerMage( Serial serial ) : base( serial ) - { - } + states[1] = count + 1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + if (!m.Alive) + StopEffect(m, false); + } + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/LBR/Meers/MeerWarrior.cs b/Scripts/Mobiles/Monsters/LBR/Meers/MeerWarrior.cs index c7dd80695..fdd0e101b 100644 --- a/Scripts/Mobiles/Monsters/LBR/Meers/MeerWarrior.cs +++ b/Scripts/Mobiles/Monsters/LBR/Meers/MeerWarrior.cs @@ -3,87 +3,88 @@ using Server.Spells; namespace Server.Mobiles { - public class MeerWarrior : BaseCreature - { - public override string CorpseName => "a meer corpse"; - public override string DefaultName => "a meer warrior"; + public class MeerWarrior : BaseCreature + { + [Constructible] + public MeerWarrior() : base(AIType.AI_Melee, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 771; - [Constructible] - public MeerWarrior() : base( AIType.AI_Melee, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 771; + SetStr(86, 100); + SetDex(186, 200); + SetInt(86, 100); - SetStr( 86, 100 ); - SetDex( 186, 200 ); - SetInt( 86, 100 ); + SetHits(52, 60); - SetHits( 52, 60 ); + SetDamage(12, 19); - SetDamage( 12, 19 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 5, 15); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 5, 15 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.MagicResist, 91.0, 100.0); + SetSkill(SkillName.Tactics, 91.0, 100.0); + SetSkill(SkillName.Wrestling, 91.0, 100.0); - SetSkill( SkillName.MagicResist, 91.0, 100.0 ); - SetSkill( SkillName.Tactics, 91.0, 100.0 ); - SetSkill( SkillName.Wrestling, 91.0, 100.0 ); + VirtualArmor = 22; - VirtualArmor = 22; + Fame = 2000; + Karma = 5000; + } - Fame = 2000; - Karma = 5000; - } + public MeerWarrior(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a meer corpse"; + public override string DefaultName => "a meer warrior"; - public override bool BardImmune => !Core.AOS; - public override bool CanRummageCorpses => true; + public override bool BardImmune => !Core.AOS; + public override bool CanRummageCorpses => true; - public override bool InitialInnocent => true; + public override bool InitialInnocent => true; - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( from != null && !willKill && amount > 3 && from != null && !InRange( from, 7 ) ) - { - MovingEffect( from, 0xF51, 10, 0, false, false ); - SpellHelper.Damage( TimeSpan.FromSeconds( 1.0 ), from, this, Utility.RandomMinMax( 30, 40 ) - (Core.AOS ? 0 : 10), 100, 0, 0, 0, 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (from != null && !willKill && amount > 3 && from != null && !InRange(from, 7)) + { + MovingEffect(from, 0xF51, 10, 0, false, false); + SpellHelper.Damage(TimeSpan.FromSeconds(1.0), from, this, Utility.RandomMinMax(30, 40) - (Core.AOS ? 0 : 10), + 100, 0, 0, 0, 0); + } - public override int GetHurtSound() - { - return 0x156; - } + base.OnDamage(amount, from, willKill); + } - public override int GetDeathSound() - { - return 0x15C; - } + public override int GetHurtSound() + { + return 0x156; + } - public MeerWarrior( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 0x15C; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Animal/CuSidhe.cs b/Scripts/Mobiles/Monsters/ML/Animal/CuSidhe.cs index 29ab30e97..80f410b5c 100644 --- a/Scripts/Mobiles/Monsters/ML/Animal/CuSidhe.cs +++ b/Scripts/Mobiles/Monsters/ML/Animal/CuSidhe.cs @@ -2,128 +2,152 @@ using Server.Items; namespace Server.Mobiles { - public class CuSidhe : BaseMount - { - public override string CorpseName => "a cu sidhe corpse"; - public override string DefaultName => "a cu sidhe"; + public class CuSidhe : BaseMount + { + [Constructible] + public CuSidhe() : this(null) + { + } - [Constructible] - public CuSidhe() : this( null ) - { - } + [Constructible] + public CuSidhe(string name) : base(name, 277, 0x3E91, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + double chance = Utility.RandomDouble() * 23301; - [Constructible] - public CuSidhe( string name ) : base( name, 277, 0x3E91, AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - double chance = Utility.RandomDouble() * 23301; + if (chance <= 1) + Hue = 0x489; + else if (chance < 50) + Hue = Utility.RandomList(0x657, 0x515, 0x4B1, 0x481, 0x482, 0x455); + else if (chance < 500) + Hue = Utility.RandomList(0x97A, 0x978, 0x901, 0x8AC, 0x5A7, 0x527); - if ( chance <= 1 ) - Hue = 0x489; - else if ( chance < 50 ) - Hue = Utility.RandomList( 0x657, 0x515, 0x4B1, 0x481, 0x482, 0x455 ); - else if ( chance < 500 ) - Hue = Utility.RandomList( 0x97A, 0x978, 0x901, 0x8AC, 0x5A7, 0x527 ); + SetStr(1200, 1225); + SetDex(150, 170); + SetInt(250, 285); - SetStr( 1200, 1225 ); - SetDex( 150, 170 ); - SetInt( 250, 285 ); + SetHits(1010, 1275); - SetHits( 1010, 1275 ); + SetDamage(21, 28); - SetDamage( 21, 28 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 50, 65); + SetResistance(ResistanceType.Fire, 25, 45); + SetResistance(ResistanceType.Cold, 70, 85); + SetResistance(ResistanceType.Poison, 30, 50); + SetResistance(ResistanceType.Energy, 70, 85); - SetResistance( ResistanceType.Physical, 50, 65 ); - SetResistance( ResistanceType.Fire, 25, 45 ); - SetResistance( ResistanceType.Cold, 70, 85 ); - SetResistance( ResistanceType.Poison, 30, 50 ); - SetResistance( ResistanceType.Energy, 70, 85 ); + SetSkill(SkillName.Wrestling, 90.1, 96.8); + SetSkill(SkillName.Tactics, 90.3, 99.3); + SetSkill(SkillName.MagicResist, 75.3, 90.0); + SetSkill(SkillName.Anatomy, 65.5, 69.4); + SetSkill(SkillName.Healing, 72.2, 98.9); - SetSkill( SkillName.Wrestling, 90.1, 96.8 ); - SetSkill( SkillName.Tactics, 90.3, 99.3 ); - SetSkill( SkillName.MagicResist, 75.3, 90.0 ); - SetSkill( SkillName.Anatomy, 65.5, 69.4 ); - SetSkill( SkillName.Healing, 72.2, 98.9 ); + Fame = 5000; //Guessing here + Karma = 5000; //Guessing here - Fame = 5000; //Guessing here - Karma = 5000; //Guessing here + Tamable = true; + ControlSlots = 4; + MinTameSkill = 101.1; - Tamable = true; - ControlSlots = 4; - MinTameSkill = 101.1; + if (Utility.RandomDouble() < 0.2) + PackItem(new TreasureMap(5, Map.Trammel)); - if ( Utility.RandomDouble() < 0.2 ) - PackItem( new TreasureMap( 5, Map.Trammel ) ); + //if ( Utility.RandomDouble() < 0.1 ) + //PackItem( new ParrotItem() ); - //if ( Utility.RandomDouble() < 0.1 ) - //PackItem( new ParrotItem() ); + PackGold(500, 800); - PackGold( 500, 800 ); + // TODO 0-2 spellweaving scroll + } - // TODO 0-2 spellweaving scroll - } + public CuSidhe(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.AosFilthyRich, 5 ); - } + public override string CorpseName => "a cu sidhe corpse"; + public override string DefaultName => "a cu sidhe"; - public override void OnDoubleClick( Mobile from ) - { - if ( from.Race != Race.Elf && from == ControlMaster && from.AccessLevel == AccessLevel.Player ) - { - Item pads = from.FindItemOnLayer( Layer.Shoes ); + public override bool CanHeal => true; + public override bool CanHealOwner => true; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies; + public override bool CanAngerOnTame => true; + public override bool StatLossAfterTame => true; + public override int Hides => 10; + public override int Meat => 3; - if ( pads is PadsOfTheCuSidhe ) - from.SendLocalizedMessage( 1071981 ); // Your boots allow you to mount the Cu Sidhe. - else - { - from.SendLocalizedMessage( 1072203 ); // Only Elves may use this. - return; - } - } + public override void GenerateLoot() + { + AddLoot(LootPack.AosFilthyRich, 5); + } - base.OnDoubleClick( from ); - } + public override void OnDoubleClick(Mobile from) + { + if (from.Race != Race.Elf && from == ControlMaster && from.AccessLevel == AccessLevel.Player) + { + Item pads = from.FindItemOnLayer(Layer.Shoes); - public override bool CanHeal => true; - public override bool CanHealOwner => true; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies; - public override bool CanAngerOnTame => true; - public override bool StatLossAfterTame => true; - public override int Hides => 10; - public override int Meat => 3; + if (pads is PadsOfTheCuSidhe) + { + from.SendLocalizedMessage(1071981); // Your boots allow you to mount the Cu Sidhe. + } + else + { + from.SendLocalizedMessage(1072203); // Only Elves may use this. + return; + } + } - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; + base.OnDoubleClick(from); + } - public CuSidhe( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override int GetIdleSound() { return 0x577; } - public override int GetAttackSound() { return 0x576; } - public override int GetAngerSound() { return 0x578; } - public override int GetHurtSound() { return 0x576; } - public override int GetDeathSound() { return 0x579; } + public override int GetIdleSound() + { + return 0x577; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int GetAttackSound() + { + return 0x576; + } - writer.Write( (int) 1 ); // version - } + public override int GetAngerSound() + { + return 0x578; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int GetHurtSound() + { + return 0x576; + } - int version = reader.ReadInt(); + public override int GetDeathSound() + { + return 0x579; + } - if ( version < 1 && Name == "a Cu Sidhe" ) - Name = null; - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version < 1 && Name == "a Cu Sidhe") + Name = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Animal/Ferret.cs b/Scripts/Mobiles/Monsters/ML/Animal/Ferret.cs index a8301be99..d5875b234 100644 --- a/Scripts/Mobiles/Monsters/ML/Animal/Ferret.cs +++ b/Scripts/Mobiles/Monsters/ML/Animal/Ferret.cs @@ -3,101 +3,102 @@ using Server.Engines.Quests; namespace Server.Mobiles { - public class Ferret : BaseCreature - { - public override string CorpseName => "a ferret corpse"; - public override string DefaultName => "a ferret"; + public class Ferret : BaseCreature + { + private static string[] m_Vocabulary = + { + "dook", + "dook dook", + "dook dook dook!" + }; - [Constructible] - public Ferret() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0x117; + private bool m_CanTalk; - SetStr( 41, 48 ); - SetDex( 55 ); - SetInt( 75 ); + [Constructible] + public Ferret() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0x117; - SetHits( 45, 50 ); + SetStr(41, 48); + SetDex(55); + SetInt(75); - SetDamage( 7, 9 ); + SetHits(45, 50); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamage(7, 9); - SetResistance( ResistanceType.Physical, 45, 50 ); - SetResistance( ResistanceType.Fire, 10, 14 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 21, 25 ); - SetResistance( ResistanceType.Energy, 20, 25 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.MagicResist, 4.0 ); - SetSkill( SkillName.Tactics, 4.0 ); - SetSkill( SkillName.Wrestling, 4.0 ); + SetResistance(ResistanceType.Physical, 45, 50); + SetResistance(ResistanceType.Fire, 10, 14); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 21, 25); + SetResistance(ResistanceType.Energy, 20, 25); - Tamable = true; - ControlSlots = 1; - MinTameSkill = -21.3; + SetSkill(SkillName.MagicResist, 4.0); + SetSkill(SkillName.Tactics, 4.0); + SetSkill(SkillName.Wrestling, 4.0); - m_CanTalk = true; - } + Tamable = true; + ControlSlots = 1; + MinTameSkill = -21.3; - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Fish; + m_CanTalk = true; + } - public Ferret( Serial serial ) : base( serial ) - { - } + public Ferret(Serial serial) : base(serial) + { + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( m is Ferret ferret && ferret.InRange( this, 3 ) && ferret.Alive ) - Talk( ferret ); - } + public override string CorpseName => "a ferret corpse"; + public override string DefaultName => "a ferret"; - private static string[] m_Vocabulary = { - "dook", - "dook dook", - "dook dook dook!" - }; + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Fish; - private bool m_CanTalk; + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (m is Ferret ferret && ferret.InRange(this, 3) && ferret.Alive) + Talk(ferret); + } - public void Talk() - { - Talk( null ); - } + public void Talk() + { + Talk(null); + } - public void Talk( Ferret to ) - { - if ( m_CanTalk ) - { - if ( to != null ) - QuestSystem.FocusTo( this, to ); + public void Talk(Ferret to) + { + if (m_CanTalk) + { + if (to != null) + QuestSystem.FocusTo(this, to); - Say( m_Vocabulary[ Utility.Random( m_Vocabulary.Length ) ] ); + Say(m_Vocabulary[Utility.Random(m_Vocabulary.Length)]); - if ( to != null && Utility.RandomBool() ) - Timer.DelayCall( TimeSpan.FromSeconds( Utility.RandomMinMax( 5, 8 ) ), delegate { to.Talk(); } ); + if (to != null && Utility.RandomBool()) + Timer.DelayCall(TimeSpan.FromSeconds(Utility.RandomMinMax(5, 8)), delegate { to.Talk(); }); - m_CanTalk = false; + m_CanTalk = false; - Timer.DelayCall( TimeSpan.FromSeconds( Utility.RandomMinMax( 20, 30 ) ), delegate { m_CanTalk = true; } ); - } - } + Timer.DelayCall(TimeSpan.FromSeconds(Utility.RandomMinMax(20, 30)), delegate { m_CanTalk = true; }); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - m_CanTalk = true; - } - } -} + m_CanTalk = true; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Animal/RagingGrizzlyBear.cs b/Scripts/Mobiles/Monsters/ML/Animal/RagingGrizzlyBear.cs index ca4f222cd..3b30a7236 100644 --- a/Scripts/Mobiles/Monsters/ML/Animal/RagingGrizzlyBear.cs +++ b/Scripts/Mobiles/Monsters/ML/Animal/RagingGrizzlyBear.cs @@ -1,67 +1,66 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Grizzlybear" )] - public class RagingGrizzlyBear : BaseCreature - { - public override string CorpseName => "a grizzly bear corpse"; - public override string DefaultName => "a raging grizzly bear"; + [TypeAlias("Server.Mobiles.Grizzlybear")] + public class RagingGrizzlyBear : BaseCreature + { + [Constructible] + public RagingGrizzlyBear() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 212; + BaseSoundID = 0xA3; - [Constructible] - public RagingGrizzlyBear() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 212; - BaseSoundID = 0xA3; + SetStr(1251, 1550); + SetDex(801, 1050); + SetInt(151, 400); - SetStr( 1251, 1550 ); - SetDex( 801, 1050 ); - SetInt( 151, 400 ); + SetHits(751, 930); + SetMana(0); - SetHits( 751, 930 ); - SetMana( 0 ); + SetDamage(18, 23); - SetDamage( 18, 23 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 50, 70); + SetResistance(ResistanceType.Cold, 30, 50); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 50, 70 ); - SetResistance( ResistanceType.Cold, 30, 50 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.Wrestling, 73.4, 88.1); + SetSkill(SkillName.Tactics, 73.6, 110.5); + SetSkill(SkillName.MagicResist, 32.8, 54.6); + SetSkill(SkillName.Anatomy, 0, 0); - SetSkill( SkillName.Wrestling, 73.4, 88.1 ); - SetSkill( SkillName.Tactics, 73.6, 110.5 ); - SetSkill( SkillName.MagicResist, 32.8, 54.6 ); - SetSkill( SkillName.Anatomy, 0, 0 ); + Fame = 10000; //Guessing here + Karma = 10000; //Guessing here - Fame = 10000; //Guessing here - Karma = 10000; //Guessing here + VirtualArmor = 24; - VirtualArmor = 24; + Tamable = false; + } - Tamable = false; + public RagingGrizzlyBear(Serial serial) : base(serial) + { + } - } + public override string CorpseName => "a grizzly bear corpse"; + public override string DefaultName => "a raging grizzly bear"; - public override int Meat => 4; - public override int Hides => 32; - public override PackInstinct PackInstinct => PackInstinct.Bear; + public override int Meat => 4; + public override int Hides => 32; + public override PackInstinct PackInstinct => PackInstinct.Bear; - public RagingGrizzlyBear( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize(GenericWriter writer) - { - base.Serialize( writer ); + writer.Write(0); + } - writer.Write( (int) 0 ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Animal/Squirrel.cs b/Scripts/Mobiles/Monsters/ML/Animal/Squirrel.cs index edb556e45..59d7ab37d 100644 --- a/Scripts/Mobiles/Monsters/ML/Animal/Squirrel.cs +++ b/Scripts/Mobiles/Monsters/ML/Animal/Squirrel.cs @@ -1,59 +1,59 @@ namespace Server.Mobiles { - public class Squirrel : BaseCreature - { - public override string CorpseName => "a squirrel corpse"; - public override string DefaultName => "a squirrell"; + public class Squirrel : BaseCreature + { + [Constructible] + public Squirrel() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 0x116; - [Constructible] - public Squirrel() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 0x116; + SetStr(44, 50); + SetDex(35); + SetInt(5); - SetStr( 44, 50 ); - SetDex( 35 ); - SetInt( 5 ); + SetHits(42, 50); - SetHits( 42, 50 ); + SetDamage(1, 2); - SetDamage( 1, 2 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 34); + SetResistance(ResistanceType.Fire, 10, 14); + SetResistance(ResistanceType.Cold, 30, 35); + SetResistance(ResistanceType.Poison, 20, 25); + SetResistance(ResistanceType.Energy, 20, 25); - SetResistance( ResistanceType.Physical, 30, 34 ); - SetResistance( ResistanceType.Fire, 10, 14 ); - SetResistance( ResistanceType.Cold, 30, 35 ); - SetResistance( ResistanceType.Poison, 20, 25 ); - SetResistance( ResistanceType.Energy, 20, 25 ); + SetSkill(SkillName.MagicResist, 4.0); + SetSkill(SkillName.Tactics, 4.0); + SetSkill(SkillName.Wrestling, 4.0); - SetSkill( SkillName.MagicResist, 4.0 ); - SetSkill( SkillName.Tactics, 4.0 ); - SetSkill( SkillName.Wrestling, 4.0 ); + Tamable = true; + ControlSlots = 1; + MinTameSkill = -21.3; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = -21.3; - } + public Squirrel(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies; + public override string CorpseName => "a squirrel corpse"; + public override string DefaultName => "a squirrell"; - public Squirrel( Serial serial ) : base( serial ) - { - } + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/LadyJennifyr.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/LadyJennifyr.cs index eb9338f37..8b2d2b4c1 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/LadyJennifyr.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/LadyJennifyr.cs @@ -3,133 +3,134 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class LadyJennifyr : SkeletalKnight - { - public override string CorpseName => "a Lady Jennifyr corpse"; - public override string DefaultName => "Lady Jennifyr"; + public class LadyJennifyr : SkeletalKnight + { + private static Dictionary m_Table = new Dictionary(); - [Constructible] - public LadyJennifyr() - { - IsParagon = true; + [Constructible] + public LadyJennifyr() + { + IsParagon = true; - Hue = 0x76D; + Hue = 0x76D; - SetStr( 208, 309 ); - SetDex( 91, 118 ); - SetInt( 44, 101 ); + SetStr(208, 309); + SetDex(91, 118); + SetInt(44, 101); - SetHits( 1113, 1285 ); + SetHits(1113, 1285); - SetDamage( 15, 25 ); + SetDamage(15, 25); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetResistance( ResistanceType.Physical, 56, 65 ); - SetResistance( ResistanceType.Fire, 41, 49 ); - SetResistance( ResistanceType.Cold, 71, 80 ); - SetResistance( ResistanceType.Poison, 41, 50 ); - SetResistance( ResistanceType.Energy, 50, 58 ); + SetResistance(ResistanceType.Physical, 56, 65); + SetResistance(ResistanceType.Fire, 41, 49); + SetResistance(ResistanceType.Cold, 71, 80); + SetResistance(ResistanceType.Poison, 41, 50); + SetResistance(ResistanceType.Energy, 50, 58); - SetSkill( SkillName.Wrestling, 127.9, 137.1 ); - SetSkill( SkillName.Tactics, 128.4, 141.9 ); - SetSkill( SkillName.MagicResist, 102.1, 119.5 ); - SetSkill( SkillName.Anatomy, 129.0, 137.5 ); + SetSkill(SkillName.Wrestling, 127.9, 137.1); + SetSkill(SkillName.Tactics, 128.4, 141.9); + SetSkill(SkillName.MagicResist, 102.1, 119.5); + SetSkill(SkillName.Anatomy, 129.0, 137.5); - Fame = 18000; - Karma = -18000; - } + Fame = 18000; + Karma = -18000; + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public LadyJennifyr(Serial serial) + : base(serial) + { + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override string CorpseName => "a Lady Jennifyr corpse"; + public override string DefaultName => "Lady Jennifyr"; - if ( Utility.RandomDouble() < 0.1 ) - { - if (m_Table.TryGetValue( defender, out ExpireTimer timer )) - timer.DoExpire(); + /* + // TODO: Uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - defender.FixedParticles( 0x3709, 10, 30, 5052, EffectLayer.LeftFoot ); - defender.PlaySound( 0x208 ); - defender.SendLocalizedMessage( 1070833 ); // The creature fans you with fire, reducing your resistance to fire attacks. + if ( Utility.RandomDouble() < 0.15 ) + c.DropItem( new DisintegratingThesisNotes() ); - ResistanceMod mod = new ResistanceMod( ResistanceType.Fire, -10 ); - defender.AddResistanceMod( mod ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - m_Table[defender] = timer = new ExpireTimer( defender, mod ); - timer.Start(); - } - } + public override bool GivesMLMinorArtifact => true; - private static Dictionary m_Table = new Dictionary(); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod m_Mod; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public ExpireTimer( Mobile m, ResistanceMod mod ) - : base( TimeSpan.FromSeconds( 10 ) ) - { - m_Mobile = m; - m_Mod = mod; - Priority = TimerPriority.TwoFiftyMS; - } + if (Utility.RandomDouble() < 0.1) + { + if (m_Table.TryGetValue(defender, out ExpireTimer timer)) + timer.DoExpire(); - public void DoExpire() - { - m_Mobile.RemoveResistanceMod( m_Mod ); + defender.FixedParticles(0x3709, 10, 30, 5052, EffectLayer.LeftFoot); + defender.PlaySound(0x208); + defender.SendLocalizedMessage( + 1070833); // The creature fans you with fire, reducing your resistance to fire attacks. - Stop(); - m_Table.Remove( m_Mobile ); - } + ResistanceMod mod = new ResistanceMod(ResistanceType.Fire, -10); + defender.AddResistanceMod(mod); - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1070834 ); // Your resistance to fire attacks has returned. - DoExpire(); - } - } + m_Table[defender] = timer = new ExpireTimer(defender, mod); + timer.Start(); + } + } - /* - // TODO: Uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( Utility.RandomDouble() < 0.15 ) - c.DropItem( new DisintegratingThesisNotes() ); + writer.Write(0); // version + } - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override bool GivesMLMinorArtifact => true; + int version = reader.ReadInt(); + } - public LadyJennifyr( Serial serial ) - : base( serial ) - { - } + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod m_Mod; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public ExpireTimer(Mobile m, ResistanceMod mod) + : base(TimeSpan.FromSeconds(10)) + { + m_Mobile = m; + m_Mod = mod; + Priority = TimerPriority.TwoFiftyMS; + } - writer.Write( (int) 0 ); // version - } + public void DoExpire() + { + m_Mobile.RemoveResistanceMod(m_Mod); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Stop(); + m_Table.Remove(m_Mobile); + } - int version = reader.ReadInt(); - } - } -} + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1070834); // Your resistance to fire attacks has returned. + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/LadyMarai.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/LadyMarai.cs index bc33eb24d..4f630e331 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/LadyMarai.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/LadyMarai.cs @@ -2,84 +2,87 @@ using Server.Items; namespace Server.Mobiles { - public class LadyMarai : SkeletalKnight - { - public override string CorpseName => "a Lady Marai corpse"; - public override string DefaultName => "Lady Marai"; + public class LadyMarai : SkeletalKnight + { + [Constructible] + public LadyMarai() + { + IsParagon = true; - [Constructible] - public LadyMarai() - { - IsParagon = true; + Hue = 0x21; - Hue = 0x21; + SetStr(221, 304); + SetDex(98, 138); + SetInt(54, 99); - SetStr( 221, 304 ); - SetDex( 98, 138 ); - SetInt( 54, 99 ); + SetHits(694, 846); - SetHits( 694, 846 ); + SetDamage(15, 25); - SetDamage( 15, 25 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.Wrestling, 126.6, 137.2); + SetSkill(SkillName.Tactics, 128.7, 134.5); + SetSkill(SkillName.MagicResist, 102.1, 119.1); + SetSkill(SkillName.Anatomy, 126.2, 136.5); - SetSkill( SkillName.Wrestling, 126.6, 137.2 ); - SetSkill( SkillName.Tactics, 128.7, 134.5 ); - SetSkill( SkillName.MagicResist, 102.1, 119.1 ); - SetSkill( SkillName.Anatomy, 126.2, 136.5 ); + Fame = 18000; + Karma = -18000; + } - Fame = 18000; - Karma = -18000; - } + public LadyMarai(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Lady Marai corpse"; + public override string DefaultName => "Lady Marai"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.CrushingBlow; + /* + // TODO: Uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* - // TODO: Uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.15 ) + c.DropItem( new DisintegratingThesisNotes() ); - if ( Utility.RandomDouble() < 0.15 ) - c.DropItem( new DisintegratingThesisNotes() ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public LadyMarai( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.CrushingBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/MasterJonath.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/MasterJonath.cs index 4c8dead54..e66070ee2 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/MasterJonath.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/MasterJonath.cs @@ -1,95 +1,95 @@ namespace Server.Mobiles { - public class MasterJonath : BoneMagi - { - public override string CorpseName => "a Master Jonath corpse"; - public override string DefaultName => "Master Jonath"; + public class MasterJonath : BoneMagi + { + [Constructible] + public MasterJonath() + { + IsParagon = true; - [Constructible] - public MasterJonath() - { - IsParagon = true; + Hue = 0x455; - Hue = 0x455; + SetStr(109, 131); + SetDex(98, 110); + SetInt(232, 259); - SetStr( 109, 131 ); - SetDex( 98, 110 ); - SetInt( 232, 259 ); + SetHits(766, 920); - SetHits( 766, 920 ); + SetDamage(10, 15); - SetDamage( 10, 15 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 55, 60); + SetResistance(ResistanceType.Fire, 43, 49); + SetResistance(ResistanceType.Cold, 45, 80); + SetResistance(ResistanceType.Poison, 41, 45); + SetResistance(ResistanceType.Energy, 54, 55); - SetResistance( ResistanceType.Physical, 55, 60 ); - SetResistance( ResistanceType.Fire, 43, 49 ); - SetResistance( ResistanceType.Cold, 45, 80 ); - SetResistance( ResistanceType.Poison, 41, 45 ); - SetResistance( ResistanceType.Energy, 54, 55 ); + SetSkill(SkillName.Wrestling, 80.5, 88.6); + SetSkill(SkillName.Tactics, 88.5, 95.1); + SetSkill(SkillName.MagicResist, 102.7, 102.9); + SetSkill(SkillName.Magery, 100.0, 106.6); + SetSkill(SkillName.EvalInt, 99.6, 106.9); + SetSkill(SkillName.Necromancy, 100.0, 106.6); + SetSkill(SkillName.SpiritSpeak, 99.6, 106.9); - SetSkill( SkillName.Wrestling, 80.5, 88.6 ); - SetSkill( SkillName.Tactics, 88.5, 95.1 ); - SetSkill( SkillName.MagicResist, 102.7, 102.9 ); - SetSkill( SkillName.Magery, 100.0, 106.6 ); - SetSkill( SkillName.EvalInt, 99.6, 106.9 ); - SetSkill( SkillName.Necromancy, 100.0, 106.6 ); - SetSkill( SkillName.SpiritSpeak, 99.6, 106.9 ); + Fame = 18000; + Karma = -18000; - Fame = 18000; - Karma = -18000; + if (Utility.RandomBool()) + PackNecroScroll(Utility.RandomMinMax(5, 9)); + else + PackScroll(4, 7); - if ( Utility.RandomBool() ) - PackNecroScroll( Utility.RandomMinMax( 5, 9 ) ); - else - PackScroll( 4, 7 ); + PackReg(7); + PackReg(7); + PackReg(8); + } - PackReg( 7 ); - PackReg( 7 ); - PackReg( 8 ); - } + public MasterJonath(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Master Jonath corpse"; + public override string DefaultName => "Master Jonath"; - // TODO: Special move? + // TODO: Special move? - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - if ( Utility.RandomDouble() < 0.05 ) - c.DropItem( new ParrotItem() ); + if ( Utility.RandomDouble() < 0.05 ) + c.DropItem( new ParrotItem() ); - if ( Utility.RandomDouble() < 0.15 ) - c.DropItem( new DisintegratingThesisNotes() ); - } - */ + if ( Utility.RandomDouble() < 0.15 ) + c.DropItem( new DisintegratingThesisNotes() ); + } + */ - public override bool GivesMLMinorArtifact => true; - public override int TreasureMapLevel => 5; + public override bool GivesMLMinorArtifact => true; + public override int TreasureMapLevel => 5; - public MasterJonath( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/MasterMikael.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/MasterMikael.cs index 11e1af950..89da14f92 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/MasterMikael.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/MasterMikael.cs @@ -1,93 +1,93 @@ namespace Server.Mobiles { - public class MasterMikael : BoneMagi - { - public override string CorpseName => "a Master Mikael corpse"; - public override string DefaultName => "Master Mikael"; + public class MasterMikael : BoneMagi + { + [Constructible] + public MasterMikael() + { + IsParagon = true; - [Constructible] - public MasterMikael() - { - IsParagon = true; + Hue = 0x8FD; - Hue = 0x8FD; + SetStr(93, 122); + SetDex(91, 100); + SetInt(252, 271); - SetStr( 93, 122 ); - SetDex( 91, 100 ); - SetInt( 252, 271 ); + SetHits(789, 1014); - SetHits( 789, 1014 ); + SetDamage(11, 19); - SetDamage( 11, 19 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 55, 59); + SetResistance(ResistanceType.Fire, 40, 46); + SetResistance(ResistanceType.Cold, 72, 80); + SetResistance(ResistanceType.Poison, 44, 49); + SetResistance(ResistanceType.Energy, 50, 57); - SetResistance( ResistanceType.Physical, 55, 59 ); - SetResistance( ResistanceType.Fire, 40, 46 ); - SetResistance( ResistanceType.Cold, 72, 80 ); - SetResistance( ResistanceType.Poison, 44, 49 ); - SetResistance( ResistanceType.Energy, 50, 57 ); + SetSkill(SkillName.Wrestling, 80.1, 87.2); + SetSkill(SkillName.Tactics, 79.0, 90.9); + SetSkill(SkillName.MagicResist, 90.3, 106.9); + SetSkill(SkillName.Magery, 103.8, 108.0); + SetSkill(SkillName.EvalInt, 96.1, 105.3); + SetSkill(SkillName.Necromancy, 103.8, 108.0); + SetSkill(SkillName.SpiritSpeak, 96.1, 105.3); - SetSkill( SkillName.Wrestling, 80.1, 87.2 ); - SetSkill( SkillName.Tactics, 79.0, 90.9 ); - SetSkill( SkillName.MagicResist, 90.3, 106.9 ); - SetSkill( SkillName.Magery, 103.8, 108.0 ); - SetSkill( SkillName.EvalInt, 96.1, 105.3 ); - SetSkill( SkillName.Necromancy, 103.8, 108.0 ); - SetSkill( SkillName.SpiritSpeak, 96.1, 105.3 ); + Fame = 18000; + Karma = -18000; - Fame = 18000; - Karma = -18000; + if (Utility.RandomBool()) + PackNecroScroll(Utility.RandomMinMax(5, 9)); + else + PackScroll(4, 7); - if ( Utility.RandomBool() ) - PackNecroScroll( Utility.RandomMinMax( 5, 9 ) ); - else - PackScroll( 4, 7 ); + PackReg(3); + PackNecroReg(1, 10); + } - PackReg( 3 ); - PackNecroReg( 1, 10 ); - } + public MasterMikael(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Master Mikael corpse"; + public override string DefaultName => "Master Mikael"; - // TODO: Special move? + // TODO: Special move? - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - if ( Utility.RandomDouble() < 0.15 ) - c.DropItem( new DisintegratingThesisNotes() ); + if ( Utility.RandomDouble() < 0.15 ) + c.DropItem( new DisintegratingThesisNotes() ); - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - public override bool GivesMLMinorArtifact => true; + public override bool GivesMLMinorArtifact => true; - public MasterMikael( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/MasterTheophilus.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/MasterTheophilus.cs index a8513dc33..1aa1c96a2 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/MasterTheophilus.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/MasterTheophilus.cs @@ -2,90 +2,91 @@ using Server.Items; namespace Server.Mobiles { - public class MasterTheophilus : EvilMageLord - { - public override string CorpseName => "a Master Theophilus corpse"; - public override string DefaultName => "Master Theophilus"; + public class MasterTheophilus : EvilMageLord + { + [Constructible] + public MasterTheophilus() + { + IsParagon = true; - [Constructible] - public MasterTheophilus() - { - IsParagon = true; + Title = "the necromancer"; + Hue = 0; - Title = "the necromancer"; - Hue = 0; + SetStr(137, 187); + SetDex(253, 301); + SetInt(393, 444); - SetStr( 137, 187 ); - SetDex( 253, 301 ); - SetInt( 393, 444 ); + SetHits(663, 876); - SetHits( 663, 876 ); + SetDamage(15, 20); - SetDamage( 15, 20 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 55, 60); + SetResistance(ResistanceType.Fire, 50, 58); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 55, 60 ); - SetResistance( ResistanceType.Fire, 50, 58 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.Wrestling, 69.9, 105.3); + SetSkill(SkillName.Tactics, 113.0, 117.9); + SetSkill(SkillName.MagicResist, 127.0, 132.8); + SetSkill(SkillName.Magery, 138.1, 143.7); + SetSkill(SkillName.EvalInt, 125.6, 133.8); + SetSkill(SkillName.Necromancy, 125.6, 133.8); + SetSkill(SkillName.SpiritSpeak, 125.6, 133.8); + SetSkill(SkillName.Meditation, 128.8, 132.9); - SetSkill( SkillName.Wrestling, 69.9, 105.3 ); - SetSkill( SkillName.Tactics, 113.0, 117.9 ); - SetSkill( SkillName.MagicResist, 127.0, 132.8 ); - SetSkill( SkillName.Magery, 138.1, 143.7 ); - SetSkill( SkillName.EvalInt, 125.6, 133.8 ); - SetSkill( SkillName.Necromancy, 125.6, 133.8 ); - SetSkill( SkillName.SpiritSpeak, 125.6, 133.8 ); - SetSkill( SkillName.Meditation, 128.8, 132.9 ); + Fame = 18000; + Karma = -18000; - Fame = 18000; - Karma = -18000; + AddItem(new Shoes(0x537)); + AddItem(new Robe(0x452)); - AddItem( new Shoes( 0x537 ) ); - AddItem( new Robe( 0x452 ) ); + for (int i = 0; i < 2; ++i) + if (Utility.RandomBool()) + PackNecroScroll(Utility.RandomMinMax(5, 9)); + else + PackScroll(4, 7); - for ( int i = 0; i < 2; ++i ) - { - if ( Utility.RandomBool() ) - PackNecroScroll( Utility.RandomMinMax( 5, 9 ) ); - else - PackScroll( 4, 7 ); - } + PackReg(7); + PackReg(7); + PackReg(8); + } - PackReg( 7 ); - PackReg( 7 ); - PackReg( 8 ); - } + public MasterTheophilus(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Master Theophilus corpse"; + public override string DefaultName => "Master Theophilus"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ParalyzingBlow; + public override bool GivesMLMinorArtifact => true; + public override int TreasureMapLevel => 5; - public override bool GivesMLMinorArtifact => true; - public override int TreasureMapLevel => 5; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public MasterTheophilus( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ParalyzingBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/RedDeath.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/RedDeath.cs index 2d04db633..a1fbb9756 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/RedDeath.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/RedDeath.cs @@ -2,90 +2,94 @@ using Server.Items; namespace Server.Mobiles { - public class RedDeath : SkeletalMount - { - public override string CorpseName => "a Red Death corpse"; - [Constructible] - public RedDeath() - : base( "Red Death" ) - { - IsParagon = true; + public class RedDeath : SkeletalMount + { + [Constructible] + public RedDeath() + : base("Red Death") + { + IsParagon = true; - Hue = 0x21; - BaseSoundID = 0x1C3; + Hue = 0x21; + BaseSoundID = 0x1C3; - AI = AIType.AI_Melee; - FightMode = FightMode.Closest; + AI = AIType.AI_Melee; + FightMode = FightMode.Closest; - SetStr( 319, 324 ); - SetDex( 241, 244 ); - SetInt( 242, 255 ); + SetStr(319, 324); + SetDex(241, 244); + SetInt(242, 255); - SetHits( 1540, 1605 ); + SetHits(1540, 1605); - SetDamage( 25, 29 ); + SetDamage(25, 29); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Fire, 75 ); - SetDamageType( ResistanceType.Cold, 0 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Fire, 75); + SetDamageType(ResistanceType.Cold, 0); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 90 ); - SetResistance( ResistanceType.Cold, 0 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 0 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 90); + SetResistance(ResistanceType.Cold, 0); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 0); - SetSkill( SkillName.Wrestling, 121.4, 143.7 ); - SetSkill( SkillName.Tactics, 120.9, 142.2 ); - SetSkill( SkillName.MagicResist, 120.1, 142.3 ); - SetSkill( SkillName.Anatomy, 120.2, 144.0 ); + SetSkill(SkillName.Wrestling, 121.4, 143.7); + SetSkill(SkillName.Tactics, 120.9, 142.2); + SetSkill(SkillName.MagicResist, 120.1, 142.3); + SetSkill(SkillName.Anatomy, 120.2, 144.0); - Fame = 28000; - Karma = -28000; + Fame = 28000; + Karma = -28000; - if ( Utility.RandomBool() ) - PackNecroScroll( Utility.RandomMinMax( 5, 9 ) ); - else - PackScroll( 4, 7 ); - } + if (Utility.RandomBool()) + PackNecroScroll(Utility.RandomMinMax(5, 9)); + else + PackScroll(4, 7); + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public RedDeath(Serial serial) + : base(serial) + { + } - public override WeaponAbility GetWeaponAbility() => WeaponAbility.WhirlwindAttack; + public override string CorpseName => "a Red Death corpse"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool GivesMLMinorArtifact => true; + public override bool AlwaysMurderer => true; + public override bool HasBreath => true; + public override int BreathChaosDamage => 100; + public override int BreathFireDamage => 0; - c.DropItem( new ResolvesBridle() ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public override bool GivesMLMinorArtifact => true; - public override bool AlwaysMurderer => true; - public override bool HasBreath => true; - public override int BreathChaosDamage => 100; - public override int BreathFireDamage => 0; + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.WhirlwindAttack; + } - public RedDeath( Serial serial ) - : base( serial ) - { - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + c.DropItem(new ResolvesBridle()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Bedlam/SirPatrick.cs b/Scripts/Mobiles/Monsters/ML/Bedlam/SirPatrick.cs index 9b7af689a..dcc820ae0 100644 --- a/Scripts/Mobiles/Monsters/ML/Bedlam/SirPatrick.cs +++ b/Scripts/Mobiles/Monsters/ML/Bedlam/SirPatrick.cs @@ -2,133 +2,132 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class SirPatrick : SkeletalKnight - { - public override string CorpseName => "a Sir Patrick corpse"; - public override string DefaultName => "Sir Patrick"; + public class SirPatrick : SkeletalKnight + { + [Constructible] + public SirPatrick() + { + IsParagon = true; - [Constructible] - public SirPatrick() - { - IsParagon = true; + Hue = 0x47E; - Hue = 0x47E; + SetStr(208, 319); + SetDex(98, 132); + SetInt(45, 91); - SetStr( 208, 319 ); - SetDex( 98, 132 ); - SetInt( 45, 91 ); + SetHits(616, 884); - SetHits( 616, 884 ); + SetDamage(15, 25); - SetDamage( 15, 25 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 60 ); + SetResistance(ResistanceType.Physical, 55, 62); + SetResistance(ResistanceType.Fire, 40, 48); + SetResistance(ResistanceType.Cold, 71, 80); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 55, 62 ); - SetResistance( ResistanceType.Fire, 40, 48 ); - SetResistance( ResistanceType.Cold, 71, 80 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.Wrestling, 126.3, 136.5); + SetSkill(SkillName.Tactics, 128.5, 143.8); + SetSkill(SkillName.MagicResist, 102.8, 117.9); + SetSkill(SkillName.Anatomy, 127.5, 137.2); - SetSkill( SkillName.Wrestling, 126.3, 136.5 ); - SetSkill( SkillName.Tactics, 128.5, 143.8 ); - SetSkill( SkillName.MagicResist, 102.8, 117.9 ); - SetSkill( SkillName.Anatomy, 127.5, 137.2 ); + Fame = 18000; + Karma = -18000; + } - Fame = 18000; - Karma = -18000; - } + public SirPatrick(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Sir Patrick corpse"; + public override string DefaultName => "Sir Patrick"; - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - if ( Utility.RandomDouble() < 0.1 ) - DrainLife(); - } + if ( Utility.RandomDouble() < 0.15 ) + c.DropItem( new DisintegratingThesisNotes() ); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + if ( Utility.RandomDouble() < 0.05 ) + c.DropItem( new AssassinChest() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - DrainLife(); - } + public override bool GivesMLMinorArtifact => true; - public virtual void DrainLife() - { - List list = new List(); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - foreach ( Mobile m in GetMobilesInRange( 2 ) ) - { - if ( m == this || !CanBeHarmful( m, false ) || ( Core.AOS && !InLOS( m ) ) ) - continue; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( m is BaseCreature bc ) - { - if ( bc.Controlled || bc.Summoned || bc.Team != Team ) - list.Add( bc ); - } - else if ( m.Player ) - { - list.Add( m ); - } - } + if (Utility.RandomDouble() < 0.1) + DrainLife(); + } - foreach ( Mobile m in list ) - { - DoHarmful( m ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - m.FixedParticles( 0x374A, 10, 15, 5013, 0x455, 0, EffectLayer.Waist ); - m.PlaySound( 0x1EA ); + if (Utility.RandomDouble() < 0.1) + DrainLife(); + } - int drain = Utility.RandomMinMax( 14, 30 ); + public virtual void DrainLife() + { + List list = new List(); - Hits += drain; - m.Damage( drain, this ); - } - } + foreach (Mobile m in GetMobilesInRange(2)) + { + if (m == this || !CanBeHarmful(m, false) || Core.AOS && !InLOS(m)) + continue; - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if (m is BaseCreature bc) + { + if (bc.Controlled || bc.Summoned || bc.Team != Team) + list.Add(bc); + } + else if (m.Player) + { + list.Add(m); + } + } - if ( Utility.RandomDouble() < 0.15 ) - c.DropItem( new DisintegratingThesisNotes() ); + foreach (Mobile m in list) + { + DoHarmful(m); - if ( Utility.RandomDouble() < 0.05 ) - c.DropItem( new AssassinChest() ); - } - */ + m.FixedParticles(0x374A, 10, 15, 5013, 0x455, 0, EffectLayer.Waist); + m.PlaySound(0x1EA); - public override bool GivesMLMinorArtifact => true; + int drain = Utility.RandomMinMax(14, 30); - public SirPatrick( Serial serial ) - : base( serial ) - { - } + Hits += drain; + m.Damage(drain, this); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Abscess.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Abscess.cs index 5b28a875a..975288dc9 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Abscess.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Abscess.cs @@ -2,77 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class Abscess : Hydra - { - public override string CorpseName => "an Abscess corpse"; - public override string DefaultName => "Abscess"; + public class Abscess : Hydra + { + [Constructible] + public Abscess() + { + IsParagon = true; - [Constructible] - public Abscess() - { - IsParagon = true; + Hue = 0x8FD; - Hue = 0x8FD; + SetStr(845, 871); + SetDex(121, 134); + SetInt(124, 142); - SetStr( 845, 871 ); - SetDex( 121, 134 ); - SetInt( 124, 142 ); + SetHits(7470, 7540); - SetHits( 7470, 7540 ); + SetDamage(26, 31); - SetDamage( 26, 31 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Cold, 10); + SetDamageType(ResistanceType.Poison, 10); + SetDamageType(ResistanceType.Energy, 10); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Cold, 10 ); - SetDamageType( ResistanceType.Poison, 10 ); - SetDamageType( ResistanceType.Energy, 10 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 45); + SetResistance(ResistanceType.Energy, 35, 45); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 45 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetSkill(SkillName.Wrestling, 132.3, 143.8); + SetSkill(SkillName.Tactics, 121.0, 130.5); + SetSkill(SkillName.MagicResist, 102.9, 119.0); + SetSkill(SkillName.Anatomy, 91.8, 94.3); - SetSkill( SkillName.Wrestling, 132.3, 143.8 ); - SetSkill( SkillName.Tactics, 121.0, 130.5 ); - SetSkill( SkillName.MagicResist, 102.9, 119.0 ); - SetSkill( SkillName.Anatomy, 91.8, 94.3 ); + // TODO: Fame/Karma + } - // TODO: Fame/Karma - } + public Abscess(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 4 ); - } + public override string CorpseName => "an Abscess corpse"; + public override string DefaultName => "Abscess"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool GivesMLMinorArtifact => true; - c.DropItem( new AbscessTail() ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 4); + } - public override bool GivesMLMinorArtifact => true; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public Abscess( Serial serial ) - : base( serial ) - { - } + c.DropItem(new AbscessTail()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Coil.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Coil.cs index 3acda862b..a6ab8c2db 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Coil.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Coil.cs @@ -2,101 +2,104 @@ using Server.Items; namespace Server.Mobiles { - public class Coil : SilverSerpent - { - public override string CorpseName => "a Coil corpse"; - // TODO: Check faction allegiance + public class Coil : SilverSerpent + { + [Constructible] + public Coil() + { + IsParagon = true; - public override string DefaultName => "Coil"; + Hue = 0x3F; - [Constructible] - public Coil() - { - IsParagon = true; + SetStr(205, 343); + SetDex(202, 283); + SetInt(88, 142); - Hue = 0x3F; + SetHits(628, 1291); - SetStr( 205, 343 ); - SetDex( 202, 283 ); - SetInt( 88, 142 ); + SetDamage(19, 28); - SetHits( 628, 1291 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamage( 19, 28 ); + SetResistance(ResistanceType.Physical, 56, 62); + SetResistance(ResistanceType.Fire, 25, 30); + SetResistance(ResistanceType.Cold, 25, 30); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 25, 30); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetSkill(SkillName.Wrestling, 124.5, 141.3); + SetSkill(SkillName.Tactics, 130.2, 142.0); + SetSkill(SkillName.MagicResist, 102.3, 113.0); + SetSkill(SkillName.Anatomy, 120.8, 138.1); + SetSkill(SkillName.Poisoning, 110.1, 133.4); - SetResistance( ResistanceType.Physical, 56, 62 ); - SetResistance( ResistanceType.Fire, 25, 30 ); - SetResistance( ResistanceType.Cold, 25, 30 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 25, 30 ); + // TODO: Fame/Karma - SetSkill( SkillName.Wrestling, 124.5, 141.3 ); - SetSkill( SkillName.Tactics, 130.2, 142.0 ); - SetSkill( SkillName.MagicResist, 102.3, 113.0 ); - SetSkill( SkillName.Anatomy, 120.8, 138.1 ); - SetSkill( SkillName.Poisoning, 110.1, 133.4 ); + PackGem(2); + PackItem(new Bone()); + } - // TODO: Fame/Karma + public Coil(Serial serial) + : base(serial) + { + } - PackGem( 2 ); - PackItem( new Bone() ); - } + public override string CorpseName => "a Coil corpse"; + // TODO: Check faction allegiance - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string DefaultName => "Coil"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.MortalStrike; + public override Poison HitPoison => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; + public override bool GivesMLMinorArtifact => true; + public override int Hides => 48; + public override int Meat => 1; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - c.DropItem( new CoilsFang() ); + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.MortalStrike; + } - /* - // TODO: uncomment once added - if ( Utility.RandomDouble() < 0.025 ) - { - switch ( Utility.Random( 5 ) ) - { - case 0: c.DropItem( new AssassinChest() ); break; - case 1: c.DropItem( new DeathGloves() ); break; - case 2: c.DropItem( new LeafweaveLegs() ); break; - case 3: c.DropItem( new HunterLegs() ); break; - case 4: c.DropItem( new MyrmidonLegs() ); break; - } - } - */ - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override Poison HitPoison => Poison.Lethal; - public override Poison PoisonImmune => Poison.Lethal; - public override bool GivesMLMinorArtifact => true; - public override int Hides => 48; - public override int Meat => 1; + c.DropItem(new CoilsFang()); - public Coil( Serial serial ) - : base( serial ) - { - } + /* + // TODO: uncomment once added + if ( Utility.RandomDouble() < 0.025 ) + { + switch ( Utility.Random( 5 ) ) + { + case 0: c.DropItem( new AssassinChest() ); break; + case 1: c.DropItem( new DeathGloves() ); break; + case 2: c.DropItem( new LeafweaveLegs() ); break; + case 3: c.DropItem( new HunterLegs() ); break; + case 4: c.DropItem( new MyrmidonLegs() ); break; + } + } + */ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/EnslavedSatyr.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/EnslavedSatyr.cs index 379d8b732..659b86d4d 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/EnslavedSatyr.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/EnslavedSatyr.cs @@ -1,43 +1,43 @@ namespace Server.Mobiles { - public class EnslavedSatyr : Satyr - { - public override string CorpseName => "an enslaved satyr corpse"; - public override string DefaultName => "an enslaved satyr"; + public class EnslavedSatyr : Satyr + { + [Constructible] + public EnslavedSatyr() + { + } - [Constructible] - public EnslavedSatyr() - { - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public EnslavedSatyr(Serial serial) + : base(serial) + { + } - public EnslavedSatyr( Serial serial ) - : base( serial ) - { - } + public override string CorpseName => "an enslaved satyr corpse"; + public override string DefaultName => "an enslaved satyr"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Hydra.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Hydra.cs index d24974c09..78180591f 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Hydra.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Hydra.cs @@ -2,89 +2,89 @@ using Server.Items; namespace Server.Mobiles { - public class Hydra : BaseCreature - { - public override string CorpseName => "a hydra corpse"; - public override string DefaultName => "a hydra"; + public class Hydra : BaseCreature + { + [Constructible] + public Hydra() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x109; + BaseSoundID = 0x16A; - [Constructible] - public Hydra() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x109; - BaseSoundID = 0x16A; + SetStr(801, 828); + SetDex(102, 118); + SetInt(102, 120); - SetStr( 801, 828 ); - SetDex( 102, 118 ); - SetInt( 102, 120 ); + SetHits(1480, 1500); - SetHits( 1480, 1500 ); + SetDamage(21, 26); - SetDamage( 21, 26 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Cold, 10); + SetDamageType(ResistanceType.Poison, 10); + SetDamageType(ResistanceType.Energy, 10); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Cold, 10 ); - SetDamageType( ResistanceType.Poison, 10 ); - SetDamageType( ResistanceType.Energy, 10 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 70, 85); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 43); + SetResistance(ResistanceType.Energy, 36, 45); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 70, 85 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 43 ); - SetResistance( ResistanceType.Energy, 36, 45 ); + SetSkill(SkillName.Wrestling, 103.5, 117.4); + SetSkill(SkillName.Tactics, 100.1, 109.8); + SetSkill(SkillName.MagicResist, 85.5, 98.5); + SetSkill(SkillName.Anatomy, 75.4, 79.8); - SetSkill( SkillName.Wrestling, 103.5, 117.4 ); - SetSkill( SkillName.Tactics, 100.1, 109.8 ); - SetSkill( SkillName.MagicResist, 85.5, 98.5 ); - SetSkill( SkillName.Anatomy, 75.4, 79.8 ); + // TODO: Fame/Karma + } - // TODO: Fame/Karma - } + public Hydra(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a hydra corpse"; + public override string DefaultName => "a hydra"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool HasBreath => true; + public override int Hides => 40; + public override int Meat => 19; + public override int TreasureMapLevel => 5; - c.DropItem( new HydraScale() ); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - /* - // TODO: uncomment once added - if ( Utility.RandomDouble() < 0.2 ) - c.DropItem( new ParrotItem() ); + public override void OnDeath(Container c) + { + base.OnDeath(c); - if ( Utility.RandomDouble() < 0.05 ) - c.DropItem( new ThorvaldsMedallion() ); - */ - } + c.DropItem(new HydraScale()); - public override bool HasBreath => true; - public override int Hides => 40; - public override int Meat => 19; - public override int TreasureMapLevel => 5; + /* + // TODO: uncomment once added + if ( Utility.RandomDouble() < 0.2 ) + c.DropItem( new ParrotItem() ); - public Hydra( Serial serial ) - : base( serial ) - { - } + if ( Utility.RandomDouble() < 0.05 ) + c.DropItem( new ThorvaldsMedallion() ); + */ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/InsaneDryad.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/InsaneDryad.cs index 38fdd6d9b..15ea42d33 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/InsaneDryad.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/InsaneDryad.cs @@ -1,46 +1,46 @@ namespace Server.Mobiles { - public class InsaneDryad : MLDryad - { - public override string CorpseName => "an insane dryad corpse"; - public override bool InitialInnocent => false; + public class InsaneDryad : MLDryad + { + [Constructible] + public InsaneDryad() + { + // TODO: Perhaps these should have negative karma? + } - public override string DefaultName => "an insane dryad"; + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - [Constructible] - public InsaneDryad() - { - // TODO: Perhaps these should have negative karma? - } + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public InsaneDryad(Serial serial) + : base(serial) + { + } - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override string CorpseName => "an insane dryad corpse"; + public override bool InitialInnocent => false; - public InsaneDryad( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "an insane dryad"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Saliva.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Saliva.cs index c32efcbca..88bf754fa 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Saliva.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Saliva.cs @@ -2,75 +2,75 @@ using Server.Items; namespace Server.Mobiles { - public class Saliva : Harpy - { - public override string CorpseName => "a Saliva corpse"; - public override string DefaultName => "Saliva"; + public class Saliva : Harpy + { + [Constructible] + public Saliva() + { + // TODO: Not a paragon? No ML arties? + // It moves like a paragon on OSI... - [Constructible] - public Saliva() - { - // TODO: Not a paragon? No ML arties? - // It moves like a paragon on OSI... + Hue = 0x11E; - Hue = 0x11E; + SetStr(110, 206); + SetDex(123, 222); + SetInt(80, 127); - SetStr( 110, 206 ); - SetDex( 123, 222 ); - SetInt( 80, 127 ); + SetHits(409, 842); - SetHits( 409, 842 ); + SetDamage(20, 22); - SetDamage( 20, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 46, 48); + SetResistance(ResistanceType.Fire, 32, 40); + SetResistance(ResistanceType.Cold, 34, 49); + SetResistance(ResistanceType.Poison, 40, 48); + SetResistance(ResistanceType.Energy, 35, 39); - SetResistance( ResistanceType.Physical, 46, 48 ); - SetResistance( ResistanceType.Fire, 32, 40 ); - SetResistance( ResistanceType.Cold, 34, 49 ); - SetResistance( ResistanceType.Poison, 40, 48 ); - SetResistance( ResistanceType.Energy, 35, 39 ); + SetSkill(SkillName.Wrestling, 106.4, 128.8); + SetSkill(SkillName.Tactics, 129.9, 141.0); + SetSkill(SkillName.MagicResist, 84.3, 105.0); - SetSkill( SkillName.Wrestling, 106.4, 128.8 ); - SetSkill( SkillName.Tactics, 129.9, 141.0 ); - SetSkill( SkillName.MagicResist, 84.3, 105.0 ); + // TODO: Fame/Karma? + } - // TODO: Fame/Karma? - } + public Saliva(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Saliva corpse"; + public override string DefaultName => "Saliva"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - c.DropItem( new SalivasFeather() ); + public override void OnDeath(Container c) + { + base.OnDeath(c); - // TODO: uncomment once added - //if ( Utility.RandomDouble() < 0.1 ) - // c.DropItem( new ParrotItem() ); - } + c.DropItem(new SalivasFeather()); - public Saliva( Serial serial ) - : base( serial ) - { - } + // TODO: uncomment once added + //if ( Utility.RandomDouble() < 0.1 ) + // c.DropItem( new ParrotItem() ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Tangle.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Tangle.cs index 737c9028a..a9125238e 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Tangle.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Tangle.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class Tangle : BogThing - { - public override string CorpseName => "a Tangle corpse"; - public override string DefaultName => "Tangle"; + public class Tangle : BogThing + { + [Constructible] + public Tangle() + { + // TODO: Not a paragon? No ML arties? + // It moves like a paragon on OSI... - [Constructible] - public Tangle() - { - // TODO: Not a paragon? No ML arties? - // It moves like a paragon on OSI... + Hue = 0x21; - Hue = 0x21; + SetStr(870, 940); + SetDex(58, 74); + SetInt(46, 58); - SetStr( 870, 940 ); - SetDex( 58, 74 ); - SetInt( 46, 58 ); + SetHits(2468, 2733); + SetMana(8, 12); - SetHits( 2468, 2733 ); - SetMana( 8, 12 ); + SetDamage(15, 28); - SetDamage( 15, 28 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetResistance(ResistanceType.Physical, 50, 57); + SetResistance(ResistanceType.Fire, 40, 43); + SetResistance(ResistanceType.Cold, 30, 35); + SetResistance(ResistanceType.Poison, 61, 69); + SetResistance(ResistanceType.Energy, 41, 45); - SetResistance( ResistanceType.Physical, 50, 57 ); - SetResistance( ResistanceType.Fire, 40, 43 ); - SetResistance( ResistanceType.Cold, 30, 35 ); - SetResistance( ResistanceType.Poison, 61, 69 ); - SetResistance( ResistanceType.Energy, 41, 45 ); + SetSkill(SkillName.Wrestling, 77.8, 94.6); + SetSkill(SkillName.Tactics, 90.6, 100.4); + SetSkill(SkillName.MagicResist, 108.4, 114.0); - SetSkill( SkillName.Wrestling, 77.8, 94.6 ); - SetSkill( SkillName.Tactics, 90.6, 100.4 ); - SetSkill( SkillName.MagicResist, 108.4, 114.0 ); + // TODO: Fame/Karma? + } - // TODO: Fame/Karma? - } + public Tangle(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Tangle corpse"; + public override string DefaultName => "Tangle"; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override Poison PoisonImmune => Poison.Lethal; - if ( Utility.RandomDouble() < 0.3 ) - c.DropItem( new TaintedSeeds() ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public override Poison PoisonImmune => Poison.Lethal; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public Tangle( Serial serial ) - : base( serial ) - { - } + if (Utility.RandomDouble() < 0.3) + c.DropItem(new TaintedSeeds()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Thrasher.cs b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Thrasher.cs index 413c699af..ccd4eff03 100644 --- a/Scripts/Mobiles/Monsters/ML/Blighted Grove/Thrasher.cs +++ b/Scripts/Mobiles/Monsters/ML/Blighted Grove/Thrasher.cs @@ -2,76 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public class Thrasher : Alligator - { - public override string CorpseName => "a Thrasher corpse"; - public override string DefaultName => "Thrasher"; + public class Thrasher : Alligator + { + [Constructible] + public Thrasher() + { + IsParagon = true; - [Constructible] - public Thrasher() - { - IsParagon = true; + Hue = 0x497; - Hue = 0x497; + SetStr(93, 327); + SetDex(7, 201); + SetInt(15, 67); - SetStr( 93, 327 ); - SetDex( 7, 201 ); - SetInt( 15, 67 ); + SetHits(260, 984); + SetStam(56, 75); + SetMana(25, 30); - SetHits( 260, 984 ); - SetStam( 56, 75 ); - SetMana( 25, 30 ); + SetDamage(20, 30); - SetDamage( 20, 30 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 50, 55); + SetResistance(ResistanceType.Fire, 25, 29); + SetResistance(ResistanceType.Poison, 25, 28); - SetResistance( ResistanceType.Physical, 50, 55 ); - SetResistance( ResistanceType.Fire, 25, 29 ); - SetResistance( ResistanceType.Poison, 25, 28 ); + SetSkill(SkillName.Wrestling, 101.2, 118.3); + SetSkill(SkillName.Tactics, 96.3, 117.3); + SetSkill(SkillName.MagicResist, 102.4, 118.6); - SetSkill( SkillName.Wrestling, 101.2, 118.3 ); - SetSkill( SkillName.Tactics, 96.3, 117.3 ); - SetSkill( SkillName.MagicResist, 102.4, 118.6 ); + // TODO: Fame/Karma + } - // TODO: Fame/Karma - } + public Thrasher(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 4 ); - } + public override string CorpseName => "a Thrasher corpse"; + public override string DefaultName => "Thrasher"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ArmorIgnore; + public override bool GivesMLMinorArtifact => true; + public override int Hides => 48; + public override int Meat => 1; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 4); + } - c.DropItem( new ThrashersTail() ); - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ArmorIgnore; + } - public override bool GivesMLMinorArtifact => true; - public override int Hides => 48; - public override int Meat => 1; + public override void OnDeath(Container c) + { + base.OnDeath(c); - public Thrasher( Serial serial ) - : base( serial ) - { - } + c.DropItem(new ThrashersTail()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/FetidEssence.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/FetidEssence.cs index 7d21d90ac..7b91c4ec2 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/FetidEssence.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/FetidEssence.cs @@ -1,107 +1,107 @@ namespace Server.Mobiles { - public class FetidEssence : BaseCreature - { - public override string CorpseName => "a fetid essence corpse"; - public override string DefaultName => "a fetid essence"; + public class FetidEssence : BaseCreature + { + [Constructible] + public FetidEssence() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 273; - [Constructible] - public FetidEssence () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 273; + SetStr(101, 150); + SetDex(210, 250); + SetInt(451, 550); - SetStr( 101, 150 ); - SetDex( 210, 250 ); - SetInt( 451, 550 ); + SetHits(551, 650); - SetHits( 551, 650 ); + SetDamage(21, 25); - SetDamage( 21, 25 ); + SetDamageType(ResistanceType.Physical, 30); + SetDamageType(ResistanceType.Poison, 70); - SetDamageType( ResistanceType.Physical, 30 ); - SetDamageType( ResistanceType.Poison, 70 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 70, 90); + SetResistance(ResistanceType.Energy, 75, 80); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 70, 90 ); - SetResistance( ResistanceType.Energy, 75, 80 ); + SetSkill(SkillName.Meditation, 91.4, 99.4); + SetSkill(SkillName.EvalInt, 88.5, 92.3); + SetSkill(SkillName.Magery, 97.9, 101.7); + SetSkill(SkillName.Poisoning, 100); + SetSkill(SkillName.Anatomy, 0, 4.5); + SetSkill(SkillName.MagicResist, 103.5, 108.8); + SetSkill(SkillName.Tactics, 81.0, 84.6); + SetSkill(SkillName.Wrestling, 81.3, 83.9); - SetSkill(SkillName.Meditation, 91.4, 99.4 ); - SetSkill(SkillName.EvalInt, 88.5, 92.3 ); - SetSkill(SkillName.Magery, 97.9, 101.7 ); - SetSkill(SkillName.Poisoning, 100 ); - SetSkill(SkillName.Anatomy, 0, 4.5 ); - SetSkill( SkillName.MagicResist, 103.5, 108.8 ); - SetSkill( SkillName.Tactics, 81.0, 84.6 ); - SetSkill( SkillName.Wrestling, 81.3, 83.9 ); + Fame = 3700; // Guessed + Karma = -3700; // Guessed + } - Fame = 3700; // Guessed - Karma = -3700; // Guessed - } + public FetidEssence(Serial serial) : base(serial) + { + } - public override void GenerateLoot() // Need to verify - { - AddLoot( LootPack.FilthyRich ); - } + public override string CorpseName => "a fetid essence corpse"; + public override string DefaultName => "a fetid essence"; - public override Poison HitPoison => Poison.Deadly; - public override Poison PoisonImmune => Poison.Deadly; + public override Poison HitPoison => Poison.Deadly; + public override Poison PoisonImmune => Poison.Deadly; - public override int GetAngerSound() - { - return 0x56d; - } + public override void GenerateLoot() // Need to verify + { + AddLoot(LootPack.FilthyRich); + } - public override int GetIdleSound() - { - return 0x56b; - } + public override int GetAngerSound() + { + return 0x56d; + } - public override int GetAttackSound() - { - return 0x56c; - } + public override int GetIdleSound() + { + return 0x56b; + } - public override int GetHurtSound() - { - return 0x56c; - } + public override int GetAttackSound() + { + return 0x56c; + } - public override int GetDeathSound() - { - return 0x56e; - } + public override int GetHurtSound() + { + return 0x56c; + } - public FetidEssence ( Serial serial ) : base( serial ) - { - } + public override int GetDeathSound() + { + return 0x56e; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - /*private class InternalTimer : Timer - { - private Mobile m_From; - private Mobile m_Mobile; - private int m_Count; + /*private class InternalTimer : Timer + { + private Mobile m_From; + private Mobile m_Mobile; + private int m_Count; - public InternalTimer( Mobile from, Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_From = from; - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } + public InternalTimer( Mobile from, Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) + { + m_From = from; + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - }*/ - } -} + }*/ + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/InterredGrizzle .cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/InterredGrizzle .cs index 18c9d23d5..5f34955e7 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/InterredGrizzle .cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/InterredGrizzle .cs @@ -1,174 +1,174 @@ namespace Server.Mobiles { - public class InterredGrizzle : BaseCreature - { - public override string CorpseName => "an interred grizzle corpse"; - public override string DefaultName => "a interred grizzle"; + public class InterredGrizzle : BaseCreature + { + [Constructible] + public InterredGrizzle() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 259; - [Constructible] - public InterredGrizzle () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 259; + SetStr(451, 500); + SetDex(201, 250); + SetInt(801, 850); - SetStr( 451, 500 ); - SetDex( 201, 250 ); - SetInt( 801, 850 ); + SetHits(1500); + SetStam(150); - SetHits( 1500 ); - SetStam( 150 ); + SetDamage(16, 19); - SetDamage( 16, 19 ); + SetDamageType(ResistanceType.Physical, 30); + SetDamageType(ResistanceType.Fire, 70); - SetDamageType( ResistanceType.Physical, 30 ); - SetDamageType( ResistanceType.Fire, 70 ); + SetResistance(ResistanceType.Physical, 35, 55); + SetResistance(ResistanceType.Fire, 20, 65); + SetResistance(ResistanceType.Cold, 55, 80); + SetResistance(ResistanceType.Poison, 20, 35); + SetResistance(ResistanceType.Energy, 60, 80); - SetResistance( ResistanceType.Physical, 35, 55 ); - SetResistance( ResistanceType.Fire, 20, 65 ); - SetResistance( ResistanceType.Cold, 55, 80 ); - SetResistance( ResistanceType.Poison, 20, 35 ); - SetResistance( ResistanceType.Energy, 60, 80 ); + SetSkill(SkillName.Meditation, 77.7, 84.0); + SetSkill(SkillName.EvalInt, 72.2, 79.6); + SetSkill(SkillName.Magery, 83.7, 89.6); + SetSkill(SkillName.Poisoning, 0); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 80.2, 87.3); + SetSkill(SkillName.Tactics, 104.5, 105.1); + SetSkill(SkillName.Wrestling, 105.1, 109.4); - SetSkill(SkillName.Meditation, 77.7, 84.0 ); - SetSkill(SkillName.EvalInt, 72.2, 79.6 ); - SetSkill(SkillName.Magery, 83.7, 89.6); - SetSkill(SkillName.Poisoning, 0 ); - SetSkill(SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 80.2, 87.3 ); - SetSkill( SkillName.Tactics, 104.5, 105.1 ); - SetSkill( SkillName.Wrestling, 105.1, 109.4 ); + Fame = 3700; // Guessed + Karma = -3700; // Guessed + } + /* + public override bool OnBeforeDeath() + { + SpillAcid( 1, 4, 10, 6, 10 ); - Fame = 3700; // Guessed - Karma = -3700; // Guessed - } + return base.OnBeforeDeath(); + } + */ - public override void GenerateLoot() // -- Need to verify - { - AddLoot( LootPack.FilthyRich ); - } + public InterredGrizzle(Serial serial) : base(serial) + { + } - // TODO: Acid Blood - /* - * Message: 1070820 - * Spits pool of acid (blood, hue 0x3F), hits lost 6-10 per second/step - * Damage is resistable (physical) - * Acid last 10 seconds - */ + public override string CorpseName => "an interred grizzle corpse"; + public override string DefaultName => "a interred grizzle"; - public override int GetAngerSound() - { - return 0x581; - } + public override void GenerateLoot() // -- Need to verify + { + AddLoot(LootPack.FilthyRich); + } - public override int GetIdleSound() - { - return 0x582; - } + // TODO: Acid Blood + /* + * Message: 1070820 + * Spits pool of acid (blood, hue 0x3F), hits lost 6-10 per second/step + * Damage is resistable (physical) + * Acid last 10 seconds + */ - public override int GetAttackSound() - { - return 0x580; - } + public override int GetAngerSound() + { + return 0x581; + } - public override int GetHurtSound() - { - return 0x583; - } + public override int GetIdleSound() + { + return 0x582; + } - public override int GetDeathSound() - { - return 0x584; - } + public override int GetAttackSound() + { + return 0x580; + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( Utility.RandomDouble() < 0.1 ) - DropOoze(); + public override int GetHurtSound() + { + return 0x583; + } - base.OnDamage( amount, from, willKill ); - } + public override int GetDeathSound() + { + return 0x584; + } - private int RandomPoint( int mid ) - { - return ( mid + Utility.RandomMinMax( -2, 2 ) ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (Utility.RandomDouble() < 0.1) + DropOoze(); - public virtual Point3D GetSpawnPosition( int range ) - { - return GetSpawnPosition( Location, Map, range ); - } + base.OnDamage(amount, from, willKill); + } - public virtual Point3D GetSpawnPosition( Point3D from, Map map, int range ) - { - if ( map == null ) - return from; + private int RandomPoint(int mid) + { + return mid + Utility.RandomMinMax(-2, 2); + } - Point3D loc = new Point3D( ( RandomPoint( X ) ), ( RandomPoint( Y ) ), Z ); + public virtual Point3D GetSpawnPosition(int range) + { + return GetSpawnPosition(Location, Map, range); + } - loc.Z = Map.GetAverageZ( loc.X, loc.Y ); + public virtual Point3D GetSpawnPosition(Point3D from, Map map, int range) + { + if (map == null) + return from; - return loc; - } + Point3D loc = new Point3D(RandomPoint(X), RandomPoint(Y), Z); - public virtual void DropOoze() - { - int amount = Utility.RandomMinMax( 1, 3 ); - bool corrosive = Utility.RandomBool(); + loc.Z = Map.GetAverageZ(loc.X, loc.Y); - for( int i = 0; i < amount; i++ ) - { - Item ooze = new StainedOoze( corrosive ); - Point3D p = new Point3D( Location ); + return loc; + } - for( int j = 0; j < 5; j++ ) - { - p = GetSpawnPosition( 2 ); - bool found = false; + public virtual void DropOoze() + { + int amount = Utility.RandomMinMax(1, 3); + bool corrosive = Utility.RandomBool(); - foreach( Item item in Map.GetItemsInRange( p, 0 ) ) - if ( item is StainedOoze ) - { - found = true; - break; - } + for (int i = 0; i < amount; i++) + { + Item ooze = new StainedOoze(corrosive); + Point3D p = new Point3D(Location); - if ( !found ) - break; - } + for (int j = 0; j < 5; j++) + { + p = GetSpawnPosition(2); + bool found = false; - ooze.MoveToWorld( p, Map ); - } + foreach (Item item in Map.GetItemsInRange(p, 0)) + if (item is StainedOoze) + { + found = true; + break; + } - if ( Combatant != null ) - { - if ( corrosive ) - Combatant.SendLocalizedMessage( 1072071 ); // A corrosive gas seeps out of your enemy's skin! - else - Combatant.SendLocalizedMessage( 1072072 ); // A poisonous gas seeps out of your enemy's skin! - } - } - /* - public override bool OnBeforeDeath() - { - SpillAcid( 1, 4, 10, 6, 10 ); + if (!found) + break; + } - return base.OnBeforeDeath(); - } - */ + ooze.MoveToWorld(p, Map); + } - public InterredGrizzle ( Serial serial ) : base( serial ) - { - } + if (Combatant != null) + { + if (corrosive) + Combatant.SendLocalizedMessage(1072071); // A corrosive gas seeps out of your enemy's skin! + else + Combatant.SendLocalizedMessage(1072072); // A poisonous gas seeps out of your enemy's skin! + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/MLDryad.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/MLDryad.cs index 3a5575c02..8501b26be 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/MLDryad.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/MLDryad.cs @@ -3,157 +3,162 @@ using Server.Engines.Plants; namespace Server.Mobiles { - public class MLDryad : BaseCreature - { - public override string CorpseName => "a dryad's corpse"; - public override bool InitialInnocent => true; + public class MLDryad : BaseCreature + { + [Constructible] + public MLDryad() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 266; + BaseSoundID = 0x57B; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + SetStr(132, 149); + SetDex(152, 168); + SetInt(251, 280); - public override string DefaultName => "a dryad"; + SetHits(304, 321); - [Constructible] - public MLDryad() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 266; - BaseSoundID = 0x57B; + SetDamage(11, 20); - SetStr( 132, 149 ); - SetDex( 152, 168 ); - SetInt( 251, 280 ); + SetDamageType(ResistanceType.Physical, 100); - SetHits( 304, 321 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 40, 45); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 25, 35); - SetDamage( 11, 20 ); + SetSkill(SkillName.Meditation, 80.0, 90.0); + SetSkill(SkillName.EvalInt, 70.0, 80.0); + SetSkill(SkillName.Magery, 70.0, 80.0); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 100.0, 120.0); + SetSkill(SkillName.Tactics, 70.0, 80.0); + SetSkill(SkillName.Wrestling, 70.0, 80.0); - SetDamageType( ResistanceType.Physical, 100 ); + Fame = 5000; + Karma = 5000; - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 40, 45 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + VirtualArmor = 28; // Don't know what it should be - SetSkill( SkillName.Meditation, 80.0, 90.0 ); - SetSkill( SkillName.EvalInt, 70.0, 80.0 ); - SetSkill( SkillName.Magery, 70.0, 80.0 ); - SetSkill( SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 100.0, 120.0 ); - SetSkill( SkillName.Tactics, 70.0, 80.0 ); - SetSkill( SkillName.Wrestling, 70.0, 80.0 ); + if (Core.ML && Utility.RandomDouble() < .60) + PackItem(Seed.RandomPeculiarSeed(1)); - Fame = 5000; - Karma = 5000; + PackArcanceScroll(0.05); + } - VirtualArmor = 28; // Don't know what it should be + public MLDryad(Serial serial) : base(serial) + { + } - if ( Core.ML && Utility.RandomDouble() < .60 ) - PackItem( Seed.RandomPeculiarSeed( 1 ) ); + public override string CorpseName => "a dryad's corpse"; + public override bool InitialInnocent => true; - PackArcanceScroll( 0.05 ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override void GenerateLoot() - { - AddLoot( LootPack.MlRich ); - } + public override string DefaultName => "a dryad"; - public override int Meat => 1; + public override int Meat => 1; - public override void OnThink() - { - base.OnThink(); + public override void GenerateLoot() + { + AddLoot(LootPack.MlRich); + } - AreaPeace(); - AreaUndress(); - } + public override void OnThink() + { + base.OnThink(); - #region Area Peace - private DateTime m_NextPeace; + AreaPeace(); + AreaUndress(); + } - public void AreaPeace() - { - if ( Combatant == null || Deleted || !Alive || m_NextPeace > DateTime.UtcNow || 0.1 < Utility.RandomDouble() ) - return; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - TimeSpan duration = TimeSpan.FromSeconds( Utility.RandomMinMax( 20, 80 ) ); + writer.Write(0); // version + } - foreach ( Mobile m in GetMobilesInRange( RangePerception ) ) - { - PlayerMobile p = m as PlayerMobile; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( IsValidTarget( p ) ) - { - p.PeacedUntil = DateTime.UtcNow + duration; - p.SendLocalizedMessage( 1072065 ); // You gaze upon the dryad's beauty, and forget to continue battling! - p.FixedParticles( 0x376A, 1, 20, 0x7F5, EffectLayer.Waist ); - p.Combatant = null; - } - } + int version = reader.ReadInt(); + } - m_NextPeace = DateTime.UtcNow + TimeSpan.FromSeconds( 10 ); - PlaySound( 0x1D3 ); - } + #region Area Peace - public bool IsValidTarget( PlayerMobile m ) - { - if ( m != null && m.PeacedUntil < DateTime.UtcNow && !m.Hidden && m.AccessLevel == AccessLevel.Player && CanBeHarmful( m ) ) - return true; + private DateTime m_NextPeace; - return false; - } - #endregion + public void AreaPeace() + { + if (Combatant == null || Deleted || !Alive || m_NextPeace > DateTime.UtcNow || 0.1 < Utility.RandomDouble()) + return; - #region Undress - private DateTime m_NextUndress; + TimeSpan duration = TimeSpan.FromSeconds(Utility.RandomMinMax(20, 80)); - public void AreaUndress() - { - if ( Combatant == null || Deleted || !Alive || m_NextUndress > DateTime.UtcNow || 0.005 < Utility.RandomDouble() ) - return; + foreach (Mobile m in GetMobilesInRange(RangePerception)) + { + PlayerMobile p = m as PlayerMobile; - foreach ( Mobile m in GetMobilesInRange( RangePerception ) ) - { - if ( m != null && m.Player && !m.Female && !m.Hidden && m.AccessLevel == AccessLevel.Player && CanBeHarmful( m ) ) - { - UndressItem( m, Layer.OuterTorso ); - UndressItem( m, Layer.InnerTorso ); - UndressItem( m, Layer.MiddleTorso ); - UndressItem( m, Layer.Pants ); - UndressItem( m, Layer.Shirt ); + if (IsValidTarget(p)) + { + p.PeacedUntil = DateTime.UtcNow + duration; + p.SendLocalizedMessage(1072065); // You gaze upon the dryad's beauty, and forget to continue battling! + p.FixedParticles(0x376A, 1, 20, 0x7F5, EffectLayer.Waist); + p.Combatant = null; + } + } - m.SendLocalizedMessage( 1072197 ); // The dryad's beauty makes your blood race. Your clothing is too confining. - } - } + m_NextPeace = DateTime.UtcNow + TimeSpan.FromSeconds(10); + PlaySound(0x1D3); + } - m_NextUndress = DateTime.UtcNow + TimeSpan.FromMinutes( 1 ); - } + public bool IsValidTarget(PlayerMobile m) + { + if (m != null && m.PeacedUntil < DateTime.UtcNow && !m.Hidden && m.AccessLevel == AccessLevel.Player && + CanBeHarmful(m)) + return true; - public void UndressItem( Mobile m, Layer layer ) - { - Item item = m.FindItemOnLayer( layer ); + return false; + } - if ( item != null && item.Movable ) - m.PlaceInBackpack( item ); - } - #endregion + #endregion - public MLDryad( Serial serial ) : base( serial ) - { - } + #region Undress - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private DateTime m_NextUndress; - writer.Write( (int) 0 ); // version - } + public void AreaUndress() + { + if (Combatant == null || Deleted || !Alive || m_NextUndress > DateTime.UtcNow || 0.005 < Utility.RandomDouble()) + return; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + foreach (Mobile m in GetMobilesInRange(RangePerception)) + if (m != null && m.Player && !m.Female && !m.Hidden && m.AccessLevel == AccessLevel.Player && + CanBeHarmful(m)) + { + UndressItem(m, Layer.OuterTorso); + UndressItem(m, Layer.InnerTorso); + UndressItem(m, Layer.MiddleTorso); + UndressItem(m, Layer.Pants); + UndressItem(m, Layer.Shirt); - int version = reader.ReadInt(); - } - } -} + m.SendLocalizedMessage( + 1072197); // The dryad's beauty makes your blood race. Your clothing is too confining. + } + + m_NextUndress = DateTime.UtcNow + TimeSpan.FromMinutes(1); + } + + public void UndressItem(Mobile m, Layer layer) + { + Item item = m.FindItemOnLayer(layer); + + if (item != null && item.Movable) + m.PlaceInBackpack(item); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/Satyr.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/Satyr.cs index 2912760ce..d939f7b04 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/Satyr.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Magic/Satyr.cs @@ -3,229 +3,236 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Satyr : BaseCreature - { - public override string CorpseName => "a satyr's corpse"; - public override string DefaultName => "a satyr"; + public class Satyr : BaseCreature + { + [Constructible] + public Satyr() : base(AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 271; + BaseSoundID = 0x586; - [Constructible] - public Satyr() : base( AIType.AI_Animal, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 271; - BaseSoundID = 0x586; + SetStr(177, 195); + SetDex(251, 269); + SetInt(153, 170); - SetStr( 177, 195 ); - SetDex( 251, 269 ); - SetInt( 153, 170 ); + SetHits(350, 400); - SetHits( 350, 400 ); + SetDamage(13, 24); - SetDamage( 13, 24 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 55, 60); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 55, 60 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 55.0, 65.0); + SetSkill(SkillName.Tactics, 80.0, 100.0); + SetSkill(SkillName.Wrestling, 80.0, 100.0); - SetSkill( SkillName.MagicResist, 55.0, 65.0 ); - SetSkill( SkillName.Tactics, 80.0, 100.0 ); - SetSkill( SkillName.Wrestling, 80.0, 100.0 ); + Fame = 5000; + Karma = 0; - Fame = 5000; - Karma = 0; + VirtualArmor = 28; // Don't know what it should be - VirtualArmor = 28; // Don't know what it should be + PackArcanceScroll(0.05); + } - PackArcanceScroll( 0.05 ); - } + public Satyr(Serial serial) : base(serial) + { + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string CorpseName => "a satyr's corpse"; + public override string DefaultName => "a satyr"; - public override void GenerateLoot() - { - AddLoot( LootPack.MlRich ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override void OnThink() - { - base.OnThink(); + public override int Meat => 1; - Peace( Combatant ); - Undress( Combatant ); - Suppress( Combatant ); - Provoke( Combatant ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.MlRich); + } - #region Peace - private DateTime m_NextPeace; + public override void OnThink() + { + base.OnThink(); - public void Peace( Mobile target ) - { - if ( target == null || Deleted || !Alive || m_NextPeace > DateTime.UtcNow || 0.1 < Utility.RandomDouble() ) - return; + Peace(Combatant); + Undress(Combatant); + Suppress(Combatant); + Provoke(Combatant); + } - if ( target is PlayerMobile p && p.PeacedUntil < DateTime.UtcNow && !p.Hidden && CanBeHarmful( p ) ) - { - p.PeacedUntil = DateTime.UtcNow + TimeSpan.FromMinutes( 1 ); - p.SendLocalizedMessage( 500616 ); // You hear lovely music, and forget to continue battling! - p.FixedParticles( 0x376A, 1, 32, 0x15BD, EffectLayer.Waist ); - p.Combatant = null; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - PlaySound( 0x58D ); - } + writer.Write(0); // version + } - m_NextPeace = DateTime.UtcNow + TimeSpan.FromSeconds( 10 ); - } - #endregion + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - #region Suppress - private static Dictionary m_Suppressed = new Dictionary(); - private DateTime m_NextSuppress; + int version = reader.ReadInt(); + } - public void Suppress( Mobile target ) - { - if ( target == null || m_Suppressed.ContainsKey( target ) || Deleted || !Alive || m_NextSuppress > DateTime.UtcNow || 0.1 < Utility.RandomDouble() ) - return; + #region Peace - TimeSpan delay = TimeSpan.FromSeconds( Utility.RandomMinMax( 20, 80 ) ); + private DateTime m_NextPeace; - if ( !target.Hidden && CanBeHarmful( target ) ) - { - target.SendLocalizedMessage( 1072061 ); // You hear jarring music, suppressing your strength. + public void Peace(Mobile target) + { + if (target == null || Deleted || !Alive || m_NextPeace > DateTime.UtcNow || 0.1 < Utility.RandomDouble()) + return; - for ( int i = 0; i < target.Skills.Length; i++ ) - { - Skill s = target.Skills[ i ]; + if (target is PlayerMobile p && p.PeacedUntil < DateTime.UtcNow && !p.Hidden && CanBeHarmful(p)) + { + p.PeacedUntil = DateTime.UtcNow + TimeSpan.FromMinutes(1); + p.SendLocalizedMessage(500616); // You hear lovely music, and forget to continue battling! + p.FixedParticles(0x376A, 1, 32, 0x15BD, EffectLayer.Waist); + p.Combatant = null; - target.AddSkillMod( new TimedSkillMod( s.SkillName, true, s.Base * -0.28, delay ) ); - } + PlaySound(0x58D); + } - int count = (int) Math.Round( delay.TotalSeconds / 1.25 ); - Timer timer = new AnimateTimer( target, count ); - m_Suppressed.Add( target, timer ); - timer.Start(); + m_NextPeace = DateTime.UtcNow + TimeSpan.FromSeconds(10); + } - PlaySound( 0x58C ); - } + #endregion - m_NextSuppress = DateTime.UtcNow + TimeSpan.FromSeconds( 10 ); - } + #region Suppress - public static void SuppressRemove( Mobile target ) - { - if ( target != null && m_Suppressed[target] is Timer t ) - { - if ( t.Running ) - t.Stop(); + private static Dictionary m_Suppressed = new Dictionary(); + private DateTime m_NextSuppress; - m_Suppressed.Remove( target ); - } - } + public void Suppress(Mobile target) + { + if (target == null || m_Suppressed.ContainsKey(target) || Deleted || !Alive || + m_NextSuppress > DateTime.UtcNow || 0.1 < Utility.RandomDouble()) + return; - private class AnimateTimer : Timer - { - private Mobile m_Owner; - private int m_Count; + TimeSpan delay = TimeSpan.FromSeconds(Utility.RandomMinMax(20, 80)); - public AnimateTimer( Mobile owner, int count ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1.25 ) ) - { - m_Owner = owner; - m_Count = count; - } + if (!target.Hidden && CanBeHarmful(target)) + { + target.SendLocalizedMessage(1072061); // You hear jarring music, suppressing your strength. - protected override void OnTick() - { - if ( m_Owner.Deleted || !m_Owner.Alive || m_Count-- < 0 ) - { - SuppressRemove( m_Owner ); - } - else - m_Owner.FixedParticles( 0x376A, 1, 32, 0x15BD, EffectLayer.Waist ); - } - } - #endregion + for (int i = 0; i < target.Skills.Length; i++) + { + Skill s = target.Skills[i]; - #region Undress - private DateTime m_NextUndress; + target.AddSkillMod(new TimedSkillMod(s.SkillName, true, s.Base * -0.28, delay)); + } - public void Undress( Mobile target ) - { - if ( target == null || Deleted || !Alive || m_NextUndress > DateTime.UtcNow || 0.005 < Utility.RandomDouble() ) - return; + int count = (int)Math.Round(delay.TotalSeconds / 1.25); + Timer timer = new AnimateTimer(target, count); + m_Suppressed.Add(target, timer); + timer.Start(); - if ( target.Player && target.Female && !target.Hidden && CanBeHarmful( target ) ) - { - UndressItem( target, Layer.OuterTorso ); - UndressItem( target, Layer.InnerTorso ); - UndressItem( target, Layer.MiddleTorso ); - UndressItem( target, Layer.Pants ); - UndressItem( target, Layer.Shirt ); + PlaySound(0x58C); + } - target.SendLocalizedMessage( 1072196 ); // The satyr's music makes your blood race. Your clothing is too confining. - } + m_NextSuppress = DateTime.UtcNow + TimeSpan.FromSeconds(10); + } - m_NextUndress = DateTime.UtcNow + TimeSpan.FromMinutes( 1 ); - } + public static void SuppressRemove(Mobile target) + { + if (target != null && m_Suppressed[target] is Timer t) + { + if (t.Running) + t.Stop(); - public void UndressItem( Mobile m, Layer layer ) - { - Item item = m.FindItemOnLayer( layer ); + m_Suppressed.Remove(target); + } + } - if ( item != null && item.Movable ) - m.PlaceInBackpack( item ); - } - #endregion + private class AnimateTimer : Timer + { + private int m_Count; + private Mobile m_Owner; - #region Provoke - private DateTime m_NextProvoke; + public AnimateTimer(Mobile owner, int count) : base(TimeSpan.Zero, TimeSpan.FromSeconds(1.25)) + { + m_Owner = owner; + m_Count = count; + } - public void Provoke( Mobile target ) - { - if ( target == null || Deleted || !Alive || m_NextProvoke > DateTime.UtcNow || 0.05 < Utility.RandomDouble() ) - return; + protected override void OnTick() + { + if (m_Owner.Deleted || !m_Owner.Alive || m_Count-- < 0) + SuppressRemove(m_Owner); + else + m_Owner.FixedParticles(0x376A, 1, 32, 0x15BD, EffectLayer.Waist); + } + } - foreach ( Mobile m in GetMobilesInRange( RangePerception ) ) - { - if ( m is BaseCreature c ) - { - if ( c == this || c == target || c.Unprovokable || c.IsParagon || c.BardProvoked || c.AccessLevel != AccessLevel.Player || !c.CanBeHarmful( target ) ) - continue; + #endregion - c.Provoke( this, target, true ); + #region Undress - if ( target.Player ) - target.SendLocalizedMessage( 1072062 ); // You hear angry music, and start to fight. + private DateTime m_NextUndress; - PlaySound( 0x58A ); - break; - } - } + public void Undress(Mobile target) + { + if (target == null || Deleted || !Alive || m_NextUndress > DateTime.UtcNow || 0.005 < Utility.RandomDouble()) + return; - m_NextProvoke = DateTime.UtcNow + TimeSpan.FromSeconds( 10 ); - } - #endregion + if (target.Player && target.Female && !target.Hidden && CanBeHarmful(target)) + { + UndressItem(target, Layer.OuterTorso); + UndressItem(target, Layer.InnerTorso); + UndressItem(target, Layer.MiddleTorso); + UndressItem(target, Layer.Pants); + UndressItem(target, Layer.Shirt); - public override int Meat => 1; + target.SendLocalizedMessage( + 1072196); // The satyr's music makes your blood race. Your clothing is too confining. + } - public Satyr( Serial serial ) : base( serial ) - { - } + m_NextUndress = DateTime.UtcNow + TimeSpan.FromMinutes(1); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public void UndressItem(Mobile m, Layer layer) + { + Item item = m.FindItemOnLayer(layer); - writer.Write( (int) 0 ); // version - } + if (item != null && item.Movable) + m.PlaceInBackpack(item); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + #endregion - int version = reader.ReadInt(); - } - } -} + #region Provoke + + private DateTime m_NextProvoke; + + public void Provoke(Mobile target) + { + if (target == null || Deleted || !Alive || m_NextProvoke > DateTime.UtcNow || 0.05 < Utility.RandomDouble()) + return; + + foreach (Mobile m in GetMobilesInRange(RangePerception)) + if (m is BaseCreature c) + { + if (c == this || c == target || c.Unprovokable || c.IsParagon || c.BardProvoked || + c.AccessLevel != AccessLevel.Player || !c.CanBeHarmful(target)) + continue; + + c.Provoke(this, target, true); + + if (target.Player) + target.SendLocalizedMessage(1072062); // You hear angry music, and start to fight. + + PlaySound(0x58A); + break; + } + + m_NextProvoke = DateTime.UtcNow + TimeSpan.FromSeconds(10); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/CorruptedSoul.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/CorruptedSoul.cs index 5e023dc25..2c15e24f3 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/CorruptedSoul.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/CorruptedSoul.cs @@ -1,92 +1,92 @@ namespace Server.Mobiles { - public class CorruptedSoul : BaseCreature - { - public override bool DeleteCorpseOnDeath => true; + public class CorruptedSoul : BaseCreature + { + [Constructible] + public CorruptedSoul() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, .1, 5) + { + Body = 0x3CA; + Hue = 0x453; - public override string DefaultName => "a corrupted soul"; + SetStr(102, 115); + SetDex(101, 115); + SetInt(203, 215); - [Constructible] - public CorruptedSoul() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, .1, 5 ) - { - Body = 0x3CA; - Hue = 0x453; + SetHits(61, 69); - SetStr( 102, 115 ); - SetDex( 101, 115 ); - SetInt( 203, 215 ); + SetDamage(4, 40); - SetHits( 61, 69 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 4, 40 ); + SetResistance(ResistanceType.Physical, 61, 74); + SetResistance(ResistanceType.Fire, 22, 48); + SetResistance(ResistanceType.Cold, 73, 100); + SetResistance(ResistanceType.Poison, 0); + SetResistance(ResistanceType.Energy, 51, 60); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 80.2, 89.4); + SetSkill(SkillName.Tactics, 81.3, 89.9); + SetSkill(SkillName.Wrestling, 80.1, 88.7); - SetResistance( ResistanceType.Physical, 61, 74 ); - SetResistance( ResistanceType.Fire, 22, 48 ); - SetResistance( ResistanceType.Cold, 73, 100 ); - SetResistance( ResistanceType.Poison, 0 ); - SetResistance( ResistanceType.Energy, 51, 60 ); + Fame = 5000; + Karma = -5000; - SetSkill( SkillName.MagicResist, 80.2, 89.4 ); - SetSkill( SkillName.Tactics, 81.3, 89.9 ); - SetSkill( SkillName.Wrestling, 80.1, 88.7 ); + // VirtualArmor = 6; Not sure + } - Fame = 5000; - Karma = -5000; + public CorruptedSoul(Serial serial) : base(serial) + { + } - // VirtualArmor = 6; Not sure - } + public override bool DeleteCorpseOnDeath => true; - public override bool AlwaysAttackable => true; - public override bool BleedImmune => true; // NEED TO VERIFY + public override string DefaultName => "a corrupted soul"; - // NEED TO VERIFY SOUNDS! Known: No Idle Sound. + public override bool AlwaysAttackable => true; + public override bool BleedImmune => true; // NEED TO VERIFY - /*public override int GetAngerSound() - { - return 0x0; - }*/ + /*public override int GetDeathSound() + { + return 0x0; + }*/ - public override int GetAttackSound() - { - return 0x233; - } + public override bool AlwaysMurderer => true; - /*public override int GetDeathSound() - { - return 0x0; - }*/ + // NEED TO VERIFY SOUNDS! Known: No Idle Sound. - public override bool AlwaysMurderer => true; + /*public override int GetAngerSound() + { + return 0x0; + }*/ - // TODO: Proper OnDeath Effect + public override int GetAttackSound() + { + return 0x233; + } - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + // TODO: Proper OnDeath Effect - // 1 in 20 chance that a Thread of Fate will appear in the killer's pack + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; - Effects.SendLocationEffect( Location, Map, 0x376A, 10, 1 ); - return true; - } + // 1 in 20 chance that a Thread of Fate will appear in the killer's pack - public CorruptedSoul( Serial serial ) : base( serial ) - { - } + Effects.SendLocationEffect(Location, Map, 0x376A, 10, 1); + return true; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/FerelTreefellow.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/FerelTreefellow.cs index 438ad1216..b873d1021 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/FerelTreefellow.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/FerelTreefellow.cs @@ -2,83 +2,87 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias("Server.Mobiles.FerelTreefellow")] - public class FeralTreefellow : BaseCreature - { - public override string CorpseName => "a treefellow corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + [TypeAlias("Server.Mobiles.FerelTreefellow")] + public class FeralTreefellow : BaseCreature + { + [Constructible] + public FeralTreefellow() : base(AIType.AI_Melee, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 301; - public override string DefaultName => "a feral treefellow"; + SetStr(1351, 1600); + SetDex(301, 550); + SetInt(651, 900); - [Constructible] - public FeralTreefellow() : base( AIType.AI_Melee, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 301; + SetHits(1170, 1320); - SetStr( 1351, 1600 ); - SetDex( 301, 550 ); - SetInt( 651, 900 ); + SetDamage(26, 35); - SetHits( 1170, 1320 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 26, 35 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 40, 60); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 40.1, 55.0); // Unknown + SetSkill(SkillName.Tactics, 65.1, 90.0); // Unknown + SetSkill(SkillName.Wrestling, 65.1, 85.0); // Unknown - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 40, 60 ); + Fame = 12500; //Unknown + Karma = 12500; //Unknown - SetSkill( SkillName.MagicResist, 40.1, 55.0 );// Unknown - SetSkill( SkillName.Tactics, 65.1, 90.0 );// Unknown - SetSkill( SkillName.Wrestling, 65.1, 85.0 );// Unknown + VirtualArmor = 24; + PackItem(new Log(Utility.RandomMinMax(23, 34))); + } - Fame = 12500; //Unknown - Karma = 12500; //Unknown + public FeralTreefellow(Serial serial) : base(serial) + { + } - VirtualArmor = 24; - PackItem( new Log( Utility.RandomMinMax( 23, 34 ) ) ); - } + public override string CorpseName => "a treefellow corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string DefaultName => "a feral treefellow"; - public override int GetIdleSound() - { - return 443; - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override int GetDeathSound() - { - return 31; - } + public override bool BleedImmune => true; - public override int GetAttackSound() - { - return 672; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - public override bool BleedImmune => true; + public override int GetIdleSound() + { + return 443; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); //Unknown - } + public override int GetDeathSound() + { + return 31; + } - public FeralTreefellow( Serial serial ) : base( serial ) - { - } + public override int GetAttackSound() + { + return 672; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); //Unknown + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Minotaur.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Minotaur.cs index 8e33cb93b..39bd2492e 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Minotaur.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Minotaur.cs @@ -2,94 +2,98 @@ using Server.Items; namespace Server.Mobiles { - public class Minotaur : BaseCreature - { - public override string CorpseName => "a minotaur corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ParalyzingBlow; + public class Minotaur : BaseCreature + { + [Constructible] + public Minotaur() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) // NEED TO CHECK + { + Body = 263; - public override string DefaultName => "a minotaur"; + SetStr(301, 340); + SetDex(91, 110); + SetInt(31, 50); - [Constructible] - public Minotaur() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) // NEED TO CHECK - { - Body = 263; + SetHits(301, 340); - SetStr( 301, 340 ); - SetDex( 91, 110 ); - SetInt( 31, 50 ); + SetDamage(11, 20); - SetHits( 301, 340 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 11, 20 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.Meditation, 0); + SetSkill(SkillName.EvalInt, 0); + SetSkill(SkillName.Magery, 0); + SetSkill(SkillName.Poisoning, 0); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 56.1, 64.0); + SetSkill(SkillName.Tactics, 93.3, 97.8); + SetSkill(SkillName.Wrestling, 90.4, 92.1); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 5000; + Karma = -5000; - SetSkill( SkillName.Meditation, 0 ); - SetSkill( SkillName.EvalInt, 0 ); - SetSkill( SkillName.Magery, 0 ); - SetSkill( SkillName.Poisoning, 0 ); - SetSkill( SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 56.1, 64.0 ); - SetSkill( SkillName.Tactics, 93.3, 97.8 ); - SetSkill( SkillName.Wrestling, 90.4, 92.1 ); + VirtualArmor = 28; // Don't know what it should be + } - Fame = 5000; - Karma = -5000; + public Minotaur(Serial serial) : base(serial) + { + } - VirtualArmor = 28; // Don't know what it should be - } + public override string CorpseName => "a minotaur corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); // Need to verify - } + public override string DefaultName => "a minotaur"; - // Using Tormented Minotaur sounds - Need to veryfy - public override int GetAngerSound() - { - return 0x597; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ParalyzingBlow; + } - public override int GetIdleSound() - { - return 0x596; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); // Need to verify + } - public override int GetAttackSound() - { - return 0x599; - } + // Using Tormented Minotaur sounds - Need to veryfy + public override int GetAngerSound() + { + return 0x597; + } - public override int GetHurtSound() - { - return 0x59a; - } + public override int GetIdleSound() + { + return 0x596; + } - public override int GetDeathSound() - { - return 0x59c; - } + public override int GetAttackSound() + { + return 0x599; + } - public Minotaur( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x59a; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetDeathSound() + { + return 0x59c; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurCaptain.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurCaptain.cs index 636899efb..6cb075bc6 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurCaptain.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurCaptain.cs @@ -2,94 +2,98 @@ using Server.Items; namespace Server.Mobiles { - public class MinotaurCaptain : BaseCreature - { - public override string CorpseName => "a minotaur corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ParalyzingBlow; + public class MinotaurCaptain : BaseCreature + { + [Constructible] + public MinotaurCaptain() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) // NEED TO CHECK + { + Body = 280; - public override string DefaultName => "a minotaur captain"; + SetStr(401, 425); + SetDex(91, 110); + SetInt(31, 50); - [Constructible] - public MinotaurCaptain() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) // NEED TO CHECK - { - Body = 280; + SetHits(401, 440); - SetStr( 401, 425 ); - SetDex( 91, 110 ); - SetInt( 31, 50 ); + SetDamage(11, 20); - SetHits( 401, 440 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 11, 20 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.Meditation, 0); + SetSkill(SkillName.EvalInt, 0); + SetSkill(SkillName.Magery, 0); + SetSkill(SkillName.Poisoning, 0); + SetSkill(SkillName.Anatomy, 0, 6.3); + SetSkill(SkillName.MagicResist, 66.1, 73.6); + SetSkill(SkillName.Tactics, 93.0, 109.9); + SetSkill(SkillName.Wrestling, 92.6, 107.2); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + Fame = 7000; + Karma = -7000; - SetSkill( SkillName.Meditation, 0 ); - SetSkill( SkillName.EvalInt, 0 ); - SetSkill( SkillName.Magery, 0 ); - SetSkill( SkillName.Poisoning, 0 ); - SetSkill( SkillName.Anatomy, 0, 6.3 ); - SetSkill( SkillName.MagicResist, 66.1, 73.6 ); - SetSkill( SkillName.Tactics, 93.0, 109.9 ); - SetSkill( SkillName.Wrestling, 92.6, 107.2 ); + VirtualArmor = 28; // Don't know what it should be + } - Fame = 7000; - Karma = -7000; + public MinotaurCaptain(Serial serial) : base(serial) + { + } - VirtualArmor = 28; // Don't know what it should be - } + public override string CorpseName => "a minotaur corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); // Need to verify - } + public override string DefaultName => "a minotaur captain"; - // Using Tormented Minotaur sounds - Need to veryfy - public override int GetAngerSound() - { - return 0x597; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ParalyzingBlow; + } - public override int GetIdleSound() - { - return 0x596; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); // Need to verify + } - public override int GetAttackSound() - { - return 0x599; - } + // Using Tormented Minotaur sounds - Need to veryfy + public override int GetAngerSound() + { + return 0x597; + } - public override int GetHurtSound() - { - return 0x59a; - } + public override int GetIdleSound() + { + return 0x596; + } - public override int GetDeathSound() - { - return 0x59c; - } + public override int GetAttackSound() + { + return 0x599; + } - public MinotaurCaptain( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x59a; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetDeathSound() + { + return 0x59c; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurScout.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurScout.cs index 8d38f2dd0..de318167c 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurScout.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/MinotaurScout.cs @@ -2,94 +2,98 @@ using Server.Items; namespace Server.Mobiles { - public class MinotaurScout : BaseCreature - { - public override string CorpseName => "a minotaur corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ParalyzingBlow; + public class MinotaurScout : BaseCreature + { + [Constructible] + public MinotaurScout() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) // NEED TO CHECK + { + Body = 281; - public override string DefaultName => "a minotaur scout"; + SetStr(353, 375); + SetDex(111, 130); + SetInt(34, 50); - [Constructible] - public MinotaurScout() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) // NEED TO CHECK - { - Body = 281; + SetHits(354, 383); - SetStr( 353, 375 ); - SetDex( 111, 130 ); - SetInt( 34, 50 ); + SetDamage(11, 20); - SetHits( 354, 383 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 11, 20 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 100 ); + //SetSkill( SkillName.Meditation, Unknown ); + //SetSkill( SkillName.EvalInt, Unknown ); + //SetSkill( SkillName.Magery, Unknown ); + //SetSkill( SkillName.Poisoning, Unknown ); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 60.6, 67.5); + SetSkill(SkillName.Tactics, 86.9, 103.6); + SetSkill(SkillName.Wrestling, 85.6, 104.5); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 5000; + Karma = -5000; - //SetSkill( SkillName.Meditation, Unknown ); - //SetSkill( SkillName.EvalInt, Unknown ); - //SetSkill( SkillName.Magery, Unknown ); - //SetSkill( SkillName.Poisoning, Unknown ); - SetSkill( SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 60.6, 67.5 ); - SetSkill( SkillName.Tactics, 86.9, 103.6 ); - SetSkill( SkillName.Wrestling, 85.6, 104.5 ); + VirtualArmor = 28; // Don't know what it should be + } - Fame = 5000; - Karma = -5000; + public MinotaurScout(Serial serial) : base(serial) + { + } - VirtualArmor = 28; // Don't know what it should be - } + public override string CorpseName => "a minotaur corpse"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); // Need to verify - } + public override string DefaultName => "a minotaur scout"; - // Using Tormented Minotaur sounds - Need to veryfy - public override int GetAngerSound() - { - return 0x597; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ParalyzingBlow; + } - public override int GetIdleSound() - { - return 0x596; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); // Need to verify + } - public override int GetAttackSound() - { - return 0x599; - } + // Using Tormented Minotaur sounds - Need to veryfy + public override int GetAngerSound() + { + return 0x597; + } - public override int GetHurtSound() - { - return 0x59a; - } + public override int GetIdleSound() + { + return 0x596; + } - public override int GetDeathSound() - { - return 0x59c; - } + public override int GetAttackSound() + { + return 0x599; + } - public MinotaurScout( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x59a; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetDeathSound() + { + return 0x59c; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/PestilentBandage.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/PestilentBandage.cs index a89e69325..a6a0a2d50 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/PestilentBandage.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/PestilentBandage.cs @@ -2,79 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public class PestilentBandage : BaseCreature - { - public override string CorpseName => "a pestilent bandage corpse"; - // Neither Stratics nor UOGuide have much description - // beyond being a "Grey Mummy". BodyValue, Sound and - // Hue are all guessed until they can be verified. - // Loot and Fame/Karma are also guesses at this point. - // - // They also apparently have a Poison Attack, which I've stolen from Yamandons. + public class PestilentBandage : BaseCreature + { + [Constructible] + public PestilentBandage() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) // NEED TO CHECK + { + Body = 154; + Hue = 0x515; + BaseSoundID = 471; - public override string DefaultName => "a pestilent bandage"; + SetStr(691, 740); + SetDex(141, 180); + SetInt(51, 80); - [Constructible] - public PestilentBandage() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) // NEED TO CHECK - { - Body = 154; - Hue = 0x515; - BaseSoundID = 471; + SetHits(415, 445); - SetStr( 691, 740 ); - SetDex( 141, 180 ); - SetInt( 51, 80 ); + SetDamage(13, 23); - SetHits( 415, 445 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Cold, 20); + SetDamageType(ResistanceType.Poison, 40); - SetDamage( 13, 23 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Cold, 20 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetSkill(SkillName.Poisoning, 0.0, 10.0); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 75.0, 80.0); + SetSkill(SkillName.Tactics, 80.0, 85.0); + SetSkill(SkillName.Wrestling, 70.0, 75.0); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Fame = 20000; + Karma = -20000; - SetSkill( SkillName.Poisoning, 0.0, 10.0 ); - SetSkill( SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 75.0, 80.0 ); - SetSkill( SkillName.Tactics, 80.0, 85.0 ); - SetSkill( SkillName.Wrestling, 70.0, 75.0 ); + // VirtualArmor = 28; // Don't know what it should be - Fame = 20000; - Karma = -20000; + PackItem(new Bandage(5)); // How many? + } - // VirtualArmor = 28; // Don't know what it should be + public PestilentBandage(Serial serial) : base(serial) + { + } - PackItem( new Bandage( 5 ) ); // How many? + public override string CorpseName => "a pestilent bandage corpse"; + // Neither Stratics nor UOGuide have much description + // beyond being a "Grey Mummy". BodyValue, Sound and + // Hue are all guessed until they can be verified. + // Loot and Fame/Karma are also guesses at this point. + // + // They also apparently have a Poison Attack, which I've stolen from Yamandons. - } + public override string DefaultName => "a pestilent bandage"; - public override Poison HitPoison => Poison.Lethal; - public override bool CanHeal => true; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); // Need to verify - } + public override Poison HitPoison => Poison.Lethal; + public override bool CanHeal => true; - public PestilentBandage( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); // Need to verify + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Tormented Minotaur.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Tormented Minotaur.cs index 9210bf311..981fa0a16 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Tormented Minotaur.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Tormented Minotaur.cs @@ -2,74 +2,96 @@ using Server.Items; namespace Server.Mobiles { - public class TormentedMinotaur : BaseCreature - { - public override string CorpseName => "a tormented minotaur corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + public class TormentedMinotaur : BaseCreature + { + [Constructible] + public TormentedMinotaur() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 262; - public override string DefaultName => "Tormented Minotaur"; + SetStr(822, 930); + SetDex(401, 415); + SetInt(128, 138); - [Constructible] - public TormentedMinotaur() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 262; + SetHits(4000, 4200); - SetStr( 822, 930 ); - SetDex( 401, 415 ); - SetInt( 128, 138 ); + SetDamage(16, 30); - SetHits( 4000, 4200 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 16, 30 ); + SetResistance(ResistanceType.Physical, 62); + SetResistance(ResistanceType.Fire, 74); + SetResistance(ResistanceType.Cold, 54); + SetResistance(ResistanceType.Poison, 56); + SetResistance(ResistanceType.Energy, 54); - SetDamageType( ResistanceType.Physical, 100 ); - - SetResistance( ResistanceType.Physical, 62 ); - SetResistance( ResistanceType.Fire, 74 ); - SetResistance( ResistanceType.Cold, 54 ); - SetResistance( ResistanceType.Poison, 56 ); - SetResistance( ResistanceType.Energy, 54 ); - - SetSkill( SkillName.Wrestling, 110.1, 111.0 ); - SetSkill( SkillName.Tactics, 100.7, 102.8 ); - SetSkill( SkillName.MagicResist, 104.3, 116.3 ); + SetSkill(SkillName.Wrestling, 110.1, 111.0); + SetSkill(SkillName.Tactics, 100.7, 102.8); + SetSkill(SkillName.MagicResist, 104.3, 116.3); - Fame = 20000; - Karma = -20000; + Fame = 20000; + Karma = -20000; + } - } + public TormentedMinotaur(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot(LootPack.FilthyRich, 10); - } + public override string CorpseName => "a tormented minotaur corpse"; - public override Poison PoisonImmune => Poison.Deadly; - public override int TreasureMapLevel => 3; + public override string DefaultName => "Tormented Minotaur"; - public override int GetDeathSound() { return 0x596; } - public override int GetAttackSound() { return 0x597; } - public override int GetIdleSound() { return 0x598; } - public override int GetAngerSound() { return 0x599; } - public override int GetHurtSound() { return 0x59A; } + public override Poison PoisonImmune => Poison.Deadly; + public override int TreasureMapLevel => 3; - public TormentedMinotaur( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 10); + } - writer.Write( (int) 0 ); // version - } + public override int GetDeathSound() + { + return 0x596; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int GetAttackSound() + { + return 0x597; + } - int version = reader.ReadInt(); - } - } -} + public override int GetIdleSound() + { + return 0x598; + } + + public override int GetAngerSound() + { + return 0x599; + } + + public override int GetHurtSound() + { + return 0x59A; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Troglodyte.cs b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Troglodyte.cs index e35af0eba..c06de61e2 100644 --- a/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Troglodyte.cs +++ b/Scripts/Mobiles/Monsters/ML/Humanoid/Melee/Troglodyte.cs @@ -2,77 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class Troglodyte : BaseCreature - { - public override string CorpseName => "a troglodyte corpse"; - public override string DefaultName => "a troglodyte"; + public class Troglodyte : BaseCreature + { + [Constructible] + public Troglodyte() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) // NEED TO CHECK + { + Body = 267; + BaseSoundID = 0x59F; - [Constructible] - public Troglodyte() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) // NEED TO CHECK - { - Body = 267; - BaseSoundID = 0x59F; + SetStr(148, 217); + SetDex(91, 120); + SetInt(51, 70); - SetStr( 148, 217 ); - SetDex( 91, 120 ); - SetInt( 51, 70 ); + SetHits(302, 340); - SetHits( 302, 340 ); + SetDamage(11, 14); - SetDamage( 11, 14 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 35); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 35, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 30, 35 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 35, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Anatomy, 70.5, 94.8); + SetSkill(SkillName.MagicResist, 51.8, 65.0); + SetSkill(SkillName.Tactics, 80.4, 94.7); + SetSkill(SkillName.Wrestling, 70.2, 93.5); + SetSkill(SkillName.Healing, 70.0, 95.0); - SetSkill( SkillName.Anatomy, 70.5, 94.8 ); - SetSkill( SkillName.MagicResist, 51.8, 65.0 ); - SetSkill( SkillName.Tactics, 80.4, 94.7 ); - SetSkill( SkillName.Wrestling, 70.2, 93.5 ); - SetSkill( SkillName.Healing, 70.0, 95.0 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + VirtualArmor = 28; // Don't know what it should be - VirtualArmor = 28; // Don't know what it should be + PackItem(new Bandage(5)); // How many? + PackItem(new Ribs()); + } - PackItem( new Bandage( 5 ) ); // How many? - PackItem( new Ribs() ); - } + public Troglodyte(Serial serial) : base(serial) + { + } - public override bool CanHeal => true; + public override string CorpseName => "a troglodyte corpse"; + public override string DefaultName => "a troglodyte"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); // Need to verify - } + public override bool CanHeal => true; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); // Need to verify + } - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new PrimitiveFetish() ); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public Troglodyte( Serial serial ) : base( serial ) - { - } + if (Utility.RandomDouble() < 0.1) + c.DropItem(new PrimitiveFetish()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Labyrinth/Miasma.cs b/Scripts/Mobiles/Monsters/ML/Labyrinth/Miasma.cs index e9edc6364..0236bd164 100644 --- a/Scripts/Mobiles/Monsters/ML/Labyrinth/Miasma.cs +++ b/Scripts/Mobiles/Monsters/ML/Labyrinth/Miasma.cs @@ -2,109 +2,112 @@ using Server.Items; namespace Server.Mobiles { - public class Miasma : Scorpion - { - public override string CorpseName => "a Miasma corpse"; - public override string DefaultName => "Miasma"; + public class Miasma : Scorpion + { + [Constructible] + public Miasma() + { + IsParagon = true; - [Constructible] - public Miasma() - { - IsParagon = true; + Hue = 0x8FD; - Hue = 0x8FD; + SetStr(255, 847); + SetDex(145, 428); + SetInt(26, 380); - SetStr( 255, 847 ); - SetDex( 145, 428 ); - SetInt( 26, 380 ); + SetHits(750, 2000); + SetMana(5, 60); - SetHits( 750, 2000 ); - SetMana( 5, 60 ); + SetDamage(20, 30); - SetDamage( 20, 30 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetResistance(ResistanceType.Physical, 50, 54); + SetResistance(ResistanceType.Fire, 40, 45); + SetResistance(ResistanceType.Cold, 50, 55); + SetResistance(ResistanceType.Poison, 70, 80); + SetResistance(ResistanceType.Energy, 40, 45); - SetResistance( ResistanceType.Physical, 50, 54 ); - SetResistance( ResistanceType.Fire, 40, 45 ); - SetResistance( ResistanceType.Cold, 50, 55 ); - SetResistance( ResistanceType.Poison, 70, 80 ); - SetResistance( ResistanceType.Energy, 40, 45 ); + SetSkill(SkillName.Wrestling, 84.9, 103.3); + SetSkill(SkillName.Tactics, 98.4, 110.6); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 74.4, 77.7); + SetSkill(SkillName.Poisoning, 128.5, 143.6); - SetSkill( SkillName.Wrestling, 84.9, 103.3 ); - SetSkill( SkillName.Tactics, 98.4, 110.6 ); - SetSkill( SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 74.4, 77.7 ); - SetSkill( SkillName.Poisoning, 128.5, 143.6 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* yes, this is OSI style */ - public override double WeaponAbilityChance => 0.75; - public override double HitPoisonChance => 0.35; - public override Poison HitPoison => ( Poison.Lethal ); - public override bool HasManaOveride => true; - public override bool GivesMLMinorArtifact => true; - public override int TreasureMapLevel => 5; + if ( Utility.RandomDouble() < 0.025 ) + { + switch ( Utility.Random( 16 ) ) + { + case 0: c.DropItem( new MyrmidonGloves() ); break; + case 1: c.DropItem( new MyrmidonGorget() ); break; + case 2: c.DropItem( new MyrmidonLegs() ); break; + case 3: c.DropItem( new MyrmidonArms() ); break; + case 4: c.DropItem( new PaladinArms() ); break; + case 5: c.DropItem( new PaladinGorget() ); break; + case 6: c.DropItem( new LeafweaveLegs() ); break; + case 7: c.DropItem( new DeathChest() ); break; + case 8: c.DropItem( new DeathGloves() ); break; + case 9: c.DropItem( new DeathLegs() ); break; + case 10: c.DropItem( new GreymistGloves() ); break; + case 11: c.DropItem( new GreymistArms() ); break; + case 12: c.DropItem( new AssassinChest() ); break; + case 13: c.DropItem( new AssassinArms() ); break; + case 14: c.DropItem( new HunterGloves() ); break; + case 15: c.DropItem( new HunterLegs() ); break; + } + } + } + */ - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 4 ); - } + public Miasma(Serial serial) + : base(serial) + { + } - public override WeaponAbility GetWeaponAbility() => WeaponAbility.MortalStrike; + public override string CorpseName => "a Miasma corpse"; + public override string DefaultName => "Miasma"; - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + /* yes, this is OSI style */ + public override double WeaponAbilityChance => 0.75; + public override double HitPoisonChance => 0.35; + public override Poison HitPoison => Poison.Lethal; + public override bool HasManaOveride => true; + public override bool GivesMLMinorArtifact => true; + public override int TreasureMapLevel => 5; - if ( Utility.RandomDouble() < 0.025 ) - { - switch ( Utility.Random( 16 ) ) - { - case 0: c.DropItem( new MyrmidonGloves() ); break; - case 1: c.DropItem( new MyrmidonGorget() ); break; - case 2: c.DropItem( new MyrmidonLegs() ); break; - case 3: c.DropItem( new MyrmidonArms() ); break; - case 4: c.DropItem( new PaladinArms() ); break; - case 5: c.DropItem( new PaladinGorget() ); break; - case 6: c.DropItem( new LeafweaveLegs() ); break; - case 7: c.DropItem( new DeathChest() ); break; - case 8: c.DropItem( new DeathGloves() ); break; - case 9: c.DropItem( new DeathLegs() ); break; - case 10: c.DropItem( new GreymistGloves() ); break; - case 11: c.DropItem( new GreymistArms() ); break; - case 12: c.DropItem( new AssassinChest() ); break; - case 13: c.DropItem( new AssassinArms() ); break; - case 14: c.DropItem( new HunterGloves() ); break; - case 15: c.DropItem( new HunterLegs() ); break; - } - } - } - */ + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 4); + } - public Miasma( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.MortalStrike; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Labyrinth/Pyre.cs b/Scripts/Mobiles/Monsters/ML/Labyrinth/Pyre.cs index 9d15f9bb9..5627725c3 100644 --- a/Scripts/Mobiles/Monsters/ML/Labyrinth/Pyre.cs +++ b/Scripts/Mobiles/Monsters/ML/Labyrinth/Pyre.cs @@ -2,81 +2,81 @@ using Server.Items; namespace Server.Mobiles { - public class Pyre : Phoenix - { - public override string CorpseName => "a Pyre corpse"; - public override string DefaultName => "Pyre"; + public class Pyre : Phoenix + { + [Constructible] + public Pyre() + { + IsParagon = true; - [Constructible] - public Pyre() - { - IsParagon = true; + Hue = 0x489; - Hue = 0x489; + FightMode = FightMode.Closest; - FightMode = FightMode.Closest; + SetStr(605, 611); + SetDex(391, 519); + SetInt(669, 818); - SetStr( 605, 611 ); - SetDex( 391, 519 ); - SetInt( 669, 818 ); + SetHits(1783, 1939); - SetHits( 1783, 1939 ); + SetDamage(30); - SetDamage( 30 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Fire, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Fire, 50 ); + SetResistance(ResistanceType.Physical, 65); + SetResistance(ResistanceType.Fire, 72, 75); + SetResistance(ResistanceType.Poison, 36, 41); + SetResistance(ResistanceType.Energy, 50, 51); - SetResistance( ResistanceType.Physical, 65 ); - SetResistance( ResistanceType.Fire, 72, 75 ); - SetResistance( ResistanceType.Poison, 36, 41 ); - SetResistance( ResistanceType.Energy, 50, 51 ); + SetSkill(SkillName.Wrestling, 121.9, 130.6); + SetSkill(SkillName.Tactics, 114.4, 117.4); + SetSkill(SkillName.MagicResist, 147.7, 153.0); + SetSkill(SkillName.Poisoning, 122.8, 124.0); + SetSkill(SkillName.Magery, 121.8, 127.8); + SetSkill(SkillName.EvalInt, 103.6, 117.0); + SetSkill(SkillName.Meditation, 100.0, 110.0); - SetSkill( SkillName.Wrestling, 121.9, 130.6 ); - SetSkill( SkillName.Tactics, 114.4, 117.4 ); - SetSkill( SkillName.MagicResist, 147.7, 153.0 ); - SetSkill( SkillName.Poisoning, 122.8, 124.0 ); - SetSkill( SkillName.Magery, 121.8, 127.8 ); - SetSkill( SkillName.EvalInt, 103.6, 117.0 ); - SetSkill( SkillName.Meditation, 100.0, 110.0 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + public Pyre(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Pyre corpse"; + public override string DefaultName => "Pyre"; - public override WeaponAbility GetWeaponAbility() - { - if ( Utility.RandomBool() ) - return WeaponAbility.ParalyzingBlow; - return WeaponAbility.BleedAttack; - } + public override bool GivesMLMinorArtifact => true; + public override int TreasureMapLevel => 5; + public override bool HasAura => true; - public override bool GivesMLMinorArtifact => true; - public override int TreasureMapLevel => 5; - public override bool HasAura => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public Pyre( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + if (Utility.RandomBool()) + return WeaponAbility.ParalyzingBlow; + return WeaponAbility.BleedAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Labyrinth/Rend.cs b/Scripts/Mobiles/Monsters/ML/Labyrinth/Rend.cs index 34aa3b260..9fc4267db 100644 --- a/Scripts/Mobiles/Monsters/ML/Labyrinth/Rend.cs +++ b/Scripts/Mobiles/Monsters/ML/Labyrinth/Rend.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class Rend : Reptalon - { - public override string CorpseName => "a Rend corpse"; - public override string DefaultName => "Rend"; + public class Rend : Reptalon + { + [Constructible] + public Rend() + { + IsParagon = true; - [Constructible] - public Rend() - { - IsParagon = true; + Hue = 0x455; - Hue = 0x455; + SetStr(1261, 1284); + SetDex(363, 384); + SetInt(601, 642); - SetStr( 1261, 1284 ); - SetDex( 363, 384 ); - SetInt( 601, 642 ); + SetHits(5176, 6100); - SetHits( 5176, 6100 ); + SetDamage(26, 33); - SetDamage( 26, 33 ); + SetDamageType(ResistanceType.Physical, 100); + SetDamageType(ResistanceType.Poison, 0); + SetDamageType(ResistanceType.Energy, 0); - SetDamageType( ResistanceType.Physical, 100 ); - SetDamageType( ResistanceType.Poison, 0 ); - SetDamageType( ResistanceType.Energy, 0 ); + SetResistance(ResistanceType.Physical, 75, 85); + SetResistance(ResistanceType.Fire, 81, 94); + SetResistance(ResistanceType.Cold, 46, 55); + SetResistance(ResistanceType.Poison, 35, 44); + SetResistance(ResistanceType.Energy, 45, 52); - SetResistance( ResistanceType.Physical, 75, 85 ); - SetResistance( ResistanceType.Fire, 81, 94 ); - SetResistance( ResistanceType.Cold, 46, 55 ); - SetResistance( ResistanceType.Poison, 35, 44 ); - SetResistance( ResistanceType.Energy, 45, 52 ); + SetSkill(SkillName.Wrestling, 136.3, 150.3); + SetSkill(SkillName.Tactics, 133.4, 141.4); + SetSkill(SkillName.MagicResist, 90.9, 110.0); + SetSkill(SkillName.Anatomy, 66.6, 72.0); - SetSkill( SkillName.Wrestling, 136.3, 150.3 ); - SetSkill( SkillName.Tactics, 133.4, 141.4 ); - SetSkill( SkillName.MagicResist, 90.9, 110.0 ); - SetSkill( SkillName.Anatomy, 66.6, 72.0 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + public Rend(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Rend corpse"; + public override string DefaultName => "Rend"; - public override WeaponAbility GetWeaponAbility() - { - if ( Utility.RandomBool() ) - return WeaponAbility.ParalyzingBlow; - return WeaponAbility.BleedAttack; - } + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public Rend( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + if (Utility.RandomBool()) + return WeaponAbility.ParalyzingBlow; + return WeaponAbility.BleedAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Misc/Magic/GreaterDragon.cs b/Scripts/Mobiles/Monsters/ML/Misc/Magic/GreaterDragon.cs index ca4f1f1b8..524c43e7d 100644 --- a/Scripts/Mobiles/Monsters/ML/Misc/Magic/GreaterDragon.cs +++ b/Scripts/Mobiles/Monsters/ML/Misc/Magic/GreaterDragon.cs @@ -1,99 +1,105 @@ using Server.Items; +using Server.SkillHandlers; namespace Server.Mobiles { - public class GreaterDragon : BaseCreature - { - public override string CorpseName => "a dragon corpse"; - public override bool StatLossAfterTame => true; - public override string DefaultName => "a greater dragon"; + public class GreaterDragon : BaseCreature + { + [Constructible] + public GreaterDragon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.3, 0.5) + { + Body = Utility.RandomList(12, 59); + BaseSoundID = 362; - [Constructible] - public GreaterDragon () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.3, 0.5 ) - { - Body = Utility.RandomList( 12, 59 ); - BaseSoundID = 362; + SetStr(1025, 1425); + SetDex(81, 148); + SetInt(475, 675); - SetStr( 1025, 1425 ); - SetDex( 81, 148 ); - SetInt( 475, 675 ); + SetHits(1000, 2000); + SetStam(120, 135); - SetHits( 1000, 2000 ); - SetStam( 120, 135 ); + SetDamage(24, 33); - SetDamage( 24, 33 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 60, 85); + SetResistance(ResistanceType.Fire, 65, 90); + SetResistance(ResistanceType.Cold, 40, 55); + SetResistance(ResistanceType.Poison, 40, 60); + SetResistance(ResistanceType.Energy, 50, 75); - SetResistance( ResistanceType.Physical, 60, 85 ); - SetResistance( ResistanceType.Fire, 65, 90 ); - SetResistance( ResistanceType.Cold, 40, 55 ); - SetResistance( ResistanceType.Poison, 40, 60 ); - SetResistance( ResistanceType.Energy, 50, 75 ); + SetSkill(SkillName.Meditation, 0); + SetSkill(SkillName.EvalInt, 110.0, 140.0); + SetSkill(SkillName.Magery, 110.0, 140.0); + SetSkill(SkillName.Poisoning, 0); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 110.0, 140.0); + SetSkill(SkillName.Tactics, 110.0, 140.0); + SetSkill(SkillName.Wrestling, 115.0, 145.0); - SetSkill( SkillName.Meditation, 0 ); - SetSkill( SkillName.EvalInt, 110.0, 140.0 ); - SetSkill( SkillName.Magery, 110.0, 140.0 ); - SetSkill( SkillName.Poisoning, 0 ); - SetSkill( SkillName.Anatomy, 0 ); - SetSkill( SkillName.MagicResist, 110.0, 140.0 ); - SetSkill( SkillName.Tactics, 110.0, 140.0 ); - SetSkill( SkillName.Wrestling, 115.0, 145.0 ); + Fame = 22000; + Karma = -15000; - Fame = 22000; - Karma = -15000; + VirtualArmor = 60; - VirtualArmor = 60; + Tamable = true; + ControlSlots = 5; + MinTameSkill = 104.7; + } - Tamable = true; - ControlSlots = 5; - MinTameSkill = 104.7; - } + public GreaterDragon(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 4 ); - AddLoot( LootPack.Gems, 8 ); - } + public override string CorpseName => "a dragon corpse"; + public override bool StatLossAfterTame => true; + public override string DefaultName => "a greater dragon"; - public override bool ReacquireOnMovement => !Controlled; - public override bool HasBreath => true; // fire breath enabled - public override bool AutoDispel => !Controlled; - public override int TreasureMapLevel => 5; - public override int Meat => 19; - public override int Hides => 30; - public override HideType HideType => HideType.Barbed; - public override int Scales => 7; - public override ScaleType ScaleType => ( Body == 12 ? ScaleType.Yellow : ScaleType.Red ); - public override FoodType FavoriteFood => FoodType.Meat; - public override bool CanAngerOnTame => true; - public override bool CanFly => true; + public override bool ReacquireOnMovement => !Controlled; + public override bool HasBreath => true; // fire breath enabled + public override bool AutoDispel => !Controlled; + public override int TreasureMapLevel => 5; + public override int Meat => 19; + public override int Hides => 30; + public override HideType HideType => HideType.Barbed; + public override int Scales => 7; + public override ScaleType ScaleType => Body == 12 ? ScaleType.Yellow : ScaleType.Red; + public override FoodType FavoriteFood => FoodType.Meat; + public override bool CanAngerOnTame => true; + public override bool CanFly => true; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 4); + AddLoot(LootPack.Gems, 8); + } - public GreaterDragon( Serial serial ) : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - SetDamage( 24, 33 ); + SetDamage(24, 33); - if ( version == 0 ) - { - SkillHandlers.AnimalTaming.ScaleStats( this, 0.50 ); - SkillHandlers.AnimalTaming.ScaleSkills( this, 0.80, 0.90 ); // 90% * 80% = 72% of original skills trainable to 90% - Skills[SkillName.Magery].Base = Skills[SkillName.Magery].Cap; // Greater dragons have a 90% cap reduction and 90% skill reduction on magery - } - } - } -} + if (version == 0) + { + AnimalTaming.ScaleStats(this, 0.50); + AnimalTaming.ScaleSkills(this, 0.80, 0.90); // 90% * 80% = 72% of original skills trainable to 90% + Skills[SkillName.Magery].Base = + Skills[SkillName.Magery] + .Cap; // Greater dragons have a 90% cap reduction and 90% skill reduction on magery + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Misc/Melee/CorrosiveSlime.cs b/Scripts/Mobiles/Monsters/ML/Misc/Melee/CorrosiveSlime.cs index 90f9b8dea..5ab7d708d 100644 --- a/Scripts/Mobiles/Monsters/ML/Misc/Melee/CorrosiveSlime.cs +++ b/Scripts/Mobiles/Monsters/ML/Misc/Melee/CorrosiveSlime.cs @@ -1,73 +1,73 @@ namespace Server.Mobiles { - public class CorrosiveSlime : BaseCreature - { - public override string CorpseName => "a slimey corpse"; - public override string DefaultName => "a corrosive slime"; + public class CorrosiveSlime : BaseCreature + { + [Constructible] + public CorrosiveSlime() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 51; + BaseSoundID = 456; - [Constructible] - public CorrosiveSlime() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 51; - BaseSoundID = 456; + Hue = Utility.RandomSlimeHue(); - Hue = Utility.RandomSlimeHue(); + SetStr(22, 34); + SetDex(16, 21); + SetInt(16, 20); - SetStr( 22, 34 ); - SetDex( 16, 21 ); - SetInt( 16, 20 ); + SetHits(15, 19); - SetHits( 15, 19 ); + SetDamage(1, 5); - SetDamage( 1, 5 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); + SetResistance(ResistanceType.Poison, 15, 20); - SetResistance( ResistanceType.Physical, 5, 10 ); - SetResistance( ResistanceType.Poison, 15, 20 ); + SetSkill(SkillName.Poisoning, 36.0, 49.1); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 15.9, 18.9); + SetSkill(SkillName.Tactics, 24.6, 26.1); + SetSkill(SkillName.Wrestling, 24.9, 26.1); - SetSkill( SkillName.Poisoning, 36.0, 49.1 ); - SetSkill(SkillName.Anatomy, 0); - SetSkill( SkillName.MagicResist, 15.9, 18.9 ); - SetSkill( SkillName.Tactics, 24.6, 26.1 ); - SetSkill( SkillName.Wrestling, 24.9, 26.1 ); + Fame = 300; + Karma = -300; - Fame = 300; - Karma = -300; + VirtualArmor = 8; - VirtualArmor = 8; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 23.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 23.1; - } + //TODO: Damage weapon via acid - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - AddLoot( LootPack.Gems ); - } + public CorrosiveSlime(Serial serial) : base(serial) + { + } - public override Poison PoisonImmune => Poison.Regular; - public override Poison HitPoison => Poison.Regular; - public override FoodType FavoriteFood => FoodType.Fish; + public override string CorpseName => "a slimey corpse"; + public override string DefaultName => "a corrosive slime"; - //TODO: Damage weapon via acid + public override Poison PoisonImmune => Poison.Regular; + public override Poison HitPoison => Poison.Regular; + public override FoodType FavoriteFood => FoodType.Fish; - public CorrosiveSlime( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Misc/Melee/Reptalon.cs b/Scripts/Mobiles/Monsters/ML/Misc/Melee/Reptalon.cs index 781bbdd97..704466ae5 100644 --- a/Scripts/Mobiles/Monsters/ML/Misc/Melee/Reptalon.cs +++ b/Scripts/Mobiles/Monsters/ML/Misc/Melee/Reptalon.cs @@ -2,74 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class Reptalon : BaseMount - { - public override string CorpseName => "a reptalon corpse"; - [Constructible] - public Reptalon() : base( "a reptalon", 0x114, 0x3E90, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.35 ) - { - BaseSoundID = 0x16A; + public class Reptalon : BaseMount + { + [Constructible] + public Reptalon() : base("a reptalon", 0x114, 0x3E90, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.35) + { + BaseSoundID = 0x16A; - SetStr( 1001, 1025 ); - SetDex( 152, 164 ); - SetInt( 251, 289 ); + SetStr(1001, 1025); + SetDex(152, 164); + SetInt(251, 289); - SetHits( 833, 931 ); + SetHits(833, 931); - SetDamage( 21, 28 ); + SetDamage(21, 28); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Poison, 25 ); - SetDamageType( ResistanceType.Energy, 75 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Poison, 25); + SetDamageType(ResistanceType.Energy, 75); - SetResistance( ResistanceType.Physical, 53, 64 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 36, 45 ); - SetResistance( ResistanceType.Poison, 52, 63 ); - SetResistance( ResistanceType.Energy, 71, 83 ); + SetResistance(ResistanceType.Physical, 53, 64); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 36, 45); + SetResistance(ResistanceType.Poison, 52, 63); + SetResistance(ResistanceType.Energy, 71, 83); - SetSkill( SkillName.Wrestling, 101.5, 118.2 ); - SetSkill( SkillName.Tactics, 101.7, 108.2 ); - SetSkill( SkillName.MagicResist, 76.4, 89.9 ); - SetSkill( SkillName.Anatomy, 56.4, 59.7 ); + SetSkill(SkillName.Wrestling, 101.5, 118.2); + SetSkill(SkillName.Tactics, 101.7, 108.2); + SetSkill(SkillName.MagicResist, 76.4, 89.9); + SetSkill(SkillName.Anatomy, 56.4, 59.7); - Tamable = true; - ControlSlots = 4; - MinTameSkill = 101.1; - } + Tamable = true; + ControlSlots = 4; + MinTameSkill = 101.1; + } - public override void GenerateLoot() - { - AddLoot( LootPack.AosUltraRich, 3 ); - } + public Reptalon(Serial serial) : base(serial) + { + } - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ParalyzingBlow; + public override string CorpseName => "a reptalon corpse"; - public override int TreasureMapLevel => 5; - public override int Meat => 5; - public override int Hides => 10; - public override bool CanBreath => true; - public override bool CanAngerOnTame => true; - public override bool StatLossAfterTame => true; - public override FoodType FavoriteFood => FoodType.Meat; - public override bool CanFly => true; + public override int TreasureMapLevel => 5; + public override int Meat => 5; + public override int Hides => 10; + public override bool CanBreath => true; + public override bool CanAngerOnTame => true; + public override bool StatLossAfterTame => true; + public override FoodType FavoriteFood => FoodType.Meat; + public override bool CanFly => true; - public Reptalon( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.AosUltraRich, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ParalyzingBlow; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Painted Caves/Grobu.cs b/Scripts/Mobiles/Monsters/ML/Painted Caves/Grobu.cs index bb2991779..1fefc0ba7 100644 --- a/Scripts/Mobiles/Monsters/ML/Painted Caves/Grobu.cs +++ b/Scripts/Mobiles/Monsters/ML/Painted Caves/Grobu.cs @@ -2,79 +2,79 @@ using Server.Items; namespace Server.Mobiles { - public class Grobu : BlackBear - { - public override string CorpseName => "a Grobu corpse"; - public override string DefaultName => "Grobu"; + public class Grobu : BlackBear + { + [Constructible] + public Grobu() + { + IsParagon = true; - [Constructible] - public Grobu() - { - IsParagon = true; + Hue = 0x455; - Hue = 0x455; + AI = AIType.AI_Melee; + FightMode = FightMode.Closest; - AI = AIType.AI_Melee; - FightMode = FightMode.Closest; + SetStr(192, 210); + SetDex(132, 150); + SetInt(50, 52); - SetStr( 192, 210 ); - SetDex( 132, 150 ); - SetInt( 50, 52 ); + SetHits(1235, 1299); + SetStam(132, 150); + SetMana(9); - SetHits( 1235, 1299 ); - SetStam( 132, 150 ); - SetMana( 9 ); + SetDamage(15, 18); - SetDamage( 15, 18 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 45); + SetResistance(ResistanceType.Fire, 20, 40); + SetResistance(ResistanceType.Cold, 32, 35); + SetResistance(ResistanceType.Poison, 25, 30); + SetResistance(ResistanceType.Energy, 22, 34); - SetResistance( ResistanceType.Physical, 40, 45 ); - SetResistance( ResistanceType.Fire, 20, 40 ); - SetResistance( ResistanceType.Cold, 32, 35 ); - SetResistance( ResistanceType.Poison, 25, 30 ); - SetResistance( ResistanceType.Energy, 22, 34 ); + SetSkill(SkillName.Wrestling, 96.4, 119.0); + SetSkill(SkillName.Tactics, 96.2, 116.5); + SetSkill(SkillName.MagicResist, 66.2, 83.7); - SetSkill( SkillName.Wrestling, 96.4, 119.0 ); - SetSkill( SkillName.Tactics, 96.2, 116.5 ); - SetSkill( SkillName.MagicResist, 66.2, 83.7 ); + Fame = 1000; + Karma = 1000; + } - Fame = 1000; - Karma = 1000; - } + public Grobu(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - } + public override string CorpseName => "a Grobu corpse"; + public override string DefaultName => "Grobu"; + + public override bool GivesMLMinorArtifact => true; + + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void OnDeath(Container c) + { + base.OnDeath(c); - c.DropItem( new GrobusFur() ); - } + c.DropItem(new GrobusFur()); + } - public override bool GivesMLMinorArtifact => true; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public Grobu( Serial serial ) - : base( serial ) - { - } + writer.Write(0); // version + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Painted Caves/Lurg.cs b/Scripts/Mobiles/Monsters/ML/Painted Caves/Lurg.cs index 6618227bf..af030fd84 100644 --- a/Scripts/Mobiles/Monsters/ML/Painted Caves/Lurg.cs +++ b/Scripts/Mobiles/Monsters/ML/Painted Caves/Lurg.cs @@ -2,73 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class Lurg : Troglodyte - { - public override string CorpseName => "a Lurg corpse"; - public override string DefaultName => "Lurg"; + public class Lurg : Troglodyte + { + [Constructible] + public Lurg() + { + IsParagon = true; - [Constructible] - public Lurg() - { - IsParagon = true; + Hue = 0x455; - Hue = 0x455; + SetStr(584, 625); + SetDex(163, 176); + SetInt(90, 106); - SetStr( 584, 625 ); - SetDex( 163, 176 ); - SetInt( 90, 106 ); + SetHits(3034, 3189); + SetStam(163, 176); + SetMana(90, 106); - SetHits( 3034, 3189 ); - SetStam( 163, 176 ); - SetMana( 90, 106 ); + SetDamage(16, 19); - SetDamage( 16, 19 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 50, 53); + SetResistance(ResistanceType.Fire, 45, 47); + SetResistance(ResistanceType.Cold, 56, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 41, 56); - SetResistance( ResistanceType.Physical, 50, 53 ); - SetResistance( ResistanceType.Fire, 45, 47 ); - SetResistance( ResistanceType.Cold, 56, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 41, 56 ); + SetSkill(SkillName.Wrestling, 122.7, 130.5); + SetSkill(SkillName.Tactics, 109.3, 118.5); + SetSkill(SkillName.MagicResist, 72.9, 87.6); + SetSkill(SkillName.Anatomy, 110.5, 124.0); + SetSkill(SkillName.Healing, 84.1, 105.0); - SetSkill( SkillName.Wrestling, 122.7, 130.5 ); - SetSkill( SkillName.Tactics, 109.3, 118.5 ); - SetSkill( SkillName.MagicResist, 72.9, 87.6 ); - SetSkill( SkillName.Anatomy, 110.5, 124.0 ); - SetSkill( SkillName.Healing, 84.1, 105.0 ); + Fame = 10000; + Karma = -10000; + } - Fame = 10000; - Karma = -10000; - } + public Lurg(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Lurg corpse"; + public override string DefaultName => "Lurg"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.CrushingBlow; + public override bool GivesMLMinorArtifact => true; + public override int TreasureMapLevel => 4; - public override bool GivesMLMinorArtifact => true; - public override int TreasureMapLevel => 4; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public Lurg( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.CrushingBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Palace of Paroxysmus/Putrefier.cs b/Scripts/Mobiles/Monsters/ML/Palace of Paroxysmus/Putrefier.cs index 6f2f7774a..f2971eac2 100644 --- a/Scripts/Mobiles/Monsters/ML/Palace of Paroxysmus/Putrefier.cs +++ b/Scripts/Mobiles/Monsters/ML/Palace of Paroxysmus/Putrefier.cs @@ -1,91 +1,91 @@ namespace Server.Mobiles { - public class Putrefier : Balron - { - public override string CorpseName => "a Putrefier corpse"; - public override string DefaultName => "Putrefier"; + public class Putrefier : Balron + { + [Constructible] + public Putrefier() + { + IsParagon = true; - [Constructible] - public Putrefier() - { - IsParagon = true; + Hue = 63; - Hue = 63; + SetStr(1057, 1400); + SetDex(232, 560); + SetInt(201, 440); - SetStr( 1057, 1400 ); - SetDex( 232, 560 ); - SetInt( 201, 440 ); + SetHits(3010, 4092); - SetHits( 3010, 4092 ); + SetDamage(27, 34); - SetDamage( 27, 34 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Fire, 0); + SetDamageType(ResistanceType.Poison, 50); + SetDamageType(ResistanceType.Energy, 0); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Fire, 0 ); - SetDamageType( ResistanceType.Poison, 50 ); - SetDamageType( ResistanceType.Energy, 0 ); + SetResistance(ResistanceType.Physical, 65, 80); + SetResistance(ResistanceType.Fire, 65, 80); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 65, 80 ); - SetResistance( ResistanceType.Fire, 65, 80 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Wrestling, 111.2, 128.0); + SetSkill(SkillName.Tactics, 115.2, 125.2); + SetSkill(SkillName.MagicResist, 143.4, 170.0); + SetSkill(SkillName.Anatomy, 44.6, 67.0); + SetSkill(SkillName.Magery, 117.6, 118.8); + SetSkill(SkillName.EvalInt, 113.0, 128.8); + SetSkill(SkillName.Meditation, 41.4, 85.0); + SetSkill(SkillName.Poisoning, 45.0, 50.0); - SetSkill( SkillName.Wrestling, 111.2, 128.0 ); - SetSkill( SkillName.Tactics, 115.2, 125.2 ); - SetSkill( SkillName.MagicResist, 143.4, 170.0 ); - SetSkill( SkillName.Anatomy, 44.6, 67.0 ); - SetSkill( SkillName.Magery, 117.6, 118.8 ); - SetSkill( SkillName.EvalInt, 113.0, 128.8 ); - SetSkill( SkillName.Meditation, 41.4, 85.0 ); - SetSkill( SkillName.Poisoning, 45.0, 50.0 ); + Fame = 24000; + Karma = -24000; - Fame = 24000; - Karma = -24000; + PackScroll(4, 7); + PackScroll(4, 7); + } - PackScroll( 4, 7 ); - PackScroll( 4, 7 ); - } + public Putrefier(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Putrefier corpse"; + public override string DefaultName => "Putrefier"; - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - c.DropItem( new SpleenOfThePutrefier() ); + c.DropItem( new SpleenOfThePutrefier() ); - if ( Utility.RandomDouble() < 0.6 ) - c.DropItem( new ParrotItem() ); - } - */ + if ( Utility.RandomDouble() < 0.6 ) + c.DropItem( new ParrotItem() ); + } + */ - public override bool GivesMLMinorArtifact => true; - public override Poison HitPoison => Poison.Deadly; // Becomes Lethal with Paragon bonus - public override int TreasureMapLevel => 5; + public override bool GivesMLMinorArtifact => true; + public override Poison HitPoison => Poison.Deadly; // Becomes Lethal with Paragon bonus + public override int TreasureMapLevel => 5; - public Putrefier( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/CorporealBrume.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/CorporealBrume.cs index bec1510a3..e7e57504c 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/CorporealBrume.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/CorporealBrume.cs @@ -2,81 +2,81 @@ using System; namespace Server.Mobiles { - public class CorporealBrume : BaseCreature - { - public override string CorpseName => "a corporeal brume corpse"; - public override string DefaultName => "a corporeal brume"; + public class CorporealBrume : BaseCreature + { + [Constructible] + public CorporealBrume() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x104; // TODO: Verify + BaseSoundID = 0x56B; - [Constructible] - public CorporealBrume() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x104; // TODO: Verify - BaseSoundID = 0x56B; + SetStr(400, 450); + SetDex(100, 150); + SetInt(50, 60); - SetStr( 400, 450 ); - SetDex( 100, 150 ); - SetInt( 50, 60 ); + SetHits(1150, 1250); - SetHits( 1150, 1250 ); + SetDamage(21, 25); - SetDamage( 21, 25 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 100); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 100 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Wrestling, 110.0, 115.0); + SetSkill(SkillName.Tactics, 110.0, 115.0); + SetSkill(SkillName.MagicResist, 80.0, 95.0); + SetSkill(SkillName.Anatomy, 100.0, 110.0); - SetSkill( SkillName.Wrestling, 110.0, 115.0 ); - SetSkill( SkillName.Tactics, 110.0, 115.0 ); - SetSkill( SkillName.MagicResist, 80.0, 95.0 ); - SetSkill( SkillName.Anatomy, 100.0, 110.0 ); + Fame = 12000; + Karma = -12000; + } - Fame = 12000; - Karma = -12000; - } + public CorporealBrume(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a corporeal brume corpse"; + public override string DefaultName => "a corporeal brume"; - // TODO: Verify area attack specifics - public override bool HasAura => ( Combatant != null ); - public override TimeSpan AuraInterval => TimeSpan.FromSeconds( 20 ); - public override int AuraRange => 10; + // TODO: Verify area attack specifics + public override bool HasAura => Combatant != null; + public override TimeSpan AuraInterval => TimeSpan.FromSeconds(20); + public override int AuraRange => 10; - public override int AuraBaseDamage => Utility.RandomMinMax( 25, 35 ); - public override int AuraFireDamage => 0; - public override int AuraColdDamage => 100; + public override int AuraBaseDamage => Utility.RandomMinMax(25, 35); + public override int AuraFireDamage => 0; + public override int AuraColdDamage => 100; - public override void AuraEffect( Mobile m ) - { - m.FixedParticles( 0x374A, 10, 15, 5038, 1181, 2, EffectLayer.Head ); - m.PlaySound( 0x213 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - public CorporealBrume( Serial serial ) - : base( serial ) - { - } + public override void AuraEffect(Mobile m) + { + m.FixedParticles(0x374A, 10, 15, 5038, 1181, 2, EffectLayer.Head); + m.PlaySound(0x213); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalDaemon.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalDaemon.cs index e29ab6e38..cd46ec9e5 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalDaemon.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalDaemon.cs @@ -1,82 +1,82 @@ namespace Server.Mobiles { - public class CrystalDaemon : BaseCreature - { - public override string CorpseName => "a crystal daemon corpse"; - public override string DefaultName => "a crystal daemon"; + public class CrystalDaemon : BaseCreature + { + [Constructible] + public CrystalDaemon() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x310; + Hue = 0x3E8; + BaseSoundID = 0x47D; - [Constructible] - public CrystalDaemon() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x310; - Hue = 0x3E8; - BaseSoundID = 0x47D; + SetStr(140, 200); + SetDex(120, 150); + SetInt(800, 850); - SetStr( 140, 200 ); - SetDex( 120, 150 ); - SetInt( 800, 850 ); + SetHits(200, 220); - SetHits( 200, 220 ); + SetDamage(16, 20); - SetDamage( 16, 20 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 40); + SetDamageType(ResistanceType.Energy, 60); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 40 ); - SetDamageType( ResistanceType.Energy, 60 ); + SetResistance(ResistanceType.Physical, 20, 40); + SetResistance(ResistanceType.Fire, 0, 20); + SetResistance(ResistanceType.Cold, 60, 80); + SetResistance(ResistanceType.Poison, 20, 40); + SetResistance(ResistanceType.Energy, 65, 75); - SetResistance( ResistanceType.Physical, 20, 40 ); - SetResistance( ResistanceType.Fire, 0, 20 ); - SetResistance( ResistanceType.Cold, 60, 80 ); - SetResistance( ResistanceType.Poison, 20, 40 ); - SetResistance( ResistanceType.Energy, 65, 75 ); + SetSkill(SkillName.Wrestling, 60.0, 80.0); + SetSkill(SkillName.Tactics, 70.0, 80.0); + SetSkill(SkillName.MagicResist, 100.0, 110.0); + SetSkill(SkillName.Magery, 120.0, 130.0); + SetSkill(SkillName.EvalInt, 100.0, 110.0); + SetSkill(SkillName.Meditation, 100.0, 110.0); - SetSkill( SkillName.Wrestling, 60.0, 80.0 ); - SetSkill( SkillName.Tactics, 70.0, 80.0 ); - SetSkill( SkillName.MagicResist, 100.0, 110.0 ); - SetSkill( SkillName.Magery, 120.0, 130.0 ); - SetSkill( SkillName.EvalInt, 100.0, 110.0 ); - SetSkill( SkillName.Meditation, 100.0, 110.0 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + PackArcaneScroll(0, 1); + } - PackArcaneScroll( 0, 1 ); - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - } + if ( Utility.RandomDouble() < 0.4 ) + c.DropItem( new ScatteredCrystals() ); + } + */ - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public CrystalDaemon(Serial serial) + : base(serial) + { + } - if ( Utility.RandomDouble() < 0.4 ) - c.DropItem( new ScatteredCrystals() ); - } - */ + public override string CorpseName => "a crystal daemon corpse"; + public override string DefaultName => "a crystal daemon"; - public CrystalDaemon( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalLatticeSeeker.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalLatticeSeeker.cs index e92dbba3e..92698fcea 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalLatticeSeeker.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalLatticeSeeker.cs @@ -1,150 +1,169 @@ namespace Server.Mobiles { - public class CrystalLatticeSeeker : BaseCreature - { - public override string CorpseName => "a Crystal Lattice Seeker corpse"; - public override string DefaultName => "Crystal Lattice Seeker"; + public class CrystalLatticeSeeker : BaseCreature + { + [Constructible] + public CrystalLatticeSeeker() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x7B; + Hue = 0x47E; - [Constructible] - public CrystalLatticeSeeker() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x7B; - Hue = 0x47E; + SetStr(550, 850); + SetDex(190, 250); + SetInt(350, 450); - SetStr( 550, 850 ); - SetDex( 190, 250 ); - SetInt( 350, 450 ); + SetHits(350, 550); - SetHits( 350, 550 ); + SetDamage(13, 19); - SetDamage( 13, 19 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Anatomy, 50.0, 75.0); + SetSkill(SkillName.EvalInt, 90.0, 100.0); + SetSkill(SkillName.Magery, 100.0, 100.0); + SetSkill(SkillName.Meditation, 90.0, 100.0); + SetSkill(SkillName.MagicResist, 90.0, 100.0); + SetSkill(SkillName.Tactics, 90.0, 100.0); + SetSkill(SkillName.Wrestling, 90.0, 100.0); - SetSkill( SkillName.Anatomy, 50.0, 75.0 ); - SetSkill( SkillName.EvalInt, 90.0, 100.0 ); - SetSkill( SkillName.Magery, 100.0, 100.0 ); - SetSkill( SkillName.Meditation, 90.0, 100.0 ); - SetSkill( SkillName.MagicResist, 90.0, 100.0 ); - SetSkill( SkillName.Tactics, 90.0, 100.0 ); - SetSkill( SkillName.Wrestling, 90.0, 100.0 ); + Fame = 17000; + Karma = -17000; - Fame = 17000; - Karma = -17000; + PackArcaneScroll(0, 2); + } - PackArcaneScroll( 0, 2 ); - } + public CrystalLatticeSeeker(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 4 ); - // TODO: uncomment once added - //AddLoot( LootPack.Parrot ); - AddLoot( LootPack.Gems ); - } + public override string CorpseName => "a Crystal Lattice Seeker corpse"; + public override string DefaultName => "Crystal Lattice Seeker"; - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - if ( Utility.RandomDouble() < 0.1 ) - Drain( defender ); - } + if ( Utility.RandomDouble() < 0.75 ) + c.DropItem( new CrystallineFragments() ); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + if ( Utility.RandomDouble() < 0.07 ) + c.DropItem( new PiecesOfCrystal() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - Drain( attacker ); - } + public override int Feathers => 100; + public override int TreasureMapLevel => 5; - public virtual void Drain( Mobile m ) - { - int toDrain; + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 4); + // TODO: uncomment once added + //AddLoot( LootPack.Parrot ); + AddLoot(LootPack.Gems); + } - switch ( Utility.Random( 3 ) ) - { - case 0: - { - Say( 1042156 ); // I can grant life, and I can sap it as easily. - PlaySound( 0x1E6 ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - toDrain = Utility.RandomMinMax( 3, 6 ); - Hits += toDrain; - m.Hits -= toDrain; - break; - } - case 1: - { - Say( 1042157 ); // You'll go nowhere, unless I deem it should be so. - PlaySound( 0x1DF ); + if (Utility.RandomDouble() < 0.1) + Drain(defender); + } - toDrain = Utility.RandomMinMax( 10, 25 ); - Stam += toDrain; - m.Stam -= toDrain; - break; - } - case 2: - { - Say( 1042155 ); // Your power is mine to use as I will. - PlaySound( 0x1F8 ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - toDrain = Utility.RandomMinMax( 15, 25 ); - Mana += toDrain; - m.Mana -= toDrain; - break; - } - } - } + if (Utility.RandomDouble() < 0.1) + Drain(attacker); + } - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public virtual void Drain(Mobile m) + { + int toDrain; - if ( Utility.RandomDouble() < 0.75 ) - c.DropItem( new CrystallineFragments() ); + switch (Utility.Random(3)) + { + case 0: + { + Say(1042156); // I can grant life, and I can sap it as easily. + PlaySound(0x1E6); - if ( Utility.RandomDouble() < 0.07 ) - c.DropItem( new PiecesOfCrystal() ); - } - */ + toDrain = Utility.RandomMinMax(3, 6); + Hits += toDrain; + m.Hits -= toDrain; + break; + } + case 1: + { + Say(1042157); // You'll go nowhere, unless I deem it should be so. + PlaySound(0x1DF); - public override int Feathers => 100; - public override int TreasureMapLevel => 5; + toDrain = Utility.RandomMinMax(10, 25); + Stam += toDrain; + m.Stam -= toDrain; + break; + } + case 2: + { + Say(1042155); // Your power is mine to use as I will. + PlaySound(0x1F8); - public override int GetAttackSound() { return 0x2F6; } - public override int GetDeathSound() { return 0x2F7; } - public override int GetAngerSound() { return 0x2F8; } - public override int GetHurtSound() { return 0x2F9; } - public override int GetIdleSound() { return 0x2FA; } + toDrain = Utility.RandomMinMax(15, 25); + Mana += toDrain; + m.Mana -= toDrain; + break; + } + } + } - public CrystalLatticeSeeker( Serial serial ) - : base( serial ) - { - } + public override int GetAttackSound() + { + return 0x2F6; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int GetDeathSound() + { + return 0x2F7; + } - writer.Write( (int) 0 ); // version - } + public override int GetAngerSound() + { + return 0x2F8; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int GetHurtSound() + { + return 0x2F9; + } - int version = reader.ReadInt(); - } - } -} + public override int GetIdleSound() + { + return 0x2FA; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalSeaSerpent.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalSeaSerpent.cs index 9f5d086f4..1d65e7c1b 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalSeaSerpent.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalSeaSerpent.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - public class CrystalSeaSerpent : SeaSerpent - { - public override string CorpseName => "a crystal sea serpent corpse"; - public override string DefaultName => "a crystal sea serpent"; + public class CrystalSeaSerpent : SeaSerpent + { + [Constructible] + public CrystalSeaSerpent() + { + Hue = 0x47E; - [Constructible] - public CrystalSeaSerpent() - { - Hue = 0x47E; + SetStr(250, 450); + SetDex(100, 150); + SetInt(90, 190); - SetStr( 250, 450 ); - SetDex( 100, 150 ); - SetInt( 90, 190 ); + SetHits(230, 330); - SetHits( 230, 330 ); + SetDamage(10, 18); - SetDamage( 10, 18 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Cold, 45); + SetDamageType(ResistanceType.Energy, 45); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Cold, 45 ); - SetDamageType( ResistanceType.Energy, 45 ); + SetResistance(ResistanceType.Physical, 50, 70); + SetResistance(ResistanceType.Fire, 0); + SetResistance(ResistanceType.Cold, 70, 90); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 60, 80); + } - SetResistance( ResistanceType.Physical, 50, 70 ); - SetResistance( ResistanceType.Fire, 0 ); - SetResistance( ResistanceType.Cold, 70, 90 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 60, 80 ); - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.05 ) + c.DropItem( new CrushedCrystals() ); - if ( Utility.RandomDouble() < 0.05 ) - c.DropItem( new CrushedCrystals() ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new IcyHeart() ); - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new IcyHeart() ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new LuckyDagger() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new LuckyDagger() ); - } - */ + public CrystalSeaSerpent(Serial serial) + : base(serial) + { + } - public CrystalSeaSerpent( Serial serial ) - : base( serial ) - { - } + public override string CorpseName => "a crystal sea serpent corpse"; + public override string DefaultName => "a crystal sea serpent"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalVortex.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalVortex.cs index 0282c62ce..de833287c 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalVortex.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalVortex.cs @@ -1,88 +1,95 @@ namespace Server.Mobiles { - public class CrystalVortex : BaseCreature - { - public override string CorpseName => "a crystal vortex corpse"; - public override string DefaultName => "a crystal vortex"; + public class CrystalVortex : BaseCreature + { + [Constructible] + public CrystalVortex() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0xD; + Hue = 0x2B2; + BaseSoundID = 0x107; - [Constructible] - public CrystalVortex() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0xD; - Hue = 0x2B2; - BaseSoundID = 0x107; + SetStr(800, 900); + SetDex(500, 600); + SetInt(200); - SetStr( 800, 900 ); - SetDex( 500, 600 ); - SetInt( 200 ); + SetHits(350, 400); + SetMana(0); - SetHits( 350, 400 ); - SetMana( 0 ); + SetDamage(15, 20); - SetDamage( 15, 20 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 60, 80); + SetResistance(ResistanceType.Fire, 0, 10); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 60, 90); - SetResistance( ResistanceType.Physical, 60, 80 ); - SetResistance( ResistanceType.Fire, 0, 10 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 60, 90 ); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Wrestling, 120.0); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); + Fame = 17000; + Karma = -17000; - Fame = 17000; - Karma = -17000; + PackArcaneScroll(0, 2); + } - PackArcaneScroll( 0, 2 ); - } + public CrystalVortex(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - // TODO: uncomment once added - //AddLoot( LootPack.Parrot ); - } + public override string CorpseName => "a crystal vortex corpse"; + public override string DefaultName => "a crystal vortex"; - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + // TODO: uncomment once added + //AddLoot( LootPack.Parrot ); + } - if ( Utility.RandomDouble() < 0.75 ) - c.DropItem( new CrystallineFragments() ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - if ( Utility.RandomDouble() < 0.06 ) - c.DropItem( new JaggedCrystals() ); - } - */ + if ( Utility.RandomDouble() < 0.75 ) + c.DropItem( new CrystallineFragments() ); - public override int GetAngerSound() { return 0x15; } - public override int GetAttackSound() { return 0x28; } + if ( Utility.RandomDouble() < 0.06 ) + c.DropItem( new JaggedCrystals() ); + } + */ - public CrystalVortex( Serial serial ) - : base( serial ) - { - } + public override int GetAngerSound() + { + return 0x15; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int GetAttackSound() + { + return 0x28; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalWisp.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalWisp.cs index 2f61b72dc..dbfc24ae1 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalWisp.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/CrystalWisp.cs @@ -1,34 +1,34 @@ namespace Server.Mobiles { - public class CrystalWisp : Wisp - { - public override string DefaultName => "a crystal wisp"; + public class CrystalWisp : Wisp + { + [Constructible] + public CrystalWisp() + { + Hue = 0x482; - [Constructible] - public CrystalWisp() - { - Hue = 0x482; + PackArcaneScroll(0, 1); + } - PackArcaneScroll( 0, 1 ); - } + public CrystalWisp(Serial serial) + : base(serial) + { + } - public CrystalWisp( Serial serial ) - : base( serial ) - { - } + public override string DefaultName => "a crystal wisp"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/MantraEffervescence.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/MantraEffervescence.cs index a1035b827..cb2431b05 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/MantraEffervescence.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/MantraEffervescence.cs @@ -1,68 +1,68 @@ namespace Server.Mobiles { - public class MantraEffervescence : BaseCreature - { - public override string CorpseName => "a mantra effervescence corpse"; - public override string DefaultName => "a mantra effervescence"; + public class MantraEffervescence : BaseCreature + { + [Constructible] + public MantraEffervescence() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x111; + BaseSoundID = 0x56E; - [Constructible] - public MantraEffervescence() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x111; - BaseSoundID = 0x56E; + SetStr(130, 150); + SetDex(120, 130); + SetInt(150, 230); - SetStr( 130, 150 ); - SetDex( 120, 130 ); - SetInt( 150, 230 ); + SetHits(150, 250); - SetHits( 150, 250 ); + SetDamage(21, 25); - SetDamage( 21, 25 ); + SetDamageType(ResistanceType.Physical, 30); + SetDamageType(ResistanceType.Energy, 70); - SetDamageType( ResistanceType.Physical, 30 ); - SetDamageType( ResistanceType.Energy, 70 ); + SetResistance(ResistanceType.Physical, 60, 65); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 100); - SetResistance( ResistanceType.Physical, 60, 65 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 100 ); + SetSkill(SkillName.Wrestling, 80.0, 85.0); + SetSkill(SkillName.Tactics, 80.0, 85.0); + SetSkill(SkillName.MagicResist, 105.0, 115.0); + SetSkill(SkillName.Magery, 90.0, 110.0); + SetSkill(SkillName.EvalInt, 80.0, 90.0); + SetSkill(SkillName.Meditation, 90.0, 100.0); - SetSkill( SkillName.Wrestling, 80.0, 85.0 ); - SetSkill( SkillName.Tactics, 80.0, 85.0 ); - SetSkill( SkillName.MagicResist, 105.0, 115.0 ); - SetSkill( SkillName.Magery, 90.0, 110.0 ); - SetSkill( SkillName.EvalInt, 80.0, 90.0 ); - SetSkill( SkillName.Meditation, 90.0, 100.0 ); + Fame = 6500; + Karma = -6500; + } - Fame = 6500; - Karma = -6500; - } + public MantraEffervescence(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a mantra effervescence corpse"; + public override string DefaultName => "a mantra effervescence"; - public MantraEffervescence( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/Protector.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/Protector.cs index 8d1877c28..8c47b6d01 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/Protector.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/Protector.cs @@ -2,106 +2,106 @@ using Server.Items; namespace Server.Mobiles { - public class Protector : BaseCreature - { - public override string CorpseName => "a human corpse"; - public override string DefaultName => "a Protector"; + public class Protector : BaseCreature + { + [Constructible] + public Protector() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 401; + Female = true; + Hue = Race.Human.RandomSkinHue(); + HairItemID = Race.Human.RandomHair(this); + HairHue = Race.Human.RandomHairHue(); - [Constructible] - public Protector() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 401; - Female = true; - Hue = Race.Human.RandomSkinHue(); - HairItemID = Race.Human.RandomHair( this ); - HairHue = Race.Human.RandomHairHue(); + Title = "the mystic llamaherder"; - Title = "the mystic llamaherder"; + SetStr(700, 800); + SetDex(100, 150); + SetInt(50, 75); - SetStr( 700, 800 ); - SetDex( 100, 150 ); - SetInt( 50, 75 ); + SetHits(350, 450); - SetHits( 350, 450 ); + SetDamage(6, 12); - SetDamage( 6, 12 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 35, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 35, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Wrestling, 70.0, 100.0); + SetSkill(SkillName.Tactics, 80.0, 100.0); + SetSkill(SkillName.MagicResist, 50.0, 70.0); + SetSkill(SkillName.Anatomy, 70.0, 100.0); - SetSkill( SkillName.Wrestling, 70.0, 100.0 ); - SetSkill( SkillName.Tactics, 80.0, 100.0 ); - SetSkill( SkillName.MagicResist, 50.0, 70.0 ); - SetSkill( SkillName.Anatomy, 70.0, 100.0 ); + Fame = 10000; + Karma = -10000; - Fame = 10000; - Karma = -10000; + Item boots = new ThighBoots(); + boots.Movable = false; + boots.Hue = Utility.Random(2); - Item boots = new ThighBoots(); - boots.Movable = false; - boots.Hue = Utility.Random( 2 ); + Item shroud = new Item(0x204E); + shroud.Layer = Layer.OuterTorso; + shroud.Movable = false; + shroud.Hue = Utility.Random(2); - Item shroud = new Item( 0x204E ); - shroud.Layer = Layer.OuterTorso; - shroud.Movable = false; - shroud.Hue = Utility.Random( 2 ); + AddItem(boots); + AddItem(shroud); + } - AddItem( boots ); - AddItem( shroud ); - } + public Protector(Serial serial) + : base(serial) + { + } - public override bool AlwaysMurderer => true; - public override bool PropertyTitle => false; - public override bool ShowFameTitle => false; + public override string CorpseName => "a human corpse"; + public override string DefaultName => "a Protector"; - public Protector( Serial serial ) - : base( serial ) - { - } + public override bool AlwaysMurderer => true; + public override bool PropertyTitle => false; + public override bool ShowFameTitle => false; - public override void GenerateLoot( bool spawning ) - { - if ( spawning ) - return; // No loot/backpack on spawn + public override void GenerateLoot(bool spawning) + { + if (spawning) + return; // No loot/backpack on spawn - base.GenerateLoot( true ); - base.GenerateLoot( false ); - } + base.GenerateLoot(true); + base.GenerateLoot(false); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + } - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - if ( Utility.RandomDouble() < 0.4 ) - c.DropItem( new ProtectorsEssence() ); - } - */ + if ( Utility.RandomDouble() < 0.4 ) + c.DropItem( new ProtectorsEssence() ); + } + */ - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Prism of Light/UnfrozenMummy.cs b/Scripts/Mobiles/Monsters/ML/Prism of Light/UnfrozenMummy.cs index 1f6c721dc..3f926fac4 100644 --- a/Scripts/Mobiles/Monsters/ML/Prism of Light/UnfrozenMummy.cs +++ b/Scripts/Mobiles/Monsters/ML/Prism of Light/UnfrozenMummy.cs @@ -1,87 +1,87 @@ namespace Server.Mobiles { - public class UnfrozenMummy : BaseCreature - { - public override string CorpseName => "an unfrozen mummy corpse"; - public override string DefaultName => "an unfrozen mummy"; + public class UnfrozenMummy : BaseCreature + { + [Constructible] + public UnfrozenMummy() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.4, 0.8) + { + Body = 0x9B; + Hue = 0x480; + BaseSoundID = 0x1D7; - [Constructible] - public UnfrozenMummy() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.4, 0.8 ) - { - Body = 0x9B; - Hue = 0x480; - BaseSoundID = 0x1D7; + SetStr(450, 500); + SetDex(200, 250); + SetInt(800, 850); - SetStr( 450, 500 ); - SetDex( 200, 250 ); - SetInt( 800, 850 ); + SetHits(1500); - SetHits( 1500 ); + SetDamage(16, 20); - SetDamage( 16, 20 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Energy, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Energy, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 60, 80); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 70, 80); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 60, 80 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 70, 80 ); + SetSkill(SkillName.Wrestling, 90.0, 100.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.MagicResist, 250.0); + SetSkill(SkillName.Magery, 50.0, 60.0); + SetSkill(SkillName.EvalInt, 50.0, 60.0); + SetSkill(SkillName.Meditation, 80.0); - SetSkill( SkillName.Wrestling, 90.0, 100.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.MagicResist, 250.0 ); - SetSkill( SkillName.Magery, 50.0, 60.0 ); - SetSkill( SkillName.EvalInt, 50.0, 60.0 ); - SetSkill( SkillName.Meditation, 80.0 ); + Fame = 25000; + Karma = -25000; - Fame = 25000; - Karma = -25000; + PackArcaneScroll(0, 2); + } - PackArcaneScroll( 0, 2 ); - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - // TODO: uncomment once added - //AddLoot( LootPack.Parrot ); - } + if ( Utility.RandomDouble() < 0.6 ) + c.DropItem( new BrokenCrystals() ); - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( Utility.RandomDouble() < 0.6 ) - c.DropItem( new BrokenCrystals() ); + public UnfrozenMummy(Serial serial) + : base(serial) + { + } - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override string CorpseName => "an unfrozen mummy corpse"; + public override string DefaultName => "an unfrozen mummy"; - public UnfrozenMummy( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + // TODO: uncomment once added + //AddLoot( LootPack.Parrot ); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Sanctuary/Chiikkaha.cs b/Scripts/Mobiles/Monsters/ML/Sanctuary/Chiikkaha.cs index 9688b8166..411e6af5b 100644 --- a/Scripts/Mobiles/Monsters/ML/Sanctuary/Chiikkaha.cs +++ b/Scripts/Mobiles/Monsters/ML/Sanctuary/Chiikkaha.cs @@ -1,56 +1,56 @@ namespace Server.Mobiles { - public class Chiikkaha : RatmanMage - { - public override string CorpseName => "a Chiikkaha the Toothed corpse"; - public override string DefaultName => "Chiikkaha the Toothed"; + public class Chiikkaha : RatmanMage + { + [Constructible] + public Chiikkaha() + { + SetStr(450, 476); + SetDex(157, 179); + SetInt(251, 275); - [Constructible] - public Chiikkaha() - { - SetStr( 450, 476 ); - SetDex( 157, 179 ); - SetInt( 251, 275 ); + SetHits(400, 425); - SetHits( 400, 425 ); + SetDamage(10, 17); - SetDamage( 10, 17 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 45); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 100); - SetResistance( ResistanceType.Physical, 40, 45 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 100 ); + SetSkill(SkillName.EvalInt, 70.1, 80.0); + SetSkill(SkillName.Magery, 70.1, 90.0); + SetSkill(SkillName.MagicResist, 65.1, 96.0); + SetSkill(SkillName.Tactics, 50.1, 75.0); + SetSkill(SkillName.Wrestling, 50.1, 75.0); - SetSkill( SkillName.EvalInt, 70.1, 80.0 ); - SetSkill( SkillName.Magery, 70.1, 90.0 ); - SetSkill( SkillName.MagicResist, 65.1, 96.0 ); - SetSkill( SkillName.Tactics, 50.1, 75.0 ); - SetSkill( SkillName.Wrestling, 50.1, 75.0 ); + Fame = 7500; + Karma = -7500; + } - Fame = 7500; - Karma = -7500; - } + public Chiikkaha(Serial serial) + : base(serial) + { + } - public Chiikkaha( Serial serial ) - : base( serial ) - { - } + public override string CorpseName => "a Chiikkaha the Toothed corpse"; + public override string DefaultName => "Chiikkaha the Toothed"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Sanctuary/MougGuur.cs b/Scripts/Mobiles/Monsters/ML/Sanctuary/MougGuur.cs index 63c823681..0a7c088ed 100644 --- a/Scripts/Mobiles/Monsters/ML/Sanctuary/MougGuur.cs +++ b/Scripts/Mobiles/Monsters/ML/Sanctuary/MougGuur.cs @@ -1,54 +1,54 @@ namespace Server.Mobiles { - public class MougGuur : Ettin - { - public override string CorpseName => "a Moug-Guur corpse"; - public override string DefaultName => "Moug-Guur"; + public class MougGuur : Ettin + { + [Constructible] + public MougGuur() + { + SetStr(556, 575); + SetDex(84, 94); + SetInt(59, 73); - [Constructible] - public MougGuur() - { - SetStr( 556, 575 ); - SetDex( 84, 94 ); - SetInt( 59, 73 ); + SetHits(400, 415); - SetHits( 400, 415 ); + SetDamage(12, 20); - SetDamage( 12, 20 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 61, 65); + SetResistance(ResistanceType.Fire, 16, 19); + SetResistance(ResistanceType.Cold, 41, 46); + SetResistance(ResistanceType.Poison, 21, 24); + SetResistance(ResistanceType.Energy, 19, 25); - SetResistance( ResistanceType.Physical, 61, 65 ); - SetResistance( ResistanceType.Fire, 16, 19 ); - SetResistance( ResistanceType.Cold, 41, 46 ); - SetResistance( ResistanceType.Poison, 21, 24 ); - SetResistance( ResistanceType.Energy, 19, 25 ); + SetSkill(SkillName.MagicResist, 70.2, 75.0); + SetSkill(SkillName.Tactics, 80.8, 81.7); + SetSkill(SkillName.Wrestling, 93.9, 99.4); - SetSkill( SkillName.MagicResist, 70.2, 75.0 ); - SetSkill( SkillName.Tactics, 80.8, 81.7 ); - SetSkill( SkillName.Wrestling, 93.9, 99.4 ); + Fame = 3000; + Karma = -3000; + } - Fame = 3000; - Karma = -3000; - } + public MougGuur(Serial serial) + : base(serial) + { + } - public MougGuur( Serial serial ) - : base( serial ) - { - } + public override string CorpseName => "a Moug-Guur corpse"; + public override string DefaultName => "Moug-Guur"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Sanctuary/Szavetra.cs b/Scripts/Mobiles/Monsters/ML/Sanctuary/Szavetra.cs index ed779785d..f495d9fb1 100644 --- a/Scripts/Mobiles/Monsters/ML/Sanctuary/Szavetra.cs +++ b/Scripts/Mobiles/Monsters/ML/Sanctuary/Szavetra.cs @@ -1,58 +1,58 @@ namespace Server.Mobiles { - public class Szavetra : Succubus - { - public override string CorpseName => "a Szavetra corpse"; - public override string DefaultName => "Szavetra"; + public class Szavetra : Succubus + { + [Constructible] + public Szavetra() + { + SetStr(627, 655); + SetDex(164, 193); + SetInt(566, 595); - [Constructible] - public Szavetra() - { - SetStr( 627, 655 ); - SetDex( 164, 193 ); - SetInt( 566, 595 ); + SetHits(312, 415); - SetHits( 312, 415 ); + SetDamage(20, 30); - SetDamage( 20, 30 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Energy, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Energy, 25 ); + SetResistance(ResistanceType.Physical, 83, 90); + SetResistance(ResistanceType.Fire, 72, 80); + SetResistance(ResistanceType.Cold, 40, 49); + SetResistance(ResistanceType.Poison, 51, 60); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 83, 90 ); - SetResistance( ResistanceType.Fire, 72, 80 ); - SetResistance( ResistanceType.Cold, 40, 49 ); - SetResistance( ResistanceType.Poison, 51, 60 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.EvalInt, 90.3, 99.8); + SetSkill(SkillName.Magery, 100.1, 100.6); // 10.1-10.6 on OSI, bug? + SetSkill(SkillName.Meditation, 90.1, 110.0); + SetSkill(SkillName.MagicResist, 112.2, 127.2); + SetSkill(SkillName.Tactics, 91.2, 92.8); + SetSkill(SkillName.Wrestling, 80.2, 86.4); - SetSkill( SkillName.EvalInt, 90.3, 99.8 ); - SetSkill( SkillName.Magery, 100.1, 100.6 ); // 10.1-10.6 on OSI, bug? - SetSkill( SkillName.Meditation, 90.1, 110.0 ); - SetSkill( SkillName.MagicResist, 112.2, 127.2 ); - SetSkill( SkillName.Tactics, 91.2, 92.8 ); - SetSkill( SkillName.Wrestling, 80.2, 86.4 ); + Fame = 24000; + Karma = -24000; + } - Fame = 24000; - Karma = -24000; - } + public Szavetra(Serial serial) + : base(serial) + { + } - public Szavetra( Serial serial ) - : base( serial ) - { - } + public override string CorpseName => "a Szavetra corpse"; + public override string DefaultName => "Szavetra"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Special/Ilhenir.cs b/Scripts/Mobiles/Monsters/ML/Special/Ilhenir.cs index 9893cad2a..67101ac2d 100644 --- a/Scripts/Mobiles/Monsters/ML/Special/Ilhenir.cs +++ b/Scripts/Mobiles/Monsters/ML/Special/Ilhenir.cs @@ -1,435 +1,450 @@ using System; using System.Collections; -using Server.Items; -using Server.Network; using System.Collections.Generic; using Server.Engines.CannedEvil; +using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class Ilhenir : BaseChampion - { - public override string CorpseName => "a corpse of Ilhenir"; - public override ChampionSkullType SkullType => ChampionSkullType.Pain; - - public override Type[] UniqueList => new Type[] { }; - - public override Type[] SharedList => new [] - { - typeof(ANecromancerShroud), - typeof(LieutenantOfTheBritannianRoyalGuard), - typeof(OblivionsNeedle), - typeof(TheRobeOfBritanniaAri), - }; - - public override Type[] DecorativeList => new [] { typeof(MonsterStatuette) }; - - public override MonsterStatuetteType[] StatueTypes => new [] - { - MonsterStatuetteType.PlagueBeast, - MonsterStatuetteType.RedDeath, - }; - - public override string DefaultName => "Ilhenir"; - - [Constructible] - public Ilhenir() - : base( AIType.AI_Mage ) - { - Title = "the Stained"; - Body = 0x103; - - BaseSoundID = 589; - - SetStr( 1105, 1350 ); - SetDex( 82, 160 ); - SetInt( 505, 750 ); - - SetHits( 9000 ); - - SetDamage( 21, 28 ); - - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Fire, 20 ); - SetDamageType( ResistanceType.Poison, 20 ); - - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 55, 65 ); - SetResistance( ResistanceType.Poison, 70, 90 ); - SetResistance( ResistanceType.Energy, 65, 75 ); - - SetSkill( SkillName.EvalInt, 100 ); - SetSkill( SkillName.Magery, 100 ); - SetSkill( SkillName.Meditation, 0 ); - SetSkill( SkillName.Poisoning, 5.4 ); - SetSkill( SkillName.Anatomy, 117.5 ); - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Tactics, 119.9 ); - SetSkill( SkillName.Wrestling, 119.9 ); - - Fame = 50000; - Karma = -50000; - - VirtualArmor = 44; - - if ( Core.ML ) { - PackResources( 8 ); - PackTalismans( 5 ); - } - } - - public virtual void PackResources( int amount ) - { - for( int i = 0; i < amount; i++ ) - switch( Utility.Random( 6 ) ) - { - case 0: PackItem( new Blight() ); break; - case 1: PackItem( new Scourge() ); break; - case 2: PackItem( new Taint() ); break; - case 3: PackItem( new Putrefication() ); break; - case 4: PackItem( new Corruption() ); break; - case 5: PackItem( new Muculent() ); break; - } - } - - public virtual void PackItems( Item item, int amount ) - { - for( int i = 0; i < amount; i++ ) - PackItem( item ); - } - - public virtual void PackTalismans( int amount ) - { - int count = Utility.Random( amount ); - - for( int i = 0; i < count; i++ ) - PackItem( new RandomTalisman() ); - } - - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 8 ); - } - - public override void OnDeath( Container c ) - { - base.OnDeath( c ); - - if ( Core.ML ) { - c.DropItem( new GrizzledBones() ); - - // TODO: Parrots - /*if ( Utility.RandomDouble() < 0.6 ) - c.DropItem( new ParrotItem() ); */ - - if ( Utility.RandomDouble() < 0.05 ) - c.DropItem( new GrizzledMareStatuette() ); - - if ( Utility.RandomDouble() < 0.025 ) - c.DropItem( new CrimsonCincture() ); - - // TODO: Armor sets - /*if ( Utility.RandomDouble() < 0.05 ) - { - switch ( Utility.Random(5) ) - { - case 0: c.DropItem( new GrizzleGauntlets() ); break; - case 1: c.DropItem( new GrizzleGreaves() ); break; - case 2: c.DropItem( new GrizzleHelm() ); break; - case 3: c.DropItem( new GrizzleTunic() ); break; - case 4: c.DropItem( new GrizzleVambraces() ); break; - } - }*/ - } - } - - public override bool Unprovokable => true; - public override bool Uncalmable => true; - public override Poison PoisonImmune => Poison.Lethal; - //public override bool GivesMLMinorArtifact => true; // TODO: Needs verification - public override int TreasureMapLevel => 5; - - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); - - if ( Utility.RandomDouble() < 0.25 ) - CacophonicAttack( defender ); - } - - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( Utility.RandomDouble() < 0.1 ) - DropOoze(); - - base.OnDamage( amount, from, willKill ); - } - - public override int GetAngerSound() - { - return 0x581; - } - - public override int GetIdleSound() - { - return 0x582; - } - - public override int GetAttackSound() - { - return 0x580; - } - - public override int GetHurtSound() - { - return 0x583; - } - - public override int GetDeathSound() - { - return 0x584; - } - - public Ilhenir( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - private static Hashtable m_Table; - - public virtual void CacophonicAttack( Mobile to ) - { - if ( m_Table == null ) - m_Table = new Hashtable(); - - if ( to.Alive && to.Player && m_Table[ to ] == null ) - { - to.Send( SpeedControl.WalkSpeed ); - to.SendLocalizedMessage( 1072069 ); // A cacophonic sound lambastes you, suppressing your ability to move. - to.PlaySound( 0x584 ); - - m_Table[ to ] = Timer.DelayCall( TimeSpan.FromSeconds( 30 ), new TimerStateCallback( EndCacophonic_Callback ), to ); - } - } - - private void EndCacophonic_Callback( object state ) - { - if ( state is Mobile mobile ) - CacophonicEnd( mobile ); - } - - public virtual void CacophonicEnd( Mobile from ) - { - if ( m_Table == null ) - m_Table = new Hashtable(); - - m_Table[ from ] = null; - - from.Send( SpeedControl.Disable ); - } - - public static bool UnderCacophonicAttack( Mobile from ) - { - if ( m_Table == null ) - m_Table = new Hashtable(); - - return m_Table[ from ] != null; - } - - private DateTime m_NextDrop = DateTime.UtcNow; - - public virtual void DropOoze() - { - int amount = Utility.RandomMinMax( 1, 3 ); - bool corrosive = Utility.RandomBool(); - - for( int i = 0; i < amount; i++ ) - { - Item ooze = new StainedOoze( corrosive ); - Point3D p = new Point3D( Location ); - - for( int j = 0; j < 5; j++ ) - { - p = GetSpawnPosition( 2 ); - bool found = false; - - foreach( Item item in Map.GetItemsInRange( p, 0 ) ) - if ( item is StainedOoze ) - { - found = true; - break; - } - - if ( !found ) - break; - } - - ooze.MoveToWorld( p, Map ); - } - - if ( Combatant != null ) - { - if ( corrosive ) - Combatant.SendLocalizedMessage( 1072071 ); // A corrosive gas seeps out of your enemy's skin! - else - Combatant.SendLocalizedMessage( 1072072 ); // A poisonous gas seeps out of your enemy's skin! - } - } - - private int RandomPoint( int mid ) - { - return ( mid + Utility.RandomMinMax( -2, 2 ) ); - } - - public virtual Point3D GetSpawnPosition( int range ) - { - return GetSpawnPosition( Location, Map, range ); - } - - public virtual Point3D GetSpawnPosition( Point3D from, Map map, int range ) - { - if ( map == null ) - return from; - - Point3D loc = new Point3D( ( RandomPoint( X ) ), ( RandomPoint( Y ) ), Z ); - - loc.Z = Map.GetAverageZ( loc.X, loc.Y ); - - return loc; - } - } - - public class StainedOoze : Item - { - private Timer m_Timer; - private int m_Ticks; - - [CommandProperty( AccessLevel.GameMaster )] - public bool Corrosive { get; set; } - - [Constructible] - public StainedOoze() - : this( false ) - { - } - - [Constructible] - public StainedOoze( bool corrosive ) - : base( 0x122A ) - { - Movable = false; - Hue = 0x95; - - Corrosive = corrosive; - m_Timer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromSeconds( 1 ), OnTick ); - m_Ticks = 0; - } - - public override void OnAfterDelete() - { - if ( m_Timer != null ) - { - m_Timer.Stop(); - m_Timer = null; - } - } - - private void OnTick() - { - List toDamage = new List(); - - foreach ( Mobile m in GetMobilesInRange( 0 ) ) - { - if ( m is BaseCreature bc ) - { - if ( !bc.Controlled && !bc.Summoned ) - continue; - } - else if ( !m.Player ) - { - continue; - } - - if ( m.Alive && !m.IsDeadBondedPet && m.CanBeDamaged() ) - toDamage.Add( m ); - } - - for ( int i = 0; i < toDamage.Count; ++i ) - Damage( toDamage[i] ); - - ++m_Ticks; - - if ( m_Ticks >= 35 ) - Delete(); - else if ( m_Ticks == 30 ) - ItemID = 0x122B; - } - - public void Damage( Mobile m ) - { - if ( Corrosive ) - { - List items = m.Items; - bool damaged = false; - - for ( int i = 0; i < items.Count; ++i ) - { - if ( items[i] is IDurability wearable && wearable.HitPoints >= 10 && Utility.RandomDouble() < 0.25 ) - { - wearable.HitPoints -= ( wearable.HitPoints == 10 ) ? Utility.Random( 1, 5 ) : 10; - damaged = true; - } - } - - if ( damaged ) - { - m.LocalOverheadMessage( MessageType.Regular, 0x21, 1072070 ); // The infernal ooze scorches you, setting you and your equipment ablaze! - return; - } - } - - AOS.Damage( m, 40, 0, 0, 0, 100, 0 ); - } - - public StainedOoze( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( Corrosive ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Corrosive = reader.ReadBool(); - - m_Timer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromSeconds( 1 ), OnTick ); - m_Ticks = ( ItemID == 0x122A ) ? 0 : 30; - } - } -} + public class Ilhenir : BaseChampion + { + private static Hashtable m_Table; + + private DateTime m_NextDrop = DateTime.UtcNow; + + [Constructible] + public Ilhenir() + : base(AIType.AI_Mage) + { + Title = "the Stained"; + Body = 0x103; + + BaseSoundID = 589; + + SetStr(1105, 1350); + SetDex(82, 160); + SetInt(505, 750); + + SetHits(9000); + + SetDamage(21, 28); + + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Fire, 20); + SetDamageType(ResistanceType.Poison, 20); + + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 55, 65); + SetResistance(ResistanceType.Poison, 70, 90); + SetResistance(ResistanceType.Energy, 65, 75); + + SetSkill(SkillName.EvalInt, 100); + SetSkill(SkillName.Magery, 100); + SetSkill(SkillName.Meditation, 0); + SetSkill(SkillName.Poisoning, 5.4); + SetSkill(SkillName.Anatomy, 117.5); + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Tactics, 119.9); + SetSkill(SkillName.Wrestling, 119.9); + + Fame = 50000; + Karma = -50000; + + VirtualArmor = 44; + + if (Core.ML) + { + PackResources(8); + PackTalismans(5); + } + } + + public Ilhenir(Serial serial) + : base(serial) + { + } + + public override string CorpseName => "a corpse of Ilhenir"; + public override ChampionSkullType SkullType => ChampionSkullType.Pain; + + public override Type[] UniqueList => new Type[] { }; + + public override Type[] SharedList => new[] + { + typeof(ANecromancerShroud), + typeof(LieutenantOfTheBritannianRoyalGuard), + typeof(OblivionsNeedle), + typeof(TheRobeOfBritanniaAri) + }; + + public override Type[] DecorativeList => new[] { typeof(MonsterStatuette) }; + + public override MonsterStatuetteType[] StatueTypes => new[] + { + MonsterStatuetteType.PlagueBeast, + MonsterStatuetteType.RedDeath + }; + + public override string DefaultName => "Ilhenir"; + + public override bool Unprovokable => true; + public override bool Uncalmable => true; + + public override Poison PoisonImmune => Poison.Lethal; + + //public override bool GivesMLMinorArtifact => true; // TODO: Needs verification + public override int TreasureMapLevel => 5; + + public virtual void PackResources(int amount) + { + for (int i = 0; i < amount; i++) + switch (Utility.Random(6)) + { + case 0: + PackItem(new Blight()); + break; + case 1: + PackItem(new Scourge()); + break; + case 2: + PackItem(new Taint()); + break; + case 3: + PackItem(new Putrefication()); + break; + case 4: + PackItem(new Corruption()); + break; + case 5: + PackItem(new Muculent()); + break; + } + } + + public virtual void PackItems(Item item, int amount) + { + for (int i = 0; i < amount; i++) + PackItem(item); + } + + public virtual void PackTalismans(int amount) + { + int count = Utility.Random(amount); + + for (int i = 0; i < count; i++) + PackItem(new RandomTalisman()); + } + + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 8); + } + + public override void OnDeath(Container c) + { + base.OnDeath(c); + + if (Core.ML) + { + c.DropItem(new GrizzledBones()); + + // TODO: Parrots + /*if ( Utility.RandomDouble() < 0.6 ) + c.DropItem( new ParrotItem() ); */ + + if (Utility.RandomDouble() < 0.05) + c.DropItem(new GrizzledMareStatuette()); + + if (Utility.RandomDouble() < 0.025) + c.DropItem(new CrimsonCincture()); + + // TODO: Armor sets + /*if ( Utility.RandomDouble() < 0.05 ) + { + switch ( Utility.Random(5) ) + { + case 0: c.DropItem( new GrizzleGauntlets() ); break; + case 1: c.DropItem( new GrizzleGreaves() ); break; + case 2: c.DropItem( new GrizzleHelm() ); break; + case 3: c.DropItem( new GrizzleTunic() ); break; + case 4: c.DropItem( new GrizzleVambraces() ); break; + } + }*/ + } + } + + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); + + if (Utility.RandomDouble() < 0.25) + CacophonicAttack(defender); + } + + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (Utility.RandomDouble() < 0.1) + DropOoze(); + + base.OnDamage(amount, from, willKill); + } + + public override int GetAngerSound() + { + return 0x581; + } + + public override int GetIdleSound() + { + return 0x582; + } + + public override int GetAttackSound() + { + return 0x580; + } + + public override int GetHurtSound() + { + return 0x583; + } + + public override int GetDeathSound() + { + return 0x584; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public virtual void CacophonicAttack(Mobile to) + { + if (m_Table == null) + m_Table = new Hashtable(); + + if (to.Alive && to.Player && m_Table[to] == null) + { + to.Send(SpeedControl.WalkSpeed); + to.SendLocalizedMessage(1072069); // A cacophonic sound lambastes you, suppressing your ability to move. + to.PlaySound(0x584); + + m_Table[to] = Timer.DelayCall(TimeSpan.FromSeconds(30), new TimerStateCallback(EndCacophonic_Callback), to); + } + } + + private void EndCacophonic_Callback(object state) + { + if (state is Mobile mobile) + CacophonicEnd(mobile); + } + + public virtual void CacophonicEnd(Mobile from) + { + if (m_Table == null) + m_Table = new Hashtable(); + + m_Table[from] = null; + + from.Send(SpeedControl.Disable); + } + + public static bool UnderCacophonicAttack(Mobile from) + { + if (m_Table == null) + m_Table = new Hashtable(); + + return m_Table[from] != null; + } + + public virtual void DropOoze() + { + int amount = Utility.RandomMinMax(1, 3); + bool corrosive = Utility.RandomBool(); + + for (int i = 0; i < amount; i++) + { + Item ooze = new StainedOoze(corrosive); + Point3D p = new Point3D(Location); + + for (int j = 0; j < 5; j++) + { + p = GetSpawnPosition(2); + bool found = false; + + foreach (Item item in Map.GetItemsInRange(p, 0)) + if (item is StainedOoze) + { + found = true; + break; + } + + if (!found) + break; + } + + ooze.MoveToWorld(p, Map); + } + + if (Combatant != null) + { + if (corrosive) + Combatant.SendLocalizedMessage(1072071); // A corrosive gas seeps out of your enemy's skin! + else + Combatant.SendLocalizedMessage(1072072); // A poisonous gas seeps out of your enemy's skin! + } + } + + private int RandomPoint(int mid) + { + return mid + Utility.RandomMinMax(-2, 2); + } + + public virtual Point3D GetSpawnPosition(int range) + { + return GetSpawnPosition(Location, Map, range); + } + + public virtual Point3D GetSpawnPosition(Point3D from, Map map, int range) + { + if (map == null) + return from; + + Point3D loc = new Point3D(RandomPoint(X), RandomPoint(Y), Z); + + loc.Z = Map.GetAverageZ(loc.X, loc.Y); + + return loc; + } + } + + public class StainedOoze : Item + { + private int m_Ticks; + private Timer m_Timer; + + [Constructible] + public StainedOoze() + : this(false) + { + } + + [Constructible] + public StainedOoze(bool corrosive) + : base(0x122A) + { + Movable = false; + Hue = 0x95; + + Corrosive = corrosive; + m_Timer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromSeconds(1), OnTick); + m_Ticks = 0; + } + + public StainedOoze(Serial serial) + : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Corrosive{ get; set; } + + public override void OnAfterDelete() + { + if (m_Timer != null) + { + m_Timer.Stop(); + m_Timer = null; + } + } + + private void OnTick() + { + List toDamage = new List(); + + foreach (Mobile m in GetMobilesInRange(0)) + { + if (m is BaseCreature bc) + { + if (!bc.Controlled && !bc.Summoned) + continue; + } + else if (!m.Player) + { + continue; + } + + if (m.Alive && !m.IsDeadBondedPet && m.CanBeDamaged()) + toDamage.Add(m); + } + + for (int i = 0; i < toDamage.Count; ++i) + Damage(toDamage[i]); + + ++m_Ticks; + + if (m_Ticks >= 35) + Delete(); + else if (m_Ticks == 30) + ItemID = 0x122B; + } + + public void Damage(Mobile m) + { + if (Corrosive) + { + List items = m.Items; + bool damaged = false; + + for (int i = 0; i < items.Count; ++i) + if (items[i] is IDurability wearable && wearable.HitPoints >= 10 && Utility.RandomDouble() < 0.25) + { + wearable.HitPoints -= wearable.HitPoints == 10 ? Utility.Random(1, 5) : 10; + damaged = true; + } + + if (damaged) + { + m.LocalOverheadMessage(MessageType.Regular, 0x21, + 1072070); // The infernal ooze scorches you, setting you and your equipment ablaze! + return; + } + } + + AOS.Damage(m, 40, 0, 0, 0, 100, 0); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(Corrosive); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Corrosive = reader.ReadBool(); + + m_Timer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromSeconds(1), OnTick); + m_Ticks = ItemID == 0x122A ? 0 : 30; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Special/Meraktus.cs b/Scripts/Mobiles/Monsters/ML/Special/Meraktus.cs index 342108e4e..c4f6a4965 100644 --- a/Scripts/Mobiles/Monsters/ML/Special/Meraktus.cs +++ b/Scripts/Mobiles/Monsters/ML/Special/Meraktus.cs @@ -1,238 +1,259 @@ using System; using System.Collections; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class Meraktus : BaseChampion - { - public override string CorpseName => "the remains of Meraktus"; - public override ChampionSkullType SkullType => ChampionSkullType.Pain; + public class Meraktus : BaseChampion + { + [Constructible] + public Meraktus() + : base(AIType.AI_Melee) + { + Title = "the Tormented"; + Body = 263; + BaseSoundID = 680; + Hue = 0x835; - public override Type[] UniqueList => new [] { typeof( Subdue ) }; - public override Type[] SharedList => new Type[] { }; + SetStr(1419, 1438); + SetDex(309, 413); + SetInt(129, 131); - public override Type[] DecorativeList => new[] - { - typeof(ArtifactLargeVase), - typeof(ArtifactVase), - typeof(MinotaurStatueDeed), - }; + SetHits(4100, 4200); - public override MonsterStatuetteType[] StatueTypes => new [] { MonsterStatuetteType.Minotaur }; + SetDamage(16, 30); - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + SetDamageType(ResistanceType.Physical, 100); - public override string DefaultName => "Meraktus"; + SetResistance(ResistanceType.Physical, 65, 90); + SetResistance(ResistanceType.Fire, 65, 70); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 40, 60); + SetResistance(ResistanceType.Energy, 50, 55); - [Constructible] - public Meraktus() - : base(AIType.AI_Melee) - { - Title = "the Tormented"; - Body = 263; - BaseSoundID = 680; - Hue = 0x835; + //SetSkill( SkillName.Meditation, Unknown ); + //SetSkill( SkillName.EvalInt, Unknown ); + //SetSkill( SkillName.Magery, Unknown ); + //SetSkill( SkillName.Poisoning, Unknown ); + SetSkill(SkillName.Anatomy, 0); + SetSkill(SkillName.MagicResist, 107.0, 111.3); + SetSkill(SkillName.Tactics, 107.0, 117.0); + SetSkill(SkillName.Wrestling, 100.0, 105.0); - SetStr( 1419, 1438 ); - SetDex( 309, 413 ); - SetInt( 129, 131 ); + Fame = 70000; + Karma = -70000; - SetHits( 4100, 4200 ); + VirtualArmor = 28; // Don't know what it should be - SetDamage( 16, 30 ); + if (Core.ML) + { + PackResources(8); + PackTalismans(5); + } - SetDamageType( ResistanceType.Physical, 100 ); + Timer.DelayCall(TimeSpan.FromSeconds(1), SpawnTormented); + } - SetResistance( ResistanceType.Physical, 65, 90 ); - SetResistance( ResistanceType.Fire, 65, 70 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); - SetResistance( ResistanceType.Energy, 50, 55 ); + public Meraktus(Serial serial) : base(serial) + { + } - //SetSkill( SkillName.Meditation, Unknown ); - //SetSkill( SkillName.EvalInt, Unknown ); - //SetSkill( SkillName.Magery, Unknown ); - //SetSkill( SkillName.Poisoning, Unknown ); - SetSkill( SkillName.Anatomy, 0); - SetSkill( SkillName.MagicResist, 107.0, 111.3 ); - SetSkill( SkillName.Tactics, 107.0, 117.0 ); - SetSkill( SkillName.Wrestling, 100.0, 105.0 ); + public override string CorpseName => "the remains of Meraktus"; + public override ChampionSkullType SkullType => ChampionSkullType.Pain; - Fame = 70000; - Karma = -70000; + public override Type[] UniqueList => new[] { typeof(Subdue) }; + public override Type[] SharedList => new Type[] { }; - VirtualArmor = 28; // Don't know what it should be + public override Type[] DecorativeList => new[] + { + typeof(ArtifactLargeVase), + typeof(ArtifactVase), + typeof(MinotaurStatueDeed) + }; - if ( Core.ML ) { - PackResources(8); - PackTalismans(5); - } + public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.Minotaur }; - Timer.DelayCall(TimeSpan.FromSeconds(1), SpawnTormented); - } + public override string DefaultName => "Meraktus"; - public virtual void PackResources(int amount) - { - for (int i = 0; i < amount; i++) - switch (Utility.Random(6)) - { - case 0: PackItem(new Blight()); break; - case 1: PackItem(new Scourge()); break; - case 2: PackItem(new Taint()); break; - case 3: PackItem(new Putrefication()); break; - case 4: PackItem(new Corruption()); break; - case 5: PackItem(new Muculent()); break; - } - } + public override int Meat => 2; + public override int Hides => 10; + public override HideType HideType => HideType.Regular; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 3; + public override bool BardImmune => true; + public override bool Unprovokable => true; + public override bool Uncalmable => true; - public virtual void PackTalismans(int amount) - { - int count = Utility.Random(amount); + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - for (int i = 0; i < count; i++) - PackItem(new RandomTalisman()); - } + public virtual void PackResources(int amount) + { + for (int i = 0; i < amount; i++) + switch (Utility.Random(6)) + { + case 0: + PackItem(new Blight()); + break; + case 1: + PackItem(new Scourge()); + break; + case 2: + PackItem(new Taint()); + break; + case 3: + PackItem(new Putrefication()); + break; + case 4: + PackItem(new Corruption()); + break; + case 5: + PackItem(new Muculent()); + break; + } + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public virtual void PackTalismans(int amount) + { + int count = Utility.Random(amount); - if ( Core.ML ) { - c.DropItem( new MalletAndChisel() ); + for (int i = 0; i < count; i++) + PackItem(new RandomTalisman()); + } - switch ( Utility.Random( 3 ) ) - { - case 0: c.DropItem( new MinotaurHedge() ); break; - case 1: c.DropItem( new BonePile() ); break; - case 2: c.DropItem( new LightYarn() ); break; - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - if ( Utility.RandomBool() ) - c.DropItem( new TormentedChains() ); + if (Core.ML) + { + c.DropItem(new MalletAndChisel()); - if ( Utility.RandomDouble() < 0.025 ) - c.DropItem(new CrimsonCincture()); - } - } + switch (Utility.Random(3)) + { + case 0: + c.DropItem(new MinotaurHedge()); + break; + case 1: + c.DropItem(new BonePile()); + break; + case 2: + c.DropItem(new LightYarn()); + break; + } - public override void GenerateLoot() - { - if ( Core.ML ) { - AddLoot( LootPack.AosSuperBoss, 5 ); // Need to verify - } - } + if (Utility.RandomBool()) + c.DropItem(new TormentedChains()); - public override int GetAngerSound() - { - return 0x597; - } + if (Utility.RandomDouble() < 0.025) + c.DropItem(new CrimsonCincture()); + } + } - public override int GetIdleSound() - { - return 0x596; - } + public override void GenerateLoot() + { + if (Core.ML) AddLoot(LootPack.AosSuperBoss, 5); // Need to verify + } - public override int GetAttackSound() - { - return 0x599; - } + public override int GetAngerSound() + { + return 0x597; + } - public override int GetHurtSound() - { - return 0x59a; - } + public override int GetIdleSound() + { + return 0x596; + } - public override int GetDeathSound() - { - return 0x59c; - } + public override int GetAttackSound() + { + return 0x599; + } - public override int Meat => 2; - public override int Hides => 10; - public override HideType HideType => HideType.Regular; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 3; - public override bool BardImmune => true; - public override bool Unprovokable => true; - public override bool Uncalmable => true; + public override int GetHurtSound() + { + return 0x59a; + } - public override void OnGaveMeleeAttack(Mobile defender) - { - base.OnGaveMeleeAttack(defender); - if (0.2 >= Utility.RandomDouble()) - Earthquake(); - } + public override int GetDeathSound() + { + return 0x59c; + } - public void Earthquake() - { - Map map = Map; - if (map == null) - return; - ArrayList targets = new ArrayList(); - foreach (Mobile m in GetMobilesInRange(8)) - { - if (m == this || !CanBeHarmful(m)) - continue; - if (m is BaseCreature creature && (creature.Controlled || creature.Summoned || creature.Team != Team)) - targets.Add(m); - else if (m.Player) - targets.Add(m); - } - PlaySound(0x2F3); - for (int i = 0; i < targets.Count; ++i) - { - Mobile m = (Mobile)targets[i]; - if ( m != null && !m.Deleted && m is PlayerMobile pm ) - { - if (pm.Mounted) - { - pm.Mount.Rider = null; - } - } - double damage = m.Hits * 0.6; //was .6 - if (damage < 10.0) - damage = 10.0; - else if (damage > 75.0) - damage = 75.0; - DoHarmful(m); - AOS.Damage(m, this, (int)damage, 100, 0, 0, 0, 0); - if (m.Alive && m.Body.IsHuman && !m.Mounted) - m.Animate(20, 7, 1, true, false, 0); // take hit - } - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); + if (0.2 >= Utility.RandomDouble()) + Earthquake(); + } - public Meraktus( Serial serial ) : base( serial ) - { - } + public void Earthquake() + { + Map map = Map; + if (map == null) + return; + ArrayList targets = new ArrayList(); + foreach (Mobile m in GetMobilesInRange(8)) + { + if (m == this || !CanBeHarmful(m)) + continue; + if (m is BaseCreature creature && (creature.Controlled || creature.Summoned || creature.Team != Team)) + targets.Add(m); + else if (m.Player) + targets.Add(m); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + PlaySound(0x2F3); + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = (Mobile)targets[i]; + if (m != null && !m.Deleted && m is PlayerMobile pm) + if (pm.Mounted) + pm.Mount.Rider = null; + double damage = m.Hits * 0.6; //was .6 + if (damage < 10.0) + damage = 10.0; + else if (damage > 75.0) + damage = 75.0; + DoHarmful(m); + AOS.Damage(m, this, (int)damage, 100, 0, 0, 0, 0); + if (m.Alive && m.Body.IsHuman && !m.Mounted) + m.Animate(20, 7, 1, true, false, 0); // take hit + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - #region SpawnHelpers - public void SpawnTormented() - { - BaseCreature spawna = new TormentedMinotaur(); - spawna.MoveToWorld(Location, Map); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - BaseCreature spawnb = new TormentedMinotaur(); - spawnb.MoveToWorld(Location, Map); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - BaseCreature spawnc = new TormentedMinotaur(); - spawnc.MoveToWorld(Location, Map); + #region SpawnHelpers - BaseCreature spawnd = new TormentedMinotaur(); - spawnd.MoveToWorld(Location, Map); - } - #endregion - } -} + public void SpawnTormented() + { + BaseCreature spawna = new TormentedMinotaur(); + spawna.MoveToWorld(Location, Map); + + BaseCreature spawnb = new TormentedMinotaur(); + spawnb.MoveToWorld(Location, Map); + + BaseCreature spawnc = new TormentedMinotaur(); + spawnc.MoveToWorld(Location, Map); + + BaseCreature spawnd = new TormentedMinotaur(); + spawnd.MoveToWorld(Location, Map); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Special/Twaulo.cs b/Scripts/Mobiles/Monsters/ML/Special/Twaulo.cs index 8404946c6..fba4f7ca2 100644 --- a/Scripts/Mobiles/Monsters/ML/Special/Twaulo.cs +++ b/Scripts/Mobiles/Monsters/ML/Special/Twaulo.cs @@ -1,156 +1,156 @@ using System; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class Twaulo : BaseChampion - { - public override string CorpseName => "a corpse of Twaulo"; - public override ChampionSkullType SkullType => ChampionSkullType.Pain; + public class Twaulo : BaseChampion + { + [Constructible] + public Twaulo() + : base(AIType.AI_Melee) + { + Title = "of the Glade"; + Body = 101; + BaseSoundID = 679; + Hue = 0x455; - public override Type[] UniqueList => new[] { typeof( Quell ) }; - public override Type[] SharedList => new[] { typeof( TheMostKnowledgePerson ), typeof( OblivionsNeedle ) }; - public override Type[] DecorativeList => new[] { typeof( Pier ), typeof( MonsterStatuette ) }; + SetStr(1751, 1950); + SetDex(251, 450); + SetInt(801, 1000); - public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.DreadHorn }; + SetHits(7500); - public override string DefaultName => "Twaulo"; + SetDamage(19, 24); - [Constructible] - public Twaulo() - : base(AIType.AI_Melee) - { - Title = "of the Glade"; - Body = 101; - BaseSoundID = 679; - Hue = 0x455; + SetDamageType(ResistanceType.Physical, 100); - SetStr( 1751, 1950 ); - SetDex( 251, 450 ); - SetInt( 801, 1000 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 45, 55); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 50, 60); - SetHits( 7500 ); + SetSkill(SkillName.EvalInt, 0); // Per Stratics?!? + SetSkill(SkillName.Magery, 0); // Per Stratics?!? + SetSkill(SkillName.Meditation, 0); // Per Stratics?!? + SetSkill(SkillName.Anatomy, 95.1, 115.0); + SetSkill(SkillName.Archery, 95.1, 100.0); + SetSkill(SkillName.MagicResist, 50.3, 80.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 95.1, 100.0); - SetDamage( 19, 24 ); + Fame = 50000; + Karma = 50000; - SetDamageType( ResistanceType.Physical, 100 ); + VirtualArmor = 50; - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 45, 55 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + AddItem(new Bow()); + PackItem(new Arrow(Utility.RandomMinMax(500, 700))); + } - SetSkill( SkillName.EvalInt, 0 ); // Per Stratics?!? - SetSkill( SkillName.Magery, 0 ); // Per Stratics?!? - SetSkill( SkillName.Meditation, 0 ); // Per Stratics?!? - SetSkill(SkillName.Anatomy, 95.1, 115.0); - SetSkill(SkillName.Archery, 95.1, 100.0); - SetSkill(SkillName.MagicResist, 50.3, 80.0); - SetSkill(SkillName.Tactics, 90.1, 100.0); - SetSkill(SkillName.Wrestling, 95.1, 100.0); + public Twaulo(Serial serial) + : base(serial) + { + } - Fame = 50000; - Karma = 50000; + public override string CorpseName => "a corpse of Twaulo"; + public override ChampionSkullType SkullType => ChampionSkullType.Pain; - VirtualArmor = 50; + public override Type[] UniqueList => new[] { typeof(Quell) }; + public override Type[] SharedList => new[] { typeof(TheMostKnowledgePerson), typeof(OblivionsNeedle) }; + public override Type[] DecorativeList => new[] { typeof(Pier), typeof(MonsterStatuette) }; - AddItem(new Bow()); - PackItem(new Arrow(Utility.RandomMinMax(500, 700))); - } + public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.DreadHorn }; - public override void GenerateLoot() - { - AddLoot(LootPack.UltraRich, 2); - AddLoot(LootPack.Average); - AddLoot(LootPack.Gems); - } + public override string DefaultName => "Twaulo"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override bool Unprovokable => true; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 5; - public override int Meat => 1; - public override int Hides => 8; - public override HideType HideType => HideType.Spined; + public override bool Unprovokable => true; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 5; + public override int Meat => 1; + public override int Hides => 8; + public override HideType HideType => HideType.Spined; - public void SpawnPixies( Mobile target ) - { - Map map = Map; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems); + } - if ( map == null ) - return; + public void SpawnPixies(Mobile target) + { + Map map = Map; - int newPixies = Utility.RandomMinMax( 3, 6 ); + if (map == null) + return; - for ( int i = 0; i < newPixies; ++i ) - { - Pixie pixie = new Pixie(); + int newPixies = Utility.RandomMinMax(3, 6); - pixie.Team = Team; - pixie.FightMode = FightMode.Closest; + for (int i = 0; i < newPixies; ++i) + { + Pixie pixie = new Pixie(); - bool validLocation = false; - Point3D loc = Location; + pixie.Team = Team; + pixie.FightMode = FightMode.Closest; - for ( int j = 0; !validLocation && j < 10; ++j ) - { - int x = X + Utility.Random( 3 ) - 1; - int y = Y + Utility.Random( 3 ) - 1; - int z = map.GetAverageZ( x, y ); + bool validLocation = false; + Point3D loc = Location; - if ( validLocation = map.CanFit( x, y, Z, 16, false, false ) ) - loc = new Point3D( x, y, Z ); - else if ( validLocation = map.CanFit( x, y, z, 16, false, false ) ) - loc = new Point3D( x, y, z ); - } + for (int j = 0; !validLocation && j < 10; ++j) + { + int x = X + Utility.Random(3) - 1; + int y = Y + Utility.Random(3) - 1; + int z = map.GetAverageZ(x, y); - pixie.MoveToWorld( loc, map ); - pixie.Combatant = target; - } - } + if (validLocation = map.CanFit(x, y, Z, 16, false, false)) + loc = new Point3D(x, y, Z); + else if (validLocation = map.CanFit(x, y, z, 16, false, false)) + loc = new Point3D(x, y, z); + } - public override void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - if ( 0.1 >= Utility.RandomDouble() ) - SpawnPixies( caster ); - } + pixie.MoveToWorld(loc, map); + pixie.Combatant = target; + } + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + if (0.1 >= Utility.RandomDouble()) + SpawnPixies(caster); + } - defender.Damage( Utility.Random( 20, 10 ), this ); - defender.Stam -= Utility.Random( 20, 10 ); - defender.Mana -= Utility.Random( 20, 10 ); - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + defender.Damage(Utility.Random(20, 10), this); + defender.Stam -= Utility.Random(20, 10); + defender.Mana -= Utility.Random(20, 10); + } - if ( 0.1 >= Utility.RandomDouble() ) - SpawnPixies( attacker ); - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public Twaulo(Serial serial) - : base(serial) - { - } + if (0.1 >= Utility.RandomDouble()) + SpawnPixies(attacker); + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); - writer.Write((int)0); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Changeling.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Changeling.cs index 1a94a720c..30a8c0cec 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Changeling.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Changeling.cs @@ -1,299 +1,315 @@ using System; -using Server.Spells; using Server.Items; +using Server.Spells; namespace Server.Mobiles { - public class Changeling : BaseCreature - { - public override string CorpseName => "a changeling corpse"; - public override string DefaultName => "a changeling"; - public virtual int DefaultHue => 0; + public class Changeling : BaseCreature + { + private static readonly int[] m_FireNorth = + { + -1, -1, + 1, -1, + -1, 2, + 1, 2 + }; - [Constructible] - public Changeling() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 264; - Hue = DefaultHue; + private static readonly int[] m_FireEast = + { + -1, 0, + 2, 0 + }; - SetStr( 36, 105 ); - SetDex( 212, 262 ); - SetInt( 317, 399 ); + private DateTime m_LastMorph; - SetHits( 201, 211 ); - SetStam( 212, 262 ); - SetMana( 317, 399 ); + private Mobile m_MorphedInto; + private DateTime m_NextFireRing; - SetDamage( 9, 15 ); + [Constructible] + public Changeling() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 264; + Hue = DefaultHue; - SetDamageType( ResistanceType.Physical, 100 ); + SetStr(36, 105); + SetDex(212, 262); + SetInt(317, 399); - SetResistance( ResistanceType.Physical, 81, 90 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 49 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 43, 50 ); + SetHits(201, 211); + SetStam(212, 262); + SetMana(317, 399); - SetSkill( SkillName.Wrestling, 10.4, 12.5 ); - SetSkill( SkillName.Tactics, 101.1, 108.3 ); - SetSkill( SkillName.MagicResist, 121.6, 132.2 ); - SetSkill( SkillName.Magery, 91.6, 99.5 ); - SetSkill( SkillName.EvalInt, 91.5, 98.8 ); - SetSkill( SkillName.Meditation, 91.7, 98.5 ); + SetDamage(9, 15); - Fame = 15000; - Karma = -15000; + SetDamageType(ResistanceType.Physical, 100); - PackScroll( 1, 7 ); - PackItem( new Arrow( 35 ) ); - PackItem( new Bolt( 25 ) ); - PackGem( 2 ); + SetResistance(ResistanceType.Physical, 81, 90); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 49); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 43, 50); - PackArcaneScroll( 0, 1 ); - } + SetSkill(SkillName.Wrestling, 10.4, 12.5); + SetSkill(SkillName.Tactics, 101.1, 108.3); + SetSkill(SkillName.MagicResist, 121.6, 132.2); + SetSkill(SkillName.Magery, 91.6, 99.5); + SetSkill(SkillName.EvalInt, 91.5, 98.8); + SetSkill(SkillName.Meditation, 91.7, 98.5); - public override bool ShowFameTitle => false; - public override bool InitialInnocent => m_MorphedInto != null; + Fame = 15000; + Karma = -15000; - public override void GenerateLoot() - { - AddLoot( LootPack.AosRich, 3 ); - } + PackScroll(1, 7); + PackItem(new Arrow(35)); + PackItem(new Bolt(25)); + PackGem(2); - public override int GetAngerSound() { return 0x46E; } - public override int GetIdleSound() { return 0x470; } - public override int GetAttackSound() { return 0x46D; } - public override int GetHurtSound() { return 0x471; } - public override int GetDeathSound() { return 0x46F; } + PackArcaneScroll(0, 1); + } - private Mobile m_MorphedInto; - private DateTime m_LastMorph; - private DateTime m_NextFireRing; + public Changeling(Serial serial) + : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile MorphedInto - { - get => m_MorphedInto; - set - { - if ( value == this ) - value = null; + public override string CorpseName => "a changeling corpse"; + public override string DefaultName => "a changeling"; + public virtual int DefaultHue => 0; - if ( m_MorphedInto != value ) - { - Revert(); + public override bool ShowFameTitle => false; + public override bool InitialInnocent => m_MorphedInto != null; - if ( value != null ) - { - Morph( value ); - m_LastMorph = DateTime.UtcNow; - } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile MorphedInto + { + get => m_MorphedInto; + set + { + if (value == this) + value = null; - m_MorphedInto = value; - Delta( MobileDelta.Noto ); - } - } - } + if (m_MorphedInto != value) + { + Revert(); - public override void OnThink() - { - base.OnThink(); + if (value != null) + { + Morph(value); + m_LastMorph = DateTime.UtcNow; + } - if ( Combatant != null ) - { - if ( m_NextFireRing <= DateTime.UtcNow && Utility.RandomDouble() < 0.02 ) - { - FireRing(); - m_NextFireRing = DateTime.UtcNow + TimeSpan.FromMinutes( 2 ); - } + m_MorphedInto = value; + Delta(MobileDelta.Noto); + } + } + } - if ( Combatant.Player && m_MorphedInto != Combatant && Utility.RandomDouble() < 0.05 ) - MorphedInto = Combatant; - } - } + public override void GenerateLoot() + { + AddLoot(LootPack.AosRich, 3); + } - public override bool CheckIdle() - { - bool idle = base.CheckIdle(); + public override int GetAngerSound() + { + return 0x46E; + } - if ( idle && m_MorphedInto != null && DateTime.UtcNow - m_LastMorph > TimeSpan.FromSeconds( 30 ) ) - MorphedInto = null; + public override int GetIdleSound() + { + return 0x470; + } - return idle; - } + public override int GetAttackSound() + { + return 0x46D; + } - private void FireEffects( int itemID, int[] offsets ) - { - for ( int i = 0; i < offsets.Length; i += 2 ) - { - Point3D p = Location; + public override int GetHurtSound() + { + return 0x471; + } - p.X += offsets[i]; - p.Y += offsets[i + 1]; + public override int GetDeathSound() + { + return 0x46F; + } - if ( SpellHelper.AdjustField( ref p, Map, 12, false ) ) - Effects.SendLocationEffect( p, Map, itemID, 50 ); - } - } + public override void OnThink() + { + base.OnThink(); - private static readonly int[] m_FireNorth = - { - -1, -1, - 1, -1, - -1, 2, - 1, 2 - }; + if (Combatant != null) + { + if (m_NextFireRing <= DateTime.UtcNow && Utility.RandomDouble() < 0.02) + { + FireRing(); + m_NextFireRing = DateTime.UtcNow + TimeSpan.FromMinutes(2); + } - private static readonly int[] m_FireEast = - { - -1, 0, - 2, 0 - }; + if (Combatant.Player && m_MorphedInto != Combatant && Utility.RandomDouble() < 0.05) + MorphedInto = Combatant; + } + } - protected virtual void FireRing() - { - FireEffects( 0x3E27, m_FireNorth ); - FireEffects( 0x3E31, m_FireEast ); - } + public override bool CheckIdle() + { + bool idle = base.CheckIdle(); - protected virtual void Morph( Mobile m ) - { - Body = m.Body; - Hue = m.Hue; - Female = m.Female; - Name = m.Name; - NameHue = m.NameHue; - Title = m.Title; - Kills = m.Kills; - HairItemID = m.HairItemID; - HairHue = m.HairHue; - FacialHairItemID = m.FacialHairItemID; - FacialHairHue = m.FacialHairHue; + if (idle && m_MorphedInto != null && DateTime.UtcNow - m_LastMorph > TimeSpan.FromSeconds(30)) + MorphedInto = null; - // TODO: Skills? + return idle; + } - foreach ( Item item in m.Items ) - { - if ( item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank ) - AddItem( new ClonedItem( item ) ); // TODO: Clone weapon/armor attributes - } + private void FireEffects(int itemID, int[] offsets) + { + for (int i = 0; i < offsets.Length; i += 2) + { + Point3D p = Location; - PlaySound( 0x511 ); - FixedParticles( 0x376A, 1, 14, 5045, EffectLayer.Waist ); - } + p.X += offsets[i]; + p.Y += offsets[i + 1]; - protected virtual void Revert() - { - Body = 264; - Hue = ( IsParagon && DefaultHue == 0 ) ? Paragon.Hue : DefaultHue; - Female = false; - Name = null; - NameHue = -1; - Title = null; - Kills = 0; - HairItemID = 0; - HairHue = 0; - FacialHairItemID = 0; - FacialHairHue = 0; + if (SpellHelper.AdjustField(ref p, Map, 12, false)) + Effects.SendLocationEffect(p, Map, itemID, 50); + } + } - DeleteClonedItems(); + protected virtual void FireRing() + { + FireEffects(0x3E27, m_FireNorth); + FireEffects(0x3E31, m_FireEast); + } - PlaySound( 0x511 ); - FixedParticles( 0x376A, 1, 14, 5045, EffectLayer.Waist ); - } + protected virtual void Morph(Mobile m) + { + Body = m.Body; + Hue = m.Hue; + Female = m.Female; + Name = m.Name; + NameHue = m.NameHue; + Title = m.Title; + Kills = m.Kills; + HairItemID = m.HairItemID; + HairHue = m.HairHue; + FacialHairItemID = m.FacialHairItemID; + FacialHairHue = m.FacialHairHue; - public void DeleteClonedItems() - { - for ( int i = Items.Count - 1; i >= 0; --i ) - { - Item item = Items[i]; + // TODO: Skills? - if ( item is ClonedItem ) - item.Delete(); - } + foreach (Item item in m.Items) + if (item.Layer != Layer.Backpack && item.Layer != Layer.Mount && item.Layer != Layer.Bank) + AddItem(new ClonedItem(item)); // TODO: Clone weapon/armor attributes - if ( Backpack != null ) - { - for ( int i = Backpack.Items.Count - 1; i >= 0; --i ) - { - Item item = Backpack.Items[i]; + PlaySound(0x511); + FixedParticles(0x376A, 1, 14, 5045, EffectLayer.Waist); + } - if ( item is ClonedItem ) - item.Delete(); - } - } - } + protected virtual void Revert() + { + Body = 264; + Hue = IsParagon && DefaultHue == 0 ? Paragon.Hue : DefaultHue; + Female = false; + Name = null; + NameHue = -1; + Title = null; + Kills = 0; + HairItemID = 0; + HairHue = 0; + FacialHairItemID = 0; + FacialHairHue = 0; - public override void OnAfterDelete() - { - DeleteClonedItems(); + DeleteClonedItems(); - base.OnAfterDelete(); - } + PlaySound(0x511); + FixedParticles(0x376A, 1, 14, 5045, EffectLayer.Waist); + } - public override void ClearHands() - { - } + public void DeleteClonedItems() + { + for (int i = Items.Count - 1; i >= 0; --i) + { + Item item = Items[i]; - public Changeling( Serial serial ) - : base( serial ) - { - } + if (item is ClonedItem) + item.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (Backpack != null) + for (int i = Backpack.Items.Count - 1; i >= 0; --i) + { + Item item = Backpack.Items[i]; - writer.Write( (int) 0 ); // version - writer.Write( ( m_MorphedInto != null ) ); - } + if (item is ClonedItem) + item.Delete(); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnAfterDelete() + { + DeleteClonedItems(); - int version = reader.ReadInt(); + base.OnAfterDelete(); + } - if ( reader.ReadBool() ) - ValidationQueue.Add( this ); - } + public override void ClearHands() + { + } - public void Validate() - { - Revert(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private class ClonedItem : Item - { - public ClonedItem( Item item ) - : base( item.ItemID ) - { - Name = item.Name; - Weight = item.Weight; - Hue = item.Hue; - Layer = item.Layer; - Movable = false; - } + writer.Write(0); // version + writer.Write(m_MorphedInto != null); + } - public ClonedItem( Serial serial ) - : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); - writer.Write( (int) 0 ); // version - } + if (reader.ReadBool()) + ValidationQueue.Add(this); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void Validate() + { + Revert(); + } - int version = reader.ReadInt(); - } - } - } -} + private class ClonedItem : Item + { + public ClonedItem(Item item) + : base(item.ItemID) + { + Name = item.Name; + Weight = item.Weight; + Hue = item.Hue; + Layer = item.Layer; + Movable = false; + } + + public ClonedItem(Serial serial) + : base(serial) + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Gnaw.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Gnaw.cs index 9cfa2b505..c636e7905 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Gnaw.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Gnaw.cs @@ -1,80 +1,80 @@ namespace Server.Mobiles { - public class Gnaw : DireWolf - { - public override string CorpseName => "a Gnaw corpse"; - public override string DefaultName => "Gnaw"; + public class Gnaw : DireWolf + { + [Constructible] + public Gnaw() + { + IsParagon = true; - [Constructible] - public Gnaw() - { - IsParagon = true; + Hue = 0x130; - Hue = 0x130; + SetStr(151, 172); + SetDex(124, 145); + SetInt(60, 86); - SetStr( 151, 172 ); - SetDex( 124, 145 ); - SetInt( 60, 86 ); + SetHits(817, 857); + SetStam(124, 145); + SetMana(52, 86); - SetHits( 817, 857 ); - SetStam( 124, 145 ); - SetMana( 52, 86 ); + SetDamage(16, 22); - SetDamage( 16, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 64, 69); + SetResistance(ResistanceType.Fire, 53, 56); + SetResistance(ResistanceType.Cold, 22, 27); + SetResistance(ResistanceType.Poison, 27, 30); + SetResistance(ResistanceType.Energy, 21, 34); - SetResistance( ResistanceType.Physical, 64, 69 ); - SetResistance( ResistanceType.Fire, 53, 56 ); - SetResistance( ResistanceType.Cold, 22, 27 ); - SetResistance( ResistanceType.Poison, 27, 30 ); - SetResistance( ResistanceType.Energy, 21, 34 ); + SetSkill(SkillName.Wrestling, 106.4, 116.5); + SetSkill(SkillName.Tactics, 84.1, 103.2); + SetSkill(SkillName.MagicResist, 96.8, 110.7); - SetSkill( SkillName.Wrestling, 106.4, 116.5 ); - SetSkill( SkillName.Tactics, 84.1, 103.2 ); - SetSkill( SkillName.MagicResist, 96.8, 110.7 ); + Fame = 17500; + Karma = -17500; + } - Fame = 17500; - Karma = -17500; - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - } + if ( Utility.RandomDouble() < 0.3 ) + c.DropItem( new GnawsFang() ); + } + */ - public override bool GivesMLMinorArtifact => true; - public override int Hides => 28; - public override int Meat => 4; + public Gnaw(Serial serial) + : base(serial) + { + } - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override string CorpseName => "a Gnaw corpse"; + public override string DefaultName => "Gnaw"; - if ( Utility.RandomDouble() < 0.3 ) - c.DropItem( new GnawsFang() ); - } - */ + public override bool GivesMLMinorArtifact => true; + public override int Hides => 28; + public override int Meat => 4; - public Gnaw( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Guile.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Guile.cs index 23b54a892..afcf3b726 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Guile.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Guile.cs @@ -1,86 +1,84 @@ namespace Server.Mobiles { - public class Guile : Changeling - { - public override string CorpseName => "a Guile corpse"; - public override string DefaultName => "Guile"; - public override int DefaultHue => 0x3F; + public class Guile : Changeling + { + [Constructible] + public Guile() + { + IsParagon = true; - [Constructible] - public Guile() - { - IsParagon = true; + Hue = DefaultHue; - Hue = DefaultHue; + SetStr(53, 214); + SetDex(243, 367); + SetInt(369, 586); - SetStr( 53, 214 ); - SetDex( 243, 367 ); - SetInt( 369, 586 ); + SetHits(1013, 1058); + SetStam(243, 367); + SetMana(369, 586); - SetHits( 1013, 1058 ); - SetStam( 243, 367 ); - SetMana( 369, 586 ); + SetDamage(14, 20); - SetDamage( 14, 20 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 43, 46); + SetResistance(ResistanceType.Cold, 42, 44); + SetResistance(ResistanceType.Poison, 42, 50); + SetResistance(ResistanceType.Energy, 47, 50); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 43, 46 ); - SetResistance( ResistanceType.Cold, 42, 44 ); - SetResistance( ResistanceType.Poison, 42, 50 ); - SetResistance( ResistanceType.Energy, 47, 50 ); + SetSkill(SkillName.Wrestling, 12.8, 16.7); + SetSkill(SkillName.Tactics, 102.6, 131.0); + SetSkill(SkillName.MagicResist, 141.2, 161.6); + SetSkill(SkillName.Magery, 108.4, 120.0); + SetSkill(SkillName.EvalInt, 108.4, 120.0); + SetSkill(SkillName.Meditation, 109.2, 120.0); - SetSkill( SkillName.Wrestling, 12.8, 16.7 ); - SetSkill( SkillName.Tactics, 102.6, 131.0 ); - SetSkill( SkillName.MagicResist, 141.2, 161.6 ); - SetSkill( SkillName.Magery, 108.4, 120.0 ); - SetSkill( SkillName.EvalInt, 108.4, 120.0 ); - SetSkill( SkillName.Meditation, 109.2, 120.0 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + public Guile(Serial serial) + : base(serial) + { + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override string CorpseName => "a Guile corpse"; + public override string DefaultName => "Guile"; + public override int DefaultHue => 0x3F; - if ( Utility.RandomBool() ) - { - if ( !Kappa.IsBeingDrained( defender ) && Mana > 14 ) - { - defender.SendLocalizedMessage( 1070848 ); // You feel your life force being stolen away. - Kappa.BeginLifeDrain( defender, this ); - Mana -= 15; - } - } - } + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + if (Utility.RandomBool()) + if (!Kappa.IsBeingDrained(defender) && Mana > 14) + { + defender.SendLocalizedMessage(1070848); // You feel your life force being stolen away. + Kappa.BeginLifeDrain(defender, this); + Mana -= 15; + } + } - public Guile( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Irk.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Irk.cs index d0992ce4d..b6e67a42c 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Irk.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Irk.cs @@ -1,85 +1,85 @@ namespace Server.Mobiles { - public class Irk : Changeling - { - public override string CorpseName => "an Irk corpse"; - public override string DefaultName => "Irk"; - public override int DefaultHue => 0x489; + public class Irk : Changeling + { + [Constructible] + public Irk() + { + IsParagon = true; - [Constructible] - public Irk() - { - IsParagon = true; + Hue = DefaultHue; - Hue = DefaultHue; + SetStr(23, 183); + SetDex(259, 360); + SetInt(374, 600); - SetStr( 23, 183 ); - SetDex( 259, 360 ); - SetInt( 374, 600 ); + SetHits(1006, 1064); + SetStam(259, 360); + SetMana(374, 600); - SetHits( 1006, 1064 ); - SetStam( 259, 360 ); - SetMana( 374, 600 ); + SetDamage(14, 20); - SetDamage( 14, 20 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 41, 50); + SetResistance(ResistanceType.Energy, 40, 49); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 41, 50 ); - SetResistance( ResistanceType.Energy, 40, 49 ); + SetSkill(SkillName.Wrestling, 120.3, 123.0); + SetSkill(SkillName.Tactics, 120.1, 131.8); + SetSkill(SkillName.MagicResist, 132.3, 165.8); + SetSkill(SkillName.Magery, 108.9, 119.7); + SetSkill(SkillName.EvalInt, 108.4, 120.0); + SetSkill(SkillName.Meditation, 108.9, 119.1); - SetSkill( SkillName.Wrestling, 120.3, 123.0 ); - SetSkill( SkillName.Tactics, 120.1, 131.8 ); - SetSkill( SkillName.MagicResist, 132.3, 165.8 ); - SetSkill( SkillName.Magery, 108.9, 119.7 ); - SetSkill( SkillName.EvalInt, 108.4, 120.0 ); - SetSkill( SkillName.Meditation, 108.9, 119.1 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - // TODO: Angry fire + if ( Utility.RandomDouble() < 0.25 ) + c.DropItem( new IrksBrain() ); - public override bool GivesMLMinorArtifact => true; + if ( Utility.RandomDouble() < 0.025 ) + c.DropItem( new PaladinGloves() ); + } + */ - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public Irk(Serial serial) + : base(serial) + { + } - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override string CorpseName => "an Irk corpse"; + public override string DefaultName => "Irk"; + public override int DefaultHue => 0x489; - if ( Utility.RandomDouble() < 0.25 ) - c.DropItem( new IrksBrain() ); + // TODO: Angry fire - if ( Utility.RandomDouble() < 0.025 ) - c.DropItem( new PaladinGloves() ); - } - */ + public override bool GivesMLMinorArtifact => true; - public Irk( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadyLissith.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadyLissith.cs index 0a019a028..70a958d81 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadyLissith.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadyLissith.cs @@ -2,88 +2,91 @@ using Server.Items; namespace Server.Mobiles { - public class LadyLissith : GiantBlackWidow - { - public override string CorpseName => "a Lady Lissith corpse"; - public override string DefaultName => "Lady Lissith"; + public class LadyLissith : GiantBlackWidow + { + [Constructible] + public LadyLissith() + { + IsParagon = true; + Hue = 0x452; - [Constructible] - public LadyLissith() - { - IsParagon = true; - Hue = 0x452; + SetStr(81, 130); + SetDex(116, 152); + SetInt(44, 100); - SetStr( 81, 130 ); - SetDex( 116, 152 ); - SetInt( 44, 100 ); + SetHits(245, 375); + SetStam(116, 152); + SetMana(44, 100); - SetHits( 245, 375 ); - SetStam( 116, 152 ); - SetMana( 44, 100 ); + SetDamage(15, 22); - SetDamage( 15, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 31, 39); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 71, 80); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 31, 39 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 71, 80 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Wrestling, 108.6, 123.0); + SetSkill(SkillName.Tactics, 102.7, 119.0); + SetSkill(SkillName.MagicResist, 78.8, 95.6); + SetSkill(SkillName.Anatomy, 68.6, 106.8); + SetSkill(SkillName.Poisoning, 96.6, 112.9); - SetSkill( SkillName.Wrestling, 108.6, 123.0 ); - SetSkill( SkillName.Tactics, 102.7, 119.0 ); - SetSkill( SkillName.MagicResist, 78.8, 95.6 ); - SetSkill( SkillName.Anatomy, 68.6, 106.8 ); - SetSkill( SkillName.Poisoning, 96.6, 112.9 ); + Fame = 18900; + Karma = -18900; + } - Fame = 18900; - Karma = -18900; - } + public LadyLissith(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Lady Lissith corpse"; + public override string DefaultName => "Lady Lissith"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.025 ) + c.DropItem( new GreymistChest() ); - if ( Utility.RandomDouble() < 0.025 ) - c.DropItem( new GreymistChest() ); + if ( Utility.RandomDouble() < 0.45 ) + c.DropItem( new LissithsSilk() ); - if ( Utility.RandomDouble() < 0.45 ) - c.DropItem( new LissithsSilk() ); + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public LadyLissith( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadySabrix.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadySabrix.cs index 7ba834092..b91f63fc6 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadySabrix.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/LadySabrix.cs @@ -2,94 +2,97 @@ using Server.Items; namespace Server.Mobiles { - public class LadySabrix : GiantBlackWidow - { - public override string CorpseName => "a Lady Sabrix corpse"; - public override string DefaultName => "Lady Sabrix"; + public class LadySabrix : GiantBlackWidow + { + [Constructible] + public LadySabrix() + { + IsParagon = true; + Hue = 0x497; - [Constructible] - public LadySabrix() - { - IsParagon = true; - Hue = 0x497; + SetStr(82, 130); + SetDex(117, 146); + SetInt(50, 98); - SetStr( 82, 130 ); - SetDex( 117, 146 ); - SetInt( 50, 98 ); + SetHits(233, 361); + SetStam(117, 146); + SetMana(50, 98); - SetHits( 233, 361 ); - SetStam( 117, 146 ); - SetMana( 50, 98 ); + SetDamage(15, 22); - SetDamage( 15, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 39); + SetResistance(ResistanceType.Poison, 70, 80); + SetResistance(ResistanceType.Energy, 35, 44); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 39 ); - SetResistance( ResistanceType.Poison, 70, 80 ); - SetResistance( ResistanceType.Energy, 35, 44 ); + SetSkill(SkillName.Wrestling, 109.8, 122.8); + SetSkill(SkillName.Tactics, 102.8, 120.0); + SetSkill(SkillName.MagicResist, 79.4, 95.1); + SetSkill(SkillName.Anatomy, 68.8, 105.1); + SetSkill(SkillName.Poisoning, 97.8, 116.7); - SetSkill( SkillName.Wrestling, 109.8, 122.8 ); - SetSkill( SkillName.Tactics, 102.8, 120.0 ); - SetSkill( SkillName.MagicResist, 79.4, 95.1 ); - SetSkill( SkillName.Anatomy, 68.8, 105.1 ); - SetSkill( SkillName.Poisoning, 97.8, 116.7 ); + Fame = 18900; + Karma = -18900; + } - Fame = 18900; - Karma = -18900; - } + public LadySabrix(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Lady Sabrix corpse"; + public override string DefaultName => "Lady Sabrix"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ArmorIgnore; + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.2 ) + c.DropItem( new SabrixsEye() ); - if ( Utility.RandomDouble() < 0.2 ) - c.DropItem( new SabrixsEye() ); + if ( Utility.RandomDouble() < 0.25 ) + { + switch ( Utility.Random( 2 ) ) + { + case 0: AddToBackpack( new PaladinArms() ); break; + case 1: AddToBackpack( new HunterLegs() ); break; + } + } - if ( Utility.RandomDouble() < 0.25 ) - { - switch ( Utility.Random( 2 ) ) - { - case 0: AddToBackpack( new PaladinArms() ); break; - case 1: AddToBackpack( new HunterLegs() ); break; - } - } + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public LadySabrix( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ArmorIgnore; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Malefic.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Malefic.cs index e9ec041ba..a295b46a1 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Malefic.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Malefic.cs @@ -2,79 +2,82 @@ using Server.Items; namespace Server.Mobiles { - public class Malefic : DreadSpider - { - public override string CorpseName => "a Malefic corpse"; - public override string DefaultName => "Malefic"; + public class Malefic : DreadSpider + { + [Constructible] + public Malefic() + { + IsParagon = true; + Hue = 0x455; - [Constructible] - public Malefic() - { - IsParagon = true; - Hue = 0x455; + SetStr(210, 284); + SetDex(153, 197); + SetInt(349, 390); - SetStr( 210, 284 ); - SetDex( 153, 197 ); - SetInt( 349, 390 ); + SetHits(600, 747); + SetStam(153, 197); + SetMana(349, 390); - SetHits( 600, 747 ); - SetStam( 153, 197 ); - SetMana( 349, 390 ); + SetDamage(15, 22); - SetDamage( 15, 22 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Poison, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Poison, 80 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 49); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 41, 48); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 49 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 41, 48 ); + SetSkill(SkillName.Wrestling, 96.9, 112.4); + SetSkill(SkillName.Tactics, 91.3, 105.4); + SetSkill(SkillName.MagicResist, 79.8, 95.1); + SetSkill(SkillName.Magery, 103.0, 118.6); + SetSkill(SkillName.EvalInt, 105.7, 119.6); + SetSkill(SkillName.Meditation, 0); - SetSkill( SkillName.Wrestling, 96.9, 112.4 ); - SetSkill( SkillName.Tactics, 91.3, 105.4 ); - SetSkill( SkillName.MagicResist, 79.8, 95.1 ); - SetSkill( SkillName.Magery, 103.0, 118.6 ); - SetSkill( SkillName.EvalInt, 105.7, 119.6 ); - SetSkill( SkillName.Meditation, 0 ); + Fame = 21000; + Karma = -21000; - Fame = 21000; - Karma = -21000; + /* + // TODO: uncomment once added + if ( Utility.RandomDouble() < 0.1 ) + PackItem( new ParrotItem() ); + */ + } - /* - // TODO: uncomment once added - if ( Utility.RandomDouble() < 0.1 ) - PackItem( new ParrotItem() ); - */ - } + public Malefic(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Malefic corpse"; + public override string DefaultName => "Malefic"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.Dismount; + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public Malefic( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.Dismount; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Silk.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Silk.cs index 4c6b3383f..0f809fb6e 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Silk.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Silk.cs @@ -2,71 +2,74 @@ using Server.Items; namespace Server.Mobiles { - public class Silk : GiantBlackWidow - { - public override string CorpseName => "a Silk corpse"; - public override string DefaultName => "Silk"; + public class Silk : GiantBlackWidow + { + [Constructible] + public Silk() + { + IsParagon = true; + Hue = 0x47E; - [Constructible] - public Silk() - { - IsParagon = true; - Hue = 0x47E; + SetStr(80, 131); + SetDex(126, 156); + SetInt(63, 102); - SetStr( 80, 131 ); - SetDex( 126, 156 ); - SetInt( 63, 102 ); + SetHits(279, 378); + SetStam(126, 156); + SetMana(63, 102); - SetHits( 279, 378 ); - SetStam( 126, 156 ); - SetMana( 63, 102 ); + SetDamage(15, 22); - SetDamage( 15, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 39); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 70, 76); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 39 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 70, 76 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Wrestling, 114.1, 123.7); + SetSkill(SkillName.Tactics, 102.6, 118.3); + SetSkill(SkillName.MagicResist, 78.6, 94.8); + SetSkill(SkillName.Anatomy, 81.3, 105.7); + SetSkill(SkillName.Poisoning, 106.0, 119.2); - SetSkill( SkillName.Wrestling, 114.1, 123.7 ); - SetSkill( SkillName.Tactics, 102.6, 118.3 ); - SetSkill( SkillName.MagicResist, 78.6, 94.8 ); - SetSkill( SkillName.Anatomy, 81.3, 105.7 ); - SetSkill( SkillName.Poisoning, 106.0, 119.2 ); + Fame = 18900; + Karma = -18900; + } - Fame = 18900; - Karma = -18900; - } + public Silk(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Silk corpse"; + public override string DefaultName => "Silk"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.ParalyzingBlow; + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public Silk( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.ParalyzingBlow; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Spite.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Spite.cs index 951a2fcce..196e4d286 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Spite.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Spite.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class Spite : Changeling - { - public override string CorpseName => "a Spite corpse"; - public override string DefaultName => "Spite"; - public override int DefaultHue => 0x21; + public class Spite : Changeling + { + [Constructible] + public Spite() + { + IsParagon = true; - [Constructible] - public Spite() - { - IsParagon = true; + Hue = DefaultHue; - Hue = DefaultHue; + SetStr(53, 214); + SetDex(243, 367); + SetInt(369, 586); - SetStr( 53, 214 ); - SetDex( 243, 367 ); - SetInt( 369, 586 ); + SetHits(1013, 1052); + SetStam(243, 367); + SetMana(369, 586); - SetHits( 1013, 1052 ); - SetStam( 243, 367 ); - SetMana( 369, 586 ); + SetDamage(14, 20); - SetDamage( 14, 20 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 85, 90); + SetResistance(ResistanceType.Fire, 41, 46); + SetResistance(ResistanceType.Cold, 40, 44); + SetResistance(ResistanceType.Poison, 42, 46); + SetResistance(ResistanceType.Energy, 45, 47); - SetResistance( ResistanceType.Physical, 85, 90 ); - SetResistance( ResistanceType.Fire, 41, 46 ); - SetResistance( ResistanceType.Cold, 40, 44 ); - SetResistance( ResistanceType.Poison, 42, 46 ); - SetResistance( ResistanceType.Energy, 45, 47 ); + SetSkill(SkillName.Wrestling, 12.8, 16.7); + SetSkill(SkillName.Tactics, 102.6, 131.0); + SetSkill(SkillName.MagicResist, 141.2, 161.6); + SetSkill(SkillName.Magery, 108.4, 119.2); + SetSkill(SkillName.EvalInt, 108.4, 120.0); + SetSkill(SkillName.Meditation, 109.2, 120.0); - SetSkill( SkillName.Wrestling, 12.8, 16.7 ); - SetSkill( SkillName.Tactics, 102.6, 131.0 ); - SetSkill( SkillName.MagicResist, 141.2, 161.6 ); - SetSkill( SkillName.Magery, 108.4, 119.2 ); - SetSkill( SkillName.EvalInt, 108.4, 120.0 ); - SetSkill( SkillName.Meditation, 109.2, 120.0 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + public Spite(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string CorpseName => "a Spite corpse"; + public override string DefaultName => "Spite"; + public override int DefaultHue => 0x21; - public override bool GivesMLMinorArtifact => true; + public override bool GivesMLMinorArtifact => true; - public Spite( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Swoop.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Swoop.cs index 58830de99..62c1653f5 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Swoop.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Swoop.cs @@ -3,167 +3,170 @@ using System.Collections; namespace Server.Mobiles { - public class Swoop : Eagle - { - public override string CorpseName => "a Swoop corpse"; - public override string DefaultName => "Swoop"; + public class Swoop : Eagle + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public Swoop() - { - IsParagon = true; - Hue = 0xE0; + [Constructible] + public Swoop() + { + IsParagon = true; + Hue = 0xE0; - AI = AIType.AI_Melee; + AI = AIType.AI_Melee; - SetStr( 100, 150 ); - SetDex( 400, 500 ); - SetInt( 80, 90 ); + SetStr(100, 150); + SetDex(400, 500); + SetInt(80, 90); - SetHits( 1500, 2000 ); + SetHits(1500, 2000); - SetDamage( 20, 30 ); + SetDamage(20, 30); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 75, 90 ); - SetResistance( ResistanceType.Fire, 60, 77 ); - SetResistance( ResistanceType.Cold, 70, 85 ); - SetResistance( ResistanceType.Poison, 55, 85 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetResistance(ResistanceType.Physical, 75, 90); + SetResistance(ResistanceType.Fire, 60, 77); + SetResistance(ResistanceType.Cold, 70, 85); + SetResistance(ResistanceType.Poison, 55, 85); + SetResistance(ResistanceType.Energy, 50, 60); - SetSkill( SkillName.Wrestling, 120.0, 140.0 ); - SetSkill( SkillName.Tactics, 120.0, 140.0 ); - SetSkill( SkillName.MagicResist, 95.0, 105.0 ); + SetSkill(SkillName.Wrestling, 120.0, 140.0); + SetSkill(SkillName.Tactics, 120.0, 140.0); + SetSkill(SkillName.MagicResist, 95.0, 105.0); - Fame = 18000; - Karma = 0; + Fame = 18000; + Karma = 0; - PackReg( 4 ); - PackArcaneScroll( 0, 1 ); - } + PackReg(4); + PackArcaneScroll(0, 1); + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - // TODO: Put this attack shared with Hiryu and Lesser Hiryu in one place - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + if ( Utility.RandomDouble() < 0.025 ) + { + switch ( Utility.Random( 18 ) ) + { + case 0: c.DropItem( new AssassinChest() ); break; + case 1: c.DropItem( new AssassinArms() ); break; + case 2: c.DropItem( new DeathChest() ); break; + case 3: c.DropItem( new MyrmidonArms() ); break; + case 4: c.DropItem( new MyrmidonLegs() ); break; + case 5: c.DropItem( new MyrmidonGorget() ); break; + case 6: c.DropItem( new LeafweaveGloves() ); break; + case 7: c.DropItem( new LeafweaveLegs() ); break; + case 8: c.DropItem( new LeafweavePauldrons() ); break; + case 9: c.DropItem( new PaladinGloves() ); break; + case 10: c.DropItem( new PaladinGorget() ); break; + case 11: c.DropItem( new PaladinArms() ); break; + case 12: c.DropItem( new HunterArms() ); break; + case 13: c.DropItem( new HunterGloves() ); break; + case 14: c.DropItem( new HunterLegs() ); break; + case 15: c.DropItem( new HunterChest() ); break; + case 16: c.DropItem( new GreymistArms() ); break; + case 17: c.DropItem( new GreymistGloves() ); break; + } + } - if ( 0.1 > Utility.RandomDouble() ) - { - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070837 ); // The creature lands another blow in your weakened state. - } - else - defender.SendLocalizedMessage( 1070836 ); // The blow from the creature's claws has made you more susceptible to physical attacks. + public Swoop(Serial serial) + : base(serial) + { + } - int effect = -(defender.PhysicalResistance * 15 / 100); + public override string CorpseName => "a Swoop corpse"; + public override string DefaultName => "Swoop"; - ResistanceMod mod = new ResistanceMod( ResistanceType.Physical, effect ); + public override bool CanFly => true; + public override bool GivesMLMinorArtifact => true; + public override int Feathers => 72; - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.AddResistanceMod( mod ); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - timer = new ExpireTimer( defender, mod, TimeSpan.FromSeconds( 5.0 ) ); - timer.Start(); - m_Table[defender] = timer; - } - } + // TODO: Put this attack shared with Hiryu and Lesser Hiryu in one place + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - private static Hashtable m_Table = new Hashtable(); + if (0.1 > Utility.RandomDouble()) + { + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod m_Mod; + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070837); // The creature lands another blow in your weakened state. + } + else + { + defender.SendLocalizedMessage( + 1070836); // The blow from the creature's claws has made you more susceptible to physical attacks. + } - public ExpireTimer( Mobile m, ResistanceMod mod, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - m_Mod = mod; - Priority = TimerPriority.TwoFiftyMS; - } + int effect = -(defender.PhysicalResistance * 15 / 100); - public void DoExpire() - { - m_Mobile.RemoveResistanceMod( m_Mod ); - Stop(); - m_Table.Remove( m_Mobile ); - } + ResistanceMod mod = new ResistanceMod(ResistanceType.Physical, effect); - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1070838 ); // Your resistance to physical attacks has returned. - DoExpire(); - } - } + defender.FixedEffect(0x37B9, 10, 5); + defender.AddResistanceMod(mod); - public override bool CanFly => true; - public override bool GivesMLMinorArtifact => true; - public override int Feathers => 72; + timer = new ExpireTimer(defender, mod, TimeSpan.FromSeconds(5.0)); + timer.Start(); + m_Table[defender] = timer; + } + } - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( Utility.RandomDouble() < 0.025 ) - { - switch ( Utility.Random( 18 ) ) - { - case 0: c.DropItem( new AssassinChest() ); break; - case 1: c.DropItem( new AssassinArms() ); break; - case 2: c.DropItem( new DeathChest() ); break; - case 3: c.DropItem( new MyrmidonArms() ); break; - case 4: c.DropItem( new MyrmidonLegs() ); break; - case 5: c.DropItem( new MyrmidonGorget() ); break; - case 6: c.DropItem( new LeafweaveGloves() ); break; - case 7: c.DropItem( new LeafweaveLegs() ); break; - case 8: c.DropItem( new LeafweavePauldrons() ); break; - case 9: c.DropItem( new PaladinGloves() ); break; - case 10: c.DropItem( new PaladinGorget() ); break; - case 11: c.DropItem( new PaladinArms() ); break; - case 12: c.DropItem( new HunterArms() ); break; - case 13: c.DropItem( new HunterGloves() ); break; - case 14: c.DropItem( new HunterLegs() ); break; - case 15: c.DropItem( new HunterChest() ); break; - case 16: c.DropItem( new GreymistArms() ); break; - case 17: c.DropItem( new GreymistGloves() ); break; - } - } + writer.Write(0); // version + } - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public Swoop( Serial serial ) - : base( serial ) - { - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod m_Mod; - writer.Write( (int) 0 ); // version - } + public ExpireTimer(Mobile m, ResistanceMod mod, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + m_Mod = mod; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void DoExpire() + { + m_Mobile.RemoveResistanceMod(m_Mod); + Stop(); + m_Table.Remove(m_Mobile); + } - int version = reader.ReadInt(); - } - } -} + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1070838); // Your resistance to physical attacks has returned. + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Virulent.cs b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Virulent.cs index b1712fca4..e483a68cc 100644 --- a/Scripts/Mobiles/Monsters/ML/Twisted Weald/Virulent.cs +++ b/Scripts/Mobiles/Monsters/ML/Twisted Weald/Virulent.cs @@ -2,93 +2,96 @@ using Server.Items; namespace Server.Mobiles { - public class Virulent : DreadSpider - { - public override string CorpseName => "a Virulent corpse"; - public override string DefaultName => "Virulent"; + public class Virulent : DreadSpider + { + [Constructible] + public Virulent() + { + IsParagon = true; + Hue = 0x8FD; - [Constructible] - public Virulent() - { - IsParagon = true; - Hue = 0x8FD; + SetStr(207, 252); + SetDex(156, 194); + SetInt(346, 398); - SetStr( 207, 252 ); - SetDex( 156, 194 ); - SetInt( 346, 398 ); + SetHits(616, 740); + SetStam(156, 194); + SetMana(346, 398); - SetHits( 616, 740 ); - SetStam( 156, 194 ); - SetMana( 346, 398 ); + SetDamage(15, 22); - SetDamage( 15, 22 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Poison, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Poison, 80 ); + SetResistance(ResistanceType.Physical, 60, 68); + SetResistance(ResistanceType.Fire, 40, 49); + SetResistance(ResistanceType.Cold, 41, 50); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 40, 49); - SetResistance( ResistanceType.Physical, 60, 68 ); - SetResistance( ResistanceType.Fire, 40, 49 ); - SetResistance( ResistanceType.Cold, 41, 50 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 40, 49 ); + SetSkill(SkillName.Wrestling, 92.8, 111.7); + SetSkill(SkillName.Tactics, 91.6, 107.4); + SetSkill(SkillName.MagicResist, 78.1, 93.3); + SetSkill(SkillName.Poisoning, 120.0); + SetSkill(SkillName.Magery, 104.2, 119.8); + SetSkill(SkillName.EvalInt, 102.8, 117.8); - SetSkill( SkillName.Wrestling, 92.8, 111.7 ); - SetSkill( SkillName.Tactics, 91.6, 107.4 ); - SetSkill( SkillName.MagicResist, 78.1, 93.3 ); - SetSkill( SkillName.Poisoning, 120.0 ); - SetSkill( SkillName.Magery, 104.2, 119.8 ); - SetSkill( SkillName.EvalInt, 102.8, 117.8 ); + Fame = 21000; + Karma = -21000; + } - Fame = 21000; - Karma = -21000; - } + public Virulent(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override string CorpseName => "a Virulent corpse"; + public override string DefaultName => "Virulent"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.MortalStrike; + /* + // TODO: uncomment once added + public override void OnDeath( Container c ) + { + base.OnDeath( c ); - /* - // TODO: uncomment once added - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + if ( Utility.RandomDouble() < 0.025 ) + { + switch ( Utility.Random( 2 ) ) + { + case 0: c.DropItem( new HunterLegs() ); break; + case 1: c.DropItem( new MalekisHonor() ); break; + } + } - if ( Utility.RandomDouble() < 0.025 ) - { - switch ( Utility.Random( 2 ) ) - { - case 0: c.DropItem( new HunterLegs() ); break; - case 1: c.DropItem( new MalekisHonor() ); break; - } - } + if ( Utility.RandomDouble() < 0.1 ) + c.DropItem( new ParrotItem() ); + } + */ - if ( Utility.RandomDouble() < 0.1 ) - c.DropItem( new ParrotItem() ); - } - */ + public override bool GivesMLMinorArtifact => true; - public override bool GivesMLMinorArtifact => true; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - public Virulent( Serial serial ) - : base( serial ) - { - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.MortalStrike; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Mammal/Melee/HellHound.cs b/Scripts/Mobiles/Monsters/Mammal/Melee/HellHound.cs index 0c2e261c7..3ab0b7013 100644 --- a/Scripts/Mobiles/Monsters/Mammal/Melee/HellHound.cs +++ b/Scripts/Mobiles/Monsters/Mammal/Melee/HellHound.cs @@ -2,70 +2,70 @@ using Server.Items; namespace Server.Mobiles { - public class HellHound : BaseCreature - { - public override string CorpseName => "a hell hound corpse"; - public override string DefaultName => "a hell hound"; + public class HellHound : BaseCreature + { + [Constructible] + public HellHound() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 98; + BaseSoundID = 229; - [Constructible] - public HellHound() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 98; - BaseSoundID = 229; + SetStr(102, 150); + SetDex(81, 105); + SetInt(36, 60); - SetStr( 102, 150 ); - SetDex( 81, 105 ); - SetInt( 36, 60 ); + SetHits(66, 125); - SetHits( 66, 125 ); + SetDamage(11, 17); - SetDamage( 11, 17 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Fire, 80); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Fire, 80 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + Fame = 3400; + Karma = -3400; - Fame = 3400; - Karma = -3400; + VirtualArmor = 30; - VirtualArmor = 30; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 85.5; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 85.5; + PackItem(new SulfurousAsh(5)); + } - PackItem( new SulfurousAsh( 5 ) ); - } + public HellHound(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a hell hound corpse"; + public override string DefaultName => "a hell hound"; - public override bool HasBreath => true; // fire breath enabled - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Canine; + public override bool HasBreath => true; // fire breath enabled + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Canine; - public HellHound( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Mammal/Melee/VorpalBunny.cs b/Scripts/Mobiles/Monsters/Mammal/Melee/VorpalBunny.cs index 4f2d42d3f..019c302b5 100644 --- a/Scripts/Mobiles/Monsters/Mammal/Melee/VorpalBunny.cs +++ b/Scripts/Mobiles/Monsters/Mammal/Melee/VorpalBunny.cs @@ -3,144 +3,144 @@ using Server.Items; namespace Server.Mobiles { - public class VorpalBunny : BaseCreature - { - public override string CorpseName => "a vorpal bunny corpse"; - public override string DefaultName => "a vorpal bunny"; + public class VorpalBunny : BaseCreature + { + [Constructible] + public VorpalBunny() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 205; + Hue = 0x480; - [Constructible] - public VorpalBunny() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 205; - Hue = 0x480; + SetStr(15); + SetDex(2000); + SetInt(1000); - SetStr( 15 ); - SetDex( 2000 ); - SetInt( 1000 ); + SetHits(2000); + SetStam(500); + SetMana(0); - SetHits( 2000 ); - SetStam( 500 ); - SetMana( 0 ); + SetDamage(1); - SetDamage( 1 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 200.0); + SetSkill(SkillName.Tactics, 5.0); + SetSkill(SkillName.Wrestling, 5.0); - SetSkill( SkillName.MagicResist, 200.0 ); - SetSkill( SkillName.Tactics, 5.0 ); - SetSkill( SkillName.Wrestling, 5.0 ); + Fame = 1000; + Karma = 0; - Fame = 1000; - Karma = 0; + VirtualArmor = 4; - VirtualArmor = 4; + int carrots = Utility.RandomMinMax(5, 10); + PackItem(new Carrot(carrots)); - int carrots = Utility.RandomMinMax( 5, 10 ); - PackItem( new Carrot( carrots ) ); + if (Utility.Random(5) == 0) + PackItem(new BrightlyColoredEggs()); - if ( Utility.Random( 5 ) == 0 ) - PackItem( new BrightlyColoredEggs() ); + PackStatue(); - PackStatue(); + DelayBeginTunnel(); + } - DelayBeginTunnel(); - } + public VorpalBunny(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich, 2 ); - } + public override string CorpseName => "a vorpal bunny corpse"; + public override string DefaultName => "a vorpal bunny"; - public class BunnyHole : Item - { - public override string DefaultName => "a mysterious rabbit hole"; + public override int Meat => 1; + public override int Hides => 1; + public override bool BardImmune => !Core.AOS; - public BunnyHole() : base( 0x913 ) - { - Movable = false; - Hue = 1; + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich, 2); + } - Timer.DelayCall( TimeSpan.FromSeconds( 40.0 ), Delete ); - } + public virtual void DelayBeginTunnel() + { + Timer.DelayCall(TimeSpan.FromMinutes(3.0), BeginTunnel); + } - public BunnyHole( Serial serial ) : base( serial ) - { - } + public virtual void BeginTunnel() + { + if (Deleted) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize(writer); + new BunnyHole().MoveToWorld(Location, Map); - writer.Write( (int) 0 ); - } + Frozen = true; + Say("* The bunny begins to dig a tunnel back to its underground lair *"); + PlaySound(0x247); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + Timer.DelayCall(TimeSpan.FromSeconds(5.0), Delete); + } - int version = reader.ReadInt(); + public override int GetAttackSound() + { + return 0xC9; + } - Delete(); - } - } + public override int GetHurtSound() + { + return 0xCA; + } - public virtual void DelayBeginTunnel() - { - Timer.DelayCall( TimeSpan.FromMinutes( 3.0 ), BeginTunnel ); - } + public override int GetDeathSound() + { + return 0xCB; + } - public virtual void BeginTunnel() - { - if ( Deleted ) - return; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - new BunnyHole().MoveToWorld( Location, Map ); + writer.Write(0); + } - Frozen = true; - Say( "* The bunny begins to dig a tunnel back to its underground lair *" ); - PlaySound( 0x247 ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), Delete ); - } + int version = reader.ReadInt(); - public override int Meat => 1; - public override int Hides => 1; - public override bool BardImmune => !Core.AOS; + DelayBeginTunnel(); + } - public VorpalBunny( Serial serial ) : base( serial ) - { - } + public class BunnyHole : Item + { + public BunnyHole() : base(0x913) + { + Movable = false; + Hue = 1; - public override int GetAttackSound() - { - return 0xC9; - } + Timer.DelayCall(TimeSpan.FromSeconds(40.0), Delete); + } - public override int GetHurtSound() - { - return 0xCA; - } + public BunnyHole(Serial serial) : base(serial) + { + } - public override int GetDeathSound() - { - return 0xCB; - } + public override string DefaultName => "a mysterious rabbit hole"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - DelayBeginTunnel(); - } - } -} + Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Magic/DarkWisp.cs b/Scripts/Mobiles/Monsters/Misc/Magic/DarkWisp.cs index 3009cc719..3e37aef2a 100644 --- a/Scripts/Mobiles/Monsters/Misc/Magic/DarkWisp.cs +++ b/Scripts/Mobiles/Monsters/Misc/Magic/DarkWisp.cs @@ -1,80 +1,81 @@ using System; -using Server.Misc; +using Server.Ethics; using Server.Items; +using Server.Misc; namespace Server.Mobiles { - public class DarkWisp : BaseCreature - { - public override string CorpseName => "a wisp corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Wisp; + public class DarkWisp : BaseCreature + { + [Constructible] + public DarkWisp() : base(AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 165; + BaseSoundID = 466; - public override Ethics.Ethic EthicAllegiance => Ethics.Ethic.Evil; + SetStr(196, 225); + SetDex(196, 225); + SetInt(196, 225); - public override TimeSpan ReacquireDelay => TimeSpan.FromSeconds( 1.0 ); + SetHits(118, 135); - public override string DefaultName => "a wisp"; + SetDamage(17, 18); - [Constructible] - public DarkWisp() : base( AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 165; - BaseSoundID = 466; + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); - SetStr( 196, 225 ); - SetDex( 196, 225 ); - SetInt( 196, 225 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 20, 40); + SetResistance(ResistanceType.Cold, 10, 30); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 50, 70); - SetHits( 118, 135 ); + SetSkill(SkillName.EvalInt, 80.0); + SetSkill(SkillName.Magery, 80.0); + SetSkill(SkillName.MagicResist, 80.0); + SetSkill(SkillName.Tactics, 80.0); + SetSkill(SkillName.Wrestling, 80.0); - SetDamage( 17, 18 ); + Fame = 4000; + Karma = -4000; - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + VirtualArmor = 40; - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 20, 40 ); - SetResistance( ResistanceType.Cold, 10, 30 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 50, 70 ); + AddItem(new LightSource()); + } - SetSkill( SkillName.EvalInt, 80.0 ); - SetSkill( SkillName.Magery, 80.0 ); - SetSkill( SkillName.MagicResist, 80.0 ); - SetSkill( SkillName.Tactics, 80.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + public DarkWisp(Serial serial) + : base(serial) + { + } - Fame = 4000; - Karma = -4000; + public override string CorpseName => "a wisp corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Wisp; - VirtualArmor = 40; + public override Ethic EthicAllegiance => Ethic.Evil; - AddItem( new LightSource() ); - } + public override TimeSpan ReacquireDelay => TimeSpan.FromSeconds(1.0); - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - } + public override string DefaultName => "a wisp"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public DarkWisp( Serial serial ) - : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Magic/EtherealWarrior.cs b/Scripts/Mobiles/Monsters/Misc/Magic/EtherealWarrior.cs index 025352cd0..536ac9385 100644 --- a/Scripts/Mobiles/Monsters/Misc/Magic/EtherealWarrior.cs +++ b/Scripts/Mobiles/Monsters/Misc/Magic/EtherealWarrior.cs @@ -3,141 +3,139 @@ using Server.Gumps; namespace Server.Mobiles { - public class EtherealWarrior : BaseCreature - { - public override string CorpseName => "an ethereal warrior corpse"; - public override bool InitialInnocent => true; + public class EtherealWarrior : BaseCreature + { + private static TimeSpan ResurrectDelay = TimeSpan.FromSeconds(2.0); - [Constructible] - public EtherealWarrior() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "ethereal warrior" ); - Body = 123; + private DateTime m_NextResurrect; - SetStr( 586, 785 ); - SetDex( 177, 255 ); - SetInt( 351, 450 ); + [Constructible] + public EtherealWarrior() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("ethereal warrior"); + Body = 123; - SetHits( 352, 471 ); + SetStr(586, 785); + SetDex(177, 255); + SetInt(351, 450); - SetDamage( 13, 19 ); + SetHits(352, 471); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamage(13, 19); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetDamageType(ResistanceType.Physical, 100); - SetSkill( SkillName.Anatomy, 50.1, 75.0 ); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 99.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - Fame = 7000; - Karma = 7000; + SetSkill(SkillName.Anatomy, 50.1, 75.0); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 99.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - VirtualArmor = 120; - } + Fame = 7000; + Karma = 7000; - public override int TreasureMapLevel => Core.AOS ? 5 : 0; + VirtualArmor = 120; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 3 ); - AddLoot( LootPack.Gems ); - } + public EtherealWarrior(Serial serial) : base(serial) + { + } - private DateTime m_NextResurrect; - private static TimeSpan ResurrectDelay = TimeSpan.FromSeconds(2.0); + public override string CorpseName => "an ethereal warrior corpse"; + public override bool InitialInnocent => true; - public override void OnMovement(Mobile from, Point3D oldLocation) - { - if (!from.Alive && (from is PlayerMobile)) - { - if (!from.Frozen && (DateTime.UtcNow >= m_NextResurrect) && InRange(from, 4) && !InRange(oldLocation, 4) && InLOS(from)) - { - m_NextResurrect = DateTime.UtcNow + ResurrectDelay; - if (!from.Criminal && (from.Kills < 5) && (from.Karma > 0)) - { - if (from.Map != null && from.Map.CanFit(from.Location, 16, false, false)) - { - Direction = GetDirectionTo(from); - from.PlaySound(0x1F2); - from.FixedEffect(0x376A, 10, 16); - from.CloseGump(typeof(ResurrectGump)); - from.SendGump(new ResurrectGump(from, ResurrectMessage.Healer)); - } - } - } - } - } + public override int TreasureMapLevel => Core.AOS ? 5 : 0; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override int Feathers => 100; + public override int Feathers => 100; - public override int GetAngerSound() - { - return 0x2F8; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 3); + AddLoot(LootPack.Gems); + } - public override int GetIdleSound() - { - return 0x2F8; - } + public override void OnMovement(Mobile from, Point3D oldLocation) + { + if (!from.Alive && from is PlayerMobile) + if (!from.Frozen && DateTime.UtcNow >= m_NextResurrect && InRange(from, 4) && !InRange(oldLocation, 4) && + InLOS(from)) + { + m_NextResurrect = DateTime.UtcNow + ResurrectDelay; + if (!from.Criminal && from.Kills < 5 && from.Karma > 0) + if (from.Map != null && from.Map.CanFit(from.Location, 16, false, false)) + { + Direction = GetDirectionTo(from); + from.PlaySound(0x1F2); + from.FixedEffect(0x376A, 10, 16); + from.CloseGump(typeof(ResurrectGump)); + from.SendGump(new ResurrectGump(from, ResurrectMessage.Healer)); + } + } + } - public override int GetAttackSound() - { - return Utility.Random( 0x2F5, 2 ); - } + public override int GetAngerSound() + { + return 0x2F8; + } - public override int GetHurtSound() - { - return 0x2F9; - } + public override int GetIdleSound() + { + return 0x2F8; + } - public override int GetDeathSound() - { - return 0x2F7; - } + public override int GetAttackSound() + { + return Utility.Random(0x2F5, 2); + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override int GetHurtSound() + { + return 0x2F9; + } - defender.Damage( Utility.Random( 10, 10 ), this ); - defender.Stam -= Utility.Random( 10, 10 ); - defender.Mana -= Utility.Random( 10, 10 ); - } + public override int GetDeathSound() + { + return 0x2F7; + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - attacker.Damage( Utility.Random( 10, 10 ), this ); - attacker.Stam -= Utility.Random( 10, 10 ); - attacker.Mana -= Utility.Random( 10, 10 ); - } + defender.Damage(Utility.Random(10, 10), this); + defender.Stam -= Utility.Random(10, 10); + defender.Mana -= Utility.Random(10, 10); + } - public EtherealWarrior( Serial serial ) : base( serial ) - { - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + attacker.Damage(Utility.Random(10, 10), this); + attacker.Stam -= Utility.Random(10, 10); + attacker.Mana -= Utility.Random(10, 10); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Magic/Pixie.cs b/Scripts/Mobiles/Monsters/Misc/Magic/Pixie.cs index d8cb179b7..10b872740 100644 --- a/Scripts/Mobiles/Monsters/Misc/Magic/Pixie.cs +++ b/Scripts/Mobiles/Monsters/Misc/Magic/Pixie.cs @@ -2,84 +2,84 @@ using Server.Items; namespace Server.Mobiles { - public class Pixie : BaseCreature - { - public override string CorpseName => "a pixie corpse"; - public override bool InitialInnocent => true; + public class Pixie : BaseCreature + { + [Constructible] + public Pixie() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("pixie"); + Body = 128; + BaseSoundID = 0x467; - [Constructible] - public Pixie() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "pixie" ); - Body = 128; - BaseSoundID = 0x467; + SetStr(21, 30); + SetDex(301, 400); + SetInt(201, 250); - SetStr( 21, 30 ); - SetDex( 301, 400 ); - SetInt( 201, 250 ); + SetHits(13, 18); - SetHits( 13, 18 ); + SetDamage(9, 15); - SetDamage( 9, 15 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 100.5, 150.0); + SetSkill(SkillName.Tactics, 10.1, 20.0); + SetSkill(SkillName.Wrestling, 10.1, 12.5); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 100.5, 150.0 ); - SetSkill( SkillName.Tactics, 10.1, 20.0 ); - SetSkill( SkillName.Wrestling, 10.1, 12.5 ); + Fame = 7000; + Karma = 7000; - Fame = 7000; - Karma = 7000; + VirtualArmor = 100; + if (0.02 > Utility.RandomDouble()) + PackStatue(); + } - VirtualArmor = 100; - if ( 0.02 > Utility.RandomDouble() ) - PackStatue(); - } + public Pixie(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "a pixie corpse"; + public override bool InitialInnocent => true; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override HideType HideType => HideType.Spined; + public override int Hides => 5; + public override int Meat => 1; - if ( Utility.RandomDouble() < 0.35 ) - c.DropItem( new PixieLeg() ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override HideType HideType => HideType.Spined; - public override int Hides => 5; - public override int Meat => 1; + public override void GenerateLoot() + { + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.Gems, 2); + } - public Pixie( Serial serial ) : base( serial ) - { - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + if (Utility.RandomDouble() < 0.35) + c.DropItem(new PixieLeg()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Magic/ShadowWisp.cs b/Scripts/Mobiles/Monsters/Misc/Magic/ShadowWisp.cs index dbcffa84d..0c2758649 100644 --- a/Scripts/Mobiles/Monsters/Misc/Magic/ShadowWisp.cs +++ b/Scripts/Mobiles/Monsters/Misc/Magic/ShadowWisp.cs @@ -2,76 +2,96 @@ using Server.Items; namespace Server.Mobiles { - public class ShadowWisp : BaseCreature - { - public override string CorpseName => "a wisp corpse"; - public override string DefaultName => "a shadow wisp"; + public class ShadowWisp : BaseCreature + { + [Constructible] + public ShadowWisp() : base(AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.3, 0.6) + { + Body = 165; + BaseSoundID = 466; - [Constructible] - public ShadowWisp() : base( AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.3, 0.6 ) - { - Body = 165; - BaseSoundID = 466; + SetStr(16, 40); + SetDex(16, 45); + SetInt(11, 25); - SetStr( 16, 40 ); - SetDex( 16, 45 ); - SetInt( 11, 25 ); + SetHits(10, 24); - SetHits( 10, 24 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 15, 20); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 15, 20 ); + SetSkill(SkillName.EvalInt, 40.0); + SetSkill(SkillName.Magery, 50.0); + SetSkill(SkillName.Meditation, 40.0); + SetSkill(SkillName.MagicResist, 10.0); + SetSkill(SkillName.Tactics, 0.1, 15.0); + SetSkill(SkillName.Wrestling, 25.1, 40.0); - SetSkill( SkillName.EvalInt, 40.0 ); - SetSkill( SkillName.Magery, 50.0 ); - SetSkill( SkillName.Meditation, 40.0 ); - SetSkill( SkillName.MagicResist, 10.0 ); - SetSkill( SkillName.Tactics, 0.1, 15.0 ); - SetSkill( SkillName.Wrestling, 25.1, 40.0 ); + Fame = 500; - Fame = 500; + VirtualArmor = 18; - VirtualArmor = 18; + AddItem(new LightSource()); - AddItem( new LightSource() ); + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } + } - switch ( Utility.Random( 10 )) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } - } + public ShadowWisp(Serial serial) : base(serial) + { + } - public ShadowWisp( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a wisp corpse"; + public override string DefaultName => "a shadow wisp"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Magic/Wisp.cs b/Scripts/Mobiles/Monsters/Misc/Magic/Wisp.cs index 8f78a0138..d60a03943 100644 --- a/Scripts/Mobiles/Monsters/Misc/Magic/Wisp.cs +++ b/Scripts/Mobiles/Monsters/Misc/Magic/Wisp.cs @@ -1,84 +1,86 @@ using System; -using Server.Misc; -using Server.Items; +using Server.Engines.Plants; +using Server.Ethics; using Server.Factions; +using Server.Items; +using Server.Misc; namespace Server.Mobiles { - public class Wisp : BaseCreature - { - public override string CorpseName => "a wisp corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Wisp; + public class Wisp : BaseCreature + { + [Constructible] + public Wisp() : base(AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Body = 58; + BaseSoundID = 466; - public override Faction FactionAllegiance => CouncilOfMages.Instance; - public override Ethics.Ethic EthicAllegiance => Ethics.Ethic.Hero; + SetStr(196, 225); + SetDex(196, 225); + SetInt(196, 225); - public override TimeSpan ReacquireDelay => TimeSpan.FromSeconds( 1.0 ); + SetHits(118, 135); - public override string DefaultName => "a wisp"; + SetDamage(17, 18); - [Constructible] - public Wisp() : base( AIType.AI_Mage, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Body = 58; - BaseSoundID = 466; + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); - SetStr( 196, 225 ); - SetDex( 196, 225 ); - SetInt( 196, 225 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 20, 40); + SetResistance(ResistanceType.Cold, 10, 30); + SetResistance(ResistanceType.Poison, 5, 10); + SetResistance(ResistanceType.Energy, 50, 70); - SetHits( 118, 135 ); + SetSkill(SkillName.EvalInt, 80.0); + SetSkill(SkillName.Magery, 80.0); + SetSkill(SkillName.MagicResist, 80.0); + SetSkill(SkillName.Tactics, 80.0); + SetSkill(SkillName.Wrestling, 80.0); - SetDamage( 17, 18 ); + Fame = 4000; + Karma = 0; - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + VirtualArmor = 40; - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 20, 40 ); - SetResistance( ResistanceType.Cold, 10, 30 ); - SetResistance( ResistanceType.Poison, 5, 10 ); - SetResistance( ResistanceType.Energy, 50, 70 ); + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(3)); - SetSkill( SkillName.EvalInt, 80.0 ); - SetSkill( SkillName.Magery, 80.0 ); - SetSkill( SkillName.MagicResist, 80.0 ); - SetSkill( SkillName.Tactics, 80.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + AddItem(new LightSource()); + } - Fame = 4000; - Karma = 0; + public Wisp(Serial serial) : base(serial) + { + } - VirtualArmor = 40; + public override string CorpseName => "a wisp corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Wisp; - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(3) ); + public override Faction FactionAllegiance => CouncilOfMages.Instance; + public override Ethic EthicAllegiance => Ethic.Hero; - AddItem( new LightSource() ); - } + public override TimeSpan ReacquireDelay => TimeSpan.FromSeconds(1.0); - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - } + public override string DefaultName => "a wisp"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public Wisp( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/AnimatedWeapon.cs b/Scripts/Mobiles/Monsters/Misc/Melee/AnimatedWeapon.cs index 57e927a20..dae1e9c57 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/AnimatedWeapon.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/AnimatedWeapon.cs @@ -2,110 +2,110 @@ namespace Server.Mobiles { - public class AnimatedWeapon : BaseCreature - { - public override string CorpseName => "an animated weapon corpse"; - public override bool DeleteCorpseOnDeath => true; - public override bool IsHouseSummonable => true; + public class AnimatedWeapon : BaseCreature + { + [Constructible] + public AnimatedWeapon(Mobile caster, int level) + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.3, 0.6) + { + Body = 692; - public override double DispelDifficulty => 0.0; - public override double DispelFocus => 20.0; + SetStr(10 + level); + SetDex(10 + level); + SetInt(10); - public override double GetFightModeRanking( Mobile m, FightMode acqType, bool bPlayerOnly ) - { - return m.Str / Math.Max( GetDistanceToSqrt( m ), 1.0 ); - } + SetHits(20 + level * 3 / 2); + SetStam(10 + level); + SetMana(0); - public override string DefaultName => "an animated weapon"; + if (level >= 120) + SetDamage(14, 18); + else if (level >= 105) + SetDamage(13, 17); + else if (level >= 90) + SetDamage(12, 15); + else if (level >= 75) + SetDamage(11, 14); + else if (level >= 60) + SetDamage(10, 12); + else if (level >= 45) + SetDamage(9, 11); + else if (level >= 30) + SetDamage(8, 9); + else + SetDamage(7, 8); - [Constructible] - public AnimatedWeapon( Mobile caster, int level ) - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.3, 0.6 ) - { - Body = 692; + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 20); + SetDamageType(ResistanceType.Energy, 20); - SetStr( 10 + level ); - SetDex( 10 + level ); - SetInt( 10 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 20, 30); - SetHits( 20 + ( level * 3 / 2 ) ); - SetStam( 10 + level ); - SetMana( 0 ); + SetSkill(SkillName.MagicResist, level); + SetSkill(SkillName.Wrestling, level); + SetSkill(SkillName.Anatomy, caster.Skills[SkillName.Anatomy].Value / 2); + SetSkill(SkillName.Tactics, caster.Skills[SkillName.Tactics].Value / 2); - if ( level >= 120 ) - SetDamage( 14, 18 ); - else if ( level >= 105 ) - SetDamage( 13, 17 ); - else if ( level >= 90 ) - SetDamage( 12, 15 ); - else if ( level >= 75 ) - SetDamage( 11, 14 ); - else if ( level >= 60 ) - SetDamage( 10, 12 ); - else if ( level >= 45 ) - SetDamage( 9, 11 ); - else if ( level >= 30 ) - SetDamage( 8, 9 ); - else - SetDamage( 7, 8 ); + Fame = 0; + Karma = 0; - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 20 ); - SetDamageType( ResistanceType.Energy, 20 ); + ControlSlots = 4; + } - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + public AnimatedWeapon(Serial serial) + : base(serial) + { + } - SetSkill( SkillName.MagicResist, level ); - SetSkill( SkillName.Wrestling, level ); - SetSkill( SkillName.Anatomy, caster.Skills[SkillName.Anatomy].Value / 2 ); - SetSkill( SkillName.Tactics, caster.Skills[SkillName.Tactics].Value / 2 ); + public override string CorpseName => "an animated weapon corpse"; + public override bool DeleteCorpseOnDeath => true; + public override bool IsHouseSummonable => true; - Fame = 0; - Karma = 0; + public override double DispelDifficulty => 0.0; + public override double DispelFocus => 20.0; - ControlSlots = 4; - } + public override string DefaultName => "an animated weapon"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public override int GetAngerSound() - { - return 0x23A; - } + public override double GetFightModeRanking(Mobile m, FightMode acqType, bool bPlayerOnly) + { + return m.Str / Math.Max(GetDistanceToSqrt(m), 1.0); + } - public override int GetAttackSound() - { - return 0x3B8; - } + public override int GetAngerSound() + { + return 0x23A; + } - public override int GetHurtSound() - { - return 0x23A; - } + public override int GetAttackSound() + { + return 0x3B8; + } - public AnimatedWeapon( Serial serial ) - : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x23A; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - /*int version = */ - reader.ReadInt(); - } - } -} + /*int version = */ + reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/BladeSpirits.cs b/Scripts/Mobiles/Monsters/Misc/Melee/BladeSpirits.cs index 0c9e62986..c1a373aa1 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/BladeSpirits.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/BladeSpirits.cs @@ -3,120 +3,116 @@ using System.Collections; namespace Server.Mobiles { - public class BladeSpirits : BaseCreature - { - public override string CorpseName => "a blade spirit corpse"; - public override bool DeleteCorpseOnDeath => Core.AOS; - public override bool IsHouseSummonable => true; + public class BladeSpirits : BaseCreature + { + [Constructible] + public BladeSpirits() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.3, 0.6) + { + Body = 574; - public override double DispelDifficulty => 0.0; - public override double DispelFocus => 20.0; + SetStr(150); + SetDex(150); + SetInt(100); - public override double GetFightModeRanking( Mobile m, FightMode acqType, bool bPlayerOnly ) - { - return ( m.Str + m.Skills[SkillName.Tactics].Value ) / Math.Max( GetDistanceToSqrt( m ), 1.0 ); - } + SetHits(Core.SE ? 160 : 80); + SetStam(250); + SetMana(0); - public override string DefaultName => "a blade spirit"; + SetDamage(10, 14); - [Constructible] - public BladeSpirits() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.3, 0.6 ) - { - Body = 574; + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 20); + SetDamageType(ResistanceType.Energy, 20); - SetStr( 150 ); - SetDex( 150 ); - SetInt( 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 20, 30); - SetHits( ( Core.SE ) ? 160 : 80 ); - SetStam( 250 ); - SetMana( 0 ); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 90.0); + SetSkill(SkillName.Wrestling, 90.0); - SetDamage( 10, 14 ); + Fame = 0; + Karma = 0; - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 20 ); - SetDamageType( ResistanceType.Energy, 20 ); + VirtualArmor = 40; + ControlSlots = Core.SE ? 2 : 1; + } - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + public BladeSpirits(Serial serial) + : base(serial) + { + } - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 90.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + public override string CorpseName => "a blade spirit corpse"; + public override bool DeleteCorpseOnDeath => Core.AOS; + public override bool IsHouseSummonable => true; - Fame = 0; - Karma = 0; + public override double DispelDifficulty => 0.0; + public override double DispelFocus => 20.0; - VirtualArmor = 40; - ControlSlots = ( Core.SE ) ? 2 : 1; - } + public override string DefaultName => "a blade spirit"; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public override int GetAngerSound() - { - return 0x23A; - } + public override double GetFightModeRanking(Mobile m, FightMode acqType, bool bPlayerOnly) + { + return (m.Str + m.Skills[SkillName.Tactics].Value) / Math.Max(GetDistanceToSqrt(m), 1.0); + } - public override int GetAttackSound() - { - return 0x3B8; - } + public override int GetAngerSound() + { + return 0x23A; + } - public override int GetHurtSound() - { - return 0x23A; - } + public override int GetAttackSound() + { + return 0x3B8; + } - public override void OnThink() - { - if ( Core.SE && Summoned ) - { - ArrayList spirtsOrVortexes = new ArrayList(); + public override int GetHurtSound() + { + return 0x23A; + } - foreach ( Mobile m in GetMobilesInRange( 5 ) ) - { - if ( m is EnergyVortex || m is BladeSpirits ) - { - if ( ( (BaseCreature) m ).Summoned ) - spirtsOrVortexes.Add( m ); - } - } + public override void OnThink() + { + if (Core.SE && Summoned) + { + ArrayList spirtsOrVortexes = new ArrayList(); - while ( spirtsOrVortexes.Count > 6 ) - { - int index = Utility.Random( spirtsOrVortexes.Count ); - Dispel( ( (Mobile) spirtsOrVortexes[index] ) ); - spirtsOrVortexes.RemoveAt( index ); - } - } + foreach (Mobile m in GetMobilesInRange(5)) + if (m is EnergyVortex || m is BladeSpirits) + if (((BaseCreature)m).Summoned) + spirtsOrVortexes.Add(m); - base.OnThink(); - } + while (spirtsOrVortexes.Count > 6) + { + int index = Utility.Random(spirtsOrVortexes.Count); + Dispel((Mobile)spirtsOrVortexes[index]); + spirtsOrVortexes.RemoveAt(index); + } + } - public BladeSpirits( Serial serial ) - : base( serial ) - { - } + base.OnThink(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/Centaur.cs b/Scripts/Mobiles/Monsters/Misc/Melee/Centaur.cs index e04e80979..abcd878b6 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/Centaur.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/Centaur.cs @@ -2,76 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class Centaur : BaseCreature - { - public override string CorpseName => "a centaur corpse"; - [Constructible] - public Centaur() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "centaur" ); - Body = 101; - BaseSoundID = 679; + public class Centaur : BaseCreature + { + [Constructible] + public Centaur() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("centaur"); + Body = 101; + BaseSoundID = 679; - SetStr( 202, 300 ); - SetDex( 104, 260 ); - SetInt( 91, 100 ); + SetStr(202, 300); + SetDex(104, 260); + SetInt(91, 100); - SetHits( 130, 172 ); + SetHits(130, 172); - SetDamage( 13, 24 ); + SetDamage(13, 24); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 45, 55 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 45, 55); + SetResistance(ResistanceType.Energy, 35, 45); - SetSkill( SkillName.Anatomy, 95.1, 115.0 ); - SetSkill( SkillName.Archery, 95.1, 100.0 ); - SetSkill( SkillName.MagicResist, 50.3, 80.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 95.1, 100.0 ); + SetSkill(SkillName.Anatomy, 95.1, 115.0); + SetSkill(SkillName.Archery, 95.1, 100.0); + SetSkill(SkillName.MagicResist, 50.3, 80.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 95.1, 100.0); - Fame = 6500; - Karma = 0; + Fame = 6500; + Karma = 0; - VirtualArmor = 50; - AddItem( new Bow() ); - PackItem( new Arrow( Utility.RandomMinMax( 80, 90 ) ) ); // OSI it is different: in a sub backpack, this is probably just a limitation of their engine - } + VirtualArmor = 50; + AddItem(new Bow()); + PackItem(new Arrow(Utility.RandomMinMax(80, + 90))); // OSI it is different: in a sub backpack, this is probably just a limitation of their engine + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems ); - } + public Centaur(Serial serial) : base(serial) + { + } - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string CorpseName => "a centaur corpse"; - public override int Meat => 1; - public override int Hides => 8; - public override HideType HideType => HideType.Spined; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public Centaur( Serial serial ) : base( serial ) - { - } + public override int Meat => 1; + public override int Hides => 8; + public override HideType HideType => HideType.Spined; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - if ( BaseSoundID == 678 ) - BaseSoundID = 679; - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + if (BaseSoundID == 678) + BaseSoundID = 679; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/EnergyVortex.cs b/Scripts/Mobiles/Monsters/Misc/Melee/EnergyVortex.cs index 374f41487..0ecbc6e43 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/EnergyVortex.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/EnergyVortex.cs @@ -3,128 +3,124 @@ using System.Collections; namespace Server.Mobiles { - public class EnergyVortex : BaseCreature - { - public override string CorpseName => "an energy vortex corpse"; - public override bool DeleteCorpseOnDeath => Summoned; - public override bool AlwaysMurderer => true; // Or Llama vortices will appear gray. + public class EnergyVortex : BaseCreature + { + [Constructible] + public EnergyVortex() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + if (Core.SE && 0.002 > Utility.RandomDouble()) // Per OSI FoF, it's a 1/500 chance. + { + // Llama vortex! + Body = 0xDC; + Hue = 0x76; + } + else + { + Body = 164; + } - public override double DispelDifficulty => 80.0; - public override double DispelFocus => 20.0; + SetStr(200); + SetDex(200); + SetInt(100); - public override double GetFightModeRanking( Mobile m, FightMode acqType, bool bPlayerOnly ) - { - return ( m.Int + m.Skills[SkillName.Magery].Value ) / Math.Max( GetDistanceToSqrt( m ), 1.0 ); - } + SetHits(Core.SE ? 140 : 70); + SetStam(250); + SetMana(0); - public override string DefaultName => "an energy vortex"; + SetDamage(14, 17); - [Constructible] - public EnergyVortex() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - if ( Core.SE && 0.002 > Utility.RandomDouble() ) // Per OSI FoF, it's a 1/500 chance. - { - // Llama vortex! - Body = 0xDC; - Hue = 0x76; - } - else - { - Body = 164; - } + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Energy, 100); - SetStr( 200 ); - SetDex( 200 ); - SetInt( 100 ); + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 90, 100); - SetHits( ( Core.SE ) ? 140 : 70 ); - SetStam( 250 ); - SetMana( 0 ); + SetSkill(SkillName.MagicResist, 99.9); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 120.0); - SetDamage( 14, 17 ); + Fame = 0; + Karma = 0; - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Energy, 100 ); - - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 90, 100 ); - - SetSkill( SkillName.MagicResist, 99.9 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 120.0 ); - - Fame = 0; - Karma = 0; - - VirtualArmor = 40; - ControlSlots = ( Core.SE ) ? 2 : 1; - } - - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - - public override int GetAngerSound() - { - return 0x15; - } - - public override int GetAttackSound() - { - return 0x28; - } - - public override void OnThink() - { - if ( Core.SE && Summoned ) - { - ArrayList spirtsOrVortexes = new ArrayList(); - - foreach ( Mobile m in GetMobilesInRange( 5 ) ) - { - if ( m is EnergyVortex || m is BladeSpirits ) - { - if ( ( (BaseCreature) m ).Summoned ) - spirtsOrVortexes.Add( m ); - } - } - - while ( spirtsOrVortexes.Count > 6 ) - { - int index = Utility.Random( spirtsOrVortexes.Count ); - //TODO: Confirm if it's the dispel with all the pretty effects or just a deletion of it. - Dispel( ( (Mobile) spirtsOrVortexes[index] ) ); - spirtsOrVortexes.RemoveAt( index ); - } - } - - base.OnThink(); - } + VirtualArmor = 40; + ControlSlots = Core.SE ? 2 : 1; + } - public EnergyVortex( Serial serial ) - : base( serial ) - { - } + public EnergyVortex(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string CorpseName => "an energy vortex corpse"; + public override bool DeleteCorpseOnDeath => Summoned; + public override bool AlwaysMurderer => true; // Or Llama vortices will appear gray. - writer.Write( (int) 0 ); // version - } + public override double DispelDifficulty => 80.0; + public override double DispelFocus => 20.0; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override string DefaultName => "an energy vortex"; - int version = reader.ReadInt(); + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - if ( BaseSoundID == 263 ) - BaseSoundID = 0; - } - } -} + public override double GetFightModeRanking(Mobile m, FightMode acqType, bool bPlayerOnly) + { + return (m.Int + m.Skills[SkillName.Magery].Value) / Math.Max(GetDistanceToSqrt(m), 1.0); + } + + public override int GetAngerSound() + { + return 0x15; + } + + public override int GetAttackSound() + { + return 0x28; + } + + public override void OnThink() + { + if (Core.SE && Summoned) + { + ArrayList spirtsOrVortexes = new ArrayList(); + + foreach (Mobile m in GetMobilesInRange(5)) + if (m is EnergyVortex || m is BladeSpirits) + if (((BaseCreature)m).Summoned) + spirtsOrVortexes.Add(m); + + while (spirtsOrVortexes.Count > 6) + { + int index = Utility.Random(spirtsOrVortexes.Count); + //TODO: Confirm if it's the dispel with all the pretty effects or just a deletion of it. + Dispel((Mobile)spirtsOrVortexes[index]); + spirtsOrVortexes.RemoveAt(index); + } + } + + base.OnThink(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (BaseSoundID == 263) + BaseSoundID = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/FrostOoze.cs b/Scripts/Mobiles/Monsters/Misc/Melee/FrostOoze.cs index bacf00054..d43ededab 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/FrostOoze.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/FrostOoze.cs @@ -1,60 +1,60 @@ namespace Server.Mobiles { - public class FrostOoze : BaseCreature - { - public override string CorpseName => "a frost ooze corpse"; - public override string DefaultName => "a frost ooze"; + public class FrostOoze : BaseCreature + { + [Constructible] + public FrostOoze() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 94; + BaseSoundID = 456; - [Constructible] - public FrostOoze() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 94; - BaseSoundID = 456; + SetStr(18, 30); + SetDex(16, 21); + SetInt(16, 20); - SetStr( 18, 30 ); - SetDex( 16, 21 ); - SetInt( 16, 20 ); + SetHits(13, 17); - SetHits( 13, 17 ); + SetDamage(3, 9); - SetDamage( 3, 9 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 5.1, 10.0); + SetSkill(SkillName.Tactics, 19.3, 34.0); + SetSkill(SkillName.Wrestling, 25.3, 40.0); - SetSkill( SkillName.MagicResist, 5.1, 10.0 ); - SetSkill( SkillName.Tactics, 19.3, 34.0 ); - SetSkill( SkillName.Wrestling, 25.3, 40.0 ); + Fame = 450; + Karma = -450; - Fame = 450; - Karma = -450; + VirtualArmor = 38; + } - VirtualArmor = 38; - } + public FrostOoze(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Gems, Utility.RandomMinMax( 1, 2 ) ); - } + public override string CorpseName => "a frost ooze corpse"; + public override string DefaultName => "a frost ooze"; - public FrostOoze( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Gems, Utility.RandomMinMax(1, 2)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/Golem.cs b/Scripts/Mobiles/Monsters/Misc/Melee/Golem.cs index d18f6864c..fae0240b1 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/Golem.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/Golem.cs @@ -4,227 +4,231 @@ using Server.Network; namespace Server.Mobiles { - public class Golem : BaseCreature - { - public override string CorpseName => "a golem corpse"; - private bool m_Stunning; + public class Golem : BaseCreature + { + private bool m_Stunning; - public override bool IsScaredOfScaryThings => false; - public override bool IsScaryToPets => true; + [Constructible] + public Golem() : this(false, 1.0) + { + } - public override bool IsBondable => false; + [Constructible] + public Golem(bool summoned, double scalar) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8) + { + Body = 752; - public override FoodType FavoriteFood => FoodType.None; + if (summoned) + Hue = 2101; - public override bool CanBeDistracted => false; + SetStr((int)(251 * scalar), (int)(350 * scalar)); + SetDex((int)(76 * scalar), (int)(100 * scalar)); + SetInt((int)(101 * scalar), (int)(150 * scalar)); - public override string DefaultName => "a golem"; + SetHits((int)(151 * scalar), (int)(210 * scalar)); - [Constructible] - public Golem() : this( false, 1.0 ) - { - } + SetDamage((int)(13 * scalar), (int)(24 * scalar)); - [Constructible] - public Golem( bool summoned, double scalar ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8 ) - { - Body = 752; + SetDamageType(ResistanceType.Physical, 100); - if ( summoned ) - Hue = 2101; + SetResistance(ResistanceType.Physical, (int)(35 * scalar), (int)(55 * scalar)); - SetStr( (int)(251*scalar), (int)(350*scalar) ); - SetDex( (int)(76*scalar), (int)(100*scalar) ); - SetInt( (int)(101*scalar), (int)(150*scalar) ); + if (summoned) + SetResistance(ResistanceType.Fire, (int)(50 * scalar), (int)(60 * scalar)); + else + SetResistance(ResistanceType.Fire, (int)(100 * scalar)); - SetHits( (int)(151*scalar), (int)(210*scalar) ); + SetResistance(ResistanceType.Cold, (int)(10 * scalar), (int)(30 * scalar)); + SetResistance(ResistanceType.Poison, (int)(10 * scalar), (int)(25 * scalar)); + SetResistance(ResistanceType.Energy, (int)(30 * scalar), (int)(40 * scalar)); - SetDamage( (int)(13*scalar), (int)(24*scalar) ); + SetSkill(SkillName.MagicResist, 150.1 * scalar, 190.0 * scalar); + SetSkill(SkillName.Tactics, 60.1 * scalar, 100.0 * scalar); + SetSkill(SkillName.Wrestling, 60.1 * scalar, 100.0 * scalar); - SetDamageType( ResistanceType.Physical, 100 ); + if (summoned) + { + Fame = 10; + Karma = 10; + } + else + { + Fame = 3500; + Karma = -3500; + } - SetResistance( ResistanceType.Physical, (int)(35*scalar), (int)(55*scalar) ); + if (!summoned) + { + PackItem(new IronIngot(Utility.RandomMinMax(13, 21))); - if ( summoned ) - SetResistance( ResistanceType.Fire, (int)(50*scalar), (int)(60*scalar) ); - else - SetResistance( ResistanceType.Fire, (int)(100*scalar) ); + if (0.1 > Utility.RandomDouble()) + PackItem(new PowerCrystal()); - SetResistance( ResistanceType.Cold, (int)(10*scalar), (int)(30*scalar) ); - SetResistance( ResistanceType.Poison, (int)(10*scalar), (int)(25*scalar) ); - SetResistance( ResistanceType.Energy, (int)(30*scalar), (int)(40*scalar) ); + if (0.15 > Utility.RandomDouble()) + PackItem(new ClockworkAssembly()); - SetSkill( SkillName.MagicResist, (150.1*scalar), (190.0*scalar) ); - SetSkill( SkillName.Tactics, (60.1*scalar), (100.0*scalar) ); - SetSkill( SkillName.Wrestling, (60.1*scalar), (100.0*scalar) ); + if (0.2 > Utility.RandomDouble()) + PackItem(new ArcaneGem()); - if ( summoned ) - { - Fame = 10; - Karma = 10; - } - else - { - Fame = 3500; - Karma = -3500; - } + if (0.25 > Utility.RandomDouble()) + PackItem(new Gears()); + } - if ( !summoned ) - { - PackItem( new IronIngot( Utility.RandomMinMax( 13, 21 ) ) ); + ControlSlots = 3; + } - if ( 0.1 > Utility.RandomDouble() ) - PackItem( new PowerCrystal() ); + public Golem(Serial serial) : base(serial) + { + } - if ( 0.15 > Utility.RandomDouble() ) - PackItem( new ClockworkAssembly() ); + public override string CorpseName => "a golem corpse"; - if ( 0.2 > Utility.RandomDouble() ) - PackItem( new ArcaneGem() ); + public override bool IsScaredOfScaryThings => false; + public override bool IsScaryToPets => true; - if ( 0.25 > Utility.RandomDouble() ) - PackItem( new Gears() ); - } + public override bool IsBondable => false; - ControlSlots = 3; - } + public override FoodType FavoriteFood => FoodType.None; - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override bool CanBeDistracted => false; - if ( 0.05 > Utility.RandomDouble() ) - { - if ( !IsParagon ) - { - if ( 0.75 > Utility.RandomDouble() ) - c.DropItem( DawnsMusicGear.RandomCommon ); - else - c.DropItem( DawnsMusicGear.RandomUncommon ); - } - else - c.DropItem( DawnsMusicGear.RandomRare ); - } - } + public override string DefaultName => "a golem"; - public override bool DeleteOnRelease => true; + public override bool DeleteOnRelease => true; - public override int GetAngerSound() - { - return 541; - } + public override bool AutoDispel => !Controlled; + public override bool BleedImmune => true; - public override int GetIdleSound() - { - if ( !Controlled ) - return 542; + public override bool BardImmune => !Core.AOS || Controlled; + public override Poison PoisonImmune => Poison.Lethal; - return base.GetIdleSound(); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); - public override int GetDeathSound() - { - if ( !Controlled ) - return 545; + if (0.05 > Utility.RandomDouble()) + { + if (!IsParagon) + { + if (0.75 > Utility.RandomDouble()) + c.DropItem(DawnsMusicGear.RandomCommon); + else + c.DropItem(DawnsMusicGear.RandomUncommon); + } + else + { + c.DropItem(DawnsMusicGear.RandomRare); + } + } + } - return base.GetDeathSound(); - } + public override int GetAngerSound() + { + return 541; + } - public override int GetAttackSound() - { - return 562; - } + public override int GetIdleSound() + { + if (!Controlled) + return 542; - public override int GetHurtSound() - { - if ( Controlled ) - return 320; + return base.GetIdleSound(); + } - return base.GetHurtSound(); - } + public override int GetDeathSound() + { + if (!Controlled) + return 545; - public override bool AutoDispel => !Controlled; - public override bool BleedImmune => true; + return base.GetDeathSound(); + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override int GetAttackSound() + { + return 562; + } - if ( !m_Stunning && 0.3 > Utility.RandomDouble() ) - { - m_Stunning = true; + public override int GetHurtSound() + { + if (Controlled) + return 320; - defender.Animate( 21, 6, 1, true, false, 0 ); - PlaySound( 0xEE ); - defender.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You have been stunned by a colossal blow!" ); + return base.GetHurtSound(); + } - if ( Weapon is BaseWeapon weapon ) - weapon.OnHit( this, defender ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( defender.Alive ) - { - defender.Frozen = true; - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( Recover_Callback ), defender ); - } - } - } + if (!m_Stunning && 0.3 > Utility.RandomDouble()) + { + m_Stunning = true; - private void Recover_Callback( object state ) - { - if ( state is Mobile defender ) - { - defender.Frozen = false; - defender.Combatant = null; - defender.LocalOverheadMessage( MessageType.Regular, 0x3B2, false, "You recover your senses." ); - } + defender.Animate(21, 6, 1, true, false, 0); + PlaySound(0xEE); + defender.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, + "You have been stunned by a colossal blow!"); - m_Stunning = false; - } + if (Weapon is BaseWeapon weapon) + weapon.OnHit(this, defender); - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( Controlled || Summoned ) - { - Mobile master = ( ControlMaster ); + if (defender.Alive) + { + defender.Frozen = true; + Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(Recover_Callback), defender); + } + } + } - if ( master == null ) - master = SummonMaster; + private void Recover_Callback(object state) + { + if (state is Mobile defender) + { + defender.Frozen = false; + defender.Combatant = null; + defender.LocalOverheadMessage(MessageType.Regular, 0x3B2, false, "You recover your senses."); + } - if ( master != null && master.Player && master.Map == Map && master.InRange( Location, 20 ) ) - { - if ( master.Mana >= amount ) - { - master.Mana -= amount; - } - else - { - amount -= master.Mana; - master.Mana = 0; - master.Damage( amount ); - } - } - } + m_Stunning = false; + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (Controlled || Summoned) + { + Mobile master = ControlMaster; - public override bool BardImmune => !Core.AOS || Controlled; - public override Poison PoisonImmune => Poison.Lethal; + if (master == null) + master = SummonMaster; - public Golem( Serial serial ) : base( serial ) - { - } + if (master != null && master.Player && master.Map == Map && master.InRange(Location, 20)) + { + if (master.Mana >= amount) + { + master.Mana -= amount; + } + else + { + amount -= master.Mana; + master.Mana = 0; + master.Damage(amount); + } + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + base.OnDamage(amount, from, willKill); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeast.cs b/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeast.cs index 288994e20..719e8af04 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeast.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeast.cs @@ -1,246 +1,248 @@ using System; +using Server.Engines.Plants; using Server.Items; using Server.Network; namespace Server.Mobiles { - public class PlagueBeast : BaseCreature, IDevourer - { - public override string CorpseName => "a plague beast corpse"; - private int m_DevourGoal; + public class PlagueBeast : BaseCreature, IDevourer + { + private int m_DevourGoal; - [CommandProperty( AccessLevel.GameMaster )] - public int TotalDevoured { get; set; } + [Constructible] + public PlagueBeast() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 775; - [CommandProperty( AccessLevel.GameMaster )] - public int DevourGoal - { - get => ( IsParagon ? m_DevourGoal + 25 : m_DevourGoal ); - set => m_DevourGoal = value; - } + SetStr(302, 500); + SetDex(80); + SetInt(16, 20); - [CommandProperty( AccessLevel.GameMaster )] - public bool HasMetalChest { get; private set; } + SetHits(318, 404); - public override string DefaultName => "a plague beast"; + SetDamage(20, 24); - [Constructible] - public PlagueBeast() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 775; + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetStr( 302, 500 ); - SetDex( 80 ); - SetInt( 16, 20 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 65, 75); + SetResistance(ResistanceType.Energy, 25, 35); - SetHits( 318, 404 ); + SetSkill(SkillName.MagicResist, 35.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - SetDamage( 20, 24 ); + Fame = 13000; + Karma = -13000; - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + VirtualArmor = 30; + PackArmor(1, 5); + if (Utility.RandomDouble() < 0.80) + PackItem(new PlagueBeastGland()); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 65, 75 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + if (Core.ML && Utility.RandomDouble() < 0.33) + PackItem(Seed.RandomPeculiarSeed(4)); - SetSkill( SkillName.MagicResist, 35.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + TotalDevoured = 0; + m_DevourGoal = Utility.RandomMinMax(15, 25); // How many corpses must be devoured before a metal chest is awarded + } - Fame = 13000; - Karma = -13000; + public PlagueBeast(Serial serial) : base(serial) + { + } - VirtualArmor = 30; - PackArmor( 1, 5 ); - if ( Utility.RandomDouble() < 0.80 ) - PackItem( new PlagueBeastGland() ); + public override string CorpseName => "a plague beast corpse"; - if ( Core.ML && Utility.RandomDouble() < 0.33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(4) ); + [CommandProperty(AccessLevel.GameMaster)] + public int TotalDevoured{ get; set; } - TotalDevoured = 0; - m_DevourGoal = Utility.RandomMinMax( 15, 25 ); // How many corpses must be devoured before a metal chest is awarded - } + [CommandProperty(AccessLevel.GameMaster)] + public int DevourGoal + { + get => IsParagon ? m_DevourGoal + 25 : m_DevourGoal; + set => m_DevourGoal = value; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Gems, Utility.Random( 1, 3 ) ); - // TODO: dungeon chest, healthy gland - } + [CommandProperty(AccessLevel.GameMaster)] + public bool HasMetalChest{ get; private set; } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override string DefaultName => "a plague beast"; - defender.ApplyPoison( this, IsParagon ? Poison.Lethal : Poison.Deadly ); - defender.FixedParticles( 0x374A, 10, 15, 5021, EffectLayer.Waist ); - defender.PlaySound( 0x1CB ); - } + public override bool AutoDispel => true; + public override Poison PoisonImmune => Poison.Lethal; - public override void OnDamagedBySpell( Mobile caster ) - { - if ( Map != null && caster != this && 0.25 > Utility.RandomDouble() ) - { - BaseCreature spawn = new PlagueSpawn( this ); + #region IDevourer Members - spawn.Team = Team; - spawn.MoveToWorld( Location, Map ); - spawn.Combatant = caster; + public bool Devour(Corpse corpse) + { + if (corpse?.Owner == null) // sorry we can't devour because the corpse's owner is null + return false; - Say( 1053034 ); // * The plague beast creates another beast from its flesh! * - } + if (corpse.Owner.Body.IsHuman) + corpse.TurnToBones(); // Not bones yet, and we are a human body therefore we turn to bones. - base.OnDamagedBySpell( caster ); - } + IncreaseHits((int)Math.Ceiling(corpse.Owner.HitsMax * 0.75)); + TotalDevoured++; - public override bool AutoDispel => true; - public override Poison PoisonImmune => Poison.Lethal; + PublicOverheadMessage(MessageType.Emote, 0x3B2, + 1053033); // * The plague beast absorbs the fleshy remains of the corpse * - public override void OnGotMeleeAttack( Mobile attacker ) - { - if ( Map != null && attacker != this && 0.25 > Utility.RandomDouble() ) - { - BaseCreature spawn = new PlagueSpawn( this ); + if (!HasMetalChest && TotalDevoured >= DevourGoal) + { + PackItem(new MetalChest()); + HasMetalChest = true; + } - spawn.Team = Team; - spawn.MoveToWorld( Location, Map ); - spawn.Combatant = attacker; + return true; + } - Say( 1053034 ); // * The plague beast creates another beast from its flesh! * - } + #endregion - base.OnGotMeleeAttack( attacker ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Gems, Utility.Random(1, 3)); + // TODO: dungeon chest, healthy gland + } - public PlagueBeast( Serial serial ) : base( serial ) - { - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override int GetIdleSound() - { - return 0x1BF; - } + defender.ApplyPoison(this, IsParagon ? Poison.Lethal : Poison.Deadly); + defender.FixedParticles(0x374A, 10, 15, 5021, EffectLayer.Waist); + defender.PlaySound(0x1CB); + } - public override int GetAttackSound() - { - return 0x1C0; - } + public override void OnDamagedBySpell(Mobile caster) + { + if (Map != null && caster != this && 0.25 > Utility.RandomDouble()) + { + BaseCreature spawn = new PlagueSpawn(this); - public override int GetHurtSound() - { - return 0x1C1; - } + spawn.Team = Team; + spawn.MoveToWorld(Location, Map); + spawn.Combatant = caster; - public override int GetDeathSound() - { - return 0x1C2; - } + Say(1053034); // * The plague beast creates another beast from its flesh! * + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); + base.OnDamagedBySpell(caster); + } - writer.Write( HasMetalChest ); - writer.Write( TotalDevoured ); - writer.Write( m_DevourGoal ); - } + public override void OnGotMeleeAttack(Mobile attacker) + { + if (Map != null && attacker != this && 0.25 > Utility.RandomDouble()) + { + BaseCreature spawn = new PlagueSpawn(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + spawn.Team = Team; + spawn.MoveToWorld(Location, Map); + spawn.Combatant = attacker; - switch( version ) - { - case 1: - { - HasMetalChest = reader.ReadBool(); - TotalDevoured = reader.ReadInt(); - m_DevourGoal = reader.ReadInt(); - break; - } - } - } + Say(1053034); // * The plague beast creates another beast from its flesh! * + } - public override void OnThink() - { - base.OnThink(); + base.OnGotMeleeAttack(attacker); + } - // Check to see if we need to devour any corpses - IPooledEnumerable eable = GetItemsInRange( 3 ); // Get all corpses in range + public override int GetIdleSound() + { + return 0x1BF; + } - foreach( Corpse item in eable ) - { - // Ensure that the corpse was killed by us - if ( item.Killer == this && item.Owner != null ) - { - if ( !item.DevourCorpse() && !item.Devoured ) - PublicOverheadMessage( MessageType.Emote, 0x3B2, 1053032 ); // * The plague beast attempts to absorb the remains, but cannot! * - } - } - eable.Free(); - } + public override int GetAttackSound() + { + return 0x1C0; + } - #region IDevourer Members + public override int GetHurtSound() + { + return 0x1C1; + } - public bool Devour( Corpse corpse ) - { - if ( corpse?.Owner == null ) // sorry we can't devour because the corpse's owner is null - return false; + public override int GetDeathSound() + { + return 0x1C2; + } - if ( corpse.Owner.Body.IsHuman ) - corpse.TurnToBones(); // Not bones yet, and we are a human body therefore we turn to bones. + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); - IncreaseHits( (int)Math.Ceiling( (double)corpse.Owner.HitsMax * 0.75 ) ); - TotalDevoured++; + writer.Write(HasMetalChest); + writer.Write(TotalDevoured); + writer.Write(m_DevourGoal); + } - PublicOverheadMessage( MessageType.Emote, 0x3B2, 1053033 ); // * The plague beast absorbs the fleshy remains of the corpse * + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( !HasMetalChest && TotalDevoured >= DevourGoal ) - { - PackItem( new MetalChest() ); - HasMetalChest = true; - } + switch (version) + { + case 1: + { + HasMetalChest = reader.ReadBool(); + TotalDevoured = reader.ReadInt(); + m_DevourGoal = reader.ReadInt(); + break; + } + } + } - return true; - } + public override void OnThink() + { + base.OnThink(); - #endregion + // Check to see if we need to devour any corpses + IPooledEnumerable eable = GetItemsInRange(3); // Get all corpses in range - private void IncreaseHits( int hp ) - { - int maxhits = 2000; + foreach (Corpse item in eable) + // Ensure that the corpse was killed by us + if (item.Killer == this && item.Owner != null) + if (!item.DevourCorpse() && !item.Devoured) + PublicOverheadMessage(MessageType.Emote, 0x3B2, + 1053032); // * The plague beast attempts to absorb the remains, but cannot! * + eable.Free(); + } - if ( IsParagon ) - maxhits = (int)(maxhits * Paragon.HitsBuff); + private void IncreaseHits(int hp) + { + int maxhits = 2000; - if ( hp < 1000 && !Core.AOS ) - hp = (hp * 100) / 60; + if (IsParagon) + maxhits = (int)(maxhits * Paragon.HitsBuff); - if ( HitsMaxSeed >= maxhits ) - { - HitsMaxSeed = maxhits; + if (hp < 1000 && !Core.AOS) + hp = hp * 100 / 60; - int newHits = Hits + hp + Utility.RandomMinMax( 10, 20 ); // increase the hp until it hits if it goes over it'll max at 2000 + if (HitsMaxSeed >= maxhits) + { + HitsMaxSeed = maxhits; - Hits = Math.Min( maxhits, newHits ); - // Also provide heal for each devour on top of the hp increase - } - else - { - int min = (hp / 2) + 10; - int max = hp + 20; - int hpToIncrease = Utility.RandomMinMax( min, max ); + int newHits = + Hits + hp + Utility.RandomMinMax(10, + 20); // increase the hp until it hits if it goes over it'll max at 2000 - HitsMaxSeed += hpToIncrease; - Hits += hpToIncrease; - // Also provide heal for each devour - } - } - } -} + Hits = Math.Min(maxhits, newHits); + // Also provide heal for each devour on top of the hp increase + } + else + { + int min = hp / 2 + 10; + int max = hp + 20; + int hpToIncrease = Utility.RandomMinMax(min, max); + + HitsMaxSeed += hpToIncrease; + Hits += hpToIncrease; + // Also provide heal for each devour + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeastLord.cs b/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeastLord.cs index 46c6d754e..b65490fb0 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeastLord.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/PlagueBeastLord.cs @@ -4,347 +4,354 @@ using Server.Network; namespace Server.Mobiles { - public class PlagueBeastLord : BaseCreature, ICarvable, IScissorable - { - public override string CorpseName => "a plague beast lord corpse"; - public override Poison PoisonImmune => Poison.Lethal; - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile OpenedBy { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsBleeding - { - get - { - Container pack = Backpack; - - if ( pack != null ) - { - for ( int i = 0; i < pack.Items.Count; i++ ) - { - if ( pack.Items[ i ] is PlagueBeastBlood blood && !blood.Patched ) - return true; - } - } - - return false; - } - } - - private DecayTimer m_Timer; - - public override string DefaultName => "a plague beast lord"; - - [Constructible] - public PlagueBeastLord() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 775; - BaseSoundID = 679; - SpeechHue = 0x3B2; - - SetStr( 500 ); - SetDex( 100 ); - SetInt( 30 ); - - SetHits( 1800 ); - - SetDamage( 20, 25 ); - - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Fire, 25 ); - SetDamageType( ResistanceType.Poison, 25 ); - - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 75, 85 ); - SetResistance( ResistanceType.Energy, 25, 35 ); - - SetSkill( SkillName.Tactics, 100 ); - SetSkill( SkillName.Wrestling, 100 ); - - Fame = 2000; - Karma = -2000; - - VirtualArmor = 50; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsAccessibleTo( from ) ) - { - if ( OpenedBy != null && Backpack != null ) - Backpack.DisplayTo( from ); - else - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1071917, from.NetState ); // * You attempt to tear open the amorphous flesh, but it resists * - } - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( IsAccessibleTo( from ) && ( dropped is PlagueBeastInnard || dropped is PlagueBeastGland ) ) - return base.OnDragDrop( from, dropped ); - - return false; - } - - public override void OnDeath( Container c ) - { - base.OnDeath( c ); - - for ( int i = c.Items.Count - 1; i >= 0; i-- ) - c.Items[ i ].Delete(); - } - - public override void OnDelete() - { - if ( OpenedBy?.Holding is PlagueBeastInnard ) - OpenedBy.Holding.Delete(); - - if ( Backpack != null ) - { - for ( int i = Backpack.Items.Count - 1; i >= 0; i-- ) - Backpack.Items[ i ].Delete(); - - Backpack.Delete(); - } - - base.OnDelete(); - } - - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); - - if ( Backpack != null && IsAccessibleTo( m ) && m.InRange( oldLocation, 3 ) && !m.InRange( this, 3 ) ) - Backpack.SendRemovePacket(); - } - - public override bool CheckNonlocalLift( Mobile from, Item item ) - { - return true; - } - - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - return true; - } - - public override bool IsSnoop( Mobile from ) - { - return false; - } - - public override int GetIdleSound() - { - return 0x1BF; - } - - public override int GetAttackSound() - { - return 0x1C0; - } - - public override int GetHurtSound() - { - return 0x1C1; - } - - public override int GetDeathSound() - { - return 0x1C2; - } - - public virtual void OnParalyzed( Mobile from ) - { - FightMode = FightMode.None; - Frozen = true; - Blessed = true; - Combatant = null; - Hue = 0x480; - from.Combatant = null; - from.Warmode = false; - - m_Timer = new DecayTimer( this ); - m_Timer.Start(); - - Timer.DelayCall( TimeSpan.Zero, BroadcastMessage ); - } - - private void BroadcastMessage() - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071920 ); // * The plague beast's amorphous flesh hardens and becomes immobilized * - } - - public virtual bool IsAccessibleTo( Mobile check ) - { - if ( check.AccessLevel >= AccessLevel.GameMaster ) - return true; - - if ( !InRange( check, 2 ) ) - PrivateOverheadMessage( MessageType.Label, 0x3B2, 500446, check.NetState ); // That is too far away. - else if ( OpenedBy != null && OpenedBy != check ) - PrivateOverheadMessage( MessageType.Label, 0x3B2, 500365, check.NetState ); // That is being used by someone else - else if ( Frozen ) - return true; - - return false; - } - - public virtual void Carve( Mobile from, Item item ) - { - if ( OpenedBy == null && IsAccessibleTo( from ) ) - { - OpenedBy = from; - - if ( m_Timer == null ) - m_Timer = new DecayTimer( this ); - - if ( !m_Timer.Running ) - m_Timer.Start(); - - m_Timer.StartDissolving(); - - PlagueBeastBackpack pack = new PlagueBeastBackpack(); - AddItem( pack ); - pack.Initialize(); - - foreach ( NetState state in GetClientsInRange( 12 ) ) - { - Mobile m = state.Mobile; - - if ( m != null && m.Player && m != from ) - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1071919, from.Name, m.NetState ); // * ~1_VAL~ slices through the plague beast's amorphous tissue * - } - - from.LocalOverheadMessage( MessageType.Regular, 0x21, 1071904 ); // * You slice through the plague beast's amorphous tissue * - Timer.DelayCall( TimeSpan.Zero, pack.Open, from ); - } - } - - public virtual bool Scissor( Mobile from, Scissors scissors ) - { - if ( IsAccessibleTo( from ) ) - scissors.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071918 ); // You can't cut through the plague beast's amorphous skin with scissors! - - return false; - } - - public void Unfreeze() - { - FightMode = FightMode.Closest; - Frozen = false; - Blessed = false; - - if ( OpenedBy == null ) - Hue = 0; - } - - public PlagueBeastLord( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.Write( OpenedBy ); - - if ( m_Timer != null ) - { - writer.Write( (bool) true ); - writer.Write( (int) m_Timer.Count ); - writer.Write( (int) m_Timer.Deadline ); - } - else - writer.Write( (bool) false ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - OpenedBy = reader.ReadMobile(); - - if ( reader.ReadBool() ) - { - int count = reader.ReadInt(); - int deadline = reader.ReadInt(); - - m_Timer = new DecayTimer( this, count, deadline ); - m_Timer.Start(); - } - - if ( FightMode == FightMode.None ) - Frozen = true; - } - - private class DecayTimer : Timer - { - private PlagueBeastLord m_Lord; - - public int Count { get; private set; } - - public int Deadline { get; private set; } - - public DecayTimer( PlagueBeastLord lord ) : this( lord, 0, 120 ) - { - } - - public DecayTimer( PlagueBeastLord lord, int count, int deadline ) : base( TimeSpan.Zero, TimeSpan.FromSeconds( 1 ) ) - { - m_Lord = lord; - Count = count; - Deadline = deadline; - } - - protected override void OnTick() - { - if ( m_Lord == null || m_Lord.Deleted ) - { - Stop(); - return; - } - - if ( Count + 15 == Deadline ) - { - if ( m_Lord.OpenedBy != null ) - m_Lord.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1071921 ); // * The plague beast begins to bubble and dissolve! * - - m_Lord.PlaySound( 0x103 ); - } - else if ( Count + 10 == Deadline ) - { - m_Lord.PlaySound( 0x21 ); - } - else if ( Count + 5 == Deadline ) - { - m_Lord.PlaySound( 0x1C2 ); - } - else if ( Count == Deadline ) - { - m_Lord.Unfreeze(); - - if ( m_Lord.OpenedBy != null ) - m_Lord.Kill(); - - Stop(); - } - else if ( Count % 15 == 0 ) - m_Lord.PlaySound( 0x1BF ); - - Count++; - } - - public void StartDissolving() - { - Deadline = Math.Min( Count + 60, Deadline ); - } - } - } -} + public class PlagueBeastLord : BaseCreature, ICarvable, IScissorable + { + private DecayTimer m_Timer; + + [Constructible] + public PlagueBeastLord() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 775; + BaseSoundID = 679; + SpeechHue = 0x3B2; + + SetStr(500); + SetDex(100); + SetInt(30); + + SetHits(1800); + + SetDamage(20, 25); + + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Fire, 25); + SetDamageType(ResistanceType.Poison, 25); + + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 75, 85); + SetResistance(ResistanceType.Energy, 25, 35); + + SetSkill(SkillName.Tactics, 100); + SetSkill(SkillName.Wrestling, 100); + + Fame = 2000; + Karma = -2000; + + VirtualArmor = 50; + } + + public PlagueBeastLord(Serial serial) : base(serial) + { + } + + public override string CorpseName => "a plague beast lord corpse"; + public override Poison PoisonImmune => Poison.Lethal; + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile OpenedBy{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsBleeding + { + get + { + Container pack = Backpack; + + if (pack != null) + for (int i = 0; i < pack.Items.Count; i++) + if (pack.Items[i] is PlagueBeastBlood blood && !blood.Patched) + return true; + + return false; + } + } + + public override string DefaultName => "a plague beast lord"; + + public virtual void Carve(Mobile from, Item item) + { + if (OpenedBy == null && IsAccessibleTo(from)) + { + OpenedBy = from; + + if (m_Timer == null) + m_Timer = new DecayTimer(this); + + if (!m_Timer.Running) + m_Timer.Start(); + + m_Timer.StartDissolving(); + + PlagueBeastBackpack pack = new PlagueBeastBackpack(); + AddItem(pack); + pack.Initialize(); + + foreach (NetState state in GetClientsInRange(12)) + { + Mobile m = state.Mobile; + + if (m != null && m.Player && m != from) + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1071919, from.Name, + m.NetState); // * ~1_VAL~ slices through the plague beast's amorphous tissue * + } + + from.LocalOverheadMessage(MessageType.Regular, 0x21, + 1071904); // * You slice through the plague beast's amorphous tissue * + Timer.DelayCall(TimeSpan.Zero, pack.Open, from); + } + } + + public virtual bool Scissor(Mobile from, Scissors scissors) + { + if (IsAccessibleTo(from)) + scissors.PublicOverheadMessage(MessageType.Regular, 0x3B2, + 1071918); // You can't cut through the plague beast's amorphous skin with scissors! + + return false; + } + + public override void OnDoubleClick(Mobile from) + { + if (IsAccessibleTo(from)) + { + if (OpenedBy != null && Backpack != null) + Backpack.DisplayTo(from); + else + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1071917, + from.NetState); // * You attempt to tear open the amorphous flesh, but it resists * + } + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (IsAccessibleTo(from) && (dropped is PlagueBeastInnard || dropped is PlagueBeastGland)) + return base.OnDragDrop(from, dropped); + + return false; + } + + public override void OnDeath(Container c) + { + base.OnDeath(c); + + for (int i = c.Items.Count - 1; i >= 0; i--) + c.Items[i].Delete(); + } + + public override void OnDelete() + { + if (OpenedBy?.Holding is PlagueBeastInnard) + OpenedBy.Holding.Delete(); + + if (Backpack != null) + { + for (int i = Backpack.Items.Count - 1; i >= 0; i--) + Backpack.Items[i].Delete(); + + Backpack.Delete(); + } + + base.OnDelete(); + } + + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); + + if (Backpack != null && IsAccessibleTo(m) && m.InRange(oldLocation, 3) && !m.InRange(this, 3)) + Backpack.SendRemovePacket(); + } + + public override bool CheckNonlocalLift(Mobile from, Item item) + { + return true; + } + + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + return true; + } + + public override bool IsSnoop(Mobile from) + { + return false; + } + + public override int GetIdleSound() + { + return 0x1BF; + } + + public override int GetAttackSound() + { + return 0x1C0; + } + + public override int GetHurtSound() + { + return 0x1C1; + } + + public override int GetDeathSound() + { + return 0x1C2; + } + + public virtual void OnParalyzed(Mobile from) + { + FightMode = FightMode.None; + Frozen = true; + Blessed = true; + Combatant = null; + Hue = 0x480; + from.Combatant = null; + from.Warmode = false; + + m_Timer = new DecayTimer(this); + m_Timer.Start(); + + Timer.DelayCall(TimeSpan.Zero, BroadcastMessage); + } + + private void BroadcastMessage() + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, + 1071920); // * The plague beast's amorphous flesh hardens and becomes immobilized * + } + + public virtual bool IsAccessibleTo(Mobile check) + { + if (check.AccessLevel >= AccessLevel.GameMaster) + return true; + + if (!InRange(check, 2)) + PrivateOverheadMessage(MessageType.Label, 0x3B2, 500446, check.NetState); // That is too far away. + else if (OpenedBy != null && OpenedBy != check) + PrivateOverheadMessage(MessageType.Label, 0x3B2, 500365, + check.NetState); // That is being used by someone else + else if (Frozen) + return true; + + return false; + } + + public void Unfreeze() + { + FightMode = FightMode.Closest; + Frozen = false; + Blessed = false; + + if (OpenedBy == null) + Hue = 0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.Write(OpenedBy); + + if (m_Timer != null) + { + writer.Write(true); + writer.Write(m_Timer.Count); + writer.Write(m_Timer.Deadline); + } + else + { + writer.Write(false); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + OpenedBy = reader.ReadMobile(); + + if (reader.ReadBool()) + { + int count = reader.ReadInt(); + int deadline = reader.ReadInt(); + + m_Timer = new DecayTimer(this, count, deadline); + m_Timer.Start(); + } + + if (FightMode == FightMode.None) + Frozen = true; + } + + private class DecayTimer : Timer + { + private PlagueBeastLord m_Lord; + + public DecayTimer(PlagueBeastLord lord) : this(lord, 0, 120) + { + } + + public DecayTimer(PlagueBeastLord lord, int count, int deadline) : base(TimeSpan.Zero, TimeSpan.FromSeconds(1)) + { + m_Lord = lord; + Count = count; + Deadline = deadline; + } + + public int Count{ get; private set; } + + public int Deadline{ get; private set; } + + protected override void OnTick() + { + if (m_Lord == null || m_Lord.Deleted) + { + Stop(); + return; + } + + if (Count + 15 == Deadline) + { + if (m_Lord.OpenedBy != null) + m_Lord.PublicOverheadMessage(MessageType.Regular, 0x3B2, + 1071921); // * The plague beast begins to bubble and dissolve! * + + m_Lord.PlaySound(0x103); + } + else if (Count + 10 == Deadline) + { + m_Lord.PlaySound(0x21); + } + else if (Count + 5 == Deadline) + { + m_Lord.PlaySound(0x1C2); + } + else if (Count == Deadline) + { + m_Lord.Unfreeze(); + + if (m_Lord.OpenedBy != null) + m_Lord.Kill(); + + Stop(); + } + else if (Count % 15 == 0) + { + m_Lord.PlaySound(0x1BF); + } + + Count++; + } + + public void StartDissolving() + { + Deadline = Math.Min(Count + 60, Deadline); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/PlagueSpawn.cs b/Scripts/Mobiles/Monsters/Misc/Melee/PlagueSpawn.cs index 363ea89b4..fc4697473 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/PlagueSpawn.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/PlagueSpawn.cs @@ -4,134 +4,132 @@ using Server.ContextMenus; namespace Server.Mobiles { - public class PlagueSpawn : BaseCreature - { - public override string CorpseName => "a plague spawn corpse"; + public class PlagueSpawn : BaseCreature + { + [Constructible] + public PlagueSpawn() : this(null) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } + public PlagueSpawn(Mobile owner) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Owner = owner; + ExpireTime = DateTime.UtcNow + TimeSpan.FromMinutes(1.0); - [CommandProperty( AccessLevel.GameMaster )] - public DateTime ExpireTime { get; set; } + Hue = Utility.Random(0x11, 15); - [Constructible] - public PlagueSpawn() : this( null ) - { - } + switch (Utility.Random(12)) + { + case 0: // earth elemental + Body = 14; + BaseSoundID = 268; + break; + case 1: // headless one + Body = 31; + BaseSoundID = 0x39D; + break; + case 2: // person + Body = Utility.RandomList(400, 401); + break; + case 3: // gorilla + Body = 0x1D; + BaseSoundID = 0x9E; + break; + case 4: // serpent + Body = 0x15; + BaseSoundID = 0xDB; + break; + default: + case 5: // slime + Body = 51; + BaseSoundID = 456; + break; + } - public override bool AlwaysMurderer => true; + SetStr(201, 300); + SetDex(80); + SetInt(16, 20); - public override void DisplayPaperdollTo(Mobile to) - { - } + SetHits(121, 180); - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + SetDamage(11, 17); - for ( int i = 0; i < list.Count; ++i ) - { - if ( list[i] is PaperdollEntry ) - list.RemoveAt( i-- ); - } - } + SetDamageType(ResistanceType.Physical, 100); - public override void OnThink() - { - if ( Owner != null && ( DateTime.UtcNow >= ExpireTime || Owner.Deleted || Map != Owner.Map || !InRange( Owner, 16 ) ) ) - { - PlaySound( GetIdleSound() ); - Delete(); - } - else - { - base.OnThink(); - } - } + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 65, 75); + SetResistance(ResistanceType.Energy, 25, 35); - public override string DefaultName => "a plague spawn"; + SetSkill(SkillName.MagicResist, 25.0); + SetSkill(SkillName.Tactics, 25.0); + SetSkill(SkillName.Wrestling, 50.0); - public PlagueSpawn( Mobile owner ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Owner = owner; - ExpireTime = DateTime.UtcNow + TimeSpan.FromMinutes( 1.0 ); + Fame = 1000; + Karma = -1000; - Hue = Utility.Random( 0x11, 15 ); + VirtualArmor = 20; + } - switch ( Utility.Random( 12 ) ) - { - case 0: // earth elemental - Body = 14; - BaseSoundID = 268; - break; - case 1: // headless one - Body = 31; - BaseSoundID = 0x39D; - break; - case 2: // person - Body = Utility.RandomList( 400, 401 ); - break; - case 3: // gorilla - Body = 0x1D; - BaseSoundID = 0x9E; - break; - case 4: // serpent - Body = 0x15; - BaseSoundID = 0xDB; - break; - default: - case 5: // slime - Body = 51; - BaseSoundID = 456; - break; - } + public PlagueSpawn(Serial serial) : base(serial) + { + } - SetStr( 201, 300 ); - SetDex( 80 ); - SetInt( 16, 20 ); + public override string CorpseName => "a plague spawn corpse"; - SetHits( 121, 180 ); + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } - SetDamage( 11, 17 ); + [CommandProperty(AccessLevel.GameMaster)] + public DateTime ExpireTime{ get; set; } - SetDamageType( ResistanceType.Physical, 100 ); + public override bool AlwaysMurderer => true; - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 65, 75 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + public override string DefaultName => "a plague spawn"; - SetSkill( SkillName.MagicResist, 25.0 ); - SetSkill( SkillName.Tactics, 25.0 ); - SetSkill( SkillName.Wrestling, 50.0 ); + public override void DisplayPaperdollTo(Mobile to) + { + } - Fame = 1000; - Karma = -1000; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - VirtualArmor = 20; - } + for (int i = 0; i < list.Count; ++i) + if (list[i] is PaperdollEntry) + list.RemoveAt(i--); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - AddLoot( LootPack.Gems ); - } + public override void OnThink() + { + if (Owner != null && (DateTime.UtcNow >= ExpireTime || Owner.Deleted || Map != Owner.Map || !InRange(Owner, 16))) + { + PlaySound(GetIdleSound()); + Delete(); + } + else + { + base.OnThink(); + } + } - public PlagueSpawn( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + AddLoot(LootPack.Gems); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/SandVortex.cs b/Scripts/Mobiles/Monsters/Misc/Melee/SandVortex.cs index eae54cd2e..3a062b50f 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/SandVortex.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/SandVortex.cs @@ -3,109 +3,110 @@ using Server.Items; namespace Server.Mobiles { - public class SandVortex : BaseCreature - { - public override string CorpseName => "a sand vortex corpse"; - public override string DefaultName => "a sand vortex"; + public class SandVortex : BaseCreature + { + private DateTime m_NextAttack; - [Constructible] - public SandVortex() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 790; - BaseSoundID = 263; + [Constructible] + public SandVortex() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 790; + BaseSoundID = 263; - SetStr( 96, 120 ); - SetDex( 171, 195 ); - SetInt( 76, 100 ); + SetStr(96, 120); + SetDex(171, 195); + SetInt(76, 100); - SetHits( 51, 62 ); + SetHits(51, 62); - SetDamage( 3, 16 ); + SetDamage(3, 16); - SetDamageType( ResistanceType.Physical, 90 ); - SetDamageType( ResistanceType.Fire, 10 ); + SetDamageType(ResistanceType.Physical, 90); + SetDamageType(ResistanceType.Fire, 10); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 60, 70 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 60, 70); - SetSkill( SkillName.MagicResist, 150.0 ); - SetSkill( SkillName.Tactics, 70.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + SetSkill(SkillName.MagicResist, 150.0); + SetSkill(SkillName.Tactics, 70.0); + SetSkill(SkillName.Wrestling, 80.0); - Fame = 4500; - Karma = -4500; + Fame = 4500; + Karma = -4500; - VirtualArmor = 28; - PackItem( new Bone() ); - } + VirtualArmor = 28; + PackItem(new Bone()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager, 2 ); - } + public SandVortex(Serial serial) : base(serial) + { + } - private DateTime m_NextAttack; + public override string CorpseName => "a sand vortex corpse"; + public override string DefaultName => "a sand vortex"; - public override void OnActionCombat() - { - Mobile combatant = Combatant; + public override void GenerateLoot() + { + AddLoot(LootPack.Meager, 2); + } - if ( combatant == null || combatant.Deleted || combatant.Map != Map || !InRange( combatant, 12 ) || !CanBeHarmful( combatant ) || !InLOS( combatant ) ) - return; + public override void OnActionCombat() + { + Mobile combatant = Combatant; - if ( DateTime.UtcNow >= m_NextAttack ) - { - SandAttack( combatant ); - m_NextAttack = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 + (10.0 * Utility.RandomDouble()) ); - } - } + if (combatant == null || combatant.Deleted || combatant.Map != Map || !InRange(combatant, 12) || + !CanBeHarmful(combatant) || !InLOS(combatant)) + return; - public void SandAttack( Mobile m ) - { - DoHarmful( m ); + if (DateTime.UtcNow >= m_NextAttack) + { + SandAttack(combatant); + m_NextAttack = DateTime.UtcNow + TimeSpan.FromSeconds(10.0 + 10.0 * Utility.RandomDouble()); + } + } - m.FixedParticles( 0x36B0, 10, 25, 9540, 2413, 0, EffectLayer.Waist ); + public void SandAttack(Mobile m) + { + DoHarmful(m); - new InternalTimer( m, this ).Start(); - } + m.FixedParticles(0x36B0, 10, 25, 9540, 2413, 0, EffectLayer.Waist); - private class InternalTimer : Timer - { - private Mobile m_Mobile, m_From; + new InternalTimer(m, this).Start(); + } - public InternalTimer( Mobile m, Mobile from ) : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_From = from; - Priority = TimerPriority.TwoFiftyMS; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - protected override void OnTick() - { - m_Mobile.PlaySound( 0x4CF ); - AOS.Damage( m_Mobile, m_From, Utility.RandomMinMax( 1, 40 ), 90, 10, 0, 0, 0 ); - } - } + writer.Write(0); // version + } - public SandVortex( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); + } - writer.Write( (int) 0 ); // version - } + private class InternalTimer : Timer + { + private Mobile m_Mobile, m_From; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public InternalTimer(Mobile m, Mobile from) : base(TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_From = from; + Priority = TimerPriority.TwoFiftyMS; + } - int version = reader.ReadInt(); - } - } -} + protected override void OnTick() + { + m_Mobile.PlaySound(0x4CF); + AOS.Damage(m_Mobile, m_From, Utility.RandomMinMax(1, 40), 90, 10, 0, 0, 0); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Misc/Melee/Slime.cs b/Scripts/Mobiles/Monsters/Misc/Melee/Slime.cs index f74145e40..9b00bd4af 100644 --- a/Scripts/Mobiles/Monsters/Misc/Melee/Slime.cs +++ b/Scripts/Mobiles/Monsters/Misc/Melee/Slime.cs @@ -1,70 +1,72 @@ namespace Server.Mobiles { - public class Slime : BaseCreature - { - public override string CorpseName => "a slimey corpse"; - public override string DefaultName => "a slime"; + public class Slime : BaseCreature + { + [Constructible] + public Slime() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 51; + BaseSoundID = 456; - [Constructible] - public Slime() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 51; - BaseSoundID = 456; + Hue = Utility.RandomSlimeHue(); - Hue = Utility.RandomSlimeHue(); + SetStr(22, 34); + SetDex(16, 21); + SetInt(16, 20); - SetStr( 22, 34 ); - SetDex( 16, 21 ); - SetInt( 16, 20 ); + SetHits(15, 19); - SetHits( 15, 19 ); + SetDamage(1, 5); - SetDamage( 1, 5 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 5, 10); + SetResistance(ResistanceType.Poison, 10, 20); - SetResistance( ResistanceType.Physical, 5, 10 ); - SetResistance( ResistanceType.Poison, 10, 20 ); + SetSkill(SkillName.Poisoning, 30.1, 50.0); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 19.3, 34.0); + SetSkill(SkillName.Wrestling, 19.3, 34.0); - SetSkill( SkillName.Poisoning, 30.1, 50.0 ); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 19.3, 34.0 ); - SetSkill( SkillName.Wrestling, 19.3, 34.0 ); + Fame = 300; + Karma = -300; - Fame = 300; - Karma = -300; + VirtualArmor = 8; - VirtualArmor = 8; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 23.1; + } - Tamable = true; - ControlSlots = 1; - MinTameSkill = 23.1; - } + public Slime(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Poor ); - AddLoot( LootPack.Gems ); - } + public override string CorpseName => "a slimey corpse"; + public override string DefaultName => "a slime"; - public override Poison PoisonImmune => Poison.Lesser; - public override Poison HitPoison => Poison.Lesser; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish | FoodType.FruitsAndVegies | FoodType.GrainsAndHay | FoodType.Eggs; + public override Poison PoisonImmune => Poison.Lesser; + public override Poison HitPoison => Poison.Lesser; - public Slime( Serial serial ) : base( serial ) - { - } + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish | FoodType.FruitsAndVegies | + FoodType.GrainsAndHay | FoodType.Eggs; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Poor); + AddLoot(LootPack.Gems); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/AgapiteElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/AgapiteElemental.cs index 6859e0549..96ed6b501 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/AgapiteElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/AgapiteElemental.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class AgapiteElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "an agapite elemental"; + public class AgapiteElemental : BaseCreature + { + [Constructible] + public AgapiteElemental() : this(2) + { + } - [Constructible] - public AgapiteElemental() : this( 2 ) - { - } + [Constructible] + public AgapiteElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 107; + BaseSoundID = 268; - [Constructible] - public AgapiteElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 107; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(28); - SetDamage( 28 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 32; - VirtualArmor = 32; + Item ore = new AgapiteOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new AgapiteOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public AgapiteElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "an agapite elemental"; - public override bool BleedImmune => true; - public override bool AutoDispel => true; - public override int TreasureMapLevel => 1; + public override bool BleedImmune => true; + public override bool AutoDispel => true; + public override int TreasureMapLevel => 1; - public AgapiteElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/BronzeElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/BronzeElemental.cs index 202cbb41c..3f57cff16 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/BronzeElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/BronzeElemental.cs @@ -2,78 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class BronzeElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a bronze elemental"; + public class BronzeElemental : BaseCreature + { + [Constructible] + public BronzeElemental() : this(2) + { + } - [Constructible] - public BronzeElemental() : this( 2 ) - { - } + [Constructible] + public BronzeElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + // TODO: Gas attack + Body = 108; + BaseSoundID = 268; - [Constructible] - public BronzeElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - // TODO: Gas attack - Body = 108; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(9, 16); - SetDamage( 9, 16 ); + SetDamageType(ResistanceType.Physical, 30); + SetDamageType(ResistanceType.Fire, 70); - SetDamageType( ResistanceType.Physical, 30 ); - SetDamageType( ResistanceType.Fire, 70 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 70, 80); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 70, 80 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + VirtualArmor = 29; - VirtualArmor = 29; + Item ore = new BronzeOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new BronzeOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public BronzeElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a bronze elemental"; - public override bool BleedImmune => true; - public override bool AutoDispel => true; - public override int TreasureMapLevel => 1; + public override bool BleedImmune => true; + public override bool AutoDispel => true; + public override int TreasureMapLevel => 1; - public BronzeElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/CopperElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/CopperElemental.cs index 782dca8e4..35bf90d39 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/CopperElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/CopperElemental.cs @@ -2,81 +2,81 @@ using Server.Items; namespace Server.Mobiles { - public class CopperElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a copper elemental"; + public class CopperElemental : BaseCreature + { + [Constructible] + public CopperElemental() : this(2) + { + } - [Constructible] - public CopperElemental() : this( 2 ) - { - } + [Constructible] + public CopperElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 109; + BaseSoundID = 268; - [Constructible] - public CopperElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 109; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(9, 16); - SetDamage( 9, 16 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 4800; + Karma = -4800; - Fame = 4800; - Karma = -4800; + VirtualArmor = 26; - VirtualArmor = 26; + Item ore = new CopperOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new CopperOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public CopperElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a copper elemental"; - public override bool BleedImmune => true; - public override bool AutoDispel => true; - public override int TreasureMapLevel => 1; + public override bool BleedImmune => true; + public override bool AutoDispel => true; + public override int TreasureMapLevel => 1; - public override void CheckReflect( Mobile caster, ref bool reflect ) - { - reflect = true; // Every spell is reflected back to the caster - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public CopperElemental( Serial serial ) : base( serial ) - { - } + public override void CheckReflect(Mobile caster, ref bool reflect) + { + reflect = true; // Every spell is reflected back to the caster + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/DullCopperElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/DullCopperElemental.cs index b4c9694ed..cc4ec0d86 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/DullCopperElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/DullCopperElemental.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class DullCopperElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a dull copper elemental"; + public class DullCopperElemental : BaseCreature + { + [Constructible] + public DullCopperElemental() : this(2) + { + } - [Constructible] - public DullCopperElemental() : this( 2 ) - { - } + [Constructible] + public DullCopperElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 110; + BaseSoundID = 268; - [Constructible] - public DullCopperElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 110; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(9, 16); - SetDamage( 9, 16 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 20; - VirtualArmor = 20; + Item ore = new DullCopperOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new DullCopperOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public DullCopperElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a dull copper elemental"; - public override bool AutoDispel => true; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; + public override bool AutoDispel => true; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; - public DullCopperElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/GoldenElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/GoldenElemental.cs index 6c32a3ef0..1848d76c6 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/GoldenElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/GoldenElemental.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class GoldenElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a golden elemental"; + public class GoldenElemental : BaseCreature + { + [Constructible] + public GoldenElemental() : this(2) + { + } - [Constructible] - public GoldenElemental() : this( 2 ) - { - } + [Constructible] + public GoldenElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 166; + BaseSoundID = 268; - [Constructible] - public GoldenElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 166; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(9, 16); - SetDamage( 9, 16 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 60, 75); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 60, 75 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 60; - VirtualArmor = 60; + Item ore = new GoldOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new GoldOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public GoldenElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a golden elemental"; - public override bool AutoDispel => true; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; + public override bool AutoDispel => true; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; - public GoldenElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/ShadowIronElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/ShadowIronElemental.cs index dbae9c848..c7d313843 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/ShadowIronElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/ShadowIronElemental.cs @@ -2,96 +2,94 @@ using Server.Items; namespace Server.Mobiles { - public class ShadowIronElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a shadow iron elemental"; + public class ShadowIronElemental : BaseCreature + { + [Constructible] + public ShadowIronElemental() : this(2) + { + } - [Constructible] - public ShadowIronElemental() : this( 2 ) - { - } + [Constructible] + public ShadowIronElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 111; + BaseSoundID = 268; - [Constructible] - public ShadowIronElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 111; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(9, 16); - SetDamage( 9, 16 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 10, 20); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 10, 20 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 4500; + Karma = -4500; - Fame = 4500; - Karma = -4500; + VirtualArmor = 23; - VirtualArmor = 23; + Item ore = new ShadowIronOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new ShadowIronOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public ShadowIronElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a shadow iron elemental"; - public override bool AutoDispel => true; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; - public override Poison PoisonImmune => Poison.Deadly; - public override bool BreathImmune => true; + public override bool AutoDispel => true; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; + public override Poison PoisonImmune => Poison.Deadly; + public override bool BreathImmune => true; - public override void AlterMeleeDamageFrom( Mobile from, ref int damage ) - { - if ( from is BaseCreature bc && (bc.Controlled || bc.BardTarget == this) ) - { - damage = 0; // Immune to pets and provoked creatures - } - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, 2); + } - public override void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - scalar = 0.0; // Immune to magic - } + public override void AlterMeleeDamageFrom(Mobile from, ref int damage) + { + if (from is BaseCreature bc && (bc.Controlled || bc.BardTarget == this)) + damage = 0; // Immune to pets and provoked creatures + } - public override void AlterSpellDamageFrom( Mobile from, ref int damage ) - { - damage = 0; - } + public override void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + scalar = 0.0; // Immune to magic + } - public ShadowIronElemental( Serial serial ) : base( serial ) - { - } + public override void AlterSpellDamageFrom(Mobile from, ref int damage) + { + damage = 0; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/ValoriteElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/ValoriteElemental.cs index 3651aba03..5338526fc 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/ValoriteElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/ValoriteElemental.cs @@ -2,94 +2,92 @@ using Server.Items; namespace Server.Mobiles { - public class ValoriteElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a valorite elemental"; + public class ValoriteElemental : BaseCreature + { + [Constructible] + public ValoriteElemental() : this(2) + { + } - [Constructible] - public ValoriteElemental() : this( 2 ) - { - } + [Constructible] + public ValoriteElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + // TODO: Gas attack + Body = 112; + BaseSoundID = 268; - [Constructible] - public ValoriteElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - // TODO: Gas attack - Body = 112; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(28); - SetDamage( 28 ); + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Fire, 25); + SetDamageType(ResistanceType.Cold, 25); + SetDamageType(ResistanceType.Energy, 25); - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Fire, 25 ); - SetDamageType( ResistanceType.Cold, 25 ); - SetDamageType( ResistanceType.Energy, 25 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 38; - VirtualArmor = 38; + Item ore = new ValoriteOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new ValoriteOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public ValoriteElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Gems, 4 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a valorite elemental"; - public override bool AutoDispel => true; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; + public override bool AutoDispel => true; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; - public override void AlterMeleeDamageFrom( Mobile from, ref int damage ) - { - if ( from is BaseCreature bc ) - { - if ( bc.Controlled || bc.BardTarget == this ) - damage = 0; // Immune to pets and provoked creatures - } - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Gems, 4); + } - public override void CheckReflect( Mobile caster, ref bool reflect ) - { - reflect = true; // Every spell is reflected back to the caster - } + public override void AlterMeleeDamageFrom(Mobile from, ref int damage) + { + if (from is BaseCreature bc) + if (bc.Controlled || bc.BardTarget == this) + damage = 0; // Immune to pets and provoked creatures + } - public ValoriteElemental( Serial serial ) : base( serial ) - { - } + public override void CheckReflect(Mobile caster, ref bool reflect) + { + reflect = true; // Every spell is reflected back to the caster + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Ore Elementals/VeriteElemental.cs b/Scripts/Mobiles/Monsters/Ore Elementals/VeriteElemental.cs index b3d84a26d..373fb9c63 100644 --- a/Scripts/Mobiles/Monsters/Ore Elementals/VeriteElemental.cs +++ b/Scripts/Mobiles/Monsters/Ore Elementals/VeriteElemental.cs @@ -2,77 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class VeriteElemental : BaseCreature - { - public override string CorpseName => "an ore elemental corpse"; - public override string DefaultName => "a verite elemental"; + public class VeriteElemental : BaseCreature + { + [Constructible] + public VeriteElemental() : this(2) + { + } - [Constructible] - public VeriteElemental() : this( 2 ) - { - } + [Constructible] + public VeriteElemental(int oreAmount) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 113; + BaseSoundID = 268; - [Constructible] - public VeriteElemental( int oreAmount ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 113; - BaseSoundID = 268; + SetStr(226, 255); + SetDex(126, 145); + SetInt(71, 92); - SetStr( 226, 255 ); - SetDex( 126, 145 ); - SetInt( 71, 92 ); + SetHits(136, 153); - SetHits( 136, 153 ); + SetDamage(9, 16); - SetDamage( 9, 16 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.MagicResist, 50.1, 95.0); + SetSkill(SkillName.Tactics, 60.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 95.0 ); - SetSkill( SkillName.Tactics, 60.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 100.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 35; - VirtualArmor = 35; + Item ore = new VeriteOre(oreAmount); + ore.ItemID = 0x19B9; + PackItem(ore); + } - Item ore = new VeriteOre( oreAmount ); - ore.ItemID = 0x19B9; - PackItem( ore ); - } + public VeriteElemental(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "an ore elemental corpse"; + public override string DefaultName => "a verite elemental"; - public override bool AutoDispel => true; - public override bool BleedImmune => true; - public override int TreasureMapLevel => 1; + public override bool AutoDispel => true; + public override bool BleedImmune => true; + public override int TreasureMapLevel => 1; - public VeriteElemental( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Magic/Reaper.cs b/Scripts/Mobiles/Monsters/Plant/Magic/Reaper.cs index 197cf946b..65a30b2d5 100644 --- a/Scripts/Mobiles/Monsters/Plant/Magic/Reaper.cs +++ b/Scripts/Mobiles/Monsters/Plant/Magic/Reaper.cs @@ -2,73 +2,73 @@ using Server.Items; namespace Server.Mobiles { - public class Reaper : BaseCreature - { - public override string CorpseName => "a reapers corpse"; - public override string DefaultName => "a reaper"; + public class Reaper : BaseCreature + { + [Constructible] + public Reaper() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 47; + BaseSoundID = 442; - [Constructible] - public Reaper() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 47; - BaseSoundID = 442; + SetStr(66, 215); + SetDex(66, 75); + SetInt(101, 250); - SetStr( 66, 215 ); - SetDex( 66, 75 ); - SetInt( 101, 250 ); + SetHits(40, 129); + SetStam(0); - SetHits( 40, 129 ); - SetStam( 0 ); + SetDamage(9, 11); - SetDamage( 9, 11 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Poison, 20); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Poison, 20 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 100.1, 125.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 50.1, 60.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 100.1, 125.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 50.1, 60.0 ); + Fame = 3500; + Karma = -3500; - Fame = 3500; - Karma = -3500; + VirtualArmor = 40; - VirtualArmor = 40; + PackItem(new Log(10)); + PackItem(new MandrakeRoot(5)); + } - PackItem( new Log( 10 ) ); - PackItem( new MandrakeRoot( 5 ) ); - } + public Reaper(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a reapers corpse"; + public override string DefaultName => "a reaper"; - public override Poison PoisonImmune => Poison.Greater; - public override int TreasureMapLevel => 2; - public override bool DisallowAllMoves => true; + public override Poison PoisonImmune => Poison.Greater; + public override int TreasureMapLevel => 2; + public override bool DisallowAllMoves => true; - public Reaper( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Melee/BogThing.cs b/Scripts/Mobiles/Monsters/Plant/Melee/BogThing.cs index 277360c01..c25325544 100644 --- a/Scripts/Mobiles/Monsters/Plant/Melee/BogThing.cs +++ b/Scripts/Mobiles/Monsters/Plant/Melee/BogThing.cs @@ -1,144 +1,143 @@ using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class BogThing : BaseCreature - { - public override string CorpseName => "a plant corpse"; - public override string DefaultName => "a bog thing"; + public class BogThing : BaseCreature + { + [Constructible] + public BogThing() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.6, 1.2) + { + Body = 780; - [Constructible] - public BogThing() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.6, 1.2 ) - { - Body = 780; + SetStr(801, 900); + SetDex(46, 65); + SetInt(36, 50); - SetStr( 801, 900 ); - SetDex( 46, 65 ); - SetInt( 36, 50 ); + SetHits(481, 540); + SetMana(0); - SetHits( 481, 540 ); - SetMana( 0 ); + SetDamage(10, 23); - SetDamage( 10, 23 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 20, 25); + SetResistance(ResistanceType.Cold, 10, 15); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 20, 25); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 20, 25 ); - SetResistance( ResistanceType.Cold, 10, 15 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 20, 25 ); + SetSkill(SkillName.MagicResist, 90.1, 95.0); + SetSkill(SkillName.Tactics, 70.1, 85.0); + SetSkill(SkillName.Wrestling, 65.1, 80.0); - SetSkill( SkillName.MagicResist, 90.1, 95.0 ); - SetSkill( SkillName.Tactics, 70.1, 85.0 ); - SetSkill( SkillName.Wrestling, 65.1, 80.0 ); + Fame = 8000; + Karma = -8000; - Fame = 8000; - Karma = -8000; + VirtualArmor = 28; - VirtualArmor = 28; + if (0.25 > Utility.RandomDouble()) + PackItem(new Board(10)); + else + PackItem(new Log(10)); - if ( 0.25 > Utility.RandomDouble() ) - PackItem( new Board( 10 ) ); - else - PackItem( new Log( 10 ) ); + PackReg(3); + PackItem(new Seed()); + PackItem(new Seed()); + } - PackReg( 3 ); - PackItem( new Engines.Plants.Seed() ); - PackItem( new Engines.Plants.Seed() ); - } + public BogThing(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - } + public override string CorpseName => "a plant corpse"; + public override string DefaultName => "a bog thing"; - public override bool BardImmune => !Core.AOS; - public override Poison PoisonImmune => Poison.Lethal; + public override bool BardImmune => !Core.AOS; + public override Poison PoisonImmune => Poison.Lethal; - public BogThing( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - public void SpawnBogling( Mobile m ) - { - Map map = Map; + public void SpawnBogling(Mobile m) + { + Map map = Map; - if ( map == null ) - return; + if (map == null) + return; - Bogling spawned = new Bogling(); + Bogling spawned = new Bogling(); - spawned.Team = Team; + spawned.Team = Team; - bool validLocation = false; - Point3D loc = Location; + bool validLocation = false; + Point3D loc = Location; - for ( int j = 0; !validLocation && j < 10; ++j ) - { - int x = X + Utility.Random( 3 ) - 1; - int y = Y + Utility.Random( 3 ) - 1; - int z = map.GetAverageZ( x, y ); + for (int j = 0; !validLocation && j < 10; ++j) + { + int x = X + Utility.Random(3) - 1; + int y = Y + Utility.Random(3) - 1; + int z = map.GetAverageZ(x, y); - if ( validLocation = map.CanFit( x, y, Z, 16, false, false ) ) - loc = new Point3D( x, y, Z ); - else if ( validLocation = map.CanFit( x, y, z, 16, false, false ) ) - loc = new Point3D( x, y, z ); - } + if (validLocation = map.CanFit(x, y, Z, 16, false, false)) + loc = new Point3D(x, y, Z); + else if (validLocation = map.CanFit(x, y, z, 16, false, false)) + loc = new Point3D(x, y, z); + } - spawned.MoveToWorld( loc, map ); - spawned.Combatant = m; - } + spawned.MoveToWorld(loc, map); + spawned.Combatant = m; + } - public void EatBoglings() - { - ArrayList toEat = new ArrayList(); + public void EatBoglings() + { + ArrayList toEat = new ArrayList(); - foreach ( Mobile m in GetMobilesInRange( 2 ) ) - { - if ( m is Bogling ) - toEat.Add( m ); - } + foreach (Mobile m in GetMobilesInRange(2)) + if (m is Bogling) + toEat.Add(m); - if ( toEat.Count > 0 ) - { - PlaySound( Utility.Random( 0x3B, 2 ) ); // Eat sound + if (toEat.Count > 0) + { + PlaySound(Utility.Random(0x3B, 2)); // Eat sound - foreach ( Mobile m in toEat ) - { - Hits += (m.Hits / 2); - m.Delete(); - } - } - } + foreach (Mobile m in toEat) + { + Hits += m.Hits / 2; + m.Delete(); + } + } + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - if ( Hits > (HitsMax / 4) ) - { - if ( 0.25 >= Utility.RandomDouble() ) - SpawnBogling( attacker ); - } - else if ( 0.25 >= Utility.RandomDouble() ) - { - EatBoglings(); - } - } - } -} + if (Hits > HitsMax / 4) + { + if (0.25 >= Utility.RandomDouble()) + SpawnBogling(attacker); + } + else if (0.25 >= Utility.RandomDouble()) + { + EatBoglings(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Melee/Bogling.cs b/Scripts/Mobiles/Monsters/Plant/Melee/Bogling.cs index fb2889019..260947de6 100644 --- a/Scripts/Mobiles/Monsters/Plant/Melee/Bogling.cs +++ b/Scripts/Mobiles/Monsters/Plant/Melee/Bogling.cs @@ -1,69 +1,70 @@ +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class Bogling : BaseCreature - { - public override string CorpseName => "a plant corpse"; - public override string DefaultName => "a bogling"; + public class Bogling : BaseCreature + { + [Constructible] + public Bogling() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 779; + BaseSoundID = 422; - [Constructible] - public Bogling() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 779; - BaseSoundID = 422; + SetStr(96, 120); + SetDex(91, 115); + SetInt(21, 45); - SetStr( 96, 120 ); - SetDex( 91, 115 ); - SetInt( 21, 45 ); + SetHits(58, 72); - SetHits( 58, 72 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 15, 25); + SetResistance(ResistanceType.Energy, 15, 25); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 15, 25 ); - SetResistance( ResistanceType.Energy, 15, 25 ); + SetSkill(SkillName.MagicResist, 75.1, 100.0); + SetSkill(SkillName.Tactics, 55.1, 80.0); + SetSkill(SkillName.Wrestling, 55.1, 75.0); - SetSkill( SkillName.MagicResist, 75.1, 100.0 ); - SetSkill( SkillName.Tactics, 55.1, 80.0 ); - SetSkill( SkillName.Wrestling, 55.1, 75.0 ); + Fame = 450; + Karma = -450; - Fame = 450; - Karma = -450; + VirtualArmor = 28; - VirtualArmor = 28; + PackItem(new Log(4)); + PackItem(new Seed()); + } - PackItem( new Log( 4 ) ); - PackItem( new Engines.Plants.Seed() ); - } + public Bogling(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a plant corpse"; + public override string DefaultName => "a bogling"; - public override int Hides => 6; - public override int Meat => 1; + public override int Hides => 6; + public override int Meat => 1; - public Bogling( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Melee/Corpser.cs b/Scripts/Mobiles/Monsters/Plant/Melee/Corpser.cs index 5227e9cec..097f05ba2 100644 --- a/Scripts/Mobiles/Monsters/Plant/Melee/Corpser.cs +++ b/Scripts/Mobiles/Monsters/Plant/Melee/Corpser.cs @@ -2,76 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class Corpser : BaseCreature - { - public override string CorpseName => "a corpser corpse"; - public override string DefaultName => "a corpser"; + public class Corpser : BaseCreature + { + [Constructible] + public Corpser() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 8; + BaseSoundID = 684; - [Constructible] - public Corpser() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 8; - BaseSoundID = 684; + SetStr(156, 180); + SetDex(26, 45); + SetInt(26, 40); - SetStr( 156, 180 ); - SetDex( 26, 45 ); - SetInt( 26, 40 ); + SetHits(94, 108); + SetMana(0); - SetHits( 94, 108 ); - SetMana( 0 ); + SetDamage(10, 23); - SetDamage( 10, 23 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetResistance(ResistanceType.Physical, 15, 20); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 20, 30); - SetResistance( ResistanceType.Physical, 15, 20 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 20, 30 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 60.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 60.0 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + VirtualArmor = 18; - VirtualArmor = 18; + if (0.25 > Utility.RandomDouble()) + PackItem(new Board(10)); + else + PackItem(new Log(10)); - if ( 0.25 > Utility.RandomDouble() ) - PackItem( new Board( 10 ) ); - else - PackItem( new Log( 10 ) ); + PackItem(new MandrakeRoot(3)); + } - PackItem( new MandrakeRoot( 3 ) ); - } + public Corpser(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a corpser corpse"; + public override string DefaultName => "a corpser"; - public override Poison PoisonImmune => Poison.Lesser; - public override bool DisallowAllMoves => true; + public override Poison PoisonImmune => Poison.Lesser; + public override bool DisallowAllMoves => true; - public Corpser( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 352 ) - BaseSoundID = 684; - } - } -} + if (BaseSoundID == 352) + BaseSoundID = 684; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Melee/Quagmire.cs b/Scripts/Mobiles/Monsters/Plant/Melee/Quagmire.cs index 1e41f644f..085174fe2 100644 --- a/Scripts/Mobiles/Monsters/Plant/Melee/Quagmire.cs +++ b/Scripts/Mobiles/Monsters/Plant/Melee/Quagmire.cs @@ -1,74 +1,74 @@ namespace Server.Mobiles { - public class Quagmire : BaseCreature - { - public override string CorpseName => "a quagmire corpse"; - public override string DefaultName => "a quagmire"; + public class Quagmire : BaseCreature + { + [Constructible] + public Quagmire() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8) + { + Body = 789; + BaseSoundID = 352; - [Constructible] - public Quagmire() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.4, 0.8 ) - { - Body = 789; - BaseSoundID = 352; + SetStr(101, 130); + SetDex(66, 85); + SetInt(31, 55); - SetStr( 101, 130 ); - SetDex( 66, 85 ); - SetInt( 31, 55 ); + SetHits(91, 105); - SetHits( 91, 105 ); + SetDamage(10, 14); - SetDamage( 10, 14 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 20, 30); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetSkill(SkillName.MagicResist, 65.1, 75.0); + SetSkill(SkillName.Tactics, 50.1, 60.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.MagicResist, 65.1, 75.0 ); - SetSkill( SkillName.Tactics, 50.1, 60.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 32; + } - VirtualArmor = 32; - } + public Quagmire(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a quagmire corpse"; + public override string DefaultName => "a quagmire"; - public override int GetAngerSound() - { - return 353; - } + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; + public override double HitPoisonChance => 0.1; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; - public override double HitPoisonChance => 0.1; + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public Quagmire( Serial serial ) : base( serial ) - { - } + public override int GetAngerSound() + { + return 353; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == -1 ) - BaseSoundID = 352; - } - } -} + if (BaseSoundID == -1) + BaseSoundID = 352; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Melee/SwampTentacle.cs b/Scripts/Mobiles/Monsters/Plant/Melee/SwampTentacle.cs index 8f9e59555..e73d5f44e 100644 --- a/Scripts/Mobiles/Monsters/Plant/Melee/SwampTentacle.cs +++ b/Scripts/Mobiles/Monsters/Plant/Melee/SwampTentacle.cs @@ -1,67 +1,67 @@ namespace Server.Mobiles { - public class SwampTentacle : BaseCreature - { - public override string CorpseName => "a swamp tentacle corpse"; - public override string DefaultName => "a swamp tentacle"; + public class SwampTentacle : BaseCreature + { + [Constructible] + public SwampTentacle() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 66; + BaseSoundID = 352; - [Constructible] - public SwampTentacle() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 66; - BaseSoundID = 352; + SetStr(96, 120); + SetDex(66, 85); + SetInt(16, 30); - SetStr( 96, 120 ); - SetDex( 66, 85 ); - SetInt( 16, 30 ); + SetHits(58, 72); + SetMana(0); - SetHits( 58, 72 ); - SetMana( 0 ); + SetDamage(6, 12); - SetDamage( 6, 12 ); + SetDamageType(ResistanceType.Physical, 40); + SetDamageType(ResistanceType.Poison, 60); - SetDamageType( ResistanceType.Physical, 40 ); - SetDamageType( ResistanceType.Poison, 60 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 60, 80); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 60, 80 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 65.1, 80.0); + SetSkill(SkillName.Wrestling, 65.1, 80.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 65.1, 80.0 ); - SetSkill( SkillName.Wrestling, 65.1, 80.0 ); + Fame = 3000; + Karma = -3000; - Fame = 3000; - Karma = -3000; + VirtualArmor = 28; - VirtualArmor = 28; + PackReg(3); + } - PackReg( 3 ); - } + public SwampTentacle(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - } + public override string CorpseName => "a swamp tentacle corpse"; + public override string DefaultName => "a swamp tentacle"; - public override Poison PoisonImmune => Poison.Greater; + public override Poison PoisonImmune => Poison.Greater; - public SwampTentacle( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Plant/Melee/WhippingVine.cs b/Scripts/Mobiles/Monsters/Plant/Melee/WhippingVine.cs index bd3266e5e..b3f03c987 100644 --- a/Scripts/Mobiles/Monsters/Plant/Melee/WhippingVine.cs +++ b/Scripts/Mobiles/Monsters/Plant/Melee/WhippingVine.cs @@ -2,70 +2,70 @@ using Server.Items; namespace Server.Mobiles { - public class WhippingVine : BaseCreature - { - public override string CorpseName => "a whipping vine corpse"; - public override string DefaultName => "a whipping vine"; + public class WhippingVine : BaseCreature + { + [Constructible] + public WhippingVine() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 8; + Hue = 0x851; + BaseSoundID = 352; - [Constructible] - public WhippingVine() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 8; - Hue = 0x851; - BaseSoundID = 352; + SetStr(251, 300); + SetDex(76, 100); + SetInt(26, 40); - SetStr( 251, 300 ); - SetDex( 76, 100 ); - SetInt( 26, 40 ); + SetMana(0); - SetMana( 0 ); + SetDamage(7, 25); - SetDamage( 7, 25 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 30 ); + SetResistance(ResistanceType.Physical, 75, 85); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 15, 25); + SetResistance(ResistanceType.Poison, 75, 85); + SetResistance(ResistanceType.Energy, 35, 45); - SetResistance( ResistanceType.Physical, 75, 85 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 15, 25 ); - SetResistance( ResistanceType.Poison, 75, 85 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 70.0); + SetSkill(SkillName.Wrestling, 70.0); - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 70.0 ); - SetSkill( SkillName.Wrestling, 70.0 ); + Fame = 1000; + Karma = -1000; - Fame = 1000; - Karma = -1000; + VirtualArmor = 45; - VirtualArmor = 45; + PackReg(3); + PackItem(new FertileDirt(Utility.RandomMinMax(1, 10))); - PackReg( 3 ); - PackItem( new FertileDirt( Utility.RandomMinMax( 1, 10 ) ) ); + if (0.2 >= Utility.RandomDouble()) + PackItem(new ExecutionersCap()); - if ( 0.2 >= Utility.RandomDouble() ) - PackItem( new ExecutionersCap() ); + PackItem(new Vines()); + } - PackItem( new Vines() ); - } + public WhippingVine(Serial serial) : base(serial) + { + } - public override bool BardImmune => !Core.AOS; - public override Poison PoisonImmune => Poison.Lethal; + public override string CorpseName => "a whipping vine corpse"; + public override string DefaultName => "a whipping vine"; - public WhippingVine( Serial serial ) : base( serial ) - { - } + public override bool BardImmune => !Core.AOS; + public override Poison PoisonImmune => Poison.Lethal; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/AncientWyrm.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/AncientWyrm.cs index c0e09e954..c3d0e219f 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/AncientWyrm.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/AncientWyrm.cs @@ -1,89 +1,89 @@ namespace Server.Mobiles { - public class AncientWyrm : BaseCreature - { - public override string CorpseName => "a dragon corpse"; - public override string DefaultName => "an ancient wyrm"; + public class AncientWyrm : BaseCreature + { + [Constructible] + public AncientWyrm() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 46; + BaseSoundID = 362; - [Constructible] - public AncientWyrm () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 46; - BaseSoundID = 362; + SetStr(1096, 1185); + SetDex(86, 175); + SetInt(686, 775); - SetStr( 1096, 1185 ); - SetDex( 86, 175 ); - SetInt( 686, 775 ); + SetHits(658, 711); - SetHits( 658, 711 ); + SetDamage(29, 35); - SetDamage( 29, 35 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Fire, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Fire, 25 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 80, 90); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 60, 70); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 80, 90 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 60, 70 ); + SetSkill(SkillName.EvalInt, 80.1, 100.0); + SetSkill(SkillName.Magery, 80.1, 100.0); + SetSkill(SkillName.Meditation, 52.5, 75.0); + SetSkill(SkillName.MagicResist, 100.5, 150.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - SetSkill( SkillName.EvalInt, 80.1, 100.0 ); - SetSkill( SkillName.Magery, 80.1, 100.0 ); - SetSkill( SkillName.Meditation, 52.5, 75.0 ); - SetSkill( SkillName.MagicResist, 100.5, 150.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + Fame = 22500; + Karma = -22500; - Fame = 22500; - Karma = -22500; + VirtualArmor = 70; + } - VirtualArmor = 70; - } + public AncientWyrm(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - AddLoot( LootPack.Gems, 5 ); - } + public override string CorpseName => "a dragon corpse"; + public override string DefaultName => "an ancient wyrm"; - public override int GetIdleSound() - { - return 0x2D3; - } + public override bool ReacquireOnMovement => true; + public override bool HasBreath => true; // fire breath enabled + public override bool AutoDispel => true; + public override HideType HideType => HideType.Barbed; + public override int Hides => 40; + public override int Meat => 19; + public override int Scales => 12; + public override ScaleType ScaleType => (ScaleType)Utility.Random(4); + public override Poison PoisonImmune => Poison.Regular; + public override Poison HitPoison => Utility.RandomBool() ? Poison.Lesser : Poison.Regular; + public override int TreasureMapLevel => 5; + public override bool CanFly => true; - public override int GetHurtSound() - { - return 0x2D1; - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + AddLoot(LootPack.Gems, 5); + } - public override bool ReacquireOnMovement => true; - public override bool HasBreath => true; // fire breath enabled - public override bool AutoDispel => true; - public override HideType HideType => HideType.Barbed; - public override int Hides => 40; - public override int Meat => 19; - public override int Scales => 12; - public override ScaleType ScaleType => (ScaleType)Utility.Random( 4 ); - public override Poison PoisonImmune => Poison.Regular; - public override Poison HitPoison => Utility.RandomBool() ? Poison.Lesser : Poison.Regular; - public override int TreasureMapLevel => 5; - public override bool CanFly => true; + public override int GetIdleSound() + { + return 0x2D3; + } - public AncientWyrm( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x2D1; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/DeepSeaSerpent.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/DeepSeaSerpent.cs index 5ea1791b9..23986d8d4 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/DeepSeaSerpent.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/DeepSeaSerpent.cs @@ -2,78 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class DeepSeaSerpent : BaseCreature - { - public override string CorpseName => "a deep sea serpents corpse"; - public override string DefaultName => "a deep sea serpent"; + public class DeepSeaSerpent : BaseCreature + { + [Constructible] + public DeepSeaSerpent() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 150; + BaseSoundID = 447; - [Constructible] - public DeepSeaSerpent() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 150; - BaseSoundID = 447; + Hue = Utility.Random(0x8A0, 5); - Hue = Utility.Random( 0x8A0, 5 ); + SetStr(251, 425); + SetDex(87, 135); + SetInt(87, 155); - SetStr( 251, 425 ); - SetDex( 87, 135 ); - SetInt( 87, 155 ); + SetHits(151, 255); - SetHits( 151, 255 ); + SetDamage(6, 14); - SetDamage( 6, 14 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 30, 40); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 15, 20); - SetResistance( ResistanceType.Physical, 30, 40 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 15, 20 ); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 60.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 70.0); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 60.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 70.0 ); + Fame = 6000; + Karma = -6000; - Fame = 6000; - Karma = -6000; + VirtualArmor = 60; + CanSwim = true; + CantWalk = true; - VirtualArmor = 60; - CanSwim = true; - CantWalk = true; + if (Utility.RandomBool()) + PackItem(new SulfurousAsh(4)); + else + PackItem(new BlackPearl(4)); - if ( Utility.RandomBool() ) - PackItem( new SulfurousAsh( 4 ) ); - else - PackItem( new BlackPearl( 4 ) ); + //PackItem( new SpecialFishingNet() ); + } - //PackItem( new SpecialFishingNet() ); - } + public DeepSeaSerpent(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a deep sea serpents corpse"; + public override string DefaultName => "a deep sea serpent"; - public override bool HasBreath => true; - public override int Meat => 1; - public override int Scales => 8; - public override ScaleType ScaleType => ScaleType.Blue; + public override bool HasBreath => true; + public override int Meat => 1; + public override int Scales => 8; + public override ScaleType ScaleType => ScaleType.Blue; - public DeepSeaSerpent( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/Dragon.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/Dragon.cs index 1e64259c0..9ec06f97d 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/Dragon.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/Dragon.cs @@ -1,81 +1,81 @@ namespace Server.Mobiles { - public class Dragon : BaseCreature - { - public override string CorpseName => "a dragon corpse"; - public override string DefaultName => "a dragon"; + public class Dragon : BaseCreature + { + [Constructible] + public Dragon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(12, 59); + BaseSoundID = 362; - [Constructible] - public Dragon () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 12, 59 ); - BaseSoundID = 362; + SetStr(796, 825); + SetDex(86, 105); + SetInt(436, 475); - SetStr( 796, 825 ); - SetDex( 86, 105 ); - SetInt( 436, 475 ); + SetHits(478, 495); - SetHits( 478, 495 ); + SetDamage(16, 22); - SetDamage( 16, 22 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 35, 45); - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetSkill(SkillName.EvalInt, 30.1, 40.0); + SetSkill(SkillName.Magery, 30.1, 40.0); + SetSkill(SkillName.MagicResist, 99.1, 100.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 92.5); - SetSkill( SkillName.EvalInt, 30.1, 40.0 ); - SetSkill( SkillName.Magery, 30.1, 40.0 ); - SetSkill( SkillName.MagicResist, 99.1, 100.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 92.5 ); + Fame = 15000; + Karma = -15000; - Fame = 15000; - Karma = -15000; + VirtualArmor = 60; - VirtualArmor = 60; + Tamable = true; + ControlSlots = 3; + MinTameSkill = 93.9; + } - Tamable = true; - ControlSlots = 3; - MinTameSkill = 93.9; - } + public Dragon(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.Gems, 8 ); - } + public override string CorpseName => "a dragon corpse"; + public override string DefaultName => "a dragon"; - public override bool ReacquireOnMovement => !Controlled; - public override bool HasBreath => true; // fire breath enabled - public override bool AutoDispel => !Controlled; - public override int TreasureMapLevel => 4; - public override int Meat => 19; - public override int Hides => 20; - public override HideType HideType => HideType.Barbed; - public override int Scales => 7; - public override ScaleType ScaleType => ( Body == 12 ? ScaleType.Yellow : ScaleType.Red ); - public override FoodType FavoriteFood => FoodType.Meat; - public override bool CanAngerOnTame => true; - public override bool CanFly => true; + public override bool ReacquireOnMovement => !Controlled; + public override bool HasBreath => true; // fire breath enabled + public override bool AutoDispel => !Controlled; + public override int TreasureMapLevel => 4; + public override int Meat => 19; + public override int Hides => 20; + public override HideType HideType => HideType.Barbed; + public override int Scales => 7; + public override ScaleType ScaleType => Body == 12 ? ScaleType.Yellow : ScaleType.Red; + public override FoodType FavoriteFood => FoodType.Meat; + public override bool CanAngerOnTame => true; + public override bool CanFly => true; - public Dragon( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.Gems, 8); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/Leviathan.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/Leviathan.cs index 7d35497b5..7685e5a4d 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/Leviathan.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/Leviathan.cs @@ -3,172 +3,173 @@ using Server.Items; namespace Server.Mobiles { - public class Leviathan : BaseCreature - { - public override string CorpseName => "a leviathan corpse"; + public class Leviathan : BaseCreature + { + [Constructible] + public Leviathan() : this(null) + { + } - public Mobile Fisher { get; set; } + [Constructible] + public Leviathan(Mobile fisher) : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Fisher = fisher; - public override string DefaultName => "a leviathan"; + // May not be OSI accurate; mostly copied from krakens + Body = 77; + BaseSoundID = 353; - [Constructible] - public Leviathan() : this( null ) - { - } + Hue = 0x481; - [Constructible] - public Leviathan( Mobile fisher ) : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Fisher = fisher; + SetStr(1000); + SetDex(501, 520); + SetInt(501, 515); - // May not be OSI accurate; mostly copied from krakens - Body = 77; - BaseSoundID = 353; + SetHits(1500); - Hue = 0x481; + SetDamage(25, 33); - SetStr( 1000 ); - SetDex( 501, 520 ); - SetInt( 501, 515 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Cold, 30); - SetHits( 1500 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 45, 55); + SetResistance(ResistanceType.Cold, 45, 55); + SetResistance(ResistanceType.Poison, 35, 45); + SetResistance(ResistanceType.Energy, 25, 35); - SetDamage( 25, 33 ); + SetSkill(SkillName.EvalInt, 97.6, 107.5); + SetSkill(SkillName.Magery, 97.6, 107.5); + SetSkill(SkillName.MagicResist, 97.6, 107.5); + SetSkill(SkillName.Meditation, 97.6, 107.5); + SetSkill(SkillName.Tactics, 97.6, 107.5); + SetSkill(SkillName.Wrestling, 97.6, 107.5); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Cold, 30 ); + Fame = 24000; + Karma = -24000; - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 45, 55 ); - SetResistance( ResistanceType.Cold, 45, 55 ); - SetResistance( ResistanceType.Poison, 35, 45 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + VirtualArmor = 50; - SetSkill( SkillName.EvalInt, 97.6, 107.5 ); - SetSkill( SkillName.Magery, 97.6, 107.5 ); - SetSkill( SkillName.MagicResist, 97.6, 107.5 ); - SetSkill( SkillName.Meditation, 97.6, 107.5 ); - SetSkill( SkillName.Tactics, 97.6, 107.5 ); - SetSkill( SkillName.Wrestling, 97.6, 107.5 ); + CanSwim = true; + CantWalk = true; - Fame = 24000; - Karma = -24000; + PackItem(new MessageInABottle()); - VirtualArmor = 50; + Rope rope = new Rope(); + rope.ItemID = 0x14F8; + PackItem(rope); - CanSwim = true; - CantWalk = true; + rope = new Rope(); + rope.ItemID = 0x14FA; + PackItem(rope); + } - PackItem( new MessageInABottle() ); + public Leviathan(Serial serial) : base(serial) + { + } - Rope rope = new Rope(); - rope.ItemID = 0x14F8; - PackItem( rope ); + public override string CorpseName => "a leviathan corpse"; - rope = new Rope(); - rope.ItemID = 0x14FA; - PackItem( rope ); - } + public Mobile Fisher{ get; set; } - public override bool HasBreath => true; - public override int BreathPhysicalDamage => 70; // TODO: Verify damage type - public override int BreathColdDamage => 30; - public override int BreathFireDamage => 0; - public override int BreathEffectHue => 0x1ED; - public override double BreathDamageScalar => 0.05; - public override double BreathMinDelay => 5.0; - public override double BreathMaxDelay => 7.5; + public override string DefaultName => "a leviathan"; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 5 ); - } + public override bool HasBreath => true; + public override int BreathPhysicalDamage => 70; // TODO: Verify damage type + public override int BreathColdDamage => 30; + public override int BreathFireDamage => 0; + public override int BreathEffectHue => 0x1ED; + public override double BreathDamageScalar => 0.05; + public override double BreathMinDelay => 5.0; + public override double BreathMaxDelay => 7.5; - public override double TreasureMapChance => 0.25; - public override int TreasureMapLevel => 5; + public override double TreasureMapChance => 0.25; + public override int TreasureMapLevel => 5; - public Leviathan( Serial serial ) : base( serial ) - { - } + public static Type[] Artifacts{ get; } = + { + // Decorations + typeof(CandelabraOfSouls), + typeof(GhostShipAnchor), + typeof(GoldBricks), + typeof(PhillipsWoodenSteed), + typeof(SeahorseStatuette), + typeof(ShipModelOfTheHMSCape), + typeof(AdmiralsHeartyRum), - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + // Equipment + typeof(AlchemistsBauble), + typeof(ArcticDeathDealer), + typeof(BlazeOfDeath), + typeof(BurglarsBandana), + typeof(CaptainQuacklebushsCutlass), + typeof(CavortingClub), + typeof(DreadPirateHat), + typeof(EnchantedTitanLegBone), + typeof(GwennosHarp), + typeof(IolosLute), + typeof(LunaLance), + typeof(NightsKiss), + typeof(NoxRangersHeavyCrossbow), + typeof(PolarBearMask), + typeof(VioletCourage) + }; - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 5); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } + writer.Write(0); + } - public static Type[] Artifacts { get; } = - { - // Decorations - typeof( CandelabraOfSouls ), - typeof( GhostShipAnchor ), - typeof( GoldBricks ), - typeof( PhillipsWoodenSteed ), - typeof( SeahorseStatuette ), - typeof( ShipModelOfTheHMSCape ), - typeof( AdmiralsHeartyRum ), + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - // Equipment - typeof( AlchemistsBauble ), - typeof( ArcticDeathDealer ), - typeof( BlazeOfDeath ), - typeof( BurglarsBandana ), - typeof( CaptainQuacklebushsCutlass ), - typeof( CavortingClub ), - typeof( DreadPirateHat ), - typeof( EnchantedTitanLegBone ), - typeof( GwennosHarp ), - typeof( IolosLute ), - typeof( LunaLance ), - typeof( NightsKiss ), - typeof( NoxRangersHeavyCrossbow ), - typeof( PolarBearMask ), - typeof( VioletCourage ) - }; + int version = reader.ReadInt(); + } - public static void GiveArtifactTo( Mobile m ) - { - Item item = Loot.Construct( Artifacts ); + public static void GiveArtifactTo(Mobile m) + { + Item item = Loot.Construct(Artifacts); - if ( item == null ) - return; + if (item == null) + return; - // TODO: Confirm messages - if ( m.AddToBackpack( item ) ) - m.SendMessage( "As a reward for slaying the mighty leviathan, an artifact has been placed in your backpack." ); - else - m.SendMessage( "As your backpack is full, your reward for destroying the legendary leviathan has been placed at your feet." ); - } + // TODO: Confirm messages + if (m.AddToBackpack(item)) + m.SendMessage("As a reward for slaying the mighty leviathan, an artifact has been placed in your backpack."); + else + m.SendMessage( + "As your backpack is full, your reward for destroying the legendary leviathan has been placed at your feet."); + } - public override void OnKilledBy( Mobile mob ) - { - base.OnKilledBy( mob ); + public override void OnKilledBy(Mobile mob) + { + base.OnKilledBy(mob); - if ( Paragon.CheckArtifactChance( mob, this ) ) - { - GiveArtifactTo( mob ); + if (Paragon.CheckArtifactChance(mob, this)) + { + GiveArtifactTo(mob); - if ( mob == Fisher ) - Fisher = null; - } - } + if (mob == Fisher) + Fisher = null; + } + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); + public override void OnDeath(Container c) + { + base.OnDeath(c); - if ( Fisher != null && 25 > Utility.Random( 100 ) ) - GiveArtifactTo( Fisher ); + if (Fisher != null && 25 > Utility.Random(100)) + GiveArtifactTo(Fisher); - Fisher = null; - } - } -} + Fisher = null; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianArchmage.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianArchmage.cs index f1225bc7b..58a35cdb2 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianArchmage.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianArchmage.cs @@ -1,77 +1,79 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.OphidianJusticar", "Server.Mobiles.OphidianZealot" )] - public class OphidianArchmage : BaseCreature - { - public override string CorpseName => "an ophidian corpse"; - private static string[] m_Names = { - "an ophidian justicar", - "an ophidian zealot" - }; + [TypeAlias("Server.Mobiles.OphidianJusticar", "Server.Mobiles.OphidianZealot")] + public class OphidianArchmage : BaseCreature + { + private static string[] m_Names = + { + "an ophidian justicar", + "an ophidian zealot" + }; - [Constructible] - public OphidianArchmage() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = m_Names[Utility.Random( m_Names.Length )]; - Body = 85; - BaseSoundID = 639; + [Constructible] + public OphidianArchmage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = m_Names[Utility.Random(m_Names.Length)]; + Body = 85; + BaseSoundID = 639; - SetStr( 281, 305 ); - SetDex( 191, 215 ); - SetInt( 226, 250 ); + SetStr(281, 305); + SetDex(191, 215); + SetInt(226, 250); - SetHits( 169, 183 ); - SetStam( 36, 45 ); + SetHits(169, 183); + SetStam(36, 45); - SetDamage( 5, 10 ); + SetDamage(5, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 40, 45 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 35, 40 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetResistance(ResistanceType.Physical, 40, 45); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 35, 40); + SetResistance(ResistanceType.Energy, 25, 35); - SetSkill( SkillName.EvalInt, 95.1, 100.0 ); - SetSkill( SkillName.Magery, 95.1, 100.0 ); - SetSkill( SkillName.MagicResist, 75.0, 97.5 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 20.2, 60.0 ); + SetSkill(SkillName.EvalInt, 95.1, 100.0); + SetSkill(SkillName.Magery, 95.1, 100.0); + SetSkill(SkillName.MagicResist, 75.0, 97.5); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 20.2, 60.0); - Fame = 11500; - Karma = -11500; + Fame = 11500; + Karma = -11500; - VirtualArmor = 44; + VirtualArmor = 44; - PackReg( 5, 15 ); - PackNecroReg( 5, 15 ); - } + PackReg(5, 15); + PackNecroReg(5, 15); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public OphidianArchmage(Serial serial) : base(serial) + { + } - public override int Meat => 1; + public override string CorpseName => "an ophidian corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override int Meat => 1; - public OphidianArchmage( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMage.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMage.cs index d335263de..80e0ac250 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMage.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMage.cs @@ -1,78 +1,80 @@ namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.OphidianShaman" )] - public class OphidianMage : BaseCreature - { - public override string CorpseName => "an ophidian corpse"; - private static string[] m_Names = { - "an ophidian apprentice mage", - "an ophidian shaman" - }; + [TypeAlias("Server.Mobiles.OphidianShaman")] + public class OphidianMage : BaseCreature + { + private static string[] m_Names = + { + "an ophidian apprentice mage", + "an ophidian shaman" + }; - [Constructible] - public OphidianMage() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = m_Names[Utility.Random( m_Names.Length )]; - Body = 85; - BaseSoundID = 639; + [Constructible] + public OphidianMage() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = m_Names[Utility.Random(m_Names.Length)]; + Body = 85; + BaseSoundID = 639; - SetStr( 181, 205 ); - SetDex( 191, 215 ); - SetInt( 96, 120 ); + SetStr(181, 205); + SetDex(191, 215); + SetInt(96, 120); - SetHits( 109, 123 ); + SetHits(109, 123); - SetDamage( 5, 10 ); + SetDamage(5, 10); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 35, 45); - SetSkill( SkillName.EvalInt, 85.1, 100.0 ); - SetSkill( SkillName.Magery, 85.1, 100.0 ); - SetSkill( SkillName.MagicResist, 75.0, 97.5 ); - SetSkill( SkillName.Tactics, 65.0, 87.5 ); - SetSkill( SkillName.Wrestling, 20.2, 60.0 ); + SetSkill(SkillName.EvalInt, 85.1, 100.0); + SetSkill(SkillName.Magery, 85.1, 100.0); + SetSkill(SkillName.MagicResist, 75.0, 97.5); + SetSkill(SkillName.Tactics, 65.0, 87.5); + SetSkill(SkillName.Wrestling, 20.2, 60.0); - Fame = 4000; - Karma = -4000; + Fame = 4000; + Karma = -4000; - VirtualArmor = 30; + VirtualArmor = 30; - PackReg( 10 ); - } + PackReg(10); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.LowScrolls ); - AddLoot( LootPack.MedScrolls ); - AddLoot( LootPack.Potions ); - } + public OphidianMage(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int TreasureMapLevel => 2; + public override string CorpseName => "an ophidian corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override int Meat => 1; + public override int TreasureMapLevel => 2; - public OphidianMage( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.LowScrolls); + AddLoot(LootPack.MedScrolls); + AddLoot(LootPack.Potions); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMatriarch.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMatriarch.cs index 0960f4c3a..ee0f56511 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMatriarch.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/OphidianMatriarch.cs @@ -1,71 +1,71 @@ namespace Server.Mobiles { - public class OphidianMatriarch : BaseCreature - { - public override string CorpseName => "an ophidian corpse"; - public override string DefaultName => "an ophidian matriarch"; + public class OphidianMatriarch : BaseCreature + { + [Constructible] + public OphidianMatriarch() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 87; + BaseSoundID = 644; - [Constructible] - public OphidianMatriarch() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 87; - BaseSoundID = 644; + SetStr(416, 505); + SetDex(96, 115); + SetInt(366, 455); - SetStr( 416, 505 ); - SetDex( 96, 115 ); - SetInt( 366, 455 ); + SetHits(250, 303); - SetHits( 250, 303 ); + SetDamage(11, 13); - SetDamage( 11, 13 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 35, 45); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.Meditation, 5.4, 25.0); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 80.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.Meditation, 5.4, 25.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 80.0 ); + Fame = 16000; + Karma = -16000; - Fame = 16000; - Karma = -16000; + VirtualArmor = 50; + } - VirtualArmor = 50; - } + public OphidianMatriarch(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override string CorpseName => "an ophidian corpse"; + public override string DefaultName => "an ophidian matriarch"; - public override Poison PoisonImmune => Poison.Greater; - public override int TreasureMapLevel => 4; + public override Poison PoisonImmune => Poison.Greater; + public override int TreasureMapLevel => 4; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public OphidianMatriarch( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/SeaSerpent.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/SeaSerpent.cs index a76535479..aa42325cf 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/SeaSerpent.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/SeaSerpent.cs @@ -2,84 +2,84 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Seaserpant" )] - public class SeaSerpent : BaseCreature - { - public override string CorpseName => "a sea serpents corpse"; - public override string DefaultName => "a sea serpent"; + [TypeAlias("Server.Mobiles.Seaserpant")] + public class SeaSerpent : BaseCreature + { + [Constructible] + public SeaSerpent() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 150; + BaseSoundID = 447; - [Constructible] - public SeaSerpent() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 150; - BaseSoundID = 447; + Hue = Utility.Random(0x530, 9); - Hue = Utility.Random( 0x530, 9 ); + SetStr(168, 225); + SetDex(58, 85); + SetInt(53, 95); - SetStr( 168, 225 ); - SetDex( 58, 85 ); - SetInt( 53, 95 ); + SetHits(110, 127); - SetHits( 110, 127 ); + SetDamage(7, 13); - SetDamage( 7, 13 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 15, 20); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 15, 20 ); + SetSkill(SkillName.MagicResist, 60.1, 75.0); + SetSkill(SkillName.Tactics, 60.1, 70.0); + SetSkill(SkillName.Wrestling, 60.1, 70.0); - SetSkill( SkillName.MagicResist, 60.1, 75.0 ); - SetSkill( SkillName.Tactics, 60.1, 70.0 ); - SetSkill( SkillName.Wrestling, 60.1, 70.0 ); + Fame = 6000; + Karma = -6000; - Fame = 6000; - Karma = -6000; + VirtualArmor = 30; + CanSwim = true; + CantWalk = true; - VirtualArmor = 30; - CanSwim = true; - CantWalk = true; + if (Utility.RandomBool()) + PackItem(new SulfurousAsh(4)); + else + PackItem(new BlackPearl(4)); - if ( Utility.RandomBool() ) - PackItem( new SulfurousAsh( 4 ) ); - else - PackItem( new BlackPearl( 4 ) ); + PackItem(new RawFishSteak()); - PackItem( new RawFishSteak() ); + //PackItem( new SpecialFishingNet() ); + } - //PackItem( new SpecialFishingNet() ); - } + public SeaSerpent(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a sea serpents corpse"; + public override string DefaultName => "a sea serpent"; - public override bool HasBreath => true; - public override int TreasureMapLevel => 2; + public override bool HasBreath => true; + public override int TreasureMapLevel => 2; - public override int Hides => 10; - public override HideType HideType => HideType.Horned; - public override int Scales => 8; - public override ScaleType ScaleType => ScaleType.Blue; + public override int Hides => 10; + public override HideType HideType => HideType.Horned; + public override int Scales => 8; + public override ScaleType ScaleType => ScaleType.Blue; - public SeaSerpent( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/SerpentineDragon.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/SerpentineDragon.cs index 7a5eda825..e18bcd495 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/SerpentineDragon.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/SerpentineDragon.cs @@ -1,118 +1,121 @@ +using Server.Engines.Plants; + namespace Server.Mobiles { - public class SerpentineDragon : BaseCreature - { - public override string CorpseName => "a dragon corpse"; - public override string DefaultName => "a serpentine dragon"; + public class SerpentineDragon : BaseCreature + { + [Constructible] + public SerpentineDragon() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Body = 103; + BaseSoundID = 362; - [Constructible] - public SerpentineDragon() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Body = 103; - BaseSoundID = 362; + SetStr(111, 140); + SetDex(201, 220); + SetInt(1001, 1040); - SetStr( 111, 140 ); - SetDex( 201, 220 ); - SetInt( 1001, 1040 ); + SetHits(480); - SetHits( 480 ); + SetDamage(5, 12); - SetDamage( 5, 12 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Poison, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Poison, 25 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 25, 35); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 25, 35); + SetResistance(ResistanceType.Energy, 25, 35); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 25, 35 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 25, 35 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetSkill(SkillName.EvalInt, 100.1, 110.0); + SetSkill(SkillName.Magery, 110.1, 120.0); + SetSkill(SkillName.Meditation, 100.0); + SetSkill(SkillName.MagicResist, 100.0); + SetSkill(SkillName.Tactics, 50.1, 60.0); + SetSkill(SkillName.Wrestling, 30.1, 100.0); - SetSkill( SkillName.EvalInt, 100.1, 110.0 ); - SetSkill( SkillName.Magery, 110.1, 120.0 ); - SetSkill( SkillName.Meditation, 100.0 ); - SetSkill( SkillName.MagicResist, 100.0 ); - SetSkill( SkillName.Tactics, 50.1, 60.0 ); - SetSkill( SkillName.Wrestling, 30.1, 100.0 ); + Fame = 15000; + Karma = 15000; - Fame = 15000; - Karma = 15000; + VirtualArmor = 36; - VirtualArmor = 36; + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(2)); + } - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(2) ); - } + public SerpentineDragon(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "a dragon corpse"; + public override string DefaultName => "a serpentine dragon"; - public override int GetIdleSound() - { - return 0x2C4; - } + public override bool ReacquireOnMovement => true; + public override bool HasBreath => true; // fire breath enabled + public override double BonusPetDamageScalar => Core.SE ? 3.0 : 1.0; - public override int GetAttackSound() - { - return 0x2C0; - } + public override bool AutoDispel => true; + public override HideType HideType => HideType.Barbed; + public override int Hides => 20; + public override int Meat => 19; + public override int Scales => 6; + public override ScaleType ScaleType => Utility.RandomBool() ? ScaleType.Black : ScaleType.White; + public override int TreasureMapLevel => 4; - public override int GetDeathSound() - { - return 0x2C1; - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.Gems, 2); + } - public override int GetAngerSound() - { - return 0x2C4; - } + public override int GetIdleSound() + { + return 0x2C4; + } - public override int GetHurtSound() - { - return 0x2C3; - } + public override int GetAttackSound() + { + return 0x2C0; + } - public override bool ReacquireOnMovement => true; - public override bool HasBreath => true; // fire breath enabled - public override double BonusPetDamageScalar => (Core.SE) ? 3.0 : 1.0; + public override int GetDeathSound() + { + return 0x2C1; + } - public override bool AutoDispel => true; - public override HideType HideType => HideType.Barbed; - public override int Hides => 20; - public override int Meat => 19; - public override int Scales => 6; - public override ScaleType ScaleType => ( Utility.RandomBool() ? ScaleType.Black : ScaleType.White ); - public override int TreasureMapLevel => 4; + public override int GetAngerSound() + { + return 0x2C4; + } - public SerpentineDragon( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x2C3; + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - if ( !Core.SE && 0.2 > Utility.RandomDouble() && attacker is BaseCreature c && c.Controlled && c.ControlMaster != null ) - { - c.ControlTarget = c.ControlMaster; - c.ControlOrder = OrderType.Attack; - c.Combatant = c.ControlMaster; - } - } + if (!Core.SE && 0.2 > Utility.RandomDouble() && attacker is BaseCreature c && c.Controlled && + c.ControlMaster != null) + { + c.ControlTarget = c.ControlMaster; + c.ControlOrder = OrderType.Attack; + c.Combatant = c.ControlMaster; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/ShadowWyrm.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/ShadowWyrm.cs index 71e21da3f..3c8dc365f 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/ShadowWyrm.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/ShadowWyrm.cs @@ -1,90 +1,90 @@ namespace Server.Mobiles { - public class ShadowWyrm : BaseCreature - { - public override string CorpseName => "a shadow wyrm corpse"; - public override string DefaultName => "a shadow wyrm"; + public class ShadowWyrm : BaseCreature + { + [Constructible] + public ShadowWyrm() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 106; + BaseSoundID = 362; - [Constructible] - public ShadowWyrm() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 106; - BaseSoundID = 362; + SetStr(898, 1030); + SetDex(68, 200); + SetInt(488, 620); - SetStr( 898, 1030 ); - SetDex( 68, 200 ); - SetInt( 488, 620 ); + SetHits(558, 599); - SetHits( 558, 599 ); + SetDamage(29, 35); - SetDamage( 29, 35 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Cold, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Cold, 25 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 45, 55); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 45, 55 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.EvalInt, 80.1, 100.0); + SetSkill(SkillName.Magery, 80.1, 100.0); + SetSkill(SkillName.Meditation, 52.5, 75.0); + SetSkill(SkillName.MagicResist, 100.3, 130.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - SetSkill( SkillName.EvalInt, 80.1, 100.0 ); - SetSkill( SkillName.Magery, 80.1, 100.0 ); - SetSkill( SkillName.Meditation, 52.5, 75.0 ); - SetSkill( SkillName.MagicResist, 100.3, 130.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + Fame = 22500; + Karma = -22500; - Fame = 22500; - Karma = -22500; + VirtualArmor = 70; + } - VirtualArmor = 70; - } + public ShadowWyrm(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - AddLoot( LootPack.Gems, 5 ); - } + public override string CorpseName => "a shadow wyrm corpse"; + public override string DefaultName => "a shadow wyrm"; - public override int GetIdleSound() - { - return 0x2D5; - } + public override bool ReacquireOnMovement => true; + public override bool HasBreath => true; // fire breath enabled + public override bool AutoDispel => true; + public override Poison PoisonImmune => Poison.Deadly; + public override Poison HitPoison => Poison.Deadly; + public override int TreasureMapLevel => 5; - public override int GetHurtSound() - { - return 0x2D1; - } + public override int Meat => 19; + public override int Hides => 20; + public override int Scales => 10; + public override ScaleType ScaleType => ScaleType.Black; + public override HideType HideType => HideType.Barbed; + public override bool CanFly => true; - public override bool ReacquireOnMovement => true; - public override bool HasBreath => true; // fire breath enabled - public override bool AutoDispel => true; - public override Poison PoisonImmune => Poison.Deadly; - public override Poison HitPoison => Poison.Deadly; - public override int TreasureMapLevel => 5; + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + AddLoot(LootPack.Gems, 5); + } - public override int Meat => 19; - public override int Hides => 20; - public override int Scales => 10; - public override ScaleType ScaleType => ScaleType.Black; - public override HideType HideType => HideType.Barbed; - public override bool CanFly => true; + public override int GetIdleSound() + { + return 0x2D5; + } - public ShadowWyrm( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x2D1; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/SkeletalDragon.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/SkeletalDragon.cs index e6fcdc908..f8e641461 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/SkeletalDragon.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/SkeletalDragon.cs @@ -1,82 +1,83 @@ namespace Server.Mobiles { - public class SkeletalDragon : BaseCreature - { - public override string CorpseName => "a skeletal dragon corpse"; - public override string DefaultName => "a skeletal dragon"; + public class SkeletalDragon : BaseCreature + { + [Constructible] + public SkeletalDragon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 104; + BaseSoundID = 0x488; - [Constructible] - public SkeletalDragon () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 104; - BaseSoundID = 0x488; + SetStr(898, 1030); + SetDex(68, 200); + SetInt(488, 620); - SetStr( 898, 1030 ); - SetDex( 68, 200 ); - SetInt( 488, 620 ); + SetHits(558, 599); - SetHits( 558, 599 ); + SetDamage(29, 35); - SetDamage( 29, 35 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Fire, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Fire, 25 ); + SetResistance(ResistanceType.Physical, 75, 80); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Poison, 70, 80); + SetResistance(ResistanceType.Energy, 40, 60); - SetResistance( ResistanceType.Physical, 75, 80 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Poison, 70, 80 ); - SetResistance( ResistanceType.Energy, 40, 60 ); + SetSkill(SkillName.EvalInt, 80.1, 100.0); + SetSkill(SkillName.Magery, 80.1, 100.0); + SetSkill(SkillName.MagicResist, 100.3, 130.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); + SetSkill(SkillName.Necromancy, 120.1, 130.0); + SetSkill(SkillName.SpiritSpeak, 120.1, 130.0); - SetSkill( SkillName.EvalInt, 80.1, 100.0 ); - SetSkill( SkillName.Magery, 80.1, 100.0 ); - SetSkill( SkillName.MagicResist, 100.3, 130.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); - SetSkill( SkillName.Necromancy, 120.1, 130.0 ); - SetSkill( SkillName.SpiritSpeak, 120.1, 130.0 ); + Fame = 22500; + Karma = -22500; - Fame = 22500; - Karma = -22500; + VirtualArmor = 80; + } - VirtualArmor = 80; - } + public SkeletalDragon(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 4 ); - AddLoot( LootPack.Gems, 5 ); - } + public override string CorpseName => "a skeletal dragon corpse"; + public override string DefaultName => "a skeletal dragon"; - public override bool ReacquireOnMovement => true; - public override bool HasBreath => true; // fire breath enabled - public override int BreathFireDamage => 0; - public override int BreathColdDamage => 100; - public override int BreathEffectHue => 0x480; - public override double BonusPetDamageScalar => (Core.SE)? 3.0 : 1.0; - // TODO: Undead summoning? + public override bool ReacquireOnMovement => true; + public override bool HasBreath => true; // fire breath enabled + public override int BreathFireDamage => 0; + public override int BreathColdDamage => 100; + public override int BreathEffectHue => 0x480; - public override bool AutoDispel => true; - public override Poison PoisonImmune => Poison.Lethal; - public override bool BleedImmune => true; - public override int Meat => 19; // where's it hiding these? :) - public override int Hides => 20; - public override HideType HideType => HideType.Barbed; + public override double BonusPetDamageScalar => Core.SE ? 3.0 : 1.0; + // TODO: Undead summoning? - public SkeletalDragon( Serial serial ) : base( serial ) - { - } + public override bool AutoDispel => true; + public override Poison PoisonImmune => Poison.Lethal; + public override bool BleedImmune => true; + public override int Meat => 19; // where's it hiding these? :) + public override int Hides => 20; + public override HideType HideType => HideType.Barbed; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 4); + AddLoot(LootPack.Gems, 5); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Magic/WhiteWyrm.cs b/Scripts/Mobiles/Monsters/Reptile/Magic/WhiteWyrm.cs index 8fe16a3bc..f3c6965b0 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Magic/WhiteWyrm.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Magic/WhiteWyrm.cs @@ -1,81 +1,81 @@ namespace Server.Mobiles { - public class WhiteWyrm : BaseCreature - { - public override string CorpseName => "a white wyrm corpse"; - public override string DefaultName => "a white wyrm"; + public class WhiteWyrm : BaseCreature + { + [Constructible] + public WhiteWyrm() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomBool() ? 180 : 49; + BaseSoundID = 362; - [Constructible] - public WhiteWyrm() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomBool() ? 180 : 49; - BaseSoundID = 362; + SetStr(721, 760); + SetDex(101, 130); + SetInt(386, 425); - SetStr( 721, 760 ); - SetDex( 101, 130 ); - SetInt( 386, 425 ); + SetHits(433, 456); - SetHits( 433, 456 ); + SetDamage(17, 25); - SetDamage( 17, 25 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Cold, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Cold, 50 ); + SetResistance(ResistanceType.Physical, 55, 70); + SetResistance(ResistanceType.Fire, 15, 25); + SetResistance(ResistanceType.Cold, 80, 90); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 55, 70 ); - SetResistance( ResistanceType.Fire, 15, 25 ); - SetResistance( ResistanceType.Cold, 80, 90 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 99.1, 100.0); + SetSkill(SkillName.Magery, 99.1, 100.0); + SetSkill(SkillName.MagicResist, 99.1, 100.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.EvalInt, 99.1, 100.0 ); - SetSkill( SkillName.Magery, 99.1, 100.0 ); - SetSkill( SkillName.MagicResist, 99.1, 100.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 18000; + Karma = -18000; - Fame = 18000; - Karma = -18000; + VirtualArmor = 64; - VirtualArmor = 64; + Tamable = true; + ControlSlots = 3; + MinTameSkill = 96.3; + } - Tamable = true; - ControlSlots = 3; - MinTameSkill = 96.3; - } + public WhiteWyrm(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems, Utility.Random( 1, 5 ) ); - } + public override string CorpseName => "a white wyrm corpse"; + public override string DefaultName => "a white wyrm"; - public override bool ReacquireOnMovement => true; - public override int TreasureMapLevel => 4; - public override int Meat => 19; - public override int Hides => 20; - public override HideType HideType => HideType.Barbed; - public override int Scales => 9; - public override ScaleType ScaleType => ScaleType.White; - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Gold; - public override bool CanAngerOnTame => true; - public override bool CanFly => true; + public override bool ReacquireOnMovement => true; + public override int TreasureMapLevel => 4; + public override int Meat => 19; + public override int Hides => 20; + public override HideType HideType => HideType.Barbed; + public override int Scales => 9; + public override ScaleType ScaleType => ScaleType.White; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Gold; + public override bool CanAngerOnTame => true; + public override bool CanFly => true; - public WhiteWyrm( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems, Utility.Random(1, 5)); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/Drake.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/Drake.cs index 68319c373..f4a64b8eb 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/Drake.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/Drake.cs @@ -1,80 +1,80 @@ namespace Server.Mobiles { - public class Drake : BaseCreature - { - public override string CorpseName => "a drake corpse"; - public override string DefaultName => "a drake"; + public class Drake : BaseCreature + { + [Constructible] + public Drake() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = Utility.RandomList(60, 61); + BaseSoundID = 362; - [Constructible] - public Drake () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = Utility.RandomList( 60, 61 ); - BaseSoundID = 362; + SetStr(401, 430); + SetDex(133, 152); + SetInt(101, 140); - SetStr( 401, 430 ); - SetDex( 133, 152 ); - SetInt( 101, 140 ); + SetHits(241, 258); - SetHits( 241, 258 ); + SetDamage(11, 17); - SetDamage( 11, 17 ); + SetDamageType(ResistanceType.Physical, 80); + SetDamageType(ResistanceType.Fire, 20); - SetDamageType( ResistanceType.Physical, 80 ); - SetDamageType( ResistanceType.Fire, 20 ); + SetResistance(ResistanceType.Physical, 45, 50); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 45, 50 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 65.1, 90.0); + SetSkill(SkillName.Wrestling, 65.1, 80.0); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 65.1, 90.0 ); - SetSkill( SkillName.Wrestling, 65.1, 80.0 ); + Fame = 5500; + Karma = -5500; - Fame = 5500; - Karma = -5500; + VirtualArmor = 46; - VirtualArmor = 46; + Tamable = true; + ControlSlots = 2; + MinTameSkill = 84.3; - Tamable = true; - ControlSlots = 2; - MinTameSkill = 84.3; + PackReg(3); + } - PackReg( 3 ); - } + public Drake(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override string CorpseName => "a drake corpse"; + public override string DefaultName => "a drake"; - public override bool ReacquireOnMovement => true; - public override bool HasBreath => true; // fire breath enabled - public override int TreasureMapLevel => 2; - public override int Meat => 10; - public override int Hides => 20; - public override HideType HideType => HideType.Horned; - public override int Scales => 2; - public override ScaleType ScaleType => ( Body == 60 ? ScaleType.Yellow : ScaleType.Red ); - public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; - public override bool CanFly => true; + public override bool ReacquireOnMovement => true; + public override bool HasBreath => true; // fire breath enabled + public override int TreasureMapLevel => 2; + public override int Meat => 10; + public override int Hides => 20; + public override HideType HideType => HideType.Horned; + public override int Scales => 2; + public override ScaleType ScaleType => Body == 60 ? ScaleType.Yellow : ScaleType.Red; + public override FoodType FavoriteFood => FoodType.Meat | FoodType.Fish; + public override bool CanFly => true; - public Drake( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/Harpy.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/Harpy.cs index 03edd35d0..fa0e4a7f1 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/Harpy.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/Harpy.cs @@ -1,91 +1,92 @@ namespace Server.Mobiles { - public class Harpy : BaseCreature - { - public override string CorpseName => "a harpy corpse"; - public override string DefaultName => "a harpy"; - [Constructible] - public Harpy() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 30; - BaseSoundID = 402; + public class Harpy : BaseCreature + { + [Constructible] + public Harpy() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 30; + BaseSoundID = 402; - SetStr( 96, 120 ); - SetDex( 86, 110 ); - SetInt( 51, 75 ); + SetStr(96, 120); + SetDex(86, 110); + SetInt(51, 75); - SetHits( 58, 72 ); + SetHits(58, 72); - SetDamage( 5, 7 ); + SetDamage(5, 7); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 10, 20 ); - SetResistance( ResistanceType.Cold, 10, 30 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 10, 20); + SetResistance(ResistanceType.Cold, 10, 30); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetSkill( SkillName.MagicResist, 50.1, 65.0 ); - SetSkill( SkillName.Tactics, 70.1, 100.0 ); - SetSkill( SkillName.Wrestling, 60.1, 90.0 ); + SetSkill(SkillName.MagicResist, 50.1, 65.0); + SetSkill(SkillName.Tactics, 70.1, 100.0); + SetSkill(SkillName.Wrestling, 60.1, 90.0); - Fame = 2500; - Karma = -2500; + Fame = 2500; + Karma = -2500; - VirtualArmor = 28; - } + VirtualArmor = 28; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager, 2 ); - } + public Harpy(Serial serial) : base(serial) + { + } - public override int GetAttackSound() - { - return 916; - } + public override string CorpseName => "a harpy corpse"; + public override string DefaultName => "a harpy"; - public override int GetAngerSound() - { - return 916; - } + public override bool CanRummageCorpses => true; + public override int Meat => 4; + public override MeatType MeatType => MeatType.Bird; + public override int Feathers => 50; + public override bool CanFly => true; - public override int GetDeathSound() - { - return 917; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager, 2); + } - public override int GetHurtSound() - { - return 919; - } + public override int GetAttackSound() + { + return 916; + } - public override int GetIdleSound() - { - return 918; - } + public override int GetAngerSound() + { + return 916; + } - public override bool CanRummageCorpses => true; - public override int Meat => 4; - public override MeatType MeatType => MeatType.Bird; - public override int Feathers => 50; - public override bool CanFly => true; + public override int GetDeathSound() + { + return 917; + } - public Harpy( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 919; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetIdleSound() + { + return 918; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/Kraken.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/Kraken.cs index 695e43b78..ff31cce02 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/Kraken.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/Kraken.cs @@ -2,78 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class Kraken : BaseCreature - { - public override string CorpseName => "a krakens corpse"; - public override string DefaultName => "a kraken"; + public class Kraken : BaseCreature + { + [Constructible] + public Kraken() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 77; + BaseSoundID = 353; - [Constructible] - public Kraken() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 77; - BaseSoundID = 353; + SetStr(756, 780); + SetDex(226, 245); + SetInt(26, 40); - SetStr( 756, 780 ); - SetDex( 226, 245 ); - SetInt( 26, 40 ); + SetHits(454, 468); + SetMana(0); - SetHits( 454, 468 ); - SetMana( 0 ); + SetDamage(19, 33); - SetDamage( 19, 33 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Cold, 30); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Cold, 30 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + SetSkill(SkillName.MagicResist, 15.1, 20.0); + SetSkill(SkillName.Tactics, 45.1, 60.0); + SetSkill(SkillName.Wrestling, 45.1, 60.0); - SetSkill( SkillName.MagicResist, 15.1, 20.0 ); - SetSkill( SkillName.Tactics, 45.1, 60.0 ); - SetSkill( SkillName.Wrestling, 45.1, 60.0 ); + Fame = 11000; + Karma = -11000; - Fame = 11000; - Karma = -11000; + VirtualArmor = 50; - VirtualArmor = 50; + CanSwim = true; + CantWalk = true; - CanSwim = true; - CantWalk = true; + Rope rope = new Rope(); + rope.ItemID = 0x14F8; + PackItem(rope); - Rope rope = new Rope(); - rope.ItemID = 0x14F8; - PackItem( rope ); + if (Utility.RandomDouble() < .05) + PackItem(new MessageInABottle()); - if ( Utility.RandomDouble() < .05 ) - PackItem( new MessageInABottle() ); + PackItem(new SpecialFishingNet()); //Confirm? + } - PackItem( new SpecialFishingNet() ); //Confirm? - } + public Kraken(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a krakens corpse"; + public override string DefaultName => "a kraken"; - public override int TreasureMapLevel => 4; + public override int TreasureMapLevel => 4; - public Kraken( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/Lizardman.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/Lizardman.cs index 0a0334184..3afe5bf7a 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/Lizardman.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/Lizardman.cs @@ -2,68 +2,68 @@ using Server.Misc; namespace Server.Mobiles { - public class Lizardman : BaseCreature - { - public override string CorpseName => "a lizardman corpse"; - public override InhumanSpeech SpeechType => InhumanSpeech.Lizardman; + public class Lizardman : BaseCreature + { + [Constructible] + public Lizardman() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("lizardman"); + Body = Utility.RandomList(35, 36); + BaseSoundID = 417; - [Constructible] - public Lizardman() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "lizardman" ); - Body = Utility.RandomList( 35, 36 ); - BaseSoundID = 417; + SetStr(96, 120); + SetDex(86, 105); + SetInt(36, 60); - SetStr( 96, 120 ); - SetDex( 86, 105 ); - SetInt( 36, 60 ); + SetHits(58, 72); - SetHits( 58, 72 ); + SetDamage(5, 7); - SetDamage( 5, 7 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 5, 10); + SetResistance(ResistanceType.Cold, 5, 10); + SetResistance(ResistanceType.Poison, 10, 20); - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 5, 10 ); - SetResistance( ResistanceType.Cold, 5, 10 ); - SetResistance( ResistanceType.Poison, 10, 20 ); + SetSkill(SkillName.MagicResist, 35.1, 60.0); + SetSkill(SkillName.Tactics, 55.1, 80.0); + SetSkill(SkillName.Wrestling, 50.1, 70.0); - SetSkill( SkillName.MagicResist, 35.1, 60.0 ); - SetSkill( SkillName.Tactics, 55.1, 80.0 ); - SetSkill( SkillName.Wrestling, 50.1, 70.0 ); + Fame = 1500; + Karma = -1500; - Fame = 1500; - Karma = -1500; + VirtualArmor = 28; + } - VirtualArmor = 28; - } + public Lizardman(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - // TODO: weapon - } + public override string CorpseName => "a lizardman corpse"; + public override InhumanSpeech SpeechType => InhumanSpeech.Lizardman; - public override bool CanRummageCorpses => true; - public override int Meat => 1; - public override int Hides => 12; - public override HideType HideType => HideType.Spined; + public override bool CanRummageCorpses => true; + public override int Meat => 1; + public override int Hides => 12; + public override HideType HideType => HideType.Spined; - public Lizardman( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + // TODO: weapon + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianKnight.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianKnight.cs index 1f8f379b3..0b4c8a0d4 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianKnight.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianKnight.cs @@ -2,79 +2,81 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.OphidianAvenger" )] - public class OphidianKnight : BaseCreature - { - public override string CorpseName => "an ophidian corpse"; - private static string[] m_Names = { - "an ophidian knight-errant", - "an ophidian avenger" - }; + [TypeAlias("Server.Mobiles.OphidianAvenger")] + public class OphidianKnight : BaseCreature + { + private static string[] m_Names = + { + "an ophidian knight-errant", + "an ophidian avenger" + }; - [Constructible] - public OphidianKnight() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = m_Names[Utility.Random( m_Names.Length )]; - Body = 86; - BaseSoundID = 634; + [Constructible] + public OphidianKnight() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = m_Names[Utility.Random(m_Names.Length)]; + Body = 86; + BaseSoundID = 634; - SetStr( 417, 595 ); - SetDex( 166, 175 ); - SetInt( 46, 70 ); + SetStr(417, 595); + SetDex(166, 175); + SetInt(46, 70); - SetHits( 266, 342 ); - SetMana( 0 ); + SetHits(266, 342); + SetMana(0); - SetDamage( 16, 19 ); + SetDamage(16, 19); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 90, 100 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 90, 100); + SetResistance(ResistanceType.Energy, 35, 45); - SetSkill( SkillName.Poisoning, 60.1, 80.0 ); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + SetSkill(SkillName.Poisoning, 60.1, 80.0); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - Fame = 10000; - Karma = -10000; + Fame = 10000; + Karma = -10000; - VirtualArmor = 40; + VirtualArmor = 40; - PackItem( new LesserPoisonPotion() ); - } + PackItem(new LesserPoisonPotion()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 2 ); - } + public OphidianKnight(Serial serial) : base(serial) + { + } - public override int Meat => 2; + public override string CorpseName => "an ophidian corpse"; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; - public override int TreasureMapLevel => 3; + public override int Meat => 2; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; + public override int TreasureMapLevel => 3; - public OphidianKnight( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 2); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianWarrior.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianWarrior.cs index 9af09b752..fd9d7bede 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianWarrior.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/OphidianWarrior.cs @@ -1,73 +1,75 @@ namespace Server.Mobiles { - public class OphidianWarrior : BaseCreature - { - public override string CorpseName => "an ophidian corpse"; - private static string[] m_Names = { - "an ophidian warrior", - "an ophidian enforcer" - }; + public class OphidianWarrior : BaseCreature + { + private static string[] m_Names = + { + "an ophidian warrior", + "an ophidian enforcer" + }; - [Constructible] - public OphidianWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = m_Names[Utility.Random( m_Names.Length )]; - Body = 86; - BaseSoundID = 634; + [Constructible] + public OphidianWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = m_Names[Utility.Random(m_Names.Length)]; + Body = 86; + BaseSoundID = 634; - SetStr( 150, 320 ); - SetDex( 94, 190 ); - SetInt( 64, 160 ); + SetStr(150, 320); + SetDex(94, 190); + SetInt(64, 160); - SetHits( 128, 155 ); - SetMana( 0 ); + SetHits(128, 155); + SetMana(0); - SetDamage( 5, 11 ); + SetDamage(5, 11); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 25, 35 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 25, 35 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 25, 35); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 25, 35); - SetSkill( SkillName.MagicResist, 70.1, 85.0 ); - SetSkill( SkillName.Swords, 60.1, 85.0 ); - SetSkill( SkillName.Tactics, 75.1, 90.0 ); + SetSkill(SkillName.MagicResist, 70.1, 85.0); + SetSkill(SkillName.Swords, 60.1, 85.0); + SetSkill(SkillName.Tactics, 75.1, 90.0); - Fame = 4500; - Karma = -4500; + Fame = 4500; + Karma = -4500; - VirtualArmor = 36; - } + VirtualArmor = 36; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Average ); - AddLoot( LootPack.Gems ); - } + public OphidianWarrior(Serial serial) : base(serial) + { + } - public override int Meat => 1; - public override int TreasureMapLevel => 1; + public override string CorpseName => "an ophidian corpse"; - public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; + public override int Meat => 1; + public override int TreasureMapLevel => 1; - public OphidianWarrior( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.TerathansAndOphidians; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.Average); + AddLoot(LootPack.Gems); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/Scorpion.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/Scorpion.cs index c2e23dae5..33747189e 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/Scorpion.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/Scorpion.cs @@ -2,77 +2,77 @@ using Server.Items; namespace Server.Mobiles { - public class Scorpion : BaseCreature - { - public override string CorpseName => "a scorpion corpse"; - public override string DefaultName => "a scorpion"; + public class Scorpion : BaseCreature + { + [Constructible] + public Scorpion() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 48; + BaseSoundID = 397; - [Constructible] - public Scorpion() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 48; - BaseSoundID = 397; + SetStr(73, 115); + SetDex(76, 95); + SetInt(16, 30); - SetStr( 73, 115 ); - SetDex( 76, 95 ); - SetInt( 16, 30 ); + SetHits(50, 63); + SetMana(0); - SetHits( 50, 63 ); - SetMana( 0 ); + SetDamage(5, 10); - SetDamage( 5, 10 ); + SetDamageType(ResistanceType.Physical, 60); + SetDamageType(ResistanceType.Poison, 40); - SetDamageType( ResistanceType.Physical, 60 ); - SetDamageType( ResistanceType.Poison, 40 ); + SetResistance(ResistanceType.Physical, 20, 25); + SetResistance(ResistanceType.Fire, 10, 15); + SetResistance(ResistanceType.Cold, 20, 25); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 10, 15); - SetResistance( ResistanceType.Physical, 20, 25 ); - SetResistance( ResistanceType.Fire, 10, 15 ); - SetResistance( ResistanceType.Cold, 20, 25 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 10, 15 ); + SetSkill(SkillName.Poisoning, 80.1, 100.0); + SetSkill(SkillName.MagicResist, 30.1, 35.0); + SetSkill(SkillName.Tactics, 60.3, 75.0); + SetSkill(SkillName.Wrestling, 50.3, 65.0); - SetSkill( SkillName.Poisoning, 80.1, 100.0 ); - SetSkill( SkillName.MagicResist, 30.1, 35.0 ); - SetSkill( SkillName.Tactics, 60.3, 75.0 ); - SetSkill( SkillName.Wrestling, 50.3, 65.0 ); + Fame = 2000; + Karma = -2000; - Fame = 2000; - Karma = -2000; + VirtualArmor = 28; - VirtualArmor = 28; + Tamable = true; + ControlSlots = 1; + MinTameSkill = 47.1; - Tamable = true; - ControlSlots = 1; - MinTameSkill = 47.1; + PackItem(new LesserPoisonPotion()); + } - PackItem( new LesserPoisonPotion() ); - } + public Scorpion(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - } + public override string CorpseName => "a scorpion corpse"; + public override string DefaultName => "a scorpion"; - public override int Meat => 1; - public override FoodType FavoriteFood => FoodType.Meat; - public override PackInstinct PackInstinct => PackInstinct.Arachnid; - public override Poison PoisonImmune => Poison.Greater; - public override Poison HitPoison => (0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly); + public override int Meat => 1; + public override FoodType FavoriteFood => FoodType.Meat; + public override PackInstinct PackInstinct => PackInstinct.Arachnid; + public override Poison PoisonImmune => Poison.Greater; + public override Poison HitPoison => 0.8 >= Utility.RandomDouble() ? Poison.Greater : Poison.Deadly; - public Scorpion( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/StoneHarpy.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/StoneHarpy.cs index fc48a0bf1..251182231 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/StoneHarpy.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/StoneHarpy.cs @@ -1,93 +1,93 @@ namespace Server.Mobiles { - public class StoneHarpy : BaseCreature - { - public override string CorpseName => "a stone harpy corpse"; - public override string DefaultName => "a stone harpy"; + public class StoneHarpy : BaseCreature + { + [Constructible] + public StoneHarpy() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 73; + BaseSoundID = 402; - [Constructible] - public StoneHarpy() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 73; - BaseSoundID = 402; + SetStr(296, 320); + SetDex(86, 110); + SetInt(51, 75); - SetStr( 296, 320 ); - SetDex( 86, 110 ); - SetInt( 51, 75 ); + SetHits(178, 192); + SetMana(0); - SetHits( 178, 192 ); - SetMana( 0 ); + SetDamage(8, 16); - SetDamage( 8, 16 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Poison, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Poison, 25 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 10, 20); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 10, 20 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.MagicResist, 50.1, 65.0); + SetSkill(SkillName.Tactics, 70.1, 100.0); + SetSkill(SkillName.Wrestling, 70.1, 100.0); - SetSkill( SkillName.MagicResist, 50.1, 65.0 ); - SetSkill( SkillName.Tactics, 70.1, 100.0 ); - SetSkill( SkillName.Wrestling, 70.1, 100.0 ); + Fame = 4500; + Karma = -4500; - Fame = 4500; - Karma = -4500; + VirtualArmor = 50; + } - VirtualArmor = 50; - } + public StoneHarpy(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average, 2 ); - AddLoot( LootPack.Gems, 2 ); - } + public override string CorpseName => "a stone harpy corpse"; + public override string DefaultName => "a stone harpy"; - public override int GetAttackSound() - { - return 916; - } + public override int Meat => 1; + public override int Feathers => 50; + public override bool CanFly => true; - public override int GetAngerSound() - { - return 916; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average, 2); + AddLoot(LootPack.Gems, 2); + } - public override int GetDeathSound() - { - return 917; - } + public override int GetAttackSound() + { + return 916; + } - public override int GetHurtSound() - { - return 919; - } + public override int GetAngerSound() + { + return 916; + } - public override int GetIdleSound() - { - return 918; - } + public override int GetDeathSound() + { + return 917; + } - public override int Meat => 1; - public override int Feathers => 50; - public override bool CanFly => true; + public override int GetHurtSound() + { + return 919; + } - public StoneHarpy( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 918; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Reptile/Melee/Wyvern.cs b/Scripts/Mobiles/Monsters/Reptile/Melee/Wyvern.cs index fcc70355b..bbd88e358 100644 --- a/Scripts/Mobiles/Monsters/Reptile/Melee/Wyvern.cs +++ b/Scripts/Mobiles/Monsters/Reptile/Melee/Wyvern.cs @@ -2,104 +2,104 @@ using Server.Items; namespace Server.Mobiles { - public class Wyvern : BaseCreature - { - public override string CorpseName => "a wyvern corpse"; - public override string DefaultName => "a wyvern"; + public class Wyvern : BaseCreature + { + [Constructible] + public Wyvern() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 62; + BaseSoundID = 362; - [Constructible] - public Wyvern () : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 62; - BaseSoundID = 362; + SetStr(202, 240); + SetDex(153, 172); + SetInt(51, 90); - SetStr( 202, 240 ); - SetDex( 153, 172 ); - SetInt( 51, 90 ); + SetHits(125, 141); - SetHits( 125, 141 ); + SetDamage(8, 19); - SetDamage( 8, 19 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetResistance(ResistanceType.Physical, 35, 45); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 90, 100); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 35, 45 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 90, 100 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.Poisoning, 60.1, 80.0); + SetSkill(SkillName.MagicResist, 65.1, 80.0); + SetSkill(SkillName.Tactics, 65.1, 90.0); + SetSkill(SkillName.Wrestling, 65.1, 80.0); - SetSkill( SkillName.Poisoning, 60.1, 80.0 ); - SetSkill( SkillName.MagicResist, 65.1, 80.0 ); - SetSkill( SkillName.Tactics, 65.1, 90.0 ); - SetSkill( SkillName.Wrestling, 65.1, 80.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + VirtualArmor = 40; - VirtualArmor = 40; + PackItem(new LesserPoisonPotion()); + } - PackItem( new LesserPoisonPotion() ); - } + public Wyvern(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Meager ); - AddLoot( LootPack.MedScrolls ); - } + public override string CorpseName => "a wyvern corpse"; + public override string DefaultName => "a wyvern"; - public override bool ReacquireOnMovement => true; + public override bool ReacquireOnMovement => true; - public override Poison PoisonImmune => Poison.Deadly; - public override Poison HitPoison => Poison.Deadly; - public override int TreasureMapLevel => 2; + public override Poison PoisonImmune => Poison.Deadly; + public override Poison HitPoison => Poison.Deadly; + public override int TreasureMapLevel => 2; - public override int Meat => 10; - public override int Hides => 20; - public override HideType HideType => HideType.Horned; - public override bool CanFly => true; + public override int Meat => 10; + public override int Hides => 20; + public override HideType HideType => HideType.Horned; + public override bool CanFly => true; - public override int GetAttackSound() - { - return 713; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Meager); + AddLoot(LootPack.MedScrolls); + } - public override int GetAngerSound() - { - return 718; - } + public override int GetAttackSound() + { + return 713; + } - public override int GetDeathSound() - { - return 716; - } + public override int GetAngerSound() + { + return 718; + } - public override int GetHurtSound() - { - return 721; - } + public override int GetDeathSound() + { + return 716; + } - public override int GetIdleSound() - { - return 725; - } + public override int GetHurtSound() + { + return 721; + } - public Wyvern( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 725; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/BakeKitsune.cs b/Scripts/Mobiles/Monsters/SE/BakeKitsune.cs index 782170de5..6495f3ae9 100644 --- a/Scripts/Mobiles/Monsters/SE/BakeKitsune.cs +++ b/Scripts/Mobiles/Monsters/SE/BakeKitsune.cs @@ -1,276 +1,289 @@ using System; using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class BakeKitsune : BaseCreature - { - public override string CorpseName => "a bake kitsune corpse"; - public override string DefaultName => "a bake kitsune"; + public class BakeKitsune : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public BakeKitsune() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 246; + [Constructible] + public BakeKitsune() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 246; - SetStr( 171, 220 ); - SetDex( 126, 145 ); - SetInt( 376, 425 ); + SetStr(171, 220); + SetDex(126, 145); + SetInt(376, 425); - SetHits( 301, 350 ); + SetHits(301, 350); - SetDamage( 15, 22 ); + SetDamage(15, 22); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Energy, 30 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Energy, 30); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 70, 90 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); - SetResistance( ResistanceType.Energy, 40, 60 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 70, 90); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Poison, 40, 60); + SetResistance(ResistanceType.Energy, 40, 60); - SetSkill( SkillName.EvalInt, 80.1, 90.0 ); - SetSkill( SkillName.Magery, 80.1, 90.0 ); - SetSkill( SkillName.MagicResist, 80.1, 100.0 ); - SetSkill( SkillName.Tactics, 70.1, 90.0 ); - SetSkill( SkillName.Wrestling, 50.1, 55.0 ); + SetSkill(SkillName.EvalInt, 80.1, 90.0); + SetSkill(SkillName.Magery, 80.1, 90.0); + SetSkill(SkillName.MagicResist, 80.1, 100.0); + SetSkill(SkillName.Tactics, 70.1, 90.0); + SetSkill(SkillName.Wrestling, 50.1, 55.0); - Fame = 8000; - Karma = -8000; + Fame = 8000; + Karma = -8000; - Tamable = true; - ControlSlots = 2; - MinTameSkill = 80.7; + Tamable = true; + ControlSlots = 2; + MinTameSkill = 80.7; - if ( Utility.RandomDouble() < .25 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - } + if (Utility.RandomDouble() < .25) + PackItem(Seed.RandomBonsaiSeed()); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public BakeKitsune(Serial serial) : base(serial) + { + } - public override int Meat => 5; - public override int Hides => 10; - public override HideType HideType => HideType.Barbed; - public override FoodType FavoriteFood => FoodType.Fish; - public override bool ShowFameTitle => false; - public override bool ClickTitle => false; - public override bool PropertyTitle => false; + public override string CorpseName => "a bake kitsune corpse"; + public override string DefaultName => "a bake kitsune"; - public override void OnCombatantChange() - { - if ( Combatant == null && !IsBodyMod && !Controlled && m_DisguiseTimer == null && Utility.RandomBool() ) - m_DisguiseTimer = Timer.DelayCall( TimeSpan.FromSeconds( Utility.RandomMinMax( 15, 30 ) ), Disguise ); - } + public override int Meat => 5; + public override int Hides => 10; + public override HideType HideType => HideType.Barbed; + public override FoodType FavoriteFood => FoodType.Fish; + public override bool ShowFameTitle => false; + public override bool ClickTitle => false; + public override bool PropertyTitle => false; - public override bool OnBeforeDeath() - { - RemoveDisguise(); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls, 2); + } - return base.OnBeforeDeath(); - } + public override void OnCombatantChange() + { + if (Combatant == null && !IsBodyMod && !Controlled && m_DisguiseTimer == null && Utility.RandomBool()) + m_DisguiseTimer = Timer.DelayCall(TimeSpan.FromSeconds(Utility.RandomMinMax(15, 30)), Disguise); + } - #region Disguise - private Timer m_DisguiseTimer; + public override bool OnBeforeDeath() + { + RemoveDisguise(); - public void Disguise() - { - if ( Combatant != null || IsBodyMod || Controlled ) - return; + return base.OnBeforeDeath(); + } - FixedEffect( 0x376A, 8, 32 ); - PlaySound( 0x1FE ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - Female = Utility.RandomBool(); + if (0.1 > Utility.RandomDouble()) + { + /* Blood Bath + * Start cliloc 1070826 + * Sound: 0x52B + * 2-3 blood spots + * Damage: 2 hps per second for 5 seconds + * End cliloc: 1070824 + */ - if ( Female ) - { - BodyMod = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - BodyMod = 0x190; - Name = NameList.RandomName( "male" ); - } + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - Title = "the mystic llama herder"; - Hue = Race.Human.RandomSkinHue(); - HairItemID = Race.Human.RandomHair( this ); - HairHue = Race.Human.RandomHairHue(); - FacialHairItemID = Race.Human.RandomFacialHair( this ); - FacialHairHue = HairHue; + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070825); // The creature continues to rage! + } + else + { + defender.SendLocalizedMessage(1070826); // The creature goes into a rage, inflicting heavy damage! + } - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new Shoes( Utility.RandomNeutralHue() ) ); break; - case 1: AddItem( new Boots( Utility.RandomNeutralHue() ) ); break; - case 2: AddItem( new Sandals( Utility.RandomNeutralHue() ) ); break; - case 3: AddItem( new ThighBoots( Utility.RandomNeutralHue() ) ); break; - } + timer = new ExpireTimer(defender, this); + timer.Start(); + m_Table[defender] = timer; + } + } - AddItem( new Robe( Utility.RandomNondyedHue() ) ); + public override int GetAngerSound() + { + return 0x4DE; + } - m_DisguiseTimer = null; - m_DisguiseTimer = Timer.DelayCall( TimeSpan.FromSeconds( 75 ), RemoveDisguise ); - } + public override int GetIdleSound() + { + return 0x4DD; + } - public void RemoveDisguise() - { - if ( !IsBodyMod ) - return; + public override int GetAttackSound() + { + return 0x4DC; + } - Name = null; - Title = null; - BodyMod = 0; - Hue = 0; - HairItemID = 0; - HairHue = 0; - FacialHairItemID = 0; - FacialHairHue = 0; + public override int GetHurtSound() + { + return 0x4DF; + } - DeleteItemOnLayer( Layer.OuterTorso ); - DeleteItemOnLayer( Layer.Shoes ); + public override int GetDeathSound() + { + return 0x4DB; + } - m_DisguiseTimer = null; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - public void DeleteItemOnLayer( Layer layer ) - { - Item item = FindItemOnLayer( layer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - item?.Delete(); - } - #endregion + if (version == 0 && PhysicalResistance > 60) + { + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 70, 90); + SetResistance(ResistanceType.Cold, 40, 60); + SetResistance(ResistanceType.Poison, 40, 60); + SetResistance(ResistanceType.Energy, 40, 60); + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + Timer.DelayCall(TimeSpan.Zero, RemoveDisguise); + } - if ( 0.1 > Utility.RandomDouble() ) - { - /* Blood Bath - * Start cliloc 1070826 - * Sound: 0x52B - * 2-3 blood spots - * Damage: 2 hps per second for 5 seconds - * End cliloc: 1070824 - */ + private class ExpireTimer : Timer + { + private int m_Count; + private Mobile m_From; + private Mobile m_Mobile; - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + public ExpireTimer(Mobile m, Mobile from) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_From = from; + Priority = TimerPriority.TwoFiftyMS; + } - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070825 ); // The creature continues to rage! - } - else - defender.SendLocalizedMessage( 1070826 ); // The creature goes into a rage, inflicting heavy damage! + public void DoExpire() + { + Stop(); + m_Table.Remove(m_Mobile); + } - timer = new ExpireTimer( defender, this ); - timer.Start(); - m_Table[defender] = timer; - } - } + public void DrainLife() + { + if (m_Mobile.Alive) + m_Mobile.Damage(2, m_From); + else + DoExpire(); + } - private static Hashtable m_Table = new Hashtable(); + protected override void OnTick() + { + DrainLife(); - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private Mobile m_From; - private int m_Count; + if (++m_Count >= 5) + { + DoExpire(); + m_Mobile.SendLocalizedMessage(1070824); // The creature's rage subsides. + } + } + } - public ExpireTimer( Mobile m, Mobile from ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_From = from; - Priority = TimerPriority.TwoFiftyMS; - } + #region Disguise - public void DoExpire() - { - Stop(); - m_Table.Remove( m_Mobile ); - } + private Timer m_DisguiseTimer; - public void DrainLife() - { - if ( m_Mobile.Alive ) - m_Mobile.Damage( 2, m_From ); - else - DoExpire(); - } + public void Disguise() + { + if (Combatant != null || IsBodyMod || Controlled) + return; - protected override void OnTick() - { - DrainLife(); + FixedEffect(0x376A, 8, 32); + PlaySound(0x1FE); - if ( ++m_Count >= 5 ) - { - DoExpire(); - m_Mobile.SendLocalizedMessage( 1070824 ); // The creature's rage subsides. - } - } - } + Female = Utility.RandomBool(); - public override int GetAngerSound() - { - return 0x4DE; - } + if (Female) + { + BodyMod = 0x191; + Name = NameList.RandomName("female"); + } + else + { + BodyMod = 0x190; + Name = NameList.RandomName("male"); + } - public override int GetIdleSound() - { - return 0x4DD; - } + Title = "the mystic llama herder"; + Hue = Race.Human.RandomSkinHue(); + HairItemID = Race.Human.RandomHair(this); + HairHue = Race.Human.RandomHairHue(); + FacialHairItemID = Race.Human.RandomFacialHair(this); + FacialHairHue = HairHue; - public override int GetAttackSound() - { - return 0x4DC; - } + switch (Utility.Random(4)) + { + case 0: + AddItem(new Shoes(Utility.RandomNeutralHue())); + break; + case 1: + AddItem(new Boots(Utility.RandomNeutralHue())); + break; + case 2: + AddItem(new Sandals(Utility.RandomNeutralHue())); + break; + case 3: + AddItem(new ThighBoots(Utility.RandomNeutralHue())); + break; + } - public override int GetHurtSound() - { - return 0x4DF; - } + AddItem(new Robe(Utility.RandomNondyedHue())); - public override int GetDeathSound() - { - return 0x4DB; - } + m_DisguiseTimer = null; + m_DisguiseTimer = Timer.DelayCall(TimeSpan.FromSeconds(75), RemoveDisguise); + } - public BakeKitsune( Serial serial ) : base( serial ) - { - } + public void RemoveDisguise() + { + if (!IsBodyMod) + return; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + Name = null; + Title = null; + BodyMod = 0; + Hue = 0; + HairItemID = 0; + HairHue = 0; + FacialHairItemID = 0; + FacialHairHue = 0; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + DeleteItemOnLayer(Layer.OuterTorso); + DeleteItemOnLayer(Layer.Shoes); - if ( version == 0 && PhysicalResistance > 60 ) - { - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 70, 90 ); - SetResistance( ResistanceType.Cold, 40, 60 ); - SetResistance( ResistanceType.Poison, 40, 60 ); - SetResistance( ResistanceType.Energy, 40, 60 ); - } + m_DisguiseTimer = null; + } - Timer.DelayCall( TimeSpan.Zero, RemoveDisguise ); - } - } -} + public void DeleteItemOnLayer(Layer layer) + { + Item item = FindItemOnLayer(layer); + + item?.Delete(); + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/DeathWatchBeetle.cs b/Scripts/Mobiles/Monsters/SE/DeathWatchBeetle.cs index 2e22211bd..99c2aecc5 100644 --- a/Scripts/Mobiles/Monsters/SE/DeathWatchBeetle.cs +++ b/Scripts/Mobiles/Monsters/SE/DeathWatchBeetle.cs @@ -1,142 +1,161 @@ +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.DeathWatchBeetle" )] - public class DeathwatchBeetle : BaseCreature - { - public override string CorpseName => "a deathwatchbeetle corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.CrushingBlow; + [TypeAlias("Server.Mobiles.DeathWatchBeetle")] + public class DeathwatchBeetle : BaseCreature + { + [Constructible] + public DeathwatchBeetle() : base(AIType.AI_Melee, Core.ML ? FightMode.Aggressor : FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 242; - public override string DefaultName => "a deathwatch beetle"; + SetStr(136, 160); + SetDex(41, 52); + SetInt(31, 40); - [Constructible] - public DeathwatchBeetle() : base( AIType.AI_Melee, Core.ML ? FightMode.Aggressor : FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 242; + SetHits(121, 145); + SetMana(20); - SetStr( 136, 160 ); - SetDex( 41, 52 ); - SetInt( 31, 40 ); + SetDamage(5, 10); - SetHits( 121, 145 ); - SetMana( 20 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 5, 10 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 15, 30); + SetResistance(ResistanceType.Cold, 15, 30); + SetResistance(ResistanceType.Poison, 50, 80); + SetResistance(ResistanceType.Energy, 20, 35); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.MagicResist, 50.1, 58.0); + SetSkill(SkillName.Tactics, 67.1, 77.0); + SetSkill(SkillName.Wrestling, 50.1, 60.0); + SetSkill(SkillName.Anatomy, 30.1, 34.0); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 15, 30 ); - SetResistance( ResistanceType.Cold, 15, 30 ); - SetResistance( ResistanceType.Poison, 50, 80 ); - SetResistance( ResistanceType.Energy, 20, 35 ); + Fame = 1400; + Karma = -1400; - SetSkill( SkillName.MagicResist, 50.1, 58.0 ); - SetSkill( SkillName.Tactics, 67.1, 77.0 ); - SetSkill( SkillName.Wrestling, 50.1, 60.0 ); - SetSkill( SkillName.Anatomy, 30.1, 34.0 ); + switch (Utility.Random(12)) + { + case 0: + PackItem(new LeatherGorget()); + break; + case 1: + PackItem(new LeatherGloves()); + break; + case 2: + PackItem(new LeatherArms()); + break; + case 3: + PackItem(new LeatherLegs()); + break; + case 4: + PackItem(new LeatherCap()); + break; + case 5: + PackItem(new LeatherChest()); + break; + } - Fame = 1400; - Karma = -1400; + if (Utility.RandomDouble() < .5) + PackItem(Seed.RandomBonsaiSeed()); - switch ( Utility.Random( 12 ) ) - { - case 0: PackItem( new LeatherGorget() ); break; - case 1: PackItem( new LeatherGloves() ); break; - case 2: PackItem( new LeatherArms() ); break; - case 3: PackItem( new LeatherLegs() ); break; - case 4: PackItem( new LeatherCap() ); break; - case 5: PackItem( new LeatherChest() ); break; - } + Tamable = true; + MinTameSkill = 41.1; + ControlSlots = 1; + } - if ( Utility.RandomDouble() < .5 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); + public DeathwatchBeetle(Serial serial) : base(serial) + { + } - Tamable = true; - MinTameSkill = 41.1; - ControlSlots = 1; - } + public override string CorpseName => "a deathwatchbeetle corpse"; - public override int GetAngerSound() - { - return 0x4F3; - } + public override string DefaultName => "a deathwatch beetle"; - public override int GetIdleSound() - { - return 0x4F2; - } + public override int Hides => 8; - public override int GetAttackSound() - { - return 0x4F1; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.CrushingBlow; + } - public override int GetHurtSound() - { - return 0x4F4; - } + public override int GetAngerSound() + { + return 0x4F3; + } - public override int GetDeathSound() - { - return 0x4F0; - } + public override int GetIdleSound() + { + return 0x4F2; + } - public override void GenerateLoot() - { - AddLoot( LootPack.LowScrolls, 1 ); - AddLoot( LootPack.Potions, 1 ); - } + public override int GetAttackSound() + { + return 0x4F1; + } - public override void AlterMeleeDamageTo( Mobile to, ref int damage ) - { - if ( Utility.RandomBool() && (Mana > 14) && to != null ) - { - damage = (damage + (damage / 2)); - to.SendLocalizedMessage( 1060091 ); // You take extra damage from the crushing attack! - to.PlaySound( 0x1E1 ); - to.FixedParticles( 0x377A, 1, 32, 0x26da, 0, 0, 0 ); - Mana -= 15; - } - } + public override int GetHurtSound() + { + return 0x4F4; + } - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - Mobile combatant = Combatant; + public override int GetDeathSound() + { + return 0x4F0; + } - if ( combatant == null || combatant.Deleted || combatant.Map != Map || !InRange( combatant, 12 ) || !CanBeHarmful( combatant ) || !InLOS( combatant ) ) - return; + public override void GenerateLoot() + { + AddLoot(LootPack.LowScrolls, 1); + AddLoot(LootPack.Potions, 1); + } - if ( Utility.Random( 10 ) == 0 ) - PoisonAttack( combatant ); + public override void AlterMeleeDamageTo(Mobile to, ref int damage) + { + if (Utility.RandomBool() && Mana > 14 && to != null) + { + damage = damage + damage / 2; + to.SendLocalizedMessage(1060091); // You take extra damage from the crushing attack! + to.PlaySound(0x1E1); + to.FixedParticles(0x377A, 1, 32, 0x26da, 0, 0, 0); + Mana -= 15; + } + } - base.OnDamage( amount, from, willKill ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + Mobile combatant = Combatant; - public void PoisonAttack( Mobile m ) - { - DoHarmful( m ); - MovingParticles( m, 0x36D4, 1, 0, false, false, 0x3F, 0, 0x1F73, 1, 0, (EffectLayer)255, 0x100 ); - m.ApplyPoison( this, Poison.Regular ); - m.SendLocalizedMessage( 1070821, Name ); // %s spits a poisonous substance at you! - } + if (combatant == null || combatant.Deleted || combatant.Map != Map || !InRange(combatant, 12) || + !CanBeHarmful(combatant) || !InLOS(combatant)) + return; - public override int Hides => 8; - public DeathwatchBeetle( Serial serial ) : base( serial ) - { - } + if (Utility.Random(10) == 0) + PoisonAttack(combatant); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + base.OnDamage(amount, from, willKill); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public void PoisonAttack(Mobile m) + { + DoHarmful(m); + MovingParticles(m, 0x36D4, 1, 0, false, false, 0x3F, 0, 0x1F73, 1, 0, (EffectLayer)255, 0x100); + m.ApplyPoison(this, Poison.Regular); + m.SendLocalizedMessage(1070821, Name); // %s spits a poisonous substance at you! + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/DeathWatchBeetleHatchling.cs b/Scripts/Mobiles/Monsters/SE/DeathWatchBeetleHatchling.cs index 2273445be..3f0d21201 100644 --- a/Scripts/Mobiles/Monsters/SE/DeathWatchBeetleHatchling.cs +++ b/Scripts/Mobiles/Monsters/SE/DeathWatchBeetleHatchling.cs @@ -2,106 +2,120 @@ using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.DeathWatchBeetleHatchling" )] - public class DeathwatchBeetleHatchling : BaseCreature - { - public override string CorpseName => "a deathwatchbeetle hatchling corpse"; - public override string DefaultName => "a deathwatch beetle hatchling"; + [TypeAlias("Server.Mobiles.DeathWatchBeetleHatchling")] + public class DeathwatchBeetleHatchling : BaseCreature + { + [Constructible] + public DeathwatchBeetleHatchling() : base(AIType.AI_Melee, Core.ML ? FightMode.Aggressor : FightMode.Closest, 10, 1, + 0.2, 0.4) + { + Body = 242; - [Constructible] - public DeathwatchBeetleHatchling() : base( AIType.AI_Melee, Core.ML ? FightMode.Aggressor : FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 242; + SetStr(26, 50); + SetDex(41, 52); + SetInt(21, 30); - SetStr( 26, 50 ); - SetDex( 41, 52 ); - SetInt( 21, 30 ); + SetHits(51, 60); + SetMana(20); - SetHits( 51, 60 ); - SetMana( 20 ); + SetDamage(2, 8); - SetDamage( 2, 8 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 35, 40); + SetResistance(ResistanceType.Fire, 15, 30); + SetResistance(ResistanceType.Cold, 15, 30); + SetResistance(ResistanceType.Poison, 20, 40); + SetResistance(ResistanceType.Energy, 20, 35); - SetResistance( ResistanceType.Physical, 35, 40 ); - SetResistance( ResistanceType.Fire, 15, 30 ); - SetResistance( ResistanceType.Cold, 15, 30 ); - SetResistance( ResistanceType.Poison, 20, 40 ); - SetResistance( ResistanceType.Energy, 20, 35 ); + SetSkill(SkillName.Wrestling, 30.1, 40.0); + SetSkill(SkillName.Tactics, 47.1, 57.0); + SetSkill(SkillName.MagicResist, 30.1, 38.0); + SetSkill(SkillName.Anatomy, 20.1, 24.0); - SetSkill( SkillName.Wrestling, 30.1, 40.0 ); - SetSkill( SkillName.Tactics, 47.1, 57.0 ); - SetSkill( SkillName.MagicResist, 30.1, 38.0 ); - SetSkill( SkillName.Anatomy, 20.1, 24.0 ); - - Fame = 700; - Karma = -700; + Fame = 700; + Karma = -700; - if ( Utility.RandomBool() ) - { - Item i = Loot.RandomReagent(); - i.Amount = 3; - PackItem( i ); - } + if (Utility.RandomBool()) + { + Item i = Loot.RandomReagent(); + i.Amount = 3; + PackItem(i); + } - switch ( Utility.Random( 12 ) ) - { - case 0: PackItem( new LeatherGorget() ); break; - case 1: PackItem( new LeatherGloves() ); break; - case 2: PackItem( new LeatherArms() ); break; - case 3: PackItem( new LeatherLegs() ); break; - case 4: PackItem( new LeatherCap() ); break; - case 5: PackItem( new LeatherChest() ); break; - } - } + switch (Utility.Random(12)) + { + case 0: + PackItem(new LeatherGorget()); + break; + case 1: + PackItem(new LeatherGloves()); + break; + case 2: + PackItem(new LeatherArms()); + break; + case 3: + PackItem(new LeatherLegs()); + break; + case 4: + PackItem(new LeatherCap()); + break; + case 5: + PackItem(new LeatherChest()); + break; + } + } - public override int GetAngerSound() - { - return 0x4F3; - } + public DeathwatchBeetleHatchling(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x4F2; - } + public override string CorpseName => "a deathwatchbeetle hatchling corpse"; + public override string DefaultName => "a deathwatch beetle hatchling"; + public override int Hides => 8; - public override int GetAttackSound() - { - return 0x4F1; - } + public override int GetAngerSound() + { + return 0x4F3; + } - public override int GetHurtSound() - { - return 0x4F4; - } + public override int GetIdleSound() + { + return 0x4F2; + } - public override int GetDeathSound() - { - return 0x4F0; - } + public override int GetAttackSound() + { + return 0x4F1; + } - public override void GenerateLoot() - { - AddLoot( LootPack.LowScrolls, 1 ); - AddLoot( LootPack.Potions, 1 ); - } + public override int GetHurtSound() + { + return 0x4F4; + } - public DeathwatchBeetleHatchling( Serial serial ) : base( serial ) - { - } - public override int Hides => 8; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetDeathSound() + { + return 0x4F0; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void GenerateLoot() + { + AddLoot(LootPack.LowScrolls, 1); + AddLoot(LootPack.Potions, 1); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/EliteNinja.cs b/Scripts/Mobiles/Monsters/SE/EliteNinja.cs index 4c98d2bd0..c9d6f2ed1 100644 --- a/Scripts/Mobiles/Monsters/SE/EliteNinja.cs +++ b/Scripts/Mobiles/Monsters/SE/EliteNinja.cs @@ -2,118 +2,134 @@ using Server.Items; namespace Server.Mobiles { - public class EliteNinja : BaseCreature - { - public override bool ClickTitle => false; - public override string DefaultName => "an elite ninja"; + public class EliteNinja : BaseCreature + { + [Constructible] + public EliteNinja() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SpeechHue = Utility.RandomDyedHue(); + Hue = Utility.RandomSkinHue(); + Female = Utility.RandomBool(); - [Constructible] - public EliteNinja() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); - Female = Utility.RandomBool(); + Body = Female ? 0x191 : 0x190; - Body = Female ? 0x191 : 0x190; + SetHits(251, 350); - SetHits( 251, 350 ); + SetStr(126, 225); + SetDex(81, 95); + SetInt(151, 165); - SetStr( 126, 225 ); - SetDex( 81, 95 ); - SetInt( 151, 165 ); + SetDamage(12, 20); - SetDamage( 12, 20 ); + SetDamageType(ResistanceType.Physical, 65); + SetDamageType(ResistanceType.Fire, 15); + SetDamageType(ResistanceType.Poison, 15); + SetDamageType(ResistanceType.Energy, 5); - SetDamageType( ResistanceType.Physical, 65 ); - SetDamageType( ResistanceType.Fire, 15 ); - SetDamageType( ResistanceType.Poison, 15 ); - SetDamageType( ResistanceType.Energy, 5 ); + SetResistance(ResistanceType.Physical, 35, 65); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 25, 45); + SetResistance(ResistanceType.Poison, 40, 60); + SetResistance(ResistanceType.Energy, 35, 55); - SetResistance( ResistanceType.Physical, 35, 65 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 25, 45 ); - SetResistance( ResistanceType.Poison, 40, 60 ); - SetResistance( ResistanceType.Energy, 35, 55 ); - - SetSkill( SkillName.Anatomy, 105.0, 120.0 ); - SetSkill( SkillName.MagicResist, 80.0, 100.0 ); - SetSkill( SkillName.Tactics, 115.0, 130.0 ); - SetSkill( SkillName.Wrestling, 95.0, 120.0 ); - SetSkill( SkillName.Fencing, 95.0, 120.0 ); - SetSkill( SkillName.Macing, 95.0, 120.0 ); - SetSkill( SkillName.Swords, 95.0, 120.0 ); - SetSkill( SkillName.Ninjitsu, 95.0, 120.0 ); + SetSkill(SkillName.Anatomy, 105.0, 120.0); + SetSkill(SkillName.MagicResist, 80.0, 100.0); + SetSkill(SkillName.Tactics, 115.0, 130.0); + SetSkill(SkillName.Wrestling, 95.0, 120.0); + SetSkill(SkillName.Fencing, 95.0, 120.0); + SetSkill(SkillName.Macing, 95.0, 120.0); + SetSkill(SkillName.Swords, 95.0, 120.0); + SetSkill(SkillName.Ninjitsu, 95.0, 120.0); - Fame = 8500; - Karma = -8500; + Fame = 8500; + Karma = -8500; - /* TODO: - Uses Smokebombs - Hides - Stealths - Can use Ninjitsu Abilities - Can change weapons during a fight - */ + /* TODO: + Uses Smokebombs + Hides + Stealths + Can use Ninjitsu Abilities + Can change weapons during a fight + */ - AddItem( new NinjaTabi() ); - AddItem( new LeatherNinjaJacket()); - AddItem( new LeatherNinjaHood()); - AddItem( new LeatherNinjaPants()); - AddItem( new LeatherNinjaMitts()); + AddItem(new NinjaTabi()); + AddItem(new LeatherNinjaJacket()); + AddItem(new LeatherNinjaHood()); + AddItem(new LeatherNinjaPants()); + AddItem(new LeatherNinjaMitts()); - if ( Utility.RandomDouble() < 0.33 ) - AddItem( new SmokeBomb() ); + if (Utility.RandomDouble() < 0.33) + AddItem(new SmokeBomb()); - switch ( Utility.Random( 8 )) - { - case 0: AddItem( new Tessen() ); break; - case 1: AddItem( new Wakizashi() ); break; - case 2: AddItem( new Nunchaku() ); break; - case 3: AddItem( new Daisho() ); break; - case 4: AddItem( new Sai() ); break; - case 5: AddItem( new Tekagi() ); break; - case 6: AddItem( new Kama() ); break; - case 7: AddItem( new Katana() ); break; - } + switch (Utility.Random(8)) + { + case 0: + AddItem(new Tessen()); + break; + case 1: + AddItem(new Wakizashi()); + break; + case 2: + AddItem(new Nunchaku()); + break; + case 3: + AddItem(new Daisho()); + break; + case 4: + AddItem(new Sai()); + break; + case 5: + AddItem(new Tekagi()); + break; + case 6: + AddItem(new Kama()); + break; + case 7: + AddItem(new Katana()); + break; + } - Utility.AssignRandomHair( this ); - } + Utility.AssignRandomHair(this); + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); - c.DropItem( new BookOfNinjitsu() ); - } + public EliteNinja(Serial serial) : base(serial) + { + } - public override bool BardImmune => true; + public override bool ClickTitle => false; + public override string DefaultName => "an elite ninja"; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 2 ); - } + public override bool BardImmune => true; - public override bool AlwaysMurderer => true; + public override bool AlwaysMurderer => true; - public EliteNinja( Serial serial ) : base( serial ) - { - } + public override void OnDeath(Container c) + { + base.OnDeath(c); + c.DropItem(new BookOfNinjitsu()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 2); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/FanDancer.cs b/Scripts/Mobiles/Monsters/SE/FanDancer.cs index ea2d76227..f588561ef 100644 --- a/Scripts/Mobiles/Monsters/SE/FanDancer.cs +++ b/Scripts/Mobiles/Monsters/SE/FanDancer.cs @@ -1,182 +1,189 @@ using System; using System.Collections; -using Server.Network; +using Server.Engines.Plants; using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class FanDancer : BaseCreature - { - public override string CorpseName => "a fan dancer corpse"; - public override string DefaultName => "a fan dancer"; - [Constructible] - public FanDancer() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 247; - BaseSoundID = 0x372; + public class FanDancer : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - SetStr( 301, 375 ); - SetDex( 201, 255 ); - SetInt( 21, 25 ); + [Constructible] + public FanDancer() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 247; + BaseSoundID = 0x372; - SetHits( 351, 430 ); + SetStr(301, 375); + SetDex(201, 255); + SetInt(21, 25); - SetDamage( 12, 17 ); + SetHits(351, 430); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Cold, 10 ); - SetDamageType( ResistanceType.Poison, 10 ); + SetDamage(12, 17); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 50, 70 ); - SetResistance( ResistanceType.Cold, 50, 70 ); - SetResistance( ResistanceType.Poison, 50, 70 ); - SetResistance( ResistanceType.Energy, 40, 60 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Cold, 10); + SetDamageType(ResistanceType.Poison, 10); - SetSkill( SkillName.MagicResist, 100.1, 110.0 ); - SetSkill( SkillName.Tactics, 85.1, 95.0 ); - SetSkill( SkillName.Wrestling, 85.1, 95.0 ); - SetSkill( SkillName.Anatomy, 85.1, 95.0 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 50, 70); + SetResistance(ResistanceType.Cold, 50, 70); + SetResistance(ResistanceType.Poison, 50, 70); + SetResistance(ResistanceType.Energy, 40, 60); - Fame = 9000; - Karma = -9000; + SetSkill(SkillName.MagicResist, 100.1, 110.0); + SetSkill(SkillName.Tactics, 85.1, 95.0); + SetSkill(SkillName.Wrestling, 85.1, 95.0); + SetSkill(SkillName.Anatomy, 85.1, 95.0); - if ( Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); + Fame = 9000; + Karma = -9000; - AddItem( new Tessen() ); + if (Utility.RandomDouble() < .33) + PackItem(Seed.RandomBonsaiSeed()); - if ( 0.02 >= Utility.RandomDouble() ) - PackItem( new OrigamiPaper() ); - } + AddItem(new Tessen()); + + if (0.02 >= Utility.RandomDouble()) + PackItem(new OrigamiPaper()); + } + + public FanDancer(Serial serial) : base(serial) + { + } + + public override string CorpseName => "a fan dancer corpse"; + public override string DefaultName => "a fan dancer"; + + public override bool Uncalmable => true; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 2 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 2); + } - public override bool Uncalmable => true; + /* TODO: Repel Magic + * 10% chance of repelling a melee attack (why did they call it repel magic anyway?) + * Cliloc: 1070844 + * Effect: damage is dealt to the attacker, no damage is taken by the fan dancer + */ - /* TODO: Repel Magic - * 10% chance of repelling a melee attack (why did they call it repel magic anyway?) - * Cliloc: 1070844 - * Effect: damage is dealt to the attacker, no damage is taken by the fan dancer - */ + public override void OnDamagedBySpell(Mobile attacker) + { + base.OnDamagedBySpell(attacker); - public override void OnDamagedBySpell( Mobile attacker ) - { - base.OnDamagedBySpell( attacker ); + if (0.8 > Utility.RandomDouble() && !attacker.InRange(this, 1)) + { + /* Fan Throw + * Effect: - To: "0x57D4F5B" - ItemId: "0x27A3" - ItemIdName: "Tessen" - FromLocation: "(992 299, 24)" - ToLocation: "(992 308, 22)" - Speed: "10" - Duration: "0" - FixedDirection: "False" - Explode: "False" - Hue: "0x0" - Render: "0x0" + * Damage: 50-65 + */ + Effects.SendPacket(attacker, attacker.Map, + new HuedEffect(EffectType.Moving, Serial.Zero, Serial.Zero, 0x27A3, Location, attacker.Location, 10, 0, + false, false, 0, 0)); + AOS.Damage(attacker, this, Utility.RandomMinMax(50, 65), 100, 0, 0, 0, 0); + } + } - if ( 0.8 > Utility.RandomDouble() && !attacker.InRange( this, 1 ) ) - { - /* Fan Throw - * Effect: - To: "0x57D4F5B" - ItemId: "0x27A3" - ItemIdName: "Tessen" - FromLocation: "(992 299, 24)" - ToLocation: "(992 308, 22)" - Speed: "10" - Duration: "0" - FixedDirection: "False" - Explode: "False" - Hue: "0x0" - Render: "0x0" - * Damage: 50-65 - */ - Effects.SendPacket( attacker, attacker.Map, new HuedEffect( EffectType.Moving, Serial.Zero, Serial.Zero, 0x27A3, Location, attacker.Location, 10, 0, false, false, 0, 0 ) ); - AOS.Damage( attacker, this, Utility.RandomMinMax( 50, 65 ), 100, 0, 0, 0, 0 ); - } - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + if (0.8 > Utility.RandomDouble() && !attacker.InRange(this, 1)) + { + /* Fan Throw + * Effect: - To: "0x57D4F5B" - ItemId: "0x27A3" - ItemIdName: "Tessen" - FromLocation: "(992 299, 24)" - ToLocation: "(992 308, 22)" - Speed: "10" - Duration: "0" - FixedDirection: "False" - Explode: "False" - Hue: "0x0" - Render: "0x0" + * Damage: 50-65 + */ + Effects.SendPacket(attacker, attacker.Map, + new HuedEffect(EffectType.Moving, Serial.Zero, Serial.Zero, 0x27A3, Location, attacker.Location, 10, 0, + false, false, 0, 0)); + AOS.Damage(attacker, this, Utility.RandomMinMax(50, 65), 100, 0, 0, 0, 0); + } + } - if ( 0.8 > Utility.RandomDouble() && !attacker.InRange( this, 1 ) ) - { - /* Fan Throw - * Effect: - To: "0x57D4F5B" - ItemId: "0x27A3" - ItemIdName: "Tessen" - FromLocation: "(992 299, 24)" - ToLocation: "(992 308, 22)" - Speed: "10" - Duration: "0" - FixedDirection: "False" - Explode: "False" - Hue: "0x0" - Render: "0x0" - * Damage: 50-65 - */ - Effects.SendPacket( attacker, attacker.Map, new HuedEffect( EffectType.Moving, Serial.Zero, Serial.Zero, 0x27A3, Location, attacker.Location, 10, 0, false, false, 0, 0 ) ); - AOS.Damage( attacker, this, Utility.RandomMinMax( 50, 65 ), 100, 0, 0, 0, 0 ); - } - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + if (!IsFanned(defender) && 0.05 > Utility.RandomDouble()) + { + /* Fanning Fire + * Graphic: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x3709" ItemIdName: "fire column" FromLocation: "(994 325, 16)" ToLocation: "(994 325, 16)" Speed: "10" Duration: "30" FixedDirection: "True" Explode: "False" Hue: "0x0" RenderMode: "0x0" Effect: "0x34" ExplodeEffect: "0x1" ExplodeSound: "0x0" Serial: "0x57D4F5B" Layer: "5" Unknown: "0x0" + * Sound: 0x208 + * Start cliloc: 1070833 + * Effect: Fire res -10% for 10 seconds + * Damage: 35-45, 100% fire + * End cliloc: 1070834 + * Effect does not stack + */ - if ( !IsFanned( defender ) && 0.05 > Utility.RandomDouble() ) - { - /* Fanning Fire - * Graphic: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x3709" ItemIdName: "fire column" FromLocation: "(994 325, 16)" ToLocation: "(994 325, 16)" Speed: "10" Duration: "30" FixedDirection: "True" Explode: "False" Hue: "0x0" RenderMode: "0x0" Effect: "0x34" ExplodeEffect: "0x1" ExplodeSound: "0x0" Serial: "0x57D4F5B" Layer: "5" Unknown: "0x0" - * Sound: 0x208 - * Start cliloc: 1070833 - * Effect: Fire res -10% for 10 seconds - * Damage: 35-45, 100% fire - * End cliloc: 1070834 - * Effect does not stack - */ + defender.SendLocalizedMessage( + 1070833); // The creature fans you with fire, reducing your resistance to fire attacks. - defender.SendLocalizedMessage( 1070833 ); // The creature fans you with fire, reducing your resistance to fire attacks. + int effect = -(defender.FireResistance / 10); - int effect = -(defender.FireResistance / 10); + ResistanceMod mod = new ResistanceMod(ResistanceType.Fire, effect); - ResistanceMod mod = new ResistanceMod( ResistanceType.Fire, effect ); + defender.FixedParticles(0x37B9, 10, 30, 0x34, EffectLayer.RightFoot); + defender.PlaySound(0x208); - defender.FixedParticles( 0x37B9, 10, 30, 0x34, EffectLayer.RightFoot ); - defender.PlaySound( 0x208 ); + // This should be done in place of the normal attack damage. + //AOS.Damage( defender, this, Utility.RandomMinMax( 35, 45 ), 0, 100, 0, 0, 0 ); - // This should be done in place of the normal attack damage. - //AOS.Damage( defender, this, Utility.RandomMinMax( 35, 45 ), 0, 100, 0, 0, 0 ); + defender.AddResistanceMod(mod); - defender.AddResistanceMod( mod ); + ExpireTimer timer = new ExpireTimer(defender, mod, TimeSpan.FromSeconds(10.0)); + timer.Start(); + m_Table[defender] = timer; + } + } - ExpireTimer timer = new ExpireTimer( defender, mod, TimeSpan.FromSeconds( 10.0 ) ); - timer.Start(); - m_Table[defender] = timer; - } - } + public bool IsFanned(Mobile m) + { + return m_Table.Contains(m); + } - private static Hashtable m_Table = new Hashtable(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public bool IsFanned( Mobile m ) - { - return m_Table.Contains( m ); - } + writer.Write(0); // version + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod m_Mod; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public ExpireTimer( Mobile m, ResistanceMod mod, TimeSpan delay ) : base( delay ) - { - m_Mobile = m; - m_Mod = mod; - Priority = TimerPriority.TwoFiftyMS; - } + int version = reader.ReadInt(); + } - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1070834 ); // Your resistance to fire attacks has returned. - m_Mobile.RemoveResistanceMod( m_Mod ); - Stop(); - m_Table.Remove( m_Mobile ); - } - } + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod m_Mod; - public FanDancer( Serial serial ) : base( serial ) - { - } + public ExpireTimer(Mobile m, ResistanceMod mod, TimeSpan delay) : base(delay) + { + m_Mobile = m; + m_Mod = mod; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1070834); // Your resistance to fire attacks has returned. + m_Mobile.RemoveResistanceMod(m_Mod); + Stop(); + m_Table.Remove(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/FireBeetle.cs b/Scripts/Mobiles/Monsters/SE/FireBeetle.cs index 5f46f17a7..bab9cddea 100644 --- a/Scripts/Mobiles/Monsters/SE/FireBeetle.cs +++ b/Scripts/Mobiles/Monsters/SE/FireBeetle.cs @@ -1,123 +1,124 @@ +using Server.Engines.Craft; using Server.Items; namespace Server.Mobiles { - [Engines.Craft.Forge] - public class FireBeetle : BaseMount - { - public override string CorpseName => "a fire beetle corpse"; - public override bool SubdueBeforeTame => true; // Must be beaten into submission - public override bool StatLossAfterTame => true; - public virtual double BoostedSpeed => 0.1; - public override bool ReduceSpeedWithDamage => false; + [Forge] + public class FireBeetle : BaseMount + { + [Constructible] + public FireBeetle() : base("a fire beetle", 0xA9, 0x3E95, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SetStr(300); + SetDex(100); + SetInt(500); - [Constructible] - public FireBeetle() : base( "a fire beetle", 0xA9, 0x3E95, AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SetStr( 300 ); - SetDex( 100 ); - SetInt( 500 ); + SetHits(200); - SetHits( 200 ); + SetDamage(7, 20); - SetDamage( 7, 20 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Fire, 100); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Fire, 100 ); + SetResistance(ResistanceType.Physical, 40); + SetResistance(ResistanceType.Fire, 70, 75); + SetResistance(ResistanceType.Cold, 10); + SetResistance(ResistanceType.Poison, 30); + SetResistance(ResistanceType.Energy, 30); - SetResistance( ResistanceType.Physical, 40 ); - SetResistance( ResistanceType.Fire, 70, 75 ); - SetResistance( ResistanceType.Cold, 10 ); - SetResistance( ResistanceType.Poison, 30 ); - SetResistance( ResistanceType.Energy, 30 ); + SetSkill(SkillName.MagicResist, 90.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - SetSkill( SkillName.MagicResist, 90.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + Fame = 4000; + Karma = -4000; - Fame = 4000; - Karma = -4000; + Tamable = true; + ControlSlots = 3; + MinTameSkill = 93.9; - Tamable = true; - ControlSlots = 3; - MinTameSkill = 93.9; + PackItem(new SulfurousAsh(Utility.RandomMinMax(16, 25))); + PackItem(new IronIngot(2)); - PackItem( new SulfurousAsh( Utility.RandomMinMax( 16, 25 ) ) ); - PackItem( new IronIngot( 2 ) ); + Hue = 0x489; + } - Hue = 0x489; - } + public FireBeetle(Serial serial) : base(serial) + { + } - public override void OnHarmfulSpell( Mobile from ) - { - if ( !Controlled && ControlMaster == null ) - CurrentSpeed = BoostedSpeed; - } - - public override void OnCombatantChange() - { - if ( Combatant == null && !Controlled && ControlMaster == null ) - CurrentSpeed = PassiveSpeed; - } - - public override bool OverrideBondingReqs() - { - return true; - } - - public override int GetAngerSound() - { - return 0x21D; - } - - public override int GetIdleSound() - { - return 0x21D; - } - - public override int GetAttackSound() - { - return 0x162; - } - - public override int GetHurtSound() - { - return 0x163; - } - - public override int GetDeathSound() - { - return 0x21D; - } + public override string CorpseName => "a fire beetle corpse"; + public override bool SubdueBeforeTame => true; // Must be beaten into submission + public override bool StatLossAfterTame => true; + public virtual double BoostedSpeed => 0.1; + public override bool ReduceSpeedWithDamage => false; - public override int Meat => 16; - public override FoodType FavoriteFood => FoodType.Meat; + public override int Meat => 16; + public override FoodType FavoriteFood => FoodType.Meat; - public override double GetControlChance( Mobile m, bool useBaseSkill ) - { - return 1.0; - } + public override void OnHarmfulSpell(Mobile from) + { + if (!Controlled && ControlMaster == null) + CurrentSpeed = BoostedSpeed; + } - public FireBeetle( Serial serial ) : base( serial ) - { - } + public override void OnCombatantChange() + { + if (Combatant == null && !Controlled && ControlMaster == null) + CurrentSpeed = PassiveSpeed; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool OverrideBondingReqs() + { + return true; + } - writer.Write( (int) 1 ); // version - } + public override int GetAngerSound() + { + return 0x21D; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int GetIdleSound() + { + return 0x21D; + } - int version = reader.ReadInt(); + public override int GetAttackSound() + { + return 0x162; + } - if ( version == 0 ) - Hue = 0x489; - } - } -} + public override int GetHurtSound() + { + return 0x163; + } + + public override int GetDeathSound() + { + return 0x21D; + } + + public override double GetControlChance(Mobile m, bool useBaseSkill) + { + return 1.0; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (version == 0) + Hue = 0x489; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/Kappa.cs b/Scripts/Mobiles/Monsters/SE/Kappa.cs index 6d4a71c62..757bff0e5 100644 --- a/Scripts/Mobiles/Monsters/SE/Kappa.cs +++ b/Scripts/Mobiles/Monsters/SE/Kappa.cs @@ -1,216 +1,218 @@ using System; using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class Kappa : BaseCreature - { - public override string CorpseName => "a kappa corpse"; - public override string DefaultName => "a kappa"; + public class Kappa : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public Kappa() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 240; + [Constructible] + public Kappa() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 240; - SetStr( 186, 230 ); - SetDex( 51, 75 ); - SetInt( 41, 55 ); + SetStr(186, 230); + SetDex(51, 75); + SetInt(41, 55); - SetMana ( 30 ); + SetMana(30); - SetHits( 151, 180 ); + SetHits(151, 180); - SetDamage( 6, 12 ); + SetDamage(6, 12); - SetDamageType( ResistanceType.Physical, 100 ); + SetDamageType(ResistanceType.Physical, 100); - SetResistance( ResistanceType.Physical, 35, 50 ); - SetResistance( ResistanceType.Fire, 35, 50 ); - SetResistance( ResistanceType.Cold, 25, 50 ); - SetResistance( ResistanceType.Poison, 35, 50 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + SetResistance(ResistanceType.Physical, 35, 50); + SetResistance(ResistanceType.Fire, 35, 50); + SetResistance(ResistanceType.Cold, 25, 50); + SetResistance(ResistanceType.Poison, 35, 50); + SetResistance(ResistanceType.Energy, 20, 30); - SetSkill( SkillName.MagicResist, 60.1, 70.0 ); - SetSkill( SkillName.Tactics, 79.1, 89.0 ); - SetSkill( SkillName.Wrestling, 60.1, 70.0 ); + SetSkill(SkillName.MagicResist, 60.1, 70.0); + SetSkill(SkillName.Tactics, 79.1, 89.0); + SetSkill(SkillName.Wrestling, 60.1, 70.0); - Fame = 1700; - Karma = -1700; + Fame = 1700; + Karma = -1700; - PackItem( new RawFishSteak( 3 ) ); - for( int i = 0; i < 2; i++ ) - { - switch ( Utility.Random( 6 ) ) - { - case 0: PackItem( new Gears() ); break; - case 1: PackItem( new Hinge() ); break; - case 2: PackItem( new Axle() ); break; - } - } - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(4) ); - } + PackItem(new RawFishSteak(3)); + for (int i = 0; i < 2; i++) + switch (Utility.Random(6)) + { + case 0: + PackItem(new Gears()); + break; + case 1: + PackItem(new Hinge()); + break; + case 2: + PackItem(new Axle()); + break; + } + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(4)); + } - public override void GenerateLoot() - { - AddLoot( LootPack.Meager ); - AddLoot( LootPack.Average ); - } + public Kappa(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x50B; - } + public override string CorpseName => "a kappa corpse"; + public override string DefaultName => "a kappa"; - public override int GetIdleSound() - { - return 0x50A; - } + public override void GenerateLoot() + { + AddLoot(LootPack.Meager); + AddLoot(LootPack.Average); + } - public override int GetAttackSound() - { - return 0x509; - } + public override int GetAngerSound() + { + return 0x50B; + } - public override int GetHurtSound() - { - return 0x50C; - } + public override int GetIdleSound() + { + return 0x50A; + } - public override int GetDeathSound() - { - return 0x508; - } + public override int GetAttackSound() + { + return 0x509; + } - public override void OnGaveMeleeAttack(Mobile defender) - { - base.OnGaveMeleeAttack (defender); + public override int GetHurtSound() + { + return 0x50C; + } - if ( Utility.RandomBool() ) - { - if ( !IsBeingDrained( defender ) && Mana > 14) - { - defender.SendLocalizedMessage( 1070848 ); // You feel your life force being stolen away. - BeginLifeDrain( defender, this ); - Mana-=15; - } - } - } + public override int GetDeathSound() + { + return 0x508; + } - private static Hashtable m_Table = new Hashtable(); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public static bool IsBeingDrained( Mobile m ) - { - return m_Table.Contains( m ); - } + if (Utility.RandomBool()) + if (!IsBeingDrained(defender) && Mana > 14) + { + defender.SendLocalizedMessage(1070848); // You feel your life force being stolen away. + BeginLifeDrain(defender, this); + Mana -= 15; + } + } - public static void BeginLifeDrain( Mobile m, Mobile from ) - { - Timer t = (Timer)m_Table[m]; + public static bool IsBeingDrained(Mobile m) + { + return m_Table.Contains(m); + } - t?.Stop(); + public static void BeginLifeDrain(Mobile m, Mobile from) + { + Timer t = (Timer)m_Table[m]; - t = new InternalTimer( from, m ); - m_Table[m] = t; + t?.Stop(); - t.Start(); - } + t = new InternalTimer(from, m); + m_Table[m] = t; - public static void DrainLife( Mobile m, Mobile from ) - { - if ( m.Alive ) - { - int damageGiven = AOS.Damage( m, from, 5, 0, 0, 0, 0, 100 ); - from.Hits += damageGiven; - } - else - { - EndLifeDrain( m ); - } - } + t.Start(); + } - public static void EndLifeDrain( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + public static void DrainLife(Mobile m, Mobile from) + { + if (m.Alive) + { + int damageGiven = AOS.Damage(m, from, 5, 0, 0, 0, 0, 100); + from.Hits += damageGiven; + } + else + { + EndLifeDrain(m); + } + } - t?.Stop(); + public static void EndLifeDrain(Mobile m) + { + Timer t = (Timer)m_Table[m]; - m_Table.Remove( m ); + t?.Stop(); - m.SendLocalizedMessage( 1070849 ); // The drain on your life force is gone. - } + m_Table.Remove(m); - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - if ( from?.Map != null ) - { - int amt=0; - Mobile target = this; - int rand = Utility.Random( 1, 100 ); - if ( willKill ) - { - amt = ((( rand % 5 ) >> 2 ) + 3); - } - if ( ( Hits < 100 ) && ( rand < 21 ) ) - { - target = ( rand % 2 ) < 1 ? this : from; - amt++; - } - if ( amt > 0 ) - { - SpillAcid( target, amt ); - from.SendLocalizedMessage( 1070820 ); - if ( Mana > 14) - Mana -= 15; - amt ^= amt; - } - } - base.OnDamage( amount, from, willKill ); - } + m.SendLocalizedMessage(1070849); // The drain on your life force is gone. + } - public override Item NewHarmfulItem() - { - return new AcidSlime( TimeSpan.FromSeconds(10), 5, 10 ); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + if (from?.Map != null) + { + int amt = 0; + Mobile target = this; + int rand = Utility.Random(1, 100); + if (willKill) amt = ((rand % 5) >> 2) + 3; + if (Hits < 100 && rand < 21) + { + target = rand % 2 < 1 ? this : from; + amt++; + } - public Kappa( Serial serial ) : base( serial ) - { - } + if (amt > 0) + { + SpillAcid(target, amt); + from.SendLocalizedMessage(1070820); + if (Mana > 14) + Mana -= 15; + amt ^= amt; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + base.OnDamage(amount, from, willKill); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override Item NewHarmfulItem() + { + return new AcidSlime(TimeSpan.FromSeconds(10), 5, 10); + } - private class InternalTimer : Timer - { - private Mobile m_From; - private Mobile m_Mobile; - private int m_Count; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public InternalTimer( Mobile from, Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_From = from; - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - protected override void OnTick() - { - DrainLife( m_Mobile, m_From ); + private class InternalTimer : Timer + { + private int m_Count; + private Mobile m_From; + private Mobile m_Mobile; - if ( Running && ++m_Count == 5 ) - EndLifeDrain( m_Mobile ); - } - } - } -} + public InternalTimer(Mobile from, Mobile m) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_From = from; + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } + + protected override void OnTick() + { + DrainLife(m_Mobile, m_From); + + if (Running && ++m_Count == 5) + EndLifeDrain(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/KazeKemono.cs b/Scripts/Mobiles/Monsters/SE/KazeKemono.cs index 7cfd57208..40fc9b8e5 100644 --- a/Scripts/Mobiles/Monsters/SE/KazeKemono.cs +++ b/Scripts/Mobiles/Monsters/SE/KazeKemono.cs @@ -3,172 +3,178 @@ using System.Collections; namespace Server.Mobiles { - public class KazeKemono : BaseCreature - { - public override string CorpseName => "a kaze kemono corpse"; - public override string DefaultName => "a kaze kemono"; + public class KazeKemono : BaseCreature + { + private static Hashtable m_FlurryOfTwigsTable = new Hashtable(); + private static Hashtable m_ChlorophylBlastTable = new Hashtable(); - [Constructible] - public KazeKemono() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 196; - BaseSoundID = 655; + [Constructible] + public KazeKemono() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 196; + BaseSoundID = 655; - SetStr( 201, 275 ); - SetDex( 101, 155 ); - SetInt( 101, 105 ); + SetStr(201, 275); + SetDex(101, 155); + SetInt(101, 105); - SetHits( 251, 330 ); + SetHits(251, 330); - SetDamage( 15, 20 ); + SetDamage(15, 20); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Cold, 10 ); - SetDamageType( ResistanceType.Poison, 10 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Cold, 10); + SetDamageType(ResistanceType.Poison, 10); - SetResistance( ResistanceType.Physical, 50, 70 ); - SetResistance( ResistanceType.Fire, 30, 60 ); - SetResistance( ResistanceType.Cold, 30, 60 ); - SetResistance( ResistanceType.Poison, 50, 70 ); - SetResistance( ResistanceType.Energy, 60, 80 ); + SetResistance(ResistanceType.Physical, 50, 70); + SetResistance(ResistanceType.Fire, 30, 60); + SetResistance(ResistanceType.Cold, 30, 60); + SetResistance(ResistanceType.Poison, 50, 70); + SetResistance(ResistanceType.Energy, 60, 80); - SetSkill( SkillName.MagicResist, 110.1, 125.0 ); - SetSkill( SkillName.Tactics, 55.1, 65.0 ); - SetSkill( SkillName.Wrestling, 85.1, 95.0 ); - SetSkill( SkillName.Anatomy, 25.1, 35.0 ); - SetSkill( SkillName.Magery, 95.1, 105.0 ); + SetSkill(SkillName.MagicResist, 110.1, 125.0); + SetSkill(SkillName.Tactics, 55.1, 65.0); + SetSkill(SkillName.Wrestling, 85.1, 95.0); + SetSkill(SkillName.Anatomy, 25.1, 35.0); + SetSkill(SkillName.Magery, 95.1, 105.0); - Fame = 8000; - Karma = -8000; - } + Fame = 8000; + Karma = -8000; + } + + public KazeKemono(Serial serial) + : base(serial) + { + } + + public override string CorpseName => "a kaze kemono corpse"; + public override string DefaultName => "a kaze kemono"; + + public override bool BleedImmune => true; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 3 ); - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 3); + } - public override bool BleedImmune => true; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + if (0.1 > Utility.RandomDouble()) + { + /* Flurry of Twigs + * Start cliloc: 1070850 + * Effect: Physical resistance -15% for 5 seconds + * End cliloc: 1070852 + * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(1048 779, 6)" ToLocation: "(1048 779, 6)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + */ - if ( 0.1 > Utility.RandomDouble() ) - { - /* Flurry of Twigs - * Start cliloc: 1070850 - * Effect: Physical resistance -15% for 5 seconds - * End cliloc: 1070852 - * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(1048 779, 6)" ToLocation: "(1048 779, 6)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - */ + ExpireTimer timer = (ExpireTimer)m_FlurryOfTwigsTable[defender]; - ExpireTimer timer = (ExpireTimer)m_FlurryOfTwigsTable[defender]; + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070851); // The creature lands another blow in your weakened state. + } + else + { + defender.SendLocalizedMessage( + 1070850); // The creature's flurry of twigs has made you more susceptible to physical attacks! + } - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070851 ); // The creature lands another blow in your weakened state. - } - else - defender.SendLocalizedMessage( 1070850 ); // The creature's flurry of twigs has made you more susceptible to physical attacks! + int effect = -(defender.PhysicalResistance * 15 / 100); - int effect = -(defender.PhysicalResistance * 15 / 100); + ResistanceMod mod = new ResistanceMod(ResistanceType.Physical, effect); - ResistanceMod mod = new ResistanceMod( ResistanceType.Physical, effect ); + defender.FixedEffect(0x37B9, 10, 5); + defender.AddResistanceMod(mod); - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.AddResistanceMod( mod ); + timer = new ExpireTimer(defender, mod, m_FlurryOfTwigsTable, TimeSpan.FromSeconds(5.0)); + timer.Start(); + m_FlurryOfTwigsTable[defender] = timer; + } + else if (0.05 > Utility.RandomDouble()) + { + /* Chlorophyl Blast + * Start cliloc: 1070827 + * Effect: Energy resistance -50% for 10 seconds + * End cliloc: 1070829 + * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(1048 779, 6)" ToLocation: "(1048 779, 6)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + */ - timer = new ExpireTimer( defender, mod, m_FlurryOfTwigsTable, TimeSpan.FromSeconds( 5.0 ) ); - timer.Start(); - m_FlurryOfTwigsTable[defender] = timer; - } - else if ( 0.05 > Utility.RandomDouble() ) - { - /* Chlorophyl Blast - * Start cliloc: 1070827 - * Effect: Energy resistance -50% for 10 seconds - * End cliloc: 1070829 - * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(1048 779, 6)" ToLocation: "(1048 779, 6)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - */ + ExpireTimer timer = (ExpireTimer)m_ChlorophylBlastTable[defender]; - ExpireTimer timer = (ExpireTimer)m_ChlorophylBlastTable[defender]; + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070828); // The creature continues to hinder your energy resistance! + } + else + { + defender.SendLocalizedMessage( + 1070827); // The creature's attack has made you more susceptible to energy attacks! + } - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070828 ); // The creature continues to hinder your energy resistance! - } - else - defender.SendLocalizedMessage( 1070827 ); // The creature's attack has made you more susceptible to energy attacks! + int effect = -(defender.EnergyResistance / 2); - int effect = -(defender.EnergyResistance / 2); + ResistanceMod mod = new ResistanceMod(ResistanceType.Energy, effect); - ResistanceMod mod = new ResistanceMod( ResistanceType.Energy, effect ); + defender.FixedEffect(0x37B9, 10, 5); + defender.AddResistanceMod(mod); - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.AddResistanceMod( mod ); + timer = new ExpireTimer(defender, mod, m_ChlorophylBlastTable, TimeSpan.FromSeconds(10.0)); + timer.Start(); + m_ChlorophylBlastTable[defender] = timer; + } + } - timer = new ExpireTimer( defender, mod, m_ChlorophylBlastTable, TimeSpan.FromSeconds( 10.0 ) ); - timer.Start(); - m_ChlorophylBlastTable[defender] = timer; - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - private static Hashtable m_FlurryOfTwigsTable = new Hashtable(); - private static Hashtable m_ChlorophylBlastTable = new Hashtable(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod m_Mod; - private Hashtable m_Table; + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod m_Mod; + private Hashtable m_Table; - public ExpireTimer( Mobile m, ResistanceMod mod, Hashtable table, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - m_Mod = mod; - m_Table = table; - Priority = TimerPriority.TwoFiftyMS; - } + public ExpireTimer(Mobile m, ResistanceMod mod, Hashtable table, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + m_Mod = mod; + m_Table = table; + Priority = TimerPriority.TwoFiftyMS; + } - public void DoExpire() - { - m_Mobile.RemoveResistanceMod( m_Mod ); - Stop(); - m_Table.Remove( m_Mobile ); - } + public void DoExpire() + { + m_Mobile.RemoveResistanceMod(m_Mod); + Stop(); + m_Table.Remove(m_Mobile); + } - protected override void OnTick() - { - if ( m_Mod.Type == ResistanceType.Physical ) - m_Mobile.SendLocalizedMessage( 1070852 ); // Your resistance to physical attacks has returned. - else - m_Mobile.SendLocalizedMessage( 1070829 ); // Your resistance to energy attacks has returned. + protected override void OnTick() + { + if (m_Mod.Type == ResistanceType.Physical) + m_Mobile.SendLocalizedMessage(1070852); // Your resistance to physical attacks has returned. + else + m_Mobile.SendLocalizedMessage(1070829); // Your resistance to energy attacks has returned. - DoExpire(); - } - } - - public KazeKemono( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/LadyOfTheSnow.cs b/Scripts/Mobiles/Monsters/SE/LadyOfTheSnow.cs index 9bb82f075..b8f36e8e8 100644 --- a/Scripts/Mobiles/Monsters/SE/LadyOfTheSnow.cs +++ b/Scripts/Mobiles/Monsters/SE/LadyOfTheSnow.cs @@ -1,162 +1,165 @@ using System; using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class LadyOfTheSnow : BaseCreature - { - public override string CorpseName => "a lady of the snow corpse"; - public override string DefaultName => "a lady of the snow"; + public class LadyOfTheSnow : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public LadyOfTheSnow() - : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 252; - BaseSoundID = 0x482; + [Constructible] + public LadyOfTheSnow() + : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 252; + BaseSoundID = 0x482; - SetStr( 276, 305 ); - SetDex( 106, 125 ); - SetInt( 471, 495 ); + SetStr(276, 305); + SetDex(106, 125); + SetInt(471, 495); - SetHits( 596, 625 ); + SetHits(596, 625); - SetDamage( 13, 20 ); + SetDamage(13, 20); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Cold, 80 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Cold, 80); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 40, 55 ); - SetResistance( ResistanceType.Cold, 70, 90 ); - SetResistance( ResistanceType.Poison, 60, 70 ); - SetResistance( ResistanceType.Energy, 65, 85 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 40, 55); + SetResistance(ResistanceType.Cold, 70, 90); + SetResistance(ResistanceType.Poison, 60, 70); + SetResistance(ResistanceType.Energy, 65, 85); - SetSkill( SkillName.Magery, 95.1, 110.0 ); - SetSkill( SkillName.MagicResist, 90.1, 105.0 ); - SetSkill( SkillName.Tactics, 80.1, 100.0 ); - SetSkill( SkillName.Wrestling, 80.1, 100.0 ); - SetSkill( SkillName.Necromancy, 90, 110.0 ); - SetSkill( SkillName.SpiritSpeak, 90.0, 110.0 ); + SetSkill(SkillName.Magery, 95.1, 110.0); + SetSkill(SkillName.MagicResist, 90.1, 105.0); + SetSkill(SkillName.Tactics, 80.1, 100.0); + SetSkill(SkillName.Wrestling, 80.1, 100.0); + SetSkill(SkillName.Necromancy, 90, 110.0); + SetSkill(SkillName.SpiritSpeak, 90.0, 110.0); - Fame = 15200; - Karma = -15200; + Fame = 15200; + Karma = -15200; - PackReg( 3 ); - PackItem( new Necklace() ); + PackReg(3); + PackItem(new Necklace()); - if ( 0.25 > Utility.RandomDouble() ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - } + if (0.25 > Utility.RandomDouble()) + PackItem(Seed.RandomBonsaiSeed()); + } - public override int GetDeathSound() - { - return 0x370; - } + public LadyOfTheSnow(Serial serial) + : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - } + public override string CorpseName => "a lady of the snow corpse"; + public override string DefaultName => "a lady of the snow"; - public override bool BleedImmune => true; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 4; + public override bool BleedImmune => true; + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 4; - // TODO: Snowball + public override int GetDeathSound() + { + return 0x370; + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + } - if ( 0.1 > Utility.RandomDouble() ) - { - /* Cold Wind - * Graphics: Message - Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(928 164, 34)" ToLocation: "(928 164, 34)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - * Start cliloc: 1070832 - * Damage: 1hp per second for 5 seconds - * End cliloc: 1070830 - * Reset cliloc: 1070831 - */ + // TODO: Snowball - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070831 ); // The freezing wind continues to blow! - } - else - defender.SendLocalizedMessage( 1070832 ); // An icy wind surrounds you, freezing your lungs as you breathe! + if (0.1 > Utility.RandomDouble()) + { + /* Cold Wind + * Graphics: Message - Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(928 164, 34)" ToLocation: "(928 164, 34)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + * Start cliloc: 1070832 + * Damage: 1hp per second for 5 seconds + * End cliloc: 1070830 + * Reset cliloc: 1070831 + */ - timer = new ExpireTimer( defender, this ); - timer.Start(); - m_Table[defender] = timer; - } - } + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - private static Hashtable m_Table = new Hashtable(); + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070831); // The freezing wind continues to blow! + } + else + { + defender.SendLocalizedMessage(1070832); // An icy wind surrounds you, freezing your lungs as you breathe! + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private Mobile m_From; - private int m_Count; + timer = new ExpireTimer(defender, this); + timer.Start(); + m_Table[defender] = timer; + } + } - public ExpireTimer( Mobile m, Mobile from ) - : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_From = from; - Priority = TimerPriority.TwoFiftyMS; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void DoExpire() - { - Stop(); - m_Table.Remove( m_Mobile ); - } + writer.Write(0); // version + } - public void DrainLife() - { - if ( m_Mobile.Alive ) - m_Mobile.Damage( 2, m_From ); - else - DoExpire(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - protected override void OnTick() - { - DrainLife(); + int version = reader.ReadInt(); + } - if ( ++m_Count >= 5 ) - { - DoExpire(); - m_Mobile.SendLocalizedMessage( 1070830 ); // The icy wind dissipates. - } - } - } + private class ExpireTimer : Timer + { + private int m_Count; + private Mobile m_From; + private Mobile m_Mobile; - public LadyOfTheSnow( Serial serial ) - : base( serial ) - { - } + public ExpireTimer(Mobile m, Mobile from) + : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_From = from; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public void DoExpire() + { + Stop(); + m_Table.Remove(m_Mobile); + } - writer.Write( (int)0 ); // version - } + public void DrainLife() + { + if (m_Mobile.Alive) + m_Mobile.Damage(2, m_From); + else + DoExpire(); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + protected override void OnTick() + { + DrainLife(); - int version = reader.ReadInt(); - } - } -} + if (++m_Count >= 5) + { + DoExpire(); + m_Mobile.SendLocalizedMessage(1070830); // The icy wind dissipates. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/Oni.cs b/Scripts/Mobiles/Monsters/SE/Oni.cs index ea68ff19a..ad992d08f 100644 --- a/Scripts/Mobiles/Monsters/SE/Oni.cs +++ b/Scripts/Mobiles/Monsters/SE/Oni.cs @@ -1,107 +1,109 @@ +using Server.Engines.Plants; + namespace Server.Mobiles { - public class Oni : BaseCreature - { - public override string CorpseName => "an oni corpse"; - public override string DefaultName => "an oni"; + public class Oni : BaseCreature + { + [Constructible] + public Oni() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 241; - [Constructible] - public Oni() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 241; + SetStr(801, 910); + SetDex(151, 300); + SetInt(171, 195); - SetStr( 801, 910 ); - SetDex( 151, 300 ); - SetInt( 171, 195 ); + SetHits(401, 530); - SetHits( 401, 530 ); + SetDamage(14, 20); - SetDamage( 14, 20 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Energy, 20); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Energy, 20 ); + SetResistance(ResistanceType.Physical, 65, 80); + SetResistance(ResistanceType.Fire, 50, 70); + SetResistance(ResistanceType.Cold, 35, 50); + SetResistance(ResistanceType.Poison, 45, 70); + SetResistance(ResistanceType.Energy, 45, 65); - SetResistance( ResistanceType.Physical, 65, 80 ); - SetResistance( ResistanceType.Fire, 50, 70 ); - SetResistance( ResistanceType.Cold, 35, 50 ); - SetResistance( ResistanceType.Poison, 45, 70 ); - SetResistance( ResistanceType.Energy, 45, 65 ); + SetSkill(SkillName.EvalInt, 100.1, 125.0); + SetSkill(SkillName.Magery, 96.1, 106.0); + SetSkill(SkillName.Anatomy, 85.1, 95.0); + SetSkill(SkillName.MagicResist, 85.1, 100.0); + SetSkill(SkillName.Tactics, 86.1, 101.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetSkill( SkillName.EvalInt, 100.1, 125.0 ); - SetSkill( SkillName.Magery, 96.1, 106.0 ); - SetSkill( SkillName.Anatomy, 85.1, 95.0 ); - SetSkill( SkillName.MagicResist, 85.1, 100.0 ); - SetSkill( SkillName.Tactics, 86.1, 101.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + Fame = 12000; + Karma = -12000; - Fame = 12000; - Karma = -12000; + if (Utility.RandomDouble() < .33) + PackItem(Seed.RandomBonsaiSeed()); - if ( Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); + // TODO: Brain (0x1CF0) or Skull (0x1AE3) or Body Part (0x1CE3) + } - // TODO: Brain (0x1CF0) or Skull (0x1AE3) or Body Part (0x1CE3) - } + /* TODO: Angry Fire + * cliloc 1070823 + * Action: 4 4 1 true false 1 + * Damage: 50-85, 60 phys, 20 fire, 20 nrgy according to the guide + * With 45/49/70 res I got 48 + * 50: 30/10/10 -> 16 + 5 + 3 = 24 + * 85: 51/17/17 -> 28 + 8 + 5 = 41 + */ - public override int GetAngerSound() - { - return 0x4E3; - } + public Oni(Serial serial) : base(serial) + { + } - public override int GetIdleSound() - { - return 0x4E2; - } + public override string CorpseName => "an oni corpse"; + public override string DefaultName => "an oni"; - public override int GetAttackSound() - { - return 0x4E1; - } + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 4; - public override int GetHurtSound() - { - return 0x4E4; - } + public override int GetAngerSound() + { + return 0x4E3; + } - public override int GetDeathSound() - { - return 0x4E0; - } + public override int GetIdleSound() + { + return 0x4E2; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - } + public override int GetAttackSound() + { + return 0x4E1; + } - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 4; + public override int GetHurtSound() + { + return 0x4E4; + } - /* TODO: Angry Fire - * cliloc 1070823 - * Action: 4 4 1 true false 1 - * Damage: 50-85, 60 phys, 20 fire, 20 nrgy according to the guide - * With 45/49/70 res I got 48 - * 50: 30/10/10 -> 16 + 5 + 3 = 24 - * 85: 51/17/17 -> 28 + 8 + 5 = 41 - */ + public override int GetDeathSound() + { + return 0x4E0; + } - public Oni( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); - } + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/RaiJu.cs b/Scripts/Mobiles/Monsters/SE/RaiJu.cs index dd38b05b7..0f9bbcce5 100644 --- a/Scripts/Mobiles/Monsters/SE/RaiJu.cs +++ b/Scripts/Mobiles/Monsters/SE/RaiJu.cs @@ -3,129 +3,128 @@ using System.Collections; namespace Server.Mobiles { - public class RaiJu : BaseCreature - { - public override string CorpseName => "a rai-ju corpse"; - public override string DefaultName => "a Rai-Ju"; + public class RaiJu : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public RaiJu() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 199; - BaseSoundID = 0x346; + [Constructible] + public RaiJu() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 199; + BaseSoundID = 0x346; - SetStr( 151, 225 ); - SetDex( 81, 135 ); - SetInt( 176, 180 ); + SetStr(151, 225); + SetDex(81, 135); + SetInt(176, 180); - SetHits( 201, 280 ); + SetHits(201, 280); - SetDamage( 12, 15 ); + SetDamage(12, 15); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Fire, 10 ); - SetDamageType( ResistanceType.Cold, 10 ); - SetDamageType( ResistanceType.Poison, 10 ); - SetDamageType( ResistanceType.Energy, 60 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Fire, 10); + SetDamageType(ResistanceType.Cold, 10); + SetDamageType(ResistanceType.Poison, 10); + SetDamageType(ResistanceType.Energy, 60); - SetResistance( ResistanceType.Physical, 45, 65 ); - SetResistance( ResistanceType.Fire, 70, 85 ); - SetResistance( ResistanceType.Cold, 30, 60 ); - SetResistance( ResistanceType.Poison, 50, 70 ); - SetResistance( ResistanceType.Energy, 60, 80 ); + SetResistance(ResistanceType.Physical, 45, 65); + SetResistance(ResistanceType.Fire, 70, 85); + SetResistance(ResistanceType.Cold, 30, 60); + SetResistance(ResistanceType.Poison, 50, 70); + SetResistance(ResistanceType.Energy, 60, 80); - SetSkill( SkillName.Wrestling, 85.1, 95.0 ); - SetSkill( SkillName.Tactics, 55.1, 65.0 ); - SetSkill( SkillName.MagicResist, 110.1, 125.0 ); - SetSkill( SkillName.Anatomy, 25.1, 35.0 ); + SetSkill(SkillName.Wrestling, 85.1, 95.0); + SetSkill(SkillName.Tactics, 55.1, 65.0); + SetSkill(SkillName.MagicResist, 110.1, 125.0); + SetSkill(SkillName.Anatomy, 25.1, 35.0); - Fame = 8000; - Karma = -8000; + Fame = 8000; + Karma = -8000; + } - } + public RaiJu(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 2 ); - AddLoot( LootPack.Gems, 2 ); - } - public override bool BleedImmune => true; + public override string CorpseName => "a rai-ju corpse"; + public override string DefaultName => "a Rai-Ju"; + public override bool BleedImmune => true; - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 2); + AddLoot(LootPack.Gems, 2); + } - if ( 0.1 > Utility.RandomDouble() && !IsStunned( defender ) ) - { - /* Lightning Fist - * Cliloc: 1070839 - * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - * Damage: 35-65, 100% energy, resistable - * Freezes for 4 seconds - * Effect cannot stack - */ + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.SendLocalizedMessage( 1070839 ); // The creature attacks with stunning force! + if (0.1 > Utility.RandomDouble() && !IsStunned(defender)) + { + /* Lightning Fist + * Cliloc: 1070839 + * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + * Damage: 35-65, 100% energy, resistable + * Freezes for 4 seconds + * Effect cannot stack + */ - // This should be done in place of the normal attack damage. - //AOS.Damage( defender, this, Utility.RandomMinMax( 35, 65 ), 0, 0, 0, 0, 100 ); + defender.FixedEffect(0x37B9, 10, 5); + defender.SendLocalizedMessage(1070839); // The creature attacks with stunning force! - defender.Frozen = true; + // This should be done in place of the normal attack damage. + //AOS.Damage( defender, this, Utility.RandomMinMax( 35, 65 ), 0, 0, 0, 0, 100 ); - ExpireTimer timer = new ExpireTimer( defender, TimeSpan.FromSeconds( 4.0 ) ); - timer.Start(); - m_Table[defender] = timer; - } - } + defender.Frozen = true; - private static Hashtable m_Table = new Hashtable(); + ExpireTimer timer = new ExpireTimer(defender, TimeSpan.FromSeconds(4.0)); + timer.Start(); + m_Table[defender] = timer; + } + } - public bool IsStunned( Mobile m ) - { - return m_Table.Contains( m ); - } + public bool IsStunned(Mobile m) + { + return m_Table.Contains(m); + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public ExpireTimer( Mobile m, TimeSpan delay ) : base( delay ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } + writer.Write(0); // version + } - public void DoExpire() - { - m_Mobile.Frozen = false; - Stop(); - m_Table.Remove( m_Mobile ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1005603 ); // You can move again! - DoExpire(); - } - } + int version = reader.ReadInt(); + } - public RaiJu( Serial serial ) : base( serial ) - { - } + private class ExpireTimer : Timer + { + private Mobile m_Mobile; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public ExpireTimer(Mobile m, TimeSpan delay) : base(delay) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - writer.Write( (int) 0 ); // version - } + public void DoExpire() + { + m_Mobile.Frozen = false; + Stop(); + m_Table.Remove(m_Mobile); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1005603); // You can move again! + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/RevenantLion.cs b/Scripts/Mobiles/Monsters/SE/RevenantLion.cs index 47f5637f3..e6c98cd2d 100644 --- a/Scripts/Mobiles/Monsters/SE/RevenantLion.cs +++ b/Scripts/Mobiles/Monsters/SE/RevenantLion.cs @@ -2,113 +2,137 @@ using Server.Items; namespace Server.Mobiles { - public class RevenantLion : BaseCreature - { - public override string CorpseName => "a revenant lion corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; - public override string DefaultName => "a Revenant Lion"; + public class RevenantLion : BaseCreature + { + [Constructible] + public RevenantLion() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 251; - [Constructible] - public RevenantLion() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 251; + SetStr(276, 325); + SetDex(156, 175); + SetInt(76, 105); - SetStr( 276, 325 ); - SetDex( 156, 175 ); - SetInt( 76, 105 ); + SetHits(251, 280); - SetHits( 251, 280 ); + SetDamage(18, 24); - SetDamage( 18, 24 ); + SetDamageType(ResistanceType.Physical, 30); + SetDamageType(ResistanceType.Cold, 30); + SetDamageType(ResistanceType.Poison, 10); + SetDamageType(ResistanceType.Energy, 30); - SetDamageType( ResistanceType.Physical, 30 ); - SetDamageType( ResistanceType.Cold, 30 ); - SetDamageType( ResistanceType.Poison, 10 ); - SetDamageType( ResistanceType.Energy, 30 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 55, 65); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 55, 65 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 80.1, 90.0); + SetSkill(SkillName.Magery, 80.1, 90.0); + SetSkill(SkillName.Poisoning, 120.1, 130.0); + SetSkill(SkillName.MagicResist, 70.1, 90.0); + SetSkill(SkillName.Tactics, 60.1, 80.0); + SetSkill(SkillName.Wrestling, 80.1, 88.0); - SetSkill( SkillName.EvalInt, 80.1, 90.0 ); - SetSkill( SkillName.Magery, 80.1, 90.0 ); - SetSkill( SkillName.Poisoning, 120.1, 130.0 ); - SetSkill( SkillName.MagicResist, 70.1, 90.0 ); - SetSkill( SkillName.Tactics, 60.1, 80.0 ); - SetSkill( SkillName.Wrestling, 80.1, 88.0 ); + Fame = 4000; + Karma = -4000; + PackNecroReg(6, 8); - Fame = 4000; - Karma = -4000; - PackNecroReg( 6, 8 ); + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } + } - switch ( Utility.Random( 10 )) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } - } + public RevenantLion(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x518; - } + public override string CorpseName => "a revenant lion corpse"; + public override string DefaultName => "a Revenant Lion"; - public override int GetIdleSound() - { - return 0x517; - } + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Greater; + public override Poison HitPoison => Poison.Greater; - public override int GetAttackSound() - { - return 0x516; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override int GetHurtSound() - { - return 0x519; - } + public override int GetAngerSound() + { + return 0x518; + } - public override int GetDeathSound() - { - return 0x515; - } + public override int GetIdleSound() + { + return 0x517; + } - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 2 ); - AddLoot( LootPack.MedScrolls, 2 ); + public override int GetAttackSound() + { + return 0x516; + } - // TODO: Bone Pile - } + public override int GetHurtSound() + { + return 0x519; + } - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Greater; - public override Poison HitPoison => Poison.Greater; + public override int GetDeathSound() + { + return 0x515; + } - public RevenantLion( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 2); + AddLoot(LootPack.MedScrolls, 2); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + // TODO: Bone Pile + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/Ronin.cs b/Scripts/Mobiles/Monsters/SE/Ronin.cs index 31e41434a..bc3bbc105 100644 --- a/Scripts/Mobiles/Monsters/SE/Ronin.cs +++ b/Scripts/Mobiles/Monsters/SE/Ronin.cs @@ -2,117 +2,130 @@ using Server.Items; namespace Server.Mobiles { - public class Ronin : BaseCreature - { - public override string CorpseName => "a ronin corpse"; - public override bool ClickTitle => false; - public override string DefaultName => "a ronin"; + public class Ronin : BaseCreature + { + [Constructible] + public Ronin() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + SpeechHue = Utility.RandomDyedHue(); + Hue = Utility.RandomSkinHue(); + Female = Utility.RandomBool(); + Body = Female ? 0x191 : 0x190; - [Constructible] - public Ronin() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); - Female = Utility.RandomBool(); - Body = Female ? 0x191 : 0x190; + SetStr(326, 375); + SetDex(31, 45); + SetInt(101, 110); - SetStr( 326, 375 ); - SetDex( 31, 45 ); - SetInt( 101, 110 ); + SetHits(301, 400); + SetMana(101, 110); - SetHits( 301, 400 ); - SetMana( 101, 110 ); + SetDamage(17, 25); - SetDamage( 17, 25 ); + SetDamageType(ResistanceType.Physical, 90); + SetDamageType(ResistanceType.Poison, 10); - SetDamageType( ResistanceType.Physical, 90 ); - SetDamageType( ResistanceType.Poison, 10 ); + SetResistance(ResistanceType.Physical, 55, 75); + SetResistance(ResistanceType.Fire, 40, 60); + SetResistance(ResistanceType.Cold, 35, 55); + SetResistance(ResistanceType.Poison, 50, 70); + SetResistance(ResistanceType.Energy, 55, 75); - SetResistance( ResistanceType.Physical, 55, 75 ); - SetResistance( ResistanceType.Fire, 40, 60 ); - SetResistance( ResistanceType.Cold, 35, 55 ); - SetResistance( ResistanceType.Poison, 50, 70 ); - SetResistance( ResistanceType.Energy, 55, 75 ); + SetSkill(SkillName.MagicResist, 42.6, 57.5); + SetSkill(SkillName.Tactics, 115.1, 130.0); + SetSkill(SkillName.Wrestling, 92.6, 107.5); + SetSkill(SkillName.Anatomy, 110.1, 125.0); - SetSkill( SkillName.MagicResist, 42.6, 57.5 ); - SetSkill( SkillName.Tactics, 115.1, 130.0 ); - SetSkill( SkillName.Wrestling, 92.6, 107.5 ); - SetSkill( SkillName.Anatomy, 110.1, 125.0 ); + SetSkill(SkillName.Fencing, 92.6, 107.5); + SetSkill(SkillName.Macing, 92.6, 107.5); + SetSkill(SkillName.Swords, 92.6, 107.5); - SetSkill( SkillName.Fencing, 92.6, 107.5 ); - SetSkill( SkillName.Macing, 92.6, 107.5 ); - SetSkill( SkillName.Swords, 92.6, 107.5 ); + Fame = 8500; + Karma = -8500; - Fame = 8500; - Karma = -8500; + AddItem(new SamuraiTabi()); + AddItem(new LeatherHiroSode()); + AddItem(new LeatherDo()); - AddItem( new SamuraiTabi() ); - AddItem( new LeatherHiroSode()); - AddItem( new LeatherDo()); + switch (Utility.Random(4)) + { + case 0: + AddItem(new LightPlateJingasa()); + break; + case 1: + AddItem(new ChainHatsuburi()); + break; + case 2: + AddItem(new DecorativePlateKabuto()); + break; + case 3: + AddItem(new LeatherJingasa()); + break; + } - switch ( Utility.Random( 4 )) - { - case 0: AddItem( new LightPlateJingasa()); break; - case 1: AddItem( new ChainHatsuburi() ); break; - case 2: AddItem( new DecorativePlateKabuto() ); break; - case 3: AddItem( new LeatherJingasa()); break; - } - - switch ( Utility.Random( 3 )) - { - case 0: AddItem( new StuddedHaidate()); break; - case 1: AddItem( new LeatherSuneate() ); break; - case 2: AddItem( new PlateSuneate() ); break; - } + switch (Utility.Random(3)) + { + case 0: + AddItem(new StuddedHaidate()); + break; + case 1: + AddItem(new LeatherSuneate()); + break; + case 2: + AddItem(new PlateSuneate()); + break; + } + if (Utility.RandomDouble() > .2) + AddItem(new NoDachi()); + else + AddItem(new Halberd()); - if ( Utility.RandomDouble() > .2 ) - AddItem( new NoDachi() ); - else - AddItem( new Halberd() ); + PackItem(new Wakizashi()); + PackItem(new Longsword()); - PackItem( new Wakizashi() ); - PackItem( new Longsword() ); + Utility.AssignRandomHair(this); + } - Utility.AssignRandomHair( this ); - } + public Ronin(Serial serial) : base(serial) + { + } - public override void OnDeath( Container c ) - { - base.OnDeath( c ); - c.DropItem( new BookOfBushido() ); - } + public override string CorpseName => "a ronin corpse"; + public override bool ClickTitle => false; + public override string DefaultName => "a ronin"; - // TODO: Bushido abilities + public override bool AlwaysMurderer => true; + public override bool BardImmune => true; + public override bool CanRummageCorpses => true; - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 2 ); - } + public override void OnDeath(Container c) + { + base.OnDeath(c); + c.DropItem(new BookOfBushido()); + } - public override bool AlwaysMurderer => true; - public override bool BardImmune => true; - public override bool CanRummageCorpses => true; + // TODO: Bushido abilities - public Ronin( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/RuneBeetle.cs b/Scripts/Mobiles/Monsters/SE/RuneBeetle.cs index 302e7dd79..f3bd9f183 100644 --- a/Scripts/Mobiles/Monsters/SE/RuneBeetle.cs +++ b/Scripts/Mobiles/Monsters/SE/RuneBeetle.cs @@ -1,236 +1,262 @@ using System; using System.Collections; using System.Collections.Generic; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class RuneBeetle : BaseCreature - { - public override string CorpseName => "a rune beetle corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.BleedAttack; - public override string DefaultName => "a rune beetle"; + public class RuneBeetle : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public RuneBeetle() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 244; + [Constructible] + public RuneBeetle() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 244; - SetStr( 401, 460 ); - SetDex( 121, 170 ); - SetInt( 376, 450 ); + SetStr(401, 460); + SetDex(121, 170); + SetInt(376, 450); - SetHits( 301, 360 ); + SetHits(301, 360); - SetDamage( 15, 22 ); + SetDamage(15, 22); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Poison, 10 ); - SetDamageType( ResistanceType.Energy, 70 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Poison, 10); + SetDamageType(ResistanceType.Energy, 70); - SetResistance( ResistanceType.Physical, 40, 65 ); - SetResistance( ResistanceType.Fire, 35, 50 ); - SetResistance( ResistanceType.Cold, 35, 50 ); - SetResistance( ResistanceType.Poison, 75, 95 ); - SetResistance( ResistanceType.Energy, 40, 60 ); + SetResistance(ResistanceType.Physical, 40, 65); + SetResistance(ResistanceType.Fire, 35, 50); + SetResistance(ResistanceType.Cold, 35, 50); + SetResistance(ResistanceType.Poison, 75, 95); + SetResistance(ResistanceType.Energy, 40, 60); - SetSkill( SkillName.EvalInt, 100.1, 125.0 ); - SetSkill( SkillName.Magery, 100.1, 110.0 ); - SetSkill( SkillName.Poisoning, 120.1, 140.0 ); - SetSkill( SkillName.MagicResist, 95.1, 110.0 ); - SetSkill( SkillName.Tactics, 78.1, 93.0 ); - SetSkill( SkillName.Wrestling, 70.1, 77.5 ); + SetSkill(SkillName.EvalInt, 100.1, 125.0); + SetSkill(SkillName.Magery, 100.1, 110.0); + SetSkill(SkillName.Poisoning, 120.1, 140.0); + SetSkill(SkillName.MagicResist, 95.1, 110.0); + SetSkill(SkillName.Tactics, 78.1, 93.0); + SetSkill(SkillName.Wrestling, 70.1, 77.5); - Fame = 15000; - Karma = -15000; + Fame = 15000; + Karma = -15000; - if ( Utility.RandomDouble() < .25 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); + if (Utility.RandomDouble() < .25) + PackItem(Seed.RandomBonsaiSeed()); - switch ( Utility.Random( 10 )) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } - Tamable = true; - ControlSlots = 3; - MinTameSkill = 93.9; + Tamable = true; + ControlSlots = 3; + MinTameSkill = 93.9; + } - } + public RuneBeetle(Serial serial) : base(serial) + { + } - public override int GetAngerSound() - { - return 0x4E8; - } + public override string CorpseName => "a rune beetle corpse"; + public override string DefaultName => "a rune beetle"; - public override int GetIdleSound() - { - return 0x4E7; - } + public override Poison PoisonImmune => Poison.Greater; + public override Poison HitPoison => Poison.Greater; + public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; + public override bool CanAngerOnTame => true; - public override int GetAttackSound() - { - return 0x4E6; - } + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.BleedAttack; + } - public override int GetHurtSound() - { - return 0x4E9; - } + public override int GetAngerSound() + { + return 0x4E8; + } - public override int GetDeathSound() - { - return 0x4E5; - } + public override int GetIdleSound() + { + return 0x4E7; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.MedScrolls, 1 ); - } + public override int GetAttackSound() + { + return 0x4E6; + } - public override Poison PoisonImmune => Poison.Greater; - public override Poison HitPoison => Poison.Greater; - public override FoodType FavoriteFood => FoodType.FruitsAndVegies | FoodType.GrainsAndHay; - public override bool CanAngerOnTame => true; + public override int GetHurtSound() + { + return 0x4E9; + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override int GetDeathSound() + { + return 0x4E5; + } - if ( 0.05 > Utility.RandomDouble() ) - { - /* Rune Corruption - * Start cliloc: 1070846 "The creature magically corrupts your armor!" - * Effect: All resistances -70 (lowest 0) for 5 seconds - * End ASCII: "The corruption of your armor has worn off" - */ + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.MedScrolls, 1); + } - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070845 ); // The creature continues to corrupt your armor! - } - else - defender.SendLocalizedMessage( 1070846 ); // The creature magically corrupts your armor! + if (0.05 > Utility.RandomDouble()) + { + /* Rune Corruption + * Start cliloc: 1070846 "The creature magically corrupts your armor!" + * Effect: All resistances -70 (lowest 0) for 5 seconds + * End ASCII: "The corruption of your armor has worn off" + */ - List mods = new List(); + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - if ( Core.ML ) - { - if ( defender.PhysicalResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Physical, -(defender.PhysicalResistance / 2) ) ); + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070845); // The creature continues to corrupt your armor! + } + else + { + defender.SendLocalizedMessage(1070846); // The creature magically corrupts your armor! + } - if ( defender.FireResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Fire, -(defender.FireResistance / 2) ) ); + List mods = new List(); - if ( defender.ColdResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Cold, -(defender.ColdResistance / 2) ) ); + if (Core.ML) + { + if (defender.PhysicalResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Physical, -(defender.PhysicalResistance / 2))); - if ( defender.PoisonResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Poison, -(defender.PoisonResistance / 2) ) ); + if (defender.FireResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Fire, -(defender.FireResistance / 2))); - if ( defender.EnergyResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Energy, -(defender.EnergyResistance / 2) ) ); - } - else - { - if ( defender.PhysicalResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Physical, (defender.PhysicalResistance > 70) ? -70 : -defender.PhysicalResistance ) ); + if (defender.ColdResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Cold, -(defender.ColdResistance / 2))); - if ( defender.FireResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Fire, (defender.FireResistance > 70) ? -70 : -defender.FireResistance ) ); + if (defender.PoisonResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Poison, -(defender.PoisonResistance / 2))); - if ( defender.ColdResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Cold, (defender.ColdResistance > 70) ? -70 : -defender.ColdResistance ) ); + if (defender.EnergyResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Energy, -(defender.EnergyResistance / 2))); + } + else + { + if (defender.PhysicalResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Physical, + defender.PhysicalResistance > 70 ? -70 : -defender.PhysicalResistance)); - if ( defender.PoisonResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Poison, (defender.PoisonResistance > 70) ? -70 : -defender.PoisonResistance ) ); + if (defender.FireResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Fire, + defender.FireResistance > 70 ? -70 : -defender.FireResistance)); - if ( defender.EnergyResistance > 0 ) - mods.Add( new ResistanceMod( ResistanceType.Energy, (defender.EnergyResistance > 70) ? -70 : -defender.EnergyResistance ) ); - } + if (defender.ColdResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Cold, + defender.ColdResistance > 70 ? -70 : -defender.ColdResistance)); - for ( int i = 0; i < mods.Count; ++i ) - defender.AddResistanceMod( mods[i] ); + if (defender.PoisonResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Poison, + defender.PoisonResistance > 70 ? -70 : -defender.PoisonResistance)); - defender.FixedEffect( 0x37B9, 10, 5 ); + if (defender.EnergyResistance > 0) + mods.Add(new ResistanceMod(ResistanceType.Energy, + defender.EnergyResistance > 70 ? -70 : -defender.EnergyResistance)); + } - timer = new ExpireTimer( defender, mods, TimeSpan.FromSeconds( 5.0 ) ); - timer.Start(); - m_Table[defender] = timer; - } - } + for (int i = 0; i < mods.Count; ++i) + defender.AddResistanceMod(mods[i]); - private static Hashtable m_Table = new Hashtable(); + defender.FixedEffect(0x37B9, 10, 5); - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private List m_Mods; + timer = new ExpireTimer(defender, mods, TimeSpan.FromSeconds(5.0)); + timer.Start(); + m_Table[defender] = timer; + } + } - public ExpireTimer( Mobile m, List mods, TimeSpan delay ) : base( delay ) - { - m_Mobile = m; - m_Mods = mods; - Priority = TimerPriority.TwoFiftyMS; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(1); + } - public void DoExpire() - { - for ( int i = 0; i < m_Mods.Count; ++i ) - m_Mobile.RemoveResistanceMod( m_Mods[i] ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - Stop(); - m_Table.Remove( m_Mobile ); - } + if (version < 1) + for (int i = 0; i < Skills.Length; ++i) + { + Skills[i].Cap = Math.Max(100.0, Skills[i].Cap * 0.9); - protected override void OnTick() - { - m_Mobile.SendMessage( "The corruption of your armor has worn off" ); - DoExpire(); - } - } + if (Skills[i].Base > Skills[i].Cap) Skills[i].Base = Skills[i].Cap; + } + } - public RuneBeetle( Serial serial ) : base( serial ) - { - } + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private List m_Mods; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 1 ); - } + public ExpireTimer(Mobile m, List mods, TimeSpan delay) : base(delay) + { + m_Mobile = m; + m_Mods = mods; + Priority = TimerPriority.TwoFiftyMS; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public void DoExpire() + { + for (int i = 0; i < m_Mods.Count; ++i) + m_Mobile.RemoveResistanceMod(m_Mods[i]); - if ( version < 1 ) - { - for ( int i = 0; i < Skills.Length; ++i ) - { - Skills[i].Cap = Math.Max( 100.0, Skills[i].Cap * 0.9 ); + Stop(); + m_Table.Remove(m_Mobile); + } - if ( Skills[i].Base > Skills[i].Cap ) - { - Skills[i].Base = Skills[i].Cap; - } - } - } - } - } -} + protected override void OnTick() + { + m_Mobile.SendMessage("The corruption of your armor has worn off"); + DoExpire(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/TsukiWolf.cs b/Scripts/Mobiles/Monsters/SE/TsukiWolf.cs index a86ca7fe5..3d1726c85 100644 --- a/Scripts/Mobiles/Monsters/SE/TsukiWolf.cs +++ b/Scripts/Mobiles/Monsters/SE/TsukiWolf.cs @@ -1,189 +1,212 @@ using System; using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class TsukiWolf : BaseCreature - { - public override string CorpseName => "a tsuki wolf corpse"; - public override string DefaultName => "a tsuki wolf"; + public class TsukiWolf : BaseCreature + { + private static Hashtable m_Table = new Hashtable(); - [Constructible] - public TsukiWolf() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 250; - Hue = Utility.Random(3) == 0 ? Utility.RandomNeutralHue() : 0; + [Constructible] + public TsukiWolf() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 250; + Hue = Utility.Random(3) == 0 ? Utility.RandomNeutralHue() : 0; - SetStr( 401, 450 ); - SetDex( 151, 200 ); - SetInt( 66, 76 ); + SetStr(401, 450); + SetDex(151, 200); + SetInt(66, 76); - SetHits( 376, 450 ); - SetMana( 40 ); + SetHits(376, 450); + SetMana(40); - SetDamage( 14, 18 ); + SetDamage(14, 18); - SetDamageType( ResistanceType.Physical, 90 ); - SetDamageType( ResistanceType.Cold, 5 ); - SetDamageType( ResistanceType.Energy, 5 ); + SetDamageType(ResistanceType.Physical, 90); + SetDamageType(ResistanceType.Cold, 5); + SetDamageType(ResistanceType.Energy, 5); - SetResistance( ResistanceType.Physical, 40, 60 ); - SetResistance( ResistanceType.Fire, 50, 70 ); - SetResistance( ResistanceType.Cold, 50, 70 ); - SetResistance( ResistanceType.Poison, 50, 70 ); - SetResistance( ResistanceType.Energy, 50, 70 ); + SetResistance(ResistanceType.Physical, 40, 60); + SetResistance(ResistanceType.Fire, 50, 70); + SetResistance(ResistanceType.Cold, 50, 70); + SetResistance(ResistanceType.Poison, 50, 70); + SetResistance(ResistanceType.Energy, 50, 70); - SetSkill( SkillName.Anatomy, 65.1, 72.0 ); - SetSkill( SkillName.MagicResist, 65.1, 70.0 ); - SetSkill( SkillName.Tactics, 95.1, 110.0 ); - SetSkill( SkillName.Wrestling, 97.6, 107.5 ); + SetSkill(SkillName.Anatomy, 65.1, 72.0); + SetSkill(SkillName.MagicResist, 65.1, 70.0); + SetSkill(SkillName.Tactics, 95.1, 110.0); + SetSkill(SkillName.Wrestling, 97.6, 107.5); - Fame = 8500; - Karma = -8500; + Fame = 8500; + Karma = -8500; - if ( Core.ML && Utility.RandomDouble() < .33 ) - PackItem( Engines.Plants.Seed.RandomPeculiarSeed(1) ); + if (Core.ML && Utility.RandomDouble() < .33) + PackItem(Seed.RandomPeculiarSeed(1)); - switch( Utility.Random( 10 ) ) - { - case 0: PackItem( new LeftArm() ); break; - case 1: PackItem( new RightArm() ); break; - case 2: PackItem( new Torso() ); break; - case 3: PackItem( new Bone() ); break; - case 4: PackItem( new RibCage() ); break; - case 5: PackItem( new RibCage() ); break; - case 6: PackItem( new BonePile() ); break; - case 7: PackItem( new BonePile() ); break; - case 8: PackItem( new BonePile() ); break; - case 9: PackItem( new BonePile() ); break; - } - } + switch (Utility.Random(10)) + { + case 0: + PackItem(new LeftArm()); + break; + case 1: + PackItem(new RightArm()); + break; + case 2: + PackItem(new Torso()); + break; + case 3: + PackItem(new Bone()); + break; + case 4: + PackItem(new RibCage()); + break; + case 5: + PackItem(new RibCage()); + break; + case 6: + PackItem(new BonePile()); + break; + case 7: + PackItem(new BonePile()); + break; + case 8: + PackItem(new BonePile()); + break; + case 9: + PackItem(new BonePile()); + break; + } + } - public override void GenerateLoot() - { - AddLoot( LootPack.Average ); - AddLoot( LootPack.Rich ); - } - public override int Meat => 4; - public override int Hides => 25; - public override FoodType FavoriteFood => FoodType.Meat; + public TsukiWolf(Serial serial) + : base(serial) + { + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override string CorpseName => "a tsuki wolf corpse"; + public override string DefaultName => "a tsuki wolf"; + public override int Meat => 4; + public override int Hides => 25; + public override FoodType FavoriteFood => FoodType.Meat; - if ( 0.1 > Utility.RandomDouble() ) - { - /* Blood Bath - * Start cliloc 1070826 - * Sound: 0x52B - * 2-3 blood spots - * Damage: 2 hps per second for 5 seconds - * End cliloc: 1070824 - */ + public override void GenerateLoot() + { + AddLoot(LootPack.Average); + AddLoot(LootPack.Rich); + } - ExpireTimer timer = (ExpireTimer)m_Table[defender]; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( timer != null ) - { - timer.DoExpire(); - defender.SendLocalizedMessage( 1070825 ); // The creature continues to rage! - } - else - defender.SendLocalizedMessage( 1070826 ); // The creature goes into a rage, inflicting heavy damage! + if (0.1 > Utility.RandomDouble()) + { + /* Blood Bath + * Start cliloc 1070826 + * Sound: 0x52B + * 2-3 blood spots + * Damage: 2 hps per second for 5 seconds + * End cliloc: 1070824 + */ - timer = new ExpireTimer( defender, this ); - timer.Start(); - m_Table[defender] = timer; - } - } + ExpireTimer timer = (ExpireTimer)m_Table[defender]; - private static Hashtable m_Table = new Hashtable(); + if (timer != null) + { + timer.DoExpire(); + defender.SendLocalizedMessage(1070825); // The creature continues to rage! + } + else + { + defender.SendLocalizedMessage(1070826); // The creature goes into a rage, inflicting heavy damage! + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private Mobile m_From; - private int m_Count; + timer = new ExpireTimer(defender, this); + timer.Start(); + m_Table[defender] = timer; + } + } - public ExpireTimer( Mobile m, Mobile from ) - : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_From = from; - Priority = TimerPriority.TwoFiftyMS; - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public void DoExpire() - { - Stop(); - m_Table.Remove( m_Mobile ); - } + writer.Write(0); + } - public void DrainLife() - { - if ( m_Mobile.Alive ) - m_Mobile.Damage( 2, m_From ); - else - DoExpire(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - protected override void OnTick() - { - DrainLife(); + int version = reader.ReadInt(); + } - if ( ++m_Count >= 5 ) - { - DoExpire(); - m_Mobile.SendLocalizedMessage( 1070824 ); // The creature's rage subsides. - } - } - } + public override int GetAngerSound() + { + return 0x52D; + } - public TsukiWolf( Serial serial ) - : base( serial ) - { - } + public override int GetIdleSound() + { + return 0x52C; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int GetAttackSound() + { + return 0x52B; + } - writer.Write( (int)0 ); - } + public override int GetHurtSound() + { + return 0x52E; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override int GetDeathSound() + { + return 0x52A; + } - int version = reader.ReadInt(); - } + private class ExpireTimer : Timer + { + private int m_Count; + private Mobile m_From; + private Mobile m_Mobile; - public override int GetAngerSound() - { - return 0x52D; - } + public ExpireTimer(Mobile m, Mobile from) + : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_From = from; + Priority = TimerPriority.TwoFiftyMS; + } - public override int GetIdleSound() - { - return 0x52C; - } + public void DoExpire() + { + Stop(); + m_Table.Remove(m_Mobile); + } - public override int GetAttackSound() - { - return 0x52B; - } + public void DrainLife() + { + if (m_Mobile.Alive) + m_Mobile.Damage(2, m_From); + else + DoExpire(); + } - public override int GetHurtSound() - { - return 0x52E; - } + protected override void OnTick() + { + DrainLife(); - public override int GetDeathSound() - { - return 0x52A; - } - } -} + if (++m_Count >= 5) + { + DoExpire(); + m_Mobile.SendLocalizedMessage(1070824); // The creature's rage subsides. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/Yamandon.cs b/Scripts/Mobiles/Monsters/SE/Yamandon.cs index 44eca7fec..c98651a4f 100644 --- a/Scripts/Mobiles/Monsters/SE/Yamandon.cs +++ b/Scripts/Mobiles/Monsters/SE/Yamandon.cs @@ -1,181 +1,186 @@ using System.Collections; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Yamadon" )] - public class Yamandon : BaseCreature - { - public override string CorpseName => "a yamandon corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.DoubleStrike; - public override string DefaultName => "a yamandon"; + [TypeAlias("Server.Mobiles.Yamadon")] + public class Yamandon : BaseCreature + { + [Constructible] + public Yamandon() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 249; - [Constructible] - public Yamandon() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 249; + SetStr(786, 930); + SetDex(251, 365); + SetInt(101, 115); - SetStr( 786, 930 ); - SetDex( 251, 365 ); - SetInt( 101, 115 ); + SetHits(1601, 1800); - SetHits( 1601, 1800 ); + SetDamage(19, 35); - SetDamage( 19, 35 ); + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 20); + SetDamageType(ResistanceType.Energy, 10); - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 20 ); - SetDamageType( ResistanceType.Energy, 10 ); + SetResistance(ResistanceType.Physical, 65, 85); + SetResistance(ResistanceType.Fire, 70, 90); + SetResistance(ResistanceType.Cold, 50, 70); + SetResistance(ResistanceType.Poison, 50, 70); + SetResistance(ResistanceType.Energy, 50, 70); - SetResistance( ResistanceType.Physical, 65, 85 ); - SetResistance( ResistanceType.Fire, 70, 90 ); - SetResistance( ResistanceType.Cold, 50, 70 ); - SetResistance( ResistanceType.Poison, 50, 70 ); - SetResistance( ResistanceType.Energy, 50, 70 ); + SetSkill(SkillName.Anatomy, 115.1, 130.0); + SetSkill(SkillName.MagicResist, 117.6, 132.5); + SetSkill(SkillName.Poisoning, 120.1, 140.0); + SetSkill(SkillName.Tactics, 117.1, 132.0); + SetSkill(SkillName.Wrestling, 112.6, 132.5); - SetSkill( SkillName.Anatomy, 115.1, 130.0 ); - SetSkill( SkillName.MagicResist, 117.6, 132.5 ); - SetSkill( SkillName.Poisoning, 120.1, 140.0 ); - SetSkill( SkillName.Tactics, 117.1, 132.0 ); - SetSkill( SkillName.Wrestling, 112.6, 132.5 ); + Fame = 22000; + Karma = -22000; - Fame = 22000; - Karma = -22000; + if (Utility.RandomDouble() < .50) + PackItem(Seed.RandomBonsaiSeed()); - if ( Utility.RandomDouble() < .50 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - - PackItem( new Eggs( 2 ) ); - } - - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich ); - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.Gems, 6 ); - } - - public override bool ReacquireOnMovement => true; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Utility.RandomBool() ? Poison.Deadly : Poison.Lethal; - public override int TreasureMapLevel => 5; - public override int Hides => 20; - - public override void OnDamagedBySpell( Mobile attacker ) - { - base.OnDamagedBySpell( attacker ); - - DoCounter( attacker ); - } - - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); - - DoCounter( attacker ); - } - - private void DoCounter( Mobile attacker ) - { - if ( Map == null ) - return; - - if ( attacker is BaseCreature creature && creature.BardProvoked ) - return; - - if ( 0.2 > Utility.RandomDouble() ) - { - /* Counterattack with Hit Poison Area - * 20-25 damage, unresistable - * Lethal poison, 100% of the time - * Particle effect: Type: "2" From: "0x4061A107" To: "0x0" ItemId: "0x36BD" ItemIdName: "explosion" FromLocation: "(296 615, 17)" ToLocation: "(296 615, 17)" Speed: "1" Duration: "10" FixedDirection: "True" Explode: "False" Hue: "0xA6" RenderMode: "0x0" Effect: "0x1F78" ExplodeEffect: "0x1" ExplodeSound: "0x0" Serial: "0x4061A107" Layer: "255" Unknown: "0x0" - * Doesn't work on provoked monsters - */ - - Mobile target = null; - - if ( attacker is BaseCreature baseCreature ) - { - Mobile m = baseCreature.GetMaster(); - - if ( m != null ) - target = m; - } - - if ( target == null || !target.InRange( this, 18 ) ) - target = attacker; - - Animate( 10, 4, 1, true, false, 0 ); - - ArrayList targets = new ArrayList(); - - foreach ( Mobile m in target.GetMobilesInRange( 8 ) ) - { - if ( m == this || !CanBeHarmful( m ) ) - continue; - - if ( m is BaseCreature bc && (bc.Controlled || bc.Summoned || bc.Team != Team)) - targets.Add( m ); - else if ( m.Player && m.Alive ) - targets.Add( m ); - } - - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = (Mobile)targets[i]; - - DoHarmful( m ); - - AOS.Damage( m, this, Utility.RandomMinMax( 20, 25 ), true, 0, 0, 0, 100, 0 ); - - m.FixedParticles( 0x36BD, 1, 10, 0x1F78, 0xA6, 0, (EffectLayer)255 ); - m.ApplyPoison( this, Poison.Lethal ); - } - } - } - - public override int GetAttackSound() - { - return 1260; - } - - public override int GetAngerSound() - { - return 1262; - } - - public override int GetDeathSound() - { - return 1259; //Other Death sound is 1258... One for Yamadon, one for Serado? - } - - public override int GetHurtSound() - { - return 1263; - } - - public override int GetIdleSound() - { - return 1261; - } + PackItem(new Eggs(2)); + } - public Yamandon( Serial serial ) : base( serial ) - { - } + public Yamandon(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string CorpseName => "a yamandon corpse"; + public override string DefaultName => "a yamandon"; - writer.Write( (int) 0 ); - } + public override bool ReacquireOnMovement => true; + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Utility.RandomBool() ? Poison.Deadly : Poison.Lethal; + public override int TreasureMapLevel => 5; + public override int Hides => 20; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.DoubleStrike; + } - int version = reader.ReadInt(); - } - } -} + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich); + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.Gems, 6); + } + + public override void OnDamagedBySpell(Mobile attacker) + { + base.OnDamagedBySpell(attacker); + + DoCounter(attacker); + } + + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); + + DoCounter(attacker); + } + + private void DoCounter(Mobile attacker) + { + if (Map == null) + return; + + if (attacker is BaseCreature creature && creature.BardProvoked) + return; + + if (0.2 > Utility.RandomDouble()) + { + /* Counterattack with Hit Poison Area + * 20-25 damage, unresistable + * Lethal poison, 100% of the time + * Particle effect: Type: "2" From: "0x4061A107" To: "0x0" ItemId: "0x36BD" ItemIdName: "explosion" FromLocation: "(296 615, 17)" ToLocation: "(296 615, 17)" Speed: "1" Duration: "10" FixedDirection: "True" Explode: "False" Hue: "0xA6" RenderMode: "0x0" Effect: "0x1F78" ExplodeEffect: "0x1" ExplodeSound: "0x0" Serial: "0x4061A107" Layer: "255" Unknown: "0x0" + * Doesn't work on provoked monsters + */ + + Mobile target = null; + + if (attacker is BaseCreature baseCreature) + { + Mobile m = baseCreature.GetMaster(); + + if (m != null) + target = m; + } + + if (target == null || !target.InRange(this, 18)) + target = attacker; + + Animate(10, 4, 1, true, false, 0); + + ArrayList targets = new ArrayList(); + + foreach (Mobile m in target.GetMobilesInRange(8)) + { + if (m == this || !CanBeHarmful(m)) + continue; + + if (m is BaseCreature bc && (bc.Controlled || bc.Summoned || bc.Team != Team)) + targets.Add(m); + else if (m.Player && m.Alive) + targets.Add(m); + } + + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = (Mobile)targets[i]; + + DoHarmful(m); + + AOS.Damage(m, this, Utility.RandomMinMax(20, 25), true, 0, 0, 0, 100, 0); + + m.FixedParticles(0x36BD, 1, 10, 0x1F78, 0xA6, 0, (EffectLayer)255); + m.ApplyPoison(this, Poison.Lethal); + } + } + } + + public override int GetAttackSound() + { + return 1260; + } + + public override int GetAngerSound() + { + return 1262; + } + + public override int GetDeathSound() + { + return 1259; //Other Death sound is 1258... One for Yamadon, one for Serado? + } + + public override int GetHurtSound() + { + return 1263; + } + + public override int GetIdleSound() + { + return 1261; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/YomotsuElder.cs b/Scripts/Mobiles/Monsters/SE/YomotsuElder.cs index 7ba4f9a84..3dbaab27c 100644 --- a/Scripts/Mobiles/Monsters/SE/YomotsuElder.cs +++ b/Scripts/Mobiles/Monsters/SE/YomotsuElder.cs @@ -1,136 +1,152 @@ using System; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class YomotsuElder : BaseCreature - { - public override string CorpseName => "a wrinkly yomotsu corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.DoubleStrike; - public override string DefaultName => "a yomotsu elder"; + public class YomotsuElder : BaseCreature + { + [Constructible] + public YomotsuElder() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 255; + BaseSoundID = 0x452; - [Constructible] - public YomotsuElder() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 255; - BaseSoundID = 0x452; + SetStr(686, 830); + SetDex(251, 365); + SetInt(17, 31); - SetStr( 686, 830 ); - SetDex( 251, 365 ); - SetInt( 17, 31 ); + SetHits(801, 900); - SetHits( 801, 900 ); + SetDamage(19, 27); - SetDamage( 19, 27 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 65, 85); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 45, 65); + SetResistance(ResistanceType.Poison, 35, 55); + SetResistance(ResistanceType.Energy, 25, 50); - SetResistance( ResistanceType.Physical, 65, 85 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 45, 65 ); - SetResistance( ResistanceType.Poison, 35, 55 ); - SetResistance( ResistanceType.Energy, 25, 50 ); + SetSkill(SkillName.Anatomy, 115.1, 130.0); + SetSkill(SkillName.MagicResist, 100.1, 120.0); + SetSkill(SkillName.Tactics, 115.1, 130.0); + SetSkill(SkillName.Wrestling, 110.1, 130.0); - SetSkill( SkillName.Anatomy, 115.1, 130.0 ); - SetSkill( SkillName.MagicResist, 100.1, 120.0 ); - SetSkill( SkillName.Tactics, 115.1, 130.0 ); - SetSkill( SkillName.Wrestling, 110.1, 130.0 ); - - Fame = 12000; - Karma = -12000; + Fame = 12000; + Karma = -12000; - PackItem( new GreenGourd() ); - PackItem( new ExecutionersAxe() ); + PackItem(new GreenGourd()); + PackItem(new ExecutionersAxe()); - switch ( Utility.Random( 3 ) ) - { - case 0: PackItem( new LongPants() ); break; - case 1: PackItem( new ShortPants() ); break; - } + switch (Utility.Random(3)) + { + case 0: + PackItem(new LongPants()); + break; + case 1: + PackItem(new ShortPants()); + break; + } - switch ( Utility.Random( 6 ) ) - { - case 0: PackItem( new Shoes() ); break; - case 1: PackItem( new Sandals() ); break; - case 2: PackItem( new Boots() ); break; - case 3: PackItem( new ThighBoots() ); break; - } + switch (Utility.Random(6)) + { + case 0: + PackItem(new Shoes()); + break; + case 1: + PackItem(new Sandals()); + break; + case 2: + PackItem(new Boots()); + break; + case 3: + PackItem(new ThighBoots()); + break; + } - if ( Utility.RandomDouble() < .25 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - } + if (Utility.RandomDouble() < .25) + PackItem(Seed.RandomBonsaiSeed()); + } - public override FoodType FavoriteFood => FoodType.Fish; + public YomotsuElder(Serial serial) : base(serial) + { + } - public override int Meat => 1; + public override string CorpseName => "a wrinkly yomotsu corpse"; + public override string DefaultName => "a yomotsu elder"; + + public override FoodType FavoriteFood => FoodType.Fish; + + public override int Meat => 1; + + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 5; + + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.DoubleStrike; + } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 3); + AddLoot(LootPack.Gems, 2); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 3 ); - AddLoot( LootPack.Gems, 2 ); - } + // TODO: Axe Throw - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 5; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - // TODO: Axe Throw + if (0.1 > Utility.RandomDouble()) + { + /* Maniacal laugh + * Cliloc: 1070840 + * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + * Paralyzes for 4 seconds, or until hit + */ - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + defender.FixedEffect(0x37B9, 10, 5); + defender.SendLocalizedMessage(1070840); // You are frozen as the creature laughs maniacally. - if ( 0.1 > Utility.RandomDouble() ) - { - /* Maniacal laugh - * Cliloc: 1070840 - * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - * Paralyzes for 4 seconds, or until hit - */ + defender.Paralyze(TimeSpan.FromSeconds(4.0)); + } + } - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.SendLocalizedMessage( 1070840 ); // You are frozen as the creature laughs maniacally. + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - defender.Paralyze( TimeSpan.FromSeconds( 4.0 ) ); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - public YomotsuElder( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 0x42A; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetAttackSound() + { + return 0x435; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override int GetHurtSound() + { + return 0x436; + } - public override int GetIdleSound() - { - return 0x42A; - } - - public override int GetAttackSound() - { - return 0x435; - } - - public override int GetHurtSound() - { - return 0x436; - } - - public override int GetDeathSound() - { - return 0x43A; - } - } -} + public override int GetDeathSound() + { + return 0x43A; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/YomotsuPriest.cs b/Scripts/Mobiles/Monsters/SE/YomotsuPriest.cs index 3c9eca642..7fb52d56a 100644 --- a/Scripts/Mobiles/Monsters/SE/YomotsuPriest.cs +++ b/Scripts/Mobiles/Monsters/SE/YomotsuPriest.cs @@ -1,137 +1,153 @@ using System; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class YomotsuPriest : BaseCreature - { - public override string CorpseName => "a glowing yomotsu corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.DoubleStrike; - public override string DefaultName => "a yomotsu priest"; + public class YomotsuPriest : BaseCreature + { + [Constructible] + public YomotsuPriest() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 253; + BaseSoundID = 0x452; - [Constructible] - public YomotsuPriest() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 253; - BaseSoundID = 0x452; + SetStr(486, 530); + SetDex(101, 115); + SetInt(601, 670); - SetStr( 486, 530 ); - SetDex( 101, 115 ); - SetInt( 601, 670 ); + SetHits(486, 530); - SetHits( 486, 530 ); + SetDamage(8, 10); - SetDamage( 8, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 65, 85); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 45, 65); + SetResistance(ResistanceType.Poison, 35, 55); + SetResistance(ResistanceType.Energy, 25, 50); - SetResistance( ResistanceType.Physical, 65, 85 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 45, 65 ); - SetResistance( ResistanceType.Poison, 35, 55 ); - SetResistance( ResistanceType.Energy, 25, 50 ); + SetSkill(SkillName.EvalInt, 92.6, 107.5); + SetSkill(SkillName.Magery, 105.1, 115.0); + SetSkill(SkillName.Meditation, 100.1, 110.0); + SetSkill(SkillName.MagicResist, 112.6, 122.5); + SetSkill(SkillName.Tactics, 55.1, 105.0); + SetSkill(SkillName.Wrestling, 47.6, 57.5); - SetSkill( SkillName.EvalInt, 92.6, 107.5 ); - SetSkill( SkillName.Magery, 105.1, 115.0 ); - SetSkill( SkillName.Meditation, 100.1, 110.0 ); - SetSkill( SkillName.MagicResist, 112.6, 122.5 ); - SetSkill( SkillName.Tactics, 55.1, 105.0 ); - SetSkill( SkillName.Wrestling, 47.6, 57.5 ); - - Fame = 9000; - Karma = -9000; + Fame = 9000; + Karma = -9000; - PackItem( new GreenGourd() ); - PackItem( new ExecutionersAxe() ); + PackItem(new GreenGourd()); + PackItem(new ExecutionersAxe()); - switch ( Utility.Random( 3 ) ) - { - case 0: PackItem( new LongPants() ); break; - case 1: PackItem( new ShortPants() ); break; - } + switch (Utility.Random(3)) + { + case 0: + PackItem(new LongPants()); + break; + case 1: + PackItem(new ShortPants()); + break; + } - switch ( Utility.Random( 6 ) ) - { - case 0: PackItem( new Shoes() ); break; - case 1: PackItem( new Sandals() ); break; - case 2: PackItem( new Boots() ); break; - case 3: PackItem( new ThighBoots() ); break; - } + switch (Utility.Random(6)) + { + case 0: + PackItem(new Shoes()); + break; + case 1: + PackItem(new Sandals()); + break; + case 2: + PackItem(new Boots()); + break; + case 3: + PackItem(new ThighBoots()); + break; + } - if ( Utility.RandomDouble() < .25 ) PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - } + if (Utility.RandomDouble() < .25) PackItem(Seed.RandomBonsaiSeed()); + } - public override FoodType FavoriteFood => FoodType.Fish; + public YomotsuPriest(Serial serial) : base(serial) + { + } - public override int Meat => 1; + public override string CorpseName => "a glowing yomotsu corpse"; + public override string DefaultName => "a yomotsu priest"; + + public override FoodType FavoriteFood => FoodType.Fish; + + public override int Meat => 1; + + public override bool CanRummageCorpses => true; + + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.DoubleStrike; + } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Rich); + AddLoot(LootPack.Gems, 4); + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Rich ); - AddLoot( LootPack.Gems, 4); - } + // TODO: Body Transformation - public override bool CanRummageCorpses => true; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - // TODO: Body Transformation + if (0.1 > Utility.RandomDouble()) + { + /* Maniacal laugh + * Cliloc: 1070840 + * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + * Paralyzes for 4 seconds, or until hit + */ - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + defender.FixedEffect(0x37B9, 10, 5); + defender.SendLocalizedMessage(1070840); // You are frozen as the creature laughs maniacally. - if ( 0.1 > Utility.RandomDouble() ) - { - /* Maniacal laugh - * Cliloc: 1070840 - * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - * Paralyzes for 4 seconds, or until hit - */ + defender.Paralyze(TimeSpan.FromSeconds(4.0)); + } + } - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.SendLocalizedMessage( 1070840 ); // You are frozen as the creature laughs maniacally. + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - defender.Paralyze( TimeSpan.FromSeconds( 4.0 ) ); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - public YomotsuPriest( Serial serial ) : base( serial ) - { - } + public override int GetIdleSound() + { + return 0x42A; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override int GetAttackSound() + { + return 0x435; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override int GetHurtSound() + { + return 0x436; + } - public override int GetIdleSound() - { - return 0x42A; - } - - public override int GetAttackSound() - { - return 0x435; - } - - public override int GetHurtSound() - { - return 0x436; - } - - public override int GetDeathSound() - { - return 0x43A; - } - } -} + public override int GetDeathSound() + { + return 0x43A; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/SE/YomotsuWarrior.cs b/Scripts/Mobiles/Monsters/SE/YomotsuWarrior.cs index 2b64461c2..cc74a0eaa 100644 --- a/Scripts/Mobiles/Monsters/SE/YomotsuWarrior.cs +++ b/Scripts/Mobiles/Monsters/SE/YomotsuWarrior.cs @@ -1,134 +1,146 @@ using System; +using Server.Engines.Plants; using Server.Items; namespace Server.Mobiles { - public class YomotsuWarrior : BaseCreature - { - public override string CorpseName => "a yomotsu corpse"; - public override WeaponAbility GetWeaponAbility() => WeaponAbility.DoubleStrike; - public override string DefaultName => "a yomotsu warrior"; + public class YomotsuWarrior : BaseCreature + { + [Constructible] + public YomotsuWarrior() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 245; + BaseSoundID = 0x452; - [Constructible] - public YomotsuWarrior() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 245; - BaseSoundID = 0x452; + SetStr(486, 530); + SetDex(151, 165); + SetInt(17, 31); - SetStr( 486, 530 ); - SetDex( 151, 165 ); - SetInt( 17, 31 ); + SetHits(486, 530); + SetMana(17, 31); - SetHits( 486, 530 ); - SetMana( 17, 31 ); + SetDamage(8, 10); - SetDamage( 8, 10 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 65, 85); + SetResistance(ResistanceType.Fire, 30, 50); + SetResistance(ResistanceType.Cold, 45, 65); + SetResistance(ResistanceType.Poison, 35, 55); + SetResistance(ResistanceType.Energy, 25, 50); - SetResistance( ResistanceType.Physical, 65, 85 ); - SetResistance( ResistanceType.Fire, 30, 50 ); - SetResistance( ResistanceType.Cold, 45, 65 ); - SetResistance( ResistanceType.Poison, 35, 55 ); - SetResistance( ResistanceType.Energy, 25, 50 ); + SetSkill(SkillName.Anatomy, 85.1, 95.0); + SetSkill(SkillName.MagicResist, 82.6, 90.5); + SetSkill(SkillName.Tactics, 95.1, 105.0); + SetSkill(SkillName.Wrestling, 97.6, 107.5); - SetSkill( SkillName.Anatomy, 85.1, 95.0 ); - SetSkill( SkillName.MagicResist, 82.6, 90.5 ); - SetSkill( SkillName.Tactics, 95.1, 105.0 ); - SetSkill( SkillName.Wrestling, 97.6, 107.5 ); + Fame = 4200; + Karma = -4200; - Fame = 4200; - Karma = -4200; + PackItem(new GreenGourd()); + PackItem(new ExecutionersAxe()); - PackItem( new GreenGourd() ); - PackItem( new ExecutionersAxe() ); + if (Utility.RandomBool()) + PackItem(new LongPants()); + else + PackItem(new ShortPants()); - if ( Utility.RandomBool() ) - PackItem( new LongPants() ); - else - PackItem( new ShortPants() ); + switch (Utility.Random(4)) + { + case 0: + PackItem(new Shoes()); + break; + case 1: + PackItem(new Sandals()); + break; + case 2: + PackItem(new Boots()); + break; + case 3: + PackItem(new ThighBoots()); + break; + } - switch ( Utility.Random( 4 ) ) - { - case 0: PackItem( new Shoes() ); break; - case 1: PackItem( new Sandals() ); break; - case 2: PackItem( new Boots() ); break; - case 3: PackItem( new ThighBoots() ); break; - } + if (Utility.RandomDouble() < .25) + PackItem(Seed.RandomBonsaiSeed()); + } - if ( Utility.RandomDouble() < .25 ) - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); + public YomotsuWarrior(Serial serial) : base(serial) + { + } - } + public override string CorpseName => "a yomotsu corpse"; + public override string DefaultName => "a yomotsu warrior"; - public override FoodType FavoriteFood => FoodType.Fish; + public override FoodType FavoriteFood => FoodType.Fish; - public override int Meat => 1; + public override int Meat => 1; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich, 2 ); - AddLoot( LootPack.Gems,2); - } + public override bool CanRummageCorpses => true; + public override int TreasureMapLevel => 3; - public override bool CanRummageCorpses => true; - public override int TreasureMapLevel => 3; + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.DoubleStrike; + } - // TODO: Throwing Dagger + public override void GenerateLoot() + { + AddLoot(LootPack.Rich, 2); + AddLoot(LootPack.Gems, 2); + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + // TODO: Throwing Dagger - if ( 0.1 > Utility.RandomDouble() ) - { - /* Maniacal laugh - * Cliloc: 1070840 - * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" - * Paralyzes for 4 seconds, or until hit - */ + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - defender.FixedEffect( 0x37B9, 10, 5 ); - defender.SendLocalizedMessage( 1070840 ); // You are frozen as the creature laughs maniacally. + if (0.1 > Utility.RandomDouble()) + { + /* Maniacal laugh + * Cliloc: 1070840 + * Effect: Type: "3" From: "0x57D4F5B" To: "0x0" ItemId: "0x37B9" ItemIdName: "glow" FromLocation: "(884 715, 10)" ToLocation: "(884 715, 10)" Speed: "10" Duration: "5" FixedDirection: "True" Explode: "False" + * Paralyzes for 4 seconds, or until hit + */ - defender.Paralyze( TimeSpan.FromSeconds( 4.0 ) ); - } - } + defender.FixedEffect(0x37B9, 10, 5); + defender.SendLocalizedMessage(1070840); // You are frozen as the creature laughs maniacally. - public YomotsuWarrior( Serial serial ) : base( serial ) - { - } + defender.Paralyze(TimeSpan.FromSeconds(4.0)); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } - public override int GetIdleSound() - { - return 0x42A; - } + public override int GetIdleSound() + { + return 0x42A; + } - public override int GetAttackSound() - { - return 0x435; - } + public override int GetAttackSound() + { + return 0x435; + } - public override int GetHurtSound() - { - return 0x436; - } + public override int GetHurtSound() + { + return 0x436; + } - public override int GetDeathSound() - { - return 0x43A; - } - } -} + public override int GetDeathSound() + { + return 0x43A; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Summons/SummonedAirElemental.cs b/Scripts/Mobiles/Monsters/Summons/SummonedAirElemental.cs index aa3c6a82a..05405ffbe 100644 --- a/Scripts/Mobiles/Monsters/Summons/SummonedAirElemental.cs +++ b/Scripts/Mobiles/Monsters/Summons/SummonedAirElemental.cs @@ -1,65 +1,65 @@ namespace Server.Mobiles { - public class SummonedAirElemental : BaseCreature - { - public override string CorpseName => "an air elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; - public override string DefaultName => "an air elemental"; + public class SummonedAirElemental : BaseCreature + { + [Constructible] + public SummonedAirElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 13; + Hue = 0x4001; + BaseSoundID = 655; - [Constructible] - public SummonedAirElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 13; - Hue = 0x4001; - BaseSoundID = 655; + SetStr(200); + SetDex(200); + SetInt(100); - SetStr( 200 ); - SetDex( 200 ); - SetInt( 100 ); + SetHits(150); + SetStam(50); - SetHits( 150 ); - SetStam( 50 ); + SetDamage(6, 9); - SetDamage( 6, 9 ); + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 70, 80); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 70, 80 ); + SetSkill(SkillName.Meditation, 90.0); + SetSkill(SkillName.EvalInt, 70.0); + SetSkill(SkillName.Magery, 70.0); + SetSkill(SkillName.MagicResist, 60.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 80.0); - SetSkill( SkillName.Meditation, 90.0 ); - SetSkill( SkillName.EvalInt, 70.0 ); - SetSkill( SkillName.Magery, 70.0 ); - SetSkill( SkillName.MagicResist, 60.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 80.0 ); + VirtualArmor = 40; + ControlSlots = 2; + } - VirtualArmor = 40; - ControlSlots = 2; - } + public SummonedAirElemental(Serial serial) : base(serial) + { + } - public SummonedAirElemental( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "an air elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; + public override string DefaultName => "an air elemental"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - if ( BaseSoundID == 263 ) - BaseSoundID = 655; - } - } -} + if (BaseSoundID == 263) + BaseSoundID = 655; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Summons/SummonedDaemon.cs b/Scripts/Mobiles/Monsters/Summons/SummonedDaemon.cs index c5bcf27ea..e24f70d6f 100644 --- a/Scripts/Mobiles/Monsters/Summons/SummonedDaemon.cs +++ b/Scripts/Mobiles/Monsters/Summons/SummonedDaemon.cs @@ -1,61 +1,61 @@ namespace Server.Mobiles { - public class SummonedDaemon : BaseCreature - { - public override string CorpseName => "a daemon corpse"; - public override double DispelDifficulty => 125.0; - public override double DispelFocus => 45.0; + public class SummonedDaemon : BaseCreature + { + [Constructible] + public SummonedDaemon() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("daemon"); + Body = Core.AOS ? 10 : 9; + BaseSoundID = 357; - [Constructible] - public SummonedDaemon () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "daemon" ); - Body = Core.AOS ? 10 : 9; - BaseSoundID = 357; + SetStr(200); + SetDex(110); + SetInt(150); - SetStr( 200 ); - SetDex( 110 ); - SetInt( 150 ); + SetDamage(14, 21); - SetDamage( 14, 21 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Poison, 100); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Poison, 100 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 70, 80); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 70, 80 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 90.1, 100.0); + SetSkill(SkillName.Meditation, 90.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 100.0); + SetSkill(SkillName.MagicResist, 90.1, 100.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 98.1, 99.0); - SetSkill( SkillName.EvalInt, 90.1, 100.0 ); - SetSkill( SkillName.Meditation, 90.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 100.0 ); - SetSkill( SkillName.MagicResist, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 98.1, 99.0 ); + VirtualArmor = 58; + ControlSlots = Core.SE ? 4 : 5; + } - VirtualArmor = 58; - ControlSlots = Core.SE ? 4 : 5; - } + public SummonedDaemon(Serial serial) : base(serial) + { + } - public override Poison PoisonImmune => Poison.Regular; // TODO: Immune to poison? - public override bool CanFly => true; + public override string CorpseName => "a daemon corpse"; + public override double DispelDifficulty => 125.0; + public override double DispelFocus => 45.0; - public SummonedDaemon( Serial serial ) : base( serial ) - { - } + public override Poison PoisonImmune => Poison.Regular; // TODO: Immune to poison? + public override bool CanFly => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Summons/SummonedEarthElemental.cs b/Scripts/Mobiles/Monsters/Summons/SummonedEarthElemental.cs index 48140874f..c4e588c69 100644 --- a/Scripts/Mobiles/Monsters/Summons/SummonedEarthElemental.cs +++ b/Scripts/Mobiles/Monsters/Summons/SummonedEarthElemental.cs @@ -1,56 +1,56 @@ namespace Server.Mobiles { - public class SummonedEarthElemental : BaseCreature - { - public override string CorpseName => "an earth elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; - public override string DefaultName => "an earth elemental"; + public class SummonedEarthElemental : BaseCreature + { + [Constructible] + public SummonedEarthElemental() : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 14; + BaseSoundID = 268; - [Constructible] - public SummonedEarthElemental() : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 14; - BaseSoundID = 268; + SetStr(200); + SetDex(70); + SetInt(70); - SetStr( 200 ); - SetDex( 70 ); - SetInt( 70 ); + SetHits(180); - SetHits( 180 ); + SetDamage(14, 21); - SetDamage( 14, 21 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamageType( ResistanceType.Physical, 100 ); + SetResistance(ResistanceType.Physical, 65, 75); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 65, 75 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.MagicResist, 65.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 90.0); - SetSkill( SkillName.MagicResist, 65.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 90.0 ); + VirtualArmor = 34; + ControlSlots = 2; + } - VirtualArmor = 34; - ControlSlots = 2; - } + public SummonedEarthElemental(Serial serial) : base(serial) + { + } - public SummonedEarthElemental( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "an earth elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; + public override string DefaultName => "an earth elemental"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Summons/SummonedFireElemental.cs b/Scripts/Mobiles/Monsters/Summons/SummonedFireElemental.cs index 97a990ea9..7ef542481 100644 --- a/Scripts/Mobiles/Monsters/Summons/SummonedFireElemental.cs +++ b/Scripts/Mobiles/Monsters/Summons/SummonedFireElemental.cs @@ -2,60 +2,60 @@ using Server.Items; namespace Server.Mobiles { - public class SummonedFireElemental : BaseCreature - { - public override string CorpseName => "a fire elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; - public override string DefaultName => "a fire elemental"; + public class SummonedFireElemental : BaseCreature + { + [Constructible] + public SummonedFireElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 15; + BaseSoundID = 838; - [Constructible] - public SummonedFireElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 15; - BaseSoundID = 838; + SetStr(200); + SetDex(200); + SetInt(100); - SetStr( 200 ); - SetDex( 200 ); - SetInt( 100 ); + SetDamage(9, 14); - SetDamage( 9, 14 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Fire, 100); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Fire, 100 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 70, 80); + SetResistance(ResistanceType.Cold, 0, 10); + SetResistance(ResistanceType.Poison, 50, 60); + SetResistance(ResistanceType.Energy, 50, 60); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 70, 80 ); - SetResistance( ResistanceType.Cold, 0, 10 ); - SetResistance( ResistanceType.Poison, 50, 60 ); - SetResistance( ResistanceType.Energy, 50, 60 ); + SetSkill(SkillName.EvalInt, 90.0); + SetSkill(SkillName.Magery, 90.0); + SetSkill(SkillName.MagicResist, 85.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 92.0); - SetSkill( SkillName.EvalInt, 90.0 ); - SetSkill( SkillName.Magery, 90.0 ); - SetSkill( SkillName.MagicResist, 85.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 92.0 ); + VirtualArmor = 40; + ControlSlots = 4; - VirtualArmor = 40; - ControlSlots = 4; + AddItem(new LightSource()); + } - AddItem( new LightSource() ); - } + public SummonedFireElemental(Serial serial) : base(serial) + { + } - public SummonedFireElemental( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a fire elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; + public override string DefaultName => "a fire elemental"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Monsters/Summons/SummonedWaterElemental.cs b/Scripts/Mobiles/Monsters/Summons/SummonedWaterElemental.cs index 103d7149c..b7b6d16d0 100644 --- a/Scripts/Mobiles/Monsters/Summons/SummonedWaterElemental.cs +++ b/Scripts/Mobiles/Monsters/Summons/SummonedWaterElemental.cs @@ -1,61 +1,61 @@ namespace Server.Mobiles { - public class SummonedWaterElemental : BaseCreature - { - public override string CorpseName => "a water elemental corpse"; - public override double DispelDifficulty => 117.5; - public override double DispelFocus => 45.0; - public override string DefaultName => "a water elemental"; + public class SummonedWaterElemental : BaseCreature + { + [Constructible] + public SummonedWaterElemental() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 16; + BaseSoundID = 278; - [Constructible] - public SummonedWaterElemental () : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 16; - BaseSoundID = 278; + SetStr(200); + SetDex(70); + SetInt(100); - SetStr( 200 ); - SetDex( 70 ); - SetInt( 100 ); + SetHits(165); - SetHits( 165 ); + SetDamage(12, 16); - SetDamage( 12, 16 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Cold, 100); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Cold, 100 ); + SetResistance(ResistanceType.Physical, 50, 60); + SetResistance(ResistanceType.Fire, 20, 30); + SetResistance(ResistanceType.Cold, 70, 80); + SetResistance(ResistanceType.Poison, 45, 55); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 50, 60 ); - SetResistance( ResistanceType.Fire, 20, 30 ); - SetResistance( ResistanceType.Cold, 70, 80 ); - SetResistance( ResistanceType.Poison, 45, 55 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.Meditation, 90.0); + SetSkill(SkillName.EvalInt, 80.0); + SetSkill(SkillName.Magery, 80.0); + SetSkill(SkillName.MagicResist, 75.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 85.0); - SetSkill( SkillName.Meditation, 90.0 ); - SetSkill( SkillName.EvalInt, 80.0 ); - SetSkill( SkillName.Magery, 80.0 ); - SetSkill( SkillName.MagicResist, 75.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 85.0 ); + VirtualArmor = 40; + ControlSlots = 3; + CanSwim = true; + } - VirtualArmor = 40; - ControlSlots = 3; - CanSwim = true; - } + public SummonedWaterElemental(Serial serial) : base(serial) + { + } - public SummonedWaterElemental( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a water elemental corpse"; + public override double DispelDifficulty => 117.5; + public override double DispelFocus => 45.0; + public override string DefaultName => "a water elemental"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/PlayerMobile.cs b/Scripts/Mobiles/PlayerMobile.cs index 5850cd909..e6ff74c6a 100644 --- a/Scripts/Mobiles/PlayerMobile.cs +++ b/Scripts/Mobiles/PlayerMobile.cs @@ -1,4863 +1,4883 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Misc; -using Server.Items; -using Server.Gumps; -using Server.Multis; -using Server.Engines.Help; +using Server.Accounting; using Server.ContextMenus; +using Server.Engines.BulkOrders; +using Server.Engines.CannedEvil; +using Server.Engines.ConPVP; +using Server.Engines.Craft; +using Server.Engines.Help; +using Server.Engines.MLQuests; +using Server.Engines.MLQuests.Gumps; +using Server.Engines.MyRunUO; +using Server.Engines.PartySystem; +using Server.Engines.Quests; +using Server.Ethics; +using Server.Factions; +using Server.Guilds; +using Server.Gumps; +using Server.Items; +using Server.Misc; +using Server.Movement; +using Server.Multis; using Server.Network; +using Server.Regions; +using Server.SkillHandlers; using Server.Spells; +using Server.Spells.Bushido; using Server.Spells.Fifth; -using Server.Spells.Seventh; +using Server.Spells.Fourth; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; -using Server.Spells.Bushido; -using Server.Targeting; -using Server.Engines.Quests; -using Server.Factions; -using Server.Regions; -using Server.Accounting; -using Server.Engines.CannedEvil; -using Server.Engines.Craft; +using Server.Spells.Seventh; +using Server.Spells.Sixth; using Server.Spells.Spellweaving; -using Server.Engines.PartySystem; -using Server.Engines.MLQuests; -using Server.Guilds; +using Server.Targeting; +using BaseQuestGump = Server.Engines.MLQuests.Gumps.BaseQuestGump; +using QuestOfferGump = Server.Engines.MLQuests.Gumps.QuestOfferGump; +using RankDefinition = Server.Guilds.RankDefinition; namespace Server.Mobiles { - #region Enums - [Flags] - public enum PlayerFlag // First 16 bits are reserved for default-distro use, start custom flags at 0x00010000 - { - None = 0x00000000, - Glassblowing = 0x00000001, - Masonry = 0x00000002, - SandMining = 0x00000004, - StoneMining = 0x00000008, - ToggleMiningStone = 0x00000010, - KarmaLocked = 0x00000020, - AutoRenewInsurance = 0x00000040, - UseOwnFilter = 0x00000080, - PublicMyRunUO = 0x00000100, - PagingSquelched = 0x00000200, - Young = 0x00000400, - AcceptGuildInvites = 0x00000800, - DisplayChampionTitle = 0x00001000, - HasStatReward = 0x00002000, - RefuseTrades = 0x00004000 - } - - public enum NpcGuild - { - None, - MagesGuild, - WarriorsGuild, - ThievesGuild, - RangersGuild, - HealersGuild, - MinersGuild, - MerchantsGuild, - TinkersGuild, - TailorsGuild, - FishermensGuild, - BardsGuild, - BlacksmithsGuild - } - - public enum SolenFriendship - { - None, - Red, - Black - } - - public enum BlockMountType - { - None = -1, - Dazed = 1040024, - BolaRecovery = 1062910, - DismountRecovery = 1070859 - } - - #endregion - - public partial class PlayerMobile : Mobile, IHonorTarget - { - #region Stygian Abyss - public override void ToggleFlying() - { - if (Race != Race.Gargoyle) - { - return; - } - - if (Flying) - { - Freeze(TimeSpan.FromSeconds(1)); - Animate(61, 10, 1, true, false, 0); - Flying = false; - BuffInfo.RemoveBuff(this, BuffIcon.Fly); - SendMessage("You have landed."); - - BaseMount.Dismount(this); - return; - } - - BlockMountType type = MountBlockReason; - - if (!Alive) - { - SendLocalizedMessage(1113082); // You may not fly while dead. - } - else if (IsBodyMod && !(BodyMod == 666 || BodyMod == 667)) - { - SendLocalizedMessage(1112453); // You can't fly in your current form! - } - else if (type != BlockMountType.None) - { - switch (type) - { - case BlockMountType.Dazed: - SendLocalizedMessage(1112457); - break; // You are still too dazed to fly. - case BlockMountType.BolaRecovery: - SendLocalizedMessage(1112455); - break; // You cannot fly while recovering from a bola throw. - case BlockMountType.DismountRecovery: - SendLocalizedMessage(1112456); - break; // You cannot fly while recovering from a dismount maneuver. - } - } - else if (Hits < 25) // TODO confirm - { - SendLocalizedMessage(1112454); // You must heal before flying. - } - else - { - if (!Flying) - { - // No message? - if (Spell is FlySpell spell) - spell.Stop(); - - new FlySpell(this).Cast(); - } - else - { - Flying = false; - BuffInfo.RemoveBuff(this, BuffIcon.Fly); - } - } - } - #endregion - - private class CountAndTimeStamp - { - private int m_Count; - - public CountAndTimeStamp() - { - } - - public DateTime TimeStamp { get; private set; } - - public int Count - { - get => m_Count; - set { m_Count = value; TimeStamp = DateTime.UtcNow; } - } - } - - private bool m_IgnoreMobiles; // IgnoreMobiles should be moved to Server.Mobiles - private int m_NonAutoreinsuredItems; // number of items that could not be automatically reinsured because gold in bank was not enough - - /* - * a value of zero means, that the mobile is not executing the spell. Otherwise, - * the value should match the BaseMana required - */ - - private Guilds.RankDefinition m_GuildRank; - - private List m_AllFollowers; - - #region Getters & Setters - - public List RecentlyReported { get; set; } - - public List AutoStabled { get; private set; } - - public bool NinjaWepCooldown { get; set; } - - public List AllFollowers - { - get - { - if ( m_AllFollowers == null ) - m_AllFollowers = new List(); - return m_AllFollowers; - } - } - - public Guilds.RankDefinition GuildRank - { - get - { - if ( AccessLevel >= AccessLevel.GameMaster ) - return Guilds.RankDefinition.Leader; - return m_GuildRank; - } - set => m_GuildRank = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int GuildMessageHue { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int AllianceMessageHue { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int Profession { get; set; } - - public int StepsTaken { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsStealthing // IsStealthing should be moved to Server.Mobiles - { - get; - set; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool IgnoreMobiles // IgnoreMobiles should be moved to Server.Mobiles - { - get => m_IgnoreMobiles; - set - { - if ( m_IgnoreMobiles != value ) - { - m_IgnoreMobiles = value; - Delta( MobileDelta.Flags ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public NpcGuild NpcGuild { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NpcGuildJoinTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextBODTurnInTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastOnline { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public long LastMoved => LastMoveTime; - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan NpcGuildGameTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ToTItemsTurnedIn { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ToTTotalMonsterFame { get; set; } - - public int ExecutesLightningStrike { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int ToothAche - { - get => CandyCane.GetToothAche( this ); - set => CandyCane.SetToothAche( this, value ); - } - - #endregion - - #region PlayerFlags - public PlayerFlag Flags { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool PagingSquelched - { - get => GetFlag( PlayerFlag.PagingSquelched ); - set => SetFlag( PlayerFlag.PagingSquelched, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Glassblowing - { - get => GetFlag( PlayerFlag.Glassblowing ); - set => SetFlag( PlayerFlag.Glassblowing, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Masonry - { - get => GetFlag( PlayerFlag.Masonry ); - set => SetFlag( PlayerFlag.Masonry, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool SandMining - { - get => GetFlag( PlayerFlag.SandMining ); - set => SetFlag( PlayerFlag.SandMining, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool StoneMining - { - get => GetFlag( PlayerFlag.StoneMining ); - set => SetFlag( PlayerFlag.StoneMining, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool ToggleMiningStone - { - get => GetFlag( PlayerFlag.ToggleMiningStone ); - set => SetFlag( PlayerFlag.ToggleMiningStone, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool KarmaLocked - { - get => GetFlag( PlayerFlag.KarmaLocked ); - set => SetFlag( PlayerFlag.KarmaLocked, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool AutoRenewInsurance - { - get => GetFlag( PlayerFlag.AutoRenewInsurance ); - set => SetFlag( PlayerFlag.AutoRenewInsurance, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool UseOwnFilter - { - get => GetFlag( PlayerFlag.UseOwnFilter ); - set => SetFlag( PlayerFlag.UseOwnFilter, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool PublicMyRunUO - { - get => GetFlag( PlayerFlag.PublicMyRunUO ); - set{ SetFlag( PlayerFlag.PublicMyRunUO, value ); InvalidateMyRunUO(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool AcceptGuildInvites - { - get => GetFlag( PlayerFlag.AcceptGuildInvites ); - set => SetFlag( PlayerFlag.AcceptGuildInvites, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool HasStatReward - { - get => GetFlag( PlayerFlag.HasStatReward ); - set => SetFlag( PlayerFlag.HasStatReward, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool RefuseTrades - { - get => GetFlag( PlayerFlag.RefuseTrades ); - set => SetFlag( PlayerFlag.RefuseTrades, value ); - } - #endregion - - #region Auto Arrow Recovery - - public Dictionary RecoverableAmmo { get; } = new Dictionary(); - - public void RecoverAmmo() - { - if ( Core.SE && Alive ) - { - foreach ( KeyValuePair kvp in RecoverableAmmo ) - { - if ( kvp.Value > 0 ) - { - Item ammo = null; - - try - { - ammo = Activator.CreateInstance( kvp.Key ) as Item; - } - catch - { - } - - if ( ammo != null ) - { - string name = ammo.Name; - ammo.Amount = kvp.Value; - - if ( name == null ) - { - if ( ammo is Arrow ) - name = "arrow"; - else if ( ammo is Bolt ) - name = "bolt"; - } - - if ( name != null && ammo.Amount > 1 ) - name = $"{name}s"; - - if ( name == null ) - name = $"#{ammo.LabelNumber}"; - - PlaceInBackpack( ammo ); - SendLocalizedMessage( 1073504, $"{ammo.Amount}\t{name}"); // You recover ~1_NUM~ ~2_AMMO~. - } - } - } - - RecoverableAmmo.Clear(); - } - } - - #endregion - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime AnkhNextUse { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan DisguiseTimeLeft => DisguiseTimers.TimeRemaining( this ); - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime PeacedUntil { get; set; } - - #region Scroll of Alacrity - - [CommandProperty(AccessLevel.GameMaster)] - public DateTime AcceleratedStart { get; set; } - - [CommandProperty(AccessLevel.GameMaster)] - public SkillName AcceleratedSkill { get; set; } - - #endregion - - public static Direction GetDirection4( Point3D from, Point3D to ) - { - int dx = from.X - to.X; - int dy = from.Y - to.Y; - - int rx = dx - dy; - int ry = dx + dy; - - Direction ret; - - if ( rx >= 0 && ry >= 0 ) - ret = Direction.West; - else if ( rx >= 0 && ry < 0 ) - ret = Direction.South; - else if ( rx < 0 && ry < 0 ) - ret = Direction.East; - else - ret = Direction.North; - - return ret; - } - - public override bool OnDroppedItemToWorld( Item item, Point3D location ) - { - if ( !base.OnDroppedItemToWorld( item, location ) ) - return false; - - if ( Core.AOS ) - { - IPooledEnumerable mobiles = Map.GetMobilesInRange( location, 0 ); - - foreach ( Mobile m in mobiles ) - { - if ( m.Z >= location.Z && m.Z < location.Z + 16 && ( !m.Hidden || m.AccessLevel == AccessLevel.Player ) ) - { - mobiles.Free(); - return false; - } - } - - mobiles.Free(); - } - - BounceInfo bi = item.GetBounce(); - - if ( bi != null ) - { - Type type = item.GetType(); - - if ( type.IsDefined( typeof( FurnitureAttribute ), true ) || type.IsDefined( typeof( DynamicFlipingAttribute ), true ) ) - { - object[] objs = type.GetCustomAttributes( typeof( FlippableAttribute ), true ); - - if ( objs.Length > 0 ) - { - if ( objs[0] is FlippableAttribute fp ) - { - int[] itemIDs = fp.ItemIDs; - - Point3D oldWorldLoc = bi.m_WorldLoc; - Point3D newWorldLoc = location; - - if ( oldWorldLoc.X != newWorldLoc.X || oldWorldLoc.Y != newWorldLoc.Y ) - { - Direction dir = GetDirection4( oldWorldLoc, newWorldLoc ); - - if ( itemIDs.Length == 2 ) - { - switch ( dir ) - { - case Direction.North: - case Direction.South: item.ItemID = itemIDs[0]; break; - case Direction.East: - case Direction.West: item.ItemID = itemIDs[1]; break; - } - } - else if ( itemIDs.Length == 4 ) - { - switch ( dir ) - { - case Direction.South: item.ItemID = itemIDs[0]; break; - case Direction.East: item.ItemID = itemIDs[1]; break; - case Direction.North: item.ItemID = itemIDs[2]; break; - case Direction.West: item.ItemID = itemIDs[3]; break; - } - } - } - } - } - } - } - - return true; - } - - public override int GetPacketFlags() - { - int flags = base.GetPacketFlags(); - - if ( m_IgnoreMobiles ) - flags |= 0x10; - - return flags; - } - - public override int GetOldPacketFlags() - { - int flags = base.GetOldPacketFlags(); - - if ( m_IgnoreMobiles ) - flags |= 0x10; - - return flags; - } - - public bool GetFlag( PlayerFlag flag ) - { - return ( (Flags & flag) != 0 ); - } - - public void SetFlag( PlayerFlag flag, bool value ) - { - if ( value ) - Flags |= flag; - else - Flags &= ~flag; - } - - public DesignContext DesignContext { get; set; } - - public static void Initialize() - { - if ( FastwalkPrevention ) - PacketHandlers.RegisterThrottler( 0x02, MovementThrottle_Callback ); - - EventSink.Login += OnLogin; - EventSink.Logout += OnLogout; - EventSink.Connected += EventSink_Connected; - EventSink.Disconnected += EventSink_Disconnected; - - if ( Core.SE ) - { - Timer.DelayCall( TimeSpan.Zero, CheckPets ); - } - } - - private static void CheckPets() - { - foreach( Mobile m in World.Mobiles.Values ) - { - if ( m is PlayerMobile pm ) - { - if ((( !pm.Mounted || ( pm.Mount is EtherealMount )) && ( pm.AllFollowers.Count > pm.AutoStabled.Count )) || - ( pm.Mounted && ( pm.AllFollowers.Count > ( pm.AutoStabled.Count +1 )))) - { - pm.AutoStablePets(); /* autostable checks summons, et al: no need here */ - } - } - } - } - - private MountBlock m_MountBlock; - - public BlockMountType MountBlockReason => ( CheckBlock( m_MountBlock ) ) ? m_MountBlock.m_Type : BlockMountType.None; - - private static bool CheckBlock( MountBlock block ) - { - return ( ( block is MountBlock ) && block.m_Timer.Running ); - } - - private class MountBlock - { - public BlockMountType m_Type; - public Timer m_Timer; - - public MountBlock( TimeSpan duration, BlockMountType type, Mobile mobile ) - { - m_Type = type; - - m_Timer = Timer.DelayCall( duration, RemoveBlock, mobile ); - } - - private void RemoveBlock( Mobile mobile ) - { - ( mobile as PlayerMobile ).m_MountBlock = null; - } - } - - public void SetMountBlock( BlockMountType type, TimeSpan duration, bool dismount ) - { - if ( dismount ) - { - if ( Mount != null ) - { - Mount.Rider = null; - } - else if ( AnimalForm.UnderTransformation( this ) ) - { - AnimalForm.RemoveContext(this, true); - } - } - - if ( ( m_MountBlock == null ) || !m_MountBlock.m_Timer.Running || ( m_MountBlock.m_Timer.Next < ( DateTime.UtcNow + duration ) ) ) - { - m_MountBlock = new MountBlock( duration, type, this ); - } - } - - public override void OnSkillInvalidated( Skill skill ) - { - if ( Core.AOS && skill.SkillName == SkillName.MagicResist ) - UpdateResistances(); - } - - public override int GetMaxResistance( ResistanceType type ) - { - if ( AccessLevel > AccessLevel.Player ) - return 100; - - int max = base.GetMaxResistance( type ); - - if ( type != ResistanceType.Physical && 60 < max && Spells.Fourth.CurseSpell.UnderEffect( this ) ) - max = 60; - - if ( Core.ML && Race == Race.Elf && type == ResistanceType.Energy ) - max += 5; //Intended to go after the 60 max from curse - - return max; - } - - protected override void OnRaceChange( Race oldRace ) - { - ValidateEquipment(); - UpdateResistances(); - } - - public override int MaxWeight => (((Core.ML && Race == Race.Human) ? 100 : 40) + (int)(3.5 * Str)); - - private int m_LastGlobalLight = -1, m_LastPersonalLight = -1; - - public override void OnNetStateChanged() - { - m_LastGlobalLight = -1; - m_LastPersonalLight = -1; - } - - public override void ComputeBaseLightLevels( out int global, out int personal ) - { - global = LightCycle.ComputeLevelFor( this ); - - bool racialNightSight = (Core.ML && Race == Race.Elf); - - if ( LightLevel < 21 && ( AosAttributes.GetValue( this, AosAttribute.NightSight ) > 0 || racialNightSight )) - personal = 21; - else - personal = LightLevel; - } - - public override void CheckLightLevels( bool forceResend ) - { - NetState ns = NetState; - - if ( ns == null ) - return; - - int global, personal; - - ComputeLightLevels( out global, out personal ); - - if ( !forceResend ) - forceResend = ( global != m_LastGlobalLight || personal != m_LastPersonalLight ); - - if ( !forceResend ) - return; - - m_LastGlobalLight = global; - m_LastPersonalLight = personal; - - ns.Send( GlobalLightLevel.Instantiate( global ) ); - ns.Send( new PersonalLightLevel( this, personal ) ); - } - - public override int GetMinResistance( ResistanceType type ) - { - int magicResist = (int)(Skills[SkillName.MagicResist].Value * 10); - int min = int.MinValue; - - if ( magicResist >= 1000 ) - min = 40 + ((magicResist - 1000) / 50); - else if ( magicResist >= 400 ) - min = (magicResist - 400) / 15; - - if ( min > MaxPlayerResistance ) - min = MaxPlayerResistance; - - int baseMin = base.GetMinResistance( type ); - - if ( min < baseMin ) - min = baseMin; + #region Enums + + [Flags] + public enum PlayerFlag // First 16 bits are reserved for default-distro use, start custom flags at 0x00010000 + { + None = 0x00000000, + Glassblowing = 0x00000001, + Masonry = 0x00000002, + SandMining = 0x00000004, + StoneMining = 0x00000008, + ToggleMiningStone = 0x00000010, + KarmaLocked = 0x00000020, + AutoRenewInsurance = 0x00000040, + UseOwnFilter = 0x00000080, + PublicMyRunUO = 0x00000100, + PagingSquelched = 0x00000200, + Young = 0x00000400, + AcceptGuildInvites = 0x00000800, + DisplayChampionTitle = 0x00001000, + HasStatReward = 0x00002000, + RefuseTrades = 0x00004000 + } + + public enum NpcGuild + { + None, + MagesGuild, + WarriorsGuild, + ThievesGuild, + RangersGuild, + HealersGuild, + MinersGuild, + MerchantsGuild, + TinkersGuild, + TailorsGuild, + FishermensGuild, + BardsGuild, + BlacksmithsGuild + } + + public enum SolenFriendship + { + None, + Red, + Black + } + + public enum BlockMountType + { + None = -1, + Dazed = 1040024, + BolaRecovery = 1062910, + DismountRecovery = 1070859 + } + + #endregion + + public class PlayerMobile : Mobile, IHonorTarget + { + private static bool m_NoRecursion; + + private List m_AllFollowers; + + private Hashtable m_AntiMacroTable; + private TimeSpan m_GameTime; + + /* + * a value of zero means, that the mobile is not executing the spell. Otherwise, + * the value should match the BaseMana required + */ + + private RankDefinition m_GuildRank; + + private bool m_IgnoreMobiles; // IgnoreMobiles should be moved to Server.Mobiles + + private Mobile m_InsuranceAward; + private int m_InsuranceBonus; + private int m_InsuranceCost; + + private int m_LastGlobalLight = -1, m_LastPersonalLight = -1; + + private bool m_LastProtectedMessage; + private TimeSpan m_LongTermElapse; + + private MountBlock m_MountBlock; + private int m_NextProtectionCheck = 10; + private DateTime m_NextSmithBulkOrder; + private DateTime m_NextTailorBulkOrder; + + private bool m_NoDeltaRecursion; + + private int + m_NonAutoreinsuredItems; // number of items that could not be automatically reinsured because gold in bank was not enough + + private DateTime m_SavagePaintExpiration; + private TimeSpan m_ShortTermElapse; + + public PlayerMobile() + { + AutoStabled = new List(); + + VisibilityList = new List(); + PermaFlags = new List(); + m_AntiMacroTable = new Hashtable(); + RecentlyReported = new List(); + + BOBFilter = new BOBFilter(); + + m_GameTime = TimeSpan.Zero; + m_ShortTermElapse = TimeSpan.FromHours(8.0); + m_LongTermElapse = TimeSpan.FromHours(40.0); + + JusticeProtectors = new List(); + m_GuildRank = RankDefinition.Lowest; + + m_ChampionTitles = new ChampionTitleInfo(); + + InvalidateMyRunUO(); + } + + public PlayerMobile(Serial s) : base(s) + { + VisibilityList = new List(); + m_AntiMacroTable = new Hashtable(); + InvalidateMyRunUO(); + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime AnkhNextUse{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan DisguiseTimeLeft => DisguiseTimers.TimeRemaining(this); + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime PeacedUntil{ get; set; } + + public DesignContext DesignContext{ get; set; } + + public BlockMountType MountBlockReason => CheckBlock(m_MountBlock) ? m_MountBlock.m_Type : BlockMountType.None; + + public override int MaxWeight => (Core.ML && Race == Race.Human ? 100 : 40) + (int)(3.5 * Str); + + public override double ArmorRating + { + get + { + //BaseArmor ar; + double rating = 0.0; + + AddArmorRating(ref rating, NeckArmor); + AddArmorRating(ref rating, HandArmor); + AddArmorRating(ref rating, HeadArmor); + AddArmorRating(ref rating, ArmsArmor); + AddArmorRating(ref rating, LegsArmor); + AddArmorRating(ref rating, ChestArmor); + AddArmorRating(ref rating, ShieldArmor); + + return VirtualArmor + VirtualArmorMod + rating; + } + } - return min; - } + public SkillName[] AnimalFormRestrictedSkills{ get; } = + { + SkillName.ArmsLore, SkillName.Begging, SkillName.Discordance, SkillName.Forensics, + SkillName.Inscribe, SkillName.ItemID, SkillName.Meditation, SkillName.Peacemaking, + SkillName.Provocation, SkillName.RemoveTrap, SkillName.SpiritSpeak, SkillName.Stealing, + SkillName.TasteID + }; + + public override double RacialSkillBonus + { + get + { + if (Core.ML && Race == Race.Human) + return 20.0; + + return 0; + } + } + + public List EquipSnapshot{ get; private set; } + + public SkillName Learning{ get; set; } = (SkillName)(-1); + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan SavagePaintExpiration + { + get + { + TimeSpan ts = m_SavagePaintExpiration - DateTime.UtcNow; + + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; + + return ts; + } + set => m_SavagePaintExpiration = DateTime.UtcNow + value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan NextSmithBulkOrder + { + get + { + TimeSpan ts = m_NextSmithBulkOrder - DateTime.UtcNow; + + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; + + return ts; + } + set + { + try + { + m_NextSmithBulkOrder = DateTime.UtcNow + value; + } + catch + { + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan NextTailorBulkOrder + { + get + { + TimeSpan ts = m_NextTailorBulkOrder - DateTime.UtcNow; + + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; + + return ts; + } + set + { + try + { + m_NextTailorBulkOrder = DateTime.UtcNow + value; + } + catch + { + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastEscortTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastPetBallTime{ get; set; } + + public List VisibilityList{ get; } + + public List PermaFlags{ get; private set; } + + public override int Luck => AosAttributes.GetValue(this, AosAttribute.Luck); + + public BOBFilter BOBFilter{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime SessionStart{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan GameTime + { + get + { + if (NetState != null) + return m_GameTime + (DateTime.UtcNow - SessionStart); + return m_GameTime; + } + } + + public override bool NewGuildDisplay => Guilds.Guild.NewGuildSystem; + + public bool BedrollLogout{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public override bool Paralyzed + { + get => base.Paralyzed; + set + { + base.Paralyzed = value; + + if (value) + AddBuff(new BuffInfo(BuffIcon.Paralyze, 1075827)); //Paralyze/You are frozen and can not move + else + RemoveBuff(BuffIcon.Paralyze); + } + } + + #region Ethics + + [CommandProperty(AccessLevel.GameMaster)] + public Player EthicPlayer{ get; set; } + + #endregion + + #region Factions + + public PlayerState FactionPlayerState{ get; set; } + + #endregion + + #region Stygian Abyss + + public override void ToggleFlying() + { + if (Race != Race.Gargoyle) return; + + if (Flying) + { + Freeze(TimeSpan.FromSeconds(1)); + Animate(61, 10, 1, true, false, 0); + Flying = false; + BuffInfo.RemoveBuff(this, BuffIcon.Fly); + SendMessage("You have landed."); + + BaseMount.Dismount(this); + return; + } + + BlockMountType type = MountBlockReason; + + if (!Alive) + { + SendLocalizedMessage(1113082); // You may not fly while dead. + } + else if (IsBodyMod && !(BodyMod == 666 || BodyMod == 667)) + { + SendLocalizedMessage(1112453); // You can't fly in your current form! + } + else if (type != BlockMountType.None) + { + switch (type) + { + case BlockMountType.Dazed: + SendLocalizedMessage(1112457); + break; // You are still too dazed to fly. + case BlockMountType.BolaRecovery: + SendLocalizedMessage(1112455); + break; // You cannot fly while recovering from a bola throw. + case BlockMountType.DismountRecovery: + SendLocalizedMessage(1112456); + break; // You cannot fly while recovering from a dismount maneuver. + } + } + else if (Hits < 25) // TODO confirm + { + SendLocalizedMessage(1112454); // You must heal before flying. + } + else + { + if (!Flying) + { + // No message? + if (Spell is FlySpell spell) + spell.Stop(); + + new FlySpell(this).Cast(); + } + else + { + Flying = false; + BuffInfo.RemoveBuff(this, BuffIcon.Fly); + } + } + } + + #endregion + + public static Direction GetDirection4(Point3D from, Point3D to) + { + int dx = from.X - to.X; + int dy = from.Y - to.Y; + + int rx = dx - dy; + int ry = dx + dy; + + Direction ret; + + if (rx >= 0 && ry >= 0) + ret = Direction.West; + else if (rx >= 0 && ry < 0) + ret = Direction.South; + else if (rx < 0 && ry < 0) + ret = Direction.East; + else + ret = Direction.North; + + return ret; + } + + public override bool OnDroppedItemToWorld(Item item, Point3D location) + { + if (!base.OnDroppedItemToWorld(item, location)) + return false; + + if (Core.AOS) + { + IPooledEnumerable mobiles = Map.GetMobilesInRange(location, 0); + + foreach (Mobile m in mobiles) + if (m.Z >= location.Z && m.Z < location.Z + 16 && (!m.Hidden || m.AccessLevel == AccessLevel.Player)) + { + mobiles.Free(); + return false; + } + + mobiles.Free(); + } + + BounceInfo bi = item.GetBounce(); + + if (bi != null) + { + Type type = item.GetType(); + + if (type.IsDefined(typeof(FurnitureAttribute), true) || + type.IsDefined(typeof(DynamicFlipingAttribute), true)) + { + object[] objs = type.GetCustomAttributes(typeof(FlippableAttribute), true); + + if (objs.Length > 0) + if (objs[0] is FlippableAttribute fp) + { + int[] itemIDs = fp.ItemIDs; + + Point3D oldWorldLoc = bi.m_WorldLoc; + Point3D newWorldLoc = location; + + if (oldWorldLoc.X != newWorldLoc.X || oldWorldLoc.Y != newWorldLoc.Y) + { + Direction dir = GetDirection4(oldWorldLoc, newWorldLoc); + + if (itemIDs.Length == 2) + switch (dir) + { + case Direction.North: + case Direction.South: + item.ItemID = itemIDs[0]; + break; + case Direction.East: + case Direction.West: + item.ItemID = itemIDs[1]; + break; + } + else if (itemIDs.Length == 4) + switch (dir) + { + case Direction.South: + item.ItemID = itemIDs[0]; + break; + case Direction.East: + item.ItemID = itemIDs[1]; + break; + case Direction.North: + item.ItemID = itemIDs[2]; + break; + case Direction.West: + item.ItemID = itemIDs[3]; + break; + } + } + } + } + } + + return true; + } + + public override int GetPacketFlags() + { + int flags = base.GetPacketFlags(); + + if (m_IgnoreMobiles) + flags |= 0x10; + + return flags; + } + + public override int GetOldPacketFlags() + { + int flags = base.GetOldPacketFlags(); + + if (m_IgnoreMobiles) + flags |= 0x10; + + return flags; + } + + public bool GetFlag(PlayerFlag flag) + { + return (Flags & flag) != 0; + } + + public void SetFlag(PlayerFlag flag, bool value) + { + if (value) + Flags |= flag; + else + Flags &= ~flag; + } + + public static void Initialize() + { + if (FastwalkPrevention) + PacketHandlers.RegisterThrottler(0x02, MovementThrottle_Callback); + + EventSink.Login += OnLogin; + EventSink.Logout += OnLogout; + EventSink.Connected += EventSink_Connected; + EventSink.Disconnected += EventSink_Disconnected; + + if (Core.SE) Timer.DelayCall(TimeSpan.Zero, CheckPets); + } + + private static void CheckPets() + { + foreach (Mobile m in World.Mobiles.Values) + if (m is PlayerMobile pm) + if ((!pm.Mounted || pm.Mount is EtherealMount) && pm.AllFollowers.Count > pm.AutoStabled.Count || + pm.Mounted && pm.AllFollowers.Count > pm.AutoStabled.Count + 1) + pm.AutoStablePets(); /* autostable checks summons, et al: no need here */ + } + + private static bool CheckBlock(MountBlock block) + { + return block is MountBlock && block.m_Timer.Running; + } + + public void SetMountBlock(BlockMountType type, TimeSpan duration, bool dismount) + { + if (dismount) + { + if (Mount != null) + Mount.Rider = null; + else if (AnimalForm.UnderTransformation(this)) AnimalForm.RemoveContext(this, true); + } + + if (m_MountBlock == null || !m_MountBlock.m_Timer.Running || + m_MountBlock.m_Timer.Next < DateTime.UtcNow + duration) m_MountBlock = new MountBlock(duration, type, this); + } + + public override void OnSkillInvalidated(Skill skill) + { + if (Core.AOS && skill.SkillName == SkillName.MagicResist) + UpdateResistances(); + } + + public override int GetMaxResistance(ResistanceType type) + { + if (AccessLevel > AccessLevel.Player) + return 100; + + int max = base.GetMaxResistance(type); + + if (type != ResistanceType.Physical && 60 < max && CurseSpell.UnderEffect(this)) + max = 60; + + if (Core.ML && Race == Race.Elf && type == ResistanceType.Energy) + max += 5; //Intended to go after the 60 max from curse + + return max; + } + + protected override void OnRaceChange(Race oldRace) + { + ValidateEquipment(); + UpdateResistances(); + } + + public override void OnNetStateChanged() + { + m_LastGlobalLight = -1; + m_LastPersonalLight = -1; + } + + public override void ComputeBaseLightLevels(out int global, out int personal) + { + global = LightCycle.ComputeLevelFor(this); + + bool racialNightSight = Core.ML && Race == Race.Elf; + + if (LightLevel < 21 && (AosAttributes.GetValue(this, AosAttribute.NightSight) > 0 || racialNightSight)) + personal = 21; + else + personal = LightLevel; + } + + public override void CheckLightLevels(bool forceResend) + { + NetState ns = NetState; + + if (ns == null) + return; + + int global, personal; + + ComputeLightLevels(out global, out personal); + + if (!forceResend) + forceResend = global != m_LastGlobalLight || personal != m_LastPersonalLight; + + if (!forceResend) + return; + + m_LastGlobalLight = global; + m_LastPersonalLight = personal; + + ns.Send(GlobalLightLevel.Instantiate(global)); + ns.Send(new PersonalLightLevel(this, personal)); + } + + public override int GetMinResistance(ResistanceType type) + { + int magicResist = (int)(Skills[SkillName.MagicResist].Value * 10); + int min = int.MinValue; + + if (magicResist >= 1000) + min = 40 + (magicResist - 1000) / 50; + else if (magicResist >= 400) + min = (magicResist - 400) / 15; - public override void OnManaChange(int oldValue) - { - base.OnManaChange(oldValue); - if (ExecutesLightningStrike > 0) - { - if (Mana < ExecutesLightningStrike) - { - SpecialMove.ClearCurrentMove(this); - } - } - } - - private static void OnLogin( LoginEventArgs e ) - { - Mobile from = e.Mobile; - - CheckAtrophies( from ); - - if ( AccountHandler.LockdownLevel > AccessLevel.Player ) - { - string notice; - - if ( !(from.Account is Account acct) || !acct.HasAccess( from.NetState ) ) - { - if ( from.AccessLevel == AccessLevel.Player ) - notice = "The server is currently under lockdown. No players are allowed to log in at this time."; - else - notice = "The server is currently under lockdown. You do not have sufficient access level to connect."; - - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), new TimerStateCallback( Disconnect ), from ); - } - else if ( from.AccessLevel >= AccessLevel.Administrator ) - { - notice = "The server is currently under lockdown. As you are an administrator, you may change this from the [Admin gump."; - } - else - { - notice = "The server is currently under lockdown. You have sufficient access level to connect."; - } - - from.SendGump( new NoticeGump( 1060637, 30720, notice, 0xFFC000, 300, 140, null, null ) ); - return; - } - - if ( from is PlayerMobile mobile ) - mobile.ClaimAutoStabledPets(); - } - - private bool m_NoDeltaRecursion; - - public void ValidateEquipment() - { - if ( m_NoDeltaRecursion || Map == null || Map == Map.Internal ) - return; - - if ( Items == null ) - return; - - m_NoDeltaRecursion = true; - Timer.DelayCall( TimeSpan.Zero, ValidateEquipment_Sandbox ); - } - - private void ValidateEquipment_Sandbox() - { - try - { - if ( Map == null || Map == Map.Internal ) - return; - - List items = Items; - - if ( items == null ) - return; - - bool moved = false; - - int str = Str; - int dex = Dex; - int intel = Int; - - #region Factions - int factionItemCount = 0; - #endregion - - Mobile from = this; - - #region Ethics - Ethics.Ethic ethic = Ethics.Ethic.Find( from ); - #endregion - - for ( int i = items.Count - 1; i >= 0; --i ) - { - if ( i >= items.Count ) - continue; - - Item item = items[i]; - - #region Ethics - if ( ( item.SavedFlags & 0x100 ) != 0 ) - { - if ( item.Hue != Ethics.Ethic.Hero.Definition.PrimaryHue ) - { - item.SavedFlags &= ~0x100; - } - else if ( ethic != Ethics.Ethic.Hero ) - { - from.AddToBackpack( item ); - moved = true; - continue; - } - } - else if ( ( item.SavedFlags & 0x200 ) != 0 ) - { - if ( item.Hue != Ethics.Ethic.Evil.Definition.PrimaryHue ) - { - item.SavedFlags &= ~0x200; - } - else if ( ethic != Ethics.Ethic.Evil ) - { - from.AddToBackpack( item ); - moved = true; - continue; - } - } - #endregion - - if ( item is BaseWeapon weapon ) - { - bool drop = false; - - if ( dex < weapon.DexRequirement ) - drop = true; - else if ( str < AOS.Scale( weapon.StrRequirement, 100 - weapon.GetLowerStatReq() ) ) - drop = true; - else if ( intel < weapon.IntRequirement ) - drop = true; - else if ( weapon.RequiredRace != null && weapon.RequiredRace != Race ) - drop = true; - - if ( drop ) - { - string name = weapon.Name; - - if ( name == null ) - name = $"#{weapon.LabelNumber}"; - - from.SendLocalizedMessage( 1062001, name ); // You can no longer wield your ~1_WEAPON~ - from.AddToBackpack( weapon ); - moved = true; - } - } - else if ( item is BaseArmor armor ) - { - bool drop = false; - - if ( !armor.AllowMaleWearer && !from.Female && from.AccessLevel < AccessLevel.GameMaster ) - { - drop = true; - } - else if ( !armor.AllowFemaleWearer && from.Female && from.AccessLevel < AccessLevel.GameMaster ) - { - drop = true; - } - else if ( armor.RequiredRace != null && armor.RequiredRace != Race ) - { - drop = true; - } - else - { - int strBonus = armor.ComputeStatBonus( StatType.Str ), strReq = armor.ComputeStatReq( StatType.Str ); - int dexBonus = armor.ComputeStatBonus( StatType.Dex ), dexReq = armor.ComputeStatReq( StatType.Dex ); - int intBonus = armor.ComputeStatBonus( StatType.Int ), intReq = armor.ComputeStatReq( StatType.Int ); - - if ( dex < dexReq || (dex + dexBonus) < 1 ) - drop = true; - else if ( str < strReq || (str + strBonus) < 1 ) - drop = true; - else if ( intel < intReq || (intel + intBonus) < 1 ) - drop = true; - } - - if ( drop ) - { - string name = armor.Name; - - if ( name == null ) - name = $"#{armor.LabelNumber}"; - - if ( armor is BaseShield ) - from.SendLocalizedMessage( 1062003, name ); // You can no longer equip your ~1_SHIELD~ - else - from.SendLocalizedMessage( 1062002, name ); // You can no longer wear your ~1_ARMOR~ - - from.AddToBackpack( armor ); - moved = true; - } - } - else if ( item is BaseClothing clothing ) - { - bool drop = false; - - if ( !clothing.AllowMaleWearer && !from.Female && from.AccessLevel < AccessLevel.GameMaster ) - { - drop = true; - } - else if ( !clothing.AllowFemaleWearer && from.Female && from.AccessLevel < AccessLevel.GameMaster ) - { - drop = true; - } - else if ( clothing.RequiredRace != null && clothing.RequiredRace != Race ) - { - drop = true; - } - else - { - int strBonus = clothing.ComputeStatBonus( StatType.Str ); - int strReq = clothing.ComputeStatReq( StatType.Str ); - - if ( str < strReq || (str + strBonus) < 1 ) - drop = true; - } - - if ( drop ) - { - string name = clothing.Name; - - if ( name == null ) - name = $"#{clothing.LabelNumber}"; - - from.SendLocalizedMessage( 1062002, name ); // You can no longer wear your ~1_ARMOR~ - - from.AddToBackpack( clothing ); - moved = true; - } - } - - FactionItem factionItem = FactionItem.Find( item ); - - if ( factionItem != null ) - { - bool drop = false; - - Faction ourFaction = Faction.Find( this ); - - if ( ourFaction == null || ourFaction != factionItem.Faction ) - drop = true; - else if ( ++factionItemCount > FactionItem.GetMaxWearables( this ) ) - drop = true; - - if ( drop ) - { - from.AddToBackpack( item ); - moved = true; - } - } - } - - if ( moved ) - from.SendLocalizedMessage( 500647 ); // Some equipment has been moved to your backpack. - } - catch ( Exception e ) - { - Console.WriteLine( e ); - } - finally - { - m_NoDeltaRecursion = false; - } - } - - public override void Delta( MobileDelta flag ) - { - base.Delta( flag ); - - if ( (flag & MobileDelta.Stat) != 0 ) - ValidateEquipment(); - - if ( (flag & (MobileDelta.Name | MobileDelta.Hue)) != 0 ) - InvalidateMyRunUO(); - } - - private static void Disconnect( object state ) - { - NetState ns = ((Mobile)state).NetState; - ns?.Dispose(); - } - - private static void OnLogout( LogoutEventArgs e ) - { - if ( e.Mobile is PlayerMobile mobile ) - mobile.AutoStablePets(); - } - - private static void EventSink_Connected( ConnectedEventArgs e ) - { - if ( e.Mobile is PlayerMobile pm ) - { - pm.SessionStart = DateTime.UtcNow; - - pm.Quest?.StartTimer(); - - pm.BedrollLogout = false; - pm.LastOnline = DateTime.UtcNow; - } - - DisguiseTimers.StartTimer( e.Mobile ); - - Timer.DelayCall( TimeSpan.Zero, new TimerStateCallback( ClearSpecialMovesCallback ), e.Mobile ); - } - - private static void ClearSpecialMovesCallback( object state ) - { - Mobile from = (Mobile)state; - - SpecialMove.ClearAllMoves( from ); - } - - private static void EventSink_Disconnected( DisconnectedEventArgs e ) - { - Mobile from = e.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client disconnected - * - Remove design context - * - Eject all from house - * - Restore relocated entities - */ - - // Remove design context - DesignContext.Remove( from ); - - // Eject all from house - from.RevealingAction(); - - foreach ( Item item in context.Foundation.GetItems() ) - item.Location = context.Foundation.BanLocation; - - foreach ( Mobile mobile in context.Foundation.GetMobiles() ) - mobile.Location = context.Foundation.BanLocation; - - // Restore relocated entities - context.Foundation.RestoreRelocatedEntities(); - } - - if ( e.Mobile is PlayerMobile pm ) - { - pm.m_GameTime += (DateTime.UtcNow - pm.SessionStart); - - pm.Quest?.StopTimer(); - - pm.SpeechLog = null; - pm.LastOnline = DateTime.UtcNow; - } - - DisguiseTimers.StopTimer( from ); - } - - public override void RevealingAction() - { - if ( DesignContext != null ) - return; - - Spells.Sixth.InvisibilitySpell.RemoveTimer( this ); - - base.RevealingAction(); - - IsStealthing = false; // IsStealthing should be moved to Server.Mobiles - } - - public override void OnHiddenChanged() - { - base.OnHiddenChanged(); - - RemoveBuff(BuffIcon.Invisibility); //Always remove, default to the hiding icon EXCEPT in the invis spell where it's explicitly set - - if (!Hidden) - { - RemoveBuff(BuffIcon.HidingAndOrStealth); - } - else// if ( !InvisibilitySpell.HasTimer( this ) ) - { - BuffInfo.AddBuff(this, new BuffInfo(BuffIcon.HidingAndOrStealth, 1075655)); //Hidden/Stealthing & You Are Hidden - } - } - - public override void OnSubItemAdded( Item item ) - { - if ( AccessLevel < AccessLevel.GameMaster && item.IsChildOf( Backpack ) ) - { - int maxWeight = WeightOverloading.GetMaxWeight( this ); - int curWeight = BodyWeight + TotalWeight; - - if ( curWeight > maxWeight ) - SendLocalizedMessage( 1019035, true, $" : {curWeight} / {maxWeight}"); - } - - base.OnSubItemAdded(item); - } - - public override bool CanBeHarmful( Mobile target, bool message, bool ignoreOurBlessedness ) - { - if ( DesignContext != null || (target is PlayerMobile mobile && mobile.DesignContext != null) ) - return false; - - if ( (target is BaseCreature creature && creature.IsInvulnerable) || target is PlayerVendor || target is TownCrier ) - { - if ( message ) - { - if ( target.Title == null ) - SendMessage( "{0} cannot be harmed.", target.Name ); - else - SendMessage( "{0} {1} cannot be harmed.", target.Name, target.Title ); - } - - return false; - } - - return base.CanBeHarmful( target, message, ignoreOurBlessedness ); - } - - public override bool CanBeBeneficial( Mobile target, bool message, bool allowDead ) - { - if ( DesignContext != null || (target is PlayerMobile mobile && mobile.DesignContext != null) ) - return false; - - return base.CanBeBeneficial( target, message, allowDead ); - } - - public override bool CheckContextMenuDisplay( IEntity target ) - { - return ( DesignContext == null ); - } - - public override void OnItemAdded( Item item ) - { - base.OnItemAdded( item ); - - if ( item is BaseArmor || item is BaseWeapon ) - { - Hits = Hits; - Stam = Stam; - Mana = Mana; - } - - if ( NetState != null ) - CheckLightLevels( false ); - - InvalidateMyRunUO(); - } - - public override void OnItemRemoved( Item item ) - { - base.OnItemRemoved( item ); - - if ( item is BaseArmor || item is BaseWeapon ) - { - Hits = Hits; - Stam = Stam; - Mana = Mana; - } - - if ( NetState != null ) - CheckLightLevels( false ); - - InvalidateMyRunUO(); - } - - public override double ArmorRating - { - get - { - //BaseArmor ar; - double rating = 0.0; - - AddArmorRating( ref rating, NeckArmor ); - AddArmorRating( ref rating, HandArmor ); - AddArmorRating( ref rating, HeadArmor ); - AddArmorRating( ref rating, ArmsArmor ); - AddArmorRating( ref rating, LegsArmor ); - AddArmorRating( ref rating, ChestArmor ); - AddArmorRating( ref rating, ShieldArmor ); - - return VirtualArmor + VirtualArmorMod + rating; - } - } - - private void AddArmorRating( ref double rating, Item armor ) - { - if ( armor is BaseArmor ar && ( !Core.AOS || ar.ArmorAttributes.MageArmor == 0 )) - rating += ar.ArmorRatingScaled; - } - - #region [Stats]Max - [CommandProperty( AccessLevel.GameMaster )] - public override int HitsMax - { - get - { - int strBase; - int strOffs = GetStatOffset( StatType.Str ); - - if ( Core.AOS ) - { - strBase = Str; //this.Str already includes GetStatOffset/str - strOffs = AosAttributes.GetValue( this, AosAttribute.BonusHits ); - - if ( Core.ML && strOffs > 25 && AccessLevel <= AccessLevel.Player ) - strOffs = 25; - - if ( AnimalForm.UnderTransformation( this, typeof( BakeKitsune ) ) || AnimalForm.UnderTransformation( this, typeof( GreyWolf ) ) ) - strOffs += 20; - } - else - { - strBase = RawStr; - } - - return (strBase / 2) + 50 + strOffs; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public override int StamMax => base.StamMax + AosAttributes.GetValue( this, AosAttribute.BonusStam ); - - [CommandProperty( AccessLevel.GameMaster )] - public override int ManaMax => base.ManaMax + AosAttributes.GetValue( this, AosAttribute.BonusMana ) + ((Core.ML && Race == Race.Elf) ? 20 : 0); - - #endregion - - #region Stat Getters/Setters - - [CommandProperty( AccessLevel.GameMaster )] - public override int Str - { - get - { - if ( Core.ML && AccessLevel == AccessLevel.Player ) - return Math.Min( base.Str, 150 ); - - return base.Str; - } - set => base.Str = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public override int Int - { - get - { - if ( Core.ML && AccessLevel == AccessLevel.Player ) - return Math.Min( base.Int, 150 ); - - return base.Int; - } - set => base.Int = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public override int Dex - { - get - { - if ( Core.ML && AccessLevel == AccessLevel.Player ) - return Math.Min( base.Dex, 150 ); - - return base.Dex; - } - set => base.Dex = value; - } - - #endregion - - public override bool Move( Direction d ) - { - NetState ns = NetState; - - if ( ns != null ) - { - if ( HasGump( typeof( ResurrectGump ) ) ) { - if ( Alive ) { - CloseGump( typeof( ResurrectGump ) ); - } else { - SendLocalizedMessage( 500111 ); // You are frozen and cannot move. - return false; - } - } - } - - int speed = ComputeMovementSpeed( d ); - - bool res; - - if ( !Alive ) - Movement.MovementImpl.IgnoreMovableImpassables = true; - - res = base.Move( d ); - - Movement.MovementImpl.IgnoreMovableImpassables = false; - - if ( !res ) - return false; - - m_NextMovementTime += speed; - - return true; - } - - public override bool CheckMovement( Direction d, out int newZ ) - { - DesignContext context = DesignContext; - - if ( context == null ) - return base.CheckMovement( d, out newZ ); - - HouseFoundation foundation = context.Foundation; - - newZ = foundation.Z + HouseFoundation.GetLevelZ( context.Level, context.Foundation ); - - int newX = X, newY = Y; - Movement.Movement.Offset( d, ref newX, ref newY ); - - int startX = foundation.X + foundation.Components.Min.X + 1; - int startY = foundation.Y + foundation.Components.Min.Y + 1; - int endX = startX + foundation.Components.Width - 1; - int endY = startY + foundation.Components.Height - 2; - - return ( newX >= startX && newY >= startY && newX < endX && newY < endY && Map == foundation.Map ); - } - - public override bool AllowItemUse( Item item ) - { - #region Dueling - if ( DuelContext != null && !DuelContext.AllowItemUse( this, item ) ) - return false; - #endregion - - return DesignContext.Check( this ); - } - - public SkillName[] AnimalFormRestrictedSkills { get; } = - { - SkillName.ArmsLore, SkillName.Begging, SkillName.Discordance, SkillName.Forensics, - SkillName.Inscribe, SkillName.ItemID, SkillName.Meditation, SkillName.Peacemaking, - SkillName.Provocation, SkillName.RemoveTrap, SkillName.SpiritSpeak, SkillName.Stealing, - SkillName.TasteID - }; - - public override bool AllowSkillUse( SkillName skill ) - { - if ( AnimalForm.UnderTransformation( this ) ) - { - for( int i = 0; i < AnimalFormRestrictedSkills.Length; i++ ) - { - if ( AnimalFormRestrictedSkills[i] == skill ) - { - SendLocalizedMessage( 1070771 ); // You cannot use that skill in this form. - return false; - } - } - } - - #region Dueling - if ( DuelContext != null && !DuelContext.AllowSkillUse( this, skill ) ) - return false; - #endregion - - return DesignContext.Check( this ); - } - - private bool m_LastProtectedMessage; - private int m_NextProtectionCheck = 10; - - public virtual void RecheckTownProtection() - { - m_NextProtectionCheck = 10; - - GuardedRegion reg = (GuardedRegion) Region.GetRegion( typeof( GuardedRegion ) ); - bool isProtected = ( reg != null && !reg.IsDisabled() ); - - if ( isProtected != m_LastProtectedMessage ) - { - if ( isProtected ) - SendLocalizedMessage( 500112 ); // You are now under the protection of the town guards. - else - SendLocalizedMessage( 500113 ); // You have left the protection of the town guards. - - m_LastProtectedMessage = isProtected; - } - } - - public override void MoveToWorld( Point3D loc, Map map ) - { - base.MoveToWorld( loc, map ); - - RecheckTownProtection(); - } - - public override void SetLocation( Point3D loc, bool isTeleport ) - { - if ( !isTeleport && AccessLevel == AccessLevel.Player ) - { - // moving, not teleporting - int zDrop = ( Location.Z - loc.Z ); - - if ( zDrop > 20 ) // we fell more than one story - Hits -= ((zDrop / 20) * 10) - 5; // deal some damage; does not kill, disrupt, etc - } - - base.SetLocation( loc, isTeleport ); - - if ( isTeleport || --m_NextProtectionCheck == 0 ) - RecheckTownProtection(); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( from == this ) - { - Quest?.GetContextMenuEntries( list ); - - if ( Alive ) - { - if ( InsuranceEnabled ) - { - if ( Core.SA ) - list.Add( new CallbackEntry( 1114299, OpenItemInsuranceMenu ) ); // Open Item Insurance Menu - - list.Add( new CallbackEntry( 6201, ToggleItemInsurance ) ); // Toggle Item Insurance - - if ( !Core.SA ) - { - if ( AutoRenewInsurance ) - list.Add( new CallbackEntry( 6202, CancelRenewInventoryInsurance ) ); // Cancel Renewing Inventory Insurance - else - list.Add( new CallbackEntry( 6200, AutoRenewInventoryInsurance ) ); // Auto Renew Inventory Insurance - } - } - - if ( MLQuestSystem.Enabled ) - list.Add( new CallbackEntry( 6169, ToggleQuestItem ) ); // Toggle Quest Item - } - - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null ) - { - if ( Alive && house.InternalizedVendors.Count > 0 && house.IsOwner( this ) ) - list.Add( new CallbackEntry( 6204, GetVendor ) ); - - if ( house.IsAosRules && !Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) // Dueling - list.Add( new CallbackEntry( 6207, LeaveHouse ) ); - } - - if ( JusticeProtectors.Count > 0 ) - list.Add( new CallbackEntry( 6157, CancelProtection ) ); - - if ( Alive ) - list.Add( new CallbackEntry( 6210, ToggleChampionTitleDisplay ) ); - - if ( Core.HS ) - { - NetState ns = from.NetState; - - if ( ns != null && ns.ExtendedStatus ) - list.Add( new CallbackEntry( RefuseTrades ? 1154112 : 1154113, ToggleTrades ) ); // Allow Trades / Refuse Trades - } - } - else - { - if (Core.TOL && from.InRange(this, 2)) - { - list.Add(new CallbackEntry(1077728, () => OpenTrade(from))); // Trade - } - - if ( Alive && Core.Expansion >= Expansion.AOS ) - { - Party theirParty = from.Party as Party; - Party ourParty = Party as Party; - - if ( theirParty == null && ourParty == null ) { - list.Add( new AddToPartyEntry( from, this ) ); - } else if ( theirParty != null && theirParty.Leader == from ) { - if ( ourParty == null ) { - list.Add( new AddToPartyEntry( from, this ) ); - } else if ( ourParty == theirParty ) { - list.Add( new RemoveFromPartyEntry( from, this ) ); - } - } - } - - BaseHouse curhouse = BaseHouse.FindHouseAt( this ); - - if ( curhouse != null ) - { - if ( Alive && Core.Expansion >= Expansion.AOS && curhouse.IsAosRules && curhouse.IsFriend( from ) ) - list.Add( new EjectPlayerEntry( from, this ) ); - } - } - } - - private void CancelProtection() - { - for ( int i = 0; i < JusticeProtectors.Count; ++i ) - { - Mobile prot = JusticeProtectors[i]; - - string args = $"{Name}\t{prot.Name}"; - - prot.SendLocalizedMessage( 1049371, args ); // The protective relationship between ~1_PLAYER1~ and ~2_PLAYER2~ has been ended. - SendLocalizedMessage( 1049371, args ); // The protective relationship between ~1_PLAYER1~ and ~2_PLAYER2~ has been ended. - } - - JusticeProtectors.Clear(); - } - - #region Insurance - - private static int GetInsuranceCost( Item item ) - { - return 600; // TODO - } - - private void ToggleItemInsurance() - { - if ( !CheckAlive() ) - return; - - BeginTarget( -1, false, TargetFlags.None, ToggleItemInsurance_Callback ); - SendLocalizedMessage( 1060868 ); // Target the item you wish to toggle insurance status on to cancel - } - - private bool CanInsure( Item item ) - { - if ( ( item is Container && !( item is BaseQuiver ) ) || item is BagOfSending || item is KeyRing || item is PotionKeg || item is Sigil ) - return false; - - if ( item.Stackable ) - return false; - - if ( item.LootType == LootType.Cursed ) - return false; - - if ( item.ItemID == 0x204E ) // death shroud - return false; - - if ( item.Layer == Layer.Mount ) - return false; - - if ( item.LootType == LootType.Blessed || item.LootType == LootType.Newbied || item.BlessedFor == this ) - { - //SendLocalizedMessage( 1060870, "", 0x23 ); // That item is blessed and does not need to be insured - return false; - } - - return true; - } - - private void ToggleItemInsurance_Callback( Mobile from, object obj ) - { - if ( !CheckAlive() ) - return; - - ToggleItemInsurance_Callback( from, obj as Item, true ); - } - - private void ToggleItemInsurance_Callback( Mobile from, Item item, bool target ) - { - if ( item == null || !item.IsChildOf( this ) ) - { - if ( target ) - BeginTarget( -1, false, TargetFlags.None, ToggleItemInsurance_Callback ); - - SendLocalizedMessage( 1060871, "", 0x23 ); // You can only insure items that you have equipped or that are in your backpack - } - else if ( item.Insured ) - { - item.Insured = false; - - SendLocalizedMessage( 1060874, "", 0x35 ); // You cancel the insurance on the item - - if ( target ) - { - BeginTarget( -1, false, TargetFlags.None, ToggleItemInsurance_Callback ); - SendLocalizedMessage( 1060868, "", 0x23 ); // Target the item you wish to toggle insurance status on to cancel - } - } - else if ( !CanInsure( item ) ) - { - if ( target ) - BeginTarget( -1, false, TargetFlags.None, ToggleItemInsurance_Callback ); - - SendLocalizedMessage( 1060869, "", 0x23 ); // You cannot insure that - } - else - { - if ( !item.PaidInsurance ) - { - int cost = GetInsuranceCost( item ); - - if ( Banker.Withdraw( from, cost ) ) - { - SendLocalizedMessage( 1060398, cost.ToString() ); // ~1_AMOUNT~ gold has been withdrawn from your bank box. - item.PaidInsurance = true; - } - else - { - SendLocalizedMessage( 1061079, "", 0x23 ); // You lack the funds to purchase the insurance - return; - } - } - - item.Insured = true; - - SendLocalizedMessage( 1060873, "", 0x23 ); // You have insured the item - - if ( target ) - { - BeginTarget( -1, false, TargetFlags.None, ToggleItemInsurance_Callback ); - SendLocalizedMessage( 1060868, "", 0x23 ); // Target the item you wish to toggle insurance status on to cancel - } - } - } - - private void AutoRenewInventoryInsurance() - { - if ( !CheckAlive() ) - return; - - SendLocalizedMessage( 1060881, "", 0x23 ); // You have selected to automatically reinsure all insured items upon death - AutoRenewInsurance = true; - } - - private void CancelRenewInventoryInsurance() - { - if ( !CheckAlive() ) - return; - - if ( Core.SE ) - { - if ( !HasGump( typeof( CancelRenewInventoryInsuranceGump ) ) ) - SendGump( new CancelRenewInventoryInsuranceGump( this, null ) ); - } - else - { - SendLocalizedMessage( 1061075, "", 0x23 ); // You have cancelled automatically reinsuring all insured items upon death - AutoRenewInsurance = false; - } - } - - private class CancelRenewInventoryInsuranceGump : Gump - { - private PlayerMobile m_Player; - private ItemInsuranceMenuGump m_InsuranceGump; - - public CancelRenewInventoryInsuranceGump( PlayerMobile player, ItemInsuranceMenuGump insuranceGump ) : base( 250, 200 ) - { - m_Player = player; - m_InsuranceGump = insuranceGump; - - AddBackground( 0, 0, 240, 142, 0x13BE ); - AddImageTiled( 6, 6, 228, 100, 0xA40 ); - AddImageTiled( 6, 116, 228, 20, 0xA40 ); - AddAlphaRegion( 6, 6, 228, 142 ); - - AddHtmlLocalized( 8, 8, 228, 100, 1071021, 0x7FFF, false, false ); // You are about to disable inventory insurance auto-renewal. - - AddButton( 6, 116, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 118, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - - AddButton( 114, 116, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 148, 118, 450, 20, 1071022, 0x7FFF, false, false ); // DISABLE IT! - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !m_Player.CheckAlive() ) - return; - - if ( info.ButtonID == 1 ) - { - m_Player.SendLocalizedMessage( 1061075, "", 0x23 ); // You have cancelled automatically reinsuring all insured items upon death - m_Player.AutoRenewInsurance = false; - } - else - { - m_Player.SendLocalizedMessage( 1042021 ); // Cancelled. - } - - if ( m_InsuranceGump != null ) - m_Player.SendGump( m_InsuranceGump.NewInstance() ); - } - } - - private void OpenItemInsuranceMenu() - { - if ( !CheckAlive() ) - return; - - List items = new List(); - - foreach ( Item item in Items ) - { - if ( DisplayInItemInsuranceGump( item ) ) - items.Add( item ); - } - - Container pack = Backpack; - - if ( pack != null ) - items.AddRange( pack.FindItemsByType( true, DisplayInItemInsuranceGump ) ); - - // TODO: Investigate item sorting - - CloseGump( typeof( ItemInsuranceMenuGump ) ); - - if ( items.Count == 0 ) - SendLocalizedMessage( 1114915, "", 0x35 ); // None of your current items meet the requirements for insurance. - else - SendGump( new ItemInsuranceMenuGump( this, items.ToArray() ) ); - } - - private bool DisplayInItemInsuranceGump( Item item ) - { - return ( ( item.Visible || AccessLevel >= AccessLevel.GameMaster ) && ( item.Insured || CanInsure( item ) ) ); - } - - private class ItemInsuranceMenuGump : Gump - { - private PlayerMobile m_From; - private Item[] m_Items; - private bool[] m_Insure; - private int m_Page; - - public ItemInsuranceMenuGump( PlayerMobile from, Item[] items ) - : this( from, items, null, 0 ) - { - } - - public ItemInsuranceMenuGump( PlayerMobile from, Item[] items, bool[] insure, int page ) - : base( 25, 50 ) - { - m_From = from; - m_Items = items; - - if ( insure == null ) - { - insure = new bool[items.Length]; - - for ( int i = 0; i < items.Length; ++i ) - insure[i] = items[i].Insured; - } - - m_Insure = insure; - m_Page = page; - - AddPage( 0 ); - - AddBackground( 0, 0, 520, 510, 0x13BE ); - AddImageTiled( 10, 10, 500, 30, 0xA40 ); - AddImageTiled( 10, 50, 500, 355, 0xA40 ); - AddImageTiled( 10, 415, 500, 80, 0xA40 ); - AddAlphaRegion( 10, 10, 500, 485 ); - - AddButton( 15, 470, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 472, 80, 20, 1011012, 0x7FFF, false, false ); // CANCEL - - if ( from.AutoRenewInsurance ) - AddButton( 360, 10, 9723, 9724, 1, GumpButtonType.Reply, 0 ); - else - AddButton( 360, 10, 9720, 9722, 1, GumpButtonType.Reply, 0 ); - - AddHtmlLocalized( 395, 14, 105, 20, 1114122, 0x7FFF, false, false ); // AUTO REINSURE - - AddButton( 395, 470, 0xFA5, 0xFA6, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 430, 472, 50, 20, 1006044, 0x7FFF, false, false ); // OK - - AddHtmlLocalized( 10, 14, 150, 20, 1114121, 0x7FFF, false, false ); //
ITEM INSURANCE MENU
- - AddHtmlLocalized( 45, 54, 70, 20, 1062214, 0x7FFF, false, false ); // Item - AddHtmlLocalized( 250, 54, 70, 20, 1061038, 0x7FFF, false, false ); // Cost - AddHtmlLocalized( 400, 54, 70, 20, 1114311, 0x7FFF, false, false ); // Insured - - int balance = Banker.GetBalance( from ); - int cost = 0; - - for ( int i = 0; i < items.Length; ++i ) - { - if ( insure[i] ) - cost += GetInsuranceCost( items[i] ); - } - - AddHtmlLocalized( 15, 420, 300, 20, 1114310, 0x7FFF, false, false ); // GOLD AVAILABLE: - AddLabel( 215, 420, 0x481, balance.ToString() ); - AddHtmlLocalized( 15, 435, 300, 20, 1114123, 0x7FFF, false, false ); // TOTAL COST OF INSURANCE: - AddLabel( 215, 435, 0x481, cost.ToString() ); - - if ( cost != 0 ) - { - AddHtmlLocalized( 15, 450, 300, 20, 1114125, 0x7FFF, false, false ); // NUMBER OF DEATHS PAYABLE: - AddLabel( 215, 450, 0x481, ( balance / cost ).ToString() ); - } - - for ( int i = page * 4, y = 72; i < ( page + 1 ) * 4 && i < items.Length; ++i, y += 75 ) - { - Item item = items[i]; - Rectangle2D b = ItemBounds.Table[item.ItemID]; - - AddImageTiledButton( 40, y, 0x918, 0x918, 0, GumpButtonType.Page, 0, item.ItemID, item.Hue, 40 - b.Width / 2 - b.X, 30 - b.Height / 2 - b.Y ); - AddItemProperty( item.Serial ); - - if ( insure[i] ) - { - AddButton( 400, y, 9723, 9724, 100 + i, GumpButtonType.Reply, 0 ); - AddLabel( 250, y, 0x481, GetInsuranceCost( item ).ToString() ); - } - else - { - AddButton( 400, y, 9720, 9722, 100 + i, GumpButtonType.Reply, 0 ); - AddLabel( 250, y, 0x66C, GetInsuranceCost( item ).ToString() ); - } - } - - if ( page >= 1 ) - { - AddButton( 15, 380, 0xFAE, 0xFAF, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 380, 450, 20, 1044044, 0x7FFF, false, false ); // PREV PAGE - } - - if ( ( page + 1 ) * 4 < items.Length ) - { - AddButton( 400, 380, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 435, 380, 70, 20, 1044045, 0x7FFF, false, false ); // NEXT PAGE - } - } - - public ItemInsuranceMenuGump NewInstance() - { - return new ItemInsuranceMenuGump( m_From, m_Items, m_Insure, m_Page ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 0 || !m_From.CheckAlive() ) - return; - - switch ( info.ButtonID ) - { - case 1: // Auto Reinsure - { - if ( m_From.AutoRenewInsurance ) - { - if ( !m_From.HasGump( typeof( CancelRenewInventoryInsuranceGump ) ) ) - m_From.SendGump( new CancelRenewInventoryInsuranceGump( m_From, this ) ); - } - else - { - m_From.AutoRenewInventoryInsurance(); - m_From.SendGump( new ItemInsuranceMenuGump( m_From, m_Items, m_Insure, m_Page ) ); - } - - break; - } - case 2: // OK - { - m_From.SendGump( new ItemInsuranceMenuConfirmGump( m_From, m_Items, m_Insure, m_Page ) ); - - break; - } - case 3: // Prev - { - if ( m_Page >= 1 ) - m_From.SendGump( new ItemInsuranceMenuGump( m_From, m_Items, m_Insure, m_Page - 1 ) ); - - break; - } - case 4: // Next - { - if ( ( m_Page + 1 ) * 4 < m_Items.Length ) - m_From.SendGump( new ItemInsuranceMenuGump( m_From, m_Items, m_Insure, m_Page + 1 ) ); - - break; - } - default: - { - int idx = info.ButtonID - 100; - - if ( idx >= 0 && idx < m_Items.Length ) - m_Insure[idx] = !m_Insure[idx]; - - m_From.SendGump( new ItemInsuranceMenuGump( m_From, m_Items, m_Insure, m_Page ) ); - - break; - } - } - } - } - - private class ItemInsuranceMenuConfirmGump : Gump - { - private PlayerMobile m_From; - private Item[] m_Items; - private bool[] m_Insure; - private int m_Page; - - public ItemInsuranceMenuConfirmGump( PlayerMobile from, Item[] items, bool[] insure, int page ) - : base( 250, 200 ) - { - m_From = from; - m_Items = items; - m_Insure = insure; - m_Page = page; - - AddBackground( 0, 0, 240, 142, 0x13BE ); - AddImageTiled( 6, 6, 228, 100, 0xA40 ); - AddImageTiled( 6, 116, 228, 20, 0xA40 ); - AddAlphaRegion( 6, 6, 228, 142 ); - - AddHtmlLocalized( 8, 8, 228, 100, 1114300, 0x7FFF, false, false ); // Do you wish to insure all newly selected items? - - AddButton( 6, 116, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 40, 118, 450, 20, 1060051, 0x7FFF, false, false ); // CANCEL - - AddButton( 114, 116, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 148, 118, 450, 20, 1073996, 0x7FFF, false, false ); // ACCEPT - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( !m_From.CheckAlive() ) - return; - - if ( info.ButtonID == 1 ) - { - for ( int i = 0; i < m_Items.Length; ++i ) - { - Item item = m_Items[i]; - - if ( item.Insured != m_Insure[i] ) - m_From.ToggleItemInsurance_Callback( m_From, item, false ); - } - } - else - { - m_From.SendLocalizedMessage( 1042021 ); // Cancelled. - m_From.SendGump( new ItemInsuranceMenuGump( m_From, m_Items, m_Insure, m_Page ) ); - } - } - } - - #endregion - - #region Toggle Quest Item - - private void ToggleQuestItem() - { - if ( !CheckAlive() ) - return; - - ToggleQuestItemTarget(); - } - - private void ToggleQuestItemTarget() - { - Engines.MLQuests.Gumps.BaseQuestGump.CloseOtherGumps( this ); - CloseGump( typeof( Server.Engines.MLQuests.Gumps.QuestLogDetailedGump ) ); - CloseGump( typeof( Server.Engines.MLQuests.Gumps.QuestLogGump ) ); - CloseGump( typeof( Server.Engines.MLQuests.Gumps.QuestOfferGump ) ); - //CloseGump( typeof( UnknownGump802 ) ); - //CloseGump( typeof( UnknownGump804 ) ); - - BeginTarget( -1, false, TargetFlags.None, ToggleQuestItem_Callback ); - SendLocalizedMessage( 1072352 ); // Target the item you wish to toggle Quest Item status on to cancel - } - - private void ToggleQuestItem_Callback( Mobile from, object obj ) - { - if ( !CheckAlive() ) - return; - - if ( !(obj is Item item) ) - return; - - if ( from.Backpack == null || item.Parent != from.Backpack ) - { - SendLocalizedMessage( 1074769 ); // An item must be in your backpack (and not in a container within) to be toggled as a quest item. - } - else if ( item.QuestItem ) - { - item.QuestItem = false; - SendLocalizedMessage( 1072354 ); // You remove Quest Item status from the item - } - else if ( MLQuestSystem.MarkQuestItem( this, item ) ) - { - SendLocalizedMessage( 1072353 ); // You set the item to Quest Item status - } - else - { - SendLocalizedMessage( 1072355, "", 0x23 ); // That item does not match any of your quest criteria - } - - ToggleQuestItemTarget(); - } - - #endregion - - private void ToggleTrades() - { - RefuseTrades = !RefuseTrades; - } - - private void GetVendor() - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( CheckAlive() && house != null && house.IsOwner( this ) && house.InternalizedVendors.Count > 0 ) - { - CloseGump( typeof( ReclaimVendorGump ) ); - SendGump( new ReclaimVendorGump( house ) ); - } - } - - private void LeaveHouse() - { - BaseHouse house = BaseHouse.FindHouseAt( this ); - - if ( house != null ) - Location = house.BanLocation; - } - - private delegate void ContextCallback(); - - private class CallbackEntry : ContextMenuEntry - { - private ContextCallback m_Callback; - - public CallbackEntry( int number, ContextCallback callback ) : this( number, -1, callback ) - { - } - - public CallbackEntry( int number, int range, ContextCallback callback ) : base( number, range ) - { - m_Callback = callback; - } - - public override void OnClick() - { - m_Callback?.Invoke(); - } - } - - public override void DisruptiveAction() - { - if ( Meditating ) - { - RemoveBuff( BuffIcon.ActiveMeditation ); - } - - base.DisruptiveAction(); - } - - public override void OnDoubleClick( Mobile from ) - { - if ( this == from && !Warmode ) - { - IMount mount = Mount; - - if ( mount != null && !DesignContext.Check( this ) ) - return; - } - - base.OnDoubleClick( from ); - } - - public override void DisplayPaperdollTo( Mobile to ) - { - if ( DesignContext.Check( this ) ) - base.DisplayPaperdollTo( to ); - } - - private static bool m_NoRecursion; - - public override bool CheckEquip( Item item ) - { - if ( !base.CheckEquip( item ) ) - return false; - - #region Dueling - if ( DuelContext != null && !DuelContext.AllowItemEquip( this, item ) ) - return false; - #endregion - - #region Factions - FactionItem factionItem = FactionItem.Find( item ); - - if ( factionItem != null ) - { - Faction faction = Faction.Find( this ); - - if ( faction == null ) - { - SendLocalizedMessage( 1010371 ); // You cannot equip a faction item! - return false; - } - - if ( faction != factionItem.Faction ) - { - SendLocalizedMessage( 1010372 ); // You cannot equip an opposing faction's item! - return false; - } - - int maxWearables = FactionItem.GetMaxWearables( this ); - - for ( int i = 0; i < Items.Count; ++i ) - { - Item equipped = Items[i]; - - if ( item != equipped && FactionItem.Find( equipped ) != null ) - { - if ( --maxWearables == 0 ) - { - SendLocalizedMessage( 1010373 ); // You do not have enough rank to equip more faction items! - return false; - } - } - } - } - #endregion - - if ( AccessLevel < AccessLevel.GameMaster && item.Layer != Layer.Mount && HasTrade ) - { - BounceInfo bounce = item.GetBounce(); - - if ( bounce != null ) - { - if ( bounce.m_Parent is Item parent ) - { - if ( parent == Backpack || parent.IsChildOf( Backpack ) ) - return true; - } - else if ( bounce.m_Parent == this ) - { - return true; - } - } - - SendLocalizedMessage( 1004042 ); // You can only equip what you are already carrying while you have a trade pending. - return false; - } - - return true; - } - - public override bool CheckTrade( Mobile to, Item item, SecureTradeContainer cont, bool message, bool checkItems, int plusItems, int plusWeight ) - { - int msgNum = 0; - - if ( cont == null ) - { - if ( to.Holding != null ) - msgNum = 1062727; // You cannot trade with someone who is dragging something. - else if ( HasTrade ) - msgNum = 1062781; // You are already trading with someone else! - else if ( to.HasTrade ) - msgNum = 1062779; // That person is already involved in a trade - else if ( to is PlayerMobile mobile && mobile.RefuseTrades ) - msgNum = 1154111; // ~1_NAME~ is refusing all trades. - } - - if ( msgNum == 0 && item != null ) - { - if ( cont != null ) - { - plusItems += cont.TotalItems; - plusWeight += cont.TotalWeight; - } - - if ( Backpack == null || !Backpack.CheckHold( this, item, false, checkItems, plusItems, plusWeight ) ) - msgNum = 1004040; // You would not be able to hold this if the trade failed. - else if ( to.Backpack == null || !to.Backpack.CheckHold( to, item, false, checkItems, plusItems, plusWeight ) ) - msgNum = 1004039; // The recipient of this trade would not be able to carry this. - else - msgNum = CheckContentForTrade( item ); - } - - if ( msgNum != 0 ) - { - if ( message ) - { - if ( msgNum == 1154111 ) - SendLocalizedMessage( msgNum, to.Name ); - else - SendLocalizedMessage( msgNum ); - } - - return false; - } - - return true; - } - - private static int CheckContentForTrade( Item item ) - { - if ( item is TrappableContainer container && container.TrapType != TrapType.None ) - return 1004044; // You may not trade trapped items. - - if ( SkillHandlers.StolenItem.IsStolen( item ) ) - return 1004043; // You may not trade recently stolen items. - - if ( item is Container ) - { - foreach ( Item subItem in item.Items ) - { - int msg = CheckContentForTrade( subItem ); - - if ( msg != 0 ) - return msg; - } - } - - return 0; - } - - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - if ( !base.CheckNonlocalDrop( from, item, target ) ) - return false; - - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - - Container pack = Backpack; - if ( from == this && HasTrade && ( target == pack || target.IsChildOf( pack ) ) ) - { - BounceInfo bounce = item.GetBounce(); - - if ( bounce?.m_Parent is Item parent && (parent == pack || parent.IsChildOf( pack )) ) - return true; - - SendLocalizedMessage( 1004041 ); // You can't do that while you have a trade pending. - return false; - } - - return true; - } - - protected override void OnLocationChange( Point3D oldLocation ) - { - CheckLightLevels( false ); - - #region Dueling - DuelContext?.OnLocationChanged( this ); - #endregion - - DesignContext context = DesignContext; - - if ( context == null || m_NoRecursion ) - return; - - m_NoRecursion = true; - - HouseFoundation foundation = context.Foundation; - - int newX = X, newY = Y; - int newZ = foundation.Z + HouseFoundation.GetLevelZ( context.Level, context.Foundation ); + if (min > MaxPlayerResistance) + min = MaxPlayerResistance; - int startX = foundation.X + foundation.Components.Min.X + 1; - int startY = foundation.Y + foundation.Components.Min.Y + 1; - int endX = startX + foundation.Components.Width - 1; - int endY = startY + foundation.Components.Height - 2; + int baseMin = base.GetMinResistance(type); - if ( newX >= startX && newY >= startY && newX < endX && newY < endY && Map == foundation.Map ) - { - if ( Z != newZ ) - Location = new Point3D( X, Y, newZ ); + if (min < baseMin) + min = baseMin; - m_NoRecursion = false; - return; - } + return min; + } - Location = new Point3D( foundation.X, foundation.Y, newZ ); - Map = foundation.Map; + public override void OnManaChange(int oldValue) + { + base.OnManaChange(oldValue); + if (ExecutesLightningStrike > 0) + if (Mana < ExecutesLightningStrike) + SpecialMove.ClearCurrentMove(this); + } - m_NoRecursion = false; - } + private static void OnLogin(LoginEventArgs e) + { + Mobile from = e.Mobile; - public override bool OnMoveOver( Mobile m ) - { - if ( m is BaseCreature creature && !creature.Controlled ) - return ( !Alive || !creature.Alive || IsDeadBondedPet || creature.IsDeadBondedPet ) || ( Hidden && AccessLevel > AccessLevel.Player ); + CheckAtrophies(from); - #region Dueling - if ( Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) && m is PlayerMobile pm ) - { - if ( pm.DuelContext == null || pm.DuelPlayer == null || !pm.DuelContext.Started || pm.DuelContext.Finished || pm.DuelPlayer.Eliminated ) - return true; - } - #endregion + if (AccountHandler.LockdownLevel > AccessLevel.Player) + { + string notice; - return base.OnMoveOver( m ); - } + if (!(from.Account is Account acct) || !acct.HasAccess(from.NetState)) + { + if (from.AccessLevel == AccessLevel.Player) + notice = "The server is currently under lockdown. No players are allowed to log in at this time."; + else + notice = + "The server is currently under lockdown. You do not have sufficient access level to connect."; + + Timer.DelayCall(TimeSpan.FromSeconds(1.0), new TimerStateCallback(Disconnect), from); + } + else if (from.AccessLevel >= AccessLevel.Administrator) + { + notice = + "The server is currently under lockdown. As you are an administrator, you may change this from the [Admin gump."; + } + else + { + notice = "The server is currently under lockdown. You have sufficient access level to connect."; + } + + from.SendGump(new NoticeGump(1060637, 30720, notice, 0xFFC000, 300, 140, null, null)); + return; + } + + if (from is PlayerMobile mobile) + mobile.ClaimAutoStabledPets(); + } + + public void ValidateEquipment() + { + if (m_NoDeltaRecursion || Map == null || Map == Map.Internal) + return; + + if (Items == null) + return; + + m_NoDeltaRecursion = true; + Timer.DelayCall(TimeSpan.Zero, ValidateEquipment_Sandbox); + } + + private void ValidateEquipment_Sandbox() + { + try + { + if (Map == null || Map == Map.Internal) + return; + + List items = Items; + + if (items == null) + return; + + bool moved = false; + + int str = Str; + int dex = Dex; + int intel = Int; + + #region Factions + + int factionItemCount = 0; + + #endregion + + Mobile from = this; + + #region Ethics + + Ethic ethic = Ethic.Find(from); + + #endregion + + for (int i = items.Count - 1; i >= 0; --i) + { + if (i >= items.Count) + continue; + + Item item = items[i]; + + #region Ethics + + if ((item.SavedFlags & 0x100) != 0) + { + if (item.Hue != Ethic.Hero.Definition.PrimaryHue) + { + item.SavedFlags &= ~0x100; + } + else if (ethic != Ethic.Hero) + { + from.AddToBackpack(item); + moved = true; + continue; + } + } + else if ((item.SavedFlags & 0x200) != 0) + { + if (item.Hue != Ethic.Evil.Definition.PrimaryHue) + { + item.SavedFlags &= ~0x200; + } + else if (ethic != Ethic.Evil) + { + from.AddToBackpack(item); + moved = true; + continue; + } + } + + #endregion + + if (item is BaseWeapon weapon) + { + bool drop = false; + + if (dex < weapon.DexRequirement) + drop = true; + else if (str < AOS.Scale(weapon.StrRequirement, 100 - weapon.GetLowerStatReq())) + drop = true; + else if (intel < weapon.IntRequirement) + drop = true; + else if (weapon.RequiredRace != null && weapon.RequiredRace != Race) + drop = true; + + if (drop) + { + string name = weapon.Name; + + if (name == null) + name = $"#{weapon.LabelNumber}"; + + from.SendLocalizedMessage(1062001, name); // You can no longer wield your ~1_WEAPON~ + from.AddToBackpack(weapon); + moved = true; + } + } + else if (item is BaseArmor armor) + { + bool drop = false; + + if (!armor.AllowMaleWearer && !from.Female && from.AccessLevel < AccessLevel.GameMaster) + { + drop = true; + } + else if (!armor.AllowFemaleWearer && from.Female && from.AccessLevel < AccessLevel.GameMaster) + { + drop = true; + } + else if (armor.RequiredRace != null && armor.RequiredRace != Race) + { + drop = true; + } + else + { + int strBonus = armor.ComputeStatBonus(StatType.Str), strReq = armor.ComputeStatReq(StatType.Str); + int dexBonus = armor.ComputeStatBonus(StatType.Dex), dexReq = armor.ComputeStatReq(StatType.Dex); + int intBonus = armor.ComputeStatBonus(StatType.Int), intReq = armor.ComputeStatReq(StatType.Int); + + if (dex < dexReq || dex + dexBonus < 1) + drop = true; + else if (str < strReq || str + strBonus < 1) + drop = true; + else if (intel < intReq || intel + intBonus < 1) + drop = true; + } + + if (drop) + { + string name = armor.Name; + + if (name == null) + name = $"#{armor.LabelNumber}"; + + if (armor is BaseShield) + from.SendLocalizedMessage(1062003, name); // You can no longer equip your ~1_SHIELD~ + else + from.SendLocalizedMessage(1062002, name); // You can no longer wear your ~1_ARMOR~ + + from.AddToBackpack(armor); + moved = true; + } + } + else if (item is BaseClothing clothing) + { + bool drop = false; + + if (!clothing.AllowMaleWearer && !from.Female && from.AccessLevel < AccessLevel.GameMaster) + { + drop = true; + } + else if (!clothing.AllowFemaleWearer && from.Female && from.AccessLevel < AccessLevel.GameMaster) + { + drop = true; + } + else if (clothing.RequiredRace != null && clothing.RequiredRace != Race) + { + drop = true; + } + else + { + int strBonus = clothing.ComputeStatBonus(StatType.Str); + int strReq = clothing.ComputeStatReq(StatType.Str); + + if (str < strReq || str + strBonus < 1) + drop = true; + } + + if (drop) + { + string name = clothing.Name; + + if (name == null) + name = $"#{clothing.LabelNumber}"; + + from.SendLocalizedMessage(1062002, name); // You can no longer wear your ~1_ARMOR~ + + from.AddToBackpack(clothing); + moved = true; + } + } + + FactionItem factionItem = FactionItem.Find(item); + + if (factionItem != null) + { + bool drop = false; + + Faction ourFaction = Faction.Find(this); + + if (ourFaction == null || ourFaction != factionItem.Faction) + drop = true; + else if (++factionItemCount > FactionItem.GetMaxWearables(this)) + drop = true; + + if (drop) + { + from.AddToBackpack(item); + moved = true; + } + } + } + + if (moved) + from.SendLocalizedMessage(500647); // Some equipment has been moved to your backpack. + } + catch (Exception e) + { + Console.WriteLine(e); + } + finally + { + m_NoDeltaRecursion = false; + } + } + + public override void Delta(MobileDelta flag) + { + base.Delta(flag); + + if ((flag & MobileDelta.Stat) != 0) + ValidateEquipment(); + + if ((flag & (MobileDelta.Name | MobileDelta.Hue)) != 0) + InvalidateMyRunUO(); + } + + private static void Disconnect(object state) + { + NetState ns = ((Mobile)state).NetState; + ns?.Dispose(); + } + + private static void OnLogout(LogoutEventArgs e) + { + if (e.Mobile is PlayerMobile mobile) + mobile.AutoStablePets(); + } + + private static void EventSink_Connected(ConnectedEventArgs e) + { + if (e.Mobile is PlayerMobile pm) + { + pm.SessionStart = DateTime.UtcNow; + + pm.Quest?.StartTimer(); + + pm.BedrollLogout = false; + pm.LastOnline = DateTime.UtcNow; + } + + DisguiseTimers.StartTimer(e.Mobile); + + Timer.DelayCall(TimeSpan.Zero, new TimerStateCallback(ClearSpecialMovesCallback), e.Mobile); + } + + private static void ClearSpecialMovesCallback(object state) + { + Mobile from = (Mobile)state; + + SpecialMove.ClearAllMoves(from); + } + + private static void EventSink_Disconnected(DisconnectedEventArgs e) + { + Mobile from = e.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client disconnected + * - Remove design context + * - Eject all from house + * - Restore relocated entities + */ + + // Remove design context + DesignContext.Remove(from); + + // Eject all from house + from.RevealingAction(); + + foreach (Item item in context.Foundation.GetItems()) + item.Location = context.Foundation.BanLocation; + + foreach (Mobile mobile in context.Foundation.GetMobiles()) + mobile.Location = context.Foundation.BanLocation; + + // Restore relocated entities + context.Foundation.RestoreRelocatedEntities(); + } + + if (e.Mobile is PlayerMobile pm) + { + pm.m_GameTime += DateTime.UtcNow - pm.SessionStart; + + pm.Quest?.StopTimer(); + + pm.SpeechLog = null; + pm.LastOnline = DateTime.UtcNow; + } + + DisguiseTimers.StopTimer(from); + } + + public override void RevealingAction() + { + if (DesignContext != null) + return; + + InvisibilitySpell.RemoveTimer(this); + + base.RevealingAction(); + + IsStealthing = false; // IsStealthing should be moved to Server.Mobiles + } + + public override void OnHiddenChanged() + { + base.OnHiddenChanged(); + + RemoveBuff(BuffIcon + .Invisibility); //Always remove, default to the hiding icon EXCEPT in the invis spell where it's explicitly set + + if (!Hidden) + RemoveBuff(BuffIcon.HidingAndOrStealth); + else // if ( !InvisibilitySpell.HasTimer( this ) ) + BuffInfo.AddBuff(this, + new BuffInfo(BuffIcon.HidingAndOrStealth, 1075655)); //Hidden/Stealthing & You Are Hidden + } + + public override void OnSubItemAdded(Item item) + { + if (AccessLevel < AccessLevel.GameMaster && item.IsChildOf(Backpack)) + { + int maxWeight = WeightOverloading.GetMaxWeight(this); + int curWeight = BodyWeight + TotalWeight; + + if (curWeight > maxWeight) + SendLocalizedMessage(1019035, true, $" : {curWeight} / {maxWeight}"); + } + + base.OnSubItemAdded(item); + } + + public override bool CanBeHarmful(Mobile target, bool message, bool ignoreOurBlessedness) + { + if (DesignContext != null || target is PlayerMobile mobile && mobile.DesignContext != null) + return false; + + if (target is BaseCreature creature && creature.IsInvulnerable || target is PlayerVendor || target is TownCrier) + { + if (message) + { + if (target.Title == null) + SendMessage("{0} cannot be harmed.", target.Name); + else + SendMessage("{0} {1} cannot be harmed.", target.Name, target.Title); + } - public override bool CheckShove( Mobile shoved ) - { - if ( m_IgnoreMobiles || TransformationSpellHelper.UnderTransformation( shoved, typeof( WraithFormSpell ) ) ) - return true; + return false; + } - return base.CheckShove( shoved ); - } + return base.CanBeHarmful(target, message, ignoreOurBlessedness); + } - protected override void OnMapChange( Map oldMap ) - { - if ( (Map != Faction.Facet && oldMap == Faction.Facet) || (Map == Faction.Facet && oldMap != Faction.Facet) ) - InvalidateProperties(); + public override bool CanBeBeneficial(Mobile target, bool message, bool allowDead) + { + if (DesignContext != null || target is PlayerMobile mobile && mobile.DesignContext != null) + return false; - #region Dueling - DuelContext?.OnMapChanged( this ); - #endregion + return base.CanBeBeneficial(target, message, allowDead); + } - DesignContext context = DesignContext; + public override bool CheckContextMenuDisplay(IEntity target) + { + return DesignContext == null; + } - if ( context == null || m_NoRecursion ) - return; + public override void OnItemAdded(Item item) + { + base.OnItemAdded(item); - m_NoRecursion = true; + if (item is BaseArmor || item is BaseWeapon) + { + Hits = Hits; + Stam = Stam; + Mana = Mana; + } - HouseFoundation foundation = context.Foundation; + if (NetState != null) + CheckLightLevels(false); - if ( Map != foundation.Map ) - Map = foundation.Map; + InvalidateMyRunUO(); + } - m_NoRecursion = false; - } + public override void OnItemRemoved(Item item) + { + base.OnItemRemoved(item); - public override void OnBeneficialAction( Mobile target, bool isCriminal ) - { - SentHonorContext?.OnSourceBeneficialAction( target ); + if (item is BaseArmor || item is BaseWeapon) + { + Hits = Hits; + Stam = Stam; + Mana = Mana; + } - base.OnBeneficialAction( target, isCriminal ); - } + if (NetState != null) + CheckLightLevels(false); - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - int disruptThreshold; + InvalidateMyRunUO(); + } - if ( !Core.AOS ) - disruptThreshold = 0; - else if ( from != null && from.Player ) - disruptThreshold = 18; - else - disruptThreshold = 25; + private void AddArmorRating(ref double rating, Item armor) + { + if (armor is BaseArmor ar && (!Core.AOS || ar.ArmorAttributes.MageArmor == 0)) + rating += ar.ArmorRatingScaled; + } - if ( amount > disruptThreshold ) - { - BandageContext c = BandageContext.GetContext( this ); + public override bool Move(Direction d) + { + NetState ns = NetState; + + if (ns != null) + if (HasGump(typeof(ResurrectGump))) + { + if (Alive) + { + CloseGump(typeof(ResurrectGump)); + } + else + { + SendLocalizedMessage(500111); // You are frozen and cannot move. + return false; + } + } - c?.Slip(); - } + int speed = ComputeMovementSpeed(d); - if ( Confidence.IsRegenerating( this ) ) - Confidence.StopRegenerating( this ); + bool res; - WeightOverloading.FatigueOnDamage( this, amount ); + if (!Alive) + MovementImpl.IgnoreMovableImpassables = true; - ReceivedHonorContext?.OnTargetDamaged( from, amount ); - SentHonorContext?.OnSourceDamaged( from, amount ); + res = base.Move(d); - if ( willKill && from is PlayerMobile mobile ) - Timer.DelayCall( TimeSpan.FromSeconds( 10 ), mobile.RecoverAmmo ); + MovementImpl.IgnoreMovableImpassables = false; - base.OnDamage( amount, from, willKill ); - } + if (!res) + return false; - public override void Resurrect() - { - bool wasAlive = Alive; + m_NextMovementTime += speed; - base.Resurrect(); + return true; + } - if ( Alive && !wasAlive ) - { - Item deathRobe = new DeathRobe(); + public override bool CheckMovement(Direction d, out int newZ) + { + DesignContext context = DesignContext; - if ( !EquipItem( deathRobe ) ) - deathRobe.Delete(); - } - } + if (context == null) + return base.CheckMovement(d, out newZ); - public override double RacialSkillBonus - { - get - { - if ( Core.ML && Race == Race.Human ) - return 20.0; + HouseFoundation foundation = context.Foundation; - return 0; - } - } + newZ = foundation.Z + HouseFoundation.GetLevelZ(context.Level, context.Foundation); - public override void OnWarmodeChanged() - { - if ( !Warmode ) - Timer.DelayCall( TimeSpan.FromSeconds( 10 ), RecoverAmmo ); - } - - private Mobile m_InsuranceAward; - private int m_InsuranceCost; - private int m_InsuranceBonus; - - public List EquipSnapshot { get; private set; } - - private bool FindItems_Callback(Item item) - { - if (!item.Deleted && (item.LootType == LootType.Blessed || item.Insured)) - { - if (Backpack != item.Parent) - { - return true; - } - } - return false; - } - - public override bool OnBeforeDeath() - { - NetState state = NetState; - - state?.CancelAllTrades(); - - DropHolding(); - - if (Core.AOS && Backpack != null && !Backpack.Deleted) - { - List ilist = Backpack.FindItemsByType(FindItems_Callback); - - for (int i = 0; i < ilist.Count; i++) - { - Backpack.AddItem(ilist[i]); - } - } - - EquipSnapshot = new List( Items ); - - m_NonAutoreinsuredItems = 0; - m_InsuranceCost = 0; - m_InsuranceAward = FindMostRecentDamager( false ); - - if ( m_InsuranceAward is BaseCreature creature ) - { - Mobile master = creature.GetMaster(); - - if ( master != null ) - m_InsuranceAward = master; - } - - if ( m_InsuranceAward != null && (!m_InsuranceAward.Player || m_InsuranceAward == this) ) - m_InsuranceAward = null; - - if ( m_InsuranceAward is PlayerMobile mobile ) - mobile.m_InsuranceBonus = 0; - - ReceivedHonorContext?.OnTargetKilled(); - SentHonorContext?.OnSourceKilled(); - - RecoverAmmo(); - - return base.OnBeforeDeath(); - } - - private bool CheckInsuranceOnDeath( Item item ) - { - if ( InsuranceEnabled && item.Insured ) - { - #region Dueling - if ( m_DuelPlayer != null && DuelContext != null && DuelContext.Registered && DuelContext.Started && !m_DuelPlayer.Eliminated ) - return true; - #endregion - - if ( AutoRenewInsurance ) - { - int cost = GetInsuranceCost( item ); - - if ( m_InsuranceAward != null ) - cost /= 2; - - if ( Banker.Withdraw( this, cost ) ) - { - m_InsuranceCost += cost; - item.PaidInsurance = true; - SendLocalizedMessage(1060398, cost.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. - } - else - { - SendLocalizedMessage( 1061079, "", 0x23 ); // You lack the funds to purchase the insurance - item.PaidInsurance = false; - item.Insured = false; - m_NonAutoreinsuredItems++; - } - } - else - { - item.PaidInsurance = false; - item.Insured = false; - } - - if ( m_InsuranceAward != null ) - { - if ( Banker.Deposit( m_InsuranceAward, 300 ) ) - { - if ( m_InsuranceAward is PlayerMobile mobile ) - mobile.m_InsuranceBonus += 300; - } - } - - return true; - } - - return false; - } + int newX = X, newY = Y; + Movement.Movement.Offset(d, ref newX, ref newY); - public override DeathMoveResult GetParentMoveResultFor( Item item ) - { - // It seems all items are unmarked on death, even blessed/insured ones - if ( item.QuestItem ) - item.QuestItem = false; + int startX = foundation.X + foundation.Components.Min.X + 1; + int startY = foundation.Y + foundation.Components.Min.Y + 1; + int endX = startX + foundation.Components.Width - 1; + int endY = startY + foundation.Components.Height - 2; - if ( CheckInsuranceOnDeath( item ) ) - return DeathMoveResult.MoveToBackpack; + return newX >= startX && newY >= startY && newX < endX && newY < endY && Map == foundation.Map; + } - DeathMoveResult res = base.GetParentMoveResultFor( item ); - - if ( res == DeathMoveResult.MoveToCorpse && item.Movable && Young ) - res = DeathMoveResult.MoveToBackpack; - - return res; - } - - public override DeathMoveResult GetInventoryMoveResultFor( Item item ) - { - // It seems all items are unmarked on death, even blessed/insured ones - if ( item.QuestItem ) - item.QuestItem = false; - - if ( CheckInsuranceOnDeath( item ) ) - return DeathMoveResult.MoveToBackpack; - - DeathMoveResult res = base.GetInventoryMoveResultFor( item ); - - if ( res == DeathMoveResult.MoveToCorpse && item.Movable && Young ) - res = DeathMoveResult.MoveToBackpack; - - return res; - } - - public override void OnDeath( Container c ) - { - if (m_NonAutoreinsuredItems > 0) - { - SendLocalizedMessage(1061115); - } - - base.OnDeath(c); - - EquipSnapshot = null; - - HueMod = -1; - NameMod = null; - SavagePaintExpiration = TimeSpan.Zero; - - SetHairMods( -1, -1 ); - - PolymorphSpell.StopTimer( this ); - IncognitoSpell.StopTimer( this ); - DisguiseTimers.RemoveTimer( this ); - - EndAction( typeof( PolymorphSpell ) ); - EndAction( typeof( IncognitoSpell ) ); - - MeerMage.StopEffect( this, false ); - - #region Stygian Abyss - if (Flying) - { - Flying = false; - BuffInfo.RemoveBuff(this, BuffIcon.Fly); - } - #endregion - - SkillHandlers.StolenItem.ReturnOnDeath( this, c ); - - if ( PermaFlags.Count > 0 ) - { - PermaFlags.Clear(); - - if ( c is Corpse corpse ) - corpse.Criminal = true; - - if ( SkillHandlers.Stealing.ClassicMode ) - Criminal = true; - } - - if ( Kills >= 5 && DateTime.UtcNow >= m_NextJustAward ) - { - Mobile m = FindMostRecentDamager( false ); + public override bool AllowItemUse(Item item) + { + #region Dueling - if ( m is BaseCreature bc ) - m = bc.GetMaster(); - - if ( m != this && m is PlayerMobile ) - { - bool gainedPath = false; + if (DuelContext != null && !DuelContext.AllowItemUse(this, item)) + return false; - int pointsToGain = 0; + #endregion - pointsToGain += (int) Math.Sqrt( GameTime.TotalSeconds * 4 ); - pointsToGain *= 5; - pointsToGain += (int) Math.Pow( Skills.Total / 250, 2 ); - - if ( VirtueHelper.Award( m, VirtueName.Justice, pointsToGain, ref gainedPath ) ) - { - if ( gainedPath ) - m.SendLocalizedMessage( 1049367 ); // You have gained a path in Justice! - else - m.SendLocalizedMessage( 1049363 ); // You have gained in Justice. - - m.FixedParticles( 0x375A, 9, 20, 5027, EffectLayer.Waist ); - m.PlaySound( 0x1F7 ); - - m_NextJustAward = DateTime.UtcNow + TimeSpan.FromMinutes( pointsToGain / 3 ); - } - } - } - - if ( m_InsuranceAward is PlayerMobile pm ) - { - if ( pm.m_InsuranceBonus > 0 ) - pm.SendLocalizedMessage( 1060397, pm.m_InsuranceBonus.ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. - } - - Mobile killer = FindMostRecentDamager( true ); - - if ( killer is BaseCreature bcKiller ) - { - Mobile master = bcKiller.GetMaster(); - if ( master != null ) - killer = master; - } - - if ( Young && DuelContext == null ) - { - if ( YoungDeathTeleport() ) - Timer.DelayCall( TimeSpan.FromSeconds( 2.5 ), SendYoungDeathNotice ); - } - - if ( DuelContext == null || !DuelContext.Registered || !DuelContext.Started || m_DuelPlayer == null || m_DuelPlayer.Eliminated ) - Faction.HandleDeath( this, killer ); - - Server.Guilds.Guild.HandleDeath( this, killer ); - - MLQuestSystem.HandleDeath( this ); - - #region Dueling - DuelContext?.OnDeath( this, c ); - #endregion - - if ( m_BuffTable != null ) - { - List list = new List(); - - foreach( BuffInfo buff in m_BuffTable.Values ) - { - if ( !buff.RetainThroughDeath ) - { - list.Add( buff ); - } - } - - for( int i = 0; i < list.Count; i++ ) - { - RemoveBuff( list[i] ); - } - } - } - - #region Stuck Menu - private DateTime[] m_StuckMenuUses; - - public bool CanUseStuckMenu() - { - if (m_StuckMenuUses == null) - { - return true; - } - - for (int i = 0; i < m_StuckMenuUses.Length; ++i) - { - if ((DateTime.UtcNow - m_StuckMenuUses[i]) > TimeSpan.FromDays(1.0)) - { - return true; - } - } - - return false; - } - - public void UsedStuckMenu() - { - if (m_StuckMenuUses == null) - { - m_StuckMenuUses = new DateTime[2]; - } - - for (int i = 0; i < m_StuckMenuUses.Length; ++i) - { - if ((DateTime.UtcNow - m_StuckMenuUses[i]) > TimeSpan.FromDays(1.0)) - { - m_StuckMenuUses[i] = DateTime.UtcNow; - return; - } - } - } - #endregion - - private Hashtable m_AntiMacroTable; - private TimeSpan m_GameTime; - private TimeSpan m_ShortTermElapse; - private TimeSpan m_LongTermElapse; - private DateTime m_NextSmithBulkOrder; - private DateTime m_NextTailorBulkOrder; - private DateTime m_SavagePaintExpiration; - - public SkillName Learning { get; set; } = (SkillName)(-1); - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan SavagePaintExpiration - { - get - { - TimeSpan ts = m_SavagePaintExpiration - DateTime.UtcNow; - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - return ts; - } - set => m_SavagePaintExpiration = DateTime.UtcNow + value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan NextSmithBulkOrder - { - get - { - TimeSpan ts = m_NextSmithBulkOrder - DateTime.UtcNow; - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - return ts; - } - set - { - try{ m_NextSmithBulkOrder = DateTime.UtcNow + value; } - catch{} - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan NextTailorBulkOrder - { - get - { - TimeSpan ts = m_NextTailorBulkOrder - DateTime.UtcNow; - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - return ts; - } - set - { - try{ m_NextTailorBulkOrder = DateTime.UtcNow + value; } - catch{} - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastEscortTime { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastPetBallTime { get; set; } - - public PlayerMobile() - { - AutoStabled = new List(); - - VisibilityList = new List(); - PermaFlags = new List(); - m_AntiMacroTable = new Hashtable(); - RecentlyReported = new List(); - - BOBFilter = new Engines.BulkOrders.BOBFilter(); - - m_GameTime = TimeSpan.Zero; - m_ShortTermElapse = TimeSpan.FromHours( 8.0 ); - m_LongTermElapse = TimeSpan.FromHours( 40.0 ); - - JusticeProtectors = new List(); - m_GuildRank = Guilds.RankDefinition.Lowest; - - m_ChampionTitles = new ChampionTitleInfo(); - - InvalidateMyRunUO(); - } - - public override bool MutateSpeech( List hears, ref string text, ref object context ) - { - if ( Alive ) - return false; - - if ( Core.ML && Skills[SkillName.SpiritSpeak].Value >= 100.0 ) - return false; - - if ( Core.AOS ) - { - for ( int i = 0; i < hears.Count; ++i ) - { - Mobile m = hears[i]; - - if ( m != this && m.Skills[SkillName.SpiritSpeak].Value >= 100.0 ) - return false; - } - } - - return base.MutateSpeech( hears, ref text, ref context ); - } - - public override void DoSpeech( string text, int[] keywords, MessageType type, int hue ) - { - if ( Guilds.Guild.NewGuildSystem && (type == MessageType.Guild || type == MessageType.Alliance) ) - { - if ( !(Guild is Guild g) ) - { - SendLocalizedMessage( 1063142 ); // You are not in a guild! - } - else if ( type == MessageType.Alliance ) - { - if ( g.Alliance != null && g.Alliance.IsMember( g ) ) - { - //g.Alliance.AllianceTextMessage( hue, "[Alliance][{0}]: {1}", this.Name, text ); - g.Alliance.AllianceChat( this, text ); - SendToStaffMessage( this, "[Alliance]: {0}", text ); - - AllianceMessageHue = hue; - } - else - { - SendLocalizedMessage( 1071020 ); // You are not in an alliance! - } - } - else //Type == MessageType.Guild - { - GuildMessageHue = hue; - - g.GuildChat( this, text ); - SendToStaffMessage( this, "[Guild]: {0}", text ); - } - } - else - { - base.DoSpeech( text, keywords, type, hue ); - } - } - - private static void SendToStaffMessage( Mobile from, string text ) - { - Packet p = null; - - foreach( NetState ns in from.GetClientsInRange( 8 ) ) - { - Mobile mob = ns.Mobile; - - if ( mob != null && mob.AccessLevel >= AccessLevel.GameMaster && mob.AccessLevel > from.AccessLevel ) - { - if ( p == null ) - p = Packet.Acquire( new UnicodeMessage( from.Serial, from.Body, MessageType.Regular, from.SpeechHue, 3, from.Language, from.Name, text ) ); - - ns.Send( p ); - } - } - - Packet.Release( p ); - } - - private static void SendToStaffMessage( Mobile from, string format, params object[] args ) - { - SendToStaffMessage( from, string.Format( format, args ) ); - } - - public override void Damage( int amount, Mobile from ) - { - if ( EvilOmenSpell.TryEndEffect( this ) ) - amount = (int)(amount * 1.25); - - Mobile oath = BloodOathSpell.GetBloodOath( from ); - - /* Per EA's UO Herald Pub48 (ML): - * ((resist spellsx10)/20 + 10=percentage of damage resisted) - */ - - if ( oath == this ) - { - amount = (int)(amount * 1.1); - - if ( amount > 35 && from is PlayerMobile ) /* capped @ 35, seems no expansion */ - { - amount = 35; - } - - if ( Core.ML ) - { - from.Damage( (int)(amount * ( 1 - ((( from.Skills.MagicResist.Value * .5 ) + 10) / 100 ))), this ); - } - else - { - from.Damage( amount, this ); - } - } - - if ( from != null && Talisman is BaseTalisman talisman ) - { - if ( talisman.Protection != null && talisman.Protection.Type != null ) - { - Type type = talisman.Protection.Type; - - if ( type.IsAssignableFrom( from.GetType() ) ) - amount = (int)( amount * ( 1 - (double)talisman.Protection.Amount / 100 ) ); - } - } - - base.Damage( amount, from ); - } - - #region Poison - - public override ApplyPoisonResult ApplyPoison( Mobile from, Poison poison ) - { - if ( !Alive ) - return ApplyPoisonResult.Immune; - - if ( EvilOmenSpell.TryEndEffect( this ) ) - poison = PoisonImpl.IncreaseLevel( poison ); - - ApplyPoisonResult result = base.ApplyPoison( from, poison ); - - if ( from != null && result == ApplyPoisonResult.Poisoned && PoisonTimer is PoisonImpl.PoisonTimer timer ) - timer.From = from; - - return result; - } - - public override bool CheckPoisonImmunity( Mobile from, Poison poison ) - { - if ( Young && (DuelContext == null || !DuelContext.Started || DuelContext.Finished) ) - return true; - - return base.CheckPoisonImmunity( from, poison ); - } - - public override void OnPoisonImmunity( Mobile from, Poison poison ) - { - if ( Young && (DuelContext == null || !DuelContext.Started || DuelContext.Finished) ) - SendLocalizedMessage( 502808 ); // You would have been poisoned, were you not new to the land of Britannia. Be careful in the future. - else - base.OnPoisonImmunity( from, poison ); - } - - #endregion - - public PlayerMobile( Serial s ) : base( s ) - { - VisibilityList = new List(); - m_AntiMacroTable = new Hashtable(); - InvalidateMyRunUO(); - } - - public List VisibilityList { get; } - - public List PermaFlags { get; private set; } - - public override int Luck => AosAttributes.GetValue( this, AosAttribute.Luck ); - - public override bool IsHarmfulCriminal( Mobile target ) - { - if ( SkillHandlers.Stealing.ClassicMode && target is PlayerMobile mobile && mobile.PermaFlags.Count > 0 ) - { - if ( Notoriety.Compute( this, mobile ) == Notoriety.Innocent ) - mobile.Delta( MobileDelta.Noto ); - - return false; - } - - BaseCreature bc = target as BaseCreature; - - if ( bc?.InitialInnocent == true && !bc.Controlled ) - return false; - - if ( Core.ML && bc?.Controlled == true && this == bc.ControlMaster ) - return false; - - return base.IsHarmfulCriminal( target ); - } - - public bool AntiMacroCheck( Skill skill, object obj ) - { - if ( obj == null || m_AntiMacroTable == null || AccessLevel != AccessLevel.Player ) - return true; - - Hashtable tbl = (Hashtable)m_AntiMacroTable[skill]; - if ( tbl == null ) - m_AntiMacroTable[skill] = tbl = new Hashtable(); - - CountAndTimeStamp count = (CountAndTimeStamp)tbl[obj]; - if ( count != null ) - { - if ( count.TimeStamp + SkillCheck.AntiMacroExpire <= DateTime.UtcNow ) - { - count.Count = 1; - return true; - } - - ++count.Count; - if ( count.Count <= SkillCheck.Allowance ) - return true; - return false; - } - - tbl[obj] = count = new CountAndTimeStamp(); - count.Count = 1; - - return true; - } - - private void RevertHair() - { - SetHairMods( -1, -1 ); - } - - public Engines.BulkOrders.BOBFilter BOBFilter { get; private set; } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - switch ( version ) - { - case 29: - { - if (reader.ReadBool()) - { - m_StuckMenuUses = new DateTime[reader.ReadInt()]; - - for (int i = 0; i < m_StuckMenuUses.Length; ++i) - { - m_StuckMenuUses[i] = reader.ReadDateTime(); - } - } - else - { - m_StuckMenuUses = null; - } - - goto case 28; - } - case 28: - { - PeacedUntil = reader.ReadDateTime(); - - goto case 27; - } - case 27: - { - AnkhNextUse = reader.ReadDateTime(); - - goto case 26; - } - case 26: - { - AutoStabled = reader.ReadStrongMobileList(); - - goto case 25; - } - case 25: - { - int recipeCount = reader.ReadInt(); - - if ( recipeCount > 0 ) - { - m_AcquiredRecipes = new Dictionary(); - - for( int i = 0; i < recipeCount; i++ ) - { - int r = reader.ReadInt(); - if ( reader.ReadBool() ) //Don't add in recipies which we haven't gotten or have been removed - m_AcquiredRecipes.Add( r, true ); - } - } - goto case 24; - } - case 24: - { - LastHonorLoss = reader.ReadDeltaTime(); - goto case 23; - } - case 23: - { - m_ChampionTitles = new ChampionTitleInfo( reader ); - goto case 22; - } - case 22: - { - LastValorLoss = reader.ReadDateTime(); - goto case 21; - } - case 21: - { - ToTItemsTurnedIn = reader.ReadEncodedInt(); - ToTTotalMonsterFame = reader.ReadInt(); - goto case 20; - } - case 20: - { - AllianceMessageHue = reader.ReadEncodedInt(); - GuildMessageHue = reader.ReadEncodedInt(); - - goto case 19; - } - case 19: - { - int rank = reader.ReadEncodedInt(); - int maxRank = Guilds.RankDefinition.Ranks.Length -1; - if ( rank > maxRank ) - rank = maxRank; - - m_GuildRank = Guilds.RankDefinition.Ranks[rank]; - LastOnline = reader.ReadDateTime(); - goto case 18; - } - case 18: - { - SolenFriendship = (SolenFriendship) reader.ReadEncodedInt(); - - goto case 17; - } - case 17: // changed how DoneQuests is serialized - case 16: - { - Quest = QuestSerializer.DeserializeQuest( reader ); - - if ( Quest != null ) - Quest.From = this; - - int count = reader.ReadEncodedInt(); - - if ( count > 0 ) - { - DoneQuests = new List(); - - for ( int i = 0; i < count; ++i ) - { - Type questType = QuestSerializer.ReadType( QuestSystem.QuestTypes, reader ); - DateTime restartTime; - - if ( version < 17 ) - restartTime = DateTime.MaxValue; - else - restartTime = reader.ReadDateTime(); - - DoneQuests.Add( new QuestRestartInfo( questType, restartTime ) ); - } - } - - Profession = reader.ReadEncodedInt(); - goto case 15; - } - case 15: - { - LastCompassionLoss = reader.ReadDeltaTime(); - goto case 14; - } - case 14: - { - CompassionGains = reader.ReadEncodedInt(); - - if ( CompassionGains > 0 ) - NextCompassionDay = reader.ReadDeltaTime(); - - goto case 13; - } - case 13: // just removed m_PaidInsurance list - case 12: - { - BOBFilter = new Engines.BulkOrders.BOBFilter( reader ); - goto case 11; - } - case 11: - { - if ( version < 13 ) - { - List paid = reader.ReadStrongItemList(); - - for ( int i = 0; i < paid.Count; ++i ) - paid[i].PaidInsurance = true; - } - - goto case 10; - } - case 10: - { - if ( reader.ReadBool() ) - { - m_HairModID = reader.ReadInt(); - m_HairModHue = reader.ReadInt(); - m_BeardModID = reader.ReadInt(); - m_BeardModHue = reader.ReadInt(); - } - - goto case 9; - } - case 9: - { - SavagePaintExpiration = reader.ReadTimeSpan(); - - if ( SavagePaintExpiration > TimeSpan.Zero ) - { - BodyMod = ( Female ? 184 : 183 ); - HueMod = 0; - } - - goto case 8; - } - case 8: - { - NpcGuild = (NpcGuild)reader.ReadInt(); - NpcGuildJoinTime = reader.ReadDateTime(); - NpcGuildGameTime = reader.ReadTimeSpan(); - goto case 7; - } - case 7: - { - PermaFlags = reader.ReadStrongMobileList(); - goto case 6; - } - case 6: - { - NextTailorBulkOrder = reader.ReadTimeSpan(); - goto case 5; - } - case 5: - { - NextSmithBulkOrder = reader.ReadTimeSpan(); - goto case 4; - } - case 4: - { - LastJusticeLoss = reader.ReadDeltaTime(); - JusticeProtectors = reader.ReadStrongMobileList(); - goto case 3; - } - case 3: - { - LastSacrificeGain = reader.ReadDeltaTime(); - LastSacrificeLoss = reader.ReadDeltaTime(); - AvailableResurrects = reader.ReadInt(); - goto case 2; - } - case 2: - { - Flags = (PlayerFlag)reader.ReadInt(); - goto case 1; - } - case 1: - { - m_LongTermElapse = reader.ReadTimeSpan(); - m_ShortTermElapse = reader.ReadTimeSpan(); - m_GameTime = reader.ReadTimeSpan(); - goto case 0; - } - case 0: - { - if ( version < 26 ) - AutoStabled = new List(); - break; - } - } - - if (RecentlyReported == null) - RecentlyReported = new List(); - - // Professions weren't verified on 1.0 RC0 - if ( !CharacterCreation.VerifyProfession( Profession ) ) - Profession = 0; - - if ( PermaFlags == null ) - PermaFlags = new List(); - - if ( JusticeProtectors == null ) - JusticeProtectors = new List(); - - if ( BOBFilter == null ) - BOBFilter = new Engines.BulkOrders.BOBFilter(); - - if ( m_GuildRank == null ) - m_GuildRank = Guilds.RankDefinition.Member; //Default to member if going from older version to new version (only time it should be null) - - if ( LastOnline == DateTime.MinValue && Account != null ) - LastOnline = ((Account)Account).LastLogin; - - if ( m_ChampionTitles == null ) - m_ChampionTitles = new ChampionTitleInfo(); - - if ( AccessLevel > AccessLevel.Player ) - m_IgnoreMobiles = true; - - List list = Stabled; - - for ( int i = 0; i < list.Count; ++i ) - { - if ( list[i] is BaseCreature bc ) - { - bc.IsStabled = true; - bc.StabledBy = this; - } - } - - CheckAtrophies( this ); - - if ( Hidden ) //Hiding is the only buff where it has an effect that's serialized. - AddBuff( new BuffInfo( BuffIcon.HidingAndOrStealth, 1075655 ) ); - } - - public override void Serialize( GenericWriter writer ) - { - //cleanup our anti-macro table - foreach ( Hashtable t in m_AntiMacroTable.Values ) - { - ArrayList remove = new ArrayList(); - foreach ( CountAndTimeStamp time in t.Values ) - { - if ( time.TimeStamp + SkillCheck.AntiMacroExpire <= DateTime.UtcNow ) - remove.Add( time ); - } - - for (int i=0;i kvp in m_AcquiredRecipes ) - { - writer.Write( kvp.Key ); - writer.Write( kvp.Value ); - } - } + if (DuelContext != null && !DuelContext.AllowSkillUse(this, skill)) + return false; - writer.WriteDeltaTime( LastHonorLoss ); + #endregion - ChampionTitleInfo.Serialize( writer, m_ChampionTitles ); + return DesignContext.Check(this); + } - writer.Write( LastValorLoss ); - writer.WriteEncodedInt( ToTItemsTurnedIn ); - writer.Write( ToTTotalMonsterFame ); //This ain't going to be a small #. + public virtual void RecheckTownProtection() + { + m_NextProtectionCheck = 10; - writer.WriteEncodedInt( AllianceMessageHue ); - writer.WriteEncodedInt( GuildMessageHue ); + GuardedRegion reg = (GuardedRegion)Region.GetRegion(typeof(GuardedRegion)); + bool isProtected = reg != null && !reg.IsDisabled(); - writer.WriteEncodedInt( m_GuildRank.Rank ); - writer.Write( LastOnline ); + if (isProtected != m_LastProtectedMessage) + { + if (isProtected) + SendLocalizedMessage(500112); // You are now under the protection of the town guards. + else + SendLocalizedMessage(500113); // You have left the protection of the town guards. + + m_LastProtectedMessage = isProtected; + } + } + + public override void MoveToWorld(Point3D loc, Map map) + { + base.MoveToWorld(loc, map); - writer.WriteEncodedInt( (int) SolenFriendship ); + RecheckTownProtection(); + } - QuestSerializer.Serialize( Quest, writer ); + public override void SetLocation(Point3D loc, bool isTeleport) + { + if (!isTeleport && AccessLevel == AccessLevel.Player) + { + // moving, not teleporting + int zDrop = Location.Z - loc.Z; + + if (zDrop > 20) // we fell more than one story + Hits -= zDrop / 20 * 10 - 5; // deal some damage; does not kill, disrupt, etc + } + + base.SetLocation(loc, isTeleport); + + if (isTeleport || --m_NextProtectionCheck == 0) + RecheckTownProtection(); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (from == this) + { + Quest?.GetContextMenuEntries(list); + + if (Alive) + { + if (InsuranceEnabled) + { + if (Core.SA) + list.Add(new CallbackEntry(1114299, OpenItemInsuranceMenu)); // Open Item Insurance Menu + + list.Add(new CallbackEntry(6201, ToggleItemInsurance)); // Toggle Item Insurance + + if (!Core.SA) + { + if (AutoRenewInsurance) + list.Add(new CallbackEntry(6202, + CancelRenewInventoryInsurance)); // Cancel Renewing Inventory Insurance + else + list.Add(new CallbackEntry(6200, + AutoRenewInventoryInsurance)); // Auto Renew Inventory Insurance + } + } + + if (MLQuestSystem.Enabled) + list.Add(new CallbackEntry(6169, ToggleQuestItem)); // Toggle Quest Item + } + + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null) + { + if (Alive && house.InternalizedVendors.Count > 0 && house.IsOwner(this)) + list.Add(new CallbackEntry(6204, GetVendor)); + + if (house.IsAosRules && !Region.IsPartOf(typeof(SafeZone))) // Dueling + list.Add(new CallbackEntry(6207, LeaveHouse)); + } + + if (JusticeProtectors.Count > 0) + list.Add(new CallbackEntry(6157, CancelProtection)); + + if (Alive) + list.Add(new CallbackEntry(6210, ToggleChampionTitleDisplay)); + + if (Core.HS) + { + NetState ns = from.NetState; + + if (ns != null && ns.ExtendedStatus) + list.Add(new CallbackEntry(RefuseTrades ? 1154112 : 1154113, + ToggleTrades)); // Allow Trades / Refuse Trades + } + } + else + { + if (Core.TOL && from.InRange(this, 2)) list.Add(new CallbackEntry(1077728, () => OpenTrade(from))); // Trade + + if (Alive && Core.Expansion >= Expansion.AOS) + { + Party theirParty = from.Party as Party; + Party ourParty = Party as Party; + + if (theirParty == null && ourParty == null) + { + list.Add(new AddToPartyEntry(from, this)); + } + else if (theirParty != null && theirParty.Leader == from) + { + if (ourParty == null) + list.Add(new AddToPartyEntry(from, this)); + else if (ourParty == theirParty) list.Add(new RemoveFromPartyEntry(from, this)); + } + } + + BaseHouse curhouse = BaseHouse.FindHouseAt(this); + + if (curhouse != null) + if (Alive && Core.Expansion >= Expansion.AOS && curhouse.IsAosRules && curhouse.IsFriend(from)) + list.Add(new EjectPlayerEntry(from, this)); + } + } + + private void CancelProtection() + { + for (int i = 0; i < JusticeProtectors.Count; ++i) + { + Mobile prot = JusticeProtectors[i]; + + string args = $"{Name}\t{prot.Name}"; + + prot.SendLocalizedMessage(1049371, + args); // The protective relationship between ~1_PLAYER1~ and ~2_PLAYER2~ has been ended. + SendLocalizedMessage(1049371, + args); // The protective relationship between ~1_PLAYER1~ and ~2_PLAYER2~ has been ended. + } + + JusticeProtectors.Clear(); + } + + private void ToggleTrades() + { + RefuseTrades = !RefuseTrades; + } + + private void GetVendor() + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (CheckAlive() && house != null && house.IsOwner(this) && house.InternalizedVendors.Count > 0) + { + CloseGump(typeof(ReclaimVendorGump)); + SendGump(new ReclaimVendorGump(house)); + } + } + + private void LeaveHouse() + { + BaseHouse house = BaseHouse.FindHouseAt(this); + + if (house != null) + Location = house.BanLocation; + } + + public override void DisruptiveAction() + { + if (Meditating) RemoveBuff(BuffIcon.ActiveMeditation); + + base.DisruptiveAction(); + } + + public override void OnDoubleClick(Mobile from) + { + if (this == from && !Warmode) + { + IMount mount = Mount; + + if (mount != null && !DesignContext.Check(this)) + return; + } + + base.OnDoubleClick(from); + } + + public override void DisplayPaperdollTo(Mobile to) + { + if (DesignContext.Check(this)) + base.DisplayPaperdollTo(to); + } + + public override bool CheckEquip(Item item) + { + if (!base.CheckEquip(item)) + return false; + + #region Dueling + + if (DuelContext != null && !DuelContext.AllowItemEquip(this, item)) + return false; + + #endregion + + #region Factions + + FactionItem factionItem = FactionItem.Find(item); + + if (factionItem != null) + { + Faction faction = Faction.Find(this); + + if (faction == null) + { + SendLocalizedMessage(1010371); // You cannot equip a faction item! + return false; + } + + if (faction != factionItem.Faction) + { + SendLocalizedMessage(1010372); // You cannot equip an opposing faction's item! + return false; + } + + int maxWearables = FactionItem.GetMaxWearables(this); + + for (int i = 0; i < Items.Count; ++i) + { + Item equipped = Items[i]; + + if (item != equipped && FactionItem.Find(equipped) != null) + if (--maxWearables == 0) + { + SendLocalizedMessage(1010373); // You do not have enough rank to equip more faction items! + return false; + } + } + } + + #endregion + + if (AccessLevel < AccessLevel.GameMaster && item.Layer != Layer.Mount && HasTrade) + { + BounceInfo bounce = item.GetBounce(); + + if (bounce != null) + { + if (bounce.m_Parent is Item parent) + { + if (parent == Backpack || parent.IsChildOf(Backpack)) + return true; + } + else if (bounce.m_Parent == this) + { + return true; + } + } + + SendLocalizedMessage( + 1004042); // You can only equip what you are already carrying while you have a trade pending. + return false; + } + + return true; + } + + public override bool CheckTrade(Mobile to, Item item, SecureTradeContainer cont, bool message, bool checkItems, + int plusItems, int plusWeight) + { + int msgNum = 0; + + if (cont == null) + { + if (to.Holding != null) + msgNum = 1062727; // You cannot trade with someone who is dragging something. + else if (HasTrade) + msgNum = 1062781; // You are already trading with someone else! + else if (to.HasTrade) + msgNum = 1062779; // That person is already involved in a trade + else if (to is PlayerMobile mobile && mobile.RefuseTrades) + msgNum = 1154111; // ~1_NAME~ is refusing all trades. + } + + if (msgNum == 0 && item != null) + { + if (cont != null) + { + plusItems += cont.TotalItems; + plusWeight += cont.TotalWeight; + } + + if (Backpack == null || !Backpack.CheckHold(this, item, false, checkItems, plusItems, plusWeight)) + msgNum = 1004040; // You would not be able to hold this if the trade failed. + else if (to.Backpack == null || !to.Backpack.CheckHold(to, item, false, checkItems, plusItems, plusWeight)) + msgNum = 1004039; // The recipient of this trade would not be able to carry this. + else + msgNum = CheckContentForTrade(item); + } + + if (msgNum != 0) + { + if (message) + { + if (msgNum == 1154111) + SendLocalizedMessage(msgNum, to.Name); + else + SendLocalizedMessage(msgNum); + } + + return false; + } + + return true; + } + + private static int CheckContentForTrade(Item item) + { + if (item is TrappableContainer container && container.TrapType != TrapType.None) + return 1004044; // You may not trade trapped items. + + if (StolenItem.IsStolen(item)) + return 1004043; // You may not trade recently stolen items. + + if (item is Container) + foreach (Item subItem in item.Items) + { + int msg = CheckContentForTrade(subItem); + + if (msg != 0) + return msg; + } + + return 0; + } + + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + if (!base.CheckNonlocalDrop(from, item, target)) + return false; + + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + + Container pack = Backpack; + if (from == this && HasTrade && (target == pack || target.IsChildOf(pack))) + { + BounceInfo bounce = item.GetBounce(); - if ( DoneQuests == null ) - { - writer.WriteEncodedInt( (int) 0 ); - } - else - { - writer.WriteEncodedInt( (int) DoneQuests.Count ); - - for ( int i = 0; i < DoneQuests.Count; ++i ) - { - QuestRestartInfo restartInfo = DoneQuests[i]; - - QuestSerializer.Write( (Type) restartInfo.QuestType, QuestSystem.QuestTypes, writer ); - writer.Write( (DateTime) restartInfo.RestartTime ); - } - } - - writer.WriteEncodedInt( (int) Profession ); - - writer.WriteDeltaTime( LastCompassionLoss ); - - writer.WriteEncodedInt( CompassionGains ); - - if ( CompassionGains > 0 ) - writer.WriteDeltaTime( NextCompassionDay ); - - BOBFilter.Serialize( writer ); - - bool useMods = ( m_HairModID != -1 || m_BeardModID != -1 ); + if (bounce?.m_Parent is Item parent && (parent == pack || parent.IsChildOf(pack))) + return true; - writer.Write( useMods ); + SendLocalizedMessage(1004041); // You can't do that while you have a trade pending. + return false; + } - if ( useMods ) - { - writer.Write( (int) m_HairModID ); - writer.Write( (int) m_HairModHue ); - writer.Write( (int) m_BeardModID ); - writer.Write( (int) m_BeardModHue ); - } + return true; + } - writer.Write( SavagePaintExpiration ); + protected override void OnLocationChange(Point3D oldLocation) + { + CheckLightLevels(false); - writer.Write( (int) NpcGuild ); - writer.Write( (DateTime) NpcGuildJoinTime ); - writer.Write( (TimeSpan) NpcGuildGameTime ); - - writer.Write( PermaFlags, true ); - - writer.Write( NextTailorBulkOrder ); - - writer.Write( NextSmithBulkOrder ); - - writer.WriteDeltaTime( LastJusticeLoss ); - writer.Write( JusticeProtectors, true ); - - writer.WriteDeltaTime( LastSacrificeGain ); - writer.WriteDeltaTime( LastSacrificeLoss ); - writer.Write( AvailableResurrects ); - - writer.Write( (int) Flags ); - - writer.Write( m_LongTermElapse ); - writer.Write( m_ShortTermElapse ); - writer.Write( GameTime ); - } - - public static void CheckAtrophies( Mobile m ) - { - SacrificeVirtue.CheckAtrophy( m ); - JusticeVirtue.CheckAtrophy( m ); - CompassionVirtue.CheckAtrophy( m ); - ValorVirtue.CheckAtrophy( m ); + #region Dueling - if ( m is PlayerMobile mobile ) - ChampionTitleInfo.CheckAtrophy( mobile ); - } + DuelContext?.OnLocationChanged(this); - public void CheckKillDecay() - { - if ( m_ShortTermElapse < GameTime ) - { - m_ShortTermElapse += TimeSpan.FromHours( 8 ); - if ( ShortTermMurders > 0 ) - --ShortTermMurders; - } + #endregion - if ( m_LongTermElapse < GameTime ) - { - m_LongTermElapse += TimeSpan.FromHours( 40 ); - if ( Kills > 0 ) - --Kills; - } - } + DesignContext context = DesignContext; - public void ResetKillTime() - { - m_ShortTermElapse = GameTime + TimeSpan.FromHours( 8 ); - m_LongTermElapse = GameTime + TimeSpan.FromHours( 40 ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime SessionStart { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan GameTime - { - get - { - if ( NetState != null ) - return m_GameTime + (DateTime.UtcNow - SessionStart); - return m_GameTime; - } - } - - public override bool CanSee( Mobile m ) - { - if ( m is CharacterStatue statue ) - statue.OnRequestedAnimation( this ); - - if ( m is PlayerMobile mobile && mobile.VisibilityList.Contains( this ) ) - return true; - - if ( DuelContext != null && m_DuelPlayer != null && !DuelContext.Finished && DuelContext.m_Tournament != null && !m_DuelPlayer.Eliminated ) - { - Mobile owner = m; - - if ( owner is BaseCreature bc ) - { - Mobile master = bc.GetMaster(); - - if ( master != null ) - owner = master; - } - - if ( m.AccessLevel == AccessLevel.Player && owner is PlayerMobile pm && pm.DuelContext != DuelContext ) - return false; - } - - return base.CanSee( m ); - } - - public virtual void CheckedAnimate( int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay ) - { - if ( !Mounted ) - { - base.Animate( action, frameCount, repeatCount, forward, repeat, delay ); - } - } - - public override void Animate( int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay ) - { - base.Animate( action, frameCount, repeatCount, forward, repeat, delay ); - } - - public override bool CanSee( Item item ) - { - if ( DesignContext != null && DesignContext.Foundation.IsHiddenToCustomizer( item ) ) - return false; - - return base.CanSee( item ); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - Faction faction = Faction.Find( this ); - - faction?.RemoveMember( this ); - - MLQuestSystem.HandleDeletion( this ); - - BaseHouse.HandleDeletion( this ); - - DisguiseTimers.RemoveTimer( this ); - } - - public override bool NewGuildDisplay => Server.Guilds.Guild.NewGuildSystem; - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Map == Faction.Facet ) - { - PlayerState pl = PlayerState.Find( this ); - - if ( pl != null ) - { - Faction faction = pl.Faction; - - if ( faction.Commander == this ) - list.Add( 1042733, faction.Definition.PropName ); // Commanding Lord of the ~1_FACTION_NAME~ - else if ( pl.Sheriff != null ) - list.Add( 1042734, "{0}\t{1}", pl.Sheriff.Definition.FriendlyName, faction.Definition.PropName ); // The Sheriff of ~1_CITY~, ~2_FACTION_NAME~ - else if ( pl.Finance != null ) - list.Add( 1042735, "{0}\t{1}", pl.Finance.Definition.FriendlyName, faction.Definition.PropName ); // The Finance Minister of ~1_CITY~, ~2_FACTION_NAME~ - else if ( pl.MerchantTitle != MerchantTitle.None ) - list.Add( 1060776, "{0}\t{1}", MerchantTitles.GetInfo( pl.MerchantTitle ).Title, faction.Definition.PropName ); // ~1_val~, ~2_val~ - else - list.Add( 1060776, "{0}\t{1}", pl.Rank.Title, faction.Definition.PropName ); // ~1_val~, ~2_val~ - } - } - - if ( Core.ML ) - { - for ( int i = AllFollowers.Count - 1; i >= 0; i-- ) - { - if ( AllFollowers[i] is BaseCreature c && c.ControlOrder == OrderType.Guard ) - { - list.Add( 501129 ); // guarded - break; - } - } - } - } - - public override void OnSingleClick( Mobile from ) - { - if ( Map == Faction.Facet ) - { - PlayerState pl = PlayerState.Find( this ); - - if ( pl != null ) - { - string text; - bool ascii = false; - - Faction faction = pl.Faction; - - if ( faction.Commander == this ) - text = string.Concat( Female ? "(Commanding Lady of the " : "(Commanding Lord of the ", faction.Definition.FriendlyName, ")" ); - else if ( pl.Sheriff != null ) - text = string.Concat( "(The Sheriff of ", pl.Sheriff.Definition.FriendlyName, ", ", faction.Definition.FriendlyName, ")" ); - else if ( pl.Finance != null ) - text = string.Concat( "(The Finance Minister of ", pl.Finance.Definition.FriendlyName, ", ", faction.Definition.FriendlyName, ")" ); - else - { - ascii = true; - - if ( pl.MerchantTitle != MerchantTitle.None ) - text = string.Concat( "(", MerchantTitles.GetInfo( pl.MerchantTitle ).Title.String, ", ", faction.Definition.FriendlyName, ")" ); - else - text = string.Concat( "(", pl.Rank.Title.String, ", ", faction.Definition.FriendlyName, ")" ); - } - - int hue = ( Faction.Find( from ) == faction ? 98 : 38 ); - - PrivateOverheadMessage( MessageType.Label, hue, ascii, text, from.NetState ); - } - } - - base.OnSingleClick( from ); - } - - protected override bool OnMove( Direction d ) - { - if ( !Core.SE ) - return base.OnMove( d ); - - if ( AccessLevel != AccessLevel.Player ) - return true; - - if ( Hidden && DesignContext.Find( this ) == null ) //Hidden & NOT customizing a house - { - if ( !Mounted && Skills.Stealth.Value >= 25.0 ) - { - bool running = (d & Direction.Running) != 0; - - if ( running ) - { - if ( (AllowedStealthSteps -= 2) <= 0 ) - RevealingAction(); - } - else if ( AllowedStealthSteps-- <= 0 ) - { - SkillHandlers.Stealth.OnUse( this ); - } - } - else - { - RevealingAction(); - } - } - - return true; - } - - public bool BedrollLogout { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public override bool Paralyzed - { - get => base.Paralyzed; - set - { - base.Paralyzed = value; - - if ( value ) - AddBuff( new BuffInfo( BuffIcon.Paralyze, 1075827 ) ); //Paralyze/You are frozen and can not move - else - RemoveBuff( BuffIcon.Paralyze ); - } - } - - #region Ethics - - [CommandProperty( AccessLevel.GameMaster )] - public Ethics.Player EthicPlayer { get; set; } - - #endregion - - #region Factions - - public PlayerState FactionPlayerState { get; set; } - - #endregion - - #region Dueling - - private Engines.ConPVP.DuelPlayer m_DuelPlayer; - - public Engines.ConPVP.DuelContext DuelContext { get; private set; } - - public Engines.ConPVP.DuelPlayer DuelPlayer - { - get => m_DuelPlayer; - set - { - bool wasInTourny = ( DuelContext != null && !DuelContext.Finished && DuelContext.m_Tournament != null ); - - m_DuelPlayer = value; - - if ( m_DuelPlayer == null ) - DuelContext = null; - else - DuelContext = m_DuelPlayer.Participant.Context; - - bool isInTourny = ( DuelContext != null && !DuelContext.Finished && DuelContext.m_Tournament != null ); - - if ( wasInTourny != isInTourny ) - SendEverything(); - } - } - #endregion + if (context == null || m_NoRecursion) + return; - #region Quests + m_NoRecursion = true; - public QuestSystem Quest { get; set; } + HouseFoundation foundation = context.Foundation; - public List DoneQuests { get; set; } + int newX = X, newY = Y; + int newZ = foundation.Z + HouseFoundation.GetLevelZ(context.Level, context.Foundation); - [CommandProperty( AccessLevel.GameMaster )] - public SolenFriendship SolenFriendship { get; set; } + int startX = foundation.X + foundation.Components.Min.X + 1; + int startY = foundation.Y + foundation.Components.Min.Y + 1; + int endX = startX + foundation.Components.Width - 1; + int endY = startY + foundation.Components.Height - 2; - #endregion + if (newX >= startX && newY >= startY && newX < endX && newY < endY && Map == foundation.Map) + { + if (Z != newZ) + Location = new Point3D(X, Y, newZ); - #region MyRunUO Invalidation + m_NoRecursion = false; + return; + } - public bool ChangedMyRunUO { get; set; } + Location = new Point3D(foundation.X, foundation.Y, newZ); + Map = foundation.Map; - public void InvalidateMyRunUO() - { - if ( !Deleted && !ChangedMyRunUO ) - { - ChangedMyRunUO = true; - Engines.MyRunUO.MyRunUO.QueueMobileUpdate( this ); - } - } + m_NoRecursion = false; + } - public override void OnKillsChange( int oldValue ) - { - if ( Young && Kills > oldValue ) - { - ((Account)Account)?.RemoveYoungStatus( 0 ); - } + public override bool OnMoveOver(Mobile m) + { + if (m is BaseCreature creature && !creature.Controlled) + return !Alive || !creature.Alive || IsDeadBondedPet || creature.IsDeadBondedPet || + Hidden && AccessLevel > AccessLevel.Player; - InvalidateMyRunUO(); - } + #region Dueling - public override void OnGenderChanged( bool oldFemale ) - { - InvalidateMyRunUO(); - } + if (Region.IsPartOf(typeof(SafeZone)) && m is PlayerMobile pm) + if (pm.DuelContext == null || pm.DuelPlayer == null || !pm.DuelContext.Started || pm.DuelContext.Finished || + pm.DuelPlayer.Eliminated) + return true; - public override void OnGuildChange( BaseGuild oldGuild ) - { - InvalidateMyRunUO(); - } + #endregion - public override void OnGuildTitleChange( string oldTitle ) - { - InvalidateMyRunUO(); - } + return base.OnMoveOver(m); + } - public override void OnKarmaChange( int oldValue ) - { - InvalidateMyRunUO(); - } + public override bool CheckShove(Mobile shoved) + { + if (m_IgnoreMobiles || TransformationSpellHelper.UnderTransformation(shoved, typeof(WraithFormSpell))) + return true; - public override void OnFameChange( int oldValue ) - { - InvalidateMyRunUO(); - } + return base.CheckShove(shoved); + } - public override void OnSkillChange( SkillName skill, double oldBase ) - { - if ( Young && SkillsTotal >= 4500 ) - { - ((Account)Account)?.RemoveYoungStatus( 1019036 ); // You have successfully obtained a respectable skill level, and have outgrown your status as a young player! - } + protected override void OnMapChange(Map oldMap) + { + if (Map != Faction.Facet && oldMap == Faction.Facet || Map == Faction.Facet && oldMap != Faction.Facet) + InvalidateProperties(); - if ( MLQuestSystem.Enabled ) - MLQuestSystem.HandleSkillGain( this, skill ); + #region Dueling - InvalidateMyRunUO(); - } + DuelContext?.OnMapChanged(this); - public override void OnAccessLevelChanged( AccessLevel oldLevel ) - { - if ( AccessLevel == AccessLevel.Player ) - IgnoreMobiles = false; - else - IgnoreMobiles = true; + #endregion - InvalidateMyRunUO(); - } + DesignContext context = DesignContext; - public override void OnRawStatChange( StatType stat, int oldValue ) - { - InvalidateMyRunUO(); - } + if (context == null || m_NoRecursion) + return; - public override void OnDelete() - { - ReceivedHonorContext?.Cancel(); - SentHonorContext?.Cancel(); + m_NoRecursion = true; - InvalidateMyRunUO(); - } + HouseFoundation foundation = context.Foundation; - #endregion + if (Map != foundation.Map) + Map = foundation.Map; - #region Fastwalk Prevention - private static bool FastwalkPrevention = true; // Is fastwalk prevention enabled? - private static int FastwalkThreshold = 400; // Fastwalk prevention will become active after 0.4 seconds + m_NoRecursion = false; + } - private long m_NextMovementTime; - private bool m_HasMoved; + public override void OnBeneficialAction(Mobile target, bool isCriminal) + { + SentHonorContext?.OnSourceBeneficialAction(target); - public virtual bool UsesFastwalkPrevention => ( AccessLevel < AccessLevel.Counselor ); + base.OnBeneficialAction(target, isCriminal); + } - public override int ComputeMovementSpeed( Direction dir, bool checkTurning ) - { - if ( checkTurning && (dir & Direction.Mask) != (Direction & Direction.Mask) ) - return RunMount; // We are NOT actually moving (just a direction change) - - TransformContext context = TransformationSpellHelper.GetContext( this ); - - if ( context != null && context.Type == typeof( ReaperFormSpell ) ) - return WalkFoot; - - bool running = ( (dir & Direction.Running) != 0 ); - - bool onHorse = ( Mount != null ); - - AnimalFormContext animalContext = AnimalForm.GetContext( this ); - - if ( onHorse || (animalContext != null && animalContext.SpeedBoost) ) - return ( running ? RunMount : WalkMount ); - - return ( running ? RunFoot : WalkFoot ); - } - - public static bool MovementThrottle_Callback( NetState ns ) - { - if ( !(ns.Mobile is PlayerMobile pm) || !pm.UsesFastwalkPrevention ) - return true; - - if ( !pm.m_HasMoved ) - { - // has not yet moved - pm.m_NextMovementTime = Core.TickCount; - pm.m_HasMoved = true; - return true; - } - - long ts = pm.m_NextMovementTime - Core.TickCount; - - if ( ts < 0 ) - { - // been a while since we've last moved - pm.m_NextMovementTime = Core.TickCount; - return true; - } - - return ( ts < FastwalkThreshold ); - } - - #endregion - - #region Enemy of One - private Type m_EnemyOfOneType; - - public Type EnemyOfOneType - { - get => m_EnemyOfOneType; - set - { - Type oldType = m_EnemyOfOneType; - Type newType = value; - - if ( oldType == newType ) - return; - - m_EnemyOfOneType = value; - - DeltaEnemies( oldType, newType ); - } - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + int disruptThreshold; - public bool WaitingForEnemy { get; set; } + if (!Core.AOS) + disruptThreshold = 0; + else if (from != null && from.Player) + disruptThreshold = 18; + else + disruptThreshold = 25; - private void DeltaEnemies( Type oldType, Type newType ) - { - foreach ( Mobile m in GetMobilesInRange( 18 ) ) - { - Type t = m.GetType(); + if (amount > disruptThreshold) + { + BandageContext c = BandageContext.GetContext(this); - if ( t == oldType || t == newType ) { - NetState ns = NetState; + c?.Slip(); + } - if ( ns != null ) { - if ( ns.StygianAbyss ) { - ns.Send( new MobileMoving( m, Notoriety.Compute( this, m ) ) ); - } else { - ns.Send( new MobileMovingOld( m, Notoriety.Compute( this, m ) ) ); - } - } - } - } - } + if (Confidence.IsRegenerating(this)) + Confidence.StopRegenerating(this); - #endregion + WeightOverloading.FatigueOnDamage(this, amount); - #region Hair and beard mods - private int m_HairModID = -1, m_HairModHue; - private int m_BeardModID = -1, m_BeardModHue; + ReceivedHonorContext?.OnTargetDamaged(from, amount); + SentHonorContext?.OnSourceDamaged(from, amount); - public void SetHairMods( int hairID, int beardID ) - { - if ( hairID == -1 ) - InternalRestoreHair( true, ref m_HairModID, ref m_HairModHue ); - else if ( hairID != -2 ) - InternalChangeHair( true, hairID, ref m_HairModID, ref m_HairModHue ); + if (willKill && from is PlayerMobile mobile) + Timer.DelayCall(TimeSpan.FromSeconds(10), mobile.RecoverAmmo); - if ( beardID == -1 ) - InternalRestoreHair( false, ref m_BeardModID, ref m_BeardModHue ); - else if ( beardID != -2 ) - InternalChangeHair( false, beardID, ref m_BeardModID, ref m_BeardModHue ); - } + base.OnDamage(amount, from, willKill); + } - private void CreateHair( bool hair, int id, int hue ) - { - if ( hair ) - { - //TODO Verification? - HairItemID = id; - HairHue = hue; - } - else - { - FacialHairItemID = id; - FacialHairHue = hue; - } - } - - private void InternalRestoreHair( bool hair, ref int id, ref int hue ) - { - if ( id == -1 ) - return; - - if ( hair ) - HairItemID = 0; - else - FacialHairItemID = 0; - - //if ( id != 0 ) - CreateHair( hair, id, hue ); - - id = -1; - hue = 0; - } - - private void InternalChangeHair( bool hair, int id, ref int storeID, ref int storeHue ) - { - if ( storeID == -1 ) - { - storeID = hair ? HairItemID : FacialHairItemID; - storeHue = hair ? HairHue : FacialHairHue; - } - CreateHair( hair, id, 0 ); - } - - #endregion - - #region Virtues - - public DateTime LastSacrificeGain { get; set; } - - public DateTime LastSacrificeLoss { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int AvailableResurrects { get; set; } - - private DateTime m_NextJustAward; - - public DateTime LastJusticeLoss { get; set; } - - public List JusticeProtectors { get; set; } - - public DateTime LastCompassionLoss { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextCompassionDay { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int CompassionGains { get; set; } - - public DateTime LastValorLoss { get; set; } - - public DateTime m_hontime; - - public DateTime LastHonorLoss { get; set; } - - public DateTime LastHonorUse { get; set; } - - public bool HonorActive { get; set; } - - public HonorContext ReceivedHonorContext { get; set; } - - public HonorContext SentHonorContext { get; set; } - - #endregion - - #region Young system - [CommandProperty( AccessLevel.GameMaster )] - public bool Young - { - get => GetFlag( PlayerFlag.Young ); - set{ SetFlag( PlayerFlag.Young, value ); InvalidateProperties(); } - } - - public override string ApplyNameSuffix( string suffix ) - { - if ( Young ) - { - if ( suffix.Length == 0 ) - suffix = "(Young)"; - else - suffix = string.Concat( suffix, " (Young)" ); - } - - #region Ethics - if ( EthicPlayer != null ) - { - if ( suffix.Length == 0 ) - suffix = EthicPlayer.Ethic.Definition.Adjunct.String; - else - suffix = string.Concat( suffix, " ", EthicPlayer.Ethic.Definition.Adjunct.String ); - } - #endregion - - if ( Core.ML && Map == Faction.Facet ) - { - Faction faction = Faction.Find( this ); - - if ( faction != null ) - { - string adjunct = $"[{faction.Definition.Abbreviation}]"; - if ( suffix.Length == 0 ) - suffix = adjunct; - else - suffix = string.Concat( suffix, " ", adjunct ); - } - } - - return base.ApplyNameSuffix( suffix ); - } - - public override TimeSpan GetLogoutDelay() - { - if ( Young || BedrollLogout || TestCenter.Enabled ) - return TimeSpan.Zero; - - return base.GetLogoutDelay(); - } - - private DateTime m_LastYoungMessage = DateTime.MinValue; - - public bool CheckYoungProtection( Mobile from ) - { - if ( !Young ) - return false; - - if ( Region is BaseRegion region && !region.YoungProtected ) - return false; - - if ( from is BaseCreature creature && creature.IgnoreYoungProtection ) - return false; - - if ( Quest != null && Quest.IgnoreYoungProtection( from ) ) - return false; - - if ( DateTime.UtcNow - m_LastYoungMessage > TimeSpan.FromMinutes( 1.0 ) ) - { - m_LastYoungMessage = DateTime.UtcNow; - SendLocalizedMessage( 1019067 ); // A monster looks at you menacingly but does not attack. You would be under attack now if not for your status as a new citizen of Britannia. - } - - return true; - } - - private DateTime m_LastYoungHeal = DateTime.MinValue; - - public bool CheckYoungHealTime() - { - if ( DateTime.UtcNow - m_LastYoungHeal > TimeSpan.FromMinutes( 5.0 ) ) - { - m_LastYoungHeal = DateTime.UtcNow; - return true; - } - - return false; - } - - private static Point3D[] m_TrammelDeathDestinations = { - new Point3D( 1481, 1612, 20 ), - new Point3D( 2708, 2153, 0 ), - new Point3D( 2249, 1230, 0 ), - new Point3D( 5197, 3994, 37 ), - new Point3D( 1412, 3793, 0 ), - new Point3D( 3688, 2232, 20 ), - new Point3D( 2578, 604, 0 ), - new Point3D( 4397, 1089, 0 ), - new Point3D( 5741, 3218, -2 ), - new Point3D( 2996, 3441, 15 ), - new Point3D( 624, 2225, 0 ), - new Point3D( 1916, 2814, 0 ), - new Point3D( 2929, 854, 0 ), - new Point3D( 545, 967, 0 ), - new Point3D( 3665, 2587, 0 ) - }; - - private static Point3D[] m_IlshenarDeathDestinations = { - new Point3D( 1216, 468, -13 ), - new Point3D( 723, 1367, -60 ), - new Point3D( 745, 725, -28 ), - new Point3D( 281, 1017, 0 ), - new Point3D( 986, 1011, -32 ), - new Point3D( 1175, 1287, -30 ), - new Point3D( 1533, 1341, -3 ), - new Point3D( 529, 217, -44 ), - new Point3D( 1722, 219, 96 ) - }; - - private static Point3D[] m_MalasDeathDestinations = { - new Point3D( 2079, 1376, -70 ), - new Point3D( 944, 519, -71 ) - }; - - private static Point3D[] m_TokunoDeathDestinations = { - new Point3D( 1166, 801, 27 ), - new Point3D( 782, 1228, 25 ), - new Point3D( 268, 624, 15 ) - }; - - public bool YoungDeathTeleport() - { - if ( Region.IsPartOf( typeof( Jail ) ) - || Region.IsPartOf( "Samurai start location" ) - || Region.IsPartOf( "Ninja start location" ) - || Region.IsPartOf( "Ninja cave" ) ) - return false; - - Point3D loc; - Map map; - - DungeonRegion dungeon = (DungeonRegion) Region.GetRegion( typeof( DungeonRegion ) ); - if ( dungeon != null && dungeon.EntranceLocation != Point3D.Zero ) - { - loc = dungeon.EntranceLocation; - map = dungeon.EntranceMap; - } - else - { - loc = Location; - map = Map; - } - - Point3D[] list; - - if ( map == Map.Trammel ) - list = m_TrammelDeathDestinations; - else if ( map == Map.Ilshenar ) - list = m_IlshenarDeathDestinations; - else if ( map == Map.Malas ) - list = m_MalasDeathDestinations; - else if ( map == Map.Tokuno ) - list = m_TokunoDeathDestinations; - else - return false; - - Point3D dest = Point3D.Zero; - int sqDistance = int.MaxValue; - - for ( int i = 0; i < list.Length; i++ ) - { - Point3D curDest = list[i]; - - int width = loc.X - curDest.X; - int height = loc.Y - curDest.Y; - int curSqDistance = width * width + height * height; - - if ( curSqDistance < sqDistance ) - { - dest = curDest; - sqDistance = curSqDistance; - } - } - - MoveToWorld( dest, map ); - return true; - } - - private void SendYoungDeathNotice() - { - SendGump( new YoungDeathNotice() ); - } - - #endregion - - #region Speech log - - public SpeechLog SpeechLog { get; private set; } - - public override void OnSpeech( SpeechEventArgs e ) - { - if ( SpeechLog.Enabled && NetState != null ) - { - if ( SpeechLog == null ) - SpeechLog = new SpeechLog(); - - SpeechLog.Add( e.Mobile, e.Speech ); - } - } - - #endregion - - #region Champion Titles - [CommandProperty( AccessLevel.GameMaster )] - public bool DisplayChampionTitle - { - get => GetFlag( PlayerFlag.DisplayChampionTitle ); - set => SetFlag( PlayerFlag.DisplayChampionTitle, value ); - } - - private ChampionTitleInfo m_ChampionTitles; - - [CommandProperty( AccessLevel.GameMaster )] - public ChampionTitleInfo ChampionTitles { get => m_ChampionTitles; - set { } } - - private void ToggleChampionTitleDisplay() - { - if ( !CheckAlive() ) - return; - - if ( DisplayChampionTitle ) - SendLocalizedMessage( 1062419, "", 0x23 ); // You have chosen to hide your monster kill title. - else - SendLocalizedMessage( 1062418, "", 0x23 ); // You have chosen to display your monster kill title. - - DisplayChampionTitle = !DisplayChampionTitle; - } - - [PropertyObject] - public class ChampionTitleInfo - { - public static TimeSpan LossDelay = TimeSpan.FromDays( 1.0 ); - public const int LossAmount = 90; - - private class TitleInfo - { - public int Value { get; set; } - - public DateTime LastDecay { get; set; } - - public TitleInfo() - { - } - - public TitleInfo( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch( version ) - { - case 0: - { - Value = reader.ReadEncodedInt(); - LastDecay = reader.ReadDateTime(); - break; - } - } - } - - public static void Serialize( GenericWriter writer, TitleInfo info ) - { - writer.WriteEncodedInt( (int)0 ); // version - - writer.WriteEncodedInt( info.Value ); - writer.Write( info.LastDecay ); - } - } - - private TitleInfo[] m_Values; + public override void Resurrect() + { + bool wasAlive = Alive; - public int GetValue( ChampionSpawnType type ) - { - return GetValue( (int)type ); - } + base.Resurrect(); - public void SetValue( ChampionSpawnType type, int value ) - { - SetValue( (int)type, value ); - } + if (Alive && !wasAlive) + { + Item deathRobe = new DeathRobe(); - public void Award( ChampionSpawnType type, int value ) - { - Award( (int)type, value ); - } - - public int GetValue( int index ) - { - if ( m_Values == null || index < 0 || index >= m_Values.Length ) - return 0; - - if ( m_Values[index] == null ) - m_Values[index] = new TitleInfo(); - - return m_Values[index].Value; - } - - public DateTime GetLastDecay( int index ) - { - if ( m_Values == null || index < 0 || index >= m_Values.Length ) - return DateTime.MinValue; - - if ( m_Values[index] == null ) - m_Values[index] = new TitleInfo(); - - return m_Values[index].LastDecay; - } - - public void SetValue( int index, int value ) - { - if ( m_Values == null ) - m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; - - if ( value < 0 ) - value = 0; - - if ( index < 0 || index >= m_Values.Length ) - return; - - if ( m_Values[index] == null ) - m_Values[index] = new TitleInfo(); - - m_Values[index].Value = value; - } - - public void Award( int index, int value ) - { - if ( m_Values == null ) - m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; - - if ( index < 0 || index >= m_Values.Length || value <= 0 ) - return; - - if ( m_Values[index] == null ) - m_Values[index] = new TitleInfo(); - - m_Values[index].Value += value; - } - - public void Atrophy( int index, int value ) - { - if ( m_Values == null ) - m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; - - if ( index < 0 || index >= m_Values.Length || value <= 0 ) - return; - - if ( m_Values[index] == null ) - m_Values[index] = new TitleInfo(); - - int before = m_Values[index].Value; - - if ( (m_Values[index].Value - value) < 0 ) - m_Values[index].Value = 0; - else - m_Values[index].Value -= value; - - if ( before != m_Values[index].Value ) - m_Values[index].LastDecay = DateTime.UtcNow; - } - - public override string ToString() - { - return "..."; - } - - [CommandProperty(AccessLevel.GameMaster)] - public int Pestilence { get => GetValue(ChampionSpawnType.Pestilence); - set => SetValue(ChampionSpawnType.Pestilence, value); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Abyss { get => GetValue( ChampionSpawnType.Abyss ); - set => SetValue( ChampionSpawnType.Abyss, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Arachnid { get => GetValue( ChampionSpawnType.Arachnid ); - set => SetValue( ChampionSpawnType.Arachnid, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ColdBlood { get => GetValue( ChampionSpawnType.ColdBlood ); - set => SetValue( ChampionSpawnType.ColdBlood, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ForestLord { get => GetValue( ChampionSpawnType.ForestLord ); - set => SetValue( ChampionSpawnType.ForestLord, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SleepingDragon { get => GetValue( ChampionSpawnType.SleepingDragon ); - set => SetValue( ChampionSpawnType.SleepingDragon, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int UnholyTerror { get => GetValue( ChampionSpawnType.UnholyTerror ); - set => SetValue( ChampionSpawnType.UnholyTerror, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int VerminHorde { get => GetValue( ChampionSpawnType.VerminHorde ); - set => SetValue( ChampionSpawnType.VerminHorde, value ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Harrower { get; set; } - - public ChampionTitleInfo() - { - } - - public ChampionTitleInfo( GenericReader reader ) - { - int version = reader.ReadEncodedInt(); - - switch( version ) - { - case 0: - { - Harrower = reader.ReadEncodedInt(); - - int length = reader.ReadEncodedInt(); - m_Values = new TitleInfo[length]; - - for( int i = 0; i < length; i++ ) - { - m_Values[i] = new TitleInfo( reader ); - } - - if ( m_Values.Length != ChampionSpawnInfo.Table.Length ) - { - TitleInfo[] oldValues = m_Values; - m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; - - for( int i = 0; i < m_Values.Length && i < oldValues.Length; i++ ) - { - m_Values[i] = oldValues[i]; - } - } - break; - } - } - } - - public static void Serialize( GenericWriter writer, ChampionTitleInfo titles ) - { - writer.WriteEncodedInt( (int)0 ); // version - - writer.WriteEncodedInt( titles.Harrower ); - - int length = titles.m_Values.Length; - writer.WriteEncodedInt( length ); - - for( int i = 0; i < length; i++ ) - { - if ( titles.m_Values[i] == null ) - titles.m_Values[i] = new TitleInfo(); - - TitleInfo.Serialize( writer, titles.m_Values[i] ); - } - } - - public static void CheckAtrophy( PlayerMobile pm ) - { - ChampionTitleInfo t = pm.m_ChampionTitles; - if ( t == null ) - return; - - if ( t.m_Values == null ) - t.m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; - - for( int i = 0; i < t.m_Values.Length; i++ ) - { - if ( (t.GetLastDecay( i ) + LossDelay) < DateTime.UtcNow ) - { - t.Atrophy( i, LossAmount ); - } - } - } - - public static void AwardHarrowerTitle( PlayerMobile pm ) //Called when killing a harrower. Will give a minimum of 1 point. - { - ChampionTitleInfo t = pm.m_ChampionTitles; - if ( t == null ) - return; - - if ( t.m_Values == null ) - t.m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; - - int count = 1; - - for( int i = 0; i < t.m_Values.Length; i++ ) - { - if ( t.m_Values[i].Value > 900 ) - count++; - } - - t.Harrower = Math.Max( count, t.Harrower ); //Harrower titles never decay. - } - } - - #endregion - - #region Recipes - - private Dictionary m_AcquiredRecipes; - - public virtual bool HasRecipe( Recipe r ) - { - if ( r == null ) - return false; - - return HasRecipe( r.ID ); - } - - public virtual bool HasRecipe( int recipeID ) - { - if ( m_AcquiredRecipes != null && m_AcquiredRecipes.ContainsKey( recipeID ) ) - return m_AcquiredRecipes[recipeID]; + if (!EquipItem(deathRobe)) + deathRobe.Delete(); + } + } - return false; - } + public override void OnWarmodeChanged() + { + if (!Warmode) + Timer.DelayCall(TimeSpan.FromSeconds(10), RecoverAmmo); + } - public virtual void AcquireRecipe( Recipe r ) - { - if ( r != null ) - AcquireRecipe( r.ID ); - } + private bool FindItems_Callback(Item item) + { + if (!item.Deleted && (item.LootType == LootType.Blessed || item.Insured)) + if (Backpack != item.Parent) + return true; + return false; + } - public virtual void AcquireRecipe( int recipeID ) - { - if ( m_AcquiredRecipes == null ) - m_AcquiredRecipes = new Dictionary(); + public override bool OnBeforeDeath() + { + NetState state = NetState; - m_AcquiredRecipes[recipeID] = true; - } - - public virtual void ResetRecipes() - { - m_AcquiredRecipes = null; - } + state?.CancelAllTrades(); - [CommandProperty( AccessLevel.GameMaster )] - public int KnownRecipes - { - get - { - if ( m_AcquiredRecipes == null ) - return 0; - - return m_AcquiredRecipes.Count; - } - } - - #endregion - - #region Buff Icons + DropHolding(); - public void ResendBuffs() - { - if ( !BuffInfo.Enabled || m_BuffTable == null ) - return; - - NetState state = NetState; + if (Core.AOS && Backpack != null && !Backpack.Deleted) + { + List ilist = Backpack.FindItemsByType(FindItems_Callback); - if ( state != null && state.BuffIcon ) - { - foreach( BuffInfo info in m_BuffTable.Values ) - { - state.Send( new AddBuffPacket( this, info ) ); - } - } - } + for (int i = 0; i < ilist.Count; i++) Backpack.AddItem(ilist[i]); + } - private Dictionary m_BuffTable; + EquipSnapshot = new List(Items); - public void AddBuff( BuffInfo b ) - { - if ( !BuffInfo.Enabled || b == null ) - return; + m_NonAutoreinsuredItems = 0; + m_InsuranceCost = 0; + m_InsuranceAward = FindMostRecentDamager(false); - RemoveBuff( b ); //Check & subsequently remove the old one. + if (m_InsuranceAward is BaseCreature creature) + { + Mobile master = creature.GetMaster(); - if ( m_BuffTable == null ) - m_BuffTable = new Dictionary(); + if (master != null) + m_InsuranceAward = master; + } - m_BuffTable.Add( b.ID, b ); + if (m_InsuranceAward != null && (!m_InsuranceAward.Player || m_InsuranceAward == this)) + m_InsuranceAward = null; - NetState state = NetState; + if (m_InsuranceAward is PlayerMobile mobile) + mobile.m_InsuranceBonus = 0; - if ( state != null && state.BuffIcon ) - { - state.Send( new AddBuffPacket( this, b ) ); - } - } + ReceivedHonorContext?.OnTargetKilled(); + SentHonorContext?.OnSourceKilled(); - public void RemoveBuff( BuffInfo b ) - { - if ( b == null ) - return; + RecoverAmmo(); - RemoveBuff( b.ID ); - } + return base.OnBeforeDeath(); + } - public void RemoveBuff( BuffIcon b ) - { - if ( m_BuffTable == null || !m_BuffTable.ContainsKey( b ) ) - return; + private bool CheckInsuranceOnDeath(Item item) + { + if (InsuranceEnabled && item.Insured) + { + #region Dueling - BuffInfo info = m_BuffTable[b]; + if (m_DuelPlayer != null && DuelContext != null && DuelContext.Registered && DuelContext.Started && + !m_DuelPlayer.Eliminated) + return true; - if ( info.Timer != null && info.Timer.Running ) - info.Timer.Stop(); + #endregion - m_BuffTable.Remove( b ); + if (AutoRenewInsurance) + { + int cost = GetInsuranceCost(item); - NetState state = NetState; + if (m_InsuranceAward != null) + cost /= 2; - if ( state != null && state.BuffIcon ) - { - state.Send( new RemoveBuffPacket( this, b ) ); - } + if (Banker.Withdraw(this, cost)) + { + m_InsuranceCost += cost; + item.PaidInsurance = true; + SendLocalizedMessage(1060398, + cost.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. + } + else + { + SendLocalizedMessage(1061079, "", 0x23); // You lack the funds to purchase the insurance + item.PaidInsurance = false; + item.Insured = false; + m_NonAutoreinsuredItems++; + } + } + else + { + item.PaidInsurance = false; + item.Insured = false; + } - if ( m_BuffTable.Count <= 0 ) - m_BuffTable = null; - } + if (m_InsuranceAward != null) + if (Banker.Deposit(m_InsuranceAward, 300)) + if (m_InsuranceAward is PlayerMobile mobile) + mobile.m_InsuranceBonus += 300; - #endregion + return true; + } - public void AutoStablePets() - { - if ( Core.SE && AllFollowers.Count > 0 ) - { - for ( int i = m_AllFollowers.Count - 1; i >= 0; --i ) - { - if (!(AllFollowers[i] is BaseCreature pet) || pet.ControlMaster == null) - continue; + return false; + } - if (pet.Summoned) - { - if (pet.Map != Map) - { - pet.PlaySound( pet.GetAngerSound() ); - Timer.DelayCall( TimeSpan.Zero, pet.Delete ); - } - continue; - } + public override DeathMoveResult GetParentMoveResultFor(Item item) + { + // It seems all items are unmarked on death, even blessed/insured ones + if (item.QuestItem) + item.QuestItem = false; - if ( pet is IMount mount && mount.Rider != null ) - continue; + if (CheckInsuranceOnDeath(item)) + return DeathMoveResult.MoveToBackpack; - if ( (pet is PackLlama || pet is PackHorse || pet is Beetle ) && (pet.Backpack != null && pet.Backpack.Items.Count > 0) ) - continue; + DeathMoveResult res = base.GetParentMoveResultFor(item); - if ( pet is BaseEscortable ) - continue; + if (res == DeathMoveResult.MoveToCorpse && item.Movable && Young) + res = DeathMoveResult.MoveToBackpack; - pet.ControlTarget = null; - pet.ControlOrder = OrderType.Stay; - pet.Internalize(); + return res; + } - pet.SetControlMaster( null ); - pet.SummonMaster = null; + public override DeathMoveResult GetInventoryMoveResultFor(Item item) + { + // It seems all items are unmarked on death, even blessed/insured ones + if (item.QuestItem) + item.QuestItem = false; - pet.IsStabled = true; - pet.StabledBy = this; + if (CheckInsuranceOnDeath(item)) + return DeathMoveResult.MoveToBackpack; - pet.Loyalty = BaseCreature.MaxLoyalty; // Wonderfully happy + DeathMoveResult res = base.GetInventoryMoveResultFor(item); - Stabled.Add( pet ); - AutoStabled.Add( pet ); - } - } - } + if (res == DeathMoveResult.MoveToCorpse && item.Movable && Young) + res = DeathMoveResult.MoveToBackpack; - public void ClaimAutoStabledPets() - { - if ( !Core.SE || AutoStabled.Count <= 0 ) - return; + return res; + } - if ( !Alive ) - { - SendLocalizedMessage( 1076251 ); // Your pet was unable to join you while you are a ghost. Please re-login once you have ressurected to claim your pets. - return; - } + public override void OnDeath(Container c) + { + if (m_NonAutoreinsuredItems > 0) SendLocalizedMessage(1061115); - for ( int i = AutoStabled.Count - 1; i >= 0; --i ) - { - BaseCreature pet = AutoStabled[i] as BaseCreature; + base.OnDeath(c); - if ( pet == null || pet.Deleted ) - { - pet.IsStabled = false; - pet.StabledBy = null; + EquipSnapshot = null; - if ( Stabled.Contains( pet ) ) - Stabled.Remove( pet ); + HueMod = -1; + NameMod = null; + SavagePaintExpiration = TimeSpan.Zero; - continue; - } + SetHairMods(-1, -1); - if ( (Followers + pet.ControlSlots) <= FollowersMax ) - { - pet.SetControlMaster( this ); + PolymorphSpell.StopTimer(this); + IncognitoSpell.StopTimer(this); + DisguiseTimers.RemoveTimer(this); - if ( pet.Summoned ) - pet.SummonMaster = this; + EndAction(typeof(PolymorphSpell)); + EndAction(typeof(IncognitoSpell)); - pet.ControlTarget = this; - pet.ControlOrder = OrderType.Follow; + MeerMage.StopEffect(this, false); - pet.MoveToWorld( Location, Map ); + #region Stygian Abyss - pet.IsStabled = false; - pet.StabledBy = null; - - pet.Loyalty = BaseCreature.MaxLoyalty; // Wonderfully Happy - - if ( Stabled.Contains( pet ) ) - Stabled.Remove( pet ); - } - else - { - SendLocalizedMessage( 1049612, pet.Name ); // ~1_NAME~ remained in the stables because you have too many followers. - } - } - - AutoStabled.Clear(); - } - } -} + if (Flying) + { + Flying = false; + BuffInfo.RemoveBuff(this, BuffIcon.Fly); + } + + #endregion + + StolenItem.ReturnOnDeath(this, c); + + if (PermaFlags.Count > 0) + { + PermaFlags.Clear(); + + if (c is Corpse corpse) + corpse.Criminal = true; + + if (Stealing.ClassicMode) + Criminal = true; + } + + if (Kills >= 5 && DateTime.UtcNow >= m_NextJustAward) + { + Mobile m = FindMostRecentDamager(false); + + if (m is BaseCreature bc) + m = bc.GetMaster(); + + if (m != this && m is PlayerMobile) + { + bool gainedPath = false; + + int pointsToGain = 0; + + pointsToGain += (int)Math.Sqrt(GameTime.TotalSeconds * 4); + pointsToGain *= 5; + pointsToGain += (int)Math.Pow(Skills.Total / 250, 2); + + if (VirtueHelper.Award(m, VirtueName.Justice, pointsToGain, ref gainedPath)) + { + if (gainedPath) + m.SendLocalizedMessage(1049367); // You have gained a path in Justice! + else + m.SendLocalizedMessage(1049363); // You have gained in Justice. + + m.FixedParticles(0x375A, 9, 20, 5027, EffectLayer.Waist); + m.PlaySound(0x1F7); + + m_NextJustAward = DateTime.UtcNow + TimeSpan.FromMinutes(pointsToGain / 3); + } + } + } + + if (m_InsuranceAward is PlayerMobile pm) + if (pm.m_InsuranceBonus > 0) + pm.SendLocalizedMessage(1060397, + pm.m_InsuranceBonus.ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + + Mobile killer = FindMostRecentDamager(true); + + if (killer is BaseCreature bcKiller) + { + Mobile master = bcKiller.GetMaster(); + if (master != null) + killer = master; + } + + if (Young && DuelContext == null) + if (YoungDeathTeleport()) + Timer.DelayCall(TimeSpan.FromSeconds(2.5), SendYoungDeathNotice); + + if (DuelContext == null || !DuelContext.Registered || !DuelContext.Started || m_DuelPlayer == null || + m_DuelPlayer.Eliminated) + Faction.HandleDeath(this, killer); + + Guilds.Guild.HandleDeath(this, killer); + + MLQuestSystem.HandleDeath(this); + + #region Dueling + + DuelContext?.OnDeath(this, c); + + #endregion + + if (m_BuffTable != null) + { + List list = new List(); + + foreach (BuffInfo buff in m_BuffTable.Values) + if (!buff.RetainThroughDeath) + list.Add(buff); + + for (int i = 0; i < list.Count; i++) RemoveBuff(list[i]); + } + } + + public override bool MutateSpeech(List hears, ref string text, ref object context) + { + if (Alive) + return false; + + if (Core.ML && Skills[SkillName.SpiritSpeak].Value >= 100.0) + return false; + + if (Core.AOS) + for (int i = 0; i < hears.Count; ++i) + { + Mobile m = hears[i]; + + if (m != this && m.Skills[SkillName.SpiritSpeak].Value >= 100.0) + return false; + } + + return base.MutateSpeech(hears, ref text, ref context); + } + + public override void DoSpeech(string text, int[] keywords, MessageType type, int hue) + { + if (Guilds.Guild.NewGuildSystem && (type == MessageType.Guild || type == MessageType.Alliance)) + { + if (!(Guild is Guild g)) + { + SendLocalizedMessage(1063142); // You are not in a guild! + } + else if (type == MessageType.Alliance) + { + if (g.Alliance != null && g.Alliance.IsMember(g)) + { + //g.Alliance.AllianceTextMessage( hue, "[Alliance][{0}]: {1}", this.Name, text ); + g.Alliance.AllianceChat(this, text); + SendToStaffMessage(this, "[Alliance]: {0}", text); + + AllianceMessageHue = hue; + } + else + { + SendLocalizedMessage(1071020); // You are not in an alliance! + } + } + else //Type == MessageType.Guild + { + GuildMessageHue = hue; + + g.GuildChat(this, text); + SendToStaffMessage(this, "[Guild]: {0}", text); + } + } + else + { + base.DoSpeech(text, keywords, type, hue); + } + } + + private static void SendToStaffMessage(Mobile from, string text) + { + Packet p = null; + + foreach (NetState ns in from.GetClientsInRange(8)) + { + Mobile mob = ns.Mobile; + + if (mob != null && mob.AccessLevel >= AccessLevel.GameMaster && mob.AccessLevel > from.AccessLevel) + { + if (p == null) + p = Packet.Acquire(new UnicodeMessage(from.Serial, from.Body, MessageType.Regular, from.SpeechHue, 3, + from.Language, from.Name, text)); + + ns.Send(p); + } + } + + Packet.Release(p); + } + + private static void SendToStaffMessage(Mobile from, string format, params object[] args) + { + SendToStaffMessage(from, string.Format(format, args)); + } + + public override void Damage(int amount, Mobile from) + { + if (EvilOmenSpell.TryEndEffect(this)) + amount = (int)(amount * 1.25); + + Mobile oath = BloodOathSpell.GetBloodOath(from); + + /* Per EA's UO Herald Pub48 (ML): + * ((resist spellsx10)/20 + 10=percentage of damage resisted) + */ + + if (oath == this) + { + amount = (int)(amount * 1.1); + + if (amount > 35 && from is PlayerMobile) /* capped @ 35, seems no expansion */ amount = 35; + + if (Core.ML) + from.Damage((int)(amount * (1 - (from.Skills.MagicResist.Value * .5 + 10) / 100)), this); + else + from.Damage(amount, this); + } + + if (from != null && Talisman is BaseTalisman talisman) + if (talisman.Protection != null && talisman.Protection.Type != null) + { + Type type = talisman.Protection.Type; + + if (type.IsAssignableFrom(from.GetType())) + amount = (int)(amount * (1 - (double)talisman.Protection.Amount / 100)); + } + + base.Damage(amount, from); + } + + public override bool IsHarmfulCriminal(Mobile target) + { + if (Stealing.ClassicMode && target is PlayerMobile mobile && mobile.PermaFlags.Count > 0) + { + if (Notoriety.Compute(this, mobile) == Notoriety.Innocent) + mobile.Delta(MobileDelta.Noto); + + return false; + } + + BaseCreature bc = target as BaseCreature; + + if (bc?.InitialInnocent == true && !bc.Controlled) + return false; + + if (Core.ML && bc?.Controlled == true && this == bc.ControlMaster) + return false; + + return base.IsHarmfulCriminal(target); + } + + public bool AntiMacroCheck(Skill skill, object obj) + { + if (obj == null || m_AntiMacroTable == null || AccessLevel != AccessLevel.Player) + return true; + + Hashtable tbl = (Hashtable)m_AntiMacroTable[skill]; + if (tbl == null) + m_AntiMacroTable[skill] = tbl = new Hashtable(); + + CountAndTimeStamp count = (CountAndTimeStamp)tbl[obj]; + if (count != null) + { + if (count.TimeStamp + SkillCheck.AntiMacroExpire <= DateTime.UtcNow) + { + count.Count = 1; + return true; + } + + ++count.Count; + if (count.Count <= SkillCheck.Allowance) + return true; + return false; + } + + tbl[obj] = count = new CountAndTimeStamp(); + count.Count = 1; + + return true; + } + + private void RevertHair() + { + SetHairMods(-1, -1); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + + switch (version) + { + case 29: + { + if (reader.ReadBool()) + { + m_StuckMenuUses = new DateTime[reader.ReadInt()]; + + for (int i = 0; i < m_StuckMenuUses.Length; ++i) m_StuckMenuUses[i] = reader.ReadDateTime(); + } + else + { + m_StuckMenuUses = null; + } + + goto case 28; + } + case 28: + { + PeacedUntil = reader.ReadDateTime(); + + goto case 27; + } + case 27: + { + AnkhNextUse = reader.ReadDateTime(); + + goto case 26; + } + case 26: + { + AutoStabled = reader.ReadStrongMobileList(); + + goto case 25; + } + case 25: + { + int recipeCount = reader.ReadInt(); + + if (recipeCount > 0) + { + m_AcquiredRecipes = new Dictionary(); + + for (int i = 0; i < recipeCount; i++) + { + int r = reader.ReadInt(); + if (reader.ReadBool()) //Don't add in recipies which we haven't gotten or have been removed + m_AcquiredRecipes.Add(r, true); + } + } + + goto case 24; + } + case 24: + { + LastHonorLoss = reader.ReadDeltaTime(); + goto case 23; + } + case 23: + { + m_ChampionTitles = new ChampionTitleInfo(reader); + goto case 22; + } + case 22: + { + LastValorLoss = reader.ReadDateTime(); + goto case 21; + } + case 21: + { + ToTItemsTurnedIn = reader.ReadEncodedInt(); + ToTTotalMonsterFame = reader.ReadInt(); + goto case 20; + } + case 20: + { + AllianceMessageHue = reader.ReadEncodedInt(); + GuildMessageHue = reader.ReadEncodedInt(); + + goto case 19; + } + case 19: + { + int rank = reader.ReadEncodedInt(); + int maxRank = RankDefinition.Ranks.Length - 1; + if (rank > maxRank) + rank = maxRank; + + m_GuildRank = RankDefinition.Ranks[rank]; + LastOnline = reader.ReadDateTime(); + goto case 18; + } + case 18: + { + SolenFriendship = (SolenFriendship)reader.ReadEncodedInt(); + + goto case 17; + } + case 17: // changed how DoneQuests is serialized + case 16: + { + Quest = QuestSerializer.DeserializeQuest(reader); + + if (Quest != null) + Quest.From = this; + + int count = reader.ReadEncodedInt(); + + if (count > 0) + { + DoneQuests = new List(); + + for (int i = 0; i < count; ++i) + { + Type questType = QuestSerializer.ReadType(QuestSystem.QuestTypes, reader); + DateTime restartTime; + + if (version < 17) + restartTime = DateTime.MaxValue; + else + restartTime = reader.ReadDateTime(); + + DoneQuests.Add(new QuestRestartInfo(questType, restartTime)); + } + } + + Profession = reader.ReadEncodedInt(); + goto case 15; + } + case 15: + { + LastCompassionLoss = reader.ReadDeltaTime(); + goto case 14; + } + case 14: + { + CompassionGains = reader.ReadEncodedInt(); + + if (CompassionGains > 0) + NextCompassionDay = reader.ReadDeltaTime(); + + goto case 13; + } + case 13: // just removed m_PaidInsurance list + case 12: + { + BOBFilter = new BOBFilter(reader); + goto case 11; + } + case 11: + { + if (version < 13) + { + List paid = reader.ReadStrongItemList(); + + for (int i = 0; i < paid.Count; ++i) + paid[i].PaidInsurance = true; + } + + goto case 10; + } + case 10: + { + if (reader.ReadBool()) + { + m_HairModID = reader.ReadInt(); + m_HairModHue = reader.ReadInt(); + m_BeardModID = reader.ReadInt(); + m_BeardModHue = reader.ReadInt(); + } + + goto case 9; + } + case 9: + { + SavagePaintExpiration = reader.ReadTimeSpan(); + + if (SavagePaintExpiration > TimeSpan.Zero) + { + BodyMod = Female ? 184 : 183; + HueMod = 0; + } + + goto case 8; + } + case 8: + { + NpcGuild = (NpcGuild)reader.ReadInt(); + NpcGuildJoinTime = reader.ReadDateTime(); + NpcGuildGameTime = reader.ReadTimeSpan(); + goto case 7; + } + case 7: + { + PermaFlags = reader.ReadStrongMobileList(); + goto case 6; + } + case 6: + { + NextTailorBulkOrder = reader.ReadTimeSpan(); + goto case 5; + } + case 5: + { + NextSmithBulkOrder = reader.ReadTimeSpan(); + goto case 4; + } + case 4: + { + LastJusticeLoss = reader.ReadDeltaTime(); + JusticeProtectors = reader.ReadStrongMobileList(); + goto case 3; + } + case 3: + { + LastSacrificeGain = reader.ReadDeltaTime(); + LastSacrificeLoss = reader.ReadDeltaTime(); + AvailableResurrects = reader.ReadInt(); + goto case 2; + } + case 2: + { + Flags = (PlayerFlag)reader.ReadInt(); + goto case 1; + } + case 1: + { + m_LongTermElapse = reader.ReadTimeSpan(); + m_ShortTermElapse = reader.ReadTimeSpan(); + m_GameTime = reader.ReadTimeSpan(); + goto case 0; + } + case 0: + { + if (version < 26) + AutoStabled = new List(); + break; + } + } + + if (RecentlyReported == null) + RecentlyReported = new List(); + + // Professions weren't verified on 1.0 RC0 + if (!CharacterCreation.VerifyProfession(Profession)) + Profession = 0; + + if (PermaFlags == null) + PermaFlags = new List(); + + if (JusticeProtectors == null) + JusticeProtectors = new List(); + + if (BOBFilter == null) + BOBFilter = new BOBFilter(); + + if (m_GuildRank == null) + m_GuildRank = + RankDefinition + .Member; //Default to member if going from older version to new version (only time it should be null) + + if (LastOnline == DateTime.MinValue && Account != null) + LastOnline = ((Account)Account).LastLogin; + + if (m_ChampionTitles == null) + m_ChampionTitles = new ChampionTitleInfo(); + + if (AccessLevel > AccessLevel.Player) + m_IgnoreMobiles = true; + + List list = Stabled; + + for (int i = 0; i < list.Count; ++i) + if (list[i] is BaseCreature bc) + { + bc.IsStabled = true; + bc.StabledBy = this; + } + + CheckAtrophies(this); + + if (Hidden) //Hiding is the only buff where it has an effect that's serialized. + AddBuff(new BuffInfo(BuffIcon.HidingAndOrStealth, 1075655)); + } + + public override void Serialize(GenericWriter writer) + { + //cleanup our anti-macro table + foreach (Hashtable t in m_AntiMacroTable.Values) + { + ArrayList remove = new ArrayList(); + foreach (CountAndTimeStamp time in t.Values) + if (time.TimeStamp + SkillCheck.AntiMacroExpire <= DateTime.UtcNow) + remove.Add(time); + + for (int i = 0; i < remove.Count; ++i) + t.Remove(remove[i]); + } + + CheckKillDecay(); + + CheckAtrophies(this); + + base.Serialize(writer); + + writer.Write(29); // version + + if (m_StuckMenuUses != null) + { + writer.Write(true); + + writer.Write(m_StuckMenuUses.Length); + + for (int i = 0; i < m_StuckMenuUses.Length; ++i) writer.Write(m_StuckMenuUses[i]); + } + else + { + writer.Write(false); + } + + writer.Write(PeacedUntil); + writer.Write(AnkhNextUse); + writer.Write(AutoStabled, true); + + if (m_AcquiredRecipes == null) + { + writer.Write(0); + } + else + { + writer.Write(m_AcquiredRecipes.Count); + + foreach (KeyValuePair kvp in m_AcquiredRecipes) + { + writer.Write(kvp.Key); + writer.Write(kvp.Value); + } + } + + writer.WriteDeltaTime(LastHonorLoss); + + ChampionTitleInfo.Serialize(writer, m_ChampionTitles); + + writer.Write(LastValorLoss); + writer.WriteEncodedInt(ToTItemsTurnedIn); + writer.Write(ToTTotalMonsterFame); //This ain't going to be a small #. + + writer.WriteEncodedInt(AllianceMessageHue); + writer.WriteEncodedInt(GuildMessageHue); + + writer.WriteEncodedInt(m_GuildRank.Rank); + writer.Write(LastOnline); + + writer.WriteEncodedInt((int)SolenFriendship); + + QuestSerializer.Serialize(Quest, writer); + + if (DoneQuests == null) + { + writer.WriteEncodedInt(0); + } + else + { + writer.WriteEncodedInt(DoneQuests.Count); + + for (int i = 0; i < DoneQuests.Count; ++i) + { + QuestRestartInfo restartInfo = DoneQuests[i]; + + QuestSerializer.Write(restartInfo.QuestType, QuestSystem.QuestTypes, writer); + writer.Write(restartInfo.RestartTime); + } + } + + writer.WriteEncodedInt(Profession); + + writer.WriteDeltaTime(LastCompassionLoss); + + writer.WriteEncodedInt(CompassionGains); + + if (CompassionGains > 0) + writer.WriteDeltaTime(NextCompassionDay); + + BOBFilter.Serialize(writer); + + bool useMods = m_HairModID != -1 || m_BeardModID != -1; + + writer.Write(useMods); + + if (useMods) + { + writer.Write(m_HairModID); + writer.Write(m_HairModHue); + writer.Write(m_BeardModID); + writer.Write(m_BeardModHue); + } + + writer.Write(SavagePaintExpiration); + + writer.Write((int)NpcGuild); + writer.Write(NpcGuildJoinTime); + writer.Write(NpcGuildGameTime); + + writer.Write(PermaFlags, true); + + writer.Write(NextTailorBulkOrder); + + writer.Write(NextSmithBulkOrder); + + writer.WriteDeltaTime(LastJusticeLoss); + writer.Write(JusticeProtectors, true); + + writer.WriteDeltaTime(LastSacrificeGain); + writer.WriteDeltaTime(LastSacrificeLoss); + writer.Write(AvailableResurrects); + + writer.Write((int)Flags); + + writer.Write(m_LongTermElapse); + writer.Write(m_ShortTermElapse); + writer.Write(GameTime); + } + + public static void CheckAtrophies(Mobile m) + { + SacrificeVirtue.CheckAtrophy(m); + JusticeVirtue.CheckAtrophy(m); + CompassionVirtue.CheckAtrophy(m); + ValorVirtue.CheckAtrophy(m); + + if (m is PlayerMobile mobile) + ChampionTitleInfo.CheckAtrophy(mobile); + } + + public void CheckKillDecay() + { + if (m_ShortTermElapse < GameTime) + { + m_ShortTermElapse += TimeSpan.FromHours(8); + if (ShortTermMurders > 0) + --ShortTermMurders; + } + + if (m_LongTermElapse < GameTime) + { + m_LongTermElapse += TimeSpan.FromHours(40); + if (Kills > 0) + --Kills; + } + } + + public void ResetKillTime() + { + m_ShortTermElapse = GameTime + TimeSpan.FromHours(8); + m_LongTermElapse = GameTime + TimeSpan.FromHours(40); + } + + public override bool CanSee(Mobile m) + { + if (m is CharacterStatue statue) + statue.OnRequestedAnimation(this); + + if (m is PlayerMobile mobile && mobile.VisibilityList.Contains(this)) + return true; + + if (DuelContext != null && m_DuelPlayer != null && !DuelContext.Finished && DuelContext.m_Tournament != null && + !m_DuelPlayer.Eliminated) + { + Mobile owner = m; + + if (owner is BaseCreature bc) + { + Mobile master = bc.GetMaster(); + + if (master != null) + owner = master; + } + + if (m.AccessLevel == AccessLevel.Player && owner is PlayerMobile pm && pm.DuelContext != DuelContext) + return false; + } + + return base.CanSee(m); + } + + public virtual void CheckedAnimate(int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay) + { + if (!Mounted) base.Animate(action, frameCount, repeatCount, forward, repeat, delay); + } + + public override void Animate(int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay) + { + base.Animate(action, frameCount, repeatCount, forward, repeat, delay); + } + + public override bool CanSee(Item item) + { + if (DesignContext != null && DesignContext.Foundation.IsHiddenToCustomizer(item)) + return false; + + return base.CanSee(item); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + Faction faction = Faction.Find(this); + + faction?.RemoveMember(this); + + MLQuestSystem.HandleDeletion(this); + + BaseHouse.HandleDeletion(this); + + DisguiseTimers.RemoveTimer(this); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Map == Faction.Facet) + { + PlayerState pl = PlayerState.Find(this); + + if (pl != null) + { + Faction faction = pl.Faction; + + if (faction.Commander == this) + list.Add(1042733, faction.Definition.PropName); // Commanding Lord of the ~1_FACTION_NAME~ + else if (pl.Sheriff != null) + list.Add(1042734, "{0}\t{1}", pl.Sheriff.Definition.FriendlyName, + faction.Definition.PropName); // The Sheriff of ~1_CITY~, ~2_FACTION_NAME~ + else if (pl.Finance != null) + list.Add(1042735, "{0}\t{1}", pl.Finance.Definition.FriendlyName, + faction.Definition.PropName); // The Finance Minister of ~1_CITY~, ~2_FACTION_NAME~ + else if (pl.MerchantTitle != MerchantTitle.None) + list.Add(1060776, "{0}\t{1}", MerchantTitles.GetInfo(pl.MerchantTitle).Title, + faction.Definition.PropName); // ~1_val~, ~2_val~ + else + list.Add(1060776, "{0}\t{1}", pl.Rank.Title, faction.Definition.PropName); // ~1_val~, ~2_val~ + } + } + + if (Core.ML) + for (int i = AllFollowers.Count - 1; i >= 0; i--) + if (AllFollowers[i] is BaseCreature c && c.ControlOrder == OrderType.Guard) + { + list.Add(501129); // guarded + break; + } + } + + public override void OnSingleClick(Mobile from) + { + if (Map == Faction.Facet) + { + PlayerState pl = PlayerState.Find(this); + + if (pl != null) + { + string text; + bool ascii = false; + + Faction faction = pl.Faction; + + if (faction.Commander == this) + { + text = string.Concat(Female ? "(Commanding Lady of the " : "(Commanding Lord of the ", + faction.Definition.FriendlyName, ")"); + } + else if (pl.Sheriff != null) + { + text = string.Concat("(The Sheriff of ", pl.Sheriff.Definition.FriendlyName, ", ", + faction.Definition.FriendlyName, ")"); + } + else if (pl.Finance != null) + { + text = string.Concat("(The Finance Minister of ", pl.Finance.Definition.FriendlyName, ", ", + faction.Definition.FriendlyName, ")"); + } + else + { + ascii = true; + + if (pl.MerchantTitle != MerchantTitle.None) + text = string.Concat("(", MerchantTitles.GetInfo(pl.MerchantTitle).Title.String, ", ", + faction.Definition.FriendlyName, ")"); + else + text = string.Concat("(", pl.Rank.Title.String, ", ", faction.Definition.FriendlyName, ")"); + } + + int hue = Faction.Find(from) == faction ? 98 : 38; + + PrivateOverheadMessage(MessageType.Label, hue, ascii, text, from.NetState); + } + } + + base.OnSingleClick(from); + } + + protected override bool OnMove(Direction d) + { + if (!Core.SE) + return base.OnMove(d); + + if (AccessLevel != AccessLevel.Player) + return true; + + if (Hidden && DesignContext.Find(this) == null) //Hidden & NOT customizing a house + { + if (!Mounted && Skills.Stealth.Value >= 25.0) + { + bool running = (d & Direction.Running) != 0; + + if (running) + { + if ((AllowedStealthSteps -= 2) <= 0) + RevealingAction(); + } + else if (AllowedStealthSteps-- <= 0) + { + Stealth.OnUse(this); + } + } + else + { + RevealingAction(); + } + } + + return true; + } + + public void AutoStablePets() + { + if (Core.SE && AllFollowers.Count > 0) + for (int i = m_AllFollowers.Count - 1; i >= 0; --i) + { + if (!(AllFollowers[i] is BaseCreature pet) || pet.ControlMaster == null) + continue; + + if (pet.Summoned) + { + if (pet.Map != Map) + { + pet.PlaySound(pet.GetAngerSound()); + Timer.DelayCall(TimeSpan.Zero, pet.Delete); + } + + continue; + } + + if (pet is IMount mount && mount.Rider != null) + continue; + + if ((pet is PackLlama || pet is PackHorse || pet is Beetle) && pet.Backpack != null && + pet.Backpack.Items.Count > 0) + continue; + + if (pet is BaseEscortable) + continue; + + pet.ControlTarget = null; + pet.ControlOrder = OrderType.Stay; + pet.Internalize(); + + pet.SetControlMaster(null); + pet.SummonMaster = null; + + pet.IsStabled = true; + pet.StabledBy = this; + + pet.Loyalty = BaseCreature.MaxLoyalty; // Wonderfully happy + + Stabled.Add(pet); + AutoStabled.Add(pet); + } + } + + public void ClaimAutoStabledPets() + { + if (!Core.SE || AutoStabled.Count <= 0) + return; + + if (!Alive) + { + SendLocalizedMessage( + 1076251); // Your pet was unable to join you while you are a ghost. Please re-login once you have ressurected to claim your pets. + return; + } + + for (int i = AutoStabled.Count - 1; i >= 0; --i) + { + BaseCreature pet = AutoStabled[i] as BaseCreature; + + if (pet == null || pet.Deleted) + { + pet.IsStabled = false; + pet.StabledBy = null; + + if (Stabled.Contains(pet)) + Stabled.Remove(pet); + + continue; + } + + if (Followers + pet.ControlSlots <= FollowersMax) + { + pet.SetControlMaster(this); + + if (pet.Summoned) + pet.SummonMaster = this; + + pet.ControlTarget = this; + pet.ControlOrder = OrderType.Follow; + + pet.MoveToWorld(Location, Map); + + pet.IsStabled = false; + pet.StabledBy = null; + + pet.Loyalty = BaseCreature.MaxLoyalty; // Wonderfully Happy + + if (Stabled.Contains(pet)) + Stabled.Remove(pet); + } + else + { + SendLocalizedMessage(1049612, + pet.Name); // ~1_NAME~ remained in the stables because you have too many followers. + } + } + + AutoStabled.Clear(); + } + + private class CountAndTimeStamp + { + private int m_Count; + + public DateTime TimeStamp{ get; private set; } + + public int Count + { + get => m_Count; + set + { + m_Count = value; + TimeStamp = DateTime.UtcNow; + } + } + } + + private class MountBlock + { + public Timer m_Timer; + public BlockMountType m_Type; + + public MountBlock(TimeSpan duration, BlockMountType type, Mobile mobile) + { + m_Type = type; + + m_Timer = Timer.DelayCall(duration, RemoveBlock, mobile); + } + + private void RemoveBlock(Mobile mobile) + { + (mobile as PlayerMobile).m_MountBlock = null; + } + } + + private delegate void ContextCallback(); + + private class CallbackEntry : ContextMenuEntry + { + private ContextCallback m_Callback; + + public CallbackEntry(int number, ContextCallback callback) : this(number, -1, callback) + { + } + + public CallbackEntry(int number, int range, ContextCallback callback) : base(number, range) + { + m_Callback = callback; + } + + public override void OnClick() + { + m_Callback?.Invoke(); + } + } + + #region Getters & Setters + + public List RecentlyReported{ get; set; } + + public List AutoStabled{ get; private set; } + + public bool NinjaWepCooldown{ get; set; } + + public List AllFollowers + { + get + { + if (m_AllFollowers == null) + m_AllFollowers = new List(); + return m_AllFollowers; + } + } + + public RankDefinition GuildRank + { + get + { + if (AccessLevel >= AccessLevel.GameMaster) + return RankDefinition.Leader; + return m_GuildRank; + } + set => m_GuildRank = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int GuildMessageHue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int AllianceMessageHue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int Profession{ get; set; } + + public int StepsTaken{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsStealthing // IsStealthing should be moved to Server.Mobiles + { + get; + set; + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool IgnoreMobiles // IgnoreMobiles should be moved to Server.Mobiles + { + get => m_IgnoreMobiles; + set + { + if (m_IgnoreMobiles != value) + { + m_IgnoreMobiles = value; + Delta(MobileDelta.Flags); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public NpcGuild NpcGuild{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NpcGuildJoinTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextBODTurnInTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastOnline{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public long LastMoved => LastMoveTime; + + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan NpcGuildGameTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ToTItemsTurnedIn{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ToTTotalMonsterFame{ get; set; } + + public int ExecutesLightningStrike{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int ToothAche + { + get => CandyCane.GetToothAche(this); + set => CandyCane.SetToothAche(this, value); + } + + #endregion + + #region PlayerFlags + + public PlayerFlag Flags{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool PagingSquelched + { + get => GetFlag(PlayerFlag.PagingSquelched); + set => SetFlag(PlayerFlag.PagingSquelched, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Glassblowing + { + get => GetFlag(PlayerFlag.Glassblowing); + set => SetFlag(PlayerFlag.Glassblowing, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Masonry + { + get => GetFlag(PlayerFlag.Masonry); + set => SetFlag(PlayerFlag.Masonry, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool SandMining + { + get => GetFlag(PlayerFlag.SandMining); + set => SetFlag(PlayerFlag.SandMining, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool StoneMining + { + get => GetFlag(PlayerFlag.StoneMining); + set => SetFlag(PlayerFlag.StoneMining, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool ToggleMiningStone + { + get => GetFlag(PlayerFlag.ToggleMiningStone); + set => SetFlag(PlayerFlag.ToggleMiningStone, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool KarmaLocked + { + get => GetFlag(PlayerFlag.KarmaLocked); + set => SetFlag(PlayerFlag.KarmaLocked, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool AutoRenewInsurance + { + get => GetFlag(PlayerFlag.AutoRenewInsurance); + set => SetFlag(PlayerFlag.AutoRenewInsurance, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool UseOwnFilter + { + get => GetFlag(PlayerFlag.UseOwnFilter); + set => SetFlag(PlayerFlag.UseOwnFilter, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool PublicMyRunUO + { + get => GetFlag(PlayerFlag.PublicMyRunUO); + set + { + SetFlag(PlayerFlag.PublicMyRunUO, value); + InvalidateMyRunUO(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool AcceptGuildInvites + { + get => GetFlag(PlayerFlag.AcceptGuildInvites); + set => SetFlag(PlayerFlag.AcceptGuildInvites, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool HasStatReward + { + get => GetFlag(PlayerFlag.HasStatReward); + set => SetFlag(PlayerFlag.HasStatReward, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool RefuseTrades + { + get => GetFlag(PlayerFlag.RefuseTrades); + set => SetFlag(PlayerFlag.RefuseTrades, value); + } + + #endregion + + #region Auto Arrow Recovery + + public Dictionary RecoverableAmmo{ get; } = new Dictionary(); + + public void RecoverAmmo() + { + if (Core.SE && Alive) + { + foreach (KeyValuePair kvp in RecoverableAmmo) + if (kvp.Value > 0) + { + Item ammo = null; + + try + { + ammo = Activator.CreateInstance(kvp.Key) as Item; + } + catch + { + } + + if (ammo != null) + { + string name = ammo.Name; + ammo.Amount = kvp.Value; + + if (name == null) + { + if (ammo is Arrow) + name = "arrow"; + else if (ammo is Bolt) + name = "bolt"; + } + + if (name != null && ammo.Amount > 1) + name = $"{name}s"; + + if (name == null) + name = $"#{ammo.LabelNumber}"; + + PlaceInBackpack(ammo); + SendLocalizedMessage(1073504, $"{ammo.Amount}\t{name}"); // You recover ~1_NUM~ ~2_AMMO~. + } + } + + RecoverableAmmo.Clear(); + } + } + + #endregion + + #region Scroll of Alacrity + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime AcceleratedStart{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public SkillName AcceleratedSkill{ get; set; } + + #endregion + + #region [Stats]Max + + [CommandProperty(AccessLevel.GameMaster)] + public override int HitsMax + { + get + { + int strBase; + int strOffs = GetStatOffset(StatType.Str); + + if (Core.AOS) + { + strBase = Str; //this.Str already includes GetStatOffset/str + strOffs = AosAttributes.GetValue(this, AosAttribute.BonusHits); + + if (Core.ML && strOffs > 25 && AccessLevel <= AccessLevel.Player) + strOffs = 25; + + if (AnimalForm.UnderTransformation(this, typeof(BakeKitsune)) || + AnimalForm.UnderTransformation(this, typeof(GreyWolf))) + strOffs += 20; + } + else + { + strBase = RawStr; + } + + return strBase / 2 + 50 + strOffs; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public override int StamMax => base.StamMax + AosAttributes.GetValue(this, AosAttribute.BonusStam); + + [CommandProperty(AccessLevel.GameMaster)] + public override int ManaMax => base.ManaMax + AosAttributes.GetValue(this, AosAttribute.BonusMana) + + (Core.ML && Race == Race.Elf ? 20 : 0); + + #endregion + + #region Stat Getters/Setters + + [CommandProperty(AccessLevel.GameMaster)] + public override int Str + { + get + { + if (Core.ML && AccessLevel == AccessLevel.Player) + return Math.Min(base.Str, 150); + + return base.Str; + } + set => base.Str = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public override int Int + { + get + { + if (Core.ML && AccessLevel == AccessLevel.Player) + return Math.Min(base.Int, 150); + + return base.Int; + } + set => base.Int = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public override int Dex + { + get + { + if (Core.ML && AccessLevel == AccessLevel.Player) + return Math.Min(base.Dex, 150); + + return base.Dex; + } + set => base.Dex = value; + } + + #endregion + + #region Insurance + + private static int GetInsuranceCost(Item item) + { + return 600; // TODO + } + + private void ToggleItemInsurance() + { + if (!CheckAlive()) + return; + + BeginTarget(-1, false, TargetFlags.None, ToggleItemInsurance_Callback); + SendLocalizedMessage(1060868); // Target the item you wish to toggle insurance status on to cancel + } + + private bool CanInsure(Item item) + { + if (item is Container && !(item is BaseQuiver) || item is BagOfSending || item is KeyRing || item is PotionKeg || + item is Sigil) + return false; + + if (item.Stackable) + return false; + + if (item.LootType == LootType.Cursed) + return false; + + if (item.ItemID == 0x204E) // death shroud + return false; + + if (item.Layer == Layer.Mount) + return false; + + if (item.LootType == LootType.Blessed || item.LootType == LootType.Newbied || item.BlessedFor == this) + return false; + + return true; + } + + private void ToggleItemInsurance_Callback(Mobile from, object obj) + { + if (!CheckAlive()) + return; + + ToggleItemInsurance_Callback(from, obj as Item, true); + } + + private void ToggleItemInsurance_Callback(Mobile from, Item item, bool target) + { + if (item == null || !item.IsChildOf(this)) + { + if (target) + BeginTarget(-1, false, TargetFlags.None, ToggleItemInsurance_Callback); + + SendLocalizedMessage(1060871, "", + 0x23); // You can only insure items that you have equipped or that are in your backpack + } + else if (item.Insured) + { + item.Insured = false; + + SendLocalizedMessage(1060874, "", 0x35); // You cancel the insurance on the item + + if (target) + { + BeginTarget(-1, false, TargetFlags.None, ToggleItemInsurance_Callback); + SendLocalizedMessage(1060868, "", + 0x23); // Target the item you wish to toggle insurance status on to cancel + } + } + else if (!CanInsure(item)) + { + if (target) + BeginTarget(-1, false, TargetFlags.None, ToggleItemInsurance_Callback); + + SendLocalizedMessage(1060869, "", 0x23); // You cannot insure that + } + else + { + if (!item.PaidInsurance) + { + int cost = GetInsuranceCost(item); + + if (Banker.Withdraw(from, cost)) + { + SendLocalizedMessage(1060398, + cost.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. + item.PaidInsurance = true; + } + else + { + SendLocalizedMessage(1061079, "", 0x23); // You lack the funds to purchase the insurance + return; + } + } + + item.Insured = true; + + SendLocalizedMessage(1060873, "", 0x23); // You have insured the item + + if (target) + { + BeginTarget(-1, false, TargetFlags.None, ToggleItemInsurance_Callback); + SendLocalizedMessage(1060868, "", + 0x23); // Target the item you wish to toggle insurance status on to cancel + } + } + } + + private void AutoRenewInventoryInsurance() + { + if (!CheckAlive()) + return; + + SendLocalizedMessage(1060881, "", + 0x23); // You have selected to automatically reinsure all insured items upon death + AutoRenewInsurance = true; + } + + private void CancelRenewInventoryInsurance() + { + if (!CheckAlive()) + return; + + if (Core.SE) + { + if (!HasGump(typeof(CancelRenewInventoryInsuranceGump))) + SendGump(new CancelRenewInventoryInsuranceGump(this, null)); + } + else + { + SendLocalizedMessage(1061075, "", + 0x23); // You have cancelled automatically reinsuring all insured items upon death + AutoRenewInsurance = false; + } + } + + private class CancelRenewInventoryInsuranceGump : Gump + { + private ItemInsuranceMenuGump m_InsuranceGump; + private PlayerMobile m_Player; + + public CancelRenewInventoryInsuranceGump(PlayerMobile player, ItemInsuranceMenuGump insuranceGump) : base(250, + 200) + { + m_Player = player; + m_InsuranceGump = insuranceGump; + + AddBackground(0, 0, 240, 142, 0x13BE); + AddImageTiled(6, 6, 228, 100, 0xA40); + AddImageTiled(6, 116, 228, 20, 0xA40); + AddAlphaRegion(6, 6, 228, 142); + + AddHtmlLocalized(8, 8, 228, 100, 1071021, 0x7FFF, false, + false); // You are about to disable inventory insurance auto-renewal. + + AddButton(6, 116, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 118, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + + AddButton(114, 116, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(148, 118, 450, 20, 1071022, 0x7FFF, false, false); // DISABLE IT! + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_Player.CheckAlive()) + return; + + if (info.ButtonID == 1) + { + m_Player.SendLocalizedMessage(1061075, "", + 0x23); // You have cancelled automatically reinsuring all insured items upon death + m_Player.AutoRenewInsurance = false; + } + else + { + m_Player.SendLocalizedMessage(1042021); // Cancelled. + } + + if (m_InsuranceGump != null) + m_Player.SendGump(m_InsuranceGump.NewInstance()); + } + } + + private void OpenItemInsuranceMenu() + { + if (!CheckAlive()) + return; + + List items = new List(); + + foreach (Item item in Items) + if (DisplayInItemInsuranceGump(item)) + items.Add(item); + + Container pack = Backpack; + + if (pack != null) + items.AddRange(pack.FindItemsByType(true, DisplayInItemInsuranceGump)); + + // TODO: Investigate item sorting + + CloseGump(typeof(ItemInsuranceMenuGump)); + + if (items.Count == 0) + SendLocalizedMessage(1114915, "", 0x35); // None of your current items meet the requirements for insurance. + else + SendGump(new ItemInsuranceMenuGump(this, items.ToArray())); + } + + private bool DisplayInItemInsuranceGump(Item item) + { + return (item.Visible || AccessLevel >= AccessLevel.GameMaster) && (item.Insured || CanInsure(item)); + } + + private class ItemInsuranceMenuGump : Gump + { + private PlayerMobile m_From; + private bool[] m_Insure; + private Item[] m_Items; + private int m_Page; + + public ItemInsuranceMenuGump(PlayerMobile from, Item[] items) + : this(from, items, null, 0) + { + } + + public ItemInsuranceMenuGump(PlayerMobile from, Item[] items, bool[] insure, int page) + : base(25, 50) + { + m_From = from; + m_Items = items; + + if (insure == null) + { + insure = new bool[items.Length]; + + for (int i = 0; i < items.Length; ++i) + insure[i] = items[i].Insured; + } + + m_Insure = insure; + m_Page = page; + + AddPage(0); + + AddBackground(0, 0, 520, 510, 0x13BE); + AddImageTiled(10, 10, 500, 30, 0xA40); + AddImageTiled(10, 50, 500, 355, 0xA40); + AddImageTiled(10, 415, 500, 80, 0xA40); + AddAlphaRegion(10, 10, 500, 485); + + AddButton(15, 470, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 472, 80, 20, 1011012, 0x7FFF, false, false); // CANCEL + + if (from.AutoRenewInsurance) + AddButton(360, 10, 9723, 9724, 1, GumpButtonType.Reply, 0); + else + AddButton(360, 10, 9720, 9722, 1, GumpButtonType.Reply, 0); + + AddHtmlLocalized(395, 14, 105, 20, 1114122, 0x7FFF, false, false); // AUTO REINSURE + + AddButton(395, 470, 0xFA5, 0xFA6, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(430, 472, 50, 20, 1006044, 0x7FFF, false, false); // OK + + AddHtmlLocalized(10, 14, 150, 20, 1114121, 0x7FFF, false, false); //
ITEM INSURANCE MENU
+ + AddHtmlLocalized(45, 54, 70, 20, 1062214, 0x7FFF, false, false); // Item + AddHtmlLocalized(250, 54, 70, 20, 1061038, 0x7FFF, false, false); // Cost + AddHtmlLocalized(400, 54, 70, 20, 1114311, 0x7FFF, false, false); // Insured + + int balance = Banker.GetBalance(from); + int cost = 0; + + for (int i = 0; i < items.Length; ++i) + if (insure[i]) + cost += GetInsuranceCost(items[i]); + + AddHtmlLocalized(15, 420, 300, 20, 1114310, 0x7FFF, false, false); // GOLD AVAILABLE: + AddLabel(215, 420, 0x481, balance.ToString()); + AddHtmlLocalized(15, 435, 300, 20, 1114123, 0x7FFF, false, false); // TOTAL COST OF INSURANCE: + AddLabel(215, 435, 0x481, cost.ToString()); + + if (cost != 0) + { + AddHtmlLocalized(15, 450, 300, 20, 1114125, 0x7FFF, false, false); // NUMBER OF DEATHS PAYABLE: + AddLabel(215, 450, 0x481, (balance / cost).ToString()); + } + + for (int i = page * 4, y = 72; i < (page + 1) * 4 && i < items.Length; ++i, y += 75) + { + Item item = items[i]; + Rectangle2D b = ItemBounds.Table[item.ItemID]; + + AddImageTiledButton(40, y, 0x918, 0x918, 0, GumpButtonType.Page, 0, item.ItemID, item.Hue, + 40 - b.Width / 2 - b.X, 30 - b.Height / 2 - b.Y); + AddItemProperty(item.Serial); + + if (insure[i]) + { + AddButton(400, y, 9723, 9724, 100 + i, GumpButtonType.Reply, 0); + AddLabel(250, y, 0x481, GetInsuranceCost(item).ToString()); + } + else + { + AddButton(400, y, 9720, 9722, 100 + i, GumpButtonType.Reply, 0); + AddLabel(250, y, 0x66C, GetInsuranceCost(item).ToString()); + } + } + + if (page >= 1) + { + AddButton(15, 380, 0xFAE, 0xFAF, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 380, 450, 20, 1044044, 0x7FFF, false, false); // PREV PAGE + } + + if ((page + 1) * 4 < items.Length) + { + AddButton(400, 380, 0xFA5, 0xFA7, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(435, 380, 70, 20, 1044045, 0x7FFF, false, false); // NEXT PAGE + } + } + + public ItemInsuranceMenuGump NewInstance() + { + return new ItemInsuranceMenuGump(m_From, m_Items, m_Insure, m_Page); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 0 || !m_From.CheckAlive()) + return; + + switch (info.ButtonID) + { + case 1: // Auto Reinsure + { + if (m_From.AutoRenewInsurance) + { + if (!m_From.HasGump(typeof(CancelRenewInventoryInsuranceGump))) + m_From.SendGump(new CancelRenewInventoryInsuranceGump(m_From, this)); + } + else + { + m_From.AutoRenewInventoryInsurance(); + m_From.SendGump(new ItemInsuranceMenuGump(m_From, m_Items, m_Insure, m_Page)); + } + + break; + } + case 2: // OK + { + m_From.SendGump(new ItemInsuranceMenuConfirmGump(m_From, m_Items, m_Insure, m_Page)); + + break; + } + case 3: // Prev + { + if (m_Page >= 1) + m_From.SendGump(new ItemInsuranceMenuGump(m_From, m_Items, m_Insure, m_Page - 1)); + + break; + } + case 4: // Next + { + if ((m_Page + 1) * 4 < m_Items.Length) + m_From.SendGump(new ItemInsuranceMenuGump(m_From, m_Items, m_Insure, m_Page + 1)); + + break; + } + default: + { + int idx = info.ButtonID - 100; + + if (idx >= 0 && idx < m_Items.Length) + m_Insure[idx] = !m_Insure[idx]; + + m_From.SendGump(new ItemInsuranceMenuGump(m_From, m_Items, m_Insure, m_Page)); + + break; + } + } + } + } + + private class ItemInsuranceMenuConfirmGump : Gump + { + private PlayerMobile m_From; + private bool[] m_Insure; + private Item[] m_Items; + private int m_Page; + + public ItemInsuranceMenuConfirmGump(PlayerMobile from, Item[] items, bool[] insure, int page) + : base(250, 200) + { + m_From = from; + m_Items = items; + m_Insure = insure; + m_Page = page; + + AddBackground(0, 0, 240, 142, 0x13BE); + AddImageTiled(6, 6, 228, 100, 0xA40); + AddImageTiled(6, 116, 228, 20, 0xA40); + AddAlphaRegion(6, 6, 228, 142); + + AddHtmlLocalized(8, 8, 228, 100, 1114300, 0x7FFF, false, + false); // Do you wish to insure all newly selected items? + + AddButton(6, 116, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(40, 118, 450, 20, 1060051, 0x7FFF, false, false); // CANCEL + + AddButton(114, 116, 0xFA5, 0xFA7, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(148, 118, 450, 20, 1073996, 0x7FFF, false, false); // ACCEPT + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_From.CheckAlive()) + return; + + if (info.ButtonID == 1) + { + for (int i = 0; i < m_Items.Length; ++i) + { + Item item = m_Items[i]; + + if (item.Insured != m_Insure[i]) + m_From.ToggleItemInsurance_Callback(m_From, item, false); + } + } + else + { + m_From.SendLocalizedMessage(1042021); // Cancelled. + m_From.SendGump(new ItemInsuranceMenuGump(m_From, m_Items, m_Insure, m_Page)); + } + } + } + + #endregion + + #region Toggle Quest Item + + private void ToggleQuestItem() + { + if (!CheckAlive()) + return; + + ToggleQuestItemTarget(); + } + + private void ToggleQuestItemTarget() + { + BaseQuestGump.CloseOtherGumps(this); + CloseGump(typeof(QuestLogDetailedGump)); + CloseGump(typeof(QuestLogGump)); + CloseGump(typeof(QuestOfferGump)); + //CloseGump( typeof( UnknownGump802 ) ); + //CloseGump( typeof( UnknownGump804 ) ); + + BeginTarget(-1, false, TargetFlags.None, ToggleQuestItem_Callback); + SendLocalizedMessage(1072352); // Target the item you wish to toggle Quest Item status on to cancel + } + + private void ToggleQuestItem_Callback(Mobile from, object obj) + { + if (!CheckAlive()) + return; + + if (!(obj is Item item)) + return; + + if (from.Backpack == null || item.Parent != from.Backpack) + { + SendLocalizedMessage( + 1074769); // An item must be in your backpack (and not in a container within) to be toggled as a quest item. + } + else if (item.QuestItem) + { + item.QuestItem = false; + SendLocalizedMessage(1072354); // You remove Quest Item status from the item + } + else if (MLQuestSystem.MarkQuestItem(this, item)) + { + SendLocalizedMessage(1072353); // You set the item to Quest Item status + } + else + { + SendLocalizedMessage(1072355, "", 0x23); // That item does not match any of your quest criteria + } + + ToggleQuestItemTarget(); + } + + #endregion + + #region Stuck Menu + + private DateTime[] m_StuckMenuUses; + + public bool CanUseStuckMenu() + { + if (m_StuckMenuUses == null) return true; + + for (int i = 0; i < m_StuckMenuUses.Length; ++i) + if (DateTime.UtcNow - m_StuckMenuUses[i] > TimeSpan.FromDays(1.0)) + return true; + + return false; + } + + public void UsedStuckMenu() + { + if (m_StuckMenuUses == null) m_StuckMenuUses = new DateTime[2]; + + for (int i = 0; i < m_StuckMenuUses.Length; ++i) + if (DateTime.UtcNow - m_StuckMenuUses[i] > TimeSpan.FromDays(1.0)) + { + m_StuckMenuUses[i] = DateTime.UtcNow; + return; + } + } + + #endregion + + #region Poison + + public override ApplyPoisonResult ApplyPoison(Mobile from, Poison poison) + { + if (!Alive) + return ApplyPoisonResult.Immune; + + if (EvilOmenSpell.TryEndEffect(this)) + poison = PoisonImpl.IncreaseLevel(poison); + + ApplyPoisonResult result = base.ApplyPoison(from, poison); + + if (from != null && result == ApplyPoisonResult.Poisoned && PoisonTimer is PoisonImpl.PoisonTimer timer) + timer.From = from; + + return result; + } + + public override bool CheckPoisonImmunity(Mobile from, Poison poison) + { + if (Young && (DuelContext == null || !DuelContext.Started || DuelContext.Finished)) + return true; + + return base.CheckPoisonImmunity(from, poison); + } + + public override void OnPoisonImmunity(Mobile from, Poison poison) + { + if (Young && (DuelContext == null || !DuelContext.Started || DuelContext.Finished)) + SendLocalizedMessage( + 502808); // You would have been poisoned, were you not new to the land of Britannia. Be careful in the future. + else + base.OnPoisonImmunity(from, poison); + } + + #endregion + + #region Dueling + + private DuelPlayer m_DuelPlayer; + + public DuelContext DuelContext{ get; private set; } + + public DuelPlayer DuelPlayer + { + get => m_DuelPlayer; + set + { + bool wasInTourny = DuelContext != null && !DuelContext.Finished && DuelContext.m_Tournament != null; + + m_DuelPlayer = value; + + if (m_DuelPlayer == null) + DuelContext = null; + else + DuelContext = m_DuelPlayer.Participant.Context; + + bool isInTourny = DuelContext != null && !DuelContext.Finished && DuelContext.m_Tournament != null; + + if (wasInTourny != isInTourny) + SendEverything(); + } + } + + #endregion + + #region Quests + + public QuestSystem Quest{ get; set; } + + public List DoneQuests{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public SolenFriendship SolenFriendship{ get; set; } + + #endregion + + #region MyRunUO Invalidation + + public bool ChangedMyRunUO{ get; set; } + + public void InvalidateMyRunUO() + { + if (!Deleted && !ChangedMyRunUO) + { + ChangedMyRunUO = true; + MyRunUO.QueueMobileUpdate(this); + } + } + + public override void OnKillsChange(int oldValue) + { + if (Young && Kills > oldValue) ((Account)Account)?.RemoveYoungStatus(0); + + InvalidateMyRunUO(); + } + + public override void OnGenderChanged(bool oldFemale) + { + InvalidateMyRunUO(); + } + + public override void OnGuildChange(BaseGuild oldGuild) + { + InvalidateMyRunUO(); + } + + public override void OnGuildTitleChange(string oldTitle) + { + InvalidateMyRunUO(); + } + + public override void OnKarmaChange(int oldValue) + { + InvalidateMyRunUO(); + } + + public override void OnFameChange(int oldValue) + { + InvalidateMyRunUO(); + } + + public override void OnSkillChange(SkillName skill, double oldBase) + { + if (Young && SkillsTotal >= 4500) + ((Account)Account) + ?.RemoveYoungStatus( + 1019036); // You have successfully obtained a respectable skill level, and have outgrown your status as a young player! + + if (MLQuestSystem.Enabled) + MLQuestSystem.HandleSkillGain(this, skill); + + InvalidateMyRunUO(); + } + + public override void OnAccessLevelChanged(AccessLevel oldLevel) + { + if (AccessLevel == AccessLevel.Player) + IgnoreMobiles = false; + else + IgnoreMobiles = true; + + InvalidateMyRunUO(); + } + + public override void OnRawStatChange(StatType stat, int oldValue) + { + InvalidateMyRunUO(); + } + + public override void OnDelete() + { + ReceivedHonorContext?.Cancel(); + SentHonorContext?.Cancel(); + + InvalidateMyRunUO(); + } + + #endregion + + #region Fastwalk Prevention + + private static bool FastwalkPrevention = true; // Is fastwalk prevention enabled? + private static int FastwalkThreshold = 400; // Fastwalk prevention will become active after 0.4 seconds + + private long m_NextMovementTime; + private bool m_HasMoved; + + public virtual bool UsesFastwalkPrevention => AccessLevel < AccessLevel.Counselor; + + public override int ComputeMovementSpeed(Direction dir, bool checkTurning) + { + if (checkTurning && (dir & Direction.Mask) != (Direction & Direction.Mask)) + return RunMount; // We are NOT actually moving (just a direction change) + + TransformContext context = TransformationSpellHelper.GetContext(this); + + if (context != null && context.Type == typeof(ReaperFormSpell)) + return WalkFoot; + + bool running = (dir & Direction.Running) != 0; + + bool onHorse = Mount != null; + + AnimalFormContext animalContext = AnimalForm.GetContext(this); + + if (onHorse || animalContext != null && animalContext.SpeedBoost) + return running ? RunMount : WalkMount; + + return running ? RunFoot : WalkFoot; + } + + public static bool MovementThrottle_Callback(NetState ns) + { + if (!(ns.Mobile is PlayerMobile pm) || !pm.UsesFastwalkPrevention) + return true; + + if (!pm.m_HasMoved) + { + // has not yet moved + pm.m_NextMovementTime = Core.TickCount; + pm.m_HasMoved = true; + return true; + } + + long ts = pm.m_NextMovementTime - Core.TickCount; + + if (ts < 0) + { + // been a while since we've last moved + pm.m_NextMovementTime = Core.TickCount; + return true; + } + + return ts < FastwalkThreshold; + } + + #endregion + + #region Enemy of One + + private Type m_EnemyOfOneType; + + public Type EnemyOfOneType + { + get => m_EnemyOfOneType; + set + { + Type oldType = m_EnemyOfOneType; + Type newType = value; + + if (oldType == newType) + return; + + m_EnemyOfOneType = value; + + DeltaEnemies(oldType, newType); + } + } + + public bool WaitingForEnemy{ get; set; } + + private void DeltaEnemies(Type oldType, Type newType) + { + foreach (Mobile m in GetMobilesInRange(18)) + { + Type t = m.GetType(); + + if (t == oldType || t == newType) + { + NetState ns = NetState; + + if (ns != null) + { + if (ns.StygianAbyss) + ns.Send(new MobileMoving(m, Notoriety.Compute(this, m))); + else + ns.Send(new MobileMovingOld(m, Notoriety.Compute(this, m))); + } + } + } + } + + #endregion + + #region Hair and beard mods + + private int m_HairModID = -1, m_HairModHue; + private int m_BeardModID = -1, m_BeardModHue; + + public void SetHairMods(int hairID, int beardID) + { + if (hairID == -1) + InternalRestoreHair(true, ref m_HairModID, ref m_HairModHue); + else if (hairID != -2) + InternalChangeHair(true, hairID, ref m_HairModID, ref m_HairModHue); + + if (beardID == -1) + InternalRestoreHair(false, ref m_BeardModID, ref m_BeardModHue); + else if (beardID != -2) + InternalChangeHair(false, beardID, ref m_BeardModID, ref m_BeardModHue); + } + + private void CreateHair(bool hair, int id, int hue) + { + if (hair) + { + //TODO Verification? + HairItemID = id; + HairHue = hue; + } + else + { + FacialHairItemID = id; + FacialHairHue = hue; + } + } + + private void InternalRestoreHair(bool hair, ref int id, ref int hue) + { + if (id == -1) + return; + + if (hair) + HairItemID = 0; + else + FacialHairItemID = 0; + + //if ( id != 0 ) + CreateHair(hair, id, hue); + + id = -1; + hue = 0; + } + + private void InternalChangeHair(bool hair, int id, ref int storeID, ref int storeHue) + { + if (storeID == -1) + { + storeID = hair ? HairItemID : FacialHairItemID; + storeHue = hair ? HairHue : FacialHairHue; + } + + CreateHair(hair, id, 0); + } + + #endregion + + #region Virtues + + public DateTime LastSacrificeGain{ get; set; } + + public DateTime LastSacrificeLoss{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int AvailableResurrects{ get; set; } + + private DateTime m_NextJustAward; + + public DateTime LastJusticeLoss{ get; set; } + + public List JusticeProtectors{ get; set; } + + public DateTime LastCompassionLoss{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextCompassionDay{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int CompassionGains{ get; set; } + + public DateTime LastValorLoss{ get; set; } + + public DateTime m_hontime; + + public DateTime LastHonorLoss{ get; set; } + + public DateTime LastHonorUse{ get; set; } + + public bool HonorActive{ get; set; } + + public HonorContext ReceivedHonorContext{ get; set; } + + public HonorContext SentHonorContext{ get; set; } + + #endregion + + #region Young system + + [CommandProperty(AccessLevel.GameMaster)] + public bool Young + { + get => GetFlag(PlayerFlag.Young); + set + { + SetFlag(PlayerFlag.Young, value); + InvalidateProperties(); + } + } + + public override string ApplyNameSuffix(string suffix) + { + if (Young) + { + if (suffix.Length == 0) + suffix = "(Young)"; + else + suffix = string.Concat(suffix, " (Young)"); + } + + #region Ethics + + if (EthicPlayer != null) + { + if (suffix.Length == 0) + suffix = EthicPlayer.Ethic.Definition.Adjunct.String; + else + suffix = string.Concat(suffix, " ", EthicPlayer.Ethic.Definition.Adjunct.String); + } + + #endregion + + if (Core.ML && Map == Faction.Facet) + { + Faction faction = Faction.Find(this); + + if (faction != null) + { + string adjunct = $"[{faction.Definition.Abbreviation}]"; + if (suffix.Length == 0) + suffix = adjunct; + else + suffix = string.Concat(suffix, " ", adjunct); + } + } + + return base.ApplyNameSuffix(suffix); + } + + public override TimeSpan GetLogoutDelay() + { + if (Young || BedrollLogout || TestCenter.Enabled) + return TimeSpan.Zero; + + return base.GetLogoutDelay(); + } + + private DateTime m_LastYoungMessage = DateTime.MinValue; + + public bool CheckYoungProtection(Mobile from) + { + if (!Young) + return false; + + if (Region is BaseRegion region && !region.YoungProtected) + return false; + + if (from is BaseCreature creature && creature.IgnoreYoungProtection) + return false; + + if (Quest != null && Quest.IgnoreYoungProtection(from)) + return false; + + if (DateTime.UtcNow - m_LastYoungMessage > TimeSpan.FromMinutes(1.0)) + { + m_LastYoungMessage = DateTime.UtcNow; + SendLocalizedMessage( + 1019067); // A monster looks at you menacingly but does not attack. You would be under attack now if not for your status as a new citizen of Britannia. + } + + return true; + } + + private DateTime m_LastYoungHeal = DateTime.MinValue; + + public bool CheckYoungHealTime() + { + if (DateTime.UtcNow - m_LastYoungHeal > TimeSpan.FromMinutes(5.0)) + { + m_LastYoungHeal = DateTime.UtcNow; + return true; + } + + return false; + } + + private static Point3D[] m_TrammelDeathDestinations = + { + new Point3D(1481, 1612, 20), + new Point3D(2708, 2153, 0), + new Point3D(2249, 1230, 0), + new Point3D(5197, 3994, 37), + new Point3D(1412, 3793, 0), + new Point3D(3688, 2232, 20), + new Point3D(2578, 604, 0), + new Point3D(4397, 1089, 0), + new Point3D(5741, 3218, -2), + new Point3D(2996, 3441, 15), + new Point3D(624, 2225, 0), + new Point3D(1916, 2814, 0), + new Point3D(2929, 854, 0), + new Point3D(545, 967, 0), + new Point3D(3665, 2587, 0) + }; + + private static Point3D[] m_IlshenarDeathDestinations = + { + new Point3D(1216, 468, -13), + new Point3D(723, 1367, -60), + new Point3D(745, 725, -28), + new Point3D(281, 1017, 0), + new Point3D(986, 1011, -32), + new Point3D(1175, 1287, -30), + new Point3D(1533, 1341, -3), + new Point3D(529, 217, -44), + new Point3D(1722, 219, 96) + }; + + private static Point3D[] m_MalasDeathDestinations = + { + new Point3D(2079, 1376, -70), + new Point3D(944, 519, -71) + }; + + private static Point3D[] m_TokunoDeathDestinations = + { + new Point3D(1166, 801, 27), + new Point3D(782, 1228, 25), + new Point3D(268, 624, 15) + }; + + public bool YoungDeathTeleport() + { + if (Region.IsPartOf(typeof(Jail)) + || Region.IsPartOf("Samurai start location") + || Region.IsPartOf("Ninja start location") + || Region.IsPartOf("Ninja cave")) + return false; + + Point3D loc; + Map map; + + DungeonRegion dungeon = (DungeonRegion)Region.GetRegion(typeof(DungeonRegion)); + if (dungeon != null && dungeon.EntranceLocation != Point3D.Zero) + { + loc = dungeon.EntranceLocation; + map = dungeon.EntranceMap; + } + else + { + loc = Location; + map = Map; + } + + Point3D[] list; + + if (map == Map.Trammel) + list = m_TrammelDeathDestinations; + else if (map == Map.Ilshenar) + list = m_IlshenarDeathDestinations; + else if (map == Map.Malas) + list = m_MalasDeathDestinations; + else if (map == Map.Tokuno) + list = m_TokunoDeathDestinations; + else + return false; + + Point3D dest = Point3D.Zero; + int sqDistance = int.MaxValue; + + for (int i = 0; i < list.Length; i++) + { + Point3D curDest = list[i]; + + int width = loc.X - curDest.X; + int height = loc.Y - curDest.Y; + int curSqDistance = width * width + height * height; + + if (curSqDistance < sqDistance) + { + dest = curDest; + sqDistance = curSqDistance; + } + } + + MoveToWorld(dest, map); + return true; + } + + private void SendYoungDeathNotice() + { + SendGump(new YoungDeathNotice()); + } + + #endregion + + #region Speech log + + public SpeechLog SpeechLog{ get; private set; } + + public override void OnSpeech(SpeechEventArgs e) + { + if (SpeechLog.Enabled && NetState != null) + { + if (SpeechLog == null) + SpeechLog = new SpeechLog(); + + SpeechLog.Add(e.Mobile, e.Speech); + } + } + + #endregion + + #region Champion Titles + + [CommandProperty(AccessLevel.GameMaster)] + public bool DisplayChampionTitle + { + get => GetFlag(PlayerFlag.DisplayChampionTitle); + set => SetFlag(PlayerFlag.DisplayChampionTitle, value); + } + + private ChampionTitleInfo m_ChampionTitles; + + [CommandProperty(AccessLevel.GameMaster)] + public ChampionTitleInfo ChampionTitles + { + get => m_ChampionTitles; + set { } + } + + private void ToggleChampionTitleDisplay() + { + if (!CheckAlive()) + return; + + if (DisplayChampionTitle) + SendLocalizedMessage(1062419, "", 0x23); // You have chosen to hide your monster kill title. + else + SendLocalizedMessage(1062418, "", 0x23); // You have chosen to display your monster kill title. + + DisplayChampionTitle = !DisplayChampionTitle; + } + + [PropertyObject] + public class ChampionTitleInfo + { + public const int LossAmount = 90; + public static TimeSpan LossDelay = TimeSpan.FromDays(1.0); + + private TitleInfo[] m_Values; + + public ChampionTitleInfo() + { + } + + public ChampionTitleInfo(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 0: + { + Harrower = reader.ReadEncodedInt(); + + int length = reader.ReadEncodedInt(); + m_Values = new TitleInfo[length]; + + for (int i = 0; i < length; i++) m_Values[i] = new TitleInfo(reader); + + if (m_Values.Length != ChampionSpawnInfo.Table.Length) + { + TitleInfo[] oldValues = m_Values; + m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; + + for (int i = 0; i < m_Values.Length && i < oldValues.Length; i++) m_Values[i] = oldValues[i]; + } + + break; + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Pestilence + { + get => GetValue(ChampionSpawnType.Pestilence); + set => SetValue(ChampionSpawnType.Pestilence, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Abyss + { + get => GetValue(ChampionSpawnType.Abyss); + set => SetValue(ChampionSpawnType.Abyss, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Arachnid + { + get => GetValue(ChampionSpawnType.Arachnid); + set => SetValue(ChampionSpawnType.Arachnid, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ColdBlood + { + get => GetValue(ChampionSpawnType.ColdBlood); + set => SetValue(ChampionSpawnType.ColdBlood, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ForestLord + { + get => GetValue(ChampionSpawnType.ForestLord); + set => SetValue(ChampionSpawnType.ForestLord, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SleepingDragon + { + get => GetValue(ChampionSpawnType.SleepingDragon); + set => SetValue(ChampionSpawnType.SleepingDragon, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int UnholyTerror + { + get => GetValue(ChampionSpawnType.UnholyTerror); + set => SetValue(ChampionSpawnType.UnholyTerror, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int VerminHorde + { + get => GetValue(ChampionSpawnType.VerminHorde); + set => SetValue(ChampionSpawnType.VerminHorde, value); + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Harrower{ get; set; } + + public int GetValue(ChampionSpawnType type) + { + return GetValue((int)type); + } + + public void SetValue(ChampionSpawnType type, int value) + { + SetValue((int)type, value); + } + + public void Award(ChampionSpawnType type, int value) + { + Award((int)type, value); + } + + public int GetValue(int index) + { + if (m_Values == null || index < 0 || index >= m_Values.Length) + return 0; + + if (m_Values[index] == null) + m_Values[index] = new TitleInfo(); + + return m_Values[index].Value; + } + + public DateTime GetLastDecay(int index) + { + if (m_Values == null || index < 0 || index >= m_Values.Length) + return DateTime.MinValue; + + if (m_Values[index] == null) + m_Values[index] = new TitleInfo(); + + return m_Values[index].LastDecay; + } + + public void SetValue(int index, int value) + { + if (m_Values == null) + m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; + + if (value < 0) + value = 0; + + if (index < 0 || index >= m_Values.Length) + return; + + if (m_Values[index] == null) + m_Values[index] = new TitleInfo(); + + m_Values[index].Value = value; + } + + public void Award(int index, int value) + { + if (m_Values == null) + m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; + + if (index < 0 || index >= m_Values.Length || value <= 0) + return; + + if (m_Values[index] == null) + m_Values[index] = new TitleInfo(); + + m_Values[index].Value += value; + } + + public void Atrophy(int index, int value) + { + if (m_Values == null) + m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; + + if (index < 0 || index >= m_Values.Length || value <= 0) + return; + + if (m_Values[index] == null) + m_Values[index] = new TitleInfo(); + + int before = m_Values[index].Value; + + if (m_Values[index].Value - value < 0) + m_Values[index].Value = 0; + else + m_Values[index].Value -= value; + + if (before != m_Values[index].Value) + m_Values[index].LastDecay = DateTime.UtcNow; + } + + public override string ToString() + { + return "..."; + } + + public static void Serialize(GenericWriter writer, ChampionTitleInfo titles) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(titles.Harrower); + + int length = titles.m_Values.Length; + writer.WriteEncodedInt(length); + + for (int i = 0; i < length; i++) + { + if (titles.m_Values[i] == null) + titles.m_Values[i] = new TitleInfo(); + + TitleInfo.Serialize(writer, titles.m_Values[i]); + } + } + + public static void CheckAtrophy(PlayerMobile pm) + { + ChampionTitleInfo t = pm.m_ChampionTitles; + if (t == null) + return; + + if (t.m_Values == null) + t.m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; + + for (int i = 0; i < t.m_Values.Length; i++) + if (t.GetLastDecay(i) + LossDelay < DateTime.UtcNow) + t.Atrophy(i, LossAmount); + } + + public static void + AwardHarrowerTitle(PlayerMobile pm) //Called when killing a harrower. Will give a minimum of 1 point. + { + ChampionTitleInfo t = pm.m_ChampionTitles; + if (t == null) + return; + + if (t.m_Values == null) + t.m_Values = new TitleInfo[ChampionSpawnInfo.Table.Length]; + + int count = 1; + + for (int i = 0; i < t.m_Values.Length; i++) + if (t.m_Values[i].Value > 900) + count++; + + t.Harrower = Math.Max(count, t.Harrower); //Harrower titles never decay. + } + + private class TitleInfo + { + public TitleInfo() + { + } + + public TitleInfo(GenericReader reader) + { + int version = reader.ReadEncodedInt(); + + switch (version) + { + case 0: + { + Value = reader.ReadEncodedInt(); + LastDecay = reader.ReadDateTime(); + break; + } + } + } + + public int Value{ get; set; } + + public DateTime LastDecay{ get; set; } + + public static void Serialize(GenericWriter writer, TitleInfo info) + { + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(info.Value); + writer.Write(info.LastDecay); + } + } + } + + #endregion + + #region Recipes + + private Dictionary m_AcquiredRecipes; + + public virtual bool HasRecipe(Recipe r) + { + if (r == null) + return false; + + return HasRecipe(r.ID); + } + + public virtual bool HasRecipe(int recipeID) + { + if (m_AcquiredRecipes != null && m_AcquiredRecipes.ContainsKey(recipeID)) + return m_AcquiredRecipes[recipeID]; + + return false; + } + + public virtual void AcquireRecipe(Recipe r) + { + if (r != null) + AcquireRecipe(r.ID); + } + + public virtual void AcquireRecipe(int recipeID) + { + if (m_AcquiredRecipes == null) + m_AcquiredRecipes = new Dictionary(); + + m_AcquiredRecipes[recipeID] = true; + } + + public virtual void ResetRecipes() + { + m_AcquiredRecipes = null; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int KnownRecipes + { + get + { + if (m_AcquiredRecipes == null) + return 0; + + return m_AcquiredRecipes.Count; + } + } + + #endregion + + #region Buff Icons + + public void ResendBuffs() + { + if (!BuffInfo.Enabled || m_BuffTable == null) + return; + + NetState state = NetState; + + if (state != null && state.BuffIcon) + foreach (BuffInfo info in m_BuffTable.Values) + state.Send(new AddBuffPacket(this, info)); + } + + private Dictionary m_BuffTable; + + public void AddBuff(BuffInfo b) + { + if (!BuffInfo.Enabled || b == null) + return; + + RemoveBuff(b); //Check & subsequently remove the old one. + + if (m_BuffTable == null) + m_BuffTable = new Dictionary(); + + m_BuffTable.Add(b.ID, b); + + NetState state = NetState; + + if (state != null && state.BuffIcon) state.Send(new AddBuffPacket(this, b)); + } + + public void RemoveBuff(BuffInfo b) + { + if (b == null) + return; + + RemoveBuff(b.ID); + } + + public void RemoveBuff(BuffIcon b) + { + if (m_BuffTable == null || !m_BuffTable.ContainsKey(b)) + return; + + BuffInfo info = m_BuffTable[b]; + + if (info.Timer != null && info.Timer.Running) + info.Timer.Stop(); + + m_BuffTable.Remove(b); + + NetState state = NetState; + + if (state != null && state.BuffIcon) state.Send(new RemoveBuffPacket(this, b)); + + if (m_BuffTable.Count <= 0) + m_BuffTable = null; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Barracoon.cs b/Scripts/Mobiles/Special/Barracoon.cs index ff8067203..9927f0ce5 100644 --- a/Scripts/Mobiles/Special/Barracoon.cs +++ b/Scripts/Mobiles/Special/Barracoon.cs @@ -1,240 +1,250 @@ using System; -using Server.Items; -using Server.Spells.Seventh; -using Server.Spells.Fifth; using Server.Engines.CannedEvil; +using Server.Items; +using Server.Spells.Fifth; +using Server.Spells.Seventh; namespace Server.Mobiles { - public class Barracoon : BaseChampion - { - public override ChampionSkullType SkullType => ChampionSkullType.Greed; + public class Barracoon : BaseChampion + { + [Constructible] + public Barracoon() : base(AIType.AI_Melee) + { + Title = "the piper"; + Body = 0x190; + Hue = 0x83EC; - public override Type[] UniqueList => new[] { typeof( FangOfRactus ) }; - public override Type[] SharedList => new[] { typeof( EmbroideredOakLeafCloak ), - typeof( DjinnisRing ), - typeof( DetectiveBoots ), - typeof( GuantletsOfAnger ) }; + SetStr(305, 425); + SetDex(72, 150); + SetInt(505, 750); - public override Type[] DecorativeList => new[] { typeof( SwampTile ), typeof( MonsterStatuette ) }; + SetHits(4200); + SetStam(102, 300); - public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.Slime }; + SetDamage(25, 35); - public override string DefaultName => "Barracoon"; + SetDamageType(ResistanceType.Physical, 100); - [Constructible] - public Barracoon() : base( AIType.AI_Melee ) - { - Title = "the piper"; - Body = 0x190; - Hue = 0x83EC; + SetResistance(ResistanceType.Physical, 60, 70); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetStr( 305, 425 ); - SetDex( 72, 150 ); - SetInt( 505, 750 ); + SetSkill(SkillName.MagicResist, 100.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - SetHits( 4200 ); - SetStam( 102, 300 ); + Fame = 22500; + Karma = -22500; - SetDamage( 25, 35 ); + VirtualArmor = 70; - SetDamageType( ResistanceType.Physical, 100 ); + AddItem(new FancyShirt(Utility.RandomGreenHue())); + AddItem(new LongPants(Utility.RandomYellowHue())); + AddItem(new JesterHat(Utility.RandomPinkHue())); + AddItem(new Cloak(Utility.RandomPinkHue())); + AddItem(new Sandals()); - SetResistance( ResistanceType.Physical, 60, 70 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + HairItemID = 0x203B; // Short Hair + HairHue = 0x94; + } - SetSkill( SkillName.MagicResist, 100.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + public Barracoon(Serial serial) : base(serial) + { + } - Fame = 22500; - Karma = -22500; + public override ChampionSkullType SkullType => ChampionSkullType.Greed; - VirtualArmor = 70; + public override Type[] UniqueList => new[] { typeof(FangOfRactus) }; - AddItem( new FancyShirt( Utility.RandomGreenHue() ) ); - AddItem( new LongPants( Utility.RandomYellowHue() ) ); - AddItem( new JesterHat( Utility.RandomPinkHue() ) ); - AddItem( new Cloak( Utility.RandomPinkHue() ) ); - AddItem( new Sandals() ); + public override Type[] SharedList => new[] + { + typeof(EmbroideredOakLeafCloak), + typeof(DjinnisRing), + typeof(DetectiveBoots), + typeof(GuantletsOfAnger) + }; - HairItemID = 0x203B; // Short Hair - HairHue = 0x94; - } + public override Type[] DecorativeList => new[] { typeof(SwampTile), typeof(MonsterStatuette) }; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - } + public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.Slime }; - public override bool AlwaysMurderer => true; - public override bool AutoDispel => true; - public override double AutoDispelChance => 1.0; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool Uncalmable => Core.SE; - public override Poison PoisonImmune => Poison.Deadly; + public override string DefaultName => "Barracoon"; - public override bool ShowFameTitle => false; - public override bool ClickTitle => false; + public override bool AlwaysMurderer => true; + public override bool AutoDispel => true; + public override double AutoDispelChance => 1.0; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool Uncalmable => Core.SE; + public override Poison PoisonImmune => Poison.Deadly; - public void Polymorph( Mobile m ) - { - if ( !m.CanBeginAction( typeof( PolymorphSpell ) ) || !m.CanBeginAction( typeof( IncognitoSpell ) ) || m.IsBodyMod ) - return; + public override bool ShowFameTitle => false; + public override bool ClickTitle => false; - IMount mount = m.Mount; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + } - if ( mount != null ) - mount.Rider = null; + public void Polymorph(Mobile m) + { + if (!m.CanBeginAction(typeof(PolymorphSpell)) || !m.CanBeginAction(typeof(IncognitoSpell)) || m.IsBodyMod) + return; - if ( m.Mounted ) - return; + IMount mount = m.Mount; - if ( m.BeginAction( typeof( PolymorphSpell ) ) ) - { - Item disarm = m.FindItemOnLayer( Layer.OneHanded ); + if (mount != null) + mount.Rider = null; - if ( disarm != null && disarm.Movable ) - m.AddToBackpack( disarm ); + if (m.Mounted) + return; - disarm = m.FindItemOnLayer( Layer.TwoHanded ); + if (m.BeginAction(typeof(PolymorphSpell))) + { + Item disarm = m.FindItemOnLayer(Layer.OneHanded); - if ( disarm != null && disarm.Movable ) - m.AddToBackpack( disarm ); + if (disarm != null && disarm.Movable) + m.AddToBackpack(disarm); - m.BodyMod = 42; - m.HueMod = 0; + disarm = m.FindItemOnLayer(Layer.TwoHanded); - new ExpirePolymorphTimer( m ).Start(); - } - } + if (disarm != null && disarm.Movable) + m.AddToBackpack(disarm); - private class ExpirePolymorphTimer : Timer - { - private Mobile m_Owner; + m.BodyMod = 42; + m.HueMod = 0; - public ExpirePolymorphTimer( Mobile owner ) : base( TimeSpan.FromMinutes( 3.0 ) ) - { - m_Owner = owner; + new ExpirePolymorphTimer(m).Start(); + } + } - Priority = TimerPriority.OneSecond; - } + public void SpawnRatmen(Mobile target) + { + Map map = Map; - protected override void OnTick() - { - if ( !m_Owner.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - m_Owner.BodyMod = 0; - m_Owner.HueMod = -1; - m_Owner.EndAction( typeof( PolymorphSpell ) ); - } - } - } + if (map == null) + return; - public void SpawnRatmen( Mobile target ) - { - Map map = Map; + int rats = 0; - if ( map == null ) - return; + foreach (Mobile m in GetMobilesInRange(10)) + if (m is Ratman || m is RatmanArcher || m is RatmanMage) + ++rats; - int rats = 0; + if (rats < 16) + { + PlaySound(0x3D); - foreach ( Mobile m in GetMobilesInRange( 10 ) ) - { - if ( m is Ratman || m is RatmanArcher || m is RatmanMage ) - ++rats; - } + int newRats = Utility.RandomMinMax(3, 6); - if ( rats < 16 ) - { - PlaySound( 0x3D ); + for (int i = 0; i < newRats; ++i) + { + BaseCreature rat; - int newRats = Utility.RandomMinMax( 3, 6 ); + switch (Utility.Random(5)) + { + default: + case 0: + case 1: + rat = new Ratman(); + break; + case 2: + case 3: + rat = new RatmanArcher(); + break; + case 4: + rat = new RatmanMage(); + break; + } - for ( int i = 0; i < newRats; ++i ) - { - BaseCreature rat; + rat.Team = Team; - switch ( Utility.Random( 5 ) ) - { - default: - case 0: case 1: rat = new Ratman(); break; - case 2: case 3: rat = new RatmanArcher(); break; - case 4: rat = new RatmanMage(); break; - } + bool validLocation = false; + Point3D loc = Location; - rat.Team = Team; + for (int j = 0; !validLocation && j < 10; ++j) + { + int x = X + Utility.Random(3) - 1; + int y = Y + Utility.Random(3) - 1; + int z = map.GetAverageZ(x, y); - bool validLocation = false; - Point3D loc = Location; + if (validLocation = map.CanFit(x, y, Z, 16, false, false)) + loc = new Point3D(x, y, Z); + else if (validLocation = map.CanFit(x, y, z, 16, false, false)) + loc = new Point3D(x, y, z); + } - for ( int j = 0; !validLocation && j < 10; ++j ) - { - int x = X + Utility.Random( 3 ) - 1; - int y = Y + Utility.Random( 3 ) - 1; - int z = map.GetAverageZ( x, y ); + rat.MoveToWorld(loc, map); + rat.Combatant = target; + } + } + } - if ( validLocation = map.CanFit( x, y, Z, 16, false, false ) ) - loc = new Point3D( x, y, Z ); - else if ( validLocation = map.CanFit( x, y, z, 16, false, false ) ) - loc = new Point3D( x, y, z ); - } + public void DoSpecialAbility(Mobile target) + { + if (target == null || target.Deleted) //sanity + return; + if (0.6 >= Utility.RandomDouble()) // 60% chance to polymorph attacker into a ratman + Polymorph(target); - rat.MoveToWorld( loc, map ); - rat.Combatant = target; - } - } - } + if (0.2 >= Utility.RandomDouble()) // 20% chance to more ratmen + SpawnRatmen(target); - public void DoSpecialAbility( Mobile target ) - { - if ( target == null || target.Deleted ) //sanity - return; - if ( 0.6 >= Utility.RandomDouble() ) // 60% chance to polymorph attacker into a ratman - Polymorph( target ); + if (Hits < 500 && !IsBodyMod) // Baracoon is low on life, polymorph into a ratman + Polymorph(this); + } - if ( 0.2 >= Utility.RandomDouble() ) // 20% chance to more ratmen - SpawnRatmen( target ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - if ( Hits < 500 && !IsBodyMod ) // Baracoon is low on life, polymorph into a ratman - Polymorph( this ); - } + DoSpecialAbility(attacker); + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - DoSpecialAbility( attacker ); - } + DoSpecialAbility(defender); + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - DoSpecialAbility( defender ); - } + writer.Write(0); // version + } - public Barracoon( Serial serial ) : base( serial ) - { - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + int version = reader.ReadInt(); + } - writer.Write( (int) 0 ); // version - } + private class ExpirePolymorphTimer : Timer + { + private Mobile m_Owner; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public ExpirePolymorphTimer(Mobile owner) : base(TimeSpan.FromMinutes(3.0)) + { + m_Owner = owner; - int version = reader.ReadInt(); - } - } -} + Priority = TimerPriority.OneSecond; + } + + protected override void OnTick() + { + if (!m_Owner.CanBeginAction(typeof(PolymorphSpell))) + { + m_Owner.BodyMod = 0; + m_Owner.HueMod = -1; + m_Owner.EndAction(typeof(PolymorphSpell)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/BaseChampion.cs b/Scripts/Mobiles/Special/BaseChampion.cs index f6c98bd0e..546664dbb 100644 --- a/Scripts/Mobiles/Special/BaseChampion.cs +++ b/Scripts/Mobiles/Special/BaseChampion.cs @@ -1,326 +1,331 @@ using System; using System.Collections.Generic; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public abstract class BaseChampion : BaseCreature - { - public override bool CanMoveOverObstacles => true; - public override bool CanDestroyObstacles => true; + public abstract class BaseChampion : BaseCreature + { + public BaseChampion(AIType aiType) : this(aiType, FightMode.Closest) + { + } - public BaseChampion( AIType aiType ) : this( aiType, FightMode.Closest ) - { - } + public BaseChampion(AIType aiType, FightMode mode) : base(aiType, mode, 18, 1, 0.1, 0.2) + { + } - public BaseChampion( AIType aiType, FightMode mode ) : base( aiType, mode, 18, 1, 0.1, 0.2 ) - { - } + public BaseChampion(Serial serial) : base(serial) + { + } - public BaseChampion( Serial serial ) : base( serial ) - { - } + public override bool CanMoveOverObstacles => true; + public override bool CanDestroyObstacles => true; - public abstract ChampionSkullType SkullType{ get; } + public abstract ChampionSkullType SkullType{ get; } - public abstract Type[] UniqueList{ get; } - public abstract Type[] SharedList{ get; } - public abstract Type[] DecorativeList{ get; } - public abstract MonsterStatuetteType[] StatueTypes{ get; } + public abstract Type[] UniqueList{ get; } + public abstract Type[] SharedList{ get; } + public abstract Type[] DecorativeList{ get; } + public abstract MonsterStatuetteType[] StatueTypes{ get; } - public virtual bool NoGoodies => false; + public virtual bool NoGoodies => false; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - - public Item GetArtifact() - { - double random = Utility.RandomDouble(); - if ( 0.05 >= random ) - return CreateArtifact( UniqueList ); - if ( 0.15 >= random ) - return CreateArtifact( SharedList ); - if ( 0.30 >= random ) - return CreateArtifact( DecorativeList ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + + public Item GetArtifact() + { + double random = Utility.RandomDouble(); + if (0.05 >= random) + return CreateArtifact(UniqueList); + if (0.15 >= random) + return CreateArtifact(SharedList); + if (0.30 >= random) + return CreateArtifact(DecorativeList); - return null; - } + return null; + } - public Item CreateArtifact( Type[] list ) - { - if ( list.Length == 0 ) - return null; + public Item CreateArtifact(Type[] list) + { + if (list.Length == 0) + return null; - int random = Utility.Random( list.Length ); - - Type type = list[random]; - - Item artifact = Loot.Construct( type ); - - if ( artifact is MonsterStatuette && StatueTypes.Length > 0 ) - { - ((MonsterStatuette)artifact).Type = StatueTypes[Utility.Random( StatueTypes.Length )]; - ((MonsterStatuette)artifact).LootType = LootType.Regular; - } - - return artifact; - } - - private PowerScroll CreateRandomPowerScroll() - { - int level; - double random = Utility.RandomDouble(); - - if ( 0.05 >= random ) - level = 20; - else if ( 0.4 >= random ) - level = 15; - else - level = 10; - - return PowerScroll.CreateRandomNoCraft( level, level ); - } - - public void GivePowerScrolls() - { - if ( Map != Map.Felucca ) - return; - - List toGive = new List(); - List rights = GetLootingRights( DamageEntries, HitsMax ); - - for ( int i = rights.Count - 1; i >= 0; --i ) - { - DamageStore ds = rights[i]; - - if ( ds.m_HasRight ) - toGive.Add( ds.m_Mobile ); - } - - if ( toGive.Count == 0 ) - return; - - for( int i = 0; i < toGive.Count; i++ ) - { - Mobile m = toGive[i]; - - if ( !(m is PlayerMobile) ) - continue; - - bool gainedPath = false; - - int pointsToGain = 800; - - if ( VirtueHelper.Award( m, VirtueName.Valor, pointsToGain, ref gainedPath ) ) - { - if ( gainedPath ) - m.SendLocalizedMessage( 1054032 ); // You have gained a path in Valor! - else - m.SendLocalizedMessage( 1054030 ); // You have gained in Valor! - - //No delay on Valor gains - } - } - - // Randomize - for ( int i = 0; i < toGive.Count; ++i ) - { - int rand = Utility.Random( toGive.Count ); - Mobile hold = toGive[i]; - toGive[i] = toGive[rand]; - toGive[rand] = hold; - } - - for ( int i = 0; i < 6; ++i ) - { - Mobile m = toGive[i % toGive.Count]; - - PowerScroll ps = CreateRandomPowerScroll(); - - GivePowerScrollTo( m, ps ); - } - } - - public static void GivePowerScrollTo( Mobile m, PowerScroll ps ) - { - if ( ps == null || m == null ) //sanity - return; - - m.SendLocalizedMessage( 1049524 ); // You have received a scroll of power! - - if ( !Core.SE || m.Alive ) - m.AddToBackpack( ps ); - else - { - if ( m.Corpse != null && !m.Corpse.Deleted ) - m.Corpse.DropItem( ps ); - else - m.AddToBackpack( ps ); - } - - if ( m is PlayerMobile pm ) - { - for( int j = 0; j < pm.JusticeProtectors.Count; ++j ) - { - Mobile prot = pm.JusticeProtectors[j]; - - if ( prot.Map != pm.Map || prot.Kills >= 5 || prot.Criminal || !JusticeVirtue.CheckMapRegion( pm, prot ) ) - continue; - - int chance = 0; - - switch( VirtueHelper.GetLevel( prot, VirtueName.Justice ) ) - { - case VirtueLevel.Seeker: chance = 60; break; - case VirtueLevel.Follower: chance = 80; break; - case VirtueLevel.Knight: chance = 100; break; - } - - if ( chance > Utility.Random( 100 ) ) - { - PowerScroll powerScroll = new PowerScroll( ps.Skill, ps.Value ); - - prot.SendLocalizedMessage( 1049368 ); // You have been rewarded for your dedication to Justice! - - if ( !Core.SE || prot.Alive ) - prot.AddToBackpack( powerScroll ); - else - { - if ( prot.Corpse != null && !prot.Corpse.Deleted ) - prot.Corpse.DropItem( powerScroll ); - else - prot.AddToBackpack( powerScroll ); - } - } - } - } - } - - public override bool OnBeforeDeath() - { - if ( !NoKillAwards ) - { - GivePowerScrolls(); - - if ( NoGoodies ) - return base.OnBeforeDeath(); - - Map map = Map; - - if ( map != null ) - { - for ( int x = -12; x <= 12; ++x ) - { - for ( int y = -12; y <= 12; ++y ) - { - double dist = Math.Sqrt(x*x+y*y); - - if ( dist <= 12 ) - new GoodiesTimer( map, X + x, Y + y ).Start(); - } - } - } - } - - return base.OnBeforeDeath(); - } - - public override void OnDeath( Container c ) - { - if ( Map == Map.Felucca ) - { - //TODO: Confirm SE change or AoS one too? - List rights = GetLootingRights( DamageEntries, HitsMax ); - List toGive = new List(); - - for ( int i = rights.Count - 1; i >= 0; --i ) - { - DamageStore ds = rights[i]; - - if ( ds.m_HasRight ) - toGive.Add( ds.m_Mobile ); - } - - if ( toGive.Count > 0 ) - toGive[Utility.Random( toGive.Count )].AddToBackpack( new ChampionSkull( SkullType ) ); - else - c.DropItem( new ChampionSkull( SkullType ) ); - } - - base.OnDeath( c ); - } - - private class GoodiesTimer : Timer - { - private Map m_Map; - private int m_X, m_Y; - - public GoodiesTimer( Map map, int x, int y ) : base( TimeSpan.FromSeconds( Utility.RandomDouble() * 10.0 ) ) - { - m_Map = map; - m_X = x; - m_Y = y; - } - - protected override void OnTick() - { - int z = m_Map.GetAverageZ( m_X, m_Y ); - bool canFit = m_Map.CanFit( m_X, m_Y, z, 6, false, false ); - - for ( int i = -3; !canFit && i <= 3; ++i ) - { - canFit = m_Map.CanFit( m_X, m_Y, z + i, 6, false, false ); - - if ( canFit ) - z += i; - } - - if ( !canFit ) - return; - - Gold g = new Gold( 500, 1000 ); - - g.MoveToWorld( new Point3D( m_X, m_Y, z ), m_Map ); - - if ( 0.5 >= Utility.RandomDouble() ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: // Fire column - { - Effects.SendLocationParticles( EffectItem.Create( g.Location, g.Map, EffectItem.DefaultDuration ), 0x3709, 10, 30, 5052 ); - Effects.PlaySound( g, g.Map, 0x208 ); - - break; - } - case 1: // Explosion - { - Effects.SendLocationParticles( EffectItem.Create( g.Location, g.Map, EffectItem.DefaultDuration ), 0x36BD, 20, 10, 5044 ); - Effects.PlaySound( g, g.Map, 0x307 ); - - break; - } - case 2: // Ball of fire - { - Effects.SendLocationParticles( EffectItem.Create( g.Location, g.Map, EffectItem.DefaultDuration ), 0x36FE, 10, 10, 5052 ); - - break; - } - } - } - } - } - } -} + int random = Utility.Random(list.Length); + + Type type = list[random]; + + Item artifact = Loot.Construct(type); + + if (artifact is MonsterStatuette && StatueTypes.Length > 0) + { + ((MonsterStatuette)artifact).Type = StatueTypes[Utility.Random(StatueTypes.Length)]; + ((MonsterStatuette)artifact).LootType = LootType.Regular; + } + + return artifact; + } + + private PowerScroll CreateRandomPowerScroll() + { + int level; + double random = Utility.RandomDouble(); + + if (0.05 >= random) + level = 20; + else if (0.4 >= random) + level = 15; + else + level = 10; + + return PowerScroll.CreateRandomNoCraft(level, level); + } + + public void GivePowerScrolls() + { + if (Map != Map.Felucca) + return; + + List toGive = new List(); + List rights = GetLootingRights(DamageEntries, HitsMax); + + for (int i = rights.Count - 1; i >= 0; --i) + { + DamageStore ds = rights[i]; + + if (ds.m_HasRight) + toGive.Add(ds.m_Mobile); + } + + if (toGive.Count == 0) + return; + + for (int i = 0; i < toGive.Count; i++) + { + Mobile m = toGive[i]; + + if (!(m is PlayerMobile)) + continue; + + bool gainedPath = false; + + int pointsToGain = 800; + + if (VirtueHelper.Award(m, VirtueName.Valor, pointsToGain, ref gainedPath)) + { + if (gainedPath) + m.SendLocalizedMessage(1054032); // You have gained a path in Valor! + else + m.SendLocalizedMessage(1054030); // You have gained in Valor! + + //No delay on Valor gains + } + } + + // Randomize + for (int i = 0; i < toGive.Count; ++i) + { + int rand = Utility.Random(toGive.Count); + Mobile hold = toGive[i]; + toGive[i] = toGive[rand]; + toGive[rand] = hold; + } + + for (int i = 0; i < 6; ++i) + { + Mobile m = toGive[i % toGive.Count]; + + PowerScroll ps = CreateRandomPowerScroll(); + + GivePowerScrollTo(m, ps); + } + } + + public static void GivePowerScrollTo(Mobile m, PowerScroll ps) + { + if (ps == null || m == null) //sanity + return; + + m.SendLocalizedMessage(1049524); // You have received a scroll of power! + + if (!Core.SE || m.Alive) + { + m.AddToBackpack(ps); + } + else + { + if (m.Corpse != null && !m.Corpse.Deleted) + m.Corpse.DropItem(ps); + else + m.AddToBackpack(ps); + } + + if (m is PlayerMobile pm) + for (int j = 0; j < pm.JusticeProtectors.Count; ++j) + { + Mobile prot = pm.JusticeProtectors[j]; + + if (prot.Map != pm.Map || prot.Kills >= 5 || prot.Criminal || !JusticeVirtue.CheckMapRegion(pm, prot)) + continue; + + int chance = 0; + + switch (VirtueHelper.GetLevel(prot, VirtueName.Justice)) + { + case VirtueLevel.Seeker: + chance = 60; + break; + case VirtueLevel.Follower: + chance = 80; + break; + case VirtueLevel.Knight: + chance = 100; + break; + } + + if (chance > Utility.Random(100)) + { + PowerScroll powerScroll = new PowerScroll(ps.Skill, ps.Value); + + prot.SendLocalizedMessage(1049368); // You have been rewarded for your dedication to Justice! + + if (!Core.SE || prot.Alive) + { + prot.AddToBackpack(powerScroll); + } + else + { + if (prot.Corpse != null && !prot.Corpse.Deleted) + prot.Corpse.DropItem(powerScroll); + else + prot.AddToBackpack(powerScroll); + } + } + } + } + + public override bool OnBeforeDeath() + { + if (!NoKillAwards) + { + GivePowerScrolls(); + + if (NoGoodies) + return base.OnBeforeDeath(); + + Map map = Map; + + if (map != null) + for (int x = -12; x <= 12; ++x) + for (int y = -12; y <= 12; ++y) + { + double dist = Math.Sqrt(x * x + y * y); + + if (dist <= 12) + new GoodiesTimer(map, X + x, Y + y).Start(); + } + } + + return base.OnBeforeDeath(); + } + + public override void OnDeath(Container c) + { + if (Map == Map.Felucca) + { + //TODO: Confirm SE change or AoS one too? + List rights = GetLootingRights(DamageEntries, HitsMax); + List toGive = new List(); + + for (int i = rights.Count - 1; i >= 0; --i) + { + DamageStore ds = rights[i]; + + if (ds.m_HasRight) + toGive.Add(ds.m_Mobile); + } + + if (toGive.Count > 0) + toGive[Utility.Random(toGive.Count)].AddToBackpack(new ChampionSkull(SkullType)); + else + c.DropItem(new ChampionSkull(SkullType)); + } + + base.OnDeath(c); + } + + private class GoodiesTimer : Timer + { + private Map m_Map; + private int m_X, m_Y; + + public GoodiesTimer(Map map, int x, int y) : base(TimeSpan.FromSeconds(Utility.RandomDouble() * 10.0)) + { + m_Map = map; + m_X = x; + m_Y = y; + } + + protected override void OnTick() + { + int z = m_Map.GetAverageZ(m_X, m_Y); + bool canFit = m_Map.CanFit(m_X, m_Y, z, 6, false, false); + + for (int i = -3; !canFit && i <= 3; ++i) + { + canFit = m_Map.CanFit(m_X, m_Y, z + i, 6, false, false); + + if (canFit) + z += i; + } + + if (!canFit) + return; + + Gold g = new Gold(500, 1000); + + g.MoveToWorld(new Point3D(m_X, m_Y, z), m_Map); + + if (0.5 >= Utility.RandomDouble()) + switch (Utility.Random(3)) + { + case 0: // Fire column + { + Effects.SendLocationParticles(EffectItem.Create(g.Location, g.Map, EffectItem.DefaultDuration), + 0x3709, 10, 30, 5052); + Effects.PlaySound(g, g.Map, 0x208); + + break; + } + case 1: // Explosion + { + Effects.SendLocationParticles(EffectItem.Create(g.Location, g.Map, EffectItem.DefaultDuration), + 0x36BD, 20, 10, 5044); + Effects.PlaySound(g, g.Map, 0x307); + + break; + } + case 2: // Ball of fire + { + Effects.SendLocationParticles(EffectItem.Create(g.Location, g.Map, EffectItem.DefaultDuration), + 0x36FE, 10, 10, 5052); + + break; + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/BaseShieldGuard.cs b/Scripts/Mobiles/Special/BaseShieldGuard.cs index 53686e3af..8154bba7b 100644 --- a/Scripts/Mobiles/Special/BaseShieldGuard.cs +++ b/Scripts/Mobiles/Special/BaseShieldGuard.cs @@ -1,148 +1,163 @@ -using Server.Items; using Server.Guilds; +using Server.Items; namespace Server.Mobiles { - public abstract class BaseShieldGuard : BaseCreature - { - public BaseShieldGuard() : base( AIType.AI_Melee, FightMode.Aggressor, 14, 1, 0.8, 1.6 ) - { - InitStats( 1000, 1000, 1000 ); - Title = "the guard"; + public abstract class BaseShieldGuard : BaseCreature + { + public BaseShieldGuard() : base(AIType.AI_Melee, FightMode.Aggressor, 14, 1, 0.8, 1.6) + { + InitStats(1000, 1000, 1000); + Title = "the guard"; - SpeechHue = Utility.RandomDyedHue(); + SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); - AddItem( new FemalePlateChest() ); - AddItem( new PlateArms() ); - AddItem( new PlateLegs() ); + AddItem(new FemalePlateChest()); + AddItem(new PlateArms()); + AddItem(new PlateLegs()); - switch( Utility.Random( 2 ) ) - { - case 0: AddItem( new Doublet( Utility.RandomNondyedHue() ) ); break; - case 1: AddItem( new BodySash( Utility.RandomNondyedHue() ) ); break; - } + switch (Utility.Random(2)) + { + case 0: + AddItem(new Doublet(Utility.RandomNondyedHue())); + break; + case 1: + AddItem(new BodySash(Utility.RandomNondyedHue())); + break; + } - switch( Utility.Random( 2 ) ) - { - case 0: AddItem( new Skirt( Utility.RandomNondyedHue() ) ); break; - case 1: AddItem( new Kilt( Utility.RandomNondyedHue() ) ); break; - } - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); + switch (Utility.Random(2)) + { + case 0: + AddItem(new Skirt(Utility.RandomNondyedHue())); + break; + case 1: + AddItem(new Kilt(Utility.RandomNondyedHue())); + break; + } + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); - AddItem( new PlateChest() ); - AddItem( new PlateArms() ); - AddItem( new PlateLegs() ); + AddItem(new PlateChest()); + AddItem(new PlateArms()); + AddItem(new PlateLegs()); - switch( Utility.Random( 3 ) ) - { - case 0: AddItem( new Doublet( Utility.RandomNondyedHue() ) ); break; - case 1: AddItem( new Tunic( Utility.RandomNondyedHue() ) ); break; - case 2: AddItem( new BodySash( Utility.RandomNondyedHue() ) ); break; - } - } + switch (Utility.Random(3)) + { + case 0: + AddItem(new Doublet(Utility.RandomNondyedHue())); + break; + case 1: + AddItem(new Tunic(Utility.RandomNondyedHue())); + break; + case 2: + AddItem(new BodySash(Utility.RandomNondyedHue())); + break; + } + } - Utility.AssignRandomHair( this ); - if ( Utility.RandomBool() ) - Utility.AssignRandomFacialHair( this, HairHue ); + Utility.AssignRandomHair(this); + if (Utility.RandomBool()) + Utility.AssignRandomFacialHair(this, HairHue); - VikingSword weapon = new VikingSword(); - weapon.Movable = false; - AddItem( weapon ); + VikingSword weapon = new VikingSword(); + weapon.Movable = false; + AddItem(weapon); - BaseShield shield = Shield; - shield.Movable = false; - AddItem( shield ); + BaseShield shield = Shield; + shield.Movable = false; + AddItem(shield); - PackGold( 250, 500 ); + PackGold(250, 500); - Skills[SkillName.Anatomy].Base = 120.0; - Skills[SkillName.Tactics].Base = 120.0; - Skills[SkillName.Swords].Base = 120.0; - Skills[SkillName.MagicResist].Base = 120.0; - Skills[SkillName.DetectHidden].Base = 100.0; - } + Skills[SkillName.Anatomy].Base = 120.0; + Skills[SkillName.Tactics].Base = 120.0; + Skills[SkillName.Swords].Base = 120.0; + Skills[SkillName.MagicResist].Base = 120.0; + Skills[SkillName.DetectHidden].Base = 100.0; + } - public abstract int Keyword{ get; } - public abstract BaseShield Shield{ get; } - public abstract int SignupNumber{ get; } - public abstract GuildType Type{ get; } + public BaseShieldGuard(Serial serial) : base(serial) + { + } - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - return true; + public abstract int Keyword{ get; } + public abstract BaseShield Shield{ get; } + public abstract int SignupNumber{ get; } + public abstract GuildType Type{ get; } - return base.HandlesOnSpeech( from ); - } + public override bool HandlesOnSpeech(Mobile from) + { + if (from.InRange(Location, 2)) + return true; - public override void OnSpeech( SpeechEventArgs e ) - { - if ( !e.Handled && e.HasKeyword( Keyword ) && e.Mobile.InRange( Location, 2 ) ) - { - e.Handled = true; + return base.HandlesOnSpeech(from); + } - Mobile from = e.Mobile; - Guild g = from.Guild as Guild; + public override void OnSpeech(SpeechEventArgs e) + { + if (!e.Handled && e.HasKeyword(Keyword) && e.Mobile.InRange(Location, 2)) + { + e.Handled = true; - if ( g == null || g.Type != Type ) - { - Say( SignupNumber ); - } - else - { - Container pack = from.Backpack; - BaseShield shield = Shield; - Item twoHanded = from.FindItemOnLayer( Layer.TwoHanded ); + Mobile from = e.Mobile; + Guild g = from.Guild as Guild; - if ( (pack?.FindItemByType( shield.GetType() ) != null) || ( twoHanded != null && shield.GetType().IsAssignableFrom( twoHanded.GetType() ) ) ) - { - Say( 1007110 ); // Why dost thou ask about virtue guards when thou art one? - shield.Delete(); - } - else if ( from.PlaceInBackpack( shield ) ) - { - Say( Utility.Random( 1007101, 5 ) ); - Say( 1007139 ); // I see you are in need of our shield, Here you go. - from.AddToBackpack( shield ); - } - else - { - from.SendLocalizedMessage( 502868 ); // Your backpack is too full. - shield.Delete(); - } - } - } + if (g == null || g.Type != Type) + { + Say(SignupNumber); + } + else + { + Container pack = from.Backpack; + BaseShield shield = Shield; + Item twoHanded = from.FindItemOnLayer(Layer.TwoHanded); - base.OnSpeech( e ); - } + if (pack?.FindItemByType(shield.GetType()) != null || + twoHanded != null && shield.GetType().IsAssignableFrom(twoHanded.GetType())) + { + Say(1007110); // Why dost thou ask about virtue guards when thou art one? + shield.Delete(); + } + else if (from.PlaceInBackpack(shield)) + { + Say(Utility.Random(1007101, 5)); + Say(1007139); // I see you are in need of our shield, Here you go. + from.AddToBackpack(shield); + } + else + { + from.SendLocalizedMessage(502868); // Your backpack is too full. + shield.Delete(); + } + } + } - public BaseShieldGuard( Serial serial ) : base( serial ) - { - } + base.OnSpeech(e); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/CapturedHordeMinion.cs b/Scripts/Mobiles/Special/CapturedHordeMinion.cs index f12d848dc..ac74633d9 100644 --- a/Scripts/Mobiles/Special/CapturedHordeMinion.cs +++ b/Scripts/Mobiles/Special/CapturedHordeMinion.cs @@ -1,36 +1,36 @@ namespace Server.Mobiles { - public class CapturedHordeMinion : HordeMinion - { - [Constructible] - public CapturedHordeMinion() - { - FightMode = FightMode.None; - } + public class CapturedHordeMinion : HordeMinion + { + [Constructible] + public CapturedHordeMinion() + { + FightMode = FightMode.None; + } - public override bool InitialInnocent => true; + public CapturedHordeMinion(Serial serial) : base(serial) + { + } - public override bool CanBeDamaged() - { - return false; - } + public override bool InitialInnocent => true; - public CapturedHordeMinion( Serial serial ) : base( serial ) - { - } + public override bool CanBeDamaged() + { + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/ChaosGuard.cs b/Scripts/Mobiles/Special/ChaosGuard.cs index 4ad6dba10..a7ad50117 100644 --- a/Scripts/Mobiles/Special/ChaosGuard.cs +++ b/Scripts/Mobiles/Special/ChaosGuard.cs @@ -1,38 +1,38 @@ -using Server.Items; using Server.Guilds; +using Server.Items; namespace Server.Mobiles { - public class ChaosGuard : BaseShieldGuard - { - public override int Keyword => 0x22; // *chaos shield* - public override BaseShield Shield => new ChaosShield(); - public override int SignupNumber => 1007140; // Sign up with a guild of chaos if thou art interested. - public override GuildType Type => GuildType.Chaos; + public class ChaosGuard : BaseShieldGuard + { + [Constructible] + public ChaosGuard() + { + } - public override bool BardImmune => true; + public ChaosGuard(Serial serial) : base(serial) + { + } - [Constructible] - public ChaosGuard() - { - } + public override int Keyword => 0x22; // *chaos shield* + public override BaseShield Shield => new ChaosShield(); + public override int SignupNumber => 1007140; // Sign up with a guild of chaos if thou art interested. + public override GuildType Type => GuildType.Chaos; - public ChaosGuard( Serial serial ) : base( serial ) - { - } + public override bool BardImmune => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/DarkGuardian.cs b/Scripts/Mobiles/Special/DarkGuardian.cs index b1a43f544..cee8280d7 100644 --- a/Scripts/Mobiles/Special/DarkGuardian.cs +++ b/Scripts/Mobiles/Special/DarkGuardian.cs @@ -2,79 +2,78 @@ using Server.Items; namespace Server.Mobiles { - public class DarkGuardian : BaseCreature - { - public override string CorpseName => "a dark guardians' corpse"; - public override string DefaultName => "a dark guardian"; + public class DarkGuardian : BaseCreature + { + [Constructible] + public DarkGuardian() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 78; + BaseSoundID = 0x3E9; - [Constructible] - public DarkGuardian() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 78; - BaseSoundID = 0x3E9; + SetStr(125, 150); + SetDex(100, 120); + SetInt(200, 235); - SetStr( 125, 150 ); - SetDex( 100, 120 ); - SetInt( 200, 235 ); + SetHits(150, 180); - SetHits( 150, 180 ); + SetDamage(43, 48); - SetDamage( 43, 48 ); + SetDamageType(ResistanceType.Physical, 10); + SetDamageType(ResistanceType.Cold, 40); + SetDamageType(ResistanceType.Energy, 50); - SetDamageType( ResistanceType.Physical, 10 ); - SetDamageType( ResistanceType.Cold, 40 ); - SetDamageType( ResistanceType.Energy, 50 ); + SetResistance(ResistanceType.Physical, 40, 50); + SetResistance(ResistanceType.Fire, 20, 45); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 20, 45); + SetResistance(ResistanceType.Energy, 30, 40); - SetResistance( ResistanceType.Physical, 40, 50 ); - SetResistance( ResistanceType.Fire, 20, 45 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 20, 45 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + SetSkill(SkillName.EvalInt, 40.1, 50); + SetSkill(SkillName.Magery, 50.1, 60.0); + SetSkill(SkillName.Meditation, 85.1, 95.0); + SetSkill(SkillName.MagicResist, 50.1, 70.0); + SetSkill(SkillName.Tactics, 50.1, 70.0); - SetSkill( SkillName.EvalInt, 40.1, 50); - SetSkill( SkillName.Magery, 50.1, 60.0 ); - SetSkill( SkillName.Meditation, 85.1, 95.0 ); - SetSkill( SkillName.MagicResist, 50.1, 70.0 ); - SetSkill( SkillName.Tactics, 50.1, 70.0 ); + Fame = 5000; + Karma = -5000; - Fame = 5000; - Karma = -5000; + VirtualArmor = 50; + PackNecroReg(15, 25); + PackItem(new DaemonBone(30)); + } - VirtualArmor = 50; - PackNecroReg( 15, 25 ); - PackItem( new DaemonBone( 30 ) ); - } + public DarkGuardian(Serial serial) : base(serial) + { + } - public DarkGuardian( Serial serial ) : base( serial ) - { - } + public override string CorpseName => "a dark guardians' corpse"; + public override string DefaultName => "a dark guardian"; - public override void GenerateLoot() - { - AddLoot( LootPack.Rich ); - AddLoot( LootPack.MedScrolls, 2 ); - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override int TreasureMapLevel => 2; + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; + public override bool Unprovokable => true; - public override int TreasureMapLevel => 2; - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; - public override bool Unprovokable => true; + public override void GenerateLoot() + { + AddLoot(LootPack.Rich); + AddLoot(LootPack.MedScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Dummy.cs b/Scripts/Mobiles/Special/Dummy.cs index 149e91e52..2458b248d 100644 --- a/Scripts/Mobiles/Special/Dummy.cs +++ b/Scripts/Mobiles/Special/Dummy.cs @@ -3,148 +3,144 @@ using Server.Items; namespace Server.Mobiles { - /// - /// This is a test creature - /// You can set its value in game - /// It die after 5 minutes, so your test server stay clean - /// Create a macro to help your creation "[add Dummy 1 15 7 -1 0.5 2" - /// - /// A iTeam of negative will set a faction at random - /// - /// Say Kill if you want them to die - /// - /// - public class Dummy : BaseCreature - { - public Timer m_Timer; + /// + /// This is a test creature + /// You can set its value in game + /// It die after 5 minutes, so your test server stay clean + /// Create a macro to help your creation "[add Dummy 1 15 7 -1 0.5 2" + /// A iTeam of negative will set a faction at random + /// Say Kill if you want them to die + /// + public class Dummy : BaseCreature + { + public Timer m_Timer; - [Constructible] - public Dummy(AIType iAI, FightMode iFightMode, int iRangePerception, int iRangeFight, double dActiveSpeed, double dPassiveSpeed) : base(iAI, iFightMode, iRangePerception, iRangeFight, dActiveSpeed, dPassiveSpeed) - { - Body = 400 + Utility.Random(2); - Hue = Utility.RandomSkinHue(); + [Constructible] + public Dummy(AIType iAI, FightMode iFightMode, int iRangePerception, int iRangeFight, double dActiveSpeed, + double dPassiveSpeed) : base(iAI, iFightMode, iRangePerception, iRangeFight, dActiveSpeed, dPassiveSpeed) + { + Body = 400 + Utility.Random(2); + Hue = Utility.RandomSkinHue(); - Skills[SkillName.DetectHidden].Base = 100; - Skills[SkillName.MagicResist].Base = 120; + Skills[SkillName.DetectHidden].Base = 100; + Skills[SkillName.MagicResist].Base = 120; - Team = Utility.Random(3); + Team = Utility.Random(3); - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; - Utility.AssignRandomHair( this, iHue ); + Utility.AssignRandomHair(this, iHue); - LeatherGloves glv = new LeatherGloves(); - glv.Hue = iHue; - glv.LootType = LootType.Newbied; - AddItem(glv); + LeatherGloves glv = new LeatherGloves(); + glv.Hue = iHue; + glv.LootType = LootType.Newbied; + AddItem(glv); - Container pack = new Backpack(); + Container pack = new Backpack(); - pack.Movable = false; + pack.Movable = false; - AddItem( pack ); + AddItem(pack); - m_Timer = new AutokillTimer(this); - m_Timer.Start(); - } + m_Timer = new AutokillTimer(this); + m_Timer.Start(); + } - public Dummy( Serial serial ) : base( serial ) - { - m_Timer = new AutokillTimer(this); - m_Timer.Start(); - } + public Dummy(Serial serial) : base(serial) + { + m_Timer = new AutokillTimer(this); + m_Timer.Start(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; + public override bool HandlesOnSpeech(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; - return base.HandlesOnSpeech( from ); - } + return base.HandlesOnSpeech(from); + } - public override void OnSpeech( SpeechEventArgs e ) - { - base.OnSpeech( e ); + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); - if (e.Mobile.AccessLevel >= AccessLevel.GameMaster) - { - if (e.Speech == "kill") - { - m_Timer.Stop(); - m_Timer.Delay = TimeSpan.FromSeconds( Utility.Random(1, 5) ); - m_Timer.Start(); - } - } - } + if (e.Mobile.AccessLevel >= AccessLevel.GameMaster) + if (e.Speech == "kill") + { + m_Timer.Stop(); + m_Timer.Delay = TimeSpan.FromSeconds(Utility.Random(1, 5)); + m_Timer.Start(); + } + } - public override void OnTeamChange() - { - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; + public override void OnTeamChange() + { + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; - Item item = FindItemOnLayer( Layer.OuterTorso ); + Item item = FindItemOnLayer(Layer.OuterTorso); - if ( item != null ) - item.Hue = jHue; + if (item != null) + item.Hue = jHue; - item = FindItemOnLayer( Layer.Helm ); + item = FindItemOnLayer(Layer.Helm); - if ( item != null ) - item.Hue = iHue; + if (item != null) + item.Hue = iHue; - item = FindItemOnLayer( Layer.Gloves ); + item = FindItemOnLayer(Layer.Gloves); - if ( item != null ) - item.Hue = iHue; + if (item != null) + item.Hue = iHue; - item = FindItemOnLayer( Layer.Shoes ); + item = FindItemOnLayer(Layer.Shoes); - if ( item != null ) - item.Hue = iHue; + if (item != null) + item.Hue = iHue; - HairHue = iHue; + HairHue = iHue; - item = FindItemOnLayer( Layer.MiddleTorso ); + item = FindItemOnLayer(Layer.MiddleTorso); - if ( item != null ) - item.Hue = iHue; + if (item != null) + item.Hue = iHue; - item = FindItemOnLayer( Layer.OuterLegs ); + item = FindItemOnLayer(Layer.OuterLegs); - if ( item != null ) - item.Hue = iHue; - } + if (item != null) + item.Hue = iHue; + } - private class AutokillTimer : Timer - { - private Dummy m_Owner; + private class AutokillTimer : Timer + { + private Dummy m_Owner; - public AutokillTimer( Dummy owner ) : base( TimeSpan.FromMinutes(5.0) ) - { - m_Owner = owner; - Priority = TimerPriority.FiveSeconds; - } + public AutokillTimer(Dummy owner) : base(TimeSpan.FromMinutes(5.0)) + { + m_Owner = owner; + Priority = TimerPriority.FiveSeconds; + } - protected override void OnTick() - { - m_Owner.Kill(); - Stop(); - } - } - } -} + protected override void OnTick() + { + m_Owner.Kill(); + Stop(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/DummySpecific.cs b/Scripts/Mobiles/Special/DummySpecific.cs index 6681159dd..2e9e2eaaf 100644 --- a/Scripts/Mobiles/Special/DummySpecific.cs +++ b/Scripts/Mobiles/Special/DummySpecific.cs @@ -1,786 +1,784 @@ using Server.Items; +using Server.Spells.First; +using Server.Spells.Third; namespace Server.Mobiles { - /// - /// This is a test creature - /// You can set its value in game - /// It die after 5 minutes, so your test server stay clean - /// Create a macro to help your creation "[add Dummy 1 15 7 -1 0.5 2" - /// - /// A iTeam of negative will set a faction at random - /// - /// Say Kill if you want them to die - /// - /// - - public class DummyMace : Dummy - { - public override string DefaultName => "Macer"; - - [Constructible] - public DummyMace() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Macer - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 125, 125, 90 ); - Skills[SkillName.Macing].Base = 120; - Skills[SkillName.Anatomy].Base = 120; - Skills[SkillName.Healing].Base = 120; - Skills[SkillName.Tactics].Base = 120; - - // Equip - WarHammer war = new WarHammer(); - war.Movable = true; - war.Crafter = this; - war.Quality = WeaponQuality.Regular; - AddItem( war ); - - Boots bts = new Boots(); - bts.Hue = iHue; - AddItem( bts ); - - ChainChest cht = new ChainChest(); - cht.Movable = false; - cht.LootType = LootType.Newbied; - cht.Crafter = this; - cht.Quality = ArmorQuality.Regular; - AddItem( cht ); - - ChainLegs chl = new ChainLegs(); - chl.Movable = false; - chl.LootType = LootType.Newbied; - chl.Crafter = this; - chl.Quality = ArmorQuality.Regular; - AddItem( chl ); - - PlateArms pla = new PlateArms(); - pla.Movable = false; - pla.LootType = LootType.Newbied; - pla.Crafter = this; - pla.Quality = ArmorQuality.Regular; - AddItem( pla ); - - Bandage band = new Bandage( 50 ); - AddToBackpack( band ); - } - - public DummyMace( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummyFence : Dummy - { - public override string DefaultName => "Fencer"; - - [Constructible] - public DummyFence() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Fencer - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 125, 125, 90 ); - Skills[SkillName.Fencing].Base = 120; - Skills[SkillName.Anatomy].Base = 120; - Skills[SkillName.Healing].Base = 120; - Skills[SkillName.Tactics].Base = 120; - - // Equip - Spear ssp = new Spear(); - ssp.Movable = true; - ssp.Crafter = this; - ssp.Quality = WeaponQuality.Regular; - AddItem( ssp ); - - Boots snd = new Boots(); - snd.Hue = iHue; - snd.LootType = LootType.Newbied; - AddItem( snd ); - - ChainChest cht = new ChainChest(); - cht.Movable = false; - cht.LootType = LootType.Newbied; - cht.Crafter = this; - cht.Quality = ArmorQuality.Regular; - AddItem( cht ); - - ChainLegs chl = new ChainLegs(); - chl.Movable = false; - chl.LootType = LootType.Newbied; - chl.Crafter = this; - chl.Quality = ArmorQuality.Regular; - AddItem( chl ); - - PlateArms pla = new PlateArms(); - pla.Movable = false; - pla.LootType = LootType.Newbied; - pla.Crafter = this; - pla.Quality = ArmorQuality.Regular; - AddItem( pla ); - - Bandage band = new Bandage( 50 ); - AddToBackpack( band ); - } - - public DummyFence( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummySword : Dummy - { - public override string DefaultName => "Swordsman"; - [Constructible] - public DummySword() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Swordsman - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 125, 125, 90 ); - Skills[SkillName.Swords].Base = 120; - Skills[SkillName.Anatomy].Base = 120; - Skills[SkillName.Healing].Base = 120; - Skills[SkillName.Tactics].Base = 120; - Skills[SkillName.Parry].Base = 120; - - // Equip - Katana kat = new Katana(); - kat.Crafter = this; - kat.Movable = true; - kat.Quality = WeaponQuality.Regular; - AddItem( kat ); - - Boots bts = new Boots(); - bts.Hue = iHue; - AddItem( bts ); - - ChainChest cht = new ChainChest(); - cht.Movable = false; - cht.LootType = LootType.Newbied; - cht.Crafter = this; - cht.Quality = ArmorQuality.Regular; - AddItem( cht ); - - ChainLegs chl = new ChainLegs(); - chl.Movable = false; - chl.LootType = LootType.Newbied; - chl.Crafter = this; - chl.Quality = ArmorQuality.Regular; - AddItem( chl ); - - PlateArms pla = new PlateArms(); - pla.Movable = false; - pla.LootType = LootType.Newbied; - pla.Crafter = this; - pla.Quality = ArmorQuality.Regular; - AddItem( pla ); - - Bandage band = new Bandage( 50 ); - AddToBackpack( band ); - } - - public DummySword( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummyNox : Dummy - { - public override string DefaultName => "Nox Mage"; - [Constructible] - public DummyNox() : base(AIType.AI_Mage, FightMode.Closest, 15, 1, 0.2, 0.6) - { - - // A Dummy Nox or Pure Mage - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 90, 90, 125 ); - Skills[SkillName.Magery].Base = 120; - Skills[SkillName.EvalInt].Base = 120; - Skills[SkillName.Inscribe].Base = 100; - Skills[SkillName.Wrestling].Base = 120; - Skills[SkillName.Meditation].Base = 120; - Skills[SkillName.Poisoning].Base = 100; - - // Equip - Spellbook book = new Spellbook(); - book.Movable = false; - book.LootType = LootType.Newbied; - book.Content =0xFFFFFFFFFFFFFFFF; - AddItem( book ); - - Kilt kilt = new Kilt(); - kilt.Hue = jHue; - AddItem( kilt ); - - Sandals snd = new Sandals(); - snd.Hue = iHue; - snd.LootType = LootType.Newbied; - AddItem( snd ); - - SkullCap skc = new SkullCap(); - skc.Hue = iHue; - AddItem( skc ); - - // Spells - AddSpellAttack( typeof(Spells.First.MagicArrowSpell) ); - AddSpellAttack( typeof(Spells.First.WeakenSpell) ); - AddSpellAttack( typeof(Spells.Third.FireballSpell) ); - AddSpellDefense( typeof(Spells.Third.WallOfStoneSpell) ); - AddSpellDefense( typeof(Spells.First.HealSpell) ); - } - - public DummyNox( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummyStun : Dummy - { - public override string DefaultName => "Stun Mage"; - - [Constructible] - public DummyStun() : base(AIType.AI_Mage, FightMode.Closest, 15, 1, 0.2, 0.6) - { - - // A Dummy Stun Mage - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 90, 90, 125 ); - Skills[SkillName.Magery].Base = 100; - Skills[SkillName.EvalInt].Base = 120; - Skills[SkillName.Anatomy].Base = 80; - Skills[SkillName.Wrestling].Base = 80; - Skills[SkillName.Meditation].Base = 100; - Skills[SkillName.Poisoning].Base = 100; - - // Equip - Spellbook book = new Spellbook(); - book.Movable = false; - book.LootType = LootType.Newbied; - book.Content =0xFFFFFFFFFFFFFFFF; - AddItem( book ); - - LeatherArms lea = new LeatherArms(); - lea.Movable = false; - lea.LootType = LootType.Newbied; - lea.Crafter = this; - lea.Quality = ArmorQuality.Regular; - AddItem( lea ); - - LeatherChest lec = new LeatherChest(); - lec.Movable = false; - lec.LootType = LootType.Newbied; - lec.Crafter = this; - lec.Quality = ArmorQuality.Regular; - AddItem( lec ); - - LeatherGorget leg = new LeatherGorget(); - leg.Movable = false; - leg.LootType = LootType.Newbied; - leg.Crafter = this; - leg.Quality = ArmorQuality.Regular; - AddItem( leg ); - - LeatherLegs lel = new LeatherLegs(); - lel.Movable = false; - lel.LootType = LootType.Newbied; - lel.Crafter = this; - lel.Quality = ArmorQuality.Regular; - AddItem( lel ); - - Boots bts = new Boots(); - bts.Hue = iHue; - AddItem( bts ); - - Cap cap = new Cap(); - cap.Hue = iHue; - AddItem( cap ); - - // Spells - AddSpellAttack( typeof(Spells.First.MagicArrowSpell) ); - AddSpellAttack( typeof(Spells.First.WeakenSpell) ); - AddSpellAttack( typeof(Spells.Third.FireballSpell) ); - AddSpellDefense( typeof(Spells.Third.WallOfStoneSpell) ); - AddSpellDefense( typeof(Spells.First.HealSpell) ); - } - - public DummyStun( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummySuper : Dummy - { - public override string DefaultName => "Super Mage"; - - [Constructible] - public DummySuper() : base(AIType.AI_Mage, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Super Mage - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 125, 125, 125 ); - Skills[SkillName.Magery].Base = 120; - Skills[SkillName.EvalInt].Base = 120; - Skills[SkillName.Anatomy].Base = 120; - Skills[SkillName.Wrestling].Base = 120; - Skills[SkillName.Meditation].Base = 120; - Skills[SkillName.Poisoning].Base = 100; - Skills[SkillName.Inscribe].Base = 100; - - // Equip - Spellbook book = new Spellbook(); - book.Movable = false; - book.LootType = LootType.Newbied; - book.Content =0xFFFFFFFFFFFFFFFF; - AddItem( book ); - - LeatherArms lea = new LeatherArms(); - lea.Movable = false; - lea.LootType = LootType.Newbied; - lea.Crafter = this; - lea.Quality = ArmorQuality.Regular; - AddItem( lea ); - - LeatherChest lec = new LeatherChest(); - lec.Movable = false; - lec.LootType = LootType.Newbied; - lec.Crafter = this; - lec.Quality = ArmorQuality.Regular; - AddItem( lec ); - - LeatherGorget leg = new LeatherGorget(); - leg.Movable = false; - leg.LootType = LootType.Newbied; - leg.Crafter = this; - leg.Quality = ArmorQuality.Regular; - AddItem( leg ); - - LeatherLegs lel = new LeatherLegs(); - lel.Movable = false; - lel.LootType = LootType.Newbied; - lel.Crafter = this; - lel.Quality = ArmorQuality.Regular; - AddItem( lel ); - - Sandals snd = new Sandals(); - snd.Hue = iHue; - snd.LootType = LootType.Newbied; - AddItem( snd ); - - JesterHat jhat = new JesterHat(); - jhat.Hue = iHue; - AddItem( jhat ); - - Doublet dblt = new Doublet(); - dblt.Hue = iHue; - AddItem( dblt ); - - // Spells - AddSpellAttack( typeof(Spells.First.MagicArrowSpell) ); - AddSpellAttack( typeof(Spells.First.WeakenSpell) ); - AddSpellAttack( typeof(Spells.Third.FireballSpell) ); - AddSpellDefense( typeof(Spells.Third.WallOfStoneSpell) ); - AddSpellDefense( typeof(Spells.First.HealSpell) ); - } - - public DummySuper( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummyHealer : Dummy - { - public override string DefaultName => "Healer"; - [Constructible] - public DummyHealer() : base(AIType.AI_Healer, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Healer Mage - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 125, 125, 125 ); - Skills[SkillName.Magery].Base = 120; - Skills[SkillName.EvalInt].Base = 120; - Skills[SkillName.Anatomy].Base = 120; - Skills[SkillName.Wrestling].Base = 120; - Skills[SkillName.Meditation].Base = 120; - Skills[SkillName.Healing].Base = 100; - - // Equip - Spellbook book = new Spellbook(); - book.Movable = false; - book.LootType = LootType.Newbied; - book.Content =0xFFFFFFFFFFFFFFFF; - AddItem( book ); - - LeatherArms lea = new LeatherArms(); - lea.Movable = false; - lea.LootType = LootType.Newbied; - lea.Crafter = this; - lea.Quality = ArmorQuality.Regular; - AddItem( lea ); - - LeatherChest lec = new LeatherChest(); - lec.Movable = false; - lec.LootType = LootType.Newbied; - lec.Crafter = this; - lec.Quality = ArmorQuality.Regular; - AddItem( lec ); - - LeatherGorget leg = new LeatherGorget(); - leg.Movable = false; - leg.LootType = LootType.Newbied; - leg.Crafter = this; - leg.Quality = ArmorQuality.Regular; - AddItem( leg ); - - LeatherLegs lel = new LeatherLegs(); - lel.Movable = false; - lel.LootType = LootType.Newbied; - lel.Crafter = this; - lel.Quality = ArmorQuality.Regular; - AddItem( lel ); - - Sandals snd = new Sandals(); - snd.Hue = iHue; - snd.LootType = LootType.Newbied; - AddItem( snd ); - - Cap cap = new Cap(); - cap.Hue = iHue; - AddItem( cap ); - - Robe robe = new Robe(); - robe.Hue = iHue; - AddItem( robe ); - - } - - public DummyHealer( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class DummyAssassin : Dummy - { - public override string DefaultName => "Hybrid Assassin"; - - [Constructible] - public DummyAssassin() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Hybrid Assassin - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 105, 105, 105 ); - Skills[SkillName.Magery].Base = 120; - Skills[SkillName.EvalInt].Base = 120; - Skills[SkillName.Swords].Base = 120; - Skills[SkillName.Tactics].Base = 120; - Skills[SkillName.Meditation].Base = 120; - Skills[SkillName.Poisoning].Base = 100; - - // Equip - Spellbook book = new Spellbook(); - book.Movable = false; - book.LootType = LootType.Newbied; - book.Content =0xFFFFFFFFFFFFFFFF; - AddToBackpack( book ); - - Katana kat = new Katana(); - kat.Movable = false; - kat.LootType = LootType.Newbied; - kat.Crafter = this; - kat.Poison = Poison.Deadly; - kat.PoisonCharges = 12; - kat.Quality = WeaponQuality.Regular; - AddToBackpack( kat ); - - LeatherArms lea = new LeatherArms(); - lea.Movable = false; - lea.LootType = LootType.Newbied; - lea.Crafter = this; - lea.Quality = ArmorQuality.Regular; - AddItem( lea ); - - LeatherChest lec = new LeatherChest(); - lec.Movable = false; - lec.LootType = LootType.Newbied; - lec.Crafter = this; - lec.Quality = ArmorQuality.Regular; - AddItem( lec ); - - LeatherGorget leg = new LeatherGorget(); - leg.Movable = false; - leg.LootType = LootType.Newbied; - leg.Crafter = this; - leg.Quality = ArmorQuality.Regular; - AddItem( leg ); - - LeatherLegs lel = new LeatherLegs(); - lel.Movable = false; - lel.LootType = LootType.Newbied; - lel.Crafter = this; - lel.Quality = ArmorQuality.Regular; - AddItem( lel ); - - Sandals snd = new Sandals(); - snd.Hue = iHue; - snd.LootType = LootType.Newbied; - AddItem( snd ); - - Cap cap = new Cap(); - cap.Hue = iHue; - AddItem( cap ); - - Robe robe = new Robe(); - robe.Hue = iHue; - AddItem( robe ); - - DeadlyPoisonPotion pota = new DeadlyPoisonPotion(); - pota.LootType = LootType.Newbied; - AddToBackpack( pota ); - - DeadlyPoisonPotion potb = new DeadlyPoisonPotion(); - potb.LootType = LootType.Newbied; - AddToBackpack( potb ); - - DeadlyPoisonPotion potc = new DeadlyPoisonPotion(); - potc.LootType = LootType.Newbied; - AddToBackpack( potc ); - - DeadlyPoisonPotion potd = new DeadlyPoisonPotion(); - potd.LootType = LootType.Newbied; - AddToBackpack( potd ); - - Bandage band = new Bandage( 50 ); - AddToBackpack( band ); - - } - - public DummyAssassin( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - [TypeAlias( "Server.Mobiles.DummyTheif" )] - public class DummyThief : Dummy - { - public override string DefaultName => "Hybrid Thief"; - [Constructible] - public DummyThief() : base(AIType.AI_Thief, FightMode.Closest, 15, 1, 0.2, 0.6) - { - // A Dummy Hybrid Thief - int iHue = 20 + Team * 40; - int jHue = 25 + Team * 40; - - // Skills and Stats - InitStats( 105, 105, 105 ); - Skills[SkillName.Healing].Base = 120; - Skills[SkillName.Anatomy].Base = 120; - Skills[SkillName.Stealing].Base = 120; - Skills[SkillName.ArmsLore].Base = 100; - Skills[SkillName.Meditation].Base = 120; - Skills[SkillName.Wrestling].Base = 120; - - // Equip - Spellbook book = new Spellbook(); - book.Movable = false; - book.LootType = LootType.Newbied; - book.Content =0xFFFFFFFFFFFFFFFF; - AddItem( book ); - - LeatherArms lea = new LeatherArms(); - lea.Movable = false; - lea.LootType = LootType.Newbied; - lea.Crafter = this; - lea.Quality = ArmorQuality.Regular; - AddItem( lea ); - - LeatherChest lec = new LeatherChest(); - lec.Movable = false; - lec.LootType = LootType.Newbied; - lec.Crafter = this; - lec.Quality = ArmorQuality.Regular; - AddItem( lec ); - - LeatherGorget leg = new LeatherGorget(); - leg.Movable = false; - leg.LootType = LootType.Newbied; - leg.Crafter = this; - leg.Quality = ArmorQuality.Regular; - AddItem( leg ); - - LeatherLegs lel = new LeatherLegs(); - lel.Movable = false; - lel.LootType = LootType.Newbied; - lel.Crafter = this; - lel.Quality = ArmorQuality.Regular; - AddItem( lel ); - - Sandals snd = new Sandals(); - snd.Hue = iHue; - snd.LootType = LootType.Newbied; - AddItem( snd ); - - Cap cap = new Cap(); - cap.Hue = iHue; - AddItem( cap ); - - Robe robe = new Robe(); - robe.Hue = iHue; - AddItem( robe ); - - Bandage band = new Bandage( 50 ); - AddToBackpack( band ); - } - - public DummyThief( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + /// + /// This is a test creature + /// You can set its value in game + /// It die after 5 minutes, so your test server stay clean + /// Create a macro to help your creation "[add Dummy 1 15 7 -1 0.5 2" + /// A iTeam of negative will set a faction at random + /// Say Kill if you want them to die + /// + public class DummyMace : Dummy + { + [Constructible] + public DummyMace() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Macer + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(125, 125, 90); + Skills[SkillName.Macing].Base = 120; + Skills[SkillName.Anatomy].Base = 120; + Skills[SkillName.Healing].Base = 120; + Skills[SkillName.Tactics].Base = 120; + + // Equip + WarHammer war = new WarHammer(); + war.Movable = true; + war.Crafter = this; + war.Quality = WeaponQuality.Regular; + AddItem(war); + + Boots bts = new Boots(); + bts.Hue = iHue; + AddItem(bts); + + ChainChest cht = new ChainChest(); + cht.Movable = false; + cht.LootType = LootType.Newbied; + cht.Crafter = this; + cht.Quality = ArmorQuality.Regular; + AddItem(cht); + + ChainLegs chl = new ChainLegs(); + chl.Movable = false; + chl.LootType = LootType.Newbied; + chl.Crafter = this; + chl.Quality = ArmorQuality.Regular; + AddItem(chl); + + PlateArms pla = new PlateArms(); + pla.Movable = false; + pla.LootType = LootType.Newbied; + pla.Crafter = this; + pla.Quality = ArmorQuality.Regular; + AddItem(pla); + + Bandage band = new Bandage(50); + AddToBackpack(band); + } + + public DummyMace(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Macer"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummyFence : Dummy + { + [Constructible] + public DummyFence() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Fencer + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(125, 125, 90); + Skills[SkillName.Fencing].Base = 120; + Skills[SkillName.Anatomy].Base = 120; + Skills[SkillName.Healing].Base = 120; + Skills[SkillName.Tactics].Base = 120; + + // Equip + Spear ssp = new Spear(); + ssp.Movable = true; + ssp.Crafter = this; + ssp.Quality = WeaponQuality.Regular; + AddItem(ssp); + + Boots snd = new Boots(); + snd.Hue = iHue; + snd.LootType = LootType.Newbied; + AddItem(snd); + + ChainChest cht = new ChainChest(); + cht.Movable = false; + cht.LootType = LootType.Newbied; + cht.Crafter = this; + cht.Quality = ArmorQuality.Regular; + AddItem(cht); + + ChainLegs chl = new ChainLegs(); + chl.Movable = false; + chl.LootType = LootType.Newbied; + chl.Crafter = this; + chl.Quality = ArmorQuality.Regular; + AddItem(chl); + + PlateArms pla = new PlateArms(); + pla.Movable = false; + pla.LootType = LootType.Newbied; + pla.Crafter = this; + pla.Quality = ArmorQuality.Regular; + AddItem(pla); + + Bandage band = new Bandage(50); + AddToBackpack(band); + } + + public DummyFence(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Fencer"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummySword : Dummy + { + [Constructible] + public DummySword() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Swordsman + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(125, 125, 90); + Skills[SkillName.Swords].Base = 120; + Skills[SkillName.Anatomy].Base = 120; + Skills[SkillName.Healing].Base = 120; + Skills[SkillName.Tactics].Base = 120; + Skills[SkillName.Parry].Base = 120; + + // Equip + Katana kat = new Katana(); + kat.Crafter = this; + kat.Movable = true; + kat.Quality = WeaponQuality.Regular; + AddItem(kat); + + Boots bts = new Boots(); + bts.Hue = iHue; + AddItem(bts); + + ChainChest cht = new ChainChest(); + cht.Movable = false; + cht.LootType = LootType.Newbied; + cht.Crafter = this; + cht.Quality = ArmorQuality.Regular; + AddItem(cht); + + ChainLegs chl = new ChainLegs(); + chl.Movable = false; + chl.LootType = LootType.Newbied; + chl.Crafter = this; + chl.Quality = ArmorQuality.Regular; + AddItem(chl); + + PlateArms pla = new PlateArms(); + pla.Movable = false; + pla.LootType = LootType.Newbied; + pla.Crafter = this; + pla.Quality = ArmorQuality.Regular; + AddItem(pla); + + Bandage band = new Bandage(50); + AddToBackpack(band); + } + + public DummySword(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Swordsman"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummyNox : Dummy + { + [Constructible] + public DummyNox() : base(AIType.AI_Mage, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Nox or Pure Mage + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(90, 90, 125); + Skills[SkillName.Magery].Base = 120; + Skills[SkillName.EvalInt].Base = 120; + Skills[SkillName.Inscribe].Base = 100; + Skills[SkillName.Wrestling].Base = 120; + Skills[SkillName.Meditation].Base = 120; + Skills[SkillName.Poisoning].Base = 100; + + // Equip + Spellbook book = new Spellbook(); + book.Movable = false; + book.LootType = LootType.Newbied; + book.Content = 0xFFFFFFFFFFFFFFFF; + AddItem(book); + + Kilt kilt = new Kilt(); + kilt.Hue = jHue; + AddItem(kilt); + + Sandals snd = new Sandals(); + snd.Hue = iHue; + snd.LootType = LootType.Newbied; + AddItem(snd); + + SkullCap skc = new SkullCap(); + skc.Hue = iHue; + AddItem(skc); + + // Spells + AddSpellAttack(typeof(MagicArrowSpell)); + AddSpellAttack(typeof(WeakenSpell)); + AddSpellAttack(typeof(FireballSpell)); + AddSpellDefense(typeof(WallOfStoneSpell)); + AddSpellDefense(typeof(HealSpell)); + } + + public DummyNox(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Nox Mage"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummyStun : Dummy + { + [Constructible] + public DummyStun() : base(AIType.AI_Mage, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Stun Mage + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(90, 90, 125); + Skills[SkillName.Magery].Base = 100; + Skills[SkillName.EvalInt].Base = 120; + Skills[SkillName.Anatomy].Base = 80; + Skills[SkillName.Wrestling].Base = 80; + Skills[SkillName.Meditation].Base = 100; + Skills[SkillName.Poisoning].Base = 100; + + // Equip + Spellbook book = new Spellbook(); + book.Movable = false; + book.LootType = LootType.Newbied; + book.Content = 0xFFFFFFFFFFFFFFFF; + AddItem(book); + + LeatherArms lea = new LeatherArms(); + lea.Movable = false; + lea.LootType = LootType.Newbied; + lea.Crafter = this; + lea.Quality = ArmorQuality.Regular; + AddItem(lea); + + LeatherChest lec = new LeatherChest(); + lec.Movable = false; + lec.LootType = LootType.Newbied; + lec.Crafter = this; + lec.Quality = ArmorQuality.Regular; + AddItem(lec); + + LeatherGorget leg = new LeatherGorget(); + leg.Movable = false; + leg.LootType = LootType.Newbied; + leg.Crafter = this; + leg.Quality = ArmorQuality.Regular; + AddItem(leg); + + LeatherLegs lel = new LeatherLegs(); + lel.Movable = false; + lel.LootType = LootType.Newbied; + lel.Crafter = this; + lel.Quality = ArmorQuality.Regular; + AddItem(lel); + + Boots bts = new Boots(); + bts.Hue = iHue; + AddItem(bts); + + Cap cap = new Cap(); + cap.Hue = iHue; + AddItem(cap); + + // Spells + AddSpellAttack(typeof(MagicArrowSpell)); + AddSpellAttack(typeof(WeakenSpell)); + AddSpellAttack(typeof(FireballSpell)); + AddSpellDefense(typeof(WallOfStoneSpell)); + AddSpellDefense(typeof(HealSpell)); + } + + public DummyStun(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Stun Mage"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummySuper : Dummy + { + [Constructible] + public DummySuper() : base(AIType.AI_Mage, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Super Mage + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(125, 125, 125); + Skills[SkillName.Magery].Base = 120; + Skills[SkillName.EvalInt].Base = 120; + Skills[SkillName.Anatomy].Base = 120; + Skills[SkillName.Wrestling].Base = 120; + Skills[SkillName.Meditation].Base = 120; + Skills[SkillName.Poisoning].Base = 100; + Skills[SkillName.Inscribe].Base = 100; + + // Equip + Spellbook book = new Spellbook(); + book.Movable = false; + book.LootType = LootType.Newbied; + book.Content = 0xFFFFFFFFFFFFFFFF; + AddItem(book); + + LeatherArms lea = new LeatherArms(); + lea.Movable = false; + lea.LootType = LootType.Newbied; + lea.Crafter = this; + lea.Quality = ArmorQuality.Regular; + AddItem(lea); + + LeatherChest lec = new LeatherChest(); + lec.Movable = false; + lec.LootType = LootType.Newbied; + lec.Crafter = this; + lec.Quality = ArmorQuality.Regular; + AddItem(lec); + + LeatherGorget leg = new LeatherGorget(); + leg.Movable = false; + leg.LootType = LootType.Newbied; + leg.Crafter = this; + leg.Quality = ArmorQuality.Regular; + AddItem(leg); + + LeatherLegs lel = new LeatherLegs(); + lel.Movable = false; + lel.LootType = LootType.Newbied; + lel.Crafter = this; + lel.Quality = ArmorQuality.Regular; + AddItem(lel); + + Sandals snd = new Sandals(); + snd.Hue = iHue; + snd.LootType = LootType.Newbied; + AddItem(snd); + + JesterHat jhat = new JesterHat(); + jhat.Hue = iHue; + AddItem(jhat); + + Doublet dblt = new Doublet(); + dblt.Hue = iHue; + AddItem(dblt); + + // Spells + AddSpellAttack(typeof(MagicArrowSpell)); + AddSpellAttack(typeof(WeakenSpell)); + AddSpellAttack(typeof(FireballSpell)); + AddSpellDefense(typeof(WallOfStoneSpell)); + AddSpellDefense(typeof(HealSpell)); + } + + public DummySuper(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Super Mage"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummyHealer : Dummy + { + [Constructible] + public DummyHealer() : base(AIType.AI_Healer, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Healer Mage + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(125, 125, 125); + Skills[SkillName.Magery].Base = 120; + Skills[SkillName.EvalInt].Base = 120; + Skills[SkillName.Anatomy].Base = 120; + Skills[SkillName.Wrestling].Base = 120; + Skills[SkillName.Meditation].Base = 120; + Skills[SkillName.Healing].Base = 100; + + // Equip + Spellbook book = new Spellbook(); + book.Movable = false; + book.LootType = LootType.Newbied; + book.Content = 0xFFFFFFFFFFFFFFFF; + AddItem(book); + + LeatherArms lea = new LeatherArms(); + lea.Movable = false; + lea.LootType = LootType.Newbied; + lea.Crafter = this; + lea.Quality = ArmorQuality.Regular; + AddItem(lea); + + LeatherChest lec = new LeatherChest(); + lec.Movable = false; + lec.LootType = LootType.Newbied; + lec.Crafter = this; + lec.Quality = ArmorQuality.Regular; + AddItem(lec); + + LeatherGorget leg = new LeatherGorget(); + leg.Movable = false; + leg.LootType = LootType.Newbied; + leg.Crafter = this; + leg.Quality = ArmorQuality.Regular; + AddItem(leg); + + LeatherLegs lel = new LeatherLegs(); + lel.Movable = false; + lel.LootType = LootType.Newbied; + lel.Crafter = this; + lel.Quality = ArmorQuality.Regular; + AddItem(lel); + + Sandals snd = new Sandals(); + snd.Hue = iHue; + snd.LootType = LootType.Newbied; + AddItem(snd); + + Cap cap = new Cap(); + cap.Hue = iHue; + AddItem(cap); + + Robe robe = new Robe(); + robe.Hue = iHue; + AddItem(robe); + } + + public DummyHealer(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Healer"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class DummyAssassin : Dummy + { + [Constructible] + public DummyAssassin() : base(AIType.AI_Melee, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Hybrid Assassin + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(105, 105, 105); + Skills[SkillName.Magery].Base = 120; + Skills[SkillName.EvalInt].Base = 120; + Skills[SkillName.Swords].Base = 120; + Skills[SkillName.Tactics].Base = 120; + Skills[SkillName.Meditation].Base = 120; + Skills[SkillName.Poisoning].Base = 100; + + // Equip + Spellbook book = new Spellbook(); + book.Movable = false; + book.LootType = LootType.Newbied; + book.Content = 0xFFFFFFFFFFFFFFFF; + AddToBackpack(book); + + Katana kat = new Katana(); + kat.Movable = false; + kat.LootType = LootType.Newbied; + kat.Crafter = this; + kat.Poison = Poison.Deadly; + kat.PoisonCharges = 12; + kat.Quality = WeaponQuality.Regular; + AddToBackpack(kat); + + LeatherArms lea = new LeatherArms(); + lea.Movable = false; + lea.LootType = LootType.Newbied; + lea.Crafter = this; + lea.Quality = ArmorQuality.Regular; + AddItem(lea); + + LeatherChest lec = new LeatherChest(); + lec.Movable = false; + lec.LootType = LootType.Newbied; + lec.Crafter = this; + lec.Quality = ArmorQuality.Regular; + AddItem(lec); + + LeatherGorget leg = new LeatherGorget(); + leg.Movable = false; + leg.LootType = LootType.Newbied; + leg.Crafter = this; + leg.Quality = ArmorQuality.Regular; + AddItem(leg); + + LeatherLegs lel = new LeatherLegs(); + lel.Movable = false; + lel.LootType = LootType.Newbied; + lel.Crafter = this; + lel.Quality = ArmorQuality.Regular; + AddItem(lel); + + Sandals snd = new Sandals(); + snd.Hue = iHue; + snd.LootType = LootType.Newbied; + AddItem(snd); + + Cap cap = new Cap(); + cap.Hue = iHue; + AddItem(cap); + + Robe robe = new Robe(); + robe.Hue = iHue; + AddItem(robe); + + DeadlyPoisonPotion pota = new DeadlyPoisonPotion(); + pota.LootType = LootType.Newbied; + AddToBackpack(pota); + + DeadlyPoisonPotion potb = new DeadlyPoisonPotion(); + potb.LootType = LootType.Newbied; + AddToBackpack(potb); + + DeadlyPoisonPotion potc = new DeadlyPoisonPotion(); + potc.LootType = LootType.Newbied; + AddToBackpack(potc); + + DeadlyPoisonPotion potd = new DeadlyPoisonPotion(); + potd.LootType = LootType.Newbied; + AddToBackpack(potd); + + Bandage band = new Bandage(50); + AddToBackpack(band); + } + + public DummyAssassin(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Hybrid Assassin"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + [TypeAlias("Server.Mobiles.DummyTheif")] + public class DummyThief : Dummy + { + [Constructible] + public DummyThief() : base(AIType.AI_Thief, FightMode.Closest, 15, 1, 0.2, 0.6) + { + // A Dummy Hybrid Thief + int iHue = 20 + Team * 40; + int jHue = 25 + Team * 40; + + // Skills and Stats + InitStats(105, 105, 105); + Skills[SkillName.Healing].Base = 120; + Skills[SkillName.Anatomy].Base = 120; + Skills[SkillName.Stealing].Base = 120; + Skills[SkillName.ArmsLore].Base = 100; + Skills[SkillName.Meditation].Base = 120; + Skills[SkillName.Wrestling].Base = 120; + + // Equip + Spellbook book = new Spellbook(); + book.Movable = false; + book.LootType = LootType.Newbied; + book.Content = 0xFFFFFFFFFFFFFFFF; + AddItem(book); + + LeatherArms lea = new LeatherArms(); + lea.Movable = false; + lea.LootType = LootType.Newbied; + lea.Crafter = this; + lea.Quality = ArmorQuality.Regular; + AddItem(lea); + + LeatherChest lec = new LeatherChest(); + lec.Movable = false; + lec.LootType = LootType.Newbied; + lec.Crafter = this; + lec.Quality = ArmorQuality.Regular; + AddItem(lec); + + LeatherGorget leg = new LeatherGorget(); + leg.Movable = false; + leg.LootType = LootType.Newbied; + leg.Crafter = this; + leg.Quality = ArmorQuality.Regular; + AddItem(leg); + + LeatherLegs lel = new LeatherLegs(); + lel.Movable = false; + lel.LootType = LootType.Newbied; + lel.Crafter = this; + lel.Quality = ArmorQuality.Regular; + AddItem(lel); + + Sandals snd = new Sandals(); + snd.Hue = iHue; + snd.LootType = LootType.Newbied; + AddItem(snd); + + Cap cap = new Cap(); + cap.Hue = iHue; + AddItem(cap); + + Robe robe = new Robe(); + robe.Hue = iHue; + AddItem(robe); + + Bandage band = new Bandage(50); + AddToBackpack(band); + } + + public DummyThief(Serial serial) : base(serial) + { + } + + public override string DefaultName => "Hybrid Thief"; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Harrower.cs b/Scripts/Mobiles/Special/Harrower.cs index 9b9f3cde5..43acf18b6 100644 --- a/Scripts/Mobiles/Special/Harrower.cs +++ b/Scripts/Mobiles/Special/Harrower.cs @@ -2,651 +2,655 @@ using System; using System.Collections; using System.Collections.Generic; using Server.Items; +using Server.Spells; namespace Server.Mobiles { - public class Harrower : BaseCreature - { - public Type[] UniqueList => new[] { typeof( AcidProofRobe ) }; - public Type[] SharedList => new[] { typeof( TheRobeOfBritanniaAri ) }; - public Type[] DecorativeList => new[] { typeof( EvilIdolSkull ), typeof( SkullPole ) }; - - private bool m_TrueForm; - private Item m_GateItem; - private List m_Tentacles; - private Timer m_Timer; - - private class SpawnEntry - { - public Point3D m_Location; - public Point3D m_Entrance; - - public SpawnEntry( Point3D loc, Point3D ent ) - { - m_Location = loc; - m_Entrance = ent; - } - } - - private static SpawnEntry[] m_Entries = { - new SpawnEntry( new Point3D( 5242, 945, -40 ), new Point3D( 1176, 2638, 0 ) ), // Destard - new SpawnEntry( new Point3D( 5225, 798, 0 ), new Point3D( 1176, 2638, 0 ) ), // Destard - new SpawnEntry( new Point3D( 5556, 886, 30 ), new Point3D( 1298, 1080, 0 ) ), // Despise - new SpawnEntry( new Point3D( 5187, 615, 0 ), new Point3D( 4111, 432, 5 ) ), // Deceit - new SpawnEntry( new Point3D( 5319, 583, 0 ), new Point3D( 4111, 432, 5 ) ), // Deceit - new SpawnEntry( new Point3D( 5713, 1334, -1 ), new Point3D( 2923, 3407, 8 ) ), // Fire - new SpawnEntry( new Point3D( 5860, 1460, -2 ), new Point3D( 2923, 3407, 8 ) ), // Fire - new SpawnEntry( new Point3D( 5328, 1620, 0 ), new Point3D( 5451, 3143, -60 ) ), // Terathan Keep - new SpawnEntry( new Point3D( 5690, 538, 0 ), new Point3D( 2042, 224, 14 ) ), // Wrong - new SpawnEntry( new Point3D( 5609, 195, 0 ), new Point3D( 514, 1561, 0 ) ), // Shame - new SpawnEntry( new Point3D( 5475, 187, 0 ), new Point3D( 514, 1561, 0 ) ), // Shame - new SpawnEntry( new Point3D( 6085, 179, 0 ), new Point3D( 4721, 3822, 0 ) ), // Hythloth - new SpawnEntry( new Point3D( 6084, 66, 0 ), new Point3D( 4721, 3822, 0 ) ), // Hythloth - new SpawnEntry( new Point3D( 5499, 2003, 0 ), new Point3D( 2499, 919, 0 ) ), // Covetous - new SpawnEntry( new Point3D( 5579, 1858, 0 ), new Point3D( 2499, 919, 0 ) ) // Covetous - }; - - public static ArrayList Instances { get; } = new ArrayList(); - - public static Harrower Spawn( Point3D platLoc, Map platMap ) - { - if ( Instances.Count > 0 ) - return null; - - SpawnEntry entry = m_Entries[Utility.Random( m_Entries.Length )]; - - Harrower harrower = new Harrower(); - - harrower.MoveToWorld( entry.m_Location, Map.Felucca ); - - harrower.m_GateItem = new HarrowerGate( harrower, platLoc, platMap, entry.m_Entrance, Map.Felucca ); - - return harrower; - } - - public static bool CanSpawn => ( Instances.Count == 0 ); - - public override string DefaultName => "the harrower"; - - [Constructible] - public Harrower() : base( AIType.AI_Mage, FightMode.Closest, 18, 1, 0.2, 0.4 ) - { - Instances.Add( this ); - BodyValue = 146; - - SetStr( 900, 1000 ); - SetDex( 125, 135 ); - SetInt( 1000, 1200 ); - - Fame = 22500; - Karma = -22500; - - VirtualArmor = 60; - - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Energy, 50 ); - - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 60, 80 ); - SetResistance( ResistanceType.Cold, 60, 80 ); - SetResistance( ResistanceType.Poison, 60, 80 ); - SetResistance( ResistanceType.Energy, 60, 80 ); - - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.2, 110.0 ); - SetSkill( SkillName.MagicResist, 120.2, 160.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - - m_Tentacles = new List(); - - m_Timer = new TeleportTimer( this ); - m_Timer.Start(); - } - - public override void GenerateLoot() - { - AddLoot( LootPack.SuperBoss, 2 ); - AddLoot( LootPack.Meager ); - } + public class Harrower : BaseCreature + { + private static SpawnEntry[] m_Entries = + { + new SpawnEntry(new Point3D(5242, 945, -40), new Point3D(1176, 2638, 0)), // Destard + new SpawnEntry(new Point3D(5225, 798, 0), new Point3D(1176, 2638, 0)), // Destard + new SpawnEntry(new Point3D(5556, 886, 30), new Point3D(1298, 1080, 0)), // Despise + new SpawnEntry(new Point3D(5187, 615, 0), new Point3D(4111, 432, 5)), // Deceit + new SpawnEntry(new Point3D(5319, 583, 0), new Point3D(4111, 432, 5)), // Deceit + new SpawnEntry(new Point3D(5713, 1334, -1), new Point3D(2923, 3407, 8)), // Fire + new SpawnEntry(new Point3D(5860, 1460, -2), new Point3D(2923, 3407, 8)), // Fire + new SpawnEntry(new Point3D(5328, 1620, 0), new Point3D(5451, 3143, -60)), // Terathan Keep + new SpawnEntry(new Point3D(5690, 538, 0), new Point3D(2042, 224, 14)), // Wrong + new SpawnEntry(new Point3D(5609, 195, 0), new Point3D(514, 1561, 0)), // Shame + new SpawnEntry(new Point3D(5475, 187, 0), new Point3D(514, 1561, 0)), // Shame + new SpawnEntry(new Point3D(6085, 179, 0), new Point3D(4721, 3822, 0)), // Hythloth + new SpawnEntry(new Point3D(6084, 66, 0), new Point3D(4721, 3822, 0)), // Hythloth + new SpawnEntry(new Point3D(5499, 2003, 0), new Point3D(2499, 919, 0)), // Covetous + new SpawnEntry(new Point3D(5579, 1858, 0), new Point3D(2499, 919, 0)) // Covetous + }; + + private static readonly double[] m_Offsets = + { + Math.Cos(000.0 / 180.0 * Math.PI), Math.Sin(000.0 / 180.0 * Math.PI), + Math.Cos(040.0 / 180.0 * Math.PI), Math.Sin(040.0 / 180.0 * Math.PI), + Math.Cos(080.0 / 180.0 * Math.PI), Math.Sin(080.0 / 180.0 * Math.PI), + Math.Cos(120.0 / 180.0 * Math.PI), Math.Sin(120.0 / 180.0 * Math.PI), + Math.Cos(160.0 / 180.0 * Math.PI), Math.Sin(160.0 / 180.0 * Math.PI), + Math.Cos(200.0 / 180.0 * Math.PI), Math.Sin(200.0 / 180.0 * Math.PI), + Math.Cos(240.0 / 180.0 * Math.PI), Math.Sin(240.0 / 180.0 * Math.PI), + Math.Cos(280.0 / 180.0 * Math.PI), Math.Sin(280.0 / 180.0 * Math.PI), + Math.Cos(320.0 / 180.0 * Math.PI), Math.Sin(320.0 / 180.0 * Math.PI) + }; + + private Dictionary m_DamageEntries; + private Item m_GateItem; + private List m_Tentacles; + private Timer m_Timer; + + private bool m_TrueForm; + + [Constructible] + public Harrower() : base(AIType.AI_Mage, FightMode.Closest, 18, 1, 0.2, 0.4) + { + Instances.Add(this); + BodyValue = 146; + + SetStr(900, 1000); + SetDex(125, 135); + SetInt(1000, 1200); + + Fame = 22500; + Karma = -22500; + + VirtualArmor = 60; + + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Energy, 50); + + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 60, 80); + SetResistance(ResistanceType.Cold, 60, 80); + SetResistance(ResistanceType.Poison, 60, 80); + SetResistance(ResistanceType.Energy, 60, 80); + + SetSkill(SkillName.Wrestling, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.2, 110.0); + SetSkill(SkillName.MagicResist, 120.2, 160.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Meditation, 120.0); + + m_Tentacles = new List(); + + m_Timer = new TeleportTimer(this); + m_Timer.Start(); + } + + public Harrower(Serial serial) : base(serial) + { + Instances.Add(this); + } - public override bool AutoDispel => true; - public override bool Unprovokable => true; - public override Poison PoisonImmune => Poison.Lethal; + public Type[] UniqueList => new[] { typeof(AcidProofRobe) }; + public Type[] SharedList => new[] { typeof(TheRobeOfBritanniaAri) }; + public Type[] DecorativeList => new[] { typeof(EvilIdolSkull), typeof(SkullPole) }; - private static readonly double[] m_Offsets = { - Math.Cos( 000.0 / 180.0 * Math.PI ), Math.Sin( 000.0 / 180.0 * Math.PI ), - Math.Cos( 040.0 / 180.0 * Math.PI ), Math.Sin( 040.0 / 180.0 * Math.PI ), - Math.Cos( 080.0 / 180.0 * Math.PI ), Math.Sin( 080.0 / 180.0 * Math.PI ), - Math.Cos( 120.0 / 180.0 * Math.PI ), Math.Sin( 120.0 / 180.0 * Math.PI ), - Math.Cos( 160.0 / 180.0 * Math.PI ), Math.Sin( 160.0 / 180.0 * Math.PI ), - Math.Cos( 200.0 / 180.0 * Math.PI ), Math.Sin( 200.0 / 180.0 * Math.PI ), - Math.Cos( 240.0 / 180.0 * Math.PI ), Math.Sin( 240.0 / 180.0 * Math.PI ), - Math.Cos( 280.0 / 180.0 * Math.PI ), Math.Sin( 280.0 / 180.0 * Math.PI ), - Math.Cos( 320.0 / 180.0 * Math.PI ), Math.Sin( 320.0 / 180.0 * Math.PI ), - }; + public static ArrayList Instances{ get; } = new ArrayList(); - public void Morph() - { - if ( m_TrueForm ) - return; + public static bool CanSpawn => Instances.Count == 0; - m_TrueForm = true; + public override string DefaultName => "the harrower"; - Name = "the true harrower"; - BodyValue = 780; - Hue = 0x497; + public override bool AutoDispel => true; + public override bool Unprovokable => true; + public override Poison PoisonImmune => Poison.Lethal; - Hits = HitsMax; - Stam = StamMax; - Mana = ManaMax; + [CommandProperty(AccessLevel.GameMaster)] + public override int HitsMax => m_TrueForm ? 65000 : 30000; - ProcessDelta(); + [CommandProperty(AccessLevel.GameMaster)] + public override int ManaMax => 5000; - Say( 1049499 ); // Behold my true form! + public override bool DisallowAllMoves => m_TrueForm; - Map map = Map; + public static Harrower Spawn(Point3D platLoc, Map platMap) + { + if (Instances.Count > 0) + return null; - if ( map != null ) - { - for ( int i = 0; i < m_Offsets.Length; i += 2 ) - { - double rx = m_Offsets[i]; - double ry = m_Offsets[i + 1]; + SpawnEntry entry = m_Entries[Utility.Random(m_Entries.Length)]; - int dist = 0; - bool ok = false; - int x = 0, y = 0, z = 0; + Harrower harrower = new Harrower(); - while ( !ok && dist < 10 ) - { - int rdist = 10 + dist; + harrower.MoveToWorld(entry.m_Location, Map.Felucca); - x = X + (int)(rx * rdist); - y = Y + (int)(ry * rdist); - z = map.GetAverageZ( x, y ); - - if ( !(ok = map.CanFit( x, y, Z, 16, false, false ) ) ) - ok = map.CanFit( x, y, z, 16, false, false ); - - if ( dist >= 0 ) - dist = -(dist + 1); - else - dist = -(dist - 1); - } - - if ( !ok ) - continue; - - HarrowerTentacles spawn = new HarrowerTentacles( this ); - - spawn.Team = Team; - - spawn.MoveToWorld( new Point3D( x, y, z ), map ); - - m_Tentacles.Add( spawn ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public override int HitsMax => m_TrueForm ? 65000 : 30000; - - [CommandProperty( AccessLevel.GameMaster )] - public override int ManaMax => 5000; - - public Harrower( Serial serial ) : base( serial ) - { - Instances.Add( this ); - } - - public override void OnAfterDelete() - { - Instances.Remove( this ); - - base.OnAfterDelete(); - } - - public override bool DisallowAllMoves => m_TrueForm; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - - writer.Write( m_TrueForm ); - writer.Write( m_GateItem ); - writer.WriteMobileList( m_Tentacles ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 0: - { - m_TrueForm = reader.ReadBool(); - m_GateItem = reader.ReadItem(); - m_Tentacles = reader.ReadStrongMobileList(); - - m_Timer = new TeleportTimer( this ); - m_Timer.Start(); - - break; - } - } - } - - public void GivePowerScrolls() - { - List toGive = new List(); - List rights = GetLootingRights( DamageEntries, HitsMax ); - - for ( int i = rights.Count - 1; i >= 0; --i ) - { - DamageStore ds = rights[i]; - - if ( ds.m_HasRight ) - toGive.Add( ds.m_Mobile ); - } - - if ( toGive.Count == 0 ) - return; - - // Randomize - for ( int i = 0; i < toGive.Count; ++i ) - { - int rand = Utility.Random( toGive.Count ); - Mobile hold = toGive[i]; - toGive[i] = toGive[rand]; - toGive[rand] = hold; - } - - for ( int i = 0; i < 16; ++i ) - { - int level; - double random = Utility.RandomDouble(); - - if ( 0.1 >= random ) - level = 25; - else if ( 0.25 >= random ) - level = 20; - else if ( 0.45 >= random ) - level = 15; - else if ( 0.70 >= random ) - level = 10; - else - level = 5; - - Mobile m = toGive[i % toGive.Count]; - - m.SendLocalizedMessage( 1049524 ); // You have received a scroll of power! - m.AddToBackpack( new StatCapScroll( 225 + level ) ); - - if ( m is PlayerMobile pm ) - { - for ( int j = 0; j < pm.JusticeProtectors.Count; ++j ) - { - Mobile prot = pm.JusticeProtectors[j]; - - if ( prot.Map != pm.Map || prot.Kills >= 5 || prot.Criminal || !JusticeVirtue.CheckMapRegion( pm, prot ) ) - continue; - - int chance = 0; - - switch ( VirtueHelper.GetLevel( prot, VirtueName.Justice ) ) - { - case VirtueLevel.Seeker: chance = 60; break; - case VirtueLevel.Follower: chance = 80; break; - case VirtueLevel.Knight: chance = 100; break; - } - - if ( chance > Utility.Random( 100 ) ) - { - prot.SendLocalizedMessage( 1049368 ); // You have been rewarded for your dedication to Justice! - prot.AddToBackpack( new StatCapScroll( 225 + level ) ); - } - } - } - } - } - - public override bool OnBeforeDeath() - { - if ( m_TrueForm ) - { - List rights = GetLootingRights( DamageEntries, HitsMax ); - - for ( int i = rights.Count - 1; i >= 0; --i ) - { - DamageStore ds = rights[i]; - - if ( ds.m_HasRight && ds.m_Mobile is PlayerMobile ) - PlayerMobile.ChampionTitleInfo.AwardHarrowerTitle( (PlayerMobile)ds.m_Mobile ); - } - - if ( !NoKillAwards ) - { - GivePowerScrolls(); - - Map map = Map; - - if ( map != null ) - { - for ( int x = -16; x <= 16; ++x ) - { - for ( int y = -16; y <= 16; ++y ) - { - double dist = Math.Sqrt(x*x+y*y); - - if ( dist <= 16 ) - new GoodiesTimer( map, X + x, Y + y ).Start(); - } - } - } - - m_DamageEntries = new Dictionary(); - - for ( int i = 0; i < m_Tentacles.Count; ++i ) - { - Mobile m = m_Tentacles[i]; - - if ( !m.Deleted ) - m.Kill(); - - RegisterDamageTo( m ); - } - - m_Tentacles.Clear(); - - RegisterDamageTo( this ); - AwardArtifact( GetArtifact() ); - - m_GateItem?.Delete(); - } - - return base.OnBeforeDeath(); - } - - Morph(); - return false; - } - - Dictionary m_DamageEntries; - - public virtual void RegisterDamageTo( Mobile m ) - { - if ( m == null ) - return; - - foreach( DamageEntry de in m.DamageEntries ) - { - Mobile damager = de.Damager; - - Mobile master = damager.GetDamageMaster( m ); - - if ( master != null ) - damager = master; + harrower.m_GateItem = new HarrowerGate(harrower, platLoc, platMap, entry.m_Entrance, Map.Felucca); - RegisterDamage( damager, de.DamageGiven ); - } - } - - public void RegisterDamage( Mobile from, int amount ) - { - if ( from == null || !from.Player ) - return; - - if ( m_DamageEntries.ContainsKey( from ) ) - m_DamageEntries[from] += amount; - else - m_DamageEntries.Add( from, amount ); - - from.SendMessage($"Total Damage: {m_DamageEntries[from]}"); - } - - public void AwardArtifact( Item artifact ) - { - if (artifact == null ) - return; - - int totalDamage = 0; - - Dictionary validEntries = new Dictionary(); - - foreach (KeyValuePair kvp in m_DamageEntries) - { - if ( IsEligible( kvp.Key, artifact ) ) - { - validEntries.Add( kvp.Key, kvp.Value ); - totalDamage += kvp.Value; - } - } + return harrower; + } - int randomDamage = Utility.RandomMinMax( 1, totalDamage ); + public override void GenerateLoot() + { + AddLoot(LootPack.SuperBoss, 2); + AddLoot(LootPack.Meager); + } - totalDamage = 0; + public void Morph() + { + if (m_TrueForm) + return; - foreach (KeyValuePair kvp in validEntries) - { - totalDamage += kvp.Value; - - if ( totalDamage >= randomDamage ) - { - GiveArtifact( kvp.Key, artifact ); - return; - } - } + m_TrueForm = true; - artifact.Delete(); - } + Name = "the true harrower"; + BodyValue = 780; + Hue = 0x497; - public void GiveArtifact( Mobile to, Item artifact ) - { - if ( to == null || artifact == null ) - return; + Hits = HitsMax; + Stam = StamMax; + Mana = ManaMax; - Container pack = to.Backpack; - - if ( pack == null || !pack.TryDropItem( to, artifact, false ) ) - artifact.Delete(); - else - to.SendLocalizedMessage( 1062317 ); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. - } + ProcessDelta(); - public bool IsEligible( Mobile m, Item Artifact ) - { - return m.Player && m.Alive && m.InRange( Location, 32 ) && m.Backpack != null && m.Backpack.CheckHold( m, Artifact, false ); - } - - public Item GetArtifact() - { - double random = Utility.RandomDouble(); - if ( 0.05 >= random ) - return CreateArtifact( UniqueList ); - if ( 0.15 >= random ) - return CreateArtifact( SharedList ); - if ( 0.30 >= random ) - return CreateArtifact( DecorativeList ); - - return null; - } + Say(1049499); // Behold my true form! - public Item CreateArtifact( Type[] list ) - { - if ( list.Length == 0 ) - return null; + Map map = Map; - int random = Utility.Random( list.Length ); + if (map != null) + for (int i = 0; i < m_Offsets.Length; i += 2) + { + double rx = m_Offsets[i]; + double ry = m_Offsets[i + 1]; - Type type = list[random]; + int dist = 0; + bool ok = false; + int x = 0, y = 0, z = 0; - return Loot.Construct( type ); - } - - private class TeleportTimer : Timer - { - private Mobile m_Owner; - - private static int[] m_Offsets = { - -1, -1, - -1, 0, - -1, 1, - 0, -1, - 0, 1, - 1, -1, - 1, 0, - 1, 1 - }; - - public TeleportTimer( Mobile owner ) : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - Priority = TimerPriority.TwoFiftyMS; - - m_Owner = owner; - } - - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } + while (!ok && dist < 10) + { + int rdist = 10 + dist; - Map map = m_Owner.Map; - - if ( map == null ) - return; - - if ( 0.25 < Utility.RandomDouble() ) - return; - - Mobile toTeleport = null; - - foreach ( Mobile m in m_Owner.GetMobilesInRange( 16 ) ) - { - if ( m != m_Owner && m.Player && m_Owner.CanBeHarmful( m ) && m_Owner.CanSee( m ) ) - { - toTeleport = m; - break; - } - } - - if ( toTeleport != null ) - { - int offset = Utility.Random( 8 ) * 2; - - Point3D to = m_Owner.Location; - - for ( int i = 0; i < m_Offsets.Length; i += 2 ) - { - int x = m_Owner.X + m_Offsets[(offset + i) % m_Offsets.Length]; - int y = m_Owner.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; - - if ( map.CanSpawnMobile( x, y, m_Owner.Z ) ) - { - to = new Point3D( x, y, m_Owner.Z ); - break; - } - - int z = map.GetAverageZ( x, y ); - - if ( map.CanSpawnMobile( x, y, z ) ) - { - to = new Point3D( x, y, z ); - break; - } - } - - Mobile m = toTeleport; - - Point3D from = m.Location; - - m.Location = to; - - Spells.SpellHelper.Turn( m_Owner, toTeleport ); - Spells.SpellHelper.Turn( toTeleport, m_Owner ); - - m.ProcessDelta(); - - Effects.SendLocationParticles( EffectItem.Create( from, m.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( to, m.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); - - m.PlaySound( 0x1FE ); - - m_Owner.Combatant = toTeleport; - } - } - } - - private class GoodiesTimer : Timer - { - private Map m_Map; - private int m_X, m_Y; - - public GoodiesTimer( Map map, int x, int y ) : base( TimeSpan.FromSeconds( Utility.RandomDouble() * 10.0 ) ) - { - Priority = TimerPriority.TwoFiftyMS; - - m_Map = map; - m_X = x; - m_Y = y; - } - - protected override void OnTick() - { - int z = m_Map.GetAverageZ( m_X, m_Y ); - bool canFit = m_Map.CanFit( m_X, m_Y, z, 6, false, false ); - - for ( int i = -3; !canFit && i <= 3; ++i ) - { - canFit = m_Map.CanFit( m_X, m_Y, z + i, 6, false, false ); - - if ( canFit ) - z += i; - } - - if ( !canFit ) - return; - - Gold g = new Gold( 750, 1250 ); - - g.MoveToWorld( new Point3D( m_X, m_Y, z ), m_Map ); + x = X + (int)(rx * rdist); + y = Y + (int)(ry * rdist); + z = map.GetAverageZ(x, y); - if ( 0.5 >= Utility.RandomDouble() ) - { - switch ( Utility.Random( 3 ) ) - { - case 0: // Fire column - { - Effects.SendLocationParticles( EffectItem.Create( g.Location, g.Map, EffectItem.DefaultDuration ), 0x3709, 10, 30, 5052 ); - Effects.PlaySound( g, g.Map, 0x208 ); - - break; - } - case 1: // Explosion - { - Effects.SendLocationParticles( EffectItem.Create( g.Location, g.Map, EffectItem.DefaultDuration ), 0x36BD, 20, 10, 5044 ); - Effects.PlaySound( g, g.Map, 0x307 ); - - break; - } - case 2: // Ball of fire - { - Effects.SendLocationParticles( EffectItem.Create( g.Location, g.Map, EffectItem.DefaultDuration ), 0x36FE, 10, 10, 5052 ); - - break; - } - } - } - } - } - } -} + if (!(ok = map.CanFit(x, y, Z, 16, false, false))) + ok = map.CanFit(x, y, z, 16, false, false); + + if (dist >= 0) + dist = -(dist + 1); + else + dist = -(dist - 1); + } + + if (!ok) + continue; + + HarrowerTentacles spawn = new HarrowerTentacles(this); + + spawn.Team = Team; + + spawn.MoveToWorld(new Point3D(x, y, z), map); + + m_Tentacles.Add(spawn); + } + } + + public override void OnAfterDelete() + { + Instances.Remove(this); + + base.OnAfterDelete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_TrueForm); + writer.Write(m_GateItem); + writer.WriteMobileList(m_Tentacles); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_TrueForm = reader.ReadBool(); + m_GateItem = reader.ReadItem(); + m_Tentacles = reader.ReadStrongMobileList(); + + m_Timer = new TeleportTimer(this); + m_Timer.Start(); + + break; + } + } + } + + public void GivePowerScrolls() + { + List toGive = new List(); + List rights = GetLootingRights(DamageEntries, HitsMax); + + for (int i = rights.Count - 1; i >= 0; --i) + { + DamageStore ds = rights[i]; + + if (ds.m_HasRight) + toGive.Add(ds.m_Mobile); + } + + if (toGive.Count == 0) + return; + + // Randomize + for (int i = 0; i < toGive.Count; ++i) + { + int rand = Utility.Random(toGive.Count); + Mobile hold = toGive[i]; + toGive[i] = toGive[rand]; + toGive[rand] = hold; + } + + for (int i = 0; i < 16; ++i) + { + int level; + double random = Utility.RandomDouble(); + + if (0.1 >= random) + level = 25; + else if (0.25 >= random) + level = 20; + else if (0.45 >= random) + level = 15; + else if (0.70 >= random) + level = 10; + else + level = 5; + + Mobile m = toGive[i % toGive.Count]; + + m.SendLocalizedMessage(1049524); // You have received a scroll of power! + m.AddToBackpack(new StatCapScroll(225 + level)); + + if (m is PlayerMobile pm) + for (int j = 0; j < pm.JusticeProtectors.Count; ++j) + { + Mobile prot = pm.JusticeProtectors[j]; + + if (prot.Map != pm.Map || prot.Kills >= 5 || prot.Criminal || + !JusticeVirtue.CheckMapRegion(pm, prot)) + continue; + + int chance = 0; + + switch (VirtueHelper.GetLevel(prot, VirtueName.Justice)) + { + case VirtueLevel.Seeker: + chance = 60; + break; + case VirtueLevel.Follower: + chance = 80; + break; + case VirtueLevel.Knight: + chance = 100; + break; + } + + if (chance > Utility.Random(100)) + { + prot.SendLocalizedMessage(1049368); // You have been rewarded for your dedication to Justice! + prot.AddToBackpack(new StatCapScroll(225 + level)); + } + } + } + } + + public override bool OnBeforeDeath() + { + if (m_TrueForm) + { + List rights = GetLootingRights(DamageEntries, HitsMax); + + for (int i = rights.Count - 1; i >= 0; --i) + { + DamageStore ds = rights[i]; + + if (ds.m_HasRight && ds.m_Mobile is PlayerMobile) + PlayerMobile.ChampionTitleInfo.AwardHarrowerTitle((PlayerMobile)ds.m_Mobile); + } + + if (!NoKillAwards) + { + GivePowerScrolls(); + + Map map = Map; + + if (map != null) + for (int x = -16; x <= 16; ++x) + for (int y = -16; y <= 16; ++y) + { + double dist = Math.Sqrt(x * x + y * y); + + if (dist <= 16) + new GoodiesTimer(map, X + x, Y + y).Start(); + } + + m_DamageEntries = new Dictionary(); + + for (int i = 0; i < m_Tentacles.Count; ++i) + { + Mobile m = m_Tentacles[i]; + + if (!m.Deleted) + m.Kill(); + + RegisterDamageTo(m); + } + + m_Tentacles.Clear(); + + RegisterDamageTo(this); + AwardArtifact(GetArtifact()); + + m_GateItem?.Delete(); + } + + return base.OnBeforeDeath(); + } + + Morph(); + return false; + } + + public virtual void RegisterDamageTo(Mobile m) + { + if (m == null) + return; + + foreach (DamageEntry de in m.DamageEntries) + { + Mobile damager = de.Damager; + + Mobile master = damager.GetDamageMaster(m); + + if (master != null) + damager = master; + + RegisterDamage(damager, de.DamageGiven); + } + } + + public void RegisterDamage(Mobile from, int amount) + { + if (from == null || !from.Player) + return; + + if (m_DamageEntries.ContainsKey(from)) + m_DamageEntries[from] += amount; + else + m_DamageEntries.Add(from, amount); + + from.SendMessage($"Total Damage: {m_DamageEntries[from]}"); + } + + public void AwardArtifact(Item artifact) + { + if (artifact == null) + return; + + int totalDamage = 0; + + Dictionary validEntries = new Dictionary(); + + foreach (KeyValuePair kvp in m_DamageEntries) + if (IsEligible(kvp.Key, artifact)) + { + validEntries.Add(kvp.Key, kvp.Value); + totalDamage += kvp.Value; + } + + int randomDamage = Utility.RandomMinMax(1, totalDamage); + + totalDamage = 0; + + foreach (KeyValuePair kvp in validEntries) + { + totalDamage += kvp.Value; + + if (totalDamage >= randomDamage) + { + GiveArtifact(kvp.Key, artifact); + return; + } + } + + artifact.Delete(); + } + + public void GiveArtifact(Mobile to, Item artifact) + { + if (to == null || artifact == null) + return; + + Container pack = to.Backpack; + + if (pack == null || !pack.TryDropItem(to, artifact, false)) + artifact.Delete(); + else + to.SendLocalizedMessage( + 1062317); // For your valor in combating the fallen beast, a special artifact has been bestowed on you. + } + + public bool IsEligible(Mobile m, Item Artifact) + { + return m.Player && m.Alive && m.InRange(Location, 32) && m.Backpack != null && + m.Backpack.CheckHold(m, Artifact, false); + } + + public Item GetArtifact() + { + double random = Utility.RandomDouble(); + if (0.05 >= random) + return CreateArtifact(UniqueList); + if (0.15 >= random) + return CreateArtifact(SharedList); + if (0.30 >= random) + return CreateArtifact(DecorativeList); + + return null; + } + + public Item CreateArtifact(Type[] list) + { + if (list.Length == 0) + return null; + + int random = Utility.Random(list.Length); + + Type type = list[random]; + + return Loot.Construct(type); + } + + private class SpawnEntry + { + public Point3D m_Entrance; + public Point3D m_Location; + + public SpawnEntry(Point3D loc, Point3D ent) + { + m_Location = loc; + m_Entrance = ent; + } + } + + private class TeleportTimer : Timer + { + private static int[] m_Offsets = + { + -1, -1, + -1, 0, + -1, 1, + 0, -1, + 0, 1, + 1, -1, + 1, 0, + 1, 1 + }; + + private Mobile m_Owner; + + public TeleportTimer(Mobile owner) : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + Priority = TimerPriority.TwoFiftyMS; + + m_Owner = owner; + } + + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } + + Map map = m_Owner.Map; + + if (map == null) + return; + + if (0.25 < Utility.RandomDouble()) + return; + + Mobile toTeleport = null; + + foreach (Mobile m in m_Owner.GetMobilesInRange(16)) + if (m != m_Owner && m.Player && m_Owner.CanBeHarmful(m) && m_Owner.CanSee(m)) + { + toTeleport = m; + break; + } + + if (toTeleport != null) + { + int offset = Utility.Random(8) * 2; + + Point3D to = m_Owner.Location; + + for (int i = 0; i < m_Offsets.Length; i += 2) + { + int x = m_Owner.X + m_Offsets[(offset + i) % m_Offsets.Length]; + int y = m_Owner.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; + + if (map.CanSpawnMobile(x, y, m_Owner.Z)) + { + to = new Point3D(x, y, m_Owner.Z); + break; + } + + int z = map.GetAverageZ(x, y); + + if (map.CanSpawnMobile(x, y, z)) + { + to = new Point3D(x, y, z); + break; + } + } + + Mobile m = toTeleport; + + Point3D from = m.Location; + + m.Location = to; + + SpellHelper.Turn(m_Owner, toTeleport); + SpellHelper.Turn(toTeleport, m_Owner); + + m.ProcessDelta(); + + Effects.SendLocationParticles(EffectItem.Create(from, m.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 2023); + Effects.SendLocationParticles(EffectItem.Create(to, m.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); + + m.PlaySound(0x1FE); + + m_Owner.Combatant = toTeleport; + } + } + } + + private class GoodiesTimer : Timer + { + private Map m_Map; + private int m_X, m_Y; + + public GoodiesTimer(Map map, int x, int y) : base(TimeSpan.FromSeconds(Utility.RandomDouble() * 10.0)) + { + Priority = TimerPriority.TwoFiftyMS; + + m_Map = map; + m_X = x; + m_Y = y; + } + + protected override void OnTick() + { + int z = m_Map.GetAverageZ(m_X, m_Y); + bool canFit = m_Map.CanFit(m_X, m_Y, z, 6, false, false); + + for (int i = -3; !canFit && i <= 3; ++i) + { + canFit = m_Map.CanFit(m_X, m_Y, z + i, 6, false, false); + + if (canFit) + z += i; + } + + if (!canFit) + return; + + Gold g = new Gold(750, 1250); + + g.MoveToWorld(new Point3D(m_X, m_Y, z), m_Map); + + if (0.5 >= Utility.RandomDouble()) + switch (Utility.Random(3)) + { + case 0: // Fire column + { + Effects.SendLocationParticles(EffectItem.Create(g.Location, g.Map, EffectItem.DefaultDuration), + 0x3709, 10, 30, 5052); + Effects.PlaySound(g, g.Map, 0x208); + + break; + } + case 1: // Explosion + { + Effects.SendLocationParticles(EffectItem.Create(g.Location, g.Map, EffectItem.DefaultDuration), + 0x36BD, 20, 10, 5044); + Effects.PlaySound(g, g.Map, 0x307); + + break; + } + case 2: // Ball of fire + { + Effects.SendLocationParticles(EffectItem.Create(g.Location, g.Map, EffectItem.DefaultDuration), + 0x36FE, 10, 10, 5052); + + break; + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/HarrowerTentacles.cs b/Scripts/Mobiles/Special/HarrowerTentacles.cs index 46172881e..d7e03aaa6 100644 --- a/Scripts/Mobiles/Special/HarrowerTentacles.cs +++ b/Scripts/Mobiles/Special/HarrowerTentacles.cs @@ -3,204 +3,203 @@ using System.Collections; namespace Server.Mobiles { - public class HarrowerTentacles : BaseCreature - { - public override string CorpseName => "a tentacles corpse"; + public class HarrowerTentacles : BaseCreature + { + private DrainTimer m_Timer; - private DrainTimer m_Timer; + [Constructible] + public HarrowerTentacles() : this(null) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Harrower { get; set; } + public HarrowerTentacles(Mobile harrower) : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Harrower = harrower; + Body = 129; - public override string DefaultName => "tentacles of the harrower"; + SetStr(901, 1000); + SetDex(126, 140); + SetInt(1001, 1200); - [Constructible] - public HarrowerTentacles() : this( null ) - { - } + SetHits(541, 600); - public HarrowerTentacles( Mobile harrower ) : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Harrower = harrower; - Body = 129; + SetDamage(13, 20); - SetStr( 901, 1000 ); - SetDex( 126, 140 ); - SetInt( 1001, 1200 ); + SetDamageType(ResistanceType.Physical, 20); + SetDamageType(ResistanceType.Fire, 20); + SetDamageType(ResistanceType.Cold, 20); + SetDamageType(ResistanceType.Poison, 20); + SetDamageType(ResistanceType.Energy, 20); - SetHits( 541, 600 ); + SetResistance(ResistanceType.Physical, 55, 65); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 35, 45); + SetResistance(ResistanceType.Poison, 35, 45); + SetResistance(ResistanceType.Energy, 35, 45); - SetDamage( 13, 20 ); + SetSkill(SkillName.Meditation, 100.0); + SetSkill(SkillName.MagicResist, 120.1, 140.0); + SetSkill(SkillName.Swords, 90.1, 100.0); + SetSkill(SkillName.Tactics, 90.1, 100.0); + SetSkill(SkillName.Wrestling, 90.1, 100.0); - SetDamageType( ResistanceType.Physical, 20 ); - SetDamageType( ResistanceType.Fire, 20 ); - SetDamageType( ResistanceType.Cold, 20 ); - SetDamageType( ResistanceType.Poison, 20 ); - SetDamageType( ResistanceType.Energy, 20 ); + Fame = 15000; + Karma = -15000; - SetResistance( ResistanceType.Physical, 55, 65 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 35, 45 ); - SetResistance( ResistanceType.Poison, 35, 45 ); - SetResistance( ResistanceType.Energy, 35, 45 ); + VirtualArmor = 60; - SetSkill( SkillName.Meditation, 100.0 ); - SetSkill( SkillName.MagicResist, 120.1, 140.0 ); - SetSkill( SkillName.Swords, 90.1, 100.0 ); - SetSkill( SkillName.Tactics, 90.1, 100.0 ); - SetSkill( SkillName.Wrestling, 90.1, 100.0 ); + m_Timer = new DrainTimer(this); + m_Timer.Start(); - Fame = 15000; - Karma = -15000; + PackReg(50); + PackNecroReg(15, 75); + } - VirtualArmor = 60; + public HarrowerTentacles(Serial serial) : base(serial) + { + } - m_Timer = new DrainTimer( this ); - m_Timer.Start(); + public override string CorpseName => "a tentacles corpse"; - PackReg( 50 ); - PackNecroReg( 15, 75 ); - } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Harrower{ get; set; } - public override void CheckReflect( Mobile caster, ref bool reflect ) - { - reflect = true; - } + public override string DefaultName => "tentacles of the harrower"; - public override int GetIdleSound() - { - return 0x101; - } + public override bool AutoDispel => true; + public override bool Unprovokable => true; + public override Poison PoisonImmune => Poison.Lethal; + public override bool DisallowAllMoves => true; - public override int GetAngerSound() - { - return 0x5E; - } + public override void CheckReflect(Mobile caster, ref bool reflect) + { + reflect = true; + } - public override int GetDeathSound() - { - return 0x1C2; - } + public override int GetIdleSound() + { + return 0x101; + } - public override int GetAttackSound() - { - return -1; // unknown - } + public override int GetAngerSound() + { + return 0x5E; + } - public override int GetHurtSound() - { - return 0x289; - } + public override int GetDeathSound() + { + return 0x1C2; + } - public override void GenerateLoot() - { - AddLoot( LootPack.FilthyRich, 2 ); - AddLoot( LootPack.MedScrolls, 3 ); - AddLoot( LootPack.HighScrolls, 2 ); - } + public override int GetAttackSound() + { + return -1; // unknown + } - public override bool AutoDispel => true; - public override bool Unprovokable => true; - public override Poison PoisonImmune => Poison.Lethal; - public override bool DisallowAllMoves => true; + public override int GetHurtSound() + { + return 0x289; + } - public HarrowerTentacles( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.FilthyRich, 2); + AddLoot(LootPack.MedScrolls, 3); + AddLoot(LootPack.HighScrolls, 2); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( Harrower ); - } + writer.Write(Harrower); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - Harrower = reader.ReadMobile(); + switch (version) + { + case 0: + { + Harrower = reader.ReadMobile(); - m_Timer = new DrainTimer( this ); - m_Timer.Start(); + m_Timer = new DrainTimer(this); + m_Timer.Start(); - break; - } - } - } + break; + } + } + } - public override void OnAfterDelete() - { - m_Timer?.Stop(); + public override void OnAfterDelete() + { + m_Timer?.Stop(); - m_Timer = null; + m_Timer = null; - base.OnAfterDelete(); - } + base.OnAfterDelete(); + } - private class DrainTimer : Timer - { - private HarrowerTentacles m_Owner; + private class DrainTimer : Timer + { + private static ArrayList m_ToDrain = new ArrayList(); + private HarrowerTentacles m_Owner; - public DrainTimer( HarrowerTentacles owner ) : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_Owner = owner; - Priority = TimerPriority.TwoFiftyMS; - } + public DrainTimer(HarrowerTentacles owner) : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + m_Owner = owner; + Priority = TimerPriority.TwoFiftyMS; + } - private static ArrayList m_ToDrain = new ArrayList(); + protected override void OnTick() + { + if (m_Owner.Deleted) + { + Stop(); + return; + } - protected override void OnTick() - { - if ( m_Owner.Deleted ) - { - Stop(); - return; - } + foreach (Mobile m in m_Owner.GetMobilesInRange(9)) + { + if (m == m_Owner || m == m_Owner.Harrower || !m_Owner.CanBeHarmful(m)) + continue; - foreach ( Mobile m in m_Owner.GetMobilesInRange( 9 ) ) - { - if ( m == m_Owner || m == m_Owner.Harrower || !m_Owner.CanBeHarmful( m ) ) - continue; + if (m is BaseCreature bc) + { + if (bc.Controlled || bc.Summoned) + m_ToDrain.Add(m); + } + else if (m.Player) + { + m_ToDrain.Add(m); + } + } - if ( m is BaseCreature bc ) - { - if ( bc.Controlled || bc.Summoned ) - m_ToDrain.Add( m ); - } - else if ( m.Player ) - { - m_ToDrain.Add( m ); - } - } + foreach (Mobile m in m_ToDrain) + { + m_Owner.DoHarmful(m); - foreach ( Mobile m in m_ToDrain ) - { - m_Owner.DoHarmful( m ); + m.FixedParticles(0x374A, 10, 15, 5013, 0x455, 0, EffectLayer.Waist); + m.PlaySound(0x1F1); - m.FixedParticles( 0x374A, 10, 15, 5013, 0x455, 0, EffectLayer.Waist ); - m.PlaySound( 0x1F1 ); + int drain = Utility.RandomMinMax(14, 30); - int drain = Utility.RandomMinMax( 14, 30 ); + m_Owner.Hits += drain; - m_Owner.Hits += drain; + if (m_Owner.Harrower != null) + m_Owner.Harrower.Hits += drain; - if ( m_Owner.Harrower != null ) - m_Owner.Harrower.Hits += drain; + m.Damage(drain, m_Owner); + } - m.Damage( drain, m_Owner ); - } - - m_ToDrain.Clear(); - } - } - } -} + m_ToDrain.Clear(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/LordOaks.cs b/Scripts/Mobiles/Special/LordOaks.cs index 8d80c5e4a..fc8f8cad4 100644 --- a/Scripts/Mobiles/Special/LordOaks.cs +++ b/Scripts/Mobiles/Special/LordOaks.cs @@ -1,235 +1,242 @@ using System; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class LordOaks : BaseChampion - { - private Mobile m_Queen; - private bool m_SpawnedQueen; + public class LordOaks : BaseChampion + { + private Mobile m_Queen; + private bool m_SpawnedQueen; - public override ChampionSkullType SkullType => ChampionSkullType.Enlightenment; + [Constructible] + public LordOaks() : base(AIType.AI_Mage, FightMode.Evil) + { + Body = 175; + SetStr(403, 850); + SetDex(101, 150); + SetInt(503, 800); - public override Type[] UniqueList => new[] { typeof( OrcChieftainHelm ) }; - public override Type[] SharedList => new[] { typeof( RoyalGuardSurvivalKnife ), - typeof( DjinnisRing ), - typeof( LieutenantOfTheBritannianRoyalGuard ), - typeof( SamaritanRobe ), - typeof( DetectiveBoots ), - typeof( TheMostKnowledgePerson ) }; + SetHits(3000); + SetStam(202, 400); - public override Type[] DecorativeList => new[] { typeof( WaterTile ), - typeof( WindSpirit ), - typeof( Pier ), - typeof( DirtPatch )}; + SetDamage(21, 33); - public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Fire, 25); - public override string DefaultName => "Lord Oaks"; + SetResistance(ResistanceType.Physical, 85, 90); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 80, 90); + SetResistance(ResistanceType.Energy, 80, 90); - [Constructible] - public LordOaks() : base( AIType.AI_Mage, FightMode.Evil ) - { - Body = 175; - SetStr( 403, 850 ); - SetDex( 101, 150 ); - SetInt( 503, 800 ); + SetSkill(SkillName.Anatomy, 75.1, 100.0); + SetSkill(SkillName.EvalInt, 120.1, 130.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.Meditation, 120.1, 130.0); + SetSkill(SkillName.MagicResist, 100.5, 150.0); + SetSkill(SkillName.Tactics, 100.0); + SetSkill(SkillName.Wrestling, 100.0); - SetHits( 3000 ); - SetStam( 202, 400 ); + Fame = 22500; + Karma = 22500; - SetDamage( 21, 33 ); + VirtualArmor = 100; + } - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Fire, 25 ); + public LordOaks(Serial serial) : base(serial) + { + } - SetResistance( ResistanceType.Physical, 85, 90 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 80, 90 ); - SetResistance( ResistanceType.Energy, 80, 90 ); + public override ChampionSkullType SkullType => ChampionSkullType.Enlightenment; - SetSkill( SkillName.Anatomy, 75.1, 100.0 ); - SetSkill( SkillName.EvalInt, 120.1, 130.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.Meditation, 120.1, 130.0 ); - SetSkill( SkillName.MagicResist, 100.5, 150.0 ); - SetSkill( SkillName.Tactics, 100.0 ); - SetSkill( SkillName.Wrestling, 100.0 ); + public override Type[] UniqueList => new[] { typeof(OrcChieftainHelm) }; - Fame = 22500; - Karma = 22500; + public override Type[] SharedList => new[] + { + typeof(RoyalGuardSurvivalKnife), + typeof(DjinnisRing), + typeof(LieutenantOfTheBritannianRoyalGuard), + typeof(SamaritanRobe), + typeof(DetectiveBoots), + typeof(TheMostKnowledgePerson) + }; - VirtualArmor = 100; - } + public override Type[] DecorativeList => new[] + { + typeof(WaterTile), + typeof(WindSpirit), + typeof(Pier), + typeof(DirtPatch) + }; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 5 ); - } + public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; - public override bool AutoDispel => true; - public override bool CanFly => true; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool Uncalmable => Core.SE; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override string DefaultName => "Lord Oaks"; - public override Poison PoisonImmune => Poison.Deadly; + public override bool AutoDispel => true; + public override bool CanFly => true; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool Uncalmable => Core.SE; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public void SpawnPixies( Mobile target ) - { - Map map = Map; + public override Poison PoisonImmune => Poison.Deadly; - if ( map == null ) - return; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 5); + } - Say( 1042154 ); // You shall never defeat me as long as I have my queen! + public void SpawnPixies(Mobile target) + { + Map map = Map; - int newPixies = Utility.RandomMinMax( 3, 6 ); + if (map == null) + return; - for ( int i = 0; i < newPixies; ++i ) - { - Pixie pixie = new Pixie(); + Say(1042154); // You shall never defeat me as long as I have my queen! - pixie.Team = Team; - pixie.FightMode = FightMode.Closest; + int newPixies = Utility.RandomMinMax(3, 6); - bool validLocation = false; - Point3D loc = Location; + for (int i = 0; i < newPixies; ++i) + { + Pixie pixie = new Pixie(); - for ( int j = 0; !validLocation && j < 10; ++j ) - { - int x = X + Utility.Random( 3 ) - 1; - int y = Y + Utility.Random( 3 ) - 1; - int z = map.GetAverageZ( x, y ); + pixie.Team = Team; + pixie.FightMode = FightMode.Closest; - if ( validLocation = map.CanFit( x, y, Z, 16, false, false ) ) - loc = new Point3D( x, y, Z ); - else if ( validLocation = map.CanFit( x, y, z, 16, false, false ) ) - loc = new Point3D( x, y, z ); - } + bool validLocation = false; + Point3D loc = Location; - pixie.MoveToWorld( loc, map ); - pixie.Combatant = target; - } - } + for (int j = 0; !validLocation && j < 10; ++j) + { + int x = X + Utility.Random(3) - 1; + int y = Y + Utility.Random(3) - 1; + int z = map.GetAverageZ(x, y); - public override int GetAngerSound() - { - return 0x2F8; - } + if (validLocation = map.CanFit(x, y, Z, 16, false, false)) + loc = new Point3D(x, y, Z); + else if (validLocation = map.CanFit(x, y, z, 16, false, false)) + loc = new Point3D(x, y, z); + } - public override int GetIdleSound() - { - return 0x2F8; - } + pixie.MoveToWorld(loc, map); + pixie.Combatant = target; + } + } - public override int GetAttackSound() - { - return Utility.Random( 0x2F5, 2 ); - } + public override int GetAngerSound() + { + return 0x2F8; + } - public override int GetHurtSound() - { - return 0x2F9; - } + public override int GetIdleSound() + { + return 0x2F8; + } - public override int GetDeathSound() - { - return 0x2F7; - } + public override int GetAttackSound() + { + return Utility.Random(0x2F5, 2); + } - public void CheckQueen() - { - if ( Map == null ) - return; + public override int GetHurtSound() + { + return 0x2F9; + } - if ( !m_SpawnedQueen ) - { - Say( 1042153 ); // Come forth my queen! + public override int GetDeathSound() + { + return 0x2F7; + } - m_Queen = new Silvani(); + public void CheckQueen() + { + if (Map == null) + return; - ((BaseCreature)m_Queen).Team = Team; + if (!m_SpawnedQueen) + { + Say(1042153); // Come forth my queen! - m_Queen.MoveToWorld( Location, Map ); + m_Queen = new Silvani(); - m_SpawnedQueen = true; - } - else if ( m_Queen != null && m_Queen.Deleted ) - { - m_Queen = null; - } - } + ((BaseCreature)m_Queen).Team = Team; - public override void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - CheckQueen(); + m_Queen.MoveToWorld(Location, Map); - if ( m_Queen != null ) - { - scalar *= 0.1; + m_SpawnedQueen = true; + } + else if (m_Queen != null && m_Queen.Deleted) + { + m_Queen = null; + } + } - if ( 0.1 >= Utility.RandomDouble() ) - SpawnPixies( caster ); - } - } + public override void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + CheckQueen(); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + if (m_Queen != null) + { + scalar *= 0.1; - defender.Damage( Utility.Random( 20, 10 ), this ); - defender.Stam -= Utility.Random( 20, 10 ); - defender.Mana -= Utility.Random( 20, 10 ); - } + if (0.1 >= Utility.RandomDouble()) + SpawnPixies(caster); + } + } - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - CheckQueen(); + defender.Damage(Utility.Random(20, 10), this); + defender.Stam -= Utility.Random(20, 10); + defender.Mana -= Utility.Random(20, 10); + } - if ( m_Queen != null && 0.1 >= Utility.RandomDouble() ) - SpawnPixies( attacker ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - attacker.Damage( Utility.Random( 20, 10 ), this ); - attacker.Stam -= Utility.Random( 20, 10 ); - attacker.Mana -= Utility.Random( 20, 10 ); - } + CheckQueen(); - public LordOaks( Serial serial ) : base( serial ) - { - } + if (m_Queen != null && 0.1 >= Utility.RandomDouble()) + SpawnPixies(attacker); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + attacker.Damage(Utility.Random(20, 10), this); + attacker.Stam -= Utility.Random(20, 10); + attacker.Mana -= Utility.Random(20, 10); + } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( m_Queen ); - writer.Write( m_SpawnedQueen ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(m_Queen); + writer.Write(m_SpawnedQueen); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - m_Queen = reader.ReadMobile(); - m_SpawnedQueen = reader.ReadBool(); + int version = reader.ReadInt(); - break; - } - } - } - } -} + switch (version) + { + case 0: + { + m_Queen = reader.ReadMobile(); + m_SpawnedQueen = reader.ReadBool(); + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Mephitis.cs b/Scripts/Mobiles/Special/Mephitis.cs index 7c3fa7f14..2c80b0802 100644 --- a/Scripts/Mobiles/Special/Mephitis.cs +++ b/Scripts/Mobiles/Special/Mephitis.cs @@ -1,86 +1,92 @@ using System; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class Mephitis : BaseChampion - { - public override ChampionSkullType SkullType => ChampionSkullType.Venom; + public class Mephitis : BaseChampion + { + [Constructible] + public Mephitis() : base(AIType.AI_Melee) + { + Body = 173; + BaseSoundID = 0x183; - public override Type[] UniqueList => new[] { typeof( Calm ) }; - public override Type[] SharedList => new[] { typeof(OblivionsNeedle), typeof(ANecromancerShroud), typeof(EmbroideredOakLeafCloak), typeof(TheMostKnowledgePerson) }; - public override Type[] DecorativeList => new[] { typeof( Web ), typeof( MonsterStatuette ) }; + SetStr(505, 1000); + SetDex(102, 300); + SetInt(402, 600); - public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.Spider }; + SetHits(3000); + SetStam(105, 600); - public override string DefaultName => "Mephitis"; + SetDamage(21, 33); - [Constructible] - public Mephitis() : base( AIType.AI_Melee ) - { - Body = 173; - BaseSoundID = 0x183; + SetDamageType(ResistanceType.Physical, 50); + SetDamageType(ResistanceType.Poison, 50); - SetStr( 505, 1000 ); - SetDex( 102, 300 ); - SetInt( 402, 600 ); + SetResistance(ResistanceType.Physical, 75, 80); + SetResistance(ResistanceType.Fire, 60, 70); + SetResistance(ResistanceType.Cold, 60, 70); + SetResistance(ResistanceType.Poison, 100); + SetResistance(ResistanceType.Energy, 60, 70); - SetHits( 3000 ); - SetStam( 105, 600 ); + SetSkill(SkillName.MagicResist, 70.7, 140.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - SetDamage( 21, 33 ); + Fame = 22500; + Karma = -22500; - SetDamageType( ResistanceType.Physical, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + VirtualArmor = 80; + } - SetResistance( ResistanceType.Physical, 75, 80 ); - SetResistance( ResistanceType.Fire, 60, 70 ); - SetResistance( ResistanceType.Cold, 60, 70 ); - SetResistance( ResistanceType.Poison, 100 ); - SetResistance( ResistanceType.Energy, 60, 70 ); + public Mephitis(Serial serial) : base(serial) + { + } - SetSkill( SkillName.MagicResist, 70.7, 140.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + public override ChampionSkullType SkullType => ChampionSkullType.Venom; - Fame = 22500; - Karma = -22500; + public override Type[] UniqueList => new[] { typeof(Calm) }; - VirtualArmor = 80; - } + public override Type[] SharedList => new[] + { + typeof(OblivionsNeedle), typeof(ANecromancerShroud), typeof(EmbroideredOakLeafCloak), + typeof(TheMostKnowledgePerson) + }; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 4 ); - } + public override Type[] DecorativeList => new[] { typeof(Web), typeof(MonsterStatuette) }; - public override Poison PoisonImmune => Poison.Lethal; - public override Poison HitPoison => Poison.Lethal; + public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.Spider }; - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override string DefaultName => "Mephitis"; - // TODO: Web ability - } + public override Poison PoisonImmune => Poison.Lethal; + public override Poison HitPoison => Poison.Lethal; - public Mephitis( Serial serial ) : base( serial ) - { - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 4); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - writer.Write( (int) 0 ); // version - } + // TODO: Web ability + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Neira.cs b/Scripts/Mobiles/Special/Neira.cs index ab1599b1b..68751dfcc 100644 --- a/Scripts/Mobiles/Special/Neira.cs +++ b/Scripts/Mobiles/Special/Neira.cs @@ -1,293 +1,297 @@ using System; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class Neira : BaseChampion - { - public override ChampionSkullType SkullType => ChampionSkullType.Death; + public class Neira : BaseChampion + { + private const double SpeedBoostScalar = 1.2; - public override Type[] UniqueList => new[] { typeof( ShroudOfDeciet ) }; - public override Type[] SharedList => new[] { typeof( ANecromancerShroud ), + private bool m_SpeedBoost; - typeof( CaptainJohnsHat ) }; + [Constructible] + public Neira() : base(AIType.AI_Mage) + { + Title = "the necromancer"; + Body = 401; + Hue = 0x83EC; - public override Type[] DecorativeList => new[] { typeof( WallBlood ), typeof( TatteredAncientMummyWrapping ) }; + SetStr(305, 425); + SetDex(72, 150); + SetInt(505, 750); - public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; + SetHits(4800); + SetStam(102, 300); - public override string DefaultName => "Neira"; + SetDamage(25, 35); - [Constructible] - public Neira() : base( AIType.AI_Mage ) - { - Title = "the necromancer"; - Body = 401; - Hue = 0x83EC; + SetDamageType(ResistanceType.Physical, 100); - SetStr( 305, 425 ); - SetDex( 72, 150 ); - SetInt( 505, 750 ); + SetResistance(ResistanceType.Physical, 25, 30); + SetResistance(ResistanceType.Fire, 35, 45); + SetResistance(ResistanceType.Cold, 50, 60); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 20, 30); - SetHits( 4800 ); - SetStam( 102, 300 ); + SetSkill(SkillName.EvalInt, 120.0); + SetSkill(SkillName.Magery, 120.0); + SetSkill(SkillName.Meditation, 120.0); + SetSkill(SkillName.MagicResist, 150.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - SetDamage( 25, 35 ); + Fame = 22500; + Karma = -22500; - SetDamageType( ResistanceType.Physical, 100 ); + VirtualArmor = 30; + Female = true; - SetResistance( ResistanceType.Physical, 25, 30 ); - SetResistance( ResistanceType.Fire, 35, 45 ); - SetResistance( ResistanceType.Cold, 50, 60 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 20, 30 ); + Item shroud = new HoodedShroudOfShadows(); - SetSkill( SkillName.EvalInt, 120.0 ); - SetSkill( SkillName.Magery, 120.0 ); - SetSkill( SkillName.Meditation, 120.0 ); - SetSkill( SkillName.MagicResist, 150.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + shroud.Movable = false; - Fame = 22500; - Karma = -22500; + AddItem(shroud); - VirtualArmor = 30; - Female = true; + Scimitar weapon = new Scimitar(); - Item shroud = new HoodedShroudOfShadows(); + weapon.Skill = SkillName.Wrestling; + weapon.Hue = 38; + weapon.Movable = false; - shroud.Movable = false; + AddItem(weapon); - AddItem( shroud ); + //new SkeletalMount().Rider = this; + AddItem(new VirtualMountItem(this)); + } - Scimitar weapon = new Scimitar(); + public Neira(Serial serial) : base(serial) + { + } - weapon.Skill = SkillName.Wrestling; - weapon.Hue = 38; - weapon.Movable = false; + public override ChampionSkullType SkullType => ChampionSkullType.Death; - AddItem( weapon ); + public override Type[] UniqueList => new[] { typeof(ShroudOfDeciet) }; - //new SkeletalMount().Rider = this; - AddItem( new VirtualMountItem( this ) ); - } + public override Type[] SharedList => new[] + { + typeof(ANecromancerShroud), - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 3 ); - AddLoot( LootPack.Meager ); - } + typeof(CaptainJohnsHat) + }; + + public override Type[] DecorativeList => new[] { typeof(WallBlood), typeof(TatteredAncientMummyWrapping) }; - public override bool OnBeforeDeath() - { - IMount mount = Mount; + public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; + + public override string DefaultName => "Neira"; - if ( mount != null ) - mount.Rider = null; + public override bool AlwaysMurderer => true; + public override bool BardImmune => !Core.SE; + public override bool Unprovokable => Core.SE; + public override bool Uncalmable => Core.SE; + public override Poison PoisonImmune => Poison.Deadly; + + public override bool ShowFameTitle => false; + public override bool ClickTitle => false; - (mount as Mobile)?.Delete(); - - return base.OnBeforeDeath(); - } - - private bool m_SpeedBoost; - - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - CheckSpeedBoost(); - base.OnDamage( amount, from, willKill ); - } - - private const double SpeedBoostScalar = 1.2; - - private void CheckSpeedBoost() - { - if ( Hits < (HitsMax / 4 ) ) - { - if ( !m_SpeedBoost ) - { - ActiveSpeed /= SpeedBoostScalar; - PassiveSpeed /= SpeedBoostScalar; - m_SpeedBoost = true; - } - } - else if ( m_SpeedBoost ) - { - ActiveSpeed *= SpeedBoostScalar; - PassiveSpeed *= SpeedBoostScalar; - m_SpeedBoost = false; - } - } - - private class VirtualMount : IMount - { - private VirtualMountItem m_Item; - - public Mobile Rider - { - get => m_Item.Rider; - set { } - } - - public VirtualMount( VirtualMountItem item ) - { - m_Item = item; - } - - public virtual void OnRiderDamaged( int amount, Mobile from, bool willKill ) - { - } - } - - private class VirtualMountItem : Item, IMountItem - { - private VirtualMount m_Mount; - - public Mobile Rider { get; private set; } - - public VirtualMountItem( Mobile mob ) - : base( 0x3EBB ) - { - Layer = Layer.Mount; - - Movable = false; - - Rider = mob; - m_Mount = new VirtualMount( this ); - } - - public IMount Mount => m_Mount; - - public VirtualMountItem( Serial serial ) - : base( serial ) - { - m_Mount = new VirtualMount( this ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - - writer.Write( (Mobile)Rider ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - Rider = reader.ReadMobile(); - - if ( Rider == null ) - Delete(); - } - } - - public override bool AlwaysMurderer => true; - public override bool BardImmune => !Core.SE; - public override bool Unprovokable => Core.SE; - public override bool Uncalmable => Core.SE; - public override Poison PoisonImmune => Poison.Deadly; - - public override bool ShowFameTitle => false; - public override bool ClickTitle => false; - - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); - - if ( 0.1 >= Utility.RandomDouble() ) // 10% chance to drop or throw an unholy bone - AddUnholyBone( defender, 0.25 ); - - CheckSpeedBoost(); - } - - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); - - if ( 0.1 >= Utility.RandomDouble() ) // 10% chance to drop or throw an unholy bone - AddUnholyBone( attacker, 0.25 ); - } - - public override void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - base.AlterDamageScalarFrom( caster, ref scalar ); - - if ( 0.1 >= Utility.RandomDouble() ) // 10% chance to throw an unholy bone - AddUnholyBone( caster, 1.0 ); - } - - public void AddUnholyBone( Mobile target, double chanceToThrow ) - { - if ( Map == null ) - return; - - if ( chanceToThrow >= Utility.RandomDouble() ) - { - Direction = GetDirectionTo( target ); - MovingEffect( target, 0xF7E, 10, 1, true, false, 0x496, 0 ); - new DelayTimer( this, target ).Start(); - } - else - { - new UnholyBone().MoveToWorld( Location, Map ); - } - } - - private class DelayTimer : Timer - { - private Mobile m_Mobile; - private Mobile m_Target; - - public DelayTimer( Mobile m, Mobile target ) : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_Target = target; - } - - protected override void OnTick() - { - if ( m_Mobile.CanBeHarmful( m_Target ) ) - { - m_Mobile.DoHarmful( m_Target ); - AOS.Damage( m_Target, m_Mobile, Utility.RandomMinMax( 10, 20 ), 100, 0, 0, 0, 0 ); - new UnholyBone().MoveToWorld( m_Target.Location, m_Target.Map ); - } - } - } - - public Neira( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version - writer.Write( m_SpeedBoost ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch( version ) - { - case 1: - { - m_SpeedBoost = reader.ReadBool(); - break; - } - } - } - } -} + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 3); + AddLoot(LootPack.Meager); + } + + public override bool OnBeforeDeath() + { + IMount mount = Mount; + + if (mount != null) + mount.Rider = null; + + (mount as Mobile)?.Delete(); + + return base.OnBeforeDeath(); + } + + public override void OnDamage(int amount, Mobile from, bool willKill) + { + CheckSpeedBoost(); + base.OnDamage(amount, from, willKill); + } + + private void CheckSpeedBoost() + { + if (Hits < HitsMax / 4) + { + if (!m_SpeedBoost) + { + ActiveSpeed /= SpeedBoostScalar; + PassiveSpeed /= SpeedBoostScalar; + m_SpeedBoost = true; + } + } + else if (m_SpeedBoost) + { + ActiveSpeed *= SpeedBoostScalar; + PassiveSpeed *= SpeedBoostScalar; + m_SpeedBoost = false; + } + } + + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); + + if (0.1 >= Utility.RandomDouble()) // 10% chance to drop or throw an unholy bone + AddUnholyBone(defender, 0.25); + + CheckSpeedBoost(); + } + + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); + + if (0.1 >= Utility.RandomDouble()) // 10% chance to drop or throw an unholy bone + AddUnholyBone(attacker, 0.25); + } + + public override void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + base.AlterDamageScalarFrom(caster, ref scalar); + + if (0.1 >= Utility.RandomDouble()) // 10% chance to throw an unholy bone + AddUnholyBone(caster, 1.0); + } + + public void AddUnholyBone(Mobile target, double chanceToThrow) + { + if (Map == null) + return; + + if (chanceToThrow >= Utility.RandomDouble()) + { + Direction = GetDirectionTo(target); + MovingEffect(target, 0xF7E, 10, 1, true, false, 0x496, 0); + new DelayTimer(this, target).Start(); + } + else + { + new UnholyBone().MoveToWorld(Location, Map); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + writer.Write(m_SpeedBoost); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_SpeedBoost = reader.ReadBool(); + break; + } + } + } + + private class VirtualMount : IMount + { + private VirtualMountItem m_Item; + + public VirtualMount(VirtualMountItem item) + { + m_Item = item; + } + + public Mobile Rider + { + get => m_Item.Rider; + set { } + } + + public virtual void OnRiderDamaged(int amount, Mobile from, bool willKill) + { + } + } + + private class VirtualMountItem : Item, IMountItem + { + private VirtualMount m_Mount; + + public VirtualMountItem(Mobile mob) + : base(0x3EBB) + { + Layer = Layer.Mount; + + Movable = false; + + Rider = mob; + m_Mount = new VirtualMount(this); + } + + public VirtualMountItem(Serial serial) + : base(serial) + { + m_Mount = new VirtualMount(this); + } + + public Mobile Rider{ get; private set; } + + public IMount Mount => m_Mount; + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(Rider); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Rider = reader.ReadMobile(); + + if (Rider == null) + Delete(); + } + } + + private class DelayTimer : Timer + { + private Mobile m_Mobile; + private Mobile m_Target; + + public DelayTimer(Mobile m, Mobile target) : base(TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_Target = target; + } + + protected override void OnTick() + { + if (m_Mobile.CanBeHarmful(m_Target)) + { + m_Mobile.DoHarmful(m_Target); + AOS.Damage(m_Target, m_Mobile, Utility.RandomMinMax(10, 20), 100, 0, 0, 0, 0); + new UnholyBone().MoveToWorld(m_Target.Location, m_Target.Map); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/OrderGuard.cs b/Scripts/Mobiles/Special/OrderGuard.cs index 76658593b..e3db5a597 100644 --- a/Scripts/Mobiles/Special/OrderGuard.cs +++ b/Scripts/Mobiles/Special/OrderGuard.cs @@ -1,38 +1,38 @@ -using Server.Items; using Server.Guilds; +using Server.Items; namespace Server.Mobiles { - public class OrderGuard : BaseShieldGuard - { - public override int Keyword => 0x21; // *order shield* - public override BaseShield Shield => new OrderShield(); - public override int SignupNumber => 1007141; // Sign up with a guild of order if thou art interested. - public override GuildType Type => GuildType.Order; + public class OrderGuard : BaseShieldGuard + { + [Constructible] + public OrderGuard() + { + } - public override bool BardImmune => true; + public OrderGuard(Serial serial) : base(serial) + { + } - [Constructible] - public OrderGuard() - { - } + public override int Keyword => 0x21; // *order shield* + public override BaseShield Shield => new OrderShield(); + public override int SignupNumber => 1007141; // Sign up with a guild of order if thou art interested. + public override GuildType Type => GuildType.Order; - public OrderGuard( Serial serial ) : base( serial ) - { - } + public override bool BardImmune => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Paragon.cs b/Scripts/Mobiles/Special/Paragon.cs index f55052f4d..8fc894436 100644 --- a/Scripts/Mobiles/Special/Paragon.cs +++ b/Scripts/Mobiles/Special/Paragon.cs @@ -3,212 +3,219 @@ using Server.Items; namespace Server.Mobiles { - public class Paragon - { - public static double ChestChance = .10; // Chance that a paragon will carry a paragon chest - public static double ChocolateIngredientChance = .20; // Chance that a paragon will drop a chocolatiering ingredient - public static Map[] Maps = { - Map.Ilshenar - }; + public class Paragon + { + public static double ChestChance = .10; // Chance that a paragon will carry a paragon chest + public static double ChocolateIngredientChance = .20; // Chance that a paragon will drop a chocolatiering ingredient - private static TimeSpan FastRegenRate = TimeSpan.FromSeconds( .5 ); - private static TimeSpan CPUSaverRate = TimeSpan.FromSeconds( 2 ); + public static Map[] Maps = + { + Map.Ilshenar + }; - private class ParagonStamRegen : Timer - { - private BaseCreature m_Owner; + private static TimeSpan FastRegenRate = TimeSpan.FromSeconds(.5); + private static TimeSpan CPUSaverRate = TimeSpan.FromSeconds(2); - public ParagonStamRegen( Mobile m ) - : base( FastRegenRate, FastRegenRate ) - { - Priority = TimerPriority.FiftyMS; + public static Type[] Artifacts = + { + typeof(GoldBricks), typeof(PhillipsWoodenSteed), + typeof(AlchemistsBauble), typeof(ArcticDeathDealer), + typeof(BlazeOfDeath), typeof(BowOfTheJukaKing), + typeof(BurglarsBandana), typeof(CavortingClub), + typeof(EnchantedTitanLegBone), typeof(GwennosHarp), + typeof(IolosLute), typeof(LunaLance), + typeof(NightsKiss), typeof(NoxRangersHeavyCrossbow), + typeof(OrcishVisage), typeof(PolarBearMask), + typeof(ShieldOfInvulnerability), typeof(StaffOfPower), + typeof(VioletCourage), typeof(HeartOfTheLion), + typeof(WrathOfTheDryad), typeof(PixieSwatter), + typeof(GlovesOfThePugilist) + }; - m_Owner = m as BaseCreature; - } + public static int Hue = 0x501; // Paragon hue - protected override void OnTick() - { - if ( !m_Owner.Deleted && m_Owner.IsParagon && m_Owner .Map != Map.Internal ) - { - m_Owner.Stam++; + // Buffs + public static double HitsBuff = 5.0; + public static double StrBuff = 1.05; + public static double IntBuff = 1.20; + public static double DexBuff = 1.20; + public static double SkillsBuff = 1.20; + public static double SpeedBuff = 1.20; + public static double FameBuff = 1.40; + public static double KarmaBuff = 1.40; + public static int DamageBuff = 5; - Delay = Interval = ( m_Owner.Stam < ( m_Owner.StamMax * .75 ) ) ? FastRegenRate : CPUSaverRate; - } - else - { - Stop(); - } - } - } + public static void Convert(BaseCreature bc) + { + if (bc.IsParagon) + return; - public static Type[] Artifacts = { - typeof( GoldBricks ), typeof( PhillipsWoodenSteed ), - typeof( AlchemistsBauble ), typeof( ArcticDeathDealer ), - typeof( BlazeOfDeath ), typeof( BowOfTheJukaKing ), - typeof( BurglarsBandana ), typeof( CavortingClub ), - typeof( EnchantedTitanLegBone ), typeof( GwennosHarp ), - typeof( IolosLute ), typeof( LunaLance ), - typeof( NightsKiss ), typeof( NoxRangersHeavyCrossbow ), - typeof( OrcishVisage ), typeof( PolarBearMask ), - typeof( ShieldOfInvulnerability ), typeof( StaffOfPower ), - typeof( VioletCourage ), typeof( HeartOfTheLion ), - typeof( WrathOfTheDryad ), typeof( PixieSwatter ), - typeof( GlovesOfThePugilist ) - }; + bc.Hue = Hue; - public static int Hue = 0x501; // Paragon hue + if (bc.HitsMaxSeed >= 0) + bc.HitsMaxSeed = (int)(bc.HitsMaxSeed * HitsBuff); - // Buffs - public static double HitsBuff = 5.0; - public static double StrBuff = 1.05; - public static double IntBuff = 1.20; - public static double DexBuff = 1.20; - public static double SkillsBuff = 1.20; - public static double SpeedBuff = 1.20; - public static double FameBuff = 1.40; - public static double KarmaBuff = 1.40; - public static int DamageBuff = 5; + bc.RawStr = (int)(bc.RawStr * StrBuff); + bc.RawInt = (int)(bc.RawInt * IntBuff); + bc.RawDex = (int)(bc.RawDex * DexBuff); - public static void Convert( BaseCreature bc ) - { - if ( bc.IsParagon ) - return; + bc.Hits = bc.HitsMax; + bc.Mana = bc.ManaMax; + bc.Stam = bc.StamMax; - bc.Hue = Hue; + for (int i = 0; i < bc.Skills.Length; i++) + { + Skill skill = bc.Skills[i]; - if ( bc.HitsMaxSeed >= 0 ) - bc.HitsMaxSeed = (int)( bc.HitsMaxSeed * HitsBuff ); + if (skill.Base > 0.0) + skill.Base *= SkillsBuff; + } - bc.RawStr = (int)( bc.RawStr * StrBuff ); - bc.RawInt = (int)( bc.RawInt * IntBuff ); - bc.RawDex = (int)( bc.RawDex * DexBuff ); + bc.PassiveSpeed /= SpeedBuff; + bc.ActiveSpeed /= SpeedBuff; + bc.CurrentSpeed = bc.PassiveSpeed; - bc.Hits = bc.HitsMax; - bc.Mana = bc.ManaMax; - bc.Stam = bc.StamMax; + bc.DamageMin += DamageBuff; + bc.DamageMax += DamageBuff; - for( int i = 0; i < bc.Skills.Length; i++ ) - { - Skill skill = (Skill)bc.Skills[i]; + if (bc.Fame > 0) + bc.Fame = (int)(bc.Fame * FameBuff); - if ( skill.Base > 0.0 ) - skill.Base *= SkillsBuff; - } + if (bc.Fame > 32000) + bc.Fame = 32000; - bc.PassiveSpeed /= SpeedBuff; - bc.ActiveSpeed /= SpeedBuff; - bc.CurrentSpeed = bc.PassiveSpeed; + // TODO: Mana regeneration rate = Sqrt( buffedFame ) / 4 - bc.DamageMin += DamageBuff; - bc.DamageMax += DamageBuff; + if (bc.Karma != 0) + { + bc.Karma = (int)(bc.Karma * KarmaBuff); - if ( bc.Fame > 0 ) - bc.Fame = (int)( bc.Fame * FameBuff ); + if (Math.Abs(bc.Karma) > 32000) + bc.Karma = 32000 * Math.Sign(bc.Karma); + } - if ( bc.Fame > 32000 ) - bc.Fame = 32000; + new ParagonStamRegen(bc).Start(); + } - // TODO: Mana regeneration rate = Sqrt( buffedFame ) / 4 + public static void UnConvert(BaseCreature bc) + { + if (!bc.IsParagon) + return; - if ( bc.Karma != 0 ) - { - bc.Karma = (int)( bc.Karma * KarmaBuff ); + bc.Hue = 0; - if ( Math.Abs( bc.Karma ) > 32000 ) - bc.Karma = 32000 * Math.Sign( bc.Karma ); - } + if (bc.HitsMaxSeed >= 0) + bc.HitsMaxSeed = (int)(bc.HitsMaxSeed / HitsBuff); - new ParagonStamRegen( bc ).Start(); - } + bc.RawStr = (int)(bc.RawStr / StrBuff); + bc.RawInt = (int)(bc.RawInt / IntBuff); + bc.RawDex = (int)(bc.RawDex / DexBuff); - public static void UnConvert( BaseCreature bc ) - { - if ( !bc.IsParagon ) - return; + bc.Hits = bc.HitsMax; + bc.Mana = bc.ManaMax; + bc.Stam = bc.StamMax; - bc.Hue = 0; + for (int i = 0; i < bc.Skills.Length; i++) + { + Skill skill = bc.Skills[i]; - if ( bc.HitsMaxSeed >= 0 ) - bc.HitsMaxSeed = (int)( bc.HitsMaxSeed / HitsBuff ); + if (skill.Base > 0.0) + skill.Base /= SkillsBuff; + } - bc.RawStr = (int)( bc.RawStr / StrBuff ); - bc.RawInt = (int)( bc.RawInt / IntBuff ); - bc.RawDex = (int)( bc.RawDex / DexBuff ); + bc.PassiveSpeed *= SpeedBuff; + bc.ActiveSpeed *= SpeedBuff; + bc.CurrentSpeed = bc.PassiveSpeed; - bc.Hits = bc.HitsMax; - bc.Mana = bc.ManaMax; - bc.Stam = bc.StamMax; + bc.DamageMin -= DamageBuff; + bc.DamageMax -= DamageBuff; - for( int i = 0; i < bc.Skills.Length; i++ ) - { - Skill skill = (Skill)bc.Skills[i]; + if (bc.Fame > 0) + bc.Fame = (int)(bc.Fame / FameBuff); + if (bc.Karma != 0) + bc.Karma = (int)(bc.Karma / KarmaBuff); + } - if ( skill.Base > 0.0 ) - skill.Base /= SkillsBuff; - } + public static bool CheckConvert(BaseCreature bc) + { + return CheckConvert(bc, bc.Location, bc.Map); + } - bc.PassiveSpeed *= SpeedBuff; - bc.ActiveSpeed *= SpeedBuff; - bc.CurrentSpeed = bc.PassiveSpeed; + public static bool CheckConvert(BaseCreature bc, Point3D location, Map m) + { + if (!Core.AOS) + return false; - bc.DamageMin -= DamageBuff; - bc.DamageMax -= DamageBuff; + if (Array.IndexOf(Maps, m) == -1) + return false; - if ( bc.Fame > 0 ) - bc.Fame = (int)( bc.Fame / FameBuff ); - if ( bc.Karma != 0 ) - bc.Karma = (int)( bc.Karma / KarmaBuff ); - } + if (bc is BaseChampion || bc is Harrower || bc is BaseVendor || bc is BaseEscortable || bc is Clone || + bc.IsParagon) + return false; - public static bool CheckConvert( BaseCreature bc ) - { - return CheckConvert( bc, bc.Location, bc.Map ); - } + int fame = bc.Fame; - public static bool CheckConvert( BaseCreature bc, Point3D location, Map m ) - { - if ( !Core.AOS ) - return false; + if (fame > 32000) + fame = 32000; - if ( Array.IndexOf( Maps, m ) == -1 ) - return false; + double chance = 1 / Math.Round(20.0 - fame / 3200); - if ( bc is BaseChampion || bc is Harrower || bc is BaseVendor || bc is BaseEscortable || bc is Clone || bc.IsParagon ) - return false; + return chance > Utility.RandomDouble(); + } - int fame = bc.Fame; + public static bool CheckArtifactChance(Mobile m, BaseCreature bc) + { + if (!Core.AOS) + return false; - if ( fame > 32000 ) - fame = 32000; + double fame = bc.Fame; - double chance = 1 / Math.Round( 20.0 - ( fame / 3200 )); + if (fame > 32000) + fame = 32000; - return ( chance > Utility.RandomDouble() ); - } + double chance = + 1 / (Math.Max(10, 100 * (0.83 - Math.Round(Math.Log(Math.Round(fame / 6000, 3) + 0.001, 10), 3))) * + (100 - Math.Sqrt(m.Luck)) / 100.0); - public static bool CheckArtifactChance( Mobile m, BaseCreature bc ) - { - if ( !Core.AOS ) - return false; + return chance > Utility.RandomDouble(); + } - double fame = (double)bc.Fame; + public static void GiveArtifactTo(Mobile m) + { + Item item = (Item)Activator.CreateInstance(Artifacts[Utility.Random(Artifacts.Length)]); - if ( fame > 32000 ) - fame = 32000; + if (m.AddToBackpack(item)) + m.SendMessage("As a reward for slaying the mighty paragon, an artifact has been placed in your backpack."); + else + m.SendMessage( + "As your backpack is full, your reward for destroying the legendary paragon has been placed at your feet."); + } - double chance = 1 / ( Math.Max( 10, 100 * ( 0.83 - Math.Round( Math.Log( Math.Round( fame / 6000, 3 ) + 0.001, 10 ), 3 ) ) ) * ( 100 - Math.Sqrt( m.Luck ) ) / 100.0 ); + private class ParagonStamRegen : Timer + { + private BaseCreature m_Owner; - return chance > Utility.RandomDouble(); - } + public ParagonStamRegen(Mobile m) + : base(FastRegenRate, FastRegenRate) + { + Priority = TimerPriority.FiftyMS; - public static void GiveArtifactTo( Mobile m ) - { - Item item = (Item)Activator.CreateInstance( Artifacts[Utility.Random(Artifacts.Length)] ); + m_Owner = m as BaseCreature; + } - if ( m.AddToBackpack( item ) ) - m.SendMessage( "As a reward for slaying the mighty paragon, an artifact has been placed in your backpack." ); - else - m.SendMessage( "As your backpack is full, your reward for destroying the legendary paragon has been placed at your feet." ); - } - } -} + protected override void OnTick() + { + if (!m_Owner.Deleted && m_Owner.IsParagon && m_Owner.Map != Map.Internal) + { + m_Owner.Stam++; + + Delay = Interval = m_Owner.Stam < m_Owner.StamMax * .75 ? FastRegenRate : CPUSaverRate; + } + else + { + Stop(); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Rikktor.cs b/Scripts/Mobiles/Special/Rikktor.cs index 466d0869e..ac39ea1a6 100644 --- a/Scripts/Mobiles/Special/Rikktor.cs +++ b/Scripts/Mobiles/Special/Rikktor.cs @@ -1,162 +1,173 @@ using System; using System.Collections; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class Rikktor : BaseChampion - { - public override ChampionSkullType SkullType => ChampionSkullType.Power; + public class Rikktor : BaseChampion + { + [Constructible] + public Rikktor() : base(AIType.AI_Melee) + { + Body = 172; - public override Type[] UniqueList => new[] { typeof( CrownOfTalKeesh ) }; - public override Type[] SharedList => new[] { typeof( TheMostKnowledgePerson ), - typeof( BraveKnightOfTheBritannia ), - typeof( LieutenantOfTheBritannianRoyalGuard ) }; + SetStr(701, 900); + SetDex(201, 350); + SetInt(51, 100); - public override Type[] DecorativeList => new[] { typeof( LavaTile ), - typeof( MonsterStatuette ), - typeof( MonsterStatuette ) }; + SetHits(3000); + SetStam(203, 650); - public override MonsterStatuetteType[] StatueTypes => new[] { MonsterStatuetteType.OphidianArchMage, - MonsterStatuetteType.OphidianWarrior }; + SetDamage(28, 55); - public override string DefaultName => "Rikktor"; + SetDamageType(ResistanceType.Physical, 25); + SetDamageType(ResistanceType.Fire, 50); + SetDamageType(ResistanceType.Energy, 25); - [Constructible] - public Rikktor() : base( AIType.AI_Melee ) - { - Body = 172; + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 80, 90); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 80, 90); + SetResistance(ResistanceType.Energy, 80, 90); - SetStr( 701, 900 ); - SetDex( 201, 350 ); - SetInt( 51, 100 ); + SetSkill(SkillName.Anatomy, 100.0); + SetSkill(SkillName.MagicResist, 140.2, 160.0); + SetSkill(SkillName.Tactics, 100.0); - SetHits( 3000 ); - SetStam( 203, 650 ); + Fame = 22500; + Karma = -22500; - SetDamage( 28, 55 ); + VirtualArmor = 130; + } - SetDamageType( ResistanceType.Physical, 25 ); - SetDamageType( ResistanceType.Fire, 50 ); - SetDamageType( ResistanceType.Energy, 25 ); + public Rikktor(Serial serial) : base(serial) + { + } - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 80, 90 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 80, 90 ); - SetResistance( ResistanceType.Energy, 80, 90 ); + public override ChampionSkullType SkullType => ChampionSkullType.Power; - SetSkill( SkillName.Anatomy, 100.0 ); - SetSkill( SkillName.MagicResist, 140.2, 160.0 ); - SetSkill( SkillName.Tactics, 100.0 ); + public override Type[] UniqueList => new[] { typeof(CrownOfTalKeesh) }; - Fame = 22500; - Karma = -22500; + public override Type[] SharedList => new[] + { + typeof(TheMostKnowledgePerson), + typeof(BraveKnightOfTheBritannia), + typeof(LieutenantOfTheBritannianRoyalGuard) + }; - VirtualArmor = 130; - } + public override Type[] DecorativeList => new[] + { + typeof(LavaTile), + typeof(MonsterStatuette), + typeof(MonsterStatuette) + }; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 4 ); - } + public override MonsterStatuetteType[] StatueTypes => new[] + { + MonsterStatuetteType.OphidianArchMage, + MonsterStatuetteType.OphidianWarrior + }; - public override Poison PoisonImmune => Poison.Lethal; - public override ScaleType ScaleType => ScaleType.All; - public override int Scales => 20; + public override string DefaultName => "Rikktor"; - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override Poison PoisonImmune => Poison.Lethal; + public override ScaleType ScaleType => ScaleType.All; + public override int Scales => 20; - if ( 0.2 >= Utility.RandomDouble() ) - Earthquake(); - } + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 4); + } - public void Earthquake() - { - Map map = Map; + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - if ( map == null ) - return; + if (0.2 >= Utility.RandomDouble()) + Earthquake(); + } - ArrayList targets = new ArrayList(); + public void Earthquake() + { + Map map = Map; - foreach ( Mobile m in GetMobilesInRange( 8 ) ) - { - if ( m == this || !CanBeHarmful( m ) ) - continue; + if (map == null) + return; - if ( m is BaseCreature && (((BaseCreature)m).Controlled || ((BaseCreature)m).Summoned || ((BaseCreature)m).Team != Team) ) - targets.Add( m ); - else if ( m.Player ) - targets.Add( m ); - } + ArrayList targets = new ArrayList(); - PlaySound( 0x2F3 ); + foreach (Mobile m in GetMobilesInRange(8)) + { + if (m == this || !CanBeHarmful(m)) + continue; - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = (Mobile)targets[i]; + if (m is BaseCreature && (((BaseCreature)m).Controlled || ((BaseCreature)m).Summoned || + ((BaseCreature)m).Team != Team)) + targets.Add(m); + else if (m.Player) + targets.Add(m); + } - double damage = m.Hits * 0.6; + PlaySound(0x2F3); - if ( damage < 10.0 ) - damage = 10.0; - else if ( damage > 75.0 ) - damage = 75.0; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = (Mobile)targets[i]; - DoHarmful( m ); + double damage = m.Hits * 0.6; - AOS.Damage( m, this, (int)damage, 100, 0, 0, 0, 0 ); + if (damage < 10.0) + damage = 10.0; + else if (damage > 75.0) + damage = 75.0; - if ( m.Alive && m.Body.IsHuman && !m.Mounted ) - m.Animate( 20, 7, 1, true, false, 0 ); // take hit - } - } + DoHarmful(m); - public override int GetAngerSound() - { - return Utility.Random( 0x2CE, 2 ); - } + AOS.Damage(m, this, (int)damage, 100, 0, 0, 0, 0); - public override int GetIdleSound() - { - return 0x2D2; - } + if (m.Alive && m.Body.IsHuman && !m.Mounted) + m.Animate(20, 7, 1, true, false, 0); // take hit + } + } - public override int GetAttackSound() - { - return Utility.Random( 0x2C7, 5 ); - } + public override int GetAngerSound() + { + return Utility.Random(0x2CE, 2); + } - public override int GetHurtSound() - { - return 0x2D1; - } + public override int GetIdleSound() + { + return 0x2D2; + } - public override int GetDeathSound() - { - return 0x2CC; - } + public override int GetAttackSound() + { + return Utility.Random(0x2C7, 5); + } - public Rikktor( Serial serial ) : base( serial ) - { - } + public override int GetHurtSound() + { + return 0x2D1; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override int GetDeathSound() + { + return 0x2CC; + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Semidar.cs b/Scripts/Mobiles/Special/Semidar.cs index 9a3733341..1e167eac1 100644 --- a/Scripts/Mobiles/Special/Semidar.cs +++ b/Scripts/Mobiles/Special/Semidar.cs @@ -1,144 +1,148 @@ using System; using System.Collections; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Items; namespace Server.Mobiles { - public class Semidar : BaseChampion - { - public override ChampionSkullType SkullType => ChampionSkullType.Pain; + public class Semidar : BaseChampion + { + [Constructible] + public Semidar() : base(AIType.AI_Mage) + { + Body = 174; + BaseSoundID = 0x4B0; - public override Type[] UniqueList => new[] { typeof( GladiatorsCollar ) }; - public override Type[] SharedList => new[] { typeof(RoyalGuardSurvivalKnife), typeof(ANecromancerShroud), typeof(LieutenantOfTheBritannianRoyalGuard) }; - public override Type[] DecorativeList => new[] { typeof( LavaTile ), typeof( DemonSkull ) }; + SetStr(502, 600); + SetDex(102, 200); + SetInt(601, 750); - public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; + SetHits(1500); + SetStam(103, 250); - public override string DefaultName => "Semidar"; + SetDamage(29, 35); - [Constructible] - public Semidar() : base( AIType.AI_Mage ) - { - Body = 174; - BaseSoundID = 0x4B0; + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Fire, 25); - SetStr( 502, 600 ); - SetDex( 102, 200 ); - SetInt( 601, 750 ); + SetResistance(ResistanceType.Physical, 20, 30); + SetResistance(ResistanceType.Fire, 50, 60); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 20, 30); + SetResistance(ResistanceType.Energy, 10, 20); - SetHits( 1500 ); - SetStam( 103, 250 ); + SetSkill(SkillName.EvalInt, 95.1, 100.0); + SetSkill(SkillName.Magery, 90.1, 105.0); + SetSkill(SkillName.Meditation, 95.1, 100.0); + SetSkill(SkillName.MagicResist, 120.2, 140.0); + SetSkill(SkillName.Tactics, 90.1, 105.0); + SetSkill(SkillName.Wrestling, 90.1, 105.0); - SetDamage( 29, 35 ); + Fame = 24000; + Karma = -24000; - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Fire, 25 ); + VirtualArmor = 20; + } - SetResistance( ResistanceType.Physical, 20, 30 ); - SetResistance( ResistanceType.Fire, 50, 60 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 20, 30 ); - SetResistance( ResistanceType.Energy, 10, 20 ); + public Semidar(Serial serial) : base(serial) + { + } - SetSkill( SkillName.EvalInt, 95.1, 100.0 ); - SetSkill( SkillName.Magery, 90.1, 105.0 ); - SetSkill( SkillName.Meditation, 95.1, 100.0 ); - SetSkill( SkillName.MagicResist, 120.2, 140.0 ); - SetSkill( SkillName.Tactics, 90.1, 105.0 ); - SetSkill( SkillName.Wrestling, 90.1, 105.0 ); + public override ChampionSkullType SkullType => ChampionSkullType.Pain; - Fame = 24000; - Karma = -24000; + public override Type[] UniqueList => new[] { typeof(GladiatorsCollar) }; - VirtualArmor = 20; - } + public override Type[] SharedList => new[] + { typeof(RoyalGuardSurvivalKnife), typeof(ANecromancerShroud), typeof(LieutenantOfTheBritannianRoyalGuard) }; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 4 ); - AddLoot( LootPack.FilthyRich ); - } + public override Type[] DecorativeList => new[] { typeof(LavaTile), typeof(DemonSkull) }; - public override bool Unprovokable => true; - public override Poison PoisonImmune => Poison.Lethal; + public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; - public override void CheckReflect( Mobile caster, ref bool reflect ) - { - if ( caster.Body.IsMale ) - reflect = true; // Always reflect if caster isn't female - } + public override string DefaultName => "Semidar"; - public override void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - if ( caster.Body.IsMale ) - scalar = 20; // Male bodies always reflect.. damage scaled 20x - } + public override bool Unprovokable => true; + public override Poison PoisonImmune => Poison.Lethal; - public void DrainLife() - { - if ( Map == null ) - return; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 4); + AddLoot(LootPack.FilthyRich); + } - ArrayList list = new ArrayList(); + public override void CheckReflect(Mobile caster, ref bool reflect) + { + if (caster.Body.IsMale) + reflect = true; // Always reflect if caster isn't female + } - foreach ( Mobile m in GetMobilesInRange( 2 ) ) - { - if ( m == this || !CanBeHarmful( m ) ) - continue; + public override void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + if (caster.Body.IsMale) + scalar = 20; // Male bodies always reflect.. damage scaled 20x + } - if ( m is BaseCreature && (((BaseCreature)m).Controlled || ((BaseCreature)m).Summoned || ((BaseCreature)m).Team != Team) ) - list.Add( m ); - else if ( m.Player ) - list.Add( m ); - } + public void DrainLife() + { + if (Map == null) + return; - foreach ( Mobile m in list ) - { - DoHarmful( m ); + ArrayList list = new ArrayList(); - m.FixedParticles( 0x374A, 10, 15, 5013, 0x496, 0, EffectLayer.Waist ); - m.PlaySound( 0x231 ); + foreach (Mobile m in GetMobilesInRange(2)) + { + if (m == this || !CanBeHarmful(m)) + continue; - m.SendMessage( "You feel the life drain out of you!" ); + if (m is BaseCreature && (((BaseCreature)m).Controlled || ((BaseCreature)m).Summoned || + ((BaseCreature)m).Team != Team)) + list.Add(m); + else if (m.Player) + list.Add(m); + } - int toDrain = Utility.RandomMinMax( 10, 40 ); + foreach (Mobile m in list) + { + DoHarmful(m); - Hits += toDrain; - m.Damage( toDrain, this ); - } - } + m.FixedParticles(0x374A, 10, 15, 5013, 0x496, 0, EffectLayer.Waist); + m.PlaySound(0x231); - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + m.SendMessage("You feel the life drain out of you!"); - if ( 0.25 >= Utility.RandomDouble() ) - DrainLife(); - } + int toDrain = Utility.RandomMinMax(10, 40); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + Hits += toDrain; + m.Damage(toDrain, this); + } + } - if ( 0.25 >= Utility.RandomDouble() ) - DrainLife(); - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public Semidar( Serial serial ) : base( serial ) - { - } + if (0.25 >= Utility.RandomDouble()) + DrainLife(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + if (0.25 >= Utility.RandomDouble()) + DrainLife(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Serado.cs b/Scripts/Mobiles/Special/Serado.cs index 5d6eadc2f..25a6707ac 100644 --- a/Scripts/Mobiles/Special/Serado.cs +++ b/Scripts/Mobiles/Special/Serado.cs @@ -1,185 +1,194 @@ using System; using System.Collections; -using Server.Items; using Server.Engines.CannedEvil; +using Server.Engines.Plants; +using Server.Items; namespace Server.Mobiles { - public class Serado : BaseChampion - { - public override ChampionSkullType SkullType => ChampionSkullType.Power; + public class Serado : BaseChampion + { + [Constructible] + public Serado() : base(AIType.AI_Melee) + { + Title = "the awakened"; - public override Type[] UniqueList => new[] { typeof( Pacify ) }; - public override Type[] SharedList => new[] { typeof( BraveKnightOfTheBritannia ), - typeof( DetectiveBoots ), - typeof( EmbroideredOakLeafCloak ), - typeof( LieutenantOfTheBritannianRoyalGuard ) }; + Body = 249; + Hue = 0x96C; - public override Type[] DecorativeList => new[] { typeof( Futon ), typeof( SwampTile ) }; + SetStr(1000); + SetDex(150); + SetInt(300); - public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; + SetHits(9000); + SetMana(300); - public override WeaponAbility GetWeaponAbility() => WeaponAbility.DoubleStrike; + SetDamage(29, 35); - public override string DefaultName => "Serado"; + SetDamageType(ResistanceType.Physical, 70); + SetDamageType(ResistanceType.Poison, 20); + SetDamageType(ResistanceType.Energy, 10); - [Constructible] - public Serado() : base( AIType.AI_Melee ) - { - Title = "the awakened"; + SetResistance(ResistanceType.Physical, 30); + SetResistance(ResistanceType.Fire, 60); + SetResistance(ResistanceType.Cold, 60); + SetResistance(ResistanceType.Poison, 90); + SetResistance(ResistanceType.Energy, 50); - Body = 249; - Hue = 0x96C; + SetSkill(SkillName.MagicResist, 120.0); + SetSkill(SkillName.Tactics, 120.0); + SetSkill(SkillName.Wrestling, 70.0); + SetSkill(SkillName.Poisoning, 150.0); - SetStr( 1000 ); - SetDex( 150 ); - SetInt( 300 ); + Fame = 22500; + Karma = -22500; - SetHits( 9000 ); - SetMana( 300 ); + PackItem(Seed.RandomBonsaiSeed()); + } - SetDamage( 29, 35 ); + public Serado(Serial serial) : base(serial) + { + } - SetDamageType( ResistanceType.Physical, 70 ); - SetDamageType( ResistanceType.Poison, 20 ); - SetDamageType( ResistanceType.Energy, 10 ); + public override ChampionSkullType SkullType => ChampionSkullType.Power; - SetResistance( ResistanceType.Physical, 30 ); - SetResistance( ResistanceType.Fire, 60 ); - SetResistance( ResistanceType.Cold, 60 ); - SetResistance( ResistanceType.Poison, 90 ); - SetResistance( ResistanceType.Energy, 50 ); + public override Type[] UniqueList => new[] { typeof(Pacify) }; - SetSkill( SkillName.MagicResist, 120.0 ); - SetSkill( SkillName.Tactics, 120.0 ); - SetSkill( SkillName.Wrestling, 70.0 ); - SetSkill( SkillName.Poisoning, 150.0 ); + public override Type[] SharedList => new[] + { + typeof(BraveKnightOfTheBritannia), + typeof(DetectiveBoots), + typeof(EmbroideredOakLeafCloak), + typeof(LieutenantOfTheBritannianRoyalGuard) + }; - Fame = 22500; - Karma = -22500; + public override Type[] DecorativeList => new[] { typeof(Futon), typeof(SwampTile) }; - PackItem( Engines.Plants.Seed.RandomBonsaiSeed() ); - } + public override MonsterStatuetteType[] StatueTypes => new MonsterStatuetteType[] { }; - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 4 ); - AddLoot( LootPack.FilthyRich ); - AddLoot( LootPack.Gems, 6 ); - } + public override string DefaultName => "Serado"; - public override int TreasureMapLevel => 5; + public override int TreasureMapLevel => 5; - public override Poison HitPoison => Poison.Lethal; - public override Poison PoisonImmune => Poison.Lethal; - public override double HitPoisonChance => 0.8; + public override Poison HitPoison => Poison.Lethal; + public override Poison PoisonImmune => Poison.Lethal; + public override double HitPoisonChance => 0.8; - public override int Feathers => 30; + public override int Feathers => 30; - public override bool ShowFameTitle => false; - public override bool ClickTitle => false; + public override bool ShowFameTitle => false; + public override bool ClickTitle => false; - // TODO: Hit Lightning Area + public override WeaponAbility GetWeaponAbility() + { + return WeaponAbility.DoubleStrike; + } - public override void OnDamagedBySpell( Mobile attacker ) - { - base.OnDamagedBySpell( attacker ); + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 4); + AddLoot(LootPack.FilthyRich); + AddLoot(LootPack.Gems, 6); + } - ScaleResistances(); - DoCounter( attacker ); - } + // TODO: Hit Lightning Area - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + public override void OnDamagedBySpell(Mobile attacker) + { + base.OnDamagedBySpell(attacker); - ScaleResistances(); - DoCounter( attacker ); - } + ScaleResistances(); + DoCounter(attacker); + } - private void ScaleResistances() - { - double hitsLost = (HitsMax - Hits) / (double)HitsMax; + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - SetResistance( ResistanceType.Physical, 30 + (int)(hitsLost * ( 95 - 30 )) ); - SetResistance( ResistanceType.Fire, 60 + (int)(hitsLost * ( 95 - 60 )) ); - SetResistance( ResistanceType.Cold, 60 + (int)(hitsLost * ( 95 - 60 )) ); - SetResistance( ResistanceType.Poison, 90 + (int)(hitsLost * ( 95 - 90 )) ); - SetResistance( ResistanceType.Energy, 50 + (int)(hitsLost * ( 95 - 50 )) ); - } + ScaleResistances(); + DoCounter(attacker); + } - private void DoCounter( Mobile attacker ) - { - if ( Map == null || ( attacker is BaseCreature && ((BaseCreature)attacker).BardProvoked ) ) - return; + private void ScaleResistances() + { + double hitsLost = (HitsMax - Hits) / (double)HitsMax; - if ( 0.2 > Utility.RandomDouble() ) - { - /* Counterattack with Hit Poison Area - * 20-25 damage, unresistable - * Lethal poison, 100% of the time - * Particle effect: Type: "2" From: "0x4061A107" To: "0x0" ItemId: "0x36BD" ItemIdName: "explosion" FromLocation: "(296 615, 17)" ToLocation: "(296 615, 17)" Speed: "1" Duration: "10" FixedDirection: "True" Explode: "False" Hue: "0xA6" RenderMode: "0x0" Effect: "0x1F78" ExplodeEffect: "0x1" ExplodeSound: "0x0" Serial: "0x4061A107" Layer: "255" Unknown: "0x0" - * Doesn't work on provoked monsters - */ + SetResistance(ResistanceType.Physical, 30 + (int)(hitsLost * (95 - 30))); + SetResistance(ResistanceType.Fire, 60 + (int)(hitsLost * (95 - 60))); + SetResistance(ResistanceType.Cold, 60 + (int)(hitsLost * (95 - 60))); + SetResistance(ResistanceType.Poison, 90 + (int)(hitsLost * (95 - 90))); + SetResistance(ResistanceType.Energy, 50 + (int)(hitsLost * (95 - 50))); + } - Mobile target = null; + private void DoCounter(Mobile attacker) + { + if (Map == null || attacker is BaseCreature && ((BaseCreature)attacker).BardProvoked) + return; - if ( attacker is BaseCreature ) - { - Mobile m = ((BaseCreature)attacker).GetMaster(); + if (0.2 > Utility.RandomDouble()) + { + /* Counterattack with Hit Poison Area + * 20-25 damage, unresistable + * Lethal poison, 100% of the time + * Particle effect: Type: "2" From: "0x4061A107" To: "0x0" ItemId: "0x36BD" ItemIdName: "explosion" FromLocation: "(296 615, 17)" ToLocation: "(296 615, 17)" Speed: "1" Duration: "10" FixedDirection: "True" Explode: "False" Hue: "0xA6" RenderMode: "0x0" Effect: "0x1F78" ExplodeEffect: "0x1" ExplodeSound: "0x0" Serial: "0x4061A107" Layer: "255" Unknown: "0x0" + * Doesn't work on provoked monsters + */ - if ( m != null ) - target = m; - } + Mobile target = null; - if ( target == null || !target.InRange( this, 25 ) ) - target = attacker; + if (attacker is BaseCreature) + { + Mobile m = ((BaseCreature)attacker).GetMaster(); - Animate( 10, 4, 1, true, false, 0 ); + if (m != null) + target = m; + } - ArrayList targets = new ArrayList(); + if (target == null || !target.InRange(this, 25)) + target = attacker; - foreach ( Mobile m in target.GetMobilesInRange( 8 ) ) - { - if ( m == this || !CanBeHarmful( m ) ) - continue; + Animate(10, 4, 1, true, false, 0); - if ( m is BaseCreature && (((BaseCreature)m).Controlled || ((BaseCreature)m).Summoned || ((BaseCreature)m).Team != Team) ) - targets.Add( m ); - else if ( m.Player ) - targets.Add( m ); - } + ArrayList targets = new ArrayList(); - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = (Mobile)targets[i]; + foreach (Mobile m in target.GetMobilesInRange(8)) + { + if (m == this || !CanBeHarmful(m)) + continue; - DoHarmful( m ); + if (m is BaseCreature && (((BaseCreature)m).Controlled || ((BaseCreature)m).Summoned || + ((BaseCreature)m).Team != Team)) + targets.Add(m); + else if (m.Player) + targets.Add(m); + } - AOS.Damage( m, this, Utility.RandomMinMax( 20, 25 ), true, 0, 0, 0, 100, 0 ); + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = (Mobile)targets[i]; - m.FixedParticles( 0x36BD, 1, 10, 0x1F78, 0xA6, 0, (EffectLayer)255 ); - m.ApplyPoison( this, Poison.Lethal ); - } - } - } + DoHarmful(m); - public Serado( Serial serial ) : base( serial ) - { - } + AOS.Damage(m, this, Utility.RandomMinMax(20, 25), true, 0, 0, 0, 100, 0); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m.FixedParticles(0x36BD, 1, 10, 0x1F78, 0xA6, 0, (EffectLayer)255); + m.ApplyPoison(this, Poison.Lethal); + } + } + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/ServantOfSemidar.cs b/Scripts/Mobiles/Special/ServantOfSemidar.cs index 5b1a0ae9c..9170f6422 100644 --- a/Scripts/Mobiles/Special/ServantOfSemidar.cs +++ b/Scripts/Mobiles/Special/ServantOfSemidar.cs @@ -1,47 +1,47 @@ namespace Server.Mobiles { - public class ServantOfSemidar : BaseCreature - { - public override string DefaultName => "a Servant of Semidar"; + public class ServantOfSemidar : BaseCreature + { + [Constructible] + public ServantOfSemidar() : base(AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4) + { + Body = 0x26; + } - [Constructible] - public ServantOfSemidar() : base( AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4 ) - { - Body = 0x26; - } + public ServantOfSemidar(Serial serial) : base(serial) + { + } - public override bool DisallowAllMoves => true; + public override string DefaultName => "a Servant of Semidar"; - public override bool InitialInnocent => true; + public override bool DisallowAllMoves => true; - public override bool CanBeDamaged() - { - return false; - } + public override bool InitialInnocent => true; - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); + public override bool CanBeDamaged() + { + return false; + } - list.Add( 1005494 ); // enslaved - } + public override void AddNameProperties(ObjectPropertyList list) + { + base.AddNameProperties(list); - public ServantOfSemidar( Serial serial ) : base( serial ) - { - } + list.Add(1005494); // enslaved + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version - } + writer.WriteEncodedInt(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); - } - } -} + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Silvani.cs b/Scripts/Mobiles/Special/Silvani.cs index f439bc992..5e3634923 100644 --- a/Scripts/Mobiles/Special/Silvani.cs +++ b/Scripts/Mobiles/Special/Silvani.cs @@ -1,132 +1,132 @@ namespace Server.Mobiles { - public class Silvani : BaseCreature - { - public override string DefaultName => "Silvani"; + public class Silvani : BaseCreature + { + [Constructible] + public Silvani() : base(AIType.AI_Mage, FightMode.Evil, 18, 1, 0.1, 0.2) + { + Body = 176; + BaseSoundID = 0x467; - [Constructible] - public Silvani() : base( AIType.AI_Mage, FightMode.Evil, 18, 1, 0.1, 0.2 ) - { - Body = 176; - BaseSoundID = 0x467; + SetStr(253, 400); + SetDex(157, 850); + SetInt(503, 800); - SetStr( 253, 400 ); - SetDex( 157, 850 ); - SetInt( 503, 800 ); + SetHits(600); - SetHits( 600 ); + SetDamage(27, 38); - SetDamage( 27, 38 ); + SetDamageType(ResistanceType.Physical, 75); + SetDamageType(ResistanceType.Cold, 25); - SetDamageType( ResistanceType.Physical, 75 ); - SetDamageType( ResistanceType.Cold, 25 ); + SetResistance(ResistanceType.Physical, 45, 55); + SetResistance(ResistanceType.Fire, 30, 40); + SetResistance(ResistanceType.Cold, 30, 40); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetResistance( ResistanceType.Physical, 45, 55 ); - SetResistance( ResistanceType.Fire, 30, 40 ); - SetResistance( ResistanceType.Cold, 30, 40 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Magery, 97.6, 107.5); + SetSkill(SkillName.Meditation, 100.0); + SetSkill(SkillName.MagicResist, 100.5, 150.0); + SetSkill(SkillName.Tactics, 97.6, 100.0); + SetSkill(SkillName.Wrestling, 97.6, 100.0); - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Magery, 97.6, 107.5 ); - SetSkill( SkillName.Meditation, 100.0 ); - SetSkill( SkillName.MagicResist, 100.5, 150.0 ); - SetSkill( SkillName.Tactics, 97.6, 100.0 ); - SetSkill( SkillName.Wrestling, 97.6, 100.0 ); + Fame = 20000; + Karma = 20000; - Fame = 20000; - Karma = 20000; + VirtualArmor = 50; + } - VirtualArmor = 50; - } + public Silvani(Serial serial) : base(serial) + { + } - public override void GenerateLoot() - { - AddLoot( LootPack.UltraRich, 2 ); - } + public override string DefaultName => "Silvani"; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override bool CanFly => true; - public override bool Unprovokable => true; - public override Poison PoisonImmune => Poison.Regular; - public override int TreasureMapLevel => 5; + public override bool CanFly => true; + public override bool Unprovokable => true; + public override Poison PoisonImmune => Poison.Regular; + public override int TreasureMapLevel => 5; - public void SpawnPixies( Mobile target ) - { - Map map = Map; + public override void GenerateLoot() + { + AddLoot(LootPack.UltraRich, 2); + } - if ( map == null ) - return; + public void SpawnPixies(Mobile target) + { + Map map = Map; - int newPixies = Utility.RandomMinMax( 3, 6 ); + if (map == null) + return; - for ( int i = 0; i < newPixies; ++i ) - { - Pixie pixie = new Pixie(); + int newPixies = Utility.RandomMinMax(3, 6); - pixie.Team = Team; - pixie.FightMode = FightMode.Closest; + for (int i = 0; i < newPixies; ++i) + { + Pixie pixie = new Pixie(); - bool validLocation = false; - Point3D loc = Location; + pixie.Team = Team; + pixie.FightMode = FightMode.Closest; - for ( int j = 0; !validLocation && j < 10; ++j ) - { - int x = X + Utility.Random( 3 ) - 1; - int y = Y + Utility.Random( 3 ) - 1; - int z = map.GetAverageZ( x, y ); + bool validLocation = false; + Point3D loc = Location; - if ( validLocation = map.CanFit( x, y, Z, 16, false, false ) ) - loc = new Point3D( x, y, Z ); - else if ( validLocation = map.CanFit( x, y, z, 16, false, false ) ) - loc = new Point3D( x, y, z ); - } + for (int j = 0; !validLocation && j < 10; ++j) + { + int x = X + Utility.Random(3) - 1; + int y = Y + Utility.Random(3) - 1; + int z = map.GetAverageZ(x, y); - pixie.MoveToWorld( loc, map ); - pixie.Combatant = target; - } - } + if (validLocation = map.CanFit(x, y, Z, 16, false, false)) + loc = new Point3D(x, y, Z); + else if (validLocation = map.CanFit(x, y, z, 16, false, false)) + loc = new Point3D(x, y, z); + } - public override void AlterDamageScalarFrom( Mobile caster, ref double scalar ) - { - if ( 0.1 >= Utility.RandomDouble() ) - SpawnPixies( caster ); - } + pixie.MoveToWorld(loc, map); + pixie.Combatant = target; + } + } - public override void OnGaveMeleeAttack( Mobile defender ) - { - base.OnGaveMeleeAttack( defender ); + public override void AlterDamageScalarFrom(Mobile caster, ref double scalar) + { + if (0.1 >= Utility.RandomDouble()) + SpawnPixies(caster); + } - defender.Damage( Utility.Random( 20, 10 ), this ); - defender.Stam -= Utility.Random( 20, 10 ); - defender.Mana -= Utility.Random( 20, 10 ); - } + public override void OnGaveMeleeAttack(Mobile defender) + { + base.OnGaveMeleeAttack(defender); - public override void OnGotMeleeAttack( Mobile attacker ) - { - base.OnGotMeleeAttack( attacker ); + defender.Damage(Utility.Random(20, 10), this); + defender.Stam -= Utility.Random(20, 10); + defender.Mana -= Utility.Random(20, 10); + } - if ( 0.1 >= Utility.RandomDouble() ) - SpawnPixies( attacker ); - } + public override void OnGotMeleeAttack(Mobile attacker) + { + base.OnGotMeleeAttack(attacker); - public Silvani( Serial serial ) : base( serial ) - { - } + if (0.1 >= Utility.RandomDouble()) + SpawnPixies(attacker); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Special/Wanderer.cs b/Scripts/Mobiles/Special/Wanderer.cs index c7bb61a43..2225dc19d 100644 --- a/Scripts/Mobiles/Special/Wanderer.cs +++ b/Scripts/Mobiles/Special/Wanderer.cs @@ -2,67 +2,64 @@ using System; namespace Server.Mobiles { - public class Wanderer : Mobile - { - private Timer m_Timer; + public class Wanderer : Mobile + { + private Timer m_Timer; - [Constructible] - public Wanderer() - { - Name = "Me"; - Body = 0x1; - AccessLevel = AccessLevel.Counselor; + [Constructible] + public Wanderer() + { + Name = "Me"; + Body = 0x1; + AccessLevel = AccessLevel.Counselor; - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - } + m_Timer = new InternalTimer(this); + m_Timer.Start(); + } - public Wanderer( Serial serial ) : base( serial ) - { - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - } + public Wanderer(Serial serial) : base(serial) + { + m_Timer = new InternalTimer(this); + m_Timer.Start(); + } - public override void OnDelete() - { - m_Timer.Stop(); + public override void OnDelete() + { + m_Timer.Stop(); - base.OnDelete(); - } + base.OnDelete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - private class InternalTimer : Timer - { - private Wanderer m_Owner; - private int m_Count; + private class InternalTimer : Timer + { + private int m_Count; + private Wanderer m_Owner; - public InternalTimer( Wanderer owner ) : base( TimeSpan.FromSeconds( 0.1 ), TimeSpan.FromSeconds( 0.1 ) ) - { - m_Owner = owner; - } + public InternalTimer(Wanderer owner) : base(TimeSpan.FromSeconds(0.1), TimeSpan.FromSeconds(0.1)) + { + m_Owner = owner; + } - protected override void OnTick() - { - if ( (m_Count++ & 0x3) == 0 ) - { - m_Owner.Direction = (Direction)(Utility.Random( 8 ) | 0x80); - } + protected override void OnTick() + { + if ((m_Count++ & 0x3) == 0) m_Owner.Direction = (Direction)(Utility.Random(8) | 0x80); - m_Owner.Move( m_Owner.Direction ); - } - } - } -} + m_Owner.Move(m_Owner.Direction); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Actor.cs b/Scripts/Mobiles/Townfolk/Actor.cs index 50c9bc9ca..5c09e680a 100644 --- a/Scripts/Mobiles/Townfolk/Actor.cs +++ b/Scripts/Mobiles/Townfolk/Actor.cs @@ -2,65 +2,65 @@ using Server.Items; namespace Server.Mobiles { - public class Actor : BaseCreature - { - [Constructible] - public Actor () : base( AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4 ) - { - InitStats( 31, 41, 51 ); + public class Actor : BaseCreature + { + [Constructible] + public Actor() : base(AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4) + { + InitStats(31, 41, 51); - SpeechHue = Utility.RandomDyedHue(); + SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - AddItem( new FancyDress( Utility.RandomDyedHue() ) ); - Title = "the actress"; - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - AddItem( new LongPants( Utility.RandomNeutralHue() ) ); - AddItem( new FancyShirt( Utility.RandomDyedHue() ) ); - Title = "the actor"; - } + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + AddItem(new FancyDress(Utility.RandomDyedHue())); + Title = "the actress"; + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + AddItem(new LongPants(Utility.RandomNeutralHue())); + AddItem(new FancyShirt(Utility.RandomDyedHue())); + Title = "the actor"; + } - AddItem( new Boots( Utility.RandomNeutralHue() ) ); + AddItem(new Boots(Utility.RandomNeutralHue())); - Utility.AssignRandomHair( this ); + Utility.AssignRandomHair(this); - Container pack = new Backpack(); + Container pack = new Backpack(); - pack.DropItem( new Gold( 250, 300 ) ); + pack.DropItem(new Gold(250, 300)); - pack.Movable = false; + pack.Movable = false; - AddItem( pack ); - } + AddItem(pack); + } + + public Actor(Serial serial) : base(serial) + { + } - public override bool ClickTitle => false; + public override bool ClickTitle => false; - public Actor( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Artist.cs b/Scripts/Mobiles/Townfolk/Artist.cs index 043234cff..4e038873a 100644 --- a/Scripts/Mobiles/Townfolk/Artist.cs +++ b/Scripts/Mobiles/Townfolk/Artist.cs @@ -2,70 +2,71 @@ using Server.Items; namespace Server.Mobiles { - public class Artist : BaseCreature - { - public override bool CanTeach => true; + public class Artist : BaseCreature + { + [Constructible] + public Artist() + : base(AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4) + { + InitStats(31, 41, 51); - [Constructible] - public Artist() - : base( AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4 ) - { - InitStats( 31, 41, 51 ); - - SetSkill( SkillName.Healing, 36, 68 ); + SetSkill(SkillName.Healing, 36, 68); - SpeechHue = Utility.RandomDyedHue(); - Title = "the artist"; - Hue = Utility.RandomSkinHue(); + SpeechHue = Utility.RandomDyedHue(); + Title = "the artist"; + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } - AddItem( new Doublet( Utility.RandomDyedHue() ) ); - AddItem( new Sandals( Utility.RandomNeutralHue() ) ); - AddItem( new ShortPants( Utility.RandomNeutralHue() ) ); - AddItem( new HalfApron( Utility.RandomDyedHue() ) ); + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } - Utility.AssignRandomHair( this ); + AddItem(new Doublet(Utility.RandomDyedHue())); + AddItem(new Sandals(Utility.RandomNeutralHue())); + AddItem(new ShortPants(Utility.RandomNeutralHue())); + AddItem(new HalfApron(Utility.RandomDyedHue())); - Container pack = new Backpack(); + Utility.AssignRandomHair(this); - pack.DropItem( new Gold( 250, 300 ) ); + Container pack = new Backpack(); - pack.Movable = false; + pack.DropItem(new Gold(250, 300)); - AddItem( pack ); - } + pack.Movable = false; - public override bool ClickTitle => false; + AddItem(pack); + } - public Artist( Serial serial ) - : base( serial ) - { - } + public Artist(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CanTeach => true; - writer.Write( (int)0 ); // version - } + public override bool ClickTitle => false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Banker.cs b/Scripts/Mobiles/Townfolk/Banker.cs index 0d9d50819..9e3a01a3b 100644 --- a/Scripts/Mobiles/Townfolk/Banker.cs +++ b/Scripts/Mobiles/Townfolk/Banker.cs @@ -1,458 +1,433 @@ using System; using System.Collections.Generic; using System.Linq; - using Server.Accounting; -using Server.Items; using Server.ContextMenus; +using Server.Items; using Server.Network; namespace Server.Mobiles { - public class Banker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; - - public override NpcGuild NpcGuild => NpcGuild.MerchantsGuild; - - [Constructible] - public Banker() : base( "the banker" ) - { - } - - public override void InitSBInfo() - { - m_SBInfos.Add( new SBBanker() ); - } - - public static int GetBalance(Mobile m) - { - long balance = 0; - - if (AccountGold.Enabled && m.Account != null) - { - balance = m.Account.GetTotalGold(); - if (balance >= int.MaxValue) { return int.MaxValue; } - } - - Container bank = m.FindBankNoCreate(); - - if (bank != null) - { - var gold = bank.FindItemsByType(); - var checks = bank.FindItemsByType(); - - balance += gold.Aggregate(0L, (c, t) => c + t.Amount); - if (balance >= int.MaxValue) { return int.MaxValue; } - balance += checks.Aggregate(0L, (c, t) => c + t.Worth); - } - - return Math.Max(0, (int)Math.Min(int.MaxValue, balance)); - } - - public static int GetBalance(Mobile m, out Item[] gold, out Item[] checks) - { - long balance = 0; - - if (AccountGold.Enabled && m.Account != null) - { - balance = m.Account.GetTotalGold(); - - if (balance > int.MaxValue) - { - gold = checks = new Item[0]; - return int.MaxValue; - } - } - - Container bank = m.FindBankNoCreate(); - - if (bank != null) - { - gold = bank.FindItemsByType(typeof(Gold)); - checks = bank.FindItemsByType(typeof(BankCheck)); - - balance += gold.OfType().Aggregate(0L, (c, t) => c + t.Amount); - if (balance >= int.MaxValue) { return int.MaxValue; } - balance += checks.OfType().Aggregate(0L, (c, t) => c + t.Worth); - } - else - { - gold = checks = new Item[0]; - } - - return Math.Max(0, (int)Math.Min(int.MaxValue, balance)); - } - - public static bool Withdraw(Mobile from, int amount) - { - // If for whatever reason the TOL checks fail, we should still try old methods for withdrawing currency. - if (AccountGold.Enabled && from.Account != null && from.Account.WithdrawGold(amount)) - { - return true; - } - - Item[] gold, checks; - var balance = GetBalance(from, out gold, out checks); - - if (balance < amount) - { - return false; - } - - for (var i = 0; amount > 0 && i < gold.Length; ++i) - { - if (gold[i].Amount <= amount) - { - amount -= gold[i].Amount; - gold[i].Delete(); - } - else - { - gold[i].Amount -= amount; - amount = 0; - } - } - - for (var i = 0; amount > 0 && i < checks.Length; ++i) - { - var check = (BankCheck)checks[i]; - - if (check.Worth <= amount) - { - amount -= check.Worth; - check.Delete(); - } - else - { - check.Worth -= amount; - amount = 0; - } - } - - return true; - } - - public static bool Deposit(Mobile from, int amount) - { - // If for whatever reason the TOL checks fail, we should still try old methods for depositing currency. - if (AccountGold.Enabled && from.Account != null && from.Account.DepositGold(amount)) - { - return true; - } - - var box = from.FindBankNoCreate(); - - if (box == null) - { - return false; - } - - var items = new List(); - - while (amount > 0) - { - Item item; - if (amount < 5000) - { - item = new Gold(amount); - amount = 0; - } - else if (amount <= 1000000) - { - item = new BankCheck(amount); - amount = 0; - } - else - { - item = new BankCheck(1000000); - amount -= 1000000; - } - - if (box.TryDropItem(from, item, false)) - { - items.Add(item); - } - else - { - item.Delete(); - foreach (var curItem in items) - { - curItem.Delete(); - } - - return false; - } - } - - return true; - } - - public static int DepositUpTo(Mobile from, int amount) - { - // If for whatever reason the TOL checks fail, we should still try old methods for depositing currency. - if (AccountGold.Enabled && from.Account != null && from.Account.DepositGold(amount)) - { - return amount; - } - - var box = from.FindBankNoCreate(); - - if (box == null) - { - return 0; - } - - var amountLeft = amount; - while (amountLeft > 0) - { - Item item; - int amountGiven; - - if (amountLeft < 5000) - { - item = new Gold(amountLeft); - amountGiven = amountLeft; - } - else if (amountLeft <= 1000000) - { - item = new BankCheck(amountLeft); - amountGiven = amountLeft; - } - else - { - item = new BankCheck(1000000); - amountGiven = 1000000; - } - - if (box.TryDropItem(from, item, false)) - { - amountLeft -= amountGiven; - } - else - { - item.Delete(); - break; - } - } - - return amount - amountLeft; - } - - public static void Deposit(Container cont, int amount) - { - while (amount > 0) - { - Item item; - - if (amount < 5000) - { - item = new Gold(amount); - amount = 0; - } - else if (amount <= 1000000) - { - item = new BankCheck(amount); - amount = 0; - } - else - { - item = new BankCheck(1000000); - amount -= 1000000; - } - - cont.DropItem(item); - } - } - - public Banker( Serial serial ) : base( serial ) - { - } - - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.InRange( Location, 12 ) ) - return true; - - return base.HandlesOnSpeech( from ); - } - - public override void OnSpeech( SpeechEventArgs e ) - { - if ( !e.Handled && e.Mobile.InRange( Location, 12 ) ) - { - for ( int i = 0; i < e.Keywords.Length; ++i ) - { - int keyword = e.Keywords[i]; - - switch ( keyword ) - { - case 0x0000: // *withdraw* - { - e.Handled = true; - - if ( e.Mobile.Criminal ) - { - Say( 500389 ); // I will not do business with a criminal! - break; - } - - string[] split = e.Speech.Split( ' ' ); - - if ( split.Length >= 2 ) - { - int amount; - - Container pack = e.Mobile.Backpack; - - if ( !int.TryParse( split[1], out amount ) ) - break; - - if ( (!Core.ML && amount > 5000) || (Core.ML && amount > 60000) ) - { - Say( 500381 ); // Thou canst not withdraw so much at one time! - } - else if (pack == null || pack.Deleted || !(pack.TotalWeight < pack.MaxWeight) || !(pack.TotalItems < pack.MaxItems)) - { - Say(1048147); // Your backpack can't hold anything else. - } - else if (amount > 0) - { - BankBox box = e.Mobile.FindBankNoCreate(); - - if (box == null || !Withdraw(e.Mobile, amount)) - { - Say(500384); // Ah, art thou trying to fool me? Thou hast not so much gold! - } - else - { - pack.DropItem(new Gold(amount)); - - Say(1010005); // Thou hast withdrawn gold from thy account. - } - } - } - - break; - } - case 0x0001: // *balance* - { - e.Handled = true; - - if ( e.Mobile.Criminal ) - { - Say( 500389 ); // I will not do business with a criminal! - break; - } - - if ( AccountGold.Enabled && e.Mobile.Account != null ) - { - Say( 1155855, $"{e.Mobile.Account.TotalPlat:#,0}\t{e.Mobile.Account.TotalGold:#,0}"); // Thy current bank balance is ~1_AMOUNT~ platinum and ~2_AMOUNT~ gold. - } - else - { - Say( 1042759, GetBalance(e.Mobile).ToString("#,0") ); // Thy current bank balance is ~1_AMOUNT~ gold. - } - - break; - } - case 0x0002: // *bank* - { - e.Handled = true; - - if ( e.Mobile.Criminal ) - { - Say( 500378 ); // Thou art a criminal and cannot access thy bank box. - break; - } - - e.Mobile.BankBox.Open(); - - break; - } - case 0x0003: // *check* - { - e.Handled = true; - - if ( AccountGold.Enabled ) - break; - - if ( e.Mobile.Criminal ) - { - Say( 500389 ); // I will not do business with a criminal! - break; - } - - string[] split = e.Speech.Split( ' ' ); - - if ( split.Length >= 2 ) - { - int amount; - - if ( !int.TryParse( split[1], out amount ) ) - break; - - if ( amount < 5000 ) - { - Say( 1010006 ); // We cannot create checks for such a paltry amount of gold! - } - else if ( amount > 1000000 ) - { - Say( 1010007 ); // Our policies prevent us from creating checks worth that much! - } - else - { - BankCheck check = new BankCheck( amount ); - - BankBox box = e.Mobile.BankBox; - - if ( !box.TryDropItem( e.Mobile, check, false ) ) - { - Say( 500386 ); // There's not enough room in your bankbox for the check! - check.Delete(); - } - else if ( !box.ConsumeTotal( typeof( Gold ), amount ) ) - { - Say( 500384 ); // Ah, art thou trying to fool me? Thou hast not so much gold! - check.Delete(); - } - else - { - Say( 1042673, AffixType.Append, amount.ToString(), "" ); // Into your bank box I have placed a check in the amount of: - } - } - } - - break; - } - } - } - } - - base.OnSpeech( e ); - } - - public override void AddCustomContextEntries( Mobile from, List list ) - { - if ( from.Alive ) - list.Add( new OpenBankEntry( from, this ) ); - - base.AddCustomContextEntries( from, list ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + public class Banker : BaseVendor + { + private List m_SBInfos = new List(); + + [Constructible] + public Banker() : base("the banker") + { + } + + public Banker(Serial serial) : base(serial) + { + } + + protected override List SBInfos => m_SBInfos; + + public override NpcGuild NpcGuild => NpcGuild.MerchantsGuild; + + public override void InitSBInfo() + { + m_SBInfos.Add(new SBBanker()); + } + + public static int GetBalance(Mobile m) + { + long balance = 0; + + if (AccountGold.Enabled && m.Account != null) + { + balance = m.Account.GetTotalGold(); + if (balance >= int.MaxValue) return int.MaxValue; + } + + Container bank = m.FindBankNoCreate(); + + if (bank != null) + { + List gold = bank.FindItemsByType(); + List checks = bank.FindItemsByType(); + + balance += gold.Aggregate(0L, (c, t) => c + t.Amount); + if (balance >= int.MaxValue) return int.MaxValue; + balance += checks.Aggregate(0L, (c, t) => c + t.Worth); + } + + return Math.Max(0, (int)Math.Min(int.MaxValue, balance)); + } + + public static int GetBalance(Mobile m, out Item[] gold, out Item[] checks) + { + long balance = 0; + + if (AccountGold.Enabled && m.Account != null) + { + balance = m.Account.GetTotalGold(); + + if (balance > int.MaxValue) + { + gold = checks = new Item[0]; + return int.MaxValue; + } + } + + Container bank = m.FindBankNoCreate(); + + if (bank != null) + { + gold = bank.FindItemsByType(typeof(Gold)); + checks = bank.FindItemsByType(typeof(BankCheck)); + + balance += gold.OfType().Aggregate(0L, (c, t) => c + t.Amount); + if (balance >= int.MaxValue) return int.MaxValue; + balance += checks.OfType().Aggregate(0L, (c, t) => c + t.Worth); + } + else + { + gold = checks = new Item[0]; + } + + return Math.Max(0, (int)Math.Min(int.MaxValue, balance)); + } + + public static bool Withdraw(Mobile from, int amount) + { + // If for whatever reason the TOL checks fail, we should still try old methods for withdrawing currency. + if (AccountGold.Enabled && from.Account != null && from.Account.WithdrawGold(amount)) return true; + + Item[] gold, checks; + int balance = GetBalance(from, out gold, out checks); + + if (balance < amount) return false; + + for (int i = 0; amount > 0 && i < gold.Length; ++i) + if (gold[i].Amount <= amount) + { + amount -= gold[i].Amount; + gold[i].Delete(); + } + else + { + gold[i].Amount -= amount; + amount = 0; + } + + for (int i = 0; amount > 0 && i < checks.Length; ++i) + { + BankCheck check = (BankCheck)checks[i]; + + if (check.Worth <= amount) + { + amount -= check.Worth; + check.Delete(); + } + else + { + check.Worth -= amount; + amount = 0; + } + } + + return true; + } + + public static bool Deposit(Mobile from, int amount) + { + // If for whatever reason the TOL checks fail, we should still try old methods for depositing currency. + if (AccountGold.Enabled && from.Account != null && from.Account.DepositGold(amount)) return true; + + BankBox box = from.FindBankNoCreate(); + + if (box == null) return false; + + List items = new List(); + + while (amount > 0) + { + Item item; + if (amount < 5000) + { + item = new Gold(amount); + amount = 0; + } + else if (amount <= 1000000) + { + item = new BankCheck(amount); + amount = 0; + } + else + { + item = new BankCheck(1000000); + amount -= 1000000; + } + + if (box.TryDropItem(from, item, false)) + { + items.Add(item); + } + else + { + item.Delete(); + foreach (Item curItem in items) curItem.Delete(); + + return false; + } + } + + return true; + } + + public static int DepositUpTo(Mobile from, int amount) + { + // If for whatever reason the TOL checks fail, we should still try old methods for depositing currency. + if (AccountGold.Enabled && from.Account != null && from.Account.DepositGold(amount)) return amount; + + BankBox box = from.FindBankNoCreate(); + + if (box == null) return 0; + + int amountLeft = amount; + while (amountLeft > 0) + { + Item item; + int amountGiven; + + if (amountLeft < 5000) + { + item = new Gold(amountLeft); + amountGiven = amountLeft; + } + else if (amountLeft <= 1000000) + { + item = new BankCheck(amountLeft); + amountGiven = amountLeft; + } + else + { + item = new BankCheck(1000000); + amountGiven = 1000000; + } + + if (box.TryDropItem(from, item, false)) + { + amountLeft -= amountGiven; + } + else + { + item.Delete(); + break; + } + } + + return amount - amountLeft; + } + + public static void Deposit(Container cont, int amount) + { + while (amount > 0) + { + Item item; + + if (amount < 5000) + { + item = new Gold(amount); + amount = 0; + } + else if (amount <= 1000000) + { + item = new BankCheck(amount); + amount = 0; + } + else + { + item = new BankCheck(1000000); + amount -= 1000000; + } + + cont.DropItem(item); + } + } + + public override bool HandlesOnSpeech(Mobile from) + { + if (from.InRange(Location, 12)) + return true; + + return base.HandlesOnSpeech(from); + } + + public override void OnSpeech(SpeechEventArgs e) + { + if (!e.Handled && e.Mobile.InRange(Location, 12)) + for (int i = 0; i < e.Keywords.Length; ++i) + { + int keyword = e.Keywords[i]; + + switch (keyword) + { + case 0x0000: // *withdraw* + { + e.Handled = true; + + if (e.Mobile.Criminal) + { + Say(500389); // I will not do business with a criminal! + break; + } + + string[] split = e.Speech.Split(' '); + + if (split.Length >= 2) + { + int amount; + + Container pack = e.Mobile.Backpack; + + if (!int.TryParse(split[1], out amount)) + break; + + if (!Core.ML && amount > 5000 || Core.ML && amount > 60000) + { + Say(500381); // Thou canst not withdraw so much at one time! + } + else if (pack == null || pack.Deleted || !(pack.TotalWeight < pack.MaxWeight) || + !(pack.TotalItems < pack.MaxItems)) + { + Say(1048147); // Your backpack can't hold anything else. + } + else if (amount > 0) + { + BankBox box = e.Mobile.FindBankNoCreate(); + + if (box == null || !Withdraw(e.Mobile, amount)) + { + Say(500384); // Ah, art thou trying to fool me? Thou hast not so much gold! + } + else + { + pack.DropItem(new Gold(amount)); + + Say(1010005); // Thou hast withdrawn gold from thy account. + } + } + } + + break; + } + case 0x0001: // *balance* + { + e.Handled = true; + + if (e.Mobile.Criminal) + { + Say(500389); // I will not do business with a criminal! + break; + } + + if (AccountGold.Enabled && e.Mobile.Account != null) + Say(1155855, + $"{e.Mobile.Account.TotalPlat:#,0}\t{e.Mobile.Account.TotalGold:#,0}"); // Thy current bank balance is ~1_AMOUNT~ platinum and ~2_AMOUNT~ gold. + else + Say(1042759, + GetBalance(e.Mobile).ToString("#,0")); // Thy current bank balance is ~1_AMOUNT~ gold. + + break; + } + case 0x0002: // *bank* + { + e.Handled = true; + + if (e.Mobile.Criminal) + { + Say(500378); // Thou art a criminal and cannot access thy bank box. + break; + } + + e.Mobile.BankBox.Open(); + + break; + } + case 0x0003: // *check* + { + e.Handled = true; + + if (AccountGold.Enabled) + break; + + if (e.Mobile.Criminal) + { + Say(500389); // I will not do business with a criminal! + break; + } + + string[] split = e.Speech.Split(' '); + + if (split.Length >= 2) + { + int amount; + + if (!int.TryParse(split[1], out amount)) + break; + + if (amount < 5000) + { + Say(1010006); // We cannot create checks for such a paltry amount of gold! + } + else if (amount > 1000000) + { + Say(1010007); // Our policies prevent us from creating checks worth that much! + } + else + { + BankCheck check = new BankCheck(amount); + + BankBox box = e.Mobile.BankBox; + + if (!box.TryDropItem(e.Mobile, check, false)) + { + Say(500386); // There's not enough room in your bankbox for the check! + check.Delete(); + } + else if (!box.ConsumeTotal(typeof(Gold), amount)) + { + Say(500384); // Ah, art thou trying to fool me? Thou hast not so much gold! + check.Delete(); + } + else + { + Say(1042673, AffixType.Append, amount.ToString(), + ""); // Into your bank box I have placed a check in the amount of: + } + } + } + + break; + } + } + } + + base.OnSpeech(e); + } + + public override void AddCustomContextEntries(Mobile from, List list) + { + if (from.Alive) + list.Add(new OpenBankEntry(from, this)); + + base.AddCustomContextEntries(from, list); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/BaseEscortable.cs b/Scripts/Mobiles/Townfolk/BaseEscortable.cs index d6bd09f63..d5891c79b 100644 --- a/Scripts/Mobiles/Townfolk/BaseEscortable.cs +++ b/Scripts/Mobiles/Townfolk/BaseEscortable.cs @@ -1,754 +1,772 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Items; using Server.ContextMenus; -using EDI = Server.Mobiles.EscortDestinationInfo; using Server.Engines.MLQuests; using Server.Engines.MLQuests.Definitions; using Server.Engines.MLQuests.Objectives; +using Server.Items; +using Server.Misc; +using Server.Regions; +using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class BaseEscortable : BaseCreature - { - public static readonly TimeSpan EscortDelay = TimeSpan.FromMinutes( 5.0 ); - public static readonly TimeSpan AbandonDelay = MLQuestSystem.Enabled ? TimeSpan.FromMinutes( 1.0 ) : TimeSpan.FromMinutes( 2.0 ); - public static readonly TimeSpan DeleteTime = MLQuestSystem.Enabled ? TimeSpan.FromSeconds( 100 ) : TimeSpan.FromSeconds( 30 ); - - public override bool StaticMLQuester => false; // Suppress automatic quest registration on creation/deserialization - - private MLQuest m_MLQuest; - - protected override List ConstructQuestList() - { - if ( m_MLQuest == null ) - { - Region reg = Region; - Type[] list = reg.IsPartOf( "Haven Island" ) ? m_MLQuestTypesNH : m_MLQuestTypes; - - int randomIdx = Utility.Random( list.Length ); - - for ( int i = 0; i < list.Length; ++i ) - { - Type questType = list[randomIdx]; - - MLQuest quest = MLQuestSystem.FindQuest( questType ); - - if ( quest != null ) - { - bool okay = true; - - foreach ( BaseObjective obj in quest.Objectives ) - { - if ( obj is EscortObjective && ( (EscortObjective)obj ).Destination.Contains( reg ) ) - { - okay = false; // We're already there! - break; - } - } - - if ( okay ) - { - m_MLQuest = quest; - break; - } - } - else if ( MLQuestSystem.Debug ) - { - Console.WriteLine( "Warning: Escortable cannot be assigned quest type '{0}', it is not registered", questType.Name ); - } - - randomIdx = ( randomIdx + 1 ) % list.Length; - } - - if ( m_MLQuest == null ) - { - if ( MLQuestSystem.Debug ) - Console.WriteLine( "Warning: No suitable quest found for escort {0}", Serial ); - - return null; - } - } - - List result = new List { m_MLQuest }; - - return result; - } - - public override bool CanShout => ( !Controlled && !IsBeingDeleted ); - - public override void Shout( PlayerMobile pm ) - { - /* - * 1072301 - You there! Care to hear how to earn some easy gold? - * 1072302 - Adventurer! I have an offer for you. - * 1072303 - Wait! I have an opportunity for you to make some gold! - */ - MLQuestSystem.Tell( this, pm, Utility.Random( 1072301, 3 ) ); - } - - private EDI m_Destination; - private string m_DestinationString; - - private DateTime m_DeleteTime; - private Timer m_DeleteTimer; - - private bool m_DeleteCorpse; - - public bool IsBeingDeleted => ( m_DeleteTimer != null ); - - public override bool Commandable => false; // Our master cannot boss us around! - public override bool DeleteCorpseOnDeath => m_DeleteCorpse; - - [CommandProperty(AccessLevel.GameMaster)] - public string Destination - { - get => m_Destination?.Name; - set { m_DestinationString = value; m_Destination = EDI.Find(value); } - } - - // Classic list - // Used when: !MLQuestSystem.Enabled && !Core.ML - private static string[] m_TownNames = { - "Cove", "Britain", "Jhelom", - "Minoc", "Ocllo", "Trinsic", - "Vesper", "Yew", "Skara Brae", - "Nujel'm", "Moonglow", "Magincia" - }; - - // ML list, pre-ML quest system - // Used when: !MLQuestSystem.Enabled && Core.ML - private static string[] m_MLTownNames = { - "Cove", "Serpent's Hold", "Jhelom", - "Nujel'm" - }; - - // ML quest system general list - // Used when: MLQuestSystem.Enabled && !Region.IsPartOf( "Haven Island" ) - private static Type[] m_MLQuestTypes = - { - typeof( EscortToYew ), - typeof( EscortToVesper ), - typeof( EscortToTrinsic ), - typeof( EscortToSkaraBrae ), - typeof( EscortToSerpentsHold ), - typeof( EscortToNujelm ), - typeof( EscortToMoonglow ), - typeof( EscortToMinoc ), - typeof( EscortToMagincia ), - typeof( EscortToJhelom ), - typeof( EscortToCove ), - typeof( EscortToBritain ) - // Ocllo was removed in pub 56 - //typeof( EscortToOcllo ) - }; - - // ML quest system New Haven list - // Used when: MLQuestSystem.Enabled && Region.IsPartOf( "Haven Island" ) - private static Type[] m_MLQuestTypesNH = - { - typeof( EscortToNHAlchemist ), - typeof( EscortToNHBard ), - typeof( EscortToNHWarrior ), - typeof( EscortToNHTailor ), - typeof( EscortToNHCarpenter ), - typeof( EscortToNHMapmaker ), - typeof( EscortToNHMage ), - typeof( EscortToNHInn ), - // Farm destination was removed - //typeof( EscortToNHFarm ), - typeof( EscortToNHDocks ), - typeof( EscortToNHBowyer ), - typeof( EscortToNHBank ) - }; - - [Constructible] - public BaseEscortable() - : base(AIType.AI_Melee, FightMode.Aggressor, 22, 1, 0.2, 1.0) - { - InitBody(); - InitOutfit(); - - Fame = 200; - Karma = 4000; - } - - public virtual void InitBody() - { - SetStr(90, 100); - SetDex(90, 100); - SetInt(15, 25); - - Hue = Utility.RandomSkinHue(); - - if (Female = Utility.RandomBool()) - { - Body = 401; - Name = NameList.RandomName("female"); - } - else - { - Body = 400; - Name = NameList.RandomName("male"); - } - } - - public virtual void InitOutfit() - { - AddItem(new FancyShirt(Utility.RandomNeutralHue())); - AddItem(new ShortPants(Utility.RandomNeutralHue())); - AddItem(new Boots(Utility.RandomNeutralHue())); - - Utility.AssignRandomHair(this); - - PackGold(200, 250); - } - - public virtual bool SayDestinationTo(Mobile m) - { - EDI dest = GetDestination(); - - if (dest == null || !m.Alive) - return false; - - Mobile escorter = GetEscorter(); - - if (escorter == null) - { - Say("I am looking to go to {0}, will you take me?", (dest.Name == "Ocllo" && m.Map == Map.Trammel) ? "Haven" : dest.Name); - return true; - } - - if (escorter == m) - { - Say("Lead on! Payment will be made when we arrive in {0}.", (dest.Name == "Ocllo" && m.Map == Map.Trammel) ? "Haven" : dest.Name); - return true; - } - - return false; - } - - public static Hashtable EscortTable { get; } = new Hashtable(); - - public virtual bool AcceptEscorter(Mobile m) - { - EDI dest = GetDestination(); - - if (dest == null) - return false; - - Mobile escorter = GetEscorter(); - - if (escorter != null || !m.Alive) - return false; - - BaseEscortable escortable = (BaseEscortable)EscortTable[m]; - - if (escortable != null && !escortable.Deleted && escortable.GetEscorter() == m) - { - Say("I see you already have an escort."); - return false; - } - - if (m is PlayerMobile && (((PlayerMobile)m).LastEscortTime + EscortDelay) >= DateTime.UtcNow) - { - int minutes = (int)Math.Ceiling(((((PlayerMobile)m).LastEscortTime + EscortDelay) - DateTime.UtcNow).TotalMinutes); - - Say("You must rest {0} minute{1} before we set out on this journey.", minutes, minutes == 1 ? "" : "s"); - return false; - } - if (SetControlMaster(m)) - { - m_LastSeenEscorter = DateTime.UtcNow; - - if (m is PlayerMobile) - ((PlayerMobile)m).LastEscortTime = DateTime.UtcNow; - - Say("Lead on! Payment will be made when we arrive in {0}.", (dest.Name == "Ocllo" && m.Map == Map.Trammel) ? "Haven" : dest.Name); - EscortTable[m] = this; - StartFollow(); - return true; - } + public class BaseEscortable : BaseCreature + { + public static readonly TimeSpan EscortDelay = TimeSpan.FromMinutes(5.0); + + public static readonly TimeSpan AbandonDelay = + MLQuestSystem.Enabled ? TimeSpan.FromMinutes(1.0) : TimeSpan.FromMinutes(2.0); + + public static readonly TimeSpan DeleteTime = + MLQuestSystem.Enabled ? TimeSpan.FromSeconds(100) : TimeSpan.FromSeconds(30); + + // Classic list + // Used when: !MLQuestSystem.Enabled && !Core.ML + private static string[] m_TownNames = + { + "Cove", "Britain", "Jhelom", + "Minoc", "Ocllo", "Trinsic", + "Vesper", "Yew", "Skara Brae", + "Nujel'm", "Moonglow", "Magincia" + }; + + // ML list, pre-ML quest system + // Used when: !MLQuestSystem.Enabled && Core.ML + private static string[] m_MLTownNames = + { + "Cove", "Serpent's Hold", "Jhelom", + "Nujel'm" + }; + + // ML quest system general list + // Used when: MLQuestSystem.Enabled && !Region.IsPartOf( "Haven Island" ) + private static Type[] m_MLQuestTypes = + { + typeof(EscortToYew), + typeof(EscortToVesper), + typeof(EscortToTrinsic), + typeof(EscortToSkaraBrae), + typeof(EscortToSerpentsHold), + typeof(EscortToNujelm), + typeof(EscortToMoonglow), + typeof(EscortToMinoc), + typeof(EscortToMagincia), + typeof(EscortToJhelom), + typeof(EscortToCove), + typeof(EscortToBritain) + // Ocllo was removed in pub 56 + //typeof( EscortToOcllo ) + }; + + // ML quest system New Haven list + // Used when: MLQuestSystem.Enabled && Region.IsPartOf( "Haven Island" ) + private static Type[] m_MLQuestTypesNH = + { + typeof(EscortToNHAlchemist), + typeof(EscortToNHBard), + typeof(EscortToNHWarrior), + typeof(EscortToNHTailor), + typeof(EscortToNHCarpenter), + typeof(EscortToNHMapmaker), + typeof(EscortToNHMage), + typeof(EscortToNHInn), + // Farm destination was removed + //typeof( EscortToNHFarm ), + typeof(EscortToNHDocks), + typeof(EscortToNHBowyer), + typeof(EscortToNHBank) + }; + + private bool m_DeleteCorpse; + + private DateTime m_DeleteTime; + private Timer m_DeleteTimer; + + private EDI m_Destination; + private string m_DestinationString; + + private DateTime m_LastSeenEscorter; + + private MLQuest m_MLQuest; + + [Constructible] + public BaseEscortable() + : base(AIType.AI_Melee, FightMode.Aggressor, 22, 1, 0.2, 1.0) + { + InitBody(); + InitOutfit(); + + Fame = 200; + Karma = 4000; + } + + public BaseEscortable(Serial serial) + : base(serial) + { + } + + public override bool StaticMLQuester => false; // Suppress automatic quest registration on creation/deserialization + + public override bool CanShout => !Controlled && !IsBeingDeleted; + + public bool IsBeingDeleted => m_DeleteTimer != null; + + public override bool Commandable => false; // Our master cannot boss us around! + public override bool DeleteCorpseOnDeath => m_DeleteCorpse; + + [CommandProperty(AccessLevel.GameMaster)] + public string Destination + { + get => m_Destination?.Name; + set + { + m_DestinationString = value; + m_Destination = EDI.Find(value); + } + } + + public static Hashtable EscortTable{ get; } = new Hashtable(); + + protected override List ConstructQuestList() + { + if (m_MLQuest == null) + { + Region reg = Region; + Type[] list = reg.IsPartOf("Haven Island") ? m_MLQuestTypesNH : m_MLQuestTypes; + + int randomIdx = Utility.Random(list.Length); + + for (int i = 0; i < list.Length; ++i) + { + Type questType = list[randomIdx]; + + MLQuest quest = MLQuestSystem.FindQuest(questType); + + if (quest != null) + { + bool okay = true; + + foreach (BaseObjective obj in quest.Objectives) + if (obj is EscortObjective && ((EscortObjective)obj).Destination.Contains(reg)) + { + okay = false; // We're already there! + break; + } + + if (okay) + { + m_MLQuest = quest; + break; + } + } + else if (MLQuestSystem.Debug) + { + Console.WriteLine("Warning: Escortable cannot be assigned quest type '{0}', it is not registered", + questType.Name); + } + + randomIdx = (randomIdx + 1) % list.Length; + } + + if (m_MLQuest == null) + { + if (MLQuestSystem.Debug) + Console.WriteLine("Warning: No suitable quest found for escort {0}", Serial); + + return null; + } + } + + List result = new List { m_MLQuest }; + + return result; + } + + public override void Shout(PlayerMobile pm) + { + /* + * 1072301 - You there! Care to hear how to earn some easy gold? + * 1072302 - Adventurer! I have an offer for you. + * 1072303 - Wait! I have an opportunity for you to make some gold! + */ + MLQuestSystem.Tell(this, pm, Utility.Random(1072301, 3)); + } + + public virtual void InitBody() + { + SetStr(90, 100); + SetDex(90, 100); + SetInt(15, 25); + + Hue = Utility.RandomSkinHue(); + + if (Female = Utility.RandomBool()) + { + Body = 401; + Name = NameList.RandomName("female"); + } + else + { + Body = 400; + Name = NameList.RandomName("male"); + } + } + + public virtual void InitOutfit() + { + AddItem(new FancyShirt(Utility.RandomNeutralHue())); + AddItem(new ShortPants(Utility.RandomNeutralHue())); + AddItem(new Boots(Utility.RandomNeutralHue())); + + Utility.AssignRandomHair(this); + + PackGold(200, 250); + } + + public virtual bool SayDestinationTo(Mobile m) + { + EDI dest = GetDestination(); + + if (dest == null || !m.Alive) + return false; + + Mobile escorter = GetEscorter(); + + if (escorter == null) + { + Say("I am looking to go to {0}, will you take me?", + dest.Name == "Ocllo" && m.Map == Map.Trammel ? "Haven" : dest.Name); + return true; + } + + if (escorter == m) + { + Say("Lead on! Payment will be made when we arrive in {0}.", + dest.Name == "Ocllo" && m.Map == Map.Trammel ? "Haven" : dest.Name); + return true; + } + + return false; + } + + public virtual bool AcceptEscorter(Mobile m) + { + EDI dest = GetDestination(); + + if (dest == null) + return false; + + Mobile escorter = GetEscorter(); + + if (escorter != null || !m.Alive) + return false; + + BaseEscortable escortable = (BaseEscortable)EscortTable[m]; + + if (escortable != null && !escortable.Deleted && escortable.GetEscorter() == m) + { + Say("I see you already have an escort."); + return false; + } + + if (m is PlayerMobile && ((PlayerMobile)m).LastEscortTime + EscortDelay >= DateTime.UtcNow) + { + int minutes = + (int)Math.Ceiling((((PlayerMobile)m).LastEscortTime + EscortDelay - DateTime.UtcNow).TotalMinutes); + + Say("You must rest {0} minute{1} before we set out on this journey.", minutes, minutes == 1 ? "" : "s"); + return false; + } + + if (SetControlMaster(m)) + { + m_LastSeenEscorter = DateTime.UtcNow; + + if (m is PlayerMobile) + ((PlayerMobile)m).LastEscortTime = DateTime.UtcNow; + + Say("Lead on! Payment will be made when we arrive in {0}.", + dest.Name == "Ocllo" && m.Map == Map.Trammel ? "Haven" : dest.Name); + EscortTable[m] = this; + StartFollow(); + return true; + } - return false; - } + return false; + } - public override bool HandlesOnSpeech(Mobile from) - { - if ( MLQuestSystem.Enabled ) - return false; + public override bool HandlesOnSpeech(Mobile from) + { + if (MLQuestSystem.Enabled) + return false; - if (from.InRange(Location, 3)) - return true; + if (from.InRange(Location, 3)) + return true; - return base.HandlesOnSpeech(from); - } + return base.HandlesOnSpeech(from); + } - public override void OnSpeech(SpeechEventArgs e) - { - base.OnSpeech(e); + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); - EDI dest = GetDestination(); + EDI dest = GetDestination(); - if (dest != null && !e.Handled && e.Mobile.InRange(Location, 3)) - { - if (e.HasKeyword(0x1D)) // *destination* - e.Handled = SayDestinationTo(e.Mobile); - else if (e.HasKeyword(0x1E)) // *i will take thee* - e.Handled = AcceptEscorter(e.Mobile); - } - } + if (dest != null && !e.Handled && e.Mobile.InRange(Location, 3)) + { + if (e.HasKeyword(0x1D)) // *destination* + e.Handled = SayDestinationTo(e.Mobile); + else if (e.HasKeyword(0x1E)) // *i will take thee* + e.Handled = AcceptEscorter(e.Mobile); + } + } - public override void OnAfterDelete() - { - m_DeleteTimer?.Stop(); + public override void OnAfterDelete() + { + m_DeleteTimer?.Stop(); - m_DeleteTimer = null; + m_DeleteTimer = null; - base.OnAfterDelete(); - } + base.OnAfterDelete(); + } - public override void OnThink() - { - base.OnThink(); - CheckAtDestination(); - } + public override void OnThink() + { + base.OnThink(); + CheckAtDestination(); + } - protected override bool OnMove(Direction d) - { - if (!base.OnMove(d)) - return false; + protected override bool OnMove(Direction d) + { + if (!base.OnMove(d)) + return false; - CheckAtDestination(); + CheckAtDestination(); - return true; - } + return true; + } - // TODO: Pre-ML methods below, might be mergeable with the ML methods in EscortObjective + // TODO: Pre-ML methods below, might be mergeable with the ML methods in EscortObjective - public virtual void StartFollow() - { - StartFollow(GetEscorter()); - } + public virtual void StartFollow() + { + StartFollow(GetEscorter()); + } - public virtual void StartFollow(Mobile escorter) - { - if (escorter == null) - return; + public virtual void StartFollow(Mobile escorter) + { + if (escorter == null) + return; - ActiveSpeed = 0.1; - PassiveSpeed = 0.2; + ActiveSpeed = 0.1; + PassiveSpeed = 0.2; - ControlOrder = OrderType.Follow; - ControlTarget = escorter; + ControlOrder = OrderType.Follow; + ControlTarget = escorter; - if ((IsPrisoner == true) && (CantWalk == true)) - { - CantWalk = false; - } - CurrentSpeed = 0.1; - } + if (IsPrisoner && CantWalk) CantWalk = false; + CurrentSpeed = 0.1; + } - public virtual void StopFollow() - { - ActiveSpeed = 0.2; - PassiveSpeed = 1.0; + public virtual void StopFollow() + { + ActiveSpeed = 0.2; + PassiveSpeed = 1.0; - ControlOrder = OrderType.None; - ControlTarget = null; + ControlOrder = OrderType.None; + ControlTarget = null; - CurrentSpeed = 1.0; - } + CurrentSpeed = 1.0; + } - private DateTime m_LastSeenEscorter; + public virtual Mobile GetEscorter() + { + if (!Controlled) + return null; - public virtual Mobile GetEscorter() - { - if ( !Controlled ) - return null; + Mobile master = ControlMaster; - Mobile master = ControlMaster; + if (MLQuestSystem.Enabled || master == null) + return master; - if ( MLQuestSystem.Enabled || master == null ) - return master; + if (master.Deleted || master.Map != Map || !master.InRange(Location, 30) || !master.Alive) + { + StopFollow(); - if (master.Deleted || master.Map != Map || !master.InRange(Location, 30) || !master.Alive) - { - StopFollow(); + TimeSpan lastSeenDelay = DateTime.UtcNow - m_LastSeenEscorter; - TimeSpan lastSeenDelay = DateTime.UtcNow - m_LastSeenEscorter; + if (lastSeenDelay >= AbandonDelay) + { + master.SendLocalizedMessage(1042473); // You have lost the person you were escorting. + Say(1005653); // Hmmm. I seem to have lost my master. - if (lastSeenDelay >= AbandonDelay) - { - master.SendLocalizedMessage(1042473); // You have lost the person you were escorting. - Say(1005653); // Hmmm. I seem to have lost my master. + SetControlMaster(null); + EscortTable.Remove(master); - SetControlMaster(null); - EscortTable.Remove(master); + Timer.DelayCall(TimeSpan.FromSeconds(5.0), Delete); + return null; + } - Timer.DelayCall(TimeSpan.FromSeconds(5.0), Delete); - return null; - } + ControlOrder = OrderType.Stay; + return master; + } - ControlOrder = OrderType.Stay; - return master; - } + if (ControlOrder != OrderType.Follow) + StartFollow(master); - if (ControlOrder != OrderType.Follow) - StartFollow(master); + m_LastSeenEscorter = DateTime.UtcNow; + return master; + } - m_LastSeenEscorter = DateTime.UtcNow; - return master; - } + public virtual void BeginDelete() + { + m_DeleteTimer?.Stop(); - public virtual void BeginDelete() - { - m_DeleteTimer?.Stop(); + m_DeleteTime = DateTime.UtcNow + DeleteTime; - m_DeleteTime = DateTime.UtcNow + DeleteTime; + m_DeleteTimer = new DeleteTimer(this, m_DeleteTime - DateTime.UtcNow); + m_DeleteTimer.Start(); + } - m_DeleteTimer = new DeleteTimer(this, m_DeleteTime - DateTime.UtcNow); - m_DeleteTimer.Start(); - } + public virtual bool CheckAtDestination() + { + if (MLQuestSystem.Enabled) + return false; - public virtual bool CheckAtDestination() - { - if ( MLQuestSystem.Enabled ) - return false; + EDI dest = GetDestination(); - EDI dest = GetDestination(); + if (dest == null) + return false; - if (dest == null) - return false; + Mobile escorter = GetEscorter(); - Mobile escorter = GetEscorter(); + if (escorter == null) + return false; - if (escorter == null) - return false; + if (dest.Contains(Location)) + { + Say(1042809, + escorter.Name); // We have arrived! I thank thee, ~1_PLAYER_NAME~! I have no further need of thy services. Here is thy pay. - if (dest.Contains(Location)) - { - Say(1042809, escorter.Name); // We have arrived! I thank thee, ~1_PLAYER_NAME~! I have no further need of thy services. Here is thy pay. + // not going anywhere + m_Destination = null; + m_DestinationString = null; - // not going anywhere - m_Destination = null; - m_DestinationString = null; + Container cont = escorter.Backpack; - Container cont = escorter.Backpack; + if (cont == null) + cont = escorter.BankBox; - if (cont == null) - cont = escorter.BankBox; + Gold gold = new Gold(500, 1000); - Gold gold = new Gold(500, 1000); + if (!cont.TryDropItem(escorter, gold, false)) + gold.MoveToWorld(escorter.Location, escorter.Map); - if (!cont.TryDropItem(escorter, gold, false)) - gold.MoveToWorld(escorter.Location, escorter.Map); + StopFollow(); + SetControlMaster(null); + EscortTable.Remove(escorter); + BeginDelete(); - StopFollow(); - SetControlMaster(null); - EscortTable.Remove(escorter); - BeginDelete(); + Titles.AwardFame(escorter, 10, true); - Misc.Titles.AwardFame(escorter, 10, true); + bool gainedPath = false; - bool gainedPath = false; + PlayerMobile pm = escorter as PlayerMobile; - PlayerMobile pm = escorter as PlayerMobile; + if (pm != null) + { + if (pm.CompassionGains > 0 && DateTime.UtcNow > pm.NextCompassionDay) + { + pm.NextCompassionDay = DateTime.MinValue; + pm.CompassionGains = 0; + } - if (pm != null) - { - if (pm.CompassionGains > 0 && DateTime.UtcNow > pm.NextCompassionDay) - { - pm.NextCompassionDay = DateTime.MinValue; - pm.CompassionGains = 0; - } + if (pm.CompassionGains >= 5) // have already gained 5 times in one day, can gain no more + { + pm.SendLocalizedMessage( + 1053004); // You must wait about a day before you can gain in compassion again. + } + else if (VirtueHelper.Award(pm, VirtueName.Compassion, IsPrisoner ? 400 : 200, ref gainedPath)) + { + if (gainedPath) + pm.SendLocalizedMessage(1053005); // You have achieved a path in compassion! + else + pm.SendLocalizedMessage(1053002); // You have gained in compassion. - if (pm.CompassionGains >= 5) // have already gained 5 times in one day, can gain no more - { - pm.SendLocalizedMessage(1053004); // You must wait about a day before you can gain in compassion again. - } - else if (VirtueHelper.Award(pm, VirtueName.Compassion, IsPrisoner ? 400 : 200, ref gainedPath)) - { - if (gainedPath) - pm.SendLocalizedMessage(1053005); // You have achieved a path in compassion! - else - pm.SendLocalizedMessage(1053002); // You have gained in compassion. + pm.NextCompassionDay = + DateTime.UtcNow + TimeSpan.FromDays(1.0); // in one day CompassionGains gets reset to 0 + ++pm.CompassionGains; - pm.NextCompassionDay = DateTime.UtcNow + TimeSpan.FromDays(1.0); // in one day CompassionGains gets reset to 0 - ++pm.CompassionGains; + if (pm.CompassionGains >= 5) + pm.SendLocalizedMessage( + 1053004); // You must wait about a day before you can gain in compassion again. + } + else + { + pm.SendLocalizedMessage( + 1053003); // You have achieved the highest path of compassion and can no longer gain any further. + } + } - if (pm.CompassionGains >= 5) - pm.SendLocalizedMessage(1053004); // You must wait about a day before you can gain in compassion again. - } - else - { - pm.SendLocalizedMessage(1053003); // You have achieved the highest path of compassion and can no longer gain any further. - } - } + return true; + } - return true; - } + return false; + } - return false; - } + public override bool OnBeforeDeath() + { + m_DeleteCorpse = Controlled || IsBeingDeleted; - public override bool OnBeforeDeath() - { - m_DeleteCorpse = ( Controlled || IsBeingDeleted ); + return base.OnBeforeDeath(); + } - return base.OnBeforeDeath(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public BaseEscortable(Serial serial) - : base(serial) - { - } + writer.Write(1); // version - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + EDI dest = GetDestination(); - writer.Write((int)1); // version + writer.Write(dest != null); - EDI dest = GetDestination(); + if (dest != null) + writer.Write(dest.Name); - writer.Write(dest != null); + writer.Write(m_DeleteTimer != null); - if (dest != null) - writer.Write(dest.Name); + if (m_DeleteTimer != null) + writer.WriteDeltaTime(m_DeleteTime); - writer.Write(m_DeleteTimer != null); + MLQuestSystem.WriteQuestRef(writer, StaticMLQuester ? null : m_MLQuest); + } - if (m_DeleteTimer != null) - writer.WriteDeltaTime(m_DeleteTime); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - MLQuestSystem.WriteQuestRef( writer, StaticMLQuester ? null : m_MLQuest ); - } + int version = reader.ReadInt(); - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + if (reader.ReadBool()) + m_DestinationString = + reader.ReadString(); // NOTE: We cannot EDI.Find here, regions have not yet been loaded :-( - int version = reader.ReadInt(); + if (reader.ReadBool()) + { + m_DeleteTime = reader.ReadDeltaTime(); + m_DeleteTimer = new DeleteTimer(this, m_DeleteTime - DateTime.UtcNow); + m_DeleteTimer.Start(); + } + + if (version >= 1) + { + MLQuest quest = MLQuestSystem.ReadQuestRef(reader); + + if (MLQuestSystem.Enabled && quest != null && !StaticMLQuester) + m_MLQuest = quest; + } + } + + public override bool CanBeRenamedBy(Mobile from) + { + return from.AccessLevel >= AccessLevel.GameMaster; + } + + public override void AddCustomContextEntries(Mobile from, List list) + { + if (from.Alive) + { + Mobile escorter = GetEscorter(); + + if (!MLQuestSystem.Enabled && GetDestination() != null) + { + if (escorter == null || escorter == from) + list.Add(new AskDestinationEntry(this, from)); + + if (escorter == null) + list.Add(new AcceptEscortEntry(this, from)); + } + + if (escorter == from) + list.Add(new AbandonEscortEntry(this, from)); + } - if (reader.ReadBool()) - m_DestinationString = reader.ReadString(); // NOTE: We cannot EDI.Find here, regions have not yet been loaded :-( + base.AddCustomContextEntries(from, list); + } - if (reader.ReadBool()) - { - m_DeleteTime = reader.ReadDeltaTime(); - m_DeleteTimer = new DeleteTimer(this, m_DeleteTime - DateTime.UtcNow); - m_DeleteTimer.Start(); - } + public virtual string[] GetPossibleDestinations() + { + if (!Core.ML) + return m_TownNames; + return m_MLTownNames; + } - if ( version >= 1 ) - { - MLQuest quest = MLQuestSystem.ReadQuestRef( reader ); - - if ( MLQuestSystem.Enabled && quest != null && !StaticMLQuester ) - m_MLQuest = quest; - } - } + public virtual string PickRandomDestination() + { + if (Map.Felucca.Regions.Count == 0 || Map == null || Map == Map.Internal || Location == Point3D.Zero) + return null; // Not yet fully initialized - public override bool CanBeRenamedBy(Mobile from) - { - return (from.AccessLevel >= AccessLevel.GameMaster); - } - - public override void AddCustomContextEntries( Mobile from, List list ) - { - if ( from.Alive ) - { - Mobile escorter = GetEscorter(); - - if ( !MLQuestSystem.Enabled && GetDestination() != null ) - { - if ( escorter == null || escorter == from ) - list.Add( new AskDestinationEntry( this, from ) ); + string[] possible = GetPossibleDestinations(); + string picked = null; - if ( escorter == null ) - list.Add( new AcceptEscortEntry( this, from ) ); - } + while (picked == null) + { + picked = possible[Utility.Random(possible.Length)]; + EDI test = EDI.Find(picked); - if ( escorter == from ) - list.Add( new AbandonEscortEntry( this, from ) ); - } + if (test != null && test.Contains(Location)) + picked = null; + } - base.AddCustomContextEntries( from, list ); - } + return picked; + } - public virtual string[] GetPossibleDestinations() - { - if (!Core.ML) - return m_TownNames; - return m_MLTownNames; - } + public EDI GetDestination() + { + if (MLQuestSystem.Enabled) + return null; - public virtual string PickRandomDestination() - { - if (Map.Felucca.Regions.Count == 0 || Map == null || Map == Map.Internal || Location == Point3D.Zero) - return null; // Not yet fully initialized - - string[] possible = GetPossibleDestinations(); - string picked = null; - - while (picked == null) - { - picked = possible[Utility.Random(possible.Length)]; - EDI test = EDI.Find(picked); - - if (test != null && test.Contains(Location)) - picked = null; - } - - return picked; - } - - public EDI GetDestination() - { - if ( MLQuestSystem.Enabled ) - return null; - - if (m_DestinationString == null && m_DeleteTimer == null) - m_DestinationString = PickRandomDestination(); - - if (m_Destination != null && m_Destination.Name == m_DestinationString) - return m_Destination; - - if (Map.Felucca.Regions.Count > 0) - return (m_Destination = EDI.Find(m_DestinationString)); - - return (m_Destination = null); - } - - private class DeleteTimer : Timer - { - private Mobile m_Mobile; - - public DeleteTimer(Mobile m, TimeSpan delay) - : base(delay) - { - m_Mobile = m; - - Priority = TimerPriority.OneSecond; - } - - protected override void OnTick() - { - m_Mobile.Delete(); - } - } - } - - public class EscortDestinationInfo - { - //private Rectangle2D[] m_Bounds; - - public string Name { get; } - - public Region Region { get; } - - /*public Rectangle2D[] Bounds - { - get{ return m_Bounds; } - }*/ - - public bool Contains(Point3D p) - { - return Region.Contains(p); - } - - public EscortDestinationInfo(string name, Region region) - { - Name = name; - Region = region; - } - - private static Hashtable m_Table; - - public static void LoadTable() - { - ICollection list = Map.Felucca.Regions.Values; - - if (list.Count == 0) - return; - - m_Table = new Hashtable(); - - foreach (Region r in list) - { - if (r.Name == null) - continue; - - if (r is Regions.DungeonRegion || r is Regions.TownRegion) - m_Table[r.Name] = new EscortDestinationInfo(r.Name, r); - } - } - - public static EDI Find(string name) - { - if (m_Table == null) - LoadTable(); - - if (name == null || m_Table == null) - return null; - - return (EscortDestinationInfo)m_Table[name]; - } - } - - public class AskDestinationEntry : ContextMenuEntry - { - private BaseEscortable m_Mobile; - private Mobile m_From; - - public AskDestinationEntry(BaseEscortable m, Mobile from) - : base(6100, 3) - { - m_Mobile = m; - m_From = from; - } - - public override void OnClick() - { - m_Mobile.SayDestinationTo(m_From); - } - } - - public class AcceptEscortEntry : ContextMenuEntry - { - private BaseEscortable m_Mobile; - private Mobile m_From; - - public AcceptEscortEntry(BaseEscortable m, Mobile from) - : base(6101, 3) - { - m_Mobile = m; - m_From = from; - } - - public override void OnClick() - { - m_Mobile.AcceptEscorter(m_From); - } - } - - public class AbandonEscortEntry : ContextMenuEntry - { - private BaseEscortable m_Mobile; - private Mobile m_From; - - public AbandonEscortEntry(BaseEscortable m, Mobile from) - : base(6102, 3) - { - m_Mobile = m; - m_From = from; - } - - public override void OnClick() - { - m_Mobile.Delete(); // OSI just seems to delete instantly - } - } -} + if (m_DestinationString == null && m_DeleteTimer == null) + m_DestinationString = PickRandomDestination(); + + if (m_Destination != null && m_Destination.Name == m_DestinationString) + return m_Destination; + + if (Map.Felucca.Regions.Count > 0) + return m_Destination = EDI.Find(m_DestinationString); + + return m_Destination = null; + } + + private class DeleteTimer : Timer + { + private Mobile m_Mobile; + + public DeleteTimer(Mobile m, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + + Priority = TimerPriority.OneSecond; + } + + protected override void OnTick() + { + m_Mobile.Delete(); + } + } + } + + public class EscortDestinationInfo + { + private static Hashtable m_Table; + + public EscortDestinationInfo(string name, Region region) + { + Name = name; + Region = region; + } + //private Rectangle2D[] m_Bounds; + + public string Name{ get; } + + public Region Region{ get; } + + /*public Rectangle2D[] Bounds + { + get{ return m_Bounds; } + }*/ + + public bool Contains(Point3D p) + { + return Region.Contains(p); + } + + public static void LoadTable() + { + ICollection list = Map.Felucca.Regions.Values; + + if (list.Count == 0) + return; + + m_Table = new Hashtable(); + + foreach (Region r in list) + { + if (r.Name == null) + continue; + + if (r is DungeonRegion || r is TownRegion) + m_Table[r.Name] = new EscortDestinationInfo(r.Name, r); + } + } + + public static EDI Find(string name) + { + if (m_Table == null) + LoadTable(); + + if (name == null || m_Table == null) + return null; + + return (EscortDestinationInfo)m_Table[name]; + } + } + + public class AskDestinationEntry : ContextMenuEntry + { + private Mobile m_From; + private BaseEscortable m_Mobile; + + public AskDestinationEntry(BaseEscortable m, Mobile from) + : base(6100, 3) + { + m_Mobile = m; + m_From = from; + } + + public override void OnClick() + { + m_Mobile.SayDestinationTo(m_From); + } + } + + public class AcceptEscortEntry : ContextMenuEntry + { + private Mobile m_From; + private BaseEscortable m_Mobile; + + public AcceptEscortEntry(BaseEscortable m, Mobile from) + : base(6101, 3) + { + m_Mobile = m; + m_From = from; + } + + public override void OnClick() + { + m_Mobile.AcceptEscorter(m_From); + } + } + + public class AbandonEscortEntry : ContextMenuEntry + { + private Mobile m_From; + private BaseEscortable m_Mobile; + + public AbandonEscortEntry(BaseEscortable m, Mobile from) + : base(6102, 3) + { + m_Mobile = m; + m_From = from; + } + + public override void OnClick() + { + m_Mobile.Delete(); // OSI just seems to delete instantly + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/BrideGroom.cs b/Scripts/Mobiles/Townfolk/BrideGroom.cs index fb63cf3dc..41e6701b4 100644 --- a/Scripts/Mobiles/Townfolk/BrideGroom.cs +++ b/Scripts/Mobiles/Townfolk/BrideGroom.cs @@ -3,76 +3,76 @@ using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class BrideGroom : BaseEscortable - { - [Constructible] - public BrideGroom() - { - if ( Female ) - Title = "the bride"; - else - Title = "the groom"; - } + public class BrideGroom : BaseEscortable + { + [Constructible] + public BrideGroom() + { + if (Female) + Title = "the bride"; + else + Title = "the groom"; + } - public override bool CanTeach => true; - public override bool ClickTitle => false; // Do not display 'the groom' when single-clicking + public BrideGroom(Serial serial) : base(serial) + { + } - private static int GetRandomHue() - { - switch ( Utility.Random( 6 ) ) - { - default: - case 0: return 0; - case 1: return Utility.RandomBlueHue(); - case 2: return Utility.RandomGreenHue(); - case 3: return Utility.RandomRedHue(); - case 4: return Utility.RandomYellowHue(); - case 5: return Utility.RandomNeutralHue(); - } - } + public override bool CanTeach => true; + public override bool ClickTitle => false; // Do not display 'the groom' when single-clicking - public override void InitOutfit() - { - if ( Female ) - AddItem( new FancyDress() ); - else - AddItem( new FancyShirt() ); + private static int GetRandomHue() + { + switch (Utility.Random(6)) + { + default: + case 0: return 0; + case 1: return Utility.RandomBlueHue(); + case 2: return Utility.RandomGreenHue(); + case 3: return Utility.RandomRedHue(); + case 4: return Utility.RandomYellowHue(); + case 5: return Utility.RandomNeutralHue(); + } + } - int lowHue = GetRandomHue(); + public override void InitOutfit() + { + if (Female) + AddItem(new FancyDress()); + else + AddItem(new FancyShirt()); - AddItem( new LongPants( lowHue ) ); + int lowHue = GetRandomHue(); - if ( Female ) - AddItem( new Shoes( lowHue ) ); - else - AddItem( new Boots( lowHue ) ); + AddItem(new LongPants(lowHue)); - if ( Utility.RandomBool() ) - HairItemID = 0x203B; - else - HairItemID = 0x203C; + if (Female) + AddItem(new Shoes(lowHue)); + else + AddItem(new Boots(lowHue)); - HairHue = Race.RandomHairHue(); + if (Utility.RandomBool()) + HairItemID = 0x203B; + else + HairItemID = 0x203C; - PackGold( 200, 250 ); - } + HairHue = Race.RandomHairHue(); - public BrideGroom( Serial serial ) : base( serial ) - { - } + PackGold(200, 250); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/EscortableMage.cs b/Scripts/Mobiles/Townfolk/EscortableMage.cs index df7a1607b..cec9a7150 100644 --- a/Scripts/Mobiles/Townfolk/EscortableMage.cs +++ b/Scripts/Mobiles/Townfolk/EscortableMage.cs @@ -3,70 +3,70 @@ using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class EscortableMage : BaseEscortable - { - [Constructible] - public EscortableMage() - { - Title = "the mage"; + public class EscortableMage : BaseEscortable + { + [Constructible] + public EscortableMage() + { + Title = "the mage"; - SetSkill( SkillName.EvalInt, 80.0, 100.0 ); - SetSkill( SkillName.Inscribe, 80.0, 100.0 ); - SetSkill( SkillName.Magery, 80.0, 100.0 ); - SetSkill( SkillName.Meditation, 80.0, 100.0 ); - SetSkill( SkillName.MagicResist, 80.0, 100.0 ); - } + SetSkill(SkillName.EvalInt, 80.0, 100.0); + SetSkill(SkillName.Inscribe, 80.0, 100.0); + SetSkill(SkillName.Magery, 80.0, 100.0); + SetSkill(SkillName.Meditation, 80.0, 100.0); + SetSkill(SkillName.MagicResist, 80.0, 100.0); + } - public override bool CanTeach => true; - public override bool ClickTitle => false; // Do not display 'the mage' when single-clicking + public EscortableMage(Serial serial) : base(serial) + { + } - private static int GetRandomHue() - { - switch ( Utility.Random( 5 ) ) - { - default: - case 0: return Utility.RandomBlueHue(); - case 1: return Utility.RandomGreenHue(); - case 2: return Utility.RandomRedHue(); - case 3: return Utility.RandomYellowHue(); - case 4: return Utility.RandomNeutralHue(); - } - } + public override bool CanTeach => true; + public override bool ClickTitle => false; // Do not display 'the mage' when single-clicking - public override void InitOutfit() - { - AddItem( new Robe( GetRandomHue() ) ); + private static int GetRandomHue() + { + switch (Utility.Random(5)) + { + default: + case 0: return Utility.RandomBlueHue(); + case 1: return Utility.RandomGreenHue(); + case 2: return Utility.RandomRedHue(); + case 3: return Utility.RandomYellowHue(); + case 4: return Utility.RandomNeutralHue(); + } + } - int lowHue = GetRandomHue(); + public override void InitOutfit() + { + AddItem(new Robe(GetRandomHue())); - AddItem( new ShortPants( lowHue ) ); + int lowHue = GetRandomHue(); - if ( Female ) - AddItem( new ThighBoots( lowHue ) ); - else - AddItem( new Boots( lowHue ) ); + AddItem(new ShortPants(lowHue)); - Utility.AssignRandomHair( this ); + if (Female) + AddItem(new ThighBoots(lowHue)); + else + AddItem(new Boots(lowHue)); - PackGold( 200, 250 ); - } + Utility.AssignRandomHair(this); - public EscortableMage( Serial serial ) : base( serial ) - { - } + PackGold(200, 250); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Gypsy.cs b/Scripts/Mobiles/Townfolk/Gypsy.cs index d3374fcd2..3f2f7f78a 100644 --- a/Scripts/Mobiles/Townfolk/Gypsy.cs +++ b/Scripts/Mobiles/Townfolk/Gypsy.cs @@ -2,78 +2,76 @@ using Server.Items; namespace Server.Mobiles { - public class Gypsy : BaseCreature - { + public class Gypsy : BaseCreature + { + [Constructible] + public Gypsy() + : base(AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4) + { + InitStats(31, 41, 51); + + SpeechHue = Utility.RandomDyedHue(); + + SetSkill(SkillName.Cooking, 65, 88); + SetSkill(SkillName.Snooping, 65, 88); + SetSkill(SkillName.Stealing, 65, 88); + + Hue = Utility.RandomSkinHue(); + + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + AddItem(new Kilt(Utility.RandomDyedHue())); + AddItem(new Shirt(Utility.RandomDyedHue())); + AddItem(new ThighBoots()); + Title = "the gypsy"; + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + AddItem(new ShortPants(Utility.RandomNeutralHue())); + AddItem(new Shirt(Utility.RandomDyedHue())); + AddItem(new Sandals()); + Title = "the gypsy"; + } + + AddItem(new Bandana(Utility.RandomDyedHue())); + AddItem(new Dagger()); + + Utility.AssignRandomHair(this); + + Container pack = new Backpack(); + + pack.DropItem(new Gold(250, 300)); + + pack.Movable = false; + + AddItem(pack); + } + + public Gypsy(Serial serial) + : base(serial) + { + } - [Constructible] - public Gypsy() - : base( AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4 ) - { - InitStats( 31, 41, 51 ); + public override bool CanTeach => true; + public override bool ClickTitle => false; - SpeechHue = Utility.RandomDyedHue(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - SetSkill( SkillName.Cooking, 65, 88 ); - SetSkill( SkillName.Snooping, 65, 88 ); - SetSkill( SkillName.Stealing, 65, 88 ); + writer.Write(0); // version + } - Hue = Utility.RandomSkinHue(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - AddItem( new Kilt( Utility.RandomDyedHue() ) ); - AddItem( new Shirt( Utility.RandomDyedHue() ) ); - AddItem( new ThighBoots() ); - Title = "the gypsy"; - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - AddItem( new ShortPants( Utility.RandomNeutralHue() ) ); - AddItem( new Shirt( Utility.RandomDyedHue() ) ); - AddItem( new Sandals() ); - Title = "the gypsy"; - } - - AddItem( new Bandana( Utility.RandomDyedHue() ) ); - AddItem( new Dagger() ); - - Utility.AssignRandomHair( this ); - - Container pack = new Backpack(); - - pack.DropItem( new Gold( 250, 300 ) ); - - pack.Movable = false; - - AddItem( pack ); - } - - - public override bool CanTeach => true; - public override bool ClickTitle => false; - - public Gypsy( Serial serial ) - : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/HarborMaster.cs b/Scripts/Mobiles/Townfolk/HarborMaster.cs index fce448cbb..c5591e02b 100644 --- a/Scripts/Mobiles/Townfolk/HarborMaster.cs +++ b/Scripts/Mobiles/Townfolk/HarborMaster.cs @@ -2,72 +2,73 @@ using Server.Items; namespace Server.Mobiles { - public class HarborMaster : BaseCreature - { - public override bool CanTeach => false; + public class HarborMaster : BaseCreature + { + [Constructible] + public HarborMaster() + : base(AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4) + { + InitStats(31, 41, 51); - [Constructible] - public HarborMaster() - : base( AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4 ) - { - InitStats( 31, 41, 51 ); - - SetSkill( SkillName.Mining, 36, 68 ); + SetSkill(SkillName.Mining, 36, 68); - SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); - Blessed = true; + SpeechHue = Utility.RandomDyedHue(); + Hue = Utility.RandomSkinHue(); + Blessed = true; - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - Title = "the Harbor Mistress"; - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - Title = "the Harbor Master"; - } - AddItem( new Shirt( Utility.RandomDyedHue() ) ); - AddItem( new Boots() ); - AddItem( new LongPants( Utility.RandomNeutralHue() ) ); - AddItem( new QuarterStaff() ); + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + Title = "the Harbor Mistress"; + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + Title = "the Harbor Master"; + } - Utility.AssignRandomHair( this ); + AddItem(new Shirt(Utility.RandomDyedHue())); + AddItem(new Boots()); + AddItem(new LongPants(Utility.RandomNeutralHue())); + AddItem(new QuarterStaff()); - Container pack = new Backpack(); + Utility.AssignRandomHair(this); - pack.DropItem( new Gold( 250, 300 ) ); + Container pack = new Backpack(); - pack.Movable = false; + pack.DropItem(new Gold(250, 300)); - AddItem( pack ); - } + pack.Movable = false; - public override bool ClickTitle => false; + AddItem(pack); + } - public HarborMaster( Serial serial ) - : base( serial ) - { - } + public HarborMaster(Serial serial) + : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CanTeach => false; - writer.Write( (int)0 ); // version - } + public override bool ClickTitle => false; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Merchant.cs b/Scripts/Mobiles/Townfolk/Merchant.cs index 17a15045c..94ca2fe94 100644 --- a/Scripts/Mobiles/Townfolk/Merchant.cs +++ b/Scripts/Mobiles/Townfolk/Merchant.cs @@ -1,83 +1,81 @@ using Server.Items; -using EDI=Server.Mobiles.EscortDestinationInfo; +using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class Merchant : BaseEscortable - { - [Constructible] - public Merchant() - { - Title = "the merchant"; - SetSkill( SkillName.ItemID, 55.0, 78.0 ); - SetSkill( SkillName.ArmsLore, 55, 78 ); - } + public class Merchant : BaseEscortable + { + [Constructible] + public Merchant() + { + Title = "the merchant"; + SetSkill(SkillName.ItemID, 55.0, 78.0); + SetSkill(SkillName.ArmsLore, 55, 78); + } - public override bool CanTeach => true; - public override bool ClickTitle => false; // Do not display 'the merchant' when single-clicking + public Merchant(Serial serial) + : base(serial) + { + } - private static int GetRandomHue() - { - switch( Utility.Random( 6 ) ) - { - default: - case 0: return 0; - case 1: return Utility.RandomBlueHue(); - case 2: return Utility.RandomGreenHue(); - case 3: return Utility.RandomRedHue(); - case 4: return Utility.RandomYellowHue(); - case 5: return Utility.RandomNeutralHue(); - } + public override bool CanTeach => true; + public override bool ClickTitle => false; // Do not display 'the merchant' when single-clicking - } + private static int GetRandomHue() + { + switch (Utility.Random(6)) + { + default: + case 0: return 0; + case 1: return Utility.RandomBlueHue(); + case 2: return Utility.RandomGreenHue(); + case 3: return Utility.RandomRedHue(); + case 4: return Utility.RandomYellowHue(); + case 5: return Utility.RandomNeutralHue(); + } + } - public override void InitOutfit() - { - if ( Female ) - AddItem( new PlainDress() ); - else - AddItem( new Shirt( GetRandomHue() ) ); + public override void InitOutfit() + { + if (Female) + AddItem(new PlainDress()); + else + AddItem(new Shirt(GetRandomHue())); - int lowHue = GetRandomHue(); + int lowHue = GetRandomHue(); - AddItem( new ThighBoots() ); + AddItem(new ThighBoots()); - if ( Female ) - AddItem( new FancyDress( lowHue ) ); - else - AddItem( new FancyShirt( lowHue ) ); - AddItem( new LongPants( lowHue ) ); + if (Female) + AddItem(new FancyDress(lowHue)); + else + AddItem(new FancyShirt(lowHue)); + AddItem(new LongPants(lowHue)); - if ( !Female ) - AddItem( new BodySash( lowHue ) ); + if (!Female) + AddItem(new BodySash(lowHue)); + //if ( !Female ) + //AddItem( new Longsword() ); - //if ( !Female ) - //AddItem( new Longsword() ); + Utility.AssignRandomHair(this); - Utility.AssignRandomHair( this ); + PackGold(200, 250); + } - PackGold( 200, 250 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public Merchant( Serial serial ) - : base( serial ) - { - } + writer.Write(0); // version + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - writer.Write( (int)0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Messenger.cs b/Scripts/Mobiles/Townfolk/Messenger.cs index a13e695f3..0892a542b 100644 --- a/Scripts/Mobiles/Townfolk/Messenger.cs +++ b/Scripts/Mobiles/Townfolk/Messenger.cs @@ -3,82 +3,90 @@ using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class Messenger : BaseEscortable - { - [Constructible] - public Messenger() - { - Title = "the messenger"; - } + public class Messenger : BaseEscortable + { + [Constructible] + public Messenger() + { + Title = "the messenger"; + } - public override bool CanTeach => true; - public override bool ClickTitle => false; // Do not display 'the messenger' when single-clicking + public Messenger(Serial serial) : base(serial) + { + } - private static int GetRandomHue() - { - switch ( Utility.Random( 6 ) ) - { - default: - case 0: return 0; - case 1: return Utility.RandomBlueHue(); - case 2: return Utility.RandomGreenHue(); - case 3: return Utility.RandomRedHue(); - case 4: return Utility.RandomYellowHue(); - case 5: return Utility.RandomNeutralHue(); - } - } + public override bool CanTeach => true; + public override bool ClickTitle => false; // Do not display 'the messenger' when single-clicking - public override void InitOutfit() - { - if ( Female ) - AddItem( new PlainDress() ); - else - AddItem( new Shirt( GetRandomHue() ) ); + private static int GetRandomHue() + { + switch (Utility.Random(6)) + { + default: + case 0: return 0; + case 1: return Utility.RandomBlueHue(); + case 2: return Utility.RandomGreenHue(); + case 3: return Utility.RandomRedHue(); + case 4: return Utility.RandomYellowHue(); + case 5: return Utility.RandomNeutralHue(); + } + } - int lowHue = GetRandomHue(); + public override void InitOutfit() + { + if (Female) + AddItem(new PlainDress()); + else + AddItem(new Shirt(GetRandomHue())); - AddItem( new ShortPants( lowHue ) ); + int lowHue = GetRandomHue(); - if ( Female ) - AddItem( new Boots( lowHue ) ); - else - AddItem( new Shoes( lowHue ) ); + AddItem(new ShortPants(lowHue)); - //if ( !Female ) - //AddItem( new BodySash( lowHue ) ); + if (Female) + AddItem(new Boots(lowHue)); + else + AddItem(new Shoes(lowHue)); - //AddItem( new Cloak( GetRandomHue() ) ); + //if ( !Female ) + //AddItem( new BodySash( lowHue ) ); - //if ( !Female ) - //AddItem( new Longsword() ); + //AddItem( new Cloak( GetRandomHue() ) ); - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new ShortHair( Utility.RandomHairHue() ) ); break; - case 1: AddItem( new TwoPigTails( Utility.RandomHairHue() ) ); break; - case 2: AddItem( new ReceedingHair( Utility.RandomHairHue() ) ); break; - case 3: AddItem( new KrisnaHair( Utility.RandomHairHue() ) ); break; - } + //if ( !Female ) + //AddItem( new Longsword() ); - PackGold( 200, 250 ); - } + switch (Utility.Random(4)) + { + case 0: + AddItem(new ShortHair(Utility.RandomHairHue())); + break; + case 1: + AddItem(new TwoPigTails(Utility.RandomHairHue())); + break; + case 2: + AddItem(new ReceedingHair(Utility.RandomHairHue())); + break; + case 3: + AddItem(new KrisnaHair(Utility.RandomHairHue())); + break; + } - public Messenger( Serial serial ) : base( serial ) - { - } + PackGold(200, 250); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Minter.cs b/Scripts/Mobiles/Townfolk/Minter.cs index fbd3ed216..88843054d 100644 --- a/Scripts/Mobiles/Townfolk/Minter.cs +++ b/Scripts/Mobiles/Townfolk/Minter.cs @@ -1,31 +1,31 @@ namespace Server.Mobiles { - public class Minter : Banker - { - public override NpcGuild NpcGuild => NpcGuild.MerchantsGuild; + public class Minter : Banker + { + [Constructible] + public Minter() + { + Title = "the minter"; + } - [Constructible] - public Minter() - { - Title = "the minter"; - } + public Minter(Serial serial) : base(serial) + { + } - public Minter( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.MerchantsGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Ninja.cs b/Scripts/Mobiles/Townfolk/Ninja.cs index c3756468c..38f9857c6 100644 --- a/Scripts/Mobiles/Townfolk/Ninja.cs +++ b/Scripts/Mobiles/Townfolk/Ninja.cs @@ -2,75 +2,75 @@ using Server.Items; namespace Server.Mobiles { - public class Ninja : BaseCreature - { - public override bool CanTeach => true; - public override bool ClickTitle => false; + public class Ninja : BaseCreature + { + [Constructible] + public Ninja() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Title = "the ninja"; - [Constructible] - public Ninja() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Title = "the ninja"; + InitStats(100, 100, 25); - InitStats( 100, 100, 25 ); + SetSkill(SkillName.Fencing, 64.0, 80.0); + SetSkill(SkillName.Macing, 64.0, 80.0); + SetSkill(SkillName.Ninjitsu, 60.0, 80.0); + SetSkill(SkillName.Parry, 64.0, 80.0); + SetSkill(SkillName.Tactics, 64.0, 85.0); + SetSkill(SkillName.Swords, 64.0, 85.0); - SetSkill( SkillName.Fencing, 64.0, 80.0 ); - SetSkill( SkillName.Macing, 64.0, 80.0 ); - SetSkill( SkillName.Ninjitsu, 60.0, 80.0 ); - SetSkill( SkillName.Parry, 64.0, 80.0 ); - SetSkill( SkillName.Tactics, 64.0, 85.0 ); - SetSkill( SkillName.Swords, 64.0, 85.0 ); + SpeechHue = Utility.RandomDyedHue(); - SpeechHue = Utility.RandomDyedHue(); + Hue = Utility.RandomSkinHue(); - Hue = Utility.RandomSkinHue(); + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + if (!Female) + AddItem(new LeatherNinjaHood()); - if ( !Female ) - AddItem( new LeatherNinjaHood() ); + AddItem(new LeatherNinjaPants()); + AddItem(new LeatherNinjaBelt()); + AddItem(new LeatherNinjaJacket()); + AddItem(new NinjaTabi()); - AddItem( new LeatherNinjaPants() ); - AddItem( new LeatherNinjaBelt() ); - AddItem( new LeatherNinjaJacket() ); - AddItem( new NinjaTabi() ); - - int hairHue = Utility.RandomNondyedHue(); + int hairHue = Utility.RandomNondyedHue(); - Utility.AssignRandomHair( this, hairHue ); + Utility.AssignRandomHair(this, hairHue); - if ( Utility.Random( 7 ) != 0 ) - Utility.AssignRandomFacialHair( this, hairHue ); + if (Utility.Random(7) != 0) + Utility.AssignRandomFacialHair(this, hairHue); - PackGold( 250, 300 ); - } + PackGold(250, 300); + } - public Ninja( Serial serial ) : base( serial ) - { - } + public Ninja(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CanTeach => true; + public override bool ClickTitle => false; - writer.WriteEncodedInt( 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Noble.cs b/Scripts/Mobiles/Townfolk/Noble.cs index e22510e97..95a7d8510 100644 --- a/Scripts/Mobiles/Townfolk/Noble.cs +++ b/Scripts/Mobiles/Townfolk/Noble.cs @@ -3,80 +3,80 @@ using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class Noble : BaseEscortable - { - [Constructible] - public Noble() - { - Title = "the noble"; + public class Noble : BaseEscortable + { + [Constructible] + public Noble() + { + Title = "the noble"; - SetSkill( SkillName.Parry, 80.0, 100.0 ); - SetSkill( SkillName.Swords, 80.0, 100.0 ); - SetSkill( SkillName.Tactics, 80.0, 100.0 ); - } + SetSkill(SkillName.Parry, 80.0, 100.0); + SetSkill(SkillName.Swords, 80.0, 100.0); + SetSkill(SkillName.Tactics, 80.0, 100.0); + } - public override bool CanTeach => true; - public override bool ClickTitle => false; // Do not display 'the noble' when single-clicking + public Noble(Serial serial) : base(serial) + { + } - private static int GetRandomHue() - { - switch ( Utility.Random( 6 ) ) - { - default: - case 0: return 0; - case 1: return Utility.RandomBlueHue(); - case 2: return Utility.RandomGreenHue(); - case 3: return Utility.RandomRedHue(); - case 4: return Utility.RandomYellowHue(); - case 5: return Utility.RandomNeutralHue(); - } - } + public override bool CanTeach => true; + public override bool ClickTitle => false; // Do not display 'the noble' when single-clicking - public override void InitOutfit() - { - if ( Female ) - AddItem( new FancyDress() ); - else - AddItem( new FancyShirt( GetRandomHue() ) ); + private static int GetRandomHue() + { + switch (Utility.Random(6)) + { + default: + case 0: return 0; + case 1: return Utility.RandomBlueHue(); + case 2: return Utility.RandomGreenHue(); + case 3: return Utility.RandomRedHue(); + case 4: return Utility.RandomYellowHue(); + case 5: return Utility.RandomNeutralHue(); + } + } - int lowHue = GetRandomHue(); + public override void InitOutfit() + { + if (Female) + AddItem(new FancyDress()); + else + AddItem(new FancyShirt(GetRandomHue())); - AddItem( new ShortPants( lowHue ) ); + int lowHue = GetRandomHue(); - if ( Female ) - AddItem( new ThighBoots( lowHue ) ); - else - AddItem( new Boots( lowHue ) ); + AddItem(new ShortPants(lowHue)); - if ( !Female ) - AddItem( new BodySash( lowHue ) ); + if (Female) + AddItem(new ThighBoots(lowHue)); + else + AddItem(new Boots(lowHue)); - AddItem( new Cloak( GetRandomHue() ) ); + if (!Female) + AddItem(new BodySash(lowHue)); - if ( !Female ) - AddItem( new Longsword() ); + AddItem(new Cloak(GetRandomHue())); - Utility.AssignRandomHair( this ); + if (!Female) + AddItem(new Longsword()); - PackGold( 200, 250 ); - } + Utility.AssignRandomHair(this); - public Noble( Serial serial ) : base( serial ) - { - } + PackGold(200, 250); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Peasant.cs b/Scripts/Mobiles/Townfolk/Peasant.cs index 0832b7043..6ab91394e 100644 --- a/Scripts/Mobiles/Townfolk/Peasant.cs +++ b/Scripts/Mobiles/Townfolk/Peasant.cs @@ -3,77 +3,76 @@ using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class Peasant : BaseEscortable - { - [Constructible] - public Peasant() - { - Title = "the peasant"; + public class Peasant : BaseEscortable + { + [Constructible] + public Peasant() + { + Title = "the peasant"; + } - } + public Peasant(Serial serial) : base(serial) + { + } - public override bool CanTeach => true; - public override bool ClickTitle => false; // Do not display 'the peasant' when single-clicking + public override bool CanTeach => true; + public override bool ClickTitle => false; // Do not display 'the peasant' when single-clicking - private static int GetRandomHue() - { - switch ( Utility.Random( 6 ) ) - { - default: - case 0: return 0; - case 1: return Utility.RandomBlueHue(); - case 2: return Utility.RandomGreenHue(); - case 3: return Utility.RandomRedHue(); - case 4: return Utility.RandomYellowHue(); - case 5: return Utility.RandomNeutralHue(); - } - } + private static int GetRandomHue() + { + switch (Utility.Random(6)) + { + default: + case 0: return 0; + case 1: return Utility.RandomBlueHue(); + case 2: return Utility.RandomGreenHue(); + case 3: return Utility.RandomRedHue(); + case 4: return Utility.RandomYellowHue(); + case 5: return Utility.RandomNeutralHue(); + } + } - public override void InitOutfit() - { - if ( Female ) - AddItem( new PlainDress() ); - else - AddItem( new Shirt( GetRandomHue() ) ); + public override void InitOutfit() + { + if (Female) + AddItem(new PlainDress()); + else + AddItem(new Shirt(GetRandomHue())); - int lowHue = GetRandomHue(); + int lowHue = GetRandomHue(); - AddItem( new ShortPants( lowHue ) ); + AddItem(new ShortPants(lowHue)); - if ( Female ) - AddItem( new Boots( lowHue ) ); - else - AddItem( new Shoes( lowHue ) ); + if (Female) + AddItem(new Boots(lowHue)); + else + AddItem(new Shoes(lowHue)); - //if ( !Female ) - //AddItem( new BodySash( lowHue ) ); + //if ( !Female ) + //AddItem( new BodySash( lowHue ) ); - //AddItem( new Cloak( GetRandomHue() ) ); + //AddItem( new Cloak( GetRandomHue() ) ); - //if ( !Female ) - //AddItem( new Longsword() ); + //if ( !Female ) + //AddItem( new Longsword() ); - Utility.AssignRandomHair( this ); + Utility.AssignRandomHair(this); - PackGold( 200, 250 ); - } + PackGold(200, 250); + } - public Peasant( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Prisoner.cs b/Scripts/Mobiles/Townfolk/Prisoner.cs index 8bd063aed..63f49caee 100644 --- a/Scripts/Mobiles/Townfolk/Prisoner.cs +++ b/Scripts/Mobiles/Townfolk/Prisoner.cs @@ -1,82 +1,82 @@ -using Server.Items; -using Server.Engines.MLQuests; +using Server.Engines.MLQuests; +using Server.Items; namespace Server.Mobiles.Townfolk { - public class Prisoner : BaseEscortable - { - [Constructible] - public Prisoner() - { - Title = Female ? "the noblewoman" : "the nobleman"; + public class Prisoner : BaseEscortable + { + [Constructible] + public Prisoner() + { + Title = Female ? "the noblewoman" : "the nobleman"; - CantWalk = true; - IsPrisoner = true; - } + CantWalk = true; + IsPrisoner = true; + } - public override bool CanTeach => true; - public override bool ClickTitle => false; + public Prisoner(Serial serial) + : base(serial) + { + } - public override void InitOutfit() - { - if ( Female ) - { - AddItem( new FancyDress( Utility.RandomNondyedHue() ) ); - } - else - { - AddItem( new FancyShirt( Utility.RandomNondyedHue() ) ); - AddItem( new LongPants( Utility.RandomNondyedHue() ) ); - } + public override bool CanTeach => true; + public override bool ClickTitle => false; - if ( Utility.RandomBool() ) - AddItem( new Boots() ); - else - AddItem( new ThighBoots() ); + public override void InitOutfit() + { + if (Female) + { + AddItem(new FancyDress(Utility.RandomNondyedHue())); + } + else + { + AddItem(new FancyShirt(Utility.RandomNondyedHue())); + AddItem(new LongPants(Utility.RandomNondyedHue())); + } - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); - } + if (Utility.RandomBool()) + AddItem(new Boots()); + else + AddItem(new ThighBoots()); - public override void Shout( PlayerMobile pm ) - { - /* - * 502261 - HELP! - * 502262 - Help me! - * 502263 - Canst thou aid me?! - * 502264 - Help a poor prisoner! - * 502265 - Help! Please! - * 502266 - Aaah! Help me! - * 502267 - Go and get some help! - */ - MLQuestSystem.Tell( this, pm, Utility.Random( 502261, 7 ) ); - } + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - base.OnMovement( m, oldLocation ); + public override void Shout(PlayerMobile pm) + { + /* + * 502261 - HELP! + * 502262 - Help me! + * 502263 - Canst thou aid me?! + * 502264 - Help a poor prisoner! + * 502265 - Help! Please! + * 502266 - Aaah! Help me! + * 502267 - Go and get some help! + */ + MLQuestSystem.Tell(this, pm, Utility.Random(502261, 7)); + } - if ( CantWalk && InRange( m, 1 ) && !InRange( oldLocation, 1 ) && ( !m.Hidden || m.AccessLevel == AccessLevel.Player ) ) - Say( 502268 ); // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + base.OnMovement(m, oldLocation); - public Prisoner( Serial serial ) - : base( serial ) - { - } + if (CantWalk && InRange(m, 1) && !InRange(oldLocation, 1) && (!m.Hidden || m.AccessLevel == AccessLevel.Player)) + Say(502268); // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Samurai.cs b/Scripts/Mobiles/Townfolk/Samurai.cs index 672097ae9..4bed07153 100644 --- a/Scripts/Mobiles/Townfolk/Samurai.cs +++ b/Scripts/Mobiles/Townfolk/Samurai.cs @@ -2,91 +2,111 @@ using Server.Items; namespace Server.Mobiles { - public class Samurai : BaseCreature - { - public override bool CanTeach => true; - public override bool ClickTitle => false; + public class Samurai : BaseCreature + { + [Constructible] + public Samurai() : base(AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4) + { + Title = "the samurai"; - [Constructible] - public Samurai() : base( AIType.AI_Melee, FightMode.Aggressor, 10, 1, 0.2, 0.4 ) - { - Title = "the samurai"; + InitStats(100, 100, 25); - InitStats( 100, 100, 25 ); + SetSkill(SkillName.ArmsLore, 64.0, 80.0); + SetSkill(SkillName.Bushido, 64.0, 85.0); + SetSkill(SkillName.Parry, 64.0, 80.0); + SetSkill(SkillName.Swords, 64.0, 85.0); - SetSkill( SkillName.ArmsLore, 64.0, 80.0 ); - SetSkill( SkillName.Bushido, 64.0, 85.0 ); - SetSkill( SkillName.Parry, 64.0, 80.0 ); - SetSkill( SkillName.Swords, 64.0, 85.0 ); + SpeechHue = Utility.RandomDyedHue(); - SpeechHue = Utility.RandomDyedHue(); + Hue = Utility.RandomSkinHue(); - Hue = Utility.RandomSkinHue(); + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } + switch (Utility.Random(3)) + { + case 0: + AddItem(new Lajatang()); + break; + case 1: + AddItem(new Wakizashi()); + break; + case 2: + AddItem(new NoDachi()); + break; + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new Lajatang() ); break; - case 1: AddItem( new Wakizashi() ); break; - case 2: AddItem( new NoDachi() ); break; - } + switch (Utility.Random(3)) + { + case 0: + AddItem(new LeatherSuneate()); + break; + case 1: + AddItem(new PlateSuneate()); + break; + case 2: + AddItem(new StuddedHaidate()); + break; + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new LeatherSuneate() ); break; - case 1: AddItem( new PlateSuneate() ); break; - case 2: AddItem( new StuddedHaidate() ); break; - } + switch (Utility.Random(4)) + { + case 0: + AddItem(new LeatherJingasa()); + break; + case 1: + AddItem(new ChainHatsuburi()); + break; + case 2: + AddItem(new HeavyPlateJingasa()); + break; + case 3: + AddItem(new DecorativePlateKabuto()); + break; + } - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new LeatherJingasa() ); break; - case 1: AddItem( new ChainHatsuburi() ); break; - case 2: AddItem( new HeavyPlateJingasa() ); break; - case 3: AddItem( new DecorativePlateKabuto() ); break; - } + AddItem(new LeatherDo()); + AddItem(new LeatherHiroSode()); + AddItem(new SamuraiTabi(Utility.RandomNondyedHue())); // TODO: Hue - AddItem( new LeatherDo() ); - AddItem( new LeatherHiroSode() ); - AddItem( new SamuraiTabi( Utility.RandomNondyedHue() ) ); // TODO: Hue - - int hairHue = Utility.RandomNondyedHue(); + int hairHue = Utility.RandomNondyedHue(); - Utility.AssignRandomHair( this, hairHue ); + Utility.AssignRandomHair(this, hairHue); - if ( Utility.Random( 7 ) != 0 ) - Utility.AssignRandomFacialHair( this, hairHue ); + if (Utility.Random(7) != 0) + Utility.AssignRandomFacialHair(this, hairHue); - PackGold( 250, 300 ); - } + PackGold(250, 300); + } - public Samurai( Serial serial ) : base( serial ) - { - } + public Samurai(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override bool CanTeach => true; + public override bool ClickTitle => false; - writer.WriteEncodedInt( 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(0); // version + } - int version = reader.ReadEncodedInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/Sculptor.cs b/Scripts/Mobiles/Townfolk/Sculptor.cs index 40050116d..95743bf31 100644 --- a/Scripts/Mobiles/Townfolk/Sculptor.cs +++ b/Scripts/Mobiles/Townfolk/Sculptor.cs @@ -2,66 +2,65 @@ using Server.Items; namespace Server.Mobiles { - public class Sculptor : BaseCreature - { - [Constructible] - public Sculptor() - : base( AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4 ) - { - InitStats( 31, 41, 51 ); + public class Sculptor : BaseCreature + { + [Constructible] + public Sculptor() + : base(AIType.AI_Animal, FightMode.None, 10, 1, 0.2, 0.4) + { + InitStats(31, 41, 51); - SpeechHue = Utility.RandomDyedHue(); - Title = "the sculptor"; - Hue = Utility.RandomSkinHue(); + SpeechHue = Utility.RandomDyedHue(); + Title = "the sculptor"; + Hue = Utility.RandomSkinHue(); - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - AddItem( new Kilt( Utility.RandomNeutralHue() ) ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - AddItem( new LongPants( Utility.RandomNeutralHue() ) ); - } + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + AddItem(new Kilt(Utility.RandomNeutralHue())); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + AddItem(new LongPants(Utility.RandomNeutralHue())); + } + AddItem(new Doublet(Utility.RandomNeutralHue())); + AddItem(new HalfApron()); - AddItem( new Doublet( Utility.RandomNeutralHue() ) ); - AddItem( new HalfApron() ); + Utility.AssignRandomHair(this); - Utility.AssignRandomHair( this ); + Container pack = new Backpack(); - Container pack = new Backpack(); + pack.DropItem(new Gold(250, 300)); - pack.DropItem( new Gold( 250, 300 ) ); + pack.Movable = false; - pack.Movable = false; + AddItem(pack); + } - AddItem( pack ); - } + public Sculptor(Serial serial) + : base(serial) + { + } - public override bool ClickTitle => false; + public override bool ClickTitle => false; - public Sculptor( Serial serial ) - : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int)0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/SeekerOfAdventure.cs b/Scripts/Mobiles/Townfolk/SeekerOfAdventure.cs index bd3934033..3d766024b 100644 --- a/Scripts/Mobiles/Townfolk/SeekerOfAdventure.cs +++ b/Scripts/Mobiles/Townfolk/SeekerOfAdventure.cs @@ -3,92 +3,94 @@ using EDI = Server.Mobiles.EscortDestinationInfo; namespace Server.Mobiles { - public class SeekerOfAdventure : BaseEscortable - { - private static string[] m_Dungeons = { - "Covetous", "Deceit", "Despise", - "Destard", "Hythloth", "Shame", // Old Code for Pre-ML shards. - "Wrong" - }; + public class SeekerOfAdventure : BaseEscortable + { + private static string[] m_Dungeons = + { + "Covetous", "Deceit", "Despise", + "Destard", "Hythloth", "Shame", // Old Code for Pre-ML shards. + "Wrong" + }; - private static string[] m_MLDestinations = { - "Cove", "Serpent's Hold", "Jhelom", // ML List - "Nujel'm" - }; + private static string[] m_MLDestinations = + { + "Cove", "Serpent's Hold", "Jhelom", // ML List + "Nujel'm" + }; - public override string[] GetPossibleDestinations() - { - if ( Core.ML ) - return m_MLDestinations; - return m_Dungeons; - } + [Constructible] + public SeekerOfAdventure() + { + Title = "the seeker of adventure"; + } - [Constructible] - public SeekerOfAdventure() - { - Title = "the seeker of adventure"; - } + public SeekerOfAdventure(Serial serial) : base(serial) + { + } - public override bool ClickTitle => false; // Do not display 'the seeker of adventure' when single-clicking + public override bool ClickTitle => false; // Do not display 'the seeker of adventure' when single-clicking - private static int GetRandomHue() - { - switch ( Utility.Random( 6 ) ) - { - default: - case 0: return 0; - case 1: return Utility.RandomBlueHue(); - case 2: return Utility.RandomGreenHue(); - case 3: return Utility.RandomRedHue(); - case 4: return Utility.RandomYellowHue(); - case 5: return Utility.RandomNeutralHue(); - } - } + public override string[] GetPossibleDestinations() + { + if (Core.ML) + return m_MLDestinations; + return m_Dungeons; + } - public override void InitOutfit() - { - if ( Female ) - AddItem( new FancyDress( GetRandomHue() ) ); - else - AddItem( new FancyShirt( GetRandomHue() ) ); + private static int GetRandomHue() + { + switch (Utility.Random(6)) + { + default: + case 0: return 0; + case 1: return Utility.RandomBlueHue(); + case 2: return Utility.RandomGreenHue(); + case 3: return Utility.RandomRedHue(); + case 4: return Utility.RandomYellowHue(); + case 5: return Utility.RandomNeutralHue(); + } + } - int lowHue = GetRandomHue(); + public override void InitOutfit() + { + if (Female) + AddItem(new FancyDress(GetRandomHue())); + else + AddItem(new FancyShirt(GetRandomHue())); - AddItem( new ShortPants( lowHue ) ); + int lowHue = GetRandomHue(); - if ( Female ) - AddItem( new ThighBoots( lowHue ) ); - else - AddItem( new Boots( lowHue ) ); + AddItem(new ShortPants(lowHue)); - if ( !Female ) - AddItem( new BodySash( lowHue ) ); + if (Female) + AddItem(new ThighBoots(lowHue)); + else + AddItem(new Boots(lowHue)); - AddItem( new Cloak( GetRandomHue() ) ); + if (!Female) + AddItem(new BodySash(lowHue)); - AddItem( new Longsword() ); + AddItem(new Cloak(GetRandomHue())); - Utility.AssignRandomHair( this ); + AddItem(new Longsword()); - PackGold( 100, 150 ); - } + Utility.AssignRandomHair(this); - public SeekerOfAdventure( Serial serial ) : base( serial ) - { - } + PackGold(100, 150); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Townfolk/TownCrier.cs b/Scripts/Mobiles/Townfolk/TownCrier.cs index c007021ac..f5290d338 100644 --- a/Scripts/Mobiles/Townfolk/TownCrier.cs +++ b/Scripts/Mobiles/Townfolk/TownCrier.cs @@ -1,548 +1,553 @@ using System; -using System.Text; using System.Collections.Generic; -using Server.Prompts; -using Server.Gumps; -using Server.Network; -using Server.Items; +using System.Text; using Server.Commands; +using Server.Gumps; +using Server.Items; +using Server.Network; +using Server.Prompts; namespace Server.Mobiles { - public interface ITownCrierEntryList - { - List Entries{ get; } - TownCrierEntry GetRandomEntry(); - TownCrierEntry AddEntry( string[] lines, TimeSpan duration ); - void RemoveEntry( TownCrierEntry entry ); - } + public interface ITownCrierEntryList + { + List Entries{ get; } + TownCrierEntry GetRandomEntry(); + TownCrierEntry AddEntry(string[] lines, TimeSpan duration); + void RemoveEntry(TownCrierEntry entry); + } - public class GlobalTownCrierEntryList : ITownCrierEntryList - { - private static GlobalTownCrierEntryList m_Instance; + public class GlobalTownCrierEntryList : ITownCrierEntryList + { + private static GlobalTownCrierEntryList m_Instance; - public static void Initialize() - { - CommandSystem.Register( "TownCriers", AccessLevel.GameMaster, TownCriers_OnCommand ); - } + public static GlobalTownCrierEntryList Instance + { + get + { + if (m_Instance == null) + m_Instance = new GlobalTownCrierEntryList(); - [Usage( "TownCriers" )] - [Description( "Manages the global town crier list." )] - public static void TownCriers_OnCommand( CommandEventArgs e ) - { - e.Mobile.SendGump( new TownCrierGump( e.Mobile, Instance ) ); - } + return m_Instance; + } + } - public static GlobalTownCrierEntryList Instance - { - get - { - if ( m_Instance == null ) - m_Instance = new GlobalTownCrierEntryList(); + public bool IsEmpty => Entries == null || Entries.Count == 0; - return m_Instance; - } - } + public List Entries{ get; private set; } - public bool IsEmpty => ( Entries == null || Entries.Count == 0 ); + public TownCrierEntry GetRandomEntry() + { + if (Entries == null || Entries.Count == 0) + return null; - public GlobalTownCrierEntryList() - { - } + for (int i = Entries.Count - 1; Entries != null && i >= 0; --i) + { + if (i >= Entries.Count) + continue; - public List Entries { get; private set; } + TownCrierEntry tce = Entries[i]; - public TownCrierEntry GetRandomEntry() - { - if ( Entries == null || Entries.Count == 0 ) - return null; + if (tce.Expired) + RemoveEntry(tce); + } - for ( int i = Entries.Count - 1; Entries != null && i >= 0; --i ) - { - if ( i >= Entries.Count ) - continue; + if (Entries == null || Entries.Count == 0) + return null; - TownCrierEntry tce = Entries[i]; + return Entries[Utility.Random(Entries.Count)]; + } - if ( tce.Expired ) - RemoveEntry( tce ); - } + public TownCrierEntry AddEntry(string[] lines, TimeSpan duration) + { + if (Entries == null) + Entries = new List(); - if ( Entries == null || Entries.Count == 0 ) - return null; - - return Entries[Utility.Random( Entries.Count )]; - } - - public TownCrierEntry AddEntry( string[] lines, TimeSpan duration ) - { - if ( Entries == null ) - Entries = new List(); - - TownCrierEntry tce = new TownCrierEntry( lines, duration ); - - Entries.Add( tce ); - - List instances = TownCrier.Instances; - - for ( int i = 0; i < instances.Count; ++i ) - instances[i].ForceBeginAutoShout(); - - return tce; - } - - public void RemoveEntry( TownCrierEntry tce ) - { - if ( Entries == null ) - return; - - Entries.Remove( tce ); - - if ( Entries.Count == 0 ) - Entries = null; - } - } - - public class TownCrierEntry - { - public string[] Lines { get; } - - public DateTime ExpireTime { get; } - - public bool Expired => ( DateTime.UtcNow >= ExpireTime ); - - public TownCrierEntry( string[] lines, TimeSpan duration ) - { - Lines = lines; - - if ( duration < TimeSpan.Zero ) - duration = TimeSpan.Zero; - else if ( duration > TimeSpan.FromDays( 365.0 ) ) - duration = TimeSpan.FromDays( 365.0 ); - - ExpireTime = DateTime.UtcNow + duration; - } - } - - public class TownCrierDurationPrompt : Prompt - { - private ITownCrierEntryList m_Owner; - - public TownCrierDurationPrompt( ITownCrierEntryList owner ) - { - m_Owner = owner; - } - - public override void OnResponse( Mobile from, string text ) - { - TimeSpan ts; - - if ( !TimeSpan.TryParse( text, out ts ) ) - { - from.SendMessage( "Value was not properly formatted. Use: " ); - from.SendGump( new TownCrierGump( from, m_Owner ) ); - return; - } - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - from.SendMessage( "Duration set to: {0}", ts ); - from.SendMessage( "Enter the first line to shout:" ); - - from.Prompt = new TownCrierLinesPrompt( m_Owner, null, new List(), ts ); - } - - public override void OnCancel( Mobile from ) - { - from.SendLocalizedMessage( 502980 ); // Message entry cancelled. - from.SendGump( new TownCrierGump( from, m_Owner ) ); - } - } - - public class TownCrierLinesPrompt : Prompt - { - private ITownCrierEntryList m_Owner; - private TownCrierEntry m_Entry; - private List m_Lines; - private TimeSpan m_Duration; - - public TownCrierLinesPrompt( ITownCrierEntryList owner, TownCrierEntry entry, List lines, TimeSpan duration ) - { - m_Owner = owner; - m_Entry = entry; - m_Lines = lines; - m_Duration = duration; - } - - public override void OnResponse( Mobile from, string text ) - { - m_Lines.Add( text ); - - from.SendMessage( "Enter the next line to shout, or press if the message is finished." ); - from.Prompt = new TownCrierLinesPrompt( m_Owner, m_Entry, m_Lines, m_Duration ); - } - - public override void OnCancel( Mobile from ) - { - if ( m_Entry != null ) - m_Owner.RemoveEntry( m_Entry ); - - if ( m_Lines.Count > 0 ) - { - m_Owner.AddEntry( m_Lines.ToArray(), m_Duration ); - from.SendMessage( "Message has been set." ); - } - else - { - if ( m_Entry != null ) - from.SendMessage( "Message deleted." ); - else - from.SendLocalizedMessage( 502980 ); // Message entry cancelled. - } - - from.SendGump( new TownCrierGump( from, m_Owner ) ); - } - } - - public class TownCrierGump : Gump - { - private Mobile m_From; - private ITownCrierEntryList m_Owner; - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - { - m_From.SendMessage( "Enter the duration for the new message. Format: " ); - m_From.Prompt = new TownCrierDurationPrompt( m_Owner ); - } - else if ( info.ButtonID > 1 ) - { - List entries = m_Owner.Entries; - int index = info.ButtonID - 2; - - if ( entries != null && index < entries.Count ) - { - TownCrierEntry tce = entries[index]; - TimeSpan ts = tce.ExpireTime - DateTime.UtcNow; - - if ( ts < TimeSpan.Zero ) - ts = TimeSpan.Zero; - - m_From.SendMessage( "Editing entry #{0}.", index + 1 ); - m_From.SendMessage( "Enter the first line to shout:" ); - m_From.Prompt = new TownCrierLinesPrompt( m_Owner, tce, new List(), ts ); - } - } - } - - public TownCrierGump( Mobile from, ITownCrierEntryList owner ) : base( 50, 50 ) - { - m_From = from; - m_Owner = owner; - - from.CloseGump( typeof( TownCrierGump ) ); - - AddPage( 0 ); - - List entries = owner.Entries; - - owner.GetRandomEntry(); // force expiration checks - - int count = 0; - - if ( entries != null ) - count = entries.Count; - - AddImageTiled( 0, 0, 300, 38 + (count == 0 ? 20 : (count * 85)), 0xA40 ); - AddAlphaRegion( 1, 1, 298, 36 + (count == 0 ? 20 : (count * 85)) ); - - AddHtml( 8, 8, 300 - 8 - 30, 20, "
TOWN CRIER MESSAGES
", false, false ); - - AddButton( 300 - 8 - 30, 8, 0xFAB, 0xFAD, 1, GumpButtonType.Reply, 0 ); - - if ( count == 0 ) - { - AddHtml( 8, 30, 284, 20, "The crier has no news.", false, false ); - } - else - { - for ( int i = 0; i < entries.Count; ++i ) - { - TownCrierEntry tce = (TownCrierEntry)entries[i]; - - TimeSpan toExpire = tce.ExpireTime - DateTime.UtcNow; + TownCrierEntry tce = new TownCrierEntry(lines, duration); + + Entries.Add(tce); + + List instances = TownCrier.Instances; + + for (int i = 0; i < instances.Count; ++i) + instances[i].ForceBeginAutoShout(); + + return tce; + } + + public void RemoveEntry(TownCrierEntry tce) + { + if (Entries == null) + return; + + Entries.Remove(tce); + + if (Entries.Count == 0) + Entries = null; + } + + public static void Initialize() + { + CommandSystem.Register("TownCriers", AccessLevel.GameMaster, TownCriers_OnCommand); + } + + [Usage("TownCriers")] + [Description("Manages the global town crier list.")] + public static void TownCriers_OnCommand(CommandEventArgs e) + { + e.Mobile.SendGump(new TownCrierGump(e.Mobile, Instance)); + } + } + + public class TownCrierEntry + { + public TownCrierEntry(string[] lines, TimeSpan duration) + { + Lines = lines; + + if (duration < TimeSpan.Zero) + duration = TimeSpan.Zero; + else if (duration > TimeSpan.FromDays(365.0)) + duration = TimeSpan.FromDays(365.0); + + ExpireTime = DateTime.UtcNow + duration; + } + + public string[] Lines{ get; } + + public DateTime ExpireTime{ get; } + + public bool Expired => DateTime.UtcNow >= ExpireTime; + } + + public class TownCrierDurationPrompt : Prompt + { + private ITownCrierEntryList m_Owner; - if ( toExpire < TimeSpan.Zero ) - toExpire = TimeSpan.Zero; + public TownCrierDurationPrompt(ITownCrierEntryList owner) + { + m_Owner = owner; + } - StringBuilder sb = new StringBuilder(); + public override void OnResponse(Mobile from, string text) + { + TimeSpan ts; - sb.Append( "[Expires: " ); + if (!TimeSpan.TryParse(text, out ts)) + { + from.SendMessage("Value was not properly formatted. Use: "); + from.SendGump(new TownCrierGump(from, m_Owner)); + return; + } - if ( toExpire.TotalHours >= 1 ) - { - sb.Append( (int)toExpire.TotalHours ); - sb.Append( ':' ); - sb.Append( toExpire.Minutes.ToString( "D2" ) ); - } - else - { - sb.Append( toExpire.Minutes ); - } + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; - sb.Append( ':' ); - sb.Append( toExpire.Seconds.ToString( "D2" ) ); + from.SendMessage("Duration set to: {0}", ts); + from.SendMessage("Enter the first line to shout:"); - sb.Append( "] " ); + from.Prompt = new TownCrierLinesPrompt(m_Owner, null, new List(), ts); + } - for ( int j = 0; j < tce.Lines.Length; ++j ) - { - if ( j > 0 ) - sb.Append( "
" ); + public override void OnCancel(Mobile from) + { + from.SendLocalizedMessage(502980); // Message entry cancelled. + from.SendGump(new TownCrierGump(from, m_Owner)); + } + } + + public class TownCrierLinesPrompt : Prompt + { + private TimeSpan m_Duration; + private TownCrierEntry m_Entry; + private List m_Lines; + private ITownCrierEntryList m_Owner; - sb.Append( tce.Lines[j] ); - } + public TownCrierLinesPrompt(ITownCrierEntryList owner, TownCrierEntry entry, List lines, TimeSpan duration) + { + m_Owner = owner; + m_Entry = entry; + m_Lines = lines; + m_Duration = duration; + } + + public override void OnResponse(Mobile from, string text) + { + m_Lines.Add(text); + + from.SendMessage("Enter the next line to shout, or press if the message is finished."); + from.Prompt = new TownCrierLinesPrompt(m_Owner, m_Entry, m_Lines, m_Duration); + } + + public override void OnCancel(Mobile from) + { + if (m_Entry != null) + m_Owner.RemoveEntry(m_Entry); + + if (m_Lines.Count > 0) + { + m_Owner.AddEntry(m_Lines.ToArray(), m_Duration); + from.SendMessage("Message has been set."); + } + else + { + if (m_Entry != null) + from.SendMessage("Message deleted."); + else + from.SendLocalizedMessage(502980); // Message entry cancelled. + } + + from.SendGump(new TownCrierGump(from, m_Owner)); + } + } + + public class TownCrierGump : Gump + { + private Mobile m_From; + private ITownCrierEntryList m_Owner; + + public TownCrierGump(Mobile from, ITownCrierEntryList owner) : base(50, 50) + { + m_From = from; + m_Owner = owner; + + from.CloseGump(typeof(TownCrierGump)); + + AddPage(0); + + List entries = owner.Entries; + + owner.GetRandomEntry(); // force expiration checks + + int count = 0; + + if (entries != null) + count = entries.Count; + + AddImageTiled(0, 0, 300, 38 + (count == 0 ? 20 : count * 85), 0xA40); + AddAlphaRegion(1, 1, 298, 36 + (count == 0 ? 20 : count * 85)); + + AddHtml(8, 8, 300 - 8 - 30, 20, "
TOWN CRIER MESSAGES
", false, + false); + + AddButton(300 - 8 - 30, 8, 0xFAB, 0xFAD, 1, GumpButtonType.Reply, 0); + + if (count == 0) + AddHtml(8, 30, 284, 20, "The crier has no news.", false, false); + else + for (int i = 0; i < entries.Count; ++i) + { + TownCrierEntry tce = entries[i]; + + TimeSpan toExpire = tce.ExpireTime - DateTime.UtcNow; + + if (toExpire < TimeSpan.Zero) + toExpire = TimeSpan.Zero; + + StringBuilder sb = new StringBuilder(); + + sb.Append("[Expires: "); + + if (toExpire.TotalHours >= 1) + { + sb.Append((int)toExpire.TotalHours); + sb.Append(':'); + sb.Append(toExpire.Minutes.ToString("D2")); + } + else + { + sb.Append(toExpire.Minutes); + } + + sb.Append(':'); + sb.Append(toExpire.Seconds.ToString("D2")); + + sb.Append("] "); + + for (int j = 0; j < tce.Lines.Length; ++j) + { + if (j > 0) + sb.Append("
"); + + sb.Append(tce.Lines[j]); + } + + AddHtml(8, 35 + i * 85, 254, 80, sb.ToString(), true, true); + + AddButton(300 - 8 - 26, 35 + i * 85, 0x15E1, 0x15E5, 2 + i, GumpButtonType.Reply, 0); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + { + m_From.SendMessage("Enter the duration for the new message. Format: "); + m_From.Prompt = new TownCrierDurationPrompt(m_Owner); + } + else if (info.ButtonID > 1) + { + List entries = m_Owner.Entries; + int index = info.ButtonID - 2; + + if (entries != null && index < entries.Count) + { + TownCrierEntry tce = entries[index]; + TimeSpan ts = tce.ExpireTime - DateTime.UtcNow; - AddHtml( 8, 35 + (i * 85), 254, 80, sb.ToString(), true, true ); + if (ts < TimeSpan.Zero) + ts = TimeSpan.Zero; - AddButton( 300 - 8 - 26, 35 + (i * 85), 0x15E1, 0x15E5, 2 + i, GumpButtonType.Reply, 0 ); - } - } - } - } + m_From.SendMessage("Editing entry #{0}.", index + 1); + m_From.SendMessage("Enter the first line to shout:"); + m_From.Prompt = new TownCrierLinesPrompt(m_Owner, tce, new List(), ts); + } + } + } + } - public class TownCrier : Mobile, ITownCrierEntryList - { - private Timer m_NewsTimer; - private Timer m_AutoShoutTimer; + public class TownCrier : Mobile, ITownCrierEntryList + { + private Timer m_AutoShoutTimer; + private Timer m_NewsTimer; - public List Entries { get; private set; } + [Constructible] + public TownCrier() + { + Instances.Add(this); - public TownCrierEntry GetRandomEntry() - { - if ( Entries == null || Entries.Count == 0 ) - return GlobalTownCrierEntryList.Instance.GetRandomEntry(); + InitStats(100, 100, 25); - for ( int i = Entries.Count - 1; Entries != null && i >= 0; --i ) - { - if ( i >= Entries.Count ) - continue; + Title = "the town crier"; + Hue = Utility.RandomSkinHue(); - TownCrierEntry tce = Entries[i]; + if (!Core.AOS) + NameHue = 0x35; - if ( tce.Expired ) - RemoveEntry( tce ); - } + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } - if ( Entries == null || Entries.Count == 0 ) - return GlobalTownCrierEntryList.Instance.GetRandomEntry(); + AddItem(new FancyShirt(Utility.RandomBlueHue())); - TownCrierEntry entry = GlobalTownCrierEntryList.Instance.GetRandomEntry(); + Item skirt; - if ( entry == null || Utility.RandomBool() ) - entry = Entries[Utility.Random( Entries.Count )]; + switch (Utility.Random(2)) + { + case 0: + skirt = new Skirt(); + break; + default: + case 1: + skirt = new Kilt(); + break; + } + + skirt.Hue = Utility.RandomGreenHue(); + + AddItem(skirt); - return entry; - } + AddItem(new FeatheredHat(Utility.RandomGreenHue())); - public void ForceBeginAutoShout() - { - if ( m_AutoShoutTimer == null ) - m_AutoShoutTimer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromMinutes( 1.0 ), AutoShout_Callback ); - } - - public TownCrierEntry AddEntry( string[] lines, TimeSpan duration ) - { - if ( Entries == null ) - Entries = new List(); - - TownCrierEntry tce = new TownCrierEntry( lines, duration ); - - Entries.Add( tce ); - - if ( m_AutoShoutTimer == null ) - m_AutoShoutTimer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromMinutes( 1.0 ), AutoShout_Callback ); - - return tce; - } - - public void RemoveEntry( TownCrierEntry tce ) - { - if ( Entries == null ) - return; + Item boots; - Entries.Remove( tce ); - - if ( Entries.Count == 0 ) - Entries = null; - - if ( Entries == null && GlobalTownCrierEntryList.Instance.IsEmpty ) - { - m_AutoShoutTimer?.Stop(); - - m_AutoShoutTimer = null; - } - } - - private void AutoShout_Callback() - { - TownCrierEntry tce = GetRandomEntry(); - - if ( tce == null ) - { - m_AutoShoutTimer?.Stop(); - - m_AutoShoutTimer = null; - } - else if ( m_NewsTimer == null ) - { - m_NewsTimer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 3.0 ), new TimerStateCallback( ShoutNews_Callback ), new object[]{ tce, 0 } ); + switch (Utility.Random(2)) + { + case 0: + boots = new Boots(); + break; + default: + case 1: + boots = new ThighBoots(); + break; + } - PublicOverheadMessage( MessageType.Regular, 0x3B2, 502976 ); // Hear ye! Hear ye! - } - } - - private void ShoutNews_Callback( object state ) - { - object[] states = (object[])state; - TownCrierEntry tce = (TownCrierEntry)states[0]; - int index = (int)states[1]; - - if ( index < 0 || index >= tce.Lines.Length ) - { - m_NewsTimer?.Stop(); - - m_NewsTimer = null; - } - else - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, false, tce.Lines[index] ); - states[1] = index + 1; - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster ) - from.SendGump( new TownCrierGump( from, this ) ); - else - base.OnDoubleClick( from ); - } - - public override bool HandlesOnSpeech( Mobile from ) - { - return ( m_NewsTimer == null && from.Alive && InRange( from, 12 ) ); - } - - public override void OnSpeech( SpeechEventArgs e ) - { - if ( m_NewsTimer == null && e.HasKeyword( 0x30 ) && e.Mobile.Alive && InRange( e.Mobile, 12 ) ) // *news* - { - Direction = GetDirectionTo( e.Mobile ); - - TownCrierEntry tce = GetRandomEntry(); - - if ( tce == null ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1005643 ); // I have no news at this time. - } - else - { - m_NewsTimer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 3.0 ), new TimerStateCallback( ShoutNews_Callback ), new object[]{ tce, 0 } ); - - PublicOverheadMessage( MessageType.Regular, 0x3B2, 502978 ); // Some of the latest news! - } - } - } - - public static List Instances { get; } = new List(); - - [Constructible] - public TownCrier() - { - Instances.Add( this ); - - InitStats( 100, 100, 25 ); - - Title = "the town crier"; - Hue = Utility.RandomSkinHue(); - - if ( !Core.AOS ) - NameHue = 0x35; - - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } - - AddItem( new FancyShirt( Utility.RandomBlueHue() ) ); - - Item skirt; - - switch ( Utility.Random( 2 ) ) - { - case 0: skirt = new Skirt(); break; - default: case 1: skirt = new Kilt(); break; - } - - skirt.Hue = Utility.RandomGreenHue(); - - AddItem( skirt ); - - AddItem( new FeatheredHat( Utility.RandomGreenHue() ) ); - - Item boots; - - switch ( Utility.Random( 2 ) ) - { - case 0: boots = new Boots(); break; - default: case 1: boots = new ThighBoots(); break; - } - - AddItem( boots ); - - Utility.AssignRandomHair( this ); - } - - public override bool CanBeDamaged() - { - return false; - } - - public override void OnDelete() - { - Instances.Remove( this ); - base.OnDelete(); - } - - public TownCrier( Serial serial ) : base( serial ) - { - Instances.Add( this ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Core.AOS && NameHue == 0x35 ) - NameHue = -1; - } - } -} + AddItem(boots); + + Utility.AssignRandomHair(this); + } + + public TownCrier(Serial serial) : base(serial) + { + Instances.Add(this); + } + + public static List Instances{ get; } = new List(); + + public List Entries{ get; private set; } + + public TownCrierEntry GetRandomEntry() + { + if (Entries == null || Entries.Count == 0) + return GlobalTownCrierEntryList.Instance.GetRandomEntry(); + + for (int i = Entries.Count - 1; Entries != null && i >= 0; --i) + { + if (i >= Entries.Count) + continue; + + TownCrierEntry tce = Entries[i]; + + if (tce.Expired) + RemoveEntry(tce); + } + + if (Entries == null || Entries.Count == 0) + return GlobalTownCrierEntryList.Instance.GetRandomEntry(); + + TownCrierEntry entry = GlobalTownCrierEntryList.Instance.GetRandomEntry(); + + if (entry == null || Utility.RandomBool()) + entry = Entries[Utility.Random(Entries.Count)]; + + return entry; + } + + public TownCrierEntry AddEntry(string[] lines, TimeSpan duration) + { + if (Entries == null) + Entries = new List(); + + TownCrierEntry tce = new TownCrierEntry(lines, duration); + + Entries.Add(tce); + + if (m_AutoShoutTimer == null) + m_AutoShoutTimer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), TimeSpan.FromMinutes(1.0), AutoShout_Callback); + + return tce; + } + + public void RemoveEntry(TownCrierEntry tce) + { + if (Entries == null) + return; + + Entries.Remove(tce); + + if (Entries.Count == 0) + Entries = null; + + if (Entries == null && GlobalTownCrierEntryList.Instance.IsEmpty) + { + m_AutoShoutTimer?.Stop(); + + m_AutoShoutTimer = null; + } + } + + public void ForceBeginAutoShout() + { + if (m_AutoShoutTimer == null) + m_AutoShoutTimer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), TimeSpan.FromMinutes(1.0), AutoShout_Callback); + } + + private void AutoShout_Callback() + { + TownCrierEntry tce = GetRandomEntry(); + + if (tce == null) + { + m_AutoShoutTimer?.Stop(); + + m_AutoShoutTimer = null; + } + else if (m_NewsTimer == null) + { + m_NewsTimer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(3.0), + new TimerStateCallback(ShoutNews_Callback), new object[] { tce, 0 }); + + PublicOverheadMessage(MessageType.Regular, 0x3B2, 502976); // Hear ye! Hear ye! + } + } + + private void ShoutNews_Callback(object state) + { + object[] states = (object[])state; + TownCrierEntry tce = (TownCrierEntry)states[0]; + int index = (int)states[1]; + + if (index < 0 || index >= tce.Lines.Length) + { + m_NewsTimer?.Stop(); + + m_NewsTimer = null; + } + else + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, false, tce.Lines[index]); + states[1] = index + 1; + } + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster) + from.SendGump(new TownCrierGump(from, this)); + else + base.OnDoubleClick(from); + } + + public override bool HandlesOnSpeech(Mobile from) + { + return m_NewsTimer == null && from.Alive && InRange(from, 12); + } + + public override void OnSpeech(SpeechEventArgs e) + { + if (m_NewsTimer == null && e.HasKeyword(0x30) && e.Mobile.Alive && InRange(e.Mobile, 12)) // *news* + { + Direction = GetDirectionTo(e.Mobile); + + TownCrierEntry tce = GetRandomEntry(); + + if (tce == null) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1005643); // I have no news at this time. + } + else + { + m_NewsTimer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(3.0), + new TimerStateCallback(ShoutNews_Callback), new object[] { tce, 0 }); + + PublicOverheadMessage(MessageType.Regular, 0x3B2, 502978); // Some of the latest news! + } + } + } + + public override bool CanBeDamaged() + { + return false; + } + + public override void OnDelete() + { + Instances.Remove(this); + base.OnDelete(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Core.AOS && NameHue == 0x35) + NameHue = -1; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/AnimalBuy.cs b/Scripts/Mobiles/Vendors/AnimalBuy.cs index de189059e..15dca90c1 100644 --- a/Scripts/Mobiles/Vendors/AnimalBuy.cs +++ b/Scripts/Mobiles/Vendors/AnimalBuy.cs @@ -2,17 +2,19 @@ using System; namespace Server.Mobiles { - public class AnimalBuyInfo : GenericBuyInfo - { - public AnimalBuyInfo( int controlSlots, Type type, int price, int amount, int itemID, int hue ) : this( controlSlots, null, type, price, amount, itemID, hue ) - { - } + public class AnimalBuyInfo : GenericBuyInfo + { + public AnimalBuyInfo(int controlSlots, Type type, int price, int amount, int itemID, int hue) : this(controlSlots, + null, type, price, amount, itemID, hue) + { + } - public AnimalBuyInfo( int controlSlots, string name, Type type, int price, int amount, int itemID, int hue ) : base( name, type, price, amount, itemID, hue ) - { - ControlSlots = controlSlots; - } + public AnimalBuyInfo(int controlSlots, string name, Type type, int price, int amount, int itemID, int hue) : base( + name, type, price, amount, itemID, hue) + { + ControlSlots = controlSlots; + } - public override int ControlSlots { get; } - } + public override int ControlSlots{ get; } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/BaseVendor.cs b/Scripts/Mobiles/Vendors/BaseVendor.cs index 5ca6ed04e..a7bcd8d7b 100644 --- a/Scripts/Mobiles/Vendors/BaseVendor.cs +++ b/Scripts/Mobiles/Vendors/BaseVendor.cs @@ -1,1487 +1,1520 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Items; -using Server.Network; using Server.ContextMenus; -using Server.Mobiles; -using Server.Misc; using Server.Engines.BulkOrders; -using Server.Regions; using Server.Factions; +using Server.Items; +using Server.Misc; +using Server.Mobiles; +using Server.Network; +using Server.Regions; namespace Server.Mobiles { - public enum VendorShoeType - { - None, - Shoes, - Boots, - Sandals, - ThighBoots - } + public enum VendorShoeType + { + None, + Shoes, + Boots, + Sandals, + ThighBoots + } - public abstract class BaseVendor : BaseCreature, IVendor - { - private const int MaxSell = 500; + public abstract class BaseVendor : BaseCreature, IVendor + { + private const int MaxSell = 500; - protected abstract List SBInfos { get; } + private static TimeSpan InventoryDecayTime = TimeSpan.FromHours(1.0); - private ArrayList m_ArmorBuyInfo = new ArrayList(); - private ArrayList m_ArmorSellInfo = new ArrayList(); + private ArrayList m_ArmorBuyInfo = new ArrayList(); + private ArrayList m_ArmorSellInfo = new ArrayList(); - public override bool CanTeach => true; - - public override bool BardImmune => true; - - public override bool PlayerRangeSensitive => true; - - public virtual bool IsActiveVendor => true; - public virtual bool IsActiveBuyer => IsActiveVendor; // response to vendor SELL - public virtual bool IsActiveSeller => IsActiveVendor; // response to vendor BUY - - public virtual NpcGuild NpcGuild => NpcGuild.None; - - public override bool IsInvulnerable => true; - - public virtual DateTime NextTrickOrTreat { get; set; } - - public override bool ShowFameTitle => false; - - public virtual bool IsValidBulkOrder( Item item ) - { - return false; - } - - public virtual Item CreateBulkOrder( Mobile from, bool fromContextMenu ) - { - return null; - } - - public virtual bool SupportsBulkOrders( Mobile from ) - { - return false; - } - - public virtual TimeSpan GetNextBulkOrder( Mobile from ) - { - return TimeSpan.Zero; - } - - public virtual void OnSuccessfulBulkOrderReceive( Mobile from ) - { - } - - #region Faction - public virtual int GetPriceScalar() - { - Town town = Town.FromRegion( Region ); - - if ( town != null ) - return ( 100 + town.Tax ); - - return 100; - } - - public void UpdateBuyInfo() - { - int priceScalar = GetPriceScalar(); - - IBuyItemInfo[] buyinfo = (IBuyItemInfo[])m_ArmorBuyInfo.ToArray( typeof( IBuyItemInfo ) ); - - if ( buyinfo != null ) - { - foreach ( IBuyItemInfo info in buyinfo ) - info.PriceScalar = priceScalar; - } - } - #endregion - - private class BulkOrderInfoEntry : ContextMenuEntry - { - private Mobile m_From; - private BaseVendor m_Vendor; - - public BulkOrderInfoEntry( Mobile from, BaseVendor vendor ) - : base( 6152 ) - { - m_From = from; - m_Vendor = vendor; - } - - public override void OnClick() - { - if ( m_Vendor.SupportsBulkOrders( m_From ) ) - { - TimeSpan ts = m_Vendor.GetNextBulkOrder( m_From ); - - int totalSeconds = (int)ts.TotalSeconds; - int totalHours = ( totalSeconds + 3599 ) / 3600; - int totalMinutes = ( totalSeconds + 59 ) / 60; - - if ( ( ( Core.SE ) ? totalMinutes == 0 : totalHours == 0 ) ) - { - m_From.SendLocalizedMessage( 1049038 ); // You can get an order now. - - if ( Core.AOS ) - { - Item bulkOrder = m_Vendor.CreateBulkOrder( m_From, true ); - - if ( bulkOrder is LargeBOD bod ) - m_From.SendGump( new LargeBODAcceptGump( m_From, bod ) ); - else if ( bulkOrder is SmallBOD smallBod ) - m_From.SendGump( new SmallBODAcceptGump( m_From, smallBod ) ); - } - } - else - { - int oldSpeechHue = m_Vendor.SpeechHue; - m_Vendor.SpeechHue = 0x3B2; - - if ( Core.SE ) - m_Vendor.SayTo( m_From, 1072058, totalMinutes.ToString() ); // An offer may be available in about ~1_minutes~ minutes. - else - m_Vendor.SayTo( m_From, 1049039, totalHours.ToString() ); // An offer may be available in about ~1_hours~ hours. - - m_Vendor.SpeechHue = oldSpeechHue; - } - } - } - } - - public BaseVendor( string title ) - : base( AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2 ) - { - LoadSBInfo(); - - Title = title; - InitBody(); - InitOutfit(); - - Container pack; - //these packs MUST exist, or the client will crash when the packets are sent - pack = new Backpack(); - pack.Layer = Layer.ShopBuy; - pack.Movable = false; - pack.Visible = false; - AddItem( pack ); - - pack = new Backpack(); - pack.Layer = Layer.ShopResale; - pack.Movable = false; - pack.Visible = false; - AddItem( pack ); - - LastRestock = DateTime.UtcNow; - } - - public BaseVendor( Serial serial ) - : base( serial ) - { - } - - public DateTime LastRestock { get; set; } - - public virtual TimeSpan RestockDelay => TimeSpan.FromHours( 1 ); - - public Container BuyPack - { - get - { - if ( !(FindItemOnLayer( Layer.ShopBuy ) is Container pack) ) - { - pack = new Backpack { Layer = Layer.ShopBuy, Visible = false }; - AddItem( pack ); - } - - return pack; - } - } - - public abstract void InitSBInfo(); - - public virtual bool IsTokunoVendor => ( Map == Map.Tokuno ); - - protected void LoadSBInfo() - { - LastRestock = DateTime.UtcNow; - - for ( int i = 0; i < m_ArmorBuyInfo.Count; ++i ) - { - if ( m_ArmorBuyInfo[i] is GenericBuyInfo buy ) - buy.DeleteDisplayEntity(); - } - - SBInfos.Clear(); - - InitSBInfo(); - - m_ArmorBuyInfo.Clear(); - m_ArmorSellInfo.Clear(); - - for ( int i = 0; i < SBInfos.Count; i++ ) - { - SBInfo sbInfo = (SBInfo)SBInfos[i]; - m_ArmorBuyInfo.AddRange( sbInfo.BuyInfo ); - m_ArmorSellInfo.Add( sbInfo.SellInfo ); - } - } - - public virtual bool GetGender() - { - return Utility.RandomBool(); - } - - public virtual void InitBody() - { - InitStats( 100, 100, 25 ); - - SpeechHue = Utility.RandomDyedHue(); - Hue = Utility.RandomSkinHue(); - - if ( Female = GetGender() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } - } - - public virtual int GetRandomHue() - { - switch ( Utility.Random( 5 ) ) - { - default: - case 0: return Utility.RandomBlueHue(); - case 1: return Utility.RandomGreenHue(); - case 2: return Utility.RandomRedHue(); - case 3: return Utility.RandomYellowHue(); - case 4: return Utility.RandomNeutralHue(); - } - } - - public virtual int GetShoeHue() - { - if ( 0.1 > Utility.RandomDouble() ) - return 0; - - return Utility.RandomNeutralHue(); - } - - public virtual VendorShoeType ShoeType => VendorShoeType.Shoes; - - public virtual void CheckMorph() - { - if ( CheckGargoyle() ) - return; - - if ( CheckNecromancer() ) - return; - - CheckTokuno(); - } - - public virtual bool CheckTokuno() - { - if ( Map != Map.Tokuno ) - return false; - - NameList n; - - if ( Female ) - n = NameList.GetNameList( "tokuno female" ); - else - n = NameList.GetNameList( "tokuno male" ); - - if ( !n.ContainsName( Name ) ) - TurnToTokuno(); - - return true; - } - - public virtual void TurnToTokuno() - { - if ( Female ) - Name = NameList.RandomName( "tokuno female" ); - else - Name = NameList.RandomName( "tokuno male" ); - } - - public virtual bool CheckGargoyle() - { - Map map = Map; - - if ( map != Map.Ilshenar ) - return false; - - if ( !Region.IsPartOf( "Gargoyle City" ) ) - return false; - - if ( Body != 0x2F6 || ( Hue & 0x8000 ) == 0 ) - TurnToGargoyle(); - - return true; - } - - public virtual bool CheckNecromancer() - { - Map map = Map; - - if ( map != Map.Malas ) - return false; - - if ( !Region.IsPartOf( "Umbra" ) ) - return false; - - if ( Hue != 0x83E8 ) - TurnToNecromancer(); - - return true; - } - - public override void OnAfterSpawn() - { - CheckMorph(); - } - - protected override void OnMapChange( Map oldMap ) - { - base.OnMapChange( oldMap ); - - CheckMorph(); - - LoadSBInfo(); - } - - public virtual int GetRandomNecromancerHue() - { - switch ( Utility.Random( 20 ) ) - { - case 0: return 0; - case 1: return 0x4E9; - default: return Utility.RandomList( 0x485, 0x497 ); - } - } - - public virtual void TurnToNecromancer() - { - for ( int i = 0; i < Items.Count; ++i ) - { - Item item = Items[i]; - - if ( item is Hair || item is Beard ) - item.Hue = 0; - else if ( item is BaseClothing || item is BaseWeapon || item is BaseArmor || item is BaseTool ) - item.Hue = GetRandomNecromancerHue(); - } - - HairHue = 0; - FacialHairHue = 0; - - Hue = 0x83E8; - } - - public virtual void TurnToGargoyle() - { - for ( int i = 0; i < Items.Count; ++i ) - { - Item item = Items[i]; - - if ( item is BaseClothing || item is Hair || item is Beard ) - item.Delete(); - } - - HairItemID = 0; - FacialHairItemID = 0; - - Body = 0x2F6; - Hue = Utility.RandomBrightHue() | 0x8000; - Name = NameList.RandomName( "gargoyle vendor" ); - - CapitalizeTitle(); - } - - public virtual void CapitalizeTitle() - { - string title = Title; - - if ( title == null ) - return; - - string[] split = title.Split( ' ' ); - - for ( int i = 0; i < split.Length; ++i ) - { - if ( Insensitive.Equals( split[i], "the" ) ) - continue; - - if ( split[i].Length > 1 ) - split[i] = char.ToUpper( split[i][0] ) + split[i].Substring( 1 ); - else if ( split[i].Length > 0 ) - split[i] = char.ToUpper( split[i][0] ).ToString(); - } - - Title = string.Join( " ", split ); - } - - public virtual int GetHairHue() - { - return Utility.RandomHairHue(); - } - - public virtual void InitOutfit() - { - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new FancyShirt( GetRandomHue() ) ); break; - case 1: AddItem( new Doublet( GetRandomHue() ) ); break; - case 2: AddItem( new Shirt( GetRandomHue() ) ); break; - } - - switch ( ShoeType ) - { - case VendorShoeType.Shoes: AddItem( new Shoes( GetShoeHue() ) ); break; - case VendorShoeType.Boots: AddItem( new Boots( GetShoeHue() ) ); break; - case VendorShoeType.Sandals: AddItem( new Sandals( GetShoeHue() ) ); break; - case VendorShoeType.ThighBoots: AddItem( new ThighBoots( GetShoeHue() ) ); break; - } - - int hairHue = GetHairHue(); - - Utility.AssignRandomHair( this, hairHue ); - Utility.AssignRandomFacialHair( this, hairHue ); - - if ( Female ) - { - switch ( Utility.Random( 6 ) ) - { - case 0: AddItem( new ShortPants( GetRandomHue() ) ); break; - case 1: - case 2: AddItem( new Kilt( GetRandomHue() ) ); break; - case 3: - case 4: - case 5: AddItem( new Skirt( GetRandomHue() ) ); break; - } - } - else - { - switch ( Utility.Random( 2 ) ) - { - case 0: AddItem( new LongPants( GetRandomHue() ) ); break; - case 1: AddItem( new ShortPants( GetRandomHue() ) ); break; - } - } - - PackGold( 100, 200 ); - } - - public virtual void Restock() - { - LastRestock = DateTime.UtcNow; - - IBuyItemInfo[] buyInfo = GetBuyInfo(); - - foreach ( IBuyItemInfo bii in buyInfo ) - bii.OnRestock(); - } - - private static TimeSpan InventoryDecayTime = TimeSpan.FromHours( 1.0 ); - - public virtual void VendorBuy( Mobile from ) - { - if ( !IsActiveSeller ) - return; - - if ( !from.CheckAlive() ) - return; - - if ( !CheckVendorAccess( from ) ) - { - Say( 501522 ); // I shall not treat with scum like thee! - return; - } - - if ( DateTime.UtcNow - LastRestock > RestockDelay ) - Restock(); - - UpdateBuyInfo(); - - int count = 0; - List list; - IBuyItemInfo[] buyInfo = GetBuyInfo(); - IShopSellInfo[] sellInfo = GetSellInfo(); - - list = new List( buyInfo.Length ); - Container cont = BuyPack; - - List opls = null; - - for ( int idx = 0; idx < buyInfo.Length; idx++ ) - { - IBuyItemInfo buyItem = (IBuyItemInfo)buyInfo[idx]; - - if ( buyItem.Amount <= 0 || list.Count >= 250 ) - continue; - - // NOTE: Only GBI supported; if you use another implementation of IBuyItemInfo, this will crash - GenericBuyInfo gbi = (GenericBuyInfo)buyItem; - IEntity disp = gbi.GetDisplayEntity(); - - list.Add( new BuyItemState( buyItem.Name, cont.Serial, disp?.Serial ?? (Serial)0x7FC0FFEE, buyItem.Price, buyItem.Amount, buyItem.ItemID, buyItem.Hue ) ); - count++; - - if ( opls == null ) { - opls = new List(); - } - - if ( disp is Item item ) { - opls.Add( item.PropertyList ); - } else if ( disp is Mobile mobile ) { - opls.Add( mobile.PropertyList ); - } - } - - List playerItems = cont.Items; - - for ( int i = playerItems.Count - 1; i >= 0; --i ) - { - if ( i >= playerItems.Count ) - continue; - - Item item = playerItems[i]; - - if ( ( item.LastMoved + InventoryDecayTime ) <= DateTime.UtcNow ) - item.Delete(); - } - - for ( int i = 0; i < playerItems.Count; ++i ) - { - Item item = playerItems[i]; - - int price = 0; - string name = null; - - foreach ( IShopSellInfo ssi in sellInfo ) - { - if ( ssi.IsSellable( item ) ) - { - price = ssi.GetBuyPriceFor( item ); - name = ssi.GetNameFor( item ); - break; - } - } + public BaseVendor(string title) + : base(AIType.AI_Vendor, FightMode.None, 2, 1, 0.5, 2) + { + LoadSBInfo(); - if ( name != null && list.Count < 250 ) - { - list.Add( new BuyItemState( name, cont.Serial, item.Serial, price, item.Amount, item.ItemID, item.Hue ) ); - count++; + Title = title; + InitBody(); + InitOutfit(); - if ( opls == null ) { - opls = new List(); - } + Container pack; + //these packs MUST exist, or the client will crash when the packets are sent + pack = new Backpack(); + pack.Layer = Layer.ShopBuy; + pack.Movable = false; + pack.Visible = false; + AddItem(pack); - opls.Add( item.PropertyList ); - } - } + pack = new Backpack(); + pack.Layer = Layer.ShopResale; + pack.Movable = false; + pack.Visible = false; + AddItem(pack); - //one (not all) of the packets uses a byte to describe number of items in the list. Osi = dumb. - //if ( list.Count > 255 ) - // Console.WriteLine( "Vendor Warning: Vendor {0} has more than 255 buy items, may cause client errors!", this ); + LastRestock = DateTime.UtcNow; + } - if ( list.Count > 0 ) - { - list.Sort( new BuyItemStateComparer() ); + public BaseVendor(Serial serial) + : base(serial) + { + } - SendPacksTo( from ); + protected abstract List SBInfos{ get; } - NetState ns = from.NetState; + public override bool CanTeach => true; - if ( ns == null ) - return; + public override bool BardImmune => true; - if ( ns.ContainerGridLines ) - from.Send( new VendorBuyContent6017( list ) ); - else - from.Send( new VendorBuyContent( list ) ); + public override bool PlayerRangeSensitive => true; - from.Send( new VendorBuyList( this, list ) ); + public virtual bool IsActiveVendor => true; + public virtual bool IsActiveBuyer => IsActiveVendor; // response to vendor SELL + public virtual bool IsActiveSeller => IsActiveVendor; // response to vendor BUY - if ( ns.HighSeas ) - from.Send( new DisplayBuyListHS( this ) ); - else - from.Send( new DisplayBuyList( this ) ); + public virtual NpcGuild NpcGuild => NpcGuild.None; - from.Send( new MobileStatusExtended( from ) );//make sure their gold amount is sent + public override bool IsInvulnerable => true; - if ( opls != null ) { - for ( int i = 0; i < opls.Count; ++i ) { - from.Send( opls[i] ); - } - } + public virtual DateTime NextTrickOrTreat{ get; set; } - SayTo( from, 500186 ); // Greetings. Have a look around. - } - } - - public virtual void SendPacksTo( Mobile from ) - { - Item pack = FindItemOnLayer( Layer.ShopBuy ); - - if ( pack == null ) - { - pack = new Backpack(); - pack.Layer = Layer.ShopBuy; - pack.Movable = false; - pack.Visible = false; - AddItem( pack ); - } - - from.Send( new EquipUpdate( pack ) ); - - pack = FindItemOnLayer( Layer.ShopSell ); - - if ( pack != null ) - from.Send( new EquipUpdate( pack ) ); - - pack = FindItemOnLayer( Layer.ShopResale ); - - if ( pack == null ) - { - pack = new Backpack(); - pack.Layer = Layer.ShopResale; - pack.Movable = false; - pack.Visible = false; - AddItem( pack ); - } - - from.Send( new EquipUpdate( pack ) ); - } - - public virtual void VendorSell( Mobile from ) - { - if ( !IsActiveBuyer ) - return; - - if ( !from.CheckAlive() ) - return; - - if ( !CheckVendorAccess( from ) ) - { - Say( 501522 ); // I shall not treat with scum like thee! - return; - } + public override bool ShowFameTitle => false; - Container pack = from.Backpack; + public Container BuyPack + { + get + { + if (!(FindItemOnLayer(Layer.ShopBuy) is Container pack)) + { + pack = new Backpack { Layer = Layer.ShopBuy, Visible = false }; + AddItem(pack); + } - if ( pack != null ) - { - IShopSellInfo[] info = GetSellInfo(); + return pack; + } + } - Dictionary table = new Dictionary(); + public virtual bool IsTokunoVendor => Map == Map.Tokuno; - foreach ( IShopSellInfo ssi in info ) - { - Item[] items = pack.FindItemsByType( ssi.Types ); + public virtual VendorShoeType ShoeType => VendorShoeType.Shoes; - foreach ( Item item in items ) - { - if ( item is Container container && container.Items.Count != 0 ) - continue; + public DateTime LastRestock{ get; set; } - if ( item.IsStandardLoot() && item.Movable && ssi.IsSellable( item ) ) - table[item] = new SellItemState( item, ssi.GetSellPriceFor( item ), ssi.GetNameFor( item ) ); - } - } + public virtual TimeSpan RestockDelay => TimeSpan.FromHours(1); - if ( table.Count > 0 ) - { - SendPacksTo( from ); - - from.Send( new VendorSellList( this, table.Values ) ); - } - else - { - Say( true, "You have nothing I would be interested in." ); - } - } - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - /* TODO: Thou art giving me? and fame/karma for gold gifts */ - - SmallBOD smallBod = dropped as SmallBOD; - LargeBOD largeBod = dropped as LargeBOD; - - if ( !(smallBod != null || largeBod != null) ) - return base.OnDragDrop( from, dropped ); - - PlayerMobile pm = from as PlayerMobile; + public virtual void Restock() + { + LastRestock = DateTime.UtcNow; - if ( Core.ML && pm?.NextBODTurnInTime > DateTime.UtcNow ) - { - SayTo( from, 1079976 ); // You'll have to wait a few seconds while I inspect the last order. - return false; - } - if ( !IsValidBulkOrder( dropped ) ) - { - SayTo( from, 1045130 ); // That order is for some other shopkeeper. - return false; - } - if ( smallBod?.Complete == false || largeBod?.Complete == false ) - { - SayTo( from, 1045131 ); // You have not completed the order yet. - return false; - } + IBuyItemInfo[] buyInfo = GetBuyInfo(); - Item reward; - int gold, fame; + foreach (IBuyItemInfo bii in buyInfo) + bii.OnRestock(); + } - if ( smallBod != null ) - smallBod.GetRewards( out reward, out gold, out fame ); - else - largeBod.GetRewards( out reward, out gold, out fame ); - - from.SendSound( 0x3D ); - - SayTo( from, 1045132 ); // Thank you so much! Here is a reward for your effort. - - if ( reward != null ) - from.AddToBackpack( reward ); - - if ( gold > 1000 ) - from.AddToBackpack( new BankCheck( gold ) ); - else if ( gold > 0 ) - from.AddToBackpack( new Gold( gold ) ); - - Titles.AwardFame( from, fame, true ); - - OnSuccessfulBulkOrderReceive( from ); - - if ( Core.ML && pm != null ) - pm.NextBODTurnInTime = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 ); - - dropped.Delete(); - return true; - } - - private GenericBuyInfo LookupDisplayObject( object obj ) - { - IBuyItemInfo[] buyInfo = GetBuyInfo(); - - for ( int i = 0; i < buyInfo.Length; ++i ) { - GenericBuyInfo gbi = (GenericBuyInfo)buyInfo[i]; - - if ( gbi.GetDisplayEntity() == obj ) - return gbi; - } - - return null; - } - - private void ProcessSinglePurchase( BuyItemResponse buy, IBuyItemInfo bii, List validBuy, ref int controlSlots, ref bool fullPurchase, ref int totalCost ) - { - int amount = buy.Amount; - - if ( amount > bii.Amount ) - amount = bii.Amount; - - if ( amount <= 0 ) - return; - - int slots = bii.ControlSlots * amount; - - if ( controlSlots >= slots ) - { - controlSlots -= slots; - } - else - { - fullPurchase = false; - return; - } - - totalCost += bii.Price * amount; - validBuy.Add( buy ); - } - - private void ProcessValidPurchase( int amount, IBuyItemInfo bii, Mobile buyer, Container cont ) - { - if ( amount > bii.Amount ) - amount = bii.Amount; - - if ( amount < 1 ) - return; - - bii.Amount -= amount; - - IEntity o = bii.GetEntity(); - - if ( o is Item item ) - { - if ( item.Stackable ) - { - item.Amount = amount; - - if ( cont == null || !cont.TryDropItem( buyer, item, false ) ) - item.MoveToWorld( buyer.Location, buyer.Map ); - } - else - { - item.Amount = 1; + public virtual bool OnBuyItems(Mobile buyer, List list) + { + if (!IsActiveSeller) + return false; - if ( cont == null || !cont.TryDropItem( buyer, item, false ) ) - item.MoveToWorld( buyer.Location, buyer.Map ); + if (!buyer.CheckAlive()) + return false; - for ( int i = 1; i < amount; i++ ) - { - item = bii.GetEntity() as Item; + if (!CheckVendorAccess(buyer)) + { + Say(501522); // I shall not treat with scum like thee! + return false; + } - if ( item != null ) - { - item.Amount = 1; + UpdateBuyInfo(); - if ( cont == null || !cont.TryDropItem( buyer, item, false ) ) - item.MoveToWorld( buyer.Location, buyer.Map ); - } - } - } - } - else if ( o is Mobile m ) - { - m.Direction = (Direction)Utility.Random( 8 ); - m.MoveToWorld( buyer.Location, buyer.Map ); - m.PlaySound( m.GetIdleSound() ); + // IBuyItemInfo[] buyInfo = this.GetBuyInfo(); + IShopSellInfo[] info = GetSellInfo(); + int totalCost = 0; + List validBuy = new List(list.Count); + Container cont; + bool bought = false; + bool fromBank = false; + bool fullPurchase = true; + int controlSlots = buyer.FollowersMax - buyer.Followers; - if (m is BaseCreature bc) + foreach (BuyItemResponse buy in list) + { + Serial ser = buy.Serial; + int amount = buy.Amount; + + if (ser.IsItem) + { + Item item = World.FindItem(ser); + + if (item == null) + continue; + + GenericBuyInfo gbi = LookupDisplayObject(item); + + if (gbi != null) + { + ProcessSinglePurchase(buy, gbi, validBuy, ref controlSlots, ref fullPurchase, ref totalCost); + } + else if (item != BuyPack && item.IsChildOf(BuyPack)) + { + if (amount > item.Amount) + amount = item.Amount; + + if (amount <= 0) + continue; + + foreach (IShopSellInfo ssi in info) + if (ssi.IsSellable(item)) + if (ssi.IsResellable(item)) { - bc.SetControlMaster(buyer); - bc.ControlOrder = OrderType.Stop; + totalCost += ssi.GetBuyPriceFor(item) * amount; + validBuy.Add(buy); + break; + } + } + } + else if (ser.IsMobile) + { + Mobile mob = World.FindMobile(ser); + + if (mob == null) + continue; + + GenericBuyInfo gbi = LookupDisplayObject(mob); + + if (gbi != null) + ProcessSinglePurchase(buy, gbi, validBuy, ref controlSlots, ref fullPurchase, ref totalCost); + } + } //foreach + + if (fullPurchase && validBuy.Count == 0) + SayTo(buyer, 500190); // Thou hast bought nothing! + else if (validBuy.Count == 0) + SayTo(buyer, 500187); // Your order cannot be fulfilled, please try again. + + if (validBuy.Count == 0) + return false; + + bought = buyer.AccessLevel >= AccessLevel.GameMaster; + + cont = buyer.Backpack; + if (!bought && cont != null) + { + if (cont.ConsumeTotal(typeof(Gold), totalCost)) + bought = true; + else if (totalCost < 2000) + SayTo(buyer, 500192); // Begging thy pardon, but thou canst not afford that. + } + + if (!bought && totalCost >= 2000) + { + cont = buyer.FindBankNoCreate(); + if (cont != null && cont.ConsumeTotal(typeof(Gold), totalCost)) + { + bought = true; + fromBank = true; + } + else + { + SayTo(buyer, 500191); //Begging thy pardon, but thy bank account lacks these funds. + } + } + + if (!bought) + return false; + + buyer.PlaySound(0x32); + + cont = buyer.Backpack; + if (cont == null) + cont = buyer.BankBox; + + foreach (BuyItemResponse buy in validBuy) + { + Serial ser = buy.Serial; + int amount = buy.Amount; + + if (amount < 1) + continue; + + if (ser.IsItem) + { + Item item = World.FindItem(ser); + + if (item == null) + continue; + + GenericBuyInfo gbi = LookupDisplayObject(item); + + if (gbi != null) + { + ProcessValidPurchase(amount, gbi, buyer, cont); + } + else + { + if (amount > item.Amount) + amount = item.Amount; + + foreach (IShopSellInfo ssi in info) + if (ssi.IsSellable(item)) + if (ssi.IsResellable(item)) + { + Item buyItem; + if (amount >= item.Amount) + { + buyItem = item; + } + else + { + buyItem = LiftItemDupe(item, item.Amount - amount); + + if (buyItem == null) + buyItem = item; + } + + if (cont == null || !cont.TryDropItem(buyer, buyItem, false)) + buyItem.MoveToWorld(buyer.Location, buyer.Map); + + break; + } + } + } + else if (ser.IsMobile) + { + Mobile mob = World.FindMobile(ser); + + if (mob == null) + continue; + + GenericBuyInfo gbi = LookupDisplayObject(mob); + + if (gbi != null) + ProcessValidPurchase(amount, gbi, buyer, cont); + } + } //foreach + + if (fullPurchase) + { + if (buyer.AccessLevel >= AccessLevel.GameMaster) + SayTo(buyer, true, "I would not presume to charge thee anything. Here are the goods you requested."); + else if (fromBank) + SayTo(buyer, 1151638, + totalCost + .ToString()); //The total of your purchase is ~1_val~ gold, which has been drawn from your bank account. My thanks for the patronage. + else + SayTo(buyer, 1151639, + totalCost.ToString()); //The total of your purchase is ~1_val~ gold. My thanks for the patronage. + } + else + { + if (buyer.AccessLevel >= AccessLevel.GameMaster) + SayTo(buyer, true, + "I would not presume to charge thee anything. Unfortunately, I could not sell you all the goods you requested."); + else if (fromBank) + SayTo(buyer, true, + "The total of thy purchase is {0} gold, which has been withdrawn from your bank account. My thanks for the patronage. Unfortunately, I could not sell you all the goods you requested.", + totalCost); + else + SayTo(buyer, true, + "The total of thy purchase is {0} gold. My thanks for the patronage. Unfortunately, I could not sell you all the goods you requested.", + totalCost); + } + + return true; + } + + public virtual bool OnSellItems(Mobile seller, List list) + { + if (!IsActiveBuyer) + return false; + + if (!seller.CheckAlive()) + return false; + + if (!CheckVendorAccess(seller)) + { + Say(501522); // I shall not treat with scum like thee! + return false; + } + + seller.PlaySound(0x32); + + IShopSellInfo[] info = GetSellInfo(); + IBuyItemInfo[] buyInfo = GetBuyInfo(); + int GiveGold = 0; + int Sold = 0; + Container cont; + + foreach (SellItemResponse resp in list) + { + if (resp.Item.RootParent != seller || resp.Amount <= 0 || !resp.Item.IsStandardLoot() || + !resp.Item.Movable || resp.Item is Container container && container.Items.Count != 0) + continue; + + foreach (IShopSellInfo ssi in info) + if (ssi.IsSellable(resp.Item)) + { + Sold++; + break; + } + } + + if (Sold > MaxSell) + { + SayTo(seller, true, "You may only sell {0} items at a time!", MaxSell); + return false; + } + + if (Sold == 0) return true; + + foreach (SellItemResponse resp in list) + { + if (resp.Item.RootParent != seller || resp.Amount <= 0 || !resp.Item.IsStandardLoot() || + !resp.Item.Movable || resp.Item is Container container && container.Items.Count != 0) + continue; + + foreach (IShopSellInfo ssi in info) + if (ssi.IsSellable(resp.Item)) + { + int amount = resp.Amount; + + if (amount > resp.Item.Amount) + amount = resp.Item.Amount; + + if (ssi.IsResellable(resp.Item)) + { + bool found = false; + + foreach (IBuyItemInfo bii in buyInfo) + if (bii.Restock(resp.Item, amount)) + { + resp.Item.Consume(amount); + found = true; + + break; } - for ( int i = 1; i < amount; ++i ) - { - m = bii.GetEntity() as Mobile; - - if ( m != null ) - { - m.Direction = (Direction)Utility.Random( 8 ); - m.MoveToWorld( buyer.Location, buyer.Map ); - - bc = m as BaseCreature; - - if (bc != null) - { - bc.SetControlMaster(buyer); - bc.ControlOrder = OrderType.Stop; - } - } - } - } - } - - public virtual bool OnBuyItems( Mobile buyer, List list ) - { - if ( !IsActiveSeller ) - return false; - - if ( !buyer.CheckAlive() ) - return false; - - if ( !CheckVendorAccess( buyer ) ) - { - Say( 501522 ); // I shall not treat with scum like thee! - return false; - } - - UpdateBuyInfo(); - - // IBuyItemInfo[] buyInfo = this.GetBuyInfo(); - IShopSellInfo[] info = GetSellInfo(); - int totalCost = 0; - List validBuy = new List( list.Count ); - Container cont; - bool bought = false; - bool fromBank = false; - bool fullPurchase = true; - int controlSlots = buyer.FollowersMax - buyer.Followers; - - foreach ( BuyItemResponse buy in list ) - { - Serial ser = buy.Serial; - int amount = buy.Amount; - - if ( ser.IsItem ) - { - Item item = World.FindItem( ser ); - - if ( item == null ) - continue; - - GenericBuyInfo gbi = LookupDisplayObject( item ); - - if ( gbi != null ) - { - ProcessSinglePurchase( buy, gbi, validBuy, ref controlSlots, ref fullPurchase, ref totalCost ); - } - else if ( item != BuyPack && item.IsChildOf( BuyPack ) ) - { - if ( amount > item.Amount ) - amount = item.Amount; - - if ( amount <= 0 ) - continue; - - foreach ( IShopSellInfo ssi in info ) - { - if ( ssi.IsSellable( item ) ) - { - if ( ssi.IsResellable( item ) ) - { - totalCost += ssi.GetBuyPriceFor( item ) * amount; - validBuy.Add( buy ); - break; - } - } - } - } - } - else if ( ser.IsMobile ) - { - Mobile mob = World.FindMobile( ser ); - - if ( mob == null ) - continue; - - GenericBuyInfo gbi = LookupDisplayObject( mob ); - - if ( gbi != null ) - ProcessSinglePurchase( buy, gbi, validBuy, ref controlSlots, ref fullPurchase, ref totalCost ); - } - }//foreach - - if ( fullPurchase && validBuy.Count == 0 ) - SayTo( buyer, 500190 ); // Thou hast bought nothing! - else if ( validBuy.Count == 0 ) - SayTo( buyer, 500187 ); // Your order cannot be fulfilled, please try again. - - if ( validBuy.Count == 0 ) - return false; - - bought = ( buyer.AccessLevel >= AccessLevel.GameMaster ); - - cont = buyer.Backpack; - if ( !bought && cont != null ) - { - if ( cont.ConsumeTotal( typeof( Gold ), totalCost ) ) - bought = true; - else if ( totalCost < 2000 ) - SayTo( buyer, 500192 ); // Begging thy pardon, but thou canst not afford that. - } - - if ( !bought && totalCost >= 2000 ) - { - cont = buyer.FindBankNoCreate(); - if ( cont != null && cont.ConsumeTotal( typeof( Gold ), totalCost ) ) - { - bought = true; - fromBank = true; - } - else - { - SayTo( buyer, 500191 ); //Begging thy pardon, but thy bank account lacks these funds. - } - } - - if ( !bought ) - return false; - - buyer.PlaySound( 0x32 ); - - cont = buyer.Backpack; - if ( cont == null ) - cont = buyer.BankBox; - - foreach ( BuyItemResponse buy in validBuy ) - { - Serial ser = buy.Serial; - int amount = buy.Amount; - - if ( amount < 1 ) - continue; - - if ( ser.IsItem ) - { - Item item = World.FindItem( ser ); - - if ( item == null ) - continue; - - GenericBuyInfo gbi = LookupDisplayObject( item ); - - if ( gbi != null ) - { - ProcessValidPurchase( amount, gbi, buyer, cont ); - } - else - { - if ( amount > item.Amount ) - amount = item.Amount; - - foreach ( IShopSellInfo ssi in info ) - { - if ( ssi.IsSellable( item ) ) - { - if ( ssi.IsResellable( item ) ) - { - Item buyItem; - if ( amount >= item.Amount ) - { - buyItem = item; - } - else - { - buyItem = LiftItemDupe( item, item.Amount - amount ); - - if ( buyItem == null ) - buyItem = item; - } - - if ( cont == null || !cont.TryDropItem( buyer, buyItem, false ) ) - buyItem.MoveToWorld( buyer.Location, buyer.Map ); - - break; - } - } - } - } - } - else if ( ser.IsMobile ) - { - Mobile mob = World.FindMobile( ser ); - - if ( mob == null ) - continue; - - GenericBuyInfo gbi = LookupDisplayObject( mob ); - - if ( gbi != null ) - ProcessValidPurchase( amount, gbi, buyer, cont ); - } - }//foreach - - if ( fullPurchase ) - { - if ( buyer.AccessLevel >= AccessLevel.GameMaster ) - SayTo( buyer, true, "I would not presume to charge thee anything. Here are the goods you requested." ); - else if ( fromBank ) - SayTo(buyer, 1151638, totalCost.ToString());//The total of your purchase is ~1_val~ gold, which has been drawn from your bank account. My thanks for the patronage. - else - SayTo(buyer, 1151639, totalCost.ToString());//The total of your purchase is ~1_val~ gold. My thanks for the patronage. - } - else - { - if ( buyer.AccessLevel >= AccessLevel.GameMaster ) - SayTo( buyer, true, "I would not presume to charge thee anything. Unfortunately, I could not sell you all the goods you requested." ); - else if ( fromBank ) - SayTo( buyer, true, "The total of thy purchase is {0} gold, which has been withdrawn from your bank account. My thanks for the patronage. Unfortunately, I could not sell you all the goods you requested.", totalCost ); - else - SayTo( buyer, true, "The total of thy purchase is {0} gold. My thanks for the patronage. Unfortunately, I could not sell you all the goods you requested.", totalCost ); - } - - return true; - } - - public virtual bool CheckVendorAccess( Mobile from ) - { - GuardedRegion reg = (GuardedRegion)Region.GetRegion( typeof( GuardedRegion ) ); - - if ( reg != null && !reg.CheckVendorAccess( this, from ) ) - return false; - - if ( Region != from.Region ) - { - reg = (GuardedRegion)from.Region.GetRegion( typeof( GuardedRegion ) ); - - if ( reg != null && !reg.CheckVendorAccess( this, from ) ) - return false; - } - - return true; - } - - public virtual bool OnSellItems( Mobile seller, List list ) - { - if ( !IsActiveBuyer ) - return false; - - if ( !seller.CheckAlive() ) - return false; - - if ( !CheckVendorAccess( seller ) ) - { - Say( 501522 ); // I shall not treat with scum like thee! - return false; - } - - seller.PlaySound( 0x32 ); - - IShopSellInfo[] info = GetSellInfo(); - IBuyItemInfo[] buyInfo = GetBuyInfo(); - int GiveGold = 0; - int Sold = 0; - Container cont; - - foreach ( SellItemResponse resp in list ) - { - if ( resp.Item.RootParent != seller || resp.Amount <= 0 || !resp.Item.IsStandardLoot() || !resp.Item.Movable || ( resp.Item is Container container && container.Items.Count != 0 ) ) - continue; - - foreach ( IShopSellInfo ssi in info ) - { - if ( ssi.IsSellable( resp.Item ) ) - { - Sold++; - break; - } - } - } - - if ( Sold > MaxSell ) - { - SayTo( seller, true, "You may only sell {0} items at a time!", MaxSell ); - return false; - } - if ( Sold == 0 ) - { - return true; - } - - foreach ( SellItemResponse resp in list ) - { - if ( resp.Item.RootParent != seller || resp.Amount <= 0 || !resp.Item.IsStandardLoot() || !resp.Item.Movable || ( resp.Item is Container container && container.Items.Count != 0 ) ) - continue; - - foreach ( IShopSellInfo ssi in info ) - { - if ( ssi.IsSellable( resp.Item ) ) - { - int amount = resp.Amount; - - if ( amount > resp.Item.Amount ) - amount = resp.Item.Amount; - - if ( ssi.IsResellable( resp.Item ) ) - { - bool found = false; - - foreach ( IBuyItemInfo bii in buyInfo ) - { - if ( bii.Restock( resp.Item, amount ) ) - { - resp.Item.Consume( amount ); - found = true; - - break; - } - } - - if ( !found ) - { - cont = BuyPack; - - if ( amount < resp.Item.Amount ) - { - Item item = LiftItemDupe( resp.Item, resp.Item.Amount - amount ); - - if ( item != null ) - { - item.SetLastMoved(); - cont.DropItem( item ); - } - else - { - resp.Item.SetLastMoved(); - cont.DropItem( resp.Item ); - } - } - else - { - resp.Item.SetLastMoved(); - cont.DropItem( resp.Item ); - } - } - } - else - { - if ( amount < resp.Item.Amount ) - resp.Item.Amount -= amount; - else - resp.Item.Delete(); - } - - GiveGold += ssi.GetSellPriceFor( resp.Item ) * amount; - break; - } - } - } - - if ( GiveGold > 0 ) - { - while ( GiveGold > 60000 ) - { - seller.AddToBackpack( new Gold( 60000 ) ); - GiveGold -= 60000; - } - - seller.AddToBackpack( new Gold( GiveGold ) ); - - seller.PlaySound( 0x0037 );//Gold dropping sound - - if ( SupportsBulkOrders( seller ) ) - { - Item bulkOrder = CreateBulkOrder( seller, false ); - - if ( bulkOrder is LargeBOD largeBod ) - seller.SendGump( new LargeBODAcceptGump( seller, largeBod ) ); - else if ( bulkOrder is SmallBOD smallBod ) - seller.SendGump( new SmallBODAcceptGump( seller, smallBod ) ); - } - } - //no cliloc for this? - //SayTo( seller, true, "Thank you! I bought {0} item{1}. Here is your {2}gp.", Sold, (Sold > 1 ? "s" : ""), GiveGold ); - - return true; - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int)1 ); // version - - List sbInfos = SBInfos; - - for ( int i = 0; sbInfos != null && i < sbInfos.Count; ++i ) - { - SBInfo sbInfo = sbInfos[i]; - List buyInfo = sbInfo.BuyInfo; - - for ( int j = 0; buyInfo != null && j < buyInfo.Count; ++j ) - { - GenericBuyInfo gbi = buyInfo[j]; - - int maxAmount = gbi.MaxAmount; - int doubled = 0; - - switch ( maxAmount ) - { - case 40: doubled = 1; break; - case 80: doubled = 2; break; - case 160: doubled = 3; break; - case 320: doubled = 4; break; - case 640: doubled = 5; break; - case 999: doubled = 6; break; - } - - if ( doubled > 0 ) - { - writer.WriteEncodedInt( 1 + ( ( j * sbInfos.Count ) + i ) ); - writer.WriteEncodedInt( doubled ); - } - } - } - - writer.WriteEncodedInt( 0 ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - LoadSBInfo(); - - List sbInfos = SBInfos; - - switch ( version ) - { - case 1: - { - int index; - - while ( ( index = reader.ReadEncodedInt() ) > 0 ) - { - int doubled = reader.ReadEncodedInt(); - - if ( sbInfos != null ) - { - index -= 1; - int sbInfoIndex = index % sbInfos.Count; - int buyInfoIndex = index / sbInfos.Count; - - if ( sbInfoIndex >= 0 && sbInfoIndex < sbInfos.Count ) - { - SBInfo sbInfo = sbInfos[sbInfoIndex]; - List buyInfo = sbInfo.BuyInfo; - - if ( buyInfo != null && buyInfoIndex >= 0 && buyInfoIndex < buyInfo.Count ) - { - GenericBuyInfo gbi = buyInfo[buyInfoIndex]; - - int amount = 20; - - switch ( doubled ) - { - case 1: amount = 40; break; - case 2: amount = 80; break; - case 3: amount = 160; break; - case 4: amount = 320; break; - case 5: amount = 640; break; - case 6: amount = 999; break; - } - - gbi.Amount = gbi.MaxAmount = amount; - } - } - } - } - - break; - } - } - - if ( IsParagon ) - IsParagon = false; - - Timer.DelayCall( TimeSpan.Zero, CheckMorph ); - } - - public override void AddCustomContextEntries( Mobile from, List list ) - { - if ( from.Alive && IsActiveVendor ) - { - if ( SupportsBulkOrders( from ) ) - list.Add( new BulkOrderInfoEntry( from, this ) ); - - if ( IsActiveSeller ) - list.Add( new VendorBuyEntry( from, this ) ); - - if ( IsActiveBuyer ) - list.Add( new VendorSellEntry( from, this ) ); - } - - base.AddCustomContextEntries( from, list ); - } - - public virtual IShopSellInfo[] GetSellInfo() - { - return (IShopSellInfo[])m_ArmorSellInfo.ToArray( typeof( IShopSellInfo ) ); - } - - public virtual IBuyItemInfo[] GetBuyInfo() - { - return (IBuyItemInfo[])m_ArmorBuyInfo.ToArray( typeof( IBuyItemInfo ) ); - } - } + if (!found) + { + cont = BuyPack; + + if (amount < resp.Item.Amount) + { + Item item = LiftItemDupe(resp.Item, resp.Item.Amount - amount); + + if (item != null) + { + item.SetLastMoved(); + cont.DropItem(item); + } + else + { + resp.Item.SetLastMoved(); + cont.DropItem(resp.Item); + } + } + else + { + resp.Item.SetLastMoved(); + cont.DropItem(resp.Item); + } + } + } + else + { + if (amount < resp.Item.Amount) + resp.Item.Amount -= amount; + else + resp.Item.Delete(); + } + + GiveGold += ssi.GetSellPriceFor(resp.Item) * amount; + break; + } + } + + if (GiveGold > 0) + { + while (GiveGold > 60000) + { + seller.AddToBackpack(new Gold(60000)); + GiveGold -= 60000; + } + + seller.AddToBackpack(new Gold(GiveGold)); + + seller.PlaySound(0x0037); //Gold dropping sound + + if (SupportsBulkOrders(seller)) + { + Item bulkOrder = CreateBulkOrder(seller, false); + + if (bulkOrder is LargeBOD largeBod) + seller.SendGump(new LargeBODAcceptGump(seller, largeBod)); + else if (bulkOrder is SmallBOD smallBod) + seller.SendGump(new SmallBODAcceptGump(seller, smallBod)); + } + } + //no cliloc for this? + //SayTo( seller, true, "Thank you! I bought {0} item{1}. Here is your {2}gp.", Sold, (Sold > 1 ? "s" : ""), GiveGold ); + + return true; + } + + public virtual bool IsValidBulkOrder(Item item) + { + return false; + } + + public virtual Item CreateBulkOrder(Mobile from, bool fromContextMenu) + { + return null; + } + + public virtual bool SupportsBulkOrders(Mobile from) + { + return false; + } + + public virtual TimeSpan GetNextBulkOrder(Mobile from) + { + return TimeSpan.Zero; + } + + public virtual void OnSuccessfulBulkOrderReceive(Mobile from) + { + } + + public abstract void InitSBInfo(); + + protected void LoadSBInfo() + { + LastRestock = DateTime.UtcNow; + + for (int i = 0; i < m_ArmorBuyInfo.Count; ++i) + if (m_ArmorBuyInfo[i] is GenericBuyInfo buy) + buy.DeleteDisplayEntity(); + + SBInfos.Clear(); + + InitSBInfo(); + + m_ArmorBuyInfo.Clear(); + m_ArmorSellInfo.Clear(); + + for (int i = 0; i < SBInfos.Count; i++) + { + SBInfo sbInfo = SBInfos[i]; + m_ArmorBuyInfo.AddRange(sbInfo.BuyInfo); + m_ArmorSellInfo.Add(sbInfo.SellInfo); + } + } + + public virtual bool GetGender() + { + return Utility.RandomBool(); + } + + public virtual void InitBody() + { + InitStats(100, 100, 25); + + SpeechHue = Utility.RandomDyedHue(); + Hue = Utility.RandomSkinHue(); + + if (Female = GetGender()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } + } + + public virtual int GetRandomHue() + { + switch (Utility.Random(5)) + { + default: + case 0: return Utility.RandomBlueHue(); + case 1: return Utility.RandomGreenHue(); + case 2: return Utility.RandomRedHue(); + case 3: return Utility.RandomYellowHue(); + case 4: return Utility.RandomNeutralHue(); + } + } + + public virtual int GetShoeHue() + { + if (0.1 > Utility.RandomDouble()) + return 0; + + return Utility.RandomNeutralHue(); + } + + public virtual void CheckMorph() + { + if (CheckGargoyle()) + return; + + if (CheckNecromancer()) + return; + + CheckTokuno(); + } + + public virtual bool CheckTokuno() + { + if (Map != Map.Tokuno) + return false; + + NameList n; + + if (Female) + n = NameList.GetNameList("tokuno female"); + else + n = NameList.GetNameList("tokuno male"); + + if (!n.ContainsName(Name)) + TurnToTokuno(); + + return true; + } + + public virtual void TurnToTokuno() + { + if (Female) + Name = NameList.RandomName("tokuno female"); + else + Name = NameList.RandomName("tokuno male"); + } + + public virtual bool CheckGargoyle() + { + Map map = Map; + + if (map != Map.Ilshenar) + return false; + + if (!Region.IsPartOf("Gargoyle City")) + return false; + + if (Body != 0x2F6 || (Hue & 0x8000) == 0) + TurnToGargoyle(); + + return true; + } + + public virtual bool CheckNecromancer() + { + Map map = Map; + + if (map != Map.Malas) + return false; + + if (!Region.IsPartOf("Umbra")) + return false; + + if (Hue != 0x83E8) + TurnToNecromancer(); + + return true; + } + + public override void OnAfterSpawn() + { + CheckMorph(); + } + + protected override void OnMapChange(Map oldMap) + { + base.OnMapChange(oldMap); + + CheckMorph(); + + LoadSBInfo(); + } + + public virtual int GetRandomNecromancerHue() + { + switch (Utility.Random(20)) + { + case 0: return 0; + case 1: return 0x4E9; + default: return Utility.RandomList(0x485, 0x497); + } + } + + public virtual void TurnToNecromancer() + { + for (int i = 0; i < Items.Count; ++i) + { + Item item = Items[i]; + + if (item is Hair || item is Beard) + item.Hue = 0; + else if (item is BaseClothing || item is BaseWeapon || item is BaseArmor || item is BaseTool) + item.Hue = GetRandomNecromancerHue(); + } + + HairHue = 0; + FacialHairHue = 0; + + Hue = 0x83E8; + } + + public virtual void TurnToGargoyle() + { + for (int i = 0; i < Items.Count; ++i) + { + Item item = Items[i]; + + if (item is BaseClothing || item is Hair || item is Beard) + item.Delete(); + } + + HairItemID = 0; + FacialHairItemID = 0; + + Body = 0x2F6; + Hue = Utility.RandomBrightHue() | 0x8000; + Name = NameList.RandomName("gargoyle vendor"); + + CapitalizeTitle(); + } + + public virtual void CapitalizeTitle() + { + string title = Title; + + if (title == null) + return; + + string[] split = title.Split(' '); + + for (int i = 0; i < split.Length; ++i) + { + if (Insensitive.Equals(split[i], "the")) + continue; + + if (split[i].Length > 1) + split[i] = char.ToUpper(split[i][0]) + split[i].Substring(1); + else if (split[i].Length > 0) + split[i] = char.ToUpper(split[i][0]).ToString(); + } + + Title = string.Join(" ", split); + } + + public virtual int GetHairHue() + { + return Utility.RandomHairHue(); + } + + public virtual void InitOutfit() + { + switch (Utility.Random(3)) + { + case 0: + AddItem(new FancyShirt(GetRandomHue())); + break; + case 1: + AddItem(new Doublet(GetRandomHue())); + break; + case 2: + AddItem(new Shirt(GetRandomHue())); + break; + } + + switch (ShoeType) + { + case VendorShoeType.Shoes: + AddItem(new Shoes(GetShoeHue())); + break; + case VendorShoeType.Boots: + AddItem(new Boots(GetShoeHue())); + break; + case VendorShoeType.Sandals: + AddItem(new Sandals(GetShoeHue())); + break; + case VendorShoeType.ThighBoots: + AddItem(new ThighBoots(GetShoeHue())); + break; + } + + int hairHue = GetHairHue(); + + Utility.AssignRandomHair(this, hairHue); + Utility.AssignRandomFacialHair(this, hairHue); + + if (Female) + switch (Utility.Random(6)) + { + case 0: + AddItem(new ShortPants(GetRandomHue())); + break; + case 1: + case 2: + AddItem(new Kilt(GetRandomHue())); + break; + case 3: + case 4: + case 5: + AddItem(new Skirt(GetRandomHue())); + break; + } + else + switch (Utility.Random(2)) + { + case 0: + AddItem(new LongPants(GetRandomHue())); + break; + case 1: + AddItem(new ShortPants(GetRandomHue())); + break; + } + + PackGold(100, 200); + } + + public virtual void VendorBuy(Mobile from) + { + if (!IsActiveSeller) + return; + + if (!from.CheckAlive()) + return; + + if (!CheckVendorAccess(from)) + { + Say(501522); // I shall not treat with scum like thee! + return; + } + + if (DateTime.UtcNow - LastRestock > RestockDelay) + Restock(); + + UpdateBuyInfo(); + + int count = 0; + List list; + IBuyItemInfo[] buyInfo = GetBuyInfo(); + IShopSellInfo[] sellInfo = GetSellInfo(); + + list = new List(buyInfo.Length); + Container cont = BuyPack; + + List opls = null; + + for (int idx = 0; idx < buyInfo.Length; idx++) + { + IBuyItemInfo buyItem = buyInfo[idx]; + + if (buyItem.Amount <= 0 || list.Count >= 250) + continue; + + // NOTE: Only GBI supported; if you use another implementation of IBuyItemInfo, this will crash + GenericBuyInfo gbi = (GenericBuyInfo)buyItem; + IEntity disp = gbi.GetDisplayEntity(); + + list.Add(new BuyItemState(buyItem.Name, cont.Serial, disp?.Serial ?? (Serial)0x7FC0FFEE, buyItem.Price, + buyItem.Amount, buyItem.ItemID, buyItem.Hue)); + count++; + + if (opls == null) opls = new List(); + + if (disp is Item item) + opls.Add(item.PropertyList); + else if (disp is Mobile mobile) opls.Add(mobile.PropertyList); + } + + List playerItems = cont.Items; + + for (int i = playerItems.Count - 1; i >= 0; --i) + { + if (i >= playerItems.Count) + continue; + + Item item = playerItems[i]; + + if (item.LastMoved + InventoryDecayTime <= DateTime.UtcNow) + item.Delete(); + } + + for (int i = 0; i < playerItems.Count; ++i) + { + Item item = playerItems[i]; + + int price = 0; + string name = null; + + foreach (IShopSellInfo ssi in sellInfo) + if (ssi.IsSellable(item)) + { + price = ssi.GetBuyPriceFor(item); + name = ssi.GetNameFor(item); + break; + } + + if (name != null && list.Count < 250) + { + list.Add(new BuyItemState(name, cont.Serial, item.Serial, price, item.Amount, item.ItemID, item.Hue)); + count++; + + if (opls == null) opls = new List(); + + opls.Add(item.PropertyList); + } + } + + //one (not all) of the packets uses a byte to describe number of items in the list. Osi = dumb. + //if ( list.Count > 255 ) + // Console.WriteLine( "Vendor Warning: Vendor {0} has more than 255 buy items, may cause client errors!", this ); + + if (list.Count > 0) + { + list.Sort(new BuyItemStateComparer()); + + SendPacksTo(from); + + NetState ns = from.NetState; + + if (ns == null) + return; + + if (ns.ContainerGridLines) + from.Send(new VendorBuyContent6017(list)); + else + from.Send(new VendorBuyContent(list)); + + from.Send(new VendorBuyList(this, list)); + + if (ns.HighSeas) + from.Send(new DisplayBuyListHS(this)); + else + from.Send(new DisplayBuyList(this)); + + from.Send(new MobileStatusExtended(from)); //make sure their gold amount is sent + + if (opls != null) + for (int i = 0; i < opls.Count; ++i) + from.Send(opls[i]); + + SayTo(from, 500186); // Greetings. Have a look around. + } + } + + public virtual void SendPacksTo(Mobile from) + { + Item pack = FindItemOnLayer(Layer.ShopBuy); + + if (pack == null) + { + pack = new Backpack(); + pack.Layer = Layer.ShopBuy; + pack.Movable = false; + pack.Visible = false; + AddItem(pack); + } + + from.Send(new EquipUpdate(pack)); + + pack = FindItemOnLayer(Layer.ShopSell); + + if (pack != null) + from.Send(new EquipUpdate(pack)); + + pack = FindItemOnLayer(Layer.ShopResale); + + if (pack == null) + { + pack = new Backpack(); + pack.Layer = Layer.ShopResale; + pack.Movable = false; + pack.Visible = false; + AddItem(pack); + } + + from.Send(new EquipUpdate(pack)); + } + + public virtual void VendorSell(Mobile from) + { + if (!IsActiveBuyer) + return; + + if (!from.CheckAlive()) + return; + + if (!CheckVendorAccess(from)) + { + Say(501522); // I shall not treat with scum like thee! + return; + } + + Container pack = from.Backpack; + + if (pack != null) + { + IShopSellInfo[] info = GetSellInfo(); + + Dictionary table = new Dictionary(); + + foreach (IShopSellInfo ssi in info) + { + Item[] items = pack.FindItemsByType(ssi.Types); + + foreach (Item item in items) + { + if (item is Container container && container.Items.Count != 0) + continue; + + if (item.IsStandardLoot() && item.Movable && ssi.IsSellable(item)) + table[item] = new SellItemState(item, ssi.GetSellPriceFor(item), ssi.GetNameFor(item)); + } + } + + if (table.Count > 0) + { + SendPacksTo(from); + + from.Send(new VendorSellList(this, table.Values)); + } + else + { + Say(true, "You have nothing I would be interested in."); + } + } + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + /* TODO: Thou art giving me? and fame/karma for gold gifts */ + + SmallBOD smallBod = dropped as SmallBOD; + LargeBOD largeBod = dropped as LargeBOD; + + if (!(smallBod != null || largeBod != null)) + return base.OnDragDrop(from, dropped); + + PlayerMobile pm = from as PlayerMobile; + + if (Core.ML && pm?.NextBODTurnInTime > DateTime.UtcNow) + { + SayTo(from, 1079976); // You'll have to wait a few seconds while I inspect the last order. + return false; + } + + if (!IsValidBulkOrder(dropped)) + { + SayTo(from, 1045130); // That order is for some other shopkeeper. + return false; + } + + if (smallBod?.Complete == false || largeBod?.Complete == false) + { + SayTo(from, 1045131); // You have not completed the order yet. + return false; + } + + Item reward; + int gold, fame; + + if (smallBod != null) + smallBod.GetRewards(out reward, out gold, out fame); + else + largeBod.GetRewards(out reward, out gold, out fame); + + from.SendSound(0x3D); + + SayTo(from, 1045132); // Thank you so much! Here is a reward for your effort. + + if (reward != null) + from.AddToBackpack(reward); + + if (gold > 1000) + from.AddToBackpack(new BankCheck(gold)); + else if (gold > 0) + from.AddToBackpack(new Gold(gold)); + + Titles.AwardFame(from, fame, true); + + OnSuccessfulBulkOrderReceive(from); + + if (Core.ML && pm != null) + pm.NextBODTurnInTime = DateTime.UtcNow + TimeSpan.FromSeconds(10.0); + + dropped.Delete(); + return true; + } + + private GenericBuyInfo LookupDisplayObject(object obj) + { + IBuyItemInfo[] buyInfo = GetBuyInfo(); + + for (int i = 0; i < buyInfo.Length; ++i) + { + GenericBuyInfo gbi = (GenericBuyInfo)buyInfo[i]; + + if (gbi.GetDisplayEntity() == obj) + return gbi; + } + + return null; + } + + private void ProcessSinglePurchase(BuyItemResponse buy, IBuyItemInfo bii, List validBuy, + ref int controlSlots, ref bool fullPurchase, ref int totalCost) + { + int amount = buy.Amount; + + if (amount > bii.Amount) + amount = bii.Amount; + + if (amount <= 0) + return; + + int slots = bii.ControlSlots * amount; + + if (controlSlots >= slots) + { + controlSlots -= slots; + } + else + { + fullPurchase = false; + return; + } + + totalCost += bii.Price * amount; + validBuy.Add(buy); + } + + private void ProcessValidPurchase(int amount, IBuyItemInfo bii, Mobile buyer, Container cont) + { + if (amount > bii.Amount) + amount = bii.Amount; + + if (amount < 1) + return; + + bii.Amount -= amount; + + IEntity o = bii.GetEntity(); + + if (o is Item item) + { + if (item.Stackable) + { + item.Amount = amount; + + if (cont == null || !cont.TryDropItem(buyer, item, false)) + item.MoveToWorld(buyer.Location, buyer.Map); + } + else + { + item.Amount = 1; + + if (cont == null || !cont.TryDropItem(buyer, item, false)) + item.MoveToWorld(buyer.Location, buyer.Map); + + for (int i = 1; i < amount; i++) + { + item = bii.GetEntity() as Item; + + if (item != null) + { + item.Amount = 1; + + if (cont == null || !cont.TryDropItem(buyer, item, false)) + item.MoveToWorld(buyer.Location, buyer.Map); + } + } + } + } + else if (o is Mobile m) + { + m.Direction = (Direction)Utility.Random(8); + m.MoveToWorld(buyer.Location, buyer.Map); + m.PlaySound(m.GetIdleSound()); + + if (m is BaseCreature bc) + { + bc.SetControlMaster(buyer); + bc.ControlOrder = OrderType.Stop; + } + + for (int i = 1; i < amount; ++i) + { + m = bii.GetEntity() as Mobile; + + if (m != null) + { + m.Direction = (Direction)Utility.Random(8); + m.MoveToWorld(buyer.Location, buyer.Map); + + bc = m as BaseCreature; + + if (bc != null) + { + bc.SetControlMaster(buyer); + bc.ControlOrder = OrderType.Stop; + } + } + } + } + } + + public virtual bool CheckVendorAccess(Mobile from) + { + GuardedRegion reg = (GuardedRegion)Region.GetRegion(typeof(GuardedRegion)); + + if (reg != null && !reg.CheckVendorAccess(this, from)) + return false; + + if (Region != from.Region) + { + reg = (GuardedRegion)from.Region.GetRegion(typeof(GuardedRegion)); + + if (reg != null && !reg.CheckVendorAccess(this, from)) + return false; + } + + return true; + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + List sbInfos = SBInfos; + + for (int i = 0; sbInfos != null && i < sbInfos.Count; ++i) + { + SBInfo sbInfo = sbInfos[i]; + List buyInfo = sbInfo.BuyInfo; + + for (int j = 0; buyInfo != null && j < buyInfo.Count; ++j) + { + GenericBuyInfo gbi = buyInfo[j]; + + int maxAmount = gbi.MaxAmount; + int doubled = 0; + + switch (maxAmount) + { + case 40: + doubled = 1; + break; + case 80: + doubled = 2; + break; + case 160: + doubled = 3; + break; + case 320: + doubled = 4; + break; + case 640: + doubled = 5; + break; + case 999: + doubled = 6; + break; + } + + if (doubled > 0) + { + writer.WriteEncodedInt(1 + j * sbInfos.Count + i); + writer.WriteEncodedInt(doubled); + } + } + } + + writer.WriteEncodedInt(0); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + LoadSBInfo(); + + List sbInfos = SBInfos; + + switch (version) + { + case 1: + { + int index; + + while ((index = reader.ReadEncodedInt()) > 0) + { + int doubled = reader.ReadEncodedInt(); + + if (sbInfos != null) + { + index -= 1; + int sbInfoIndex = index % sbInfos.Count; + int buyInfoIndex = index / sbInfos.Count; + + if (sbInfoIndex >= 0 && sbInfoIndex < sbInfos.Count) + { + SBInfo sbInfo = sbInfos[sbInfoIndex]; + List buyInfo = sbInfo.BuyInfo; + + if (buyInfo != null && buyInfoIndex >= 0 && buyInfoIndex < buyInfo.Count) + { + GenericBuyInfo gbi = buyInfo[buyInfoIndex]; + + int amount = 20; + + switch (doubled) + { + case 1: + amount = 40; + break; + case 2: + amount = 80; + break; + case 3: + amount = 160; + break; + case 4: + amount = 320; + break; + case 5: + amount = 640; + break; + case 6: + amount = 999; + break; + } + + gbi.Amount = gbi.MaxAmount = amount; + } + } + } + } + + break; + } + } + + if (IsParagon) + IsParagon = false; + + Timer.DelayCall(TimeSpan.Zero, CheckMorph); + } + + public override void AddCustomContextEntries(Mobile from, List list) + { + if (from.Alive && IsActiveVendor) + { + if (SupportsBulkOrders(from)) + list.Add(new BulkOrderInfoEntry(from, this)); + + if (IsActiveSeller) + list.Add(new VendorBuyEntry(from, this)); + + if (IsActiveBuyer) + list.Add(new VendorSellEntry(from, this)); + } + + base.AddCustomContextEntries(from, list); + } + + public virtual IShopSellInfo[] GetSellInfo() + { + return (IShopSellInfo[])m_ArmorSellInfo.ToArray(typeof(IShopSellInfo)); + } + + public virtual IBuyItemInfo[] GetBuyInfo() + { + return (IBuyItemInfo[])m_ArmorBuyInfo.ToArray(typeof(IBuyItemInfo)); + } + + private class BulkOrderInfoEntry : ContextMenuEntry + { + private Mobile m_From; + private BaseVendor m_Vendor; + + public BulkOrderInfoEntry(Mobile from, BaseVendor vendor) + : base(6152) + { + m_From = from; + m_Vendor = vendor; + } + + public override void OnClick() + { + if (m_Vendor.SupportsBulkOrders(m_From)) + { + TimeSpan ts = m_Vendor.GetNextBulkOrder(m_From); + + int totalSeconds = (int)ts.TotalSeconds; + int totalHours = (totalSeconds + 3599) / 3600; + int totalMinutes = (totalSeconds + 59) / 60; + + if (Core.SE ? totalMinutes == 0 : totalHours == 0) + { + m_From.SendLocalizedMessage(1049038); // You can get an order now. + + if (Core.AOS) + { + Item bulkOrder = m_Vendor.CreateBulkOrder(m_From, true); + + if (bulkOrder is LargeBOD bod) + m_From.SendGump(new LargeBODAcceptGump(m_From, bod)); + else if (bulkOrder is SmallBOD smallBod) + m_From.SendGump(new SmallBODAcceptGump(m_From, smallBod)); + } + } + else + { + int oldSpeechHue = m_Vendor.SpeechHue; + m_Vendor.SpeechHue = 0x3B2; + + if (Core.SE) + m_Vendor.SayTo(m_From, 1072058, + totalMinutes.ToString()); // An offer may be available in about ~1_minutes~ minutes. + else + m_Vendor.SayTo(m_From, 1049039, + totalHours.ToString()); // An offer may be available in about ~1_hours~ hours. + + m_Vendor.SpeechHue = oldSpeechHue; + } + } + } + } + + #region Faction + + public virtual int GetPriceScalar() + { + Town town = Town.FromRegion(Region); + + if (town != null) + return 100 + town.Tax; + + return 100; + } + + public void UpdateBuyInfo() + { + int priceScalar = GetPriceScalar(); + + IBuyItemInfo[] buyinfo = (IBuyItemInfo[])m_ArmorBuyInfo.ToArray(typeof(IBuyItemInfo)); + + if (buyinfo != null) + foreach (IBuyItemInfo info in buyinfo) + info.PriceScalar = priceScalar; + } + + #endregion + } } namespace Server.ContextMenus { - public class VendorBuyEntry : ContextMenuEntry - { - private BaseVendor m_Vendor; + public class VendorBuyEntry : ContextMenuEntry + { + private BaseVendor m_Vendor; - public VendorBuyEntry( Mobile from, BaseVendor vendor ) - : base( 6103, 8 ) - { - m_Vendor = vendor; - Enabled = vendor.CheckVendorAccess( from ); - } + public VendorBuyEntry(Mobile from, BaseVendor vendor) + : base(6103, 8) + { + m_Vendor = vendor; + Enabled = vendor.CheckVendorAccess(from); + } - public override void OnClick() - { - m_Vendor.VendorBuy( Owner.From ); - } - } + public override void OnClick() + { + m_Vendor.VendorBuy(Owner.From); + } + } - public class VendorSellEntry : ContextMenuEntry - { - private BaseVendor m_Vendor; + public class VendorSellEntry : ContextMenuEntry + { + private BaseVendor m_Vendor; - public VendorSellEntry( Mobile from, BaseVendor vendor ) - : base( 6104, 8 ) - { - m_Vendor = vendor; - Enabled = vendor.CheckVendorAccess( from ); - } + public VendorSellEntry(Mobile from, BaseVendor vendor) + : base(6104, 8) + { + m_Vendor = vendor; + Enabled = vendor.CheckVendorAccess(from); + } - public override void OnClick() - { - m_Vendor.VendorSell( Owner.From ); - } - } + public override void OnClick() + { + m_Vendor.VendorSell(Owner.From); + } + } } namespace Server { - public interface IShopSellInfo - { - //get display name for an item - string GetNameFor( Item item ); + public interface IShopSellInfo + { + //What do we sell? + Type[] Types{ get; } - //get price for an item which the player is selling - int GetSellPriceFor( Item item ); + //get display name for an item + string GetNameFor(Item item); - //get price for an item which the player is buying - int GetBuyPriceFor( Item item ); + //get price for an item which the player is selling + int GetSellPriceFor(Item item); - //can we sell this item to this vendor? - bool IsSellable( Item item ); + //get price for an item which the player is buying + int GetBuyPriceFor(Item item); - //What do we sell? - Type[] Types { get; } + //can we sell this item to this vendor? + bool IsSellable(Item item); - //does the vendor resell this item? - bool IsResellable( Item item ); - } + //does the vendor resell this item? + bool IsResellable(Item item); + } - public interface IBuyItemInfo - { - //get a new instance of an object (we just bought it) - IEntity GetEntity(); + public interface IBuyItemInfo + { + int ControlSlots{ get; } - int ControlSlots { get; } + int PriceScalar{ get; set; } - int PriceScalar { get; set; } + //display price of the item + int Price{ get; } - //display price of the item - int Price { get; } + //display name of the item + string Name{ get; } - //display name of the item - string Name { get; } + //display hue + int Hue{ get; } - //display hue - int Hue { get; } + //display id + int ItemID{ get; } - //display id - int ItemID { get; } + //amount in stock + int Amount{ get; set; } - //amount in stock - int Amount { get; set; } + //max amount in stock + int MaxAmount{ get; } - //max amount in stock - int MaxAmount { get; } + //get a new instance of an object (we just bought it) + IEntity GetEntity(); - //Attempt to restock with item, (return true if restock successful) - bool Restock( Item item, int amount ); + //Attempt to restock with item, (return true if restock successful) + bool Restock(Item item, int amount); - //called when its time for the whole shop to restock - void OnRestock(); - } -} + //called when its time for the whole shop to restock + void OnRestock(); + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/BeverageBuy.cs b/Scripts/Mobiles/Vendors/BeverageBuy.cs index 8eaf3a92b..6b808a213 100644 --- a/Scripts/Mobiles/Vendors/BeverageBuy.cs +++ b/Scripts/Mobiles/Vendors/BeverageBuy.cs @@ -3,31 +3,33 @@ using Server.Items; namespace Server.Mobiles { - public class BeverageBuyInfo : GenericBuyInfo - { - private BeverageType m_Content; + public class BeverageBuyInfo : GenericBuyInfo + { + private BeverageType m_Content; - public override bool CanCacheDisplay => false; + public BeverageBuyInfo(Type type, BeverageType content, int price, int amount, int itemID, int hue) : this(null, + type, content, price, amount, itemID, hue) + { + } - public BeverageBuyInfo( Type type, BeverageType content, int price, int amount, int itemID, int hue ) : this( null, type, content, price, amount, itemID, hue ) - { - } + public BeverageBuyInfo(string name, Type type, BeverageType content, int price, int amount, int itemID, int hue) : + base(name, type, price, amount, itemID, hue) + { + m_Content = content; - public BeverageBuyInfo( string name, Type type, BeverageType content, int price, int amount, int itemID, int hue ) : base( name, type, price, amount, itemID, hue ) - { - m_Content = content; + if (type == typeof(Pitcher)) + Name = (1048128 + (int)content).ToString(); + else if (type == typeof(BeverageBottle)) + Name = (1042959 + (int)content).ToString(); + else if (type == typeof(Jug)) + Name = (1042965 + (int)content).ToString(); + } - if ( type == typeof( Pitcher ) ) - Name = (1048128 + (int)content).ToString(); - else if ( type == typeof( BeverageBottle ) ) - Name = (1042959 + (int)content).ToString(); - else if ( type == typeof( Jug ) ) - Name = (1042965 + (int)content).ToString(); - } + public override bool CanCacheDisplay => false; - public override IEntity GetEntity() - { - return (IEntity)Activator.CreateInstance( Type, new object[]{ m_Content } ); - } - } -} + public override IEntity GetEntity() + { + return (IEntity)Activator.CreateInstance(Type, m_Content); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/GenericBuy.cs b/Scripts/Mobiles/Vendors/GenericBuy.cs index c3b0a26d2..d064f6313 100644 --- a/Scripts/Mobiles/Vendors/GenericBuy.cs +++ b/Scripts/Mobiles/Vendors/GenericBuy.cs @@ -4,309 +4,315 @@ using Server.Items; namespace Server.Mobiles { - public class GenericBuyInfo : IBuyItemInfo - { - private class DisplayCache : Container - { - private static DisplayCache m_Cache; + public class GenericBuyInfo : IBuyItemInfo + { + private int m_Amount; + private IEntity m_DisplayEntity; + + private int m_Price; + + public GenericBuyInfo(Type type, int price, int amount, int itemID, int hue) : this(null, type, price, amount, + itemID, hue, null) + { + } + + public GenericBuyInfo(string name, Type type, int price, int amount, int itemID, int hue) : this(name, type, price, + amount, itemID, hue, null) + { + } + + public GenericBuyInfo(Type type, int price, int amount, int itemID, int hue, object[] args) : this(null, type, price, + amount, itemID, hue, args) + { + } + + public GenericBuyInfo(string name, Type type, int price, int amount, int itemID, int hue, object[] args) + { + Type = type; + m_Price = price; + MaxAmount = m_Amount = amount; + ItemID = itemID; + Hue = hue; + Args = args; + + if (name == null) + Name = itemID < 0x4000 ? (1020000 + itemID).ToString() : (1078872 + itemID).ToString(); + else + Name = name; + } + + public virtual bool CanCacheDisplay //return ( m_Args == null || m_Args.Length == 0 ); } + => false; + + public Type Type{ get; set; } + + public int DefaultPrice{ get; private set; } + + public object[] Args{ get; set; } + + public virtual int ControlSlots => 0; + + public string Name{ get; set; } + + public int PriceScalar + { + get => DefaultPrice; + set => DefaultPrice = value; + } + + public int Price + { + get + { + if (DefaultPrice != 0) + { + if (m_Price > 5000000) + { + long price = m_Price; + + price *= DefaultPrice; + price += 50; + price /= 100; + + if (price > int.MaxValue) + price = int.MaxValue; + + return (int)price; + } + + return (m_Price * DefaultPrice + 50) / 100; + } + + return m_Price; + } + set => m_Price = value; + } + + public int ItemID{ get; set; } + + public int Hue{ get; set; } + + public int Amount + { + get => m_Amount; + set + { + if (value < 0) value = 0; + m_Amount = value; + } + } + + public int MaxAmount{ get; set; } + + //get a new instance of an object (we just bought it) + public virtual IEntity GetEntity() + { + if (Args == null || Args.Length == 0) + return (IEntity)Activator.CreateInstance(Type); + + return (IEntity)Activator.CreateInstance(Type, Args); + //return (Item)Activator.CreateInstance( m_Type ); + } + + //Attempt to restock with item, (return true if restock successful) + public bool Restock(Item item, int amount) + { + return false; + /*if ( item.GetType() == m_Type ) + { + if ( item is BaseWeapon ) + { + BaseWeapon weapon = (BaseWeapon)item; + + if ( weapon.Quality == WeaponQuality.Low || weapon.Quality == WeaponQuality.Exceptional || (int)weapon.DurabilityLevel > 0 || (int)weapon.DamageLevel > 0 || (int)weapon.AccuracyLevel > 0 ) + return false; + } + + if ( item is BaseArmor ) + { + BaseArmor armor = (BaseArmor)item; + + if ( armor.Quality == ArmorQuality.Low || armor.Quality == ArmorQuality.Exceptional || (int)armor.Durability > 0 || (int)armor.ProtectionLevel > 0 ) + return false; + } + + m_Amount += amount; + + return true; + } + else + { + return false; + }*/ + } + + public void OnRestock() + { + if (m_Amount <= 0) + { + /* + Core.ML using this vendor system is undefined behavior, so being + as it lends itself to an abusable exploit to cause ingame havok + and the stackable items are not found to be over 20 items, this is + changed until there is a better solution. + */ + + object Obj_Disp = GetDisplayEntity(); + + if (Core.ML && Obj_Disp is Item && !(Obj_Disp as Item).Stackable) + MaxAmount = Math.Min(20, MaxAmount); + else + MaxAmount = Math.Min(999, MaxAmount * 2); + } + else + { + /* NOTE: According to UO.com, the quantity is halved if the item does not reach 0 + * Here we implement differently: the quantity is halved only if less than half + * of the maximum quantity was bought. That is, if more than half is sold, then + * there's clearly a demand and we should not cut down on the stock. + */ + + int halfQuantity = MaxAmount; + + if (halfQuantity >= 999) + halfQuantity = 640; + else if (halfQuantity > 20) + halfQuantity /= 2; + + if (m_Amount >= halfQuantity) + MaxAmount = halfQuantity; + } + + m_Amount = MaxAmount; + } + + private bool IsDeleted(IEntity obj) + { + return obj.Deleted; + } + + public void DeleteDisplayEntity() + { + if (m_DisplayEntity == null) + return; + + m_DisplayEntity.Delete(); + m_DisplayEntity = null; + } + + public IEntity GetDisplayEntity() + { + if (m_DisplayEntity != null && !IsDeleted(m_DisplayEntity)) + return m_DisplayEntity; + + bool canCache = CanCacheDisplay; + + if (canCache) + m_DisplayEntity = DisplayCache.Cache.Lookup(Type); + + if (m_DisplayEntity == null || IsDeleted(m_DisplayEntity)) + m_DisplayEntity = GetEntity(); + + DisplayCache.Cache.Store(Type, m_DisplayEntity, canCache); + + return m_DisplayEntity; + } + + private class DisplayCache : Container + { + private static DisplayCache m_Cache; + private List m_Mobiles; + + private Dictionary m_Table; + + public DisplayCache() : base(0) + { + m_Table = new Dictionary(); + m_Mobiles = new List(); + } + + public DisplayCache(Serial serial) : base(serial) + { + } + + public static DisplayCache Cache + { + get + { + if (m_Cache == null || m_Cache.Deleted) + m_Cache = new DisplayCache(); + + return m_Cache; + } + } + + public IEntity Lookup(Type key) + { + m_Table.TryGetValue(key, out IEntity e); + return e; + } + + public void Store(Type key, IEntity obj, bool cache) + { + if (cache) + m_Table[key] = obj; - public static DisplayCache Cache { - get { - if ( m_Cache == null || m_Cache.Deleted ) - m_Cache = new DisplayCache(); + if (obj is Item) + AddItem((Item)obj); + else if (obj is Mobile) + m_Mobiles.Add((Mobile)obj); + } - return m_Cache; - } - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - private Dictionary m_Table; - private List m_Mobiles; + for (int i = 0; i < m_Mobiles.Count; ++i) + m_Mobiles[i].Delete(); - public DisplayCache() : base( 0 ) - { - m_Table = new Dictionary(); - m_Mobiles = new List(); - } + m_Mobiles.Clear(); - public IEntity Lookup( Type key ) - { - m_Table.TryGetValue( key, out IEntity e ); - return e; - } + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + Items[i].Delete(); - public void Store( Type key, IEntity obj, bool cache ) - { - if ( cache ) - m_Table[key] = obj; + if (m_Cache == this) + m_Cache = null; + } - if ( obj is Item ) - AddItem( (Item)obj ); - else if ( obj is Mobile ) - m_Mobiles.Add( (Mobile)obj ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public DisplayCache( Serial serial ) : base( serial ) - { - } + writer.Write(0); // version - public override void OnAfterDelete() - { - base.OnAfterDelete(); + writer.Write(m_Mobiles); + } - for ( int i = 0; i < m_Mobiles.Count; ++i ) - m_Mobiles[i].Delete(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - m_Mobiles.Clear(); + int version = reader.ReadInt(); - for ( int i = Items.Count - 1; i >= 0; --i ) - if ( i < Items.Count ) - Items[i].Delete(); + m_Mobiles = reader.ReadStrongMobileList(); - if ( m_Cache == this ) - m_Cache = null; - } + for (int i = 0; i < m_Mobiles.Count; ++i) + m_Mobiles[i].Delete(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_Mobiles.Clear(); - writer.Write( (int) 0 ); // version + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + Items[i].Delete(); - writer.Write( m_Mobiles ); - } + if (m_Cache == null) + m_Cache = this; + else + Delete(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - m_Mobiles = reader.ReadStrongMobileList(); - - for ( int i = 0; i < m_Mobiles.Count; ++i ) - m_Mobiles[i].Delete(); - - m_Mobiles.Clear(); - - for ( int i = Items.Count - 1; i >= 0; --i ) - if ( i < Items.Count ) - Items[i].Delete(); - - if ( m_Cache == null ) - m_Cache = this; - else - Delete(); - - m_Table = new Dictionary(); - } - } - - private int m_Price; - private int m_Amount; - private IEntity m_DisplayEntity; - - public virtual int ControlSlots => 0; - - public virtual bool CanCacheDisplay //return ( m_Args == null || m_Args.Length == 0 ); } - => false; - - private bool IsDeleted( IEntity obj ) - { - return obj.Deleted; - } - - public void DeleteDisplayEntity() - { - if ( m_DisplayEntity == null ) - return; - - m_DisplayEntity.Delete(); - m_DisplayEntity = null; - } - - public IEntity GetDisplayEntity() - { - if ( m_DisplayEntity != null && !IsDeleted( m_DisplayEntity ) ) - return m_DisplayEntity; - - bool canCache = CanCacheDisplay; - - if ( canCache ) - m_DisplayEntity = DisplayCache.Cache.Lookup( Type ); - - if ( m_DisplayEntity == null || IsDeleted( m_DisplayEntity ) ) - m_DisplayEntity = GetEntity(); - - DisplayCache.Cache.Store( Type, m_DisplayEntity, canCache ); - - return m_DisplayEntity; - } - - public Type Type { get; set; } - - public string Name { get; set; } - - public int DefaultPrice { get; private set; } - - public int PriceScalar - { - get => DefaultPrice; - set => DefaultPrice = value; - } - - public int Price - { - get - { - if ( DefaultPrice != 0 ) - { - if ( m_Price > 5000000 ) - { - long price = m_Price; - - price *= DefaultPrice; - price += 50; - price /= 100; - - if ( price > int.MaxValue ) - price = int.MaxValue; - - return (int)price; - } - - return ( ((m_Price * DefaultPrice) + 50) / 100 ); - } - - return m_Price; - } - set => m_Price = value; - } - - public int ItemID { get; set; } - - public int Hue { get; set; } - - public int Amount - { - get => m_Amount; - set{ if ( value < 0 ) value = 0; m_Amount = value; } - } - - public int MaxAmount { get; set; } - - public object[] Args { get; set; } - - public GenericBuyInfo( Type type, int price, int amount, int itemID, int hue ) : this( null, type, price, amount, itemID, hue, null ) - { - } - - public GenericBuyInfo( string name, Type type, int price, int amount, int itemID, int hue ) : this( name, type, price, amount, itemID, hue, null ) - { - } - - public GenericBuyInfo( Type type, int price, int amount, int itemID, int hue, object[] args ) : this( null, type, price, amount, itemID, hue, args ) - { - } - - public GenericBuyInfo( string name, Type type, int price, int amount, int itemID, int hue, object[] args ) - { - Type = type; - m_Price = price; - MaxAmount = m_Amount = amount; - ItemID = itemID; - Hue = hue; - Args = args; - - if ( name == null ) - Name = itemID < 0x4000 ? (1020000 + itemID).ToString() : (1078872 + itemID).ToString(); - else - Name = name; - } - - //get a new instance of an object (we just bought it) - public virtual IEntity GetEntity() - { - if ( Args == null || Args.Length == 0 ) - return (IEntity)Activator.CreateInstance( Type ); - - return (IEntity)Activator.CreateInstance( Type, Args ); - //return (Item)Activator.CreateInstance( m_Type ); - } - - //Attempt to restock with item, (return true if restock successful) - public bool Restock( Item item, int amount ) - { - return false; - /*if ( item.GetType() == m_Type ) - { - if ( item is BaseWeapon ) - { - BaseWeapon weapon = (BaseWeapon)item; - - if ( weapon.Quality == WeaponQuality.Low || weapon.Quality == WeaponQuality.Exceptional || (int)weapon.DurabilityLevel > 0 || (int)weapon.DamageLevel > 0 || (int)weapon.AccuracyLevel > 0 ) - return false; - } - - if ( item is BaseArmor ) - { - BaseArmor armor = (BaseArmor)item; - - if ( armor.Quality == ArmorQuality.Low || armor.Quality == ArmorQuality.Exceptional || (int)armor.Durability > 0 || (int)armor.ProtectionLevel > 0 ) - return false; - } - - m_Amount += amount; - - return true; - } - else - { - return false; - }*/ - } - - public void OnRestock() - { - if ( m_Amount <= 0 ) - { - /* - Core.ML using this vendor system is undefined behavior, so being - as it lends itself to an abusable exploit to cause ingame havok - and the stackable items are not found to be over 20 items, this is - changed until there is a better solution. - */ - - object Obj_Disp = GetDisplayEntity(); - - if ( Core.ML && Obj_Disp is Item && !( Obj_Disp as Item ).Stackable ) - { - MaxAmount = Math.Min( 20, MaxAmount ); - } - else - { - MaxAmount = Math.Min( 999, MaxAmount * 2 ); - } - } - else - { - /* NOTE: According to UO.com, the quantity is halved if the item does not reach 0 - * Here we implement differently: the quantity is halved only if less than half - * of the maximum quantity was bought. That is, if more than half is sold, then - * there's clearly a demand and we should not cut down on the stock. - */ - - int halfQuantity = MaxAmount; - - if ( halfQuantity >= 999 ) - halfQuantity = 640; - else if ( halfQuantity > 20 ) - halfQuantity /= 2; - - if ( m_Amount >= halfQuantity ) - MaxAmount = halfQuantity; - } - - m_Amount = MaxAmount; - } - } -} + m_Table = new Dictionary(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Alchemist.cs b/Scripts/Mobiles/Vendors/NPC/Alchemist.cs index a4fb14663..d14da06d3 100644 --- a/Scripts/Mobiles/Vendors/NPC/Alchemist.cs +++ b/Scripts/Mobiles/Vendors/NPC/Alchemist.cs @@ -1,51 +1,53 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Alchemist : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Alchemist : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.MagesGuild; + [Constructible] + public Alchemist() : base("the alchemist") + { + SetSkill(SkillName.Alchemy, 85.0, 100.0); + SetSkill(SkillName.TasteID, 65.0, 88.0); + } - [Constructible] - public Alchemist() : base( "the alchemist" ) - { - SetSkill( SkillName.Alchemy, 85.0, 100.0 ); - SetSkill( SkillName.TasteID, 65.0, 88.0 ); - } + public Alchemist(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBAlchemist() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.MagesGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - AddItem( new Items.Robe( Utility.RandomPinkHue() ) ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBAlchemist()); + } - public Alchemist( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new Robe(Utility.RandomPinkHue())); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/AnimalTrainer.cs b/Scripts/Mobiles/Vendors/NPC/AnimalTrainer.cs index 29c9dcb15..b4e0f3ccb 100644 --- a/Scripts/Mobiles/Vendors/NPC/AnimalTrainer.cs +++ b/Scripts/Mobiles/Vendors/NPC/AnimalTrainer.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Generic; using Server.ContextMenus; using Server.Gumps; @@ -8,464 +7,472 @@ using Server.Targeting; namespace Server.Mobiles { - public class AnimalTrainer : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class AnimalTrainer : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public AnimalTrainer() : base( "the animal trainer" ) - { - SetSkill( SkillName.AnimalLore, 64.0, 100.0 ); - SetSkill( SkillName.AnimalTaming, 90.0, 100.0 ); - SetSkill( SkillName.Veterinary, 65.0, 88.0 ); - } + [Constructible] + public AnimalTrainer() : base("the animal trainer") + { + SetSkill(SkillName.AnimalLore, 64.0, 100.0); + SetSkill(SkillName.AnimalTaming, 90.0, 100.0); + SetSkill(SkillName.Veterinary, 65.0, 88.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBAnimalTrainer() ); - } + public AnimalTrainer(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; + protected override List SBInfos => m_SBInfos; - public override int GetShoeHue() - { - return 0; - } + public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBAnimalTrainer()); + } - AddItem( Utility.RandomBool() ? (Item)new QuarterStaff() : (Item)new ShepherdsCrook() ); - } + public override int GetShoeHue() + { + return 0; + } - private class StableEntry : ContextMenuEntry - { - private AnimalTrainer m_Trainer; - private Mobile m_From; + public override void InitOutfit() + { + base.InitOutfit(); - public StableEntry( AnimalTrainer trainer, Mobile from ) : base( 6126, 12 ) - { - m_Trainer = trainer; - m_From = from; - } + AddItem(Utility.RandomBool() ? new QuarterStaff() : (Item)new ShepherdsCrook()); + } - public override void OnClick() - { - m_Trainer.BeginStable( m_From ); - } - } + public override void AddCustomContextEntries(Mobile from, List list) + { + if (from.Alive) + { + list.Add(new StableEntry(this, from)); - private class ClaimListGump : Gump - { - private AnimalTrainer m_Trainer; - private Mobile m_From; - private List m_List; + if (from.Stabled.Count > 0) + list.Add(new ClaimAllEntry(this, from)); + } - public ClaimListGump( AnimalTrainer trainer, Mobile from, List list ) : base( 50, 50 ) - { - m_Trainer = trainer; - m_From = from; - m_List = list; + base.AddCustomContextEntries(from, list); + } - from.CloseGump( typeof( ClaimListGump ) ); + public static int GetMaxStabled(Mobile from) + { + double taming = from.Skills[SkillName.AnimalTaming].Value; + double anlore = from.Skills[SkillName.AnimalLore].Value; + double vetern = from.Skills[SkillName.Veterinary].Value; + double sklsum = taming + anlore + vetern; - AddPage( 0 ); + int max; - AddBackground( 0, 0, 325, 50 + (list.Count * 20), 9250 ); - AddAlphaRegion( 5, 5, 315, 40 + (list.Count * 20) ); + if (sklsum >= 240.0) + max = 5; + else if (sklsum >= 200.0) + max = 4; + else if (sklsum >= 160.0) + max = 3; + else + max = 2; - AddHtml( 15, 15, 275, 20, "Select a pet to retrieve from the stables:", false, false ); + if (taming >= 100.0) + max += (int)((taming - 90.0) / 10); - for ( int i = 0; i < list.Count; ++i ) - { - BaseCreature pet = list[i]; + if (anlore >= 100.0) + max += (int)((anlore - 90.0) / 10); - if ( pet == null || pet.Deleted ) - continue; + if (vetern >= 100.0) + max += (int)((vetern - 90.0) / 10); - AddButton( 15, 39 + (i * 20), 10006, 10006, i + 1, GumpButtonType.Reply, 0 ); - AddHtml( 32, 35 + (i * 20), 275, 18, $"{pet.Name}", false, false ); - } - } + return max; + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - int index = info.ButtonID - 1; + private void CloseClaimList(Mobile from) + { + from.CloseGump(typeof(ClaimListGump)); + } - if ( index >= 0 && index < m_List.Count ) - m_Trainer.EndClaimList( m_From, m_List[index] ); - } - } + public void BeginClaimList(Mobile from) + { + if (Deleted || !from.CheckAlive()) + return; - private class ClaimAllEntry : ContextMenuEntry - { - private AnimalTrainer m_Trainer; - private Mobile m_From; + List list = new List(); - public ClaimAllEntry( AnimalTrainer trainer, Mobile from ) : base( 6127, 12 ) - { - m_Trainer = trainer; - m_From = from; - } + for (int i = 0; i < from.Stabled.Count; ++i) + { + BaseCreature pet = from.Stabled[i] as BaseCreature; - public override void OnClick() - { - m_Trainer.Claim( m_From ); - } - } + if (pet == null || pet.Deleted) + { + pet.IsStabled = false; + pet.StabledBy = null; + from.Stabled.RemoveAt(i); + --i; + continue; + } - public override void AddCustomContextEntries( Mobile from, List list ) - { - if ( from.Alive ) - { - list.Add( new StableEntry( this, from ) ); + list.Add(pet); + } - if ( from.Stabled.Count > 0 ) - list.Add( new ClaimAllEntry( this, from ) ); - } + if (list.Count > 0) + from.SendGump(new ClaimListGump(this, from, list)); + else + SayTo(from, 502671); // But I have no animals stabled with me at the moment! + } - base.AddCustomContextEntries( from, list ); - } + public void EndClaimList(Mobile from, BaseCreature pet) + { + if (pet == null || pet.Deleted || from.Map != Map || !from.Stabled.Contains(pet) || !from.CheckAlive()) + return; - public static int GetMaxStabled( Mobile from ) - { - double taming = from.Skills[SkillName.AnimalTaming].Value; - double anlore = from.Skills[SkillName.AnimalLore].Value; - double vetern = from.Skills[SkillName.Veterinary].Value; - double sklsum = taming + anlore + vetern; + if (!from.InRange(this, 14)) + { + from.SendLocalizedMessage(500446); // That is too far away. + return; + } - int max; + if (CanClaim(from, pet)) + { + DoClaim(from, pet); - if ( sklsum >= 240.0 ) - max = 5; - else if ( sklsum >= 200.0 ) - max = 4; - else if ( sklsum >= 160.0 ) - max = 3; - else - max = 2; + from.Stabled.Remove(pet); - if ( taming >= 100.0 ) - max += (int)((taming - 90.0) / 10); + (from as PlayerMobile)?.AutoStabled.Remove(pet); + } + else + { + SayTo(from, 1049612, pet.Name); // ~1_NAME~ remained in the stables because you have too many followers. + } + } - if ( anlore >= 100.0 ) - max += (int)((anlore - 90.0) / 10); + public void BeginStable(Mobile from) + { + if (Deleted || !from.CheckAlive()) + return; - if ( vetern >= 100.0 ) - max += (int)((vetern - 90.0) / 10); + Container bank = from.FindBankNoCreate(); - return max; - } + if ((from.Backpack == null || from.Backpack.GetAmount(typeof(Gold)) < 30) && + (bank == null || bank.GetAmount(typeof(Gold)) < 30)) + { + SayTo(from, 1042556); // Thou dost not have enough gold, not even in thy bank account. + } + else + { + /* I charge 30 gold per pet for a real week's stable time. + * I will withdraw it from thy bank account. + * Which animal wouldst thou like to stable here? + */ + from.SendLocalizedMessage(1042558); - private class StableTarget : Target - { - private AnimalTrainer m_Trainer; + from.Target = new StableTarget(this); + } + } - public StableTarget( AnimalTrainer trainer ) : base( 12, false, TargetFlags.None ) - { - m_Trainer = trainer; - } + public void EndStable(Mobile from, BaseCreature pet) + { + if (Deleted || !from.CheckAlive()) + return; - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is BaseCreature ) - m_Trainer.EndStable( from, (BaseCreature)targeted ); - else if ( targeted == from ) - m_Trainer.SayTo( from, 502672 ); // HA HA HA! Sorry, I am not an inn. - else - m_Trainer.SayTo( from, 1048053 ); // You can't stable that! - } - } - - private void CloseClaimList( Mobile from ) - { - from.CloseGump( typeof( ClaimListGump ) ); - } - - public void BeginClaimList( Mobile from ) - { - if ( Deleted || !from.CheckAlive() ) - return; - - List list = new List(); - - for ( int i = 0; i < from.Stabled.Count; ++i ) - { - BaseCreature pet = from.Stabled[i] as BaseCreature; - - if ( pet == null || pet.Deleted ) - { - pet.IsStabled = false; - pet.StabledBy = null; - from.Stabled.RemoveAt( i ); - --i; - continue; - } - - list.Add( pet ); - } - - if ( list.Count > 0 ) - from.SendGump( new ClaimListGump( this, from, list ) ); - else - SayTo( from, 502671 ); // But I have no animals stabled with me at the moment! - } - - public void EndClaimList( Mobile from, BaseCreature pet ) - { - if ( pet == null || pet.Deleted || from.Map != Map || !from.Stabled.Contains( pet ) || !from.CheckAlive() ) - return; - - if ( !from.InRange( this, 14 ) ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - return; - } - - if ( CanClaim( from, pet ) ) - { - DoClaim( from, pet ); - - from.Stabled.Remove( pet ); - - (from as PlayerMobile)?.AutoStabled.Remove( pet ); - } - else - { - SayTo( from, 1049612, pet.Name ); // ~1_NAME~ remained in the stables because you have too many followers. - } - } - - public void BeginStable( Mobile from ) - { - if ( Deleted || !from.CheckAlive() ) - return; - - Container bank = from.FindBankNoCreate(); - - if ( ( from.Backpack == null || from.Backpack.GetAmount( typeof( Gold ) ) < 30 ) && ( bank == null || bank.GetAmount( typeof( Gold ) ) < 30 ) ) - { - SayTo( from, 1042556 ); // Thou dost not have enough gold, not even in thy bank account. - } - else - { - /* I charge 30 gold per pet for a real week's stable time. - * I will withdraw it from thy bank account. - * Which animal wouldst thou like to stable here? - */ - from.SendLocalizedMessage(1042558); - - from.Target = new StableTarget( this ); - } - } - - public void EndStable( Mobile from, BaseCreature pet ) - { - if ( Deleted || !from.CheckAlive() ) - return; - - if ( pet.Body.IsHuman ) - { - SayTo( from, 502672 ); // HA HA HA! Sorry, I am not an inn. - } - else if ( !pet.Controlled ) - { - SayTo( from, 1048053 ); // You can't stable that! - } - else if ( pet.ControlMaster != from ) - { - SayTo( from, 1042562 ); // You do not own that pet! - } - else if ( pet.IsDeadPet ) - { - SayTo( from, 1049668 ); // Living pets only, please. - } - else if ( pet.Summoned ) - { - SayTo( from, 502673 ); // I can not stable summoned creatures. - } + if (pet.Body.IsHuman) + { + SayTo(from, 502672); // HA HA HA! Sorry, I am not an inn. + } + else if (!pet.Controlled) + { + SayTo(from, 1048053); // You can't stable that! + } + else if (pet.ControlMaster != from) + { + SayTo(from, 1042562); // You do not own that pet! + } + else if (pet.IsDeadPet) + { + SayTo(from, 1049668); // Living pets only, please. + } + else if (pet.Summoned) + { + SayTo(from, 502673); // I can not stable summoned creatures. + } /* else if ( pet.Allured ) { SayTo( from, 1048053 ); // You can't stable that! } */ - else if ( (pet is PackLlama || pet is PackHorse || pet is Beetle) && (pet.Backpack != null && pet.Backpack.Items.Count > 0) ) - { - SayTo( from, 1042563 ); // You need to unload your pet. - } - else if ( pet.Combatant != null && pet.InRange( pet.Combatant, 12 ) && pet.Map == pet.Combatant.Map ) - { - SayTo( from, 1042564 ); // I'm sorry. Your pet seems to be busy. - } - else if ( from.Stabled.Count >= GetMaxStabled( from ) ) - { - SayTo( from, 1042565 ); // You have too many pets in the stables! - } - else - { - Container bank = from.FindBankNoCreate(); + else if ((pet is PackLlama || pet is PackHorse || pet is Beetle) && pet.Backpack != null && + pet.Backpack.Items.Count > 0) + { + SayTo(from, 1042563); // You need to unload your pet. + } + else if (pet.Combatant != null && pet.InRange(pet.Combatant, 12) && pet.Map == pet.Combatant.Map) + { + SayTo(from, 1042564); // I'm sorry. Your pet seems to be busy. + } + else if (from.Stabled.Count >= GetMaxStabled(from)) + { + SayTo(from, 1042565); // You have too many pets in the stables! + } + else + { + Container bank = from.FindBankNoCreate(); - if ( ( from.Backpack != null && from.Backpack.ConsumeTotal( typeof( Gold ), 30 ) ) || ( bank != null && bank.ConsumeTotal( typeof( Gold ), 30 ) ) ) - { - pet.ControlTarget = null; - pet.ControlOrder = OrderType.Stay; - pet.Internalize(); + if (from.Backpack != null && from.Backpack.ConsumeTotal(typeof(Gold), 30) || + bank != null && bank.ConsumeTotal(typeof(Gold), 30)) + { + pet.ControlTarget = null; + pet.ControlOrder = OrderType.Stay; + pet.Internalize(); - pet.SetControlMaster( null ); - pet.SummonMaster = null; + pet.SetControlMaster(null); + pet.SummonMaster = null; - pet.IsStabled = true; - pet.StabledBy = from; + pet.IsStabled = true; + pet.StabledBy = from; - if ( Core.SE ) - pet.Loyalty = MaxLoyalty; // Wonderfully happy + if (Core.SE) + pet.Loyalty = MaxLoyalty; // Wonderfully happy - from.Stabled.Add( pet ); + from.Stabled.Add(pet); - SayTo( from, Core.AOS ? 1049677 : 502679 ); // [AOS: Your pet has been stabled.] Very well, thy pet is stabled. Thou mayst recover it by saying 'claim' to me. In one real world week, I shall sell it off if it is not claimed! - } - else - { - SayTo( from, 502677 ); // But thou hast not the funds in thy bank account! - } - } - } + SayTo(from, + Core.AOS + ? 1049677 + : 502679); // [AOS: Your pet has been stabled.] Very well, thy pet is stabled. Thou mayst recover it by saying 'claim' to me. In one real world week, I shall sell it off if it is not claimed! + } + else + { + SayTo(from, 502677); // But thou hast not the funds in thy bank account! + } + } + } - public void Claim( Mobile from ) - { - Claim( from, null ); - } + public void Claim(Mobile from) + { + Claim(from, null); + } - public void Claim( Mobile from, string petName ) - { - if ( Deleted || !from.CheckAlive() ) - return; + public void Claim(Mobile from, string petName) + { + if (Deleted || !from.CheckAlive()) + return; - bool claimed = false; - int stabled = 0; + bool claimed = false; + int stabled = 0; - bool claimByName = ( petName != null ); + bool claimByName = petName != null; - for ( int i = 0; i < from.Stabled.Count; ++i ) - { - BaseCreature pet = from.Stabled[i] as BaseCreature; + for (int i = 0; i < from.Stabled.Count; ++i) + { + BaseCreature pet = from.Stabled[i] as BaseCreature; - if ( pet == null || pet.Deleted ) - { - pet.IsStabled = false; - pet.StabledBy = null; - from.Stabled.RemoveAt( i ); - --i; - continue; - } + if (pet == null || pet.Deleted) + { + pet.IsStabled = false; + pet.StabledBy = null; + from.Stabled.RemoveAt(i); + --i; + continue; + } - ++stabled; + ++stabled; - if ( claimByName && !Insensitive.Equals( pet.Name, petName ) ) - continue; + if (claimByName && !Insensitive.Equals(pet.Name, petName)) + continue; - if ( CanClaim( from, pet ) ) - { - DoClaim( from, pet ); + if (CanClaim(from, pet)) + { + DoClaim(from, pet); - from.Stabled.RemoveAt( i ); + from.Stabled.RemoveAt(i); - (from as PlayerMobile)?.AutoStabled.Remove( pet ); + (from as PlayerMobile)?.AutoStabled.Remove(pet); - --i; + --i; - claimed = true; - } - else - { - SayTo( from, 1049612, pet.Name ); // ~1_NAME~ remained in the stables because you have too many followers. - } - } + claimed = true; + } + else + { + SayTo(from, 1049612, pet.Name); // ~1_NAME~ remained in the stables because you have too many followers. + } + } - if ( claimed ) - SayTo( from, 1042559 ); // Here you go... and good day to you! - else if ( stabled == 0 ) - SayTo( from, 502671 ); // But I have no animals stabled with me at the moment! - else if ( claimByName ) - BeginClaimList( from ); - } + if (claimed) + SayTo(from, 1042559); // Here you go... and good day to you! + else if (stabled == 0) + SayTo(from, 502671); // But I have no animals stabled with me at the moment! + else if (claimByName) + BeginClaimList(from); + } - public bool CanClaim( Mobile from, BaseCreature pet ) - { - return ((from.Followers + pet.ControlSlots) <= from.FollowersMax); - } + public bool CanClaim(Mobile from, BaseCreature pet) + { + return from.Followers + pet.ControlSlots <= from.FollowersMax; + } - private void DoClaim( Mobile from, BaseCreature pet ) - { - pet.SetControlMaster( from ); + private void DoClaim(Mobile from, BaseCreature pet) + { + pet.SetControlMaster(from); - if ( pet.Summoned ) - pet.SummonMaster = from; + if (pet.Summoned) + pet.SummonMaster = from; - pet.ControlTarget = from; - pet.ControlOrder = OrderType.Follow; + pet.ControlTarget = from; + pet.ControlOrder = OrderType.Follow; - pet.MoveToWorld( from.Location, from.Map ); + pet.MoveToWorld(from.Location, from.Map); - pet.IsStabled = false; - pet.StabledBy = null; + pet.IsStabled = false; + pet.StabledBy = null; - if ( Core.SE ) - pet.Loyalty = MaxLoyalty; // Wonderfully Happy - } + if (Core.SE) + pet.Loyalty = MaxLoyalty; // Wonderfully Happy + } - public override bool HandlesOnSpeech( Mobile from ) - { - return true; - } + public override bool HandlesOnSpeech(Mobile from) + { + return true; + } - public override void OnSpeech( SpeechEventArgs e ) - { - if ( !e.Handled && e.HasKeyword( 0x0008 ) ) // *stable* - { - e.Handled = true; + public override void OnSpeech(SpeechEventArgs e) + { + if (!e.Handled && e.HasKeyword(0x0008)) // *stable* + { + e.Handled = true; - CloseClaimList( e.Mobile ); - BeginStable( e.Mobile ); - } - else if ( !e.Handled && e.HasKeyword( 0x0009 ) ) // *claim* - { - e.Handled = true; + CloseClaimList(e.Mobile); + BeginStable(e.Mobile); + } + else if (!e.Handled && e.HasKeyword(0x0009)) // *claim* + { + e.Handled = true; - CloseClaimList( e.Mobile ); + CloseClaimList(e.Mobile); - int index = e.Speech.IndexOf( ' ' ); + int index = e.Speech.IndexOf(' '); - if ( index != -1 ) - Claim( e.Mobile, e.Speech.Substring( index ).Trim() ); - else - Claim( e.Mobile ); - } - else - { - base.OnSpeech( e ); - } - } + if (index != -1) + Claim(e.Mobile, e.Speech.Substring(index).Trim()); + else + Claim(e.Mobile); + } + else + { + base.OnSpeech(e); + } + } - public AnimalTrainer( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + int version = reader.ReadInt(); + } - int version = reader.ReadInt(); - } - } -} + private class StableEntry : ContextMenuEntry + { + private Mobile m_From; + private AnimalTrainer m_Trainer; + + public StableEntry(AnimalTrainer trainer, Mobile from) : base(6126, 12) + { + m_Trainer = trainer; + m_From = from; + } + + public override void OnClick() + { + m_Trainer.BeginStable(m_From); + } + } + + private class ClaimListGump : Gump + { + private Mobile m_From; + private List m_List; + private AnimalTrainer m_Trainer; + + public ClaimListGump(AnimalTrainer trainer, Mobile from, List list) : base(50, 50) + { + m_Trainer = trainer; + m_From = from; + m_List = list; + + from.CloseGump(typeof(ClaimListGump)); + + AddPage(0); + + AddBackground(0, 0, 325, 50 + list.Count * 20, 9250); + AddAlphaRegion(5, 5, 315, 40 + list.Count * 20); + + AddHtml(15, 15, 275, 20, "Select a pet to retrieve from the stables:", + false, false); + + for (int i = 0; i < list.Count; ++i) + { + BaseCreature pet = list[i]; + + if (pet == null || pet.Deleted) + continue; + + AddButton(15, 39 + i * 20, 10006, 10006, i + 1, GumpButtonType.Reply, 0); + AddHtml(32, 35 + i * 20, 275, 18, $"{pet.Name}", false, false); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int index = info.ButtonID - 1; + + if (index >= 0 && index < m_List.Count) + m_Trainer.EndClaimList(m_From, m_List[index]); + } + } + + private class ClaimAllEntry : ContextMenuEntry + { + private Mobile m_From; + private AnimalTrainer m_Trainer; + + public ClaimAllEntry(AnimalTrainer trainer, Mobile from) : base(6127, 12) + { + m_Trainer = trainer; + m_From = from; + } + + public override void OnClick() + { + m_Trainer.Claim(m_From); + } + } + + private class StableTarget : Target + { + private AnimalTrainer m_Trainer; + + public StableTarget(AnimalTrainer trainer) : base(12, false, TargetFlags.None) + { + m_Trainer = trainer; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is BaseCreature) + m_Trainer.EndStable(from, (BaseCreature)targeted); + else if (targeted == from) + m_Trainer.SayTo(from, 502672); // HA HA HA! Sorry, I am not an inn. + else + m_Trainer.SayTo(from, 1048053); // You can't stable that! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Architect.cs b/Scripts/Mobiles/Vendors/NPC/Architect.cs index 985da8934..3bd6792c9 100644 --- a/Scripts/Mobiles/Vendors/NPC/Architect.cs +++ b/Scripts/Mobiles/Vendors/NPC/Architect.cs @@ -2,42 +2,43 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Architect : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Architect : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; + [Constructible] + public Architect() : base("the architect") + { + } - [Constructible] - public Architect() : base( "the architect" ) - { - } + public Architect(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - if ( !Core.AOS ) - m_SBInfos.Add( new SBHouseDeed() ); + protected override List SBInfos => m_SBInfos; - m_SBInfos.Add( new SBArchitect() ); - } + public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; - public Architect( Serial serial ) : base( serial ) - { - } + public override void InitSBInfo() + { + if (!Core.AOS) + m_SBInfos.Add(new SBHouseDeed()); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_SBInfos.Add(new SBArchitect()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Armorer.cs b/Scripts/Mobiles/Vendors/NPC/Armorer.cs index 4da92adbf..ee539a539 100644 --- a/Scripts/Mobiles/Vendors/NPC/Armorer.cs +++ b/Scripts/Mobiles/Vendors/NPC/Armorer.cs @@ -1,91 +1,94 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Armorer : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Armorer : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Armorer() : base( "the armorer" ) - { - SetSkill( SkillName.ArmsLore, 64.0, 100.0 ); - SetSkill( SkillName.Blacksmith, 60.0, 83.0 ); - } + [Constructible] + public Armorer() : base("the armorer") + { + SetSkill(SkillName.ArmsLore, 64.0, 100.0); + SetSkill(SkillName.Blacksmith, 60.0, 83.0); + } - public override void InitSBInfo() - { - switch ( Utility.Random( 4 )) - { - case 0: - { - m_SBInfos.Add( new SBLeatherArmor() ); - m_SBInfos.Add( new SBStuddedArmor() ); - m_SBInfos.Add( new SBMetalShields() ); - m_SBInfos.Add( new SBPlateArmor() ); - m_SBInfos.Add( new SBHelmetArmor() ); - m_SBInfos.Add( new SBChainmailArmor() ); - m_SBInfos.Add( new SBRingmailArmor() ); - break; - } - case 1: - { - m_SBInfos.Add( new SBStuddedArmor() ); - m_SBInfos.Add( new SBLeatherArmor() ); - m_SBInfos.Add( new SBMetalShields() ); - m_SBInfos.Add( new SBHelmetArmor() ); - break; - } - case 2: - { - m_SBInfos.Add( new SBMetalShields() ); - m_SBInfos.Add( new SBPlateArmor() ); - m_SBInfos.Add( new SBHelmetArmor() ); - m_SBInfos.Add( new SBChainmailArmor() ); - m_SBInfos.Add( new SBRingmailArmor() ); - break; - } - case 3: - { - m_SBInfos.Add( new SBMetalShields() ); - m_SBInfos.Add( new SBHelmetArmor() ); - break; - } - } - if ( IsTokunoVendor ) - { - m_SBInfos.Add( new SBSELeatherArmor() ); - m_SBInfos.Add( new SBSEArmor() ); - } - } + public Armorer(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => VendorShoeType.Boots; + protected override List SBInfos => m_SBInfos; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => VendorShoeType.Boots; - AddItem( new Items.HalfApron( Utility.RandomYellowHue() ) ); - AddItem( new Items.Bascinet() ); - } + public override void InitSBInfo() + { + switch (Utility.Random(4)) + { + case 0: + { + m_SBInfos.Add(new SBLeatherArmor()); + m_SBInfos.Add(new SBStuddedArmor()); + m_SBInfos.Add(new SBMetalShields()); + m_SBInfos.Add(new SBPlateArmor()); + m_SBInfos.Add(new SBHelmetArmor()); + m_SBInfos.Add(new SBChainmailArmor()); + m_SBInfos.Add(new SBRingmailArmor()); + break; + } + case 1: + { + m_SBInfos.Add(new SBStuddedArmor()); + m_SBInfos.Add(new SBLeatherArmor()); + m_SBInfos.Add(new SBMetalShields()); + m_SBInfos.Add(new SBHelmetArmor()); + break; + } + case 2: + { + m_SBInfos.Add(new SBMetalShields()); + m_SBInfos.Add(new SBPlateArmor()); + m_SBInfos.Add(new SBHelmetArmor()); + m_SBInfos.Add(new SBChainmailArmor()); + m_SBInfos.Add(new SBRingmailArmor()); + break; + } + case 3: + { + m_SBInfos.Add(new SBMetalShields()); + m_SBInfos.Add(new SBHelmetArmor()); + break; + } + } - public Armorer( Serial serial ) : base( serial ) - { - } + if (IsTokunoVendor) + { + m_SBInfos.Add(new SBSELeatherArmor()); + m_SBInfos.Add(new SBSEArmor()); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitOutfit() + { + base.InitOutfit(); - writer.Write( (int) 0 ); // version - } + AddItem(new HalfApron(Utility.RandomYellowHue())); + AddItem(new Bascinet()); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Baker.cs b/Scripts/Mobiles/Vendors/NPC/Baker.cs index 48766c918..1b33fb7d2 100644 --- a/Scripts/Mobiles/Vendors/NPC/Baker.cs +++ b/Scripts/Mobiles/Vendors/NPC/Baker.cs @@ -2,39 +2,40 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Baker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Baker : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Baker() : base( "the baker" ) - { - SetSkill( SkillName.Cooking, 75.0, 98.0 ); - SetSkill( SkillName.TasteID, 36.0, 68.0 ); - } + [Constructible] + public Baker() : base("the baker") + { + SetSkill(SkillName.Cooking, 75.0, 98.0); + SetSkill(SkillName.TasteID, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBBaker() ); - } + public Baker(Serial serial) : base(serial) + { + } - public Baker( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBBaker()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Bard.cs b/Scripts/Mobiles/Vendors/NPC/Bard.cs index 627d6d870..cdc0e08b0 100644 --- a/Scripts/Mobiles/Vendors/NPC/Bard.cs +++ b/Scripts/Mobiles/Vendors/NPC/Bard.cs @@ -2,45 +2,46 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Bard : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Bard : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.BardsGuild; + [Constructible] + public Bard() : base("the bard") + { + SetSkill(SkillName.Discordance, 64.0, 100.0); + SetSkill(SkillName.Musicianship, 64.0, 100.0); + SetSkill(SkillName.Peacemaking, 65.0, 88.0); + SetSkill(SkillName.Provocation, 60.0, 83.0); + SetSkill(SkillName.Archery, 36.0, 68.0); + SetSkill(SkillName.Swords, 36.0, 68.0); + } - [Constructible] - public Bard() : base( "the bard" ) - { - SetSkill( SkillName.Discordance, 64.0, 100.0 ); - SetSkill( SkillName.Musicianship, 64.0, 100.0 ); - SetSkill( SkillName.Peacemaking, 65.0, 88.0 ); - SetSkill( SkillName.Provocation, 60.0, 83.0 ); - SetSkill( SkillName.Archery, 36.0, 68.0 ); - SetSkill( SkillName.Swords, 36.0, 68.0 ); - } + public Bard(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBBard() ); - } + protected override List SBInfos => m_SBInfos; - public Bard( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.BardsGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBBard()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Barkeeper.cs b/Scripts/Mobiles/Vendors/NPC/Barkeeper.cs index bbe7944dd..1d4c69232 100644 --- a/Scripts/Mobiles/Vendors/NPC/Barkeeper.cs +++ b/Scripts/Mobiles/Vendors/NPC/Barkeeper.cs @@ -3,46 +3,47 @@ using Server.Items; namespace Server.Mobiles { - public class Barkeeper : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Barkeeper : BaseVendor + { + private List m_SBInfos = new List(); - public override void InitSBInfo() - { - m_SBInfos.Add( new SBBarkeeper() ); - } + [Constructible] + public Barkeeper() : base("the barkeeper") + { + } - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.ThighBoots : VendorShoeType.Boots; + public Barkeeper(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new HalfApron( Utility.RandomBrightHue() ) ); - } + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.ThighBoots : VendorShoeType.Boots; - [Constructible] - public Barkeeper() : base( "the barkeeper" ) - { - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBBarkeeper()); + } - public Barkeeper( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new HalfApron(Utility.RandomBrightHue())); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Beekeeper.cs b/Scripts/Mobiles/Vendors/NPC/Beekeeper.cs index 82fb67c77..67c3158b1 100644 --- a/Scripts/Mobiles/Vendors/NPC/Beekeeper.cs +++ b/Scripts/Mobiles/Vendors/NPC/Beekeeper.cs @@ -2,39 +2,40 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Beekeeper : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Beekeeper : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Beekeeper() : base( "the beekeeper" ) - { - } + [Constructible] + public Beekeeper() : base("the beekeeper") + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBBeekeeper() ); - } + public Beekeeper(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => VendorShoeType.Boots; + protected override List SBInfos => m_SBInfos; - public Beekeeper( Serial serial ) : base( serial ) - { - } + public override VendorShoeType ShoeType => VendorShoeType.Boots; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBBeekeeper()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Blacksmith.cs b/Scripts/Mobiles/Vendors/NPC/Blacksmith.cs index 7c7caf8de..8f7af7c52 100644 --- a/Scripts/Mobiles/Vendors/NPC/Blacksmith.cs +++ b/Scripts/Mobiles/Vendors/NPC/Blacksmith.cs @@ -1,144 +1,148 @@ using System; using System.Collections.Generic; using Server.Engines.BulkOrders; +using Server.Items; namespace Server.Mobiles { - public class Blacksmith : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Blacksmith : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.BlacksmithsGuild; + [Constructible] + public Blacksmith() : base("the blacksmith") + { + SetSkill(SkillName.ArmsLore, 36.0, 68.0); + SetSkill(SkillName.Blacksmith, 65.0, 88.0); + SetSkill(SkillName.Fencing, 60.0, 83.0); + SetSkill(SkillName.Macing, 61.0, 93.0); + SetSkill(SkillName.Swords, 60.0, 83.0); + SetSkill(SkillName.Tactics, 60.0, 83.0); + SetSkill(SkillName.Parry, 61.0, 93.0); + } - [Constructible] - public Blacksmith() : base( "the blacksmith" ) - { - SetSkill( SkillName.ArmsLore, 36.0, 68.0 ); - SetSkill( SkillName.Blacksmith, 65.0, 88.0 ); - SetSkill( SkillName.Fencing, 60.0, 83.0 ); - SetSkill( SkillName.Macing, 61.0, 93.0 ); - SetSkill( SkillName.Swords, 60.0, 83.0 ); - SetSkill( SkillName.Tactics, 60.0, 83.0 ); - SetSkill( SkillName.Parry, 61.0, 93.0 ); - } + public Blacksmith(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - /*m_SBInfos.Add( new SBSmithTools() ); + protected override List SBInfos => m_SBInfos; - m_SBInfos.Add( new SBMetalShields() ); - m_SBInfos.Add( new SBWoodenShields() ); + public override NpcGuild NpcGuild => NpcGuild.BlacksmithsGuild; - m_SBInfos.Add( new SBPlateArmor() ); + public override VendorShoeType ShoeType => VendorShoeType.None; - m_SBInfos.Add( new SBHelmetArmor() ); - m_SBInfos.Add( new SBChainmailArmor() ); - m_SBInfos.Add( new SBRingmailArmor() ); - m_SBInfos.Add( new SBAxeWeapon() ); - m_SBInfos.Add( new SBPoleArmWeapon() ); - m_SBInfos.Add( new SBRangedWeapon() ); + public override void InitSBInfo() + { + /*m_SBInfos.Add( new SBSmithTools() ); - m_SBInfos.Add( new SBKnifeWeapon() ); - m_SBInfos.Add( new SBMaceWeapon() ); - m_SBInfos.Add( new SBSpearForkWeapon() ); - m_SBInfos.Add( new SBSwordWeapon() );*/ + m_SBInfos.Add( new SBMetalShields() ); + m_SBInfos.Add( new SBWoodenShields() ); - m_SBInfos.Add( new SBBlacksmith() ); - if ( IsTokunoVendor ) - { - m_SBInfos.Add( new SBSEArmor() ); - m_SBInfos.Add( new SBSEWeapons() ); - } - } + m_SBInfos.Add( new SBPlateArmor() ); - public override VendorShoeType ShoeType => VendorShoeType.None; + m_SBInfos.Add( new SBHelmetArmor() ); + m_SBInfos.Add( new SBChainmailArmor() ); + m_SBInfos.Add( new SBRingmailArmor() ); + m_SBInfos.Add( new SBAxeWeapon() ); + m_SBInfos.Add( new SBPoleArmWeapon() ); + m_SBInfos.Add( new SBRangedWeapon() ); - public override void InitOutfit() - { - base.InitOutfit(); + m_SBInfos.Add( new SBKnifeWeapon() ); + m_SBInfos.Add( new SBMaceWeapon() ); + m_SBInfos.Add( new SBSpearForkWeapon() ); + m_SBInfos.Add( new SBSwordWeapon() );*/ - Item item = ( Utility.RandomBool() ? null : new Items.RingmailChest() ); + m_SBInfos.Add(new SBBlacksmith()); + if (IsTokunoVendor) + { + m_SBInfos.Add(new SBSEArmor()); + m_SBInfos.Add(new SBSEWeapons()); + } + } - if ( item != null && !EquipItem( item ) ) - { - item.Delete(); - item = null; - } + public override void InitOutfit() + { + base.InitOutfit(); - if ( item == null ) - AddItem( new Items.FullApron() ); + Item item = Utility.RandomBool() ? null : new RingmailChest(); - AddItem( new Items.Bascinet() ); - AddItem( new Items.SmithHammer() ); - } + if (item != null && !EquipItem(item)) + { + item.Delete(); + item = null; + } - #region Bulk Orders - public override Item CreateBulkOrder( Mobile from, bool fromContextMenu ) - { - PlayerMobile pm = from as PlayerMobile; + if (item == null) + AddItem(new FullApron()); - if ( pm != null && pm.NextSmithBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble()) ) - { - double theirSkill = pm.Skills[SkillName.Blacksmith].Base; + AddItem(new Bascinet()); + AddItem(new SmithHammer()); + } - if ( theirSkill >= 70.1 ) - pm.NextSmithBulkOrder = TimeSpan.FromHours( 6.0 ); - else if ( theirSkill >= 50.1 ) - pm.NextSmithBulkOrder = TimeSpan.FromHours( 2.0 ); - else - pm.NextSmithBulkOrder = TimeSpan.FromHours( 1.0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( theirSkill >= 70.1 && ((theirSkill - 40.0) / 300.0) > Utility.RandomDouble() ) - return new LargeSmithBOD(); + writer.Write(0); // version + } - return SmallSmithBOD.CreateRandomFor( from ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return null; - } + int version = reader.ReadInt(); + } - public override bool IsValidBulkOrder( Item item ) - { - return ( item is SmallSmithBOD || item is LargeSmithBOD ); - } + #region Bulk Orders - public override bool SupportsBulkOrders( Mobile from ) - { - return ( from is PlayerMobile && from.Skills[SkillName.Blacksmith].Base > 0 ); - } + public override Item CreateBulkOrder(Mobile from, bool fromContextMenu) + { + PlayerMobile pm = from as PlayerMobile; - public override TimeSpan GetNextBulkOrder( Mobile from ) - { - if ( from is PlayerMobile ) - return ((PlayerMobile)from).NextSmithBulkOrder; + if (pm != null && pm.NextSmithBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble())) + { + double theirSkill = pm.Skills[SkillName.Blacksmith].Base; - return TimeSpan.Zero; - } + if (theirSkill >= 70.1) + pm.NextSmithBulkOrder = TimeSpan.FromHours(6.0); + else if (theirSkill >= 50.1) + pm.NextSmithBulkOrder = TimeSpan.FromHours(2.0); + else + pm.NextSmithBulkOrder = TimeSpan.FromHours(1.0); - public override void OnSuccessfulBulkOrderReceive( Mobile from ) - { - if ( Core.SE && from is PlayerMobile ) - ((PlayerMobile)from).NextSmithBulkOrder = TimeSpan.Zero; - } - #endregion + if (theirSkill >= 70.1 && (theirSkill - 40.0) / 300.0 > Utility.RandomDouble()) + return new LargeSmithBOD(); - public Blacksmith( Serial serial ) : base( serial ) - { - } + return SmallSmithBOD.CreateRandomFor(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return null; + } - writer.Write( (int) 0 ); // version - } + public override bool IsValidBulkOrder(Item item) + { + return item is SmallSmithBOD || item is LargeSmithBOD; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool SupportsBulkOrders(Mobile from) + { + return from is PlayerMobile && from.Skills[SkillName.Blacksmith].Base > 0; + } - int version = reader.ReadInt(); - } - } -} + public override TimeSpan GetNextBulkOrder(Mobile from) + { + if (from is PlayerMobile) + return ((PlayerMobile)from).NextSmithBulkOrder; + + return TimeSpan.Zero; + } + + public override void OnSuccessfulBulkOrderReceive(Mobile from) + { + if (Core.SE && from is PlayerMobile) + ((PlayerMobile)from).NextSmithBulkOrder = TimeSpan.Zero; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Bowyer.cs b/Scripts/Mobiles/Vendors/NPC/Bowyer.cs index 4ba273355..5dbda4233 100644 --- a/Scripts/Mobiles/Vendors/NPC/Bowyer.cs +++ b/Scripts/Mobiles/Vendors/NPC/Bowyer.cs @@ -1,60 +1,62 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.Bower" )] - public class Bowyer : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + [TypeAlias("Server.Mobiles.Bower")] + public class Bowyer : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Bowyer() : base( "the bowyer" ) - { - SetSkill( SkillName.Fletching, 80.0, 100.0 ); - SetSkill( SkillName.Archery, 80.0, 100.0 ); - } + [Constructible] + public Bowyer() : base("the bowyer") + { + SetSkill(SkillName.Fletching, 80.0, 100.0); + SetSkill(SkillName.Archery, 80.0, 100.0); + } - public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; + public Bowyer(Serial serial) : base(serial) + { + } - public override int GetShoeHue() - { - return 0; - } + protected override List SBInfos => m_SBInfos; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; - AddItem( new Items.Bow() ); - AddItem( new Items.LeatherGorget() ); - } + public override int GetShoeHue() + { + return 0; + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBBowyer() ); - m_SBInfos.Add( new SBRangedWeapon() ); - - if ( IsTokunoVendor ) - m_SBInfos.Add( new SBSEBowyer() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public Bowyer( Serial serial ) : base( serial ) - { - } + AddItem(new Bow()); + AddItem(new LeatherGorget()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBBowyer()); + m_SBInfos.Add(new SBRangedWeapon()); - writer.Write( (int) 0 ); // version - } + if (IsTokunoVendor) + m_SBInfos.Add(new SBSEBowyer()); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Butcher.cs b/Scripts/Mobiles/Vendors/NPC/Butcher.cs index df896d3a6..122fb9600 100644 --- a/Scripts/Mobiles/Vendors/NPC/Butcher.cs +++ b/Scripts/Mobiles/Vendors/NPC/Butcher.cs @@ -1,47 +1,49 @@ using System.Collections.Generic; +using Server.Items; -namespace Server.Mobiles -{ - public class Butcher : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class Butcher : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Butcher() : base( "the butcher" ) - { - SetSkill( SkillName.Anatomy, 45.0, 68.0 ); - } + [Constructible] + public Butcher() : base("the butcher") + { + SetSkill(SkillName.Anatomy, 45.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBButcher() ); - } + public Butcher(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.HalfApron() ); - AddItem( new Items.Cleaver() ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBButcher()); + } - public Butcher( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new HalfApron()); + AddItem(new Cleaver()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Carpenter.cs b/Scripts/Mobiles/Vendors/NPC/Carpenter.cs index ca2ce1215..b4bb08d02 100644 --- a/Scripts/Mobiles/Vendors/NPC/Carpenter.cs +++ b/Scripts/Mobiles/Vendors/NPC/Carpenter.cs @@ -1,54 +1,56 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Carpenter : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Carpenter : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; + [Constructible] + public Carpenter() : base("the carpenter") + { + SetSkill(SkillName.Carpentry, 85.0, 100.0); + SetSkill(SkillName.Lumberjacking, 60.0, 83.0); + } - [Constructible] - public Carpenter() : base( "the carpenter" ) - { - SetSkill( SkillName.Carpentry, 85.0, 100.0 ); - SetSkill( SkillName.Lumberjacking, 60.0, 83.0 ); - } + public Carpenter(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBStavesWeapon() ); - m_SBInfos.Add( new SBCarpenter() ); - m_SBInfos.Add( new SBWoodenShields() ); + protected override List SBInfos => m_SBInfos; - if ( IsTokunoVendor ) - m_SBInfos.Add( new SBSECarpenter() ); - } + public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBStavesWeapon()); + m_SBInfos.Add(new SBCarpenter()); + m_SBInfos.Add(new SBWoodenShields()); - AddItem( new Items.HalfApron() ); - } + if (IsTokunoVendor) + m_SBInfos.Add(new SBSECarpenter()); + } - public Carpenter( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new HalfApron()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Cobbler.cs b/Scripts/Mobiles/Vendors/NPC/Cobbler.cs index 3c47375a9..054887906 100644 --- a/Scripts/Mobiles/Vendors/NPC/Cobbler.cs +++ b/Scripts/Mobiles/Vendors/NPC/Cobbler.cs @@ -1,41 +1,42 @@ using System.Collections.Generic; -namespace Server.Mobiles -{ - public class Cobbler : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class Cobbler : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Cobbler() : base( "the cobbler" ) - { - SetSkill( SkillName.Tailoring, 60.0, 83.0 ); - } + [Constructible] + public Cobbler() : base("the cobbler") + { + SetSkill(SkillName.Tailoring, 60.0, 83.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBCobbler() ); - } + public Cobbler(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; + protected override List SBInfos => m_SBInfos; - public Cobbler( Serial serial ) : base( serial ) - { - } + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBCobbler()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Cook.cs b/Scripts/Mobiles/Vendors/NPC/Cook.cs index d1a555985..e2e786fa3 100644 --- a/Scripts/Mobiles/Vendors/NPC/Cook.cs +++ b/Scripts/Mobiles/Vendors/NPC/Cook.cs @@ -1,52 +1,54 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Cook : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Cook : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Cook() : base( "the cook" ) - { - SetSkill( SkillName.Cooking, 90.0, 100.0 ); - SetSkill( SkillName.TasteID, 75.0, 98.0 ); - } + [Constructible] + public Cook() : base("the cook") + { + SetSkill(SkillName.Cooking, 90.0, 100.0); + SetSkill(SkillName.TasteID, 75.0, 98.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBCook() ); + public Cook(Serial serial) : base(serial) + { + } - if ( IsTokunoVendor ) - m_SBInfos.Add( new SBSECook() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBCook()); - AddItem( new Items.HalfApron() ); - } + if (IsTokunoVendor) + m_SBInfos.Add(new SBSECook()); + } - public Cook( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new HalfApron()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/CustomHairstylist.cs b/Scripts/Mobiles/Vendors/NPC/CustomHairstylist.cs index e2323f7bd..c9f6af408 100644 --- a/Scripts/Mobiles/Vendors/NPC/CustomHairstylist.cs +++ b/Scripts/Mobiles/Vendors/NPC/CustomHairstylist.cs @@ -1,570 +1,576 @@ using System; using System.Collections.Generic; using Server.Gumps; +using Server.Items; using Server.Network; namespace Server.Mobiles { - public class CustomHairstylist : BaseVendor - { - protected override List SBInfos { get; } = new List(); - - public override bool ClickTitle => false; - - public override bool IsActiveBuyer => false; - public override bool IsActiveSeller => true; - - public override bool OnBuyItems( Mobile buyer, List list ) - { - return false; - } - - public static readonly object From = new object(); - public static readonly object Vendor = new object(); - public static readonly object Price = new object(); - - private static HairstylistBuyInfo[] m_SellList = { - new HairstylistBuyInfo( 1018357, 50000, false, typeof( ChangeHairstyleGump ), new[] - { From, Vendor, Price, false, ChangeHairstyleEntry.HairEntries } ), - new HairstylistBuyInfo( 1018358, 50000, true, typeof( ChangeHairstyleGump ), new[] - { From, Vendor, Price, true, ChangeHairstyleEntry.BeardEntries } ), - new HairstylistBuyInfo( 1018359, 50, false, typeof( ChangeHairHueGump ), new[] - { From, Vendor, Price, true, true, ChangeHairHueEntry.RegularEntries } ), - new HairstylistBuyInfo( 1018360, 500000, false, typeof( ChangeHairHueGump ), new[] - { From, Vendor, Price, true, true, ChangeHairHueEntry.BrightEntries } ), - new HairstylistBuyInfo( 1018361, 30000, false, typeof( ChangeHairHueGump ), new[] - { From, Vendor, Price, true, false, ChangeHairHueEntry.RegularEntries } ), - new HairstylistBuyInfo( 1018362, 30000, true, typeof( ChangeHairHueGump ), new[] - { From, Vendor, Price, false, true, ChangeHairHueEntry.RegularEntries } ), - new HairstylistBuyInfo( 1018363, 500000, false, typeof( ChangeHairHueGump ), new[] - { From, Vendor, Price, true, false, ChangeHairHueEntry.BrightEntries } ), - new HairstylistBuyInfo( 1018364, 500000, true, typeof( ChangeHairHueGump ), new[] - { From, Vendor, Price, false, true, ChangeHairHueEntry.BrightEntries } ) - }; - - public override void VendorBuy( Mobile from ) - { - from.SendGump( new HairstylistBuyGump( from, this, m_SellList ) ); - } - - [Constructible] - public CustomHairstylist() : base( "the hairstylist" ) - { - } - - public override int GetHairHue() - { - return Utility.RandomBrightHue(); - } - - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - - public override void InitOutfit() - { - base.InitOutfit(); - - AddItem( new Items.Robe( Utility.RandomPinkHue() ) ); - } - - public override void InitSBInfo() - { - } - - public CustomHairstylist( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class HairstylistBuyInfo - { - public int Title { get; } - - public string TitleString { get; } - - public int Price { get; } - - public bool FacialHair { get; } - - public Type GumpType { get; } - - public object[] GumpArgs { get; } - - public HairstylistBuyInfo( int title, int price, bool facialHair, Type gumpType, object[] args ) - { - Title = title; - Price = price; - FacialHair = facialHair; - GumpType = gumpType; - GumpArgs = args; - } - - public HairstylistBuyInfo( string title, int price, bool facialHair, Type gumpType, object[] args ) - { - TitleString = title; - Price = price; - FacialHair = facialHair; - GumpType = gumpType; - GumpArgs = args; - } - } - - public class HairstylistBuyGump : Gump - { - private Mobile m_From; - private Mobile m_Vendor; - private HairstylistBuyInfo[] m_SellList; - - public HairstylistBuyGump( Mobile from, Mobile vendor, HairstylistBuyInfo[] sellList ) : base( 50, 50 ) - { - m_From = from; - m_Vendor = vendor; - m_SellList = sellList; - - from.CloseGump( typeof( HairstylistBuyGump ) ); - from.CloseGump( typeof( ChangeHairHueGump ) ); - from.CloseGump( typeof( ChangeHairstyleGump ) ); - - bool isFemale = ( from.Female || from.Body.IsFemale ); - - int balance = Banker.GetBalance( from ); - int canAfford = 0; - - for ( int i = 0; i < sellList.Length; ++i ) - { - if ( balance >= sellList[i].Price && (!sellList[i].FacialHair || !isFemale) ) - ++canAfford; - } - - AddPage( 0 ); - - AddBackground( 50, 10, 450, 100 + (canAfford * 25), 2600 ); - - AddHtmlLocalized( 100, 40, 350, 20, 1018356, false, false ); // Choose your hairstyle change: - - int index = 0; - - for ( int i = 0; i < sellList.Length; ++i ) - { - if ( balance >= sellList[i].Price && (!sellList[i].FacialHair || !isFemale) ) - { - if ( sellList[i].TitleString != null ) - AddHtml( 140, 75 + (index * 25), 300, 20, sellList[i].TitleString, false, false ); - else - AddHtmlLocalized( 140, 75 + (index * 25), 300, 20, sellList[i].Title, false, false ); - - AddButton( 100, 75 + (index++ * 25), 4005, 4007, 1 + i, GumpButtonType.Reply, 0 ); - } - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int index = info.ButtonID - 1; - - if ( index >= 0 && index < m_SellList.Length ) - { - HairstylistBuyInfo buyInfo = m_SellList[index]; - - int balance = Banker.GetBalance( m_From ); - - bool isFemale = ( m_From.Female || m_From.Body.IsFemale ); - - if ( buyInfo.FacialHair && isFemale ) - { - // You cannot place facial hair on a woman! - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1010639, m_From.NetState ); - } - else if ( balance >= buyInfo.Price ) - { - try - { - object[] origArgs = buyInfo.GumpArgs; - object[] args = new object[origArgs.Length]; - - for ( int i = 0; i < args.Length; ++i ) - { - if ( origArgs[i] == CustomHairstylist.Price ) - args[i] = m_SellList[index].Price; - else if ( origArgs[i] == CustomHairstylist.From ) - args[i] = m_From; - else if ( origArgs[i] == CustomHairstylist.Vendor ) - args[i] = m_Vendor; - else - args[i] = origArgs[i]; - } - - Gump g = Activator.CreateInstance( buyInfo.GumpType, args ) as Gump; - - m_From.SendGump( g ); - } - catch - { - } - } - else - { - // You cannot afford my services for that style. - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042293, m_From.NetState ); - } - } - } - } - - public class ChangeHairHueEntry - { - public string Name { get; } - - public int[] Hues { get; } - - public ChangeHairHueEntry( string name, int[] hues ) - { - Name = name; - Hues = hues; - } - - public ChangeHairHueEntry( string name, int start, int count ) - { - Name = name; - - Hues = new int[count]; - - for ( int i = 0; i < count; ++i ) - Hues[i] = start + i; - } - - public static readonly ChangeHairHueEntry[] BrightEntries = { - new ChangeHairHueEntry( "*****", 12, 10 ), - new ChangeHairHueEntry( "*****", 32, 5 ), - new ChangeHairHueEntry( "*****", 38, 8 ), - new ChangeHairHueEntry( "*****", 54, 3 ), - new ChangeHairHueEntry( "*****", 62, 10 ), - new ChangeHairHueEntry( "*****", 81, 2 ), - new ChangeHairHueEntry( "*****", 89, 2 ), - new ChangeHairHueEntry( "*****", 1153, 2 ) - }; - - public static readonly ChangeHairHueEntry[] RegularEntries = { - new ChangeHairHueEntry( "*****", 1602, 26 ), - new ChangeHairHueEntry( "*****", 1628, 27 ), - new ChangeHairHueEntry( "*****", 1502, 32 ), - new ChangeHairHueEntry( "*****", 1302, 32 ), - new ChangeHairHueEntry( "*****", 1402, 32 ), - new ChangeHairHueEntry( "*****", 1202, 24 ), - new ChangeHairHueEntry( "*****", 2402, 29 ), - new ChangeHairHueEntry( "*****", 2213, 6 ), - new ChangeHairHueEntry( "*****", 1102, 8 ), - new ChangeHairHueEntry( "*****", 1110, 8 ), - new ChangeHairHueEntry( "*****", 1118, 16 ), - new ChangeHairHueEntry( "*****", 1134, 16 ) - }; - } - - public class ChangeHairHueGump : Gump - { - private Mobile m_From; - private Mobile m_Vendor; - private int m_Price; - private bool m_Hair; - private bool m_FacialHair; - private ChangeHairHueEntry[] m_Entries; - - public ChangeHairHueGump( Mobile from, Mobile vendor, int price, bool hair, bool facialHair, ChangeHairHueEntry[] entries ) : base( 50, 50 ) - { - m_From = from; - m_Vendor = vendor; - m_Price = price; - m_Hair = hair; - m_FacialHair = facialHair; - m_Entries = entries; - - from.CloseGump( typeof( HairstylistBuyGump ) ); - from.CloseGump( typeof( ChangeHairHueGump ) ); - from.CloseGump( typeof( ChangeHairstyleGump ) ); - - AddPage( 0 ); - - AddBackground( 100, 10, 350, 370, 2600 ); - AddBackground( 120, 54, 110, 270, 5100 ); - - AddHtmlLocalized( 155, 25, 240, 30, 1011013, false, false ); //
Hair Color Selection Menu
- - AddHtmlLocalized( 150, 330, 220, 35, 1011014, false, false ); // Dye my hair this color! - AddButton( 380, 330, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - - for ( int i = 0; i < entries.Length; ++i ) - { - ChangeHairHueEntry entry = entries[i]; - - AddLabel( 130, 59 + (i * 22), entry.Hues[0] - 1, entry.Name ); - AddButton( 207, 60 + (i * 22), 5224, 5224, 0, GumpButtonType.Page, 1 + i ); - } - - for ( int i = 0; i < entries.Length; ++i ) - { - ChangeHairHueEntry entry = entries[i]; - int[] hues = entry.Hues; - string name = entry.Name; - - AddPage( 1 + i ); - - for ( int j = 0; j < hues.Length; ++j ) - { - AddLabel( 278 + ((j / 16) * 80), 52 + ((j % 16) * 17), hues[j] - 1, name ); - AddRadio( 260 + ((j / 16) * 80), 52 + ((j % 16) * 17), 210, 211, false, (j * entries.Length) + i ); - } - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; - - if ( switches.Length > 0 ) - { - int index = switches[0] % m_Entries.Length; - int offset = switches[0] / m_Entries.Length; - - if ( index >= 0 && index < m_Entries.Length ) - { - if ( offset >= 0 && offset < m_Entries[index].Hues.Length ) - { - if ( m_Hair && m_From.HairItemID > 0 || m_FacialHair && m_From.FacialHairItemID > 0 ) - { - if ( !Banker.Withdraw( m_From, m_Price ) ) - { - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042293, m_From.NetState ); // You cannot afford my services for that style. - return; - } - - int hue = m_Entries[index].Hues[offset]; - - if ( m_Hair ) - m_From.HairHue = hue; - - if ( m_FacialHair ) - m_From.FacialHairHue = hue; - } - else - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502623, m_From.NetState ); // You have no hair to dye and you cannot use this. - } - } - } - else - { - // You decide not to change your hairstyle. - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1013009, m_From.NetState ); - } - } - else - { - // You decide not to change your hairstyle. - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1013009, m_From.NetState ); - } - } - } - - public class ChangeHairstyleEntry - { - public int ItemID { get; } - - public int GumpID { get; } - - public int X { get; } - - public int Y { get; } - - public ChangeHairstyleEntry( int gumpID, int x, int y, int itemID ) - { - GumpID = gumpID; - X = x; - Y = y; - ItemID = itemID; - } - - public static readonly ChangeHairstyleEntry[] HairEntries = { - new ChangeHairstyleEntry( 50700, 70 - 137, 20 - 60, 0x203B ), - new ChangeHairstyleEntry( 60710, 193 - 260, 18 - 60, 0x2045 ), - new ChangeHairstyleEntry( 50703, 316 - 383, 25 - 60, 0x2044 ), - new ChangeHairstyleEntry( 60708, 70 - 137, 75 - 125, 0x203C ), - new ChangeHairstyleEntry( 60900, 193 - 260, 85 - 125, 0x2047 ), - new ChangeHairstyleEntry( 60713, 320 - 383, 85 - 125, 0x204A ), - new ChangeHairstyleEntry( 60702, 70 - 137, 140 - 190, 0x203D ), - new ChangeHairstyleEntry( 60707, 193 - 260, 140 - 190, 0x2049 ), - new ChangeHairstyleEntry( 60901, 315 - 383, 150 - 190, 0x2048 ), - new ChangeHairstyleEntry( 0, 0, 0, 0 ) - }; - - public static readonly ChangeHairstyleEntry[] BeardEntries = { - new ChangeHairstyleEntry( 50800, 120 - 187, 30 - 80, 0x2040 ), - new ChangeHairstyleEntry( 50904, 243 - 310, 33 - 80, 0x204B ), - new ChangeHairstyleEntry( 50906, 120 - 187, 100 - 150, 0x204D ), - new ChangeHairstyleEntry( 50801, 243 - 310, 95 - 150, 0x203E ), - new ChangeHairstyleEntry( 50802, 120 - 187, 173 - 220, 0x203F ), - new ChangeHairstyleEntry( 50905, 243 - 310, 165 - 220, 0x204C ), - new ChangeHairstyleEntry( 50808, 120 - 187, 242 - 290, 0x2041 ), - new ChangeHairstyleEntry( 0, 0, 0, 0 ) - }; - } - - public class ChangeHairstyleGump : Gump - { - private Mobile m_From; - private Mobile m_Vendor; - private int m_Price; - private bool m_FacialHair; - private ChangeHairstyleEntry[] m_Entries; - - public ChangeHairstyleGump( Mobile from, Mobile vendor, int price, bool facialHair, ChangeHairstyleEntry[] entries ) : base( 50, 50 ) - { - m_From = from; - m_Vendor = vendor; - m_Price = price; - m_FacialHair = facialHair; - m_Entries = entries; - - from.CloseGump( typeof( HairstylistBuyGump ) ); - from.CloseGump( typeof( ChangeHairHueGump ) ); - from.CloseGump( typeof( ChangeHairstyleGump ) ); - - int tableWidth = ( m_FacialHair ? 2 : 3 ); - int tableHeight = ( (entries.Length + tableWidth - ( m_FacialHair ? 1 : 2 )) / tableWidth ); - int offsetWidth = 123; - int offsetHeight = ( m_FacialHair ? 70 : 65 ); - - AddPage( 0 ); - - AddBackground( 0, 0, 81 + (tableWidth * offsetWidth), 105 + (tableHeight * offsetHeight), 2600 ); - - AddButton( 45, 45 + (tableHeight * offsetHeight), 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 77, 45 + (tableHeight * offsetHeight), 90, 35, 1006044, false, false ); // Ok - - AddButton( 81 + (tableWidth * offsetWidth) - 180, 45 + (tableHeight * offsetHeight), 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 81 + (tableWidth * offsetWidth) - 148, 45 + (tableHeight * offsetHeight), 90, 35, 1006045, false, false ); // Cancel - - if ( !facialHair ) - AddHtmlLocalized( 50, 15, 350, 20, 1018353, false, false ); //
New Hairstyle
- else - AddHtmlLocalized( 55, 15, 200, 20, 1018354, false, false ); //
New Beard
- - for ( int i = 0; i < entries.Length; ++i ) - { - int xTable = i % tableWidth; - int yTable = i / tableWidth; - - if ( entries[i].GumpID != 0 ) - { - AddRadio( 40 + (xTable * offsetWidth), 70 + (yTable * offsetHeight), 208, 209, false, i ); - AddBackground( 87 + (xTable * offsetWidth), 50 + (yTable * offsetHeight), 50, 50, 2620 ); - AddImage( 87 + (xTable * offsetWidth) + entries[i].X, 50 + (yTable * offsetHeight) + entries[i].Y, entries[i].GumpID ); - } - else if ( !facialHair ) - { - AddRadio( 40 + ((xTable + 1) * offsetWidth), 240, 208, 209, false, i ); - AddHtmlLocalized( 60 + ((xTable + 1) * offsetWidth), 240, 85, 35, 1011064, false, false ); // Bald - } - else - { - AddRadio( 40 + (xTable * offsetWidth), 70 + (yTable * offsetHeight), 208, 209, false, i ); - AddHtmlLocalized( 60 + (xTable * offsetWidth), 70 + (yTable * offsetHeight), 85, 35, 1011064, false, false ); // Bald - } - } - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( m_FacialHair && (m_From.Female || m_From.Body.IsFemale) ) - return; - - if ( m_From.Race == Race.Elf ) - { - m_From.SendMessage( "This isn't implemented for elves yet. Sorry!" ); - return; - } - - if ( info.ButtonID == 1 ) - { - int[] switches = info.Switches; - - if ( switches.Length > 0 ) - { - int index = switches[0]; - - if ( index >= 0 && index < m_Entries.Length ) - { - ChangeHairstyleEntry entry = m_Entries[index]; - - (m_From as PlayerMobile)?.SetHairMods( -1, -1 ); - - int hairID = m_From.HairItemID; - int facialHairID = m_From.FacialHairItemID; - - if ( entry.ItemID == 0 ) - { - if ( m_FacialHair ? (facialHairID == 0) : (hairID == 0) ) - return; - - if ( Banker.Withdraw( m_From, m_Price ) ) - { - if ( m_FacialHair ) - m_From.FacialHairItemID = 0; - else - m_From.HairItemID = 0; - } - else - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042293, m_From.NetState ); // You cannot afford my services for that style. - } - else - { - if ( m_FacialHair ) - { - if ( facialHairID > 0 && facialHairID == entry.ItemID ) - return; - } - else - { - if ( hairID > 0 && hairID == entry.ItemID ) - return; - } - - if ( Banker.Withdraw( m_From, m_Price ) ) - { - if ( m_FacialHair ) - m_From.FacialHairItemID = entry.ItemID; - else - m_From.HairItemID = entry.ItemID; - } - else - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042293, m_From.NetState ); // You cannot afford my services for that style. - } - } - } - else - { - // You decide not to change your hairstyle. - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1013009, m_From.NetState ); - } - } - else - { - // You decide not to change your hairstyle. - m_Vendor.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1013009, m_From.NetState ); - } - } - } -} + public class CustomHairstylist : BaseVendor + { + public static readonly object From = new object(); + public static readonly object Vendor = new object(); + public static readonly object Price = new object(); + + private static HairstylistBuyInfo[] m_SellList = + { + new HairstylistBuyInfo(1018357, 50000, false, typeof(ChangeHairstyleGump), new[] + { From, Vendor, Price, false, ChangeHairstyleEntry.HairEntries }), + new HairstylistBuyInfo(1018358, 50000, true, typeof(ChangeHairstyleGump), new[] + { From, Vendor, Price, true, ChangeHairstyleEntry.BeardEntries }), + new HairstylistBuyInfo(1018359, 50, false, typeof(ChangeHairHueGump), new[] + { From, Vendor, Price, true, true, ChangeHairHueEntry.RegularEntries }), + new HairstylistBuyInfo(1018360, 500000, false, typeof(ChangeHairHueGump), new[] + { From, Vendor, Price, true, true, ChangeHairHueEntry.BrightEntries }), + new HairstylistBuyInfo(1018361, 30000, false, typeof(ChangeHairHueGump), new[] + { From, Vendor, Price, true, false, ChangeHairHueEntry.RegularEntries }), + new HairstylistBuyInfo(1018362, 30000, true, typeof(ChangeHairHueGump), new[] + { From, Vendor, Price, false, true, ChangeHairHueEntry.RegularEntries }), + new HairstylistBuyInfo(1018363, 500000, false, typeof(ChangeHairHueGump), new[] + { From, Vendor, Price, true, false, ChangeHairHueEntry.BrightEntries }), + new HairstylistBuyInfo(1018364, 500000, true, typeof(ChangeHairHueGump), new[] + { From, Vendor, Price, false, true, ChangeHairHueEntry.BrightEntries }) + }; + + [Constructible] + public CustomHairstylist() : base("the hairstylist") + { + } + + public CustomHairstylist(Serial serial) : base(serial) + { + } + + protected override List SBInfos{ get; } = new List(); + + public override bool ClickTitle => false; + + public override bool IsActiveBuyer => false; + public override bool IsActiveSeller => true; + + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + + public override bool OnBuyItems(Mobile buyer, List list) + { + return false; + } + + public override void VendorBuy(Mobile from) + { + from.SendGump(new HairstylistBuyGump(from, this, m_SellList)); + } + + public override int GetHairHue() + { + return Utility.RandomBrightHue(); + } + + public override void InitOutfit() + { + base.InitOutfit(); + + AddItem(new Robe(Utility.RandomPinkHue())); + } + + public override void InitSBInfo() + { + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class HairstylistBuyInfo + { + public HairstylistBuyInfo(int title, int price, bool facialHair, Type gumpType, object[] args) + { + Title = title; + Price = price; + FacialHair = facialHair; + GumpType = gumpType; + GumpArgs = args; + } + + public HairstylistBuyInfo(string title, int price, bool facialHair, Type gumpType, object[] args) + { + TitleString = title; + Price = price; + FacialHair = facialHair; + GumpType = gumpType; + GumpArgs = args; + } + + public int Title{ get; } + + public string TitleString{ get; } + + public int Price{ get; } + + public bool FacialHair{ get; } + + public Type GumpType{ get; } + + public object[] GumpArgs{ get; } + } + + public class HairstylistBuyGump : Gump + { + private Mobile m_From; + private HairstylistBuyInfo[] m_SellList; + private Mobile m_Vendor; + + public HairstylistBuyGump(Mobile from, Mobile vendor, HairstylistBuyInfo[] sellList) : base(50, 50) + { + m_From = from; + m_Vendor = vendor; + m_SellList = sellList; + + from.CloseGump(typeof(HairstylistBuyGump)); + from.CloseGump(typeof(ChangeHairHueGump)); + from.CloseGump(typeof(ChangeHairstyleGump)); + + bool isFemale = from.Female || from.Body.IsFemale; + + int balance = Banker.GetBalance(from); + int canAfford = 0; + + for (int i = 0; i < sellList.Length; ++i) + if (balance >= sellList[i].Price && (!sellList[i].FacialHair || !isFemale)) + ++canAfford; + + AddPage(0); + + AddBackground(50, 10, 450, 100 + canAfford * 25, 2600); + + AddHtmlLocalized(100, 40, 350, 20, 1018356, false, false); // Choose your hairstyle change: + + int index = 0; + + for (int i = 0; i < sellList.Length; ++i) + if (balance >= sellList[i].Price && (!sellList[i].FacialHair || !isFemale)) + { + if (sellList[i].TitleString != null) + AddHtml(140, 75 + index * 25, 300, 20, sellList[i].TitleString, false, false); + else + AddHtmlLocalized(140, 75 + index * 25, 300, 20, sellList[i].Title, false, false); + + AddButton(100, 75 + index++ * 25, 4005, 4007, 1 + i, GumpButtonType.Reply, 0); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int index = info.ButtonID - 1; + + if (index >= 0 && index < m_SellList.Length) + { + HairstylistBuyInfo buyInfo = m_SellList[index]; + + int balance = Banker.GetBalance(m_From); + + bool isFemale = m_From.Female || m_From.Body.IsFemale; + + if (buyInfo.FacialHair && isFemale) + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1010639, m_From.NetState); + else if (balance >= buyInfo.Price) + try + { + object[] origArgs = buyInfo.GumpArgs; + object[] args = new object[origArgs.Length]; + + for (int i = 0; i < args.Length; ++i) + if (origArgs[i] == CustomHairstylist.Price) + args[i] = m_SellList[index].Price; + else if (origArgs[i] == CustomHairstylist.From) + args[i] = m_From; + else if (origArgs[i] == CustomHairstylist.Vendor) + args[i] = m_Vendor; + else + args[i] = origArgs[i]; + + Gump g = Activator.CreateInstance(buyInfo.GumpType, args) as Gump; + + m_From.SendGump(g); + } + catch + { + } + else + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042293, m_From.NetState); + } + } + } + + public class ChangeHairHueEntry + { + public static readonly ChangeHairHueEntry[] BrightEntries = + { + new ChangeHairHueEntry("*****", 12, 10), + new ChangeHairHueEntry("*****", 32, 5), + new ChangeHairHueEntry("*****", 38, 8), + new ChangeHairHueEntry("*****", 54, 3), + new ChangeHairHueEntry("*****", 62, 10), + new ChangeHairHueEntry("*****", 81, 2), + new ChangeHairHueEntry("*****", 89, 2), + new ChangeHairHueEntry("*****", 1153, 2) + }; + + public static readonly ChangeHairHueEntry[] RegularEntries = + { + new ChangeHairHueEntry("*****", 1602, 26), + new ChangeHairHueEntry("*****", 1628, 27), + new ChangeHairHueEntry("*****", 1502, 32), + new ChangeHairHueEntry("*****", 1302, 32), + new ChangeHairHueEntry("*****", 1402, 32), + new ChangeHairHueEntry("*****", 1202, 24), + new ChangeHairHueEntry("*****", 2402, 29), + new ChangeHairHueEntry("*****", 2213, 6), + new ChangeHairHueEntry("*****", 1102, 8), + new ChangeHairHueEntry("*****", 1110, 8), + new ChangeHairHueEntry("*****", 1118, 16), + new ChangeHairHueEntry("*****", 1134, 16) + }; + + public ChangeHairHueEntry(string name, int[] hues) + { + Name = name; + Hues = hues; + } + + public ChangeHairHueEntry(string name, int start, int count) + { + Name = name; + + Hues = new int[count]; + + for (int i = 0; i < count; ++i) + Hues[i] = start + i; + } + + public string Name{ get; } + + public int[] Hues{ get; } + } + + public class ChangeHairHueGump : Gump + { + private ChangeHairHueEntry[] m_Entries; + private bool m_FacialHair; + private Mobile m_From; + private bool m_Hair; + private int m_Price; + private Mobile m_Vendor; + + public ChangeHairHueGump(Mobile from, Mobile vendor, int price, bool hair, bool facialHair, + ChangeHairHueEntry[] entries) : base(50, 50) + { + m_From = from; + m_Vendor = vendor; + m_Price = price; + m_Hair = hair; + m_FacialHair = facialHair; + m_Entries = entries; + + from.CloseGump(typeof(HairstylistBuyGump)); + from.CloseGump(typeof(ChangeHairHueGump)); + from.CloseGump(typeof(ChangeHairstyleGump)); + + AddPage(0); + + AddBackground(100, 10, 350, 370, 2600); + AddBackground(120, 54, 110, 270, 5100); + + AddHtmlLocalized(155, 25, 240, 30, 1011013, false, false); //
Hair Color Selection Menu
+ + AddHtmlLocalized(150, 330, 220, 35, 1011014, false, false); // Dye my hair this color! + AddButton(380, 330, 4005, 4007, 1, GumpButtonType.Reply, 0); + + for (int i = 0; i < entries.Length; ++i) + { + ChangeHairHueEntry entry = entries[i]; + + AddLabel(130, 59 + i * 22, entry.Hues[0] - 1, entry.Name); + AddButton(207, 60 + i * 22, 5224, 5224, 0, GumpButtonType.Page, 1 + i); + } + + for (int i = 0; i < entries.Length; ++i) + { + ChangeHairHueEntry entry = entries[i]; + int[] hues = entry.Hues; + string name = entry.Name; + + AddPage(1 + i); + + for (int j = 0; j < hues.Length; ++j) + { + AddLabel(278 + j / 16 * 80, 52 + j % 16 * 17, hues[j] - 1, name); + AddRadio(260 + j / 16 * 80, 52 + j % 16 * 17, 210, 211, false, j * entries.Length + i); + } + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + { + int[] switches = info.Switches; + + if (switches.Length > 0) + { + int index = switches[0] % m_Entries.Length; + int offset = switches[0] / m_Entries.Length; + + if (index >= 0 && index < m_Entries.Length) + if (offset >= 0 && offset < m_Entries[index].Hues.Length) + { + if (m_Hair && m_From.HairItemID > 0 || m_FacialHair && m_From.FacialHairItemID > 0) + { + if (!Banker.Withdraw(m_From, m_Price)) + { + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042293, + m_From.NetState); // You cannot afford my services for that style. + return; + } + + int hue = m_Entries[index].Hues[offset]; + + if (m_Hair) + m_From.HairHue = hue; + + if (m_FacialHair) + m_From.FacialHairHue = hue; + } + else + { + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502623, + m_From.NetState); // You have no hair to dye and you cannot use this. + } + } + } + else + { + // You decide not to change your hairstyle. + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1013009, m_From.NetState); + } + } + else + { + // You decide not to change your hairstyle. + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1013009, m_From.NetState); + } + } + } + + public class ChangeHairstyleEntry + { + public static readonly ChangeHairstyleEntry[] HairEntries = + { + new ChangeHairstyleEntry(50700, 70 - 137, 20 - 60, 0x203B), + new ChangeHairstyleEntry(60710, 193 - 260, 18 - 60, 0x2045), + new ChangeHairstyleEntry(50703, 316 - 383, 25 - 60, 0x2044), + new ChangeHairstyleEntry(60708, 70 - 137, 75 - 125, 0x203C), + new ChangeHairstyleEntry(60900, 193 - 260, 85 - 125, 0x2047), + new ChangeHairstyleEntry(60713, 320 - 383, 85 - 125, 0x204A), + new ChangeHairstyleEntry(60702, 70 - 137, 140 - 190, 0x203D), + new ChangeHairstyleEntry(60707, 193 - 260, 140 - 190, 0x2049), + new ChangeHairstyleEntry(60901, 315 - 383, 150 - 190, 0x2048), + new ChangeHairstyleEntry(0, 0, 0, 0) + }; + + public static readonly ChangeHairstyleEntry[] BeardEntries = + { + new ChangeHairstyleEntry(50800, 120 - 187, 30 - 80, 0x2040), + new ChangeHairstyleEntry(50904, 243 - 310, 33 - 80, 0x204B), + new ChangeHairstyleEntry(50906, 120 - 187, 100 - 150, 0x204D), + new ChangeHairstyleEntry(50801, 243 - 310, 95 - 150, 0x203E), + new ChangeHairstyleEntry(50802, 120 - 187, 173 - 220, 0x203F), + new ChangeHairstyleEntry(50905, 243 - 310, 165 - 220, 0x204C), + new ChangeHairstyleEntry(50808, 120 - 187, 242 - 290, 0x2041), + new ChangeHairstyleEntry(0, 0, 0, 0) + }; + + public ChangeHairstyleEntry(int gumpID, int x, int y, int itemID) + { + GumpID = gumpID; + X = x; + Y = y; + ItemID = itemID; + } + + public int ItemID{ get; } + + public int GumpID{ get; } + + public int X{ get; } + + public int Y{ get; } + } + + public class ChangeHairstyleGump : Gump + { + private ChangeHairstyleEntry[] m_Entries; + private bool m_FacialHair; + private Mobile m_From; + private int m_Price; + private Mobile m_Vendor; + + public ChangeHairstyleGump(Mobile from, Mobile vendor, int price, bool facialHair, ChangeHairstyleEntry[] entries) : + base(50, 50) + { + m_From = from; + m_Vendor = vendor; + m_Price = price; + m_FacialHair = facialHair; + m_Entries = entries; + + from.CloseGump(typeof(HairstylistBuyGump)); + from.CloseGump(typeof(ChangeHairHueGump)); + from.CloseGump(typeof(ChangeHairstyleGump)); + + int tableWidth = m_FacialHair ? 2 : 3; + int tableHeight = (entries.Length + tableWidth - (m_FacialHair ? 1 : 2)) / tableWidth; + int offsetWidth = 123; + int offsetHeight = m_FacialHair ? 70 : 65; + + AddPage(0); + + AddBackground(0, 0, 81 + tableWidth * offsetWidth, 105 + tableHeight * offsetHeight, 2600); + + AddButton(45, 45 + tableHeight * offsetHeight, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(77, 45 + tableHeight * offsetHeight, 90, 35, 1006044, false, false); // Ok + + AddButton(81 + tableWidth * offsetWidth - 180, 45 + tableHeight * offsetHeight, 4005, 4007, 0, + GumpButtonType.Reply, 0); + AddHtmlLocalized(81 + tableWidth * offsetWidth - 148, 45 + tableHeight * offsetHeight, 90, 35, 1006045, false, + false); // Cancel + + if (!facialHair) + AddHtmlLocalized(50, 15, 350, 20, 1018353, false, false); //
New Hairstyle
+ else + AddHtmlLocalized(55, 15, 200, 20, 1018354, false, false); //
New Beard
+ + for (int i = 0; i < entries.Length; ++i) + { + int xTable = i % tableWidth; + int yTable = i / tableWidth; + + if (entries[i].GumpID != 0) + { + AddRadio(40 + xTable * offsetWidth, 70 + yTable * offsetHeight, 208, 209, false, i); + AddBackground(87 + xTable * offsetWidth, 50 + yTable * offsetHeight, 50, 50, 2620); + AddImage(87 + xTable * offsetWidth + entries[i].X, 50 + yTable * offsetHeight + entries[i].Y, + entries[i].GumpID); + } + else if (!facialHair) + { + AddRadio(40 + (xTable + 1) * offsetWidth, 240, 208, 209, false, i); + AddHtmlLocalized(60 + (xTable + 1) * offsetWidth, 240, 85, 35, 1011064, false, false); // Bald + } + else + { + AddRadio(40 + xTable * offsetWidth, 70 + yTable * offsetHeight, 208, 209, false, i); + AddHtmlLocalized(60 + xTable * offsetWidth, 70 + yTable * offsetHeight, 85, 35, 1011064, false, + false); // Bald + } + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (m_FacialHair && (m_From.Female || m_From.Body.IsFemale)) + return; + + if (m_From.Race == Race.Elf) + { + m_From.SendMessage("This isn't implemented for elves yet. Sorry!"); + return; + } + + if (info.ButtonID == 1) + { + int[] switches = info.Switches; + + if (switches.Length > 0) + { + int index = switches[0]; + + if (index >= 0 && index < m_Entries.Length) + { + ChangeHairstyleEntry entry = m_Entries[index]; + + (m_From as PlayerMobile)?.SetHairMods(-1, -1); + + int hairID = m_From.HairItemID; + int facialHairID = m_From.FacialHairItemID; + + if (entry.ItemID == 0) + { + if (m_FacialHair ? facialHairID == 0 : hairID == 0) + return; + + if (Banker.Withdraw(m_From, m_Price)) + { + if (m_FacialHair) + m_From.FacialHairItemID = 0; + else + m_From.HairItemID = 0; + } + else + { + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042293, + m_From.NetState); // You cannot afford my services for that style. + } + } + else + { + if (m_FacialHair) + { + if (facialHairID > 0 && facialHairID == entry.ItemID) + return; + } + else + { + if (hairID > 0 && hairID == entry.ItemID) + return; + } + + if (Banker.Withdraw(m_From, m_Price)) + { + if (m_FacialHair) + m_From.FacialHairItemID = entry.ItemID; + else + m_From.HairItemID = entry.ItemID; + } + else + { + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042293, + m_From.NetState); // You cannot afford my services for that style. + } + } + } + } + else + { + // You decide not to change your hairstyle. + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1013009, m_From.NetState); + } + } + else + { + // You decide not to change your hairstyle. + m_Vendor.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1013009, m_From.NetState); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Farmer.cs b/Scripts/Mobiles/Vendors/NPC/Farmer.cs index 4d58adff6..d77772850 100644 --- a/Scripts/Mobiles/Vendors/NPC/Farmer.cs +++ b/Scripts/Mobiles/Vendors/NPC/Farmer.cs @@ -1,55 +1,57 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Farmer : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Farmer : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Farmer() : base( "the farmer" ) - { - SetSkill( SkillName.Lumberjacking, 36.0, 68.0 ); - SetSkill( SkillName.TasteID, 36.0, 68.0 ); - SetSkill( SkillName.Cooking, 36.0, 68.0 ); - } + [Constructible] + public Farmer() : base("the farmer") + { + SetSkill(SkillName.Lumberjacking, 36.0, 68.0); + SetSkill(SkillName.TasteID, 36.0, 68.0); + SetSkill(SkillName.Cooking, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBFarmer() ); - } + public Farmer(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => VendorShoeType.ThighBoots; + protected override List SBInfos => m_SBInfos; - public override int GetShoeHue() - { - return 0; - } + public override VendorShoeType ShoeType => VendorShoeType.ThighBoots; - public override void InitOutfit() - { - base.InitOutfit(); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBFarmer()); + } - AddItem( new Items.WideBrimHat( Utility.RandomNeutralHue() ) ); - } + public override int GetShoeHue() + { + return 0; + } - public Farmer( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new WideBrimHat(Utility.RandomNeutralHue())); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Fisherman.cs b/Scripts/Mobiles/Vendors/NPC/Fisherman.cs index 3273dddf7..82aa37af9 100644 --- a/Scripts/Mobiles/Vendors/NPC/Fisherman.cs +++ b/Scripts/Mobiles/Vendors/NPC/Fisherman.cs @@ -1,48 +1,50 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Fisherman : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Fisherman : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.FishermensGuild; + [Constructible] + public Fisherman() : base("the fisher") + { + SetSkill(SkillName.Fishing, 75.0, 98.0); + } - [Constructible] - public Fisherman() : base( "the fisher" ) - { - SetSkill( SkillName.Fishing, 75.0, 98.0 ); - } + public Fisherman(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBFisherman() ); - } + protected override List SBInfos => m_SBInfos; - public override void InitOutfit() - { - base.InitOutfit(); + public override NpcGuild NpcGuild => NpcGuild.FishermensGuild; - AddItem( new Items.FishingPole() ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBFisherman()); + } - public Fisherman( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new FishingPole()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Furtrader.cs b/Scripts/Mobiles/Vendors/NPC/Furtrader.cs index 067c74322..9afeb3b6d 100644 --- a/Scripts/Mobiles/Vendors/NPC/Furtrader.cs +++ b/Scripts/Mobiles/Vendors/NPC/Furtrader.cs @@ -2,42 +2,43 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Furtrader : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Furtrader : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Furtrader() : base( "the furtrader" ) - { - SetSkill( SkillName.Camping, 55.0, 78.0 ); - //SetSkill( SkillName.Alchemy, 60.0, 83.0 ); - SetSkill( SkillName.AnimalLore, 85.0, 100.0 ); - SetSkill( SkillName.Cooking, 45.0, 68.0 ); - SetSkill( SkillName.Tracking, 36.0, 68.0 ); - } + [Constructible] + public Furtrader() : base("the furtrader") + { + SetSkill(SkillName.Camping, 55.0, 78.0); + //SetSkill( SkillName.Alchemy, 60.0, 83.0 ); + SetSkill(SkillName.AnimalLore, 85.0, 100.0); + SetSkill(SkillName.Cooking, 45.0, 68.0); + SetSkill(SkillName.Tracking, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBFurtrader() ); - } + public Furtrader(Serial serial) : base(serial) + { + } - public Furtrader( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBFurtrader()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Glassblower.cs b/Scripts/Mobiles/Vendors/NPC/Glassblower.cs index ed3a0bcfc..34a4be6af 100644 --- a/Scripts/Mobiles/Vendors/NPC/Glassblower.cs +++ b/Scripts/Mobiles/Vendors/NPC/Glassblower.cs @@ -2,46 +2,47 @@ using System.Collections.Generic; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.GargoyleAlchemist" )] - public class Glassblower : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + [TypeAlias("Server.Mobiles.GargoyleAlchemist")] + public class Glassblower : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.MagesGuild; + [Constructible] + public Glassblower() : base("the alchemist") + { + SetSkill(SkillName.Alchemy, 85.0, 100.0); + SetSkill(SkillName.TasteID, 85.0, 100.0); + } - [Constructible] - public Glassblower() : base( "the alchemist" ) - { - SetSkill( SkillName.Alchemy, 85.0, 100.0 ); - SetSkill( SkillName.TasteID, 85.0, 100.0 ); - } + public Glassblower(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBGlassblower() ); - m_SBInfos.Add( new SBAlchemist() ); - } + protected override List SBInfos => m_SBInfos; - public Glassblower( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.MagesGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBGlassblower()); + m_SBInfos.Add(new SBAlchemist()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Body == 0x2F2 ) - Body = 0x2F6; - } - } -} + int version = reader.ReadInt(); + + if (Body == 0x2F2) + Body = 0x2F6; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/GolemCrafter.cs b/Scripts/Mobiles/Vendors/NPC/GolemCrafter.cs index 0026c6ddc..3a78d7ab2 100644 --- a/Scripts/Mobiles/Vendors/NPC/GolemCrafter.cs +++ b/Scripts/Mobiles/Vendors/NPC/GolemCrafter.cs @@ -2,41 +2,42 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class GolemCrafter : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class GolemCrafter : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public GolemCrafter() : base( "the golem crafter" ) - { - SetSkill( SkillName.Lockpicking, 60.0, 83.0 ); - SetSkill( SkillName.RemoveTrap, 75.0, 98.0 ); - SetSkill( SkillName.Tinkering, 64.0, 100.0 ); - } + [Constructible] + public GolemCrafter() : base("the golem crafter") + { + SetSkill(SkillName.Lockpicking, 60.0, 83.0); + SetSkill(SkillName.RemoveTrap, 75.0, 98.0); + SetSkill(SkillName.Tinkering, 64.0, 100.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBTinker() ); - m_SBInfos.Add( new SBVagabond() ); - } + public GolemCrafter(Serial serial) : base(serial) + { + } - public GolemCrafter( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBTinker()); + m_SBInfos.Add(new SBVagabond()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/BardGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/BardGuildmaster.cs index 3c3239ba1..867a3dd69 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/BardGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/BardGuildmaster.cs @@ -1,36 +1,36 @@ namespace Server.Mobiles { - public class BardGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.BardsGuild; + public class BardGuildmaster : BaseGuildmaster + { + [Constructible] + public BardGuildmaster() : base("bard") + { + SetSkill(SkillName.Archery, 80.0, 100.0); + SetSkill(SkillName.Discordance, 80.0, 100.0); + SetSkill(SkillName.Musicianship, 80.0, 100.0); + SetSkill(SkillName.Peacemaking, 80.0, 100.0); + SetSkill(SkillName.Provocation, 80.0, 100.0); + SetSkill(SkillName.Swords, 80.0, 100.0); + } - [Constructible] - public BardGuildmaster() : base( "bard" ) - { - SetSkill( SkillName.Archery, 80.0, 100.0 ); - SetSkill( SkillName.Discordance, 80.0, 100.0 ); - SetSkill( SkillName.Musicianship, 80.0, 100.0 ); - SetSkill( SkillName.Peacemaking, 80.0, 100.0 ); - SetSkill( SkillName.Provocation, 80.0, 100.0 ); - SetSkill( SkillName.Swords, 80.0, 100.0 ); - } + public BardGuildmaster(Serial serial) : base(serial) + { + } - public BardGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.BardsGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/BaseGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/BaseGuildmaster.cs index deb9e7dc8..1df95146f 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/BaseGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/BaseGuildmaster.cs @@ -5,161 +5,163 @@ using Server.Network; namespace Server.Mobiles { - public abstract class BaseGuildmaster : BaseVendor - { - protected override List SBInfos { get; } = new List(); + public abstract class BaseGuildmaster : BaseVendor + { + public BaseGuildmaster(string title) : base(title) + { + Title = $"the {title} {(Female ? "guildmistress" : "guildmaster")}"; + } - public override bool IsActiveVendor => false; + public BaseGuildmaster(Serial serial) : base(serial) + { + } - public override bool ClickTitle => false; + protected override List SBInfos{ get; } = new List(); - public virtual int JoinCost => 500; + public override bool IsActiveVendor => false; - public virtual TimeSpan JoinAge => TimeSpan.FromDays( 0.0 ); - public virtual TimeSpan JoinGameAge => TimeSpan.FromDays( 2.0 ); - public virtual TimeSpan QuitAge => TimeSpan.FromDays( 7.0 ); - public virtual TimeSpan QuitGameAge => TimeSpan.FromDays( 4.0 ); + public override bool ClickTitle => false; - public override void InitSBInfo() - { - } + public virtual int JoinCost => 500; - public virtual bool CheckCustomReqs( PlayerMobile pm ) - { - return true; - } + public virtual TimeSpan JoinAge => TimeSpan.FromDays(0.0); + public virtual TimeSpan JoinGameAge => TimeSpan.FromDays(2.0); + public virtual TimeSpan QuitAge => TimeSpan.FromDays(7.0); + public virtual TimeSpan QuitGameAge => TimeSpan.FromDays(4.0); - public virtual void SayGuildTo( Mobile m ) - { - SayTo( m, 1008055 + (int)NpcGuild ); - } + public override void InitSBInfo() + { + } - public virtual void SayWelcomeTo( Mobile m ) - { - SayTo( m, 1008054 ); // Welcome to the guild! Thou shalt find that fellow members shall grant thee lower prices in shops. - } + public virtual bool CheckCustomReqs(PlayerMobile pm) + { + return true; + } - public virtual void SayPriceTo( Mobile m ) - { - m.Send( new MessageLocalizedAffix( Serial, Body, MessageType.Regular, SpeechHue, 3, 1008052, Name, AffixType.Append, JoinCost.ToString(), "" ) ); - } + public virtual void SayGuildTo(Mobile m) + { + SayTo(m, 1008055 + (int)NpcGuild); + } - public virtual bool WasNamed( string speech ) - { - string name = Name; + public virtual void SayWelcomeTo(Mobile m) + { + SayTo(m, 1008054); // Welcome to the guild! Thou shalt find that fellow members shall grant thee lower prices in shops. + } - return ( name != null && Insensitive.StartsWith( speech, name ) ); - } + public virtual void SayPriceTo(Mobile m) + { + m.Send(new MessageLocalizedAffix(Serial, Body, MessageType.Regular, SpeechHue, 3, 1008052, Name, + AffixType.Append, JoinCost.ToString(), "")); + } - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - return true; + public virtual bool WasNamed(string speech) + { + string name = Name; - return base.HandlesOnSpeech( from ); - } + return name != null && Insensitive.StartsWith(speech, name); + } - public override void OnSpeech( SpeechEventArgs e ) - { - Mobile from = e.Mobile; + public override bool HandlesOnSpeech(Mobile from) + { + if (from.InRange(Location, 2)) + return true; - if ( !e.Handled && from is PlayerMobile && from.InRange( Location, 2 ) && WasNamed( e.Speech ) ) - { - PlayerMobile pm = (PlayerMobile)from; + return base.HandlesOnSpeech(from); + } - if ( e.HasKeyword( 0x0004 ) ) // *join* | *member* - { - if ( pm.NpcGuild == NpcGuild ) - SayTo( from, 501047 ); // Thou art already a member of our guild. - else if ( pm.NpcGuild != NpcGuild.None ) - SayTo( from, 501046 ); // Thou must resign from thy other guild first. - else if ( pm.GameTime < JoinGameAge || (pm.CreationTime + JoinAge) > DateTime.UtcNow ) - SayTo( from, 501048 ); // You are too young to join my guild... - else if ( CheckCustomReqs( pm ) ) - SayPriceTo( from ); + public override void OnSpeech(SpeechEventArgs e) + { + Mobile from = e.Mobile; - e.Handled = true; - } - else if ( e.HasKeyword( 0x0005 ) ) // *resign* | *quit* - { - if ( pm.NpcGuild != NpcGuild ) - { - SayTo( from, 501052 ); // Thou dost not belong to my guild! - } - else if ( (pm.NpcGuildJoinTime + QuitAge) > DateTime.UtcNow || (pm.NpcGuildGameTime + QuitGameAge) > pm.GameTime ) - { - SayTo( from, 501053 ); // You just joined my guild! You must wait a week to resign. - } - else - { - SayTo( from, 501054 ); // I accept thy resignation. - pm.NpcGuild = NpcGuild.None; - } + if (!e.Handled && from is PlayerMobile && from.InRange(Location, 2) && WasNamed(e.Speech)) + { + PlayerMobile pm = (PlayerMobile)from; - e.Handled = true; - } - } + if (e.HasKeyword(0x0004)) // *join* | *member* + { + if (pm.NpcGuild == NpcGuild) + SayTo(from, 501047); // Thou art already a member of our guild. + else if (pm.NpcGuild != NpcGuild.None) + SayTo(from, 501046); // Thou must resign from thy other guild first. + else if (pm.GameTime < JoinGameAge || pm.CreationTime + JoinAge > DateTime.UtcNow) + SayTo(from, 501048); // You are too young to join my guild... + else if (CheckCustomReqs(pm)) + SayPriceTo(from); - base.OnSpeech( e ); - } + e.Handled = true; + } + else if (e.HasKeyword(0x0005)) // *resign* | *quit* + { + if (pm.NpcGuild != NpcGuild) + { + SayTo(from, 501052); // Thou dost not belong to my guild! + } + else if (pm.NpcGuildJoinTime + QuitAge > DateTime.UtcNow || + pm.NpcGuildGameTime + QuitGameAge > pm.GameTime) + { + SayTo(from, 501053); // You just joined my guild! You must wait a week to resign. + } + else + { + SayTo(from, 501054); // I accept thy resignation. + pm.NpcGuild = NpcGuild.None; + } - public override bool OnGoldGiven( Mobile from, Gold dropped ) - { - if ( from is PlayerMobile && dropped.Amount == JoinCost ) - { - PlayerMobile pm = (PlayerMobile)from; + e.Handled = true; + } + } - if ( pm.NpcGuild == NpcGuild ) - { - SayTo( from, 501047 ); // Thou art already a member of our guild. - } - else if ( pm.NpcGuild != NpcGuild.None ) - { - SayTo( from, 501046 ); // Thou must resign from thy other guild first. - } - else if ( pm.GameTime < JoinGameAge || (pm.CreationTime + JoinAge) > DateTime.UtcNow ) - { - SayTo( from, 501048 ); // You are too young to join my guild... - } - else if ( CheckCustomReqs( pm ) ) - { - SayWelcomeTo( from ); + base.OnSpeech(e); + } - pm.NpcGuild = NpcGuild; - pm.NpcGuildJoinTime = DateTime.UtcNow; - pm.NpcGuildGameTime = pm.GameTime; + public override bool OnGoldGiven(Mobile from, Gold dropped) + { + if (from is PlayerMobile && dropped.Amount == JoinCost) + { + PlayerMobile pm = (PlayerMobile)from; - dropped.Delete(); - return true; - } + if (pm.NpcGuild == NpcGuild) + { + SayTo(from, 501047); // Thou art already a member of our guild. + } + else if (pm.NpcGuild != NpcGuild.None) + { + SayTo(from, 501046); // Thou must resign from thy other guild first. + } + else if (pm.GameTime < JoinGameAge || pm.CreationTime + JoinAge > DateTime.UtcNow) + { + SayTo(from, 501048); // You are too young to join my guild... + } + else if (CheckCustomReqs(pm)) + { + SayWelcomeTo(from); - return false; - } + pm.NpcGuild = NpcGuild; + pm.NpcGuildJoinTime = DateTime.UtcNow; + pm.NpcGuildGameTime = pm.GameTime; - return base.OnGoldGiven( from, dropped ); - } + dropped.Delete(); + return true; + } - public BaseGuildmaster( string title ) : base( title ) - { - Title = $"the {title} {(Female ? "guildmistress" : "guildmaster")}"; - } + return false; + } - public BaseGuildmaster( Serial serial ) : base( serial ) - { - } + return base.OnGoldGiven(from, dropped); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/BlacksmithGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/BlacksmithGuildmaster.cs index 385cc837f..beb602204 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/BlacksmithGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/BlacksmithGuildmaster.cs @@ -1,63 +1,66 @@ +using Server.Items; + namespace Server.Mobiles { - public class BlacksmithGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.BlacksmithsGuild; + public class BlacksmithGuildmaster : BaseGuildmaster + { + [Constructible] + public BlacksmithGuildmaster() : base("blacksmith") + { + SetSkill(SkillName.ArmsLore, 65.0, 88.0); + SetSkill(SkillName.Blacksmith, 90.0, 100.0); + SetSkill(SkillName.Macing, 36.0, 68.0); + SetSkill(SkillName.Parry, 36.0, 68.0); + } - public override bool IsActiveVendor => true; + public BlacksmithGuildmaster(Serial serial) : base(serial) + { + } - public override bool ClickTitle => true; + public override NpcGuild NpcGuild => NpcGuild.BlacksmithsGuild; - [Constructible] - public BlacksmithGuildmaster() : base( "blacksmith" ) - { - SetSkill( SkillName.ArmsLore, 65.0, 88.0 ); - SetSkill( SkillName.Blacksmith, 90.0, 100.0 ); - SetSkill( SkillName.Macing, 36.0, 68.0 ); - SetSkill( SkillName.Parry, 36.0, 68.0 ); - } - public override void InitSBInfo() - { - SBInfos.Add( new SBBlacksmith() ); - } + public override bool IsActiveVendor => true; - public override VendorShoeType ShoeType => VendorShoeType.ThighBoots; + public override bool ClickTitle => true; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => VendorShoeType.ThighBoots; - Item item = ( Utility.RandomBool() ? null : new Items.RingmailChest() ); + public override void InitSBInfo() + { + SBInfos.Add(new SBBlacksmith()); + } - if ( item != null && !EquipItem( item ) ) - { - item.Delete(); - item = null; - } + public override void InitOutfit() + { + base.InitOutfit(); - if ( item == null ) - AddItem( new Items.FullApron() ); + Item item = Utility.RandomBool() ? null : new RingmailChest(); - AddItem( new Items.Bascinet() ); - AddItem( new Items.SmithHammer() ); - } + if (item != null && !EquipItem(item)) + { + item.Delete(); + item = null; + } - public BlacksmithGuildmaster( Serial serial ) : base( serial ) - { - } + if (item == null) + AddItem(new FullApron()); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new Bascinet()); + AddItem(new SmithHammer()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/FisherGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/FisherGuildmaster.cs index 96ae8952b..33d3a8e4d 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/FisherGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/FisherGuildmaster.cs @@ -1,31 +1,31 @@ namespace Server.Mobiles { - public class FisherGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.FishermensGuild; + public class FisherGuildmaster : BaseGuildmaster + { + [Constructible] + public FisherGuildmaster() : base("fisher") + { + SetSkill(SkillName.Fishing, 80.0, 100.0); + } - [Constructible] - public FisherGuildmaster() : base( "fisher" ) - { - SetSkill( SkillName.Fishing, 80.0, 100.0 ); - } + public FisherGuildmaster(Serial serial) : base(serial) + { + } - public FisherGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.FishermensGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/HealerGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/HealerGuildmaster.cs index 3e541e624..3966d2bfc 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/HealerGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/HealerGuildmaster.cs @@ -1,44 +1,46 @@ +using Server.Items; + namespace Server.Mobiles { - public class HealerGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.HealersGuild; + public class HealerGuildmaster : BaseGuildmaster + { + [Constructible] + public HealerGuildmaster() : base("healer") + { + SetSkill(SkillName.Anatomy, 85.0, 100.0); + SetSkill(SkillName.Healing, 90.0, 100.0); + SetSkill(SkillName.Forensics, 75.0, 98.0); + SetSkill(SkillName.MagicResist, 75.0, 98.0); + SetSkill(SkillName.SpiritSpeak, 65.0, 88.0); + } - [Constructible] - public HealerGuildmaster() : base( "healer" ) - { - SetSkill( SkillName.Anatomy, 85.0, 100.0 ); - SetSkill( SkillName.Healing, 90.0, 100.0 ); - SetSkill( SkillName.Forensics, 75.0, 98.0 ); - SetSkill( SkillName.MagicResist, 75.0, 98.0 ); - SetSkill( SkillName.SpiritSpeak, 65.0, 88.0 ); - } + public HealerGuildmaster(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.HealersGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => VendorShoeType.Sandals; - AddItem( new Items.Robe( Utility.RandomYellowHue() ) ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public HealerGuildmaster( Serial serial ) : base( serial ) - { - } + AddItem(new Robe(Utility.RandomYellowHue())); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/MageGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/MageGuildmaster.cs index 4fb2f6eba..b5b2cf595 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/MageGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/MageGuildmaster.cs @@ -1,47 +1,49 @@ +using Server.Items; + namespace Server.Mobiles { - public class MageGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.MagesGuild; + public class MageGuildmaster : BaseGuildmaster + { + [Constructible] + public MageGuildmaster() : base("mage") + { + SetSkill(SkillName.EvalInt, 85.0, 100.0); + SetSkill(SkillName.Inscribe, 65.0, 88.0); + SetSkill(SkillName.MagicResist, 64.0, 100.0); + SetSkill(SkillName.Magery, 90.0, 100.0); + SetSkill(SkillName.Wrestling, 60.0, 83.0); + SetSkill(SkillName.Meditation, 85.0, 100.0); + SetSkill(SkillName.Macing, 36.0, 68.0); + } - [Constructible] - public MageGuildmaster() : base( "mage" ) - { - SetSkill( SkillName.EvalInt, 85.0, 100.0 ); - SetSkill( SkillName.Inscribe, 65.0, 88.0 ); - SetSkill( SkillName.MagicResist, 64.0, 100.0 ); - SetSkill( SkillName.Magery, 90.0, 100.0 ); - SetSkill( SkillName.Wrestling, 60.0, 83.0 ); - SetSkill( SkillName.Meditation, 85.0, 100.0 ); - SetSkill( SkillName.Macing, 36.0, 68.0 ); - } + public MageGuildmaster(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.MagesGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - AddItem( new Items.Robe( Utility.RandomBlueHue() ) ); - AddItem( new Items.GnarledStaff() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public MageGuildmaster( Serial serial ) : base( serial ) - { - } + AddItem(new Robe(Utility.RandomBlueHue())); + AddItem(new GnarledStaff()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/MerchantGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/MerchantGuildmaster.cs index fe0d0e0b9..d0bcfbaae 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/MerchantGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/MerchantGuildmaster.cs @@ -1,32 +1,32 @@ namespace Server.Mobiles { - public class MerchantGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.MerchantsGuild; + public class MerchantGuildmaster : BaseGuildmaster + { + [Constructible] + public MerchantGuildmaster() : base("merchant") + { + SetSkill(SkillName.ItemID, 85.0, 100.0); + SetSkill(SkillName.ArmsLore, 85.0, 100.0); + } - [Constructible] - public MerchantGuildmaster() : base( "merchant" ) - { - SetSkill( SkillName.ItemID, 85.0, 100.0 ); - SetSkill( SkillName.ArmsLore, 85.0, 100.0 ); - } + public MerchantGuildmaster(Serial serial) : base(serial) + { + } - public MerchantGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.MerchantsGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/MinerGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/MinerGuildmaster.cs index d2693f367..b33a487bf 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/MinerGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/MinerGuildmaster.cs @@ -1,32 +1,32 @@ namespace Server.Mobiles { - public class MinerGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.MinersGuild; + public class MinerGuildmaster : BaseGuildmaster + { + [Constructible] + public MinerGuildmaster() : base("miner") + { + SetSkill(SkillName.ItemID, 60.0, 83.0); + SetSkill(SkillName.Mining, 90.0, 100.0); + } - [Constructible] - public MinerGuildmaster() : base( "miner" ) - { - SetSkill( SkillName.ItemID, 60.0, 83.0 ); - SetSkill( SkillName.Mining, 90.0, 100.0 ); - } + public MinerGuildmaster(Serial serial) : base(serial) + { + } - public MinerGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.MinersGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/RangerGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/RangerGuildmaster.cs index a89095ea0..1926f2aa6 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/RangerGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/RangerGuildmaster.cs @@ -1,41 +1,41 @@ namespace Server.Mobiles { - public class RangerGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.RangersGuild; + public class RangerGuildmaster : BaseGuildmaster + { + [Constructible] + public RangerGuildmaster() : base("ranger") + { + SetSkill(SkillName.AnimalLore, 64.0, 100.0); + SetSkill(SkillName.Camping, 75.0, 98.0); + SetSkill(SkillName.Hiding, 75.0, 98.0); + SetSkill(SkillName.MagicResist, 75.0, 98.0); + SetSkill(SkillName.Tactics, 65.0, 88.0); + SetSkill(SkillName.Archery, 90.0, 100.0); + SetSkill(SkillName.Tracking, 90.0, 100.0); + SetSkill(SkillName.Stealth, 60.0, 83.0); + SetSkill(SkillName.Fencing, 36.0, 68.0); + SetSkill(SkillName.Herding, 36.0, 68.0); + SetSkill(SkillName.Swords, 45.0, 68.0); + } - [Constructible] - public RangerGuildmaster() : base( "ranger" ) - { - SetSkill( SkillName.AnimalLore, 64.0, 100.0 ); - SetSkill( SkillName.Camping, 75.0, 98.0 ); - SetSkill( SkillName.Hiding, 75.0, 98.0 ); - SetSkill( SkillName.MagicResist, 75.0, 98.0 ); - SetSkill( SkillName.Tactics, 65.0, 88.0 ); - SetSkill( SkillName.Archery, 90.0, 100.0 ); - SetSkill( SkillName.Tracking, 90.0, 100.0 ); - SetSkill( SkillName.Stealth, 60.0, 83.0 ); - SetSkill( SkillName.Fencing, 36.0, 68.0 ); - SetSkill( SkillName.Herding, 36.0, 68.0 ); - SetSkill( SkillName.Swords, 45.0, 68.0 ); - } + public RangerGuildmaster(Serial serial) : base(serial) + { + } - public RangerGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.RangersGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/TailorGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/TailorGuildmaster.cs index e34dad785..2a38fbb95 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/TailorGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/TailorGuildmaster.cs @@ -1,31 +1,31 @@ namespace Server.Mobiles { - public class TailorGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.TailorsGuild; + public class TailorGuildmaster : BaseGuildmaster + { + [Constructible] + public TailorGuildmaster() : base("tailor") + { + SetSkill(SkillName.Tailoring, 90.0, 100.0); + } - [Constructible] - public TailorGuildmaster() : base( "tailor" ) - { - SetSkill( SkillName.Tailoring, 90.0, 100.0 ); - } + public TailorGuildmaster(Serial serial) : base(serial) + { + } - public TailorGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.TailorsGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/ThiefGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/ThiefGuildmaster.cs index 993af8baf..fa6c18ed9 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/ThiefGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/ThiefGuildmaster.cs @@ -3,124 +3,125 @@ using Server.Items; namespace Server.Mobiles { - public class ThiefGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.ThievesGuild; + public class ThiefGuildmaster : BaseGuildmaster + { + [Constructible] + public ThiefGuildmaster() : base("thief") + { + SetSkill(SkillName.DetectHidden, 75.0, 98.0); + SetSkill(SkillName.Hiding, 65.0, 88.0); + SetSkill(SkillName.Lockpicking, 85.0, 100.0); + SetSkill(SkillName.Snooping, 90.0, 100.0); + SetSkill(SkillName.Poisoning, 60.0, 83.0); + SetSkill(SkillName.Stealing, 90.0, 100.0); + SetSkill(SkillName.Fencing, 75.0, 98.0); + SetSkill(SkillName.Stealth, 85.0, 100.0); + SetSkill(SkillName.RemoveTrap, 85.0, 100.0); + } - public override TimeSpan JoinAge => TimeSpan.FromDays( 7.0 ); + public ThiefGuildmaster(Serial serial) : base(serial) + { + } - [Constructible] - public ThiefGuildmaster() : base( "thief" ) - { - SetSkill( SkillName.DetectHidden, 75.0, 98.0 ); - SetSkill( SkillName.Hiding, 65.0, 88.0 ); - SetSkill( SkillName.Lockpicking, 85.0, 100.0 ); - SetSkill( SkillName.Snooping, 90.0, 100.0 ); - SetSkill( SkillName.Poisoning, 60.0, 83.0 ); - SetSkill( SkillName.Stealing, 90.0, 100.0 ); - SetSkill( SkillName.Fencing, 75.0, 98.0 ); - SetSkill( SkillName.Stealth, 85.0, 100.0 ); - SetSkill( SkillName.RemoveTrap, 85.0, 100.0 ); - } + public override NpcGuild NpcGuild => NpcGuild.ThievesGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override TimeSpan JoinAge => TimeSpan.FromDays(7.0); - if ( Utility.RandomBool() ) - AddItem( new Kryss() ); - else - AddItem( new Dagger() ); - } + public override void InitOutfit() + { + base.InitOutfit(); - public override bool CheckCustomReqs( PlayerMobile pm ) - { - if ( pm.Young ) - { - SayTo( pm, 502089 ); // You cannot be a member of the Thieves' Guild while you are Young. - return false; - } + if (Utility.RandomBool()) + AddItem(new Kryss()); + else + AddItem(new Dagger()); + } - if ( pm.Kills > 0 ) - { - SayTo( pm, 501050 ); // This guild is for cunning thieves, not oafish cutthroats. - return false; - } - if ( pm.Skills[SkillName.Stealing].Base < 60.0 ) - { - SayTo( pm, 501051 ); // You must be at least a journeyman pickpocket to join this elite organization. - return false; - } + public override bool CheckCustomReqs(PlayerMobile pm) + { + if (pm.Young) + { + SayTo(pm, 502089); // You cannot be a member of the Thieves' Guild while you are Young. + return false; + } - return true; - } + if (pm.Kills > 0) + { + SayTo(pm, 501050); // This guild is for cunning thieves, not oafish cutthroats. + return false; + } - public override void SayWelcomeTo( Mobile m ) - { - SayTo( m, 1008053 ); // Welcome to the guild! Stay to the shadows, friend. - } + if (pm.Skills[SkillName.Stealing].Base < 60.0) + { + SayTo(pm, 501051); // You must be at least a journeyman pickpocket to join this elite organization. + return false; + } - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.InRange( Location, 2 ) ) - return true; + return true; + } - return base.HandlesOnSpeech( from ); - } + public override void SayWelcomeTo(Mobile m) + { + SayTo(m, 1008053); // Welcome to the guild! Stay to the shadows, friend. + } - public override void OnSpeech( SpeechEventArgs e ) - { - Mobile from = e.Mobile; + public override bool HandlesOnSpeech(Mobile from) + { + if (from.InRange(Location, 2)) + return true; - if ( !e.Handled && from is PlayerMobile && from.InRange( Location, 2 ) && e.HasKeyword( 0x1F ) ) // *disguise* - { - PlayerMobile pm = (PlayerMobile)from; + return base.HandlesOnSpeech(from); + } - if ( pm.NpcGuild == NpcGuild.ThievesGuild ) - SayTo( from, 501839 ); // That particular item costs 700 gold pieces. - else - SayTo( from, 501838 ); // I don't know what you're talking about. + public override void OnSpeech(SpeechEventArgs e) + { + Mobile from = e.Mobile; - e.Handled = true; - } + if (!e.Handled && from is PlayerMobile && from.InRange(Location, 2) && e.HasKeyword(0x1F)) // *disguise* + { + PlayerMobile pm = (PlayerMobile)from; - base.OnSpeech( e ); - } + if (pm.NpcGuild == NpcGuild.ThievesGuild) + SayTo(from, 501839); // That particular item costs 700 gold pieces. + else + SayTo(from, 501838); // I don't know what you're talking about. - public override bool OnGoldGiven( Mobile from, Gold dropped ) - { - if ( from is PlayerMobile && dropped.Amount == 700 ) - { - PlayerMobile pm = (PlayerMobile)from; + e.Handled = true; + } - if ( pm.NpcGuild == NpcGuild.ThievesGuild ) - { - from.AddToBackpack( new DisguiseKit() ); + base.OnSpeech(e); + } - dropped.Delete(); - return true; - } - } + public override bool OnGoldGiven(Mobile from, Gold dropped) + { + if (from is PlayerMobile && dropped.Amount == 700) + { + PlayerMobile pm = (PlayerMobile)from; - return base.OnGoldGiven( from, dropped ); - } + if (pm.NpcGuild == NpcGuild.ThievesGuild) + { + from.AddToBackpack(new DisguiseKit()); - public ThiefGuildmaster( Serial serial ) : base( serial ) - { - } + dropped.Delete(); + return true; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return base.OnGoldGiven(from, dropped); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/TinkerGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/TinkerGuildmaster.cs index f35605f78..2cde91d5b 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/TinkerGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/TinkerGuildmaster.cs @@ -1,82 +1,85 @@ using System.Collections.Generic; -using Server.Items; using Server.ContextMenus; +using Server.Items; namespace Server.Mobiles { - public class TinkerGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; + public class TinkerGuildmaster : BaseGuildmaster + { + [Constructible] + public TinkerGuildmaster() : base("tinker") + { + SetSkill(SkillName.Lockpicking, 65.0, 88.0); + SetSkill(SkillName.Tinkering, 90.0, 100.0); + SetSkill(SkillName.RemoveTrap, 85.0, 100.0); + } - [Constructible] - public TinkerGuildmaster() : base( "tinker" ) - { - SetSkill( SkillName.Lockpicking, 65.0, 88.0 ); - SetSkill( SkillName.Tinkering, 90.0, 100.0 ); - SetSkill( SkillName.RemoveTrap, 85.0, 100.0 ); - } + public TinkerGuildmaster(Serial serial) : base(serial) + { + } - public TinkerGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void AddCustomContextEntries( Mobile from, List list ) - { - if ( Core.ML && from.Alive ) - { - RechargeEntry entry = new RechargeEntry( from, this ); + public override void AddCustomContextEntries(Mobile from, List list) + { + if (Core.ML && from.Alive) + { + RechargeEntry entry = new RechargeEntry(from, this); - if ( WeaponEngravingTool.Find( from ) == null ) - entry.Enabled = false; + if (WeaponEngravingTool.Find(from) == null) + entry.Enabled = false; - list.Add( entry ); - } + list.Add(entry); + } - base.AddCustomContextEntries( from, list ); - } + base.AddCustomContextEntries(from, list); + } - private class RechargeEntry : ContextMenuEntry - { - private Mobile m_From; - private Mobile m_Vendor; + private class RechargeEntry : ContextMenuEntry + { + private Mobile m_From; + private Mobile m_Vendor; - public RechargeEntry( Mobile from, Mobile vendor ) : base( 6271, 6 ) - { - m_From = from; - m_Vendor = vendor; - } + public RechargeEntry(Mobile from, Mobile vendor) : base(6271, 6) + { + m_From = from; + m_Vendor = vendor; + } - public override void OnClick() - { - if ( !Core.ML || m_Vendor == null || m_Vendor.Deleted ) - return; + public override void OnClick() + { + if (!Core.ML || m_Vendor == null || m_Vendor.Deleted) + return; - WeaponEngravingTool tool = WeaponEngravingTool.Find( m_From ); + WeaponEngravingTool tool = WeaponEngravingTool.Find(m_From); - if ( tool != null && tool.UsesRemaining <= 0 ) - { - if ( Banker.GetBalance( m_From ) >= 100000 ) - m_From.SendGump( new WeaponEngravingTool.ConfirmGump( tool, m_Vendor ) ); - else - m_Vendor.Say( 1076167 ); // You need a 100,000 gold and a blue diamond to recharge the weapon engraver. - } - else - m_Vendor.Say( 1076164 ); // I can only help with this if you are carrying an engraving tool that needs repair. - } - } - } -} + if (tool != null && tool.UsesRemaining <= 0) + { + if (Banker.GetBalance(m_From) >= 100000) + m_From.SendGump(new WeaponEngravingTool.ConfirmGump(tool, m_Vendor)); + else + m_Vendor.Say(1076167); // You need a 100,000 gold and a blue diamond to recharge the weapon engraver. + } + else + { + m_Vendor.Say( + 1076164); // I can only help with this if you are carrying an engraving tool that needs repair. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Guildmasters/WarriorGuildmaster.cs b/Scripts/Mobiles/Vendors/NPC/Guildmasters/WarriorGuildmaster.cs index a8b768348..4c702d138 100644 --- a/Scripts/Mobiles/Vendors/NPC/Guildmasters/WarriorGuildmaster.cs +++ b/Scripts/Mobiles/Vendors/NPC/Guildmasters/WarriorGuildmaster.cs @@ -1,37 +1,37 @@ namespace Server.Mobiles { - public class WarriorGuildmaster : BaseGuildmaster - { - public override NpcGuild NpcGuild => NpcGuild.WarriorsGuild; + public class WarriorGuildmaster : BaseGuildmaster + { + [Constructible] + public WarriorGuildmaster() : base("warrior") + { + SetSkill(SkillName.ArmsLore, 75.0, 98.0); + SetSkill(SkillName.Parry, 85.0, 100.0); + SetSkill(SkillName.MagicResist, 60.0, 83.0); + SetSkill(SkillName.Tactics, 85.0, 100.0); + SetSkill(SkillName.Swords, 90.0, 100.0); + SetSkill(SkillName.Macing, 60.0, 83.0); + SetSkill(SkillName.Fencing, 60.0, 83.0); + } - [Constructible] - public WarriorGuildmaster() : base( "warrior" ) - { - SetSkill( SkillName.ArmsLore, 75.0, 98.0 ); - SetSkill( SkillName.Parry, 85.0, 100.0 ); - SetSkill( SkillName.MagicResist, 60.0, 83.0 ); - SetSkill( SkillName.Tactics, 85.0, 100.0 ); - SetSkill( SkillName.Swords, 90.0, 100.0 ); - SetSkill( SkillName.Macing, 60.0, 83.0 ); - SetSkill( SkillName.Fencing, 60.0, 83.0 ); - } + public WarriorGuildmaster(Serial serial) : base(serial) + { + } - public WarriorGuildmaster( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.WarriorsGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/GypsyAnimalTrainer.cs b/Scripts/Mobiles/Vendors/NPC/GypsyAnimalTrainer.cs index a456135b1..d6f371eaa 100644 --- a/Scripts/Mobiles/Vendors/NPC/GypsyAnimalTrainer.cs +++ b/Scripts/Mobiles/Vendors/NPC/GypsyAnimalTrainer.cs @@ -1,74 +1,74 @@ namespace Server.Mobiles { - public class GypsyAnimalTrainer : AnimalTrainer - { - [Constructible] - public GypsyAnimalTrainer() - { - if ( Utility.RandomBool() ) - Title = "the gypsy animal trainer"; - else - Title = "the gypsy animal herder"; - } + public class GypsyAnimalTrainer : AnimalTrainer + { + [Constructible] + public GypsyAnimalTrainer() + { + if (Utility.RandomBool()) + Title = "the gypsy animal trainer"; + else + Title = "the gypsy animal herder"; + } - public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; + public GypsyAnimalTrainer(Serial serial) : base(serial) + { + } - public override int GetShoeHue() - { - return 0; - } + public override VendorShoeType ShoeType => Female ? VendorShoeType.ThighBoots : VendorShoeType.Boots; - public override void InitOutfit() - { - base.InitOutfit(); + public override int GetShoeHue() + { + return 0; + } - Item item = FindItemOnLayer( Layer.Pants ); + public override void InitOutfit() + { + base.InitOutfit(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + Item item = FindItemOnLayer(Layer.Pants); - item = FindItemOnLayer( Layer.OuterLegs ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.OuterLegs); - item = FindItemOnLayer( Layer.InnerLegs ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.InnerLegs); - item = FindItemOnLayer( Layer.OuterTorso ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.OuterTorso); - item = FindItemOnLayer( Layer.InnerTorso ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.InnerTorso); - item = FindItemOnLayer( Layer.Shirt ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); - } + item = FindItemOnLayer(Layer.Shirt); - public GypsyAnimalTrainer( Serial serial ) : base( serial ) - { - } + if (item != null) + item.Hue = Utility.RandomBrightHue(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/GypsyBanker.cs b/Scripts/Mobiles/Vendors/NPC/GypsyBanker.cs index a010d5784..a5a6c7f2d 100644 --- a/Scripts/Mobiles/Vendors/NPC/GypsyBanker.cs +++ b/Scripts/Mobiles/Vendors/NPC/GypsyBanker.cs @@ -2,81 +2,87 @@ using Server.Items; namespace Server.Mobiles { - public class GypsyBanker : Banker - { - public override bool IsActiveVendor => false; - public override NpcGuild NpcGuild => NpcGuild.None; - public override bool ClickTitle => false; + public class GypsyBanker : Banker + { + [Constructible] + public GypsyBanker() + { + Title = "the gypsy banker"; + } - [Constructible] - public GypsyBanker() - { - Title = "the gypsy banker"; - } + public GypsyBanker(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + public override bool IsActiveVendor => false; + public override NpcGuild NpcGuild => NpcGuild.None; + public override bool ClickTitle => false; - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new JesterHat( Utility.RandomBrightHue() ) ); break; - case 1: AddItem( new Bandana( Utility.RandomBrightHue() ) ); break; - case 2: AddItem( new SkullCap( Utility.RandomBrightHue() ) ); break; - } + public override void InitOutfit() + { + base.InitOutfit(); - Item item = FindItemOnLayer( Layer.Pants ); + switch (Utility.Random(4)) + { + case 0: + AddItem(new JesterHat(Utility.RandomBrightHue())); + break; + case 1: + AddItem(new Bandana(Utility.RandomBrightHue())); + break; + case 2: + AddItem(new SkullCap(Utility.RandomBrightHue())); + break; + } - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + Item item = FindItemOnLayer(Layer.Pants); - item = FindItemOnLayer( Layer.Shoes ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.Shoes); - item = FindItemOnLayer( Layer.OuterLegs ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.OuterLegs); - item = FindItemOnLayer( Layer.InnerLegs ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.InnerLegs); - item = FindItemOnLayer( Layer.OuterTorso ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.OuterTorso); - item = FindItemOnLayer( Layer.InnerTorso ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + item = FindItemOnLayer(Layer.InnerTorso); - item = FindItemOnLayer( Layer.Shirt ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); - } + item = FindItemOnLayer(Layer.Shirt); - public GypsyBanker( Serial serial ) : base( serial ) - { - } + if (item != null) + item.Hue = Utility.RandomBrightHue(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/GypsyMaiden.cs b/Scripts/Mobiles/Vendors/NPC/GypsyMaiden.cs index 5efb26b11..2ade6fa42 100644 --- a/Scripts/Mobiles/Vendors/NPC/GypsyMaiden.cs +++ b/Scripts/Mobiles/Vendors/NPC/GypsyMaiden.cs @@ -3,72 +3,79 @@ using Server.Items; namespace Server.Mobiles { - public class GypsyMaiden : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class GypsyMaiden : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public GypsyMaiden() : base( "the gypsy maiden" ) - { - } + [Constructible] + public GypsyMaiden() : base("the gypsy maiden") + { + } - public override bool GetGender() - { - return true; // always female - } + public GypsyMaiden(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBProvisioner() ); - } + protected override List SBInfos => m_SBInfos; - public override void InitOutfit() - { - base.InitOutfit(); + public override bool GetGender() + { + return true; // always female + } - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new JesterHat( Utility.RandomBrightHue() ) ); break; - case 1: AddItem( new Bandana( Utility.RandomBrightHue() ) ); break; - case 2: AddItem( new SkullCap( Utility.RandomBrightHue() ) ); break; - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBProvisioner()); + } - if ( Utility.RandomBool() ) - AddItem( new HalfApron( Utility.RandomBrightHue() ) ); + public override void InitOutfit() + { + base.InitOutfit(); - Item item = FindItemOnLayer( Layer.Pants ); + switch (Utility.Random(4)) + { + case 0: + AddItem(new JesterHat(Utility.RandomBrightHue())); + break; + case 1: + AddItem(new Bandana(Utility.RandomBrightHue())); + break; + case 2: + AddItem(new SkullCap(Utility.RandomBrightHue())); + break; + } - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + if (Utility.RandomBool()) + AddItem(new HalfApron(Utility.RandomBrightHue())); - item = FindItemOnLayer( Layer.OuterLegs ); + Item item = FindItemOnLayer(Layer.Pants); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - item = FindItemOnLayer( Layer.InnerLegs ); + item = FindItemOnLayer(Layer.OuterLegs); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); - } + if (item != null) + item.Hue = Utility.RandomBrightHue(); - public GypsyMaiden( Serial serial ) : base( serial ) - { - } + item = FindItemOnLayer(Layer.InnerLegs); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/HairStylist.cs b/Scripts/Mobiles/Vendors/NPC/HairStylist.cs index a09ede1ac..541552449 100644 --- a/Scripts/Mobiles/Vendors/NPC/HairStylist.cs +++ b/Scripts/Mobiles/Vendors/NPC/HairStylist.cs @@ -1,41 +1,42 @@ using System.Collections.Generic; -namespace Server.Mobiles -{ - public class HairStylist : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class HairStylist : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public HairStylist() : base( "the hair stylist" ) - { - SetSkill( SkillName.Alchemy, 80.0, 100.0 ); - SetSkill( SkillName.Magery, 90.0, 110.0 ); - SetSkill( SkillName.TasteID, 85.0, 100.0 ); - } + [Constructible] + public HairStylist() : base("the hair stylist") + { + SetSkill(SkillName.Alchemy, 80.0, 100.0); + SetSkill(SkillName.Magery, 90.0, 110.0); + SetSkill(SkillName.TasteID, 85.0, 100.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBHairStylist() ); - } + public HairStylist(Serial serial) : base(serial) + { + } - public HairStylist( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBHairStylist()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Herbalist.cs b/Scripts/Mobiles/Vendors/NPC/Herbalist.cs index 211423e75..106f445b9 100644 --- a/Scripts/Mobiles/Vendors/NPC/Herbalist.cs +++ b/Scripts/Mobiles/Vendors/NPC/Herbalist.cs @@ -2,44 +2,45 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Herbalist : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Herbalist : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.MagesGuild; + [Constructible] + public Herbalist() : base("the herbalist") + { + SetSkill(SkillName.Alchemy, 80.0, 100.0); + SetSkill(SkillName.Cooking, 80.0, 100.0); + SetSkill(SkillName.TasteID, 80.0, 100.0); + } - [Constructible] - public Herbalist() : base( "the herbalist" ) - { - SetSkill( SkillName.Alchemy, 80.0, 100.0 ); - SetSkill( SkillName.Cooking, 80.0, 100.0 ); - SetSkill( SkillName.TasteID, 80.0, 100.0 ); - } + public Herbalist(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBHerbalist() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.MagesGuild; - public Herbalist( Serial serial ) : base( serial ) - { - } + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBHerbalist()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/HolyMage.cs b/Scripts/Mobiles/Vendors/NPC/HolyMage.cs index 831a21f7b..0fbd202ae 100644 --- a/Scripts/Mobiles/Vendors/NPC/HolyMage.cs +++ b/Scripts/Mobiles/Vendors/NPC/HolyMage.cs @@ -3,78 +3,83 @@ using Server.Items; namespace Server.Mobiles { - public class HolyMage : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class HolyMage : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public HolyMage() : base( "the Holy Mage" ) - { - SetSkill( SkillName.EvalInt, 65.0, 88.0 ); - SetSkill( SkillName.Inscribe, 60.0, 83.0 ); - SetSkill( SkillName.Magery, 64.0, 100.0 ); - SetSkill( SkillName.Meditation, 60.0, 83.0 ); - SetSkill( SkillName.MagicResist, 65.0, 88.0 ); - SetSkill( SkillName.Wrestling, 36.0, 68.0 ); - } + [Constructible] + public HolyMage() : base("the Holy Mage") + { + SetSkill(SkillName.EvalInt, 65.0, 88.0); + SetSkill(SkillName.Inscribe, 60.0, 83.0); + SetSkill(SkillName.Magery, 64.0, 100.0); + SetSkill(SkillName.Meditation, 60.0, 83.0); + SetSkill(SkillName.MagicResist, 65.0, 88.0); + SetSkill(SkillName.Wrestling, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBHolyMage() ); - } + public HolyMage(Serial serial) : base(serial) + { + } - public Item ApplyHue( Item item, int hue ) - { - item.Hue = hue; + protected override List SBInfos => m_SBInfos; - return item; - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBHolyMage()); + } - public override void InitOutfit() - { - AddItem( ApplyHue( new Robe(), 0x47E ) ); - AddItem( ApplyHue( new ThighBoots(), 0x47E ) ); - AddItem( ApplyHue( new BlackStaff(), 0x47E ) ); + public Item ApplyHue(Item item, int hue) + { + item.Hue = hue; - if ( Female ) - { - AddItem( ApplyHue( new LeatherGloves(), 0x47E ) ); - AddItem( ApplyHue( new GoldNecklace(), 0x47E ) ); - } - else - { - AddItem( ApplyHue( new PlateGloves(), 0x47E ) ); - AddItem( ApplyHue( new PlateGorget(), 0x47E ) ); - } + return item; + } - switch ( Utility.Random( Female ? 2 : 1 ) ) - { - case 0: HairItemID = 0x203C; break; - case 1: HairItemID = 0x203D; break; - } + public override void InitOutfit() + { + AddItem(ApplyHue(new Robe(), 0x47E)); + AddItem(ApplyHue(new ThighBoots(), 0x47E)); + AddItem(ApplyHue(new BlackStaff(), 0x47E)); - HairHue = 0x47E; + if (Female) + { + AddItem(ApplyHue(new LeatherGloves(), 0x47E)); + AddItem(ApplyHue(new GoldNecklace(), 0x47E)); + } + else + { + AddItem(ApplyHue(new PlateGloves(), 0x47E)); + AddItem(ApplyHue(new PlateGorget(), 0x47E)); + } - PackGold( 100, 200 ); - } + switch (Utility.Random(Female ? 2 : 1)) + { + case 0: + HairItemID = 0x203C; + break; + case 1: + HairItemID = 0x203D; + break; + } - public HolyMage( Serial serial ) : base( serial ) - { - } + HairHue = 0x47E; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + PackGold(100, 200); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/InnKeeper.cs b/Scripts/Mobiles/Vendors/NPC/InnKeeper.cs index 0918970cb..981dcb56a 100644 --- a/Scripts/Mobiles/Vendors/NPC/InnKeeper.cs +++ b/Scripts/Mobiles/Vendors/NPC/InnKeeper.cs @@ -1,43 +1,44 @@ using System.Collections.Generic; -namespace Server.Mobiles -{ - public class InnKeeper : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class InnKeeper : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public InnKeeper() : base( "the innkeeper" ) - { - } + [Constructible] + public InnKeeper() : base("the innkeeper") + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBInnKeeper() ); - - if ( IsTokunoVendor ) - m_SBInfos.Add( new SBSEFood() ); - } + public InnKeeper(Serial serial) : base(serial) + { + } - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; + protected override List SBInfos => m_SBInfos; - public InnKeeper( Serial serial ) : base( serial ) - { - } + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBInnKeeper()); - writer.Write( (int) 0 ); // version - } + if (IsTokunoVendor) + m_SBInfos.Add(new SBSEFood()); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int version = reader.ReadInt(); - } - } + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/IronWorker.cs b/Scripts/Mobiles/Vendors/NPC/IronWorker.cs index e6d55e00a..3fa98fcd2 100644 --- a/Scripts/Mobiles/Vendors/NPC/IronWorker.cs +++ b/Scripts/Mobiles/Vendors/NPC/IronWorker.cs @@ -3,117 +3,122 @@ using Server.Items; namespace Server.Mobiles { - public class IronWorker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class IronWorker : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public IronWorker() : base( "the iron worker" ) - { - SetSkill( SkillName.ArmsLore, 36.0, 68.0 ); - SetSkill( SkillName.Blacksmith, 65.0, 88.0 ); - SetSkill( SkillName.Fencing, 60.0, 83.0 ); - SetSkill( SkillName.Macing, 61.0, 93.0 ); - SetSkill( SkillName.Swords, 60.0, 83.0 ); - SetSkill( SkillName.Tactics, 60.0, 83.0 ); - SetSkill( SkillName.Parry, 61.0, 93.0 ); - } + [Constructible] + public IronWorker() : base("the iron worker") + { + SetSkill(SkillName.ArmsLore, 36.0, 68.0); + SetSkill(SkillName.Blacksmith, 65.0, 88.0); + SetSkill(SkillName.Fencing, 60.0, 83.0); + SetSkill(SkillName.Macing, 61.0, 93.0); + SetSkill(SkillName.Swords, 60.0, 83.0); + SetSkill(SkillName.Tactics, 60.0, 83.0); + SetSkill(SkillName.Parry, 61.0, 93.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBAxeWeapon() ); - m_SBInfos.Add( new SBKnifeWeapon() ); - m_SBInfos.Add( new SBMaceWeapon() ); - m_SBInfos.Add( new SBSmithTools() ); - m_SBInfos.Add( new SBPoleArmWeapon() ); - m_SBInfos.Add( new SBSpearForkWeapon() ); - m_SBInfos.Add( new SBSwordWeapon() ); + public IronWorker(Serial serial) : base(serial) + { + } - m_SBInfos.Add( new SBMetalShields() ); + protected override List SBInfos => m_SBInfos; - m_SBInfos.Add( new SBHelmetArmor() ); - m_SBInfos.Add( new SBPlateArmor() ); - m_SBInfos.Add( new SBChainmailArmor() ); - m_SBInfos.Add( new SBRingmailArmor() ); - m_SBInfos.Add( new SBStuddedArmor() ); - m_SBInfos.Add( new SBLeatherArmor() ); - } + public override VendorShoeType ShoeType => VendorShoeType.None; - public override VendorShoeType ShoeType => VendorShoeType.None; + public override void InitSBInfo() + { + m_SBInfos.Add(new SBAxeWeapon()); + m_SBInfos.Add(new SBKnifeWeapon()); + m_SBInfos.Add(new SBMaceWeapon()); + m_SBInfos.Add(new SBSmithTools()); + m_SBInfos.Add(new SBPoleArmWeapon()); + m_SBInfos.Add(new SBSpearForkWeapon()); + m_SBInfos.Add(new SBSwordWeapon()); - public override void InitOutfit() - { - base.InitOutfit(); + m_SBInfos.Add(new SBMetalShields()); - Item item = ( Utility.RandomBool() ? null : new RingmailChest() ); + m_SBInfos.Add(new SBHelmetArmor()); + m_SBInfos.Add(new SBPlateArmor()); + m_SBInfos.Add(new SBChainmailArmor()); + m_SBInfos.Add(new SBRingmailArmor()); + m_SBInfos.Add(new SBStuddedArmor()); + m_SBInfos.Add(new SBLeatherArmor()); + } - if ( item != null && !EquipItem( item ) ) - { - item.Delete(); - item = null; - } + public override void InitOutfit() + { + base.InitOutfit(); - switch ( Utility.Random( 3 ) ) - { - case 0: - case 1: AddItem( new JesterHat( Utility.RandomBrightHue() ) ); break; - case 2: AddItem( new Bandana( Utility.RandomBrightHue() ) ); break; - } + Item item = Utility.RandomBool() ? null : new RingmailChest(); - if ( item == null ) - AddItem( new FullApron( Utility.RandomBrightHue() ) ); + if (item != null && !EquipItem(item)) + { + item.Delete(); + item = null; + } - AddItem( new Bascinet() ); - AddItem( new SmithHammer() ); + switch (Utility.Random(3)) + { + case 0: + case 1: + AddItem(new JesterHat(Utility.RandomBrightHue())); + break; + case 2: + AddItem(new Bandana(Utility.RandomBrightHue())); + break; + } - item = FindItemOnLayer( Layer.Pants ); + if (item == null) + AddItem(new FullApron(Utility.RandomBrightHue())); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + AddItem(new Bascinet()); + AddItem(new SmithHammer()); - item = FindItemOnLayer( Layer.OuterLegs ); + item = FindItemOnLayer(Layer.Pants); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - item = FindItemOnLayer( Layer.InnerLegs ); + item = FindItemOnLayer(Layer.OuterLegs); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - item = FindItemOnLayer( Layer.OuterTorso ); + item = FindItemOnLayer(Layer.InnerLegs); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - item = FindItemOnLayer( Layer.InnerTorso ); + item = FindItemOnLayer(Layer.OuterTorso); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); + if (item != null) + item.Hue = Utility.RandomBrightHue(); - item = FindItemOnLayer( Layer.Shirt ); + item = FindItemOnLayer(Layer.InnerTorso); - if ( item != null ) - item.Hue = Utility.RandomBrightHue(); - } + if (item != null) + item.Hue = Utility.RandomBrightHue(); - public IronWorker( Serial serial ) : base( serial ) - { - } + item = FindItemOnLayer(Layer.Shirt); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (item != null) + item.Hue = Utility.RandomBrightHue(); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Jeweler.cs b/Scripts/Mobiles/Vendors/NPC/Jeweler.cs index 766ffcf79..bc1f337fc 100644 --- a/Scripts/Mobiles/Vendors/NPC/Jeweler.cs +++ b/Scripts/Mobiles/Vendors/NPC/Jeweler.cs @@ -2,38 +2,39 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Jeweler : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Jeweler : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Jeweler() : base( "the jeweler" ) - { - SetSkill( SkillName.ItemID, 64.0, 100.0 ); - } + [Constructible] + public Jeweler() : base("the jeweler") + { + SetSkill(SkillName.ItemID, 64.0, 100.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBJewel() ); - } + public Jeweler(Serial serial) : base(serial) + { + } - public Jeweler( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBJewel()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/KeeperOfChivalry.cs b/Scripts/Mobiles/Vendors/NPC/KeeperOfChivalry.cs index 4b3feee63..cd0bf8e3c 100644 --- a/Scripts/Mobiles/Vendors/NPC/KeeperOfChivalry.cs +++ b/Scripts/Mobiles/Vendors/NPC/KeeperOfChivalry.cs @@ -3,81 +3,100 @@ using Server.Items; namespace Server.Mobiles { - public class KeeperOfChivalry : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class KeeperOfChivalry : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public KeeperOfChivalry() : base( "the Keeper of Chivalry" ) - { - SetSkill( SkillName.Fencing, 75.0, 85.0 ); - SetSkill( SkillName.Macing, 75.0, 85.0 ); - SetSkill( SkillName.Swords, 75.0, 85.0 ); - SetSkill( SkillName.Chivalry, 100.0 ); - } + [Constructible] + public KeeperOfChivalry() : base("the Keeper of Chivalry") + { + SetSkill(SkillName.Fencing, 75.0, 85.0); + SetSkill(SkillName.Macing, 75.0, 85.0); + SetSkill(SkillName.Swords, 75.0, 85.0); + SetSkill(SkillName.Chivalry, 100.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBKeeperOfChivalry() ); - } + public KeeperOfChivalry(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - AddItem( new PlateArms() ); - AddItem( new PlateChest() ); - AddItem( new PlateGloves() ); - AddItem( new StuddedGorget() ); - AddItem( new PlateLegs() ); + protected override List SBInfos => m_SBInfos; - switch ( Utility.Random( 4 ) ) - { - case 0: AddItem( new PlateHelm() ); break; - case 1: AddItem( new NorseHelm() ); break; - case 2: AddItem( new CloseHelm() ); break; - case 3: AddItem( new Helmet() ); break; - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBKeeperOfChivalry()); + } - switch ( Utility.Random( 3 ) ) - { - case 0: AddItem( new BodySash( 0x482 ) ); break; - case 1: AddItem( new Doublet( 0x482 ) ); break; - case 2: AddItem( new Tunic( 0x482 ) ); break; - } + public override void InitOutfit() + { + AddItem(new PlateArms()); + AddItem(new PlateChest()); + AddItem(new PlateGloves()); + AddItem(new StuddedGorget()); + AddItem(new PlateLegs()); - AddItem( new Broadsword() ); + switch (Utility.Random(4)) + { + case 0: + AddItem(new PlateHelm()); + break; + case 1: + AddItem(new NorseHelm()); + break; + case 2: + AddItem(new CloseHelm()); + break; + case 3: + AddItem(new Helmet()); + break; + } - Item shield = new MetalKiteShield(); + switch (Utility.Random(3)) + { + case 0: + AddItem(new BodySash(0x482)); + break; + case 1: + AddItem(new Doublet(0x482)); + break; + case 2: + AddItem(new Tunic(0x482)); + break; + } - shield.Hue = Utility.RandomNondyedHue(); + AddItem(new Broadsword()); - AddItem( shield ); + Item shield = new MetalKiteShield(); - switch ( Utility.Random( 2 ) ) - { - case 0: AddItem( new Boots() ); break; - case 1: AddItem( new ThighBoots() ); break; - } + shield.Hue = Utility.RandomNondyedHue(); - PackGold( 100, 200 ); - } + AddItem(shield); - public KeeperOfChivalry( Serial serial ) : base( serial ) - { - } + switch (Utility.Random(2)) + { + case 0: + AddItem(new Boots()); + break; + case 1: + AddItem(new ThighBoots()); + break; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + PackGold(100, 200); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/LeatherWorker.cs b/Scripts/Mobiles/Vendors/NPC/LeatherWorker.cs index 72f4858a0..a145bf469 100644 --- a/Scripts/Mobiles/Vendors/NPC/LeatherWorker.cs +++ b/Scripts/Mobiles/Vendors/NPC/LeatherWorker.cs @@ -1,38 +1,41 @@ using System.Collections.Generic; -namespace Server.Mobiles -{ - public class LeatherWorker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class LeatherWorker : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public LeatherWorker() : base( "the leather worker" ) - { - } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBLeatherArmor() ); - m_SBInfos.Add( new SBStuddedArmor() ); - m_SBInfos.Add( new SBLeatherWorker() ); - } - public LeatherWorker( Serial serial ) : base( serial ) - { - } + [Constructible] + public LeatherWorker() : base("the leather worker") + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public LeatherWorker(Serial serial) : base(serial) + { + } - writer.Write( (int) 0 ); // version - } + protected override List SBInfos => m_SBInfos; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBLeatherArmor()); + m_SBInfos.Add(new SBStuddedArmor()); + m_SBInfos.Add(new SBLeatherWorker()); + } - int version = reader.ReadInt(); - } - } -} + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Mage.cs b/Scripts/Mobiles/Vendors/NPC/Mage.cs index 3616a75ec..003815594 100644 --- a/Scripts/Mobiles/Vendors/NPC/Mage.cs +++ b/Scripts/Mobiles/Vendors/NPC/Mage.cs @@ -1,55 +1,57 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Mage : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Mage : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.MagesGuild; + [Constructible] + public Mage() : base("the mage") + { + SetSkill(SkillName.EvalInt, 65.0, 88.0); + SetSkill(SkillName.Inscribe, 60.0, 83.0); + SetSkill(SkillName.Magery, 64.0, 100.0); + SetSkill(SkillName.Meditation, 60.0, 83.0); + SetSkill(SkillName.MagicResist, 65.0, 88.0); + SetSkill(SkillName.Wrestling, 36.0, 68.0); + } - [Constructible] - public Mage() : base( "the mage" ) - { - SetSkill( SkillName.EvalInt, 65.0, 88.0 ); - SetSkill( SkillName.Inscribe, 60.0, 83.0 ); - SetSkill( SkillName.Magery, 64.0, 100.0 ); - SetSkill( SkillName.Meditation, 60.0, 83.0 ); - SetSkill( SkillName.MagicResist, 65.0, 88.0 ); - SetSkill( SkillName.Wrestling, 36.0, 68.0 ); - } + public Mage(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBMage() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.MagesGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - AddItem( new Items.Robe( Utility.RandomBlueHue() ) ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBMage()); + } - public Mage( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new Robe(Utility.RandomBlueHue())); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Mapmaker.cs b/Scripts/Mobiles/Vendors/NPC/Mapmaker.cs index e3369142a..18c36f28f 100644 --- a/Scripts/Mobiles/Vendors/NPC/Mapmaker.cs +++ b/Scripts/Mobiles/Vendors/NPC/Mapmaker.cs @@ -2,38 +2,39 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Mapmaker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Mapmaker : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Mapmaker() : base( "the mapmaker" ) - { - SetSkill( SkillName.Cartography, 90.0, 100.0 ); - } + [Constructible] + public Mapmaker() : base("the mapmaker") + { + SetSkill(SkillName.Cartography, 90.0, 100.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBMapmaker() ); - } + public Mapmaker(Serial serial) : base(serial) + { + } - public Mapmaker( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBMapmaker()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Miller.cs b/Scripts/Mobiles/Vendors/NPC/Miller.cs index b9239d827..e313f01d8 100644 --- a/Scripts/Mobiles/Vendors/NPC/Miller.cs +++ b/Scripts/Mobiles/Vendors/NPC/Miller.cs @@ -2,38 +2,38 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Miller : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Miller : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Miller() : base( "the miller" ) - { - - } + [Constructible] + public Miller() : base("the miller") + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBMiller() ); - } + public Miller(Serial serial) : base(serial) + { + } - public Miller( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBMiller()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Miner.cs b/Scripts/Mobiles/Vendors/NPC/Miner.cs index 750638b04..254ca14ec 100644 --- a/Scripts/Mobiles/Vendors/NPC/Miner.cs +++ b/Scripts/Mobiles/Vendors/NPC/Miner.cs @@ -1,49 +1,51 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Miner : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Miner : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Miner() : base( "the miner" ) - { - SetSkill( SkillName.Mining, 65.0, 88.0 ); - } + [Constructible] + public Miner() : base("the miner") + { + SetSkill(SkillName.Mining, 65.0, 88.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBMiner() ); - } + public Miner(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.FancyShirt( 0x3E4 ) ); - AddItem( new Items.LongPants( 0x192 ) ); - AddItem( new Items.Pickaxe() ); - AddItem( new Items.ThighBoots( 0x283 ) ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBMiner()); + } - public Miner( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new FancyShirt(0x3E4)); + AddItem(new LongPants(0x192)); + AddItem(new Pickaxe()); + AddItem(new ThighBoots(0x283)); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Monk.cs b/Scripts/Mobiles/Vendors/NPC/Monk.cs index 5abb802ca..87042653a 100644 --- a/Scripts/Mobiles/Vendors/NPC/Monk.cs +++ b/Scripts/Mobiles/Vendors/NPC/Monk.cs @@ -3,48 +3,49 @@ using Server.Items; namespace Server.Mobiles { - public class Monk : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Monk : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Monk() : base( "the Monk" ) - { - SetSkill( SkillName.EvalInt, 100.0 ); - SetSkill( SkillName.Tactics, 70.0, 90.0 ); - SetSkill( SkillName.Wrestling, 70.0, 90.0 ); - SetSkill( SkillName.MagicResist, 70.0, 90.0 ); - SetSkill( SkillName.Macing, 70.0, 90.0 ); - } - - public override void InitSBInfo() - { - m_SBInfos.Add( new SBMonk() ); - } - public override void InitOutfit() - { - AddItem( new Sandals() ); - AddItem( new MonkRobe() ); - } + [Constructible] + public Monk() : base("the Monk") + { + SetSkill(SkillName.EvalInt, 100.0); + SetSkill(SkillName.Tactics, 70.0, 90.0); + SetSkill(SkillName.Wrestling, 70.0, 90.0); + SetSkill(SkillName.MagicResist, 70.0, 90.0); + SetSkill(SkillName.Macing, 70.0, 90.0); + } - public Monk( Serial serial ) : base( serial ) - { - } + public Monk(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + protected override List SBInfos => m_SBInfos; - writer.Write( (int) 0 ); // version - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBMonk()); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void InitOutfit() + { + AddItem(new Sandals()); + AddItem(new MonkRobe()); + } - int version = reader.ReadInt(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - } -} + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Provisioner.cs b/Scripts/Mobiles/Vendors/NPC/Provisioner.cs index aca28c914..0aca41e37 100644 --- a/Scripts/Mobiles/Vendors/NPC/Provisioner.cs +++ b/Scripts/Mobiles/Vendors/NPC/Provisioner.cs @@ -2,42 +2,43 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Provisioner : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Provisioner : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Provisioner() : base( "the provisioner" ) - { - SetSkill( SkillName.Camping, 45.0, 68.0 ); - SetSkill( SkillName.Tactics, 45.0, 68.0 ); - } + [Constructible] + public Provisioner() : base("the provisioner") + { + SetSkill(SkillName.Camping, 45.0, 68.0); + SetSkill(SkillName.Tactics, 45.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBProvisioner() ); + public Provisioner(Serial serial) : base(serial) + { + } - if ( IsTokunoVendor ) - m_SBInfos.Add( new SBSEHats() ); - } + protected override List SBInfos => m_SBInfos; - public Provisioner( Serial serial ) : base( serial ) - { - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBProvisioner()); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (IsTokunoVendor) + m_SBInfos.Add(new SBSEHats()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Rancher.cs b/Scripts/Mobiles/Vendors/NPC/Rancher.cs index 88a8981c0..64f0d1ab1 100644 --- a/Scripts/Mobiles/Vendors/NPC/Rancher.cs +++ b/Scripts/Mobiles/Vendors/NPC/Rancher.cs @@ -2,41 +2,42 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Rancher : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Rancher : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Rancher() : base( "the rancher" ) - { - SetSkill( SkillName.AnimalLore, 55.0, 78.0 ); - SetSkill( SkillName.AnimalTaming, 55.0, 78.0 ); - SetSkill( SkillName.Herding, 64.0, 100.0 ); - SetSkill( SkillName.Veterinary, 60.0, 83.0 ); - } + [Constructible] + public Rancher() : base("the rancher") + { + SetSkill(SkillName.AnimalLore, 55.0, 78.0); + SetSkill(SkillName.AnimalTaming, 55.0, 78.0); + SetSkill(SkillName.Herding, 64.0, 100.0); + SetSkill(SkillName.Veterinary, 60.0, 83.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBRancher() ); - } + public Rancher(Serial serial) : base(serial) + { + } - public Rancher( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBRancher()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Ranger.cs b/Scripts/Mobiles/Vendors/NPC/Ranger.cs index 0f77360d2..c449575ee 100644 --- a/Scripts/Mobiles/Vendors/NPC/Ranger.cs +++ b/Scripts/Mobiles/Vendors/NPC/Ranger.cs @@ -1,54 +1,56 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Ranger : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Ranger : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Ranger() : base( "the ranger" ) - { - SetSkill( SkillName.Camping, 55.0, 78.0 ); - SetSkill( SkillName.DetectHidden, 65.0, 88.0 ); - SetSkill( SkillName.Hiding, 45.0, 68.0 ); - SetSkill( SkillName.Archery, 65.0, 88.0 ); - SetSkill( SkillName.Tracking, 65.0, 88.0 ); - SetSkill( SkillName.Veterinary, 60.0, 83.0 ); - } + [Constructible] + public Ranger() : base("the ranger") + { + SetSkill(SkillName.Camping, 55.0, 78.0); + SetSkill(SkillName.DetectHidden, 65.0, 88.0); + SetSkill(SkillName.Hiding, 45.0, 68.0); + SetSkill(SkillName.Archery, 65.0, 88.0); + SetSkill(SkillName.Tracking, 65.0, 88.0); + SetSkill(SkillName.Veterinary, 60.0, 83.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBRanger() ); - } + public Ranger(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.Shirt( Utility.RandomNeutralHue() ) ); - AddItem( new Items.LongPants( Utility.RandomNeutralHue() ) ); - AddItem( new Items.Bow() ); - AddItem( new Items.ThighBoots( Utility.RandomNeutralHue() ) ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBRanger()); + } - public Ranger( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new Shirt(Utility.RandomNeutralHue())); + AddItem(new LongPants(Utility.RandomNeutralHue())); + AddItem(new Bow()); + AddItem(new ThighBoots(Utility.RandomNeutralHue())); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/RealEstateBroker.cs b/Scripts/Mobiles/Vendors/NPC/RealEstateBroker.cs index 70723af5f..a988e1b08 100644 --- a/Scripts/Mobiles/Vendors/NPC/RealEstateBroker.cs +++ b/Scripts/Mobiles/Vendors/NPC/RealEstateBroker.cs @@ -2,180 +2,183 @@ using System; using System.Collections.Generic; using Server.Items; using Server.Multis.Deeds; -using Server.Targeting; using Server.Network; +using Server.Targeting; namespace Server.Mobiles { - public class RealEstateBroker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class RealEstateBroker : BaseVendor + { + private DateTime m_NextCheckPack; + private List m_SBInfos = new List(); - [Constructible] - public RealEstateBroker() : base( "the real estate broker" ) - { - } + [Constructible] + public RealEstateBroker() : base("the real estate broker") + { + } - public override bool HandlesOnSpeech( Mobile from ) - { - if ( from.Alive && from.InRange( this, 3 ) ) - return true; + public RealEstateBroker(Serial serial) : base(serial) + { + } - return base.HandlesOnSpeech( from ); - } + protected override List SBInfos => m_SBInfos; - private DateTime m_NextCheckPack; + public override bool HandlesOnSpeech(Mobile from) + { + if (from.Alive && from.InRange(this, 3)) + return true; - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - if ( DateTime.UtcNow > m_NextCheckPack && InRange( m, 4 ) && !InRange( oldLocation, 4 ) && m.Player ) - { - Container pack = m.Backpack; + return base.HandlesOnSpeech(from); + } - if ( pack != null ) - { - m_NextCheckPack = DateTime.UtcNow + TimeSpan.FromSeconds( 2.0 ); + public override void OnMovement(Mobile m, Point3D oldLocation) + { + if (DateTime.UtcNow > m_NextCheckPack && InRange(m, 4) && !InRange(oldLocation, 4) && m.Player) + { + Container pack = m.Backpack; - Item deed = pack.FindItemByType( typeof( HouseDeed ), false ); + if (pack != null) + { + m_NextCheckPack = DateTime.UtcNow + TimeSpan.FromSeconds(2.0); - if ( deed != null ) - { - // If you have a deed, I can appraise it or buy it from you... - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500605, m.NetState ); + Item deed = pack.FindItemByType(typeof(HouseDeed), false); - // Simply hand me a deed to sell it. - PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500606, m.NetState ); - } - } - } + if (deed != null) + { + // If you have a deed, I can appraise it or buy it from you... + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500605, m.NetState); - base.OnMovement( m, oldLocation ); - } + // Simply hand me a deed to sell it. + PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500606, m.NetState); + } + } + } - public override void OnSpeech( SpeechEventArgs e ) - { - if ( !e.Handled && e.Mobile.Alive && e.HasKeyword( 0x38 ) ) // *appraise* - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500608 ); // Which deed would you like appraised? - e.Mobile.BeginTarget( 12, false, TargetFlags.None, Appraise_OnTarget ); - e.Handled = true; - } + base.OnMovement(m, oldLocation); + } - base.OnSpeech( e ); - } + public override void OnSpeech(SpeechEventArgs e) + { + if (!e.Handled && e.Mobile.Alive && e.HasKeyword(0x38)) // *appraise* + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 500608); // Which deed would you like appraised? + e.Mobile.BeginTarget(12, false, TargetFlags.None, Appraise_OnTarget); + e.Handled = true; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is HouseDeed ) - { - HouseDeed deed = (HouseDeed)dropped; - int price = ComputePriceFor( deed ); + base.OnSpeech(e); + } - if ( price > 0 ) - { - if ( Banker.Deposit( from, price ) ) - { - // For the deed I have placed gold in your bankbox : - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1008000, AffixType.Append, price.ToString(), "" ); + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is HouseDeed) + { + HouseDeed deed = (HouseDeed)dropped; + int price = ComputePriceFor(deed); - deed.Delete(); - return true; - } + if (price > 0) + { + if (Banker.Deposit(from, price)) + { + // For the deed I have placed gold in your bankbox : + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1008000, AffixType.Append, price.ToString(), ""); - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500390 ); // Your bank box is full. - return false; - } + deed.Delete(); + return true; + } - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500607 ); // I'm not interested in that. - return false; - } + PublicOverheadMessage(MessageType.Regular, 0x3B2, 500390); // Your bank box is full. + return false; + } - return base.OnDragDrop (from, dropped); - } + PublicOverheadMessage(MessageType.Regular, 0x3B2, 500607); // I'm not interested in that. + return false; + } - public void Appraise_OnTarget( Mobile from, object obj ) - { - if ( obj is HouseDeed ) - { - HouseDeed deed = (HouseDeed)obj; - int price = ComputePriceFor( deed ); + return base.OnDragDrop(from, dropped); + } - if ( price > 0 ) - { - // I will pay you gold for this deed : - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1008001, AffixType.Append, price.ToString(), "" ); + public void Appraise_OnTarget(Mobile from, object obj) + { + if (obj is HouseDeed) + { + HouseDeed deed = (HouseDeed)obj; + int price = ComputePriceFor(deed); - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500610 ); // Simply hand me the deed if you wish to sell it. - } - else - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500607 ); // I'm not interested in that. - } - } - else - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 500609 ); // I can't appraise things I know nothing about... - } - } + if (price > 0) + { + // I will pay you gold for this deed : + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1008001, AffixType.Append, price.ToString(), ""); - public int ComputePriceFor( HouseDeed deed ) - { - int price = 0; + PublicOverheadMessage(MessageType.Regular, 0x3B2, + 500610); // Simply hand me the deed if you wish to sell it. + } + else + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 500607); // I'm not interested in that. + } + } + else + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 500609); // I can't appraise things I know nothing about... + } + } - if ( deed is SmallBrickHouseDeed || deed is StonePlasterHouseDeed || deed is FieldStoneHouseDeed || deed is SmallBrickHouseDeed || deed is WoodHouseDeed || deed is WoodPlasterHouseDeed || deed is ThatchedRoofCottageDeed ) - price = 43800; - else if ( deed is BrickHouseDeed ) - price = 144500; - else if ( deed is TwoStoryWoodPlasterHouseDeed || deed is TwoStoryStonePlasterHouseDeed ) - price = 192400; - else if ( deed is TowerDeed ) - price = 433200; - else if ( deed is KeepDeed ) - price = 665200; - else if ( deed is CastleDeed ) - price = 1022800; - else if ( deed is LargePatioDeed ) - price = 152800; - else if ( deed is LargeMarbleDeed ) - price = 192800; - else if ( deed is SmallTowerDeed ) - price = 88500; - else if ( deed is LogCabinDeed ) - price = 97800; - else if ( deed is SandstonePatioDeed ) - price = 90900; - else if ( deed is VillaDeed ) - price = 136500; - else if ( deed is StoneWorkshopDeed ) - price = 60600; - else if ( deed is MarbleWorkshopDeed ) - price = 60300; + public int ComputePriceFor(HouseDeed deed) + { + int price = 0; - return AOS.Scale( price, 80 ); // refunds 80% of the purchase price - } + if (deed is SmallBrickHouseDeed || deed is StonePlasterHouseDeed || deed is FieldStoneHouseDeed || + deed is SmallBrickHouseDeed || deed is WoodHouseDeed || deed is WoodPlasterHouseDeed || + deed is ThatchedRoofCottageDeed) + price = 43800; + else if (deed is BrickHouseDeed) + price = 144500; + else if (deed is TwoStoryWoodPlasterHouseDeed || deed is TwoStoryStonePlasterHouseDeed) + price = 192400; + else if (deed is TowerDeed) + price = 433200; + else if (deed is KeepDeed) + price = 665200; + else if (deed is CastleDeed) + price = 1022800; + else if (deed is LargePatioDeed) + price = 152800; + else if (deed is LargeMarbleDeed) + price = 192800; + else if (deed is SmallTowerDeed) + price = 88500; + else if (deed is LogCabinDeed) + price = 97800; + else if (deed is SandstonePatioDeed) + price = 90900; + else if (deed is VillaDeed) + price = 136500; + else if (deed is StoneWorkshopDeed) + price = 60600; + else if (deed is MarbleWorkshopDeed) + price = 60300; - public override void InitSBInfo() - { - m_SBInfos.Add( new SBRealEstateBroker() ); - } + return AOS.Scale(price, 80); // refunds 80% of the purchase price + } - public RealEstateBroker( Serial serial ) : base( serial ) - { - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBRealEstateBroker()); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Scribe.cs b/Scripts/Mobiles/Vendors/NPC/Scribe.cs index 2ff5a85bf..268164f84 100644 --- a/Scripts/Mobiles/Vendors/NPC/Scribe.cs +++ b/Scripts/Mobiles/Vendors/NPC/Scribe.cs @@ -1,76 +1,79 @@ using System; using System.Collections.Generic; +using Server.Items; +using Server.Network; namespace Server.Mobiles { - public class Scribe : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Scribe : BaseVendor + { + public static readonly TimeSpan ShushDelay = TimeSpan.FromMinutes(1); - public override NpcGuild NpcGuild => NpcGuild.MagesGuild; + private DateTime m_NextShush; + private List m_SBInfos = new List(); - private DateTime m_NextShush; - public static readonly TimeSpan ShushDelay = TimeSpan.FromMinutes( 1 ); + [Constructible] + public Scribe() : base("the scribe") + { + SetSkill(SkillName.EvalInt, 60.0, 83.0); + SetSkill(SkillName.Inscribe, 90.0, 100.0); + } - [Constructible] - public Scribe() : base( "the scribe" ) - { - SetSkill( SkillName.EvalInt, 60.0, 83.0 ); - SetSkill( SkillName.Inscribe, 90.0, 100.0 ); - } + public Scribe(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBScribe() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.MagesGuild; - public override void InitOutfit() - { - base.InitOutfit(); + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Shoes : VendorShoeType.Sandals; - AddItem( new Items.Robe( Utility.RandomNeutralHue() ) ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBScribe()); + } - public override bool HandlesOnSpeech( Mobile from ) - { - return from.Player; - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void OnSpeech( SpeechEventArgs e ) - { - base.OnSpeech( e ); + AddItem(new Robe(Utility.RandomNeutralHue())); + } - if ( !e.Handled && m_NextShush <= DateTime.UtcNow && InLOS( e.Mobile ) ) - { - Direction = GetDirectionTo( e.Mobile ); + public override bool HandlesOnSpeech(Mobile from) + { + return from.Player; + } - PlaySound( Female ? 0x32F : 0x441 ); - PublicOverheadMessage( Network.MessageType.Regular, 0x3B2, 1073990 ); // Shhhh! + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); - m_NextShush = DateTime.UtcNow + ShushDelay; - e.Handled = true; - } - } + if (!e.Handled && m_NextShush <= DateTime.UtcNow && InLOS(e.Mobile)) + { + Direction = GetDirectionTo(e.Mobile); - public Scribe( Serial serial ) : base( serial ) - { - } + PlaySound(Female ? 0x32F : 0x441); + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1073990); // Shhhh! - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + m_NextShush = DateTime.UtcNow + ShushDelay; + e.Handled = true; + } + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Shipwright.cs b/Scripts/Mobiles/Vendors/NPC/Shipwright.cs index 736af7497..cb97fe143 100644 --- a/Scripts/Mobiles/Vendors/NPC/Shipwright.cs +++ b/Scripts/Mobiles/Vendors/NPC/Shipwright.cs @@ -1,47 +1,49 @@ using System.Collections.Generic; +using Server.Items; -namespace Server.Mobiles -{ - public class Shipwright : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class Shipwright : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Shipwright() : base( "the shipwright" ) - { - SetSkill( SkillName.Carpentry, 60.0, 83.0 ); - SetSkill( SkillName.Macing, 36.0, 68.0 ); - } + [Constructible] + public Shipwright() : base("the shipwright") + { + SetSkill(SkillName.Carpentry, 60.0, 83.0); + SetSkill(SkillName.Macing, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBShipwright() ); - } + public Shipwright(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.SmithHammer() ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBShipwright()); + } - public Shipwright( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new SmithHammer()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/StoneCrafter.cs b/Scripts/Mobiles/Vendors/NPC/StoneCrafter.cs index 1a0d6ec7e..3f3e7f68c 100644 --- a/Scripts/Mobiles/Vendors/NPC/StoneCrafter.cs +++ b/Scripts/Mobiles/Vendors/NPC/StoneCrafter.cs @@ -2,47 +2,48 @@ using System.Collections.Generic; namespace Server.Mobiles { - [TypeAlias( "Server.Mobiles.GargoyleStonecrafter" )] - public class StoneCrafter : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + [TypeAlias("Server.Mobiles.GargoyleStonecrafter")] + public class StoneCrafter : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; + [Constructible] + public StoneCrafter() : base("the stone crafter") + { + SetSkill(SkillName.Carpentry, 85.0, 100.0); + } - [Constructible] - public StoneCrafter() : base( "the stone crafter" ) - { - SetSkill( SkillName.Carpentry, 85.0, 100.0 ); - } + public StoneCrafter(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBStoneCrafter() ); - m_SBInfos.Add( new SBStavesWeapon() ); - m_SBInfos.Add( new SBCarpenter() ); - m_SBInfos.Add( new SBWoodenShields() ); - } + protected override List SBInfos => m_SBInfos; - public StoneCrafter( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBStoneCrafter()); + m_SBInfos.Add(new SBStavesWeapon()); + m_SBInfos.Add(new SBCarpenter()); + m_SBInfos.Add(new SBWoodenShields()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Title == "the stonecrafter" ) - Title = "the stone crafter"; - } - } -} + int version = reader.ReadInt(); + + if (Title == "the stonecrafter") + Title = "the stone crafter"; + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Tailor.cs b/Scripts/Mobiles/Vendors/NPC/Tailor.cs index baae46b46..d3fd5b757 100644 --- a/Scripts/Mobiles/Vendors/NPC/Tailor.cs +++ b/Scripts/Mobiles/Vendors/NPC/Tailor.cs @@ -4,92 +4,95 @@ using Server.Engines.BulkOrders; namespace Server.Mobiles { - public class Tailor : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Tailor : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.TailorsGuild; + [Constructible] + public Tailor() : base("the tailor") + { + SetSkill(SkillName.Tailoring, 64.0, 100.0); + } - [Constructible] - public Tailor() : base( "the tailor" ) - { - SetSkill( SkillName.Tailoring, 64.0, 100.0 ); - } + public Tailor(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBTailor() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; + public override NpcGuild NpcGuild => NpcGuild.TailorsGuild; - #region Bulk Orders - public override Item CreateBulkOrder( Mobile from, bool fromContextMenu ) - { - PlayerMobile pm = from as PlayerMobile; + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Sandals : VendorShoeType.Shoes; - if ( pm != null && pm.NextTailorBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble()) ) - { - double theirSkill = pm.Skills[SkillName.Tailoring].Base; + public override void InitSBInfo() + { + m_SBInfos.Add(new SBTailor()); + } - if ( theirSkill >= 70.1 ) - pm.NextTailorBulkOrder = TimeSpan.FromHours( 6.0 ); - else if ( theirSkill >= 50.1 ) - pm.NextTailorBulkOrder = TimeSpan.FromHours( 2.0 ); - else - pm.NextTailorBulkOrder = TimeSpan.FromHours( 1.0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( theirSkill >= 70.1 && ((theirSkill - 40.0) / 300.0) > Utility.RandomDouble() ) - return new LargeTailorBOD(); + writer.Write(0); // version + } - return SmallTailorBOD.CreateRandomFor( from ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return null; - } + int version = reader.ReadInt(); + } - public override bool IsValidBulkOrder( Item item ) - { - return ( item is SmallTailorBOD || item is LargeTailorBOD ); - } + #region Bulk Orders - public override bool SupportsBulkOrders( Mobile from ) - { - return ( from is PlayerMobile && from.Skills[SkillName.Tailoring].Base > 0 ); - } + public override Item CreateBulkOrder(Mobile from, bool fromContextMenu) + { + PlayerMobile pm = from as PlayerMobile; - public override TimeSpan GetNextBulkOrder( Mobile from ) - { - if ( from is PlayerMobile ) - return ((PlayerMobile)from).NextTailorBulkOrder; + if (pm != null && pm.NextTailorBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble())) + { + double theirSkill = pm.Skills[SkillName.Tailoring].Base; - return TimeSpan.Zero; - } + if (theirSkill >= 70.1) + pm.NextTailorBulkOrder = TimeSpan.FromHours(6.0); + else if (theirSkill >= 50.1) + pm.NextTailorBulkOrder = TimeSpan.FromHours(2.0); + else + pm.NextTailorBulkOrder = TimeSpan.FromHours(1.0); - public override void OnSuccessfulBulkOrderReceive( Mobile from ) - { - if ( Core.SE && from is PlayerMobile ) - ((PlayerMobile)from).NextTailorBulkOrder = TimeSpan.Zero; - } - #endregion + if (theirSkill >= 70.1 && (theirSkill - 40.0) / 300.0 > Utility.RandomDouble()) + return new LargeTailorBOD(); - public Tailor( Serial serial ) : base( serial ) - { - } + return SmallTailorBOD.CreateRandomFor(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return null; + } - writer.Write( (int) 0 ); // version - } + public override bool IsValidBulkOrder(Item item) + { + return item is SmallTailorBOD || item is LargeTailorBOD; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool SupportsBulkOrders(Mobile from) + { + return from is PlayerMobile && from.Skills[SkillName.Tailoring].Base > 0; + } - int version = reader.ReadInt(); - } - } -} + public override TimeSpan GetNextBulkOrder(Mobile from) + { + if (from is PlayerMobile) + return ((PlayerMobile)from).NextTailorBulkOrder; + + return TimeSpan.Zero; + } + + public override void OnSuccessfulBulkOrderReceive(Mobile from) + { + if (Core.SE && from is PlayerMobile) + ((PlayerMobile)from).NextTailorBulkOrder = TimeSpan.Zero; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Tanner.cs b/Scripts/Mobiles/Vendors/NPC/Tanner.cs index 98b9f0e27..d72dad39d 100644 --- a/Scripts/Mobiles/Vendors/NPC/Tanner.cs +++ b/Scripts/Mobiles/Vendors/NPC/Tanner.cs @@ -2,38 +2,39 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Tanner : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Tanner : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Tanner() : base( "the tanner" ) - { - SetSkill( SkillName.Tailoring, 36.0, 68.0 ); - } + [Constructible] + public Tanner() : base("the tanner") + { + SetSkill(SkillName.Tailoring, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBTanner() ); - } + public Tanner(Serial serial) : base(serial) + { + } - public Tanner( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBTanner()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/TavernKeeper.cs b/Scripts/Mobiles/Vendors/NPC/TavernKeeper.cs index ea0391ded..85a89dae7 100644 --- a/Scripts/Mobiles/Vendors/NPC/TavernKeeper.cs +++ b/Scripts/Mobiles/Vendors/NPC/TavernKeeper.cs @@ -1,45 +1,47 @@ using System.Collections.Generic; +using Server.Items; -namespace Server.Mobiles -{ - public class TavernKeeper : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; +namespace Server.Mobiles +{ + public class TavernKeeper : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public TavernKeeper() : base( "the tavern keeper" ) - { - } + [Constructible] + public TavernKeeper() : base("the tavern keeper") + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBTavernKeeper() ); - } + public TavernKeeper(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.HalfApron() ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBTavernKeeper()); + } - public TavernKeeper( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new HalfApron()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Thief.cs b/Scripts/Mobiles/Vendors/NPC/Thief.cs index e4583604a..bbc9a3f23 100644 --- a/Scripts/Mobiles/Vendors/NPC/Thief.cs +++ b/Scripts/Mobiles/Vendors/NPC/Thief.cs @@ -1,54 +1,56 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Thief : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Thief : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Thief() : base( "the thief" ) - { - SetSkill( SkillName.Camping, 55.0, 78.0 ); - SetSkill( SkillName.DetectHidden, 65.0, 88.0 ); - SetSkill( SkillName.Hiding, 45.0, 68.0 ); - SetSkill( SkillName.Archery, 65.0, 88.0 ); - SetSkill( SkillName.Tracking, 65.0, 88.0 ); - SetSkill( SkillName.Veterinary, 60.0, 83.0 ); - } + [Constructible] + public Thief() : base("the thief") + { + SetSkill(SkillName.Camping, 55.0, 78.0); + SetSkill(SkillName.DetectHidden, 65.0, 88.0); + SetSkill(SkillName.Hiding, 45.0, 68.0); + SetSkill(SkillName.Archery, 65.0, 88.0); + SetSkill(SkillName.Tracking, 65.0, 88.0); + SetSkill(SkillName.Veterinary, 60.0, 83.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBThief() ); - } + public Thief(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.Shirt( Utility.RandomNeutralHue() ) ); - AddItem( new Items.LongPants( Utility.RandomNeutralHue() ) ); - AddItem( new Items.Dagger() ); - AddItem( new Items.ThighBoots( Utility.RandomNeutralHue() ) ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBThief()); + } - public Thief( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new Shirt(Utility.RandomNeutralHue())); + AddItem(new LongPants(Utility.RandomNeutralHue())); + AddItem(new Dagger()); + AddItem(new ThighBoots(Utility.RandomNeutralHue())); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Tinker.cs b/Scripts/Mobiles/Vendors/NPC/Tinker.cs index 56859ad47..48547cf97 100644 --- a/Scripts/Mobiles/Vendors/NPC/Tinker.cs +++ b/Scripts/Mobiles/Vendors/NPC/Tinker.cs @@ -2,42 +2,43 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Tinker : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Tinker : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; + [Constructible] + public Tinker() : base("the tinker") + { + SetSkill(SkillName.Lockpicking, 60.0, 83.0); + SetSkill(SkillName.RemoveTrap, 75.0, 98.0); + SetSkill(SkillName.Tinkering, 64.0, 100.0); + } - [Constructible] - public Tinker() : base( "the tinker" ) - { - SetSkill( SkillName.Lockpicking, 60.0, 83.0 ); - SetSkill( SkillName.RemoveTrap, 75.0, 98.0 ); - SetSkill( SkillName.Tinkering, 64.0, 100.0 ); - } + public Tinker(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBTinker() ); - } + protected override List SBInfos => m_SBInfos; - public Tinker( Serial serial ) : base( serial ) - { - } + public override NpcGuild NpcGuild => NpcGuild.TinkersGuild; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBTinker()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Vagabond.cs b/Scripts/Mobiles/Vendors/NPC/Vagabond.cs index 15f826a57..ced742a7b 100644 --- a/Scripts/Mobiles/Vendors/NPC/Vagabond.cs +++ b/Scripts/Mobiles/Vendors/NPC/Vagabond.cs @@ -3,61 +3,66 @@ using Server.Items; namespace Server.Mobiles { - public class Vagabond : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Vagabond : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Vagabond() : base( "the vagabond" ) - { - SetSkill( SkillName.ItemID, 60.0, 83.0 ); - } + [Constructible] + public Vagabond() : base("the vagabond") + { + SetSkill(SkillName.ItemID, 60.0, 83.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBTinker() ); - m_SBInfos.Add( new SBVagabond() ); - } + public Vagabond(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - AddItem( new FancyShirt( Utility.RandomBrightHue() ) ); - AddItem( new Shoes( GetShoeHue() ) ); - AddItem( new LongPants( GetRandomHue() ) ); + protected override List SBInfos => m_SBInfos; - if ( Utility.RandomBool() ) - AddItem( new Cloak( Utility.RandomBrightHue() ) ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBTinker()); + m_SBInfos.Add(new SBVagabond()); + } - switch ( Utility.Random( 2 ) ) - { - case 0: AddItem( new SkullCap( Utility.RandomNeutralHue() ) ); break; - case 1: AddItem( new Bandana( Utility.RandomNeutralHue() ) ); break; - } + public override void InitOutfit() + { + AddItem(new FancyShirt(Utility.RandomBrightHue())); + AddItem(new Shoes(GetShoeHue())); + AddItem(new LongPants(GetRandomHue())); + + if (Utility.RandomBool()) + AddItem(new Cloak(Utility.RandomBrightHue())); + + switch (Utility.Random(2)) + { + case 0: + AddItem(new SkullCap(Utility.RandomNeutralHue())); + break; + case 1: + AddItem(new Bandana(Utility.RandomNeutralHue())); + break; + } - Utility.AssignRandomHair( this ); - Utility.AssignRandomFacialHair( this, HairHue ); + Utility.AssignRandomHair(this); + Utility.AssignRandomFacialHair(this, HairHue); - PackGold( 100, 200 ); - } + PackGold(100, 200); + } - public Vagabond( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/VarietyDealer.cs b/Scripts/Mobiles/Vendors/NPC/VarietyDealer.cs index bf5523dd3..49eee0e28 100644 --- a/Scripts/Mobiles/Vendors/NPC/VarietyDealer.cs +++ b/Scripts/Mobiles/Vendors/NPC/VarietyDealer.cs @@ -2,37 +2,38 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class VarietyDealer : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class VarietyDealer : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public VarietyDealer() : base( "the variety dealer" ) - { - } + [Constructible] + public VarietyDealer() : base("the variety dealer") + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBVarietyDealer() ); - } + public VarietyDealer(Serial serial) : base(serial) + { + } - public VarietyDealer( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBVarietyDealer()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Veterinarian.cs b/Scripts/Mobiles/Vendors/NPC/Veterinarian.cs index 65cf0126d..b6ed18320 100644 --- a/Scripts/Mobiles/Vendors/NPC/Veterinarian.cs +++ b/Scripts/Mobiles/Vendors/NPC/Veterinarian.cs @@ -2,39 +2,40 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class Veterinarian : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Veterinarian : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Veterinarian() : base( "the vet" ) - { - SetSkill( SkillName.AnimalLore, 85.0, 100.0 ); - SetSkill( SkillName.Veterinary, 90.0, 100.0 ); - } + [Constructible] + public Veterinarian() : base("the vet") + { + SetSkill(SkillName.AnimalLore, 85.0, 100.0); + SetSkill(SkillName.Veterinary, 90.0, 100.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBVeterinarian() ); - } + public Veterinarian(Serial serial) : base(serial) + { + } - public Veterinarian( Serial serial ) : base( serial ) - { - } + protected override List SBInfos => m_SBInfos; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void InitSBInfo() + { + m_SBInfos.Add(new SBVeterinarian()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Waiter.cs b/Scripts/Mobiles/Vendors/NPC/Waiter.cs index 01ba7142e..3cb475cb5 100644 --- a/Scripts/Mobiles/Vendors/NPC/Waiter.cs +++ b/Scripts/Mobiles/Vendors/NPC/Waiter.cs @@ -1,46 +1,48 @@ using System.Collections.Generic; +using Server.Items; namespace Server.Mobiles { - public class Waiter : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Waiter : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Waiter() : base( "the waiter" ) - { - SetSkill( SkillName.Discordance, 36.0, 68.0 ); - } + [Constructible] + public Waiter() : base("the waiter") + { + SetSkill(SkillName.Discordance, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBWaiter() ); - } + public Waiter(Serial serial) : base(serial) + { + } - public override void InitOutfit() - { - base.InitOutfit(); + protected override List SBInfos => m_SBInfos; - AddItem( new Items.HalfApron() ); - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBWaiter()); + } - public Waiter( Serial serial ) : base( serial ) - { - } + public override void InitOutfit() + { + base.InitOutfit(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + AddItem(new HalfApron()); + } - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Weaponsmith.cs b/Scripts/Mobiles/Vendors/NPC/Weaponsmith.cs index bda6d5de5..a309283a3 100644 --- a/Scripts/Mobiles/Vendors/NPC/Weaponsmith.cs +++ b/Scripts/Mobiles/Vendors/NPC/Weaponsmith.cs @@ -1,113 +1,117 @@ using System; using System.Collections.Generic; using Server.Engines.BulkOrders; +using Server.Items; namespace Server.Mobiles { - public class Weaponsmith : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Weaponsmith : BaseVendor + { + private List m_SBInfos = new List(); - [Constructible] - public Weaponsmith() : base( "the weaponsmith" ) - { - SetSkill( SkillName.ArmsLore, 64.0, 100.0 ); - SetSkill( SkillName.Blacksmith, 65.0, 88.0 ); - SetSkill( SkillName.Fencing, 45.0, 68.0 ); - SetSkill( SkillName.Macing, 45.0, 68.0 ); - SetSkill( SkillName.Swords, 45.0, 68.0 ); - SetSkill( SkillName.Tactics, 36.0, 68.0 ); - } + [Constructible] + public Weaponsmith() : base("the weaponsmith") + { + SetSkill(SkillName.ArmsLore, 64.0, 100.0); + SetSkill(SkillName.Blacksmith, 65.0, 88.0); + SetSkill(SkillName.Fencing, 45.0, 68.0); + SetSkill(SkillName.Macing, 45.0, 68.0); + SetSkill(SkillName.Swords, 45.0, 68.0); + SetSkill(SkillName.Tactics, 36.0, 68.0); + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBWeaponSmith() ); + public Weaponsmith(Serial serial) : base(serial) + { + } - if ( IsTokunoVendor ) - m_SBInfos.Add( new SBSEWeapons() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Boots : VendorShoeType.ThighBoots; + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.Boots : VendorShoeType.ThighBoots; - public override int GetShoeHue() - { - return 0; - } + public override void InitSBInfo() + { + m_SBInfos.Add(new SBWeaponSmith()); - public override void InitOutfit() - { - base.InitOutfit(); + if (IsTokunoVendor) + m_SBInfos.Add(new SBSEWeapons()); + } - AddItem( new Items.HalfApron() ); - } + public override int GetShoeHue() + { + return 0; + } - #region Bulk Orders - public override Item CreateBulkOrder( Mobile from, bool fromContextMenu ) - { - PlayerMobile pm = from as PlayerMobile; + public override void InitOutfit() + { + base.InitOutfit(); - if ( pm != null && pm.NextSmithBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble()) ) - { - double theirSkill = pm.Skills[SkillName.Blacksmith].Base; + AddItem(new HalfApron()); + } - if ( theirSkill >= 70.1 ) - pm.NextSmithBulkOrder = TimeSpan.FromHours( 6.0 ); - else if ( theirSkill >= 50.1 ) - pm.NextSmithBulkOrder = TimeSpan.FromHours( 2.0 ); - else - pm.NextSmithBulkOrder = TimeSpan.FromHours( 1.0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( theirSkill >= 70.1 && ((theirSkill - 40.0) / 300.0) > Utility.RandomDouble() ) - return new LargeSmithBOD(); + writer.Write(0); // version + } - return SmallSmithBOD.CreateRandomFor( from ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return null; - } + int version = reader.ReadInt(); + } - public override bool IsValidBulkOrder( Item item ) - { - return ( item is SmallSmithBOD || item is LargeSmithBOD ); - } + #region Bulk Orders - public override bool SupportsBulkOrders( Mobile from ) - { - return ( from is PlayerMobile && Core.AOS && from.Skills[SkillName.Blacksmith].Base > 0 ); - } + public override Item CreateBulkOrder(Mobile from, bool fromContextMenu) + { + PlayerMobile pm = from as PlayerMobile; - public override TimeSpan GetNextBulkOrder( Mobile from ) - { - if ( from is PlayerMobile ) - return ((PlayerMobile)from).NextSmithBulkOrder; + if (pm != null && pm.NextSmithBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble())) + { + double theirSkill = pm.Skills[SkillName.Blacksmith].Base; - return TimeSpan.Zero; - } + if (theirSkill >= 70.1) + pm.NextSmithBulkOrder = TimeSpan.FromHours(6.0); + else if (theirSkill >= 50.1) + pm.NextSmithBulkOrder = TimeSpan.FromHours(2.0); + else + pm.NextSmithBulkOrder = TimeSpan.FromHours(1.0); - public override void OnSuccessfulBulkOrderReceive( Mobile from ) - { - if ( Core.SE && from is PlayerMobile ) - ((PlayerMobile)from).NextSmithBulkOrder = TimeSpan.Zero; - } - #endregion + if (theirSkill >= 70.1 && (theirSkill - 40.0) / 300.0 > Utility.RandomDouble()) + return new LargeSmithBOD(); - public Weaponsmith( Serial serial ) : base( serial ) - { - } + return SmallSmithBOD.CreateRandomFor(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return null; + } - writer.Write( (int) 0 ); // version - } + public override bool IsValidBulkOrder(Item item) + { + return item is SmallSmithBOD || item is LargeSmithBOD; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool SupportsBulkOrders(Mobile from) + { + return from is PlayerMobile && Core.AOS && from.Skills[SkillName.Blacksmith].Base > 0; + } - int version = reader.ReadInt(); - } - } -} + public override TimeSpan GetNextBulkOrder(Mobile from) + { + if (from is PlayerMobile) + return ((PlayerMobile)from).NextSmithBulkOrder; + + return TimeSpan.Zero; + } + + public override void OnSuccessfulBulkOrderReceive(Mobile from) + { + if (Core.SE && from is PlayerMobile) + ((PlayerMobile)from).NextSmithBulkOrder = TimeSpan.Zero; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/NPC/Weaver.cs b/Scripts/Mobiles/Vendors/NPC/Weaver.cs index 2cdd6df32..34a6de815 100644 --- a/Scripts/Mobiles/Vendors/NPC/Weaver.cs +++ b/Scripts/Mobiles/Vendors/NPC/Weaver.cs @@ -4,92 +4,95 @@ using Server.Engines.BulkOrders; namespace Server.Mobiles { - public class Weaver : BaseVendor - { - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; + public class Weaver : BaseVendor + { + private List m_SBInfos = new List(); - public override NpcGuild NpcGuild => NpcGuild.TailorsGuild; + [Constructible] + public Weaver() : base("the weaver") + { + SetSkill(SkillName.Tailoring, 65.0, 88.0); + } - [Constructible] - public Weaver() : base( "the weaver" ) - { - SetSkill( SkillName.Tailoring, 65.0, 88.0 ); - } + public Weaver(Serial serial) : base(serial) + { + } - public override void InitSBInfo() - { - m_SBInfos.Add( new SBWeaver() ); - } + protected override List SBInfos => m_SBInfos; - public override VendorShoeType ShoeType => VendorShoeType.Sandals; + public override NpcGuild NpcGuild => NpcGuild.TailorsGuild; - #region Bulk Orders - public override Item CreateBulkOrder( Mobile from, bool fromContextMenu ) - { - PlayerMobile pm = from as PlayerMobile; + public override VendorShoeType ShoeType => VendorShoeType.Sandals; - if ( pm != null && pm.NextTailorBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble()) ) - { - double theirSkill = pm.Skills[SkillName.Tailoring].Base; + public override void InitSBInfo() + { + m_SBInfos.Add(new SBWeaver()); + } - if ( theirSkill >= 70.1 ) - pm.NextTailorBulkOrder = TimeSpan.FromHours( 6.0 ); - else if ( theirSkill >= 50.1 ) - pm.NextTailorBulkOrder = TimeSpan.FromHours( 2.0 ); - else - pm.NextTailorBulkOrder = TimeSpan.FromHours( 1.0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( theirSkill >= 70.1 && ((theirSkill - 40.0) / 300.0) > Utility.RandomDouble() ) - return new LargeTailorBOD(); + writer.Write(0); // version + } - return SmallTailorBOD.CreateRandomFor( from ); - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - return null; - } + int version = reader.ReadInt(); + } - public override bool IsValidBulkOrder( Item item ) - { - return ( item is SmallTailorBOD || item is LargeTailorBOD ); - } + #region Bulk Orders - public override bool SupportsBulkOrders( Mobile from ) - { - return ( from is PlayerMobile && from.Skills[SkillName.Tailoring].Base > 0 ); - } + public override Item CreateBulkOrder(Mobile from, bool fromContextMenu) + { + PlayerMobile pm = from as PlayerMobile; - public override TimeSpan GetNextBulkOrder( Mobile from ) - { - if ( from is PlayerMobile ) - return ((PlayerMobile)from).NextTailorBulkOrder; + if (pm != null && pm.NextTailorBulkOrder == TimeSpan.Zero && (fromContextMenu || 0.2 > Utility.RandomDouble())) + { + double theirSkill = pm.Skills[SkillName.Tailoring].Base; - return TimeSpan.Zero; - } + if (theirSkill >= 70.1) + pm.NextTailorBulkOrder = TimeSpan.FromHours(6.0); + else if (theirSkill >= 50.1) + pm.NextTailorBulkOrder = TimeSpan.FromHours(2.0); + else + pm.NextTailorBulkOrder = TimeSpan.FromHours(1.0); - public override void OnSuccessfulBulkOrderReceive( Mobile from ) - { - if ( Core.SE && from is PlayerMobile ) - ((PlayerMobile)from).NextTailorBulkOrder = TimeSpan.Zero; - } - #endregion + if (theirSkill >= 70.1 && (theirSkill - 40.0) / 300.0 > Utility.RandomDouble()) + return new LargeTailorBOD(); - public Weaver( Serial serial ) : base( serial ) - { - } + return SmallTailorBOD.CreateRandomFor(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + return null; + } - writer.Write( (int) 0 ); // version - } + public override bool IsValidBulkOrder(Item item) + { + return item is SmallTailorBOD || item is LargeTailorBOD; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool SupportsBulkOrders(Mobile from) + { + return from is PlayerMobile && from.Skills[SkillName.Tailoring].Base > 0; + } - int version = reader.ReadInt(); - } - } -} + public override TimeSpan GetNextBulkOrder(Mobile from) + { + if (from is PlayerMobile) + return ((PlayerMobile)from).NextTailorBulkOrder; + + return TimeSpan.Zero; + } + + public override void OnSuccessfulBulkOrderReceive(Mobile from) + { + if (Core.SE && from is PlayerMobile) + ((PlayerMobile)from).NextTailorBulkOrder = TimeSpan.Zero; + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/PlayerBarkeeper.cs b/Scripts/Mobiles/Vendors/PlayerBarkeeper.cs index 0433265d3..9561a5db0 100644 --- a/Scripts/Mobiles/Vendors/PlayerBarkeeper.cs +++ b/Scripts/Mobiles/Vendors/PlayerBarkeeper.cs @@ -1,1048 +1,1066 @@ using System; using System.Collections.Generic; -using Server.Items; -using Server.Gumps; -using Server.Prompts; -using Server.Network; using Server.ContextMenus; +using Server.Gumps; +using Server.Items; using Server.Multis; +using Server.Network; +using Server.Prompts; namespace Server.Mobiles { - public class ChangeRumorMessagePrompt : Prompt - { - private PlayerBarkeeper m_Barkeeper; - private int m_RumorIndex; - - public ChangeRumorMessagePrompt( PlayerBarkeeper barkeeper, int rumorIndex ) - { - m_Barkeeper = barkeeper; - m_RumorIndex = rumorIndex; - } - - public override void OnCancel( Mobile from ) - { - OnResponse( from, "" ); - } - - public override void OnResponse( Mobile from, string text ) - { - if ( text.Length > 130 ) - text = text.Substring( 0, 130 ); - - m_Barkeeper.EndChangeRumor( from, m_RumorIndex, text ); - } - } - - public class ChangeRumorKeywordPrompt : Prompt - { - private PlayerBarkeeper m_Barkeeper; - private int m_RumorIndex; - - public ChangeRumorKeywordPrompt( PlayerBarkeeper barkeeper, int rumorIndex ) - { - m_Barkeeper = barkeeper; - m_RumorIndex = rumorIndex; - } - - public override void OnCancel( Mobile from ) - { - OnResponse( from, "" ); - } - - public override void OnResponse( Mobile from, string text ) - { - if ( text.Length > 130 ) - text = text.Substring( 0, 130 ); - - m_Barkeeper.EndChangeKeyword( from, m_RumorIndex, text ); - } - } - - public class ChangeTipMessagePrompt : Prompt - { - private PlayerBarkeeper m_Barkeeper; - - public ChangeTipMessagePrompt( PlayerBarkeeper barkeeper ) - { - m_Barkeeper = barkeeper; - } - - public override void OnCancel( Mobile from ) - { - OnResponse( from, "" ); - } - - public override void OnResponse( Mobile from, string text ) - { - if ( text.Length > 130 ) - text = text.Substring( 0, 130 ); - - m_Barkeeper.EndChangeTip( from, text ); - } - } - - public class BarkeeperRumor - { - public string Message { get; set; } - - public string Keyword { get; set; } - - public BarkeeperRumor( string message, string keyword ) - { - Message = message; - Keyword = keyword; - } - - public static BarkeeperRumor Deserialize( GenericReader reader ) - { - if ( !reader.ReadBool() ) - return null; - - return new BarkeeperRumor( reader.ReadString(), reader.ReadString() ); - } - - public static void Serialize( GenericWriter writer, BarkeeperRumor rumor ) - { - if ( rumor == null ) - { - writer.Write( false ); - } - else - { - writer.Write( true ); - writer.Write( rumor.Message ); - writer.Write( rumor.Keyword ); - } - } - } - - public class ManageBarkeeperEntry : ContextMenuEntry - { - private Mobile m_From; - private PlayerBarkeeper m_Barkeeper; - - public ManageBarkeeperEntry( Mobile from, PlayerBarkeeper barkeeper ) : base( 6151, 12 ) - { - m_From = from; - m_Barkeeper = barkeeper; - } - - public override void OnClick() - { - m_Barkeeper.BeginManagement( m_From ); - } - } - - public class PlayerBarkeeper : BaseVendor - { - private BaseHouse m_House; - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } - - public BaseHouse House - { - get => m_House; - set - { - m_House?.PlayerBarkeepers.Remove( this ); - - value?.PlayerBarkeepers.Add( this ); - - m_House = value; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string TipMessage { get; set; } - - public override bool IsActiveBuyer => false; - public override bool IsActiveSeller => ( m_SBInfos.Count > 0 ); - - public override bool DisallowAllMoves => true; - public override bool NoHouseRestrictions => true; - - public BarkeeperRumor[] Rumors { get; private set; } - - public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.ThighBoots : VendorShoeType.Boots; - - public override bool GetGender() - { - return false; // always starts as male - } - - public override void InitOutfit() - { - base.InitOutfit(); - - AddItem( new HalfApron( Utility.RandomBrightHue() ) ); - - Container pack = Backpack; - - pack?.Delete(); - } - - public override void InitBody() - { - base.InitBody(); - - if ( BodyValue == 0x340 || BodyValue == 0x402 ) - Hue = 0; - else - Hue = 0x83F4; // hue is not random - - Container pack = Backpack; - - pack?.Delete(); - } - - public PlayerBarkeeper( Mobile owner, BaseHouse house ) : base( "the barkeeper" ) - { - Owner = owner; - House = house; - Rumors = new BarkeeperRumor[3]; - - LoadSBInfo(); - } - - public override bool HandlesOnSpeech(Mobile from) - { - if ( InRange( from, 3 ) ) - return true; - - return base.HandlesOnSpeech (from); - } - - private Timer m_NewsTimer; - - private void ShoutNews_Callback( object state ) - { - object[] states = (object[])state; - TownCrierEntry tce = (TownCrierEntry)states[0]; - int index = (int)states[1]; - - if ( index < 0 || index >= tce.Lines.Length ) - { - m_NewsTimer?.Stop(); - - m_NewsTimer = null; - } - else - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, false, tce.Lines[index] ); - states[1] = index + 1; - } - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - House = null; - } - - public override bool OnBeforeDeath() - { - if ( !base.OnBeforeDeath() ) - return false; + public class ChangeRumorMessagePrompt : Prompt + { + private PlayerBarkeeper m_Barkeeper; + private int m_RumorIndex; + + public ChangeRumorMessagePrompt(PlayerBarkeeper barkeeper, int rumorIndex) + { + m_Barkeeper = barkeeper; + m_RumorIndex = rumorIndex; + } + + public override void OnCancel(Mobile from) + { + OnResponse(from, ""); + } + + public override void OnResponse(Mobile from, string text) + { + if (text.Length > 130) + text = text.Substring(0, 130); + + m_Barkeeper.EndChangeRumor(from, m_RumorIndex, text); + } + } + + public class ChangeRumorKeywordPrompt : Prompt + { + private PlayerBarkeeper m_Barkeeper; + private int m_RumorIndex; + + public ChangeRumorKeywordPrompt(PlayerBarkeeper barkeeper, int rumorIndex) + { + m_Barkeeper = barkeeper; + m_RumorIndex = rumorIndex; + } + + public override void OnCancel(Mobile from) + { + OnResponse(from, ""); + } + + public override void OnResponse(Mobile from, string text) + { + if (text.Length > 130) + text = text.Substring(0, 130); + + m_Barkeeper.EndChangeKeyword(from, m_RumorIndex, text); + } + } + + public class ChangeTipMessagePrompt : Prompt + { + private PlayerBarkeeper m_Barkeeper; + + public ChangeTipMessagePrompt(PlayerBarkeeper barkeeper) + { + m_Barkeeper = barkeeper; + } + + public override void OnCancel(Mobile from) + { + OnResponse(from, ""); + } + + public override void OnResponse(Mobile from, string text) + { + if (text.Length > 130) + text = text.Substring(0, 130); + + m_Barkeeper.EndChangeTip(from, text); + } + } + + public class BarkeeperRumor + { + public BarkeeperRumor(string message, string keyword) + { + Message = message; + Keyword = keyword; + } + + public string Message{ get; set; } + + public string Keyword{ get; set; } + + public static BarkeeperRumor Deserialize(GenericReader reader) + { + if (!reader.ReadBool()) + return null; + + return new BarkeeperRumor(reader.ReadString(), reader.ReadString()); + } + + public static void Serialize(GenericWriter writer, BarkeeperRumor rumor) + { + if (rumor == null) + { + writer.Write(false); + } + else + { + writer.Write(true); + writer.Write(rumor.Message); + writer.Write(rumor.Keyword); + } + } + } + + public class ManageBarkeeperEntry : ContextMenuEntry + { + private PlayerBarkeeper m_Barkeeper; + private Mobile m_From; + + public ManageBarkeeperEntry(Mobile from, PlayerBarkeeper barkeeper) : base(6151, 12) + { + m_From = from; + m_Barkeeper = barkeeper; + } + + public override void OnClick() + { + m_Barkeeper.BeginManagement(m_From); + } + } + + public class PlayerBarkeeper : BaseVendor + { + private BaseHouse m_House; + + private Timer m_NewsTimer; + + private List m_SBInfos = new List(); + + public PlayerBarkeeper(Mobile owner, BaseHouse house) : base("the barkeeper") + { + Owner = owner; + House = house; + Rumors = new BarkeeperRumor[3]; + + LoadSBInfo(); + } + + public PlayerBarkeeper(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } + + public BaseHouse House + { + get => m_House; + set + { + m_House?.PlayerBarkeepers.Remove(this); + + value?.PlayerBarkeepers.Add(this); + + m_House = value; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string TipMessage{ get; set; } + + public override bool IsActiveBuyer => false; + public override bool IsActiveSeller => m_SBInfos.Count > 0; + + public override bool DisallowAllMoves => true; + public override bool NoHouseRestrictions => true; + + public BarkeeperRumor[] Rumors{ get; private set; } + + public override VendorShoeType ShoeType => Utility.RandomBool() ? VendorShoeType.ThighBoots : VendorShoeType.Boots; + protected override List SBInfos => m_SBInfos; + + public override bool GetGender() + { + return false; // always starts as male + } + + public override void InitOutfit() + { + base.InitOutfit(); + + AddItem(new HalfApron(Utility.RandomBrightHue())); + + Container pack = Backpack; + + pack?.Delete(); + } + + public override void InitBody() + { + base.InitBody(); + + if (BodyValue == 0x340 || BodyValue == 0x402) + Hue = 0; + else + Hue = 0x83F4; // hue is not random + + Container pack = Backpack; + + pack?.Delete(); + } - Item shoes = FindItemOnLayer( Layer.Shoes ); - - if ( shoes is Sandals ) - shoes.Hue = 0; - - return true; - } - - public override void OnSpeech( SpeechEventArgs e ) - { - base.OnSpeech( e ); - - if ( !e.Handled && InRange( e.Mobile, 3 ) ) - { - if ( m_NewsTimer == null && e.HasKeyword( 0x30 ) ) // *news* - { - TownCrierEntry tce = GlobalTownCrierEntryList.Instance.GetRandomEntry(); - - if ( tce == null ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, 1005643 ); // I have no news at this time. - } - else - { - m_NewsTimer = Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 3.0 ), new TimerStateCallback( ShoutNews_Callback ), new object[]{ tce, 0 } ); - - PublicOverheadMessage( MessageType.Regular, 0x3B2, 502978 ); // Some of the latest news! - } - } - - for ( int i = 0; i < Rumors.Length; ++i ) - { - BarkeeperRumor rumor = Rumors[i]; - - string keyword = rumor?.Keyword; - - if ( keyword == null || (keyword = keyword.Trim()).Length == 0 ) - continue; - - if ( Insensitive.Equals( keyword, e.Speech ) ) - { - string message = rumor.Message; - - if ( message == null || (message = message.Trim()).Length == 0 ) - continue; - - PublicOverheadMessage( MessageType.Regular, 0x3B2, false, message ); - } - } - } - } - - public override bool CheckGold( Mobile from, Item dropped ) - { - if ( dropped is Gold ) - { - Gold g = (Gold)dropped; - - if ( g.Amount > 50 ) - { - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "I cannot accept so large a tip!", from.NetState ); - } - else - { - string tip = TipMessage; - - if ( tip == null || (tip = tip.Trim()).Length == 0 ) - { - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "It would not be fair of me to take your money and not offer you information in return.", from.NetState ); - } - else - { - Direction = GetDirectionTo( from ); - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, tip, from.NetState ); - - g.Delete(); - return true; - } - } - } - - return false; - } - - public bool IsOwner( Mobile from ) - { - if ( from == null || from.Deleted || Deleted ) - return false; - - if ( from.AccessLevel > AccessLevel.GameMaster ) - return true; - - return ( Owner == from ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - - if ( IsOwner( from ) && from.InLOS( this ) ) - list.Add( new ManageBarkeeperEntry( from, this ) ); - } - - public void BeginManagement( Mobile from ) - { - if ( !IsOwner( from ) ) - return; - - from.SendGump( new BarkeeperGump( from, this ) ); - } - - public void Dismiss() - { - Delete(); - } - - public void BeginChangeRumor( Mobile from, int index ) - { - if ( index < 0 || index >= Rumors.Length ) - return; - - from.Prompt = new ChangeRumorMessagePrompt( this, index ); - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "Say what news you would like me to tell our guests.", from.NetState ); - } - - public void EndChangeRumor( Mobile from, int index, string text ) - { - if ( index < 0 || index >= Rumors.Length ) - return; - - if ( Rumors[index] == null ) - Rumors[index] = new BarkeeperRumor( text, null ); - else - Rumors[index].Message = text; - - from.Prompt = new ChangeRumorKeywordPrompt( this, index ); - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "What keyword should a guest say to me to get this news?", from.NetState ); - } - - public void EndChangeKeyword( Mobile from, int index, string text ) - { - if ( index < 0 || index >= Rumors.Length ) - return; - - if ( Rumors[index] == null ) - Rumors[index] = new BarkeeperRumor( null, text ); - else - Rumors[index].Keyword = text; - - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "I'll pass on the message.", from.NetState ); - } - - public void RemoveRumor( Mobile from, int index ) - { - if ( index < 0 || index >= Rumors.Length ) - return; - - Rumors[index] = null; - } - - public void BeginChangeTip( Mobile from ) - { - from.Prompt = new ChangeTipMessagePrompt( this ); - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "Say what you want me to tell guests when they give me a good tip.", from.NetState ); - } - - public void EndChangeTip( Mobile from, string text ) - { - TipMessage = text; - PrivateOverheadMessage( MessageType.Regular, 0x3B2, false, "I'll say that to anyone who gives me a good tip.", from.NetState ); - } - - public void RemoveTip( Mobile from ) - { - TipMessage = null; - } - - public void BeginChangeTitle( Mobile from ) - { - from.SendGump( new BarkeeperTitleGump( from, this ) ); - } - - public void EndChangeTitle( Mobile from, string title, bool vendor ) - { - Title = title; - - LoadSBInfo(); - } - - public void CancelChangeTitle( Mobile from ) - { - from.SendGump( new BarkeeperGump( from, this ) ); - } - - public void BeginChangeAppearance( Mobile from ) - { - from.CloseGump( typeof( PlayerVendorCustomizeGump ) ); - from.SendGump( new PlayerVendorCustomizeGump( this, from ) ); - } - - public void ChangeGender( Mobile from ) - { - Female = !Female; - - if ( Female ) - { - Body = 401; - Name = NameList.RandomName( "female" ); - - FacialHairItemID = 0; - } - else - { - Body = 400; - Name = NameList.RandomName( "male" ); - } - } - - private List m_SBInfos = new List(); - protected override List SBInfos => m_SBInfos; - - public override void InitSBInfo() - { - if ( Title == "the waiter" || Title == "the barkeeper" || Title == "the baker" || Title == "the innkeeper" || Title == "the chef" ) - { - if ( m_SBInfos.Count == 0 ) - m_SBInfos.Add( new SBPlayerBarkeeper() ); - } - else - { - m_SBInfos.Clear(); - } - } - - public PlayerBarkeeper( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 1 ); // version; - - writer.Write( (Item) m_House ); - - writer.Write( (Mobile) Owner ); - - writer.WriteEncodedInt( (int) Rumors.Length ); - - for ( int i = 0; i < Rumors.Length; ++i ) - BarkeeperRumor.Serialize( writer, Rumors[i] ); - - writer.Write( (string) TipMessage ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 1: - { - House = (BaseHouse) reader.ReadItem(); - - goto case 0; - } - case 0: - { - Owner = reader.ReadMobile(); - - Rumors = new BarkeeperRumor[reader.ReadEncodedInt()]; - - for ( int i = 0; i < Rumors.Length; ++i ) - Rumors[i] = BarkeeperRumor.Deserialize( reader ); - - TipMessage = reader.ReadString(); - - break; - } - } - - if ( version < 1 ) - Timer.DelayCall( TimeSpan.Zero, UpgradeFromVersion0 ); - } - - private void UpgradeFromVersion0() - { - House = BaseHouse.FindHouseAt( this ); - } - } - - public class BarkeeperTitleGump : Gump - { - private Mobile m_From; - private PlayerBarkeeper m_Barkeeper; - - private class Entry - { - public string m_Description; - public string m_Title; - public bool m_Vendor; - - public Entry( string desc ) : this( desc, $"the {desc.ToLower()}", false ) - { - } - - public Entry( string desc, bool vendor ) : this( desc, $"the {desc.ToLower()}", vendor ) - { - } - - public Entry( string desc, string title, bool vendor ) - { - m_Description = desc; - m_Title = title; - m_Vendor = vendor; - } - } - - private static Entry[] m_Entries = { - new Entry( "Alchemist" ), - new Entry( "Animal Tamer" ), - new Entry( "Apothecary" ), - new Entry( "Artist" ), - new Entry( "Baker", true ), - new Entry( "Bard" ), - new Entry( "Barkeep", "the barkeeper", true ), - new Entry( "Beggar" ), - new Entry( "Blacksmith" ), - new Entry( "Bounty Hunter" ), - new Entry( "Brigand" ), - new Entry( "Butler" ), - new Entry( "Carpenter" ), - new Entry( "Chef", true ), - new Entry( "Commander" ), - new Entry( "Curator" ), - new Entry( "Drunkard" ), - new Entry( "Farmer" ), - new Entry( "Fisherman" ), - new Entry( "Gambler" ), - new Entry( "Gypsy" ), - new Entry( "Herald" ), - new Entry( "Herbalist" ), - new Entry( "Hermit" ), - new Entry( "Innkeeper", true ), - new Entry( "Jailor" ), - new Entry( "Jester" ), - new Entry( "Librarian" ), - new Entry( "Mage" ), - new Entry( "Mercenary" ), - new Entry( "Merchant" ), - new Entry( "Messenger" ), - new Entry( "Miner" ), - new Entry( "Monk" ), - new Entry( "Noble" ), - new Entry( "Paladin" ), - new Entry( "Peasant" ), - new Entry( "Pirate" ), - new Entry( "Prisoner" ), - new Entry( "Prophet" ), - new Entry( "Ranger" ), - new Entry( "Sage" ), - new Entry( "Sailor" ), - new Entry( "Scholar" ), - new Entry( "Scribe" ), - new Entry( "Sentry" ), - new Entry( "Servant" ), - new Entry( "Shepherd" ), - new Entry( "Soothsayer" ), - new Entry( "Stoic" ), - new Entry( "Storyteller" ), - new Entry( "Tailor" ), - new Entry( "Thief" ), - new Entry( "Tinker" ), - new Entry( "Town Crier" ), - new Entry( "Treasure Hunter" ), - new Entry( "Waiter", true ), - new Entry( "Warrior" ), - new Entry( "Watchman" ), - new Entry( "No Title", null, false ) - }; - - private void RenderBackground() - { - AddPage( 0 ); - - AddBackground( 30, 40, 585, 410, 5054 ); - - AddImage( 30, 40, 9251 ); - AddImage( 180, 40, 9251 ); - AddImage( 30, 40, 9253 ); - AddImage( 30, 130, 9253 ); - AddImage( 598, 40, 9255 ); - AddImage( 598, 130, 9255 ); - AddImage( 30, 433, 9257 ); - AddImage( 180, 433, 9257 ); - AddImage( 30, 40, 9250 ); - AddImage( 598, 40, 9252 ); - AddImage( 598, 433, 9258 ); - AddImage( 30, 433, 9256 ); - - AddItem( 30, 40, 6816 ); - AddItem( 30, 125, 6817 ); - AddItem( 30, 233, 6817 ); - AddItem( 30, 341, 6817 ); - AddItem( 580, 40, 6814 ); - AddItem( 588, 125, 6815 ); - AddItem( 588, 233, 6815 ); - AddItem( 588, 341, 6815 ); - - AddImage( 560, 20, 1417 ); - AddItem( 580, 44, 4033 ); - - AddBackground( 183, 25, 280, 30, 5054 ); - - AddImage( 180, 25, 10460 ); - AddImage( 434, 25, 10460 ); - - AddHtml( 223, 32, 200, 40, "BARKEEP CUSTOMIZATION MENU", false, false ); - AddBackground( 243, 433, 150, 30, 5054 ); - - AddImage( 240, 433, 10460 ); - AddImage( 375, 433, 10460 ); - - AddImage( 80, 398, 2151 ); - AddItem( 72, 406, 2543 ); - - AddHtml( 110, 412, 180, 25, "sells food and drink", false, false ); - } - - private void RenderPage( Entry[] entries, int page ) - { - AddPage( 1 + page ); - - AddHtml( 430, 70, 180, 25, $"Page {page + 1} of {(entries.Length + 19) / 20}", false, false ); - - for ( int count = 0, i = (page * 20); count < 20 && i < entries.Length; ++count, ++i ) - { - Entry entry = entries[i]; - - AddButton( 80 + ((count / 10) * 260), 100 + ((count % 10) * 30), 4005, 4007, 2 + i, GumpButtonType.Reply, 0 ); - AddHtml( 120 + ((count / 10) * 260), 100 + ((count % 10) * 30), entry.m_Vendor ? 148 : 180, 25, entry.m_Description, true, false ); - - if ( entry.m_Vendor ) - { - AddImage( 270 + ((count / 10) * 260), 98 + ((count % 10) * 30), 2151 ); - AddItem( 262 + ((count / 10) * 260), 106 + ((count % 10) * 30), 2543 ); - } - } - - AddButton( 340, 400, 4005, 4007, 0, GumpButtonType.Page, 1 + ((page + 1) % ((entries.Length + 19) / 20)) ); - AddHtml( 380, 400, 180, 25, "More Job Titles", false, false ); - - AddButton( 338, 437, 4014, 4016, 1, GumpButtonType.Reply, 0 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); - } - - public BarkeeperTitleGump( Mobile from, PlayerBarkeeper barkeeper ) : base( 0, 0 ) - { - m_From = from; - m_Barkeeper = barkeeper; - - from.CloseGump( typeof( BarkeeperGump ) ); - from.CloseGump( typeof( BarkeeperTitleGump ) ); - - Entry[] entries = m_Entries; - - RenderBackground(); - - int pageCount = (entries.Length + 19) / 20; - - for ( int i = 0; i < pageCount; ++i ) - RenderPage( entries, i ); - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - int buttonID = info.ButtonID; - - if ( buttonID > 0 ) - { - --buttonID; - - if ( buttonID > 0 ) - { - --buttonID; - - if ( buttonID >= 0 && buttonID < m_Entries.Length ) - m_Barkeeper.EndChangeTitle( m_From, m_Entries[buttonID].m_Title, m_Entries[buttonID].m_Vendor ); - } - else - { - m_Barkeeper.CancelChangeTitle( m_From ); - } - } - } - } + public override bool HandlesOnSpeech(Mobile from) + { + if (InRange(from, 3)) + return true; + + return base.HandlesOnSpeech(from); + } + + private void ShoutNews_Callback(object state) + { + object[] states = (object[])state; + TownCrierEntry tce = (TownCrierEntry)states[0]; + int index = (int)states[1]; + + if (index < 0 || index >= tce.Lines.Length) + { + m_NewsTimer?.Stop(); + + m_NewsTimer = null; + } + else + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, false, tce.Lines[index]); + states[1] = index + 1; + } + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + House = null; + } + + public override bool OnBeforeDeath() + { + if (!base.OnBeforeDeath()) + return false; + + Item shoes = FindItemOnLayer(Layer.Shoes); + + if (shoes is Sandals) + shoes.Hue = 0; + + return true; + } + + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); + + if (!e.Handled && InRange(e.Mobile, 3)) + { + if (m_NewsTimer == null && e.HasKeyword(0x30)) // *news* + { + TownCrierEntry tce = GlobalTownCrierEntryList.Instance.GetRandomEntry(); + + if (tce == null) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, 1005643); // I have no news at this time. + } + else + { + m_NewsTimer = Timer.DelayCall(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(3.0), + new TimerStateCallback(ShoutNews_Callback), new object[] { tce, 0 }); + + PublicOverheadMessage(MessageType.Regular, 0x3B2, 502978); // Some of the latest news! + } + } + + for (int i = 0; i < Rumors.Length; ++i) + { + BarkeeperRumor rumor = Rumors[i]; + + string keyword = rumor?.Keyword; + + if (keyword == null || (keyword = keyword.Trim()).Length == 0) + continue; + + if (Insensitive.Equals(keyword, e.Speech)) + { + string message = rumor.Message; + + if (message == null || (message = message.Trim()).Length == 0) + continue; + + PublicOverheadMessage(MessageType.Regular, 0x3B2, false, message); + } + } + } + } + + public override bool CheckGold(Mobile from, Item dropped) + { + if (dropped is Gold) + { + Gold g = (Gold)dropped; + + if (g.Amount > 50) + { + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, "I cannot accept so large a tip!", + from.NetState); + } + else + { + string tip = TipMessage; + + if (tip == null || (tip = tip.Trim()).Length == 0) + { + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, + "It would not be fair of me to take your money and not offer you information in return.", + from.NetState); + } + else + { + Direction = GetDirectionTo(from); + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, tip, from.NetState); + + g.Delete(); + return true; + } + } + } + + return false; + } + + public bool IsOwner(Mobile from) + { + if (from == null || from.Deleted || Deleted) + return false; + + if (from.AccessLevel > AccessLevel.GameMaster) + return true; + + return Owner == from; + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + + if (IsOwner(from) && from.InLOS(this)) + list.Add(new ManageBarkeeperEntry(from, this)); + } + + public void BeginManagement(Mobile from) + { + if (!IsOwner(from)) + return; + + from.SendGump(new BarkeeperGump(from, this)); + } + + public void Dismiss() + { + Delete(); + } + + public void BeginChangeRumor(Mobile from, int index) + { + if (index < 0 || index >= Rumors.Length) + return; + + from.Prompt = new ChangeRumorMessagePrompt(this, index); + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, "Say what news you would like me to tell our guests.", + from.NetState); + } + + public void EndChangeRumor(Mobile from, int index, string text) + { + if (index < 0 || index >= Rumors.Length) + return; + + if (Rumors[index] == null) + Rumors[index] = new BarkeeperRumor(text, null); + else + Rumors[index].Message = text; + + from.Prompt = new ChangeRumorKeywordPrompt(this, index); + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, + "What keyword should a guest say to me to get this news?", from.NetState); + } + + public void EndChangeKeyword(Mobile from, int index, string text) + { + if (index < 0 || index >= Rumors.Length) + return; + + if (Rumors[index] == null) + Rumors[index] = new BarkeeperRumor(null, text); + else + Rumors[index].Keyword = text; + + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, "I'll pass on the message.", from.NetState); + } + + public void RemoveRumor(Mobile from, int index) + { + if (index < 0 || index >= Rumors.Length) + return; + + Rumors[index] = null; + } + + public void BeginChangeTip(Mobile from) + { + from.Prompt = new ChangeTipMessagePrompt(this); + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, + "Say what you want me to tell guests when they give me a good tip.", from.NetState); + } + + public void EndChangeTip(Mobile from, string text) + { + TipMessage = text; + PrivateOverheadMessage(MessageType.Regular, 0x3B2, false, "I'll say that to anyone who gives me a good tip.", + from.NetState); + } + + public void RemoveTip(Mobile from) + { + TipMessage = null; + } + + public void BeginChangeTitle(Mobile from) + { + from.SendGump(new BarkeeperTitleGump(from, this)); + } + + public void EndChangeTitle(Mobile from, string title, bool vendor) + { + Title = title; + + LoadSBInfo(); + } + + public void CancelChangeTitle(Mobile from) + { + from.SendGump(new BarkeeperGump(from, this)); + } + + public void BeginChangeAppearance(Mobile from) + { + from.CloseGump(typeof(PlayerVendorCustomizeGump)); + from.SendGump(new PlayerVendorCustomizeGump(this, from)); + } + + public void ChangeGender(Mobile from) + { + Female = !Female; + + if (Female) + { + Body = 401; + Name = NameList.RandomName("female"); + + FacialHairItemID = 0; + } + else + { + Body = 400; + Name = NameList.RandomName("male"); + } + } + + public override void InitSBInfo() + { + if (Title == "the waiter" || Title == "the barkeeper" || Title == "the baker" || Title == "the innkeeper" || + Title == "the chef") + { + if (m_SBInfos.Count == 0) + m_SBInfos.Add(new SBPlayerBarkeeper()); + } + else + { + m_SBInfos.Clear(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version; + + writer.Write(m_House); + + writer.Write(Owner); + + writer.WriteEncodedInt(Rumors.Length); + + for (int i = 0; i < Rumors.Length; ++i) + BarkeeperRumor.Serialize(writer, Rumors[i]); + + writer.Write(TipMessage); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + House = (BaseHouse)reader.ReadItem(); + + goto case 0; + } + case 0: + { + Owner = reader.ReadMobile(); + + Rumors = new BarkeeperRumor[reader.ReadEncodedInt()]; + + for (int i = 0; i < Rumors.Length; ++i) + Rumors[i] = BarkeeperRumor.Deserialize(reader); + + TipMessage = reader.ReadString(); + + break; + } + } + + if (version < 1) + Timer.DelayCall(TimeSpan.Zero, UpgradeFromVersion0); + } + + private void UpgradeFromVersion0() + { + House = BaseHouse.FindHouseAt(this); + } + } + + public class BarkeeperTitleGump : Gump + { + private static Entry[] m_Entries = + { + new Entry("Alchemist"), + new Entry("Animal Tamer"), + new Entry("Apothecary"), + new Entry("Artist"), + new Entry("Baker", true), + new Entry("Bard"), + new Entry("Barkeep", "the barkeeper", true), + new Entry("Beggar"), + new Entry("Blacksmith"), + new Entry("Bounty Hunter"), + new Entry("Brigand"), + new Entry("Butler"), + new Entry("Carpenter"), + new Entry("Chef", true), + new Entry("Commander"), + new Entry("Curator"), + new Entry("Drunkard"), + new Entry("Farmer"), + new Entry("Fisherman"), + new Entry("Gambler"), + new Entry("Gypsy"), + new Entry("Herald"), + new Entry("Herbalist"), + new Entry("Hermit"), + new Entry("Innkeeper", true), + new Entry("Jailor"), + new Entry("Jester"), + new Entry("Librarian"), + new Entry("Mage"), + new Entry("Mercenary"), + new Entry("Merchant"), + new Entry("Messenger"), + new Entry("Miner"), + new Entry("Monk"), + new Entry("Noble"), + new Entry("Paladin"), + new Entry("Peasant"), + new Entry("Pirate"), + new Entry("Prisoner"), + new Entry("Prophet"), + new Entry("Ranger"), + new Entry("Sage"), + new Entry("Sailor"), + new Entry("Scholar"), + new Entry("Scribe"), + new Entry("Sentry"), + new Entry("Servant"), + new Entry("Shepherd"), + new Entry("Soothsayer"), + new Entry("Stoic"), + new Entry("Storyteller"), + new Entry("Tailor"), + new Entry("Thief"), + new Entry("Tinker"), + new Entry("Town Crier"), + new Entry("Treasure Hunter"), + new Entry("Waiter", true), + new Entry("Warrior"), + new Entry("Watchman"), + new Entry("No Title", null, false) + }; + + private PlayerBarkeeper m_Barkeeper; + private Mobile m_From; + + public BarkeeperTitleGump(Mobile from, PlayerBarkeeper barkeeper) : base(0, 0) + { + m_From = from; + m_Barkeeper = barkeeper; + + from.CloseGump(typeof(BarkeeperGump)); + from.CloseGump(typeof(BarkeeperTitleGump)); + + Entry[] entries = m_Entries; + + RenderBackground(); + + int pageCount = (entries.Length + 19) / 20; + + for (int i = 0; i < pageCount; ++i) + RenderPage(entries, i); + } + + private void RenderBackground() + { + AddPage(0); + + AddBackground(30, 40, 585, 410, 5054); + + AddImage(30, 40, 9251); + AddImage(180, 40, 9251); + AddImage(30, 40, 9253); + AddImage(30, 130, 9253); + AddImage(598, 40, 9255); + AddImage(598, 130, 9255); + AddImage(30, 433, 9257); + AddImage(180, 433, 9257); + AddImage(30, 40, 9250); + AddImage(598, 40, 9252); + AddImage(598, 433, 9258); + AddImage(30, 433, 9256); + + AddItem(30, 40, 6816); + AddItem(30, 125, 6817); + AddItem(30, 233, 6817); + AddItem(30, 341, 6817); + AddItem(580, 40, 6814); + AddItem(588, 125, 6815); + AddItem(588, 233, 6815); + AddItem(588, 341, 6815); + + AddImage(560, 20, 1417); + AddItem(580, 44, 4033); + + AddBackground(183, 25, 280, 30, 5054); + + AddImage(180, 25, 10460); + AddImage(434, 25, 10460); + + AddHtml(223, 32, 200, 40, "BARKEEP CUSTOMIZATION MENU", false, false); + AddBackground(243, 433, 150, 30, 5054); + + AddImage(240, 433, 10460); + AddImage(375, 433, 10460); + + AddImage(80, 398, 2151); + AddItem(72, 406, 2543); + + AddHtml(110, 412, 180, 25, "sells food and drink", false, false); + } + + private void RenderPage(Entry[] entries, int page) + { + AddPage(1 + page); + + AddHtml(430, 70, 180, 25, $"Page {page + 1} of {(entries.Length + 19) / 20}", false, false); + + for (int count = 0, i = page * 20; count < 20 && i < entries.Length; ++count, ++i) + { + Entry entry = entries[i]; + + AddButton(80 + count / 10 * 260, 100 + count % 10 * 30, 4005, 4007, 2 + i, GumpButtonType.Reply, 0); + AddHtml(120 + count / 10 * 260, 100 + count % 10 * 30, entry.m_Vendor ? 148 : 180, 25, entry.m_Description, + true, false); + + if (entry.m_Vendor) + { + AddImage(270 + count / 10 * 260, 98 + count % 10 * 30, 2151); + AddItem(262 + count / 10 * 260, 106 + count % 10 * 30, 2543); + } + } + + AddButton(340, 400, 4005, 4007, 0, GumpButtonType.Page, 1 + (page + 1) % ((entries.Length + 19) / 20)); + AddHtml(380, 400, 180, 25, "More Job Titles", false, false); + + AddButton(338, 437, 4014, 4016, 1, GumpButtonType.Reply, 0); + AddHtml(290, 440, 35, 40, "Back", false, false); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int buttonID = info.ButtonID; + + if (buttonID > 0) + { + --buttonID; + + if (buttonID > 0) + { + --buttonID; + + if (buttonID >= 0 && buttonID < m_Entries.Length) + m_Barkeeper.EndChangeTitle(m_From, m_Entries[buttonID].m_Title, m_Entries[buttonID].m_Vendor); + } + else + { + m_Barkeeper.CancelChangeTitle(m_From); + } + } + } + + private class Entry + { + public string m_Description; + public string m_Title; + public bool m_Vendor; + + public Entry(string desc) : this(desc, $"the {desc.ToLower()}", false) + { + } + + public Entry(string desc, bool vendor) : this(desc, $"the {desc.ToLower()}", vendor) + { + } + + public Entry(string desc, string title, bool vendor) + { + m_Description = desc; + m_Title = title; + m_Vendor = vendor; + } + } + } + + public class BarkeeperGump : Gump + { + private PlayerBarkeeper m_Barkeeper; + private Mobile m_From; + + public BarkeeperGump(Mobile from, PlayerBarkeeper barkeeper) : base(0, 0) + { + m_From = from; + m_Barkeeper = barkeeper; + + from.CloseGump(typeof(BarkeeperGump)); + from.CloseGump(typeof(BarkeeperTitleGump)); + + RenderBackground(); + RenderCategories(); + RenderMessageManagement(); + RenderDismissConfirmation(); + RenderMessageManagement_Message_AddOrChange(); + RenderMessageManagement_Message_Remove(); + RenderMessageManagement_Tip_AddOrChange(); + RenderMessageManagement_Tip_Remove(); + RenderAppearanceCategories(); + } + + public void RenderBackground() + { + AddPage(0); + + AddBackground(30, 40, 585, 410, 5054); + + AddImage(30, 40, 9251); + AddImage(180, 40, 9251); + AddImage(30, 40, 9253); + AddImage(30, 130, 9253); + AddImage(598, 40, 9255); + AddImage(598, 130, 9255); + AddImage(30, 433, 9257); + AddImage(180, 433, 9257); + AddImage(30, 40, 9250); + AddImage(598, 40, 9252); + AddImage(598, 433, 9258); + AddImage(30, 433, 9256); + + AddItem(30, 40, 6816); + AddItem(30, 125, 6817); + AddItem(30, 233, 6817); + AddItem(30, 341, 6817); + AddItem(580, 40, 6814); + AddItem(588, 125, 6815); + AddItem(588, 233, 6815); + AddItem(588, 341, 6815); + + AddBackground(183, 25, 280, 30, 5054); + + AddImage(180, 25, 10460); + AddImage(434, 25, 10460); + AddImage(560, 20, 1417); + + AddHtml(223, 32, 200, 40, "BARKEEP CUSTOMIZATION MENU", false, false); + AddBackground(243, 433, 150, 30, 5054); + + AddImage(240, 433, 10460); + AddImage(375, 433, 10460); + } + + public void RenderCategories() + { + AddPage(1); + + AddButton(130, 120, 4005, 4007, 0, GumpButtonType.Page, 2); + AddHtml(170, 120, 200, 40, "Message Control", false, false); - public class BarkeeperGump : Gump - { - private Mobile m_From; - private PlayerBarkeeper m_Barkeeper; + AddButton(130, 200, 4005, 4007, 0, GumpButtonType.Page, 8); + AddHtml(170, 200, 200, 40, "Customize your barkeep", false, false); - public void RenderBackground() - { - AddPage( 0 ); + AddButton(130, 280, 4005, 4007, 0, GumpButtonType.Page, 3); + AddHtml(170, 280, 200, 40, "Dismiss your barkeep", false, false); - AddBackground( 30, 40, 585, 410, 5054 ); + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Reply, 0); + AddHtml(290, 440, 35, 40, "Back", false, false); - AddImage( 30, 40, 9251 ); - AddImage( 180, 40, 9251 ); - AddImage( 30, 40, 9253 ); - AddImage( 30, 130, 9253 ); - AddImage( 598, 40, 9255 ); - AddImage( 598, 130, 9255 ); - AddImage( 30, 433, 9257 ); - AddImage( 180, 433, 9257 ); - AddImage( 30, 40, 9250 ); - AddImage( 598, 40, 9252 ); - AddImage( 598, 433, 9258 ); - AddImage( 30, 433, 9256 ); + AddItem(574, 43, 5360); + } - AddItem( 30, 40, 6816 ); - AddItem( 30, 125, 6817 ); - AddItem( 30, 233, 6817 ); - AddItem( 30, 341, 6817 ); - AddItem( 580, 40, 6814 ); - AddItem( 588, 125, 6815 ); - AddItem( 588, 233, 6815 ); - AddItem( 588, 341, 6815 ); + public void RenderMessageManagement() + { + AddPage(2); - AddBackground( 183, 25, 280, 30, 5054 ); + AddButton(130, 120, 4005, 4007, 0, GumpButtonType.Page, 4); + AddHtml(170, 120, 380, 20, "Add or change a message and keyword", false, false); - AddImage( 180, 25, 10460 ); - AddImage( 434, 25, 10460 ); - AddImage( 560, 20, 1417 ); + AddButton(130, 200, 4005, 4007, 0, GumpButtonType.Page, 5); + AddHtml(170, 200, 380, 20, "Remove a message and keyword from your barkeep", false, false); - AddHtml( 223, 32, 200, 40, "BARKEEP CUSTOMIZATION MENU", false, false ); - AddBackground( 243, 433, 150, 30, 5054 ); + AddButton(130, 280, 4005, 4007, 0, GumpButtonType.Page, 6); + AddHtml(170, 280, 380, 20, "Add or change your barkeeper's tip message", false, false); - AddImage( 240, 433, 10460 ); - AddImage( 375, 433, 10460 ); - } + AddButton(130, 360, 4005, 4007, 0, GumpButtonType.Page, 7); + AddHtml(170, 360, 380, 20, "Delete your barkeepers tip message", false, false); - public void RenderCategories() - { - AddPage( 1 ); + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 1); + AddHtml(290, 440, 35, 40, "Back", false, false); - AddButton( 130, 120, 4005, 4007, 0, GumpButtonType.Page, 2 ); - AddHtml( 170, 120, 200, 40, "Message Control", false, false ); + AddItem(580, 46, 4030); + } - AddButton( 130, 200, 4005, 4007, 0, GumpButtonType.Page, 8 ); - AddHtml( 170, 200, 200, 40, "Customize your barkeep", false, false ); + public void RenderDismissConfirmation() + { + AddPage(3); - AddButton( 130, 280, 4005, 4007, 0, GumpButtonType.Page, 3 ); - AddHtml( 170, 280, 200, 40, "Dismiss your barkeep", false, false ); + AddHtml(170, 160, 380, 20, "Are you sure you want to dismiss your barkeeper?", false, false); - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Reply, 0 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); + AddButton(205, 280, 4005, 4007, GetButtonID(0, 0), GumpButtonType.Reply, 0); + AddHtml(240, 280, 100, 20, @"Yes", false, false); - AddItem( 574, 43, 5360 ); - } + AddButton(395, 280, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtml(430, 280, 100, 20, "No", false, false); - public void RenderMessageManagement() - { - AddPage( 2 ); + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 1); + AddHtml(290, 440, 35, 40, "Back", false, false); - AddButton( 130, 120, 4005, 4007, 0, GumpButtonType.Page, 4 ); - AddHtml( 170, 120, 380, 20, "Add or change a message and keyword", false, false ); + AddItem(574, 43, 5360); + AddItem(584, 34, 6579); + } - AddButton( 130, 200, 4005, 4007, 0, GumpButtonType.Page, 5 ); - AddHtml( 170, 200, 380, 20, "Remove a message and keyword from your barkeep", false, false ); + public void RenderMessageManagement_Message_AddOrChange() + { + AddPage(4); - AddButton( 130, 280, 4005, 4007, 0, GumpButtonType.Page, 6 ); - AddHtml( 170, 280, 380, 20, "Add or change your barkeeper's tip message", false, false ); + AddHtml(250, 60, 500, 25, "Add or change a message", false, false); - AddButton( 130, 360, 4005, 4007, 0, GumpButtonType.Page, 7 ); - AddHtml( 170, 360, 380, 20, "Delete your barkeepers tip message", false, false ); + BarkeeperRumor[] rumors = m_Barkeeper.Rumors; - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 1 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); + for (int i = 0; i < rumors.Length; ++i) + { + BarkeeperRumor rumor = rumors[i]; - AddItem( 580, 46, 4030 ); - } + AddHtml(100, 70 + i * 120, 50, 20, "Message", false, false); + AddHtml(100, 90 + i * 120, 450, 40, rumor == null ? "No current message" : rumor.Message, true, false); + AddHtml(100, 130 + i * 120, 50, 20, "Keyword", false, false); + AddHtml(100, 150 + i * 120, 450, 40, rumor == null ? "None" : rumor.Keyword, true, false); - public void RenderDismissConfirmation() - { - AddPage( 3 ); + AddButton(60, 90 + i * 120, 4005, 4007, GetButtonID(1, i), GumpButtonType.Reply, 0); + } - AddHtml( 170, 160, 380, 20, "Are you sure you want to dismiss your barkeeper?", false, false ); + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 2); + AddHtml(290, 440, 35, 40, "Back", false, false); - AddButton( 205, 280, 4005, 4007, GetButtonID( 0, 0 ), GumpButtonType.Reply, 0 ); - AddHtml( 240, 280, 100, 20,@"Yes", false, false ); + AddItem(580, 46, 4030); + } - AddButton( 395, 280, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtml( 430, 280, 100, 20, "No", false, false ); + public void RenderMessageManagement_Message_Remove() + { + AddPage(5); - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 1 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); + AddHtml(190, 60, 500, 25, "Choose the message you would like to remove", false, false); - AddItem( 574, 43, 5360 ); - AddItem( 584, 34, 6579 ); - } + BarkeeperRumor[] rumors = m_Barkeeper.Rumors; - public void RenderMessageManagement_Message_AddOrChange() - { - AddPage( 4 ); + for (int i = 0; i < rumors.Length; ++i) + { + BarkeeperRumor rumor = rumors[i]; - AddHtml( 250, 60, 500, 25, "Add or change a message", false, false ); + AddHtml(100, 70 + i * 120, 50, 20, "Message", false, false); + AddHtml(100, 90 + i * 120, 450, 40, rumor == null ? "No current message" : rumor.Message, true, false); + AddHtml(100, 130 + i * 120, 50, 20, "Keyword", false, false); + AddHtml(100, 150 + i * 120, 450, 40, rumor == null ? "None" : rumor.Keyword, true, false); - BarkeeperRumor[] rumors = m_Barkeeper.Rumors; + AddButton(60, 90 + i * 120, 4005, 4007, GetButtonID(2, i), GumpButtonType.Reply, 0); + } - for ( int i = 0; i < rumors.Length; ++i ) - { - BarkeeperRumor rumor = rumors[i]; + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 2); + AddHtml(290, 440, 35, 40, "Back", false, false); - AddHtml( 100, 70 + (i * 120), 50, 20, "Message", false, false ); - AddHtml( 100, 90 + (i * 120), 450, 40, rumor == null ? "No current message" : rumor.Message, true, false ); - AddHtml( 100, 130 + (i * 120), 50, 20, "Keyword", false, false ); - AddHtml( 100, 150 + (i * 120), 450, 40, rumor == null ? "None" : rumor.Keyword, true, false ); + AddItem(580, 46, 4030); + } - AddButton( 60, 90 + (i * 120), 4005, 4007, GetButtonID( 1, i ), GumpButtonType.Reply, 0 ); - } + private int GetButtonID(int type, int index) + { + return 1 + index * 6 + type; + } - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 2 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); + private void RenderMessageManagement_Tip_AddOrChange() + { + AddPage(6); - AddItem( 580, 46, 4030 ); - } + AddHtml(250, 95, 500, 20, "Change this tip message", false, false); + AddHtml(100, 190, 50, 20, "Message", false, false); + AddHtml(100, 210, 450, 40, m_Barkeeper.TipMessage ?? "No current message", true, false); - public void RenderMessageManagement_Message_Remove() - { - AddPage( 5 ); - - AddHtml( 190, 60, 500, 25, "Choose the message you would like to remove", false, false ); - - BarkeeperRumor[] rumors = m_Barkeeper.Rumors; - - for ( int i = 0; i < rumors.Length; ++i ) - { - BarkeeperRumor rumor = rumors[i]; - - AddHtml( 100, 70 + (i * 120), 50, 20, "Message", false, false ); - AddHtml( 100, 90 + (i * 120), 450, 40, rumor == null ? "No current message" : rumor.Message, true, false ); - AddHtml( 100, 130 + (i * 120), 50, 20, "Keyword", false, false ); - AddHtml( 100, 150 + (i * 120), 450, 40, rumor == null ? "None" : rumor.Keyword, true, false ); - - AddButton( 60, 90 + (i * 120), 4005, 4007, GetButtonID( 2, i ), GumpButtonType.Reply, 0 ); - } - - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 2 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); - - AddItem( 580, 46, 4030 ); - } - - private int GetButtonID( int type, int index ) - { - return 1 + (index * 6) + type; - } - - private void RenderMessageManagement_Tip_AddOrChange() - { - AddPage( 6 ); - - AddHtml( 250, 95, 500, 20, "Change this tip message", false, false ); - AddHtml( 100, 190, 50, 20, "Message", false, false ); - AddHtml( 100, 210, 450, 40, m_Barkeeper.TipMessage ?? "No current message", true, false ); - - AddButton( 60, 210, 4005, 4007, GetButtonID( 3, 0 ), GumpButtonType.Reply, 0 ); - - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 2 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); - - AddItem( 580, 46, 4030 ); - } - - private void RenderMessageManagement_Tip_Remove() - { - AddPage( 7 ); - - AddHtml( 250, 95, 500, 20, "Remove this tip message", false, false ); - AddHtml( 100, 190, 50, 20, "Message", false, false ); - AddHtml( 100, 210, 450, 40, m_Barkeeper.TipMessage ?? "No current message", true, false ); - - AddButton( 60, 210, 4005, 4007, GetButtonID( 4, 0 ), GumpButtonType.Reply, 0 ); - - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 2 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); - - AddItem( 580, 46, 4030 ); - } - - private void RenderAppearanceCategories() - { - AddPage( 8 ); - - AddButton( 130, 120, 4005, 4007, GetButtonID( 5, 0 ), GumpButtonType.Reply, 0 ); - AddHtml( 170, 120, 120, 20, "Title", false, false ); - - if ( m_Barkeeper.BodyValue != 0x340 && m_Barkeeper.BodyValue != 0x402 ) { - AddButton( 130, 200, 4005, 4007, GetButtonID( 5, 1 ), GumpButtonType.Reply, 0 ); - AddHtml( 170, 200, 120, 20, "Appearance", false, false ); - - AddButton( 130, 280, 4005, 4007, GetButtonID( 5, 2 ), GumpButtonType.Reply, 0 ); - AddHtml( 170, 280, 120, 20, "Male / Female", false, false ); - - AddButton( 338, 437, 4014, 4016, 0, GumpButtonType.Page, 1 ); - AddHtml( 290, 440, 35, 40, "Back", false, false ); - } - - AddItem( 580, 44, 4033 ); - } - - public BarkeeperGump( Mobile from, PlayerBarkeeper barkeeper ) : base( 0, 0 ) - { - m_From = from; - m_Barkeeper = barkeeper; - - from.CloseGump( typeof( BarkeeperGump ) ); - from.CloseGump( typeof( BarkeeperTitleGump ) ); - - RenderBackground(); - RenderCategories(); - RenderMessageManagement(); - RenderDismissConfirmation(); - RenderMessageManagement_Message_AddOrChange(); - RenderMessageManagement_Message_Remove(); - RenderMessageManagement_Tip_AddOrChange(); - RenderMessageManagement_Tip_Remove(); - RenderAppearanceCategories(); - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( !m_Barkeeper.IsOwner( m_From ) ) - return; - - int index = info.ButtonID - 1; - - if ( index < 0 ) - return; - - int type = index % 6; - index /= 6; - - switch ( type ) - { - case 0: // Controls - { - switch ( index ) - { - case 0: // Dismiss - { - m_Barkeeper.Dismiss(); - break; - } - } - - break; - } - case 1: // Change message - { - m_Barkeeper.BeginChangeRumor( m_From, index ); - break; - } - case 2: // Remove message - { - m_Barkeeper.RemoveRumor( m_From, index ); - break; - } - case 3: // Change tip - { - m_Barkeeper.BeginChangeTip( m_From ); - break; - } - case 4: // Remove tip - { - m_Barkeeper.RemoveTip( m_From ); - break; - } - case 5: // Appearance category selection - { - switch ( index ) - { - case 0: m_Barkeeper.BeginChangeTitle( m_From ); break; - case 1: m_Barkeeper.BeginChangeAppearance( m_From ); break; - case 2: m_Barkeeper.ChangeGender( m_From ); break; - } - - break; - } - } - } - } -} + AddButton(60, 210, 4005, 4007, GetButtonID(3, 0), GumpButtonType.Reply, 0); + + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 2); + AddHtml(290, 440, 35, 40, "Back", false, false); + + AddItem(580, 46, 4030); + } + + private void RenderMessageManagement_Tip_Remove() + { + AddPage(7); + + AddHtml(250, 95, 500, 20, "Remove this tip message", false, false); + AddHtml(100, 190, 50, 20, "Message", false, false); + AddHtml(100, 210, 450, 40, m_Barkeeper.TipMessage ?? "No current message", true, false); + + AddButton(60, 210, 4005, 4007, GetButtonID(4, 0), GumpButtonType.Reply, 0); + + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 2); + AddHtml(290, 440, 35, 40, "Back", false, false); + + AddItem(580, 46, 4030); + } + + private void RenderAppearanceCategories() + { + AddPage(8); + + AddButton(130, 120, 4005, 4007, GetButtonID(5, 0), GumpButtonType.Reply, 0); + AddHtml(170, 120, 120, 20, "Title", false, false); + + if (m_Barkeeper.BodyValue != 0x340 && m_Barkeeper.BodyValue != 0x402) + { + AddButton(130, 200, 4005, 4007, GetButtonID(5, 1), GumpButtonType.Reply, 0); + AddHtml(170, 200, 120, 20, "Appearance", false, false); + + AddButton(130, 280, 4005, 4007, GetButtonID(5, 2), GumpButtonType.Reply, 0); + AddHtml(170, 280, 120, 20, "Male / Female", false, false); + + AddButton(338, 437, 4014, 4016, 0, GumpButtonType.Page, 1); + AddHtml(290, 440, 35, 40, "Back", false, false); + } + + AddItem(580, 44, 4033); + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (!m_Barkeeper.IsOwner(m_From)) + return; + + int index = info.ButtonID - 1; + + if (index < 0) + return; + + int type = index % 6; + index /= 6; + + switch (type) + { + case 0: // Controls + { + switch (index) + { + case 0: // Dismiss + { + m_Barkeeper.Dismiss(); + break; + } + } + + break; + } + case 1: // Change message + { + m_Barkeeper.BeginChangeRumor(m_From, index); + break; + } + case 2: // Remove message + { + m_Barkeeper.RemoveRumor(m_From, index); + break; + } + case 3: // Change tip + { + m_Barkeeper.BeginChangeTip(m_From); + break; + } + case 4: // Remove tip + { + m_Barkeeper.RemoveTip(m_From); + break; + } + case 5: // Appearance category selection + { + switch (index) + { + case 0: + m_Barkeeper.BeginChangeTitle(m_From); + break; + case 1: + m_Barkeeper.BeginChangeAppearance(m_From); + break; + case 2: + m_Barkeeper.ChangeGender(m_From); + break; + } + + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/PlayerVendor.cs b/Scripts/Mobiles/Vendors/PlayerVendor.cs index a8fe8077e..8d2b15988 100644 --- a/Scripts/Mobiles/Vendors/PlayerVendor.cs +++ b/Scripts/Mobiles/Vendors/PlayerVendor.cs @@ -1,1680 +1,1617 @@ using System; using System.Collections.Generic; using System.Globalization; -using Server.Items; +using Server.ContextMenus; +using Server.Engines.BulkOrders; +using Server.Ethics; using Server.Gumps; -using Server.Prompts; -using Server.Targeting; +using Server.Items; using Server.Misc; using Server.Multis; -using Server.ContextMenus; +using Server.Prompts; +using Server.Targeting; namespace Server.Mobiles { - [AttributeUsage( AttributeTargets.Class )] - public class PlayerVendorTargetAttribute : Attribute - { - public PlayerVendorTargetAttribute() - { - } - } - - public class VendorItem - { - private string m_Description; - - public Item Item { get; } - - public int Price { get; } - - public string FormattedPrice - { - get - { - if ( Core.ML ) - return Price.ToString( "N0", CultureInfo.GetCultureInfo( "en-US" ) ); - - return Price.ToString(); - } - } - - public string Description - { - get => m_Description; - set - { - if ( value != null ) - m_Description = value; - else - m_Description = ""; - - if ( Valid ) - Item.InvalidateProperties(); - } - } - - public DateTime Created { get; } - - public bool IsForSale => Price >= 0; - public bool IsForFree => Price == 0; - - public bool Valid { get; private set; } - - public VendorItem( Item item, int price, string description, DateTime created ) - { - Item = item; - Price = price; - - if ( description != null ) - m_Description = description; - else - m_Description = ""; - - Created = created; - - Valid = true; - } - - public void Invalidate() - { - Valid = false; - } - } - - public class VendorBackpack : Backpack - { - public VendorBackpack() - { - Layer = Layer.Backpack; - Weight = 1.0; - } + [AttributeUsage(AttributeTargets.Class)] + public class PlayerVendorTargetAttribute : Attribute + { + } + + public class VendorItem + { + private string m_Description; + + public VendorItem(Item item, int price, string description, DateTime created) + { + Item = item; + Price = price; + + if (description != null) + m_Description = description; + else + m_Description = ""; + + Created = created; + + Valid = true; + } + + public Item Item{ get; } + + public int Price{ get; } + + public string FormattedPrice + { + get + { + if (Core.ML) + return Price.ToString("N0", CultureInfo.GetCultureInfo("en-US")); + + return Price.ToString(); + } + } + + public string Description + { + get => m_Description; + set + { + if (value != null) + m_Description = value; + else + m_Description = ""; - public override int DefaultMaxWeight => 0; + if (Valid) + Item.InvalidateProperties(); + } + } - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if ( !base.CheckHold( m, item, message, checkItems, plusItems, plusWeight ) ) - return false; + public DateTime Created{ get; } + + public bool IsForSale => Price >= 0; + public bool IsForFree => Price == 0; - if ( Ethics.Ethic.IsImbued( item, true ) ) - { - if ( message ) - m.SendMessage( "Imbued items may not be sold here." ); - - return false; - } - - if ( !BaseHouse.NewVendorSystem && Parent is PlayerVendor ) - { - BaseHouse house = ((PlayerVendor)Parent).House; + public bool Valid{ get; private set; } - if ( house != null && house.IsAosRules && !house.CheckAosStorage( 1 + item.TotalItems + plusItems ) ) - { - if ( message ) - m.SendLocalizedMessage( 1061839 ); // This action would exceed the secure storage limit of the house. + public void Invalidate() + { + Valid = false; + } + } - return false; - } - } + public class VendorBackpack : Backpack + { + public VendorBackpack() + { + Layer = Layer.Backpack; + Weight = 1.0; + } - return true; - } + public VendorBackpack(Serial serial) : base(serial) + { + } - public override bool IsAccessibleTo( Mobile m ) - { - return true; - } + public override int DefaultMaxWeight => 0; - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( !base.CheckItemUse( from, item ) ) - return false; - - if ( item is Container || item is Engines.BulkOrders.BulkOrderBook ) - return true; + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (!base.CheckHold(m, item, message, checkItems, plusItems, plusWeight)) + return false; - from.SendLocalizedMessage( 500447 ); // That is not accessible. - return false; - } - - public override bool CheckTarget( Mobile from, Target targ, object targeted ) - { - if ( !base.CheckTarget( from, targ, targeted ) ) - return false; + if (Ethic.IsImbued(item, true)) + { + if (message) + m.SendMessage("Imbued items may not be sold here."); - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; + return false; + } - return targ.GetType().IsDefined( typeof( PlayerVendorTargetAttribute ), false ); - } + if (!BaseHouse.NewVendorSystem && Parent is PlayerVendor) + { + BaseHouse house = ((PlayerVendor)Parent).House; - public override void GetChildContextMenuEntries( Mobile from, List list, Item item ) - { - base.GetChildContextMenuEntries( from, list, item ); + if (house != null && house.IsAosRules && !house.CheckAosStorage(1 + item.TotalItems + plusItems)) + { + if (message) + m.SendLocalizedMessage(1061839); // This action would exceed the secure storage limit of the house. - PlayerVendor pv = RootParent as PlayerVendor; + return false; + } + } - if ( pv == null || pv.IsOwner( from ) ) - return; + return true; + } - VendorItem vi = pv.GetVendorItem( item ); + public override bool IsAccessibleTo(Mobile m) + { + return true; + } - if ( vi != null ) - list.Add( new BuyEntry( item ) ); - } + public override bool CheckItemUse(Mobile from, Item item) + { + if (!base.CheckItemUse(from, item)) + return false; - private class BuyEntry : ContextMenuEntry - { - private Item m_Item; + if (item is Container || item is BulkOrderBook) + return true; - public BuyEntry( Item item ) : base( 6103 ) - { - m_Item = item; - } + from.SendLocalizedMessage(500447); // That is not accessible. + return false; + } - public override bool NonLocalUse => true; + public override bool CheckTarget(Mobile from, Target targ, object targeted) + { + if (!base.CheckTarget(from, targ, targeted)) + return false; - public override void OnClick() - { - if ( m_Item.Deleted ) - return; + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; - PlayerVendor.TryToBuy( m_Item, Owner.From ); - } - } + return targ.GetType().IsDefined(typeof(PlayerVendorTargetAttribute), false); + } - public override void GetChildNameProperties( ObjectPropertyList list, Item item ) - { - base.GetChildNameProperties( list, item ); + public override void GetChildContextMenuEntries(Mobile from, List list, Item item) + { + base.GetChildContextMenuEntries(from, list, item); - PlayerVendor pv = RootParent as PlayerVendor; + PlayerVendor pv = RootParent as PlayerVendor; - VendorItem vi = pv?.GetVendorItem( item ); + if (pv == null || pv.IsOwner(from)) + return; - if ( vi == null ) - return; + VendorItem vi = pv.GetVendorItem(item); - if ( !vi.IsForSale ) - list.Add( 1043307 ); // Price: Not for sale. - else if ( vi.IsForFree ) - list.Add( 1043306 ); // Price: FREE! - else - list.Add( 1043304, vi.FormattedPrice ); // Price: ~1_COST~ - } + if (vi != null) + list.Add(new BuyEntry(item)); + } - public override void GetChildProperties( ObjectPropertyList list, Item item ) - { - base.GetChildProperties( list, item ); + public override void GetChildNameProperties(ObjectPropertyList list, Item item) + { + base.GetChildNameProperties(list, item); - PlayerVendor pv = RootParent as PlayerVendor; + PlayerVendor pv = RootParent as PlayerVendor; - VendorItem vi = pv?.GetVendorItem( item ); + VendorItem vi = pv?.GetVendorItem(item); - if ( vi?.Description != null && vi.Description.Length > 0 ) - list.Add( 1043305, vi.Description ); //
Seller's Description:
"~1_DESC~" - } + if (vi == null) + return; - public override void OnSingleClickContained( Mobile from, Item item ) - { - if ( RootParent is PlayerVendor ) - { - PlayerVendor vendor = (PlayerVendor)RootParent; + if (!vi.IsForSale) + list.Add(1043307); // Price: Not for sale. + else if (vi.IsForFree) + list.Add(1043306); // Price: FREE! + else + list.Add(1043304, vi.FormattedPrice); // Price: ~1_COST~ + } - VendorItem vi = vendor.GetVendorItem( item ); + public override void GetChildProperties(ObjectPropertyList list, Item item) + { + base.GetChildProperties(list, item); - if ( vi != null ) - { - if ( !vi.IsForSale ) - item.LabelTo( from, 1043307 ); // Price: Not for sale. - else if ( vi.IsForFree ) - item.LabelTo( from, 1043306 ); // Price: FREE! - else - item.LabelTo( from, 1043304, vi.FormattedPrice ); // Price: ~1_COST~ + PlayerVendor pv = RootParent as PlayerVendor; - if ( !string.IsNullOrEmpty( vi.Description ) ) - { - // The localized message (1043305) is no longer valid -
Seller's Description:
"~1_DESC~" - item.LabelTo( from, "Description: {0}", vi.Description ); - } - } - } + VendorItem vi = pv?.GetVendorItem(item); - base.OnSingleClickContained( from, item ); - } + if (vi?.Description != null && vi.Description.Length > 0) + list.Add(1043305, vi.Description); //
Seller's Description:
"~1_DESC~" + } - public VendorBackpack( Serial serial ) : base( serial ) - { - } + public override void OnSingleClickContained(Mobile from, Item item) + { + if (RootParent is PlayerVendor) + { + PlayerVendor vendor = (PlayerVendor)RootParent; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + VendorItem vi = vendor.GetVendorItem(item); - writer.Write( (int) 0 ); // version - } + if (vi != null) + { + if (!vi.IsForSale) + item.LabelTo(from, 1043307); // Price: Not for sale. + else if (vi.IsForFree) + item.LabelTo(from, 1043306); // Price: FREE! + else + item.LabelTo(from, 1043304, vi.FormattedPrice); // Price: ~1_COST~ - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (!string.IsNullOrEmpty(vi.Description)) item.LabelTo(from, "Description: {0}", vi.Description); + } + } - int version = reader.ReadInt(); - } - } + base.OnSingleClickContained(from, item); + } - public class PlayerVendor : Mobile - { - private Dictionary m_SellItems; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - private BaseHouse m_House; + writer.Write(0); // version + } - private string m_ShopName; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - private Timer m_PayTimer; + int version = reader.ReadInt(); + } - public PlayerVendor( Mobile owner, BaseHouse house ) - { - Owner = owner; - House = house; + private class BuyEntry : ContextMenuEntry + { + private Item m_Item; - if ( BaseHouse.NewVendorSystem ) - { - BankAccount = 0; - HoldGold = 4; - } - else - { - BankAccount = 1000; - HoldGold = 0; - } + public BuyEntry(Item item) : base(6103) + { + m_Item = item; + } - ShopName = "Shop Not Yet Named"; + public override bool NonLocalUse => true; - m_SellItems = new Dictionary(); + public override void OnClick() + { + if (m_Item.Deleted) + return; - CantWalk = true; + PlayerVendor.TryToBuy(m_Item, Owner.From); + } + } + } - if ( !Core.AOS ) - NameHue = 0x35; + public class PlayerVendor : Mobile + { + private BaseHouse m_House; - InitStats( 100, 100, 25 ); - InitBody(); - InitOutfit(); + private Timer m_PayTimer; + private Dictionary m_SellItems; - TimeSpan delay = PayTimer.GetInterval(); + private string m_ShopName; - m_PayTimer = new PayTimer( this, delay ); - m_PayTimer.Start(); + public PlayerVendor(Mobile owner, BaseHouse house) + { + Owner = owner; + House = house; - NextPayTime = DateTime.UtcNow + delay; - } + if (BaseHouse.NewVendorSystem) + { + BankAccount = 0; + HoldGold = 4; + } + else + { + BankAccount = 1000; + HoldGold = 0; + } - public PlayerVendor( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version + ShopName = "Shop Not Yet Named"; - writer.Write( (bool) BaseHouse.NewVendorSystem ); - writer.Write( (string) m_ShopName ); - writer.WriteDeltaTime( (DateTime) NextPayTime ); - writer.Write( (Item) House ); + m_SellItems = new Dictionary(); - writer.Write( (Mobile) Owner ); - writer.Write( (int) BankAccount ); - writer.Write( (int) HoldGold ); + CantWalk = true; - writer.Write( (int) m_SellItems.Count ); - foreach ( VendorItem vi in m_SellItems.Values ) - { - writer.Write( (Item) vi.Item ); - writer.Write( (int) vi.Price ); - writer.Write( (string) vi.Description ); + if (!Core.AOS) + NameHue = 0x35; - writer.Write( (DateTime) vi.Created ); - } - } + InitStats(100, 100, 25); + InitBody(); + InitOutfit(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + TimeSpan delay = PayTimer.GetInterval(); - int version = reader.ReadInt(); + m_PayTimer = new PayTimer(this, delay); + m_PayTimer.Start(); - bool newVendorSystem = false; + NextPayTime = DateTime.UtcNow + delay; + } - switch ( version ) - { - case 2: - case 1: - { - newVendorSystem = reader.ReadBool(); - m_ShopName = reader.ReadString(); - NextPayTime = reader.ReadDeltaTime(); - House = (BaseHouse) reader.ReadItem(); + public PlayerVendor(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } - goto case 0; - } - case 0: - { - Owner = reader.ReadMobile(); - BankAccount = reader.ReadInt(); - HoldGold = reader.ReadInt(); + [CommandProperty(AccessLevel.GameMaster)] + public int BankAccount{ get; set; } - int count = reader.ReadInt(); + [CommandProperty(AccessLevel.GameMaster)] + public int HoldGold{ get; set; } - m_SellItems = new Dictionary(count); + [CommandProperty(AccessLevel.GameMaster)] + public string ShopName + { + get => m_ShopName; + set + { + if (value == null) + m_ShopName = ""; + else + m_ShopName = value; - for ( int i = 0; i < count; i++ ) - { - Item item = reader.ReadItem(); - - int price = reader.ReadInt(); - if ( price > 100000000 ) - price = 100000000; - - string description = reader.ReadString(); - - DateTime created = version < 1 ? DateTime.UtcNow : reader.ReadDateTime(); - - if ( item != null ) - { - SetVendorItem( item, version < 1 && price <= 0 ? -1 : price, description, created ); - } - } + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextPayTime{ get; private set; } + + public PlayerVendorPlaceholder Placeholder{ get; set; } + + public BaseHouse House + { + get => m_House; + set + { + m_House?.PlayerVendors.Remove(this); - break; - } - } - - bool newVendorSystemActivated = BaseHouse.NewVendorSystem && !newVendorSystem; - - if ( version < 1 || newVendorSystemActivated ) - { - if ( version < 1 ) - { - m_ShopName = "Shop Not Yet Named"; - Timer.DelayCall( TimeSpan.Zero, new TimerStateCallback( UpgradeFromVersion0 ), newVendorSystemActivated ); - } - else - { - Timer.DelayCall( TimeSpan.Zero, FixDresswear ); - } - - NextPayTime = DateTime.UtcNow + PayTimer.GetInterval(); - - if ( newVendorSystemActivated ) - { - HoldGold += BankAccount; - BankAccount = 0; - } - } - - if ( version < 2 && RawStr == 75 && RawDex == 75 && RawInt == 75 ) - InitStats( 100, 100, 25 ); - - TimeSpan delay = NextPayTime - DateTime.UtcNow; - - m_PayTimer = new PayTimer( this, delay > TimeSpan.Zero ? delay : TimeSpan.Zero ); - m_PayTimer.Start(); - - Blessed = false; - - if ( Core.AOS && NameHue == 0x35 ) - NameHue = -1; - } - - private void UpgradeFromVersion0( object newVendorSystem ) - { - List toRemove = new List(); - - foreach ( VendorItem vi in m_SellItems.Values ) - if ( !CanBeVendorItem( vi.Item ) ) - toRemove.Add( vi.Item ); - else - vi.Description = Utility.FixHtml( vi.Description ); - - foreach ( Item item in toRemove ) - RemoveVendorItem( item ); - - House = BaseHouse.FindHouseAt( this ); - - if ( (bool) newVendorSystem ) - ActivateNewVendorSystem(); - } - - private void ActivateNewVendorSystem() - { - FixDresswear(); - - if ( House != null && !House.IsOwner( Owner ) ) - Destroy( false ); - } - - public void InitBody() - { - Hue = Utility.RandomSkinHue(); - SpeechHue = 0x3B2; - - if ( !Core.AOS ) - NameHue = 0x35; - - if ( Female = Utility.RandomBool() ) - { - Body = 0x191; - Name = NameList.RandomName( "female" ); - } - else - { - Body = 0x190; - Name = NameList.RandomName( "male" ); - } - } - - public virtual void InitOutfit() - { - Item item = new FancyShirt( Utility.RandomNeutralHue() ); - item.Layer = Layer.InnerTorso; - AddItem( item ); - AddItem( new LongPants( Utility.RandomNeutralHue() ) ); - AddItem( new BodySash( Utility.RandomNeutralHue() ) ); - AddItem( new Boots( Utility.RandomNeutralHue() ) ); - AddItem( new Cloak( Utility.RandomNeutralHue() ) ); - - Utility.AssignRandomHair( this ); - - Container pack = new VendorBackpack(); - pack.Movable = false; - AddItem( pack ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int BankAccount { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int HoldGold { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public string ShopName - { - get => m_ShopName; - set - { - if ( value == null ) - m_ShopName = ""; - else - m_ShopName = value; - - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextPayTime { get; private set; } - - public PlayerVendorPlaceholder Placeholder { get; set; } - - public BaseHouse House - { - get => m_House; - set - { - m_House?.PlayerVendors.Remove( this ); - - value?.PlayerVendors.Add( this ); - - m_House = value; - } - } - - public int ChargePerDay - { - get - { - if ( BaseHouse.NewVendorSystem ) - { - return ChargePerRealWorldDay / 12; - } - - long total = 0; - foreach ( VendorItem vi in m_SellItems.Values ) - { - total += vi.Price; - } - - total -= 500; - - if ( total < 0 ) - total = 0; - - return (int)( 20 + (total / 500) ); - } - } - - public int ChargePerRealWorldDay - { - get - { - if ( BaseHouse.NewVendorSystem ) - { - long total = 0; - foreach ( VendorItem vi in m_SellItems.Values ) - { - total += vi.Price; - } - - return (int)( 60 + (total / 500) * 3 ); - } - - return ChargePerDay * 12; - } - } - - public virtual bool IsOwner( Mobile m ) - { - if ( m.AccessLevel >= AccessLevel.GameMaster ) - return true; - - if ( BaseHouse.NewVendorSystem && House != null ) - { - return House.IsOwner( m ); - } - - return m == Owner; - } - - protected List GetItems() - { - List list = new List(); - - foreach ( Item item in Items ) - if ( item.Movable && item != Backpack && item.Layer != Layer.Hair && item.Layer != Layer.FacialHair ) - list.Add( item ); - - if ( Backpack != null ) - list.AddRange( Backpack.Items ); - - return list; - } - - public virtual void Destroy( bool toBackpack ) - { - Return(); - - if ( !BaseHouse.NewVendorSystem ) - FixDresswear(); - - /* Possible cases regarding item return: - * - * 1. No item must be returned - * -> do nothing. - * 2. ( toBackpack is false OR the vendor is in the internal map ) AND the vendor is associated with a AOS house - * -> put the items into the moving crate or a vendor inventory, - * depending on whether the vendor owner is also the house owner. - * 3. ( toBackpack is true OR the vendor isn't associated with any AOS house ) AND the vendor isn't in the internal map - * -> put the items into a backpack. - * 4. The vendor isn't associated with any house AND it's in the internal map - * -> do nothing (we can't do anything). - */ - - List list = GetItems(); - - if ( list.Count > 0 || HoldGold > 0 ) // No case 1 - { - if ( ( !toBackpack || Map == Map.Internal ) && House != null && House.IsAosRules ) // Case 2 - { - if ( House.IsOwner( Owner ) ) // Move to moving crate - { - if ( House.MovingCrate == null ) - House.MovingCrate = new MovingCrate( House ); - - if ( HoldGold > 0 ) - Banker.Deposit( House.MovingCrate, HoldGold ); - - foreach ( Item item in list ) - { - House.MovingCrate.DropItem( item ); - } - } - else // Move to vendor inventory - { - VendorInventory inventory = new VendorInventory( House, Owner, Name, ShopName ); - inventory.Gold = HoldGold; - - foreach ( Item item in list ) - { - inventory.AddItem( item ); - } - - House.VendorInventories.Add( inventory ); - } - } - else if ( ( toBackpack || House == null || !House.IsAosRules ) && Map != Map.Internal ) // Case 3 - Move to backpack - { - Container backpack = new Backpack(); - - if ( HoldGold > 0 ) - Banker.Deposit( backpack, HoldGold ); - - foreach ( Item item in list ) - { - backpack.DropItem( item ); - } - - backpack.MoveToWorld( Location, Map ); - } - } - - Delete(); - } - - private void FixDresswear() - { - for ( int i = 0; i < Items.Count; ++i ) - { - Item item = Items[i] as Item; - - if ( item is BaseHat ) - item.Layer = Layer.Helm; - else if ( item is BaseMiddleTorso ) - item.Layer = Layer.MiddleTorso; - else if ( item is BaseOuterLegs ) - item.Layer = Layer.OuterLegs; - else if ( item is BaseOuterTorso ) - item.Layer = Layer.OuterTorso; - else if ( item is BasePants ) - item.Layer = Layer.Pants; - else if ( item is BaseShirt ) - item.Layer = Layer.Shirt; - else if ( item is BaseWaist ) - item.Layer = Layer.Waist; - else if ( item is BaseShoes ) - { - if ( item is Sandals ) - item.Hue = 0; - - item.Layer = Layer.Shoes; - } - } - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_PayTimer.Stop(); - - House = null; - - Placeholder?.Delete(); - } - - public override bool IsSnoop( Mobile from ) - { - return false; - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( BaseHouse.NewVendorSystem ) - { - list.Add( 1062449, ShopName ); // Shop Name: ~1_NAME~ - } - } - - public VendorItem GetVendorItem( Item item ) - { - m_SellItems.TryGetValue( item, out VendorItem v ); - return v; - } - - private VendorItem SetVendorItem( Item item, int price, string description ) - { - return SetVendorItem( item, price, description, DateTime.UtcNow ); - } - - private VendorItem SetVendorItem( Item item, int price, string description, DateTime created ) - { - RemoveVendorItem( item ); - - VendorItem vi = new VendorItem( item, price, description, created ); - m_SellItems[item] = vi; - - item.InvalidateProperties(); - - return vi; - } - - private void RemoveVendorItem( Item item ) - { - VendorItem vi = GetVendorItem( item ); - - if ( vi != null ) - { - vi.Invalidate(); - m_SellItems.Remove( item ); - - foreach ( Item subItem in item.Items ) - { - RemoveVendorItem( subItem ); - } - - item.InvalidateProperties(); - } - } - - private bool CanBeVendorItem( Item item ) - { - Item parent = item.Parent as Item; - - if ( parent == Backpack ) - return true; - - if ( parent is Container ) - { - VendorItem parentVI = GetVendorItem( parent ); - - if ( parentVI != null ) - return !parentVI.IsForSale; - } - - return false; - } - - public override void OnSubItemAdded( Item item ) - { - base.OnSubItemAdded( item ); - - if ( GetVendorItem( item ) == null && CanBeVendorItem( item ) ) - { - // TODO: default price should be dependent to the type of object - SetVendorItem( item, 999, "" ); - } - } - - public override void OnSubItemRemoved( Item item ) - { - base.OnSubItemRemoved( item ); - - if ( item.GetBounce() == null ) - RemoveVendorItem( item ); - } - - public override void OnSubItemBounceCleared( Item item ) - { - base.OnSubItemBounceCleared( item ); - - if ( !CanBeVendorItem( item ) ) - RemoveVendorItem( item ); - } - - public override void OnItemRemoved( Item item ) - { - base.OnItemRemoved( item ); - - if ( item == Backpack ) - { - foreach ( Item subItem in item.Items ) - { - RemoveVendorItem( subItem ); - } - } - } - - public override bool OnDragDrop( Mobile from, Item item ) - { - if ( !IsOwner( from ) ) - { - SayTo( from, 503209 ); // I can only take item from the shop owner. - return false; - } - - if ( item is Gold ) - { - if ( BaseHouse.NewVendorSystem ) - { - if ( HoldGold < 1000000 ) - { - SayTo( from, 503210 ); // I'll take that to fund my services. - - HoldGold += item.Amount; - item.Delete(); - - return true; - } - - from.SendLocalizedMessage( 1062493 ); // Your vendor has sufficient funds for operation and cannot accept this gold. - - return false; - } - - if ( BankAccount < 1000000 ) - { - SayTo( from, 503210 ); // I'll take that to fund my services. - - BankAccount += item.Amount; - item.Delete(); - - return true; - } - - from.SendLocalizedMessage( 1062493 ); // Your vendor has sufficient funds for operation and cannot accept this gold. - - return false; - } - - bool newItem = ( GetVendorItem( item ) == null ); - - if ( Backpack != null && Backpack.TryDropItem( from, item, false ) ) - { - if ( newItem ) - OnItemGiven( from, item ); - - return true; - } - - SayTo( from, 503211 ); // I can't carry any more. - return false; - } - - public override bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - if ( IsOwner( from ) ) - { - if ( GetVendorItem( item ) == null ) - { - // We must wait until the item is added - Timer.DelayCall( TimeSpan.Zero, new TimerStateCallback( NonLocalDropCallback ), new object[] { from, item } ); - } - - return true; - } - - SayTo( from, 503209 ); // I can only take item from the shop owner. - return false; - } - - private void NonLocalDropCallback( object state ) - { - object[] aState = (object[]) state; - - Mobile from = (Mobile) aState[0]; - Item item = (Item) aState[1]; - - OnItemGiven( from, item ); - } - - private void OnItemGiven( Mobile from, Item item ) - { - VendorItem vi = GetVendorItem( item ); - - if ( vi != null ) - { - string name; - if ( !string.IsNullOrEmpty( item.Name ) ) - name = item.Name; - else - name = "#" + item.LabelNumber.ToString(); - - from.SendLocalizedMessage( 1043303, name ); // Type in a price and description for ~1_ITEM~ (ESC=not for sale) - from.Prompt = new VendorPricePrompt( this, vi ); - } - } - - public override bool AllowEquipFrom( Mobile from ) - { - if ( BaseHouse.NewVendorSystem && IsOwner( from ) ) - return true; - - return base.AllowEquipFrom( from ); - } - - public override bool CheckNonlocalLift( Mobile from, Item item ) - { - if ( item.IsChildOf( Backpack ) ) - { - if ( IsOwner( from ) ) - { - return true; - } - - SayTo( from, 503223 ); // If you'd like to purchase an item, just ask. - return false; - } - - if ( BaseHouse.NewVendorSystem && IsOwner( from ) ) - { - return true; - } - - return base.CheckNonlocalLift( from, item ); - } - - public bool CanInteractWith( Mobile from, bool ownerOnly ) - { - if ( !from.CanSee( this ) || !Utility.InUpdateRange( from, this ) || !from.CheckAlive() ) - return false; - - if ( ownerOnly ) - return IsOwner( from ); - - if ( House != null && House.IsBanned( from ) && !IsOwner( from ) ) - { - from.SendLocalizedMessage( 1062674 ); // You can't shop from this home as you have been banned from this establishment. - return false; - } - - return true; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsOwner( from ) ) - { - SendOwnerGump( from ); - } - else if ( CanInteractWith( from, false ) ) - { - OpenBackpack( from ); - } - } - - public override void DisplayPaperdollTo( Mobile m ) - { - if ( BaseHouse.NewVendorSystem ) - { - base.DisplayPaperdollTo( m ); - } - else if ( CanInteractWith( m, false ) ) - { - OpenBackpack( m ); - } - } - - public void SendOwnerGump( Mobile to ) - { - if ( BaseHouse.NewVendorSystem ) - { - to.CloseGump( typeof( NewPlayerVendorOwnerGump ) ); - to.CloseGump( typeof( NewPlayerVendorCustomizeGump ) ); - - to.SendGump( new NewPlayerVendorOwnerGump( this ) ); - } - else - { - to.CloseGump( typeof( PlayerVendorOwnerGump ) ); - to.CloseGump( typeof( PlayerVendorCustomizeGump ) ); - - to.SendGump( new PlayerVendorOwnerGump( this ) ); - } - } - - public void OpenBackpack( Mobile from ) - { - if ( Backpack != null ) - { - SayTo( from, IsOwner( from ) ? 1010642 : 503208 ); // Take a look at my/your goods. - - Backpack.DisplayTo( from ); - } - } - - public static void TryToBuy( Item item, Mobile from ) - { - PlayerVendor vendor = item.RootParent as PlayerVendor; - - if ( vendor == null || !vendor.CanInteractWith( from, false ) ) - return; - - if ( vendor.IsOwner( from ) ) - { - vendor.SayTo( from, 503212 ); // You own this shop, just take what you want. - return; - } - - VendorItem vi = vendor.GetVendorItem( item ); - - if ( vi == null ) - { - vendor.SayTo( from, 503216 ); // You can't buy that. - } - else if ( !vi.IsForSale ) - { - vendor.SayTo( from, 503202 ); // This item is not for sale. - } - else if ( vi.Created + TimeSpan.FromMinutes( 1.0 ) > DateTime.UtcNow ) - { - from.SendMessage( "You cannot buy this item right now. Please wait one minute and try again." ); - } - else - { - from.CloseGump( typeof( PlayerVendorBuyGump ) ); - from.SendGump( new PlayerVendorBuyGump( vendor, vi ) ); - } - } - - public void CollectGold( Mobile to ) - { - if ( HoldGold > 0 ) - { - SayTo( to, "How much of the {0} that I'm holding would you like?", HoldGold.ToString() ); - to.SendMessage( "Enter the amount of gold you wish to withdraw (ESC = CANCEL):" ); - - to.Prompt = new CollectGoldPrompt( this ); - } - else - { - SayTo( to, 503215 ); // I am holding no gold for you. - } - } - - public int GiveGold( Mobile to, int amount ) - { - if ( amount <= 0 ) - return 0; - - if ( amount > HoldGold ) - { - SayTo( to, "I'm sorry, but I'm only holding {0} gold for you.", HoldGold.ToString() ); - return 0; - } - - int amountGiven = Banker.DepositUpTo( to, amount ); - HoldGold -= amountGiven; - - if ( amountGiven > 0 ) - { - to.SendLocalizedMessage( 1060397, amountGiven.ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. - } - - if ( amountGiven == 0 ) - { - SayTo( to, 1070755 ); // Your bank box cannot hold the gold you are requesting. I will keep the gold until you can take it. - } - else if ( amount > amountGiven ) - { - SayTo( to, 1070756 ); // I can only give you part of the gold now, as your bank box is too full to hold the full amount. - } - else if ( HoldGold > 0 ) - { - SayTo( to, 1042639 ); // Your gold has been transferred. - } - else - { - SayTo( to, 503234 ); // All the gold I have been carrying for you has been deposited into your bank account. - } - - return amountGiven; - } - - public void Dismiss( Mobile from ) - { - Container pack = Backpack; - - if ( pack != null && pack.Items.Count > 0 ) - { - SayTo( from, 1038325 ); // You cannot dismiss me while I am holding your goods. - return; - } - - if ( HoldGold > 0 ) - { - GiveGold( from, HoldGold ); - - if ( HoldGold > 0 ) - return; - } - - Destroy( true ); - } - - public void Rename( Mobile from ) - { - from.SendLocalizedMessage( 1062494 ); // Enter a new name for your vendor (20 characters max): - - from.Prompt = new VendorNamePrompt( this ); - } - - public void RenameShop( Mobile from ) - { - from.SendLocalizedMessage( 1062433 ); // Enter a new name for your shop (20 chars max): - - from.Prompt = new ShopNamePrompt( this ); - } - - public bool CheckTeleport( Mobile to ) - { - if ( Deleted || !IsOwner( to ) || House == null || Map == Map.Internal ) - return false; - - if ( House.IsInside( to ) || to.Map != House.Map || !House.InRange( to, 5 ) ) - return false; - - if ( Placeholder == null ) - { - Placeholder = new PlayerVendorPlaceholder( this ); - Placeholder.MoveToWorld( Location, Map ); - - MoveToWorld( to.Location, to.Map ); - - to.SendLocalizedMessage( 1062431 ); // This vendor has been moved out of the house to your current location temporarily. The vendor will return home automatically after two minutes have passed once you are done managing its inventory or customizing it. - } - else - { - Placeholder.RestartTimer(); - - to.SendLocalizedMessage( 1062430 ); // This vendor is currently temporarily in a location outside its house. The vendor will return home automatically after two minutes have passed once you are done managing its inventory or customizing it. - } - - return true; - } - - public void Return() - { - Placeholder?.Delete(); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - if ( from.Alive && Placeholder != null && IsOwner( from ) ) - { - list.Add( new ReturnVendorEntry( this ) ); - } - - base.GetContextMenuEntries( from, list ); - } - - private class ReturnVendorEntry : ContextMenuEntry - { - private PlayerVendor m_Vendor; - - public ReturnVendorEntry( PlayerVendor vendor ) : base( 6214 ) - { - m_Vendor = vendor; - } - - public override void OnClick() - { - Mobile from = Owner.From; - - if ( !m_Vendor.Deleted && m_Vendor.IsOwner( from ) && from.CheckAlive() ) - m_Vendor.Return(); - } - } - - public override bool HandlesOnSpeech( Mobile from ) - { - return ( from.Alive && from.GetDistanceToSqrt( this ) <= 3 ); - } - - public bool WasNamed( string speech ) - { - return Name != null && Insensitive.StartsWith( speech, Name ); - } - - public override void OnSpeech( SpeechEventArgs e ) - { - Mobile from = e.Mobile; - - if ( e.Handled || !from.Alive || from.GetDistanceToSqrt( this ) > 3 ) - return; - - if ( e.HasKeyword( 0x3C ) || (e.HasKeyword( 0x171 ) && WasNamed( e.Speech )) ) // vendor buy, *buy* - { - if ( IsOwner( from ) ) - { - SayTo( from, 503212 ); // You own this shop, just take what you want. - } - else if ( House == null || !House.IsBanned( from ) ) - { - from.SendLocalizedMessage( 503213 ); // Select the item you wish to buy. - from.Target = new PVBuyTarget(); - - e.Handled = true; - } - } - else if ( e.HasKeyword( 0x3D ) || (e.HasKeyword( 0x172 ) && WasNamed( e.Speech )) ) // vendor browse, *browse - { - if ( House != null && House.IsBanned( from ) && !IsOwner( from ) ) - { - SayTo( from, 1062674 ); // You can't shop from this home as you have been banned from this establishment. - } - else - { - if ( WasNamed( e.Speech ) ) - OpenBackpack( from ); - else - { - IPooledEnumerable mobiles = e.Mobile.GetMobilesInRange( 2 ); - - foreach ( PlayerVendor m in mobiles ) - if ( m.CanSee( e.Mobile ) && m.InLOS( e.Mobile ) ) - m.OpenBackpack( from ); - - mobiles.Free(); - } - - e.Handled = true; - } - } - else if ( e.HasKeyword( 0x3E ) || (e.HasKeyword( 0x173 ) && WasNamed( e.Speech )) ) // vendor collect, *collect - { - if ( IsOwner( from ) ) - { - CollectGold( from ); - - e.Handled = true; - } - } - else if ( e.HasKeyword( 0x3F ) || (e.HasKeyword( 0x174 ) && WasNamed( e.Speech )) ) // vendor status, *status - { - if ( IsOwner( from ) ) - { - SendOwnerGump( from ); - - e.Handled = true; - } - else - { - SayTo( from, 503226 ); // What do you care? You don't run this shop. - } - } - else if ( e.HasKeyword( 0x40 ) || (e.HasKeyword( 0x175 ) && WasNamed( e.Speech )) ) // vendor dismiss, *dismiss - { - if ( IsOwner( from ) ) - { - Dismiss( from ); - - e.Handled = true; - } - } - else if ( e.HasKeyword( 0x41 ) || (e.HasKeyword( 0x176 ) && WasNamed( e.Speech )) ) // vendor cycle, *cycle - { - if ( IsOwner( from ) ) - { - Direction = GetDirectionTo( from ); - - e.Handled = true; - } - } - } - - private class PayTimer : Timer - { - public static TimeSpan GetInterval() - { - if ( BaseHouse.NewVendorSystem ) - return TimeSpan.FromDays( 1.0 ); - return TimeSpan.FromMinutes( Clock.MinutesPerUODay ); - } - - private PlayerVendor m_Vendor; - - public PayTimer( PlayerVendor vendor, TimeSpan delay ) : base( delay, GetInterval() ) - { - m_Vendor = vendor; - - Priority = TimerPriority.OneMinute; - } - - protected override void OnTick() - { - m_Vendor.NextPayTime = DateTime.UtcNow + Interval; - - int pay; - int totalGold; - if ( BaseHouse.NewVendorSystem ) - { - pay = m_Vendor.ChargePerRealWorldDay; - totalGold = m_Vendor.HoldGold; - } - else - { - pay = m_Vendor.ChargePerDay; - totalGold = m_Vendor.BankAccount + m_Vendor.HoldGold; - } - - if ( pay > totalGold ) - { - m_Vendor.Destroy( !BaseHouse.NewVendorSystem ); - } - else - { - if ( !BaseHouse.NewVendorSystem ) - { - if ( m_Vendor.BankAccount >= pay ) - { - m_Vendor.BankAccount -= pay; - pay = 0; - } - else - { - pay -= m_Vendor.BankAccount; - m_Vendor.BankAccount = 0; - } - } - - m_Vendor.HoldGold -= pay; - } - } - } - - [PlayerVendorTarget] - private class PVBuyTarget : Target - { - public PVBuyTarget() : base( 3, false, TargetFlags.None ) - { - AllowNonlocal = true; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Item ) - { - TryToBuy( (Item) targeted, from ); - } - } - } - - private class VendorPricePrompt : Prompt - { - private PlayerVendor m_Vendor; - private VendorItem m_VI; - - public VendorPricePrompt( PlayerVendor vendor, VendorItem vi ) - { - m_Vendor = vendor; - m_VI = vi; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( !m_VI.Valid || !m_Vendor.CanInteractWith( from, true ) ) - return; - - string firstWord; - - int sep = text.IndexOfAny( new[] { ' ', ',' } ); - if ( sep >= 0 ) - firstWord = text.Substring( 0, sep ); - else - firstWord = text; - - int price; - string description; - - if ( int.TryParse( firstWord, out price ) ) - { - if ( sep >= 0 ) - description = text.Substring( sep + 1 ).Trim(); - else - description = ""; - } - else - { - price = -1; - description = text.Trim(); - } - - SetInfo( from, price, Utility.FixHtml( description ) ); - } - - public override void OnCancel( Mobile from ) - { - if ( !m_VI.Valid || !m_Vendor.CanInteractWith( from, true ) ) - return; - - SetInfo( from, -1, "" ); - } - - private void SetInfo( Mobile from, int price, string description ) - { - Item item = m_VI.Item; - - bool setPrice = false; - - if ( price < 0 ) // Not for sale - { - price = -1; - - if ( item is Container ) - { - if ( item is LockableContainer && ((LockableContainer)item).Locked ) - m_Vendor.SayTo( from, 1043298 ); // Locked items may not be made not-for-sale. - else if ( item.Items.Count > 0 ) - m_Vendor.SayTo( from, 1043299 ); // To be not for sale, all items in a container must be for sale. - else - setPrice = true; - } - else if ( item is BaseBook || item is Engines.BulkOrders.BulkOrderBook ) - { - setPrice = true; - } - else - { - m_Vendor.SayTo( from, 1043301 ); // Only the following may be made not-for-sale: books, containers, keyrings, and items in for-sale containers. - } - } - else - { - if ( price > 100000000 ) - { - price = 100000000; - from.SendMessage( "You cannot price items above 100,000,000 gold. The price has been adjusted." ); - } - - setPrice = true; - } - - if ( setPrice ) - { - m_Vendor.SetVendorItem( item, price, description ); - } - else - { - m_VI.Description = description; - } - } - } - - private class CollectGoldPrompt : Prompt - { - private PlayerVendor m_Vendor; - - public CollectGoldPrompt( PlayerVendor vendor ) - { - m_Vendor = vendor; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - text = text.Trim(); - - int amount; - - if ( !int.TryParse( text, out amount ) ) - amount = 0; - - GiveGold( from, amount ); - } - - public override void OnCancel( Mobile from ) - { - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - GiveGold( from, 0 ); - } - - private void GiveGold( Mobile to, int amount ) - { - if ( amount <= 0 ) - { - m_Vendor.SayTo( to, "Very well. I will hold on to the money for now then." ); - } - else - { - m_Vendor.GiveGold( to, amount ); - } - } - } - - private class VendorNamePrompt : Prompt - { - private PlayerVendor m_Vendor; - - public VendorNamePrompt( PlayerVendor vendor ) - { - m_Vendor = vendor; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - string name = text.Trim(); - - if ( !NameVerification.Validate( name, 1, 20, true, true, true, 0, NameVerification.Empty ) ) - { - m_Vendor.SayTo( from, "That name is unacceptable." ); - return; - } - - m_Vendor.Name = Utility.FixHtml( name ); - - from.SendLocalizedMessage( 1062496 ); // Your vendor has been renamed. - - from.SendGump( new NewPlayerVendorOwnerGump( m_Vendor ) ); - } - } - - private class ShopNamePrompt : Prompt - { - private PlayerVendor m_Vendor; - - public ShopNamePrompt( PlayerVendor vendor ) - { - m_Vendor = vendor; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( !m_Vendor.CanInteractWith( from, true ) ) - return; - - string name = text.Trim(); - - if ( !NameVerification.Validate( name, 1, 20, true, true, true, 0, NameVerification.Empty ) ) - { - m_Vendor.SayTo( from, "That name is unacceptable." ); - return; - } - - m_Vendor.ShopName = Utility.FixHtml( name ); + value?.PlayerVendors.Add(this); - from.SendGump( new NewPlayerVendorOwnerGump( m_Vendor ) ); - } - } + m_House = value; + } + } - public override bool CanBeDamaged() - { - return false; - } + public int ChargePerDay + { + get + { + if (BaseHouse.NewVendorSystem) return ChargePerRealWorldDay / 12; - } - - public class PlayerVendorPlaceholder : Item - { - private ExpireTimer m_Timer; + long total = 0; + foreach (VendorItem vi in m_SellItems.Values) total += vi.Price; - [CommandProperty( AccessLevel.GameMaster )] - public PlayerVendor Vendor { get; private set; } - - public PlayerVendorPlaceholder( PlayerVendor vendor ) : base( 0x1F28 ) - { - Hue = 0x672; - Movable = false; - - Vendor = vendor; - - m_Timer = new ExpireTimer( this ); - m_Timer.Start(); - } - - public PlayerVendorPlaceholder( Serial serial ) : base( serial ) - { - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( Vendor != null ) - list.Add( 1062498, Vendor.Name ); // reserved for vendor ~1_NAME~ - } + total -= 500; - public void RestartTimer() - { - m_Timer.Stop(); - m_Timer.Start(); - } + if (total < 0) + total = 0; - private class ExpireTimer : Timer - { - private PlayerVendorPlaceholder m_Placeholder; + return (int)(20 + total / 500); + } + } + + public int ChargePerRealWorldDay + { + get + { + if (BaseHouse.NewVendorSystem) + { + long total = 0; + foreach (VendorItem vi in m_SellItems.Values) total += vi.Price; - public ExpireTimer( PlayerVendorPlaceholder placeholder ) : base( TimeSpan.FromMinutes( 2.0 ) ) - { - m_Placeholder = placeholder; + return (int)(60 + total / 500 * 3); + } - Priority = TimerPriority.FiveSeconds; - } + return ChargePerDay * 12; + } + } - protected override void OnTick() - { - m_Placeholder.Delete(); - } - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void OnDelete() - { - if ( Vendor != null && !Vendor.Deleted ) - { - Vendor.MoveToWorld( Location, Map ); - Vendor.Placeholder = null; - } - } + writer.Write(2); // version - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(BaseHouse.NewVendorSystem); + writer.Write(m_ShopName); + writer.WriteDeltaTime(NextPayTime); + writer.Write(House); - writer.WriteEncodedInt( (int) 0 ); + writer.Write(Owner); + writer.Write(BankAccount); + writer.Write(HoldGold); + + writer.Write(m_SellItems.Count); + foreach (VendorItem vi in m_SellItems.Values) + { + writer.Write(vi.Item); + writer.Write(vi.Price); + writer.Write(vi.Description); + + writer.Write(vi.Created); + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + bool newVendorSystem = false; + + switch (version) + { + case 2: + case 1: + { + newVendorSystem = reader.ReadBool(); + m_ShopName = reader.ReadString(); + NextPayTime = reader.ReadDeltaTime(); + House = (BaseHouse)reader.ReadItem(); - writer.Write( (Mobile) Vendor ); - } + goto case 0; + } + case 0: + { + Owner = reader.ReadMobile(); + BankAccount = reader.ReadInt(); + HoldGold = reader.ReadInt(); + + int count = reader.ReadInt(); + + m_SellItems = new Dictionary(count); + + for (int i = 0; i < count; i++) + { + Item item = reader.ReadItem(); + + int price = reader.ReadInt(); + if (price > 100000000) + price = 100000000; + + string description = reader.ReadString(); + + DateTime created = version < 1 ? DateTime.UtcNow : reader.ReadDateTime(); + + if (item != null) SetVendorItem(item, version < 1 && price <= 0 ? -1 : price, description, created); + } + + break; + } + } + + bool newVendorSystemActivated = BaseHouse.NewVendorSystem && !newVendorSystem; + + if (version < 1 || newVendorSystemActivated) + { + if (version < 1) + { + m_ShopName = "Shop Not Yet Named"; + Timer.DelayCall(TimeSpan.Zero, new TimerStateCallback(UpgradeFromVersion0), newVendorSystemActivated); + } + else + { + Timer.DelayCall(TimeSpan.Zero, FixDresswear); + } + + NextPayTime = DateTime.UtcNow + PayTimer.GetInterval(); + + if (newVendorSystemActivated) + { + HoldGold += BankAccount; + BankAccount = 0; + } + } + + if (version < 2 && RawStr == 75 && RawDex == 75 && RawInt == 75) + InitStats(100, 100, 25); + + TimeSpan delay = NextPayTime - DateTime.UtcNow; + + m_PayTimer = new PayTimer(this, delay > TimeSpan.Zero ? delay : TimeSpan.Zero); + m_PayTimer.Start(); + + Blessed = false; + + if (Core.AOS && NameHue == 0x35) + NameHue = -1; + } + + private void UpgradeFromVersion0(object newVendorSystem) + { + List toRemove = new List(); + + foreach (VendorItem vi in m_SellItems.Values) + if (!CanBeVendorItem(vi.Item)) + toRemove.Add(vi.Item); + else + vi.Description = Utility.FixHtml(vi.Description); + + foreach (Item item in toRemove) + RemoveVendorItem(item); + + House = BaseHouse.FindHouseAt(this); + + if ((bool)newVendorSystem) + ActivateNewVendorSystem(); + } + + private void ActivateNewVendorSystem() + { + FixDresswear(); + + if (House != null && !House.IsOwner(Owner)) + Destroy(false); + } + + public void InitBody() + { + Hue = Utility.RandomSkinHue(); + SpeechHue = 0x3B2; + + if (!Core.AOS) + NameHue = 0x35; + + if (Female = Utility.RandomBool()) + { + Body = 0x191; + Name = NameList.RandomName("female"); + } + else + { + Body = 0x190; + Name = NameList.RandomName("male"); + } + } + + public virtual void InitOutfit() + { + Item item = new FancyShirt(Utility.RandomNeutralHue()); + item.Layer = Layer.InnerTorso; + AddItem(item); + AddItem(new LongPants(Utility.RandomNeutralHue())); + AddItem(new BodySash(Utility.RandomNeutralHue())); + AddItem(new Boots(Utility.RandomNeutralHue())); + AddItem(new Cloak(Utility.RandomNeutralHue())); + + Utility.AssignRandomHair(this); + + Container pack = new VendorBackpack(); + pack.Movable = false; + AddItem(pack); + } + + public virtual bool IsOwner(Mobile m) + { + if (m.AccessLevel >= AccessLevel.GameMaster) + return true; + + if (BaseHouse.NewVendorSystem && House != null) return House.IsOwner(m); + + return m == Owner; + } + + protected List GetItems() + { + List list = new List(); + + foreach (Item item in Items) + if (item.Movable && item != Backpack && item.Layer != Layer.Hair && item.Layer != Layer.FacialHair) + list.Add(item); + + if (Backpack != null) + list.AddRange(Backpack.Items); + + return list; + } + + public virtual void Destroy(bool toBackpack) + { + Return(); + + if (!BaseHouse.NewVendorSystem) + FixDresswear(); + + /* Possible cases regarding item return: + * + * 1. No item must be returned + * -> do nothing. + * 2. ( toBackpack is false OR the vendor is in the internal map ) AND the vendor is associated with a AOS house + * -> put the items into the moving crate or a vendor inventory, + * depending on whether the vendor owner is also the house owner. + * 3. ( toBackpack is true OR the vendor isn't associated with any AOS house ) AND the vendor isn't in the internal map + * -> put the items into a backpack. + * 4. The vendor isn't associated with any house AND it's in the internal map + * -> do nothing (we can't do anything). + */ + + List list = GetItems(); + + if (list.Count > 0 || HoldGold > 0) // No case 1 + { + if ((!toBackpack || Map == Map.Internal) && House != null && House.IsAosRules) // Case 2 + { + if (House.IsOwner(Owner)) // Move to moving crate + { + if (House.MovingCrate == null) + House.MovingCrate = new MovingCrate(House); + + if (HoldGold > 0) + Banker.Deposit(House.MovingCrate, HoldGold); + + foreach (Item item in list) House.MovingCrate.DropItem(item); + } + else // Move to vendor inventory + { + VendorInventory inventory = new VendorInventory(House, Owner, Name, ShopName); + inventory.Gold = HoldGold; + + foreach (Item item in list) inventory.AddItem(item); + + House.VendorInventories.Add(inventory); + } + } + else if ((toBackpack || House == null || !House.IsAosRules) && Map != Map.Internal + ) // Case 3 - Move to backpack + { + Container backpack = new Backpack(); + + if (HoldGold > 0) + Banker.Deposit(backpack, HoldGold); + + foreach (Item item in list) backpack.DropItem(item); + + backpack.MoveToWorld(Location, Map); + } + } + + Delete(); + } + + private void FixDresswear() + { + for (int i = 0; i < Items.Count; ++i) + { + Item item = Items[i]; + + if (item is BaseHat) + { + item.Layer = Layer.Helm; + } + else if (item is BaseMiddleTorso) + { + item.Layer = Layer.MiddleTorso; + } + else if (item is BaseOuterLegs) + { + item.Layer = Layer.OuterLegs; + } + else if (item is BaseOuterTorso) + { + item.Layer = Layer.OuterTorso; + } + else if (item is BasePants) + { + item.Layer = Layer.Pants; + } + else if (item is BaseShirt) + { + item.Layer = Layer.Shirt; + } + else if (item is BaseWaist) + { + item.Layer = Layer.Waist; + } + else if (item is BaseShoes) + { + if (item is Sandals) + item.Hue = 0; + + item.Layer = Layer.Shoes; + } + } + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_PayTimer.Stop(); + + House = null; + + Placeholder?.Delete(); + } + + public override bool IsSnoop(Mobile from) + { + return false; + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (BaseHouse.NewVendorSystem) list.Add(1062449, ShopName); // Shop Name: ~1_NAME~ + } + + public VendorItem GetVendorItem(Item item) + { + m_SellItems.TryGetValue(item, out VendorItem v); + return v; + } + + private VendorItem SetVendorItem(Item item, int price, string description) + { + return SetVendorItem(item, price, description, DateTime.UtcNow); + } + + private VendorItem SetVendorItem(Item item, int price, string description, DateTime created) + { + RemoveVendorItem(item); + + VendorItem vi = new VendorItem(item, price, description, created); + m_SellItems[item] = vi; + + item.InvalidateProperties(); + + return vi; + } + + private void RemoveVendorItem(Item item) + { + VendorItem vi = GetVendorItem(item); + + if (vi != null) + { + vi.Invalidate(); + m_SellItems.Remove(item); + + foreach (Item subItem in item.Items) RemoveVendorItem(subItem); + + item.InvalidateProperties(); + } + } + + private bool CanBeVendorItem(Item item) + { + Item parent = item.Parent as Item; + + if (parent == Backpack) + return true; + + if (parent is Container) + { + VendorItem parentVI = GetVendorItem(parent); + + if (parentVI != null) + return !parentVI.IsForSale; + } + + return false; + } + + public override void OnSubItemAdded(Item item) + { + base.OnSubItemAdded(item); + + if (GetVendorItem(item) == null && CanBeVendorItem(item)) SetVendorItem(item, 999, ""); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnSubItemRemoved(Item item) + { + base.OnSubItemRemoved(item); - int version = reader.ReadEncodedInt(); + if (item.GetBounce() == null) + RemoveVendorItem(item); + } - Vendor = (PlayerVendor) reader.ReadMobile(); + public override void OnSubItemBounceCleared(Item item) + { + base.OnSubItemBounceCleared(item); - Timer.DelayCall( TimeSpan.Zero, Delete ); - } - } -} + if (!CanBeVendorItem(item)) + RemoveVendorItem(item); + } + + public override void OnItemRemoved(Item item) + { + base.OnItemRemoved(item); + + if (item == Backpack) + foreach (Item subItem in item.Items) + RemoveVendorItem(subItem); + } + + public override bool OnDragDrop(Mobile from, Item item) + { + if (!IsOwner(from)) + { + SayTo(from, 503209); // I can only take item from the shop owner. + return false; + } + + if (item is Gold) + { + if (BaseHouse.NewVendorSystem) + { + if (HoldGold < 1000000) + { + SayTo(from, 503210); // I'll take that to fund my services. + + HoldGold += item.Amount; + item.Delete(); + + return true; + } + + from.SendLocalizedMessage( + 1062493); // Your vendor has sufficient funds for operation and cannot accept this gold. + + return false; + } + + if (BankAccount < 1000000) + { + SayTo(from, 503210); // I'll take that to fund my services. + + BankAccount += item.Amount; + item.Delete(); + + return true; + } + + from.SendLocalizedMessage( + 1062493); // Your vendor has sufficient funds for operation and cannot accept this gold. + + return false; + } + + bool newItem = GetVendorItem(item) == null; + + if (Backpack != null && Backpack.TryDropItem(from, item, false)) + { + if (newItem) + OnItemGiven(from, item); + + return true; + } + + SayTo(from, 503211); // I can't carry any more. + return false; + } + + public override bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + if (IsOwner(from)) + { + if (GetVendorItem(item) == null) + Timer.DelayCall(TimeSpan.Zero, new TimerStateCallback(NonLocalDropCallback), + new object[] { from, item }); + + return true; + } + + SayTo(from, 503209); // I can only take item from the shop owner. + return false; + } + + private void NonLocalDropCallback(object state) + { + object[] aState = (object[])state; + + Mobile from = (Mobile)aState[0]; + Item item = (Item)aState[1]; + + OnItemGiven(from, item); + } + + private void OnItemGiven(Mobile from, Item item) + { + VendorItem vi = GetVendorItem(item); + + if (vi != null) + { + string name; + if (!string.IsNullOrEmpty(item.Name)) + name = item.Name; + else + name = "#" + item.LabelNumber; + + from.SendLocalizedMessage(1043303, name); // Type in a price and description for ~1_ITEM~ (ESC=not for sale) + from.Prompt = new VendorPricePrompt(this, vi); + } + } + + public override bool AllowEquipFrom(Mobile from) + { + if (BaseHouse.NewVendorSystem && IsOwner(from)) + return true; + + return base.AllowEquipFrom(from); + } + + public override bool CheckNonlocalLift(Mobile from, Item item) + { + if (item.IsChildOf(Backpack)) + { + if (IsOwner(from)) return true; + + SayTo(from, 503223); // If you'd like to purchase an item, just ask. + return false; + } + + if (BaseHouse.NewVendorSystem && IsOwner(from)) return true; + + return base.CheckNonlocalLift(from, item); + } + + public bool CanInteractWith(Mobile from, bool ownerOnly) + { + if (!from.CanSee(this) || !Utility.InUpdateRange(from, this) || !from.CheckAlive()) + return false; + + if (ownerOnly) + return IsOwner(from); + + if (House != null && House.IsBanned(from) && !IsOwner(from)) + { + from.SendLocalizedMessage( + 1062674); // You can't shop from this home as you have been banned from this establishment. + return false; + } + + return true; + } + + public override void OnDoubleClick(Mobile from) + { + if (IsOwner(from)) + SendOwnerGump(from); + else if (CanInteractWith(from, false)) OpenBackpack(from); + } + + public override void DisplayPaperdollTo(Mobile m) + { + if (BaseHouse.NewVendorSystem) + base.DisplayPaperdollTo(m); + else if (CanInteractWith(m, false)) OpenBackpack(m); + } + + public void SendOwnerGump(Mobile to) + { + if (BaseHouse.NewVendorSystem) + { + to.CloseGump(typeof(NewPlayerVendorOwnerGump)); + to.CloseGump(typeof(NewPlayerVendorCustomizeGump)); + + to.SendGump(new NewPlayerVendorOwnerGump(this)); + } + else + { + to.CloseGump(typeof(PlayerVendorOwnerGump)); + to.CloseGump(typeof(PlayerVendorCustomizeGump)); + + to.SendGump(new PlayerVendorOwnerGump(this)); + } + } + + public void OpenBackpack(Mobile from) + { + if (Backpack != null) + { + SayTo(from, IsOwner(from) ? 1010642 : 503208); // Take a look at my/your goods. + + Backpack.DisplayTo(from); + } + } + + public static void TryToBuy(Item item, Mobile from) + { + PlayerVendor vendor = item.RootParent as PlayerVendor; + + if (vendor == null || !vendor.CanInteractWith(from, false)) + return; + + if (vendor.IsOwner(from)) + { + vendor.SayTo(from, 503212); // You own this shop, just take what you want. + return; + } + + VendorItem vi = vendor.GetVendorItem(item); + + if (vi == null) + { + vendor.SayTo(from, 503216); // You can't buy that. + } + else if (!vi.IsForSale) + { + vendor.SayTo(from, 503202); // This item is not for sale. + } + else if (vi.Created + TimeSpan.FromMinutes(1.0) > DateTime.UtcNow) + { + from.SendMessage("You cannot buy this item right now. Please wait one minute and try again."); + } + else + { + from.CloseGump(typeof(PlayerVendorBuyGump)); + from.SendGump(new PlayerVendorBuyGump(vendor, vi)); + } + } + + public void CollectGold(Mobile to) + { + if (HoldGold > 0) + { + SayTo(to, "How much of the {0} that I'm holding would you like?", HoldGold.ToString()); + to.SendMessage("Enter the amount of gold you wish to withdraw (ESC = CANCEL):"); + + to.Prompt = new CollectGoldPrompt(this); + } + else + { + SayTo(to, 503215); // I am holding no gold for you. + } + } + + public int GiveGold(Mobile to, int amount) + { + if (amount <= 0) + return 0; + + if (amount > HoldGold) + { + SayTo(to, "I'm sorry, but I'm only holding {0} gold for you.", HoldGold.ToString()); + return 0; + } + + int amountGiven = Banker.DepositUpTo(to, amount); + HoldGold -= amountGiven; + + if (amountGiven > 0) + to.SendLocalizedMessage(1060397, + amountGiven.ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + + if (amountGiven == 0) + SayTo(to, 1070755); // Your bank box cannot hold the gold you are requesting. I will keep the gold until you can take it. + else if (amount > amountGiven) + SayTo(to, 1070756); // I can only give you part of the gold now, as your bank box is too full to hold the full amount. + else if (HoldGold > 0) + SayTo(to, 1042639); // Your gold has been transferred. + else + SayTo(to, 503234); // All the gold I have been carrying for you has been deposited into your bank account. + + return amountGiven; + } + + public void Dismiss(Mobile from) + { + Container pack = Backpack; + + if (pack != null && pack.Items.Count > 0) + { + SayTo(from, 1038325); // You cannot dismiss me while I am holding your goods. + return; + } + + if (HoldGold > 0) + { + GiveGold(from, HoldGold); + + if (HoldGold > 0) + return; + } + + Destroy(true); + } + + public void Rename(Mobile from) + { + from.SendLocalizedMessage(1062494); // Enter a new name for your vendor (20 characters max): + + from.Prompt = new VendorNamePrompt(this); + } + + public void RenameShop(Mobile from) + { + from.SendLocalizedMessage(1062433); // Enter a new name for your shop (20 chars max): + + from.Prompt = new ShopNamePrompt(this); + } + + public bool CheckTeleport(Mobile to) + { + if (Deleted || !IsOwner(to) || House == null || Map == Map.Internal) + return false; + + if (House.IsInside(to) || to.Map != House.Map || !House.InRange(to, 5)) + return false; + + if (Placeholder == null) + { + Placeholder = new PlayerVendorPlaceholder(this); + Placeholder.MoveToWorld(Location, Map); + + MoveToWorld(to.Location, to.Map); + + to.SendLocalizedMessage( + 1062431); // This vendor has been moved out of the house to your current location temporarily. The vendor will return home automatically after two minutes have passed once you are done managing its inventory or customizing it. + } + else + { + Placeholder.RestartTimer(); + + to.SendLocalizedMessage( + 1062430); // This vendor is currently temporarily in a location outside its house. The vendor will return home automatically after two minutes have passed once you are done managing its inventory or customizing it. + } + + return true; + } + + public void Return() + { + Placeholder?.Delete(); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + if (from.Alive && Placeholder != null && IsOwner(from)) list.Add(new ReturnVendorEntry(this)); + + base.GetContextMenuEntries(from, list); + } + + public override bool HandlesOnSpeech(Mobile from) + { + return from.Alive && from.GetDistanceToSqrt(this) <= 3; + } + + public bool WasNamed(string speech) + { + return Name != null && Insensitive.StartsWith(speech, Name); + } + + public override void OnSpeech(SpeechEventArgs e) + { + Mobile from = e.Mobile; + + if (e.Handled || !from.Alive || from.GetDistanceToSqrt(this) > 3) + return; + + if (e.HasKeyword(0x3C) || e.HasKeyword(0x171) && WasNamed(e.Speech)) // vendor buy, *buy* + { + if (IsOwner(from)) + { + SayTo(from, 503212); // You own this shop, just take what you want. + } + else if (House == null || !House.IsBanned(from)) + { + from.SendLocalizedMessage(503213); // Select the item you wish to buy. + from.Target = new PVBuyTarget(); + + e.Handled = true; + } + } + else if (e.HasKeyword(0x3D) || e.HasKeyword(0x172) && WasNamed(e.Speech)) // vendor browse, *browse + { + if (House != null && House.IsBanned(from) && !IsOwner(from)) + { + SayTo(from, 1062674); // You can't shop from this home as you have been banned from this establishment. + } + else + { + if (WasNamed(e.Speech)) + { + OpenBackpack(from); + } + else + { + IPooledEnumerable mobiles = e.Mobile.GetMobilesInRange(2); + + foreach (PlayerVendor m in mobiles) + if (m.CanSee(e.Mobile) && m.InLOS(e.Mobile)) + m.OpenBackpack(from); + + mobiles.Free(); + } + + e.Handled = true; + } + } + else if (e.HasKeyword(0x3E) || e.HasKeyword(0x173) && WasNamed(e.Speech)) // vendor collect, *collect + { + if (IsOwner(from)) + { + CollectGold(from); + + e.Handled = true; + } + } + else if (e.HasKeyword(0x3F) || e.HasKeyword(0x174) && WasNamed(e.Speech)) // vendor status, *status + { + if (IsOwner(from)) + { + SendOwnerGump(from); + + e.Handled = true; + } + else + { + SayTo(from, 503226); // What do you care? You don't run this shop. + } + } + else if (e.HasKeyword(0x40) || e.HasKeyword(0x175) && WasNamed(e.Speech)) // vendor dismiss, *dismiss + { + if (IsOwner(from)) + { + Dismiss(from); + + e.Handled = true; + } + } + else if (e.HasKeyword(0x41) || e.HasKeyword(0x176) && WasNamed(e.Speech)) // vendor cycle, *cycle + { + if (IsOwner(from)) + { + Direction = GetDirectionTo(from); + + e.Handled = true; + } + } + } + + public override bool CanBeDamaged() + { + return false; + } + + private class ReturnVendorEntry : ContextMenuEntry + { + private PlayerVendor m_Vendor; + + public ReturnVendorEntry(PlayerVendor vendor) : base(6214) + { + m_Vendor = vendor; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (!m_Vendor.Deleted && m_Vendor.IsOwner(from) && from.CheckAlive()) + m_Vendor.Return(); + } + } + + private class PayTimer : Timer + { + private PlayerVendor m_Vendor; + + public PayTimer(PlayerVendor vendor, TimeSpan delay) : base(delay, GetInterval()) + { + m_Vendor = vendor; + + Priority = TimerPriority.OneMinute; + } + + public static TimeSpan GetInterval() + { + if (BaseHouse.NewVendorSystem) + return TimeSpan.FromDays(1.0); + return TimeSpan.FromMinutes(Clock.MinutesPerUODay); + } + + protected override void OnTick() + { + m_Vendor.NextPayTime = DateTime.UtcNow + Interval; + + int pay; + int totalGold; + if (BaseHouse.NewVendorSystem) + { + pay = m_Vendor.ChargePerRealWorldDay; + totalGold = m_Vendor.HoldGold; + } + else + { + pay = m_Vendor.ChargePerDay; + totalGold = m_Vendor.BankAccount + m_Vendor.HoldGold; + } + + if (pay > totalGold) + { + m_Vendor.Destroy(!BaseHouse.NewVendorSystem); + } + else + { + if (!BaseHouse.NewVendorSystem) + { + if (m_Vendor.BankAccount >= pay) + { + m_Vendor.BankAccount -= pay; + pay = 0; + } + else + { + pay -= m_Vendor.BankAccount; + m_Vendor.BankAccount = 0; + } + } + + m_Vendor.HoldGold -= pay; + } + } + } + + [PlayerVendorTarget] + private class PVBuyTarget : Target + { + public PVBuyTarget() : base(3, false, TargetFlags.None) + { + AllowNonlocal = true; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Item) TryToBuy((Item)targeted, from); + } + } + + private class VendorPricePrompt : Prompt + { + private PlayerVendor m_Vendor; + private VendorItem m_VI; + + public VendorPricePrompt(PlayerVendor vendor, VendorItem vi) + { + m_Vendor = vendor; + m_VI = vi; + } + + public override void OnResponse(Mobile from, string text) + { + if (!m_VI.Valid || !m_Vendor.CanInteractWith(from, true)) + return; + + string firstWord; + + int sep = text.IndexOfAny(new[] { ' ', ',' }); + if (sep >= 0) + firstWord = text.Substring(0, sep); + else + firstWord = text; + + int price; + string description; + + if (int.TryParse(firstWord, out price)) + { + if (sep >= 0) + description = text.Substring(sep + 1).Trim(); + else + description = ""; + } + else + { + price = -1; + description = text.Trim(); + } + + SetInfo(from, price, Utility.FixHtml(description)); + } + + public override void OnCancel(Mobile from) + { + if (!m_VI.Valid || !m_Vendor.CanInteractWith(from, true)) + return; + + SetInfo(from, -1, ""); + } + + private void SetInfo(Mobile from, int price, string description) + { + Item item = m_VI.Item; + + bool setPrice = false; + + if (price < 0) // Not for sale + { + price = -1; + + if (item is Container) + { + if (item is LockableContainer && ((LockableContainer)item).Locked) + m_Vendor.SayTo(from, 1043298); // Locked items may not be made not-for-sale. + else if (item.Items.Count > 0) + m_Vendor.SayTo(from, 1043299); // To be not for sale, all items in a container must be for sale. + else + setPrice = true; + } + else if (item is BaseBook || item is BulkOrderBook) + { + setPrice = true; + } + else + { + m_Vendor.SayTo(from, + 1043301); // Only the following may be made not-for-sale: books, containers, keyrings, and items in for-sale containers. + } + } + else + { + if (price > 100000000) + { + price = 100000000; + from.SendMessage("You cannot price items above 100,000,000 gold. The price has been adjusted."); + } + + setPrice = true; + } + + if (setPrice) + m_Vendor.SetVendorItem(item, price, description); + else + m_VI.Description = description; + } + } + + private class CollectGoldPrompt : Prompt + { + private PlayerVendor m_Vendor; + + public CollectGoldPrompt(PlayerVendor vendor) + { + m_Vendor = vendor; + } + + public override void OnResponse(Mobile from, string text) + { + if (!m_Vendor.CanInteractWith(from, true)) + return; + + text = text.Trim(); + + int amount; + + if (!int.TryParse(text, out amount)) + amount = 0; + + GiveGold(from, amount); + } + + public override void OnCancel(Mobile from) + { + if (!m_Vendor.CanInteractWith(from, true)) + return; + + GiveGold(from, 0); + } + + private void GiveGold(Mobile to, int amount) + { + if (amount <= 0) + m_Vendor.SayTo(to, "Very well. I will hold on to the money for now then."); + else + m_Vendor.GiveGold(to, amount); + } + } + + private class VendorNamePrompt : Prompt + { + private PlayerVendor m_Vendor; + + public VendorNamePrompt(PlayerVendor vendor) + { + m_Vendor = vendor; + } + + public override void OnResponse(Mobile from, string text) + { + if (!m_Vendor.CanInteractWith(from, true)) + return; + + string name = text.Trim(); + + if (!NameVerification.Validate(name, 1, 20, true, true, true, 0, NameVerification.Empty)) + { + m_Vendor.SayTo(from, "That name is unacceptable."); + return; + } + + m_Vendor.Name = Utility.FixHtml(name); + + from.SendLocalizedMessage(1062496); // Your vendor has been renamed. + + from.SendGump(new NewPlayerVendorOwnerGump(m_Vendor)); + } + } + + private class ShopNamePrompt : Prompt + { + private PlayerVendor m_Vendor; + + public ShopNamePrompt(PlayerVendor vendor) + { + m_Vendor = vendor; + } + + public override void OnResponse(Mobile from, string text) + { + if (!m_Vendor.CanInteractWith(from, true)) + return; + + string name = text.Trim(); + + if (!NameVerification.Validate(name, 1, 20, true, true, true, 0, NameVerification.Empty)) + { + m_Vendor.SayTo(from, "That name is unacceptable."); + return; + } + + m_Vendor.ShopName = Utility.FixHtml(name); + + from.SendGump(new NewPlayerVendorOwnerGump(m_Vendor)); + } + } + } + + public class PlayerVendorPlaceholder : Item + { + private ExpireTimer m_Timer; + + public PlayerVendorPlaceholder(PlayerVendor vendor) : base(0x1F28) + { + Hue = 0x672; + Movable = false; + + Vendor = vendor; + + m_Timer = new ExpireTimer(this); + m_Timer.Start(); + } + + public PlayerVendorPlaceholder(Serial serial) : base(serial) + { + } + + [CommandProperty(AccessLevel.GameMaster)] + public PlayerVendor Vendor{ get; private set; } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (Vendor != null) + list.Add(1062498, Vendor.Name); // reserved for vendor ~1_NAME~ + } + + public void RestartTimer() + { + m_Timer.Stop(); + m_Timer.Start(); + } + + public override void OnDelete() + { + if (Vendor != null && !Vendor.Deleted) + { + Vendor.MoveToWorld(Location, Map); + Vendor.Placeholder = null; + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); + + writer.Write(Vendor); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + Vendor = (PlayerVendor)reader.ReadMobile(); + + Timer.DelayCall(TimeSpan.Zero, Delete); + } + + private class ExpireTimer : Timer + { + private PlayerVendorPlaceholder m_Placeholder; + + public ExpireTimer(PlayerVendorPlaceholder placeholder) : base(TimeSpan.FromMinutes(2.0)) + { + m_Placeholder = placeholder; + + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + m_Placeholder.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/PresetMapBuy.cs b/Scripts/Mobiles/Vendors/PresetMapBuy.cs index 3317f4387..a43bf88ed 100644 --- a/Scripts/Mobiles/Vendors/PresetMapBuy.cs +++ b/Scripts/Mobiles/Vendors/PresetMapBuy.cs @@ -2,20 +2,21 @@ using Server.Items; namespace Server.Mobiles { - public class PresetMapBuyInfo : GenericBuyInfo - { - private PresetMapEntry m_Entry; + public class PresetMapBuyInfo : GenericBuyInfo + { + private PresetMapEntry m_Entry; - public override bool CanCacheDisplay => false; + public PresetMapBuyInfo(PresetMapEntry entry, int price, int amount) : base(entry.Name.ToString(), null, price, + amount, 0x14EC, 0) + { + m_Entry = entry; + } - public PresetMapBuyInfo( PresetMapEntry entry, int price, int amount ) : base( entry.Name.ToString(), null, price, amount, 0x14EC, 0 ) - { - m_Entry = entry; - } + public override bool CanCacheDisplay => false; - public override IEntity GetEntity() - { - return new PresetMap( m_Entry ); - } - } -} + public override IEntity GetEntity() + { + return new PresetMap(m_Entry); + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/RentedVendor.cs b/Scripts/Mobiles/Vendors/RentedVendor.cs index cdbd7369d..cc2111247 100644 --- a/Scripts/Mobiles/Vendors/RentedVendor.cs +++ b/Scripts/Mobiles/Vendors/RentedVendor.cs @@ -1,381 +1,380 @@ using System; using System.Collections.Generic; +using Server.ContextMenus; using Server.Gumps; using Server.Misc; using Server.Multis; -using Server.ContextMenus; using Server.Prompts; namespace Server.Mobiles { - public class VendorRentalDuration - { - public static readonly VendorRentalDuration[] Instances = { - new VendorRentalDuration( TimeSpan.FromDays( 7.0 ), 1062361 ), // 1 Week - new VendorRentalDuration( TimeSpan.FromDays( 14.0 ), 1062362 ), // 2 Weeks - new VendorRentalDuration( TimeSpan.FromDays( 21.0 ), 1062363 ), // 3 Weeks - new VendorRentalDuration( TimeSpan.FromDays( 28.0 ), 1062364 ) // 1 Month - }; - - public TimeSpan Duration { get; } - - public int Name { get; } - - public int ID - { - get - { - for ( int i = 0; i < Instances.Length; i++ ) - { - if ( Instances[i] == this ) - return i; - } - - return 0; - } - } - - private VendorRentalDuration( TimeSpan duration, int name ) - { - Duration = duration; - Name = name; - } - } - - public class RentedVendor : PlayerVendor - { - private Timer m_RentalExpireTimer; - - public RentedVendor( Mobile owner, BaseHouse house, VendorRentalDuration duration, int rentalPrice, bool landlordRenew, int rentalGold ) : base( owner, house ) - { - RentalDuration = duration; - RentalPrice = RenewalPrice = rentalPrice; - LandlordRenew = landlordRenew; - RenterRenew = false; - - RentalGold = rentalGold; - - RentalExpireTime = DateTime.UtcNow + duration.Duration; - m_RentalExpireTimer = new RentalExpireTimer( this, duration.Duration ); - m_RentalExpireTimer.Start(); - } - - public RentedVendor( Serial serial ) : base( serial ) - { - } - - public VendorRentalDuration RentalDuration { get; private set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RentalPrice { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool LandlordRenew { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool RenterRenew { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Renew => LandlordRenew && RenterRenew && House != null && House.DecayType != DecayType.Condemned; - - [CommandProperty( AccessLevel.GameMaster )] - public int RenewalPrice { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public int RentalGold { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime RentalExpireTime { get; private set; } - - public override bool IsOwner( Mobile m ) - { - return m == Owner || m.AccessLevel >= AccessLevel.GameMaster || ( Core.ML && AccountHandler.CheckAccount( m, Owner ) ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Landlord - { - get - { - return House?.Owner; - } - } - - public bool IsLandlord( Mobile m ) - { - return House != null && House.IsOwner( m ); - } - - public void ComputeRentalExpireDelay( out int days, out int hours ) - { - TimeSpan delay = RentalExpireTime - DateTime.UtcNow; - - if ( delay <= TimeSpan.Zero ) - { - days = 0; - hours = 0; - } - else - { - days = delay.Days; - hours = delay.Hours; - } - } - - public void SendRentalExpireMessage( Mobile to ) - { - int days, hours; - ComputeRentalExpireDelay( out days, out hours ); - - to.SendLocalizedMessage( 1062464, days.ToString() + "\t" + hours.ToString() ); // The rental contract on this vendor will expire in ~1_DAY~ day(s) and ~2_HOUR~ hour(s). - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_RentalExpireTimer.Stop(); - } - - public override void Destroy( bool toBackpack ) - { - if ( RentalGold > 0 && House != null && House.IsAosRules ) - { - if ( House.MovingCrate == null ) - House.MovingCrate = new MovingCrate( House ); - - Banker.Deposit( House.MovingCrate, RentalGold ); - RentalGold = 0; - } - - base.Destroy( toBackpack ); - } - - public override void GetContextMenuEntries( Mobile from, List list ) - { - if ( from.Alive ) - { - if ( IsOwner( from ) ) - { - list.Add( new ContractOptionsEntry( this ) ); - } - else if ( IsLandlord( from ) ) - { - if ( RentalGold > 0 ) - list.Add( new CollectRentEntry( this ) ); - - list.Add( new TerminateContractEntry( this ) ); - list.Add( new ContractOptionsEntry( this ) ); - } - } - - base.GetContextMenuEntries( from, list ); - } - - private class ContractOptionsEntry : ContextMenuEntry - { - private RentedVendor m_Vendor; - - public ContractOptionsEntry( RentedVendor vendor ) : base( 6209 ) - { - m_Vendor = vendor; - } - - public override void OnClick() - { - Mobile from = Owner.From; - - if ( m_Vendor.Deleted || !from.CheckAlive() ) - return; - - if ( m_Vendor.IsOwner( from ) ) - { - from.CloseGump( typeof( RenterVendorRentalGump ) ); - from.SendGump( new RenterVendorRentalGump( m_Vendor ) ); - - m_Vendor.SendRentalExpireMessage( from ); - } - else if ( m_Vendor.IsLandlord( from ) ) - { - from.CloseGump( typeof( LandlordVendorRentalGump ) ); - from.SendGump( new LandlordVendorRentalGump( m_Vendor ) ); - - m_Vendor.SendRentalExpireMessage( from ); - } - } - } - - private class CollectRentEntry : ContextMenuEntry - { - private RentedVendor m_Vendor; - - public CollectRentEntry( RentedVendor vendor ) : base( 6212 ) - { - m_Vendor = vendor; - } - - public override void OnClick() - { - Mobile from = Owner.From; - - if ( m_Vendor.Deleted || !from.CheckAlive() || !m_Vendor.IsLandlord( from ) ) - return; - - if ( m_Vendor.RentalGold > 0 ) - { - int depositedGold = Banker.DepositUpTo( from, m_Vendor.RentalGold ); - m_Vendor.RentalGold -= depositedGold; - - if ( depositedGold > 0 ) - from.SendLocalizedMessage( 1060397, depositedGold.ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. - - if ( m_Vendor.RentalGold > 0 ) - from.SendLocalizedMessage( 500390 ); // Your bank box is full. - } - } - } - - private class TerminateContractEntry : ContextMenuEntry - { - private RentedVendor m_Vendor; - - public TerminateContractEntry( RentedVendor vendor ) : base( 6218 ) - { - m_Vendor = vendor; - } - - public override void OnClick() - { - Mobile from = Owner.From; - - if ( m_Vendor.Deleted || !from.CheckAlive() || !m_Vendor.IsLandlord( from ) ) - return; - - from.SendLocalizedMessage( 1062503 ); // Enter the amount of gold you wish to offer the renter in exchange for immediate termination of this contract? - from.Prompt = new RefundOfferPrompt( m_Vendor ); - } - } - - private class RefundOfferPrompt : Prompt - { - private RentedVendor m_Vendor; - - public RefundOfferPrompt( RentedVendor vendor ) - { - m_Vendor = vendor; - } - - public override void OnResponse( Mobile from, string text ) - { - if ( !m_Vendor.CanInteractWith( from, false ) || !m_Vendor.IsLandlord( from ) ) - return; - - text = text.Trim(); - - int amount; - - if ( !int.TryParse( text, out amount ) ) - amount = -1; - - Mobile owner = m_Vendor.Owner; - if ( owner == null ) - return; - - if ( amount < 0 ) - { - from.SendLocalizedMessage( 1062506 ); // You did not enter a valid amount. Offer canceled. - } - else if ( Banker.GetBalance( from ) < amount ) - { - from.SendLocalizedMessage( 1062507 ); // You do not have that much money in your bank account. - } - else if ( owner.Map != m_Vendor.Map || !owner.InRange( m_Vendor, 5 ) ) - { - from.SendLocalizedMessage( 1062505 ); // The renter must be closer to the vendor in order for you to make this offer. - } - else - { - from.SendLocalizedMessage( 1062504 ); // Please wait while the renter considers your offer. - - owner.CloseGump( typeof( VendorRentalRefundGump ) ); - owner.SendGump( new VendorRentalRefundGump( m_Vendor, from, amount ) ); - } - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 0 ); // version - - writer.WriteEncodedInt( RentalDuration.ID ); - - writer.Write( (int) RentalPrice ); - writer.Write( (bool) LandlordRenew ); - writer.Write( (bool) RenterRenew ); - writer.Write( (int) RenewalPrice ); - - writer.Write( (int) RentalGold ); - - writer.WriteDeltaTime( (DateTime) RentalExpireTime ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - int durationID = reader.ReadEncodedInt(); - if ( durationID < VendorRentalDuration.Instances.Length ) - RentalDuration = VendorRentalDuration.Instances[durationID]; - else - RentalDuration = VendorRentalDuration.Instances[0]; - - RentalPrice = reader.ReadInt(); - LandlordRenew = reader.ReadBool(); - RenterRenew = reader.ReadBool(); - RenewalPrice = reader.ReadInt(); - - RentalGold = reader.ReadInt(); - - RentalExpireTime = reader.ReadDeltaTime(); - - TimeSpan delay = RentalExpireTime - DateTime.UtcNow; - m_RentalExpireTimer = new RentalExpireTimer( this, delay > TimeSpan.Zero ? delay : TimeSpan.Zero ); - m_RentalExpireTimer.Start(); - } - - private class RentalExpireTimer : Timer - { - private RentedVendor m_Vendor; - - public RentalExpireTimer( RentedVendor vendor, TimeSpan delay ) : base( delay, vendor.RentalDuration.Duration ) - { - m_Vendor = vendor; - - Priority = TimerPriority.OneMinute; - } - - protected override void OnTick() - { - int renewalPrice = m_Vendor.RenewalPrice; - - if ( m_Vendor.Renew && m_Vendor.HoldGold >= renewalPrice ) - { - m_Vendor.HoldGold -= renewalPrice; - m_Vendor.RentalGold += renewalPrice; - - m_Vendor.RentalPrice = renewalPrice; - - m_Vendor.RentalExpireTime = DateTime.UtcNow + m_Vendor.RentalDuration.Duration; - } - else - { - m_Vendor.Destroy( false ); - } - } - } - } + public class VendorRentalDuration + { + public static readonly VendorRentalDuration[] Instances = + { + new VendorRentalDuration(TimeSpan.FromDays(7.0), 1062361), // 1 Week + new VendorRentalDuration(TimeSpan.FromDays(14.0), 1062362), // 2 Weeks + new VendorRentalDuration(TimeSpan.FromDays(21.0), 1062363), // 3 Weeks + new VendorRentalDuration(TimeSpan.FromDays(28.0), 1062364) // 1 Month + }; + + private VendorRentalDuration(TimeSpan duration, int name) + { + Duration = duration; + Name = name; + } + + public TimeSpan Duration{ get; } + + public int Name{ get; } + + public int ID + { + get + { + for (int i = 0; i < Instances.Length; i++) + if (Instances[i] == this) + return i; + + return 0; + } + } + } + + public class RentedVendor : PlayerVendor + { + private Timer m_RentalExpireTimer; + + public RentedVendor(Mobile owner, BaseHouse house, VendorRentalDuration duration, int rentalPrice, + bool landlordRenew, int rentalGold) : base(owner, house) + { + RentalDuration = duration; + RentalPrice = RenewalPrice = rentalPrice; + LandlordRenew = landlordRenew; + RenterRenew = false; + + RentalGold = rentalGold; + + RentalExpireTime = DateTime.UtcNow + duration.Duration; + m_RentalExpireTimer = new RentalExpireTimer(this, duration.Duration); + m_RentalExpireTimer.Start(); + } + + public RentedVendor(Serial serial) : base(serial) + { + } + + public VendorRentalDuration RentalDuration{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int RentalPrice{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool LandlordRenew{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool RenterRenew{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Renew => LandlordRenew && RenterRenew && House != null && House.DecayType != DecayType.Condemned; + + [CommandProperty(AccessLevel.GameMaster)] + public int RenewalPrice{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int RentalGold{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime RentalExpireTime{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Landlord => House?.Owner; + + public override bool IsOwner(Mobile m) + { + return m == Owner || m.AccessLevel >= AccessLevel.GameMaster || Core.ML && AccountHandler.CheckAccount(m, Owner); + } + + public bool IsLandlord(Mobile m) + { + return House != null && House.IsOwner(m); + } + + public void ComputeRentalExpireDelay(out int days, out int hours) + { + TimeSpan delay = RentalExpireTime - DateTime.UtcNow; + + if (delay <= TimeSpan.Zero) + { + days = 0; + hours = 0; + } + else + { + days = delay.Days; + hours = delay.Hours; + } + } + + public void SendRentalExpireMessage(Mobile to) + { + int days, hours; + ComputeRentalExpireDelay(out days, out hours); + + to.SendLocalizedMessage(1062464, + days + "\t" + + hours); // The rental contract on this vendor will expire in ~1_DAY~ day(s) and ~2_HOUR~ hour(s). + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_RentalExpireTimer.Stop(); + } + + public override void Destroy(bool toBackpack) + { + if (RentalGold > 0 && House != null && House.IsAosRules) + { + if (House.MovingCrate == null) + House.MovingCrate = new MovingCrate(House); + + Banker.Deposit(House.MovingCrate, RentalGold); + RentalGold = 0; + } + + base.Destroy(toBackpack); + } + + public override void GetContextMenuEntries(Mobile from, List list) + { + if (from.Alive) + { + if (IsOwner(from)) + { + list.Add(new ContractOptionsEntry(this)); + } + else if (IsLandlord(from)) + { + if (RentalGold > 0) + list.Add(new CollectRentEntry(this)); + + list.Add(new TerminateContractEntry(this)); + list.Add(new ContractOptionsEntry(this)); + } + } + + base.GetContextMenuEntries(from, list); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(0); // version + + writer.WriteEncodedInt(RentalDuration.ID); + + writer.Write(RentalPrice); + writer.Write(LandlordRenew); + writer.Write(RenterRenew); + writer.Write(RenewalPrice); + + writer.Write(RentalGold); + + writer.WriteDeltaTime(RentalExpireTime); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + int durationID = reader.ReadEncodedInt(); + if (durationID < VendorRentalDuration.Instances.Length) + RentalDuration = VendorRentalDuration.Instances[durationID]; + else + RentalDuration = VendorRentalDuration.Instances[0]; + + RentalPrice = reader.ReadInt(); + LandlordRenew = reader.ReadBool(); + RenterRenew = reader.ReadBool(); + RenewalPrice = reader.ReadInt(); + + RentalGold = reader.ReadInt(); + + RentalExpireTime = reader.ReadDeltaTime(); + + TimeSpan delay = RentalExpireTime - DateTime.UtcNow; + m_RentalExpireTimer = new RentalExpireTimer(this, delay > TimeSpan.Zero ? delay : TimeSpan.Zero); + m_RentalExpireTimer.Start(); + } + + private class ContractOptionsEntry : ContextMenuEntry + { + private RentedVendor m_Vendor; + + public ContractOptionsEntry(RentedVendor vendor) : base(6209) + { + m_Vendor = vendor; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (m_Vendor.Deleted || !from.CheckAlive()) + return; + + if (m_Vendor.IsOwner(from)) + { + from.CloseGump(typeof(RenterVendorRentalGump)); + from.SendGump(new RenterVendorRentalGump(m_Vendor)); + + m_Vendor.SendRentalExpireMessage(from); + } + else if (m_Vendor.IsLandlord(from)) + { + from.CloseGump(typeof(LandlordVendorRentalGump)); + from.SendGump(new LandlordVendorRentalGump(m_Vendor)); + + m_Vendor.SendRentalExpireMessage(from); + } + } + } + + private class CollectRentEntry : ContextMenuEntry + { + private RentedVendor m_Vendor; + + public CollectRentEntry(RentedVendor vendor) : base(6212) + { + m_Vendor = vendor; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (m_Vendor.Deleted || !from.CheckAlive() || !m_Vendor.IsLandlord(from)) + return; + + if (m_Vendor.RentalGold > 0) + { + int depositedGold = Banker.DepositUpTo(from, m_Vendor.RentalGold); + m_Vendor.RentalGold -= depositedGold; + + if (depositedGold > 0) + from.SendLocalizedMessage(1060397, + depositedGold.ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + + if (m_Vendor.RentalGold > 0) + from.SendLocalizedMessage(500390); // Your bank box is full. + } + } + } + + private class TerminateContractEntry : ContextMenuEntry + { + private RentedVendor m_Vendor; + + public TerminateContractEntry(RentedVendor vendor) : base(6218) + { + m_Vendor = vendor; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (m_Vendor.Deleted || !from.CheckAlive() || !m_Vendor.IsLandlord(from)) + return; + + from.SendLocalizedMessage( + 1062503); // Enter the amount of gold you wish to offer the renter in exchange for immediate termination of this contract? + from.Prompt = new RefundOfferPrompt(m_Vendor); + } + } + + private class RefundOfferPrompt : Prompt + { + private RentedVendor m_Vendor; + + public RefundOfferPrompt(RentedVendor vendor) + { + m_Vendor = vendor; + } + + public override void OnResponse(Mobile from, string text) + { + if (!m_Vendor.CanInteractWith(from, false) || !m_Vendor.IsLandlord(from)) + return; + + text = text.Trim(); + + int amount; + + if (!int.TryParse(text, out amount)) + amount = -1; + + Mobile owner = m_Vendor.Owner; + if (owner == null) + return; + + if (amount < 0) + { + from.SendLocalizedMessage(1062506); // You did not enter a valid amount. Offer canceled. + } + else if (Banker.GetBalance(from) < amount) + { + from.SendLocalizedMessage(1062507); // You do not have that much money in your bank account. + } + else if (owner.Map != m_Vendor.Map || !owner.InRange(m_Vendor, 5)) + { + from.SendLocalizedMessage( + 1062505); // The renter must be closer to the vendor in order for you to make this offer. + } + else + { + from.SendLocalizedMessage(1062504); // Please wait while the renter considers your offer. + + owner.CloseGump(typeof(VendorRentalRefundGump)); + owner.SendGump(new VendorRentalRefundGump(m_Vendor, from, amount)); + } + } + } + + private class RentalExpireTimer : Timer + { + private RentedVendor m_Vendor; + + public RentalExpireTimer(RentedVendor vendor, TimeSpan delay) : base(delay, vendor.RentalDuration.Duration) + { + m_Vendor = vendor; + + Priority = TimerPriority.OneMinute; + } + + protected override void OnTick() + { + int renewalPrice = m_Vendor.RenewalPrice; + + if (m_Vendor.Renew && m_Vendor.HoldGold >= renewalPrice) + { + m_Vendor.HoldGold -= renewalPrice; + m_Vendor.RentalGold += renewalPrice; + + m_Vendor.RentalPrice = renewalPrice; + + m_Vendor.RentalExpireTime = DateTime.UtcNow + m_Vendor.RentalDuration.Duration; + } + else + { + m_Vendor.Destroy(false); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBChainmailArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBChainmailArmor.cs index cf610f9aa..c9d751c8f 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBChainmailArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBChainmailArmor.cs @@ -3,34 +3,30 @@ using Server.Items; namespace Server.Mobiles { - public class SBChainmailArmor: SBInfo - { - public SBChainmailArmor() - { - } + public class SBChainmailArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(ChainCoif), 17, 20, 0x13BB, 0)); + Add(new GenericBuyInfo(typeof(ChainChest), 143, 20, 0x13BF, 0)); + Add(new GenericBuyInfo(typeof(ChainLegs), 149, 20, 0x13BE, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( ChainCoif ), 17, 20, 0x13BB, 0 ) ); - Add( new GenericBuyInfo( typeof( ChainChest ), 143, 20, 0x13BF, 0 ) ); - Add( new GenericBuyInfo( typeof( ChainLegs ), 149, 20, 0x13BE, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( ChainCoif ), 6 ); - Add( typeof( ChainChest ), 71 ); - Add( typeof( ChainLegs ), 74 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(ChainCoif), 6); + Add(typeof(ChainChest), 71); + Add(typeof(ChainLegs), 74); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBHelmetArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBHelmetArmor.cs index 97468a773..7dfd52c44 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBHelmetArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBHelmetArmor.cs @@ -3,42 +3,38 @@ using Server.Items; namespace Server.Mobiles { - public class SBHelmetArmor: SBInfo - { - public SBHelmetArmor() - { - } + public class SBHelmetArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(PlateHelm), 21, 20, 0x1412, 0)); + Add(new GenericBuyInfo(typeof(CloseHelm), 18, 20, 0x1408, 0)); + Add(new GenericBuyInfo(typeof(CloseHelm), 18, 20, 0x1409, 0)); + Add(new GenericBuyInfo(typeof(Helmet), 31, 20, 0x140A, 0)); + Add(new GenericBuyInfo(typeof(Helmet), 18, 20, 0x140B, 0)); + Add(new GenericBuyInfo(typeof(NorseHelm), 18, 20, 0x140E, 0)); + Add(new GenericBuyInfo(typeof(NorseHelm), 18, 20, 0x140F, 0)); + Add(new GenericBuyInfo(typeof(Bascinet), 18, 20, 0x140C, 0)); + Add(new GenericBuyInfo(typeof(PlateHelm), 21, 20, 0x1419, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( PlateHelm ), 21, 20, 0x1412, 0 ) ); - Add( new GenericBuyInfo( typeof( CloseHelm ), 18, 20, 0x1408, 0 ) ); - Add( new GenericBuyInfo( typeof( CloseHelm ), 18, 20, 0x1409, 0 ) ); - Add( new GenericBuyInfo( typeof( Helmet ), 31, 20, 0x140A, 0 ) ); - Add( new GenericBuyInfo( typeof( Helmet ), 18, 20, 0x140B, 0 ) ); - Add( new GenericBuyInfo( typeof( NorseHelm ), 18, 20, 0x140E, 0 ) ); - Add( new GenericBuyInfo( typeof( NorseHelm ), 18, 20, 0x140F, 0 ) ); - Add( new GenericBuyInfo( typeof( Bascinet ), 18, 20, 0x140C, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateHelm ), 21, 20, 0x1419, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bascinet ), 9 ); - Add( typeof( CloseHelm ), 9 ); - Add( typeof( Helmet ), 9 ); - Add( typeof( NorseHelm ), 9 ); - Add( typeof( PlateHelm ), 10 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bascinet), 9); + Add(typeof(CloseHelm), 9); + Add(typeof(Helmet), 9); + Add(typeof(NorseHelm), 9); + Add(typeof(PlateHelm), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBLeatherArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBLeatherArmor.cs index 430cb2e96..3bf592d14 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBLeatherArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBLeatherArmor.cs @@ -3,51 +3,47 @@ using Server.Items; namespace Server.Mobiles { - public class SBLeatherArmor: SBInfo - { - public SBLeatherArmor() - { - } + public class SBLeatherArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(LeatherArms), 80, 20, 0x13CD, 0)); + Add(new GenericBuyInfo(typeof(LeatherChest), 101, 20, 0x13CC, 0)); + Add(new GenericBuyInfo(typeof(LeatherGloves), 60, 20, 0x13C6, 0)); + Add(new GenericBuyInfo(typeof(LeatherGorget), 74, 20, 0x13C7, 0)); + Add(new GenericBuyInfo(typeof(LeatherLegs), 80, 20, 0x13cb, 0)); + Add(new GenericBuyInfo(typeof(LeatherCap), 10, 20, 0x1DB9, 0)); + Add(new GenericBuyInfo(typeof(FemaleLeatherChest), 116, 20, 0x1C06, 0)); + Add(new GenericBuyInfo(typeof(LeatherBustierArms), 97, 20, 0x1C0A, 0)); + Add(new GenericBuyInfo(typeof(LeatherShorts), 86, 20, 0x1C00, 0)); + Add(new GenericBuyInfo(typeof(LeatherSkirt), 87, 20, 0x1C08, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( LeatherArms ), 80, 20, 0x13CD, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherChest ), 101, 20, 0x13CC, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherGloves ), 60, 20, 0x13C6, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherGorget ), 74, 20, 0x13C7, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherLegs ), 80, 20, 0x13cb, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherCap ), 10, 20, 0x1DB9, 0 ) ); - Add( new GenericBuyInfo( typeof( FemaleLeatherChest ), 116, 20, 0x1C06, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherBustierArms ), 97, 20, 0x1C0A, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherShorts ), 86, 20, 0x1C00, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherSkirt ), 87, 20, 0x1C08, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(LeatherArms), 40); + Add(typeof(LeatherChest), 52); + Add(typeof(LeatherGloves), 30); + Add(typeof(LeatherGorget), 37); + Add(typeof(LeatherLegs), 40); + Add(typeof(LeatherCap), 5); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( LeatherArms ), 40 ); - Add( typeof( LeatherChest ), 52 ); - Add( typeof( LeatherGloves ), 30 ); - Add( typeof( LeatherGorget ), 37 ); - Add( typeof( LeatherLegs ), 40 ); - Add( typeof( LeatherCap ), 5 ); - - Add( typeof( FemaleLeatherChest ), 18 ); - Add( typeof( FemaleStuddedChest ), 25 ); - Add( typeof( LeatherShorts ), 14 ); - Add( typeof( LeatherSkirt ), 11 ); - Add( typeof( LeatherBustierArms ), 11 ); - Add( typeof( StuddedBustierArms ), 27 ); - } - } - } -} + Add(typeof(FemaleLeatherChest), 18); + Add(typeof(FemaleStuddedChest), 25); + Add(typeof(LeatherShorts), 14); + Add(typeof(LeatherSkirt), 11); + Add(typeof(LeatherBustierArms), 11); + Add(typeof(StuddedBustierArms), 27); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBMetalShields.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBMetalShields.cs index b8d10a9ed..241ede93b 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBMetalShields.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBMetalShields.cs @@ -3,40 +3,36 @@ using Server.Items; namespace Server.Mobiles { - public class SBMetalShields : SBInfo - { - public SBMetalShields() - { - } + public class SBMetalShields : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BronzeShield), 66, 20, 0x1B72, 0)); + Add(new GenericBuyInfo(typeof(Buckler), 50, 20, 0x1B73, 0)); + Add(new GenericBuyInfo(typeof(MetalKiteShield), 123, 20, 0x1B74, 0)); + Add(new GenericBuyInfo(typeof(HeaterShield), 231, 20, 0x1B76, 0)); + Add(new GenericBuyInfo(typeof(WoodenKiteShield), 70, 20, 0x1B78, 0)); + Add(new GenericBuyInfo(typeof(MetalShield), 121, 20, 0x1B7B, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BronzeShield ), 66, 20, 0x1B72, 0 ) ); - Add( new GenericBuyInfo( typeof( Buckler ), 50, 20, 0x1B73, 0 ) ); - Add( new GenericBuyInfo( typeof( MetalKiteShield ), 123, 20, 0x1B74, 0 ) ); - Add( new GenericBuyInfo( typeof( HeaterShield ), 231, 20, 0x1B76, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenKiteShield ), 70, 20, 0x1B78, 0 ) ); - Add( new GenericBuyInfo( typeof( MetalShield ), 121, 20, 0x1B7B, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Buckler ), 25 ); - Add( typeof( BronzeShield ), 33 ); - Add( typeof( MetalShield ), 60 ); - Add( typeof( MetalKiteShield ), 62 ); - Add( typeof( HeaterShield ), 115 ); - Add( typeof( WoodenKiteShield ), 35 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Buckler), 25); + Add(typeof(BronzeShield), 33); + Add(typeof(MetalShield), 60); + Add(typeof(MetalKiteShield), 62); + Add(typeof(HeaterShield), 115); + Add(typeof(WoodenKiteShield), 35); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBPlateArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBPlateArmor.cs index 9661859f4..977160127 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBPlateArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBPlateArmor.cs @@ -3,41 +3,36 @@ using Server.Items; namespace Server.Mobiles { - public class SBPlateArmor: SBInfo - { - public SBPlateArmor() - { - } + public class SBPlateArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(PlateGorget), 104, 20, 0x1413, 0)); + Add(new GenericBuyInfo(typeof(PlateChest), 243, 20, 0x1415, 0)); + Add(new GenericBuyInfo(typeof(PlateLegs), 218, 20, 0x1411, 0)); + Add(new GenericBuyInfo(typeof(PlateArms), 188, 20, 0x1410, 0)); + Add(new GenericBuyInfo(typeof(PlateGloves), 155, 20, 0x1414, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( PlateGorget ), 104, 20, 0x1413, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateChest ), 243, 20, 0x1415, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateLegs ), 218, 20, 0x1411, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateArms ), 188, 20, 0x1410, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateGloves ), 155, 20, 0x1414, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(PlateArms), 94); + Add(typeof(PlateChest), 121); + Add(typeof(PlateGloves), 72); + Add(typeof(PlateGorget), 52); + Add(typeof(PlateLegs), 109); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( PlateArms ), 94 ); - Add( typeof( PlateChest ), 121 ); - Add( typeof( PlateGloves ), 72 ); - Add( typeof( PlateGorget ), 52 ); - Add( typeof( PlateLegs ), 109 ); - - Add( typeof( FemalePlateChest ), 113 ); - - } - } - } -} + Add(typeof(FemalePlateChest), 113); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBRingmailArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBRingmailArmor.cs index b6d711319..9518a340e 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBRingmailArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBRingmailArmor.cs @@ -3,37 +3,32 @@ using Server.Items; namespace Server.Mobiles { - public class SBRingmailArmor: SBInfo - { - public SBRingmailArmor() - { - } + public class SBRingmailArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(RingmailChest), 121, 20, 0x13ec, 0)); + Add(new GenericBuyInfo(typeof(RingmailLegs), 90, 20, 0x13F0, 0)); + Add(new GenericBuyInfo(typeof(RingmailArms), 85, 20, 0x13EE, 0)); + Add(new GenericBuyInfo(typeof(RingmailGloves), 93, 20, 0x13eb, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( RingmailChest ), 121, 20, 0x13ec, 0 ) ); - Add( new GenericBuyInfo( typeof( RingmailLegs ), 90, 20, 0x13F0, 0 ) ); - Add( new GenericBuyInfo( typeof( RingmailArms ), 85, 20, 0x13EE, 0 ) ); - Add( new GenericBuyInfo( typeof( RingmailGloves ), 93, 20, 0x13eb, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( RingmailArms ), 42 ); - Add( typeof( RingmailChest ), 60 ); - Add( typeof( RingmailGloves ), 26 ); - Add( typeof( RingmailLegs ), 45 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(RingmailArms), 42); + Add(typeof(RingmailChest), 60); + Add(typeof(RingmailGloves), 26); + Add(typeof(RingmailLegs), 45); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBStuddedArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBStuddedArmor.cs index 57a0d4c0b..f62112ace 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBStuddedArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBStuddedArmor.cs @@ -3,42 +3,38 @@ using Server.Items; namespace Server.Mobiles { - public class SBStuddedArmor: SBInfo - { - public SBStuddedArmor() - { - } + public class SBStuddedArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(StuddedArms), 87, 20, 0x13DC, 0)); + Add(new GenericBuyInfo(typeof(StuddedChest), 128, 20, 0x13DB, 0)); + Add(new GenericBuyInfo(typeof(StuddedGloves), 79, 20, 0x13D5, 0)); + Add(new GenericBuyInfo(typeof(StuddedGorget), 73, 20, 0x13D6, 0)); + Add(new GenericBuyInfo(typeof(StuddedLegs), 103, 20, 0x13DA, 0)); + Add(new GenericBuyInfo(typeof(FemaleStuddedChest), 142, 20, 0x1C02, 0)); + Add(new GenericBuyInfo(typeof(StuddedBustierArms), 120, 20, 0x1c0c, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( StuddedArms ), 87, 20, 0x13DC, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedChest ), 128, 20, 0x13DB, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedGloves ), 79, 20, 0x13D5, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedGorget ), 73, 20, 0x13D6, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedLegs ), 103, 20, 0x13DA, 0 ) ); - Add( new GenericBuyInfo( typeof( FemaleStuddedChest ), 142, 20, 0x1C02, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedBustierArms ), 120, 20, 0x1c0c, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( StuddedArms ), 43 ); - Add( typeof( StuddedChest ), 64 ); - Add( typeof( StuddedGloves ), 39 ); - Add( typeof( StuddedGorget ), 36 ); - Add( typeof( StuddedLegs ), 51 ); - Add( typeof( FemaleStuddedChest ), 71 ); - Add( typeof( StuddedBustierArms ), 60 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(StuddedArms), 43); + Add(typeof(StuddedChest), 64); + Add(typeof(StuddedGloves), 39); + Add(typeof(StuddedGorget), 36); + Add(typeof(StuddedLegs), 51); + Add(typeof(FemaleStuddedChest), 71); + Add(typeof(StuddedBustierArms), 60); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBWoodenShields.cs b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBWoodenShields.cs index 4e4761f49..41f2346e5 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Armors/SBWoodenShields.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Armors/SBWoodenShields.cs @@ -3,30 +3,26 @@ using Server.Items; namespace Server.Mobiles { - public class SBWoodenShields: SBInfo - { - public SBWoodenShields() - { - } + public class SBWoodenShields : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(WoodenShield), 30, 20, 0x1B7A, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( WoodenShield ), 30, 20, 0x1B7A, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( WoodenShield ), 15 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(WoodenShield), 15); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBAlchemist.cs b/Scripts/Mobiles/Vendors/SBInfo/SBAlchemist.cs index 89fd2ac8a..f15ae5b24 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBAlchemist.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBAlchemist.cs @@ -3,71 +3,67 @@ using Server.Items; namespace Server.Mobiles { - public class SBAlchemist : SBInfo - { - public SBAlchemist() - { - } + public class SBAlchemist : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(RefreshPotion), 15, 10, 0xF0B, 0)); + Add(new GenericBuyInfo(typeof(AgilityPotion), 15, 10, 0xF08, 0)); + Add(new GenericBuyInfo(typeof(NightSightPotion), 15, 10, 0xF06, 0)); + Add(new GenericBuyInfo(typeof(LesserHealPotion), 15, 10, 0xF0C, 0)); + Add(new GenericBuyInfo(typeof(StrengthPotion), 15, 10, 0xF09, 0)); + Add(new GenericBuyInfo(typeof(LesserPoisonPotion), 15, 10, 0xF0A, 0)); + Add(new GenericBuyInfo(typeof(LesserCurePotion), 15, 10, 0xF07, 0)); + Add(new GenericBuyInfo(typeof(LesserExplosionPotion), 21, 10, 0xF0D, 0)); + Add(new GenericBuyInfo(typeof(MortarPestle), 8, 10, 0xE9B, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( RefreshPotion ), 15, 10, 0xF0B, 0 ) ); - Add( new GenericBuyInfo( typeof( AgilityPotion ), 15, 10, 0xF08, 0 ) ); - Add( new GenericBuyInfo( typeof( NightSightPotion ), 15, 10, 0xF06, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserHealPotion ), 15, 10, 0xF0C, 0 ) ); - Add( new GenericBuyInfo( typeof( StrengthPotion ), 15, 10, 0xF09, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserPoisonPotion ), 15, 10, 0xF0A, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserCurePotion ), 15, 10, 0xF07, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserExplosionPotion ), 21, 10, 0xF0D, 0 ) ); - Add( new GenericBuyInfo( typeof( MortarPestle ), 8, 10, 0xE9B, 0 ) ); + Add(new GenericBuyInfo(typeof(BlackPearl), 5, 20, 0xF7A, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 20, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(SulfurousAsh), 3, 20, 0xF8C, 0)); - Add( new GenericBuyInfo( typeof( BlackPearl ), 5, 20, 0xF7A, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 20, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( SulfurousAsh ), 3, 20, 0xF8C, 0 ) ); + Add(new GenericBuyInfo(typeof(Bottle), 5, 100, 0xF0E, 0)); + Add(new GenericBuyInfo(typeof(HeatingStand), 2, 100, 0x1849, 0)); - Add( new GenericBuyInfo( typeof( Bottle ), 5, 100, 0xF0E, 0 ) ); - Add( new GenericBuyInfo( typeof( HeatingStand ), 2, 100, 0x1849, 0 ) ); + Add(new GenericBuyInfo("1041060", typeof(HairDye), 37, 10, 0xEFF, 0)); + } + } - Add( new GenericBuyInfo( "1041060", typeof( HairDye ), 37, 10, 0xEFF, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BlackPearl), 3); + Add(typeof(Bloodmoss), 3); + Add(typeof(MandrakeRoot), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Nightshade), 2); + Add(typeof(SpidersSilk), 2); + Add(typeof(SulfurousAsh), 2); + Add(typeof(Bottle), 3); + Add(typeof(MortarPestle), 4); + Add(typeof(HairDye), 19); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BlackPearl ), 3 ); - Add( typeof( Bloodmoss ), 3 ); - Add( typeof( MandrakeRoot ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( SpidersSilk ), 2 ); - Add( typeof( SulfurousAsh ), 2 ); - Add( typeof( Bottle ), 3 ); - Add( typeof( MortarPestle ), 4 ); - Add( typeof( HairDye ), 19 ); - - Add( typeof( NightSightPotion ), 7 ); - Add( typeof( AgilityPotion ), 7 ); - Add( typeof( StrengthPotion ), 7 ); - Add( typeof( RefreshPotion ), 7 ); - Add( typeof( LesserCurePotion ), 7 ); - Add( typeof( LesserHealPotion ), 7 ); - Add( typeof( LesserPoisonPotion ), 7 ); - Add( typeof( LesserExplosionPotion ), 10 ); - } - } - } -} + Add(typeof(NightSightPotion), 7); + Add(typeof(AgilityPotion), 7); + Add(typeof(StrengthPotion), 7); + Add(typeof(RefreshPotion), 7); + Add(typeof(LesserCurePotion), 7); + Add(typeof(LesserHealPotion), 7); + Add(typeof(LesserPoisonPotion), 7); + Add(typeof(LesserExplosionPotion), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBAnimalTrainer.cs b/Scripts/Mobiles/Vendors/SBInfo/SBAnimalTrainer.cs index 8db403177..86804d9a3 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBAnimalTrainer.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBAnimalTrainer.cs @@ -2,45 +2,37 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class SBAnimalTrainer : SBInfo - { - public SBAnimalTrainer() - { - } + public class SBAnimalTrainer : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new AnimalBuyInfo(1, typeof(Cat), 132, 10, 201, 0)); + Add(new AnimalBuyInfo(1, typeof(Dog), 170, 10, 217, 0)); + Add(new AnimalBuyInfo(1, typeof(Horse), 550, 10, 204, 0)); + Add(new AnimalBuyInfo(1, typeof(PackHorse), 631, 10, 291, 0)); + Add(new AnimalBuyInfo(1, typeof(PackLlama), 565, 10, 292, 0)); + Add(new AnimalBuyInfo(1, typeof(Rabbit), 106, 10, 205, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new AnimalBuyInfo( 1, typeof( Cat ), 132, 10, 201, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Dog ), 170, 10, 217, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Horse ), 550, 10, 204, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( PackHorse ), 631, 10, 291, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( PackLlama ), 565, 10, 292, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Rabbit ), 106, 10, 205, 0 ) ); + if (!Core.AOS) + { + Add(new AnimalBuyInfo(1, typeof(Eagle), 402, 10, 5, 0)); + Add(new AnimalBuyInfo(1, typeof(BrownBear), 855, 10, 167, 0)); + Add(new AnimalBuyInfo(1, typeof(GrizzlyBear), 1767, 10, 212, 0)); + Add(new AnimalBuyInfo(1, typeof(Panther), 1271, 10, 214, 0)); + Add(new AnimalBuyInfo(1, typeof(TimberWolf), 768, 10, 225, 0)); + Add(new AnimalBuyInfo(1, typeof(Rat), 107, 10, 238, 0)); + } + } + } - if ( !Core.AOS ) - { - Add( new AnimalBuyInfo( 1, typeof( Eagle ), 402, 10, 5, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( BrownBear ), 855, 10, 167, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( GrizzlyBear ), 1767, 10, 212, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Panther ), 1271, 10, 214, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( TimberWolf ), 768, 10, 225, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Rat ), 107, 10, 238, 0 ) ); - } - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBArchitect.cs b/Scripts/Mobiles/Vendors/SBInfo/SBArchitect.cs index 7ba2e23b7..5325e7669 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBArchitect.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBArchitect.cs @@ -3,35 +3,31 @@ using Server.Items; namespace Server.Mobiles { - public class SBArchitect : SBInfo - { - public SBArchitect() - { - } + public class SBArchitect : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo("1041280", typeof(InteriorDecorator), 10001, 20, 0xFC1, 0)); + if (Core.AOS) + Add(new GenericBuyInfo("1060651", typeof(HousePlacementTool), 627, 20, 0x14F6, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( "1041280", typeof( InteriorDecorator ), 10001, 20, 0xFC1, 0 ) ); - if ( Core.AOS ) - Add( new GenericBuyInfo( "1060651", typeof( HousePlacementTool ), 627, 20, 0x14F6, 0 )); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(InteriorDecorator), 5000); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( InteriorDecorator ), 5000 ); - - if ( Core.AOS ) - Add( typeof( HousePlacementTool ), 301 ); - } - } - } -} + if (Core.AOS) + Add(typeof(HousePlacementTool), 301); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBaker.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBaker.cs index eb6e63c69..4ed914fed 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBaker.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBaker.cs @@ -3,53 +3,49 @@ using Server.Items; namespace Server.Mobiles { - public class SBBaker : SBInfo - { - public SBBaker() - { - } + public class SBBaker : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BreadLoaf), 6, 20, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(BreadLoaf), 5, 20, 0x103C, 0)); + Add(new GenericBuyInfo(typeof(ApplePie), 7, 20, 0x1041, 0)); //OSI just has Pie, not Apple/Fruit/Meat + Add(new GenericBuyInfo(typeof(Cake), 13, 20, 0x9E9, 0)); + Add(new GenericBuyInfo(typeof(Muffins), 3, 20, 0x9EA, 0)); + Add(new GenericBuyInfo(typeof(SackFlour), 3, 20, 0x1039, 0)); + Add(new GenericBuyInfo(typeof(FrenchBread), 5, 20, 0x98C, 0)); + Add(new GenericBuyInfo(typeof(Cookies), 3, 20, 0x160b, 0)); + Add(new GenericBuyInfo(typeof(CheesePizza), 8, 10, 0x1040, 0)); // OSI just has Pizza + Add(new GenericBuyInfo(typeof(JarHoney), 3, 20, 0x9ec, 0)); + Add(new GenericBuyInfo(typeof(BowlFlour), 7, 20, 0xA1E, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BreadLoaf ), 6, 20, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 5, 20, 0x103C, 0 ) ); - Add( new GenericBuyInfo( typeof( ApplePie ), 7, 20, 0x1041, 0 ) ); //OSI just has Pie, not Apple/Fruit/Meat - Add( new GenericBuyInfo( typeof( Cake ), 13, 20, 0x9E9, 0 ) ); - Add( new GenericBuyInfo( typeof( Muffins ), 3, 20, 0x9EA, 0 ) ); - Add( new GenericBuyInfo( typeof( SackFlour ), 3, 20, 0x1039, 0 ) ); - Add( new GenericBuyInfo( typeof( FrenchBread ), 5, 20, 0x98C, 0 ) ); - Add( new GenericBuyInfo( typeof( Cookies ), 3, 20, 0x160b, 0 ) ); - Add( new GenericBuyInfo( typeof( CheesePizza ), 8, 10, 0x1040, 0 ) ); // OSI just has Pizza - Add( new GenericBuyInfo( typeof( JarHoney ), 3, 20, 0x9ec, 0 ) ); - Add (new GenericBuyInfo( typeof( BowlFlour ), 7, 20, 0xA1E, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BreadLoaf ), 3 ); - Add( typeof( FrenchBread ), 1 ); - Add( typeof( Cake ), 5 ); - Add( typeof( Cookies ), 3 ); - Add( typeof( Muffins ), 2 ); - Add( typeof( CheesePizza ), 4 ); - Add( typeof( ApplePie ), 5 ); - Add( typeof( PeachCobbler ), 5 ); - Add( typeof( Quiche ), 6 ); - Add( typeof( Dough ), 4 ); - Add( typeof( JarHoney ), 1 ); - Add( typeof( Pitcher ), 5 ); - Add( typeof( SackFlour ), 1 ); - Add( typeof( Eggs ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BreadLoaf), 3); + Add(typeof(FrenchBread), 1); + Add(typeof(Cake), 5); + Add(typeof(Cookies), 3); + Add(typeof(Muffins), 2); + Add(typeof(CheesePizza), 4); + Add(typeof(ApplePie), 5); + Add(typeof(PeachCobbler), 5); + Add(typeof(Quiche), 6); + Add(typeof(Dough), 4); + Add(typeof(JarHoney), 1); + Add(typeof(Pitcher), 5); + Add(typeof(SackFlour), 1); + Add(typeof(Eggs), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBanker.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBanker.cs index 22da9420e..f97986bfd 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBanker.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBanker.cs @@ -1,35 +1,29 @@ using System.Collections.Generic; using Server.Items; +using Server.Multis; namespace Server.Mobiles { - public class SBBanker : SBInfo - { - public SBBanker() - { - } + public class SBBanker : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo("1041243", typeof(ContractOfEmployment), 1252, 20, 0x14F0, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( "1041243", typeof( ContractOfEmployment ), 1252, 20, 0x14F0, 0 ) ); + if (BaseHouse.NewVendorSystem) + Add(new GenericBuyInfo("1062332", typeof(VendorRentalContract), 1252, 20, 0x14F0, 0x672)); + Add(new GenericBuyInfo("1047016", typeof(CommodityDeed), 5, 20, 0x14F0, 0x47)); + } + } - if ( Multis.BaseHouse.NewVendorSystem ) - Add( new GenericBuyInfo( "1062332", typeof( VendorRentalContract ), 1252, 20, 0x14F0, 0x672 ) ); - Add( new GenericBuyInfo( "1047016", typeof( CommodityDeed ), 5, 20, 0x14F0, 0x47 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBard.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBard.cs index 729c8007c..8a4bae901 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBard.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBard.cs @@ -3,37 +3,33 @@ using Server.Items; namespace Server.Mobiles { - public class SBBard: SBInfo - { - public SBBard() - { - } + public class SBBard : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Drums), 21, 10, 0x0E9C, 0)); + Add(new GenericBuyInfo(typeof(Tambourine), 21, 10, 0x0E9E, 0)); + Add(new GenericBuyInfo(typeof(LapHarp), 21, 10, 0x0EB2, 0)); + Add(new GenericBuyInfo(typeof(Lute), 21, 10, 0x0EB3, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Drums ), 21, ( 10 ), 0x0E9C, 0 ) ); - Add( new GenericBuyInfo( typeof( Tambourine ), 21, ( 10 ), 0x0E9E, 0 ) ); - Add( new GenericBuyInfo( typeof( LapHarp ), 21, ( 10 ), 0x0EB2, 0 ) ); - Add( new GenericBuyInfo( typeof( Lute ), 21, ( 10 ), 0x0EB3, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( LapHarp ), 10 ); - Add( typeof( Lute ), 10 ); - Add( typeof( Drums ), 10 ); - Add( typeof( Harp ), 10 ); - Add( typeof( Tambourine ), 10 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(LapHarp), 10); + Add(typeof(Lute), 10); + Add(typeof(Drums), 10); + Add(typeof(Harp), 10); + Add(typeof(Tambourine), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBarkeeper.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBarkeeper.cs index 43fe689cc..ade4c1f28 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBarkeeper.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBarkeeper.cs @@ -1,106 +1,103 @@ using System.Collections.Generic; using Server.Items; +using Server.Multis; namespace Server.Mobiles { - public class SBBarkeeper : SBInfo - { - public SBBarkeeper() - { - } + public class SBBarkeeper : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Ale, 7, 20, 0x99F, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Wine, 7, 20, 0x9C7, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Liquor, 7, 20, 0x99B, 0)); + Add(new BeverageBuyInfo(typeof(Jug), BeverageType.Cider, 13, 20, 0x9C8, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Milk, 7, 20, 0x9F0, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Ale, 11, 20, 0x1F95, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Cider, 11, 20, 0x1F97, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Liquor, 11, 20, 0x1F99, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Wine, 11, 20, 0x1F9B, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Water, 11, 20, 0x1F9D, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Ale, 7, 20, 0x99F, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Wine, 7, 20, 0x9C7, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Liquor, 7, 20, 0x99B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Jug ), BeverageType.Cider, 13, 20, 0x9C8, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Milk, 7, 20, 0x9F0, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Ale, 11, 20, 0x1F95, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Cider, 11, 20, 0x1F97, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Liquor, 11, 20, 0x1F99, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Wine, 11, 20, 0x1F9B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Water, 11, 20, 0x1F9D, 0 ) ); + Add(new GenericBuyInfo(typeof(BreadLoaf), 6, 10, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(CheeseWheel), 21, 10, 0x97E, 0)); + Add(new GenericBuyInfo(typeof(CookedBird), 17, 20, 0x9B7, 0)); + Add(new GenericBuyInfo(typeof(LambLeg), 8, 20, 0x160A, 0)); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 6, 10, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( CheeseWheel ), 21, 10, 0x97E, 0 ) ); - Add( new GenericBuyInfo( typeof( CookedBird ), 17, 20, 0x9B7, 0 ) ); - Add( new GenericBuyInfo( typeof( LambLeg ), 8, 20, 0x160A, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCarrots), 3, 20, 0x15F9, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCorn), 3, 20, 0x15FA, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfLettuce), 3, 20, 0x15FB, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfPeas), 3, 20, 0x15FC, 0)); + Add(new GenericBuyInfo(typeof(EmptyPewterBowl), 2, 20, 0x15FD, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfCorn), 3, 20, 0x15FE, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfLettuce), 3, 20, 0x15FF, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPeas), 3, 20, 0x1600, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPotatos), 3, 20, 0x1601, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfStew), 3, 20, 0x1604, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfTomatoSoup), 3, 20, 0x1606, 0)); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCarrots ), 3, 20, 0x15F9, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCorn ), 3, 20, 0x15FA, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfLettuce ), 3, 20, 0x15FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfPeas ), 3, 20, 0x15FC, 0 ) ); - Add( new GenericBuyInfo( typeof( EmptyPewterBowl ), 2, 20, 0x15FD, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfCorn ), 3, 20, 0x15FE, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfLettuce ), 3, 20, 0x15FF, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPeas ), 3, 20, 0x1600, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPotatos ), 3, 20, 0x1601, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfStew ), 3, 20, 0x1604, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfTomatoSoup ), 3, 20, 0x1606, 0 ) ); + Add(new GenericBuyInfo(typeof(ApplePie), 7, 20, 0x1041, 0)); //OSI just has Pie, not Apple/Fruit/Meat - Add( new GenericBuyInfo( typeof( ApplePie ), 7, 20, 0x1041, 0 ) ); //OSI just has Pie, not Apple/Fruit/Meat + Add(new GenericBuyInfo("1016450", typeof(Chessboard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo("1016449", typeof(CheckerBoard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo(typeof(Backgammon), 2, 20, 0xE1C, 0)); + Add(new GenericBuyInfo(typeof(Dices), 2, 20, 0xFA7, 0)); + Add(new GenericBuyInfo("1041243", typeof(ContractOfEmployment), 1252, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("a barkeep contract", typeof(BarkeepContract), 1252, 20, 0x14F0, 0)); + if (BaseHouse.NewVendorSystem) + Add(new GenericBuyInfo("1062332", typeof(VendorRentalContract), 1252, 20, 0x14F0, 0x672)); - Add( new GenericBuyInfo( "1016450", typeof( Chessboard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( "1016449", typeof( CheckerBoard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( typeof( Backgammon ), 2, 20, 0xE1C, 0 ) ); - Add( new GenericBuyInfo( typeof( Dices ), 2, 20, 0xFA7, 0 ) ); - Add( new GenericBuyInfo( "1041243", typeof( ContractOfEmployment ), 1252, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "a barkeep contract", typeof( BarkeepContract ), 1252, 20, 0x14F0, 0 ) ); - if ( Multis.BaseHouse.NewVendorSystem ) - Add( new GenericBuyInfo( "1062332", typeof( VendorRentalContract ), 1252, 20, 0x14F0, 0x672 ) ); + /*if ( Map == Tokuno ) + { + Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E8, 0 ) ); + Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E9, 0 ) ); + Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2836, 0 ) ); + Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2837, 0 ) ); + Add( new GenericBuyInfo( typeof( GreenTeaBasket ), 2, 20, 0x284B, 0 ) ); + }*/ + } + } - /*if ( Map == Tokuno ) - { - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E8, 0 ) ); - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E9, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2836, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2837, 0 ) ); - Add( new GenericBuyInfo( typeof( GreenTeaBasket ), 2, 20, 0x284B, 0 ) ); - }*/ - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( WoodenBowlOfCarrots ), 1 ); - Add( typeof( WoodenBowlOfCorn ), 1 ); - Add( typeof( WoodenBowlOfLettuce ), 1 ); - Add( typeof( WoodenBowlOfPeas ), 1 ); - Add( typeof( EmptyPewterBowl ), 1 ); - Add( typeof( PewterBowlOfCorn ), 1 ); - Add( typeof( PewterBowlOfLettuce ), 1 ); - Add( typeof( PewterBowlOfPeas ), 1 ); - Add( typeof( PewterBowlOfPotatos ), 1 ); - Add( typeof( WoodenBowlOfStew ), 1 ); - Add( typeof( WoodenBowlOfTomatoSoup ), 1 ); - Add( typeof( BeverageBottle ), 3 ); - Add( typeof( Jug ), 6 ); - Add( typeof( Pitcher ), 5 ); - Add( typeof( GlassMug ), 1 ); - Add( typeof( BreadLoaf ), 3 ); - Add( typeof( CheeseWheel ), 12 ); - Add( typeof( Ribs ), 6 ); - Add( typeof( Peach ), 1 ); - Add( typeof( Pear ), 1 ); - Add( typeof( Grapes ), 1 ); - Add( typeof( Apple ), 1 ); - Add( typeof( Banana ), 1 ); - Add( typeof( Candle ), 3 ); - Add( typeof( Chessboard ), 1 ); - Add( typeof( CheckerBoard ), 1 ); - Add( typeof( Backgammon ), 1 ); - Add( typeof( Dices ), 1 ); - Add( typeof( ContractOfEmployment ), 626 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(WoodenBowlOfCarrots), 1); + Add(typeof(WoodenBowlOfCorn), 1); + Add(typeof(WoodenBowlOfLettuce), 1); + Add(typeof(WoodenBowlOfPeas), 1); + Add(typeof(EmptyPewterBowl), 1); + Add(typeof(PewterBowlOfCorn), 1); + Add(typeof(PewterBowlOfLettuce), 1); + Add(typeof(PewterBowlOfPeas), 1); + Add(typeof(PewterBowlOfPotatos), 1); + Add(typeof(WoodenBowlOfStew), 1); + Add(typeof(WoodenBowlOfTomatoSoup), 1); + Add(typeof(BeverageBottle), 3); + Add(typeof(Jug), 6); + Add(typeof(Pitcher), 5); + Add(typeof(GlassMug), 1); + Add(typeof(BreadLoaf), 3); + Add(typeof(CheeseWheel), 12); + Add(typeof(Ribs), 6); + Add(typeof(Peach), 1); + Add(typeof(Pear), 1); + Add(typeof(Grapes), 1); + Add(typeof(Apple), 1); + Add(typeof(Banana), 1); + Add(typeof(Candle), 3); + Add(typeof(Chessboard), 1); + Add(typeof(CheckerBoard), 1); + Add(typeof(Backgammon), 1); + Add(typeof(Dices), 1); + Add(typeof(ContractOfEmployment), 626); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBeekeeper.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBeekeeper.cs index 42aa05cc9..02d08aea8 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBeekeeper.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBeekeeper.cs @@ -3,32 +3,28 @@ using Server.Items; namespace Server.Mobiles { - public class SBBeekeeper : SBInfo - { - public SBBeekeeper() - { - } + public class SBBeekeeper : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(JarHoney), 3, 20, 0x9EC, 0)); + Add(new GenericBuyInfo(typeof(Beeswax), 2, 20, 0x1422, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( JarHoney ), 3, 20, 0x9EC, 0 ) ); - Add( new GenericBuyInfo( typeof( Beeswax ), 2, 20, 0x1422, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( JarHoney ), 1 ); - Add( typeof( Beeswax ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(JarHoney), 1); + Add(typeof(Beeswax), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBlacksmith.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBlacksmith.cs index 8be5b3384..62cc0db71 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBlacksmith.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBlacksmith.cs @@ -3,229 +3,223 @@ using Server.Items; namespace Server.Mobiles { - public class SBBlacksmith : SBInfo - { - public SBBlacksmith() - { - } + public class SBBlacksmith : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(IronIngot), 5, 16, 0x1BF2, 0)); + Add(new GenericBuyInfo(typeof(Tongs), 13, 14, 0xFBB, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( IronIngot ), 5, 16, 0x1BF2, 0 ) ); - Add( new GenericBuyInfo( typeof( Tongs ), 13, 14, 0xFBB, 0 ) ); + Add(new GenericBuyInfo(typeof(BronzeShield), 66, 20, 0x1B72, 0)); + Add(new GenericBuyInfo(typeof(Buckler), 50, 20, 0x1B73, 0)); + Add(new GenericBuyInfo(typeof(MetalKiteShield), 123, 20, 0x1B74, 0)); + Add(new GenericBuyInfo(typeof(HeaterShield), 231, 20, 0x1B76, 0)); + Add(new GenericBuyInfo(typeof(WoodenKiteShield), 70, 20, 0x1B78, 0)); + Add(new GenericBuyInfo(typeof(MetalShield), 121, 20, 0x1B7B, 0)); - Add( new GenericBuyInfo( typeof( BronzeShield ), 66, 20, 0x1B72, 0 ) ); - Add( new GenericBuyInfo( typeof( Buckler ), 50, 20, 0x1B73, 0 ) ); - Add( new GenericBuyInfo( typeof( MetalKiteShield ), 123, 20, 0x1B74, 0 ) ); - Add( new GenericBuyInfo( typeof( HeaterShield ), 231, 20, 0x1B76, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenKiteShield ), 70, 20, 0x1B78, 0 ) ); - Add( new GenericBuyInfo( typeof( MetalShield ), 121, 20, 0x1B7B, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenShield), 30, 20, 0x1B7A, 0)); - Add( new GenericBuyInfo( typeof( WoodenShield ), 30, 20, 0x1B7A, 0 ) ); + Add(new GenericBuyInfo(typeof(PlateGorget), 104, 20, 0x1413, 0)); + Add(new GenericBuyInfo(typeof(PlateChest), 243, 20, 0x1415, 0)); + Add(new GenericBuyInfo(typeof(PlateLegs), 218, 20, 0x1411, 0)); + Add(new GenericBuyInfo(typeof(PlateArms), 188, 20, 0x1410, 0)); + Add(new GenericBuyInfo(typeof(PlateGloves), 155, 20, 0x1414, 0)); - Add( new GenericBuyInfo( typeof( PlateGorget ), 104, 20, 0x1413, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateChest ), 243, 20, 0x1415, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateLegs ), 218, 20, 0x1411, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateArms ), 188, 20, 0x1410, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateGloves ), 155, 20, 0x1414, 0 ) ); + Add(new GenericBuyInfo(typeof(PlateHelm), 21, 20, 0x1412, 0)); + Add(new GenericBuyInfo(typeof(CloseHelm), 18, 20, 0x1408, 0)); + Add(new GenericBuyInfo(typeof(CloseHelm), 18, 20, 0x1409, 0)); + Add(new GenericBuyInfo(typeof(Helmet), 31, 20, 0x140A, 0)); + Add(new GenericBuyInfo(typeof(Helmet), 18, 20, 0x140B, 0)); + Add(new GenericBuyInfo(typeof(NorseHelm), 18, 20, 0x140E, 0)); + Add(new GenericBuyInfo(typeof(NorseHelm), 18, 20, 0x140F, 0)); + Add(new GenericBuyInfo(typeof(Bascinet), 18, 20, 0x140C, 0)); + Add(new GenericBuyInfo(typeof(PlateHelm), 21, 20, 0x1419, 0)); - Add( new GenericBuyInfo( typeof( PlateHelm ), 21, 20, 0x1412, 0 ) ); - Add( new GenericBuyInfo( typeof( CloseHelm ), 18, 20, 0x1408, 0 ) ); - Add( new GenericBuyInfo( typeof( CloseHelm ), 18, 20, 0x1409, 0 ) ); - Add( new GenericBuyInfo( typeof( Helmet ), 31, 20, 0x140A, 0 ) ); - Add( new GenericBuyInfo( typeof( Helmet ), 18, 20, 0x140B, 0 ) ); - Add( new GenericBuyInfo( typeof( NorseHelm ), 18, 20, 0x140E, 0 ) ); - Add( new GenericBuyInfo( typeof( NorseHelm ), 18, 20, 0x140F, 0 ) ); - Add( new GenericBuyInfo( typeof( Bascinet ), 18, 20, 0x140C, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateHelm ), 21, 20, 0x1419, 0 ) ); + Add(new GenericBuyInfo(typeof(ChainCoif), 17, 20, 0x13BB, 0)); + Add(new GenericBuyInfo(typeof(ChainChest), 143, 20, 0x13BF, 0)); + Add(new GenericBuyInfo(typeof(ChainLegs), 149, 20, 0x13BE, 0)); - Add( new GenericBuyInfo( typeof( ChainCoif ), 17, 20, 0x13BB, 0 ) ); - Add( new GenericBuyInfo( typeof( ChainChest ), 143, 20, 0x13BF, 0 ) ); - Add( new GenericBuyInfo( typeof( ChainLegs ), 149, 20, 0x13BE, 0 ) ); + Add(new GenericBuyInfo(typeof(RingmailChest), 121, 20, 0x13ec, 0)); + Add(new GenericBuyInfo(typeof(RingmailLegs), 90, 20, 0x13F0, 0)); + Add(new GenericBuyInfo(typeof(RingmailArms), 85, 20, 0x13EE, 0)); + Add(new GenericBuyInfo(typeof(RingmailGloves), 93, 20, 0x13eb, 0)); - Add( new GenericBuyInfo( typeof( RingmailChest ), 121, 20, 0x13ec, 0 ) ); - Add( new GenericBuyInfo( typeof( RingmailLegs ), 90, 20, 0x13F0, 0 ) ); - Add( new GenericBuyInfo( typeof( RingmailArms ), 85, 20, 0x13EE, 0 ) ); - Add( new GenericBuyInfo( typeof( RingmailGloves ), 93, 20, 0x13eb, 0 ) ); + Add(new GenericBuyInfo(typeof(ExecutionersAxe), 30, 20, 0xF45, 0)); + Add(new GenericBuyInfo(typeof(Bardiche), 60, 20, 0xF4D, 0)); + Add(new GenericBuyInfo(typeof(BattleAxe), 26, 20, 0xF47, 0)); + Add(new GenericBuyInfo(typeof(TwoHandedAxe), 32, 20, 0x1443, 0)); + Add(new GenericBuyInfo(typeof(Bow), 35, 20, 0x13B2, 0)); + Add(new GenericBuyInfo(typeof(ButcherKnife), 14, 20, 0x13F6, 0)); + Add(new GenericBuyInfo(typeof(Crossbow), 46, 20, 0xF50, 0)); + Add(new GenericBuyInfo(typeof(HeavyCrossbow), 55, 20, 0x13FD, 0)); + Add(new GenericBuyInfo(typeof(Cutlass), 24, 20, 0x1441, 0)); + Add(new GenericBuyInfo(typeof(Dagger), 21, 20, 0xF52, 0)); + Add(new GenericBuyInfo(typeof(Halberd), 42, 20, 0x143E, 0)); + Add(new GenericBuyInfo(typeof(HammerPick), 26, 20, 0x143D, 0)); + Add(new GenericBuyInfo(typeof(Katana), 33, 20, 0x13FF, 0)); + Add(new GenericBuyInfo(typeof(Kryss), 32, 20, 0x1401, 0)); + Add(new GenericBuyInfo(typeof(Broadsword), 35, 20, 0xF5E, 0)); + Add(new GenericBuyInfo(typeof(Longsword), 55, 20, 0xF61, 0)); + Add(new GenericBuyInfo(typeof(ThinLongsword), 27, 20, 0x13B8, 0)); + Add(new GenericBuyInfo(typeof(VikingSword), 55, 20, 0x13B9, 0)); + Add(new GenericBuyInfo(typeof(Cleaver), 15, 20, 0xEC3, 0)); + Add(new GenericBuyInfo(typeof(Axe), 40, 20, 0xF49, 0)); + Add(new GenericBuyInfo(typeof(DoubleAxe), 52, 20, 0xF4B, 0)); + Add(new GenericBuyInfo(typeof(Pickaxe), 22, 20, 0xE86, 0)); + Add(new GenericBuyInfo(typeof(Pitchfork), 19, 20, 0xE87, 0)); + Add(new GenericBuyInfo(typeof(Scimitar), 36, 20, 0x13B6, 0)); + Add(new GenericBuyInfo(typeof(SkinningKnife), 14, 20, 0xEC4, 0)); + Add(new GenericBuyInfo(typeof(LargeBattleAxe), 33, 20, 0x13FB, 0)); + Add(new GenericBuyInfo(typeof(WarAxe), 29, 20, 0x13B0, 0)); - Add( new GenericBuyInfo( typeof( ExecutionersAxe ), 30, 20, 0xF45, 0 ) ); - Add( new GenericBuyInfo( typeof( Bardiche ), 60, 20, 0xF4D, 0 ) ); - Add( new GenericBuyInfo( typeof( BattleAxe ), 26, 20, 0xF47, 0 ) ); - Add( new GenericBuyInfo( typeof( TwoHandedAxe ), 32, 20, 0x1443, 0 ) ); - Add( new GenericBuyInfo( typeof( Bow ), 35, 20, 0x13B2, 0 ) ); - Add( new GenericBuyInfo( typeof( ButcherKnife ), 14, 20, 0x13F6, 0 ) ); - Add( new GenericBuyInfo( typeof( Crossbow ), 46, 20, 0xF50, 0 ) ); - Add( new GenericBuyInfo( typeof( HeavyCrossbow ), 55, 20, 0x13FD, 0 ) ); - Add( new GenericBuyInfo( typeof( Cutlass ), 24, 20, 0x1441, 0 ) ); - Add( new GenericBuyInfo( typeof( Dagger ), 21, 20, 0xF52, 0 ) ); - Add( new GenericBuyInfo( typeof( Halberd ), 42, 20, 0x143E, 0 ) ); - Add( new GenericBuyInfo( typeof( HammerPick ), 26, 20, 0x143D, 0 ) ); - Add( new GenericBuyInfo( typeof( Katana ), 33, 20, 0x13FF, 0 ) ); - Add( new GenericBuyInfo( typeof( Kryss ), 32, 20, 0x1401, 0 ) ); - Add( new GenericBuyInfo( typeof( Broadsword ), 35, 20, 0xF5E, 0 ) ); - Add( new GenericBuyInfo( typeof( Longsword ), 55, 20, 0xF61, 0 ) ); - Add( new GenericBuyInfo( typeof( ThinLongsword ), 27, 20, 0x13B8, 0 ) ); - Add( new GenericBuyInfo( typeof( VikingSword ), 55, 20, 0x13B9, 0 ) ); - Add( new GenericBuyInfo( typeof( Cleaver ), 15, 20, 0xEC3, 0 ) ); - Add( new GenericBuyInfo( typeof( Axe ), 40, 20, 0xF49, 0 ) ); - Add( new GenericBuyInfo( typeof( DoubleAxe ), 52, 20, 0xF4B, 0 ) ); - Add( new GenericBuyInfo( typeof( Pickaxe ), 22, 20, 0xE86, 0 ) ); - Add( new GenericBuyInfo( typeof( Pitchfork ), 19, 20, 0xE87, 0 ) ); - Add( new GenericBuyInfo( typeof( Scimitar ), 36, 20, 0x13B6, 0 ) ); - Add( new GenericBuyInfo( typeof( SkinningKnife ), 14, 20, 0xEC4, 0 ) ); - Add( new GenericBuyInfo( typeof( LargeBattleAxe ), 33, 20, 0x13FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WarAxe ), 29, 20, 0x13B0, 0 ) ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(BoneHarvester), 35, 20, 0x26BB, 0)); + Add(new GenericBuyInfo(typeof(CrescentBlade), 37, 20, 0x26C1, 0)); + Add(new GenericBuyInfo(typeof(DoubleBladedStaff), 35, 20, 0x26BF, 0)); + Add(new GenericBuyInfo(typeof(Lance), 34, 20, 0x26C0, 0)); + Add(new GenericBuyInfo(typeof(Pike), 39, 20, 0x26BE, 0)); + Add(new GenericBuyInfo(typeof(Scythe), 39, 20, 0x26BA, 0)); + Add(new GenericBuyInfo(typeof(CompositeBow), 50, 20, 0x26C2, 0)); + Add(new GenericBuyInfo(typeof(RepeatingCrossbow), 57, 20, 0x26C3, 0)); + } - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( BoneHarvester ), 35, 20, 0x26BB, 0 ) ); - Add( new GenericBuyInfo( typeof( CrescentBlade ), 37, 20, 0x26C1, 0 ) ); - Add( new GenericBuyInfo( typeof( DoubleBladedStaff ), 35, 20, 0x26BF, 0 ) ); - Add( new GenericBuyInfo( typeof( Lance ), 34, 20, 0x26C0, 0 ) ); - Add( new GenericBuyInfo( typeof( Pike ), 39, 20, 0x26BE, 0 ) ); - Add( new GenericBuyInfo( typeof( Scythe ), 39, 20, 0x26BA, 0 ) ); - Add( new GenericBuyInfo( typeof( CompositeBow ), 50, 20, 0x26C2, 0 ) ); - Add( new GenericBuyInfo( typeof( RepeatingCrossbow ), 57, 20, 0x26C3, 0 ) ); - } + Add(new GenericBuyInfo(typeof(BlackStaff), 22, 20, 0xDF1, 0)); + Add(new GenericBuyInfo(typeof(Club), 16, 20, 0x13B4, 0)); + Add(new GenericBuyInfo(typeof(GnarledStaff), 16, 20, 0x13F8, 0)); + Add(new GenericBuyInfo(typeof(Mace), 28, 20, 0xF5C, 0)); + Add(new GenericBuyInfo(typeof(Maul), 21, 20, 0x143B, 0)); + Add(new GenericBuyInfo(typeof(QuarterStaff), 19, 20, 0xE89, 0)); + Add(new GenericBuyInfo(typeof(ShepherdsCrook), 20, 20, 0xE81, 0)); + Add(new GenericBuyInfo(typeof(SmithHammer), 21, 20, 0x13E3, 0)); + Add(new GenericBuyInfo(typeof(ShortSpear), 23, 20, 0x1403, 0)); + Add(new GenericBuyInfo(typeof(Spear), 31, 20, 0xF62, 0)); + Add(new GenericBuyInfo(typeof(WarHammer), 25, 20, 0x1439, 0)); + Add(new GenericBuyInfo(typeof(WarMace), 31, 20, 0x1407, 0)); - Add( new GenericBuyInfo( typeof( BlackStaff ), 22, 20, 0xDF1, 0 ) ); - Add( new GenericBuyInfo( typeof( Club ), 16, 20, 0x13B4, 0 ) ); - Add( new GenericBuyInfo( typeof( GnarledStaff ), 16, 20, 0x13F8, 0 ) ); - Add( new GenericBuyInfo( typeof( Mace ), 28, 20, 0xF5C, 0 ) ); - Add( new GenericBuyInfo( typeof( Maul ), 21, 20, 0x143B, 0 ) ); - Add( new GenericBuyInfo( typeof( QuarterStaff ), 19, 20, 0xE89, 0 ) ); - Add( new GenericBuyInfo( typeof( ShepherdsCrook ), 20, 20, 0xE81, 0 ) ); - Add( new GenericBuyInfo( typeof( SmithHammer ), 21, 20, 0x13E3, 0 ) ); - Add( new GenericBuyInfo( typeof( ShortSpear ), 23, 20, 0x1403, 0 ) ); - Add( new GenericBuyInfo( typeof( Spear ), 31, 20, 0xF62, 0 ) ); - Add( new GenericBuyInfo( typeof( WarHammer ), 25, 20, 0x1439, 0 ) ); - Add( new GenericBuyInfo( typeof( WarMace ), 31, 20, 0x1407, 0 ) ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(Scepter), 39, 20, 0x26BC, 0)); + Add(new GenericBuyInfo(typeof(BladedStaff), 40, 20, 0x26BD, 0)); + } + } + } - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( Scepter ), 39, 20, 0x26BC, 0 ) ); - Add( new GenericBuyInfo( typeof( BladedStaff ), 40, 20, 0x26BD, 0 ) ); - } - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Tongs), 7); + Add(typeof(IronIngot), 4); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Tongs ), 7 ); - Add( typeof( IronIngot ), 4 ); + Add(typeof(Buckler), 25); + Add(typeof(BronzeShield), 33); + Add(typeof(MetalShield), 60); + Add(typeof(MetalKiteShield), 62); + Add(typeof(HeaterShield), 115); + Add(typeof(WoodenKiteShield), 35); - Add( typeof( Buckler ), 25 ); - Add( typeof( BronzeShield ), 33 ); - Add( typeof( MetalShield ), 60 ); - Add( typeof( MetalKiteShield ), 62 ); - Add( typeof( HeaterShield ), 115 ); - Add( typeof( WoodenKiteShield ), 35 ); + Add(typeof(WoodenShield), 15); - Add( typeof( WoodenShield ), 15 ); + Add(typeof(PlateArms), 94); + Add(typeof(PlateChest), 121); + Add(typeof(PlateGloves), 72); + Add(typeof(PlateGorget), 52); + Add(typeof(PlateLegs), 109); - Add( typeof( PlateArms ), 94 ); - Add( typeof( PlateChest ), 121 ); - Add( typeof( PlateGloves ), 72 ); - Add( typeof( PlateGorget ), 52 ); - Add( typeof( PlateLegs ), 109 ); + Add(typeof(FemalePlateChest), 113); + Add(typeof(FemaleLeatherChest), 18); + Add(typeof(FemaleStuddedChest), 25); + Add(typeof(LeatherShorts), 14); + Add(typeof(LeatherSkirt), 11); + Add(typeof(LeatherBustierArms), 11); + Add(typeof(StuddedBustierArms), 27); - Add( typeof( FemalePlateChest ), 113 ); - Add( typeof( FemaleLeatherChest ), 18 ); - Add( typeof( FemaleStuddedChest ), 25 ); - Add( typeof( LeatherShorts ), 14 ); - Add( typeof( LeatherSkirt ), 11 ); - Add( typeof( LeatherBustierArms ), 11 ); - Add( typeof( StuddedBustierArms ), 27 ); + Add(typeof(Bascinet), 9); + Add(typeof(CloseHelm), 9); + Add(typeof(Helmet), 9); + Add(typeof(NorseHelm), 9); + Add(typeof(PlateHelm), 10); - Add( typeof( Bascinet ), 9 ); - Add( typeof( CloseHelm ), 9 ); - Add( typeof( Helmet ), 9 ); - Add( typeof( NorseHelm ), 9 ); - Add( typeof( PlateHelm ), 10 ); + Add(typeof(ChainCoif), 6); + Add(typeof(ChainChest), 71); + Add(typeof(ChainLegs), 74); - Add( typeof( ChainCoif ), 6 ); - Add( typeof( ChainChest ), 71 ); - Add( typeof( ChainLegs ), 74 ); + Add(typeof(RingmailArms), 42); + Add(typeof(RingmailChest), 60); + Add(typeof(RingmailGloves), 26); + Add(typeof(RingmailLegs), 45); - Add( typeof( RingmailArms ), 42 ); - Add( typeof( RingmailChest ), 60 ); - Add( typeof( RingmailGloves ), 26 ); - Add( typeof( RingmailLegs ), 45 ); + Add(typeof(BattleAxe), 13); + Add(typeof(DoubleAxe), 26); + Add(typeof(ExecutionersAxe), 15); + Add(typeof(LargeBattleAxe), 16); + Add(typeof(Pickaxe), 11); + Add(typeof(TwoHandedAxe), 16); + Add(typeof(WarAxe), 14); + Add(typeof(Axe), 20); - Add( typeof( BattleAxe ), 13 ); - Add( typeof( DoubleAxe ), 26 ); - Add( typeof( ExecutionersAxe ), 15 ); - Add( typeof( LargeBattleAxe ),16 ); - Add( typeof( Pickaxe ), 11 ); - Add( typeof( TwoHandedAxe ), 16 ); - Add( typeof( WarAxe ), 14 ); - Add( typeof( Axe ), 20 ); + Add(typeof(Bardiche), 30); + Add(typeof(Halberd), 21); - Add( typeof( Bardiche ), 30 ); - Add( typeof( Halberd ), 21 ); + Add(typeof(ButcherKnife), 7); + Add(typeof(Cleaver), 7); + Add(typeof(Dagger), 10); + Add(typeof(SkinningKnife), 7); - Add( typeof( ButcherKnife ), 7 ); - Add( typeof( Cleaver ), 7 ); - Add( typeof( Dagger ), 10 ); - Add( typeof( SkinningKnife ), 7 ); + Add(typeof(Club), 8); + Add(typeof(HammerPick), 13); + Add(typeof(Mace), 14); + Add(typeof(Maul), 10); + Add(typeof(WarHammer), 12); + Add(typeof(WarMace), 15); - Add( typeof( Club ), 8 ); - Add( typeof( HammerPick ), 13 ); - Add( typeof( Mace ), 14 ); - Add( typeof( Maul ), 10 ); - Add( typeof( WarHammer ), 12 ); - Add( typeof( WarMace ), 15 ); + Add(typeof(HeavyCrossbow), 27); + Add(typeof(Bow), 17); + Add(typeof(Crossbow), 23); - Add( typeof( HeavyCrossbow ), 27 ); - Add( typeof( Bow ), 17 ); - Add( typeof( Crossbow ), 23 ); + if (Core.AOS) + { + Add(typeof(CompositeBow), 25); + Add(typeof(RepeatingCrossbow), 28); + Add(typeof(Scepter), 20); + Add(typeof(BladedStaff), 20); + Add(typeof(Scythe), 19); + Add(typeof(BoneHarvester), 17); + Add(typeof(Scepter), 18); + Add(typeof(BladedStaff), 16); + Add(typeof(Pike), 19); + Add(typeof(DoubleBladedStaff), 17); + Add(typeof(Lance), 17); + Add(typeof(CrescentBlade), 18); + } - if ( Core.AOS ) - { - Add( typeof( CompositeBow ), 25 ); - Add( typeof( RepeatingCrossbow ), 28 ); - Add( typeof( Scepter ), 20 ); - Add( typeof( BladedStaff ), 20 ); - Add( typeof( Scythe ), 19 ); - Add( typeof( BoneHarvester ), 17 ); - Add( typeof( Scepter ), 18 ); - Add( typeof( BladedStaff ), 16 ); - Add( typeof( Pike ), 19 ); - Add( typeof( DoubleBladedStaff ), 17 ); - Add( typeof( Lance ), 17 ); - Add( typeof( CrescentBlade ), 18 ); - } + Add(typeof(Spear), 15); + Add(typeof(Pitchfork), 9); + Add(typeof(ShortSpear), 11); - Add( typeof( Spear ), 15 ); - Add( typeof( Pitchfork ), 9 ); - Add( typeof( ShortSpear ), 11 ); + Add(typeof(BlackStaff), 11); + Add(typeof(GnarledStaff), 8); + Add(typeof(QuarterStaff), 9); + Add(typeof(ShepherdsCrook), 10); - Add( typeof( BlackStaff ), 11 ); - Add( typeof( GnarledStaff ), 8 ); - Add( typeof( QuarterStaff ), 9 ); - Add( typeof( ShepherdsCrook ), 10 ); + Add(typeof(SmithHammer), 10); - Add( typeof( SmithHammer ), 10 ); - - Add( typeof( Broadsword ), 17 ); - Add( typeof( Cutlass ), 12 ); - Add( typeof( Katana ), 16 ); - Add( typeof( Kryss ), 16 ); - Add( typeof( Longsword ), 27 ); - Add( typeof( Scimitar ), 18 ); - Add( typeof( ThinLongsword ), 13 ); - Add( typeof( VikingSword ), 27 ); - - - } - } - } -} + Add(typeof(Broadsword), 17); + Add(typeof(Cutlass), 12); + Add(typeof(Katana), 16); + Add(typeof(Kryss), 16); + Add(typeof(Longsword), 27); + Add(typeof(Scimitar), 18); + Add(typeof(ThinLongsword), 13); + Add(typeof(VikingSword), 27); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBBowyer.cs b/Scripts/Mobiles/Vendors/SBInfo/SBBowyer.cs index 9b2a17806..8a25a670b 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBBowyer.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBBowyer.cs @@ -3,30 +3,26 @@ using Server.Items; namespace Server.Mobiles { - public class SBBowyer : SBInfo - { - public SBBowyer() - { - } + public class SBBowyer : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(FletcherTools), 2, 20, 0x1022, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( FletcherTools ), 2, 20, 0x1022, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( FletcherTools ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(FletcherTools), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBButcher.cs b/Scripts/Mobiles/Vendors/SBInfo/SBButcher.cs index 51eabfef1..325a9b54d 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBButcher.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBButcher.cs @@ -3,48 +3,44 @@ using Server.Items; namespace Server.Mobiles { - public class SBButcher : SBInfo - { - public SBButcher() - { - } + public class SBButcher : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bacon), 7, 20, 0x979, 0)); + Add(new GenericBuyInfo(typeof(Ham), 26, 20, 0x9C9, 0)); + Add(new GenericBuyInfo(typeof(Sausage), 18, 20, 0x9C0, 0)); + Add(new GenericBuyInfo(typeof(RawChickenLeg), 6, 20, 0x1607, 0)); + Add(new GenericBuyInfo(typeof(RawBird), 9, 20, 0x9B9, 0)); + Add(new GenericBuyInfo(typeof(RawLambLeg), 9, 20, 0x1609, 0)); + Add(new GenericBuyInfo(typeof(RawRibs), 16, 20, 0x9F1, 0)); + Add(new GenericBuyInfo(typeof(ButcherKnife), 13, 20, 0x13F6, 0)); + Add(new GenericBuyInfo(typeof(Cleaver), 13, 20, 0xEC3, 0)); + Add(new GenericBuyInfo(typeof(SkinningKnife), 13, 20, 0xEC4, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bacon ), 7, 20, 0x979, 0 ) ); - Add( new GenericBuyInfo( typeof( Ham ), 26, 20, 0x9C9, 0 ) ); - Add( new GenericBuyInfo( typeof( Sausage ), 18, 20, 0x9C0, 0 ) ); - Add( new GenericBuyInfo( typeof( RawChickenLeg ), 6, 20, 0x1607, 0 ) ); - Add( new GenericBuyInfo( typeof( RawBird ), 9, 20, 0x9B9, 0 ) ); - Add( new GenericBuyInfo( typeof( RawLambLeg ), 9, 20, 0x1609, 0 ) ); - Add( new GenericBuyInfo( typeof( RawRibs ), 16, 20, 0x9F1, 0 ) ); - Add( new GenericBuyInfo( typeof( ButcherKnife ), 13, 20, 0x13F6, 0 ) ); - Add( new GenericBuyInfo( typeof( Cleaver ), 13, 20, 0xEC3, 0 ) ); - Add( new GenericBuyInfo( typeof( SkinningKnife ), 13, 20, 0xEC4, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( RawRibs ), 8 ); - Add( typeof( RawLambLeg ), 4 ); - Add( typeof( RawChickenLeg ), 3 ); - Add( typeof( RawBird ), 4 ); - Add( typeof( Bacon ), 3 ); - Add( typeof( Sausage ), 9 ); - Add( typeof( Ham ), 13 ); - Add( typeof( ButcherKnife ), 7 ); - Add( typeof( Cleaver ), 7 ); - Add( typeof( SkinningKnife ), 7 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(RawRibs), 8); + Add(typeof(RawLambLeg), 4); + Add(typeof(RawChickenLeg), 3); + Add(typeof(RawBird), 4); + Add(typeof(Bacon), 3); + Add(typeof(Sausage), 9); + Add(typeof(Ham), 13); + Add(typeof(ButcherKnife), 7); + Add(typeof(Cleaver), 7); + Add(typeof(SkinningKnife), 7); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBCarpenter.cs b/Scripts/Mobiles/Vendors/SBInfo/SBCarpenter.cs index b65a63196..077da73e4 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBCarpenter.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBCarpenter.cs @@ -3,87 +3,83 @@ using Server.Items; namespace Server.Mobiles { - public class SBCarpenter: SBInfo - { - public SBCarpenter() - { - } + public class SBCarpenter : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Nails), 3, 20, 0x102E, 0)); + Add(new GenericBuyInfo(typeof(Axle), 2, 20, 0x105B, 0)); + Add(new GenericBuyInfo(typeof(Board), 3, 20, 0x1BD7, 0)); + Add(new GenericBuyInfo(typeof(DrawKnife), 10, 20, 0x10E4, 0)); + Add(new GenericBuyInfo(typeof(Froe), 10, 20, 0x10E5, 0)); + Add(new GenericBuyInfo(typeof(Scorp), 10, 20, 0x10E7, 0)); + Add(new GenericBuyInfo(typeof(Inshave), 10, 20, 0x10E6, 0)); + Add(new GenericBuyInfo(typeof(DovetailSaw), 12, 20, 0x1028, 0)); + Add(new GenericBuyInfo(typeof(Saw), 15, 20, 0x1034, 0)); + Add(new GenericBuyInfo(typeof(Hammer), 17, 20, 0x102A, 0)); + Add(new GenericBuyInfo(typeof(MouldingPlane), 11, 20, 0x102C, 0)); + Add(new GenericBuyInfo(typeof(SmoothingPlane), 10, 20, 0x1032, 0)); + Add(new GenericBuyInfo(typeof(JointingPlane), 11, 20, 0x1030, 0)); + Add(new GenericBuyInfo(typeof(Drums), 21, 20, 0xE9C, 0)); + Add(new GenericBuyInfo(typeof(Tambourine), 21, 20, 0xE9D, 0)); + Add(new GenericBuyInfo(typeof(LapHarp), 21, 20, 0xEB2, 0)); + Add(new GenericBuyInfo(typeof(Lute), 21, 20, 0xEB3, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Nails ), 3, 20, 0x102E, 0 ) ); - Add( new GenericBuyInfo( typeof( Axle ), 2, 20, 0x105B, 0 ) ); - Add( new GenericBuyInfo( typeof( Board ), 3, 20, 0x1BD7, 0 ) ); - Add( new GenericBuyInfo( typeof( DrawKnife ), 10, 20, 0x10E4, 0 ) ); - Add( new GenericBuyInfo( typeof( Froe ), 10, 20, 0x10E5, 0 ) ); - Add( new GenericBuyInfo( typeof( Scorp ), 10, 20, 0x10E7, 0 ) ); - Add( new GenericBuyInfo( typeof( Inshave ), 10, 20, 0x10E6, 0 ) ); - Add( new GenericBuyInfo( typeof( DovetailSaw ), 12, 20, 0x1028, 0 ) ); - Add( new GenericBuyInfo( typeof( Saw ), 15, 20, 0x1034, 0 ) ); - Add( new GenericBuyInfo( typeof( Hammer ), 17, 20, 0x102A, 0 ) ); - Add( new GenericBuyInfo( typeof( MouldingPlane ), 11, 20, 0x102C, 0 ) ); - Add( new GenericBuyInfo( typeof( SmoothingPlane ), 10, 20, 0x1032, 0 ) ); - Add( new GenericBuyInfo( typeof( JointingPlane ), 11, 20, 0x1030, 0 ) ); - Add( new GenericBuyInfo( typeof( Drums ), 21, 20, 0xE9C, 0 ) ); - Add( new GenericBuyInfo( typeof( Tambourine ), 21, 20, 0xE9D, 0 ) ); - Add( new GenericBuyInfo( typeof( LapHarp ), 21, 20, 0xEB2, 0 ) ); - Add( new GenericBuyInfo( typeof( Lute ), 21, 20, 0xEB3, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(WoodenBox), 7); + Add(typeof(SmallCrate), 5); + Add(typeof(MediumCrate), 6); + Add(typeof(LargeCrate), 7); + Add(typeof(WoodenChest), 15); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( WoodenBox ), 7 ); - Add( typeof( SmallCrate ), 5 ); - Add( typeof( MediumCrate ), 6 ); - Add( typeof( LargeCrate ), 7 ); - Add( typeof( WoodenChest ), 15 ); + Add(typeof(LargeTable), 10); + Add(typeof(Nightstand), 7); + Add(typeof(YewWoodTable), 10); - Add( typeof( LargeTable ), 10 ); - Add( typeof( Nightstand ), 7 ); - Add( typeof( YewWoodTable ), 10 ); + Add(typeof(Throne), 24); + Add(typeof(WoodenThrone), 6); + Add(typeof(Stool), 6); + Add(typeof(FootStool), 6); - Add( typeof( Throne ), 24 ); - Add( typeof( WoodenThrone ), 6 ); - Add( typeof( Stool ), 6 ); - Add( typeof( FootStool ), 6 ); + Add(typeof(FancyWoodenChairCushion), 12); + Add(typeof(WoodenChairCushion), 10); + Add(typeof(WoodenChair), 8); + Add(typeof(BambooChair), 6); + Add(typeof(WoodenBench), 6); - Add( typeof( FancyWoodenChairCushion ), 12 ); - Add( typeof( WoodenChairCushion ), 10 ); - Add( typeof( WoodenChair ), 8 ); - Add( typeof( BambooChair ), 6 ); - Add( typeof( WoodenBench ), 6 ); + Add(typeof(Saw), 9); + Add(typeof(Scorp), 6); + Add(typeof(SmoothingPlane), 6); + Add(typeof(DrawKnife), 6); + Add(typeof(Froe), 6); + Add(typeof(Hammer), 14); + Add(typeof(Inshave), 6); + Add(typeof(JointingPlane), 6); + Add(typeof(MouldingPlane), 6); + Add(typeof(DovetailSaw), 7); + Add(typeof(Board), 2); + Add(typeof(Axle), 1); - Add( typeof( Saw ), 9 ); - Add( typeof( Scorp ), 6 ); - Add( typeof( SmoothingPlane ), 6 ); - Add( typeof( DrawKnife ), 6 ); - Add( typeof( Froe ), 6 ); - Add( typeof( Hammer ), 14 ); - Add( typeof( Inshave ), 6 ); - Add( typeof( JointingPlane ), 6 ); - Add( typeof( MouldingPlane ), 6 ); - Add( typeof( DovetailSaw ), 7 ); - Add( typeof( Board ), 2 ); - Add( typeof( Axle ), 1 ); + Add(typeof(Club), 13); - Add( typeof( Club ), 13 ); + Add(typeof(Lute), 10); + Add(typeof(LapHarp), 10); + Add(typeof(Tambourine), 10); + Add(typeof(Drums), 10); - Add( typeof( Lute ), 10 ); - Add( typeof( LapHarp ), 10 ); - Add( typeof( Tambourine ), 10 ); - Add( typeof( Drums ), 10 ); - - Add( typeof( Log ), 1 ); - } - } - } -} + Add(typeof(Log), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBCobbler.cs b/Scripts/Mobiles/Vendors/SBInfo/SBCobbler.cs index 7b81dcab0..635eb3be4 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBCobbler.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBCobbler.cs @@ -3,36 +3,32 @@ using Server.Items; namespace Server.Mobiles { - public class SBCobbler : SBInfo - { - public SBCobbler() - { - } + public class SBCobbler : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(ThighBoots), 15, 20, 0x1711, Utility.RandomNeutralHue())); + Add(new GenericBuyInfo(typeof(Shoes), 8, 20, 0x170f, Utility.RandomNeutralHue())); + Add(new GenericBuyInfo(typeof(Boots), 10, 20, 0x170b, Utility.RandomNeutralHue())); + Add(new GenericBuyInfo(typeof(Sandals), 5, 20, 0x170d, Utility.RandomNeutralHue())); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( ThighBoots ), 15, 20, 0x1711, Utility.RandomNeutralHue() ) ); - Add( new GenericBuyInfo( typeof( Shoes ), 8, 20, 0x170f, Utility.RandomNeutralHue() ) ); - Add( new GenericBuyInfo( typeof( Boots ), 10, 20, 0x170b, Utility.RandomNeutralHue() ) ); - Add( new GenericBuyInfo( typeof( Sandals ), 5, 20, 0x170d, Utility.RandomNeutralHue() ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Shoes ), 4 ); - Add( typeof( Boots ), 5 ); - Add( typeof( ThighBoots ), 7 ); - Add( typeof( Sandals ), 2 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Shoes), 4); + Add(typeof(Boots), 5); + Add(typeof(ThighBoots), 7); + Add(typeof(Sandals), 2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBCook.cs b/Scripts/Mobiles/Vendors/SBInfo/SBCook.cs index 688a8154e..7687c433a 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBCook.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBCook.cs @@ -3,84 +3,79 @@ using Server.Items; namespace Server.Mobiles { - public class SBCook : SBInfo - { - public SBCook() - { - } + public class SBCook : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BreadLoaf), 5, 20, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(BreadLoaf), 5, 20, 0x103C, 0)); + Add(new GenericBuyInfo(typeof(ApplePie), 7, 20, 0x1041, 0)); //OSI just has Pie, not Apple/Fruit/Meat + Add(new GenericBuyInfo(typeof(Cake), 13, 20, 0x9E9, 0)); + Add(new GenericBuyInfo(typeof(Muffins), 3, 20, 0x9EA, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BreadLoaf ), 5, 20, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 5, 20, 0x103C, 0 ) ); - Add( new GenericBuyInfo( typeof( ApplePie ), 7, 20, 0x1041, 0 ) ); //OSI just has Pie, not Apple/Fruit/Meat - Add( new GenericBuyInfo( typeof( Cake ), 13, 20, 0x9E9, 0 ) ); - Add( new GenericBuyInfo( typeof( Muffins ), 3, 20, 0x9EA, 0 ) ); + Add(new GenericBuyInfo(typeof(CheeseWheel), 21, 10, 0x97E, 0)); + Add(new GenericBuyInfo(typeof(CookedBird), 17, 20, 0x9B7, 0)); + Add(new GenericBuyInfo(typeof(LambLeg), 8, 20, 0x160A, 0)); + Add(new GenericBuyInfo(typeof(ChickenLeg), 5, 20, 0x1608, 0)); - Add( new GenericBuyInfo( typeof( CheeseWheel ), 21, 10, 0x97E, 0 ) ); - Add( new GenericBuyInfo( typeof( CookedBird ), 17, 20, 0x9B7, 0 ) ); - Add( new GenericBuyInfo( typeof( LambLeg ), 8, 20, 0x160A, 0 ) ); - Add( new GenericBuyInfo( typeof( ChickenLeg ), 5, 20, 0x1608, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCarrots), 3, 20, 0x15F9, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCorn), 3, 20, 0x15FA, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfLettuce), 3, 20, 0x15FB, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfPeas), 3, 20, 0x15FC, 0)); + Add(new GenericBuyInfo(typeof(EmptyPewterBowl), 2, 20, 0x15FD, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfCorn), 3, 20, 0x15FE, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfLettuce), 3, 20, 0x15FF, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPeas), 3, 20, 0x1600, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPotatos), 3, 20, 0x1601, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfStew), 3, 20, 0x1604, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfTomatoSoup), 3, 20, 0x1606, 0)); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCarrots ), 3, 20, 0x15F9, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCorn ), 3, 20, 0x15FA, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfLettuce ), 3, 20, 0x15FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfPeas ), 3, 20, 0x15FC, 0 ) ); - Add( new GenericBuyInfo( typeof( EmptyPewterBowl ), 2, 20, 0x15FD, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfCorn ), 3, 20, 0x15FE, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfLettuce ), 3, 20, 0x15FF, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPeas ), 3, 20, 0x1600, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPotatos ), 3, 20, 0x1601, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfStew ), 3, 20, 0x1604, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfTomatoSoup ), 3, 20, 0x1606, 0 ) ); + Add(new GenericBuyInfo(typeof(RoastPig), 106, 20, 0x9BB, 0)); + Add(new GenericBuyInfo(typeof(SackFlour), 3, 20, 0x1039, 0)); + Add(new GenericBuyInfo(typeof(JarHoney), 3, 20, 0x9EC, 0)); + Add(new GenericBuyInfo(typeof(RollingPin), 2, 20, 0x1043, 0)); + Add(new GenericBuyInfo(typeof(FlourSifter), 2, 20, 0x103E, 0)); + Add(new GenericBuyInfo("1044567", typeof(Skillet), 3, 20, 0x97F, 0)); + } + } - Add( new GenericBuyInfo( typeof( RoastPig ), 106, 20, 0x9BB, 0 ) ); - Add( new GenericBuyInfo( typeof( SackFlour ), 3, 20, 0x1039, 0 ) ); - Add( new GenericBuyInfo( typeof( JarHoney ), 3, 20, 0x9EC, 0 ) ); - Add( new GenericBuyInfo( typeof( RollingPin ), 2, 20, 0x1043, 0 ) ); - Add( new GenericBuyInfo( typeof( FlourSifter ), 2, 20, 0x103E, 0 ) ); - Add( new GenericBuyInfo( "1044567", typeof( Skillet ), 3, 20, 0x97F, 0 ) ); + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(CheeseWheel), 12); + Add(typeof(CookedBird), 8); + Add(typeof(RoastPig), 53); + Add(typeof(Cake), 5); + Add(typeof(JarHoney), 1); + Add(typeof(SackFlour), 1); + Add(typeof(BreadLoaf), 2); + Add(typeof(ChickenLeg), 3); + Add(typeof(LambLeg), 4); + Add(typeof(Skillet), 1); + Add(typeof(FlourSifter), 1); + Add(typeof(RollingPin), 1); + Add(typeof(Muffins), 1); + Add(typeof(ApplePie), 3); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( CheeseWheel ), 12 ); - Add( typeof( CookedBird ), 8 ); - Add( typeof( RoastPig ), 53 ); - Add( typeof( Cake ), 5 ); - Add( typeof( JarHoney ), 1 ); - Add( typeof( SackFlour ), 1 ); - Add( typeof( BreadLoaf ), 2 ); - Add( typeof( ChickenLeg ), 3 ); - Add( typeof( LambLeg ), 4 ); - Add( typeof( Skillet ), 1 ); - Add( typeof( FlourSifter ), 1 ); - Add( typeof( RollingPin ), 1 ); - Add( typeof( Muffins ), 1 ); - Add( typeof( ApplePie ), 3 ); - - Add( typeof( WoodenBowlOfCarrots ), 1 ); - Add( typeof( WoodenBowlOfCorn ), 1 ); - Add( typeof( WoodenBowlOfLettuce ), 1 ); - Add( typeof( WoodenBowlOfPeas ), 1 ); - Add( typeof( EmptyPewterBowl ), 1 ); - Add( typeof( PewterBowlOfCorn ), 1 ); - Add( typeof( PewterBowlOfLettuce ), 1 ); - Add( typeof( PewterBowlOfPeas ), 1 ); - Add( typeof( PewterBowlOfPotatos ), 1 ); - Add( typeof( WoodenBowlOfStew ), 1 ); - Add( typeof( WoodenBowlOfTomatoSoup ), 1 ); - } - } - } -} + Add(typeof(WoodenBowlOfCarrots), 1); + Add(typeof(WoodenBowlOfCorn), 1); + Add(typeof(WoodenBowlOfLettuce), 1); + Add(typeof(WoodenBowlOfPeas), 1); + Add(typeof(EmptyPewterBowl), 1); + Add(typeof(PewterBowlOfCorn), 1); + Add(typeof(PewterBowlOfLettuce), 1); + Add(typeof(PewterBowlOfPeas), 1); + Add(typeof(PewterBowlOfPotatos), 1); + Add(typeof(WoodenBowlOfStew), 1); + Add(typeof(WoodenBowlOfTomatoSoup), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBFarmer.cs b/Scripts/Mobiles/Vendors/SBInfo/SBFarmer.cs index 7e4382fef..c8d901748 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBFarmer.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBFarmer.cs @@ -3,71 +3,66 @@ using Server.Items; namespace Server.Mobiles { - public class SBFarmer : SBInfo - { - public SBFarmer() - { - } + public class SBFarmer : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Cabbage), 5, 20, 0xC7B, 0)); + Add(new GenericBuyInfo(typeof(Cantaloupe), 6, 20, 0xC79, 0)); + Add(new GenericBuyInfo(typeof(Carrot), 3, 20, 0xC78, 0)); + Add(new GenericBuyInfo(typeof(HoneydewMelon), 7, 20, 0xC74, 0)); + Add(new GenericBuyInfo(typeof(Squash), 3, 20, 0xC72, 0)); + Add(new GenericBuyInfo(typeof(Lettuce), 5, 20, 0xC70, 0)); + Add(new GenericBuyInfo(typeof(Onion), 3, 20, 0xC6D, 0)); + Add(new GenericBuyInfo(typeof(Pumpkin), 11, 20, 0xC6A, 0)); + Add(new GenericBuyInfo(typeof(GreenGourd), 3, 20, 0xC66, 0)); + Add(new GenericBuyInfo(typeof(YellowGourd), 3, 20, 0xC64, 0)); + //Add( new GenericBuyInfo( typeof( Turnip ), 6, 20, XXXXXX, 0 ) ); + Add(new GenericBuyInfo(typeof(Watermelon), 7, 20, 0xC5C, 0)); + //Add( new GenericBuyInfo( typeof( EarOfCorn ), 3, 20, XXXXXX, 0 ) ); + Add(new GenericBuyInfo(typeof(Eggs), 3, 20, 0x9B5, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Milk, 7, 20, 0x9AD, 0)); + Add(new GenericBuyInfo(typeof(Peach), 3, 20, 0x9D2, 0)); + Add(new GenericBuyInfo(typeof(Pear), 3, 20, 0x994, 0)); + Add(new GenericBuyInfo(typeof(Lemon), 3, 20, 0x1728, 0)); + Add(new GenericBuyInfo(typeof(Lime), 3, 20, 0x172A, 0)); + Add(new GenericBuyInfo(typeof(Grapes), 3, 20, 0x9D1, 0)); + Add(new GenericBuyInfo(typeof(Apple), 3, 20, 0x9D0, 0)); + Add(new GenericBuyInfo(typeof(SheafOfHay), 2, 20, 0xF36, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Cabbage ), 5, 20, 0xC7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Cantaloupe ), 6, 20, 0xC79, 0 ) ); - Add( new GenericBuyInfo( typeof( Carrot ), 3, 20, 0xC78, 0 ) ); - Add( new GenericBuyInfo( typeof( HoneydewMelon ), 7, 20, 0xC74, 0 ) ); - Add( new GenericBuyInfo( typeof( Squash ), 3, 20, 0xC72, 0 ) ); - Add( new GenericBuyInfo( typeof( Lettuce ), 5, 20, 0xC70, 0 ) ); - Add( new GenericBuyInfo( typeof( Onion ), 3, 20, 0xC6D, 0 ) ); - Add( new GenericBuyInfo( typeof( Pumpkin ), 11, 20, 0xC6A, 0 ) ); - Add( new GenericBuyInfo( typeof( GreenGourd ), 3, 20, 0xC66, 0 ) ); - Add( new GenericBuyInfo( typeof( YellowGourd ), 3, 20, 0xC64, 0 ) ); - //Add( new GenericBuyInfo( typeof( Turnip ), 6, 20, XXXXXX, 0 ) ); - Add( new GenericBuyInfo( typeof( Watermelon ), 7, 20, 0xC5C, 0 ) ); - //Add( new GenericBuyInfo( typeof( EarOfCorn ), 3, 20, XXXXXX, 0 ) ); - Add( new GenericBuyInfo( typeof( Eggs ), 3, 20, 0x9B5, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Milk, 7, 20, 0x9AD, 0 ) ); - Add( new GenericBuyInfo( typeof( Peach ), 3, 20, 0x9D2, 0 ) ); - Add( new GenericBuyInfo( typeof( Pear ), 3, 20, 0x994, 0 ) ); - Add( new GenericBuyInfo( typeof( Lemon ), 3, 20, 0x1728, 0 ) ); - Add( new GenericBuyInfo( typeof( Lime ), 3, 20, 0x172A, 0 ) ); - Add( new GenericBuyInfo( typeof( Grapes ), 3, 20, 0x9D1, 0 ) ); - Add( new GenericBuyInfo( typeof( Apple ), 3, 20, 0x9D0, 0 ) ); - Add( new GenericBuyInfo( typeof( SheafOfHay ), 2, 20, 0xF36, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Pitcher ), 5 ); - Add( typeof( Eggs ), 1 ); - Add( typeof( Apple ), 1 ); - Add( typeof( Grapes ), 1 ); - Add( typeof( Watermelon ), 3 ); - Add( typeof( YellowGourd ), 1 ); - Add( typeof( GreenGourd ), 1 ); - Add( typeof( Pumpkin ), 5 ); - Add( typeof( Onion ), 1 ); - Add( typeof( Lettuce ), 2 ); - Add( typeof( Squash ), 1 ); - Add( typeof( Carrot ), 1 ); - Add( typeof( HoneydewMelon ), 3 ); - Add( typeof( Cantaloupe ), 3 ); - Add( typeof( Cabbage ), 2 ); - Add( typeof( Lemon ), 1 ); - Add( typeof( Lime ), 1 ); - Add( typeof( Peach ), 1 ); - Add( typeof( Pear ), 1 ); - Add( typeof( SheafOfHay ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Pitcher), 5); + Add(typeof(Eggs), 1); + Add(typeof(Apple), 1); + Add(typeof(Grapes), 1); + Add(typeof(Watermelon), 3); + Add(typeof(YellowGourd), 1); + Add(typeof(GreenGourd), 1); + Add(typeof(Pumpkin), 5); + Add(typeof(Onion), 1); + Add(typeof(Lettuce), 2); + Add(typeof(Squash), 1); + Add(typeof(Carrot), 1); + Add(typeof(HoneydewMelon), 3); + Add(typeof(Cantaloupe), 3); + Add(typeof(Cabbage), 2); + Add(typeof(Lemon), 1); + Add(typeof(Lime), 1); + Add(typeof(Peach), 1); + Add(typeof(Pear), 1); + Add(typeof(SheafOfHay), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBFisherman.cs b/Scripts/Mobiles/Vendors/SBInfo/SBFisherman.cs index ae47755af..43e6cc7bd 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBFisherman.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBFisherman.cs @@ -3,50 +3,48 @@ using Server.Items; namespace Server.Mobiles { - public class SBFisherman : SBInfo - { - public SBFisherman() - { - } + public class SBFisherman : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(RawFishSteak), 3, 20, 0x97A, 0)); + //TODO: Add( new GenericBuyInfo( typeof( SmallFish ), 3, 20, 0xDD6, 0 ) ); + //TODO: Add( new GenericBuyInfo( typeof( SmallFish ), 3, 20, 0xDD7, 0 ) ); + Add(new GenericBuyInfo(typeof(Fish), 6, 80, 0x9CC, 0)); + Add(new GenericBuyInfo(typeof(Fish), 6, 80, 0x9CD, 0)); + Add(new GenericBuyInfo(typeof(Fish), 6, 80, 0x9CE, 0)); + Add(new GenericBuyInfo(typeof(Fish), 6, 80, 0x9CF, 0)); + Add(new GenericBuyInfo(typeof(FishingPole), 15, 20, 0xDC0, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( RawFishSteak ), 3, 20, 0x97A, 0 ) ); - //TODO: Add( new GenericBuyInfo( typeof( SmallFish ), 3, 20, 0xDD6, 0 ) ); - //TODO: Add( new GenericBuyInfo( typeof( SmallFish ), 3, 20, 0xDD7, 0 ) ); - Add( new GenericBuyInfo( typeof( Fish ), 6, 80, 0x9CC, 0 ) ); - Add( new GenericBuyInfo( typeof( Fish ), 6, 80, 0x9CD, 0 ) ); - Add( new GenericBuyInfo( typeof( Fish ), 6, 80, 0x9CE, 0 ) ); - Add( new GenericBuyInfo( typeof( Fish ), 6, 80, 0x9CF, 0 ) ); - Add( new GenericBuyInfo( typeof( FishingPole ), 15, 20, 0xDC0, 0 ) ); + #region Mondain's Legacy - #region Mondain's Legacy - Add( new GenericBuyInfo( typeof( AquariumFishNet ), 250, 20, 0xDC8, 0x240 ) ); - Add( new GenericBuyInfo( typeof( AquariumFood ), 62, 20, 0xEFC, 0 ) ); - Add( new GenericBuyInfo( typeof( FishBowl ), 6312, 20, 0x241C, 0x482 ) ); - Add( new GenericBuyInfo( typeof( VacationWafer ), 67, 20, 0x971, 0 ) ); - Add( new GenericBuyInfo( typeof( AquariumNorthDeed ), 250002, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( typeof( AquariumEastDeed ), 250002, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( typeof( NewAquariumBook ), 15, 20, 0xFF2, 0 ) ); - #endregion - } - } + Add(new GenericBuyInfo(typeof(AquariumFishNet), 250, 20, 0xDC8, 0x240)); + Add(new GenericBuyInfo(typeof(AquariumFood), 62, 20, 0xEFC, 0)); + Add(new GenericBuyInfo(typeof(FishBowl), 6312, 20, 0x241C, 0x482)); + Add(new GenericBuyInfo(typeof(VacationWafer), 67, 20, 0x971, 0)); + Add(new GenericBuyInfo(typeof(AquariumNorthDeed), 250002, 20, 0x14F0, 0)); + Add(new GenericBuyInfo(typeof(AquariumEastDeed), 250002, 20, 0x14F0, 0)); + Add(new GenericBuyInfo(typeof(NewAquariumBook), 15, 20, 0xFF2, 0)); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( RawFishSteak ), 1 ); - Add( typeof( Fish ), 1 ); - //TODO: Add( typeof( SmallFish ), 1 ); - Add( typeof( FishingPole ), 7 ); - } - } - } -} + #endregion + } + } + + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(RawFishSteak), 1); + Add(typeof(Fish), 1); + //TODO: Add( typeof( SmallFish ), 1 ); + Add(typeof(FishingPole), 7); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBFortuneTeller.cs b/Scripts/Mobiles/Vendors/SBInfo/SBFortuneTeller.cs index cfdf3249e..69547b5d3 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBFortuneTeller.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBFortuneTeller.cs @@ -3,30 +3,26 @@ using Server.Items; namespace Server.Mobiles { - public class SBFortuneTeller : SBInfo - { - public SBFortuneTeller() - { - } + public class SBFortuneTeller : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bandage), 5, 20, 0xE21, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bandage ), 5, 20, 0xE21, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bandage ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bandage), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBFurtrader.cs b/Scripts/Mobiles/Vendors/SBInfo/SBFurtrader.cs index a78b68dbb..7ff0fb717 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBFurtrader.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBFurtrader.cs @@ -3,30 +3,26 @@ using Server.Items; namespace Server.Mobiles { - public class SBFurtrader : SBInfo - { - public SBFurtrader() - { - } + public class SBFurtrader : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Hides), 3, 40, 0x1079, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Hides ), 3, 40, 0x1079, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Hides ), 2 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Hides), 2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBGlassblower.cs b/Scripts/Mobiles/Vendors/SBInfo/SBGlassblower.cs index bde160e79..31cc4cd9b 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBGlassblower.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBGlassblower.cs @@ -3,78 +3,74 @@ using Server.Items; namespace Server.Mobiles { - public class SBGlassblower : SBInfo - { - public SBGlassblower() - { - } + public class SBGlassblower : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(RefreshPotion), 15, 10, 0xF0B, 0)); + Add(new GenericBuyInfo(typeof(AgilityPotion), 15, 10, 0xF08, 0)); + Add(new GenericBuyInfo(typeof(NightSightPotion), 15, 10, 0xF06, 0)); + Add(new GenericBuyInfo(typeof(LesserHealPotion), 15, 10, 0xF0C, 0)); + Add(new GenericBuyInfo(typeof(StrengthPotion), 15, 10, 0xF09, 0)); + Add(new GenericBuyInfo(typeof(LesserPoisonPotion), 15, 10, 0xF0A, 0)); + Add(new GenericBuyInfo(typeof(LesserCurePotion), 15, 10, 0xF07, 0)); + Add(new GenericBuyInfo(typeof(LesserExplosionPotion), 21, 10, 0xF0D, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( RefreshPotion ), 15, 10, 0xF0B, 0 ) ); - Add( new GenericBuyInfo( typeof( AgilityPotion ), 15, 10, 0xF08, 0 ) ); - Add( new GenericBuyInfo( typeof( NightSightPotion ), 15, 10, 0xF06, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserHealPotion ), 15, 10, 0xF0C, 0 ) ); - Add( new GenericBuyInfo( typeof( StrengthPotion ), 15, 10, 0xF09, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserPoisonPotion ), 15, 10, 0xF0A, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserCurePotion ), 15, 10, 0xF07, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserExplosionPotion ), 21, 10, 0xF0D, 0 ) ); + Add(new GenericBuyInfo(typeof(MortarPestle), 8, 10, 0xE9B, 0)); - Add( new GenericBuyInfo( typeof( MortarPestle ), 8, 10, 0xE9B, 0 ) ); + Add(new GenericBuyInfo(typeof(BlackPearl), 5, 20, 0xF7A, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 20, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(SulfurousAsh), 3, 20, 0xF8C, 0)); - Add( new GenericBuyInfo( typeof( BlackPearl ), 5, 20, 0xF7A, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 20, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( SulfurousAsh ), 3, 20, 0xF8C, 0 ) ); + Add(new GenericBuyInfo(typeof(Bottle), 5, 100, 0xF0E, 0)); - Add( new GenericBuyInfo( typeof( Bottle ), 5, 100, 0xF0E, 0 ) ); + Add(new GenericBuyInfo(typeof(HeatingStand), 2, 100, 0x1849, 0)); - Add( new GenericBuyInfo( typeof( HeatingStand ), 2, 100, 0x1849, 0 ) ); + Add(new GenericBuyInfo("Crafting Glass With Glassblowing", typeof(GlassblowingBook), 10637, 30, 0xFF4, 0)); + Add(new GenericBuyInfo("Finding Glass-Quality Sand", typeof(SandMiningBook), 10637, 30, 0xFF4, 0)); + Add(new GenericBuyInfo("1044608", typeof(Blowpipe), 21, 100, 0xE8A, 0x3B9)); + } + } - Add( new GenericBuyInfo( "Crafting Glass With Glassblowing", typeof( GlassblowingBook ), 10637, 30, 0xFF4, 0 ) ); - Add( new GenericBuyInfo( "Finding Glass-Quality Sand", typeof( SandMiningBook ), 10637, 30, 0xFF4, 0 ) ); - Add( new GenericBuyInfo( "1044608", typeof( Blowpipe ), 21, 100, 0xE8A, 0x3B9 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BlackPearl), 3); + Add(typeof(Bloodmoss), 3); + Add(typeof(MandrakeRoot), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Nightshade), 2); + Add(typeof(SpidersSilk), 2); + Add(typeof(SulfurousAsh), 2); + Add(typeof(Bottle), 3); + Add(typeof(MortarPestle), 4); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BlackPearl ), 3 ); - Add( typeof( Bloodmoss ), 3 ); - Add( typeof( MandrakeRoot ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( SpidersSilk ), 2 ); - Add( typeof( SulfurousAsh ), 2 ); - Add( typeof( Bottle ), 3 ); - Add( typeof( MortarPestle ), 4 ); + Add(typeof(NightSightPotion), 7); + Add(typeof(AgilityPotion), 7); + Add(typeof(StrengthPotion), 7); + Add(typeof(RefreshPotion), 7); + Add(typeof(LesserCurePotion), 7); + Add(typeof(LesserHealPotion), 7); + Add(typeof(LesserPoisonPotion), 7); + Add(typeof(LesserExplosionPotion), 10); - Add( typeof( NightSightPotion ), 7 ); - Add( typeof( AgilityPotion ), 7 ); - Add( typeof( StrengthPotion ), 7 ); - Add( typeof( RefreshPotion ), 7 ); - Add( typeof( LesserCurePotion ), 7 ); - Add( typeof( LesserHealPotion ), 7 ); - Add( typeof( LesserPoisonPotion ), 7 ); - Add( typeof( LesserExplosionPotion ), 10 ); - - Add( typeof( GlassblowingBook ), 5000 ); - Add( typeof( SandMiningBook ), 5000 ); - Add( typeof( Blowpipe ), 10 ); - } - } - } -} + Add(typeof(GlassblowingBook), 5000); + Add(typeof(SandMiningBook), 5000); + Add(typeof(Blowpipe), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBHairStylist.cs b/Scripts/Mobiles/Vendors/SBInfo/SBHairStylist.cs index 6a49582a3..6fbc2773d 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBHairStylist.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBHairStylist.cs @@ -3,34 +3,30 @@ using Server.Items; namespace Server.Mobiles { - public class SBHairStylist : SBInfo - { - public SBHairStylist() - { - } + public class SBHairStylist : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo("special beard dye", typeof(SpecialBeardDye), 500000, 20, 0xE26, 0)); + Add(new GenericBuyInfo("special hair dye", typeof(SpecialHairDye), 500000, 20, 0xE26, 0)); + Add(new GenericBuyInfo("1041060", typeof(HairDye), 60, 20, 0xEFF, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( "special beard dye", typeof( SpecialBeardDye ), 500000, 20, 0xE26, 0 ) ); - Add( new GenericBuyInfo( "special hair dye", typeof( SpecialHairDye ), 500000, 20, 0xE26, 0 ) ); - Add( new GenericBuyInfo( "1041060", typeof( HairDye ), 60, 20, 0xEFF, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( HairDye ), 30 ); - Add( typeof( SpecialBeardDye ), 250000 ); - Add( typeof( SpecialHairDye ), 250000 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(HairDye), 30); + Add(typeof(SpecialBeardDye), 250000); + Add(typeof(SpecialHairDye), 250000); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBHealer.cs b/Scripts/Mobiles/Vendors/SBInfo/SBHealer.cs index 5953533de..9da118cb2 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBHealer.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBHealer.cs @@ -3,38 +3,34 @@ using Server.Items; namespace Server.Mobiles { - public class SBHealer : SBInfo - { - public SBHealer() - { - } + public class SBHealer : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bandage), 5, 20, 0xE21, 0)); + Add(new GenericBuyInfo(typeof(LesserHealPotion), 15, 20, 0xF0C, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(RefreshPotion), 15, 20, 0xF0B, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bandage ), 5, 20, 0xE21, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserHealPotion ), 15, 20, 0xF0C, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( RefreshPotion ), 15, 20, 0xF0B, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bandage ), 1 ); - Add( typeof( LesserHealPotion ), 7 ); - Add( typeof( RefreshPotion ), 7 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bandage), 1); + Add(typeof(LesserHealPotion), 7); + Add(typeof(RefreshPotion), 7); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBHerbalist.cs b/Scripts/Mobiles/Vendors/SBInfo/SBHerbalist.cs index 4d57cb507..66284ba87 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBHerbalist.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBHerbalist.cs @@ -3,42 +3,38 @@ using Server.Items; namespace Server.Mobiles { - public class SBHerbalist : SBInfo - { - public SBHerbalist() - { - } + public class SBHerbalist : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(MortarPestle), 8, 20, 0xE9B, 0)); + Add(new GenericBuyInfo(typeof(Bottle), 5, 20, 0xF0E, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( MortarPestle ), 8, 20, 0xE9B, 0 ) ); - Add( new GenericBuyInfo( typeof( Bottle ), 5, 20, 0xF0E, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bloodmoss ), 3 ); - Add( typeof( MandrakeRoot ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( Bottle ), 3 ); - Add( typeof( MortarPestle ), 4 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bloodmoss), 3); + Add(typeof(MandrakeRoot), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Nightshade), 2); + Add(typeof(Bottle), 3); + Add(typeof(MortarPestle), 4); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBHolyMage.cs b/Scripts/Mobiles/Vendors/SBInfo/SBHolyMage.cs index 1f22d69a8..23b390eff 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBHolyMage.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBHolyMage.cs @@ -4,88 +4,84 @@ using Server.Items; namespace Server.Mobiles { - public class SBHolyMage : SBInfo - { - public SBHolyMage() - { - } + public class SBHolyMage : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Spellbook), 18, 10, 0xEFA, 0)); + Add(new GenericBuyInfo(typeof(ScribesPen), 8, 10, 0xFBF, 0)); + Add(new GenericBuyInfo(typeof(BlankScroll), 5, 20, 0x0E34, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Spellbook ), 18, 10, 0xEFA, 0 ) ); - Add( new GenericBuyInfo( typeof( ScribesPen ), 8, 10, 0xFBF, 0 ) ); - Add( new GenericBuyInfo( typeof( BlankScroll ), 5, 20, 0x0E34, 0 ) ); + Add(new GenericBuyInfo("1041072", typeof(MagicWizardsHat), 11, 10, 0x1718, Utility.RandomDyedHue())); - Add( new GenericBuyInfo( "1041072", typeof( MagicWizardsHat ), 11, 10, 0x1718, Utility.RandomDyedHue() ) ); + Add(new GenericBuyInfo(typeof(RecallRune), 15, 10, 0x1f14, 0)); - Add( new GenericBuyInfo( typeof( RecallRune ), 15, 10, 0x1f14, 0 ) ); + Add(new GenericBuyInfo(typeof(RefreshPotion), 15, 20, 0xF0B, 0)); + Add(new GenericBuyInfo(typeof(AgilityPotion), 15, 20, 0xF08, 0)); + Add(new GenericBuyInfo(typeof(NightSightPotion), 15, 20, 0xF06, 0)); + Add(new GenericBuyInfo(typeof(LesserHealPotion), 15, 20, 0xF0C, 0)); + Add(new GenericBuyInfo(typeof(StrengthPotion), 15, 20, 0xF09, 0)); + Add(new GenericBuyInfo(typeof(LesserCurePotion), 15, 20, 0xF07, 0)); - Add( new GenericBuyInfo( typeof( RefreshPotion ), 15, 20, 0xF0B, 0 ) ); - Add( new GenericBuyInfo( typeof( AgilityPotion ), 15, 20, 0xF08, 0 ) ); - Add( new GenericBuyInfo( typeof( NightSightPotion ), 15, 20, 0xF06, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserHealPotion ), 15, 20, 0xF0C, 0 ) ); - Add( new GenericBuyInfo( typeof( StrengthPotion ), 15, 20, 0xF09, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserCurePotion ), 15, 20, 0xF07, 0 ) ); + Add(new GenericBuyInfo(typeof(BlackPearl), 5, 20, 0xF7A, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 20, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(SulfurousAsh), 3, 20, 0xF8C, 0)); - Add( new GenericBuyInfo( typeof( BlackPearl ), 5, 20, 0xF7A, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 20, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( SulfurousAsh ), 3, 20, 0xF8C, 0 ) ); + Type[] types = Loot.RegularScrollTypes; - Type[] types = Loot.RegularScrollTypes; + for (int i = 0; i < types.Length && i < 8; ++i) + { + int itemID = 0x1F2E + i; - for ( int i = 0; i < types.Length && i < 8; ++i ) - { - int itemID = 0x1F2E + i; + if (i == 6) + itemID = 0x1F2D; + else if (i > 6) + --itemID; - if ( i == 6 ) - itemID = 0x1F2D; - else if ( i > 6 ) - --itemID; + Add(new GenericBuyInfo(types[i], 12 + i / 8 * 10, 20, itemID, 0)); + } + } + } - Add( new GenericBuyInfo( types[i], 12 + ((i / 8) * 10), 20, itemID, 0 ) ); - } - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BlackPearl), 3); + Add(typeof(Bloodmoss), 3); + Add(typeof(MandrakeRoot), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Nightshade), 2); + Add(typeof(SpidersSilk), 2); + Add(typeof(SulfurousAsh), 2); + Add(typeof(RecallRune), 8); + Add(typeof(Spellbook), 9); + Add(typeof(BlankScroll), 3); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BlackPearl ), 3 ); - Add( typeof( Bloodmoss ), 3 ); - Add( typeof( MandrakeRoot ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( SpidersSilk ), 2 ); - Add( typeof( SulfurousAsh ), 2 ); - Add( typeof( RecallRune ), 8 ); - Add( typeof( Spellbook ), 9 ); - Add( typeof( BlankScroll ), 3 ); + Add(typeof(NightSightPotion), 7); + Add(typeof(AgilityPotion), 7); + Add(typeof(StrengthPotion), 7); + Add(typeof(RefreshPotion), 7); + Add(typeof(LesserCurePotion), 7); + Add(typeof(LesserHealPotion), 7); - Add( typeof( NightSightPotion ), 7 ); - Add( typeof( AgilityPotion ), 7 ); - Add( typeof( StrengthPotion ), 7 ); - Add( typeof( RefreshPotion ), 7 ); - Add( typeof( LesserCurePotion ), 7 ); - Add( typeof( LesserHealPotion ), 7 ); + Type[] types = Loot.RegularScrollTypes; - Type[] types = Loot.RegularScrollTypes; - - for ( int i = 0; i < types.Length; ++i ) - Add( types[ i ], ( ( i / 8 ) + 2 ) * 2 ); - } - } - } -} + for (int i = 0; i < types.Length; ++i) + Add(types[i], (i / 8 + 2) * 2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBHouseDeed.cs b/Scripts/Mobiles/Vendors/SBInfo/SBHouseDeed.cs index a7c3eb94a..2c322aee2 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBHouseDeed.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBHouseDeed.cs @@ -3,67 +3,45 @@ using Server.Multis.Deeds; namespace Server.Mobiles { - public class SBHouseDeed: SBInfo - { - public SBHouseDeed() - { - } + public class SBHouseDeed : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo("deed to a stone-and-plaster house", typeof(StonePlasterHouseDeed), 43800, 20, 0x14F0, + 0)); + Add(new GenericBuyInfo("deed to a field stone house", typeof(FieldStoneHouseDeed), 43800, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a small brick house", typeof(SmallBrickHouseDeed), 43800, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a wooden house", typeof(WoodHouseDeed), 43800, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a wood-and-plaster house", typeof(WoodPlasterHouseDeed), 43800, 20, 0x14F0, + 0)); + Add(new GenericBuyInfo("deed to a thatched-roof cottage", typeof(ThatchedRoofCottageDeed), 43800, 20, 0x14F0, + 0)); + Add(new GenericBuyInfo("deed to a brick house", typeof(BrickHouseDeed), 144500, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a two-story wood-and-plaster house", typeof(TwoStoryWoodPlasterHouseDeed), + 192400, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a tower", typeof(TowerDeed), 433200, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a small stone keep", typeof(KeepDeed), 665200, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a castle", typeof(CastleDeed), 1022800, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a large house with patio", typeof(LargePatioDeed), 152800, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a marble house with patio", typeof(LargeMarbleDeed), 192000, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a small stone tower", typeof(SmallTowerDeed), 88500, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a two story log cabin", typeof(LogCabinDeed), 97800, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a sandstone house with patio", typeof(SandstonePatioDeed), 90900, 20, 0x14F0, + 0)); + Add(new GenericBuyInfo("deed to a two story villa", typeof(VillaDeed), 136500, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a small stone workshop", typeof(StoneWorkshopDeed), 60600, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("deed to a small marble workshop", typeof(MarbleWorkshopDeed), 63000, 20, 0x14F0, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( "deed to a stone-and-plaster house", typeof( StonePlasterHouseDeed ), 43800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a field stone house", typeof( FieldStoneHouseDeed ), 43800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a small brick house", typeof( SmallBrickHouseDeed), 43800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a wooden house", typeof( WoodHouseDeed ), 43800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a wood-and-plaster house", typeof( WoodPlasterHouseDeed ), 43800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a thatched-roof cottage", typeof( ThatchedRoofCottageDeed ), 43800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a brick house", typeof( BrickHouseDeed ), 144500, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a two-story wood-and-plaster house", typeof( TwoStoryWoodPlasterHouseDeed ), 192400, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a tower", typeof( TowerDeed ), 433200, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a small stone keep", typeof( KeepDeed ), 665200, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a castle", typeof( CastleDeed ), 1022800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a large house with patio", typeof( LargePatioDeed ), 152800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a marble house with patio", typeof( LargeMarbleDeed ), 192000, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a small stone tower", typeof( SmallTowerDeed ), 88500, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a two story log cabin", typeof( LogCabinDeed ), 97800, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a sandstone house with patio", typeof( SandstonePatioDeed ), 90900, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a two story villa", typeof( VillaDeed ), 136500, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a small stone workshop", typeof( StoneWorkshopDeed ), 60600, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "deed to a small marble workshop", typeof( MarbleWorkshopDeed ), 63000, 20, 0x14F0, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - /*Add( typeof( StonePlasterHouseDeed ), 43800 ); - Add( typeof( FieldStoneHouseDeed ), 43800 ); - Add( typeof( SmallBrickHouseDeed ), 43800 ); - Add( typeof( WoodHouseDeed ), 43800 ); - Add( typeof( WoodPlasterHouseDeed ), 43800 ); - Add( typeof( ThatchedRoofCottageDeed ), 43800 ); - Add( typeof( BrickHouseDeed ), 144500 ); - Add( typeof( TwoStoryWoodPlasterHouseDeed ), 192400 ); - Add( typeof( TowerDeed ), 433200 ); - Add( typeof( KeepDeed ), 665200 ); - Add( typeof( CastleDeed ), 1022800 ); - Add( typeof( LargePatioDeed ), 152800 ); - Add( typeof( LargeMarbleDeed ), 192800 ); - Add( typeof( SmallTowerDeed ), 88500 ); - Add( typeof( LogCabinDeed ), 97800 ); - Add( typeof( SandstonePatioDeed ), 90900 ); - Add( typeof( VillaDeed ), 136500 ); - Add( typeof( StoneWorkshopDeed ), 60600 ); - Add( typeof( MarbleWorkshopDeed ), 60300 ); - Add( typeof( SmallBrickHouseDeed ), 43800 );*/ - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBInfo.cs b/Scripts/Mobiles/Vendors/SBInfo/SBInfo.cs index 2a95d8eff..e09238467 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBInfo.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBInfo.cs @@ -2,15 +2,11 @@ using System.Collections.Generic; namespace Server.Mobiles { - public abstract class SBInfo - { - public static readonly List Empty = new List(); + public abstract class SBInfo + { + public static readonly List Empty = new List(); - public SBInfo() - { - } - - public abstract IShopSellInfo SellInfo { get; } - public abstract List BuyInfo { get; } - } -} + public abstract IShopSellInfo SellInfo{ get; } + public abstract List BuyInfo{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBInnKeeper.cs b/Scripts/Mobiles/Vendors/SBInfo/SBInnKeeper.cs index d8a76d464..eafd6d350 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBInnKeeper.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBInnKeeper.cs @@ -1,112 +1,109 @@ using System.Collections.Generic; using Server.Items; +using Server.Multis; namespace Server.Mobiles { - public class SBInnKeeper : SBInfo - { - public SBInnKeeper() - { - } + public class SBInnKeeper : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Ale, 7, 20, 0x99F, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Wine, 7, 20, 0x9C7, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Liquor, 7, 20, 0x99B, 0)); + Add(new BeverageBuyInfo(typeof(Jug), BeverageType.Cider, 13, 20, 0x9C8, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Milk, 7, 20, 0x9F0, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Ale, 11, 20, 0x1F95, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Cider, 11, 20, 0x1F97, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Liquor, 11, 20, 0x1F99, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Wine, 11, 20, 0x1F9B, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Water, 11, 20, 0x1F9D, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Ale, 7, 20, 0x99F, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Wine, 7, 20, 0x9C7, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Liquor, 7, 20, 0x99B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Jug ), BeverageType.Cider, 13, 20, 0x9C8, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Milk, 7, 20, 0x9F0, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Ale, 11, 20, 0x1F95, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Cider, 11, 20, 0x1F97, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Liquor, 11, 20, 0x1F99, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Wine, 11, 20, 0x1F9B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Water, 11, 20, 0x1F9D, 0 ) ); + Add(new GenericBuyInfo(typeof(BreadLoaf), 6, 10, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(CheeseWheel), 21, 10, 0x97E, 0)); + Add(new GenericBuyInfo(typeof(CookedBird), 17, 20, 0x9B7, 0)); + Add(new GenericBuyInfo(typeof(LambLeg), 8, 20, 0x160A, 0)); + Add(new GenericBuyInfo(typeof(ChickenLeg), 5, 20, 0x1608, 0)); + Add(new GenericBuyInfo(typeof(Ribs), 7, 20, 0x9F2, 0)); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 6, 10, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( CheeseWheel ), 21, 10, 0x97E, 0 ) ); - Add( new GenericBuyInfo( typeof( CookedBird ), 17, 20, 0x9B7, 0 ) ); - Add( new GenericBuyInfo( typeof( LambLeg ), 8, 20, 0x160A, 0 ) ); - Add( new GenericBuyInfo( typeof( ChickenLeg ), 5, 20, 0x1608, 0 ) ); - Add( new GenericBuyInfo( typeof( Ribs ), 7, 20, 0x9F2, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCarrots), 3, 20, 0x15F9, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCorn), 3, 20, 0x15FA, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfLettuce), 3, 20, 0x15FB, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfPeas), 3, 20, 0x15FC, 0)); + Add(new GenericBuyInfo(typeof(EmptyPewterBowl), 2, 20, 0x15FD, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfCorn), 3, 20, 0x15FE, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfLettuce), 3, 20, 0x15FF, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPeas), 3, 20, 0x1600, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPotatos), 3, 20, 0x1601, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfStew), 3, 20, 0x1604, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfTomatoSoup), 3, 20, 0x1606, 0)); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCarrots ), 3, 20, 0x15F9, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCorn ), 3, 20, 0x15FA, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfLettuce ), 3, 20, 0x15FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfPeas ), 3, 20, 0x15FC, 0 ) ); - Add( new GenericBuyInfo( typeof( EmptyPewterBowl ), 2, 20, 0x15FD, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfCorn ), 3, 20, 0x15FE, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfLettuce ), 3, 20, 0x15FF, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPeas ), 3, 20, 0x1600, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPotatos ), 3, 20, 0x1601, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfStew ), 3, 20, 0x1604, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfTomatoSoup ), 3, 20, 0x1606, 0 ) ); + Add(new GenericBuyInfo(typeof(ApplePie), 7, 20, 0x1041, 0)); //OSI just has Pie, not Apple/Fruit/Meat - Add( new GenericBuyInfo( typeof( ApplePie ), 7, 20, 0x1041, 0 ) ); //OSI just has Pie, not Apple/Fruit/Meat + Add(new GenericBuyInfo(typeof(Peach), 3, 20, 0x9D2, 0)); + Add(new GenericBuyInfo(typeof(Pear), 3, 20, 0x994, 0)); + Add(new GenericBuyInfo(typeof(Grapes), 3, 20, 0x9D1, 0)); + Add(new GenericBuyInfo(typeof(Apple), 3, 20, 0x9D0, 0)); + Add(new GenericBuyInfo(typeof(Banana), 2, 20, 0x171F, 0)); + Add(new GenericBuyInfo(typeof(Torch), 7, 20, 0xF6B, 0)); + Add(new GenericBuyInfo(typeof(Candle), 6, 20, 0xA28, 0)); + Add(new GenericBuyInfo(typeof(Beeswax), 1, 20, 0x1422, 0)); - Add( new GenericBuyInfo( typeof( Peach ), 3, 20, 0x9D2, 0 ) ); - Add( new GenericBuyInfo( typeof( Pear ), 3, 20, 0x994, 0 ) ); - Add( new GenericBuyInfo( typeof( Grapes ), 3, 20, 0x9D1, 0 ) ); - Add( new GenericBuyInfo( typeof( Apple ), 3, 20, 0x9D0, 0 ) ); - Add( new GenericBuyInfo( typeof( Banana ), 2, 20, 0x171F, 0 ) ); - Add( new GenericBuyInfo( typeof( Torch ), 7, 20, 0xF6B, 0 ) ); - Add( new GenericBuyInfo( typeof( Candle ), 6, 20, 0xA28, 0 ) ); - Add( new GenericBuyInfo( typeof( Beeswax ), 1, 20, 0x1422, 0 ) ); + Add(new GenericBuyInfo(typeof(Backpack), 15, 20, 0x9B2, 0)); + Add(new GenericBuyInfo("1016450", typeof(Chessboard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo("1016449", typeof(CheckerBoard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo(typeof(Backgammon), 2, 20, 0xE1C, 0)); + Add(new GenericBuyInfo(typeof(Dices), 2, 20, 0xFA7, 0)); + Add(new GenericBuyInfo("1041243", typeof(ContractOfEmployment), 1252, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("a barkeep contract", typeof(BarkeepContract), 1252, 20, 0x14F0, 0)); - Add( new GenericBuyInfo( typeof( Backpack ), 15, 20, 0x9B2, 0 ) ); - Add( new GenericBuyInfo( "1016450", typeof( Chessboard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( "1016449", typeof( CheckerBoard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( typeof( Backgammon ), 2, 20, 0xE1C, 0 ) ); - Add( new GenericBuyInfo( typeof( Dices ), 2, 20, 0xFA7, 0 ) ); - Add( new GenericBuyInfo( "1041243", typeof( ContractOfEmployment ), 1252, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "a barkeep contract", typeof( BarkeepContract ), 1252, 20, 0x14F0, 0 ) ); + if (BaseHouse.NewVendorSystem) + Add(new GenericBuyInfo("1062332", typeof(VendorRentalContract), 1252, 20, 0x14F0, 0x672)); + } + } - if ( Multis.BaseHouse.NewVendorSystem ) - Add( new GenericBuyInfo( "1062332", typeof( VendorRentalContract ), 1252, 20, 0x14F0, 0x672 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BeverageBottle ), 3 ); - Add( typeof( Jug ), 6 ); - Add( typeof( Pitcher ), 5 ); - Add( typeof( GlassMug ), 1 ); - Add( typeof( BreadLoaf ), 3 ); - Add( typeof( CheeseWheel ), 12 ); - Add( typeof( Ribs ), 6 ); - Add( typeof( Peach ), 1 ); - Add( typeof( Pear ), 1 ); - Add( typeof( Grapes ), 1 ); - Add( typeof( Apple ), 1 ); - Add( typeof( Banana ), 1 ); - Add( typeof( Torch ), 3 ); - Add( typeof( Candle ), 3 ); - Add( typeof( Chessboard ), 1 ); - Add( typeof( CheckerBoard ), 1 ); - Add( typeof( Backgammon ), 1 ); - Add( typeof( Dices ), 1 ); - Add( typeof( ContractOfEmployment ), 626 ); - Add( typeof( Beeswax ), 1 ); - Add( typeof( WoodenBowlOfCarrots ), 1 ); - Add( typeof( WoodenBowlOfCorn ), 1 ); - Add( typeof( WoodenBowlOfLettuce ), 1 ); - Add( typeof( WoodenBowlOfPeas ), 1 ); - Add( typeof( EmptyPewterBowl ), 1 ); - Add( typeof( PewterBowlOfCorn ), 1 ); - Add( typeof( PewterBowlOfLettuce ), 1 ); - Add( typeof( PewterBowlOfPeas ), 1 ); - Add( typeof( PewterBowlOfPotatos ), 1 ); - Add( typeof( WoodenBowlOfStew ), 1 ); - Add( typeof( WoodenBowlOfTomatoSoup ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BeverageBottle), 3); + Add(typeof(Jug), 6); + Add(typeof(Pitcher), 5); + Add(typeof(GlassMug), 1); + Add(typeof(BreadLoaf), 3); + Add(typeof(CheeseWheel), 12); + Add(typeof(Ribs), 6); + Add(typeof(Peach), 1); + Add(typeof(Pear), 1); + Add(typeof(Grapes), 1); + Add(typeof(Apple), 1); + Add(typeof(Banana), 1); + Add(typeof(Torch), 3); + Add(typeof(Candle), 3); + Add(typeof(Chessboard), 1); + Add(typeof(CheckerBoard), 1); + Add(typeof(Backgammon), 1); + Add(typeof(Dices), 1); + Add(typeof(ContractOfEmployment), 626); + Add(typeof(Beeswax), 1); + Add(typeof(WoodenBowlOfCarrots), 1); + Add(typeof(WoodenBowlOfCorn), 1); + Add(typeof(WoodenBowlOfLettuce), 1); + Add(typeof(WoodenBowlOfPeas), 1); + Add(typeof(EmptyPewterBowl), 1); + Add(typeof(PewterBowlOfCorn), 1); + Add(typeof(PewterBowlOfLettuce), 1); + Add(typeof(PewterBowlOfPeas), 1); + Add(typeof(PewterBowlOfPotatos), 1); + Add(typeof(WoodenBowlOfStew), 1); + Add(typeof(WoodenBowlOfTomatoSoup), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBJewel.cs b/Scripts/Mobiles/Vendors/SBInfo/SBJewel.cs index 4176e87b5..0fc73eb36 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBJewel.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBJewel.cs @@ -3,73 +3,71 @@ using Server.Items; namespace Server.Mobiles { - public class SBJewel: SBInfo - { - public SBJewel() - { - } + public class SBJewel : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(GoldRing), 27, 20, 0x108A, 0)); + Add(new GenericBuyInfo(typeof(Necklace), 26, 20, 0x1085, 0)); + Add(new GenericBuyInfo(typeof(GoldNecklace), 27, 20, 0x1088, 0)); + Add(new GenericBuyInfo(typeof(GoldBeadNecklace), 27, 20, 0x1089, 0)); + Add(new GenericBuyInfo(typeof(Beads), 27, 20, 0x108B, 0)); + Add(new GenericBuyInfo(typeof(GoldBracelet), 27, 20, 0x1086, 0)); + Add(new GenericBuyInfo(typeof(GoldEarrings), 27, 20, 0x1087, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( GoldRing ), 27, 20, 0x108A, 0 ) ); - Add( new GenericBuyInfo( typeof( Necklace ), 26, 20, 0x1085, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldNecklace ), 27, 20, 0x1088, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldBeadNecklace ), 27, 20, 0x1089, 0 ) ); - Add( new GenericBuyInfo( typeof( Beads ), 27, 20, 0x108B, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldBracelet ), 27, 20, 0x1086, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldEarrings ), 27, 20, 0x1087, 0 ) ); + Add(new GenericBuyInfo("1060740", typeof(BroadcastCrystal), 68, 20, 0x1ED0, 0, + new object[] { 500 })); // 500 charges + Add(new GenericBuyInfo("1060740", typeof(BroadcastCrystal), 131, 20, 0x1ED0, 0, + new object[] { 1000 })); // 1000 charges + Add(new GenericBuyInfo("1060740", typeof(BroadcastCrystal), 256, 20, 0x1ED0, 0, + new object[] { 2000 })); // 2000 charges - Add( new GenericBuyInfo( "1060740", typeof( BroadcastCrystal ), 68, 20, 0x1ED0, 0, new object[] { 500 } ) ); // 500 charges - Add( new GenericBuyInfo( "1060740", typeof( BroadcastCrystal ), 131, 20, 0x1ED0, 0, new object[] { 1000 } ) ); // 1000 charges - Add( new GenericBuyInfo( "1060740", typeof( BroadcastCrystal ), 256, 20, 0x1ED0, 0, new object[] { 2000 } ) ); // 2000 charges + Add(new GenericBuyInfo("1060740", typeof(ReceiverCrystal), 6, 20, 0x1ED0, 0)); - Add( new GenericBuyInfo( "1060740", typeof( ReceiverCrystal ), 6, 20, 0x1ED0, 0 ) ); + Add(new GenericBuyInfo(typeof(StarSapphire), 125, 20, 0xF21, 0)); + Add(new GenericBuyInfo(typeof(Emerald), 100, 20, 0xF10, 0)); + Add(new GenericBuyInfo(typeof(Sapphire), 100, 20, 0xF19, 0)); + Add(new GenericBuyInfo(typeof(Ruby), 75, 20, 0xF13, 0)); + Add(new GenericBuyInfo(typeof(Citrine), 50, 20, 0xF15, 0)); + Add(new GenericBuyInfo(typeof(Amethyst), 100, 20, 0xF16, 0)); + Add(new GenericBuyInfo(typeof(Tourmaline), 75, 20, 0xF2D, 0)); + Add(new GenericBuyInfo(typeof(Amber), 50, 20, 0xF25, 0)); + Add(new GenericBuyInfo(typeof(Diamond), 200, 20, 0xF26, 0)); + } + } - Add( new GenericBuyInfo( typeof( StarSapphire ), 125, 20, 0xF21, 0 ) ); - Add( new GenericBuyInfo( typeof( Emerald ), 100, 20, 0xF10, 0 ) ); - Add( new GenericBuyInfo( typeof( Sapphire ), 100, 20, 0xF19, 0 ) ); - Add( new GenericBuyInfo( typeof( Ruby ), 75, 20, 0xF13, 0 ) ); - Add( new GenericBuyInfo( typeof( Citrine ), 50, 20, 0xF15, 0 ) ); - Add( new GenericBuyInfo( typeof( Amethyst ), 100, 20, 0xF16, 0 ) ); - Add( new GenericBuyInfo( typeof( Tourmaline ), 75, 20, 0xF2D, 0 ) ); - Add( new GenericBuyInfo( typeof( Amber ), 50, 20, 0xF25, 0 ) ); - Add( new GenericBuyInfo( typeof( Diamond ), 200, 20, 0xF26, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Amber ), 25 ); - Add( typeof( Amethyst ), 50 ); - Add( typeof( Citrine ), 25 ); - Add( typeof( Diamond ), 100 ); - Add( typeof( Emerald ), 50 ); - Add( typeof( Ruby ), 37 ); - Add( typeof( Sapphire ), 50 ); - Add( typeof( StarSapphire ), 62 ); - Add( typeof( Tourmaline ), 47 ); - Add( typeof( GoldRing ), 13 ); - Add( typeof( SilverRing ), 10 ); - Add( typeof( Necklace ), 13 ); - Add( typeof( GoldNecklace ), 13 ); - Add( typeof( GoldBeadNecklace ), 13 ); - Add( typeof( SilverNecklace ), 10 ); - Add( typeof( SilverBeadNecklace ), 10 ); - Add( typeof( Beads ), 13 ); - Add( typeof( GoldBracelet ), 13 ); - Add( typeof( SilverBracelet ), 10 ); - Add( typeof( GoldEarrings ), 13 ); - Add( typeof( SilverEarrings ), 10 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Amber), 25); + Add(typeof(Amethyst), 50); + Add(typeof(Citrine), 25); + Add(typeof(Diamond), 100); + Add(typeof(Emerald), 50); + Add(typeof(Ruby), 37); + Add(typeof(Sapphire), 50); + Add(typeof(StarSapphire), 62); + Add(typeof(Tourmaline), 47); + Add(typeof(GoldRing), 13); + Add(typeof(SilverRing), 10); + Add(typeof(Necklace), 13); + Add(typeof(GoldNecklace), 13); + Add(typeof(GoldBeadNecklace), 13); + Add(typeof(SilverNecklace), 10); + Add(typeof(SilverBeadNecklace), 10); + Add(typeof(Beads), 13); + Add(typeof(GoldBracelet), 13); + Add(typeof(SilverBracelet), 10); + Add(typeof(GoldEarrings), 13); + Add(typeof(SilverEarrings), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBKeeperOfChivalry.cs b/Scripts/Mobiles/Vendors/SBInfo/SBKeeperOfChivalry.cs index 2c77c416a..c902fc9d5 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBKeeperOfChivalry.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBKeeperOfChivalry.cs @@ -3,29 +3,22 @@ using Server.Items; namespace Server.Mobiles { - public class SBKeeperOfChivalry : SBInfo - { - public SBKeeperOfChivalry() - { - } + public class SBKeeperOfChivalry : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BookOfChivalry), 140, 20, 0x2252, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BookOfChivalry ), 140, 20, 0x2252, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBLeatherWorker.cs b/Scripts/Mobiles/Vendors/SBInfo/SBLeatherWorker.cs index a58ec85b9..5807b0b67 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBLeatherWorker.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBLeatherWorker.cs @@ -3,32 +3,28 @@ using Server.Items; namespace Server.Mobiles { - public class SBLeatherWorker: SBInfo - { - public SBLeatherWorker() - { - } + public class SBLeatherWorker : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Hides), 4, 999, 0x1078, 0)); + Add(new GenericBuyInfo(typeof(ThighBoots), 56, 10, 0x1711, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Hides ), 4, 999, 0x1078, 0 ) ); - Add( new GenericBuyInfo( typeof( ThighBoots ), 56, 10, 0x1711, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Hides ), 2 ); - Add( typeof( ThighBoots ), 28 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Hides), 2); + Add(typeof(ThighBoots), 28); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBMage.cs b/Scripts/Mobiles/Vendors/SBInfo/SBMage.cs index 17f8e25e6..defa29c22 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBMage.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBMage.cs @@ -4,130 +4,126 @@ using Server.Items; namespace Server.Mobiles { - public class SBMage : SBInfo - { - public SBMage() - { - } + public class SBMage : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Spellbook), 18, 10, 0xEFA, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Spellbook ), 18, 10, 0xEFA, 0 ) ); + if (Core.AOS) + Add(new GenericBuyInfo(typeof(NecromancerSpellbook), 115, 10, 0x2253, 0)); - if ( Core.AOS ) - Add( new GenericBuyInfo( typeof( NecromancerSpellbook ), 115, 10, 0x2253, 0 ) ); + Add(new GenericBuyInfo(typeof(ScribesPen), 8, 10, 0xFBF, 0)); - Add( new GenericBuyInfo( typeof( ScribesPen ), 8, 10, 0xFBF, 0 ) ); + Add(new GenericBuyInfo(typeof(BlankScroll), 5, 20, 0x0E34, 0)); - Add( new GenericBuyInfo( typeof( BlankScroll ), 5, 20, 0x0E34, 0 ) ); + Add(new GenericBuyInfo("1041072", typeof(MagicWizardsHat), 11, 10, 0x1718, Utility.RandomDyedHue())); - Add( new GenericBuyInfo( "1041072", typeof( MagicWizardsHat ), 11, 10, 0x1718, Utility.RandomDyedHue() ) ); + Add(new GenericBuyInfo(typeof(RecallRune), 15, 10, 0x1F14, 0)); - Add( new GenericBuyInfo( typeof( RecallRune ), 15, 10, 0x1F14, 0 ) ); + Add(new GenericBuyInfo(typeof(RefreshPotion), 15, 10, 0xF0B, 0)); + Add(new GenericBuyInfo(typeof(AgilityPotion), 15, 10, 0xF08, 0)); + Add(new GenericBuyInfo(typeof(NightSightPotion), 15, 10, 0xF06, 0)); + Add(new GenericBuyInfo(typeof(LesserHealPotion), 15, 10, 0xF0C, 0)); + Add(new GenericBuyInfo(typeof(StrengthPotion), 15, 10, 0xF09, 0)); + Add(new GenericBuyInfo(typeof(LesserPoisonPotion), 15, 10, 0xF0A, 0)); + Add(new GenericBuyInfo(typeof(LesserCurePotion), 15, 10, 0xF07, 0)); + Add(new GenericBuyInfo(typeof(LesserExplosionPotion), 21, 10, 0xF0D, 0)); - Add( new GenericBuyInfo( typeof( RefreshPotion ), 15, 10, 0xF0B, 0 ) ); - Add( new GenericBuyInfo( typeof( AgilityPotion ), 15, 10, 0xF08, 0 ) ); - Add( new GenericBuyInfo( typeof( NightSightPotion ), 15, 10, 0xF06, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserHealPotion ), 15, 10, 0xF0C, 0 ) ); - Add( new GenericBuyInfo( typeof( StrengthPotion ), 15, 10, 0xF09, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserPoisonPotion ), 15, 10, 0xF0A, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserCurePotion ), 15, 10, 0xF07, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserExplosionPotion ), 21, 10, 0xF0D, 0 ) ); + Add(new GenericBuyInfo(typeof(BlackPearl), 5, 20, 0xF7A, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 20, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 20, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 20, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 20, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(SulfurousAsh), 3, 20, 0xF8C, 0)); - Add( new GenericBuyInfo( typeof( BlackPearl ), 5, 20, 0xF7A, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 20, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 20, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 20, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 20, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( SulfurousAsh ), 3, 20, 0xF8C, 0 ) ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(BatWing), 3, 999, 0xF78, 0)); + Add(new GenericBuyInfo(typeof(DaemonBlood), 6, 999, 0xF7D, 0)); + Add(new GenericBuyInfo(typeof(PigIron), 5, 999, 0xF8A, 0)); + Add(new GenericBuyInfo(typeof(NoxCrystal), 6, 999, 0xF8E, 0)); + Add(new GenericBuyInfo(typeof(GraveDust), 3, 999, 0xF8F, 0)); + } - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( BatWing ), 3, 999, 0xF78, 0 ) ); - Add( new GenericBuyInfo( typeof( DaemonBlood ), 6, 999, 0xF7D, 0 ) ); - Add( new GenericBuyInfo( typeof( PigIron ), 5, 999, 0xF8A, 0 ) ); - Add( new GenericBuyInfo( typeof( NoxCrystal ), 6, 999, 0xF8E, 0 ) ); - Add( new GenericBuyInfo( typeof( GraveDust ), 3, 999, 0xF8F, 0 ) ); - } + Type[] types = Loot.RegularScrollTypes; - Type[] types = Loot.RegularScrollTypes; + int circles = 3; - int circles = 3; + for (int i = 0; i < circles * 8 && i < types.Length; ++i) + { + int itemID = 0x1F2E + i; - for ( int i = 0; i < circles*8 && i < types.Length; ++i ) - { - int itemID = 0x1F2E + i; + if (i == 6) + itemID = 0x1F2D; + else if (i > 6) + --itemID; - if ( i == 6 ) - itemID = 0x1F2D; - else if ( i > 6 ) - --itemID; + Add(new GenericBuyInfo(types[i], 12 + i / 8 * 10, 20, itemID, 0)); + } + } + } - Add( new GenericBuyInfo( types[i], 12 + ((i / 8) * 10), 20, itemID, 0 ) ); - } - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(WizardsHat), 15); + Add(typeof(BlackPearl), 3); + Add(typeof(Bloodmoss), 4); + Add(typeof(MandrakeRoot), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Nightshade), 2); + Add(typeof(SpidersSilk), 2); + Add(typeof(SulfurousAsh), 2); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( WizardsHat ), 15 ); - Add( typeof( BlackPearl ), 3 ); - Add( typeof( Bloodmoss ),4 ); - Add( typeof( MandrakeRoot ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( SpidersSilk ), 2 ); - Add( typeof( SulfurousAsh ), 2 ); + if (Core.AOS) + { + Add(typeof(BatWing), 1); + Add(typeof(DaemonBlood), 3); + Add(typeof(PigIron), 2); + Add(typeof(NoxCrystal), 3); + Add(typeof(GraveDust), 1); + } - if ( Core.AOS ) - { - Add( typeof( BatWing ), 1 ); - Add( typeof( DaemonBlood ), 3 ); - Add( typeof( PigIron ), 2 ); - Add( typeof( NoxCrystal ), 3 ); - Add( typeof( GraveDust ), 1 ); - } + Add(typeof(RecallRune), 13); + Add(typeof(Spellbook), 25); - Add( typeof( RecallRune ), 13 ); - Add( typeof( Spellbook ), 25 ); + Type[] types = Loot.RegularScrollTypes; - Type[] types = Loot.RegularScrollTypes; + for (int i = 0; i < types.Length; ++i) + Add(types[i], (i / 8 + 2) * 2); - for ( int i = 0; i < types.Length; ++i ) - Add( types[i], ((i / 8) + 2) * 2 ); - - if ( Core.SE ) - { - Add( typeof( ExorcismScroll ), 3 ); - Add( typeof( AnimateDeadScroll ), 8 ); - Add( typeof( BloodOathScroll ), 8 ); - Add( typeof( CorpseSkinScroll ), 8 ); - Add( typeof( CurseWeaponScroll ), 8 ); - Add( typeof( EvilOmenScroll ), 8 ); - Add( typeof( PainSpikeScroll ), 8 ); - Add( typeof( SummonFamiliarScroll ), 8 ); - Add( typeof( HorrificBeastScroll ), 8 ); - Add( typeof( MindRotScroll ), 10 ); - Add( typeof( PoisonStrikeScroll ), 10 ); - Add( typeof( WraithFormScroll ), 15 ); - Add( typeof( LichFormScroll ), 16 ); - Add( typeof( StrangleScroll ), 16 ); - Add( typeof( WitherScroll ), 16 ); - Add( typeof( VampiricEmbraceScroll ), 20 ); - Add( typeof( VengefulSpiritScroll ), 20 ); - } - } - } - } -} + if (Core.SE) + { + Add(typeof(ExorcismScroll), 3); + Add(typeof(AnimateDeadScroll), 8); + Add(typeof(BloodOathScroll), 8); + Add(typeof(CorpseSkinScroll), 8); + Add(typeof(CurseWeaponScroll), 8); + Add(typeof(EvilOmenScroll), 8); + Add(typeof(PainSpikeScroll), 8); + Add(typeof(SummonFamiliarScroll), 8); + Add(typeof(HorrificBeastScroll), 8); + Add(typeof(MindRotScroll), 10); + Add(typeof(PoisonStrikeScroll), 10); + Add(typeof(WraithFormScroll), 15); + Add(typeof(LichFormScroll), 16); + Add(typeof(StrangleScroll), 16); + Add(typeof(WitherScroll), 16); + Add(typeof(VampiricEmbraceScroll), 20); + Add(typeof(VengefulSpiritScroll), 20); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBMapmaker.cs b/Scripts/Mobiles/Vendors/SBInfo/SBMapmaker.cs index 73d9db4d7..aa31be373 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBMapmaker.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBMapmaker.cs @@ -3,42 +3,38 @@ using Server.Items; namespace Server.Mobiles { - public class SBMapmaker : SBInfo - { - public SBMapmaker() - { - } + public class SBMapmaker : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BlankMap), 5, 40, 0x14EC, 0)); + Add(new GenericBuyInfo(typeof(MapmakersPen), 8, 20, 0x0FBF, 0)); + Add(new GenericBuyInfo(typeof(BlankScroll), 12, 40, 0xEF3, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BlankMap ), 5, 40, 0x14EC, 0 ) ); - Add( new GenericBuyInfo( typeof( MapmakersPen ), 8, 20, 0x0FBF, 0 ) ); - Add( new GenericBuyInfo( typeof( BlankScroll ), 12, 40, 0xEF3, 0 ) ); + for (int i = 0; i < PresetMapEntry.Table.Length; ++i) + Add(new PresetMapBuyInfo(PresetMapEntry.Table[i], Utility.RandomMinMax(7, 10), 20)); + } + } - for ( int i = 0; i < PresetMapEntry.Table.Length; ++i ) - Add( new PresetMapBuyInfo( PresetMapEntry.Table[i], Utility.RandomMinMax( 7, 10 ), 20 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BlankScroll ), 6 ); - Add( typeof( MapmakersPen ), 4 ); - Add( typeof( BlankMap ), 2 ); - Add( typeof( CityMap ), 3 ); - Add( typeof( LocalMap ), 3 ); - Add( typeof( WorldMap ), 3 ); - Add( typeof( PresetMapEntry ), 3 ); - //TODO: Buy back maps that the mapmaker sells!!! - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BlankScroll), 6); + Add(typeof(MapmakersPen), 4); + Add(typeof(BlankMap), 2); + Add(typeof(CityMap), 3); + Add(typeof(LocalMap), 3); + Add(typeof(WorldMap), 3); + Add(typeof(PresetMapEntry), 3); + //TODO: Buy back maps that the mapmaker sells!!! + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBMiller.cs b/Scripts/Mobiles/Vendors/SBInfo/SBMiller.cs index 46b02fe77..c3005d563 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBMiller.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBMiller.cs @@ -3,32 +3,28 @@ using Server.Items; namespace Server.Mobiles { - public class SBMiller : SBInfo - { - public SBMiller() - { - } + public class SBMiller : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(SackFlour), 3, 20, 0x1039, 0)); + Add(new GenericBuyInfo(typeof(SheafOfHay), 2, 20, 0xF36, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( SackFlour ), 3, 20, 0x1039, 0 ) ); - Add( new GenericBuyInfo( typeof( SheafOfHay ), 2, 20, 0xF36, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( SackFlour ), 1 ); - Add( typeof( SheafOfHay ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(SackFlour), 1); + Add(typeof(SheafOfHay), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBMiner.cs b/Scripts/Mobiles/Vendors/SBInfo/SBMiner.cs index 7e01d9c86..111056f41 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBMiner.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBMiner.cs @@ -3,42 +3,38 @@ using Server.Items; namespace Server.Mobiles { - public class SBMiner: SBInfo - { - public SBMiner() - { - } + public class SBMiner : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bag), 6, 20, 0xE76, 0)); + Add(new GenericBuyInfo(typeof(Candle), 6, 10, 0xA28, 0)); + Add(new GenericBuyInfo(typeof(Torch), 8, 10, 0xF6B, 0)); + Add(new GenericBuyInfo(typeof(Lantern), 2, 10, 0xA25, 0)); + //Add( new GenericBuyInfo( typeof( OilFlask ), 8, 10, 0x####, 0 ) ); + Add(new GenericBuyInfo(typeof(Pickaxe), 25, 10, 0xE86, 0)); + Add(new GenericBuyInfo(typeof(Shovel), 12, 10, 0xF39, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bag ), 6, 20, 0xE76, 0 ) ); - Add( new GenericBuyInfo( typeof( Candle ), 6, 10, 0xA28, 0 ) ); - Add( new GenericBuyInfo( typeof( Torch ), 8, 10, 0xF6B, 0 ) ); - Add( new GenericBuyInfo( typeof( Lantern ), 2, 10, 0xA25, 0 ) ); - //Add( new GenericBuyInfo( typeof( OilFlask ), 8, 10, 0x####, 0 ) ); - Add( new GenericBuyInfo( typeof( Pickaxe ), 25, 10, 0xE86, 0 ) ); - Add( new GenericBuyInfo( typeof( Shovel ), 12, 10, 0xF39, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Pickaxe ), 12 ); - Add( typeof( Shovel ), 6 ); - Add( typeof( Lantern ), 1 ); - //Add( typeof( OilFlask ), 4 ); - Add( typeof( Torch ), 3 ); - Add( typeof( Bag ), 3 ); - Add( typeof( Candle ), 3 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Pickaxe), 12); + Add(typeof(Shovel), 6); + Add(typeof(Lantern), 1); + //Add( typeof( OilFlask ), 4 ); + Add(typeof(Torch), 3); + Add(typeof(Bag), 3); + Add(typeof(Candle), 3); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBMonk.cs b/Scripts/Mobiles/Vendors/SBInfo/SBMonk.cs index 06aaf76e9..f3e252b25 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBMonk.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBMonk.cs @@ -3,29 +3,22 @@ using Server.Items; namespace Server.Mobiles { - public class SBMonk : SBInfo - { - public SBMonk() - { - } + public class SBMonk : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + if (Core.AOS) Add(new GenericBuyInfo(typeof(MonkRobe), 136, 20, 0x2687, 0x21E)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - if ( Core.AOS ) Add( new GenericBuyInfo( typeof( MonkRobe ), 136, 20, 0x2687, 0x21E ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBNinja.cs b/Scripts/Mobiles/Vendors/SBInfo/SBNinja.cs index 229befd9f..507b4a6b2 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBNinja.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBNinja.cs @@ -3,29 +3,22 @@ using Server.Items; namespace Server.Mobiles { - public class SBNinja : SBInfo - { - public SBNinja() - { - } + public class SBNinja : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BookOfNinjitsu), 335, 20, 0x23A0, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BookOfNinjitsu ), 335, 20, 0x23A0, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBPlayerBarkeeper.cs b/Scripts/Mobiles/Vendors/SBInfo/SBPlayerBarkeeper.cs index ffe6f1d70..ffc3ef4d6 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBPlayerBarkeeper.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBPlayerBarkeeper.cs @@ -3,44 +3,37 @@ using Server.Items; namespace Server.Mobiles { - public class SBPlayerBarkeeper : SBInfo - { - public SBPlayerBarkeeper() - { - } + public class SBPlayerBarkeeper : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Ale, 7, 20, 0x99F, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Wine, 7, 20, 0x9C7, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Liquor, 7, 20, 0x99B, 0)); + Add(new BeverageBuyInfo(typeof(Jug), BeverageType.Cider, 13, 20, 0x9C8, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Milk, 7, 20, 0x9F0, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Ale, 11, 20, 0x1F95, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Cider, 11, 20, 0x1F97, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Liquor, 11, 20, 0x1F99, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Wine, 11, 20, 0x1F9B, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Water, 11, 20, 0x1F9D, 0)); + // TODO: pizza + // TODO: bowl of *, tomato soup + Add(new GenericBuyInfo("1016450", typeof(Chessboard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo("1016449", typeof(CheckerBoard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo(typeof(Backgammon), 2, 20, 0xE1C, 0)); + Add(new GenericBuyInfo(typeof(Dices), 2, 20, 0xFA7, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Ale, 7, 20, 0x99F, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Wine, 7, 20, 0x9C7, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Liquor, 7, 20, 0x99B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Jug ), BeverageType.Cider, 13, 20, 0x9C8, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Milk, 7, 20, 0x9F0, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Ale, 11, 20, 0x1F95, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Cider, 11, 20, 0x1F97, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Liquor, 11, 20, 0x1F99, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Wine, 11, 20, 0x1F9B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Water, 11, 20, 0x1F9D, 0 ) ); - // TODO: pizza - // TODO: bowl of *, tomato soup - Add( new GenericBuyInfo( "1016450", typeof( Chessboard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( "1016449", typeof( CheckerBoard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( typeof( Backgammon ), 2, 20, 0xE1C, 0 ) ); - Add( new GenericBuyInfo( typeof( Dices ), 2, 20, 0xFA7, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBProvisioner.cs b/Scripts/Mobiles/Vendors/SBInfo/SBProvisioner.cs index d3d0bfb00..5b28385c1 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBProvisioner.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBProvisioner.cs @@ -1,171 +1,173 @@ using System.Collections.Generic; -using Server.Items; +using Server.Engines.Mahjong; +using Server.Engines.Plants; using Server.Guilds; +using Server.Items; +using Server.Multis; namespace Server.Mobiles { - public class SBProvisioner : SBInfo - { - public SBProvisioner() - { - } + public class SBProvisioner : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + #region Salvage Bag - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - #region Salvage Bag - if ( Core.ML ) - Add( new GenericBuyInfo( "1079931", typeof( SalvageBag ), 1255, 20, 0xE76, Utility.RandomBlueHue() ) ); - #endregion - Add( new GenericBuyInfo( "1060834", typeof( Engines.Plants.PlantBowl ), 2, 20, 0x15FD, 0 ) ); + if (Core.ML) + Add(new GenericBuyInfo("1079931", typeof(SalvageBag), 1255, 20, 0xE76, Utility.RandomBlueHue())); - Add( new GenericBuyInfo( typeof( Arrow ), 2, 20, 0xF3F, 0 ) ); - Add( new GenericBuyInfo( typeof( Bolt ), 5, 20, 0x1BFB, 0 ) ); + #endregion - Add( new GenericBuyInfo( typeof( Backpack ), 15, 20, 0x9B2, 0 ) ); - Add( new GenericBuyInfo( typeof( Pouch ), 6, 20, 0xE79, 0 ) ); - Add( new GenericBuyInfo( typeof( Bag ), 6, 20, 0xE76, 0 ) ); + Add(new GenericBuyInfo("1060834", typeof(PlantBowl), 2, 20, 0x15FD, 0)); - Add( new GenericBuyInfo( typeof( Candle ), 6, 20, 0xA28, 0 ) ); - Add( new GenericBuyInfo( typeof( Torch ), 8, 20, 0xF6B, 0 ) ); - Add( new GenericBuyInfo( typeof( Lantern ), 2, 20, 0xA25, 0 ) ); + Add(new GenericBuyInfo(typeof(Arrow), 2, 20, 0xF3F, 0)); + Add(new GenericBuyInfo(typeof(Bolt), 5, 20, 0x1BFB, 0)); - //TODO: Oil Flask @ 8GP + Add(new GenericBuyInfo(typeof(Backpack), 15, 20, 0x9B2, 0)); + Add(new GenericBuyInfo(typeof(Pouch), 6, 20, 0xE79, 0)); + Add(new GenericBuyInfo(typeof(Bag), 6, 20, 0xE76, 0)); - Add( new GenericBuyInfo( typeof( Lockpick ), 12, 20, 0x14FC, 0 ) ); + Add(new GenericBuyInfo(typeof(Candle), 6, 20, 0xA28, 0)); + Add(new GenericBuyInfo(typeof(Torch), 8, 20, 0xF6B, 0)); + Add(new GenericBuyInfo(typeof(Lantern), 2, 20, 0xA25, 0)); - Add( new GenericBuyInfo( typeof( FloppyHat ), 7, 20, 0x1713, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( WideBrimHat ), 8, 20, 0x1714, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( Cap ), 10, 20, 0x1715, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( TallStrawHat ), 8, 20, 0x1716, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( StrawHat ), 7, 20, 0x1717, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( WizardsHat ), 11, 20, 0x1718, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( LeatherCap ), 10, 20, 0x1DB9, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( FeatheredHat ), 10, 20, 0x171A, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( TricorneHat ), 8, 20, 0x171B, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( Bandana ), 6, 20, 0x1540, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( SkullCap ), 7, 20, 0x1544, Utility.RandomDyedHue() ) ); + //TODO: Oil Flask @ 8GP - Add( new GenericBuyInfo( typeof( BreadLoaf ), 6, 10, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( LambLeg ), 8, 20, 0x160A, 0 ) ); - Add( new GenericBuyInfo( typeof( ChickenLeg ), 5, 20, 0x1608, 0 ) ); - Add( new GenericBuyInfo( typeof( CookedBird ), 17, 20, 0x9B7, 0 ) ); + Add(new GenericBuyInfo(typeof(Lockpick), 12, 20, 0x14FC, 0)); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Ale, 7, 20, 0x99F, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Wine, 7, 20, 0x9C7, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Liquor, 7, 20, 0x99B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Jug ), BeverageType.Cider, 13, 20, 0x9C8, 0 ) ); + Add(new GenericBuyInfo(typeof(FloppyHat), 7, 20, 0x1713, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(WideBrimHat), 8, 20, 0x1714, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(Cap), 10, 20, 0x1715, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(TallStrawHat), 8, 20, 0x1716, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(StrawHat), 7, 20, 0x1717, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(WizardsHat), 11, 20, 0x1718, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(LeatherCap), 10, 20, 0x1DB9, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(FeatheredHat), 10, 20, 0x171A, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(TricorneHat), 8, 20, 0x171B, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(Bandana), 6, 20, 0x1540, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(SkullCap), 7, 20, 0x1544, Utility.RandomDyedHue())); - Add( new GenericBuyInfo( typeof( Pear ), 3, 20, 0x994, 0 ) ); - Add( new GenericBuyInfo( typeof( Apple ), 3, 20, 0x9D0, 0 ) ); + Add(new GenericBuyInfo(typeof(BreadLoaf), 6, 10, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(LambLeg), 8, 20, 0x160A, 0)); + Add(new GenericBuyInfo(typeof(ChickenLeg), 5, 20, 0x1608, 0)); + Add(new GenericBuyInfo(typeof(CookedBird), 17, 20, 0x9B7, 0)); - Add( new GenericBuyInfo( typeof( Beeswax ), 1, 20, 0x1422, 0 ) ); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Ale, 7, 20, 0x99F, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Wine, 7, 20, 0x9C7, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Liquor, 7, 20, 0x99B, 0)); + Add(new BeverageBuyInfo(typeof(Jug), BeverageType.Cider, 13, 20, 0x9C8, 0)); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 20, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 20, 0xF85, 0 ) ); + Add(new GenericBuyInfo(typeof(Pear), 3, 20, 0x994, 0)); + Add(new GenericBuyInfo(typeof(Apple), 3, 20, 0x9D0, 0)); - Add( new GenericBuyInfo( typeof( Bottle ), 5, 20, 0xF0E, 0 ) ); + Add(new GenericBuyInfo(typeof(Beeswax), 1, 20, 0x1422, 0)); - Add( new GenericBuyInfo( typeof( RedBook ), 15, 20, 0xFF1, 0 ) ); - Add( new GenericBuyInfo( typeof( BlueBook ), 15, 20, 0xFF2, 0 ) ); - Add( new GenericBuyInfo( typeof( TanBook ), 15, 20, 0xFF0, 0 ) ); + Add(new GenericBuyInfo(typeof(Garlic), 3, 20, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 20, 0xF85, 0)); - Add( new GenericBuyInfo( typeof( WoodenBox ), 14, 20, 0xE7D, 0 ) ); - Add( new GenericBuyInfo( typeof( Key ), 2, 20, 0x100E, 0 ) ); + Add(new GenericBuyInfo(typeof(Bottle), 5, 20, 0xF0E, 0)); - Add( new GenericBuyInfo( typeof( Bedroll ), 5, 20, 0xA59, 0 ) ); - Add( new GenericBuyInfo( typeof( Kindling ), 2, 20, 0xDE1, 0 ) ); + Add(new GenericBuyInfo(typeof(RedBook), 15, 20, 0xFF1, 0)); + Add(new GenericBuyInfo(typeof(BlueBook), 15, 20, 0xFF2, 0)); + Add(new GenericBuyInfo(typeof(TanBook), 15, 20, 0xFF0, 0)); - Add( new GenericBuyInfo( "1041205", typeof( Multis.SmallBoatDeed ), 10177, 20, 0x14F2, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenBox), 14, 20, 0xE7D, 0)); + Add(new GenericBuyInfo(typeof(Key), 2, 20, 0x100E, 0)); - Add( new GenericBuyInfo( "1041060", typeof( HairDye ), 60, 20, 0xEFF, 0 ) ); + Add(new GenericBuyInfo(typeof(Bedroll), 5, 20, 0xA59, 0)); + Add(new GenericBuyInfo(typeof(Kindling), 2, 20, 0xDE1, 0)); - Add( new GenericBuyInfo( "1016450", typeof( Chessboard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( "1016449", typeof( CheckerBoard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( typeof( Backgammon ), 2, 20, 0xE1C, 0 ) ); - if ( Core.AOS ) - Add( new GenericBuyInfo( typeof( Engines.Mahjong.MahjongGame ), 6, 20, 0xFAA, 0 ) ); - Add( new GenericBuyInfo( typeof( Dices ), 2, 20, 0xFA7, 0 ) ); + Add(new GenericBuyInfo("1041205", typeof(SmallBoatDeed), 10177, 20, 0x14F2, 0)); - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( SmallBagBall ), 3, 20, 0x2256, 0 ) ); - Add( new GenericBuyInfo( typeof( LargeBagBall ), 3, 20, 0x2257, 0 ) ); - } + Add(new GenericBuyInfo("1041060", typeof(HairDye), 60, 20, 0xEFF, 0)); - if ( !Guild.NewGuildSystem ) - Add( new GenericBuyInfo( "1041055", typeof( GuildDeed ), 12450, 20, 0x14F0, 0 ) ); - } - } + Add(new GenericBuyInfo("1016450", typeof(Chessboard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo("1016449", typeof(CheckerBoard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo(typeof(Backgammon), 2, 20, 0xE1C, 0)); + if (Core.AOS) + Add(new GenericBuyInfo(typeof(MahjongGame), 6, 20, 0xFAA, 0)); + Add(new GenericBuyInfo(typeof(Dices), 2, 20, 0xFA7, 0)); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Arrow ), 1 ); - Add( typeof( Bolt ), 2 ); - Add( typeof( Backpack ), 7 ); - Add( typeof( Pouch ), 3 ); - Add( typeof( Bag ), 3 ); - Add( typeof( Candle ), 3 ); - Add( typeof( Torch ), 4 ); - Add( typeof( Lantern ), 1 ); - Add( typeof( Lockpick ), 6 ); - Add( typeof( FloppyHat ), 3 ); - Add( typeof( WideBrimHat ), 4 ); - Add( typeof( Cap ), 5 ); - Add( typeof( TallStrawHat ), 4 ); - Add( typeof( StrawHat ), 3 ); - Add( typeof( WizardsHat ), 5 ); - Add( typeof( LeatherCap ), 5 ); - Add( typeof( FeatheredHat ), 5 ); - Add( typeof( TricorneHat ), 4 ); - Add( typeof( Bandana ), 3 ); - Add( typeof( SkullCap ), 3 ); - Add( typeof( Bottle ), 3 ); - Add( typeof( RedBook ), 7 ); - Add( typeof( BlueBook ), 7 ); - Add( typeof( TanBook ), 7 ); - Add( typeof( WoodenBox ), 7 ); - Add( typeof( Kindling ), 1 ); - Add( typeof( HairDye ), 30 ); - Add( typeof( Chessboard ), 1 ); - Add( typeof( CheckerBoard ), 1 ); - Add( typeof( Backgammon ), 1 ); - Add( typeof( Dices ), 1 ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(SmallBagBall), 3, 20, 0x2256, 0)); + Add(new GenericBuyInfo(typeof(LargeBagBall), 3, 20, 0x2257, 0)); + } - Add( typeof( Beeswax ), 1 ); + if (!Guild.NewGuildSystem) + Add(new GenericBuyInfo("1041055", typeof(GuildDeed), 12450, 20, 0x14F0, 0)); + } + } - Add( typeof( Amber ), 25 ); - Add( typeof( Amethyst ), 50 ); - Add( typeof( Citrine ), 25 ); - Add( typeof( Diamond ), 100 ); - Add( typeof( Emerald ), 50 ); - Add( typeof( Ruby ), 37 ); - Add( typeof( Sapphire ), 50 ); - Add( typeof( StarSapphire ), 62 ); - Add( typeof( Tourmaline ), 47 ); - Add( typeof( GoldRing ), 13 ); - Add( typeof( SilverRing ), 10 ); - Add( typeof( Necklace ), 13 ); - Add( typeof( GoldNecklace ), 13 ); - Add( typeof( GoldBeadNecklace ), 13 ); - Add( typeof( SilverNecklace ), 10 ); - Add( typeof( SilverBeadNecklace ), 10 ); - Add( typeof( Beads ), 13 ); - Add( typeof( GoldBracelet ), 13 ); - Add( typeof( SilverBracelet ), 10 ); - Add( typeof( GoldEarrings ), 13 ); - Add( typeof( SilverEarrings ), 10 ); + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Arrow), 1); + Add(typeof(Bolt), 2); + Add(typeof(Backpack), 7); + Add(typeof(Pouch), 3); + Add(typeof(Bag), 3); + Add(typeof(Candle), 3); + Add(typeof(Torch), 4); + Add(typeof(Lantern), 1); + Add(typeof(Lockpick), 6); + Add(typeof(FloppyHat), 3); + Add(typeof(WideBrimHat), 4); + Add(typeof(Cap), 5); + Add(typeof(TallStrawHat), 4); + Add(typeof(StrawHat), 3); + Add(typeof(WizardsHat), 5); + Add(typeof(LeatherCap), 5); + Add(typeof(FeatheredHat), 5); + Add(typeof(TricorneHat), 4); + Add(typeof(Bandana), 3); + Add(typeof(SkullCap), 3); + Add(typeof(Bottle), 3); + Add(typeof(RedBook), 7); + Add(typeof(BlueBook), 7); + Add(typeof(TanBook), 7); + Add(typeof(WoodenBox), 7); + Add(typeof(Kindling), 1); + Add(typeof(HairDye), 30); + Add(typeof(Chessboard), 1); + Add(typeof(CheckerBoard), 1); + Add(typeof(Backgammon), 1); + Add(typeof(Dices), 1); - if ( !Guild.NewGuildSystem ) - Add( typeof( GuildDeed ), 6225 ); - } - } - } -} + Add(typeof(Beeswax), 1); + + Add(typeof(Amber), 25); + Add(typeof(Amethyst), 50); + Add(typeof(Citrine), 25); + Add(typeof(Diamond), 100); + Add(typeof(Emerald), 50); + Add(typeof(Ruby), 37); + Add(typeof(Sapphire), 50); + Add(typeof(StarSapphire), 62); + Add(typeof(Tourmaline), 47); + Add(typeof(GoldRing), 13); + Add(typeof(SilverRing), 10); + Add(typeof(Necklace), 13); + Add(typeof(GoldNecklace), 13); + Add(typeof(GoldBeadNecklace), 13); + Add(typeof(SilverNecklace), 10); + Add(typeof(SilverBeadNecklace), 10); + Add(typeof(Beads), 13); + Add(typeof(GoldBracelet), 13); + Add(typeof(SilverBracelet), 10); + Add(typeof(GoldEarrings), 13); + Add(typeof(SilverEarrings), 10); + + if (!Guild.NewGuildSystem) + Add(typeof(GuildDeed), 6225); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBRancher.cs b/Scripts/Mobiles/Vendors/SBInfo/SBRancher.cs index 53b135ea9..e8db7d8f6 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBRancher.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBRancher.cs @@ -2,29 +2,22 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class SBRancher : SBInfo - { - public SBRancher() - { - } + public class SBRancher : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new AnimalBuyInfo(1, typeof(PackHorse), 631, 10, 291, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new AnimalBuyInfo( 1, typeof( PackHorse ), 631, 10, 291, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBRanger.cs b/Scripts/Mobiles/Vendors/SBInfo/SBRanger.cs index 7eb4aae23..fd4d0d9e5 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBRanger.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBRanger.cs @@ -3,33 +3,26 @@ using Server.Items; namespace Server.Mobiles { - public class SBRanger : SBInfo - { - public SBRanger() - { - } + public class SBRanger : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new AnimalBuyInfo(1, typeof(Cat), 138, 20, 201, 0)); + Add(new AnimalBuyInfo(1, typeof(Dog), 181, 20, 217, 0)); + Add(new AnimalBuyInfo(1, typeof(PackLlama), 491, 20, 292, 0)); + Add(new AnimalBuyInfo(1, typeof(PackHorse), 606, 20, 291, 0)); + Add(new GenericBuyInfo(typeof(Bandage), 5, 20, 0xE21, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new AnimalBuyInfo( 1, typeof( Cat ), 138, 20, 201, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Dog ), 181, 20, 217, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( PackLlama ), 491, 20, 292, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( PackHorse ), 606, 20, 291, 0 ) ); - Add( new GenericBuyInfo( typeof( Bandage ), 5, 20, 0xE21, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBRealEstateBroker.cs b/Scripts/Mobiles/Vendors/SBInfo/SBRealEstateBroker.cs index acc8c7e0b..6914df1ae 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBRealEstateBroker.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBRealEstateBroker.cs @@ -3,32 +3,28 @@ using Server.Items; namespace Server.Mobiles { - public class SBRealEstateBroker : SBInfo - { - public SBRealEstateBroker() - { - } + public class SBRealEstateBroker : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BlankScroll), 5, 20, 0x0E34, 0)); + Add(new GenericBuyInfo(typeof(ScribesPen), 8, 20, 0xFBF, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BlankScroll ), 5, 20, 0x0E34, 0 ) ); - Add( new GenericBuyInfo( typeof( ScribesPen ), 8, 20, 0xFBF, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( ScribesPen ), 4 ); - Add( typeof( BlankScroll ), 2 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(ScribesPen), 4); + Add(typeof(BlankScroll), 2); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBSECook.cs b/Scripts/Mobiles/Vendors/SBInfo/SBSECook.cs index 7a4ae45a2..c8bf63d9b 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBSECook.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBSECook.cs @@ -3,48 +3,44 @@ using Server.Items; namespace Server.Mobiles { - public class SBSECook: SBInfo - { - public SBSECook() - { - } + public class SBSECook : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Wasabi), 2, 20, 0x24E8, 0)); + Add(new GenericBuyInfo(typeof(Wasabi), 2, 20, 0x24E9, 0)); + Add(new GenericBuyInfo(typeof(SushiRolls), 3, 20, 0x283E, 0)); + Add(new GenericBuyInfo(typeof(SushiPlatter), 3, 20, 0x2840, 0)); + Add(new GenericBuyInfo(typeof(GreenTea), 3, 20, 0x284C, 0)); + Add(new GenericBuyInfo(typeof(MisoSoup), 3, 20, 0x284D, 0)); + Add(new GenericBuyInfo(typeof(WhiteMisoSoup), 3, 20, 0x284E, 0)); + Add(new GenericBuyInfo(typeof(RedMisoSoup), 3, 20, 0x284F, 0)); + Add(new GenericBuyInfo(typeof(AwaseMisoSoup), 3, 20, 0x2850, 0)); + Add(new GenericBuyInfo(typeof(BentoBox), 6, 20, 0x2836, 0)); + Add(new GenericBuyInfo(typeof(BentoBox), 6, 20, 0x2837, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E8, 0 ) ); - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E9, 0 ) ); - Add( new GenericBuyInfo( typeof( SushiRolls ), 3, 20, 0x283E, 0 ) ); - Add( new GenericBuyInfo( typeof( SushiPlatter ), 3, 20, 0x2840, 0 ) ); - Add( new GenericBuyInfo( typeof( GreenTea ), 3, 20, 0x284C, 0 ) ); - Add( new GenericBuyInfo( typeof( MisoSoup ), 3, 20, 0x284D, 0 ) ); - Add( new GenericBuyInfo( typeof( WhiteMisoSoup ), 3, 20, 0x284E, 0 ) ); - Add( new GenericBuyInfo( typeof( RedMisoSoup ), 3, 20, 0x284F, 0 ) ); - Add( new GenericBuyInfo( typeof( AwaseMisoSoup ), 3, 20, 0x2850, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2836, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2837, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Wasabi ), 1 ); - Add( typeof( BentoBox ), 3 ); - Add( typeof( GreenTea ), 1 ); - Add( typeof( SushiRolls ), 1 ); - Add( typeof( SushiPlatter ), 2 ); - Add( typeof( MisoSoup ), 1 ); - Add( typeof( RedMisoSoup ), 1 ); - Add( typeof( WhiteMisoSoup ), 1 ); - Add( typeof( AwaseMisoSoup ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Wasabi), 1); + Add(typeof(BentoBox), 3); + Add(typeof(GreenTea), 1); + Add(typeof(SushiRolls), 1); + Add(typeof(SushiPlatter), 2); + Add(typeof(MisoSoup), 1); + Add(typeof(RedMisoSoup), 1); + Add(typeof(WhiteMisoSoup), 1); + Add(typeof(AwaseMisoSoup), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBSEHats.cs b/Scripts/Mobiles/Vendors/SBInfo/SBSEHats.cs index 14401c6c8..fdcab5486 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBSEHats.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBSEHats.cs @@ -3,34 +3,30 @@ using Server.Items; namespace Server.Mobiles { - public class SBSEHats: SBInfo - { - public SBSEHats() - { - } + public class SBSEHats : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Kasa), 31, 20, 0x2798, 0)); + Add(new GenericBuyInfo(typeof(LeatherJingasa), 11, 20, 0x2776, 0)); + Add(new GenericBuyInfo(typeof(ClothNinjaHood), 33, 20, 0x278F, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Kasa ), 31, 20, 0x2798, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherJingasa ), 11, 20, 0x2776, 0 ) ); - Add( new GenericBuyInfo( typeof( ClothNinjaHood ), 33, 20, 0x278F, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Kasa ), 15 ); - Add( typeof( LeatherJingasa ), 5 ); - Add( typeof( ClothNinjaHood ), 16 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Kasa), 15); + Add(typeof(LeatherJingasa), 5); + Add(typeof(ClothNinjaHood), 16); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBSamurai.cs b/Scripts/Mobiles/Vendors/SBInfo/SBSamurai.cs index 7d6c9d946..33ecff1d4 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBSamurai.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBSamurai.cs @@ -3,29 +3,22 @@ using Server.Items; namespace Server.Mobiles { - public class SBSamurai : SBInfo - { - public SBSamurai() - { - } + public class SBSamurai : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BookOfBushido), 280, 20, 0x238C, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BookOfBushido ), 280, 20, 0x238C, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBScribe.cs b/Scripts/Mobiles/Vendors/SBInfo/SBScribe.cs index 08704ecf4..dcb69111d 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBScribe.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBScribe.cs @@ -3,40 +3,36 @@ using Server.Items; namespace Server.Mobiles { - public class SBScribe: SBInfo - { - public SBScribe() - { - } + public class SBScribe : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(ScribesPen), 8, 20, 0xFBF, 0)); + Add(new GenericBuyInfo(typeof(BlankScroll), 5, 999, 0x0E34, 0)); + Add(new GenericBuyInfo(typeof(ScribesPen), 8, 20, 0xFC0, 0)); + Add(new GenericBuyInfo(typeof(BrownBook), 15, 10, 0xFEF, 0)); + Add(new GenericBuyInfo(typeof(TanBook), 15, 10, 0xFF0, 0)); + Add(new GenericBuyInfo(typeof(BlueBook), 15, 10, 0xFF2, 0)); + //Add( new GenericBuyInfo( "1041267", typeof( Runebook ), 3500, 10, 0xEFA, 0x461 ) ); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( ScribesPen ), 8, 20, 0xFBF, 0 ) ); - Add( new GenericBuyInfo( typeof( BlankScroll ), 5, 999, 0x0E34, 0 ) ); - Add( new GenericBuyInfo( typeof( ScribesPen ), 8, 20, 0xFC0, 0 ) ); - Add( new GenericBuyInfo( typeof( BrownBook ), 15, 10, 0xFEF, 0 ) ); - Add( new GenericBuyInfo( typeof( TanBook ), 15, 10, 0xFF0, 0 ) ); - Add( new GenericBuyInfo( typeof( BlueBook ), 15, 10, 0xFF2, 0 ) ); - //Add( new GenericBuyInfo( "1041267", typeof( Runebook ), 3500, 10, 0xEFA, 0x461 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( ScribesPen ), 4 ); - Add( typeof( BrownBook ), 7 ); - Add( typeof( TanBook ), 7 ); - Add( typeof( BlueBook ), 7 ); - Add( typeof( BlankScroll ), 3 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(ScribesPen), 4); + Add(typeof(BrownBook), 7); + Add(typeof(TanBook), 7); + Add(typeof(BlueBook), 7); + Add(typeof(BlankScroll), 3); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBShipwright.cs b/Scripts/Mobiles/Vendors/SBInfo/SBShipwright.cs index 036fbdd9b..aa8da3c61 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBShipwright.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBShipwright.cs @@ -3,35 +3,27 @@ using Server.Multis; namespace Server.Mobiles { - public class SBShipwright : SBInfo - { - public SBShipwright() - { - } + public class SBShipwright : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo("1041205", typeof(SmallBoatDeed), 10177, 20, 0x14F2, 0)); + Add(new GenericBuyInfo("1041206", typeof(SmallDragonBoatDeed), 10177, 20, 0x14F2, 0)); + Add(new GenericBuyInfo("1041207", typeof(MediumBoatDeed), 11552, 20, 0x14F2, 0)); + Add(new GenericBuyInfo("1041208", typeof(MediumDragonBoatDeed), 11552, 20, 0x14F2, 0)); + Add(new GenericBuyInfo("1041209", typeof(LargeBoatDeed), 12927, 20, 0x14F2, 0)); + Add(new GenericBuyInfo("1041210", typeof(LargeDragonBoatDeed), 12927, 20, 0x14F2, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( "1041205", typeof( SmallBoatDeed ), 10177, 20, 0x14F2, 0 ) ); - Add( new GenericBuyInfo( "1041206", typeof( SmallDragonBoatDeed ), 10177, 20, 0x14F2, 0 ) ); - Add( new GenericBuyInfo( "1041207", typeof( MediumBoatDeed ), 11552, 20, 0x14F2, 0 ) ); - Add( new GenericBuyInfo( "1041208", typeof( MediumDragonBoatDeed ), 11552, 20, 0x14F2, 0 ) ); - Add( new GenericBuyInfo( "1041209", typeof( LargeBoatDeed ), 12927, 20, 0x14F2, 0 ) ); - Add( new GenericBuyInfo( "1041210", typeof( LargeDragonBoatDeed ), 12927, 20, 0x14F2, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - //You technically CAN sell them back, *BUT* the vendors do not carry enough money to buy with - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBSmithTools.cs b/Scripts/Mobiles/Vendors/SBInfo/SBSmithTools.cs index 556218f49..82ec939e6 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBSmithTools.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBSmithTools.cs @@ -3,33 +3,28 @@ using Server.Items; namespace Server.Mobiles { - public class SBSmithTools: SBInfo - { - public SBSmithTools() - { - } + public class SBSmithTools : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(IronIngot), 5, 16, 0x1BF2, 0)); + Add(new GenericBuyInfo(typeof(Tongs), 13, 14, 0xFBB, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( IronIngot ), 5, 16, 0x1BF2, 0 ) ); - Add( new GenericBuyInfo( typeof( Tongs ), 13, 14, 0xFBB, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Tongs ), 7 ); - Add( typeof( IronIngot ), 4 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Tongs), 7); + Add(typeof(IronIngot), 4); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBStoneCrafter.cs b/Scripts/Mobiles/Vendors/SBInfo/SBStoneCrafter.cs index b68f58080..c29bee499 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBStoneCrafter.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBStoneCrafter.cs @@ -3,91 +3,87 @@ using Server.Items; namespace Server.Mobiles { - public class SBStoneCrafter : SBInfo - { - public SBStoneCrafter() - { - } + public class SBStoneCrafter : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Nails), 3, 20, 0x102E, 0)); + Add(new GenericBuyInfo(typeof(Axle), 2, 20, 0x105B, 0)); + Add(new GenericBuyInfo(typeof(Board), 3, 20, 0x1BD7, 0)); + Add(new GenericBuyInfo(typeof(DrawKnife), 10, 20, 0x10E4, 0)); + Add(new GenericBuyInfo(typeof(Froe), 10, 20, 0x10E5, 0)); + Add(new GenericBuyInfo(typeof(Scorp), 10, 20, 0x10E7, 0)); + Add(new GenericBuyInfo(typeof(Inshave), 10, 20, 0x10E6, 0)); + Add(new GenericBuyInfo(typeof(DovetailSaw), 12, 20, 0x1028, 0)); + Add(new GenericBuyInfo(typeof(Saw), 15, 20, 0x1034, 0)); + Add(new GenericBuyInfo(typeof(Hammer), 17, 20, 0x102A, 0)); + Add(new GenericBuyInfo(typeof(MouldingPlane), 11, 20, 0x102C, 0)); + Add(new GenericBuyInfo(typeof(SmoothingPlane), 10, 20, 0x1032, 0)); + Add(new GenericBuyInfo(typeof(JointingPlane), 11, 20, 0x1030, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Nails ), 3, 20, 0x102E, 0 ) ); - Add( new GenericBuyInfo( typeof( Axle ), 2, 20, 0x105B, 0 ) ); - Add( new GenericBuyInfo( typeof( Board ), 3, 20, 0x1BD7, 0 ) ); - Add( new GenericBuyInfo( typeof( DrawKnife ), 10, 20, 0x10E4, 0 ) ); - Add( new GenericBuyInfo( typeof( Froe ), 10, 20, 0x10E5, 0 ) ); - Add( new GenericBuyInfo( typeof( Scorp ), 10, 20, 0x10E7, 0 ) ); - Add( new GenericBuyInfo( typeof( Inshave ), 10, 20, 0x10E6, 0 ) ); - Add( new GenericBuyInfo( typeof( DovetailSaw ), 12, 20, 0x1028, 0 ) ); - Add( new GenericBuyInfo( typeof( Saw ), 15, 20, 0x1034, 0 ) ); - Add( new GenericBuyInfo( typeof( Hammer ), 17, 20, 0x102A, 0 ) ); - Add( new GenericBuyInfo( typeof( MouldingPlane ), 11, 20, 0x102C, 0 ) ); - Add( new GenericBuyInfo( typeof( SmoothingPlane ), 10, 20, 0x1032, 0 ) ); - Add( new GenericBuyInfo( typeof( JointingPlane ), 11, 20, 0x1030, 0 ) ); + Add(new GenericBuyInfo("Making Valuables With Stonecrafting", typeof(MasonryBook), 10625, 10, 0xFBE, 0)); + Add(new GenericBuyInfo("Mining For Quality Stone", typeof(StoneMiningBook), 10625, 10, 0xFBE, 0)); + Add(new GenericBuyInfo("1044515", typeof(MalletAndChisel), 3, 50, 0x12B3, 0)); + } + } - Add( new GenericBuyInfo( "Making Valuables With Stonecrafting", typeof( MasonryBook ), 10625, 10, 0xFBE, 0 ) ); - Add( new GenericBuyInfo( "Mining For Quality Stone", typeof( StoneMiningBook ), 10625, 10, 0xFBE, 0 ) ); - Add( new GenericBuyInfo( "1044515", typeof( MalletAndChisel ), 3, 50, 0x12B3, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(MasonryBook), 5000); + Add(typeof(StoneMiningBook), 5000); + Add(typeof(MalletAndChisel), 1); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( MasonryBook ), 5000 ); - Add( typeof( StoneMiningBook ), 5000 ); - Add( typeof( MalletAndChisel ), 1 ); + Add(typeof(WoodenBox), 7); + Add(typeof(SmallCrate), 5); + Add(typeof(MediumCrate), 6); + Add(typeof(LargeCrate), 7); + Add(typeof(WoodenChest), 15); - Add( typeof( WoodenBox ), 7 ); - Add( typeof( SmallCrate ), 5 ); - Add( typeof( MediumCrate ), 6 ); - Add( typeof( LargeCrate ), 7 ); - Add( typeof( WoodenChest ), 15 ); + Add(typeof(LargeTable), 10); + Add(typeof(Nightstand), 7); + Add(typeof(YewWoodTable), 10); - Add( typeof( LargeTable ), 10 ); - Add( typeof( Nightstand ), 7 ); - Add( typeof( YewWoodTable ), 10 ); + Add(typeof(Throne), 24); + Add(typeof(WoodenThrone), 6); + Add(typeof(Stool), 6); + Add(typeof(FootStool), 6); - Add( typeof( Throne ), 24 ); - Add( typeof( WoodenThrone ), 6 ); - Add( typeof( Stool ), 6 ); - Add( typeof( FootStool ), 6 ); + Add(typeof(FancyWoodenChairCushion), 12); + Add(typeof(WoodenChairCushion), 10); + Add(typeof(WoodenChair), 8); + Add(typeof(BambooChair), 6); + Add(typeof(WoodenBench), 6); - Add( typeof( FancyWoodenChairCushion ), 12 ); - Add( typeof( WoodenChairCushion ), 10 ); - Add( typeof( WoodenChair ), 8 ); - Add( typeof( BambooChair ), 6 ); - Add( typeof( WoodenBench ), 6 ); + Add(typeof(Saw), 9); + Add(typeof(Scorp), 6); + Add(typeof(SmoothingPlane), 6); + Add(typeof(DrawKnife), 6); + Add(typeof(Froe), 6); + Add(typeof(Hammer), 14); + Add(typeof(Inshave), 6); + Add(typeof(JointingPlane), 6); + Add(typeof(MouldingPlane), 6); + Add(typeof(DovetailSaw), 7); + Add(typeof(Board), 2); + Add(typeof(Axle), 1); - Add( typeof( Saw ), 9 ); - Add( typeof( Scorp ), 6 ); - Add( typeof( SmoothingPlane ), 6 ); - Add( typeof( DrawKnife ), 6 ); - Add( typeof( Froe ), 6 ); - Add( typeof( Hammer ), 14 ); - Add( typeof( Inshave ), 6 ); - Add( typeof( JointingPlane ), 6 ); - Add( typeof( MouldingPlane ), 6 ); - Add( typeof( DovetailSaw ), 7 ); - Add( typeof( Board ), 2 ); - Add( typeof( Axle ), 1 ); + Add(typeof(WoodenShield), 31); + Add(typeof(BlackStaff), 24); + Add(typeof(GnarledStaff), 12); + Add(typeof(QuarterStaff), 15); + Add(typeof(ShepherdsCrook), 12); + Add(typeof(Club), 13); - Add( typeof( WoodenShield ), 31 ); - Add( typeof( BlackStaff ), 24 ); - Add( typeof( GnarledStaff ), 12 ); - Add( typeof( QuarterStaff ), 15 ); - Add( typeof( ShepherdsCrook ), 12 ); - Add( typeof( Club ), 13 ); - - Add( typeof( Log ), 1 ); - } - } - } -} + Add(typeof(Log), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBTailor.cs b/Scripts/Mobiles/Vendors/SBInfo/SBTailor.cs index 7a7c211e2..a1a2dd246 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBTailor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBTailor.cs @@ -3,117 +3,113 @@ using Server.Items; namespace Server.Mobiles { - public class SBTailor: SBInfo - { - public SBTailor() - { - } + public class SBTailor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(SewingKit), 3, 20, 0xF9D, 0)); + Add(new GenericBuyInfo(typeof(Scissors), 11, 20, 0xF9F, 0)); + Add(new GenericBuyInfo(typeof(DyeTub), 8, 20, 0xFAB, 0)); + Add(new GenericBuyInfo(typeof(Dyes), 8, 20, 0xFA9, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( SewingKit ), 3, 20, 0xF9D, 0 ) ); - Add( new GenericBuyInfo( typeof( Scissors ), 11, 20, 0xF9F, 0 ) ); - Add( new GenericBuyInfo( typeof( DyeTub ), 8, 20, 0xFAB, 0 ) ); - Add( new GenericBuyInfo( typeof( Dyes ), 8, 20, 0xFA9, 0 ) ); + Add(new GenericBuyInfo(typeof(Shirt), 12, 20, 0x1517, 0)); + Add(new GenericBuyInfo(typeof(ShortPants), 7, 20, 0x152E, 0)); + Add(new GenericBuyInfo(typeof(FancyShirt), 21, 20, 0x1EFD, 0)); + Add(new GenericBuyInfo(typeof(LongPants), 10, 20, 0x1539, 0)); + Add(new GenericBuyInfo(typeof(FancyDress), 26, 20, 0x1EFF, 0)); + Add(new GenericBuyInfo(typeof(PlainDress), 13, 20, 0x1F01, 0)); + Add(new GenericBuyInfo(typeof(Kilt), 11, 20, 0x1537, 0)); + Add(new GenericBuyInfo(typeof(Kilt), 11, 20, 0x1537, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(HalfApron), 10, 20, 0x153b, 0)); + Add(new GenericBuyInfo(typeof(Robe), 18, 20, 0x1F03, 0)); + Add(new GenericBuyInfo(typeof(Cloak), 8, 20, 0x1515, 0)); + Add(new GenericBuyInfo(typeof(Cloak), 8, 20, 0x1515, 0)); + Add(new GenericBuyInfo(typeof(Doublet), 13, 20, 0x1F7B, 0)); + Add(new GenericBuyInfo(typeof(Tunic), 18, 20, 0x1FA1, 0)); + Add(new GenericBuyInfo(typeof(JesterSuit), 26, 20, 0x1F9F, 0)); - Add( new GenericBuyInfo( typeof( Shirt ), 12, 20, 0x1517, 0 ) ); - Add( new GenericBuyInfo( typeof( ShortPants ), 7, 20, 0x152E, 0 ) ); - Add( new GenericBuyInfo( typeof( FancyShirt ), 21, 20, 0x1EFD, 0 ) ); - Add( new GenericBuyInfo( typeof( LongPants ), 10, 20, 0x1539, 0 ) ); - Add( new GenericBuyInfo( typeof( FancyDress ), 26, 20, 0x1EFF, 0 ) ); - Add( new GenericBuyInfo( typeof( PlainDress ), 13, 20, 0x1F01, 0 ) ); - Add( new GenericBuyInfo( typeof( Kilt ), 11, 20, 0x1537, 0 ) ); - Add( new GenericBuyInfo( typeof( Kilt ), 11, 20, 0x1537, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( HalfApron ), 10, 20, 0x153b, 0 ) ); - Add( new GenericBuyInfo( typeof( Robe ), 18, 20, 0x1F03, 0 ) ); - Add( new GenericBuyInfo( typeof( Cloak ), 8, 20, 0x1515, 0 ) ); - Add( new GenericBuyInfo( typeof( Cloak ), 8, 20, 0x1515, 0 ) ); - Add( new GenericBuyInfo( typeof( Doublet ), 13, 20, 0x1F7B, 0 ) ); - Add( new GenericBuyInfo( typeof( Tunic ), 18, 20, 0x1FA1, 0 ) ); - Add( new GenericBuyInfo( typeof( JesterSuit ), 26, 20, 0x1F9F, 0 ) ); + Add(new GenericBuyInfo(typeof(JesterHat), 12, 20, 0x171C, 0)); + Add(new GenericBuyInfo(typeof(FloppyHat), 7, 20, 0x1713, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(WideBrimHat), 8, 20, 0x1714, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(Cap), 10, 20, 0x1715, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(TallStrawHat), 8, 20, 0x1716, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(StrawHat), 7, 20, 0x1717, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(WizardsHat), 11, 20, 0x1718, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(LeatherCap), 10, 20, 0x1DB9, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(FeatheredHat), 10, 20, 0x171A, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(TricorneHat), 8, 20, 0x171B, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(Bandana), 6, 20, 0x1540, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(SkullCap), 7, 20, 0x1544, Utility.RandomDyedHue())); - Add( new GenericBuyInfo( typeof( JesterHat ), 12, 20, 0x171C, 0 ) ); - Add( new GenericBuyInfo( typeof( FloppyHat ), 7, 20, 0x1713, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( WideBrimHat ), 8, 20, 0x1714, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( Cap ), 10, 20, 0x1715, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( TallStrawHat ), 8, 20, 0x1716, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( StrawHat ), 7, 20, 0x1717, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( WizardsHat ), 11, 20, 0x1718, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( LeatherCap ), 10, 20, 0x1DB9, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( FeatheredHat ), 10, 20, 0x171A, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( TricorneHat ), 8, 20, 0x171B, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( Bandana ), 6, 20, 0x1540, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( SkullCap ), 7, 20, 0x1544, Utility.RandomDyedHue() ) ); + Add(new GenericBuyInfo(typeof(BoltOfCloth), 100, 20, 0xf95, Utility.RandomDyedHue())); - Add( new GenericBuyInfo( typeof( BoltOfCloth ), 100, 20, 0xf95, Utility.RandomDyedHue() ) ); + Add(new GenericBuyInfo(typeof(Cloth), 2, 20, 0x1766, Utility.RandomDyedHue())); + Add(new GenericBuyInfo(typeof(UncutCloth), 2, 20, 0x1767, Utility.RandomDyedHue())); - Add( new GenericBuyInfo( typeof( Cloth ), 2, 20, 0x1766, Utility.RandomDyedHue() ) ); - Add( new GenericBuyInfo( typeof( UncutCloth ), 2, 20, 0x1767, Utility.RandomDyedHue() ) ); + Add(new GenericBuyInfo(typeof(Cotton), 102, 20, 0xDF9, 0)); + Add(new GenericBuyInfo(typeof(Wool), 62, 20, 0xDF8, 0)); + Add(new GenericBuyInfo(typeof(Flax), 102, 20, 0x1A9C, 0)); + Add(new GenericBuyInfo(typeof(SpoolOfThread), 18, 20, 0xFA0, 0)); + } + } - Add( new GenericBuyInfo( typeof( Cotton ), 102, 20, 0xDF9, 0 ) ); - Add( new GenericBuyInfo( typeof( Wool ), 62, 20, 0xDF8, 0 ) ); - Add( new GenericBuyInfo( typeof( Flax ), 102, 20, 0x1A9C, 0 ) ); - Add( new GenericBuyInfo( typeof( SpoolOfThread ), 18, 20, 0xFA0, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Scissors), 6); + Add(typeof(SewingKit), 1); + Add(typeof(Dyes), 4); + Add(typeof(DyeTub), 4); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Scissors ), 6 ); - Add( typeof( SewingKit ), 1 ); - Add( typeof( Dyes ), 4 ); - Add( typeof( DyeTub ), 4 ); + Add(typeof(BoltOfCloth), 50); - Add( typeof( BoltOfCloth ), 50 ); + Add(typeof(FancyShirt), 10); + Add(typeof(Shirt), 6); - Add( typeof( FancyShirt ), 10 ); - Add( typeof( Shirt ), 6 ); + Add(typeof(ShortPants), 3); + Add(typeof(LongPants), 5); - Add( typeof( ShortPants ), 3 ); - Add( typeof( LongPants ), 5 ); + Add(typeof(Cloak), 4); + Add(typeof(FancyDress), 12); + Add(typeof(Robe), 9); + Add(typeof(PlainDress), 7); - Add( typeof( Cloak ), 4 ); - Add( typeof( FancyDress ), 12 ); - Add( typeof( Robe ), 9 ); - Add( typeof( PlainDress ), 7 ); + Add(typeof(Skirt), 5); + Add(typeof(Kilt), 5); - Add( typeof( Skirt ), 5 ); - Add( typeof( Kilt ), 5 ); + Add(typeof(Doublet), 7); + Add(typeof(Tunic), 9); + Add(typeof(JesterSuit), 13); - Add( typeof( Doublet ), 7 ); - Add( typeof( Tunic ), 9 ); - Add( typeof( JesterSuit ), 13 ); + Add(typeof(FullApron), 5); + Add(typeof(HalfApron), 5); - Add( typeof( FullApron ), 5 ); - Add( typeof( HalfApron ), 5 ); + Add(typeof(JesterHat), 6); + Add(typeof(FloppyHat), 3); + Add(typeof(WideBrimHat), 4); + Add(typeof(Cap), 5); + Add(typeof(SkullCap), 3); + Add(typeof(Bandana), 3); + Add(typeof(TallStrawHat), 4); + Add(typeof(StrawHat), 4); + Add(typeof(WizardsHat), 5); + Add(typeof(Bonnet), 4); + Add(typeof(FeatheredHat), 5); + Add(typeof(TricorneHat), 4); - Add( typeof( JesterHat ), 6 ); - Add( typeof( FloppyHat ), 3 ); - Add( typeof( WideBrimHat ), 4 ); - Add( typeof( Cap ), 5 ); - Add( typeof( SkullCap ), 3 ); - Add( typeof( Bandana ), 3 ); - Add( typeof( TallStrawHat ), 4 ); - Add( typeof( StrawHat ), 4 ); - Add( typeof( WizardsHat ), 5 ); - Add( typeof( Bonnet ), 4 ); - Add( typeof( FeatheredHat ), 5 ); - Add( typeof( TricorneHat ), 4 ); + Add(typeof(SpoolOfThread), 9); - Add( typeof( SpoolOfThread ), 9 ); - - Add( typeof( Flax ), 51 ); - Add( typeof( Cotton ), 51 ); - Add( typeof( Wool ), 31 ); - } - } - } -} + Add(typeof(Flax), 51); + Add(typeof(Cotton), 51); + Add(typeof(Wool), 31); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBTanner.cs b/Scripts/Mobiles/Vendors/SBInfo/SBTanner.cs index c10d7f942..8e2ca742f 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBTanner.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBTanner.cs @@ -3,87 +3,83 @@ using Server.Items; namespace Server.Mobiles { - public class SBTanner : SBInfo - { - public SBTanner() - { - } + public class SBTanner : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(LeatherGorget), 31, 20, 0x13C7, 0)); + Add(new GenericBuyInfo(typeof(LeatherCap), 10, 20, 0x1DB9, 0)); + Add(new GenericBuyInfo(typeof(LeatherArms), 37, 20, 0x13CD, 0)); + Add(new GenericBuyInfo(typeof(LeatherChest), 47, 20, 0x13CC, 0)); + Add(new GenericBuyInfo(typeof(LeatherLegs), 36, 20, 0x13CB, 0)); + Add(new GenericBuyInfo(typeof(LeatherGloves), 31, 20, 0x13C6, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( LeatherGorget ), 31, 20, 0x13C7, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherCap ), 10, 20, 0x1DB9, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherArms ), 37, 20, 0x13CD, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherChest ), 47, 20, 0x13CC, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherLegs ), 36, 20, 0x13CB, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherGloves ), 31, 20, 0x13C6, 0 ) ); + Add(new GenericBuyInfo(typeof(StuddedGorget), 50, 20, 0x13D6, 0)); + Add(new GenericBuyInfo(typeof(StuddedArms), 57, 20, 0x13DC, 0)); + Add(new GenericBuyInfo(typeof(StuddedChest), 75, 20, 0x13DB, 0)); + Add(new GenericBuyInfo(typeof(StuddedLegs), 67, 20, 0x13DA, 0)); + Add(new GenericBuyInfo(typeof(StuddedGloves), 45, 20, 0x13D5, 0)); - Add( new GenericBuyInfo( typeof( StuddedGorget ), 50, 20, 0x13D6, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedArms ), 57, 20, 0x13DC, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedChest ), 75, 20, 0x13DB, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedLegs ), 67, 20, 0x13DA, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedGloves ), 45, 20, 0x13D5, 0 ) ); + Add(new GenericBuyInfo(typeof(FemaleStuddedChest), 62, 20, 0x1C02, 0)); + Add(new GenericBuyInfo(typeof(FemalePlateChest), 207, 20, 0x1C04, 0)); + Add(new GenericBuyInfo(typeof(FemaleLeatherChest), 36, 20, 0x1C06, 0)); + Add(new GenericBuyInfo(typeof(LeatherShorts), 28, 20, 0x1C00, 0)); + Add(new GenericBuyInfo(typeof(LeatherSkirt), 25, 20, 0x1C08, 0)); + Add(new GenericBuyInfo(typeof(LeatherBustierArms), 25, 20, 0x1C0A, 0)); + Add(new GenericBuyInfo(typeof(LeatherBustierArms), 30, 20, 0x1C0B, 0)); + Add(new GenericBuyInfo(typeof(StuddedBustierArms), 50, 20, 0x1C0C, 0)); + Add(new GenericBuyInfo(typeof(StuddedBustierArms), 47, 20, 0x1C0D, 0)); - Add( new GenericBuyInfo( typeof( FemaleStuddedChest ), 62, 20, 0x1C02, 0 ) ); - Add( new GenericBuyInfo( typeof( FemalePlateChest ), 207, 20, 0x1C04, 0 ) ); - Add( new GenericBuyInfo( typeof( FemaleLeatherChest ), 36, 20, 0x1C06, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherShorts ), 28, 20, 0x1C00, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherSkirt ), 25, 20, 0x1C08, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherBustierArms ), 25, 20, 0x1C0A, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherBustierArms ), 30, 20, 0x1C0B, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedBustierArms ), 50, 20, 0x1C0C, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedBustierArms ), 47, 20, 0x1C0D, 0 ) ); + Add(new GenericBuyInfo(typeof(Bag), 6, 20, 0xE76, 0)); + Add(new GenericBuyInfo(typeof(Pouch), 6, 20, 0xE79, 0)); + Add(new GenericBuyInfo(typeof(Backpack), 15, 20, 0x9B2, 0)); + Add(new GenericBuyInfo(typeof(Leather), 6, 20, 0x1081, 0)); - Add( new GenericBuyInfo( typeof( Bag ), 6, 20, 0xE76, 0 ) ); - Add( new GenericBuyInfo( typeof( Pouch ), 6, 20, 0xE79, 0 ) ); - Add( new GenericBuyInfo( typeof( Backpack ), 15, 20, 0x9B2, 0 ) ); - Add( new GenericBuyInfo( typeof( Leather ), 6, 20, 0x1081, 0 ) ); + Add(new GenericBuyInfo(typeof(SkinningKnife), 15, 20, 0xEC4, 0)); - Add( new GenericBuyInfo( typeof( SkinningKnife ), 15, 20, 0xEC4, 0 ) ); + Add(new GenericBuyInfo("1041279", typeof(TaxidermyKit), 100000, 20, 0x1EBA, 0)); + } + } - Add( new GenericBuyInfo( "1041279", typeof( TaxidermyKit ), 100000, 20, 0x1EBA, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bag), 3); + Add(typeof(Pouch), 3); + Add(typeof(Backpack), 7); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bag ), 3 ); - Add( typeof( Pouch ), 3 ); - Add( typeof( Backpack ), 7 ); + Add(typeof(Leather), 5); - Add( typeof( Leather ), 5 ); + Add(typeof(SkinningKnife), 7); - Add( typeof( SkinningKnife ), 7 ); + Add(typeof(LeatherArms), 18); + Add(typeof(LeatherChest), 23); + Add(typeof(LeatherGloves), 15); + Add(typeof(LeatherGorget), 15); + Add(typeof(LeatherLegs), 18); + Add(typeof(LeatherCap), 5); - Add( typeof( LeatherArms ), 18 ); - Add( typeof( LeatherChest ), 23 ); - Add( typeof( LeatherGloves ), 15 ); - Add( typeof( LeatherGorget ), 15 ); - Add( typeof( LeatherLegs ), 18 ); - Add( typeof( LeatherCap ), 5 ); + Add(typeof(StuddedArms), 43); + Add(typeof(StuddedChest), 37); + Add(typeof(StuddedGloves), 39); + Add(typeof(StuddedGorget), 22); + Add(typeof(StuddedLegs), 33); - Add( typeof( StuddedArms ), 43 ); - Add( typeof( StuddedChest ), 37 ); - Add( typeof( StuddedGloves ), 39 ); - Add( typeof( StuddedGorget ), 22 ); - Add( typeof( StuddedLegs ), 33 ); - - Add( typeof( FemaleStuddedChest ), 31 ); - Add( typeof( StuddedBustierArms ), 23 ); - Add( typeof( FemalePlateChest), 103 ); - Add( typeof( FemaleLeatherChest ), 18 ); - Add( typeof( LeatherBustierArms ), 12 ); - Add( typeof( LeatherShorts ), 14 ); - Add( typeof( LeatherSkirt ), 12 ); - } - } - } -} + Add(typeof(FemaleStuddedChest), 31); + Add(typeof(StuddedBustierArms), 23); + Add(typeof(FemalePlateChest), 103); + Add(typeof(FemaleLeatherChest), 18); + Add(typeof(LeatherBustierArms), 12); + Add(typeof(LeatherShorts), 14); + Add(typeof(LeatherSkirt), 12); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBTavernKeeper.cs b/Scripts/Mobiles/Vendors/SBInfo/SBTavernKeeper.cs index f3c454865..30e5e1772 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBTavernKeeper.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBTavernKeeper.cs @@ -1,109 +1,106 @@ using System.Collections.Generic; using Server.Items; +using Server.Multis; namespace Server.Mobiles { - public class SBTavernKeeper : SBInfo - { - public SBTavernKeeper() - { - } + public class SBTavernKeeper : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Ale, 7, 20, 0x99F, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Wine, 7, 20, 0x9C7, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Liquor, 7, 20, 0x99B, 0)); + Add(new BeverageBuyInfo(typeof(Jug), BeverageType.Cider, 13, 20, 0x9C8, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Milk, 7, 20, 0x9F0, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Ale, 11, 20, 0x1F95, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Cider, 11, 20, 0x1F97, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Liquor, 11, 20, 0x1F99, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Wine, 11, 20, 0x1F9B, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Water, 11, 20, 0x1F9D, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Ale, 7, 20, 0x99F, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Wine, 7, 20, 0x9C7, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Liquor, 7, 20, 0x99B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Jug ), BeverageType.Cider, 13, 20, 0x9C8, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Milk, 7, 20, 0x9F0, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Ale, 11, 20, 0x1F95, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Cider, 11, 20, 0x1F97, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Liquor, 11, 20, 0x1F99, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Wine, 11, 20, 0x1F9B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Water, 11, 20, 0x1F9D, 0 ) ); + Add(new GenericBuyInfo(typeof(BreadLoaf), 6, 10, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(CheeseWheel), 21, 10, 0x97E, 0)); + Add(new GenericBuyInfo(typeof(CookedBird), 17, 20, 0x9B7, 0)); + Add(new GenericBuyInfo(typeof(LambLeg), 8, 20, 0x160A, 0)); + Add(new GenericBuyInfo(typeof(ChickenLeg), 5, 20, 0x1608, 0)); + Add(new GenericBuyInfo(typeof(Ribs), 7, 20, 0x9F2, 0)); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 6, 10, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( CheeseWheel ), 21, 10, 0x97E, 0 ) ); - Add( new GenericBuyInfo( typeof( CookedBird ), 17, 20, 0x9B7, 0 ) ); - Add( new GenericBuyInfo( typeof( LambLeg ), 8, 20, 0x160A, 0 ) ); - Add( new GenericBuyInfo( typeof( ChickenLeg ), 5, 20, 0x1608, 0 ) ); - Add( new GenericBuyInfo( typeof( Ribs ), 7, 20, 0x9F2, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCarrots), 3, 20, 0x15F9, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCorn), 3, 20, 0x15FA, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfLettuce), 3, 20, 0x15FB, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfPeas), 3, 20, 0x15FC, 0)); + Add(new GenericBuyInfo(typeof(EmptyPewterBowl), 2, 20, 0x15FD, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfCorn), 3, 20, 0x15FE, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfLettuce), 3, 20, 0x15FF, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPeas), 3, 20, 0x1600, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPotatos), 3, 20, 0x1601, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfStew), 3, 20, 0x1604, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfTomatoSoup), 3, 20, 0x1606, 0)); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCarrots ), 3, 20, 0x15F9, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCorn ), 3, 20, 0x15FA, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfLettuce ), 3, 20, 0x15FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfPeas ), 3, 20, 0x15FC, 0 ) ); - Add( new GenericBuyInfo( typeof( EmptyPewterBowl ), 2, 20, 0x15FD, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfCorn ), 3, 20, 0x15FE, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfLettuce ), 3, 20, 0x15FF, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPeas ), 3, 20, 0x1600, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPotatos ), 3, 20, 0x1601, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfStew ), 3, 20, 0x1604, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfTomatoSoup ), 3, 20, 0x1606, 0 ) ); + Add(new GenericBuyInfo(typeof(ApplePie), 7, 20, 0x1041, 0)); //OSI just has Pie, not Apple/Fruit/Meat - Add( new GenericBuyInfo( typeof( ApplePie ), 7, 20, 0x1041, 0 ) ); //OSI just has Pie, not Apple/Fruit/Meat + Add(new GenericBuyInfo("1016450", typeof(Chessboard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo("1016449", typeof(CheckerBoard), 2, 20, 0xFA6, 0)); + Add(new GenericBuyInfo(typeof(Backgammon), 2, 20, 0xE1C, 0)); + Add(new GenericBuyInfo(typeof(Dices), 2, 20, 0xFA7, 0)); + Add(new GenericBuyInfo("1041243", typeof(ContractOfEmployment), 1252, 20, 0x14F0, 0)); + Add(new GenericBuyInfo("a barkeep contract", typeof(BarkeepContract), 1252, 20, 0x14F0, 0)); - Add( new GenericBuyInfo( "1016450", typeof( Chessboard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( "1016449", typeof( CheckerBoard ), 2, 20, 0xFA6, 0 ) ); - Add( new GenericBuyInfo( typeof( Backgammon ), 2, 20, 0xE1C, 0 ) ); - Add( new GenericBuyInfo( typeof( Dices ), 2, 20, 0xFA7, 0 ) ); - Add( new GenericBuyInfo( "1041243", typeof( ContractOfEmployment ), 1252, 20, 0x14F0, 0 ) ); - Add( new GenericBuyInfo( "a barkeep contract", typeof( BarkeepContract ), 1252, 20, 0x14F0, 0 ) ); + if (BaseHouse.NewVendorSystem) + Add(new GenericBuyInfo("1062332", typeof(VendorRentalContract), 1252, 20, 0x14F0, 0x672)); - if ( Multis.BaseHouse.NewVendorSystem ) - Add( new GenericBuyInfo( "1062332", typeof( VendorRentalContract ), 1252, 20, 0x14F0, 0x672 ) ); + /*if ( Map == Tokuno ) + { + Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E8, 0 ) ); + Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E9, 0 ) ); + Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2836, 0 ) ); + Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2837, 0 ) ); + Add( new GenericBuyInfo( typeof( GreenTeaBasket ), 2, 20, 0x284B, 0 ) ); + }*/ + } + } - /*if ( Map == Tokuno ) - { - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E8, 0 ) ); - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E9, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2836, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2837, 0 ) ); - Add( new GenericBuyInfo( typeof( GreenTeaBasket ), 2, 20, 0x284B, 0 ) ); - }*/ - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( WoodenBowlOfCarrots ), 1 ); - Add( typeof( WoodenBowlOfCorn ), 1 ); - Add( typeof( WoodenBowlOfLettuce ), 1 ); - Add( typeof( WoodenBowlOfPeas ), 1 ); - Add( typeof( EmptyPewterBowl ), 1 ); - Add( typeof( PewterBowlOfCorn ), 1 ); - Add( typeof( PewterBowlOfLettuce ), 1 ); - Add( typeof( PewterBowlOfPeas ), 1 ); - Add( typeof( PewterBowlOfPotatos ), 1 ); - Add( typeof( WoodenBowlOfStew ), 1 ); - Add( typeof( WoodenBowlOfTomatoSoup ), 1 ); - Add( typeof( BeverageBottle ), 3 ); - Add( typeof( Jug ), 6 ); - Add( typeof( Pitcher ), 5 ); - Add( typeof( GlassMug ), 1 ); - Add( typeof( BreadLoaf ), 3 ); - Add( typeof( CheeseWheel ), 12 ); - Add( typeof( Ribs ), 6 ); - Add( typeof( Peach ), 1 ); - Add( typeof( Pear ), 1 ); - Add( typeof( Grapes ), 1 ); - Add( typeof( Apple ), 1 ); - Add( typeof( Banana ), 1 ); - Add( typeof( Candle ), 3 ); - Add( typeof( Chessboard ), 1 ); - Add( typeof( CheckerBoard ), 1 ); - Add( typeof( Backgammon ), 1 ); - Add( typeof( Dices ), 1 ); - Add( typeof( ContractOfEmployment ), 626 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(WoodenBowlOfCarrots), 1); + Add(typeof(WoodenBowlOfCorn), 1); + Add(typeof(WoodenBowlOfLettuce), 1); + Add(typeof(WoodenBowlOfPeas), 1); + Add(typeof(EmptyPewterBowl), 1); + Add(typeof(PewterBowlOfCorn), 1); + Add(typeof(PewterBowlOfLettuce), 1); + Add(typeof(PewterBowlOfPeas), 1); + Add(typeof(PewterBowlOfPotatos), 1); + Add(typeof(WoodenBowlOfStew), 1); + Add(typeof(WoodenBowlOfTomatoSoup), 1); + Add(typeof(BeverageBottle), 3); + Add(typeof(Jug), 6); + Add(typeof(Pitcher), 5); + Add(typeof(GlassMug), 1); + Add(typeof(BreadLoaf), 3); + Add(typeof(CheeseWheel), 12); + Add(typeof(Ribs), 6); + Add(typeof(Peach), 1); + Add(typeof(Pear), 1); + Add(typeof(Grapes), 1); + Add(typeof(Apple), 1); + Add(typeof(Banana), 1); + Add(typeof(Candle), 3); + Add(typeof(Chessboard), 1); + Add(typeof(CheckerBoard), 1); + Add(typeof(Backgammon), 1); + Add(typeof(Dices), 1); + Add(typeof(ContractOfEmployment), 626); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBThief.cs b/Scripts/Mobiles/Vendors/SBInfo/SBThief.cs index 375bbbc1d..6e74b1b09 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBThief.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBThief.cs @@ -3,45 +3,41 @@ using Server.Items; namespace Server.Mobiles { - public class SBThief : SBInfo - { - public SBThief() - { - } + public class SBThief : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Backpack), 15, 20, 0x9B2, 0)); + Add(new GenericBuyInfo(typeof(Pouch), 6, 20, 0xE79, 0)); + Add(new GenericBuyInfo(typeof(Torch), 8, 20, 0xF6B, 0)); + Add(new GenericBuyInfo(typeof(Lantern), 2, 20, 0xA25, 0)); + //Add( new GenericBuyInfo( typeof( OilFlask ), 8, 20, 0x####, 0 ) ); + Add(new GenericBuyInfo(typeof(Lockpick), 12, 20, 0x14FC, 0)); + Add(new GenericBuyInfo(typeof(WoodenBox), 14, 20, 0x9AA, 0)); + Add(new GenericBuyInfo(typeof(Key), 2, 20, 0x100E, 0)); + Add(new GenericBuyInfo(typeof(HairDye), 37, 20, 0xEFF, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Backpack ), 15, 20, 0x9B2, 0 ) ); - Add( new GenericBuyInfo( typeof( Pouch ), 6, 20, 0xE79, 0 ) ); - Add( new GenericBuyInfo( typeof( Torch ), 8, 20, 0xF6B, 0 ) ); - Add( new GenericBuyInfo( typeof( Lantern ), 2, 20, 0xA25, 0 ) ); - //Add( new GenericBuyInfo( typeof( OilFlask ), 8, 20, 0x####, 0 ) ); - Add( new GenericBuyInfo( typeof( Lockpick ), 12, 20, 0x14FC, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBox ), 14, 20, 0x9AA, 0 ) ); - Add( new GenericBuyInfo( typeof( Key ), 2, 20, 0x100E, 0 ) ); - Add( new GenericBuyInfo( typeof( HairDye ), 37, 20, 0xEFF, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Backpack ), 7 ); - Add( typeof( Pouch ), 3 ); - Add( typeof( Torch ), 3 ); - Add( typeof( Lantern ), 1 ); - //Add( typeof( OilFlask ), 4 ); - Add( typeof( Lockpick ), 6 ); - Add( typeof( WoodenBox ), 7 ); - Add( typeof( HairDye ), 19 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Backpack), 7); + Add(typeof(Pouch), 3); + Add(typeof(Torch), 3); + Add(typeof(Lantern), 1); + //Add( typeof( OilFlask ), 4 ); + Add(typeof(Lockpick), 6); + Add(typeof(WoodenBox), 7); + Add(typeof(HairDye), 19); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBTinker.cs b/Scripts/Mobiles/Vendors/SBInfo/SBTinker.cs index 96dc8fccf..98d81172b 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBTinker.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBTinker.cs @@ -3,125 +3,121 @@ using Server.Items; namespace Server.Mobiles { - public class SBTinker: SBInfo - { - public SBTinker() - { - } + public class SBTinker : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Clock), 22, 20, 0x104B, 0)); + Add(new GenericBuyInfo(typeof(Nails), 3, 20, 0x102E, 0)); + Add(new GenericBuyInfo(typeof(ClockParts), 3, 20, 0x104F, 0)); + Add(new GenericBuyInfo(typeof(AxleGears), 3, 20, 0x1051, 0)); + Add(new GenericBuyInfo(typeof(Gears), 2, 20, 0x1053, 0)); + Add(new GenericBuyInfo(typeof(Hinge), 2, 20, 0x1055, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Clock ), 22, 20, 0x104B, 0 ) ); - Add( new GenericBuyInfo( typeof( Nails ), 3, 20, 0x102E, 0 ) ); - Add( new GenericBuyInfo( typeof( ClockParts ), 3, 20, 0x104F, 0 ) ); - Add( new GenericBuyInfo( typeof( AxleGears ), 3, 20, 0x1051, 0 ) ); - Add( new GenericBuyInfo( typeof( Gears ), 2, 20, 0x1053, 0 ) ); - Add( new GenericBuyInfo( typeof( Hinge ), 2, 20, 0x1055, 0 ) ); + Add(new GenericBuyInfo(typeof(Sextant), 13, 20, 0x1057, 0)); + Add(new GenericBuyInfo(typeof(SextantParts), 5, 20, 0x1059, 0)); + Add(new GenericBuyInfo(typeof(Axle), 2, 20, 0x105B, 0)); + Add(new GenericBuyInfo(typeof(Springs), 3, 20, 0x105D, 0)); - Add( new GenericBuyInfo( typeof( Sextant ), 13, 20, 0x1057, 0 ) ); - Add( new GenericBuyInfo( typeof( SextantParts ), 5, 20, 0x1059, 0 ) ); - Add( new GenericBuyInfo( typeof( Axle ), 2, 20, 0x105B, 0 ) ); - Add( new GenericBuyInfo( typeof( Springs ), 3, 20, 0x105D, 0 ) ); + Add(new GenericBuyInfo("1024111", typeof(Key), 8, 20, 0x100F, 0)); + Add(new GenericBuyInfo("1024112", typeof(Key), 8, 20, 0x1010, 0)); + Add(new GenericBuyInfo("1024115", typeof(Key), 8, 20, 0x1013, 0)); + Add(new GenericBuyInfo(typeof(KeyRing), 8, 20, 0x1010, 0)); + Add(new GenericBuyInfo(typeof(Lockpick), 12, 20, 0x14FC, 0)); - Add( new GenericBuyInfo( "1024111", typeof( Key ), 8, 20, 0x100F, 0 ) ); - Add( new GenericBuyInfo( "1024112", typeof( Key ), 8, 20, 0x1010, 0 ) ); - Add( new GenericBuyInfo( "1024115", typeof( Key ), 8, 20, 0x1013, 0 ) ); - Add( new GenericBuyInfo( typeof( KeyRing ), 8, 20, 0x1010, 0 ) ); - Add( new GenericBuyInfo( typeof( Lockpick ), 12, 20, 0x14FC, 0 ) ); + Add(new GenericBuyInfo(typeof(TinkersTools), 7, 20, 0x1EBC, 0)); + Add(new GenericBuyInfo(typeof(Board), 3, 20, 0x1BD7, 0)); + Add(new GenericBuyInfo(typeof(IronIngot), 5, 16, 0x1BF2, 0)); + Add(new GenericBuyInfo(typeof(SewingKit), 3, 20, 0xF9D, 0)); - Add( new GenericBuyInfo( typeof( TinkersTools ), 7, 20, 0x1EBC, 0 ) ); - Add( new GenericBuyInfo( typeof( Board ), 3, 20, 0x1BD7, 0 ) ); - Add( new GenericBuyInfo( typeof( IronIngot ), 5, 16, 0x1BF2, 0 ) ); - Add( new GenericBuyInfo( typeof( SewingKit ), 3, 20, 0xF9D, 0 ) ); + Add(new GenericBuyInfo(typeof(DrawKnife), 10, 20, 0x10E4, 0)); + Add(new GenericBuyInfo(typeof(Froe), 10, 20, 0x10E5, 0)); + Add(new GenericBuyInfo(typeof(Scorp), 10, 20, 0x10E7, 0)); + Add(new GenericBuyInfo(typeof(Inshave), 10, 20, 0x10E6, 0)); - Add( new GenericBuyInfo( typeof( DrawKnife ), 10, 20, 0x10E4, 0 ) ); - Add( new GenericBuyInfo( typeof( Froe ), 10, 20, 0x10E5, 0 ) ); - Add( new GenericBuyInfo( typeof( Scorp ), 10, 20, 0x10E7, 0 ) ); - Add( new GenericBuyInfo( typeof( Inshave ), 10, 20, 0x10E6, 0 ) ); + Add(new GenericBuyInfo(typeof(ButcherKnife), 13, 20, 0x13F6, 0)); - Add( new GenericBuyInfo( typeof( ButcherKnife ), 13, 20, 0x13F6, 0 ) ); + Add(new GenericBuyInfo(typeof(Scissors), 11, 20, 0xF9F, 0)); - Add( new GenericBuyInfo( typeof( Scissors ), 11, 20, 0xF9F, 0 ) ); + Add(new GenericBuyInfo(typeof(Tongs), 13, 14, 0xFBB, 0)); - Add( new GenericBuyInfo( typeof( Tongs ), 13, 14, 0xFBB, 0 ) ); + Add(new GenericBuyInfo(typeof(DovetailSaw), 12, 20, 0x1028, 0)); + Add(new GenericBuyInfo(typeof(Saw), 15, 20, 0x1034, 0)); - Add( new GenericBuyInfo( typeof( DovetailSaw ), 12, 20, 0x1028, 0 ) ); - Add( new GenericBuyInfo( typeof( Saw ), 15, 20, 0x1034, 0 ) ); + Add(new GenericBuyInfo(typeof(Hammer), 17, 20, 0x102A, 0)); + Add(new GenericBuyInfo(typeof(SmithHammer), 23, 20, 0x13E3, 0)); + // TODO: Sledgehammer - Add( new GenericBuyInfo( typeof( Hammer ), 17, 20, 0x102A, 0 ) ); - Add( new GenericBuyInfo( typeof( SmithHammer ), 23, 20, 0x13E3, 0 ) ); - // TODO: Sledgehammer + Add(new GenericBuyInfo(typeof(Shovel), 12, 20, 0xF39, 0)); - Add( new GenericBuyInfo( typeof( Shovel ), 12, 20, 0xF39, 0 ) ); + Add(new GenericBuyInfo(typeof(MouldingPlane), 11, 20, 0x102C, 0)); + Add(new GenericBuyInfo(typeof(JointingPlane), 10, 20, 0x1030, 0)); + Add(new GenericBuyInfo(typeof(SmoothingPlane), 11, 20, 0x1032, 0)); - Add( new GenericBuyInfo( typeof( MouldingPlane ), 11, 20, 0x102C, 0 ) ); - Add( new GenericBuyInfo( typeof( JointingPlane ), 10, 20, 0x1030, 0 ) ); - Add( new GenericBuyInfo( typeof( SmoothingPlane ), 11, 20, 0x1032, 0 ) ); - - Add( new GenericBuyInfo( typeof( Pickaxe ), 25, 20, 0xE86, 0 ) ); + Add(new GenericBuyInfo(typeof(Pickaxe), 25, 20, 0xE86, 0)); - Add( new GenericBuyInfo( typeof( Drums ), 21, 20, 0x0E9C, 0 ) ); - Add( new GenericBuyInfo( typeof( Tambourine ), 21, 20, 0x0E9E, 0 ) ); - Add( new GenericBuyInfo( typeof( LapHarp ), 21, 20, 0x0EB2, 0 ) ); - Add( new GenericBuyInfo( typeof( Lute ), 21, 20, 0x0EB3, 0 ) ); - } - } + Add(new GenericBuyInfo(typeof(Drums), 21, 20, 0x0E9C, 0)); + Add(new GenericBuyInfo(typeof(Tambourine), 21, 20, 0x0E9E, 0)); + Add(new GenericBuyInfo(typeof(LapHarp), 21, 20, 0x0EB2, 0)); + Add(new GenericBuyInfo(typeof(Lute), 21, 20, 0x0EB3, 0)); + } + } - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Drums ), 10 ); - Add( typeof( Tambourine ), 10 ); - Add( typeof( LapHarp ), 10 ); - Add( typeof( Lute ), 10 ); + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Drums), 10); + Add(typeof(Tambourine), 10); + Add(typeof(LapHarp), 10); + Add(typeof(Lute), 10); - Add( typeof( Shovel ), 6 ); - Add( typeof( SewingKit ), 1 ); - Add( typeof( Scissors ), 6 ); - Add( typeof( Tongs ), 7 ); - Add( typeof( Key ), 1 ); + Add(typeof(Shovel), 6); + Add(typeof(SewingKit), 1); + Add(typeof(Scissors), 6); + Add(typeof(Tongs), 7); + Add(typeof(Key), 1); - Add( typeof( DovetailSaw ), 6 ); - Add( typeof( MouldingPlane ), 6 ); - Add( typeof( Nails ), 1 ); - Add( typeof( JointingPlane ), 6 ); - Add( typeof( SmoothingPlane ), 6 ); - Add( typeof( Saw ), 7 ); + Add(typeof(DovetailSaw), 6); + Add(typeof(MouldingPlane), 6); + Add(typeof(Nails), 1); + Add(typeof(JointingPlane), 6); + Add(typeof(SmoothingPlane), 6); + Add(typeof(Saw), 7); - Add( typeof( Clock ), 11 ); - Add( typeof( ClockParts ), 1 ); - Add( typeof( AxleGears ), 1 ); - Add( typeof( Gears ), 1 ); - Add( typeof( Hinge ), 1 ); - Add( typeof( Sextant ), 6 ); - Add( typeof( SextantParts ), 2 ); - Add( typeof( Axle ), 1 ); - Add( typeof( Springs ), 1 ); + Add(typeof(Clock), 11); + Add(typeof(ClockParts), 1); + Add(typeof(AxleGears), 1); + Add(typeof(Gears), 1); + Add(typeof(Hinge), 1); + Add(typeof(Sextant), 6); + Add(typeof(SextantParts), 2); + Add(typeof(Axle), 1); + Add(typeof(Springs), 1); - Add( typeof( DrawKnife ), 5 ); - Add( typeof( Froe ), 5 ); - Add( typeof( Inshave ), 5 ); - Add( typeof( Scorp ), 5 ); + Add(typeof(DrawKnife), 5); + Add(typeof(Froe), 5); + Add(typeof(Inshave), 5); + Add(typeof(Scorp), 5); - Add( typeof( Lockpick ), 6 ); - Add( typeof( TinkerTools ), 3 ); + Add(typeof(Lockpick), 6); + Add(typeof(TinkerTools), 3); - Add( typeof( Board ), 1 ); - Add( typeof( Log ), 1 ); + Add(typeof(Board), 1); + Add(typeof(Log), 1); - Add( typeof( Pickaxe ), 16 ); - Add( typeof( Hammer ), 3 ); - Add( typeof( SmithHammer ), 11 ); - Add( typeof( ButcherKnife ), 6 ); - } - } - } -} + Add(typeof(Pickaxe), 16); + Add(typeof(Hammer), 3); + Add(typeof(SmithHammer), 11); + Add(typeof(ButcherKnife), 6); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBVagabond.cs b/Scripts/Mobiles/Vendors/SBInfo/SBVagabond.cs index 4bc39b2bc..73881b51c 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBVagabond.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBVagabond.cs @@ -3,72 +3,68 @@ using Server.Items; namespace Server.Mobiles { - public class SBVagabond : SBInfo - { - public SBVagabond() - { - } + public class SBVagabond : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(GoldRing), 27, 20, 0x108A, 0)); + Add(new GenericBuyInfo(typeof(Necklace), 26, 20, 0x1085, 0)); + Add(new GenericBuyInfo(typeof(GoldNecklace), 27, 20, 0x1088, 0)); + Add(new GenericBuyInfo(typeof(GoldBeadNecklace), 27, 20, 0x1089, 0)); + Add(new GenericBuyInfo(typeof(Beads), 27, 20, 0x108B, 0)); + Add(new GenericBuyInfo(typeof(GoldBracelet), 27, 20, 0x1086, 0)); + Add(new GenericBuyInfo(typeof(GoldEarrings), 27, 20, 0x1087, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( GoldRing ), 27, 20, 0x108A, 0 ) ); - Add( new GenericBuyInfo( typeof( Necklace ), 26, 20, 0x1085, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldNecklace ), 27, 20, 0x1088, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldBeadNecklace ), 27, 20, 0x1089, 0 ) ); - Add( new GenericBuyInfo( typeof( Beads ), 27, 20, 0x108B, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldBracelet ), 27, 20, 0x1086, 0 ) ); - Add( new GenericBuyInfo( typeof( GoldEarrings ), 27, 20, 0x1087, 0 ) ); + Add(new GenericBuyInfo(typeof(Board), 3, 20, 0x1BD7, 0)); + Add(new GenericBuyInfo(typeof(IronIngot), 6, 20, 0x1BF2, 0)); - Add( new GenericBuyInfo( typeof( Board ), 3, 20, 0x1BD7, 0 ) ); - Add( new GenericBuyInfo( typeof( IronIngot ), 6, 20, 0x1BF2, 0 ) ); + Add(new GenericBuyInfo(typeof(StarSapphire), 125, 20, 0xF21, 0)); + Add(new GenericBuyInfo(typeof(Emerald), 100, 20, 0xF10, 0)); + Add(new GenericBuyInfo(typeof(Sapphire), 100, 20, 0xF19, 0)); + Add(new GenericBuyInfo(typeof(Ruby), 75, 20, 0xF13, 0)); + Add(new GenericBuyInfo(typeof(Citrine), 50, 20, 0xF15, 0)); + Add(new GenericBuyInfo(typeof(Amethyst), 100, 20, 0xF16, 0)); + Add(new GenericBuyInfo(typeof(Tourmaline), 75, 20, 0xF2D, 0)); + Add(new GenericBuyInfo(typeof(Amber), 50, 20, 0xF25, 0)); + Add(new GenericBuyInfo(typeof(Diamond), 200, 20, 0xF26, 0)); + } + } - Add( new GenericBuyInfo( typeof( StarSapphire ), 125, 20, 0xF21, 0 ) ); - Add( new GenericBuyInfo( typeof( Emerald ), 100, 20, 0xF10, 0 ) ); - Add( new GenericBuyInfo( typeof( Sapphire ), 100, 20, 0xF19, 0 ) ); - Add( new GenericBuyInfo( typeof( Ruby ), 75, 20, 0xF13, 0 ) ); - Add( new GenericBuyInfo( typeof( Citrine ), 50, 20, 0xF15, 0 ) ); - Add( new GenericBuyInfo( typeof( Amethyst ), 100, 20, 0xF16, 0 ) ); - Add( new GenericBuyInfo( typeof( Tourmaline ), 75, 20, 0xF2D, 0 ) ); - Add( new GenericBuyInfo( typeof( Amber ), 50, 20, 0xF25, 0 ) ); - Add( new GenericBuyInfo( typeof( Diamond ), 200, 20, 0xF26, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Board), 1); + Add(typeof(IronIngot), 3); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Board ), 1 ); - Add( typeof( IronIngot ), 3 ); - - Add( typeof( Amber ), 25 ); - Add( typeof( Amethyst ), 50 ); - Add( typeof( Citrine ), 25 ); - Add( typeof( Diamond ), 100 ); - Add( typeof( Emerald ), 50 ); - Add( typeof( Ruby ), 37 ); - Add( typeof( Sapphire ), 50 ); - Add( typeof( StarSapphire ), 62 ); - Add( typeof( Tourmaline ), 47 ); - Add( typeof( GoldRing ), 13 ); - Add( typeof( SilverRing ), 10 ); - Add( typeof( Necklace ), 13 ); - Add( typeof( GoldNecklace ), 13 ); - Add( typeof( GoldBeadNecklace ), 13 ); - Add( typeof( SilverNecklace ), 10 ); - Add( typeof( SilverBeadNecklace ), 10 ); - Add( typeof( Beads ), 13 ); - Add( typeof( GoldBracelet ), 13 ); - Add( typeof( SilverBracelet ), 10 ); - Add( typeof( GoldEarrings ), 13 ); - Add( typeof( SilverEarrings ), 10 ); - } - } - } -} + Add(typeof(Amber), 25); + Add(typeof(Amethyst), 50); + Add(typeof(Citrine), 25); + Add(typeof(Diamond), 100); + Add(typeof(Emerald), 50); + Add(typeof(Ruby), 37); + Add(typeof(Sapphire), 50); + Add(typeof(StarSapphire), 62); + Add(typeof(Tourmaline), 47); + Add(typeof(GoldRing), 13); + Add(typeof(SilverRing), 10); + Add(typeof(Necklace), 13); + Add(typeof(GoldNecklace), 13); + Add(typeof(GoldBeadNecklace), 13); + Add(typeof(SilverNecklace), 10); + Add(typeof(SilverBeadNecklace), 10); + Add(typeof(Beads), 13); + Add(typeof(GoldBracelet), 13); + Add(typeof(SilverBracelet), 10); + Add(typeof(GoldEarrings), 13); + Add(typeof(SilverEarrings), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBVarietyDealer.cs b/Scripts/Mobiles/Vendors/SBInfo/SBVarietyDealer.cs index d295347b6..2cb6e18f4 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBVarietyDealer.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBVarietyDealer.cs @@ -4,131 +4,127 @@ using Server.Items; namespace Server.Mobiles { - public class SBVarietyDealer : SBInfo - { - public SBVarietyDealer() - { - } + public class SBVarietyDealer : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bandage), 5, 20, 0xE21, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bandage ), 5, 20, 0xE21, 0 ) ); + Add(new GenericBuyInfo(typeof(BlankScroll), 5, 999, 0x0E34, 0)); - Add( new GenericBuyInfo( typeof( BlankScroll ), 5, 999, 0x0E34, 0 ) ); + Add(new GenericBuyInfo(typeof(NightSightPotion), 15, 10, 0xF06, 0)); + Add(new GenericBuyInfo(typeof(AgilityPotion), 15, 10, 0xF08, 0)); + Add(new GenericBuyInfo(typeof(StrengthPotion), 15, 10, 0xF09, 0)); + Add(new GenericBuyInfo(typeof(RefreshPotion), 15, 10, 0xF0B, 0)); + Add(new GenericBuyInfo(typeof(LesserCurePotion), 15, 10, 0xF07, 0)); + Add(new GenericBuyInfo(typeof(LesserHealPotion), 15, 10, 0xF0C, 0)); + Add(new GenericBuyInfo(typeof(LesserPoisonPotion), 15, 10, 0xF0A, 0)); + Add(new GenericBuyInfo(typeof(LesserExplosionPotion), 21, 10, 0xF0D, 0)); - Add( new GenericBuyInfo( typeof( NightSightPotion ), 15, 10, 0xF06, 0 ) ); - Add( new GenericBuyInfo( typeof( AgilityPotion ), 15, 10, 0xF08, 0 ) ); - Add( new GenericBuyInfo( typeof( StrengthPotion ), 15, 10, 0xF09, 0 ) ); - Add( new GenericBuyInfo( typeof( RefreshPotion ), 15, 10, 0xF0B, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserCurePotion ), 15, 10, 0xF07, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserHealPotion ), 15, 10, 0xF0C, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserPoisonPotion ), 15, 10, 0xF0A, 0 ) ); - Add( new GenericBuyInfo( typeof( LesserExplosionPotion ), 21, 10, 0xF0D, 0 ) ); + Add(new GenericBuyInfo(typeof(Bolt), 6, Utility.Random(30, 60), 0x1BFB, 0)); + Add(new GenericBuyInfo(typeof(Arrow), 3, Utility.Random(30, 60), 0xF3F, 0)); - Add( new GenericBuyInfo( typeof( Bolt ), 6, Utility.Random( 30, 60 ), 0x1BFB, 0 ) ); - Add( new GenericBuyInfo( typeof( Arrow ), 3, Utility.Random( 30, 60 ), 0xF3F, 0 ) ); + Add(new GenericBuyInfo(typeof(BlackPearl), 5, 999, 0xF7A, 0)); + Add(new GenericBuyInfo(typeof(Bloodmoss), 5, 999, 0xF7B, 0)); + Add(new GenericBuyInfo(typeof(MandrakeRoot), 3, 999, 0xF86, 0)); + Add(new GenericBuyInfo(typeof(Garlic), 3, 999, 0xF84, 0)); + Add(new GenericBuyInfo(typeof(Ginseng), 3, 999, 0xF85, 0)); + Add(new GenericBuyInfo(typeof(Nightshade), 3, 999, 0xF88, 0)); + Add(new GenericBuyInfo(typeof(SpidersSilk), 3, 999, 0xF8D, 0)); + Add(new GenericBuyInfo(typeof(SulfurousAsh), 3, 999, 0xF8C, 0)); - Add( new GenericBuyInfo( typeof( BlackPearl ), 5, 999, 0xF7A, 0 ) ); - Add( new GenericBuyInfo( typeof( Bloodmoss ), 5, 999, 0xF7B, 0 ) ); - Add( new GenericBuyInfo( typeof( MandrakeRoot ), 3, 999, 0xF86, 0 ) ); - Add( new GenericBuyInfo( typeof( Garlic ), 3, 999, 0xF84, 0 ) ); - Add( new GenericBuyInfo( typeof( Ginseng ), 3, 999, 0xF85, 0 ) ); - Add( new GenericBuyInfo( typeof( Nightshade ), 3, 999, 0xF88, 0 ) ); - Add( new GenericBuyInfo( typeof( SpidersSilk ), 3, 999, 0xF8D, 0 ) ); - Add( new GenericBuyInfo( typeof( SulfurousAsh ), 3, 999, 0xF8C, 0 ) ); + Add(new GenericBuyInfo(typeof(BreadLoaf), 7, 10, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(Backpack), 15, 20, 0x9B2, 0)); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 7, 10, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( Backpack ), 15, 20, 0x9B2, 0 ) ); + Type[] types = Loot.RegularScrollTypes; - Type[] types = Loot.RegularScrollTypes; + int circles = 3; - int circles = 3; + for (int i = 0; i < circles * 8 && i < types.Length; ++i) + { + int itemID = 0x1F2E + i; - for ( int i = 0; i < circles*8 && i < types.Length; ++i ) - { - int itemID = 0x1F2E + i; + if (i == 6) + itemID = 0x1F2D; + else if (i > 6) + --itemID; - if ( i == 6 ) - itemID = 0x1F2D; - else if ( i > 6 ) - --itemID; + Add(new GenericBuyInfo(types[i], 12 + i / 8 * 10, 20, itemID, 0)); + } - Add( new GenericBuyInfo( types[i], 12 + ((i / 8) * 10), 20, itemID, 0 ) ); - } + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(BatWing), 3, 999, 0xF78, 0)); + Add(new GenericBuyInfo(typeof(GraveDust), 3, 999, 0xF8F, 0)); + Add(new GenericBuyInfo(typeof(DaemonBlood), 6, 999, 0xF7D, 0)); + Add(new GenericBuyInfo(typeof(NoxCrystal), 6, 999, 0xF8E, 0)); + Add(new GenericBuyInfo(typeof(PigIron), 5, 999, 0xF8A, 0)); - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( BatWing ), 3, 999, 0xF78, 0 ) ); - Add( new GenericBuyInfo( typeof( GraveDust ), 3, 999, 0xF8F, 0 ) ); - Add( new GenericBuyInfo( typeof( DaemonBlood ), 6, 999, 0xF7D, 0 ) ); - Add( new GenericBuyInfo( typeof( NoxCrystal ), 6, 999, 0xF8E, 0 ) ); - Add( new GenericBuyInfo( typeof( PigIron ), 5, 999, 0xF8A, 0 ) ); + Add(new GenericBuyInfo(typeof(NecromancerSpellbook), 115, 10, 0x2253, 0)); + } - Add( new GenericBuyInfo( typeof( NecromancerSpellbook ), 115, 10, 0x2253, 0 ) ); - } + Add(new GenericBuyInfo(typeof(RecallRune), 15, 10, 0x1f14, 0)); + Add(new GenericBuyInfo(typeof(Spellbook), 18, 10, 0xEFA, 0)); - Add( new GenericBuyInfo( typeof( RecallRune ), 15, 10, 0x1f14, 0 ) ); - Add( new GenericBuyInfo( typeof( Spellbook ), 18, 10, 0xEFA, 0 ) ); + Add(new GenericBuyInfo("1041072", typeof(MagicWizardsHat), 11, 10, 0x1718, 0)); + } + } - Add( new GenericBuyInfo( "1041072", typeof( MagicWizardsHat ), 11, 10, 0x1718, 0 ) ); - } - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bandage), 1); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bandage ), 1 ); + Add(typeof(BlankScroll), 3); - Add( typeof( BlankScroll ), 3 ); + Add(typeof(NightSightPotion), 7); + Add(typeof(AgilityPotion), 7); + Add(typeof(StrengthPotion), 7); + Add(typeof(RefreshPotion), 7); + Add(typeof(LesserCurePotion), 7); + Add(typeof(LesserHealPotion), 7); + Add(typeof(LesserPoisonPotion), 7); + Add(typeof(LesserExplosionPotion), 10); - Add( typeof( NightSightPotion ), 7 ); - Add( typeof( AgilityPotion ), 7 ); - Add( typeof( StrengthPotion ), 7 ); - Add( typeof( RefreshPotion ), 7 ); - Add( typeof( LesserCurePotion ), 7 ); - Add( typeof( LesserHealPotion ), 7 ); - Add( typeof( LesserPoisonPotion ), 7 ); - Add( typeof( LesserExplosionPotion ), 10 ); + Add(typeof(Bolt), 3); + Add(typeof(Arrow), 2); - Add( typeof( Bolt ), 3 ); - Add( typeof( Arrow ), 2 ); + Add(typeof(BlackPearl), 3); + Add(typeof(Bloodmoss), 3); + Add(typeof(MandrakeRoot), 2); + Add(typeof(Garlic), 2); + Add(typeof(Ginseng), 2); + Add(typeof(Nightshade), 2); + Add(typeof(SpidersSilk), 2); + Add(typeof(SulfurousAsh), 2); - Add( typeof( BlackPearl ), 3 ); - Add( typeof( Bloodmoss ), 3 ); - Add( typeof( MandrakeRoot ), 2 ); - Add( typeof( Garlic ), 2 ); - Add( typeof( Ginseng ), 2 ); - Add( typeof( Nightshade ), 2 ); - Add( typeof( SpidersSilk ), 2 ); - Add( typeof( SulfurousAsh ), 2 ); + Add(typeof(BreadLoaf), 3); + Add(typeof(Backpack), 7); + Add(typeof(RecallRune), 8); + Add(typeof(Spellbook), 9); + Add(typeof(BlankScroll), 3); - Add( typeof( BreadLoaf ), 3 ); - Add( typeof( Backpack ), 7 ); - Add( typeof( RecallRune ), 8 ); - Add( typeof( Spellbook ), 9 ); - Add( typeof( BlankScroll ), 3 ); + if (Core.AOS) + { + Add(typeof(BatWing), 2); + Add(typeof(GraveDust), 2); + Add(typeof(DaemonBlood), 3); + Add(typeof(NoxCrystal), 3); + Add(typeof(PigIron), 3); + } - if ( Core.AOS ) - { - Add( typeof( BatWing ), 2 ); - Add( typeof( GraveDust ), 2 ); - Add( typeof( DaemonBlood ), 3 ); - Add( typeof( NoxCrystal ), 3 ); - Add( typeof( PigIron ), 3 ); - } + Type[] types = Loot.RegularScrollTypes; - Type[] types = Loot.RegularScrollTypes; - - for ( int i = 0; i < types.Length; ++i ) - Add( types[i], ((i / 8) + 2) * 5 ); - } - } - } -} + for (int i = 0; i < types.Length; ++i) + Add(types[i], (i / 8 + 2) * 5); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBVeterinarian.cs b/Scripts/Mobiles/Vendors/SBInfo/SBVeterinarian.cs index 8d05e974b..a1735f8e3 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBVeterinarian.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBVeterinarian.cs @@ -3,34 +3,30 @@ using Server.Items; namespace Server.Mobiles { - public class SBVeterinarian : SBInfo - { - public SBVeterinarian() - { - } + public class SBVeterinarian : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bandage), 6, 20, 0xE21, 0)); + Add(new AnimalBuyInfo(1, typeof(PackHorse), 616, 10, 291, 0)); + Add(new AnimalBuyInfo(1, typeof(PackLlama), 523, 10, 292, 0)); + Add(new AnimalBuyInfo(1, typeof(Dog), 158, 10, 217, 0)); + Add(new AnimalBuyInfo(1, typeof(Cat), 131, 10, 201, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bandage ), 6, 20, 0xE21, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( PackHorse ), 616, 10, 291, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( PackLlama ), 523, 10, 292, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Dog ), 158, 10, 217, 0 ) ); - Add( new AnimalBuyInfo( 1, typeof( Cat ), 131, 10, 201, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bandage ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bandage), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBWaiter.cs b/Scripts/Mobiles/Vendors/SBInfo/SBWaiter.cs index adfcbb1ca..f6f2f0a8e 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBWaiter.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBWaiter.cs @@ -3,58 +3,50 @@ using Server.Items; namespace Server.Mobiles { - public class SBWaiter : SBInfo - { - public SBWaiter() - { - } + public class SBWaiter : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Ale, 7, 20, 0x99F, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Wine, 7, 20, 0x9C7, 0)); + Add(new BeverageBuyInfo(typeof(BeverageBottle), BeverageType.Liquor, 7, 20, 0x99B, 0)); + Add(new BeverageBuyInfo(typeof(Jug), BeverageType.Cider, 13, 20, 0x9C8, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Milk, 7, 20, 0x9F0, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Ale, 11, 20, 0x1F95, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Cider, 11, 20, 0x1F97, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Liquor, 11, 20, 0x1F99, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Wine, 11, 20, 0x1F9B, 0)); + Add(new BeverageBuyInfo(typeof(Pitcher), BeverageType.Water, 11, 20, 0x1F9D, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Ale, 7, 20, 0x99F, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Wine, 7, 20, 0x9C7, 0 ) ); - Add( new BeverageBuyInfo( typeof( BeverageBottle ), BeverageType.Liquor, 7, 20, 0x99B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Jug ), BeverageType.Cider, 13, 20, 0x9C8, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Milk, 7, 20, 0x9F0, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Ale, 11, 20, 0x1F95, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Cider, 11, 20, 0x1F97, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Liquor, 11, 20, 0x1F99, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Wine, 11, 20, 0x1F9B, 0 ) ); - Add( new BeverageBuyInfo( typeof( Pitcher ), BeverageType.Water, 11, 20, 0x1F9D, 0 ) ); + Add(new GenericBuyInfo(typeof(BreadLoaf), 6, 10, 0x103B, 0)); + Add(new GenericBuyInfo(typeof(CheeseWheel), 21, 10, 0x97E, 0)); + Add(new GenericBuyInfo(typeof(CookedBird), 17, 20, 0x9B7, 0)); + Add(new GenericBuyInfo(typeof(LambLeg), 8, 20, 0x160A, 0)); - Add( new GenericBuyInfo( typeof( BreadLoaf ), 6, 10, 0x103B, 0 ) ); - Add( new GenericBuyInfo( typeof( CheeseWheel ), 21, 10, 0x97E, 0 ) ); - Add( new GenericBuyInfo( typeof( CookedBird ), 17, 20, 0x9B7, 0 ) ); - Add( new GenericBuyInfo( typeof( LambLeg ), 8, 20, 0x160A, 0 ) ); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCarrots), 3, 20, 0x15F9, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfCorn), 3, 20, 0x15FA, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfLettuce), 3, 20, 0x15FB, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfPeas), 3, 20, 0x15FC, 0)); + Add(new GenericBuyInfo(typeof(EmptyPewterBowl), 2, 20, 0x15FD, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfCorn), 3, 20, 0x15FE, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfLettuce), 3, 20, 0x15FF, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPeas), 3, 20, 0x1600, 0)); + Add(new GenericBuyInfo(typeof(PewterBowlOfPotatos), 3, 20, 0x1601, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfStew), 3, 20, 0x1604, 0)); + Add(new GenericBuyInfo(typeof(WoodenBowlOfTomatoSoup), 3, 20, 0x1606, 0)); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCarrots ), 3, 20, 0x15F9, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfCorn ), 3, 20, 0x15FA, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfLettuce ), 3, 20, 0x15FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfPeas ), 3, 20, 0x15FC, 0 ) ); - Add( new GenericBuyInfo( typeof( EmptyPewterBowl ), 2, 20, 0x15FD, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfCorn ), 3, 20, 0x15FE, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfLettuce ), 3, 20, 0x15FF, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPeas ), 3, 20, 0x1600, 0 ) ); - Add( new GenericBuyInfo( typeof( PewterBowlOfPotatos ), 3, 20, 0x1601, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfStew ), 3, 20, 0x1604, 0 ) ); - Add( new GenericBuyInfo( typeof( WoodenBowlOfTomatoSoup ), 3, 20, 0x1606, 0 ) ); + Add(new GenericBuyInfo(typeof(ApplePie), 7, 20, 0x1041, 0)); //OSI just has Pie, not Apple/Fruit/Meat + } + } - Add( new GenericBuyInfo( typeof( ApplePie ), 7, 20, 0x1041, 0 ) ); //OSI just has Pie, not Apple/Fruit/Meat - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBWeaponSmith.cs b/Scripts/Mobiles/Vendors/SBInfo/SBWeaponSmith.cs index ffc56ba94..12639b278 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBWeaponSmith.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBWeaponSmith.cs @@ -3,177 +3,171 @@ using Server.Items; namespace Server.Mobiles { - public class SBWeaponSmith: SBInfo - { - public SBWeaponSmith() - { - } + public class SBWeaponSmith : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BlackStaff), 22, 20, 0xDF1, 0)); + Add(new GenericBuyInfo(typeof(Club), 16, 20, 0x13B4, 0)); + Add(new GenericBuyInfo(typeof(GnarledStaff), 16, 20, 0x13F8, 0)); + Add(new GenericBuyInfo(typeof(Mace), 28, 20, 0xF5C, 0)); + Add(new GenericBuyInfo(typeof(Maul), 21, 20, 0x143B, 0)); + Add(new GenericBuyInfo(typeof(QuarterStaff), 19, 20, 0xE89, 0)); + Add(new GenericBuyInfo(typeof(ShepherdsCrook), 20, 20, 0xE81, 0)); + Add(new GenericBuyInfo(typeof(SmithHammer), 21, 20, 0x13E3, 0)); + Add(new GenericBuyInfo(typeof(ShortSpear), 23, 20, 0x1403, 0)); + Add(new GenericBuyInfo(typeof(Spear), 31, 20, 0xF62, 0)); + Add(new GenericBuyInfo(typeof(WarHammer), 25, 20, 0x1439, 0)); + Add(new GenericBuyInfo(typeof(WarMace), 31, 20, 0x1407, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BlackStaff ), 22, 20, 0xDF1, 0 ) ); - Add( new GenericBuyInfo( typeof( Club ), 16, 20, 0x13B4, 0 ) ); - Add( new GenericBuyInfo( typeof( GnarledStaff ), 16, 20, 0x13F8, 0 ) ); - Add( new GenericBuyInfo( typeof( Mace ), 28, 20, 0xF5C, 0 ) ); - Add( new GenericBuyInfo( typeof( Maul ), 21, 20, 0x143B, 0 ) ); - Add( new GenericBuyInfo( typeof( QuarterStaff ), 19, 20, 0xE89, 0 ) ); - Add( new GenericBuyInfo( typeof( ShepherdsCrook ), 20, 20, 0xE81, 0 ) ); - Add( new GenericBuyInfo( typeof( SmithHammer ), 21, 20, 0x13E3, 0 ) ); - Add( new GenericBuyInfo( typeof( ShortSpear ), 23, 20, 0x1403, 0 ) ); - Add( new GenericBuyInfo( typeof( Spear ), 31, 20, 0xF62, 0 ) ); - Add( new GenericBuyInfo( typeof( WarHammer ), 25, 20, 0x1439, 0 ) ); - Add( new GenericBuyInfo( typeof( WarMace ), 31, 20, 0x1407, 0 ) ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(Scepter), 39, 20, 0x26BC, 0)); + Add(new GenericBuyInfo(typeof(BladedStaff), 40, 20, 0x26BD, 0)); + } - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( Scepter ), 39, 20, 0x26BC, 0 ) ); - Add( new GenericBuyInfo( typeof( BladedStaff ), 40, 20, 0x26BD, 0 ) ); - } + Add(new GenericBuyInfo(typeof(Hatchet), 25, 20, 0xF44, 0)); + Add(new GenericBuyInfo(typeof(Hatchet), 27, 20, 0xF43, 0)); + Add(new GenericBuyInfo(typeof(WarFork), 32, 20, 0x1405, 0)); - Add( new GenericBuyInfo( typeof( Hatchet ), 25, 20, 0xF44, 0 ) ); - Add( new GenericBuyInfo( typeof( Hatchet ), 27, 20, 0xF43, 0 ) ); - Add( new GenericBuyInfo( typeof( WarFork ), 32, 20, 0x1405, 0 ) ); + switch (Utility.Random(3)) + { + case 0: + { + Add(new GenericBuyInfo(typeof(ExecutionersAxe), 30, 20, 0xF45, 0)); + Add(new GenericBuyInfo(typeof(Bardiche), 60, 20, 0xF4D, 0)); + Add(new GenericBuyInfo(typeof(BattleAxe), 26, 20, 0xF47, 0)); + Add(new GenericBuyInfo(typeof(TwoHandedAxe), 32, 20, 0x1443, 0)); - switch ( Utility.Random( 3 )) - { - case 0: - { - Add( new GenericBuyInfo( typeof( ExecutionersAxe ), 30, 20, 0xF45, 0 ) ); - Add( new GenericBuyInfo( typeof( Bardiche ), 60, 20, 0xF4D, 0 ) ); - Add( new GenericBuyInfo( typeof( BattleAxe ), 26, 20, 0xF47, 0 ) ); - Add( new GenericBuyInfo( typeof( TwoHandedAxe ), 32, 20, 0x1443, 0 ) ); + Add(new GenericBuyInfo(typeof(Bow), 35, 20, 0x13B2, 0)); - Add( new GenericBuyInfo( typeof( Bow ), 35, 20, 0x13B2, 0 ) ); + Add(new GenericBuyInfo(typeof(ButcherKnife), 14, 20, 0x13F6, 0)); - Add( new GenericBuyInfo( typeof( ButcherKnife ), 14, 20, 0x13F6, 0 ) ); + Add(new GenericBuyInfo(typeof(Crossbow), 46, 20, 0xF50, 0)); + Add(new GenericBuyInfo(typeof(HeavyCrossbow), 55, 20, 0x13FD, 0)); - Add( new GenericBuyInfo( typeof( Crossbow ), 46, 20, 0xF50, 0 ) ); - Add( new GenericBuyInfo( typeof( HeavyCrossbow ), 55, 20, 0x13FD, 0 ) ); + Add(new GenericBuyInfo(typeof(Cutlass), 24, 20, 0x1441, 0)); + Add(new GenericBuyInfo(typeof(Dagger), 21, 20, 0xF52, 0)); + Add(new GenericBuyInfo(typeof(Halberd), 42, 20, 0x143E, 0)); - Add( new GenericBuyInfo( typeof( Cutlass ), 24, 20, 0x1441, 0 ) ); - Add( new GenericBuyInfo( typeof( Dagger ), 21, 20, 0xF52, 0 ) ); - Add( new GenericBuyInfo( typeof( Halberd ), 42, 20, 0x143E, 0 ) ); + Add(new GenericBuyInfo(typeof(HammerPick), 26, 20, 0x143D, 0)); - Add( new GenericBuyInfo( typeof( HammerPick ), 26, 20, 0x143D, 0 ) ); + Add(new GenericBuyInfo(typeof(Katana), 33, 20, 0x13FF, 0)); + Add(new GenericBuyInfo(typeof(Kryss), 32, 20, 0x1401, 0)); + Add(new GenericBuyInfo(typeof(Broadsword), 35, 20, 0xF5E, 0)); + Add(new GenericBuyInfo(typeof(Longsword), 55, 20, 0xF61, 0)); + Add(new GenericBuyInfo(typeof(ThinLongsword), 27, 20, 0x13B8, 0)); + Add(new GenericBuyInfo(typeof(VikingSword), 55, 20, 0x13B9, 0)); - Add( new GenericBuyInfo( typeof( Katana ), 33, 20, 0x13FF, 0 ) ); - Add( new GenericBuyInfo( typeof( Kryss ), 32, 20, 0x1401, 0 ) ); - Add( new GenericBuyInfo( typeof( Broadsword ), 35, 20, 0xF5E, 0 ) ); - Add( new GenericBuyInfo( typeof( Longsword ), 55, 20, 0xF61, 0 ) ); - Add( new GenericBuyInfo( typeof( ThinLongsword ), 27, 20, 0x13B8, 0 ) ); - Add( new GenericBuyInfo( typeof( VikingSword ), 55, 20, 0x13B9, 0 ) ); + Add(new GenericBuyInfo(typeof(Cleaver), 15, 20, 0xEC3, 0)); + Add(new GenericBuyInfo(typeof(Axe), 40, 20, 0xF49, 0)); + Add(new GenericBuyInfo(typeof(DoubleAxe), 52, 20, 0xF4B, 0)); + Add(new GenericBuyInfo(typeof(Pickaxe), 22, 20, 0xE86, 0)); - Add( new GenericBuyInfo( typeof( Cleaver ), 15, 20, 0xEC3, 0 ) ); - Add( new GenericBuyInfo( typeof( Axe ), 40, 20, 0xF49, 0 ) ); - Add( new GenericBuyInfo( typeof( DoubleAxe ), 52, 20, 0xF4B, 0 ) ); - Add( new GenericBuyInfo( typeof( Pickaxe ), 22, 20, 0xE86, 0 ) ); + Add(new GenericBuyInfo(typeof(Pitchfork), 19, 20, 0xE87, 0)); - Add( new GenericBuyInfo( typeof( Pitchfork ), 19, 20, 0xE87, 0 ) ); + Add(new GenericBuyInfo(typeof(Scimitar), 36, 20, 0x13B6, 0)); - Add( new GenericBuyInfo( typeof( Scimitar ), 36, 20, 0x13B6, 0 ) ); + Add(new GenericBuyInfo(typeof(SkinningKnife), 14, 20, 0xEC4, 0)); - Add( new GenericBuyInfo( typeof( SkinningKnife ), 14, 20, 0xEC4, 0 ) ); + Add(new GenericBuyInfo(typeof(LargeBattleAxe), 33, 20, 0x13FB, 0)); + Add(new GenericBuyInfo(typeof(WarAxe), 29, 20, 0x13B0, 0)); - Add( new GenericBuyInfo( typeof( LargeBattleAxe ), 33, 20, 0x13FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WarAxe ), 29, 20, 0x13B0, 0 ) ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(BoneHarvester), 35, 20, 0x26BB, 0)); + Add(new GenericBuyInfo(typeof(CrescentBlade), 37, 20, 0x26C1, 0)); + Add(new GenericBuyInfo(typeof(DoubleBladedStaff), 35, 20, 0x26BF, 0)); + Add(new GenericBuyInfo(typeof(Lance), 34, 20, 0x26C0, 0)); + Add(new GenericBuyInfo(typeof(Pike), 39, 20, 0x26BE, 0)); + Add(new GenericBuyInfo(typeof(Scythe), 39, 20, 0x26BA, 0)); + Add(new GenericBuyInfo(typeof(CompositeBow), 50, 20, 0x26C2, 0)); + Add(new GenericBuyInfo(typeof(RepeatingCrossbow), 57, 20, 0x26C3, 0)); + } - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( BoneHarvester ), 35, 20, 0x26BB, 0 ) ); - Add( new GenericBuyInfo( typeof( CrescentBlade ), 37, 20, 0x26C1, 0 ) ); - Add( new GenericBuyInfo( typeof( DoubleBladedStaff ), 35, 20, 0x26BF, 0 ) ); - Add( new GenericBuyInfo( typeof( Lance ), 34, 20, 0x26C0, 0 ) ); - Add( new GenericBuyInfo( typeof( Pike ), 39, 20, 0x26BE, 0 ) ); - Add( new GenericBuyInfo( typeof( Scythe ), 39, 20, 0x26BA, 0 ) ); - Add( new GenericBuyInfo( typeof( CompositeBow ), 50, 20, 0x26C2, 0 ) ); - Add( new GenericBuyInfo( typeof( RepeatingCrossbow ), 57, 20, 0x26C3, 0 ) ); - } + break; + } + } + } + } - break; - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BattleAxe), 13); + Add(typeof(DoubleAxe), 26); + Add(typeof(ExecutionersAxe), 15); + Add(typeof(LargeBattleAxe), 16); + Add(typeof(Pickaxe), 11); + Add(typeof(TwoHandedAxe), 16); + Add(typeof(WarAxe), 14); + Add(typeof(Axe), 20); - } + Add(typeof(Bardiche), 30); + Add(typeof(Halberd), 21); - } - } + Add(typeof(ButcherKnife), 7); + Add(typeof(Cleaver), 7); + Add(typeof(Dagger), 10); + Add(typeof(SkinningKnife), 7); - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BattleAxe ), 13 ); - Add( typeof( DoubleAxe ), 26 ); - Add( typeof( ExecutionersAxe ), 15 ); - Add( typeof( LargeBattleAxe ),16 ); - Add( typeof( Pickaxe ), 11 ); - Add( typeof( TwoHandedAxe ), 16 ); - Add( typeof( WarAxe ), 14 ); - Add( typeof( Axe ), 20 ); + Add(typeof(Club), 8); + Add(typeof(HammerPick), 13); + Add(typeof(Mace), 14); + Add(typeof(Maul), 10); + Add(typeof(WarHammer), 12); + Add(typeof(WarMace), 15); - Add( typeof( Bardiche ), 30 ); - Add( typeof( Halberd ), 21 ); + Add(typeof(HeavyCrossbow), 27); + Add(typeof(Bow), 17); + Add(typeof(Crossbow), 23); - Add( typeof( ButcherKnife ), 7 ); - Add( typeof( Cleaver ), 7 ); - Add( typeof( Dagger ), 10 ); - Add( typeof( SkinningKnife ), 7 ); + if (Core.AOS) + { + Add(typeof(CompositeBow), 25); + Add(typeof(RepeatingCrossbow), 28); + Add(typeof(Scepter), 20); + Add(typeof(BladedStaff), 20); + Add(typeof(Scythe), 19); + Add(typeof(BoneHarvester), 17); + Add(typeof(Scepter), 18); + Add(typeof(BladedStaff), 16); + Add(typeof(Pike), 19); + Add(typeof(DoubleBladedStaff), 17); + Add(typeof(Lance), 17); + Add(typeof(CrescentBlade), 18); + } - Add( typeof( Club ), 8 ); - Add( typeof( HammerPick ), 13 ); - Add( typeof( Mace ), 14 ); - Add( typeof( Maul ), 10 ); - Add( typeof( WarHammer ), 12 ); - Add( typeof( WarMace ), 15 ); + Add(typeof(Spear), 15); + Add(typeof(Pitchfork), 9); + Add(typeof(ShortSpear), 11); - Add( typeof( HeavyCrossbow ), 27 ); - Add( typeof( Bow ), 17 ); - Add( typeof( Crossbow ), 23 ); + Add(typeof(BlackStaff), 11); + Add(typeof(GnarledStaff), 8); + Add(typeof(QuarterStaff), 9); + Add(typeof(ShepherdsCrook), 10); - if ( Core.AOS ) - { - Add( typeof( CompositeBow ), 25 ); - Add( typeof( RepeatingCrossbow ), 28 ); - Add( typeof( Scepter ), 20 ); - Add( typeof( BladedStaff ), 20 ); - Add( typeof( Scythe ), 19 ); - Add( typeof( BoneHarvester ), 17 ); - Add( typeof( Scepter ), 18 ); - Add( typeof( BladedStaff ), 16 ); - Add( typeof( Pike ), 19 ); - Add( typeof( DoubleBladedStaff ), 17 ); - Add( typeof( Lance ), 17 ); - Add( typeof( CrescentBlade ), 18 ); - } + Add(typeof(SmithHammer), 10); - Add( typeof( Spear ), 15 ); - Add( typeof( Pitchfork ), 9 ); - Add( typeof( ShortSpear ), 11 ); + Add(typeof(Broadsword), 17); + Add(typeof(Cutlass), 12); + Add(typeof(Katana), 16); + Add(typeof(Kryss), 16); + Add(typeof(Longsword), 27); + Add(typeof(Scimitar), 18); + Add(typeof(ThinLongsword), 13); + Add(typeof(VikingSword), 27); - Add( typeof( BlackStaff ), 11 ); - Add( typeof( GnarledStaff ), 8 ); - Add( typeof( QuarterStaff ), 9 ); - Add( typeof( ShepherdsCrook ), 10 ); - - Add( typeof( SmithHammer ), 10 ); - - Add( typeof( Broadsword ), 17 ); - Add( typeof( Cutlass ), 12 ); - Add( typeof( Katana ), 16 ); - Add( typeof( Kryss ), 16 ); - Add( typeof( Longsword ), 27 ); - Add( typeof( Scimitar ), 18 ); - Add( typeof( ThinLongsword ), 13 ); - Add( typeof( VikingSword ), 27 ); - - Add( typeof( Hatchet ), 13 ); - Add( typeof( WarFork ), 16 ); - } - } - } -} + Add(typeof(Hatchet), 13); + Add(typeof(WarFork), 16); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SBWeaver.cs b/Scripts/Mobiles/Vendors/SBInfo/SBWeaver.cs index ed6e5c36c..e3d427314 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SBWeaver.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SBWeaver.cs @@ -3,55 +3,50 @@ using Server.Items; namespace Server.Mobiles { - public class SBWeaver: SBInfo - { - public SBWeaver() - { - } + public class SBWeaver : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Dyes), 8, 20, 0xFA9, 0)); + Add(new GenericBuyInfo(typeof(DyeTub), 8, 20, 0xFAB, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Dyes ), 8, 20, 0xFA9, 0 ) ); - Add( new GenericBuyInfo( typeof( DyeTub ), 8, 20, 0xFAB, 0 ) ); + Add(new GenericBuyInfo(typeof(UncutCloth), 3, 20, 0x1761, 0)); + Add(new GenericBuyInfo(typeof(UncutCloth), 3, 20, 0x1762, 0)); + Add(new GenericBuyInfo(typeof(UncutCloth), 3, 20, 0x1763, 0)); + Add(new GenericBuyInfo(typeof(UncutCloth), 3, 20, 0x1764, 0)); - Add( new GenericBuyInfo( typeof( UncutCloth ), 3, 20, 0x1761, 0 ) ); - Add( new GenericBuyInfo( typeof( UncutCloth ), 3, 20, 0x1762, 0 ) ); - Add( new GenericBuyInfo( typeof( UncutCloth ), 3, 20, 0x1763, 0 ) ); - Add( new GenericBuyInfo( typeof( UncutCloth ), 3, 20, 0x1764, 0 ) ); + Add(new GenericBuyInfo(typeof(BoltOfCloth), 100, 20, 0xf9B, 0)); + Add(new GenericBuyInfo(typeof(BoltOfCloth), 100, 20, 0xf9C, 0)); + Add(new GenericBuyInfo(typeof(BoltOfCloth), 100, 20, 0xf96, 0)); + Add(new GenericBuyInfo(typeof(BoltOfCloth), 100, 20, 0xf97, 0)); - Add( new GenericBuyInfo( typeof( BoltOfCloth ), 100, 20, 0xf9B, 0 ) ); - Add( new GenericBuyInfo( typeof( BoltOfCloth ), 100, 20, 0xf9C, 0 ) ); - Add( new GenericBuyInfo( typeof( BoltOfCloth ), 100, 20, 0xf96, 0 ) ); - Add( new GenericBuyInfo( typeof( BoltOfCloth ), 100, 20, 0xf97, 0 ) ); + Add(new GenericBuyInfo(typeof(DarkYarn), 18, 20, 0xE1D, 0)); + Add(new GenericBuyInfo(typeof(LightYarn), 18, 20, 0xE1E, 0)); + Add(new GenericBuyInfo(typeof(LightYarnUnraveled), 18, 20, 0xE1F, 0)); - Add( new GenericBuyInfo( typeof( DarkYarn ), 18, 20, 0xE1D, 0 ) ); - Add( new GenericBuyInfo( typeof( LightYarn ), 18, 20, 0xE1E, 0 ) ); - Add( new GenericBuyInfo( typeof( LightYarnUnraveled ), 18, 20, 0xE1F, 0 ) ); + Add(new GenericBuyInfo(typeof(Scissors), 11, 20, 0xF9F, 0)); + } + } - Add( new GenericBuyInfo( typeof( Scissors ), 11, 20, 0xF9F, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Scissors ), 6 ); - Add( typeof( Dyes ), 4 ); - Add( typeof( DyeTub ), 4 ); - Add( typeof( UncutCloth ), 1 ); - Add( typeof( BoltOfCloth ), 50 ); - Add( typeof( LightYarnUnraveled ), 9 ); - Add( typeof( LightYarn ), 9 ); - Add( typeof( DarkYarn ), 9 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Scissors), 6); + Add(typeof(Dyes), 4); + Add(typeof(DyeTub), 4); + Add(typeof(UncutCloth), 1); + Add(typeof(BoltOfCloth), 50); + Add(typeof(LightYarnUnraveled), 9); + Add(typeof(LightYarn), 9); + Add(typeof(DarkYarn), 9); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEArmor.cs index c8cfa18c5..4c680ef11 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEArmor.cs @@ -3,45 +3,40 @@ using Server.Items; namespace Server.Mobiles { - public class SBSEArmor: SBInfo - { - public SBSEArmor() - { - } + public class SBSEArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(PlateHatsuburi), 76, 20, 0x2775, 0)); + Add(new GenericBuyInfo(typeof(HeavyPlateJingasa), 76, 20, 0x2777, 0)); + Add(new GenericBuyInfo(typeof(DecorativePlateKabuto), 95, 20, 0x2778, 0)); + Add(new GenericBuyInfo(typeof(PlateDo), 310, 20, 0x277D, 0)); + Add(new GenericBuyInfo(typeof(PlateHiroSode), 222, 20, 0x2780, 0)); + Add(new GenericBuyInfo(typeof(PlateSuneate), 224, 20, 0x2788, 0)); + Add(new GenericBuyInfo(typeof(PlateHaidate), 235, 20, 0x278D, 0)); + Add(new GenericBuyInfo(typeof(ChainHatsuburi), 76, 20, 0x2774, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( PlateHatsuburi ), 76, 20, 0x2775, 0 ) ); - Add( new GenericBuyInfo( typeof( HeavyPlateJingasa ), 76, 20, 0x2777, 0 ) ); - Add( new GenericBuyInfo( typeof( DecorativePlateKabuto ), 95, 20, 0x2778, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateDo ), 310, 20, 0x277D, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateHiroSode ), 222, 20, 0x2780, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateSuneate ), 224, 20, 0x2788, 0 ) ); - Add( new GenericBuyInfo( typeof( PlateHaidate ), 235, 20, 0x278D, 0 ) ); - Add( new GenericBuyInfo( typeof( ChainHatsuburi ), 76, 20, 0x2774, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( PlateHatsuburi ), 38 ); - Add( typeof( HeavyPlateJingasa ), 38 ); - Add( typeof( DecorativePlateKabuto ), 47 ); - Add( typeof( PlateDo ), 155 ); - Add( typeof( PlateHiroSode ), 111 ); - Add( typeof( PlateSuneate ), 112 ); - Add( typeof( PlateHaidate), 117 ); - Add( typeof( ChainHatsuburi ), 38 ); - - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(PlateHatsuburi), 38); + Add(typeof(HeavyPlateJingasa), 38); + Add(typeof(DecorativePlateKabuto), 47); + Add(typeof(PlateDo), 155); + Add(typeof(PlateHiroSode), 111); + Add(typeof(PlateSuneate), 112); + Add(typeof(PlateHaidate), 117); + Add(typeof(ChainHatsuburi), 38); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEBowyer.cs b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEBowyer.cs index a8837d74a..55b120cf8 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEBowyer.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEBowyer.cs @@ -3,38 +3,34 @@ using Server.Items; namespace Server.Mobiles { - public class SBSEBowyer: SBInfo - { - public SBSEBowyer() - { - } + public class SBSEBowyer : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Yumi), 53, 20, 0x27A5, 0)); + Add(new GenericBuyInfo(typeof(Fukiya), 20, 20, 0x27AA, 0)); + Add(new GenericBuyInfo(typeof(Nunchaku), 35, 20, 0x27AE, 0)); + Add(new GenericBuyInfo(typeof(FukiyaDarts), 3, 20, 0x2806, 0)); + Add(new GenericBuyInfo(typeof(Bokuto), 21, 20, 0x27A8, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Yumi ), 53, 20, 0x27A5, 0 ) ); - Add( new GenericBuyInfo( typeof( Fukiya ), 20, 20, 0x27AA, 0 ) ); - Add( new GenericBuyInfo( typeof( Nunchaku ), 35, 20, 0x27AE, 0 ) ); - Add( new GenericBuyInfo( typeof( FukiyaDarts ), 3, 20, 0x2806, 0 ) ); - Add( new GenericBuyInfo( typeof( Bokuto ), 21, 20, 0x27A8, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Yumi ), 26 ); - Add( typeof( Fukiya ), 10 ); - Add( typeof( Nunchaku ), 17 ); - Add( typeof( FukiyaDarts ), 1 ); - Add( typeof( Bokuto ), 10 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Yumi), 26); + Add(typeof(Fukiya), 10); + Add(typeof(Nunchaku), 17); + Add(typeof(FukiyaDarts), 1); + Add(typeof(Bokuto), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSECarpenter.cs b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSECarpenter.cs index 6258f1e50..7bff0eb92 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSECarpenter.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSECarpenter.cs @@ -3,37 +3,33 @@ using Server.Items; namespace Server.Mobiles { - public class SBSECarpenter: SBInfo - { - public SBSECarpenter() - { - } + public class SBSECarpenter : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bokuto), 21, 20, 0x27A8, 0)); + Add(new GenericBuyInfo(typeof(Tetsubo), 43, 20, 0x27A6, 0)); + Add(new GenericBuyInfo(typeof(Fukiya), 20, 20, 0x27AA, 0)); + Add(new GenericBuyInfo(typeof(BambooFlute), 21, 20, 0x2805, 0)); + Add(new GenericBuyInfo(typeof(BambooFlute), 21, 20, 0x2805, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bokuto ), 21, 20, 0x27A8, 0 ) ); - Add( new GenericBuyInfo( typeof( Tetsubo ), 43, 20, 0x27A6, 0 ) ); - Add( new GenericBuyInfo( typeof( Fukiya ), 20, 20, 0x27AA, 0 ) ); - Add( new GenericBuyInfo( typeof( BambooFlute ), 21, 20, 0x2805, 0 ) ); - Add( new GenericBuyInfo( typeof( BambooFlute ), 21, 20, 0x2805, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Tetsubo ), 21 ); - Add( typeof( Fukiya ), 10 ); - Add( typeof( BambooFlute ), 10 ); - Add( typeof( Bokuto ), 10 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Tetsubo), 21); + Add(typeof(Fukiya), 10); + Add(typeof(BambooFlute), 10); + Add(typeof(Bokuto), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEFood.cs b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEFood.cs index 40f30c236..be03374b2 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEFood.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEFood.cs @@ -3,36 +3,32 @@ using Server.Items; namespace Server.Mobiles { - public class SBSEFood: SBInfo - { - public SBSEFood() - { - } + public class SBSEFood : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Wasabi), 2, 20, 0x24E8, 0)); + Add(new GenericBuyInfo(typeof(Wasabi), 2, 20, 0x24E9, 0)); + Add(new GenericBuyInfo(typeof(BentoBox), 6, 20, 0x2836, 0)); + Add(new GenericBuyInfo(typeof(BentoBox), 6, 20, 0x2837, 0)); + Add(new GenericBuyInfo(typeof(GreenTeaBasket), 2, 20, 0x284B, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E8, 0 ) ); - Add( new GenericBuyInfo( typeof( Wasabi ), 2, 20, 0x24E9, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2836, 0 ) ); - Add( new GenericBuyInfo( typeof( BentoBox ), 6, 20, 0x2837, 0 ) ); - Add( new GenericBuyInfo( typeof( GreenTeaBasket ), 2, 20, 0x284B, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Wasabi ), 1 ); - Add( typeof( BentoBox ), 3 ); - Add( typeof( GreenTeaBasket ), 1 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Wasabi), 1); + Add(typeof(BentoBox), 3); + Add(typeof(GreenTeaBasket), 1); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSELeatherArmor.cs b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSELeatherArmor.cs index cc5a6c969..7bd5fa9ea 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSELeatherArmor.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSELeatherArmor.cs @@ -3,53 +3,49 @@ using Server.Items; namespace Server.Mobiles { - public class SBSELeatherArmor: SBInfo - { - public SBSELeatherArmor() - { - } + public class SBSELeatherArmor : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(LeatherJingasa), 11, 20, 0x2776, 0)); + Add(new GenericBuyInfo(typeof(LeatherDo), 87, 20, 0x277B, 0)); + Add(new GenericBuyInfo(typeof(LeatherHiroSode), 49, 20, 0x277E, 0)); + Add(new GenericBuyInfo(typeof(LeatherSuneate), 55, 20, 0x2786, 0)); + Add(new GenericBuyInfo(typeof(LeatherHaidate), 54, 20, 0x278A, 0)); + Add(new GenericBuyInfo(typeof(LeatherNinjaPants), 49, 20, 0x2791, 0)); + Add(new GenericBuyInfo(typeof(LeatherNinjaJacket), 51, 20, 0x2793, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( LeatherJingasa ), 11, 20, 0x2776, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherDo ), 87, 20, 0x277B, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherHiroSode ), 49, 20, 0x277E, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherSuneate ), 55, 20, 0x2786, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherHaidate), 54, 20, 0x278A, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherNinjaPants ), 49, 20, 0x2791, 0 ) ); - Add( new GenericBuyInfo( typeof( LeatherNinjaJacket ), 51, 20, 0x2793, 0 ) ); + Add(new GenericBuyInfo(typeof(StuddedMempo), 61, 20, 0x279D, 0)); + Add(new GenericBuyInfo(typeof(StuddedDo), 130, 20, 0x277C, 0)); + Add(new GenericBuyInfo(typeof(StuddedHiroSode), 73, 20, 0x277F, 0)); + Add(new GenericBuyInfo(typeof(StuddedSuneate), 78, 20, 0x2787, 0)); + Add(new GenericBuyInfo(typeof(StuddedHaidate), 76, 20, 0x278B, 0)); + } + } - Add( new GenericBuyInfo( typeof( StuddedMempo ), 61, 20, 0x279D, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedDo ), 130, 20, 0x277C, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedHiroSode ), 73, 20, 0x277F, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedSuneate ), 78, 20, 0x2787, 0 ) ); - Add( new GenericBuyInfo( typeof( StuddedHaidate ), 76, 20, 0x278B, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( LeatherJingasa ), 5 ); - Add( typeof( LeatherDo ), 42 ); - Add( typeof( LeatherHiroSode ), 23 ); - Add( typeof( LeatherSuneate ), 26 ); - Add( typeof( LeatherHaidate), 28 ); - Add( typeof( LeatherNinjaPants ), 25 ); - Add( typeof( LeatherNinjaJacket ), 26 ); - Add( typeof( StuddedMempo ), 28 ); - Add( typeof( StuddedDo ), 66 ); - Add( typeof( StuddedHiroSode ), 32 ); - Add( typeof( StuddedSuneate ), 40 ); - Add( typeof( StuddedHaidate ), 37 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(LeatherJingasa), 5); + Add(typeof(LeatherDo), 42); + Add(typeof(LeatherHiroSode), 23); + Add(typeof(LeatherSuneate), 26); + Add(typeof(LeatherHaidate), 28); + Add(typeof(LeatherNinjaPants), 25); + Add(typeof(LeatherNinjaJacket), 26); + Add(typeof(StuddedMempo), 28); + Add(typeof(StuddedDo), 66); + Add(typeof(StuddedHiroSode), 32); + Add(typeof(StuddedSuneate), 40); + Add(typeof(StuddedHaidate), 37); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEWeapons.cs b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEWeapons.cs index 79d9a0a27..a97354d95 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEWeapons.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/SE/SBSEWeapons.cs @@ -3,49 +3,44 @@ using Server.Items; namespace Server.Mobiles { - public class SBSEWeapons: SBInfo - { - public SBSEWeapons() - { - } + public class SBSEWeapons : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(NoDachi), 82, 20, 0x27A2, 0)); + Add(new GenericBuyInfo(typeof(Tessen), 83, 20, 0x27A3, 0)); + Add(new GenericBuyInfo(typeof(Wakizashi), 38, 20, 0x27A4, 0)); + Add(new GenericBuyInfo(typeof(Tetsubo), 43, 20, 0x27A6, 0)); + Add(new GenericBuyInfo(typeof(Lajatang), 108, 20, 0x27A7, 0)); + Add(new GenericBuyInfo(typeof(Daisho), 66, 20, 0x27A9, 0)); + Add(new GenericBuyInfo(typeof(Tekagi), 55, 20, 0x27AB, 0)); + Add(new GenericBuyInfo(typeof(Shuriken), 18, 20, 0x27AC, 0)); + Add(new GenericBuyInfo(typeof(Kama), 61, 20, 0x27AD, 0)); + Add(new GenericBuyInfo(typeof(Sai), 56, 20, 0x27AF, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( NoDachi ), 82, 20, 0x27A2, 0 ) ); - Add( new GenericBuyInfo( typeof( Tessen ), 83, 20, 0x27A3, 0 ) ); - Add( new GenericBuyInfo( typeof( Wakizashi ), 38, 20, 0x27A4, 0 ) ); - Add( new GenericBuyInfo( typeof( Tetsubo ), 43, 20, 0x27A6, 0 ) ); - Add( new GenericBuyInfo( typeof( Lajatang ), 108, 20, 0x27A7, 0 ) ); - Add( new GenericBuyInfo( typeof( Daisho ), 66, 20, 0x27A9, 0 ) ); - Add( new GenericBuyInfo( typeof( Tekagi ), 55, 20, 0x27AB, 0 ) ); - Add( new GenericBuyInfo( typeof( Shuriken ), 18, 20, 0x27AC, 0 ) ); - Add( new GenericBuyInfo( typeof( Kama ), 61, 20, 0x27AD, 0 ) ); - Add( new GenericBuyInfo( typeof( Sai ), 56, 20, 0x27AF, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( NoDachi ), 41 ); - Add( typeof( Tessen ), 41 ); - Add( typeof( Wakizashi ), 19 ); - Add( typeof( Tetsubo ), 21 ); - Add( typeof( Lajatang ), 54 ); - Add( typeof( Daisho ), 33 ); - Add( typeof( Tekagi ), 22 ); - Add( typeof( Shuriken), 9 ); - Add( typeof( Kama ), 30 ); - Add( typeof( Sai ), 28 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(NoDachi), 41); + Add(typeof(Tessen), 41); + Add(typeof(Wakizashi), 19); + Add(typeof(Tetsubo), 21); + Add(typeof(Lajatang), 54); + Add(typeof(Daisho), 33); + Add(typeof(Tekagi), 22); + Add(typeof(Shuriken), 9); + Add(typeof(Kama), 30); + Add(typeof(Sai), 28); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBAxeWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBAxeWeapon.cs index 95ac3f25b..304746d00 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBAxeWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBAxeWeapon.cs @@ -3,45 +3,40 @@ using Server.Items; namespace Server.Mobiles { - public class SBAxeWeapon: SBInfo - { - public SBAxeWeapon() - { - } + public class SBAxeWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(ExecutionersAxe), 30, 20, 0xF45, 0)); + Add(new GenericBuyInfo(typeof(BattleAxe), 26, 20, 0xF47, 0)); + Add(new GenericBuyInfo(typeof(TwoHandedAxe), 32, 20, 0x1443, 0)); + Add(new GenericBuyInfo(typeof(Axe), 40, 20, 0xF49, 0)); + Add(new GenericBuyInfo(typeof(DoubleAxe), 52, 20, 0xF4B, 0)); + Add(new GenericBuyInfo(typeof(Pickaxe), 22, 20, 0xE86, 0)); + Add(new GenericBuyInfo(typeof(LargeBattleAxe), 33, 20, 0x13FB, 0)); + Add(new GenericBuyInfo(typeof(WarAxe), 29, 20, 0x13B0, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( ExecutionersAxe ), 30, 20, 0xF45, 0 ) ); - Add( new GenericBuyInfo( typeof( BattleAxe ), 26, 20, 0xF47, 0 ) ); - Add( new GenericBuyInfo( typeof( TwoHandedAxe ), 32, 20, 0x1443, 0 ) ); - Add( new GenericBuyInfo( typeof( Axe ), 40, 20, 0xF49, 0 ) ); - Add( new GenericBuyInfo( typeof( DoubleAxe ), 52, 20, 0xF4B, 0 ) ); - Add( new GenericBuyInfo( typeof( Pickaxe ), 22, 20, 0xE86, 0 ) ); - Add( new GenericBuyInfo( typeof( LargeBattleAxe ), 33, 20, 0x13FB, 0 ) ); - Add( new GenericBuyInfo( typeof( WarAxe ), 29, 20, 0x13B0, 0 ) ); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BattleAxe ), 13 ); - Add( typeof( DoubleAxe ), 26 ); - Add( typeof( ExecutionersAxe ), 15 ); - Add( typeof( LargeBattleAxe ),16 ); - Add( typeof( Pickaxe ), 11 ); - Add( typeof( TwoHandedAxe ), 16 ); - Add( typeof( WarAxe ), 14 ); - Add( typeof( Axe ), 20 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BattleAxe), 13); + Add(typeof(DoubleAxe), 26); + Add(typeof(ExecutionersAxe), 15); + Add(typeof(LargeBattleAxe), 16); + Add(typeof(Pickaxe), 11); + Add(typeof(TwoHandedAxe), 16); + Add(typeof(WarAxe), 14); + Add(typeof(Axe), 20); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBKnifeWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBKnifeWeapon.cs index d112fe6b0..1df846f6e 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBKnifeWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBKnifeWeapon.cs @@ -3,36 +3,32 @@ using Server.Items; namespace Server.Mobiles { - public class SBKnifeWeapon: SBInfo - { - public SBKnifeWeapon() - { - } + public class SBKnifeWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(ButcherKnife), 14, 20, 0x13F6, 0)); + Add(new GenericBuyInfo(typeof(Dagger), 21, 20, 0xF52, 0)); + Add(new GenericBuyInfo(typeof(Cleaver), 15, 20, 0xEC3, 0)); + Add(new GenericBuyInfo(typeof(SkinningKnife), 14, 20, 0xEC4, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( ButcherKnife ), 14, 20, 0x13F6, 0 ) ); - Add( new GenericBuyInfo( typeof( Dagger ), 21, 20, 0xF52, 0 ) ); - Add( new GenericBuyInfo( typeof( Cleaver ), 15, 20, 0xEC3, 0 ) ); - Add( new GenericBuyInfo( typeof( SkinningKnife ), 14, 20, 0xEC4, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( ButcherKnife ), 7 ); - Add( typeof( Cleaver ), 7 ); - Add( typeof( Dagger ), 10 ); - Add( typeof( SkinningKnife ), 7 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(ButcherKnife), 7); + Add(typeof(Cleaver), 7); + Add(typeof(Dagger), 10); + Add(typeof(SkinningKnife), 7); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBMaceWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBMaceWeapon.cs index 415fa20b5..b881944b5 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBMaceWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBMaceWeapon.cs @@ -3,40 +3,36 @@ using Server.Items; namespace Server.Mobiles { - public class SBMaceWeapon: SBInfo - { - public SBMaceWeapon() - { - } + public class SBMaceWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(HammerPick), 26, 20, 0x143D, 0)); + Add(new GenericBuyInfo(typeof(Club), 16, 20, 0x13B4, 0)); + Add(new GenericBuyInfo(typeof(Mace), 28, 20, 0xF5C, 0)); + Add(new GenericBuyInfo(typeof(Maul), 21, 20, 0x143B, 0)); + Add(new GenericBuyInfo(typeof(WarHammer), 25, 20, 0x1439, 0)); + Add(new GenericBuyInfo(typeof(WarMace), 31, 20, 0x1407, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( HammerPick ), 26, 20, 0x143D, 0 ) ); - Add( new GenericBuyInfo( typeof( Club ), 16, 20, 0x13B4, 0 ) ); - Add( new GenericBuyInfo( typeof( Mace ), 28, 20, 0xF5C, 0 ) ); - Add( new GenericBuyInfo( typeof( Maul ), 21, 20, 0x143B, 0 ) ); - Add( new GenericBuyInfo( typeof( WarHammer ), 25, 20, 0x1439, 0 ) ); - Add( new GenericBuyInfo( typeof( WarMace ), 31, 20, 0x1407, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Club ), 8 ); - Add( typeof( HammerPick ), 13 ); - Add( typeof( Mace ), 14 ); - Add( typeof( Maul ), 10 ); - Add( typeof( WarHammer ), 12 ); - Add( typeof( WarMace ), 15 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Club), 8); + Add(typeof(HammerPick), 13); + Add(typeof(Mace), 14); + Add(typeof(Maul), 10); + Add(typeof(WarHammer), 12); + Add(typeof(WarMace), 15); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBPoleArmWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBPoleArmWeapon.cs index 96540ee17..7ab86d4de 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBPoleArmWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBPoleArmWeapon.cs @@ -3,32 +3,28 @@ using Server.Items; namespace Server.Mobiles { - public class SBPoleArmWeapon: SBInfo - { - public SBPoleArmWeapon() - { - } + public class SBPoleArmWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Bardiche), 60, 20, 0xF4D, 0)); + Add(new GenericBuyInfo(typeof(Halberd), 42, 20, 0x143E, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Bardiche ), 60, 20, 0xF4D, 0 ) ); - Add( new GenericBuyInfo( typeof( Halberd ), 42, 20, 0x143E, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bardiche ), 30 ); - Add( typeof( Halberd ), 21 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bardiche), 30); + Add(typeof(Halberd), 21); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBRangedWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBRangedWeapon.cs index 926deef63..9d62a0176 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBRangedWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBRangedWeapon.cs @@ -3,54 +3,51 @@ using Server.Items; namespace Server.Mobiles { - public class SBRangedWeapon: SBInfo - { - public SBRangedWeapon() - { - } + public class SBRangedWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Crossbow), 55, 20, 0xF50, 0)); + Add(new GenericBuyInfo(typeof(HeavyCrossbow), 55, 20, 0x13FD, 0)); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(RepeatingCrossbow), 46, 20, 0x26C3, 0)); + Add(new GenericBuyInfo(typeof(CompositeBow), 45, 20, 0x26C2, 0)); + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Crossbow ), 55, 20, 0xF50, 0 ) ); - Add( new GenericBuyInfo( typeof( HeavyCrossbow ), 55, 20, 0x13FD, 0 ) ); - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( RepeatingCrossbow ), 46, 20, 0x26C3, 0 ) ); - Add( new GenericBuyInfo( typeof( CompositeBow ), 45, 20, 0x26C2, 0 ) ); - } - Add( new GenericBuyInfo( typeof( Bolt ), 2, Utility.Random( 30, 60 ), 0x1BFB, 0 ) ); - Add( new GenericBuyInfo( typeof( Bow ), 40, 20, 0x13B2, 0 ) ); - Add( new GenericBuyInfo( typeof( Arrow ), 2, Utility.Random( 30, 60 ), 0xF3F, 0 ) ); - Add( new GenericBuyInfo( typeof( Feather ), 2, Utility.Random( 30, 60 ), 0x1BD1, 0 ) ); - Add( new GenericBuyInfo( typeof( Shaft ), 3, Utility.Random( 30, 60 ), 0x1BD4, 0 ) ); - } - } + Add(new GenericBuyInfo(typeof(Bolt), 2, Utility.Random(30, 60), 0x1BFB, 0)); + Add(new GenericBuyInfo(typeof(Bow), 40, 20, 0x13B2, 0)); + Add(new GenericBuyInfo(typeof(Arrow), 2, Utility.Random(30, 60), 0xF3F, 0)); + Add(new GenericBuyInfo(typeof(Feather), 2, Utility.Random(30, 60), 0x1BD1, 0)); + Add(new GenericBuyInfo(typeof(Shaft), 3, Utility.Random(30, 60), 0x1BD4, 0)); + } + } - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Bolt ), 1 ); - Add( typeof( Arrow ), 1 ); - Add( typeof( Shaft ), 1 ); - Add( typeof( Feather ), 1 ); + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Bolt), 1); + Add(typeof(Arrow), 1); + Add(typeof(Shaft), 1); + Add(typeof(Feather), 1); - Add( typeof( HeavyCrossbow ), 27 ); - Add( typeof( Bow ), 17 ); - Add( typeof( Crossbow ), 25 ); + Add(typeof(HeavyCrossbow), 27); + Add(typeof(Bow), 17); + Add(typeof(Crossbow), 25); - if ( Core.AOS ) - { - Add( typeof( CompositeBow ), 23 ); - Add( typeof( RepeatingCrossbow ), 22 ); - } - } - } - } -} + if (Core.AOS) + { + Add(typeof(CompositeBow), 23); + Add(typeof(RepeatingCrossbow), 22); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSpearForkWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSpearForkWeapon.cs index 702afd1ab..e044dbf7e 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSpearForkWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSpearForkWeapon.cs @@ -3,34 +3,30 @@ using Server.Items; namespace Server.Mobiles { - public class SBSpearForkWeapon: SBInfo - { - public SBSpearForkWeapon() - { - } + public class SBSpearForkWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Pitchfork), 19, 20, 0xE87, 0)); + Add(new GenericBuyInfo(typeof(ShortSpear), 23, 20, 0x1403, 0)); + Add(new GenericBuyInfo(typeof(Spear), 31, 20, 0xF62, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Pitchfork ), 19, 20, 0xE87, 0 ) ); - Add( new GenericBuyInfo( typeof( ShortSpear ), 23, 20, 0x1403, 0 ) ); - Add( new GenericBuyInfo( typeof( Spear ), 31, 20, 0xF62, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Spear ), 15 ); - Add( typeof( Pitchfork ), 9 ); - Add( typeof( ShortSpear ), 11 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Spear), 15); + Add(typeof(Pitchfork), 9); + Add(typeof(ShortSpear), 11); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBStavesWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBStavesWeapon.cs index be4f2e736..5b06d87dd 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBStavesWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBStavesWeapon.cs @@ -3,36 +3,32 @@ using Server.Items; namespace Server.Mobiles { - public class SBStavesWeapon: SBInfo - { - public SBStavesWeapon() - { - } + public class SBStavesWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(BlackStaff), 22, 20, 0xDF1, 0)); + Add(new GenericBuyInfo(typeof(GnarledStaff), 16, 20, 0x13F8, 0)); + Add(new GenericBuyInfo(typeof(QuarterStaff), 19, 20, 0xE89, 0)); + Add(new GenericBuyInfo(typeof(ShepherdsCrook), 20, 20, 0xE81, 0)); + } + } - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( BlackStaff ), 22, 20, 0xDF1, 0 ) ); - Add( new GenericBuyInfo( typeof( GnarledStaff ), 16, 20, 0x13F8, 0 ) ); - Add( new GenericBuyInfo( typeof( QuarterStaff ), 19, 20, 0xE89, 0 ) ); - Add( new GenericBuyInfo( typeof( ShepherdsCrook ), 20, 20, 0xE81, 0 ) ); - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( BlackStaff ), 11 ); - Add( typeof( GnarledStaff ), 8 ); - Add( typeof( QuarterStaff ), 9 ); - Add( typeof( ShepherdsCrook ), 10 ); - } - } - } -} + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(BlackStaff), 11); + Add(typeof(GnarledStaff), 8); + Add(typeof(QuarterStaff), 9); + Add(typeof(ShepherdsCrook), 10); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSwordWeapon.cs b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSwordWeapon.cs index eb71e08c9..a9797b0f5 100644 --- a/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSwordWeapon.cs +++ b/Scripts/Mobiles/Vendors/SBInfo/Weapons/SBSwordWeapon.cs @@ -3,68 +3,62 @@ using Server.Items; namespace Server.Mobiles { - public class SBSwordWeapon: SBInfo - { - public SBSwordWeapon() - { - } + public class SBSwordWeapon : SBInfo + { + public override IShopSellInfo SellInfo{ get; } = new InternalSellInfo(); - public override IShopSellInfo SellInfo { get; } = new InternalSellInfo(); + public override List BuyInfo{ get; } = new InternalBuyInfo(); - public override List BuyInfo { get; } = new InternalBuyInfo(); + public class InternalBuyInfo : List + { + public InternalBuyInfo() + { + Add(new GenericBuyInfo(typeof(Cutlass), 24, 20, 0x1441, 0)); + Add(new GenericBuyInfo(typeof(Katana), 33, 20, 0x13FF, 0)); + Add(new GenericBuyInfo(typeof(Kryss), 32, 20, 0x1401, 0)); + Add(new GenericBuyInfo(typeof(Broadsword), 35, 20, 0xF5E, 0)); + Add(new GenericBuyInfo(typeof(Longsword), 55, 20, 0xF61, 0)); + Add(new GenericBuyInfo(typeof(ThinLongsword), 27, 20, 0x13B8, 0)); + Add(new GenericBuyInfo(typeof(VikingSword), 55, 20, 0x13B9, 0)); + Add(new GenericBuyInfo(typeof(Scimitar), 36, 20, 0x13B6, 0)); - public class InternalBuyInfo : List - { - public InternalBuyInfo() - { - Add( new GenericBuyInfo( typeof( Cutlass ), 24, 20, 0x1441, 0 ) ); - Add( new GenericBuyInfo( typeof( Katana ), 33, 20, 0x13FF, 0 ) ); - Add( new GenericBuyInfo( typeof( Kryss ), 32, 20, 0x1401, 0 ) ); - Add( new GenericBuyInfo( typeof( Broadsword ), 35, 20, 0xF5E, 0 ) ); - Add( new GenericBuyInfo( typeof( Longsword ), 55, 20, 0xF61, 0 ) ); - Add( new GenericBuyInfo( typeof( ThinLongsword ), 27, 20, 0x13B8, 0 ) ); - Add( new GenericBuyInfo( typeof( VikingSword ), 55, 20, 0x13B9, 0 ) ); - Add( new GenericBuyInfo( typeof( Scimitar ), 36, 20, 0x13B6, 0 ) ); + if (Core.AOS) + { + Add(new GenericBuyInfo(typeof(BoneHarvester), 35, 20, 0x26BB, 0)); + Add(new GenericBuyInfo(typeof(CrescentBlade), 37, 20, 0x26C1, 0)); + Add(new GenericBuyInfo(typeof(DoubleBladedStaff), 35, 20, 0x26BF, 0)); + Add(new GenericBuyInfo(typeof(Lance), 34, 20, 0x26C0, 0)); + Add(new GenericBuyInfo(typeof(Pike), 39, 20, 0x26BE, 0)); + Add(new GenericBuyInfo(typeof(Scythe), 39, 20, 0x26BA, 0)); + } + } + } - if ( Core.AOS ) - { - Add( new GenericBuyInfo( typeof( BoneHarvester ), 35, 20, 0x26BB, 0 ) ); - Add( new GenericBuyInfo( typeof( CrescentBlade ), 37, 20, 0x26C1, 0 ) ); - Add( new GenericBuyInfo( typeof( DoubleBladedStaff ), 35, 20, 0x26BF, 0 ) ); - Add( new GenericBuyInfo( typeof( Lance ), 34, 20, 0x26C0, 0 ) ); - Add( new GenericBuyInfo( typeof( Pike ), 39, 20, 0x26BE, 0 ) ); - Add( new GenericBuyInfo( typeof( Scythe ), 39, 20, 0x26BA, 0 ) ); - } + public class InternalSellInfo : GenericSellInfo + { + public InternalSellInfo() + { + Add(typeof(Broadsword), 17); + Add(typeof(Cutlass), 12); + Add(typeof(Katana), 16); + Add(typeof(Kryss), 16); + Add(typeof(Longsword), 27); + Add(typeof(Scimitar), 18); + Add(typeof(ThinLongsword), 13); + Add(typeof(VikingSword), 27); - - } - } - - public class InternalSellInfo : GenericSellInfo - { - public InternalSellInfo() - { - Add( typeof( Broadsword ), 17 ); - Add( typeof( Cutlass ), 12 ); - Add( typeof( Katana ), 16 ); - Add( typeof( Kryss ), 16 ); - Add( typeof( Longsword ), 27 ); - Add( typeof( Scimitar ), 18 ); - Add( typeof( ThinLongsword ), 13 ); - Add( typeof( VikingSword ), 27 ); - - if ( Core.AOS ) - { - Add( typeof( Scythe ), 19 ); - Add( typeof( BoneHarvester ), 17 ); - Add( typeof( Scepter ), 18 ); - Add( typeof( BladedStaff ), 16 ); - Add( typeof( Pike ), 19 ); - Add( typeof( DoubleBladedStaff ), 17 ); - Add( typeof( Lance ), 17 ); - Add( typeof( CrescentBlade ), 18 ); - } - } - } - } -} + if (Core.AOS) + { + Add(typeof(Scythe), 19); + Add(typeof(BoneHarvester), 17); + Add(typeof(Scepter), 18); + Add(typeof(BladedStaff), 16); + Add(typeof(Pike), 19); + Add(typeof(DoubleBladedStaff), 17); + Add(typeof(Lance), 17); + Add(typeof(CrescentBlade), 18); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Mobiles/Vendors/VendorInventory.cs b/Scripts/Mobiles/Vendors/VendorInventory.cs index 9491b8b9f..ad3104ae5 100644 --- a/Scripts/Mobiles/Vendors/VendorInventory.cs +++ b/Scripts/Mobiles/Vendors/VendorInventory.cs @@ -4,139 +4,134 @@ using Server.Multis; namespace Server.Mobiles { - public class VendorInventory - { - public static readonly TimeSpan GracePeriod = TimeSpan.FromDays( 7.0 ); + public class VendorInventory + { + public static readonly TimeSpan GracePeriod = TimeSpan.FromDays(7.0); - private Timer m_ExpireTimer; + private Timer m_ExpireTimer; - public VendorInventory( BaseHouse house, Mobile owner, string vendorName, string shopName ) - { - House = house; - Owner = owner; - VendorName = vendorName; - ShopName = shopName; + public VendorInventory(BaseHouse house, Mobile owner, string vendorName, string shopName) + { + House = house; + Owner = owner; + VendorName = vendorName; + ShopName = shopName; - Items = new List(); + Items = new List(); - ExpireTime = DateTime.UtcNow + GracePeriod; - m_ExpireTimer = new ExpireTimer( this, GracePeriod ); - m_ExpireTimer.Start(); - } + ExpireTime = DateTime.UtcNow + GracePeriod; + m_ExpireTimer = new ExpireTimer(this, GracePeriod); + m_ExpireTimer.Start(); + } - public BaseHouse House { get; set; } + public VendorInventory(BaseHouse house, GenericReader reader) + { + House = house; - public string VendorName { get; set; } + int version = reader.ReadEncodedInt(); - public string ShopName { get; set; } + Owner = reader.ReadMobile(); + VendorName = reader.ReadString(); + ShopName = reader.ReadString(); - public Mobile Owner { get; set; } + Items = reader.ReadStrongItemList(); + Gold = reader.ReadInt(); - public List Items { get; } + ExpireTime = reader.ReadDeltaTime(); - public int Gold { get; set; } + if (Items.Count == 0 && Gold == 0) + { + Timer.DelayCall(TimeSpan.Zero, Delete); + } + else + { + TimeSpan delay = ExpireTime - DateTime.UtcNow; + m_ExpireTimer = new ExpireTimer(this, delay > TimeSpan.Zero ? delay : TimeSpan.Zero); + m_ExpireTimer.Start(); + } + } - public DateTime ExpireTime { get; } + public BaseHouse House{ get; set; } - public void AddItem( Item item ) - { - item.Internalize(); - Items.Add( item ); - } + public string VendorName{ get; set; } - public void Delete() - { - foreach ( Item item in Items ) - { - item.Delete(); - } + public string ShopName{ get; set; } - Items.Clear(); - Gold = 0; + public Mobile Owner{ get; set; } - House?.VendorInventories.Remove( this ); + public List Items{ get; } - m_ExpireTimer.Stop(); - } + public int Gold{ get; set; } - public void Serialize( GenericWriter writer ) - { - writer.WriteEncodedInt( 0 ); // version + public DateTime ExpireTime{ get; } - writer.Write( (Mobile) Owner ); - writer.Write( (string) VendorName ); - writer.Write( (string) ShopName ); + public void AddItem(Item item) + { + item.Internalize(); + Items.Add(item); + } - writer.Write( Items, true ); - writer.Write( (int) Gold ); + public void Delete() + { + foreach (Item item in Items) item.Delete(); - writer.WriteDeltaTime( ExpireTime ); - } + Items.Clear(); + Gold = 0; - public VendorInventory( BaseHouse house, GenericReader reader ) - { - House = house; + House?.VendorInventories.Remove(this); - int version = reader.ReadEncodedInt(); + m_ExpireTimer.Stop(); + } - Owner = reader.ReadMobile(); - VendorName = reader.ReadString(); - ShopName = reader.ReadString(); + public void Serialize(GenericWriter writer) + { + writer.WriteEncodedInt(0); // version - Items = reader.ReadStrongItemList(); - Gold = reader.ReadInt(); + writer.Write(Owner); + writer.Write(VendorName); + writer.Write(ShopName); - ExpireTime = reader.ReadDeltaTime(); + writer.Write(Items, true); + writer.Write(Gold); - if ( Items.Count == 0 && Gold == 0 ) - { - Timer.DelayCall( TimeSpan.Zero, Delete ); - } - else - { - TimeSpan delay = ExpireTime - DateTime.UtcNow; - m_ExpireTimer = new ExpireTimer( this, delay > TimeSpan.Zero ? delay : TimeSpan.Zero ); - m_ExpireTimer.Start(); - } - } + writer.WriteDeltaTime(ExpireTime); + } - private class ExpireTimer : Timer - { - private VendorInventory m_Inventory; + private class ExpireTimer : Timer + { + private VendorInventory m_Inventory; - public ExpireTimer( VendorInventory inventory, TimeSpan delay ) : base( delay ) - { - m_Inventory = inventory; + public ExpireTimer(VendorInventory inventory, TimeSpan delay) : base(delay) + { + m_Inventory = inventory; - Priority = TimerPriority.OneMinute; - } + Priority = TimerPriority.OneMinute; + } - protected override void OnTick() - { - BaseHouse house = m_Inventory.House; + protected override void OnTick() + { + BaseHouse house = m_Inventory.House; - if ( house != null ) - { - if ( m_Inventory.Gold > 0 ) - { - if ( house.MovingCrate == null ) - house.MovingCrate = new MovingCrate( house ); + if (house != null) + { + if (m_Inventory.Gold > 0) + { + if (house.MovingCrate == null) + house.MovingCrate = new MovingCrate(house); - Banker.Deposit( house.MovingCrate, m_Inventory.Gold ); - } + Banker.Deposit(house.MovingCrate, m_Inventory.Gold); + } - foreach ( Item item in m_Inventory.Items ) - { - if ( !item.Deleted ) - house.DropToMovingCrate( item ); - } + foreach (Item item in m_Inventory.Items) + if (!item.Deleted) + house.DropToMovingCrate(item); - m_Inventory.Gold = 0; - m_Inventory.Items.Clear(); - } + m_Inventory.Gold = 0; + m_Inventory.Items.Clear(); + } - m_Inventory.Delete(); - } - } - } + m_Inventory.Delete(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Multis/BaseHouse.cs b/Scripts/Multis/BaseHouse.cs index 5da4eade8..6d6fda708 100644 --- a/Scripts/Multis/BaseHouse.cs +++ b/Scripts/Multis/BaseHouse.cs @@ -1,3857 +1,3835 @@ using System; using System.Collections; using System.Collections.Generic; +using Server.Accounting; +using Server.ContextMenus; +using Server.Ethics; +using Server.Guilds; +using Server.Gumps; using Server.Items; using Server.Misc; using Server.Mobiles; using Server.Multis.Deeds; -using Server.Regions; using Server.Network; +using Server.Regions; using Server.Targeting; -using Server.Accounting; -using Server.ContextMenus; -using Server.Gumps; -using Server.Guilds; namespace Server.Multis { - public abstract class BaseHouse : BaseMulti - { - public static bool NewVendorSystem // Is new player vendor system enabled? - => Core.AOS; + public abstract class BaseHouse : BaseMulti + { + public const int MaxCoOwners = 15; - public const int MaxCoOwners = 15; - public static int MaxFriends => !Core.AOS ? 50 : 140; - public static int MaxBans => !Core.AOS ? 50 : 140; + public const bool DecayEnabled = true; - #region Dynamic decay system - private DecayLevel m_CurrentStage; + public const int MaximumBarkeepCount = 2; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime NextDecayStage { get; set; } + private static Dictionary> m_Table = new Dictionary>(); - public void ResetDynamicDecay() - { - m_CurrentStage = DecayLevel.Ageless; - NextDecayStage = DateTime.MinValue; - } + private DecayLevel m_LastDecayLevel; - public void SetDynamicDecay( DecayLevel level ) - { - m_CurrentStage = level; + private Mobile m_Owner; - if ( DynamicDecay.Decays( level ) ) - NextDecayStage = DateTime.UtcNow + DynamicDecay.GetRandomDuration( level ); - else - NextDecayStage = DateTime.MinValue; - } - #endregion + private bool m_Public; - public const bool DecayEnabled = true; + private HouseRegion m_Region; - public static void Decay_OnTick() - { - for ( int i = 0; i < AllHouses.Count; ++i ) - AllHouses[i].CheckDecay(); - } + private Point3D m_RelativeBanLocation; + private TrashBarrel m_Trash; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastRefreshed { get; set; } + public BaseHouse(int multiID, Mobile owner, int MaxLockDown, int MaxSecure) : base(multiID) + { + AllHouses.Add(this); - [CommandProperty( AccessLevel.GameMaster )] - public bool RestrictDecay { get; set; } + LastRefreshed = DateTime.UtcNow; - public virtual TimeSpan DecayPeriod => TimeSpan.FromDays( 5.0 ); + BuiltOn = DateTime.UtcNow; + LastTraded = DateTime.MinValue; - public virtual DecayType DecayType - { - get - { - if ( RestrictDecay || !DecayEnabled || DecayPeriod == TimeSpan.Zero ) - return DecayType.Ageless; + Doors = new ArrayList(); + LockDowns = new ArrayList(); + Secures = new ArrayList(); + Addons = new ArrayList(); - if ( m_Owner == null ) - return Core.AOS ? DecayType.Condemned : DecayType.ManualRefresh; - - Account acct = m_Owner.Account as Account; - - if ( acct == null ) - return Core.AOS ? DecayType.Condemned : DecayType.ManualRefresh; + CoOwners = new ArrayList(); + Friends = new ArrayList(); + Bans = new ArrayList(); + Access = new ArrayList(); - if ( acct.AccessLevel >= AccessLevel.GameMaster ) - return DecayType.Ageless; - - for ( int i = 0; i < acct.Length; ++i ) - { - Mobile mob = acct[i]; - - if ( mob != null && mob.AccessLevel >= AccessLevel.GameMaster ) - return DecayType.Ageless; - } - - if ( !Core.AOS ) - return DecayType.ManualRefresh; - - if ( acct.Inactive ) - return DecayType.Condemned; - - List allHouses = new List(); - - for ( int i = 0; i < acct.Length; ++i ) - { - Mobile mob = acct[i]; - - if ( mob != null ) - allHouses.AddRange( GetHouses( mob ) ); - } - - BaseHouse newest = null; - - for ( int i = 0; i < allHouses.Count; ++i ) - { - BaseHouse check = allHouses[i]; - - if ( newest == null || IsNewer( check, newest ) ) - newest = check; - } - - if ( this == newest ) - return DecayType.AutoRefresh; - - return DecayType.ManualRefresh; - } - } - - public bool IsNewer( BaseHouse check, BaseHouse house ) - { - DateTime checkTime = ( check.LastTraded > check.BuiltOn ? check.LastTraded : check.BuiltOn ); - DateTime houseTime = ( house.LastTraded > house.BuiltOn ? house.LastTraded : house.BuiltOn ); - - return ( checkTime > houseTime ); - } - - public virtual bool CanDecay - { - get - { - DecayType type = DecayType; - - return ( type == DecayType.Condemned || type == DecayType.ManualRefresh ); - } - } - - private DecayLevel m_LastDecayLevel; - - [CommandProperty( AccessLevel.GameMaster )] - public virtual DecayLevel DecayLevel - { - get - { - DecayLevel result; + VendorRentalContracts = new ArrayList(); + InternalizedVendors = new ArrayList(); - if ( !CanDecay ) - { - if ( DynamicDecay.Enabled ) - ResetDynamicDecay(); + m_Owner = owner; - LastRefreshed = DateTime.UtcNow; - result = DecayLevel.Ageless; - } - else if ( DynamicDecay.Enabled ) - { - DecayLevel stage = m_CurrentStage; + MaxLockDowns = MaxLockDown; + MaxSecures = MaxSecure; - if ( stage == DecayLevel.Ageless || ( DynamicDecay.Decays( stage ) && NextDecayStage <= DateTime.UtcNow ) ) - SetDynamicDecay( ++stage ); - - if ( stage == DecayLevel.Collapsed && ( HasRentedVendors || VendorInventories.Count > 0 ) ) - result = DecayLevel.DemolitionPending; - else - result = stage; - } - else - { - result = GetOldDecayLevel(); - } + m_RelativeBanLocation = BaseBanLocation; - if ( result != m_LastDecayLevel ) - { - m_LastDecayLevel = result; + UpdateRegion(); - if ( Sign != null && !Sign.GettingProperties ) - Sign.InvalidateProperties(); - } + if (owner != null) + { + m_Table.TryGetValue(owner, out List list); - return result; - } - } + if (list == null) + m_Table[owner] = list = new List(); - public DecayLevel GetOldDecayLevel() - { - TimeSpan timeAfterRefresh = DateTime.UtcNow - LastRefreshed; - int percent = (int) ((timeAfterRefresh.Ticks * 1000) / DecayPeriod.Ticks); + list.Add(this); + } - if ( percent >= 1000 ) // 100.0% - return ( HasRentedVendors || VendorInventories.Count > 0 ) ? DecayLevel.DemolitionPending : DecayLevel.Collapsed; - if ( percent >= 950 ) // 95.0% - 99.9% - return DecayLevel.IDOC; - if ( percent >= 750 ) // 75.0% - 94.9% - return DecayLevel.Greatly; - if ( percent >= 500 ) // 50.0% - 74.9% - return DecayLevel.Fairly; - if ( percent >= 250 ) // 25.0% - 49.9% - return DecayLevel.Somewhat; - if ( percent >= 005 ) // 00.5% - 24.9% - return DecayLevel.Slightly; + Movable = false; + } - return DecayLevel.LikeNew; - } + public BaseHouse(Serial serial) : base(serial) + { + AllHouses.Add(this); + } - public virtual bool RefreshDecay() - { - if ( DecayType == DecayType.Condemned ) - return false; + public static bool NewVendorSystem // Is new player vendor system enabled? + => Core.AOS; - DecayLevel oldLevel = DecayLevel; + public static int MaxFriends => !Core.AOS ? 50 : 140; + public static int MaxBans => !Core.AOS ? 50 : 140; - LastRefreshed = DateTime.UtcNow; + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastRefreshed{ get; set; } - if ( DynamicDecay.Enabled ) - ResetDynamicDecay(); + [CommandProperty(AccessLevel.GameMaster)] + public bool RestrictDecay{ get; set; } - Sign?.InvalidateProperties(); + public virtual TimeSpan DecayPeriod => TimeSpan.FromDays(5.0); - return ( oldLevel > DecayLevel.LikeNew ); - } + public virtual DecayType DecayType + { + get + { + if (RestrictDecay || !DecayEnabled || DecayPeriod == TimeSpan.Zero) + return DecayType.Ageless; - public virtual bool CheckDecay() - { - if ( !Deleted && DecayLevel == DecayLevel.Collapsed ) - { - Timer.DelayCall( TimeSpan.Zero, Decay_Sandbox ); - return true; - } + if (m_Owner == null) + return Core.AOS ? DecayType.Condemned : DecayType.ManualRefresh; - return false; - } + Account acct = m_Owner.Account as Account; - public virtual void KillVendors() - { - ArrayList list = new ArrayList( PlayerVendors ); + if (acct == null) + return Core.AOS ? DecayType.Condemned : DecayType.ManualRefresh; - foreach ( PlayerVendor vendor in list ) - vendor.Destroy( true ); + if (acct.AccessLevel >= AccessLevel.GameMaster) + return DecayType.Ageless; - list = new ArrayList( PlayerBarkeepers ); + for (int i = 0; i < acct.Length; ++i) + { + Mobile mob = acct[i]; - foreach ( PlayerBarkeeper barkeeper in list ) - barkeeper.Delete(); - } + if (mob != null && mob.AccessLevel >= AccessLevel.GameMaster) + return DecayType.Ageless; + } - public virtual void Decay_Sandbox() - { - if ( Deleted ) - return; + if (!Core.AOS) + return DecayType.ManualRefresh; - if ( Core.ML ) - new TempNoHousingRegion( this, null ); + if (acct.Inactive) + return DecayType.Condemned; - KillVendors(); - Delete(); - } + List allHouses = new List(); - public virtual TimeSpan RestrictedPlacingTime => TimeSpan.FromHours( 1.0 ); + for (int i = 0; i < acct.Length; ++i) + { + Mobile mob = acct[i]; - [CommandProperty( AccessLevel.GameMaster )] - public virtual double BonusStorageScalar => (Core.ML ? 1.2 : 1.0); + if (mob != null) + allHouses.AddRange(GetHouses(mob)); + } - private bool m_Public; + BaseHouse newest = null; - private HouseRegion m_Region; - private TrashBarrel m_Trash; + for (int i = 0; i < allHouses.Count; ++i) + { + BaseHouse check = allHouses[i]; - private Mobile m_Owner; + if (newest == null || IsNewer(check, newest)) + newest = check; + } - private Point3D m_RelativeBanLocation; + if (this == newest) + return DecayType.AutoRefresh; - private static Dictionary> m_Table = new Dictionary>(); + return DecayType.ManualRefresh; + } + } - public virtual bool IsAosRules => Core.AOS; + public virtual bool CanDecay + { + get + { + DecayType type = DecayType; - public virtual bool IsActive => true; + return type == DecayType.Condemned || type == DecayType.ManualRefresh; + } + } - public virtual HousePlacementEntry GetAosEntry() - { - return HousePlacementEntry.Find( this ); - } + [CommandProperty(AccessLevel.GameMaster)] + public virtual DecayLevel DecayLevel + { + get + { + DecayLevel result; - public virtual int GetAosMaxSecures() - { - HousePlacementEntry hpe = GetAosEntry(); + if (!CanDecay) + { + if (DynamicDecay.Enabled) + ResetDynamicDecay(); - if ( hpe == null ) - return 0; + LastRefreshed = DateTime.UtcNow; + result = DecayLevel.Ageless; + } + else if (DynamicDecay.Enabled) + { + DecayLevel stage = m_CurrentStage; - return (int)(hpe.Storage * BonusStorageScalar); - } + if (stage == DecayLevel.Ageless || DynamicDecay.Decays(stage) && NextDecayStage <= DateTime.UtcNow) + SetDynamicDecay(++stage); - public virtual int GetAosMaxLockdowns() - { - HousePlacementEntry hpe = GetAosEntry(); + if (stage == DecayLevel.Collapsed && (HasRentedVendors || VendorInventories.Count > 0)) + result = DecayLevel.DemolitionPending; + else + result = stage; + } + else + { + result = GetOldDecayLevel(); + } + + if (result != m_LastDecayLevel) + { + m_LastDecayLevel = result; - if ( hpe == null ) - return 0; + if (Sign != null && !Sign.GettingProperties) + Sign.InvalidateProperties(); + } - return (int)(hpe.Lockdowns * BonusStorageScalar); - } + return result; + } + } + + public virtual TimeSpan RestrictedPlacingTime => TimeSpan.FromHours(1.0); + + [CommandProperty(AccessLevel.GameMaster)] + public virtual double BonusStorageScalar => Core.ML ? 1.2 : 1.0; + + public virtual bool IsAosRules => Core.AOS; + + public virtual bool IsActive => true; + + public bool HasPersonalVendors + { + get + { + foreach (PlayerVendor vendor in PlayerVendors) + if (!(vendor is RentedVendor)) + return true; + + return false; + } + } + + public bool HasRentedVendors + { + get + { + foreach (PlayerVendor vendor in PlayerVendors) + if (vendor is RentedVendor) + return true; + + return false; + } + } + + #region Mondain's Legacy + + public bool HasAddonContainers + { + get + { + foreach (Item item in Addons) + if (item is BaseAddonContainer) + return true; + + return false; + } + } + + #endregion + + public static List AllHouses{ get; } = new List(); + + public abstract Rectangle2D[] Area{ get; } + public abstract Point3D BaseBanLocation{ get; } + + public override bool Decays => false; + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner + { + get => m_Owner; + set + { + if (m_Owner != null) + { + m_Table.TryGetValue(m_Owner, out List list); + + if (list == null) + m_Table[m_Owner] = list = new List(); + + list.Remove(this); + m_Owner.Delta(MobileDelta.Noto); + } + + m_Owner = value; + + if (m_Owner != null) + { + m_Table.TryGetValue(m_Owner, out List list); + + if (list == null) + m_Table[m_Owner] = list = new List(); + + list.Add(this); + m_Owner.Delta(MobileDelta.Noto); + } + + Sign?.InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Visits{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Public + { + get => m_Public; + set + { + if (m_Public != value) + { + m_Public = value; + + if (!m_Public) // Privatizing the house, change to brass sign + ChangeSignType(0xBD2); + + Sign?.InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxSecures{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Point3D BanLocation + { + get + { + if (m_Region != null) + return m_Region.GoLocation; - public virtual int GetAosCurSecures( out int fromSecures, out int fromVendors, out int fromLockdowns, out int fromMovingCrate ) - { - fromSecures = 0; - fromVendors = 0; - fromLockdowns = 0; - fromMovingCrate = 0; + Point3D rel = m_RelativeBanLocation; + return new Point3D(X + rel.X, Y + rel.Y, Z + rel.Z); + } + set => RelativeBanLocation = new Point3D(value.X - X, value.Y - Y, value.Z - Z); + } - ArrayList list = Secures; + [CommandProperty(AccessLevel.GameMaster)] + public Point3D RelativeBanLocation + { + get => m_RelativeBanLocation; + set + { + m_RelativeBanLocation = value; - if ( list != null ) - { - for ( int i = 0; i < list.Count; ++i ) - { - SecureInfo si = (SecureInfo)list[i]; + if (m_Region != null) + m_Region.GoLocation = new Point3D(X + value.X, Y + value.Y, Z + value.Z); + } + } - fromSecures += si.Item.TotalItems; - } + [CommandProperty(AccessLevel.GameMaster)] + public int MaxLockDowns{ get; set; } - fromLockdowns += list.Count; - } + public Region Region => m_Region; + public ArrayList CoOwners{ get; set; } - fromLockdowns += GetLockdowns(); + public ArrayList Friends{ get; set; } - if ( !NewVendorSystem ) - { - foreach ( PlayerVendor vendor in PlayerVendors ) - { - if ( vendor.Backpack != null ) - { - fromVendors += vendor.Backpack.TotalItems; - } - } - } + public ArrayList Access{ get; set; } - if ( MovingCrate != null ) - { - fromMovingCrate += MovingCrate.TotalItems; - - foreach ( Item item in MovingCrate.Items ) - { - if ( item is PackingBox ) - fromMovingCrate--; - } - } - - return fromSecures + fromVendors + fromLockdowns + fromMovingCrate; - } - - public bool InRange( IPoint2D from, int range ) - { - if ( Region == null ) - return false; - - foreach ( Rectangle3D rect in Region.Area ) - { - if ( from.X >= rect.Start.X - range && from.Y >= rect.Start.Y - range && from.X < rect.End.X + range && from.Y < rect.End.Y + range ) - return true; - } - - return false; - } - - public virtual int GetNewVendorSystemMaxVendors() - { - HousePlacementEntry hpe = GetAosEntry(); - - if ( hpe == null ) - return 0; - - return (int)(hpe.Vendors * BonusStorageScalar); - } - - public virtual bool CanPlaceNewVendor() - { - if ( !IsAosRules ) - return true; - - if ( !NewVendorSystem ) - return CheckAosLockdowns( 10 ); - - return ( (PlayerVendors.Count + VendorRentalContracts.Count) < GetNewVendorSystemMaxVendors() ); - } - - public const int MaximumBarkeepCount = 2; - - public virtual bool CanPlaceNewBarkeep() - { - return ( PlayerBarkeepers.Count < MaximumBarkeepCount ); - } - - public static void IsThereVendor( Point3D location, Map map, out bool vendor, out bool rentalContract ) - { - vendor = false; - rentalContract = false; - - IPooledEnumerable eable = map.GetObjectsInRange( location, 0 ); - - foreach ( IEntity entity in eable ) - { - if ( Math.Abs( location.Z - entity.Z ) <= 16 ) - { - if ( entity is PlayerVendor || entity is PlayerBarkeeper || entity is PlayerVendorPlaceholder ) - { - vendor = true; - break; - } - - if ( entity is VendorRentalContract ) - { - rentalContract = true; - break; - } - } - } - - eable.Free(); - } - - public bool HasPersonalVendors - { - get - { - foreach ( PlayerVendor vendor in PlayerVendors ) - { - if ( !(vendor is RentedVendor) ) - return true; - } - - return false; - } - } - - public bool HasRentedVendors - { - get - { - foreach ( PlayerVendor vendor in PlayerVendors ) - { - if ( vendor is RentedVendor ) - return true; - } - - return false; - } - } - - #region Mondain's Legacy - public bool HasAddonContainers - { - get - { - foreach ( Item item in Addons ) - { - if ( item is BaseAddonContainer ) - return true; - } - - return false; - } - } - #endregion - - public ArrayList AvailableVendorsFor( Mobile m ) - { - ArrayList list = new ArrayList(); - - foreach ( PlayerVendor vendor in PlayerVendors ) - { - if ( vendor.CanInteractWith( m, false ) ) - list.Add( vendor ); - } - - return list; - } - - public bool AreThereAvailableVendorsFor( Mobile m ) - { - foreach ( PlayerVendor vendor in PlayerVendors ) - { - if ( vendor.CanInteractWith( m, false ) ) - return true; - } - - return false; - } - - public void MoveAllToCrate() - { - RelocatedEntities.Clear(); - - MovingCrate?.Hide(); - - if ( m_Trash != null ) - { - m_Trash.Delete(); - m_Trash = null; - } - - foreach ( Item item in LockDowns ) - { - if ( !item.Deleted ) - { - item.IsLockedDown = false; - item.IsSecure = false; - item.Movable = true; - - if ( item.Parent == null ) - DropToMovingCrate( item ); - } - } - - LockDowns.Clear(); - - foreach ( Item item in VendorRentalContracts ) - { - if ( !item.Deleted ) - { - item.IsLockedDown = false; - item.IsSecure = false; - item.Movable = true; - - if ( item.Parent == null ) - DropToMovingCrate( item ); - } - } - - VendorRentalContracts.Clear(); - - foreach ( SecureInfo info in Secures ) - { - Item item = info.Item; - - if ( !item.Deleted ) - { - if ( item is StrongBox ) - item = ((StrongBox)item).ConvertToStandardContainer(); - - item.IsLockedDown = false; - item.IsSecure = false; - item.Movable = true; - - if ( item.Parent == null ) - DropToMovingCrate( item ); - } - } - - Secures.Clear(); - - foreach ( Item addon in Addons ) - { - if ( !addon.Deleted ) - { - Item deed = null; - bool retainDeedHue = false; //if the items aren't hued but the deed itself is - int hue = 0; - - if ( addon is IAddon ) - { - deed = ((IAddon)addon).Deed; - - if ( addon is BaseAddon && ((BaseAddon)addon).RetainDeedHue) //There are things that are IAddon which aren't BaseAddon - { - BaseAddon ba = (BaseAddon)addon; - retainDeedHue = true; - - for( int i = 0; hue == 0 && i < ba.Components.Count; ++i ) - { - AddonComponent c = ba.Components[i]; - - if ( c.Hue != 0 ) - hue = c.Hue; - } - } - } - - if ( deed != null ) - { - #region Mondain's Legacy - if ( deed is BaseAddonContainerDeed && addon is BaseAddonContainer ) - { - BaseAddonContainer c = (BaseAddonContainer) addon; - c.DropItemsToGround(); - - ((BaseAddonContainerDeed) deed).Resource = c.Resource; - } - else if ( deed is BaseAddonDeed && addon is BaseAddon ) - ((BaseAddonDeed) deed).Resource = ((BaseAddon) addon).Resource; - #endregion - - addon.Delete(); - - if ( retainDeedHue ) - deed.Hue = hue; - - DropToMovingCrate( deed ); - } - else - { - DropToMovingCrate( addon ); - } - } - } - - Addons.Clear(); - - foreach ( PlayerVendor mobile in PlayerVendors ) - { - mobile.Return(); - mobile.Internalize(); - InternalizedVendors.Add( mobile ); - } - - foreach ( Mobile mobile in PlayerBarkeepers ) - { - mobile.Internalize(); - InternalizedVendors.Add( mobile ); - } - } - - public List GetHouseEntities() - { - List list = new List(); - - MovingCrate?.Hide(); - - if ( m_Trash != null && m_Trash.Map != Map.Internal ) - list.Add( m_Trash ); - - foreach ( Item item in LockDowns ) - { - if ( item.Parent == null && item.Map != Map.Internal ) - list.Add( item ); - } - - foreach ( Item item in VendorRentalContracts ) - { - if ( item.Parent == null && item.Map != Map.Internal ) - list.Add( item ); - } - - foreach ( SecureInfo info in Secures ) - { - Item item = info.Item; - - if ( item.Parent == null && item.Map != Map.Internal ) - list.Add( item ); - } - - foreach ( Item item in Addons ) - { - if ( item.Parent == null && item.Map != Map.Internal ) - list.Add( item ); - } - - foreach ( PlayerVendor mobile in PlayerVendors ) - { - mobile.Return(); - - if ( mobile.Map != Map.Internal ) - list.Add( mobile ); - } - - foreach ( Mobile mobile in PlayerBarkeepers ) - { - if ( mobile.Map != Map.Internal ) - list.Add( mobile ); - } - - return list; - } - - public void RelocateEntities() - { - foreach ( IEntity entity in GetHouseEntities() ) - { - Point3D relLoc = new Point3D( entity.X - X, entity.Y - Y, entity.Z - Z ); - RelocatedEntity relocEntity = new RelocatedEntity( entity, relLoc ); - - RelocatedEntities.Add( relocEntity ); - - if ( entity is Item ) - ((Item)entity).Internalize(); - else - ((Mobile)entity).Internalize(); - } - } - - public void RestoreRelocatedEntities() - { - foreach ( RelocatedEntity relocEntity in RelocatedEntities ) - { - Point3D relLoc = relocEntity.RelativeLocation; - Point3D location = new Point3D( relLoc.X + X, relLoc.Y + Y, relLoc.Z + Z ); - - IEntity entity = relocEntity.Entity; - if ( entity is Item ) - { - Item item = (Item) entity; - - if ( !item.Deleted ) - { - if ( item is IAddon ) - { - if ( ((IAddon)item).CouldFit( location, Map ) ) - { - item.MoveToWorld( location, Map ); - continue; - } - } - else - { - int height; - bool requireSurface; - if ( item is VendorRentalContract ) - { - height = 16; - requireSurface = true; - } - else - { - height = item.ItemData.Height; - requireSurface = false; - } - - if ( Map.CanFit( location.X, location.Y, location.Z, height, false, false, requireSurface ) ) - { - item.MoveToWorld( location, Map ); - continue; - } - } - - // The item can't fit - - if ( item is TrashBarrel ) - { - item.Delete(); // Trash barrels don't go to the moving crate - } - else - { - SetLockdown( item, false ); - item.IsSecure = false; - item.Movable = true; - - Item relocateItem = item; - - if ( item is StrongBox ) - relocateItem = ((StrongBox)item).ConvertToStandardContainer(); - - if ( item is IAddon ) - { - Item deed = ((IAddon)item).Deed; - bool retainDeedHue = false; //if the items aren't hued but the deed itself is - int hue = 0; - - if ( item is BaseAddon && ((BaseAddon)item).RetainDeedHue ) //There are things that are IAddon which aren't BaseAddon - { - BaseAddon ba = (BaseAddon)item; - retainDeedHue = true; - - for( int i = 0; hue == 0 && i < ba.Components.Count; ++i ) - { - AddonComponent c = ba.Components[i]; - - if ( c.Hue != 0 ) - hue = c.Hue; - } - } - - #region Mondain's Legacy - if ( deed != null ) - { - if ( deed is BaseAddonContainerDeed && item is BaseAddonContainer ) - { - BaseAddonContainer c = (BaseAddonContainer) item; - c.DropItemsToGround(); - - ((BaseAddonContainerDeed) deed).Resource = c.Resource; - } - else if ( deed is BaseAddonDeed && item is BaseAddon ) - ((BaseAddonDeed) deed).Resource = ((BaseAddon) item).Resource; - - if ( retainDeedHue ) - deed.Hue = hue; - } - #endregion - - relocateItem = deed; - item.Delete(); - } - - if ( relocateItem != null ) - DropToMovingCrate( relocateItem ); - } - } - - if ( m_Trash == item ) - m_Trash = null; - - LockDowns.Remove( item ); - VendorRentalContracts.Remove( item ); - Addons.Remove( item ); - for ( int i = Secures.Count - 1; i >= 0; i-- ) - { - if ( ((SecureInfo)Secures[i]).Item == item ) - Secures.RemoveAt( i ); - } - } - else - { - Mobile mobile = (Mobile) entity; - - if ( !mobile.Deleted ) - { - if ( Map.CanFit( location, 16, false, false ) ) - { - mobile.MoveToWorld( location, Map ); - } - else - { - InternalizedVendors.Add( mobile ); - } - } - } - } - - RelocatedEntities.Clear(); - } - - public void DropToMovingCrate( Item item ) - { - if ( MovingCrate == null ) - MovingCrate = new MovingCrate( this ); - - MovingCrate.DropItem( item ); - } - - public List GetItems() - { - if ( Map == null || Map == Map.Internal ) - return new List(); - - Point2D start = new Point2D( X + Components.Min.X, Y + Components.Min.Y ); - Point2D end = new Point2D( X + Components.Max.X + 1, Y + Components.Max.Y + 1 ); - Rectangle2D rect = new Rectangle2D( start, end ); - - List list = new List(); - - IPooledEnumerable eable = Map.GetItemsInBounds( rect ); - - foreach ( Item item in eable ) - if ( item.Movable && IsInside( item ) ) - list.Add( item ); - - eable.Free(); - - return list; - } - - public List GetMobiles() - { - if ( Map == null || Map == Map.Internal ) - return new List(); - - List list = new List(); - - foreach ( Mobile mobile in Region.GetMobiles() ) - if ( IsInside( mobile ) ) - list.Add( mobile ); - - return list; - } - - public virtual bool CheckAosLockdowns( int need ) - { - return ( (GetAosCurLockdowns() + need) <= GetAosMaxLockdowns() ); - } - - public virtual bool CheckAosStorage( int need ) - { - int fromSecures, fromVendors, fromLockdowns, fromMovingCrate; + public ArrayList Bans{ get; set; } - return ( (GetAosCurSecures( out fromSecures, out fromVendors, out fromLockdowns, out fromMovingCrate ) + need) <= GetAosMaxSecures() ); - } + public ArrayList Doors{ get; set; } - public static void Configure() - { - LockedDownFlag = 1; - SecureFlag = 2; + public int LockDownCount + { + get + { + int count = 0; - Timer.DelayCall( TimeSpan.FromMinutes( 1.0 ), TimeSpan.FromMinutes( 1.0 ), Decay_OnTick ); - } + count += GetLockdowns(); - public virtual int GetAosCurLockdowns() - { - int v = 0; + if (Secures != null) + for (int i = 0; i < Secures.Count; ++i) + { + SecureInfo info = (SecureInfo)Secures[i]; - v += GetLockdowns(); + if (info.Item.Deleted) + continue; + if (info.Item is StrongBox) + count += 1; + else + count += 125; + } - if ( Secures != null ) - v += Secures.Count; + return count; + } + } - if ( !NewVendorSystem ) - v += PlayerVendors.Count * 10; + public int SecureCount + { + get + { + int count = 0; - return v; - } + if (Secures != null) + for (int i = 0; i < Secures.Count; i++) + { + SecureInfo info = (SecureInfo)Secures[i]; - public static bool CheckLockedDown( Item item ) - { - BaseHouse house = FindHouseAt( item ); + if (info.Item.Deleted) + continue; + if (!(info.Item is StrongBox)) + count += 1; + } - return ( house != null && house.IsLockedDown( item ) ); - } + return count; + } + } - public static bool CheckSecured( Item item ) - { - BaseHouse house = FindHouseAt( item ); + public ArrayList Addons{ get; set; } - return ( house != null && house.IsSecure( item ) ); - } + public ArrayList LockDowns{ get; private set; } - public static bool CheckLockedDownOrSecured( Item item ) - { - BaseHouse house = FindHouseAt( item ); + public ArrayList Secures{ get; private set; } - return ( house != null && (house.IsSecure( item ) || house.IsLockedDown( item )) ); - } + public HouseSign Sign{ get; set; } - public static List GetHouses( Mobile m ) - { - List list = new List(); + public ArrayList PlayerVendors{ get; } = new ArrayList(); - if ( m != null ) - { - m_Table.TryGetValue( m, out List exists ); + public ArrayList PlayerBarkeepers{ get; } = new ArrayList(); - if ( exists != null ) - { - for ( int i = 0; i < exists.Count; ++i ) - { - BaseHouse house = exists[i]; + public ArrayList VendorRentalContracts{ get; private set; } - if ( house != null && !house.Deleted && house.Owner == m ) - list.Add( house ); - } - } - } + public ArrayList VendorInventories{ get; } = new ArrayList(); - return list; - } + public ArrayList RelocatedEntities{ get; } = new ArrayList(); - public static bool CheckHold( Mobile m, Container cont, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - BaseHouse house = FindHouseAt( cont ); + public MovingCrate MovingCrate{ get; set; } - if ( house == null || !house.IsAosRules ) - return true; + public ArrayList InternalizedVendors{ get; private set; } - if ( house.IsSecure( cont ) && !house.CheckAosStorage( 1 + item.TotalItems + plusItems ) ) - { - if ( message ) - m.SendLocalizedMessage( 1061839 ); // This action would exceed the secure storage limit of the house. + public DateTime BuiltOn{ get; set; } - return false; - } + public DateTime LastTraded{ get; set; } - return true; - } + public virtual HousePlacementEntry ConvertEntry => null; + public virtual int ConvertOffsetX => 0; + public virtual int ConvertOffsetY => 0; + public virtual int ConvertOffsetZ => 0; - public static bool CheckAccessible( Mobile m, Item item ) - { - if ( m.AccessLevel >= AccessLevel.GameMaster ) - return true; // Staff can access anything - - BaseHouse house = FindHouseAt( item ); - - if ( house == null ) - return true; - - SecureAccessResult res = house.CheckSecureAccess( m, item ); - - switch ( res ) - { - case SecureAccessResult.Insecure: break; - case SecureAccessResult.Accessible: return true; - case SecureAccessResult.Inaccessible: return false; - } - - if ( house.IsLockedDown( item ) ) - return house.IsCoOwner( m ) && (item is Container); - - return true; - } - - public static BaseHouse FindHouseAt( Mobile m ) - { - if ( m == null || m.Deleted ) - return null; - - return FindHouseAt( m.Location, m.Map, 16 ); - } - - public static BaseHouse FindHouseAt( Item item ) - { - if ( item == null || item.Deleted ) - return null; - - return FindHouseAt( item.GetWorldLocation(), item.Map, item.ItemData.Height ); - } - - public static BaseHouse FindHouseAt( Point3D loc, Map map, int height ) - { - if ( map == null || map == Map.Internal ) - return null; - - Sector sector = map.GetSector( loc ); - - for ( int i = 0; i < sector.Multis.Count; ++i ) - { - BaseHouse house = sector.Multis[i] as BaseHouse; - - if ( house != null && house.IsInside( loc, height ) ) - return house; - } - - return null; - } - - public bool IsInside( Mobile m ) - { - if ( m == null || m.Deleted || m.Map != Map ) - return false; - - return IsInside( m.Location, 16 ); - } - - public bool IsInside( Item item ) - { - if ( item == null || item.Deleted || item.Map != Map ) - return false; - - return IsInside( item.Location, item.ItemData.Height ); - } - - public bool CheckAccessibility( Item item, Mobile from ) - { - SecureAccessResult res = CheckSecureAccess( from, item ); - - switch ( res ) - { - case SecureAccessResult.Insecure: break; - case SecureAccessResult.Accessible: return true; - case SecureAccessResult.Inaccessible: return false; - } - - if ( !IsLockedDown( item ) ) - return true; - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return true; - if ( item is Runebook ) - return true; - if ( item is ISecurable ) - return HasSecureAccess( from, ((ISecurable)item).Level ); - if ( item is Container ) - return IsCoOwner( from ); - if ( item.Stackable ) - return true; - if ( item is BaseLight ) - return IsFriend( from ); - if ( item is PotionKeg ) - return IsFriend( from ); - if ( item is BaseBoard ) - return true; - if ( item is Dices ) - return true; - if ( item is RecallRune ) - return true; - if ( item is TreasureMap ) - return true; - if ( item is Clock ) - return true; - if ( item is BaseInstrument ) - return true; - if ( item is Dyes || item is DyeTub ) - return true; - if ( item is VendorRentalContract ) - return true; - if ( item is RewardBrazier ) - return true; - - return false; - } - - public virtual bool IsInside( Point3D p, int height ) - { - if ( Deleted ) - return false; - - MultiComponentList mcl = Components; - - int x = p.X - (X + mcl.Min.X); - int y = p.Y - (Y + mcl.Min.Y); - - if ( x < 0 || x >= mcl.Width || y < 0 || y >= mcl.Height ) - return false; - - if ( this is HouseFoundation && y < (mcl.Height-1) && p.Z >= Z ) - return true; - - StaticTile[] tiles = mcl.Tiles[x][y]; - - for ( int j = 0; j < tiles.Length; ++j ) - { - StaticTile tile = tiles[j]; - int id = tile.ID & TileData.MaxItemValue; - ItemData data = TileData.ItemTable[id]; - - // Slanted roofs do not count; they overhang blocking south and east sides of the multi - if ( (data.Flags & TileFlag.Roof) != 0 ) - continue; - - // Signs and signposts are not considered part of the multi - if ( (id >= 0xB95 && id <= 0xC0E) || (id >= 0xC43 && id <= 0xC44) ) - continue; - - int tileZ = tile.Z + Z; - - if ( p.Z == tileZ || (p.Z + height) > tileZ ) - return true; - } - - return false; - } - - public SecureAccessResult CheckSecureAccess( Mobile m, Item item ) - { - if ( Secures == null || !(item is Container) ) - return SecureAccessResult.Insecure; - - for ( int i = 0; i < Secures.Count; ++i ) - { - SecureInfo info = (SecureInfo)Secures[i]; - - if ( info.Item == item ) - return HasSecureAccess( m, info.Level ) ? SecureAccessResult.Accessible : SecureAccessResult.Inaccessible; - } - - return SecureAccessResult.Insecure; - } - - public static List AllHouses { get; } = new List(); - - public BaseHouse( int multiID, Mobile owner, int MaxLockDown, int MaxSecure ) : base( multiID ) - { - AllHouses.Add( this ); - - LastRefreshed = DateTime.UtcNow; - - BuiltOn = DateTime.UtcNow; - LastTraded = DateTime.MinValue; - - Doors = new ArrayList(); - LockDowns = new ArrayList(); - Secures = new ArrayList(); - Addons = new ArrayList(); - - CoOwners = new ArrayList(); - Friends = new ArrayList(); - Bans = new ArrayList(); - Access = new ArrayList(); - - VendorRentalContracts = new ArrayList(); - InternalizedVendors = new ArrayList(); - - m_Owner = owner; - - MaxLockDowns = MaxLockDown; - MaxSecures = MaxSecure; - - m_RelativeBanLocation = BaseBanLocation; - - UpdateRegion(); - - if ( owner != null ) - { - m_Table.TryGetValue( owner, out List list ); + public virtual int DefaultPrice => 0; - if ( list == null ) - m_Table[owner] = list = new List(); + [CommandProperty(AccessLevel.GameMaster)] + public int Price{ get; set; } - list.Add( this ); - } + public static void Decay_OnTick() + { + for (int i = 0; i < AllHouses.Count; ++i) + AllHouses[i].CheckDecay(); + } - Movable = false; - } + public bool IsNewer(BaseHouse check, BaseHouse house) + { + DateTime checkTime = check.LastTraded > check.BuiltOn ? check.LastTraded : check.BuiltOn; + DateTime houseTime = house.LastTraded > house.BuiltOn ? house.LastTraded : house.BuiltOn; - public BaseHouse( Serial serial ) : base( serial ) - { - AllHouses.Add( this ); - } + return checkTime > houseTime; + } - public override void OnMapChange() - { - if ( LockDowns == null ) - return; + public DecayLevel GetOldDecayLevel() + { + TimeSpan timeAfterRefresh = DateTime.UtcNow - LastRefreshed; + int percent = (int)(timeAfterRefresh.Ticks * 1000 / DecayPeriod.Ticks); - UpdateRegion(); + if (percent >= 1000) // 100.0% + return HasRentedVendors || VendorInventories.Count > 0 ? DecayLevel.DemolitionPending : DecayLevel.Collapsed; + if (percent >= 950) // 95.0% - 99.9% + return DecayLevel.IDOC; + if (percent >= 750) // 75.0% - 94.9% + return DecayLevel.Greatly; + if (percent >= 500) // 50.0% - 74.9% + return DecayLevel.Fairly; + if (percent >= 250) // 25.0% - 49.9% + return DecayLevel.Somewhat; + if (percent >= 005) // 00.5% - 24.9% + return DecayLevel.Slightly; - if ( Sign != null && !Sign.Deleted ) - Sign.Map = Map; + return DecayLevel.LikeNew; + } - if ( Doors != null ) - { - foreach ( Item item in Doors ) - item.Map = Map; - } + public virtual bool RefreshDecay() + { + if (DecayType == DecayType.Condemned) + return false; - foreach ( IEntity entity in GetHouseEntities() ) - { - if ( entity is Item ) - ((Item)entity).Map = Map; - else - ((Mobile)entity).Map = Map; - } - } + DecayLevel oldLevel = DecayLevel; - public virtual void ChangeSignType( int itemID ) - { - if ( Sign != null ) - Sign.ItemID = itemID; - } + LastRefreshed = DateTime.UtcNow; - public abstract Rectangle2D[] Area{ get; } - public abstract Point3D BaseBanLocation{ get; } + if (DynamicDecay.Enabled) + ResetDynamicDecay(); - public virtual void UpdateRegion() - { - m_Region?.Unregister(); + Sign?.InvalidateProperties(); - if ( Map != null ) - { - m_Region = new HouseRegion( this ); - m_Region.Register(); - } - else - { - m_Region = null; - } - } + return oldLevel > DecayLevel.LikeNew; + } - public override void OnLocationChange( Point3D oldLocation ) - { - if ( LockDowns == null ) - return; + public virtual bool CheckDecay() + { + if (!Deleted && DecayLevel == DecayLevel.Collapsed) + { + Timer.DelayCall(TimeSpan.Zero, Decay_Sandbox); + return true; + } - int x = base.Location.X - oldLocation.X; - int y = base.Location.Y - oldLocation.Y; - int z = base.Location.Z - oldLocation.Z; + return false; + } - if ( Sign != null && !Sign.Deleted ) - Sign.Location = new Point3D( Sign.X + x, Sign.Y + y, Sign.Z + z ); + public virtual void KillVendors() + { + ArrayList list = new ArrayList(PlayerVendors); - UpdateRegion(); + foreach (PlayerVendor vendor in list) + vendor.Destroy(true); - if ( Doors != null ) - { - foreach ( Item item in Doors ) - { - if ( !item.Deleted ) - item.Location = new Point3D( item.X + x, item.Y + y, item.Z + z ); - } - } + list = new ArrayList(PlayerBarkeepers); - foreach ( IEntity entity in GetHouseEntities() ) - { - Point3D newLocation = new Point3D( entity.X + x, entity.Y + y, entity.Z + z ); + foreach (PlayerBarkeeper barkeeper in list) + barkeeper.Delete(); + } - if ( entity is Item ) - ((Item)entity).Location = newLocation; - else - ((Mobile)entity).Location = newLocation; - } - } - - public BaseDoor AddEastDoor( int x, int y, int z ) - { - return AddEastDoor( true, x, y, z ); - } + public virtual void Decay_Sandbox() + { + if (Deleted) + return; - public BaseDoor AddEastDoor( bool wood, int x, int y, int z ) - { - BaseDoor door = MakeDoor( wood, DoorFacing.SouthCW ); + if (Core.ML) + new TempNoHousingRegion(this, null); - AddDoor( door, x, y, z ); + KillVendors(); + Delete(); + } - return door; - } + public virtual HousePlacementEntry GetAosEntry() + { + return HousePlacementEntry.Find(this); + } - public BaseDoor AddSouthDoor( int x, int y, int z ) - { - return AddSouthDoor( true, x, y, z ); - } + public virtual int GetAosMaxSecures() + { + HousePlacementEntry hpe = GetAosEntry(); - public BaseDoor AddSouthDoor( bool wood, int x, int y, int z ) - { - BaseDoor door = MakeDoor( wood, DoorFacing.WestCW ); + if (hpe == null) + return 0; - AddDoor( door, x, y, z ); - - return door; - } - - public BaseDoor AddEastDoor( int x, int y, int z, uint k ) - { - return AddEastDoor( true, x, y, z, k ); - } + return (int)(hpe.Storage * BonusStorageScalar); + } - public BaseDoor AddEastDoor( bool wood, int x, int y, int z, uint k ) - { - BaseDoor door = MakeDoor( wood, DoorFacing.SouthCW ); + public virtual int GetAosMaxLockdowns() + { + HousePlacementEntry hpe = GetAosEntry(); + + if (hpe == null) + return 0; - door.Locked = true; - door.KeyValue = k; + return (int)(hpe.Lockdowns * BonusStorageScalar); + } + + public virtual int GetAosCurSecures(out int fromSecures, out int fromVendors, out int fromLockdowns, + out int fromMovingCrate) + { + fromSecures = 0; + fromVendors = 0; + fromLockdowns = 0; + fromMovingCrate = 0; + + ArrayList list = Secures; - AddDoor( door, x, y, z ); + if (list != null) + { + for (int i = 0; i < list.Count; ++i) + { + SecureInfo si = (SecureInfo)list[i]; - return door; - } + fromSecures += si.Item.TotalItems; + } - public BaseDoor AddSouthDoor( int x, int y, int z, uint k ) - { - return AddSouthDoor( true, x, y, z, k ); - } + fromLockdowns += list.Count; + } - public BaseDoor AddSouthDoor( bool wood, int x, int y, int z, uint k ) - { - BaseDoor door = MakeDoor( wood, DoorFacing.WestCW ); + fromLockdowns += GetLockdowns(); - door.Locked = true; - door.KeyValue = k; + if (!NewVendorSystem) + foreach (PlayerVendor vendor in PlayerVendors) + if (vendor.Backpack != null) + fromVendors += vendor.Backpack.TotalItems; - AddDoor( door, x, y, z ); + if (MovingCrate != null) + { + fromMovingCrate += MovingCrate.TotalItems; - return door; - } + foreach (Item item in MovingCrate.Items) + if (item is PackingBox) + fromMovingCrate--; + } - public BaseDoor[] AddSouthDoors( int x, int y, int z, uint k ) - { - return AddSouthDoors( true, x, y, z, k ); - } + return fromSecures + fromVendors + fromLockdowns + fromMovingCrate; + } + + public bool InRange(IPoint2D from, int range) + { + if (Region == null) + return false; - public BaseDoor[] AddSouthDoors( bool wood, int x, int y, int z, uint k ) - { - BaseDoor westDoor = MakeDoor( wood, DoorFacing.WestCW ); - BaseDoor eastDoor = MakeDoor( wood, DoorFacing.EastCCW ); + foreach (Rectangle3D rect in Region.Area) + if (from.X >= rect.Start.X - range && from.Y >= rect.Start.Y - range && from.X < rect.End.X + range && + from.Y < rect.End.Y + range) + return true; - westDoor.Locked = true; - eastDoor.Locked = true; + return false; + } - westDoor.KeyValue = k; - eastDoor.KeyValue = k; + public virtual int GetNewVendorSystemMaxVendors() + { + HousePlacementEntry hpe = GetAosEntry(); + + if (hpe == null) + return 0; + + return (int)(hpe.Vendors * BonusStorageScalar); + } + + public virtual bool CanPlaceNewVendor() + { + if (!IsAosRules) + return true; + + if (!NewVendorSystem) + return CheckAosLockdowns(10); + + return PlayerVendors.Count + VendorRentalContracts.Count < GetNewVendorSystemMaxVendors(); + } + + public virtual bool CanPlaceNewBarkeep() + { + return PlayerBarkeepers.Count < MaximumBarkeepCount; + } + + public static void IsThereVendor(Point3D location, Map map, out bool vendor, out bool rentalContract) + { + vendor = false; + rentalContract = false; + + IPooledEnumerable eable = map.GetObjectsInRange(location, 0); + + foreach (IEntity entity in eable) + if (Math.Abs(location.Z - entity.Z) <= 16) + { + if (entity is PlayerVendor || entity is PlayerBarkeeper || entity is PlayerVendorPlaceholder) + { + vendor = true; + break; + } + + if (entity is VendorRentalContract) + { + rentalContract = true; + break; + } + } + + eable.Free(); + } + + public ArrayList AvailableVendorsFor(Mobile m) + { + ArrayList list = new ArrayList(); + + foreach (PlayerVendor vendor in PlayerVendors) + if (vendor.CanInteractWith(m, false)) + list.Add(vendor); + + return list; + } + + public bool AreThereAvailableVendorsFor(Mobile m) + { + foreach (PlayerVendor vendor in PlayerVendors) + if (vendor.CanInteractWith(m, false)) + return true; + + return false; + } + + public void MoveAllToCrate() + { + RelocatedEntities.Clear(); + + MovingCrate?.Hide(); + + if (m_Trash != null) + { + m_Trash.Delete(); + m_Trash = null; + } + + foreach (Item item in LockDowns) + if (!item.Deleted) + { + item.IsLockedDown = false; + item.IsSecure = false; + item.Movable = true; + + if (item.Parent == null) + DropToMovingCrate(item); + } + + LockDowns.Clear(); + + foreach (Item item in VendorRentalContracts) + if (!item.Deleted) + { + item.IsLockedDown = false; + item.IsSecure = false; + item.Movable = true; + + if (item.Parent == null) + DropToMovingCrate(item); + } + + VendorRentalContracts.Clear(); + + foreach (SecureInfo info in Secures) + { + Item item = info.Item; + + if (!item.Deleted) + { + if (item is StrongBox) + item = ((StrongBox)item).ConvertToStandardContainer(); + + item.IsLockedDown = false; + item.IsSecure = false; + item.Movable = true; + + if (item.Parent == null) + DropToMovingCrate(item); + } + } + + Secures.Clear(); + + foreach (Item addon in Addons) + if (!addon.Deleted) + { + Item deed = null; + bool retainDeedHue = false; //if the items aren't hued but the deed itself is + int hue = 0; + + if (addon is IAddon) + { + deed = ((IAddon)addon).Deed; + + if (addon is BaseAddon && ((BaseAddon)addon).RetainDeedHue + ) //There are things that are IAddon which aren't BaseAddon + { + BaseAddon ba = (BaseAddon)addon; + retainDeedHue = true; + + for (int i = 0; hue == 0 && i < ba.Components.Count; ++i) + { + AddonComponent c = ba.Components[i]; + + if (c.Hue != 0) + hue = c.Hue; + } + } + } + + if (deed != null) + { + #region Mondain's Legacy + + if (deed is BaseAddonContainerDeed && addon is BaseAddonContainer) + { + BaseAddonContainer c = (BaseAddonContainer)addon; + c.DropItemsToGround(); + + ((BaseAddonContainerDeed)deed).Resource = c.Resource; + } + else if (deed is BaseAddonDeed && addon is BaseAddon) + { + ((BaseAddonDeed)deed).Resource = ((BaseAddon)addon).Resource; + } + + #endregion + + addon.Delete(); + + if (retainDeedHue) + deed.Hue = hue; + + DropToMovingCrate(deed); + } + else + { + DropToMovingCrate(addon); + } + } + + Addons.Clear(); + + foreach (PlayerVendor mobile in PlayerVendors) + { + mobile.Return(); + mobile.Internalize(); + InternalizedVendors.Add(mobile); + } + + foreach (Mobile mobile in PlayerBarkeepers) + { + mobile.Internalize(); + InternalizedVendors.Add(mobile); + } + } + + public List GetHouseEntities() + { + List list = new List(); + + MovingCrate?.Hide(); + + if (m_Trash != null && m_Trash.Map != Map.Internal) + list.Add(m_Trash); + + foreach (Item item in LockDowns) + if (item.Parent == null && item.Map != Map.Internal) + list.Add(item); + + foreach (Item item in VendorRentalContracts) + if (item.Parent == null && item.Map != Map.Internal) + list.Add(item); + + foreach (SecureInfo info in Secures) + { + Item item = info.Item; + + if (item.Parent == null && item.Map != Map.Internal) + list.Add(item); + } + + foreach (Item item in Addons) + if (item.Parent == null && item.Map != Map.Internal) + list.Add(item); + + foreach (PlayerVendor mobile in PlayerVendors) + { + mobile.Return(); + + if (mobile.Map != Map.Internal) + list.Add(mobile); + } + + foreach (Mobile mobile in PlayerBarkeepers) + if (mobile.Map != Map.Internal) + list.Add(mobile); + + return list; + } + + public void RelocateEntities() + { + foreach (IEntity entity in GetHouseEntities()) + { + Point3D relLoc = new Point3D(entity.X - X, entity.Y - Y, entity.Z - Z); + RelocatedEntity relocEntity = new RelocatedEntity(entity, relLoc); + + RelocatedEntities.Add(relocEntity); + + if (entity is Item) + ((Item)entity).Internalize(); + else + ((Mobile)entity).Internalize(); + } + } + + public void RestoreRelocatedEntities() + { + foreach (RelocatedEntity relocEntity in RelocatedEntities) + { + Point3D relLoc = relocEntity.RelativeLocation; + Point3D location = new Point3D(relLoc.X + X, relLoc.Y + Y, relLoc.Z + Z); + + IEntity entity = relocEntity.Entity; + if (entity is Item) + { + Item item = (Item)entity; + + if (!item.Deleted) + { + if (item is IAddon) + { + if (((IAddon)item).CouldFit(location, Map)) + { + item.MoveToWorld(location, Map); + continue; + } + } + else + { + int height; + bool requireSurface; + if (item is VendorRentalContract) + { + height = 16; + requireSurface = true; + } + else + { + height = item.ItemData.Height; + requireSurface = false; + } + + if (Map.CanFit(location.X, location.Y, location.Z, height, false, false, requireSurface)) + { + item.MoveToWorld(location, Map); + continue; + } + } + + // The item can't fit + + if (item is TrashBarrel) + { + item.Delete(); // Trash barrels don't go to the moving crate + } + else + { + SetLockdown(item, false); + item.IsSecure = false; + item.Movable = true; + + Item relocateItem = item; + + if (item is StrongBox) + relocateItem = ((StrongBox)item).ConvertToStandardContainer(); + + if (item is IAddon) + { + Item deed = ((IAddon)item).Deed; + bool retainDeedHue = false; //if the items aren't hued but the deed itself is + int hue = 0; + + if (item is BaseAddon && ((BaseAddon)item).RetainDeedHue + ) //There are things that are IAddon which aren't BaseAddon + { + BaseAddon ba = (BaseAddon)item; + retainDeedHue = true; + + for (int i = 0; hue == 0 && i < ba.Components.Count; ++i) + { + AddonComponent c = ba.Components[i]; + + if (c.Hue != 0) + hue = c.Hue; + } + } + + #region Mondain's Legacy + + if (deed != null) + { + if (deed is BaseAddonContainerDeed && item is BaseAddonContainer) + { + BaseAddonContainer c = (BaseAddonContainer)item; + c.DropItemsToGround(); + + ((BaseAddonContainerDeed)deed).Resource = c.Resource; + } + else if (deed is BaseAddonDeed && item is BaseAddon) + { + ((BaseAddonDeed)deed).Resource = ((BaseAddon)item).Resource; + } + + if (retainDeedHue) + deed.Hue = hue; + } + + #endregion + + relocateItem = deed; + item.Delete(); + } + + if (relocateItem != null) + DropToMovingCrate(relocateItem); + } + } + + if (m_Trash == item) + m_Trash = null; + + LockDowns.Remove(item); + VendorRentalContracts.Remove(item); + Addons.Remove(item); + for (int i = Secures.Count - 1; i >= 0; i--) + if (((SecureInfo)Secures[i]).Item == item) + Secures.RemoveAt(i); + } + else + { + Mobile mobile = (Mobile)entity; + + if (!mobile.Deleted) + { + if (Map.CanFit(location, 16, false, false)) + mobile.MoveToWorld(location, Map); + else + InternalizedVendors.Add(mobile); + } + } + } + + RelocatedEntities.Clear(); + } + + public void DropToMovingCrate(Item item) + { + if (MovingCrate == null) + MovingCrate = new MovingCrate(this); + + MovingCrate.DropItem(item); + } + + public List GetItems() + { + if (Map == null || Map == Map.Internal) + return new List(); + + Point2D start = new Point2D(X + Components.Min.X, Y + Components.Min.Y); + Point2D end = new Point2D(X + Components.Max.X + 1, Y + Components.Max.Y + 1); + Rectangle2D rect = new Rectangle2D(start, end); + + List list = new List(); + + IPooledEnumerable eable = Map.GetItemsInBounds(rect); + + foreach (Item item in eable) + if (item.Movable && IsInside(item)) + list.Add(item); + + eable.Free(); - westDoor.Link = eastDoor; - eastDoor.Link = westDoor; + return list; + } - AddDoor( westDoor, x, y, z ); - AddDoor( eastDoor, x + 1, y, z ); + public List GetMobiles() + { + if (Map == null || Map == Map.Internal) + return new List(); - return new BaseDoor[2]{ westDoor, eastDoor }; - } + List list = new List(); - public uint CreateKeys( Mobile m ) - { - uint value = Key.RandomValue(); + foreach (Mobile mobile in Region.GetMobiles()) + if (IsInside(mobile)) + list.Add(mobile); - if ( !IsAosRules ) - { - Key packKey = new Key( KeyType.Gold ); - Key bankKey = new Key( KeyType.Gold ); + return list; + } - packKey.KeyValue = value; - bankKey.KeyValue = value; + public virtual bool CheckAosLockdowns(int need) + { + return GetAosCurLockdowns() + need <= GetAosMaxLockdowns(); + } - packKey.LootType = LootType.Newbied; - bankKey.LootType = LootType.Newbied; + public virtual bool CheckAosStorage(int need) + { + int fromSecures, fromVendors, fromLockdowns, fromMovingCrate; - BankBox box = m.BankBox; + return GetAosCurSecures(out fromSecures, out fromVendors, out fromLockdowns, out fromMovingCrate) + need <= + GetAosMaxSecures(); + } - if ( !box.TryDropItem( m, bankKey, false ) ) - bankKey.Delete(); + public static void Configure() + { + LockedDownFlag = 1; + SecureFlag = 2; - m.AddToBackpack( packKey ); - } + Timer.DelayCall(TimeSpan.FromMinutes(1.0), TimeSpan.FromMinutes(1.0), Decay_OnTick); + } - return value; - } + public virtual int GetAosCurLockdowns() + { + int v = 0; - public BaseDoor[] AddSouthDoors( int x, int y, int z ) - { - return AddSouthDoors( true, x, y, z, false ); - } + v += GetLockdowns(); - public BaseDoor[] AddSouthDoors( bool wood, int x, int y, int z, bool inv ) - { - BaseDoor westDoor = MakeDoor( wood, inv ? DoorFacing.WestCCW : DoorFacing.WestCW ); - BaseDoor eastDoor = MakeDoor( wood, inv ? DoorFacing.EastCW : DoorFacing.EastCCW ); + if (Secures != null) + v += Secures.Count; - westDoor.Link = eastDoor; - eastDoor.Link = westDoor; + if (!NewVendorSystem) + v += PlayerVendors.Count * 10; - AddDoor( westDoor, x, y, z ); - AddDoor( eastDoor, x + 1, y, z ); + return v; + } - return new BaseDoor[2]{ westDoor, eastDoor }; - } + public static bool CheckLockedDown(Item item) + { + BaseHouse house = FindHouseAt(item); - public BaseDoor MakeDoor( bool wood, DoorFacing facing ) - { - if ( wood ) - return new DarkWoodHouseDoor( facing ); - return new MetalHouseDoor( facing ); - } + return house != null && house.IsLockedDown(item); + } - public void AddDoor( BaseDoor door, int xoff, int yoff, int zoff ) - { - door.MoveToWorld( new Point3D( xoff+X, yoff+Y, zoff+Z ), Map ); - Doors.Add( door ); - } + public static bool CheckSecured(Item item) + { + BaseHouse house = FindHouseAt(item); - public void AddTrashBarrel( Mobile from ) - { - if ( !IsActive ) - return; + return house != null && house.IsSecure(item); + } - for ( int i = 0; Doors != null && i < Doors.Count; ++i ) - { - BaseDoor door = Doors[i] as BaseDoor; - Point3D p = door.Location; + public static bool CheckLockedDownOrSecured(Item item) + { + BaseHouse house = FindHouseAt(item); - if ( door.Open ) - p = new Point3D( p.X - door.Offset.X, p.Y - door.Offset.Y, p.Z - door.Offset.Z ); + return house != null && (house.IsSecure(item) || house.IsLockedDown(item)); + } - if ( (from.Z + 16) >= p.Z && (p.Z + 16) >= from.Z ) - { - if ( from.InRange( p, 1 ) ) - { - from.SendLocalizedMessage( 502120 ); // You cannot place a trash barrel near a door or near steps. - return; - } - } - } + public static List GetHouses(Mobile m) + { + List list = new List(); - if ( m_Trash == null || m_Trash.Deleted ) - { - m_Trash = new TrashBarrel(); + if (m != null) + { + m_Table.TryGetValue(m, out List exists); - m_Trash.Movable = false; - m_Trash.MoveToWorld( from.Location, from.Map ); + if (exists != null) + for (int i = 0; i < exists.Count; ++i) + { + BaseHouse house = exists[i]; - from.SendLocalizedMessage( 502121 ); /* You have a new trash barrel. + if (house != null && !house.Deleted && house.Owner == m) + list.Add(house); + } + } + + return list; + } + + public static bool CheckHold(Mobile m, Container cont, Item item, bool message, bool checkItems, int plusItems, + int plusWeight) + { + BaseHouse house = FindHouseAt(cont); + + if (house == null || !house.IsAosRules) + return true; + + if (house.IsSecure(cont) && !house.CheckAosStorage(1 + item.TotalItems + plusItems)) + { + if (message) + m.SendLocalizedMessage(1061839); // This action would exceed the secure storage limit of the house. + + return false; + } + + return true; + } + + public static bool CheckAccessible(Mobile m, Item item) + { + if (m.AccessLevel >= AccessLevel.GameMaster) + return true; // Staff can access anything + + BaseHouse house = FindHouseAt(item); + + if (house == null) + return true; + + SecureAccessResult res = house.CheckSecureAccess(m, item); + + switch (res) + { + case SecureAccessResult.Insecure: break; + case SecureAccessResult.Accessible: return true; + case SecureAccessResult.Inaccessible: return false; + } + + if (house.IsLockedDown(item)) + return house.IsCoOwner(m) && item is Container; + + return true; + } + + public static BaseHouse FindHouseAt(Mobile m) + { + if (m == null || m.Deleted) + return null; + + return FindHouseAt(m.Location, m.Map, 16); + } + + public static BaseHouse FindHouseAt(Item item) + { + if (item == null || item.Deleted) + return null; + + return FindHouseAt(item.GetWorldLocation(), item.Map, item.ItemData.Height); + } + + public static BaseHouse FindHouseAt(Point3D loc, Map map, int height) + { + if (map == null || map == Map.Internal) + return null; + + Sector sector = map.GetSector(loc); + + for (int i = 0; i < sector.Multis.Count; ++i) + { + BaseHouse house = sector.Multis[i] as BaseHouse; + + if (house != null && house.IsInside(loc, height)) + return house; + } + + return null; + } + + public bool IsInside(Mobile m) + { + if (m == null || m.Deleted || m.Map != Map) + return false; + + return IsInside(m.Location, 16); + } + + public bool IsInside(Item item) + { + if (item == null || item.Deleted || item.Map != Map) + return false; + + return IsInside(item.Location, item.ItemData.Height); + } + + public bool CheckAccessibility(Item item, Mobile from) + { + SecureAccessResult res = CheckSecureAccess(from, item); + + switch (res) + { + case SecureAccessResult.Insecure: break; + case SecureAccessResult.Accessible: return true; + case SecureAccessResult.Inaccessible: return false; + } + + if (!IsLockedDown(item)) + return true; + if (from.AccessLevel >= AccessLevel.GameMaster) + return true; + if (item is Runebook) + return true; + if (item is ISecurable) + return HasSecureAccess(from, ((ISecurable)item).Level); + if (item is Container) + return IsCoOwner(from); + if (item.Stackable) + return true; + if (item is BaseLight) + return IsFriend(from); + if (item is PotionKeg) + return IsFriend(from); + if (item is BaseBoard) + return true; + if (item is Dices) + return true; + if (item is RecallRune) + return true; + if (item is TreasureMap) + return true; + if (item is Clock) + return true; + if (item is BaseInstrument) + return true; + if (item is Dyes || item is DyeTub) + return true; + if (item is VendorRentalContract) + return true; + if (item is RewardBrazier) + return true; + + return false; + } + + public virtual bool IsInside(Point3D p, int height) + { + if (Deleted) + return false; + + MultiComponentList mcl = Components; + + int x = p.X - (X + mcl.Min.X); + int y = p.Y - (Y + mcl.Min.Y); + + if (x < 0 || x >= mcl.Width || y < 0 || y >= mcl.Height) + return false; + + if (this is HouseFoundation && y < mcl.Height - 1 && p.Z >= Z) + return true; + + StaticTile[] tiles = mcl.Tiles[x][y]; + + for (int j = 0; j < tiles.Length; ++j) + { + StaticTile tile = tiles[j]; + int id = tile.ID & TileData.MaxItemValue; + ItemData data = TileData.ItemTable[id]; + + // Slanted roofs do not count; they overhang blocking south and east sides of the multi + if ((data.Flags & TileFlag.Roof) != 0) + continue; + + // Signs and signposts are not considered part of the multi + if (id >= 0xB95 && id <= 0xC0E || id >= 0xC43 && id <= 0xC44) + continue; + + int tileZ = tile.Z + Z; + + if (p.Z == tileZ || p.Z + height > tileZ) + return true; + } + + return false; + } + + public SecureAccessResult CheckSecureAccess(Mobile m, Item item) + { + if (Secures == null || !(item is Container)) + return SecureAccessResult.Insecure; + + for (int i = 0; i < Secures.Count; ++i) + { + SecureInfo info = (SecureInfo)Secures[i]; + + if (info.Item == item) + return HasSecureAccess(m, info.Level) ? SecureAccessResult.Accessible : SecureAccessResult.Inaccessible; + } + + return SecureAccessResult.Insecure; + } + + public override void OnMapChange() + { + if (LockDowns == null) + return; + + UpdateRegion(); + + if (Sign != null && !Sign.Deleted) + Sign.Map = Map; + + if (Doors != null) + foreach (Item item in Doors) + item.Map = Map; + + foreach (IEntity entity in GetHouseEntities()) + if (entity is Item) + ((Item)entity).Map = Map; + else + ((Mobile)entity).Map = Map; + } + + public virtual void ChangeSignType(int itemID) + { + if (Sign != null) + Sign.ItemID = itemID; + } + + public virtual void UpdateRegion() + { + m_Region?.Unregister(); + + if (Map != null) + { + m_Region = new HouseRegion(this); + m_Region.Register(); + } + else + { + m_Region = null; + } + } + + public override void OnLocationChange(Point3D oldLocation) + { + if (LockDowns == null) + return; + + int x = base.Location.X - oldLocation.X; + int y = base.Location.Y - oldLocation.Y; + int z = base.Location.Z - oldLocation.Z; + + if (Sign != null && !Sign.Deleted) + Sign.Location = new Point3D(Sign.X + x, Sign.Y + y, Sign.Z + z); + + UpdateRegion(); + + if (Doors != null) + foreach (Item item in Doors) + if (!item.Deleted) + item.Location = new Point3D(item.X + x, item.Y + y, item.Z + z); + + foreach (IEntity entity in GetHouseEntities()) + { + Point3D newLocation = new Point3D(entity.X + x, entity.Y + y, entity.Z + z); + + if (entity is Item) + ((Item)entity).Location = newLocation; + else + ((Mobile)entity).Location = newLocation; + } + } + + public BaseDoor AddEastDoor(int x, int y, int z) + { + return AddEastDoor(true, x, y, z); + } + + public BaseDoor AddEastDoor(bool wood, int x, int y, int z) + { + BaseDoor door = MakeDoor(wood, DoorFacing.SouthCW); + + AddDoor(door, x, y, z); + + return door; + } + + public BaseDoor AddSouthDoor(int x, int y, int z) + { + return AddSouthDoor(true, x, y, z); + } + + public BaseDoor AddSouthDoor(bool wood, int x, int y, int z) + { + BaseDoor door = MakeDoor(wood, DoorFacing.WestCW); + + AddDoor(door, x, y, z); + + return door; + } + + public BaseDoor AddEastDoor(int x, int y, int z, uint k) + { + return AddEastDoor(true, x, y, z, k); + } + + public BaseDoor AddEastDoor(bool wood, int x, int y, int z, uint k) + { + BaseDoor door = MakeDoor(wood, DoorFacing.SouthCW); + + door.Locked = true; + door.KeyValue = k; + + AddDoor(door, x, y, z); + + return door; + } + + public BaseDoor AddSouthDoor(int x, int y, int z, uint k) + { + return AddSouthDoor(true, x, y, z, k); + } + + public BaseDoor AddSouthDoor(bool wood, int x, int y, int z, uint k) + { + BaseDoor door = MakeDoor(wood, DoorFacing.WestCW); + + door.Locked = true; + door.KeyValue = k; + + AddDoor(door, x, y, z); + + return door; + } + + public BaseDoor[] AddSouthDoors(int x, int y, int z, uint k) + { + return AddSouthDoors(true, x, y, z, k); + } + + public BaseDoor[] AddSouthDoors(bool wood, int x, int y, int z, uint k) + { + BaseDoor westDoor = MakeDoor(wood, DoorFacing.WestCW); + BaseDoor eastDoor = MakeDoor(wood, DoorFacing.EastCCW); + + westDoor.Locked = true; + eastDoor.Locked = true; + + westDoor.KeyValue = k; + eastDoor.KeyValue = k; + + westDoor.Link = eastDoor; + eastDoor.Link = westDoor; + + AddDoor(westDoor, x, y, z); + AddDoor(eastDoor, x + 1, y, z); + + return new BaseDoor[2] { westDoor, eastDoor }; + } + + public uint CreateKeys(Mobile m) + { + uint value = Key.RandomValue(); + + if (!IsAosRules) + { + Key packKey = new Key(KeyType.Gold); + Key bankKey = new Key(KeyType.Gold); + + packKey.KeyValue = value; + bankKey.KeyValue = value; + + packKey.LootType = LootType.Newbied; + bankKey.LootType = LootType.Newbied; + + BankBox box = m.BankBox; + + if (!box.TryDropItem(m, bankKey, false)) + bankKey.Delete(); + + m.AddToBackpack(packKey); + } + + return value; + } + + public BaseDoor[] AddSouthDoors(int x, int y, int z) + { + return AddSouthDoors(true, x, y, z, false); + } + + public BaseDoor[] AddSouthDoors(bool wood, int x, int y, int z, bool inv) + { + BaseDoor westDoor = MakeDoor(wood, inv ? DoorFacing.WestCCW : DoorFacing.WestCW); + BaseDoor eastDoor = MakeDoor(wood, inv ? DoorFacing.EastCW : DoorFacing.EastCCW); + + westDoor.Link = eastDoor; + eastDoor.Link = westDoor; + + AddDoor(westDoor, x, y, z); + AddDoor(eastDoor, x + 1, y, z); + + return new BaseDoor[2] { westDoor, eastDoor }; + } + + public BaseDoor MakeDoor(bool wood, DoorFacing facing) + { + if (wood) + return new DarkWoodHouseDoor(facing); + return new MetalHouseDoor(facing); + } + + public void AddDoor(BaseDoor door, int xoff, int yoff, int zoff) + { + door.MoveToWorld(new Point3D(xoff + X, yoff + Y, zoff + Z), Map); + Doors.Add(door); + } + + public void AddTrashBarrel(Mobile from) + { + if (!IsActive) + return; + + for (int i = 0; Doors != null && i < Doors.Count; ++i) + { + BaseDoor door = Doors[i] as BaseDoor; + Point3D p = door.Location; + + if (door.Open) + p = new Point3D(p.X - door.Offset.X, p.Y - door.Offset.Y, p.Z - door.Offset.Z); + + if (from.Z + 16 >= p.Z && p.Z + 16 >= from.Z) + if (from.InRange(p, 1)) + { + from.SendLocalizedMessage(502120); // You cannot place a trash barrel near a door or near steps. + return; + } + } + + if (m_Trash == null || m_Trash.Deleted) + { + m_Trash = new TrashBarrel(); + + m_Trash.Movable = false; + m_Trash.MoveToWorld(from.Location, from.Map); + + from.SendLocalizedMessage(502121); /* You have a new trash barrel. * Three minutes after you put something in the barrel, the trash will be emptied. * Be forewarned, this is permanent! */ - } - else - { - from.SendLocalizedMessage( 502117 ); // You already have a trash barrel! - } - } + } + else + { + from.SendLocalizedMessage(502117); // You already have a trash barrel! + } + } - public void SetSign( int xoff, int yoff, int zoff ) - { - Sign = new HouseSign( this ); - Sign.MoveToWorld( new Point3D( X + xoff, Y + yoff, Z + zoff ), Map ); - } + public void SetSign(int xoff, int yoff, int zoff) + { + Sign = new HouseSign(this); + Sign.MoveToWorld(new Point3D(X + xoff, Y + yoff, Z + zoff), Map); + } - private void SetLockdown( Item i, bool locked ) - { - SetLockdown( i, locked, false ); - } + private void SetLockdown(Item i, bool locked) + { + SetLockdown(i, locked, false); + } - private void SetLockdown( Item i, bool locked, bool checkContains ) - { - if ( LockDowns == null ) - return; + private void SetLockdown(Item i, bool locked, bool checkContains) + { + if (LockDowns == null) + return; - #region Mondain's Legacy - if ( i is BaseAddonContainer ) - i.Movable = false; - else - #endregion + #region Mondain's Legacy - i.Movable = !locked; - i.IsLockedDown = locked; + if (i is BaseAddonContainer) + i.Movable = false; + else - if ( locked ) - { - if ( i is VendorRentalContract ) - { - if ( !VendorRentalContracts.Contains( i ) ) - VendorRentalContracts.Add( i ); - } - else - { - if ( !checkContains || !LockDowns.Contains( i ) ) - LockDowns.Add( i ); - } - } - else - { - VendorRentalContracts.Remove( i ); - LockDowns.Remove( i ); - } + #endregion - if ( !locked ) - i.SetLastMoved(); + i.Movable = !locked; + i.IsLockedDown = locked; - if ( (i is Container) && (!locked || !(i is BaseBoard || i is Aquarium || i is FishBowl)) ) - { - foreach ( Item c in i.Items ) - SetLockdown( c, locked, checkContains ); - } - } + if (locked) + { + if (i is VendorRentalContract) + { + if (!VendorRentalContracts.Contains(i)) + VendorRentalContracts.Add(i); + } + else + { + if (!checkContains || !LockDowns.Contains(i)) + LockDowns.Add(i); + } + } + else + { + VendorRentalContracts.Remove(i); + LockDowns.Remove(i); + } - public bool LockDown( Mobile m, Item item ) - { - return LockDown( m, item, true ); - } + if (!locked) + i.SetLastMoved(); - public bool LockDown( Mobile m, Item item, bool checkIsInside ) - { - if ( !IsCoOwner( m ) || !IsActive ) - return false; + if (i is Container && (!locked || !(i is BaseBoard || i is Aquarium || i is FishBowl))) + foreach (Item c in i.Items) + SetLockdown(c, locked, checkContains); + } - if ( item is BaseAddonContainer || item.Movable && !IsSecure( item ) ) - { - int amt = 1 + item.TotalItems; + public bool LockDown(Mobile m, Item item) + { + return LockDown(m, item, true); + } - Item rootItem = item.RootParent as Item; - Item parentItem = item.Parent as Item; + public bool LockDown(Mobile m, Item item, bool checkIsInside) + { + if (!IsCoOwner(m) || !IsActive) + return false; - if ( checkIsInside && item.RootParent is Mobile ) - { - m.SendLocalizedMessage( 1005525 );//That is not in your house - } - else if ( checkIsInside && !IsInside( item.GetWorldLocation(), item.ItemData.Height ) ) - { - m.SendLocalizedMessage( 1005525 );//That is not in your house - } - else if ( Ethics.Ethic.IsImbued( item ) ) - { - m.SendLocalizedMessage( 1005377 );//You cannot lock that down - } - else if ( IsSecure( rootItem ) ) - { - m.SendLocalizedMessage( 501737 ); // You need not lock down items in a secure container. - } - else if ( parentItem != null && !IsLockedDown( parentItem ) ) - { - m.SendLocalizedMessage( 501736 ); // You must lockdown the container first! - } - else if ( !(item is VendorRentalContract) && ( IsAosRules ? (!CheckAosLockdowns( amt ) || !CheckAosStorage( amt )) : (LockDownCount + amt) > MaxLockDowns ) ) - { - m.SendLocalizedMessage( 1005379 );//That would exceed the maximum lock down limit for this house - } - else - { - SetLockdown( item, true ); - return true; - } - } - else if ( LockDowns.IndexOf( item ) != -1 ) - { - m.LocalOverheadMessage( MessageType.Regular, 0x3E9, 1005526 ); //That is already locked down - return true; - } - else if ( item is HouseSign || item is Static ) - { - m.LocalOverheadMessage( MessageType.Regular, 0x3E9, 1005526 ); // This is already locked down. - } - else - { - m.SendLocalizedMessage( 1005377 );//You cannot lock that down - } + if (item is BaseAddonContainer || item.Movable && !IsSecure(item)) + { + int amt = 1 + item.TotalItems; - return false; - } + Item rootItem = item.RootParent as Item; + Item parentItem = item.Parent as Item; - private class TransferItem : Item - { - private BaseHouse m_House; + if (checkIsInside && item.RootParent is Mobile) + { + m.SendLocalizedMessage(1005525); //That is not in your house + } + else if (checkIsInside && !IsInside(item.GetWorldLocation(), item.ItemData.Height)) + { + m.SendLocalizedMessage(1005525); //That is not in your house + } + else if (Ethic.IsImbued(item)) + { + m.SendLocalizedMessage(1005377); //You cannot lock that down + } + else if (IsSecure(rootItem)) + { + m.SendLocalizedMessage(501737); // You need not lock down items in a secure container. + } + else if (parentItem != null && !IsLockedDown(parentItem)) + { + m.SendLocalizedMessage(501736); // You must lockdown the container first! + } + else if (!(item is VendorRentalContract) && (IsAosRules + ? !CheckAosLockdowns(amt) || !CheckAosStorage(amt) + : LockDownCount + amt > MaxLockDowns)) + { + m.SendLocalizedMessage(1005379); //That would exceed the maximum lock down limit for this house + } + else + { + SetLockdown(item, true); + return true; + } + } + else if (LockDowns.IndexOf(item) != -1) + { + m.LocalOverheadMessage(MessageType.Regular, 0x3E9, 1005526); //That is already locked down + return true; + } + else if (item is HouseSign || item is Static) + { + m.LocalOverheadMessage(MessageType.Regular, 0x3E9, 1005526); // This is already locked down. + } + else + { + m.SendLocalizedMessage(1005377); //You cannot lock that down + } - public override string DefaultName => "a house transfer contract"; + return false; + } - public TransferItem( BaseHouse house ) : base( 0x14F0 ) - { - m_House = house; + public bool CheckTransferPosition(Mobile from, Mobile to) + { + bool isValid = true; + Item sign = Sign; + Point3D p = sign?.GetWorldLocation() ?? Point3D.Zero; - Hue = 0x480; - Movable = false; - } + if (from.Map != Map || to.Map != Map) + isValid = false; + else if (sign == null) + isValid = false; + else if (from.Map != sign.Map || to.Map != sign.Map) + isValid = false; + else if (IsInside(from)) + isValid = false; + else if (IsInside(to)) + isValid = false; + else if (!from.InRange(p, 2)) + isValid = false; + else if (!to.InRange(p, 2)) + isValid = false; - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + if (!isValid) + from.SendLocalizedMessage( + 1062067); // In order to transfer the house, you and the recipient must both be outside the building and within two paces of the house sign. - string houseName, owner, location; + return isValid; + } - houseName = ( m_House == null ? "an unnamed house" : m_House.Sign.GetName() ); + public void BeginConfirmTransfer(Mobile from, Mobile to) + { + if (Deleted || !from.CheckAlive() || !IsOwner(from)) + return; - Mobile houseOwner = m_House?.Owner; + if (NewVendorSystem && HasPersonalVendors) + { + from.SendLocalizedMessage( + 1062467); // You cannot trade this house while you still have personal vendors inside. + } + else if (DecayLevel == DecayLevel.DemolitionPending) + { + from.SendLocalizedMessage( + 1005321); // This house has been marked for demolition, and it cannot be transferred. + } + else if (from == to) + { + from.SendLocalizedMessage(1005330); // You cannot transfer a house to yourself, silly. + } + else if (to.Player) + { + if (HasAccountHouse(to)) + { + from.SendLocalizedMessage(501388); // You cannot transfer ownership to another house owner or co-owner! + } + else if (CheckTransferPosition(from, to)) + { + from.SendLocalizedMessage(1005326); // Please wait while the other player verifies the transfer. - if ( houseOwner == null ) - owner = "nobody"; - else - owner = houseOwner.Name; + if (HasRentedVendors) + { + /* You are about to be traded a home that has active vendor contracts. + * While there are active vendor contracts in this house, you + * cannot demolish OR customize the home. + * When you accept this house, you also accept landlordship for every + * contract vendor in the house. + */ + to.SendGump( + new WarningGump(1060635, 30720, 1062487, 32512, 420, 280, ConfirmTransfer_Callback, from)); + } + else + { + to.CloseGump(typeof(HouseTransferGump)); + to.SendGump(new HouseTransferGump(from, to, this)); + } + } + } + else + { + from.SendLocalizedMessage(501384); // Only a player can own a house! + } + } - int xLong = 0, yLat = 0, xMins = 0, yMins = 0; - bool xEast = false, ySouth = false; + private void ConfirmTransfer_Callback(Mobile to, bool ok, object state) + { + Mobile from = (Mobile)state; - bool valid = m_House != null && Sextant.Format( m_House.Location, m_House.Map, ref xLong, ref yLat, ref xMins, ref yMins, ref xEast, ref ySouth ); + if (!ok || Deleted || !from.CheckAlive() || !IsOwner(from)) + return; - if ( valid ) - location = $"{yLat}° {yMins}'{(ySouth ? "S" : "N")}, {xLong}° {xMins}'{(xEast ? "E" : "W")}"; - else - location = "unknown"; + if (CheckTransferPosition(from, to)) + { + to.CloseGump(typeof(HouseTransferGump)); + to.SendGump(new HouseTransferGump(from, to, this)); + } + } - list.Add( 1061112, Utility.FixHtml( houseName ) ); // House Name: ~1_val~ - list.Add( 1061113, owner ); // Owner: ~1_val~ - list.Add( 1061114, location ); // Location: ~1_val~ - } + public void EndConfirmTransfer(Mobile from, Mobile to) + { + if (Deleted || !from.CheckAlive() || !IsOwner(from)) + return; - public TransferItem( Serial serial ) : base( serial ) - { - } + if (NewVendorSystem && HasPersonalVendors) + { + from.SendLocalizedMessage( + 1062467); // You cannot trade this house while you still have personal vendors inside. + } + else if (DecayLevel == DecayLevel.DemolitionPending) + { + from.SendLocalizedMessage( + 1005321); // This house has been marked for demolition, and it cannot be transferred. + } + else if (from == to) + { + from.SendLocalizedMessage(1005330); // You cannot transfer a house to yourself, silly. + } + else if (to.Player) + { + if (HasAccountHouse(to)) + { + from.SendLocalizedMessage(501388); // You cannot transfer ownership to another house owner or co-owner! + } + else if (CheckTransferPosition(from, to)) + { + NetState fromState = from.NetState, toState = to.NetState; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (fromState != null && toState != null) + { + if (from.HasTrade) + { + from.SendLocalizedMessage( + 1062071); // You cannot trade a house while you have other trades pending. + } + else if (to.HasTrade) + { + to.SendLocalizedMessage( + 1062071); // You cannot trade a house while you have other trades pending. + } + else if (!to.Alive) + { + // TODO: Check if the message is correct. + from.SendLocalizedMessage(1062069); // You cannot transfer this house to that person. + } + else + { + Container c = fromState.AddTrade(toState); - writer.Write( (int) 0 ); // version - } + c.DropItem(new TransferItem(this)); + } + } + } + } + else + { + from.SendLocalizedMessage(501384); // Only a player can own a house! + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public void Release(Mobile m, Item item) + { + if (!IsCoOwner(m) || !IsActive) + return; - int version = reader.ReadInt(); + if (IsLockedDown(item)) + { + item.PublicOverheadMessage(MessageType.Label, 0x3B2, 501657); //[no longer locked down] + SetLockdown(item, false); + //TidyItemList( m_LockDowns ); - Delete(); - } + (item as RewardBrazier)?.TurnOff(); + } + else if (IsSecure(item)) + { + ReleaseSecure(m, item); + } + else + { + m.LocalOverheadMessage(MessageType.Regular, 0x3E9, 1010416); // This is not locked down or secured. + } + } - public override bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - if ( !base.AllowSecureTrade( from, to, newOwner, accepted ) ) - return false; - if ( !accepted ) - return true; + public void AddSecure(Mobile m, Item item) + { + if (Secures == null || !IsOwner(m) || !IsActive) + return; - if ( Deleted || m_House == null || m_House.Deleted || !m_House.IsOwner( from ) || !from.CheckAlive() || !to.CheckAlive() ) - return false; + if (!IsInside(item)) + { + m.SendLocalizedMessage(1005525); // That is not in your house + } + else if (IsLockedDown(item)) + { + m.SendLocalizedMessage(1010550); // This is already locked down and cannot be secured. + } + else if (!(item is Container)) + { + LockDown(m, item); + } + else + { + SecureInfo info = null; - if ( HasAccountHouse( to ) ) - { - from.SendLocalizedMessage( 501388 ); // You cannot transfer ownership to another house owner or co-owner! - return false; - } + for (int i = 0; info == null && i < Secures.Count; ++i) + if (((SecureInfo)Secures[i]).Item == item) + info = (SecureInfo)Secures[i]; - return m_House.CheckTransferPosition( from, to ); - } + if (info != null) + { + m.CloseGump(typeof(SetSecureLevelGump)); + m.SendGump(new SetSecureLevelGump(m_Owner, info, this)); + } + else if (item.Parent != null) + { + m.SendLocalizedMessage(1010423); // You cannot secure this, place it on the ground first. + } + // Mondain's Legacy mod + else if (!(item is BaseAddonContainer) && !item.Movable) + { + m.SendLocalizedMessage(1010424); // You cannot secure this. + } + else if (!IsAosRules && SecureCount >= MaxSecures) + { + // The maximum number of secure items has been reached : + m.SendLocalizedMessage(1008142, true, MaxSecures.ToString()); + } + else if (IsAosRules ? !CheckAosLockdowns(1) : LockDownCount + 125 >= MaxLockDowns) + { + m.SendLocalizedMessage(1005379); // That would exceed the maximum lock down limit for this house + } + else if (IsAosRules && !CheckAosStorage(item.TotalItems)) + { + m.SendLocalizedMessage(1061839); // This action would exceed the secure storage limit of the house. + } + else + { + info = new SecureInfo((Container)item, SecureLevel.Owner); - public override void OnSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - if ( Deleted ) - return; + item.IsLockedDown = false; + item.IsSecure = true; - Delete(); + Secures.Add(info); + LockDowns.Remove(item); + item.Movable = false; - if ( m_House == null || m_House.Deleted || !m_House.IsOwner( from ) || !from.CheckAlive() || !to.CheckAlive() ) - return; + m.CloseGump(typeof(SetSecureLevelGump)); + m.SendGump(new SetSecureLevelGump(m_Owner, info, this)); + } + } + } + + public virtual bool IsCombatRestricted(Mobile m) + { + if (m == null || !m.Player || m.AccessLevel >= AccessLevel.GameMaster || !IsAosRules || + m_Owner != null && m_Owner.AccessLevel >= AccessLevel.GameMaster) + return false; + + for (int i = 0; i < m.Aggressed.Count; ++i) + { + AggressorInfo info = m.Aggressed[i]; + + Guild attackerGuild = m.Guild as Guild; + Guild defenderGuild = info.Defender.Guild as Guild; + + if (info.Defender.Player && info.Defender.Alive && + DateTime.UtcNow - info.LastCombatTime < HouseRegion.CombatHeatDelay && + (attackerGuild == null || defenderGuild == null || + defenderGuild != attackerGuild && !defenderGuild.IsEnemy(attackerGuild))) + return true; + } + + return false; + } + + public bool HasSecureAccess(Mobile m, SecureLevel level) + { + if (m.AccessLevel >= AccessLevel.GameMaster) + return true; + + if (IsCombatRestricted(m)) + return false; + + switch (level) + { + case SecureLevel.Owner: return IsOwner(m); + case SecureLevel.CoOwners: return IsCoOwner(m); + case SecureLevel.Friends: return IsFriend(m); + case SecureLevel.Anyone: return true; + case SecureLevel.Guild: return IsGuildMember(m); + } + + return false; + } + + public void ReleaseSecure(Mobile m, Item item) + { + if (Secures == null || !IsOwner(m) || item is StrongBox || !IsActive) + return; + + for (int i = 0; i < Secures.Count; ++i) + { + SecureInfo info = (SecureInfo)Secures[i]; + + if (info.Item == item && HasSecureAccess(m, info.Level)) + { + item.IsLockedDown = false; + item.IsSecure = false; + + #region Mondain's Legacy + + if (item is BaseAddonContainer) + item.Movable = false; + else + + #endregion + + item.Movable = true; + item.SetLastMoved(); + item.PublicOverheadMessage(MessageType.Label, 0x3B2, 501656); //[no longer secure] + Secures.RemoveAt(i); + return; + } + } + + m.SendLocalizedMessage(501717); //This isn't secure... + } + + public void AddStrongBox(Mobile from) + { + if (!IsCoOwner(from) || !IsActive) + return; + + if (from == Owner) + { + from.SendLocalizedMessage(502109); // Owners don't get a strong box + return; + } + + if (IsAosRules ? !CheckAosLockdowns(1) : LockDownCount + 1 > MaxLockDowns) + { + from.SendLocalizedMessage(1005379); //That would exceed the maximum lock down limit for this house + return; + } + + foreach (SecureInfo info in Secures) + { + Container c = info.Item; + + if (!c.Deleted && c is StrongBox && ((StrongBox)c).Owner == from) + { + from.SendLocalizedMessage(502112); //You already have a strong box + return; + } + } + + for (int i = 0; Doors != null && i < Doors.Count; ++i) + { + BaseDoor door = Doors[i] as BaseDoor; + Point3D p = door.Location; + + if (door.Open) + p = new Point3D(p.X - door.Offset.X, p.Y - door.Offset.Y, p.Z - door.Offset.Z); + + if (from.Z + 16 >= p.Z && p.Z + 16 >= from.Z) + if (from.InRange(p, 1)) + { + from.SendLocalizedMessage(502113); // You cannot place a strongbox near a door or near steps. + return; + } + } + + StrongBox sb = new StrongBox(from, this); + sb.Movable = false; + sb.IsLockedDown = false; + sb.IsSecure = true; + Secures.Add(new SecureInfo(sb, SecureLevel.CoOwners)); + sb.MoveToWorld(from.Location, from.Map); + } + + public void Kick(Mobile from, Mobile targ) + { + if (!IsFriend(from) || Friends == null) + return; + + if (targ.AccessLevel > AccessLevel.Player && from.AccessLevel <= targ.AccessLevel) + { + from.SendLocalizedMessage(501346); // Uh oh...a bigger boot may be required! + } + else if (IsFriend(targ) && !Core.ML) + { + from.SendLocalizedMessage(501348); // You cannot eject a friend of the house! + } + else if (targ is PlayerVendor) + { + from.SendLocalizedMessage(501351); // You cannot eject a vendor. + } + else if (!IsInside(targ)) + { + from.SendLocalizedMessage(501352); // You may not eject someone who is not in your house! + } + else if (targ is BaseCreature && ((BaseCreature)targ).NoHouseRestrictions) + { + from.SendLocalizedMessage(501347); // You cannot eject that from the house! + } + else + { + targ.MoveToWorld(BanLocation, Map); + + from.SendLocalizedMessage(1042840, targ.Name); // ~1_PLAYER NAME~ has been ejected from this house. + targ.SendLocalizedMessage(501341); /* You have been ejected from this house. + * If you persist in entering, you may be banned from the house. + */ + } + } + + public void RemoveAccess(Mobile from, Mobile targ) + { + if (!IsFriend(from) || Access == null) + return; + + if (Access.Contains(targ)) + { + Access.Remove(targ); + + if (!HasAccess(targ) && IsInside(targ)) + { + targ.Location = BanLocation; + targ.SendLocalizedMessage(1060734); // Your access to this house has been revoked. + } + + from.SendLocalizedMessage(1050051); // The invitation has been revoked. + } + } + + public void RemoveBan(Mobile from, Mobile targ) + { + if (!IsCoOwner(from) || Bans == null) + return; + + if (Bans.Contains(targ)) + { + Bans.Remove(targ); + + from.SendLocalizedMessage(501297); // The ban is lifted. + } + } + + public void Ban(Mobile from, Mobile targ) + { + if (!IsFriend(from) || Bans == null) + return; + + if (targ.AccessLevel > AccessLevel.Player && from.AccessLevel <= targ.AccessLevel) + { + from.SendLocalizedMessage(501354); // Uh oh...a bigger boot may be required. + } + else if (IsFriend(targ)) + { + from.SendLocalizedMessage(501348); // You cannot eject a friend of the house! + } + else if (targ is PlayerVendor) + { + from.SendLocalizedMessage(501351); // You cannot eject a vendor. + } + else if (Bans.Count >= MaxBans) + { + from.SendLocalizedMessage(501355); // The ban limit for this house has been reached! + } + else if (IsBanned(targ)) + { + from.SendLocalizedMessage(501356); // This person is already banned! + } + else if (!IsInside(targ)) + { + from.SendLocalizedMessage(501352); // You may not eject someone who is not in your house! + } + else if (!Public && IsAosRules) + { + from.SendLocalizedMessage( + 1062521); // You cannot ban someone from a private house. Revoke their access instead. + } + else if (targ is BaseCreature && ((BaseCreature)targ).NoHouseRestrictions) + { + from.SendLocalizedMessage(1062040); // You cannot ban that. + } + else + { + Bans.Add(targ); + + from.SendLocalizedMessage(1042839, targ.Name); // ~1_PLAYER_NAME~ has been banned from this house. + targ.SendLocalizedMessage(501340); // You have been banned from this house. + + targ.MoveToWorld(BanLocation, Map); + } + } + + public void GrantAccess(Mobile from, Mobile targ) + { + if (!IsFriend(from) || Access == null) + return; + + if (HasAccess(targ)) + { + from.SendLocalizedMessage(1060729); // That person already has access to this house. + } + else if (!targ.Player) + { + from.SendLocalizedMessage(1060712); // That is not a player. + } + else if (IsBanned(targ)) + { + from.SendLocalizedMessage(501367); // This person is banned! Unban them first. + } + else + { + Access.Add(targ); + + targ.SendLocalizedMessage(1060735); // You have been granted access to this house. + } + } + + public void AddCoOwner(Mobile from, Mobile targ) + { + if (!IsOwner(from) || CoOwners == null || Friends == null) + return; + + if (IsOwner(targ)) + { + from.SendLocalizedMessage(501360); // This person is already the house owner! + } + else if (Friends.Contains(targ)) + { + from.SendLocalizedMessage(501361); // This person is a friend of the house. Remove them first. + } + else if (!targ.Player) + { + from.SendLocalizedMessage(501362); // That can't be a co-owner of the house. + } + else if (!Core.AOS && HasAccountHouse(targ)) + { + from.SendLocalizedMessage(501364); // That person is already a house owner. + } + else if (IsBanned(targ)) + { + from.SendLocalizedMessage(501367); // This person is banned! Unban them first. + } + else if (CoOwners.Count >= MaxCoOwners) + { + from.SendLocalizedMessage(501368); // Your co-owner list is full! + } + else if (CoOwners.Contains(targ)) + { + from.SendLocalizedMessage(501369); // This person is already on your co-owner list! + } + else + { + CoOwners.Add(targ); + + targ.Delta(MobileDelta.Noto); + targ.SendLocalizedMessage(501343); // You have been made a co-owner of this house. + } + } + + public void RemoveCoOwner(Mobile from, Mobile targ) + { + if (!IsOwner(from) || CoOwners == null) + return; + + if (CoOwners.Contains(targ)) + { + CoOwners.Remove(targ); + + targ.Delta(MobileDelta.Noto); + + from.SendLocalizedMessage(501299); // Co-owner removed from list. + targ.SendLocalizedMessage(501300); // You have been removed as a house co-owner. + + foreach (SecureInfo info in Secures) + { + Container c = info.Item; + + if (c is StrongBox && ((StrongBox)c).Owner == targ) + { + c.IsLockedDown = false; + c.IsSecure = false; + Secures.Remove(info); + c.Destroy(); + break; + } + } + } + } + + public void AddFriend(Mobile from, Mobile targ) + { + if (!IsCoOwner(from) || Friends == null || CoOwners == null) + return; + + if (IsOwner(targ)) + { + from.SendLocalizedMessage(501370); // This person is already an owner of the house! + } + else if (CoOwners.Contains(targ)) + { + from.SendLocalizedMessage(501369); // This person is already on your co-owner list! + } + else if (!targ.Player) + { + from.SendLocalizedMessage(501371); // That can't be a friend of the house. + } + else if (IsBanned(targ)) + { + from.SendLocalizedMessage(501374); // This person is banned! Unban them first. + } + else if (Friends.Count >= MaxFriends) + { + from.SendLocalizedMessage(501375); // Your friends list is full! + } + else if (Friends.Contains(targ)) + { + from.SendLocalizedMessage(501376); // This person is already on your friends list! + } + else + { + Friends.Add(targ); + + targ.Delta(MobileDelta.Noto); + targ.SendLocalizedMessage(501337); // You have been made a friend of this house. + } + } + + public void RemoveFriend(Mobile from, Mobile targ) + { + if (!IsCoOwner(from) || Friends == null) + return; + + if (Friends.Contains(targ)) + { + Friends.Remove(targ); + + targ.Delta(MobileDelta.Noto); + + from.SendLocalizedMessage(501298); // Friend removed from list. + targ.SendLocalizedMessage(1060751); // You are no longer a friend of this house. + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(15); // version + + if (!DynamicDecay.Enabled) + { + writer.Write(-1); + } + else + { + writer.Write((int)m_CurrentStage); + writer.Write(NextDecayStage); + } + + writer.Write(m_RelativeBanLocation); + + writer.WriteItemList(VendorRentalContracts, true); + writer.WriteMobileList(InternalizedVendors, true); + + writer.WriteEncodedInt(RelocatedEntities.Count); + foreach (RelocatedEntity relEntity in RelocatedEntities) + { + writer.Write(relEntity.RelativeLocation); + + if (relEntity.Entity.Deleted) + writer.Write(Serial.MinusOne); + else + writer.Write(relEntity.Entity.Serial); + } + + writer.WriteEncodedInt(VendorInventories.Count); + for (int i = 0; i < VendorInventories.Count; i++) + { + VendorInventory inventory = (VendorInventory)VendorInventories[i]; + inventory.Serialize(writer); + } + + writer.Write(LastRefreshed); + writer.Write(RestrictDecay); + + writer.Write(Visits); + + writer.Write(Price); + + writer.WriteMobileList(Access); + + writer.Write(BuiltOn); + writer.Write(LastTraded); + + writer.WriteItemList(Addons, true); + + writer.Write(Secures.Count); + + for (int i = 0; i < Secures.Count; ++i) + ((SecureInfo)Secures[i]).Serialize(writer); + + writer.Write(m_Public); + + //writer.Write( BanLocation ); + + writer.Write(m_Owner); + + // Version 5 no longer serializes region coords + /*writer.Write( (int)m_Region.Coords.Count ); + foreach( Rectangle2D rect in m_Region.Coords ) + { + writer.Write( rect ); + }*/ + + writer.WriteMobileList(CoOwners, true); + writer.WriteMobileList(Friends, true); + writer.WriteMobileList(Bans, true); + + writer.Write(Sign); + writer.Write(m_Trash); + + writer.WriteItemList(Doors, true); + writer.WriteItemList(LockDowns, true); + //writer.WriteItemList( m_Secures, true ); + + writer.Write(MaxLockDowns); + writer.Write(MaxSecures); + + // Items in locked down containers that aren't locked down themselves must decay! + for (int i = 0; i < LockDowns.Count; ++i) + { + Item item = (Item)LockDowns[i]; + + if (item is Container && !(item is BaseBoard || item is Aquarium || item is FishBowl)) + { + Container cont = (Container)item; + List children = cont.Items; + + for (int j = 0; j < children.Count; ++j) + { + Item child = children[j]; + + if (child.Decays && !child.IsLockedDown && !child.IsSecure && + child.LastMoved + child.DecayTime <= DateTime.UtcNow) + Timer.DelayCall(TimeSpan.Zero, child.Delete); + } + } + } + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + int count; + bool loadedDynamicDecay = false; + + switch (version) + { + case 15: + { + int stage = reader.ReadInt(); + + if (stage != -1) + { + m_CurrentStage = (DecayLevel)stage; + NextDecayStage = reader.ReadDateTime(); + loadedDynamicDecay = true; + } + + goto case 14; + } + case 14: + { + m_RelativeBanLocation = reader.ReadPoint3D(); + goto case 13; + } + case 13: // removed ban location serialization + case 12: + { + VendorRentalContracts = reader.ReadItemList(); + InternalizedVendors = reader.ReadMobileList(); + + int relocatedCount = reader.ReadEncodedInt(); + for (int i = 0; i < relocatedCount; i++) + { + Point3D relLocation = reader.ReadPoint3D(); + IEntity entity = World.FindEntity(reader.ReadInt()); + + if (entity != null) + RelocatedEntities.Add(new RelocatedEntity(entity, relLocation)); + } + + int inventoryCount = reader.ReadEncodedInt(); + for (int i = 0; i < inventoryCount; i++) + { + VendorInventory inventory = new VendorInventory(this, reader); + VendorInventories.Add(inventory); + } + + goto case 11; + } + case 11: + { + LastRefreshed = reader.ReadDateTime(); + RestrictDecay = reader.ReadBool(); + goto case 10; + } + case 10: // just a signal for updates + case 9: + { + Visits = reader.ReadInt(); + goto case 8; + } + case 8: + { + Price = reader.ReadInt(); + goto case 7; + } + case 7: + { + Access = reader.ReadMobileList(); + goto case 6; + } + case 6: + { + BuiltOn = reader.ReadDateTime(); + LastTraded = reader.ReadDateTime(); + goto case 5; + } + case 5: // just removed fields + case 4: + { + Addons = reader.ReadItemList(); + goto case 3; + } + case 3: + { + count = reader.ReadInt(); + Secures = new ArrayList(count); + + for (int i = 0; i < count; ++i) + { + SecureInfo info = new SecureInfo(reader); + + if (info.Item != null) + { + info.Item.IsSecure = true; + Secures.Add(info); + } + } + + goto case 2; + } + case 2: + { + m_Public = reader.ReadBool(); + goto case 1; + } + case 1: + { + if (version < 13) + reader.ReadPoint3D(); // house ban location + goto case 0; + } + case 0: + { + if (version < 14) + m_RelativeBanLocation = BaseBanLocation; + + if (version < 12) + { + VendorRentalContracts = new ArrayList(); + InternalizedVendors = new ArrayList(); + } + + if (version < 4) + Addons = new ArrayList(); + + if (version < 7) + Access = new ArrayList(); + + if (version < 8) + Price = DefaultPrice; + + m_Owner = reader.ReadMobile(); + + if (version < 5) + { + count = reader.ReadInt(); + + for (int i = 0; i < count; i++) + reader.ReadRect2D(); + } + + UpdateRegion(); + + CoOwners = reader.ReadMobileList(); + Friends = reader.ReadMobileList(); + Bans = reader.ReadMobileList(); + + Sign = reader.ReadItem() as HouseSign; + m_Trash = reader.ReadItem() as TrashBarrel; + + Doors = reader.ReadItemList(); + LockDowns = reader.ReadItemList(); + + for (int i = 0; i < LockDowns.Count; ++i) + ((Item)LockDowns[i]).IsLockedDown = true; + + for (int i = 0; i < VendorRentalContracts.Count; ++i) + ((Item)VendorRentalContracts[i]).IsLockedDown = true; + + if (version < 3) + { + ArrayList items = reader.ReadItemList(); + Secures = new ArrayList(items.Count); + + for (int i = 0; i < items.Count; ++i) + { + Container c = items[i] as Container; + + if (c != null) + { + c.IsSecure = true; + Secures.Add(new SecureInfo(c, SecureLevel.CoOwners)); + } + } + } + + MaxLockDowns = reader.ReadInt(); + MaxSecures = reader.ReadInt(); + + if ((Map == null || Map == Map.Internal) && Location == Point3D.Zero) + Delete(); + + if (m_Owner != null) + { + m_Table.TryGetValue(m_Owner, out List list); + + if (list == null) + m_Table[m_Owner] = list = new List(); + + list.Add(this); + } + + break; + } + } + + if (version <= 1) + ChangeSignType(0xBD2); //private house, plain brass sign + + if (version < 10) Timer.DelayCall(TimeSpan.Zero, FixLockdowns_Sandbox); + + if (version < 11) + LastRefreshed = DateTime.UtcNow + TimeSpan.FromHours(24 * Utility.RandomDouble()); + + if (DynamicDecay.Enabled && !loadedDynamicDecay) + { + DecayLevel old = GetOldDecayLevel(); + + if (old == DecayLevel.DemolitionPending) + old = DecayLevel.Collapsed; + + SetDynamicDecay(old); + } + + if (!CheckDecay()) + { + if (RelocatedEntities.Count > 0) + Timer.DelayCall(TimeSpan.Zero, RestoreRelocatedEntities); + + if (m_Owner == null && Friends.Count == 0 && CoOwners.Count == 0) + Timer.DelayCall(TimeSpan.FromSeconds(10.0), Delete); + } + } + + private void FixLockdowns_Sandbox() + { + ArrayList lockDowns = new ArrayList(); + + for (int i = 0; LockDowns != null && i < LockDowns.Count; ++i) + { + Item item = (Item)LockDowns[i]; + + if (item is Container) + lockDowns.Add(item); + } + + for (int i = 0; i < lockDowns.Count; ++i) + SetLockdown((Item)lockDowns[i], true, true); + } + + public static void HandleDeletion(Mobile mob) + { + List houses = GetHouses(mob); + + if (houses.Count == 0) + return; + + Account acct = mob.Account as Account; + Mobile trans = null; + + for (int i = 0; i < acct.Length; ++i) + if (acct[i] != null && acct[i] != mob) + trans = acct[i]; + + for (int i = 0; i < houses.Count; ++i) + { + BaseHouse house = houses[i]; + + bool canClaim = false; + + if (trans == null) + canClaim = house.CoOwners.Count > 0; + /*{ + for ( int j = 0; j < house.CoOwners.Count; ++j ) + { + Mobile check = house.CoOwners[j] as Mobile; + + if ( check != null && !check.Deleted && !HasAccountHouse( check ) ) + { + canClaim = true; + break; + } + } + }*/ + + if (trans == null && !canClaim) + Timer.DelayCall(TimeSpan.Zero, house.Delete); + else + house.Owner = trans; + } + } + + public int GetLockdowns() + { + int count = 0; + + if (LockDowns != null) + for (int i = 0; i < LockDowns.Count; ++i) + { + if (LockDowns[i] is Item) + { + Item item = (Item)LockDowns[i]; + + if (!(item is Container)) + count += item.TotalItems; + } + + count++; + } + + return count; + } + + public override void OnDelete() + { + RestoreRelocatedEntities(); + + new FixColumnTimer(this).Start(); + + base.OnDelete(); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + if (m_Owner != null) + { + m_Table.TryGetValue(m_Owner, out List list); + + if (list == null) + m_Table[m_Owner] = list = new List(); + + list.Remove(this); + } + + if (m_Region != null) + { + m_Region.Unregister(); + m_Region = null; + } + + Sign?.Delete(); + + m_Trash?.Delete(); + + if (Doors != null) + { + for (int i = 0; i < Doors.Count; ++i) + { + Item item = (Item)Doors[i]; + + item?.Delete(); + } + + Doors.Clear(); + } + + if (LockDowns != null) + { + for (int i = 0; i < LockDowns.Count; ++i) + { + Item item = (Item)LockDowns[i]; + + if (item != null) + { + item.IsLockedDown = false; + item.IsSecure = false; + item.Movable = true; + item.SetLastMoved(); + } + } + + LockDowns.Clear(); + } + + if (VendorRentalContracts != null) + { + for (int i = 0; i < VendorRentalContracts.Count; ++i) + { + Item item = (Item)VendorRentalContracts[i]; + + if (item != null) + { + item.IsLockedDown = false; + item.IsSecure = false; + item.Movable = true; + item.SetLastMoved(); + } + } + + VendorRentalContracts.Clear(); + } + + if (Secures != null) + { + for (int i = 0; i < Secures.Count; ++i) + { + SecureInfo info = (SecureInfo)Secures[i]; + + if (info.Item is StrongBox) + { + info.Item.Destroy(); + } + else + { + info.Item.IsLockedDown = false; + info.Item.IsSecure = false; + info.Item.Movable = true; + info.Item.SetLastMoved(); + } + } + + Secures.Clear(); + } + + if (Addons != null) + { + for (int i = 0; i < Addons.Count; ++i) + { + Item item = (Item)Addons[i]; + + if (item != null) + { + if (!item.Deleted && item is IAddon) + { + Item deed = ((IAddon)item).Deed; + bool retainDeedHue = false; //if the items aren't hued but the deed itself is + int hue = 0; + + if (item is BaseAddon && ((BaseAddon)item).RetainDeedHue + ) //There are things that are IAddon which aren't BaseAddon + { + BaseAddon ba = (BaseAddon)item; + retainDeedHue = true; + + for (int j = 0; hue == 0 && j < ba.Components.Count; ++j) + { + AddonComponent c = ba.Components[j]; + + if (c.Hue != 0) + hue = c.Hue; + } + } + + if (deed != null) + { + if (retainDeedHue) + deed.Hue = hue; + deed.MoveToWorld(item.Location, item.Map); + } + } + + item.Delete(); + } + } + + Addons.Clear(); + } + + ArrayList inventories = new ArrayList(VendorInventories); + + foreach (VendorInventory inventory in inventories) + inventory.Delete(); + + MovingCrate?.Delete(); + + KillVendors(); + + AllHouses.Remove(this); + } + + public static bool HasHouse(Mobile m) + { + if (m == null) + return false; + + m_Table.TryGetValue(m, out List list); + + if (list == null) + return false; + + for (int i = 0; i < list.Count; ++i) + { + BaseHouse h = list[i]; + + if (!h.Deleted) + return true; + } + + return false; + } + + public static bool HasAccountHouse(Mobile m) + { + Account a = m.Account as Account; + + if (a == null) + return false; + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null && HasHouse(a[i])) + return true; + + return false; + } + + public bool IsOwner(Mobile m) + { + if (m == null) + return false; + + if (m == m_Owner || m.AccessLevel >= AccessLevel.GameMaster) + return true; + + return IsAosRules && AccountHandler.CheckAccount(m, m_Owner); + } + + public bool IsCoOwner(Mobile m) + { + if (m == null || CoOwners == null) + return false; + + if (IsOwner(m) || CoOwners.Contains(m)) + return true; + + return !IsAosRules && AccountHandler.CheckAccount(m, m_Owner); + } + + public bool IsGuildMember(Mobile m) + { + if (m == null || Owner?.Guild == null) + return false; + + return m.Guild == Owner.Guild; + } + + public void RemoveKeys(Mobile m) + { + if (Doors != null) + { + uint keyValue = 0; + + for (int i = 0; keyValue == 0 && i < Doors.Count; ++i) + { + BaseDoor door = Doors[i] as BaseDoor; + + if (door != null) + keyValue = door.KeyValue; + } + + Key.RemoveKeys(m, keyValue); + } + } + + public void ChangeLocks(Mobile m) + { + uint keyValue = CreateKeys(m); + + if (Doors != null) + for (int i = 0; i < Doors.Count; ++i) + { + BaseDoor door = Doors[i] as BaseDoor; + + if (door != null) + door.KeyValue = keyValue; + } + } + + public void RemoveLocks() + { + if (Doors != null) + for (int i = 0; i < Doors.Count; ++i) + { + BaseDoor door = Doors[i] as BaseDoor; + + if (door != null) + { + door.KeyValue = 0; + door.Locked = false; + } + } + } + + public virtual HouseDeed GetDeed() + { + return null; + } + + public bool IsFriend(Mobile m) + { + if (m == null || Friends == null) + return false; + + return IsCoOwner(m) || Friends.Contains(m); + } + + public bool IsBanned(Mobile m) + { + if (m == null || m == Owner || m.AccessLevel > AccessLevel.Player || Bans == null) + return false; + + Account theirAccount = m.Account as Account; + + for (int i = 0; i < Bans.Count; ++i) + { + Mobile c = (Mobile)Bans[i]; + + if (c == m) + return true; + + Account bannedAccount = c.Account as Account; + + if (bannedAccount != null && bannedAccount == theirAccount) + return true; + } + + return false; + } + + public bool HasAccess(Mobile m) + { + if (m == null) + return false; + + if (m.AccessLevel > AccessLevel.Player || IsFriend(m) || Access != null && Access.Contains(m)) + return true; + + if (m is BaseCreature) + { + BaseCreature bc = (BaseCreature)m; + + if (bc.NoHouseRestrictions) + return true; + + if (bc.Controlled || bc.Summoned) + { + m = bc.ControlMaster; + + if (m == null) + m = bc.SummonMaster; + + if (m == null) + return false; + + if (m.AccessLevel > AccessLevel.Player || IsFriend(m) || Access != null && Access.Contains(m)) + return true; + } + } + + return false; + } + + public bool IsLockedDown(Item check) + { + if (check == null) + return false; + + if (LockDowns == null) + return false; + + return LockDowns.Contains(check) || VendorRentalContracts.Contains(check); + } + + public bool IsSecure(Item item) + { + if (item == null) + return false; + + if (Secures == null) + return false; + + bool contains = false; + + for (int i = 0; !contains && i < Secures.Count; ++i) + contains = ((SecureInfo)Secures[i]).Item == item; + + return contains; + } + + public virtual Guildstone FindGuildstone() + { + Map map = Map; + + if (map == null) + return null; + + MultiComponentList mcl = Components; + IPooledEnumerable eable = + map.GetItemsInBounds(new Rectangle2D(X + mcl.Min.X, Y + mcl.Min.Y, mcl.Width, mcl.Height)); + + foreach (Guildstone item in eable) + if (Contains(item)) + { + eable.Free(); + return item; + } + + eable.Free(); + return null; + } + + private class TransferItem : Item + { + private BaseHouse m_House; + + public TransferItem(BaseHouse house) : base(0x14F0) + { + m_House = house; + + Hue = 0x480; + Movable = false; + } + + public TransferItem(Serial serial) : base(serial) + { + } + + public override string DefaultName => "a house transfer contract"; + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + string houseName, owner, location; + + houseName = m_House == null ? "an unnamed house" : m_House.Sign.GetName(); + + Mobile houseOwner = m_House?.Owner; + + if (houseOwner == null) + owner = "nobody"; + else + owner = houseOwner.Name; + + int xLong = 0, yLat = 0, xMins = 0, yMins = 0; + bool xEast = false, ySouth = false; + + bool valid = m_House != null && Sextant.Format(m_House.Location, m_House.Map, ref xLong, ref yLat, ref xMins, + ref yMins, ref xEast, ref ySouth); + + if (valid) + location = $"{yLat}° {yMins}'{(ySouth ? "S" : "N")}, {xLong}° {xMins}'{(xEast ? "E" : "W")}"; + else + location = "unknown"; + + list.Add(1061112, Utility.FixHtml(houseName)); // House Name: ~1_val~ + list.Add(1061113, owner); // Owner: ~1_val~ + list.Add(1061114, location); // Location: ~1_val~ + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + Delete(); + } + + public override bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (!base.AllowSecureTrade(from, to, newOwner, accepted)) + return false; + if (!accepted) + return true; + + if (Deleted || m_House == null || m_House.Deleted || !m_House.IsOwner(from) || !from.CheckAlive() || + !to.CheckAlive()) + return false; + + if (HasAccountHouse(to)) + { + from.SendLocalizedMessage(501388); // You cannot transfer ownership to another house owner or co-owner! + return false; + } + + return m_House.CheckTransferPosition(from, to); + } + + public override void OnSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + if (Deleted) + return; + + Delete(); + + if (m_House == null || m_House.Deleted || !m_House.IsOwner(from) || !from.CheckAlive() || !to.CheckAlive()) + return; - if ( !accepted ) - return; + if (!accepted) + return; - from.SendLocalizedMessage( 501338 ); // You have transferred ownership of the house. - to.SendLocalizedMessage( 501339 ); /* You are now the owner of this house. + from.SendLocalizedMessage(501338); // You have transferred ownership of the house. + to.SendLocalizedMessage(501339); /* You are now the owner of this house. * The house's co-owner, friend, ban, and access lists have been cleared. * You should double-check the security settings on any doors and teleporters in the house. */ - m_House.RemoveKeys( from ); - m_House.Owner = to; - m_House.Bans.Clear(); - m_House.Friends.Clear(); - m_House.CoOwners.Clear(); - m_House.ChangeLocks( to ); - m_House.LastTraded = DateTime.UtcNow; - } - } - - public bool CheckTransferPosition( Mobile from, Mobile to ) - { - bool isValid = true; - Item sign = Sign; - Point3D p = sign?.GetWorldLocation() ?? Point3D.Zero; - - if ( from.Map != Map || to.Map != Map ) - isValid = false; - else if ( sign == null ) - isValid = false; - else if ( from.Map != sign.Map || to.Map != sign.Map ) - isValid = false; - else if ( IsInside( from ) ) - isValid = false; - else if ( IsInside( to ) ) - isValid = false; - else if ( !from.InRange( p, 2 ) ) - isValid = false; - else if ( !to.InRange( p, 2 ) ) - isValid = false; - - if ( !isValid ) - from.SendLocalizedMessage( 1062067 ); // In order to transfer the house, you and the recipient must both be outside the building and within two paces of the house sign. - - return isValid; - } - - public void BeginConfirmTransfer( Mobile from, Mobile to ) - { - if ( Deleted || !from.CheckAlive() || !IsOwner( from ) ) - return; - - if ( NewVendorSystem && HasPersonalVendors ) - { - from.SendLocalizedMessage( 1062467 ); // You cannot trade this house while you still have personal vendors inside. - } - else if ( DecayLevel == DecayLevel.DemolitionPending ) - { - from.SendLocalizedMessage( 1005321 ); // This house has been marked for demolition, and it cannot be transferred. - } - else if ( from == to ) - { - from.SendLocalizedMessage( 1005330 ); // You cannot transfer a house to yourself, silly. - } - else if ( to.Player ) - { - if ( HasAccountHouse( to ) ) - { - from.SendLocalizedMessage( 501388 ); // You cannot transfer ownership to another house owner or co-owner! - } - else if ( CheckTransferPosition( from, to ) ) - { - from.SendLocalizedMessage( 1005326 ); // Please wait while the other player verifies the transfer. - - if ( HasRentedVendors ) - { - /* You are about to be traded a home that has active vendor contracts. - * While there are active vendor contracts in this house, you - * cannot demolish OR customize the home. - * When you accept this house, you also accept landlordship for every - * contract vendor in the house. - */ - to.SendGump( new WarningGump( 1060635, 30720, 1062487, 32512, 420, 280, ConfirmTransfer_Callback, from ) ); - } - else - { - to.CloseGump( typeof( HouseTransferGump ) ); - to.SendGump( new HouseTransferGump( from, to, this ) ); - } - } - } - else - { - from.SendLocalizedMessage( 501384 ); // Only a player can own a house! - } - } - - private void ConfirmTransfer_Callback( Mobile to, bool ok, object state ) - { - Mobile from = (Mobile) state; - - if ( !ok || Deleted || !from.CheckAlive() || !IsOwner( from ) ) - return; - - if ( CheckTransferPosition( from, to ) ) - { - to.CloseGump( typeof( HouseTransferGump ) ); - to.SendGump( new HouseTransferGump( from, to, this ) ); - } - } - - public void EndConfirmTransfer( Mobile from, Mobile to ) - { - if ( Deleted || !from.CheckAlive() || !IsOwner( from ) ) - return; - - if ( NewVendorSystem && HasPersonalVendors ) - { - from.SendLocalizedMessage( 1062467 ); // You cannot trade this house while you still have personal vendors inside. - } - else if ( DecayLevel == DecayLevel.DemolitionPending ) - { - from.SendLocalizedMessage( 1005321 ); // This house has been marked for demolition, and it cannot be transferred. - } - else if ( from == to ) - { - from.SendLocalizedMessage( 1005330 ); // You cannot transfer a house to yourself, silly. - } - else if ( to.Player ) - { - if ( HasAccountHouse( to ) ) - { - from.SendLocalizedMessage( 501388 ); // You cannot transfer ownership to another house owner or co-owner! - } - else if ( CheckTransferPosition( from, to ) ) - { - NetState fromState = from.NetState, toState = to.NetState; - - if ( fromState != null && toState != null ) - { - if ( from.HasTrade ) - { - from.SendLocalizedMessage( 1062071 ); // You cannot trade a house while you have other trades pending. - } - else if ( to.HasTrade ) - { - to.SendLocalizedMessage( 1062071 ); // You cannot trade a house while you have other trades pending. - } - else if ( !to.Alive ) - { - // TODO: Check if the message is correct. - from.SendLocalizedMessage( 1062069 ); // You cannot transfer this house to that person. - } - else - { - Container c = fromState.AddTrade( toState ); - - c.DropItem( new TransferItem( this ) ); - } - } - } - } - else - { - from.SendLocalizedMessage( 501384 ); // Only a player can own a house! - } - } - - public void Release( Mobile m, Item item ) - { - if ( !IsCoOwner( m ) || !IsActive ) - return; - - if ( IsLockedDown( item ) ) - { - item.PublicOverheadMessage( MessageType.Label, 0x3B2, 501657 );//[no longer locked down] - SetLockdown( item, false ); - //TidyItemList( m_LockDowns ); - - (item as RewardBrazier)?.TurnOff(); - } - else if ( IsSecure( item ) ) - { - ReleaseSecure( m, item ); - } - else - { - m.LocalOverheadMessage( MessageType.Regular, 0x3E9, 1010416 ); // This is not locked down or secured. - } - } - - public void AddSecure( Mobile m, Item item ) - { - if ( Secures == null || !IsOwner( m ) || !IsActive ) - return; - - if ( !IsInside( item ) ) - { - m.SendLocalizedMessage( 1005525 ); // That is not in your house - } - else if ( IsLockedDown( item ) ) - { - m.SendLocalizedMessage( 1010550 ); // This is already locked down and cannot be secured. - } - else if ( !(item is Container) ) - { - LockDown( m, item ); - } - else - { - SecureInfo info = null; - - for ( int i = 0; info == null && i < Secures.Count; ++i ) - if ( ((SecureInfo)Secures[i]).Item == item ) - info = (SecureInfo)Secures[i]; - - if ( info != null ) - { - m.CloseGump( typeof ( SetSecureLevelGump ) ); - m.SendGump( new SetSecureLevelGump( m_Owner, info, this ) ); - } - else if ( item.Parent != null ) - { - m.SendLocalizedMessage( 1010423 ); // You cannot secure this, place it on the ground first. - } - // Mondain's Legacy mod - else if ( !( item is BaseAddonContainer ) && !item.Movable ) - { - m.SendLocalizedMessage( 1010424 ); // You cannot secure this. - } - else if ( !IsAosRules && SecureCount >= MaxSecures ) - { - // The maximum number of secure items has been reached : - m.SendLocalizedMessage( 1008142, true, MaxSecures.ToString() ); - } - else if ( IsAosRules ? !CheckAosLockdowns( 1 ) : ((LockDownCount + 125) >= MaxLockDowns) ) - { - m.SendLocalizedMessage( 1005379 ); // That would exceed the maximum lock down limit for this house - } - else if ( IsAosRules && !CheckAosStorage( item.TotalItems ) ) - { - m.SendLocalizedMessage( 1061839 ); // This action would exceed the secure storage limit of the house. - } - else - { - info = new SecureInfo( (Container)item, SecureLevel.Owner ); - - item.IsLockedDown = false; - item.IsSecure = true; - - Secures.Add( info ); - LockDowns.Remove( item ); - item.Movable = false; - - m.CloseGump( typeof ( SetSecureLevelGump ) ); - m.SendGump( new SetSecureLevelGump( m_Owner, info, this ) ); - } - } - } - - public virtual bool IsCombatRestricted( Mobile m ) - { - if ( m == null || !m.Player || m.AccessLevel >= AccessLevel.GameMaster || !IsAosRules || ( m_Owner != null && m_Owner.AccessLevel >= AccessLevel.GameMaster )) - return false; - - for ( int i = 0; i < m.Aggressed.Count; ++i ) - { - AggressorInfo info = m.Aggressed[i]; - - Guild attackerGuild = m.Guild as Guild; - Guild defenderGuild = info.Defender.Guild as Guild; - - if ( info.Defender.Player && info.Defender.Alive && (DateTime.UtcNow - info.LastCombatTime) < HouseRegion.CombatHeatDelay && (attackerGuild == null || defenderGuild == null || defenderGuild != attackerGuild && !defenderGuild.IsEnemy( attackerGuild )) ) - return true; - } - - return false; - } - - public bool HasSecureAccess( Mobile m, SecureLevel level ) - { - if ( m.AccessLevel >= AccessLevel.GameMaster ) - return true; - - if ( IsCombatRestricted( m ) ) - return false; - - switch ( level ) - { - case SecureLevel.Owner: return IsOwner( m ); - case SecureLevel.CoOwners: return IsCoOwner( m ); - case SecureLevel.Friends: return IsFriend( m ); - case SecureLevel.Anyone: return true; - case SecureLevel.Guild: return IsGuildMember( m ); - } - - return false; - } - - public void ReleaseSecure( Mobile m, Item item ) - { - if ( Secures == null || !IsOwner( m ) || item is StrongBox || !IsActive ) - return; - - for ( int i = 0; i < Secures.Count; ++i ) - { - SecureInfo info = (SecureInfo)Secures[i]; - - if ( info.Item == item && HasSecureAccess( m, info.Level ) ) - { - item.IsLockedDown = false; - item.IsSecure = false; - - #region Mondain's Legacy - if ( item is BaseAddonContainer ) - item.Movable = false; - else - #endregion - - item.Movable = true; - item.SetLastMoved(); - item.PublicOverheadMessage( MessageType.Label, 0x3B2, 501656 );//[no longer secure] - Secures.RemoveAt( i ); - return; - } - } - - m.SendLocalizedMessage( 501717 );//This isn't secure... - } - - public override bool Decays => false; - - public void AddStrongBox( Mobile from ) - { - if ( !IsCoOwner( from ) || !IsActive ) - return; - - if ( from == Owner ) - { - from.SendLocalizedMessage( 502109 ); // Owners don't get a strong box - return; - } - - if ( IsAosRules ? !CheckAosLockdowns( 1 ) : ((LockDownCount + 1) > MaxLockDowns) ) - { - from.SendLocalizedMessage( 1005379 );//That would exceed the maximum lock down limit for this house - return; - } - - foreach ( SecureInfo info in Secures ) - { - Container c = info.Item; - - if ( !c.Deleted && c is StrongBox && ((StrongBox)c).Owner == from ) - { - from.SendLocalizedMessage( 502112 );//You already have a strong box - return; - } - } - - for ( int i = 0; Doors != null && i < Doors.Count; ++i ) - { - BaseDoor door = Doors[i] as BaseDoor; - Point3D p = door.Location; - - if ( door.Open ) - p = new Point3D( p.X - door.Offset.X, p.Y - door.Offset.Y, p.Z - door.Offset.Z ); - - if ( (from.Z + 16) >= p.Z && (p.Z + 16) >= from.Z ) - { - if ( from.InRange( p, 1 ) ) - { - from.SendLocalizedMessage( 502113 ); // You cannot place a strongbox near a door or near steps. - return; - } - } - } - - StrongBox sb = new StrongBox( from, this ); - sb.Movable = false; - sb.IsLockedDown = false; - sb.IsSecure = true; - Secures.Add( new SecureInfo( sb, SecureLevel.CoOwners ) ); - sb.MoveToWorld( from.Location, from.Map ); - } - - public void Kick( Mobile from, Mobile targ ) - { - if ( !IsFriend( from ) || Friends == null ) - return; - - if ( targ.AccessLevel > AccessLevel.Player && from.AccessLevel <= targ.AccessLevel ) - { - from.SendLocalizedMessage( 501346 ); // Uh oh...a bigger boot may be required! - } - else if ( IsFriend( targ ) && !Core.ML ) - { - from.SendLocalizedMessage( 501348 ); // You cannot eject a friend of the house! - } - else if ( targ is PlayerVendor ) - { - from.SendLocalizedMessage( 501351 ); // You cannot eject a vendor. - } - else if ( !IsInside( targ ) ) - { - from.SendLocalizedMessage( 501352 ); // You may not eject someone who is not in your house! - } - else if ( targ is BaseCreature && ((BaseCreature)targ).NoHouseRestrictions ) - { - from.SendLocalizedMessage( 501347 ); // You cannot eject that from the house! - } - else - { - targ.MoveToWorld( BanLocation, Map ); - - from.SendLocalizedMessage( 1042840, targ.Name ); // ~1_PLAYER NAME~ has been ejected from this house. - targ.SendLocalizedMessage( 501341 ); /* You have been ejected from this house. - * If you persist in entering, you may be banned from the house. - */ - } - } - - public void RemoveAccess( Mobile from, Mobile targ ) - { - if ( !IsFriend( from ) || Access == null ) - return; - - if ( Access.Contains( targ ) ) - { - Access.Remove( targ ); - - if ( !HasAccess( targ ) && IsInside( targ ) ) - { - targ.Location = BanLocation; - targ.SendLocalizedMessage( 1060734 ); // Your access to this house has been revoked. - } - - from.SendLocalizedMessage( 1050051 ); // The invitation has been revoked. - } - } - - public void RemoveBan( Mobile from, Mobile targ ) - { - if ( !IsCoOwner( from ) || Bans == null ) - return; - - if ( Bans.Contains( targ ) ) - { - Bans.Remove( targ ); - - from.SendLocalizedMessage( 501297 ); // The ban is lifted. - } - } - - public void Ban( Mobile from, Mobile targ ) - { - if ( !IsFriend( from ) || Bans == null ) - return; - - if ( targ.AccessLevel > AccessLevel.Player && from.AccessLevel <= targ.AccessLevel ) - { - from.SendLocalizedMessage( 501354 ); // Uh oh...a bigger boot may be required. - } - else if ( IsFriend( targ ) ) - { - from.SendLocalizedMessage( 501348 ); // You cannot eject a friend of the house! - } - else if ( targ is PlayerVendor ) - { - from.SendLocalizedMessage( 501351 ); // You cannot eject a vendor. - } - else if ( Bans.Count >= MaxBans ) - { - from.SendLocalizedMessage( 501355 ); // The ban limit for this house has been reached! - } - else if ( IsBanned( targ ) ) - { - from.SendLocalizedMessage( 501356 ); // This person is already banned! - } - else if ( !IsInside( targ ) ) - { - from.SendLocalizedMessage( 501352 ); // You may not eject someone who is not in your house! - } - else if ( !Public && IsAosRules ) - { - from.SendLocalizedMessage( 1062521 ); // You cannot ban someone from a private house. Revoke their access instead. - } - else if ( targ is BaseCreature && ((BaseCreature)targ).NoHouseRestrictions ) - { - from.SendLocalizedMessage( 1062040 ); // You cannot ban that. - } - else - { - Bans.Add( targ ); - - from.SendLocalizedMessage( 1042839, targ.Name ); // ~1_PLAYER_NAME~ has been banned from this house. - targ.SendLocalizedMessage( 501340 ); // You have been banned from this house. - - targ.MoveToWorld( BanLocation, Map ); - } - } - - public void GrantAccess( Mobile from, Mobile targ ) - { - if ( !IsFriend( from ) || Access == null ) - return; - - if ( HasAccess( targ ) ) - { - from.SendLocalizedMessage( 1060729 ); // That person already has access to this house. - } - else if ( !targ.Player ) - { - from.SendLocalizedMessage( 1060712 ); // That is not a player. - } - else if ( IsBanned( targ ) ) - { - from.SendLocalizedMessage( 501367 ); // This person is banned! Unban them first. - } - else - { - Access.Add( targ ); - - targ.SendLocalizedMessage( 1060735 ); // You have been granted access to this house. - } - } - - public void AddCoOwner( Mobile from, Mobile targ ) - { - if ( !IsOwner( from ) || CoOwners == null || Friends == null ) - return; - - if ( IsOwner( targ ) ) - { - from.SendLocalizedMessage( 501360 ); // This person is already the house owner! - } - else if ( Friends.Contains( targ ) ) - { - from.SendLocalizedMessage( 501361 ); // This person is a friend of the house. Remove them first. - } - else if ( !targ.Player ) - { - from.SendLocalizedMessage( 501362 ); // That can't be a co-owner of the house. - } - else if ( !Core.AOS && HasAccountHouse( targ ) ) - { - from.SendLocalizedMessage( 501364 ); // That person is already a house owner. - } - else if ( IsBanned( targ ) ) - { - from.SendLocalizedMessage( 501367 ); // This person is banned! Unban them first. - } - else if ( CoOwners.Count >= MaxCoOwners ) - { - from.SendLocalizedMessage( 501368 ); // Your co-owner list is full! - } - else if ( CoOwners.Contains( targ ) ) - { - from.SendLocalizedMessage( 501369 ); // This person is already on your co-owner list! - } - else - { - CoOwners.Add( targ ); - - targ.Delta( MobileDelta.Noto ); - targ.SendLocalizedMessage( 501343 ); // You have been made a co-owner of this house. - } - } - - public void RemoveCoOwner( Mobile from, Mobile targ ) - { - if ( !IsOwner( from ) || CoOwners == null ) - return; - - if ( CoOwners.Contains( targ ) ) - { - CoOwners.Remove( targ ); - - targ.Delta( MobileDelta.Noto ); - - from.SendLocalizedMessage( 501299 ); // Co-owner removed from list. - targ.SendLocalizedMessage( 501300 ); // You have been removed as a house co-owner. - - foreach ( SecureInfo info in Secures ) - { - Container c = info.Item; - - if ( c is StrongBox && ((StrongBox)c).Owner == targ ) - { - c.IsLockedDown = false; - c.IsSecure = false; - Secures.Remove( info ); - c.Destroy(); - break; - } - } - } - } - - public void AddFriend( Mobile from, Mobile targ ) - { - if ( !IsCoOwner( from ) || Friends == null || CoOwners == null ) - return; - - if ( IsOwner( targ ) ) - { - from.SendLocalizedMessage( 501370 ); // This person is already an owner of the house! - } - else if ( CoOwners.Contains( targ ) ) - { - from.SendLocalizedMessage( 501369 ); // This person is already on your co-owner list! - } - else if ( !targ.Player ) - { - from.SendLocalizedMessage( 501371 ); // That can't be a friend of the house. - } - else if ( IsBanned( targ ) ) - { - from.SendLocalizedMessage( 501374 ); // This person is banned! Unban them first. - } - else if ( Friends.Count >= MaxFriends ) - { - from.SendLocalizedMessage( 501375 ); // Your friends list is full! - } - else if ( Friends.Contains( targ ) ) - { - from.SendLocalizedMessage( 501376 ); // This person is already on your friends list! - } - else - { - Friends.Add( targ ); - - targ.Delta( MobileDelta.Noto ); - targ.SendLocalizedMessage( 501337 ); // You have been made a friend of this house. - } - } - - public void RemoveFriend( Mobile from, Mobile targ ) - { - if ( !IsCoOwner( from ) || Friends == null ) - return; - - if ( Friends.Contains( targ ) ) - { - Friends.Remove( targ ); - - targ.Delta( MobileDelta.Noto ); - - from.SendLocalizedMessage( 501298 ); // Friend removed from list. - targ.SendLocalizedMessage( 1060751 ); // You are no longer a friend of this house. - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 15 ); // version - - if ( !DynamicDecay.Enabled ) - { - writer.Write( (int) -1 ); - } - else - { - writer.Write( (int) m_CurrentStage ); - writer.Write( NextDecayStage ); - } - - writer.Write( (Point3D) m_RelativeBanLocation ); - - writer.WriteItemList( VendorRentalContracts, true ); - writer.WriteMobileList( InternalizedVendors, true ); - - writer.WriteEncodedInt( RelocatedEntities.Count ); - foreach ( RelocatedEntity relEntity in RelocatedEntities ) - { - writer.Write( (Point3D) relEntity.RelativeLocation ); - - if (relEntity.Entity.Deleted) - writer.Write( (int) Serial.MinusOne ); - else - writer.Write( (int) relEntity.Entity.Serial ); - } - - writer.WriteEncodedInt( VendorInventories.Count ); - for ( int i = 0; i < VendorInventories.Count; i++ ) - { - VendorInventory inventory = (VendorInventory) VendorInventories[i]; - inventory.Serialize( writer ); - } - - writer.Write( (DateTime) LastRefreshed ); - writer.Write( (bool) RestrictDecay ); - - writer.Write( (int) Visits ); - - writer.Write( (int) Price ); - - writer.WriteMobileList( Access ); - - writer.Write( BuiltOn ); - writer.Write( LastTraded ); - - writer.WriteItemList( Addons, true ); - - writer.Write( Secures.Count ); - - for ( int i = 0; i < Secures.Count; ++i ) - ((SecureInfo)Secures[i]).Serialize( writer ); - - writer.Write( m_Public ); - - //writer.Write( BanLocation ); - - writer.Write( m_Owner ); - - // Version 5 no longer serializes region coords - /*writer.Write( (int)m_Region.Coords.Count ); - foreach( Rectangle2D rect in m_Region.Coords ) - { - writer.Write( rect ); - }*/ - - writer.WriteMobileList( CoOwners, true ); - writer.WriteMobileList( Friends, true ); - writer.WriteMobileList( Bans, true ); - - writer.Write( Sign ); - writer.Write( m_Trash ); - - writer.WriteItemList( Doors, true ); - writer.WriteItemList( LockDowns, true ); - //writer.WriteItemList( m_Secures, true ); - - writer.Write( (int) MaxLockDowns ); - writer.Write( (int) MaxSecures ); - - // Items in locked down containers that aren't locked down themselves must decay! - for ( int i = 0; i < LockDowns.Count; ++i ) - { - Item item = (Item)LockDowns[i]; - - if ( item is Container && !(item is BaseBoard || item is Aquarium || item is FishBowl) ) - { - Container cont = (Container)item; - List children = cont.Items; - - for ( int j = 0; j < children.Count; ++j ) - { - Item child = children[j]; - - if ( child.Decays && !child.IsLockedDown && !child.IsSecure && (child.LastMoved + child.DecayTime) <= DateTime.UtcNow ) - Timer.DelayCall( TimeSpan.Zero, child.Delete ); - } - } - } - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - int count; - bool loadedDynamicDecay = false; - - switch ( version ) - { - case 15: - { - int stage = reader.ReadInt(); - - if ( stage != -1 ) - { - m_CurrentStage = (DecayLevel)stage; - NextDecayStage = reader.ReadDateTime(); - loadedDynamicDecay = true; - } - - goto case 14; - } - case 14: - { - m_RelativeBanLocation = reader.ReadPoint3D(); - goto case 13; - } - case 13: // removed ban location serialization - case 12: - { - VendorRentalContracts = reader.ReadItemList(); - InternalizedVendors = reader.ReadMobileList(); - - int relocatedCount = reader.ReadEncodedInt(); - for ( int i = 0; i < relocatedCount; i++ ) - { - Point3D relLocation = reader.ReadPoint3D(); - IEntity entity = World.FindEntity( reader.ReadInt() ); - - if ( entity != null ) - RelocatedEntities.Add( new RelocatedEntity( entity, relLocation ) ); - } - - int inventoryCount = reader.ReadEncodedInt(); - for ( int i = 0; i < inventoryCount; i++ ) - { - VendorInventory inventory = new VendorInventory( this, reader ); - VendorInventories.Add( inventory ); - } - - goto case 11; - } - case 11: - { - LastRefreshed = reader.ReadDateTime(); - RestrictDecay = reader.ReadBool(); - goto case 10; - } - case 10: // just a signal for updates - case 9: - { - Visits = reader.ReadInt(); - goto case 8; - } - case 8: - { - Price = reader.ReadInt(); - goto case 7; - } - case 7: - { - Access = reader.ReadMobileList(); - goto case 6; - } - case 6: - { - BuiltOn = reader.ReadDateTime(); - LastTraded = reader.ReadDateTime(); - goto case 5; - } - case 5: // just removed fields - case 4: - { - Addons = reader.ReadItemList(); - goto case 3; - } - case 3: - { - count = reader.ReadInt(); - Secures = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) - { - SecureInfo info = new SecureInfo( reader ); - - if ( info.Item != null ) - { - info.Item.IsSecure = true; - Secures.Add( info ); - } - } - - goto case 2; - } - case 2: - { - m_Public = reader.ReadBool(); - goto case 1; - } - case 1: - { - if ( version < 13 ) - reader.ReadPoint3D(); // house ban location - goto case 0; - } - case 0: - { - if ( version < 14 ) - m_RelativeBanLocation = BaseBanLocation; - - if ( version < 12 ) - { - VendorRentalContracts = new ArrayList(); - InternalizedVendors = new ArrayList(); - } - - if ( version < 4 ) - Addons = new ArrayList(); - - if ( version < 7 ) - Access = new ArrayList(); - - if ( version < 8 ) - Price = DefaultPrice; - - m_Owner = reader.ReadMobile(); - - if ( version < 5 ) - { - count = reader.ReadInt(); - - for(int i=0;i list ); - - if ( list == null ) - m_Table[m_Owner] = list = new List(); - - list.Add( this ); - } - break; - } - } - - if ( version <= 1 ) - ChangeSignType( 0xBD2 );//private house, plain brass sign - - if ( version < 10 ) - { - /* NOTE: This can exceed the house lockdown limit. It must be this way, because - * we do not want players' items to decay without them knowing. Or not even - * having a chance to fix it themselves. - */ - - Timer.DelayCall( TimeSpan.Zero, FixLockdowns_Sandbox ); - } - - if ( version < 11 ) - LastRefreshed = DateTime.UtcNow + TimeSpan.FromHours( 24 * Utility.RandomDouble() ); - - if ( DynamicDecay.Enabled && !loadedDynamicDecay ) - { - DecayLevel old = GetOldDecayLevel(); - - if ( old == DecayLevel.DemolitionPending ) - old = DecayLevel.Collapsed; - - SetDynamicDecay( old ); - } - - if ( !CheckDecay() ) - { - if ( RelocatedEntities.Count > 0 ) - Timer.DelayCall( TimeSpan.Zero, RestoreRelocatedEntities ); - - if ( m_Owner == null && Friends.Count == 0 && CoOwners.Count == 0 ) - Timer.DelayCall( TimeSpan.FromSeconds( 10.0 ), Delete ); - } - } - - private void FixLockdowns_Sandbox() - { - ArrayList lockDowns = new ArrayList(); - - for ( int i = 0; LockDowns != null && i < LockDowns.Count; ++i ) - { - Item item = (Item)LockDowns[i]; - - if ( item is Container ) - lockDowns.Add( item ); - } - - for ( int i = 0; i < lockDowns.Count; ++i ) - SetLockdown( (Item)lockDowns[i], true, true ); - } - - public static void HandleDeletion( Mobile mob ) - { - List houses = GetHouses( mob ); - - if ( houses.Count == 0 ) - return; - - Account acct = mob.Account as Account; - Mobile trans = null; - - for ( int i = 0; i < acct.Length; ++i ) - { - if ( acct[i] != null && acct[i] != mob ) - trans = acct[i]; - } - - for ( int i = 0; i < houses.Count; ++i ) - { - BaseHouse house = houses[i]; - - bool canClaim = false; - - if ( trans == null ) - canClaim = ( house.CoOwners.Count > 0 ); - /*{ - for ( int j = 0; j < house.CoOwners.Count; ++j ) - { - Mobile check = house.CoOwners[j] as Mobile; - - if ( check != null && !check.Deleted && !HasAccountHouse( check ) ) - { - canClaim = true; - break; - } - } - }*/ - - if ( trans == null && !canClaim ) - Timer.DelayCall( TimeSpan.Zero, house.Delete ); - else - house.Owner = trans; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner - { - get => m_Owner; - set - { - if ( m_Owner != null ) - { - m_Table.TryGetValue( m_Owner, out List list ); - - if ( list == null ) - m_Table[m_Owner] = list = new List(); - - list.Remove( this ); - m_Owner.Delta( MobileDelta.Noto ); - } - - m_Owner = value; - - if ( m_Owner != null ) - { - m_Table.TryGetValue( m_Owner, out List list ); - - if ( list == null ) - m_Table[m_Owner] = list = new List(); - - list.Add( this ); - m_Owner.Delta( MobileDelta.Noto ); - } - - Sign?.InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Visits { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Public - { - get => m_Public; - set - { - if ( m_Public != value ) - { - m_Public = value; - - if ( !m_Public ) // Privatizing the house, change to brass sign - ChangeSignType( 0xBD2 ); - - Sign?.InvalidateProperties(); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxSecures { get; set; } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D BanLocation - { - get - { - if ( m_Region != null ) - return m_Region.GoLocation; - - Point3D rel = m_RelativeBanLocation; - return new Point3D( X + rel.X, Y + rel.Y, Z + rel.Z ); - } - set => RelativeBanLocation = new Point3D( value.X - X, value.Y - Y, value.Z - Z ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public Point3D RelativeBanLocation - { - get => m_RelativeBanLocation; - set - { - m_RelativeBanLocation = value; - - if ( m_Region != null ) - m_Region.GoLocation = new Point3D( X + value.X, Y + value.Y, Z + value.Z ); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxLockDowns { get; set; } - - public Region Region => m_Region; - public ArrayList CoOwners { get; set; } - - public ArrayList Friends { get; set; } - - public ArrayList Access { get; set; } - - public ArrayList Bans { get; set; } - - public ArrayList Doors { get; set; } - - public int GetLockdowns() - { - int count = 0; - - if ( LockDowns != null ) - { - for ( int i = 0; i < LockDowns.Count; ++i ) - { - if ( LockDowns[i] is Item ) - { - Item item = (Item)LockDowns[i]; - - if ( !(item is Container) ) - count += item.TotalItems; - } - - count++; - } - } - - return count; - } - - public int LockDownCount - { - get - { - int count = 0; - - count += GetLockdowns(); - - if ( Secures != null ) - { - for ( int i = 0; i < Secures.Count; ++i ) - { - SecureInfo info = (SecureInfo)Secures[i]; - - if ( info.Item.Deleted ) - continue; - if ( info.Item is StrongBox ) - count += 1; - else - count += 125; - } - } - - return count; - } - } - - public int SecureCount - { - get - { - int count = 0; - - if ( Secures != null ) - { - for ( int i = 0; i < Secures.Count; i++ ) - { - SecureInfo info = (SecureInfo)Secures[i]; - - if ( info.Item.Deleted ) - continue; - if ( !(info.Item is StrongBox) ) - count += 1; - } - } - - return count; - } - } - - public ArrayList Addons { get; set; } - - public ArrayList LockDowns { get; private set; } - - public ArrayList Secures { get; private set; } - - public HouseSign Sign { get; set; } - - public ArrayList PlayerVendors { get; } = new ArrayList(); - - public ArrayList PlayerBarkeepers { get; } = new ArrayList(); - - public ArrayList VendorRentalContracts { get; private set; } - - public ArrayList VendorInventories { get; } = new ArrayList(); - - public ArrayList RelocatedEntities { get; } = new ArrayList(); - - public MovingCrate MovingCrate { get; set; } - - public ArrayList InternalizedVendors { get; private set; } - - public DateTime BuiltOn { get; set; } - - public DateTime LastTraded { get; set; } - - public override void OnDelete() - { - RestoreRelocatedEntities(); - - new FixColumnTimer( this ).Start(); - - base.OnDelete(); - } - - private class FixColumnTimer : Timer - { - private Map m_Map; - private int m_StartX, m_StartY, m_EndX, m_EndY; - - public FixColumnTimer( BaseMulti multi ) : base( TimeSpan.Zero ) - { - m_Map = multi.Map; - - MultiComponentList mcl = multi.Components; - - m_StartX = multi.X + mcl.Min.X; - m_StartY = multi.Y + mcl.Min.Y; - m_EndX = multi.X + mcl.Max.X; - m_EndY = multi.Y + mcl.Max.Y; - } - - protected override void OnTick() - { - if ( m_Map == null ) - return; - - for ( int x = m_StartX; x <= m_EndX; ++x ) - for ( int y = m_StartY; y <= m_EndY; ++y ) - m_Map.FixColumn( x, y ); - } - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - if ( m_Owner != null ) - { - m_Table.TryGetValue( m_Owner, out List list ); - - if ( list == null ) - m_Table[m_Owner] = list = new List(); - - list.Remove( this ); - } - - if ( m_Region != null ) - { - m_Region.Unregister(); - m_Region = null; - } - - Sign?.Delete(); - - m_Trash?.Delete(); - - if ( Doors != null ) - { - for ( int i = 0; i < Doors.Count; ++i ) - { - Item item = (Item)Doors[i]; - - item?.Delete(); - } - - Doors.Clear(); - } - - if ( LockDowns != null ) - { - for ( int i = 0; i < LockDowns.Count; ++i ) - { - Item item = (Item)LockDowns[i]; - - if ( item != null ) - { - item.IsLockedDown = false; - item.IsSecure = false; - item.Movable = true; - item.SetLastMoved(); - } - } - - LockDowns.Clear(); - } - - if ( VendorRentalContracts != null ) - { - for ( int i = 0; i < VendorRentalContracts.Count; ++i ) - { - Item item = (Item)VendorRentalContracts[i]; - - if ( item != null ) - { - item.IsLockedDown = false; - item.IsSecure = false; - item.Movable = true; - item.SetLastMoved(); - } - } - - VendorRentalContracts.Clear(); - } - - if ( Secures != null ) - { - for ( int i = 0; i < Secures.Count; ++i ) - { - SecureInfo info = (SecureInfo)Secures[i]; - - if ( info.Item is StrongBox ) - { - info.Item.Destroy(); - } - else - { - info.Item.IsLockedDown = false; - info.Item.IsSecure = false; - info.Item.Movable = true; - info.Item.SetLastMoved(); - } - } - - Secures.Clear(); - } - - if ( Addons != null ) - { - for ( int i = 0; i < Addons.Count; ++i ) - { - Item item = (Item)Addons[i]; - - if ( item != null ) - { - if ( !item.Deleted && item is IAddon ) - { - - Item deed = ((IAddon)item).Deed; - bool retainDeedHue = false; //if the items aren't hued but the deed itself is - int hue = 0; - - if ( item is BaseAddon && ((BaseAddon)item).RetainDeedHue ) //There are things that are IAddon which aren't BaseAddon - { - BaseAddon ba = (BaseAddon)item; - retainDeedHue = true; - - for( int j = 0; hue == 0 && j < ba.Components.Count; ++j ) - { - AddonComponent c = ba.Components[j]; - - if ( c.Hue != 0 ) - hue = c.Hue; - } - } - - if ( deed != null ) - { - if ( retainDeedHue ) - deed.Hue = hue; - deed.MoveToWorld( item.Location, item.Map ); - } - } - - item.Delete(); - } - } - - Addons.Clear(); - } - - ArrayList inventories = new ArrayList( VendorInventories ); - - foreach ( VendorInventory inventory in inventories ) - inventory.Delete(); - - MovingCrate?.Delete(); - - KillVendors(); - - AllHouses.Remove( this ); - } - - public static bool HasHouse( Mobile m ) - { - if ( m == null ) - return false; - - m_Table.TryGetValue( m, out List list ); - - if ( list == null ) - return false; - - for ( int i = 0; i < list.Count; ++i ) - { - BaseHouse h = list[i]; - - if ( !h.Deleted ) - return true; - } - - return false; - } - - public static bool HasAccountHouse( Mobile m ) - { - Account a = m.Account as Account; - - if ( a == null ) - return false; - - for ( int i = 0; i < a.Length; ++i ) - if ( a[i] != null && HasHouse( a[i] ) ) - return true; - - return false; - } - - public bool IsOwner( Mobile m ) - { - if ( m == null ) - return false; - - if ( m == m_Owner || m.AccessLevel >= AccessLevel.GameMaster ) - return true; - - return IsAosRules && AccountHandler.CheckAccount( m, m_Owner ); - } - - public bool IsCoOwner( Mobile m ) - { - if ( m == null || CoOwners == null ) - return false; - - if ( IsOwner( m ) || CoOwners.Contains( m ) ) - return true; - - return !IsAosRules && AccountHandler.CheckAccount( m, m_Owner ); - } - - public bool IsGuildMember( Mobile m ) - { - if ( m == null || Owner?.Guild == null ) - return false; - - return ( m.Guild == Owner.Guild ); - } - - public void RemoveKeys( Mobile m ) - { - if ( Doors != null ) - { - uint keyValue = 0; - - for ( int i = 0; keyValue == 0 && i < Doors.Count; ++i ) - { - BaseDoor door = Doors[i] as BaseDoor; - - if ( door != null ) - keyValue = door.KeyValue; - } - - Key.RemoveKeys( m, keyValue ); - } - } - - public void ChangeLocks( Mobile m ) - { - uint keyValue = CreateKeys( m ); - - if ( Doors != null ) - { - for ( int i = 0; i < Doors.Count; ++i ) - { - BaseDoor door = Doors[i] as BaseDoor; - - if ( door != null ) - door.KeyValue = keyValue; - } - } - } - - public void RemoveLocks() - { - if ( Doors != null ) - { - for (int i=0;i null; - public virtual int ConvertOffsetX => 0; - public virtual int ConvertOffsetY => 0; - public virtual int ConvertOffsetZ => 0; - - public virtual int DefaultPrice => 0; - - [CommandProperty( AccessLevel.GameMaster )] - public int Price { get; set; } - - public virtual HouseDeed GetDeed() - { - return null; - } - - public bool IsFriend( Mobile m ) - { - if ( m == null || Friends == null ) - return false; - - return ( IsCoOwner( m ) || Friends.Contains( m ) ); - } - - public bool IsBanned( Mobile m ) - { - if ( m == null || m == Owner || m.AccessLevel > AccessLevel.Player || Bans == null ) - return false; - - Account theirAccount = m.Account as Account; - - for ( int i = 0; i < Bans.Count; ++i ) - { - Mobile c = (Mobile)Bans[i]; - - if ( c == m ) - return true; - - Account bannedAccount = c.Account as Account; - - if ( bannedAccount != null && bannedAccount == theirAccount ) - return true; - } - - return false; - } - - public bool HasAccess( Mobile m ) - { - if ( m == null ) - return false; - - if ( m.AccessLevel > AccessLevel.Player || IsFriend( m ) || ( Access != null && Access.Contains( m ) ) ) - return true; - - if ( m is BaseCreature ) - { - BaseCreature bc = (BaseCreature)m; - - if ( bc.NoHouseRestrictions ) - return true; - - if ( bc.Controlled || bc.Summoned ) - { - m = bc.ControlMaster; - - if ( m == null ) - m = bc.SummonMaster; - - if ( m == null ) - return false; - - if ( m.AccessLevel > AccessLevel.Player || IsFriend( m ) || ( Access != null && Access.Contains( m ) ) ) - return true; - } - } - - return false; - } - - public new bool IsLockedDown( Item check ) - { - if ( check == null ) - return false; - - if ( LockDowns == null ) - return false; - - return ( LockDowns.Contains( check ) || VendorRentalContracts.Contains( check ) ); - } - - public new bool IsSecure( Item item ) - { - if ( item == null ) - return false; - - if ( Secures == null ) - return false; - - bool contains = false; - - for ( int i = 0; !contains && i < Secures.Count; ++i ) - contains = ( ((SecureInfo)Secures[i]).Item == item ); - - return contains; - } - - public virtual Guildstone FindGuildstone() - { - Map map = Map; - - if ( map == null ) - return null; - - MultiComponentList mcl = Components; - IPooledEnumerable eable = map.GetItemsInBounds( new Rectangle2D( X + mcl.Min.X, Y + mcl.Min.Y, mcl.Width, mcl.Height ) ); - - foreach ( Guildstone item in eable ) - { - if ( Contains( item ) ) - { - eable.Free(); - return item; - } - } - - eable.Free(); - return null; - } - } - - public enum DecayType - { - Ageless, - AutoRefresh, - ManualRefresh, - Condemned - } - - public enum DecayLevel - { - Ageless, - LikeNew, - Slightly, - Somewhat, - Fairly, - Greatly, - IDOC, - Collapsed, - DemolitionPending - } - - public enum SecureAccessResult - { - Insecure, - Accessible, - Inaccessible - } - - public enum SecureLevel - { - Owner, - CoOwners, - Friends, - Anyone, - Guild - } - - public class SecureInfo : ISecurable - { - public Container Item { get; } - - public SecureLevel Level { get; set; } - - public SecureInfo( Container item, SecureLevel level ) - { - Item = item; - Level = level; - } - - public SecureInfo( GenericReader reader ) - { - Item = reader.ReadItem() as Container; - Level = (SecureLevel)reader.ReadByte(); - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( Item ); - writer.Write( (byte) Level ); - } - } - - public class RelocatedEntity - { - public IEntity Entity { get; } - - public Point3D RelativeLocation { get; } - - public RelocatedEntity( IEntity entity, Point3D relativeLocation ) - { - Entity = entity; - RelativeLocation = relativeLocation; - } - } - - #region Targets - - public class LockdownTarget : Target - { - private bool m_Release; - private BaseHouse m_House; - - public LockdownTarget( bool release, BaseHouse house ) : base( 12, false, TargetFlags.None ) - { - CheckLOS = false; - - m_Release = release; - m_House = house; - } - - protected override void OnTargetNotAccessible( Mobile from, object targeted ) - { - OnTarget( from, targeted ); - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsCoOwner( from ) ) - return; - - if ( targeted is Item ) - { - if ( m_Release ) - { - #region Mondain's legacy - if ( targeted is AddonContainerComponent ) - { - AddonContainerComponent component = (AddonContainerComponent) targeted; - - if ( component.Addon != null ) - m_House.Release( from, component.Addon ); - } - else - #endregion - - m_House.Release( from, (Item)targeted ); - } - else - { - if ( targeted is VendorRentalContract ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1062392 ); // You must double click the contract in your pack to lock it down. - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501732 ); // I cannot lock this down! - } - else if ( (Item)targeted is AddonComponent ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 501727 ); // You cannot lock that down! - from.LocalOverheadMessage( MessageType.Regular, 0x3E9, 501732 ); // I cannot lock this down! - } - else - { - #region Mondain's legacy - if ( targeted is AddonContainerComponent ) - { - AddonContainerComponent component = (AddonContainerComponent) targeted; - - if ( component.Addon != null ) - m_House.LockDown( from, component.Addon ); - } - else - #endregion - - m_House.LockDown( from, (Item)targeted ); - } - } - } - else if ( targeted is StaticTarget ) - { - } - else - { - from.SendLocalizedMessage( 1005377 ); //You cannot lock that down - } - } - } - - public class SecureTarget : Target - { - private bool m_Release; - private BaseHouse m_House; - - public SecureTarget( bool release, BaseHouse house ) : base( 12, false, TargetFlags.None ) - { - CheckLOS = false; - - m_Release = release; - m_House = house; - } - - protected override void OnTargetNotAccessible( Mobile from, object targeted ) - { - OnTarget( from, targeted ); - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsCoOwner( from ) ) - return; - - if ( targeted is Item ) - { - if ( m_Release ) - { - #region Mondain's legacy - if ( targeted is AddonContainerComponent ) - { - AddonContainerComponent component = (AddonContainerComponent) targeted; - - if ( component.Addon != null ) - m_House.ReleaseSecure( from, component.Addon ); - } - else - #endregion - - m_House.ReleaseSecure( from, (Item)targeted ); - } - else - { - if ( targeted is VendorRentalContract ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1062392 ); // You must double click the contract in your pack to lock it down. - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501732 ); // I cannot lock this down! - } - else - { - #region Mondain's legacy - if ( targeted is AddonContainerComponent ) - { - AddonContainerComponent component = (AddonContainerComponent) targeted; - - if ( component.Addon != null ) - m_House.AddSecure( from, component.Addon ); - } - else - #endregion - - m_House.AddSecure( from, (Item)targeted ); - } - } - } - else - { - from.SendLocalizedMessage( 1010424 );//You cannot secure this - } - } - } - - public class HouseKickTarget : Target - { - private BaseHouse m_House; - - public HouseKickTarget( BaseHouse house ) : base( -1, false, TargetFlags.None ) - { - CheckLOS = false; - - m_House = house; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsFriend( from ) ) - return; - - if ( targeted is Mobile ) - { - m_House.Kick( from, (Mobile)targeted ); - } - else - { - from.SendLocalizedMessage( 501347 );//You cannot eject that from the house! - } - } - } - - public class HouseBanTarget : Target - { - private BaseHouse m_House; - private bool m_Banning; - - public HouseBanTarget( bool ban, BaseHouse house ) : base( -1, false, TargetFlags.None ) - { - CheckLOS = false; - - m_House = house; - m_Banning = ban; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsFriend( from ) ) - return; - - if ( targeted is Mobile ) - { - if ( m_Banning ) - m_House.Ban( from, (Mobile)targeted ); - else - m_House.RemoveBan( from, (Mobile)targeted ); - } - else - { - from.SendLocalizedMessage( 501347 );//You cannot eject that from the house! - } - } - } - - public class HouseAccessTarget : Target - { - private BaseHouse m_House; - - public HouseAccessTarget( BaseHouse house ) : base( -1, false, TargetFlags.None ) - { - CheckLOS = false; - - m_House = house; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsFriend( from ) ) - return; - - if ( targeted is Mobile ) - m_House.GrantAccess( from, (Mobile)targeted ); - else - from.SendLocalizedMessage( 1060712 ); // That is not a player. - } - } - - public class CoOwnerTarget : Target - { - private BaseHouse m_House; - private bool m_Add; - - public CoOwnerTarget( bool add, BaseHouse house ) : base( 12, false, TargetFlags.None ) - { - CheckLOS = false; - - m_House = house; - m_Add = add; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsOwner( from ) ) - return; - - if ( targeted is Mobile ) - { - if ( m_Add ) - m_House.AddCoOwner( from, (Mobile)targeted ); - else - m_House.RemoveCoOwner( from, (Mobile)targeted ); - } - else - { - from.SendLocalizedMessage( 501362 );//That can't be a coowner - } - } - } - - public class HouseFriendTarget : Target - { - private BaseHouse m_House; - private bool m_Add; - - public HouseFriendTarget( bool add, BaseHouse house ) : base( 12, false, TargetFlags.None ) - { - CheckLOS = false; - - m_House = house; - m_Add = add; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive || m_House.Deleted || !m_House.IsCoOwner( from ) ) - return; - - if ( targeted is Mobile ) - { - if ( m_Add ) - m_House.AddFriend( from, (Mobile)targeted ); - else - m_House.RemoveFriend( from, (Mobile)targeted ); - } - else - { - from.SendLocalizedMessage( 501371 ); // That can't be a friend - } - } - } - - public class HouseOwnerTarget : Target - { - private BaseHouse m_House; - - public HouseOwnerTarget( BaseHouse house ) : base( 12, false, TargetFlags.None ) - { - CheckLOS = false; - - m_House = house; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile ) - m_House.BeginConfirmTransfer( from, (Mobile)targeted ); - else - from.SendLocalizedMessage( 501384 ); // Only a player can own a house! - } - } - - #endregion - - public class SetSecureLevelEntry : ContextMenuEntry - { - private Item m_Item; - private ISecurable m_Securable; - - public SetSecureLevelEntry( Item item, ISecurable securable ) : base( 6203, 6 ) - { - m_Item = item; - m_Securable = securable; - } - - public static ISecurable GetSecurable( Mobile from, Item item ) - { - BaseHouse house = BaseHouse.FindHouseAt( item ); - - if ( house == null || !house.IsOwner( from ) || !house.IsAosRules ) - return null; - - ISecurable sec = null; - - if ( item is ISecurable ) - { - bool isOwned = house.Doors.Contains( item ); - - if ( !isOwned ) - isOwned = ( house is HouseFoundation && ((HouseFoundation)house).IsFixture( item ) ); - - if ( !isOwned ) - isOwned = house.IsLockedDown( item ); - - if ( isOwned ) - sec = (ISecurable)item; - } - else - { - ArrayList list = house.Secures; - - for ( int i = 0; sec == null && list != null && i < list.Count; ++i ) - { - SecureInfo si = (SecureInfo)list[i]; - - if ( si.Item == item ) - sec = si; - } - } - - return sec; - } - - public static void AddTo( Mobile from, Item item, List list ) - { - ISecurable sec = GetSecurable( from, item ); - - if ( sec != null ) - list.Add( new SetSecureLevelEntry( item, sec ) ); - } - - public override void OnClick() - { - ISecurable sec = GetSecurable( Owner.From, m_Item ); - - if ( sec != null ) - { - Owner.From.CloseGump( typeof ( SetSecureLevelGump ) ); - Owner.From.SendGump( new SetSecureLevelGump( Owner.From, sec, BaseHouse.FindHouseAt( m_Item ) ) ); - } - } - } - - public class TempNoHousingRegion : BaseRegion - { - private Mobile m_RegionOwner; - - public TempNoHousingRegion( BaseHouse house, Mobile regionowner ) - : base( null, house.Map, DefaultPriority, house.Region.Area ) - { - Register(); - - m_RegionOwner = regionowner; - - Timer.DelayCall( house.RestrictedPlacingTime, Unregister ); - } - - public override bool AllowHousing( Mobile from, Point3D p ) - { - return ( from == m_RegionOwner || AccountHandler.CheckAccount( from, m_RegionOwner ) ); - } - } -} + m_House.RemoveKeys(from); + m_House.Owner = to; + m_House.Bans.Clear(); + m_House.Friends.Clear(); + m_House.CoOwners.Clear(); + m_House.ChangeLocks(to); + m_House.LastTraded = DateTime.UtcNow; + } + } + + private class FixColumnTimer : Timer + { + private Map m_Map; + private int m_StartX, m_StartY, m_EndX, m_EndY; + + public FixColumnTimer(BaseMulti multi) : base(TimeSpan.Zero) + { + m_Map = multi.Map; + + MultiComponentList mcl = multi.Components; + + m_StartX = multi.X + mcl.Min.X; + m_StartY = multi.Y + mcl.Min.Y; + m_EndX = multi.X + mcl.Max.X; + m_EndY = multi.Y + mcl.Max.Y; + } + + protected override void OnTick() + { + if (m_Map == null) + return; + + for (int x = m_StartX; x <= m_EndX; ++x) + for (int y = m_StartY; y <= m_EndY; ++y) + m_Map.FixColumn(x, y); + } + } + + #region Dynamic decay system + + private DecayLevel m_CurrentStage; + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime NextDecayStage{ get; set; } + + public void ResetDynamicDecay() + { + m_CurrentStage = DecayLevel.Ageless; + NextDecayStage = DateTime.MinValue; + } + + public void SetDynamicDecay(DecayLevel level) + { + m_CurrentStage = level; + + if (DynamicDecay.Decays(level)) + NextDecayStage = DateTime.UtcNow + DynamicDecay.GetRandomDuration(level); + else + NextDecayStage = DateTime.MinValue; + } + + #endregion + } + + public enum DecayType + { + Ageless, + AutoRefresh, + ManualRefresh, + Condemned + } + + public enum DecayLevel + { + Ageless, + LikeNew, + Slightly, + Somewhat, + Fairly, + Greatly, + IDOC, + Collapsed, + DemolitionPending + } + + public enum SecureAccessResult + { + Insecure, + Accessible, + Inaccessible + } + + public enum SecureLevel + { + Owner, + CoOwners, + Friends, + Anyone, + Guild + } + + public class SecureInfo : ISecurable + { + public SecureInfo(Container item, SecureLevel level) + { + Item = item; + Level = level; + } + + public SecureInfo(GenericReader reader) + { + Item = reader.ReadItem() as Container; + Level = (SecureLevel)reader.ReadByte(); + } + + public Container Item{ get; } + + public SecureLevel Level{ get; set; } + + public void Serialize(GenericWriter writer) + { + writer.Write(Item); + writer.Write((byte)Level); + } + } + + public class RelocatedEntity + { + public RelocatedEntity(IEntity entity, Point3D relativeLocation) + { + Entity = entity; + RelativeLocation = relativeLocation; + } + + public IEntity Entity{ get; } + + public Point3D RelativeLocation{ get; } + } + + #region Targets + + public class LockdownTarget : Target + { + private BaseHouse m_House; + private bool m_Release; + + public LockdownTarget(bool release, BaseHouse house) : base(12, false, TargetFlags.None) + { + CheckLOS = false; + + m_Release = release; + m_House = house; + } + + protected override void OnTargetNotAccessible(Mobile from, object targeted) + { + OnTarget(from, targeted); + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsCoOwner(from)) + return; + + if (targeted is Item) + { + if (m_Release) + { + #region Mondain's legacy + + if (targeted is AddonContainerComponent) + { + AddonContainerComponent component = (AddonContainerComponent)targeted; + + if (component.Addon != null) + m_House.Release(from, component.Addon); + } + else + + #endregion + + { + m_House.Release(from, (Item)targeted); + } + } + else + { + if (targeted is VendorRentalContract) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1062392); // You must double click the contract in your pack to lock it down. + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501732); // I cannot lock this down! + } + else if ((Item)targeted is AddonComponent) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 501727); // You cannot lock that down! + from.LocalOverheadMessage(MessageType.Regular, 0x3E9, 501732); // I cannot lock this down! + } + else + { + #region Mondain's legacy + + if (targeted is AddonContainerComponent) + { + AddonContainerComponent component = (AddonContainerComponent)targeted; + + if (component.Addon != null) + m_House.LockDown(from, component.Addon); + } + else + + #endregion + + { + m_House.LockDown(from, (Item)targeted); + } + } + } + } + else if (targeted is StaticTarget) + { + } + else + { + from.SendLocalizedMessage(1005377); //You cannot lock that down + } + } + } + + public class SecureTarget : Target + { + private BaseHouse m_House; + private bool m_Release; + + public SecureTarget(bool release, BaseHouse house) : base(12, false, TargetFlags.None) + { + CheckLOS = false; + + m_Release = release; + m_House = house; + } + + protected override void OnTargetNotAccessible(Mobile from, object targeted) + { + OnTarget(from, targeted); + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsCoOwner(from)) + return; + + if (targeted is Item) + { + if (m_Release) + { + #region Mondain's legacy + + if (targeted is AddonContainerComponent) + { + AddonContainerComponent component = (AddonContainerComponent)targeted; + + if (component.Addon != null) + m_House.ReleaseSecure(from, component.Addon); + } + else + + #endregion + + { + m_House.ReleaseSecure(from, (Item)targeted); + } + } + else + { + if (targeted is VendorRentalContract) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1062392); // You must double click the contract in your pack to lock it down. + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501732); // I cannot lock this down! + } + else + { + #region Mondain's legacy + + if (targeted is AddonContainerComponent) + { + AddonContainerComponent component = (AddonContainerComponent)targeted; + + if (component.Addon != null) + m_House.AddSecure(from, component.Addon); + } + else + + #endregion + + { + m_House.AddSecure(from, (Item)targeted); + } + } + } + } + else + { + from.SendLocalizedMessage(1010424); //You cannot secure this + } + } + } + + public class HouseKickTarget : Target + { + private BaseHouse m_House; + + public HouseKickTarget(BaseHouse house) : base(-1, false, TargetFlags.None) + { + CheckLOS = false; + + m_House = house; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsFriend(from)) + return; + + if (targeted is Mobile) + m_House.Kick(from, (Mobile)targeted); + else + from.SendLocalizedMessage(501347); //You cannot eject that from the house! + } + } + + public class HouseBanTarget : Target + { + private bool m_Banning; + private BaseHouse m_House; + + public HouseBanTarget(bool ban, BaseHouse house) : base(-1, false, TargetFlags.None) + { + CheckLOS = false; + + m_House = house; + m_Banning = ban; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsFriend(from)) + return; + + if (targeted is Mobile) + { + if (m_Banning) + m_House.Ban(from, (Mobile)targeted); + else + m_House.RemoveBan(from, (Mobile)targeted); + } + else + { + from.SendLocalizedMessage(501347); //You cannot eject that from the house! + } + } + } + + public class HouseAccessTarget : Target + { + private BaseHouse m_House; + + public HouseAccessTarget(BaseHouse house) : base(-1, false, TargetFlags.None) + { + CheckLOS = false; + + m_House = house; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsFriend(from)) + return; + + if (targeted is Mobile) + m_House.GrantAccess(from, (Mobile)targeted); + else + from.SendLocalizedMessage(1060712); // That is not a player. + } + } + + public class CoOwnerTarget : Target + { + private bool m_Add; + private BaseHouse m_House; + + public CoOwnerTarget(bool add, BaseHouse house) : base(12, false, TargetFlags.None) + { + CheckLOS = false; + + m_House = house; + m_Add = add; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsOwner(from)) + return; + + if (targeted is Mobile) + { + if (m_Add) + m_House.AddCoOwner(from, (Mobile)targeted); + else + m_House.RemoveCoOwner(from, (Mobile)targeted); + } + else + { + from.SendLocalizedMessage(501362); //That can't be a coowner + } + } + } + + public class HouseFriendTarget : Target + { + private bool m_Add; + private BaseHouse m_House; + + public HouseFriendTarget(bool add, BaseHouse house) : base(12, false, TargetFlags.None) + { + CheckLOS = false; + + m_House = house; + m_Add = add; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive || m_House.Deleted || !m_House.IsCoOwner(from)) + return; + + if (targeted is Mobile) + { + if (m_Add) + m_House.AddFriend(from, (Mobile)targeted); + else + m_House.RemoveFriend(from, (Mobile)targeted); + } + else + { + from.SendLocalizedMessage(501371); // That can't be a friend + } + } + } + + public class HouseOwnerTarget : Target + { + private BaseHouse m_House; + + public HouseOwnerTarget(BaseHouse house) : base(12, false, TargetFlags.None) + { + CheckLOS = false; + + m_House = house; + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile) + m_House.BeginConfirmTransfer(from, (Mobile)targeted); + else + from.SendLocalizedMessage(501384); // Only a player can own a house! + } + } + + #endregion + + public class SetSecureLevelEntry : ContextMenuEntry + { + private Item m_Item; + private ISecurable m_Securable; + + public SetSecureLevelEntry(Item item, ISecurable securable) : base(6203, 6) + { + m_Item = item; + m_Securable = securable; + } + + public static ISecurable GetSecurable(Mobile from, Item item) + { + BaseHouse house = BaseHouse.FindHouseAt(item); + + if (house == null || !house.IsOwner(from) || !house.IsAosRules) + return null; + + ISecurable sec = null; + + if (item is ISecurable) + { + bool isOwned = house.Doors.Contains(item); + + if (!isOwned) + isOwned = house is HouseFoundation && ((HouseFoundation)house).IsFixture(item); + + if (!isOwned) + isOwned = house.IsLockedDown(item); + + if (isOwned) + sec = (ISecurable)item; + } + else + { + ArrayList list = house.Secures; + + for (int i = 0; sec == null && list != null && i < list.Count; ++i) + { + SecureInfo si = (SecureInfo)list[i]; + + if (si.Item == item) + sec = si; + } + } + + return sec; + } + + public static void AddTo(Mobile from, Item item, List list) + { + ISecurable sec = GetSecurable(from, item); + + if (sec != null) + list.Add(new SetSecureLevelEntry(item, sec)); + } + + public override void OnClick() + { + ISecurable sec = GetSecurable(Owner.From, m_Item); + + if (sec != null) + { + Owner.From.CloseGump(typeof(SetSecureLevelGump)); + Owner.From.SendGump(new SetSecureLevelGump(Owner.From, sec, BaseHouse.FindHouseAt(m_Item))); + } + } + } + + public class TempNoHousingRegion : BaseRegion + { + private Mobile m_RegionOwner; + + public TempNoHousingRegion(BaseHouse house, Mobile regionowner) + : base(null, house.Map, DefaultPriority, house.Region.Area) + { + Register(); + + m_RegionOwner = regionowner; + + Timer.DelayCall(house.RestrictedPlacingTime, Unregister); + } + + public override bool AllowHousing(Mobile from, Point3D p) + { + return from == m_RegionOwner || AccountHandler.CheckAccount(from, m_RegionOwner); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/BaseBoat.cs b/Scripts/Multis/Boats/BaseBoat.cs index ddf910260..473ebbfd5 100644 --- a/Scripts/Multis/Boats/BaseBoat.cs +++ b/Scripts/Multis/Boats/BaseBoat.cs @@ -1,1857 +1,1970 @@ using System; using System.Collections.Generic; +using System.IO; using Server.Items; using Server.Network; namespace Server.Multis { - public enum BoatOrder - { - Move, - Course, - Single - } + public enum BoatOrder + { + Move, + Course, + Single + } - public abstract class BaseBoat : BaseMulti - { - private static Rectangle2D[] m_BritWrap = { new Rectangle2D( 16, 16, 5120 - 32, 4096 - 32 ), new Rectangle2D( 5136, 2320, 992, 1760 ) }; - private static Rectangle2D[] m_IlshWrap = { new Rectangle2D( 16, 16, 2304 - 32, 1600 - 32 ) }; - private static Rectangle2D[] m_TokunoWrap = { new Rectangle2D( 16, 16, 1448 - 32, 1448 - 32 ) }; + public abstract class BaseBoat : BaseMulti + { + public enum DryDockResult + { + Valid, + Dead, + NoKey, + NotAnchored, + Mobiles, + Items, + Hold, + Decaying + } - private static TimeSpan BoatDecayDelay = TimeSpan.FromDays( 9.0 ); + private static Rectangle2D[] m_BritWrap = + { new Rectangle2D(16, 16, 5120 - 32, 4096 - 32), new Rectangle2D(5136, 2320, 992, 1760) }; - public static BaseBoat FindBoatAt( IPoint2D loc, Map map ) - { - Sector sector = map.GetSector( loc ); + private static Rectangle2D[] m_IlshWrap = { new Rectangle2D(16, 16, 2304 - 32, 1600 - 32) }; + private static Rectangle2D[] m_TokunoWrap = { new Rectangle2D(16, 16, 1448 - 32, 1448 - 32) }; - for ( int i = 0; i < sector.Multis.Count; i++ ) - { - BaseBoat boat = sector.Multis[i] as BaseBoat; + private static TimeSpan BoatDecayDelay = TimeSpan.FromDays(9.0); - if ( boat != null && boat.Contains( loc.X, loc.Y ) ) - return boat; - } + private static TimeSpan SlowInterval = TimeSpan.FromSeconds(NewBoatMovement ? 0.50 : 0.75); + private static TimeSpan FastInterval = TimeSpan.FromSeconds(NewBoatMovement ? 0.25 : 0.75); - return null; - } + private static int SlowSpeed = 1; + private static int FastSpeed = NewBoatMovement ? 1 : 3; - private Direction m_Facing; + private static TimeSpan SlowDriftInterval = TimeSpan.FromSeconds(NewBoatMovement ? 0.50 : 1.50); + private static TimeSpan FastDriftInterval = TimeSpan.FromSeconds(NewBoatMovement ? 0.25 : 0.75); - private int m_ClientSpeed; + private static int SlowDriftSpeed = 1; + private static int FastDriftSpeed = 1; - private string m_ShipName; + private static Direction Forward = Direction.North; + private static Direction ForwardLeft = Direction.Up; + private static Direction ForwardRight = Direction.Right; + private static Direction Backward = Direction.South; + private static Direction BackwardLeft = Direction.Left; + private static Direction BackwardRight = Direction.Down; + private static Direction Left = Direction.West; + private static Direction Right = Direction.East; + private static Direction Port = Left; + private static Direction Starboard = Right; - private DateTime m_DecayTime; + private int m_ClientSpeed; - private Timer m_TurnTimer; - private Timer m_MoveTimer; + private bool m_Decaying; - [CommandProperty( AccessLevel.GameMaster )] - public Hold Hold { get; set; } + private DateTime m_DecayTime; - [CommandProperty( AccessLevel.GameMaster )] - public TillerMan TillerMan { get; set; } + private Direction m_Facing; + private Timer m_MoveTimer; - [CommandProperty( AccessLevel.GameMaster )] - public Plank PPlank { get; set; } + private string m_ShipName; - [CommandProperty( AccessLevel.GameMaster )] - public Plank SPlank { get; set; } + private Timer m_TurnTimer; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile Owner { get; set; } + public BaseBoat() : base(0x0) + { + m_DecayTime = DateTime.UtcNow + BoatDecayDelay; - [CommandProperty( AccessLevel.GameMaster )] - public Direction Facing{ get => m_Facing; - set => SetFacing( value ); - } + TillerMan = new TillerMan(this); + Hold = new Hold(this); - [CommandProperty( AccessLevel.GameMaster )] - public Direction Moving { get; set; } + PPlank = new Plank(this, PlankSide.Port, 0); + SPlank = new Plank(this, PlankSide.Starboard, 0); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsMoving => ( m_MoveTimer != null ); + PPlank.MoveToWorld(new Point3D(X + PortOffset.X, Y + PortOffset.Y, Z), Map); + SPlank.MoveToWorld(new Point3D(X + StarboardOffset.X, Y + StarboardOffset.Y, Z), Map); - [CommandProperty( AccessLevel.GameMaster )] - public int Speed { get; set; } + Facing = Direction.North; - [CommandProperty( AccessLevel.GameMaster )] - public bool Anchored { get; set; } + NextNavPoint = -1; - [CommandProperty( AccessLevel.GameMaster )] - public string ShipName{ get => m_ShipName; - set{ m_ShipName = value; - TillerMan?.InvalidateProperties(); - } } + Movable = false; - [CommandProperty( AccessLevel.GameMaster )] - public BoatOrder Order { get; set; } + Boats.Add(this); + } - [CommandProperty( AccessLevel.GameMaster )] - public MapItem MapItem { get; set; } + public BaseBoat(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int NextNavPoint { get; set; } + [CommandProperty(AccessLevel.GameMaster)] + public Hold Hold{ get; set; } - [CommandProperty( AccessLevel.GameMaster )] - public DateTime TimeOfDecay{ get => m_DecayTime; - set{ m_DecayTime = value; - TillerMan?.InvalidateProperties(); - } } + [CommandProperty(AccessLevel.GameMaster)] + public TillerMan TillerMan{ get; set; } - public int Status - { - get - { - DateTime start = TimeOfDecay - BoatDecayDelay; + [CommandProperty(AccessLevel.GameMaster)] + public Plank PPlank{ get; set; } - if ( DateTime.UtcNow - start < TimeSpan.FromHours( 1.0 ) ) - return 1043010; // This structure is like new. + [CommandProperty(AccessLevel.GameMaster)] + public Plank SPlank{ get; set; } - if ( DateTime.UtcNow - start < TimeSpan.FromDays( 2.0 ) ) - return 1043011; // This structure is slightly worn. + [CommandProperty(AccessLevel.GameMaster)] + public Mobile Owner{ get; set; } - if ( DateTime.UtcNow - start < TimeSpan.FromDays( 3.0 ) ) - return 1043012; // This structure is somewhat worn. + [CommandProperty(AccessLevel.GameMaster)] + public Direction Facing + { + get => m_Facing; + set => SetFacing(value); + } - if ( DateTime.UtcNow - start < TimeSpan.FromDays( 4.0 ) ) - return 1043013; // This structure is fairly worn. + [CommandProperty(AccessLevel.GameMaster)] + public Direction Moving{ get; set; } - if ( DateTime.UtcNow - start < TimeSpan.FromDays( 5.0 ) ) - return 1043014; // This structure is greatly worn. + [CommandProperty(AccessLevel.GameMaster)] + public bool IsMoving => m_MoveTimer != null; - return 1043015; // This structure is in danger of collapsing. - } - } + [CommandProperty(AccessLevel.GameMaster)] + public int Speed{ get; set; } - public virtual int NorthID => 0; - public virtual int EastID => 0; - public virtual int SouthID => 0; - public virtual int WestID => 0; + [CommandProperty(AccessLevel.GameMaster)] + public bool Anchored{ get; set; } - public virtual int HoldDistance => 0; - public virtual int TillerManDistance => 0; - public virtual Point2D StarboardOffset => Point2D.Zero; - public virtual Point2D PortOffset => Point2D.Zero; - public virtual Point3D MarkOffset => Point3D.Zero; + [CommandProperty(AccessLevel.GameMaster)] + public string ShipName + { + get => m_ShipName; + set + { + m_ShipName = value; + TillerMan?.InvalidateProperties(); + } + } - public virtual BaseDockedBoat DockedBoat => null; + [CommandProperty(AccessLevel.GameMaster)] + public BoatOrder Order{ get; set; } - public static List Boats { get; } = new List(); + [CommandProperty(AccessLevel.GameMaster)] + public MapItem MapItem{ get; set; } - public BaseBoat() : base( 0x0 ) - { - m_DecayTime = DateTime.UtcNow + BoatDecayDelay; + [CommandProperty(AccessLevel.GameMaster)] + public int NextNavPoint{ get; set; } - TillerMan = new TillerMan( this ); - Hold = new Hold( this ); + [CommandProperty(AccessLevel.GameMaster)] + public DateTime TimeOfDecay + { + get => m_DecayTime; + set + { + m_DecayTime = value; + TillerMan?.InvalidateProperties(); + } + } - PPlank = new Plank( this, PlankSide.Port, 0 ); - SPlank = new Plank( this, PlankSide.Starboard, 0 ); + public int Status + { + get + { + DateTime start = TimeOfDecay - BoatDecayDelay; + + if (DateTime.UtcNow - start < TimeSpan.FromHours(1.0)) + return 1043010; // This structure is like new. + + if (DateTime.UtcNow - start < TimeSpan.FromDays(2.0)) + return 1043011; // This structure is slightly worn. + + if (DateTime.UtcNow - start < TimeSpan.FromDays(3.0)) + return 1043012; // This structure is somewhat worn. + + if (DateTime.UtcNow - start < TimeSpan.FromDays(4.0)) + return 1043013; // This structure is fairly worn. + + if (DateTime.UtcNow - start < TimeSpan.FromDays(5.0)) + return 1043014; // This structure is greatly worn. + + return 1043015; // This structure is in danger of collapsing. + } + } + + public virtual int NorthID => 0; + public virtual int EastID => 0; + public virtual int SouthID => 0; + public virtual int WestID => 0; + + public virtual int HoldDistance => 0; + public virtual int TillerManDistance => 0; + public virtual Point2D StarboardOffset => Point2D.Zero; + public virtual Point2D PortOffset => Point2D.Zero; + public virtual Point3D MarkOffset => Point3D.Zero; + + public virtual BaseDockedBoat DockedBoat => null; + + public static List Boats{ get; } = new List(); + + /* + * Intervals: + * drift forward + * fast | 0.25| 0.25 + * slow | 0.50| 0.50 + * + * Speed: + * drift forward + * fast | 0x4| 0x4 + * slow | 0x3| 0x3 + * + * Tiles (per interval): + * drift forward + * fast | 1| 1 + * slow | 1| 1 + * + * 'walking' in piloting mode has a 1s interval, speed 0x2 + */ + + private static bool NewBoatMovement => Core.HS; + + public override bool HandlesOnSpeech => true; + + public static BaseBoat FindBoatAt(IPoint2D loc, Map map) + { + Sector sector = map.GetSector(loc); + + for (int i = 0; i < sector.Multis.Count; i++) + { + BaseBoat boat = sector.Multis[i] as BaseBoat; + + if (boat != null && boat.Contains(loc.X, loc.Y)) + return boat; + } + + return null; + } + + public Point3D GetRotatedLocation(int x, int y) + { + Point3D p = new Point3D(X + x, Y + y, Z); + + return Rotate(p, (int)m_Facing / 2); + } + + public void UpdateComponents() + { + if (PPlank != null) + { + PPlank.MoveToWorld(GetRotatedLocation(PortOffset.X, PortOffset.Y), Map); + PPlank.SetFacing(m_Facing); + } + + if (SPlank != null) + { + SPlank.MoveToWorld(GetRotatedLocation(StarboardOffset.X, StarboardOffset.Y), Map); + SPlank.SetFacing(m_Facing); + } + + int xOffset = 0, yOffset = 0; + Movement.Movement.Offset(m_Facing, ref xOffset, ref yOffset); + + if (TillerMan != null) + { + TillerMan.Location = new Point3D(X + xOffset * TillerManDistance + (m_Facing == Direction.North ? 1 : 0), + Y + yOffset * TillerManDistance, TillerMan.Z); + TillerMan.SetFacing(m_Facing); + TillerMan.InvalidateProperties(); + } + + if (Hold != null) + { + Hold.Location = new Point3D(X + xOffset * HoldDistance, Y + yOffset * HoldDistance, Hold.Z); + Hold.SetFacing(m_Facing); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(3); + + writer.Write(MapItem); + writer.Write(NextNavPoint); + + writer.Write((int)m_Facing); + + writer.WriteDeltaTime(m_DecayTime); + + writer.Write(Owner); + writer.Write(PPlank); + writer.Write(SPlank); + writer.Write(TillerMan); + writer.Write(Hold); + writer.Write(Anchored); + writer.Write(m_ShipName); + + CheckDecay(); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + { + MapItem = (MapItem)reader.ReadItem(); + NextNavPoint = reader.ReadInt(); + + goto case 2; + } + case 2: + { + m_Facing = (Direction)reader.ReadInt(); + + goto case 1; + } + case 1: + { + m_DecayTime = reader.ReadDeltaTime(); + + goto case 0; + } + case 0: + { + if (version < 3) + NextNavPoint = -1; + + if (version < 2) + { + if (ItemID == NorthID) + m_Facing = Direction.North; + else if (ItemID == SouthID) + m_Facing = Direction.South; + else if (ItemID == EastID) + m_Facing = Direction.East; + else if (ItemID == WestID) + m_Facing = Direction.West; + } + + Owner = reader.ReadMobile(); + PPlank = reader.ReadItem() as Plank; + SPlank = reader.ReadItem() as Plank; + TillerMan = reader.ReadItem() as TillerMan; + Hold = reader.ReadItem() as Hold; + Anchored = reader.ReadBool(); + m_ShipName = reader.ReadString(); - PPlank.MoveToWorld( new Point3D( X + PortOffset.X, Y + PortOffset.Y, Z ), Map ); - SPlank.MoveToWorld( new Point3D( X + StarboardOffset.X, Y + StarboardOffset.Y, Z ), Map ); + if (version < 1) + Refresh(); + + break; + } + } + + Boats.Add(this); + } + + public void RemoveKeys(Mobile m) + { + uint keyValue = 0; - Facing = Direction.North; + if (PPlank != null) + keyValue = PPlank.KeyValue; - NextNavPoint = -1; + if (keyValue == 0 && SPlank != null) + keyValue = SPlank.KeyValue; - Movable = false; + Key.RemoveKeys(m, keyValue); + } - Boats.Add( this ); - } + public uint CreateKeys(Mobile m) + { + uint value = Key.RandomValue(); - public BaseBoat( Serial serial ) : base( serial ) - { - } + Key packKey = new Key(KeyType.Gold, value, this); + Key bankKey = new Key(KeyType.Gold, value, this); - public Point3D GetRotatedLocation( int x, int y ) - { - Point3D p = new Point3D( X + x, Y + y, Z ); - - return Rotate( p, (int)m_Facing / 2 ); - } - - public void UpdateComponents() - { - if ( PPlank != null ) - { - PPlank.MoveToWorld( GetRotatedLocation( PortOffset.X, PortOffset.Y ), Map ); - PPlank.SetFacing( m_Facing ); - } - - if ( SPlank != null ) - { - SPlank.MoveToWorld( GetRotatedLocation( StarboardOffset.X, StarboardOffset.Y ), Map ); - SPlank.SetFacing( m_Facing ); - } - - int xOffset = 0, yOffset = 0; - Movement.Movement.Offset( m_Facing, ref xOffset, ref yOffset ); - - if ( TillerMan != null ) - { - TillerMan.Location = new Point3D( X + (xOffset * TillerManDistance) + (m_Facing == Direction.North ? 1 : 0), Y + (yOffset * TillerManDistance), TillerMan.Z ); - TillerMan.SetFacing( m_Facing ); - TillerMan.InvalidateProperties(); - } - - if ( Hold != null ) - { - Hold.Location = new Point3D( X + (xOffset * HoldDistance), Y + (yOffset * HoldDistance), Hold.Z ); - Hold.SetFacing( m_Facing ); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 3 ); - - writer.Write( (Item) MapItem ); - writer.Write( (int) NextNavPoint ); - - writer.Write( (int) m_Facing ); - - writer.WriteDeltaTime( m_DecayTime ); - - writer.Write( Owner ); - writer.Write( PPlank ); - writer.Write( SPlank ); - writer.Write( TillerMan ); - writer.Write( Hold ); - writer.Write( Anchored ); - writer.Write( m_ShipName ); - - CheckDecay(); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 3: - { - MapItem = (MapItem) reader.ReadItem(); - NextNavPoint = reader.ReadInt(); + packKey.MaxRange = 10; + bankKey.MaxRange = 10; - goto case 2; - } - case 2: - { - m_Facing = (Direction)reader.ReadInt(); + packKey.Name = "a ship key"; + bankKey.Name = "a ship key"; - goto case 1; - } - case 1: - { - m_DecayTime = reader.ReadDeltaTime(); + BankBox box = m.BankBox; - goto case 0; - } - case 0: - { - if ( version < 3 ) - NextNavPoint = -1; - - if ( version < 2 ) - { - if ( ItemID == NorthID ) - m_Facing = Direction.North; - else if ( ItemID == SouthID ) - m_Facing = Direction.South; - else if ( ItemID == EastID ) - m_Facing = Direction.East; - else if ( ItemID == WestID ) - m_Facing = Direction.West; - } - - Owner = reader.ReadMobile(); - PPlank = reader.ReadItem() as Plank; - SPlank = reader.ReadItem() as Plank; - TillerMan = reader.ReadItem() as TillerMan; - Hold = reader.ReadItem() as Hold; - Anchored = reader.ReadBool(); - m_ShipName = reader.ReadString(); + if (!box.TryDropItem(m, bankKey, false)) + bankKey.Delete(); + else + m.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502484); // A ship's key is now in my safety deposit box. - if ( version < 1) - Refresh(); + if (m.AddToBackpack(packKey)) + m.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502485); // A ship's key is now in my backpack. + else + m.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502483); // A ship's key is now at my feet. - break; - } - } + return value; + } - Boats.Add( this ); - } + public override void OnAfterDelete() + { + TillerMan?.Delete(); - public void RemoveKeys( Mobile m ) - { - uint keyValue = 0; + Hold?.Delete(); - if ( PPlank != null ) - keyValue = PPlank.KeyValue; + PPlank?.Delete(); - if ( keyValue == 0 && SPlank != null ) - keyValue = SPlank.KeyValue; + SPlank?.Delete(); - Key.RemoveKeys( m, keyValue ); - } + m_TurnTimer?.Stop(); - public uint CreateKeys( Mobile m ) - { - uint value = Key.RandomValue(); + m_MoveTimer?.Stop(); - Key packKey = new Key( KeyType.Gold, value, this ); - Key bankKey = new Key( KeyType.Gold, value, this ); + Boats.Remove(this); + } - packKey.MaxRange = 10; - bankKey.MaxRange = 10; - - packKey.Name = "a ship key"; - bankKey.Name = "a ship key"; - - BankBox box = m.BankBox; - - if ( !box.TryDropItem( m, bankKey, false ) ) - bankKey.Delete(); - else - m.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502484 ); // A ship's key is now in my safety deposit box. - - if ( m.AddToBackpack( packKey ) ) - m.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502485 ); // A ship's key is now in my backpack. - else - m.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502483 ); // A ship's key is now at my feet. - - return value; - } - - public override void OnAfterDelete() - { - TillerMan?.Delete(); - - Hold?.Delete(); - - PPlank?.Delete(); - - SPlank?.Delete(); - - m_TurnTimer?.Stop(); - - m_MoveTimer?.Stop(); - - Boats.Remove( this ); - } - - public override void OnLocationChange( Point3D old ) - { - if ( TillerMan != null ) - TillerMan.Location = new Point3D( X + (TillerMan.X - old.X), Y + (TillerMan.Y - old.Y), Z + (TillerMan.Z - old.Z ) ); - - if ( Hold != null ) - Hold.Location = new Point3D( X + (Hold.X - old.X), Y + (Hold.Y - old.Y), Z + (Hold.Z - old.Z ) ); - - if ( PPlank != null ) - PPlank.Location = new Point3D( X + (PPlank.X - old.X), Y + (PPlank.Y - old.Y), Z + (PPlank.Z - old.Z ) ); + public override void OnLocationChange(Point3D old) + { + if (TillerMan != null) + TillerMan.Location = new Point3D(X + (TillerMan.X - old.X), Y + (TillerMan.Y - old.Y), + Z + (TillerMan.Z - old.Z)); - if ( SPlank != null ) - SPlank.Location = new Point3D( X + (SPlank.X - old.X), Y + (SPlank.Y - old.Y), Z + (SPlank.Z - old.Z ) ); - } + if (Hold != null) + Hold.Location = new Point3D(X + (Hold.X - old.X), Y + (Hold.Y - old.Y), Z + (Hold.Z - old.Z)); - public override void OnMapChange() - { - if ( TillerMan != null ) - TillerMan.Map = Map; + if (PPlank != null) + PPlank.Location = new Point3D(X + (PPlank.X - old.X), Y + (PPlank.Y - old.Y), Z + (PPlank.Z - old.Z)); - if ( Hold != null ) - Hold.Map = Map; + if (SPlank != null) + SPlank.Location = new Point3D(X + (SPlank.X - old.X), Y + (SPlank.Y - old.Y), Z + (SPlank.Z - old.Z)); + } - if ( PPlank != null ) - PPlank.Map = Map; + public override void OnMapChange() + { + if (TillerMan != null) + TillerMan.Map = Map; - if ( SPlank != null ) - SPlank.Map = Map; - } + if (Hold != null) + Hold.Map = Map; - public bool CanCommand( Mobile m ) - { - return true; - } + if (PPlank != null) + PPlank.Map = Map; - public Point3D GetMarkedLocation() - { - Point3D p = new Point3D( X + MarkOffset.X, Y + MarkOffset.Y, Z + MarkOffset.Z ); + if (SPlank != null) + SPlank.Map = Map; + } - return Rotate( p, (int)m_Facing / 2 ); - } + public bool CanCommand(Mobile m) + { + return true; + } - public bool CheckKey( uint keyValue ) - { - if ( SPlank != null && SPlank.KeyValue == keyValue ) - return true; + public Point3D GetMarkedLocation() + { + Point3D p = new Point3D(X + MarkOffset.X, Y + MarkOffset.Y, Z + MarkOffset.Z); - if ( PPlank != null && PPlank.KeyValue == keyValue ) - return true; + return Rotate(p, (int)m_Facing / 2); + } - return false; - } + public bool CheckKey(uint keyValue) + { + if (SPlank != null && SPlank.KeyValue == keyValue) + return true; - /* - * Intervals: - * drift forward - * fast | 0.25| 0.25 - * slow | 0.50| 0.50 - * - * Speed: - * drift forward - * fast | 0x4| 0x4 - * slow | 0x3| 0x3 - * - * Tiles (per interval): - * drift forward - * fast | 1| 1 - * slow | 1| 1 - * - * 'walking' in piloting mode has a 1s interval, speed 0x2 - */ + if (PPlank != null && PPlank.KeyValue == keyValue) + return true; - private static bool NewBoatMovement => Core.HS; + return false; + } - private static TimeSpan SlowInterval = TimeSpan.FromSeconds( NewBoatMovement ? 0.50 : 0.75 ); - private static TimeSpan FastInterval = TimeSpan.FromSeconds( NewBoatMovement ? 0.25 : 0.75 ); + public void Refresh() + { + m_DecayTime = DateTime.UtcNow + BoatDecayDelay; - private static int SlowSpeed = 1; - private static int FastSpeed = NewBoatMovement ? 1 : 3; + TillerMan?.InvalidateProperties(); + } - private static TimeSpan SlowDriftInterval = TimeSpan.FromSeconds( NewBoatMovement ? 0.50 : 1.50 ); - private static TimeSpan FastDriftInterval = TimeSpan.FromSeconds( NewBoatMovement ? 0.25 : 0.75 ); + public bool CheckDecay() + { + if (m_Decaying) + return true; - private static int SlowDriftSpeed = 1; - private static int FastDriftSpeed = 1; + if (!IsMoving && DateTime.UtcNow >= m_DecayTime) + { + new DecayTimer(this).Start(); - private static Direction Forward = Direction.North; - private static Direction ForwardLeft = Direction.Up; - private static Direction ForwardRight = Direction.Right; - private static Direction Backward = Direction.South; - private static Direction BackwardLeft = Direction.Left; - private static Direction BackwardRight = Direction.Down; - private static Direction Left = Direction.West; - private static Direction Right = Direction.East; - private static Direction Port = Left; - private static Direction Starboard = Right; + m_Decaying = true; - private bool m_Decaying; - - public void Refresh() - { - m_DecayTime = DateTime.UtcNow + BoatDecayDelay; - - TillerMan?.InvalidateProperties(); - } - - private class DecayTimer : Timer - { - private BaseBoat m_Boat; - private int m_Count; - - public DecayTimer( BaseBoat boat ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_Boat = boat; - - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - if ( m_Count == 5 ) - { - m_Boat.Delete(); - Stop(); - } - else - { - m_Boat.Location = new Point3D( m_Boat.X, m_Boat.Y, m_Boat.Z - 1 ); - - m_Boat.TillerMan?.Say( 1007168 + m_Count ); - - ++m_Count; - } - } - } - - public bool CheckDecay() - { - if ( m_Decaying ) - return true; - - if ( !IsMoving && DateTime.UtcNow >= m_DecayTime ) - { - new DecayTimer( this ).Start(); - - m_Decaying = true; - - return true; - } + return true; + } - return false; - } + return false; + } - public bool LowerAnchor( bool message ) - { - if ( CheckDecay() ) - return false; + public bool LowerAnchor(bool message) + { + if (CheckDecay()) + return false; - if ( Anchored ) - { - if ( message ) - TillerMan?.Say( 501445 ); // Ar, the anchor was already dropped sir. + if (Anchored) + { + if (message) + TillerMan?.Say(501445); // Ar, the anchor was already dropped sir. - return false; - } + return false; + } - StopMove( false ); + StopMove(false); - Anchored = true; + Anchored = true; - if ( message ) - TillerMan?.Say( 501444 ); // Ar, anchor dropped sir. + if (message) + TillerMan?.Say(501444); // Ar, anchor dropped sir. - return true; - } + return true; + } - public bool RaiseAnchor( bool message ) - { - if ( CheckDecay() ) - return false; + public bool RaiseAnchor(bool message) + { + if (CheckDecay()) + return false; - if ( !Anchored ) - { - if ( message ) - TillerMan?.Say( 501447 ); // Ar, the anchor has not been dropped sir. + if (!Anchored) + { + if (message) + TillerMan?.Say(501447); // Ar, the anchor has not been dropped sir. - return false; - } + return false; + } - Anchored = false; + Anchored = false; - if ( message ) - TillerMan?.Say( 501446 ); // Ar, anchor raised sir. + if (message) + TillerMan?.Say(501446); // Ar, anchor raised sir. - return true; - } + return true; + } - public bool StartMove( Direction dir, bool fast ) - { - if ( CheckDecay() ) - return false; + public bool StartMove(Direction dir, bool fast) + { + if (CheckDecay()) + return false; - bool drift = ( dir != Forward && dir != ForwardLeft && dir != ForwardRight ); - TimeSpan interval = (fast ? (drift ? FastDriftInterval : FastInterval) : (drift ? SlowDriftInterval : SlowInterval)); - int speed = (fast ? (drift ? FastDriftSpeed : FastSpeed) : (drift ? SlowDriftSpeed : SlowSpeed)); - int clientSpeed = fast ? 0x4 : 0x3; + bool drift = dir != Forward && dir != ForwardLeft && dir != ForwardRight; + TimeSpan interval = fast ? drift ? FastDriftInterval : FastInterval : drift ? SlowDriftInterval : SlowInterval; + int speed = fast ? drift ? FastDriftSpeed : FastSpeed : drift ? SlowDriftSpeed : SlowSpeed; + int clientSpeed = fast ? 0x4 : 0x3; - if ( StartMove( dir, speed, clientSpeed, interval, false, true ) ) - { - TillerMan?.Say( 501429 ); // Aye aye sir. + if (StartMove(dir, speed, clientSpeed, interval, false, true)) + { + TillerMan?.Say(501429); // Aye aye sir. - return true; - } + return true; + } - return false; - } + return false; + } - public bool OneMove( Direction dir ) - { - if ( CheckDecay() ) - return false; + public bool OneMove(Direction dir) + { + if (CheckDecay()) + return false; - bool drift = ( dir != Forward ); - TimeSpan interval = drift ? FastDriftInterval : FastInterval; - int speed = drift ? FastDriftSpeed : FastSpeed; + bool drift = dir != Forward; + TimeSpan interval = drift ? FastDriftInterval : FastInterval; + int speed = drift ? FastDriftSpeed : FastSpeed; - if ( StartMove( dir, speed, 0x1, interval, true, true ) ) - { - TillerMan?.Say( 501429 ); // Aye aye sir. + if (StartMove(dir, speed, 0x1, interval, true, true)) + { + TillerMan?.Say(501429); // Aye aye sir. - return true; - } + return true; + } - return false; - } + return false; + } - public void BeginRename( Mobile from ) - { - if ( CheckDecay() ) - return; + public void BeginRename(Mobile from) + { + if (CheckDecay()) + return; - if ( from.AccessLevel < AccessLevel.GameMaster && from != Owner ) - { - TillerMan?.Say( Utility.Random( 1042876, 4 ) ); // Arr, don't do that! | Arr, leave me alone! | Arr, watch what thour'rt doing, matey! | Arr! Do that again and I’ll throw ye overhead! + if (from.AccessLevel < AccessLevel.GameMaster && from != Owner) + { + TillerMan?.Say(Utility.Random(1042876, + 4)); // Arr, don't do that! | Arr, leave me alone! | Arr, watch what thour'rt doing, matey! | Arr! Do that again and I’ll throw ye overhead! - return; - } + return; + } - TillerMan?.Say( 502580 ); // What dost thou wish to name thy ship? + TillerMan?.Say(502580); // What dost thou wish to name thy ship? - from.Prompt = new RenameBoatPrompt( this ); - } + from.Prompt = new RenameBoatPrompt(this); + } - public void EndRename( Mobile from, string newName ) - { - if ( Deleted || CheckDecay() ) - return; + public void EndRename(Mobile from, string newName) + { + if (Deleted || CheckDecay()) + return; - if ( from.AccessLevel < AccessLevel.GameMaster && from != Owner ) - { - TillerMan?.Say( 1042880 ); // Arr! Only the owner of the ship may change its name! + if (from.AccessLevel < AccessLevel.GameMaster && from != Owner) + { + TillerMan?.Say(1042880); // Arr! Only the owner of the ship may change its name! - return; - } + return; + } - if ( !from.Alive ) - { - TillerMan?.Say( 502582 ); // You appear to be dead. + if (!from.Alive) + { + TillerMan?.Say(502582); // You appear to be dead. - return; - } + return; + } - newName = newName.Trim(); + newName = newName.Trim(); - if ( newName.Length == 0 ) - newName = null; + if (newName.Length == 0) + newName = null; - Rename( newName ); - } + Rename(newName); + } - public enum DryDockResult{ Valid, Dead, NoKey, NotAnchored, Mobiles, Items, Hold, Decaying } + public DryDockResult CheckDryDock(Mobile from) + { + if (CheckDecay()) + return DryDockResult.Decaying; - public DryDockResult CheckDryDock( Mobile from ) - { - if ( CheckDecay() ) - return DryDockResult.Decaying; + if (!from.Alive) + return DryDockResult.Dead; - if ( !from.Alive ) - return DryDockResult.Dead; + Container pack = from.Backpack; + if ((SPlank == null || !Key.ContainsKey(pack, SPlank.KeyValue)) && + (PPlank == null || !Key.ContainsKey(pack, PPlank.KeyValue))) + return DryDockResult.NoKey; - Container pack = from.Backpack; - if ( (SPlank == null || !Key.ContainsKey( pack, SPlank.KeyValue )) && (PPlank == null || !Key.ContainsKey( pack, PPlank.KeyValue )) ) - return DryDockResult.NoKey; + if (!Anchored) + return DryDockResult.NotAnchored; - if ( !Anchored ) - return DryDockResult.NotAnchored; + if (Hold != null && Hold.Items.Count > 0) + return DryDockResult.Hold; - if ( Hold != null && Hold.Items.Count > 0 ) - return DryDockResult.Hold; + Map map = Map; - Map map = Map; + if (map == null || map == Map.Internal) + return DryDockResult.Items; - if ( map == null || map == Map.Internal ) - return DryDockResult.Items; + List ents = GetMovingEntities(); - List ents = GetMovingEntities(); + if (ents.Count >= 1) + return ents[0] is Mobile ? DryDockResult.Mobiles : DryDockResult.Items; - if ( ents.Count >= 1 ) - return ( ents[0] is Mobile ) ? DryDockResult.Mobiles : DryDockResult.Items; + return DryDockResult.Valid; + } - return DryDockResult.Valid; - } + public void BeginDryDock(Mobile from) + { + if (CheckDecay()) + return; - public void BeginDryDock( Mobile from ) - { - if ( CheckDecay() ) - return; + DryDockResult result = CheckDryDock(from); - DryDockResult result = CheckDryDock( from ); + if (result == DryDockResult.Dead) + from.SendLocalizedMessage(502493); // You appear to be dead. + else if (result == DryDockResult.NoKey) + from.SendLocalizedMessage(502494); // You must have a key to the ship to dock the boat. + else if (result == DryDockResult.NotAnchored) + from.SendLocalizedMessage(1010570); // You must lower the anchor to dock the boat. + else if (result == DryDockResult.Mobiles) + from.SendLocalizedMessage(502495); // You cannot dock the ship with beings on board! + else if (result == DryDockResult.Items) + from.SendLocalizedMessage(502496); // You cannot dock the ship with a cluttered deck. + else if (result == DryDockResult.Hold) + from.SendLocalizedMessage(502497); // Make sure your hold is empty, and try again! + else if (result == DryDockResult.Valid) + from.SendGump(new ConfirmDryDockGump(from, this)); + } - if ( result == DryDockResult.Dead ) - from.SendLocalizedMessage( 502493 ); // You appear to be dead. - else if ( result == DryDockResult.NoKey ) - from.SendLocalizedMessage( 502494 ); // You must have a key to the ship to dock the boat. - else if ( result == DryDockResult.NotAnchored ) - from.SendLocalizedMessage( 1010570 ); // You must lower the anchor to dock the boat. - else if ( result == DryDockResult.Mobiles ) - from.SendLocalizedMessage( 502495 ); // You cannot dock the ship with beings on board! - else if ( result == DryDockResult.Items ) - from.SendLocalizedMessage( 502496 ); // You cannot dock the ship with a cluttered deck. - else if ( result == DryDockResult.Hold ) - from.SendLocalizedMessage( 502497 ); // Make sure your hold is empty, and try again! - else if ( result == DryDockResult.Valid ) - from.SendGump( new ConfirmDryDockGump( from, this ) ); - } + public void EndDryDock(Mobile from) + { + if (Deleted || CheckDecay()) + return; - public void EndDryDock( Mobile from ) - { - if ( Deleted || CheckDecay() ) - return; + DryDockResult result = CheckDryDock(from); - DryDockResult result = CheckDryDock( from ); + if (result == DryDockResult.Dead) + from.SendLocalizedMessage(502493); // You appear to be dead. + else if (result == DryDockResult.NoKey) + from.SendLocalizedMessage(502494); // You must have a key to the ship to dock the boat. + else if (result == DryDockResult.NotAnchored) + from.SendLocalizedMessage(1010570); // You must lower the anchor to dock the boat. + else if (result == DryDockResult.Mobiles) + from.SendLocalizedMessage(502495); // You cannot dock the ship with beings on board! + else if (result == DryDockResult.Items) + from.SendLocalizedMessage(502496); // You cannot dock the ship with a cluttered deck. + else if (result == DryDockResult.Hold) + from.SendLocalizedMessage(502497); // Make sure your hold is empty, and try again! - if ( result == DryDockResult.Dead ) - from.SendLocalizedMessage( 502493 ); // You appear to be dead. - else if ( result == DryDockResult.NoKey ) - from.SendLocalizedMessage( 502494 ); // You must have a key to the ship to dock the boat. - else if ( result == DryDockResult.NotAnchored ) - from.SendLocalizedMessage( 1010570 ); // You must lower the anchor to dock the boat. - else if ( result == DryDockResult.Mobiles ) - from.SendLocalizedMessage( 502495 ); // You cannot dock the ship with beings on board! - else if ( result == DryDockResult.Items ) - from.SendLocalizedMessage( 502496 ); // You cannot dock the ship with a cluttered deck. - else if ( result == DryDockResult.Hold ) - from.SendLocalizedMessage( 502497 ); // Make sure your hold is empty, and try again! + if (result != DryDockResult.Valid) + return; - if ( result != DryDockResult.Valid ) - return; + BaseDockedBoat boat = DockedBoat; - BaseDockedBoat boat = DockedBoat; + if (boat == null) + return; - if ( boat == null ) - return; + RemoveKeys(from); - RemoveKeys( from ); + from.AddToBackpack(boat); + Delete(); + } - from.AddToBackpack( boat ); - Delete(); - } + public void SetName(SpeechEventArgs e) + { + if (CheckDecay()) + return; - public void SetName( SpeechEventArgs e ) - { - if ( CheckDecay() ) - return; + if (e.Mobile.AccessLevel < AccessLevel.GameMaster && e.Mobile != Owner) + { + TillerMan?.Say(1042880); // Arr! Only the owner of the ship may change its name! + + return; + } + + if (!e.Mobile.Alive) + { + TillerMan?.Say(502582); // You appear to be dead. + + return; + } + + if (e.Speech.Length > 8) + { + string newName = e.Speech.Substring(8).Trim(); + + if (newName.Length == 0) + newName = null; + + Rename(newName); + } + } + + public void Rename(string newName) + { + if (CheckDecay()) + return; + + if (newName != null && newName.Length > 40) + newName = newName.Substring(0, 40); + + if (m_ShipName == newName) + { + TillerMan?.Say(502531); // Yes, sir. + + return; + } + + ShipName = newName; + + if (TillerMan != null && m_ShipName != null) + TillerMan.Say(1042885, m_ShipName); // This ship is now called the ~1_NEW_SHIP_NAME~. + else + TillerMan?.Say(502534); // This ship now has no name. + } + + public void RemoveName(Mobile m) + { + if (CheckDecay()) + return; + + if (m.AccessLevel < AccessLevel.GameMaster && m != Owner) + { + TillerMan?.Say(1042880); // Arr! Only the owner of the ship may change its name! + + return; + } + + if (!m.Alive) + { + TillerMan?.Say(502582); // You appear to be dead. + + return; + } + + if (m_ShipName == null) + { + TillerMan?.Say(502526); // Ar, this ship has no name. + + return; + } + + ShipName = null; + + TillerMan?.Say(502534); // This ship now has no name. + } + + public void GiveName(Mobile m) + { + if (TillerMan == null || CheckDecay()) + return; + + if (m_ShipName == null) + TillerMan.Say(502526); // Ar, this ship has no name. + else + TillerMan.Say(1042881, m_ShipName); // This is the ~1_BOAT_NAME~. + } + + public void GiveNavPoint() + { + if (TillerMan == null || CheckDecay()) + return; + + if (NextNavPoint < 0) + TillerMan.Say(1042882); // I have no current nav point. + else + TillerMan.Say(1042883, + (NextNavPoint + 1).ToString()); // My current destination navpoint is nav ~1_NAV_POINT_NUM~. + } + + public void AssociateMap(MapItem map) + { + if (CheckDecay()) + return; + + if (map is BlankMap) + { + TillerMan?.Say(502575); // Ar, that is not a map, tis but a blank piece of paper! + } + else if (map.Pins.Count == 0) + { + TillerMan?.Say(502576); // Arrrr, this map has no course on it! + } + else + { + StopMove(false); + + MapItem = map; + NextNavPoint = -1; + + TillerMan?.Say(502577); // A map! + } + } + + public bool StartCourse(string navPoint, bool single, bool message) + { + int number = -1; + + int start = -1; + for (int i = 0; i < navPoint.Length; i++) + if (char.IsDigit(navPoint[i])) + { + start = i; + break; + } + + if (start != -1) + { + string sNumber = navPoint.Substring(start); + + if (!int.TryParse(sNumber, out number)) + number = -1; + + if (number != -1) + { + number--; + + if (MapItem == null || number < 0 || number >= MapItem.Pins.Count) number = -1; + } + } + + if (number == -1) + { + if (message) + TillerMan?.Say(1042551); // I don't see that navpoint, sir. + + return false; + } + + NextNavPoint = number; + return StartCourse(single, message); + } + + public bool StartCourse(bool single, bool message) + { + if (CheckDecay()) + return false; + + if (Anchored) + { + if (message) + TillerMan?.Say(501419); // Ar, the anchor is down sir! + + return false; + } + + if (MapItem == null || MapItem.Deleted) + { + if (message) + TillerMan?.Say(502513); // I have seen no map, sir. + + return false; + } + + if (Map != MapItem.Map || !Contains(MapItem.GetWorldLocation())) + { + if (message) + TillerMan?.Say(502514); // The map is too far away from me, sir. + + return false; + } + + if (Map != Map.Trammel && Map != Map.Felucca || NextNavPoint < 0 || NextNavPoint >= MapItem.Pins.Count) + { + if (message) + TillerMan?.Say(1042551); // I don't see that navpoint, sir. + + return false; + } + + Speed = FastSpeed; + Order = single ? BoatOrder.Single : BoatOrder.Course; + + m_MoveTimer?.Stop(); + + m_MoveTimer = new MoveTimer(this, FastInterval, false); + m_MoveTimer.Start(); + + if (message) + TillerMan?.Say(501429); // Aye aye sir. + + return true; + } + + public override void OnSpeech(SpeechEventArgs e) + { + if (CheckDecay()) + return; + + Mobile from = e.Mobile; + + if (CanCommand(from) && Contains(from)) + for (int i = 0; i < e.Keywords.Length; ++i) + { + int keyword = e.Keywords[i]; + + if (keyword >= 0x42 && keyword <= 0x6B) + { + switch (keyword) + { + case 0x42: + SetName(e); + break; + case 0x43: + RemoveName(e.Mobile); + break; + case 0x44: + GiveName(e.Mobile); + break; + case 0x45: + StartMove(Forward, true); + break; + case 0x46: + StartMove(Backward, true); + break; + case 0x47: + StartMove(Left, true); + break; + case 0x48: + StartMove(Right, true); + break; + case 0x4B: + StartMove(ForwardLeft, true); + break; + case 0x4C: + StartMove(ForwardRight, true); + break; + case 0x4D: + StartMove(BackwardLeft, true); + break; + case 0x4E: + StartMove(BackwardRight, true); + break; + case 0x4F: + StopMove(true); + break; + case 0x50: + StartMove(Left, false); + break; + case 0x51: + StartMove(Right, false); + break; + case 0x52: + StartMove(Forward, false); + break; + case 0x53: + StartMove(Backward, false); + break; + case 0x54: + StartMove(ForwardLeft, false); + break; + case 0x55: + StartMove(ForwardRight, false); + break; + case 0x56: + StartMove(BackwardRight, false); + break; + case 0x57: + StartMove(BackwardLeft, false); + break; + case 0x58: + OneMove(Left); + break; + case 0x59: + OneMove(Right); + break; + case 0x5A: + OneMove(Forward); + break; + case 0x5B: + OneMove(Backward); + break; + case 0x5C: + OneMove(ForwardLeft); + break; + case 0x5D: + OneMove(ForwardRight); + break; + case 0x5E: + OneMove(BackwardRight); + break; + case 0x5F: + OneMove(BackwardLeft); + break; + case 0x49: + case 0x65: + StartTurn(2, true); + break; // turn right + case 0x4A: + case 0x66: + StartTurn(-2, true); + break; // turn left + case 0x67: + StartTurn(-4, true); + break; // turn around, come about + case 0x68: + StartMove(Forward, true); + break; + case 0x69: + StopMove(true); + break; + case 0x6A: + LowerAnchor(true); + break; + case 0x6B: + RaiseAnchor(true); + break; + case 0x60: + GiveNavPoint(); + break; // nav + case 0x61: + NextNavPoint = 0; + StartCourse(false, true); + break; // start + case 0x62: + StartCourse(false, true); + break; // continue + case 0x63: + StartCourse(e.Speech, false, true); + break; // goto* + case 0x64: + StartCourse(e.Speech, true, true); + break; // single* + } + + break; + } + } + } + + public bool StartTurn(int offset, bool message) + { + if (CheckDecay()) + return false; + + if (Anchored) + { + if (message) + TillerMan.Say(501419); // Ar, the anchor is down sir! + + return false; + } + + if (m_MoveTimer != null && Order != BoatOrder.Move) + { + m_MoveTimer.Stop(); + m_MoveTimer = null; + } + + m_TurnTimer?.Stop(); + + m_TurnTimer = new TurnTimer(this, offset); + m_TurnTimer.Start(); + + if (message) + TillerMan?.Say(501429); // Aye aye sir. + + return true; + } + + public bool Turn(int offset, bool message) + { + if (m_TurnTimer != null) + { + m_TurnTimer.Stop(); + m_TurnTimer = null; + } + + if (CheckDecay()) + return false; + + if (Anchored) + { + if (message) + TillerMan.Say(501419); // Ar, the anchor is down sir! + + return false; + } + + if (SetFacing((Direction)(((int)m_Facing + offset) & 0x7))) return true; + if (message) + TillerMan.Say(501423); // Ar, can't turn sir. + + return false; + } + + public bool StartMove(Direction dir, int speed, int clientSpeed, TimeSpan interval, bool single, bool message) + { + if (CheckDecay()) + return false; + + if (Anchored) + { + if (message) + TillerMan?.Say(501419); // Ar, the anchor is down sir! + + return false; + } + + Moving = dir; + Speed = speed; + m_ClientSpeed = clientSpeed; + Order = BoatOrder.Move; + + m_MoveTimer?.Stop(); + + m_MoveTimer = new MoveTimer(this, interval, single); + m_MoveTimer.Start(); + + return true; + } - if ( e.Mobile.AccessLevel < AccessLevel.GameMaster && e.Mobile != Owner ) - { - TillerMan?.Say( 1042880 ); // Arr! Only the owner of the ship may change its name! + public bool StopMove(bool message) + { + if (CheckDecay()) + return false; - return; - } - - if ( !e.Mobile.Alive ) - { - TillerMan?.Say( 502582 ); // You appear to be dead. - - return; - } - - if ( e.Speech.Length > 8 ) - { - string newName = e.Speech.Substring( 8 ).Trim(); - - if ( newName.Length == 0 ) - newName = null; - - Rename( newName ); - } - } - - public void Rename( string newName ) - { - if ( CheckDecay() ) - return; - - if ( newName != null && newName.Length > 40 ) - newName = newName.Substring( 0, 40 ); - - if ( m_ShipName == newName ) - { - TillerMan?.Say( 502531 ); // Yes, sir. - - return; - } - - ShipName = newName; - - if ( TillerMan != null && m_ShipName != null ) - TillerMan.Say( 1042885, m_ShipName ); // This ship is now called the ~1_NEW_SHIP_NAME~. - else - { - TillerMan?.Say( 502534 ); // This ship now has no name. - } - } - - public void RemoveName( Mobile m ) - { - if ( CheckDecay() ) - return; - - if ( m.AccessLevel < AccessLevel.GameMaster && m != Owner ) - { - TillerMan?.Say( 1042880 ); // Arr! Only the owner of the ship may change its name! - - return; - } - - if ( !m.Alive ) - { - TillerMan?.Say( 502582 ); // You appear to be dead. - - return; - } - - if ( m_ShipName == null ) - { - TillerMan?.Say( 502526 ); // Ar, this ship has no name. - - return; - } - - ShipName = null; - - TillerMan?.Say( 502534 ); // This ship now has no name. - } - - public void GiveName( Mobile m ) - { - if ( TillerMan == null || CheckDecay() ) - return; - - if ( m_ShipName == null ) - TillerMan.Say( 502526 ); // Ar, this ship has no name. - else - TillerMan.Say( 1042881, m_ShipName ); // This is the ~1_BOAT_NAME~. - } - - public void GiveNavPoint() - { - if ( TillerMan == null || CheckDecay() ) - return; - - if ( NextNavPoint < 0 ) - TillerMan.Say( 1042882 ); // I have no current nav point. - else - TillerMan.Say( 1042883, (NextNavPoint + 1).ToString() ); // My current destination navpoint is nav ~1_NAV_POINT_NUM~. - } - - public void AssociateMap( MapItem map ) - { - if ( CheckDecay() ) - return; - - if ( map is BlankMap ) - { - TillerMan?.Say( 502575 ); // Ar, that is not a map, tis but a blank piece of paper! - } - else if ( map.Pins.Count == 0 ) - { - TillerMan?.Say( 502576 ); // Arrrr, this map has no course on it! - } - else - { - StopMove( false ); - - MapItem = map; - NextNavPoint = -1; - - TillerMan?.Say( 502577 ); // A map! - } - } - - public bool StartCourse( string navPoint, bool single, bool message ) - { - int number = -1; - - int start = -1; - for ( int i = 0; i < navPoint.Length; i++ ) - { - if ( char.IsDigit( navPoint[i] ) ) - { - start = i; - break; - } - } - - if ( start != -1 ) - { - string sNumber = navPoint.Substring( start ); - - if ( !int.TryParse( sNumber, out number ) ) - number = -1; - - if ( number != -1 ) - { - number--; - - if ( MapItem == null || number < 0 || number >= MapItem.Pins.Count ) - { - number = -1; - } - } - } - - if ( number == -1 ) - { - if ( message ) - TillerMan?.Say( 1042551 ); // I don't see that navpoint, sir. - - return false; - } - - NextNavPoint = number; - return StartCourse( single, message ); - } - - public bool StartCourse( bool single, bool message ) - { - if ( CheckDecay() ) - return false; - - if ( Anchored ) - { - if ( message ) - TillerMan?.Say( 501419 ); // Ar, the anchor is down sir! - - return false; - } - - if ( MapItem == null || MapItem.Deleted ) - { - if ( message ) - TillerMan?.Say( 502513 ); // I have seen no map, sir. - - return false; - } - if ( Map != MapItem.Map || !Contains( MapItem.GetWorldLocation() ) ) - { - if ( message ) - TillerMan?.Say( 502514 ); // The map is too far away from me, sir. - - return false; - } - if ( ( Map != Map.Trammel && Map != Map.Felucca ) || NextNavPoint < 0 || NextNavPoint >= MapItem.Pins.Count ) - { - if ( message ) - TillerMan?.Say( 1042551 ); // I don't see that navpoint, sir. - - return false; - } - - Speed = FastSpeed; - Order = single ? BoatOrder.Single : BoatOrder.Course; - - m_MoveTimer?.Stop(); - - m_MoveTimer = new MoveTimer( this, FastInterval, false ); - m_MoveTimer.Start(); - - if ( message ) - TillerMan?.Say( 501429 ); // Aye aye sir. - - return true; - } - - public override bool HandlesOnSpeech => true; - - public override void OnSpeech( SpeechEventArgs e ) - { - if ( CheckDecay() ) - return; - - Mobile from = e.Mobile; - - if ( CanCommand( from ) && Contains( from ) ) - { - for ( int i = 0; i < e.Keywords.Length; ++i ) - { - int keyword = e.Keywords[i]; - - if ( keyword >= 0x42 && keyword <= 0x6B ) - { - switch ( keyword ) - { - case 0x42: SetName( e ); break; - case 0x43: RemoveName( e.Mobile ); break; - case 0x44: GiveName( e.Mobile ); break; - case 0x45: StartMove( Forward, true ); break; - case 0x46: StartMove( Backward, true ); break; - case 0x47: StartMove( Left, true ); break; - case 0x48: StartMove( Right, true ); break; - case 0x4B: StartMove( ForwardLeft, true ); break; - case 0x4C: StartMove( ForwardRight, true ); break; - case 0x4D: StartMove( BackwardLeft, true ); break; - case 0x4E: StartMove( BackwardRight, true ); break; - case 0x4F: StopMove( true ); break; - case 0x50: StartMove( Left, false ); break; - case 0x51: StartMove( Right, false ); break; - case 0x52: StartMove( Forward, false ); break; - case 0x53: StartMove( Backward, false ); break; - case 0x54: StartMove( ForwardLeft, false ); break; - case 0x55: StartMove( ForwardRight, false ); break; - case 0x56: StartMove( BackwardRight, false ); break; - case 0x57: StartMove( BackwardLeft, false ); break; - case 0x58: OneMove( Left ); break; - case 0x59: OneMove( Right ); break; - case 0x5A: OneMove( Forward ); break; - case 0x5B: OneMove( Backward ); break; - case 0x5C: OneMove( ForwardLeft ); break; - case 0x5D: OneMove( ForwardRight ); break; - case 0x5E: OneMove( BackwardRight ); break; - case 0x5F: OneMove( BackwardLeft ); break; - case 0x49: case 0x65: StartTurn( 2, true ); break; // turn right - case 0x4A: case 0x66: StartTurn( -2, true ); break; // turn left - case 0x67: StartTurn( -4, true ); break; // turn around, come about - case 0x68: StartMove( Forward, true ); break; - case 0x69: StopMove( true ); break; - case 0x6A: LowerAnchor( true ); break; - case 0x6B: RaiseAnchor( true ); break; - case 0x60: GiveNavPoint(); break; // nav - case 0x61: NextNavPoint = 0; StartCourse( false, true ); break; // start - case 0x62: StartCourse( false, true ); break; // continue - case 0x63: StartCourse( e.Speech, false, true ); break; // goto* - case 0x64: StartCourse( e.Speech, true, true ); break; // single* - } - - break; - } - } - } - } - - public bool StartTurn( int offset, bool message ) - { - if ( CheckDecay() ) - return false; - - if ( Anchored ) - { - if ( message ) - TillerMan.Say( 501419 ); // Ar, the anchor is down sir! - - return false; - } - - if ( m_MoveTimer != null && Order != BoatOrder.Move ) - { - m_MoveTimer.Stop(); - m_MoveTimer = null; - } - - m_TurnTimer?.Stop(); - - m_TurnTimer = new TurnTimer( this, offset ); - m_TurnTimer.Start(); - - if ( message ) - TillerMan?.Say( 501429 ); // Aye aye sir. - - return true; - } - - public bool Turn( int offset, bool message ) - { - if ( m_TurnTimer != null ) - { - m_TurnTimer.Stop(); - m_TurnTimer = null; - } - - if ( CheckDecay() ) - return false; - - if ( Anchored ) - { - if ( message ) - TillerMan.Say( 501419 ); // Ar, the anchor is down sir! - - return false; - } - - if ( SetFacing( (Direction)(((int)m_Facing + offset) & 0x7) ) ) - { - return true; - } - if ( message ) - TillerMan.Say( 501423 ); // Ar, can't turn sir. - - return false; - } - - private class TurnTimer : Timer - { - private BaseBoat m_Boat; - private int m_Offset; - - public TurnTimer( BaseBoat boat, int offset ) : base( TimeSpan.FromSeconds( 0.5 ) ) - { - m_Boat = boat; - m_Offset = offset; - - Priority = TimerPriority.TenMS; - } - - protected override void OnTick() - { - if ( !m_Boat.Deleted ) - m_Boat.Turn( m_Offset, true ); - } - } - - public bool StartMove( Direction dir, int speed, int clientSpeed, TimeSpan interval, bool single, bool message ) - { - if ( CheckDecay() ) - return false; - - if ( Anchored ) - { - if ( message ) - TillerMan?.Say( 501419 ); // Ar, the anchor is down sir! - - return false; - } + if (m_MoveTimer == null) + { + if (message) + TillerMan?.Say(501443); // Er, the ship is not moving sir. - Moving = dir; - Speed = speed; - m_ClientSpeed = clientSpeed; - Order = BoatOrder.Move; + return false; + } - m_MoveTimer?.Stop(); + Moving = Direction.North; + Speed = 0; + m_ClientSpeed = 0; + m_MoveTimer.Stop(); + m_MoveTimer = null; - m_MoveTimer = new MoveTimer( this, interval, single ); - m_MoveTimer.Start(); + if (message) + TillerMan?.Say(501429); // Aye aye sir. - return true; - } + return true; + } - public bool StopMove( bool message ) - { - if ( CheckDecay() ) - return false; + public bool CanFit(Point3D p, Map map, int itemID) + { + if (map == null || map == Map.Internal || Deleted || CheckDecay()) + return false; - if ( m_MoveTimer == null ) - { - if ( message ) - TillerMan?.Say( 501443 ); // Er, the ship is not moving sir. + MultiComponentList newComponents = MultiData.GetComponents(itemID); - return false; - } + for (int x = 0; x < newComponents.Width; ++x) + for (int y = 0; y < newComponents.Height; ++y) + { + int tx = p.X + newComponents.Min.X + x; + int ty = p.Y + newComponents.Min.Y + y; - Moving = Direction.North; - Speed = 0; - m_ClientSpeed = 0; - m_MoveTimer.Stop(); - m_MoveTimer = null; + if (newComponents.Tiles[x][y].Length == 0 || Contains(tx, ty)) + continue; - if ( message ) - TillerMan?.Say( 501429 ); // Aye aye sir. + LandTile landTile = map.Tiles.GetLandTile(tx, ty); + StaticTile[] tiles = map.Tiles.GetStaticTiles(tx, ty, true); - return true; - } + bool hasWater = false; - public bool CanFit( Point3D p, Map map, int itemID ) - { - if ( map == null || map == Map.Internal || Deleted || CheckDecay() ) - return false; + if (landTile.Z == p.Z && + (landTile.ID >= 168 && landTile.ID <= 171 || landTile.ID >= 310 && landTile.ID <= 311)) + hasWater = true; - MultiComponentList newComponents = MultiData.GetComponents( itemID ); + int z = p.Z; - for ( int x = 0; x < newComponents.Width; ++x ) - { - for ( int y = 0; y < newComponents.Height; ++y ) - { - int tx = p.X + newComponents.Min.X + x; - int ty = p.Y + newComponents.Min.Y + y; + //int landZ = 0, landAvg = 0, landTop = 0; - if ( newComponents.Tiles[x][y].Length == 0 || Contains( tx, ty ) ) - continue; + //map.GetAverageZ( tx, ty, ref landZ, ref landAvg, ref landTop ); - LandTile landTile = map.Tiles.GetLandTile( tx, ty ); - StaticTile[] tiles = map.Tiles.GetStaticTiles( tx, ty, true ); + //if ( !landTile.Ignored && top > landZ && landTop > z ) + // return false; - bool hasWater = false; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; + bool isWater = tile.ID >= 0x1796 && tile.ID <= 0x17B2; - if ( landTile.Z == p.Z && ((landTile.ID >= 168 && landTile.ID <= 171) || (landTile.ID >= 310 && landTile.ID <= 311)) ) - hasWater = true; + if (tile.Z == p.Z && isWater) + hasWater = true; + else if (tile.Z >= p.Z && !isWater) + return false; + } - int z = p.Z; + if (!hasWater) + return false; + } - //int landZ = 0, landAvg = 0, landTop = 0; + IPooledEnumerable eable = map.GetItemsInBounds(new Rectangle2D(p.X + newComponents.Min.X, + p.Y + newComponents.Min.Y, newComponents.Width, newComponents.Height)); - //map.GetAverageZ( tx, ty, ref landZ, ref landAvg, ref landTop ); + foreach (Item item in eable) + { + if (item is BaseMulti || item.ItemID > TileData.MaxItemValue || item.Z < p.Z || !item.Visible) + continue; - //if ( !landTile.Ignored && top > landZ && landTop > z ) - // return false; + int x = item.X - p.X + newComponents.Min.X; + int y = item.Y - p.Y + newComponents.Min.Y; - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - bool isWater = ( tile.ID >= 0x1796 && tile.ID <= 0x17B2 ); + if (x >= 0 && x < newComponents.Width && y >= 0 && y < newComponents.Height && + newComponents.Tiles[x][y].Length == 0) + continue; + if (Contains(item)) + continue; - if ( tile.Z == p.Z && isWater ) - hasWater = true; - else if ( tile.Z >= p.Z && !isWater ) - return false; - } - - if ( !hasWater ) - return false; - } - } - - IPooledEnumerable eable = map.GetItemsInBounds( new Rectangle2D( p.X + newComponents.Min.X, p.Y + newComponents.Min.Y, newComponents.Width, newComponents.Height ) ); - - foreach ( Item item in eable ) - { - if ( item is BaseMulti || item.ItemID > TileData.MaxItemValue || item.Z < p.Z || !item.Visible ) - continue; - - int x = item.X - p.X + newComponents.Min.X; - int y = item.Y - p.Y + newComponents.Min.Y; - - if ( x >= 0 && x < newComponents.Width && y >= 0 && y < newComponents.Height && newComponents.Tiles[x][y].Length == 0 ) - continue; - if ( Contains( item ) ) - continue; - - eable.Free(); - return false; - } - - eable.Free(); - - return true; - } - - public Point3D Rotate( Point3D p, int count ) - { - int rx = p.X - Location.X; - int ry = p.Y - Location.Y; - - for ( int i = 0; i < count; ++i ) - { - int temp = rx; - rx = -ry; - ry = temp; - } - - return new Point3D( Location.X + rx, Location.Y + ry, p.Z ); - } - - public override bool Contains( int x, int y ) - { - if ( base.Contains( x, y ) ) - return true; - - if ( TillerMan != null && x == TillerMan.X && y == TillerMan.Y ) - return true; - - if ( Hold != null && x == Hold.X && y == Hold.Y ) - return true; - - if ( PPlank != null && x == PPlank.X && y == PPlank.Y ) - return true; - - if ( SPlank != null && x == SPlank.X && y == SPlank.Y ) - return true; - - return false; - } - - public static bool IsValidLocation( Point3D p, Map map ) - { - Rectangle2D[] wrap = GetWrapFor( map ); - - for ( int i = 0; i < wrap.Length; ++i ) - { - if ( wrap[i].Contains( p ) ) - return true; - } - - return false; - } - - public static Rectangle2D[] GetWrapFor( Map m ) - { - if ( m == Map.Ilshenar ) - return m_IlshWrap; - if ( m == Map.Tokuno ) - return m_TokunoWrap; - return m_BritWrap; - } - - public Direction GetMovementFor( int x, int y, out int maxSpeed ) - { - int dx = x - X; - int dy = y - Y; - - int adx = Math.Abs( dx ); - int ady = Math.Abs( dy ); - - Direction dir = Utility.GetDirection( this, new Point2D( x, y ) ); - int iDir = (int) dir; - - // Compute the maximum distance we can travel without going too far away - if ( iDir % 2 == 0 ) // North, East, South and West - maxSpeed = Math.Abs( adx - ady ); - else // Right, Down, Left and Up - maxSpeed = Math.Min( adx, ady ); - - return (Direction) ((iDir - (int)Facing) & 0x7); - } - - public bool DoMovement( bool message ) - { - Direction dir; - int speed, clientSpeed; - - if ( Order == BoatOrder.Move ) - { - dir = Moving; - speed = Speed; - clientSpeed = m_ClientSpeed; - } - else if ( MapItem == null || MapItem.Deleted ) - { - if ( message ) - TillerMan?.Say( 502513 ); // I have seen no map, sir. - - return false; - } - else if ( Map != MapItem.Map || !Contains( MapItem.GetWorldLocation() ) ) - { - if ( message ) - TillerMan?.Say( 502514 ); // The map is too far away from me, sir. - - return false; - } - else if ( ( Map != Map.Trammel && Map != Map.Felucca ) || NextNavPoint < 0 || NextNavPoint >= MapItem.Pins.Count ) - { - if ( message ) - TillerMan?.Say( 1042551 ); // I don't see that navpoint, sir. - - return false; - } - else - { - Point2D dest = (Point2D) MapItem.Pins[NextNavPoint]; - - int x, y; - MapItem.ConvertToWorld( dest.X, dest.Y, out x, out y ); - - int maxSpeed; - dir = GetMovementFor( x, y, out maxSpeed ); - - if ( maxSpeed == 0 ) - { - if ( message && Order == BoatOrder.Single ) - TillerMan?.Say( 1042874, (NextNavPoint + 1).ToString() ); // We have arrived at nav point ~1_POINT_NUM~ , sir. - - if ( NextNavPoint + 1 < MapItem.Pins.Count ) - { - NextNavPoint++; - - if ( Order == BoatOrder.Course ) - { - if ( message ) - TillerMan?.Say( 1042875, (NextNavPoint + 1).ToString() ); // Heading to nav point ~1_POINT_NUM~, sir. - - return true; - } - - return false; - } - - NextNavPoint = -1; - - if ( message && Order == BoatOrder.Course ) - TillerMan?.Say( 502515 ); // The course is completed, sir. - - return false; - } - - if ( dir == Left || dir == BackwardLeft || dir == Backward ) - return Turn( -2, true ); - if ( dir == Right || dir == BackwardRight ) - return Turn( 2, true ); - - speed = Math.Min( Speed, maxSpeed ); - clientSpeed = 0x4; - } - - return Move( dir, speed, clientSpeed, true ); - } - - public bool Move( Direction dir, int speed, int clientSpeed, bool message ) - { - Map map = Map; - - if ( map == null || Deleted || CheckDecay() ) - return false; - - if ( Anchored ) - { - if ( message ) - TillerMan?.Say( 501419 ); // Ar, the anchor is down sir! - - return false; - } - - int rx = 0, ry = 0; - Direction d = (Direction)(((int)m_Facing + (int)dir) & 0x7); - Movement.Movement.Offset( d, ref rx, ref ry ); - - for ( int i = 1; i <= speed; ++i ) - { - if ( !CanFit( new Point3D( X + (i * rx), Y + (i * ry), Z ), Map, ItemID ) ) - { - if ( i == 1 ) - { - if ( message ) - TillerMan?.Say( 501424 ); // Ar, we've stopped sir. - - return false; - } - - speed = i - 1; - break; - } - } - - int xOffset = speed*rx; - int yOffset = speed*ry; - - int newX = X + xOffset; - int newY = Y + yOffset; - - Rectangle2D[] wrap = GetWrapFor( map ); - - for ( int i = 0; i < wrap.Length; ++i ) - { - Rectangle2D rect = wrap[i]; - - if ( rect.Contains( new Point2D( X, Y ) ) && !rect.Contains( new Point2D( newX, newY ) ) ) - { - if ( newX < rect.X ) - newX = rect.X + rect.Width - 1; - else if ( newX >= rect.X + rect.Width ) - newX = rect.X; - - if ( newY < rect.Y ) - newY = rect.Y + rect.Height - 1; - else if ( newY >= rect.Y + rect.Height ) - newY = rect.Y; - - for ( int j = 1; j <= speed; ++j ) - { - if ( !CanFit( new Point3D( newX + (j * rx), newY + (j * ry), Z ), Map, ItemID ) ) - { - if ( message ) - TillerMan?.Say( 501424 ); // Ar, we've stopped sir. - - return false; - } - } - - xOffset = newX - X; - yOffset = newY - Y; - } - } - - if ( !NewBoatMovement || Math.Abs( xOffset ) > 1 || Math.Abs( yOffset ) > 1 ) - { - Teleport( xOffset, yOffset, 0 ); - } - else - { - List toMove = GetMovingEntities(); - - SafeAdd( TillerMan, toMove ); - SafeAdd( Hold, toMove ); - SafeAdd( PPlank, toMove ); - SafeAdd( SPlank, toMove ); - - // Packet must be sent before actual locations are changed - foreach ( NetState ns in Map.GetClientsInRange( Location, GetMaxUpdateRange() ) ) - { - Mobile m = ns.Mobile; - - if ( ns.HighSeas && m.CanSee( this ) && m.InRange( Location, GetUpdateRange( m ) ) ) - ns.Send( new MoveBoatHS( m, this, d, clientSpeed, toMove, xOffset, yOffset ) ); - } - - foreach ( IEntity e in toMove ) - { - if ( e is Item ) - { - Item item = (Item)e; - - item.NoMoveHS = true; - - if ( !( item is TillerMan || item is Hold || item is Plank ) ) - item.Location = new Point3D( item.X + xOffset, item.Y + yOffset, item.Z ); - } - else if ( e is Mobile ) - { - Mobile m = (Mobile)e; - - m.NoMoveHS = true; - m.Location = new Point3D( m.X + xOffset, m.Y + yOffset, m.Z ); - } - } - - NoMoveHS = true; - Location = new Point3D( X + xOffset, Y + yOffset, Z ); - - foreach ( IEntity e in toMove ) - { - if ( e is Item ) - ((Item)e).NoMoveHS = false; - else if ( e is Mobile ) - ((Mobile)e).NoMoveHS = false; - } - - NoMoveHS = false; - } - - return true; - } - - private static void SafeAdd( Item item, List toMove ) - { - if ( item != null ) - toMove.Add( item ); - } - - public void Teleport( int xOffset, int yOffset, int zOffset ) - { - List toMove = GetMovingEntities(); - - for ( int i = 0; i < toMove.Count; ++i ) - { - IEntity e = toMove[i]; - - if ( e is Item ) - { - Item item = (Item)e; - - item.Location = new Point3D( item.X + xOffset, item.Y + yOffset, item.Z + zOffset ); - } - else if ( e is Mobile ) - { - Mobile m = (Mobile)e; - - m.Location = new Point3D( m.X + xOffset, m.Y + yOffset, m.Z + zOffset ); - } - } - - Location = new Point3D( X + xOffset, Y + yOffset, Z + zOffset ); - } - - public List GetMovingEntities() - { - List list = new List(); - - Map map = Map; - - if ( map == null || map == Map.Internal ) - return list; - - MultiComponentList mcl = Components; - - foreach ( object o in map.GetObjectsInBounds( new Rectangle2D( X + mcl.Min.X, Y + mcl.Min.Y, mcl.Width, mcl.Height ) ) ) - { - if ( o == this || o is TillerMan || o is Hold || o is Plank ) - continue; - - if ( o is Item ) - { - Item item = (Item)o; - - if ( Contains( item ) && item.Visible && item.Z >= Z ) - list.Add( item ); - } - else if ( o is Mobile ) - { - Mobile m = (Mobile)o; - - if ( Contains( m ) ) - list.Add( m ); - } - } - - return list; - } - - public bool SetFacing( Direction facing ) - { - if ( Parent != null || Map == null ) - return false; - - if ( CheckDecay() ) - return false; - - if ( Map != Map.Internal ) - { - switch ( facing ) - { - case Direction.North: if ( !CanFit( Location, Map, NorthID ) ) return false; break; - case Direction.East: if ( !CanFit( Location, Map, EastID ) ) return false; break; - case Direction.South: if ( !CanFit( Location, Map, SouthID ) ) return false; break; - case Direction.West: if ( !CanFit( Location, Map, WestID ) ) return false; break; - } - } - - Direction old = m_Facing; - - m_Facing = facing; - - TillerMan?.SetFacing( facing ); - - Hold?.SetFacing( facing ); - - PPlank?.SetFacing( facing ); - - SPlank?.SetFacing( facing ); - - List toMove = GetMovingEntities(); - - toMove.Add( PPlank ); - toMove.Add( SPlank ); - - int xOffset = 0, yOffset = 0; - Movement.Movement.Offset( facing, ref xOffset, ref yOffset ); - - if ( TillerMan != null ) - TillerMan.Location = new Point3D( X + (xOffset * TillerManDistance) + (facing == Direction.North ? 1 : 0), Y + (yOffset * TillerManDistance), TillerMan.Z ); - - if ( Hold != null ) - Hold.Location = new Point3D( X + (xOffset * HoldDistance), Y + (yOffset * HoldDistance), Hold.Z ); - - int count = (int)(m_Facing - old) & 0x7; - count /= 2; - - for ( int i = 0; i < toMove.Count; ++i ) - { - IEntity e = toMove[i]; - - if ( e is Item ) - { - Item item = (Item)e; - - item.Location = Rotate( item.Location, count ); - } - else if ( e is Mobile ) - { - Mobile m = (Mobile)e; - - m.Direction = ( m.Direction - old + facing ) & Direction.Mask; - m.Location = Rotate( m.Location, count ); - } - } - - switch ( facing ) - { - case Direction.North: ItemID = NorthID; break; - case Direction.East: ItemID = EastID; break; - case Direction.South: ItemID = SouthID; break; - case Direction.West: ItemID = WestID; break; - } - - return true; - } - - private class MoveTimer : Timer - { - private BaseBoat m_Boat; - - public MoveTimer( BaseBoat boat, TimeSpan interval, bool single ) : base( interval, interval, single ? 1 : 0 ) - { - m_Boat = boat; - Priority = TimerPriority.TwentyFiveMS; - } - - protected override void OnTick() - { - if ( !m_Boat.DoMovement( true ) ) - m_Boat.StopMove( false ); - } - } - - public static void UpdateAllComponents() - { - for ( int i = Boats.Count - 1; i >= 0; --i ) - Boats[i].UpdateComponents(); - } - - public static void Initialize() - { - new UpdateAllTimer().Start(); - EventSink.WorldSave += EventSink_WorldSave; - } - - private static void EventSink_WorldSave( WorldSaveEventArgs e ) - { - new UpdateAllTimer().Start(); - } - - public class UpdateAllTimer : Timer - { - public UpdateAllTimer() : base( TimeSpan.FromSeconds( 1.0 ) ) - { - } - - protected override void OnTick() - { - UpdateAllComponents(); - } - } - - #region High Seas - - public override bool AllowsRelativeDrop => true; - - /* - * OSI sends the 0xF7 packet instead, holding 0xF3 packets - * for every entity on the boat. Though, the regular 0xF3 - * packets are still being sent as well as entities come - * into sight. Do we really need it? - */ - /* - protected override Packet GetWorldPacketFor( NetState state ) - { - if ( NewBoatMovement && state.HighSeas ) - return new DisplayBoatHS( state.Mobile, this ); - else - return base.GetWorldPacketFor( state ); - } - */ - - public sealed class MoveBoatHS : Packet - { - public MoveBoatHS( Mobile beholder, BaseBoat boat, Direction d, int speed, List ents, int xOffset, int yOffset ) - : base( 0xF6 ) - { - EnsureCapacity( 3 + 15 + ents.Count * 10 ); - - m_Stream.Write( (int) boat.Serial ); - m_Stream.Write( (byte) speed ); - m_Stream.Write( (byte) d ); - m_Stream.Write( (byte) boat.Facing ); - m_Stream.Write( (short) ( boat.X + xOffset ) ); - m_Stream.Write( (short) ( boat.Y + yOffset ) ); - m_Stream.Write( (short) boat.Z ); - m_Stream.Write( (short) 0 ); // count placeholder - - int count = 0; - - foreach ( IEntity ent in ents ) - { - if ( !beholder.CanSee( ent ) ) - continue; - - m_Stream.Write( (int) ent.Serial ); - m_Stream.Write( (short) ( ent.X + xOffset ) ); - m_Stream.Write( (short) ( ent.Y + yOffset ) ); - m_Stream.Write( (short) ent.Z ); - ++count; - } - - m_Stream.Seek( 16, System.IO.SeekOrigin.Begin ); - m_Stream.Write( (short) count ); - } - } - - public sealed class DisplayBoatHS : Packet - { - public DisplayBoatHS( Mobile beholder, BaseBoat boat ) - : base( 0xF7 ) - { - List ents = boat.GetMovingEntities(); - - SafeAdd( boat.TillerMan, ents ); - SafeAdd( boat.Hold, ents ); - SafeAdd( boat.PPlank, ents ); - SafeAdd( boat.SPlank, ents ); - - ents.Add( boat ); - - EnsureCapacity( 3 + 2 + ents.Count * 26 ); - - m_Stream.Write( (short) 0 ); // count placeholder - - int count = 0; - - foreach ( IEntity ent in ents ) - { - if ( !beholder.CanSee( ent ) ) - continue; - - // Embedded WorldItemHS packets - m_Stream.Write( (byte) 0xF3 ); - m_Stream.Write( (short) 0x1 ); - - if ( ent is BaseMulti ) - { - BaseMulti bm = (BaseMulti)ent; - - m_Stream.Write( (byte) 0x02 ); - m_Stream.Write( (int) bm.Serial ); - // TODO: Mask no longer needed, merge with Item case? - m_Stream.Write( (ushort) ( bm.ItemID & 0x3FFF ) ); - m_Stream.Write( (byte) 0 ); - - m_Stream.Write( (short) bm.Amount ); - m_Stream.Write( (short) bm.Amount ); - - m_Stream.Write( (short) ( bm.X & 0x7FFF ) ); - m_Stream.Write( (short) ( bm.Y & 0x3FFF ) ); - m_Stream.Write( (sbyte) bm.Z ); - - m_Stream.Write( (byte) bm.Light ); - m_Stream.Write( (short) bm.Hue ); - m_Stream.Write( (byte) bm.GetPacketFlags() ); - } - else if ( ent is Mobile ) - { - Mobile m = (Mobile)ent; - - m_Stream.Write( (byte) 0x01 ); - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.Body ); - m_Stream.Write( (byte) 0 ); - - m_Stream.Write( (short) 1 ); - m_Stream.Write( (short) 1 ); - - m_Stream.Write( (short) ( m.X & 0x7FFF ) ); - m_Stream.Write( (short) ( m.Y & 0x3FFF ) ); - m_Stream.Write( (sbyte) m.Z ); - - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (short) m.Hue ); - m_Stream.Write( (byte) m.GetPacketFlags() ); - } - else if ( ent is Item ) - { - Item item = (Item)ent; - - m_Stream.Write( (byte) 0x00 ); - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (ushort) ( item.ItemID & 0xFFFF ) ); - m_Stream.Write( (byte) 0 ); - - m_Stream.Write( (short) item.Amount ); - m_Stream.Write( (short) item.Amount ); - - m_Stream.Write( (short) ( item.X & 0x7FFF ) ); - m_Stream.Write( (short) ( item.Y & 0x3FFF ) ); - m_Stream.Write( (sbyte) item.Z ); - - m_Stream.Write( (byte) item.Light ); - m_Stream.Write( (short) item.Hue ); - m_Stream.Write( (byte) item.GetPacketFlags() ); - } - - m_Stream.Write( (short) 0x00 ); - ++count; - } - - m_Stream.Seek( 3, System.IO.SeekOrigin.Begin ); - m_Stream.Write( (short) count ); - } - } - - #endregion - } -} + eable.Free(); + return false; + } + + eable.Free(); + + return true; + } + + public Point3D Rotate(Point3D p, int count) + { + int rx = p.X - Location.X; + int ry = p.Y - Location.Y; + + for (int i = 0; i < count; ++i) + { + int temp = rx; + rx = -ry; + ry = temp; + } + + return new Point3D(Location.X + rx, Location.Y + ry, p.Z); + } + + public override bool Contains(int x, int y) + { + if (base.Contains(x, y)) + return true; + + if (TillerMan != null && x == TillerMan.X && y == TillerMan.Y) + return true; + + if (Hold != null && x == Hold.X && y == Hold.Y) + return true; + + if (PPlank != null && x == PPlank.X && y == PPlank.Y) + return true; + + if (SPlank != null && x == SPlank.X && y == SPlank.Y) + return true; + + return false; + } + + public static bool IsValidLocation(Point3D p, Map map) + { + Rectangle2D[] wrap = GetWrapFor(map); + + for (int i = 0; i < wrap.Length; ++i) + if (wrap[i].Contains(p)) + return true; + + return false; + } + + public static Rectangle2D[] GetWrapFor(Map m) + { + if (m == Map.Ilshenar) + return m_IlshWrap; + if (m == Map.Tokuno) + return m_TokunoWrap; + return m_BritWrap; + } + + public Direction GetMovementFor(int x, int y, out int maxSpeed) + { + int dx = x - X; + int dy = y - Y; + + int adx = Math.Abs(dx); + int ady = Math.Abs(dy); + + Direction dir = Utility.GetDirection(this, new Point2D(x, y)); + int iDir = (int)dir; + + // Compute the maximum distance we can travel without going too far away + if (iDir % 2 == 0) // North, East, South and West + maxSpeed = Math.Abs(adx - ady); + else // Right, Down, Left and Up + maxSpeed = Math.Min(adx, ady); + + return (Direction)((iDir - (int)Facing) & 0x7); + } + + public bool DoMovement(bool message) + { + Direction dir; + int speed, clientSpeed; + + if (Order == BoatOrder.Move) + { + dir = Moving; + speed = Speed; + clientSpeed = m_ClientSpeed; + } + else if (MapItem == null || MapItem.Deleted) + { + if (message) + TillerMan?.Say(502513); // I have seen no map, sir. + + return false; + } + else if (Map != MapItem.Map || !Contains(MapItem.GetWorldLocation())) + { + if (message) + TillerMan?.Say(502514); // The map is too far away from me, sir. + + return false; + } + else if (Map != Map.Trammel && Map != Map.Felucca || NextNavPoint < 0 || NextNavPoint >= MapItem.Pins.Count) + { + if (message) + TillerMan?.Say(1042551); // I don't see that navpoint, sir. + + return false; + } + else + { + Point2D dest = MapItem.Pins[NextNavPoint]; + + int x, y; + MapItem.ConvertToWorld(dest.X, dest.Y, out x, out y); + + int maxSpeed; + dir = GetMovementFor(x, y, out maxSpeed); + + if (maxSpeed == 0) + { + if (message && Order == BoatOrder.Single) + TillerMan?.Say(1042874, + (NextNavPoint + 1).ToString()); // We have arrived at nav point ~1_POINT_NUM~ , sir. + + if (NextNavPoint + 1 < MapItem.Pins.Count) + { + NextNavPoint++; + + if (Order == BoatOrder.Course) + { + if (message) + TillerMan?.Say(1042875, + (NextNavPoint + 1).ToString()); // Heading to nav point ~1_POINT_NUM~, sir. + + return true; + } + + return false; + } + + NextNavPoint = -1; + + if (message && Order == BoatOrder.Course) + TillerMan?.Say(502515); // The course is completed, sir. + + return false; + } + + if (dir == Left || dir == BackwardLeft || dir == Backward) + return Turn(-2, true); + if (dir == Right || dir == BackwardRight) + return Turn(2, true); + + speed = Math.Min(Speed, maxSpeed); + clientSpeed = 0x4; + } + + return Move(dir, speed, clientSpeed, true); + } + + public bool Move(Direction dir, int speed, int clientSpeed, bool message) + { + Map map = Map; + + if (map == null || Deleted || CheckDecay()) + return false; + + if (Anchored) + { + if (message) + TillerMan?.Say(501419); // Ar, the anchor is down sir! + + return false; + } + + int rx = 0, ry = 0; + Direction d = (Direction)(((int)m_Facing + (int)dir) & 0x7); + Movement.Movement.Offset(d, ref rx, ref ry); + + for (int i = 1; i <= speed; ++i) + if (!CanFit(new Point3D(X + i * rx, Y + i * ry, Z), Map, ItemID)) + { + if (i == 1) + { + if (message) + TillerMan?.Say(501424); // Ar, we've stopped sir. + + return false; + } + + speed = i - 1; + break; + } + + int xOffset = speed * rx; + int yOffset = speed * ry; + + int newX = X + xOffset; + int newY = Y + yOffset; + + Rectangle2D[] wrap = GetWrapFor(map); + + for (int i = 0; i < wrap.Length; ++i) + { + Rectangle2D rect = wrap[i]; + + if (rect.Contains(new Point2D(X, Y)) && !rect.Contains(new Point2D(newX, newY))) + { + if (newX < rect.X) + newX = rect.X + rect.Width - 1; + else if (newX >= rect.X + rect.Width) + newX = rect.X; + + if (newY < rect.Y) + newY = rect.Y + rect.Height - 1; + else if (newY >= rect.Y + rect.Height) + newY = rect.Y; + + for (int j = 1; j <= speed; ++j) + if (!CanFit(new Point3D(newX + j * rx, newY + j * ry, Z), Map, ItemID)) + { + if (message) + TillerMan?.Say(501424); // Ar, we've stopped sir. + + return false; + } + + xOffset = newX - X; + yOffset = newY - Y; + } + } + + if (!NewBoatMovement || Math.Abs(xOffset) > 1 || Math.Abs(yOffset) > 1) + { + Teleport(xOffset, yOffset, 0); + } + else + { + List toMove = GetMovingEntities(); + + SafeAdd(TillerMan, toMove); + SafeAdd(Hold, toMove); + SafeAdd(PPlank, toMove); + SafeAdd(SPlank, toMove); + + // Packet must be sent before actual locations are changed + foreach (NetState ns in Map.GetClientsInRange(Location, GetMaxUpdateRange())) + { + Mobile m = ns.Mobile; + + if (ns.HighSeas && m.CanSee(this) && m.InRange(Location, GetUpdateRange(m))) + ns.Send(new MoveBoatHS(m, this, d, clientSpeed, toMove, xOffset, yOffset)); + } + + foreach (IEntity e in toMove) + if (e is Item) + { + Item item = (Item)e; + + item.NoMoveHS = true; + + if (!(item is TillerMan || item is Hold || item is Plank)) + item.Location = new Point3D(item.X + xOffset, item.Y + yOffset, item.Z); + } + else if (e is Mobile) + { + Mobile m = (Mobile)e; + + m.NoMoveHS = true; + m.Location = new Point3D(m.X + xOffset, m.Y + yOffset, m.Z); + } + + NoMoveHS = true; + Location = new Point3D(X + xOffset, Y + yOffset, Z); + + foreach (IEntity e in toMove) + if (e is Item) + ((Item)e).NoMoveHS = false; + else if (e is Mobile) + ((Mobile)e).NoMoveHS = false; + + NoMoveHS = false; + } + + return true; + } + + private static void SafeAdd(Item item, List toMove) + { + if (item != null) + toMove.Add(item); + } + + public void Teleport(int xOffset, int yOffset, int zOffset) + { + List toMove = GetMovingEntities(); + + for (int i = 0; i < toMove.Count; ++i) + { + IEntity e = toMove[i]; + + if (e is Item) + { + Item item = (Item)e; + + item.Location = new Point3D(item.X + xOffset, item.Y + yOffset, item.Z + zOffset); + } + else if (e is Mobile) + { + Mobile m = (Mobile)e; + + m.Location = new Point3D(m.X + xOffset, m.Y + yOffset, m.Z + zOffset); + } + } + + Location = new Point3D(X + xOffset, Y + yOffset, Z + zOffset); + } + + public List GetMovingEntities() + { + List list = new List(); + + Map map = Map; + + if (map == null || map == Map.Internal) + return list; + + MultiComponentList mcl = Components; + + foreach (object o in map.GetObjectsInBounds(new Rectangle2D(X + mcl.Min.X, Y + mcl.Min.Y, mcl.Width, mcl.Height)) + ) + { + if (o == this || o is TillerMan || o is Hold || o is Plank) + continue; + + if (o is Item) + { + Item item = (Item)o; + + if (Contains(item) && item.Visible && item.Z >= Z) + list.Add(item); + } + else if (o is Mobile) + { + Mobile m = (Mobile)o; + + if (Contains(m)) + list.Add(m); + } + } + + return list; + } + + public bool SetFacing(Direction facing) + { + if (Parent != null || Map == null) + return false; + + if (CheckDecay()) + return false; + + if (Map != Map.Internal) + switch (facing) + { + case Direction.North: + if (!CanFit(Location, Map, NorthID)) return false; + break; + case Direction.East: + if (!CanFit(Location, Map, EastID)) return false; + break; + case Direction.South: + if (!CanFit(Location, Map, SouthID)) return false; + break; + case Direction.West: + if (!CanFit(Location, Map, WestID)) return false; + break; + } + + Direction old = m_Facing; + + m_Facing = facing; + + TillerMan?.SetFacing(facing); + + Hold?.SetFacing(facing); + + PPlank?.SetFacing(facing); + + SPlank?.SetFacing(facing); + + List toMove = GetMovingEntities(); + + toMove.Add(PPlank); + toMove.Add(SPlank); + + int xOffset = 0, yOffset = 0; + Movement.Movement.Offset(facing, ref xOffset, ref yOffset); + + if (TillerMan != null) + TillerMan.Location = new Point3D(X + xOffset * TillerManDistance + (facing == Direction.North ? 1 : 0), + Y + yOffset * TillerManDistance, TillerMan.Z); + + if (Hold != null) + Hold.Location = new Point3D(X + xOffset * HoldDistance, Y + yOffset * HoldDistance, Hold.Z); + + int count = (m_Facing - old) & 0x7; + count /= 2; + + for (int i = 0; i < toMove.Count; ++i) + { + IEntity e = toMove[i]; + + if (e is Item) + { + Item item = (Item)e; + + item.Location = Rotate(item.Location, count); + } + else if (e is Mobile) + { + Mobile m = (Mobile)e; + + m.Direction = (m.Direction - old + facing) & Direction.Mask; + m.Location = Rotate(m.Location, count); + } + } + + switch (facing) + { + case Direction.North: + ItemID = NorthID; + break; + case Direction.East: + ItemID = EastID; + break; + case Direction.South: + ItemID = SouthID; + break; + case Direction.West: + ItemID = WestID; + break; + } + + return true; + } + + public static void UpdateAllComponents() + { + for (int i = Boats.Count - 1; i >= 0; --i) + Boats[i].UpdateComponents(); + } + + public static void Initialize() + { + new UpdateAllTimer().Start(); + EventSink.WorldSave += EventSink_WorldSave; + } + + private static void EventSink_WorldSave(WorldSaveEventArgs e) + { + new UpdateAllTimer().Start(); + } + + private class DecayTimer : Timer + { + private BaseBoat m_Boat; + private int m_Count; + + public DecayTimer(BaseBoat boat) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(5.0)) + { + m_Boat = boat; + + Priority = TimerPriority.TwoFiftyMS; + } + + protected override void OnTick() + { + if (m_Count == 5) + { + m_Boat.Delete(); + Stop(); + } + else + { + m_Boat.Location = new Point3D(m_Boat.X, m_Boat.Y, m_Boat.Z - 1); + + m_Boat.TillerMan?.Say(1007168 + m_Count); + + ++m_Count; + } + } + } + + private class TurnTimer : Timer + { + private BaseBoat m_Boat; + private int m_Offset; + + public TurnTimer(BaseBoat boat, int offset) : base(TimeSpan.FromSeconds(0.5)) + { + m_Boat = boat; + m_Offset = offset; + + Priority = TimerPriority.TenMS; + } + + protected override void OnTick() + { + if (!m_Boat.Deleted) + m_Boat.Turn(m_Offset, true); + } + } + + private class MoveTimer : Timer + { + private BaseBoat m_Boat; + + public MoveTimer(BaseBoat boat, TimeSpan interval, bool single) : base(interval, interval, single ? 1 : 0) + { + m_Boat = boat; + Priority = TimerPriority.TwentyFiveMS; + } + + protected override void OnTick() + { + if (!m_Boat.DoMovement(true)) + m_Boat.StopMove(false); + } + } + + public class UpdateAllTimer : Timer + { + public UpdateAllTimer() : base(TimeSpan.FromSeconds(1.0)) + { + } + + protected override void OnTick() + { + UpdateAllComponents(); + } + } + + #region High Seas + + public override bool AllowsRelativeDrop => true; + + /* + * OSI sends the 0xF7 packet instead, holding 0xF3 packets + * for every entity on the boat. Though, the regular 0xF3 + * packets are still being sent as well as entities come + * into sight. Do we really need it? + */ + /* + protected override Packet GetWorldPacketFor( NetState state ) + { + if ( NewBoatMovement && state.HighSeas ) + return new DisplayBoatHS( state.Mobile, this ); + else + return base.GetWorldPacketFor( state ); + } + */ + + public sealed class MoveBoatHS : Packet + { + public MoveBoatHS(Mobile beholder, BaseBoat boat, Direction d, int speed, List ents, int xOffset, + int yOffset) + : base(0xF6) + { + EnsureCapacity(3 + 15 + ents.Count * 10); + + m_Stream.Write(boat.Serial); + m_Stream.Write((byte)speed); + m_Stream.Write((byte)d); + m_Stream.Write((byte)boat.Facing); + m_Stream.Write((short)(boat.X + xOffset)); + m_Stream.Write((short)(boat.Y + yOffset)); + m_Stream.Write((short)boat.Z); + m_Stream.Write((short)0); // count placeholder + + int count = 0; + + foreach (IEntity ent in ents) + { + if (!beholder.CanSee(ent)) + continue; + + m_Stream.Write(ent.Serial); + m_Stream.Write((short)(ent.X + xOffset)); + m_Stream.Write((short)(ent.Y + yOffset)); + m_Stream.Write((short)ent.Z); + ++count; + } + + m_Stream.Seek(16, SeekOrigin.Begin); + m_Stream.Write((short)count); + } + } + + public sealed class DisplayBoatHS : Packet + { + public DisplayBoatHS(Mobile beholder, BaseBoat boat) + : base(0xF7) + { + List ents = boat.GetMovingEntities(); + + SafeAdd(boat.TillerMan, ents); + SafeAdd(boat.Hold, ents); + SafeAdd(boat.PPlank, ents); + SafeAdd(boat.SPlank, ents); + + ents.Add(boat); + + EnsureCapacity(3 + 2 + ents.Count * 26); + + m_Stream.Write((short)0); // count placeholder + + int count = 0; + + foreach (IEntity ent in ents) + { + if (!beholder.CanSee(ent)) + continue; + + // Embedded WorldItemHS packets + m_Stream.Write((byte)0xF3); + m_Stream.Write((short)0x1); + + if (ent is BaseMulti) + { + BaseMulti bm = (BaseMulti)ent; + + m_Stream.Write((byte)0x02); + m_Stream.Write(bm.Serial); + // TODO: Mask no longer needed, merge with Item case? + m_Stream.Write((ushort)(bm.ItemID & 0x3FFF)); + m_Stream.Write((byte)0); + + m_Stream.Write((short)bm.Amount); + m_Stream.Write((short)bm.Amount); + + m_Stream.Write((short)(bm.X & 0x7FFF)); + m_Stream.Write((short)(bm.Y & 0x3FFF)); + m_Stream.Write((sbyte)bm.Z); + + m_Stream.Write((byte)bm.Light); + m_Stream.Write((short)bm.Hue); + m_Stream.Write((byte)bm.GetPacketFlags()); + } + else if (ent is Mobile) + { + Mobile m = (Mobile)ent; + + m_Stream.Write((byte)0x01); + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.Body); + m_Stream.Write((byte)0); + + m_Stream.Write((short)1); + m_Stream.Write((short)1); + + m_Stream.Write((short)(m.X & 0x7FFF)); + m_Stream.Write((short)(m.Y & 0x3FFF)); + m_Stream.Write((sbyte)m.Z); + + m_Stream.Write((byte)m.Direction); + m_Stream.Write((short)m.Hue); + m_Stream.Write((byte)m.GetPacketFlags()); + } + else if (ent is Item) + { + Item item = (Item)ent; + + m_Stream.Write((byte)0x00); + m_Stream.Write(item.Serial); + m_Stream.Write((ushort)(item.ItemID & 0xFFFF)); + m_Stream.Write((byte)0); + + m_Stream.Write((short)item.Amount); + m_Stream.Write((short)item.Amount); + + m_Stream.Write((short)(item.X & 0x7FFF)); + m_Stream.Write((short)(item.Y & 0x3FFF)); + m_Stream.Write((sbyte)item.Z); + + m_Stream.Write((byte)item.Light); + m_Stream.Write((short)item.Hue); + m_Stream.Write((byte)item.GetPacketFlags()); + } + + m_Stream.Write((short)0x00); + ++count; + } + + m_Stream.Seek(3, SeekOrigin.Begin); + m_Stream.Write((short)count); + } + } + + #endregion + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/BaseBoatDeed.cs b/Scripts/Multis/Boats/BaseBoatDeed.cs index c3f744c38..5171d8c27 100644 --- a/Scripts/Multis/Boats/BaseBoatDeed.cs +++ b/Scripts/Multis/Boats/BaseBoatDeed.cs @@ -1,179 +1,177 @@ -using Server.Regions; -using Server.Targeting; using Server.Engines.CannedEvil; using Server.Network; +using Server.Regions; +using Server.Targeting; namespace Server.Multis { - public abstract class BaseBoatDeed : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public int MultiID { get; set; } + public abstract class BaseBoatDeed : Item + { + public BaseBoatDeed(int id, Point3D offset) : base(0x14F2) + { + Weight = 1.0; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Offset { get; set; } + if (!Core.AOS) + LootType = LootType.Newbied; - public BaseBoatDeed( int id, Point3D offset ) : base( 0x14F2 ) - { - Weight = 1.0; + MultiID = id; + Offset = offset; + } - if ( !Core.AOS ) - LootType = LootType.Newbied; + public BaseBoatDeed(Serial serial) : base(serial) + { + } - MultiID = id; - Offset = offset; - } + [CommandProperty(AccessLevel.GameMaster)] + public int MultiID{ get; set; } - public BaseBoatDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Offset{ get; set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public abstract BaseBoat Boat{ get; } - writer.Write( (int) 0 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( MultiID ); - writer.Write( Offset ); - } + writer.Write(0); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(MultiID); + writer.Write(Offset); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 0: - { - MultiID = reader.ReadInt(); - Offset = reader.ReadPoint3D(); + int version = reader.ReadInt(); - break; - } - } + switch (version) + { + case 0: + { + MultiID = reader.ReadInt(); + Offset = reader.ReadPoint3D(); - if ( Weight == 0.0 ) - Weight = 1.0; - } + break; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.AccessLevel < AccessLevel.GameMaster && (from.Map == Map.Ilshenar || from.Map == Map.Malas) ) - { - from.SendLocalizedMessage( 1010567, null, 0x25 ); // You may not place a boat from this location. - } - else - { - if ( Core.SE ) - from.SendLocalizedMessage( 502482 ); // Where do you wish to place the ship? - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502482 ); // Where do you wish to place the ship? + if (Weight == 0.0) + Weight = 1.0; + } - from.Target = new InternalTarget( this ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.AccessLevel < AccessLevel.GameMaster && (from.Map == Map.Ilshenar || from.Map == Map.Malas)) + { + from.SendLocalizedMessage(1010567, null, 0x25); // You may not place a boat from this location. + } + else + { + if (Core.SE) + from.SendLocalizedMessage(502482); // Where do you wish to place the ship? + else + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502482); // Where do you wish to place the ship? - public abstract BaseBoat Boat{ get; } + from.Target = new InternalTarget(this); + } + } - public void OnPlacement( Mobile from, Point3D p ) - { - if ( Deleted ) - { - return; - } + public void OnPlacement(Mobile from, Point3D p) + { + if (Deleted) return; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - Map map = from.Map; + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + Map map = from.Map; - if ( map == null ) - return; + if (map == null) + return; - if ( from.AccessLevel < AccessLevel.GameMaster && (map == Map.Ilshenar || map == Map.Malas) ) - { - from.SendLocalizedMessage( 1043284 ); // A ship can not be created here. - return; - } + if (from.AccessLevel < AccessLevel.GameMaster && (map == Map.Ilshenar || map == Map.Malas)) + { + from.SendLocalizedMessage(1043284); // A ship can not be created here. + return; + } - if ( from.Region.IsPartOf( typeof( HouseRegion ) ) || BaseBoat.FindBoatAt( from, from.Map ) != null ) - { - from.SendLocalizedMessage( 1010568, null, 0x25 ); // You may not place a ship while on another ship or inside a house. - return; - } + if (from.Region.IsPartOf(typeof(HouseRegion)) || BaseBoat.FindBoatAt(from, from.Map) != null) + { + from.SendLocalizedMessage(1010568, null, + 0x25); // You may not place a ship while on another ship or inside a house. + return; + } - BaseBoat boat = Boat; + BaseBoat boat = Boat; - if ( boat == null ) - return; + if (boat == null) + return; - p = new Point3D( p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z ); + p = new Point3D(p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z); - if ( BaseBoat.IsValidLocation( p, map ) && boat.CanFit( p, map, boat.ItemID ) ) - { - Delete(); + if (BaseBoat.IsValidLocation(p, map) && boat.CanFit(p, map, boat.ItemID)) + { + Delete(); - boat.Owner = from; - boat.Anchored = true; + boat.Owner = from; + boat.Anchored = true; - uint keyValue = boat.CreateKeys( from ); + uint keyValue = boat.CreateKeys(from); - if ( boat.PPlank != null ) - boat.PPlank.KeyValue = keyValue; + if (boat.PPlank != null) + boat.PPlank.KeyValue = keyValue; - if ( boat.SPlank != null ) - boat.SPlank.KeyValue = keyValue; + if (boat.SPlank != null) + boat.SPlank.KeyValue = keyValue; - boat.MoveToWorld( p, map ); - } - else - { - boat.Delete(); - from.SendLocalizedMessage( 1043284 ); // A ship can not be created here. - } - } - } + boat.MoveToWorld(p, map); + } + else + { + boat.Delete(); + from.SendLocalizedMessage(1043284); // A ship can not be created here. + } + } + } - private class InternalTarget : MultiTarget - { - private BaseBoatDeed m_Deed; + private class InternalTarget : MultiTarget + { + private BaseBoatDeed m_Deed; - public InternalTarget( BaseBoatDeed deed ) : base( deed.MultiID, deed.Offset ) - { - m_Deed = deed; - } + public InternalTarget(BaseBoatDeed deed) : base(deed.MultiID, deed.Offset) + { + m_Deed = deed; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D ip = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D ip = o as IPoint3D; - if ( ip != null ) - { - if ( ip is Item ) - ip = ((Item)ip).GetWorldTop(); + if (ip != null) + { + if (ip is Item) + ip = ((Item)ip).GetWorldTop(); - Point3D p = new Point3D( ip ); + Point3D p = new Point3D(ip); - Region region = Region.Find( p, from.Map ); + Region region = Region.Find(p, from.Map); - if ( region.IsPartOf( typeof( DungeonRegion ) ) ) - from.SendLocalizedMessage( 502488 ); // You can not place a ship inside a dungeon. - else if ( region.IsPartOf( typeof( HouseRegion ) ) || region.IsPartOf( typeof( ChampionSpawnRegion ) ) ) - from.SendLocalizedMessage( 1042549 ); // A boat may not be placed in this area. - else - m_Deed.OnPlacement( from, p ); - } - } - } - } -} + if (region.IsPartOf(typeof(DungeonRegion))) + from.SendLocalizedMessage(502488); // You can not place a ship inside a dungeon. + else if (region.IsPartOf(typeof(HouseRegion)) || region.IsPartOf(typeof(ChampionSpawnRegion))) + from.SendLocalizedMessage(1042549); // A boat may not be placed in this area. + else + m_Deed.OnPlacement(from, p); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/BaseDockedBoat.cs b/Scripts/Multis/Boats/BaseDockedBoat.cs index 033d6fa35..dbd03d0bc 100644 --- a/Scripts/Multis/Boats/BaseDockedBoat.cs +++ b/Scripts/Multis/Boats/BaseDockedBoat.cs @@ -1,191 +1,196 @@ +using Server.Engines.CannedEvil; using Server.Regions; using Server.Targeting; -using Server.Engines.CannedEvil; namespace Server.Multis { - public abstract class BaseDockedBoat : Item - { - private string m_ShipName; + public abstract class BaseDockedBoat : Item + { + private string m_ShipName; - [CommandProperty( AccessLevel.GameMaster )] - public int MultiID { get; set; } + public BaseDockedBoat(int id, Point3D offset, BaseBoat boat) : base(0x14F4) + { + Weight = 1.0; + LootType = LootType.Blessed; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Offset { get; set; } + MultiID = id; + Offset = offset; - [CommandProperty( AccessLevel.GameMaster )] - public string ShipName{ get => m_ShipName; - set{ m_ShipName = value; InvalidateProperties(); } } + m_ShipName = boat.ShipName; + } - public BaseDockedBoat( int id, Point3D offset, BaseBoat boat ) : base( 0x14F4 ) - { - Weight = 1.0; - LootType = LootType.Blessed; + public BaseDockedBoat(Serial serial) : base(serial) + { + } - MultiID = id; - Offset = offset; + [CommandProperty(AccessLevel.GameMaster)] + public int MultiID{ get; set; } - m_ShipName = boat.ShipName; - } + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Offset{ get; set; } - public BaseDockedBoat( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public string ShipName + { + get => m_ShipName; + set + { + m_ShipName = value; + InvalidateProperties(); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public abstract BaseBoat Boat{ get; } - writer.Write( (int) 1 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( MultiID ); - writer.Write( Offset ); - writer.Write( m_ShipName ); - } + writer.Write(1); // version - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(MultiID); + writer.Write(Offset); + writer.Write(m_ShipName); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - case 0: - { - MultiID = reader.ReadInt(); - Offset = reader.ReadPoint3D(); - m_ShipName = reader.ReadString(); + int version = reader.ReadInt(); - if ( version == 0 ) - reader.ReadUInt(); + switch (version) + { + case 1: + case 0: + { + MultiID = reader.ReadInt(); + Offset = reader.ReadPoint3D(); + m_ShipName = reader.ReadString(); - break; - } - } + if (version == 0) + reader.ReadUInt(); - if ( LootType == LootType.Newbied ) - LootType = LootType.Blessed; + break; + } + } - if ( Weight == 0.0 ) - Weight = 1.0; - } + if (LootType == LootType.Newbied) + LootType = LootType.Blessed; - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - from.SendLocalizedMessage( 502482 ); // Where do you wish to place the ship? + if (Weight == 0.0) + Weight = 1.0; + } - from.Target = new InternalTarget( this ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + from.SendLocalizedMessage(502482); // Where do you wish to place the ship? - public abstract BaseBoat Boat{ get; } + from.Target = new InternalTarget(this); + } + } - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_ShipName != null ) - list.Add( m_ShipName ); - else - base.AddNameProperty( list ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_ShipName != null) + list.Add(m_ShipName); + else + base.AddNameProperty(list); + } - public override void OnSingleClick( Mobile from ) - { - if ( m_ShipName != null ) - LabelTo( from, m_ShipName ); - else - base.OnSingleClick( from ); - } + public override void OnSingleClick(Mobile from) + { + if (m_ShipName != null) + LabelTo(from, m_ShipName); + else + base.OnSingleClick(from); + } - public void OnPlacement( Mobile from, Point3D p ) - { - if ( Deleted ) - { - return; - } + public void OnPlacement(Mobile from, Point3D p) + { + if (Deleted) return; - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else - { - Map map = from.Map; + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else + { + Map map = from.Map; - if ( map == null ) - return; + if (map == null) + return; - BaseBoat boat = Boat; + BaseBoat boat = Boat; - if ( boat == null ) - return; + if (boat == null) + return; - p = new Point3D( p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z ); + p = new Point3D(p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z); - if ( BaseBoat.IsValidLocation( p, map ) && boat.CanFit( p, map, boat.ItemID ) && map != Map.Ilshenar && map != Map.Malas ) - { - Delete(); + if (BaseBoat.IsValidLocation(p, map) && boat.CanFit(p, map, boat.ItemID) && map != Map.Ilshenar && + map != Map.Malas) + { + Delete(); - boat.Owner = from; - boat.Anchored = true; - boat.ShipName = m_ShipName; + boat.Owner = from; + boat.Anchored = true; + boat.ShipName = m_ShipName; - uint keyValue = boat.CreateKeys( from ); + uint keyValue = boat.CreateKeys(from); - if ( boat.PPlank != null ) - boat.PPlank.KeyValue = keyValue; + if (boat.PPlank != null) + boat.PPlank.KeyValue = keyValue; - if ( boat.SPlank != null ) - boat.SPlank.KeyValue = keyValue; + if (boat.SPlank != null) + boat.SPlank.KeyValue = keyValue; - boat.MoveToWorld( p, map ); - } - else - { - boat.Delete(); - from.SendLocalizedMessage( 1043284 ); // A ship can not be created here. - } - } - } + boat.MoveToWorld(p, map); + } + else + { + boat.Delete(); + from.SendLocalizedMessage(1043284); // A ship can not be created here. + } + } + } - private class InternalTarget : MultiTarget - { - private BaseDockedBoat m_Model; + private class InternalTarget : MultiTarget + { + private BaseDockedBoat m_Model; - public InternalTarget( BaseDockedBoat model ) : base( model.MultiID, model.Offset ) - { - m_Model = model; - } + public InternalTarget(BaseDockedBoat model) : base(model.MultiID, model.Offset) + { + m_Model = model; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D ip = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D ip = o as IPoint3D; - if ( ip != null ) - { - if ( ip is Item ) - ip = ((Item)ip).GetWorldTop(); + if (ip != null) + { + if (ip is Item) + ip = ((Item)ip).GetWorldTop(); - Point3D p = new Point3D( ip ); + Point3D p = new Point3D(ip); - Region region = Region.Find( p, from.Map ); + Region region = Region.Find(p, from.Map); - if ( region.IsPartOf( typeof( DungeonRegion ) ) ) - from.SendLocalizedMessage( 502488 ); // You can not place a ship inside a dungeon. - else if ( region.IsPartOf( typeof( HouseRegion ) ) || region.IsPartOf( typeof( ChampionSpawnRegion ) ) ) - from.SendLocalizedMessage( 1042549 ); // A boat may not be placed in this area. - else - m_Model.OnPlacement( from, p ); - } - } - } - } -} + if (region.IsPartOf(typeof(DungeonRegion))) + from.SendLocalizedMessage(502488); // You can not place a ship inside a dungeon. + else if (region.IsPartOf(typeof(HouseRegion)) || region.IsPartOf(typeof(ChampionSpawnRegion))) + from.SendLocalizedMessage(1042549); // A boat may not be placed in this area. + else + m_Model.OnPlacement(from, p); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/ConfirmDryDockGump.cs b/Scripts/Multis/Boats/ConfirmDryDockGump.cs index b462949b6..31d2a7330 100644 --- a/Scripts/Multis/Boats/ConfirmDryDockGump.cs +++ b/Scripts/Multis/Boats/ConfirmDryDockGump.cs @@ -3,36 +3,36 @@ using Server.Network; namespace Server.Multis { - public class ConfirmDryDockGump : Gump - { - private Mobile m_From; - private BaseBoat m_Boat; + public class ConfirmDryDockGump : Gump + { + private BaseBoat m_Boat; + private Mobile m_From; - public ConfirmDryDockGump( Mobile from, BaseBoat boat ) : base( 150, 200 ) - { - m_From = from; - m_Boat = boat; + public ConfirmDryDockGump(Mobile from, BaseBoat boat) : base(150, 200) + { + m_From = from; + m_Boat = boat; - m_From.CloseGump( typeof( ConfirmDryDockGump ) ); + m_From.CloseGump(typeof(ConfirmDryDockGump)); - AddPage( 0 ); + AddPage(0); - AddBackground( 0, 0, 220, 170, 5054 ); - AddBackground( 10, 10, 200, 150, 3000 ); + AddBackground(0, 0, 220, 170, 5054); + AddBackground(10, 10, 200, 150, 3000); - AddHtmlLocalized( 20, 20, 180, 80, 1018319, true, false ); // Do you wish to dry dock this boat? + AddHtmlLocalized(20, 20, 180, 80, 1018319, true, false); // Do you wish to dry dock this boat? - AddHtmlLocalized( 55, 100, 140, 25, 1011011, false, false ); // CONTINUE - AddButton( 20, 100, 4005, 4007, 2, GumpButtonType.Reply, 0 ); + AddHtmlLocalized(55, 100, 140, 25, 1011011, false, false); // CONTINUE + AddButton(20, 100, 4005, 4007, 2, GumpButtonType.Reply, 0); - AddHtmlLocalized( 55, 125, 140, 25, 1011012, false, false ); // CANCEL - AddButton( 20, 125, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - } + AddHtmlLocalized(55, 125, 140, 25, 1011012, false, false); // CANCEL + AddButton(20, 125, 4005, 4007, 1, GumpButtonType.Reply, 0); + } - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID == 2 ) - m_Boat.EndDryDock( m_From ); - } - } + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID == 2) + m_Boat.EndDryDock(m_From); + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Boats/Hold.cs b/Scripts/Multis/Boats/Hold.cs index a39551852..ea685542b 100644 --- a/Scripts/Multis/Boats/Hold.cs +++ b/Scripts/Multis/Boats/Hold.cs @@ -3,115 +3,117 @@ using Server.Network; namespace Server.Items { - public class Hold : Container - { - private BaseBoat m_Boat; + public class Hold : Container + { + private BaseBoat m_Boat; - public Hold( BaseBoat boat ) : base( 0x3EAE ) - { - m_Boat = boat; - Movable = false; - } + public Hold(BaseBoat boat) : base(0x3EAE) + { + m_Boat = boat; + Movable = false; + } - public Hold( Serial serial ) : base( serial ) - { - } + public Hold(Serial serial) : base(serial) + { + } - public void SetFacing( Direction dir ) - { - switch ( dir ) - { - case Direction.East: ItemID = 0x3E65; break; - case Direction.West: ItemID = 0x3E93; break; - case Direction.North: ItemID = 0x3EAE; break; - case Direction.South: ItemID = 0x3EB9; break; - } - } + public override bool IsDecoContainer => false; - public override bool OnDragDrop( Mobile from, Item item ) - { - if ( m_Boat == null || !m_Boat.Contains( from ) || m_Boat.IsMoving ) - return false; + public void SetFacing(Direction dir) + { + switch (dir) + { + case Direction.East: + ItemID = 0x3E65; + break; + case Direction.West: + ItemID = 0x3E93; + break; + case Direction.North: + ItemID = 0x3EAE; + break; + case Direction.South: + ItemID = 0x3EB9; + break; + } + } - return base.OnDragDrop( from, item ); - } + public override bool OnDragDrop(Mobile from, Item item) + { + if (m_Boat == null || !m_Boat.Contains(from) || m_Boat.IsMoving) + return false; - public override bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( m_Boat == null || !m_Boat.Contains( from ) || m_Boat.IsMoving ) - return false; + return base.OnDragDrop(from, item); + } - return base.OnDragDropInto( from, item, p ); - } + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (m_Boat == null || !m_Boat.Contains(from) || m_Boat.IsMoving) + return false; - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( item != this && (m_Boat == null || !m_Boat.Contains( from ) || m_Boat.IsMoving) ) - return false; + return base.OnDragDropInto(from, item, p); + } - return base.CheckItemUse( from, item ); - } + public override bool CheckItemUse(Mobile from, Item item) + { + if (item != this && (m_Boat == null || !m_Boat.Contains(from) || m_Boat.IsMoving)) + return false; - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( m_Boat == null || !m_Boat.Contains( from ) || m_Boat.IsMoving ) - return false; + return base.CheckItemUse(from, item); + } - return base.CheckLift( from, item, ref reject ); - } + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (m_Boat == null || !m_Boat.Contains(from) || m_Boat.IsMoving) + return false; - public override void OnAfterDelete() - { - m_Boat?.Delete(); - } + return base.CheckLift(from, item, ref reject); + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_Boat == null || !m_Boat.Contains( from ) ) - { - m_Boat.TillerMan?.Say( 502490 ); // You must be on the ship to open the hold. - } - else if ( m_Boat.IsMoving ) - { - m_Boat.TillerMan?.Say( 502491 ); // I can not open the hold while the ship is moving. - } - else - { - base.OnDoubleClick( from ); - } - } + public override void OnAfterDelete() + { + m_Boat?.Delete(); + } - public override bool IsDecoContainer => false; + public override void OnDoubleClick(Mobile from) + { + if (m_Boat == null || !m_Boat.Contains(from)) + m_Boat.TillerMan?.Say(502490); // You must be on the ship to open the hold. + else if (m_Boat.IsMoving) + m_Boat.TillerMan?.Say(502491); // I can not open the hold while the ship is moving. + else + base.OnDoubleClick(from); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); + writer.Write(0); - writer.Write( m_Boat ); - } + writer.Write(m_Boat); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Boat = reader.ReadItem() as BaseBoat; + switch (version) + { + case 0: + { + m_Boat = reader.ReadItem() as BaseBoat; - if ( m_Boat == null || Parent != null ) - Delete(); + if (m_Boat == null || Parent != null) + Delete(); - Movable = false; + Movable = false; - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Boats/LargeBoat.cs b/Scripts/Multis/Boats/LargeBoat.cs index 625c2959f..5a3e40898 100644 --- a/Scripts/Multis/Boats/LargeBoat.cs +++ b/Scripts/Multis/Boats/LargeBoat.cs @@ -1,99 +1,99 @@ namespace Server.Multis { - public class LargeBoat : BaseBoat - { - public override int NorthID => 0x10; - public override int EastID => 0x11; - public override int SouthID => 0x12; - public override int WestID => 0x13; + public class LargeBoat : BaseBoat + { + [Constructible] + public LargeBoat() + { + } - public override int HoldDistance => 5; - public override int TillerManDistance => -5; + public LargeBoat(Serial serial) : base(serial) + { + } - public override Point2D StarboardOffset => new Point2D( 2, -1 ); - public override Point2D PortOffset => new Point2D( -2, -1 ); + public override int NorthID => 0x10; + public override int EastID => 0x11; + public override int SouthID => 0x12; + public override int WestID => 0x13; - public override Point3D MarkOffset => new Point3D( 0, 0, 3 ); + public override int HoldDistance => 5; + public override int TillerManDistance => -5; - public override BaseDockedBoat DockedBoat => new LargeDockedBoat( this ); + public override Point2D StarboardOffset => new Point2D(2, -1); + public override Point2D PortOffset => new Point2D(-2, -1); - [Constructible] - public LargeBoat() - { - } + public override Point3D MarkOffset => new Point3D(0, 0, 3); - public LargeBoat( Serial serial ) : base( serial ) - { - } + public override BaseDockedBoat DockedBoat => new LargeDockedBoat(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class LargeBoatDeed : BaseBoatDeed - { - public override int LabelNumber => 1041209; // large ship deed - public override BaseBoat Boat => new LargeBoat(); + public class LargeBoatDeed : BaseBoatDeed + { + [Constructible] + public LargeBoatDeed() : base(0x10, new Point3D(0, -1, 0)) + { + } - [Constructible] - public LargeBoatDeed() : base( 0x10, new Point3D( 0, -1, 0 ) ) - { - } + public LargeBoatDeed(Serial serial) : base(serial) + { + } - public LargeBoatDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041209; // large ship deed + public override BaseBoat Boat => new LargeBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class LargeDockedBoat : BaseDockedBoat - { - public override BaseBoat Boat => new LargeBoat(); + public class LargeDockedBoat : BaseDockedBoat + { + public LargeDockedBoat(BaseBoat boat) : base(0x10, new Point3D(0, -1, 0), boat) + { + } - public LargeDockedBoat( BaseBoat boat ) : base( 0x10, new Point3D( 0, -1, 0 ), boat ) - { - } + public LargeDockedBoat(Serial serial) : base(serial) + { + } - public LargeDockedBoat( Serial serial ) : base( serial ) - { - } + public override BaseBoat Boat => new LargeBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } -} + writer.Write(0); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/LargeDragonBoat.cs b/Scripts/Multis/Boats/LargeDragonBoat.cs index 9cf185d63..cdd1b3d2a 100644 --- a/Scripts/Multis/Boats/LargeDragonBoat.cs +++ b/Scripts/Multis/Boats/LargeDragonBoat.cs @@ -1,99 +1,99 @@ namespace Server.Multis { - public class LargeDragonBoat : BaseBoat - { - public override int NorthID => 0x14; - public override int EastID => 0x15; - public override int SouthID => 0x16; - public override int WestID => 0x17; + public class LargeDragonBoat : BaseBoat + { + [Constructible] + public LargeDragonBoat() + { + } - public override int HoldDistance => 5; - public override int TillerManDistance => -5; + public LargeDragonBoat(Serial serial) : base(serial) + { + } - public override Point2D StarboardOffset => new Point2D( 2, -1 ); - public override Point2D PortOffset => new Point2D( -2, -1 ); + public override int NorthID => 0x14; + public override int EastID => 0x15; + public override int SouthID => 0x16; + public override int WestID => 0x17; - public override Point3D MarkOffset => new Point3D( 0, 0, 3 ); + public override int HoldDistance => 5; + public override int TillerManDistance => -5; - public override BaseDockedBoat DockedBoat => new LargeDockedDragonBoat( this ); + public override Point2D StarboardOffset => new Point2D(2, -1); + public override Point2D PortOffset => new Point2D(-2, -1); - [Constructible] - public LargeDragonBoat() - { - } + public override Point3D MarkOffset => new Point3D(0, 0, 3); - public LargeDragonBoat( Serial serial ) : base( serial ) - { - } + public override BaseDockedBoat DockedBoat => new LargeDockedDragonBoat(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class LargeDragonBoatDeed : BaseBoatDeed - { - public override int LabelNumber => 1041210;// large dragon ship deed - public override BaseBoat Boat => new LargeDragonBoat(); + public class LargeDragonBoatDeed : BaseBoatDeed + { + [Constructible] + public LargeDragonBoatDeed() : base(0x14, new Point3D(0, -1, 0)) + { + } - [Constructible] - public LargeDragonBoatDeed() : base( 0x14, new Point3D( 0, -1, 0 ) ) - { - } + public LargeDragonBoatDeed(Serial serial) : base(serial) + { + } - public LargeDragonBoatDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041210; // large dragon ship deed + public override BaseBoat Boat => new LargeDragonBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class LargeDockedDragonBoat : BaseDockedBoat - { - public override BaseBoat Boat => new LargeDragonBoat(); + public class LargeDockedDragonBoat : BaseDockedBoat + { + public LargeDockedDragonBoat(BaseBoat boat) : base(0x14, new Point3D(0, -1, 0), boat) + { + } - public LargeDockedDragonBoat( BaseBoat boat ) : base( 0x14, new Point3D( 0, -1, 0 ), boat ) - { - } + public LargeDockedDragonBoat(Serial serial) : base(serial) + { + } - public LargeDockedDragonBoat( Serial serial ) : base( serial ) - { - } + public override BaseBoat Boat => new LargeDragonBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } -} + writer.Write(0); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/MediumBoat.cs b/Scripts/Multis/Boats/MediumBoat.cs index 6c6c3fd33..0e7f5fdb5 100644 --- a/Scripts/Multis/Boats/MediumBoat.cs +++ b/Scripts/Multis/Boats/MediumBoat.cs @@ -1,99 +1,99 @@ namespace Server.Multis { - public class MediumBoat : BaseBoat - { - public override int NorthID => 0x8; - public override int EastID => 0x9; - public override int SouthID => 0xA; - public override int WestID => 0xB; + public class MediumBoat : BaseBoat + { + [Constructible] + public MediumBoat() + { + } - public override int HoldDistance => 4; - public override int TillerManDistance => -5; + public MediumBoat(Serial serial) : base(serial) + { + } - public override Point2D StarboardOffset => new Point2D( 2, 0 ); - public override Point2D PortOffset => new Point2D( -2, 0 ); + public override int NorthID => 0x8; + public override int EastID => 0x9; + public override int SouthID => 0xA; + public override int WestID => 0xB; - public override Point3D MarkOffset => new Point3D( 0, 1, 3 ); + public override int HoldDistance => 4; + public override int TillerManDistance => -5; - public override BaseDockedBoat DockedBoat => new MediumDockedBoat( this ); + public override Point2D StarboardOffset => new Point2D(2, 0); + public override Point2D PortOffset => new Point2D(-2, 0); - [Constructible] - public MediumBoat() - { - } + public override Point3D MarkOffset => new Point3D(0, 1, 3); - public MediumBoat( Serial serial ) : base( serial ) - { - } + public override BaseDockedBoat DockedBoat => new MediumDockedBoat(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class MediumBoatDeed : BaseBoatDeed - { - public override int LabelNumber => 1041207; // medium ship deed - public override BaseBoat Boat => new MediumBoat(); + public class MediumBoatDeed : BaseBoatDeed + { + [Constructible] + public MediumBoatDeed() : base(0x8, Point3D.Zero) + { + } - [Constructible] - public MediumBoatDeed() : base( 0x8, Point3D.Zero ) - { - } + public MediumBoatDeed(Serial serial) : base(serial) + { + } - public MediumBoatDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041207; // medium ship deed + public override BaseBoat Boat => new MediumBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class MediumDockedBoat : BaseDockedBoat - { - public override BaseBoat Boat => new MediumBoat(); + public class MediumDockedBoat : BaseDockedBoat + { + public MediumDockedBoat(BaseBoat boat) : base(0x8, Point3D.Zero, boat) + { + } - public MediumDockedBoat( BaseBoat boat ) : base( 0x8, Point3D.Zero, boat ) - { - } + public MediumDockedBoat(Serial serial) : base(serial) + { + } - public MediumDockedBoat( Serial serial ) : base( serial ) - { - } + public override BaseBoat Boat => new MediumBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } -} + writer.Write(0); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/MediumDragonBoat.cs b/Scripts/Multis/Boats/MediumDragonBoat.cs index f9a491121..4e716d356 100644 --- a/Scripts/Multis/Boats/MediumDragonBoat.cs +++ b/Scripts/Multis/Boats/MediumDragonBoat.cs @@ -1,99 +1,99 @@ namespace Server.Multis { - public class MediumDragonBoat : BaseBoat - { - public override int NorthID => 0xC; - public override int EastID => 0xD; - public override int SouthID => 0xE; - public override int WestID => 0xF; + public class MediumDragonBoat : BaseBoat + { + [Constructible] + public MediumDragonBoat() + { + } - public override int HoldDistance => 4; - public override int TillerManDistance => -5; + public MediumDragonBoat(Serial serial) : base(serial) + { + } - public override Point2D StarboardOffset => new Point2D( 2, 0 ); - public override Point2D PortOffset => new Point2D( -2, 0 ); + public override int NorthID => 0xC; + public override int EastID => 0xD; + public override int SouthID => 0xE; + public override int WestID => 0xF; - public override Point3D MarkOffset => new Point3D( 0, 1, 3 ); + public override int HoldDistance => 4; + public override int TillerManDistance => -5; - public override BaseDockedBoat DockedBoat => new MediumDockedDragonBoat( this ); + public override Point2D StarboardOffset => new Point2D(2, 0); + public override Point2D PortOffset => new Point2D(-2, 0); - [Constructible] - public MediumDragonBoat() - { - } + public override Point3D MarkOffset => new Point3D(0, 1, 3); - public MediumDragonBoat( Serial serial ) : base( serial ) - { - } + public override BaseDockedBoat DockedBoat => new MediumDockedDragonBoat(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class MediumDragonBoatDeed : BaseBoatDeed - { - public override int LabelNumber => 1041208; // medium dragon ship deed - public override BaseBoat Boat => new MediumDragonBoat(); + public class MediumDragonBoatDeed : BaseBoatDeed + { + [Constructible] + public MediumDragonBoatDeed() : base(0xC, Point3D.Zero) + { + } - [Constructible] - public MediumDragonBoatDeed() : base( 0xC, Point3D.Zero ) - { - } + public MediumDragonBoatDeed(Serial serial) : base(serial) + { + } - public MediumDragonBoatDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041208; // medium dragon ship deed + public override BaseBoat Boat => new MediumDragonBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class MediumDockedDragonBoat : BaseDockedBoat - { - public override BaseBoat Boat => new MediumDragonBoat(); + public class MediumDockedDragonBoat : BaseDockedBoat + { + public MediumDockedDragonBoat(BaseBoat boat) : base(0xC, Point3D.Zero, boat) + { + } - public MediumDockedDragonBoat( BaseBoat boat ) : base( 0xC, Point3D.Zero, boat ) - { - } + public MediumDockedDragonBoat(Serial serial) : base(serial) + { + } - public MediumDockedDragonBoat( Serial serial ) : base( serial ) - { - } + public override BaseBoat Boat => new MediumDragonBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } -} + writer.Write(0); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/Plank.cs b/Scripts/Multis/Boats/Plank.cs index 164e54e4d..e6f93013f 100644 --- a/Scripts/Multis/Boats/Plank.cs +++ b/Scripts/Multis/Boats/Plank.cs @@ -1,301 +1,337 @@ using System; using Server.Factions; using Server.Multis; +using Server.Network; +using Server.Spells; namespace Server.Items { - public enum PlankSide{ Port, Starboard } + public enum PlankSide + { + Port, + Starboard + } - public class Plank : Item, ILockable - { - private Timer m_CloseTimer; + public class Plank : Item, ILockable + { + private Timer m_CloseTimer; - public Plank( BaseBoat boat, PlankSide side, uint keyValue ) : base( 0x3EB1 + (int)side ) - { - Boat = boat; - Side = side; - KeyValue = keyValue; - Locked = true; + public Plank(BaseBoat boat, PlankSide side, uint keyValue) : base(0x3EB1 + (int)side) + { + Boat = boat; + Side = side; + KeyValue = keyValue; + Locked = true; - Movable = false; - } + Movable = false; + } - public Plank( Serial serial ) : base(serial) - { - } + public Plank(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + [CommandProperty(AccessLevel.GameMaster)] + public BaseBoat Boat{ get; set; } - writer.Write( (int) 0 );//version + [CommandProperty(AccessLevel.GameMaster)] + public PlankSide Side{ get; set; } - writer.Write( Boat ); - writer.Write( (int) Side ); - writer.Write( Locked ); - writer.Write( KeyValue ); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool IsOpen => ItemID == 0x3ED5 || ItemID == 0x3ED4 || ItemID == 0x3E84 || ItemID == 0x3E89; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + [CommandProperty(AccessLevel.GameMaster)] + public bool Starboard => Side == PlankSide.Starboard; - int version = reader.ReadInt(); + [CommandProperty(AccessLevel.GameMaster)] + public bool Locked{ get; set; } - switch ( version ) - { - case 0: - { - Boat = reader.ReadItem() as BaseBoat; - Side = (PlankSide) reader.ReadInt(); - Locked = reader.ReadBool(); - KeyValue = reader.ReadUInt(); + [CommandProperty(AccessLevel.GameMaster)] + public uint KeyValue{ get; set; } - if ( Boat == null ) - Delete(); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - break; - } - } + writer.Write(0); //version - if ( IsOpen ) - { - m_CloseTimer = new CloseTimer( this ); - m_CloseTimer.Start(); - } - } + writer.Write(Boat); + writer.Write((int)Side); + writer.Write(Locked); + writer.Write(KeyValue); + } - [CommandProperty( AccessLevel.GameMaster )] - public BaseBoat Boat { get; set; } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - [CommandProperty( AccessLevel.GameMaster )] - public PlankSide Side { get; set; } + int version = reader.ReadInt(); - [CommandProperty( AccessLevel.GameMaster )] - public bool Locked { get; set; } + switch (version) + { + case 0: + { + Boat = reader.ReadItem() as BaseBoat; + Side = (PlankSide)reader.ReadInt(); + Locked = reader.ReadBool(); + KeyValue = reader.ReadUInt(); - [CommandProperty( AccessLevel.GameMaster )] - public uint KeyValue { get; set; } + if (Boat == null) + Delete(); - [CommandProperty( AccessLevel.GameMaster )] - public bool IsOpen => ( ItemID == 0x3ED5 || ItemID == 0x3ED4 || ItemID == 0x3E84 || ItemID == 0x3E89 ); + break; + } + } - [CommandProperty( AccessLevel.GameMaster )] - public bool Starboard => ( Side == PlankSide.Starboard ); + if (IsOpen) + { + m_CloseTimer = new CloseTimer(this); + m_CloseTimer.Start(); + } + } - public void SetFacing( Direction dir ) - { - if ( IsOpen ) - { - switch ( dir ) - { - case Direction.North: ItemID = Starboard ? 0x3ED4 : 0x3ED5; break; - case Direction.East: ItemID = Starboard ? 0x3E84 : 0x3E89; break; - case Direction.South: ItemID = Starboard ? 0x3ED5 : 0x3ED4; break; - case Direction.West: ItemID = Starboard ? 0x3E89 : 0x3E84; break; - } - } - else - { - switch ( dir ) - { - case Direction.North: ItemID = Starboard ? 0x3EB2 : 0x3EB1; break; - case Direction.East: ItemID = Starboard ? 0x3E85 : 0x3E8A; break; - case Direction.South: ItemID = Starboard ? 0x3EB1 : 0x3EB2; break; - case Direction.West: ItemID = Starboard ? 0x3E8A : 0x3E85; break; - } - } - } + public void SetFacing(Direction dir) + { + if (IsOpen) + switch (dir) + { + case Direction.North: + ItemID = Starboard ? 0x3ED4 : 0x3ED5; + break; + case Direction.East: + ItemID = Starboard ? 0x3E84 : 0x3E89; + break; + case Direction.South: + ItemID = Starboard ? 0x3ED5 : 0x3ED4; + break; + case Direction.West: + ItemID = Starboard ? 0x3E89 : 0x3E84; + break; + } + else + switch (dir) + { + case Direction.North: + ItemID = Starboard ? 0x3EB2 : 0x3EB1; + break; + case Direction.East: + ItemID = Starboard ? 0x3E85 : 0x3E8A; + break; + case Direction.South: + ItemID = Starboard ? 0x3EB1 : 0x3EB2; + break; + case Direction.West: + ItemID = Starboard ? 0x3E8A : 0x3E85; + break; + } + } - public void Open() - { - if ( IsOpen || Deleted ) - return; + public void Open() + { + if (IsOpen || Deleted) + return; - m_CloseTimer?.Stop(); + m_CloseTimer?.Stop(); - m_CloseTimer = new CloseTimer( this ); - m_CloseTimer.Start(); + m_CloseTimer = new CloseTimer(this); + m_CloseTimer.Start(); - switch ( ItemID ) - { - case 0x3EB1: ItemID = 0x3ED5; break; - case 0x3E8A: ItemID = 0x3E89; break; - case 0x3EB2: ItemID = 0x3ED4; break; - case 0x3E85: ItemID = 0x3E84; break; - } + switch (ItemID) + { + case 0x3EB1: + ItemID = 0x3ED5; + break; + case 0x3E8A: + ItemID = 0x3E89; + break; + case 0x3EB2: + ItemID = 0x3ED4; + break; + case 0x3E85: + ItemID = 0x3E84; + break; + } - Boat?.Refresh(); - } + Boat?.Refresh(); + } - public override bool OnMoveOver( Mobile from ) - { - if ( IsOpen ) - { - if ( from is BaseFactionGuard ) - return false; + public override bool OnMoveOver(Mobile from) + { + if (IsOpen) + { + if (from is BaseFactionGuard) + return false; - if ( (from.Direction & Direction.Running) != 0 || (Boat != null && !Boat.Contains( from )) ) - return true; + if ((from.Direction & Direction.Running) != 0 || Boat != null && !Boat.Contains(from)) + return true; - Map map = Map; + Map map = Map; - if ( map == null ) - return false; + if (map == null) + return false; - int rx = 0, ry = 0; + int rx = 0, ry = 0; - if ( ItemID == 0x3ED4 ) - rx = 1; - else if ( ItemID == 0x3ED5 ) - rx = -1; - else if ( ItemID == 0x3E84 ) - ry = 1; - else if ( ItemID == 0x3E89 ) - ry = -1; + if (ItemID == 0x3ED4) + rx = 1; + else if (ItemID == 0x3ED5) + rx = -1; + else if (ItemID == 0x3E84) + ry = 1; + else if (ItemID == 0x3E89) + ry = -1; - for ( int i = 1; i <= 6; ++i ) - { - int x = X + (i*rx); - int y = Y + (i*ry); - int z; + for (int i = 1; i <= 6; ++i) + { + int x = X + i * rx; + int y = Y + i * ry; + int z; - for ( int j = -8; j <= 8; ++j ) - { - z = from.Z + j; + for (int j = -8; j <= 8; ++j) + { + z = from.Z + j; - if ( map.CanFit( x, y, z, 16, false, false ) && !Spells.SpellHelper.CheckMulti( new Point3D( x, y, z ), map ) && !Region.Find( new Point3D( x, y, z ), map ).IsPartOf( typeof( StrongholdRegion ) ) ) - { - if ( i == 1 && j >= -2 && j <= 2 ) - return true; + if (map.CanFit(x, y, z, 16, false, false) && !SpellHelper.CheckMulti(new Point3D(x, y, z), map) && + !Region.Find(new Point3D(x, y, z), map).IsPartOf(typeof(StrongholdRegion))) + { + if (i == 1 && j >= -2 && j <= 2) + return true; - from.Location = new Point3D( x, y, z ); - return false; - } - } + from.Location = new Point3D(x, y, z); + return false; + } + } - z = map.GetAverageZ( x, y ); + z = map.GetAverageZ(x, y); - if ( map.CanFit( x, y, z, 16, false, false ) && !Spells.SpellHelper.CheckMulti( new Point3D( x, y, z ), map ) && !Region.Find( new Point3D( x, y, z ), map ).IsPartOf( typeof( StrongholdRegion ) ) ) - { - if ( i == 1 ) - return true; + if (map.CanFit(x, y, z, 16, false, false) && !SpellHelper.CheckMulti(new Point3D(x, y, z), map) && + !Region.Find(new Point3D(x, y, z), map).IsPartOf(typeof(StrongholdRegion))) + { + if (i == 1) + return true; - from.Location = new Point3D( x, y, z ); - return false; - } - } + from.Location = new Point3D(x, y, z); + return false; + } + } - return true; - } + return true; + } - return false; - } + return false; + } - public bool CanClose() - { - Map map = Map; + public bool CanClose() + { + Map map = Map; - if ( map == null || Deleted ) - return false; + if (map == null || Deleted) + return false; - foreach ( object o in GetObjectsInRange( 0 ) ) - { - if ( o != this ) - return false; - } + foreach (object o in GetObjectsInRange(0)) + if (o != this) + return false; - return true; - } + return true; + } - public void Close() - { - if ( !IsOpen || !CanClose() || Deleted ) - return; + public void Close() + { + if (!IsOpen || !CanClose() || Deleted) + return; - m_CloseTimer?.Stop(); + m_CloseTimer?.Stop(); - m_CloseTimer = null; + m_CloseTimer = null; - switch ( ItemID ) - { - case 0x3ED5: ItemID = 0x3EB1; break; - case 0x3E89: ItemID = 0x3E8A; break; - case 0x3ED4: ItemID = 0x3EB2; break; - case 0x3E84: ItemID = 0x3E85; break; - } + switch (ItemID) + { + case 0x3ED5: + ItemID = 0x3EB1; + break; + case 0x3E89: + ItemID = 0x3E8A; + break; + case 0x3ED4: + ItemID = 0x3EB2; + break; + case 0x3E84: + ItemID = 0x3E85; + break; + } - Boat?.Refresh(); - } + Boat?.Refresh(); + } - public override void OnDoubleClickDead( Mobile from ) - { - OnDoubleClick( from ); - } + public override void OnDoubleClickDead(Mobile from) + { + OnDoubleClick(from); + } - public override void OnDoubleClick( Mobile from ) - { - if ( Boat == null ) - return; + public override void OnDoubleClick(Mobile from) + { + if (Boat == null) + return; - if ( from.InRange( GetWorldLocation(), 8 ) ) - { - if ( Boat.Contains( from ) ) - { - if ( IsOpen ) - Close(); - else - Open(); - } - else - { - if ( !IsOpen ) - { - if ( !Locked ) - { - Open(); - } - else if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x00, 502502 ); // That is locked but your godly powers allow access - Open(); - } - else - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x00, 502503 ); // That is locked. - } - } - else if ( !Locked ) - { - from.Location = new Point3D( X, Y, Z + 3 ); - } - else if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x00, 502502 ); // That is locked but your godly powers allow access - from.Location = new Point3D( X, Y, Z + 3 ); - } - else - { - from.LocalOverheadMessage( Network.MessageType.Regular, 0x00, 502503 ); // That is locked. - } - } - } - } + if (from.InRange(GetWorldLocation(), 8)) + { + if (Boat.Contains(from)) + { + if (IsOpen) + Close(); + else + Open(); + } + else + { + if (!IsOpen) + { + if (!Locked) + { + Open(); + } + else if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.LocalOverheadMessage(MessageType.Regular, 0x00, + 502502); // That is locked but your godly powers allow access + Open(); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x00, 502503); // That is locked. + } + } + else if (!Locked) + { + from.Location = new Point3D(X, Y, Z + 3); + } + else if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.LocalOverheadMessage(MessageType.Regular, 0x00, + 502502); // That is locked but your godly powers allow access + from.Location = new Point3D(X, Y, Z + 3); + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x00, 502503); // That is locked. + } + } + } + } - private class CloseTimer : Timer - { - private Plank m_Plank; + private class CloseTimer : Timer + { + private Plank m_Plank; - public CloseTimer( Plank plank ) : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_Plank = plank; - Priority = TimerPriority.OneSecond; - } + public CloseTimer(Plank plank) : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + m_Plank = plank; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - m_Plank.Close(); - } - } - } + protected override void OnTick() + { + m_Plank.Close(); + } + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Boats/RenameBoatPrompt.cs b/Scripts/Multis/Boats/RenameBoatPrompt.cs index a1075e2c2..0eefb902e 100644 --- a/Scripts/Multis/Boats/RenameBoatPrompt.cs +++ b/Scripts/Multis/Boats/RenameBoatPrompt.cs @@ -2,18 +2,18 @@ using Server.Prompts; namespace Server.Multis { - public class RenameBoatPrompt : Prompt - { - private BaseBoat m_Boat; + public class RenameBoatPrompt : Prompt + { + private BaseBoat m_Boat; - public RenameBoatPrompt( BaseBoat boat ) - { - m_Boat = boat; - } + public RenameBoatPrompt(BaseBoat boat) + { + m_Boat = boat; + } - public override void OnResponse( Mobile from, string text ) - { - m_Boat.EndRename( from, text ); - } - } + public override void OnResponse(Mobile from, string text) + { + m_Boat.EndRename(from, text); + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Boats/SmallBoat.cs b/Scripts/Multis/Boats/SmallBoat.cs index 1b0d31591..42ff7b455 100644 --- a/Scripts/Multis/Boats/SmallBoat.cs +++ b/Scripts/Multis/Boats/SmallBoat.cs @@ -1,99 +1,99 @@ namespace Server.Multis { - public class SmallBoat : BaseBoat - { - public override int NorthID => 0x0; - public override int EastID => 0x1; - public override int SouthID => 0x2; - public override int WestID => 0x3; + public class SmallBoat : BaseBoat + { + [Constructible] + public SmallBoat() + { + } - public override int HoldDistance => 4; - public override int TillerManDistance => -4; + public SmallBoat(Serial serial) : base(serial) + { + } - public override Point2D StarboardOffset => new Point2D( 2, 0 ); - public override Point2D PortOffset => new Point2D( -2, 0 ); + public override int NorthID => 0x0; + public override int EastID => 0x1; + public override int SouthID => 0x2; + public override int WestID => 0x3; - public override Point3D MarkOffset => new Point3D( 0, 1, 3 ); + public override int HoldDistance => 4; + public override int TillerManDistance => -4; - public override BaseDockedBoat DockedBoat => new SmallDockedBoat( this ); + public override Point2D StarboardOffset => new Point2D(2, 0); + public override Point2D PortOffset => new Point2D(-2, 0); - [Constructible] - public SmallBoat() - { - } + public override Point3D MarkOffset => new Point3D(0, 1, 3); - public SmallBoat( Serial serial ) : base( serial ) - { - } + public override BaseDockedBoat DockedBoat => new SmallDockedBoat(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class SmallBoatDeed : BaseBoatDeed - { - public override int LabelNumber => 1041205; // small ship deed - public override BaseBoat Boat => new SmallBoat(); + public class SmallBoatDeed : BaseBoatDeed + { + [Constructible] + public SmallBoatDeed() : base(0x0, Point3D.Zero) + { + } - [Constructible] - public SmallBoatDeed() : base( 0x0, Point3D.Zero ) - { - } + public SmallBoatDeed(Serial serial) : base(serial) + { + } - public SmallBoatDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041205; // small ship deed + public override BaseBoat Boat => new SmallBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class SmallDockedBoat : BaseDockedBoat - { - public override BaseBoat Boat => new SmallBoat(); + public class SmallDockedBoat : BaseDockedBoat + { + public SmallDockedBoat(BaseBoat boat) : base(0x0, Point3D.Zero, boat) + { + } - public SmallDockedBoat( BaseBoat boat ) : base( 0x0, Point3D.Zero, boat ) - { - } + public SmallDockedBoat(Serial serial) : base(serial) + { + } - public SmallDockedBoat( Serial serial ) : base( serial ) - { - } + public override BaseBoat Boat => new SmallBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } -} + writer.Write(0); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/SmallDragonBoat.cs b/Scripts/Multis/Boats/SmallDragonBoat.cs index e3abc891f..73b367d9e 100644 --- a/Scripts/Multis/Boats/SmallDragonBoat.cs +++ b/Scripts/Multis/Boats/SmallDragonBoat.cs @@ -1,99 +1,99 @@ namespace Server.Multis { - public class SmallDragonBoat : BaseBoat - { - public override int NorthID => 0x4; - public override int EastID => 0x5; - public override int SouthID => 0x6; - public override int WestID => 0x7; + public class SmallDragonBoat : BaseBoat + { + [Constructible] + public SmallDragonBoat() + { + } - public override int HoldDistance => 4; - public override int TillerManDistance => -4; + public SmallDragonBoat(Serial serial) : base(serial) + { + } - public override Point2D StarboardOffset => new Point2D( 2, 0 ); - public override Point2D PortOffset => new Point2D( -2, 0 ); + public override int NorthID => 0x4; + public override int EastID => 0x5; + public override int SouthID => 0x6; + public override int WestID => 0x7; - public override Point3D MarkOffset => new Point3D( 0, 1, 3 ); + public override int HoldDistance => 4; + public override int TillerManDistance => -4; - public override BaseDockedBoat DockedBoat => new SmallDockedDragonBoat( this ); + public override Point2D StarboardOffset => new Point2D(2, 0); + public override Point2D PortOffset => new Point2D(-2, 0); - [Constructible] - public SmallDragonBoat() - { - } + public override Point3D MarkOffset => new Point3D(0, 1, 3); - public SmallDragonBoat( Serial serial ) : base( serial ) - { - } + public override BaseDockedBoat DockedBoat => new SmallDockedDragonBoat(this); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class SmallDragonBoatDeed : BaseBoatDeed - { - public override int LabelNumber => 1041206; // small dragon ship deed - public override BaseBoat Boat => new SmallDragonBoat(); + public class SmallDragonBoatDeed : BaseBoatDeed + { + [Constructible] + public SmallDragonBoatDeed() : base(0x4, Point3D.Zero) + { + } - [Constructible] - public SmallDragonBoatDeed() : base( 0x4, Point3D.Zero ) - { - } + public SmallDragonBoatDeed(Serial serial) : base(serial) + { + } - public SmallDragonBoatDeed( Serial serial ) : base( serial ) - { - } + public override int LabelNumber => 1041206; // small dragon ship deed + public override BaseBoat Boat => new SmallDragonBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } + writer.Write(0); + } + } - public class SmallDockedDragonBoat : BaseDockedBoat - { - public override BaseBoat Boat => new SmallDragonBoat(); + public class SmallDockedDragonBoat : BaseDockedBoat + { + public SmallDockedDragonBoat(BaseBoat boat) : base(0x4, Point3D.Zero, boat) + { + } - public SmallDockedDragonBoat( BaseBoat boat ) : base( 0x4, Point3D.Zero, boat ) - { - } + public SmallDockedDragonBoat(Serial serial) : base(serial) + { + } - public SmallDockedDragonBoat( Serial serial ) : base( serial ) - { - } + public override BaseBoat Boat => new SmallDragonBoat(); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); - } - } -} + writer.Write(0); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/Strandedness.cs b/Scripts/Multis/Boats/Strandedness.cs index a44ac7869..f01c4b3c0 100644 --- a/Scripts/Multis/Boats/Strandedness.cs +++ b/Scripts/Multis/Boats/Strandedness.cs @@ -1,179 +1,178 @@ namespace Server.Misc { - public class Strandedness - { - private static Point2D[] m_Felucca = { - new Point2D( 2528, 3568 ), new Point2D( 2376, 3400 ), new Point2D( 2528, 3896 ), - new Point2D( 2168, 3904 ), new Point2D( 1136, 3416 ), new Point2D( 1432, 3648 ), - new Point2D( 1416, 4000 ), new Point2D( 4512, 3936 ), new Point2D( 4440, 3120 ), - new Point2D( 4192, 3672 ), new Point2D( 4720, 3472 ), new Point2D( 3744, 2768 ), - new Point2D( 3480, 2432 ), new Point2D( 3560, 2136 ), new Point2D( 3792, 2112 ), - new Point2D( 2800, 2296 ), new Point2D( 2736, 2016 ), new Point2D( 4576, 1456 ), - new Point2D( 4680, 1152 ), new Point2D( 4304, 1104 ), new Point2D( 4496, 984 ), - new Point2D( 4248, 696 ), new Point2D( 4040, 616 ), new Point2D( 3896, 248 ), - new Point2D( 4176, 384 ), new Point2D( 3672, 1104 ), new Point2D( 3520, 1152 ), - new Point2D( 3720, 1360 ), new Point2D( 2184, 2152 ), new Point2D( 1952, 2088 ), - new Point2D( 2056, 1936 ), new Point2D( 1720, 1992 ), new Point2D( 472, 2064 ), - new Point2D( 656, 2096 ), new Point2D( 3008, 3592 ), new Point2D( 2784, 3472 ), - new Point2D( 5456, 2400 ), new Point2D( 5976, 2424 ), new Point2D( 5328, 3112 ), - new Point2D( 5792, 3152 ), new Point2D( 2120, 3616 ), new Point2D( 2136, 3128 ), - new Point2D( 1632, 3528 ), new Point2D( 1328, 3160 ), new Point2D( 1072, 3136 ), - new Point2D( 1128, 2976 ), new Point2D( 960, 2576 ), new Point2D( 752, 1832 ), - new Point2D( 184, 1488 ), new Point2D( 592, 1440 ), new Point2D( 368, 1216 ), - new Point2D( 232, 752 ), new Point2D( 696, 744 ), new Point2D( 304, 1000 ), - new Point2D( 840, 376 ), new Point2D( 1192, 624 ), new Point2D( 1200, 192 ), - new Point2D( 1512, 240 ), new Point2D( 1336, 456 ), new Point2D( 1536, 648 ), - new Point2D( 1104, 952 ), new Point2D( 1864, 264 ), new Point2D( 2136, 200 ), - new Point2D( 2160, 528 ), new Point2D( 1904, 512 ), new Point2D( 2240, 784 ), - new Point2D( 2536, 776 ), new Point2D( 2488, 216 ), new Point2D( 2336, 72 ), - new Point2D( 2648, 288 ), new Point2D( 2680, 576 ), new Point2D( 2896, 88 ), - new Point2D( 2840, 344 ), new Point2D( 3136, 72 ), new Point2D( 2968, 520 ), - new Point2D( 3192, 328 ), new Point2D( 3448, 208 ), new Point2D( 3432, 608 ), - new Point2D( 3184, 752 ), new Point2D( 2800, 704 ), new Point2D( 2768, 1016 ), - new Point2D( 2448, 1232 ), new Point2D( 2272, 920 ), new Point2D( 2072, 1080 ), - new Point2D( 2048, 1264 ), new Point2D( 1808, 1528 ), new Point2D( 1496, 1880 ), - new Point2D( 1656, 2168 ), new Point2D( 2096, 2320 ), new Point2D( 1816, 2528 ), - new Point2D( 1840, 2640 ), new Point2D( 1928, 2952 ), new Point2D( 2120, 2712 ) - }; + public class Strandedness + { + private static Point2D[] m_Felucca = + { + new Point2D(2528, 3568), new Point2D(2376, 3400), new Point2D(2528, 3896), + new Point2D(2168, 3904), new Point2D(1136, 3416), new Point2D(1432, 3648), + new Point2D(1416, 4000), new Point2D(4512, 3936), new Point2D(4440, 3120), + new Point2D(4192, 3672), new Point2D(4720, 3472), new Point2D(3744, 2768), + new Point2D(3480, 2432), new Point2D(3560, 2136), new Point2D(3792, 2112), + new Point2D(2800, 2296), new Point2D(2736, 2016), new Point2D(4576, 1456), + new Point2D(4680, 1152), new Point2D(4304, 1104), new Point2D(4496, 984), + new Point2D(4248, 696), new Point2D(4040, 616), new Point2D(3896, 248), + new Point2D(4176, 384), new Point2D(3672, 1104), new Point2D(3520, 1152), + new Point2D(3720, 1360), new Point2D(2184, 2152), new Point2D(1952, 2088), + new Point2D(2056, 1936), new Point2D(1720, 1992), new Point2D(472, 2064), + new Point2D(656, 2096), new Point2D(3008, 3592), new Point2D(2784, 3472), + new Point2D(5456, 2400), new Point2D(5976, 2424), new Point2D(5328, 3112), + new Point2D(5792, 3152), new Point2D(2120, 3616), new Point2D(2136, 3128), + new Point2D(1632, 3528), new Point2D(1328, 3160), new Point2D(1072, 3136), + new Point2D(1128, 2976), new Point2D(960, 2576), new Point2D(752, 1832), + new Point2D(184, 1488), new Point2D(592, 1440), new Point2D(368, 1216), + new Point2D(232, 752), new Point2D(696, 744), new Point2D(304, 1000), + new Point2D(840, 376), new Point2D(1192, 624), new Point2D(1200, 192), + new Point2D(1512, 240), new Point2D(1336, 456), new Point2D(1536, 648), + new Point2D(1104, 952), new Point2D(1864, 264), new Point2D(2136, 200), + new Point2D(2160, 528), new Point2D(1904, 512), new Point2D(2240, 784), + new Point2D(2536, 776), new Point2D(2488, 216), new Point2D(2336, 72), + new Point2D(2648, 288), new Point2D(2680, 576), new Point2D(2896, 88), + new Point2D(2840, 344), new Point2D(3136, 72), new Point2D(2968, 520), + new Point2D(3192, 328), new Point2D(3448, 208), new Point2D(3432, 608), + new Point2D(3184, 752), new Point2D(2800, 704), new Point2D(2768, 1016), + new Point2D(2448, 1232), new Point2D(2272, 920), new Point2D(2072, 1080), + new Point2D(2048, 1264), new Point2D(1808, 1528), new Point2D(1496, 1880), + new Point2D(1656, 2168), new Point2D(2096, 2320), new Point2D(1816, 2528), + new Point2D(1840, 2640), new Point2D(1928, 2952), new Point2D(2120, 2712) + }; - private static Point2D[] m_Trammel = m_Felucca; + private static Point2D[] m_Trammel = m_Felucca; - private static Point2D[] m_Ilshenar = { - new Point2D( 1252, 1180 ), new Point2D( 1562, 1090 ), new Point2D( 1444, 1016 ), - new Point2D( 1324, 968 ), new Point2D( 1418, 806 ), new Point2D( 1722, 874 ), - new Point2D( 1456, 684 ), new Point2D( 1036, 866 ), new Point2D( 612, 476 ), - new Point2D( 1476, 372 ), new Point2D( 762, 472 ), new Point2D( 812, 1162 ), - new Point2D( 1422, 1144 ), new Point2D( 1254, 1066 ), new Point2D( 1598, 870 ), - new Point2D( 1358, 866 ), new Point2D( 510, 302 ), new Point2D( 510, 392 ) - }; + private static Point2D[] m_Ilshenar = + { + new Point2D(1252, 1180), new Point2D(1562, 1090), new Point2D(1444, 1016), + new Point2D(1324, 968), new Point2D(1418, 806), new Point2D(1722, 874), + new Point2D(1456, 684), new Point2D(1036, 866), new Point2D(612, 476), + new Point2D(1476, 372), new Point2D(762, 472), new Point2D(812, 1162), + new Point2D(1422, 1144), new Point2D(1254, 1066), new Point2D(1598, 870), + new Point2D(1358, 866), new Point2D(510, 302), new Point2D(510, 392) + }; - private static Point2D[] m_Tokuno = { - //Makoto-Jima - new Point2D( 837, 1351 ), new Point2D( 941, 1241 ), new Point2D( 959, 1185 ), - new Point2D( 923, 1091 ), new Point2D( 904, 983 ), new Point2D( 845, 944 ), - new Point2D( 829, 896 ), new Point2D( 794, 852 ), new Point2D( 766, 821 ), - new Point2D( 695, 814 ), new Point2D( 576, 835 ), new Point2D( 518, 840 ), - new Point2D( 519, 902 ), new Point2D( 502, 950 ), new Point2D( 503, 1045 ), - new Point2D( 547, 1131 ), new Point2D( 518, 1204 ), new Point2D( 506, 1243 ), - new Point2D( 526, 1271 ), new Point2D( 562, 1295 ), new Point2D( 616, 1335 ), - new Point2D( 789, 1347 ), new Point2D( 712, 1359 ), + private static Point2D[] m_Tokuno = + { + //Makoto-Jima + new Point2D(837, 1351), new Point2D(941, 1241), new Point2D(959, 1185), + new Point2D(923, 1091), new Point2D(904, 983), new Point2D(845, 944), + new Point2D(829, 896), new Point2D(794, 852), new Point2D(766, 821), + new Point2D(695, 814), new Point2D(576, 835), new Point2D(518, 840), + new Point2D(519, 902), new Point2D(502, 950), new Point2D(503, 1045), + new Point2D(547, 1131), new Point2D(518, 1204), new Point2D(506, 1243), + new Point2D(526, 1271), new Point2D(562, 1295), new Point2D(616, 1335), + new Point2D(789, 1347), new Point2D(712, 1359), - //Homare-Jima - new Point2D( 202, 498 ), new Point2D( 116, 600 ), new Point2D( 107, 699 ), - new Point2D( 162, 799 ), new Point2D( 158, 889 ), new Point2D( 169, 989 ), - new Point2D( 194, 1101 ), new Point2D( 250, 1163 ), new Point2D( 295, 1176 ), - new Point2D( 280, 1194 ), new Point2D( 286, 1102 ), new Point2D( 250, 1000 ), - new Point2D( 260, 906 ), new Point2D( 360, 838 ), new Point2D( 389, 763 ), - new Point2D( 415, 662 ), new Point2D( 500, 597 ), new Point2D( 570, 572 ), - new Point2D( 631, 577 ), new Point2D( 692, 500 ), new Point2D( 723, 445 ), - new Point2D( 672, 379 ), new Point2D( 626, 332 ), new Point2D( 494, 291 ), - new Point2D( 371, 336 ), new Point2D( 324, 334 ), new Point2D( 270, 362 ), + //Homare-Jima + new Point2D(202, 498), new Point2D(116, 600), new Point2D(107, 699), + new Point2D(162, 799), new Point2D(158, 889), new Point2D(169, 989), + new Point2D(194, 1101), new Point2D(250, 1163), new Point2D(295, 1176), + new Point2D(280, 1194), new Point2D(286, 1102), new Point2D(250, 1000), + new Point2D(260, 906), new Point2D(360, 838), new Point2D(389, 763), + new Point2D(415, 662), new Point2D(500, 597), new Point2D(570, 572), + new Point2D(631, 577), new Point2D(692, 500), new Point2D(723, 445), + new Point2D(672, 379), new Point2D(626, 332), new Point2D(494, 291), + new Point2D(371, 336), new Point2D(324, 334), new Point2D(270, 362), - //Isamu-Jima - new Point2D( 1240, 1076 ), new Point2D( 1189, 1115 ), new Point2D( 1046, 1039 ), - new Point2D( 1025, 885 ), new Point2D( 907, 809 ), new Point2D( 840, 506 ), - new Point2D( 799, 396 ), new Point2D( 720, 258 ), new Point2D( 744, 158 ), - new Point2D( 904, 37 ), new Point2D( 974, 91 ), new Point2D( 1020, 187 ), - new Point2D( 1035, 288 ), new Point2D( 1104, 395 ), new Point2D( 1215, 462 ), - new Point2D( 1275, 488 ), new Point2D( 1348, 611 ), new Point2D( 1363, 739 ), - new Point2D( 1364, 765 ), new Point2D( 1364, 876 ), new Point2D( 1300, 936 ), - new Point2D( 1240, 1003 ) + //Isamu-Jima + new Point2D(1240, 1076), new Point2D(1189, 1115), new Point2D(1046, 1039), + new Point2D(1025, 885), new Point2D(907, 809), new Point2D(840, 506), + new Point2D(799, 396), new Point2D(720, 258), new Point2D(744, 158), + new Point2D(904, 37), new Point2D(974, 91), new Point2D(1020, 187), + new Point2D(1035, 288), new Point2D(1104, 395), new Point2D(1215, 462), + new Point2D(1275, 488), new Point2D(1348, 611), new Point2D(1363, 739), + new Point2D(1364, 765), new Point2D(1364, 876), new Point2D(1300, 936), + new Point2D(1240, 1003) + }; + public static void Initialize() + { + EventSink.Login += EventSink_Login; + } - }; + private static bool IsStranded(Mobile from) + { + Map map = from.Map; - public static void Initialize() - { - EventSink.Login += EventSink_Login; - } + if (map == null) + return false; - private static bool IsStranded( Mobile from ) - { - Map map = from.Map; + object surface = map.GetTopSurface(from.Location); - if ( map == null ) - return false; + if (surface is LandTile) + { + int id = ((LandTile)surface).ID; - object surface = map.GetTopSurface( from.Location ); + return id >= 168 && id <= 171 + || id >= 310 && id <= 311; + } - if ( surface is LandTile ) { - int id = ((LandTile)surface).ID; + if (surface is StaticTile) + { + int id = ((StaticTile)surface).ID; - return (id >= 168 && id <= 171) - || (id >= 310 && id <= 311); - } + return id >= 0x1796 && id <= 0x17B2; + } - if ( surface is StaticTile ) { - int id = ((StaticTile)surface).ID; + return false; + } - return (id >= 0x1796 && id <= 0x17B2); - } + public static void EventSink_Login(LoginEventArgs e) + { + Mobile from = e.Mobile; - return false; - } + if (!IsStranded(from)) + return; - public static void EventSink_Login( LoginEventArgs e ) - { - Mobile from = e.Mobile; + Map map = from.Map; - if ( !IsStranded( from ) ) - return; + Point2D[] list; - Map map = from.Map; + if (map == Map.Felucca) + list = m_Felucca; + else if (map == Map.Trammel) + list = m_Trammel; + else if (map == Map.Ilshenar) + list = m_Ilshenar; + else if (map == Map.Tokuno) + list = m_Tokuno; + else + return; - Point2D[] list; + Point2D p = Point2D.Zero; + double pdist = double.MaxValue; - if ( map == Map.Felucca ) - list = m_Felucca; - else if ( map == Map.Trammel ) - list = m_Trammel; - else if ( map == Map.Ilshenar ) - list = m_Ilshenar; - else if ( map == Map.Tokuno ) - list = m_Tokuno; - else - return; + for (int i = 0; i < list.Length; ++i) + { + double dist = from.GetDistanceToSqrt(list[i]); - Point2D p = Point2D.Zero; - double pdist = double.MaxValue; + if (dist < pdist) + { + p = list[i]; + pdist = dist; + } + } - for ( int i = 0; i < list.Length; ++i ) - { - double dist = from.GetDistanceToSqrt( list[i] ); + int x = p.X, y = p.Y; + int z; + bool canFit = false; - if ( dist < pdist ) - { - p = list[i]; - pdist = dist; - } - } + z = map.GetAverageZ(x, y); + canFit = map.CanSpawnMobile(x, y, z); - int x = p.X, y = p.Y; - int z; - bool canFit = false; + for (int i = 1; !canFit && i <= 40; i += 2) + for (int xo = -1; !canFit && xo <= 1; ++xo) + for (int yo = -1; !canFit && yo <= 1; ++yo) + { + if (xo == 0 && yo == 0) + continue; - z = map.GetAverageZ( x, y ); - canFit = map.CanSpawnMobile( x, y, z ); + x = p.X + xo * i; + y = p.Y + yo * i; + z = map.GetAverageZ(x, y); + canFit = map.CanSpawnMobile(x, y, z); + } - for ( int i = 1; !canFit && i <= 40; i += 2 ) - { - for ( int xo = -1; !canFit && xo <= 1; ++xo ) - { - for ( int yo = -1; !canFit && yo <= 1; ++yo ) - { - if ( xo == 0 && yo == 0 ) - continue; - - x = p.X + (xo * i); - y = p.Y + (yo * i); - z = map.GetAverageZ( x, y ); - canFit = map.CanSpawnMobile( x, y, z ); - } - } - } - - if ( canFit ) - from.Location = new Point3D( x, y, z ); - } - } -} + if (canFit) + from.Location = new Point3D(x, y, z); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Boats/TillerMan.cs b/Scripts/Multis/Boats/TillerMan.cs index 049b01d80..1e9cb3014 100644 --- a/Scripts/Multis/Boats/TillerMan.cs +++ b/Scripts/Multis/Boats/TillerMan.cs @@ -3,116 +3,120 @@ using Server.Network; namespace Server.Items { - public class TillerMan : Item - { - private BaseBoat m_Boat; + public class TillerMan : Item + { + private BaseBoat m_Boat; - public TillerMan( BaseBoat boat ) : base( 0x3E4E ) - { - m_Boat = boat; - Movable = false; - } + public TillerMan(BaseBoat boat) : base(0x3E4E) + { + m_Boat = boat; + Movable = false; + } - public TillerMan( Serial serial ) : base(serial) - { - } + public TillerMan(Serial serial) : base(serial) + { + } - public void SetFacing( Direction dir ) - { - switch ( dir ) - { - case Direction.South: ItemID = 0x3E4B; break; - case Direction.North: ItemID = 0x3E4E; break; - case Direction.West: ItemID = 0x3E50; break; - case Direction.East: ItemID = 0x3E55; break; - } - } + public void SetFacing(Direction dir) + { + switch (dir) + { + case Direction.South: + ItemID = 0x3E4B; + break; + case Direction.North: + ItemID = 0x3E4E; + break; + case Direction.West: + ItemID = 0x3E50; + break; + case Direction.East: + ItemID = 0x3E55; + break; + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( m_Boat.Status ); - } + list.Add(m_Boat.Status); + } - public void Say( int number ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, number ); - } + public void Say(int number) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, number); + } - public void Say( int number, string args ) - { - PublicOverheadMessage( MessageType.Regular, 0x3B2, number, args ); - } + public void Say(int number, string args) + { + PublicOverheadMessage(MessageType.Regular, 0x3B2, number, args); + } - public override void AddNameProperty( ObjectPropertyList list ) - { - if ( m_Boat?.ShipName != null ) - list.Add( 1042884, m_Boat.ShipName ); // the tiller man of the ~1_SHIP_NAME~ - else - base.AddNameProperty( list ); - } + public override void AddNameProperty(ObjectPropertyList list) + { + if (m_Boat?.ShipName != null) + list.Add(1042884, m_Boat.ShipName); // the tiller man of the ~1_SHIP_NAME~ + else + base.AddNameProperty(list); + } - public override void OnSingleClick( Mobile from ) - { - if ( m_Boat?.ShipName != null ) - LabelTo( from, 1042884, m_Boat.ShipName ); // the tiller man of the ~1_SHIP_NAME~ - else - base.OnSingleClick( from ); - } + public override void OnSingleClick(Mobile from) + { + if (m_Boat?.ShipName != null) + LabelTo(from, 1042884, m_Boat.ShipName); // the tiller man of the ~1_SHIP_NAME~ + else + base.OnSingleClick(from); + } - public override void OnDoubleClick( Mobile from ) - { - if ( m_Boat != null && m_Boat.Contains( from ) ) - m_Boat.BeginRename( from ); - else - { - m_Boat?.BeginDryDock( from ); - } - } + public override void OnDoubleClick(Mobile from) + { + if (m_Boat != null && m_Boat.Contains(from)) + m_Boat.BeginRename(from); + else + m_Boat?.BeginDryDock(from); + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( dropped is MapItem && m_Boat != null && m_Boat.CanCommand( from ) && m_Boat.Contains( from ) ) - { - m_Boat.AssociateMap( (MapItem) dropped ); - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (dropped is MapItem && m_Boat != null && m_Boat.CanCommand(from) && m_Boat.Contains(from)) + m_Boat.AssociateMap((MapItem)dropped); - return false; - } + return false; + } - public override void OnAfterDelete() - { - m_Boat?.Delete(); - } + public override void OnAfterDelete() + { + m_Boat?.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 );//version + writer.Write(0); //version - writer.Write( m_Boat ); - } + writer.Write(m_Boat); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Boat = reader.ReadItem() as BaseBoat; + switch (version) + { + case 0: + { + m_Boat = reader.ReadItem() as BaseBoat; - if ( m_Boat == null ) - Delete(); + if (m_Boat == null) + Delete(); - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Camps/BankerCamp.cs b/Scripts/Multis/Camps/BankerCamp.cs index 95ad849da..1bbdff154 100644 --- a/Scripts/Multis/Camps/BankerCamp.cs +++ b/Scripts/Multis/Camps/BankerCamp.cs @@ -3,45 +3,45 @@ using Server.Mobiles; namespace Server.Multis { - public class BankerCamp : BaseCamp - { - [Constructible] - public BankerCamp() : base( 0x1F6 ) - { - } + public class BankerCamp : BaseCamp + { + [Constructible] + public BankerCamp() : base(0x1F6) + { + } - public override void AddComponents() - { - BaseDoor west, east; + public BankerCamp(Serial serial) : base(serial) + { + } - AddItem( west = new LightWoodGate( DoorFacing.WestCW ), -4, 4, 7 ); - AddItem( east = new LightWoodGate( DoorFacing.EastCCW ), -3, 4, 7 ); + public override void AddComponents() + { + BaseDoor west, east; - west.Link = east; - east.Link = west; + AddItem(west = new LightWoodGate(DoorFacing.WestCW), -4, 4, 7); + AddItem(east = new LightWoodGate(DoorFacing.EastCCW), -3, 4, 7); - AddItem( new Sign( SignType.Bank, SignFacing.West ), -5, 5, -4 ); + west.Link = east; + east.Link = west; - AddMobile( new Banker(), 4, -4, 3, 7 ); - AddMobile( new Banker(), 5, 4, -2, 0 ); - } + AddItem(new Sign(SignType.Bank, SignFacing.West), -5, 5, -4); - public BankerCamp( Serial serial ) : base( serial ) - { - } + AddMobile(new Banker(), 4, -4, 3, 7); + AddMobile(new Banker(), 5, 4, -2, 0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Camps/BaseCamp.cs b/Scripts/Multis/Camps/BaseCamp.cs index 70c1a1f5c..6a8b0a727 100644 --- a/Scripts/Multis/Camps/BaseCamp.cs +++ b/Scripts/Multis/Camps/BaseCamp.cs @@ -1,201 +1,201 @@ using System; +using System.Collections.Generic; using Server.Items; using Server.Mobiles; -using System.Collections.Generic; namespace Server.Multis { - public abstract class BaseCamp : BaseMulti - { - private List m_Items; - private List m_Mobiles; - private DateTime m_DecayTime; - private Timer m_DecayTimer; - private TimeSpan m_DecayDelay; + public abstract class BaseCamp : BaseMulti + { + private TimeSpan m_DecayDelay; + private DateTime m_DecayTime; + private Timer m_DecayTimer; + private List m_Items; + private List m_Mobiles; - public virtual int EventRange => 10; + public BaseCamp(int multiID) : base(multiID) + { + m_Items = new List(); + m_Mobiles = new List(); + m_DecayDelay = TimeSpan.FromMinutes(30.0); + RefreshDecay(true); - public virtual TimeSpan DecayDelay - { - get => m_DecayDelay; - set - { - m_DecayDelay = value; - RefreshDecay( true ); - } - } + Timer.DelayCall(TimeSpan.Zero, CheckAddComponents); + } - public BaseCamp( int multiID ) : base( multiID ) - { - m_Items = new List(); - m_Mobiles = new List(); - m_DecayDelay = TimeSpan.FromMinutes( 30.0 ); - RefreshDecay( true ); + public BaseCamp(Serial serial) : base(serial) + { + } - Timer.DelayCall( TimeSpan.Zero, CheckAddComponents ); - } + public virtual int EventRange => 10; - public void CheckAddComponents() - { - if ( Deleted ) - return; + public virtual TimeSpan DecayDelay + { + get => m_DecayDelay; + set + { + m_DecayDelay = value; + RefreshDecay(true); + } + } - AddComponents(); - } + public override bool HandlesOnMovement => true; - public virtual void AddComponents() - { - } + public void CheckAddComponents() + { + if (Deleted) + return; - public virtual void RefreshDecay( bool setDecayTime ) - { - if ( Deleted ) - return; + AddComponents(); + } - m_DecayTimer?.Stop(); + public virtual void AddComponents() + { + } - if ( setDecayTime ) - m_DecayTime = DateTime.UtcNow + DecayDelay; + public virtual void RefreshDecay(bool setDecayTime) + { + if (Deleted) + return; - m_DecayTimer = Timer.DelayCall( DecayDelay, Delete ); - } + m_DecayTimer?.Stop(); - public virtual void AddItem( Item item, int xOffset, int yOffset, int zOffset ) - { - m_Items.Add( item ); + if (setDecayTime) + m_DecayTime = DateTime.UtcNow + DecayDelay; - int zavg = Map.GetAverageZ(X + xOffset, Y + yOffset); - item.MoveToWorld( new Point3D( X + xOffset, Y + yOffset, zavg + zOffset ), Map ); - } + m_DecayTimer = Timer.DelayCall(DecayDelay, Delete); + } - public virtual void AddMobile( Mobile m, int wanderRange, int xOffset, int yOffset, int zOffset ) - { - m_Mobiles.Add(m); + public virtual void AddItem(Item item, int xOffset, int yOffset, int zOffset) + { + m_Items.Add(item); - int zavg = Map.GetAverageZ(X + xOffset, Y + yOffset); - Point3D loc = new Point3D(X + xOffset, Y + yOffset, zavg + zOffset); - BaseCreature bc = m as BaseCreature; + int zavg = Map.GetAverageZ(X + xOffset, Y + yOffset); + item.MoveToWorld(new Point3D(X + xOffset, Y + yOffset, zavg + zOffset), Map); + } - if ( bc != null ) - { - bc.RangeHome = wanderRange; - bc.Home = loc; - } + public virtual void AddMobile(Mobile m, int wanderRange, int xOffset, int yOffset, int zOffset) + { + m_Mobiles.Add(m); - if ( m is BaseVendor || m is Banker ) - m.Direction = Direction.South; + int zavg = Map.GetAverageZ(X + xOffset, Y + yOffset); + Point3D loc = new Point3D(X + xOffset, Y + yOffset, zavg + zOffset); + BaseCreature bc = m as BaseCreature; - m.MoveToWorld( loc, Map ); - } + if (bc != null) + { + bc.RangeHome = wanderRange; + bc.Home = loc; + } - public virtual void OnEnter( Mobile m ) - { - RefreshDecay( true ); - } + if (m is BaseVendor || m is Banker) + m.Direction = Direction.South; - public virtual void OnExit( Mobile m ) - { - RefreshDecay( true ); - } + m.MoveToWorld(loc, Map); + } - public override bool HandlesOnMovement => true; + public virtual void OnEnter(Mobile m) + { + RefreshDecay(true); + } - public override void OnMovement( Mobile m, Point3D oldLocation ) - { - bool inOldRange = Utility.InRange( oldLocation, Location, EventRange ); - bool inNewRange = Utility.InRange( m.Location, Location, EventRange ); + public virtual void OnExit(Mobile m) + { + RefreshDecay(true); + } - if ( inNewRange && !inOldRange ) - OnEnter( m ); - else if ( inOldRange && !inNewRange ) - OnExit( m ); - } + public override void OnMovement(Mobile m, Point3D oldLocation) + { + bool inOldRange = Utility.InRange(oldLocation, Location, EventRange); + bool inNewRange = Utility.InRange(m.Location, Location, EventRange); - public override void OnAfterDelete() - { - base.OnAfterDelete(); + if (inNewRange && !inOldRange) + OnEnter(m); + else if (inOldRange && !inNewRange) + OnExit(m); + } - for ( int i = 0; i < m_Items.Count; ++i ) - m_Items[i].Delete(); + public override void OnAfterDelete() + { + base.OnAfterDelete(); - for ( int i = 0; i < m_Mobiles.Count; ++i ) - { - BaseCreature bc = (BaseCreature)m_Mobiles[i]; + for (int i = 0; i < m_Items.Count; ++i) + m_Items[i].Delete(); - if ( bc.IsPrisoner == false ) - m_Mobiles[i].Delete(); - else if ( m_Mobiles[i].CantWalk == true ) - m_Mobiles[i].Delete(); - } + for (int i = 0; i < m_Mobiles.Count; ++i) + { + BaseCreature bc = (BaseCreature)m_Mobiles[i]; - m_Items.Clear(); - m_Mobiles.Clear(); - } + if (bc.IsPrisoner == false) + m_Mobiles[i].Delete(); + else if (m_Mobiles[i].CantWalk) + m_Mobiles[i].Delete(); + } - public BaseCamp( Serial serial ) : base( serial ) - { - } + m_Items.Clear(); + m_Mobiles.Clear(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Items, true ); - writer.Write( m_Mobiles, true ); - writer.WriteDeltaTime( m_DecayTime ); - } + writer.Write(m_Items, true); + writer.Write(m_Mobiles, true); + writer.WriteDeltaTime(m_DecayTime); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Items = reader.ReadStrongItemList(); - m_Mobiles = reader.ReadStrongMobileList(); - m_DecayTime = reader.ReadDeltaTime(); + switch (version) + { + case 0: + { + m_Items = reader.ReadStrongItemList(); + m_Mobiles = reader.ReadStrongMobileList(); + m_DecayTime = reader.ReadDeltaTime(); - RefreshDecay( false ); + RefreshDecay(false); - break; - } - } - } - } + break; + } + } + } + } - public class LockableBarrel : LockableContainer - { - [Constructible] - public LockableBarrel() : base(0xE77) - { - Weight = 1.0; - } + public class LockableBarrel : LockableContainer + { + [Constructible] + public LockableBarrel() : base(0xE77) + { + Weight = 1.0; + } - public LockableBarrel(Serial serial) : base(serial) - { - } + public LockableBarrel(Serial serial) : base(serial) + { + } - public override void Serialize(GenericWriter writer) - { - base.Serialize(writer); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write((int)0); // version - } + writer.Write(0); // version + } - public override void Deserialize(GenericReader reader) - { - base.Deserialize(reader); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if (Weight == 8.0) - Weight = 1.0; - } - } -} + if (Weight == 8.0) + Weight = 1.0; + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Camps/BrigandCamp.cs b/Scripts/Multis/Camps/BrigandCamp.cs index 7ee1fa3af..9fb3a22d1 100644 --- a/Scripts/Multis/Camps/BrigandCamp.cs +++ b/Scripts/Multis/Camps/BrigandCamp.cs @@ -3,192 +3,230 @@ using Server.Items; using Server.Mobiles; namespace Server.Multis -{ - public class BrigandCamp : BaseCamp - { - public virtual Mobile Brigands => new Brigand(); - public virtual Mobile Executioners => new Executioner(); +{ + public class BrigandCamp : BaseCamp + { + private Mobile m_Prisoner; - private Mobile m_Prisoner; - - [Constructible] - public BrigandCamp() : base( 0x10EE ) // dummy garbage at center - { - } + [Constructible] + public BrigandCamp() : base(0x10EE) // dummy garbage at center + { + } - public override void AddComponents() - { - BaseCreature bc; - //BaseEscortable be; + public BrigandCamp(Serial serial) : base(serial) + { + } - Visible = false; - DecayDelay = TimeSpan.FromMinutes( 5.0 ); + public virtual Mobile Brigands => new Brigand(); + public virtual Mobile Executioners => new Executioner(); - AddItem(new Static(0x10ee), 0, 0, 0); - AddItem(new Static(0xfac), 0, 7, 0); - - switch ( Utility.Random( 3 ) ) - { - case 0: - { - AddItem( new Item( 0xDE3 ), 0, 7, 0 ); // Campfire - AddItem( new Item( 0x974 ), 0, 7, 1 ); // Cauldron - break; - } - case 1: - { - AddItem( new Item( 0x1E95 ), 0, 7, 1 ); // Rabbit on a spit - break; - } - default: - { - AddItem( new Item( 0x1E94 ), 0, 7, 1 ); // Chicken on a spit - break; - } - } + public override void AddComponents() + { + BaseCreature bc; + //BaseEscortable be; - AddCampChests(); - - for ( int i = 0; i < 4; i ++ ) - { - AddMobile( Brigands, 6, Utility.RandomMinMax( -7, 7 ), Utility.RandomMinMax( -7, 7 ), 0 ); - } - - switch ( Utility.Random( 2 ) ) - { - case 0: m_Prisoner = new Noble(); break; - default: m_Prisoner = new SeekerOfAdventure(); break; - } - - //be = (BaseEscortable)m_Prisoner; - //be.m_Captive = true; - - bc = (BaseCreature)m_Prisoner; - bc.IsPrisoner = true; - bc.CantWalk = true; - - m_Prisoner.YellHue = Utility.RandomList( 0x57, 0x67, 0x77, 0x87, 0x117 ); - AddMobile( m_Prisoner, 2, Utility.RandomMinMax( -2, 2 ), Utility.RandomMinMax( -2, 2 ), 0 ); - } + Visible = false; + DecayDelay = TimeSpan.FromMinutes(5.0); - private void AddCampChests() - { - LockableContainer chest = null; + AddItem(new Static(0x10ee), 0, 0, 0); + AddItem(new Static(0xfac), 0, 7, 0); - switch (Utility.Random(3)) - { - case 0: chest = new MetalChest(); break; - case 1: chest = new MetalGoldenChest(); break; - default: chest = new WoodenChest(); break; - } + switch (Utility.Random(3)) + { + case 0: + { + AddItem(new Item(0xDE3), 0, 7, 0); // Campfire + AddItem(new Item(0x974), 0, 7, 1); // Cauldron + break; + } + case 1: + { + AddItem(new Item(0x1E95), 0, 7, 1); // Rabbit on a spit + break; + } + default: + { + AddItem(new Item(0x1E94), 0, 7, 1); // Chicken on a spit + break; + } + } - chest.LiftOverride = true; + AddCampChests(); - TreasureMapChest.Fill(chest, 1); + for (int i = 0; i < 4; i++) AddMobile(Brigands, 6, Utility.RandomMinMax(-7, 7), Utility.RandomMinMax(-7, 7), 0); - AddItem(chest, -2, -2, 0); + switch (Utility.Random(2)) + { + case 0: + m_Prisoner = new Noble(); + break; + default: + m_Prisoner = new SeekerOfAdventure(); + break; + } - LockableContainer crates = null; + //be = (BaseEscortable)m_Prisoner; + //be.m_Captive = true; - switch (Utility.Random(4)) - { - case 0: crates = new SmallCrate(); break; - case 1: crates = new MediumCrate(); break; - case 2: crates = new LargeCrate(); break; - default: crates = new LockableBarrel(); break; - } + bc = (BaseCreature)m_Prisoner; + bc.IsPrisoner = true; + bc.CantWalk = true; - crates.TrapType = TrapType.ExplosionTrap; - crates.TrapPower = Utility.RandomMinMax(30, 40); - crates.TrapLevel = 2; + m_Prisoner.YellHue = Utility.RandomList(0x57, 0x67, 0x77, 0x87, 0x117); + AddMobile(m_Prisoner, 2, Utility.RandomMinMax(-2, 2), Utility.RandomMinMax(-2, 2), 0); + } - crates.RequiredSkill = 76; - crates.LockLevel = 66; - crates.MaxLockLevel = 116; - crates.Locked = true; + private void AddCampChests() + { + LockableContainer chest = null; - crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); - crates.DropItem(new Arrow(10)); - crates.DropItem(new Bolt(10)); + switch (Utility.Random(3)) + { + case 0: + chest = new MetalChest(); + break; + case 1: + chest = new MetalGoldenChest(); + break; + default: + chest = new WoodenChest(); + break; + } - crates.LiftOverride = true; + chest.LiftOverride = true; - if (Utility.RandomDouble() < 0.8) - { - switch (Utility.Random(4)) - { - case 0: crates.DropItem(new LesserCurePotion()); break; - case 1: crates.DropItem(new LesserExplosionPotion()); break; - case 2: crates.DropItem(new LesserHealPotion()); break; - default: crates.DropItem(new LesserPoisonPotion()); break; - } - } + TreasureMapChest.Fill(chest, 1); - AddItem(crates, 2, 2, 0); - } + AddItem(chest, -2, -2, 0); - // Don't refresh decay timer - public override void OnEnter( Mobile m ) - { - if ( m.Player && m_Prisoner != null && m_Prisoner.CantWalk ) - { - int number; + LockableContainer crates = null; - switch ( Utility.Random( 8 ) ) - { - case 0: number = 502261; break; // HELP! - case 1: number = 502262; break; // Help me! - case 2: number = 502263; break; // Canst thou aid me?! - case 3: number = 502264; break; // Help a poor prisoner! - case 4: number = 502265; break; // Help! Please! - case 5: number = 502266; break; // Aaah! Help me! - case 6: number = 502267; break; // Go and get some help! - default: number = 502268; break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. - } - m_Prisoner.Yell( number ); - } - } + switch (Utility.Random(4)) + { + case 0: + crates = new SmallCrate(); + break; + case 1: + crates = new MediumCrate(); + break; + case 2: + crates = new LargeCrate(); + break; + default: + crates = new LockableBarrel(); + break; + } - // Don't refresh decay timer - public override void OnExit(Mobile m) - { - } + crates.TrapType = TrapType.ExplosionTrap; + crates.TrapPower = Utility.RandomMinMax(30, 40); + crates.TrapLevel = 2; - public BrigandCamp( Serial serial ) : base( serial ) - { - } - - public override void AddItem( Item item, int xOffset, int yOffset, int zOffset ) - { - if ( item != null ) - item.Movable = false; - - base.AddItem( item, xOffset, yOffset, zOffset ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + crates.RequiredSkill = 76; + crates.LockLevel = 66; + crates.MaxLockLevel = 116; + crates.Locked = true; - writer.Write( (int) 0 ); // version + crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); + crates.DropItem(new Arrow(10)); + crates.DropItem(new Bolt(10)); - writer.Write( m_Prisoner ); - } + crates.LiftOverride = true; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + if (Utility.RandomDouble() < 0.8) + switch (Utility.Random(4)) + { + case 0: + crates.DropItem(new LesserCurePotion()); + break; + case 1: + crates.DropItem(new LesserExplosionPotion()); + break; + case 2: + crates.DropItem(new LesserHealPotion()); + break; + default: + crates.DropItem(new LesserPoisonPotion()); + break; + } - int version = reader.ReadInt(); + AddItem(crates, 2, 2, 0); + } - switch ( version ) - { - case 0: - { - m_Prisoner = reader.ReadMobile(); - break; - } - } - } - } -} + // Don't refresh decay timer + public override void OnEnter(Mobile m) + { + if (m.Player && m_Prisoner != null && m_Prisoner.CantWalk) + { + int number; + + switch (Utility.Random(8)) + { + case 0: + number = 502261; + break; // HELP! + case 1: + number = 502262; + break; // Help me! + case 2: + number = 502263; + break; // Canst thou aid me?! + case 3: + number = 502264; + break; // Help a poor prisoner! + case 4: + number = 502265; + break; // Help! Please! + case 5: + number = 502266; + break; // Aaah! Help me! + case 6: + number = 502267; + break; // Go and get some help! + default: + number = 502268; + break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. + } + + m_Prisoner.Yell(number); + } + } + + // Don't refresh decay timer + public override void OnExit(Mobile m) + { + } + + public override void AddItem(Item item, int xOffset, int yOffset, int zOffset) + { + if (item != null) + item.Movable = false; + + base.AddItem(item, xOffset, yOffset, zOffset); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Prisoner); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Prisoner = reader.ReadMobile(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Camps/HealerCamp.cs b/Scripts/Multis/Camps/HealerCamp.cs index 284117a42..c59716e53 100644 --- a/Scripts/Multis/Camps/HealerCamp.cs +++ b/Scripts/Multis/Camps/HealerCamp.cs @@ -3,45 +3,45 @@ using Server.Mobiles; namespace Server.Multis { - public class HealerCamp : BaseCamp - { - [Constructible] - public HealerCamp() : base( 0x1F4 ) - { - } + public class HealerCamp : BaseCamp + { + [Constructible] + public HealerCamp() : base(0x1F4) + { + } - public override void AddComponents() - { - BaseDoor west, east; + public HealerCamp(Serial serial) : base(serial) + { + } - AddItem( west = new LightWoodGate( DoorFacing.WestCW ), -4, 4, 7 ); - AddItem( east = new LightWoodGate( DoorFacing.EastCCW ), -3, 4, 7 ); + public override void AddComponents() + { + BaseDoor west, east; - west.Link = east; - east.Link = west; + AddItem(west = new LightWoodGate(DoorFacing.WestCW), -4, 4, 7); + AddItem(east = new LightWoodGate(DoorFacing.EastCCW), -3, 4, 7); - AddItem( new Sign( SignType.Healer, SignFacing.West ), -5, 5, -4 ); + west.Link = east; + east.Link = west; - AddMobile( new Healer(), 4, -4, 3, 7 ); - AddMobile( new Healer(), 5, 4, -2, 0 ); - } + AddItem(new Sign(SignType.Healer, SignFacing.West), -5, 5, -4); - public HealerCamp( Serial serial ) : base( serial ) - { - } + AddMobile(new Healer(), 4, -4, 3, 7); + AddMobile(new Healer(), 5, 4, -2, 0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Camps/LizardmenCamp.cs b/Scripts/Multis/Camps/LizardmenCamp.cs index 1e965857e..c0cf48779 100644 --- a/Scripts/Multis/Camps/LizardmenCamp.cs +++ b/Scripts/Multis/Camps/LizardmenCamp.cs @@ -3,191 +3,230 @@ using Server.Items; using Server.Mobiles; namespace Server.Multis -{ - public class LizardmenCamp : BaseCamp - { - public virtual Mobile Lizardmen => new Lizardman(); +{ + public class LizardmenCamp : BaseCamp + { + private Mobile m_Prisoner; - private Mobile m_Prisoner; - - [Constructible] - public LizardmenCamp() : base( 0x10EE ) // dummy garbage at center - { - } + [Constructible] + public LizardmenCamp() : base(0x10EE) // dummy garbage at center + { + } - public override void AddComponents() - { - BaseCreature bc; - //BaseEscortable be; + public LizardmenCamp(Serial serial) : base(serial) + { + } - Visible = false; - DecayDelay = TimeSpan.FromMinutes( 5.0 ); - AddItem(new Static(0x10ee), 0, 0, 0); - AddItem(new Static(0xfac), 0, 7, 0); + public virtual Mobile Lizardmen => new Lizardman(); - switch ( Utility.Random( 3 ) ) - { - case 0: - { - AddItem( new Item( 0xDE3 ), 0, 7, 0 ); // Campfire - AddItem( new Item( 0x974 ), 0, 7, 1); // Cauldron - break; - } - case 1: - { - AddItem( new Item( 0x1E95 ), 0, 7, 1); // Rabbit on a spit - break; - } - default: - { - AddItem( new Item( 0x1E94 ), 0, 7, 1); // Chicken on a spit - break; - } - } - AddItem(new Item(0x41F), 4, 4, 0); // Gruesome Standart South + public override void AddComponents() + { + BaseCreature bc; + //BaseEscortable be; - AddCampChests(); + Visible = false; + DecayDelay = TimeSpan.FromMinutes(5.0); + AddItem(new Static(0x10ee), 0, 0, 0); + AddItem(new Static(0xfac), 0, 7, 0); - for ( int i = 0; i < 4; i ++ ) - { - AddMobile( Lizardmen, 6, Utility.RandomMinMax( -7, 7 ), Utility.RandomMinMax( -7, 7 ), 0 ); - } - - switch ( Utility.Random( 2 ) ) - { - case 0: m_Prisoner = new Noble(); break; - default: m_Prisoner = new SeekerOfAdventure(); break; - } - - //be = (BaseEscortable)m_Prisoner; - //be.m_Captive = true; - - bc = (BaseCreature)m_Prisoner; - bc.IsPrisoner = true; - bc.CantWalk = true; - - m_Prisoner.YellHue = Utility.RandomList( 0x57, 0x67, 0x77, 0x87, 0x117 ); - AddMobile( m_Prisoner, 2, Utility.RandomMinMax( -2, 2 ), Utility.RandomMinMax( -2, 2 ), 0 ); - } + switch (Utility.Random(3)) + { + case 0: + { + AddItem(new Item(0xDE3), 0, 7, 0); // Campfire + AddItem(new Item(0x974), 0, 7, 1); // Cauldron + break; + } + case 1: + { + AddItem(new Item(0x1E95), 0, 7, 1); // Rabbit on a spit + break; + } + default: + { + AddItem(new Item(0x1E94), 0, 7, 1); // Chicken on a spit + break; + } + } - private void AddCampChests() - { - LockableContainer chest = null; - - switch ( Utility.Random( 3 ) ) - { - case 0: chest = new MetalChest(); break; - case 1: chest = new MetalGoldenChest(); break; - default: chest = new WoodenChest(); break; - } + AddItem(new Item(0x41F), 4, 4, 0); // Gruesome Standart South - chest.LiftOverride = true; + AddCampChests(); - TreasureMapChest.Fill( chest, 1 ); - - AddItem( chest, 2, -2, 0 ); - - LockableContainer crates = null; + for (int i = 0; i < 4; i++) AddMobile(Lizardmen, 6, Utility.RandomMinMax(-7, 7), Utility.RandomMinMax(-7, 7), 0); - switch ( Utility.Random( 4 ) ) - { - case 0: crates = new SmallCrate(); break; - case 1: crates = new MediumCrate(); break; - case 2: crates = new LargeCrate(); break; - default: crates = new LockableBarrel(); break; - } - - crates.TrapType = TrapType.ExplosionTrap; - crates.TrapPower = Utility.RandomMinMax( 30, 40 ); - crates.TrapLevel = 2; - - crates.RequiredSkill = 76; - crates.LockLevel = 66; - crates.MaxLockLevel = 116; - crates.Locked = true; - - crates.DropItem( new Gold( Utility.RandomMinMax( 100, 400 ) ) ); - crates.DropItem( new Arrow( 10 ) ); - crates.DropItem( new Bolt( 10 ) ); + switch (Utility.Random(2)) + { + case 0: + m_Prisoner = new Noble(); + break; + default: + m_Prisoner = new SeekerOfAdventure(); + break; + } - crates.LiftOverride = true; - - if ( Utility.RandomDouble() < 0.8 ) - { - switch ( Utility.Random( 4 ) ) - { - case 0: crates.DropItem( new LesserCurePotion() ); break; - case 1: crates.DropItem( new LesserExplosionPotion() ); break; - case 2: crates.DropItem( new LesserHealPotion() ); break; - default: crates.DropItem(new LesserPoisonPotion()); break; - } - } - - AddItem( crates, -2, 2, 0 ); - } + //be = (BaseEscortable)m_Prisoner; + //be.m_Captive = true; - // Don't refresh decay timer - public override void OnEnter(Mobile m) - { - if ( m.Player && m_Prisoner != null && m_Prisoner.CantWalk ) - { - int number; + bc = (BaseCreature)m_Prisoner; + bc.IsPrisoner = true; + bc.CantWalk = true; - switch ( Utility.Random( 8 ) ) - { - case 0: number = 502261; break; // HELP! - case 1: number = 502262; break; // Help me! - case 2: number = 502263; break; // Canst thou aid me?! - case 3: number = 502264; break; // Help a poor prisoner! - case 4: number = 502265; break; // Help! Please! - case 5: number = 502266; break; // Aaah! Help me! - case 6: number = 502267; break; // Go and get some help! - default: number = 502268; break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. - } - m_Prisoner.Yell( number ); - } - } + m_Prisoner.YellHue = Utility.RandomList(0x57, 0x67, 0x77, 0x87, 0x117); + AddMobile(m_Prisoner, 2, Utility.RandomMinMax(-2, 2), Utility.RandomMinMax(-2, 2), 0); + } - // Don't refresh decay timer - public override void OnExit(Mobile m) - { - } + private void AddCampChests() + { + LockableContainer chest = null; - public LizardmenCamp( Serial serial ) : base( serial ) - { - } - - public override void AddItem( Item item, int xOffset, int yOffset, int zOffset ) - { - if ( item != null ) - item.Movable = false; - - base.AddItem( item, xOffset, yOffset, zOffset ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + switch (Utility.Random(3)) + { + case 0: + chest = new MetalChest(); + break; + case 1: + chest = new MetalGoldenChest(); + break; + default: + chest = new WoodenChest(); + break; + } - writer.Write( (int) 0 ); // version + chest.LiftOverride = true; - writer.Write( m_Prisoner ); - } + TreasureMapChest.Fill(chest, 1); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + AddItem(chest, 2, -2, 0); - int version = reader.ReadInt(); + LockableContainer crates = null; - switch ( version ) - { - case 0: - { - m_Prisoner = reader.ReadMobile(); - break; - } - } - } - } -} + switch (Utility.Random(4)) + { + case 0: + crates = new SmallCrate(); + break; + case 1: + crates = new MediumCrate(); + break; + case 2: + crates = new LargeCrate(); + break; + default: + crates = new LockableBarrel(); + break; + } + + crates.TrapType = TrapType.ExplosionTrap; + crates.TrapPower = Utility.RandomMinMax(30, 40); + crates.TrapLevel = 2; + + crates.RequiredSkill = 76; + crates.LockLevel = 66; + crates.MaxLockLevel = 116; + crates.Locked = true; + + crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); + crates.DropItem(new Arrow(10)); + crates.DropItem(new Bolt(10)); + + crates.LiftOverride = true; + + if (Utility.RandomDouble() < 0.8) + switch (Utility.Random(4)) + { + case 0: + crates.DropItem(new LesserCurePotion()); + break; + case 1: + crates.DropItem(new LesserExplosionPotion()); + break; + case 2: + crates.DropItem(new LesserHealPotion()); + break; + default: + crates.DropItem(new LesserPoisonPotion()); + break; + } + + AddItem(crates, -2, 2, 0); + } + + // Don't refresh decay timer + public override void OnEnter(Mobile m) + { + if (m.Player && m_Prisoner != null && m_Prisoner.CantWalk) + { + int number; + + switch (Utility.Random(8)) + { + case 0: + number = 502261; + break; // HELP! + case 1: + number = 502262; + break; // Help me! + case 2: + number = 502263; + break; // Canst thou aid me?! + case 3: + number = 502264; + break; // Help a poor prisoner! + case 4: + number = 502265; + break; // Help! Please! + case 5: + number = 502266; + break; // Aaah! Help me! + case 6: + number = 502267; + break; // Go and get some help! + default: + number = 502268; + break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. + } + + m_Prisoner.Yell(number); + } + } + + // Don't refresh decay timer + public override void OnExit(Mobile m) + { + } + + public override void AddItem(Item item, int xOffset, int yOffset, int zOffset) + { + if (item != null) + item.Movable = false; + + base.AddItem(item, xOffset, yOffset, zOffset); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + + writer.Write(m_Prisoner); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + m_Prisoner = reader.ReadMobile(); + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Camps/MageCamp.cs b/Scripts/Multis/Camps/MageCamp.cs index 7627a533a..83c44a088 100644 --- a/Scripts/Multis/Camps/MageCamp.cs +++ b/Scripts/Multis/Camps/MageCamp.cs @@ -3,45 +3,45 @@ using Server.Mobiles; namespace Server.Multis { - public class MageCamp : BaseCamp - { - [Constructible] - public MageCamp() : base( 0x1F5 ) - { - } + public class MageCamp : BaseCamp + { + [Constructible] + public MageCamp() : base(0x1F5) + { + } - public override void AddComponents() - { - BaseDoor west, east; + public MageCamp(Serial serial) : base(serial) + { + } - AddItem( west = new LightWoodGate( DoorFacing.WestCW ), -4, 4, 7 ); - AddItem( east = new LightWoodGate( DoorFacing.EastCCW ), -3, 4, 7 ); + public override void AddComponents() + { + BaseDoor west, east; - west.Link = east; - east.Link = west; + AddItem(west = new LightWoodGate(DoorFacing.WestCW), -4, 4, 7); + AddItem(east = new LightWoodGate(DoorFacing.EastCCW), -3, 4, 7); - AddItem( new Sign( SignType.Mage, SignFacing.West ), -5, 5, -4 ); + west.Link = east; + east.Link = west; - AddMobile( new Mage(), 4, -4, 3, 7 ); - AddMobile( new Mage(), 5, 4, -2, 0 ); - } + AddItem(new Sign(SignType.Mage, SignFacing.West), -5, 5, -4); - public MageCamp( Serial serial ) : base( serial ) - { - } + AddMobile(new Mage(), 4, -4, 3, 7); + AddMobile(new Mage(), 5, 4, -2, 0); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Camps/OrcCamp.cs b/Scripts/Multis/Camps/OrcCamp.cs index 2ff86313e..e76e842a5 100644 --- a/Scripts/Multis/Camps/OrcCamp.cs +++ b/Scripts/Multis/Camps/OrcCamp.cs @@ -4,197 +4,236 @@ using Server.Mobiles; namespace Server.Multis { - public class OrcCamp : BaseCamp - { - public virtual Mobile Orcs => new Orc(); + public class OrcCamp : BaseCamp + { + private Mobile m_Prisoner; - private Mobile m_Prisoner; - - [Constructible] - public OrcCamp() : base( 0x10EE ) // dummy garbage at center - { - } + [Constructible] + public OrcCamp() : base(0x10EE) // dummy garbage at center + { + } - public override void AddComponents() - { - BaseCreature bc; - //BaseEscortable be; + public OrcCamp(Serial serial) : base(serial) + { + } - Visible = false; - DecayDelay = TimeSpan.FromMinutes(5.0); - AddItem(new Static(0x10ee), 0, 0, 0); - AddItem(new Static(0xfac), 0, 7, 0); - - switch ( Utility.Random( 3 ) ) - { - case 0: - { - AddItem( new Item( 0xDE3 ), 0, 7, 0 ); // Campfire - AddItem( new Item( 0x974 ), 0, 7, 1 ); // Cauldron - break; - } - case 1: - { - AddItem( new Item( 0x1E95 ), 0, 7, 1 ); // Rabbit on a spit - break; - } - default: - { - AddItem( new Item( 0x1E94 ), 0, 7, 1 ); // Chicken on a spit - break; - } - } - AddItem(new Item(0x428), -5, -4, 0); // Gruesome Standart West + public virtual Mobile Orcs => new Orc(); - AddCampChests(); - - for ( int i = 0; i < 3; i ++ ) - { - AddMobile( Orcs, 6, Utility.RandomMinMax( -7, 7 ), Utility.RandomMinMax( -7, 7 ), 0 ); - } - AddMobile( new OrcCaptain(), 2, Utility.RandomMinMax( -7, 7 ), Utility.RandomMinMax( -7, 7 ), 0 ); - - switch ( Utility.Random( 2 ) ) - { - case 0: m_Prisoner = new Noble(); break; - default: m_Prisoner = new SeekerOfAdventure(); break; - } - - //be = (BaseEscortable)m_Prisoner; - //be.m_Captive = true; - - bc = (BaseCreature)m_Prisoner; - bc.IsPrisoner = true; - bc.CantWalk = true; - - m_Prisoner.YellHue = Utility.RandomList( 0x57, 0x67, 0x77, 0x87, 0x117 ); - AddMobile( m_Prisoner, 2, Utility.RandomMinMax( -2, 2 ), Utility.RandomMinMax( -2, 2 ), 0 ); - } + public override void AddComponents() + { + BaseCreature bc; + //BaseEscortable be; - private void AddCampChests() - { - LockableContainer chest = null; + Visible = false; + DecayDelay = TimeSpan.FromMinutes(5.0); + AddItem(new Static(0x10ee), 0, 0, 0); + AddItem(new Static(0xfac), 0, 7, 0); - switch (Utility.Random(3)) - { - case 0: chest = new MetalChest(); break; - case 1: chest = new MetalGoldenChest(); break; - default: chest = new WoodenChest(); break; - } + switch (Utility.Random(3)) + { + case 0: + { + AddItem(new Item(0xDE3), 0, 7, 0); // Campfire + AddItem(new Item(0x974), 0, 7, 1); // Cauldron + break; + } + case 1: + { + AddItem(new Item(0x1E95), 0, 7, 1); // Rabbit on a spit + break; + } + default: + { + AddItem(new Item(0x1E94), 0, 7, 1); // Chicken on a spit + break; + } + } - chest.LiftOverride = true; + AddItem(new Item(0x428), -5, -4, 0); // Gruesome Standart West - TreasureMapChest.Fill(chest, 1); + AddCampChests(); - AddItem(chest, -2, 2, 0); + for (int i = 0; i < 3; i++) AddMobile(Orcs, 6, Utility.RandomMinMax(-7, 7), Utility.RandomMinMax(-7, 7), 0); + AddMobile(new OrcCaptain(), 2, Utility.RandomMinMax(-7, 7), Utility.RandomMinMax(-7, 7), 0); - LockableContainer crates = null; + switch (Utility.Random(2)) + { + case 0: + m_Prisoner = new Noble(); + break; + default: + m_Prisoner = new SeekerOfAdventure(); + break; + } - switch (Utility.Random(4)) - { - case 0: crates = new SmallCrate(); break; - case 1: crates = new MediumCrate(); break; - case 2: crates = new LargeCrate(); break; - default: crates = new LockableBarrel(); break; - } + //be = (BaseEscortable)m_Prisoner; + //be.m_Captive = true; - crates.TrapType = TrapType.ExplosionTrap; - crates.TrapPower = Utility.RandomMinMax(30, 40); - crates.TrapLevel = 2; + bc = (BaseCreature)m_Prisoner; + bc.IsPrisoner = true; + bc.CantWalk = true; - crates.RequiredSkill = 76; - crates.LockLevel = 66; - crates.MaxLockLevel = 116; - crates.Locked = true; + m_Prisoner.YellHue = Utility.RandomList(0x57, 0x67, 0x77, 0x87, 0x117); + AddMobile(m_Prisoner, 2, Utility.RandomMinMax(-2, 2), Utility.RandomMinMax(-2, 2), 0); + } - crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); - crates.DropItem(new Arrow(10)); - crates.DropItem(new Bolt(10)); + private void AddCampChests() + { + LockableContainer chest = null; - crates.LiftOverride = true; + switch (Utility.Random(3)) + { + case 0: + chest = new MetalChest(); + break; + case 1: + chest = new MetalGoldenChest(); + break; + default: + chest = new WoodenChest(); + break; + } - if (Utility.RandomDouble() < 0.8) - { - switch (Utility.Random(4)) - { - case 0: crates.DropItem(new LesserCurePotion()); break; - case 1: crates.DropItem(new LesserExplosionPotion()); break; - case 2: crates.DropItem(new LesserHealPotion()); break; - default: crates.DropItem(new LesserPoisonPotion()); break; - } - } + chest.LiftOverride = true; - AddItem(crates, 2, -2, 0); - } + TreasureMapChest.Fill(chest, 1); - // Don't refresh decay timer - public override void OnEnter(Mobile m) - { - if ( m.Player && m_Prisoner != null && m_Prisoner.CantWalk ) - { - int number; + AddItem(chest, -2, 2, 0); - switch ( Utility.Random( 8 ) ) - { - case 0: number = 502261; break; // HELP! - case 1: number = 502262; break; // Help me! - case 2: number = 502263; break; // Canst thou aid me?! - case 3: number = 502264; break; // Help a poor prisoner! - case 4: number = 502265; break; // Help! Please! - case 5: number = 502266; break; // Aaah! Help me! - case 6: number = 502267; break; // Go and get some help! - default: number = 502268; break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. - } - m_Prisoner.Yell( number ); - } - } + LockableContainer crates = null; - // Don't refresh decay timer - public override void OnExit(Mobile m) - { - } + switch (Utility.Random(4)) + { + case 0: + crates = new SmallCrate(); + break; + case 1: + crates = new MediumCrate(); + break; + case 2: + crates = new LargeCrate(); + break; + default: + crates = new LockableBarrel(); + break; + } - public OrcCamp( Serial serial ) : base( serial ) - { - } - - public override void AddItem( Item item, int xOffset, int yOffset, int zOffset ) - { - if ( item != null ) - item.Movable = false; - - base.AddItem( item, xOffset, yOffset, zOffset ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + crates.TrapType = TrapType.ExplosionTrap; + crates.TrapPower = Utility.RandomMinMax(30, 40); + crates.TrapLevel = 2; - writer.Write( (int) 1 ); // version + crates.RequiredSkill = 76; + crates.LockLevel = 66; + crates.MaxLockLevel = 116; + crates.Locked = true; - writer.Write( m_Prisoner ); - } + crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); + crates.DropItem(new Arrow(10)); + crates.DropItem(new Bolt(10)); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + crates.LiftOverride = true; - int version = reader.ReadInt(); + if (Utility.RandomDouble() < 0.8) + switch (Utility.Random(4)) + { + case 0: + crates.DropItem(new LesserCurePotion()); + break; + case 1: + crates.DropItem(new LesserExplosionPotion()); + break; + case 2: + crates.DropItem(new LesserHealPotion()); + break; + default: + crates.DropItem(new LesserPoisonPotion()); + break; + } - switch ( version ) - { - case 1: - { - m_Prisoner = reader.ReadMobile(); - break; - } - case 0: - { - m_Prisoner = reader.ReadMobile(); - reader.ReadItem(); - break; - } - } - } - } + AddItem(crates, 2, -2, 0); + } + + // Don't refresh decay timer + public override void OnEnter(Mobile m) + { + if (m.Player && m_Prisoner != null && m_Prisoner.CantWalk) + { + int number; + + switch (Utility.Random(8)) + { + case 0: + number = 502261; + break; // HELP! + case 1: + number = 502262; + break; // Help me! + case 2: + number = 502263; + break; // Canst thou aid me?! + case 3: + number = 502264; + break; // Help a poor prisoner! + case 4: + number = 502265; + break; // Help! Please! + case 5: + number = 502266; + break; // Aaah! Help me! + case 6: + number = 502267; + break; // Go and get some help! + default: + number = 502268; + break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. + } + + m_Prisoner.Yell(number); + } + } + + // Don't refresh decay timer + public override void OnExit(Mobile m) + { + } + + public override void AddItem(Item item, int xOffset, int yOffset, int zOffset) + { + if (item != null) + item.Movable = false; + + base.AddItem(item, xOffset, yOffset, zOffset); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(m_Prisoner); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Prisoner = reader.ReadMobile(); + break; + } + case 0: + { + m_Prisoner = reader.ReadMobile(); + reader.ReadItem(); + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Camps/RatCamp.cs b/Scripts/Multis/Camps/RatCamp.cs index 8af654b2f..866b4c681 100644 --- a/Scripts/Multis/Camps/RatCamp.cs +++ b/Scripts/Multis/Camps/RatCamp.cs @@ -4,196 +4,235 @@ using Server.Mobiles; namespace Server.Multis { - public class RatCamp : BaseCamp - { - public virtual Mobile Ratmen => new Ratman(); + public class RatCamp : BaseCamp + { + private Mobile m_Prisoner; - private Mobile m_Prisoner; - - [Constructible] - public RatCamp() : base( 0x10EE ) // dummy garbage at center - { - } + [Constructible] + public RatCamp() : base(0x10EE) // dummy garbage at center + { + } - public override void AddComponents() - { - BaseCreature bc; - //BaseEscortable be; + public RatCamp(Serial serial) : base(serial) + { + } - Visible = false; - DecayDelay = TimeSpan.FromMinutes(5.0); - AddItem(new Static(0x10ee), 0, 0, 0); - AddItem(new Static(0xfac), 0, 6, 0); - - switch ( Utility.Random( 3 ) ) - { - case 0: - { - AddItem( new Item( 0xDE3 ), 0, 6, 0 ); // Campfire - AddItem( new Item( 0x974 ), 0, 6, 1 ); // Cauldron - break; - } - case 1: - { - AddItem( new Item( 0x1E95 ), 0, 6, 1 ); // Rabbit on a spit - break; - } - default: - { - AddItem( new Item( 0x1E94 ), 0, 6, 1 ); // Chicken on a spit - break; - } - } - AddItem(new Item(0x41F), 5, 5, 0); // Gruesome Standart South + public virtual Mobile Ratmen => new Ratman(); - AddCampChests(); - - for ( int i = 0; i < 4; i ++ ) - { - AddMobile( Ratmen, 6, Utility.RandomMinMax( -7, 7 ), Utility.RandomMinMax( -7, 7 ), 0 ); - } - - switch ( Utility.Random( 2 ) ) - { - case 0: m_Prisoner = new Noble(); break; - default: m_Prisoner = new SeekerOfAdventure(); break; - } - - //be = (BaseEscortable)m_Prisoner; - //be.m_Captive = true; - - bc = (BaseCreature)m_Prisoner; - bc.IsPrisoner = true; - bc.CantWalk = true; - - m_Prisoner.YellHue = Utility.RandomList( 0x57, 0x67, 0x77, 0x87, 0x117 ); - AddMobile( m_Prisoner, 2, Utility.RandomMinMax( -2, 2 ), Utility.RandomMinMax( -2, 2 ), 0 ); - } + public override void AddComponents() + { + BaseCreature bc; + //BaseEscortable be; - private void AddCampChests() - { - LockableContainer chest = null; + Visible = false; + DecayDelay = TimeSpan.FromMinutes(5.0); + AddItem(new Static(0x10ee), 0, 0, 0); + AddItem(new Static(0xfac), 0, 6, 0); - switch (Utility.Random(3)) - { - case 0: chest = new MetalChest(); break; - case 1: chest = new MetalGoldenChest(); break; - default: chest = new WoodenChest(); break; - } + switch (Utility.Random(3)) + { + case 0: + { + AddItem(new Item(0xDE3), 0, 6, 0); // Campfire + AddItem(new Item(0x974), 0, 6, 1); // Cauldron + break; + } + case 1: + { + AddItem(new Item(0x1E95), 0, 6, 1); // Rabbit on a spit + break; + } + default: + { + AddItem(new Item(0x1E94), 0, 6, 1); // Chicken on a spit + break; + } + } - chest.LiftOverride = true; + AddItem(new Item(0x41F), 5, 5, 0); // Gruesome Standart South - TreasureMapChest.Fill(chest, 1); + AddCampChests(); - AddItem(chest, -2, -2, 0); + for (int i = 0; i < 4; i++) AddMobile(Ratmen, 6, Utility.RandomMinMax(-7, 7), Utility.RandomMinMax(-7, 7), 0); - LockableContainer crates = null; + switch (Utility.Random(2)) + { + case 0: + m_Prisoner = new Noble(); + break; + default: + m_Prisoner = new SeekerOfAdventure(); + break; + } - switch (Utility.Random(4)) - { - case 0: crates = new SmallCrate(); break; - case 1: crates = new MediumCrate(); break; - case 2: crates = new LargeCrate(); break; - default: crates = new LockableBarrel(); break; - } + //be = (BaseEscortable)m_Prisoner; + //be.m_Captive = true; - crates.TrapType = TrapType.ExplosionTrap; - crates.TrapPower = Utility.RandomMinMax(30, 40); - crates.TrapLevel = 2; + bc = (BaseCreature)m_Prisoner; + bc.IsPrisoner = true; + bc.CantWalk = true; - crates.RequiredSkill = 76; - crates.LockLevel = 66; - crates.MaxLockLevel = 116; - crates.Locked = true; + m_Prisoner.YellHue = Utility.RandomList(0x57, 0x67, 0x77, 0x87, 0x117); + AddMobile(m_Prisoner, 2, Utility.RandomMinMax(-2, 2), Utility.RandomMinMax(-2, 2), 0); + } - crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); - crates.DropItem(new Arrow(10)); - crates.DropItem(new Bolt(10)); + private void AddCampChests() + { + LockableContainer chest = null; - crates.LiftOverride = true; + switch (Utility.Random(3)) + { + case 0: + chest = new MetalChest(); + break; + case 1: + chest = new MetalGoldenChest(); + break; + default: + chest = new WoodenChest(); + break; + } - if (Utility.RandomDouble() < 0.8) - { - switch (Utility.Random(4)) - { - case 0: crates.DropItem(new LesserCurePotion()); break; - case 1: crates.DropItem(new LesserExplosionPotion()); break; - case 2: crates.DropItem(new LesserHealPotion()); break; - default: crates.DropItem(new LesserPoisonPotion()); break; - } - } + chest.LiftOverride = true; - AddItem(crates, 2, 2, 0); - } + TreasureMapChest.Fill(chest, 1); - // Don't refresh decay timer - public override void OnEnter(Mobile m) - { - if ( m.Player && m_Prisoner != null && m_Prisoner.CantWalk ) - { - int number; + AddItem(chest, -2, -2, 0); - switch ( Utility.Random( 8 ) ) - { - case 0: number = 502261; break; // HELP! - case 1: number = 502262; break; // Help me! - case 2: number = 502263; break; // Canst thou aid me?! - case 3: number = 502264; break; // Help a poor prisoner! - case 4: number = 502265; break; // Help! Please! - case 5: number = 502266; break; // Aaah! Help me! - case 6: number = 502267; break; // Go and get some help! - default: number = 502268; break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. - } - m_Prisoner.Yell( number ); - } - } + LockableContainer crates = null; - // Don't refresh decay timer - public override void OnExit(Mobile m) - { - } + switch (Utility.Random(4)) + { + case 0: + crates = new SmallCrate(); + break; + case 1: + crates = new MediumCrate(); + break; + case 2: + crates = new LargeCrate(); + break; + default: + crates = new LockableBarrel(); + break; + } - public RatCamp( Serial serial ) : base( serial ) - { - } - - public override void AddItem( Item item, int xOffset, int yOffset, int zOffset ) - { - if ( item != null ) - item.Movable = false; - - base.AddItem( item, xOffset, yOffset, zOffset ); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + crates.TrapType = TrapType.ExplosionTrap; + crates.TrapPower = Utility.RandomMinMax(30, 40); + crates.TrapLevel = 2; - writer.Write( (int) 1 ); // version + crates.RequiredSkill = 76; + crates.LockLevel = 66; + crates.MaxLockLevel = 116; + crates.Locked = true; - writer.Write( m_Prisoner ); - } + crates.DropItem(new Gold(Utility.RandomMinMax(100, 400))); + crates.DropItem(new Arrow(10)); + crates.DropItem(new Bolt(10)); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + crates.LiftOverride = true; - int version = reader.ReadInt(); + if (Utility.RandomDouble() < 0.8) + switch (Utility.Random(4)) + { + case 0: + crates.DropItem(new LesserCurePotion()); + break; + case 1: + crates.DropItem(new LesserExplosionPotion()); + break; + case 2: + crates.DropItem(new LesserHealPotion()); + break; + default: + crates.DropItem(new LesserPoisonPotion()); + break; + } - switch ( version ) - { - case 1: - { - m_Prisoner = reader.ReadMobile(); - break; - } - case 0: - { - m_Prisoner = reader.ReadMobile(); - reader.ReadItem(); - break; - } - } - } - } + AddItem(crates, 2, 2, 0); + } + + // Don't refresh decay timer + public override void OnEnter(Mobile m) + { + if (m.Player && m_Prisoner != null && m_Prisoner.CantWalk) + { + int number; + + switch (Utility.Random(8)) + { + case 0: + number = 502261; + break; // HELP! + case 1: + number = 502262; + break; // Help me! + case 2: + number = 502263; + break; // Canst thou aid me?! + case 3: + number = 502264; + break; // Help a poor prisoner! + case 4: + number = 502265; + break; // Help! Please! + case 5: + number = 502266; + break; // Aaah! Help me! + case 6: + number = 502267; + break; // Go and get some help! + default: + number = 502268; + break; // Quickly, I beg thee! Unlock my chains! If thou dost look at me close thou canst see them. + } + + m_Prisoner.Yell(number); + } + } + + // Don't refresh decay timer + public override void OnExit(Mobile m) + { + } + + public override void AddItem(Item item, int xOffset, int yOffset, int zOffset) + { + if (item != null) + item.Movable = false; + + base.AddItem(item, xOffset, yOffset, zOffset); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(1); // version + + writer.Write(m_Prisoner); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 1: + { + m_Prisoner = reader.ReadMobile(); + break; + } + case 0: + { + m_Prisoner = reader.ReadMobile(); + reader.ReadItem(); + break; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Multis/ComponentVerification.cs b/Scripts/Multis/ComponentVerification.cs index a2b26025d..8cb79395a 100644 --- a/Scripts/Multis/ComponentVerification.cs +++ b/Scripts/Multis/ComponentVerification.cs @@ -3,242 +3,247 @@ using System.IO; namespace Server.Multis { - public class ComponentVerification - { - private int[] m_ItemTable; - private int[] m_MultiTable; + public class ComponentVerification + { + private int[] m_ItemTable; + private int[] m_MultiTable; - public bool IsItemValid( int itemID ) - { - if ( itemID <= 0 || itemID >= m_ItemTable.Length ) - return false; + public ComponentVerification() + { + m_ItemTable = CreateTable(TileData.MaxItemValue); + m_MultiTable = CreateTable(0x4000); - return CheckValidity( m_ItemTable[itemID] ); - } + LoadItems("Data/Components/walls.txt", "South1", "South2", "South3", "Corner", "East1", "East2", "East3", "Post", + "WindowS", "AltWindowS", "WindowE", "AltWindowE", "SecondAltWindowS", "SecondAltWindowE"); + LoadItems("Data/Components/teleprts.txt", "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", + "F12", "F13", "F14", "F15", "F16"); + LoadItems("Data/Components/stairs.txt", "Block", "North", "East", "South", "West", "Squared1", "Squared2", + "Rounded1", "Rounded2"); + LoadItems("Data/Components/roof.txt", "North", "East", "South", "West", "NSCrosspiece", "EWCrosspiece", "NDent", + "EDent", "SDent", "WDent", "NTPiece", "ETPiece", "STPiece", "WTPiece", "XPiece", "Extra Piece"); + LoadItems("Data/Components/floors.txt", "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", + "F12", "F13", "F14", "F15", "F16"); + LoadItems("Data/Components/misc.txt", "Piece1", "Piece2", "Piece3", "Piece4", "Piece5", "Piece6", "Piece7", + "Piece8"); + LoadItems("Data/Components/doors.txt", "Piece1", "Piece2", "Piece3", "Piece4", "Piece5", "Piece6", "Piece7", + "Piece8"); - public bool IsMultiValid( int multiID ) - { - if ( multiID <= 0 || multiID >= m_MultiTable.Length ) - return false; + LoadMultis("Data/Components/stairs.txt", "MultiNorth", "MultiEast", "MultiSouth", "MultiWest"); + } - return CheckValidity( m_MultiTable[multiID] ); - } + public bool IsItemValid(int itemID) + { + if (itemID <= 0 || itemID >= m_ItemTable.Length) + return false; - public bool CheckValidity( int val ) - { - if ( val == -1 ) - return false; + return CheckValidity(m_ItemTable[itemID]); + } - return ( val == 0 || ((int)ExpansionInfo.CoreExpansion.CustomHousingFlag & val) != 0 ); - } + public bool IsMultiValid(int multiID) + { + if (multiID <= 0 || multiID >= m_MultiTable.Length) + return false; - public ComponentVerification() - { - m_ItemTable = CreateTable( TileData.MaxItemValue ); - m_MultiTable = CreateTable( 0x4000 ); + return CheckValidity(m_MultiTable[multiID]); + } - LoadItems( "Data/Components/walls.txt", "South1", "South2", "South3", "Corner", "East1", "East2", "East3", "Post", "WindowS", "AltWindowS", "WindowE", "AltWindowE", "SecondAltWindowS", "SecondAltWindowE" ); - LoadItems( "Data/Components/teleprts.txt", "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", "F12", "F13", "F14", "F15", "F16" ); - LoadItems( "Data/Components/stairs.txt", "Block", "North", "East", "South", "West", "Squared1", "Squared2", "Rounded1", "Rounded2" ); - LoadItems( "Data/Components/roof.txt", "North", "East", "South", "West", "NSCrosspiece", "EWCrosspiece", "NDent", "EDent", "SDent", "WDent", "NTPiece", "ETPiece", "STPiece", "WTPiece", "XPiece", "Extra Piece" ); - LoadItems( "Data/Components/floors.txt", "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", "F12", "F13", "F14", "F15", "F16" ); - LoadItems( "Data/Components/misc.txt", "Piece1", "Piece2", "Piece3", "Piece4", "Piece5", "Piece6", "Piece7", "Piece8" ); - LoadItems( "Data/Components/doors.txt", "Piece1", "Piece2", "Piece3", "Piece4", "Piece5", "Piece6", "Piece7", "Piece8" ); + public bool CheckValidity(int val) + { + if (val == -1) + return false; - LoadMultis( "Data/Components/stairs.txt", "MultiNorth", "MultiEast", "MultiSouth", "MultiWest" ); - } + return val == 0 || ((int)ExpansionInfo.CoreExpansion.CustomHousingFlag & val) != 0; + } - private int[] CreateTable( int length ) - { - int[] table = new int[length]; + private int[] CreateTable(int length) + { + int[] table = new int[length]; - for ( int i = 0; i < table.Length; ++i ) - table[i] = -1; + for (int i = 0; i < table.Length; ++i) + table[i] = -1; - return table; - } + return table; + } - private void LoadItems( string path, params string[] itemColumns ) - { - LoadSpreadsheet( m_ItemTable, path, itemColumns ); - } + private void LoadItems(string path, params string[] itemColumns) + { + LoadSpreadsheet(m_ItemTable, path, itemColumns); + } - private void LoadMultis( string path, params string[] multiColumns ) - { - LoadSpreadsheet( m_MultiTable, path, multiColumns ); - } + private void LoadMultis(string path, params string[] multiColumns) + { + LoadSpreadsheet(m_MultiTable, path, multiColumns); + } - private void LoadSpreadsheet( int[] table, string path, params string[] tileColumns ) - { - Spreadsheet ss = new Spreadsheet( path ); + private void LoadSpreadsheet(int[] table, string path, params string[] tileColumns) + { + Spreadsheet ss = new Spreadsheet(path); - int[] tileCIDs = new int[tileColumns.Length]; + int[] tileCIDs = new int[tileColumns.Length]; - for ( int i = 0; i < tileColumns.Length; ++i ) - tileCIDs[i] = ss.GetColumnID( tileColumns[i] ); + for (int i = 0; i < tileColumns.Length; ++i) + tileCIDs[i] = ss.GetColumnID(tileColumns[i]); - int featureCID = ss.GetColumnID( "FeatureMask" ); + int featureCID = ss.GetColumnID("FeatureMask"); - for ( int i = 0; i < ss.Records.Length; ++i ) - { - DataRecord record = ss.Records[i]; + for (int i = 0; i < ss.Records.Length; ++i) + { + DataRecord record = ss.Records[i]; - int fid = record.GetInt32( featureCID ); + int fid = record.GetInt32(featureCID); - for ( int j = 0; j < tileCIDs.Length; ++j ) - { - int itemID = record.GetInt32( tileCIDs[j] ); + for (int j = 0; j < tileCIDs.Length; ++j) + { + int itemID = record.GetInt32(tileCIDs[j]); - if ( itemID <= 0 || itemID >= table.Length ) - continue; + if (itemID <= 0 || itemID >= table.Length) + continue; - table[itemID] = fid; - } - } - } - } + table[itemID] = fid; + } + } + } + } - public class Spreadsheet - { - private class ColumnInfo - { - public int m_DataIndex; + public class Spreadsheet + { + private ColumnInfo[] m_Columns; - public string m_Type; - public string m_Name; + public Spreadsheet(string path) + { + using (StreamReader ip = new StreamReader(path)) + { + string[] types = ReadLine(ip); + string[] names = ReadLine(ip); - public ColumnInfo( int dataIndex, string type, string name ) - { - m_DataIndex = dataIndex; + m_Columns = new ColumnInfo[types.Length]; - m_Type = type; - m_Name = name; - } - } + for (int i = 0; i < m_Columns.Length; ++i) + m_Columns[i] = new ColumnInfo(i, types[i], names[i]); - private ColumnInfo[] m_Columns; + List records = new List(); - public DataRecord[] Records { get; } + string[] values; - public int GetColumnID( string name ) - { - for ( int i = 0; i < m_Columns.Length; ++i ) - { - if ( m_Columns[i].m_Name == name ) - return i; - } + while ((values = ReadLine(ip)) != null) + { + object[] data = new object[m_Columns.Length]; - return -1; - } + for (int i = 0; i < m_Columns.Length; ++i) + { + ColumnInfo ci = m_Columns[i]; - public Spreadsheet( string path ) - { - using ( StreamReader ip = new StreamReader( path ) ) - { - string[] types = ReadLine( ip ); - string[] names = ReadLine( ip ); + switch (ci.m_Type) + { + case "int": + { + data[i] = Utility.ToInt32(values[ci.m_DataIndex]); + break; + } + case "string": + { + data[i] = values[ci.m_DataIndex]; + break; + } + } + } - m_Columns = new ColumnInfo[types.Length]; + records.Add(new DataRecord(this, data)); + } - for ( int i = 0; i < m_Columns.Length; ++i ) - m_Columns[i] = new ColumnInfo( i, types[i], names[i] ); + Records = records.ToArray(); + } + } - List records = new List(); + public DataRecord[] Records{ get; } - string[] values; + public int GetColumnID(string name) + { + for (int i = 0; i < m_Columns.Length; ++i) + if (m_Columns[i].m_Name == name) + return i; - while ( ( values = ReadLine( ip ) ) != null ) - { - object[] data = new object[m_Columns.Length]; + return -1; + } - for ( int i = 0; i < m_Columns.Length; ++i ) - { - ColumnInfo ci = m_Columns[i]; + private string[] ReadLine(StreamReader ip) + { + string line; - switch ( ci.m_Type ) - { - case "int": - { - data[i] = Utility.ToInt32( values[ci.m_DataIndex] ); - break; - } - case "string": - { - data[i] = values[ci.m_DataIndex]; - break; - } - } - } + while ((line = ip.ReadLine()) != null) + { + if (line.Length == 0) + continue; - records.Add( new DataRecord( this, data ) ); - } + return line.Split('\t'); + } - Records = records.ToArray(); - } - } + return null; + } - private string[] ReadLine( StreamReader ip ) - { - string line; + private class ColumnInfo + { + public int m_DataIndex; + public string m_Name; - while ( ( line = ip.ReadLine() ) != null ) - { - if ( line.Length == 0 ) - continue; + public string m_Type; - return line.Split( '\t' ); - } + public ColumnInfo(int dataIndex, string type, string name) + { + m_DataIndex = dataIndex; - return null; - } - } + m_Type = type; + m_Name = name; + } + } + } - public class DataRecord - { - public Spreadsheet Spreadsheet { get; } + public class DataRecord + { + public DataRecord(Spreadsheet ss, object[] data) + { + Spreadsheet = ss; + Data = data; + } - public object[] Data { get; } + public Spreadsheet Spreadsheet{ get; } - public DataRecord( Spreadsheet ss, object[] data ) - { - Spreadsheet = ss; - Data = data; - } + public object[] Data{ get; } - public int GetInt32( string name ) - { - return GetInt32( this[name] ); - } + public object this[string name] => this[Spreadsheet.GetColumnID(name)]; - public int GetInt32( int id ) - { - return GetInt32( this[id] ); - } + public object this[int id] + { + get + { + if (id < 0) + return null; - public int GetInt32( object obj ) - { - if ( obj is int ) - return (int) obj; + return Data[id]; + } + } - return 0; - } + public int GetInt32(string name) + { + return GetInt32(this[name]); + } - public string GetString( string name ) - { - return this[name] as string; - } + public int GetInt32(int id) + { + return GetInt32(this[id]); + } - public object this[string name] => this[Spreadsheet.GetColumnID( name )]; + public int GetInt32(object obj) + { + if (obj is int) + return (int)obj; - public object this[int id] - { - get - { - if ( id < 0 ) - return null; + return 0; + } - return Data[id]; - } - } - } -} + public string GetString(string name) + { + return this[name] as string; + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/Deeds.cs b/Scripts/Multis/Deeds.cs index 1c2378738..05e2dbf58 100644 --- a/Scripts/Multis/Deeds.cs +++ b/Scripts/Multis/Deeds.cs @@ -1,875 +1,882 @@ using System.Collections; -using Server.Targeting; using Server.Regions; +using Server.Targeting; namespace Server.Multis.Deeds { - public class HousePlacementTarget : MultiTarget - { - private HouseDeed m_Deed; + public class HousePlacementTarget : MultiTarget + { + private HouseDeed m_Deed; - public HousePlacementTarget( HouseDeed deed ) : base( deed.MultiID, deed.Offset ) - { - m_Deed = deed; - } + public HousePlacementTarget(HouseDeed deed) : base(deed.MultiID, deed.Offset) + { + m_Deed = deed; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D ip = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D ip = o as IPoint3D; - if ( ip != null ) - { - if ( ip is Item ) - ip = ((Item)ip).GetWorldTop(); + if (ip != null) + { + if (ip is Item) + ip = ((Item)ip).GetWorldTop(); - Point3D p = new Point3D( ip ); + Point3D p = new Point3D(ip); - Region reg = Region.Find( new Point3D( p ), from.Map ); + Region reg = Region.Find(new Point3D(p), from.Map); - if ( from.AccessLevel >= AccessLevel.GameMaster || reg.AllowHousing( from, p ) ) - m_Deed.OnPlacement( from, p ); - else if ( reg.IsPartOf( typeof( TempNoHousingRegion ) ) ) - from.SendLocalizedMessage( 501270 ); // Lord British has decreed a 'no build' period, thus you cannot build this house at this time. - else if ( reg.IsPartOf( typeof( TreasureRegion ) ) || reg.IsPartOf( typeof( HouseRegion ) ) ) - from.SendLocalizedMessage( 1043287 ); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. - else if ( reg.IsPartOf( typeof( HouseRaffleRegion ) ) ) - from.SendLocalizedMessage( 1150493 ); // You must have a deed for this plot of land in order to build here. - else - from.SendLocalizedMessage( 501265 ); // Housing can not be created in this area. - } - } - } + if (from.AccessLevel >= AccessLevel.GameMaster || reg.AllowHousing(from, p)) + m_Deed.OnPlacement(from, p); + else if (reg.IsPartOf(typeof(TempNoHousingRegion))) + from.SendLocalizedMessage( + 501270); // Lord British has decreed a 'no build' period, thus you cannot build this house at this time. + else if (reg.IsPartOf(typeof(TreasureRegion)) || reg.IsPartOf(typeof(HouseRegion))) + from.SendLocalizedMessage( + 1043287); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. + else if (reg.IsPartOf(typeof(HouseRaffleRegion))) + from.SendLocalizedMessage(1150493); // You must have a deed for this plot of land in order to build here. + else + from.SendLocalizedMessage(501265); // Housing can not be created in this area. + } + } + } - public abstract class HouseDeed : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public int MultiID { get; set; } + public abstract class HouseDeed : Item + { + public HouseDeed(int id, Point3D offset) : base(0x14F0) + { + Weight = 1.0; + LootType = LootType.Newbied; - [CommandProperty( AccessLevel.GameMaster )] - public Point3D Offset { get; set; } + MultiID = id; + Offset = offset; + } - public HouseDeed( int id, Point3D offset ) : base( 0x14F0 ) - { - Weight = 1.0; - LootType = LootType.Newbied; + public HouseDeed(Serial serial) : base(serial) + { + } - MultiID = id; - Offset = offset; - } + [CommandProperty(AccessLevel.GameMaster)] + public int MultiID{ get; set; } - public HouseDeed( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public Point3D Offset{ get; set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public abstract Rectangle2D[] Area{ get; } - writer.Write( (int) 1 ); // version + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( Offset ); + writer.Write(1); // version - writer.Write( MultiID ); - } + writer.Write(Offset); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(MultiID); + } - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - switch ( version ) - { - case 1: - { - Offset = reader.ReadPoint3D(); + int version = reader.ReadInt(); - goto case 0; - } - case 0: - { - MultiID = reader.ReadInt(); + switch (version) + { + case 1: + { + Offset = reader.ReadPoint3D(); - break; - } - } + goto case 0; + } + case 0: + { + MultiID = reader.ReadInt(); - if ( Weight == 0.0 ) - Weight = 1.0; - } + break; + } + } - public override void OnDoubleClick( Mobile from ) - { - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse( from ) ) - { - from.SendLocalizedMessage( 501271 ); // You already own a house, you may not place another! - } - else - { - from.SendLocalizedMessage( 1010433 ); /* House placement cancellation could result in a + if (Weight == 0.0) + Weight = 1.0; + } + + public override void OnDoubleClick(Mobile from) + { + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse(from)) + { + from.SendLocalizedMessage(501271); // You already own a house, you may not place another! + } + else + { + from.SendLocalizedMessage(1010433); /* House placement cancellation could result in a * 60 second delay in the return of your deed. */ - from.Target = new HousePlacementTarget( this ); - } - } - - public abstract BaseHouse GetHouse( Mobile owner ); - public abstract Rectangle2D[] Area{ get; } - - public void OnPlacement( Mobile from, Point3D p ) - { - if ( Deleted ) - return; - - if ( !IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - else if ( from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse( from ) ) - { - from.SendLocalizedMessage( 501271 ); // You already own a house, you may not place another! - } - else - { - ArrayList toMove; - Point3D center = new Point3D( p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z ); - HousePlacementResult res = HousePlacement.Check( from, MultiID, center, out toMove ); - - switch ( res ) - { - case HousePlacementResult.Valid: - { - BaseHouse house = GetHouse( from ); - house.MoveToWorld( center, from.Map ); - Delete(); - - for ( int i = 0; i < toMove.Count; ++i ) - { - object o = toMove[i]; - - if ( o is Mobile ) - ((Mobile)o).Location = house.BanLocation; - else if ( o is Item ) - ((Item)o).Location = house.BanLocation; - } - - break; - } - case HousePlacementResult.BadItem: - case HousePlacementResult.BadLand: - case HousePlacementResult.BadStatic: - case HousePlacementResult.BadRegionHidden: - { - from.SendLocalizedMessage( 1043287 ); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. - break; - } - case HousePlacementResult.NoSurface: - { - from.SendMessage( "The house could not be created here. Part of the foundation would not be on any surface." ); - break; - } - case HousePlacementResult.BadRegion: - { - from.SendLocalizedMessage( 501265 ); // Housing cannot be created in this area. - break; - } - case HousePlacementResult.BadRegionTemp: - { - from.SendLocalizedMessage( 501270 ); //Lord British has decreed a 'no build' period, thus you cannot build this house at this time. - break; - } - case HousePlacementResult.BadRegionRaffle: - { - from.SendLocalizedMessage( 1150493 ); // You must have a deed for this plot of land in order to build here. - break; - } - } - } - } - } - - public class StonePlasterHouseDeed : HouseDeed - { - [Constructible] - public StonePlasterHouseDeed() : base( 0x64, new Point3D( 0, 4, 0 ) ) - { - } - - public StonePlasterHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallOldHouse( owner, 0x64 ); - } - - public override int LabelNumber => 1041211; - public override Rectangle2D[] Area => SmallOldHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class FieldStoneHouseDeed : HouseDeed - { - [Constructible] - public FieldStoneHouseDeed() : base( 0x66, new Point3D( 0, 4, 0 ) ) - { - } - - public FieldStoneHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallOldHouse( owner, 0x66 ); - } - - public override int LabelNumber => 1041212; - public override Rectangle2D[] Area => SmallOldHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallBrickHouseDeed : HouseDeed - { - [Constructible] - public SmallBrickHouseDeed() : base( 0x68, new Point3D( 0, 4, 0 ) ) - { - } - - public SmallBrickHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallOldHouse( owner, 0x68 ); - } - - public override int LabelNumber => 1041213; - public override Rectangle2D[] Area => SmallOldHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodHouseDeed : HouseDeed - { - [Constructible] - public WoodHouseDeed() : base( 0x6A, new Point3D( 0, 4, 0 ) ) - { - } - - public WoodHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallOldHouse( owner, 0x6A ); - } - - public override int LabelNumber => 1041214; - public override Rectangle2D[] Area => SmallOldHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class WoodPlasterHouseDeed : HouseDeed - { - [Constructible] - public WoodPlasterHouseDeed() : base( 0x6C, new Point3D( 0, 4, 0 ) ) - { - } - - public WoodPlasterHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallOldHouse( owner, 0x6C ); - } - - public override int LabelNumber => 1041215; - public override Rectangle2D[] Area => SmallOldHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class ThatchedRoofCottageDeed : HouseDeed - { - [Constructible] - public ThatchedRoofCottageDeed() : base( 0x6E, new Point3D( 0, 4, 0 ) ) - { - } - - public ThatchedRoofCottageDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallOldHouse( owner, 0x6E ); - } - - public override int LabelNumber => 1041216; - public override Rectangle2D[] Area => SmallOldHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class BrickHouseDeed : HouseDeed - { - [Constructible] - public BrickHouseDeed() : base( 0x74, new Point3D( -1, 7, 0 ) ) - { - } - - public BrickHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new GuildHouse( owner ); - } - - public override int LabelNumber => 1041219; - public override Rectangle2D[] Area => GuildHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TwoStoryWoodPlasterHouseDeed : HouseDeed - { - [Constructible] - public TwoStoryWoodPlasterHouseDeed() : base( 0x76, new Point3D( -3, 7, 0 ) ) - { - } - - public TwoStoryWoodPlasterHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new TwoStoryHouse( owner, 0x76 ); - } - - public override int LabelNumber => 1041220; - public override Rectangle2D[] Area => TwoStoryHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TwoStoryStonePlasterHouseDeed : HouseDeed - { - [Constructible] - public TwoStoryStonePlasterHouseDeed() : base( 0x78, new Point3D( -3, 7, 0 ) ) - { - } - - public TwoStoryStonePlasterHouseDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new TwoStoryHouse( owner, 0x78 ); - } - - public override int LabelNumber => 1041221; - public override Rectangle2D[] Area => TwoStoryHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class TowerDeed : HouseDeed - { - [Constructible] - public TowerDeed() : base( 0x7A, new Point3D( 0, 7, 0 ) ) - { - } - - public TowerDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new Tower( owner ); - } - - public override int LabelNumber => 1041222; - public override Rectangle2D[] Area => Tower.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class KeepDeed : HouseDeed - { - [Constructible] - public KeepDeed() : base( 0x7C, new Point3D( 0, 11, 0 ) ) - { - } - - public KeepDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new Keep( owner ); - } - - public override int LabelNumber => 1041223; - public override Rectangle2D[] Area => Keep.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class CastleDeed : HouseDeed - { - [Constructible] - public CastleDeed() : base( 0x7E, new Point3D( 0, 16, 0 ) ) - { - } - - public CastleDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new Castle( owner ); - } - - public override int LabelNumber => 1041224; - public override Rectangle2D[] Area => Castle.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LargePatioDeed : HouseDeed - { - [Constructible] - public LargePatioDeed() : base( 0x8C, new Point3D( -4, 7, 0 ) ) - { - } - - public LargePatioDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new LargePatioHouse( owner ); - } - - public override int LabelNumber => 1041231; - public override Rectangle2D[] Area => LargePatioHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LargeMarbleDeed : HouseDeed - { - [Constructible] - public LargeMarbleDeed() : base( 0x96, new Point3D( -4, 7, 0 ) ) - { - } - - public LargeMarbleDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new LargeMarbleHouse( owner ); - } - - public override int LabelNumber => 1041236; - public override Rectangle2D[] Area => LargeMarbleHouse.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SmallTowerDeed : HouseDeed - { - [Constructible] - public SmallTowerDeed() : base( 0x98, new Point3D( 3, 4, 0 ) ) - { - } - - public SmallTowerDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallTower( owner ); - } - - public override int LabelNumber => 1041237; - public override Rectangle2D[] Area => SmallTower.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class LogCabinDeed : HouseDeed - { - [Constructible] - public LogCabinDeed() : base( 0x9A, new Point3D( 1, 6, 0 ) ) - { - } - - public LogCabinDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new LogCabin( owner ); - } - - public override int LabelNumber => 1041238; - public override Rectangle2D[] Area => LogCabin.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class SandstonePatioDeed : HouseDeed - { - [Constructible] - public SandstonePatioDeed() : base( 0x9C, new Point3D( -1, 4, 0 ) ) - { - } - - public SandstonePatioDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SandStonePatio( owner ); - } - - public override int LabelNumber => 1041239; - public override Rectangle2D[] Area => SandStonePatio.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class VillaDeed : HouseDeed - { - [Constructible] - public VillaDeed() : base( 0x9E, new Point3D( 3, 6, 0 ) ) - { - } - - public VillaDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new TwoStoryVilla( owner ); - } - - public override int LabelNumber => 1041240; - public override Rectangle2D[] Area => TwoStoryVilla.AreaArray; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class StoneWorkshopDeed : HouseDeed - { - [Constructible] - public StoneWorkshopDeed() : base( 0xA0, new Point3D( -1, 4, 0 ) ) - { - } - - public StoneWorkshopDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallShop( owner, 0xA0 ); - } - - public override int LabelNumber => 1041241; - public override Rectangle2D[] Area => SmallShop.AreaArray2; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } - - public class MarbleWorkshopDeed : HouseDeed - { - [Constructible] - public MarbleWorkshopDeed() : base( 0xA2, new Point3D( -1, 4, 0 ) ) - { - } - - public MarbleWorkshopDeed( Serial serial ) : base( serial ) - { - } - - public override BaseHouse GetHouse( Mobile owner ) - { - return new SmallShop( owner, 0xA2 ); - } - - public override int LabelNumber => 1041242; - public override Rectangle2D[] Area => SmallShop.AreaArray1; - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + from.Target = new HousePlacementTarget(this); + } + } + + public abstract BaseHouse GetHouse(Mobile owner); + + public void OnPlacement(Mobile from, Point3D p) + { + if (Deleted) + return; + + if (!IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + else if (from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse(from)) + { + from.SendLocalizedMessage(501271); // You already own a house, you may not place another! + } + else + { + ArrayList toMove; + Point3D center = new Point3D(p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z); + HousePlacementResult res = HousePlacement.Check(from, MultiID, center, out toMove); + + switch (res) + { + case HousePlacementResult.Valid: + { + BaseHouse house = GetHouse(from); + house.MoveToWorld(center, from.Map); + Delete(); + + for (int i = 0; i < toMove.Count; ++i) + { + object o = toMove[i]; + + if (o is Mobile) + ((Mobile)o).Location = house.BanLocation; + else if (o is Item) + ((Item)o).Location = house.BanLocation; + } + + break; + } + case HousePlacementResult.BadItem: + case HousePlacementResult.BadLand: + case HousePlacementResult.BadStatic: + case HousePlacementResult.BadRegionHidden: + { + from.SendLocalizedMessage( + 1043287); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. + break; + } + case HousePlacementResult.NoSurface: + { + from.SendMessage( + "The house could not be created here. Part of the foundation would not be on any surface."); + break; + } + case HousePlacementResult.BadRegion: + { + from.SendLocalizedMessage(501265); // Housing cannot be created in this area. + break; + } + case HousePlacementResult.BadRegionTemp: + { + from.SendLocalizedMessage( + 501270); //Lord British has decreed a 'no build' period, thus you cannot build this house at this time. + break; + } + case HousePlacementResult.BadRegionRaffle: + { + from.SendLocalizedMessage( + 1150493); // You must have a deed for this plot of land in order to build here. + break; + } + } + } + } + } + + public class StonePlasterHouseDeed : HouseDeed + { + [Constructible] + public StonePlasterHouseDeed() : base(0x64, new Point3D(0, 4, 0)) + { + } + + public StonePlasterHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041211; + public override Rectangle2D[] Area => SmallOldHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallOldHouse(owner, 0x64); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class FieldStoneHouseDeed : HouseDeed + { + [Constructible] + public FieldStoneHouseDeed() : base(0x66, new Point3D(0, 4, 0)) + { + } + + public FieldStoneHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041212; + public override Rectangle2D[] Area => SmallOldHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallOldHouse(owner, 0x66); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallBrickHouseDeed : HouseDeed + { + [Constructible] + public SmallBrickHouseDeed() : base(0x68, new Point3D(0, 4, 0)) + { + } + + public SmallBrickHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041213; + public override Rectangle2D[] Area => SmallOldHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallOldHouse(owner, 0x68); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodHouseDeed : HouseDeed + { + [Constructible] + public WoodHouseDeed() : base(0x6A, new Point3D(0, 4, 0)) + { + } + + public WoodHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041214; + public override Rectangle2D[] Area => SmallOldHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallOldHouse(owner, 0x6A); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class WoodPlasterHouseDeed : HouseDeed + { + [Constructible] + public WoodPlasterHouseDeed() : base(0x6C, new Point3D(0, 4, 0)) + { + } + + public WoodPlasterHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041215; + public override Rectangle2D[] Area => SmallOldHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallOldHouse(owner, 0x6C); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class ThatchedRoofCottageDeed : HouseDeed + { + [Constructible] + public ThatchedRoofCottageDeed() : base(0x6E, new Point3D(0, 4, 0)) + { + } + + public ThatchedRoofCottageDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041216; + public override Rectangle2D[] Area => SmallOldHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallOldHouse(owner, 0x6E); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class BrickHouseDeed : HouseDeed + { + [Constructible] + public BrickHouseDeed() : base(0x74, new Point3D(-1, 7, 0)) + { + } + + public BrickHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041219; + public override Rectangle2D[] Area => GuildHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new GuildHouse(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TwoStoryWoodPlasterHouseDeed : HouseDeed + { + [Constructible] + public TwoStoryWoodPlasterHouseDeed() : base(0x76, new Point3D(-3, 7, 0)) + { + } + + public TwoStoryWoodPlasterHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041220; + public override Rectangle2D[] Area => TwoStoryHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new TwoStoryHouse(owner, 0x76); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TwoStoryStonePlasterHouseDeed : HouseDeed + { + [Constructible] + public TwoStoryStonePlasterHouseDeed() : base(0x78, new Point3D(-3, 7, 0)) + { + } + + public TwoStoryStonePlasterHouseDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041221; + public override Rectangle2D[] Area => TwoStoryHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new TwoStoryHouse(owner, 0x78); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class TowerDeed : HouseDeed + { + [Constructible] + public TowerDeed() : base(0x7A, new Point3D(0, 7, 0)) + { + } + + public TowerDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041222; + public override Rectangle2D[] Area => Tower.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new Tower(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class KeepDeed : HouseDeed + { + [Constructible] + public KeepDeed() : base(0x7C, new Point3D(0, 11, 0)) + { + } + + public KeepDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041223; + public override Rectangle2D[] Area => Keep.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new Keep(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class CastleDeed : HouseDeed + { + [Constructible] + public CastleDeed() : base(0x7E, new Point3D(0, 16, 0)) + { + } + + public CastleDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041224; + public override Rectangle2D[] Area => Castle.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new Castle(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LargePatioDeed : HouseDeed + { + [Constructible] + public LargePatioDeed() : base(0x8C, new Point3D(-4, 7, 0)) + { + } + + public LargePatioDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041231; + public override Rectangle2D[] Area => LargePatioHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new LargePatioHouse(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LargeMarbleDeed : HouseDeed + { + [Constructible] + public LargeMarbleDeed() : base(0x96, new Point3D(-4, 7, 0)) + { + } + + public LargeMarbleDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041236; + public override Rectangle2D[] Area => LargeMarbleHouse.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new LargeMarbleHouse(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SmallTowerDeed : HouseDeed + { + [Constructible] + public SmallTowerDeed() : base(0x98, new Point3D(3, 4, 0)) + { + } + + public SmallTowerDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041237; + public override Rectangle2D[] Area => SmallTower.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallTower(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class LogCabinDeed : HouseDeed + { + [Constructible] + public LogCabinDeed() : base(0x9A, new Point3D(1, 6, 0)) + { + } + + public LogCabinDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041238; + public override Rectangle2D[] Area => LogCabin.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new LogCabin(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class SandstonePatioDeed : HouseDeed + { + [Constructible] + public SandstonePatioDeed() : base(0x9C, new Point3D(-1, 4, 0)) + { + } + + public SandstonePatioDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041239; + public override Rectangle2D[] Area => SandStonePatio.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SandStonePatio(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class VillaDeed : HouseDeed + { + [Constructible] + public VillaDeed() : base(0x9E, new Point3D(3, 6, 0)) + { + } + + public VillaDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041240; + public override Rectangle2D[] Area => TwoStoryVilla.AreaArray; + + public override BaseHouse GetHouse(Mobile owner) + { + return new TwoStoryVilla(owner); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class StoneWorkshopDeed : HouseDeed + { + [Constructible] + public StoneWorkshopDeed() : base(0xA0, new Point3D(-1, 4, 0)) + { + } + + public StoneWorkshopDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041241; + public override Rectangle2D[] Area => SmallShop.AreaArray2; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallShop(owner, 0xA0); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } + + public class MarbleWorkshopDeed : HouseDeed + { + [Constructible] + public MarbleWorkshopDeed() : base(0xA2, new Point3D(-1, 4, 0)) + { + } + + public MarbleWorkshopDeed(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1041242; + public override Rectangle2D[] Area => SmallShop.AreaArray1; + + public override BaseHouse GetHouse(Mobile owner) + { + return new SmallShop(owner, 0xA2); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/DynamicDecay.cs b/Scripts/Multis/DynamicDecay.cs index fa426428d..072c4c99d 100644 --- a/Scripts/Multis/DynamicDecay.cs +++ b/Scripts/Multis/DynamicDecay.cs @@ -3,62 +3,62 @@ using System.Collections.Generic; namespace Server.Multis { - public class DynamicDecay - { - public static bool Enabled => Core.ML; + public class DynamicDecay + { + private static Dictionary m_Stages; - private static Dictionary m_Stages; + static DynamicDecay() + { + m_Stages = new Dictionary(); - static DynamicDecay() - { - m_Stages = new Dictionary(); + Register(DecayLevel.LikeNew, TimeSpan.FromHours(1), TimeSpan.FromHours(1)); + Register(DecayLevel.Slightly, TimeSpan.FromDays(1), TimeSpan.FromDays(2)); + Register(DecayLevel.Somewhat, TimeSpan.FromDays(1), TimeSpan.FromDays(2)); + Register(DecayLevel.Fairly, TimeSpan.FromDays(1), TimeSpan.FromDays(2)); + Register(DecayLevel.Greatly, TimeSpan.FromDays(1), TimeSpan.FromDays(2)); + Register(DecayLevel.IDOC, TimeSpan.FromHours(12), TimeSpan.FromHours(24)); + } - Register( DecayLevel.LikeNew, TimeSpan.FromHours( 1 ), TimeSpan.FromHours( 1 ) ); - Register( DecayLevel.Slightly, TimeSpan.FromDays( 1 ), TimeSpan.FromDays( 2 ) ); - Register( DecayLevel.Somewhat, TimeSpan.FromDays( 1 ), TimeSpan.FromDays( 2 ) ); - Register( DecayLevel.Fairly, TimeSpan.FromDays( 1 ), TimeSpan.FromDays( 2 ) ); - Register( DecayLevel.Greatly, TimeSpan.FromDays( 1 ), TimeSpan.FromDays( 2 ) ); - Register( DecayLevel.IDOC, TimeSpan.FromHours( 12 ), TimeSpan.FromHours( 24 ) ); - } + public static bool Enabled => Core.ML; - public static void Register( DecayLevel level, TimeSpan min, TimeSpan max ) - { - DecayStageInfo info = new DecayStageInfo( min, max ); + public static void Register(DecayLevel level, TimeSpan min, TimeSpan max) + { + DecayStageInfo info = new DecayStageInfo(min, max); - if ( m_Stages.ContainsKey( level ) ) - m_Stages[level] = info; - else - m_Stages.Add( level, info ); - } + if (m_Stages.ContainsKey(level)) + m_Stages[level] = info; + else + m_Stages.Add(level, info); + } - public static bool Decays( DecayLevel level ) - { - return m_Stages.ContainsKey( level ); - } + public static bool Decays(DecayLevel level) + { + return m_Stages.ContainsKey(level); + } - public static TimeSpan GetRandomDuration( DecayLevel level ) - { - if ( !m_Stages.ContainsKey( level ) ) - return TimeSpan.Zero; + public static TimeSpan GetRandomDuration(DecayLevel level) + { + if (!m_Stages.ContainsKey(level)) + return TimeSpan.Zero; - DecayStageInfo info = m_Stages[level]; - long min = info.MinDuration.Ticks; - long max = info.MaxDuration.Ticks; + DecayStageInfo info = m_Stages[level]; + long min = info.MinDuration.Ticks; + long max = info.MaxDuration.Ticks; - return TimeSpan.FromTicks( min + (long)( Utility.RandomDouble() * ( max - min ) ) ); - } - } + return TimeSpan.FromTicks(min + (long)(Utility.RandomDouble() * (max - min))); + } + } - public class DecayStageInfo - { - public TimeSpan MinDuration { get; } + public class DecayStageInfo + { + public DecayStageInfo(TimeSpan min, TimeSpan max) + { + MinDuration = min; + MaxDuration = max; + } - public TimeSpan MaxDuration { get; } + public TimeSpan MinDuration{ get; } - public DecayStageInfo( TimeSpan min, TimeSpan max ) - { - MinDuration = min; - MaxDuration = max; - } - } -} + public TimeSpan MaxDuration{ get; } + } +} \ No newline at end of file diff --git a/Scripts/Multis/HouseFoundation.cs b/Scripts/Multis/HouseFoundation.cs index 68c172ae6..06bd4ede1 100644 --- a/Scripts/Multis/HouseFoundation.cs +++ b/Scripts/Multis/HouseFoundation.cs @@ -11,2491 +11,2661 @@ using Server.Spells; namespace Server.Multis { - public enum FoundationType - { - Stone, - DarkWood, - LightWood, - Dungeon, - Brick, - ElvenGrey, - ElvenNatural, - Crystal, - Shadow - } - - public class HouseFoundation : BaseHouse - { - private DesignState m_Current; // State which is currently visible. - private DesignState m_Design; // State of current design. - private DesignState m_Backup; // State at last user backup. + public enum FoundationType + { + Stone, + DarkWood, + LightWood, + Dungeon, + Brick, + ElvenGrey, + ElvenNatural, + Crystal, + Shadow + } + + public class HouseFoundation : BaseHouse + { + private static ComponentVerification m_Verification; + + public static readonly bool AllowStairSectioning = true; + + /* Stair block IDs + * (sorted ascending) + */ + private static int[] m_BlockIDs = + { + 0x3EE, 0x709, 0x71E, 0x721, + 0x738, 0x750, 0x76C, 0x788, + 0x7A3, 0x7BA, 0x35D2, 0x3609, + 0x4317, 0x4318, 0x4B07, 0x7807 + }; + + /* Stair sequence IDs + * (sorted ascending) + * Use this for stairs in the proper N,W,S,E sequence + */ + private static int[] m_StairSeqs = + { + 0x3EF, 0x70A, 0x722, 0x739, + 0x751, 0x76D, 0x789, 0x7A4 + }; + + /* Other stair IDs + * Listed in order: north, west, south, east + * Use this for stairs not in the proper sequence + */ + private static int[] m_StairIDs = + { + 0x71F, 0x736, 0x737, 0x749, + 0x35D4, 0x35D3, 0x35D6, 0x35D5, + 0x360B, 0x360A, 0x360D, 0x360C, + 0x4360, 0x435E, 0x435F, 0x4361, + 0x435C, 0x435A, 0x435B, 0x435D, + 0x4364, 0x4362, 0x4363, 0x4365, + 0x4B05, 0x4B04, 0x4B34, 0x4B33, + 0x7809, 0x7808, 0x780A, 0x780B, + 0x7BB, 0x7BC + }; + + private DesignState m_Backup; // State at last user backup. + private DesignState m_Current; // State which is currently visible. + + private int m_DefaultPrice; + private DesignState m_Design; // State of current design. + + public HouseFoundation(Mobile owner, int multiID, int maxLockdowns, int maxSecures) + : base(multiID, owner, maxLockdowns, maxSecures) + { + SignpostGraphic = 9; + + Fixtures = new List(); + + int x = Components.Min.X; + int y = Components.Height - 1 - Components.Center.Y; + + SignHanger = new Static(0xB98); + SignHanger.MoveToWorld(new Point3D(X + x, Y + y, Z + 7), Map); + + CheckSignpost(); + + SetSign(x, y, 7); + } + + public HouseFoundation(Serial serial) + : base(serial) + { + } + + public FoundationType Type{ get; set; } + + public int LastRevision{ get; set; } + + public List Fixtures{ get; private set; } + + public Item SignHanger{ get; private set; } + + public Item Signpost{ get; private set; } + + public int SignpostGraphic{ get; set; } + + public Mobile Customizer{ get; set; } + + public override bool IsAosRules => true; + + public override bool IsActive => Customizer == null; + + public virtual int CustomizationCost => Core.AOS ? 0 : 10000; + + public override MultiComponentList Components + { + get + { + if (m_Current == null) + SetInitialState(); + + return m_Current.Components; + } + } + + public DesignState CurrentState + { + get + { + if (m_Current == null) SetInitialState(); + return m_Current; + } + set => m_Current = value; + } + + public DesignState DesignState + { + get + { + if (m_Design == null) SetInitialState(); + return m_Design; + } + set => m_Design = value; + } + + public DesignState BackupState + { + get + { + if (m_Backup == null) SetInitialState(); + return m_Backup; + } + set => m_Backup = value; + } + + public override Rectangle2D[] Area + { + get + { + MultiComponentList mcl = Components; - public FoundationType Type { get; set; } + return new[] { new Rectangle2D(mcl.Min.X, mcl.Min.Y, mcl.Width, mcl.Height) }; + } + } - public int LastRevision { get; set; } + public override Point3D BaseBanLocation => + new Point3D(Components.Min.X, Components.Height - 1 - Components.Center.Y, 0); - public List Fixtures { get; private set; } + public override int DefaultPrice => m_DefaultPrice; - public Item SignHanger { get; private set; } + public int MaxLevels + { + get + { + MultiComponentList mcl = Components; - public Item Signpost { get; private set; } + if (mcl.Width >= 14 || mcl.Height >= 14) + return 4; + return 3; + } + } - public int SignpostGraphic { get; set; } + public static ComponentVerification Verification + { + get + { + if (m_Verification == null) + m_Verification = new ComponentVerification(); - public Mobile Customizer { get; set; } + return m_Verification; + } + } - public override bool IsAosRules => true; + public bool IsFixture(Item item) + { + return Fixtures != null && Fixtures.Contains(item); + } - public override bool IsActive => Customizer == null; + public override int GetMaxUpdateRange() + { + return 24; + } + + public override int GetUpdateRange(Mobile m) + { + int w = CurrentState.Components.Width; + int h = CurrentState.Components.Height - 1; + int v = 18 + (w > h ? w : h) / 2; + + if (v > 24) + v = 24; + else if (v < 18) + v = 18; + + return v; + } + + public void SetInitialState() + { + // This is a new house, it has not yet loaded a design state + m_Current = new DesignState(this, GetEmptyFoundation()); + m_Design = new DesignState(m_Current); + m_Backup = new DesignState(m_Current); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + SignHanger?.Delete(); + + Signpost?.Delete(); + + if (Fixtures == null) + return; + + for (int i = 0; i < Fixtures.Count; ++i) + { + Item item = Fixtures[i]; + + item?.Delete(); + } + + Fixtures.Clear(); + } + + public override void OnLocationChange(Point3D oldLocation) + { + base.OnLocationChange(oldLocation); + + int x = Location.X - oldLocation.X; + int y = Location.Y - oldLocation.Y; + int z = Location.Z - oldLocation.Z; + + SignHanger?.MoveToWorld(new Point3D(SignHanger.X + x, SignHanger.Y + y, SignHanger.Z + z), Map); + + Signpost?.MoveToWorld(new Point3D(Signpost.X + x, Signpost.Y + y, Signpost.Z + z), Map); + + if (Fixtures == null) + return; + + for (int i = 0; i < Fixtures.Count; ++i) + { + Item item = Fixtures[i]; + + if (Doors.Contains(item)) + continue; + + item.MoveToWorld(new Point3D(item.X + x, item.Y + y, item.Z + z), Map); + } + } + + public override void OnMapChange() + { + base.OnMapChange(); + + if (SignHanger != null) + SignHanger.Map = Map; + + if (Signpost != null) + Signpost.Map = Map; + + if (Fixtures == null) + return; + + for (int i = 0; i < Fixtures.Count; ++i) + Fixtures[i].Map = Map; + } + + public void ClearFixtures(Mobile from) + { + if (Fixtures == null) + return; + + RemoveKeys(from); + + for (int i = 0; i < Fixtures.Count; ++i) + { + Fixtures[i].Delete(); + Doors.Remove(Fixtures[i]); + } + + Fixtures.Clear(); + } + + public void AddFixtures(Mobile from, MultiTileEntry[] list) + { + if (Fixtures == null) + Fixtures = new List(); + + uint keyValue = 0; + + for (int i = 0; i < list.Length; ++i) + { + MultiTileEntry mte = list[i]; + int itemID = mte.m_ItemID; + + if (itemID >= 0x181D && itemID < 0x1829) + { + HouseTeleporter tp = new HouseTeleporter(itemID); + + AddFixture(tp, mte); + } + else + { + BaseDoor door = null; + + if (itemID >= 0x675 && itemID < 0x6F5) + { + int type = (itemID - 0x675) / 16; + DoorFacing facing = (DoorFacing)((itemID - 0x675) / 2 % 8); + + switch (type) + { + case 0: + door = new GenericHouseDoor(facing, 0x675, 0xEC, 0xF3); + break; + case 1: + door = new GenericHouseDoor(facing, 0x685, 0xEC, 0xF3); + break; + case 2: + door = new GenericHouseDoor(facing, 0x695, 0xEB, 0xF2); + break; + case 3: + door = new GenericHouseDoor(facing, 0x6A5, 0xEA, 0xF1); + break; + case 4: + door = new GenericHouseDoor(facing, 0x6B5, 0xEA, 0xF1); + break; + case 5: + door = new GenericHouseDoor(facing, 0x6C5, 0xEC, 0xF3); + break; + case 6: + door = new GenericHouseDoor(facing, 0x6D5, 0xEA, 0xF1); + break; + case 7: + door = new GenericHouseDoor(facing, 0x6E5, 0xEA, 0xF1); + break; + } + } + else if (itemID >= 0x314 && itemID < 0x364) + { + int type = (itemID - 0x314) / 16; + DoorFacing facing = (DoorFacing)((itemID - 0x314) / 2 % 8); + door = new GenericHouseDoor(facing, 0x314 + type * 16, 0xED, 0xF4); + } + else if (itemID >= 0x824 && itemID < 0x834) + { + DoorFacing facing = (DoorFacing)((itemID - 0x824) / 2 % 8); + door = new GenericHouseDoor(facing, 0x824, 0xEC, 0xF3); + } + else if (itemID >= 0x839 && itemID < 0x849) + { + DoorFacing facing = (DoorFacing)((itemID - 0x839) / 2 % 8); + door = new GenericHouseDoor(facing, 0x839, 0xEB, 0xF2); + } + else if (itemID >= 0x84C && itemID < 0x85C) + { + DoorFacing facing = (DoorFacing)((itemID - 0x84C) / 2 % 8); + door = new GenericHouseDoor(facing, 0x84C, 0xEC, 0xF3); + } + else if (itemID >= 0x866 && itemID < 0x876) + { + DoorFacing facing = (DoorFacing)((itemID - 0x866) / 2 % 8); + door = new GenericHouseDoor(facing, 0x866, 0xEB, 0xF2); + } + else if (itemID >= 0xE8 && itemID < 0xF8) + { + DoorFacing facing = (DoorFacing)((itemID - 0xE8) / 2 % 8); + door = new GenericHouseDoor(facing, 0xE8, 0xED, 0xF4); + } + else if (itemID >= 0x1FED && itemID < 0x1FFD) + { + DoorFacing facing = (DoorFacing)((itemID - 0x1FED) / 2 % 8); + door = new GenericHouseDoor(facing, 0x1FED, 0xEC, 0xF3); + } + else if (itemID >= 0x241F && itemID < 0x2421) + { + //DoorFacing facing = (DoorFacing)(((itemID - 0x241F) / 2) % 8); + door = new GenericHouseDoor(DoorFacing.NorthCCW, 0x2415, -1, -1); + } + else if (itemID >= 0x2423 && itemID < 0x2425) + { + //DoorFacing facing = (DoorFacing)(((itemID - 0x241F) / 2) % 8); + //This one and the above one are 'special' cases, ie: OSI had the ItemID pattern discombobulated for these + door = new GenericHouseDoor(DoorFacing.WestCW, 0x2423, -1, -1); + } + else if (itemID >= 0x2A05 && itemID < 0x2A1D) + { + DoorFacing facing = (DoorFacing)((itemID - 0x2A05) / 2 % 4 + 8); + + int sound = itemID >= 0x2A0D && itemID < 0x2a15 ? 0x539 : -1; + + door = new GenericHouseDoor(facing, 0x29F5 + 8 * ((itemID - 0x2A05) / 8), sound, sound); + } + else if (itemID == 0x2D46) + { + door = new GenericHouseDoor(DoorFacing.NorthCW, 0x2D46, 0xEA, 0xF1, false); + } + else if (itemID == 0x2D48 || itemID == 0x2FE2) + { + door = new GenericHouseDoor(DoorFacing.SouthCCW, itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x2D63 && itemID < 0x2D70) + { + int mod = (itemID - 0x2D63) / 2 % 2; + DoorFacing facing = mod == 0 ? DoorFacing.SouthCCW : DoorFacing.WestCCW; + + int type = (itemID - 0x2D63) / 4; + + door = new GenericHouseDoor(facing, 0x2D63 + 4 * type + mod * 2, 0xEA, 0xF1, false); + } + else if (itemID == 0x2FE4 || itemID == 0x31AE) + { + door = new GenericHouseDoor(DoorFacing.WestCCW, itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x319C && itemID < 0x31AE) + { + //special case for 0x31aa <-> 0x31a8 (a9) + + int mod = (itemID - 0x319C) / 2 % 2; + + bool specialCase = itemID == 0x31AA || itemID == 0x31A8; + + DoorFacing facing; + + if (itemID == 0x31AA || itemID == 0x31A8) + facing = mod == 0 ? DoorFacing.NorthCW : DoorFacing.EastCW; + else + facing = mod == 0 ? DoorFacing.EastCW : DoorFacing.NorthCW; + + int type = (itemID - 0x319C) / 4; + + door = new GenericHouseDoor(facing, 0x319C + 4 * type + mod * 2, 0xEA, 0xF1, false); + } + else if (itemID >= 0x367B && itemID < 0x369B) + { + int type = (itemID - 0x367B) / 16; + DoorFacing facing = (DoorFacing)((itemID - 0x367B) / 2 % 8); + + switch (type) + { + case 0: + door = new GenericHouseDoor(facing, 0x367B, 0xED, 0xF4); + break; //crystal + case 1: + door = new GenericHouseDoor(facing, 0x368B, 0xEC, 0x3E7); + break; //shadow + } + } + else if (itemID >= 0x409B && itemID < 0x40A3) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x409B), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x410C && itemID < 0x4114) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x410C), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x41C2 && itemID < 0x41CA) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x41C2), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x41CF && itemID < 0x41D7) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x41CF), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x436E && itemID < 0x437E) + { + /* These ones had to be different... + * Offset 0 2 4 6 8 10 12 14 + * DoorFacing 2 3 2 3 6 7 6 7 + */ + int offset = itemID - 0x436E; + DoorFacing facing = (DoorFacing)((offset / 2 + 2 * ((1 + offset / 4) % 2)) % 8); + door = new GenericHouseDoor(facing, itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x46DD && itemID < 0x46E5) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x46DD), itemID, 0xEB, 0xF2, false); + } + else if (itemID >= 0x4D22 && itemID < 0x4D2A) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x4D22), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x50C8 && itemID < 0x50D0) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x50C8), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x50D0 && itemID < 0x50D8) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x50D0), itemID, 0xEA, 0xF1, false); + } + else if (itemID >= 0x5142 && itemID < 0x514A) + { + door = new GenericHouseDoor(GetSADoorFacing(itemID - 0x5142), itemID, 0xF0, 0xEF, false); + } + + if (door != null) + { + if (keyValue == 0) + keyValue = CreateKeys(from); + + door.Locked = true; + door.KeyValue = keyValue; + + AddDoor(door, mte.m_OffsetX, mte.m_OffsetY, mte.m_OffsetZ); + Fixtures.Add(door); + } + } + } + + for (int i = 0; i < Fixtures.Count; ++i) + { + Item fixture = Fixtures[i]; + + if (fixture is HouseTeleporter) + { + HouseTeleporter tp = (HouseTeleporter)fixture; + + for (int j = 1; j <= Fixtures.Count; ++j) + { + HouseTeleporter check = Fixtures[(i + j) % Fixtures.Count] as HouseTeleporter; + + if (check != null && check.ItemID == tp.ItemID) + { + tp.Target = check; + break; + } + } + } + else if (fixture is BaseHouseDoor) + { + BaseHouseDoor door = (BaseHouseDoor)fixture; + + if (door.Link != null) + continue; + + DoorFacing linkFacing; + int xOffset, yOffset; + + switch (door.Facing) + { + default: + case DoorFacing.WestCW: + linkFacing = DoorFacing.EastCCW; + xOffset = 1; + yOffset = 0; + break; + case DoorFacing.EastCCW: + linkFacing = DoorFacing.WestCW; + xOffset = -1; + yOffset = 0; + break; + case DoorFacing.WestCCW: + linkFacing = DoorFacing.EastCW; + xOffset = 1; + yOffset = 0; + break; + case DoorFacing.EastCW: + linkFacing = DoorFacing.WestCCW; + xOffset = -1; + yOffset = 0; + break; + case DoorFacing.SouthCW: + linkFacing = DoorFacing.NorthCCW; + xOffset = 0; + yOffset = -1; + break; + case DoorFacing.NorthCCW: + linkFacing = DoorFacing.SouthCW; + xOffset = 0; + yOffset = 1; + break; + case DoorFacing.SouthCCW: + linkFacing = DoorFacing.NorthCW; + xOffset = 0; + yOffset = -1; + break; + case DoorFacing.NorthCW: + linkFacing = DoorFacing.SouthCCW; + xOffset = 0; + yOffset = 1; + break; + case DoorFacing.SouthSW: + linkFacing = DoorFacing.SouthSE; + xOffset = 1; + yOffset = 0; + break; + case DoorFacing.SouthSE: + linkFacing = DoorFacing.SouthSW; + xOffset = -1; + yOffset = 0; + break; + case DoorFacing.WestSN: + linkFacing = DoorFacing.WestSS; + xOffset = 0; + yOffset = 1; + break; + case DoorFacing.WestSS: + linkFacing = DoorFacing.WestSN; + xOffset = 0; + yOffset = -1; + break; + } + + for (int j = i + 1; j < Fixtures.Count; ++j) + { + BaseHouseDoor check = Fixtures[j] as BaseHouseDoor; + + if (check != null && check.Link == null && check.Facing == linkFacing && + check.X - door.X == xOffset && check.Y - door.Y == yOffset && check.Z == door.Z) + { + check.Link = door; + door.Link = check; + break; + } + } + } + } + } + + private static DoorFacing GetSADoorFacing(int offset) + { + /* Offset 0 2 4 6 + * DoorFacing 2 3 6 7 + */ + return (DoorFacing)((offset / 2 + 2 * (1 + offset / 4)) % 8); + } + + public void AddFixture(Item item, MultiTileEntry mte) + { + Fixtures.Add(item); + item.MoveToWorld(new Point3D(X + mte.m_OffsetX, Y + mte.m_OffsetY, Z + mte.m_OffsetZ), Map); + } + + public static void GetFoundationGraphics(FoundationType type, out int east, out int south, out int post, + out int corner) + { + switch (type) + { + default: + case FoundationType.DarkWood: + corner = 0x0014; + east = 0x0015; + south = 0x0016; + post = 0x0017; + break; + case FoundationType.LightWood: + corner = 0x00BD; + east = 0x00BE; + south = 0x00BF; + post = 0x00C0; + break; + case FoundationType.Dungeon: + corner = 0x02FD; + east = 0x02FF; + south = 0x02FE; + post = 0x0300; + break; + case FoundationType.Brick: + corner = 0x0041; + east = 0x0043; + south = 0x0042; + post = 0x0044; + break; + case FoundationType.Stone: + corner = 0x0065; + east = 0x0064; + south = 0x0063; + post = 0x0066; + break; + + case FoundationType.ElvenGrey: + corner = 0x2DF7; + east = 0x2DF9; + south = 0x2DFA; + post = 0x2DF8; + break; + case FoundationType.ElvenNatural: + corner = 0x2DFB; + east = 0x2DFD; + south = 0x2DFE; + post = 0x2DFC; + break; + + case FoundationType.Crystal: + corner = 0x3672; + east = 0x3671; + south = 0x3670; + post = 0x3673; + break; + case FoundationType.Shadow: + corner = 0x3676; + east = 0x3675; + south = 0x3674; + post = 0x3677; + break; + } + } + + public static void ApplyFoundation(FoundationType type, MultiComponentList mcl) + { + int east, south, post, corner; + + GetFoundationGraphics(type, out east, out south, out post, out corner); + + int xCenter = mcl.Center.X; + int yCenter = mcl.Center.Y; + + mcl.Add(post, 0 - xCenter, 0 - yCenter, 0); + mcl.Add(corner, mcl.Width - 1 - xCenter, mcl.Height - 2 - yCenter, 0); + + for (int x = 1; x < mcl.Width; ++x) + { + mcl.Add(south, x - xCenter, 0 - yCenter, 0); + + if (x < mcl.Width - 1) + mcl.Add(south, x - xCenter, mcl.Height - 2 - yCenter, 0); + } + + for (int y = 1; y < mcl.Height - 1; ++y) + { + mcl.Add(east, 0 - xCenter, y - yCenter, 0); + + if (y < mcl.Height - 2) + mcl.Add(east, mcl.Width - 1 - xCenter, y - yCenter, 0); + } + } + + public static void AddStairsTo(ref MultiComponentList mcl) + { + // copy the original.. + mcl = new MultiComponentList(mcl); + + mcl.Resize(mcl.Width, mcl.Height + 1); + + int xCenter = mcl.Center.X; + int yCenter = mcl.Center.Y; + int y = mcl.Height - 1; + + for (int x = 0; x < mcl.Width; ++x) + mcl.Add(0x63, x - xCenter, y - yCenter, 0); + } + + public MultiComponentList GetEmptyFoundation() + { + // Copy original foundation layout + MultiComponentList mcl = new MultiComponentList(MultiData.GetComponents(ItemID)); + + mcl.Resize(mcl.Width, mcl.Height + 1); + + int xCenter = mcl.Center.X; + int yCenter = mcl.Center.Y; + int y = mcl.Height - 1; + + ApplyFoundation(Type, mcl); + + for (int x = 1; x < mcl.Width; ++x) + mcl.Add(0x751, x - xCenter, y - yCenter, 0); + + return mcl; + } + + public void CheckSignpost() + { + MultiComponentList mcl = Components; + + int x = mcl.Min.X; + int y = mcl.Height - 2 - mcl.Center.Y; + + if (CheckWall(mcl, x, y)) + { + Signpost?.Delete(); + + Signpost = null; + } + else if (Signpost == null) + { + Signpost = new Static(SignpostGraphic); + Signpost.MoveToWorld(new Point3D(X + x, Y + y, Z + 7), Map); + } + else + { + Signpost.ItemID = SignpostGraphic; + Signpost.MoveToWorld(new Point3D(X + x, Y + y, Z + 7), Map); + } + } + + public bool CheckWall(MultiComponentList mcl, int x, int y) + { + x += mcl.Center.X; + y += mcl.Center.Y; - public virtual int CustomizationCost => (Core.AOS ? 0 : 10000); + if (x >= 0 && x < mcl.Width && y >= 0 && y < mcl.Height) + { + StaticTile[] tiles = mcl.Tiles[x][y]; - public bool IsFixture( Item item ) - { - return (Fixtures != null && Fixtures.Contains( item )); - } + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; - public override MultiComponentList Components - { - get - { - if ( m_Current == null ) - SetInitialState(); + if (tile.Z == 7 && tile.Height == 20) + return true; + } + } - return m_Current.Components; - } - } + return false; + } + + public void BeginCustomize(Mobile m) + { + if (!m.CheckAlive()) return; + + if (SpellHelper.CheckCombat(m)) + { + m.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + return; + } + + RelocateEntities(); + + foreach (Item item in GetItems()) item.Location = BanLocation; + + foreach (Mobile mobile in GetMobiles()) + if (mobile != m) + mobile.Location = BanLocation; + + DesignContext.Add(m, this); + m.Send(new BeginHouseCustomization(this)); + + NetState ns = m.NetState; + if (ns != null) + SendInfoTo(ns); - public override int GetMaxUpdateRange() - { - return 24; - } + DesignState.SendDetailedInfoTo(ns); + } + + public override void SendInfoTo(NetState state, bool sendOplPacket) + { + base.SendInfoTo(state, sendOplPacket); + + DesignContext context = DesignContext.Find(state.Mobile); + DesignState stateToSend; + + if (context != null && context.Foundation == this) + stateToSend = DesignState; + else + stateToSend = CurrentState; + + stateToSend.SendGeneralInfoTo(state); + } + + public override void Serialize(GenericWriter writer) + { + writer.Write(5); // version + + writer.Write(Signpost); + writer.Write(SignpostGraphic); + + writer.Write((int)Type); + + writer.Write(SignHanger); + + writer.Write(LastRevision); + writer.Write(Fixtures, true); + + CurrentState.Serialize(writer); + DesignState.Serialize(writer); + BackupState.Serialize(writer); + + base.Serialize(writer); + } + + public override void Deserialize(GenericReader reader) + { + int version = reader.ReadInt(); + + switch (version) + { + case 5: + case 4: + { + Signpost = reader.ReadItem(); + SignpostGraphic = reader.ReadInt(); + + goto case 3; + } + case 3: + { + Type = (FoundationType)reader.ReadInt(); + + goto case 2; + } + case 2: + { + SignHanger = reader.ReadItem(); + + goto case 1; + } + case 1: + { + if (version < 5) + m_DefaultPrice = reader.ReadInt(); + + goto case 0; + } + case 0: + { + if (version < 3) + Type = FoundationType.Stone; + + if (version < 4) + SignpostGraphic = 9; + + LastRevision = reader.ReadInt(); + Fixtures = reader.ReadStrongItemList(); + + m_Current = new DesignState(this, reader); + m_Design = new DesignState(this, reader); + m_Backup = new DesignState(this, reader); + + break; + } + } + + base.Deserialize(reader); + } + + public bool IsHiddenToCustomizer(Item item) + { + return item == Signpost || item == SignHanger || item == Sign || IsFixture(item); + } + + public static void Initialize() + { + PacketHandlers.RegisterExtended(0x1E, true, QueryDesignDetails); + + PacketHandlers.RegisterEncoded(0x02, true, Designer_Backup); + PacketHandlers.RegisterEncoded(0x03, true, Designer_Restore); + PacketHandlers.RegisterEncoded(0x04, true, Designer_Commit); + PacketHandlers.RegisterEncoded(0x05, true, Designer_Delete); + PacketHandlers.RegisterEncoded(0x06, true, Designer_Build); + PacketHandlers.RegisterEncoded(0x0C, true, Designer_Close); + PacketHandlers.RegisterEncoded(0x0D, true, Designer_Stairs); + PacketHandlers.RegisterEncoded(0x0E, true, Designer_Sync); + PacketHandlers.RegisterEncoded(0x10, true, Designer_Clear); + PacketHandlers.RegisterEncoded(0x12, true, Designer_Level); + + PacketHandlers.RegisterEncoded(0x13, true, Designer_Roof); // Samurai Empire roof + PacketHandlers.RegisterEncoded(0x14, true, Designer_RoofDelete); // Samurai Empire roof + + PacketHandlers.RegisterEncoded(0x1A, true, Designer_Revert); + + EventSink.Speech += EventSink_Speech; + } + + private static void EventSink_Speech(SpeechEventArgs e) + { + if (DesignContext.Find(e.Mobile) != null) + { + e.Mobile.SendLocalizedMessage(1061925); // You cannot speak while customizing your house. + e.Blocked = true; + } + } + + public static void Designer_Sync(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client requested state synchronization + * - Resend full house state + */ + + DesignState design = context.Foundation.DesignState; + + // Resend full house state + design.SendDetailedInfoTo(state); + } + } + + public static void Designer_Clear(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to clear the design + * - Restore empty foundation + * - Construct new design state from empty foundation + * - Assign constructed state to foundation + * - Update revision + * - Update client with new state + */ + + // Restore empty foundation : Construct new design state from empty foundation + DesignState newDesign = new DesignState(context.Foundation, context.Foundation.GetEmptyFoundation()); + + // Restore empty foundation : Assign constructed state to foundation + context.Foundation.DesignState = newDesign; + + // Update revision + newDesign.OnRevised(); + + // Update client with new state + context.Foundation.SendInfoTo(state); + newDesign.SendDetailedInfoTo(state); + } + } + + public static void Designer_Restore(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to restore design to the last backup state + * - Restore backup + * - Construct new design state from backup state + * - Assign constructed state to foundation + * - Update revision + * - Update client with new state + */ + + // Restore backup : Construct new design state from backup state + DesignState backupDesign = new DesignState(context.Foundation.BackupState); + + // Restore backup : Assign constructed state to foundation + context.Foundation.DesignState = backupDesign; + + // Update revision; + backupDesign.OnRevised(); + + // Update client with new state + context.Foundation.SendInfoTo(state); + backupDesign.SendDetailedInfoTo(state); + } + } + + public static void Designer_Backup(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to backup design state + * - Construct a copy of the current design state + * - Assign constructed state to backup state field + */ + + // Construct a copy of the current design state + DesignState copyState = new DesignState(context.Foundation.DesignState); + + // Assign constructed state to backup state field + context.Foundation.BackupState = copyState; + } + } + + public static void Designer_Revert(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to revert design state to currently visible state + * - Revert design state + * - Construct a copy of the current visible state + * - Freeze fixtures in constructed state + * - Assign constructed state to foundation + * - If a signpost is needed, add it + * - Update revision + * - Update client with new state + */ + + // Revert design state : Construct a copy of the current visible state + DesignState copyState = new DesignState(context.Foundation.CurrentState); + + // Revert design state : Freeze fixtures in constructed state + copyState.FreezeFixtures(); + + // Revert design state : Assign constructed state to foundation + context.Foundation.DesignState = copyState; + + // Revert design state : If a signpost is needed, add it + context.Foundation.CheckSignpost(); + + // Update revision + copyState.OnRevised(); + + // Update client with new state + context.Foundation.SendInfoTo(state); + copyState.SendDetailedInfoTo(state); + } + } + + public void EndConfirmCommit(Mobile from) + { + int oldPrice = Price; + int newPrice = oldPrice + CustomizationCost + + (DesignState.Components.List.Length - + (CurrentState.Components.List.Length + CurrentState.Fixtures.Length)) * 500; + int cost = newPrice - oldPrice; + + if (!Deleted) + { + // Temporary Fix. We should be booting a client out of customization mode in the delete handler. + if (from.AccessLevel >= AccessLevel.GameMaster && cost != 0) + { + from.SendMessage("{0} gold would have been {1} your bank if you were not a GM.", cost.ToString(), + cost > 0 ? "withdrawn from" : "deposited into"); + } + else + { + if (cost > 0) + { + if (Banker.Withdraw(from, cost)) + { + from.SendLocalizedMessage(1060398, + cost.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. + } + else + { + from.SendLocalizedMessage( + 1061903); // You cannot commit this house design, because you do not have the necessary funds in your bank box to pay for the upgrade. Please back up your design, obtain the required funds, and commit your design again. + return; + } + } + else if (cost < 0) + { + if (Banker.Deposit(from, -cost)) + from.SendLocalizedMessage(1060397, + (-cost).ToString()); // ~1_AMOUNT~ gold has been deposited into your bank box. + else + return; + } + } + } + + /* Client chose to commit current design state + * - Commit design state + * - Construct a copy of the current design state + * - Clear visible fixtures + * - Melt fixtures from constructed state + * - Add melted fixtures from constructed state + * - Assign constructed state to foundation + * - Update house price + * - Remove design context + * - Notify the client that customization has ended + * - Notify the core that the foundation has changed and should be resent to all clients + * - If a signpost is needed, add it + * - Eject all from house + * - Restore relocated entities + */ + + // Commit design state : Construct a copy of the current design state + DesignState copyState = new DesignState(DesignState); + + // Commit design state : Clear visible fixtures + ClearFixtures(from); + + // Commit design state : Melt fixtures from constructed state + copyState.MeltFixtures(); + + // Commit design state : Add melted fixtures from constructed state + AddFixtures(from, copyState.Fixtures); + + // Commit design state : Assign constructed state to foundation + CurrentState = copyState; + + // Update house price + Price = newPrice - CustomizationCost; + + // Remove design context + DesignContext.Remove(from); + + // Notify the client that customization has ended + from.Send(new EndHouseCustomization(this)); + + // Notify the core that the foundation has changed and should be resent to all clients + Delta(ItemDelta.Update); + ProcessDelta(); + CurrentState.SendDetailedInfoTo(from.NetState); + + // If a signpost is needed, add it + CheckSignpost(); + + // Eject all from house + from.RevealingAction(); + + foreach (Item item in GetItems()) + item.Location = BanLocation; + + foreach (Mobile mobile in GetMobiles()) + mobile.Location = BanLocation; + + // Restore relocated entities + RestoreRelocatedEntities(); + } + + public static void Designer_Commit(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + int oldPrice = context.Foundation.Price; + int newPrice = oldPrice + context.Foundation.CustomizationCost + + (context.Foundation.DesignState.Components.List.Length - + (context.Foundation.CurrentState.Components.List.Length + + context.Foundation.Fixtures.Count)) * 500; + int bankBalance = Banker.GetBalance(from); + + from.SendGump(new ConfirmCommitGump(from, context.Foundation, bankBalance, oldPrice, newPrice)); + } + } + + public static int GetLevelZ(int level, HouseFoundation house) + { + if (level < 1 || level > house.MaxLevels) + level = 1; + + return (level - 1) * 20 + 7; + + /* + switch( level ) + { + default: + case 1: return 07; + case 2: return 27; + case 3: return 47; + case 4: return 67; + } + * */ + } + + public static int GetZLevel(int z, HouseFoundation house) + { + int level = (z - 7) / 20 + 1; + + if (level < 1 || level > house.MaxLevels) + level = 1; + + return level; + } + + public static bool ValidPiece(int itemID) + { + return ValidPiece(itemID, false); + } + + public static bool ValidPiece(int itemID, bool roof) + { + itemID &= TileData.MaxItemValue; + + if (!roof && (TileData.ItemTable[itemID].Flags & TileFlag.Roof) != 0) + return false; + if (roof && (TileData.ItemTable[itemID].Flags & TileFlag.Roof) == 0) + return false; + + return Verification.IsItemValid(itemID); + } + + public static bool IsStairBlock(int id) + { + int delta = -1; + + for (int i = 0; delta < 0 && i < m_BlockIDs.Length; ++i) + delta = m_BlockIDs[i] - id; + + return delta == 0; + } + + public static bool IsStair(int id, ref int dir) + { + //dir n=0 w=1 s=2 e=3 + int delta = -4; + + for (int i = 0; delta < -3 && i < m_StairSeqs.Length; ++i) + delta = m_StairSeqs[i] - id; + + if (delta >= -3 && delta <= 0) + { + dir = -delta; + return true; + } + + for (int i = 0; i < m_StairIDs.Length; ++i) + if (m_StairIDs[i] == id) + { + dir = i % 4; + return true; + } + + return false; + } + + public static bool DeleteStairs(MultiComponentList mcl, int id, int x, int y, int z) + { + int ax = x + mcl.Center.X; + int ay = y + mcl.Center.Y; + + if (ax < 0 || ay < 0 || ax >= mcl.Width || ay >= mcl.Height - 1 || z < 7 || (z - 7) % 5 != 0) + return false; + + if (IsStairBlock(id)) + { + StaticTile[] tiles = mcl.Tiles[ax][ay]; + + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; + + if (tile.Z == z + 5) + { + id = tile.ID; + z = tile.Z; + + if (!IsStairBlock(id)) + break; + } + } + } + + int dir = 0; + + if (!IsStair(id, ref dir)) + return false; + + if (AllowStairSectioning) + return true; // skip deletion + + int height = (z - 7) % 20 / 5; + + int xStart, yStart; + int xInc, yInc; + + switch (dir) + { + default: + case 0: // North + { + xStart = x; + yStart = y + height; + xInc = 0; + yInc = -1; + break; + } + case 1: // West + { + xStart = x + height; + yStart = y; + xInc = -1; + yInc = 0; + break; + } + case 2: // South + { + xStart = x; + yStart = y - height; + xInc = 0; + yInc = 1; + break; + } + case 3: // East + { + xStart = x - height; + yStart = y; + xInc = 1; + yInc = 0; + break; + } + } + + int zStart = z - height * 5; + + for (int i = 0; i < 4; ++i) + { + x = xStart + i * xInc; + y = yStart + i * yInc; + + for (int j = 0; j <= i; ++j) + mcl.RemoveXYZH(x, y, zStart + j * 5, 5); + + ax = x + mcl.Center.X; + ay = y + mcl.Center.Y; + + if (ax >= 1 && ax < mcl.Width && ay >= 1 && ay < mcl.Height - 1) + { + StaticTile[] tiles = mcl.Tiles[ax][ay]; + + bool hasBaseFloor = false; + + for (int j = 0; !hasBaseFloor && j < tiles.Length; ++j) + hasBaseFloor = tiles[j].Z == 7 && tiles[j].ID != 1; + + if (!hasBaseFloor) + mcl.Add(0x31F4, x, y, 7); + } + } + + return true; + } + + public static void Designer_Delete(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to delete a component + * - Read data detailing which component to delete + * - Verify component is deletable + * - Remove the component + * - If needed, replace removed component with a dirt tile + * - Update revision + */ + + // Read data detailing which component to delete + int itemID = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt32(); + int y = pvSrc.ReadInt32(); + int z = pvSrc.ReadInt32(); + + // Verify component is deletable + DesignState design = context.Foundation.DesignState; + MultiComponentList mcl = design.Components; + + int ax = x + mcl.Center.X; + int ay = y + mcl.Center.Y; + + if (z == 0 && ax >= 0 && ax < mcl.Width && ay >= 0 && ay < mcl.Height - 1) + { + /* Component is not deletable + * - Resend design state + * - Return without further processing + */ + + design.SendDetailedInfoTo(state); + return; + } + + bool fixState = false; + + // Remove the component + if (AllowStairSectioning) + { + if (DeleteStairs(mcl, itemID, x, y, z)) + fixState = true; // The client removes the entire set of stairs locally, resend state + + mcl.Remove(itemID, x, y, z); + } + else + { + if (!DeleteStairs(mcl, itemID, x, y, z)) + mcl.Remove(itemID, x, y, z); + } + + // If needed, replace removed component with a dirt tile + if (ax >= 1 && ax < mcl.Width && ay >= 1 && ay < mcl.Height - 1) + { + StaticTile[] tiles = mcl.Tiles[ax][ay]; + + bool hasBaseFloor = false; + + for (int i = 0; !hasBaseFloor && i < tiles.Length; ++i) + hasBaseFloor = tiles[i].Z == 7 && tiles[i].ID != 1; + + if (!hasBaseFloor) mcl.Add(0x31F4, x, y, 7); + } + + // Update revision + design.OnRevised(); + + // Resend design state + if (fixState) + design.SendDetailedInfoTo(state); + } + } + + public static void Designer_Stairs(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to add stairs + * - Read data detailing stair type and location + * - Validate stair multi ID + * - Add the stairs + * - Load data describing the stair components + * - Insert described components + * - Update revision + */ + + // Read data detailing stair type and location + int itemID = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt32(); + int y = pvSrc.ReadInt32(); + + // Validate stair multi ID + DesignState design = context.Foundation.DesignState; + + if (!Verification.IsMultiValid(itemID)) + { + /* Specified multi ID is not a stair + * - Resend design state + * - Return without further processing + */ + + TraceValidity(state, itemID); + design.SendDetailedInfoTo(state); + return; + } + + // Add the stairs + MultiComponentList mcl = design.Components; + + // Add the stairs : Load data describing stair components + MultiComponentList stairs = MultiData.GetComponents(itemID); + + // Add the stairs : Insert described components + int z = GetLevelZ(context.Level, context.Foundation); + + for (int i = 0; i < stairs.List.Length; ++i) + { + MultiTileEntry entry = stairs.List[i]; + + if (entry.m_ItemID != 1) + mcl.Add(entry.m_ItemID, x + entry.m_OffsetX, y + entry.m_OffsetY, z + entry.m_OffsetZ); + } + + // Update revision + design.OnRevised(); + } + } + + private static void TraceValidity(NetState state, int itemID) + { + try + { + using (StreamWriter op = new StreamWriter("comp_val.log", true)) + { + op.WriteLine("{0}\t{1}\tInvalid ItemID 0x{2:X4}", state, state.Mobile, itemID); + } + } + catch + { + } + } + + public static void Designer_Build(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client chose to add a component + * - Read data detailing component graphic and location + * - Add component + * - Update revision + */ + + // Read data detailing component graphic and location + int itemID = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt32(); + int y = pvSrc.ReadInt32(); + + // Add component + DesignState design = context.Foundation.DesignState; + + if (from.AccessLevel < AccessLevel.GameMaster && !ValidPiece(itemID)) + { + TraceValidity(state, itemID); + design.SendDetailedInfoTo(state); + return; + } + + MultiComponentList mcl = design.Components; + + int z = GetLevelZ(context.Level, context.Foundation); + + if (y + mcl.Center.Y == mcl.Height - 1) + z = 0; // Tiles placed on the far-south of the house are at 0 Z + + mcl.Add(itemID, x, y, z); + + // Update revision + design.OnRevised(); + } + } + + public static void Designer_Close(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client closed his house design window + * - Remove design context + * - Notify the client that customization has ended + * - Refresh client with current visible design state + * - If a signpost is needed, add it + * - Eject all from house + * - Restore relocated entities + */ + + // Remove design context + DesignContext.Remove(from); + + // Notify the client that customization has ended + from.Send(new EndHouseCustomization(context.Foundation)); + + // Refresh client with current visible design state + context.Foundation.SendInfoTo(state); + context.Foundation.CurrentState.SendDetailedInfoTo(state); + + // If a signpost is needed, add it + context.Foundation.CheckSignpost(); + + // Eject all from house + from.RevealingAction(); + + foreach (Item item in context.Foundation.GetItems()) + item.Location = context.Foundation.BanLocation; + + foreach (Mobile mobile in context.Foundation.GetMobiles()) + mobile.Location = context.Foundation.BanLocation; + + // Restore relocated entities + context.Foundation.RestoreRelocatedEntities(); + } + } + + public static void Designer_Level(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null) + { + /* Client is moving to a new floor level + * - Read data detailing the target level + * - Validate target level + * - Update design context with new level + * - Teleport mobile to new level + * - Update client + * + */ + + // Read data detailing the target level + int newLevel = pvSrc.ReadInt32(); + + // Validate target level + if (newLevel < 1 || newLevel > context.MaxLevels) + newLevel = 1; + + // Update design context with new level + context.Level = newLevel; + + // Teleport mobile to new level + from.Location = new Point3D(from.X, from.Y, context.Foundation.Z + GetLevelZ(newLevel, context.Foundation)); + + // Update client + context.Foundation.SendInfoTo(state); + } + } + + public static void QueryDesignDetails(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + HouseFoundation foundation = World.FindItem(pvSrc.ReadInt32()) as HouseFoundation; + + if (foundation != null && from.Map == foundation.Map && from.InRange(foundation.GetWorldLocation(), 24) && + from.CanSee(foundation)) + { + DesignState stateToSend; + + if (context != null && context.Foundation == foundation) + stateToSend = foundation.DesignState; + else + stateToSend = foundation.CurrentState; + + stateToSend.SendDetailedInfoTo(state); + } + } + + public static void Designer_Roof(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null && (Core.SE || from.AccessLevel >= AccessLevel.GameMaster)) + { + // Read data detailing component graphic and location + int itemID = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt32(); + int y = pvSrc.ReadInt32(); + int z = pvSrc.ReadInt32(); + + // Add component + DesignState design = context.Foundation.DesignState; + + if (from.AccessLevel < AccessLevel.GameMaster && !ValidPiece(itemID, true)) + { + TraceValidity(state, itemID); + design.SendDetailedInfoTo(state); + return; + } + + MultiComponentList mcl = design.Components; + + if (z < -3 || z > 12 || z % 3 != 0) + z = -3; + z += GetLevelZ(context.Level, context.Foundation); + + MultiTileEntry[] list = mcl.List; + for (int i = 0; i < list.Length; i++) + { + MultiTileEntry mte = list[i]; + + if (mte.m_OffsetX == x && mte.m_OffsetY == y && + GetZLevel(mte.m_OffsetZ, context.Foundation) == context.Level && + (TileData.ItemTable[mte.m_ItemID & TileData.MaxItemValue].Flags & TileFlag.Roof) != 0) + mcl.Remove(mte.m_ItemID, x, y, mte.m_OffsetZ); + } + + mcl.Add(itemID, x, y, z); + + // Update revision + design.OnRevised(); + } + } + + public static void Designer_RoofDelete(NetState state, IEntity e, EncodedReader pvSrc) + { + Mobile from = state.Mobile; + DesignContext context = DesignContext.Find(from); + + if (context != null + ) // No need to check for Core.SE if trying to remove something that shouldn't be able to be placed anyways + { + // Read data detailing which component to delete + int itemID = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt32(); + int y = pvSrc.ReadInt32(); + int z = pvSrc.ReadInt32(); + + // Verify component is deletable + DesignState design = context.Foundation.DesignState; + MultiComponentList mcl = design.Components; + + if ((TileData.ItemTable[itemID & TileData.MaxItemValue].Flags & TileFlag.Roof) == 0) + { + design.SendDetailedInfoTo(state); + return; + } + + mcl.Remove(itemID, x, y, z); + + design.OnRevised(); + } + } + } + + public class DesignState + { + private Packet m_PacketCache; + + public DesignState(HouseFoundation foundation, MultiComponentList components) + { + Foundation = foundation; + Components = components; + Fixtures = new MultiTileEntry[0]; + } + + public DesignState(DesignState toCopy) + { + Foundation = toCopy.Foundation; + Components = new MultiComponentList(toCopy.Components); + Revision = toCopy.Revision; + Fixtures = new MultiTileEntry[toCopy.Fixtures.Length]; + + for (int i = 0; i < Fixtures.Length; ++i) + Fixtures[i] = toCopy.Fixtures[i]; + } + + public DesignState(HouseFoundation foundation, GenericReader reader) + { + Foundation = foundation; + + int version = reader.ReadInt(); + + switch (version) + { + case 0: + { + Components = new MultiComponentList(reader); + + int length = reader.ReadInt(); + + Fixtures = new MultiTileEntry[length]; + + for (int i = 0; i < length; ++i) + { + Fixtures[i].m_ItemID = reader.ReadUShort(); + Fixtures[i].m_OffsetX = reader.ReadShort(); + Fixtures[i].m_OffsetY = reader.ReadShort(); + Fixtures[i].m_OffsetZ = reader.ReadShort(); + Fixtures[i].m_Flags = reader.ReadInt(); + } + + Revision = reader.ReadInt(); + + break; + } + } + } + + public Packet PacketCache + { + get => m_PacketCache; + set + { + if (m_PacketCache == value) + return; + + m_PacketCache?.Release(); + + m_PacketCache = value; + } + } + + public HouseFoundation Foundation{ get; } + + public MultiComponentList Components{ get; } + + public MultiTileEntry[] Fixtures{ get; private set; } + + public int Revision{ get; set; } + + public void Serialize(GenericWriter writer) + { + writer.Write(0); // version + + Components.Serialize(writer); + + writer.Write(Fixtures.Length); + + for (int i = 0; i < Fixtures.Length; ++i) + { + MultiTileEntry ent = Fixtures[i]; + + writer.Write(ent.m_ItemID); + writer.Write(ent.m_OffsetX); + writer.Write(ent.m_OffsetY); + writer.Write(ent.m_OffsetZ); + writer.Write(ent.m_Flags); + } + + writer.Write(Revision); + } + + public void OnRevised() + { + lock (this) + { + Revision = ++Foundation.LastRevision; + + m_PacketCache?.Release(); + + m_PacketCache = null; + } + } + + public void SendGeneralInfoTo(NetState state) + { + state?.Send(new DesignStateGeneral(Foundation, this)); + } + + public void SendDetailedInfoTo(NetState state) + { + if (state != null) + lock (this) + { + if (m_PacketCache == null) + DesignStateDetailed.SendDetails(state, Foundation, this); + else + state.Send(m_PacketCache); + } + } + + public void FreezeFixtures() + { + OnRevised(); + + for (int i = 0; i < Fixtures.Length; ++i) + { + MultiTileEntry mte = Fixtures[i]; + + Components.Add(mte.m_ItemID, mte.m_OffsetX, mte.m_OffsetY, mte.m_OffsetZ); + } + + Fixtures = new MultiTileEntry[0]; + } + + public void MeltFixtures() + { + OnRevised(); + + MultiTileEntry[] list = Components.List; + int length = 0; + + for (int i = list.Length - 1; i >= 0; --i) + { + MultiTileEntry mte = list[i]; + + if (IsFixture(mte.m_ItemID)) + ++length; + } + + Fixtures = new MultiTileEntry[length]; + + for (int i = list.Length - 1; i >= 0; --i) + { + MultiTileEntry mte = list[i]; + + if (IsFixture(mte.m_ItemID)) + { + Fixtures[--length] = mte; + Components.Remove(mte.m_ItemID, mte.m_OffsetX, mte.m_OffsetY, mte.m_OffsetZ); + } + } + } + + public static bool IsFixture(int itemID) + { + if (itemID >= 0x675 && itemID < 0x6F5) + return true; + if (itemID >= 0x314 && itemID < 0x364) + return true; + if (itemID >= 0x824 && itemID < 0x834) + return true; + if (itemID >= 0x839 && itemID < 0x849) + return true; + if (itemID >= 0x84C && itemID < 0x85C) + return true; + if (itemID >= 0x866 && itemID < 0x876) + return true; + if (itemID >= 0x0E8 && itemID < 0x0F8) + return true; + if (itemID >= 0x1FED && itemID < 0x1FFD) + return true; + if (itemID >= 0x181D && itemID < 0x1829) + return true; + if (itemID >= 0x241F && itemID < 0x2421) + return true; + if (itemID >= 0x2423 && itemID < 0x2425) + return true; + if (itemID >= 0x2A05 && itemID < 0x2A1D) + return true; + if (itemID >= 0x319C && itemID < 0x31B0) + return true; + // ML doors + if (itemID == 0x2D46 || itemID == 0x2D48 || itemID == 0x2FE2 || itemID == 0x2FE4) + return true; + if (itemID >= 0x2D63 && itemID < 0x2D70) + return true; + if (itemID >= 0x319C && itemID < 0x31AF) + return true; + if (itemID >= 0x367B && itemID < 0x369B) + return true; + // SA doors + if (itemID >= 0x409B && itemID < 0x40A3) + return true; + if (itemID >= 0x410C && itemID < 0x4114) + return true; + if (itemID >= 0x41C2 && itemID < 0x41CA) + return true; + if (itemID >= 0x41CF && itemID < 0x41D7) + return true; + if (itemID >= 0x436E && itemID < 0x437E) + return true; + if (itemID >= 0x46DD && itemID < 0x46E5) + return true; + if (itemID >= 0x4D22 && itemID < 0x4D2A) + return true; + if (itemID >= 0x50C8 && itemID < 0x50D8) + return true; + if (itemID >= 0x5142 && itemID < 0x514A) + return true; + // TOL doors + if (itemID >= 0x9AD7 && itemID < 0x9AE7) + return true; + if (itemID >= 0x9B3C && itemID < 0x9B4C) + return true; + + return false; + } + } + + public class ConfirmCommitGump : Gump + { + private HouseFoundation m_Foundation; + + public ConfirmCommitGump(Mobile from, HouseFoundation foundation, int bankBalance, int oldPrice, int newPrice) + : base(50, 50) + { + m_Foundation = foundation; + + AddPage(0); + + AddBackground(0, 0, 320, 320, 5054); + + AddImageTiled(10, 10, 300, 20, 2624); + AddImageTiled(10, 40, 300, 240, 2624); + AddImageTiled(10, 290, 300, 20, 2624); + + AddAlphaRegion(10, 10, 300, 300); + + AddHtmlLocalized(10, 10, 300, 20, 1062060, 32736, false, false); //
COMMIT DESIGN
+ + AddHtmlLocalized(10, 40, 300, 140, newPrice - oldPrice <= bankBalance ? 1061898 : 1061903, 1023, false, true); + + AddHtmlLocalized(10, 190, 150, 20, 1061902, 32736, false, false); // Bank Balance: + AddLabel(170, 190, 55, bankBalance.ToString()); + + AddHtmlLocalized(10, 215, 150, 20, 1061899, 1023, false, false); // Old Value: + AddLabel(170, 215, 90, oldPrice.ToString()); + + AddHtmlLocalized(10, 235, 150, 20, 1061900, 1023, false, false); // Cost To Commit: + AddLabel(170, 235, 90, newPrice.ToString()); + + if (newPrice - oldPrice < 0) + { + AddHtmlLocalized(10, 260, 150, 20, 1062059, 992, false, false); // Your Refund: + AddLabel(170, 260, 70, (oldPrice - newPrice).ToString()); + } + else + { + AddHtmlLocalized(10, 260, 150, 20, 1061901, 31744, false, false); // Your Cost: + AddLabel(170, 260, 40, (newPrice - oldPrice).ToString()); + } + + AddButton(10, 290, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 290, 55, 20, 1011036, 32767, false, false); // OKAY + + AddButton(170, 290, 4005, 4007, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(195, 290, 55, 20, 1011012, 32767, false, false); // CANCEL + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (info.ButtonID == 1) + m_Foundation.EndConfirmCommit(sender.Mobile); + } + } + + public class DesignContext + { + public DesignContext(HouseFoundation foundation) + { + Foundation = foundation; + Level = 1; + } - public override int GetUpdateRange( Mobile m ) - { - int w = CurrentState.Components.Width; - int h = CurrentState.Components.Height-1; - int v = 18 + ((w > h ? w : h) / 2); + public HouseFoundation Foundation{ get; } - if ( v > 24 ) - v = 24; - else if ( v < 18 ) - v = 18; + public int Level{ get; set; } - return v; - } + public int MaxLevels => Foundation.MaxLevels; - public DesignState CurrentState - { - get { if ( m_Current == null ) SetInitialState(); return m_Current; } - set => m_Current = value; - } + public static Dictionary Table{ get; } = new Dictionary(); - public DesignState DesignState - { - get { if ( m_Design == null ) SetInitialState(); return m_Design; } - set => m_Design = value; - } + public static DesignContext Find(Mobile from) + { + if (from == null) + return null; - public DesignState BackupState - { - get { if ( m_Backup == null ) SetInitialState(); return m_Backup; } - set => m_Backup = value; - } + Table.TryGetValue(from, out DesignContext d); - public void SetInitialState() - { - // This is a new house, it has not yet loaded a design state - m_Current = new DesignState( this, GetEmptyFoundation() ); - m_Design = new DesignState( m_Current ); - m_Backup = new DesignState( m_Current ); - } + return d; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public static bool Check(Mobile m) + { + if (Find(m) != null) + { + m.SendLocalizedMessage(1062206); // You cannot do that while customizing a house. + return false; + } - SignHanger?.Delete(); + return true; + } - Signpost?.Delete(); + public static void Add(Mobile from, HouseFoundation foundation) + { + if (from == null) + return; - if ( Fixtures == null ) - return; + DesignContext c = new DesignContext(foundation); - for( int i = 0; i < Fixtures.Count; ++i ) - { - Item item = Fixtures[i]; + Table[from] = c; - item?.Delete(); - } + if (from is PlayerMobile) + ((PlayerMobile)from).DesignContext = c; - Fixtures.Clear(); - } + foundation.Customizer = from; - public override void OnLocationChange( Point3D oldLocation ) - { - base.OnLocationChange( oldLocation ); - - int x = Location.X - oldLocation.X; - int y = Location.Y - oldLocation.Y; - int z = Location.Z - oldLocation.Z; - - SignHanger?.MoveToWorld( new Point3D( SignHanger.X + x, SignHanger.Y + y, SignHanger.Z + z ), Map ); - - Signpost?.MoveToWorld( new Point3D( Signpost.X + x, Signpost.Y + y, Signpost.Z + z ), Map ); - - if ( Fixtures == null ) - return; - - for( int i = 0; i < Fixtures.Count; ++i ) - { - Item item = Fixtures[i]; - - if ( Doors.Contains( item ) ) - continue; - - item.MoveToWorld( new Point3D( item.X + x, item.Y + y, item.Z + z ), Map ); - } - } - - public override void OnMapChange() - { - base.OnMapChange(); - - if ( SignHanger != null ) - SignHanger.Map = Map; - - if ( Signpost != null ) - Signpost.Map = Map; - - if ( Fixtures == null ) - return; - - for( int i = 0; i < Fixtures.Count; ++i ) - Fixtures[i].Map = Map; - } - - public void ClearFixtures( Mobile from ) - { - if ( Fixtures == null ) - return; - - RemoveKeys( from ); - - for( int i = 0; i < Fixtures.Count; ++i ) - { - Fixtures[i].Delete(); - Doors.Remove( Fixtures[i] ); - } - - Fixtures.Clear(); - } - - public void AddFixtures( Mobile from, MultiTileEntry[] list ) - { - if ( Fixtures == null ) - Fixtures = new List(); - - uint keyValue = 0; - - for( int i = 0; i < list.Length; ++i ) - { - MultiTileEntry mte = list[i]; - int itemID = mte.m_ItemID; - - if ( itemID >= 0x181D && itemID < 0x1829 ) - { - HouseTeleporter tp = new HouseTeleporter( itemID ); - - AddFixture( tp, mte ); - } - else - { - BaseDoor door = null; - - if ( itemID >= 0x675 && itemID < 0x6F5 ) - { - int type = (itemID - 0x675) / 16; - DoorFacing facing = (DoorFacing)(((itemID - 0x675) / 2) % 8); - - switch( type ) - { - case 0: door = new GenericHouseDoor( facing, 0x675, 0xEC, 0xF3 ); break; - case 1: door = new GenericHouseDoor( facing, 0x685, 0xEC, 0xF3 ); break; - case 2: door = new GenericHouseDoor( facing, 0x695, 0xEB, 0xF2 ); break; - case 3: door = new GenericHouseDoor( facing, 0x6A5, 0xEA, 0xF1 ); break; - case 4: door = new GenericHouseDoor( facing, 0x6B5, 0xEA, 0xF1 ); break; - case 5: door = new GenericHouseDoor( facing, 0x6C5, 0xEC, 0xF3 ); break; - case 6: door = new GenericHouseDoor( facing, 0x6D5, 0xEA, 0xF1 ); break; - case 7: door = new GenericHouseDoor( facing, 0x6E5, 0xEA, 0xF1 ); break; - } - } - else if ( itemID >= 0x314 && itemID < 0x364 ) - { - int type = (itemID - 0x314) / 16; - DoorFacing facing = (DoorFacing)(((itemID - 0x314) / 2) % 8); - door = new GenericHouseDoor( facing, 0x314 + ( type * 16 ), 0xED, 0xF4 ); - } - else if ( itemID >= 0x824 && itemID < 0x834 ) - { - DoorFacing facing = (DoorFacing)(((itemID - 0x824) / 2) % 8); - door = new GenericHouseDoor( facing, 0x824, 0xEC, 0xF3 ); - } - else if ( itemID >= 0x839 && itemID < 0x849 ) - { - DoorFacing facing = (DoorFacing)(((itemID - 0x839) / 2) % 8); - door = new GenericHouseDoor( facing, 0x839, 0xEB, 0xF2 ); - } - else if ( itemID >= 0x84C && itemID < 0x85C ) - { - DoorFacing facing = (DoorFacing)(((itemID - 0x84C) / 2) % 8); - door = new GenericHouseDoor( facing, 0x84C, 0xEC, 0xF3 ); - } - else if ( itemID >= 0x866 && itemID < 0x876 ) - { - DoorFacing facing = (DoorFacing)(((itemID - 0x866) / 2) % 8); - door = new GenericHouseDoor( facing, 0x866, 0xEB, 0xF2 ); - } - else if ( itemID >= 0xE8 && itemID < 0xF8 ) - { - DoorFacing facing = (DoorFacing)(((itemID - 0xE8) / 2) % 8); - door = new GenericHouseDoor( facing, 0xE8, 0xED, 0xF4 ); - } - else if ( itemID >= 0x1FED && itemID < 0x1FFD ) - { - DoorFacing facing = (DoorFacing)(((itemID - 0x1FED) / 2) % 8); - door = new GenericHouseDoor( facing, 0x1FED, 0xEC, 0xF3 ); - } - else if ( itemID >= 0x241F && itemID < 0x2421 ) - { - //DoorFacing facing = (DoorFacing)(((itemID - 0x241F) / 2) % 8); - door = new GenericHouseDoor( DoorFacing.NorthCCW, 0x2415, -1, -1 ); - } - else if ( itemID >= 0x2423 && itemID < 0x2425 ) - { - //DoorFacing facing = (DoorFacing)(((itemID - 0x241F) / 2) % 8); - //This one and the above one are 'special' cases, ie: OSI had the ItemID pattern discombobulated for these - door = new GenericHouseDoor( DoorFacing.WestCW, 0x2423, -1, -1 ); - } - else if ( itemID >= 0x2A05 && itemID < 0x2A1D ) - { - DoorFacing facing = (DoorFacing)((((itemID - 0x2A05) / 2) % 4) + 8); - - int sound = (itemID >= 0x2A0D && itemID < 0x2a15) ? 0x539 : -1; - - door = new GenericHouseDoor( facing, 0x29F5 + (8 * ((itemID - 0x2A05) / 8)), sound, sound ); - } - else if ( itemID == 0x2D46 ) - { - door = new GenericHouseDoor( DoorFacing.NorthCW, 0x2D46, 0xEA, 0xF1, false ); - } - else if ( itemID == 0x2D48 || itemID == 0x2FE2 ) - { - door = new GenericHouseDoor( DoorFacing.SouthCCW, itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x2D63 && itemID < 0x2D70 ) - { - int mod = (itemID - 0x2D63)/2%2; - DoorFacing facing = ( ( mod == 0 ) ? DoorFacing.SouthCCW : DoorFacing.WestCCW ); - - int type = (itemID - 0x2D63) / 4; - - door = new GenericHouseDoor( facing, 0x2D63 + 4*type + mod*2, 0xEA, 0xF1, false ); - } - else if ( itemID == 0x2FE4 || itemID == 0x31AE ) - { - door = new GenericHouseDoor( DoorFacing.WestCCW, itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x319C && itemID < 0x31AE ) - { - //special case for 0x31aa <-> 0x31a8 (a9) - - int mod = (itemID - 0x319C) / 2 % 2; - - bool specialCase = (itemID == 0x31AA || itemID == 0x31A8); - - DoorFacing facing; - - if ( itemID == 0x31AA || itemID == 0x31A8 ) - facing = ((mod == 0) ? DoorFacing.NorthCW : DoorFacing.EastCW); - else - facing = ((mod == 0) ? DoorFacing.EastCW : DoorFacing.NorthCW); - - int type = (itemID - 0x319C) / 4; - - door = new GenericHouseDoor( facing, 0x319C + 4 * type + mod * 2, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x367B && itemID < 0x369B ) - { - int type = (itemID - 0x367B) / 16; - DoorFacing facing = (DoorFacing)(((itemID - 0x367B) / 2) % 8); - - switch( type ) - { - case 0: door = new GenericHouseDoor( facing, 0x367B, 0xED, 0xF4 ); break; //crystal - case 1: door = new GenericHouseDoor( facing, 0x368B, 0xEC, 0x3E7 ); break; //shadow - } - } - else if ( itemID >= 0x409B && itemID < 0x40A3 ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x409B ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x410C && itemID < 0x4114 ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x410C ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x41C2 && itemID < 0x41CA ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x41C2 ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x41CF && itemID < 0x41D7 ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x41CF ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x436E && itemID < 0x437E ) - { - /* These ones had to be different... - * Offset 0 2 4 6 8 10 12 14 - * DoorFacing 2 3 2 3 6 7 6 7 - */ - int offset = itemID - 0x436E; - DoorFacing facing = (DoorFacing)( ( offset / 2 + 2 * ( ( 1 + offset / 4 ) % 2 ) ) % 8 ); - door = new GenericHouseDoor( facing, itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x46DD && itemID < 0x46E5 ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x46DD ), itemID, 0xEB, 0xF2, false ); - } - else if ( itemID >= 0x4D22 && itemID < 0x4D2A ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x4D22 ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x50C8 && itemID < 0x50D0 ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x50C8 ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x50D0 && itemID < 0x50D8 ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x50D0 ), itemID, 0xEA, 0xF1, false ); - } - else if ( itemID >= 0x5142 && itemID < 0x514A ) - { - door = new GenericHouseDoor( GetSADoorFacing( itemID - 0x5142 ), itemID, 0xF0, 0xEF, false ); - } - - if ( door != null ) - { - if ( keyValue == 0 ) - keyValue = CreateKeys( from ); - - door.Locked = true; - door.KeyValue = keyValue; - - AddDoor( door, mte.m_OffsetX, mte.m_OffsetY, mte.m_OffsetZ ); - Fixtures.Add( door ); - } - } - } - - for( int i = 0; i < Fixtures.Count; ++i ) - { - Item fixture = Fixtures[i]; - - if ( fixture is HouseTeleporter ) - { - HouseTeleporter tp = (HouseTeleporter)fixture; - - for( int j = 1; j <= Fixtures.Count; ++j ) - { - HouseTeleporter check = Fixtures[(i + j) % Fixtures.Count] as HouseTeleporter; - - if ( check != null && check.ItemID == tp.ItemID ) - { - tp.Target = check; - break; - } - } - } - else if ( fixture is BaseHouseDoor ) - { - BaseHouseDoor door = (BaseHouseDoor)fixture; - - if ( door.Link != null ) - continue; - - DoorFacing linkFacing; - int xOffset, yOffset; - - switch( door.Facing ) - { - default: - case DoorFacing.WestCW: linkFacing = DoorFacing.EastCCW; xOffset = 1; yOffset = 0; break; - case DoorFacing.EastCCW: linkFacing = DoorFacing.WestCW; xOffset = -1; yOffset = 0; break; - case DoorFacing.WestCCW: linkFacing = DoorFacing.EastCW; xOffset = 1; yOffset = 0; break; - case DoorFacing.EastCW: linkFacing = DoorFacing.WestCCW; xOffset = -1; yOffset = 0; break; - case DoorFacing.SouthCW: linkFacing = DoorFacing.NorthCCW; xOffset = 0; yOffset = -1; break; - case DoorFacing.NorthCCW: linkFacing = DoorFacing.SouthCW; xOffset = 0; yOffset = 1; break; - case DoorFacing.SouthCCW: linkFacing = DoorFacing.NorthCW; xOffset = 0; yOffset = -1; break; - case DoorFacing.NorthCW: linkFacing = DoorFacing.SouthCCW; xOffset = 0; yOffset = 1; break; - case DoorFacing.SouthSW: linkFacing = DoorFacing.SouthSE; xOffset = 1; yOffset = 0; break; - case DoorFacing.SouthSE: linkFacing = DoorFacing.SouthSW; xOffset = -1; yOffset = 0; break; - case DoorFacing.WestSN: linkFacing = DoorFacing.WestSS; xOffset = 0; yOffset = 1; break; - case DoorFacing.WestSS: linkFacing = DoorFacing.WestSN; xOffset = 0; yOffset = -1; break; - } - - for( int j = i + 1; j < Fixtures.Count; ++j ) - { - BaseHouseDoor check = Fixtures[j] as BaseHouseDoor; - - if ( check != null && check.Link == null && check.Facing == linkFacing && (check.X - door.X) == xOffset && (check.Y - door.Y) == yOffset && (check.Z == door.Z) ) - { - check.Link = door; - door.Link = check; - break; - } - } - } - } - } - - private static DoorFacing GetSADoorFacing( int offset ) - { - /* Offset 0 2 4 6 - * DoorFacing 2 3 6 7 - */ - return (DoorFacing)( ( offset / 2 + 2 * ( 1 + offset / 4 ) ) % 8 ); - } - - public void AddFixture( Item item, MultiTileEntry mte ) - { - Fixtures.Add( item ); - item.MoveToWorld( new Point3D( X + mte.m_OffsetX, Y + mte.m_OffsetY, Z + mte.m_OffsetZ ), Map ); - } - - public static void GetFoundationGraphics( FoundationType type, out int east, out int south, out int post, out int corner ) - { - switch( type ) - { - default: - case FoundationType.DarkWood: corner = 0x0014; east = 0x0015; south = 0x0016; post = 0x0017; break; - case FoundationType.LightWood: corner = 0x00BD; east = 0x00BE; south = 0x00BF; post = 0x00C0; break; - case FoundationType.Dungeon: corner = 0x02FD; east = 0x02FF; south = 0x02FE; post = 0x0300; break; - case FoundationType.Brick: corner = 0x0041; east = 0x0043; south = 0x0042; post = 0x0044; break; - case FoundationType.Stone: corner = 0x0065; east = 0x0064; south = 0x0063; post = 0x0066; break; - - case FoundationType.ElvenGrey: corner = 0x2DF7; east = 0x2DF9; south = 0x2DFA; post = 0x2DF8; break; - case FoundationType.ElvenNatural: corner = 0x2DFB; east = 0x2DFD; south = 0x2DFE; post = 0x2DFC; break; - - case FoundationType.Crystal: corner = 0x3672; east = 0x3671; south = 0x3670; post = 0x3673; break; - case FoundationType.Shadow: corner = 0x3676; east = 0x3675; south = 0x3674; post = 0x3677; break; - } - } - - public static void ApplyFoundation( FoundationType type, MultiComponentList mcl ) - { - int east, south, post, corner; - - GetFoundationGraphics( type, out east, out south, out post, out corner ); - - int xCenter = mcl.Center.X; - int yCenter = mcl.Center.Y; - - mcl.Add( post, 0 - xCenter, 0 - yCenter, 0 ); - mcl.Add( corner, mcl.Width - 1 - xCenter, mcl.Height - 2 - yCenter, 0 ); - - for( int x = 1; x < mcl.Width; ++x ) - { - mcl.Add( south, x - xCenter, 0 - yCenter, 0 ); - - if ( x < mcl.Width-1 ) - mcl.Add( south, x - xCenter, mcl.Height - 2 - yCenter, 0 ); - } - - for( int y = 1; y < mcl.Height - 1; ++y ) - { - mcl.Add( east, 0 - xCenter, y - yCenter, 0 ); - - if ( y < mcl.Height - 2 ) - mcl.Add( east, mcl.Width - 1 - xCenter, y - yCenter, 0 ); - } - } - - public static void AddStairsTo( ref MultiComponentList mcl ) - { - // copy the original.. - mcl = new MultiComponentList( mcl ); - - mcl.Resize( mcl.Width, mcl.Height + 1 ); - - int xCenter = mcl.Center.X; - int yCenter = mcl.Center.Y; - int y = mcl.Height - 1; - - for( int x = 0; x < mcl.Width; ++x ) - mcl.Add( 0x63, x - xCenter, y - yCenter, 0 ); - } - - public MultiComponentList GetEmptyFoundation() - { - // Copy original foundation layout - MultiComponentList mcl = new MultiComponentList( MultiData.GetComponents( ItemID ) ); - - mcl.Resize( mcl.Width, mcl.Height + 1 ); - - int xCenter = mcl.Center.X; - int yCenter = mcl.Center.Y; - int y = mcl.Height - 1; - - ApplyFoundation( Type, mcl ); - - for( int x = 1; x < mcl.Width; ++x ) - mcl.Add( 0x751, x - xCenter, y - yCenter, 0 ); - - return mcl; - } - - public override Rectangle2D[] Area - { - get - { - MultiComponentList mcl = Components; - - return new[] { new Rectangle2D( mcl.Min.X, mcl.Min.Y, mcl.Width, mcl.Height ) }; - } - } - - public override Point3D BaseBanLocation => new Point3D( Components.Min.X, Components.Height - 1 - Components.Center.Y, 0 ); - - public void CheckSignpost() - { - MultiComponentList mcl = Components; - - int x = mcl.Min.X; - int y = mcl.Height - 2 - mcl.Center.Y; - - if ( CheckWall( mcl, x, y ) ) - { - Signpost?.Delete(); + from.Hidden = true; + from.Location = new Point3D(foundation.X, foundation.Y, foundation.Z + 7); - Signpost = null; - } - else if ( Signpost == null ) - { - Signpost = new Static( SignpostGraphic ); - Signpost.MoveToWorld( new Point3D( X + x, Y + y, Z + 7 ), Map ); - } - else - { - Signpost.ItemID = SignpostGraphic; - Signpost.MoveToWorld( new Point3D( X + x, Y + y, Z + 7 ), Map ); - } - } + NetState state = from.NetState; - public bool CheckWall( MultiComponentList mcl, int x, int y ) - { - x += mcl.Center.X; - y += mcl.Center.Y; + if (state == null) + return; - if ( x >= 0 && x < mcl.Width && y >= 0 && y < mcl.Height ) - { - StaticTile[] tiles = mcl.Tiles[x][y]; + List fixtures = foundation.Fixtures; - for( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; + for (int i = 0; fixtures != null && i < fixtures.Count; ++i) + { + Item item = fixtures[i]; - if ( tile.Z == 7 && tile.Height == 20 ) - return true; - } - } + state.Send(item.RemovePacket); + } - return false; - } + if (foundation.Signpost != null) + state.Send(foundation.Signpost.RemovePacket); - public HouseFoundation( Mobile owner, int multiID, int maxLockdowns, int maxSecures ) - : base( multiID, owner, maxLockdowns, maxSecures ) - { - SignpostGraphic = 9; + if (foundation.SignHanger != null) + state.Send(foundation.SignHanger.RemovePacket); - Fixtures = new List(); + if (foundation.Sign != null) + state.Send(foundation.Sign.RemovePacket); + } - int x = Components.Min.X; - int y = Components.Height - 1 - Components.Center.Y; + public static void Remove(Mobile from) + { + DesignContext context = Find(from); - SignHanger = new Static( 0xB98 ); - SignHanger.MoveToWorld( new Point3D( X + x, Y + y, Z + 7 ), Map ); + if (context == null) + return; - CheckSignpost(); + Table.Remove(from); - SetSign( x, y, 7 ); - } + if (from is PlayerMobile) + ((PlayerMobile)from).DesignContext = null; - public HouseFoundation( Serial serial ) - : base( serial ) - { - } + if (context == null) + return; - public void BeginCustomize( Mobile m ) - { - if ( !m.CheckAlive() ) { - return; - } + context.Foundation.Customizer = null; - if ( SpellHelper.CheckCombat( m ) ) { - m.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - return; - } - - RelocateEntities(); - - foreach( Item item in GetItems() ) - { - item.Location = BanLocation; - } - - foreach( Mobile mobile in GetMobiles() ) - { - if ( mobile != m ) - mobile.Location = BanLocation; - } - - DesignContext.Add( m, this ); - m.Send( new BeginHouseCustomization( this ) ); - - NetState ns = m.NetState; - if ( ns != null ) - SendInfoTo( ns ); - - DesignState.SendDetailedInfoTo( ns ); - } - - public override void SendInfoTo( NetState state, bool sendOplPacket ) - { - base.SendInfoTo( state, sendOplPacket ); - - DesignContext context = DesignContext.Find( state.Mobile ); - DesignState stateToSend; - - if ( context != null && context.Foundation == this ) - stateToSend = DesignState; - else - stateToSend = CurrentState; - - stateToSend.SendGeneralInfoTo( state ); - } - - public override void Serialize( GenericWriter writer ) - { - writer.Write( (int)5 ); // version - - writer.Write( Signpost ); - writer.Write( (int)SignpostGraphic ); + NetState state = from.NetState; - writer.Write( (int)Type ); + if (state == null) + return; - writer.Write( SignHanger ); + List fixtures = context.Foundation.Fixtures; - writer.Write( (int)LastRevision ); - writer.Write( Fixtures, true ); - - CurrentState.Serialize( writer ); - DesignState.Serialize( writer ); - BackupState.Serialize( writer ); - - base.Serialize( writer ); - } - - private int m_DefaultPrice; - - public override int DefaultPrice => m_DefaultPrice; - - public override void Deserialize( GenericReader reader ) - { - int version = reader.ReadInt(); - - switch( version ) - { - case 5: - case 4: - { - Signpost = reader.ReadItem(); - SignpostGraphic = reader.ReadInt(); - - goto case 3; - } - case 3: - { - Type = (FoundationType)reader.ReadInt(); - - goto case 2; - } - case 2: - { - SignHanger = reader.ReadItem(); - - goto case 1; - } - case 1: - { - if ( version < 5 ) - m_DefaultPrice = reader.ReadInt(); - - goto case 0; - } - case 0: - { - if ( version < 3 ) - Type = FoundationType.Stone; - - if ( version < 4 ) - SignpostGraphic = 9; - - LastRevision = reader.ReadInt(); - Fixtures = reader.ReadStrongItemList(); - - m_Current = new DesignState( this, reader ); - m_Design = new DesignState( this, reader ); - m_Backup = new DesignState( this, reader ); - - break; - } - } - - base.Deserialize( reader ); - } - - public bool IsHiddenToCustomizer( Item item ) - { - return ( item == Signpost || item == SignHanger || item == Sign || IsFixture( item ) ); - } - - public static void Initialize() - { - PacketHandlers.RegisterExtended( 0x1E, true, QueryDesignDetails ); - - PacketHandlers.RegisterEncoded( 0x02, true, Designer_Backup ); - PacketHandlers.RegisterEncoded( 0x03, true, Designer_Restore ); - PacketHandlers.RegisterEncoded( 0x04, true, Designer_Commit ); - PacketHandlers.RegisterEncoded( 0x05, true, Designer_Delete ); - PacketHandlers.RegisterEncoded( 0x06, true, Designer_Build ); - PacketHandlers.RegisterEncoded( 0x0C, true, Designer_Close ); - PacketHandlers.RegisterEncoded( 0x0D, true, Designer_Stairs ); - PacketHandlers.RegisterEncoded( 0x0E, true, Designer_Sync ); - PacketHandlers.RegisterEncoded( 0x10, true, Designer_Clear ); - PacketHandlers.RegisterEncoded( 0x12, true, Designer_Level ); - - PacketHandlers.RegisterEncoded( 0x13, true, Designer_Roof ); // Samurai Empire roof - PacketHandlers.RegisterEncoded( 0x14, true, Designer_RoofDelete ); // Samurai Empire roof - - PacketHandlers.RegisterEncoded( 0x1A, true, Designer_Revert ); - - EventSink.Speech += EventSink_Speech; - } - - private static void EventSink_Speech( SpeechEventArgs e ) - { - if ( DesignContext.Find( e.Mobile ) != null ) - { - e.Mobile.SendLocalizedMessage( 1061925 ); // You cannot speak while customizing your house. - e.Blocked = true; - } - } - - public static void Designer_Sync( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client requested state synchronization - * - Resend full house state - */ - - DesignState design = context.Foundation.DesignState; - - // Resend full house state - design.SendDetailedInfoTo( state ); - } - } - - public static void Designer_Clear( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to clear the design - * - Restore empty foundation - * - Construct new design state from empty foundation - * - Assign constructed state to foundation - * - Update revision - * - Update client with new state - */ - - // Restore empty foundation : Construct new design state from empty foundation - DesignState newDesign = new DesignState( context.Foundation, context.Foundation.GetEmptyFoundation() ); - - // Restore empty foundation : Assign constructed state to foundation - context.Foundation.DesignState = newDesign; - - // Update revision - newDesign.OnRevised(); - - // Update client with new state - context.Foundation.SendInfoTo( state ); - newDesign.SendDetailedInfoTo( state ); - } - } - - public static void Designer_Restore( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to restore design to the last backup state - * - Restore backup - * - Construct new design state from backup state - * - Assign constructed state to foundation - * - Update revision - * - Update client with new state - */ - - // Restore backup : Construct new design state from backup state - DesignState backupDesign = new DesignState( context.Foundation.BackupState ); - - // Restore backup : Assign constructed state to foundation - context.Foundation.DesignState = backupDesign; - - // Update revision; - backupDesign.OnRevised(); - - // Update client with new state - context.Foundation.SendInfoTo( state ); - backupDesign.SendDetailedInfoTo( state ); - } - } - - public static void Designer_Backup( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to backup design state - * - Construct a copy of the current design state - * - Assign constructed state to backup state field - */ - - // Construct a copy of the current design state - DesignState copyState = new DesignState( context.Foundation.DesignState ); - - // Assign constructed state to backup state field - context.Foundation.BackupState = copyState; - } - } - - public static void Designer_Revert( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to revert design state to currently visible state - * - Revert design state - * - Construct a copy of the current visible state - * - Freeze fixtures in constructed state - * - Assign constructed state to foundation - * - If a signpost is needed, add it - * - Update revision - * - Update client with new state - */ - - // Revert design state : Construct a copy of the current visible state - DesignState copyState = new DesignState( context.Foundation.CurrentState ); - - // Revert design state : Freeze fixtures in constructed state - copyState.FreezeFixtures(); - - // Revert design state : Assign constructed state to foundation - context.Foundation.DesignState = copyState; - - // Revert design state : If a signpost is needed, add it - context.Foundation.CheckSignpost(); - - // Update revision - copyState.OnRevised(); - - // Update client with new state - context.Foundation.SendInfoTo( state ); - copyState.SendDetailedInfoTo( state ); - } - } - - public void EndConfirmCommit( Mobile from ) - { - int oldPrice = Price; - int newPrice = oldPrice + CustomizationCost + ((DesignState.Components.List.Length - ( CurrentState.Components.List.Length + CurrentState.Fixtures.Length )) * 500); - int cost = newPrice - oldPrice; - - if ( !Deleted ) { // Temporary Fix. We should be booting a client out of customization mode in the delete handler. - if ( from.AccessLevel >= AccessLevel.GameMaster && cost != 0 ) - { - from.SendMessage( "{0} gold would have been {1} your bank if you were not a GM.", cost.ToString(), ((cost > 0 )? "withdrawn from" : "deposited into" ) ); - } - else - { - if ( cost > 0 ) - { - if ( Banker.Withdraw( from, cost ) ) - { - from.SendLocalizedMessage( 1060398, cost.ToString() ); // ~1_AMOUNT~ gold has been withdrawn from your bank box. - } - else - { - from.SendLocalizedMessage( 1061903 ); // You cannot commit this house design, because you do not have the necessary funds in your bank box to pay for the upgrade. Please back up your design, obtain the required funds, and commit your design again. - return; - } - } - else if ( cost < 0 ) - { - if ( Banker.Deposit( from, -cost ) ) - from.SendLocalizedMessage( 1060397, ( -cost ).ToString() ); // ~1_AMOUNT~ gold has been deposited into your bank box. - else - return; - } - } - } - - /* Client chose to commit current design state - * - Commit design state - * - Construct a copy of the current design state - * - Clear visible fixtures - * - Melt fixtures from constructed state - * - Add melted fixtures from constructed state - * - Assign constructed state to foundation - * - Update house price - * - Remove design context - * - Notify the client that customization has ended - * - Notify the core that the foundation has changed and should be resent to all clients - * - If a signpost is needed, add it - * - Eject all from house - * - Restore relocated entities - */ - - // Commit design state : Construct a copy of the current design state - DesignState copyState = new DesignState( DesignState ); - - // Commit design state : Clear visible fixtures - ClearFixtures( from ); - - // Commit design state : Melt fixtures from constructed state - copyState.MeltFixtures(); - - // Commit design state : Add melted fixtures from constructed state - AddFixtures( from, copyState.Fixtures ); - - // Commit design state : Assign constructed state to foundation - CurrentState = copyState; - - // Update house price - Price = newPrice - CustomizationCost; - - // Remove design context - DesignContext.Remove( from ); - - // Notify the client that customization has ended - from.Send( new EndHouseCustomization( this ) ); - - // Notify the core that the foundation has changed and should be resent to all clients - Delta( ItemDelta.Update ); - ProcessDelta(); - CurrentState.SendDetailedInfoTo( from.NetState ); - - // If a signpost is needed, add it - CheckSignpost(); - - // Eject all from house - from.RevealingAction(); - - foreach( Item item in GetItems() ) - item.Location = BanLocation; - - foreach( Mobile mobile in GetMobiles() ) - mobile.Location = BanLocation; - - // Restore relocated entities - RestoreRelocatedEntities(); - } - - public static void Designer_Commit( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - int oldPrice = context.Foundation.Price; - int newPrice = oldPrice + context.Foundation.CustomizationCost + ((context.Foundation.DesignState.Components.List.Length - ( context.Foundation.CurrentState.Components.List.Length + context.Foundation.Fixtures.Count) ) * 500); - int bankBalance = Banker.GetBalance( from ); - - from.SendGump( new ConfirmCommitGump( from, context.Foundation, bankBalance, oldPrice, newPrice ) ); - } - } - - public int MaxLevels - { - get - { - MultiComponentList mcl = Components; - - if ( mcl.Width >= 14 || mcl.Height >= 14 ) - return 4; - return 3; - } - } - - public static int GetLevelZ( int level, HouseFoundation house ) - { - if ( level < 1 || level > house.MaxLevels ) - level = 1; - - return (level-1)*20 + 7; - - /* - switch( level ) - { - default: - case 1: return 07; - case 2: return 27; - case 3: return 47; - case 4: return 67; - } - * */ - } - - public static int GetZLevel( int z, HouseFoundation house ) - { - int level = (z - 7)/20 +1; - - if ( level < 1 || level > house.MaxLevels ) - level = 1; - - return level; - } - - private static ComponentVerification m_Verification; - - public static ComponentVerification Verification - { - get - { - if ( m_Verification == null ) - m_Verification = new ComponentVerification(); - - return m_Verification; - } - } - - public static bool ValidPiece( int itemID ) - { - return ValidPiece( itemID, false ); - } - - public static bool ValidPiece( int itemID, bool roof ) - { - itemID &= TileData.MaxItemValue; - - if ( !roof && ( TileData.ItemTable[itemID].Flags & TileFlag.Roof ) != 0 ) - return false; - if ( roof && ( TileData.ItemTable[itemID].Flags & TileFlag.Roof ) == 0 ) - return false; - - return Verification.IsItemValid( itemID ); - } - - public static readonly bool AllowStairSectioning = true; - - /* Stair block IDs - * (sorted ascending) - */ - private static int[] m_BlockIDs = { - 0x3EE, 0x709, 0x71E, 0x721, - 0x738, 0x750, 0x76C, 0x788, - 0x7A3, 0x7BA, 0x35D2, 0x3609, - 0x4317, 0x4318, 0x4B07, 0x7807 - }; - - /* Stair sequence IDs - * (sorted ascending) - * Use this for stairs in the proper N,W,S,E sequence - */ - private static int[] m_StairSeqs = { - 0x3EF, 0x70A, 0x722, 0x739, - 0x751, 0x76D, 0x789, 0x7A4 - }; - - /* Other stair IDs - * Listed in order: north, west, south, east - * Use this for stairs not in the proper sequence - */ - private static int[] m_StairIDs = { - 0x71F, 0x736, 0x737, 0x749, - 0x35D4, 0x35D3, 0x35D6, 0x35D5, - 0x360B, 0x360A, 0x360D, 0x360C, - 0x4360, 0x435E, 0x435F, 0x4361, - 0x435C, 0x435A, 0x435B, 0x435D, - 0x4364, 0x4362, 0x4363, 0x4365, - 0x4B05, 0x4B04, 0x4B34, 0x4B33, - 0x7809, 0x7808, 0x780A, 0x780B, - 0x7BB, 0x7BC - }; - - public static bool IsStairBlock( int id ) - { - int delta = -1; - - for( int i = 0; delta < 0 && i < m_BlockIDs.Length; ++i ) - delta = (m_BlockIDs[i] - id); - - return (delta == 0); - } - - public static bool IsStair( int id, ref int dir ) - { - //dir n=0 w=1 s=2 e=3 - int delta = -4; - - for( int i = 0; delta < -3 && i < m_StairSeqs.Length; ++i ) - delta = (m_StairSeqs[i] - id); - - if ( delta >= -3 && delta <= 0 ) - { - dir = -delta; - return true; - } - - for( int i = 0; i < m_StairIDs.Length; ++i ) - { - if ( m_StairIDs[i] == id ) - { - dir = i % 4; - return true; - } - } - - return false; - } - - public static bool DeleteStairs( MultiComponentList mcl, int id, int x, int y, int z ) - { - int ax = x + mcl.Center.X; - int ay = y + mcl.Center.Y; - - if ( ax < 0 || ay < 0 || ax >= mcl.Width || ay >= (mcl.Height - 1) || z < 7 || ((z - 7) % 5) != 0 ) - return false; - - if ( IsStairBlock( id ) ) - { - StaticTile[] tiles = mcl.Tiles[ax][ay]; - - for( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - - if ( tile.Z == (z + 5) ) - { - id = tile.ID; - z = tile.Z; - - if ( !IsStairBlock( id ) ) - break; - } - } - } - - int dir = 0; - - if ( !IsStair( id, ref dir ) ) - return false; - - if ( AllowStairSectioning ) - return true; // skip deletion - - int height = ((z - 7) % 20) / 5; - - int xStart, yStart; - int xInc, yInc; - - switch( dir ) - { - default: - case 0: // North - { - xStart = x; - yStart = y + height; - xInc = 0; - yInc = -1; - break; - } - case 1: // West - { - xStart = x + height; - yStart = y; - xInc = -1; - yInc = 0; - break; - } - case 2: // South - { - xStart = x; - yStart = y - height; - xInc = 0; - yInc = 1; - break; - } - case 3: // East - { - xStart = x - height; - yStart = y; - xInc = 1; - yInc = 0; - break; - } - } - - int zStart = z - (height * 5); - - for( int i = 0; i < 4; ++i ) - { - x = xStart + (i * xInc); - y = yStart + (i * yInc); - - for( int j = 0; j <= i; ++j ) - mcl.RemoveXYZH( x, y, zStart + (j * 5), 5 ); - - ax = x + mcl.Center.X; - ay = y + mcl.Center.Y; - - if ( ax >= 1 && ax < mcl.Width && ay >= 1 && ay < mcl.Height - 1 ) - { - StaticTile[] tiles = mcl.Tiles[ax][ay]; - - bool hasBaseFloor = false; - - for( int j = 0; !hasBaseFloor && j < tiles.Length; ++j ) - hasBaseFloor = (tiles[j].Z == 7 && tiles[j].ID != 1); - - if ( !hasBaseFloor ) - mcl.Add( 0x31F4, x, y, 7 ); - } - } - - return true; - } - - public static void Designer_Delete( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to delete a component - * - Read data detailing which component to delete - * - Verify component is deletable - * - Remove the component - * - If needed, replace removed component with a dirt tile - * - Update revision - */ - - // Read data detailing which component to delete - int itemID = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt32(); - int y = pvSrc.ReadInt32(); - int z = pvSrc.ReadInt32(); - - // Verify component is deletable - DesignState design = context.Foundation.DesignState; - MultiComponentList mcl = design.Components; - - int ax = x + mcl.Center.X; - int ay = y + mcl.Center.Y; - - if ( z == 0 && ax >= 0 && ax < mcl.Width && ay >= 0 && ay < (mcl.Height - 1) ) - { - /* Component is not deletable - * - Resend design state - * - Return without further processing - */ - - design.SendDetailedInfoTo( state ); - return; - } - - bool fixState = false; - - // Remove the component - if ( AllowStairSectioning ) - { - if ( DeleteStairs( mcl, itemID, x, y, z ) ) - fixState = true; // The client removes the entire set of stairs locally, resend state - - mcl.Remove( itemID, x, y, z ); - } - else - { - if ( !DeleteStairs( mcl, itemID, x, y, z ) ) - mcl.Remove( itemID, x, y, z ); - } - - // If needed, replace removed component with a dirt tile - if ( ax >= 1 && ax < mcl.Width && ay >= 1 && ay < mcl.Height - 1 ) - { - StaticTile[] tiles = mcl.Tiles[ax][ay]; - - bool hasBaseFloor = false; - - for( int i = 0; !hasBaseFloor && i < tiles.Length; ++i ) - hasBaseFloor = (tiles[i].Z == 7 && tiles[i].ID != 1); - - if ( !hasBaseFloor ) - { - // Replace with a dirt tile - mcl.Add( 0x31F4, x, y, 7 ); - } - } - - // Update revision - design.OnRevised(); - - // Resend design state - if ( fixState ) - design.SendDetailedInfoTo( state ); - } - } - - public static void Designer_Stairs( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to add stairs - * - Read data detailing stair type and location - * - Validate stair multi ID - * - Add the stairs - * - Load data describing the stair components - * - Insert described components - * - Update revision - */ - - // Read data detailing stair type and location - int itemID = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt32(); - int y = pvSrc.ReadInt32(); - - // Validate stair multi ID - DesignState design = context.Foundation.DesignState; - - if ( !Verification.IsMultiValid( itemID ) ) - { - /* Specified multi ID is not a stair - * - Resend design state - * - Return without further processing - */ - - TraceValidity( state, itemID ); - design.SendDetailedInfoTo( state ); - return; - } - - // Add the stairs - MultiComponentList mcl = design.Components; - - // Add the stairs : Load data describing stair components - MultiComponentList stairs = MultiData.GetComponents( itemID ); - - // Add the stairs : Insert described components - int z = GetLevelZ( context.Level, context.Foundation ); - - for( int i = 0; i < stairs.List.Length; ++i ) - { - MultiTileEntry entry = stairs.List[i]; - - if ( entry.m_ItemID != 1 ) - mcl.Add( entry.m_ItemID, x + entry.m_OffsetX, y + entry.m_OffsetY, z + entry.m_OffsetZ ); - } - - // Update revision - design.OnRevised(); - } - } - - private static void TraceValidity( NetState state, int itemID ) - { - try - { - using ( StreamWriter op = new StreamWriter( "comp_val.log", true ) ) - op.WriteLine( "{0}\t{1}\tInvalid ItemID 0x{2:X4}", state, state.Mobile, itemID ); - } - catch - { - } - } - - public static void Designer_Build( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client chose to add a component - * - Read data detailing component graphic and location - * - Add component - * - Update revision - */ - - // Read data detailing component graphic and location - int itemID = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt32(); - int y = pvSrc.ReadInt32(); - - // Add component - DesignState design = context.Foundation.DesignState; - - if ( from.AccessLevel < AccessLevel.GameMaster && !ValidPiece( itemID ) ) - { - TraceValidity( state, itemID ); - design.SendDetailedInfoTo( state ); - return; - } - - MultiComponentList mcl = design.Components; - - int z = GetLevelZ( context.Level, context.Foundation ); - - if ( (y + mcl.Center.Y) == (mcl.Height - 1) ) - z = 0; // Tiles placed on the far-south of the house are at 0 Z - - mcl.Add( itemID, x, y, z ); - - // Update revision - design.OnRevised(); - } - } - - public static void Designer_Close( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client closed his house design window - * - Remove design context - * - Notify the client that customization has ended - * - Refresh client with current visible design state - * - If a signpost is needed, add it - * - Eject all from house - * - Restore relocated entities - */ - - // Remove design context - DesignContext.Remove( from ); - - // Notify the client that customization has ended - from.Send( new EndHouseCustomization( context.Foundation ) ); - - // Refresh client with current visible design state - context.Foundation.SendInfoTo( state ); - context.Foundation.CurrentState.SendDetailedInfoTo( state ); - - // If a signpost is needed, add it - context.Foundation.CheckSignpost(); - - // Eject all from house - from.RevealingAction(); - - foreach( Item item in context.Foundation.GetItems() ) - item.Location = context.Foundation.BanLocation; - - foreach( Mobile mobile in context.Foundation.GetMobiles() ) - mobile.Location = context.Foundation.BanLocation; - - // Restore relocated entities - context.Foundation.RestoreRelocatedEntities(); - } - } - - public static void Designer_Level( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) - { - /* Client is moving to a new floor level - * - Read data detailing the target level - * - Validate target level - * - Update design context with new level - * - Teleport mobile to new level - * - Update client - * - */ - - // Read data detailing the target level - int newLevel = pvSrc.ReadInt32(); - - // Validate target level - if ( newLevel < 1 || newLevel > context.MaxLevels ) - newLevel = 1; - - // Update design context with new level - context.Level = newLevel; - - // Teleport mobile to new level - from.Location = new Point3D( from.X, from.Y, context.Foundation.Z + GetLevelZ( newLevel, context.Foundation ) ); - - // Update client - context.Foundation.SendInfoTo( state ); - } - } - - public static void QueryDesignDetails( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - HouseFoundation foundation = World.FindItem( pvSrc.ReadInt32() ) as HouseFoundation; - - if ( foundation != null && from.Map == foundation.Map && from.InRange( foundation.GetWorldLocation(), 24 ) && from.CanSee( foundation ) ) - { - DesignState stateToSend; - - if ( context != null && context.Foundation == foundation ) - stateToSend = foundation.DesignState; - else - stateToSend = foundation.CurrentState; - - stateToSend.SendDetailedInfoTo( state ); - } - } - - public static void Designer_Roof( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null && (Core.SE || from.AccessLevel >= AccessLevel.GameMaster) ) - { - // Read data detailing component graphic and location - int itemID = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt32(); - int y = pvSrc.ReadInt32(); - int z = pvSrc.ReadInt32(); - - // Add component - DesignState design = context.Foundation.DesignState; - - if ( from.AccessLevel < AccessLevel.GameMaster && !ValidPiece( itemID, true ) ) - { - TraceValidity( state, itemID ); - design.SendDetailedInfoTo( state ); - return; - } - - MultiComponentList mcl = design.Components; - - if ( z < -3 || z > 12 || z % 3 != 0 ) - z = -3; - z += GetLevelZ( context.Level, context.Foundation ); - - MultiTileEntry[] list = mcl.List; - for( int i = 0; i < list.Length; i++ ) - { - MultiTileEntry mte = list[i]; - - if ( mte.m_OffsetX == x && mte.m_OffsetY == y && GetZLevel( mte.m_OffsetZ, context.Foundation ) == context.Level && (TileData.ItemTable[mte.m_ItemID & TileData.MaxItemValue].Flags & TileFlag.Roof) != 0 ) - mcl.Remove( mte.m_ItemID, x, y, mte.m_OffsetZ ); - } - - mcl.Add( itemID, x, y, z ); - - // Update revision - design.OnRevised(); - } - } - - public static void Designer_RoofDelete( NetState state, IEntity e, EncodedReader pvSrc ) - { - Mobile from = state.Mobile; - DesignContext context = DesignContext.Find( from ); - - if ( context != null ) // No need to check for Core.SE if trying to remove something that shouldn't be able to be placed anyways - { - // Read data detailing which component to delete - int itemID = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt32(); - int y = pvSrc.ReadInt32(); - int z = pvSrc.ReadInt32(); - - // Verify component is deletable - DesignState design = context.Foundation.DesignState; - MultiComponentList mcl = design.Components; + for (int i = 0; fixtures != null && i < fixtures.Count; ++i) + { + Item item = fixtures[i]; - if ( (TileData.ItemTable[itemID & TileData.MaxItemValue].Flags & TileFlag.Roof) == 0 ) - { - design.SendDetailedInfoTo( state ); - return; - } - - mcl.Remove( itemID, x, y, z ); - - design.OnRevised(); - } - } + item.SendInfoTo(state); + } + context.Foundation.Signpost?.SendInfoTo(state); - } - - public class DesignState - { - private Packet m_PacketCache; - - public Packet PacketCache - { - get => m_PacketCache; - set - { - if ( m_PacketCache == value ) - return; - - m_PacketCache?.Release(); - - m_PacketCache = value; - } - } - - public HouseFoundation Foundation { get; } - - public MultiComponentList Components { get; } - - public MultiTileEntry[] Fixtures { get; private set; } - - public int Revision { get; set; } - - public DesignState( HouseFoundation foundation, MultiComponentList components ) - { - Foundation = foundation; - Components = components; - Fixtures = new MultiTileEntry[0]; - } - - public DesignState( DesignState toCopy ) - { - Foundation = toCopy.Foundation; - Components = new MultiComponentList( toCopy.Components ); - Revision = toCopy.Revision; - Fixtures = new MultiTileEntry[toCopy.Fixtures.Length]; - - for( int i = 0; i < Fixtures.Length; ++i ) - Fixtures[i] = toCopy.Fixtures[i]; - } - - public DesignState( HouseFoundation foundation, GenericReader reader ) - { - Foundation = foundation; - - int version = reader.ReadInt(); - - switch( version ) - { - case 0: - { - Components = new MultiComponentList( reader ); - - int length = reader.ReadInt(); - - Fixtures = new MultiTileEntry[length]; + context.Foundation.SignHanger?.SendInfoTo(state); - for( int i = 0; i < length; ++i ) - { - Fixtures[i].m_ItemID = reader.ReadUShort(); - Fixtures[i].m_OffsetX = reader.ReadShort(); - Fixtures[i].m_OffsetY = reader.ReadShort(); - Fixtures[i].m_OffsetZ = reader.ReadShort(); - Fixtures[i].m_Flags = reader.ReadInt(); - } - - Revision = reader.ReadInt(); - - break; - } - } - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (int)0 ); // version - - Components.Serialize( writer ); - - writer.Write( (int)Fixtures.Length ); - - for( int i = 0; i < Fixtures.Length; ++i ) - { - MultiTileEntry ent = Fixtures[i]; - - writer.Write( (ushort)ent.m_ItemID ); - writer.Write( (short)ent.m_OffsetX ); - writer.Write( (short)ent.m_OffsetY ); - writer.Write( (short)ent.m_OffsetZ ); - writer.Write( (int)ent.m_Flags ); - } - - writer.Write( (int)Revision ); - } - - public void OnRevised() - { - lock( this ) - { - Revision = ++Foundation.LastRevision; - - m_PacketCache?.Release(); - - m_PacketCache = null; - } - } - - public void SendGeneralInfoTo( NetState state ) - { - state?.Send( new DesignStateGeneral( Foundation, this ) ); - } - - public void SendDetailedInfoTo( NetState state ) - { - if ( state != null ) - { - lock( this ) - { - if ( m_PacketCache == null ) - DesignStateDetailed.SendDetails( state, Foundation, this ); - else - state.Send( m_PacketCache ); - } - } - } - - public void FreezeFixtures() - { - OnRevised(); - - for( int i = 0; i < Fixtures.Length; ++i ) - { - MultiTileEntry mte = Fixtures[i]; - - Components.Add( mte.m_ItemID, mte.m_OffsetX, mte.m_OffsetY, mte.m_OffsetZ ); - } - - Fixtures = new MultiTileEntry[0]; - } - - public void MeltFixtures() - { - OnRevised(); - - MultiTileEntry[] list = Components.List; - int length = 0; - - for( int i = list.Length - 1; i >= 0; --i ) - { - MultiTileEntry mte = list[i]; - - if ( IsFixture( mte.m_ItemID ) ) - ++length; - } - - Fixtures = new MultiTileEntry[length]; - - for( int i = list.Length - 1; i >= 0; --i ) - { - MultiTileEntry mte = list[i]; - - if ( IsFixture( mte.m_ItemID ) ) - { - Fixtures[--length] = mte; - Components.Remove( mte.m_ItemID, mte.m_OffsetX, mte.m_OffsetY, mte.m_OffsetZ ); - } - } - } - - public static bool IsFixture( int itemID ) - { - if ( itemID >= 0x675 && itemID < 0x6F5 ) - return true; - if ( itemID >= 0x314 && itemID < 0x364 ) - return true; - if ( itemID >= 0x824 && itemID < 0x834 ) - return true; - if ( itemID >= 0x839 && itemID < 0x849 ) - return true; - if ( itemID >= 0x84C && itemID < 0x85C ) - return true; - if ( itemID >= 0x866 && itemID < 0x876 ) - return true; - if ( itemID >= 0x0E8 && itemID < 0x0F8 ) - return true; - if ( itemID >= 0x1FED && itemID < 0x1FFD ) - return true; - if ( itemID >= 0x181D && itemID < 0x1829 ) - return true; - if ( itemID >= 0x241F && itemID < 0x2421 ) - return true; - if ( itemID >= 0x2423 && itemID < 0x2425 ) - return true; - if ( itemID >= 0x2A05 && itemID < 0x2A1D ) - return true; - if ( itemID >= 0x319C && itemID < 0x31B0 ) - return true; - // ML doors - if ( itemID == 0x2D46 ||itemID == 0x2D48 || itemID == 0x2FE2 || itemID == 0x2FE4 ) - return true; - if ( itemID >= 0x2D63 && itemID < 0x2D70 ) - return true; - if ( itemID >= 0x319C && itemID < 0x31AF ) - return true; - if ( itemID >= 0x367B && itemID < 0x369B ) - return true; - // SA doors - if ( itemID >= 0x409B && itemID < 0x40A3 ) - return true; - if ( itemID >= 0x410C && itemID < 0x4114 ) - return true; - if ( itemID >= 0x41C2 && itemID < 0x41CA ) - return true; - if ( itemID >= 0x41CF && itemID < 0x41D7 ) - return true; - if ( itemID >= 0x436E && itemID < 0x437E ) - return true; - if ( itemID >= 0x46DD && itemID < 0x46E5 ) - return true; - if ( itemID >= 0x4D22 && itemID < 0x4D2A ) - return true; - if ( itemID >= 0x50C8 && itemID < 0x50D8 ) - return true; - if ( itemID >= 0x5142 && itemID < 0x514A ) - return true; - // TOL doors - if ( itemID >= 0x9AD7 && itemID < 0x9AE7 ) - return true; - if ( itemID >= 0x9B3C && itemID < 0x9B4C ) - return true; - - return false; - } - } - - public class ConfirmCommitGump : Gump - { - private HouseFoundation m_Foundation; - - public ConfirmCommitGump( Mobile from, HouseFoundation foundation, int bankBalance, int oldPrice, int newPrice ) - : base( 50, 50 ) - { - m_Foundation = foundation; - - AddPage( 0 ); - - AddBackground( 0, 0, 320, 320, 5054 ); - - AddImageTiled( 10, 10, 300, 20, 2624 ); - AddImageTiled( 10, 40, 300, 240, 2624 ); - AddImageTiled( 10, 290, 300, 20, 2624 ); - - AddAlphaRegion( 10, 10, 300, 300 ); - - AddHtmlLocalized( 10, 10, 300, 20, 1062060, 32736, false, false ); //
COMMIT DESIGN
- - AddHtmlLocalized( 10, 40, 300, 140, (newPrice - oldPrice) <= bankBalance ? 1061898 : 1061903, 1023, false, true ); - - AddHtmlLocalized( 10, 190, 150, 20, 1061902, 32736, false, false ); // Bank Balance: - AddLabel( 170, 190, 55, bankBalance.ToString() ); - - AddHtmlLocalized( 10, 215, 150, 20, 1061899, 1023, false, false ); // Old Value: - AddLabel( 170, 215, 90, oldPrice.ToString() ); - - AddHtmlLocalized( 10, 235, 150, 20, 1061900, 1023, false, false ); // Cost To Commit: - AddLabel( 170, 235, 90, newPrice.ToString() ); - - if ( newPrice - oldPrice < 0 ) - { - AddHtmlLocalized( 10, 260, 150, 20, 1062059, 992, false, false ); // Your Refund: - AddLabel( 170, 260, 70, (oldPrice - newPrice).ToString() ); - } - else - { - AddHtmlLocalized( 10, 260, 150, 20, 1061901, 31744, false, false ); // Your Cost: - AddLabel( 170, 260, 40, (newPrice - oldPrice).ToString() ); - } - - AddButton( 10, 290, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 290, 55, 20, 1011036, 32767, false, false ); // OKAY - - AddButton( 170, 290, 4005, 4007, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 195, 290, 55, 20, 1011012, 32767, false, false ); // CANCEL - } - - public override void OnResponse( NetState sender, RelayInfo info ) - { - if ( info.ButtonID == 1 ) - m_Foundation.EndConfirmCommit( sender.Mobile ); - } - } - - public class DesignContext - { - public HouseFoundation Foundation { get; } + context.Foundation.Sign?.SendInfoTo(state); + } + } - public int Level { get; set; } + public class BeginHouseCustomization : Packet + { + public BeginHouseCustomization(HouseFoundation house) + : base(0xBF) + { + EnsureCapacity(17); - public int MaxLevels => Foundation.MaxLevels; + m_Stream.Write((short)0x20); + m_Stream.Write(house.Serial); + m_Stream.Write((byte)0x04); + m_Stream.Write((ushort)0x0000); + m_Stream.Write((ushort)0xFFFF); + m_Stream.Write((ushort)0xFFFF); + m_Stream.Write((byte)0xFF); + } + } - public DesignContext( HouseFoundation foundation ) - { - Foundation = foundation; - Level = 1; - } + public class EndHouseCustomization : Packet + { + public EndHouseCustomization(HouseFoundation house) + : base(0xBF) + { + EnsureCapacity(17); - public static Dictionary Table { get; } = new Dictionary(); - - public static DesignContext Find( Mobile from ) - { - if ( from == null ) - return null; - - Table.TryGetValue( from, out DesignContext d ); - - return d; - } - - public static bool Check( Mobile m ) - { - if ( Find( m ) != null ) - { - m.SendLocalizedMessage( 1062206 ); // You cannot do that while customizing a house. - return false; - } - - return true; - } - - public static void Add( Mobile from, HouseFoundation foundation ) - { - if ( from == null ) - return; - - DesignContext c = new DesignContext( foundation ); - - Table[from] = c; - - if ( from is PlayerMobile ) - ((PlayerMobile)from).DesignContext = c; - - foundation.Customizer = from; - - from.Hidden = true; - from.Location = new Point3D( foundation.X, foundation.Y, foundation.Z + 7 ); - - NetState state = from.NetState; - - if ( state == null ) - return; - - List fixtures = foundation.Fixtures; - - for( int i = 0; fixtures != null && i < fixtures.Count; ++i ) - { - Item item = fixtures[i]; - - state.Send( item.RemovePacket ); - } - - if ( foundation.Signpost != null ) - state.Send( foundation.Signpost.RemovePacket ); - - if ( foundation.SignHanger != null ) - state.Send( foundation.SignHanger.RemovePacket ); - - if ( foundation.Sign != null ) - state.Send( foundation.Sign.RemovePacket ); - } - - public static void Remove( Mobile from ) - { - DesignContext context = Find( from ); - - if ( context == null ) - return; - - Table.Remove( from ); - - if ( from is PlayerMobile ) - ((PlayerMobile)from).DesignContext = null; - - if ( context == null ) - return; - - context.Foundation.Customizer = null; - - NetState state = from.NetState; - - if ( state == null ) - return; - - List fixtures = context.Foundation.Fixtures; - - for( int i = 0; fixtures != null && i < fixtures.Count; ++i ) - { - Item item = fixtures[i]; - - item.SendInfoTo( state ); - } - - context.Foundation.Signpost?.SendInfoTo( state ); - - context.Foundation.SignHanger?.SendInfoTo( state ); - - context.Foundation.Sign?.SendInfoTo( state ); - } - } - - public class BeginHouseCustomization : Packet - { - public BeginHouseCustomization( HouseFoundation house ) - : base( 0xBF ) - { - EnsureCapacity( 17 ); - - m_Stream.Write( (short)0x20 ); - m_Stream.Write( (int)house.Serial ); - m_Stream.Write( (byte)0x04 ); - m_Stream.Write( (ushort)0x0000 ); - m_Stream.Write( (ushort)0xFFFF ); - m_Stream.Write( (ushort)0xFFFF ); - m_Stream.Write( (byte)0xFF ); - } - } - - public class EndHouseCustomization : Packet - { - public EndHouseCustomization( HouseFoundation house ) - : base( 0xBF ) - { - EnsureCapacity( 17 ); - - m_Stream.Write( (short)0x20 ); - m_Stream.Write( (int)house.Serial ); - m_Stream.Write( (byte)0x05 ); - m_Stream.Write( (ushort)0x0000 ); - m_Stream.Write( (ushort)0xFFFF ); - m_Stream.Write( (ushort)0xFFFF ); - m_Stream.Write( (byte)0xFF ); - } - } - - public sealed class DesignStateGeneral : Packet - { - public DesignStateGeneral( HouseFoundation house, DesignState state ) - : base( 0xBF ) - { - EnsureCapacity( 13 ); - - m_Stream.Write( (short)0x1D ); - m_Stream.Write( (int)house.Serial ); - m_Stream.Write( (int)state.Revision ); - } - } - - public sealed class DesignStateDetailed : Packet - { - public const int MaxItemsPerStairBuffer = 750; - - private static BufferPool m_PlaneBufferPool = new BufferPool("Housing Plane Buffers", 9, 0x400); - private static BufferPool m_StairBufferPool = new BufferPool("Housing Stair Buffers", 6, MaxItemsPerStairBuffer * 5); - private static BufferPool m_DeflatedBufferPool = new BufferPool("Housing Deflated Buffers", 1, 0x2000); - - private byte[][] m_PlaneBuffers; - private byte[][] m_StairBuffers; - - private bool[] m_PlaneUsed = new bool[9]; - private byte[] m_PrimBuffer = new byte[4]; - - public void Write( int value ) - { - m_PrimBuffer[0] = (byte)(value >> 24); - m_PrimBuffer[1] = (byte)(value >> 16); - m_PrimBuffer[2] = (byte)(value >> 8); - m_PrimBuffer[3] = (byte)value; - - m_Stream.UnderlyingStream.Write( m_PrimBuffer, 0, 4 ); - } - - public void Write( short value ) - { - m_PrimBuffer[0] = (byte)(value >> 8); - m_PrimBuffer[1] = (byte)value; - - m_Stream.UnderlyingStream.Write( m_PrimBuffer, 0, 2 ); - } - - public void Write( byte value ) - { - m_Stream.UnderlyingStream.WriteByte( value ); - } - - public void Write( byte[] buffer, int offset, int size ) - { - m_Stream.UnderlyingStream.Write( buffer, offset, size ); - } - - public static void Clear( byte[] buffer, int size ) - { - for( int i = 0; i < size; ++i ) - buffer[i] = 0; - } - - public DesignStateDetailed( int serial, int revision, int xMin, int yMin, int xMax, int yMax, MultiTileEntry[] tiles ) - : base( 0xD8 ) - { - EnsureCapacity( 17 + (tiles.Length * 5) ); - - Write( (byte)0x03 ); // Compression Type - Write( (byte)0x00 ); // Unknown - Write( (int)serial ); - Write( (int)revision ); - Write( (short)tiles.Length ); - Write( (short)0 ); // Buffer length : reserved - Write( (byte)0 ); // Plane count : reserved - - int totalLength = 1; // includes plane count - - int width = (xMax - xMin) + 1; - int height = (yMax - yMin) + 1; - - m_PlaneBuffers = new byte[9][]; - - lock (m_PlaneBufferPool) - for (int i = 0; i < m_PlaneBuffers.Length; ++i) - m_PlaneBuffers[i] = m_PlaneBufferPool.AcquireBuffer(); - - m_StairBuffers = new byte[6][]; - - lock (m_StairBufferPool) - for (int i = 0; i < m_StairBuffers.Length; ++i) - m_StairBuffers[i] = m_StairBufferPool.AcquireBuffer(); - - Clear( m_PlaneBuffers[0], width * height * 2 ); - - for( int i = 0; i < 4; ++i ) - { - Clear( m_PlaneBuffers[1 + i], (width - 1) * (height - 2) * 2 ); - Clear( m_PlaneBuffers[5 + i], width * (height - 1) * 2 ); - } - - int totalStairsUsed = 0; - - for( int i = 0; i < tiles.Length; ++i ) - { - MultiTileEntry mte = tiles[i]; - int x = mte.m_OffsetX - xMin; - int y = mte.m_OffsetY - yMin; - int z = mte.m_OffsetZ; - bool floor = (TileData.ItemTable[mte.m_ItemID & TileData.MaxItemValue].Height <= 0); - int plane, size; - - switch( z ) - { - case 0: plane = 0; break; - case 7: plane = 1; break; - case 27: plane = 2; break; - case 47: plane = 3; break; - case 67: plane = 4; break; - default: - { - int stairBufferIndex = (totalStairsUsed / MaxItemsPerStairBuffer); - byte[] stairBuffer = m_StairBuffers[stairBufferIndex]; - - int byteIndex = (totalStairsUsed % MaxItemsPerStairBuffer) * 5; - - stairBuffer[byteIndex++] = (byte)(mte.m_ItemID >> 8); - stairBuffer[byteIndex++] = (byte)mte.m_ItemID; - - stairBuffer[byteIndex++] = (byte)mte.m_OffsetX; - stairBuffer[byteIndex++] = (byte)mte.m_OffsetY; - stairBuffer[byteIndex++] = (byte)mte.m_OffsetZ; - - ++totalStairsUsed; - - continue; - } - } - - if ( plane == 0 ) - { - size = height; - } - else if ( floor ) - { - size = height - 2; - x -= 1; - y -= 1; - } - else - { - size = height - 1; - plane += 4; - } - - int index = ((x * size) + y) * 2; - - if ( x < 0 || y < 0 || y >= size || (index + 1) >= 0x400 ) - { - int stairBufferIndex = (totalStairsUsed / MaxItemsPerStairBuffer); - byte[] stairBuffer = m_StairBuffers[stairBufferIndex]; - - int byteIndex = (totalStairsUsed % MaxItemsPerStairBuffer) * 5; - - stairBuffer[byteIndex++] = (byte)(mte.m_ItemID >> 8); - stairBuffer[byteIndex++] = (byte)mte.m_ItemID; - - stairBuffer[byteIndex++] = (byte)mte.m_OffsetX; - stairBuffer[byteIndex++] = (byte)mte.m_OffsetY; - stairBuffer[byteIndex++] = (byte)mte.m_OffsetZ; - - ++totalStairsUsed; - } - else - { - m_PlaneUsed[plane] = true; - m_PlaneBuffers[plane][index] = (byte)(mte.m_ItemID >> 8); - m_PlaneBuffers[plane][index + 1] = (byte)mte.m_ItemID; - } - } - - int planeCount = 0; - - byte[] m_DeflatedBuffer = null; - lock (m_DeflatedBufferPool) - m_DeflatedBuffer = m_DeflatedBufferPool.AcquireBuffer(); - - for( int i = 0; i < m_PlaneBuffers.Length; ++i ) - { - if (!m_PlaneUsed[i]) - { - m_PlaneBufferPool.ReleaseBuffer(m_PlaneBuffers[i]); - continue; - } - - ++planeCount; - - int size = 0; - - if ( i == 0 ) - size = width * height * 2; - else if ( i < 5 ) - size = (width - 1) * (height - 2) * 2; - else - size = width * (height - 1) * 2; - - byte[] inflatedBuffer = m_PlaneBuffers[i]; - - int deflatedLength = m_DeflatedBuffer.Length; - ZLibError ce = Compression.Pack( m_DeflatedBuffer, ref deflatedLength, inflatedBuffer, size, ZLibQuality.Default ); - - if ( ce != ZLibError.Okay ) - { - Console.WriteLine( "ZLib error: {0} (#{1})", ce, (int)ce ); - deflatedLength = 0; - size = 0; - } - - Write( (byte)(0x20 | i) ); - Write( (byte)size ); - Write( (byte)deflatedLength ); - Write( (byte)(((size >> 4) & 0xF0) | ((deflatedLength >> 8) & 0xF)) ); - Write( m_DeflatedBuffer, 0, deflatedLength ); - - totalLength += 4 + deflatedLength; - lock (m_PlaneBufferPool) - m_PlaneBufferPool.ReleaseBuffer(inflatedBuffer); - } - - int totalStairBuffersUsed = (totalStairsUsed + (MaxItemsPerStairBuffer - 1)) / MaxItemsPerStairBuffer; - - for( int i = 0; i < totalStairBuffersUsed; ++i ) - { - ++planeCount; - - int count = (totalStairsUsed - (i * MaxItemsPerStairBuffer)); - - if ( count > MaxItemsPerStairBuffer ) - count = MaxItemsPerStairBuffer; - - int size = count * 5; - - byte[] inflatedBuffer = m_StairBuffers[i]; - - int deflatedLength = m_DeflatedBuffer.Length; - ZLibError ce = Compression.Pack( m_DeflatedBuffer, ref deflatedLength, inflatedBuffer, size, ZLibQuality.Default ); - - if ( ce != ZLibError.Okay ) - { - Console.WriteLine( "ZLib error: {0} (#{1})", ce, (int)ce ); - deflatedLength = 0; - size = 0; - } - - Write( (byte)(9 + i) ); - Write( (byte)size ); - Write( (byte)deflatedLength ); - Write( (byte)(((size >> 4) & 0xF0) | ((deflatedLength >> 8) & 0xF)) ); - Write( m_DeflatedBuffer, 0, deflatedLength ); - - totalLength += 4 + deflatedLength; - } - - lock (m_StairBufferPool) - for (int i = 0; i < m_StairBuffers.Length; ++i) - m_StairBufferPool.ReleaseBuffer(m_StairBuffers[i]); - - lock (m_DeflatedBufferPool) - m_DeflatedBufferPool.ReleaseBuffer(m_DeflatedBuffer); - - m_Stream.Seek( 15, SeekOrigin.Begin ); - - Write( (short)totalLength ); // Buffer length - Write( (byte)planeCount ); // Plane count - } - - private class SendQueueEntry - { - public NetState m_NetState; - public int m_Serial, m_Revision; - public int m_xMin, m_yMin, m_xMax, m_yMax; - public DesignState m_Root; - public MultiTileEntry[] m_Tiles; - - public SendQueueEntry( NetState ns, HouseFoundation foundation, DesignState state ) - { - m_NetState = ns; - m_Serial = foundation.Serial; - m_Revision = state.Revision; - m_Root = state; - - MultiComponentList mcl = state.Components; - - m_xMin = mcl.Min.X; - m_yMin = mcl.Min.Y; - m_xMax = mcl.Max.X; - m_yMax = mcl.Max.Y; - - m_Tiles = mcl.List; - } - } - - private static Queue m_SendQueue; - private static object m_SendQueueSyncRoot; - private static AutoResetEvent m_Sync; - private static Thread m_Thread; - - static DesignStateDetailed() - { - m_SendQueue = new Queue(); - m_SendQueueSyncRoot = ((ICollection)m_SendQueue).SyncRoot; - m_Sync = new AutoResetEvent( false ); - - m_Thread = new Thread( CompressionThread ); - m_Thread.Name = "Housing Compression Thread"; - m_Thread.Start(); - } - - public static void CompressionThread() - { - while( !Core.Closing ) - { - m_Sync.WaitOne(); - - int count; - - lock ( m_SendQueueSyncRoot ) - count = m_SendQueue.Count; - - while( count > 0 ) - { - SendQueueEntry sqe = null; - - lock ( m_SendQueueSyncRoot ) - sqe = m_SendQueue.Dequeue(); - - try - { - Packet p = null; - - lock( sqe.m_Root ) - p = sqe.m_Root.PacketCache; - - if ( p == null ) - { - p = new DesignStateDetailed( sqe.m_Serial, sqe.m_Revision, sqe.m_xMin, sqe.m_yMin, sqe.m_xMax, sqe.m_yMax, sqe.m_Tiles ); - p.SetStatic(); - - lock( sqe.m_Root ) - { - if ( sqe.m_Revision == sqe.m_Root.Revision ) - sqe.m_Root.PacketCache = p; - } - } - - sqe.m_NetState.Send(p); - } - catch( Exception e ) - { - Console.WriteLine( e ); - - try - { - using( StreamWriter op = new StreamWriter( "dsd_exceptions.txt", true ) ) - op.WriteLine( e ); - } - catch - { - } - } - finally - { - lock ( m_SendQueueSyncRoot ) - count = m_SendQueue.Count; - } - - //sqe.m_NetState.Send( new DesignStateDetailed( sqe.m_Serial, sqe.m_Revision, sqe.m_xMin, sqe.m_yMin, sqe.m_xMax, sqe.m_yMax, sqe.m_Tiles ) ); - } - } - } - - public static void SendDetails( NetState ns, HouseFoundation house, DesignState state ) - { - lock ( m_SendQueueSyncRoot ) - m_SendQueue.Enqueue( new SendQueueEntry( ns, house, state ) ); - m_Sync.Set(); - } - } -} + m_Stream.Write((short)0x20); + m_Stream.Write(house.Serial); + m_Stream.Write((byte)0x05); + m_Stream.Write((ushort)0x0000); + m_Stream.Write((ushort)0xFFFF); + m_Stream.Write((ushort)0xFFFF); + m_Stream.Write((byte)0xFF); + } + } + + public sealed class DesignStateGeneral : Packet + { + public DesignStateGeneral(HouseFoundation house, DesignState state) + : base(0xBF) + { + EnsureCapacity(13); + + m_Stream.Write((short)0x1D); + m_Stream.Write(house.Serial); + m_Stream.Write(state.Revision); + } + } + + public sealed class DesignStateDetailed : Packet + { + public const int MaxItemsPerStairBuffer = 750; + + private static BufferPool m_PlaneBufferPool = new BufferPool("Housing Plane Buffers", 9, 0x400); + private static BufferPool m_StairBufferPool = new BufferPool("Housing Stair Buffers", 6, MaxItemsPerStairBuffer * 5); + private static BufferPool m_DeflatedBufferPool = new BufferPool("Housing Deflated Buffers", 1, 0x2000); + + private static Queue m_SendQueue; + private static object m_SendQueueSyncRoot; + private static AutoResetEvent m_Sync; + private static Thread m_Thread; + + private byte[][] m_PlaneBuffers; + + private bool[] m_PlaneUsed = new bool[9]; + private byte[] m_PrimBuffer = new byte[4]; + private byte[][] m_StairBuffers; + + static DesignStateDetailed() + { + m_SendQueue = new Queue(); + m_SendQueueSyncRoot = ((ICollection)m_SendQueue).SyncRoot; + m_Sync = new AutoResetEvent(false); + + m_Thread = new Thread(CompressionThread); + m_Thread.Name = "Housing Compression Thread"; + m_Thread.Start(); + } + + public DesignStateDetailed(int serial, int revision, int xMin, int yMin, int xMax, int yMax, MultiTileEntry[] tiles) + : base(0xD8) + { + EnsureCapacity(17 + tiles.Length * 5); + + Write((byte)0x03); // Compression Type + Write((byte)0x00); // Unknown + Write(serial); + Write(revision); + Write((short)tiles.Length); + Write((short)0); // Buffer length : reserved + Write((byte)0); // Plane count : reserved + + int totalLength = 1; // includes plane count + + int width = xMax - xMin + 1; + int height = yMax - yMin + 1; + + m_PlaneBuffers = new byte[9][]; + + lock (m_PlaneBufferPool) + { + for (int i = 0; i < m_PlaneBuffers.Length; ++i) + m_PlaneBuffers[i] = m_PlaneBufferPool.AcquireBuffer(); + } + + m_StairBuffers = new byte[6][]; + + lock (m_StairBufferPool) + { + for (int i = 0; i < m_StairBuffers.Length; ++i) + m_StairBuffers[i] = m_StairBufferPool.AcquireBuffer(); + } + + Clear(m_PlaneBuffers[0], width * height * 2); + + for (int i = 0; i < 4; ++i) + { + Clear(m_PlaneBuffers[1 + i], (width - 1) * (height - 2) * 2); + Clear(m_PlaneBuffers[5 + i], width * (height - 1) * 2); + } + + int totalStairsUsed = 0; + + for (int i = 0; i < tiles.Length; ++i) + { + MultiTileEntry mte = tiles[i]; + int x = mte.m_OffsetX - xMin; + int y = mte.m_OffsetY - yMin; + int z = mte.m_OffsetZ; + bool floor = TileData.ItemTable[mte.m_ItemID & TileData.MaxItemValue].Height <= 0; + int plane, size; + + switch (z) + { + case 0: + plane = 0; + break; + case 7: + plane = 1; + break; + case 27: + plane = 2; + break; + case 47: + plane = 3; + break; + case 67: + plane = 4; + break; + default: + { + int stairBufferIndex = totalStairsUsed / MaxItemsPerStairBuffer; + byte[] stairBuffer = m_StairBuffers[stairBufferIndex]; + + int byteIndex = totalStairsUsed % MaxItemsPerStairBuffer * 5; + + stairBuffer[byteIndex++] = (byte)(mte.m_ItemID >> 8); + stairBuffer[byteIndex++] = (byte)mte.m_ItemID; + + stairBuffer[byteIndex++] = (byte)mte.m_OffsetX; + stairBuffer[byteIndex++] = (byte)mte.m_OffsetY; + stairBuffer[byteIndex++] = (byte)mte.m_OffsetZ; + + ++totalStairsUsed; + + continue; + } + } + + if (plane == 0) + { + size = height; + } + else if (floor) + { + size = height - 2; + x -= 1; + y -= 1; + } + else + { + size = height - 1; + plane += 4; + } + + int index = (x * size + y) * 2; + + if (x < 0 || y < 0 || y >= size || index + 1 >= 0x400) + { + int stairBufferIndex = totalStairsUsed / MaxItemsPerStairBuffer; + byte[] stairBuffer = m_StairBuffers[stairBufferIndex]; + + int byteIndex = totalStairsUsed % MaxItemsPerStairBuffer * 5; + + stairBuffer[byteIndex++] = (byte)(mte.m_ItemID >> 8); + stairBuffer[byteIndex++] = (byte)mte.m_ItemID; + + stairBuffer[byteIndex++] = (byte)mte.m_OffsetX; + stairBuffer[byteIndex++] = (byte)mte.m_OffsetY; + stairBuffer[byteIndex++] = (byte)mte.m_OffsetZ; + + ++totalStairsUsed; + } + else + { + m_PlaneUsed[plane] = true; + m_PlaneBuffers[plane][index] = (byte)(mte.m_ItemID >> 8); + m_PlaneBuffers[plane][index + 1] = (byte)mte.m_ItemID; + } + } + + int planeCount = 0; + + byte[] m_DeflatedBuffer = null; + lock (m_DeflatedBufferPool) + { + m_DeflatedBuffer = m_DeflatedBufferPool.AcquireBuffer(); + } + + for (int i = 0; i < m_PlaneBuffers.Length; ++i) + { + if (!m_PlaneUsed[i]) + { + m_PlaneBufferPool.ReleaseBuffer(m_PlaneBuffers[i]); + continue; + } + + ++planeCount; + + int size = 0; + + if (i == 0) + size = width * height * 2; + else if (i < 5) + size = (width - 1) * (height - 2) * 2; + else + size = width * (height - 1) * 2; + + byte[] inflatedBuffer = m_PlaneBuffers[i]; + + int deflatedLength = m_DeflatedBuffer.Length; + ZLibError ce = Compression.Pack(m_DeflatedBuffer, ref deflatedLength, inflatedBuffer, size, + ZLibQuality.Default); + + if (ce != ZLibError.Okay) + { + Console.WriteLine("ZLib error: {0} (#{1})", ce, (int)ce); + deflatedLength = 0; + size = 0; + } + + Write((byte)(0x20 | i)); + Write((byte)size); + Write((byte)deflatedLength); + Write((byte)(((size >> 4) & 0xF0) | ((deflatedLength >> 8) & 0xF))); + Write(m_DeflatedBuffer, 0, deflatedLength); + + totalLength += 4 + deflatedLength; + lock (m_PlaneBufferPool) + { + m_PlaneBufferPool.ReleaseBuffer(inflatedBuffer); + } + } + + int totalStairBuffersUsed = (totalStairsUsed + (MaxItemsPerStairBuffer - 1)) / MaxItemsPerStairBuffer; + + for (int i = 0; i < totalStairBuffersUsed; ++i) + { + ++planeCount; + + int count = totalStairsUsed - i * MaxItemsPerStairBuffer; + + if (count > MaxItemsPerStairBuffer) + count = MaxItemsPerStairBuffer; + + int size = count * 5; + + byte[] inflatedBuffer = m_StairBuffers[i]; + + int deflatedLength = m_DeflatedBuffer.Length; + ZLibError ce = Compression.Pack(m_DeflatedBuffer, ref deflatedLength, inflatedBuffer, size, + ZLibQuality.Default); + + if (ce != ZLibError.Okay) + { + Console.WriteLine("ZLib error: {0} (#{1})", ce, (int)ce); + deflatedLength = 0; + size = 0; + } + + Write((byte)(9 + i)); + Write((byte)size); + Write((byte)deflatedLength); + Write((byte)(((size >> 4) & 0xF0) | ((deflatedLength >> 8) & 0xF))); + Write(m_DeflatedBuffer, 0, deflatedLength); + + totalLength += 4 + deflatedLength; + } + + lock (m_StairBufferPool) + { + for (int i = 0; i < m_StairBuffers.Length; ++i) + m_StairBufferPool.ReleaseBuffer(m_StairBuffers[i]); + } + + lock (m_DeflatedBufferPool) + { + m_DeflatedBufferPool.ReleaseBuffer(m_DeflatedBuffer); + } + + m_Stream.Seek(15, SeekOrigin.Begin); + + Write((short)totalLength); // Buffer length + Write((byte)planeCount); // Plane count + } + + public void Write(int value) + { + m_PrimBuffer[0] = (byte)(value >> 24); + m_PrimBuffer[1] = (byte)(value >> 16); + m_PrimBuffer[2] = (byte)(value >> 8); + m_PrimBuffer[3] = (byte)value; + + m_Stream.UnderlyingStream.Write(m_PrimBuffer, 0, 4); + } + + public void Write(short value) + { + m_PrimBuffer[0] = (byte)(value >> 8); + m_PrimBuffer[1] = (byte)value; + + m_Stream.UnderlyingStream.Write(m_PrimBuffer, 0, 2); + } + + public void Write(byte value) + { + m_Stream.UnderlyingStream.WriteByte(value); + } + + public void Write(byte[] buffer, int offset, int size) + { + m_Stream.UnderlyingStream.Write(buffer, offset, size); + } + + public static void Clear(byte[] buffer, int size) + { + for (int i = 0; i < size; ++i) + buffer[i] = 0; + } + + public static void CompressionThread() + { + while (!Core.Closing) + { + m_Sync.WaitOne(); + + int count; + + lock (m_SendQueueSyncRoot) + { + count = m_SendQueue.Count; + } + + while (count > 0) + { + SendQueueEntry sqe = null; + + lock (m_SendQueueSyncRoot) + { + sqe = m_SendQueue.Dequeue(); + } + + try + { + Packet p = null; + + lock (sqe.m_Root) + { + p = sqe.m_Root.PacketCache; + } + + if (p == null) + { + p = new DesignStateDetailed(sqe.m_Serial, sqe.m_Revision, sqe.m_xMin, sqe.m_yMin, sqe.m_xMax, + sqe.m_yMax, sqe.m_Tiles); + p.SetStatic(); + + lock (sqe.m_Root) + { + if (sqe.m_Revision == sqe.m_Root.Revision) + sqe.m_Root.PacketCache = p; + } + } + + sqe.m_NetState.Send(p); + } + catch (Exception e) + { + Console.WriteLine(e); + + try + { + using (StreamWriter op = new StreamWriter("dsd_exceptions.txt", true)) + { + op.WriteLine(e); + } + } + catch + { + } + } + finally + { + lock (m_SendQueueSyncRoot) + { + count = m_SendQueue.Count; + } + } + + //sqe.m_NetState.Send( new DesignStateDetailed( sqe.m_Serial, sqe.m_Revision, sqe.m_xMin, sqe.m_yMin, sqe.m_xMax, sqe.m_yMax, sqe.m_Tiles ) ); + } + } + } + + public static void SendDetails(NetState ns, HouseFoundation house, DesignState state) + { + lock (m_SendQueueSyncRoot) + { + m_SendQueue.Enqueue(new SendQueueEntry(ns, house, state)); + } + + m_Sync.Set(); + } + + private class SendQueueEntry + { + public NetState m_NetState; + public DesignState m_Root; + public int m_Serial, m_Revision; + public MultiTileEntry[] m_Tiles; + public int m_xMin, m_yMin, m_xMax, m_yMax; + + public SendQueueEntry(NetState ns, HouseFoundation foundation, DesignState state) + { + m_NetState = ns; + m_Serial = foundation.Serial; + m_Revision = state.Revision; + m_Root = state; + + MultiComponentList mcl = state.Components; + + m_xMin = mcl.Min.X; + m_yMin = mcl.Min.Y; + m_xMax = mcl.Max.X; + m_yMax = mcl.Max.Y; + + m_Tiles = mcl.List; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/HousePlacement.cs b/Scripts/Multis/HousePlacement.cs index c955bce79..44d01e959 100644 --- a/Scripts/Multis/HousePlacement.cs +++ b/Scripts/Multis/HousePlacement.cs @@ -5,368 +5,361 @@ using Server.Spells; namespace Server.Multis { - public enum HousePlacementResult - { - Valid, - BadRegion, - BadLand, - BadStatic, - BadItem, - NoSurface, - BadRegionHidden, - BadRegionTemp, - InvalidCastleKeep, - BadRegionRaffle - } - - public class HousePlacement - { - private const int YardSize = 5; + public enum HousePlacementResult + { + Valid, + BadRegion, + BadLand, + BadStatic, + BadItem, + NoSurface, + BadRegionHidden, + BadRegionTemp, + InvalidCastleKeep, + BadRegionRaffle + } + + public class HousePlacement + { + private const int YardSize = 5; - // Any land tile which matches one of these ID numbers is considered a road and cannot be placed over. - private static int[] m_RoadIDs = { - 0x0071, 0x0078, - 0x00E8, 0x00EB, - 0x07AE, 0x07B1, - 0x3FF4, 0x3FF4, - 0x3FF8, 0x3FFB, - 0x0442, 0x0479, // Sand stones - 0x0501, 0x0510, // Sand stones - 0x0009, 0x0015, // Furrows - 0x0150, 0x015C // Furrows - }; + // Any land tile which matches one of these ID numbers is considered a road and cannot be placed over. + private static int[] m_RoadIDs = + { + 0x0071, 0x0078, + 0x00E8, 0x00EB, + 0x07AE, 0x07B1, + 0x3FF4, 0x3FF4, + 0x3FF8, 0x3FFB, + 0x0442, 0x0479, // Sand stones + 0x0501, 0x0510, // Sand stones + 0x0009, 0x0015, // Furrows + 0x0150, 0x015C // Furrows + }; - public static HousePlacementResult Check( Mobile from, int multiID, Point3D center, out ArrayList toMove ) - { - // If this spot is considered valid, every item and mobile in this list will be moved under the house sign - toMove = new ArrayList(); + public static HousePlacementResult Check(Mobile from, int multiID, Point3D center, out ArrayList toMove) + { + // If this spot is considered valid, every item and mobile in this list will be moved under the house sign + toMove = new ArrayList(); - Map map = from.Map; + Map map = from.Map; - if ( map == null || map == Map.Internal ) - return HousePlacementResult.BadLand; // A house cannot go here + if (map == null || map == Map.Internal) + return HousePlacementResult.BadLand; // A house cannot go here - if ( from.AccessLevel >= AccessLevel.GameMaster ) - return HousePlacementResult.Valid; // Staff can place anywhere + if (from.AccessLevel >= AccessLevel.GameMaster) + return HousePlacementResult.Valid; // Staff can place anywhere - if ( map == Map.Ilshenar || SpellHelper.IsFeluccaT2A( map, center ) ) - return HousePlacementResult.BadRegion; // No houses in Ilshenar/T2A + if (map == Map.Ilshenar || SpellHelper.IsFeluccaT2A(map, center)) + return HousePlacementResult.BadRegion; // No houses in Ilshenar/T2A - if ( map == Map.Malas && ( multiID == 0x007C || multiID == 0x007E ) ) - return HousePlacementResult.InvalidCastleKeep; + if (map == Map.Malas && (multiID == 0x007C || multiID == 0x007E)) + return HousePlacementResult.InvalidCastleKeep; - NoHousingRegion noHousingRegion = (NoHousingRegion) Region.Find( center, map ).GetRegion( typeof( NoHousingRegion ) ); + NoHousingRegion noHousingRegion = (NoHousingRegion)Region.Find(center, map).GetRegion(typeof(NoHousingRegion)); - if ( noHousingRegion != null ) - return HousePlacementResult.BadRegion; + if (noHousingRegion != null) + return HousePlacementResult.BadRegion; - // This holds data describing the internal structure of the house - MultiComponentList mcl = MultiData.GetComponents( multiID ); + // This holds data describing the internal structure of the house + MultiComponentList mcl = MultiData.GetComponents(multiID); - if ( multiID >= 0x13EC && multiID < 0x1D00 ) - HouseFoundation.AddStairsTo( ref mcl ); // this is a AOS house, add the stairs + if (multiID >= 0x13EC && multiID < 0x1D00) + HouseFoundation.AddStairsTo(ref mcl); // this is a AOS house, add the stairs - // Location of the nortwest-most corner of the house - Point3D start = new Point3D( center.X + mcl.Min.X, center.Y + mcl.Min.Y, center.Z ); + // Location of the nortwest-most corner of the house + Point3D start = new Point3D(center.X + mcl.Min.X, center.Y + mcl.Min.Y, center.Z); - // These are storage lists. They hold items and mobiles found in the map for further processing - List items = new List(); - List mobiles = new List(); + // These are storage lists. They hold items and mobiles found in the map for further processing + List items = new List(); + List mobiles = new List(); - // These are also storage lists. They hold location values indicating the yard and border locations. - List yard = new List(), borders = new List(); + // These are also storage lists. They hold location values indicating the yard and border locations. + List yard = new List(), borders = new List(); - /* RULES: - * - * 1) All tiles which are around the -outside- of the foundation must not have anything impassable. - * 2) No impassable object or land tile may come in direct contact with any part of the house. - * 3) Five tiles from the front and back of the house must be completely clear of all house tiles. - * 4) The foundation must rest flatly on a surface. Any bumps around the foundation are not allowed. - * 5) No foundation tile may reside over terrain which is viewed as a road. - */ + /* RULES: + * + * 1) All tiles which are around the -outside- of the foundation must not have anything impassable. + * 2) No impassable object or land tile may come in direct contact with any part of the house. + * 3) Five tiles from the front and back of the house must be completely clear of all house tiles. + * 4) The foundation must rest flatly on a surface. Any bumps around the foundation are not allowed. + * 5) No foundation tile may reside over terrain which is viewed as a road. + */ - for ( int x = 0; x < mcl.Width; ++x ) - { - for ( int y = 0; y < mcl.Height; ++y ) - { - int tileX = start.X + x; - int tileY = start.Y + y; + for (int x = 0; x < mcl.Width; ++x) + for (int y = 0; y < mcl.Height; ++y) + { + int tileX = start.X + x; + int tileY = start.Y + y; - StaticTile[] addTiles = mcl.Tiles[x][y]; + StaticTile[] addTiles = mcl.Tiles[x][y]; - if ( addTiles.Length == 0 ) - continue; // There are no tiles here, continue checking somewhere else + if (addTiles.Length == 0) + continue; // There are no tiles here, continue checking somewhere else - Point3D testPoint = new Point3D( tileX, tileY, center.Z ); + Point3D testPoint = new Point3D(tileX, tileY, center.Z); - Region reg = Region.Find( testPoint, map ); + Region reg = Region.Find(testPoint, map); - if ( !reg.AllowHousing( from, testPoint ) ) // Cannot place houses in dungeons, towns, treasure map areas etc - { - if ( reg.IsPartOf( typeof( TempNoHousingRegion ) ) ) - return HousePlacementResult.BadRegionTemp; + if (!reg.AllowHousing(from, testPoint)) // Cannot place houses in dungeons, towns, treasure map areas etc + { + if (reg.IsPartOf(typeof(TempNoHousingRegion))) + return HousePlacementResult.BadRegionTemp; - if ( reg.IsPartOf( typeof( TreasureRegion ) ) || reg.IsPartOf( typeof( HouseRegion ) ) ) - return HousePlacementResult.BadRegionHidden; + if (reg.IsPartOf(typeof(TreasureRegion)) || reg.IsPartOf(typeof(HouseRegion))) + return HousePlacementResult.BadRegionHidden; - if ( reg.IsPartOf( typeof( HouseRaffleRegion ) ) ) - return HousePlacementResult.BadRegionRaffle; + if (reg.IsPartOf(typeof(HouseRaffleRegion))) + return HousePlacementResult.BadRegionRaffle; - return HousePlacementResult.BadRegion; - } + return HousePlacementResult.BadRegion; + } - LandTile landTile = map.Tiles.GetLandTile( tileX, tileY ); - int landID = landTile.ID & TileData.MaxLandValue; + LandTile landTile = map.Tiles.GetLandTile(tileX, tileY); + int landID = landTile.ID & TileData.MaxLandValue; - StaticTile[] oldTiles = map.Tiles.GetStaticTiles( tileX, tileY, true ); + StaticTile[] oldTiles = map.Tiles.GetStaticTiles(tileX, tileY, true); - Sector sector = map.GetSector( tileX, tileY ); + Sector sector = map.GetSector(tileX, tileY); - items.Clear(); + items.Clear(); - for ( int i = 0; i < sector.Items.Count; ++i ) - { - Item item = sector.Items[i]; + for (int i = 0; i < sector.Items.Count; ++i) + { + Item item = sector.Items[i]; - if ( item.Visible && item.X == tileX && item.Y == tileY ) - items.Add( item ); - } + if (item.Visible && item.X == tileX && item.Y == tileY) + items.Add(item); + } - mobiles.Clear(); + mobiles.Clear(); - for ( int i = 0; i < sector.Mobiles.Count; ++i ) - { - Mobile m = sector.Mobiles[i]; + for (int i = 0; i < sector.Mobiles.Count; ++i) + { + Mobile m = sector.Mobiles[i]; - if ( m.X == tileX && m.Y == tileY ) - mobiles.Add( m ); - } + if (m.X == tileX && m.Y == tileY) + mobiles.Add(m); + } - int landStartZ = 0, landAvgZ = 0, landTopZ = 0; + int landStartZ = 0, landAvgZ = 0, landTopZ = 0; - map.GetAverageZ( tileX, tileY, ref landStartZ, ref landAvgZ, ref landTopZ ); + map.GetAverageZ(tileX, tileY, ref landStartZ, ref landAvgZ, ref landTopZ); - bool hasFoundation = false; + bool hasFoundation = false; - for ( int i = 0; i < addTiles.Length; ++i ) - { - StaticTile addTile = addTiles[i]; + for (int i = 0; i < addTiles.Length; ++i) + { + StaticTile addTile = addTiles[i]; - if ( addTile.ID == 0x1 ) // Nodraw - continue; + if (addTile.ID == 0x1) // Nodraw + continue; - TileFlag addTileFlags = TileData.ItemTable[addTile.ID & TileData.MaxItemValue].Flags; + TileFlag addTileFlags = TileData.ItemTable[addTile.ID & TileData.MaxItemValue].Flags; - bool isFoundation = ( addTile.Z == 0 && (addTileFlags & TileFlag.Wall) != 0 ); - bool hasSurface = false; + bool isFoundation = addTile.Z == 0 && (addTileFlags & TileFlag.Wall) != 0; + bool hasSurface = false; - if ( isFoundation ) - hasFoundation = true; + if (isFoundation) + hasFoundation = true; - int addTileZ = center.Z + addTile.Z; - int addTileTop = addTileZ + addTile.Height; + int addTileZ = center.Z + addTile.Z; + int addTileTop = addTileZ + addTile.Height; - if ( (addTileFlags & TileFlag.Surface) != 0 ) - addTileTop += 16; + if ((addTileFlags & TileFlag.Surface) != 0) + addTileTop += 16; - if ( addTileTop > landStartZ && landAvgZ > addTileZ ) - return HousePlacementResult.BadLand; // Broke rule #2 + if (addTileTop > landStartZ && landAvgZ > addTileZ) + return HousePlacementResult.BadLand; // Broke rule #2 - if ( isFoundation && ((TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) == 0) && landAvgZ == center.Z ) - hasSurface = true; + if (isFoundation && + (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) == 0 && + landAvgZ == center.Z) + hasSurface = true; - for ( int j = 0; j < oldTiles.Length; ++j ) - { - StaticTile oldTile = oldTiles[j]; - ItemData id = TileData.ItemTable[oldTile.ID & TileData.MaxItemValue]; + for (int j = 0; j < oldTiles.Length; ++j) + { + StaticTile oldTile = oldTiles[j]; + ItemData id = TileData.ItemTable[oldTile.ID & TileData.MaxItemValue]; - if ( (id.Impassable || (id.Surface && (id.Flags & TileFlag.Background) == 0)) && addTileTop > oldTile.Z && (oldTile.Z + id.CalcHeight) > addTileZ ) - return HousePlacementResult.BadStatic; // Broke rule #2 - /*else if ( isFoundation && !hasSurface && (id.Flags & TileFlag.Surface) != 0 && (oldTile.Z + id.CalcHeight) == center.Z ) - hasSurface = true;*/ - } + if ((id.Impassable || id.Surface && (id.Flags & TileFlag.Background) == 0) && + addTileTop > oldTile.Z && oldTile.Z + id.CalcHeight > addTileZ) + return HousePlacementResult.BadStatic; // Broke rule #2 + /*else if ( isFoundation && !hasSurface && (id.Flags & TileFlag.Surface) != 0 && (oldTile.Z + id.CalcHeight) == center.Z ) + hasSurface = true;*/ + } - for ( int j = 0; j < items.Count; ++j ) - { - Item item = items[j]; - ItemData id = item.ItemData; + for (int j = 0; j < items.Count; ++j) + { + Item item = items[j]; + ItemData id = item.ItemData; - if ( addTileTop > item.Z && (item.Z + id.CalcHeight) > addTileZ ) - { - if ( item.Movable ) - toMove.Add( item ); - else if ( (id.Impassable || (id.Surface && (id.Flags & TileFlag.Background) == 0)) ) - return HousePlacementResult.BadItem; // Broke rule #2 - } - /*else if ( isFoundation && !hasSurface && (id.Flags & TileFlag.Surface) != 0 && (item.Z + id.CalcHeight) == center.Z ) - { - hasSurface = true; - }*/ - } + if (addTileTop > item.Z && item.Z + id.CalcHeight > addTileZ) + { + if (item.Movable) + toMove.Add(item); + else if (id.Impassable || id.Surface && (id.Flags & TileFlag.Background) == 0) + return HousePlacementResult.BadItem; // Broke rule #2 + } - if ( isFoundation && !hasSurface ) - return HousePlacementResult.NoSurface; // Broke rule #4 + /*else if ( isFoundation && !hasSurface && (id.Flags & TileFlag.Surface) != 0 && (item.Z + id.CalcHeight) == center.Z ) + { + hasSurface = true; + }*/ + } - for ( int j = 0; j < mobiles.Count; ++j ) - { - Mobile m = mobiles[j]; + if (isFoundation && !hasSurface) + return HousePlacementResult.NoSurface; // Broke rule #4 - if ( addTileTop > m.Z && (m.Z + 16) > addTileZ ) - toMove.Add( m ); - } - } + for (int j = 0; j < mobiles.Count; ++j) + { + Mobile m = mobiles[j]; - for ( int i = 0; i < m_RoadIDs.Length; i += 2 ) - { - if ( landID >= m_RoadIDs[i] && landID <= m_RoadIDs[i + 1] ) - return HousePlacementResult.BadLand; // Broke rule #5 - } + if (addTileTop > m.Z && m.Z + 16 > addTileZ) + toMove.Add(m); + } + } - if ( hasFoundation ) - { - for ( int xOffset = -1; xOffset <= 1; ++xOffset ) - { - for ( int yOffset = -YardSize; yOffset <= YardSize; ++yOffset ) - { - Point2D yardPoint = new Point2D( tileX + xOffset, tileY + yOffset ); - - if ( !yard.Contains( yardPoint ) ) - yard.Add( yardPoint ); - } - } - - for ( int xOffset = -1; xOffset <= 1; ++xOffset ) - { - for ( int yOffset = -1; yOffset <= 1; ++yOffset ) - { - if ( xOffset == 0 && yOffset == 0 ) - continue; - - // To ease this rule, we will not add to the border list if the tile here is under a base floor (z<=8) - - int vx = x + xOffset; - int vy = y + yOffset; - - if ( vx >= 0 && vx < mcl.Width && vy >= 0 && vy < mcl.Height ) - { - StaticTile[] breakTiles = mcl.Tiles[vx][vy]; - bool shouldBreak = false; - - for ( int i = 0; !shouldBreak && i < breakTiles.Length; ++i ) - { - StaticTile breakTile = breakTiles[i]; - - if ( breakTile.Height == 0 && breakTile.Z <= 8 && TileData.ItemTable[breakTile.ID & TileData.MaxItemValue].Surface ) - shouldBreak = true; - } - - if ( shouldBreak ) - continue; - } - - Point2D borderPoint = new Point2D( tileX + xOffset, tileY + yOffset ); - - if ( !borders.Contains( borderPoint ) ) - borders.Add( borderPoint ); - } - } - } - } - } - - for ( int i = 0; i < borders.Count; ++i ) - { - Point2D borderPoint = borders[i]; - - LandTile landTile = map.Tiles.GetLandTile( borderPoint.X, borderPoint.Y ); - int landID = landTile.ID & TileData.MaxLandValue; - - if ( (TileData.LandTable[landID].Flags & TileFlag.Impassable) != 0 ) - return HousePlacementResult.BadLand; - - for ( int j = 0; j < m_RoadIDs.Length; j += 2 ) - { - if ( landID >= m_RoadIDs[j] && landID <= m_RoadIDs[j + 1] ) - return HousePlacementResult.BadLand; // Broke rule #5 - } - - StaticTile[] tiles = map.Tiles.GetStaticTiles( borderPoint.X, borderPoint.Y, true ); - - for ( int j = 0; j < tiles.Length; ++j ) - { - StaticTile tile = tiles[j]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - - if ( id.Impassable || (id.Surface && (id.Flags & TileFlag.Background) == 0 && (tile.Z + id.CalcHeight) > (center.Z + 2)) ) - return HousePlacementResult.BadStatic; // Broke rule #1 - } - - Sector sector = map.GetSector( borderPoint.X, borderPoint.Y ); - List sectorItems = sector.Items; - - for ( int j = 0; j < sectorItems.Count; ++j ) - { - Item item = sectorItems[j]; - - if ( item.X != borderPoint.X || item.Y != borderPoint.Y || item.Movable ) - continue; - - ItemData id = item.ItemData; - - if ( id.Impassable || (id.Surface && (id.Flags & TileFlag.Background) == 0 && (item.Z + id.CalcHeight) > (center.Z + 2)) ) - return HousePlacementResult.BadItem; // Broke rule #1 - } - } - - List _sectors = new List(); - List _houses = new List(); - - for ( int i = 0; i < yard.Count; i++ ) { - Sector sector = map.GetSector( yard[i] ); - - if ( !_sectors.Contains( sector ) ) { - _sectors.Add( sector ); - - if ( sector.Multis != null ) { - for ( int j = 0; j < sector.Multis.Count; j++ ) { - if ( sector.Multis[j] is BaseHouse ) { - BaseHouse _house = (BaseHouse)sector.Multis[j]; - if ( !_houses.Contains( _house ) ) { - _houses.Add( _house ); - } - } - } - } - } - } - - for ( int i = 0; i < yard.Count; ++i ) - { - foreach ( BaseHouse b in _houses ) { - if ( b.Contains( yard[i] ) ) - return HousePlacementResult.BadStatic; // Broke rule #3 - } - - /*Point2D yardPoint = yard[i]; - - IPooledEnumerable eable = map.GetMultiTilesAt( yardPoint.X, yardPoint.Y ); - - foreach ( StaticTile[] tile in eable ) - { - for ( int j = 0; j < tile.Length; ++j ) - { - if ( (TileData.ItemTable[tile[j].ID & TileData.MaxItemValue].Flags & (TileFlag.Impassable | TileFlag.Surface)) != 0 ) - { - eable.Free(); - return HousePlacementResult.BadStatic; // Broke rule #3 - } - } - } - - eable.Free();*/ - } - - return HousePlacementResult.Valid; - } - } + for (int i = 0; i < m_RoadIDs.Length; i += 2) + if (landID >= m_RoadIDs[i] && landID <= m_RoadIDs[i + 1]) + return HousePlacementResult.BadLand; // Broke rule #5 + + if (hasFoundation) + { + for (int xOffset = -1; xOffset <= 1; ++xOffset) + for (int yOffset = -YardSize; yOffset <= YardSize; ++yOffset) + { + Point2D yardPoint = new Point2D(tileX + xOffset, tileY + yOffset); + + if (!yard.Contains(yardPoint)) + yard.Add(yardPoint); + } + + for (int xOffset = -1; xOffset <= 1; ++xOffset) + for (int yOffset = -1; yOffset <= 1; ++yOffset) + { + if (xOffset == 0 && yOffset == 0) + continue; + + // To ease this rule, we will not add to the border list if the tile here is under a base floor (z<=8) + + int vx = x + xOffset; + int vy = y + yOffset; + + if (vx >= 0 && vx < mcl.Width && vy >= 0 && vy < mcl.Height) + { + StaticTile[] breakTiles = mcl.Tiles[vx][vy]; + bool shouldBreak = false; + + for (int i = 0; !shouldBreak && i < breakTiles.Length; ++i) + { + StaticTile breakTile = breakTiles[i]; + + if (breakTile.Height == 0 && breakTile.Z <= 8 && + TileData.ItemTable[breakTile.ID & TileData.MaxItemValue].Surface) + shouldBreak = true; + } + + if (shouldBreak) + continue; + } + + Point2D borderPoint = new Point2D(tileX + xOffset, tileY + yOffset); + + if (!borders.Contains(borderPoint)) + borders.Add(borderPoint); + } + } + } + + for (int i = 0; i < borders.Count; ++i) + { + Point2D borderPoint = borders[i]; + + LandTile landTile = map.Tiles.GetLandTile(borderPoint.X, borderPoint.Y); + int landID = landTile.ID & TileData.MaxLandValue; + + if ((TileData.LandTable[landID].Flags & TileFlag.Impassable) != 0) + return HousePlacementResult.BadLand; + + for (int j = 0; j < m_RoadIDs.Length; j += 2) + if (landID >= m_RoadIDs[j] && landID <= m_RoadIDs[j + 1]) + return HousePlacementResult.BadLand; // Broke rule #5 + + StaticTile[] tiles = map.Tiles.GetStaticTiles(borderPoint.X, borderPoint.Y, true); + + for (int j = 0; j < tiles.Length; ++j) + { + StaticTile tile = tiles[j]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + + if (id.Impassable || id.Surface && (id.Flags & TileFlag.Background) == 0 && + tile.Z + id.CalcHeight > center.Z + 2) + return HousePlacementResult.BadStatic; // Broke rule #1 + } + + Sector sector = map.GetSector(borderPoint.X, borderPoint.Y); + List sectorItems = sector.Items; + + for (int j = 0; j < sectorItems.Count; ++j) + { + Item item = sectorItems[j]; + + if (item.X != borderPoint.X || item.Y != borderPoint.Y || item.Movable) + continue; + + ItemData id = item.ItemData; + + if (id.Impassable || id.Surface && (id.Flags & TileFlag.Background) == 0 && + item.Z + id.CalcHeight > center.Z + 2) + return HousePlacementResult.BadItem; // Broke rule #1 + } + } + + List _sectors = new List(); + List _houses = new List(); + + for (int i = 0; i < yard.Count; i++) + { + Sector sector = map.GetSector(yard[i]); + + if (!_sectors.Contains(sector)) + { + _sectors.Add(sector); + + if (sector.Multis != null) + for (int j = 0; j < sector.Multis.Count; j++) + if (sector.Multis[j] is BaseHouse) + { + BaseHouse _house = (BaseHouse)sector.Multis[j]; + if (!_houses.Contains(_house)) _houses.Add(_house); + } + } + } + + for (int i = 0; i < yard.Count; ++i) + foreach (BaseHouse b in _houses) + if (b.Contains(yard[i])) + return HousePlacementResult.BadStatic; // Broke rule #3 + /*Point2D yardPoint = yard[i]; + + IPooledEnumerable eable = map.GetMultiTilesAt( yardPoint.X, yardPoint.Y ); + + foreach ( StaticTile[] tile in eable ) + { + for ( int j = 0; j < tile.Length; ++j ) + { + if ( (TileData.ItemTable[tile[j].ID & TileData.MaxItemValue].Flags & (TileFlag.Impassable | TileFlag.Surface)) != 0 ) + { + eable.Free(); + return HousePlacementResult.BadStatic; // Broke rule #3 + } + } + } + + eable.Free();*/ + + return HousePlacementResult.Valid; + } + } } \ No newline at end of file diff --git a/Scripts/Multis/HousePlacementTool.cs b/Scripts/Multis/HousePlacementTool.cs index 68e29594e..82b481170 100644 --- a/Scripts/Multis/HousePlacementTool.cs +++ b/Scripts/Multis/HousePlacementTool.cs @@ -1,779 +1,888 @@ using System; using System.Collections; using Server.Gumps; -using Server.Multis; using Server.Mobiles; +using Server.Multis; +using Server.Network; using Server.Regions; using Server.Targeting; namespace Server.Items { - public class HousePlacementTool : Item - { - public override int LabelNumber => 1060651; // a house placement tool - - [Constructible] - public HousePlacementTool() : base( 0x14F6 ) - { - Weight = 3.0; - LootType = LootType.Blessed; - } - - public override void OnDoubleClick( Mobile from ) - { - if ( IsChildOf( from.Backpack ) ) - from.SendGump( new HousePlacementCategoryGump( from ) ); - else - from.SendLocalizedMessage( 1042001 ); // That must be in your pack for you to use it. - } - - public HousePlacementTool( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 0 ); // version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - if ( Weight == 0.0 ) - Weight = 3.0; - } - } - - public class HousePlacementCategoryGump : Gump - { - private Mobile m_From; - - private const int LabelColor = 0x7FFF; - private const int LabelColorDisabled = 0x4210; - - public HousePlacementCategoryGump( Mobile from ) : base( 50, 50 ) - { - m_From = from; - - from.CloseGump( typeof( HousePlacementCategoryGump ) ); - from.CloseGump( typeof( HousePlacementListGump ) ); - - AddPage( 0 ); - - AddBackground( 0, 0, 270, 145, 5054 ); - - AddImageTiled( 10, 10, 250, 125, 2624 ); - AddAlphaRegion( 10, 10, 250, 125 ); - - AddHtmlLocalized( 10, 10, 250, 20, 1060239, LabelColor, false, false ); //
HOUSE PLACEMENT TOOL
- - AddButton( 10, 110, 4017, 4019, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 110, 150, 20, 3000363, LabelColor, false, false ); // Close - - AddButton( 10, 40, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 40, 200, 20, 1060390, LabelColor, false, false ); // Classic Houses - - AddButton( 10, 60, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 60, 200, 20, 1060391, LabelColor, false, false ); // 2-Story Customizable Houses - - AddButton( 10, 80, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 45, 80, 200, 20, 1060392, LabelColor, false, false ); // 3-Story Customizable Houses - } - - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( !m_From.CheckAlive() || m_From.Backpack?.FindItemByType( typeof( HousePlacementTool ) ) == null ) - return; - - switch ( info.ButtonID ) - { - case 1: // Classic Houses - { - m_From.SendGump( new HousePlacementListGump( m_From, HousePlacementEntry.ClassicHouses ) ); - break; - } - case 2: // 2-Story Customizable Houses - { - m_From.SendGump( new HousePlacementListGump( m_From, HousePlacementEntry.TwoStoryFoundations ) ); - break; - } - case 3: // 3-Story Customizable Houses - { - m_From.SendGump( new HousePlacementListGump( m_From, HousePlacementEntry.ThreeStoryFoundations ) ); - break; - } - } - } - } - - public class HousePlacementListGump : Gump - { - private Mobile m_From; - private HousePlacementEntry[] m_Entries; - - private const int LabelColor = 0x7FFF; - private const int LabelHue = 0x480; - - public HousePlacementListGump( Mobile from, HousePlacementEntry[] entries ) : base( 50, 50 ) - { - m_From = from; - m_Entries = entries; - - from.CloseGump( typeof( HousePlacementCategoryGump ) ); - from.CloseGump( typeof( HousePlacementListGump ) ); - - AddPage( 0 ); - - AddBackground( 0, 0, 520, 420, 5054 ); - - AddImageTiled( 10, 10, 500, 20, 2624 ); - AddAlphaRegion( 10, 10, 500, 20 ); - - AddHtmlLocalized( 10, 10, 500, 20, 1060239, LabelColor, false, false ); //
HOUSE PLACEMENT TOOL
- - AddImageTiled( 10, 40, 500, 20, 2624 ); - AddAlphaRegion( 10, 40, 500, 20 ); - - AddHtmlLocalized( 50, 40, 225, 20, 1060235, LabelColor, false, false ); // House Description - AddHtmlLocalized( 275, 40, 75, 20, 1060236, LabelColor, false, false ); // Storage - AddHtmlLocalized( 350, 40, 75, 20, 1060237, LabelColor, false, false ); // Lockdowns - AddHtmlLocalized( 425, 40, 75, 20, 1060034, LabelColor, false, false ); // Cost - - AddImageTiled( 10, 70, 500, 280, 2624 ); - AddAlphaRegion( 10, 70, 500, 280 ); - - AddImageTiled( 10, 360, 500, 20, 2624 ); - AddAlphaRegion( 10, 360, 500, 20 ); - - AddHtmlLocalized( 10, 360, 250, 20, 1060645, LabelColor, false, false ); // Bank Balance: - AddLabel( 250, 360, LabelHue, Banker.GetBalance( from ).ToString() ); - - AddImageTiled( 10, 390, 500, 20, 2624 ); - AddAlphaRegion( 10, 390, 500, 20 ); - - AddButton( 10, 390, 4017, 4019, 0, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, 390, 100, 20, 3000363, LabelColor, false, false ); // Close - - for ( int i = 0; i < entries.Length; ++i ) - { - int page = 1 + (i / 14); - int index = i % 14; - - if ( index == 0 ) - { - if ( page > 1 ) - { - AddButton( 450, 390, 4005, 4007, 0, GumpButtonType.Page, page ); - AddHtmlLocalized( 400, 390, 100, 20, 3000406, LabelColor, false, false ); // Next - } - - AddPage( page ); - - if ( page > 1 ) - { - AddButton( 200, 390, 4014, 4016, 0, GumpButtonType.Page, page - 1 ); - AddHtmlLocalized( 250, 390, 100, 20, 3000405, LabelColor, false, false ); // Previous - } - } - - HousePlacementEntry entry = entries[i]; - - int y = 70 + (index * 20); - - AddButton( 10, y, 4005, 4007, 1 + i, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 50, y, 225, 20, entry.Description, LabelColor, false, false ); - AddLabel( 275, y, LabelHue, entry.Storage.ToString() ); - AddLabel( 350, y, LabelHue, entry.Lockdowns.ToString() ); - AddLabel( 425, y, LabelHue, entry.Cost.ToString() ); - } - } - - public override void OnResponse( Network.NetState sender, RelayInfo info ) - { - if ( !m_From.CheckAlive() || m_From.Backpack?.FindItemByType( typeof( HousePlacementTool ) ) == null ) - return; - - int index = info.ButtonID - 1; - - if ( index >= 0 && index < m_Entries.Length ) - { - if ( m_From.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse( m_From ) ) - m_From.SendLocalizedMessage( 501271 ); // You already own a house, you may not place another! - else - m_From.Target = new NewHousePlacementTarget( m_Entries, m_Entries[index] ); - } - else - { - m_From.SendGump( new HousePlacementCategoryGump( m_From ) ); - } - } - } - - public class NewHousePlacementTarget : MultiTarget - { - private HousePlacementEntry m_Entry; - private HousePlacementEntry[] m_Entries; - - private bool m_Placed; - - public NewHousePlacementTarget( HousePlacementEntry[] entries, HousePlacementEntry entry ) : base( entry.MultiID, entry.Offset ) - { - Range = 14; - - m_Entries = entries; - m_Entry = entry; - } - - protected override void OnTarget( Mobile from, object o ) - { - if ( !from.CheckAlive() || from.Backpack?.FindItemByType( typeof( HousePlacementTool ) ) == null ) - return; - - IPoint3D ip = o as IPoint3D; - - if ( ip != null ) - { - if ( ip is Item ) - ip = ((Item)ip).GetWorldTop(); - - Point3D p = new Point3D( ip ); - - Region reg = Region.Find( new Point3D( p ), from.Map ); - - if ( from.AccessLevel >= AccessLevel.GameMaster || reg.AllowHousing( from, p ) ) - m_Placed = m_Entry.OnPlacement( from, p ); - else if ( reg.IsPartOf( typeof( TempNoHousingRegion ) ) ) - from.SendLocalizedMessage( 501270 ); // Lord British has decreed a 'no build' period, thus you cannot build this house at this time. - else if ( reg.IsPartOf( typeof( TreasureRegion ) ) || reg.IsPartOf( typeof( HouseRegion ) ) ) - from.SendLocalizedMessage( 1043287 ); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. - else if ( reg.IsPartOf( typeof( HouseRaffleRegion ) ) ) - from.SendLocalizedMessage( 1150493 ); // You must have a deed for this plot of land in order to build here. - else - from.SendLocalizedMessage( 501265 ); // Housing can not be created in this area. - } - } - - protected override void OnTargetFinish( Mobile from ) - { - if ( !from.CheckAlive() || from.Backpack?.FindItemByType( typeof( HousePlacementTool ) ) == null ) - return; - - if ( !m_Placed ) - from.SendGump( new HousePlacementListGump( from, m_Entries ) ); - } - } - - public class HousePlacementEntry - { - private int m_Storage; - private int m_Lockdowns; - private int m_NewStorage; - private int m_NewLockdowns; - - public Type Type { get; } - - public int Description { get; } - - public int Storage => BaseHouse.NewVendorSystem ? m_NewStorage : m_Storage; - public int Lockdowns => BaseHouse.NewVendorSystem ? m_NewLockdowns : m_Lockdowns; - public int Vendors { get; } - - public int Cost { get; } - - public int MultiID { get; } - - public Point3D Offset { get; } - - public HousePlacementEntry( Type type, int description, int storage, int lockdowns, int newStorage, int newLockdowns, int vendors, int cost, int xOffset, int yOffset, int zOffset, int multiID ) - { - Type = type; - Description = description; - m_Storage = storage; - m_Lockdowns = lockdowns; - m_NewStorage = newStorage; - m_NewLockdowns = newLockdowns; - Vendors = vendors; - Cost = cost; - - Offset = new Point3D( xOffset, yOffset, zOffset ); - - MultiID = multiID; - } - - public BaseHouse ConstructHouse( Mobile from ) - { - try - { - object[] args; - - if ( Type == typeof( HouseFoundation ) ) - args = new object[4]{ from, MultiID, m_Storage, m_Lockdowns }; - else if ( Type == typeof( SmallOldHouse ) || Type == typeof( SmallShop ) || Type == typeof( TwoStoryHouse ) ) - args = new object[2]{ from, MultiID }; - else - args = new object[1]{ from }; - - return Activator.CreateInstance( Type, args ) as BaseHouse; - } - catch - { - } - - return null; - } - - public void PlacementWarning_Callback( Mobile from, bool okay, object state ) - { - if ( !from.CheckAlive() || from.Backpack?.FindItemByType( typeof( HousePlacementTool ) ) == null ) - return; - - PreviewHouse prevHouse = (PreviewHouse)state; - - if ( !okay ) - { - prevHouse.Delete(); - return; - } - - if ( prevHouse.Deleted ) - { - /* Too much time has passed and the test house you created has been deleted. - * Please try again! - */ - from.SendGump( new NoticeGump( 1060637, 30720, 1060647, 32512, 320, 180, null, null ) ); - - return; - } - - Point3D center = prevHouse.Location; - Map map = prevHouse.Map; - - prevHouse.Delete(); - - ArrayList toMove; - //Point3D center = new Point3D( p.X - m_Offset.X, p.Y - m_Offset.Y, p.Z - m_Offset.Z ); - HousePlacementResult res = HousePlacement.Check( from, MultiID, center, out toMove ); - - switch ( res ) - { - case HousePlacementResult.Valid: - { - if ( from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse( from ) ) - { - from.SendLocalizedMessage( 501271 ); // You already own a house, you may not place another! - } - else - { - BaseHouse house = ConstructHouse( from ); - - if ( house == null ) - return; - - house.Price = Cost; - - if ( from.AccessLevel >= AccessLevel.GameMaster ) - { - from.SendMessage( "{0} gold would have been withdrawn from your bank if you were not a GM.", Cost.ToString() ); - } - else - { - if ( Banker.Withdraw( from, Cost ) ) - { - from.SendLocalizedMessage( 1060398, Cost.ToString() ); // ~1_AMOUNT~ gold has been withdrawn from your bank box. - } - else - { - house.RemoveKeys( from ); - house.Delete(); - from.SendLocalizedMessage( 1060646 ); // You do not have the funds available in your bank box to purchase this house. Try placing a smaller house, or adding gold or checks to your bank box. - return; - } - } - - house.MoveToWorld( center, from.Map ); - - for ( int i = 0; i < toMove.Count; ++i ) - { - object o = toMove[ i ]; - - if ( o is Mobile ) - ( (Mobile) o ).Location = house.BanLocation; - else if ( o is Item ) - ( (Item) o ).Location = house.BanLocation; - } - } - - break; - } - case HousePlacementResult.BadItem: - case HousePlacementResult.BadLand: - case HousePlacementResult.BadStatic: - case HousePlacementResult.BadRegionHidden: - case HousePlacementResult.NoSurface: - { - from.SendLocalizedMessage( 1043287 ); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. - break; - } - case HousePlacementResult.BadRegion: - { - from.SendLocalizedMessage( 501265 ); // Housing cannot be created in this area. - break; - } - case HousePlacementResult.BadRegionTemp: - { - from.SendLocalizedMessage( 501270 ); // Lord British has decreed a 'no build' period, thus you cannot build this house at this time. - break; - } - case HousePlacementResult.BadRegionRaffle: - { - from.SendLocalizedMessage( 1150493 ); // You must have a deed for this plot of land in order to build here. - break; - } - case HousePlacementResult.InvalidCastleKeep: - { - from.SendLocalizedMessage( 1061122 ); // Castles and keeps cannot be created here. - break; - } - } - } - - public bool OnPlacement( Mobile from, Point3D p ) - { - if ( !from.CheckAlive() || from.Backpack?.FindItemByType( typeof( HousePlacementTool ) ) == null ) - return false; - - ArrayList toMove; - Point3D center = new Point3D( p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z ); - HousePlacementResult res = HousePlacement.Check( from, MultiID, center, out toMove ); - - switch ( res ) - { - case HousePlacementResult.Valid: - { - if ( from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse( from ) ) - { - from.SendLocalizedMessage( 501271 ); // You already own a house, you may not place another! - } - else - { - from.SendLocalizedMessage( 1011576 ); // This is a valid location. - - PreviewHouse prev = new PreviewHouse( MultiID ); - - MultiComponentList mcl = prev.Components; - - Point3D banLoc = new Point3D( center.X + mcl.Min.X, center.Y + mcl.Max.Y + 1, center.Z ); - - for ( int i = 0; i < mcl.List.Length; ++i ) - { - MultiTileEntry entry = mcl.List[i]; - - int itemID = entry.m_ItemID; - - if ( itemID >= 0xBA3 && itemID <= 0xC0E ) - { - banLoc = new Point3D( center.X + entry.m_OffsetX, center.Y + entry.m_OffsetY, center.Z ); - break; - } - } - - for ( int i = 0; i < toMove.Count; ++i ) - { - object o = toMove[i]; - - if ( o is Mobile ) - ((Mobile)o).Location = banLoc; - else if ( o is Item ) - ((Item)o).Location = banLoc; - } - - prev.MoveToWorld( center, from.Map ); - - /* You are about to place a new house. - * Placing this house will condemn any and all of your other houses that you may have. - * All of your houses on all shards will be affected. - * - * In addition, you will not be able to place another house or have one transferred to you for one (1) real-life week. - * - * Once you accept these terms, these effects cannot be reversed. - * Re-deeding or transferring your new house will not uncondemn your other house(s) nor will the one week timer be removed. - * - * If you are absolutely certain you wish to proceed, click the button next to OKAY below. - * If you do not wish to trade for this house, click CANCEL. - */ - from.SendGump( new WarningGump( 1060635, 30720, 1049583, 32512, 420, 280, PlacementWarning_Callback, prev ) ); - - return true; - } - - break; - } - case HousePlacementResult.BadItem: - case HousePlacementResult.BadLand: - case HousePlacementResult.BadStatic: - case HousePlacementResult.BadRegionHidden: - case HousePlacementResult.NoSurface: - { - from.SendLocalizedMessage( 1043287 ); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. - break; - } - case HousePlacementResult.BadRegion: - { - from.SendLocalizedMessage( 501265 ); // Housing cannot be created in this area. - break; - } - case HousePlacementResult.BadRegionTemp: - { - from.SendLocalizedMessage( 501270 ); //Lord British has decreed a 'no build' period, thus you cannot build this house at this time. - break; - } - case HousePlacementResult.BadRegionRaffle: - { - from.SendLocalizedMessage( 1150493 ); // You must have a deed for this plot of land in order to build here. - break; - } - case HousePlacementResult.InvalidCastleKeep: - { - from.SendLocalizedMessage( 1061122 ); // Castles and keeps cannot be created here. - break; - } - } - - return false; - } - - private static Hashtable m_Table; - - static HousePlacementEntry() - { - m_Table = new Hashtable(); - - FillTable( ClassicHouses ); - FillTable( TwoStoryFoundations ); - FillTable( ThreeStoryFoundations ); - } - - public static HousePlacementEntry Find( BaseHouse house ) - { - object obj = m_Table[house.GetType()]; - - if ( obj is HousePlacementEntry ) - { - return ((HousePlacementEntry)obj); - } - - if ( obj is ArrayList ) - { - ArrayList list = (ArrayList)obj; - - for ( int i = 0; i < list.Count; ++i ) - { - HousePlacementEntry e = (HousePlacementEntry)list[i]; - - if ( e.MultiID == house.ItemID ) - return e; - } - } - else if ( obj is Hashtable ) - { - Hashtable table = (Hashtable)obj; - - obj = table[house.ItemID]; - - if ( obj is HousePlacementEntry ) - return (HousePlacementEntry)obj; - } - - return null; - } - - private static void FillTable( HousePlacementEntry[] entries ) - { - for ( int i = 0; i < entries.Length; ++i ) - { - HousePlacementEntry e = entries[i]; - - object obj = m_Table[e.Type]; - - if ( obj == null ) - { - m_Table[e.Type] = e; - } - else if ( obj is HousePlacementEntry ) - { - ArrayList list = new ArrayList(); - - list.Add( obj ); - list.Add( e ); - - m_Table[e.Type] = list; - } - else if ( obj is ArrayList ) - { - ArrayList list = (ArrayList)obj; - - if ( list.Count == 8 ) - { - Hashtable table = new Hashtable(); - - for ( int j = 0; j < list.Count; ++j ) - table[((HousePlacementEntry)list[j]).MultiID] = list[j]; - - table[e.MultiID] = e; - - m_Table[e.Type] = table; - } - else - { - list.Add( e ); - } - } - else if ( obj is Hashtable ) - { - ((Hashtable)obj)[e.MultiID] = e; - } - } - } - - public static HousePlacementEntry[] ClassicHouses { get; } = - { - new HousePlacementEntry( typeof( SmallOldHouse ), 1011303, 425, 212, 489, 244, 10, 37000, 0, 4, 0, 0x0064 ), - new HousePlacementEntry( typeof( SmallOldHouse ), 1011304, 425, 212, 489, 244, 10, 37000, 0, 4, 0, 0x0066 ), - new HousePlacementEntry( typeof( SmallOldHouse ), 1011305, 425, 212, 489, 244, 10, 36750, 0, 4, 0, 0x0068 ), - new HousePlacementEntry( typeof( SmallOldHouse ), 1011306, 425, 212, 489, 244, 10, 35250, 0, 4, 0, 0x006A ), - new HousePlacementEntry( typeof( SmallOldHouse ), 1011307, 425, 212, 489, 244, 10, 36750, 0, 4, 0, 0x006C ), - new HousePlacementEntry( typeof( SmallOldHouse ), 1011308, 425, 212, 489, 244, 10, 36750, 0, 4, 0, 0x006E ), - new HousePlacementEntry( typeof( SmallShop ), 1011321, 425, 212, 489, 244, 10, 50500, -1, 4, 0, 0x00A0 ), - new HousePlacementEntry( typeof( SmallShop ), 1011322, 425, 212, 489, 244, 10, 52500, 0, 4, 0, 0x00A2 ), - new HousePlacementEntry( typeof( SmallTower ), 1011317, 580, 290, 667, 333, 14, 73500, 3, 4, 0, 0x0098 ), - new HousePlacementEntry( typeof( TwoStoryVilla ), 1011319, 1100, 550, 1265, 632, 24, 113750, 3, 6, 0, 0x009E ), - new HousePlacementEntry( typeof( SandStonePatio ), 1011320, 850, 425, 1265, 632, 24, 76500, -1, 4, 0, 0x009C ), - new HousePlacementEntry( typeof( LogCabin ), 1011318, 1100, 550, 1265, 632, 24, 81750, 1, 6, 0, 0x009A ), - new HousePlacementEntry( typeof( GuildHouse ), 1011309, 1370, 685, 1576, 788, 28, 131500, -1, 7, 0, 0x0074 ), - new HousePlacementEntry( typeof( TwoStoryHouse ), 1011310, 1370, 685, 1576, 788, 28, 162750, -3, 7, 0, 0x0076 ), - new HousePlacementEntry( typeof( TwoStoryHouse ), 1011311, 1370, 685, 1576, 788, 28, 162000, -3, 7, 0, 0x0078 ), - new HousePlacementEntry( typeof( LargePatioHouse ), 1011315, 1370, 685, 1576, 788, 28, 129250, -4, 7, 0, 0x008C ), - new HousePlacementEntry( typeof( LargeMarbleHouse ), 1011316, 1370, 685, 1576, 788, 28, 160500, -4, 7, 0, 0x0096 ), - new HousePlacementEntry( typeof( Tower ), 1011312, 2119, 1059, 2437, 1218, 42, 366500, 0, 7, 0, 0x007A ), - new HousePlacementEntry( typeof( Keep ), 1011313, 2625, 1312, 3019, 1509, 52, 572750, 0, 11, 0, 0x007C ), - new HousePlacementEntry( typeof( Castle ), 1011314, 4076, 2038, 4688, 2344, 78, 865250, 0, 16, 0, 0x007E ) - }; - - - public static HousePlacementEntry[] TwoStoryFoundations { get; } = - { - new HousePlacementEntry( typeof( HouseFoundation ), 1060241, 425, 212, 489, 244, 10, 30500, 0, 4, 0, 0x13EC ), // 7x7 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060242, 580, 290, 667, 333, 14, 34500, 0, 5, 0, 0x13ED ), // 7x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060243, 650, 325, 748, 374, 16, 38500, 0, 5, 0, 0x13EE ), // 7x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060244, 700, 350, 805, 402, 16, 42500, 0, 6, 0, 0x13EF ), // 7x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060245, 750, 375, 863, 431, 16, 46500, 0, 6, 0, 0x13F0 ), // 7x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060246, 800, 400, 920, 460, 18, 50500, 0, 7, 0, 0x13F1 ), // 7x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060253, 580, 290, 667, 333, 14, 34500, 0, 4, 0, 0x13F8 ), // 8x7 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060254, 650, 325, 748, 374, 16, 39000, 0, 5, 0, 0x13F9 ), // 8x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060255, 700, 350, 805, 402, 16, 43500, 0, 5, 0, 0x13FA ), // 8x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060256, 750, 375, 863, 431, 16, 48000, 0, 6, 0, 0x13FB ), // 8x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060257, 800, 400, 920, 460, 18, 52500, 0, 6, 0, 0x13FC ), // 8x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060258, 850, 425, 1265, 632, 24, 57000, 0, 7, 0, 0x13FD ), // 8x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060259, 1100, 550, 1265, 632, 24, 61500, 0, 7, 0, 0x13FE ), // 8x13 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060265, 650, 325, 748, 374, 16, 38500, 0, 4, 0, 0x1404 ), // 9x7 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060266, 700, 350, 805, 402, 16, 43500, 0, 5, 0, 0x1405 ), // 9x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060267, 750, 375, 863, 431, 16, 48500, 0, 5, 0, 0x1406 ), // 9x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060268, 800, 400, 920, 460, 18, 53500, 0, 6, 0, 0x1407 ), // 9x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060269, 850, 425, 1265, 632, 24, 58500, 0, 6, 0, 0x1408 ), // 9x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060270, 1100, 550, 1265, 632, 24, 63500, 0, 7, 0, 0x1409 ), // 9x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060271, 1100, 550, 1265, 632, 24, 68500, 0, 7, 0, 0x140A ), // 9x13 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060277, 700, 350, 805, 402, 16, 42500, 0, 4, 0, 0x1410 ), // 10x7 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060278, 750, 375, 863, 431, 16, 48000, 0, 5, 0, 0x1411 ), // 10x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060279, 800, 400, 920, 460, 18, 53500, 0, 5, 0, 0x1412 ), // 10x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060280, 850, 425, 1265, 632, 24, 59000, 0, 6, 0, 0x1413 ), // 10x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060281, 1100, 550, 1265, 632, 24, 64500, 0, 6, 0, 0x1414 ), // 10x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060282, 1100, 550, 1265, 632, 24, 70000, 0, 7, 0, 0x1415 ), // 10x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060283, 1150, 575, 1323, 661, 24, 75500, 0, 7, 0, 0x1416 ), // 10x13 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060289, 750, 375, 863, 431, 16, 46500, 0, 4, 0, 0x141C ), // 11x7 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060290, 800, 400, 920, 460, 18, 52500, 0, 5, 0, 0x141D ), // 11x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060291, 850, 425, 1265, 632, 24, 58500, 0, 5, 0, 0x141E ), // 11x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060292, 1100, 550, 1265, 632, 24, 64500, 0, 6, 0, 0x141F ), // 11x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060293, 1100, 550, 1265, 632, 24, 70500, 0, 6, 0, 0x1420 ), // 11x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060294, 1150, 575, 1323, 661, 24, 76500, 0, 7, 0, 0x1421 ), // 11x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060295, 1200, 600, 1380, 690, 26, 82500, 0, 7, 0, 0x1422 ), // 11x13 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060301, 800, 400, 920, 460, 18, 50500, 0, 4, 0, 0x1428 ), // 12x7 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060302, 850, 425, 1265, 632, 24, 57000, 0, 5, 0, 0x1429 ), // 12x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060303, 1100, 550, 1265, 632, 24, 63500, 0, 5, 0, 0x142A ), // 12x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060304, 1100, 550, 1265, 632, 24, 70000, 0, 6, 0, 0x142B ), // 12x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060305, 1150, 575, 1323, 661, 24, 76500, 0, 6, 0, 0x142C ), // 12x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060306, 1200, 600, 1380, 690, 26, 83000, 0, 7, 0, 0x142D ), // 12x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060307, 1250, 625, 1438, 719, 26, 89500, 0, 7, 0, 0x142E ), // 12x13 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060314, 1100, 550, 1265, 632, 24, 61500, 0, 5, 0, 0x1435 ), // 13x8 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060315, 1100, 550, 1265, 632, 24, 68500, 0, 5, 0, 0x1436 ), // 13x9 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060316, 1150, 575, 1323, 661, 24, 75500, 0, 6, 0, 0x1437 ), // 13x10 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060317, 1200, 600, 1380, 690, 26, 82500, 0, 6, 0, 0x1438 ), // 13x11 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060318, 1250, 625, 1438, 719, 26, 89500, 0, 7, 0, 0x1439 ), // 13x12 2-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060319, 1300, 650, 1495, 747, 28, 96500, 0, 7, 0, 0x143A ) // 13x13 2-Story Customizable House - }; - - - public static HousePlacementEntry[] ThreeStoryFoundations { get; } = - { - new HousePlacementEntry( typeof( HouseFoundation ), 1060272, 1150, 575, 1323, 661, 24, 73500, 0, 8, 0, 0x140B ), // 9x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060284, 1200, 600, 1380, 690, 26, 81000, 0, 8, 0, 0x1417 ), // 10x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060285, 1250, 625, 1438, 719, 26, 86500, 0, 8, 0, 0x1418 ), // 10x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060296, 1250, 625, 1438, 719, 26, 88500, 0, 8, 0, 0x1423 ), // 11x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060297, 1300, 650, 1495, 747, 28, 94500, 0, 8, 0, 0x1424 ), // 11x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060298, 1350, 675, 1553, 776, 28, 100500, 0, 9, 0, 0x1425 ), // 11x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060308, 1300, 650, 1495, 747, 28, 96000, 0, 8, 0, 0x142F ), // 12x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060309, 1350, 675, 1553, 776, 28, 102500, 0, 8, 0, 0x1430 ), // 12x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060310, 1370, 685, 1576, 788, 28, 109000, 0, 9, 0, 0x1431 ), // 12x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060311, 1370, 685, 1576, 788, 28, 115500, 0, 9, 0, 0x1432 ), // 12x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060320, 1350, 675, 1553, 776, 28, 103500, 0, 8, 0, 0x143B ), // 13x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060321, 1370, 685, 1576, 788, 28, 110500, 0, 8, 0, 0x143C ), // 13x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060322, 1370, 685, 1576, 788, 28, 117500, 0, 9, 0, 0x143D ), // 13x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060323, 2119, 1059, 2437, 1218, 42, 124500, 0, 9, 0, 0x143E ), // 13x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060324, 2119, 1059, 2437, 1218, 42, 131500, 0, 10, 0, 0x143F ), // 13x18 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060327, 1150, 575, 1323, 661, 24, 73500, 0, 5, 0, 0x1442 ), // 14x9 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060328, 1200, 600, 1380, 690, 26, 81000, 0, 6, 0, 0x1443 ), // 14x10 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060329, 1250, 625, 1438, 719, 26, 88500, 0, 6, 0, 0x1444 ), // 14x11 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060330, 1300, 650, 1495, 747, 28, 96000, 0, 7, 0, 0x1445 ), // 14x12 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060331, 1350, 675, 1553, 776, 28, 103500, 0, 7, 0, 0x1446 ), // 14x13 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060332, 1370, 685, 1576, 788, 28, 111000, 0, 8, 0, 0x1447 ), // 14x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060333, 1370, 685, 1576, 788, 28, 118500, 0, 8, 0, 0x1448 ), // 14x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060334, 2119, 1059, 2437, 1218, 42, 126000, 0, 9, 0, 0x1449 ), // 14x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060335, 2119, 1059, 2437, 1218, 42, 133500, 0, 9, 0, 0x144A ), // 14x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060336, 2119, 1059, 2437, 1218, 42, 141000, 0, 10, 0, 0x144B ), // 14x18 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060340, 1250, 625, 1438, 719, 26, 86500, 0, 6, 0, 0x144F ), // 15x10 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060341, 1300, 650, 1495, 747, 28, 94500, 0, 6, 0, 0x1450 ), // 15x11 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060342, 1350, 675, 1553, 776, 28, 102500, 0, 7, 0, 0x1451 ), // 15x12 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060343, 1370, 685, 1576, 788, 28, 110500, 0, 7, 0, 0x1452 ), // 15x13 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060344, 1370, 685, 1576, 788, 28, 118500, 0, 8, 0, 0x1453 ), // 15x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060345, 2119, 1059, 2437, 1218, 42, 126500, 0, 8, 0, 0x1454 ), // 15x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060346, 2119, 1059, 2437, 1218, 42, 134500, 0, 9, 0, 0x1455 ), // 15x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060347, 2119, 1059, 2437, 1218, 42, 142500, 0, 9, 0, 0x1456 ), // 15x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060348, 2119, 1059, 2437, 1218, 42, 150500, 0, 10, 0, 0x1457 ), // 15x18 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060353, 1350, 675, 1553, 776, 28, 100500, 0, 6, 0, 0x145C ), // 16x11 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060354, 1370, 685, 1576, 788, 28, 109000, 0, 7, 0, 0x145D ), // 16x12 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060355, 1370, 685, 1576, 788, 28, 117500, 0, 7, 0, 0x145E ), // 16x13 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060356, 2119, 1059, 2437, 1218, 42, 126000, 0, 8, 0, 0x145F ), // 16x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060357, 2119, 1059, 2437, 1218, 42, 134500, 0, 8, 0, 0x1460 ), // 16x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060358, 2119, 1059, 2437, 1218, 42, 143000, 0, 9, 0, 0x1461 ), // 16x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060359, 2119, 1059, 2437, 1218, 42, 151500, 0, 9, 0, 0x1462 ), // 16x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060360, 2119, 1059, 2437, 1218, 42, 160000, 0, 10, 0, 0x1463 ), // 16x18 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060366, 1370, 685, 1576, 788, 28, 115500, 0, 7, 0, 0x1469 ), // 17x12 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060367, 2119, 1059, 2437, 1218, 42, 124500, 0, 7, 0, 0x146A ), // 17x13 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060368, 2119, 1059, 2437, 1218, 42, 133500, 0, 8, 0, 0x146B ), // 17x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060369, 2119, 1059, 2437, 1218, 42, 142500, 0, 8, 0, 0x146C ), // 17x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060370, 2119, 1059, 2437, 1218, 42, 151500, 0, 9, 0, 0x146D ), // 17x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060371, 2119, 1059, 2437, 1218, 42, 160500, 0, 9, 0, 0x146E ), // 17x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060372, 2119, 1059, 2437, 1218, 42, 169500, 0, 10, 0, 0x146F ), // 17x18 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060379, 2119, 1059, 2437, 1218, 42, 131500, 0, 7, 0, 0x1476 ), // 18x13 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060380, 2119, 1059, 2437, 1218, 42, 141000, 0, 8, 0, 0x1477 ), // 18x14 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060381, 2119, 1059, 2437, 1218, 42, 150500, 0, 8, 0, 0x1478 ), // 18x15 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060382, 2119, 1059, 2437, 1218, 42, 160000, 0, 9, 0, 0x1479 ), // 18x16 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060383, 2119, 1059, 2437, 1218, 42, 169500, 0, 9, 0, 0x147A ), // 18x17 3-Story Customizable House - new HousePlacementEntry( typeof( HouseFoundation ), 1060384, 2119, 1059, 2437, 1218, 42, 179000, 0, 10, 0, 0x147B ) // 18x18 3-Story Customizable House - }; - } -} + public class HousePlacementTool : Item + { + [Constructible] + public HousePlacementTool() : base(0x14F6) + { + Weight = 3.0; + LootType = LootType.Blessed; + } + + public HousePlacementTool(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1060651; // a house placement tool + + public override void OnDoubleClick(Mobile from) + { + if (IsChildOf(from.Backpack)) + from.SendGump(new HousePlacementCategoryGump(from)); + else + from.SendLocalizedMessage(1042001); // That must be in your pack for you to use it. + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(0); // version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + if (Weight == 0.0) + Weight = 3.0; + } + } + + public class HousePlacementCategoryGump : Gump + { + private const int LabelColor = 0x7FFF; + private const int LabelColorDisabled = 0x4210; + private Mobile m_From; + + public HousePlacementCategoryGump(Mobile from) : base(50, 50) + { + m_From = from; + + from.CloseGump(typeof(HousePlacementCategoryGump)); + from.CloseGump(typeof(HousePlacementListGump)); + + AddPage(0); + + AddBackground(0, 0, 270, 145, 5054); + + AddImageTiled(10, 10, 250, 125, 2624); + AddAlphaRegion(10, 10, 250, 125); + + AddHtmlLocalized(10, 10, 250, 20, 1060239, LabelColor, false, false); //
HOUSE PLACEMENT TOOL
+ + AddButton(10, 110, 4017, 4019, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 110, 150, 20, 3000363, LabelColor, false, false); // Close + + AddButton(10, 40, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 40, 200, 20, 1060390, LabelColor, false, false); // Classic Houses + + AddButton(10, 60, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 60, 200, 20, 1060391, LabelColor, false, false); // 2-Story Customizable Houses + + AddButton(10, 80, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 80, 200, 20, 1060392, LabelColor, false, false); // 3-Story Customizable Houses + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_From.CheckAlive() || m_From.Backpack?.FindItemByType(typeof(HousePlacementTool)) == null) + return; + + switch (info.ButtonID) + { + case 1: // Classic Houses + { + m_From.SendGump(new HousePlacementListGump(m_From, HousePlacementEntry.ClassicHouses)); + break; + } + case 2: // 2-Story Customizable Houses + { + m_From.SendGump(new HousePlacementListGump(m_From, HousePlacementEntry.TwoStoryFoundations)); + break; + } + case 3: // 3-Story Customizable Houses + { + m_From.SendGump(new HousePlacementListGump(m_From, HousePlacementEntry.ThreeStoryFoundations)); + break; + } + } + } + } + + public class HousePlacementListGump : Gump + { + private const int LabelColor = 0x7FFF; + private const int LabelHue = 0x480; + private HousePlacementEntry[] m_Entries; + private Mobile m_From; + + public HousePlacementListGump(Mobile from, HousePlacementEntry[] entries) : base(50, 50) + { + m_From = from; + m_Entries = entries; + + from.CloseGump(typeof(HousePlacementCategoryGump)); + from.CloseGump(typeof(HousePlacementListGump)); + + AddPage(0); + + AddBackground(0, 0, 520, 420, 5054); + + AddImageTiled(10, 10, 500, 20, 2624); + AddAlphaRegion(10, 10, 500, 20); + + AddHtmlLocalized(10, 10, 500, 20, 1060239, LabelColor, false, false); //
HOUSE PLACEMENT TOOL
+ + AddImageTiled(10, 40, 500, 20, 2624); + AddAlphaRegion(10, 40, 500, 20); + + AddHtmlLocalized(50, 40, 225, 20, 1060235, LabelColor, false, false); // House Description + AddHtmlLocalized(275, 40, 75, 20, 1060236, LabelColor, false, false); // Storage + AddHtmlLocalized(350, 40, 75, 20, 1060237, LabelColor, false, false); // Lockdowns + AddHtmlLocalized(425, 40, 75, 20, 1060034, LabelColor, false, false); // Cost + + AddImageTiled(10, 70, 500, 280, 2624); + AddAlphaRegion(10, 70, 500, 280); + + AddImageTiled(10, 360, 500, 20, 2624); + AddAlphaRegion(10, 360, 500, 20); + + AddHtmlLocalized(10, 360, 250, 20, 1060645, LabelColor, false, false); // Bank Balance: + AddLabel(250, 360, LabelHue, Banker.GetBalance(from).ToString()); + + AddImageTiled(10, 390, 500, 20, 2624); + AddAlphaRegion(10, 390, 500, 20); + + AddButton(10, 390, 4017, 4019, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, 390, 100, 20, 3000363, LabelColor, false, false); // Close + + for (int i = 0; i < entries.Length; ++i) + { + int page = 1 + i / 14; + int index = i % 14; + + if (index == 0) + { + if (page > 1) + { + AddButton(450, 390, 4005, 4007, 0, GumpButtonType.Page, page); + AddHtmlLocalized(400, 390, 100, 20, 3000406, LabelColor, false, false); // Next + } + + AddPage(page); + + if (page > 1) + { + AddButton(200, 390, 4014, 4016, 0, GumpButtonType.Page, page - 1); + AddHtmlLocalized(250, 390, 100, 20, 3000405, LabelColor, false, false); // Previous + } + } + + HousePlacementEntry entry = entries[i]; + + int y = 70 + index * 20; + + AddButton(10, y, 4005, 4007, 1 + i, GumpButtonType.Reply, 0); + AddHtmlLocalized(50, y, 225, 20, entry.Description, LabelColor, false, false); + AddLabel(275, y, LabelHue, entry.Storage.ToString()); + AddLabel(350, y, LabelHue, entry.Lockdowns.ToString()); + AddLabel(425, y, LabelHue, entry.Cost.ToString()); + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (!m_From.CheckAlive() || m_From.Backpack?.FindItemByType(typeof(HousePlacementTool)) == null) + return; + + int index = info.ButtonID - 1; + + if (index >= 0 && index < m_Entries.Length) + { + if (m_From.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse(m_From)) + m_From.SendLocalizedMessage(501271); // You already own a house, you may not place another! + else + m_From.Target = new NewHousePlacementTarget(m_Entries, m_Entries[index]); + } + else + { + m_From.SendGump(new HousePlacementCategoryGump(m_From)); + } + } + } + + public class NewHousePlacementTarget : MultiTarget + { + private HousePlacementEntry[] m_Entries; + private HousePlacementEntry m_Entry; + + private bool m_Placed; + + public NewHousePlacementTarget(HousePlacementEntry[] entries, HousePlacementEntry entry) : base(entry.MultiID, + entry.Offset) + { + Range = 14; + + m_Entries = entries; + m_Entry = entry; + } + + protected override void OnTarget(Mobile from, object o) + { + if (!from.CheckAlive() || from.Backpack?.FindItemByType(typeof(HousePlacementTool)) == null) + return; + + IPoint3D ip = o as IPoint3D; + + if (ip != null) + { + if (ip is Item) + ip = ((Item)ip).GetWorldTop(); + + Point3D p = new Point3D(ip); + + Region reg = Region.Find(new Point3D(p), from.Map); + + if (from.AccessLevel >= AccessLevel.GameMaster || reg.AllowHousing(from, p)) + m_Placed = m_Entry.OnPlacement(from, p); + else if (reg.IsPartOf(typeof(TempNoHousingRegion))) + from.SendLocalizedMessage( + 501270); // Lord British has decreed a 'no build' period, thus you cannot build this house at this time. + else if (reg.IsPartOf(typeof(TreasureRegion)) || reg.IsPartOf(typeof(HouseRegion))) + from.SendLocalizedMessage( + 1043287); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. + else if (reg.IsPartOf(typeof(HouseRaffleRegion))) + from.SendLocalizedMessage(1150493); // You must have a deed for this plot of land in order to build here. + else + from.SendLocalizedMessage(501265); // Housing can not be created in this area. + } + } + + protected override void OnTargetFinish(Mobile from) + { + if (!from.CheckAlive() || from.Backpack?.FindItemByType(typeof(HousePlacementTool)) == null) + return; + + if (!m_Placed) + from.SendGump(new HousePlacementListGump(from, m_Entries)); + } + } + + public class HousePlacementEntry + { + private static Hashtable m_Table; + private int m_Lockdowns; + private int m_NewLockdowns; + private int m_NewStorage; + private int m_Storage; + + static HousePlacementEntry() + { + m_Table = new Hashtable(); + + FillTable(ClassicHouses); + FillTable(TwoStoryFoundations); + FillTable(ThreeStoryFoundations); + } + + public HousePlacementEntry(Type type, int description, int storage, int lockdowns, int newStorage, int newLockdowns, + int vendors, int cost, int xOffset, int yOffset, int zOffset, int multiID) + { + Type = type; + Description = description; + m_Storage = storage; + m_Lockdowns = lockdowns; + m_NewStorage = newStorage; + m_NewLockdowns = newLockdowns; + Vendors = vendors; + Cost = cost; + + Offset = new Point3D(xOffset, yOffset, zOffset); + + MultiID = multiID; + } + + public Type Type{ get; } + + public int Description{ get; } + + public int Storage => BaseHouse.NewVendorSystem ? m_NewStorage : m_Storage; + public int Lockdowns => BaseHouse.NewVendorSystem ? m_NewLockdowns : m_Lockdowns; + public int Vendors{ get; } + + public int Cost{ get; } + + public int MultiID{ get; } + + public Point3D Offset{ get; } + + public static HousePlacementEntry[] ClassicHouses{ get; } = + { + new HousePlacementEntry(typeof(SmallOldHouse), 1011303, 425, 212, 489, 244, 10, 37000, 0, 4, 0, 0x0064), + new HousePlacementEntry(typeof(SmallOldHouse), 1011304, 425, 212, 489, 244, 10, 37000, 0, 4, 0, 0x0066), + new HousePlacementEntry(typeof(SmallOldHouse), 1011305, 425, 212, 489, 244, 10, 36750, 0, 4, 0, 0x0068), + new HousePlacementEntry(typeof(SmallOldHouse), 1011306, 425, 212, 489, 244, 10, 35250, 0, 4, 0, 0x006A), + new HousePlacementEntry(typeof(SmallOldHouse), 1011307, 425, 212, 489, 244, 10, 36750, 0, 4, 0, 0x006C), + new HousePlacementEntry(typeof(SmallOldHouse), 1011308, 425, 212, 489, 244, 10, 36750, 0, 4, 0, 0x006E), + new HousePlacementEntry(typeof(SmallShop), 1011321, 425, 212, 489, 244, 10, 50500, -1, 4, 0, 0x00A0), + new HousePlacementEntry(typeof(SmallShop), 1011322, 425, 212, 489, 244, 10, 52500, 0, 4, 0, 0x00A2), + new HousePlacementEntry(typeof(SmallTower), 1011317, 580, 290, 667, 333, 14, 73500, 3, 4, 0, 0x0098), + new HousePlacementEntry(typeof(TwoStoryVilla), 1011319, 1100, 550, 1265, 632, 24, 113750, 3, 6, 0, 0x009E), + new HousePlacementEntry(typeof(SandStonePatio), 1011320, 850, 425, 1265, 632, 24, 76500, -1, 4, 0, 0x009C), + new HousePlacementEntry(typeof(LogCabin), 1011318, 1100, 550, 1265, 632, 24, 81750, 1, 6, 0, 0x009A), + new HousePlacementEntry(typeof(GuildHouse), 1011309, 1370, 685, 1576, 788, 28, 131500, -1, 7, 0, 0x0074), + new HousePlacementEntry(typeof(TwoStoryHouse), 1011310, 1370, 685, 1576, 788, 28, 162750, -3, 7, 0, 0x0076), + new HousePlacementEntry(typeof(TwoStoryHouse), 1011311, 1370, 685, 1576, 788, 28, 162000, -3, 7, 0, 0x0078), + new HousePlacementEntry(typeof(LargePatioHouse), 1011315, 1370, 685, 1576, 788, 28, 129250, -4, 7, 0, 0x008C), + new HousePlacementEntry(typeof(LargeMarbleHouse), 1011316, 1370, 685, 1576, 788, 28, 160500, -4, 7, 0, 0x0096), + new HousePlacementEntry(typeof(Tower), 1011312, 2119, 1059, 2437, 1218, 42, 366500, 0, 7, 0, 0x007A), + new HousePlacementEntry(typeof(Keep), 1011313, 2625, 1312, 3019, 1509, 52, 572750, 0, 11, 0, 0x007C), + new HousePlacementEntry(typeof(Castle), 1011314, 4076, 2038, 4688, 2344, 78, 865250, 0, 16, 0, 0x007E) + }; + + + public static HousePlacementEntry[] TwoStoryFoundations{ get; } = + { + new HousePlacementEntry(typeof(HouseFoundation), 1060241, 425, 212, 489, 244, 10, 30500, 0, 4, 0, + 0x13EC), // 7x7 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060242, 580, 290, 667, 333, 14, 34500, 0, 5, 0, + 0x13ED), // 7x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060243, 650, 325, 748, 374, 16, 38500, 0, 5, 0, + 0x13EE), // 7x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060244, 700, 350, 805, 402, 16, 42500, 0, 6, 0, + 0x13EF), // 7x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060245, 750, 375, 863, 431, 16, 46500, 0, 6, 0, + 0x13F0), // 7x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060246, 800, 400, 920, 460, 18, 50500, 0, 7, 0, + 0x13F1), // 7x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060253, 580, 290, 667, 333, 14, 34500, 0, 4, 0, + 0x13F8), // 8x7 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060254, 650, 325, 748, 374, 16, 39000, 0, 5, 0, + 0x13F9), // 8x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060255, 700, 350, 805, 402, 16, 43500, 0, 5, 0, + 0x13FA), // 8x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060256, 750, 375, 863, 431, 16, 48000, 0, 6, 0, + 0x13FB), // 8x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060257, 800, 400, 920, 460, 18, 52500, 0, 6, 0, + 0x13FC), // 8x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060258, 850, 425, 1265, 632, 24, 57000, 0, 7, 0, + 0x13FD), // 8x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060259, 1100, 550, 1265, 632, 24, 61500, 0, 7, 0, + 0x13FE), // 8x13 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060265, 650, 325, 748, 374, 16, 38500, 0, 4, 0, + 0x1404), // 9x7 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060266, 700, 350, 805, 402, 16, 43500, 0, 5, 0, + 0x1405), // 9x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060267, 750, 375, 863, 431, 16, 48500, 0, 5, 0, + 0x1406), // 9x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060268, 800, 400, 920, 460, 18, 53500, 0, 6, 0, + 0x1407), // 9x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060269, 850, 425, 1265, 632, 24, 58500, 0, 6, 0, + 0x1408), // 9x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060270, 1100, 550, 1265, 632, 24, 63500, 0, 7, 0, + 0x1409), // 9x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060271, 1100, 550, 1265, 632, 24, 68500, 0, 7, 0, + 0x140A), // 9x13 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060277, 700, 350, 805, 402, 16, 42500, 0, 4, 0, + 0x1410), // 10x7 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060278, 750, 375, 863, 431, 16, 48000, 0, 5, 0, + 0x1411), // 10x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060279, 800, 400, 920, 460, 18, 53500, 0, 5, 0, + 0x1412), // 10x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060280, 850, 425, 1265, 632, 24, 59000, 0, 6, 0, + 0x1413), // 10x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060281, 1100, 550, 1265, 632, 24, 64500, 0, 6, 0, + 0x1414), // 10x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060282, 1100, 550, 1265, 632, 24, 70000, 0, 7, 0, + 0x1415), // 10x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060283, 1150, 575, 1323, 661, 24, 75500, 0, 7, 0, + 0x1416), // 10x13 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060289, 750, 375, 863, 431, 16, 46500, 0, 4, 0, + 0x141C), // 11x7 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060290, 800, 400, 920, 460, 18, 52500, 0, 5, 0, + 0x141D), // 11x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060291, 850, 425, 1265, 632, 24, 58500, 0, 5, 0, + 0x141E), // 11x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060292, 1100, 550, 1265, 632, 24, 64500, 0, 6, 0, + 0x141F), // 11x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060293, 1100, 550, 1265, 632, 24, 70500, 0, 6, 0, + 0x1420), // 11x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060294, 1150, 575, 1323, 661, 24, 76500, 0, 7, 0, + 0x1421), // 11x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060295, 1200, 600, 1380, 690, 26, 82500, 0, 7, 0, + 0x1422), // 11x13 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060301, 800, 400, 920, 460, 18, 50500, 0, 4, 0, + 0x1428), // 12x7 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060302, 850, 425, 1265, 632, 24, 57000, 0, 5, 0, + 0x1429), // 12x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060303, 1100, 550, 1265, 632, 24, 63500, 0, 5, 0, + 0x142A), // 12x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060304, 1100, 550, 1265, 632, 24, 70000, 0, 6, 0, + 0x142B), // 12x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060305, 1150, 575, 1323, 661, 24, 76500, 0, 6, 0, + 0x142C), // 12x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060306, 1200, 600, 1380, 690, 26, 83000, 0, 7, 0, + 0x142D), // 12x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060307, 1250, 625, 1438, 719, 26, 89500, 0, 7, 0, + 0x142E), // 12x13 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060314, 1100, 550, 1265, 632, 24, 61500, 0, 5, 0, + 0x1435), // 13x8 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060315, 1100, 550, 1265, 632, 24, 68500, 0, 5, 0, + 0x1436), // 13x9 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060316, 1150, 575, 1323, 661, 24, 75500, 0, 6, 0, + 0x1437), // 13x10 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060317, 1200, 600, 1380, 690, 26, 82500, 0, 6, 0, + 0x1438), // 13x11 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060318, 1250, 625, 1438, 719, 26, 89500, 0, 7, 0, + 0x1439), // 13x12 2-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060319, 1300, 650, 1495, 747, 28, 96500, 0, 7, 0, + 0x143A) // 13x13 2-Story Customizable House + }; + + + public static HousePlacementEntry[] ThreeStoryFoundations{ get; } = + { + new HousePlacementEntry(typeof(HouseFoundation), 1060272, 1150, 575, 1323, 661, 24, 73500, 0, 8, 0, + 0x140B), // 9x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060284, 1200, 600, 1380, 690, 26, 81000, 0, 8, 0, + 0x1417), // 10x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060285, 1250, 625, 1438, 719, 26, 86500, 0, 8, 0, + 0x1418), // 10x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060296, 1250, 625, 1438, 719, 26, 88500, 0, 8, 0, + 0x1423), // 11x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060297, 1300, 650, 1495, 747, 28, 94500, 0, 8, 0, + 0x1424), // 11x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060298, 1350, 675, 1553, 776, 28, 100500, 0, 9, 0, + 0x1425), // 11x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060308, 1300, 650, 1495, 747, 28, 96000, 0, 8, 0, + 0x142F), // 12x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060309, 1350, 675, 1553, 776, 28, 102500, 0, 8, 0, + 0x1430), // 12x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060310, 1370, 685, 1576, 788, 28, 109000, 0, 9, 0, + 0x1431), // 12x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060311, 1370, 685, 1576, 788, 28, 115500, 0, 9, 0, + 0x1432), // 12x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060320, 1350, 675, 1553, 776, 28, 103500, 0, 8, 0, + 0x143B), // 13x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060321, 1370, 685, 1576, 788, 28, 110500, 0, 8, 0, + 0x143C), // 13x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060322, 1370, 685, 1576, 788, 28, 117500, 0, 9, 0, + 0x143D), // 13x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060323, 2119, 1059, 2437, 1218, 42, 124500, 0, 9, 0, + 0x143E), // 13x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060324, 2119, 1059, 2437, 1218, 42, 131500, 0, 10, 0, + 0x143F), // 13x18 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060327, 1150, 575, 1323, 661, 24, 73500, 0, 5, 0, + 0x1442), // 14x9 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060328, 1200, 600, 1380, 690, 26, 81000, 0, 6, 0, + 0x1443), // 14x10 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060329, 1250, 625, 1438, 719, 26, 88500, 0, 6, 0, + 0x1444), // 14x11 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060330, 1300, 650, 1495, 747, 28, 96000, 0, 7, 0, + 0x1445), // 14x12 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060331, 1350, 675, 1553, 776, 28, 103500, 0, 7, 0, + 0x1446), // 14x13 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060332, 1370, 685, 1576, 788, 28, 111000, 0, 8, 0, + 0x1447), // 14x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060333, 1370, 685, 1576, 788, 28, 118500, 0, 8, 0, + 0x1448), // 14x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060334, 2119, 1059, 2437, 1218, 42, 126000, 0, 9, 0, + 0x1449), // 14x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060335, 2119, 1059, 2437, 1218, 42, 133500, 0, 9, 0, + 0x144A), // 14x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060336, 2119, 1059, 2437, 1218, 42, 141000, 0, 10, 0, + 0x144B), // 14x18 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060340, 1250, 625, 1438, 719, 26, 86500, 0, 6, 0, + 0x144F), // 15x10 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060341, 1300, 650, 1495, 747, 28, 94500, 0, 6, 0, + 0x1450), // 15x11 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060342, 1350, 675, 1553, 776, 28, 102500, 0, 7, 0, + 0x1451), // 15x12 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060343, 1370, 685, 1576, 788, 28, 110500, 0, 7, 0, + 0x1452), // 15x13 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060344, 1370, 685, 1576, 788, 28, 118500, 0, 8, 0, + 0x1453), // 15x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060345, 2119, 1059, 2437, 1218, 42, 126500, 0, 8, 0, + 0x1454), // 15x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060346, 2119, 1059, 2437, 1218, 42, 134500, 0, 9, 0, + 0x1455), // 15x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060347, 2119, 1059, 2437, 1218, 42, 142500, 0, 9, 0, + 0x1456), // 15x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060348, 2119, 1059, 2437, 1218, 42, 150500, 0, 10, 0, + 0x1457), // 15x18 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060353, 1350, 675, 1553, 776, 28, 100500, 0, 6, 0, + 0x145C), // 16x11 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060354, 1370, 685, 1576, 788, 28, 109000, 0, 7, 0, + 0x145D), // 16x12 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060355, 1370, 685, 1576, 788, 28, 117500, 0, 7, 0, + 0x145E), // 16x13 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060356, 2119, 1059, 2437, 1218, 42, 126000, 0, 8, 0, + 0x145F), // 16x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060357, 2119, 1059, 2437, 1218, 42, 134500, 0, 8, 0, + 0x1460), // 16x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060358, 2119, 1059, 2437, 1218, 42, 143000, 0, 9, 0, + 0x1461), // 16x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060359, 2119, 1059, 2437, 1218, 42, 151500, 0, 9, 0, + 0x1462), // 16x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060360, 2119, 1059, 2437, 1218, 42, 160000, 0, 10, 0, + 0x1463), // 16x18 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060366, 1370, 685, 1576, 788, 28, 115500, 0, 7, 0, + 0x1469), // 17x12 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060367, 2119, 1059, 2437, 1218, 42, 124500, 0, 7, 0, + 0x146A), // 17x13 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060368, 2119, 1059, 2437, 1218, 42, 133500, 0, 8, 0, + 0x146B), // 17x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060369, 2119, 1059, 2437, 1218, 42, 142500, 0, 8, 0, + 0x146C), // 17x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060370, 2119, 1059, 2437, 1218, 42, 151500, 0, 9, 0, + 0x146D), // 17x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060371, 2119, 1059, 2437, 1218, 42, 160500, 0, 9, 0, + 0x146E), // 17x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060372, 2119, 1059, 2437, 1218, 42, 169500, 0, 10, 0, + 0x146F), // 17x18 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060379, 2119, 1059, 2437, 1218, 42, 131500, 0, 7, 0, + 0x1476), // 18x13 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060380, 2119, 1059, 2437, 1218, 42, 141000, 0, 8, 0, + 0x1477), // 18x14 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060381, 2119, 1059, 2437, 1218, 42, 150500, 0, 8, 0, + 0x1478), // 18x15 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060382, 2119, 1059, 2437, 1218, 42, 160000, 0, 9, 0, + 0x1479), // 18x16 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060383, 2119, 1059, 2437, 1218, 42, 169500, 0, 9, 0, + 0x147A), // 18x17 3-Story Customizable House + new HousePlacementEntry(typeof(HouseFoundation), 1060384, 2119, 1059, 2437, 1218, 42, 179000, 0, 10, 0, + 0x147B) // 18x18 3-Story Customizable House + }; + + public BaseHouse ConstructHouse(Mobile from) + { + try + { + object[] args; + + if (Type == typeof(HouseFoundation)) + args = new object[4] { from, MultiID, m_Storage, m_Lockdowns }; + else if (Type == typeof(SmallOldHouse) || Type == typeof(SmallShop) || Type == typeof(TwoStoryHouse)) + args = new object[2] { from, MultiID }; + else + args = new object[1] { from }; + + return Activator.CreateInstance(Type, args) as BaseHouse; + } + catch + { + } + + return null; + } + + public void PlacementWarning_Callback(Mobile from, bool okay, object state) + { + if (!from.CheckAlive() || from.Backpack?.FindItemByType(typeof(HousePlacementTool)) == null) + return; + + PreviewHouse prevHouse = (PreviewHouse)state; + + if (!okay) + { + prevHouse.Delete(); + return; + } + + if (prevHouse.Deleted) + { + /* Too much time has passed and the test house you created has been deleted. + * Please try again! + */ + from.SendGump(new NoticeGump(1060637, 30720, 1060647, 32512, 320, 180, null, null)); + + return; + } + + Point3D center = prevHouse.Location; + Map map = prevHouse.Map; + + prevHouse.Delete(); + + ArrayList toMove; + //Point3D center = new Point3D( p.X - m_Offset.X, p.Y - m_Offset.Y, p.Z - m_Offset.Z ); + HousePlacementResult res = HousePlacement.Check(from, MultiID, center, out toMove); + + switch (res) + { + case HousePlacementResult.Valid: + { + if (from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse(from)) + { + from.SendLocalizedMessage(501271); // You already own a house, you may not place another! + } + else + { + BaseHouse house = ConstructHouse(from); + + if (house == null) + return; + + house.Price = Cost; + + if (from.AccessLevel >= AccessLevel.GameMaster) + { + from.SendMessage("{0} gold would have been withdrawn from your bank if you were not a GM.", + Cost.ToString()); + } + else + { + if (Banker.Withdraw(from, Cost)) + { + from.SendLocalizedMessage(1060398, + Cost.ToString()); // ~1_AMOUNT~ gold has been withdrawn from your bank box. + } + else + { + house.RemoveKeys(from); + house.Delete(); + from.SendLocalizedMessage( + 1060646); // You do not have the funds available in your bank box to purchase this house. Try placing a smaller house, or adding gold or checks to your bank box. + return; + } + } + + house.MoveToWorld(center, from.Map); + + for (int i = 0; i < toMove.Count; ++i) + { + object o = toMove[i]; + + if (o is Mobile) + ((Mobile)o).Location = house.BanLocation; + else if (o is Item) + ((Item)o).Location = house.BanLocation; + } + } + + break; + } + case HousePlacementResult.BadItem: + case HousePlacementResult.BadLand: + case HousePlacementResult.BadStatic: + case HousePlacementResult.BadRegionHidden: + case HousePlacementResult.NoSurface: + { + from.SendLocalizedMessage( + 1043287); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. + break; + } + case HousePlacementResult.BadRegion: + { + from.SendLocalizedMessage(501265); // Housing cannot be created in this area. + break; + } + case HousePlacementResult.BadRegionTemp: + { + from.SendLocalizedMessage( + 501270); // Lord British has decreed a 'no build' period, thus you cannot build this house at this time. + break; + } + case HousePlacementResult.BadRegionRaffle: + { + from.SendLocalizedMessage(1150493); // You must have a deed for this plot of land in order to build here. + break; + } + case HousePlacementResult.InvalidCastleKeep: + { + from.SendLocalizedMessage(1061122); // Castles and keeps cannot be created here. + break; + } + } + } + + public bool OnPlacement(Mobile from, Point3D p) + { + if (!from.CheckAlive() || from.Backpack?.FindItemByType(typeof(HousePlacementTool)) == null) + return false; + + ArrayList toMove; + Point3D center = new Point3D(p.X - Offset.X, p.Y - Offset.Y, p.Z - Offset.Z); + HousePlacementResult res = HousePlacement.Check(from, MultiID, center, out toMove); + + switch (res) + { + case HousePlacementResult.Valid: + { + if (from.AccessLevel < AccessLevel.GameMaster && BaseHouse.HasAccountHouse(from)) + { + from.SendLocalizedMessage(501271); // You already own a house, you may not place another! + } + else + { + from.SendLocalizedMessage(1011576); // This is a valid location. + + PreviewHouse prev = new PreviewHouse(MultiID); + + MultiComponentList mcl = prev.Components; + + Point3D banLoc = new Point3D(center.X + mcl.Min.X, center.Y + mcl.Max.Y + 1, center.Z); + + for (int i = 0; i < mcl.List.Length; ++i) + { + MultiTileEntry entry = mcl.List[i]; + + int itemID = entry.m_ItemID; + + if (itemID >= 0xBA3 && itemID <= 0xC0E) + { + banLoc = new Point3D(center.X + entry.m_OffsetX, center.Y + entry.m_OffsetY, center.Z); + break; + } + } + + for (int i = 0; i < toMove.Count; ++i) + { + object o = toMove[i]; + + if (o is Mobile) + ((Mobile)o).Location = banLoc; + else if (o is Item) + ((Item)o).Location = banLoc; + } + + prev.MoveToWorld(center, from.Map); + + /* You are about to place a new house. + * Placing this house will condemn any and all of your other houses that you may have. + * All of your houses on all shards will be affected. + * + * In addition, you will not be able to place another house or have one transferred to you for one (1) real-life week. + * + * Once you accept these terms, these effects cannot be reversed. + * Re-deeding or transferring your new house will not uncondemn your other house(s) nor will the one week timer be removed. + * + * If you are absolutely certain you wish to proceed, click the button next to OKAY below. + * If you do not wish to trade for this house, click CANCEL. + */ + from.SendGump(new WarningGump(1060635, 30720, 1049583, 32512, 420, 280, PlacementWarning_Callback, + prev)); + + return true; + } + + break; + } + case HousePlacementResult.BadItem: + case HousePlacementResult.BadLand: + case HousePlacementResult.BadStatic: + case HousePlacementResult.BadRegionHidden: + case HousePlacementResult.NoSurface: + { + from.SendLocalizedMessage( + 1043287); // The house could not be created here. Either something is blocking the house, or the house would not be on valid terrain. + break; + } + case HousePlacementResult.BadRegion: + { + from.SendLocalizedMessage(501265); // Housing cannot be created in this area. + break; + } + case HousePlacementResult.BadRegionTemp: + { + from.SendLocalizedMessage( + 501270); //Lord British has decreed a 'no build' period, thus you cannot build this house at this time. + break; + } + case HousePlacementResult.BadRegionRaffle: + { + from.SendLocalizedMessage(1150493); // You must have a deed for this plot of land in order to build here. + break; + } + case HousePlacementResult.InvalidCastleKeep: + { + from.SendLocalizedMessage(1061122); // Castles and keeps cannot be created here. + break; + } + } + + return false; + } + + public static HousePlacementEntry Find(BaseHouse house) + { + object obj = m_Table[house.GetType()]; + + if (obj is HousePlacementEntry) return (HousePlacementEntry)obj; + + if (obj is ArrayList) + { + ArrayList list = (ArrayList)obj; + + for (int i = 0; i < list.Count; ++i) + { + HousePlacementEntry e = (HousePlacementEntry)list[i]; + + if (e.MultiID == house.ItemID) + return e; + } + } + else if (obj is Hashtable) + { + Hashtable table = (Hashtable)obj; + + obj = table[house.ItemID]; + + if (obj is HousePlacementEntry) + return (HousePlacementEntry)obj; + } + + return null; + } + + private static void FillTable(HousePlacementEntry[] entries) + { + for (int i = 0; i < entries.Length; ++i) + { + HousePlacementEntry e = entries[i]; + + object obj = m_Table[e.Type]; + + if (obj == null) + { + m_Table[e.Type] = e; + } + else if (obj is HousePlacementEntry) + { + ArrayList list = new ArrayList(); + + list.Add(obj); + list.Add(e); + + m_Table[e.Type] = list; + } + else if (obj is ArrayList) + { + ArrayList list = (ArrayList)obj; + + if (list.Count == 8) + { + Hashtable table = new Hashtable(); + + for (int j = 0; j < list.Count; ++j) + table[((HousePlacementEntry)list[j]).MultiID] = list[j]; + + table[e.MultiID] = e; + + m_Table[e.Type] = table; + } + else + { + list.Add(e); + } + } + else if (obj is Hashtable) + { + ((Hashtable)obj)[e.MultiID] = e; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/HouseSign.cs b/Scripts/Multis/HouseSign.cs index 291074c06..084ac5c8e 100644 --- a/Scripts/Multis/HouseSign.cs +++ b/Scripts/Multis/HouseSign.cs @@ -1,283 +1,294 @@ using System; using System.Collections.Generic; -using Server.Gumps; using Server.ContextMenus; +using Server.Gumps; namespace Server.Multis { - public class HouseSign : Item - { - public HouseSign( BaseHouse owner ) : base( 0xBD2 ) - { - Owner = owner; - OriginalOwner = Owner.Owner; - Movable = false; - } + public class HouseSign : Item + { + public HouseSign(BaseHouse owner) : base(0xBD2) + { + Owner = owner; + OriginalOwner = Owner.Owner; + Movable = false; + } - public HouseSign( Serial serial ) : base( serial ) - { - } + public HouseSign(Serial serial) : base(serial) + { + } - public string GetName() - { - if ( Name == null ) - return "An Unnamed House"; + public BaseHouse Owner{ get; private set; } - return Name; - } + [CommandProperty(AccessLevel.GameMaster)] + public bool RestrictDecay + { + get => Owner != null && Owner.RestrictDecay; + set + { + if (Owner != null) Owner.RestrictDecay = value; + } + } - public BaseHouse Owner { get; private set; } + [CommandProperty(AccessLevel.GameMaster)] + public Mobile OriginalOwner{ get; private set; } - [CommandProperty( AccessLevel.GameMaster )] - public bool RestrictDecay - { - get => ( Owner != null && Owner.RestrictDecay ); - set{ if ( Owner != null ) Owner.RestrictDecay = value; } - } + public override bool ForceShowProperties => ObjectPropertyList.Enabled; - [CommandProperty( AccessLevel.GameMaster )] - public Mobile OriginalOwner { get; private set; } + public bool GettingProperties{ get; private set; } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public string GetName() + { + if (Name == null) + return "An Unnamed House"; - if ( Owner != null && !Owner.Deleted ) - Owner.Delete(); - } + return Name; + } - public override void AddNameProperty(ObjectPropertyList list) - { - list.Add( 1061638 ); // A House Sign - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public override bool ForceShowProperties => ObjectPropertyList.Enabled; + if (Owner != null && !Owner.Deleted) + Owner.Delete(); + } - public bool GettingProperties { get; private set; } + public override void AddNameProperty(ObjectPropertyList list) + { + list.Add(1061638); // A House Sign + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - list.Add( 1061639, Utility.FixHtml( GetName() ) ); // Name: ~1_NAME~ - list.Add( 1061640, (Owner?.Owner == null) ? "nobody" : Owner.Owner.Name ); // Owner: ~1_OWNER~ + list.Add(1061639, Utility.FixHtml(GetName())); // Name: ~1_NAME~ + list.Add(1061640, Owner?.Owner == null ? "nobody" : Owner.Owner.Name); // Owner: ~1_OWNER~ - if ( Owner != null ) - { - list.Add( Owner.Public ? 1061641 : 1061642 ); // This House is Open to the Public : This is a Private Home + if (Owner != null) + { + list.Add(Owner.Public ? 1061641 : 1061642); // This House is Open to the Public : This is a Private Home - GettingProperties = true; - DecayLevel level = Owner.DecayLevel; - GettingProperties = false; + GettingProperties = true; + DecayLevel level = Owner.DecayLevel; + GettingProperties = false; - if ( level == DecayLevel.DemolitionPending ) - { - list.Add( 1062497 ); // Demolition Pending - } - else if ( level != DecayLevel.Ageless ) - { - if ( level == DecayLevel.Collapsed ) - level = DecayLevel.IDOC; + if (level == DecayLevel.DemolitionPending) + { + list.Add(1062497); // Demolition Pending + } + else if (level != DecayLevel.Ageless) + { + if (level == DecayLevel.Collapsed) + level = DecayLevel.IDOC; - list.Add( 1062028, $"#{1043009 + (int) level}"); // Condition: This structure is ... - } - } - } + list.Add(1062028, $"#{1043009 + (int)level}"); // Condition: This structure is ... + } + } + } - public override void OnSingleClick( Mobile from ) - { - if ( Owner != null && BaseHouse.DecayEnabled && Owner.DecayPeriod != TimeSpan.Zero ) - { - string message; + public override void OnSingleClick(Mobile from) + { + if (Owner != null && BaseHouse.DecayEnabled && Owner.DecayPeriod != TimeSpan.Zero) + { + string message; - switch ( Owner.DecayLevel ) - { - case DecayLevel.Ageless: message = "ageless"; break; - case DecayLevel.Fairly: message = "fairly worn"; break; - case DecayLevel.Greatly: message = "greatly worn"; break; - case DecayLevel.LikeNew: message = "like new"; break; - case DecayLevel.Slightly: message = "slightly worn"; break; - case DecayLevel.Somewhat: message = "somewhat worn"; break; - default: message = "in danger of collapsing"; break; - } + switch (Owner.DecayLevel) + { + case DecayLevel.Ageless: + message = "ageless"; + break; + case DecayLevel.Fairly: + message = "fairly worn"; + break; + case DecayLevel.Greatly: + message = "greatly worn"; + break; + case DecayLevel.LikeNew: + message = "like new"; + break; + case DecayLevel.Slightly: + message = "slightly worn"; + break; + case DecayLevel.Somewhat: + message = "somewhat worn"; + break; + default: + message = "in danger of collapsing"; + break; + } - LabelTo( from, "This house is {0}.", message ); - } + LabelTo(from, "This house is {0}.", message); + } - base.OnSingleClick( from ); - } + base.OnSingleClick(from); + } - public void ShowSign( Mobile m ) - { - if ( Owner != null ) - { - if ( Owner.IsFriend( m ) && m.AccessLevel < AccessLevel.GameMaster ) - { - #region Mondain's Legacy - if ( ( Core.ML && Owner.IsOwner( m ) ) || !Core.ML ) - Owner.RefreshDecay(); - #endregion - if ( !Core.AOS ) - m.SendLocalizedMessage( 501293 ); // Welcome back to the house, friend! - } + public void ShowSign(Mobile m) + { + if (Owner != null) + { + if (Owner.IsFriend(m) && m.AccessLevel < AccessLevel.GameMaster) + { + #region Mondain's Legacy - if ( Owner.IsAosRules ) - m.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Information, m, Owner ) ); - else - m.SendGump( new HouseGump( m, Owner ) ); - } - } + if (Core.ML && Owner.IsOwner(m) || !Core.ML) + Owner.RefreshDecay(); - public void ClaimGump_Callback( Mobile from, bool okay, object state ) - { - if ( okay && Owner != null && Owner.Owner == null && Owner.DecayLevel != DecayLevel.DemolitionPending ) - { - bool canClaim = false; + #endregion - if ( Owner.CoOwners == null || Owner.CoOwners.Count == 0 ) - canClaim = Owner.IsFriend( from ); - else - canClaim = Owner.IsCoOwner( from ); + if (!Core.AOS) + m.SendLocalizedMessage(501293); // Welcome back to the house, friend! + } - if ( canClaim && !BaseHouse.HasAccountHouse( from ) ) - { - Owner.Owner = from; - Owner.LastTraded = DateTime.UtcNow; - } - } + if (Owner.IsAosRules) + m.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Information, m, Owner)); + else + m.SendGump(new HouseGump(m, Owner)); + } + } - ShowSign( from ); - } + public void ClaimGump_Callback(Mobile from, bool okay, object state) + { + if (okay && Owner != null && Owner.Owner == null && Owner.DecayLevel != DecayLevel.DemolitionPending) + { + bool canClaim = false; - public override void OnDoubleClick( Mobile m ) - { - if ( Owner == null ) - return; + if (Owner.CoOwners == null || Owner.CoOwners.Count == 0) + canClaim = Owner.IsFriend(from); + else + canClaim = Owner.IsCoOwner(from); - if ( m.AccessLevel < AccessLevel.GameMaster && Owner.Owner == null && Owner.DecayLevel != DecayLevel.DemolitionPending ) - { - bool canClaim = false; + if (canClaim && !BaseHouse.HasAccountHouse(from)) + { + Owner.Owner = from; + Owner.LastTraded = DateTime.UtcNow; + } + } - if ( Owner.CoOwners == null || Owner.CoOwners.Count == 0 ) - canClaim = Owner.IsFriend( m ); - else - canClaim = Owner.IsCoOwner( m ); + ShowSign(from); + } - if ( canClaim && !BaseHouse.HasAccountHouse( m ) ) - { - /* You do not currently own any house on any shard with this account, - * and this house currently does not have an owner. If you wish, you - * may choose to claim this house and become its rightful owner. If - * you do this, it will become your Primary house and automatically - * refresh. If you claim this house, you will be unable to place - * another house or have another house transferred to you for the - * next 7 days. Do you wish to claim this house? - */ - m.SendGump( new WarningGump( 501036, 32512, 1049719, 32512, 420, 280, ClaimGump_Callback, null ) ); - } - } + public override void OnDoubleClick(Mobile m) + { + if (Owner == null) + return; - ShowSign( m ); - } + if (m.AccessLevel < AccessLevel.GameMaster && Owner.Owner == null && + Owner.DecayLevel != DecayLevel.DemolitionPending) + { + bool canClaim = false; - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); + if (Owner.CoOwners == null || Owner.CoOwners.Count == 0) + canClaim = Owner.IsFriend(m); + else + canClaim = Owner.IsCoOwner(m); - if ( BaseHouse.NewVendorSystem && from.Alive && Owner != null && Owner.IsAosRules ) - { - if ( Owner.AreThereAvailableVendorsFor( from ) ) - list.Add( new VendorsEntry( this ) ); + if (canClaim && !BaseHouse.HasAccountHouse(m)) + m.SendGump(new WarningGump(501036, 32512, 1049719, 32512, 420, 280, ClaimGump_Callback, null)); + } - if ( Owner.VendorInventories.Count > 0 ) - list.Add( new ReclaimVendorInventoryEntry( this ) ); - } - } + ShowSign(m); + } - private class VendorsEntry : ContextMenuEntry - { - private HouseSign m_Sign; + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); - public VendorsEntry( HouseSign sign ) : base( 6211 ) - { - m_Sign = sign; - } + if (BaseHouse.NewVendorSystem && from.Alive && Owner != null && Owner.IsAosRules) + { + if (Owner.AreThereAvailableVendorsFor(from)) + list.Add(new VendorsEntry(this)); - public override void OnClick() - { - Mobile from = Owner.From; + if (Owner.VendorInventories.Count > 0) + list.Add(new ReclaimVendorInventoryEntry(this)); + } + } - if ( !from.CheckAlive() || m_Sign.Deleted || m_Sign.Owner == null || !m_Sign.Owner.AreThereAvailableVendorsFor( from ) ) - return; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - if ( from.Map != m_Sign.Map || !from.InRange( m_Sign, 5 ) ) - { - from.SendLocalizedMessage( 1062429 ); // You must be within five paces of the house sign to use this option. - } - else - { - from.SendGump( new HouseGumpAOS( HouseGumpPageAOS.Vendors, from, m_Sign.Owner ) ); - } - } - } + writer.Write(0); // version - private class ReclaimVendorInventoryEntry : ContextMenuEntry - { - private HouseSign m_Sign; + writer.Write(Owner); + writer.Write(OriginalOwner); + } - public ReclaimVendorInventoryEntry( HouseSign sign ) : base( 6213 ) - { - m_Sign = sign; - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void OnClick() - { - Mobile from = Owner.From; + int version = reader.ReadInt(); - if ( m_Sign.Deleted || m_Sign.Owner == null || m_Sign.Owner.VendorInventories.Count == 0 || !from.CheckAlive() ) - return; + switch (version) + { + case 0: + { + Owner = reader.ReadItem() as BaseHouse; + OriginalOwner = reader.ReadMobile(); - if ( from.Map != m_Sign.Map || !from.InRange( m_Sign, 5 ) ) - { - from.SendLocalizedMessage( 1062429 ); // You must be within five paces of the house sign to use this option. - } - else - { - from.CloseGump( typeof( VendorInventoryGump ) ); - from.SendGump( new VendorInventoryGump( m_Sign.Owner, from ) ); - } - } - } + break; + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (Name == "a house sign") + Name = null; + } - writer.Write( (int) 0 ); // version + private class VendorsEntry : ContextMenuEntry + { + private HouseSign m_Sign; - writer.Write( Owner ); - writer.Write( OriginalOwner ); - } + public VendorsEntry(HouseSign sign) : base(6211) + { + m_Sign = sign; + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void OnClick() + { + Mobile from = Owner.From; - int version = reader.ReadInt(); + if (!from.CheckAlive() || m_Sign.Deleted || m_Sign.Owner == null || + !m_Sign.Owner.AreThereAvailableVendorsFor(from)) + return; - switch ( version ) - { - case 0: - { - Owner = reader.ReadItem() as BaseHouse; - OriginalOwner = reader.ReadMobile(); + if (from.Map != m_Sign.Map || !from.InRange(m_Sign, 5)) + from.SendLocalizedMessage( + 1062429); // You must be within five paces of the house sign to use this option. + else + from.SendGump(new HouseGumpAOS(HouseGumpPageAOS.Vendors, from, m_Sign.Owner)); + } + } - break; - } - } + private class ReclaimVendorInventoryEntry : ContextMenuEntry + { + private HouseSign m_Sign; - if ( Name == "a house sign" ) - Name = null; - } - } -} + public ReclaimVendorInventoryEntry(HouseSign sign) : base(6213) + { + m_Sign = sign; + } + + public override void OnClick() + { + Mobile from = Owner.From; + + if (m_Sign.Deleted || m_Sign.Owner == null || m_Sign.Owner.VendorInventories.Count == 0 || + !from.CheckAlive()) + return; + + if (from.Map != m_Sign.Map || !from.InRange(m_Sign, 5)) + { + from.SendLocalizedMessage( + 1062429); // You must be within five paces of the house sign to use this option. + } + else + { + from.CloseGump(typeof(VendorInventoryGump)); + from.SendGump(new VendorInventoryGump(m_Sign.Owner, from)); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/HouseTeleporter.cs b/Scripts/Multis/HouseTeleporter.cs index ee7e891cc..480048833 100644 --- a/Scripts/Multis/HouseTeleporter.cs +++ b/Scripts/Multis/HouseTeleporter.cs @@ -1,173 +1,179 @@ using System; -using Server.Gumps; -using Server.Multis; using System.Collections.Generic; using Server.ContextMenus; +using Server.Gumps; +using Server.Mobiles; +using Server.Multis; namespace Server.Items { - public class HouseTeleporter : Item, ISecurable - { - [CommandProperty( AccessLevel.GameMaster )] - public Item Target { get; set; } + public class HouseTeleporter : Item, ISecurable + { + [Constructible] + public HouseTeleporter(int itemID) : this(itemID, null) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public SecureLevel Level { get; set; } + public HouseTeleporter(int itemID, Item target) : base(itemID) + { + Movable = false; - [Constructible] - public HouseTeleporter( int itemID ) : this( itemID, null ) - { - } + Level = SecureLevel.Anyone; - public HouseTeleporter( int itemID, Item target ) : base( itemID ) - { - Movable = false; + Target = target; + } - Level = SecureLevel.Anyone; + public HouseTeleporter(Serial serial) : base(serial) + { + } - Target = target; - } + [CommandProperty(AccessLevel.GameMaster)] + public Item Target{ get; set; } - public bool CheckAccess( Mobile m ) - { - BaseHouse house = BaseHouse.FindHouseAt( this ); + [CommandProperty(AccessLevel.GameMaster)] + public SecureLevel Level{ get; set; } - if ( house != null && (house.Public ? house.IsBanned( m ) : !house.HasAccess( m )) ) - return false; + public bool CheckAccess(Mobile m) + { + BaseHouse house = BaseHouse.FindHouseAt(this); - return ( house != null && house.HasSecureAccess( m, Level ) ); - } + if (house != null && (house.Public ? house.IsBanned(m) : !house.HasAccess(m))) + return false; - public override bool OnMoveOver( Mobile m ) - { - if ( Target != null && !Target.Deleted ) - { - if ( CheckAccess( m ) ) - { - if ( !m.Hidden || m.AccessLevel == AccessLevel.Player ) - new EffectTimer( Location, Map, 2023, 0x1F0, TimeSpan.FromSeconds( 0.4 ) ).Start(); + return house != null && house.HasSecureAccess(m, Level); + } - new DelayTimer( this, m ).Start(); - } - else - { - m.SendLocalizedMessage( 1061637 ); // You are not allowed to access this. - } - } + public override bool OnMoveOver(Mobile m) + { + if (Target != null && !Target.Deleted) + { + if (CheckAccess(m)) + { + if (!m.Hidden || m.AccessLevel == AccessLevel.Player) + new EffectTimer(Location, Map, 2023, 0x1F0, TimeSpan.FromSeconds(0.4)).Start(); - return true; - } + new DelayTimer(this, m).Start(); + } + else + { + m.SendLocalizedMessage(1061637); // You are not allowed to access this. + } + } - public override void GetContextMenuEntries( Mobile from, List list ) - { - base.GetContextMenuEntries( from, list ); - SetSecureLevelEntry.AddTo( from, this, list ); - } + return true; + } - public HouseTeleporter( Serial serial ) : base( serial ) - { - } + public override void GetContextMenuEntries(Mobile from, List list) + { + base.GetContextMenuEntries(from, list); + SetSecureLevelEntry.AddTo(from, this, list); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( (int) Level ); + writer.Write((int)Level); - writer.Write( (Item) Target ); - } + writer.Write(Target); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - Level = (SecureLevel)reader.ReadInt(); - goto case 0; - } - case 0: - { - Target = reader.ReadItem(); + switch (version) + { + case 1: + { + Level = (SecureLevel)reader.ReadInt(); + goto case 0; + } + case 0: + { + Target = reader.ReadItem(); - if ( version < 0 ) - Level = SecureLevel.Anyone; + if (version < 0) + Level = SecureLevel.Anyone; - break; - } - } - } + break; + } + } + } - private class EffectTimer : Timer - { - private Point3D m_Location; - private Map m_Map; - private int m_EffectID; - private int m_SoundID; + private class EffectTimer : Timer + { + private int m_EffectID; + private Point3D m_Location; + private Map m_Map; + private int m_SoundID; - public EffectTimer( Point3D p, Map map, int effectID, int soundID, TimeSpan delay ) : base( delay ) - { - m_Location = p; - m_Map = map; - m_EffectID = effectID; - m_SoundID = soundID; - } + public EffectTimer(Point3D p, Map map, int effectID, int soundID, TimeSpan delay) : base(delay) + { + m_Location = p; + m_Map = map; + m_EffectID = effectID; + m_SoundID = soundID; + } - protected override void OnTick() - { - Effects.SendLocationParticles( EffectItem.Create( m_Location, m_Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, m_EffectID, 0 ); + protected override void OnTick() + { + Effects.SendLocationParticles(EffectItem.Create(m_Location, m_Map, EffectItem.DefaultDuration), 0x3728, 10, + 10, m_EffectID, 0); - if ( m_SoundID != -1 ) - Effects.PlaySound( m_Location, m_Map, m_SoundID ); - } - } + if (m_SoundID != -1) + Effects.PlaySound(m_Location, m_Map, m_SoundID); + } + } - private class DelayTimer : Timer - { - private HouseTeleporter m_Teleporter; - private Mobile m_Mobile; + private class DelayTimer : Timer + { + private Mobile m_Mobile; + private HouseTeleporter m_Teleporter; - public DelayTimer( HouseTeleporter tp, Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ) ) - { - m_Teleporter = tp; - m_Mobile = m; - } + public DelayTimer(HouseTeleporter tp, Mobile m) : base(TimeSpan.FromSeconds(1.0)) + { + m_Teleporter = tp; + m_Mobile = m; + } - protected override void OnTick() - { - Item target = m_Teleporter.Target; + protected override void OnTick() + { + Item target = m_Teleporter.Target; - if ( target != null && !target.Deleted ) - { - Mobile m = m_Mobile; + if (target != null && !target.Deleted) + { + Mobile m = m_Mobile; - if ( m.Location == m_Teleporter.Location && m.Map == m_Teleporter.Map ) - { - Point3D p = target.GetWorldTop(); - Map map = target.Map; + if (m.Location == m_Teleporter.Location && m.Map == m_Teleporter.Map) + { + Point3D p = target.GetWorldTop(); + Map map = target.Map; - Mobiles.BaseCreature.TeleportPets( m, p, map ); + BaseCreature.TeleportPets(m, p, map); - m.MoveToWorld( p, map ); + m.MoveToWorld(p, map); - if ( !m.Hidden || m.AccessLevel == AccessLevel.Player ) - { - Effects.PlaySound( target.Location, target.Map, 0x1FE ); + if (!m.Hidden || m.AccessLevel == AccessLevel.Player) + { + Effects.PlaySound(target.Location, target.Map, 0x1FE); - Effects.SendLocationParticles( EffectItem.Create( m_Teleporter.Location, m_Teleporter.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023, 0 ); - Effects.SendLocationParticles( EffectItem.Create( target.Location, target.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023, 0 ); + Effects.SendLocationParticles( + EffectItem.Create(m_Teleporter.Location, m_Teleporter.Map, EffectItem.DefaultDuration), + 0x3728, 10, 10, 2023, 0); + Effects.SendLocationParticles( + EffectItem.Create(target.Location, target.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023, 0); - new EffectTimer( target.Location, target.Map, 2023, -1, TimeSpan.FromSeconds( 0.4 ) ).Start(); - } - } - } - } - } - } + new EffectTimer(target.Location, target.Map, 2023, -1, TimeSpan.FromSeconds(0.4)).Start(); + } + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Multis/Houses.cs b/Scripts/Multis/Houses.cs index a7176afab..ebd9bd708 100644 --- a/Scripts/Multis/Houses.cs +++ b/Scripts/Multis/Houses.cs @@ -3,572 +3,612 @@ using Server.Multis.Deeds; namespace Server.Multis { - public class SmallOldHouse : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D(-3,-3,7,7 ), new Rectangle2D( -1, 4, 3, 1 ) }; + public class SmallOldHouse : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-3, -3, 7, 7), new Rectangle2D(-1, 4, 3, 1) }; + + public SmallOldHouse(Mobile owner, int id) : base(id, owner, 425, 3) + { + uint keyValue = CreateKeys(owner); + + AddSouthDoor(0, 3, 7, keyValue); + + SetSign(2, 4, 5); + } + + public SmallOldHouse(Serial serial) : base(serial) + { + } + + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(2, 4, 0); + + public override int DefaultPrice => 43800; - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 2, 4, 0 ); + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[0]; - public override int DefaultPrice => 43800; + public override HouseDeed GetDeed() + { + switch (ItemID) + { + case 0x64: return new StonePlasterHouseDeed(); + case 0x66: return new FieldStoneHouseDeed(); + case 0x68: return new SmallBrickHouseDeed(); + case 0x6A: return new WoodHouseDeed(); + case 0x6C: return new WoodPlasterHouseDeed(); + case 0x6E: + default: return new ThatchedRoofCottageDeed(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + public class GuildHouse : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-7, -7, 14, 14), new Rectangle2D(-2, 7, 4, 1) }; + + public GuildHouse(Mobile owner) : base(0x74, owner, 1100, 8) + { + uint keyValue = CreateKeys(owner); + + AddSouthDoors(-1, 6, 7, keyValue); + + SetSign(4, 8, 16); + + AddSouthDoor(-3, -1, 7); + AddSouthDoor(3, -1, 7); + } + + public GuildHouse(Serial serial) : base(serial) + { + } + + public override int DefaultPrice => 144500; + + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[20]; + public override int ConvertOffsetX => -1; + public override int ConvertOffsetY => -1; + + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(4, 8, 0); + + public override HouseDeed GetDeed() + { + return new BrickHouseDeed(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + public class TwoStoryHouse : BaseHouse + { + public static Rectangle2D[] AreaArray = + { new Rectangle2D(-7, 0, 14, 7), new Rectangle2D(-7, -7, 9, 7), new Rectangle2D(-4, 7, 4, 1) }; + + public TwoStoryHouse(Mobile owner, int id) : base(id, owner, 1370, 10) + { + uint keyValue = CreateKeys(owner); + + AddSouthDoors(-3, 6, 7, keyValue); + + SetSign(2, 8, 16); + + AddSouthDoor(-3, 0, 7); + AddSouthDoor(id == 0x76 ? -2 : -3, 0, 27); + } + + public TwoStoryHouse(Serial serial) : base(serial) + { + } + + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(2, 8, 0); + + public override int DefaultPrice => 192400; + + public override HouseDeed GetDeed() + { + switch (ItemID) + { + case 0x76: return new TwoStoryWoodPlasterHouseDeed(); + case 0x78: + default: return new TwoStoryStonePlasterHouseDeed(); + } + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + public class Tower : BaseHouse + { + public static Rectangle2D[] AreaArray = + { + new Rectangle2D(-7, -7, 16, 14), new Rectangle2D(-1, 7, 4, 2), new Rectangle2D(-11, 0, 4, 7), + new Rectangle2D(9, 0, 4, 7) + }; + + public Tower(Mobile owner) : base(0x7A, owner, 2119, 15) + { + uint keyValue = CreateKeys(owner); + + AddSouthDoors(false, 0, 6, 6, keyValue); + + SetSign(5, 8, 16); + + AddSouthDoor(false, 3, -2, 6); + AddEastDoor(false, 1, 4, 26); + AddEastDoor(false, 1, 4, 46); + } + + public Tower(Serial serial) : base(serial) + { + } + + public override int DefaultPrice => 433200; + + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[37]; + public override int ConvertOffsetY => -1; + + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(5, 8, 0); + + public override HouseDeed GetDeed() + { + return new TowerDeed(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + public class Keep : BaseHouse //warning: ODD shape! + { + public static Rectangle2D[] AreaArray = + { + new Rectangle2D(-11, -11, 7, 8), new Rectangle2D(-11, 5, 7, 8), new Rectangle2D(6, -11, 7, 8), + new Rectangle2D(6, 5, 7, 8), new Rectangle2D(-9, -3, 5, 8), new Rectangle2D(6, -3, 5, 8), + new Rectangle2D(-4, -9, 10, 20), new Rectangle2D(-1, 11, 4, 1) + }; + + public Keep(Mobile owner) : base(0x7C, owner, 2625, 18) + { + uint keyValue = CreateKeys(owner); + + AddSouthDoors(false, 0, 10, 6, keyValue); + + SetSign(5, 12, 16); + } + + public Keep(Serial serial) : base(serial) + { + } + + public override int DefaultPrice => 665200; + + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(5, 13, 0); + + public override HouseDeed GetDeed() + { + return new KeepDeed(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + public class Castle : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-15, -15, 31, 31), new Rectangle2D(-1, 16, 4, 1) }; - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[0]; + public Castle(Mobile owner) : base(0x7E, owner, 4076, 28) + { + uint keyValue = CreateKeys(owner); - public SmallOldHouse( Mobile owner, int id ) : base( id, owner, 425, 3 ) - { - uint keyValue = CreateKeys( owner ); + AddSouthDoors(false, 0, 15, 6, keyValue); - AddSouthDoor( 0, 3, 7, keyValue ); + SetSign(5, 17, 16); - SetSign( 2, 4, 5 ); - } + AddSouthDoors(false, 0, 11, 6, true); + AddSouthDoors(false, 0, 5, 6, false); + AddSouthDoors(false, -1, -11, 6, false); + } - public SmallOldHouse( Serial serial ) : base( serial ) - { - } + public Castle(Serial serial) : base(serial) + { + } - public override HouseDeed GetDeed() - { - switch ( ItemID ) - { - case 0x64: return new StonePlasterHouseDeed(); - case 0x66: return new FieldStoneHouseDeed(); - case 0x68: return new SmallBrickHouseDeed(); - case 0x6A: return new WoodHouseDeed(); - case 0x6C: return new WoodPlasterHouseDeed(); - case 0x6E: - default: return new ThatchedRoofCottageDeed(); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - public class GuildHouse : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -7, -7, 14, 14 ), new Rectangle2D( -2, 7, 4, 1 ) }; + public override int DefaultPrice => 1022800; - public override int DefaultPrice => 144500; - - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[20]; - public override int ConvertOffsetX => -1; - public override int ConvertOffsetY => -1; + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(5, 17, 0); + + public override HouseDeed GetDeed() + { + return new CastleDeed(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } + + public class LargePatioHouse : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-7, -7, 15, 14), new Rectangle2D(-5, 7, 4, 1) }; - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 4, 8, 0 ); + public LargePatioHouse(Mobile owner) : base(0x8C, owner, 1100, 8) + { + uint keyValue = CreateKeys(owner); - public GuildHouse( Mobile owner ) : base( 0x74, owner, 1100, 8 ) - { - uint keyValue = CreateKeys( owner ); + AddSouthDoors(-4, 6, 7, keyValue); - AddSouthDoors( -1, 6, 7, keyValue ); + SetSign(1, 8, 16); - SetSign( 4, 8, 16 ); + AddEastDoor(1, 4, 7); + AddEastDoor(1, -4, 7); + AddSouthDoor(4, -1, 7); + } - AddSouthDoor( -3, -1, 7 ); - AddSouthDoor( 3, -1, 7 ); - } + public LargePatioHouse(Serial serial) : base(serial) + { + } - public GuildHouse( Serial serial ) : base( serial ) - { - } + public override int DefaultPrice => 152800; - public override HouseDeed GetDeed() { return new BrickHouseDeed(); } + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[29]; + public override int ConvertOffsetY => -1; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(1, 8, 0); - public class TwoStoryHouse : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -7, 0, 14, 7 ), new Rectangle2D( -7, -7, 9, 7 ), new Rectangle2D( -4, 7, 4, 1 ) }; + public override HouseDeed GetDeed() + { + return new LargePatioDeed(); + } - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 2, 8, 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - public override int DefaultPrice => 192400; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - public TwoStoryHouse( Mobile owner, int id ) : base( id, owner, 1370, 10 ) - { - uint keyValue = CreateKeys( owner ); + public class LargeMarbleHouse : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-7, -7, 15, 14), new Rectangle2D(-6, 7, 6, 1) }; - AddSouthDoors( -3, 6, 7, keyValue ); + public LargeMarbleHouse(Mobile owner) : base(0x96, owner, 1370, 10) + { + uint keyValue = CreateKeys(owner); - SetSign( 2, 8, 16 ); + AddSouthDoors(false, -4, 3, 4, keyValue); - AddSouthDoor( -3, 0, 7 ); - AddSouthDoor( id == 0x76 ? -2 : -3, 0, 27 ); - } - - public TwoStoryHouse( Serial serial ) : base( serial ) - { - } - - public override HouseDeed GetDeed() - { - switch( ItemID ) - { - case 0x76: return new TwoStoryWoodPlasterHouseDeed(); - case 0x78: - default: return new TwoStoryStonePlasterHouseDeed(); - } - } + SetSign(1, 8, 11); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } + public LargeMarbleHouse(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override int DefaultPrice => 192000; - public class Tower : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -7, -7, 16, 14 ), new Rectangle2D( -1, 7, 4, 2 ), new Rectangle2D( -11, 0, 4, 7 ), new Rectangle2D( 9, 0, 4, 7 ) }; + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[29]; + public override int ConvertOffsetY => -1; - public override int DefaultPrice => 433200; + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(1, 8, 0); - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[37]; - public override int ConvertOffsetY => -1; + public override HouseDeed GetDeed() + { + return new LargeMarbleDeed(); + } - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 5, 8, 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - public Tower( Mobile owner ) : base( 0x7A, owner, 2119, 15 ) - { - uint keyValue = CreateKeys( owner ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - AddSouthDoors( false, 0, 6, 6, keyValue ); + public class SmallTower : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-3, -3, 8, 7), new Rectangle2D(2, 4, 3, 1) }; - SetSign( 5, 8, 16 ); + public SmallTower(Mobile owner) : base(0x98, owner, 580, 4) + { + uint keyValue = CreateKeys(owner); - AddSouthDoor( false, 3, -2, 6 ); - AddEastDoor( false, 1, 4, 26 ); - AddEastDoor( false, 1, 4, 46 ); - } + AddSouthDoor(false, 3, 3, 6, keyValue); - public Tower( Serial serial ) : base( serial ) - { - } + SetSign(1, 4, 5); + } - public override HouseDeed GetDeed() { return new TowerDeed(); } + public SmallTower(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } + public override int DefaultPrice => 88500; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[6]; - public class Keep : BaseHouse//warning: ODD shape! - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -11, -11, 7, 8 ), new Rectangle2D( -11, 5, 7, 8 ), new Rectangle2D( 6, -11, 7, 8 ), new Rectangle2D( 6, 5, 7, 8 ), new Rectangle2D( -9, -3, 5, 8 ), new Rectangle2D( 6, -3, 5, 8 ), new Rectangle2D( -4, -9, 10, 20 ), new Rectangle2D( -1, 11, 4, 1 ) }; + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(1, 4, 0); - public override int DefaultPrice => 665200; + public override HouseDeed GetDeed() + { + return new SmallTowerDeed(); + } - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 5, 13, 0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - public Keep( Mobile owner ) : base( 0x7C, owner, 2625, 18 ) - { - uint keyValue = CreateKeys( owner ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - AddSouthDoors( false, 0, 10, 6, keyValue ); + public class LogCabin : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-3, -6, 8, 13) }; - SetSign( 5, 12, 16 ); - } + public LogCabin(Mobile owner) : base(0x9A, owner, 1100, 8) + { + uint keyValue = CreateKeys(owner); - public Keep( Serial serial ) : base( serial ) - { - } + AddSouthDoor(1, 4, 8, keyValue); - public override HouseDeed GetDeed() { return new KeepDeed(); } + SetSign(5, 8, 20); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } + AddSouthDoor(1, 0, 29); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public LogCabin(Serial serial) : base(serial) + { + } - public class Castle : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -15, -15, 31, 31 ), new Rectangle2D( -1, 16, 4, 1 ) }; + public override int DefaultPrice => 97800; - public override int DefaultPrice => 1022800; + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[12]; - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 5, 17, 0 ); + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(5, 8, 0); - public Castle( Mobile owner ) : base( 0x7E, owner, 4076, 28 ) - { - uint keyValue = CreateKeys( owner ); + public override HouseDeed GetDeed() + { + return new LogCabinDeed(); + } - AddSouthDoors( false, 0, 15, 6, keyValue ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - SetSign( 5, 17, 16 ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - AddSouthDoors( false, 0, 11, 6, true ); - AddSouthDoors( false, 0, 5, 6, false ); - AddSouthDoors( false, -1, -11, 6, false ); - } + public class SandStonePatio : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-5, -4, 12, 8), new Rectangle2D(-2, 4, 3, 1) }; - public Castle( Serial serial ) : base( serial ) - { - } + public SandStonePatio(Mobile owner) : base(0x9C, owner, 850, 6) + { + uint keyValue = CreateKeys(owner); - public override HouseDeed GetDeed() { return new CastleDeed(); } + AddSouthDoor(-1, 3, 6, keyValue); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } + SetSign(4, 6, 24); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public SandStonePatio(Serial serial) : base(serial) + { + } - public class LargePatioHouse : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -7, -7, 15, 14 ), new Rectangle2D( -5, 7, 4, 1 ) }; + public override int DefaultPrice => 90900; - public override int DefaultPrice => 152800; + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[35]; + public override int ConvertOffsetY => -1; - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[29]; - public override int ConvertOffsetY => -1; + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(4, 6, 0); - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 1, 8, 0 ); + public override HouseDeed GetDeed() + { + return new SandstonePatioDeed(); + } - public LargePatioHouse( Mobile owner ) : base( 0x8C, owner, 1100, 8 ) - { - uint keyValue = CreateKeys( owner ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - AddSouthDoors( -4, 6, 7, keyValue ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - SetSign( 1, 8, 16 ); + public class TwoStoryVilla : BaseHouse + { + public static Rectangle2D[] AreaArray = { new Rectangle2D(-5, -5, 11, 11), new Rectangle2D(2, 6, 4, 1) }; - AddEastDoor( 1, 4, 7 ); - AddEastDoor( 1, -4, 7 ); - AddSouthDoor( 4, -1, 7 ); - } + public TwoStoryVilla(Mobile owner) : base(0x9E, owner, 1100, 8) + { + uint keyValue = CreateKeys(owner); - public LargePatioHouse( Serial serial ) : base( serial ) - { - } + AddSouthDoors(3, 1, 5, keyValue); - public override HouseDeed GetDeed() { return new LargePatioDeed(); } + SetSign(3, 8, 24); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } + AddEastDoor(1, 0, 25); + AddSouthDoor(-3, -1, 25); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + public TwoStoryVilla(Serial serial) : base(serial) + { + } - public class LargeMarbleHouse : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -7, -7, 15, 14 ), new Rectangle2D( -6, 7, 6, 1 ) }; + public override int DefaultPrice => 136500; - public override int DefaultPrice => 192000; + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[31]; - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.ThreeStoryFoundations[29]; - public override int ConvertOffsetY => -1; + public override Rectangle2D[] Area => AreaArray; + public override Point3D BaseBanLocation => new Point3D(3, 8, 0); - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 1, 8, 0 ); + public override HouseDeed GetDeed() + { + return new VillaDeed(); + } - public LargeMarbleHouse( Mobile owner ) : base( 0x96, owner, 1370, 10 ) - { - uint keyValue = CreateKeys( owner ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - AddSouthDoors( false, -4, 3, 4, keyValue ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } - SetSign( 1, 8, 11 ); - } + public class SmallShop : BaseHouse + { + public static Rectangle2D[] AreaArray1 = { new Rectangle2D(-3, -3, 7, 7), new Rectangle2D(-1, 4, 4, 1) }; + public static Rectangle2D[] AreaArray2 = { new Rectangle2D(-3, -3, 7, 7), new Rectangle2D(-2, 4, 3, 1) }; - public LargeMarbleHouse( Serial serial ) : base( serial ) - { - } + public SmallShop(Mobile owner, int id) : base(id, owner, 425, 3) + { + uint keyValue = CreateKeys(owner); - public override HouseDeed GetDeed() { return new LargeMarbleDeed(); } + BaseDoor door = MakeDoor(false, DoorFacing.EastCW); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } + door.Locked = true; + door.KeyValue = keyValue; - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } + if (door is BaseHouseDoor) + ((BaseHouseDoor)door).Facing = DoorFacing.EastCCW; - public class SmallTower : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -3, -3, 8, 7 ), new Rectangle2D( 2, 4, 3, 1 ) }; + AddDoor(door, -2, 0, id == 0xA2 ? 24 : 27); - public override int DefaultPrice => 88500; + //AddSouthDoor( false, -2, 0, 27 - (id == 0xA2 ? 3 : 0), keyValue ); - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[6]; + SetSign(3, 4, 7 - (id == 0xA2 ? 2 : 0)); + } - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 1, 4, 0 ); + public SmallShop(Serial serial) : base(serial) + { + } - public SmallTower( Mobile owner ) : base( 0x98, owner, 580, 4 ) - { - uint keyValue = CreateKeys( owner ); + public override Rectangle2D[] Area => ItemID == 0x40A2 ? AreaArray1 : AreaArray2; + public override Point3D BaseBanLocation => new Point3D(3, 4, 0); - AddSouthDoor( false, 3, 3, 6, keyValue ); + public override int DefaultPrice => 63000; - SetSign( 1, 4, 5 ); - } + public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[0]; + + public override HouseDeed GetDeed() + { + switch (ItemID) + { + case 0xA0: return new StoneWorkshopDeed(); + case 0xA2: + default: return new MarbleWorkshopDeed(); + } + } - public SmallTower( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); //version + } - public override HouseDeed GetDeed() { return new SmallTowerDeed(); } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - public class LogCabin : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -3, -6, 8, 13 ) }; - - public override int DefaultPrice => 97800; - - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[12]; - - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 5, 8, 0 ); - - public LogCabin( Mobile owner ) : base( 0x9A, owner, 1100, 8 ) - { - uint keyValue = CreateKeys( owner ); - - AddSouthDoor( 1, 4, 8, keyValue ); - - SetSign( 5, 8, 20 ); - - AddSouthDoor( 1, 0, 29 ); - } - - public LogCabin( Serial serial ) : base( serial ) - { - } - - public override HouseDeed GetDeed() { return new LogCabinDeed(); } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - public class SandStonePatio : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -5, -4, 12, 8 ), new Rectangle2D( -2, 4, 3, 1 ) }; - - public override int DefaultPrice => 90900; - - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[35]; - public override int ConvertOffsetY => -1; - - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 4, 6, 0 ); - - public SandStonePatio( Mobile owner ) : base( 0x9C, owner, 850, 6 ) - { - uint keyValue = CreateKeys( owner ); - - AddSouthDoor( -1, 3, 6, keyValue ); - - SetSign( 4, 6, 24 ); - } - - public SandStonePatio( Serial serial ) : base( serial ) - { - } - - public override HouseDeed GetDeed() { return new SandstonePatioDeed(); } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - public class TwoStoryVilla : BaseHouse - { - public static Rectangle2D[] AreaArray = { new Rectangle2D( -5, -5, 11, 11 ), new Rectangle2D( 2, 6, 4, 1 ) }; - - public override int DefaultPrice => 136500; - - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[31]; - - public override Rectangle2D[] Area => AreaArray; - public override Point3D BaseBanLocation => new Point3D( 3, 8, 0 ); - - public TwoStoryVilla( Mobile owner ) : base( 0x9E, owner, 1100, 8 ) - { - uint keyValue = CreateKeys( owner ); - - AddSouthDoors( 3, 1, 5, keyValue ); - - SetSign( 3, 8, 24 ); - - AddEastDoor( 1, 0, 25 ); - AddSouthDoor( -3, -1, 25 ); - } - - public TwoStoryVilla( Serial serial ) : base( serial ) - { - } - - public override HouseDeed GetDeed() { return new VillaDeed(); } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } - - public class SmallShop : BaseHouse - { - public override Rectangle2D[] Area => ( ItemID == 0x40A2 ? AreaArray1 : AreaArray2 ); - public override Point3D BaseBanLocation => new Point3D( 3, 4, 0 ); - - public override int DefaultPrice => 63000; - - public override HousePlacementEntry ConvertEntry => HousePlacementEntry.TwoStoryFoundations[0]; - - public static Rectangle2D[] AreaArray1 = { new Rectangle2D(-3,-3,7,7), new Rectangle2D( -1, 4, 4, 1 ) }; - public static Rectangle2D[] AreaArray2 = { new Rectangle2D(-3,-3,7,7), new Rectangle2D( -2, 4, 3, 1 ) }; - - public SmallShop( Mobile owner, int id ) : base( id, owner, 425, 3 ) - { - uint keyValue = CreateKeys( owner ); - - BaseDoor door = MakeDoor( false, DoorFacing.EastCW ); - - door.Locked = true; - door.KeyValue = keyValue; - - if ( door is BaseHouseDoor ) - ((BaseHouseDoor)door).Facing = DoorFacing.EastCCW; - - AddDoor( door, -2, 0, id == 0xA2 ? 24 : 27 ); - - //AddSouthDoor( false, -2, 0, 27 - (id == 0xA2 ? 3 : 0), keyValue ); - - SetSign( 3, 4, 7 - (id == 0xA2 ? 2 : 0) ); - } - - public SmallShop( Serial serial ) : base( serial ) - { - } - - public override HouseDeed GetDeed() - { - switch ( ItemID ) - { - case 0xA0: return new StoneWorkshopDeed(); - case 0xA2: - default: return new MarbleWorkshopDeed(); - } - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 );//version - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/MovingCrate.cs b/Scripts/Multis/MovingCrate.cs index 624fea87d..4888017bf 100644 --- a/Scripts/Multis/MovingCrate.cs +++ b/Scripts/Multis/MovingCrate.cs @@ -5,320 +5,310 @@ using Server.Network; namespace Server.Multis { - public class MovingCrate : Container - { - public static readonly int MaxItemsPerSubcontainer = 20; - public static readonly int Rows = 3; - public static readonly int Columns = 5; - public static readonly int HorizontalSpacing = 25; - public static readonly int VerticalSpacing = 25; - - public override int LabelNumber => 1061690; // Packing Crate - - private Timer m_InternalizeTimer; - - public BaseHouse House { get; set; } - - public override int DefaultMaxItems => 0; - public override int DefaultMaxWeight => 0; - - public MovingCrate( BaseHouse house ) : base( 0xE3D ) - { - Hue = 0x8A5; - Movable = false; - - House = house; - } - - public MovingCrate( Serial serial ) : base( serial ) - { - } - - /* - public override void AddNameProperties( ObjectPropertyList list ) - { - base.AddNameProperties( list ); - - if ( House != null && House.InternalizedVendors.Count > 0 ) - list.Add( 1061833, House.InternalizedVendors.Count.ToString() ); // This packing crate contains ~1_COUNT~ vendors/barkeepers. - } - */ - - public override void DropItem( Item dropped ) - { - // 1. Try to stack the item - foreach ( Item item in Items ) - { - if ( item is PackingBox ) - { - List subItems = item.Items; - - for ( int i = 0; i < subItems.Count; i++ ) - { - Item subItem = subItems[i]; - - if ( !(subItem is Container) && subItem.StackWith( null, dropped, false ) ) - return; - } - } - } - - // 2. Try to drop the item into an existing container - foreach ( Item item in Items ) - { - if ( item is PackingBox packingBox ) - { - Container box = packingBox; - List subItems = box.Items; - - if ( subItems.Count < MaxItemsPerSubcontainer ) - { - box.DropItem( dropped ); - return; - } - } - } - - // 3. Drop the item into a new container - Container subContainer = new PackingBox(); - subContainer.DropItem( dropped ); - - Point3D location = GetFreeLocation(); - if ( location != Point3D.Zero ) - { - AddItem( subContainer ); - subContainer.Location = location; - } - else - { - base.DropItem( subContainer ); - } - } - - private Point3D GetFreeLocation() - { - bool[,] positions = new bool[Rows, Columns]; - - foreach ( Item item in Items ) - { - if ( item is PackingBox ) - { - int i = (item.Y - Bounds.Y) / VerticalSpacing; - if ( i < 0 ) - i = 0; - else if ( i >= Rows ) - i = Rows - 1; - - int j = (item.X - Bounds.X) / HorizontalSpacing; - if ( j < 0 ) - j = 0; - else if ( j >= Columns ) - j = Columns - 1; - - positions[i, j] = true; - } - } - - for ( int i = 0; i < Rows; i++ ) - { - for ( int j = 0; j < Columns; j++ ) - { - if ( !positions[i, j] ) - { - int x = Bounds.X + j * HorizontalSpacing; - int y = Bounds.Y + i * VerticalSpacing; - - return new Point3D( x, y, 0 ); - } - } - } - - return Point3D.Zero; - } - - public override bool IsDecoContainer => false; - - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if ( m.AccessLevel < AccessLevel.GameMaster ) - { - m.SendLocalizedMessage( 1061145 ); // You cannot place items into a house moving crate. - return false; - } - - return base.CheckHold( m, item, message, checkItems, plusItems, plusWeight ); - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - return base.CheckLift( from, item, ref reject ) && House != null && !House.Deleted && House.IsOwner( from ); - } - - public override bool CheckItemUse( Mobile from, Item item ) - { - return base.CheckItemUse( from, item ) && House != null && !House.Deleted && House.IsOwner( from ); - } - - public override void OnItemRemoved( Item item ) - { - base.OnItemRemoved( item ); - - if ( TotalItems == 0 ) - Delete(); - } - - public void RestartTimer() - { - if ( m_InternalizeTimer == null ) - { - m_InternalizeTimer = new InternalizeTimer( this ); - m_InternalizeTimer.Start(); - } - else - { - m_InternalizeTimer.Stop(); - m_InternalizeTimer.Start(); - } - } - - public void Hide() - { - if ( m_InternalizeTimer != null ) - { - m_InternalizeTimer.Stop(); - m_InternalizeTimer = null; - } - - List toRemove = new List(); - foreach ( Item item in Items ) - if ( item is PackingBox && item.Items.Count == 0 ) - toRemove.Add( item ); - - foreach ( Item item in toRemove ) - item.Delete(); - - if ( TotalItems == 0 ) - Delete(); - else - Internalize(); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - if ( House != null && House.MovingCrate == this ) - House.MovingCrate = null; - - m_InternalizeTimer?.Stop(); - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.WriteEncodedInt( 1 ); - - writer.Write( (Item) House ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadEncodedInt(); - - House = reader.ReadItem() as BaseHouse; - - if ( House != null ) - { - House.MovingCrate = this; - Timer.DelayCall( TimeSpan.Zero, Hide ); - } - else - { - Timer.DelayCall( TimeSpan.Zero, Delete ); - } - - if ( version == 0 ) - MaxItems = -1; // reset to default - } - - public class InternalizeTimer : Timer - { - private MovingCrate m_Crate; - - public InternalizeTimer( MovingCrate crate ) : base( TimeSpan.FromMinutes( 5.0 ) ) - { - m_Crate = crate; - - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - m_Crate.Hide(); - } - } - } - - public class PackingBox : BaseContainer - { - public override int LabelNumber => 1061690; // Packing Crate - - public override int DefaultGumpID => 0x4B; - public override int DefaultDropSound => 0x42; - - public override Rectangle2D Bounds => new Rectangle2D( 16, 51, 168, 73 ); - - public override int DefaultMaxItems => 0; - public override int DefaultMaxWeight => 0; - - public PackingBox() : base( 0x9A8 ) - { - Movable = false; - } - - public PackingBox( Serial serial ) : base( serial ) - { - } - - public override void SendCantStoreMessage( Mobile to, Item item ) - { - to.SendLocalizedMessage( 1061145 ); // You cannot place items into a house moving crate. - } + public class MovingCrate : Container + { + public static readonly int MaxItemsPerSubcontainer = 20; + public static readonly int Rows = 3; + public static readonly int Columns = 5; + public static readonly int HorizontalSpacing = 25; + public static readonly int VerticalSpacing = 25; + + private Timer m_InternalizeTimer; + + public MovingCrate(BaseHouse house) : base(0xE3D) + { + Hue = 0x8A5; + Movable = false; + + House = house; + } + + public MovingCrate(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1061690; // Packing Crate + + public BaseHouse House{ get; set; } + + public override int DefaultMaxItems => 0; + public override int DefaultMaxWeight => 0; + + public override bool IsDecoContainer => false; + + /* + public override void AddNameProperties( ObjectPropertyList list ) + { + base.AddNameProperties( list ); + + if ( House != null && House.InternalizedVendors.Count > 0 ) + list.Add( 1061833, House.InternalizedVendors.Count.ToString() ); // This packing crate contains ~1_COUNT~ vendors/barkeepers. + } + */ + + public override void DropItem(Item dropped) + { + // 1. Try to stack the item + foreach (Item item in Items) + if (item is PackingBox) + { + List subItems = item.Items; + + for (int i = 0; i < subItems.Count; i++) + { + Item subItem = subItems[i]; + + if (!(subItem is Container) && subItem.StackWith(null, dropped, false)) + return; + } + } + + // 2. Try to drop the item into an existing container + foreach (Item item in Items) + if (item is PackingBox packingBox) + { + Container box = packingBox; + List subItems = box.Items; + + if (subItems.Count < MaxItemsPerSubcontainer) + { + box.DropItem(dropped); + return; + } + } + + // 3. Drop the item into a new container + Container subContainer = new PackingBox(); + subContainer.DropItem(dropped); + + Point3D location = GetFreeLocation(); + if (location != Point3D.Zero) + { + AddItem(subContainer); + subContainer.Location = location; + } + else + { + base.DropItem(subContainer); + } + } + + private Point3D GetFreeLocation() + { + bool[,] positions = new bool[Rows, Columns]; + + foreach (Item item in Items) + if (item is PackingBox) + { + int i = (item.Y - Bounds.Y) / VerticalSpacing; + if (i < 0) + i = 0; + else if (i >= Rows) + i = Rows - 1; + + int j = (item.X - Bounds.X) / HorizontalSpacing; + if (j < 0) + j = 0; + else if (j >= Columns) + j = Columns - 1; + + positions[i, j] = true; + } + + for (int i = 0; i < Rows; i++) + for (int j = 0; j < Columns; j++) + if (!positions[i, j]) + { + int x = Bounds.X + j * HorizontalSpacing; + int y = Bounds.Y + i * VerticalSpacing; + + return new Point3D(x, y, 0); + } + + return Point3D.Zero; + } + + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (m.AccessLevel < AccessLevel.GameMaster) + { + m.SendLocalizedMessage(1061145); // You cannot place items into a house moving crate. + return false; + } + + return base.CheckHold(m, item, message, checkItems, plusItems, plusWeight); + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + return base.CheckLift(from, item, ref reject) && House != null && !House.Deleted && House.IsOwner(from); + } + + public override bool CheckItemUse(Mobile from, Item item) + { + return base.CheckItemUse(from, item) && House != null && !House.Deleted && House.IsOwner(from); + } + + public override void OnItemRemoved(Item item) + { + base.OnItemRemoved(item); + + if (TotalItems == 0) + Delete(); + } + + public void RestartTimer() + { + if (m_InternalizeTimer == null) + { + m_InternalizeTimer = new InternalizeTimer(this); + m_InternalizeTimer.Start(); + } + else + { + m_InternalizeTimer.Stop(); + m_InternalizeTimer.Start(); + } + } + + public void Hide() + { + if (m_InternalizeTimer != null) + { + m_InternalizeTimer.Stop(); + m_InternalizeTimer = null; + } + + List toRemove = new List(); + foreach (Item item in Items) + if (item is PackingBox && item.Items.Count == 0) + toRemove.Add(item); + + foreach (Item item in toRemove) + item.Delete(); + + if (TotalItems == 0) + Delete(); + else + Internalize(); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + if (House != null && House.MovingCrate == this) + House.MovingCrate = null; + + m_InternalizeTimer?.Stop(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.WriteEncodedInt(1); + + writer.Write(House); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadEncodedInt(); + + House = reader.ReadItem() as BaseHouse; + + if (House != null) + { + House.MovingCrate = this; + Timer.DelayCall(TimeSpan.Zero, Hide); + } + else + { + Timer.DelayCall(TimeSpan.Zero, Delete); + } + + if (version == 0) + MaxItems = -1; // reset to default + } + + public class InternalizeTimer : Timer + { + private MovingCrate m_Crate; + + public InternalizeTimer(MovingCrate crate) : base(TimeSpan.FromMinutes(5.0)) + { + m_Crate = crate; + + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + m_Crate.Hide(); + } + } + } + + public class PackingBox : BaseContainer + { + public PackingBox() : base(0x9A8) + { + Movable = false; + } + + public PackingBox(Serial serial) : base(serial) + { + } + + public override int LabelNumber => 1061690; // Packing Crate + + public override int DefaultGumpID => 0x4B; + public override int DefaultDropSound => 0x42; + + public override Rectangle2D Bounds => new Rectangle2D(16, 51, 168, 73); - public override void OnItemRemoved( Item item ) - { - base.OnItemRemoved( item ); + public override int DefaultMaxItems => 0; + public override int DefaultMaxWeight => 0; + + public override void SendCantStoreMessage(Mobile to, Item item) + { + to.SendLocalizedMessage(1061145); // You cannot place items into a house moving crate. + } - if ( item.GetBounce() == null && TotalItems == 0 ) - Delete(); - } + public override void OnItemRemoved(Item item) + { + base.OnItemRemoved(item); - public override void OnItemBounceCleared( Item item ) - { - base.OnItemBounceCleared( item ); + if (item.GetBounce() == null && TotalItems == 0) + Delete(); + } - if ( TotalItems == 0 ) - Delete(); - } + public override void OnItemBounceCleared(Item item) + { + base.OnItemBounceCleared(item); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + if (TotalItems == 0) + Delete(); + } - writer.WriteEncodedInt( 1 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize(GenericReader reader) - { - base.Deserialize( reader ); + writer.WriteEncodedInt(1); // version + } - int version = reader.ReadEncodedInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( version == 0 ) - MaxItems = -1; // reset to default - } - } -} + int version = reader.ReadEncodedInt(); + + if (version == 0) + MaxItems = -1; // reset to default + } + } +} \ No newline at end of file diff --git a/Scripts/Multis/PreviewHouse.cs b/Scripts/Multis/PreviewHouse.cs index 6c9780d4e..50f532469 100644 --- a/Scripts/Multis/PreviewHouse.cs +++ b/Scripts/Multis/PreviewHouse.cs @@ -4,139 +4,139 @@ using Server.Items; namespace Server.Multis { - public class PreviewHouse : BaseMulti - { - private List m_Components; - private Timer m_Timer; + public class PreviewHouse : BaseMulti + { + private List m_Components; + private Timer m_Timer; - public PreviewHouse( int multiID ) : base( multiID ) - { - m_Components = new List(); + public PreviewHouse(int multiID) : base(multiID) + { + m_Components = new List(); - MultiComponentList mcl = Components; + MultiComponentList mcl = Components; - for ( int i = 1; i < mcl.List.Length; ++i ) - { - MultiTileEntry entry = mcl.List[i]; + for (int i = 1; i < mcl.List.Length; ++i) + { + MultiTileEntry entry = mcl.List[i]; - if ( entry.m_Flags == 0 ) - { - Item item = new Static( (int)entry.m_ItemID ); + if (entry.m_Flags == 0) + { + Item item = new Static((int)entry.m_ItemID); - item.MoveToWorld( new Point3D( X + entry.m_OffsetX, Y + entry.m_OffsetY, Z + entry.m_OffsetZ ), Map ); + item.MoveToWorld(new Point3D(X + entry.m_OffsetX, Y + entry.m_OffsetY, Z + entry.m_OffsetZ), Map); - m_Components.Add( item ); - } - } + m_Components.Add(item); + } + } - m_Timer = new DecayTimer( this ); - m_Timer.Start(); - } + m_Timer = new DecayTimer(this); + m_Timer.Start(); + } - public override void OnLocationChange( Point3D oldLocation ) - { - base.OnLocationChange( oldLocation ); + public PreviewHouse(Serial serial) : base(serial) + { + } - if ( m_Components == null ) - return; + public override void OnLocationChange(Point3D oldLocation) + { + base.OnLocationChange(oldLocation); - int xOffset = X - oldLocation.X; - int yOffset = Y - oldLocation.Y; - int zOffset = Z - oldLocation.Z; + if (m_Components == null) + return; - for ( int i = 0; i < m_Components.Count; ++i ) - { - Item item = m_Components[i]; + int xOffset = X - oldLocation.X; + int yOffset = Y - oldLocation.Y; + int zOffset = Z - oldLocation.Z; - item.MoveToWorld( new Point3D( item.X + xOffset, item.Y + yOffset, item.Z + zOffset ), Map ); - } - } + for (int i = 0; i < m_Components.Count; ++i) + { + Item item = m_Components[i]; - public override void OnMapChange() - { - base.OnMapChange(); + item.MoveToWorld(new Point3D(item.X + xOffset, item.Y + yOffset, item.Z + zOffset), Map); + } + } - if ( m_Components == null ) - return; + public override void OnMapChange() + { + base.OnMapChange(); - for ( int i = 0; i < m_Components.Count; ++i ) - { - Item item = m_Components[i]; + if (m_Components == null) + return; - item.Map = Map; - } - } + for (int i = 0; i < m_Components.Count; ++i) + { + Item item = m_Components[i]; - public override void OnDelete() - { - base.OnDelete(); + item.Map = Map; + } + } - if ( m_Components == null ) - return; + public override void OnDelete() + { + base.OnDelete(); - for ( int i = 0; i < m_Components.Count; ++i ) - { - Item item = m_Components[i]; + if (m_Components == null) + return; - item.Delete(); - } - } + for (int i = 0; i < m_Components.Count; ++i) + { + Item item = m_Components[i]; - public override void OnAfterDelete() - { - m_Timer?.Stop(); + item.Delete(); + } + } - m_Timer = null; + public override void OnAfterDelete() + { + m_Timer?.Stop(); - base.OnAfterDelete(); - } + m_Timer = null; - public PreviewHouse( Serial serial ) : base( serial ) - { - } + base.OnAfterDelete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Components ); - } + writer.Write(m_Components); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Components = reader.ReadStrongItemList(); + switch (version) + { + case 0: + { + m_Components = reader.ReadStrongItemList(); - break; - } - } + break; + } + } - Timer.DelayCall( TimeSpan.Zero, Delete ); - } + Timer.DelayCall(TimeSpan.Zero, Delete); + } - private class DecayTimer : Timer - { - private Item m_Item; + private class DecayTimer : Timer + { + private Item m_Item; - public DecayTimer( Item item ) : base( TimeSpan.FromSeconds( 20.0 ) ) - { - m_Item = item; - Priority = TimerPriority.OneSecond; - } + public DecayTimer(Item item) : base(TimeSpan.FromSeconds(20.0)) + { + m_Item = item; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - m_Item.Delete(); - } - } - } -} + protected override void OnTick() + { + m_Item.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Properties/AssemblyInfo.cs b/Scripts/Properties/AssemblyInfo.cs index 6c8942688..3a630d815 100644 --- a/Scripts/Properties/AssemblyInfo.cs +++ b/Scripts/Properties/AssemblyInfo.cs @@ -29,4 +29,4 @@ using System.Runtime.InteropServices; // Revision // [assembly: AssemblyVersion("0.0.0.1")] -[assembly: AssemblyFileVersion("0.0.0.1")] +[assembly: AssemblyFileVersion("0.0.0.1")] \ No newline at end of file diff --git a/Scripts/Regions/BaseRegion.cs b/Scripts/Regions/BaseRegion.cs index 1dfa7aa3e..ceff32a5e 100644 --- a/Scripts/Regions/BaseRegion.cs +++ b/Scripts/Regions/BaseRegion.cs @@ -1,557 +1,555 @@ using System; using System.Collections.Generic; using System.Xml; +using Server.Gumps; using Server.Items; using Server.Mobiles; -using Server.Gumps; namespace Server.Regions { - public enum SpawnZLevel - { - Lowest, - Highest, - Random - } - - public class BaseRegion : Region - { - public virtual bool YoungProtected => true; - public virtual bool YoungMayEnter => true; - public virtual bool MountsAllowed => true; - public virtual bool DeadMayEnter => true; - public virtual bool ResurrectionAllowed => true; - public virtual bool LogoutAllowed => true; - - public static void Configure() - { - DefaultRegionType = typeof( BaseRegion ); - } - - private string m_RuneName; - - private SpawnEntry[] m_Spawns; - private bool m_ExcludeFromParentSpawns; - - public string RuneName{ get => m_RuneName; - set => m_RuneName = value; - } - - public bool NoLogoutDelay { get; set; } - - public SpawnEntry[] Spawns - { - get => m_Spawns; - set - { - if ( m_Spawns != null ) - { - for ( int i = 0; i < m_Spawns.Length; i++ ) - m_Spawns[i].Delete(); - } - - m_Spawns = value; - } - } - - public SpawnZLevel SpawnZLevel { get; set; } - - public bool ExcludeFromParentSpawns{ get => m_ExcludeFromParentSpawns; - set => m_ExcludeFromParentSpawns = value; - } - - public override void OnUnregister() - { - base.OnUnregister(); - - Spawns = null; - } - - public static string GetRuneNameFor( Region region ) - { - while ( region != null ) - { - BaseRegion br = region as BaseRegion; - - if ( br?.m_RuneName != null ) - return br.m_RuneName; - - region = region.Parent; - } - - return null; - } - - public override TimeSpan GetLogoutDelay( Mobile m ) - { - if ( NoLogoutDelay ) - { - if ( m.Aggressors.Count == 0 && m.Aggressed.Count == 0 && !m.Criminal ) - return TimeSpan.Zero; - } - - return base.GetLogoutDelay( m ); - } - - public static bool CanSpawn( Region region, params Type[] types ) - { - while ( region != null ) - { - if ( !region.AllowSpawn() ) - return false; - - if ( region is BaseRegion br ) - { - if ( br.Spawns != null ) - { - for ( int i = 0; i < br.Spawns.Length; i++ ) - { - SpawnEntry entry = br.Spawns[i]; - - if ( entry.Definition.CanSpawn( types ) ) - return true; - } - } - - if ( br.ExcludeFromParentSpawns ) - return false; - } - - region = region.Parent; - } - - return false; - } - - public override void OnEnter(Mobile m) - { - if (m is PlayerMobile mobile && mobile.Young) - { - if (!YoungProtected) - { - mobile.SendGump(new YoungDungeonWarning()); - } - } - } - - public override bool AcceptsSpawnsFrom( Region region ) - { - if ( region == this || !m_ExcludeFromParentSpawns ) - return base.AcceptsSpawnsFrom( region ); - - return false; - } - - private Rectangle3D[] m_Rectangles; - private int[] m_RectangleWeights; - private int m_TotalWeight; - - private static List m_RectBuffer1 = new List(); - private static List m_RectBuffer2 = new List(); - - private void InitRectangles() - { - if ( m_Rectangles != null ) - return; - - // Test if area rectangles are overlapping, and in that case break them into smaller non overlapping rectangles - for ( int i = 0; i < Area.Length; i++ ) - { - m_RectBuffer2.Add( Area[i] ); - - for ( int j = 0; j < m_RectBuffer1.Count && m_RectBuffer2.Count > 0; j++ ) - { - Rectangle3D comp = m_RectBuffer1[j]; - - for ( int k = m_RectBuffer2.Count - 1; k >= 0; k-- ) - { - Rectangle3D rect = m_RectBuffer2[k]; - - int l1 = rect.Start.X, r1 = rect.End.X, t1 = rect.Start.Y, b1 = rect.End.Y; - int l2 = comp.Start.X, r2 = comp.End.X, t2 = comp.Start.Y, b2 = comp.End.Y; - - if ( l1 < r2 && r1 > l2 && t1 < b2 && b1 > t2 ) - { - m_RectBuffer2.RemoveAt( k ); - - int sz = rect.Start.Z; - int ez = rect.End.X; - - if ( l1 < l2 ) - { - m_RectBuffer2.Add( new Rectangle3D( new Point3D( l1, t1, sz ), new Point3D( l2, b1, ez ) ) ); - } - - if ( r1 > r2 ) - { - m_RectBuffer2.Add( new Rectangle3D( new Point3D( r2, t1, sz ), new Point3D( r1, b1, ez ) ) ); - } - - if ( t1 < t2 ) - { - m_RectBuffer2.Add( new Rectangle3D( new Point3D( Math.Max( l1, l2 ), t1, sz ), new Point3D( Math.Min( r1, r2 ), t2, ez ) ) ); - } - - if ( b1 > b2 ) - { - m_RectBuffer2.Add( new Rectangle3D( new Point3D( Math.Max( l1, l2 ), b2, sz ), new Point3D( Math.Min( r1, r2 ), b1, ez ) ) ); - } - } - } - } - - m_RectBuffer1.AddRange( m_RectBuffer2 ); - m_RectBuffer2.Clear(); - } - - m_Rectangles = m_RectBuffer1.ToArray(); - m_RectBuffer1.Clear(); - - m_RectangleWeights = new int[m_Rectangles.Length]; - for ( int i = 0; i < m_Rectangles.Length; i++ ) - { - Rectangle3D rect = m_Rectangles[i]; - int weight = rect.Width * rect.Height; - - m_RectangleWeights[i] = weight; - m_TotalWeight += weight; - } - } - - private static List m_SpawnBuffer1 = new List(); - private static List m_SpawnBuffer2 = new List(); - - public Point3D RandomSpawnLocation( int spawnHeight, bool land, bool water, Point3D home, int range ) - { - Map map = Map; - - if ( map == Map.Internal ) - return Point3D.Zero; - - InitRectangles(); - - if ( m_TotalWeight <= 0 ) - return Point3D.Zero; - - for ( int i = 0; i < 10; i++ ) // Try 10 times - { - int x, y, minZ, maxZ; - - if ( home == Point3D.Zero ) - { - int rand = Utility.Random( m_TotalWeight ); - - x = int.MinValue; y = int.MinValue; - minZ = int.MaxValue; maxZ = int.MinValue; - for ( int j = 0; j < m_RectangleWeights.Length; j++ ) - { - int curWeight = m_RectangleWeights[j]; - - if ( rand < curWeight ) - { - Rectangle3D rect = m_Rectangles[j]; - - x = rect.Start.X + rand % rect.Width; - y = rect.Start.Y + rand / rect.Width; - - minZ = rect.Start.Z; - maxZ = rect.End.Z; - - break; - } - - rand -= curWeight; - } - } - else - { - x = Utility.RandomMinMax( home.X - range, home.X + range ); - y = Utility.RandomMinMax( home.Y - range, home.Y + range ); - - minZ = int.MaxValue; maxZ = int.MinValue; - for ( int j = 0; j < Area.Length; j++ ) - { - Rectangle3D rect = Area[j]; - - if ( x >= rect.Start.X && x < rect.End.X && y >= rect.Start.Y && y < rect.End.Y ) - { - minZ = rect.Start.Z; - maxZ = rect.End.Z; - break; - } - } - - if ( minZ == int.MaxValue ) - continue; - } - - if ( x < 0 || y < 0 || x >= map.Width || y >= map.Height ) - continue; - - LandTile lt = map.Tiles.GetLandTile( x, y ); - - int ltLowZ = 0, ltAvgZ = 0, ltTopZ = 0; - map.GetAverageZ( x, y, ref ltLowZ, ref ltAvgZ, ref ltTopZ ); - - TileFlag ltFlags = TileData.LandTable[lt.ID & TileData.MaxLandValue].Flags; - bool ltImpassable = ( (ltFlags & TileFlag.Impassable) != 0 ); - - if ( !lt.Ignored && ltAvgZ >= minZ && ltAvgZ < maxZ ) - if ( (ltFlags & TileFlag.Wet) != 0 ) { - if ( water ) - m_SpawnBuffer1.Add( ltAvgZ ); - } - else if ( land && !ltImpassable ) - m_SpawnBuffer1.Add( ltAvgZ ); - - StaticTile[] staticTiles = map.Tiles.GetStaticTiles( x, y, true ); - - for ( int j = 0; j < staticTiles.Length; j++ ) - { - StaticTile tile = staticTiles[j]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - int tileZ = tile.Z + id.CalcHeight; - - if ( tileZ >= minZ && tileZ < maxZ ) - if ( (id.Flags & TileFlag.Wet) != 0 ) { - if ( water ) - m_SpawnBuffer1.Add( tileZ ); - } - else if ( land && id.Surface && !id.Impassable ) - m_SpawnBuffer1.Add( tileZ ); - } - - - Sector sector = map.GetSector( x, y ); - - for ( int j = 0; j < sector.Items.Count; j++ ) - { - Item item = sector.Items[j]; - - if ( !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint( x, y ) ) - { - m_SpawnBuffer2.Add( item ); - - if ( !item.Movable ) - { - ItemData id = item.ItemData; - int itemZ = item.Z + id.CalcHeight; - - if ( itemZ >= minZ && itemZ < maxZ ) - if ( (id.Flags & TileFlag.Wet) != 0 ) { - if ( water ) - m_SpawnBuffer1.Add( itemZ ); - } - else if ( land && id.Surface && !id.Impassable ) - m_SpawnBuffer1.Add( itemZ ); - } - } - } - - - if ( m_SpawnBuffer1.Count == 0 ) - { - m_SpawnBuffer1.Clear(); - m_SpawnBuffer2.Clear(); - continue; - } - - int z; - switch ( SpawnZLevel ) - { - case SpawnZLevel.Lowest: - { - z = int.MaxValue; - - for ( int j = 0; j < m_SpawnBuffer1.Count; j++ ) - { - int l = m_SpawnBuffer1[j]; - - if ( l < z ) - z = l; - } - - break; - } - case SpawnZLevel.Highest: - { - z = int.MinValue; - - for ( int j = 0; j < m_SpawnBuffer1.Count; j++ ) - { - int l = m_SpawnBuffer1[j]; - - if ( l > z ) - z = l; - } - - break; - } - default: // SpawnZLevel.Random - { - int index = Utility.Random( m_SpawnBuffer1.Count ); - z = m_SpawnBuffer1[index]; - - break; - } - } - - m_SpawnBuffer1.Clear(); - - - if ( !Find( new Point3D( x, y, z ), map ).AcceptsSpawnsFrom( this ) ) - { - m_SpawnBuffer2.Clear(); - continue; - } - - int top = z + spawnHeight; - - bool ok = true; - for ( int j = 0; j < m_SpawnBuffer2.Count; j++ ) - { - Item item = m_SpawnBuffer2[j]; - ItemData id = item.ItemData; - - if ( ( id.Surface || id.Impassable ) && item.Z + id.CalcHeight > z && item.Z < top ) - { - ok = false; - break; - } - } - - m_SpawnBuffer2.Clear(); - - if ( !ok ) - continue; - - if ( ltImpassable && ltAvgZ > z && ltLowZ < top ) - continue; - - for ( int j = 0; j < staticTiles.Length; j++ ) - { - StaticTile tile = staticTiles[j]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - - if ( ( id.Surface || id.Impassable ) && tile.Z + id.CalcHeight > z && tile.Z < top ) - { - ok = false; - break; - } - } - - if ( !ok ) - continue; - - for ( int j = 0; j < sector.Mobiles.Count; j++ ) - { - Mobile m = sector.Mobiles[j]; - - if ( m.X == x && m.Y == y && ( m.AccessLevel == AccessLevel.Player || !m.Hidden ) ) - if ( m.Z + 16 > z && m.Z < top ) - { - ok = false; - break; - } - } - - if ( ok ) - return new Point3D( x, y, z ); - } - - return Point3D.Zero; - } - - public override string ToString() - { - if ( Name != null ) - return Name; - if ( RuneName != null ) - return RuneName; - return GetType().Name; - } - - public BaseRegion( string name, Map map, int priority, params Rectangle2D[] area ) : base( name, map, priority, area ) - { - } - - public BaseRegion( string name, Map map, int priority, params Rectangle3D[] area ) : base( name, map, priority, area ) - { - } - - public BaseRegion( string name, Map map, Region parent, params Rectangle2D[] area ) : base( name, map, parent, area ) - { - } - - public BaseRegion( string name, Map map, Region parent, params Rectangle3D[] area ) : base( name, map, parent, area ) - { - } - - public BaseRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - ReadString( xml["rune"], "name", ref m_RuneName, false ); - - bool logoutDelayActive = true; - ReadBoolean( xml["logoutDelay"], "active", ref logoutDelayActive, false ); - NoLogoutDelay = !logoutDelayActive; - - - XmlElement spawning = xml["spawning"]; - if ( spawning != null ) - { - ReadBoolean( spawning, "excludeFromParent", ref m_ExcludeFromParentSpawns, false ); - - SpawnZLevel zLevel = SpawnZLevel.Lowest; - ReadEnum( spawning, "zLevel", ref zLevel, false ); - SpawnZLevel = zLevel; - - - List list = new List(); - - foreach ( XmlNode node in spawning.ChildNodes ) - { - XmlElement el = node as XmlElement; - - if ( el != null ) - { - SpawnDefinition def = SpawnDefinition.GetSpawnDefinition( el ); - if ( def == null ) - continue; - - int id = 0; - if ( !ReadInt32( el, "id", ref id, true ) ) - continue; - - int amount = 0; - if ( !ReadInt32( el, "amount", ref amount, true ) ) - continue; - - TimeSpan minSpawnTime = SpawnEntry.DefaultMinSpawnTime; - ReadTimeSpan( el, "minSpawnTime", ref minSpawnTime, false ); - - TimeSpan maxSpawnTime = SpawnEntry.DefaultMaxSpawnTime; - ReadTimeSpan( el, "maxSpawnTime", ref maxSpawnTime, false ); - - Point3D home = Point3D.Zero; - int range = 0; - - XmlElement homeEl = el["home"]; - if ( ReadPoint3D( homeEl, map, ref home, false ) ) - ReadInt32( homeEl, "range", ref range, false ); - - Direction dir = SpawnEntry.InvalidDirection; - ReadEnum( el["direction"], "value" , ref dir, false ); - - SpawnEntry entry = new SpawnEntry( id, this, home, range, dir, def, amount, minSpawnTime, maxSpawnTime ); - list.Add( entry ); - } - } - - if ( list.Count > 0 ) - { - m_Spawns = list.ToArray(); - } - } - } - } -} + public enum SpawnZLevel + { + Lowest, + Highest, + Random + } + + public class BaseRegion : Region + { + private static List m_RectBuffer1 = new List(); + private static List m_RectBuffer2 = new List(); + + private static List m_SpawnBuffer1 = new List(); + private static List m_SpawnBuffer2 = new List(); + private bool m_ExcludeFromParentSpawns; + + private Rectangle3D[] m_Rectangles; + private int[] m_RectangleWeights; + + private string m_RuneName; + + private SpawnEntry[] m_Spawns; + private int m_TotalWeight; + + public BaseRegion(string name, Map map, int priority, params Rectangle2D[] area) : base(name, map, priority, area) + { + } + + public BaseRegion(string name, Map map, int priority, params Rectangle3D[] area) : base(name, map, priority, area) + { + } + + public BaseRegion(string name, Map map, Region parent, params Rectangle2D[] area) : base(name, map, parent, area) + { + } + + public BaseRegion(string name, Map map, Region parent, params Rectangle3D[] area) : base(name, map, parent, area) + { + } + + public BaseRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + ReadString(xml["rune"], "name", ref m_RuneName, false); + + bool logoutDelayActive = true; + ReadBoolean(xml["logoutDelay"], "active", ref logoutDelayActive, false); + NoLogoutDelay = !logoutDelayActive; + + + XmlElement spawning = xml["spawning"]; + if (spawning != null) + { + ReadBoolean(spawning, "excludeFromParent", ref m_ExcludeFromParentSpawns, false); + + SpawnZLevel zLevel = SpawnZLevel.Lowest; + ReadEnum(spawning, "zLevel", ref zLevel, false); + SpawnZLevel = zLevel; + + + List list = new List(); + + foreach (XmlNode node in spawning.ChildNodes) + { + XmlElement el = node as XmlElement; + + if (el != null) + { + SpawnDefinition def = SpawnDefinition.GetSpawnDefinition(el); + if (def == null) + continue; + + int id = 0; + if (!ReadInt32(el, "id", ref id, true)) + continue; + + int amount = 0; + if (!ReadInt32(el, "amount", ref amount, true)) + continue; + + TimeSpan minSpawnTime = SpawnEntry.DefaultMinSpawnTime; + ReadTimeSpan(el, "minSpawnTime", ref minSpawnTime, false); + + TimeSpan maxSpawnTime = SpawnEntry.DefaultMaxSpawnTime; + ReadTimeSpan(el, "maxSpawnTime", ref maxSpawnTime, false); + + Point3D home = Point3D.Zero; + int range = 0; + + XmlElement homeEl = el["home"]; + if (ReadPoint3D(homeEl, map, ref home, false)) + ReadInt32(homeEl, "range", ref range, false); + + Direction dir = SpawnEntry.InvalidDirection; + ReadEnum(el["direction"], "value", ref dir, false); + + SpawnEntry entry = new SpawnEntry(id, this, home, range, dir, def, amount, minSpawnTime, + maxSpawnTime); + list.Add(entry); + } + } + + if (list.Count > 0) m_Spawns = list.ToArray(); + } + } + + public virtual bool YoungProtected => true; + public virtual bool YoungMayEnter => true; + public virtual bool MountsAllowed => true; + public virtual bool DeadMayEnter => true; + public virtual bool ResurrectionAllowed => true; + public virtual bool LogoutAllowed => true; + + public string RuneName + { + get => m_RuneName; + set => m_RuneName = value; + } + + public bool NoLogoutDelay{ get; set; } + + public SpawnEntry[] Spawns + { + get => m_Spawns; + set + { + if (m_Spawns != null) + for (int i = 0; i < m_Spawns.Length; i++) + m_Spawns[i].Delete(); + + m_Spawns = value; + } + } + + public SpawnZLevel SpawnZLevel{ get; set; } + + public bool ExcludeFromParentSpawns + { + get => m_ExcludeFromParentSpawns; + set => m_ExcludeFromParentSpawns = value; + } + + public static void Configure() + { + DefaultRegionType = typeof(BaseRegion); + } + + public override void OnUnregister() + { + base.OnUnregister(); + + Spawns = null; + } + + public static string GetRuneNameFor(Region region) + { + while (region != null) + { + BaseRegion br = region as BaseRegion; + + if (br?.m_RuneName != null) + return br.m_RuneName; + + region = region.Parent; + } + + return null; + } + + public override TimeSpan GetLogoutDelay(Mobile m) + { + if (NoLogoutDelay) + if (m.Aggressors.Count == 0 && m.Aggressed.Count == 0 && !m.Criminal) + return TimeSpan.Zero; + + return base.GetLogoutDelay(m); + } + + public static bool CanSpawn(Region region, params Type[] types) + { + while (region != null) + { + if (!region.AllowSpawn()) + return false; + + if (region is BaseRegion br) + { + if (br.Spawns != null) + for (int i = 0; i < br.Spawns.Length; i++) + { + SpawnEntry entry = br.Spawns[i]; + + if (entry.Definition.CanSpawn(types)) + return true; + } + + if (br.ExcludeFromParentSpawns) + return false; + } + + region = region.Parent; + } + + return false; + } + + public override void OnEnter(Mobile m) + { + if (m is PlayerMobile mobile && mobile.Young) + if (!YoungProtected) + mobile.SendGump(new YoungDungeonWarning()); + } + + public override bool AcceptsSpawnsFrom(Region region) + { + if (region == this || !m_ExcludeFromParentSpawns) + return base.AcceptsSpawnsFrom(region); + + return false; + } + + private void InitRectangles() + { + if (m_Rectangles != null) + return; + + // Test if area rectangles are overlapping, and in that case break them into smaller non overlapping rectangles + for (int i = 0; i < Area.Length; i++) + { + m_RectBuffer2.Add(Area[i]); + + for (int j = 0; j < m_RectBuffer1.Count && m_RectBuffer2.Count > 0; j++) + { + Rectangle3D comp = m_RectBuffer1[j]; + + for (int k = m_RectBuffer2.Count - 1; k >= 0; k--) + { + Rectangle3D rect = m_RectBuffer2[k]; + + int l1 = rect.Start.X, r1 = rect.End.X, t1 = rect.Start.Y, b1 = rect.End.Y; + int l2 = comp.Start.X, r2 = comp.End.X, t2 = comp.Start.Y, b2 = comp.End.Y; + + if (l1 < r2 && r1 > l2 && t1 < b2 && b1 > t2) + { + m_RectBuffer2.RemoveAt(k); + + int sz = rect.Start.Z; + int ez = rect.End.X; + + if (l1 < l2) + m_RectBuffer2.Add(new Rectangle3D(new Point3D(l1, t1, sz), new Point3D(l2, b1, ez))); + + if (r1 > r2) + m_RectBuffer2.Add(new Rectangle3D(new Point3D(r2, t1, sz), new Point3D(r1, b1, ez))); + + if (t1 < t2) + m_RectBuffer2.Add(new Rectangle3D(new Point3D(Math.Max(l1, l2), t1, sz), + new Point3D(Math.Min(r1, r2), t2, ez))); + + if (b1 > b2) + m_RectBuffer2.Add(new Rectangle3D(new Point3D(Math.Max(l1, l2), b2, sz), + new Point3D(Math.Min(r1, r2), b1, ez))); + } + } + } + + m_RectBuffer1.AddRange(m_RectBuffer2); + m_RectBuffer2.Clear(); + } + + m_Rectangles = m_RectBuffer1.ToArray(); + m_RectBuffer1.Clear(); + + m_RectangleWeights = new int[m_Rectangles.Length]; + for (int i = 0; i < m_Rectangles.Length; i++) + { + Rectangle3D rect = m_Rectangles[i]; + int weight = rect.Width * rect.Height; + + m_RectangleWeights[i] = weight; + m_TotalWeight += weight; + } + } + + public Point3D RandomSpawnLocation(int spawnHeight, bool land, bool water, Point3D home, int range) + { + Map map = Map; + + if (map == Map.Internal) + return Point3D.Zero; + + InitRectangles(); + + if (m_TotalWeight <= 0) + return Point3D.Zero; + + for (int i = 0; i < 10; i++) // Try 10 times + { + int x, y, minZ, maxZ; + + if (home == Point3D.Zero) + { + int rand = Utility.Random(m_TotalWeight); + + x = int.MinValue; + y = int.MinValue; + minZ = int.MaxValue; + maxZ = int.MinValue; + for (int j = 0; j < m_RectangleWeights.Length; j++) + { + int curWeight = m_RectangleWeights[j]; + + if (rand < curWeight) + { + Rectangle3D rect = m_Rectangles[j]; + + x = rect.Start.X + rand % rect.Width; + y = rect.Start.Y + rand / rect.Width; + + minZ = rect.Start.Z; + maxZ = rect.End.Z; + + break; + } + + rand -= curWeight; + } + } + else + { + x = Utility.RandomMinMax(home.X - range, home.X + range); + y = Utility.RandomMinMax(home.Y - range, home.Y + range); + + minZ = int.MaxValue; + maxZ = int.MinValue; + for (int j = 0; j < Area.Length; j++) + { + Rectangle3D rect = Area[j]; + + if (x >= rect.Start.X && x < rect.End.X && y >= rect.Start.Y && y < rect.End.Y) + { + minZ = rect.Start.Z; + maxZ = rect.End.Z; + break; + } + } + + if (minZ == int.MaxValue) + continue; + } + + if (x < 0 || y < 0 || x >= map.Width || y >= map.Height) + continue; + + LandTile lt = map.Tiles.GetLandTile(x, y); + + int ltLowZ = 0, ltAvgZ = 0, ltTopZ = 0; + map.GetAverageZ(x, y, ref ltLowZ, ref ltAvgZ, ref ltTopZ); + + TileFlag ltFlags = TileData.LandTable[lt.ID & TileData.MaxLandValue].Flags; + bool ltImpassable = (ltFlags & TileFlag.Impassable) != 0; + + if (!lt.Ignored && ltAvgZ >= minZ && ltAvgZ < maxZ) + if ((ltFlags & TileFlag.Wet) != 0) + { + if (water) + m_SpawnBuffer1.Add(ltAvgZ); + } + else if (land && !ltImpassable) + { + m_SpawnBuffer1.Add(ltAvgZ); + } + + StaticTile[] staticTiles = map.Tiles.GetStaticTiles(x, y, true); + + for (int j = 0; j < staticTiles.Length; j++) + { + StaticTile tile = staticTiles[j]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + int tileZ = tile.Z + id.CalcHeight; + + if (tileZ >= minZ && tileZ < maxZ) + if ((id.Flags & TileFlag.Wet) != 0) + { + if (water) + m_SpawnBuffer1.Add(tileZ); + } + else if (land && id.Surface && !id.Impassable) + { + m_SpawnBuffer1.Add(tileZ); + } + } + + + Sector sector = map.GetSector(x, y); + + for (int j = 0; j < sector.Items.Count; j++) + { + Item item = sector.Items[j]; + + if (!(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint(x, y)) + { + m_SpawnBuffer2.Add(item); + + if (!item.Movable) + { + ItemData id = item.ItemData; + int itemZ = item.Z + id.CalcHeight; + + if (itemZ >= minZ && itemZ < maxZ) + if ((id.Flags & TileFlag.Wet) != 0) + { + if (water) + m_SpawnBuffer1.Add(itemZ); + } + else if (land && id.Surface && !id.Impassable) + { + m_SpawnBuffer1.Add(itemZ); + } + } + } + } + + + if (m_SpawnBuffer1.Count == 0) + { + m_SpawnBuffer1.Clear(); + m_SpawnBuffer2.Clear(); + continue; + } + + int z; + switch (SpawnZLevel) + { + case SpawnZLevel.Lowest: + { + z = int.MaxValue; + + for (int j = 0; j < m_SpawnBuffer1.Count; j++) + { + int l = m_SpawnBuffer1[j]; + + if (l < z) + z = l; + } + + break; + } + case SpawnZLevel.Highest: + { + z = int.MinValue; + + for (int j = 0; j < m_SpawnBuffer1.Count; j++) + { + int l = m_SpawnBuffer1[j]; + + if (l > z) + z = l; + } + + break; + } + default: // SpawnZLevel.Random + { + int index = Utility.Random(m_SpawnBuffer1.Count); + z = m_SpawnBuffer1[index]; + + break; + } + } + + m_SpawnBuffer1.Clear(); + + + if (!Find(new Point3D(x, y, z), map).AcceptsSpawnsFrom(this)) + { + m_SpawnBuffer2.Clear(); + continue; + } + + int top = z + spawnHeight; + + bool ok = true; + for (int j = 0; j < m_SpawnBuffer2.Count; j++) + { + Item item = m_SpawnBuffer2[j]; + ItemData id = item.ItemData; + + if ((id.Surface || id.Impassable) && item.Z + id.CalcHeight > z && item.Z < top) + { + ok = false; + break; + } + } + + m_SpawnBuffer2.Clear(); + + if (!ok) + continue; + + if (ltImpassable && ltAvgZ > z && ltLowZ < top) + continue; + + for (int j = 0; j < staticTiles.Length; j++) + { + StaticTile tile = staticTiles[j]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + + if ((id.Surface || id.Impassable) && tile.Z + id.CalcHeight > z && tile.Z < top) + { + ok = false; + break; + } + } + + if (!ok) + continue; + + for (int j = 0; j < sector.Mobiles.Count; j++) + { + Mobile m = sector.Mobiles[j]; + + if (m.X == x && m.Y == y && (m.AccessLevel == AccessLevel.Player || !m.Hidden)) + if (m.Z + 16 > z && m.Z < top) + { + ok = false; + break; + } + } + + if (ok) + return new Point3D(x, y, z); + } + + return Point3D.Zero; + } + + public override string ToString() + { + if (Name != null) + return Name; + if (RuneName != null) + return RuneName; + return GetType().Name; + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/DungeonRegion.cs b/Scripts/Regions/DungeonRegion.cs index 92ffb7ced..e1730cb0e 100644 --- a/Scripts/Regions/DungeonRegion.cs +++ b/Scripts/Regions/DungeonRegion.cs @@ -2,44 +2,47 @@ using System.Xml; namespace Server.Regions { - public class DungeonRegion : BaseRegion - { - public override bool YoungProtected => false; + public class DungeonRegion : BaseRegion + { + private Point3D m_EntranceLocation; - private Point3D m_EntranceLocation; + public DungeonRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + XmlElement entrEl = xml["entrance"]; - public Point3D EntranceLocation{ get => m_EntranceLocation; - set => m_EntranceLocation = value; - } - public Map EntranceMap { get; set; } + Map entrMap = map; + ReadMap(entrEl, "map", ref entrMap, false); - public DungeonRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - XmlElement entrEl = xml["entrance"]; + if (ReadPoint3D(entrEl, entrMap, ref m_EntranceLocation, false)) + EntranceMap = entrMap; + } - Map entrMap = map; - ReadMap( entrEl, "map", ref entrMap, false ); + public override bool YoungProtected => false; - if ( ReadPoint3D( entrEl, entrMap, ref m_EntranceLocation, false ) ) - EntranceMap = entrMap; - } + public Point3D EntranceLocation + { + get => m_EntranceLocation; + set => m_EntranceLocation = value; + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } + public Map EntranceMap{ get; set; } - public override void AlterLightLevel( Mobile m, ref int global, ref int personal ) - { - global = LightCycle.DungeonLevel; - } + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } - public override bool CanUseStuckMenu( Mobile m ) - { - if ( Map == Map.Felucca ) - return false; + public override void AlterLightLevel(Mobile m, ref int global, ref int personal) + { + global = LightCycle.DungeonLevel; + } - return base.CanUseStuckMenu( m ); - } - } -} + public override bool CanUseStuckMenu(Mobile m) + { + if (Map == Map.Felucca) + return false; + + return base.CanUseStuckMenu(m); + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/GreenAcres.cs b/Scripts/Regions/GreenAcres.cs index 9cf089cc1..b5003a3b1 100644 --- a/Scripts/Regions/GreenAcres.cs +++ b/Scripts/Regions/GreenAcres.cs @@ -1,33 +1,34 @@ using System.Xml; -using Server.Spells.Seventh; -using Server.Spells.Fourth; -using Server.Spells.Sixth; using Server.Spells.Chivalry; +using Server.Spells.Fourth; +using Server.Spells.Seventh; +using Server.Spells.Sixth; namespace Server.Regions { - public class GreenAcres : BaseRegion - { - public GreenAcres( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - } + public class GreenAcres : BaseRegion + { + public GreenAcres(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - if ( from.AccessLevel == AccessLevel.Player ) - return false; - return base.AllowHousing( from, p ); - } + public override bool AllowHousing(Mobile from, Point3D p) + { + if (from.AccessLevel == AccessLevel.Player) + return false; + return base.AllowHousing(from, p); + } - public override bool OnBeginSpellCast( Mobile m, ISpell s ) - { - if ( ( s is GateTravelSpell || s is RecallSpell || s is MarkSpell || s is SacredJourneySpell ) && m.AccessLevel == AccessLevel.Player ) - { - m.SendMessage( "You cannot cast that spell here." ); - return false; - } + public override bool OnBeginSpellCast(Mobile m, ISpell s) + { + if ((s is GateTravelSpell || s is RecallSpell || s is MarkSpell || s is SacredJourneySpell) && + m.AccessLevel == AccessLevel.Player) + { + m.SendMessage("You cannot cast that spell here."); + return false; + } - return base.OnBeginSpellCast( m, s ); - } - } -} + return base.OnBeginSpellCast(m, s); + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/GuardedRegion.cs b/Scripts/Regions/GuardedRegion.cs index dcf62da8c..e143da72c 100644 --- a/Scripts/Regions/GuardedRegion.cs +++ b/Scripts/Regions/GuardedRegion.cs @@ -6,363 +6,369 @@ using Server.Mobiles; namespace Server.Regions { - public class GuardedRegion : BaseRegion - { - private static object[] m_GuardParams = new object[1]; - private Type m_GuardType; - - public bool Disabled { get; set; } - - public virtual bool IsDisabled() - { - return Disabled; - } - - public static void Initialize() - { - CommandSystem.Register( "CheckGuarded", AccessLevel.GameMaster, CheckGuarded_OnCommand ); - CommandSystem.Register( "SetGuarded", AccessLevel.Administrator, SetGuarded_OnCommand ); - CommandSystem.Register( "ToggleGuarded", AccessLevel.Administrator, ToggleGuarded_OnCommand ); - } - - [Usage( "CheckGuarded" )] - [Description( "Returns a value indicating if the current region is guarded or not." )] - private static void CheckGuarded_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; - GuardedRegion reg = (GuardedRegion) from.Region.GetRegion( typeof( GuardedRegion ) ); - - if ( reg == null ) - from.SendMessage( "You are not in a guardable region." ); - else if ( reg.Disabled ) - from.SendMessage( "The guards in this region have been disabled." ); - else - from.SendMessage( "This region is actively guarded." ); - } - - [Usage( "SetGuarded " )] - [Description( "Enables or disables guards for the current region." )] - private static void SetGuarded_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; - - if ( e.Length == 1 ) - { - GuardedRegion reg = (GuardedRegion) from.Region.GetRegion( typeof( GuardedRegion ) ); - - if ( reg == null ) - { - from.SendMessage( "You are not in a guardable region." ); - } - else - { - reg.Disabled = !e.GetBoolean( 0 ); - - if ( reg.Disabled ) - from.SendMessage( "The guards in this region have been disabled." ); - else - from.SendMessage( "The guards in this region have been enabled." ); - } - } - else - { - from.SendMessage( "Format: SetGuarded " ); - } - } - - [Usage( "ToggleGuarded" )] - [Description( "Toggles the state of guards for the current region." )] - private static void ToggleGuarded_OnCommand( CommandEventArgs e ) - { - Mobile from = e.Mobile; - GuardedRegion reg = (GuardedRegion) from.Region.GetRegion( typeof( GuardedRegion ) ); - - if ( reg == null ) - { - from.SendMessage( "You are not in a guardable region." ); - } - else - { - reg.Disabled = !reg.Disabled; - - if ( reg.Disabled ) - from.SendMessage( "The guards in this region have been disabled." ); - else - from.SendMessage( "The guards in this region have been enabled." ); - } - } - - public static GuardedRegion Disable( GuardedRegion reg ) - { - reg.Disabled = true; - return reg; - } - - public virtual bool AllowReds => Core.AOS; - - public virtual bool CheckVendorAccess( BaseVendor vendor, Mobile from ) - { - if ( from.AccessLevel >= AccessLevel.GameMaster || IsDisabled() ) - return true; - - return ( from.Kills < 5 ); - } - - public virtual Type DefaultGuardType - { - get - { - if ( Map == Map.Ilshenar || Map == Map.Malas ) - return typeof( ArcherGuard ); - return typeof( WarriorGuard ); - } - } - - public GuardedRegion( string name, Map map, int priority, params Rectangle3D[] area ) : base( name, map, priority, area ) - { - m_GuardType = DefaultGuardType; - } - - public GuardedRegion( string name, Map map, int priority, params Rectangle2D[] area ) - : base( name, map, priority, area ) - { - m_GuardType = DefaultGuardType; - } - - public GuardedRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - XmlElement el = xml["guards"]; - - if ( ReadType( el, "type", ref m_GuardType, false ) ) - { - if ( !typeof( Mobile ).IsAssignableFrom( m_GuardType ) ) - { - Console.WriteLine( "Invalid guard type for region '{0}'", this ); - m_GuardType = DefaultGuardType; - } - } - else - { - m_GuardType = DefaultGuardType; - } - - bool disabled = false; - if ( ReadBoolean( el, "disabled", ref disabled, false ) ) - Disabled = disabled; - } - - public override bool OnBeginSpellCast( Mobile m, ISpell s ) - { - if ( !IsDisabled() && !s.OnCastInTown( this ) ) - { - m.SendLocalizedMessage( 500946 ); // You cannot cast this in town! - return false; - } - - return base.OnBeginSpellCast( m, s ); - } - - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } - - public override void MakeGuard( Mobile focus ) - { - BaseGuard useGuard = null; - - IPooledEnumerable eable = focus.GetMobilesInRange( 8 ); - foreach (BaseGuard m in eable) - { - if ( m.Focus == null ) // idling - { - useGuard = m; - break; - } - } - - eable.Free(); - - if ( useGuard == null ) - { - m_GuardParams[0] = focus; - - try { Activator.CreateInstance( m_GuardType, m_GuardParams ); } catch {} - } - else - useGuard.Focus = focus; - } - - public override void OnEnter( Mobile m ) - { - if ( IsDisabled() ) - return; - - if ( !AllowReds && m.Kills >= 5 ) - CheckGuardCandidate( m ); - } - - public override void OnExit( Mobile m ) - { - if ( IsDisabled() ) - return; - } - - public override void OnSpeech( SpeechEventArgs args ) - { - base.OnSpeech( args ); - - if ( IsDisabled() ) - return; - - if ( args.Mobile.Alive && args.HasKeyword( 0x0007 ) ) // *guards* - CallGuards( args.Mobile.Location ); - } - - public override void OnAggressed( Mobile aggressor, Mobile aggressed, bool criminal ) - { - base.OnAggressed( aggressor, aggressed, criminal ); - - if ( !IsDisabled() && aggressor != aggressed && criminal ) - CheckGuardCandidate( aggressor ); - } - - public override void OnGotBeneficialAction( Mobile helper, Mobile helped ) - { - base.OnGotBeneficialAction( helper, helped ); - - if ( IsDisabled() ) - return; - - int noto = Notoriety.Compute( helper, helped ); - - if ( helper != helped && (noto == Notoriety.Criminal || noto == Notoriety.Murderer) ) - CheckGuardCandidate( helper ); - } - - public override void OnCriminalAction( Mobile m, bool message ) - { - base.OnCriminalAction( m, message ); - - if ( !IsDisabled() ) - CheckGuardCandidate( m ); - } - - private Dictionary m_GuardCandidates = new Dictionary(); - - public void CheckGuardCandidate( Mobile m ) - { - if ( IsDisabled() ) - return; - - if ( IsGuardCandidate( m ) ) - { - m_GuardCandidates.TryGetValue( m, out GuardTimer timer ); - - if ( timer == null ) - { - timer = new GuardTimer( m, m_GuardCandidates ); - timer.Start(); - - m_GuardCandidates[m] = timer; - m.SendLocalizedMessage( 502275 ); // Guards can now be called on you! - - Map map = m.Map; - - if ( map != null ) - { - Mobile fakeCall = null; - double prio = 0.0; - - foreach ( Mobile v in m.GetMobilesInRange( 8 ) ) - { - if ( !v.Player && v != m && !IsGuardCandidate( v ) && ((v as BaseCreature)?.IsHumanInTown() ?? (v.Body.IsHuman && v.Region.IsPartOf( this ))) ) - { - double dist = m.GetDistanceToSqrt( v ); - - if ( fakeCall == null || dist < prio ) - { - fakeCall = v; - prio = dist; - } - } - } - - if ( fakeCall != null ) - { - fakeCall.Say( Utility.RandomList( 1007037, 501603, 1013037, 1013038, 1013039, 1013041, 1013042, 1013043, 1013052 ) ); - MakeGuard( m ); - timer.Stop(); - m_GuardCandidates.Remove( m ); - m.SendLocalizedMessage( 502276 ); // Guards can no longer be called on you. - } - } - } - else - { - timer.Stop(); - timer.Start(); - } - } - } - - public void CallGuards( Point3D p ) - { - if ( IsDisabled() ) - return; - - IPooledEnumerable eable = Map.GetMobilesInRange( p, 14 ); - - foreach ( Mobile m in eable ) - { - if ( IsGuardCandidate( m ) && ( ( !AllowReds && m.Kills >= 5 && m.Region.IsPartOf( this ) ) || m_GuardCandidates.ContainsKey( m ) ) ) - { - m_GuardCandidates.TryGetValue( m, out GuardTimer timer ); - - if ( timer != null ) - { - timer.Stop(); - m_GuardCandidates.Remove( m ); - } - - MakeGuard( m ); - m.SendLocalizedMessage( 502276 ); // Guards can no longer be called on you. - break; - } - } - - eable.Free(); - } - - public bool IsGuardCandidate( Mobile m ) - { - if ( m is BaseGuard || !m.Alive || m.AccessLevel > AccessLevel.Player || m.Blessed || ( m is BaseCreature && ((BaseCreature)m).IsInvulnerable ) || IsDisabled() ) - return false; - - return (!AllowReds && m.Kills >= 5) || m.Criminal; - } - - private class GuardTimer : Timer - { - private Mobile m_Mobile; - private Dictionary m_Table; - - public GuardTimer( Mobile m, Dictionary table ) : base( TimeSpan.FromSeconds( 15.0 ) ) - { - Priority = TimerPriority.TwoFiftyMS; - - m_Mobile = m; - m_Table = table; - } - - protected override void OnTick() - { - if ( m_Table.ContainsKey( m_Mobile ) ) - { - m_Table.Remove( m_Mobile ); - m_Mobile.SendLocalizedMessage( 502276 ); // Guards can no longer be called on you. - } - } - } - } -} + public class GuardedRegion : BaseRegion + { + private static object[] m_GuardParams = new object[1]; + + private Dictionary m_GuardCandidates = new Dictionary(); + private Type m_GuardType; + + public GuardedRegion(string name, Map map, int priority, params Rectangle3D[] area) : base(name, map, priority, area) + { + m_GuardType = DefaultGuardType; + } + + public GuardedRegion(string name, Map map, int priority, params Rectangle2D[] area) + : base(name, map, priority, area) + { + m_GuardType = DefaultGuardType; + } + + public GuardedRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + XmlElement el = xml["guards"]; + + if (ReadType(el, "type", ref m_GuardType, false)) + { + if (!typeof(Mobile).IsAssignableFrom(m_GuardType)) + { + Console.WriteLine("Invalid guard type for region '{0}'", this); + m_GuardType = DefaultGuardType; + } + } + else + { + m_GuardType = DefaultGuardType; + } + + bool disabled = false; + if (ReadBoolean(el, "disabled", ref disabled, false)) + Disabled = disabled; + } + + public bool Disabled{ get; set; } + + public virtual bool AllowReds => Core.AOS; + + public virtual Type DefaultGuardType + { + get + { + if (Map == Map.Ilshenar || Map == Map.Malas) + return typeof(ArcherGuard); + return typeof(WarriorGuard); + } + } + + public virtual bool IsDisabled() + { + return Disabled; + } + + public static void Initialize() + { + CommandSystem.Register("CheckGuarded", AccessLevel.GameMaster, CheckGuarded_OnCommand); + CommandSystem.Register("SetGuarded", AccessLevel.Administrator, SetGuarded_OnCommand); + CommandSystem.Register("ToggleGuarded", AccessLevel.Administrator, ToggleGuarded_OnCommand); + } + + [Usage("CheckGuarded")] + [Description("Returns a value indicating if the current region is guarded or not.")] + private static void CheckGuarded_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; + GuardedRegion reg = (GuardedRegion)from.Region.GetRegion(typeof(GuardedRegion)); + + if (reg == null) + from.SendMessage("You are not in a guardable region."); + else if (reg.Disabled) + from.SendMessage("The guards in this region have been disabled."); + else + from.SendMessage("This region is actively guarded."); + } + + [Usage("SetGuarded ")] + [Description("Enables or disables guards for the current region.")] + private static void SetGuarded_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; + + if (e.Length == 1) + { + GuardedRegion reg = (GuardedRegion)from.Region.GetRegion(typeof(GuardedRegion)); + + if (reg == null) + { + from.SendMessage("You are not in a guardable region."); + } + else + { + reg.Disabled = !e.GetBoolean(0); + + if (reg.Disabled) + from.SendMessage("The guards in this region have been disabled."); + else + from.SendMessage("The guards in this region have been enabled."); + } + } + else + { + from.SendMessage("Format: SetGuarded "); + } + } + + [Usage("ToggleGuarded")] + [Description("Toggles the state of guards for the current region.")] + private static void ToggleGuarded_OnCommand(CommandEventArgs e) + { + Mobile from = e.Mobile; + GuardedRegion reg = (GuardedRegion)from.Region.GetRegion(typeof(GuardedRegion)); + + if (reg == null) + { + from.SendMessage("You are not in a guardable region."); + } + else + { + reg.Disabled = !reg.Disabled; + + if (reg.Disabled) + from.SendMessage("The guards in this region have been disabled."); + else + from.SendMessage("The guards in this region have been enabled."); + } + } + + public static GuardedRegion Disable(GuardedRegion reg) + { + reg.Disabled = true; + return reg; + } + + public virtual bool CheckVendorAccess(BaseVendor vendor, Mobile from) + { + if (from.AccessLevel >= AccessLevel.GameMaster || IsDisabled()) + return true; + + return from.Kills < 5; + } + + public override bool OnBeginSpellCast(Mobile m, ISpell s) + { + if (!IsDisabled() && !s.OnCastInTown(this)) + { + m.SendLocalizedMessage(500946); // You cannot cast this in town! + return false; + } + + return base.OnBeginSpellCast(m, s); + } + + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } + + public override void MakeGuard(Mobile focus) + { + BaseGuard useGuard = null; + + IPooledEnumerable eable = focus.GetMobilesInRange(8); + foreach (BaseGuard m in eable) + if (m.Focus == null) // idling + { + useGuard = m; + break; + } + + eable.Free(); + + if (useGuard == null) + { + m_GuardParams[0] = focus; + + try + { + Activator.CreateInstance(m_GuardType, m_GuardParams); + } + catch + { + } + } + else + { + useGuard.Focus = focus; + } + } + + public override void OnEnter(Mobile m) + { + if (IsDisabled()) + return; + + if (!AllowReds && m.Kills >= 5) + CheckGuardCandidate(m); + } + + public override void OnExit(Mobile m) + { + if (IsDisabled()) + return; + } + + public override void OnSpeech(SpeechEventArgs args) + { + base.OnSpeech(args); + + if (IsDisabled()) + return; + + if (args.Mobile.Alive && args.HasKeyword(0x0007)) // *guards* + CallGuards(args.Mobile.Location); + } + + public override void OnAggressed(Mobile aggressor, Mobile aggressed, bool criminal) + { + base.OnAggressed(aggressor, aggressed, criminal); + + if (!IsDisabled() && aggressor != aggressed && criminal) + CheckGuardCandidate(aggressor); + } + + public override void OnGotBeneficialAction(Mobile helper, Mobile helped) + { + base.OnGotBeneficialAction(helper, helped); + + if (IsDisabled()) + return; + + int noto = Notoriety.Compute(helper, helped); + + if (helper != helped && (noto == Notoriety.Criminal || noto == Notoriety.Murderer)) + CheckGuardCandidate(helper); + } + + public override void OnCriminalAction(Mobile m, bool message) + { + base.OnCriminalAction(m, message); + + if (!IsDisabled()) + CheckGuardCandidate(m); + } + + public void CheckGuardCandidate(Mobile m) + { + if (IsDisabled()) + return; + + if (IsGuardCandidate(m)) + { + m_GuardCandidates.TryGetValue(m, out GuardTimer timer); + + if (timer == null) + { + timer = new GuardTimer(m, m_GuardCandidates); + timer.Start(); + + m_GuardCandidates[m] = timer; + m.SendLocalizedMessage(502275); // Guards can now be called on you! + + Map map = m.Map; + + if (map != null) + { + Mobile fakeCall = null; + double prio = 0.0; + + foreach (Mobile v in m.GetMobilesInRange(8)) + if (!v.Player && v != m && !IsGuardCandidate(v) && + ((v as BaseCreature)?.IsHumanInTown() ?? v.Body.IsHuman && v.Region.IsPartOf(this))) + { + double dist = m.GetDistanceToSqrt(v); + + if (fakeCall == null || dist < prio) + { + fakeCall = v; + prio = dist; + } + } + + if (fakeCall != null) + { + fakeCall.Say(Utility.RandomList(1007037, 501603, 1013037, 1013038, 1013039, 1013041, 1013042, + 1013043, 1013052)); + MakeGuard(m); + timer.Stop(); + m_GuardCandidates.Remove(m); + m.SendLocalizedMessage(502276); // Guards can no longer be called on you. + } + } + } + else + { + timer.Stop(); + timer.Start(); + } + } + } + + public void CallGuards(Point3D p) + { + if (IsDisabled()) + return; + + IPooledEnumerable eable = Map.GetMobilesInRange(p, 14); + + foreach (Mobile m in eable) + if (IsGuardCandidate(m) && + (!AllowReds && m.Kills >= 5 && m.Region.IsPartOf(this) || m_GuardCandidates.ContainsKey(m))) + { + m_GuardCandidates.TryGetValue(m, out GuardTimer timer); + + if (timer != null) + { + timer.Stop(); + m_GuardCandidates.Remove(m); + } + + MakeGuard(m); + m.SendLocalizedMessage(502276); // Guards can no longer be called on you. + break; + } + + eable.Free(); + } + + public bool IsGuardCandidate(Mobile m) + { + if (m is BaseGuard || !m.Alive || m.AccessLevel > AccessLevel.Player || m.Blessed || + m is BaseCreature && ((BaseCreature)m).IsInvulnerable || IsDisabled()) + return false; + + return !AllowReds && m.Kills >= 5 || m.Criminal; + } + + private class GuardTimer : Timer + { + private Mobile m_Mobile; + private Dictionary m_Table; + + public GuardTimer(Mobile m, Dictionary table) : base(TimeSpan.FromSeconds(15.0)) + { + Priority = TimerPriority.TwoFiftyMS; + + m_Mobile = m; + m_Table = table; + } + + protected override void OnTick() + { + if (m_Table.ContainsKey(m_Mobile)) + { + m_Table.Remove(m_Mobile); + m_Mobile.SendLocalizedMessage(502276); // Guards can no longer be called on you. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/HouseRegion.cs b/Scripts/Regions/HouseRegion.cs index 6dca86132..9a823dd6e 100644 --- a/Scripts/Regions/HouseRegion.cs +++ b/Scripts/Regions/HouseRegion.cs @@ -1,419 +1,399 @@ using System; -using Server.Mobiles; -using Server.Items; -using Server.Multis; using Server.Gumps; +using Server.Items; +using Server.Mobiles; +using Server.Multis; namespace Server.Regions { - public class HouseRegion : BaseRegion - { - public static readonly int HousePriority = DefaultPriority + 1; + public class HouseRegion : BaseRegion + { + public static readonly int HousePriority = DefaultPriority + 1; - public static void Initialize() - { - EventSink.Login += OnLogin; - } + public static TimeSpan CombatHeatDelay = TimeSpan.FromSeconds(30.0); - public static void OnLogin( LoginEventArgs e ) - { - BaseHouse house = BaseHouse.FindHouseAt( e.Mobile ); + private bool m_Recursion; - if ( house != null && !house.Public && !house.IsFriend( e.Mobile ) ) - e.Mobile.Location = house.BanLocation; - } + public HouseRegion(BaseHouse house) : base(null, house.Map, HousePriority, GetArea(house)) + { + House = house; - public HouseRegion( BaseHouse house ) : base( null, house.Map, HousePriority, GetArea( house ) ) - { - House = house; + Point3D ban = house.RelativeBanLocation; - Point3D ban = house.RelativeBanLocation; + GoLocation = new Point3D(house.X + ban.X, house.Y + ban.Y, house.Z + ban.Z); + } - GoLocation = new Point3D( house.X + ban.X, house.Y + ban.Y, house.Z + ban.Z ); - } + public BaseHouse House{ get; } - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } + public static void Initialize() + { + EventSink.Login += OnLogin; + } - private static Rectangle3D[] GetArea( BaseHouse house ) - { - int x = house.X; - int y = house.Y; - int z = house.Z; + public static void OnLogin(LoginEventArgs e) + { + BaseHouse house = BaseHouse.FindHouseAt(e.Mobile); - Rectangle2D[] houseArea = house.Area; - Rectangle3D[] area = new Rectangle3D[houseArea.Length]; + if (house != null && !house.Public && !house.IsFriend(e.Mobile)) + e.Mobile.Location = house.BanLocation; + } - for ( int i = 0; i < area.Length; i++ ) - { - Rectangle2D rect = houseArea[i]; - area[i] = ConvertTo3D( new Rectangle2D( x + rect.Start.X, y + rect.Start.Y, rect.Width, rect.Height ) ); - } + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } - return area; - } + private static Rectangle3D[] GetArea(BaseHouse house) + { + int x = house.X; + int y = house.Y; + int z = house.Z; - public override bool SendInaccessibleMessage( Item item, Mobile from ) - { - if ( item is Container ) - item.SendLocalizedMessageTo( from, 501647 ); // That is secure. - else - item.SendLocalizedMessageTo( from, 1061637 ); // You are not allowed to access this. + Rectangle2D[] houseArea = house.Area; + Rectangle3D[] area = new Rectangle3D[houseArea.Length]; - return true; - } + for (int i = 0; i < area.Length; i++) + { + Rectangle2D rect = houseArea[i]; + area[i] = ConvertTo3D(new Rectangle2D(x + rect.Start.X, y + rect.Start.Y, rect.Width, rect.Height)); + } - public override bool CheckAccessibility( Item item, Mobile from ) - { - return House.CheckAccessibility( item, from ); - } + return area; + } - private bool m_Recursion; + public override bool SendInaccessibleMessage(Item item, Mobile from) + { + if (item is Container) + item.SendLocalizedMessageTo(from, 501647); // That is secure. + else + item.SendLocalizedMessageTo(from, 1061637); // You are not allowed to access this. - // Use OnLocationChanged instead of OnEnter because it can be that we enter a house region even though we're not actually inside the house - public override void OnLocationChanged( Mobile m, Point3D oldLocation ) - { - if ( m_Recursion ) - return; + return true; + } - base.OnLocationChanged( m, oldLocation ); + public override bool CheckAccessibility(Item item, Mobile from) + { + return House.CheckAccessibility(item, from); + } - m_Recursion = true; + // Use OnLocationChanged instead of OnEnter because it can be that we enter a house region even though we're not actually inside the house + public override void OnLocationChanged(Mobile m, Point3D oldLocation) + { + if (m_Recursion) + return; - if ( m is BaseCreature && ((BaseCreature)m).NoHouseRestrictions ) - { - } - else if ( m is BaseCreature && ((BaseCreature)m).IsHouseSummonable && !(BaseCreature.Summoning || House.IsInside( oldLocation, 16 )) ) - { - } - else if ( (House.Public || !House.IsAosRules) && House.IsBanned( m ) && House.IsInside( m ) ) - { - m.Location = House.BanLocation; + base.OnLocationChanged(m, oldLocation); - if ( !Core.SE ) - m.SendLocalizedMessage( 501284 ); // You may not enter. - } - else if ( House.IsAosRules && !House.Public && !House.HasAccess( m ) && House.IsInside( m ) ) - { - m.Location = House.BanLocation; + m_Recursion = true; - if ( !Core.SE ) - m.SendLocalizedMessage( 501284 ); // You may not enter. - } - else if ( House.IsCombatRestricted( m ) && House.IsInside( m ) && !House.IsInside( oldLocation, 16 ) ) - { - m.Location = House.BanLocation; - m.SendLocalizedMessage( 1061637 ); // You are not allowed to access this. - } - else - { - HouseFoundation foundation = House as HouseFoundation; + if (m is BaseCreature && ((BaseCreature)m).NoHouseRestrictions) + { + } + else if (m is BaseCreature && ((BaseCreature)m).IsHouseSummonable && + !(BaseCreature.Summoning || House.IsInside(oldLocation, 16))) + { + } + else if ((House.Public || !House.IsAosRules) && House.IsBanned(m) && House.IsInside(m)) + { + m.Location = House.BanLocation; - if ( foundation?.Customizer != null && foundation.Customizer != m && House.IsInside( m ) ) - m.Location = House.BanLocation; - } + if (!Core.SE) + m.SendLocalizedMessage(501284); // You may not enter. + } + else if (House.IsAosRules && !House.Public && !House.HasAccess(m) && House.IsInside(m)) + { + m.Location = House.BanLocation; - if ( House.InternalizedVendors.Count > 0 && House.IsInside( m ) && !House.IsInside( oldLocation, 16 ) && House.IsOwner( m ) && m.Alive && !m.HasGump( typeof( NoticeGump ) ) ) - { - /* This house has been customized recently, and vendors that work out of this - * house have been temporarily relocated. You must now put your vendors back to work. - * To do this, walk to a location inside the house where you wish to station - * your vendor, then activate the context-sensitive menu on your avatar and - * select "Get Vendor". - */ - m.SendGump( new NoticeGump( 1060635, 30720, 1061826, 32512, 320, 180, null, null ) ); - } + if (!Core.SE) + m.SendLocalizedMessage(501284); // You may not enter. + } + else if (House.IsCombatRestricted(m) && House.IsInside(m) && !House.IsInside(oldLocation, 16)) + { + m.Location = House.BanLocation; + m.SendLocalizedMessage(1061637); // You are not allowed to access this. + } + else + { + HouseFoundation foundation = House as HouseFoundation; - m_Recursion = false; - } + if (foundation?.Customizer != null && foundation.Customizer != m && House.IsInside(m)) + m.Location = House.BanLocation; + } - public override bool OnMoveInto( Mobile from, Direction d, Point3D newLocation, Point3D oldLocation ) - { - if ( !base.OnMoveInto( from, d, newLocation, oldLocation ) ) - return false; + if (House.InternalizedVendors.Count > 0 && House.IsInside(m) && !House.IsInside(oldLocation, 16) && + House.IsOwner(m) && m.Alive && + !m.HasGump(typeof(NoticeGump))) + m.SendGump(new NoticeGump(1060635, 30720, 1061826, 32512, 320, 180, null, null)); - if ( from is BaseCreature && ((BaseCreature)from).NoHouseRestrictions ) - { - } - else if ( from is BaseCreature && !((BaseCreature)from).Controlled ) // Untamed creatures cannot enter public houses - { - return false; - } - else if ( from is BaseCreature && ((BaseCreature)from).IsHouseSummonable && !(BaseCreature.Summoning || House.IsInside( oldLocation, 16 )) ) - { - return false; - } - else if ( from is BaseCreature && !((BaseCreature)from).Controlled && House.IsAosRules && !House.Public) - { - return false; - } - else if ( (House.Public || !House.IsAosRules) && House.IsBanned( from ) && House.IsInside( newLocation, 16 ) ) - { - from.Location = House.BanLocation; + m_Recursion = false; + } - if ( !Core.SE ) - from.SendLocalizedMessage( 501284 ); // You may not enter. + public override bool OnMoveInto(Mobile from, Direction d, Point3D newLocation, Point3D oldLocation) + { + if (!base.OnMoveInto(from, d, newLocation, oldLocation)) + return false; - return false; - } - else if ( House.IsAosRules && !House.Public && !House.HasAccess( from ) && House.IsInside( newLocation, 16 ) ) - { - if ( !Core.SE ) - from.SendLocalizedMessage( 501284 ); // You may not enter. + if (from is BaseCreature && ((BaseCreature)from).NoHouseRestrictions) + { + } + else if (from is BaseCreature && !((BaseCreature)from).Controlled + ) // Untamed creatures cannot enter public houses + { + return false; + } + else if (from is BaseCreature && ((BaseCreature)from).IsHouseSummonable && + !(BaseCreature.Summoning || House.IsInside(oldLocation, 16))) + { + return false; + } + else if (from is BaseCreature && !((BaseCreature)from).Controlled && House.IsAosRules && !House.Public) + { + return false; + } + else if ((House.Public || !House.IsAosRules) && House.IsBanned(from) && House.IsInside(newLocation, 16)) + { + from.Location = House.BanLocation; - return false; - } - else if ( House.IsCombatRestricted( from ) && !House.IsInside( oldLocation, 16 ) && House.IsInside( newLocation, 16 ) ) - { - from.SendLocalizedMessage( 1061637 ); // You are not allowed to access this. - return false; - } - else - { - HouseFoundation foundation = House as HouseFoundation; + if (!Core.SE) + from.SendLocalizedMessage(501284); // You may not enter. - if ( foundation?.Customizer != null && foundation.Customizer != from && House.IsInside( newLocation, 16 ) ) - return false; - } + return false; + } + else if (House.IsAosRules && !House.Public && !House.HasAccess(from) && House.IsInside(newLocation, 16)) + { + if (!Core.SE) + from.SendLocalizedMessage(501284); // You may not enter. - if ( House.InternalizedVendors.Count > 0 && House.IsInside( from ) && !House.IsInside( oldLocation, 16 ) && House.IsOwner( from ) && from.Alive && !from.HasGump( typeof( NoticeGump ) ) ) - { - /* This house has been customized recently, and vendors that work out of this - * house have been temporarily relocated. You must now put your vendors back to work. - * To do this, walk to a location inside the house where you wish to station - * your vendor, then activate the context-sensitive menu on your avatar and - * select "Get Vendor". - */ - from.SendGump( new NoticeGump( 1060635, 30720, 1061826, 32512, 320, 180, null, null ) ); - } + return false; + } + else if (House.IsCombatRestricted(from) && !House.IsInside(oldLocation, 16) && House.IsInside(newLocation, 16)) + { + from.SendLocalizedMessage(1061637); // You are not allowed to access this. + return false; + } + else + { + HouseFoundation foundation = House as HouseFoundation; - return true; - } + if (foundation?.Customizer != null && foundation.Customizer != from && House.IsInside(newLocation, 16)) + return false; + } - public override bool OnDecay( Item item ) - { - if ( (House.IsLockedDown( item ) || House.IsSecure( item )) && House.IsInside( item ) ) - return false; - return base.OnDecay(item ); - } + if (House.InternalizedVendors.Count > 0 && House.IsInside(from) && !House.IsInside(oldLocation, 16) && + House.IsOwner(from) && from.Alive && + !from.HasGump(typeof(NoticeGump))) + from.SendGump(new NoticeGump(1060635, 30720, 1061826, 32512, 320, 180, null, null)); - public static TimeSpan CombatHeatDelay = TimeSpan.FromSeconds( 30.0 ); + return true; + } - public override TimeSpan GetLogoutDelay( Mobile m ) - { - if ( House.IsFriend( m ) && House.IsInside( m ) ) - { - for ( int i = 0; i < m.Aggressed.Count; ++i ) - { - AggressorInfo info = m.Aggressed[i]; + public override bool OnDecay(Item item) + { + if ((House.IsLockedDown(item) || House.IsSecure(item)) && House.IsInside(item)) + return false; + return base.OnDecay(item); + } - if ( info.Defender.Player && (DateTime.UtcNow - info.LastCombatTime) < CombatHeatDelay ) - return base.GetLogoutDelay( m ); - } + public override TimeSpan GetLogoutDelay(Mobile m) + { + if (House.IsFriend(m) && House.IsInside(m)) + { + for (int i = 0; i < m.Aggressed.Count; ++i) + { + AggressorInfo info = m.Aggressed[i]; - return TimeSpan.Zero; - } + if (info.Defender.Player && DateTime.UtcNow - info.LastCombatTime < CombatHeatDelay) + return base.GetLogoutDelay(m); + } - return base.GetLogoutDelay( m ); - } + return TimeSpan.Zero; + } - public override void OnSpeech( SpeechEventArgs e ) - { - base.OnSpeech( e ); + return base.GetLogoutDelay(m); + } - Mobile from = e.Mobile; - Item sign = House.Sign; + public override void OnSpeech(SpeechEventArgs e) + { + base.OnSpeech(e); - bool isOwner = House.IsOwner( from ); - bool isCoOwner = isOwner || House.IsCoOwner( from ); - bool isFriend = isCoOwner || House.IsFriend( from ); + Mobile from = e.Mobile; + Item sign = House.Sign; - if ( !isFriend ) - return; + bool isOwner = House.IsOwner(from); + bool isCoOwner = isOwner || House.IsCoOwner(from); + bool isFriend = isCoOwner || House.IsFriend(from); - if ( !from.Alive ) - return; + if (!isFriend) + return; - if ( Core.ML && Insensitive.Equals( e.Speech, "I wish to resize my house" ) ) - { - if ( from.Map != sign.Map || !from.InRange( sign, 0 ) ) - { - from.SendLocalizedMessage( 500295 ); // you are too far away to do that. - } - else if ( DateTime.UtcNow <= House.BuiltOn.AddHours ( 1 ) ) - { - from.SendLocalizedMessage( 1080178 ); // You must wait one hour between each house demolition. - } - else if ( isOwner ) - { - from.CloseGump( typeof( ConfirmHouseResize ) ); - from.CloseGump( typeof( HouseGumpAOS ) ); - from.SendGump( new ConfirmHouseResize( from, House ) ); - } - else - { - from.SendLocalizedMessage( 501320 ); // Only the house owner may do this. - } - } + if (!from.Alive) + return; - if ( !House.IsInside( from ) || !House.IsActive ) - return; - if ( e.HasKeyword( 0x33 ) ) // remove thyself - { - if ( isFriend ) - { - from.SendLocalizedMessage( 501326 ); // Target the individual to eject from this house. - from.Target = new HouseKickTarget( House ); - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - else if ( e.HasKeyword( 0x34 ) ) // I ban thee - { - if ( !isFriend ) - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - else if ( !House.Public && House.IsAosRules ) - { - from.SendLocalizedMessage( 1062521 ); // You cannot ban someone from a private house. Revoke their access instead. - } - else - { - from.SendLocalizedMessage( 501325 ); // Target the individual to ban from this house. - from.Target = new HouseBanTarget( true, House ); - } - } - else if ( e.HasKeyword( 0x23 ) ) // I wish to lock this down - { - if ( isCoOwner ) - { - from.SendLocalizedMessage( 502097 ); // Lock what down? - from.Target = new LockdownTarget( false, House ); - } - else if ( isFriend ) - { - from.SendLocalizedMessage( 1010587 ); // You are not a co-owner of this house. - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - else if ( e.HasKeyword( 0x24 ) ) // I wish to release this - { - if ( isCoOwner ) - { - from.SendLocalizedMessage( 502100 ); // Choose the item you wish to release - from.Target = new LockdownTarget( true, House ); - } - else if ( isFriend ) - { - from.SendLocalizedMessage( 1010587 ); // You are not a co-owner of this house. - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - else if ( e.HasKeyword( 0x25 ) ) // I wish to secure this - { - if ( isOwner ) - { - from.SendLocalizedMessage( 502103 ); // Choose the item you wish to secure - from.Target = new SecureTarget( false, House ); - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - else if ( e.HasKeyword( 0x26 ) ) // I wish to unsecure this - { - if ( isOwner ) - { - from.SendLocalizedMessage( 502106 ); // Choose the item you wish to unsecure - from.Target = new SecureTarget( true, House ); - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - else if ( e.HasKeyword( 0x27 ) ) // I wish to place a strongbox - { - if ( isOwner ) - { - from.SendLocalizedMessage( 502109 ); // Owners do not get a strongbox of their own. - } - else if ( isCoOwner ) - { - House.AddStrongBox( from ); - } - else if ( isFriend ) - { - from.SendLocalizedMessage( 1010587 ); // You are not a co-owner of this house. - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - else if ( e.HasKeyword( 0x28 ) ) // trash barrel - { - if ( isCoOwner ) - { - House.AddTrashBarrel( from ); - } - else if ( isFriend ) - { - from.SendLocalizedMessage( 1010587 ); // You are not a co-owner of this house. - } - else - { - from.SendLocalizedMessage( 502094 ); // You must be in your house to do this. - } - } - } + if (Core.ML && Insensitive.Equals(e.Speech, "I wish to resize my house")) + { + if (from.Map != sign.Map || !from.InRange(sign, 0)) + { + from.SendLocalizedMessage(500295); // you are too far away to do that. + } + else if (DateTime.UtcNow <= House.BuiltOn.AddHours(1)) + { + from.SendLocalizedMessage(1080178); // You must wait one hour between each house demolition. + } + else if (isOwner) + { + from.CloseGump(typeof(ConfirmHouseResize)); + from.CloseGump(typeof(HouseGumpAOS)); + from.SendGump(new ConfirmHouseResize(from, House)); + } + else + { + from.SendLocalizedMessage(501320); // Only the house owner may do this. + } + } - public override bool OnDoubleClick( Mobile from, object o ) - { - if ( o is Container ) - { - Container c = (Container)o; + if (!House.IsInside(from) || !House.IsActive) + return; + if (e.HasKeyword(0x33)) // remove thyself + { + if (isFriend) + { + from.SendLocalizedMessage(501326); // Target the individual to eject from this house. + from.Target = new HouseKickTarget(House); + } + else + { + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + } + else if (e.HasKeyword(0x34)) // I ban thee + { + if (!isFriend) + { + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + else if (!House.Public && House.IsAosRules) + { + from.SendLocalizedMessage( + 1062521); // You cannot ban someone from a private house. Revoke their access instead. + } + else + { + from.SendLocalizedMessage(501325); // Target the individual to ban from this house. + from.Target = new HouseBanTarget(true, House); + } + } + else if (e.HasKeyword(0x23)) // I wish to lock this down + { + if (isCoOwner) + { + from.SendLocalizedMessage(502097); // Lock what down? + from.Target = new LockdownTarget(false, House); + } + else if (isFriend) + { + from.SendLocalizedMessage(1010587); // You are not a co-owner of this house. + } + else + { + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + } + else if (e.HasKeyword(0x24)) // I wish to release this + { + if (isCoOwner) + { + from.SendLocalizedMessage(502100); // Choose the item you wish to release + from.Target = new LockdownTarget(true, House); + } + else if (isFriend) + { + from.SendLocalizedMessage(1010587); // You are not a co-owner of this house. + } + else + { + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + } + else if (e.HasKeyword(0x25)) // I wish to secure this + { + if (isOwner) + { + from.SendLocalizedMessage(502103); // Choose the item you wish to secure + from.Target = new SecureTarget(false, House); + } + else + { + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + } + else if (e.HasKeyword(0x26)) // I wish to unsecure this + { + if (isOwner) + { + from.SendLocalizedMessage(502106); // Choose the item you wish to unsecure + from.Target = new SecureTarget(true, House); + } + else + { + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + } + else if (e.HasKeyword(0x27)) // I wish to place a strongbox + { + if (isOwner) + from.SendLocalizedMessage(502109); // Owners do not get a strongbox of their own. + else if (isCoOwner) + House.AddStrongBox(from); + else if (isFriend) + from.SendLocalizedMessage(1010587); // You are not a co-owner of this house. + else + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + else if (e.HasKeyword(0x28)) // trash barrel + { + if (isCoOwner) + House.AddTrashBarrel(from); + else if (isFriend) + from.SendLocalizedMessage(1010587); // You are not a co-owner of this house. + else + from.SendLocalizedMessage(502094); // You must be in your house to do this. + } + } - SecureAccessResult res = House.CheckSecureAccess( from, c ); + public override bool OnDoubleClick(Mobile from, object o) + { + if (o is Container) + { + Container c = (Container)o; - switch ( res ) - { - case SecureAccessResult.Insecure: break; - case SecureAccessResult.Accessible: return true; - case SecureAccessResult.Inaccessible: c.SendLocalizedMessageTo( from, 1010563 ); return false; - } - } + SecureAccessResult res = House.CheckSecureAccess(from, c); - return base.OnDoubleClick( from, o ); - } + switch (res) + { + case SecureAccessResult.Insecure: break; + case SecureAccessResult.Accessible: return true; + case SecureAccessResult.Inaccessible: + c.SendLocalizedMessageTo(from, 1010563); + return false; + } + } - public override bool OnSingleClick( Mobile from, object o ) - { - if ( o is Item ) - { - Item item = (Item)o; + return base.OnDoubleClick(from, o); + } - if ( House.IsLockedDown( item ) ) - item.LabelTo( from, 501643 ); // [locked down] - else if ( House.IsSecure( item ) ) - item.LabelTo( from, 501644 ); // [locked down & secure] - } + public override bool OnSingleClick(Mobile from, object o) + { + if (o is Item) + { + Item item = (Item)o; - return base.OnSingleClick( from, o ); - } + if (House.IsLockedDown(item)) + item.LabelTo(from, 501643); // [locked down] + else if (House.IsSecure(item)) + item.LabelTo(from, 501644); // [locked down & secure] + } - public BaseHouse House { get; } - } -} + return base.OnSingleClick(from, o); + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/Jail.cs b/Scripts/Regions/Jail.cs index f570f192f..6cf3a33c3 100644 --- a/Scripts/Regions/Jail.cs +++ b/Scripts/Regions/Jail.cs @@ -2,57 +2,57 @@ using System.Xml; namespace Server.Regions { - public class Jail : BaseRegion - { - public Jail( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - } + public class Jail : BaseRegion + { + public Jail(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + } - public override bool AllowBeneficial( Mobile from, Mobile target ) - { - if ( from.AccessLevel == AccessLevel.Player ) - from.SendMessage( "You may not do that in jail." ); + public override bool AllowBeneficial(Mobile from, Mobile target) + { + if (from.AccessLevel == AccessLevel.Player) + from.SendMessage("You may not do that in jail."); - return ( from.AccessLevel > AccessLevel.Player ); - } + return from.AccessLevel > AccessLevel.Player; + } - public override bool AllowHarmful( Mobile from, Mobile target ) - { - if ( from.AccessLevel == AccessLevel.Player ) - from.SendMessage( "You may not do that in jail." ); + public override bool AllowHarmful(Mobile from, Mobile target) + { + if (from.AccessLevel == AccessLevel.Player) + from.SendMessage("You may not do that in jail."); - return ( from.AccessLevel > AccessLevel.Player ); - } + return from.AccessLevel > AccessLevel.Player; + } - public override bool AllowHousing( Mobile from, Point3D p ) - { - return false; - } + public override bool AllowHousing(Mobile from, Point3D p) + { + return false; + } - public override void AlterLightLevel( Mobile m, ref int global, ref int personal ) - { - global = LightCycle.JailLevel; - } + public override void AlterLightLevel(Mobile m, ref int global, ref int personal) + { + global = LightCycle.JailLevel; + } - public override bool OnBeginSpellCast( Mobile from, ISpell s ) - { - if ( from.AccessLevel == AccessLevel.Player ) - from.SendLocalizedMessage( 502629 ); // You cannot cast spells here. + public override bool OnBeginSpellCast(Mobile from, ISpell s) + { + if (from.AccessLevel == AccessLevel.Player) + from.SendLocalizedMessage(502629); // You cannot cast spells here. - return ( from.AccessLevel > AccessLevel.Player ); - } + return from.AccessLevel > AccessLevel.Player; + } - public override bool OnSkillUse( Mobile from, int Skill ) - { - if ( from.AccessLevel == AccessLevel.Player ) - from.SendMessage( "You may not use skills in jail." ); + public override bool OnSkillUse(Mobile from, int Skill) + { + if (from.AccessLevel == AccessLevel.Player) + from.SendMessage("You may not use skills in jail."); - return ( from.AccessLevel > AccessLevel.Player ); - } + return from.AccessLevel > AccessLevel.Player; + } - public override bool OnCombatantChange( Mobile from, Mobile Old, Mobile New ) - { - return ( from.AccessLevel > AccessLevel.Player ); - } - } + public override bool OnCombatantChange(Mobile from, Mobile Old, Mobile New) + { + return from.AccessLevel > AccessLevel.Player; + } + } } \ No newline at end of file diff --git a/Scripts/Regions/NoHousingRegion.cs b/Scripts/Regions/NoHousingRegion.cs index 3617c856c..9c12903a3 100644 --- a/Scripts/Regions/NoHousingRegion.cs +++ b/Scripts/Regions/NoHousingRegion.cs @@ -2,23 +2,23 @@ using System.Xml; namespace Server.Regions { - public class NoHousingRegion : BaseRegion - { - /* - False: this uses 'stupid OSI' house placement checking: part of the house may be placed here provided that the center is not in the region - * - True: this uses 'smart RunUO' house placement checking: no part of the house may be in the region - */ - private bool m_SmartChecking; + public class NoHousingRegion : BaseRegion + { + /* - False: this uses 'stupid OSI' house placement checking: part of the house may be placed here provided that the center is not in the region + * - True: this uses 'smart RunUO' house placement checking: no part of the house may be in the region + */ + private bool m_SmartChecking; - public bool SmartChecking => m_SmartChecking; + public NoHousingRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + ReadBoolean(xml["smartNoHousing"], "active", ref m_SmartChecking, false); + } - public NoHousingRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - ReadBoolean( xml["smartNoHousing"], "active", ref m_SmartChecking, false ); - } + public bool SmartChecking => m_SmartChecking; - public override bool AllowHousing( Mobile from, Point3D p ) - { - return m_SmartChecking; - } - } + public override bool AllowHousing(Mobile from, Point3D p) + { + return m_SmartChecking; + } + } } \ No newline at end of file diff --git a/Scripts/Regions/Spawning/SpawnDefinition.cs b/Scripts/Regions/Spawning/SpawnDefinition.cs index 6cee51b5a..49f67da8d 100644 --- a/Scripts/Regions/Spawning/SpawnDefinition.cs +++ b/Scripts/Regions/Spawning/SpawnDefinition.cs @@ -1,397 +1,407 @@ using System; using System.Collections; +using System.Collections.Generic; using System.IO; using System.Xml; -using Server.Mobiles; using Server.Items; -using System.Collections.Generic; +using Server.Mobiles; namespace Server.Regions { - public abstract class SpawnDefinition - { - protected SpawnDefinition() - { - } - - public abstract ISpawnable Spawn( SpawnEntry entry ); - - public abstract bool CanSpawn( params Type[] types ); - - public static SpawnDefinition GetSpawnDefinition( XmlElement xml ) - { - switch ( xml.Name ) - { - case "object": - { - Type type = null; - if ( !Region.ReadType( xml, "type", ref type ) ) - return null; - - if ( typeof( Mobile ).IsAssignableFrom( type ) ) - { - return SpawnMobile.Get( type ); - } - - if ( typeof( Item ).IsAssignableFrom( type ) ) - { - return SpawnItem.Get( type ); - } - Console.WriteLine( "Invalid type '{0}' in a SpawnDefinition", type.FullName ); - return null; - } - case "group": - { - string group = null; - if ( !Region.ReadString( xml, "name", ref group ) ) - return null; - - SpawnDefinition def = (SpawnDefinition) SpawnGroup.Table[group]; - - if ( def == null ) - { - Console.WriteLine( "Could not find group '{0}' in a SpawnDefinition", group ); - return null; - } - - return def; - } - case "treasureChest": - { - int itemID = 0xE43; - Region.ReadInt32( xml, "itemID", ref itemID, false ); - - BaseTreasureChest.TreasureLevel level = BaseTreasureChest.TreasureLevel.Level2; - - Region.ReadEnum( xml, "level", ref level, false ); - - return new SpawnTreasureChest( itemID, level ); - } - default: - { - return null; - } - } - } - } - - public abstract class SpawnType : SpawnDefinition - { - private bool m_Init; - - public Type Type { get; } - - public abstract int Height{ get; } - public abstract bool Land{ get; } - public abstract bool Water{ get; } - - protected SpawnType( Type type ) - { - Type = type; - m_Init = false; - } - - protected void EnsureInit() - { - if ( m_Init ) - return; - - Init(); - m_Init = true; - } - - protected virtual void Init() - { - } - - public override ISpawnable Spawn( SpawnEntry entry ) - { - Region region = entry.Region; - Map map = region.Map; - - Point3D loc = entry.RandomSpawnLocation( Height, Land, Water ); - - if ( loc == Point3D.Zero ) - return null; - - return Construct( entry, loc, map ); - } - - protected abstract ISpawnable Construct( SpawnEntry entry, Point3D loc, Map map ); - - public override bool CanSpawn( params Type[] types ) - { - for ( int i = 0; i < types.Length; i++ ) - { - if ( types[i] == Type ) - return true; - } - - return false; - } - } - - public class SpawnMobile : SpawnType - { - private static Hashtable m_Table = new Hashtable(); - - public static SpawnMobile Get( Type type ) - { - SpawnMobile sm = (SpawnMobile) m_Table[type]; - - if ( sm == null ) - { - sm = new SpawnMobile( type ); - m_Table[type] = sm; - } - - return sm; - } - - protected bool m_Land; - protected bool m_Water; - - public override int Height => 16; - public override bool Land{ get{ EnsureInit(); return m_Land; } } - public override bool Water{ get{ EnsureInit(); return m_Water; } } - - protected SpawnMobile( Type type ) : base( type ) - { - } - - protected override void Init() - { - Mobile mob = (Mobile) Activator.CreateInstance( Type ); - - m_Land = !mob.CantWalk; - m_Water = mob.CanSwim; - - mob.Delete(); - } - - protected override ISpawnable Construct(SpawnEntry entry, Point3D loc, Map map) - { - Mobile mobile = CreateMobile(); - - BaseCreature creature = mobile as BaseCreature; - - if ( creature != null ) - { - creature.Home = entry.HomeLocation; - creature.HomeMap = map; - creature.RangeHome = entry.HomeRange; - } - - if ( entry.Direction != SpawnEntry.InvalidDirection ) - mobile.Direction = entry.Direction; - - mobile.OnBeforeSpawn( loc, map ); - mobile.MoveToWorld( loc, map ); - mobile.OnAfterSpawn(); - - return mobile; - } - - protected virtual Mobile CreateMobile() - { - return (Mobile) Activator.CreateInstance( Type ); - } - } - - public class SpawnItem : SpawnType - { - private static Hashtable m_Table = new Hashtable(); - - public static SpawnItem Get( Type type ) - { - SpawnItem si = (SpawnItem) m_Table[type]; - - if ( si == null ) - { - si = new SpawnItem( type ); - m_Table[type] = si; - } - - return si; - } - - protected int m_Height; - - public override int Height{ get{ EnsureInit(); return m_Height; } } - public override bool Land => true; - public override bool Water => false; - - protected SpawnItem( Type type ) : base( type ) - { - } - - protected override void Init() - { - Item item = (Item) Activator.CreateInstance( Type ); - - m_Height = item.ItemData.Height; - - item.Delete(); - } - - protected override ISpawnable Construct( SpawnEntry entry, Point3D loc, Map map ) - { - Item item = CreateItem(); - - item.OnBeforeSpawn( loc, map ); - item.MoveToWorld( loc, map ); - item.OnAfterSpawn(); - - return item; - } - - protected virtual Item CreateItem() - { - return (Item) Activator.CreateInstance( Type ); - } - } - - public class SpawnTreasureChest : SpawnItem - { - public int ItemID { get; } - - public BaseTreasureChest.TreasureLevel Level { get; } - - public SpawnTreasureChest( int itemID, BaseTreasureChest.TreasureLevel level ) : base( typeof( BaseTreasureChest ) ) - { - ItemID = itemID; - Level = level; - } - - protected override void Init() - { - m_Height = TileData.ItemTable[ItemID & TileData.MaxItemValue].Height; - } - - protected override Item CreateItem() - { - return new BaseTreasureChest( ItemID, Level ); - } - } - - public class SpawnGroupElement - { - public SpawnDefinition SpawnDefinition { get; } - - public int Weight { get; } - - public SpawnGroupElement( SpawnDefinition spawnDefinition, int weight ) - { - SpawnDefinition = spawnDefinition; - Weight = weight; - } - } - - public class SpawnGroup : SpawnDefinition - { - public static Hashtable Table { get; } = new Hashtable(); - - public static void Register( SpawnGroup group ) - { - if ( Table.Contains( group.Name ) ) - Console.WriteLine( "Warning: Double SpawnGroup name '{0}'", group.Name ); - else - Table[group.Name] = group; - } - - static SpawnGroup() - { - string path = Path.Combine( Core.BaseDirectory, "Data/SpawnDefinitions.xml" ); - if ( !File.Exists( path ) ) - return; - - try - { - XmlDocument doc = new XmlDocument(); - doc.Load( path ); - - XmlElement root = doc["spawnDefinitions"]; - if ( root == null ) - return; - - foreach ( XmlElement xmlDef in root.SelectNodes( "spawnGroup" ) ) - { - string name = null; - if ( !Region.ReadString( xmlDef, "name", ref name ) ) - continue; - - List list = new List(); - foreach ( XmlNode node in xmlDef.ChildNodes ) - { - XmlElement el = node as XmlElement; - - if ( el != null ) - { - SpawnDefinition def = GetSpawnDefinition( el ); - if ( def == null ) - continue; - - int weight = 1; - Region.ReadInt32( el, "weight", ref weight, false ); - - SpawnGroupElement groupElement = new SpawnGroupElement( def, weight ); - list.Add( groupElement ); - } - } - - SpawnGroupElement[] elements = list.ToArray(); - SpawnGroup group = new SpawnGroup( name, elements ); - Register( group ); - } - } - catch ( Exception ex ) - { - Console.WriteLine( "Could not load SpawnDefinitions.xml: " + ex.Message ); - } - } - - private int m_TotalWeight; - - public string Name { get; } - - public SpawnGroupElement[] Elements { get; } - - public SpawnGroup( string name, SpawnGroupElement[] elements ) - { - Name = name; - Elements = elements; - - m_TotalWeight = 0; - for ( int i = 0; i < elements.Length; i++ ) - m_TotalWeight += elements[i].Weight; - } - - public override ISpawnable Spawn(SpawnEntry entry) - { - int index = Utility.Random( m_TotalWeight ); - - for ( int i = 0; i < Elements.Length; i++ ) - { - SpawnGroupElement element = Elements[i]; - - if ( index < element.Weight ) - return element.SpawnDefinition.Spawn( entry ); - - index -= element.Weight; - } - - return null; - } - - public override bool CanSpawn( params Type[] types ) - { - for ( int i = 0; i < Elements.Length; i++ ) - { - if ( Elements[i].SpawnDefinition.CanSpawn( types ) ) - return true; - } - - return false; - } - } -} + public abstract class SpawnDefinition + { + public abstract ISpawnable Spawn(SpawnEntry entry); + + public abstract bool CanSpawn(params Type[] types); + + public static SpawnDefinition GetSpawnDefinition(XmlElement xml) + { + switch (xml.Name) + { + case "object": + { + Type type = null; + if (!Region.ReadType(xml, "type", ref type)) + return null; + + if (typeof(Mobile).IsAssignableFrom(type)) return SpawnMobile.Get(type); + + if (typeof(Item).IsAssignableFrom(type)) return SpawnItem.Get(type); + Console.WriteLine("Invalid type '{0}' in a SpawnDefinition", type.FullName); + return null; + } + case "group": + { + string group = null; + if (!Region.ReadString(xml, "name", ref group)) + return null; + + SpawnDefinition def = (SpawnDefinition)SpawnGroup.Table[group]; + + if (def == null) + { + Console.WriteLine("Could not find group '{0}' in a SpawnDefinition", group); + return null; + } + + return def; + } + case "treasureChest": + { + int itemID = 0xE43; + Region.ReadInt32(xml, "itemID", ref itemID, false); + + BaseTreasureChest.TreasureLevel level = BaseTreasureChest.TreasureLevel.Level2; + + Region.ReadEnum(xml, "level", ref level, false); + + return new SpawnTreasureChest(itemID, level); + } + default: + { + return null; + } + } + } + } + + public abstract class SpawnType : SpawnDefinition + { + private bool m_Init; + + protected SpawnType(Type type) + { + Type = type; + m_Init = false; + } + + public Type Type{ get; } + + public abstract int Height{ get; } + public abstract bool Land{ get; } + public abstract bool Water{ get; } + + protected void EnsureInit() + { + if (m_Init) + return; + + Init(); + m_Init = true; + } + + protected virtual void Init() + { + } + + public override ISpawnable Spawn(SpawnEntry entry) + { + Region region = entry.Region; + Map map = region.Map; + + Point3D loc = entry.RandomSpawnLocation(Height, Land, Water); + + if (loc == Point3D.Zero) + return null; + + return Construct(entry, loc, map); + } + + protected abstract ISpawnable Construct(SpawnEntry entry, Point3D loc, Map map); + + public override bool CanSpawn(params Type[] types) + { + for (int i = 0; i < types.Length; i++) + if (types[i] == Type) + return true; + + return false; + } + } + + public class SpawnMobile : SpawnType + { + private static Hashtable m_Table = new Hashtable(); + + protected bool m_Land; + protected bool m_Water; + + protected SpawnMobile(Type type) : base(type) + { + } + + public override int Height => 16; + + public override bool Land + { + get + { + EnsureInit(); + return m_Land; + } + } + + public override bool Water + { + get + { + EnsureInit(); + return m_Water; + } + } + + public static SpawnMobile Get(Type type) + { + SpawnMobile sm = (SpawnMobile)m_Table[type]; + + if (sm == null) + { + sm = new SpawnMobile(type); + m_Table[type] = sm; + } + + return sm; + } + + protected override void Init() + { + Mobile mob = (Mobile)Activator.CreateInstance(Type); + + m_Land = !mob.CantWalk; + m_Water = mob.CanSwim; + + mob.Delete(); + } + + protected override ISpawnable Construct(SpawnEntry entry, Point3D loc, Map map) + { + Mobile mobile = CreateMobile(); + + BaseCreature creature = mobile as BaseCreature; + + if (creature != null) + { + creature.Home = entry.HomeLocation; + creature.HomeMap = map; + creature.RangeHome = entry.HomeRange; + } + + if (entry.Direction != SpawnEntry.InvalidDirection) + mobile.Direction = entry.Direction; + + mobile.OnBeforeSpawn(loc, map); + mobile.MoveToWorld(loc, map); + mobile.OnAfterSpawn(); + + return mobile; + } + + protected virtual Mobile CreateMobile() + { + return (Mobile)Activator.CreateInstance(Type); + } + } + + public class SpawnItem : SpawnType + { + private static Hashtable m_Table = new Hashtable(); + + protected int m_Height; + + protected SpawnItem(Type type) : base(type) + { + } + + public override int Height + { + get + { + EnsureInit(); + return m_Height; + } + } + + public override bool Land => true; + public override bool Water => false; + + public static SpawnItem Get(Type type) + { + SpawnItem si = (SpawnItem)m_Table[type]; + + if (si == null) + { + si = new SpawnItem(type); + m_Table[type] = si; + } + + return si; + } + + protected override void Init() + { + Item item = (Item)Activator.CreateInstance(Type); + + m_Height = item.ItemData.Height; + + item.Delete(); + } + + protected override ISpawnable Construct(SpawnEntry entry, Point3D loc, Map map) + { + Item item = CreateItem(); + + item.OnBeforeSpawn(loc, map); + item.MoveToWorld(loc, map); + item.OnAfterSpawn(); + + return item; + } + + protected virtual Item CreateItem() + { + return (Item)Activator.CreateInstance(Type); + } + } + + public class SpawnTreasureChest : SpawnItem + { + public SpawnTreasureChest(int itemID, BaseTreasureChest.TreasureLevel level) : base(typeof(BaseTreasureChest)) + { + ItemID = itemID; + Level = level; + } + + public int ItemID{ get; } + + public BaseTreasureChest.TreasureLevel Level{ get; } + + protected override void Init() + { + m_Height = TileData.ItemTable[ItemID & TileData.MaxItemValue].Height; + } + + protected override Item CreateItem() + { + return new BaseTreasureChest(ItemID, Level); + } + } + + public class SpawnGroupElement + { + public SpawnGroupElement(SpawnDefinition spawnDefinition, int weight) + { + SpawnDefinition = spawnDefinition; + Weight = weight; + } + + public SpawnDefinition SpawnDefinition{ get; } + + public int Weight{ get; } + } + + public class SpawnGroup : SpawnDefinition + { + private int m_TotalWeight; + + static SpawnGroup() + { + string path = Path.Combine(Core.BaseDirectory, "Data/SpawnDefinitions.xml"); + if (!File.Exists(path)) + return; + + try + { + XmlDocument doc = new XmlDocument(); + doc.Load(path); + + XmlElement root = doc["spawnDefinitions"]; + if (root == null) + return; + + foreach (XmlElement xmlDef in root.SelectNodes("spawnGroup")) + { + string name = null; + if (!Region.ReadString(xmlDef, "name", ref name)) + continue; + + List list = new List(); + foreach (XmlNode node in xmlDef.ChildNodes) + { + XmlElement el = node as XmlElement; + + if (el != null) + { + SpawnDefinition def = GetSpawnDefinition(el); + if (def == null) + continue; + + int weight = 1; + Region.ReadInt32(el, "weight", ref weight, false); + + SpawnGroupElement groupElement = new SpawnGroupElement(def, weight); + list.Add(groupElement); + } + } + + SpawnGroupElement[] elements = list.ToArray(); + SpawnGroup group = new SpawnGroup(name, elements); + Register(group); + } + } + catch (Exception ex) + { + Console.WriteLine("Could not load SpawnDefinitions.xml: " + ex.Message); + } + } + + public SpawnGroup(string name, SpawnGroupElement[] elements) + { + Name = name; + Elements = elements; + + m_TotalWeight = 0; + for (int i = 0; i < elements.Length; i++) + m_TotalWeight += elements[i].Weight; + } + + public static Hashtable Table{ get; } = new Hashtable(); + + public string Name{ get; } + + public SpawnGroupElement[] Elements{ get; } + + public static void Register(SpawnGroup group) + { + if (Table.Contains(group.Name)) + Console.WriteLine("Warning: Double SpawnGroup name '{0}'", group.Name); + else + Table[group.Name] = group; + } + + public override ISpawnable Spawn(SpawnEntry entry) + { + int index = Utility.Random(m_TotalWeight); + + for (int i = 0; i < Elements.Length; i++) + { + SpawnGroupElement element = Elements[i]; + + if (index < element.Weight) + return element.SpawnDefinition.Spawn(entry); + + index -= element.Weight; + } + + return null; + } + + public override bool CanSpawn(params Type[] types) + { + for (int i = 0; i < Elements.Length; i++) + if (Elements[i].SpawnDefinition.CanSpawn(types)) + return true; + + return false; + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/Spawning/SpawnEntry.cs b/Scripts/Regions/Spawning/SpawnEntry.cs index d9e440476..524c196da 100644 --- a/Scripts/Regions/Spawning/SpawnEntry.cs +++ b/Scripts/Regions/Spawning/SpawnEntry.cs @@ -1,458 +1,445 @@ using System; using System.Collections; using System.Collections.Generic; -using Server.Mobiles; using Server.Commands; +using Server.Mobiles; namespace Server.Regions { - public class SpawnEntry : ISpawner - { - public static readonly TimeSpan DefaultMinSpawnTime = TimeSpan.FromMinutes( 2.0 ); - public static readonly TimeSpan DefaultMaxSpawnTime = TimeSpan.FromMinutes( 5.0 ); + public class SpawnEntry : ISpawner + { + public static readonly TimeSpan DefaultMinSpawnTime = TimeSpan.FromMinutes(2.0); + public static readonly TimeSpan DefaultMaxSpawnTime = TimeSpan.FromMinutes(5.0); - public static Hashtable Table { get; } = new Hashtable(); + public static readonly Direction InvalidDirection = Direction.Running; - // When a creature's AI is deactivated (PlayerRangeSensitive optimization) does it return home? - public bool ReturnOnDeactivate => true; + private static List m_RemoveList; - // Are creatures unlinked on taming (true) or should they also go out of the region (false)? - public bool UnlinkOnTaming => false; + private DateTime m_NextSpawn; + private Timer m_SpawnTimer; - // Are unlinked and untamed creatures removed after 20 hours? - public bool RemoveIfUntamed => true; + public SpawnEntry(int id, BaseRegion region, Point3D home, int range, Direction direction, + SpawnDefinition definition, int max, TimeSpan minSpawnTime, TimeSpan maxSpawnTime) + { + ID = id; + Region = region; + HomeLocation = home; + HomeRange = range; + Direction = direction; + Definition = definition; + SpawnedObjects = new List(); + Max = max; + MinSpawnTime = minSpawnTime; + MaxSpawnTime = maxSpawnTime; + Running = false; + if (Table.Contains(id)) + Console.WriteLine("Warning: double SpawnEntry ID '{0}'", id); + else + Table[id] = this; + } - public static readonly Direction InvalidDirection = Direction.Running; + public static Hashtable Table{ get; } = new Hashtable(); - private DateTime m_NextSpawn; - private Timer m_SpawnTimer; - public int ID { get; } + // When a creature's AI is deactivated (PlayerRangeSensitive optimization) does it return home? + public bool ReturnOnDeactivate => true; - public BaseRegion Region { get; } + // Are unlinked and untamed creatures removed after 20 hours? + public bool RemoveIfUntamed => true; - Region ISpawner.Region => Region; - public Point3D HomeLocation { get; } + public int ID{ get; } - public int HomeRange { get; } + public BaseRegion Region{ get; } - public Direction Direction { get; } + public Direction Direction{ get; } - public SpawnDefinition Definition { get; } + public SpawnDefinition Definition{ get; } - public List SpawnedObjects { get; } + public List SpawnedObjects{ get; } - public int Max { get; private set; } + public int Max{ get; private set; } - public TimeSpan MinSpawnTime { get; } + public TimeSpan MinSpawnTime{ get; } - public TimeSpan MaxSpawnTime { get; } + public TimeSpan MaxSpawnTime{ get; } - public bool Running { get; private set; } + public bool Running{ get; private set; } - public bool Complete => SpawnedObjects.Count >= Max; - public bool Spawning => Running && !Complete; + public bool Complete => SpawnedObjects.Count >= Max; + public bool Spawning => Running && !Complete; - public SpawnEntry( int id, BaseRegion region, Point3D home, int range, Direction direction, SpawnDefinition definition, int max, TimeSpan minSpawnTime, TimeSpan maxSpawnTime ) - { - ID = id; - Region = region; - HomeLocation = home; - HomeRange = range; - Direction = direction; - Definition = definition; - SpawnedObjects = new List(); - Max = max; - MinSpawnTime = minSpawnTime; - MaxSpawnTime = maxSpawnTime; - Running = false; + // Are creatures unlinked on taming (true) or should they also go out of the region (false)? + public bool UnlinkOnTaming => false; - if ( Table.Contains( id ) ) - Console.WriteLine( "Warning: double SpawnEntry ID '{0}'", id ); - else - Table[id] = this; - } + Region ISpawner.Region => Region; + public Point3D HomeLocation{ get; } - public Point3D RandomSpawnLocation( int spawnHeight, bool land, bool water ) - { - return Region.RandomSpawnLocation( spawnHeight, land, water, HomeLocation, HomeRange ); - } + public int HomeRange{ get; } - public void Start() - { - if ( Running ) - return; + void ISpawner.Remove(ISpawnable spawn) + { + SpawnedObjects.Remove(spawn); - Running = true; - CheckTimer(); - } + CheckTimer(); + } - public void Stop() - { - if ( !Running ) - return; + public Point3D RandomSpawnLocation(int spawnHeight, bool land, bool water) + { + return Region.RandomSpawnLocation(spawnHeight, land, water, HomeLocation, HomeRange); + } - Running = false; - CheckTimer(); - } + public void Start() + { + if (Running) + return; - private void Spawn() - { - ISpawnable spawn = Definition.Spawn(this); + Running = true; + CheckTimer(); + } - if ( spawn != null ) - Add( spawn ); - } + public void Stop() + { + if (!Running) + return; - private void Add( ISpawnable spawn ) - { - SpawnedObjects.Add( spawn ); + Running = false; + CheckTimer(); + } - spawn.Spawner = this; + private void Spawn() + { + ISpawnable spawn = Definition.Spawn(this); - if ( spawn is BaseCreature ) - ((BaseCreature)spawn).RemoveIfUntamed = RemoveIfUntamed; - } + if (spawn != null) + Add(spawn); + } - void ISpawner.Remove( ISpawnable spawn ) - { - SpawnedObjects.Remove( spawn ); + private void Add(ISpawnable spawn) + { + SpawnedObjects.Add(spawn); - CheckTimer(); - } + spawn.Spawner = this; - private TimeSpan RandomTime() - { - int min = (int) MinSpawnTime.TotalSeconds; - int max = (int) MaxSpawnTime.TotalSeconds; + if (spawn is BaseCreature) + ((BaseCreature)spawn).RemoveIfUntamed = RemoveIfUntamed; + } - int rand = Utility.RandomMinMax( min, max ); - return TimeSpan.FromSeconds( rand ); - } - - private void CheckTimer() - { - if ( Spawning ) - { - if ( m_SpawnTimer == null ) - { - TimeSpan time = RandomTime(); - m_SpawnTimer = Timer.DelayCall( time, TimerCallback ); - m_NextSpawn = DateTime.UtcNow + time; - } - } - else if ( m_SpawnTimer != null ) - { - m_SpawnTimer.Stop(); - m_SpawnTimer = null; - } - } - - private void TimerCallback() - { - int amount = Math.Max( (Max - SpawnedObjects.Count) / 3, 1 ); - - for ( int i = 0; i < amount; i++ ) - Spawn(); - - m_SpawnTimer = null; - CheckTimer(); - } - - public void DeleteSpawnedObjects() - { - InternalDeleteSpawnedObjects(); - - Running = false; - CheckTimer(); - } - - private void InternalDeleteSpawnedObjects() - { - foreach ( ISpawnable spawnable in SpawnedObjects ) - { - spawnable.Spawner = null; - - bool uncontrolled = !(spawnable is BaseCreature) || !((BaseCreature)spawnable).Controlled; - - if ( uncontrolled ) - spawnable.Delete(); - } - - SpawnedObjects.Clear(); - } - - public void Respawn() - { - InternalDeleteSpawnedObjects(); - - for ( int i = 0; !Complete && i < Max; i++ ) - Spawn(); - - Running = true; - CheckTimer(); - } - - public void Delete() - { - Max = 0; - InternalDeleteSpawnedObjects(); - - if ( m_SpawnTimer != null ) - { - m_SpawnTimer.Stop(); - m_SpawnTimer = null; - } - - if ( Table[ID] == this ) - Table.Remove( ID ); - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (int) SpawnedObjects.Count ); - - for ( int i = 0; i < SpawnedObjects.Count; i++ ) - { - ISpawnable spawn = SpawnedObjects[i]; - - int serial = spawn.Serial; - - writer.Write( (int) serial ); - } - - writer.Write( (bool) Running ); - - if ( m_SpawnTimer != null ) - { - writer.Write( true ); - writer.WriteDeltaTime( (DateTime) m_NextSpawn ); - } - else - { - writer.Write( false ); - } - } - - public void Deserialize( GenericReader reader, int version ) - { - int count = reader.ReadInt(); - - for ( int i = 0; i < count; i++ ) - { - int serial = reader.ReadInt(); - ISpawnable spawnableEntity = World.FindEntity( serial ) as ISpawnable; - - if (spawnableEntity != null) - Add(spawnableEntity); - } - - Running = reader.ReadBool(); - - if ( reader.ReadBool() ) - { - m_NextSpawn = reader.ReadDeltaTime(); - - if ( Spawning ) - { - m_SpawnTimer?.Stop(); - - TimeSpan delay = m_NextSpawn - DateTime.UtcNow; - m_SpawnTimer = Timer.DelayCall( delay > TimeSpan.Zero ? delay : TimeSpan.Zero, TimerCallback ); - } - } - - CheckTimer(); - } - - private static List m_RemoveList; - - public static void Remove( GenericReader reader, int version ) - { - int count = reader.ReadInt(); - - for ( int i = 0; i < count; i++ ) - { - int serial = reader.ReadInt(); - IEntity entity = World.FindEntity( serial ); - - if ( entity != null ) - { - if ( m_RemoveList == null ) - m_RemoveList = new List(); - - m_RemoveList.Add( entity ); - } - } - - reader.ReadBool(); // m_Running - - if ( reader.ReadBool() ) - reader.ReadDeltaTime(); // m_NextSpawn - } - - public static void Initialize() - { - if ( m_RemoveList != null ) - { - foreach ( IEntity ent in m_RemoveList ) - { - ent.Delete(); - } - - m_RemoveList = null; - } - - SpawnPersistence.EnsureExistence(); - - CommandSystem.Register( "RespawnAllRegions", AccessLevel.Administrator, RespawnAllRegions_OnCommand ); - CommandSystem.Register( "RespawnRegion", AccessLevel.GameMaster, RespawnRegion_OnCommand ); - CommandSystem.Register( "DelAllRegionSpawns", AccessLevel.Administrator, DelAllRegionSpawns_OnCommand ); - CommandSystem.Register( "DelRegionSpawns", AccessLevel.GameMaster, DelRegionSpawns_OnCommand ); - CommandSystem.Register( "StartAllRegionSpawns", AccessLevel.Administrator, StartAllRegionSpawns_OnCommand ); - CommandSystem.Register( "StartRegionSpawns", AccessLevel.GameMaster, StartRegionSpawns_OnCommand ); - CommandSystem.Register( "StopAllRegionSpawns", AccessLevel.Administrator, StopAllRegionSpawns_OnCommand ); - CommandSystem.Register( "StopRegionSpawns", AccessLevel.GameMaster, StopRegionSpawns_OnCommand ); - } - - private static BaseRegion GetCommandData( CommandEventArgs args ) - { - Mobile from = args.Mobile; - - Region reg; - if ( args.Length == 0 ) - { - reg = from.Region; - } - else - { - string name = args.GetString( 0 ); - //reg = if (!from.Map.Regions.TryGetValue( name, out (Region) from.Map.Regions[name] )) - { - from.SendMessage( "Could not find region '{0}'.", name ); - return null; - } - } - - BaseRegion br = reg as BaseRegion; - - if ( br?.Spawns == null ) - { - from.SendMessage( "There are no spawners in region '{0}'.", reg ); - return null; - } - - return br; - } - - [Usage( "RespawnAllRegions" )] - [Description( "Respawns all regions and sets the spawners as running." )] - private static void RespawnAllRegions_OnCommand( CommandEventArgs args ) - { - foreach ( SpawnEntry entry in Table.Values ) - { - entry.Respawn(); - } - - args.Mobile.SendMessage( "All regions have respawned." ); - } - - [Usage( "RespawnRegion []" )] - [Description( "Respawns the region in which you are (or that you provided) and sets the spawners as running." )] - private static void RespawnRegion_OnCommand( CommandEventArgs args ) - { - BaseRegion region = GetCommandData( args ); - - if ( region == null ) - return; - - for ( int i = 0; i < region.Spawns.Length; i++ ) - region.Spawns[i].Respawn(); - - args.Mobile.SendMessage( "Region '{0}' has respawned.", region ); - } - - [Usage( "DelAllRegionSpawns" )] - [Description( "Deletes all spawned objects of every regions and sets the spawners as not running." )] - private static void DelAllRegionSpawns_OnCommand( CommandEventArgs args ) - { - foreach ( SpawnEntry entry in Table.Values ) - { - entry.DeleteSpawnedObjects(); - } - - args.Mobile.SendMessage( "All region spawned objects have been deleted." ); - } - - [Usage( "DelRegionSpawns []" )] - [Description( "Deletes all spawned objects of the region in which you are (or that you provided) and sets the spawners as not running." )] - private static void DelRegionSpawns_OnCommand( CommandEventArgs args ) - { - BaseRegion region = GetCommandData( args ); - - if ( region == null ) - return; - - for ( int i = 0; i < region.Spawns.Length; i++ ) - region.Spawns[i].DeleteSpawnedObjects(); - - args.Mobile.SendMessage( "Spawned objects of region '{0}' have been deleted.", region ); - } - - [Usage( "StartAllRegionSpawns" )] - [Description( "Sets the region spawners of all regions as running." )] - private static void StartAllRegionSpawns_OnCommand( CommandEventArgs args ) - { - foreach ( SpawnEntry entry in Table.Values ) - { - entry.Start(); - } - - args.Mobile.SendMessage( "All region spawners have started." ); - } - - [Usage( "StartRegionSpawns []" )] - [Description( "Sets the region spawners of the region in which you are (or that you provided) as running." )] - private static void StartRegionSpawns_OnCommand( CommandEventArgs args ) - { - BaseRegion region = GetCommandData( args ); - - if ( region == null ) - return; - - for ( int i = 0; i < region.Spawns.Length; i++ ) - region.Spawns[i].Start(); - - args.Mobile.SendMessage( "Spawners of region '{0}' have started.", region ); - } - - [Usage( "StopAllRegionSpawns" )] - [Description( "Sets the region spawners of all regions as not running." )] - private static void StopAllRegionSpawns_OnCommand( CommandEventArgs args ) - { - foreach ( SpawnEntry entry in Table.Values ) - { - entry.Stop(); - } - - args.Mobile.SendMessage( "All region spawners have stopped." ); - } - - [Usage( "StopRegionSpawns []" )] - [Description( "Sets the region spawners of the region in which you are (or that you provided) as not running." )] - private static void StopRegionSpawns_OnCommand( CommandEventArgs args ) - { - BaseRegion region = GetCommandData( args ); - - if ( region == null ) - return; - - for ( int i = 0; i < region.Spawns.Length; i++ ) - region.Spawns[i].Stop(); - - args.Mobile.SendMessage( "Spawners of region '{0}' have stopped.", region ); - } - } -} + private TimeSpan RandomTime() + { + int min = (int)MinSpawnTime.TotalSeconds; + int max = (int)MaxSpawnTime.TotalSeconds; + + int rand = Utility.RandomMinMax(min, max); + return TimeSpan.FromSeconds(rand); + } + + private void CheckTimer() + { + if (Spawning) + { + if (m_SpawnTimer == null) + { + TimeSpan time = RandomTime(); + m_SpawnTimer = Timer.DelayCall(time, TimerCallback); + m_NextSpawn = DateTime.UtcNow + time; + } + } + else if (m_SpawnTimer != null) + { + m_SpawnTimer.Stop(); + m_SpawnTimer = null; + } + } + + private void TimerCallback() + { + int amount = Math.Max((Max - SpawnedObjects.Count) / 3, 1); + + for (int i = 0; i < amount; i++) + Spawn(); + + m_SpawnTimer = null; + CheckTimer(); + } + + public void DeleteSpawnedObjects() + { + InternalDeleteSpawnedObjects(); + + Running = false; + CheckTimer(); + } + + private void InternalDeleteSpawnedObjects() + { + foreach (ISpawnable spawnable in SpawnedObjects) + { + spawnable.Spawner = null; + + bool uncontrolled = !(spawnable is BaseCreature) || !((BaseCreature)spawnable).Controlled; + + if (uncontrolled) + spawnable.Delete(); + } + + SpawnedObjects.Clear(); + } + + public void Respawn() + { + InternalDeleteSpawnedObjects(); + + for (int i = 0; !Complete && i < Max; i++) + Spawn(); + + Running = true; + CheckTimer(); + } + + public void Delete() + { + Max = 0; + InternalDeleteSpawnedObjects(); + + if (m_SpawnTimer != null) + { + m_SpawnTimer.Stop(); + m_SpawnTimer = null; + } + + if (Table[ID] == this) + Table.Remove(ID); + } + + public void Serialize(GenericWriter writer) + { + writer.Write(SpawnedObjects.Count); + + for (int i = 0; i < SpawnedObjects.Count; i++) + { + ISpawnable spawn = SpawnedObjects[i]; + + int serial = spawn.Serial; + + writer.Write(serial); + } + + writer.Write(Running); + + if (m_SpawnTimer != null) + { + writer.Write(true); + writer.WriteDeltaTime(m_NextSpawn); + } + else + { + writer.Write(false); + } + } + + public void Deserialize(GenericReader reader, int version) + { + int count = reader.ReadInt(); + + for (int i = 0; i < count; i++) + { + int serial = reader.ReadInt(); + ISpawnable spawnableEntity = World.FindEntity(serial) as ISpawnable; + + if (spawnableEntity != null) + Add(spawnableEntity); + } + + Running = reader.ReadBool(); + + if (reader.ReadBool()) + { + m_NextSpawn = reader.ReadDeltaTime(); + + if (Spawning) + { + m_SpawnTimer?.Stop(); + + TimeSpan delay = m_NextSpawn - DateTime.UtcNow; + m_SpawnTimer = Timer.DelayCall(delay > TimeSpan.Zero ? delay : TimeSpan.Zero, TimerCallback); + } + } + + CheckTimer(); + } + + public static void Remove(GenericReader reader, int version) + { + int count = reader.ReadInt(); + + for (int i = 0; i < count; i++) + { + int serial = reader.ReadInt(); + IEntity entity = World.FindEntity(serial); + + if (entity != null) + { + if (m_RemoveList == null) + m_RemoveList = new List(); + + m_RemoveList.Add(entity); + } + } + + reader.ReadBool(); // m_Running + + if (reader.ReadBool()) + reader.ReadDeltaTime(); // m_NextSpawn + } + + public static void Initialize() + { + if (m_RemoveList != null) + { + foreach (IEntity ent in m_RemoveList) ent.Delete(); + + m_RemoveList = null; + } + + SpawnPersistence.EnsureExistence(); + + CommandSystem.Register("RespawnAllRegions", AccessLevel.Administrator, RespawnAllRegions_OnCommand); + CommandSystem.Register("RespawnRegion", AccessLevel.GameMaster, RespawnRegion_OnCommand); + CommandSystem.Register("DelAllRegionSpawns", AccessLevel.Administrator, DelAllRegionSpawns_OnCommand); + CommandSystem.Register("DelRegionSpawns", AccessLevel.GameMaster, DelRegionSpawns_OnCommand); + CommandSystem.Register("StartAllRegionSpawns", AccessLevel.Administrator, StartAllRegionSpawns_OnCommand); + CommandSystem.Register("StartRegionSpawns", AccessLevel.GameMaster, StartRegionSpawns_OnCommand); + CommandSystem.Register("StopAllRegionSpawns", AccessLevel.Administrator, StopAllRegionSpawns_OnCommand); + CommandSystem.Register("StopRegionSpawns", AccessLevel.GameMaster, StopRegionSpawns_OnCommand); + } + + private static BaseRegion GetCommandData(CommandEventArgs args) + { + Mobile from = args.Mobile; + + Region reg; + if (args.Length == 0) + { + reg = from.Region; + } + else + { + string name = args.GetString(0); + //reg = if (!from.Map.Regions.TryGetValue( name, out (Region) from.Map.Regions[name] )) + { + from.SendMessage("Could not find region '{0}'.", name); + return null; + } + } + + BaseRegion br = reg as BaseRegion; + + if (br?.Spawns == null) + { + from.SendMessage("There are no spawners in region '{0}'.", reg); + return null; + } + + return br; + } + + [Usage("RespawnAllRegions")] + [Description("Respawns all regions and sets the spawners as running.")] + private static void RespawnAllRegions_OnCommand(CommandEventArgs args) + { + foreach (SpawnEntry entry in Table.Values) entry.Respawn(); + + args.Mobile.SendMessage("All regions have respawned."); + } + + [Usage("RespawnRegion []")] + [Description("Respawns the region in which you are (or that you provided) and sets the spawners as running.")] + private static void RespawnRegion_OnCommand(CommandEventArgs args) + { + BaseRegion region = GetCommandData(args); + + if (region == null) + return; + + for (int i = 0; i < region.Spawns.Length; i++) + region.Spawns[i].Respawn(); + + args.Mobile.SendMessage("Region '{0}' has respawned.", region); + } + + [Usage("DelAllRegionSpawns")] + [Description("Deletes all spawned objects of every regions and sets the spawners as not running.")] + private static void DelAllRegionSpawns_OnCommand(CommandEventArgs args) + { + foreach (SpawnEntry entry in Table.Values) entry.DeleteSpawnedObjects(); + + args.Mobile.SendMessage("All region spawned objects have been deleted."); + } + + [Usage("DelRegionSpawns []")] + [Description( + "Deletes all spawned objects of the region in which you are (or that you provided) and sets the spawners as not running.")] + private static void DelRegionSpawns_OnCommand(CommandEventArgs args) + { + BaseRegion region = GetCommandData(args); + + if (region == null) + return; + + for (int i = 0; i < region.Spawns.Length; i++) + region.Spawns[i].DeleteSpawnedObjects(); + + args.Mobile.SendMessage("Spawned objects of region '{0}' have been deleted.", region); + } + + [Usage("StartAllRegionSpawns")] + [Description("Sets the region spawners of all regions as running.")] + private static void StartAllRegionSpawns_OnCommand(CommandEventArgs args) + { + foreach (SpawnEntry entry in Table.Values) entry.Start(); + + args.Mobile.SendMessage("All region spawners have started."); + } + + [Usage("StartRegionSpawns []")] + [Description("Sets the region spawners of the region in which you are (or that you provided) as running.")] + private static void StartRegionSpawns_OnCommand(CommandEventArgs args) + { + BaseRegion region = GetCommandData(args); + + if (region == null) + return; + + for (int i = 0; i < region.Spawns.Length; i++) + region.Spawns[i].Start(); + + args.Mobile.SendMessage("Spawners of region '{0}' have started.", region); + } + + [Usage("StopAllRegionSpawns")] + [Description("Sets the region spawners of all regions as not running.")] + private static void StopAllRegionSpawns_OnCommand(CommandEventArgs args) + { + foreach (SpawnEntry entry in Table.Values) entry.Stop(); + + args.Mobile.SendMessage("All region spawners have stopped."); + } + + [Usage("StopRegionSpawns []")] + [Description("Sets the region spawners of the region in which you are (or that you provided) as not running.")] + private static void StopRegionSpawns_OnCommand(CommandEventArgs args) + { + BaseRegion region = GetCommandData(args); + + if (region == null) + return; + + for (int i = 0; i < region.Spawns.Length; i++) + region.Spawns[i].Stop(); + + args.Mobile.SendMessage("Spawners of region '{0}' have stopped.", region); + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/Spawning/SpawnPersistence.cs b/Scripts/Regions/Spawning/SpawnPersistence.cs index 6460e2ed1..a4a5f8647 100644 --- a/Scripts/Regions/Spawning/SpawnPersistence.cs +++ b/Scripts/Regions/Spawning/SpawnPersistence.cs @@ -1,63 +1,63 @@ namespace Server.Regions { - [TypeAlias( "Server.Regions.SpawnPersistance" )] - public class SpawnPersistence : Item - { - private static SpawnPersistence m_Instance; + [TypeAlias("Server.Regions.SpawnPersistance")] + public class SpawnPersistence : Item + { + private static SpawnPersistence m_Instance; - public SpawnPersistence Instance => m_Instance; + private SpawnPersistence() : base(1) + { + Movable = false; + } - public static void EnsureExistence() - { - if ( m_Instance == null ) - m_Instance = new SpawnPersistence(); - } + public SpawnPersistence(Serial serial) : base(serial) + { + m_Instance = this; + } - public override string DefaultName => "Region spawn persistence - Internal"; + public SpawnPersistence Instance => m_Instance; - private SpawnPersistence() : base( 1 ) - { - Movable = false; - } + public override string DefaultName => "Region spawn persistence - Internal"; - public SpawnPersistence( Serial serial ) : base( serial ) - { - m_Instance = this; - } + public static void EnsureExistence() + { + if (m_Instance == null) + m_Instance = new SpawnPersistence(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( (int) SpawnEntry.Table.Values.Count ); - foreach ( SpawnEntry entry in SpawnEntry.Table.Values ) - { - writer.Write( (int) entry.ID ); + writer.Write(SpawnEntry.Table.Values.Count); + foreach (SpawnEntry entry in SpawnEntry.Table.Values) + { + writer.Write(entry.ID); - entry.Serialize( writer ); - } - } + entry.Serialize(writer); + } + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - int count = reader.ReadInt(); - for ( int i = 0; i < count; i++ ) - { - int id = reader.ReadInt(); + int count = reader.ReadInt(); + for (int i = 0; i < count; i++) + { + int id = reader.ReadInt(); - SpawnEntry entry = (SpawnEntry) SpawnEntry.Table[id]; + SpawnEntry entry = (SpawnEntry)SpawnEntry.Table[id]; - if ( entry != null ) - entry.Deserialize( reader, version ); - else - SpawnEntry.Remove( reader, version ); - } - } - } -} + if (entry != null) + entry.Deserialize(reader, version); + else + SpawnEntry.Remove(reader, version); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Regions/TownRegion.cs b/Scripts/Regions/TownRegion.cs index caba15e5b..dc9fd46f1 100644 --- a/Scripts/Regions/TownRegion.cs +++ b/Scripts/Regions/TownRegion.cs @@ -2,10 +2,10 @@ using System.Xml; namespace Server.Regions { - public class TownRegion : GuardedRegion - { - public TownRegion( XmlElement xml, Map map, Region parent ) : base( xml, map, parent ) - { - } - } + public class TownRegion : GuardedRegion + { + public TownRegion(XmlElement xml, Map map, Region parent) : base(xml, map, parent) + { + } + } } \ No newline at end of file diff --git a/Scripts/Skills/Anatomy.cs b/Scripts/Skills/Anatomy.cs index 44e18a6d9..dfa1148ff 100644 --- a/Scripts/Skills/Anatomy.cs +++ b/Scripts/Skills/Anatomy.cs @@ -5,82 +5,89 @@ using Server.Targeting; namespace Server.SkillHandlers { - public class Anatomy - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Anatomy].Callback = OnUse; - } + public class Anatomy + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Anatomy].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile m) + { + m.Target = new InternalTarget(); - m.SendLocalizedMessage( 500321 ); // Whom shall I examine? + m.SendLocalizedMessage(500321); // Whom shall I examine? - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - private class InternalTarget : Target - { - public InternalTarget() : base ( 8, false, TargetFlags.None ) - { - } + private class InternalTarget : Target + { + public InternalTarget() : base(8, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( from == targeted ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500324 ); // You know yourself quite well enough already. - } - else if ( targeted is TownCrier ) - { - ((TownCrier)targeted).PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500322, from.NetState ); // This person looks fine to me, though he may have some news... - } - else if ( targeted is BaseVendor && ((BaseVendor)targeted).IsInvulnerable ) - { - ((BaseVendor)targeted).PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500326, from.NetState ); // That can not be inspected. - } - else if ( targeted is Mobile ) - { - Mobile targ = (Mobile)targeted; + protected override void OnTarget(Mobile from, object targeted) + { + if (from == targeted) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 500324); // You know yourself quite well enough already. + } + else if (targeted is TownCrier) + { + ((TownCrier)targeted).PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500322, + from.NetState); // This person looks fine to me, though he may have some news... + } + else if (targeted is BaseVendor && ((BaseVendor)targeted).IsInvulnerable) + { + ((BaseVendor)targeted).PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500326, + from.NetState); // That can not be inspected. + } + else if (targeted is Mobile) + { + Mobile targ = (Mobile)targeted; - int marginOfError = Math.Max( 0, 25 - (int)(from.Skills[SkillName.Anatomy].Value / 4) ); + int marginOfError = Math.Max(0, 25 - (int)(from.Skills[SkillName.Anatomy].Value / 4)); - int str = targ.Str + Utility.RandomMinMax( -marginOfError, +marginOfError ); - int dex = targ.Dex + Utility.RandomMinMax( -marginOfError, +marginOfError ); - int stm = ((targ.Stam * 100) / Math.Max( targ.StamMax, 1 )) + Utility.RandomMinMax( -marginOfError, +marginOfError ); + int str = targ.Str + Utility.RandomMinMax(-marginOfError, +marginOfError); + int dex = targ.Dex + Utility.RandomMinMax(-marginOfError, +marginOfError); + int stm = targ.Stam * 100 / Math.Max(targ.StamMax, 1) + + Utility.RandomMinMax(-marginOfError, +marginOfError); - int strMod = str / 10; - int dexMod = dex / 10; - int stmMod = stm / 10; + int strMod = str / 10; + int dexMod = dex / 10; + int stmMod = stm / 10; - if ( strMod < 0 ) strMod = 0; - else if ( strMod > 10 ) strMod = 10; + if (strMod < 0) strMod = 0; + else if (strMod > 10) strMod = 10; - if ( dexMod < 0 ) dexMod = 0; - else if ( dexMod > 10 ) dexMod = 10; + if (dexMod < 0) dexMod = 0; + else if (dexMod > 10) dexMod = 10; - if ( stmMod > 10 ) stmMod = 10; - else if ( stmMod < 0 ) stmMod = 0; + if (stmMod > 10) stmMod = 10; + else if (stmMod < 0) stmMod = 0; - if ( from.CheckTargetSkill( SkillName.Anatomy, targ, 0, 100 ) ) - { - targ.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1038045 + (strMod * 11) + dexMod, from.NetState ); // That looks [strong] and [dexterous]. + if (from.CheckTargetSkill(SkillName.Anatomy, targ, 0, 100)) + { + targ.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1038045 + strMod * 11 + dexMod, + from.NetState); // That looks [strong] and [dexterous]. - if ( from.Skills[SkillName.Anatomy].Base >= 65.0 ) - targ.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1038303 + stmMod, from.NetState ); // That being is at [10,20,...] percent endurance. - } - else - { - targ.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042666, from.NetState ); // You can not quite get a sense of their physical characteristics. - } - } - else - { - (targeted as Item)?.SendLocalizedMessageTo( from, 500323, "" ); // Only living things have anatomies! - } - } - } - } -} + if (from.Skills[SkillName.Anatomy].Base >= 65.0) + targ.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1038303 + stmMod, + from.NetState); // That being is at [10,20,...] percent endurance. + } + else + { + targ.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042666, + from.NetState); // You can not quite get a sense of their physical characteristics. + } + } + else + { + (targeted as Item)?.SendLocalizedMessageTo(from, 500323, ""); // Only living things have anatomies! + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/AnimalLore.cs b/Scripts/Skills/AnimalLore.cs index 495a10d90..6f00b78ff 100644 --- a/Scripts/Skills/AnimalLore.cs +++ b/Scripts/Skills/AnimalLore.cs @@ -1,385 +1,406 @@ using System; using Server.Gumps; +using Server.Items; using Server.Mobiles; using Server.Targeting; namespace Server.SkillHandlers { - public class AnimalLore - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.AnimalLore].Callback = OnUse; - } - - public static TimeSpan OnUse(Mobile m) - { - m.Target = new InternalTarget(); - - m.SendLocalizedMessage( 500328 ); // What animal should I look at? - - return TimeSpan.FromSeconds( 1.0 ); - } - - private class InternalTarget : Target - { - public InternalTarget() : base( 8, false, TargetFlags.None ) - { - } - - protected override void OnTarget( Mobile from, object targeted ) - { - if ( !from.Alive ) - { - from.SendLocalizedMessage( 500331 ); // The spirits of the dead are not the province of animal lore. - } - else if ( targeted is BaseCreature ) - { - BaseCreature c = (BaseCreature)targeted; - - if ( !c.IsDeadPet ) - { - if ( c.Body.IsAnimal || c.Body.IsMonster || c.Body.IsSea ) - { - if ( !c.Controlled && from.Skills[SkillName.AnimalLore].Value < 100.0 ) - { - from.SendLocalizedMessage( 1049674 ); // At your skill level, you can only lore tamed creatures. - } - else if ( !c.Controlled && !c.Tamable && from.Skills[SkillName.AnimalLore].Value < 110.0 ) - { - from.SendLocalizedMessage( 1049675 ); // At your skill level, you can only lore tamed or tameable creatures. - } - else if ( !from.CheckTargetSkill( SkillName.AnimalLore, c, 0.0, 120.0 ) ) - { - from.SendLocalizedMessage( 500334 ); // You can't think of anything you know offhand. - } - else - { - from.CloseGump( typeof( AnimalLoreGump ) ); - from.SendGump( new AnimalLoreGump( c ) ); - } - } - else - { - from.SendLocalizedMessage( 500329 ); // That's not an animal! - } - } - else - { - from.SendLocalizedMessage( 500331 ); // The spirits of the dead are not the province of animal lore. - } - } - else - { - from.SendLocalizedMessage( 500329 ); // That's not an animal! - } - } - } - } - - public class AnimalLoreGump : Gump - { - private static string FormatSkill( BaseCreature c, SkillName name ) - { - Skill skill = c.Skills[name]; - - if ( skill.Base < 10.0 ) - return "
---
"; - - return $"
{skill.Value:F1}
"; - } - - private static string FormatAttributes( int cur, int max ) - { - if ( max == 0 ) - return "
---
"; - - return $"
{cur}/{max}
"; - } - - private static string FormatStat( int val ) - { - if ( val == 0 ) - return "
---
"; - - return $"
{val}
"; - } - - private static string FormatDouble( double val ) - { - if ( val == 0 ) - return "
---
"; - - return $"
{val:F1}
"; - } - - private static string FormatElement( int val ) - { - if ( val <= 0 ) - return "
---
"; - - return $"
{val}%
"; - } - - #region Mondain's Legacy - private static string FormatDamage( int min, int max ) - { - if ( min <= 0 || max <= 0 ) - return "
---
"; - - return $"
{min}-{max}
"; - } - #endregion - - private const int LabelColor = 0x24E5; - - public AnimalLoreGump( BaseCreature c ) : base( 250, 50 ) - { - AddPage( 0 ); - - AddImage( 100, 100, 2080 ); - AddImage( 118, 137, 2081 ); - AddImage( 118, 207, 2081 ); - AddImage( 118, 277, 2081 ); - AddImage( 118, 347, 2083 ); - - AddHtml( 147, 108, 210, 18, $"
{c.Name}
", false, false ); - - AddButton( 240, 77, 2093, 2093, 2, GumpButtonType.Reply, 0 ); - - AddImage( 140, 138, 2091 ); - AddImage( 140, 335, 2091 ); - - int pages = ( Core.AOS ? 5 : 3 ); - int page = 0; - - - #region Attributes - AddPage( ++page ); + public class AnimalLore + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.AnimalLore].Callback = OnUse; + } + + public static TimeSpan OnUse(Mobile m) + { + m.Target = new InternalTarget(); + + m.SendLocalizedMessage(500328); // What animal should I look at? + + return TimeSpan.FromSeconds(1.0); + } + + private class InternalTarget : Target + { + public InternalTarget() : base(8, false, TargetFlags.None) + { + } + + protected override void OnTarget(Mobile from, object targeted) + { + if (!from.Alive) + { + from.SendLocalizedMessage(500331); // The spirits of the dead are not the province of animal lore. + } + else if (targeted is BaseCreature) + { + BaseCreature c = (BaseCreature)targeted; + + if (!c.IsDeadPet) + { + if (c.Body.IsAnimal || c.Body.IsMonster || c.Body.IsSea) + { + if (!c.Controlled && from.Skills[SkillName.AnimalLore].Value < 100.0) + { + from.SendLocalizedMessage( + 1049674); // At your skill level, you can only lore tamed creatures. + } + else if (!c.Controlled && !c.Tamable && from.Skills[SkillName.AnimalLore].Value < 110.0) + { + from.SendLocalizedMessage( + 1049675); // At your skill level, you can only lore tamed or tameable creatures. + } + else if (!from.CheckTargetSkill(SkillName.AnimalLore, c, 0.0, 120.0)) + { + from.SendLocalizedMessage(500334); // You can't think of anything you know offhand. + } + else + { + from.CloseGump(typeof(AnimalLoreGump)); + from.SendGump(new AnimalLoreGump(c)); + } + } + else + { + from.SendLocalizedMessage(500329); // That's not an animal! + } + } + else + { + from.SendLocalizedMessage(500331); // The spirits of the dead are not the province of animal lore. + } + } + else + { + from.SendLocalizedMessage(500329); // That's not an animal! + } + } + } + } + + public class AnimalLoreGump : Gump + { + private const int LabelColor = 0x24E5; + + public AnimalLoreGump(BaseCreature c) : base(250, 50) + { + AddPage(0); + + AddImage(100, 100, 2080); + AddImage(118, 137, 2081); + AddImage(118, 207, 2081); + AddImage(118, 277, 2081); + AddImage(118, 347, 2083); + + AddHtml(147, 108, 210, 18, $"
{c.Name}
", false, false); + + AddButton(240, 77, 2093, 2093, 2, GumpButtonType.Reply, 0); + + AddImage(140, 138, 2091); + AddImage(140, 335, 2091); + + int pages = Core.AOS ? 5 : 3; + int page = 0; + + + #region Attributes + + AddPage(++page); + + AddImage(128, 152, 2086); + AddHtmlLocalized(147, 150, 160, 18, 1049593, 200, false, false); // Attributes + + AddHtmlLocalized(153, 168, 160, 18, 1049578, LabelColor, false, false); // Hits + AddHtml(280, 168, 75, 18, FormatAttributes(c.Hits, c.HitsMax), false, false); + + AddHtmlLocalized(153, 186, 160, 18, 1049579, LabelColor, false, false); // Stamina + AddHtml(280, 186, 75, 18, FormatAttributes(c.Stam, c.StamMax), false, false); + + AddHtmlLocalized(153, 204, 160, 18, 1049580, LabelColor, false, false); // Mana + AddHtml(280, 204, 75, 18, FormatAttributes(c.Mana, c.ManaMax), false, false); + + AddHtmlLocalized(153, 222, 160, 18, 1028335, LabelColor, false, false); // Strength + AddHtml(320, 222, 35, 18, FormatStat(c.Str), false, false); + + AddHtmlLocalized(153, 240, 160, 18, 3000113, LabelColor, false, false); // Dexterity + AddHtml(320, 240, 35, 18, FormatStat(c.Dex), false, false); + + AddHtmlLocalized(153, 258, 160, 18, 3000112, LabelColor, false, false); // Intelligence + AddHtml(320, 258, 35, 18, FormatStat(c.Int), false, false); + + if (Core.AOS) + { + int y = 276; + + if (Core.SE) + { + double bd = BaseInstrument.GetBaseDifficulty(c); + if (c.Uncalmable) + bd = 0; - AddImage( 128, 152, 2086 ); - AddHtmlLocalized( 147, 150, 160, 18, 1049593, 200, false, false ); // Attributes + AddHtmlLocalized(153, 276, 160, 18, 1070793, LabelColor, false, false); // Barding Difficulty + AddHtml(320, y, 35, 18, FormatDouble(bd), false, false); - AddHtmlLocalized( 153, 168, 160, 18, 1049578, LabelColor, false, false ); // Hits - AddHtml( 280, 168, 75, 18, FormatAttributes( c.Hits, c.HitsMax ), false, false ); + y += 18; + } - AddHtmlLocalized( 153, 186, 160, 18, 1049579, LabelColor, false, false ); // Stamina - AddHtml( 280, 186, 75, 18, FormatAttributes( c.Stam, c.StamMax ), false, false ); + AddImage(128, y + 2, 2086); + AddHtmlLocalized(147, y, 160, 18, 1049594, 200, false, false); // Loyalty Rating + y += 18; - AddHtmlLocalized( 153, 204, 160, 18, 1049580, LabelColor, false, false ); // Mana - AddHtml( 280, 204, 75, 18, FormatAttributes( c.Mana, c.ManaMax ), false, false ); + AddHtmlLocalized(153, y, 160, 18, !c.Controlled || c.Loyalty == 0 ? 1061643 : 1049595 + c.Loyalty / 10, + LabelColor, false, false); + } + else + { + AddImage(128, 278, 2086); + AddHtmlLocalized(147, 276, 160, 18, 3001016, 200, false, false); // Miscellaneous - AddHtmlLocalized( 153, 222, 160, 18, 1028335, LabelColor, false, false ); // Strength - AddHtml( 320, 222, 35, 18, FormatStat( c.Str ), false, false ); + AddHtmlLocalized(153, 294, 160, 18, 1049581, LabelColor, false, false); // Armor Rating + AddHtml(320, 294, 35, 18, FormatStat(c.VirtualArmor), false, false); + } - AddHtmlLocalized( 153, 240, 160, 18, 3000113, LabelColor, false, false ); // Dexterity - AddHtml( 320, 240, 35, 18, FormatStat( c.Dex ), false, false ); + AddButton(340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1); + AddButton(317, 358, 5603, 5607, 0, GumpButtonType.Page, pages); - AddHtmlLocalized( 153, 258, 160, 18, 3000112, LabelColor, false, false ); // Intelligence - AddHtml( 320, 258, 35, 18, FormatStat( c.Int ), false, false ); + #endregion - if ( Core.AOS ) - { - int y = 276; + #region Resistances - if ( Core.SE ) - { - double bd = Items.BaseInstrument.GetBaseDifficulty( c ); - if ( c.Uncalmable ) - bd = 0; + if (Core.AOS) + { + AddPage(++page); - AddHtmlLocalized( 153, 276, 160, 18, 1070793, LabelColor, false, false ); // Barding Difficulty - AddHtml( 320, y, 35, 18, FormatDouble( bd ), false, false ); + AddImage(128, 152, 2086); + AddHtmlLocalized(147, 150, 160, 18, 1061645, 200, false, false); // Resistances - y += 18; - } + AddHtmlLocalized(153, 168, 160, 18, 1061646, LabelColor, false, false); // Physical + AddHtml(320, 168, 35, 18, FormatElement(c.PhysicalResistance), false, false); - AddImage( 128, y + 2, 2086 ); - AddHtmlLocalized( 147, y, 160, 18, 1049594, 200, false, false ); // Loyalty Rating - y += 18; + AddHtmlLocalized(153, 186, 160, 18, 1061647, LabelColor, false, false); // Fire + AddHtml(320, 186, 35, 18, FormatElement(c.FireResistance), false, false); - AddHtmlLocalized( 153, y, 160, 18, (!c.Controlled || c.Loyalty == 0) ? 1061643 : 1049595 + (c.Loyalty / 10), LabelColor, false, false ); - } - else - { - AddImage( 128, 278, 2086 ); - AddHtmlLocalized( 147, 276, 160, 18, 3001016, 200, false, false ); // Miscellaneous + AddHtmlLocalized(153, 204, 160, 18, 1061648, LabelColor, false, false); // Cold + AddHtml(320, 204, 35, 18, FormatElement(c.ColdResistance), false, false); - AddHtmlLocalized( 153, 294, 160, 18, 1049581, LabelColor, false, false ); // Armor Rating - AddHtml( 320, 294, 35, 18, FormatStat( c.VirtualArmor ), false, false ); - } + AddHtmlLocalized(153, 222, 160, 18, 1061649, LabelColor, false, false); // Poison + AddHtml(320, 222, 35, 18, FormatElement(c.PoisonResistance), false, false); - AddButton( 340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1 ); - AddButton( 317, 358, 5603, 5607, 0, GumpButtonType.Page, pages ); - #endregion + AddHtmlLocalized(153, 240, 160, 18, 1061650, LabelColor, false, false); // Energy + AddHtml(320, 240, 35, 18, FormatElement(c.EnergyResistance), false, false); - #region Resistances - if ( Core.AOS ) - { - AddPage( ++page ); + AddButton(340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1); + AddButton(317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1); + } - AddImage( 128, 152, 2086 ); - AddHtmlLocalized( 147, 150, 160, 18, 1061645, 200, false, false ); // Resistances + #endregion - AddHtmlLocalized( 153, 168, 160, 18, 1061646, LabelColor, false, false ); // Physical - AddHtml( 320, 168, 35, 18, FormatElement( c.PhysicalResistance ), false, false ); + #region Damage - AddHtmlLocalized( 153, 186, 160, 18, 1061647, LabelColor, false, false ); // Fire - AddHtml( 320, 186, 35, 18, FormatElement( c.FireResistance ), false, false ); + if (Core.AOS) + { + AddPage(++page); - AddHtmlLocalized( 153, 204, 160, 18, 1061648, LabelColor, false, false ); // Cold - AddHtml( 320, 204, 35, 18, FormatElement( c.ColdResistance ), false, false ); + AddImage(128, 152, 2086); + AddHtmlLocalized(147, 150, 160, 18, 1017319, 200, false, false); // Damage - AddHtmlLocalized( 153, 222, 160, 18, 1061649, LabelColor, false, false ); // Poison - AddHtml( 320, 222, 35, 18, FormatElement( c.PoisonResistance ), false, false ); + AddHtmlLocalized(153, 168, 160, 18, 1061646, LabelColor, false, false); // Physical + AddHtml(320, 168, 35, 18, FormatElement(c.PhysicalDamage), false, false); - AddHtmlLocalized( 153, 240, 160, 18, 1061650, LabelColor, false, false ); // Energy - AddHtml( 320, 240, 35, 18, FormatElement( c.EnergyResistance ), false, false ); + AddHtmlLocalized(153, 186, 160, 18, 1061647, LabelColor, false, false); // Fire + AddHtml(320, 186, 35, 18, FormatElement(c.FireDamage), false, false); - AddButton( 340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1 ); - AddButton( 317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1 ); - } - #endregion + AddHtmlLocalized(153, 204, 160, 18, 1061648, LabelColor, false, false); // Cold + AddHtml(320, 204, 35, 18, FormatElement(c.ColdDamage), false, false); - #region Damage - if ( Core.AOS ) - { - AddPage( ++page ); + AddHtmlLocalized(153, 222, 160, 18, 1061649, LabelColor, false, false); // Poison + AddHtml(320, 222, 35, 18, FormatElement(c.PoisonDamage), false, false); - AddImage( 128, 152, 2086 ); - AddHtmlLocalized( 147, 150, 160, 18, 1017319, 200, false, false ); // Damage + AddHtmlLocalized(153, 240, 160, 18, 1061650, LabelColor, false, false); // Energy + AddHtml(320, 240, 35, 18, FormatElement(c.EnergyDamage), false, false); - AddHtmlLocalized( 153, 168, 160, 18, 1061646, LabelColor, false, false ); // Physical - AddHtml( 320, 168, 35, 18, FormatElement( c.PhysicalDamage ), false, false ); + #region Mondain's Legacy - AddHtmlLocalized( 153, 186, 160, 18, 1061647, LabelColor, false, false ); // Fire - AddHtml( 320, 186, 35, 18, FormatElement( c.FireDamage ), false, false ); + if (Core.ML) + { + AddHtmlLocalized(153, 258, 160, 18, 1076750, LabelColor, false, false); // Base Damage + AddHtml(300, 258, 55, 18, FormatDamage(c.DamageMin, c.DamageMax), false, false); + } - AddHtmlLocalized( 153, 204, 160, 18, 1061648, LabelColor, false, false ); // Cold - AddHtml( 320, 204, 35, 18, FormatElement( c.ColdDamage ), false, false ); + #endregion - AddHtmlLocalized( 153, 222, 160, 18, 1061649, LabelColor, false, false ); // Poison - AddHtml( 320, 222, 35, 18, FormatElement( c.PoisonDamage ), false, false ); + AddButton(340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1); + AddButton(317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1); + } - AddHtmlLocalized( 153, 240, 160, 18, 1061650, LabelColor, false, false ); // Energy - AddHtml( 320, 240, 35, 18, FormatElement( c.EnergyDamage ), false, false ); - - #region Mondain's Legacy - if ( Core.ML ) - { - AddHtmlLocalized( 153, 258, 160, 18, 1076750, LabelColor, false, false ); // Base Damage - AddHtml( 300, 258, 55, 18, FormatDamage( c.DamageMin, c.DamageMax ), false, false ); - } - #endregion - - AddButton( 340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1 ); - AddButton( 317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1 ); - } - #endregion - - #region Skills - AddPage( ++page ); - - AddImage( 128, 152, 2086 ); - AddHtmlLocalized( 147, 150, 160, 18, 3001030, 200, false, false ); // Combat Ratings - - AddHtmlLocalized( 153, 168, 160, 18, 1044103, LabelColor, false, false ); // Wrestling - AddHtml( 320, 168, 35, 18, FormatSkill( c, SkillName.Wrestling ), false, false ); - - AddHtmlLocalized( 153, 186, 160, 18, 1044087, LabelColor, false, false ); // Tactics - AddHtml( 320, 186, 35, 18, FormatSkill( c, SkillName.Tactics ), false, false ); - - AddHtmlLocalized( 153, 204, 160, 18, 1044086, LabelColor, false, false ); // Magic Resistance - AddHtml( 320, 204, 35, 18, FormatSkill( c, SkillName.MagicResist ), false, false ); - - AddHtmlLocalized( 153, 222, 160, 18, 1044061, LabelColor, false, false ); // Anatomy - AddHtml( 320, 222, 35, 18, FormatSkill( c, SkillName.Anatomy ), false, false ); - - #region Mondain's Legacy - if ( c is CuSidhe ) - { - AddHtmlLocalized( 153, 240, 160, 18, 1044077, LabelColor, false, false ); // Healing - AddHtml( 320, 240, 35, 18, FormatSkill( c, SkillName.Healing ), false, false ); - } - else - { - AddHtmlLocalized( 153, 240, 160, 18, 1044090, LabelColor, false, false ); // Poisoning - AddHtml( 320, 240, 35, 18, FormatSkill( c, SkillName.Poisoning ), false, false ); - } - #endregion - - AddImage( 128, 260, 2086 ); - AddHtmlLocalized( 147, 258, 160, 18, 3001032, 200, false, false ); // Lore & Knowledge - - AddHtmlLocalized( 153, 276, 160, 18, 1044085, LabelColor, false, false ); // Magery - AddHtml( 320, 276, 35, 18, FormatSkill( c, SkillName.Magery ), false, false ); - - AddHtmlLocalized( 153, 294, 160, 18, 1044076, LabelColor, false, false ); // Evaluating Intelligence - AddHtml( 320, 294, 35, 18,FormatSkill( c, SkillName.EvalInt ), false, false ); - - AddHtmlLocalized( 153, 312, 160, 18, 1044106, LabelColor, false, false ); // Meditation - AddHtml( 320, 312, 35, 18, FormatSkill( c, SkillName.Meditation ), false, false ); - - AddButton( 340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1 ); - AddButton( 317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1 ); - #endregion - - #region Misc - AddPage( ++page ); - - AddImage( 128, 152, 2086 ); - AddHtmlLocalized( 147, 150, 160, 18, 1049563, 200, false, false ); // Preferred Foods - - int foodPref = 3000340; - - if ( (c.FavoriteFood & FoodType.FruitsAndVegies) != 0 ) - foodPref = 1049565; // Fruits and Vegetables - else if ( (c.FavoriteFood & FoodType.GrainsAndHay) != 0 ) - foodPref = 1049566; // Grains and Hay - else if ( (c.FavoriteFood & FoodType.Fish) != 0 ) - foodPref = 1049568; // Fish - else if ( (c.FavoriteFood & FoodType.Meat) != 0 ) - foodPref = 1049564; // Meat - else if ( (c.FavoriteFood & FoodType.Eggs) != 0 ) - foodPref = 1044477; // Eggs - - AddHtmlLocalized( 153, 168, 160, 18, foodPref, LabelColor, false, false ); - - AddImage( 128, 188, 2086 ); - AddHtmlLocalized( 147, 186, 160, 18, 1049569, 200, false, false ); // Pack Instincts - - int packInstinct = 3000340; - - if ( (c.PackInstinct & PackInstinct.Canine) != 0 ) - packInstinct = 1049570; // Canine - else if ( (c.PackInstinct & PackInstinct.Ostard) != 0 ) - packInstinct = 1049571; // Ostard - else if ( (c.PackInstinct & PackInstinct.Feline) != 0 ) - packInstinct = 1049572; // Feline - else if ( (c.PackInstinct & PackInstinct.Arachnid) != 0 ) - packInstinct = 1049573; // Arachnid - else if ( (c.PackInstinct & PackInstinct.Daemon) != 0 ) - packInstinct = 1049574; // Daemon - else if ( (c.PackInstinct & PackInstinct.Bear) != 0 ) - packInstinct = 1049575; // Bear - else if ( (c.PackInstinct & PackInstinct.Equine) != 0 ) - packInstinct = 1049576; // Equine - else if ( (c.PackInstinct & PackInstinct.Bull) != 0 ) - packInstinct = 1049577; // Bull - - AddHtmlLocalized( 153, 204, 160, 18, packInstinct, LabelColor, false, false ); - - if ( !Core.AOS ) - { - AddImage( 128, 224, 2086 ); - AddHtmlLocalized( 147, 222, 160, 18, 1049594, 200, false, false ); // Loyalty Rating - - AddHtmlLocalized( 153, 240, 160, 18, (!c.Controlled || c.Loyalty == 0) ? 1061643 : 1049595 + (c.Loyalty / 10), LabelColor, false, false ); - } - - AddButton( 340, 358, 5601, 5605, 0, GumpButtonType.Page, 1 ); - AddButton( 317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1 ); - #endregion - } - } + #endregion + + #region Skills + + AddPage(++page); + + AddImage(128, 152, 2086); + AddHtmlLocalized(147, 150, 160, 18, 3001030, 200, false, false); // Combat Ratings + + AddHtmlLocalized(153, 168, 160, 18, 1044103, LabelColor, false, false); // Wrestling + AddHtml(320, 168, 35, 18, FormatSkill(c, SkillName.Wrestling), false, false); + + AddHtmlLocalized(153, 186, 160, 18, 1044087, LabelColor, false, false); // Tactics + AddHtml(320, 186, 35, 18, FormatSkill(c, SkillName.Tactics), false, false); + + AddHtmlLocalized(153, 204, 160, 18, 1044086, LabelColor, false, false); // Magic Resistance + AddHtml(320, 204, 35, 18, FormatSkill(c, SkillName.MagicResist), false, false); + + AddHtmlLocalized(153, 222, 160, 18, 1044061, LabelColor, false, false); // Anatomy + AddHtml(320, 222, 35, 18, FormatSkill(c, SkillName.Anatomy), false, false); + + #region Mondain's Legacy + + if (c is CuSidhe) + { + AddHtmlLocalized(153, 240, 160, 18, 1044077, LabelColor, false, false); // Healing + AddHtml(320, 240, 35, 18, FormatSkill(c, SkillName.Healing), false, false); + } + else + { + AddHtmlLocalized(153, 240, 160, 18, 1044090, LabelColor, false, false); // Poisoning + AddHtml(320, 240, 35, 18, FormatSkill(c, SkillName.Poisoning), false, false); + } + + #endregion + + AddImage(128, 260, 2086); + AddHtmlLocalized(147, 258, 160, 18, 3001032, 200, false, false); // Lore & Knowledge + + AddHtmlLocalized(153, 276, 160, 18, 1044085, LabelColor, false, false); // Magery + AddHtml(320, 276, 35, 18, FormatSkill(c, SkillName.Magery), false, false); + + AddHtmlLocalized(153, 294, 160, 18, 1044076, LabelColor, false, false); // Evaluating Intelligence + AddHtml(320, 294, 35, 18, FormatSkill(c, SkillName.EvalInt), false, false); + + AddHtmlLocalized(153, 312, 160, 18, 1044106, LabelColor, false, false); // Meditation + AddHtml(320, 312, 35, 18, FormatSkill(c, SkillName.Meditation), false, false); + + AddButton(340, 358, 5601, 5605, 0, GumpButtonType.Page, page + 1); + AddButton(317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1); + + #endregion + + #region Misc + + AddPage(++page); + + AddImage(128, 152, 2086); + AddHtmlLocalized(147, 150, 160, 18, 1049563, 200, false, false); // Preferred Foods + + int foodPref = 3000340; + + if ((c.FavoriteFood & FoodType.FruitsAndVegies) != 0) + foodPref = 1049565; // Fruits and Vegetables + else if ((c.FavoriteFood & FoodType.GrainsAndHay) != 0) + foodPref = 1049566; // Grains and Hay + else if ((c.FavoriteFood & FoodType.Fish) != 0) + foodPref = 1049568; // Fish + else if ((c.FavoriteFood & FoodType.Meat) != 0) + foodPref = 1049564; // Meat + else if ((c.FavoriteFood & FoodType.Eggs) != 0) + foodPref = 1044477; // Eggs + + AddHtmlLocalized(153, 168, 160, 18, foodPref, LabelColor, false, false); + + AddImage(128, 188, 2086); + AddHtmlLocalized(147, 186, 160, 18, 1049569, 200, false, false); // Pack Instincts + + int packInstinct = 3000340; + + if ((c.PackInstinct & PackInstinct.Canine) != 0) + packInstinct = 1049570; // Canine + else if ((c.PackInstinct & PackInstinct.Ostard) != 0) + packInstinct = 1049571; // Ostard + else if ((c.PackInstinct & PackInstinct.Feline) != 0) + packInstinct = 1049572; // Feline + else if ((c.PackInstinct & PackInstinct.Arachnid) != 0) + packInstinct = 1049573; // Arachnid + else if ((c.PackInstinct & PackInstinct.Daemon) != 0) + packInstinct = 1049574; // Daemon + else if ((c.PackInstinct & PackInstinct.Bear) != 0) + packInstinct = 1049575; // Bear + else if ((c.PackInstinct & PackInstinct.Equine) != 0) + packInstinct = 1049576; // Equine + else if ((c.PackInstinct & PackInstinct.Bull) != 0) + packInstinct = 1049577; // Bull + + AddHtmlLocalized(153, 204, 160, 18, packInstinct, LabelColor, false, false); + + if (!Core.AOS) + { + AddImage(128, 224, 2086); + AddHtmlLocalized(147, 222, 160, 18, 1049594, 200, false, false); // Loyalty Rating + + AddHtmlLocalized(153, 240, 160, 18, !c.Controlled || c.Loyalty == 0 ? 1061643 : 1049595 + c.Loyalty / 10, + LabelColor, false, false); + } + + AddButton(340, 358, 5601, 5605, 0, GumpButtonType.Page, 1); + AddButton(317, 358, 5603, 5607, 0, GumpButtonType.Page, page - 1); + + #endregion + } + + private static string FormatSkill(BaseCreature c, SkillName name) + { + Skill skill = c.Skills[name]; + + if (skill.Base < 10.0) + return "
---
"; + + return $"
{skill.Value:F1}
"; + } + + private static string FormatAttributes(int cur, int max) + { + if (max == 0) + return "
---
"; + + return $"
{cur}/{max}
"; + } + + private static string FormatStat(int val) + { + if (val == 0) + return "
---
"; + + return $"
{val}
"; + } + + private static string FormatDouble(double val) + { + if (val == 0) + return "
---
"; + + return $"
{val:F1}
"; + } + + private static string FormatElement(int val) + { + if (val <= 0) + return "
---
"; + + return $"
{val}%
"; + } + + #region Mondain's Legacy + + private static string FormatDamage(int min, int max) + { + if (min <= 0 || max <= 0) + return "
---
"; + + return $"
{min}-{max}
"; + } + + #endregion + } } \ No newline at end of file diff --git a/Scripts/Skills/AnimalTaming.cs b/Scripts/Skills/AnimalTaming.cs index d437f7dd2..b07ca2ef5 100644 --- a/Scripts/Skills/AnimalTaming.cs +++ b/Scripts/Skills/AnimalTaming.cs @@ -1,404 +1,437 @@ using System; using System.Collections.Generic; -using Server.Targeting; -using Server.Network; -using Server.Mobiles; using Server.Factions; +using Server.Mobiles; +using Server.Network; using Server.Spells; +using Server.Spells.Necromancy; using Server.Spells.Spellweaving; +using Server.Targeting; namespace Server.SkillHandlers { - public class AnimalTaming - { - private static Dictionary m_BeingTamed = new Dictionary(); + public class AnimalTaming + { + private static Dictionary m_BeingTamed = new Dictionary(); - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.AnimalTaming].Callback = OnUse; - } + public static bool DisableMessage{ get; set; } - public static bool DisableMessage { get; set; } + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.AnimalTaming].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.RevealingAction(); + public static TimeSpan OnUse(Mobile m) + { + m.RevealingAction(); - m.Target = new InternalTarget(); - m.RevealingAction(); + m.Target = new InternalTarget(); + m.RevealingAction(); - if ( !DisableMessage ) - m.SendLocalizedMessage( 502789 ); // Tame which animal? + if (!DisableMessage) + m.SendLocalizedMessage(502789); // Tame which animal? - return TimeSpan.FromHours( 6.0 ); - } + return TimeSpan.FromHours(6.0); + } - public static bool CheckMastery( Mobile tamer, BaseCreature creature ) - { - BaseCreature familiar = (BaseCreature)Spells.Necromancy.SummonFamiliarSpell.Table[tamer]; + public static bool CheckMastery(Mobile tamer, BaseCreature creature) + { + BaseCreature familiar = (BaseCreature)SummonFamiliarSpell.Table[tamer]; - if ( familiar != null && !familiar.Deleted && familiar is DarkWolfFamiliar ) - { - if ( creature is DireWolf || creature is GreyWolf || creature is TimberWolf || creature is WhiteWolf || creature is BakeKitsune ) - return true; - } + if (familiar != null && !familiar.Deleted && familiar is DarkWolfFamiliar) + if (creature is DireWolf || creature is GreyWolf || creature is TimberWolf || creature is WhiteWolf || + creature is BakeKitsune) + return true; - return false; - } + return false; + } - public static bool MustBeSubdued( BaseCreature bc ) - { - if (bc.Owners.Count > 0) { return false; } //Checks to see if the animal has been tamed before - return bc.SubdueBeforeTame && (bc.Hits > (bc.HitsMax / 10)); - } + public static bool MustBeSubdued(BaseCreature bc) + { + if (bc.Owners.Count > 0) return false; + return bc.SubdueBeforeTame && bc.Hits > bc.HitsMax / 10; + } - public static void ScaleStats( BaseCreature bc, double scalar ) - { - if ( bc.RawStr > 0 ) - bc.RawStr = (int)Math.Max( 1, bc.RawStr * scalar ); + public static void ScaleStats(BaseCreature bc, double scalar) + { + if (bc.RawStr > 0) + bc.RawStr = (int)Math.Max(1, bc.RawStr * scalar); - if ( bc.RawDex > 0 ) - bc.RawDex = (int)Math.Max( 1, bc.RawDex * scalar ); + if (bc.RawDex > 0) + bc.RawDex = (int)Math.Max(1, bc.RawDex * scalar); - if ( bc.RawInt > 0 ) - bc.RawInt = (int)Math.Max( 1, bc.RawInt * scalar ); + if (bc.RawInt > 0) + bc.RawInt = (int)Math.Max(1, bc.RawInt * scalar); - if ( bc.HitsMaxSeed > 0 ) - { - bc.HitsMaxSeed = (int)Math.Max( 1, bc.HitsMaxSeed * scalar ); - bc.Hits = bc.Hits; - } + if (bc.HitsMaxSeed > 0) + { + bc.HitsMaxSeed = (int)Math.Max(1, bc.HitsMaxSeed * scalar); + bc.Hits = bc.Hits; + } - if ( bc.StamMaxSeed > 0 ) - { - bc.StamMaxSeed = (int)Math.Max( 1, bc.StamMaxSeed * scalar ); - bc.Stam = bc.Stam; - } - } + if (bc.StamMaxSeed > 0) + { + bc.StamMaxSeed = (int)Math.Max(1, bc.StamMaxSeed * scalar); + bc.Stam = bc.Stam; + } + } - public static void ScaleSkills( BaseCreature bc, double scalar ) - { - ScaleSkills( bc, scalar, scalar ); - } + public static void ScaleSkills(BaseCreature bc, double scalar) + { + ScaleSkills(bc, scalar, scalar); + } - public static void ScaleSkills( BaseCreature bc, double scalar, double capScalar ) - { - for ( int i = 0; i < bc.Skills.Length; ++i ) - { - bc.Skills[i].Base *= scalar; + public static void ScaleSkills(BaseCreature bc, double scalar, double capScalar) + { + for (int i = 0; i < bc.Skills.Length; ++i) + { + bc.Skills[i].Base *= scalar; - bc.Skills[i].Cap = Math.Max( 100.0, bc.Skills[i].Cap * capScalar ); + bc.Skills[i].Cap = Math.Max(100.0, bc.Skills[i].Cap * capScalar); - if ( bc.Skills[i].Base > bc.Skills[i].Cap ) - { - bc.Skills[i].Cap = bc.Skills[i].Base; - } - } - } + if (bc.Skills[i].Base > bc.Skills[i].Cap) bc.Skills[i].Cap = bc.Skills[i].Base; + } + } - private class InternalTarget : Target - { - private bool m_SetSkillTime = true; + private class InternalTarget : Target + { + private bool m_SetSkillTime = true; - public InternalTarget() : base ( Core.AOS ? 3 : 2, false, TargetFlags.None ) - { - } + public InternalTarget() : base(Core.AOS ? 3 : 2, false, TargetFlags.None) + { + } - protected override void OnTargetFinish( Mobile from ) - { - if (m_SetSkillTime) - from.NextSkillTime = Core.TickCount; - } + protected override void OnTargetFinish(Mobile from) + { + if (m_SetSkillTime) + from.NextSkillTime = Core.TickCount; + } - public virtual void ResetPacify( object obj ) - { - if ( obj is BaseCreature ) - { - ((BaseCreature)obj).BardPacified = true; - } - } + public virtual void ResetPacify(object obj) + { + if (obj is BaseCreature) ((BaseCreature)obj).BardPacified = true; + } - protected override void OnTarget( Mobile from, object targeted ) - { - from.RevealingAction(); + protected override void OnTarget(Mobile from, object targeted) + { + from.RevealingAction(); - if ( targeted is Mobile ) - { - if ( targeted is BaseCreature ) - { - BaseCreature creature = (BaseCreature)targeted; + if (targeted is Mobile) + { + if (targeted is BaseCreature) + { + BaseCreature creature = (BaseCreature)targeted; - if ( !creature.Tamable ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1049655, from.NetState ); // That creature cannot be tamed. - } - else if ( creature.Controlled ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502804, from.NetState ); // That animal looks tame already. - } - else if ( from.Female && !creature.AllowFemaleTamer ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1049653, from.NetState ); // That creature can only be tamed by males. - } - else if ( !from.Female && !creature.AllowMaleTamer ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1049652, from.NetState ); // That creature can only be tamed by females. - } - else if ( creature is CuSidhe && from.Race != Race.Elf ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502801, from.NetState ); // You can't tame that! - } - else if ( from.Followers + creature.ControlSlots > from.FollowersMax ) - { - from.SendLocalizedMessage( 1049611 ); // You have too many followers to tame that creature. - } - else if ( creature.Owners.Count >= BaseCreature.MaxOwners && !creature.Owners.Contains( from ) ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1005615, from.NetState ); // This animal has had too many owners and is too upset for you to tame. - } - else if ( MustBeSubdued( creature ) ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1054025, from.NetState ); // You must subdue this creature before you can tame it! - } - else if ( CheckMastery( from, creature ) || from.Skills[SkillName.AnimalTaming].Value >= creature.MinTameSkill ) - { - FactionWarHorse warHorse = creature as FactionWarHorse; + if (!creature.Tamable) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1049655, + from.NetState); // That creature cannot be tamed. + } + else if (creature.Controlled) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502804, + from.NetState); // That animal looks tame already. + } + else if (from.Female && !creature.AllowFemaleTamer) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1049653, + from.NetState); // That creature can only be tamed by males. + } + else if (!from.Female && !creature.AllowMaleTamer) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1049652, + from.NetState); // That creature can only be tamed by females. + } + else if (creature is CuSidhe && from.Race != Race.Elf) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502801, + from.NetState); // You can't tame that! + } + else if (from.Followers + creature.ControlSlots > from.FollowersMax) + { + from.SendLocalizedMessage(1049611); // You have too many followers to tame that creature. + } + else if (creature.Owners.Count >= BaseCreature.MaxOwners && !creature.Owners.Contains(from)) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1005615, + from.NetState); // This animal has had too many owners and is too upset for you to tame. + } + else if (MustBeSubdued(creature)) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1054025, + from.NetState); // You must subdue this creature before you can tame it! + } + else if (CheckMastery(from, creature) || + from.Skills[SkillName.AnimalTaming].Value >= creature.MinTameSkill) + { + FactionWarHorse warHorse = creature as FactionWarHorse; - if ( warHorse != null ) - { - Faction faction = Faction.Find( from ); + if (warHorse != null) + { + Faction faction = Faction.Find(from); - if ( faction == null || faction != warHorse.Faction ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1042590, from.NetState ); // You cannot tame this creature. - return; - } - } + if (faction == null || faction != warHorse.Faction) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1042590, + from.NetState); // You cannot tame this creature. + return; + } + } - if ( m_BeingTamed.ContainsKey( creature ) ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502802, from.NetState ); // Someone else is already taming this. - } - else if ( creature.CanAngerOnTame && 0.95 >= Utility.RandomDouble() ) - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502805, from.NetState ); // You seem to anger the beast! - creature.PlaySound( creature.GetAngerSound() ); - creature.Direction = creature.GetDirectionTo( from ); + if (m_BeingTamed.ContainsKey(creature)) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502802, + from.NetState); // Someone else is already taming this. + } + else if (creature.CanAngerOnTame && 0.95 >= Utility.RandomDouble()) + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502805, + from.NetState); // You seem to anger the beast! + creature.PlaySound(creature.GetAngerSound()); + creature.Direction = creature.GetDirectionTo(from); - if ( creature.BardPacified && Utility.RandomDouble() > .24) - { - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), new TimerStateCallback( ResetPacify ), creature ); - } - else - { - creature.BardEndTime = DateTime.UtcNow; - } + if (creature.BardPacified && Utility.RandomDouble() > .24) + Timer.DelayCall(TimeSpan.FromSeconds(2.0), new TimerStateCallback(ResetPacify), + creature); + else + creature.BardEndTime = DateTime.UtcNow; - creature.BardPacified = false; + creature.BardPacified = false; - creature.AIObject?.DoMove( creature.Direction ); + creature.AIObject?.DoMove(creature.Direction); - if ( from is PlayerMobile && !(( (PlayerMobile)from ).HonorActive || TransformationSpellHelper.UnderTransformation( from, typeof( EtherealVoyageSpell )))) - creature.Combatant = from; - } - else - { - m_BeingTamed[creature] = from; + if (from is PlayerMobile && + !(((PlayerMobile)from).HonorActive || + TransformationSpellHelper.UnderTransformation(from, typeof(EtherealVoyageSpell)))) + creature.Combatant = from; + } + else + { + m_BeingTamed[creature] = from; - from.LocalOverheadMessage( MessageType.Emote, 0x59, 1010597 ); // You start to tame the creature. - from.NonlocalOverheadMessage( MessageType.Emote, 0x59, 1010598 ); // *begins taming a creature.* + from.LocalOverheadMessage(MessageType.Emote, 0x59, + 1010597); // You start to tame the creature. + from.NonlocalOverheadMessage(MessageType.Emote, 0x59, + 1010598); // *begins taming a creature.* - new InternalTimer( from, creature, Utility.Random( 3, 2 ) ).Start(); + new InternalTimer(from, creature, Utility.Random(3, 2)).Start(); - m_SetSkillTime = false; - } - } - else - { - creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502806, from.NetState ); // You have no chance of taming this creature. - } - } - else - { - ((Mobile)targeted).PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502469, from.NetState ); // That being cannot be tamed. - } - } - else - { - from.SendLocalizedMessage( 502801 ); // You can't tame that! - } - } + m_SetSkillTime = false; + } + } + else + { + creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502806, + from.NetState); // You have no chance of taming this creature. + } + } + else + { + ((Mobile)targeted).PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502469, + from.NetState); // That being cannot be tamed. + } + } + else + { + from.SendLocalizedMessage(502801); // You can't tame that! + } + } - private class InternalTimer : Timer - { - private Mobile m_Tamer; - private BaseCreature m_Creature; - private int m_MaxCount; - private int m_Count; - private bool m_Paralyzed; - private DateTime m_StartTime; + private class InternalTimer : Timer + { + private int m_Count; + private BaseCreature m_Creature; + private int m_MaxCount; + private bool m_Paralyzed; + private DateTime m_StartTime; + private Mobile m_Tamer; - public InternalTimer( Mobile tamer, BaseCreature creature, int count ) : base( TimeSpan.FromSeconds( 3.0 ), TimeSpan.FromSeconds( 3.0 ), count ) - { - m_Tamer = tamer; - m_Creature = creature; - m_MaxCount = count; - m_Paralyzed = creature.Paralyzed; - m_StartTime = DateTime.UtcNow; - Priority = TimerPriority.TwoFiftyMS; - } + public InternalTimer(Mobile tamer, BaseCreature creature, int count) : base(TimeSpan.FromSeconds(3.0), + TimeSpan.FromSeconds(3.0), count) + { + m_Tamer = tamer; + m_Creature = creature; + m_MaxCount = count; + m_Paralyzed = creature.Paralyzed; + m_StartTime = DateTime.UtcNow; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - m_Count++; + protected override void OnTick() + { + m_Count++; - DamageEntry de = m_Creature.FindMostRecentDamageEntry( false ); - bool alreadyOwned = m_Creature.Owners.Contains( m_Tamer ); + DamageEntry de = m_Creature.FindMostRecentDamageEntry(false); + bool alreadyOwned = m_Creature.Owners.Contains(m_Tamer); - if ( !m_Tamer.InRange( m_Creature, Core.AOS ? 7 : 6 ) ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502795, m_Tamer.NetState ); // You are too far away to continue taming. - Stop(); - } - else if ( !m_Tamer.CheckAlive() ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502796, m_Tamer.NetState ); // You are dead, and cannot continue taming. - Stop(); - } - else if ( !m_Tamer.CanSee( m_Creature ) || !m_Tamer.InLOS( m_Creature ) || !CanPath() ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Tamer.SendLocalizedMessage( 1049654 ); // You do not have a clear path to the animal you are taming, and must cease your attempt. - Stop(); - } - else if ( !m_Creature.Tamable ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1049655, m_Tamer.NetState ); // That creature cannot be tamed. - Stop(); - } - else if ( m_Creature.Controlled ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502804, m_Tamer.NetState ); // That animal looks tame already. - Stop(); - } - else if ( m_Creature.Owners.Count >= BaseCreature.MaxOwners && !m_Creature.Owners.Contains( m_Tamer ) ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1005615, m_Tamer.NetState ); // This animal has had too many owners and is too upset for you to tame. - Stop(); - } - else if ( MustBeSubdued( m_Creature ) ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1054025, m_Tamer.NetState ); // You must subdue this creature before you can tame it! - Stop(); - } - else if ( de != null && de.LastDamage > m_StartTime ) - { - m_BeingTamed.Remove( m_Creature ); - m_Tamer.NextSkillTime = Core.TickCount; - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502794, m_Tamer.NetState ); // The animal is too angry to continue taming. - Stop(); - } - else if ( m_Count < m_MaxCount ) - { - m_Tamer.RevealingAction(); + if (!m_Tamer.InRange(m_Creature, Core.AOS ? 7 : 6)) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502795, + m_Tamer.NetState); // You are too far away to continue taming. + Stop(); + } + else if (!m_Tamer.CheckAlive()) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502796, + m_Tamer.NetState); // You are dead, and cannot continue taming. + Stop(); + } + else if (!m_Tamer.CanSee(m_Creature) || !m_Tamer.InLOS(m_Creature) || !CanPath()) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Tamer.SendLocalizedMessage( + 1049654); // You do not have a clear path to the animal you are taming, and must cease your attempt. + Stop(); + } + else if (!m_Creature.Tamable) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1049655, + m_Tamer.NetState); // That creature cannot be tamed. + Stop(); + } + else if (m_Creature.Controlled) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502804, + m_Tamer.NetState); // That animal looks tame already. + Stop(); + } + else if (m_Creature.Owners.Count >= BaseCreature.MaxOwners && !m_Creature.Owners.Contains(m_Tamer)) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1005615, + m_Tamer.NetState); // This animal has had too many owners and is too upset for you to tame. + Stop(); + } + else if (MustBeSubdued(m_Creature)) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1054025, + m_Tamer.NetState); // You must subdue this creature before you can tame it! + Stop(); + } + else if (de != null && de.LastDamage > m_StartTime) + { + m_BeingTamed.Remove(m_Creature); + m_Tamer.NextSkillTime = Core.TickCount; + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502794, + m_Tamer.NetState); // The animal is too angry to continue taming. + Stop(); + } + else if (m_Count < m_MaxCount) + { + m_Tamer.RevealingAction(); - switch ( Utility.Random( 3 ) ) - { - case 0: m_Tamer.PublicOverheadMessage( MessageType.Regular, 0x3B2, Utility.Random( 502790, 4 ) ); break; - case 1: m_Tamer.PublicOverheadMessage( MessageType.Regular, 0x3B2, Utility.Random( 1005608, 6 ) ); break; - case 2: m_Tamer.PublicOverheadMessage( MessageType.Regular, 0x3B2, Utility.Random( 1010593, 4 ) ); break; - } + switch (Utility.Random(3)) + { + case 0: + m_Tamer.PublicOverheadMessage(MessageType.Regular, 0x3B2, Utility.Random(502790, 4)); + break; + case 1: + m_Tamer.PublicOverheadMessage(MessageType.Regular, 0x3B2, Utility.Random(1005608, 6)); + break; + case 2: + m_Tamer.PublicOverheadMessage(MessageType.Regular, 0x3B2, Utility.Random(1010593, 4)); + break; + } - if ( !alreadyOwned ) // Passively check animal lore for gain - m_Tamer.CheckTargetSkill( SkillName.AnimalLore, m_Creature, 0.0, 120.0 ); + if (!alreadyOwned) // Passively check animal lore for gain + m_Tamer.CheckTargetSkill(SkillName.AnimalLore, m_Creature, 0.0, 120.0); - if ( m_Creature.Paralyzed ) - m_Paralyzed = true; - } - else - { - m_Tamer.RevealingAction(); - m_Tamer.NextSkillTime = Core.TickCount; - m_BeingTamed.Remove( m_Creature ); + if (m_Creature.Paralyzed) + m_Paralyzed = true; + } + else + { + m_Tamer.RevealingAction(); + m_Tamer.NextSkillTime = Core.TickCount; + m_BeingTamed.Remove(m_Creature); - if ( m_Creature.Paralyzed ) - m_Paralyzed = true; + if (m_Creature.Paralyzed) + m_Paralyzed = true; - if ( !alreadyOwned ) // Passively check animal lore for gain - m_Tamer.CheckTargetSkill( SkillName.AnimalLore, m_Creature, 0.0, 120.0 ); + if (!alreadyOwned) // Passively check animal lore for gain + m_Tamer.CheckTargetSkill(SkillName.AnimalLore, m_Creature, 0.0, 120.0); - double minSkill = m_Creature.MinTameSkill + (m_Creature.Owners.Count * 6.0); + double minSkill = m_Creature.MinTameSkill + m_Creature.Owners.Count * 6.0; - if ( minSkill > -24.9 && CheckMastery( m_Tamer, m_Creature ) ) - minSkill = -24.9; // 50% at 0.0? + if (minSkill > -24.9 && CheckMastery(m_Tamer, m_Creature)) + minSkill = -24.9; // 50% at 0.0? - minSkill += 24.9; + minSkill += 24.9; - if ( CheckMastery( m_Tamer, m_Creature ) || alreadyOwned || m_Tamer.CheckTargetSkill( SkillName.AnimalTaming, m_Creature, minSkill - 25.0, minSkill + 25.0 ) ) - { - if ( m_Creature.Owners.Count == 0 ) // First tame - { - if ( m_Creature is GreaterDragon ) - { - ScaleSkills( m_Creature, 0.72, 0.90 ); // 72% of original skills trainable to 90% - m_Creature.Skills[SkillName.Magery].Base = m_Creature.Skills[SkillName.Magery].Cap; // Greater dragons have a 90% cap reduction and 90% skill reduction on magery - } - else if ( m_Paralyzed ) - ScaleSkills( m_Creature, 0.86 ); // 86% of original skills if they were paralyzed during the taming - else - ScaleSkills( m_Creature, 0.90 ); // 90% of original skills + if (CheckMastery(m_Tamer, m_Creature) || alreadyOwned || + m_Tamer.CheckTargetSkill(SkillName.AnimalTaming, m_Creature, minSkill - 25.0, minSkill + 25.0)) + { + if (m_Creature.Owners.Count == 0) // First tame + { + if (m_Creature is GreaterDragon) + { + ScaleSkills(m_Creature, 0.72, 0.90); // 72% of original skills trainable to 90% + m_Creature.Skills[SkillName.Magery].Base = + m_Creature.Skills[SkillName.Magery] + .Cap; // Greater dragons have a 90% cap reduction and 90% skill reduction on magery + } + else if (m_Paralyzed) + { + ScaleSkills(m_Creature, + 0.86); // 86% of original skills if they were paralyzed during the taming + } + else + { + ScaleSkills(m_Creature, 0.90); // 90% of original skills + } - if ( m_Creature.StatLossAfterTame ) - ScaleStats( m_Creature, 0.50 ); - } + if (m_Creature.StatLossAfterTame) + ScaleStats(m_Creature, 0.50); + } - if ( alreadyOwned ) - { - m_Tamer.SendLocalizedMessage( 502797 ); // That wasn't even challenging. - } - else - { - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502799, m_Tamer.NetState ); // It seems to accept you as master. - m_Creature.Owners.Add( m_Tamer ); - } + if (alreadyOwned) + { + m_Tamer.SendLocalizedMessage(502797); // That wasn't even challenging. + } + else + { + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502799, + m_Tamer.NetState); // It seems to accept you as master. + m_Creature.Owners.Add(m_Tamer); + } - m_Creature.SetControlMaster( m_Tamer ); - m_Creature.IsBonded = false; - } - else - { - m_Creature.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 502798, m_Tamer.NetState ); // You fail to tame the creature. - } - } - } + m_Creature.SetControlMaster(m_Tamer); + m_Creature.IsBonded = false; + } + else + { + m_Creature.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 502798, + m_Tamer.NetState); // You fail to tame the creature. + } + } + } - private bool CanPath() - { - IPoint3D p = m_Tamer as IPoint3D; + private bool CanPath() + { + IPoint3D p = m_Tamer; - if ( p == null ) - return false; + if (p == null) + return false; - if ( m_Creature.InRange( new Point3D( p ), 1 ) ) - return true; + if (m_Creature.InRange(new Point3D(p), 1)) + return true; - MovementPath path = new MovementPath( m_Creature, new Point3D( p ) ); - return path.Success; - } - } - } - } -} + MovementPath path = new MovementPath(m_Creature, new Point3D(p)); + return path.Success; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/ArmsLore.cs b/Scripts/Skills/ArmsLore.cs index b82f76dc4..70cf25317 100644 --- a/Scripts/Skills/ArmsLore.cs +++ b/Scripts/Skills/ArmsLore.cs @@ -6,162 +6,162 @@ using Server.Targeting; namespace Server.SkillHandlers { - public class ArmsLore - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.ArmsLore].Callback = OnUse; - } + public class ArmsLore + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.ArmsLore].Callback = OnUse; + } - public static TimeSpan OnUse(Mobile m) - { - m.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile m) + { + m.Target = new InternalTarget(); - m.SendLocalizedMessage( 500349 ); // What item do you wish to get information about? + m.SendLocalizedMessage(500349); // What item do you wish to get information about? - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - [PlayerVendorTarget] - private class InternalTarget : Target - { - public InternalTarget() : base( 2, false, TargetFlags.None ) - { - AllowNonlocal = true; - } + [PlayerVendorTarget] + private class InternalTarget : Target + { + public InternalTarget() : base(2, false, TargetFlags.None) + { + AllowNonlocal = true; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is BaseWeapon ) - { - if ( from.CheckTargetSkill( SkillName.ArmsLore, targeted, 0, 100 ) ) - { - BaseWeapon weap = (BaseWeapon)targeted; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is BaseWeapon) + { + if (from.CheckTargetSkill(SkillName.ArmsLore, targeted, 0, 100)) + { + BaseWeapon weap = (BaseWeapon)targeted; - if ( weap.MaxHitPoints != 0 ) - { - int hp = (int)((weap.HitPoints / (double)weap.MaxHitPoints) * 10); + if (weap.MaxHitPoints != 0) + { + int hp = (int)(weap.HitPoints / (double)weap.MaxHitPoints * 10); - if ( hp < 0 ) - hp = 0; - else if ( hp > 9 ) - hp = 9; + if (hp < 0) + hp = 0; + else if (hp > 9) + hp = 9; - from.SendLocalizedMessage( 1038285 + hp ); - } + from.SendLocalizedMessage(1038285 + hp); + } - int damage = (weap.MaxDamage + weap.MinDamage) / 2; - int hand = (weap.Layer == Layer.OneHanded ? 0 : 1); + int damage = (weap.MaxDamage + weap.MinDamage) / 2; + int hand = weap.Layer == Layer.OneHanded ? 0 : 1; - if ( damage < 3 ) - damage = 0; - else - damage = (int)Math.Ceiling( Math.Min( damage, 30 ) / 5.0 ); - /* - else if ( damage < 6 ) - damage = 1; - else if ( damage < 11 ) - damage = 2; - else if ( damage < 16 ) - damage = 3; - else if ( damage < 21 ) - damage = 4; - else if ( damage < 26 ) - damage = 5; - else - damage = 6; - * */ + if (damage < 3) + damage = 0; + else + damage = (int)Math.Ceiling(Math.Min(damage, 30) / 5.0); + /* + else if ( damage < 6 ) + damage = 1; + else if ( damage < 11 ) + damage = 2; + else if ( damage < 16 ) + damage = 3; + else if ( damage < 21 ) + damage = 4; + else if ( damage < 26 ) + damage = 5; + else + damage = 6; + * */ - WeaponType type = weap.Type; + WeaponType type = weap.Type; - if ( type == WeaponType.Ranged ) - from.SendLocalizedMessage( 1038224 + (damage * 9) ); - else if ( type == WeaponType.Piercing ) - from.SendLocalizedMessage( 1038218 + hand + (damage * 9) ); - else if ( type == WeaponType.Slashing ) - from.SendLocalizedMessage( 1038220 + hand + (damage * 9) ); - else if ( type == WeaponType.Bashing ) - from.SendLocalizedMessage( 1038222 + hand + (damage * 9) ); - else - from.SendLocalizedMessage( 1038216 + hand + (damage * 9) ); + if (type == WeaponType.Ranged) + from.SendLocalizedMessage(1038224 + damage * 9); + else if (type == WeaponType.Piercing) + from.SendLocalizedMessage(1038218 + hand + damage * 9); + else if (type == WeaponType.Slashing) + from.SendLocalizedMessage(1038220 + hand + damage * 9); + else if (type == WeaponType.Bashing) + from.SendLocalizedMessage(1038222 + hand + damage * 9); + else + from.SendLocalizedMessage(1038216 + hand + damage * 9); - if ( weap.Poison != null && weap.PoisonCharges > 0 ) - from.SendLocalizedMessage( 1038284 ); // It appears to have poison smeared on it. - } - else - { - from.SendLocalizedMessage( 500353 ); // You are not certain... - } - } - else if (targeted is BaseArmor) - { - if ( from.CheckTargetSkill(SkillName.ArmsLore, targeted, 0, 100) ) - { - BaseArmor arm = (BaseArmor)targeted; + if (weap.Poison != null && weap.PoisonCharges > 0) + from.SendLocalizedMessage(1038284); // It appears to have poison smeared on it. + } + else + { + from.SendLocalizedMessage(500353); // You are not certain... + } + } + else if (targeted is BaseArmor) + { + if (from.CheckTargetSkill(SkillName.ArmsLore, targeted, 0, 100)) + { + BaseArmor arm = (BaseArmor)targeted; - if ( arm.MaxHitPoints != 0 ) - { - int hp = (int)((arm.HitPoints / (double)arm.MaxHitPoints) * 10); + if (arm.MaxHitPoints != 0) + { + int hp = (int)(arm.HitPoints / (double)arm.MaxHitPoints * 10); - if ( hp < 0 ) - hp = 0; - else if ( hp > 9 ) - hp = 9; + if (hp < 0) + hp = 0; + else if (hp > 9) + hp = 9; - from.SendLocalizedMessage( 1038285 + hp ); - } + from.SendLocalizedMessage(1038285 + hp); + } - from.SendLocalizedMessage( 1038295 + (int)Math.Ceiling( Math.Min( arm.ArmorRating, 35 ) / 5.0 ) ); - /* - if ( arm.ArmorRating < 1 ) - from.SendLocalizedMessage( 1038295 ); // This armor offers no defense against attackers. - else if ( arm.ArmorRating < 6 ) - from.SendLocalizedMessage( 1038296 ); // This armor provides almost no protection. - else if ( arm.ArmorRating < 11 ) - from.SendLocalizedMessage( 1038297 ); // This armor provides very little protection. - else if ( arm.ArmorRating < 16 ) - from.SendLocalizedMessage( 1038298 ); // This armor offers some protection against blows. - else if ( arm.ArmorRating < 21 ) - from.SendLocalizedMessage( 1038299 ); // This armor serves as sturdy protection. - else if ( arm.ArmorRating < 26 ) - from.SendLocalizedMessage( 1038300 ); // This armor is a superior defense against attack. - else if ( arm.ArmorRating < 31 ) - from.SendLocalizedMessage( 1038301 ); // This armor offers excellent protection. - else - from.SendLocalizedMessage( 1038302 ); // This armor is superbly crafted to provide maximum protection. - * */ - } - else - { - from.SendLocalizedMessage( 500353 ); // You are not certain... - } - } - else if ( targeted is SwampDragon && ((SwampDragon)targeted).HasBarding ) - { - SwampDragon pet = (SwampDragon)targeted; + from.SendLocalizedMessage(1038295 + (int)Math.Ceiling(Math.Min(arm.ArmorRating, 35) / 5.0)); + /* + if ( arm.ArmorRating < 1 ) + from.SendLocalizedMessage( 1038295 ); // This armor offers no defense against attackers. + else if ( arm.ArmorRating < 6 ) + from.SendLocalizedMessage( 1038296 ); // This armor provides almost no protection. + else if ( arm.ArmorRating < 11 ) + from.SendLocalizedMessage( 1038297 ); // This armor provides very little protection. + else if ( arm.ArmorRating < 16 ) + from.SendLocalizedMessage( 1038298 ); // This armor offers some protection against blows. + else if ( arm.ArmorRating < 21 ) + from.SendLocalizedMessage( 1038299 ); // This armor serves as sturdy protection. + else if ( arm.ArmorRating < 26 ) + from.SendLocalizedMessage( 1038300 ); // This armor is a superior defense against attack. + else if ( arm.ArmorRating < 31 ) + from.SendLocalizedMessage( 1038301 ); // This armor offers excellent protection. + else + from.SendLocalizedMessage( 1038302 ); // This armor is superbly crafted to provide maximum protection. + * */ + } + else + { + from.SendLocalizedMessage(500353); // You are not certain... + } + } + else if (targeted is SwampDragon && ((SwampDragon)targeted).HasBarding) + { + SwampDragon pet = (SwampDragon)targeted; - if ( from.CheckTargetSkill( SkillName.ArmsLore, targeted, 0, 100 ) ) - { - int perc = (4 * pet.BardingHP) / pet.BardingMaxHP; + if (from.CheckTargetSkill(SkillName.ArmsLore, targeted, 0, 100)) + { + int perc = 4 * pet.BardingHP / pet.BardingMaxHP; - if ( perc < 0 ) - perc = 0; - else if ( perc > 4 ) - perc = 4; + if (perc < 0) + perc = 0; + else if (perc > 4) + perc = 4; - pet.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1053021 - perc, from.NetState ); - } - else - { - from.SendLocalizedMessage( 500353 ); // You are not certain... - } - } - else - { - from.SendLocalizedMessage( 500352 ); // This is neither weapon nor armor. - } - } - } - } -} + pet.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1053021 - perc, from.NetState); + } + else + { + from.SendLocalizedMessage(500353); // You are not certain... + } + } + else + { + from.SendLocalizedMessage(500352); // This is neither weapon nor armor. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Begging.cs b/Scripts/Skills/Begging.cs index 43f867b44..f20b63c38 100644 --- a/Scripts/Skills/Begging.cs +++ b/Scripts/Skills/Begging.cs @@ -1,174 +1,179 @@ using System; -using Server.Misc; -using Server.Targeting; using Server.Items; +using Server.Misc; using Server.Network; +using Server.Targeting; namespace Server.SkillHandlers { - public class Begging - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Begging].Callback = OnUse; - } + public class Begging + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Begging].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.RevealingAction(); + public static TimeSpan OnUse(Mobile m) + { + m.RevealingAction(); - m.Target = new InternalTarget(); - m.RevealingAction(); + m.Target = new InternalTarget(); + m.RevealingAction(); - m.SendLocalizedMessage( 500397 ); // To whom do you wish to grovel? + m.SendLocalizedMessage(500397); // To whom do you wish to grovel? - return TimeSpan.FromHours( 6.0 ); - } + return TimeSpan.FromHours(6.0); + } - private class InternalTarget : Target - { - private bool m_SetSkillTime = true; + private class InternalTarget : Target + { + private bool m_SetSkillTime = true; - public InternalTarget() : base ( 12, false, TargetFlags.None ) - { - } + public InternalTarget() : base(12, false, TargetFlags.None) + { + } - protected override void OnTargetFinish( Mobile from ) - { - if ( m_SetSkillTime ) - from.NextSkillTime = Core.TickCount; - } + protected override void OnTargetFinish(Mobile from) + { + if (m_SetSkillTime) + from.NextSkillTime = Core.TickCount; + } - protected override void OnTarget( Mobile from, object targeted ) - { - from.RevealingAction(); + protected override void OnTarget(Mobile from, object targeted) + { + from.RevealingAction(); - int number = -1; + int number = -1; - if ( targeted is Mobile ) - { - Mobile targ = (Mobile)targeted; + if (targeted is Mobile) + { + Mobile targ = (Mobile)targeted; - if ( targ.Player ) // We can't beg from players - { - number = 500398; // Perhaps just asking would work better. - } - else if ( !targ.Body.IsHuman ) // Make sure the NPC is human - { - number = 500399; // There is little chance of getting money from that! - } - else if ( !from.InRange( targ, 2 ) ) - { - if ( !targ.Female ) - number = 500401; // You are too far away to beg from him. - else - number = 500402; // You are too far away to beg from her. - } - else if ( !Core.ML && from.Mounted ) // If we're on a mount, who would give us money? TODO: guessed it's removed since ML - { - number = 500404; // They seem unwilling to give you any money. - } - else - { - // Face eachother - from.Direction = from.GetDirectionTo( targ ); - targ.Direction = targ.GetDirectionTo( from ); + if (targ.Player) // We can't beg from players + { + number = 500398; // Perhaps just asking would work better. + } + else if (!targ.Body.IsHuman) // Make sure the NPC is human + { + number = 500399; // There is little chance of getting money from that! + } + else if (!from.InRange(targ, 2)) + { + if (!targ.Female) + number = 500401; // You are too far away to beg from him. + else + number = 500402; // You are too far away to beg from her. + } + else if (!Core.ML && from.Mounted + ) // If we're on a mount, who would give us money? TODO: guessed it's removed since ML + { + number = 500404; // They seem unwilling to give you any money. + } + else + { + // Face eachother + from.Direction = from.GetDirectionTo(targ); + targ.Direction = targ.GetDirectionTo(from); - from.Animate( 32, 5, 1, true, false, 0 ); // Bow + from.Animate(32, 5, 1, true, false, 0); // Bow - new InternalTimer( from, targ ).Start(); + new InternalTimer(from, targ).Start(); - m_SetSkillTime = false; - } - } - else // Not a Mobile - { - number = 500399; // There is little chance of getting money from that! - } + m_SetSkillTime = false; + } + } + else // Not a Mobile + { + number = 500399; // There is little chance of getting money from that! + } - if ( number != -1 ) - from.SendLocalizedMessage( number ); - } + if (number != -1) + from.SendLocalizedMessage(number); + } - private class InternalTimer : Timer - { - private Mobile m_From, m_Target; + private class InternalTimer : Timer + { + private Mobile m_From, m_Target; - public InternalTimer( Mobile from, Mobile target ) : base( TimeSpan.FromSeconds( 2.0 ) ) - { - m_From = from; - m_Target = target; - Priority = TimerPriority.TwoFiftyMS; - } + public InternalTimer(Mobile from, Mobile target) : base(TimeSpan.FromSeconds(2.0)) + { + m_From = from; + m_Target = target; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - Container theirPack = m_Target.Backpack; + protected override void OnTick() + { + Container theirPack = m_Target.Backpack; - double badKarmaChance = 0.5 - ((double)m_From.Karma / 8570); + double badKarmaChance = 0.5 - (double)m_From.Karma / 8570; - if ( theirPack == null ) - { - m_From.SendLocalizedMessage( 500404 ); // They seem unwilling to give you any money. - } - else if ( m_From.Karma < 0 && badKarmaChance > Utility.RandomDouble() ) - { - m_Target.PublicOverheadMessage( MessageType.Regular, m_Target.SpeechHue, 500406 ); // Thou dost not look trustworthy... no gold for thee today! - } - else if ( m_From.CheckTargetSkill( SkillName.Begging, m_Target, 0.0, 100.0 ) ) - { - int toConsume = theirPack.GetAmount( typeof( Gold ) ) / 10; - int max = 10 + (m_From.Fame / 2500); + if (theirPack == null) + { + m_From.SendLocalizedMessage(500404); // They seem unwilling to give you any money. + } + else if (m_From.Karma < 0 && badKarmaChance > Utility.RandomDouble()) + { + m_Target.PublicOverheadMessage(MessageType.Regular, m_Target.SpeechHue, + 500406); // Thou dost not look trustworthy... no gold for thee today! + } + else if (m_From.CheckTargetSkill(SkillName.Begging, m_Target, 0.0, 100.0)) + { + int toConsume = theirPack.GetAmount(typeof(Gold)) / 10; + int max = 10 + m_From.Fame / 2500; - if ( max > 14 ) - max = 14; - else if ( max < 10 ) - max = 10; + if (max > 14) + max = 14; + else if (max < 10) + max = 10; - if ( toConsume > max ) - toConsume = max; + if (toConsume > max) + toConsume = max; - if ( toConsume > 0 ) - { - int consumed = theirPack.ConsumeUpTo( typeof( Gold ), toConsume ); + if (toConsume > 0) + { + int consumed = theirPack.ConsumeUpTo(typeof(Gold), toConsume); - if ( consumed > 0 ) - { - m_Target.PublicOverheadMessage( MessageType.Regular, m_Target.SpeechHue, 500405 ); // I feel sorry for thee... + if (consumed > 0) + { + m_Target.PublicOverheadMessage(MessageType.Regular, m_Target.SpeechHue, + 500405); // I feel sorry for thee... - Gold gold = new Gold( consumed ); + Gold gold = new Gold(consumed); - m_From.AddToBackpack( gold ); - m_From.PlaySound( gold.GetDropSound() ); + m_From.AddToBackpack(gold); + m_From.PlaySound(gold.GetDropSound()); - if ( m_From.Karma > -3000 ) - { - int toLose = m_From.Karma + 3000; + if (m_From.Karma > -3000) + { + int toLose = m_From.Karma + 3000; - if ( toLose > 40 ) - toLose = 40; + if (toLose > 40) + toLose = 40; - Titles.AwardKarma( m_From, -toLose, true ); - } - } - else - { - m_Target.PublicOverheadMessage( MessageType.Regular, m_Target.SpeechHue, 500407 ); // I have not enough money to give thee any! - } - } - else - { - m_Target.PublicOverheadMessage( MessageType.Regular, m_Target.SpeechHue, 500407 ); // I have not enough money to give thee any! - } - } - else - { - m_Target.SendLocalizedMessage( 500404 ); // They seem unwilling to give you any money. - } + Titles.AwardKarma(m_From, -toLose, true); + } + } + else + { + m_Target.PublicOverheadMessage(MessageType.Regular, m_Target.SpeechHue, + 500407); // I have not enough money to give thee any! + } + } + else + { + m_Target.PublicOverheadMessage(MessageType.Regular, m_Target.SpeechHue, + 500407); // I have not enough money to give thee any! + } + } + else + { + m_Target.SendLocalizedMessage(500404); // They seem unwilling to give you any money. + } - m_From.NextSkillTime = Core.TickCount + 10000; - } - } - } - } + m_From.NextSkillTime = Core.TickCount + 10000; + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/DetectHidden.cs b/Scripts/Skills/DetectHidden.cs index 14c4e628e..2c4386d1b 100644 --- a/Scripts/Skills/DetectHidden.cs +++ b/Scripts/Skills/DetectHidden.cs @@ -6,105 +6,101 @@ using Server.Targeting; namespace Server.SkillHandlers { - public class DetectHidden - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.DetectHidden].Callback = OnUse; - } + public class DetectHidden + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.DetectHidden].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile src ) - { - src.SendLocalizedMessage( 500819 );//Where will you search? - src.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile src) + { + src.SendLocalizedMessage(500819); //Where will you search? + src.Target = new InternalTarget(); - return TimeSpan.FromSeconds( 6.0 ); - } + return TimeSpan.FromSeconds(6.0); + } - private class InternalTarget : Target - { - public InternalTarget() : base( 12, true, TargetFlags.None ) - { - } + private class InternalTarget : Target + { + public InternalTarget() : base(12, true, TargetFlags.None) + { + } - protected override void OnTarget( Mobile src, object targ ) - { - bool foundAnyone = false; + protected override void OnTarget(Mobile src, object targ) + { + bool foundAnyone = false; - Point3D p; - if ( targ is Mobile ) - p = ((Mobile)targ).Location; - else if ( targ is Item ) - p = ((Item)targ).Location; - else if ( targ is IPoint3D ) - p = new Point3D( (IPoint3D)targ ); - else - p = src.Location; + Point3D p; + if (targ is Mobile) + p = ((Mobile)targ).Location; + else if (targ is Item) + p = ((Item)targ).Location; + else if (targ is IPoint3D) + p = new Point3D((IPoint3D)targ); + else + p = src.Location; - double srcSkill = src.Skills[SkillName.DetectHidden].Value; - int range = (int)(srcSkill / 10.0); + double srcSkill = src.Skills[SkillName.DetectHidden].Value; + int range = (int)(srcSkill / 10.0); - if ( !src.CheckSkill( SkillName.DetectHidden, 0.0, 100.0 ) ) - range /= 2; + if (!src.CheckSkill(SkillName.DetectHidden, 0.0, 100.0)) + range /= 2; - BaseHouse house = BaseHouse.FindHouseAt( p, src.Map, 16 ); + BaseHouse house = BaseHouse.FindHouseAt(p, src.Map, 16); - bool inHouse = ( house != null && house.IsFriend( src ) ); + bool inHouse = house != null && house.IsFriend(src); - if ( inHouse ) - range = 22; + if (inHouse) + range = 22; - if ( range > 0 ) - { - IPooledEnumerable inRange = src.Map.GetMobilesInRange( p, range ); + if (range > 0) + { + IPooledEnumerable inRange = src.Map.GetMobilesInRange(p, range); - foreach ( Mobile trg in inRange ) - { - if ( trg.Hidden && src != trg ) - { - double ss = srcSkill + Utility.Random( 21 ) - 10; - double ts = trg.Skills[SkillName.Hiding].Value + Utility.Random( 21 ) - 10; + foreach (Mobile trg in inRange) + if (trg.Hidden && src != trg) + { + double ss = srcSkill + Utility.Random(21) - 10; + double ts = trg.Skills[SkillName.Hiding].Value + Utility.Random(21) - 10; - if ( src.AccessLevel >= trg.AccessLevel && ( ss >= ts || ( inHouse && house.IsInside( trg ) ) ) ) - { - if ( trg is ShadowKnight && (trg.X != p.X || trg.Y != p.Y) ) - continue; + if (src.AccessLevel >= trg.AccessLevel && (ss >= ts || inHouse && house.IsInside(trg))) + { + if (trg is ShadowKnight && (trg.X != p.X || trg.Y != p.Y)) + continue; - trg.RevealingAction(); - trg.SendLocalizedMessage( 500814 ); // You have been revealed! - foundAnyone = true; - } - } - } + trg.RevealingAction(); + trg.SendLocalizedMessage(500814); // You have been revealed! + foundAnyone = true; + } + } - inRange.Free(); + inRange.Free(); - if ( Faction.Find( src ) != null ) - { - IPooledEnumerable itemsInRange = src.Map.GetItemsInRange( p, range ); + if (Faction.Find(src) != null) + { + IPooledEnumerable itemsInRange = src.Map.GetItemsInRange(p, range); - foreach ( BaseFactionTrap trap in itemsInRange ) - { - if ( src.CheckTargetSkill( SkillName.DetectHidden, trap, 80.0, 100.0 ) ) - { - src.SendLocalizedMessage( 1042712, true, " " + (trap.Faction == null ? "" : trap.Faction.Definition.FriendlyName) ); // You reveal a trap placed by a faction: + foreach (BaseFactionTrap trap in itemsInRange) + if (src.CheckTargetSkill(SkillName.DetectHidden, trap, 80.0, 100.0)) + { + src.SendLocalizedMessage(1042712, true, + " " + (trap.Faction == null + ? "" + : trap.Faction.Definition.FriendlyName)); // You reveal a trap placed by a faction: - trap.Visible = true; - trap.BeginConceal(); + trap.Visible = true; + trap.BeginConceal(); - foundAnyone = true; - } - } + foundAnyone = true; + } - itemsInRange.Free(); - } - } + itemsInRange.Free(); + } + } - if ( !foundAnyone ) - { - src.SendLocalizedMessage( 500817 ); // You can see nothing hidden there. - } - } - } - } -} + if (!foundAnyone) src.SendLocalizedMessage(500817); // You can see nothing hidden there. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Discordance.cs b/Scripts/Skills/Discordance.cs index 61bf745ce..4bfdf53e5 100644 --- a/Scripts/Skills/Discordance.cs +++ b/Scripts/Skills/Discordance.cs @@ -1,264 +1,270 @@ using System; using System.Collections; using Server.Items; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.SkillHandlers { - public class Discordance - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Discordance].Callback = OnUse; - } + public class Discordance + { + private static Hashtable m_Table = new Hashtable(); - public static TimeSpan OnUse( Mobile m ) - { - m.RevealingAction(); + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Discordance].Callback = OnUse; + } - BaseInstrument.PickInstrument( m, OnPickedInstrument ); + public static TimeSpan OnUse(Mobile m) + { + m.RevealingAction(); - return TimeSpan.FromSeconds( 1.0 ); // Cannot use another skill for 1 second - } + BaseInstrument.PickInstrument(m, OnPickedInstrument); - public static void OnPickedInstrument( Mobile from, BaseInstrument instrument ) - { - from.RevealingAction(); - from.SendLocalizedMessage( 1049541 ); // Choose the target for your song of discordance. - from.Target = new DiscordanceTarget( from, instrument ); - from.NextSkillTime = Core.TickCount + 6000; - } + return TimeSpan.FromSeconds(1.0); // Cannot use another skill for 1 second + } - private class DiscordanceInfo - { - public Mobile m_From; - public Mobile m_Creature; - public DateTime m_EndTime; - public bool m_Ending; - public Timer m_Timer; - public int m_Effect; - public ArrayList m_Mods; + public static void OnPickedInstrument(Mobile from, BaseInstrument instrument) + { + from.RevealingAction(); + from.SendLocalizedMessage(1049541); // Choose the target for your song of discordance. + from.Target = new DiscordanceTarget(from, instrument); + from.NextSkillTime = Core.TickCount + 6000; + } - public DiscordanceInfo( Mobile from, Mobile creature, int effect, ArrayList mods ) - { - m_From = from; - m_Creature = creature; - m_EndTime = DateTime.UtcNow; - m_Ending = false; - m_Effect = effect; - m_Mods = mods; + public static bool GetEffect(Mobile targ, ref int effect) + { + DiscordanceInfo info = m_Table[targ] as DiscordanceInfo; - Apply(); - } + if (info == null) + return false; - public void Apply() - { - for ( int i = 0; i < m_Mods.Count; ++i ) - { - object mod = m_Mods[i]; + effect = info.m_Effect; + return true; + } - if ( mod is ResistanceMod ) - m_Creature.AddResistanceMod( (ResistanceMod) mod ); - else if ( mod is StatMod ) - m_Creature.AddStatMod( (StatMod) mod ); - else if ( mod is SkillMod ) - m_Creature.AddSkillMod( (SkillMod) mod ); - } - } + private static void ProcessDiscordance(DiscordanceInfo info) + { + Mobile from = info.m_From; + Mobile targ = info.m_Creature; + bool ends = false; - public void Clear() - { - for ( int i = 0; i < m_Mods.Count; ++i ) - { - object mod = m_Mods[i]; + // According to uoherald bard must remain alive, visible, and + // within range of the target or the effect ends in 15 seconds. + if (!targ.Alive || targ.Deleted || !from.Alive || from.Hidden) + { + ends = true; + } + else + { + int range = (int)targ.GetDistanceToSqrt(from); + int maxRange = BaseInstrument.GetBardRange(from, SkillName.Discordance); - if ( mod is ResistanceMod ) - m_Creature.RemoveResistanceMod( (ResistanceMod) mod ); - else if ( mod is StatMod ) - m_Creature.RemoveStatMod( ((StatMod) mod).Name ); - else if ( mod is SkillMod ) - m_Creature.RemoveSkillMod( (SkillMod) mod ); - } - } - } + if (from.Map != targ.Map || range > maxRange) + ends = true; + } - private static Hashtable m_Table = new Hashtable(); + if (ends && info.m_Ending && info.m_EndTime < DateTime.UtcNow) + { + info.m_Timer?.Stop(); - public static bool GetEffect( Mobile targ, ref int effect ) - { - DiscordanceInfo info = m_Table[targ] as DiscordanceInfo; + info.Clear(); + m_Table.Remove(targ); + } + else + { + if (ends && !info.m_Ending) + { + info.m_Ending = true; + info.m_EndTime = DateTime.UtcNow + TimeSpan.FromSeconds(15); + } + else if (!ends) + { + info.m_Ending = false; + info.m_EndTime = DateTime.UtcNow; + } - if ( info == null ) - return false; + targ.FixedEffect(0x376A, 1, 32); + } + } - effect = info.m_Effect; - return true; - } + private class DiscordanceInfo + { + public Mobile m_Creature; + public int m_Effect; + public bool m_Ending; + public DateTime m_EndTime; + public Mobile m_From; + public ArrayList m_Mods; + public Timer m_Timer; - private static void ProcessDiscordance( DiscordanceInfo info ) - { - Mobile from = info.m_From; - Mobile targ = info.m_Creature; - bool ends = false; + public DiscordanceInfo(Mobile from, Mobile creature, int effect, ArrayList mods) + { + m_From = from; + m_Creature = creature; + m_EndTime = DateTime.UtcNow; + m_Ending = false; + m_Effect = effect; + m_Mods = mods; - // According to uoherald bard must remain alive, visible, and - // within range of the target or the effect ends in 15 seconds. - if ( !targ.Alive || targ.Deleted || !from.Alive || from.Hidden ) - ends = true; - else - { - int range = (int) targ.GetDistanceToSqrt( from ); - int maxRange = BaseInstrument.GetBardRange( from, SkillName.Discordance ); + Apply(); + } - if ( from.Map != targ.Map || range > maxRange ) - ends = true; - } + public void Apply() + { + for (int i = 0; i < m_Mods.Count; ++i) + { + object mod = m_Mods[i]; - if ( ends && info.m_Ending && info.m_EndTime < DateTime.UtcNow ) - { - info.m_Timer?.Stop(); + if (mod is ResistanceMod) + m_Creature.AddResistanceMod((ResistanceMod)mod); + else if (mod is StatMod) + m_Creature.AddStatMod((StatMod)mod); + else if (mod is SkillMod) + m_Creature.AddSkillMod((SkillMod)mod); + } + } - info.Clear(); - m_Table.Remove( targ ); - } - else - { - if ( ends && !info.m_Ending ) - { - info.m_Ending = true; - info.m_EndTime = DateTime.UtcNow + TimeSpan.FromSeconds( 15 ); - } - else if ( !ends ) - { - info.m_Ending = false; - info.m_EndTime = DateTime.UtcNow; - } + public void Clear() + { + for (int i = 0; i < m_Mods.Count; ++i) + { + object mod = m_Mods[i]; - targ.FixedEffect( 0x376A, 1, 32 ); - } - } + if (mod is ResistanceMod) + m_Creature.RemoveResistanceMod((ResistanceMod)mod); + else if (mod is StatMod) + m_Creature.RemoveStatMod(((StatMod)mod).Name); + else if (mod is SkillMod) + m_Creature.RemoveSkillMod((SkillMod)mod); + } + } + } - public class DiscordanceTarget : Target - { - private BaseInstrument m_Instrument; + public class DiscordanceTarget : Target + { + private BaseInstrument m_Instrument; - public DiscordanceTarget( Mobile from, BaseInstrument inst ) : base( BaseInstrument.GetBardRange( from, SkillName.Discordance ), false, TargetFlags.None ) - { - m_Instrument = inst; - } + public DiscordanceTarget(Mobile from, BaseInstrument inst) : base( + BaseInstrument.GetBardRange(from, SkillName.Discordance), false, TargetFlags.None) + { + m_Instrument = inst; + } - protected override void OnTarget( Mobile from, object target ) - { - from.RevealingAction(); - from.NextSkillTime = Core.TickCount + 1000; + protected override void OnTarget(Mobile from, object target) + { + from.RevealingAction(); + from.NextSkillTime = Core.TickCount + 1000; - if ( !m_Instrument.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1062488 ); // The instrument you are trying to play is no longer in your backpack! - } - else if ( target is Mobile ) - { - Mobile targ = (Mobile)target; + if (!m_Instrument.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage( + 1062488); // The instrument you are trying to play is no longer in your backpack! + } + else if (target is Mobile) + { + Mobile targ = (Mobile)target; - if ( targ == from || (targ is BaseCreature && ( ((BaseCreature)targ).BardImmune || !from.CanBeHarmful( targ, false ) ) && ((BaseCreature)targ).ControlMaster != from) ) - { - from.SendLocalizedMessage( 1049535 ); // A song of discord would have no effect on that. - } - else if ( m_Table.Contains( targ ) ) //Already discorded - { - from.SendLocalizedMessage( 1049537 );// Your target is already in discord. - } - else if ( !targ.Player ) - { - double diff = m_Instrument.GetDifficultyFor( targ ) - 10.0; - double music = from.Skills[SkillName.Musicianship].Value; + if (targ == from || targ is BaseCreature && + (((BaseCreature)targ).BardImmune || !from.CanBeHarmful(targ, false)) && + ((BaseCreature)targ).ControlMaster != from) + { + from.SendLocalizedMessage(1049535); // A song of discord would have no effect on that. + } + else if (m_Table.Contains(targ)) //Already discorded + { + from.SendLocalizedMessage(1049537); // Your target is already in discord. + } + else if (!targ.Player) + { + double diff = m_Instrument.GetDifficultyFor(targ) - 10.0; + double music = from.Skills[SkillName.Musicianship].Value; - if ( music > 100.0 ) - diff -= (music - 100.0) * 0.5; + if (music > 100.0) + diff -= (music - 100.0) * 0.5; - if ( !BaseInstrument.CheckMusicianship( from ) ) - { - from.SendLocalizedMessage( 500612 ); // You play poorly, and there is no effect. - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else if ( from.CheckTargetSkill( SkillName.Discordance, target, diff-25.0, diff+25.0 ) ) - { - from.SendLocalizedMessage( 1049539 ); // You play the song surpressing your targets strength - m_Instrument.PlayInstrumentWell( from ); - m_Instrument.ConsumeUse( from ); + if (!BaseInstrument.CheckMusicianship(from)) + { + from.SendLocalizedMessage(500612); // You play poorly, and there is no effect. + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else if (from.CheckTargetSkill(SkillName.Discordance, target, diff - 25.0, diff + 25.0)) + { + from.SendLocalizedMessage(1049539); // You play the song surpressing your targets strength + m_Instrument.PlayInstrumentWell(from); + m_Instrument.ConsumeUse(from); - ArrayList mods = new ArrayList(); - int effect; - double scalar; + ArrayList mods = new ArrayList(); + int effect; + double scalar; - if ( Core.AOS ) - { - double discord = from.Skills[SkillName.Discordance].Value; + if (Core.AOS) + { + double discord = from.Skills[SkillName.Discordance].Value; - if ( discord > 100.0 ) - effect = -20 + (int)((discord - 100.0) / -2.5); - else - effect = (int)(discord / -5.0); + if (discord > 100.0) + effect = -20 + (int)((discord - 100.0) / -2.5); + else + effect = (int)(discord / -5.0); - if ( Core.SE && BaseInstrument.GetBaseDifficulty( targ ) >= 160.0 ) - effect /= 2; + if (Core.SE && BaseInstrument.GetBaseDifficulty(targ) >= 160.0) + effect /= 2; - scalar = effect * 0.01; + scalar = effect * 0.01; - mods.Add( new ResistanceMod( ResistanceType.Physical, effect ) ); - mods.Add( new ResistanceMod( ResistanceType.Fire, effect ) ); - mods.Add( new ResistanceMod( ResistanceType.Cold, effect ) ); - mods.Add( new ResistanceMod( ResistanceType.Poison, effect ) ); - mods.Add( new ResistanceMod( ResistanceType.Energy, effect ) ); + mods.Add(new ResistanceMod(ResistanceType.Physical, effect)); + mods.Add(new ResistanceMod(ResistanceType.Fire, effect)); + mods.Add(new ResistanceMod(ResistanceType.Cold, effect)); + mods.Add(new ResistanceMod(ResistanceType.Poison, effect)); + mods.Add(new ResistanceMod(ResistanceType.Energy, effect)); - for ( int i = 0; i < targ.Skills.Length; ++i ) - { - if ( targ.Skills[i].Value > 0 ) - mods.Add( new DefaultSkillMod( (SkillName)i, true, targ.Skills[i].Value * scalar ) ); - } - } - else - { - effect = (int)( from.Skills[SkillName.Discordance].Value / -5.0 ); - scalar = effect * 0.01; + for (int i = 0; i < targ.Skills.Length; ++i) + if (targ.Skills[i].Value > 0) + mods.Add(new DefaultSkillMod((SkillName)i, true, targ.Skills[i].Value * scalar)); + } + else + { + effect = (int)(from.Skills[SkillName.Discordance].Value / -5.0); + scalar = effect * 0.01; - mods.Add( new StatMod( StatType.Str, "DiscordanceStr", (int)(targ.RawStr * scalar), TimeSpan.Zero ) ); - mods.Add( new StatMod( StatType.Int, "DiscordanceInt", (int)(targ.RawInt * scalar), TimeSpan.Zero ) ); - mods.Add( new StatMod( StatType.Dex, "DiscordanceDex", (int)(targ.RawDex * scalar), TimeSpan.Zero ) ); + mods.Add(new StatMod(StatType.Str, "DiscordanceStr", (int)(targ.RawStr * scalar), + TimeSpan.Zero)); + mods.Add(new StatMod(StatType.Int, "DiscordanceInt", (int)(targ.RawInt * scalar), + TimeSpan.Zero)); + mods.Add(new StatMod(StatType.Dex, "DiscordanceDex", (int)(targ.RawDex * scalar), + TimeSpan.Zero)); - for ( int i = 0; i < targ.Skills.Length; ++i ) - { - if ( targ.Skills[i].Value > 0 ) - mods.Add( new DefaultSkillMod( (SkillName)i, true, targ.Skills[i].Value * scalar ) ); - } - } + for (int i = 0; i < targ.Skills.Length; ++i) + if (targ.Skills[i].Value > 0) + mods.Add(new DefaultSkillMod((SkillName)i, true, targ.Skills[i].Value * scalar)); + } - DiscordanceInfo info = new DiscordanceInfo( from, targ, Math.Abs( effect ), mods ); - info.m_Timer = Timer.DelayCall( TimeSpan.Zero, TimeSpan.FromSeconds( 1.25 ), ProcessDiscordance, info ); + DiscordanceInfo info = new DiscordanceInfo(from, targ, Math.Abs(effect), mods); + info.m_Timer = Timer.DelayCall(TimeSpan.Zero, TimeSpan.FromSeconds(1.25), ProcessDiscordance, + info); - m_Table[targ] = info; - } - else - { - from.SendLocalizedMessage( 1049540 );// You fail to disrupt your target - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } + m_Table[targ] = info; + } + else + { + from.SendLocalizedMessage(1049540); // You fail to disrupt your target + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } - from.NextSkillTime = Core.TickCount + 12000; - } - else - { - m_Instrument.PlayInstrumentBadly( from ); - } - } - else - { - from.SendLocalizedMessage( 1049535 ); // A song of discord would have no effect on that. - } - } - } - } + from.NextSkillTime = Core.TickCount + 12000; + } + else + { + m_Instrument.PlayInstrumentBadly(from); + } + } + else + { + from.SendLocalizedMessage(1049535); // A song of discord would have no effect on that. + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/EvalInt.cs b/Scripts/Skills/EvalInt.cs index 0eb8dc44c..391e75415 100644 --- a/Scripts/Skills/EvalInt.cs +++ b/Scripts/Skills/EvalInt.cs @@ -5,84 +5,91 @@ using Server.Targeting; namespace Server.SkillHandlers { - public class EvalInt - { - public static void Initialize() - { - SkillInfo.Table[16].Callback = OnUse; - } + public class EvalInt + { + public static void Initialize() + { + SkillInfo.Table[16].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile m) + { + m.Target = new InternalTarget(); - m.SendLocalizedMessage( 500906 ); // What do you wish to evaluate? + m.SendLocalizedMessage(500906); // What do you wish to evaluate? - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - private class InternalTarget : Target - { - public InternalTarget() : base ( 8, false, TargetFlags.None ) - { - } + private class InternalTarget : Target + { + public InternalTarget() : base(8, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( from == targeted ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500910 ); // Hmm, that person looks really silly. - } - else if ( targeted is TownCrier ) - { - ((TownCrier)targeted).PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500907, from.NetState ); // He looks smart enough to remember the news. Ask him about it. - } - else if ( targeted is BaseVendor && ((BaseVendor)targeted).IsInvulnerable ) - { - ((BaseVendor)targeted).PrivateOverheadMessage( MessageType.Regular, 0x3B2, 500909, from.NetState ); // That person could probably calculate the cost of what you buy from them. - } - else if ( targeted is Mobile ) - { - Mobile targ = (Mobile)targeted; + protected override void OnTarget(Mobile from, object targeted) + { + if (from == targeted) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 500910); // Hmm, that person looks really silly. + } + else if (targeted is TownCrier) + { + ((TownCrier)targeted).PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500907, + from.NetState); // He looks smart enough to remember the news. Ask him about it. + } + else if (targeted is BaseVendor && ((BaseVendor)targeted).IsInvulnerable) + { + ((BaseVendor)targeted).PrivateOverheadMessage(MessageType.Regular, 0x3B2, 500909, + from.NetState); // That person could probably calculate the cost of what you buy from them. + } + else if (targeted is Mobile) + { + Mobile targ = (Mobile)targeted; - int marginOfError = Math.Max( 0, 20 - (int)(from.Skills[SkillName.EvalInt].Value / 5) ); + int marginOfError = Math.Max(0, 20 - (int)(from.Skills[SkillName.EvalInt].Value / 5)); - int intel = targ.Int + Utility.RandomMinMax( -marginOfError, +marginOfError ); - int mana = ((targ.Mana * 100) / Math.Max( targ.ManaMax, 1 )) + Utility.RandomMinMax( -marginOfError, +marginOfError ); + int intel = targ.Int + Utility.RandomMinMax(-marginOfError, +marginOfError); + int mana = targ.Mana * 100 / Math.Max(targ.ManaMax, 1) + + Utility.RandomMinMax(-marginOfError, +marginOfError); - int intMod = intel / 10; - int mnMod = mana / 10; + int intMod = intel / 10; + int mnMod = mana / 10; - if ( intMod > 10 ) intMod = 10; - else if ( intMod < 0 ) intMod = 0; + if (intMod > 10) intMod = 10; + else if (intMod < 0) intMod = 0; - if ( mnMod > 10 ) mnMod = 10; - else if ( mnMod < 0 ) mnMod = 0; + if (mnMod > 10) mnMod = 10; + else if (mnMod < 0) mnMod = 0; - int body; + int body; - if ( targ.Body.IsHuman ) - body = targ.Female ? 11 : 0; - else - body = 22; + if (targ.Body.IsHuman) + body = targ.Female ? 11 : 0; + else + body = 22; - if ( from.CheckTargetSkill( SkillName.EvalInt, targ, 0.0, 120.0 ) ) - { - targ.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1038169 + intMod + body, from.NetState ); // He/She/It looks [slighly less intelligent than a rock.] [Of Average intellect] [etc...] + if (from.CheckTargetSkill(SkillName.EvalInt, targ, 0.0, 120.0)) + { + targ.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1038169 + intMod + body, + from.NetState); // He/She/It looks [slighly less intelligent than a rock.] [Of Average intellect] [etc...] - if ( from.Skills[SkillName.EvalInt].Base >= 76.0 ) - targ.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1038202 + mnMod, from.NetState ); // That being is at [10,20,...] percent mental strength. - } - else - { - targ.PrivateOverheadMessage( MessageType.Regular, 0x3B2, 1038166 + (body / 11), from.NetState ); // You cannot judge his/her/its mental abilities. - } - } - else - { - (targeted as Item)?.SendLocalizedMessageTo( from, 500908, "" ); // It looks smarter than a rock, but dumber than a piece of wood. - } - } - } - } -} + if (from.Skills[SkillName.EvalInt].Base >= 76.0) + targ.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1038202 + mnMod, + from.NetState); // That being is at [10,20,...] percent mental strength. + } + else + { + targ.PrivateOverheadMessage(MessageType.Regular, 0x3B2, 1038166 + body / 11, + from.NetState); // You cannot judge his/her/its mental abilities. + } + } + else + { + (targeted as Item)?.SendLocalizedMessageTo(from, 500908, + ""); // It looks smarter than a rock, but dumber than a piece of wood. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/ForensicEval.cs b/Scripts/Skills/ForensicEval.cs index bcd6b578a..62344db5c 100644 --- a/Scripts/Skills/ForensicEval.cs +++ b/Scripts/Skills/ForensicEval.cs @@ -1,95 +1,98 @@ using System; using System.Text; +using Server.Items; using Server.Mobiles; using Server.Targeting; -using Server.Items; namespace Server.SkillHandlers { - public class ForensicEvaluation - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Forensics].Callback = OnUse; - } + public class ForensicEvaluation + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Forensics].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.Target = new ForensicTarget(); - m.RevealingAction(); + public static TimeSpan OnUse(Mobile m) + { + m.Target = new ForensicTarget(); + m.RevealingAction(); - m.SendLocalizedMessage( 501000 ); // Show me the crime. + m.SendLocalizedMessage(501000); // Show me the crime. - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - public class ForensicTarget : Target - { - public ForensicTarget() : base( 10, false, TargetFlags.None ) - { - } + public class ForensicTarget : Target + { + public ForensicTarget() : base(10, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object target ) - { - if ( target is Mobile ) - { - if ( from.CheckTargetSkill( SkillName.Forensics, target, 40.0, 100.0 ) ) - { - if ( target is PlayerMobile && ((PlayerMobile)target).NpcGuild == NpcGuild.ThievesGuild ) - from.SendLocalizedMessage( 501004 );//That individual is a thief! - else - from.SendLocalizedMessage( 501003 );//You notice nothing unusual. - } - else - { - from.SendLocalizedMessage( 501001 );//You cannot determain anything useful. - } - } - else if ( target is Corpse ) - { - if ( from.CheckTargetSkill( SkillName.Forensics, target, 0.0, 100.0 ) ) - { - Corpse c = (Corpse)target; + protected override void OnTarget(Mobile from, object target) + { + if (target is Mobile) + { + if (from.CheckTargetSkill(SkillName.Forensics, target, 40.0, 100.0)) + { + if (target is PlayerMobile && ((PlayerMobile)target).NpcGuild == NpcGuild.ThievesGuild) + from.SendLocalizedMessage(501004); //That individual is a thief! + else + from.SendLocalizedMessage(501003); //You notice nothing unusual. + } + else + { + from.SendLocalizedMessage(501001); //You cannot determain anything useful. + } + } + else if (target is Corpse) + { + if (from.CheckTargetSkill(SkillName.Forensics, target, 0.0, 100.0)) + { + Corpse c = (Corpse)target; - if ( c.m_Forensicist != null ) - from.SendLocalizedMessage( 1042750, c.m_Forensicist ) ; // The forensicist ~1_NAME~ has already discovered that: - else - c.m_Forensicist = from.Name; + if (c.m_Forensicist != null) + from.SendLocalizedMessage(1042750, + c.m_Forensicist); // The forensicist ~1_NAME~ has already discovered that: + else + c.m_Forensicist = from.Name; - if ( ((Body)c.Amount).IsHuman ) - from.SendLocalizedMessage( 1042751, ( c.Killer == null ? "no one" : c.Killer.Name ) );//This person was killed by ~1_KILLER_NAME~ + if (((Body)c.Amount).IsHuman) + from.SendLocalizedMessage(1042751, + c.Killer == null ? "no one" : c.Killer.Name); //This person was killed by ~1_KILLER_NAME~ - if ( c.Looters.Count > 0 ) - { - StringBuilder sb = new StringBuilder(); - for (int i=0;i0 ) - sb.Append( ", " ); - sb.Append( ((Mobile)c.Looters[i]).Name ); - } + if (c.Looters.Count > 0) + { + StringBuilder sb = new StringBuilder(); + for (int i = 0; i < c.Looters.Count; i++) + { + if (i > 0) + sb.Append(", "); + sb.Append(c.Looters[i].Name); + } - from.SendLocalizedMessage( 1042752, sb.ToString() );//This body has been distrubed by ~1_PLAYER_NAMES~ - } - else - { - from.SendLocalizedMessage( 501002 );//The corpse has not be desecrated. - } - } - else - { - from.SendLocalizedMessage( 501001 );//You cannot determain anything useful. - } - } - else if ( target is ILockpickable ) - { - ILockpickable p = (ILockpickable)target; - if ( p.Picker != null ) - from.SendLocalizedMessage( 1042749, p.Picker.Name );//This lock was opened by ~1_PICKER_NAME~ - else - from.SendLocalizedMessage( 501003 );//You notice nothing unusual. - } - } - } - } -} + from.SendLocalizedMessage(1042752, + sb.ToString()); //This body has been distrubed by ~1_PLAYER_NAMES~ + } + else + { + from.SendLocalizedMessage(501002); //The corpse has not be desecrated. + } + } + else + { + from.SendLocalizedMessage(501001); //You cannot determain anything useful. + } + } + else if (target is ILockpickable) + { + ILockpickable p = (ILockpickable)target; + if (p.Picker != null) + from.SendLocalizedMessage(1042749, p.Picker.Name); //This lock was opened by ~1_PICKER_NAME~ + else + from.SendLocalizedMessage(501003); //You notice nothing unusual. + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Hiding.cs b/Scripts/Skills/Hiding.cs index 40f06c383..4737fe218 100644 --- a/Scripts/Skills/Hiding.cs +++ b/Scripts/Skills/Hiding.cs @@ -1,104 +1,100 @@ using System; -using Server.Network; using Server.Multis; +using Server.Network; +using Server.Targeting; namespace Server.SkillHandlers { - public class Hiding - { - public static bool CombatOverride { get; set; } + public class Hiding + { + public static bool CombatOverride{ get; set; } - public static void Initialize() - { - SkillInfo.Table[21].Callback = OnUse; - } + public static void Initialize() + { + SkillInfo.Table[21].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - if ( m.Spell != null ) - { - m.SendLocalizedMessage( 501238 ); // You are busy doing something else and cannot hide. - return TimeSpan.FromSeconds( 1.0 ); - } + public static TimeSpan OnUse(Mobile m) + { + if (m.Spell != null) + { + m.SendLocalizedMessage(501238); // You are busy doing something else and cannot hide. + return TimeSpan.FromSeconds(1.0); + } - if ( Core.ML && m.Target != null ) - { - Targeting.Target.Cancel( m ); - } + if (Core.ML && m.Target != null) Target.Cancel(m); - double bonus = 0.0; + double bonus = 0.0; - BaseHouse house = BaseHouse.FindHouseAt( m ); + BaseHouse house = BaseHouse.FindHouseAt(m); - if ( house != null && house.IsFriend( m ) ) - { - bonus = 100.0; - } - else if ( !Core.AOS ) - { - if ( house == null ) - house = BaseHouse.FindHouseAt( new Point3D( m.X - 1, m.Y, 127 ), m.Map, 16 ); + if (house != null && house.IsFriend(m)) + { + bonus = 100.0; + } + else if (!Core.AOS) + { + if (house == null) + house = BaseHouse.FindHouseAt(new Point3D(m.X - 1, m.Y, 127), m.Map, 16); - if ( house == null ) - house = BaseHouse.FindHouseAt( new Point3D( m.X + 1, m.Y, 127 ), m.Map, 16 ); + if (house == null) + house = BaseHouse.FindHouseAt(new Point3D(m.X + 1, m.Y, 127), m.Map, 16); - if ( house == null ) - house = BaseHouse.FindHouseAt( new Point3D( m.X, m.Y - 1, 127 ), m.Map, 16 ); + if (house == null) + house = BaseHouse.FindHouseAt(new Point3D(m.X, m.Y - 1, 127), m.Map, 16); - if ( house == null ) - house = BaseHouse.FindHouseAt( new Point3D( m.X, m.Y + 1, 127 ), m.Map, 16 ); + if (house == null) + house = BaseHouse.FindHouseAt(new Point3D(m.X, m.Y + 1, 127), m.Map, 16); - if ( house != null ) - bonus = 50.0; - } + if (house != null) + bonus = 50.0; + } - //int range = 18 - (int)(m.Skills[SkillName.Hiding].Value / 10); - int range = Math.Min( (int)((100 - m.Skills[SkillName.Hiding].Value)/2) + 8, 18 ); //Cap of 18 not OSI-exact, intentional difference + //int range = 18 - (int)(m.Skills[SkillName.Hiding].Value / 10); + int range = Math.Min((int)((100 - m.Skills[SkillName.Hiding].Value) / 2) + 8, + 18); //Cap of 18 not OSI-exact, intentional difference - bool badCombat = ( !CombatOverride && m.Combatant != null && m.InRange( m.Combatant.Location, range ) && m.Combatant.InLOS( m ) ); - bool ok = ( !badCombat /*&& m.CheckSkill( SkillName.Hiding, 0.0 - bonus, 100.0 - bonus )*/ ); + bool badCombat = !CombatOverride && m.Combatant != null && m.InRange(m.Combatant.Location, range) && + m.Combatant.InLOS(m); + bool ok = !badCombat; - if ( ok ) - { - if ( !CombatOverride ) - { - foreach ( Mobile check in m.GetMobilesInRange( range ) ) - { - if ( check.InLOS( m ) && check.Combatant == m ) - { - badCombat = true; - ok = false; - break; - } - } - } + if (ok) + { + if (!CombatOverride) + foreach (Mobile check in m.GetMobilesInRange(range)) + if (check.InLOS(m) && check.Combatant == m) + { + badCombat = true; + ok = false; + break; + } - ok = ( !badCombat && m.CheckSkill( SkillName.Hiding, 0.0 - bonus, 100.0 - bonus ) ); - } + ok = !badCombat && m.CheckSkill(SkillName.Hiding, 0.0 - bonus, 100.0 - bonus); + } - if ( badCombat ) - { - m.RevealingAction(); + if (badCombat) + { + m.RevealingAction(); - m.LocalOverheadMessage( MessageType.Regular, 0x22, 501237 ); // You can't seem to hide right now. + m.LocalOverheadMessage(MessageType.Regular, 0x22, 501237); // You can't seem to hide right now. - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - if ( ok ) - { - m.Hidden = true; - m.Warmode = false; - m.LocalOverheadMessage( MessageType.Regular, 0x1F4, 501240 ); // You have hidden yourself well. - } - else - { - m.RevealingAction(); + if (ok) + { + m.Hidden = true; + m.Warmode = false; + m.LocalOverheadMessage(MessageType.Regular, 0x1F4, 501240); // You have hidden yourself well. + } + else + { + m.RevealingAction(); - m.LocalOverheadMessage( MessageType.Regular, 0x22, 501241 ); // You can't seem to hide here. - } + m.LocalOverheadMessage(MessageType.Regular, 0x22, 501241); // You can't seem to hide here. + } - return TimeSpan.FromSeconds( 10.0 ); - } - } + return TimeSpan.FromSeconds(10.0); + } + } } \ No newline at end of file diff --git a/Scripts/Skills/Inscribe.cs b/Scripts/Skills/Inscribe.cs index e691046ef..99e32f605 100644 --- a/Scripts/Skills/Inscribe.cs +++ b/Scripts/Skills/Inscribe.cs @@ -1,162 +1,176 @@ using System; using System.Collections.Generic; -using Server.Targeting; using Server.Items; +using Server.Targeting; namespace Server.SkillHandlers { - public class Inscribe - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Inscribe].Callback = OnUse; - } + public class Inscribe + { + private static Dictionary m_UseTable = new Dictionary(); - public static TimeSpan OnUse( Mobile m ) - { - Target target = new InternalTargetSrc(); - m.Target = target; - m.SendLocalizedMessage( 1046295 ); // Target the book you wish to copy. - target.BeginTimeout( m, TimeSpan.FromMinutes( 1.0 ) ); + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Inscribe].Callback = OnUse; + } - return TimeSpan.FromSeconds( 1.0 ); - } + public static TimeSpan OnUse(Mobile m) + { + Target target = new InternalTargetSrc(); + m.Target = target; + m.SendLocalizedMessage(1046295); // Target the book you wish to copy. + target.BeginTimeout(m, TimeSpan.FromMinutes(1.0)); - private static Dictionary m_UseTable = new Dictionary(); + return TimeSpan.FromSeconds(1.0); + } - private static void SetUser( BaseBook book, Mobile mob ) - { - m_UseTable[book] = mob; - } + private static void SetUser(BaseBook book, Mobile mob) + { + m_UseTable[book] = mob; + } - private static void CancelUser( BaseBook book ) - { - m_UseTable.Remove( book ); - } + private static void CancelUser(BaseBook book) + { + m_UseTable.Remove(book); + } - public static Mobile GetUser( BaseBook book ) - { - m_UseTable.TryGetValue( book, out Mobile m ); - return m; - } + public static Mobile GetUser(BaseBook book) + { + m_UseTable.TryGetValue(book, out Mobile m); + return m; + } - public static bool IsEmpty( BaseBook book ) - { - foreach ( BookPageInfo page in book.Pages ) - { - foreach ( string line in page.Lines ) - { - if ( line.Trim().Length != 0 ) - return false; - } - } - return true; - } + public static bool IsEmpty(BaseBook book) + { + foreach (BookPageInfo page in book.Pages) + foreach (string line in page.Lines) + if (line.Trim().Length != 0) + return false; + return true; + } - public static void Copy( BaseBook bookSrc, BaseBook bookDst ) - { - bookDst.Title = bookSrc.Title; - bookDst.Author = bookSrc.Author; + public static void Copy(BaseBook bookSrc, BaseBook bookDst) + { + bookDst.Title = bookSrc.Title; + bookDst.Author = bookSrc.Author; - BookPageInfo[] pagesSrc = bookSrc.Pages; - BookPageInfo[] pagesDst = bookDst.Pages; - for ( int i = 0; i < pagesSrc.Length && i < pagesDst.Length; i++ ) - { - BookPageInfo pageSrc = pagesSrc[i]; - BookPageInfo pageDst = pagesDst[i]; + BookPageInfo[] pagesSrc = bookSrc.Pages; + BookPageInfo[] pagesDst = bookDst.Pages; + for (int i = 0; i < pagesSrc.Length && i < pagesDst.Length; i++) + { + BookPageInfo pageSrc = pagesSrc[i]; + BookPageInfo pageDst = pagesDst[i]; - int length = pageSrc.Lines.Length; - pageDst.Lines = new string[length]; + int length = pageSrc.Lines.Length; + pageDst.Lines = new string[length]; - for ( int j = 0; j < length; j++ ) - pageDst.Lines[j] = pageSrc.Lines[j]; - } - } + for (int j = 0; j < length; j++) + pageDst.Lines[j] = pageSrc.Lines[j]; + } + } - private class InternalTargetSrc : Target - { - public InternalTargetSrc() : base ( 3, false, TargetFlags.None ) - { - } + private class InternalTargetSrc : Target + { + public InternalTargetSrc() : base(3, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - BaseBook book = targeted as BaseBook; - if ( book == null ) - from.SendLocalizedMessage( 1046296 ); // That is not a book - else if ( IsEmpty( book ) ) - from.SendLocalizedMessage( 501611 ); // Can't copy an empty book. - else if ( GetUser( book ) != null ) - from.SendLocalizedMessage( 501621 ); // Someone else is inscribing that item. - else - { - Target target = new InternalTargetDst( book ); - from.Target = target; - from.SendLocalizedMessage( 501612 ); // Select a book to copy this to. - target.BeginTimeout( from, TimeSpan.FromMinutes( 1.0 ) ); - SetUser( book, from ); - } - } + protected override void OnTarget(Mobile from, object targeted) + { + BaseBook book = targeted as BaseBook; + if (book == null) + { + from.SendLocalizedMessage(1046296); // That is not a book + } + else if (IsEmpty(book)) + { + from.SendLocalizedMessage(501611); // Can't copy an empty book. + } + else if (GetUser(book) != null) + { + from.SendLocalizedMessage(501621); // Someone else is inscribing that item. + } + else + { + Target target = new InternalTargetDst(book); + from.Target = target; + from.SendLocalizedMessage(501612); // Select a book to copy this to. + target.BeginTimeout(from, TimeSpan.FromMinutes(1.0)); + SetUser(book, from); + } + } - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - if ( cancelType == TargetCancelType.Timeout ) - from.SendLocalizedMessage( 501619 ); // You have waited too long to make your inscribe selection, your inscription attempt has timed out. - } - } + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + if (cancelType == TargetCancelType.Timeout) + from.SendLocalizedMessage( + 501619); // You have waited too long to make your inscribe selection, your inscription attempt has timed out. + } + } - private class InternalTargetDst : Target - { - private BaseBook m_BookSrc; + private class InternalTargetDst : Target + { + private BaseBook m_BookSrc; - public InternalTargetDst( BaseBook bookSrc ) : base ( 3, false, TargetFlags.None ) - { - m_BookSrc = bookSrc; - } + public InternalTargetDst(BaseBook bookSrc) : base(3, false, TargetFlags.None) + { + m_BookSrc = bookSrc; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_BookSrc.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_BookSrc.Deleted) + return; - BaseBook bookDst = targeted as BaseBook; + BaseBook bookDst = targeted as BaseBook; - if ( bookDst == null ) - from.SendLocalizedMessage( 1046296 ); // That is not a book - else if ( IsEmpty( m_BookSrc ) ) - from.SendLocalizedMessage( 501611 ); // Can't copy an empty book. - else if ( bookDst == m_BookSrc ) - from.SendLocalizedMessage( 501616 ); // Cannot copy a book onto itself. - else if ( !bookDst.Writable ) - from.SendLocalizedMessage( 501614 ); // Cannot write into that book. - else if ( GetUser( bookDst ) != null ) - from.SendLocalizedMessage( 501621 ); // Someone else is inscribing that item. - else - { - if ( from.CheckTargetSkill( SkillName.Inscribe, bookDst, 0, 50 ) ) - { - Copy( m_BookSrc, bookDst ); + if (bookDst == null) + { + from.SendLocalizedMessage(1046296); // That is not a book + } + else if (IsEmpty(m_BookSrc)) + { + from.SendLocalizedMessage(501611); // Can't copy an empty book. + } + else if (bookDst == m_BookSrc) + { + from.SendLocalizedMessage(501616); // Cannot copy a book onto itself. + } + else if (!bookDst.Writable) + { + from.SendLocalizedMessage(501614); // Cannot write into that book. + } + else if (GetUser(bookDst) != null) + { + from.SendLocalizedMessage(501621); // Someone else is inscribing that item. + } + else + { + if (from.CheckTargetSkill(SkillName.Inscribe, bookDst, 0, 50)) + { + Copy(m_BookSrc, bookDst); - from.SendLocalizedMessage( 501618 ); // You make a copy of the book. - from.PlaySound( 0x249 ); - } - else - { - from.SendLocalizedMessage( 501617 ); // You fail to make a copy of the book. - } - } - } + from.SendLocalizedMessage(501618); // You make a copy of the book. + from.PlaySound(0x249); + } + else + { + from.SendLocalizedMessage(501617); // You fail to make a copy of the book. + } + } + } - protected override void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - if ( cancelType == TargetCancelType.Timeout ) - from.SendLocalizedMessage( 501619 ); // You have waited too long to make your inscribe selection, your inscription attempt has timed out. - } + protected override void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + if (cancelType == TargetCancelType.Timeout) + from.SendLocalizedMessage( + 501619); // You have waited too long to make your inscribe selection, your inscription attempt has timed out. + } - protected override void OnTargetFinish( Mobile from ) - { - CancelUser( m_BookSrc ); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + CancelUser(m_BookSrc); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/ItemIdentification.cs b/Scripts/Skills/ItemIdentification.cs index b98edb34b..454b788b3 100644 --- a/Scripts/Skills/ItemIdentification.cs +++ b/Scripts/Skills/ItemIdentification.cs @@ -1,60 +1,60 @@ using System; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Items { - public class ItemIdentification - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.ItemID].Callback = OnUse; - } + public class ItemIdentification + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.ItemID].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile from ) - { - from.SendLocalizedMessage( 500343 ); // What do you wish to appraise and identify? - from.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile from) + { + from.SendLocalizedMessage(500343); // What do you wish to appraise and identify? + from.Target = new InternalTarget(); - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - [PlayerVendorTarget] - private class InternalTarget : Target - { - public InternalTarget() : base ( 8, false, TargetFlags.None ) - { - AllowNonlocal = true; - } + [PlayerVendorTarget] + private class InternalTarget : Target + { + public InternalTarget() : base(8, false, TargetFlags.None) + { + AllowNonlocal = true; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Item ) - { - if ( from.CheckTargetSkill( SkillName.ItemID, o, 0, 100 ) ) - { - if ( o is BaseWeapon ) - ((BaseWeapon)o).Identified = true; - else if ( o is BaseArmor ) - ((BaseArmor)o).Identified = true; + protected override void OnTarget(Mobile from, object o) + { + if (o is Item) + { + if (from.CheckTargetSkill(SkillName.ItemID, o, 0, 100)) + { + if (o is BaseWeapon) + ((BaseWeapon)o).Identified = true; + else if (o is BaseArmor) + ((BaseArmor)o).Identified = true; - if ( !Core.AOS ) - ((Item)o).OnSingleClick( from ); - } - else - { - from.SendLocalizedMessage( 500353 ); // You are not certain... - } - } - else if ( o is Mobile ) - { - ((Mobile)o).OnSingleClick( from ); - } - else - { - from.SendLocalizedMessage( 500353 ); // You are not certain... - } - } - } - } + if (!Core.AOS) + ((Item)o).OnSingleClick(from); + } + else + { + from.SendLocalizedMessage(500353); // You are not certain... + } + } + else if (o is Mobile) + { + ((Mobile)o).OnSingleClick(from); + } + else + { + from.SendLocalizedMessage(500353); // You are not certain... + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/Meditation.cs b/Scripts/Skills/Meditation.cs index 8c32944e1..e67eb45fb 100644 --- a/Scripts/Skills/Meditation.cs +++ b/Scripts/Skills/Meditation.cs @@ -1,99 +1,103 @@ using System; using Server.Items; +using Server.Misc; namespace Server.SkillHandlers { - class Meditation - { - public static void Initialize() - { - SkillInfo.Table[46].Callback = OnUse; - } + internal class Meditation + { + public static void Initialize() + { + SkillInfo.Table[46].Callback = OnUse; + } - public static bool CheckOkayHolding( Item item ) - { - if ( item == null ) - return true; + public static bool CheckOkayHolding(Item item) + { + if (item == null) + return true; - if ( item is Spellbook || item is Runebook ) - return true; + if (item is Spellbook || item is Runebook) + return true; - if ( Core.AOS && item is BaseWeapon && ((BaseWeapon)item).Attributes.SpellChanneling != 0 ) - return true; + if (Core.AOS && item is BaseWeapon && ((BaseWeapon)item).Attributes.SpellChanneling != 0) + return true; - if ( Core.AOS && item is BaseArmor && ((BaseArmor)item).Attributes.SpellChanneling != 0 ) - return true; + if (Core.AOS && item is BaseArmor && ((BaseArmor)item).Attributes.SpellChanneling != 0) + return true; - return false; - } + return false; + } - public static TimeSpan OnUse( Mobile m ) - { - m.RevealingAction(); + public static TimeSpan OnUse(Mobile m) + { + m.RevealingAction(); - if ( m.Target != null ) - { - m.SendLocalizedMessage( 501845 ); // You are busy doing something else and cannot focus. + if (m.Target != null) + { + m.SendLocalizedMessage(501845); // You are busy doing something else and cannot focus. - return TimeSpan.FromSeconds( 5.0 ); - } + return TimeSpan.FromSeconds(5.0); + } - if ( !Core.AOS && m.Hits < (m.HitsMax / 10) ) // Less than 10% health - { - m.SendLocalizedMessage( 501849 ); // The mind is strong but the body is weak. + if (!Core.AOS && m.Hits < m.HitsMax / 10) // Less than 10% health + { + m.SendLocalizedMessage(501849); // The mind is strong but the body is weak. - return TimeSpan.FromSeconds( 5.0 ); - } - if ( m.Mana >= m.ManaMax ) - { - m.SendLocalizedMessage( 501846 ); // You are at peace. + return TimeSpan.FromSeconds(5.0); + } - return TimeSpan.FromSeconds( Core.AOS ? 10.0 : 5.0 ); - } - if ( Core.AOS && Misc.RegenRates.GetArmorOffset( m ) > 0 ) - { - m.SendLocalizedMessage( 500135 ); // Regenerative forces cannot penetrate your armor! + if (m.Mana >= m.ManaMax) + { + m.SendLocalizedMessage(501846); // You are at peace. - return TimeSpan.FromSeconds( 10.0 ); - } - Item oneHanded = m.FindItemOnLayer( Layer.OneHanded ); - Item twoHanded = m.FindItemOnLayer( Layer.TwoHanded ); + return TimeSpan.FromSeconds(Core.AOS ? 10.0 : 5.0); + } - if ( Core.AOS && m.Player ) - { - if ( !CheckOkayHolding( oneHanded ) ) - m.AddToBackpack( oneHanded ); + if (Core.AOS && RegenRates.GetArmorOffset(m) > 0) + { + m.SendLocalizedMessage(500135); // Regenerative forces cannot penetrate your armor! - if ( !CheckOkayHolding( twoHanded ) ) - m.AddToBackpack( twoHanded ); - } - else if ( !CheckOkayHolding( oneHanded ) || !CheckOkayHolding( twoHanded ) ) - { - m.SendLocalizedMessage( 502626 ); // Your hands must be free to cast spells or meditate. + return TimeSpan.FromSeconds(10.0); + } - return TimeSpan.FromSeconds( 2.5 ); - } + Item oneHanded = m.FindItemOnLayer(Layer.OneHanded); + Item twoHanded = m.FindItemOnLayer(Layer.TwoHanded); - double skillVal = m.Skills[SkillName.Meditation].Value; - double chance = (50.0 + (( skillVal - ( m.ManaMax - m.Mana ) ) * 2)) / 100; + if (Core.AOS && m.Player) + { + if (!CheckOkayHolding(oneHanded)) + m.AddToBackpack(oneHanded); - if ( chance > Utility.RandomDouble() ) - { - m.CheckSkill( SkillName.Meditation, 0.0, 100.0 ); + if (!CheckOkayHolding(twoHanded)) + m.AddToBackpack(twoHanded); + } + else if (!CheckOkayHolding(oneHanded) || !CheckOkayHolding(twoHanded)) + { + m.SendLocalizedMessage(502626); // Your hands must be free to cast spells or meditate. - m.SendLocalizedMessage( 501851 ); // You enter a meditative trance. - m.Meditating = true; - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.ActiveMeditation, 1075657 ) ); + return TimeSpan.FromSeconds(2.5); + } - if ( m.Player || m.Body.IsHuman ) - m.PlaySound( 0xF9 ); - } - else - { - m.SendLocalizedMessage( 501850 ); // You cannot focus your concentration. - } + double skillVal = m.Skills[SkillName.Meditation].Value; + double chance = (50.0 + (skillVal - (m.ManaMax - m.Mana)) * 2) / 100; - return TimeSpan.FromSeconds( 10.0 ); - } - } -} + if (chance > Utility.RandomDouble()) + { + m.CheckSkill(SkillName.Meditation, 0.0, 100.0); + + m.SendLocalizedMessage(501851); // You enter a meditative trance. + m.Meditating = true; + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.ActiveMeditation, 1075657)); + + if (m.Player || m.Body.IsHuman) + m.PlaySound(0xF9); + } + else + { + m.SendLocalizedMessage(501850); // You cannot focus your concentration. + } + + return TimeSpan.FromSeconds(10.0); + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Peacemaking.cs b/Scripts/Skills/Peacemaking.cs index aee0f513b..14e54d8cb 100644 --- a/Scripts/Skills/Peacemaking.cs +++ b/Scripts/Skills/Peacemaking.cs @@ -1,206 +1,214 @@ using System; -using Server.Targeting; -using Server.Mobiles; +using Server.Engines.ConPVP; using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.SkillHandlers { - public class Peacemaking - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Peacemaking].Callback = OnUse; - } + public class Peacemaking + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Peacemaking].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.RevealingAction(); + public static TimeSpan OnUse(Mobile m) + { + m.RevealingAction(); - BaseInstrument.PickInstrument( m, OnPickedInstrument ); + BaseInstrument.PickInstrument(m, OnPickedInstrument); - return TimeSpan.FromSeconds( 1.0 ); // Cannot use another skill for 1 second - } + return TimeSpan.FromSeconds(1.0); // Cannot use another skill for 1 second + } - public static void OnPickedInstrument( Mobile from, BaseInstrument instrument ) - { - from.RevealingAction(); - from.SendLocalizedMessage( 1049525 ); // Whom do you wish to calm? - from.Target = new InternalTarget( from, instrument ); - from.NextSkillTime = Core.TickCount + 21600000; - } + public static void OnPickedInstrument(Mobile from, BaseInstrument instrument) + { + from.RevealingAction(); + from.SendLocalizedMessage(1049525); // Whom do you wish to calm? + from.Target = new InternalTarget(from, instrument); + from.NextSkillTime = Core.TickCount + 21600000; + } - private class InternalTarget : Target - { - private BaseInstrument m_Instrument; - private bool m_SetSkillTime = true; + private class InternalTarget : Target + { + private BaseInstrument m_Instrument; + private bool m_SetSkillTime = true; - public InternalTarget( Mobile from, BaseInstrument instrument ) : base( BaseInstrument.GetBardRange( from, SkillName.Peacemaking ), false, TargetFlags.None ) - { - m_Instrument = instrument; - } + public InternalTarget(Mobile from, BaseInstrument instrument) : base( + BaseInstrument.GetBardRange(from, SkillName.Peacemaking), false, TargetFlags.None) + { + m_Instrument = instrument; + } - protected override void OnTargetFinish( Mobile from ) - { - if ( m_SetSkillTime ) - from.NextSkillTime = Core.TickCount; - } + protected override void OnTargetFinish(Mobile from) + { + if (m_SetSkillTime) + from.NextSkillTime = Core.TickCount; + } - protected override void OnTarget( Mobile from, object targeted ) - { - from.RevealingAction(); + protected override void OnTarget(Mobile from, object targeted) + { + from.RevealingAction(); - if ( !(targeted is Mobile) ) - { - from.SendLocalizedMessage( 1049528 ); // You cannot calm that! - } - else if ( from.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - from.SendMessage( "You may not peacemake in this area." ); - } - else if ( ((Mobile)targeted).Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - from.SendMessage( "You may not peacemake there." ); - } - else if ( !m_Instrument.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1062488 ); // The instrument you are trying to play is no longer in your backpack! - } - else - { - m_SetSkillTime = false; - from.NextSkillTime = Core.TickCount + 10000; + if (!(targeted is Mobile)) + { + from.SendLocalizedMessage(1049528); // You cannot calm that! + } + else if (from.Region.IsPartOf(typeof(SafeZone))) + { + from.SendMessage("You may not peacemake in this area."); + } + else if (((Mobile)targeted).Region.IsPartOf(typeof(SafeZone))) + { + from.SendMessage("You may not peacemake there."); + } + else if (!m_Instrument.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage( + 1062488); // The instrument you are trying to play is no longer in your backpack! + } + else + { + m_SetSkillTime = false; + from.NextSkillTime = Core.TickCount + 10000; - if ( targeted == from ) - { - // Standard mode : reset combatants for everyone in the area + if (targeted == from) + { + // Standard mode : reset combatants for everyone in the area - if ( !BaseInstrument.CheckMusicianship( from ) ) - { - from.SendLocalizedMessage( 500612 ); // You play poorly, and there is no effect. - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else if ( !from.CheckSkill( SkillName.Peacemaking, 0.0, 120.0 ) ) - { - from.SendLocalizedMessage( 500613 ); // You attempt to calm everyone, but fail. - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else - { - from.NextSkillTime = Core.TickCount + 5000; - m_Instrument.PlayInstrumentWell( from ); - m_Instrument.ConsumeUse( from ); + if (!BaseInstrument.CheckMusicianship(from)) + { + from.SendLocalizedMessage(500612); // You play poorly, and there is no effect. + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else if (!from.CheckSkill(SkillName.Peacemaking, 0.0, 120.0)) + { + from.SendLocalizedMessage(500613); // You attempt to calm everyone, but fail. + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else + { + from.NextSkillTime = Core.TickCount + 5000; + m_Instrument.PlayInstrumentWell(from); + m_Instrument.ConsumeUse(from); - Map map = from.Map; + Map map = from.Map; - if ( map != null ) - { - int range = BaseInstrument.GetBardRange( from, SkillName.Peacemaking ); + if (map != null) + { + int range = BaseInstrument.GetBardRange(from, SkillName.Peacemaking); - bool calmed = false; + bool calmed = false; - foreach ( Mobile m in from.GetMobilesInRange( range ) ) - { - if ((m is BaseCreature && ((BaseCreature)m).Uncalmable) || (m is BaseCreature && ((BaseCreature)m).AreaPeaceImmune) || m == from || !from.CanBeHarmful ( m, false )) - continue; + foreach (Mobile m in from.GetMobilesInRange(range)) + { + if (m is BaseCreature && ((BaseCreature)m).Uncalmable || + m is BaseCreature && ((BaseCreature)m).AreaPeaceImmune || m == from || + !from.CanBeHarmful(m, false)) + continue; - calmed = true; + calmed = true; - m.SendLocalizedMessage( 500616 ); // You hear lovely music, and forget to continue battling! - m.Combatant = null; - m.Warmode = false; + m.SendLocalizedMessage( + 500616); // You hear lovely music, and forget to continue battling! + m.Combatant = null; + m.Warmode = false; - if ( m is BaseCreature && !((BaseCreature)m).BardPacified ) - ((BaseCreature)m).Pacify( from, DateTime.UtcNow + TimeSpan.FromSeconds( 1.0 ) ); - } + if (m is BaseCreature && !((BaseCreature)m).BardPacified) + ((BaseCreature)m).Pacify(from, DateTime.UtcNow + TimeSpan.FromSeconds(1.0)); + } - if ( !calmed ) - from.SendLocalizedMessage( 1049648 ); // You play hypnotic music, but there is nothing in range for you to calm. - else - from.SendLocalizedMessage( 500615 ); // You play your hypnotic music, stopping the battle. - } - } - } - else - { - // Target mode : pacify a single target for a longer duration + if (!calmed) + from.SendLocalizedMessage( + 1049648); // You play hypnotic music, but there is nothing in range for you to calm. + else + from.SendLocalizedMessage(500615); // You play your hypnotic music, stopping the battle. + } + } + } + else + { + // Target mode : pacify a single target for a longer duration - Mobile targ = (Mobile)targeted; + Mobile targ = (Mobile)targeted; - if ( !from.CanBeHarmful( targ, false ) ) - { - from.SendLocalizedMessage( 1049528 ); - m_SetSkillTime = true; - } - else if ( targ is BaseCreature && ((BaseCreature)targ).Uncalmable ) - { - from.SendLocalizedMessage( 1049526 ); // You have no chance of calming that creature. - m_SetSkillTime = true; - } - else if ( targ is BaseCreature && ((BaseCreature)targ).BardPacified ) - { - from.SendLocalizedMessage( 1049527 ); // That creature is already being calmed. - m_SetSkillTime = true; - } - else if ( !BaseInstrument.CheckMusicianship( from ) ) - { - from.SendLocalizedMessage( 500612 ); // You play poorly, and there is no effect. - from.NextSkillTime = Core.TickCount + 5000; - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else - { - double diff = m_Instrument.GetDifficultyFor( targ ) - 10.0; - double music = from.Skills[SkillName.Musicianship].Value; + if (!from.CanBeHarmful(targ, false)) + { + from.SendLocalizedMessage(1049528); + m_SetSkillTime = true; + } + else if (targ is BaseCreature && ((BaseCreature)targ).Uncalmable) + { + from.SendLocalizedMessage(1049526); // You have no chance of calming that creature. + m_SetSkillTime = true; + } + else if (targ is BaseCreature && ((BaseCreature)targ).BardPacified) + { + from.SendLocalizedMessage(1049527); // That creature is already being calmed. + m_SetSkillTime = true; + } + else if (!BaseInstrument.CheckMusicianship(from)) + { + from.SendLocalizedMessage(500612); // You play poorly, and there is no effect. + from.NextSkillTime = Core.TickCount + 5000; + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else + { + double diff = m_Instrument.GetDifficultyFor(targ) - 10.0; + double music = from.Skills[SkillName.Musicianship].Value; - if ( music > 100.0 ) - diff -= (music - 100.0) * 0.5; + if (music > 100.0) + diff -= (music - 100.0) * 0.5; - if ( !from.CheckTargetSkill( SkillName.Peacemaking, targ, diff - 25.0, diff + 25.0 ) ) - { - from.SendLocalizedMessage( 1049531 ); // You attempt to calm your target, but fail. - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else - { - m_Instrument.PlayInstrumentWell( from ); - m_Instrument.ConsumeUse( from ); + if (!from.CheckTargetSkill(SkillName.Peacemaking, targ, diff - 25.0, diff + 25.0)) + { + from.SendLocalizedMessage(1049531); // You attempt to calm your target, but fail. + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else + { + m_Instrument.PlayInstrumentWell(from); + m_Instrument.ConsumeUse(from); - from.NextSkillTime = Core.TickCount + 5000; - if ( targ is BaseCreature ) - { - BaseCreature bc = (BaseCreature)targ; + from.NextSkillTime = Core.TickCount + 5000; + if (targ is BaseCreature) + { + BaseCreature bc = (BaseCreature)targ; - from.SendLocalizedMessage( 1049532 ); // You play hypnotic music, calming your target. + from.SendLocalizedMessage(1049532); // You play hypnotic music, calming your target. - targ.Combatant = null; - targ.Warmode = false; + targ.Combatant = null; + targ.Warmode = false; - double seconds = 100 - (diff / 1.5); + double seconds = 100 - diff / 1.5; - if ( seconds > 120 ) - seconds = 120; - else if ( seconds < 10 ) - seconds = 10; + if (seconds > 120) + seconds = 120; + else if (seconds < 10) + seconds = 10; - bc.Pacify( from, DateTime.UtcNow + TimeSpan.FromSeconds( seconds ) ); - } - else - { - from.SendLocalizedMessage( 1049532 ); // You play hypnotic music, calming your target. + bc.Pacify(from, DateTime.UtcNow + TimeSpan.FromSeconds(seconds)); + } + else + { + from.SendLocalizedMessage(1049532); // You play hypnotic music, calming your target. - targ.SendLocalizedMessage( 500616 ); // You hear lovely music, and forget to continue battling! - targ.Combatant = null; - targ.Warmode = false; - } - } - } - } - } - } - } - } + targ.SendLocalizedMessage( + 500616); // You hear lovely music, and forget to continue battling! + targ.Combatant = null; + targ.Warmode = false; + } + } + } + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/Poisoning.cs b/Scripts/Skills/Poisoning.cs index 9a9f91e99..fec159054 100644 --- a/Scripts/Skills/Poisoning.cs +++ b/Scripts/Skills/Poisoning.cs @@ -1,173 +1,177 @@ using System; -using Server.Targeting; +using Server.Engines.ConPVP; using Server.Items; +using Server.Misc; +using Server.Targeting; namespace Server.SkillHandlers { - public class Poisoning - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Poisoning].Callback = OnUse; - } + public class Poisoning + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Poisoning].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.Target = new InternalTargetPoison(); + public static TimeSpan OnUse(Mobile m) + { + m.Target = new InternalTargetPoison(); - m.SendLocalizedMessage( 502137 ); // Select the poison you wish to use + m.SendLocalizedMessage(502137); // Select the poison you wish to use - return TimeSpan.FromSeconds( 10.0 ); // 10 second delay before beign able to re-use a skill - } + return TimeSpan.FromSeconds(10.0); // 10 second delay before beign able to re-use a skill + } - private class InternalTargetPoison : Target - { - public InternalTargetPoison() : base ( 2, false, TargetFlags.None ) - { - } + private class InternalTargetPoison : Target + { + public InternalTargetPoison() : base(2, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is BasePoisonPotion ) - { - from.SendLocalizedMessage( 502142 ); // To what do you wish to apply the poison? - from.Target = new InternalTarget( (BasePoisonPotion)targeted ); - } - else // Not a Poison Potion - { - from.SendLocalizedMessage( 502139 ); // That is not a poison potion. - } - } + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is BasePoisonPotion) + { + from.SendLocalizedMessage(502142); // To what do you wish to apply the poison? + from.Target = new InternalTarget((BasePoisonPotion)targeted); + } + else // Not a Poison Potion + { + from.SendLocalizedMessage(502139); // That is not a poison potion. + } + } - private class InternalTarget : Target - { - private BasePoisonPotion m_Potion; + private class InternalTarget : Target + { + private BasePoisonPotion m_Potion; - public InternalTarget( BasePoisonPotion potion ) : base ( 2, false, TargetFlags.None ) - { - m_Potion = potion; - } + public InternalTarget(BasePoisonPotion potion) : base(2, false, TargetFlags.None) + { + m_Potion = potion; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Potion.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Potion.Deleted) + return; - bool startTimer = false; + bool startTimer = false; - if ( targeted is Food || targeted is FukiyaDarts || targeted is Shuriken ) - { - startTimer = true; - } - else if ( targeted is BaseWeapon ) - { - BaseWeapon weapon = (BaseWeapon)targeted; + if (targeted is Food || targeted is FukiyaDarts || targeted is Shuriken) + { + startTimer = true; + } + else if (targeted is BaseWeapon) + { + BaseWeapon weapon = (BaseWeapon)targeted; - if ( Core.AOS ) - { - startTimer = ( weapon.PrimaryAbility == WeaponAbility.InfectiousStrike || weapon.SecondaryAbility == WeaponAbility.InfectiousStrike ); - } - else if ( weapon.Layer == Layer.OneHanded ) - { - // Only Bladed or Piercing weapon can be poisoned - startTimer = ( weapon.Type == WeaponType.Slashing || weapon.Type == WeaponType.Piercing ); - } - } + if (Core.AOS) + startTimer = weapon.PrimaryAbility == WeaponAbility.InfectiousStrike || + weapon.SecondaryAbility == WeaponAbility.InfectiousStrike; + else if (weapon.Layer == Layer.OneHanded) + startTimer = weapon.Type == WeaponType.Slashing || weapon.Type == WeaponType.Piercing; + } - if ( startTimer ) - { - new InternalTimer( from, (Item)targeted, m_Potion ).Start(); + if (startTimer) + { + new InternalTimer(from, (Item)targeted, m_Potion).Start(); - from.PlaySound( 0x4F ); + from.PlaySound(0x4F); - if ( !Engines.ConPVP.DuelContext.IsFreeConsume( from ) ) - { - m_Potion.Consume(); - from.AddToBackpack( new Bottle() ); - } - } - else // Target can't be poisoned - { - if ( Core.AOS ) - from.SendLocalizedMessage( 1060204 ); // You cannot poison that! You can only poison infectious weapons, food or drink. - else - from.SendLocalizedMessage( 502145 ); // You cannot poison that! You can only poison bladed or piercing weapons, food or drink. - } - } + if (!DuelContext.IsFreeConsume(from)) + { + m_Potion.Consume(); + from.AddToBackpack(new Bottle()); + } + } + else // Target can't be poisoned + { + if (Core.AOS) + from.SendLocalizedMessage( + 1060204); // You cannot poison that! You can only poison infectious weapons, food or drink. + else + from.SendLocalizedMessage( + 502145); // You cannot poison that! You can only poison bladed or piercing weapons, food or drink. + } + } - private class InternalTimer : Timer - { - private Mobile m_From; - private Item m_Target; - private Poison m_Poison; - private double m_MinSkill, m_MaxSkill; + private class InternalTimer : Timer + { + private Mobile m_From; + private double m_MinSkill, m_MaxSkill; + private Poison m_Poison; + private Item m_Target; - public InternalTimer( Mobile from, Item target, BasePoisonPotion potion ) : base( TimeSpan.FromSeconds( 2.0 ) ) - { - m_From = from; - m_Target = target; - m_Poison = potion.Poison; - m_MinSkill = potion.MinPoisoningSkill; - m_MaxSkill = potion.MaxPoisoningSkill; - Priority = TimerPriority.TwoFiftyMS; - } + public InternalTimer(Mobile from, Item target, BasePoisonPotion potion) : base(TimeSpan.FromSeconds(2.0)) + { + m_From = from; + m_Target = target; + m_Poison = potion.Poison; + m_MinSkill = potion.MinPoisoningSkill; + m_MaxSkill = potion.MaxPoisoningSkill; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - if ( m_From.CheckTargetSkill( SkillName.Poisoning, m_Target, m_MinSkill, m_MaxSkill ) ) - { - if ( m_Target is Food ) - { - ((Food)m_Target).Poison = m_Poison; - } - else if ( m_Target is BaseWeapon ) - { - ((BaseWeapon)m_Target).Poison = m_Poison; - ((BaseWeapon)m_Target).PoisonCharges = 18 - (m_Poison.Level * 2); - } - else if ( m_Target is FukiyaDarts ) - { - ((FukiyaDarts)m_Target).Poison = m_Poison; - ((FukiyaDarts)m_Target).PoisonCharges = Math.Min( 18 - (m_Poison.Level * 2), ((FukiyaDarts)m_Target).UsesRemaining ); - } - else if ( m_Target is Shuriken ) - { - ((Shuriken)m_Target).Poison = m_Poison; - ((Shuriken)m_Target).PoisonCharges = Math.Min( 18 - (m_Poison.Level * 2), ((Shuriken)m_Target).UsesRemaining ); - } + protected override void OnTick() + { + if (m_From.CheckTargetSkill(SkillName.Poisoning, m_Target, m_MinSkill, m_MaxSkill)) + { + if (m_Target is Food) + { + ((Food)m_Target).Poison = m_Poison; + } + else if (m_Target is BaseWeapon) + { + ((BaseWeapon)m_Target).Poison = m_Poison; + ((BaseWeapon)m_Target).PoisonCharges = 18 - m_Poison.Level * 2; + } + else if (m_Target is FukiyaDarts) + { + ((FukiyaDarts)m_Target).Poison = m_Poison; + ((FukiyaDarts)m_Target).PoisonCharges = Math.Min(18 - m_Poison.Level * 2, + ((FukiyaDarts)m_Target).UsesRemaining); + } + else if (m_Target is Shuriken) + { + ((Shuriken)m_Target).Poison = m_Poison; + ((Shuriken)m_Target).PoisonCharges = Math.Min(18 - m_Poison.Level * 2, + ((Shuriken)m_Target).UsesRemaining); + } - m_From.SendLocalizedMessage( 1010517 ); // You apply the poison + m_From.SendLocalizedMessage(1010517); // You apply the poison - Misc.Titles.AwardKarma( m_From, -20, true ); - } - else // Failed - { - // 5% of chance of getting poisoned if failed - if ( m_From.Skills[SkillName.Poisoning].Base < 80.0 && Utility.Random( 20 ) == 0 ) - { - m_From.SendLocalizedMessage( 502148 ); // You make a grave mistake while applying the poison. - m_From.ApplyPoison( m_From, m_Poison ); - } - else - { - if ( m_Target is BaseWeapon ) - { - BaseWeapon weapon = (BaseWeapon)m_Target; + Titles.AwardKarma(m_From, -20, true); + } + else // Failed + { + // 5% of chance of getting poisoned if failed + if (m_From.Skills[SkillName.Poisoning].Base < 80.0 && Utility.Random(20) == 0) + { + m_From.SendLocalizedMessage(502148); // You make a grave mistake while applying the poison. + m_From.ApplyPoison(m_From, m_Poison); + } + else + { + if (m_Target is BaseWeapon) + { + BaseWeapon weapon = (BaseWeapon)m_Target; - if ( weapon.Type == WeaponType.Slashing ) - m_From.SendLocalizedMessage( 1010516 ); // You fail to apply a sufficient dose of poison on the blade - else - m_From.SendLocalizedMessage( 1010518 ); // You fail to apply a sufficient dose of poison - } - else - { - m_From.SendLocalizedMessage( 1010518 ); // You fail to apply a sufficient dose of poison - } - } - } - } - } - } - } - } + if (weapon.Type == WeaponType.Slashing) + m_From.SendLocalizedMessage( + 1010516); // You fail to apply a sufficient dose of poison on the blade + else + m_From.SendLocalizedMessage( + 1010518); // You fail to apply a sufficient dose of poison + } + else + { + m_From.SendLocalizedMessage(1010518); // You fail to apply a sufficient dose of poison + } + } + } + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/Provocation.cs b/Scripts/Skills/Provocation.cs index c7afb8a92..68700b471 100644 --- a/Scripts/Skills/Provocation.cs +++ b/Scripts/Skills/Provocation.cs @@ -1,163 +1,171 @@ using System; -using Server.Targeting; -using Server.Mobiles; using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.SkillHandlers { - public class Provocation - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Provocation].Callback = OnUse; - } + public class Provocation + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Provocation].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.RevealingAction(); + public static TimeSpan OnUse(Mobile m) + { + m.RevealingAction(); - BaseInstrument.PickInstrument( m, OnPickedInstrument ); + BaseInstrument.PickInstrument(m, OnPickedInstrument); - return TimeSpan.FromSeconds( 1.0 ); // Cannot use another skill for 1 second - } + return TimeSpan.FromSeconds(1.0); // Cannot use another skill for 1 second + } - public static void OnPickedInstrument( Mobile from, BaseInstrument instrument ) - { - from.RevealingAction(); - from.SendLocalizedMessage( 501587 ); // Whom do you wish to incite? - from.Target = new InternalFirstTarget( from, instrument ); - } + public static void OnPickedInstrument(Mobile from, BaseInstrument instrument) + { + from.RevealingAction(); + from.SendLocalizedMessage(501587); // Whom do you wish to incite? + from.Target = new InternalFirstTarget(from, instrument); + } - private class InternalFirstTarget : Target - { - private BaseInstrument m_Instrument; + private class InternalFirstTarget : Target + { + private BaseInstrument m_Instrument; - public InternalFirstTarget( Mobile from, BaseInstrument instrument ) : base( BaseInstrument.GetBardRange( from, SkillName.Provocation ), false, TargetFlags.None ) - { - m_Instrument = instrument; - } + public InternalFirstTarget(Mobile from, BaseInstrument instrument) : base( + BaseInstrument.GetBardRange(from, SkillName.Provocation), false, TargetFlags.None) + { + m_Instrument = instrument; + } - protected override void OnTarget( Mobile from, object targeted ) - { - from.RevealingAction(); + protected override void OnTarget(Mobile from, object targeted) + { + from.RevealingAction(); - if ( targeted is BaseCreature && from.CanBeHarmful( (Mobile)targeted, true ) ) - { - BaseCreature creature = (BaseCreature)targeted; + if (targeted is BaseCreature && from.CanBeHarmful((Mobile)targeted, true)) + { + BaseCreature creature = (BaseCreature)targeted; - if ( !m_Instrument.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1062488 ); // The instrument you are trying to play is no longer in your backpack! - } - else if ( creature.Controlled ) - { - from.SendLocalizedMessage( 501590 ); // They are too loyal to their master to be provoked. - } - else if ( creature.IsParagon && BaseInstrument.GetBaseDifficulty( creature ) >= 160.0 ) - { - from.SendLocalizedMessage( 1049446 ); // You have no chance of provoking those creatures. - } - else - { - from.RevealingAction(); - m_Instrument.PlayInstrumentWell( from ); - from.SendLocalizedMessage( 1008085 ); // You play your music and your target becomes angered. Whom do you wish them to attack? - from.Target = new InternalSecondTarget( from, m_Instrument, creature ); - } - } - else - { - from.SendLocalizedMessage( 501589 ); // You can't incite that! - } - } - } + if (!m_Instrument.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage( + 1062488); // The instrument you are trying to play is no longer in your backpack! + } + else if (creature.Controlled) + { + from.SendLocalizedMessage(501590); // They are too loyal to their master to be provoked. + } + else if (creature.IsParagon && BaseInstrument.GetBaseDifficulty(creature) >= 160.0) + { + from.SendLocalizedMessage(1049446); // You have no chance of provoking those creatures. + } + else + { + from.RevealingAction(); + m_Instrument.PlayInstrumentWell(from); + from.SendLocalizedMessage( + 1008085); // You play your music and your target becomes angered. Whom do you wish them to attack? + from.Target = new InternalSecondTarget(from, m_Instrument, creature); + } + } + else + { + from.SendLocalizedMessage(501589); // You can't incite that! + } + } + } - private class InternalSecondTarget : Target - { - private BaseCreature m_Creature; - private BaseInstrument m_Instrument; + private class InternalSecondTarget : Target + { + private BaseCreature m_Creature; + private BaseInstrument m_Instrument; - public InternalSecondTarget( Mobile from, BaseInstrument instrument, BaseCreature creature ) : base( BaseInstrument.GetBardRange( from, SkillName.Provocation ), false, TargetFlags.None ) - { - m_Instrument = instrument; - m_Creature = creature; - } + public InternalSecondTarget(Mobile from, BaseInstrument instrument, BaseCreature creature) : base( + BaseInstrument.GetBardRange(from, SkillName.Provocation), false, TargetFlags.None) + { + m_Instrument = instrument; + m_Creature = creature; + } - protected override void OnTarget( Mobile from, object targeted ) - { - from.RevealingAction(); + protected override void OnTarget(Mobile from, object targeted) + { + from.RevealingAction(); - if ( targeted is BaseCreature ) - { - BaseCreature creature = (BaseCreature)targeted; + if (targeted is BaseCreature) + { + BaseCreature creature = (BaseCreature)targeted; - if ( !m_Instrument.IsChildOf( from.Backpack ) ) - { - from.SendLocalizedMessage( 1062488 ); // The instrument you are trying to play is no longer in your backpack! - } - else if ( m_Creature.Unprovokable ) - { - from.SendLocalizedMessage( 1049446 ); // You have no chance of provoking those creatures. - } - else if ( creature.Unprovokable && !( creature is DemonKnight ) ) - { - from.SendLocalizedMessage( 1049446 ); // You have no chance of provoking those creatures. - } - else if ( m_Creature.Map != creature.Map || !m_Creature.InRange( creature, BaseInstrument.GetBardRange( from, SkillName.Provocation ) ) ) - { - from.SendLocalizedMessage( 1049450 ); // The creatures you are trying to provoke are too far away from each other for your music to have an effect. - } - else if ( m_Creature != creature ) - { - from.NextSkillTime = Core.TickCount + 10000; + if (!m_Instrument.IsChildOf(from.Backpack)) + { + from.SendLocalizedMessage( + 1062488); // The instrument you are trying to play is no longer in your backpack! + } + else if (m_Creature.Unprovokable) + { + from.SendLocalizedMessage(1049446); // You have no chance of provoking those creatures. + } + else if (creature.Unprovokable && !(creature is DemonKnight)) + { + from.SendLocalizedMessage(1049446); // You have no chance of provoking those creatures. + } + else if (m_Creature.Map != creature.Map || !m_Creature.InRange(creature, + BaseInstrument.GetBardRange(from, SkillName.Provocation))) + { + from.SendLocalizedMessage( + 1049450); // The creatures you are trying to provoke are too far away from each other for your music to have an effect. + } + else if (m_Creature != creature) + { + from.NextSkillTime = Core.TickCount + 10000; - double diff = ((m_Instrument.GetDifficultyFor( m_Creature ) + m_Instrument.GetDifficultyFor( creature )) * 0.5) - 5.0; - double music = from.Skills[SkillName.Musicianship].Value; + double diff = (m_Instrument.GetDifficultyFor(m_Creature) + m_Instrument.GetDifficultyFor(creature)) * + 0.5 - 5.0; + double music = from.Skills[SkillName.Musicianship].Value; - if ( music > 100.0 ) - diff -= (music - 100.0) * 0.5; + if (music > 100.0) + diff -= (music - 100.0) * 0.5; - if ( from.CanBeHarmful( m_Creature, true ) && from.CanBeHarmful( creature, true ) ) - { - if ( !BaseInstrument.CheckMusicianship( from ) ) - { - from.NextSkillTime = Core.TickCount + 5000; - from.SendLocalizedMessage( 500612 ); // You play poorly, and there is no effect. - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else - { - //from.DoHarmful( m_Creature ); - //from.DoHarmful( creature ); + if (from.CanBeHarmful(m_Creature, true) && from.CanBeHarmful(creature, true)) + { + if (!BaseInstrument.CheckMusicianship(from)) + { + from.NextSkillTime = Core.TickCount + 5000; + from.SendLocalizedMessage(500612); // You play poorly, and there is no effect. + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else + { + //from.DoHarmful( m_Creature ); + //from.DoHarmful( creature ); - if ( !from.CheckTargetSkill( SkillName.Provocation, creature, diff-25.0, diff+25.0 ) ) - { - from.NextSkillTime = Core.TickCount + 5000; - from.SendLocalizedMessage( 501599 ); // Your music fails to incite enough anger. - m_Instrument.PlayInstrumentBadly( from ); - m_Instrument.ConsumeUse( from ); - } - else - { - from.SendLocalizedMessage( 501602 ); // Your music succeeds, as you start a fight. - m_Instrument.PlayInstrumentWell( from ); - m_Instrument.ConsumeUse( from ); - m_Creature.Provoke( from, creature, true ); - } - } - } - } - else - { - from.SendLocalizedMessage( 501593 ); // You can't tell someone to attack themselves! - } - } - else - { - from.SendLocalizedMessage( 501589 ); // You can't incite that! - } - } - } - } + if (!from.CheckTargetSkill(SkillName.Provocation, creature, diff - 25.0, diff + 25.0)) + { + from.NextSkillTime = Core.TickCount + 5000; + from.SendLocalizedMessage(501599); // Your music fails to incite enough anger. + m_Instrument.PlayInstrumentBadly(from); + m_Instrument.ConsumeUse(from); + } + else + { + from.SendLocalizedMessage(501602); // Your music succeeds, as you start a fight. + m_Instrument.PlayInstrumentWell(from); + m_Instrument.ConsumeUse(from); + m_Creature.Provoke(from, creature, true); + } + } + } + } + else + { + from.SendLocalizedMessage(501593); // You can't tell someone to attack themselves! + } + } + else + { + from.SendLocalizedMessage(501589); // You can't incite that! + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/RemoveTrap.cs b/Scripts/Skills/RemoveTrap.cs index 537d7a92f..d188ee105 100644 --- a/Scripts/Skills/RemoveTrap.cs +++ b/Scripts/Skills/RemoveTrap.cs @@ -1,127 +1,134 @@ using System; -using Server.Targeting; +using Server.Factions; using Server.Items; using Server.Network; -using Server.Factions; +using Server.Targeting; namespace Server.SkillHandlers { - public class RemoveTrap - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.RemoveTrap].Callback = OnUse; - } + public class RemoveTrap + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.RemoveTrap].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - if ( m.Skills[SkillName.Lockpicking].Value < 50 ) - { - m.SendLocalizedMessage( 502366 ); // You do not know enough about locks. Become better at picking locks. - } - else if ( m.Skills[SkillName.DetectHidden].Value < 50 ) - { - m.SendLocalizedMessage( 502367 ); // You are not perceptive enough. Become better at detect hidden. - } - else - { - m.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile m) + { + if (m.Skills[SkillName.Lockpicking].Value < 50) + { + m.SendLocalizedMessage(502366); // You do not know enough about locks. Become better at picking locks. + } + else if (m.Skills[SkillName.DetectHidden].Value < 50) + { + m.SendLocalizedMessage(502367); // You are not perceptive enough. Become better at detect hidden. + } + else + { + m.Target = new InternalTarget(); - m.SendLocalizedMessage( 502368 ); // Wich trap will you attempt to disarm? - } + m.SendLocalizedMessage(502368); // Wich trap will you attempt to disarm? + } - return TimeSpan.FromSeconds( 10.0 ); // 10 second delay before beign able to re-use a skill - } + return TimeSpan.FromSeconds(10.0); // 10 second delay before beign able to re-use a skill + } - private class InternalTarget : Target - { - public InternalTarget() : base ( 2, false, TargetFlags.None ) - { - } + private class InternalTarget : Target + { + public InternalTarget() : base(2, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile ) - { - from.SendLocalizedMessage( 502816 ); // You feel that such an action would be inappropriate - } - else if ( targeted is TrappableContainer ) - { - TrappableContainer targ = (TrappableContainer)targeted; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile) + { + from.SendLocalizedMessage(502816); // You feel that such an action would be inappropriate + } + else if (targeted is TrappableContainer) + { + TrappableContainer targ = (TrappableContainer)targeted; - from.Direction = from.GetDirectionTo( targ ); + from.Direction = from.GetDirectionTo(targ); - if ( targ.TrapType == TrapType.None ) - { - from.SendLocalizedMessage( 502373 ); // That doesn't appear to be trapped - return; - } + if (targ.TrapType == TrapType.None) + { + from.SendLocalizedMessage(502373); // That doesn't appear to be trapped + return; + } - from.PlaySound( 0x241 ); + from.PlaySound(0x241); - if ( from.CheckTargetSkill( SkillName.RemoveTrap, targ, targ.TrapPower, targ.TrapPower + 30 ) ) - { - targ.TrapPower = 0; - targ.TrapLevel = 0; - targ.TrapType = TrapType.None; - from.SendLocalizedMessage( 502377 ); // You successfully render the trap harmless - } - else - { - from.SendLocalizedMessage( 502372 ); // You fail to disarm the trap... but you don't set it off - } - } - else if ( targeted is BaseFactionTrap ) - { - BaseFactionTrap trap = (BaseFactionTrap) targeted; - Faction faction = Faction.Find( from ); + if (from.CheckTargetSkill(SkillName.RemoveTrap, targ, targ.TrapPower, targ.TrapPower + 30)) + { + targ.TrapPower = 0; + targ.TrapLevel = 0; + targ.TrapType = TrapType.None; + from.SendLocalizedMessage(502377); // You successfully render the trap harmless + } + else + { + from.SendLocalizedMessage(502372); // You fail to disarm the trap... but you don't set it off + } + } + else if (targeted is BaseFactionTrap) + { + BaseFactionTrap trap = (BaseFactionTrap)targeted; + Faction faction = Faction.Find(from); - FactionTrapRemovalKit kit = @from.Backpack?.FindItemByType( typeof( FactionTrapRemovalKit ) ) as FactionTrapRemovalKit; + FactionTrapRemovalKit kit = + from.Backpack?.FindItemByType(typeof(FactionTrapRemovalKit)) as FactionTrapRemovalKit; - bool isOwner = ( trap.Placer == from || ( trap.Faction != null && trap.Faction.IsCommander( from ) ) ); + bool isOwner = trap.Placer == from || trap.Faction != null && trap.Faction.IsCommander(from); - if ( faction == null ) - { - from.SendLocalizedMessage( 1010538 ); // You may not disarm faction traps unless you are in an opposing faction - } - else if ( faction == trap.Faction && trap.Faction != null && !isOwner ) - { - from.SendLocalizedMessage( 1010537 ); // You may not disarm traps set by your own faction! - } - else if ( !isOwner && kit == null ) - { - from.SendLocalizedMessage( 1042530 ); // You must have a trap removal kit at the base level of your pack to disarm a faction trap. - } - else - { - if ( (Core.ML && isOwner) || (from.CheckTargetSkill( SkillName.RemoveTrap, trap, 80.0, 100.0 ) && from.CheckTargetSkill( SkillName.Tinkering, trap, 80.0, 100.0 )) ) - { - from.PrivateOverheadMessage( MessageType.Regular, trap.MessageHue, trap.DisarmMessage, from.NetState ); + if (faction == null) + { + from.SendLocalizedMessage( + 1010538); // You may not disarm faction traps unless you are in an opposing faction + } + else if (faction == trap.Faction && trap.Faction != null && !isOwner) + { + from.SendLocalizedMessage(1010537); // You may not disarm traps set by your own faction! + } + else if (!isOwner && kit == null) + { + from.SendLocalizedMessage( + 1042530); // You must have a trap removal kit at the base level of your pack to disarm a faction trap. + } + else + { + if (Core.ML && isOwner || from.CheckTargetSkill(SkillName.RemoveTrap, trap, 80.0, 100.0) && + from.CheckTargetSkill(SkillName.Tinkering, trap, 80.0, 100.0)) + { + from.PrivateOverheadMessage(MessageType.Regular, trap.MessageHue, trap.DisarmMessage, + from.NetState); - if ( !isOwner ) - { - int silver = faction.AwardSilver( from, trap.SilverFromDisarm ); + if (!isOwner) + { + int silver = faction.AwardSilver(from, trap.SilverFromDisarm); - if ( silver > 0 ) - from.SendLocalizedMessage( 1008113, true, silver.ToString( "N0" ) ); // You have been granted faction silver for removing the enemy trap : - } + if (silver > 0) + from.SendLocalizedMessage(1008113, true, + silver.ToString( + "N0")); // You have been granted faction silver for removing the enemy trap : + } - trap.Delete(); - } - else - { - from.SendLocalizedMessage( 502372 ); // You fail to disarm the trap... but you don't set it off - } + trap.Delete(); + } + else + { + from.SendLocalizedMessage(502372); // You fail to disarm the trap... but you don't set it off + } - if ( !isOwner ) - kit?.ConsumeCharge( from ); - } - } - else - { - from.SendLocalizedMessage( 502373 ); // That does'nt appear to be trapped - } - } - } - } -} + if (!isOwner) + kit?.ConsumeCharge(from); + } + } + else + { + from.SendLocalizedMessage(502373); // That does'nt appear to be trapped + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Snooping.cs b/Scripts/Skills/Snooping.cs index f130d6992..174191e20 100644 --- a/Scripts/Skills/Snooping.cs +++ b/Scripts/Skills/Snooping.cs @@ -1,105 +1,103 @@ -using System; -using Server.Misc; using Server.Items; +using Server.Misc; using Server.Mobiles; using Server.Network; using Server.Regions; namespace Server.SkillHandlers { - public class Snooping - { - public static void Configure() - { - Container.SnoopHandler = Container_Snoop; - } + public class Snooping + { + public static void Configure() + { + Container.SnoopHandler = Container_Snoop; + } - public static bool CheckSnoopAllowed( Mobile from, Mobile to ) - { - Map map = from.Map; + public static bool CheckSnoopAllowed(Mobile from, Mobile to) + { + Map map = from.Map; - if ( to.Player ) - return from.CanBeHarmful( to, false, true ); // normal restrictions + if (to.Player) + return from.CanBeHarmful(to, false, true); // normal restrictions - if ( map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0 ) - return true; // felucca you can snoop anybody + if (map != null && (map.Rules & MapRules.HarmfulRestrictions) == 0) + return true; // felucca you can snoop anybody - GuardedRegion reg = (GuardedRegion) to.Region.GetRegion( typeof( GuardedRegion ) ); + GuardedRegion reg = (GuardedRegion)to.Region.GetRegion(typeof(GuardedRegion)); - if ( reg == null || reg.IsDisabled() ) - return true; // not in town? we can snoop any npc + if (reg == null || reg.IsDisabled()) + return true; // not in town? we can snoop any npc - BaseCreature cret = to as BaseCreature; + BaseCreature cret = to as BaseCreature; - if ( to.Body.IsHuman && (cret == null || (!cret.AlwaysAttackable && !cret.AlwaysMurderer)) ) - return false; // in town we cannot snoop blue human npcs + if (to.Body.IsHuman && (cret == null || !cret.AlwaysAttackable && !cret.AlwaysMurderer)) + return false; // in town we cannot snoop blue human npcs - return true; - } + return true; + } - public static void Container_Snoop( Container cont, Mobile from ) - { - if ( from.AccessLevel > AccessLevel.Player || from.InRange( cont.GetWorldLocation(), 1 ) ) - { - Mobile root = cont.RootParent as Mobile; + public static void Container_Snoop(Container cont, Mobile from) + { + if (from.AccessLevel > AccessLevel.Player || from.InRange(cont.GetWorldLocation(), 1)) + { + Mobile root = cont.RootParent as Mobile; - if ( root != null && !root.Alive ) - return; + if (root != null && !root.Alive) + return; - if ( root != null && root.AccessLevel > AccessLevel.Player && from.AccessLevel == AccessLevel.Player ) - { - from.SendLocalizedMessage( 500209 ); // You can not peek into the container. - return; - } + if (root != null && root.AccessLevel > AccessLevel.Player && from.AccessLevel == AccessLevel.Player) + { + from.SendLocalizedMessage(500209); // You can not peek into the container. + return; + } - if ( root != null && from.AccessLevel == AccessLevel.Player && !CheckSnoopAllowed( from, root ) ) - { - from.SendLocalizedMessage( 1001018 ); // You cannot perform negative acts on your target. - return; - } + if (root != null && from.AccessLevel == AccessLevel.Player && !CheckSnoopAllowed(from, root)) + { + from.SendLocalizedMessage(1001018); // You cannot perform negative acts on your target. + return; + } - if ( root != null && from.AccessLevel == AccessLevel.Player && from.Skills[SkillName.Snooping].Value < Utility.Random( 100 ) ) - { - Map map = from.Map; + if (root != null && from.AccessLevel == AccessLevel.Player && + from.Skills[SkillName.Snooping].Value < Utility.Random(100)) + { + Map map = from.Map; - if ( map != null ) - { - string message = $"You notice {from.Name} attempting to peek into {root.Name}'s belongings."; + if (map != null) + { + string message = $"You notice {from.Name} attempting to peek into {root.Name}'s belongings."; - IPooledEnumerable eable = map.GetClientsInRange( from.Location, 8 ); + IPooledEnumerable eable = map.GetClientsInRange(from.Location, 8); - foreach ( NetState ns in eable ) - { - if ( ns.Mobile != from ) - ns.Mobile.SendMessage( message ); - } + foreach (NetState ns in eable) + if (ns.Mobile != from) + ns.Mobile.SendMessage(message); - eable.Free(); - } - } + eable.Free(); + } + } - if ( from.AccessLevel == AccessLevel.Player ) - Titles.AwardKarma( from, -4, true ); + if (from.AccessLevel == AccessLevel.Player) + Titles.AwardKarma(from, -4, true); - if ( from.AccessLevel > AccessLevel.Player || from.CheckTargetSkill( SkillName.Snooping, cont, 0.0, 100.0 ) ) - { - if ( cont is TrappableContainer && ((TrappableContainer)cont).ExecuteTrap( from ) ) - return; + if (from.AccessLevel > AccessLevel.Player || from.CheckTargetSkill(SkillName.Snooping, cont, 0.0, 100.0)) + { + if (cont is TrappableContainer && ((TrappableContainer)cont).ExecuteTrap(from)) + return; - cont.DisplayTo( from ); - } - else - { - from.SendLocalizedMessage( 500210 ); // You failed to peek into the container. + cont.DisplayTo(from); + } + else + { + from.SendLocalizedMessage(500210); // You failed to peek into the container. - if ( from.Skills[SkillName.Hiding].Value / 2 < Utility.Random( 100 ) ) - from.RevealingAction(); - } - } - else - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } - } -} + if (from.Skills[SkillName.Hiding].Value / 2 < Utility.Random(100)) + from.RevealingAction(); + } + } + else + { + from.SendLocalizedMessage(500446); // That is too far away. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/SpiritSpeak.cs b/Scripts/Skills/SpiritSpeak.cs index 7962f5c9e..ffface8f7 100644 --- a/Scripts/Skills/SpiritSpeak.cs +++ b/Scripts/Skills/SpiritSpeak.cs @@ -1,200 +1,199 @@ using System; using Server.Items; -using Server.Spells; using Server.Network; +using Server.Spells; namespace Server.SkillHandlers { - class SpiritSpeak - { - public static void Initialize() - { - SkillInfo.Table[32].Callback = OnUse; - } + internal class SpiritSpeak + { + public static void Initialize() + { + SkillInfo.Table[32].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - if ( Core.AOS ) - { - Spell spell = new SpiritSpeakSpell( m ); + public static TimeSpan OnUse(Mobile m) + { + if (Core.AOS) + { + Spell spell = new SpiritSpeakSpell(m); - spell.Cast(); + spell.Cast(); - if ( spell.IsCasting ) - return TimeSpan.FromSeconds( 5.0 ); + if (spell.IsCasting) + return TimeSpan.FromSeconds(5.0); - return TimeSpan.Zero; - } + return TimeSpan.Zero; + } - m.RevealingAction(); + m.RevealingAction(); - if ( m.CheckSkill( SkillName.SpiritSpeak, 0, 100 ) ) - { - if ( !m.CanHearGhosts ) - { - Timer t = new SpiritSpeakTimer( m ); - double secs = m.Skills[SkillName.SpiritSpeak].Base / 50; - secs *= 90; - if ( secs < 15 ) - secs = 15; + if (m.CheckSkill(SkillName.SpiritSpeak, 0, 100)) + { + if (!m.CanHearGhosts) + { + Timer t = new SpiritSpeakTimer(m); + double secs = m.Skills[SkillName.SpiritSpeak].Base / 50; + secs *= 90; + if (secs < 15) + secs = 15; - t.Delay = TimeSpan.FromSeconds( secs );//15seconds to 3 minutes - t.Start(); - m.CanHearGhosts = true; - } + t.Delay = TimeSpan.FromSeconds(secs); //15seconds to 3 minutes + t.Start(); + m.CanHearGhosts = true; + } - m.PlaySound( 0x24A ); - m.SendLocalizedMessage( 502444 );//You contact the neitherworld. - } - else - { - m.SendLocalizedMessage( 502443 );//You fail to contact the neitherworld. - m.CanHearGhosts = false; - } + m.PlaySound(0x24A); + m.SendLocalizedMessage(502444); //You contact the neitherworld. + } + else + { + m.SendLocalizedMessage(502443); //You fail to contact the neitherworld. + m.CanHearGhosts = false; + } - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - private class SpiritSpeakTimer : Timer - { - private Mobile m_Owner; - public SpiritSpeakTimer( Mobile m ) : base( TimeSpan.FromMinutes( 2.0 ) ) - { - m_Owner = m; - Priority = TimerPriority.FiveSeconds; - } + private class SpiritSpeakTimer : Timer + { + private Mobile m_Owner; - protected override void OnTick() - { - m_Owner.CanHearGhosts = false; - m_Owner.SendLocalizedMessage( 502445 );//You feel your contact with the neitherworld fading. - } - } + public SpiritSpeakTimer(Mobile m) : base(TimeSpan.FromMinutes(2.0)) + { + m_Owner = m; + Priority = TimerPriority.FiveSeconds; + } - private class SpiritSpeakSpell : Spell - { - private static SpellInfo m_Info = new SpellInfo( "Spirit Speak", "", 269 ); + protected override void OnTick() + { + m_Owner.CanHearGhosts = false; + m_Owner.SendLocalizedMessage(502445); //You feel your contact with the neitherworld fading. + } + } - public override bool BlockedByHorrificBeast => false; + private class SpiritSpeakSpell : Spell + { + private static SpellInfo m_Info = new SpellInfo("Spirit Speak", "", 269); - public SpiritSpeakSpell( Mobile caster ) : base( caster, null, m_Info ) - { - } + public SpiritSpeakSpell(Mobile caster) : base(caster, null, m_Info) + { + } - public override bool ClearHandsOnCast => false; + public override bool BlockedByHorrificBeast => false; - public override double CastDelayFastScalar => 0; - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + public override bool ClearHandsOnCast => false; - public override int GetMana() - { - return 0; - } + public override double CastDelayFastScalar => 0; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public override void OnCasterHurt() - { - if ( IsCasting ) - Disturb( DisturbType.Hurt, false, true ); - } + public override bool CheckNextSpellTime => false; - public override bool ConsumeReagents() - { - return true; - } + public override int GetMana() + { + return 0; + } - public override bool CheckFizzle() - { - return true; - } + public override void OnCasterHurt() + { + if (IsCasting) + Disturb(DisturbType.Hurt, false, true); + } - public override bool CheckNextSpellTime => false; + public override bool ConsumeReagents() + { + return true; + } - public override void OnDisturb( DisturbType type, bool message ) - { - Caster.NextSkillTime = Core.TickCount; + public override bool CheckFizzle() + { + return true; + } - base.OnDisturb( type, message ); - } + public override void OnDisturb(DisturbType type, bool message) + { + Caster.NextSkillTime = Core.TickCount; - public override bool CheckDisturb( DisturbType type, bool checkFirst, bool resistable ) - { - if ( type == DisturbType.EquipRequest || type == DisturbType.UseRequest ) - return false; + base.OnDisturb(type, message); + } - return true; - } + public override bool CheckDisturb(DisturbType type, bool checkFirst, bool resistable) + { + if (type == DisturbType.EquipRequest || type == DisturbType.UseRequest) + return false; - public override void SayMantra() - { - // Anh Mi Sah Ko - Caster.PublicOverheadMessage( MessageType.Regular, 0x3B2, 1062074, "", false ); - Caster.PlaySound( 0x24A ); - } + return true; + } - public override void OnCast() - { - Corpse toChannel = null; + public override void SayMantra() + { + // Anh Mi Sah Ko + Caster.PublicOverheadMessage(MessageType.Regular, 0x3B2, 1062074, "", false); + Caster.PlaySound(0x24A); + } - foreach ( Item item in Caster.GetItemsInRange( 3 ) ) - { - if ( item is Corpse && !( (Corpse)item ).Channeled ) - { - toChannel = (Corpse)item; - break; - } - } + public override void OnCast() + { + Corpse toChannel = null; - int max, min, mana, number; + foreach (Item item in Caster.GetItemsInRange(3)) + if (item is Corpse && !((Corpse)item).Channeled) + { + toChannel = (Corpse)item; + break; + } - if ( toChannel != null ) - { - min = 1 + (int)(Caster.Skills[SkillName.SpiritSpeak].Value * 0.25); - max = min + 4; - mana = 0; - number = 1061287; // You channel energy from a nearby corpse to heal your wounds. - } - else - { - min = 1 + (int)(Caster.Skills[SkillName.SpiritSpeak].Value * 0.25); - max = min + 4; - mana = 10; - number = 1061286; // You channel your own spiritual energy to heal your wounds. - } + int max, min, mana, number; - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1061285 ); // You lack the mana required to use this skill. - } - else - { - Caster.CheckSkill( SkillName.SpiritSpeak, 0.0, 120.0 ); + if (toChannel != null) + { + min = 1 + (int)(Caster.Skills[SkillName.SpiritSpeak].Value * 0.25); + max = min + 4; + mana = 0; + number = 1061287; // You channel energy from a nearby corpse to heal your wounds. + } + else + { + min = 1 + (int)(Caster.Skills[SkillName.SpiritSpeak].Value * 0.25); + max = min + 4; + mana = 10; + number = 1061286; // You channel your own spiritual energy to heal your wounds. + } - if ( Utility.RandomDouble() > (Caster.Skills[SkillName.SpiritSpeak].Value / 100.0) ) - { - Caster.SendLocalizedMessage( 502443 ); // You fail your attempt at contacting the netherworld. - } - else - { - if ( toChannel != null ) - { - toChannel.Channeled = true; - toChannel.Hue = 0x835; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1061285); // You lack the mana required to use this skill. + } + else + { + Caster.CheckSkill(SkillName.SpiritSpeak, 0.0, 120.0); - Caster.Mana -= mana; - Caster.SendLocalizedMessage( number ); + if (Utility.RandomDouble() > Caster.Skills[SkillName.SpiritSpeak].Value / 100.0) + { + Caster.SendLocalizedMessage(502443); // You fail your attempt at contacting the netherworld. + } + else + { + if (toChannel != null) + { + toChannel.Channeled = true; + toChannel.Hue = 0x835; + } - if ( min > max ) - min = max; + Caster.Mana -= mana; + Caster.SendLocalizedMessage(number); - Caster.Hits += Utility.RandomMinMax( min, max ); + if (min > max) + min = max; - Caster.FixedParticles( 0x375A, 1, 15, 9501, 2100, 4, EffectLayer.Waist ); - } - } + Caster.Hits += Utility.RandomMinMax(min, max); - FinishSequence(); - } - } - } -} + Caster.FixedParticles(0x375A, 1, 15, 9501, 2100, 4, EffectLayer.Waist); + } + } + + FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Stealing.cs b/Scripts/Skills/Stealing.cs index d99875563..8977ddbc5 100644 --- a/Scripts/Skills/Stealing.cs +++ b/Scripts/Skills/Stealing.cs @@ -1,486 +1,492 @@ using System; using System.Collections.Generic; -using Server.Mobiles; -using Server.Targeting; -using Server.Items; -using Server.Network; +using Server.Engines.ConPVP; using Server.Factions; -using Server.Spells.Seventh; -using Server.Spells.Fifth; +using Server.Items; +using Server.Mobiles; +using Server.Network; using Server.Spells; +using Server.Spells.Fifth; using Server.Spells.Ninjitsu; +using Server.Spells.Seventh; +using Server.Targeting; namespace Server.SkillHandlers { - public class Stealing - { - public static void Initialize() - { - SkillInfo.Table[33].Callback = OnUse; - } - - public static readonly bool ClassicMode = false; - public static readonly bool SuspendOnMurder = false; - - public static bool IsInGuild( Mobile m ) - { - return ( m is PlayerMobile && ((PlayerMobile)m).NpcGuild == NpcGuild.ThievesGuild ); - } - - public static bool IsInnocentTo( Mobile from, Mobile to ) - { - return ( Notoriety.Compute( from, (Mobile)to ) == Notoriety.Innocent ); - } - - private class StealingTarget : Target - { - private Mobile m_Thief; - - public StealingTarget( Mobile thief ) : base ( 1, false, TargetFlags.None ) - { - m_Thief = thief; - - AllowNonlocal = true; - } - - private Item TryStealItem( Item toSteal, ref bool caught ) - { - Item stolen = null; - - object root = toSteal.RootParent; - - StealableArtifactsSpawner.StealableInstance si = null; - if ( toSteal.Parent == null || !toSteal.Movable ) - si = StealableArtifactsSpawner.GetStealableInstance( toSteal ); - - if ( !IsEmptyHanded( m_Thief ) ) - { - m_Thief.SendLocalizedMessage( 1005584 ); // Both hands must be free to steal. - } - else if ( m_Thief.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - m_Thief.SendMessage( "You may not steal in this area." ); - } - else if ( root is Mobile && ((Mobile)root).Player && !IsInGuild( m_Thief ) ) - { - m_Thief.SendLocalizedMessage( 1005596 ); // You must be in the thieves guild to steal from other players. - } - else if ( SuspendOnMurder && root is Mobile && ((Mobile)root).Player && IsInGuild( m_Thief ) && m_Thief.Kills > 0 ) - { - m_Thief.SendLocalizedMessage( 502706 ); // You are currently suspended from the thieves guild. - } - else if ( root is BaseVendor && ((BaseVendor)root).IsInvulnerable ) - { - m_Thief.SendLocalizedMessage( 1005598 ); // You can't steal from shopkeepers. - } - else if ( root is PlayerVendor ) - { - m_Thief.SendLocalizedMessage( 502709 ); // You can't steal from vendors. - } - else if ( !m_Thief.CanSee( toSteal ) ) - { - m_Thief.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( m_Thief.Backpack == null || !m_Thief.Backpack.CheckHold( m_Thief, toSteal, false, true ) ) - { - m_Thief.SendLocalizedMessage( 1048147 ); // Your backpack can't hold anything else. - } - #region Sigils - else if ( toSteal is Sigil ) - { - PlayerState pl = PlayerState.Find( m_Thief ); - Faction faction = pl?.Faction; - - Sigil sig = (Sigil) toSteal; - - if ( !m_Thief.InRange( toSteal.GetWorldLocation(), 1 ) ) - { - m_Thief.SendLocalizedMessage( 502703 ); // You must be standing next to an item to steal it. - } - else if ( root != null ) // not on the ground - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - else if ( faction != null ) - { - if ( !m_Thief.CanBeginAction( typeof( IncognitoSpell ) ) ) - { - m_Thief.SendLocalizedMessage( 1010581 ); // You cannot steal the sigil when you are incognito - } - else if ( DisguiseTimers.IsDisguised( m_Thief ) ) - { - m_Thief.SendLocalizedMessage( 1010583 ); // You cannot steal the sigil while disguised - } - else if ( !m_Thief.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - m_Thief.SendLocalizedMessage( 1010582 ); // You cannot steal the sigil while polymorphed - } - else if ( TransformationSpellHelper.UnderTransformation( m_Thief ) ) - { - m_Thief.SendLocalizedMessage( 1061622 ); // You cannot steal the sigil while in that form. - } - else if ( AnimalForm.UnderTransformation( m_Thief ) ) - { - m_Thief.SendLocalizedMessage( 1063222 ); // You cannot steal the sigil while mimicking an animal. - } - else if ( pl.IsLeaving ) - { - m_Thief.SendLocalizedMessage( 1005589 ); // You are currently quitting a faction and cannot steal the town sigil - } - else if ( sig.IsBeingCorrupted && sig.LastMonolith.Faction == faction ) - { - m_Thief.SendLocalizedMessage( 1005590 ); // You cannot steal your own sigil - } - else if ( sig.IsPurifying ) - { - m_Thief.SendLocalizedMessage( 1005592 ); // You cannot steal this sigil until it has been purified - } - else if ( m_Thief.CheckTargetSkill( SkillName.Stealing, toSteal, 80.0, 80.0 ) ) - { - if ( Sigil.ExistsOn( m_Thief ) ) - { - m_Thief.SendLocalizedMessage( 1010258 ); // The sigil has gone back to its home location because you already have a sigil. - } - else if ( m_Thief.Backpack == null || !m_Thief.Backpack.CheckHold( m_Thief, sig, false, true ) ) - { - m_Thief.SendLocalizedMessage( 1010259 ); // The sigil has gone home because your backpack is full - } - else - { - if ( sig.IsBeingCorrupted ) - sig.GraceStart = DateTime.UtcNow; // begin grace period - - m_Thief.SendLocalizedMessage( 1010586 ); // YOU STOLE THE SIGIL!!! (woah, calm down now) - - if ( sig.LastMonolith?.Sigil != null ) { - sig.LastMonolith.Sigil = null; - sig.LastStolen = DateTime.UtcNow; - } - - return sig; - } - } - else - { - m_Thief.SendLocalizedMessage( 1005594 ); // You do not have enough skill to steal the sigil - } - } - else - { - m_Thief.SendLocalizedMessage( 1005588 ); // You must join a faction to do that - } - } - #endregion - else if ( si == null && ( toSteal.Parent == null || !toSteal.Movable ) ) - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - else if ( toSteal.LootType == LootType.Newbied || toSteal.CheckBlessed( root ) ) - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - else if ( Core.AOS && si == null && toSteal is Container ) - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - else if ( !m_Thief.InRange( toSteal.GetWorldLocation(), 1 ) ) - { - m_Thief.SendLocalizedMessage( 502703 ); // You must be standing next to an item to steal it. - } - else if ( si != null && m_Thief.Skills[SkillName.Stealing].Value < 100.0 ) - { - m_Thief.SendLocalizedMessage( 1060025, "", 0x66D ); // You're not skilled enough to attempt the theft of this item. - } - else if ( toSteal.Parent is Mobile ) - { - m_Thief.SendLocalizedMessage( 1005585 ); // You cannot steal items which are equipped. - } - else if ( root == m_Thief ) - { - m_Thief.SendLocalizedMessage( 502704 ); // You catch yourself red-handed. - } - else if ( root is Mobile && ((Mobile)root).AccessLevel > AccessLevel.Player ) - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - else if ( root is Mobile && !m_Thief.CanBeHarmful( (Mobile)root ) ) - { - } - else if ( root is Corpse ) - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - else - { - double w = toSteal.Weight + toSteal.TotalWeight; - - if ( w > 10 ) - { - m_Thief.SendMessage( "That is too heavy to steal." ); - } - else - { - if ( toSteal.Stackable && toSteal.Amount > 1 ) - { - int maxAmount = (int)((m_Thief.Skills[SkillName.Stealing].Value / 10.0) / toSteal.Weight); - - if ( maxAmount < 1 ) - maxAmount = 1; - else if ( maxAmount > toSteal.Amount ) - maxAmount = toSteal.Amount; - - int amount = Utility.RandomMinMax( 1, maxAmount ); - - if ( amount >= toSteal.Amount ) - { - int pileWeight = (int)Math.Ceiling( toSteal.Weight * toSteal.Amount ); - pileWeight *= 10; - - if ( m_Thief.CheckTargetSkill( SkillName.Stealing, toSteal, pileWeight - 22.5, pileWeight + 27.5 ) ) - stolen = toSteal; - } - else - { - int pileWeight = (int)Math.Ceiling( toSteal.Weight * amount ); - pileWeight *= 10; - - if ( m_Thief.CheckTargetSkill( SkillName.Stealing, toSteal, pileWeight - 22.5, pileWeight + 27.5 ) ) - { - stolen = Mobile.LiftItemDupe( toSteal, toSteal.Amount - amount ); - - if ( stolen == null ) - stolen = toSteal; - } - } - } - else - { - int iw = (int)Math.Ceiling( w ); - iw *= 10; - - if ( m_Thief.CheckTargetSkill( SkillName.Stealing, toSteal, iw - 22.5, iw + 27.5 ) ) - stolen = toSteal; - } - - if ( stolen != null ) - { - m_Thief.SendLocalizedMessage( 502724 ); // You successfully steal the item. - - if ( si != null ) - { - toSteal.Movable = true; - si.Item = null; - } - } - else - { - m_Thief.SendLocalizedMessage( 502723 ); // You fail to steal the item. - } - - caught = ( m_Thief.Skills[SkillName.Stealing].Value < Utility.Random( 150 ) ); - } - } - - return stolen; - } - - protected override void OnTarget( Mobile from, object target ) - { - from.RevealingAction(); - - Item stolen = null; - object root = null; - bool caught = false; - - if ( target is Item ) - { - root = ((Item)target).RootParent; - stolen = TryStealItem( (Item)target, ref caught ); - } - else if ( target is Mobile ) - { - Container pack = ((Mobile)target).Backpack; - - if ( pack != null && pack.Items.Count > 0 ) - { - int randomIndex = Utility.Random( pack.Items.Count ); - - root = target; - stolen = TryStealItem( pack.Items[randomIndex], ref caught ); - } - } - else - { - m_Thief.SendLocalizedMessage( 502710 ); // You can't steal that! - } - - if ( stolen != null ) - { - from.AddToBackpack( stolen ); - - if ( !( stolen is Container || stolen.Stackable ) ) { // do not return stolen containers or stackable items - StolenItem.Add( stolen, m_Thief, root as Mobile ); - } - } - - if ( caught ) - { - if ( root == null ) - { - m_Thief.CriminalAction( false ); - } - else if ( root is Corpse && ((Corpse)root).IsCriminalAction( m_Thief ) ) - { - m_Thief.CriminalAction( false ); - } - else if ( root is Mobile ) - { - Mobile mobRoot = (Mobile)root; - - if ( !IsInGuild( mobRoot ) && IsInnocentTo( m_Thief, mobRoot ) ) - m_Thief.CriminalAction( false ); - - string message = $"You notice {m_Thief.Name} trying to steal from {mobRoot.Name}."; - - foreach ( NetState ns in m_Thief.GetClientsInRange( 8 ) ) - { - if ( ns.Mobile != m_Thief ) - ns.Mobile.SendMessage( message ); - } - } - } - else if ( root is Corpse && ((Corpse)root).IsCriminalAction( m_Thief ) ) - { - m_Thief.CriminalAction( false ); - } - - if ( root is Mobile && ((Mobile)root).Player && m_Thief is PlayerMobile && IsInnocentTo( m_Thief, (Mobile)root ) && !IsInGuild( (Mobile)root ) ) - { - PlayerMobile pm = (PlayerMobile)m_Thief; - - pm.PermaFlags.Add( (Mobile)root ); - pm.Delta( MobileDelta.Noto ); - } - } - } - - public static bool IsEmptyHanded( Mobile from ) - { - if ( from.FindItemOnLayer( Layer.OneHanded ) != null ) - return false; - - if ( from.FindItemOnLayer( Layer.TwoHanded ) != null ) - return false; - - return true; - } - - public static TimeSpan OnUse( Mobile m ) - { - if ( !IsEmptyHanded( m ) ) - { - m.SendLocalizedMessage( 1005584 ); // Both hands must be free to steal. - } - else if ( m.Region.IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - m.SendMessage( "You may not steal in this area." ); - } - else - { - m.Target = new StealingTarget( m ); - m.RevealingAction(); - - m.SendLocalizedMessage( 502698 ); // Which item do you want to steal? - } - - return TimeSpan.FromSeconds( 10.0 ); - } - } - - public class StolenItem - { - public static readonly TimeSpan StealTime = TimeSpan.FromMinutes( 2.0 ); - - public Item Stolen { get; } - - public Mobile Thief { get; } - - public Mobile Victim { get; } - - public DateTime Expires { get; private set; } - - public bool IsExpired => ( DateTime.UtcNow >= Expires ); - - public StolenItem( Item stolen, Mobile thief, Mobile victim ) - { - Stolen = stolen; - Thief = thief; - Victim = victim; - - Expires = DateTime.UtcNow + StealTime; - } - - private static Queue m_Queue = new Queue(); - - public static void Add( Item item, Mobile thief, Mobile victim ) - { - Clean(); - - m_Queue.Enqueue( new StolenItem( item, thief, victim ) ); - } - - public static bool IsStolen( Item item ) - { - Mobile victim = null; - - return IsStolen( item, ref victim ); - } - - public static bool IsStolen( Item item, ref Mobile victim ) - { - Clean(); - - foreach ( StolenItem si in m_Queue ) - { - if ( si.Stolen == item && !si.IsExpired ) - { - victim = si.Victim; - return true; - } - } - - return false; - } - - public static void ReturnOnDeath( Mobile killed, Container corpse ) - { - Clean(); - - foreach ( StolenItem si in m_Queue ) - { - if ( si.Stolen.RootParent == corpse && si.Victim != null && !si.IsExpired ) - { - if ( si.Victim.AddToBackpack( si.Stolen ) ) - si.Victim.SendLocalizedMessage( 1010464 ); // the item that was stolen is returned to you. - else - si.Victim.SendLocalizedMessage( 1010463 ); // the item that was stolen from you falls to the ground. - - si.Expires = DateTime.UtcNow; // such a hack - } - } - } - - public static void Clean() - { - while ( m_Queue.Count > 0 ) - { - StolenItem si = m_Queue.Peek(); - - if ( si.IsExpired ) - m_Queue.Dequeue(); - else - break; - } - } - } -} + public class Stealing + { + public static readonly bool ClassicMode = false; + public static readonly bool SuspendOnMurder = false; + + public static void Initialize() + { + SkillInfo.Table[33].Callback = OnUse; + } + + public static bool IsInGuild(Mobile m) + { + return m is PlayerMobile && ((PlayerMobile)m).NpcGuild == NpcGuild.ThievesGuild; + } + + public static bool IsInnocentTo(Mobile from, Mobile to) + { + return Notoriety.Compute(from, to) == Notoriety.Innocent; + } + + public static bool IsEmptyHanded(Mobile from) + { + if (from.FindItemOnLayer(Layer.OneHanded) != null) + return false; + + if (from.FindItemOnLayer(Layer.TwoHanded) != null) + return false; + + return true; + } + + public static TimeSpan OnUse(Mobile m) + { + if (!IsEmptyHanded(m)) + { + m.SendLocalizedMessage(1005584); // Both hands must be free to steal. + } + else if (m.Region.IsPartOf(typeof(SafeZone))) + { + m.SendMessage("You may not steal in this area."); + } + else + { + m.Target = new StealingTarget(m); + m.RevealingAction(); + + m.SendLocalizedMessage(502698); // Which item do you want to steal? + } + + return TimeSpan.FromSeconds(10.0); + } + + private class StealingTarget : Target + { + private Mobile m_Thief; + + public StealingTarget(Mobile thief) : base(1, false, TargetFlags.None) + { + m_Thief = thief; + + AllowNonlocal = true; + } + + private Item TryStealItem(Item toSteal, ref bool caught) + { + Item stolen = null; + + object root = toSteal.RootParent; + + StealableArtifactsSpawner.StealableInstance si = null; + if (toSteal.Parent == null || !toSteal.Movable) + si = StealableArtifactsSpawner.GetStealableInstance(toSteal); + + if (!IsEmptyHanded(m_Thief)) + { + m_Thief.SendLocalizedMessage(1005584); // Both hands must be free to steal. + } + else if (m_Thief.Region.IsPartOf(typeof(SafeZone))) + { + m_Thief.SendMessage("You may not steal in this area."); + } + else if (root is Mobile && ((Mobile)root).Player && !IsInGuild(m_Thief)) + { + m_Thief.SendLocalizedMessage(1005596); // You must be in the thieves guild to steal from other players. + } + else if (SuspendOnMurder && root is Mobile && ((Mobile)root).Player && IsInGuild(m_Thief) && + m_Thief.Kills > 0) + { + m_Thief.SendLocalizedMessage(502706); // You are currently suspended from the thieves guild. + } + else if (root is BaseVendor && ((BaseVendor)root).IsInvulnerable) + { + m_Thief.SendLocalizedMessage(1005598); // You can't steal from shopkeepers. + } + else if (root is PlayerVendor) + { + m_Thief.SendLocalizedMessage(502709); // You can't steal from vendors. + } + else if (!m_Thief.CanSee(toSteal)) + { + m_Thief.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (m_Thief.Backpack == null || !m_Thief.Backpack.CheckHold(m_Thief, toSteal, false, true)) + { + m_Thief.SendLocalizedMessage(1048147); // Your backpack can't hold anything else. + } + + #region Sigils + + else if (toSteal is Sigil) + { + PlayerState pl = PlayerState.Find(m_Thief); + Faction faction = pl?.Faction; + + Sigil sig = (Sigil)toSteal; + + if (!m_Thief.InRange(toSteal.GetWorldLocation(), 1)) + { + m_Thief.SendLocalizedMessage(502703); // You must be standing next to an item to steal it. + } + else if (root != null) // not on the ground + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + else if (faction != null) + { + if (!m_Thief.CanBeginAction(typeof(IncognitoSpell))) + { + m_Thief.SendLocalizedMessage(1010581); // You cannot steal the sigil when you are incognito + } + else if (DisguiseTimers.IsDisguised(m_Thief)) + { + m_Thief.SendLocalizedMessage(1010583); // You cannot steal the sigil while disguised + } + else if (!m_Thief.CanBeginAction(typeof(PolymorphSpell))) + { + m_Thief.SendLocalizedMessage(1010582); // You cannot steal the sigil while polymorphed + } + else if (TransformationSpellHelper.UnderTransformation(m_Thief)) + { + m_Thief.SendLocalizedMessage(1061622); // You cannot steal the sigil while in that form. + } + else if (AnimalForm.UnderTransformation(m_Thief)) + { + m_Thief.SendLocalizedMessage(1063222); // You cannot steal the sigil while mimicking an animal. + } + else if (pl.IsLeaving) + { + m_Thief.SendLocalizedMessage( + 1005589); // You are currently quitting a faction and cannot steal the town sigil + } + else if (sig.IsBeingCorrupted && sig.LastMonolith.Faction == faction) + { + m_Thief.SendLocalizedMessage(1005590); // You cannot steal your own sigil + } + else if (sig.IsPurifying) + { + m_Thief.SendLocalizedMessage(1005592); // You cannot steal this sigil until it has been purified + } + else if (m_Thief.CheckTargetSkill(SkillName.Stealing, toSteal, 80.0, 80.0)) + { + if (Sigil.ExistsOn(m_Thief)) + { + m_Thief.SendLocalizedMessage( + 1010258); // The sigil has gone back to its home location because you already have a sigil. + } + else if (m_Thief.Backpack == null || !m_Thief.Backpack.CheckHold(m_Thief, sig, false, true)) + { + m_Thief.SendLocalizedMessage( + 1010259); // The sigil has gone home because your backpack is full + } + else + { + if (sig.IsBeingCorrupted) + sig.GraceStart = DateTime.UtcNow; // begin grace period + + m_Thief.SendLocalizedMessage(1010586); // YOU STOLE THE SIGIL!!! (woah, calm down now) + + if (sig.LastMonolith?.Sigil != null) + { + sig.LastMonolith.Sigil = null; + sig.LastStolen = DateTime.UtcNow; + } + + return sig; + } + } + else + { + m_Thief.SendLocalizedMessage(1005594); // You do not have enough skill to steal the sigil + } + } + else + { + m_Thief.SendLocalizedMessage(1005588); // You must join a faction to do that + } + } + + #endregion + + else if (si == null && (toSteal.Parent == null || !toSteal.Movable)) + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + else if (toSteal.LootType == LootType.Newbied || toSteal.CheckBlessed(root)) + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + else if (Core.AOS && si == null && toSteal is Container) + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + else if (!m_Thief.InRange(toSteal.GetWorldLocation(), 1)) + { + m_Thief.SendLocalizedMessage(502703); // You must be standing next to an item to steal it. + } + else if (si != null && m_Thief.Skills[SkillName.Stealing].Value < 100.0) + { + m_Thief.SendLocalizedMessage(1060025, "", + 0x66D); // You're not skilled enough to attempt the theft of this item. + } + else if (toSteal.Parent is Mobile) + { + m_Thief.SendLocalizedMessage(1005585); // You cannot steal items which are equipped. + } + else if (root == m_Thief) + { + m_Thief.SendLocalizedMessage(502704); // You catch yourself red-handed. + } + else if (root is Mobile && ((Mobile)root).AccessLevel > AccessLevel.Player) + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + else if (root is Mobile && !m_Thief.CanBeHarmful((Mobile)root)) + { + } + else if (root is Corpse) + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + else + { + double w = toSteal.Weight + toSteal.TotalWeight; + + if (w > 10) + { + m_Thief.SendMessage("That is too heavy to steal."); + } + else + { + if (toSteal.Stackable && toSteal.Amount > 1) + { + int maxAmount = (int)(m_Thief.Skills[SkillName.Stealing].Value / 10.0 / toSteal.Weight); + + if (maxAmount < 1) + maxAmount = 1; + else if (maxAmount > toSteal.Amount) + maxAmount = toSteal.Amount; + + int amount = Utility.RandomMinMax(1, maxAmount); + + if (amount >= toSteal.Amount) + { + int pileWeight = (int)Math.Ceiling(toSteal.Weight * toSteal.Amount); + pileWeight *= 10; + + if (m_Thief.CheckTargetSkill(SkillName.Stealing, toSteal, pileWeight - 22.5, + pileWeight + 27.5)) + stolen = toSteal; + } + else + { + int pileWeight = (int)Math.Ceiling(toSteal.Weight * amount); + pileWeight *= 10; + + if (m_Thief.CheckTargetSkill(SkillName.Stealing, toSteal, pileWeight - 22.5, + pileWeight + 27.5)) + { + stolen = Mobile.LiftItemDupe(toSteal, toSteal.Amount - amount); + + if (stolen == null) + stolen = toSteal; + } + } + } + else + { + int iw = (int)Math.Ceiling(w); + iw *= 10; + + if (m_Thief.CheckTargetSkill(SkillName.Stealing, toSteal, iw - 22.5, iw + 27.5)) + stolen = toSteal; + } + + if (stolen != null) + { + m_Thief.SendLocalizedMessage(502724); // You successfully steal the item. + + if (si != null) + { + toSteal.Movable = true; + si.Item = null; + } + } + else + { + m_Thief.SendLocalizedMessage(502723); // You fail to steal the item. + } + + caught = m_Thief.Skills[SkillName.Stealing].Value < Utility.Random(150); + } + } + + return stolen; + } + + protected override void OnTarget(Mobile from, object target) + { + from.RevealingAction(); + + Item stolen = null; + object root = null; + bool caught = false; + + if (target is Item) + { + root = ((Item)target).RootParent; + stolen = TryStealItem((Item)target, ref caught); + } + else if (target is Mobile) + { + Container pack = ((Mobile)target).Backpack; + + if (pack != null && pack.Items.Count > 0) + { + int randomIndex = Utility.Random(pack.Items.Count); + + root = target; + stolen = TryStealItem(pack.Items[randomIndex], ref caught); + } + } + else + { + m_Thief.SendLocalizedMessage(502710); // You can't steal that! + } + + if (stolen != null) + { + from.AddToBackpack(stolen); + + if (!(stolen is Container || stolen.Stackable)) StolenItem.Add(stolen, m_Thief, root as Mobile); + } + + if (caught) + { + if (root == null) + { + m_Thief.CriminalAction(false); + } + else if (root is Corpse && ((Corpse)root).IsCriminalAction(m_Thief)) + { + m_Thief.CriminalAction(false); + } + else if (root is Mobile) + { + Mobile mobRoot = (Mobile)root; + + if (!IsInGuild(mobRoot) && IsInnocentTo(m_Thief, mobRoot)) + m_Thief.CriminalAction(false); + + string message = $"You notice {m_Thief.Name} trying to steal from {mobRoot.Name}."; + + foreach (NetState ns in m_Thief.GetClientsInRange(8)) + if (ns.Mobile != m_Thief) + ns.Mobile.SendMessage(message); + } + } + else if (root is Corpse && ((Corpse)root).IsCriminalAction(m_Thief)) + { + m_Thief.CriminalAction(false); + } + + if (root is Mobile && ((Mobile)root).Player && m_Thief is PlayerMobile && + IsInnocentTo(m_Thief, (Mobile)root) && !IsInGuild((Mobile)root)) + { + PlayerMobile pm = (PlayerMobile)m_Thief; + + pm.PermaFlags.Add((Mobile)root); + pm.Delta(MobileDelta.Noto); + } + } + } + } + + public class StolenItem + { + public static readonly TimeSpan StealTime = TimeSpan.FromMinutes(2.0); + + private static Queue m_Queue = new Queue(); + + public StolenItem(Item stolen, Mobile thief, Mobile victim) + { + Stolen = stolen; + Thief = thief; + Victim = victim; + + Expires = DateTime.UtcNow + StealTime; + } + + public Item Stolen{ get; } + + public Mobile Thief{ get; } + + public Mobile Victim{ get; } + + public DateTime Expires{ get; private set; } + + public bool IsExpired => DateTime.UtcNow >= Expires; + + public static void Add(Item item, Mobile thief, Mobile victim) + { + Clean(); + + m_Queue.Enqueue(new StolenItem(item, thief, victim)); + } + + public static bool IsStolen(Item item) + { + Mobile victim = null; + + return IsStolen(item, ref victim); + } + + public static bool IsStolen(Item item, ref Mobile victim) + { + Clean(); + + foreach (StolenItem si in m_Queue) + if (si.Stolen == item && !si.IsExpired) + { + victim = si.Victim; + return true; + } + + return false; + } + + public static void ReturnOnDeath(Mobile killed, Container corpse) + { + Clean(); + + foreach (StolenItem si in m_Queue) + if (si.Stolen.RootParent == corpse && si.Victim != null && !si.IsExpired) + { + if (si.Victim.AddToBackpack(si.Stolen)) + si.Victim.SendLocalizedMessage(1010464); // the item that was stolen is returned to you. + else + si.Victim.SendLocalizedMessage(1010463); // the item that was stolen from you falls to the ground. + + si.Expires = DateTime.UtcNow; // such a hack + } + } + + public static void Clean() + { + while (m_Queue.Count > 0) + { + StolenItem si = m_Queue.Peek(); + + if (si.IsExpired) + m_Queue.Dequeue(); + else + break; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/Stealth.cs b/Scripts/Skills/Stealth.cs index 6c75de487..16f1494c9 100644 --- a/Scripts/Skills/Stealth.cs +++ b/Scripts/Skills/Stealth.cs @@ -4,109 +4,110 @@ using Server.Mobiles; namespace Server.SkillHandlers { - public class Stealth - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Stealth].Callback = OnUse; - } + public class Stealth + { + public static double HidingRequirement => Core.ML ? 30.0 : Core.SE ? 50.0 : 80.0; - public static double HidingRequirement => ( Core.ML ? 30.0 : ( Core.SE ? 50.0 : 80.0 ) ); + public static int[,] ArmorTable{ get; } = + { + // Gorget Gloves Helmet Arms Legs Chest Shield + /* Cloth */ { 0, 0, 0, 0, 0, 0, 0 }, + /* Leather */ { 0, 0, 0, 0, 0, 0, 0 }, + /* Studded */ { 2, 2, 0, 4, 6, 10, 0 }, + /* Bone */ { 0, 5, 10, 10, 15, 25, 0 }, + /* Spined */ { 0, 0, 0, 0, 0, 0, 0 }, + /* Horned */ { 0, 0, 0, 0, 0, 0, 0 }, + /* Barbed */ { 0, 0, 0, 0, 0, 0, 0 }, + /* Ring */ { 0, 5, 0, 10, 15, 25, 0 }, + /* Chain */ { 0, 0, 10, 0, 15, 25, 0 }, + /* Plate */ { 5, 5, 10, 10, 15, 25, 0 }, + /* Dragon */ { 0, 5, 10, 10, 15, 25, 0 } + }; - public static int[,] ArmorTable { get; } = - { - // Gorget Gloves Helmet Arms Legs Chest Shield - /* Cloth */ { 0, 0, 0, 0, 0, 0, 0 }, - /* Leather */ { 0, 0, 0, 0, 0, 0, 0 }, - /* Studded */ { 2, 2, 0, 4, 6, 10, 0 }, - /* Bone */ { 0, 5, 10, 10, 15, 25, 0 }, - /* Spined */ { 0, 0, 0, 0, 0, 0, 0 }, - /* Horned */ { 0, 0, 0, 0, 0, 0, 0 }, - /* Barbed */ { 0, 0, 0, 0, 0, 0, 0 }, - /* Ring */ { 0, 5, 0, 10, 15, 25, 0 }, - /* Chain */ { 0, 0, 10, 0, 15, 25, 0 }, - /* Plate */ { 5, 5, 10, 10, 15, 25, 0 }, - /* Dragon */ { 0, 5, 10, 10, 15, 25, 0 } - }; + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Stealth].Callback = OnUse; + } - public static int GetArmorRating( Mobile m ) - { - if ( !Core.AOS ) - return (int)m.ArmorRating; + public static int GetArmorRating(Mobile m) + { + if (!Core.AOS) + return (int)m.ArmorRating; - int ar = 0; + int ar = 0; - for( int i = 0; i < m.Items.Count; i++ ) - { - BaseArmor armor = m.Items[i] as BaseArmor; + for (int i = 0; i < m.Items.Count; i++) + { + BaseArmor armor = m.Items[i] as BaseArmor; - if ( armor == null ) - continue; + if (armor == null) + continue; - int materialType = (int)armor.MaterialType; - int bodyPosition = (int)armor.BodyPosition; + int materialType = (int)armor.MaterialType; + int bodyPosition = (int)armor.BodyPosition; - if ( materialType >= ArmorTable.GetLength( 0 ) || bodyPosition >= ArmorTable.GetLength( 1 ) ) - continue; + if (materialType >= ArmorTable.GetLength(0) || bodyPosition >= ArmorTable.GetLength(1)) + continue; - if ( armor.ArmorAttributes.MageArmor == 0 ) - ar += ArmorTable[materialType, bodyPosition]; - } + if (armor.ArmorAttributes.MageArmor == 0) + ar += ArmorTable[materialType, bodyPosition]; + } - return ar; - } + return ar; + } - public static TimeSpan OnUse( Mobile m ) - { - if ( !m.Hidden ) - { - m.SendLocalizedMessage( 502725 ); // You must hide first - } - else if ( m.Skills[SkillName.Hiding].Base < HidingRequirement ) - { - m.SendLocalizedMessage( 502726 ); // You are not hidden well enough. Become better at hiding. - m.RevealingAction(); - } - else if ( !m.CanBeginAction( typeof( Stealth ) ) ) - { - m.SendLocalizedMessage( 1063086 ); // You cannot use this skill right now. - m.RevealingAction(); - } - else - { - int armorRating = GetArmorRating( m ); + public static TimeSpan OnUse(Mobile m) + { + if (!m.Hidden) + { + m.SendLocalizedMessage(502725); // You must hide first + } + else if (m.Skills[SkillName.Hiding].Base < HidingRequirement) + { + m.SendLocalizedMessage(502726); // You are not hidden well enough. Become better at hiding. + m.RevealingAction(); + } + else if (!m.CanBeginAction(typeof(Stealth))) + { + m.SendLocalizedMessage(1063086); // You cannot use this skill right now. + m.RevealingAction(); + } + else + { + int armorRating = GetArmorRating(m); - if ( armorRating >= (Core.AOS ? 42 : 26) ) //I have a hunch '42' was chosen cause someone's a fan of DNA - { - m.SendLocalizedMessage( 502727 ); // You could not hope to move quietly wearing this much armor. - m.RevealingAction(); - } - else if ( m.CheckSkill( SkillName.Stealth, -20.0 + (armorRating * 2), (Core.AOS ? 60.0 : 80.0) + (armorRating * 2) ) ) - { - int steps = (int)(m.Skills[SkillName.Stealth].Value / (Core.AOS ? 5.0 : 10.0)); + if (armorRating >= (Core.AOS ? 42 : 26)) //I have a hunch '42' was chosen cause someone's a fan of DNA + { + m.SendLocalizedMessage(502727); // You could not hope to move quietly wearing this much armor. + m.RevealingAction(); + } + else if (m.CheckSkill(SkillName.Stealth, -20.0 + armorRating * 2, + (Core.AOS ? 60.0 : 80.0) + armorRating * 2)) + { + int steps = (int)(m.Skills[SkillName.Stealth].Value / (Core.AOS ? 5.0 : 10.0)); - if ( steps < 1 ) - steps = 1; + if (steps < 1) + steps = 1; - m.AllowedStealthSteps = steps; + m.AllowedStealthSteps = steps; - PlayerMobile pm = m as PlayerMobile; // IsStealthing should be moved to Server.Mobiles + PlayerMobile pm = m as PlayerMobile; // IsStealthing should be moved to Server.Mobiles - if ( pm != null ) - pm.IsStealthing = true; + if (pm != null) + pm.IsStealthing = true; - m.SendLocalizedMessage( 502730 ); // You begin to move quietly. + m.SendLocalizedMessage(502730); // You begin to move quietly. - return TimeSpan.FromSeconds( 10.0 ); - } - else - { - m.SendLocalizedMessage( 502731 ); // You fail in your attempt to move unnoticed. - m.RevealingAction(); - } - } + return TimeSpan.FromSeconds(10.0); + } + else + { + m.SendLocalizedMessage(502731); // You fail in your attempt to move unnoticed. + m.RevealingAction(); + } + } - return TimeSpan.FromSeconds( 10.0 ); - } - } -} + return TimeSpan.FromSeconds(10.0); + } + } +} \ No newline at end of file diff --git a/Scripts/Skills/TasteID.cs b/Scripts/Skills/TasteID.cs index b73812c0b..43b41d358 100644 --- a/Scripts/Skills/TasteID.cs +++ b/Scripts/Skills/TasteID.cs @@ -1,94 +1,89 @@ using System; -using Server.Targeting; using Server.Items; using Server.Mobiles; +using Server.Targeting; namespace Server.SkillHandlers { - public class TasteID - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.TasteID].Callback = OnUse; - } + public class TasteID + { + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.TasteID].Callback = OnUse; + } - public static TimeSpan OnUse( Mobile m ) - { - m.Target = new InternalTarget(); + public static TimeSpan OnUse(Mobile m) + { + m.Target = new InternalTarget(); - m.SendLocalizedMessage( 502807 ); // What would you like to taste? + m.SendLocalizedMessage(502807); // What would you like to taste? - return TimeSpan.FromSeconds( 1.0 ); - } + return TimeSpan.FromSeconds(1.0); + } - [PlayerVendorTarget] - private class InternalTarget : Target - { - public InternalTarget() : base ( 2, false, TargetFlags.None ) - { - AllowNonlocal = true; - } + [PlayerVendorTarget] + private class InternalTarget : Target + { + public InternalTarget() : base(2, false, TargetFlags.None) + { + AllowNonlocal = true; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile ) - { - from.SendLocalizedMessage( 502816 ); // You feel that such an action would be inappropriate. - } - else if ( targeted is Food ) - { - Food food = (Food) targeted; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile) + { + from.SendLocalizedMessage(502816); // You feel that such an action would be inappropriate. + } + else if (targeted is Food) + { + Food food = (Food)targeted; - if ( from.CheckTargetSkill( SkillName.TasteID, food, 0, 100 ) ) - { - if ( food.Poison != null ) - { - food.SendLocalizedMessageTo( from, 1038284 ); // It appears to have poison smeared on it. - } - else - { - // No poison on the food - food.SendLocalizedMessageTo( from, 1010600 ); // You detect nothing unusual about this substance. - } - } - else - { - // Skill check failed - food.SendLocalizedMessageTo( from, 502823 ); // You cannot discern anything about this substance. - } - } - else if ( targeted is BasePotion ) - { - BasePotion potion = (BasePotion) targeted; + if (from.CheckTargetSkill(SkillName.TasteID, food, 0, 100)) + { + if (food.Poison != null) + food.SendLocalizedMessageTo(from, 1038284); // It appears to have poison smeared on it. + else + food.SendLocalizedMessageTo(from, 1010600); // You detect nothing unusual about this substance. + } + else + { + // Skill check failed + food.SendLocalizedMessageTo(from, 502823); // You cannot discern anything about this substance. + } + } + else if (targeted is BasePotion) + { + BasePotion potion = (BasePotion)targeted; - potion.SendLocalizedMessageTo( from, 502813 ); // You already know what kind of potion that is. - potion.SendLocalizedMessageTo( from, potion.LabelNumber ); - } - else if ( targeted is PotionKeg ) - { - PotionKeg keg = (PotionKeg) targeted; + potion.SendLocalizedMessageTo(from, 502813); // You already know what kind of potion that is. + potion.SendLocalizedMessageTo(from, potion.LabelNumber); + } + else if (targeted is PotionKeg) + { + PotionKeg keg = (PotionKeg)targeted; - if ( keg.Held <= 0 ) - { - keg.SendLocalizedMessageTo( from, 502228 ); // There is nothing in the keg to taste! - } - else - { - keg.SendLocalizedMessageTo( from, 502229 ); // You are already familiar with this keg's contents. - keg.SendLocalizedMessageTo( from, keg.LabelNumber ); - } - } - else - { - // The target is not food or potion or potion keg. - from.SendLocalizedMessage( 502820 ); // That's not something you can taste. - } - } + if (keg.Held <= 0) + { + keg.SendLocalizedMessageTo(from, 502228); // There is nothing in the keg to taste! + } + else + { + keg.SendLocalizedMessageTo(from, 502229); // You are already familiar with this keg's contents. + keg.SendLocalizedMessageTo(from, keg.LabelNumber); + } + } + else + { + // The target is not food or potion or potion keg. + from.SendLocalizedMessage(502820); // That's not something you can taste. + } + } - protected override void OnTargetOutOfRange( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 502815 ); // You are too far away to taste that. - } - } - } + protected override void OnTargetOutOfRange(Mobile from, object targeted) + { + from.SendLocalizedMessage(502815); // You are too far away to taste that. + } + } + } } \ No newline at end of file diff --git a/Scripts/Skills/Tracking.cs b/Scripts/Skills/Tracking.cs index ffc8368c7..42793d8d6 100644 --- a/Scripts/Skills/Tracking.cs +++ b/Scripts/Skills/Tracking.cs @@ -2,397 +2,401 @@ using System; using System.Collections.Generic; using Server.Gumps; using Server.Network; -using Server.Spells.Necromancy; using Server.Spells; +using Server.Spells.Necromancy; namespace Server.SkillHandlers { - public class Tracking - { - public static void Initialize() - { - SkillInfo.Table[(int)SkillName.Tracking].Callback = OnUse; - } + public class Tracking + { + private static Dictionary m_Table = new Dictionary(); - public static TimeSpan OnUse( Mobile m ) - { - m.SendLocalizedMessage( 1011350 ); // What do you wish to track? + public static void Initialize() + { + SkillInfo.Table[(int)SkillName.Tracking].Callback = OnUse; + } + + public static TimeSpan OnUse(Mobile m) + { + m.SendLocalizedMessage(1011350); // What do you wish to track? - m.CloseGump( typeof( TrackWhatGump ) ); - m.CloseGump( typeof( TrackWhoGump ) ); - m.SendGump( new TrackWhatGump( m ) ); + m.CloseGump(typeof(TrackWhatGump)); + m.CloseGump(typeof(TrackWhoGump)); + m.SendGump(new TrackWhatGump(m)); + + return TimeSpan.FromSeconds(10.0); // 10 second delay before beign able to re-use a skill + } + + public static void AddInfo(Mobile tracker, Mobile target) + { + TrackingInfo info = new TrackingInfo(tracker, target); + m_Table[tracker] = info; + } + + public static double GetStalkingBonus(Mobile tracker, Mobile target) + { + m_Table.TryGetValue(tracker, out TrackingInfo info); + + if (info == null || info.m_Target != target || info.m_Map != target.Map) + return 0.0; + + int xDelta = info.m_Location.X - target.X; + int yDelta = info.m_Location.Y - target.Y; + + double bonus = Math.Sqrt(xDelta * xDelta + yDelta * yDelta); - return TimeSpan.FromSeconds( 10.0 ); // 10 second delay before beign able to re-use a skill - } + m_Table.Remove(tracker); //Reset as of Pub 40, counting it as bug for Core.SE. - public class TrackingInfo - { - public Mobile m_Tracker; - public Mobile m_Target; - public Point2D m_Location; - public Map m_Map; - - public TrackingInfo( Mobile tracker, Mobile target ) - { - m_Tracker = tracker; - m_Target = target; - m_Location = new Point2D( target.X, target.Y ); - m_Map = target.Map; - } - } - - private static Dictionary m_Table = new Dictionary(); - - public static void AddInfo( Mobile tracker, Mobile target ) - { - TrackingInfo info = new TrackingInfo( tracker, target ); - m_Table[tracker] = info; - } - - public static double GetStalkingBonus( Mobile tracker, Mobile target ) - { - m_Table.TryGetValue( tracker, out TrackingInfo info ); - - if ( info == null || info.m_Target != target || info.m_Map != target.Map ) - return 0.0; - - int xDelta = info.m_Location.X - target.X; - int yDelta = info.m_Location.Y - target.Y; - - double bonus = Math.Sqrt( (xDelta * xDelta) + (yDelta * yDelta) ); - - m_Table.Remove( tracker ); //Reset as of Pub 40, counting it as bug for Core.SE. - - if ( Core.ML ) - return Math.Min( bonus, 10 + tracker.Skills.Tracking.Value/10 ); - - return bonus; - } - - - public static void ClearTrackingInfo( Mobile tracker ) - { - m_Table.Remove( tracker ); - } - } - - public class TrackWhatGump : Gump - { - private Mobile m_From; - private bool m_Success; - - public TrackWhatGump( Mobile from ) : base( 20, 30 ) - { - m_From = from; - m_Success = from.CheckSkill( SkillName.Tracking, 0.0, 21.1 ); - - AddPage( 0 ); - - AddBackground( 0, 0, 440, 135, 5054 ); - - AddBackground( 10, 10, 420, 75, 2620 ); - AddBackground( 10, 85, 420, 25, 3000 ); - - AddItem( 20, 20, 9682 ); - AddButton( 20, 110, 4005, 4007, 1, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 20, 90, 100, 20, 1018087, false, false ); // Animals - - AddItem( 120, 20, 9607 ); - AddButton( 120, 110, 4005, 4007, 2, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 120, 90, 100, 20, 1018088, false, false ); // Monsters - - AddItem( 220, 20, 8454 ); - AddButton( 220, 110, 4005, 4007, 3, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 220, 90, 100, 20, 1018089, false, false ); // Human NPCs - - AddItem( 320, 20, 8455 ); - AddButton( 320, 110, 4005, 4007, 4, GumpButtonType.Reply, 0 ); - AddHtmlLocalized( 320, 90, 100, 20, 1018090, false, false ); // Players - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - if ( info.ButtonID >= 1 && info.ButtonID <= 4 ) - TrackWhoGump.DisplayTo( m_Success, m_From, info.ButtonID - 1 ); - } - } - - public delegate bool TrackTypeDelegate( Mobile m ); - - public class TrackWhoGump : Gump - { - private Mobile m_From; - private int m_Range; - - private static TrackTypeDelegate[] m_Delegates = { - IsAnimal, - IsMonster, - IsHumanNPC, - IsPlayer - }; - - private class InternalSorter : IComparer - { - private Mobile m_From; - - public InternalSorter( Mobile from ) - { - m_From = from; - } - - public int Compare( Mobile x, Mobile y ) - { - if ( x == null && y == null ) - return 0; - if ( x == null ) - return -1; - if ( y == null ) - return 1; - - return m_From.GetDistanceToSqrt( x ).CompareTo( m_From.GetDistanceToSqrt( y ) ); - } - } - - public static void DisplayTo( bool success, Mobile from, int type ) - { - if ( !success ) - { - from.SendLocalizedMessage( 1018092 ); // You see no evidence of those in the area. - return; - } - - Map map = from.Map; - - if ( map == null ) - return; - - TrackTypeDelegate check = m_Delegates[type]; - - from.CheckSkill( SkillName.Tracking, 21.1, 100.0 ); // Passive gain - - int range = 10 + (int)(from.Skills[SkillName.Tracking].Value / 10); - - List list = new List(); - - foreach ( Mobile m in from.GetMobilesInRange( range ) ) - { - // Ghosts can no longer be tracked - if ( m != from && (!Core.AOS || m.Alive) && (!m.Hidden || m.AccessLevel == AccessLevel.Player || from.AccessLevel > m.AccessLevel) && check( m ) && CheckDifficulty( from, m ) ) - list.Add( m ); - } - - if ( list.Count > 0 ) - { - list.Sort( new InternalSorter( from ) ); - - from.SendGump( new TrackWhoGump( from, list, range ) ); - from.SendLocalizedMessage( 1018093 ); // Select the one you would like to track. - } - else - { - if ( type == 0 ) - from.SendLocalizedMessage( 502991 ); // You see no evidence of animals in the area. - else if ( type == 1 ) - from.SendLocalizedMessage( 502993 ); // You see no evidence of creatures in the area. - else - from.SendLocalizedMessage( 502995 ); // You see no evidence of people in the area. - } - } - - // Tracking players uses tracking and detect hidden vs. hiding and stealth - private static bool CheckDifficulty( Mobile from, Mobile m ) - { - if ( !Core.AOS || !m.Player ) - return true; - - - - int tracking = from.Skills[SkillName.Tracking].Fixed; - int detectHidden = from.Skills[SkillName.DetectHidden].Fixed; - - if ( Core.ML && m.Race == Race.Elf ) - tracking /= 2; //The 'Guide' says that it requires twice as Much tracking SKILL to track an elf. Not the total difficulty to track. - - int hiding = m.Skills[SkillName.Hiding].Fixed; - int stealth = m.Skills[SkillName.Stealth].Fixed; - int divisor = hiding + stealth; - - // Necromancy forms affect tracking difficulty - if ( TransformationSpellHelper.UnderTransformation( m, typeof( HorrificBeastSpell ) ) ) - divisor -= 200; - else if ( TransformationSpellHelper.UnderTransformation( m, typeof( VampiricEmbraceSpell ) ) && divisor < 500 ) - divisor = 500; - else if ( TransformationSpellHelper.UnderTransformation( m, typeof( WraithFormSpell ) ) && divisor <= 2000 ) - divisor += 200; - - int chance; - if ( divisor > 0 ) - { - if ( Core.SE ) - chance = 50 * (tracking * 2 + detectHidden) / divisor; - else - chance = 50 * (tracking + detectHidden + 10 * Utility.RandomMinMax( 1, 20 )) / divisor; - } - else - chance = 100; - - return chance > Utility.Random( 100 ); - } - - private static bool IsAnimal( Mobile m ) - { - return ( !m.Player && m.Body.IsAnimal ); - } - - private static bool IsMonster( Mobile m ) - { - return ( !m.Player && m.Body.IsMonster ); - } - - private static bool IsHumanNPC( Mobile m ) - { - return ( !m.Player && m.Body.IsHuman ); - } - - private static bool IsPlayer( Mobile m ) - { - return m.Player; - } - - private List m_List; - - private TrackWhoGump( Mobile from, List list, int range ) : base( 20, 30 ) - { - m_From = from; - m_List = list; - m_Range = range; - - AddPage( 0 ); - - AddBackground( 0, 0, 440, 155, 5054 ); - - AddBackground( 10, 10, 420, 75, 2620 ); - AddBackground( 10, 85, 420, 45, 3000 ); - - if ( list.Count > 4 ) - { - AddBackground( 0, 155, 440, 155, 5054 ); - - AddBackground( 10, 165, 420, 75, 2620 ); - AddBackground( 10, 240, 420, 45, 3000 ); - - if ( list.Count > 8 ) - { - AddBackground( 0, 310, 440, 155, 5054 ); - - AddBackground( 10, 320, 420, 75, 2620 ); - AddBackground( 10, 395, 420, 45, 3000 ); - } - } - - for ( int i = 0; i < list.Count && i < 12; ++i ) - { - Mobile m = list[i]; - - AddItem( 20 + ((i % 4) * 100), 20 + ((i / 4) * 155), ShrinkTable.Lookup( m ) ); - AddButton( 20 + ((i % 4) * 100), 130 + ((i / 4) * 155), 4005, 4007, i + 1, GumpButtonType.Reply, 0 ); - - if ( m.Name != null ) - AddHtml( 20 + ((i % 4) * 100), 90 + ((i / 4) * 155), 90, 40, m.Name, false, false ); - } - } - - public override void OnResponse( NetState state, RelayInfo info ) - { - int index = info.ButtonID - 1; - - if ( index >= 0 && index < m_List.Count && index < 12 ) - { - Mobile m = m_List[index]; - - m_From.QuestArrow = new TrackArrow( m_From, m, m_Range * 2 ); - - if ( Core.SE ) - Tracking.AddInfo( m_From, m ); - } - } - } - - public class TrackArrow : QuestArrow - { - private Mobile m_From; - private Timer m_Timer; - - public TrackArrow( Mobile from, Mobile target, int range ) : base( from, target ) - { - m_From = from; - m_Timer = new TrackTimer( from, target, range, this ); - m_Timer.Start(); - } - - public override void OnClick( bool rightClick ) - { - if ( rightClick ) - { - Tracking.ClearTrackingInfo( m_From ); - - m_From = null; - - Stop(); - } - } - - public override void OnStop() - { - m_Timer.Stop(); - - if ( m_From != null ) - { - Tracking.ClearTrackingInfo( m_From ); - - m_From.SendLocalizedMessage( 503177 ); // You have lost your quarry. - } - } - } - - public class TrackTimer : Timer - { - private Mobile m_From, m_Target; - private int m_Range; - private int m_LastX, m_LastY; - private QuestArrow m_Arrow; - - public TrackTimer( Mobile from, Mobile target, int range, QuestArrow arrow ) : base( TimeSpan.FromSeconds( 0.25 ), TimeSpan.FromSeconds( 2.5 ) ) - { - m_From = from; - m_Target = target; - m_Range = range; - - m_Arrow = arrow; - } - - protected override void OnTick() - { - if ( !m_Arrow.Running ) - { - Stop(); - return; - } - - if ( m_From.NetState == null || m_From.Deleted || m_Target.Deleted || m_From.Map != m_Target.Map || !m_From.InRange( m_Target, m_Range ) || ( m_Target.Hidden && m_Target.AccessLevel > m_From.AccessLevel ) ) - { - m_Arrow.Stop(); - Stop(); - return; - } - - if ( m_LastX != m_Target.X || m_LastY != m_Target.Y ) - { - m_LastX = m_Target.X; - m_LastY = m_Target.Y; - - m_Arrow.Update(); - } - } - } -} + if (Core.ML) + return Math.Min(bonus, 10 + tracker.Skills.Tracking.Value / 10); + + return bonus; + } + + + public static void ClearTrackingInfo(Mobile tracker) + { + m_Table.Remove(tracker); + } + + public class TrackingInfo + { + public Point2D m_Location; + public Map m_Map; + public Mobile m_Target; + public Mobile m_Tracker; + + public TrackingInfo(Mobile tracker, Mobile target) + { + m_Tracker = tracker; + m_Target = target; + m_Location = new Point2D(target.X, target.Y); + m_Map = target.Map; + } + } + } + + public class TrackWhatGump : Gump + { + private Mobile m_From; + private bool m_Success; + + public TrackWhatGump(Mobile from) : base(20, 30) + { + m_From = from; + m_Success = from.CheckSkill(SkillName.Tracking, 0.0, 21.1); + + AddPage(0); + + AddBackground(0, 0, 440, 135, 5054); + + AddBackground(10, 10, 420, 75, 2620); + AddBackground(10, 85, 420, 25, 3000); + + AddItem(20, 20, 9682); + AddButton(20, 110, 4005, 4007, 1, GumpButtonType.Reply, 0); + AddHtmlLocalized(20, 90, 100, 20, 1018087, false, false); // Animals + + AddItem(120, 20, 9607); + AddButton(120, 110, 4005, 4007, 2, GumpButtonType.Reply, 0); + AddHtmlLocalized(120, 90, 100, 20, 1018088, false, false); // Monsters + + AddItem(220, 20, 8454); + AddButton(220, 110, 4005, 4007, 3, GumpButtonType.Reply, 0); + AddHtmlLocalized(220, 90, 100, 20, 1018089, false, false); // Human NPCs + + AddItem(320, 20, 8455); + AddButton(320, 110, 4005, 4007, 4, GumpButtonType.Reply, 0); + AddHtmlLocalized(320, 90, 100, 20, 1018090, false, false); // Players + } + + public override void OnResponse(NetState state, RelayInfo info) + { + if (info.ButtonID >= 1 && info.ButtonID <= 4) + TrackWhoGump.DisplayTo(m_Success, m_From, info.ButtonID - 1); + } + } + + public delegate bool TrackTypeDelegate(Mobile m); + + public class TrackWhoGump : Gump + { + private static TrackTypeDelegate[] m_Delegates = + { + IsAnimal, + IsMonster, + IsHumanNPC, + IsPlayer + }; + + private Mobile m_From; + + private List m_List; + private int m_Range; + + private TrackWhoGump(Mobile from, List list, int range) : base(20, 30) + { + m_From = from; + m_List = list; + m_Range = range; + + AddPage(0); + + AddBackground(0, 0, 440, 155, 5054); + + AddBackground(10, 10, 420, 75, 2620); + AddBackground(10, 85, 420, 45, 3000); + + if (list.Count > 4) + { + AddBackground(0, 155, 440, 155, 5054); + + AddBackground(10, 165, 420, 75, 2620); + AddBackground(10, 240, 420, 45, 3000); + + if (list.Count > 8) + { + AddBackground(0, 310, 440, 155, 5054); + + AddBackground(10, 320, 420, 75, 2620); + AddBackground(10, 395, 420, 45, 3000); + } + } + + for (int i = 0; i < list.Count && i < 12; ++i) + { + Mobile m = list[i]; + + AddItem(20 + i % 4 * 100, 20 + i / 4 * 155, ShrinkTable.Lookup(m)); + AddButton(20 + i % 4 * 100, 130 + i / 4 * 155, 4005, 4007, i + 1, GumpButtonType.Reply, 0); + + if (m.Name != null) + AddHtml(20 + i % 4 * 100, 90 + i / 4 * 155, 90, 40, m.Name, false, false); + } + } + + public static void DisplayTo(bool success, Mobile from, int type) + { + if (!success) + { + from.SendLocalizedMessage(1018092); // You see no evidence of those in the area. + return; + } + + Map map = from.Map; + + if (map == null) + return; + + TrackTypeDelegate check = m_Delegates[type]; + + from.CheckSkill(SkillName.Tracking, 21.1, 100.0); // Passive gain + + int range = 10 + (int)(from.Skills[SkillName.Tracking].Value / 10); + + List list = new List(); + + foreach (Mobile m in from.GetMobilesInRange(range)) + // Ghosts can no longer be tracked + if (m != from && (!Core.AOS || m.Alive) && + (!m.Hidden || m.AccessLevel == AccessLevel.Player || from.AccessLevel > m.AccessLevel) && check(m) && + CheckDifficulty(from, m)) + list.Add(m); + + if (list.Count > 0) + { + list.Sort(new InternalSorter(from)); + + from.SendGump(new TrackWhoGump(from, list, range)); + from.SendLocalizedMessage(1018093); // Select the one you would like to track. + } + else + { + if (type == 0) + from.SendLocalizedMessage(502991); // You see no evidence of animals in the area. + else if (type == 1) + from.SendLocalizedMessage(502993); // You see no evidence of creatures in the area. + else + from.SendLocalizedMessage(502995); // You see no evidence of people in the area. + } + } + + // Tracking players uses tracking and detect hidden vs. hiding and stealth + private static bool CheckDifficulty(Mobile from, Mobile m) + { + if (!Core.AOS || !m.Player) + return true; + + + int tracking = from.Skills[SkillName.Tracking].Fixed; + int detectHidden = from.Skills[SkillName.DetectHidden].Fixed; + + if (Core.ML && m.Race == Race.Elf) + tracking /= 2; //The 'Guide' says that it requires twice as Much tracking SKILL to track an elf. Not the total difficulty to track. + + int hiding = m.Skills[SkillName.Hiding].Fixed; + int stealth = m.Skills[SkillName.Stealth].Fixed; + int divisor = hiding + stealth; + + // Necromancy forms affect tracking difficulty + if (TransformationSpellHelper.UnderTransformation(m, typeof(HorrificBeastSpell))) + divisor -= 200; + else if (TransformationSpellHelper.UnderTransformation(m, typeof(VampiricEmbraceSpell)) && divisor < 500) + divisor = 500; + else if (TransformationSpellHelper.UnderTransformation(m, typeof(WraithFormSpell)) && divisor <= 2000) + divisor += 200; + + int chance; + if (divisor > 0) + { + if (Core.SE) + chance = 50 * (tracking * 2 + detectHidden) / divisor; + else + chance = 50 * (tracking + detectHidden + 10 * Utility.RandomMinMax(1, 20)) / divisor; + } + else + { + chance = 100; + } + + return chance > Utility.Random(100); + } + + private static bool IsAnimal(Mobile m) + { + return !m.Player && m.Body.IsAnimal; + } + + private static bool IsMonster(Mobile m) + { + return !m.Player && m.Body.IsMonster; + } + + private static bool IsHumanNPC(Mobile m) + { + return !m.Player && m.Body.IsHuman; + } + + private static bool IsPlayer(Mobile m) + { + return m.Player; + } + + public override void OnResponse(NetState state, RelayInfo info) + { + int index = info.ButtonID - 1; + + if (index >= 0 && index < m_List.Count && index < 12) + { + Mobile m = m_List[index]; + + m_From.QuestArrow = new TrackArrow(m_From, m, m_Range * 2); + + if (Core.SE) + Tracking.AddInfo(m_From, m); + } + } + + private class InternalSorter : IComparer + { + private Mobile m_From; + + public InternalSorter(Mobile from) + { + m_From = from; + } + + public int Compare(Mobile x, Mobile y) + { + if (x == null && y == null) + return 0; + if (x == null) + return -1; + if (y == null) + return 1; + + return m_From.GetDistanceToSqrt(x).CompareTo(m_From.GetDistanceToSqrt(y)); + } + } + } + + public class TrackArrow : QuestArrow + { + private Mobile m_From; + private Timer m_Timer; + + public TrackArrow(Mobile from, Mobile target, int range) : base(from, target) + { + m_From = from; + m_Timer = new TrackTimer(from, target, range, this); + m_Timer.Start(); + } + + public override void OnClick(bool rightClick) + { + if (rightClick) + { + Tracking.ClearTrackingInfo(m_From); + + m_From = null; + + Stop(); + } + } + + public override void OnStop() + { + m_Timer.Stop(); + + if (m_From != null) + { + Tracking.ClearTrackingInfo(m_From); + + m_From.SendLocalizedMessage(503177); // You have lost your quarry. + } + } + } + + public class TrackTimer : Timer + { + private QuestArrow m_Arrow; + private Mobile m_From, m_Target; + private int m_LastX, m_LastY; + private int m_Range; + + public TrackTimer(Mobile from, Mobile target, int range, QuestArrow arrow) : base(TimeSpan.FromSeconds(0.25), + TimeSpan.FromSeconds(2.5)) + { + m_From = from; + m_Target = target; + m_Range = range; + + m_Arrow = arrow; + } + + protected override void OnTick() + { + if (!m_Arrow.Running) + { + Stop(); + return; + } + + if (m_From.NetState == null || m_From.Deleted || m_Target.Deleted || m_From.Map != m_Target.Map || + !m_From.InRange(m_Target, m_Range) || m_Target.Hidden && m_Target.AccessLevel > m_From.AccessLevel) + { + m_Arrow.Stop(); + Stop(); + return; + } + + if (m_LastX != m_Target.X || m_LastY != m_Target.Y) + { + m_LastX = m_Target.X; + m_LastY = m_Target.Y; + + m_Arrow.Update(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Engines/GiftGiving.cs b/Scripts/SpecialSystems/Engines/GiftGiving.cs index 03ab62200..21537afb8 100644 --- a/Scripts/SpecialSystems/Engines/GiftGiving.cs +++ b/Scripts/SpecialSystems/Engines/GiftGiving.cs @@ -4,83 +4,81 @@ using Server.Accounting; namespace Server.Misc { - public enum GiftResult - { - Backpack, - BankBox - } + public enum GiftResult + { + Backpack, + BankBox + } - public class GiftGiving - { - private static List m_Givers = new List(); + public class GiftGiving + { + private static List m_Givers = new List(); - public static void Register( GiftGiver giver ) - { - m_Givers.Add( giver ); - } + public static void Register(GiftGiver giver) + { + m_Givers.Add(giver); + } - public static void Initialize() - { - EventSink.Login += EventSink_Login; - } + public static void Initialize() + { + EventSink.Login += EventSink_Login; + } - private static void EventSink_Login( LoginEventArgs e ) - { - Account acct = e.Mobile.Account as Account; + private static void EventSink_Login(LoginEventArgs e) + { + Account acct = e.Mobile.Account as Account; - if ( acct == null ) - return; + if (acct == null) + return; - DateTime now = DateTime.UtcNow; + DateTime now = DateTime.UtcNow; - for ( int i = 0; i < m_Givers.Count; ++i ) - { - GiftGiver giver = m_Givers[i]; + for (int i = 0; i < m_Givers.Count; ++i) + { + GiftGiver giver = m_Givers[i]; - if ( now < giver.Start || now >= giver.Finish ) - continue; // not in the correct timefream + if (now < giver.Start || now >= giver.Finish) + continue; // not in the correct timefream - if ( acct.Created > (giver.Start - giver.MinimumAge) ) - continue; // newly created account + if (acct.Created > giver.Start - giver.MinimumAge) + continue; // newly created account - if ( acct.LastLogin >= giver.Start ) - continue; // already got one + if (acct.LastLogin >= giver.Start) + continue; // already got one - giver.DelayGiveGift( TimeSpan.FromSeconds( 5.0 ), e.Mobile ); - } + giver.DelayGiveGift(TimeSpan.FromSeconds(5.0), e.Mobile); + } - acct.LastLogin = now; - } - } + acct.LastLogin = now; + } + } - public abstract class GiftGiver - { - public virtual TimeSpan MinimumAge => TimeSpan.FromDays( 30.0 ); + public abstract class GiftGiver + { + public virtual TimeSpan MinimumAge => TimeSpan.FromDays(30.0); - public abstract DateTime Start{ get; } - public abstract DateTime Finish{ get; } - public abstract void GiveGift( Mobile mob ); + public abstract DateTime Start{ get; } + public abstract DateTime Finish{ get; } + public abstract void GiveGift(Mobile mob); - public virtual void DelayGiveGift( TimeSpan delay, Mobile mob ) - { - Timer.DelayCall( delay, new TimerStateCallback( DelayGiveGift_Callback ), mob ); - } + public virtual void DelayGiveGift(TimeSpan delay, Mobile mob) + { + Timer.DelayCall(delay, new TimerStateCallback(DelayGiveGift_Callback), mob); + } - protected virtual void DelayGiveGift_Callback( object state ) - { - GiveGift( (Mobile) state ); - } + protected virtual void DelayGiveGift_Callback(object state) + { + GiveGift((Mobile)state); + } - public virtual GiftResult GiveGift( Mobile mob, Item item ) - { - if ( mob.PlaceInBackpack( item ) ) - { - if ( !WeightOverloading.IsOverloaded( mob ) ) - return GiftResult.Backpack; - } + public virtual GiftResult GiveGift(Mobile mob, Item item) + { + if (mob.PlaceInBackpack(item)) + if (!WeightOverloading.IsOverloaded(mob)) + return GiftResult.Backpack; - mob.BankBox.DropItem( item ); - return GiftResult.BankBox; - } - } + mob.BankBox.DropItem(item); + return GiftResult.BankBox; + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Engines/ItemFixes.cs b/Scripts/SpecialSystems/Engines/ItemFixes.cs index d7cb3c88e..a0fc455fc 100644 --- a/Scripts/SpecialSystems/Engines/ItemFixes.cs +++ b/Scripts/SpecialSystems/Engines/ItemFixes.cs @@ -1,16 +1,16 @@ namespace Server.Misc { - public static class ItemFixes - { - public static void Initialize() - { - // Missing NoShoot flags - TileData.ItemTable[0x2A0].Flags |= TileFlag.NoShoot; - TileData.ItemTable[0x3E0].Flags |= TileFlag.NoShoot; - TileData.ItemTable[0x3E1].Flags |= TileFlag.NoShoot; + public static class ItemFixes + { + public static void Initialize() + { + // Missing NoShoot flags + TileData.ItemTable[0x2A0].Flags |= TileFlag.NoShoot; + TileData.ItemTable[0x3E0].Flags |= TileFlag.NoShoot; + TileData.ItemTable[0x3E1].Flags |= TileFlag.NoShoot; - // Incorrect height - TileData.ItemTable[0x34D2].Height = 0; - } - } -} + // Incorrect height + TileData.ItemTable[0x34D2].Height = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Engines/PreventInaccess.cs b/Scripts/SpecialSystems/Engines/PreventInaccess.cs index 1979074fd..231ef909a 100644 --- a/Scripts/SpecialSystems/Engines/PreventInaccess.cs +++ b/Scripts/SpecialSystems/Engines/PreventInaccess.cs @@ -2,87 +2,89 @@ using System.Collections.Generic; namespace Server.Misc { - /* - * This system prevents the inability for server staff to - * access their server due to data overflows during login. - * - * Whenever a staff character's NetState is disposed right after - * the login process, the character is moved to and logged out - * at a "safe" alternative. - * - * The location the character was moved from will be reported - * to the player upon the next successful login. - * - * This system does not affect non-staff players. - */ - public static class PreventInaccess - { - public static readonly bool Enabled = true; + /* + * This system prevents the inability for server staff to + * access their server due to data overflows during login. + * + * Whenever a staff character's NetState is disposed right after + * the login process, the character is moved to and logged out + * at a "safe" alternative. + * + * The location the character was moved from will be reported + * to the player upon the next successful login. + * + * This system does not affect non-staff players. + */ + public static class PreventInaccess + { + public static readonly bool Enabled = true; - private static readonly LocationInfo[] m_Destinations = { - new LocationInfo( new Point3D( 5275, 1163, 0 ), Map.Felucca ), // Jail - new LocationInfo( new Point3D( 5275, 1163, 0 ), Map.Trammel ), - new LocationInfo( new Point3D( 5445, 1153, 0 ), Map.Felucca ), // Green acres - new LocationInfo( new Point3D( 5445, 1153, 0 ), Map.Trammel ) - }; + private static readonly LocationInfo[] m_Destinations = + { + new LocationInfo(new Point3D(5275, 1163, 0), Map.Felucca), // Jail + new LocationInfo(new Point3D(5275, 1163, 0), Map.Trammel), + new LocationInfo(new Point3D(5445, 1153, 0), Map.Felucca), // Green acres + new LocationInfo(new Point3D(5445, 1153, 0), Map.Trammel) + }; - private static Dictionary m_MoveHistory; + private static Dictionary m_MoveHistory; - public static void Initialize() - { - m_MoveHistory = new Dictionary(); + public static void Initialize() + { + m_MoveHistory = new Dictionary(); - if ( Enabled ) - EventSink.Login += OnLogin; - } + if (Enabled) + EventSink.Login += OnLogin; + } - public static void OnLogin( LoginEventArgs e ) - { - Mobile from = e.Mobile; + public static void OnLogin(LoginEventArgs e) + { + Mobile from = e.Mobile; - if ( from == null || from.AccessLevel < AccessLevel.Counselor ) - return; + if (from == null || from.AccessLevel < AccessLevel.Counselor) + return; - if ( HasDisconnected( from ) ) - { - if ( !m_MoveHistory.ContainsKey( from ) ) - m_MoveHistory[from] = new LocationInfo( from.Location, from.Map ); + if (HasDisconnected(from)) + { + if (!m_MoveHistory.ContainsKey(from)) + m_MoveHistory[from] = new LocationInfo(from.Location, from.Map); - LocationInfo dest = GetRandomDestination(); + LocationInfo dest = GetRandomDestination(); - from.Location = dest.Location; - from.Map = dest.Map; - } - else if ( m_MoveHistory.ContainsKey( from ) ) - { - LocationInfo orig = m_MoveHistory[from]; - from.SendMessage( "Your character was moved from {0} ({1}) due to a detected client crash.", orig.Location, orig.Map ); + from.Location = dest.Location; + from.Map = dest.Map; + } + else if (m_MoveHistory.ContainsKey(from)) + { + LocationInfo orig = m_MoveHistory[from]; + from.SendMessage("Your character was moved from {0} ({1}) due to a detected client crash.", orig.Location, + orig.Map); - m_MoveHistory.Remove( from ); - } - } + m_MoveHistory.Remove(from); + } + } - private static bool HasDisconnected( Mobile m ) - { - return ( m.NetState?.Socket == null ); - } + private static bool HasDisconnected(Mobile m) + { + return m.NetState?.Socket == null; + } - private static LocationInfo GetRandomDestination() - { - return m_Destinations[Utility.Random( m_Destinations.Length )]; - } + private static LocationInfo GetRandomDestination() + { + return m_Destinations[Utility.Random(m_Destinations.Length)]; + } - private class LocationInfo - { - public Point3D Location { get; } + private class LocationInfo + { + public LocationInfo(Point3D loc, Map map) + { + Location = loc; + Map = map; + } - public Map Map { get; } + public Point3D Location{ get; } - public LocationInfo( Point3D loc, Map map ) - { - Location = loc; - Map = map; - } - } - } -} + public Map Map{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Engines/TestCenter.cs b/Scripts/SpecialSystems/Engines/TestCenter.cs index 085d80afa..504054fa7 100644 --- a/Scripts/SpecialSystems/Engines/TestCenter.cs +++ b/Scripts/SpecialSystems/Engines/TestCenter.cs @@ -1,236 +1,233 @@ using System; using System.Text; +using Server.Commands; using Server.Gumps; using Server.Network; -using Server.Commands; namespace Server.Misc { - public class TestCenter - { - private const bool m_Enabled = false; - public static bool Enabled => m_Enabled; + public class TestCenter + { + private const bool m_Enabled = false; + public static bool Enabled => m_Enabled; - public static void Initialize() - { - // Register our speech handler - if ( Enabled ) - EventSink.Speech += EventSink_Speech; - } + public static void Initialize() + { + // Register our speech handler + if (Enabled) + EventSink.Speech += EventSink_Speech; + } - private static void EventSink_Speech( SpeechEventArgs args ) - { - if ( !args.Handled ) - { - if ( Insensitive.StartsWith( args.Speech, "set" ) ) - { - Mobile from = args.Mobile; + private static void EventSink_Speech(SpeechEventArgs args) + { + if (!args.Handled) + { + if (Insensitive.StartsWith(args.Speech, "set")) + { + Mobile from = args.Mobile; - string[] split = args.Speech.Split( ' ' ); + string[] split = args.Speech.Split(' '); - if ( split.Length == 3 ) - { - try - { - string name = split[1]; - double value = Convert.ToDouble( split[2] ); + if (split.Length == 3) + try + { + string name = split[1]; + double value = Convert.ToDouble(split[2]); - if ( Insensitive.Equals( name, "str" ) ) - ChangeStrength( from, (int)value ); - else if ( Insensitive.Equals( name, "dex" ) ) - ChangeDexterity( from, (int)value ); - else if ( Insensitive.Equals( name, "int" ) ) - ChangeIntelligence( from, (int)value ); - else - ChangeSkill( from, name, value ); - } - catch - { - } - } - } - else if ( Insensitive.Equals( args.Speech, "help" ) ) - { - args.Mobile.SendGump( new TCHelpGump() ); + if (Insensitive.Equals(name, "str")) + ChangeStrength(from, (int)value); + else if (Insensitive.Equals(name, "dex")) + ChangeDexterity(from, (int)value); + else if (Insensitive.Equals(name, "int")) + ChangeIntelligence(from, (int)value); + else + ChangeSkill(from, name, value); + } + catch + { + } + } + else if (Insensitive.Equals(args.Speech, "help")) + { + args.Mobile.SendGump(new TCHelpGump()); - args.Handled = true; - } - } - } + args.Handled = true; + } + } + } - private static void ChangeStrength( Mobile from, int value ) - { - if ( value < 10 || value > 125 ) - { - from.SendLocalizedMessage( 1005628 ); // Stats range between 10 and 125. - } - else - { - if ( (value + from.RawDex + from.RawInt) > from.StatCap ) - { - from.SendLocalizedMessage( 1005629 ); // You can not exceed the stat cap. Try setting another stat lower first. - } - else - { - from.RawStr = value; - from.SendLocalizedMessage( 1005630 ); // Your stats have been adjusted. - } - } - } + private static void ChangeStrength(Mobile from, int value) + { + if (value < 10 || value > 125) + { + from.SendLocalizedMessage(1005628); // Stats range between 10 and 125. + } + else + { + if (value + from.RawDex + from.RawInt > from.StatCap) + { + from.SendLocalizedMessage( + 1005629); // You can not exceed the stat cap. Try setting another stat lower first. + } + else + { + from.RawStr = value; + from.SendLocalizedMessage(1005630); // Your stats have been adjusted. + } + } + } - private static void ChangeDexterity( Mobile from, int value ) - { - if ( value < 10 || value > 125 ) - { - from.SendLocalizedMessage( 1005628 ); // Stats range between 10 and 125. - } - else - { - if ( (from.RawStr + value + from.RawInt) > from.StatCap ) - { - from.SendLocalizedMessage( 1005629 ); // You can not exceed the stat cap. Try setting another stat lower first. - } - else - { - from.RawDex = value; - from.SendLocalizedMessage( 1005630 ); // Your stats have been adjusted. - } - } - } + private static void ChangeDexterity(Mobile from, int value) + { + if (value < 10 || value > 125) + { + from.SendLocalizedMessage(1005628); // Stats range between 10 and 125. + } + else + { + if (from.RawStr + value + from.RawInt > from.StatCap) + { + from.SendLocalizedMessage( + 1005629); // You can not exceed the stat cap. Try setting another stat lower first. + } + else + { + from.RawDex = value; + from.SendLocalizedMessage(1005630); // Your stats have been adjusted. + } + } + } - private static void ChangeIntelligence( Mobile from, int value ) - { - if ( value < 10 || value > 125 ) - { - from.SendLocalizedMessage( 1005628 ); // Stats range between 10 and 125. - } - else - { - if ( (from.RawStr + from.RawDex + value) > from.StatCap ) - { - from.SendLocalizedMessage( 1005629 ); // You can not exceed the stat cap. Try setting another stat lower first. - } - else - { - from.RawInt = value; - from.SendLocalizedMessage( 1005630 ); // Your stats have been adjusted. - } - } - } + private static void ChangeIntelligence(Mobile from, int value) + { + if (value < 10 || value > 125) + { + from.SendLocalizedMessage(1005628); // Stats range between 10 and 125. + } + else + { + if (from.RawStr + from.RawDex + value > from.StatCap) + { + from.SendLocalizedMessage( + 1005629); // You can not exceed the stat cap. Try setting another stat lower first. + } + else + { + from.RawInt = value; + from.SendLocalizedMessage(1005630); // Your stats have been adjusted. + } + } + } - private static void ChangeSkill( Mobile from, string name, double value ) - { - SkillName index; + private static void ChangeSkill(Mobile from, string name, double value) + { + SkillName index; - if ( !Enum.TryParse( name, true, out index ) || (!Core.SE && (int)index > 51) || (!Core.AOS && (int)index > 48) ) - { - from.SendLocalizedMessage( 1005631 ); // You have specified an invalid skill to set. - return; - } + if (!Enum.TryParse(name, true, out index) || !Core.SE && (int)index > 51 || !Core.AOS && (int)index > 48) + { + from.SendLocalizedMessage(1005631); // You have specified an invalid skill to set. + return; + } - Skill skill = from.Skills[index]; + Skill skill = from.Skills[index]; - if ( skill != null ) - { - if ( value < 0 || value > skill.Cap ) - { - from.SendMessage($"Your skill in {skill.Info.Name} is capped at {skill.Cap:F1}."); - } - else - { - int newFixedPoint = (int)(value * 10.0); - int oldFixedPoint = skill.BaseFixedPoint; + if (skill != null) + { + if (value < 0 || value > skill.Cap) + { + from.SendMessage($"Your skill in {skill.Info.Name} is capped at {skill.Cap:F1}."); + } + else + { + int newFixedPoint = (int)(value * 10.0); + int oldFixedPoint = skill.BaseFixedPoint; - if ( ((skill.Owner.Total - oldFixedPoint) + newFixedPoint) > skill.Owner.Cap ) - { - from.SendMessage( "You can not exceed the skill cap. Try setting another skill lower first." ); - } - else - { - skill.BaseFixedPoint = newFixedPoint; - } - } - } - else - { - from.SendLocalizedMessage( 1005631 ); // You have specified an invalid skill to set. - } - } + if (skill.Owner.Total - oldFixedPoint + newFixedPoint > skill.Owner.Cap) + from.SendMessage("You can not exceed the skill cap. Try setting another skill lower first."); + else + skill.BaseFixedPoint = newFixedPoint; + } + } + else + { + from.SendLocalizedMessage(1005631); // You have specified an invalid skill to set. + } + } - public class TCHelpGump : Gump - { - public TCHelpGump() : base( 40, 40 ) - { - AddPage( 0 ); - AddBackground( 0, 0, 160, 120, 5054 ); + public class TCHelpGump : Gump + { + public TCHelpGump() : base(40, 40) + { + AddPage(0); + AddBackground(0, 0, 160, 120, 5054); - AddButton( 10, 10, 0xFB7, 0xFB9, 1, GumpButtonType.Reply, 0 ); - AddLabel( 45, 10, 0x34, "RunUO" ); + AddButton(10, 10, 0xFB7, 0xFB9, 1, GumpButtonType.Reply, 0); + AddLabel(45, 10, 0x34, "RunUO"); - AddButton( 10, 35, 0xFB7, 0xFB9, 2, GumpButtonType.Reply, 0 ); - AddLabel( 45, 35, 0x34, "List of skills" ); + AddButton(10, 35, 0xFB7, 0xFB9, 2, GumpButtonType.Reply, 0); + AddLabel(45, 35, 0x34, "List of skills"); - AddButton( 10, 60, 0xFB7, 0xFB9, 3, GumpButtonType.Reply, 0 ); - AddLabel( 45, 60, 0x34, "Command list" ); + AddButton(10, 60, 0xFB7, 0xFB9, 3, GumpButtonType.Reply, 0); + AddLabel(45, 60, 0x34, "Command list"); - AddButton( 10, 85, 0xFB1, 0xFB3, 0, GumpButtonType.Reply, 0 ); - AddLabel( 45, 85, 0x34, "Close" ); - } + AddButton(10, 85, 0xFB1, 0xFB3, 0, GumpButtonType.Reply, 0); + AddLabel(45, 85, 0x34, "Close"); + } - public override void OnResponse( NetState sender, RelayInfo info ) - { - switch ( info.ButtonID ) - { - case 1: // RunUO - { - sender.LaunchBrowser("https://github.com/runuo/"); - break; - } - case 2: // List of skills - { - string[] strings = Enum.GetNames( typeof( SkillName ) ); + public override void OnResponse(NetState sender, RelayInfo info) + { + switch (info.ButtonID) + { + case 1: // RunUO + { + sender.LaunchBrowser("https://github.com/runuo/"); + break; + } + case 2: // List of skills + { + string[] strings = Enum.GetNames(typeof(SkillName)); - Array.Sort( strings ); + Array.Sort(strings); - StringBuilder sb = new StringBuilder(); + StringBuilder sb = new StringBuilder(); - if ( strings.Length > 0 ) - sb.Append( strings[0] ); + if (strings.Length > 0) + sb.Append(strings[0]); - for ( int i = 1; i < strings.Length; ++i ) - { - string v = strings[i]; + for (int i = 1; i < strings.Length; ++i) + { + string v = strings[i]; - if ( (sb.Length + 1 + v.Length) >= 256 ) - { - sender.Send( new AsciiMessage( Server.Serial.MinusOne, -1, MessageType.Label, 0x35, 3, "System", sb.ToString() ) ); - sb = new StringBuilder(); - sb.Append( v ); - } - else - { - sb.Append( ' ' ); - sb.Append( v ); - } - } + if (sb.Length + 1 + v.Length >= 256) + { + sender.Send(new AsciiMessage(Server.Serial.MinusOne, -1, MessageType.Label, 0x35, 3, + "System", sb.ToString())); + sb = new StringBuilder(); + sb.Append(v); + } + else + { + sb.Append(' '); + sb.Append(v); + } + } - if ( sb.Length > 0 ) - { - sender.Send( new AsciiMessage( Server.Serial.MinusOne, -1, MessageType.Label, 0x35, 3, "System", sb.ToString() ) ); - } + if (sb.Length > 0) + sender.Send(new AsciiMessage(Server.Serial.MinusOne, -1, MessageType.Label, 0x35, 3, "System", + sb.ToString())); - break; - } - case 3: // Command list - { - sender.Mobile.SendAsciiMessage( 0x482, "The command prefix is \"{0}\"", CommandSystem.Prefix ); - CommandHandlers.Help_OnCommand( new CommandEventArgs( sender.Mobile, "help", "", new string[0] ) ); + break; + } + case 3: // Command list + { + sender.Mobile.SendAsciiMessage(0x482, "The command prefix is \"{0}\"", CommandSystem.Prefix); + CommandHandlers.Help_OnCommand(new CommandEventArgs(sender.Mobile, "help", "", new string[0])); - break; - } - } - } - } - } -} + break; + } + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Resurrection/ResGate.cs b/Scripts/SpecialSystems/Items/Resurrection/ResGate.cs index d346f78d6..c4d2ebab2 100644 --- a/Scripts/SpecialSystems/Items/Resurrection/ResGate.cs +++ b/Scripts/SpecialSystems/Items/Resurrection/ResGate.cs @@ -2,52 +2,52 @@ using Server.Gumps; namespace Server.Items { - public class ResGate : Item - { - public override string DefaultName => "a resurrection gate"; + public class ResGate : Item + { + [Constructible] + public ResGate() : base(0xF6C) + { + Movable = false; + Hue = 0x2D1; + Light = LightType.Circle300; + } - [Constructible] - public ResGate() : base( 0xF6C ) - { - Movable = false; - Hue = 0x2D1; - Light = LightType.Circle300; - } + public ResGate(Serial serial) : base(serial) + { + } - public ResGate( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a resurrection gate"; - public override bool OnMoveOver( Mobile m ) - { - if ( !m.Alive && m.Map != null && m.Map.CanFit( m.Location, 16, false, false ) ) - { - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + public override bool OnMoveOver(Mobile m) + { + if (!m.Alive && m.Map != null && m.Map.CanFit(m.Location, 16, false, false)) + { + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m ) ); - } - else - { - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m)); + } + else + { + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } - return false; - } + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/AlchemyStone.cs b/Scripts/SpecialSystems/Items/Stones/AlchemyStone.cs index b3a83ced0..70665ce5a 100644 --- a/Scripts/SpecialSystems/Items/Stones/AlchemyStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/AlchemyStone.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class AlchemyStone : Item - { - public override string DefaultName => "an Alchemist Supply Stone"; + public class AlchemyStone : Item + { + [Constructible] + public AlchemyStone() : base(0xED4) + { + Movable = false; + Hue = 0x250; + } - [Constructible] - public AlchemyStone() : base( 0xED4 ) - { - Movable = false; - Hue = 0x250; - } + public AlchemyStone(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - AlchemyBag alcBag = new AlchemyBag(); + public override string DefaultName => "an Alchemist Supply Stone"; - if ( !from.AddToBackpack( alcBag ) ) - alcBag.Delete(); - } + public override void OnDoubleClick(Mobile from) + { + AlchemyBag alcBag = new AlchemyBag(); - public AlchemyStone( Serial serial ) : base( serial ) - { - } + if (!from.AddToBackpack(alcBag)) + alcBag.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/GamblingStone.cs b/Scripts/SpecialSystems/Items/Stones/GamblingStone.cs index 653a7b5d9..ca137d1bd 100644 --- a/Scripts/SpecialSystems/Items/Stones/GamblingStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/GamblingStone.cs @@ -1,126 +1,126 @@ namespace Server.Items { - public class GamblingStone : Item - { - private int m_GamblePot = 2500; + public class GamblingStone : Item + { + private int m_GamblePot = 2500; - [CommandProperty( AccessLevel.GameMaster )] - public int GamblePot - { - get => m_GamblePot; - set - { - m_GamblePot = value; - InvalidateProperties(); - } - } + [Constructible] + public GamblingStone() + : base(0xED4) + { + Movable = false; + Hue = 0x56; + } - public override string DefaultName => "a gambling stone"; + public GamblingStone(Serial serial) + : base(serial) + { + } - [Constructible] - public GamblingStone() - : base( 0xED4 ) - { - Movable = false; - Hue = 0x56; - } + [CommandProperty(AccessLevel.GameMaster)] + public int GamblePot + { + get => m_GamblePot; + set + { + m_GamblePot = value; + InvalidateProperties(); + } + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override string DefaultName => "a gambling stone"; - list.Add( "Jackpot: {0}gp", m_GamblePot ); - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - LabelTo( from, "Jackpot: {0}gp", m_GamblePot ); - } + list.Add("Jackpot: {0}gp", m_GamblePot); + } - public override void OnDoubleClick( Mobile from ) - { - Container pack = from.Backpack; + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + LabelTo(from, "Jackpot: {0}gp", m_GamblePot); + } - if ( pack != null && pack.ConsumeTotal( typeof( Gold ), 250 ) ) - { - m_GamblePot += 150; - InvalidateProperties(); + public override void OnDoubleClick(Mobile from) + { + Container pack = from.Backpack; - int roll = Utility.Random( 1200 ); + if (pack != null && pack.ConsumeTotal(typeof(Gold), 250)) + { + m_GamblePot += 150; + InvalidateProperties(); - if ( roll == 0 ) // Jackpot - { - int maxCheck = 1000000; + int roll = Utility.Random(1200); - from.SendMessage( 0x35, "You win the {0}gp jackpot!", m_GamblePot ); + if (roll == 0) // Jackpot + { + int maxCheck = 1000000; - while( m_GamblePot > maxCheck ) - { - from.AddToBackpack( new BankCheck( maxCheck ) ); + from.SendMessage(0x35, "You win the {0}gp jackpot!", m_GamblePot); - m_GamblePot -= maxCheck; - } + while (m_GamblePot > maxCheck) + { + from.AddToBackpack(new BankCheck(maxCheck)); - from.AddToBackpack( new BankCheck( m_GamblePot ) ); + m_GamblePot -= maxCheck; + } - m_GamblePot = 2500; - } - else if ( roll <= 20 ) // Chance for a regbag - { - from.SendMessage( 0x35, "You win a bag of reagents!" ); - from.AddToBackpack( new BagOfReagents( 50 ) ); - } - else if ( roll <= 40 ) // Chance for gold - { - from.SendMessage( 0x35, "You win 1500gp!" ); - from.AddToBackpack( new BankCheck( 1500 ) ); - } - else if ( roll <= 100 ) // Another chance for gold - { - from.SendMessage( 0x35, "You win 1000gp!" ); - from.AddToBackpack( new BankCheck( 1000 ) ); - } - else // Loser! - { - from.SendMessage( 0x22, "You lose!" ); - } - } - else - { - from.SendMessage( 0x22, "You need at least 250gp in your backpack to use this." ); - } - } + from.AddToBackpack(new BankCheck(m_GamblePot)); - public GamblingStone( Serial serial ) - : base( serial ) - { - } + m_GamblePot = 2500; + } + else if (roll <= 20) // Chance for a regbag + { + from.SendMessage(0x35, "You win a bag of reagents!"); + from.AddToBackpack(new BagOfReagents(50)); + } + else if (roll <= 40) // Chance for gold + { + from.SendMessage(0x35, "You win 1500gp!"); + from.AddToBackpack(new BankCheck(1500)); + } + else if (roll <= 100) // Another chance for gold + { + from.SendMessage(0x35, "You win 1000gp!"); + from.AddToBackpack(new BankCheck(1000)); + } + else // Loser! + { + from.SendMessage(0x22, "You lose!"); + } + } + else + { + from.SendMessage(0x22, "You need at least 250gp in your backpack to use this."); + } + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int)0 ); // version + writer.Write(0); // version - writer.Write( (int)m_GamblePot ); - } + writer.Write(m_GamblePot); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch( version ) - { - case 0: - { - m_GamblePot = reader.ReadInt(); + switch (version) + { + case 0: + { + m_GamblePot = reader.ReadInt(); - break; - } - } - } - } -} + break; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/IngotStone.cs b/Scripts/SpecialSystems/Items/Stones/IngotStone.cs index 74dbb1118..fbe699bae 100644 --- a/Scripts/SpecialSystems/Items/Stones/IngotStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/IngotStone.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class IngotStone : Item - { - public override string DefaultName => "an Ingot stone"; + public class IngotStone : Item + { + [Constructible] + public IngotStone() : base(0xED4) + { + Movable = false; + Hue = 0x480; + } - [Constructible] - public IngotStone() : base( 0xED4 ) - { - Movable = false; - Hue = 0x480; - } + public IngotStone(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - BagOfingots ingotBag = new BagOfingots( 5000 ); + public override string DefaultName => "an Ingot stone"; - if ( !from.AddToBackpack( ingotBag ) ) - ingotBag.Delete(); - } + public override void OnDoubleClick(Mobile from) + { + BagOfingots ingotBag = new BagOfingots(5000); - public IngotStone( Serial serial ) : base( serial ) - { - } + if (!from.AddToBackpack(ingotBag)) + ingotBag.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/RegStone.cs b/Scripts/SpecialSystems/Items/Stones/RegStone.cs index 81d3c3280..123d00da0 100644 --- a/Scripts/SpecialSystems/Items/Stones/RegStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/RegStone.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class RegStone : Item - { - public override string DefaultName => "a reagent stone"; + public class RegStone : Item + { + [Constructible] + public RegStone() : base(0xED4) + { + Movable = false; + Hue = 0x2D1; + } - [Constructible] - public RegStone() : base( 0xED4 ) - { - Movable = false; - Hue = 0x2D1; - } + public RegStone(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - BagOfReagents regBag = new BagOfReagents( 50 ); + public override string DefaultName => "a reagent stone"; - if ( !from.AddToBackpack( regBag ) ) - regBag.Delete(); - } + public override void OnDoubleClick(Mobile from) + { + BagOfReagents regBag = new BagOfReagents(50); - public RegStone( Serial serial ) : base( serial ) - { - } + if (!from.AddToBackpack(regBag)) + regBag.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/ScribeStone.cs b/Scripts/SpecialSystems/Items/Stones/ScribeStone.cs index d6774b82c..9b6000a9a 100644 --- a/Scripts/SpecialSystems/Items/Stones/ScribeStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/ScribeStone.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class ScribeStone : Item - { - public override string DefaultName => "a Scribe Supply Stone"; + public class ScribeStone : Item + { + [Constructible] + public ScribeStone() : base(0xED4) + { + Movable = false; + Hue = 0x105; + } - [Constructible] - public ScribeStone() : base( 0xED4 ) - { - Movable = false; - Hue = 0x105; - } + public ScribeStone(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - ScribeBag scribeBag = new ScribeBag(); + public override string DefaultName => "a Scribe Supply Stone"; - if ( !from.AddToBackpack( scribeBag ) ) - scribeBag.Delete(); - } + public override void OnDoubleClick(Mobile from) + { + ScribeBag scribeBag = new ScribeBag(); - public ScribeStone( Serial serial ) : base( serial ) - { - } + if (!from.AddToBackpack(scribeBag)) + scribeBag.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/SmithStone.cs b/Scripts/SpecialSystems/Items/Stones/SmithStone.cs index 3e4b02636..80152fa68 100644 --- a/Scripts/SpecialSystems/Items/Stones/SmithStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/SmithStone.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class SmithStone : Item - { - public override string DefaultName => "a Blacksmith Supply Stone"; + public class SmithStone : Item + { + [Constructible] + public SmithStone() : base(0xED4) + { + Movable = false; + Hue = 0x476; + } - [Constructible] - public SmithStone() : base( 0xED4 ) - { - Movable = false; - Hue = 0x476; - } + public SmithStone(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - SmithBag SmithBag = new SmithBag( 5000 ); + public override string DefaultName => "a Blacksmith Supply Stone"; - if ( !from.AddToBackpack( SmithBag ) ) - SmithBag.Delete(); - } + public override void OnDoubleClick(Mobile from) + { + SmithBag SmithBag = new SmithBag(5000); - public SmithStone( Serial serial ) : base( serial ) - { - } + if (!from.AddToBackpack(SmithBag)) + SmithBag.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/Stones/TailorStone.cs b/Scripts/SpecialSystems/Items/Stones/TailorStone.cs index f5a805e98..87fb219a0 100644 --- a/Scripts/SpecialSystems/Items/Stones/TailorStone.cs +++ b/Scripts/SpecialSystems/Items/Stones/TailorStone.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class TailorStone : Item - { - public override string DefaultName => "a Tailor Supply Stone"; + public class TailorStone : Item + { + [Constructible] + public TailorStone() : base(0xED4) + { + Movable = false; + Hue = 0x315; + } - [Constructible] - public TailorStone() : base( 0xED4 ) - { - Movable = false; - Hue = 0x315; - } + public TailorStone(Serial serial) : base(serial) + { + } - public override void OnDoubleClick( Mobile from ) - { - TailorBag tailorBag = new TailorBag(); + public override string DefaultName => "a Tailor Supply Stone"; - if ( !from.AddToBackpack( tailorBag ) ) - tailorBag.Delete(); - } + public override void OnDoubleClick(Mobile from) + { + TailorBag tailorBag = new TailorBag(); - public TailorStone( Serial serial ) : base( serial ) - { - } + if (!from.AddToBackpack(tailorBag)) + tailorBag.Delete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/SupplyBags/AlchemyBag.cs b/Scripts/SpecialSystems/Items/SupplyBags/AlchemyBag.cs index bece244cd..2c67ab50b 100644 --- a/Scripts/SpecialSystems/Items/SupplyBags/AlchemyBag.cs +++ b/Scripts/SpecialSystems/Items/SupplyBags/AlchemyBag.cs @@ -1,40 +1,40 @@ namespace Server.Items { - public class AlchemyBag : Bag - { - public override string DefaultName => "an Alchemy Kit"; + public class AlchemyBag : Bag + { + [Constructible] + public AlchemyBag() : this(1) + { + Movable = true; + Hue = 0x250; + } - [Constructible] - public AlchemyBag() : this( 1 ) - { - Movable = true; - Hue = 0x250; - } + [Constructible] + public AlchemyBag(int amount) + { + DropItem(new MortarPestle(5)); + DropItem(new BagOfReagents(5000)); + DropItem(new Bottle(5000)); + } - [Constructible] - public AlchemyBag( int amount ) - { - DropItem( new MortarPestle( 5 ) ); - DropItem( new BagOfReagents( 5000 ) ); - DropItem( new Bottle( 5000 ) ); - } + public AlchemyBag(Serial serial) : base(serial) + { + } - public AlchemyBag( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "an Alchemy Kit"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/SupplyBags/BagOfIngots.cs b/Scripts/SpecialSystems/Items/SupplyBags/BagOfIngots.cs index 4937ca6e0..0122384c0 100644 --- a/Scripts/SpecialSystems/Items/SupplyBags/BagOfIngots.cs +++ b/Scripts/SpecialSystems/Items/SupplyBags/BagOfIngots.cs @@ -1,45 +1,44 @@ -namespace Server.Items -{ - public class BagOfingots : Bag - { - [Constructible] - public BagOfingots() : this( 5000 ) - { - } +namespace Server.Items +{ + public class BagOfingots : Bag + { + [Constructible] + public BagOfingots() : this(5000) + { + } - [Constructible] - public BagOfingots( int amount ) - { - DropItem( new DullCopperIngot ( amount ) ); - DropItem( new ShadowIronIngot ( amount ) ); - DropItem( new CopperIngot ( amount ) ); - DropItem( new BronzeIngot ( amount ) ); - DropItem( new GoldIngot ( amount ) ); - DropItem( new AgapiteIngot ( amount ) ); - DropItem( new VeriteIngot ( amount ) ); - DropItem( new ValoriteIngot ( amount ) ); - DropItem( new IronIngot ( amount ) ); - DropItem( new Tongs() ); - DropItem( new TinkerTools() ); + [Constructible] + public BagOfingots(int amount) + { + DropItem(new DullCopperIngot(amount)); + DropItem(new ShadowIronIngot(amount)); + DropItem(new CopperIngot(amount)); + DropItem(new BronzeIngot(amount)); + DropItem(new GoldIngot(amount)); + DropItem(new AgapiteIngot(amount)); + DropItem(new VeriteIngot(amount)); + DropItem(new ValoriteIngot(amount)); + DropItem(new IronIngot(amount)); + DropItem(new Tongs()); + DropItem(new TinkerTools()); + } - } + public BagOfingots(Serial serial) : base(serial) + { + } - public BagOfingots( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/SupplyBags/ScribeBag.cs b/Scripts/SpecialSystems/Items/SupplyBags/ScribeBag.cs index 7f232f5f7..68bf9606b 100644 --- a/Scripts/SpecialSystems/Items/SupplyBags/ScribeBag.cs +++ b/Scripts/SpecialSystems/Items/SupplyBags/ScribeBag.cs @@ -1,39 +1,39 @@ namespace Server.Items { - public class ScribeBag : Bag - { - public override string DefaultName => "a Scribe Kit"; + public class ScribeBag : Bag + { + [Constructible] + public ScribeBag() : this(1) + { + Movable = true; + Hue = 0x105; + } - [Constructible] - public ScribeBag() : this( 1 ) - { - Movable = true; - Hue = 0x105; - } + [Constructible] + public ScribeBag(int amount) + { + DropItem(new BagOfReagents(5000)); + DropItem(new BlankScroll(500)); + } - [Constructible] - public ScribeBag( int amount ) - { - DropItem( new BagOfReagents( 5000 ) ); - DropItem( new BlankScroll( 500 ) ); - } + public ScribeBag(Serial serial) : base(serial) + { + } - public ScribeBag( Serial serial ) : base( serial ) - { - } + public override string DefaultName => "a Scribe Kit"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/SupplyBags/SmithBag.cs b/Scripts/SpecialSystems/Items/SupplyBags/SmithBag.cs index 1004b0013..77689763f 100644 --- a/Scripts/SpecialSystems/Items/SupplyBags/SmithBag.cs +++ b/Scripts/SpecialSystems/Items/SupplyBags/SmithBag.cs @@ -1,45 +1,44 @@ namespace Server.Items -{ - public class SmithBag : Bag - { - [Constructible] - public SmithBag() : this( 5000 ) - { - } +{ + public class SmithBag : Bag + { + [Constructible] + public SmithBag() : this(5000) + { + } - [Constructible] - public SmithBag( int amount ) - { - DropItem( new DullCopperIngot ( amount ) ); - DropItem( new ShadowIronIngot ( amount ) ); - DropItem( new CopperIngot ( amount ) ); - DropItem( new BronzeIngot ( amount ) ); - DropItem( new GoldIngot ( amount ) ); - DropItem( new AgapiteIngot ( amount ) ); - DropItem( new VeriteIngot ( amount ) ); - DropItem( new ValoriteIngot ( amount ) ); - DropItem( new IronIngot ( amount ) ); - DropItem( new Tongs ( amount ) ); - DropItem( new TinkerTools ( amount ) ); + [Constructible] + public SmithBag(int amount) + { + DropItem(new DullCopperIngot(amount)); + DropItem(new ShadowIronIngot(amount)); + DropItem(new CopperIngot(amount)); + DropItem(new BronzeIngot(amount)); + DropItem(new GoldIngot(amount)); + DropItem(new AgapiteIngot(amount)); + DropItem(new VeriteIngot(amount)); + DropItem(new ValoriteIngot(amount)); + DropItem(new IronIngot(amount)); + DropItem(new Tongs(amount)); + DropItem(new TinkerTools(amount)); + } - } + public SmithBag(Serial serial) : base(serial) + { + } - public SmithBag( Serial serial ) : base( serial ) - { - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + writer.Write(0); // version + } - writer.Write( (int) 0 ); // version - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - } - } -} + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/SpecialSystems/Items/SupplyBags/TailorBag.cs b/Scripts/SpecialSystems/Items/SupplyBags/TailorBag.cs index 48ff12ae5..38d38612a 100644 --- a/Scripts/SpecialSystems/Items/SupplyBags/TailorBag.cs +++ b/Scripts/SpecialSystems/Items/SupplyBags/TailorBag.cs @@ -1,45 +1,45 @@ namespace Server.Items { - public class TailorBag : Bag - { - public override string DefaultName => "a Tailoring Kit"; + public class TailorBag : Bag + { + [Constructible] + public TailorBag() : this(1) + { + Movable = true; + Hue = 0x315; + } - [Constructible] - public TailorBag() : this( 1 ) - { - Movable = true; - Hue = 0x315; - } + [Constructible] + public TailorBag(int amount) + { + DropItem(new SewingKit(5)); + DropItem(new Scissors()); + DropItem(new Hides(500)); + DropItem(new BoltOfCloth(20)); + DropItem(new DyeTub()); + DropItem(new DyeTub()); + DropItem(new BlackDyeTub()); + DropItem(new Dyes()); + } - [Constructible] - public TailorBag( int amount ) - { - DropItem( new SewingKit( 5 ) ); - DropItem( new Scissors() ); - DropItem( new Hides( 500 ) ); - DropItem( new BoltOfCloth( 20 ) ); - DropItem( new DyeTub() ); - DropItem( new DyeTub() ); - DropItem( new BlackDyeTub() ); - DropItem( new Dyes() ); - } - - public TailorBag( Serial serial ) : base( serial ) - { - } + public TailorBag(Serial serial) : base(serial) + { + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override string DefaultName => "a Tailoring Kit"; - writer.Write( (int) 0 ); // version - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version + } - int version = reader.ReadInt(); - } - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Scripts/Spells/Base/DisturbType.cs b/Scripts/Spells/Base/DisturbType.cs index b89d18a6c..e91d3eca9 100644 --- a/Scripts/Spells/Base/DisturbType.cs +++ b/Scripts/Spells/Base/DisturbType.cs @@ -1,12 +1,12 @@ namespace Server.Spells { - public enum DisturbType - { - Unspecified, - EquipRequest, - UseRequest, - Hurt, - Kill, - NewCast - } + public enum DisturbType + { + Unspecified, + EquipRequest, + UseRequest, + Hurt, + Kill, + NewCast + } } \ No newline at end of file diff --git a/Scripts/Spells/Base/MagerySpell.cs b/Scripts/Spells/Base/MagerySpell.cs index 93f6f7edb..4f7aa9af0 100644 --- a/Scripts/Spells/Base/MagerySpell.cs +++ b/Scripts/Spells/Base/MagerySpell.cs @@ -3,107 +3,109 @@ using Server.Items; namespace Server.Spells { - public abstract class MagerySpell : Spell - { - public MagerySpell( Mobile caster, Item scroll, SpellInfo info ) - : base( caster, scroll, info ) - { - } + public abstract class MagerySpell : Spell + { + private const double ChanceOffset = 20.0, ChanceLength = 100.0 / 7.0; - public abstract SpellCircle Circle { get; } + private static int[] m_ManaTable = { 4, 6, 9, 11, 14, 20, 40, 50 }; - public override bool ConsumeReagents() - { - if ( base.ConsumeReagents() ) - return true; + public MagerySpell(Mobile caster, Item scroll, SpellInfo info) + : base(caster, scroll, info) + { + } - if ( ArcaneGem.ConsumeCharges( Caster, (Core.SE ? 1 : 1 + (int)Circle) ) ) - return true; + public abstract SpellCircle Circle{ get; } - return false; - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds((3 + (int)Circle) * CastDelaySecondsPerTick); - private const double ChanceOffset = 20.0, ChanceLength = 100.0 / 7.0; + public override bool ConsumeReagents() + { + if (base.ConsumeReagents()) + return true; - public override void GetCastSkills( out double min, out double max ) - { - int circle = (int)Circle; + if (ArcaneGem.ConsumeCharges(Caster, Core.SE ? 1 : 1 + (int)Circle)) + return true; - if ( Scroll != null ) - circle -= 2; + return false; + } - double avg = ChanceLength * circle; + public override void GetCastSkills(out double min, out double max) + { + int circle = (int)Circle; - min = avg - ChanceOffset; - max = avg + ChanceOffset; - } + if (Scroll != null) + circle -= 2; - private static int[] m_ManaTable = { 4, 6, 9, 11, 14, 20, 40, 50 }; + double avg = ChanceLength * circle; - public override int GetMana() - { - if ( Scroll is BaseWand ) - return 0; + min = avg - ChanceOffset; + max = avg + ChanceOffset; + } - return m_ManaTable[(int)Circle]; - } + public override int GetMana() + { + if (Scroll is BaseWand) + return 0; - public override double GetResistSkill( Mobile m ) - { - int maxSkill = (1 + (int)Circle) * 10; - maxSkill += (1 + ((int)Circle / 6)) * 25; + return m_ManaTable[(int)Circle]; + } - if ( m.Skills[SkillName.MagicResist].Value < maxSkill ) - m.CheckSkill( SkillName.MagicResist, 0.0, m.Skills[SkillName.MagicResist].Cap ); + public override double GetResistSkill(Mobile m) + { + int maxSkill = (1 + (int)Circle) * 10; + maxSkill += (1 + (int)Circle / 6) * 25; - return m.Skills[SkillName.MagicResist].Value; - } + if (m.Skills[SkillName.MagicResist].Value < maxSkill) + m.CheckSkill(SkillName.MagicResist, 0.0, m.Skills[SkillName.MagicResist].Cap); - public virtual bool CheckResisted( Mobile target ) - { - double n = GetResistPercent( target ); + return m.Skills[SkillName.MagicResist].Value; + } - n /= 100.0; + public virtual bool CheckResisted(Mobile target) + { + double n = GetResistPercent(target); - if ( n <= 0.0 ) - return false; + n /= 100.0; - if ( n >= 1.0 ) - return true; + if (n <= 0.0) + return false; - int maxSkill = (1 + (int)Circle) * 10; - maxSkill += (1 + ((int)Circle / 6)) * 25; + if (n >= 1.0) + return true; - if ( target.Skills[SkillName.MagicResist].Value < maxSkill ) - target.CheckSkill( SkillName.MagicResist, 0.0, target.Skills[SkillName.MagicResist].Cap ); + int maxSkill = (1 + (int)Circle) * 10; + maxSkill += (1 + (int)Circle / 6) * 25; - return (n >= Utility.RandomDouble()); - } + if (target.Skills[SkillName.MagicResist].Value < maxSkill) + target.CheckSkill(SkillName.MagicResist, 0.0, target.Skills[SkillName.MagicResist].Cap); - public virtual double GetResistPercentForCircle( Mobile target, SpellCircle circle ) - { - double firstPercent = target.Skills[SkillName.MagicResist].Value / 5.0; - double secondPercent = target.Skills[SkillName.MagicResist].Value - (((Caster.Skills[CastSkill].Value - 20.0) / 5.0) + (1 + (int)circle) * 5.0); + return n >= Utility.RandomDouble(); + } - return (firstPercent > secondPercent ? firstPercent : secondPercent) / 2.0; // Seems should be about half of what stratics says. - } + public virtual double GetResistPercentForCircle(Mobile target, SpellCircle circle) + { + double firstPercent = target.Skills[SkillName.MagicResist].Value / 5.0; + double secondPercent = target.Skills[SkillName.MagicResist].Value - + ((Caster.Skills[CastSkill].Value - 20.0) / 5.0 + (1 + (int)circle) * 5.0); - public virtual double GetResistPercent( Mobile target ) - { - return GetResistPercentForCircle( target, Circle ); - } + return (firstPercent > secondPercent ? firstPercent : secondPercent) / + 2.0; // Seems should be about half of what stratics says. + } - public override TimeSpan GetCastDelay() - { - if ( !Core.ML && Scroll is BaseWand ) - return TimeSpan.Zero; + public virtual double GetResistPercent(Mobile target) + { + return GetResistPercentForCircle(target, Circle); + } - if ( !Core.AOS ) - return TimeSpan.FromSeconds( 0.5 + (0.25 * (int)Circle) ); + public override TimeSpan GetCastDelay() + { + if (!Core.ML && Scroll is BaseWand) + return TimeSpan.Zero; - return base.GetCastDelay(); - } + if (!Core.AOS) + return TimeSpan.FromSeconds(0.5 + 0.25 * (int)Circle); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( (3 + (int)Circle) * CastDelaySecondsPerTick ); - } -} + return base.GetCastDelay(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Base/SpecialMove.cs b/Scripts/Spells/Base/SpecialMove.cs index 6ab4efa53..3c6beb11f 100644 --- a/Scripts/Spells/Base/SpecialMove.cs +++ b/Scripts/Spells/Base/SpecialMove.cs @@ -1,353 +1,352 @@ using System; using System.Collections.Generic; +using Server.Engines.ConPVP; using Server.Items; using Server.Network; -using Server.Spells.Ninjitsu; using Server.Spells.Bushido; +using Server.Spells.Necromancy; +using Server.Spells.Ninjitsu; namespace Server.Spells { - public abstract class SpecialMove - { - public virtual int BaseMana => 0; - - public virtual SkillName MoveSkill => SkillName.Bushido; - public virtual double RequiredSkill => 0.0; - - public virtual TextDefinition AbilityMessage => 0; - - public virtual bool BlockedByAnimalForm => true; - public virtual bool DelayedContext => false; - - public virtual int GetAccuracyBonus( Mobile attacker ) - { - return 0; - } - - public virtual double GetDamageScalar( Mobile attacker, Mobile defender ) - { - return 1.0; - } - - // Called before swinging, to make sure the accuracy scalar is to be computed. - public virtual bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - return true; - } - - // Called when a hit connects, but before damage is calculated. - public virtual bool OnBeforeDamage( Mobile attacker, Mobile defender ) - { - return true; - } - - // Called as soon as the ability is used. - public virtual void OnUse( Mobile from ) - { - } - - // Called when a hit connects, at the end of the weapon.OnHit() method. - public virtual void OnHit( Mobile attacker, Mobile defender, int damage ) - { - } - - // Called when a hit misses. - public virtual void OnMiss( Mobile attacker, Mobile defender ) - { - } - - // Called when the move is cleared. - public virtual void OnClearMove( Mobile from ) - { - } - - public virtual bool IgnoreArmor( Mobile attacker ) - { - return false; - } - - public virtual double GetPropertyBonus( Mobile attacker ) - { - return 1.0; - } - - public virtual bool CheckSkills( Mobile m ) - { - if ( m.Skills[MoveSkill].Value < RequiredSkill ) - { - string args = $"{RequiredSkill.ToString("F1")}\t{MoveSkill.ToString()}\t "; - m.SendLocalizedMessage( 1063013, args ); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - return false; - } - - return true; - } - - public virtual int ScaleMana( Mobile m, int mana ) - { - double scalar = 1.0; - - if ( !Necromancy.MindRotSpell.GetMindRotScalar( m, ref scalar ) ) - scalar = 1.0; - - // Lower Mana Cost = 40% - int lmc = Math.Min( AosAttributes.GetValue( m, AosAttribute.LowerManaCost ), 40 ); - - scalar -= (double)lmc / 100; - - int total = (int)(mana * scalar); - - if ( m.Skills[MoveSkill].Value < 50.0 && GetContext( m ) != null ) - total *= 2; - - return total; - } - - public virtual bool CheckMana( Mobile from, bool consume ) - { - int mana = ScaleMana( from, BaseMana ); - - if ( from.Mana < mana ) - { - from.SendLocalizedMessage( 1060181, mana.ToString() ); // You need ~1_MANA_REQUIREMENT~ mana to perform that attack - return false; - } - - if ( consume ) - { - if ( !DelayedContext ) - SetContext( from ); - - from.Mana -= mana; - } - - return true; - } - - public virtual void SetContext( Mobile from ) - { - if ( GetContext( from ) == null ) - { - if ( DelayedContext || from.Skills[MoveSkill].Value < 50.0 ) - { - Timer timer = new SpecialMoveTimer( from ); - timer.Start(); - - AddContext( from, new SpecialMoveContext( timer, GetType() ) ); - } - } - } - - public virtual bool Validate( Mobile from ) - { - if ( !from.Player ) - return true; - - if ( HonorableExecution.IsUnderPenalty( from ) ) - { - from.SendLocalizedMessage( 1063024 ); // You cannot perform this special move right now. - return false; - } - - if ( AnimalForm.UnderTransformation( from ) ) - { - from.SendLocalizedMessage( 1063024 ); // You cannot perform this special move right now. - return false; - } - - #region Dueling - string option = null; - - if ( this is Backstab ) - option = "Backstab"; - else if ( this is DeathStrike ) - option = "Death Strike"; - else if ( this is FocusAttack ) - option = "Focus Attack"; - else if ( this is KiAttack ) - option = "Ki Attack"; - else if ( this is SurpriseAttack ) - option = "Surprise Attack"; - else if ( this is HonorableExecution ) - option = "Honorable Execution"; - else if ( this is LightningStrike ) - option = "Lightning Strike"; - else if ( this is MomentumStrike ) - option = "Momentum Strike"; - - if ( option != null && !Engines.ConPVP.DuelContext.AllowSpecialMove( from, option, this ) ) - return false; - #endregion - - return CheckSkills( from ) && CheckMana( from, false ); - } - - public virtual void CheckGain( Mobile m ) - { - m.CheckSkill( MoveSkill, RequiredSkill, RequiredSkill + 37.5 ); - } + public abstract class SpecialMove + { + private static Dictionary m_PlayersTable = new Dictionary(); - public static Dictionary Table { get; } = new Dictionary(); + public virtual int BaseMana => 0; - public static void ClearAllMoves( Mobile m ) - { - foreach ( KeyValuePair kvp in SpellRegistry.SpecialMoves ) - { - int moveID = kvp.Key; - - if ( moveID != -1 ) - m.Send( new ToggleSpecialAbility( moveID + 1, false ) ); - } - } - - public virtual bool ValidatesDuringHit => true; - - public static SpecialMove GetCurrentMove( Mobile m ) - { - if ( m == null ) - return null; - - if ( !Core.SE ) - { - ClearCurrentMove( m ); - return null; - } - - Table.TryGetValue( m, out SpecialMove move ); - - if ( move != null && move.ValidatesDuringHit && !move.Validate( m ) ) - { - ClearCurrentMove( m ); - return null; - } - - return move; - } - - public static bool SetCurrentMove( Mobile m, SpecialMove move ) - { - if ( !Core.SE ) - { - ClearCurrentMove( m ); - return false; - } + public virtual SkillName MoveSkill => SkillName.Bushido; + public virtual double RequiredSkill => 0.0; - if ( move != null && !move.Validate( m ) ) - { - ClearCurrentMove( m ); - return false; - } + public virtual TextDefinition AbilityMessage => 0; - bool sameMove = ( move == GetCurrentMove( m ) ); - - ClearCurrentMove( m ); + public virtual bool BlockedByAnimalForm => true; + public virtual bool DelayedContext => false; - if ( sameMove ) - return true; + public static Dictionary Table{ get; } = new Dictionary(); + + public virtual bool ValidatesDuringHit => true; + + public virtual int GetAccuracyBonus(Mobile attacker) + { + return 0; + } - if ( move != null ) - { - WeaponAbility.ClearCurrentAbility( m ); + public virtual double GetDamageScalar(Mobile attacker, Mobile defender) + { + return 1.0; + } + + // Called before swinging, to make sure the accuracy scalar is to be computed. + public virtual bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + return true; + } + + // Called when a hit connects, but before damage is calculated. + public virtual bool OnBeforeDamage(Mobile attacker, Mobile defender) + { + return true; + } + + // Called as soon as the ability is used. + public virtual void OnUse(Mobile from) + { + } + + // Called when a hit connects, at the end of the weapon.OnHit() method. + public virtual void OnHit(Mobile attacker, Mobile defender, int damage) + { + } + + // Called when a hit misses. + public virtual void OnMiss(Mobile attacker, Mobile defender) + { + } + + // Called when the move is cleared. + public virtual void OnClearMove(Mobile from) + { + } + + public virtual bool IgnoreArmor(Mobile attacker) + { + return false; + } + + public virtual double GetPropertyBonus(Mobile attacker) + { + return 1.0; + } + + public virtual bool CheckSkills(Mobile m) + { + if (m.Skills[MoveSkill].Value < RequiredSkill) + { + string args = $"{RequiredSkill.ToString("F1")}\t{MoveSkill.ToString()}\t "; + m.SendLocalizedMessage(1063013, + args); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + return false; + } + + return true; + } + + public virtual int ScaleMana(Mobile m, int mana) + { + double scalar = 1.0; + + if (!MindRotSpell.GetMindRotScalar(m, ref scalar)) + scalar = 1.0; + + // Lower Mana Cost = 40% + int lmc = Math.Min(AosAttributes.GetValue(m, AosAttribute.LowerManaCost), 40); + + scalar -= (double)lmc / 100; + + int total = (int)(mana * scalar); + + if (m.Skills[MoveSkill].Value < 50.0 && GetContext(m) != null) + total *= 2; + + return total; + } + + public virtual bool CheckMana(Mobile from, bool consume) + { + int mana = ScaleMana(from, BaseMana); + + if (from.Mana < mana) + { + from.SendLocalizedMessage(1060181, + mana.ToString()); // You need ~1_MANA_REQUIREMENT~ mana to perform that attack + return false; + } + + if (consume) + { + if (!DelayedContext) + SetContext(from); + + from.Mana -= mana; + } + + return true; + } + + public virtual void SetContext(Mobile from) + { + if (GetContext(from) == null) + if (DelayedContext || from.Skills[MoveSkill].Value < 50.0) + { + Timer timer = new SpecialMoveTimer(from); + timer.Start(); + + AddContext(from, new SpecialMoveContext(timer, GetType())); + } + } + + public virtual bool Validate(Mobile from) + { + if (!from.Player) + return true; + + if (HonorableExecution.IsUnderPenalty(from)) + { + from.SendLocalizedMessage(1063024); // You cannot perform this special move right now. + return false; + } + + if (AnimalForm.UnderTransformation(from)) + { + from.SendLocalizedMessage(1063024); // You cannot perform this special move right now. + return false; + } + + #region Dueling + + string option = null; + + if (this is Backstab) + option = "Backstab"; + else if (this is DeathStrike) + option = "Death Strike"; + else if (this is FocusAttack) + option = "Focus Attack"; + else if (this is KiAttack) + option = "Ki Attack"; + else if (this is SurpriseAttack) + option = "Surprise Attack"; + else if (this is HonorableExecution) + option = "Honorable Execution"; + else if (this is LightningStrike) + option = "Lightning Strike"; + else if (this is MomentumStrike) + option = "Momentum Strike"; + + if (option != null && !DuelContext.AllowSpecialMove(from, option, this)) + return false; - Table[m] = move; - - move.OnUse( m ); + #endregion - int moveID = SpellRegistry.GetRegistryNumber( move ); + return CheckSkills(from) && CheckMana(from, false); + } - if ( moveID > 0 ) - m.Send( new ToggleSpecialAbility( moveID + 1, true ) ); + public virtual void CheckGain(Mobile m) + { + m.CheckSkill(MoveSkill, RequiredSkill, RequiredSkill + 37.5); + } + + public static void ClearAllMoves(Mobile m) + { + foreach (KeyValuePair kvp in SpellRegistry.SpecialMoves) + { + int moveID = kvp.Key; + + if (moveID != -1) + m.Send(new ToggleSpecialAbility(moveID + 1, false)); + } + } + + public static SpecialMove GetCurrentMove(Mobile m) + { + if (m == null) + return null; + + if (!Core.SE) + { + ClearCurrentMove(m); + return null; + } + + Table.TryGetValue(m, out SpecialMove move); + + if (move != null && move.ValidatesDuringHit && !move.Validate(m)) + { + ClearCurrentMove(m); + return null; + } + + return move; + } + + public static bool SetCurrentMove(Mobile m, SpecialMove move) + { + if (!Core.SE) + { + ClearCurrentMove(m); + return false; + } + + if (move != null && !move.Validate(m)) + { + ClearCurrentMove(m); + return false; + } + + bool sameMove = move == GetCurrentMove(m); + + ClearCurrentMove(m); + + if (sameMove) + return true; + + if (move != null) + { + WeaponAbility.ClearCurrentAbility(m); + + Table[m] = move; + + move.OnUse(m); + + int moveID = SpellRegistry.GetRegistryNumber(move); + + if (moveID > 0) + m.Send(new ToggleSpecialAbility(moveID + 1, true)); + + TextDefinition.SendMessageTo(m, move.AbilityMessage); + } + + return true; + } + + public static void ClearCurrentMove(Mobile m) + { + Table.TryGetValue(m, out SpecialMove move); + + if (move != null) + { + move.OnClearMove(m); - TextDefinition.SendMessageTo( m, move.AbilityMessage ); - } + int moveID = SpellRegistry.GetRegistryNumber(move); - return true; - } + if (moveID > 0) + m.Send(new ToggleSpecialAbility(moveID + 1, false)); + } - public static void ClearCurrentMove( Mobile m ) - { - Table.TryGetValue( m, out SpecialMove move ); + Table.Remove(m); + } - if ( move != null ) - { - move.OnClearMove( m ); + private static void AddContext(Mobile m, SpecialMoveContext context) + { + m_PlayersTable[m] = context; + } - int moveID = SpellRegistry.GetRegistryNumber( move ); + private static void RemoveContext(Mobile m) + { + SpecialMoveContext context = GetContext(m); - if ( moveID > 0 ) - m.Send( new ToggleSpecialAbility( moveID + 1, false ) ); - } + if (context != null) + { + m_PlayersTable.Remove(m); - Table.Remove( m ); - } + context.Timer.Stop(); + } + } - public SpecialMove() - { - } + private static SpecialMoveContext GetContext(Mobile m) + { + return m_PlayersTable.ContainsKey(m) ? m_PlayersTable[m] : null; + } + public static bool GetContext(Mobile m, Type type) + { + m_PlayersTable.TryGetValue(m, out SpecialMoveContext context); - private static Dictionary m_PlayersTable = new Dictionary(); + if (context == null) + return false; - private static void AddContext( Mobile m, SpecialMoveContext context ) - { - m_PlayersTable[m] = context; - } + return context.Type == type; + } - private static void RemoveContext( Mobile m ) - { - SpecialMoveContext context = GetContext( m ); + private class SpecialMoveTimer : Timer + { + private Mobile m_Mobile; - if ( context != null ) - { - m_PlayersTable.Remove( m ); + public SpecialMoveTimer(Mobile from) : base(TimeSpan.FromSeconds(3.0)) + { + m_Mobile = from; - context.Timer.Stop(); - } - } + Priority = TimerPriority.TwentyFiveMS; + } - private static SpecialMoveContext GetContext( Mobile m ) - { - return ( m_PlayersTable.ContainsKey( m ) ? m_PlayersTable[m] : null ); - } + protected override void OnTick() + { + RemoveContext(m_Mobile); + } + } - public static bool GetContext( Mobile m, Type type ) - { - m_PlayersTable.TryGetValue( m, out SpecialMoveContext context ); + public class SpecialMoveContext + { + public SpecialMoveContext(Timer timer, Type type) + { + Timer = timer; + Type = type; + } - if ( context == null ) - return false; + public Timer Timer{ get; } - return ( context.Type == type ); - } - - private class SpecialMoveTimer : Timer - { - private Mobile m_Mobile; - - public SpecialMoveTimer( Mobile from ) : base ( TimeSpan.FromSeconds( 3.0 ) ) - { - m_Mobile = from; - - Priority = TimerPriority.TwentyFiveMS; - } - - protected override void OnTick() - { - RemoveContext( m_Mobile ); - } - } - - public class SpecialMoveContext - { - public Timer Timer { get; } - - public Type Type { get; } - - public SpecialMoveContext( Timer timer, Type type ) - { - Timer = timer; - Type = type; - } - } - } -} + public Type Type{ get; } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Base/Spell.cs b/Scripts/Spells/Base/Spell.cs index 7d6f5d128..4eb16b535 100644 --- a/Scripts/Spells/Base/Spell.cs +++ b/Scripts/Spells/Base/Spell.cs @@ -1,915 +1,929 @@ using System; +using System.Collections.Generic; +using Server.Engines.ConPVP; using Server.Items; -using Server.Network; -using Server.Targeting; +using Server.Misc; using Server.Mobiles; -using Server.Spells.Second; +using Server.Network; +using Server.Spells.Bushido; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; -using System.Collections.Generic; +using Server.Spells.Second; using Server.Spells.Spellweaving; -using Server.Spells.Bushido; +using Server.Targeting; namespace Server.Spells { - public abstract class Spell : ISpell - { - public SpellState State { get; set; } - - public Mobile Caster { get; } - - public SpellInfo Info { get; } - - public string Name => Info.Name; - public string Mantra => Info.Mantra; - public Type[] Reagents => Info.Reagents; - public Item Scroll { get; } - - public long StartCastTime { get; private set; } - - private static TimeSpan NextSpellDelay = TimeSpan.FromSeconds( 0.75 ); - private static TimeSpan AnimateDelay = TimeSpan.FromSeconds( 1.5 ); - - public virtual SkillName CastSkill => SkillName.Magery; - public virtual SkillName DamageSkill => SkillName.EvalInt; - - public virtual bool RevealOnCast => true; - public virtual bool ClearHandsOnCast => true; - public virtual bool ShowHandMovement => true; - - public virtual bool DelayedDamage => false; + public abstract class Spell : ISpell + { + private static TimeSpan NextSpellDelay = TimeSpan.FromSeconds(0.75); - public virtual bool DelayedDamageStacking => true; - //In reality, it's ANY delayed Damage spell Post-AoS that can't stack, but, only - //Expo & Magic Arrow have enough delay and a short enough cast time to bring up - //the possibility of stacking 'em. Note that a MA & an Explosion will stack, but - //of course, two MA's won't. + private static TimeSpan AnimateDelay = TimeSpan.FromSeconds(1.5); + //In reality, it's ANY delayed Damage spell Post-AoS that can't stack, but, only + //Expo & Magic Arrow have enough delay and a short enough cast time to bring up + //the possibility of stacking 'em. Note that a MA & an Explosion will stack, but + //of course, two MA's won't. - private static Dictionary m_ContextTable = new Dictionary(); + private static Dictionary m_ContextTable = + new Dictionary(); - private class DelayedDamageContextWrapper - { - private Dictionary m_Contexts = new Dictionary(); + private AnimTimer m_AnimTimer; - public void Add( Mobile m, Timer t ) - { - if (m_Contexts.TryGetValue( m, out Timer oldTimer )) - { - oldTimer.Stop(); - m_Contexts.Remove( m ); - } + private CastTimer m_CastTimer; - m_Contexts.Add( m, t ); - } + public Spell(Mobile caster, Item scroll, SpellInfo info) + { + Caster = caster; + Scroll = scroll; + Info = info; + } - public void Remove( Mobile m ) - { - m_Contexts.Remove( m ); - } - } + public SpellState State{ get; set; } - public void StartDelayedDamageContext( Mobile m, Timer t ) - { - if ( DelayedDamageStacking ) - return; //Sanity + public Mobile Caster{ get; } - if (!m_ContextTable.TryGetValue( GetType(), out DelayedDamageContextWrapper contexts )) - { - contexts = new DelayedDamageContextWrapper(); - m_ContextTable.Add( GetType(), contexts ); - } + public SpellInfo Info{ get; } - contexts.Add( m, t ); - } + public string Name => Info.Name; + public string Mantra => Info.Mantra; + public Type[] Reagents => Info.Reagents; + public Item Scroll{ get; } - public void RemoveDelayedDamageContext( Mobile m ) - { - if (!m_ContextTable.TryGetValue( GetType(), out DelayedDamageContextWrapper contexts )) - return; + public long StartCastTime{ get; private set; } - contexts.Remove( m ); - } + public virtual SkillName CastSkill => SkillName.Magery; + public virtual SkillName DamageSkill => SkillName.EvalInt; - public void HarmfulSpell( Mobile m ) - { - (m as BaseCreature)?.OnHarmfulSpell( Caster ); - } + public virtual bool RevealOnCast => true; + public virtual bool ClearHandsOnCast => true; + public virtual bool ShowHandMovement => true; - public Spell( Mobile caster, Item scroll, SpellInfo info ) - { - Caster = caster; - Scroll = scroll; - Info = info; - } - - public virtual int GetNewAosDamage( int bonus, int dice, int sides, Mobile singleTarget ) - { - if ( singleTarget != null ) - { - return GetNewAosDamage( bonus, dice, sides, (Caster.Player && singleTarget.Player), GetDamageScalar( singleTarget ) ); - } - - return GetNewAosDamage( bonus, dice, sides, false ); - } - - public virtual int GetNewAosDamage( int bonus, int dice, int sides, bool playerVsPlayer ) - { - return GetNewAosDamage( bonus, dice, sides, playerVsPlayer, 1.0 ); - } - - public virtual int GetNewAosDamage( int bonus, int dice, int sides, bool playerVsPlayer, double scalar ) - { - int damage = Utility.Dice( dice, sides, bonus ) * 100; - int damageBonus = 0; - - int inscribeSkill = GetInscribeFixed( Caster ); - int inscribeBonus = (inscribeSkill + (1000 * (inscribeSkill / 1000))) / 200; - damageBonus += inscribeBonus; - - int intBonus = Caster.Int / 10; - damageBonus += intBonus; - - int sdiBonus = AosAttributes.GetValue( Caster, AosAttribute.SpellDamage ); - // PvP spell damage increase cap of 15% from an item�s magic property - if ( playerVsPlayer && sdiBonus > 15 ) - sdiBonus = 15; - - damageBonus += sdiBonus; - - TransformContext context = TransformationSpellHelper.GetContext( Caster ); - - if ( context?.Spell is ReaperFormSpell ) - damageBonus += ((ReaperFormSpell)context.Spell).SpellDamageBonus; - - damage = AOS.Scale( damage, 100 + damageBonus ); - - int evalSkill = GetDamageFixed( Caster ); - int evalScale = 30 + ((9 * evalSkill) / 100); - - damage = AOS.Scale( damage, evalScale ); - - damage = AOS.Scale( damage, (int)(scalar*100) ); - - return damage / 100; - } - - public virtual bool IsCasting => State == SpellState.Casting; - - public virtual void OnCasterHurt() - { - //Confirm: Monsters and pets cannot be disturbed. - if ( !Caster.Player ) - return; + public virtual bool DelayedDamage => false; - if ( IsCasting ) - { - object o = ProtectionSpell.Registry[Caster]; - bool disturb = true; + public virtual bool DelayedDamageStacking => true; - if ( o is double ) - { - if ( ((double)o) > Utility.RandomDouble()*100.0 ) - disturb = false; - } + public virtual bool BlockedByHorrificBeast => true; + public virtual bool BlockedByAnimalForm => true; + public virtual bool BlocksMovement => true; - if ( disturb ) - Disturb( DisturbType.Hurt, false, true ); - } - } + public virtual bool CheckNextSpellTime => !(Scroll is BaseWand); - public virtual void OnCasterKilled() - { - Disturb( DisturbType.Kill ); - } + public virtual int CastRecoveryBase => 6; + public virtual int CastRecoveryFastScalar => 1; + public virtual int CastRecoveryPerSecond => 4; + public virtual int CastRecoveryMinimum => 0; - public virtual void OnConnectionChanged() - { - FinishSequence(); - } + public abstract TimeSpan CastDelayBase{ get; } - public virtual bool OnCasterMoving( Direction d ) - { - if ( IsCasting && BlocksMovement ) - { - Caster.SendLocalizedMessage( 500111 ); // You are frozen and can not move. - return false; - } + public virtual double CastDelayFastScalar => 1; + public virtual double CastDelaySecondsPerTick => 0.25; + public virtual TimeSpan CastDelayMinimum => TimeSpan.FromSeconds(0.25); - return true; - } + public virtual bool IsCasting => State == SpellState.Casting; - public virtual bool OnCasterEquiping( Item item ) - { - if ( IsCasting ) - Disturb( DisturbType.EquipRequest ); + public virtual void OnCasterHurt() + { + //Confirm: Monsters and pets cannot be disturbed. + if (!Caster.Player) + return; - return true; - } + if (IsCasting) + { + object o = ProtectionSpell.Registry[Caster]; + bool disturb = true; - public virtual bool OnCasterUsingObject( object o ) - { - if ( State == SpellState.Sequencing ) - Disturb( DisturbType.UseRequest ); + if (o is double) + if ((double)o > Utility.RandomDouble() * 100.0) + disturb = false; - return true; - } + if (disturb) + Disturb(DisturbType.Hurt, false, true); + } + } - public virtual bool OnCastInTown( Region r ) - { - return Info.AllowTown; - } + public virtual void OnCasterKilled() + { + Disturb(DisturbType.Kill); + } - public virtual bool ConsumeReagents() - { - if ( Scroll != null || !Caster.Player ) - return true; + public virtual void OnConnectionChanged() + { + FinishSequence(); + } - if ( AosAttributes.GetValue( Caster, AosAttribute.LowerRegCost ) > Utility.Random( 100 ) ) - return true; + public virtual bool OnCasterMoving(Direction d) + { + if (IsCasting && BlocksMovement) + { + Caster.SendLocalizedMessage(500111); // You are frozen and can not move. + return false; + } - if ( Engines.ConPVP.DuelContext.IsFreeConsume( Caster ) ) - return true; + return true; + } - Container pack = Caster.Backpack; + public virtual bool OnCasterEquipping(Item item) + { + if (IsCasting) + Disturb(DisturbType.EquipRequest); - if ( pack == null ) - return false; + return true; + } - if ( pack.ConsumeTotal( Info.Reagents, Info.Amounts ) == -1 ) - return true; + public virtual bool OnCasterUsingObject(object o) + { + if (State == SpellState.Sequencing) + Disturb(DisturbType.UseRequest); - return false; - } + return true; + } - public virtual double GetInscribeSkill( Mobile m ) - { - // There is no chance to gain - // m.CheckSkill( SkillName.Inscribe, 0.0, 120.0 ); + public virtual bool OnCastInTown(Region r) + { + return Info.AllowTown; + } - return m.Skills[SkillName.Inscribe].Value; - } + public void StartDelayedDamageContext(Mobile m, Timer t) + { + if (DelayedDamageStacking) + return; //Sanity - public virtual int GetInscribeFixed( Mobile m ) - { - // There is no chance to gain - // m.CheckSkill( SkillName.Inscribe, 0.0, 120.0 ); + if (!m_ContextTable.TryGetValue(GetType(), out DelayedDamageContextWrapper contexts)) + { + contexts = new DelayedDamageContextWrapper(); + m_ContextTable.Add(GetType(), contexts); + } - return m.Skills[SkillName.Inscribe].Fixed; - } + contexts.Add(m, t); + } - public virtual int GetDamageFixed( Mobile m ) - { - //m.CheckSkill( DamageSkill, 0.0, m.Skills[DamageSkill].Cap ); + public void RemoveDelayedDamageContext(Mobile m) + { + if (!m_ContextTable.TryGetValue(GetType(), out DelayedDamageContextWrapper contexts)) + return; - return m.Skills[DamageSkill].Fixed; - } + contexts.Remove(m); + } - public virtual double GetDamageSkill( Mobile m ) - { - //m.CheckSkill( DamageSkill, 0.0, m.Skills[DamageSkill].Cap ); + public void HarmfulSpell(Mobile m) + { + (m as BaseCreature)?.OnHarmfulSpell(Caster); + } - return m.Skills[DamageSkill].Value; - } + public virtual int GetNewAosDamage(int bonus, int dice, int sides, Mobile singleTarget) + { + if (singleTarget != null) + return GetNewAosDamage(bonus, dice, sides, Caster.Player && singleTarget.Player, + GetDamageScalar(singleTarget)); - public virtual double GetResistSkill( Mobile m ) - { - return m.Skills[SkillName.MagicResist].Value; - } + return GetNewAosDamage(bonus, dice, sides, false); + } - public virtual double GetDamageScalar( Mobile target ) - { - double scalar = 1.0; + public virtual int GetNewAosDamage(int bonus, int dice, int sides, bool playerVsPlayer) + { + return GetNewAosDamage(bonus, dice, sides, playerVsPlayer, 1.0); + } - if ( !Core.AOS ) //EvalInt stuff for AoS is handled elsewhere - { - double casterEI = Caster.Skills[DamageSkill].Value; - double targetRS = target.Skills[SkillName.MagicResist].Value; + public virtual int GetNewAosDamage(int bonus, int dice, int sides, bool playerVsPlayer, double scalar) + { + int damage = Utility.Dice(dice, sides, bonus) * 100; + int damageBonus = 0; - /* - if ( Core.AOS ) - targetRS = 0; - */ + int inscribeSkill = GetInscribeFixed(Caster); + int inscribeBonus = (inscribeSkill + 1000 * (inscribeSkill / 1000)) / 200; + damageBonus += inscribeBonus; - //m_Caster.CheckSkill( DamageSkill, 0.0, 120.0 ); + int intBonus = Caster.Int / 10; + damageBonus += intBonus; - if ( casterEI > targetRS ) - scalar = (1.0 + ((casterEI - targetRS) / 500.0)); - else - scalar = (1.0 + ((casterEI - targetRS) / 200.0)); + int sdiBonus = AosAttributes.GetValue(Caster, AosAttribute.SpellDamage); + // PvP spell damage increase cap of 15% from an item�s magic property + if (playerVsPlayer && sdiBonus > 15) + sdiBonus = 15; - // magery damage bonus, -25% at 0 skill, +0% at 100 skill, +5% at 120 skill - scalar += (Caster.Skills[CastSkill].Value - 100.0) / 400.0; + damageBonus += sdiBonus; - if ( !target.Player && !target.Body.IsHuman /*&& !Core.AOS*/ ) - scalar *= 2.0; // Double magery damage to monsters/animals if not AOS - } + TransformContext context = TransformationSpellHelper.GetContext(Caster); - (target as BaseCreature)?.AlterDamageScalarFrom( Caster, ref scalar ); + if (context?.Spell is ReaperFormSpell) + damageBonus += ((ReaperFormSpell)context.Spell).SpellDamageBonus; - (Caster as BaseCreature)?.AlterDamageScalarTo( target, ref scalar ); + damage = AOS.Scale(damage, 100 + damageBonus); - if ( Core.SE ) - scalar *= GetSlayerDamageScalar( target ); + int evalSkill = GetDamageFixed(Caster); + int evalScale = 30 + 9 * evalSkill / 100; - target.Region.SpellDamageScalar( Caster, target, ref scalar ); + damage = AOS.Scale(damage, evalScale); - if ( Evasion.CheckSpellEvasion( target ) ) //Only single target spells an be evaded - scalar = 0; + damage = AOS.Scale(damage, (int)(scalar * 100)); - return scalar; - } + return damage / 100; + } - public virtual double GetSlayerDamageScalar( Mobile defender ) - { - Spellbook atkBook = Spellbook.FindEquippedSpellbook( Caster ); + public virtual bool ConsumeReagents() + { + if (Scroll != null || !Caster.Player) + return true; - double scalar = 1.0; - if ( atkBook != null ) - { - SlayerEntry atkSlayer = SlayerGroup.GetEntryByName( atkBook.Slayer ); - SlayerEntry atkSlayer2 = SlayerGroup.GetEntryByName( atkBook.Slayer2 ); + if (AosAttributes.GetValue(Caster, AosAttribute.LowerRegCost) > Utility.Random(100)) + return true; - if ( atkSlayer != null && atkSlayer.Slays( defender ) || atkSlayer2 != null && atkSlayer2.Slays( defender ) ) - { - defender.FixedEffect( 0x37B9, 10, 5 ); //TODO: Confirm this displays on OSIs - scalar = 2.0; - } + if (DuelContext.IsFreeConsume(Caster)) + return true; + Container pack = Caster.Backpack; - TransformContext context = TransformationSpellHelper.GetContext( defender ); + if (pack == null) + return false; - if ( (atkBook.Slayer == SlayerName.Silver || atkBook.Slayer2 == SlayerName.Silver) && context != null && context.Type != typeof( HorrificBeastSpell ) ) - scalar +=.25; // Every necromancer transformation other than horrific beast take an additional 25% damage + if (pack.ConsumeTotal(Info.Reagents, Info.Amounts) == -1) + return true; - if ( scalar != 1.0 ) - return scalar; - } + return false; + } - ISlayer defISlayer = Spellbook.FindEquippedSpellbook( defender ); + public virtual double GetInscribeSkill(Mobile m) + { + // There is no chance to gain + // m.CheckSkill( SkillName.Inscribe, 0.0, 120.0 ); - if ( defISlayer == null ) - defISlayer = defender.Weapon as ISlayer; + return m.Skills[SkillName.Inscribe].Value; + } - if ( defISlayer != null ) - { - SlayerEntry defSlayer = SlayerGroup.GetEntryByName( defISlayer.Slayer ); - SlayerEntry defSlayer2 = SlayerGroup.GetEntryByName( defISlayer.Slayer2 ); + public virtual int GetInscribeFixed(Mobile m) + { + // There is no chance to gain + // m.CheckSkill( SkillName.Inscribe, 0.0, 120.0 ); - if ( defSlayer != null && defSlayer.Group.OppositionSuperSlays( Caster ) || defSlayer2 != null && defSlayer2.Group.OppositionSuperSlays( Caster ) ) - scalar = 2.0; - } + return m.Skills[SkillName.Inscribe].Fixed; + } - return scalar; - } + public virtual int GetDamageFixed(Mobile m) + { + //m.CheckSkill( DamageSkill, 0.0, m.Skills[DamageSkill].Cap ); - public virtual void DoFizzle() - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502632 ); // The spell fizzles. + return m.Skills[DamageSkill].Fixed; + } - if ( Caster.Player ) - { - if ( Core.AOS ) - Caster.FixedParticles( 0x3735, 1, 30, 9503, EffectLayer.Waist ); - else - Caster.FixedEffect( 0x3735, 6, 30 ); + public virtual double GetDamageSkill(Mobile m) + { + //m.CheckSkill( DamageSkill, 0.0, m.Skills[DamageSkill].Cap ); - Caster.PlaySound( 0x5C ); - } - } + return m.Skills[DamageSkill].Value; + } - private CastTimer m_CastTimer; - private AnimTimer m_AnimTimer; + public virtual double GetResistSkill(Mobile m) + { + return m.Skills[SkillName.MagicResist].Value; + } - public void Disturb( DisturbType type ) - { - Disturb( type, true, false ); - } + public virtual double GetDamageScalar(Mobile target) + { + double scalar = 1.0; - public virtual bool CheckDisturb( DisturbType type, bool firstCircle, bool resistable ) - { - if ( resistable && Scroll is BaseWand ) - return false; + if (!Core.AOS) //EvalInt stuff for AoS is handled elsewhere + { + double casterEI = Caster.Skills[DamageSkill].Value; + double targetRS = target.Skills[SkillName.MagicResist].Value; - return true; - } + /* + if ( Core.AOS ) + targetRS = 0; + */ - public void Disturb( DisturbType type, bool firstCircle, bool resistable ) - { - if ( !CheckDisturb( type, firstCircle, resistable ) ) - return; - - if ( State == SpellState.Casting ) - { - if ( !firstCircle && !Core.AOS && this is MagerySpell && ((MagerySpell)this).Circle == SpellCircle.First ) - return; - - State = SpellState.None; - Caster.Spell = null; - - OnDisturb( type, true ); - - m_CastTimer?.Stop(); - - m_AnimTimer?.Stop(); - - if ( Core.AOS && Caster.Player && type == DisturbType.Hurt ) - DoHurtFizzle(); - - Caster.NextSpellTime = Core.TickCount + (int)GetDisturbRecovery().TotalMilliseconds; - } - else if ( State == SpellState.Sequencing ) - { - if ( !firstCircle && !Core.AOS && this is MagerySpell && ((MagerySpell)this).Circle == SpellCircle.First ) - return; - - State = SpellState.None; - Caster.Spell = null; - - OnDisturb( type, false ); - - Target.Cancel( Caster ); - - if ( Core.AOS && Caster.Player && type == DisturbType.Hurt ) - DoHurtFizzle(); - } - } - - public virtual void DoHurtFizzle() - { - Caster.FixedEffect( 0x3735, 6, 30 ); - Caster.PlaySound( 0x5C ); - } - - public virtual void OnDisturb( DisturbType type, bool message ) - { - if ( message ) - Caster.SendLocalizedMessage( 500641 ); // Your concentration is disturbed, thus ruining thy spell. - } - - public virtual bool CheckCast() - { - return true; - } - - public virtual void SayMantra() - { - if ( Scroll is BaseWand ) - return; - - if ( Info.Mantra != null && Info.Mantra.Length > 0 && Caster.Player ) - Caster.PublicOverheadMessage( MessageType.Spell, Caster.SpeechHue, true, Info.Mantra, false ); - } - - public virtual bool BlockedByHorrificBeast => true; - public virtual bool BlockedByAnimalForm => true; - public virtual bool BlocksMovement => true; - - public virtual bool CheckNextSpellTime => !(Scroll is BaseWand); - - public bool Cast() - { - StartCastTime = Core.TickCount; - - if ( Core.AOS && Caster.Spell is Spell && ((Spell)Caster.Spell).State == SpellState.Sequencing ) - ((Spell)Caster.Spell).Disturb( DisturbType.NewCast ); - - if ( !Caster.CheckAlive() ) - { - return false; - } - - if ( Scroll is BaseWand && Caster.Spell != null && Caster.Spell.IsCasting ) - { - Caster.SendLocalizedMessage( 502643 ); // You can not cast a spell while frozen. - } - else if ( Caster.Spell != null && Caster.Spell.IsCasting ) - { - Caster.SendLocalizedMessage( 502642 ); // You are already casting a spell. - } - else if ( BlockedByHorrificBeast && TransformationSpellHelper.UnderTransformation( Caster, typeof( HorrificBeastSpell ) ) || ( BlockedByAnimalForm && AnimalForm.UnderTransformation( Caster ) )) - { - Caster.SendLocalizedMessage( 1061091 ); // You cannot cast that spell in this form. - } - else if ( !(Scroll is BaseWand) && (Caster.Paralyzed || Caster.Frozen) ) - { - Caster.SendLocalizedMessage( 502643 ); // You can not cast a spell while frozen. - } - else if (CheckNextSpellTime && Core.TickCount - Caster.NextSpellTime < 0) - { - Caster.SendLocalizedMessage( 502644 ); // You have not yet recovered from casting a spell. - } - else if ( Caster is PlayerMobile && ( (PlayerMobile) Caster ).PeacedUntil > DateTime.UtcNow ) - { - Caster.SendLocalizedMessage( 1072060 ); // You cannot cast a spell while calmed. - } - #region Dueling - else if ( (Caster as PlayerMobile)?.DuelContext != null && !((PlayerMobile)Caster).DuelContext.AllowSpellCast( Caster, this ) ) - { - } - #endregion - else if ( Caster.Mana >= ScaleMana( GetMana() ) ) - { - if ( Caster.Spell == null && Caster.CheckSpellCast( this ) && CheckCast() && Caster.Region.OnBeginSpellCast( Caster, this ) ) - { - State = SpellState.Casting; - Caster.Spell = this; - - if ( !( Scroll is BaseWand ) && RevealOnCast ) - Caster.RevealingAction(); - - SayMantra(); - - TimeSpan castDelay = GetCastDelay(); - - if ( ShowHandMovement && ( Caster.Body.IsHuman || ( Caster.Player && Caster.Body.IsMonster ) ) ) - { - int count = (int)Math.Ceiling( castDelay.TotalSeconds / AnimateDelay.TotalSeconds ); - - if ( count != 0 ) - { - m_AnimTimer = new AnimTimer( this, count ); - m_AnimTimer.Start(); - } - - if ( Info.LeftHandEffect > 0 ) - Caster.FixedParticles( 0, 10, 5, Info.LeftHandEffect, EffectLayer.LeftHand ); - - if ( Info.RightHandEffect > 0 ) - Caster.FixedParticles( 0, 10, 5, Info.RightHandEffect, EffectLayer.RightHand ); - } - - if ( ClearHandsOnCast ) - Caster.ClearHands(); - - if ( Core.ML ) - WeaponAbility.ClearCurrentAbility( Caster ); - - m_CastTimer = new CastTimer( this, castDelay ); - //m_CastTimer.Start(); - - OnBeginCast(); - - if ( castDelay > TimeSpan.Zero ) { - m_CastTimer.Start(); - } else { - m_CastTimer.Tick(); - } + //m_Caster.CheckSkill( DamageSkill, 0.0, 120.0 ); - return true; - } + if (casterEI > targetRS) + scalar = 1.0 + (casterEI - targetRS) / 500.0; + else + scalar = 1.0 + (casterEI - targetRS) / 200.0; - return false; - } - else - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x22, 502625 ); // Insufficient mana - } - - return false; - } - - public abstract void OnCast(); - - public virtual void OnBeginCast() - { - } - - public virtual void GetCastSkills( out double min, out double max ) - { - min = max = 0; //Intended but not required for overriding. - } - - public virtual bool CheckFizzle() - { - if ( Scroll is BaseWand ) - return true; + // magery damage bonus, -25% at 0 skill, +0% at 100 skill, +5% at 120 skill + scalar += (Caster.Skills[CastSkill].Value - 100.0) / 400.0; - double minSkill, maxSkill; + if (!target.Player && !target.Body.IsHuman /*&& !Core.AOS*/) + scalar *= 2.0; // Double magery damage to monsters/animals if not AOS + } - GetCastSkills( out minSkill, out maxSkill ); + (target as BaseCreature)?.AlterDamageScalarFrom(Caster, ref scalar); - if ( DamageSkill != CastSkill ) - Caster.CheckSkill( DamageSkill, 0.0, Caster.Skills[ DamageSkill ].Cap ); + (Caster as BaseCreature)?.AlterDamageScalarTo(target, ref scalar); - return Caster.CheckSkill( CastSkill, minSkill, maxSkill ); - } + if (Core.SE) + scalar *= GetSlayerDamageScalar(target); - public abstract int GetMana(); + target.Region.SpellDamageScalar(Caster, target, ref scalar); - public virtual int ScaleMana( int mana ) - { - double scalar = 1.0; + if (Evasion.CheckSpellEvasion(target)) //Only single target spells an be evaded + scalar = 0; - if ( !MindRotSpell.GetMindRotScalar( Caster, ref scalar ) ) - scalar = 1.0; + return scalar; + } - // Lower Mana Cost = 40% - int lmc = AosAttributes.GetValue( Caster, AosAttribute.LowerManaCost ); - if ( lmc > 40 ) - lmc = 40; + public virtual double GetSlayerDamageScalar(Mobile defender) + { + Spellbook atkBook = Spellbook.FindEquippedSpellbook(Caster); - scalar -= (double)lmc / 100; + double scalar = 1.0; + if (atkBook != null) + { + SlayerEntry atkSlayer = SlayerGroup.GetEntryByName(atkBook.Slayer); + SlayerEntry atkSlayer2 = SlayerGroup.GetEntryByName(atkBook.Slayer2); - return (int)(mana * scalar); - } + if (atkSlayer != null && atkSlayer.Slays(defender) || atkSlayer2 != null && atkSlayer2.Slays(defender)) + { + defender.FixedEffect(0x37B9, 10, 5); //TODO: Confirm this displays on OSIs + scalar = 2.0; + } - public virtual TimeSpan GetDisturbRecovery() - { - if ( Core.AOS ) - return TimeSpan.Zero; - double delay = 1.0 - Math.Sqrt((Core.TickCount - StartCastTime) / 1000.0 / GetCastDelay().TotalSeconds); + TransformContext context = TransformationSpellHelper.GetContext(defender); - if ( delay < 0.2 ) - delay = 0.2; + if ((atkBook.Slayer == SlayerName.Silver || atkBook.Slayer2 == SlayerName.Silver) && context != null && + context.Type != typeof(HorrificBeastSpell)) + scalar += .25; // Every necromancer transformation other than horrific beast take an additional 25% damage - return TimeSpan.FromSeconds( delay ); - } + if (scalar != 1.0) + return scalar; + } - public virtual int CastRecoveryBase => 6; - public virtual int CastRecoveryFastScalar => 1; - public virtual int CastRecoveryPerSecond => 4; - public virtual int CastRecoveryMinimum => 0; + ISlayer defISlayer = Spellbook.FindEquippedSpellbook(defender); - public virtual TimeSpan GetCastRecovery() - { - if ( !Core.AOS ) - return NextSpellDelay; + if (defISlayer == null) + defISlayer = defender.Weapon as ISlayer; - int fcr = AosAttributes.GetValue( Caster, AosAttribute.CastRecovery ); + if (defISlayer != null) + { + SlayerEntry defSlayer = SlayerGroup.GetEntryByName(defISlayer.Slayer); + SlayerEntry defSlayer2 = SlayerGroup.GetEntryByName(defISlayer.Slayer2); - fcr -= ThunderstormSpell.GetCastRecoveryMalus( Caster ); + if (defSlayer != null && defSlayer.Group.OppositionSuperSlays(Caster) || + defSlayer2 != null && defSlayer2.Group.OppositionSuperSlays(Caster)) + scalar = 2.0; + } - int fcrDelay = -(CastRecoveryFastScalar * fcr); + return scalar; + } - int delay = CastRecoveryBase + fcrDelay; + public virtual void DoFizzle() + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502632); // The spell fizzles. - if ( delay < CastRecoveryMinimum ) - delay = CastRecoveryMinimum; + if (Caster.Player) + { + if (Core.AOS) + Caster.FixedParticles(0x3735, 1, 30, 9503, EffectLayer.Waist); + else + Caster.FixedEffect(0x3735, 6, 30); - return TimeSpan.FromSeconds( (double)delay / CastRecoveryPerSecond ); - } + Caster.PlaySound(0x5C); + } + } - public abstract TimeSpan CastDelayBase { get; } + public void Disturb(DisturbType type) + { + Disturb(type, true, false); + } - public virtual double CastDelayFastScalar => 1; - public virtual double CastDelaySecondsPerTick => 0.25; - public virtual TimeSpan CastDelayMinimum => TimeSpan.FromSeconds( 0.25 ); + public virtual bool CheckDisturb(DisturbType type, bool firstCircle, bool resistable) + { + if (resistable && Scroll is BaseWand) + return false; + + return true; + } + + public void Disturb(DisturbType type, bool firstCircle, bool resistable) + { + if (!CheckDisturb(type, firstCircle, resistable)) + return; + + if (State == SpellState.Casting) + { + if (!firstCircle && !Core.AOS && this is MagerySpell && ((MagerySpell)this).Circle == SpellCircle.First) + return; + + State = SpellState.None; + Caster.Spell = null; + + OnDisturb(type, true); + + m_CastTimer?.Stop(); + + m_AnimTimer?.Stop(); + + if (Core.AOS && Caster.Player && type == DisturbType.Hurt) + DoHurtFizzle(); + + Caster.NextSpellTime = Core.TickCount + (int)GetDisturbRecovery().TotalMilliseconds; + } + else if (State == SpellState.Sequencing) + { + if (!firstCircle && !Core.AOS && this is MagerySpell && ((MagerySpell)this).Circle == SpellCircle.First) + return; + + State = SpellState.None; + Caster.Spell = null; + + OnDisturb(type, false); + + Target.Cancel(Caster); + + if (Core.AOS && Caster.Player && type == DisturbType.Hurt) + DoHurtFizzle(); + } + } + + public virtual void DoHurtFizzle() + { + Caster.FixedEffect(0x3735, 6, 30); + Caster.PlaySound(0x5C); + } + + public virtual void OnDisturb(DisturbType type, bool message) + { + if (message) + Caster.SendLocalizedMessage(500641); // Your concentration is disturbed, thus ruining thy spell. + } + + public virtual bool CheckCast() + { + return true; + } + + public virtual void SayMantra() + { + if (Scroll is BaseWand) + return; + + if (Info.Mantra != null && Info.Mantra.Length > 0 && Caster.Player) + Caster.PublicOverheadMessage(MessageType.Spell, Caster.SpeechHue, true, Info.Mantra, false); + } + + public bool Cast() + { + StartCastTime = Core.TickCount; + + if (Core.AOS && Caster.Spell is Spell && ((Spell)Caster.Spell).State == SpellState.Sequencing) + ((Spell)Caster.Spell).Disturb(DisturbType.NewCast); + + if (!Caster.CheckAlive()) return false; + + if (Scroll is BaseWand && Caster.Spell != null && Caster.Spell.IsCasting) + { + Caster.SendLocalizedMessage(502643); // You can not cast a spell while frozen. + } + else if (Caster.Spell != null && Caster.Spell.IsCasting) + { + Caster.SendLocalizedMessage(502642); // You are already casting a spell. + } + else if (BlockedByHorrificBeast && + TransformationSpellHelper.UnderTransformation(Caster, typeof(HorrificBeastSpell)) || + BlockedByAnimalForm && AnimalForm.UnderTransformation(Caster)) + { + Caster.SendLocalizedMessage(1061091); // You cannot cast that spell in this form. + } + else if (!(Scroll is BaseWand) && (Caster.Paralyzed || Caster.Frozen)) + { + Caster.SendLocalizedMessage(502643); // You can not cast a spell while frozen. + } + else if (CheckNextSpellTime && Core.TickCount - Caster.NextSpellTime < 0) + { + Caster.SendLocalizedMessage(502644); // You have not yet recovered from casting a spell. + } + else if (Caster is PlayerMobile && ((PlayerMobile)Caster).PeacedUntil > DateTime.UtcNow) + { + Caster.SendLocalizedMessage(1072060); // You cannot cast a spell while calmed. + } + + #region Dueling - //public virtual int CastDelayBase{ get{ return 3; } } - //public virtual int CastDelayFastScalar{ get{ return 1; } } - //public virtual int CastDelayPerSecond{ get{ return 4; } } - //public virtual int CastDelayMinimum{ get{ return 1; } } + else if ((Caster as PlayerMobile)?.DuelContext != null && + !((PlayerMobile)Caster).DuelContext.AllowSpellCast(Caster, this)) + { + } - public virtual TimeSpan GetCastDelay() - { - if ( Scroll is BaseWand ) - return Core.ML ? CastDelayBase : TimeSpan.Zero; // TODO: Should FC apply to wands? + #endregion + + else if (Caster.Mana >= ScaleMana(GetMana())) + { + if (Caster.Spell == null && Caster.CheckSpellCast(this) && CheckCast() && + Caster.Region.OnBeginSpellCast(Caster, this)) + { + State = SpellState.Casting; + Caster.Spell = this; + + if (!(Scroll is BaseWand) && RevealOnCast) + Caster.RevealingAction(); + + SayMantra(); + + TimeSpan castDelay = GetCastDelay(); + + if (ShowHandMovement && (Caster.Body.IsHuman || Caster.Player && Caster.Body.IsMonster)) + { + int count = (int)Math.Ceiling(castDelay.TotalSeconds / AnimateDelay.TotalSeconds); - // Faster casting cap of 2 (if not using the protection spell) - // Faster casting cap of 0 (if using the protection spell) - // Paladin spells are subject to a faster casting cap of 4 - // Paladins with magery of 70.0 or above are subject to a faster casting cap of 2 - int fcMax = 4; + if (count != 0) + { + m_AnimTimer = new AnimTimer(this, count); + m_AnimTimer.Start(); + } + + if (Info.LeftHandEffect > 0) + Caster.FixedParticles(0, 10, 5, Info.LeftHandEffect, EffectLayer.LeftHand); - if ( CastSkill == SkillName.Magery || CastSkill == SkillName.Necromancy || ( CastSkill == SkillName.Chivalry && Caster.Skills[SkillName.Magery].Value >= 70.0 ) ) - fcMax = 2; + if (Info.RightHandEffect > 0) + Caster.FixedParticles(0, 10, 5, Info.RightHandEffect, EffectLayer.RightHand); + } - int fc = AosAttributes.GetValue( Caster, AosAttribute.CastSpeed ); + if (ClearHandsOnCast) + Caster.ClearHands(); - if ( fc > fcMax ) - fc = fcMax; + if (Core.ML) + WeaponAbility.ClearCurrentAbility(Caster); - if ( ProtectionSpell.Registry.Contains( Caster ) ) - fc -= 2; + m_CastTimer = new CastTimer(this, castDelay); + //m_CastTimer.Start(); - if ( EssenceOfWindSpell.IsDebuffed( Caster ) ) - fc -= EssenceOfWindSpell.GetFCMalus( Caster ); + OnBeginCast(); - TimeSpan baseDelay = CastDelayBase; + if (castDelay > TimeSpan.Zero) + m_CastTimer.Start(); + else + m_CastTimer.Tick(); - TimeSpan fcDelay = TimeSpan.FromSeconds( -(CastDelayFastScalar * fc * CastDelaySecondsPerTick) ); - - //int delay = CastDelayBase + circleDelay + fcDelay; - TimeSpan delay = baseDelay + fcDelay; - - if ( delay < CastDelayMinimum ) - delay = CastDelayMinimum; - - //return TimeSpan.FromSeconds( (double)delay / CastDelayPerSecond ); - return delay; - } - - public virtual void FinishSequence() - { - State = SpellState.None; - - if ( Caster.Spell == this ) - Caster.Spell = null; - } - - public virtual int ComputeKarmaAward() - { - return 0; - } - - public virtual bool CheckSequence() - { - int mana = ScaleMana( GetMana() ); - - if ( Caster.Deleted || !Caster.Alive || Caster.Spell != this || State != SpellState.Sequencing ) - { - DoFizzle(); - } - else if ( Scroll != null && !(Scroll is Runebook) && (Scroll.Amount <= 0 || Scroll.Deleted || Scroll.RootParent != Caster || (Scroll is BaseWand && (((BaseWand)Scroll).Charges <= 0 || Scroll.Parent != Caster))) ) - { - DoFizzle(); - } - else if ( !ConsumeReagents() ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x22, 502630 ); // More reagents are needed for this spell. - } - else if ( Caster.Mana < mana ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x22, 502625 ); // Insufficient mana for this spell. - } - else if ( Core.AOS && (Caster.Frozen || Caster.Paralyzed) ) - { - Caster.SendLocalizedMessage( 502646 ); // You cannot cast a spell while frozen. - DoFizzle(); - } - else if ( Caster is PlayerMobile && ((PlayerMobile) Caster).PeacedUntil > DateTime.UtcNow ) - { - Caster.SendLocalizedMessage( 1072060 ); // You cannot cast a spell while calmed. - DoFizzle(); - } - else if ( CheckFizzle() ) - { - Caster.Mana -= mana; - - if ( Scroll is SpellScroll ) - Scroll.Consume(); - else if ( Scroll is BaseWand ) - { - ((BaseWand)Scroll).ConsumeCharge( Caster ); - Caster.RevealingAction(); - } - - if ( Scroll is BaseWand ) - { - bool m = Scroll.Movable; - - Scroll.Movable = false; - - if ( ClearHandsOnCast ) - Caster.ClearHands(); - - Scroll.Movable = m; - } - else - { - if ( ClearHandsOnCast ) - Caster.ClearHands(); - } - - int karma = ComputeKarmaAward(); - - if ( karma != 0 ) - Misc.Titles.AwardKarma( Caster, karma, true ); - - if ( TransformationSpellHelper.UnderTransformation( Caster, typeof( VampiricEmbraceSpell ) ) ) - { - bool garlic = false; - - for ( int i = 0; !garlic && i < Info.Reagents.Length; ++i ) - garlic = ( Info.Reagents[i] == Reagent.Garlic ); - - if ( garlic ) - { - Caster.SendLocalizedMessage( 1061651 ); // The garlic burns you! - AOS.Damage( Caster, Utility.RandomMinMax( 17, 23 ), 100, 0, 0, 0, 0 ); - } - } - - return true; - } - else - { - DoFizzle(); - } - - return false; - } - - public bool CheckBSequence( Mobile target ) - { - return CheckBSequence( target, false ); - } - - public bool CheckBSequence( Mobile target, bool allowDead ) - { - if ( !target.Alive && !allowDead ) - { - Caster.SendLocalizedMessage( 501857 ); // This spell won't work on that! - return false; - } - - if ( Caster.CanBeBeneficial( target, true, allowDead ) && CheckSequence() ) - { - Caster.DoBeneficial( target ); - return true; - } - return false; - } - - public bool CheckHSequence( Mobile target ) - { - if ( !target.Alive ) - { - Caster.SendLocalizedMessage( 501857 ); // This spell won't work on that! - return false; - } - - if ( Caster.CanBeHarmful( target ) && CheckSequence() ) - { - Caster.DoHarmful( target ); - return true; - } - return false; - } - - private class AnimTimer : Timer - { - private Spell m_Spell; - - public AnimTimer( Spell spell, int count ) : base( TimeSpan.Zero, AnimateDelay, count ) - { - m_Spell = spell; - - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - if ( m_Spell.State != SpellState.Casting || m_Spell.Caster.Spell != m_Spell ) - { - Stop(); - return; - } - - if ( !m_Spell.Caster.Mounted && m_Spell.Info.Action >= 0 ) - { - if ( m_Spell.Caster.Body.IsHuman ) - m_Spell.Caster.Animate( m_Spell.Info.Action, 7, 1, true, false, 0 ); - else if ( m_Spell.Caster.Player && m_Spell.Caster.Body.IsMonster ) - m_Spell.Caster.Animate( 12, 7, 1, true, false, 0 ); - } - - if ( !Running ) - m_Spell.m_AnimTimer = null; - } - } - - private class CastTimer : Timer - { - private Spell m_Spell; - - public CastTimer( Spell spell, TimeSpan castDelay ) : base( castDelay ) - { - m_Spell = spell; - - Priority = TimerPriority.TwentyFiveMS; - } - - protected override void OnTick() - { - if ( m_Spell?.Caster == null ) - { - return; - } - - if ( m_Spell.State == SpellState.Casting && m_Spell.Caster.Spell == m_Spell ) - { - m_Spell.State = SpellState.Sequencing; - m_Spell.m_CastTimer = null; - m_Spell.Caster.OnSpellCast( m_Spell ); - m_Spell.Caster.Region?.OnSpellCast( m_Spell.Caster, m_Spell ); - m_Spell.Caster.NextSpellTime = Core.TickCount + (int)m_Spell.GetCastRecovery().TotalMilliseconds; // Spell.NextSpellDelay; - - Target originalTarget = m_Spell.Caster.Target; - - m_Spell.OnCast(); - - if ( m_Spell.Caster.Player && m_Spell.Caster.Target != originalTarget && m_Spell.Caster.Target != null ) - m_Spell.Caster.Target.BeginTimeout( m_Spell.Caster, TimeSpan.FromSeconds( 30.0 ) ); - - m_Spell.m_CastTimer = null; - } - } - - public void Tick() { - OnTick(); - } - } - } -} + return true; + } + + return false; + } + else + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x22, 502625); // Insufficient mana + } + + return false; + } + + public abstract void OnCast(); + + public virtual void OnBeginCast() + { + } + + public virtual void GetCastSkills(out double min, out double max) + { + min = max = 0; //Intended but not required for overriding. + } + + public virtual bool CheckFizzle() + { + if (Scroll is BaseWand) + return true; + + double minSkill, maxSkill; + + GetCastSkills(out minSkill, out maxSkill); + + if (DamageSkill != CastSkill) + Caster.CheckSkill(DamageSkill, 0.0, Caster.Skills[DamageSkill].Cap); + + return Caster.CheckSkill(CastSkill, minSkill, maxSkill); + } + + public abstract int GetMana(); + + public virtual int ScaleMana(int mana) + { + double scalar = 1.0; + + if (!MindRotSpell.GetMindRotScalar(Caster, ref scalar)) + scalar = 1.0; + + // Lower Mana Cost = 40% + int lmc = AosAttributes.GetValue(Caster, AosAttribute.LowerManaCost); + if (lmc > 40) + lmc = 40; + + scalar -= (double)lmc / 100; + + return (int)(mana * scalar); + } + + public virtual TimeSpan GetDisturbRecovery() + { + if (Core.AOS) + return TimeSpan.Zero; + + double delay = 1.0 - Math.Sqrt((Core.TickCount - StartCastTime) / 1000.0 / GetCastDelay().TotalSeconds); + + if (delay < 0.2) + delay = 0.2; + + return TimeSpan.FromSeconds(delay); + } + + public virtual TimeSpan GetCastRecovery() + { + if (!Core.AOS) + return NextSpellDelay; + + int fcr = AosAttributes.GetValue(Caster, AosAttribute.CastRecovery); + + fcr -= ThunderstormSpell.GetCastRecoveryMalus(Caster); + + int fcrDelay = -(CastRecoveryFastScalar * fcr); + + int delay = CastRecoveryBase + fcrDelay; + + if (delay < CastRecoveryMinimum) + delay = CastRecoveryMinimum; + + return TimeSpan.FromSeconds((double)delay / CastRecoveryPerSecond); + } + + //public virtual int CastDelayBase{ get{ return 3; } } + //public virtual int CastDelayFastScalar{ get{ return 1; } } + //public virtual int CastDelayPerSecond{ get{ return 4; } } + //public virtual int CastDelayMinimum{ get{ return 1; } } + + public virtual TimeSpan GetCastDelay() + { + if (Scroll is BaseWand) + return Core.ML ? CastDelayBase : TimeSpan.Zero; // TODO: Should FC apply to wands? + + // Faster casting cap of 2 (if not using the protection spell) + // Faster casting cap of 0 (if using the protection spell) + // Paladin spells are subject to a faster casting cap of 4 + // Paladins with magery of 70.0 or above are subject to a faster casting cap of 2 + int fcMax = 4; + + if (CastSkill == SkillName.Magery || CastSkill == SkillName.Necromancy || + CastSkill == SkillName.Chivalry && Caster.Skills[SkillName.Magery].Value >= 70.0) + fcMax = 2; + + int fc = AosAttributes.GetValue(Caster, AosAttribute.CastSpeed); + + if (fc > fcMax) + fc = fcMax; + + if (ProtectionSpell.Registry.Contains(Caster)) + fc -= 2; + + if (EssenceOfWindSpell.IsDebuffed(Caster)) + fc -= EssenceOfWindSpell.GetFCMalus(Caster); + + TimeSpan baseDelay = CastDelayBase; + + TimeSpan fcDelay = TimeSpan.FromSeconds(-(CastDelayFastScalar * fc * CastDelaySecondsPerTick)); + + //int delay = CastDelayBase + circleDelay + fcDelay; + TimeSpan delay = baseDelay + fcDelay; + + if (delay < CastDelayMinimum) + delay = CastDelayMinimum; + + //return TimeSpan.FromSeconds( (double)delay / CastDelayPerSecond ); + return delay; + } + + public virtual void FinishSequence() + { + State = SpellState.None; + + if (Caster.Spell == this) + Caster.Spell = null; + } + + public virtual int ComputeKarmaAward() + { + return 0; + } + + public virtual bool CheckSequence() + { + int mana = ScaleMana(GetMana()); + + if (Caster.Deleted || !Caster.Alive || Caster.Spell != this || State != SpellState.Sequencing) + { + DoFizzle(); + } + else if (Scroll != null && !(Scroll is Runebook) && + (Scroll.Amount <= 0 || Scroll.Deleted || Scroll.RootParent != Caster || Scroll is BaseWand && + (((BaseWand)Scroll).Charges <= 0 || Scroll.Parent != Caster))) + { + DoFizzle(); + } + else if (!ConsumeReagents()) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x22, 502630); // More reagents are needed for this spell. + } + else if (Caster.Mana < mana) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x22, 502625); // Insufficient mana for this spell. + } + else if (Core.AOS && (Caster.Frozen || Caster.Paralyzed)) + { + Caster.SendLocalizedMessage(502646); // You cannot cast a spell while frozen. + DoFizzle(); + } + else if (Caster is PlayerMobile && ((PlayerMobile)Caster).PeacedUntil > DateTime.UtcNow) + { + Caster.SendLocalizedMessage(1072060); // You cannot cast a spell while calmed. + DoFizzle(); + } + else if (CheckFizzle()) + { + Caster.Mana -= mana; + + if (Scroll is SpellScroll) + { + Scroll.Consume(); + } + else if (Scroll is BaseWand) + { + ((BaseWand)Scroll).ConsumeCharge(Caster); + Caster.RevealingAction(); + } + + if (Scroll is BaseWand) + { + bool m = Scroll.Movable; + + Scroll.Movable = false; + + if (ClearHandsOnCast) + Caster.ClearHands(); + + Scroll.Movable = m; + } + else + { + if (ClearHandsOnCast) + Caster.ClearHands(); + } + + int karma = ComputeKarmaAward(); + + if (karma != 0) + Titles.AwardKarma(Caster, karma, true); + + if (TransformationSpellHelper.UnderTransformation(Caster, typeof(VampiricEmbraceSpell))) + { + bool garlic = false; + + for (int i = 0; !garlic && i < Info.Reagents.Length; ++i) + garlic = Info.Reagents[i] == Reagent.Garlic; + + if (garlic) + { + Caster.SendLocalizedMessage(1061651); // The garlic burns you! + AOS.Damage(Caster, Utility.RandomMinMax(17, 23), 100, 0, 0, 0, 0); + } + } + + return true; + } + else + { + DoFizzle(); + } + + return false; + } + + public bool CheckBSequence(Mobile target) + { + return CheckBSequence(target, false); + } + + public bool CheckBSequence(Mobile target, bool allowDead) + { + if (!target.Alive && !allowDead) + { + Caster.SendLocalizedMessage(501857); // This spell won't work on that! + return false; + } + + if (Caster.CanBeBeneficial(target, true, allowDead) && CheckSequence()) + { + Caster.DoBeneficial(target); + return true; + } + + return false; + } + + public bool CheckHSequence(Mobile target) + { + if (!target.Alive) + { + Caster.SendLocalizedMessage(501857); // This spell won't work on that! + return false; + } + + if (Caster.CanBeHarmful(target) && CheckSequence()) + { + Caster.DoHarmful(target); + return true; + } + + return false; + } + + private class DelayedDamageContextWrapper + { + private Dictionary m_Contexts = new Dictionary(); + + public void Add(Mobile m, Timer t) + { + if (m_Contexts.TryGetValue(m, out Timer oldTimer)) + { + oldTimer.Stop(); + m_Contexts.Remove(m); + } + + m_Contexts.Add(m, t); + } + + public void Remove(Mobile m) + { + m_Contexts.Remove(m); + } + } + + private class AnimTimer : Timer + { + private Spell m_Spell; + + public AnimTimer(Spell spell, int count) : base(TimeSpan.Zero, AnimateDelay, count) + { + m_Spell = spell; + + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + if (m_Spell.State != SpellState.Casting || m_Spell.Caster.Spell != m_Spell) + { + Stop(); + return; + } + + if (!m_Spell.Caster.Mounted && m_Spell.Info.Action >= 0) + { + if (m_Spell.Caster.Body.IsHuman) + m_Spell.Caster.Animate(m_Spell.Info.Action, 7, 1, true, false, 0); + else if (m_Spell.Caster.Player && m_Spell.Caster.Body.IsMonster) + m_Spell.Caster.Animate(12, 7, 1, true, false, 0); + } + + if (!Running) + m_Spell.m_AnimTimer = null; + } + } + + private class CastTimer : Timer + { + private Spell m_Spell; + + public CastTimer(Spell spell, TimeSpan castDelay) : base(castDelay) + { + m_Spell = spell; + + Priority = TimerPriority.TwentyFiveMS; + } + + protected override void OnTick() + { + if (m_Spell?.Caster == null) return; + + if (m_Spell.State == SpellState.Casting && m_Spell.Caster.Spell == m_Spell) + { + m_Spell.State = SpellState.Sequencing; + m_Spell.m_CastTimer = null; + m_Spell.Caster.OnSpellCast(m_Spell); + m_Spell.Caster.Region?.OnSpellCast(m_Spell.Caster, m_Spell); + m_Spell.Caster.NextSpellTime = + Core.TickCount + (int)m_Spell.GetCastRecovery().TotalMilliseconds; // Spell.NextSpellDelay; + + Target originalTarget = m_Spell.Caster.Target; + + m_Spell.OnCast(); + + if (m_Spell.Caster.Player && m_Spell.Caster.Target != originalTarget && m_Spell.Caster.Target != null) + m_Spell.Caster.Target.BeginTimeout(m_Spell.Caster, TimeSpan.FromSeconds(30.0)); + + m_Spell.m_CastTimer = null; + } + } + + public void Tick() + { + OnTick(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Base/SpellCircle.cs b/Scripts/Spells/Base/SpellCircle.cs index fead1ae5a..c5e483eee 100644 --- a/Scripts/Spells/Base/SpellCircle.cs +++ b/Scripts/Spells/Base/SpellCircle.cs @@ -1,14 +1,14 @@ namespace Server.Spells { - public enum SpellCircle - { - First, - Second, - Third, - Fourth, - Fifth, - Sixth, - Seventh, - Eighth - } + public enum SpellCircle + { + First, + Second, + Third, + Fourth, + Fifth, + Sixth, + Seventh, + Eighth + } } \ No newline at end of file diff --git a/Scripts/Spells/Base/SpellHelper.cs b/Scripts/Spells/Base/SpellHelper.cs index 047a9927e..fbb88dda6 100644 --- a/Scripts/Spells/Base/SpellHelper.cs +++ b/Scripts/Spells/Base/SpellHelper.cs @@ -1,1428 +1,1473 @@ using System; -using Server.Items; +using System.Collections.Generic; +using Server.Engines.CannedEvil; +using Server.Engines.ConPVP; +using Server.Engines.PartySystem; +using Server.Factions; using Server.Guilds; +using Server.Items; +using Server.Misc; +using Server.Mobiles; using Server.Multis; using Server.Regions; -using Server.Mobiles; -using Server.Targeting; -using Server.Engines.PartySystem; -using Server.Misc; +using Server.Spells.Fifth; using Server.Spells.Necromancy; using Server.Spells.Ninjitsu; -using System.Collections.Generic; using Server.Spells.Seventh; -using Server.Spells.Fifth; +using Server.Targeting; namespace Server { - public class DefensiveSpell - { - public static void Nullify( Mobile from ) - { - if ( !from.CanBeginAction( typeof( DefensiveSpell ) ) ) - new InternalTimer( from ).Start(); - } + public class DefensiveSpell + { + public static void Nullify(Mobile from) + { + if (!from.CanBeginAction(typeof(DefensiveSpell))) + new InternalTimer(from).Start(); + } - private class InternalTimer : Timer - { - private Mobile m_Mobile; + private class InternalTimer : Timer + { + private Mobile m_Mobile; - public InternalTimer( Mobile m ) - : base( TimeSpan.FromMinutes( 1.0 ) ) - { - m_Mobile = m; + public InternalTimer(Mobile m) + : base(TimeSpan.FromMinutes(1.0)) + { + m_Mobile = m; - Priority = TimerPriority.OneSecond; - } + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - m_Mobile.EndAction( typeof( DefensiveSpell ) ); - } - } - } + protected override void OnTick() + { + m_Mobile.EndAction(typeof(DefensiveSpell)); + } + } + } } namespace Server.Spells { - public enum TravelCheckType - { - RecallFrom, - RecallTo, - GateFrom, - GateTo, - Mark, - TeleportFrom, - TeleportTo - } - - public class SpellHelper - { - private static TimeSpan AosDamageDelay = TimeSpan.FromSeconds( 1.0 ); - private static TimeSpan OldDamageDelay = TimeSpan.FromSeconds( 0.5 ); - - public static TimeSpan GetDamageDelayForSpell( Spell sp ) - { - if ( !sp.DelayedDamage ) - return TimeSpan.Zero; - - return (Core.AOS ? AosDamageDelay : OldDamageDelay); - } - - public static bool CheckMulti( Point3D p, Map map ) - { - return CheckMulti( p, map, true, 0); - } - - public static bool CheckMulti(Point3D p, Map map, bool houses) - { - return CheckMulti(p, map, houses, 0); - } - - public static bool CheckMulti( Point3D p, Map map, bool houses, int housingrange ) - { - if ( map == null || map == Map.Internal ) - return false; - - Sector sector = map.GetSector( p.X, p.Y ); - - for( int i = 0; i < sector.Multis.Count; ++i ) - { - BaseMulti multi = sector.Multis[i]; - - if ( multi is BaseHouse ) - { - BaseHouse bh = (BaseHouse)multi; - - if ( ( houses && bh.IsInside( p, 16 ) ) || ( housingrange > 0 && bh.InRange( p, housingrange ) ) ) - return true; - } - else if ( multi.Contains( p )) - { - return true; - } - } - - return false; - } - - public static void Turn( Mobile from, object to ) - { - IPoint3D target = to as IPoint3D; - - if ( target == null ) - return; - - if ( target is Item ) - { - Item item = (Item)target; - - if ( item.RootParent != from ) - from.Direction = from.GetDirectionTo( item.GetWorldLocation() ); - } - else if ( from != target ) - { - from.Direction = from.GetDirectionTo( target ); - } - } - - private static TimeSpan CombatHeatDelay = TimeSpan.FromSeconds( 30.0 ); - private static bool RestrictTravelCombat = true; - - public static bool CheckCombat( Mobile m ) - { - if ( !RestrictTravelCombat ) - return false; - - for( int i = 0; i < m.Aggressed.Count; ++i ) - { - AggressorInfo info = m.Aggressed[i]; - - if ( info.Defender.Player && (DateTime.UtcNow - info.LastCombatTime) < CombatHeatDelay ) - return true; - } - - if ( Core.Expansion == Expansion.AOS ) - { - for( int i = 0; i < m.Aggressors.Count; ++i ) - { - AggressorInfo info = m.Aggressors[i]; - - if ( info.Attacker.Player && (DateTime.UtcNow - info.LastCombatTime) < CombatHeatDelay ) - return true; - } - } - - return false; - } - - public static bool AdjustField( ref Point3D p, Map map, int height, bool mobsBlock ) - { - if ( map == null ) - return false; - - for( int offset = 0; offset < 10; ++offset ) - { - Point3D loc = new Point3D( p.X, p.Y, p.Z - offset ); - - if ( map.CanFit( loc, height, true, mobsBlock ) ) - { - p = loc; - return true; - } - } - - return false; - } - - public static bool CanRevealCaster( Mobile m ) - { - if ( m is BaseCreature ) - { - BaseCreature c = (BaseCreature)m; - - if ( !c.Controlled ) - return true; - } - - return false; - } - - public static void GetSurfaceTop( ref IPoint3D p ) - { - if ( p is Item ) - { - p = ((Item)p).GetSurfaceTop(); - } - else if ( p is StaticTarget ) - { - StaticTarget t = (StaticTarget)p; - int z = t.Z; - - if ( (t.Flags & TileFlag.Surface) == 0 ) - z -= TileData.ItemTable[t.ItemID & TileData.MaxItemValue].CalcHeight; - - p = new Point3D( t.X, t.Y, z ); - } - } - - public static bool AddStatOffset( Mobile m, StatType type, int offset, TimeSpan duration ) - { - if ( offset > 0 ) - return AddStatBonus( m, m, type, offset, duration ); - if ( offset < 0 ) - return AddStatCurse( m, m, type, -offset, duration ); - - return true; - } - - public static bool AddStatBonus( Mobile caster, Mobile target, StatType type ) - { - return AddStatBonus( caster, target, type, GetOffset( caster, target, type, false ), GetDuration( caster, target ) ); - } - - public static bool AddStatBonus( Mobile caster, Mobile target, StatType type, int bonus, TimeSpan duration ) - { - int offset = bonus; - string name = $"[Magic] {type} Offset"; - - StatMod mod = target.GetStatMod( name ); - - if ( mod != null && mod.Offset < 0 ) - { - target.AddStatMod( new StatMod( type, name, mod.Offset + offset, duration ) ); - return true; - } - - if ( mod == null || mod.Offset < offset ) - { - target.AddStatMod( new StatMod( type, name, offset, duration ) ); - return true; - } - - return false; - } - - public static bool AddStatCurse( Mobile caster, Mobile target, StatType type ) - { - return AddStatCurse( caster, target, type, GetOffset( caster, target, type, true ), GetDuration( caster, target ) ); - } - - public static bool AddStatCurse( Mobile caster, Mobile target, StatType type, int curse, TimeSpan duration ) - { - int offset = -curse; - string name = $"[Magic] {type} Offset"; - - StatMod mod = target.GetStatMod( name ); - - if ( mod != null && mod.Offset > 0 ) - { - target.AddStatMod( new StatMod( type, name, mod.Offset + offset, duration ) ); - return true; - } - - if ( mod == null || mod.Offset > offset ) - { - target.AddStatMod( new StatMod( type, name, offset, duration ) ); - return true; - } - - return false; - } - - public static TimeSpan GetDuration( Mobile caster, Mobile target ) - { - if ( Core.AOS ) - return TimeSpan.FromSeconds( ((6 * caster.Skills.EvalInt.Fixed) / 50) + 1 ); - - return TimeSpan.FromSeconds( caster.Skills[SkillName.Magery].Value * 1.2 ); - } - - public static bool DisableSkillCheck { get; set; } - - public static double GetOffsetScalar( Mobile caster, Mobile target, bool curse ) - { - double percent; - - if ( curse ) - percent = 8 + (caster.Skills.EvalInt.Fixed / 100) - (target.Skills.MagicResist.Fixed / 100); - else - percent = 1 + (caster.Skills.EvalInt.Fixed / 100); - - percent *= 0.01; - - if ( percent < 0 ) - percent = 0; - - return percent; - } - - public static int GetOffset( Mobile caster, Mobile target, StatType type, bool curse ) - { - if ( Core.AOS ) - { - if ( !DisableSkillCheck ) - { - caster.CheckSkill( SkillName.EvalInt, 0.0, 120.0 ); - - if ( curse ) - target.CheckSkill( SkillName.MagicResist, 0.0, 120.0 ); - } - - double percent = GetOffsetScalar( caster, target, curse ); - - switch( type ) - { - case StatType.Str: - return (int)(target.RawStr * percent); - case StatType.Dex: - return (int)(target.RawDex * percent); - case StatType.Int: - return (int)(target.RawInt * percent); - } - } - - return 1 + (int)(caster.Skills[SkillName.Magery].Value * 0.1); - } - - public static Guild GetGuildFor( Mobile m ) - { - Guild g = m.Guild as Guild; - - if ( g == null && m is BaseCreature ) - { - BaseCreature c = (BaseCreature)m; - m = c.ControlMaster; + public enum TravelCheckType + { + RecallFrom, + RecallTo, + GateFrom, + GateTo, + Mark, + TeleportFrom, + TeleportTo + } + + public class SpellHelper + { + private static TimeSpan AosDamageDelay = TimeSpan.FromSeconds(1.0); + private static TimeSpan OldDamageDelay = TimeSpan.FromSeconds(0.5); + + private static TimeSpan CombatHeatDelay = TimeSpan.FromSeconds(30.0); + private static bool RestrictTravelCombat = true; + + private static int[] m_Offsets = + { + -1, -1, + -1, 0, + -1, 1, + 0, -1, + 0, 1, + 1, -1, + 1, 0, + 1, 1 + }; + + private static TravelValidator[] m_Validators = + { + IsFeluccaT2A, + IsKhaldun, + IsIlshenar, + IsTrammelWind, + IsFeluccaWind, + IsFeluccaDungeon, + IsTrammelSolenHive, + IsFeluccaSolenHive, + IsCrystalCave, + IsDoomGauntlet, + IsDoomFerry, + IsSafeZone, + IsFactionStronghold, + IsChampionSpawn, + IsTokunoDungeon, + IsLampRoom, + IsGuardianRoom, + IsHeartwood, + IsMLDungeon + }; + + private static bool[,] m_Rules = + { + /*T2A(Fel), Khaldun, Ilshenar, Wind(Tram), Wind(Fel), Dungeons(Fel), Solen(Tram), Solen(Fel), CrystalCave(Malas), Gauntlet(Malas), Gauntlet(Ferry), SafeZone, Stronghold, ChampionSpawn, Dungeons(Tokuno[Malas]), LampRoom(Doom), GuardianRoom(Doom), Heartwood, MLDungeons */ +/* Recall From */ + { + false, false, true, true, false, false, true, false, false, false, false, true, true, false, true, false, + false, false, false + }, +/* Recall To */ + { + false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, + false, false, false, false + }, +/* Gate From */ + { + false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, + false, false, false, false + }, +/* Gate To */ + { + false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, + false, false, false, false + }, +/* Mark In */ + { + false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, + false, false, false, false + }, +/* Tele From */ + { + true, true, true, true, true, true, true, true, false, true, true, true, false, true, true, true, true, + false, true + }, +/* Tele To */ + { + true, true, true, true, true, true, true, true, false, true, false, false, false, true, true, true, true, + false, false + } + }; + + private static Mobile m_TravelCaster; + private static TravelCheckType m_TravelType; + + public static bool DisableSkillCheck{ get; set; } + + public static TimeSpan GetDamageDelayForSpell(Spell sp) + { + if (!sp.DelayedDamage) + return TimeSpan.Zero; + + return Core.AOS ? AosDamageDelay : OldDamageDelay; + } + + public static bool CheckMulti(Point3D p, Map map) + { + return CheckMulti(p, map, true, 0); + } + + public static bool CheckMulti(Point3D p, Map map, bool houses) + { + return CheckMulti(p, map, houses, 0); + } + + public static bool CheckMulti(Point3D p, Map map, bool houses, int housingrange) + { + if (map == null || map == Map.Internal) + return false; + + Sector sector = map.GetSector(p.X, p.Y); + + for (int i = 0; i < sector.Multis.Count; ++i) + { + BaseMulti multi = sector.Multis[i]; + + if (multi is BaseHouse) + { + BaseHouse bh = (BaseHouse)multi; + + if (houses && bh.IsInside(p, 16) || housingrange > 0 && bh.InRange(p, housingrange)) + return true; + } + else if (multi.Contains(p)) + { + return true; + } + } + + return false; + } + + public static void Turn(Mobile from, object to) + { + IPoint3D target = to as IPoint3D; + + if (target == null) + return; + + if (target is Item) + { + Item item = (Item)target; + + if (item.RootParent != from) + from.Direction = from.GetDirectionTo(item.GetWorldLocation()); + } + else if (from != target) + { + from.Direction = from.GetDirectionTo(target); + } + } + + public static bool CheckCombat(Mobile m) + { + if (!RestrictTravelCombat) + return false; + + for (int i = 0; i < m.Aggressed.Count; ++i) + { + AggressorInfo info = m.Aggressed[i]; + + if (info.Defender.Player && DateTime.UtcNow - info.LastCombatTime < CombatHeatDelay) + return true; + } + + if (Core.Expansion == Expansion.AOS) + for (int i = 0; i < m.Aggressors.Count; ++i) + { + AggressorInfo info = m.Aggressors[i]; + + if (info.Attacker.Player && DateTime.UtcNow - info.LastCombatTime < CombatHeatDelay) + return true; + } + + return false; + } + + public static bool AdjustField(ref Point3D p, Map map, int height, bool mobsBlock) + { + if (map == null) + return false; + + for (int offset = 0; offset < 10; ++offset) + { + Point3D loc = new Point3D(p.X, p.Y, p.Z - offset); + + if (map.CanFit(loc, height, true, mobsBlock)) + { + p = loc; + return true; + } + } + + return false; + } + + public static bool CanRevealCaster(Mobile m) + { + if (m is BaseCreature) + { + BaseCreature c = (BaseCreature)m; + + if (!c.Controlled) + return true; + } + + return false; + } + + public static void GetSurfaceTop(ref IPoint3D p) + { + if (p is Item) + { + p = ((Item)p).GetSurfaceTop(); + } + else if (p is StaticTarget) + { + StaticTarget t = (StaticTarget)p; + int z = t.Z; + + if ((t.Flags & TileFlag.Surface) == 0) + z -= TileData.ItemTable[t.ItemID & TileData.MaxItemValue].CalcHeight; + + p = new Point3D(t.X, t.Y, z); + } + } + + public static bool AddStatOffset(Mobile m, StatType type, int offset, TimeSpan duration) + { + if (offset > 0) + return AddStatBonus(m, m, type, offset, duration); + if (offset < 0) + return AddStatCurse(m, m, type, -offset, duration); + + return true; + } + + public static bool AddStatBonus(Mobile caster, Mobile target, StatType type) + { + return AddStatBonus(caster, target, type, GetOffset(caster, target, type, false), GetDuration(caster, target)); + } + + public static bool AddStatBonus(Mobile caster, Mobile target, StatType type, int bonus, TimeSpan duration) + { + int offset = bonus; + string name = $"[Magic] {type} Offset"; + + StatMod mod = target.GetStatMod(name); + + if (mod != null && mod.Offset < 0) + { + target.AddStatMod(new StatMod(type, name, mod.Offset + offset, duration)); + return true; + } + + if (mod == null || mod.Offset < offset) + { + target.AddStatMod(new StatMod(type, name, offset, duration)); + return true; + } + + return false; + } + + public static bool AddStatCurse(Mobile caster, Mobile target, StatType type) + { + return AddStatCurse(caster, target, type, GetOffset(caster, target, type, true), GetDuration(caster, target)); + } + + public static bool AddStatCurse(Mobile caster, Mobile target, StatType type, int curse, TimeSpan duration) + { + int offset = -curse; + string name = $"[Magic] {type} Offset"; + + StatMod mod = target.GetStatMod(name); + + if (mod != null && mod.Offset > 0) + { + target.AddStatMod(new StatMod(type, name, mod.Offset + offset, duration)); + return true; + } + + if (mod == null || mod.Offset > offset) + { + target.AddStatMod(new StatMod(type, name, offset, duration)); + return true; + } + + return false; + } + + public static TimeSpan GetDuration(Mobile caster, Mobile target) + { + if (Core.AOS) + return TimeSpan.FromSeconds(6 * caster.Skills.EvalInt.Fixed / 50 + 1); + + return TimeSpan.FromSeconds(caster.Skills[SkillName.Magery].Value * 1.2); + } + + public static double GetOffsetScalar(Mobile caster, Mobile target, bool curse) + { + double percent; + + if (curse) + percent = 8 + caster.Skills.EvalInt.Fixed / 100 - target.Skills.MagicResist.Fixed / 100; + else + percent = 1 + caster.Skills.EvalInt.Fixed / 100; + + percent *= 0.01; + + if (percent < 0) + percent = 0; + + return percent; + } + + public static int GetOffset(Mobile caster, Mobile target, StatType type, bool curse) + { + if (Core.AOS) + { + if (!DisableSkillCheck) + { + caster.CheckSkill(SkillName.EvalInt, 0.0, 120.0); + + if (curse) + target.CheckSkill(SkillName.MagicResist, 0.0, 120.0); + } + + double percent = GetOffsetScalar(caster, target, curse); + + switch (type) + { + case StatType.Str: + return (int)(target.RawStr * percent); + case StatType.Dex: + return (int)(target.RawDex * percent); + case StatType.Int: + return (int)(target.RawInt * percent); + } + } - if ( m != null ) - g = m.Guild as Guild; - - if ( g == null ) - { - m = c.SummonMaster; - - if ( m != null ) - g = m.Guild as Guild; - } - } - - return g; - } - - public static bool ValidIndirectTarget( Mobile from, Mobile to ) - { - if ( from == to ) - return true; - - if ( to.Hidden && to.AccessLevel > from.AccessLevel ) - return false; - - #region Dueling - PlayerMobile pmFrom = from as PlayerMobile; - PlayerMobile pmTarg = to as PlayerMobile; + return 1 + (int)(caster.Skills[SkillName.Magery].Value * 0.1); + } + + public static Guild GetGuildFor(Mobile m) + { + Guild g = m.Guild as Guild; - if ( pmFrom == null && from is BaseCreature ) - { - BaseCreature bcFrom = (BaseCreature) from; + if (g == null && m is BaseCreature) + { + BaseCreature c = (BaseCreature)m; + m = c.ControlMaster; - if ( bcFrom.Summoned ) - pmFrom = bcFrom.SummonMaster as PlayerMobile; - } + if (m != null) + g = m.Guild as Guild; - if ( pmTarg == null && to is BaseCreature ) - { - BaseCreature bcTarg = (BaseCreature) to; + if (g == null) + { + m = c.SummonMaster; - if ( bcTarg.Summoned ) - pmTarg = bcTarg.SummonMaster as PlayerMobile; - } + if (m != null) + g = m.Guild as Guild; + } + } - if ( pmFrom != null && pmTarg != null ) - { - if ( pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.Started && pmFrom.DuelPlayer != null && pmTarg.DuelPlayer != null ) - return ( pmFrom.DuelPlayer.Participant != pmTarg.DuelPlayer.Participant ); - } - #endregion + return g; + } - Guild fromGuild = GetGuildFor( from ); - Guild toGuild = GetGuildFor( to ); + public static bool ValidIndirectTarget(Mobile from, Mobile to) + { + if (from == to) + return true; - if ( fromGuild != null && toGuild != null && (fromGuild == toGuild || fromGuild.IsAlly( toGuild )) ) - return false; - - Party p = Party.Get( from ); - - if ( p != null && p.Contains( to ) ) - return false; - - if ( to is BaseCreature ) - { - BaseCreature c = (BaseCreature)to; - - if ( c.Controlled || c.Summoned ) - { - if ( c.ControlMaster == from || c.SummonMaster == from ) - return false; - - if ( p != null && (p.Contains( c.ControlMaster ) || p.Contains( c.SummonMaster )) ) - return false; - } - } - - if ( from is BaseCreature ) - { - BaseCreature c = (BaseCreature)from; - - if ( c.Controlled || c.Summoned ) - { - if ( c.ControlMaster == to || c.SummonMaster == to ) - return false; - - p = Party.Get( to ); - - if ( p != null && (p.Contains( c.ControlMaster ) || p.Contains( c.SummonMaster )) ) - return false; - } - } - - if ( to is BaseCreature && !((BaseCreature)to).Controlled && ((BaseCreature)to).InitialInnocent ) - return true; - - int noto = Notoriety.Compute( from, to ); - - return (noto != Notoriety.Innocent || from.Kills >= 5); - } - - private static int[] m_Offsets = { - -1, -1, - -1, 0, - -1, 1, - 0, -1, - 0, 1, - 1, -1, - 1, 0, - 1, 1 - }; - - public static void Summon( BaseCreature creature, Mobile caster, int sound, TimeSpan duration, bool scaleDuration, bool scaleStats ) - { - Map map = caster.Map; - - if ( map == null ) - return; - - double scale = 1.0 + ((caster.Skills[SkillName.Magery].Value - 100.0) / 200.0); - - if ( scaleDuration ) - duration = TimeSpan.FromSeconds( duration.TotalSeconds * scale ); - - if ( scaleStats ) - { - creature.RawStr = (int)(creature.RawStr * scale); - creature.Hits = creature.HitsMax; - - creature.RawDex = (int)(creature.RawDex * scale); - creature.Stam = creature.StamMax; - - creature.RawInt = (int)(creature.RawInt * scale); - creature.Mana = creature.ManaMax; - } - - Point3D p = new Point3D( caster ); - - if ( FindValidSpawnLocation( map, ref p, true ) ) - { - BaseCreature.Summon( creature, caster, p, sound, duration ); - return; - } - - - /* - int offset = Utility.Random( 8 ) * 2; - - for( int i = 0; i < m_Offsets.Length; i += 2 ) - { - int x = caster.X + m_Offsets[(offset + i) % m_Offsets.Length]; - int y = caster.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; - - if ( map.CanSpawnMobile( x, y, caster.Z ) ) - { - BaseCreature.Summon( creature, caster, new Point3D( x, y, caster.Z ), sound, duration ); - return; - } - else - { - int z = map.GetAverageZ( x, y ); - - if ( map.CanSpawnMobile( x, y, z ) ) - { - BaseCreature.Summon( creature, caster, new Point3D( x, y, z ), sound, duration ); - return; - } - } - } - * */ - - creature.Delete(); - caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - - public static bool FindValidSpawnLocation( Map map, ref Point3D p, bool surroundingsOnly ) - { - if ( map == null ) //sanity - return false; - - if ( !surroundingsOnly ) - { - if ( map.CanSpawnMobile( p ) ) //p's fine. - { - p = new Point3D( p ); - return true; - } - - int z = map.GetAverageZ( p.X, p.Y ); - - if ( map.CanSpawnMobile( p.X, p.Y, z ) ) - { - p = new Point3D( p.X, p.Y, z ); - return true; - } - } - - int offset = Utility.Random( 8 ) * 2; - - for( int i = 0; i < m_Offsets.Length; i += 2 ) - { - int x = p.X + m_Offsets[(offset + i) % m_Offsets.Length]; - int y = p.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; - - if ( map.CanSpawnMobile( x, y, p.Z ) ) - { - p = new Point3D( x, y, p.Z ); - return true; - } - - int z = map.GetAverageZ( x, y ); - - if ( map.CanSpawnMobile( x, y, z ) ) - { - p = new Point3D( x, y, z ); - return true; - } - } - - return false; - } - - private delegate bool TravelValidator( Map map, Point3D loc ); - - private static TravelValidator[] m_Validators = { - IsFeluccaT2A, - IsKhaldun, - IsIlshenar, - IsTrammelWind, - IsFeluccaWind, - IsFeluccaDungeon, - IsTrammelSolenHive, - IsFeluccaSolenHive, - IsCrystalCave, - IsDoomGauntlet, - IsDoomFerry, - IsSafeZone, - IsFactionStronghold, - IsChampionSpawn, - IsTokunoDungeon, - IsLampRoom, - IsGuardianRoom, - IsHeartwood, - IsMLDungeon - }; - - private static bool[,] m_Rules = { - /*T2A(Fel), Khaldun, Ilshenar, Wind(Tram), Wind(Fel), Dungeons(Fel), Solen(Tram), Solen(Fel), CrystalCave(Malas), Gauntlet(Malas), Gauntlet(Ferry), SafeZone, Stronghold, ChampionSpawn, Dungeons(Tokuno[Malas]), LampRoom(Doom), GuardianRoom(Doom), Heartwood, MLDungeons */ -/* Recall From */ { false, false, true, true, false, false, true, false, false, false, false, true, true, false, true, false, false, false, false }, -/* Recall To */ { false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false }, -/* Gate From */ { false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false }, -/* Gate To */ { false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false }, -/* Mark In */ { false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false, false }, -/* Tele From */ { true, true, true, true, true, true, true, true, false, true, true, true, false, true, true, true, true, false, true }, -/* Tele To */ { true, true, true, true, true, true, true, true, false, true, false, false, false, true, true, true, true, false, false }, - }; - - public static void SendInvalidMessage( Mobile caster, TravelCheckType type ) - { - if ( type == TravelCheckType.RecallTo || type == TravelCheckType.GateTo ) - caster.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - else if ( type == TravelCheckType.TeleportTo ) - caster.SendLocalizedMessage( 501035 ); // You cannot teleport from here to the destination. - else - caster.SendLocalizedMessage( 501802 ); // Thy spell doth not appear to work... - } - - public static bool CheckTravel( Mobile caster, TravelCheckType type ) - { - return CheckTravel( caster, caster.Map, caster.Location, type ); - } - - public static bool CheckTravel( Map map, Point3D loc, TravelCheckType type ) - { - return CheckTravel( null, map, loc, type ); - } - - private static Mobile m_TravelCaster; - private static TravelCheckType m_TravelType; - - public static bool CheckTravel( Mobile caster, Map map, Point3D loc, TravelCheckType type ) - { - if ( IsInvalid( map, loc ) ) // null, internal, out of bounds - { - if ( caster != null ) - SendInvalidMessage( caster, type ); - - return false; - } - - if ( caster != null && caster.AccessLevel == AccessLevel.Player && caster.Region.IsPartOf( typeof( Jail ) ) ) - { - caster.SendLocalizedMessage( 1114345 ); // You'll need a better jailbreak plan than that! - return false; - } - - // Always allow monsters to teleport - if ( caster is BaseCreature && ( type == TravelCheckType.TeleportTo || type == TravelCheckType.TeleportFrom ) ) - { - BaseCreature bc = (BaseCreature)caster; - - if ( !bc.Controlled && !bc.Summoned ) - return true; - } - - m_TravelCaster = caster; - m_TravelType = type; - - int v = (int)type; - bool isValid = true; - - for( int i = 0; isValid && i < m_Validators.Length; ++i ) - isValid = (m_Rules[v, i] || !m_Validators[i]( map, loc )); - - if ( !isValid && caster != null ) - SendInvalidMessage( caster, type ); - - return isValid; - } - - public static bool IsWindLoc( Point3D loc ) - { - int x = loc.X, y = loc.Y; - - return (x >= 5120 && y >= 0 && x < 5376 && y < 256); - } - - public static bool IsFeluccaWind( Map map, Point3D loc ) - { - return (map == Map.Felucca && IsWindLoc( loc )); - } - - public static bool IsTrammelWind( Map map, Point3D loc ) - { - return (map == Map.Trammel && IsWindLoc( loc )); - } - - public static bool IsIlshenar( Map map, Point3D loc ) - { - return (map == Map.Ilshenar); - } - - public static bool IsSolenHiveLoc( Point3D loc ) - { - int x = loc.X, y = loc.Y; - - return (x >= 5640 && y >= 1776 && x < 5935 && y < 2039); - } - - public static bool IsTrammelSolenHive( Map map, Point3D loc ) - { - return (map == Map.Trammel && IsSolenHiveLoc( loc )); - } - - public static bool IsFeluccaSolenHive( Map map, Point3D loc ) - { - return (map == Map.Felucca && IsSolenHiveLoc( loc )); - } - - public static bool IsFeluccaT2A( Map map, Point3D loc ) - { - int x = loc.X, y = loc.Y; - - return (map == Map.Felucca && x >= 5120 && y >= 2304 && x < 6144 && y < 4096); - } - - public static bool IsAnyT2A( Map map, Point3D loc ) - { - int x = loc.X, y = loc.Y; - - return ((map == Map.Trammel || map == Map.Felucca) && x >= 5120 && y >= 2304 && x < 6144 && y < 4096); - } - - public static bool IsFeluccaDungeon( Map map, Point3D loc ) - { - Region region = Region.Find( loc, map ); - return (region.IsPartOf( typeof( DungeonRegion ) ) && region.Map == Map.Felucca); - } - - public static bool IsKhaldun( Map map, Point3D loc ) - { - return ( Region.Find( loc, map ).Name == "Khaldun" ); - } + if (to.Hidden && to.AccessLevel > from.AccessLevel) + return false; - public static bool IsCrystalCave( Map map, Point3D loc ) - { - if ( map != Map.Malas || loc.Z >= -80 ) - return false; + #region Dueling - int x = loc.X, y = loc.Y; + PlayerMobile pmFrom = from as PlayerMobile; + PlayerMobile pmTarg = to as PlayerMobile; - return ( x >= 1182 && y >= 437 && x < 1211 && y < 470 ) - || ( x >= 1156 && y >= 470 && x < 1211 && y < 503 ) - || ( x >= 1176 && y >= 503 && x < 1208 && y < 509 ) - || ( x >= 1188 && y >= 509 && x < 1201 && y < 513 ); - } + if (pmFrom == null && from is BaseCreature) + { + BaseCreature bcFrom = (BaseCreature)from; - public static bool IsSafeZone( Map map, Point3D loc ) - { - #region Duels - if ( Region.Find( loc, map ).IsPartOf( typeof( Engines.ConPVP.SafeZone ) ) ) - { - if ( m_TravelType == TravelCheckType.TeleportTo || m_TravelType == TravelCheckType.TeleportFrom ) - { - PlayerMobile pm = m_TravelCaster as PlayerMobile; + if (bcFrom.Summoned) + pmFrom = bcFrom.SummonMaster as PlayerMobile; + } - if ( pm?.DuelPlayer != null && !pm.DuelPlayer.Eliminated ) - return true; - } + if (pmTarg == null && to is BaseCreature) + { + BaseCreature bcTarg = (BaseCreature)to; - return true; - } - #endregion + if (bcTarg.Summoned) + pmTarg = bcTarg.SummonMaster as PlayerMobile; + } - return false; - } + if (pmFrom != null && pmTarg != null) + if (pmFrom.DuelContext != null && pmFrom.DuelContext == pmTarg.DuelContext && pmFrom.DuelContext.Started && + pmFrom.DuelPlayer != null && pmTarg.DuelPlayer != null) + return pmFrom.DuelPlayer.Participant != pmTarg.DuelPlayer.Participant; - public static bool IsFactionStronghold( Map map, Point3D loc ) - { - /*// Teleporting is allowed, but only for faction members - if ( !Core.AOS && m_TravelCaster != null && (m_TravelType == TravelCheckType.TeleportTo || m_TravelType == TravelCheckType.TeleportFrom) ) - { - if ( Factions.Faction.Find( m_TravelCaster, true, true ) != null ) - return false; - }*/ + #endregion - return (Region.Find( loc, map ).IsPartOf( typeof( Factions.StrongholdRegion ) )); - } + Guild fromGuild = GetGuildFor(from); + Guild toGuild = GetGuildFor(to); - public static bool IsChampionSpawn( Map map, Point3D loc ) - { - return (Region.Find( loc, map ).IsPartOf( typeof( Engines.CannedEvil.ChampionSpawnRegion ) )); - } + if (fromGuild != null && toGuild != null && (fromGuild == toGuild || fromGuild.IsAlly(toGuild))) + return false; - public static bool IsDoomFerry( Map map, Point3D loc ) - { - if ( map != Map.Malas ) - return false; + Party p = Party.Get(from); - int x = loc.X, y = loc.Y; + if (p != null && p.Contains(to)) + return false; - if ( x >= 426 && y >= 314 && x <= 430 && y <= 331 ) - return true; + if (to is BaseCreature) + { + BaseCreature c = (BaseCreature)to; - if ( x >= 406 && y >= 247 && x <= 410 && y <= 264 ) - return true; + if (c.Controlled || c.Summoned) + { + if (c.ControlMaster == from || c.SummonMaster == from) + return false; - return false; - } + if (p != null && (p.Contains(c.ControlMaster) || p.Contains(c.SummonMaster))) + return false; + } + } + + if (from is BaseCreature) + { + BaseCreature c = (BaseCreature)from; - public static bool IsTokunoDungeon( Map map, Point3D loc ) - { - //The tokuno dungeons are really inside malas - if ( map != Map.Malas ) - return false; + if (c.Controlled || c.Summoned) + { + if (c.ControlMaster == to || c.SummonMaster == to) + return false; - int x = loc.X, y = loc.Y, z = loc.Z; + p = Party.Get(to); - bool r1 = (x >= 0 && y >= 0 && x <= 128 && y <= 128); - bool r2 = (x >= 45 && y >= 320 && x < 195 && y < 710); + if (p != null && (p.Contains(c.ControlMaster) || p.Contains(c.SummonMaster))) + return false; + } + } - return (r1 || r2); - } + if (to is BaseCreature && !((BaseCreature)to).Controlled && ((BaseCreature)to).InitialInnocent) + return true; - public static bool IsDoomGauntlet( Map map, Point3D loc ) - { - if ( map != Map.Malas ) - return false; + int noto = Notoriety.Compute(from, to); - int x = loc.X - 256, y = loc.Y - 304; + return noto != Notoriety.Innocent || from.Kills >= 5; + } - return (x >= 0 && y >= 0 && x < 256 && y < 256); - } + public static void Summon(BaseCreature creature, Mobile caster, int sound, TimeSpan duration, bool scaleDuration, + bool scaleStats) + { + Map map = caster.Map; - public static bool IsLampRoom( Map map, Point3D loc ) - { - if ( map != Map.Malas ) - return false; + if (map == null) + return; - int x = loc.X, y = loc.Y; + double scale = 1.0 + (caster.Skills[SkillName.Magery].Value - 100.0) / 200.0; - return ( x >= 465 && y >= 92 && x < 474 && y < 102 ); - } + if (scaleDuration) + duration = TimeSpan.FromSeconds(duration.TotalSeconds * scale); - public static bool IsGuardianRoom( Map map, Point3D loc ) - { - if ( map != Map.Malas ) - return false; + if (scaleStats) + { + creature.RawStr = (int)(creature.RawStr * scale); + creature.Hits = creature.HitsMax; + + creature.RawDex = (int)(creature.RawDex * scale); + creature.Stam = creature.StamMax; + + creature.RawInt = (int)(creature.RawInt * scale); + creature.Mana = creature.ManaMax; + } + + Point3D p = new Point3D(caster); + + if (FindValidSpawnLocation(map, ref p, true)) + { + BaseCreature.Summon(creature, caster, p, sound, duration); + return; + } + + + /* + int offset = Utility.Random( 8 ) * 2; + + for( int i = 0; i < m_Offsets.Length; i += 2 ) + { + int x = caster.X + m_Offsets[(offset + i) % m_Offsets.Length]; + int y = caster.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; + + if ( map.CanSpawnMobile( x, y, caster.Z ) ) + { + BaseCreature.Summon( creature, caster, new Point3D( x, y, caster.Z ), sound, duration ); + return; + } + else + { + int z = map.GetAverageZ( x, y ); + + if ( map.CanSpawnMobile( x, y, z ) ) + { + BaseCreature.Summon( creature, caster, new Point3D( x, y, z ), sound, duration ); + return; + } + } + } + * */ + + creature.Delete(); + caster.SendLocalizedMessage(501942); // That location is blocked. + } + + public static bool FindValidSpawnLocation(Map map, ref Point3D p, bool surroundingsOnly) + { + if (map == null) //sanity + return false; + + if (!surroundingsOnly) + { + if (map.CanSpawnMobile(p)) //p's fine. + { + p = new Point3D(p); + return true; + } + + int z = map.GetAverageZ(p.X, p.Y); + + if (map.CanSpawnMobile(p.X, p.Y, z)) + { + p = new Point3D(p.X, p.Y, z); + return true; + } + } + + int offset = Utility.Random(8) * 2; + + for (int i = 0; i < m_Offsets.Length; i += 2) + { + int x = p.X + m_Offsets[(offset + i) % m_Offsets.Length]; + int y = p.Y + m_Offsets[(offset + i + 1) % m_Offsets.Length]; + + if (map.CanSpawnMobile(x, y, p.Z)) + { + p = new Point3D(x, y, p.Z); + return true; + } + + int z = map.GetAverageZ(x, y); + + if (map.CanSpawnMobile(x, y, z)) + { + p = new Point3D(x, y, z); + return true; + } + } + + return false; + } + + public static void SendInvalidMessage(Mobile caster, TravelCheckType type) + { + if (type == TravelCheckType.RecallTo || type == TravelCheckType.GateTo) + caster.SendLocalizedMessage(1019004); // You are not allowed to travel there. + else if (type == TravelCheckType.TeleportTo) + caster.SendLocalizedMessage(501035); // You cannot teleport from here to the destination. + else + caster.SendLocalizedMessage(501802); // Thy spell doth not appear to work... + } + + public static bool CheckTravel(Mobile caster, TravelCheckType type) + { + return CheckTravel(caster, caster.Map, caster.Location, type); + } + + public static bool CheckTravel(Map map, Point3D loc, TravelCheckType type) + { + return CheckTravel(null, map, loc, type); + } + + public static bool CheckTravel(Mobile caster, Map map, Point3D loc, TravelCheckType type) + { + if (IsInvalid(map, loc)) // null, internal, out of bounds + { + if (caster != null) + SendInvalidMessage(caster, type); + + return false; + } + + if (caster != null && caster.AccessLevel == AccessLevel.Player && caster.Region.IsPartOf(typeof(Jail))) + { + caster.SendLocalizedMessage(1114345); // You'll need a better jailbreak plan than that! + return false; + } + + // Always allow monsters to teleport + if (caster is BaseCreature && (type == TravelCheckType.TeleportTo || type == TravelCheckType.TeleportFrom)) + { + BaseCreature bc = (BaseCreature)caster; + + if (!bc.Controlled && !bc.Summoned) + return true; + } + + m_TravelCaster = caster; + m_TravelType = type; + + int v = (int)type; + bool isValid = true; + + for (int i = 0; isValid && i < m_Validators.Length; ++i) + isValid = m_Rules[v, i] || !m_Validators[i](map, loc); + + if (!isValid && caster != null) + SendInvalidMessage(caster, type); + + return isValid; + } + + public static bool IsWindLoc(Point3D loc) + { + int x = loc.X, y = loc.Y; + + return x >= 5120 && y >= 0 && x < 5376 && y < 256; + } + + public static bool IsFeluccaWind(Map map, Point3D loc) + { + return map == Map.Felucca && IsWindLoc(loc); + } + + public static bool IsTrammelWind(Map map, Point3D loc) + { + return map == Map.Trammel && IsWindLoc(loc); + } + + public static bool IsIlshenar(Map map, Point3D loc) + { + return map == Map.Ilshenar; + } + + public static bool IsSolenHiveLoc(Point3D loc) + { + int x = loc.X, y = loc.Y; + + return x >= 5640 && y >= 1776 && x < 5935 && y < 2039; + } + + public static bool IsTrammelSolenHive(Map map, Point3D loc) + { + return map == Map.Trammel && IsSolenHiveLoc(loc); + } + + public static bool IsFeluccaSolenHive(Map map, Point3D loc) + { + return map == Map.Felucca && IsSolenHiveLoc(loc); + } + + public static bool IsFeluccaT2A(Map map, Point3D loc) + { + int x = loc.X, y = loc.Y; + + return map == Map.Felucca && x >= 5120 && y >= 2304 && x < 6144 && y < 4096; + } + + public static bool IsAnyT2A(Map map, Point3D loc) + { + int x = loc.X, y = loc.Y; + + return (map == Map.Trammel || map == Map.Felucca) && x >= 5120 && y >= 2304 && x < 6144 && y < 4096; + } - int x = loc.X, y = loc.Y; + public static bool IsFeluccaDungeon(Map map, Point3D loc) + { + Region region = Region.Find(loc, map); + return region.IsPartOf(typeof(DungeonRegion)) && region.Map == Map.Felucca; + } - return ( x >= 356 && y >= 5 && x < 375 && y < 25 ); - } + public static bool IsKhaldun(Map map, Point3D loc) + { + return Region.Find(loc, map).Name == "Khaldun"; + } - public static bool IsHeartwood( Map map, Point3D loc ) - { - int x = loc.X, y = loc.Y; + public static bool IsCrystalCave(Map map, Point3D loc) + { + if (map != Map.Malas || loc.Z >= -80) + return false; - return (map == Map.Trammel || map == Map.Felucca) && (x >= 6911 && y >= 254 && x < 7167 && y < 511); - } + int x = loc.X, y = loc.Y; - public static bool IsMLDungeon( Map map, Point3D loc ) - { - return MondainsLegacy.IsMLRegion( Region.Find( loc, map ) ); - } + return x >= 1182 && y >= 437 && x < 1211 && y < 470 + || x >= 1156 && y >= 470 && x < 1211 && y < 503 + || x >= 1176 && y >= 503 && x < 1208 && y < 509 + || x >= 1188 && y >= 509 && x < 1201 && y < 513; + } - public static bool IsInvalid( Map map, Point3D loc ) - { - if ( map == null || map == Map.Internal ) - return true; + public static bool IsSafeZone(Map map, Point3D loc) + { + #region Duels - int x = loc.X, y = loc.Y; + if (Region.Find(loc, map).IsPartOf(typeof(SafeZone))) + { + if (m_TravelType == TravelCheckType.TeleportTo || m_TravelType == TravelCheckType.TeleportFrom) + { + PlayerMobile pm = m_TravelCaster as PlayerMobile; - return (x < 0 || y < 0 || x >= map.Width || y >= map.Height); - } + if (pm?.DuelPlayer != null && !pm.DuelPlayer.Eliminated) + return true; + } - //towns - public static bool IsTown( IPoint3D loc, Mobile caster ) - { - if ( loc is Item ) - loc = ((Item)loc).GetWorldLocation(); + return true; + } - return IsTown( new Point3D( loc ), caster ); - } + #endregion - public static bool IsTown( Point3D loc, Mobile caster ) - { - Map map = caster.Map; + return false; + } - if ( map == null ) - return false; + public static bool IsFactionStronghold(Map map, Point3D loc) + { + /*// Teleporting is allowed, but only for faction members + if ( !Core.AOS && m_TravelCaster != null && (m_TravelType == TravelCheckType.TeleportTo || m_TravelType == TravelCheckType.TeleportFrom) ) + { + if ( Factions.Faction.Find( m_TravelCaster, true, true ) != null ) + return false; + }*/ - #region Dueling - Engines.ConPVP.SafeZone sz = (Engines.ConPVP.SafeZone) Region.Find( loc, map ).GetRegion( typeof( Engines.ConPVP.SafeZone ) ); + return Region.Find(loc, map).IsPartOf(typeof(StrongholdRegion)); + } - if ( sz != null ) - { - PlayerMobile pm = (PlayerMobile) caster; + public static bool IsChampionSpawn(Map map, Point3D loc) + { + return Region.Find(loc, map).IsPartOf(typeof(ChampionSpawnRegion)); + } - if ( pm?.DuelContext == null || !pm.DuelContext.Started || pm.DuelPlayer == null || pm.DuelPlayer.Eliminated ) - return true; - } - #endregion + public static bool IsDoomFerry(Map map, Point3D loc) + { + if (map != Map.Malas) + return false; - GuardedRegion reg = (GuardedRegion) Region.Find( loc, map ).GetRegion( typeof( GuardedRegion ) ); + int x = loc.X, y = loc.Y; - return (reg != null && !reg.IsDisabled()); - } + if (x >= 426 && y >= 314 && x <= 430 && y <= 331) + return true; - public static bool CheckTown( IPoint3D loc, Mobile caster ) - { - if ( loc is Item ) - loc = ((Item)loc).GetWorldLocation(); + if (x >= 406 && y >= 247 && x <= 410 && y <= 264) + return true; - return CheckTown( new Point3D( loc ), caster ); - } + return false; + } - public static bool CheckTown( Point3D loc, Mobile caster ) - { - if ( IsTown( loc, caster ) ) - { - caster.SendLocalizedMessage( 500946 ); // You cannot cast this in town! - return false; - } + public static bool IsTokunoDungeon(Map map, Point3D loc) + { + //The tokuno dungeons are really inside malas + if (map != Map.Malas) + return false; - return true; - } + int x = loc.X, y = loc.Y, z = loc.Z; - //magic reflection - public static void CheckReflect( int circle, Mobile caster, ref Mobile target ) - { - CheckReflect( circle, ref caster, ref target ); - } + bool r1 = x >= 0 && y >= 0 && x <= 128 && y <= 128; + bool r2 = x >= 45 && y >= 320 && x < 195 && y < 710; - public static void CheckReflect( int circle, ref Mobile caster, ref Mobile target ) - { - if ( target.MagicDamageAbsorb > 0 ) - { - ++circle; + return r1 || r2; + } - target.MagicDamageAbsorb -= circle; + public static bool IsDoomGauntlet(Map map, Point3D loc) + { + if (map != Map.Malas) + return false; - // This order isn't very intuitive, but you have to nullify reflect before target gets switched + int x = loc.X - 256, y = loc.Y - 304; - bool reflect = (target.MagicDamageAbsorb >= 0); - - (target as BaseCreature)?.CheckReflect( caster, ref reflect ); + return x >= 0 && y >= 0 && x < 256 && y < 256; + } - if ( target.MagicDamageAbsorb <= 0 ) - { - target.MagicDamageAbsorb = 0; - DefensiveSpell.Nullify( target ); - } - - if ( reflect ) - { - target.FixedEffect( 0x37B9, 10, 5 ); - - Mobile temp = caster; - caster = target; - target = temp; - } - } - else if ( target is BaseCreature ) - { - bool reflect = false; + public static bool IsLampRoom(Map map, Point3D loc) + { + if (map != Map.Malas) + return false; - ((BaseCreature)target).CheckReflect( caster, ref reflect ); + int x = loc.X, y = loc.Y; - if ( reflect ) - { - target.FixedEffect( 0x37B9, 10, 5 ); + return x >= 465 && y >= 92 && x < 474 && y < 102; + } - Mobile temp = caster; - caster = target; - target = temp; - } - } - } - - public static void Damage( Spell spell, Mobile target, double damage ) - { - TimeSpan ts = GetDamageDelayForSpell( spell ); - - Damage( spell, ts, target, spell.Caster, damage ); - } - - public static void Damage( TimeSpan delay, Mobile target, double damage ) - { - Damage( delay, target, null, damage ); - } - - public static void Damage( TimeSpan delay, Mobile target, Mobile from, double damage ) - { - Damage( null, delay, target, from, damage ); - } - - public static void Damage( Spell spell, TimeSpan delay, Mobile target, Mobile from, double damage ) - { - int iDamage = (int)damage; - - if ( delay == TimeSpan.Zero ) - { - (from as BaseCreature)?.AlterSpellDamageTo( target, ref iDamage ); - - (target as BaseCreature)?.AlterSpellDamageFrom( from, ref iDamage ); - - target.Damage( iDamage, from ); - } - else - { - new SpellDamageTimer( spell, target, from, iDamage, delay ).Start(); - } - - if ( target is BaseCreature && from != null && delay == TimeSpan.Zero ) - { - BaseCreature c = (BaseCreature) target; - - c.OnHarmfulSpell( from ); - c.OnDamagedBySpell( from ); - } - } - - public static void Damage( Spell spell, Mobile target, double damage, int phys, int fire, int cold, int pois, int nrgy ) - { - TimeSpan ts = GetDamageDelayForSpell( spell ); - - Damage( spell, ts, target, spell.Caster, damage, phys, fire, cold, pois, nrgy, DFAlgorithm.Standard ); - } - - public static void Damage( Spell spell, Mobile target, double damage, int phys, int fire, int cold, int pois, int nrgy, DFAlgorithm dfa ) - { - TimeSpan ts = GetDamageDelayForSpell( spell ); - - Damage( spell, ts, target, spell.Caster, damage, phys, fire, cold, pois, nrgy, dfa ); - } - - public static void Damage( TimeSpan delay, Mobile target, double damage, int phys, int fire, int cold, int pois, int nrgy ) - { - Damage( delay, target, null, damage, phys, fire, cold, pois, nrgy ); - } - - public static void Damage( TimeSpan delay, Mobile target, Mobile from, double damage, int phys, int fire, int cold, int pois, int nrgy ) - { - Damage( delay, target, from, damage, phys, fire, cold, pois, nrgy, DFAlgorithm.Standard ); - } - - public static void Damage( TimeSpan delay, Mobile target, Mobile from, double damage, int phys, int fire, int cold, int pois, int nrgy, DFAlgorithm dfa ) - { - Damage( null, delay, target, from, damage, phys, fire, cold, pois, nrgy, dfa ); - } - - public static void Damage( Spell spell, TimeSpan delay, Mobile target, Mobile from, double damage, int phys, int fire, int cold, int pois, int nrgy, DFAlgorithm dfa ) - { - int iDamage = (int)damage; - - if ( delay == TimeSpan.Zero ) - { - (from as BaseCreature)?.AlterSpellDamageTo( target, ref iDamage ); - - (target as BaseCreature)?.AlterSpellDamageFrom( from, ref iDamage ); - - WeightOverloading.DFA = dfa; - - int damageGiven = AOS.Damage( target, from, iDamage, phys, fire, cold, pois, nrgy ); - - if ( from != null ) // sanity check - { - DoLeech( damageGiven, from, target ); - } - - WeightOverloading.DFA = DFAlgorithm.Standard; - } - else - { - new SpellDamageTimerAOS( spell, target, from, iDamage, phys, fire, cold, pois, nrgy, delay, dfa ).Start(); - } - - if ( target is BaseCreature && from != null && delay == TimeSpan.Zero ) - { - BaseCreature c = (BaseCreature) target; - - c.OnHarmfulSpell( from ); - c.OnDamagedBySpell( from ); - } - } - - public static void DoLeech( int damageGiven, Mobile from, Mobile target ) - { - TransformContext context = TransformationSpellHelper.GetContext( from ); - - if ( context != null ) /* cleanup */ - { - if ( context.Type == typeof( WraithFormSpell ) ) - { - int wraithLeech = ( 5 + (int)( ( 15 * from.Skills.SpiritSpeak.Value ) / 100 ) ); // Wraith form gives 5-20% mana leech - int manaLeech = AOS.Scale( damageGiven, wraithLeech ); - if ( manaLeech != 0 ) - { - from.Mana += manaLeech; - from.PlaySound( 0x44D ); - } - } - else if ( context.Type == typeof( VampiricEmbraceSpell ) ) - { - from.Hits += AOS.Scale( damageGiven, 20 ); - from.PlaySound( 0x44D ); - } - } - } - - public static void Heal( int amount, Mobile target, Mobile from ) - { - Heal( amount, target, from, true ); - } - public static void Heal( int amount, Mobile target, Mobile from, bool message ) - { - //TODO: All Healing *spells* go through ArcaneEmpowerment - target.Heal( amount, from, message ); - } - - private class SpellDamageTimer : Timer - { - private Mobile m_Target, m_From; - private int m_Damage; - private Spell m_Spell; - - public SpellDamageTimer( Spell s, Mobile target, Mobile from, int damage, TimeSpan delay ) - : base( delay ) - { - m_Target = target; - m_From = from; - m_Damage = damage; - m_Spell = s; - - if ( m_Spell != null && m_Spell.DelayedDamage && !m_Spell.DelayedDamageStacking ) - m_Spell.StartDelayedDamageContext( target, this ); - - Priority = TimerPriority.TwentyFiveMS; - } - - protected override void OnTick() - { - (m_From as BaseCreature)?.AlterSpellDamageTo( m_Target, ref m_Damage ); - - (m_Target as BaseCreature)?.AlterSpellDamageFrom( m_From, ref m_Damage ); - - m_Target.Damage( m_Damage ); - m_Spell?.RemoveDelayedDamageContext( m_Target ); - } - } - - private class SpellDamageTimerAOS : Timer - { - private Mobile m_Target, m_From; - private int m_Damage; - private int m_Phys, m_Fire, m_Cold, m_Pois, m_Nrgy; - private DFAlgorithm m_DFA; - private Spell m_Spell; - - public SpellDamageTimerAOS( Spell s, Mobile target, Mobile from, int damage, int phys, int fire, int cold, int pois, int nrgy, TimeSpan delay, DFAlgorithm dfa ) - : base( delay ) - { - m_Target = target; - m_From = from; - m_Damage = damage; - m_Phys = phys; - m_Fire = fire; - m_Cold = cold; - m_Pois = pois; - m_Nrgy = nrgy; - m_DFA = dfa; - m_Spell = s; - if ( m_Spell != null && m_Spell.DelayedDamage && !m_Spell.DelayedDamageStacking ) - m_Spell.StartDelayedDamageContext( target, this ); - - Priority = TimerPriority.TwentyFiveMS; - } - - protected override void OnTick() - { - if ( m_From is BaseCreature && m_Target != null ) - ((BaseCreature)m_From).AlterSpellDamageTo( m_Target, ref m_Damage ); - - if ( m_Target is BaseCreature && m_From != null ) - ((BaseCreature)m_Target).AlterSpellDamageFrom( m_From, ref m_Damage ); - - WeightOverloading.DFA = m_DFA; - - int damageGiven = AOS.Damage( m_Target, m_From, m_Damage, m_Phys, m_Fire, m_Cold, m_Pois, m_Nrgy ); - - if ( m_From != null ) // sanity check - { - DoLeech( damageGiven, m_From, m_Target ); - } - - WeightOverloading.DFA = DFAlgorithm.Standard; - - if ( m_Target is BaseCreature && m_From != null ) - { - BaseCreature c = (BaseCreature) m_Target; - - c.OnHarmfulSpell( m_From ); - c.OnDamagedBySpell( m_From ); - } - - m_Spell?.RemoveDelayedDamageContext( m_Target ); - - } - } - } - - public class TransformationSpellHelper - { - #region Context Stuff - private static Dictionary m_Table = new Dictionary(); - - public static void AddContext( Mobile m, TransformContext context ) - { - m_Table[m] = context; - } - - public static void RemoveContext( Mobile m, bool resetGraphics ) - { - TransformContext context = GetContext( m ); - - if ( context != null ) - RemoveContext( m, context, resetGraphics ); - } - - public static void RemoveContext( Mobile m, TransformContext context, bool resetGraphics ) - { - if ( m_Table.ContainsKey( m ) ) - { - m_Table.Remove( m ); - - List mods = context.Mods; - - for( int i = 0; i < mods.Count; ++i ) - m.RemoveResistanceMod( mods[i] ); - - if ( resetGraphics ) - { - m.HueMod = -1; - m.BodyMod = 0; - } - - context.Timer.Stop(); - context.Spell.RemoveEffect( m ); - } - } - - public static TransformContext GetContext( Mobile m ) - { - m_Table.TryGetValue( m, out TransformContext context ); - - return context; - } - - public static bool UnderTransformation( Mobile m ) - { - return (GetContext( m ) != null); - } - - public static bool UnderTransformation( Mobile m, Type type ) - { - TransformContext context = GetContext( m ); - - return (context != null && context.Type == type); - } - #endregion - - public static bool CheckCast( Mobile caster, Spell spell ) - { - if ( Factions.Sigil.ExistsOn( caster ) ) - { - caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } - - if ( !caster.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - caster.SendLocalizedMessage( 1061628 ); // You can't do that while polymorphed. - return false; - } - if ( AnimalForm.UnderTransformation( caster ) ) - { - caster.SendLocalizedMessage( 1061091 ); // You cannot cast that spell in this form. - return false; - } - - return true; - } - - public static bool OnCast( Mobile caster, Spell spell ) - { - ITransformationSpell transformSpell = spell as ITransformationSpell; - - if ( transformSpell == null ) - return false; - - if ( Factions.Sigil.ExistsOn( caster ) ) - { - caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( !caster.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - caster.SendLocalizedMessage( 1061628 ); // You can't do that while polymorphed. - } - else if ( DisguiseTimers.IsDisguised( caster ) ) - { - caster.SendLocalizedMessage( 1061631 ); // You can't do that while disguised. - return false; - } - else if ( AnimalForm.UnderTransformation( caster ) ) - { - caster.SendLocalizedMessage( 1061091 ); // You cannot cast that spell in this form. - } - else if ( !caster.CanBeginAction( typeof( IncognitoSpell ) ) || (caster.IsBodyMod && GetContext( caster ) == null) ) - { - spell.DoFizzle(); - } - else if ( spell.CheckSequence() ) - { - TransformContext context = GetContext( caster ); - Type ourType = spell.GetType(); - - bool wasTransformed = (context != null); - bool ourTransform = (wasTransformed && context.Type == ourType); - - if ( wasTransformed ) - { - RemoveContext( caster, context, ourTransform ); - - if ( ourTransform ) - { - caster.PlaySound( 0xFA ); - caster.FixedParticles( 0x3728, 1, 13, 5042, EffectLayer.Waist ); - } - } - - if ( !ourTransform ) - { - List mods = new List(); - - if ( transformSpell.PhysResistOffset != 0 ) - mods.Add( new ResistanceMod( ResistanceType.Physical, transformSpell.PhysResistOffset ) ); - - if ( transformSpell.FireResistOffset != 0 ) - mods.Add( new ResistanceMod( ResistanceType.Fire, transformSpell.FireResistOffset ) ); - - if ( transformSpell.ColdResistOffset != 0 ) - mods.Add( new ResistanceMod( ResistanceType.Cold, transformSpell.ColdResistOffset ) ); - - if ( transformSpell.PoisResistOffset != 0 ) - mods.Add( new ResistanceMod( ResistanceType.Poison, transformSpell.PoisResistOffset ) ); - - if ( transformSpell.NrgyResistOffset != 0 ) - mods.Add( new ResistanceMod( ResistanceType.Energy, transformSpell.NrgyResistOffset ) ); - - if ( !((Body)transformSpell.Body).IsHuman ) - { - IMount mt = caster.Mount; - - if ( mt != null ) - mt.Rider = null; - } - - caster.BodyMod = transformSpell.Body; - caster.HueMod = transformSpell.Hue; - - for( int i = 0; i < mods.Count; ++i ) - caster.AddResistanceMod( mods[i] ); - - transformSpell.DoEffect( caster ); - - Timer timer = new TransformTimer( caster, transformSpell ); - timer.Start(); - - AddContext( caster, new TransformContext( timer, mods, ourType, transformSpell ) ); - return true; - } - } - - return false; - } - } - - public interface ITransformationSpell - { - int Body { get; } - int Hue { get; } - - int PhysResistOffset { get; } - int FireResistOffset { get; } - int ColdResistOffset { get; } - int PoisResistOffset { get; } - int NrgyResistOffset { get; } - - double TickRate { get; } - void OnTick( Mobile m ); - - void DoEffect( Mobile m ); - void RemoveEffect( Mobile m ); - } - - - public class TransformContext - { - public Timer Timer { get; } - - public List Mods { get; } - - public Type Type { get; } - - public ITransformationSpell Spell { get; } - - public TransformContext( Timer timer, List mods, Type type, ITransformationSpell spell ) - { - Timer = timer; - Mods = mods; - Type = type; - Spell = spell; - } - } - - public class TransformTimer : Timer - { - private Mobile m_Mobile; - private ITransformationSpell m_Spell; - - public TransformTimer( Mobile from, ITransformationSpell spell ) - : base( TimeSpan.FromSeconds( spell.TickRate ), TimeSpan.FromSeconds( spell.TickRate ) ) - { - m_Mobile = from; - m_Spell = spell; - - Priority = TimerPriority.TwoFiftyMS; - } + public static bool IsGuardianRoom(Map map, Point3D loc) + { + if (map != Map.Malas) + return false; - protected override void OnTick() - { - if ( m_Mobile.Deleted || !m_Mobile.Alive || m_Mobile.Body != m_Spell.Body || m_Mobile.Hue != m_Spell.Hue ) - { - TransformationSpellHelper.RemoveContext( m_Mobile, true ); - Stop(); - } - else - { - m_Spell.OnTick( m_Mobile ); - } - } - } -} + int x = loc.X, y = loc.Y; + + return x >= 356 && y >= 5 && x < 375 && y < 25; + } + + public static bool IsHeartwood(Map map, Point3D loc) + { + int x = loc.X, y = loc.Y; + + return (map == Map.Trammel || map == Map.Felucca) && x >= 6911 && y >= 254 && x < 7167 && y < 511; + } + + public static bool IsMLDungeon(Map map, Point3D loc) + { + return MondainsLegacy.IsMLRegion(Region.Find(loc, map)); + } + + public static bool IsInvalid(Map map, Point3D loc) + { + if (map == null || map == Map.Internal) + return true; + + int x = loc.X, y = loc.Y; + + return x < 0 || y < 0 || x >= map.Width || y >= map.Height; + } + + //towns + public static bool IsTown(IPoint3D loc, Mobile caster) + { + if (loc is Item) + loc = ((Item)loc).GetWorldLocation(); + + return IsTown(new Point3D(loc), caster); + } + + public static bool IsTown(Point3D loc, Mobile caster) + { + Map map = caster.Map; + + if (map == null) + return false; + + #region Dueling + + SafeZone sz = (SafeZone)Region.Find(loc, map).GetRegion(typeof(SafeZone)); + + if (sz != null) + { + PlayerMobile pm = (PlayerMobile)caster; + + if (pm?.DuelContext == null || !pm.DuelContext.Started || pm.DuelPlayer == null || pm.DuelPlayer.Eliminated) + return true; + } + + #endregion + + GuardedRegion reg = (GuardedRegion)Region.Find(loc, map).GetRegion(typeof(GuardedRegion)); + + return reg != null && !reg.IsDisabled(); + } + + public static bool CheckTown(IPoint3D loc, Mobile caster) + { + if (loc is Item) + loc = ((Item)loc).GetWorldLocation(); + + return CheckTown(new Point3D(loc), caster); + } + + public static bool CheckTown(Point3D loc, Mobile caster) + { + if (IsTown(loc, caster)) + { + caster.SendLocalizedMessage(500946); // You cannot cast this in town! + return false; + } + + return true; + } + + //magic reflection + public static void CheckReflect(int circle, Mobile caster, ref Mobile target) + { + CheckReflect(circle, ref caster, ref target); + } + + public static void CheckReflect(int circle, ref Mobile caster, ref Mobile target) + { + if (target.MagicDamageAbsorb > 0) + { + ++circle; + + target.MagicDamageAbsorb -= circle; + + // This order isn't very intuitive, but you have to nullify reflect before target gets switched + + bool reflect = target.MagicDamageAbsorb >= 0; + + (target as BaseCreature)?.CheckReflect(caster, ref reflect); + + if (target.MagicDamageAbsorb <= 0) + { + target.MagicDamageAbsorb = 0; + DefensiveSpell.Nullify(target); + } + + if (reflect) + { + target.FixedEffect(0x37B9, 10, 5); + + Mobile temp = caster; + caster = target; + target = temp; + } + } + else if (target is BaseCreature) + { + bool reflect = false; + + ((BaseCreature)target).CheckReflect(caster, ref reflect); + + if (reflect) + { + target.FixedEffect(0x37B9, 10, 5); + + Mobile temp = caster; + caster = target; + target = temp; + } + } + } + + public static void Damage(Spell spell, Mobile target, double damage) + { + TimeSpan ts = GetDamageDelayForSpell(spell); + + Damage(spell, ts, target, spell.Caster, damage); + } + + public static void Damage(TimeSpan delay, Mobile target, double damage) + { + Damage(delay, target, null, damage); + } + + public static void Damage(TimeSpan delay, Mobile target, Mobile from, double damage) + { + Damage(null, delay, target, from, damage); + } + + public static void Damage(Spell spell, TimeSpan delay, Mobile target, Mobile from, double damage) + { + int iDamage = (int)damage; + + if (delay == TimeSpan.Zero) + { + (from as BaseCreature)?.AlterSpellDamageTo(target, ref iDamage); + + (target as BaseCreature)?.AlterSpellDamageFrom(from, ref iDamage); + + target.Damage(iDamage, from); + } + else + { + new SpellDamageTimer(spell, target, from, iDamage, delay).Start(); + } + + if (target is BaseCreature && from != null && delay == TimeSpan.Zero) + { + BaseCreature c = (BaseCreature)target; + + c.OnHarmfulSpell(from); + c.OnDamagedBySpell(from); + } + } + + public static void Damage(Spell spell, Mobile target, double damage, int phys, int fire, int cold, int pois, + int nrgy) + { + TimeSpan ts = GetDamageDelayForSpell(spell); + + Damage(spell, ts, target, spell.Caster, damage, phys, fire, cold, pois, nrgy, DFAlgorithm.Standard); + } + + public static void Damage(Spell spell, Mobile target, double damage, int phys, int fire, int cold, int pois, + int nrgy, DFAlgorithm dfa) + { + TimeSpan ts = GetDamageDelayForSpell(spell); + + Damage(spell, ts, target, spell.Caster, damage, phys, fire, cold, pois, nrgy, dfa); + } + + public static void Damage(TimeSpan delay, Mobile target, double damage, int phys, int fire, int cold, int pois, + int nrgy) + { + Damage(delay, target, null, damage, phys, fire, cold, pois, nrgy); + } + + public static void Damage(TimeSpan delay, Mobile target, Mobile from, double damage, int phys, int fire, int cold, + int pois, int nrgy) + { + Damage(delay, target, from, damage, phys, fire, cold, pois, nrgy, DFAlgorithm.Standard); + } + + public static void Damage(TimeSpan delay, Mobile target, Mobile from, double damage, int phys, int fire, int cold, + int pois, int nrgy, DFAlgorithm dfa) + { + Damage(null, delay, target, from, damage, phys, fire, cold, pois, nrgy, dfa); + } + + public static void Damage(Spell spell, TimeSpan delay, Mobile target, Mobile from, double damage, int phys, int fire, + int cold, int pois, int nrgy, DFAlgorithm dfa) + { + int iDamage = (int)damage; + + if (delay == TimeSpan.Zero) + { + (from as BaseCreature)?.AlterSpellDamageTo(target, ref iDamage); + + (target as BaseCreature)?.AlterSpellDamageFrom(from, ref iDamage); + + WeightOverloading.DFA = dfa; + + int damageGiven = AOS.Damage(target, from, iDamage, phys, fire, cold, pois, nrgy); + + if (from != null) // sanity check + DoLeech(damageGiven, from, target); + + WeightOverloading.DFA = DFAlgorithm.Standard; + } + else + { + new SpellDamageTimerAOS(spell, target, from, iDamage, phys, fire, cold, pois, nrgy, delay, dfa).Start(); + } + + if (target is BaseCreature && from != null && delay == TimeSpan.Zero) + { + BaseCreature c = (BaseCreature)target; + + c.OnHarmfulSpell(from); + c.OnDamagedBySpell(from); + } + } + + public static void DoLeech(int damageGiven, Mobile from, Mobile target) + { + TransformContext context = TransformationSpellHelper.GetContext(from); + + if (context != null) /* cleanup */ + { + if (context.Type == typeof(WraithFormSpell)) + { + int wraithLeech = + 5 + (int)(15 * from.Skills.SpiritSpeak.Value / 100); // Wraith form gives 5-20% mana leech + int manaLeech = AOS.Scale(damageGiven, wraithLeech); + if (manaLeech != 0) + { + from.Mana += manaLeech; + from.PlaySound(0x44D); + } + } + else if (context.Type == typeof(VampiricEmbraceSpell)) + { + from.Hits += AOS.Scale(damageGiven, 20); + from.PlaySound(0x44D); + } + } + } + + public static void Heal(int amount, Mobile target, Mobile from) + { + Heal(amount, target, from, true); + } + + public static void Heal(int amount, Mobile target, Mobile from, bool message) + { + //TODO: All Healing *spells* go through ArcaneEmpowerment + target.Heal(amount, from, message); + } + + private delegate bool TravelValidator(Map map, Point3D loc); + + private class SpellDamageTimer : Timer + { + private int m_Damage; + private Spell m_Spell; + private Mobile m_Target, m_From; + + public SpellDamageTimer(Spell s, Mobile target, Mobile from, int damage, TimeSpan delay) + : base(delay) + { + m_Target = target; + m_From = from; + m_Damage = damage; + m_Spell = s; + + if (m_Spell != null && m_Spell.DelayedDamage && !m_Spell.DelayedDamageStacking) + m_Spell.StartDelayedDamageContext(target, this); + + Priority = TimerPriority.TwentyFiveMS; + } + + protected override void OnTick() + { + (m_From as BaseCreature)?.AlterSpellDamageTo(m_Target, ref m_Damage); + + (m_Target as BaseCreature)?.AlterSpellDamageFrom(m_From, ref m_Damage); + + m_Target.Damage(m_Damage); + m_Spell?.RemoveDelayedDamageContext(m_Target); + } + } + + private class SpellDamageTimerAOS : Timer + { + private int m_Damage; + private DFAlgorithm m_DFA; + private int m_Phys, m_Fire, m_Cold, m_Pois, m_Nrgy; + private Spell m_Spell; + private Mobile m_Target, m_From; + + public SpellDamageTimerAOS(Spell s, Mobile target, Mobile from, int damage, int phys, int fire, int cold, + int pois, int nrgy, TimeSpan delay, DFAlgorithm dfa) + : base(delay) + { + m_Target = target; + m_From = from; + m_Damage = damage; + m_Phys = phys; + m_Fire = fire; + m_Cold = cold; + m_Pois = pois; + m_Nrgy = nrgy; + m_DFA = dfa; + m_Spell = s; + if (m_Spell != null && m_Spell.DelayedDamage && !m_Spell.DelayedDamageStacking) + m_Spell.StartDelayedDamageContext(target, this); + + Priority = TimerPriority.TwentyFiveMS; + } + + protected override void OnTick() + { + if (m_From is BaseCreature && m_Target != null) + ((BaseCreature)m_From).AlterSpellDamageTo(m_Target, ref m_Damage); + + if (m_Target is BaseCreature && m_From != null) + ((BaseCreature)m_Target).AlterSpellDamageFrom(m_From, ref m_Damage); + + WeightOverloading.DFA = m_DFA; + + int damageGiven = AOS.Damage(m_Target, m_From, m_Damage, m_Phys, m_Fire, m_Cold, m_Pois, m_Nrgy); + + if (m_From != null) // sanity check + DoLeech(damageGiven, m_From, m_Target); + + WeightOverloading.DFA = DFAlgorithm.Standard; + + if (m_Target is BaseCreature && m_From != null) + { + BaseCreature c = (BaseCreature)m_Target; + + c.OnHarmfulSpell(m_From); + c.OnDamagedBySpell(m_From); + } + + m_Spell?.RemoveDelayedDamageContext(m_Target); + } + } + } + + public class TransformationSpellHelper + { + public static bool CheckCast(Mobile caster, Spell spell) + { + if (Sigil.ExistsOn(caster)) + { + caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } + + if (!caster.CanBeginAction(typeof(PolymorphSpell))) + { + caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + return false; + } + + if (AnimalForm.UnderTransformation(caster)) + { + caster.SendLocalizedMessage(1061091); // You cannot cast that spell in this form. + return false; + } + + return true; + } + + public static bool OnCast(Mobile caster, Spell spell) + { + ITransformationSpell transformSpell = spell as ITransformationSpell; + + if (transformSpell == null) + return false; + + if (Sigil.ExistsOn(caster)) + { + caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (!caster.CanBeginAction(typeof(PolymorphSpell))) + { + caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + } + else if (DisguiseTimers.IsDisguised(caster)) + { + caster.SendLocalizedMessage(1061631); // You can't do that while disguised. + return false; + } + else if (AnimalForm.UnderTransformation(caster)) + { + caster.SendLocalizedMessage(1061091); // You cannot cast that spell in this form. + } + else if (!caster.CanBeginAction(typeof(IncognitoSpell)) || caster.IsBodyMod && GetContext(caster) == null) + { + spell.DoFizzle(); + } + else if (spell.CheckSequence()) + { + TransformContext context = GetContext(caster); + Type ourType = spell.GetType(); + + bool wasTransformed = context != null; + bool ourTransform = wasTransformed && context.Type == ourType; + + if (wasTransformed) + { + RemoveContext(caster, context, ourTransform); + + if (ourTransform) + { + caster.PlaySound(0xFA); + caster.FixedParticles(0x3728, 1, 13, 5042, EffectLayer.Waist); + } + } + + if (!ourTransform) + { + List mods = new List(); + + if (transformSpell.PhysResistOffset != 0) + mods.Add(new ResistanceMod(ResistanceType.Physical, transformSpell.PhysResistOffset)); + + if (transformSpell.FireResistOffset != 0) + mods.Add(new ResistanceMod(ResistanceType.Fire, transformSpell.FireResistOffset)); + + if (transformSpell.ColdResistOffset != 0) + mods.Add(new ResistanceMod(ResistanceType.Cold, transformSpell.ColdResistOffset)); + + if (transformSpell.PoisResistOffset != 0) + mods.Add(new ResistanceMod(ResistanceType.Poison, transformSpell.PoisResistOffset)); + + if (transformSpell.NrgyResistOffset != 0) + mods.Add(new ResistanceMod(ResistanceType.Energy, transformSpell.NrgyResistOffset)); + + if (!((Body)transformSpell.Body).IsHuman) + { + IMount mt = caster.Mount; + + if (mt != null) + mt.Rider = null; + } + + caster.BodyMod = transformSpell.Body; + caster.HueMod = transformSpell.Hue; + + for (int i = 0; i < mods.Count; ++i) + caster.AddResistanceMod(mods[i]); + + transformSpell.DoEffect(caster); + + Timer timer = new TransformTimer(caster, transformSpell); + timer.Start(); + + AddContext(caster, new TransformContext(timer, mods, ourType, transformSpell)); + return true; + } + } + + return false; + } + + #region Context Stuff + + private static Dictionary m_Table = new Dictionary(); + + public static void AddContext(Mobile m, TransformContext context) + { + m_Table[m] = context; + } + + public static void RemoveContext(Mobile m, bool resetGraphics) + { + TransformContext context = GetContext(m); + + if (context != null) + RemoveContext(m, context, resetGraphics); + } + + public static void RemoveContext(Mobile m, TransformContext context, bool resetGraphics) + { + if (m_Table.ContainsKey(m)) + { + m_Table.Remove(m); + + List mods = context.Mods; + + for (int i = 0; i < mods.Count; ++i) + m.RemoveResistanceMod(mods[i]); + + if (resetGraphics) + { + m.HueMod = -1; + m.BodyMod = 0; + } + + context.Timer.Stop(); + context.Spell.RemoveEffect(m); + } + } + + public static TransformContext GetContext(Mobile m) + { + m_Table.TryGetValue(m, out TransformContext context); + + return context; + } + + public static bool UnderTransformation(Mobile m) + { + return GetContext(m) != null; + } + + public static bool UnderTransformation(Mobile m, Type type) + { + TransformContext context = GetContext(m); + + return context != null && context.Type == type; + } + + #endregion + } + + public interface ITransformationSpell + { + int Body{ get; } + int Hue{ get; } + + int PhysResistOffset{ get; } + int FireResistOffset{ get; } + int ColdResistOffset{ get; } + int PoisResistOffset{ get; } + int NrgyResistOffset{ get; } + + double TickRate{ get; } + void OnTick(Mobile m); + + void DoEffect(Mobile m); + void RemoveEffect(Mobile m); + } + + + public class TransformContext + { + public TransformContext(Timer timer, List mods, Type type, ITransformationSpell spell) + { + Timer = timer; + Mods = mods; + Type = type; + Spell = spell; + } + + public Timer Timer{ get; } + + public List Mods{ get; } + + public Type Type{ get; } + + public ITransformationSpell Spell{ get; } + } + + public class TransformTimer : Timer + { + private Mobile m_Mobile; + private ITransformationSpell m_Spell; + + public TransformTimer(Mobile from, ITransformationSpell spell) + : base(TimeSpan.FromSeconds(spell.TickRate), TimeSpan.FromSeconds(spell.TickRate)) + { + m_Mobile = from; + m_Spell = spell; + + Priority = TimerPriority.TwoFiftyMS; + } + + protected override void OnTick() + { + if (m_Mobile.Deleted || !m_Mobile.Alive || m_Mobile.Body != m_Spell.Body || m_Mobile.Hue != m_Spell.Hue) + { + TransformationSpellHelper.RemoveContext(m_Mobile, true); + Stop(); + } + else + { + m_Spell.OnTick(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Base/SpellInfo.cs b/Scripts/Spells/Base/SpellInfo.cs index d3f5b3134..918a28d26 100644 --- a/Scripts/Spells/Base/SpellInfo.cs +++ b/Scripts/Spells/Base/SpellInfo.cs @@ -2,63 +2,69 @@ using System; namespace Server.Spells { - public class SpellInfo - { - public SpellInfo( string name, string mantra, params Type[] regs ) : this( name, mantra, 16, 0, 0, true, regs ) - { - } + public class SpellInfo + { + public SpellInfo(string name, string mantra, params Type[] regs) : this(name, mantra, 16, 0, 0, true, regs) + { + } - public SpellInfo( string name, string mantra, bool allowTown, params Type[] regs ) : this( name, mantra, 16, 0, 0, allowTown, regs ) - { - } + public SpellInfo(string name, string mantra, bool allowTown, params Type[] regs) : this(name, mantra, 16, 0, 0, + allowTown, regs) + { + } - public SpellInfo( string name, string mantra, int action, params Type[] regs ) : this( name, mantra, action, 0, 0, true, regs ) - { - } + public SpellInfo(string name, string mantra, int action, params Type[] regs) : this(name, mantra, action, 0, 0, true, + regs) + { + } - public SpellInfo( string name, string mantra, int action, bool allowTown, params Type[] regs ) : this( name, mantra, action, 0, 0, allowTown, regs ) - { - } + public SpellInfo(string name, string mantra, int action, bool allowTown, params Type[] regs) : this(name, mantra, + action, 0, 0, allowTown, regs) + { + } - public SpellInfo( string name, string mantra, int action, int handEffect, params Type[] regs ) : this( name, mantra, action, handEffect, handEffect, true, regs ) - { - } + public SpellInfo(string name, string mantra, int action, int handEffect, params Type[] regs) : this(name, mantra, + action, handEffect, handEffect, true, regs) + { + } - public SpellInfo( string name, string mantra, int action, int handEffect, bool allowTown, params Type[] regs ) : this( name, mantra, action, handEffect, handEffect, allowTown, regs ) - { - } + public SpellInfo(string name, string mantra, int action, int handEffect, bool allowTown, params Type[] regs) : this( + name, mantra, action, handEffect, handEffect, allowTown, regs) + { + } - public SpellInfo( string name, string mantra, int action, int leftHandEffect, int rightHandEffect, bool allowTown, params Type[] regs ) - { - Name = name; - Mantra = mantra; - Action = action; - Reagents = regs; - AllowTown = allowTown; + public SpellInfo(string name, string mantra, int action, int leftHandEffect, int rightHandEffect, bool allowTown, + params Type[] regs) + { + Name = name; + Mantra = mantra; + Action = action; + Reagents = regs; + AllowTown = allowTown; - LeftHandEffect = leftHandEffect; - RightHandEffect = rightHandEffect; + LeftHandEffect = leftHandEffect; + RightHandEffect = rightHandEffect; - Amounts = new int[regs.Length]; + Amounts = new int[regs.Length]; - for ( int i = 0; i < regs.Length; ++i ) - Amounts[i] = 1; - } + for (int i = 0; i < regs.Length; ++i) + Amounts[i] = 1; + } - public int Action { get; set; } + public int Action{ get; set; } - public bool AllowTown { get; set; } + public bool AllowTown{ get; set; } - public int[] Amounts { get; set; } + public int[] Amounts{ get; set; } - public string Mantra { get; set; } + public string Mantra{ get; set; } - public string Name { get; set; } + public string Name{ get; set; } - public Type[] Reagents { get; set; } + public Type[] Reagents{ get; set; } - public int LeftHandEffect { get; set; } + public int LeftHandEffect{ get; set; } - public int RightHandEffect { get; set; } - } + public int RightHandEffect{ get; set; } + } } \ No newline at end of file diff --git a/Scripts/Spells/Base/SpellRegistry.cs b/Scripts/Spells/Base/SpellRegistry.cs index 7c8d60b98..42d968b2e 100644 --- a/Scripts/Spells/Base/SpellRegistry.cs +++ b/Scripts/Spells/Base/SpellRegistry.cs @@ -3,167 +3,168 @@ using System.Collections.Generic; namespace Server.Spells { - public class SpellRegistry - { - private static Type[] m_Types = new Type[700]; - private static int m_Count; + public class SpellRegistry + { + private static Type[] m_Types = new Type[700]; + private static int m_Count; - public static Type[] Types - { - get - { - m_Count = -1; - return m_Types; - } - } + private static Dictionary m_IDsFromTypes = new Dictionary(m_Types.Length); - //What IS this used for anyways. - public static int Count - { - get - { - if ( m_Count == -1 ) - { - m_Count = 0; + private static object[] m_Params = new object[2]; - for ( int i = 0; i < m_Types.Length; ++i ) - if ( m_Types[i] != null ) - ++m_Count; - } + private static string[] m_CircleNames = + { + "First", + "Second", + "Third", + "Fourth", + "Fifth", + "Sixth", + "Seventh", + "Eighth", + "Necromancy", + "Chivalry", + "Bushido", + "Ninjitsu", + "Spellweaving" + }; - return m_Count; - } - } + public static Type[] Types + { + get + { + m_Count = -1; + return m_Types; + } + } - private static Dictionary m_IDsFromTypes = new Dictionary( m_Types.Length ); + //What IS this used for anyways. + public static int Count + { + get + { + if (m_Count == -1) + { + m_Count = 0; - public static Dictionary SpecialMoves { get; } = new Dictionary(); + for (int i = 0; i < m_Types.Length; ++i) + if (m_Types[i] != null) + ++m_Count; + } - public static int GetRegistryNumber( ISpell s ) - { - return GetRegistryNumber( s.GetType() ); - } + return m_Count; + } + } - public static int GetRegistryNumber( SpecialMove s ) - { - return GetRegistryNumber( s.GetType() ); - } + public static Dictionary SpecialMoves{ get; } = new Dictionary(); - public static int GetRegistryNumber( Type type ) - { - if ( m_IDsFromTypes.ContainsKey( type ) ) - return m_IDsFromTypes[type]; + public static int GetRegistryNumber(ISpell s) + { + return GetRegistryNumber(s.GetType()); + } - return -1; - } + public static int GetRegistryNumber(SpecialMove s) + { + return GetRegistryNumber(s.GetType()); + } - public static void Register( int spellID, Type type ) - { - if ( spellID < 0 || spellID >= m_Types.Length ) - return; + public static int GetRegistryNumber(Type type) + { + if (m_IDsFromTypes.ContainsKey(type)) + return m_IDsFromTypes[type]; - if ( m_Types[spellID] == null ) - ++m_Count; + return -1; + } - m_Types[spellID] = type; + public static void Register(int spellID, Type type) + { + if (spellID < 0 || spellID >= m_Types.Length) + return; - if ( !m_IDsFromTypes.ContainsKey( type ) ) - m_IDsFromTypes.Add( type, spellID ); + if (m_Types[spellID] == null) + ++m_Count; - if ( type.IsSubclassOf( typeof( SpecialMove ) ) ) - { - SpecialMove spm = null; + m_Types[spellID] = type; - try - { - spm = Activator.CreateInstance( type ) as SpecialMove; - } - catch - { - } + if (!m_IDsFromTypes.ContainsKey(type)) + m_IDsFromTypes.Add(type, spellID); - if ( spm != null ) - SpecialMoves.Add( spellID, spm ); - } - } + if (type.IsSubclassOf(typeof(SpecialMove))) + { + SpecialMove spm = null; - public static SpecialMove GetSpecialMove( int spellID ) - { - if ( spellID < 0 || spellID >= m_Types.Length ) - return null; + try + { + spm = Activator.CreateInstance(type) as SpecialMove; + } + catch + { + } - Type t = m_Types[spellID]; + if (spm != null) + SpecialMoves.Add(spellID, spm); + } + } - if ( t == null || !t.IsSubclassOf( typeof( SpecialMove ) ) || !SpecialMoves.ContainsKey( spellID ) ) - return null; + public static SpecialMove GetSpecialMove(int spellID) + { + if (spellID < 0 || spellID >= m_Types.Length) + return null; - return SpecialMoves[spellID]; - } + Type t = m_Types[spellID]; - private static object[] m_Params = new object[2]; + if (t == null || !t.IsSubclassOf(typeof(SpecialMove)) || !SpecialMoves.ContainsKey(spellID)) + return null; - public static Spell NewSpell( int spellID, Mobile caster, Item scroll ) - { - if ( spellID < 0 || spellID >= m_Types.Length ) - return null; + return SpecialMoves[spellID]; + } - Type t = m_Types[spellID]; + public static Spell NewSpell(int spellID, Mobile caster, Item scroll) + { + if (spellID < 0 || spellID >= m_Types.Length) + return null; - if ( t != null && !t.IsSubclassOf( typeof( SpecialMove ) ) ) - { - m_Params[0] = caster; - m_Params[1] = scroll; + Type t = m_Types[spellID]; - try - { - return (Spell)Activator.CreateInstance( t, m_Params ); - } - catch - { - } - } + if (t != null && !t.IsSubclassOf(typeof(SpecialMove))) + { + m_Params[0] = caster; + m_Params[1] = scroll; - return null; - } + try + { + return (Spell)Activator.CreateInstance(t, m_Params); + } + catch + { + } + } - private static string[] m_CircleNames = { - "First", - "Second", - "Third", - "Fourth", - "Fifth", - "Sixth", - "Seventh", - "Eighth", - "Necromancy", - "Chivalry", - "Bushido", - "Ninjitsu", - "Spellweaving" - }; + return null; + } - public static Spell NewSpell( string name, Mobile caster, Item scroll ) - { - for ( int i = 0; i < m_CircleNames.Length; ++i ) - { - Type t = ScriptCompiler.FindTypeByFullName($"Server.Spells.{m_CircleNames[i]}.{name}"); + public static Spell NewSpell(string name, Mobile caster, Item scroll) + { + for (int i = 0; i < m_CircleNames.Length; ++i) + { + Type t = ScriptCompiler.FindTypeByFullName($"Server.Spells.{m_CircleNames[i]}.{name}"); - if ( t != null && !t.IsSubclassOf( typeof( SpecialMove ) ) ) - { - m_Params[0] = caster; - m_Params[1] = scroll; + if (t != null && !t.IsSubclassOf(typeof(SpecialMove))) + { + m_Params[0] = caster; + m_Params[1] = scroll; - try - { - return (Spell)Activator.CreateInstance( t, m_Params ); - } - catch - { - } - } - } + try + { + return (Spell)Activator.CreateInstance(t, m_Params); + } + catch + { + } + } + } - return null; - } - } -} + return null; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Base/SpellState.cs b/Scripts/Spells/Base/SpellState.cs index b779323e0..87966e230 100644 --- a/Scripts/Spells/Base/SpellState.cs +++ b/Scripts/Spells/Base/SpellState.cs @@ -1,9 +1,13 @@ namespace Server.Spells { - public enum SpellState - { - None = 0, - Casting = 1, // We are in the process of casting (that is, waiting GetCastTime() and doing animations). Spell casting may be interupted in this state. - Sequencing = 2 // Casting completed, but the full spell sequence isn't. Usually waiting for a target response. Some actions are restricted in this state (using skills for example). - } + public enum SpellState + { + None = 0, + + Casting = + 1, // We are in the process of casting (that is, waiting GetCastTime() and doing animations). Spell casting may be interupted in this state. + + Sequencing = + 2 // Casting completed, but the full spell sequence isn't. Usually waiting for a target response. Some actions are restricted in this state (using skills for example). + } } \ No newline at end of file diff --git a/Scripts/Spells/Bushido/Confidence.cs b/Scripts/Spells/Bushido/Confidence.cs index 8e55c9a4b..602440da7 100644 --- a/Scripts/Spells/Bushido/Confidence.cs +++ b/Scripts/Spells/Bushido/Confidence.cs @@ -3,150 +3,150 @@ using System.Collections; namespace Server.Spells.Bushido { - public class Confidence : SamuraiSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Confidence", null, - -1, - 9002 - ); + public class Confidence : SamuraiSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Confidence", null, + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.25 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 25.0; - public override int RequiredMana => 10; + private static Hashtable m_RegenTable = new Hashtable(); - public Confidence( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public Confidence(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override void OnBeginCast() - { - base.OnBeginCast(); + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.25); - Caster.FixedEffect( 0x37C4, 10, 7, 4, 3 ); - } + public override double RequiredSkill => 25.0; + public override int RequiredMana => 10; - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.SendLocalizedMessage( 1063115 ); // You exude confidence. + public override void OnBeginCast() + { + base.OnBeginCast(); - Caster.FixedParticles( 0x375A, 1, 17, 0x7DA, 0x960, 0x3, EffectLayer.Waist ); - Caster.PlaySound( 0x51A ); + Caster.FixedEffect(0x37C4, 10, 7, 4, 3); + } - OnCastSuccessful( Caster ); + public override void OnCast() + { + if (CheckSequence()) + { + Caster.SendLocalizedMessage(1063115); // You exude confidence. - BeginConfidence( Caster ); - BeginRegenerating( Caster ); - } + Caster.FixedParticles(0x375A, 1, 17, 0x7DA, 0x960, 0x3, EffectLayer.Waist); + Caster.PlaySound(0x51A); - FinishSequence(); - } + OnCastSuccessful(Caster); - private static Hashtable m_Table = new Hashtable(); + BeginConfidence(Caster); + BeginRegenerating(Caster); + } - public static bool IsConfident( Mobile m ) - { - return m_Table.Contains( m ); - } + FinishSequence(); + } - public static void BeginConfidence( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + public static bool IsConfident(Mobile m) + { + return m_Table.Contains(m); + } - t?.Stop(); + public static void BeginConfidence(Mobile m) + { + Timer t = (Timer)m_Table[m]; - t = new InternalTimer( m ); + t?.Stop(); - m_Table[m] = t; + t = new InternalTimer(m); - t.Start(); - } + m_Table[m] = t; - public static void EndConfidence( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + t.Start(); + } - t?.Stop(); + public static void EndConfidence(Mobile m) + { + Timer t = (Timer)m_Table[m]; - m_Table.Remove( m ); + t?.Stop(); - OnEffectEnd( m, typeof( Confidence ) ); - } + m_Table.Remove(m); - private class InternalTimer : Timer - { - private Mobile m_Mobile; + OnEffectEnd(m, typeof(Confidence)); + } - public InternalTimer( Mobile m ) : base( TimeSpan.FromSeconds( 15.0 ) ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } + public static bool IsRegenerating(Mobile m) + { + return m_RegenTable.Contains(m); + } - protected override void OnTick() - { - EndConfidence( m_Mobile ); - m_Mobile.SendLocalizedMessage( 1063116 ); // Your confidence wanes. - } - } + public static void BeginRegenerating(Mobile m) + { + Timer t = (Timer)m_RegenTable[m]; - private static Hashtable m_RegenTable = new Hashtable(); + t?.Stop(); - public static bool IsRegenerating( Mobile m ) - { - return m_RegenTable.Contains( m ); - } + t = new RegenTimer(m); - public static void BeginRegenerating( Mobile m ) - { - Timer t = (Timer)m_RegenTable[m]; + m_RegenTable[m] = t; - t?.Stop(); + t.Start(); + } - t = new RegenTimer( m ); + public static void StopRegenerating(Mobile m) + { + Timer t = (Timer)m_RegenTable[m]; - m_RegenTable[m] = t; + t?.Stop(); - t.Start(); - } + m_RegenTable.Remove(m); + } - public static void StopRegenerating( Mobile m ) - { - Timer t = (Timer)m_RegenTable[m]; + private class InternalTimer : Timer + { + private Mobile m_Mobile; - t?.Stop(); + public InternalTimer(Mobile m) : base(TimeSpan.FromSeconds(15.0)) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - m_RegenTable.Remove( m ); - } + protected override void OnTick() + { + EndConfidence(m_Mobile); + m_Mobile.SendLocalizedMessage(1063116); // Your confidence wanes. + } + } - private class RegenTimer : Timer - { - private Mobile m_Mobile; - private int m_Ticks; - private int m_Hits; + private class RegenTimer : Timer + { + private int m_Hits; + private Mobile m_Mobile; + private int m_Ticks; - public RegenTimer( Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Mobile = m; - m_Hits = 15 + (m.Skills.Bushido.Fixed * m.Skills.Bushido.Fixed / 57600); - Priority = TimerPriority.TwoFiftyMS; - } + public RegenTimer(Mobile m) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Mobile = m; + m_Hits = 15 + m.Skills.Bushido.Fixed * m.Skills.Bushido.Fixed / 57600; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - ++m_Ticks; + protected override void OnTick() + { + ++m_Ticks; - if ( m_Ticks >= 5 ) - { - m_Mobile.Hits += (m_Hits - (m_Hits * 4 / 5)); - StopRegenerating( m_Mobile ); - } + if (m_Ticks >= 5) + { + m_Mobile.Hits += m_Hits - m_Hits * 4 / 5; + StopRegenerating(m_Mobile); + } - m_Mobile.Hits += (m_Hits / 5); - } - } - } -} + m_Mobile.Hits += m_Hits / 5; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/CounterAttack.cs b/Scripts/Spells/Bushido/CounterAttack.cs index 777e0d5b6..849fb2eca 100644 --- a/Scripts/Spells/Bushido/CounterAttack.cs +++ b/Scripts/Spells/Bushido/CounterAttack.cs @@ -4,108 +4,108 @@ using Server.Items; namespace Server.Spells.Bushido { - public class CounterAttack : SamuraiSpell - { - private static SpellInfo m_Info = new SpellInfo( - "CounterAttack", null, - -1, - 9002 - ); + public class CounterAttack : SamuraiSpell + { + private static SpellInfo m_Info = new SpellInfo( + "CounterAttack", null, + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.25 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 40.0; - public override int RequiredMana => 5; + public CounterAttack(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.25); - if ( Caster.FindItemOnLayer( Layer.TwoHanded ) as BaseShield != null ) - return true; + public override double RequiredSkill => 40.0; + public override int RequiredMana => 5; - if ( Caster.FindItemOnLayer( Layer.OneHanded ) as BaseWeapon != null ) - return true; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( Caster.FindItemOnLayer( Layer.TwoHanded ) as BaseWeapon != null ) - return true; + if (Caster.FindItemOnLayer(Layer.TwoHanded) as BaseShield != null) + return true; - Caster.SendLocalizedMessage( 1062944 ); // You must have a weapon or a shield equipped to use this ability! - return false; - } + if (Caster.FindItemOnLayer(Layer.OneHanded) as BaseWeapon != null) + return true; - public CounterAttack( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + if (Caster.FindItemOnLayer(Layer.TwoHanded) as BaseWeapon != null) + return true; - public override void OnBeginCast() - { - base.OnBeginCast(); + Caster.SendLocalizedMessage(1062944); // You must have a weapon or a shield equipped to use this ability! + return false; + } - Caster.FixedEffect( 0x37C4, 10, 7, 4, 3 ); - } + public override void OnBeginCast() + { + base.OnBeginCast(); - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.SendLocalizedMessage( 1063118 ); // You prepare to respond immediately to the next blocked blow. + Caster.FixedEffect(0x37C4, 10, 7, 4, 3); + } - OnCastSuccessful( Caster ); + public override void OnCast() + { + if (CheckSequence()) + { + Caster.SendLocalizedMessage(1063118); // You prepare to respond immediately to the next blocked blow. - StartCountering( Caster ); - } + OnCastSuccessful(Caster); - FinishSequence(); - } + StartCountering(Caster); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - public static bool IsCountering( Mobile m ) - { - return m_Table.Contains( m ); - } + public static bool IsCountering(Mobile m) + { + return m_Table.Contains(m); + } - public static void StartCountering( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + public static void StartCountering(Mobile m) + { + Timer t = (Timer)m_Table[m]; - t?.Stop(); + t?.Stop(); - t = new InternalTimer( m ); + t = new InternalTimer(m); - m_Table[m] = t; + m_Table[m] = t; - t.Start(); - } + t.Start(); + } - public static void StopCountering( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + public static void StopCountering(Mobile m) + { + Timer t = (Timer)m_Table[m]; - t?.Stop(); + t?.Stop(); - m_Table.Remove( m ); + m_Table.Remove(m); - OnEffectEnd( m, typeof( CounterAttack ) ); - } + OnEffectEnd(m, typeof(CounterAttack)); + } - private class InternalTimer : Timer - { - private Mobile m_Mobile; + private class InternalTimer : Timer + { + private Mobile m_Mobile; - public InternalTimer( Mobile m ) : base( TimeSpan.FromSeconds( 30.0 ) ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } + public InternalTimer(Mobile m) : base(TimeSpan.FromSeconds(30.0)) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - StopCountering( m_Mobile ); - m_Mobile.SendLocalizedMessage( 1063119 ); // You return to your normal stance. - } - } - } -} + protected override void OnTick() + { + StopCountering(m_Mobile); + m_Mobile.SendLocalizedMessage(1063119); // You return to your normal stance. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/Evasion.cs b/Scripts/Spells/Bushido/Evasion.cs index ea8021f6a..e631140d0 100644 --- a/Scripts/Spells/Bushido/Evasion.cs +++ b/Scripts/Spells/Bushido/Evasion.cs @@ -4,219 +4,223 @@ using Server.Items; namespace Server.Spells.Bushido { - public class Evasion : SamuraiSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Evasion", null, - -1, - 9002 - ); + public class Evasion : SamuraiSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Evasion", null, + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.25 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 60.0; - public override int RequiredMana => 10; + public Evasion(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override bool CheckCast() - { - if ( VerifyCast( Caster, true ) ) - return base.CheckCast(); + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.25); - return false; - } + public override double RequiredSkill => 60.0; + public override int RequiredMana => 10; - public static bool VerifyCast( Mobile Caster, bool messages ) - { - if ( Caster == null ) // Sanity - return false; + public override bool CheckCast() + { + if (VerifyCast(Caster, true)) + return base.CheckCast(); - BaseWeapon weap = Caster.FindItemOnLayer( Layer.OneHanded ) as BaseWeapon; + return false; + } - if ( weap == null ) - weap = Caster.FindItemOnLayer( Layer.TwoHanded ) as BaseWeapon; + public static bool VerifyCast(Mobile Caster, bool messages) + { + if (Caster == null) // Sanity + return false; - if ( weap != null ) { - if ( Core.ML && Caster.Skills[weap.Skill].Base < 50 ) { - if ( messages ) { - Caster.SendLocalizedMessage( 1076206 ); // Your skill with your equipped weapon must be 50 or higher to use Evasion. - } - return false; - } - } else if ( !( Caster.FindItemOnLayer( Layer.TwoHanded ) is BaseShield ) ) { - if ( messages ) { - Caster.SendLocalizedMessage( 1062944 ); // You must have a weapon or a shield equipped to use this ability! - } - return false; - } + BaseWeapon weap = Caster.FindItemOnLayer(Layer.OneHanded) as BaseWeapon; - if ( !Caster.CanBeginAction( typeof( Evasion ) ) ) { - if ( messages ) { - Caster.SendLocalizedMessage( 501789 ); // You must wait before trying again. - } - return false; - } + if (weap == null) + weap = Caster.FindItemOnLayer(Layer.TwoHanded) as BaseWeapon; - return true; - } + if (weap != null) + { + if (Core.ML && Caster.Skills[weap.Skill].Base < 50) + { + if (messages) + Caster.SendLocalizedMessage( + 1076206); // Your skill with your equipped weapon must be 50 or higher to use Evasion. + return false; + } + } + else if (!(Caster.FindItemOnLayer(Layer.TwoHanded) is BaseShield)) + { + if (messages) + Caster.SendLocalizedMessage(1062944); // You must have a weapon or a shield equipped to use this ability! + return false; + } - public static bool CheckSpellEvasion( Mobile defender ) - { - BaseWeapon weap = defender.FindItemOnLayer( Layer.OneHanded ) as BaseWeapon; + if (!Caster.CanBeginAction(typeof(Evasion))) + { + if (messages) Caster.SendLocalizedMessage(501789); // You must wait before trying again. + return false; + } - if ( weap == null ) - weap = defender.FindItemOnLayer( Layer.TwoHanded ) as BaseWeapon; + return true; + } - if ( Core.ML ) { - if ( defender.Spell != null && defender.Spell.IsCasting ) { - return false; - } + public static bool CheckSpellEvasion(Mobile defender) + { + BaseWeapon weap = defender.FindItemOnLayer(Layer.OneHanded) as BaseWeapon; - if ( weap != null ) { - if ( defender.Skills[weap.Skill].Base < 50 ) { - return false; - } - } else if ( !( defender.FindItemOnLayer( Layer.TwoHanded ) is BaseShield ) ) { - return false; - } - } + if (weap == null) + weap = defender.FindItemOnLayer(Layer.TwoHanded) as BaseWeapon; - if ( IsEvading( defender ) && BaseWeapon.CheckParry( defender ) ) { - defender.Emote( "*evades*" ); // Yes. Eew. Blame OSI. - defender.FixedEffect( 0x37B9, 10, 16 ); - return true; - } + if (Core.ML) + { + if (defender.Spell != null && defender.Spell.IsCasting) return false; - return false; - } + if (weap != null) + { + if (defender.Skills[weap.Skill].Base < 50) return false; + } + else if (!(defender.FindItemOnLayer(Layer.TwoHanded) is BaseShield)) + { + return false; + } + } - public Evasion( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + if (IsEvading(defender) && BaseWeapon.CheckParry(defender)) + { + defender.Emote("*evades*"); // Yes. Eew. Blame OSI. + defender.FixedEffect(0x37B9, 10, 16); + return true; + } - public override void OnBeginCast() - { - base.OnBeginCast(); + return false; + } - Caster.FixedEffect( 0x37C4, 10, 7, 4, 3 ); - } + public override void OnBeginCast() + { + base.OnBeginCast(); - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.SendLocalizedMessage( 1063120 ); // You feel that you might be able to deflect any attack! - Caster.FixedParticles( 0x376A, 1, 20, 0x7F5, 0x960, 3, EffectLayer.Waist ); - Caster.PlaySound( 0x51B ); + Caster.FixedEffect(0x37C4, 10, 7, 4, 3); + } - OnCastSuccessful( Caster ); + public override void OnCast() + { + if (CheckSequence()) + { + Caster.SendLocalizedMessage(1063120); // You feel that you might be able to deflect any attack! + Caster.FixedParticles(0x376A, 1, 20, 0x7F5, 0x960, 3, EffectLayer.Waist); + Caster.PlaySound(0x51B); - BeginEvasion( Caster ); + OnCastSuccessful(Caster); - Caster.BeginAction( typeof( Evasion ) ); - Timer.DelayCall( TimeSpan.FromSeconds( 20.0 ), delegate { Caster.EndAction( typeof( Evasion ) ); } ); - } + BeginEvasion(Caster); - FinishSequence(); - } + Caster.BeginAction(typeof(Evasion)); + Timer.DelayCall(TimeSpan.FromSeconds(20.0), delegate { Caster.EndAction(typeof(Evasion)); }); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - public static bool IsEvading( Mobile m ) - { - return m_Table.Contains( m ); - } + public static bool IsEvading(Mobile m) + { + return m_Table.Contains(m); + } - public static TimeSpan GetEvadeDuration( Mobile m ) - { + public static TimeSpan GetEvadeDuration(Mobile m) + { + /* Evasion duration now scales with Bushido skill + * + * If the player has higher than GM Bushido, and GM Tactics and Anatomy, they get a 1 second bonus + * Evasion duration range: + * o 3-6 seconds w/o tactics/anatomy + * o 6-7 seconds w/ GM+ Bushido and GM tactics/anatomy + */ - /* Evasion duration now scales with Bushido skill - * - * If the player has higher than GM Bushido, and GM Tactics and Anatomy, they get a 1 second bonus - * Evasion duration range: - * o 3-6 seconds w/o tactics/anatomy - * o 6-7 seconds w/ GM+ Bushido and GM tactics/anatomy - */ + if (!Core.ML) + return TimeSpan.FromSeconds(8.0); - if ( !Core.ML ) - return TimeSpan.FromSeconds( 8.0 ); + double seconds = 3; - double seconds = 3; + if (m.Skills.Bushido.Value > 60) + seconds += (m.Skills.Bushido.Value - 60) / 20; - if ( m.Skills.Bushido.Value > 60 ) - seconds += (m.Skills.Bushido.Value - 60) / 20; + if (m.Skills.Anatomy.Value >= 100.0 && m.Skills.Tactics.Value >= 100.0 && m.Skills.Bushido.Value > 100.0 + ) //Bushido being HIGHER than 100 for bonus is intended + seconds++; - if ( m.Skills.Anatomy.Value >= 100.0 && m.Skills.Tactics.Value >= 100.0 && m.Skills.Bushido.Value > 100.0 ) //Bushido being HIGHER than 100 for bonus is intended - seconds++; + return TimeSpan.FromSeconds((int)seconds); + } - return TimeSpan.FromSeconds( (int)seconds ); - } + public static double GetParryScalar(Mobile m) + { + /* Evasion modifier to parry now scales with Bushido skill + * + * If the player has higher than GM Bushido, and at least GM Tactics and Anatomy, they get a bonus to their evasion modifier (10% bonus to the evasion modifier to parry NOT 10% to the final parry chance) + * + * Bonus modifier to parry range: (these are the ranges for the evasion modifier) + * o 16-40% bonus w/o tactics/anatomy + * o 42-50% bonus w/ GM+ bushido and GM tactics/anatomy + */ - public static double GetParryScalar( Mobile m ) - { - /* Evasion modifier to parry now scales with Bushido skill - * - * If the player has higher than GM Bushido, and at least GM Tactics and Anatomy, they get a bonus to their evasion modifier (10% bonus to the evasion modifier to parry NOT 10% to the final parry chance) - * - * Bonus modifier to parry range: (these are the ranges for the evasion modifier) - * o 16-40% bonus w/o tactics/anatomy - * o 42-50% bonus w/ GM+ bushido and GM tactics/anatomy - */ + if (!Core.ML) + return 1.5; - if ( !Core.ML ) - return 1.5; + double bonus = 0; - double bonus = 0; + if (m.Skills.Bushido.Value >= 60) + bonus += (m.Skills.Bushido.Value - 60) * .004 + 0.16; - if ( m.Skills.Bushido.Value >= 60 ) - bonus += ( ( ( m.Skills.Bushido.Value - 60 ) * .004 ) + 0.16 ); + if (m.Skills.Anatomy.Value >= 100 && m.Skills.Tactics.Value >= 100 && m.Skills.Bushido.Value > 100 + ) //Bushido being HIGHER than 100 for bonus is intended + bonus += 0.10; - if ( m.Skills.Anatomy.Value >= 100 && m.Skills.Tactics.Value >= 100 && m.Skills.Bushido.Value > 100 ) //Bushido being HIGHER than 100 for bonus is intended - bonus += 0.10; + return 1.0 + bonus; + } - return 1.0 + bonus; - } + public static void BeginEvasion(Mobile m) + { + Timer t = (Timer)m_Table[m]; - public static void BeginEvasion( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + t = new InternalTimer(m, GetEvadeDuration(m)); - t = new InternalTimer( m, GetEvadeDuration( m ) ); + m_Table[m] = t; - m_Table[m] = t; + t.Start(); + } - t.Start(); - } + public static void EndEvasion(Mobile m) + { + Timer t = (Timer)m_Table[m]; - public static void EndEvasion( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + t?.Stop(); - t?.Stop(); + m_Table.Remove(m); - m_Table.Remove( m ); + OnEffectEnd(m, typeof(Evasion)); + } - OnEffectEnd( m, typeof( Evasion ) ); - } + private class InternalTimer : Timer + { + private Mobile m_Mobile; - private class InternalTimer : Timer - { - private Mobile m_Mobile; + public InternalTimer(Mobile m, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + Priority = TimerPriority.TwoFiftyMS; + } - public InternalTimer( Mobile m, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - Priority = TimerPriority.TwoFiftyMS; - } - - protected override void OnTick() - { - EndEvasion( m_Mobile ); - m_Mobile.SendLocalizedMessage( 1063121 ); // You no longer feel that you could deflect any attack. - } - } - } -} + protected override void OnTick() + { + EndEvasion(m_Mobile); + m_Mobile.SendLocalizedMessage(1063121); // You no longer feel that you could deflect any attack. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/HonorableExecution.cs b/Scripts/Spells/Bushido/HonorableExecution.cs index ebe643dbd..78f3cdd66 100644 --- a/Scripts/Spells/Bushido/HonorableExecution.cs +++ b/Scripts/Spells/Bushido/HonorableExecution.cs @@ -3,181 +3,177 @@ using System.Collections; namespace Server.Spells.Bushido { - public class HonorableExecution : SamuraiMove - { - public HonorableExecution() - { - } + public class HonorableExecution : SamuraiMove + { + private static Hashtable m_Table = new Hashtable(); - public override int BaseMana => 0; - public override double RequiredSkill => 25.0; + public override int BaseMana => 0; + public override double RequiredSkill => 25.0; - public override TextDefinition AbilityMessage => new TextDefinition( 1063122 ); // You better kill your enemy with your next hit or you'll be rather sorry... + public override TextDefinition AbilityMessage => + new TextDefinition(1063122); // You better kill your enemy with your next hit or you'll be rather sorry... - public override double GetDamageScalar( Mobile attacker, Mobile defender ) - { - double bushido = attacker.Skills[SkillName.Bushido].Value; + public override double GetDamageScalar(Mobile attacker, Mobile defender) + { + double bushido = attacker.Skills[SkillName.Bushido].Value; - // TODO: 20 -> Perfection - return 1.0 + (bushido * 20) / 10000; - } + // TODO: 20 -> Perfection + return 1.0 + bushido * 20 / 10000; + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentMove( attacker ); + ClearCurrentMove(attacker); - HonorableExecutionInfo info = m_Table[attacker] as HonorableExecutionInfo; + HonorableExecutionInfo info = m_Table[attacker] as HonorableExecutionInfo; - if ( info != null ) - { - info.Clear(); + if (info != null) + { + info.Clear(); - info.m_Timer?.Stop(); - } + info.m_Timer?.Stop(); + } - if ( !defender.Alive ) - { - attacker.FixedParticles( 0x373A, 1, 17, 0x7E2, EffectLayer.Waist ); + if (!defender.Alive) + { + attacker.FixedParticles(0x373A, 1, 17, 0x7E2, EffectLayer.Waist); - double bushido = attacker.Skills[SkillName.Bushido].Value; + double bushido = attacker.Skills[SkillName.Bushido].Value; - attacker.Hits += 20 + (int)((bushido * bushido) / 480.0); + attacker.Hits += 20 + (int)(bushido * bushido / 480.0); - int swingBonus = Math.Max( 1, (int)((bushido * bushido) / 720.0) ); + int swingBonus = Math.Max(1, (int)(bushido * bushido / 720.0)); - info = new HonorableExecutionInfo( attacker, swingBonus ); - info.m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 20.0 ), new TimerStateCallback( EndEffect ), info ); + info = new HonorableExecutionInfo(attacker, swingBonus); + info.m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(20.0), new TimerStateCallback(EndEffect), info); - m_Table[attacker] = info; - } - else - { - ArrayList mods = new ArrayList(); + m_Table[attacker] = info; + } + else + { + ArrayList mods = new ArrayList(); - mods.Add( new ResistanceMod( ResistanceType.Physical, -40 ) ); - mods.Add( new ResistanceMod( ResistanceType.Fire, -40 ) ); - mods.Add( new ResistanceMod( ResistanceType.Cold, -40 ) ); - mods.Add( new ResistanceMod( ResistanceType.Poison, -40 ) ); - mods.Add( new ResistanceMod( ResistanceType.Energy, -40 ) ); + mods.Add(new ResistanceMod(ResistanceType.Physical, -40)); + mods.Add(new ResistanceMod(ResistanceType.Fire, -40)); + mods.Add(new ResistanceMod(ResistanceType.Cold, -40)); + mods.Add(new ResistanceMod(ResistanceType.Poison, -40)); + mods.Add(new ResistanceMod(ResistanceType.Energy, -40)); - double resSpells = attacker.Skills[SkillName.MagicResist].Value; + double resSpells = attacker.Skills[SkillName.MagicResist].Value; - if ( resSpells > 0.0 ) - mods.Add( new DefaultSkillMod( SkillName.MagicResist, true, -resSpells ) ); + if (resSpells > 0.0) + mods.Add(new DefaultSkillMod(SkillName.MagicResist, true, -resSpells)); - info = new HonorableExecutionInfo( attacker, mods ); - info.m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 7.0 ), new TimerStateCallback( EndEffect ), info ); + info = new HonorableExecutionInfo(attacker, mods); + info.m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(7.0), new TimerStateCallback(EndEffect), info); - m_Table[attacker] = info; - } + m_Table[attacker] = info; + } - CheckGain( attacker ); - } + CheckGain(attacker); + } + public static int GetSwingBonus(Mobile target) + { + HonorableExecutionInfo info = m_Table[target] as HonorableExecutionInfo; - private static Hashtable m_Table = new Hashtable(); + if (info == null) + return 0; - public static int GetSwingBonus( Mobile target ) - { - HonorableExecutionInfo info = m_Table[target] as HonorableExecutionInfo; + return info.m_SwingBonus; + } - if ( info == null ) - return 0; + public static bool IsUnderPenalty(Mobile target) + { + HonorableExecutionInfo info = m_Table[target] as HonorableExecutionInfo; - return info.m_SwingBonus; - } + if (info == null) + return false; - public static bool IsUnderPenalty( Mobile target ) - { - HonorableExecutionInfo info = m_Table[target] as HonorableExecutionInfo; + return info.m_Penalty; + } - if ( info == null ) - return false; + public static void RemovePenalty(Mobile target) + { + HonorableExecutionInfo info = m_Table[target] as HonorableExecutionInfo; - return info.m_Penalty; - } + if (info == null || !info.m_Penalty) + return; - public static void RemovePenalty( Mobile target ) - { - HonorableExecutionInfo info = m_Table[target] as HonorableExecutionInfo; + info.Clear(); - if ( info == null || !info.m_Penalty ) - return; + info.m_Timer?.Stop(); - info.Clear(); + m_Table.Remove(target); + } - info.m_Timer?.Stop(); + public void EndEffect(object state) + { + HonorableExecutionInfo info = (HonorableExecutionInfo)state; - m_Table.Remove( target ); - } + RemovePenalty(info.m_Mobile); + } - private class HonorableExecutionInfo - { - public Mobile m_Mobile; - public int m_SwingBonus; - public ArrayList m_Mods; - public bool m_Penalty; - public Timer m_Timer; + private class HonorableExecutionInfo + { + public Mobile m_Mobile; + public ArrayList m_Mods; + public bool m_Penalty; + public int m_SwingBonus; + public Timer m_Timer; - public HonorableExecutionInfo( Mobile from, int swingBonus ) : this( from, swingBonus, null, false ) - { - } + public HonorableExecutionInfo(Mobile from, int swingBonus) : this(from, swingBonus, null, false) + { + } - public HonorableExecutionInfo( Mobile from, ArrayList mods ) : this( from, 0, mods, true ) - { - } + public HonorableExecutionInfo(Mobile from, ArrayList mods) : this(from, 0, mods, true) + { + } - public HonorableExecutionInfo( Mobile from, int swingBonus, ArrayList mods, bool penalty ) - { - m_Mobile = from; - m_SwingBonus = swingBonus; - m_Mods = mods; - m_Penalty = penalty; + public HonorableExecutionInfo(Mobile from, int swingBonus, ArrayList mods, bool penalty) + { + m_Mobile = from; + m_SwingBonus = swingBonus; + m_Mods = mods; + m_Penalty = penalty; - Apply(); - } + Apply(); + } - public void Apply() - { - if ( m_Mods == null ) - return; + public void Apply() + { + if (m_Mods == null) + return; - for ( int i = 0; i < m_Mods.Count; ++i ) - { - object mod = m_Mods[i]; + for (int i = 0; i < m_Mods.Count; ++i) + { + object mod = m_Mods[i]; - if ( mod is ResistanceMod ) - m_Mobile.AddResistanceMod( (ResistanceMod) mod ); - else if ( mod is SkillMod ) - m_Mobile.AddSkillMod( (SkillMod) mod ); - } - } + if (mod is ResistanceMod) + m_Mobile.AddResistanceMod((ResistanceMod)mod); + else if (mod is SkillMod) + m_Mobile.AddSkillMod((SkillMod)mod); + } + } - public void Clear() - { - if ( m_Mods == null ) - return; + public void Clear() + { + if (m_Mods == null) + return; - for ( int i = 0; i < m_Mods.Count; ++i ) - { - object mod = m_Mods[i]; + for (int i = 0; i < m_Mods.Count; ++i) + { + object mod = m_Mods[i]; - if ( mod is ResistanceMod ) - m_Mobile.RemoveResistanceMod( (ResistanceMod) mod ); - else if ( mod is SkillMod ) - m_Mobile.RemoveSkillMod( (SkillMod) mod ); - } - } - } - - public void EndEffect( object state ) - { - HonorableExecutionInfo info = (HonorableExecutionInfo)state; - - RemovePenalty( info.m_Mobile ); - } - } -} + if (mod is ResistanceMod) + m_Mobile.RemoveResistanceMod((ResistanceMod)mod); + else if (mod is SkillMod) + m_Mobile.RemoveSkillMod((SkillMod)mod); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/LightningStrike.cs b/Scripts/Spells/Bushido/LightningStrike.cs index 156e3c871..af3b105d4 100644 --- a/Scripts/Spells/Bushido/LightningStrike.cs +++ b/Scripts/Spells/Bushido/LightningStrike.cs @@ -2,69 +2,68 @@ using Server.Mobiles; namespace Server.Spells.Bushido { - public class LightningStrike : SamuraiMove - { - public LightningStrike() - { - } + public class LightningStrike : SamuraiMove + { + public override int BaseMana => 5; + public override double RequiredSkill => 50.0; - public override int BaseMana => 5; - public override double RequiredSkill => 50.0; + public override TextDefinition AbilityMessage => new TextDefinition(1063167); // You prepare to strike quickly. - public override TextDefinition AbilityMessage => new TextDefinition( 1063167 ); // You prepare to strike quickly. + public override bool DelayedContext => true; - public override bool DelayedContext => true; + public override bool ValidatesDuringHit => false; - public override int GetAccuracyBonus( Mobile attacker ) - { - return 50; - } + public override int GetAccuracyBonus(Mobile attacker) + { + return 50; + } - public override bool Validate(Mobile from) - { - bool isValid=base.Validate(from); - if (isValid) - { - PlayerMobile ThePlayer = from as PlayerMobile; - ThePlayer.ExecutesLightningStrike = BaseMana; - } - return isValid; - } + public override bool Validate(Mobile from) + { + bool isValid = base.Validate(from); + if (isValid) + { + PlayerMobile ThePlayer = from as PlayerMobile; + ThePlayer.ExecutesLightningStrike = BaseMana; + } - public override bool IgnoreArmor( Mobile attacker ) - { - double bushido = attacker.Skills[SkillName.Bushido].Value; - double criticalChance = (bushido * bushido) / 72000.0; - return ( criticalChance >= Utility.RandomDouble() ); - } + return isValid; + } - public override bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - /* no mana drain before actual hit */ - bool enoughMana = CheckMana(attacker, false); - return Validate(attacker); - } + public override bool IgnoreArmor(Mobile attacker) + { + double bushido = attacker.Skills[SkillName.Bushido].Value; + double criticalChance = bushido * bushido / 72000.0; + return criticalChance >= Utility.RandomDouble(); + } - public override bool ValidatesDuringHit => false; + public override bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + /* no mana drain before actual hit */ + bool enoughMana = CheckMana(attacker, false); + return Validate(attacker); + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - ClearCurrentMove(attacker); - if (CheckMana(attacker, true)) - { - attacker.SendLocalizedMessage(1063168); // You attack with lightning precision! - defender.SendLocalizedMessage(1063169); // Your opponent's quick strike causes extra damage! - defender.FixedParticles(0x3818, 1, 11, 0x13A8, 0, 0, EffectLayer.Waist); - defender.PlaySound(0x51D); - CheckGain(attacker); - SetContext(attacker); - } - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + ClearCurrentMove(attacker); + if (CheckMana(attacker, true)) + { + attacker.SendLocalizedMessage(1063168); // You attack with lightning precision! + defender.SendLocalizedMessage(1063169); // Your opponent's quick strike causes extra damage! + defender.FixedParticles(0x3818, 1, 11, 0x13A8, 0, 0, EffectLayer.Waist); + defender.PlaySound(0x51D); + CheckGain(attacker); + SetContext(attacker); + } + } - public override void OnClearMove( Mobile attacker ) - { - PlayerMobile ThePlayer = attacker as PlayerMobile; // this can be deletet if the PlayerMobile parts are moved to Server.Mobile - ThePlayer.ExecutesLightningStrike = 0; - } - } -} + public override void OnClearMove(Mobile attacker) + { + PlayerMobile + ThePlayer = + attacker as PlayerMobile; // this can be deletet if the PlayerMobile parts are moved to Server.Mobile + ThePlayer.ExecutesLightningStrike = 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/MomentumStrike.cs b/Scripts/Spells/Bushido/MomentumStrike.cs index 504db9b27..5b53c3bf6 100644 --- a/Scripts/Spells/Bushido/MomentumStrike.cs +++ b/Scripts/Spells/Bushido/MomentumStrike.cs @@ -3,71 +3,68 @@ using Server.Items; namespace Server.Spells.Bushido { - public class MomentumStrike : SamuraiMove - { - public MomentumStrike() - { - } + public class MomentumStrike : SamuraiMove + { + public override int BaseMana => 10; + public override double RequiredSkill => 70.0; - public override int BaseMana => 10; - public override double RequiredSkill => 70.0; + public override TextDefinition AbilityMessage => + new TextDefinition(1070757); // You prepare to strike two enemies with one blow. - public override TextDefinition AbilityMessage => new TextDefinition( 1070757 ); // You prepare to strike two enemies with one blow. + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, false)) + return; - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, false ) ) - return; + ClearCurrentMove(attacker); - ClearCurrentMove( attacker ); + BaseWeapon weapon = attacker.Weapon as BaseWeapon; - BaseWeapon weapon = attacker.Weapon as BaseWeapon; + List targets = new List(); - List targets = new List(); + foreach (Mobile m in attacker.GetMobilesInRange(weapon.MaxRange)) + { + if (m == defender) + continue; - foreach ( Mobile m in attacker.GetMobilesInRange( weapon.MaxRange ) ) - { - if ( m == defender ) - continue; + if (m.Combatant != attacker) + continue; - if ( m.Combatant != attacker ) - continue; + targets.Add(m); + } - targets.Add( m ); - } + if (targets.Count > 0) + { + if (!CheckMana(attacker, true)) + return; - if ( targets.Count > 0 ) - { - if ( !CheckMana( attacker, true ) ) - return; + Mobile target = targets[Utility.Random(targets.Count)]; - Mobile target = targets[Utility.Random( targets.Count )]; + double damageBonus = attacker.Skills[SkillName.Bushido].Value / 100.0; - double damageBonus = attacker.Skills[SkillName.Bushido].Value / 100.0; + if (!defender.Alive) + damageBonus *= 1.5; - if ( !defender.Alive ) - damageBonus *= 1.5; + attacker.SendLocalizedMessage(1063171); // You transfer the momentum of your weapon into another enemy! + target.SendLocalizedMessage(1063172); // You were hit by the momentum of a Samurai's weapon! - attacker.SendLocalizedMessage( 1063171 ); // You transfer the momentum of your weapon into another enemy! - target.SendLocalizedMessage( 1063172 ); // You were hit by the momentum of a Samurai's weapon! + target.FixedParticles(0x37B9, 1, 4, 0x251D, 0, 0, EffectLayer.Waist); - target.FixedParticles( 0x37B9, 1, 4, 0x251D, 0, 0, EffectLayer.Waist ); + attacker.PlaySound(0x510); - attacker.PlaySound( 0x510 ); + weapon.OnSwing(attacker, target, damageBonus); - weapon.OnSwing( attacker, target, damageBonus ); + CheckGain(attacker); + } + else + { + attacker.SendLocalizedMessage(1063123); // There are no valid targets to attack! + } + } - CheckGain( attacker ); - } - else - { - attacker.SendLocalizedMessage( 1063123 ); // There are no valid targets to attack! - } - } - - public override void CheckGain( Mobile m ) - { - m.CheckSkill( MoveSkill, RequiredSkill, 120.0 ); - } - } -} + public override void CheckGain(Mobile m) + { + m.CheckSkill(MoveSkill, RequiredSkill, 120.0); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/SamuraiMove.cs b/Scripts/Spells/Bushido/SamuraiMove.cs index 8e0584931..bd5cc5844 100644 --- a/Scripts/Spells/Bushido/SamuraiMove.cs +++ b/Scripts/Spells/Bushido/SamuraiMove.cs @@ -1,12 +1,12 @@ namespace Server.Spells { - public class SamuraiMove : SpecialMove - { - public override SkillName MoveSkill => SkillName.Bushido; + public class SamuraiMove : SpecialMove + { + public override SkillName MoveSkill => SkillName.Bushido; - public override void CheckGain( Mobile m ) - { - m.CheckSkill( MoveSkill, RequiredSkill - 12.5, RequiredSkill + 37.5 ); //Per five on friday 02/16/07 - } - } -} + public override void CheckGain(Mobile m) + { + m.CheckSkill(MoveSkill, RequiredSkill - 12.5, RequiredSkill + 37.5); //Per five on friday 02/16/07 + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Bushido/SamuraiSpell.cs b/Scripts/Spells/Bushido/SamuraiSpell.cs index 035e27a6f..7824bbe6f 100644 --- a/Scripts/Spells/Bushido/SamuraiSpell.cs +++ b/Scripts/Spells/Bushido/SamuraiSpell.cs @@ -1,128 +1,132 @@ using System; -using Server.Network; using Server.Mobiles; +using Server.Network; namespace Server.Spells.Bushido { - public abstract class SamuraiSpell : Spell - { - public abstract double RequiredSkill{ get; } - public abstract int RequiredMana{ get; } + public abstract class SamuraiSpell : Spell + { + public SamuraiSpell(Mobile caster, Item scroll, SpellInfo info) : base(caster, scroll, info) + { + } - public override SkillName CastSkill => SkillName.Bushido; - public override SkillName DamageSkill => SkillName.Bushido; + public abstract double RequiredSkill{ get; } + public abstract int RequiredMana{ get; } - public override bool ClearHandsOnCast => false; - public override bool BlocksMovement => false; - public override bool ShowHandMovement => false; + public override SkillName CastSkill => SkillName.Bushido; + public override SkillName DamageSkill => SkillName.Bushido; - //public override int CastDelayBase => 1; - public override double CastDelayFastScalar => 0; + public override bool ClearHandsOnCast => false; + public override bool BlocksMovement => false; + public override bool ShowHandMovement => false; - public override int CastRecoveryBase => 7; + //public override int CastDelayBase => 1; + public override double CastDelayFastScalar => 0; - public SamuraiSpell( Mobile caster, Item scroll, SpellInfo info ) : base( caster, scroll, info ) - { - } + public override int CastRecoveryBase => 7; - public static bool CheckExpansion( Mobile from ) - { - if ( !( from is PlayerMobile ) ) - return true; + public static bool CheckExpansion(Mobile from) + { + if (!(from is PlayerMobile)) + return true; - if ( from.NetState == null ) - return false; + if (from.NetState == null) + return false; - return from.NetState.SupportsExpansion( Expansion.SE ); - } + return from.NetState.SupportsExpansion(Expansion.SE); + } - public override bool CheckCast() - { - int mana = ScaleMana ( RequiredMana ); + public override bool CheckCast() + { + int mana = ScaleMana(RequiredMana); - if ( !base.CheckCast() ) - return false; + if (!base.CheckCast()) + return false; - if ( !CheckExpansion( Caster ) ) - { - Caster.SendLocalizedMessage( 1063456 ); // You must upgrade to Samurai Empire in order to use that ability. - return false; - } + if (!CheckExpansion(Caster)) + { + Caster.SendLocalizedMessage(1063456); // You must upgrade to Samurai Empire in order to use that ability. + return false; + } - if ( Caster.Skills[CastSkill].Value < RequiredSkill ) - { - string args = $"{RequiredSkill.ToString("F1")}\t{CastSkill.ToString()}\t "; - Caster.SendLocalizedMessage( 1063013, args ); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - return false; - } + if (Caster.Skills[CastSkill].Value < RequiredSkill) + { + string args = $"{RequiredSkill.ToString("F1")}\t{CastSkill.ToString()}\t "; + Caster.SendLocalizedMessage(1063013, + args); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + return false; + } - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - return true; - } + return true; + } - public override bool CheckFizzle() - { - int mana = ScaleMana( RequiredMana ); + public override bool CheckFizzle() + { + int mana = ScaleMana(RequiredMana); - if ( Caster.Skills[CastSkill].Value < RequiredSkill ) - { - Caster.SendLocalizedMessage( 1070768, RequiredSkill.ToString( "F1" ) ); // You need ~1_SKILL_REQUIREMENT~ Bushido skill to perform that attack! - return false; - } + if (Caster.Skills[CastSkill].Value < RequiredSkill) + { + Caster.SendLocalizedMessage(1070768, + RequiredSkill.ToString("F1")); // You need ~1_SKILL_REQUIREMENT~ Bushido skill to perform that attack! + return false; + } - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - if ( !base.CheckFizzle() ) - return false; + if (!base.CheckFizzle()) + return false; - Caster.Mana -= mana; + Caster.Mana -= mana; - return true; - } + return true; + } - public override void GetCastSkills( out double min, out double max ) - { - min = RequiredSkill - 12.5; //per 5 on friday, 2/16/07 - max = RequiredSkill + 37.5; - } + public override void GetCastSkills(out double min, out double max) + { + min = RequiredSkill - 12.5; //per 5 on friday, 2/16/07 + max = RequiredSkill + 37.5; + } - public override int GetMana() - { - return 0; - } + public override int GetMana() + { + return 0; + } - public virtual void OnCastSuccessful( Mobile caster ) - { - if ( Evasion.IsEvading( caster ) ) - Evasion.EndEvasion( caster ); + public virtual void OnCastSuccessful(Mobile caster) + { + if (Evasion.IsEvading(caster)) + Evasion.EndEvasion(caster); - if ( Confidence.IsConfident( caster ) ) - Confidence.EndConfidence( caster ); + if (Confidence.IsConfident(caster)) + Confidence.EndConfidence(caster); - if ( CounterAttack.IsCountering( caster ) ) - CounterAttack.StopCountering( caster ); + if (CounterAttack.IsCountering(caster)) + CounterAttack.StopCountering(caster); - int spellID = SpellRegistry.GetRegistryNumber( this ); + int spellID = SpellRegistry.GetRegistryNumber(this); - if ( spellID > 0 ) - caster.Send( new ToggleSpecialAbility( spellID + 1, true ) ); - } + if (spellID > 0) + caster.Send(new ToggleSpecialAbility(spellID + 1, true)); + } - public static void OnEffectEnd( Mobile caster, Type type ) - { - int spellID = SpellRegistry.GetRegistryNumber( type ); + public static void OnEffectEnd(Mobile caster, Type type) + { + int spellID = SpellRegistry.GetRegistryNumber(type); - if ( spellID > 0 ) - caster.Send( new ToggleSpecialAbility( spellID + 1, false ) ); - } - } -} + if (spellID > 0) + caster.Send(new ToggleSpecialAbility(spellID + 1, false)); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/CleanseByFire.cs b/Scripts/Spells/Chivalry/CleanseByFire.cs index d5e9c7021..85c49d26a 100644 --- a/Scripts/Spells/Chivalry/CleanseByFire.cs +++ b/Scripts/Spells/Chivalry/CleanseByFire.cs @@ -1,124 +1,126 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Spells.Chivalry { - public class CleanseByFireSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Cleanse By Fire", "Expor Flamus", - -1, - 9002 - ); + public class CleanseByFireSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Cleanse By Fire", "Expor Flamus", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + public CleanseByFireSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 5.0; - public override int RequiredMana => 10; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060718; // Expor Flamus + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public CleanseByFireSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 5.0; + public override int RequiredMana => 10; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060718; // Expor Flamus - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !m.Poisoned ) - { - Caster.SendLocalizedMessage( 1060176 ); // That creature is not poisoned! - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!m.Poisoned) + { + Caster.SendLocalizedMessage(1060176); // That creature is not poisoned! + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Cures the target of poisons, but causes the caster to be burned by fire damage for 13-55 hit points. - * The amount of fire damage is lessened if the caster has high Karma. - */ + /* Cures the target of poisons, but causes the caster to be burned by fire damage for 13-55 hit points. + * The amount of fire damage is lessened if the caster has high Karma. + */ - Poison p = m.Poison; + Poison p = m.Poison; - if ( p != null ) - { - // Cleanse by fire is now difficulty based - int chanceToCure = 10000 + (int)(Caster.Skills[SkillName.Chivalry].Value * 75) - ((p.Level + 1) * 2000); - chanceToCure /= 100; + if (p != null) + { + // Cleanse by fire is now difficulty based + int chanceToCure = 10000 + (int)(Caster.Skills[SkillName.Chivalry].Value * 75) - (p.Level + 1) * 2000; + chanceToCure /= 100; - if ( chanceToCure > Utility.Random( 100 ) ) - { - if ( m.CurePoison( Caster ) ) - { - if ( Caster != m ) - Caster.SendLocalizedMessage( 1010058 ); // You have cured the target of all poisons! + if (chanceToCure > Utility.Random(100)) + { + if (m.CurePoison(Caster)) + { + if (Caster != m) + Caster.SendLocalizedMessage(1010058); // You have cured the target of all poisons! - m.SendLocalizedMessage( 1010059 ); // You have been cured of all poisons. - } - } - else - { - m.SendLocalizedMessage( 1010060 ); // You have failed to cure your target! - } - } + m.SendLocalizedMessage(1010059); // You have been cured of all poisons. + } + } + else + { + m.SendLocalizedMessage(1010060); // You have failed to cure your target! + } + } - m.PlaySound( 0x1E0 ); - m.FixedParticles( 0x373A, 1, 15, 5012, 3, 2, EffectLayer.Waist ); + m.PlaySound(0x1E0); + m.FixedParticles(0x373A, 1, 15, 5012, 3, 2, EffectLayer.Waist); - IEntity from = new Entity( Serial.Zero, new Point3D( m.X, m.Y, m.Z - 5 ), m.Map ); - IEntity to = new Entity( Serial.Zero, new Point3D( m.X, m.Y, m.Z + 45 ), m.Map ); - Effects.SendMovingParticles( from, to, 0x374B, 1, 0, false, false, 63, 2, 9501, 1, 0, EffectLayer.Head, 0x100 ); + IEntity from = new Entity(Serial.Zero, new Point3D(m.X, m.Y, m.Z - 5), m.Map); + IEntity to = new Entity(Serial.Zero, new Point3D(m.X, m.Y, m.Z + 45), m.Map); + Effects.SendMovingParticles(from, to, 0x374B, 1, 0, false, false, 63, 2, 9501, 1, 0, EffectLayer.Head, + 0x100); - Caster.PlaySound( 0x208 ); - Caster.FixedParticles( 0x3709, 1, 30, 9934, 0, 7, EffectLayer.Waist ); + Caster.PlaySound(0x208); + Caster.FixedParticles(0x3709, 1, 30, 9934, 0, 7, EffectLayer.Waist); - int damage = 50 - ComputePowerValue( 4 ); + int damage = 50 - ComputePowerValue(4); - // TODO: Should caps be applied? - if ( damage < 13 ) - damage = 13; - else if ( damage > 55 ) - damage = 55; + // TODO: Should caps be applied? + if (damage < 13) + damage = 13; + else if (damage > 55) + damage = 55; - AOS.Damage( Caster, Caster, damage, 0, 100, 0, 0, 0, true ); - } + AOS.Damage(Caster, Caster, damage, 0, 100, 0, 0, 0, true); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private CleanseByFireSpell m_Owner; + private class InternalTarget : Target + { + private CleanseByFireSpell m_Owner; - public InternalTarget( CleanseByFireSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(CleanseByFireSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/CloseWounds.cs b/Scripts/Spells/Chivalry/CloseWounds.cs index 08e0e1618..6ebac1ee8 100644 --- a/Scripts/Spells/Chivalry/CloseWounds.cs +++ b/Scripts/Spells/Chivalry/CloseWounds.cs @@ -1,119 +1,122 @@ using System; -using Server.Network; +using Server.Engines.ConPVP; +using Server.Items; using Server.Mobiles; +using Server.Network; using Server.Targeting; namespace Server.Spells.Chivalry { - public class CloseWoundsSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Close Wounds", "Obsu Vulni", - -1, - 9002 - ); + public class CloseWoundsSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Close Wounds", "Obsu Vulni", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public CloseWoundsSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 0.0; - public override int RequiredMana => 10; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060719; // Obsu Vulni + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public CloseWoundsSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 0.0; + public override int RequiredMana => 10; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060719; // Obsu Vulni - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.InRange( m, 2 ) ) - { - Caster.SendLocalizedMessage( 1060178 ); // You are too far away to perform that action! - } - else if ( m is BaseCreature && ((BaseCreature)m).IsAnimatedDead ) - { - Caster.SendLocalizedMessage( 1061654 ); // You cannot heal that which is not alive. - } - else if ( m.IsDeadBondedPet ) - { - Caster.SendLocalizedMessage( 1060177 ); // You cannot heal a creature that is already dead! - } - else if ( m.Hits >= m.HitsMax ) - { - Caster.SendLocalizedMessage( 500955 ); // That being is not damaged! - } - else if ( m.Poisoned || Items.MortalStrike.IsWounded( m ) ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, (Caster == m) ? 1005000 : 1010398 ); - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.InRange(m, 2)) + { + Caster.SendLocalizedMessage(1060178); // You are too far away to perform that action! + } + else if (m is BaseCreature && ((BaseCreature)m).IsAnimatedDead) + { + Caster.SendLocalizedMessage(1061654); // You cannot heal that which is not alive. + } + else if (m.IsDeadBondedPet) + { + Caster.SendLocalizedMessage(1060177); // You cannot heal a creature that is already dead! + } + else if (m.Hits >= m.HitsMax) + { + Caster.SendLocalizedMessage(500955); // That being is not damaged! + } + else if (m.Poisoned || MortalStrike.IsWounded(m)) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, Caster == m ? 1005000 : 1010398); + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Heals the target for 7 to 39 points of damage. - * The caster's Karma affects the amount of damage healed. - */ + /* Heals the target for 7 to 39 points of damage. + * The caster's Karma affects the amount of damage healed. + */ - int toHeal = ComputePowerValue( 6 ) + Utility.RandomMinMax( 0, 2 ); + int toHeal = ComputePowerValue(6) + Utility.RandomMinMax(0, 2); - // TODO: Should caps be applied? - if ( toHeal < 7 ) - toHeal = 7; - else if ( toHeal > 39 ) - toHeal = 39; + // TODO: Should caps be applied? + if (toHeal < 7) + toHeal = 7; + else if (toHeal > 39) + toHeal = 39; - if ( (m.Hits + toHeal) > m.HitsMax ) - toHeal = m.HitsMax - m.Hits; + if (m.Hits + toHeal > m.HitsMax) + toHeal = m.HitsMax - m.Hits; - //m.Hits += toHeal; //Was previously due to the message - //m.Heal( toHeal, Caster, false ); - SpellHelper.Heal( toHeal, m, Caster, false ); + //m.Hits += toHeal; //Was previously due to the message + //m.Heal( toHeal, Caster, false ); + SpellHelper.Heal(toHeal, m, Caster, false); - m.SendLocalizedMessage( 1060203, toHeal.ToString() ); // You have had ~1_HEALED_AMOUNT~ hit points of damage healed. + m.SendLocalizedMessage(1060203, + toHeal.ToString()); // You have had ~1_HEALED_AMOUNT~ hit points of damage healed. - m.PlaySound( 0x202 ); - m.FixedParticles( 0x376A, 1, 62, 9923, 3, 3, EffectLayer.Waist ); - m.FixedParticles( 0x3779, 1, 46, 9502, 5, 3, EffectLayer.Waist ); - } + m.PlaySound(0x202); + m.FixedParticles(0x376A, 1, 62, 9923, 3, 3, EffectLayer.Waist); + m.FixedParticles(0x3779, 1, 46, 9502, 5, 3, EffectLayer.Waist); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private CloseWoundsSpell m_Owner; + private class InternalTarget : Target + { + private CloseWoundsSpell m_Owner; - public InternalTarget( CloseWoundsSpell owner ) : base( 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(CloseWoundsSpell owner) : base(12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/ConsecrateWeapon.cs b/Scripts/Spells/Chivalry/ConsecrateWeapon.cs index 00ac14e29..da8db66b4 100644 --- a/Scripts/Spells/Chivalry/ConsecrateWeapon.cs +++ b/Scripts/Spells/Chivalry/ConsecrateWeapon.cs @@ -4,101 +4,111 @@ using Server.Items; namespace Server.Spells.Chivalry { - public class ConsecrateWeaponSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Consecrate Weapon", "Consecrus Arma", - -1, - 9002 - ); + public class ConsecrateWeaponSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Consecrate Weapon", "Consecrus Arma", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.5 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 15.0; - public override int RequiredMana => 10; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060720; // Consecrus Arma - public override bool BlocksMovement => false; + public ConsecrateWeaponSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ConsecrateWeaponSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.5); - public override void OnCast() - { - BaseWeapon weapon = Caster.Weapon as BaseWeapon; + public override double RequiredSkill => 15.0; + public override int RequiredMana => 10; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060720; // Consecrus Arma + public override bool BlocksMovement => false; - if ( weapon == null || weapon is Fists ) - { - Caster.SendLocalizedMessage( 501078 ); // You must be holding a weapon. - } - else if ( CheckSequence() ) - { - /* Temporarily enchants the weapon the caster is currently wielding. - * The type of damage the weapon inflicts when hitting a target will - * be converted to the target's worst Resistance type. - * Duration of the effect is affected by the caster's Karma and lasts for 3 to 11 seconds. - */ + public override void OnCast() + { + BaseWeapon weapon = Caster.Weapon as BaseWeapon; - int itemID, soundID; + if (weapon == null || weapon is Fists) + { + Caster.SendLocalizedMessage(501078); // You must be holding a weapon. + } + else if (CheckSequence()) + { + /* Temporarily enchants the weapon the caster is currently wielding. + * The type of damage the weapon inflicts when hitting a target will + * be converted to the target's worst Resistance type. + * Duration of the effect is affected by the caster's Karma and lasts for 3 to 11 seconds. + */ - switch ( weapon.Skill ) - { - case SkillName.Macing: itemID = 0xFB4; soundID = 0x232; break; - case SkillName.Archery: itemID = 0x13B1; soundID = 0x145; break; - default: itemID = 0xF5F; soundID = 0x56; break; - } + int itemID, soundID; - Caster.PlaySound( 0x20C ); - Caster.PlaySound( soundID ); - Caster.FixedParticles( 0x3779, 1, 30, 9964, 3, 3, EffectLayer.Waist ); + switch (weapon.Skill) + { + case SkillName.Macing: + itemID = 0xFB4; + soundID = 0x232; + break; + case SkillName.Archery: + itemID = 0x13B1; + soundID = 0x145; + break; + default: + itemID = 0xF5F; + soundID = 0x56; + break; + } - IEntity from = new Entity( Serial.Zero, new Point3D( Caster.X, Caster.Y, Caster.Z ), Caster.Map ); - IEntity to = new Entity( Serial.Zero, new Point3D( Caster.X, Caster.Y, Caster.Z + 50 ), Caster.Map ); - Effects.SendMovingParticles( from, to, itemID, 1, 0, false, false, 33, 3, 9501, 1, 0, EffectLayer.Head, 0x100 ); + Caster.PlaySound(0x20C); + Caster.PlaySound(soundID); + Caster.FixedParticles(0x3779, 1, 30, 9964, 3, 3, EffectLayer.Waist); - double seconds = ComputePowerValue( 20 ); + IEntity from = new Entity(Serial.Zero, new Point3D(Caster.X, Caster.Y, Caster.Z), Caster.Map); + IEntity to = new Entity(Serial.Zero, new Point3D(Caster.X, Caster.Y, Caster.Z + 50), Caster.Map); + Effects.SendMovingParticles(from, to, itemID, 1, 0, false, false, 33, 3, 9501, 1, 0, EffectLayer.Head, + 0x100); - // TODO: Should caps be applied? - if ( seconds < 3.0 ) - seconds = 3.0; - else if ( seconds > 11.0 ) - seconds = 11.0; + double seconds = ComputePowerValue(20); - TimeSpan duration = TimeSpan.FromSeconds( seconds ); + // TODO: Should caps be applied? + if (seconds < 3.0) + seconds = 3.0; + else if (seconds > 11.0) + seconds = 11.0; - Timer t = (Timer)m_Table[weapon]; + TimeSpan duration = TimeSpan.FromSeconds(seconds); - t?.Stop(); + Timer t = (Timer)m_Table[weapon]; - weapon.Consecrated = true; + t?.Stop(); - m_Table[weapon] = t = new ExpireTimer( weapon, duration ); + weapon.Consecrated = true; - t.Start(); - } + m_Table[weapon] = t = new ExpireTimer(weapon, duration); - FinishSequence(); - } + t.Start(); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - private class ExpireTimer : Timer - { - private BaseWeapon m_Weapon; + private class ExpireTimer : Timer + { + private BaseWeapon m_Weapon; - public ExpireTimer( BaseWeapon weapon, TimeSpan delay ) : base( delay ) - { - m_Weapon = weapon; - Priority = TimerPriority.FiftyMS; - } + public ExpireTimer(BaseWeapon weapon, TimeSpan delay) : base(delay) + { + m_Weapon = weapon; + Priority = TimerPriority.FiftyMS; + } - protected override void OnTick() - { - m_Weapon.Consecrated = false; - Effects.PlaySound( m_Weapon.GetWorldLocation(), m_Weapon.Map, 0x1F8 ); - m_Table.Remove( this ); - } - } - } -} + protected override void OnTick() + { + m_Weapon.Consecrated = false; + Effects.PlaySound(m_Weapon.GetWorldLocation(), m_Weapon.Map, 0x1F8); + m_Table.Remove(this); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/DispelEvil.cs b/Scripts/Spells/Chivalry/DispelEvil.cs index ac1912225..b5beb5624 100644 --- a/Scripts/Spells/Chivalry/DispelEvil.cs +++ b/Scripts/Spells/Chivalry/DispelEvil.cs @@ -6,112 +6,107 @@ using Server.Spells.Necromancy; namespace Server.Spells.Chivalry { - public class DispelEvilSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Dispel Evil", "Dispiro Malas", - -1, - 9002 - ); + public class DispelEvilSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Dispel Evil", "Dispiro Malas", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.25 ); + public DispelEvilSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 35.0; - public override int RequiredMana => 10; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060721; // Dispiro Malas - public override bool BlocksMovement => false; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.25); - public DispelEvilSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 35.0; + public override int RequiredMana => 10; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060721; // Dispiro Malas + public override bool BlocksMovement => false; - public override bool DelayedDamage => false; + public override bool DelayedDamage => false; - public override void SendCastEffect() - { - Caster.FixedEffect( 0x37C4, 10, 7, 4, 3 ); // At player - } + public override void SendCastEffect() + { + Caster.FixedEffect(0x37C4, 10, 7, 4, 3); // At player + } - public override void OnCast() - { - if ( CheckSequence() ) - { - List targets = new List(); + public override void OnCast() + { + if (CheckSequence()) + { + List targets = new List(); - foreach ( Mobile m in Caster.GetMobilesInRange( 8 ) ) - { - if ( Caster != m && SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) ) - targets.Add( m ); - } + foreach (Mobile m in Caster.GetMobilesInRange(8)) + if (Caster != m && SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false)) + targets.Add(m); - Caster.PlaySound( 0xF5 ); - Caster.PlaySound( 0x299 ); - Caster.FixedParticles( 0x37C4, 1, 25, 9922, 14, 3, EffectLayer.Head ); + Caster.PlaySound(0xF5); + Caster.PlaySound(0x299); + Caster.FixedParticles(0x37C4, 1, 25, 9922, 14, 3, EffectLayer.Head); - int dispelSkill = ComputePowerValue( 2 ); + int dispelSkill = ComputePowerValue(2); - double chiv = Caster.Skills.Chivalry.Value; + double chiv = Caster.Skills.Chivalry.Value; - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; - BaseCreature bc = m as BaseCreature; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; + BaseCreature bc = m as BaseCreature; - if ( bc != null ) - { - bool dispellable = bc.Summoned && !bc.IsAnimatedDead; + if (bc != null) + { + bool dispellable = bc.Summoned && !bc.IsAnimatedDead; - if ( dispellable ) - { - double dispelChance = (50.0 + ((100 * (chiv - bc.DispelDifficulty)) / (bc.DispelFocus*2))) / 100; - dispelChance *= dispelSkill / 100.0; + if (dispellable) + { + double dispelChance = (50.0 + 100 * (chiv - bc.DispelDifficulty) / (bc.DispelFocus * 2)) / 100; + dispelChance *= dispelSkill / 100.0; - if ( dispelChance > Utility.RandomDouble() ) - { - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x3728, 8, 20, 5042 ); - Effects.PlaySound( m, m.Map, 0x201 ); + if (dispelChance > Utility.RandomDouble()) + { + Effects.SendLocationParticles( + EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), 0x3728, 8, 20, 5042); + Effects.PlaySound(m, m.Map, 0x201); - m.Delete(); - continue; - } - } + m.Delete(); + continue; + } + } - bool evil = !bc.Controlled && bc.Karma < 0; + bool evil = !bc.Controlled && bc.Karma < 0; - if ( evil ) - { - // TODO: Is this right? - double fleeChance = (100 - Math.Sqrt( m.Fame / 2 )) * chiv * dispelSkill; - fleeChance /= 1000000; + if (evil) + { + // TODO: Is this right? + double fleeChance = (100 - Math.Sqrt(m.Fame / 2)) * chiv * dispelSkill; + fleeChance /= 1000000; - if ( fleeChance > Utility.RandomDouble() ) - { - // guide says 2 seconds, it's longer - bc.BeginFlee( TimeSpan.FromSeconds( 30.0 ) ); - } - } - } + if (fleeChance > Utility.RandomDouble()) bc.BeginFlee(TimeSpan.FromSeconds(30.0)); + } + } - TransformContext context = TransformationSpellHelper.GetContext( m ); - if ( context?.Spell is NecromancerSpell ) //Trees are not evil! TODO: OSI confirm? - { - // transformed .. + TransformContext context = TransformationSpellHelper.GetContext(m); + if (context?.Spell is NecromancerSpell) //Trees are not evil! TODO: OSI confirm? + { + // transformed .. - double drainChance = 0.5 * (Caster.Skills.Chivalry.Value / Math.Max( m.Skills.Necromancy.Value, 1 )); + double drainChance = 0.5 * (Caster.Skills.Chivalry.Value / Math.Max(m.Skills.Necromancy.Value, 1)); - if ( drainChance > Utility.RandomDouble() ) - { - int drain = (5 * dispelSkill) / 100; + if (drainChance > Utility.RandomDouble()) + { + int drain = 5 * dispelSkill / 100; - m.Stam -= drain; - m.Mana -= drain; - } - } - } - } + m.Stam -= drain; + m.Mana -= drain; + } + } + } + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/DivineFury.cs b/Scripts/Spells/Chivalry/DivineFury.cs index dfaccc104..bea8dcfcb 100644 --- a/Scripts/Spells/Chivalry/DivineFury.cs +++ b/Scripts/Spells/Chivalry/DivineFury.cs @@ -3,73 +3,75 @@ using System.Collections; namespace Server.Spells.Chivalry { - public class DivineFurySpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Divine Fury", "Divinum Furis", - -1, - 9002 - ); + public class DivineFurySpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Divine Fury", "Divinum Furis", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 25.0; - public override int RequiredMana => 15; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060722; // Divinum Furis - public override bool BlocksMovement => false; + public DivineFurySpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public DivineFurySpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.PlaySound( 0x20F ); - Caster.PlaySound( Caster.Female ? 0x338 : 0x44A ); - Caster.FixedParticles( 0x376A, 1, 31, 9961, 1160, 0, EffectLayer.Waist ); - Caster.FixedParticles( 0x37C4, 1, 31, 9502, 43, 2, EffectLayer.Waist ); + public override double RequiredSkill => 25.0; + public override int RequiredMana => 15; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060722; // Divinum Furis + public override bool BlocksMovement => false; - Caster.Stam = Caster.StamMax; + public override void OnCast() + { + if (CheckSequence()) + { + Caster.PlaySound(0x20F); + Caster.PlaySound(Caster.Female ? 0x338 : 0x44A); + Caster.FixedParticles(0x376A, 1, 31, 9961, 1160, 0, EffectLayer.Waist); + Caster.FixedParticles(0x37C4, 1, 31, 9502, 43, 2, EffectLayer.Waist); - Timer t = (Timer)m_Table[Caster]; + Caster.Stam = Caster.StamMax; - t?.Stop(); + Timer t = (Timer)m_Table[Caster]; - int delay = ComputePowerValue( 10 ); + t?.Stop(); - // TODO: Should caps be applied? - if ( delay < 7 ) - delay = 7; - else if ( delay > 24 ) - delay = 24; + int delay = ComputePowerValue(10); - m_Table[Caster] = t = Timer.DelayCall( TimeSpan.FromSeconds( delay ), new TimerStateCallback( Expire_Callback ), Caster ); - Caster.Delta( MobileDelta.WeaponDamage ); + // TODO: Should caps be applied? + if (delay < 7) + delay = 7; + else if (delay > 24) + delay = 24; - BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.DivineFury, 1060589, 1075634, TimeSpan.FromSeconds(delay), Caster)); - } + m_Table[Caster] = t = Timer.DelayCall(TimeSpan.FromSeconds(delay), new TimerStateCallback(Expire_Callback), + Caster); + Caster.Delta(MobileDelta.WeaponDamage); - FinishSequence(); - } + BuffInfo.AddBuff(Caster, + new BuffInfo(BuffIcon.DivineFury, 1060589, 1075634, TimeSpan.FromSeconds(delay), Caster)); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - public static bool UnderEffect( Mobile m ) - { - return m_Table.Contains( m ); - } + public static bool UnderEffect(Mobile m) + { + return m_Table.Contains(m); + } - private static void Expire_Callback( object state ) - { - Mobile m = (Mobile)state; + private static void Expire_Callback(object state) + { + Mobile m = (Mobile)state; - m_Table.Remove( m ); + m_Table.Remove(m); - m.Delta( MobileDelta.WeaponDamage ); - m.PlaySound( 0xF8 ); - } - } -} + m.Delta(MobileDelta.WeaponDamage); + m.PlaySound(0xF8); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/EnemyOfOne.cs b/Scripts/Spells/Chivalry/EnemyOfOne.cs index 8b31d128a..1fe6fc28b 100644 --- a/Scripts/Spells/Chivalry/EnemyOfOne.cs +++ b/Scripts/Spells/Chivalry/EnemyOfOne.cs @@ -4,76 +4,78 @@ using Server.Mobiles; namespace Server.Spells.Chivalry { - public class EnemyOfOneSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Enemy of One", "Forul Solum", - -1, - 9002 - ); + public class EnemyOfOneSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Enemy of One", "Forul Solum", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.5 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 45.0; - public override int RequiredMana => 20; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060723; // Forul Solum - public override bool BlocksMovement => false; + public EnemyOfOneSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EnemyOfOneSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.5); - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.PlaySound( 0x0F5 ); - Caster.PlaySound( 0x1ED ); - Caster.FixedParticles( 0x375A, 1, 30, 9966, 33, 2, EffectLayer.Head ); - Caster.FixedParticles( 0x37B9, 1, 30, 9502, 43, 3, EffectLayer.Head ); + public override double RequiredSkill => 45.0; + public override int RequiredMana => 20; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060723; // Forul Solum + public override bool BlocksMovement => false; - Timer t = (Timer)m_Table[Caster]; + public override void OnCast() + { + if (CheckSequence()) + { + Caster.PlaySound(0x0F5); + Caster.PlaySound(0x1ED); + Caster.FixedParticles(0x375A, 1, 30, 9966, 33, 2, EffectLayer.Head); + Caster.FixedParticles(0x37B9, 1, 30, 9502, 43, 3, EffectLayer.Head); - t?.Stop(); + Timer t = (Timer)m_Table[Caster]; - double delay = (double)ComputePowerValue( 1 ) / 60; + t?.Stop(); - // TODO: Should caps be applied? - if ( delay < 1.5 ) - delay = 1.5; - else if ( delay > 3.5 ) - delay = 3.5; + double delay = (double)ComputePowerValue(1) / 60; - m_Table[Caster] = Timer.DelayCall( TimeSpan.FromMinutes( delay ), new TimerStateCallback( Expire_Callback ), Caster ); + // TODO: Should caps be applied? + if (delay < 1.5) + delay = 1.5; + else if (delay > 3.5) + delay = 3.5; - if ( Caster is PlayerMobile ) - { - ((PlayerMobile)Caster).EnemyOfOneType = null; - ((PlayerMobile)Caster).WaitingForEnemy = true; + m_Table[Caster] = Timer.DelayCall(TimeSpan.FromMinutes(delay), new TimerStateCallback(Expire_Callback), + Caster); - BuffInfo.AddBuff ( Caster, new BuffInfo ( BuffIcon.EnemyOfOne, 1075653, 1044111, TimeSpan.FromMinutes ( delay ), Caster ) ); - } - } + if (Caster is PlayerMobile) + { + ((PlayerMobile)Caster).EnemyOfOneType = null; + ((PlayerMobile)Caster).WaitingForEnemy = true; - FinishSequence(); - } + BuffInfo.AddBuff(Caster, + new BuffInfo(BuffIcon.EnemyOfOne, 1075653, 1044111, TimeSpan.FromMinutes(delay), Caster)); + } + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - private static void Expire_Callback( object state ) - { - Mobile m = (Mobile)state; + private static void Expire_Callback(object state) + { + Mobile m = (Mobile)state; - m_Table.Remove( m ); + m_Table.Remove(m); - m.PlaySound( 0x1F8 ); + m.PlaySound(0x1F8); - if ( m is PlayerMobile ) - { - ((PlayerMobile)m).EnemyOfOneType = null; - ((PlayerMobile)m).WaitingForEnemy = false; - } - } - } -} + if (m is PlayerMobile) + { + ((PlayerMobile)m).EnemyOfOneType = null; + ((PlayerMobile)m).WaitingForEnemy = false; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/HolyLight.cs b/Scripts/Spells/Chivalry/HolyLight.cs index bf5d195f3..0e7edf21f 100644 --- a/Scripts/Spells/Chivalry/HolyLight.cs +++ b/Scripts/Spells/Chivalry/HolyLight.cs @@ -4,62 +4,66 @@ using Server.Items; namespace Server.Spells.Chivalry { - public class HolyLightSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Holy Light", "Augus Luminos", - -1, - 9002 - ); + public class HolyLightSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Holy Light", "Augus Luminos", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.75 ); + public HolyLightSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 55.0; - public override int RequiredMana => 10; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060724; // Augus Luminos - public override bool BlocksMovement => false; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.75); - public HolyLightSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 55.0; + public override int RequiredMana => 10; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060724; // Augus Luminos + public override bool BlocksMovement => false; - public override bool DelayedDamage => false; + public override bool DelayedDamage => false; - public override void OnCast() - { - if ( CheckSequence() ) - { - List targets = new List(); + public override void OnCast() + { + if (CheckSequence()) + { + List targets = new List(); - foreach ( Mobile m in Caster.GetMobilesInRange( 3 ) ) - if ( Caster != m && SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) && ( !Core.AOS || Caster.InLOS( m ) ) ) - targets.Add( m ); + foreach (Mobile m in Caster.GetMobilesInRange(3)) + if (Caster != m && SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false) && + (!Core.AOS || Caster.InLOS(m))) + targets.Add(m); - Caster.PlaySound( 0x212 ); - Caster.PlaySound( 0x206 ); + Caster.PlaySound(0x212); + Caster.PlaySound(0x206); - Effects.SendLocationParticles( EffectItem.Create( Caster.Location, Caster.Map, EffectItem.DefaultDuration ), 0x376A, 1, 29, 0x47D, 2, 9962, 0 ); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( Caster.X, Caster.Y, Caster.Z - 7 ), Caster.Map, EffectItem.DefaultDuration ), 0x37C4, 1, 29, 0x47D, 2, 9502, 0 ); + Effects.SendLocationParticles(EffectItem.Create(Caster.Location, Caster.Map, EffectItem.DefaultDuration), + 0x376A, 1, 29, 0x47D, 2, 9962, 0); + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(Caster.X, Caster.Y, Caster.Z - 7), Caster.Map, EffectItem.DefaultDuration), + 0x37C4, 1, 29, 0x47D, 2, 9502, 0); - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - int damage = ComputePowerValue( 10 ) + Utility.RandomMinMax( 0, 2 ); + int damage = ComputePowerValue(10) + Utility.RandomMinMax(0, 2); - // TODO: Should caps be applied? - if ( damage < 8 ) - damage = 8; - else if ( damage > 24 ) - damage = 24; + // TODO: Should caps be applied? + if (damage < 8) + damage = 8; + else if (damage > 24) + damage = 24; - Caster.DoHarmful( m ); - SpellHelper.Damage( this, m, damage, 0, 0, 0, 0, 100 ); - } - } + Caster.DoHarmful(m); + SpellHelper.Damage(this, m, damage, 0, 0, 0, 0, 100); + } + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/NobleSacrifice.cs b/Scripts/Spells/Chivalry/NobleSacrifice.cs index b5e476d45..d40189bb0 100644 --- a/Scripts/Spells/Chivalry/NobleSacrifice.cs +++ b/Scripts/Spells/Chivalry/NobleSacrifice.cs @@ -1,168 +1,169 @@ using System; using System.Collections.Generic; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; using Server.Spells.Necromancy; namespace Server.Spells.Chivalry { - public class NobleSacrificeSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Noble Sacrifice", "Dium Prostra", - -1, - 9002 - ); + public class NobleSacrificeSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Noble Sacrifice", "Dium Prostra", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public NobleSacrificeSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 65.0; - public override int RequiredMana => 20; - public override int RequiredTithing => 30; - public override int MantraNumber => 1060725; // Dium Prostra - public override bool BlocksMovement => false; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public NobleSacrificeSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 65.0; + public override int RequiredMana => 20; + public override int RequiredTithing => 30; + public override int MantraNumber => 1060725; // Dium Prostra + public override bool BlocksMovement => false; - public override void OnCast() - { - if ( CheckSequence() ) - { - List targets = new List(); + public override void OnCast() + { + if (CheckSequence()) + { + List targets = new List(); - foreach ( Mobile m in Caster.GetMobilesInRange( 3 ) ) // TODO: Validate range - { - if ( m is BaseCreature && ((BaseCreature)m).IsAnimatedDead ) - continue; + foreach (Mobile m in Caster.GetMobilesInRange(3)) // TODO: Validate range + { + if (m is BaseCreature && ((BaseCreature)m).IsAnimatedDead) + continue; - if ( Caster != m && m.InLOS( Caster ) && Caster.CanBeBeneficial( m, false, true ) && !(m is Golem) ) - targets.Add( m ); - } + if (Caster != m && m.InLOS(Caster) && Caster.CanBeBeneficial(m, false, true) && !(m is Golem)) + targets.Add(m); + } - Caster.PlaySound( 0x244 ); - Caster.FixedParticles( 0x3709, 1, 30, 9965, 5, 7, EffectLayer.Waist ); - Caster.FixedParticles( 0x376A, 1, 30, 9502, 5, 3, EffectLayer.Waist ); + Caster.PlaySound(0x244); + Caster.FixedParticles(0x3709, 1, 30, 9965, 5, 7, EffectLayer.Waist); + Caster.FixedParticles(0x376A, 1, 30, 9502, 5, 3, EffectLayer.Waist); - /* Attempts to Resurrect, Cure and Heal all targets in a radius around the caster. - * If any target is successfully assisted, the Paladin's current - * Hit Points, Mana and Stamina are set to 1. - * Amount of damage healed is affected by the Caster's Karma, from 8 to 24 hit points. - */ + /* Attempts to Resurrect, Cure and Heal all targets in a radius around the caster. + * If any target is successfully assisted, the Paladin's current + * Hit Points, Mana and Stamina are set to 1. + * Amount of damage healed is affected by the Caster's Karma, from 8 to 24 hit points. + */ - bool sacrifice = false; + bool sacrifice = false; - // TODO: Is there really a resurrection chance? - double resChance = 0.1 + (0.9 * ((double)Caster.Karma / 10000)); + // TODO: Is there really a resurrection chance? + double resChance = 0.1 + 0.9 * ((double)Caster.Karma / 10000); - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - if ( !m.Alive ) - { - if ( m.Region != null && m.Region.IsPartOf( "Khaldun" ) ) - { - Caster.SendLocalizedMessage( 1010395 ); // The veil of death in this area is too strong and resists thy efforts to restore life. - } - else if ( resChance > Utility.RandomDouble() ) - { - m.FixedParticles( 0x375A, 1, 15, 5005, 5, 3, EffectLayer.Head ); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, Caster ) ); - sacrifice = true; - } - } - else - { - bool sendEffect = false; + if (!m.Alive) + { + if (m.Region != null && m.Region.IsPartOf("Khaldun")) + { + Caster.SendLocalizedMessage( + 1010395); // The veil of death in this area is too strong and resists thy efforts to restore life. + } + else if (resChance > Utility.RandomDouble()) + { + m.FixedParticles(0x375A, 1, 15, 5005, 5, 3, EffectLayer.Head); + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, Caster)); + sacrifice = true; + } + } + else + { + bool sendEffect = false; - if ( m.Poisoned && m.CurePoison( Caster ) ) - { - Caster.DoBeneficial( m ); + if (m.Poisoned && m.CurePoison(Caster)) + { + Caster.DoBeneficial(m); - if ( Caster != m ) - Caster.SendLocalizedMessage( 1010058 ); // You have cured the target of all poisons! + if (Caster != m) + Caster.SendLocalizedMessage(1010058); // You have cured the target of all poisons! - m.SendLocalizedMessage( 1010059 ); // You have been cured of all poisons. - sendEffect = true; - sacrifice = true; - } + m.SendLocalizedMessage(1010059); // You have been cured of all poisons. + sendEffect = true; + sacrifice = true; + } - if ( m.Hits < m.HitsMax ) - { - int toHeal = ComputePowerValue( 10 ) + Utility.RandomMinMax( 0, 2 ); + if (m.Hits < m.HitsMax) + { + int toHeal = ComputePowerValue(10) + Utility.RandomMinMax(0, 2); - // TODO: Should caps be applied? - if ( toHeal < 8 ) - toHeal = 8; - else if ( toHeal > 24 ) - toHeal = 24; + // TODO: Should caps be applied? + if (toHeal < 8) + toHeal = 8; + else if (toHeal > 24) + toHeal = 24; - Caster.DoBeneficial( m ); - m.Heal( toHeal, Caster ); - sendEffect = true; - } + Caster.DoBeneficial(m); + m.Heal(toHeal, Caster); + sendEffect = true; + } - StatMod mod; + StatMod mod; - mod = m.GetStatMod( "[Magic] Str Offset" ); - if ( mod != null && mod.Offset < 0 ) - { - m.RemoveStatMod( "[Magic] Str Offset" ); - sendEffect = true; - } + mod = m.GetStatMod("[Magic] Str Offset"); + if (mod != null && mod.Offset < 0) + { + m.RemoveStatMod("[Magic] Str Offset"); + sendEffect = true; + } - mod = m.GetStatMod( "[Magic] Dex Offset" ); - if ( mod != null && mod.Offset < 0 ) - { - m.RemoveStatMod( "[Magic] Dex Offset" ); - sendEffect = true; - } + mod = m.GetStatMod("[Magic] Dex Offset"); + if (mod != null && mod.Offset < 0) + { + m.RemoveStatMod("[Magic] Dex Offset"); + sendEffect = true; + } - mod = m.GetStatMod( "[Magic] Int Offset" ); - if ( mod != null && mod.Offset < 0 ) - { - m.RemoveStatMod( "[Magic] Int Offset" ); - sendEffect = true; - } + mod = m.GetStatMod("[Magic] Int Offset"); + if (mod != null && mod.Offset < 0) + { + m.RemoveStatMod("[Magic] Int Offset"); + sendEffect = true; + } - if ( m.Paralyzed ) - { - m.Paralyzed = false; - sendEffect = true; - } + if (m.Paralyzed) + { + m.Paralyzed = false; + sendEffect = true; + } - if ( EvilOmenSpell.TryEndEffect( m ) ) - sendEffect = true; + if (EvilOmenSpell.TryEndEffect(m)) + sendEffect = true; - if ( StrangleSpell.RemoveCurse( m ) ) - sendEffect = true; + if (StrangleSpell.RemoveCurse(m)) + sendEffect = true; - if ( CorpseSkinSpell.RemoveCurse( m ) ) - sendEffect = true; + if (CorpseSkinSpell.RemoveCurse(m)) + sendEffect = true; - // TODO: Should this remove blood oath? Pain spike? + // TODO: Should this remove blood oath? Pain spike? - if ( sendEffect ) - { - m.FixedParticles( 0x375A, 1, 15, 5005, 5, 3, EffectLayer.Head ); - sacrifice = true; - } - } - } + if (sendEffect) + { + m.FixedParticles(0x375A, 1, 15, 5005, 5, 3, EffectLayer.Head); + sacrifice = true; + } + } + } - if ( sacrifice ) - { - Caster.PlaySound( Caster.Body.IsFemale ? 0x150 : 0x423 ); - Caster.Hits = 1; - Caster.Stam = 1; - Caster.Mana = 1; - } - } + if (sacrifice) + { + Caster.PlaySound(Caster.Body.IsFemale ? 0x150 : 0x423); + Caster.Hits = 1; + Caster.Stam = 1; + Caster.Mana = 1; + } + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/PaladinSpell.cs b/Scripts/Spells/Chivalry/PaladinSpell.cs index fc0cb58c2..14d845f27 100644 --- a/Scripts/Spells/Chivalry/PaladinSpell.cs +++ b/Scripts/Spells/Chivalry/PaladinSpell.cs @@ -3,139 +3,145 @@ using Server.Network; namespace Server.Spells.Chivalry { - public abstract class PaladinSpell : Spell - { - public abstract double RequiredSkill{ get; } - public abstract int RequiredMana{ get; } - public abstract int RequiredTithing{ get; } - public abstract int MantraNumber{ get; } + public abstract class PaladinSpell : Spell + { + public PaladinSpell(Mobile caster, Item scroll, SpellInfo info) : base(caster, scroll, info) + { + } - public override SkillName CastSkill => SkillName.Chivalry; - public override SkillName DamageSkill => SkillName.Chivalry; + public abstract double RequiredSkill{ get; } + public abstract int RequiredMana{ get; } + public abstract int RequiredTithing{ get; } + public abstract int MantraNumber{ get; } - public override bool ClearHandsOnCast => false; + public override SkillName CastSkill => SkillName.Chivalry; + public override SkillName DamageSkill => SkillName.Chivalry; - //public override int CastDelayBase => 1; + public override bool ClearHandsOnCast => false; - public override int CastRecoveryBase => 7; + //public override int CastDelayBase => 1; - public PaladinSpell( Mobile caster, Item scroll, SpellInfo info ) : base( caster, scroll, info ) - { - } + public override int CastRecoveryBase => 7; - public override bool CheckCast() - { - int mana = ScaleMana( RequiredMana ); + public override bool CheckCast() + { + int mana = ScaleMana(RequiredMana); - if ( !base.CheckCast() ) - return false; + if (!base.CheckCast()) + return false; - if ( Caster.TithingPoints < RequiredTithing ) - { - Caster.SendLocalizedMessage( 1060173, RequiredTithing.ToString() ); // You must have at least ~1_TITHE_REQUIREMENT~ Tithing Points to use this ability, - return false; - } + if (Caster.TithingPoints < RequiredTithing) + { + Caster.SendLocalizedMessage(1060173, + RequiredTithing + .ToString()); // You must have at least ~1_TITHE_REQUIREMENT~ Tithing Points to use this ability, + return false; + } - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - return true; - } + return true; + } - public override bool CheckFizzle() - { - int requiredTithing = RequiredTithing; + public override bool CheckFizzle() + { + int requiredTithing = RequiredTithing; - if ( AosAttributes.GetValue( Caster, AosAttribute.LowerRegCost ) > Utility.Random( 100 ) ) - requiredTithing = 0; + if (AosAttributes.GetValue(Caster, AosAttribute.LowerRegCost) > Utility.Random(100)) + requiredTithing = 0; - int mana = ScaleMana( RequiredMana ); + int mana = ScaleMana(RequiredMana); - if ( Caster.TithingPoints < requiredTithing ) - { - Caster.SendLocalizedMessage( 1060173, RequiredTithing.ToString() ); // You must have at least ~1_TITHE_REQUIREMENT~ Tithing Points to use this ability, - return false; - } + if (Caster.TithingPoints < requiredTithing) + { + Caster.SendLocalizedMessage(1060173, + RequiredTithing + .ToString()); // You must have at least ~1_TITHE_REQUIREMENT~ Tithing Points to use this ability, + return false; + } - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - Caster.TithingPoints -= requiredTithing; + Caster.TithingPoints -= requiredTithing; - if ( !base.CheckFizzle() ) - return false; + if (!base.CheckFizzle()) + return false; - Caster.Mana -= mana; + Caster.Mana -= mana; - return true; - } + return true; + } - public override void SayMantra() - { - Caster.PublicOverheadMessage( MessageType.Regular, 0x3B2, MantraNumber, "", false ); - } + public override void SayMantra() + { + Caster.PublicOverheadMessage(MessageType.Regular, 0x3B2, MantraNumber, "", false); + } - public override void DoFizzle() - { - Caster.PlaySound( 0x1D6 ); - Caster.NextSpellTime = Core.TickCount; - } + public override void DoFizzle() + { + Caster.PlaySound(0x1D6); + Caster.NextSpellTime = Core.TickCount; + } - public override void DoHurtFizzle() - { - Caster.PlaySound( 0x1D6 ); - } + public override void DoHurtFizzle() + { + Caster.PlaySound(0x1D6); + } - public override void OnDisturb( DisturbType type, bool message ) - { - base.OnDisturb( type, message ); + public override void OnDisturb(DisturbType type, bool message) + { + base.OnDisturb(type, message); - if ( message ) - Caster.PlaySound( 0x1D6 ); - } + if (message) + Caster.PlaySound(0x1D6); + } - public override void OnBeginCast() - { - base.OnBeginCast(); + public override void OnBeginCast() + { + base.OnBeginCast(); - SendCastEffect(); - } + SendCastEffect(); + } - public virtual void SendCastEffect() - { - Caster.FixedEffect( 0x37C4, 10, (int)( GetCastDelay().TotalSeconds * 28 ), 4, 3 ); - } + public virtual void SendCastEffect() + { + Caster.FixedEffect(0x37C4, 10, (int)(GetCastDelay().TotalSeconds * 28), 4, 3); + } - public override void GetCastSkills( out double min, out double max ) - { - min = RequiredSkill; - max = RequiredSkill + 50.0; - } + public override void GetCastSkills(out double min, out double max) + { + min = RequiredSkill; + max = RequiredSkill + 50.0; + } - public override int GetMana() - { - return 0; - } + public override int GetMana() + { + return 0; + } - public int ComputePowerValue( int div ) - { - return ComputePowerValue( Caster, div ); - } + public int ComputePowerValue(int div) + { + return ComputePowerValue(Caster, div); + } - public static int ComputePowerValue( Mobile from, int div ) - { - if ( from == null ) - return 0; + public static int ComputePowerValue(Mobile from, int div) + { + if (from == null) + return 0; - int v = (int) Math.Sqrt( from.Karma + 20000 + (from.Skills.Chivalry.Fixed * 10) ); + int v = (int)Math.Sqrt(from.Karma + 20000 + from.Skills.Chivalry.Fixed * 10); - return v / div; - } - } -} + return v / div; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/RemoveCurse.cs b/Scripts/Spells/Chivalry/RemoveCurse.cs index e9aab7163..f7ac6fe21 100644 --- a/Scripts/Spells/Chivalry/RemoveCurse.cs +++ b/Scripts/Spells/Chivalry/RemoveCurse.cs @@ -1,141 +1,143 @@ using System; +using Server.Engines.ConPVP; using Server.Items; -using Server.Targeting; -using Server.Spells.Necromancy; using Server.Spells.Fourth; +using Server.Spells.Necromancy; +using Server.Targeting; namespace Server.Spells.Chivalry { - public class RemoveCurseSpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Remove Curse", "Extermo Vomica", - -1, - 9002 - ); + public class RemoveCurseSpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Remove Curse", "Extermo Vomica", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public RemoveCurseSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 5.0; - public override int RequiredMana => 20; - public override int RequiredTithing => 10; - public override int MantraNumber => 1060726; // Extermo Vomica + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public RemoveCurseSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 5.0; + public override int RequiredMana => 20; + public override int RequiredTithing => 10; + public override int MantraNumber => 1060726; // Extermo Vomica - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Attempts to remove all Curse effects from Target. - * Curses include Mage spells such as Clumsy, Weaken, Feeblemind and Paralyze - * as well as all Necromancer curses. - * Chance of removing curse is affected by Caster's Karma. - */ + /* Attempts to remove all Curse effects from Target. + * Curses include Mage spells such as Clumsy, Weaken, Feeblemind and Paralyze + * as well as all Necromancer curses. + * Chance of removing curse is affected by Caster's Karma. + */ - int chance = 0; + int chance = 0; - if ( Caster.Karma < -5000 ) - chance = 0; - else if ( Caster.Karma < 0 ) - chance = (int) Math.Sqrt( 20000 + Caster.Karma ) - 122; - else if ( Caster.Karma < 5625 ) - chance = (int) Math.Sqrt( Caster.Karma ) + 25; - else - chance = 100; + if (Caster.Karma < -5000) + chance = 0; + else if (Caster.Karma < 0) + chance = (int)Math.Sqrt(20000 + Caster.Karma) - 122; + else if (Caster.Karma < 5625) + chance = (int)Math.Sqrt(Caster.Karma) + 25; + else + chance = 100; - if ( chance > Utility.Random( 100 ) ) - { - m.PlaySound( 0xF6 ); - m.PlaySound( 0x1F7 ); - m.FixedParticles( 0x3709, 1, 30, 9963, 13, 3, EffectLayer.Head ); + if (chance > Utility.Random(100)) + { + m.PlaySound(0xF6); + m.PlaySound(0x1F7); + m.FixedParticles(0x3709, 1, 30, 9963, 13, 3, EffectLayer.Head); - IEntity from = new Entity( Serial.Zero, new Point3D( m.X, m.Y, m.Z - 10 ), Caster.Map ); - IEntity to = new Entity( Serial.Zero, new Point3D( m.X, m.Y, m.Z + 50 ), Caster.Map ); - Effects.SendMovingParticles( from, to, 0x2255, 1, 0, false, false, 13, 3, 9501, 1, 0, EffectLayer.Head, 0x100 ); + IEntity from = new Entity(Serial.Zero, new Point3D(m.X, m.Y, m.Z - 10), Caster.Map); + IEntity to = new Entity(Serial.Zero, new Point3D(m.X, m.Y, m.Z + 50), Caster.Map); + Effects.SendMovingParticles(from, to, 0x2255, 1, 0, false, false, 13, 3, 9501, 1, 0, EffectLayer.Head, + 0x100); - StatMod mod; + StatMod mod; - mod = m.GetStatMod( "[Magic] Str Offset" ); - if ( mod != null && mod.Offset < 0 ) - m.RemoveStatMod( "[Magic] Str Offset" ); + mod = m.GetStatMod("[Magic] Str Offset"); + if (mod != null && mod.Offset < 0) + m.RemoveStatMod("[Magic] Str Offset"); - mod = m.GetStatMod( "[Magic] Dex Offset" ); - if ( mod != null && mod.Offset < 0 ) - m.RemoveStatMod( "[Magic] Dex Offset" ); + mod = m.GetStatMod("[Magic] Dex Offset"); + if (mod != null && mod.Offset < 0) + m.RemoveStatMod("[Magic] Dex Offset"); - mod = m.GetStatMod( "[Magic] Int Offset" ); - if ( mod != null && mod.Offset < 0 ) - m.RemoveStatMod( "[Magic] Int Offset" ); + mod = m.GetStatMod("[Magic] Int Offset"); + if (mod != null && mod.Offset < 0) + m.RemoveStatMod("[Magic] Int Offset"); - m.Paralyzed = false; + m.Paralyzed = false; - EvilOmenSpell.TryEndEffect( m ); - StrangleSpell.RemoveCurse( m ); - CorpseSkinSpell.RemoveCurse( m ); - CurseSpell.RemoveEffect( m ); - MortalStrike.EndWound( m ); - if (Core.ML) { BloodOathSpell.RemoveCurse ( m ); } - MindRotSpell.ClearMindRotScalar ( m ); + EvilOmenSpell.TryEndEffect(m); + StrangleSpell.RemoveCurse(m); + CorpseSkinSpell.RemoveCurse(m); + CurseSpell.RemoveEffect(m); + MortalStrike.EndWound(m); + if (Core.ML) BloodOathSpell.RemoveCurse(m); + MindRotSpell.ClearMindRotScalar(m); - BuffInfo.RemoveBuff( m, BuffIcon.Clumsy ); - BuffInfo.RemoveBuff( m, BuffIcon.FeebleMind ); - BuffInfo.RemoveBuff( m, BuffIcon.Weaken ); - BuffInfo.RemoveBuff ( m, BuffIcon.Curse ); - BuffInfo.RemoveBuff( m, BuffIcon.MassCurse ); - BuffInfo.RemoveBuff( m, BuffIcon.MortalStrike ); - BuffInfo.RemoveBuff ( m, BuffIcon.Mindrot ); + BuffInfo.RemoveBuff(m, BuffIcon.Clumsy); + BuffInfo.RemoveBuff(m, BuffIcon.FeebleMind); + BuffInfo.RemoveBuff(m, BuffIcon.Weaken); + BuffInfo.RemoveBuff(m, BuffIcon.Curse); + BuffInfo.RemoveBuff(m, BuffIcon.MassCurse); + BuffInfo.RemoveBuff(m, BuffIcon.MortalStrike); + BuffInfo.RemoveBuff(m, BuffIcon.Mindrot); - // TODO: Should this remove blood oath? Pain spike? - } - else - { - m.PlaySound( 0x1DF ); - } - } + // TODO: Should this remove blood oath? Pain spike? + } + else + { + m.PlaySound(0x1DF); + } + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private RemoveCurseSpell m_Owner; + private class InternalTarget : Target + { + private RemoveCurseSpell m_Owner; - public InternalTarget( RemoveCurseSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(RemoveCurseSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Chivalry/SacredJourney.cs b/Scripts/Spells/Chivalry/SacredJourney.cs index 21d4e0ec2..d4c6cf058 100644 --- a/Scripts/Spells/Chivalry/SacredJourney.cs +++ b/Scripts/Spells/Chivalry/SacredJourney.cs @@ -1,202 +1,211 @@ using System; +using Server.Factions; using Server.Items; -using Server.Multis; +using Server.Misc; using Server.Mobiles; +using Server.Multis; using Server.Network; using Server.Targeting; namespace Server.Spells.Chivalry { - public class SacredJourneySpell : PaladinSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Sacred Journey", "Sanctum Viatas", - -1, - 9002 - ); + public class SacredJourneySpell : PaladinSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Sacred Journey", "Sanctum Viatas", + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + private Runebook m_Book; - public override double RequiredSkill => 15.0; - public override int RequiredMana => 10; - public override int RequiredTithing => 15; - public override int MantraNumber => 1060727; // Sanctum Viatas - public override bool BlocksMovement => false; + private RunebookEntry m_Entry; - private RunebookEntry m_Entry; - private Runebook m_Book; + public SacredJourneySpell(Mobile caster, Item scroll) : this(caster, scroll, null, null) + { + } - public SacredJourneySpell( Mobile caster, Item scroll ) : this( caster, scroll, null, null ) - { - } + public SacredJourneySpell(Mobile caster, Item scroll, RunebookEntry entry, Runebook book) : base(caster, scroll, + m_Info) + { + m_Entry = entry; + m_Book = book; + } - public SacredJourneySpell( Mobile caster, Item scroll, RunebookEntry entry, Runebook book ) : base( caster, scroll, m_Info ) - { - m_Entry = entry; - m_Book = book; - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public override void OnCast() - { - if ( m_Entry == null ) - Caster.Target = new InternalTarget( this ); - else - Effect( m_Entry.Location, m_Entry.Map, true ); - } + public override double RequiredSkill => 15.0; + public override int RequiredMana => 10; + public override int RequiredTithing => 15; + public override int MantraNumber => 1060727; // Sanctum Viatas + public override bool BlocksMovement => false; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override void OnCast() + { + if (m_Entry == null) + Caster.Target = new InternalTarget(this); + else + Effect(m_Entry.Location, m_Entry.Map, true); + } - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( Caster.Criminal ) - { - Caster.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - return false; - } - if ( SpellHelper.CheckCombat( Caster ) ) - { - Caster.SendLocalizedMessage( 1061282 ); // You cannot use the Sacred Journey ability to flee from combat. - return false; - } - if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - return false; - } + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } - return SpellHelper.CheckTravel( Caster, TravelCheckType.RecallFrom ); - } + if (Caster.Criminal) + { + Caster.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + return false; + } - public void Effect( Point3D loc, Map map, bool checkMulti ) - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( map == null || (!Core.AOS && Caster.Map != map) ) - { - Caster.SendLocalizedMessage( 1005569 ); // You can not recall to another facet. - } - else if ( !SpellHelper.CheckTravel( Caster, TravelCheckType.RecallFrom ) ) - { - } - else if ( !SpellHelper.CheckTravel( Caster, map, loc, TravelCheckType.RecallTo ) ) - { - } - else if ( map == Map.Felucca && Caster is PlayerMobile && ((PlayerMobile)Caster).Young ) - { - Caster.SendLocalizedMessage( 1049543 ); // You decide against traveling to Felucca while you are still young. - } - else if ( Caster.Kills >= 5 && map != Map.Felucca ) - { - Caster.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - } - else if ( Caster.Criminal ) - { - Caster.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - } - else if ( SpellHelper.CheckCombat( Caster ) ) - { - Caster.SendLocalizedMessage( 1061282 ); // You cannot use the Sacred Journey ability to flee from combat. - } - else if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - } - else if ( !map.CanSpawnMobile( loc.X, loc.Y, loc.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( (checkMulti && SpellHelper.CheckMulti( loc, map )) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( m_Book != null && m_Book.CurCharges <= 0 ) - { - Caster.SendLocalizedMessage( 502412 ); // There are no charges left on that item. - } - else if ( CheckSequence() ) - { - BaseCreature.TeleportPets( Caster, loc, map, true ); + if (SpellHelper.CheckCombat(Caster)) + { + Caster.SendLocalizedMessage(1061282); // You cannot use the Sacred Journey ability to flee from combat. + return false; + } - if ( m_Book != null ) - --m_Book.CurCharges; + if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + return false; + } - Effects.SendLocationParticles( EffectItem.Create( Caster.Location, Caster.Map, EffectItem.DefaultDuration ), 0, 0, 0, 5033 ); + return SpellHelper.CheckTravel(Caster, TravelCheckType.RecallFrom); + } - Caster.PlaySound( 0x1FC ); - Caster.MoveToWorld( loc, map ); - Caster.PlaySound( 0x1FC ); - } + public void Effect(Point3D loc, Map map, bool checkMulti) + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (map == null || !Core.AOS && Caster.Map != map) + { + Caster.SendLocalizedMessage(1005569); // You can not recall to another facet. + } + else if (!SpellHelper.CheckTravel(Caster, TravelCheckType.RecallFrom)) + { + } + else if (!SpellHelper.CheckTravel(Caster, map, loc, TravelCheckType.RecallTo)) + { + } + else if (map == Map.Felucca && Caster is PlayerMobile && ((PlayerMobile)Caster).Young) + { + Caster.SendLocalizedMessage(1049543); // You decide against traveling to Felucca while you are still young. + } + else if (Caster.Kills >= 5 && map != Map.Felucca) + { + Caster.SendLocalizedMessage(1019004); // You are not allowed to travel there. + } + else if (Caster.Criminal) + { + Caster.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + } + else if (SpellHelper.CheckCombat(Caster)) + { + Caster.SendLocalizedMessage(1061282); // You cannot use the Sacred Journey ability to flee from combat. + } + else if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + } + else if (!map.CanSpawnMobile(loc.X, loc.Y, loc.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (checkMulti && SpellHelper.CheckMulti(loc, map)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (m_Book != null && m_Book.CurCharges <= 0) + { + Caster.SendLocalizedMessage(502412); // There are no charges left on that item. + } + else if (CheckSequence()) + { + BaseCreature.TeleportPets(Caster, loc, map, true); - FinishSequence(); - } + if (m_Book != null) + --m_Book.CurCharges; - private class InternalTarget : Target - { - private SacredJourneySpell m_Owner; + Effects.SendLocationParticles(EffectItem.Create(Caster.Location, Caster.Map, EffectItem.DefaultDuration), 0, + 0, 0, 5033); - public InternalTarget( SacredJourneySpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + Caster.PlaySound(0x1FC); + Caster.MoveToWorld(loc, map); + Caster.PlaySound(0x1FC); + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is RecallRune ) - { - RecallRune rune = (RecallRune)o; + FinishSequence(); + } - if ( rune.Marked ) - m_Owner.Effect( rune.Target, rune.TargetMap, true ); - else - from.SendLocalizedMessage( 501805 ); // That rune is not yet marked. - } - else if ( o is Runebook ) - { - RunebookEntry e = ((Runebook)o).Default; + private class InternalTarget : Target + { + private SacredJourneySpell m_Owner; - if ( e != null ) - m_Owner.Effect( e.Location, e.Map, true ); - else - from.SendLocalizedMessage( 502354 ); // Target is not marked. - } - else if ( o is Key && ((Key)o).KeyValue != 0 && ((Key)o).Link is BaseBoat ) - { - BaseBoat boat = ((Key)o).Link as BaseBoat; + public InternalTarget(SacredJourneySpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - if ( !boat.Deleted && boat.CheckKey( ((Key)o).KeyValue ) ) - m_Owner.Effect( boat.GetMarkedLocation(), boat.Map, false ); - else - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, from.Name, "" ) ); // I can not recall from that object. - } - else if ( o is HouseRaffleDeed && ((HouseRaffleDeed)o).ValidLocation() ) - { - HouseRaffleDeed deed = (HouseRaffleDeed)o; + protected override void OnTarget(Mobile from, object o) + { + if (o is RecallRune) + { + RecallRune rune = (RecallRune)o; - m_Owner.Effect( deed.PlotLocation, deed.PlotFacet, true ); - } - else - { - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, from.Name, "" ) ); // I can not recall from that object. - } - } + if (rune.Marked) + m_Owner.Effect(rune.Target, rune.TargetMap, true); + else + from.SendLocalizedMessage(501805); // That rune is not yet marked. + } + else if (o is Runebook) + { + RunebookEntry e = ((Runebook)o).Default; - protected override void OnNonlocalTarget( Mobile from, object o ) - { - } + if (e != null) + m_Owner.Effect(e.Location, e.Map, true); + else + from.SendLocalizedMessage(502354); // Target is not marked. + } + else if (o is Key && ((Key)o).KeyValue != 0 && ((Key)o).Link is BaseBoat) + { + BaseBoat boat = ((Key)o).Link as BaseBoat; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + if (!boat.Deleted && boat.CheckKey(((Key)o).KeyValue)) + m_Owner.Effect(boat.GetMarkedLocation(), boat.Map, false); + else + from.Send(new MessageLocalized(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, + from.Name, "")); // I can not recall from that object. + } + else if (o is HouseRaffleDeed && ((HouseRaffleDeed)o).ValidLocation()) + { + HouseRaffleDeed deed = (HouseRaffleDeed)o; + + m_Owner.Effect(deed.PlotLocation, deed.PlotFacet, true); + } + else + { + from.Send(new MessageLocalized(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, from.Name, + "")); // I can not recall from that object. + } + } + + protected override void OnNonlocalTarget(Mobile from, object o) + { + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/AirElemental.cs b/Scripts/Spells/Eighth/AirElemental.cs index 62cbef0b3..ddef638fa 100644 --- a/Scripts/Spells/Eighth/AirElemental.cs +++ b/Scripts/Spells/Eighth/AirElemental.cs @@ -3,51 +3,51 @@ using Server.Mobiles; namespace Server.Spells.Eighth { - public class AirElementalSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Air Elemental", "Kal Vas Xen Hur", - 269, - 9010, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class AirElementalSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Air Elemental", "Kal Vas Xen Hur", + 269, + 9010, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public AirElementalSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public AirElementalSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 2) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 2 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromSeconds( (2 * Caster.Skills.Magery.Fixed) / 5 ); + public override void OnCast() + { + if (CheckSequence()) + { + TimeSpan duration = TimeSpan.FromSeconds(2 * Caster.Skills.Magery.Fixed / 5); - if ( Core.AOS ) - SpellHelper.Summon( new SummonedAirElemental(), Caster, 0x217, duration, false, false ); - else - SpellHelper.Summon( new AirElemental(), Caster, 0x217, duration, false, false ); - } + if (Core.AOS) + SpellHelper.Summon(new SummonedAirElemental(), Caster, 0x217, duration, false, false); + else + SpellHelper.Summon(new AirElemental(), Caster, 0x217, duration, false, false); + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/EarthElemental.cs b/Scripts/Spells/Eighth/EarthElemental.cs index 668fe197b..629d6ab4a 100644 --- a/Scripts/Spells/Eighth/EarthElemental.cs +++ b/Scripts/Spells/Eighth/EarthElemental.cs @@ -3,51 +3,51 @@ using Server.Mobiles; namespace Server.Spells.Eighth { - public class EarthElementalSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Earth Elemental", "Kal Vas Xen Ylem", - 269, - 9020, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class EarthElementalSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Earth Elemental", "Kal Vas Xen Ylem", + 269, + 9020, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public EarthElementalSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EarthElementalSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 2) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 2 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromSeconds( (2 * Caster.Skills.Magery.Fixed) / 5 ); + public override void OnCast() + { + if (CheckSequence()) + { + TimeSpan duration = TimeSpan.FromSeconds(2 * Caster.Skills.Magery.Fixed / 5); - if ( Core.AOS ) - SpellHelper.Summon( new SummonedEarthElemental(), Caster, 0x217, duration, false, false ); - else - SpellHelper.Summon( new EarthElemental(), Caster, 0x217, duration, false, false ); - } + if (Core.AOS) + SpellHelper.Summon(new SummonedEarthElemental(), Caster, 0x217, duration, false, false); + else + SpellHelper.Summon(new EarthElemental(), Caster, 0x217, duration, false, false); + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/Earthquake.cs b/Scripts/Spells/Eighth/Earthquake.cs index 32b2a14cb..115b3e9d7 100644 --- a/Scripts/Spells/Eighth/Earthquake.cs +++ b/Scripts/Spells/Eighth/Earthquake.cs @@ -3,73 +3,73 @@ using System.Collections.Generic; namespace Server.Spells.Eighth { - public class EarthquakeSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Earthquake", "In Vas Por", - 233, - 9012, - false, - Reagent.Bloodmoss, - Reagent.Ginseng, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class EarthquakeSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Earthquake", "In Vas Por", + 233, + 9012, + false, + Reagent.Bloodmoss, + Reagent.Ginseng, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public EarthquakeSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EarthquakeSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool DelayedDamage => !Core.AOS; + public override bool DelayedDamage => !Core.AOS; - public override void OnCast() - { - if ( SpellHelper.CheckTown( Caster, Caster ) && CheckSequence() ) - { - List targets = new List(); + public override void OnCast() + { + if (SpellHelper.CheckTown(Caster, Caster) && CheckSequence()) + { + List targets = new List(); - Map map = Caster.Map; + Map map = Caster.Map; - if ( map != null ) - foreach ( Mobile m in Caster.GetMobilesInRange( 1 + (int)(Caster.Skills[SkillName.Magery].Value / 15.0) ) ) - if ( Caster != m && SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) && (!Core.AOS || Caster.InLOS( m )) ) - targets.Add( m ); + if (map != null) + foreach (Mobile m in Caster.GetMobilesInRange(1 + (int)(Caster.Skills[SkillName.Magery].Value / 15.0))) + if (Caster != m && SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false) && + (!Core.AOS || Caster.InLOS(m))) + targets.Add(m); - Caster.PlaySound( 0x220 ); + Caster.PlaySound(0x220); - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - int damage; + int damage; - if ( Core.AOS ) - { - damage = m.Hits / 2; + if (Core.AOS) + { + damage = m.Hits / 2; - if ( !m.Player ) - damage = Math.Max( Math.Min( damage, 100 ), 15 ); - damage += Utility.RandomMinMax( 0, 15 ); + if (!m.Player) + damage = Math.Max(Math.Min(damage, 100), 15); + damage += Utility.RandomMinMax(0, 15); + } + else + { + damage = m.Hits * 6 / 10; - } - else - { - damage = (m.Hits * 6) / 10; + if (!m.Player && damage < 10) + damage = 10; + else if (damage > 75) + damage = 75; + } - if ( !m.Player && damage < 10 ) - damage = 10; - else if ( damage > 75 ) - damage = 75; - } + Caster.DoHarmful(m); + SpellHelper.Damage(TimeSpan.Zero, m, Caster, damage, 100, 0, 0, 0, 0); + } + } - Caster.DoHarmful( m ); - SpellHelper.Damage( TimeSpan.Zero, m, Caster, damage, 100, 0, 0, 0, 0 ); - } - } - - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/EnergyVortex.cs b/Scripts/Spells/Eighth/EnergyVortex.cs index a65cb7679..77075b338 100644 --- a/Scripts/Spells/Eighth/EnergyVortex.cs +++ b/Scripts/Spells/Eighth/EnergyVortex.cs @@ -4,96 +4,96 @@ using Server.Targeting; namespace Server.Spells.Eighth { - public class EnergyVortexSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Energy Vortex", "Vas Corp Por", - 260, - 9032, - false, - Reagent.Bloodmoss, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.Nightshade - ); + public class EnergyVortexSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Energy Vortex", "Vas Corp Por", + 260, + 9032, + false, + Reagent.Bloodmoss, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public EnergyVortexSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EnergyVortexSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + (Core.SE ? 2 : 1)) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + (Core.SE ? 2 : 1) > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - Map map = Caster.Map; + public void Target(IPoint3D p) + { + Map map = Caster.Map; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - if ( map == null || !map.CanSpawnMobile( p.X, p.Y, p.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - TimeSpan duration; + if (map == null || !map.CanSpawnMobile(p.X, p.Y, p.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + TimeSpan duration; - if ( Core.AOS ) - duration = TimeSpan.FromSeconds( 90.0 ); - else - duration = TimeSpan.FromSeconds( Utility.Random( 80, 40 ) ); + if (Core.AOS) + duration = TimeSpan.FromSeconds(90.0); + else + duration = TimeSpan.FromSeconds(Utility.Random(80, 40)); - BaseCreature.Summon( new EnergyVortex(), false, Caster, new Point3D( p ), 0x212, duration ); - } + BaseCreature.Summon(new EnergyVortex(), false, Caster, new Point3D(p), 0x212, duration); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private EnergyVortexSpell m_Owner; + private class InternalTarget : Target + { + private EnergyVortexSpell m_Owner; - public InternalTarget( EnergyVortexSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(EnergyVortexSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } - protected override void OnTargetOutOfLOS( Mobile from, object o ) - { - from.SendLocalizedMessage( 501943 ); // Target cannot be seen. Try again. - from.Target = new InternalTarget( m_Owner ); - from.Target.BeginTimeout( from, TimeoutTime - DateTime.UtcNow ); - m_Owner = null; - } + protected override void OnTargetOutOfLOS(Mobile from, object o) + { + from.SendLocalizedMessage(501943); // Target cannot be seen. Try again. + from.Target = new InternalTarget(m_Owner); + from.Target.BeginTimeout(from, TimeoutTime - DateTime.UtcNow); + m_Owner = null; + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner?.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner?.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/FireElemental.cs b/Scripts/Spells/Eighth/FireElemental.cs index 3bd2ac502..4aa50825b 100644 --- a/Scripts/Spells/Eighth/FireElemental.cs +++ b/Scripts/Spells/Eighth/FireElemental.cs @@ -3,52 +3,52 @@ using Server.Mobiles; namespace Server.Spells.Eighth { - public class FireElementalSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Fire Elemental", "Kal Vas Xen Flam", - 269, - 9050, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); + public class FireElementalSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Fire Elemental", "Kal Vas Xen Flam", + 269, + 9050, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public FireElementalSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public FireElementalSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 4) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 4 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromSeconds( (2 * Caster.Skills.Magery.Fixed) / 5 ); + public override void OnCast() + { + if (CheckSequence()) + { + TimeSpan duration = TimeSpan.FromSeconds(2 * Caster.Skills.Magery.Fixed / 5); - if ( Core.AOS ) - SpellHelper.Summon( new SummonedFireElemental(), Caster, 0x217, duration, false, false ); - else - SpellHelper.Summon( new FireElemental(), Caster, 0x217, duration, false, false ); - } + if (Core.AOS) + SpellHelper.Summon(new SummonedFireElemental(), Caster, 0x217, duration, false, false); + else + SpellHelper.Summon(new FireElemental(), Caster, 0x217, duration, false, false); + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/Resurrection.cs b/Scripts/Spells/Eighth/Resurrection.cs index 4b9b845d6..eb79f5642 100644 --- a/Scripts/Spells/Eighth/Resurrection.cs +++ b/Scripts/Spells/Eighth/Resurrection.cs @@ -1,111 +1,110 @@ -using Server.Targeting; +using Server.Engines.ConPVP; using Server.Gumps; +using Server.Targeting; namespace Server.Spells.Eighth { - public class ResurrectionSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Resurrection", "An Corp", - 245, - 9062, - Reagent.Bloodmoss, - Reagent.Garlic, - Reagent.Ginseng - ); + public class ResurrectionSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Resurrection", "An Corp", + 245, + 9062, + Reagent.Bloodmoss, + Reagent.Garlic, + Reagent.Ginseng + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public ResurrectionSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ResurrectionSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( m == Caster ) - { - Caster.SendLocalizedMessage( 501039 ); // Thou can not resurrect thyself. - } - else if ( !Caster.Alive ) - { - Caster.SendLocalizedMessage( 501040 ); // The resurrecter must be alive. - } - else if ( m.Alive ) - { - Caster.SendLocalizedMessage( 501041 ); // Target is not dead. - } - else if ( !Caster.InRange( m, 1 ) ) - { - Caster.SendLocalizedMessage( 501042 ); // Target is not close enough. - } - else if ( !m.Player ) - { - Caster.SendLocalizedMessage( 501043 ); // Target is not a being. - } - else if ( m.Map == null || !m.Map.CanFit( m.Location, 16, false, false ) ) - { - Caster.SendLocalizedMessage( 501042 ); // Target can not be resurrected at that location. - m.SendLocalizedMessage( 502391 ); // Thou can not be resurrected there! - } - else if ( m.Region != null && m.Region.IsPartOf( "Khaldun" ) ) - { - Caster.SendLocalizedMessage( 1010395 ); // The veil of death in this area is too strong and resists thy efforts to restore life. - } - else if ( CheckBSequence( m, true ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (m == Caster) + { + Caster.SendLocalizedMessage(501039); // Thou can not resurrect thyself. + } + else if (!Caster.Alive) + { + Caster.SendLocalizedMessage(501040); // The resurrecter must be alive. + } + else if (m.Alive) + { + Caster.SendLocalizedMessage(501041); // Target is not dead. + } + else if (!Caster.InRange(m, 1)) + { + Caster.SendLocalizedMessage(501042); // Target is not close enough. + } + else if (!m.Player) + { + Caster.SendLocalizedMessage(501043); // Target is not a being. + } + else if (m.Map == null || !m.Map.CanFit(m.Location, 16, false, false)) + { + Caster.SendLocalizedMessage(501042); // Target can not be resurrected at that location. + m.SendLocalizedMessage(502391); // Thou can not be resurrected there! + } + else if (m.Region != null && m.Region.IsPartOf("Khaldun")) + { + Caster.SendLocalizedMessage( + 1010395); // The veil of death in this area is too strong and resists thy efforts to restore life. + } + else if (CheckBSequence(m, true)) + { + SpellHelper.Turn(Caster, m); - m.PlaySound( 0x214 ); - m.FixedEffect( 0x376A, 10, 16 ); + m.PlaySound(0x214); + m.FixedEffect(0x376A, 10, 16); - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, Caster ) ); - } + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, Caster)); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private ResurrectionSpell m_Owner; + private class InternalTarget : Target + { + private ResurrectionSpell m_Owner; - public InternalTarget( ResurrectionSpell owner ) : base( 1, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(ResurrectionSpell owner) : base(1, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/SummonDaemon.cs b/Scripts/Spells/Eighth/SummonDaemon.cs index 4053a1b22..0751efa04 100644 --- a/Scripts/Spells/Eighth/SummonDaemon.cs +++ b/Scripts/Spells/Eighth/SummonDaemon.cs @@ -3,56 +3,58 @@ using Server.Mobiles; namespace Server.Spells.Eighth { - public class SummonDaemonSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Summon Daemon", "Kal Vas Xen Corp", - 269, - 9050, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); + public class SummonDaemonSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Summon Daemon", "Kal Vas Xen Corp", + 269, + 9050, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public SummonDaemonSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public SummonDaemonSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + (Core.SE ? 4 : 5)) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + (Core.SE ? 4 : 5) > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromSeconds( (2 * Caster.Skills.Magery.Fixed) / 5 ); + public override void OnCast() + { + if (CheckSequence()) + { + TimeSpan duration = TimeSpan.FromSeconds(2 * Caster.Skills.Magery.Fixed / 5); - if ( Core.AOS ) /* Why two diff daemons? TODO: solve this */ - { - BaseCreature m_Daemon = new SummonedDaemon(); - SpellHelper.Summon( m_Daemon, Caster, 0x216, duration, false, false ); - m_Daemon.FixedParticles(0x3728, 8, 20, 5042, EffectLayer.Head ); - } - else - SpellHelper.Summon( new Daemon(), Caster, 0x216, duration, false, false ); - } + if (Core.AOS) /* Why two diff daemons? TODO: solve this */ + { + BaseCreature m_Daemon = new SummonedDaemon(); + SpellHelper.Summon(m_Daemon, Caster, 0x216, duration, false, false); + m_Daemon.FixedParticles(0x3728, 8, 20, 5042, EffectLayer.Head); + } + else + { + SpellHelper.Summon(new Daemon(), Caster, 0x216, duration, false, false); + } + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Eighth/WaterElemental.cs b/Scripts/Spells/Eighth/WaterElemental.cs index e87aac1ba..80250ba26 100644 --- a/Scripts/Spells/Eighth/WaterElemental.cs +++ b/Scripts/Spells/Eighth/WaterElemental.cs @@ -3,51 +3,51 @@ using Server.Mobiles; namespace Server.Spells.Eighth { - public class WaterElementalSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Water Elemental", "Kal Vas Xen An Flam", - 269, - 9070, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class WaterElementalSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Water Elemental", "Kal Vas Xen An Flam", + 269, + 9070, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Eighth; + public WaterElementalSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public WaterElementalSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Eighth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 3) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 3 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromSeconds( (2 * Caster.Skills.Magery.Fixed) / 5 ); + public override void OnCast() + { + if (CheckSequence()) + { + TimeSpan duration = TimeSpan.FromSeconds(2 * Caster.Skills.Magery.Fixed / 5); - if ( Core.AOS ) - SpellHelper.Summon( new SummonedWaterElemental(), Caster, 0x217, duration, false, false ); - else - SpellHelper.Summon( new WaterElemental(), Caster, 0x217, duration, false, false ); - } + if (Core.AOS) + SpellHelper.Summon(new SummonedWaterElemental(), Caster, 0x217, duration, false, false); + else + SpellHelper.Summon(new WaterElemental(), Caster, 0x217, duration, false, false); + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/BladeSpirits.cs b/Scripts/Spells/Fifth/BladeSpirits.cs index d37420032..6977c4196 100644 --- a/Scripts/Spells/Fifth/BladeSpirits.cs +++ b/Scripts/Spells/Fifth/BladeSpirits.cs @@ -4,103 +4,103 @@ using Server.Targeting; namespace Server.Spells.Fifth { - public class BladeSpiritsSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Blade Spirits", "In Jux Hur Ylem", - 266, - 9040, - false, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.Nightshade - ); + public class BladeSpiritsSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Blade Spirits", "In Jux Hur Ylem", + 266, + 9040, + false, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Fifth; + public BladeSpiritsSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public BladeSpiritsSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fifth; - public override TimeSpan GetCastDelay() - { - if ( Core.AOS ) - return TimeSpan.FromTicks( base.GetCastDelay().Ticks * ((Core.SE) ? 3 : 5) ); + public override TimeSpan GetCastDelay() + { + if (Core.AOS) + return TimeSpan.FromTicks(base.GetCastDelay().Ticks * (Core.SE ? 3 : 5)); - return base.GetCastDelay() + TimeSpan.FromSeconds( 6.0 ); - } + return base.GetCastDelay() + TimeSpan.FromSeconds(6.0); + } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + (Core.SE ? 2 : 1)) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + (Core.SE ? 2 : 1) > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - Map map = Caster.Map; + public void Target(IPoint3D p) + { + Map map = Caster.Map; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - if ( map == null || !map.CanSpawnMobile( p.X, p.Y, p.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - TimeSpan duration; + if (map == null || !map.CanSpawnMobile(p.X, p.Y, p.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + TimeSpan duration; - if ( Core.AOS ) - duration = TimeSpan.FromSeconds( 120 ); - else - duration = TimeSpan.FromSeconds( Utility.Random( 80, 40 ) ); + if (Core.AOS) + duration = TimeSpan.FromSeconds(120); + else + duration = TimeSpan.FromSeconds(Utility.Random(80, 40)); - BaseCreature.Summon( new BladeSpirits(), false, Caster, new Point3D( p ), 0x212, duration ); - } + BaseCreature.Summon(new BladeSpirits(), false, Caster, new Point3D(p), 0x212, duration); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private BladeSpiritsSpell m_Owner; + private class InternalTarget : Target + { + private BladeSpiritsSpell m_Owner; - public InternalTarget( BladeSpiritsSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(BladeSpiritsSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } - protected override void OnTargetOutOfLOS( Mobile from, object o ) - { - from.SendLocalizedMessage( 501943 ); // Target cannot be seen. Try again. - from.Target = new InternalTarget( m_Owner ); - from.Target.BeginTimeout( from, TimeoutTime - DateTime.UtcNow ); - m_Owner = null; - } + protected override void OnTargetOutOfLOS(Mobile from, object o) + { + from.SendLocalizedMessage(501943); // Target cannot be seen. Try again. + from.Target = new InternalTarget(m_Owner); + from.Target.BeginTimeout(from, TimeoutTime - DateTime.UtcNow); + m_Owner = null; + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner?.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner?.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/DispelField.cs b/Scripts/Spells/Fifth/DispelField.cs index 6ee7cbd84..679231614 100644 --- a/Scripts/Spells/Fifth/DispelField.cs +++ b/Scripts/Spells/Fifth/DispelField.cs @@ -1,87 +1,84 @@ using System; -using Server.Targeting; using Server.Items; using Server.Misc; +using Server.Targeting; namespace Server.Spells.Fifth { - public class DispelFieldSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Dispel Field", "An Grav", - 206, - 9002, - Reagent.BlackPearl, - Reagent.SpidersSilk, - Reagent.SulfurousAsh, - Reagent.Garlic - ); + public class DispelFieldSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Dispel Field", "An Grav", + 206, + 9002, + Reagent.BlackPearl, + Reagent.SpidersSilk, + Reagent.SulfurousAsh, + Reagent.Garlic + ); - public override SpellCircle Circle => SpellCircle.Fifth; + public DispelFieldSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public DispelFieldSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fifth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Item item ) - { - Type t = item.GetType(); + public void Target(Item item) + { + Type t = item.GetType(); - if ( !Caster.CanSee( item ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( !t.IsDefined( typeof( DispellableFieldAttribute ), false ) ) - { - Caster.SendLocalizedMessage( 1005049 ); // That cannot be dispelled. - } - else if ( item is Moongate && !((Moongate)item).Dispellable ) - { - Caster.SendLocalizedMessage( 1005047 ); // That magic is too chaotic - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, item ); + if (!Caster.CanSee(item)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (!t.IsDefined(typeof(DispellableFieldAttribute), false)) + { + Caster.SendLocalizedMessage(1005049); // That cannot be dispelled. + } + else if (item is Moongate && !((Moongate)item).Dispellable) + { + Caster.SendLocalizedMessage(1005047); // That magic is too chaotic + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, item); - Effects.SendLocationParticles( EffectItem.Create( item.Location, item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 20, 5042 ); - Effects.PlaySound( item.GetWorldLocation(), item.Map, 0x201 ); + Effects.SendLocationParticles(EffectItem.Create(item.Location, item.Map, EffectItem.DefaultDuration), 0x376A, + 9, 20, 5042); + Effects.PlaySound(item.GetWorldLocation(), item.Map, 0x201); - item.Delete(); - } + item.Delete(); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private DispelFieldSpell m_Owner; + private class InternalTarget : Target + { + private DispelFieldSpell m_Owner; - public InternalTarget( DispelFieldSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(DispelFieldSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Item ) - { - m_Owner.Target( (Item)o ); - } - else - { - m_Owner.Caster.SendLocalizedMessage( 1005049 ); // That cannot be dispelled. - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Item) + m_Owner.Target((Item)o); + else + m_Owner.Caster.SendLocalizedMessage(1005049); // That cannot be dispelled. + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/Incognito.cs b/Scripts/Spells/Fifth/Incognito.cs index d95d498d1..90237e643 100644 --- a/Scripts/Spells/Fifth/Incognito.cs +++ b/Scripts/Spells/Fifth/Incognito.cs @@ -1,188 +1,191 @@ using System; using System.Collections; -using Server.Mobiles; +using Server.Factions; using Server.Items; +using Server.Mobiles; using Server.Spells.Seventh; namespace Server.Spells.Fifth { - public class IncognitoSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Incognito", "Kal In Ex", - 206, - 9002, - Reagent.Bloodmoss, - Reagent.Garlic, - Reagent.Nightshade - ); + public class IncognitoSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Incognito", "Kal In Ex", + 206, + 9002, + Reagent.Bloodmoss, + Reagent.Garlic, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Fifth; + private static Hashtable m_Timers = new Hashtable(); - public IncognitoSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + private static int[] m_HairIDs = + { + 0x2044, 0x2045, 0x2046, + 0x203C, 0x203B, 0x203D, + 0x2047, 0x2048, 0x2049, + 0x204A, 0x0000 + }; - public override bool CheckCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1010445 ); // You cannot incognito if you have a sigil - return false; - } + private static int[] m_BeardIDs = + { + 0x203E, 0x203F, 0x2040, + 0x2041, 0x204B, 0x204C, + 0x204D, 0x0000 + }; - if ( !Caster.CanBeginAction( typeof( IncognitoSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - return false; - } - if ( Caster.BodyMod == 183 || Caster.BodyMod == 184 ) - { - Caster.SendLocalizedMessage( 1042402 ); // You cannot use incognito while wearing body paint - return false; - } + public IncognitoSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - return true; - } + public override SpellCircle Circle => SpellCircle.Fifth; - public override void OnCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1010445 ); // You cannot incognito if you have a sigil - } - else if ( !Caster.CanBeginAction( typeof( IncognitoSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - else if ( Caster.BodyMod == 183 || Caster.BodyMod == 184 ) - { - Caster.SendLocalizedMessage( 1042402 ); // You cannot use incognito while wearing body paint - } - else if ( DisguiseTimers.IsDisguised( Caster ) ) - { - Caster.SendLocalizedMessage( 1061631 ); // You can't do that while disguised. - } - else if ( !Caster.CanBeginAction( typeof( PolymorphSpell ) ) || Caster.IsBodyMod ) - { - DoFizzle(); - } - else if ( CheckSequence() ) - { - if ( Caster.BeginAction( typeof( IncognitoSpell ) ) ) - { - DisguiseTimers.StopTimer( Caster ); + public override bool CheckCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1010445); // You cannot incognito if you have a sigil + return false; + } - Caster.HueMod = Caster.Race.RandomSkinHue(); - Caster.NameMod = Caster.Female ? NameList.RandomName( "female" ) : NameList.RandomName( "male" ); + if (!Caster.CanBeginAction(typeof(IncognitoSpell))) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + return false; + } - PlayerMobile pm = Caster as PlayerMobile; + if (Caster.BodyMod == 183 || Caster.BodyMod == 184) + { + Caster.SendLocalizedMessage(1042402); // You cannot use incognito while wearing body paint + return false; + } - if ( pm?.Race != null ) - { - pm.SetHairMods( pm.Race.RandomHair( pm.Female ), pm.Race.RandomFacialHair( pm.Female ) ); - pm.HairHue = pm.Race.RandomHairHue(); - pm.FacialHairHue = pm.Race.RandomHairHue(); - } + return true; + } - Caster.FixedParticles( 0x373A, 10, 15, 5036, EffectLayer.Head ); - Caster.PlaySound( 0x3BD ); + public override void OnCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1010445); // You cannot incognito if you have a sigil + } + else if (!Caster.CanBeginAction(typeof(IncognitoSpell))) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + else if (Caster.BodyMod == 183 || Caster.BodyMod == 184) + { + Caster.SendLocalizedMessage(1042402); // You cannot use incognito while wearing body paint + } + else if (DisguiseTimers.IsDisguised(Caster)) + { + Caster.SendLocalizedMessage(1061631); // You can't do that while disguised. + } + else if (!Caster.CanBeginAction(typeof(PolymorphSpell)) || Caster.IsBodyMod) + { + DoFizzle(); + } + else if (CheckSequence()) + { + if (Caster.BeginAction(typeof(IncognitoSpell))) + { + DisguiseTimers.StopTimer(Caster); - BaseArmor.ValidateMobile( Caster ); - BaseClothing.ValidateMobile( Caster ); + Caster.HueMod = Caster.Race.RandomSkinHue(); + Caster.NameMod = Caster.Female ? NameList.RandomName("female") : NameList.RandomName("male"); - StopTimer( Caster ); + PlayerMobile pm = Caster as PlayerMobile; + + if (pm?.Race != null) + { + pm.SetHairMods(pm.Race.RandomHair(pm.Female), pm.Race.RandomFacialHair(pm.Female)); + pm.HairHue = pm.Race.RandomHairHue(); + pm.FacialHairHue = pm.Race.RandomHairHue(); + } + + Caster.FixedParticles(0x373A, 10, 15, 5036, EffectLayer.Head); + Caster.PlaySound(0x3BD); + + BaseArmor.ValidateMobile(Caster); + BaseClothing.ValidateMobile(Caster); + + StopTimer(Caster); - int timeVal = ((6 * Caster.Skills.Magery.Fixed) / 50) + 1; + int timeVal = 6 * Caster.Skills.Magery.Fixed / 50 + 1; - if ( timeVal > 144 ) - timeVal = 144; + if (timeVal > 144) + timeVal = 144; - TimeSpan length = TimeSpan.FromSeconds( timeVal ); + TimeSpan length = TimeSpan.FromSeconds(timeVal); - Timer t = new InternalTimer( Caster, length ); + Timer t = new InternalTimer(Caster, length); - m_Timers[Caster] = t; + m_Timers[Caster] = t; - t.Start(); + t.Start(); - BuffInfo.AddBuff( Caster, new BuffInfo( BuffIcon.Incognito, 1075819, length, Caster ) ); + BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.Incognito, 1075819, length, Caster)); + } + else + { + Caster.SendLocalizedMessage(1079022); // You're already incognitoed! + } + } - } - else - { - Caster.SendLocalizedMessage( 1079022 ); // You're already incognitoed! - } - } + FinishSequence(); + } - FinishSequence(); - } + public static bool StopTimer(Mobile m) + { + Timer t = (Timer)m_Timers[m]; - private static Hashtable m_Timers = new Hashtable(); + if (t != null) + { + t.Stop(); + m_Timers.Remove(m); + BuffInfo.RemoveBuff(m, BuffIcon.Incognito); + } - public static bool StopTimer( Mobile m ) - { - Timer t = (Timer)m_Timers[m]; + return t != null; + } - if ( t != null ) - { - t.Stop(); - m_Timers.Remove( m ); - BuffInfo.RemoveBuff( m, BuffIcon.Incognito ); - } + private class InternalTimer : Timer + { + private Mobile m_Owner; - return ( t != null ); - } + public InternalTimer(Mobile owner, TimeSpan length) : base(length) + { + m_Owner = owner; - private static int[] m_HairIDs = { - 0x2044, 0x2045, 0x2046, - 0x203C, 0x203B, 0x203D, - 0x2047, 0x2048, 0x2049, - 0x204A, 0x0000 - }; + /* + int val = ((6 * owner.Skills.Magery.Fixed) / 50) + 1; - private static int[] m_BeardIDs = { - 0x203E, 0x203F, 0x2040, - 0x2041, 0x204B, 0x204C, - 0x204D, 0x0000 - }; + if ( val > 144 ) + val = 144; - private class InternalTimer : Timer - { - private Mobile m_Owner; + Delay = TimeSpan.FromSeconds( val ); + * */ + Priority = TimerPriority.OneSecond; + } - public InternalTimer( Mobile owner, TimeSpan length ) : base( length ) - { - m_Owner = owner; + protected override void OnTick() + { + if (!m_Owner.CanBeginAction(typeof(IncognitoSpell))) + { + (m_Owner as PlayerMobile)?.SetHairMods(-1, -1); - /* - int val = ((6 * owner.Skills.Magery.Fixed) / 50) + 1; + m_Owner.BodyMod = 0; + m_Owner.HueMod = -1; + m_Owner.NameMod = null; + m_Owner.EndAction(typeof(IncognitoSpell)); - if ( val > 144 ) - val = 144; - - Delay = TimeSpan.FromSeconds( val ); - * */ - Priority = TimerPriority.OneSecond; - } - - protected override void OnTick() - { - if ( !m_Owner.CanBeginAction( typeof( IncognitoSpell ) ) ) - { - (m_Owner as PlayerMobile)?.SetHairMods( -1, -1 ); - - m_Owner.BodyMod = 0; - m_Owner.HueMod = -1; - m_Owner.NameMod = null; - m_Owner.EndAction( typeof( IncognitoSpell ) ); - - BaseArmor.ValidateMobile( m_Owner ); - BaseClothing.ValidateMobile( m_Owner ); - } - } - } - } -} + BaseArmor.ValidateMobile(m_Owner); + BaseClothing.ValidateMobile(m_Owner); + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/MagicReflect.cs b/Scripts/Spells/Fifth/MagicReflect.cs index d29fbea63..c2b794b5f 100644 --- a/Scripts/Spells/Fifth/MagicReflect.cs +++ b/Scripts/Spells/Fifth/MagicReflect.cs @@ -1,153 +1,150 @@ -using System; using System.Collections; namespace Server.Spells.Fifth { - public class MagicReflectSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Magic Reflection", "In Jux Sanct", - 242, - 9012, - Reagent.Garlic, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class MagicReflectSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Magic Reflection", "In Jux Sanct", + 242, + 9012, + Reagent.Garlic, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Fifth; + private static Hashtable m_Table = new Hashtable(); - public MagicReflectSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public MagicReflectSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override bool CheckCast() - { - if ( Core.AOS ) - return true; + public override SpellCircle Circle => SpellCircle.Fifth; - if ( Caster.MagicDamageAbsorb > 0 ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - return false; - } + public override bool CheckCast() + { + if (Core.AOS) + return true; - if ( !Caster.CanBeginAction( typeof( DefensiveSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - return false; - } + if (Caster.MagicDamageAbsorb > 0) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + return false; + } - return true; - } + if (!Caster.CanBeginAction(typeof(DefensiveSpell))) + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + return false; + } - private static Hashtable m_Table = new Hashtable(); + return true; + } - public override void OnCast() - { - if ( Core.AOS ) - { - /* The magic reflection spell decreases the caster's physical resistance, while increasing the caster's elemental resistances. - * Physical decrease = 25 - (Inscription/20). - * Elemental resistance = +10 (-20 physical, +10 elemental at GM Inscription) - * The magic reflection spell has an indefinite duration, becoming active when cast, and deactivated when re-cast. - * Reactive Armor, Protection, and Magic Reflection will stay on�even after logging out, even after dying�until you �turn them off� by casting them again. - */ + public override void OnCast() + { + if (Core.AOS) + { + /* The magic reflection spell decreases the caster's physical resistance, while increasing the caster's elemental resistances. + * Physical decrease = 25 - (Inscription/20). + * Elemental resistance = +10 (-20 physical, +10 elemental at GM Inscription) + * The magic reflection spell has an indefinite duration, becoming active when cast, and deactivated when re-cast. + * Reactive Armor, Protection, and Magic Reflection will stay on�even after logging out, even after dying�until you �turn them off� by casting them again. + */ - if ( CheckSequence() ) - { - Mobile targ = Caster; + if (CheckSequence()) + { + Mobile targ = Caster; - ResistanceMod[] mods = (ResistanceMod[])m_Table[targ]; + ResistanceMod[] mods = (ResistanceMod[])m_Table[targ]; - if ( mods == null ) - { - targ.PlaySound( 0x1E9 ); - targ.FixedParticles( 0x375A, 10, 15, 5037, EffectLayer.Waist ); + if (mods == null) + { + targ.PlaySound(0x1E9); + targ.FixedParticles(0x375A, 10, 15, 5037, EffectLayer.Waist); - int physiMod = -25 + (int)(targ.Skills[SkillName.Inscribe].Value / 20); - int otherMod = 10; + int physiMod = -25 + (int)(targ.Skills[SkillName.Inscribe].Value / 20); + int otherMod = 10; - mods = new ResistanceMod[5] - { - new ResistanceMod( ResistanceType.Physical, physiMod ), - new ResistanceMod( ResistanceType.Fire, otherMod ), - new ResistanceMod( ResistanceType.Cold, otherMod ), - new ResistanceMod( ResistanceType.Poison, otherMod ), - new ResistanceMod( ResistanceType.Energy, otherMod ) - }; + mods = new ResistanceMod[5] + { + new ResistanceMod(ResistanceType.Physical, physiMod), + new ResistanceMod(ResistanceType.Fire, otherMod), + new ResistanceMod(ResistanceType.Cold, otherMod), + new ResistanceMod(ResistanceType.Poison, otherMod), + new ResistanceMod(ResistanceType.Energy, otherMod) + }; - m_Table[targ] = mods; + m_Table[targ] = mods; - for ( int i = 0; i < mods.Length; ++i ) - targ.AddResistanceMod( mods[i] ); + for (int i = 0; i < mods.Length; ++i) + targ.AddResistanceMod(mods[i]); - string buffFormat = string.Format( "{0}\t+{1}\t+{1}\t+{1}\t+{1}", physiMod, otherMod ); + string buffFormat = string.Format("{0}\t+{1}\t+{1}\t+{1}\t+{1}", physiMod, otherMod); - BuffInfo.AddBuff( targ, new BuffInfo( BuffIcon.MagicReflection, 1075817, buffFormat, true ) ); - } - else - { - targ.PlaySound( 0x1ED ); - targ.FixedParticles( 0x375A, 10, 15, 5037, EffectLayer.Waist ); + BuffInfo.AddBuff(targ, new BuffInfo(BuffIcon.MagicReflection, 1075817, buffFormat, true)); + } + else + { + targ.PlaySound(0x1ED); + targ.FixedParticles(0x375A, 10, 15, 5037, EffectLayer.Waist); - m_Table.Remove( targ ); + m_Table.Remove(targ); - for ( int i = 0; i < mods.Length; ++i ) - targ.RemoveResistanceMod( mods[i] ); + for (int i = 0; i < mods.Length; ++i) + targ.RemoveResistanceMod(mods[i]); - BuffInfo.RemoveBuff( targ, BuffIcon.MagicReflection ); - } - } + BuffInfo.RemoveBuff(targ, BuffIcon.MagicReflection); + } + } - FinishSequence(); - } - else - { - if ( Caster.MagicDamageAbsorb > 0 ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - else if ( !Caster.CanBeginAction( typeof( DefensiveSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - } - else if ( CheckSequence() ) - { - if ( Caster.BeginAction( typeof( DefensiveSpell ) ) ) - { - int value = (int)(Caster.Skills[SkillName.Magery].Value + Caster.Skills[SkillName.Inscribe].Value); - value = (int)(8 + (value/200)*7.0);//absorb from 8 to 15 "circles" + FinishSequence(); + } + else + { + if (Caster.MagicDamageAbsorb > 0) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + else if (!Caster.CanBeginAction(typeof(DefensiveSpell))) + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + } + else if (CheckSequence()) + { + if (Caster.BeginAction(typeof(DefensiveSpell))) + { + int value = (int)(Caster.Skills[SkillName.Magery].Value + Caster.Skills[SkillName.Inscribe].Value); + value = (int)(8 + value / 200 * 7.0); //absorb from 8 to 15 "circles" - Caster.MagicDamageAbsorb = value; + Caster.MagicDamageAbsorb = value; - Caster.FixedParticles( 0x375A, 10, 15, 5037, EffectLayer.Waist ); - Caster.PlaySound( 0x1E9 ); - } - else - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - } - } + Caster.FixedParticles(0x375A, 10, 15, 5037, EffectLayer.Waist); + Caster.PlaySound(0x1E9); + } + else + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + } + } - FinishSequence(); - } - } + FinishSequence(); + } + } - public static void EndReflect( Mobile m ) - { - if ( m_Table.Contains( m ) ) - { - ResistanceMod[] mods = (ResistanceMod[]) m_Table[ m ]; + public static void EndReflect(Mobile m) + { + if (m_Table.Contains(m)) + { + ResistanceMod[] mods = (ResistanceMod[])m_Table[m]; - if ( mods != null ) - { - for ( int i = 0; i < mods.Length; ++i ) - m.RemoveResistanceMod( mods[ i ] ); - } + if (mods != null) + for (int i = 0; i < mods.Length; ++i) + m.RemoveResistanceMod(mods[i]); - m_Table.Remove( m ); - BuffInfo.RemoveBuff( m, BuffIcon.MagicReflection ); - } - } - } -} + m_Table.Remove(m); + BuffInfo.RemoveBuff(m, BuffIcon.MagicReflection); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/MindBlast.cs b/Scripts/Spells/Fifth/MindBlast.cs index 3c57846a1..55ebb2689 100644 --- a/Scripts/Spells/Fifth/MindBlast.cs +++ b/Scripts/Spells/Fifth/MindBlast.cs @@ -3,152 +3,152 @@ using Server.Targeting; namespace Server.Spells.Fifth { - public class MindBlastSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mind Blast", "Por Corp Wis", - 218, - Core.AOS ? 9002 : 9032, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.Nightshade, - Reagent.SulfurousAsh - ); + public class MindBlastSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mind Blast", "Por Corp Wis", + 218, + Core.AOS ? 9002 : 9032, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.Nightshade, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Fifth; + public MindBlastSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + if (Core.AOS) + m_Info.LeftHandEffect = m_Info.RightHandEffect = 9002; + } - public MindBlastSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - if ( Core.AOS ) - m_Info.LeftHandEffect = m_Info.RightHandEffect = 9002; - } + public override SpellCircle Circle => SpellCircle.Fifth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => !Core.AOS; - private void AosDelay_Callback( object state ) - { - object[] states = (object[])state; - Mobile caster = (Mobile)states[0]; - Mobile target = (Mobile)states[1]; - Mobile defender = (Mobile)states[2]; - int damage = (int)states[3]; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - if ( caster.HarmfulCheck( defender ) ) - { - SpellHelper.Damage( this, target, Utility.RandomMinMax( damage, damage + 4 ), 0, 0, 100, 0, 0 ); + private void AosDelay_Callback(object state) + { + object[] states = (object[])state; + Mobile caster = (Mobile)states[0]; + Mobile target = (Mobile)states[1]; + Mobile defender = (Mobile)states[2]; + int damage = (int)states[3]; - target.FixedParticles( 0x374A, 10, 15, 5038, 1181, 2, EffectLayer.Head ); - target.PlaySound( 0x213 ); - } - } + if (caster.HarmfulCheck(defender)) + { + SpellHelper.Damage(this, target, Utility.RandomMinMax(damage, damage + 4), 0, 0, 100, 0, 0); - public override bool DelayedDamage => !Core.AOS; + target.FixedParticles(0x374A, 10, 15, 5038, 1181, 2, EffectLayer.Head); + target.PlaySound(0x213); + } + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( Core.AOS ) - { - if ( Caster.CanBeHarmful( m ) && CheckSequence() ) - { - Mobile from = Caster, target = m; + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (Core.AOS) + { + if (Caster.CanBeHarmful(m) && CheckSequence()) + { + Mobile from = Caster, target = m; - SpellHelper.Turn( from, target ); + SpellHelper.Turn(from, target); - SpellHelper.CheckReflect( (int)Circle, ref from, ref target ); + SpellHelper.CheckReflect((int)Circle, ref from, ref target); - int damage = (int)((Caster.Skills[SkillName.Magery].Value + Caster.Int) / 5); + int damage = (int)((Caster.Skills[SkillName.Magery].Value + Caster.Int) / 5); - if ( damage > 60 ) - damage = 60; + if (damage > 60) + damage = 60; - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), - new TimerStateCallback( AosDelay_Callback ), - new object[]{ Caster, target, m, damage } ); - } - } - else if ( CheckHSequence( m ) ) - { - Mobile from = Caster, target = m; + Timer.DelayCall(TimeSpan.FromSeconds(1.0), + new TimerStateCallback(AosDelay_Callback), + new object[] { Caster, target, m, damage }); + } + } + else if (CheckHSequence(m)) + { + Mobile from = Caster, target = m; - SpellHelper.Turn( from, target ); + SpellHelper.Turn(from, target); - SpellHelper.CheckReflect( (int)Circle, ref from, ref target ); + SpellHelper.CheckReflect((int)Circle, ref from, ref target); - // Algorithm: (highestStat - lowestStat) / 2 [- 50% if resisted] + // Algorithm: (highestStat - lowestStat) / 2 [- 50% if resisted] - int highestStat = target.Str, lowestStat = target.Str; + int highestStat = target.Str, lowestStat = target.Str; - if ( target.Dex > highestStat ) - highestStat = target.Dex; + if (target.Dex > highestStat) + highestStat = target.Dex; - if ( target.Dex < lowestStat ) - lowestStat = target.Dex; + if (target.Dex < lowestStat) + lowestStat = target.Dex; - if ( target.Int > highestStat ) - highestStat = target.Int; + if (target.Int > highestStat) + highestStat = target.Int; - if ( target.Int < lowestStat ) - lowestStat = target.Int; + if (target.Int < lowestStat) + lowestStat = target.Int; - if ( highestStat > 150 ) - highestStat = 150; + if (highestStat > 150) + highestStat = 150; - if ( lowestStat > 150 ) - lowestStat = 150; + if (lowestStat > 150) + lowestStat = 150; - double damage = GetDamageScalar(m)*(highestStat - lowestStat) / 2; // Many users prefer 3 or 4 + double damage = GetDamageScalar(m) * (highestStat - lowestStat) / 2; // Many users prefer 3 or 4 - if ( damage > 45 ) - damage = 45; + if (damage > 45) + damage = 45; - if ( CheckResisted( target ) ) - { - damage /= 2; - target.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + if (CheckResisted(target)) + { + damage /= 2; + target.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - from.FixedParticles( 0x374A, 10, 15, 2038, EffectLayer.Head ); + from.FixedParticles(0x374A, 10, 15, 2038, EffectLayer.Head); - target.FixedParticles( 0x374A, 10, 15, 5038, EffectLayer.Head ); - target.PlaySound( 0x213 ); + target.FixedParticles(0x374A, 10, 15, 5038, EffectLayer.Head); + target.PlaySound(0x213); - SpellHelper.Damage( this, target, damage, 0, 0, 100, 0, 0 ); - } + SpellHelper.Damage(this, target, damage, 0, 0, 100, 0, 0); + } - FinishSequence(); - } + FinishSequence(); + } - public override double GetSlayerDamageScalar( Mobile target ) - { - return 1.0; //This spell isn't affected by slayer spellbooks - } + public override double GetSlayerDamageScalar(Mobile target) + { + return 1.0; //This spell isn't affected by slayer spellbooks + } - private class InternalTarget : Target - { - private MindBlastSpell m_Owner; + private class InternalTarget : Target + { + private MindBlastSpell m_Owner; - public InternalTarget( MindBlastSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(MindBlastSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/Paralyze.cs b/Scripts/Spells/Fifth/Paralyze.cs index 7029928af..253f1fe5e 100644 --- a/Scripts/Spells/Fifth/Paralyze.cs +++ b/Scripts/Spells/Fifth/Paralyze.cs @@ -1,111 +1,112 @@ using System; using Server.Mobiles; -using Server.Targeting; using Server.Spells.Chivalry; +using Server.Targeting; namespace Server.Spells.Fifth { - public class ParalyzeSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Paralyze", "An Ex Por", - 218, - 9012, - Reagent.Garlic, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class ParalyzeSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Paralyze", "An Ex Por", + 218, + 9012, + Reagent.Garlic, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Fifth; + public ParalyzeSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ParalyzeSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fifth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( Core.AOS && (m.Frozen || m.Paralyzed || (m.Spell != null && m.Spell.IsCasting && !(m.Spell is PaladinSpell))) ) - { - Caster.SendLocalizedMessage( 1061923 ); // The target is already frozen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (Core.AOS && (m.Frozen || m.Paralyzed || + m.Spell != null && m.Spell.IsCasting && !(m.Spell is PaladinSpell))) + { + Caster.SendLocalizedMessage(1061923); // The target is already frozen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - double duration; + double duration; - if ( Core.AOS ) - { - int secs = (int)((GetDamageSkill( Caster ) / 10) - (GetResistSkill( m ) / 10)); + if (Core.AOS) + { + int secs = (int)(GetDamageSkill(Caster) / 10 - GetResistSkill(m) / 10); - if ( !Core.SE ) - secs += 2; + if (!Core.SE) + secs += 2; - if ( !m.Player ) - secs *= 3; + if (!m.Player) + secs *= 3; - if ( secs < 0 ) - secs = 0; + if (secs < 0) + secs = 0; - duration = secs; - } - else - { - // Algorithm: ((20% of magery) + 7) seconds [- 50% if resisted] + duration = secs; + } + else + { + // Algorithm: ((20% of magery) + 7) seconds [- 50% if resisted] - duration = 7.0 + (Caster.Skills[SkillName.Magery].Value * 0.2); + duration = 7.0 + Caster.Skills[SkillName.Magery].Value * 0.2; - if ( CheckResisted( m ) ) - duration *= 0.75; - } + if (CheckResisted(m)) + duration *= 0.75; + } - if ( m is PlagueBeastLord ) - { - ( (PlagueBeastLord) m ).OnParalyzed( Caster ); - duration = 120; - } + if (m is PlagueBeastLord) + { + ((PlagueBeastLord)m).OnParalyzed(Caster); + duration = 120; + } - m.Paralyze( TimeSpan.FromSeconds( duration ) ); + m.Paralyze(TimeSpan.FromSeconds(duration)); - m.PlaySound( 0x204 ); - m.FixedEffect( 0x376A, 6, 1 ); + m.PlaySound(0x204); + m.FixedEffect(0x376A, 6, 1); - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private ParalyzeSpell m_Owner; + public class InternalTarget : Target + { + private ParalyzeSpell m_Owner; - public InternalTarget( ParalyzeSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(ParalyzeSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/PoisonField.cs b/Scripts/Spells/Fifth/PoisonField.cs index 999d35bd6..b35c3dde7 100644 --- a/Scripts/Spells/Fifth/PoisonField.cs +++ b/Scripts/Spells/Fifth/PoisonField.cs @@ -1,298 +1,294 @@ using System; using System.Collections; -using Server.Targeting; -using Server.Misc; using Server.Items; +using Server.Misc; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Fifth { - public class PoisonFieldSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Poison Field", "In Nox Grav", - 230, - 9052, - false, - Reagent.BlackPearl, - Reagent.Nightshade, - Reagent.SpidersSilk - ); + public class PoisonFieldSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Poison Field", "In Nox Grav", + 230, + 9052, + false, + Reagent.BlackPearl, + Reagent.Nightshade, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Fifth; + public PoisonFieldSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public PoisonFieldSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fifth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - int dx = Caster.Location.X - p.X; - int dy = Caster.Location.Y - p.Y; - int rx = (dx - dy) * 44; - int ry = (dx + dy) * 44; + int dx = Caster.Location.X - p.X; + int dy = Caster.Location.Y - p.Y; + int rx = (dx - dy) * 44; + int ry = (dx + dy) * 44; - bool eastToWest; + bool eastToWest; - if ( rx >= 0 && ry >= 0 ) - { - eastToWest = false; - } - else if ( rx >= 0 ) - { - eastToWest = true; - } - else if ( ry >= 0 ) - { - eastToWest = true; - } - else - { - eastToWest = false; - } + if (rx >= 0 && ry >= 0) + eastToWest = false; + else if (rx >= 0) + eastToWest = true; + else if (ry >= 0) + eastToWest = true; + else + eastToWest = false; - Effects.PlaySound( p, Caster.Map, 0x20B ); + Effects.PlaySound(p, Caster.Map, 0x20B); - int itemID = eastToWest ? 0x3915 : 0x3922; + int itemID = eastToWest ? 0x3915 : 0x3922; - TimeSpan duration = TimeSpan.FromSeconds( 3 + (Caster.Skills.Magery.Fixed / 25) ); + TimeSpan duration = TimeSpan.FromSeconds(3 + Caster.Skills.Magery.Fixed / 25); - for ( int i = -2; i <= 2; ++i ) - { - Point3D loc = new Point3D( eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z ); + for (int i = -2; i <= 2; ++i) + { + Point3D loc = new Point3D(eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z); - new InternalItem( itemID, loc, Caster, Caster.Map, duration, i ); - } - } + new InternalItem(itemID, loc, Caster, Caster.Map, duration, i); + } + } - FinishSequence(); - } + FinishSequence(); + } - [DispellableField] - public class InternalItem : Item - { - private Timer m_Timer; - private DateTime m_End; - private Mobile m_Caster; + [DispellableField] + public class InternalItem : Item + { + private Mobile m_Caster; + private DateTime m_End; + private Timer m_Timer; - public override bool BlocksFit => true; + public InternalItem(int itemID, Point3D loc, Mobile caster, Map map, TimeSpan duration, int val) : base(itemID) + { + bool canFit = SpellHelper.AdjustField(ref loc, map, 12, false); - public InternalItem( int itemID, Point3D loc, Mobile caster, Map map, TimeSpan duration, int val ) : base( itemID ) - { - bool canFit = SpellHelper.AdjustField( ref loc, map, 12, false ); + Visible = false; + Movable = false; + Light = LightType.Circle300; - Visible = false; - Movable = false; - Light = LightType.Circle300; + MoveToWorld(loc, map); - MoveToWorld( loc, map ); + m_Caster = caster; - m_Caster = caster; + m_End = DateTime.UtcNow + duration; - m_End = DateTime.UtcNow + duration; + m_Timer = new InternalTimer(this, TimeSpan.FromSeconds(Math.Abs(val) * 0.2), caster.InLOS(this), canFit); + m_Timer.Start(); + } - m_Timer = new InternalTimer( this, TimeSpan.FromSeconds( Math.Abs( val ) * 0.2 ), caster.InLOS( this ), canFit ); - m_Timer.Start(); - } + public InternalItem(Serial serial) : base(serial) + { + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override bool BlocksFit => true; - m_Timer?.Stop(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Timer?.Stop(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.Write( m_Caster ); - writer.WriteDeltaTime( m_End ); - } + writer.Write(m_Caster); + writer.WriteDeltaTime(m_End); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_Caster = reader.ReadMobile(); + switch (version) + { + case 1: + { + m_Caster = reader.ReadMobile(); - goto case 0; - } - case 0: - { - m_End = reader.ReadDeltaTime(); + goto case 0; + } + case 0: + { + m_End = reader.ReadDeltaTime(); - m_Timer = new InternalTimer( this, TimeSpan.Zero, true, true ); - m_Timer.Start(); + m_Timer = new InternalTimer(this, TimeSpan.Zero, true, true); + m_Timer.Start(); - break; - } - } - } + break; + } + } + } - public void ApplyPoisonTo( Mobile m ) - { - if ( m_Caster == null ) - return; + public void ApplyPoisonTo(Mobile m) + { + if (m_Caster == null) + return; - Poison p; + Poison p; - if ( Core.AOS ) - { - int total = (m_Caster.Skills.Magery.Fixed + m_Caster.Skills.Poisoning.Fixed) / 2; + if (Core.AOS) + { + int total = (m_Caster.Skills.Magery.Fixed + m_Caster.Skills.Poisoning.Fixed) / 2; - if ( total >= 1000 ) - p = Poison.Deadly; - else if ( total > 850 ) - p = Poison.Greater; - else if ( total > 650 ) - p = Poison.Regular; - else - p = Poison.Lesser; - } - else - { - p = Poison.Regular; - } + if (total >= 1000) + p = Poison.Deadly; + else if (total > 850) + p = Poison.Greater; + else if (total > 650) + p = Poison.Regular; + else + p = Poison.Lesser; + } + else + { + p = Poison.Regular; + } - if ( m.ApplyPoison( m_Caster, p ) == ApplyPoisonResult.Poisoned ) - if ( SpellHelper.CanRevealCaster( m ) ) - m_Caster.RevealingAction(); + if (m.ApplyPoison(m_Caster, p) == ApplyPoisonResult.Poisoned) + if (SpellHelper.CanRevealCaster(m)) + m_Caster.RevealingAction(); - (m as BaseCreature)?.OnHarmfulSpell( m_Caster ); - } + (m as BaseCreature)?.OnHarmfulSpell(m_Caster); + } - public override bool OnMoveOver( Mobile m ) - { - if ( Visible && m_Caster != null && (!Core.AOS || m != m_Caster) && SpellHelper.ValidIndirectTarget( m_Caster, m ) && m_Caster.CanBeHarmful( m, false ) ) - { - m_Caster.DoHarmful( m ); + public override bool OnMoveOver(Mobile m) + { + if (Visible && m_Caster != null && (!Core.AOS || m != m_Caster) && + SpellHelper.ValidIndirectTarget(m_Caster, m) && m_Caster.CanBeHarmful(m, false)) + { + m_Caster.DoHarmful(m); - ApplyPoisonTo( m ); - m.PlaySound( 0x474 ); - } + ApplyPoisonTo(m); + m.PlaySound(0x474); + } - return true; - } + return true; + } - private class InternalTimer : Timer - { - private InternalItem m_Item; - private bool m_InLOS, m_CanFit; + private class InternalTimer : Timer + { + private static Queue m_Queue = new Queue(); + private bool m_InLOS, m_CanFit; + private InternalItem m_Item; - private static Queue m_Queue = new Queue(); + public InternalTimer(InternalItem item, TimeSpan delay, bool inLOS, bool canFit) : base(delay, + TimeSpan.FromSeconds(1.5)) + { + m_Item = item; + m_InLOS = inLOS; + m_CanFit = canFit; - public InternalTimer( InternalItem item, TimeSpan delay, bool inLOS, bool canFit ) : base( delay, TimeSpan.FromSeconds( 1.5 ) ) - { - m_Item = item; - m_InLOS = inLOS; - m_CanFit = canFit; + Priority = TimerPriority.FiftyMS; + } - Priority = TimerPriority.FiftyMS; - } + protected override void OnTick() + { + if (m_Item.Deleted) + return; - protected override void OnTick() - { - if ( m_Item.Deleted ) - return; + if (!m_Item.Visible) + { + if (m_InLOS && m_CanFit) + m_Item.Visible = true; + else + m_Item.Delete(); - if ( !m_Item.Visible ) - { - if ( m_InLOS && m_CanFit ) - m_Item.Visible = true; - else - m_Item.Delete(); + if (!m_Item.Deleted) + { + m_Item.ProcessDelta(); + Effects.SendLocationParticles( + EffectItem.Create(m_Item.Location, m_Item.Map, EffectItem.DefaultDuration), 0x376A, 9, 10, + 5040); + } + } + else if (DateTime.UtcNow > m_Item.m_End) + { + m_Item.Delete(); + Stop(); + } + else + { + Map map = m_Item.Map; + Mobile caster = m_Item.m_Caster; - if ( !m_Item.Deleted ) - { - m_Item.ProcessDelta(); - Effects.SendLocationParticles( EffectItem.Create( m_Item.Location, m_Item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 5040 ); - } - } - else if ( DateTime.UtcNow > m_Item.m_End ) - { - m_Item.Delete(); - Stop(); - } - else - { - Map map = m_Item.Map; - Mobile caster = m_Item.m_Caster; + if (map != null && caster != null) + { + bool eastToWest = m_Item.ItemID == 0x3915; + IPooledEnumerable eable = map.GetMobilesInBounds( + new Rectangle2D(m_Item.X - (eastToWest ? 0 : 1), m_Item.Y - (eastToWest ? 1 : 0), + eastToWest ? 1 : 2, eastToWest ? 2 : 1)); - if ( map != null && caster != null ) - { - bool eastToWest = ( m_Item.ItemID == 0x3915 ); - IPooledEnumerable eable = map.GetMobilesInBounds( new Rectangle2D( m_Item.X - (eastToWest ? 0 : 1), m_Item.Y - (eastToWest ? 1 : 0), (eastToWest ? 1 : 2), (eastToWest ? 2 : 1) ) ); + foreach (Mobile m in eable) + if (m.Z + 16 > m_Item.Z && m_Item.Z + 12 > m.Z && (!Core.AOS || m != caster) && + SpellHelper.ValidIndirectTarget(caster, m) && caster.CanBeHarmful(m, false)) + m_Queue.Enqueue(m); - foreach ( Mobile m in eable ) - { - if ( (m.Z + 16) > m_Item.Z && (m_Item.Z + 12) > m.Z && (!Core.AOS || m != caster) && SpellHelper.ValidIndirectTarget( caster, m ) && caster.CanBeHarmful( m, false ) ) - m_Queue.Enqueue( m ); - } + eable.Free(); - eable.Free(); + while (m_Queue.Count > 0) + { + Mobile m = (Mobile)m_Queue.Dequeue(); - while ( m_Queue.Count > 0 ) - { - Mobile m = (Mobile)m_Queue.Dequeue(); + caster.DoHarmful(m); - caster.DoHarmful( m ); + m_Item.ApplyPoisonTo(m); + m.PlaySound(0x474); + } + } + } + } + } + } - m_Item.ApplyPoisonTo( m ); - m.PlaySound( 0x474 ); - } - } - } - } - } - } + private class InternalTarget : Target + { + private PoisonFieldSpell m_Owner; - private class InternalTarget : Target - { - private PoisonFieldSpell m_Owner; + public InternalTarget(PoisonFieldSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - public InternalTarget( PoisonFieldSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } - - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fifth/SummonCreature.cs b/Scripts/Spells/Fifth/SummonCreature.cs index 66398f79c..69b31e9b7 100644 --- a/Scripts/Spells/Fifth/SummonCreature.cs +++ b/Scripts/Spells/Fifth/SummonCreature.cs @@ -3,93 +3,92 @@ using Server.Mobiles; namespace Server.Spells.Fifth { - public class SummonCreatureSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Summon Creature", "Kal Xen", - 16, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class SummonCreatureSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Summon Creature", "Kal Xen", + 16, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Fifth; + // NOTE: Creature list based on 1hr of summon/release on OSI. - public SummonCreatureSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + private static Type[] m_Types = + { + typeof(PolarBear), + typeof(GrizzlyBear), + typeof(BlackBear), + typeof(Horse), + typeof(Walrus), + typeof(Chicken), + typeof(Scorpion), + typeof(GiantSerpent), + typeof(Llama), + typeof(Alligator), + typeof(GreyWolf), + typeof(Slime), + typeof(Eagle), + typeof(Gorilla), + typeof(SnowLeopard), + typeof(Pig), + typeof(Hind), + typeof(Rabbit) + }; - // NOTE: Creature list based on 1hr of summon/release on OSI. + public SummonCreatureSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - private static Type[] m_Types = { - typeof( PolarBear ), - typeof( GrizzlyBear ), - typeof( BlackBear ), - typeof( Horse ), - typeof( Walrus ), - typeof( Chicken ), - typeof( Scorpion ), - typeof( GiantSerpent ), - typeof( Llama ), - typeof( Alligator ), - typeof( GreyWolf ), - typeof( Slime ), - typeof( Eagle ), - typeof( Gorilla ), - typeof( SnowLeopard ), - typeof( Pig ), - typeof( Hind ), - typeof( Rabbit ) - }; + public override SpellCircle Circle => SpellCircle.Fifth; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 2) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 2 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - try - { - BaseCreature creature = (BaseCreature)Activator.CreateInstance( m_Types[Utility.Random( m_Types.Length )] ); + public override void OnCast() + { + if (CheckSequence()) + try + { + BaseCreature creature = (BaseCreature)Activator.CreateInstance(m_Types[Utility.Random(m_Types.Length)]); - //creature.ControlSlots = 2; + //creature.ControlSlots = 2; - TimeSpan duration; + TimeSpan duration; - if ( Core.AOS ) - duration = TimeSpan.FromSeconds( (2 * Caster.Skills.Magery.Fixed) / 5 ); - else - duration = TimeSpan.FromSeconds( 4.0 * Caster.Skills[SkillName.Magery].Value ); + if (Core.AOS) + duration = TimeSpan.FromSeconds(2 * Caster.Skills.Magery.Fixed / 5); + else + duration = TimeSpan.FromSeconds(4.0 * Caster.Skills[SkillName.Magery].Value); - SpellHelper.Summon( creature, Caster, 0x215, duration, false, false ); - } - catch - { - } - } + SpellHelper.Summon(creature, Caster, 0x215, duration, false, false); + } + catch + { + } - FinishSequence(); - } + FinishSequence(); + } - public override TimeSpan GetCastDelay() - { - if ( Core.AOS ) - return TimeSpan.FromTicks( base.GetCastDelay().Ticks * 5 ); + public override TimeSpan GetCastDelay() + { + if (Core.AOS) + return TimeSpan.FromTicks(base.GetCastDelay().Ticks * 5); - return base.GetCastDelay() + TimeSpan.FromSeconds( 6.0 ); - } - } -} + return base.GetCastDelay() + TimeSpan.FromSeconds(6.0); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/Clumsy.cs b/Scripts/Spells/First/Clumsy.cs index 00d29a1f7..e4bcea5a1 100644 --- a/Scripts/Spells/First/Clumsy.cs +++ b/Scripts/Spells/First/Clumsy.cs @@ -3,80 +3,77 @@ using Server.Targeting; namespace Server.Spells.First { - public class ClumsySpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Clumsy", "Uus Jux", - 212, - 9031, - Reagent.Bloodmoss, - Reagent.Nightshade - ); + public class ClumsySpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Clumsy", "Uus Jux", + 212, + 9031, + Reagent.Bloodmoss, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.First; + public ClumsySpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ClumsySpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.First; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - SpellHelper.AddStatCurse( Caster, m, StatType.Dex ); + SpellHelper.AddStatCurse(Caster, m, StatType.Dex); - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - m.FixedParticles( 0x3779, 10, 15, 5002, EffectLayer.Head ); - m.PlaySound( 0x1DF ); + m.FixedParticles(0x3779, 10, 15, 5002, EffectLayer.Head); + m.PlaySound(0x1DF); - int percentage = (int)(SpellHelper.GetOffsetScalar( Caster, m, true )*100); - TimeSpan length = SpellHelper.GetDuration( Caster, m ); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, true) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Clumsy, 1075831, length, m, percentage.ToString() ) ); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Clumsy, 1075831, length, m, percentage.ToString())); - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private ClumsySpell m_Owner; + private class InternalTarget : Target + { + private ClumsySpell m_Owner; - public InternalTarget( ClumsySpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(ClumsySpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/CreateFood.cs b/Scripts/Spells/First/CreateFood.cs index 05e236605..a9aee7ff5 100644 --- a/Scripts/Spells/First/CreateFood.cs +++ b/Scripts/Spells/First/CreateFood.cs @@ -3,85 +3,86 @@ using Server.Items; namespace Server.Spells.First { - public class CreateFoodSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Create Food", "In Mani Ylem", - 224, - 9011, - Reagent.Garlic, - Reagent.Ginseng, - Reagent.MandrakeRoot - ); + public class CreateFoodSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Create Food", "In Mani Ylem", + 224, + 9011, + Reagent.Garlic, + Reagent.Ginseng, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.First; + private static FoodInfo[] m_Food = + { + new FoodInfo(typeof(Grapes), "a grape bunch"), + new FoodInfo(typeof(Ham), "a ham"), + new FoodInfo(typeof(CheeseWedge), "a wedge of cheese"), + new FoodInfo(typeof(Muffins), "muffins"), + new FoodInfo(typeof(FishSteak), "a fish steak"), + new FoodInfo(typeof(Ribs), "cut of ribs"), + new FoodInfo(typeof(CookedBird), "a cooked bird"), + new FoodInfo(typeof(Sausage), "sausage"), + new FoodInfo(typeof(Apple), "an apple"), + new FoodInfo(typeof(Peach), "a peach") + }; - public CreateFoodSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public CreateFoodSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - private static FoodInfo[] m_Food = { - new FoodInfo( typeof( Grapes ), "a grape bunch" ), - new FoodInfo( typeof( Ham ), "a ham" ), - new FoodInfo( typeof( CheeseWedge ), "a wedge of cheese" ), - new FoodInfo( typeof( Muffins ), "muffins" ), - new FoodInfo( typeof( FishSteak ), "a fish steak" ), - new FoodInfo( typeof( Ribs ), "cut of ribs" ), - new FoodInfo( typeof( CookedBird ), "a cooked bird" ), - new FoodInfo( typeof( Sausage ), "sausage" ), - new FoodInfo( typeof( Apple ), "an apple" ), - new FoodInfo( typeof( Peach ), "a peach" ) - }; + public override SpellCircle Circle => SpellCircle.First; - public override void OnCast() - { - if ( CheckSequence() ) - { - FoodInfo foodInfo = m_Food[Utility.Random( m_Food.Length )]; - Item food = foodInfo.Create(); + public override void OnCast() + { + if (CheckSequence()) + { + FoodInfo foodInfo = m_Food[Utility.Random(m_Food.Length)]; + Item food = foodInfo.Create(); - if ( food != null ) - { - Caster.AddToBackpack( food ); + if (food != null) + { + Caster.AddToBackpack(food); - // You magically create food in your backpack: - Caster.SendLocalizedMessage( 1042695, true, " " + foodInfo.Name ); + // You magically create food in your backpack: + Caster.SendLocalizedMessage(1042695, true, " " + foodInfo.Name); - Caster.FixedParticles( 0, 10, 5, 2003, EffectLayer.RightHand ); - Caster.PlaySound( 0x1E2 ); - } - } + Caster.FixedParticles(0, 10, 5, 2003, EffectLayer.RightHand); + Caster.PlaySound(0x1E2); + } + } - FinishSequence(); - } - } + FinishSequence(); + } + } - public class FoodInfo - { - public Type Type { get; set; } + public class FoodInfo + { + public FoodInfo(Type type, string name) + { + Type = type; + Name = name; + } - public string Name { get; set; } + public Type Type{ get; set; } - public FoodInfo( Type type, string name ) - { - Type = type; - Name = name; - } + public string Name{ get; set; } - public Item Create() - { - Item item; + public Item Create() + { + Item item; - try - { - item = (Item)Activator.CreateInstance( Type ); - } - catch - { - item = null; - } + try + { + item = (Item)Activator.CreateInstance(Type); + } + catch + { + item = null; + } - return item; - } - } -} + return item; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/Feeblemind.cs b/Scripts/Spells/First/Feeblemind.cs index 6f0a184a4..160d4008e 100644 --- a/Scripts/Spells/First/Feeblemind.cs +++ b/Scripts/Spells/First/Feeblemind.cs @@ -3,80 +3,77 @@ using Server.Targeting; namespace Server.Spells.First { - public class FeeblemindSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Feeblemind", "Rel Wis", - 212, - 9031, - Reagent.Ginseng, - Reagent.Nightshade - ); + public class FeeblemindSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Feeblemind", "Rel Wis", + 212, + 9031, + Reagent.Ginseng, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.First; + public FeeblemindSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public FeeblemindSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.First; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - SpellHelper.AddStatCurse( Caster, m, StatType.Int ); + SpellHelper.AddStatCurse(Caster, m, StatType.Int); - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - m.FixedParticles( 0x3779, 10, 15, 5004, EffectLayer.Head ); - m.PlaySound( 0x1E4 ); + m.FixedParticles(0x3779, 10, 15, 5004, EffectLayer.Head); + m.PlaySound(0x1E4); - int percentage = (int)(SpellHelper.GetOffsetScalar( Caster, m, true )*100); - TimeSpan length = SpellHelper.GetDuration( Caster, m ); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, true) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.FeebleMind, 1075833, length, m, percentage.ToString() ) ); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.FeebleMind, 1075833, length, m, percentage.ToString())); - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private FeeblemindSpell m_Owner; + private class InternalTarget : Target + { + private FeeblemindSpell m_Owner; - public InternalTarget( FeeblemindSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(FeeblemindSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/Heal.cs b/Scripts/Spells/First/Heal.cs index d9992f9b4..4e251300a 100644 --- a/Scripts/Spells/First/Heal.cs +++ b/Scripts/Spells/First/Heal.cs @@ -1,115 +1,114 @@ -using Server.Targeting; -using Server.Network; +using Server.Engines.ConPVP; +using Server.Items; using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Spells.First { - public class HealSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Heal", "In Mani", - 224, - 9061, - Reagent.Garlic, - Reagent.Ginseng, - Reagent.SpidersSilk - ); + public class HealSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Heal", "In Mani", + 224, + 9061, + Reagent.Garlic, + Reagent.Ginseng, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.First; + public HealSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public HealSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.First; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( m.IsDeadBondedPet ) - { - Caster.SendLocalizedMessage( 1060177 ); // You cannot heal a creature that is already dead! - } - else if ( m is BaseCreature && ((BaseCreature)m).IsAnimatedDead ) - { - Caster.SendLocalizedMessage( 1061654 ); // You cannot heal that which is not alive. - } - else if ( m is Golem ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500951 ); // You cannot heal that. - } - else if ( m.Poisoned || Items.MortalStrike.IsWounded( m ) ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x22, (Caster == m) ? 1005000 : 1010398 ); - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (m.IsDeadBondedPet) + { + Caster.SendLocalizedMessage(1060177); // You cannot heal a creature that is already dead! + } + else if (m is BaseCreature && ((BaseCreature)m).IsAnimatedDead) + { + Caster.SendLocalizedMessage(1061654); // You cannot heal that which is not alive. + } + else if (m is Golem) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 500951); // You cannot heal that. + } + else if (m.Poisoned || MortalStrike.IsWounded(m)) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x22, Caster == m ? 1005000 : 1010398); + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - int toHeal; + int toHeal; - if ( Core.AOS ) - { - toHeal = Caster.Skills.Magery.Fixed / 120; - toHeal += Utility.RandomMinMax( 1, 4 ); + if (Core.AOS) + { + toHeal = Caster.Skills.Magery.Fixed / 120; + toHeal += Utility.RandomMinMax(1, 4); - if ( Core.SE && Caster != m ) - toHeal = (int)(toHeal * 1.5); - } - else - { - toHeal = (int)(Caster.Skills[SkillName.Magery].Value * 0.1); - toHeal += Utility.Random( 1, 5 ); - } + if (Core.SE && Caster != m) + toHeal = (int)(toHeal * 1.5); + } + else + { + toHeal = (int)(Caster.Skills[SkillName.Magery].Value * 0.1); + toHeal += Utility.Random(1, 5); + } - //m.Heal( toHeal, Caster ); - SpellHelper.Heal( toHeal, m, Caster ); + //m.Heal( toHeal, Caster ); + SpellHelper.Heal(toHeal, m, Caster); - m.FixedParticles( 0x376A, 9, 32, 5005, EffectLayer.Waist ); - m.PlaySound( 0x1F2 ); - } + m.FixedParticles(0x376A, 9, 32, 5005, EffectLayer.Waist); + m.PlaySound(0x1F2); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private HealSpell m_Owner; + public class InternalTarget : Target + { + private HealSpell m_Owner; - public InternalTarget( HealSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(HealSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/MagicArrow.cs b/Scripts/Spells/First/MagicArrow.cs index 83f7c8b81..793214eba 100644 --- a/Scripts/Spells/First/MagicArrow.cs +++ b/Scripts/Spells/First/MagicArrow.cs @@ -2,94 +2,91 @@ using Server.Targeting; namespace Server.Spells.First { - public class MagicArrowSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Magic Arrow", "In Por Ylem", - 212, - 9041, - Reagent.SulfurousAsh - ); + public class MagicArrowSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Magic Arrow", "In Por Ylem", + 212, + 9041, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.First; + public MagicArrowSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MagicArrowSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.First; - public override bool DelayedDamageStacking => !Core.AOS; + public override bool DelayedDamageStacking => !Core.AOS; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => true; - public override bool DelayedDamage => true; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - Mobile source = Caster; + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + Mobile source = Caster; - SpellHelper.Turn( source, m ); + SpellHelper.Turn(source, m); - SpellHelper.CheckReflect( (int)Circle, ref source, ref m ); + SpellHelper.CheckReflect((int)Circle, ref source, ref m); - double damage; + double damage; - if ( Core.AOS ) - { - damage = GetNewAosDamage( 10, 1, 4, m ); - } - else - { - damage = Utility.Random( 4, 4 ); + if (Core.AOS) + { + damage = GetNewAosDamage(10, 1, 4, m); + } + else + { + damage = Utility.Random(4, 4); - if ( CheckResisted( m ) ) - { - damage *= 0.75; + if (CheckResisted(m)) + { + damage *= 0.75; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - damage *= GetDamageScalar( m ); - } + damage *= GetDamageScalar(m); + } - source.MovingParticles( m, 0x36E4, 5, 0, false, false, 3006, 0, 0 ); - source.PlaySound( 0x1E5 ); + source.MovingParticles(m, 0x36E4, 5, 0, false, false, 3006, 0, 0); + source.PlaySound(0x1E5); - SpellHelper.Damage( this, m, damage, 0, 100, 0, 0, 0 ); - } + SpellHelper.Damage(this, m, damage, 0, 100, 0, 0, 0); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private MagicArrowSpell m_Owner; + private class InternalTarget : Target + { + private MagicArrowSpell m_Owner; - public InternalTarget( MagicArrowSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(MagicArrowSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/NightSight.cs b/Scripts/Spells/First/NightSight.cs index e53627c4d..b1f796e27 100644 --- a/Scripts/Spells/First/NightSight.cs +++ b/Scripts/Spells/First/NightSight.cs @@ -2,72 +2,76 @@ using Server.Targeting; namespace Server.Spells.First { - public class NightSightSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Night Sight", "In Lor", - 236, - 9031, - Reagent.SulfurousAsh, - Reagent.SpidersSilk - ); + public class NightSightSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Night Sight", "In Lor", + 236, + 9031, + Reagent.SulfurousAsh, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.First; + public NightSightSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public NightSightSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.First; - public override void OnCast() - { - Caster.Target = new NightSightTarget( this ); - } + public override void OnCast() + { + Caster.Target = new NightSightTarget(this); + } - private class NightSightTarget : Target - { - private Spell m_Spell; + private class NightSightTarget : Target + { + private Spell m_Spell; - public NightSightTarget( Spell spell ) : base( 12, false, TargetFlags.Beneficial ) - { - m_Spell = spell; - } + public NightSightTarget(Spell spell) : base(12, false, TargetFlags.Beneficial) + { + m_Spell = spell; + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( targeted is Mobile && m_Spell.CheckBSequence( (Mobile) targeted ) ) - { - Mobile targ = (Mobile)targeted; + protected override void OnTarget(Mobile from, object targeted) + { + if (targeted is Mobile && m_Spell.CheckBSequence((Mobile)targeted)) + { + Mobile targ = (Mobile)targeted; - SpellHelper.Turn( m_Spell.Caster, targ ); + SpellHelper.Turn(m_Spell.Caster, targ); - if ( targ.BeginAction( typeof( LightCycle ) ) ) - { - new LightCycle.NightSightTimer( targ ).Start(); - int level = (int)( LightCycle.DungeonLevel * ( (Core.AOS ? targ.Skills[SkillName.Magery].Value : from.Skills[SkillName.Magery].Value )/ 100 ) ); + if (targ.BeginAction(typeof(LightCycle))) + { + new LightCycle.NightSightTimer(targ).Start(); + int level = (int)(LightCycle.DungeonLevel * + ((Core.AOS + ? targ.Skills[SkillName.Magery].Value + : from.Skills[SkillName.Magery].Value) / 100)); - if ( level < 0 ) - level = 0; + if (level < 0) + level = 0; - targ.LightLevel = level; + targ.LightLevel = level; - targ.FixedParticles( 0x376A, 9, 32, 5007, EffectLayer.Waist ); - targ.PlaySound( 0x1E3 ); + targ.FixedParticles(0x376A, 9, 32, 5007, EffectLayer.Waist); + targ.PlaySound(0x1E3); - BuffInfo.AddBuff( targ, new BuffInfo( BuffIcon.NightSight, 1075643 ) ); //Night Sight/You ignore lighting effects - } - else - { - from.SendMessage( "{0} already have nightsight.", from == targ ? "You" : "They" ); - } - } + BuffInfo.AddBuff(targ, + new BuffInfo(BuffIcon.NightSight, 1075643)); //Night Sight/You ignore lighting effects + } + else + { + from.SendMessage("{0} already have nightsight.", from == targ ? "You" : "They"); + } + } - m_Spell.FinishSequence(); - } + m_Spell.FinishSequence(); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Spell.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Spell.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/ReactiveArmor.cs b/Scripts/Spells/First/ReactiveArmor.cs index 4b471d979..4b611fb57 100644 --- a/Scripts/Spells/First/ReactiveArmor.cs +++ b/Scripts/Spells/First/ReactiveArmor.cs @@ -1,157 +1,156 @@ -using System; using System.Collections; namespace Server.Spells.First { - public class ReactiveArmorSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Reactive Armor", "Flam Sanct", - 236, - 9011, - Reagent.Garlic, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); + public class ReactiveArmorSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Reactive Armor", "Flam Sanct", + 236, + 9011, + Reagent.Garlic, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.First; + private static Hashtable m_Table = new Hashtable(); - public ReactiveArmorSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public ReactiveArmorSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override bool CheckCast() - { - if ( Core.AOS ) - return true; + public override SpellCircle Circle => SpellCircle.First; - if ( Caster.MeleeDamageAbsorb > 0 ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - return false; - } + public override bool CheckCast() + { + if (Core.AOS) + return true; - if ( !Caster.CanBeginAction( typeof( DefensiveSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - return false; - } + if (Caster.MeleeDamageAbsorb > 0) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + return false; + } - return true; - } + if (!Caster.CanBeginAction(typeof(DefensiveSpell))) + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + return false; + } - private static Hashtable m_Table = new Hashtable(); + return true; + } - public override void OnCast() - { - if ( Core.AOS ) - { - /* The reactive armor spell increases the caster's physical resistance, while lowering the caster's elemental resistances. - * 15 + (Inscription/20) Physcial bonus - * -5 Elemental - * The reactive armor spell has an indefinite duration, becoming active when cast, and deactivated when re-cast. - * Reactive Armor, Protection, and Magic Reflection will stay on�even after logging out, even after dying�until you �turn them off� by casting them again. - * (+20 physical -5 elemental at 100 Inscription) - */ + public override void OnCast() + { + if (Core.AOS) + { + /* The reactive armor spell increases the caster's physical resistance, while lowering the caster's elemental resistances. + * 15 + (Inscription/20) Physcial bonus + * -5 Elemental + * The reactive armor spell has an indefinite duration, becoming active when cast, and deactivated when re-cast. + * Reactive Armor, Protection, and Magic Reflection will stay on�even after logging out, even after dying�until you �turn them off� by casting them again. + * (+20 physical -5 elemental at 100 Inscription) + */ - if ( CheckSequence() ) - { - Mobile targ = Caster; + if (CheckSequence()) + { + Mobile targ = Caster; - ResistanceMod[] mods = (ResistanceMod[])m_Table[targ]; + ResistanceMod[] mods = (ResistanceMod[])m_Table[targ]; - if ( mods == null ) - { - targ.PlaySound( 0x1E9 ); - targ.FixedParticles( 0x376A, 9, 32, 5008, EffectLayer.Waist ); + if (mods == null) + { + targ.PlaySound(0x1E9); + targ.FixedParticles(0x376A, 9, 32, 5008, EffectLayer.Waist); - mods = new ResistanceMod[5] - { - new ResistanceMod( ResistanceType.Physical, 15 + (int)(targ.Skills[SkillName.Inscribe].Value / 20) ), - new ResistanceMod( ResistanceType.Fire, -5 ), - new ResistanceMod( ResistanceType.Cold, -5 ), - new ResistanceMod( ResistanceType.Poison, -5 ), - new ResistanceMod( ResistanceType.Energy, -5 ) - }; + mods = new ResistanceMod[5] + { + new ResistanceMod(ResistanceType.Physical, + 15 + (int)(targ.Skills[SkillName.Inscribe].Value / 20)), + new ResistanceMod(ResistanceType.Fire, -5), + new ResistanceMod(ResistanceType.Cold, -5), + new ResistanceMod(ResistanceType.Poison, -5), + new ResistanceMod(ResistanceType.Energy, -5) + }; - m_Table[targ] = mods; + m_Table[targ] = mods; - for ( int i = 0; i < mods.Length; ++i ) - targ.AddResistanceMod( mods[i] ); + for (int i = 0; i < mods.Length; ++i) + targ.AddResistanceMod(mods[i]); - int physresist = 15 + (int)(targ.Skills[SkillName.Inscribe].Value / 20); - string args = $"{physresist}\t{5}\t{5}\t{5}\t{5}"; + int physresist = 15 + (int)(targ.Skills[SkillName.Inscribe].Value / 20); + string args = $"{physresist}\t{5}\t{5}\t{5}\t{5}"; - BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.ReactiveArmor, 1075812, 1075813, args.ToString())); - } - else - { - targ.PlaySound( 0x1ED ); - targ.FixedParticles( 0x376A, 9, 32, 5008, EffectLayer.Waist ); + BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.ReactiveArmor, 1075812, 1075813, args)); + } + else + { + targ.PlaySound(0x1ED); + targ.FixedParticles(0x376A, 9, 32, 5008, EffectLayer.Waist); - m_Table.Remove( targ ); + m_Table.Remove(targ); - for ( int i = 0; i < mods.Length; ++i ) - targ.RemoveResistanceMod( mods[i] ); + for (int i = 0; i < mods.Length; ++i) + targ.RemoveResistanceMod(mods[i]); - BuffInfo.RemoveBuff(Caster, BuffIcon.ReactiveArmor); - } - } + BuffInfo.RemoveBuff(Caster, BuffIcon.ReactiveArmor); + } + } - FinishSequence(); - } - else - { - if ( Caster.MeleeDamageAbsorb > 0 ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - else if ( !Caster.CanBeginAction( typeof( DefensiveSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - } - else if ( CheckSequence() ) - { - if ( Caster.BeginAction( typeof( DefensiveSpell ) ) ) - { - int value = (int)(Caster.Skills[SkillName.Magery].Value + Caster.Skills[SkillName.Meditation].Value + Caster.Skills[SkillName.Inscribe].Value); - value /= 3; + FinishSequence(); + } + else + { + if (Caster.MeleeDamageAbsorb > 0) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + else if (!Caster.CanBeginAction(typeof(DefensiveSpell))) + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + } + else if (CheckSequence()) + { + if (Caster.BeginAction(typeof(DefensiveSpell))) + { + int value = (int)(Caster.Skills[SkillName.Magery].Value + Caster.Skills[SkillName.Meditation].Value + + Caster.Skills[SkillName.Inscribe].Value); + value /= 3; - if ( value < 0 ) - value = 1; - else if ( value > 75 ) - value = 75; + if (value < 0) + value = 1; + else if (value > 75) + value = 75; - Caster.MeleeDamageAbsorb = value; + Caster.MeleeDamageAbsorb = value; - Caster.FixedParticles( 0x376A, 9, 32, 5008, EffectLayer.Waist ); - Caster.PlaySound( 0x1F2 ); - } - else - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - } - } + Caster.FixedParticles(0x376A, 9, 32, 5008, EffectLayer.Waist); + Caster.PlaySound(0x1F2); + } + else + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + } + } - FinishSequence(); - } - } + FinishSequence(); + } + } - public static void EndArmor( Mobile m ) - { - if ( m_Table.Contains( m ) ) - { - ResistanceMod[] mods = (ResistanceMod[]) m_Table[ m ]; + public static void EndArmor(Mobile m) + { + if (m_Table.Contains(m)) + { + ResistanceMod[] mods = (ResistanceMod[])m_Table[m]; - if ( mods != null ) - { - for ( int i = 0; i < mods.Length; ++i ) - m.RemoveResistanceMod( mods[ i ] ); - } + if (mods != null) + for (int i = 0; i < mods.Length; ++i) + m.RemoveResistanceMod(mods[i]); - m_Table.Remove( m ); - BuffInfo.RemoveBuff( m, BuffIcon.ReactiveArmor ); - } - } - } -} + m_Table.Remove(m); + BuffInfo.RemoveBuff(m, BuffIcon.ReactiveArmor); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/First/Weaken.cs b/Scripts/Spells/First/Weaken.cs index 411523855..cd3acfb8f 100644 --- a/Scripts/Spells/First/Weaken.cs +++ b/Scripts/Spells/First/Weaken.cs @@ -3,80 +3,77 @@ using Server.Targeting; namespace Server.Spells.First { - public class WeakenSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Weaken", "Des Mani", - 212, - 9031, - Reagent.Garlic, - Reagent.Nightshade - ); + public class WeakenSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Weaken", "Des Mani", + 212, + 9031, + Reagent.Garlic, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.First; + public WeakenSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public WeakenSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.First; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - SpellHelper.AddStatCurse( Caster, m, StatType.Str ); + SpellHelper.AddStatCurse(Caster, m, StatType.Str); - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - m.FixedParticles( 0x3779, 10, 15, 5009, EffectLayer.Waist ); - m.PlaySound( 0x1E6 ); + m.FixedParticles(0x3779, 10, 15, 5009, EffectLayer.Waist); + m.PlaySound(0x1E6); - int percentage = (int)(SpellHelper.GetOffsetScalar( Caster, m, true )*100); - TimeSpan length = SpellHelper.GetDuration( Caster, m ); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, true) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Weaken, 1075837, length, m, percentage.ToString() ) ); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Weaken, 1075837, length, m, percentage.ToString())); - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private WeakenSpell m_Owner; + public class InternalTarget : Target + { + private WeakenSpell m_Owner; - public InternalTarget( WeakenSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(WeakenSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/ArchCure.cs b/Scripts/Spells/Fourth/ArchCure.cs index 26f8911cd..074666067 100644 --- a/Scripts/Spells/Fourth/ArchCure.cs +++ b/Scripts/Spells/Fourth/ArchCure.cs @@ -1,188 +1,185 @@ using System; using System.Collections.Generic; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Fourth { - public class ArchCureSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Arch Cure", "Vas An Nox", - 215, - 9061, - Reagent.Garlic, - Reagent.Ginseng, - Reagent.MandrakeRoot - ); + public class ArchCureSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Arch Cure", "Vas An Nox", + 215, + 9061, + Reagent.Garlic, + Reagent.Ginseng, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Fourth; + public ArchCureSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ArchCureSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fourth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + // Arch cure is now 1/4th of a second faster + public override TimeSpan CastDelayBase => base.CastDelayBase - TimeSpan.FromSeconds(0.25); - // Arch cure is now 1/4th of a second faster - public override TimeSpan CastDelayBase => base.CastDelayBase - TimeSpan.FromSeconds( 0.25 ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - List targets = new List(); + List targets = new List(); - Map map = Caster.Map; - Mobile directTarget = p as Mobile; + Map map = Caster.Map; + Mobile directTarget = p as Mobile; - if ( map != null ) - { - bool feluccaRules = ( map.Rules == MapRules.FeluccaRules ); + if (map != null) + { + bool feluccaRules = map.Rules == MapRules.FeluccaRules; - // You can target any living mobile directly, beneficial checks apply - if ( directTarget != null && Caster.CanBeBeneficial( directTarget, false ) ) - targets.Add( directTarget ); + // You can target any living mobile directly, beneficial checks apply + if (directTarget != null && Caster.CanBeBeneficial(directTarget, false)) + targets.Add(directTarget); - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), 2 ); + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), 2); - foreach ( Mobile m in eable ) - { - if ( m == directTarget ) - continue; + foreach (Mobile m in eable) + { + if (m == directTarget) + continue; - if ( AreaCanTarget( m, feluccaRules ) ) - targets.Add( m ); - } + if (AreaCanTarget(m, feluccaRules)) + targets.Add(m); + } - eable.Free(); - } + eable.Free(); + } - Effects.PlaySound( p, Caster.Map, 0x299 ); + Effects.PlaySound(p, Caster.Map, 0x299); - if ( targets.Count > 0 ) - { - int cured = 0; + if (targets.Count > 0) + { + int cured = 0; - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - Caster.DoBeneficial( m ); + Caster.DoBeneficial(m); - Poison poison = m.Poison; + Poison poison = m.Poison; - if ( poison != null ) - { - int chanceToCure = 10000 + (int)(Caster.Skills[SkillName.Magery].Value * 75) - ((poison.Level + 1) * 1750); - chanceToCure /= 100; - chanceToCure -= 1; + if (poison != null) + { + int chanceToCure = 10000 + (int)(Caster.Skills[SkillName.Magery].Value * 75) - + (poison.Level + 1) * 1750; + chanceToCure /= 100; + chanceToCure -= 1; - if ( chanceToCure > Utility.Random( 100 ) && m.CurePoison( Caster ) ) - ++cured; - } + if (chanceToCure > Utility.Random(100) && m.CurePoison(Caster)) + ++cured; + } - m.FixedParticles( 0x373A, 10, 15, 5012, EffectLayer.Waist ); - m.PlaySound( 0x1E0 ); - } + m.FixedParticles(0x373A, 10, 15, 5012, EffectLayer.Waist); + m.PlaySound(0x1E0); + } - if ( cured > 0 ) - Caster.SendLocalizedMessage( 1010058 ); // You have cured the target of all poisons! - } - } + if (cured > 0) + Caster.SendLocalizedMessage(1010058); // You have cured the target of all poisons! + } + } - FinishSequence(); - } + FinishSequence(); + } - private bool AreaCanTarget( Mobile target, bool feluccaRules ) - { - /* Arch cure area effect won't cure aggressors, victims, murderers, criminals or monsters. - * In Felucca, it will also not cure summons and pets. - * For red players it will only cure themselves and guild members. - */ + private bool AreaCanTarget(Mobile target, bool feluccaRules) + { + /* Arch cure area effect won't cure aggressors, victims, murderers, criminals or monsters. + * In Felucca, it will also not cure summons and pets. + * For red players it will only cure themselves and guild members. + */ - if ( !Caster.CanBeBeneficial( target, false ) ) - return false; + if (!Caster.CanBeBeneficial(target, false)) + return false; - if ( Core.AOS && target != Caster ) - { - if ( IsAggressor( target ) || IsAggressed( target ) ) - return false; + if (Core.AOS && target != Caster) + { + if (IsAggressor(target) || IsAggressed(target)) + return false; - if ( ( !IsInnocentTo( Caster, target ) || !IsInnocentTo( target, Caster ) ) && !IsAllyTo( Caster, target ) ) - return false; + if ((!IsInnocentTo(Caster, target) || !IsInnocentTo(target, Caster)) && !IsAllyTo(Caster, target)) + return false; - if ( feluccaRules && !( target is PlayerMobile ) ) - return false; - } + if (feluccaRules && !(target is PlayerMobile)) + return false; + } - return true; - } + return true; + } - private bool IsAggressor( Mobile m ) - { - foreach ( AggressorInfo info in Caster.Aggressors ) - { - if ( m == info.Attacker && !info.Expired ) - return true; - } + private bool IsAggressor(Mobile m) + { + foreach (AggressorInfo info in Caster.Aggressors) + if (m == info.Attacker && !info.Expired) + return true; - return false; - } + return false; + } - private bool IsAggressed( Mobile m ) - { - foreach ( AggressorInfo info in Caster.Aggressed ) - { - if ( m == info.Defender && !info.Expired ) - return true; - } + private bool IsAggressed(Mobile m) + { + foreach (AggressorInfo info in Caster.Aggressed) + if (m == info.Defender && !info.Expired) + return true; - return false; - } + return false; + } - private static bool IsInnocentTo( Mobile from, Mobile to ) - { - return ( Notoriety.Compute( from, (Mobile)to ) == Notoriety.Innocent ); - } + private static bool IsInnocentTo(Mobile from, Mobile to) + { + return Notoriety.Compute(from, to) == Notoriety.Innocent; + } - private static bool IsAllyTo( Mobile from, Mobile to ) - { - return ( Notoriety.Compute( from, (Mobile)to ) == Notoriety.Ally ); - } + private static bool IsAllyTo(Mobile from, Mobile to) + { + return Notoriety.Compute(from, to) == Notoriety.Ally; + } - private class InternalTarget : Target - { - private ArchCureSpell m_Owner; + private class InternalTarget : Target + { + private ArchCureSpell m_Owner; - public InternalTarget( ArchCureSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(ArchCureSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/ArchProtection.cs b/Scripts/Spells/Fourth/ArchProtection.cs index 1c2f464eb..5bee6953d 100644 --- a/Scripts/Spells/Fourth/ArchProtection.cs +++ b/Scripts/Spells/Fourth/ArchProtection.cs @@ -1,169 +1,167 @@ using System; using System.Collections.Generic; -using Server.Targeting; using Server.Engines.PartySystem; +using Server.Spells.Second; +using Server.Targeting; namespace Server.Spells.Fourth { - public class ArchProtectionSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Arch Protection", "Vas Uus Sanct", - Core.AOS ? 239 : 215, - 9011, - Reagent.Garlic, - Reagent.Ginseng, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class ArchProtectionSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Arch Protection", "Vas Uus Sanct", + Core.AOS ? 239 : 215, + 9011, + Reagent.Garlic, + Reagent.Ginseng, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Fourth; + private static Dictionary _Table = new Dictionary(); - public ArchProtectionSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public ArchProtectionSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override SpellCircle Circle => SpellCircle.Fourth; - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - SpellHelper.GetSurfaceTop( ref p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, p); - List targets = new List(); + SpellHelper.GetSurfaceTop(ref p); - Map map = Caster.Map; + List targets = new List(); - if ( map != null ) - { - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), Core.AOS ? 2 : 3 ); + Map map = Caster.Map; - foreach ( Mobile m in eable ) - { - if ( Caster.CanBeBeneficial( m, false ) ) - targets.Add( m ); - } + if (map != null) + { + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), Core.AOS ? 2 : 3); - eable.Free(); - } + foreach (Mobile m in eable) + if (Caster.CanBeBeneficial(m, false)) + targets.Add(m); - if ( Core.AOS ) - { - Party party = Party.Get( Caster ); + eable.Free(); + } - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + if (Core.AOS) + { + Party party = Party.Get(Caster); - if ( m == Caster || ( party != null && party.Contains( m ) ) ) - { - Caster.DoBeneficial( m ); - Second.ProtectionSpell.Toggle( Caster, m ); - } - } - } - else - { - Effects.PlaySound( p, Caster.Map, 0x299 ); + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - int val = (int)(Caster.Skills[SkillName.Magery].Value/10.0 + 1); + if (m == Caster || party != null && party.Contains(m)) + { + Caster.DoBeneficial(m); + ProtectionSpell.Toggle(Caster, m); + } + } + } + else + { + Effects.PlaySound(p, Caster.Map, 0x299); - if ( targets.Count > 0 ) - { - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + int val = (int)(Caster.Skills[SkillName.Magery].Value / 10.0 + 1); - if ( m.BeginAction( typeof( ArchProtectionSpell ) ) ) - { - Caster.DoBeneficial( m ); - m.VirtualArmorMod += val; + if (targets.Count > 0) + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - AddEntry( m, val ); - new InternalTimer( m, Caster ).Start(); + if (m.BeginAction(typeof(ArchProtectionSpell))) + { + Caster.DoBeneficial(m); + m.VirtualArmorMod += val; - m.FixedParticles( 0x375A, 9, 20, 5027, EffectLayer.Waist ); - m.PlaySound( 0x1F7 ); - } - } - } - } - } + AddEntry(m, val); + new InternalTimer(m, Caster).Start(); - FinishSequence(); - } + m.FixedParticles(0x375A, 9, 20, 5027, EffectLayer.Waist); + m.PlaySound(0x1F7); + } + } + } + } - private static Dictionary _Table = new Dictionary(); + FinishSequence(); + } - private static void AddEntry( Mobile m, int v ) - { - _Table[m] = v; - } + private static void AddEntry(Mobile m, int v) + { + _Table[m] = v; + } - public static void RemoveEntry( Mobile m ) - { - if ( _Table.ContainsKey( m ) ) { - int v = _Table[m]; - _Table.Remove( m ); - m.EndAction( typeof( ArchProtectionSpell ) ); - m.VirtualArmorMod -= v; - if ( m.VirtualArmorMod < 0 ) - m.VirtualArmorMod = 0; - } - } + public static void RemoveEntry(Mobile m) + { + if (_Table.ContainsKey(m)) + { + int v = _Table[m]; + _Table.Remove(m); + m.EndAction(typeof(ArchProtectionSpell)); + m.VirtualArmorMod -= v; + if (m.VirtualArmorMod < 0) + m.VirtualArmorMod = 0; + } + } - private class InternalTimer : Timer - { - private Mobile m_Owner; + private class InternalTimer : Timer + { + private Mobile m_Owner; - public InternalTimer( Mobile target, Mobile caster ) : base( TimeSpan.FromSeconds( 0 ) ) - { - double time = caster.Skills[SkillName.Magery].Value * 1.2; - if ( time > 144 ) - time = 144; - Delay = TimeSpan.FromSeconds( time ); - Priority = TimerPriority.OneSecond; + public InternalTimer(Mobile target, Mobile caster) : base(TimeSpan.FromSeconds(0)) + { + double time = caster.Skills[SkillName.Magery].Value * 1.2; + if (time > 144) + time = 144; + Delay = TimeSpan.FromSeconds(time); + Priority = TimerPriority.OneSecond; - m_Owner = target; - } + m_Owner = target; + } - protected override void OnTick() - { - RemoveEntry( m_Owner ); - } - } + protected override void OnTick() + { + RemoveEntry(m_Owner); + } + } - private class InternalTarget : Target - { - private ArchProtectionSpell m_Owner; + private class InternalTarget : Target + { + private ArchProtectionSpell m_Owner; - public InternalTarget( ArchProtectionSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(ArchProtectionSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/Curse.cs b/Scripts/Spells/Fourth/Curse.cs index 3cd89e956..7c5fd0587 100644 --- a/Scripts/Spells/Fourth/Curse.cs +++ b/Scripts/Spells/Fourth/Curse.cs @@ -4,108 +4,111 @@ using Server.Targeting; namespace Server.Spells.Fourth { - public class CurseSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Curse", "Des Sanct", - 227, - 9031, - Reagent.Nightshade, - Reagent.Garlic, - Reagent.SulfurousAsh - ); + public class CurseSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Curse", "Des Sanct", + 227, + 9031, + Reagent.Nightshade, + Reagent.Garlic, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Fourth; + private static Hashtable m_UnderEffect = new Hashtable(); - public CurseSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public CurseSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override SpellCircle Circle => SpellCircle.Fourth; - private static Hashtable m_UnderEffect = new Hashtable(); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public static void RemoveEffect( object state ) - { - Mobile m = (Mobile)state; + public static void RemoveEffect(object state) + { + Mobile m = (Mobile)state; - m_UnderEffect.Remove( m ); + m_UnderEffect.Remove(m); - m.UpdateResistances(); - } + m.UpdateResistances(); + } - public static bool UnderEffect( Mobile m ) - { - return m_UnderEffect.Contains( m ); - } + public static bool UnderEffect(Mobile m) + { + return m_UnderEffect.Contains(m); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - SpellHelper.AddStatCurse( Caster, m, StatType.Str ); SpellHelper.DisableSkillCheck = true; - SpellHelper.AddStatCurse( Caster, m, StatType.Dex ); - SpellHelper.AddStatCurse( Caster, m, StatType.Int ); SpellHelper.DisableSkillCheck = false; + SpellHelper.AddStatCurse(Caster, m, StatType.Str); + SpellHelper.DisableSkillCheck = true; + SpellHelper.AddStatCurse(Caster, m, StatType.Dex); + SpellHelper.AddStatCurse(Caster, m, StatType.Int); + SpellHelper.DisableSkillCheck = false; - Timer t = (Timer)m_UnderEffect[m]; + Timer t = (Timer)m_UnderEffect[m]; - if ( Caster.Player && m.Player /*&& Caster != m */ && t == null ) //On OSI you CAN curse yourself and get this effect. - { - TimeSpan duration = SpellHelper.GetDuration( Caster, m ); - m_UnderEffect[m] = t = Timer.DelayCall( duration, new TimerStateCallback( RemoveEffect ), m ); - m.UpdateResistances(); - } + if (Caster.Player && m.Player /*&& Caster != m */ && t == null + ) //On OSI you CAN curse yourself and get this effect. + { + TimeSpan duration = SpellHelper.GetDuration(Caster, m); + m_UnderEffect[m] = t = Timer.DelayCall(duration, new TimerStateCallback(RemoveEffect), m); + m.UpdateResistances(); + } - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - m.FixedParticles( 0x374A, 10, 15, 5028, EffectLayer.Waist ); - m.PlaySound( 0x1E1 ); + m.FixedParticles(0x374A, 10, 15, 5028, EffectLayer.Waist); + m.PlaySound(0x1E1); - int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, true) * 100); - TimeSpan length = SpellHelper.GetDuration(Caster, m); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, true) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - string args = $"{percentage}\t{percentage}\t{percentage}\t{10}\t{10}\t{10}\t{10}"; + string args = $"{percentage}\t{percentage}\t{percentage}\t{10}\t{10}\t{10}\t{10}"; - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Curse, 1075835, 1075836, length, m, args.ToString() ) ); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Curse, 1075835, 1075836, length, m, args)); - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private CurseSpell m_Owner; + private class InternalTarget : Target + { + private CurseSpell m_Owner; - public InternalTarget( CurseSpell owner ) : base( Core.ML? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(CurseSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/FireField.cs b/Scripts/Spells/Fourth/FireField.cs index 37b3cdafe..0a284d9b5 100644 --- a/Scripts/Spells/Fourth/FireField.cs +++ b/Scripts/Spells/Fourth/FireField.cs @@ -1,311 +1,306 @@ using System; using System.Collections; -using Server.Targeting; -using Server.Misc; using Server.Items; +using Server.Misc; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Fourth { - public class FireFieldSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Fire Field", "In Flam Grav", - 215, - 9041, - false, - Reagent.BlackPearl, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); - - public override SpellCircle Circle => SpellCircle.Fourth; - - public FireFieldSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } - - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } - - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); - - SpellHelper.GetSurfaceTop( ref p ); - - int dx = Caster.Location.X - p.X; - int dy = Caster.Location.Y - p.Y; - int rx = (dx - dy) * 44; - int ry = (dx + dy) * 44; - - bool eastToWest; - - if ( rx >= 0 && ry >= 0 ) - { - eastToWest = false; - } - else if ( rx >= 0 ) - { - eastToWest = true; - } - else if ( ry >= 0 ) - { - eastToWest = true; - } - else - { - eastToWest = false; - } - - Effects.PlaySound( p, Caster.Map, 0x20C ); - - int itemID = eastToWest ? 0x398C : 0x3996; - - TimeSpan duration; - - if ( Core.AOS ) - duration = TimeSpan.FromSeconds( (15 + (Caster.Skills.Magery.Fixed / 5)) / 4 ); - else - duration = TimeSpan.FromSeconds( 4.0 + (Caster.Skills[SkillName.Magery].Value * 0.5) ); - - for ( int i = -2; i <= 2; ++i ) - { - Point3D loc = new Point3D( eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z ); - - new FireFieldItem( itemID, loc, Caster, Caster.Map, duration, i ); - } - } - - FinishSequence(); - } - - [DispellableField] - public class FireFieldItem : Item - { - private Timer m_Timer; - private DateTime m_End; - private Mobile m_Caster; - private int m_Damage; - - public override bool BlocksFit => true; - - public FireFieldItem( int itemID, Point3D loc, Mobile caster, Map map, TimeSpan duration, int val ) - : this( itemID, loc, caster, map, duration, val, 2 ) - { - } - - public FireFieldItem( int itemID, Point3D loc, Mobile caster, Map map, TimeSpan duration, int val, int damage ) : base( itemID ) - { - bool canFit = SpellHelper.AdjustField( ref loc, map, 12, false ); - - Visible = false; - Movable = false; - Light = LightType.Circle300; - - MoveToWorld( loc, map ); - - m_Caster = caster; - - m_Damage = damage; - - m_End = DateTime.UtcNow + duration; + public class FireFieldSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Fire Field", "In Flam Grav", + 215, + 9041, + false, + Reagent.BlackPearl, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); + + public FireFieldSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } + + public override SpellCircle Circle => SpellCircle.Fourth; + + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } + + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); + + SpellHelper.GetSurfaceTop(ref p); - m_Timer = new InternalTimer( this, TimeSpan.FromSeconds( Math.Abs( val ) * 0.2 ), caster.InLOS( this ), canFit ); - m_Timer.Start(); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - m_Timer?.Stop(); - } - - public FireFieldItem( Serial serial ) : base( serial ) - { - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - - writer.Write( m_Damage ); - writer.Write( m_Caster ); - writer.WriteDeltaTime( m_End ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - { - m_Damage = reader.ReadInt(); - goto case 1; - } - case 1: - { - m_Caster = reader.ReadMobile(); - - goto case 0; - } - case 0: - { - m_End = reader.ReadDeltaTime(); - - m_Timer = new InternalTimer( this, TimeSpan.Zero, true, true ); - m_Timer.Start(); - - break; - } - } - - if ( version < 2 ) - m_Damage = 2; - } - - public override bool OnMoveOver( Mobile m ) - { - if ( Visible && m_Caster != null && (!Core.AOS || m != m_Caster) && SpellHelper.ValidIndirectTarget( m_Caster, m ) && m_Caster.CanBeHarmful( m, false ) ) - { - if ( SpellHelper.CanRevealCaster( m ) ) - m_Caster.RevealingAction(); - - m_Caster.DoHarmful( m ); - - int damage = m_Damage; - - if ( !Core.AOS && m.CheckSkill( SkillName.MagicResist, 0.0, 30.0 ) ) - { - damage = 1; - - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } - - AOS.Damage( m, m_Caster, damage, 0, 100, 0, 0, 0 ); - m.PlaySound( 0x208 ); - - (m as BaseCreature)?.OnHarmfulSpell( m_Caster ); - } - - return true; - } - - private class InternalTimer : Timer - { - private FireFieldItem m_Item; - private bool m_InLOS, m_CanFit; - - private static Queue m_Queue = new Queue(); - - public InternalTimer( FireFieldItem item, TimeSpan delay, bool inLOS, bool canFit ) : base( delay, TimeSpan.FromSeconds( 1.0 ) ) - { - m_Item = item; - m_InLOS = inLOS; - m_CanFit = canFit; - - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - if ( m_Item.Deleted ) - return; - - if ( !m_Item.Visible ) - { - if ( m_InLOS && m_CanFit ) - m_Item.Visible = true; - else - m_Item.Delete(); - - if ( !m_Item.Deleted ) - { - m_Item.ProcessDelta(); - Effects.SendLocationParticles( EffectItem.Create( m_Item.Location, m_Item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 5029 ); - } - } - else if ( DateTime.UtcNow > m_Item.m_End ) - { - m_Item.Delete(); - Stop(); - } - else - { - Map map = m_Item.Map; - Mobile caster = m_Item.m_Caster; - - if ( map != null && caster != null ) - { - foreach ( Mobile m in m_Item.GetMobilesInRange( 0 ) ) - { - if ( (m.Z + 16) > m_Item.Z && (m_Item.Z + 12) > m.Z && (!Core.AOS || m != caster) && SpellHelper.ValidIndirectTarget( caster, m ) && caster.CanBeHarmful( m, false ) ) - m_Queue.Enqueue( m ); - } - - while ( m_Queue.Count > 0 ) - { - Mobile m = (Mobile)m_Queue.Dequeue(); - - if ( SpellHelper.CanRevealCaster( m ) ) - caster.RevealingAction(); - - caster.DoHarmful( m ); - - int damage = m_Item.m_Damage; - - if ( !Core.AOS && m.CheckSkill( SkillName.MagicResist, 0.0, 30.0 ) ) - { - damage = 1; - - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } - - AOS.Damage( m, caster, damage, 0, 100, 0, 0, 0 ); - m.PlaySound( 0x208 ); - - (m as BaseCreature)?.OnHarmfulSpell( caster ); - } - } - } - } - } - } - - private class InternalTarget : Target - { - private FireFieldSpell m_Owner; - - public InternalTarget( FireFieldSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } - - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } - - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + int dx = Caster.Location.X - p.X; + int dy = Caster.Location.Y - p.Y; + int rx = (dx - dy) * 44; + int ry = (dx + dy) * 44; + + bool eastToWest; + + if (rx >= 0 && ry >= 0) + eastToWest = false; + else if (rx >= 0) + eastToWest = true; + else if (ry >= 0) + eastToWest = true; + else + eastToWest = false; + + Effects.PlaySound(p, Caster.Map, 0x20C); + + int itemID = eastToWest ? 0x398C : 0x3996; + + TimeSpan duration; + + if (Core.AOS) + duration = TimeSpan.FromSeconds((15 + Caster.Skills.Magery.Fixed / 5) / 4); + else + duration = TimeSpan.FromSeconds(4.0 + Caster.Skills[SkillName.Magery].Value * 0.5); + + for (int i = -2; i <= 2; ++i) + { + Point3D loc = new Point3D(eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z); + + new FireFieldItem(itemID, loc, Caster, Caster.Map, duration, i); + } + } + + FinishSequence(); + } + + [DispellableField] + public class FireFieldItem : Item + { + private Mobile m_Caster; + private int m_Damage; + private DateTime m_End; + private Timer m_Timer; + + public FireFieldItem(int itemID, Point3D loc, Mobile caster, Map map, TimeSpan duration, int val) + : this(itemID, loc, caster, map, duration, val, 2) + { + } + + public FireFieldItem(int itemID, Point3D loc, Mobile caster, Map map, TimeSpan duration, int val, + int damage) : base(itemID) + { + bool canFit = SpellHelper.AdjustField(ref loc, map, 12, false); + + Visible = false; + Movable = false; + Light = LightType.Circle300; + + MoveToWorld(loc, map); + + m_Caster = caster; + + m_Damage = damage; + + m_End = DateTime.UtcNow + duration; + + m_Timer = new InternalTimer(this, TimeSpan.FromSeconds(Math.Abs(val) * 0.2), caster.InLOS(this), canFit); + m_Timer.Start(); + } + + public FireFieldItem(Serial serial) : base(serial) + { + } + + public override bool BlocksFit => true; + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + m_Timer?.Stop(); + } + + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + + writer.Write(2); // version + + writer.Write(m_Damage); + writer.Write(m_Caster); + writer.WriteDeltaTime(m_End); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + + int version = reader.ReadInt(); + + switch (version) + { + case 2: + { + m_Damage = reader.ReadInt(); + goto case 1; + } + case 1: + { + m_Caster = reader.ReadMobile(); + + goto case 0; + } + case 0: + { + m_End = reader.ReadDeltaTime(); + + m_Timer = new InternalTimer(this, TimeSpan.Zero, true, true); + m_Timer.Start(); + + break; + } + } + + if (version < 2) + m_Damage = 2; + } + + public override bool OnMoveOver(Mobile m) + { + if (Visible && m_Caster != null && (!Core.AOS || m != m_Caster) && + SpellHelper.ValidIndirectTarget(m_Caster, m) && m_Caster.CanBeHarmful(m, false)) + { + if (SpellHelper.CanRevealCaster(m)) + m_Caster.RevealingAction(); + + m_Caster.DoHarmful(m); + + int damage = m_Damage; + + if (!Core.AOS && m.CheckSkill(SkillName.MagicResist, 0.0, 30.0)) + { + damage = 1; + + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } + + AOS.Damage(m, m_Caster, damage, 0, 100, 0, 0, 0); + m.PlaySound(0x208); + + (m as BaseCreature)?.OnHarmfulSpell(m_Caster); + } + + return true; + } + + private class InternalTimer : Timer + { + private static Queue m_Queue = new Queue(); + private bool m_InLOS, m_CanFit; + private FireFieldItem m_Item; + + public InternalTimer(FireFieldItem item, TimeSpan delay, bool inLOS, bool canFit) : base(delay, + TimeSpan.FromSeconds(1.0)) + { + m_Item = item; + m_InLOS = inLOS; + m_CanFit = canFit; + + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + if (m_Item.Deleted) + return; + + if (!m_Item.Visible) + { + if (m_InLOS && m_CanFit) + m_Item.Visible = true; + else + m_Item.Delete(); + + if (!m_Item.Deleted) + { + m_Item.ProcessDelta(); + Effects.SendLocationParticles( + EffectItem.Create(m_Item.Location, m_Item.Map, EffectItem.DefaultDuration), 0x376A, 9, 10, + 5029); + } + } + else if (DateTime.UtcNow > m_Item.m_End) + { + m_Item.Delete(); + Stop(); + } + else + { + Map map = m_Item.Map; + Mobile caster = m_Item.m_Caster; + + if (map != null && caster != null) + { + foreach (Mobile m in m_Item.GetMobilesInRange(0)) + if (m.Z + 16 > m_Item.Z && m_Item.Z + 12 > m.Z && (!Core.AOS || m != caster) && + SpellHelper.ValidIndirectTarget(caster, m) && caster.CanBeHarmful(m, false)) + m_Queue.Enqueue(m); + + while (m_Queue.Count > 0) + { + Mobile m = (Mobile)m_Queue.Dequeue(); + + if (SpellHelper.CanRevealCaster(m)) + caster.RevealingAction(); + + caster.DoHarmful(m); + + int damage = m_Item.m_Damage; + + if (!Core.AOS && m.CheckSkill(SkillName.MagicResist, 0.0, 30.0)) + { + damage = 1; + + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } + + AOS.Damage(m, caster, damage, 0, 100, 0, 0, 0); + m.PlaySound(0x208); + + (m as BaseCreature)?.OnHarmfulSpell(caster); + } + } + } + } + } + } + + private class InternalTarget : Target + { + private FireFieldSpell m_Owner; + + public InternalTarget(FireFieldSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } + + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/GreaterHeal.cs b/Scripts/Spells/Fourth/GreaterHeal.cs index e31d26044..5f2273545 100644 --- a/Scripts/Spells/Fourth/GreaterHeal.cs +++ b/Scripts/Spells/Fourth/GreaterHeal.cs @@ -1,105 +1,104 @@ -using Server.Targeting; -using Server.Network; +using Server.Engines.ConPVP; +using Server.Items; using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Spells.Fourth { - public class GreaterHealSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Greater Heal", "In Vas Mani", - 204, - 9061, - Reagent.Garlic, - Reagent.Ginseng, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class GreaterHealSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Greater Heal", "In Vas Mani", + 204, + 9061, + Reagent.Garlic, + Reagent.Ginseng, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Fourth; + public GreaterHealSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public GreaterHealSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fourth; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( m is BaseCreature && ((BaseCreature)m).IsAnimatedDead ) - { - Caster.SendLocalizedMessage( 1061654 ); // You cannot heal that which is not alive. - } - else if ( m.IsDeadBondedPet ) - { - Caster.SendLocalizedMessage( 1060177 ); // You cannot heal a creature that is already dead! - } - else if ( m is Golem ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 500951 ); // You cannot heal that. - } - else if ( m.Poisoned || Items.MortalStrike.IsWounded( m ) ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x22, (Caster == m) ? 1005000 : 1010398 ); - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (m is BaseCreature && ((BaseCreature)m).IsAnimatedDead) + { + Caster.SendLocalizedMessage(1061654); // You cannot heal that which is not alive. + } + else if (m.IsDeadBondedPet) + { + Caster.SendLocalizedMessage(1060177); // You cannot heal a creature that is already dead! + } + else if (m is Golem) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 500951); // You cannot heal that. + } + else if (m.Poisoned || MortalStrike.IsWounded(m)) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x22, Caster == m ? 1005000 : 1010398); + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - // Algorithm: (40% of magery) + (1-10) + // Algorithm: (40% of magery) + (1-10) - int toHeal = (int)(Caster.Skills[SkillName.Magery].Value * 0.4); - toHeal += Utility.Random( 1, 10 ); + int toHeal = (int)(Caster.Skills[SkillName.Magery].Value * 0.4); + toHeal += Utility.Random(1, 10); - //m.Heal( toHeal, Caster ); - SpellHelper.Heal( toHeal, m, Caster ); + //m.Heal( toHeal, Caster ); + SpellHelper.Heal(toHeal, m, Caster); - m.FixedParticles( 0x376A, 9, 32, 5030, EffectLayer.Waist ); - m.PlaySound( 0x202 ); - } + m.FixedParticles(0x376A, 9, 32, 5030, EffectLayer.Waist); + m.PlaySound(0x202); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private GreaterHealSpell m_Owner; + public class InternalTarget : Target + { + private GreaterHealSpell m_Owner; - public InternalTarget( GreaterHealSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(GreaterHealSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/Lightning.cs b/Scripts/Spells/Fourth/Lightning.cs index d92773e68..ca2093cb3 100644 --- a/Scripts/Spells/Fourth/Lightning.cs +++ b/Scripts/Spells/Fourth/Lightning.cs @@ -2,88 +2,88 @@ using Server.Targeting; namespace Server.Spells.Fourth { - public class LightningSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Lightning", "Por Ort Grav", - 239, - 9021, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class LightningSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Lightning", "Por Ort Grav", + 239, + 9021, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Fourth; + public LightningSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public LightningSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Fourth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => false; - public override bool DelayedDamage => false; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - double damage; + double damage; - if ( Core.AOS ) - { - damage = GetNewAosDamage( 23, 1, 4, m ); - } - else - { - damage = Utility.Random( 12, 9 ); + if (Core.AOS) + { + damage = GetNewAosDamage(23, 1, 4, m); + } + else + { + damage = Utility.Random(12, 9); - if ( CheckResisted( m ) ) - { - damage *= 0.75; + if (CheckResisted(m)) + { + damage *= 0.75; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - damage *= GetDamageScalar( m ); - } + damage *= GetDamageScalar(m); + } - m.BoltEffect( 0 ); + m.BoltEffect(0); - SpellHelper.Damage( this, m, damage, 0, 0, 0, 0, 100 ); - } + SpellHelper.Damage(this, m, damage, 0, 0, 0, 0, 100); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private LightningSpell m_Owner; + private class InternalTarget : Target + { + private LightningSpell m_Owner; - public InternalTarget( LightningSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(LightningSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/ManaDrain.cs b/Scripts/Spells/Fourth/ManaDrain.cs index 91a1d7456..e66676a7e 100644 --- a/Scripts/Spells/Fourth/ManaDrain.cs +++ b/Scripts/Spells/Fourth/ManaDrain.cs @@ -4,129 +4,130 @@ using Server.Targeting; namespace Server.Spells.Fourth { - public class ManaDrainSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mana Drain", "Ort Rel", - 215, - 9031, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class ManaDrainSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mana Drain", "Ort Rel", + 215, + 9031, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Fourth; + private static Dictionary m_Table = new Dictionary(); - public ManaDrainSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public ManaDrainSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override SpellCircle Circle => SpellCircle.Fourth; - private static Dictionary m_Table = new Dictionary(); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - private void AosDelay_Callback( object state ) - { - object[] states = (object[])state; + private void AosDelay_Callback(object state) + { + object[] states = (object[])state; - Mobile m = (Mobile)states[0]; - int mana = (int)states[1]; + Mobile m = (Mobile)states[0]; + int mana = (int)states[1]; - if ( m.Alive && !m.IsDeadBondedPet ) - { - m.Mana += mana; + if (m.Alive && !m.IsDeadBondedPet) + { + m.Mana += mana; - m.FixedEffect( 0x3779, 10, 25 ); - m.PlaySound( 0x28E ); - } + m.FixedEffect(0x3779, 10, 25); + m.PlaySound(0x28E); + } - m_Table.Remove( m ); - } + m_Table.Remove(m); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - if ( Core.AOS ) - { - int toDrain = 40 + (int)(GetDamageSkill( Caster ) - GetResistSkill( m )); + if (Core.AOS) + { + int toDrain = 40 + (int)(GetDamageSkill(Caster) - GetResistSkill(m)); - if ( toDrain < 0 ) - toDrain = 0; - else if ( toDrain > m.Mana ) - toDrain = m.Mana; + if (toDrain < 0) + toDrain = 0; + else if (toDrain > m.Mana) + toDrain = m.Mana; - if ( m_Table.ContainsKey( m ) ) - toDrain = 0; + if (m_Table.ContainsKey(m)) + toDrain = 0; - m.FixedParticles( 0x3789, 10, 25, 5032, EffectLayer.Head ); - m.PlaySound( 0x1F8 ); + m.FixedParticles(0x3789, 10, 25, 5032, EffectLayer.Head); + m.PlaySound(0x1F8); - if ( toDrain > 0 ) - { - m.Mana -= toDrain; + if (toDrain > 0) + { + m.Mana -= toDrain; - m_Table[m] = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( AosDelay_Callback ), new object[]{ m, toDrain } ); - } - } - else - { - if ( CheckResisted( m ) ) - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - else if ( m.Mana >= 100 ) - m.Mana -= Utility.Random( 1, 100 ); - else - m.Mana -= Utility.Random( 1, m.Mana ); + m_Table[m] = Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(AosDelay_Callback), + new object[] { m, toDrain }); + } + } + else + { + if (CheckResisted(m)) + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + else if (m.Mana >= 100) + m.Mana -= Utility.Random(1, 100); + else + m.Mana -= Utility.Random(1, m.Mana); - m.FixedParticles( 0x374A, 10, 15, 5032, EffectLayer.Head ); - m.PlaySound( 0x1F8 ); - } + m.FixedParticles(0x374A, 10, 15, 5032, EffectLayer.Head); + m.PlaySound(0x1F8); + } - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - public override double GetResistPercent( Mobile target ) - { - return 99.0; - } + public override double GetResistPercent(Mobile target) + { + return 99.0; + } - private class InternalTarget : Target - { - private ManaDrainSpell m_Owner; + private class InternalTarget : Target + { + private ManaDrainSpell m_Owner; - public InternalTarget( ManaDrainSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(ManaDrainSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Fourth/Recall.cs b/Scripts/Spells/Fourth/Recall.cs index 5a9034c51..8bf37ed50 100644 --- a/Scripts/Spells/Fourth/Recall.cs +++ b/Scripts/Spells/Fourth/Recall.cs @@ -1,206 +1,213 @@ +using Server.Factions; using Server.Items; -using Server.Multis; +using Server.Misc; using Server.Mobiles; +using Server.Multis; using Server.Network; -using Server.Targeting; using Server.Spells.Necromancy; +using Server.Targeting; namespace Server.Spells.Fourth { - public class RecallSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Recall", "Kal Ort Por", - 239, - 9031, - Reagent.BlackPearl, - Reagent.Bloodmoss, - Reagent.MandrakeRoot - ); + public class RecallSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Recall", "Kal Ort Por", + 239, + 9031, + Reagent.BlackPearl, + Reagent.Bloodmoss, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Fourth; + private Runebook m_Book; - private RunebookEntry m_Entry; - private Runebook m_Book; + private RunebookEntry m_Entry; - public RecallSpell( Mobile caster, Item scroll ) : this( caster, scroll, null, null ) - { - } + public RecallSpell(Mobile caster, Item scroll) : this(caster, scroll, null, null) + { + } - public RecallSpell( Mobile caster, Item scroll, RunebookEntry entry, Runebook book ) : base( caster, scroll, m_Info ) - { - m_Entry = entry; - m_Book = book; - } + public RecallSpell(Mobile caster, Item scroll, RunebookEntry entry, Runebook book) : base(caster, scroll, m_Info) + { + m_Entry = entry; + m_Book = book; + } - public override void GetCastSkills( out double min, out double max ) - { - if ( TransformationSpellHelper.UnderTransformation( Caster, typeof( WraithFormSpell ) ) ) - min = max = 0; - else if ( Core.SE && m_Book != null ) //recall using Runebook charge - min = max = 0; - else - base.GetCastSkills( out min, out max ); - } + public override SpellCircle Circle => SpellCircle.Fourth; - public override void OnCast() - { - if ( m_Entry == null ) - Caster.Target = new InternalTarget( this ); - else - Effect( m_Entry.Location, m_Entry.Map, true ); - } + public override void GetCastSkills(out double min, out double max) + { + if (TransformationSpellHelper.UnderTransformation(Caster, typeof(WraithFormSpell))) + min = max = 0; + else if (Core.SE && m_Book != null) //recall using Runebook charge + min = max = 0; + else + base.GetCastSkills(out min, out max); + } - public override bool CheckCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } + public override void OnCast() + { + if (m_Entry == null) + Caster.Target = new InternalTarget(this); + else + Effect(m_Entry.Location, m_Entry.Map, true); + } - if ( Caster.Criminal ) - { - Caster.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - return false; - } - if ( SpellHelper.CheckCombat( Caster ) ) - { - Caster.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - return false; - } - if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - return false; - } + public override bool CheckCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } - return SpellHelper.CheckTravel( Caster, TravelCheckType.RecallFrom ); - } + if (Caster.Criminal) + { + Caster.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + return false; + } - public void Effect( Point3D loc, Map map, bool checkMulti ) - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( map == null || (!Core.AOS && Caster.Map != map) ) - { - Caster.SendLocalizedMessage( 1005569 ); // You can not recall to another facet. - } - else if ( !SpellHelper.CheckTravel( Caster, TravelCheckType.RecallFrom ) ) - { - } - else if ( !SpellHelper.CheckTravel( Caster, map, loc, TravelCheckType.RecallTo ) ) - { - } - else if ( map == Map.Felucca && Caster is PlayerMobile && ((PlayerMobile)Caster).Young ) - { - Caster.SendLocalizedMessage( 1049543 ); // You decide against traveling to Felucca while you are still young. - } - else if ( Caster.Kills >= 5 && map != Map.Felucca ) - { - Caster.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - } - else if ( Caster.Criminal ) - { - Caster.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - } - else if ( SpellHelper.CheckCombat( Caster ) ) - { - Caster.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - } - else if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - } - else if ( !map.CanSpawnMobile( loc.X, loc.Y, loc.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( (checkMulti && SpellHelper.CheckMulti( loc, map )) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( m_Book != null && m_Book.CurCharges <= 0 ) - { - Caster.SendLocalizedMessage( 502412 ); // There are no charges left on that item. - } - else if ( CheckSequence() ) - { - BaseCreature.TeleportPets( Caster, loc, map, true ); + if (SpellHelper.CheckCombat(Caster)) + { + Caster.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + return false; + } - if ( m_Book != null ) - --m_Book.CurCharges; + if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + return false; + } - Caster.PlaySound( 0x1FC ); - Caster.MoveToWorld( loc, map ); - Caster.PlaySound( 0x1FC ); - } + return SpellHelper.CheckTravel(Caster, TravelCheckType.RecallFrom); + } - FinishSequence(); - } + public void Effect(Point3D loc, Map map, bool checkMulti) + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (map == null || !Core.AOS && Caster.Map != map) + { + Caster.SendLocalizedMessage(1005569); // You can not recall to another facet. + } + else if (!SpellHelper.CheckTravel(Caster, TravelCheckType.RecallFrom)) + { + } + else if (!SpellHelper.CheckTravel(Caster, map, loc, TravelCheckType.RecallTo)) + { + } + else if (map == Map.Felucca && Caster is PlayerMobile && ((PlayerMobile)Caster).Young) + { + Caster.SendLocalizedMessage(1049543); // You decide against traveling to Felucca while you are still young. + } + else if (Caster.Kills >= 5 && map != Map.Felucca) + { + Caster.SendLocalizedMessage(1019004); // You are not allowed to travel there. + } + else if (Caster.Criminal) + { + Caster.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + } + else if (SpellHelper.CheckCombat(Caster)) + { + Caster.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + } + else if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + } + else if (!map.CanSpawnMobile(loc.X, loc.Y, loc.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (checkMulti && SpellHelper.CheckMulti(loc, map)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (m_Book != null && m_Book.CurCharges <= 0) + { + Caster.SendLocalizedMessage(502412); // There are no charges left on that item. + } + else if (CheckSequence()) + { + BaseCreature.TeleportPets(Caster, loc, map, true); - private class InternalTarget : Target - { - private RecallSpell m_Owner; + if (m_Book != null) + --m_Book.CurCharges; - public InternalTarget( RecallSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; + Caster.PlaySound(0x1FC); + Caster.MoveToWorld(loc, map); + Caster.PlaySound(0x1FC); + } - owner.Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501029 ); // Select Marked item. - } + FinishSequence(); + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is RecallRune ) - { - RecallRune rune = (RecallRune)o; + private class InternalTarget : Target + { + private RecallSpell m_Owner; - if ( rune.Marked ) - m_Owner.Effect( rune.Target, rune.TargetMap, true ); - else - from.SendLocalizedMessage( 501805 ); // That rune is not yet marked. - } - else if ( o is Runebook ) - { - RunebookEntry e = ((Runebook)o).Default; + public InternalTarget(RecallSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; - if ( e != null ) - m_Owner.Effect( e.Location, e.Map, true ); - else - from.SendLocalizedMessage( 502354 ); // Target is not marked. - } - else if ( o is Key && ((Key)o).KeyValue != 0 && ((Key)o).Link is BaseBoat ) - { - BaseBoat boat = ((Key)o).Link as BaseBoat; + owner.Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501029); // Select Marked item. + } - if ( !boat.Deleted && boat.CheckKey( ((Key)o).KeyValue ) ) - m_Owner.Effect( boat.GetMarkedLocation(), boat.Map, false ); - else - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, from.Name, "" ) ); // I can not recall from that object. - } - else if ( o is HouseRaffleDeed && ((HouseRaffleDeed)o).ValidLocation() ) - { - HouseRaffleDeed deed = (HouseRaffleDeed)o; + protected override void OnTarget(Mobile from, object o) + { + if (o is RecallRune) + { + RecallRune rune = (RecallRune)o; - m_Owner.Effect( deed.PlotLocation, deed.PlotFacet, true ); - } - else - { - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, from.Name, "" ) ); // I can not recall from that object. - } - } + if (rune.Marked) + m_Owner.Effect(rune.Target, rune.TargetMap, true); + else + from.SendLocalizedMessage(501805); // That rune is not yet marked. + } + else if (o is Runebook) + { + RunebookEntry e = ((Runebook)o).Default; - protected override void OnNonlocalTarget( Mobile from, object o ) - { - } + if (e != null) + m_Owner.Effect(e.Location, e.Map, true); + else + from.SendLocalizedMessage(502354); // Target is not marked. + } + else if (o is Key && ((Key)o).KeyValue != 0 && ((Key)o).Link is BaseBoat) + { + BaseBoat boat = ((Key)o).Link as BaseBoat; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + if (!boat.Deleted && boat.CheckKey(((Key)o).KeyValue)) + m_Owner.Effect(boat.GetMarkedLocation(), boat.Map, false); + else + from.Send(new MessageLocalized(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, + from.Name, "")); // I can not recall from that object. + } + else if (o is HouseRaffleDeed && ((HouseRaffleDeed)o).ValidLocation()) + { + HouseRaffleDeed deed = (HouseRaffleDeed)o; + + m_Owner.Effect(deed.PlotLocation, deed.PlotFacet, true); + } + else + { + from.Send(new MessageLocalized(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 502357, from.Name, + "")); // I can not recall from that object. + } + } + + protected override void OnNonlocalTarget(Mobile from, object o) + { + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Gargoyle/SpellDefinitions/FlySpell.cs b/Scripts/Spells/Gargoyle/SpellDefinitions/FlySpell.cs index df9a3f9f6..5abc03b8a 100644 --- a/Scripts/Spells/Gargoyle/SpellDefinitions/FlySpell.cs +++ b/Scripts/Spells/Gargoyle/SpellDefinitions/FlySpell.cs @@ -2,80 +2,81 @@ using System; namespace Server.Spells { - public class FlySpell : Spell + public class FlySpell : Spell + { + private static readonly SpellInfo m_Info = new SpellInfo("Gargoyle Flight", null, -1, 9002); + private bool m_Stop; + + public FlySpell(Mobile caster) + : base(caster, null, m_Info) { - private static readonly SpellInfo m_Info = new SpellInfo("Gargoyle Flight", null, -1, 9002); - private bool m_Stop; - public FlySpell(Mobile caster) - : base(caster, null, m_Info) - { - } - - public override bool ClearHandsOnCast => false; - - public override bool RevealOnCast => false; - - public override double CastDelayFastScalar => 0; - - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(.25); - - public override TimeSpan GetCastRecovery() - { - return TimeSpan.Zero; - } - - public override int GetMana() - { - return 0; - } - - public override bool ConsumeReagents() - { - return true; - } - - public override bool CheckFizzle() - { - return true; - } - - public void Stop() - { - m_Stop = true; - Disturb(DisturbType.Hurt, false, false); - } - - public override bool CheckDisturb(DisturbType type, bool checkFirst, bool resistable) - { - if (type == DisturbType.EquipRequest || type == DisturbType.UseRequest/* || type == DisturbType.Hurt*/) - return false; - - return true; - } - - public override void DoHurtFizzle() - { - } - - public override void DoFizzle() - { - } - - public override void OnDisturb(DisturbType type, bool message) - { - if (message && !m_Stop) - Caster.SendLocalizedMessage(1113192); // You have been disrupted while attempting to fly! - } - - public override void OnCast() - { - Caster.Flying = false; - BuffInfo.RemoveBuff(Caster, BuffIcon.Fly); - Caster.Animate(60, 10, 1, true, false, 0); - Caster.SendLocalizedMessage(1112567); // You are flying. - Caster.Flying = true; - BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.Fly, 1112567)); - FinishSequence(); - } } + + public override bool ClearHandsOnCast => false; + + public override bool RevealOnCast => false; + + public override double CastDelayFastScalar => 0; + + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(.25); + + public override TimeSpan GetCastRecovery() + { + return TimeSpan.Zero; + } + + public override int GetMana() + { + return 0; + } + + public override bool ConsumeReagents() + { + return true; + } + + public override bool CheckFizzle() + { + return true; + } + + public void Stop() + { + m_Stop = true; + Disturb(DisturbType.Hurt, false, false); + } + + public override bool CheckDisturb(DisturbType type, bool checkFirst, bool resistable) + { + if (type == DisturbType.EquipRequest || type == DisturbType.UseRequest /* || type == DisturbType.Hurt*/) + return false; + + return true; + } + + public override void DoHurtFizzle() + { + } + + public override void DoFizzle() + { + } + + public override void OnDisturb(DisturbType type, bool message) + { + if (message && !m_Stop) + Caster.SendLocalizedMessage(1113192); // You have been disrupted while attempting to fly! + } + + public override void OnCast() + { + Caster.Flying = false; + BuffInfo.RemoveBuff(Caster, BuffIcon.Fly); + Caster.Animate(60, 10, 1, true, false, 0); + Caster.SendLocalizedMessage(1112567); // You are flying. + Caster.Flying = true; + BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.Fly, 1112567)); + FinishSequence(); + } + } } \ No newline at end of file diff --git a/Scripts/Spells/Initializer.cs b/Scripts/Spells/Initializer.cs index 4147efe0c..b027bea18 100644 --- a/Scripts/Spells/Initializer.cs +++ b/Scripts/Spells/Initializer.cs @@ -1,193 +1,207 @@ using System; +using Server.Spells.Bushido; +using Server.Spells.Chivalry; +using Server.Spells.Eighth; +using Server.Spells.Fifth; +using Server.Spells.First; +using Server.Spells.Fourth; +using Server.Spells.Mysticism; +using Server.Spells.Necromancy; +using Server.Spells.Ninjitsu; +using Server.Spells.Second; +using Server.Spells.Seventh; +using Server.Spells.Sixth; +using Server.Spells.Spellweaving; +using Server.Spells.Third; namespace Server.Spells { - public class Initializer - { - public static void Initialize() - { - // First circle - Register( 00, typeof( First.ClumsySpell ) ); - Register( 01, typeof( First.CreateFoodSpell ) ); - Register( 02, typeof( First.FeeblemindSpell ) ); - Register( 03, typeof( First.HealSpell ) ); - Register( 04, typeof( First.MagicArrowSpell ) ); - Register( 05, typeof( First.NightSightSpell ) ); - Register( 06, typeof( First.ReactiveArmorSpell ) ); - Register( 07, typeof( First.WeakenSpell ) ); + public class Initializer + { + public static void Initialize() + { + // First circle + Register(00, typeof(ClumsySpell)); + Register(01, typeof(CreateFoodSpell)); + Register(02, typeof(FeeblemindSpell)); + Register(03, typeof(HealSpell)); + Register(04, typeof(MagicArrowSpell)); + Register(05, typeof(NightSightSpell)); + Register(06, typeof(ReactiveArmorSpell)); + Register(07, typeof(WeakenSpell)); - // Second circle - Register( 08, typeof( Second.AgilitySpell ) ); - Register( 09, typeof( Second.CunningSpell ) ); - Register( 10, typeof( Second.CureSpell ) ); - Register( 11, typeof( Second.HarmSpell ) ); - Register( 12, typeof( Second.MagicTrapSpell ) ); - Register( 13, typeof( Second.RemoveTrapSpell ) ); - Register( 14, typeof( Second.ProtectionSpell ) ); - Register( 15, typeof( Second.StrengthSpell ) ); + // Second circle + Register(08, typeof(AgilitySpell)); + Register(09, typeof(CunningSpell)); + Register(10, typeof(CureSpell)); + Register(11, typeof(HarmSpell)); + Register(12, typeof(MagicTrapSpell)); + Register(13, typeof(RemoveTrapSpell)); + Register(14, typeof(ProtectionSpell)); + Register(15, typeof(StrengthSpell)); - // Third circle - Register( 16, typeof( Third.BlessSpell ) ); - Register( 17, typeof( Third.FireballSpell ) ); - Register( 18, typeof( Third.MagicLockSpell ) ); - Register( 19, typeof( Third.PoisonSpell ) ); - Register( 20, typeof( Third.TelekinesisSpell ) ); - Register( 21, typeof( Third.TeleportSpell ) ); - Register( 22, typeof( Third.UnlockSpell ) ); - Register( 23, typeof( Third.WallOfStoneSpell ) ); + // Third circle + Register(16, typeof(BlessSpell)); + Register(17, typeof(FireballSpell)); + Register(18, typeof(MagicLockSpell)); + Register(19, typeof(PoisonSpell)); + Register(20, typeof(TelekinesisSpell)); + Register(21, typeof(TeleportSpell)); + Register(22, typeof(UnlockSpell)); + Register(23, typeof(WallOfStoneSpell)); - // Fourth circle - Register( 24, typeof( Fourth.ArchCureSpell ) ); - Register( 25, typeof( Fourth.ArchProtectionSpell ) ); - Register( 26, typeof( Fourth.CurseSpell ) ); - Register( 27, typeof( Fourth.FireFieldSpell ) ); - Register( 28, typeof( Fourth.GreaterHealSpell ) ); - Register( 29, typeof( Fourth.LightningSpell ) ); - Register( 30, typeof( Fourth.ManaDrainSpell ) ); - Register( 31, typeof( Fourth.RecallSpell ) ); + // Fourth circle + Register(24, typeof(ArchCureSpell)); + Register(25, typeof(ArchProtectionSpell)); + Register(26, typeof(CurseSpell)); + Register(27, typeof(FireFieldSpell)); + Register(28, typeof(GreaterHealSpell)); + Register(29, typeof(LightningSpell)); + Register(30, typeof(ManaDrainSpell)); + Register(31, typeof(RecallSpell)); - // Fifth circle - Register( 32, typeof( Fifth.BladeSpiritsSpell ) ); - Register( 33, typeof( Fifth.DispelFieldSpell ) ); - Register( 34, typeof( Fifth.IncognitoSpell ) ); - Register( 35, typeof( Fifth.MagicReflectSpell ) ); - Register( 36, typeof( Fifth.MindBlastSpell ) ); - Register( 37, typeof( Fifth.ParalyzeSpell ) ); - Register( 38, typeof( Fifth.PoisonFieldSpell ) ); - Register( 39, typeof( Fifth.SummonCreatureSpell ) ); + // Fifth circle + Register(32, typeof(BladeSpiritsSpell)); + Register(33, typeof(DispelFieldSpell)); + Register(34, typeof(IncognitoSpell)); + Register(35, typeof(MagicReflectSpell)); + Register(36, typeof(MindBlastSpell)); + Register(37, typeof(ParalyzeSpell)); + Register(38, typeof(PoisonFieldSpell)); + Register(39, typeof(SummonCreatureSpell)); - // Sixth circle - Register( 40, typeof( Sixth.DispelSpell ) ); - Register( 41, typeof( Sixth.EnergyBoltSpell ) ); - Register( 42, typeof( Sixth.ExplosionSpell ) ); - Register( 43, typeof( Sixth.InvisibilitySpell ) ); - Register( 44, typeof( Sixth.MarkSpell ) ); - Register( 45, typeof( Sixth.MassCurseSpell ) ); - Register( 46, typeof( Sixth.ParalyzeFieldSpell ) ); - Register( 47, typeof( Sixth.RevealSpell ) ); + // Sixth circle + Register(40, typeof(DispelSpell)); + Register(41, typeof(EnergyBoltSpell)); + Register(42, typeof(ExplosionSpell)); + Register(43, typeof(InvisibilitySpell)); + Register(44, typeof(MarkSpell)); + Register(45, typeof(MassCurseSpell)); + Register(46, typeof(ParalyzeFieldSpell)); + Register(47, typeof(RevealSpell)); - // Seventh circle - Register( 48, typeof( Seventh.ChainLightningSpell ) ); - Register( 49, typeof( Seventh.EnergyFieldSpell ) ); - Register( 50, typeof( Seventh.FlameStrikeSpell ) ); - Register( 51, typeof( Seventh.GateTravelSpell ) ); - Register( 52, typeof( Seventh.ManaVampireSpell ) ); - Register( 53, typeof( Seventh.MassDispelSpell ) ); - Register( 54, typeof( Seventh.MeteorSwarmSpell ) ); - Register( 55, typeof( Seventh.PolymorphSpell ) ); + // Seventh circle + Register(48, typeof(ChainLightningSpell)); + Register(49, typeof(EnergyFieldSpell)); + Register(50, typeof(FlameStrikeSpell)); + Register(51, typeof(GateTravelSpell)); + Register(52, typeof(ManaVampireSpell)); + Register(53, typeof(MassDispelSpell)); + Register(54, typeof(MeteorSwarmSpell)); + Register(55, typeof(PolymorphSpell)); - // Eighth circle - Register( 56, typeof( Eighth.EarthquakeSpell ) ); - Register( 57, typeof( Eighth.EnergyVortexSpell ) ); - Register( 58, typeof( Eighth.ResurrectionSpell ) ); - Register( 59, typeof( Eighth.AirElementalSpell ) ); - Register( 60, typeof( Eighth.SummonDaemonSpell ) ); - Register( 61, typeof( Eighth.EarthElementalSpell ) ); - Register( 62, typeof( Eighth.FireElementalSpell ) ); - Register( 63, typeof( Eighth.WaterElementalSpell ) ); + // Eighth circle + Register(56, typeof(EarthquakeSpell)); + Register(57, typeof(EnergyVortexSpell)); + Register(58, typeof(ResurrectionSpell)); + Register(59, typeof(AirElementalSpell)); + Register(60, typeof(SummonDaemonSpell)); + Register(61, typeof(EarthElementalSpell)); + Register(62, typeof(FireElementalSpell)); + Register(63, typeof(WaterElementalSpell)); - if ( Core.AOS ) - { - // Necromancy spells - Register( 100, typeof( Necromancy.AnimateDeadSpell ) ); - Register( 101, typeof( Necromancy.BloodOathSpell ) ); - Register( 102, typeof( Necromancy.CorpseSkinSpell ) ); - Register( 103, typeof( Necromancy.CurseWeaponSpell ) ); - Register( 104, typeof( Necromancy.EvilOmenSpell ) ); - Register( 105, typeof( Necromancy.HorrificBeastSpell ) ); - Register( 106, typeof( Necromancy.LichFormSpell ) ); - Register( 107, typeof( Necromancy.MindRotSpell ) ); - Register( 108, typeof( Necromancy.PainSpikeSpell ) ); - Register( 109, typeof( Necromancy.PoisonStrikeSpell ) ); - Register( 110, typeof( Necromancy.StrangleSpell ) ); - Register( 111, typeof( Necromancy.SummonFamiliarSpell ) ); - Register( 112, typeof( Necromancy.VampiricEmbraceSpell ) ); - Register( 113, typeof( Necromancy.VengefulSpiritSpell ) ); - Register( 114, typeof( Necromancy.WitherSpell ) ); - Register( 115, typeof( Necromancy.WraithFormSpell ) ); + if (Core.AOS) + { + // Necromancy spells + Register(100, typeof(AnimateDeadSpell)); + Register(101, typeof(BloodOathSpell)); + Register(102, typeof(CorpseSkinSpell)); + Register(103, typeof(CurseWeaponSpell)); + Register(104, typeof(EvilOmenSpell)); + Register(105, typeof(HorrificBeastSpell)); + Register(106, typeof(LichFormSpell)); + Register(107, typeof(MindRotSpell)); + Register(108, typeof(PainSpikeSpell)); + Register(109, typeof(PoisonStrikeSpell)); + Register(110, typeof(StrangleSpell)); + Register(111, typeof(SummonFamiliarSpell)); + Register(112, typeof(VampiricEmbraceSpell)); + Register(113, typeof(VengefulSpiritSpell)); + Register(114, typeof(WitherSpell)); + Register(115, typeof(WraithFormSpell)); - if ( Core.SE ) - Register( 116, typeof( Necromancy.ExorcismSpell ) ); + if (Core.SE) + Register(116, typeof(ExorcismSpell)); - // Paladin abilities - Register( 200, typeof( Chivalry.CleanseByFireSpell ) ); - Register( 201, typeof( Chivalry.CloseWoundsSpell ) ); - Register( 202, typeof( Chivalry.ConsecrateWeaponSpell ) ); - Register( 203, typeof( Chivalry.DispelEvilSpell ) ); - Register( 204, typeof( Chivalry.DivineFurySpell ) ); - Register( 205, typeof( Chivalry.EnemyOfOneSpell ) ); - Register( 206, typeof( Chivalry.HolyLightSpell ) ); - Register( 207, typeof( Chivalry.NobleSacrificeSpell ) ); - Register( 208, typeof( Chivalry.RemoveCurseSpell ) ); - Register( 209, typeof( Chivalry.SacredJourneySpell ) ); + // Paladin abilities + Register(200, typeof(CleanseByFireSpell)); + Register(201, typeof(CloseWoundsSpell)); + Register(202, typeof(ConsecrateWeaponSpell)); + Register(203, typeof(DispelEvilSpell)); + Register(204, typeof(DivineFurySpell)); + Register(205, typeof(EnemyOfOneSpell)); + Register(206, typeof(HolyLightSpell)); + Register(207, typeof(NobleSacrificeSpell)); + Register(208, typeof(RemoveCurseSpell)); + Register(209, typeof(SacredJourneySpell)); - if ( Core.SE ) - { - // Samurai abilities - Register( 400, typeof( Bushido.HonorableExecution ) ); - Register( 401, typeof( Bushido.Confidence ) ); - Register( 402, typeof( Bushido.Evasion ) ); - Register( 403, typeof( Bushido.CounterAttack ) ); - Register( 404, typeof( Bushido.LightningStrike ) ); - Register( 405, typeof( Bushido.MomentumStrike ) ); + if (Core.SE) + { + // Samurai abilities + Register(400, typeof(HonorableExecution)); + Register(401, typeof(Confidence)); + Register(402, typeof(Evasion)); + Register(403, typeof(CounterAttack)); + Register(404, typeof(LightningStrike)); + Register(405, typeof(MomentumStrike)); - // Ninja abilities - Register( 500, typeof( Ninjitsu.FocusAttack ) ); - Register( 501, typeof( Ninjitsu.DeathStrike ) ); - Register( 502, typeof( Ninjitsu.AnimalForm ) ); - Register( 503, typeof( Ninjitsu.KiAttack ) ); - Register( 504, typeof( Ninjitsu.SurpriseAttack ) ); - Register( 505, typeof( Ninjitsu.Backstab ) ); - Register( 506, typeof( Ninjitsu.Shadowjump ) ); - Register( 507, typeof( Ninjitsu.MirrorImage ) ); - } + // Ninja abilities + Register(500, typeof(FocusAttack)); + Register(501, typeof(DeathStrike)); + Register(502, typeof(AnimalForm)); + Register(503, typeof(KiAttack)); + Register(504, typeof(SurpriseAttack)); + Register(505, typeof(Backstab)); + Register(506, typeof(Shadowjump)); + Register(507, typeof(MirrorImage)); + } - if ( Core.ML ) - { - Register( 600, typeof( Spellweaving.ArcaneCircleSpell ) ); - Register( 601, typeof( Spellweaving.GiftOfRenewalSpell ) ); - Register( 602, typeof( Spellweaving.ImmolatingWeaponSpell ) ); - Register( 603, typeof( Spellweaving.AttuneWeaponSpell ) ); - Register( 604, typeof( Spellweaving.ThunderstormSpell ) ); - Register( 605, typeof( Spellweaving.NatureFurySpell ) ); - Register( 606, typeof( Spellweaving.SummonFeySpell ) ); - Register( 607, typeof( Spellweaving.SummonFiendSpell ) ); - Register( 608, typeof( Spellweaving.ReaperFormSpell ) ); - //Register( 609, typeof( Spellweaving.WildfireSpell ) ); - Register( 610, typeof( Spellweaving.EssenceOfWindSpell ) ); - //Register( 611, typeof( Spellweaving.DryadAllureSpell ) ); - Register( 612, typeof( Spellweaving.EtherealVoyageSpell ) ); - Register( 613, typeof( Spellweaving.WordOfDeathSpell ) ); - Register( 614, typeof( Spellweaving.GiftOfLifeSpell ) ); - //Register( 615, typeof( Spellweaving.ArcaneEmpowermentSpell ) ); - } + if (Core.ML) + { + Register(600, typeof(ArcaneCircleSpell)); + Register(601, typeof(GiftOfRenewalSpell)); + Register(602, typeof(ImmolatingWeaponSpell)); + Register(603, typeof(AttuneWeaponSpell)); + Register(604, typeof(ThunderstormSpell)); + Register(605, typeof(NatureFurySpell)); + Register(606, typeof(SummonFeySpell)); + Register(607, typeof(SummonFiendSpell)); + Register(608, typeof(ReaperFormSpell)); + //Register( 609, typeof( Spellweaving.WildfireSpell ) ); + Register(610, typeof(EssenceOfWindSpell)); + //Register( 611, typeof( Spellweaving.DryadAllureSpell ) ); + Register(612, typeof(EtherealVoyageSpell)); + Register(613, typeof(WordOfDeathSpell)); + Register(614, typeof(GiftOfLifeSpell)); + //Register( 615, typeof( Spellweaving.ArcaneEmpowermentSpell ) ); + } - if ( Core.SA ) - { - // Mysticism spells - //Register( 677, typeof( Mysticism.NetherBoltSpell ) ); - //Register( 678, typeof( Mysticism.HealingStoneSpell ) ); - //Register( 679, typeof( Mysticism.PurgeMagicSpell ) ); - //Register( 680, typeof( Mysticism.EnchantSpell ) ); - //Register( 681, typeof( Mysticism.SleepSpell ) ); - Register( 682, typeof( Mysticism.EagleStrikeSpell ) ); - Register( 683, typeof( Mysticism.AnimatedWeaponSpell ) ); - Register( 684, typeof( Mysticism.StoneFormSpell ) ); - //Register( 685, typeof( Mysticism.SpellTriggerSpell ) ); - //Register( 686, typeof( Mysticism.MassSleepSpell ) ); - //Register( 687, typeof( Mysticism.CleansingWindsSpell ) ); - //Register( 688, typeof( Mysticism.BombardSpell ) ); - Register( 689, typeof( Mysticism.SpellPlagueSpell ) ); - Register( 690, typeof( Mysticism.HailStormSpell ) ); - Register( 691, typeof( Mysticism.NetherCycloneSpell ) ); - //Register( 692, typeof( Mysticism.RisingColossusSpell ) ); - } - } - } + if (Core.SA) + { + // Mysticism spells + //Register( 677, typeof( Mysticism.NetherBoltSpell ) ); + //Register( 678, typeof( Mysticism.HealingStoneSpell ) ); + //Register( 679, typeof( Mysticism.PurgeMagicSpell ) ); + //Register( 680, typeof( Mysticism.EnchantSpell ) ); + //Register( 681, typeof( Mysticism.SleepSpell ) ); + Register(682, typeof(EagleStrikeSpell)); + Register(683, typeof(AnimatedWeaponSpell)); + Register(684, typeof(StoneFormSpell)); + //Register( 685, typeof( Mysticism.SpellTriggerSpell ) ); + //Register( 686, typeof( Mysticism.MassSleepSpell ) ); + //Register( 687, typeof( Mysticism.CleansingWindsSpell ) ); + //Register( 688, typeof( Mysticism.BombardSpell ) ); + Register(689, typeof(SpellPlagueSpell)); + Register(690, typeof(HailStormSpell)); + Register(691, typeof(NetherCycloneSpell)); + //Register( 692, typeof( Mysticism.RisingColossusSpell ) ); + } + } + } - public static void Register( int spellId, Type type ) - { - SpellRegistry.Register( spellId, type ); - } - } -} + public static void Register(int spellId, Type type) + { + SpellRegistry.Register(spellId, type); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/AnimatedWeaponSpell.cs b/Scripts/Spells/Mysticism/AnimatedWeaponSpell.cs index 9e7047025..224b7ffaf 100644 --- a/Scripts/Spells/Mysticism/AnimatedWeaponSpell.cs +++ b/Scripts/Spells/Mysticism/AnimatedWeaponSpell.cs @@ -1,89 +1,89 @@ using System; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Mysticism { - public class AnimatedWeaponSpell : MysticSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Animated Weapon", "In Jux Por Ylem", - -1, - 9002, - Reagent.Bone, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.Nightshade - ); + public class AnimatedWeaponSpell : MysticSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Animated Weapon", "In Jux Por Ylem", + -1, + 9002, + Reagent.Bone, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.Nightshade + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public AnimatedWeaponSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 33.0; - public override int RequiredMana => 11; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public AnimatedWeaponSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 33.0; + public override int RequiredMana => 11; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( ( Caster.Followers + 4 ) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return; - } + public void Target(IPoint3D p) + { + if (Caster.Followers + 4 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return; + } - var map = Caster.Map; + Map map = Caster.Map; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - if ( map == null || ( Caster.Player && !map.CanSpawnMobile( p.X, p.Y, p.Z ) ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - var level = (int) ( ( GetBaseSkill( Caster ) + GetBoostSkill( Caster ) ) / 2.0 ); + if (map == null || Caster.Player && !map.CanSpawnMobile(p.X, p.Y, p.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + int level = (int)((GetBaseSkill(Caster) + GetBoostSkill(Caster)) / 2.0); - var duration = TimeSpan.FromSeconds( 10 + level ); + TimeSpan duration = TimeSpan.FromSeconds(10 + level); - var summon = new AnimatedWeapon( Caster, level ); - BaseCreature.Summon( summon, false, Caster, new Point3D( p ), 0x212, duration ); + AnimatedWeapon summon = new AnimatedWeapon(Caster, level); + BaseCreature.Summon(summon, false, Caster, new Point3D(p), 0x212, duration); - summon.PlaySound( 0x64A ); + summon.PlaySound(0x64A); - Effects.SendTargetParticles( summon, 0x3728, 10, 10, 0x13AA, (EffectLayer) 255 ); - } + Effects.SendTargetParticles(summon, 0x3728, 10, 10, 0x13AA, (EffectLayer)255); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private AnimatedWeaponSpell m_Owner; + public class InternalTarget : Target + { + private AnimatedWeaponSpell m_Owner; - public InternalTarget( AnimatedWeaponSpell owner ) - : base( 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(AnimatedWeaponSpell owner) + : base(12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/EagleStrikeSpell.cs b/Scripts/Spells/Mysticism/EagleStrikeSpell.cs index 6a882972a..39941eb52 100644 --- a/Scripts/Spells/Mysticism/EagleStrikeSpell.cs +++ b/Scripts/Spells/Mysticism/EagleStrikeSpell.cs @@ -3,86 +3,86 @@ using Server.Targeting; namespace Server.Spells.Mysticism { - public class EagleStrikeSpell : MysticSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Eagle Strike", "Kal Por Xen", - -1, - 9002, - Reagent.Bloodmoss, - Reagent.Bone, - Reagent.SpidersSilk, - Reagent.MandrakeRoot - ); + public class EagleStrikeSpell : MysticSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Eagle Strike", "Kal Por Xen", + -1, + 9002, + Reagent.Bloodmoss, + Reagent.Bone, + Reagent.SpidersSilk, + Reagent.MandrakeRoot + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.25 ); + public EagleStrikeSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 20.0; - public override int RequiredMana => 9; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.25); - public EagleStrikeSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 20.0; + public override int RequiredMana => 9; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( CheckHSequence( m ) ) - { - /* Conjures a magical eagle that assaults the Target with - * its talons, dealing energy damage. - */ + public void Target(Mobile m) + { + if (CheckHSequence(m)) + { + /* Conjures a magical eagle that assaults the Target with + * its talons, dealing energy damage. + */ - SpellHelper.Turn( Caster, m ); + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( 2, Caster, ref m ); + SpellHelper.CheckReflect(2, Caster, ref m); - Caster.MovingParticles( m, 0x407A, 7, 0, false, true, 0, 0, 0xBBE, 0xFA6, 0xFFFF, 0 ); - Caster.PlaySound( 0x2EE ); + Caster.MovingParticles(m, 0x407A, 7, 0, false, true, 0, 0, 0xBBE, 0xFA6, 0xFFFF, 0); + Caster.PlaySound(0x2EE); - Timer.DelayCall( TimeSpan.FromSeconds( 1.0 ), Damage, m ); - } + Timer.DelayCall(TimeSpan.FromSeconds(1.0), Damage, m); + } - FinishSequence(); - } + FinishSequence(); + } - private void Damage( Mobile to ) - { - if ( to == null ) - return; + private void Damage(Mobile to) + { + if (to == null) + return; - double damage = GetNewAosDamage( 19, 1, 5, to ); + double damage = GetNewAosDamage(19, 1, 5, to); - SpellHelper.Damage( this, to, damage, 0, 0, 0, 0, 100 ); + SpellHelper.Damage(this, to, damage, 0, 0, 0, 0, 100); - to.PlaySound( 0x64D ); - } + to.PlaySound(0x64D); + } - private class InternalTarget : Target - { - private EagleStrikeSpell m_Owner; + private class InternalTarget : Target + { + private EagleStrikeSpell m_Owner; - public InternalTarget( EagleStrikeSpell owner ) - : base( 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(EagleStrikeSpell owner) + : base(12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/HailStormSpell.cs b/Scripts/Spells/Mysticism/HailStormSpell.cs index a6cb032b4..1838ef98f 100644 --- a/Scripts/Spells/Mysticism/HailStormSpell.cs +++ b/Scripts/Spells/Mysticism/HailStormSpell.cs @@ -5,140 +5,142 @@ using Server.Targeting; namespace Server.Spells.Mysticism { - public class HailStormSpell : MysticSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Hail Storm", "Kal Des Ylem", - -1, - 9002, - Reagent.DragonsBlood, - Reagent.Bloodmoss, - Reagent.BlackPearl, - Reagent.MandrakeRoot - ); + public class HailStormSpell : MysticSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Hail Storm", "Kal Des Ylem", + -1, + 9002, + Reagent.DragonsBlood, + Reagent.Bloodmoss, + Reagent.BlackPearl, + Reagent.MandrakeRoot + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.25 ); + public HailStormSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 70.0; - public override int RequiredMana => 40; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.25); - public HailStormSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 70.0; + public override int RequiredMana => 40; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - /* Summons a storm of hailstones that strikes all Targets - * within a radius around the Target's Location, dealing - * cold damage. - */ + public void Target(IPoint3D p) + { + if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + /* Summons a storm of hailstones that strikes all Targets + * within a radius around the Target's Location, dealing + * cold damage. + */ - SpellHelper.Turn( Caster, p ); + SpellHelper.Turn(Caster, p); - if ( p is Item ) - p = ( (Item) p ).GetWorldLocation(); + if (p is Item) + p = ((Item)p).GetWorldLocation(); - var targets = new List(); + List targets = new List(); - var map = Caster.Map; + Map map = Caster.Map; - var pvp = false; + bool pvp = false; - if ( map != null ) - { - PlayEffect( p, Caster.Map ); + if (map != null) + { + PlayEffect(p, Caster.Map); - foreach ( var m in map.GetMobilesInRange( new Point3D( p ), 2 ) ) - { - if ( m == Caster ) - continue; + foreach (Mobile m in map.GetMobilesInRange(new Point3D(p), 2)) + { + if (m == Caster) + continue; - if ( SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) && Caster.CanSee( m ) ) - { - if ( !Caster.InLOS( m ) ) - continue; + if (SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false) && Caster.CanSee(m)) + { + if (!Caster.InLOS(m)) + continue; - targets.Add( m ); + targets.Add(m); - if ( m.Player ) - pvp = true; - } - } - } + if (m.Player) + pvp = true; + } + } + } - double damage = GetNewAosDamage( 51, 1, 5, pvp ); + double damage = GetNewAosDamage(51, 1, 5, pvp); - foreach ( var m in targets ) - { - Caster.DoHarmful( m ); - SpellHelper.Damage( this, m, damage, 0, 0, 100, 0, 0 ); - } - } + foreach (Mobile m in targets) + { + Caster.DoHarmful(m); + SpellHelper.Damage(this, m, damage, 0, 0, 100, 0, 0); + } + } - FinishSequence(); - } + FinishSequence(); + } - private static void PlayEffect( IPoint3D p, Map map ) - { - Effects.PlaySound( p, map, 0x64F ); + private static void PlayEffect(IPoint3D p, Map map) + { + Effects.PlaySound(p, map, 0x64F); - PlaySingleEffect( p, map, -1, 1, -1, 1 ); - PlaySingleEffect( p, map, -2, 0, -3, -1 ); - PlaySingleEffect( p, map, -3, -1, -1, 1 ); - PlaySingleEffect( p, map, 1, 3, -1, 1 ); - PlaySingleEffect( p, map, -1, 1, 1, 3 ); - } + PlaySingleEffect(p, map, -1, 1, -1, 1); + PlaySingleEffect(p, map, -2, 0, -3, -1); + PlaySingleEffect(p, map, -3, -1, -1, 1); + PlaySingleEffect(p, map, 1, 3, -1, 1); + PlaySingleEffect(p, map, -1, 1, 1, 3); + } - private static void PlaySingleEffect( IPoint3D p, Map map, int a, int b, int c, int d ) - { - int x = p.X, y = p.Y, z = p.Z + 18; + private static void PlaySingleEffect(IPoint3D p, Map map, int a, int b, int c, int d) + { + int x = p.X, y = p.Y, z = p.Z + 18; - SendEffectPacket( p, map, new Point3D( x + a, y + c, z ), new Point3D( x + a, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + b, y + c, z ), new Point3D( x + b, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + b, y + d, z ), new Point3D( x + b, y + d, z ) ); - SendEffectPacket( p, map, new Point3D( x + a, y + d, z ), new Point3D( x + a, y + d, z ) ); + SendEffectPacket(p, map, new Point3D(x + a, y + c, z), new Point3D(x + a, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + b, y + c, z), new Point3D(x + b, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + b, y + d, z), new Point3D(x + b, y + d, z)); + SendEffectPacket(p, map, new Point3D(x + a, y + d, z), new Point3D(x + a, y + d, z)); - SendEffectPacket( p, map, new Point3D( x + b, y + c, z ), new Point3D( x + a, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + b, y + d, z ), new Point3D( x + b, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + a, y + d, z ), new Point3D( x + b, y + d, z ) ); - SendEffectPacket( p, map, new Point3D( x + a, y + c, z ), new Point3D( x + a, y + d, z ) ); - } + SendEffectPacket(p, map, new Point3D(x + b, y + c, z), new Point3D(x + a, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + b, y + d, z), new Point3D(x + b, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + a, y + d, z), new Point3D(x + b, y + d, z)); + SendEffectPacket(p, map, new Point3D(x + a, y + c, z), new Point3D(x + a, y + d, z)); + } - private static void SendEffectPacket( IPoint3D p, Map map, Point3D orig, Point3D dest ) - { - Effects.SendPacket( p, map, new HuedEffect( EffectType.Moving, Serial.Zero, Serial.Zero, 0x36D4, orig, dest, 0, 0, false, false, 0x63, 0x4 ) ); - } + private static void SendEffectPacket(IPoint3D p, Map map, Point3D orig, Point3D dest) + { + Effects.SendPacket(p, map, + new HuedEffect(EffectType.Moving, Serial.Zero, Serial.Zero, 0x36D4, orig, dest, 0, 0, false, false, 0x63, + 0x4)); + } - private class InternalTarget : Target - { - private HailStormSpell m_Owner; + private class InternalTarget : Target + { + private HailStormSpell m_Owner; - public InternalTarget( HailStormSpell owner ) - : base( 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(HailStormSpell owner) + : base(12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - var p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/MysticSpell.cs b/Scripts/Spells/Mysticism/MysticSpell.cs index 2f9985c5d..99d084e98 100644 --- a/Scripts/Spells/Mysticism/MysticSpell.cs +++ b/Scripts/Spells/Mysticism/MysticSpell.cs @@ -2,90 +2,92 @@ namespace Server.Spells.Mysticism { - public abstract class MysticSpell : Spell - { - public abstract double RequiredSkill { get; } - public abstract int RequiredMana { get; } + public abstract class MysticSpell : Spell + { + public MysticSpell(Mobile caster, Item scroll, SpellInfo info) + : base(caster, scroll, info) + { + } - public override SkillName CastSkill => SkillName.Mysticism; + public abstract double RequiredSkill{ get; } + public abstract int RequiredMana{ get; } - /* - * As per OSI Publish 64: - * Imbuing is not the only skill associated with Mysticism now. - * Players can use EITHER their Focus skill or Imbuing skill. - * Evaluate Intelligence no longer has any effect on a Mystic’s spell power. - */ - public override double GetDamageSkill( Mobile m ) - { - return Math.Max( m.Skills[SkillName.Imbuing].Value, m.Skills[SkillName.Focus].Value ); - } + public override SkillName CastSkill => SkillName.Mysticism; - public override int GetDamageFixed( Mobile m ) - { - return Math.Max( m.Skills[SkillName.Imbuing].Fixed, m.Skills[SkillName.Focus].Fixed ); - } + /* + * As per OSI Publish 64: + * Imbuing is not the only skill associated with Mysticism now. + * Players can use EITHER their Focus skill or Imbuing skill. + * Evaluate Intelligence no longer has any effect on a Mystic’s spell power. + */ + public override double GetDamageSkill(Mobile m) + { + return Math.Max(m.Skills[SkillName.Imbuing].Value, m.Skills[SkillName.Focus].Value); + } - public MysticSpell( Mobile caster, Item scroll, SpellInfo info ) - : base( caster, scroll, info ) - { - } + public override int GetDamageFixed(Mobile m) + { + return Math.Max(m.Skills[SkillName.Imbuing].Fixed, m.Skills[SkillName.Focus].Fixed); + } - public override void GetCastSkills( out double min, out double max ) - { - // As per Mysticism page at the UO Herald Playguide - // This means that we have 25% success chance at min Required Skill + public override void GetCastSkills(out double min, out double max) + { + // As per Mysticism page at the UO Herald Playguide + // This means that we have 25% success chance at min Required Skill - min = RequiredSkill - 12.5; - max = RequiredSkill + 37.5; - } + min = RequiredSkill - 12.5; + max = RequiredSkill + 37.5; + } - public override int GetMana() - { - return RequiredMana; - } + public override int GetMana() + { + return RequiredMana; + } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - int mana = ScaleMana( RequiredMana ); + int mana = ScaleMana(RequiredMana); - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - if ( Caster.Skills[CastSkill].Value < RequiredSkill ) - { - Caster.SendLocalizedMessage( 1063013, $"{RequiredSkill.ToString("F1")}\t{CastSkill.ToString()}\t "); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - return false; - } + if (Caster.Skills[CastSkill].Value < RequiredSkill) + { + Caster.SendLocalizedMessage(1063013, + $"{RequiredSkill.ToString("F1")}\t{CastSkill.ToString()}\t "); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + return false; + } - return true; - } + return true; + } - public override void OnBeginCast() - { - base.OnBeginCast(); + public override void OnBeginCast() + { + base.OnBeginCast(); - SendCastEffect(); - } + SendCastEffect(); + } - public virtual void SendCastEffect() - { - Caster.FixedEffect( 0x37C4, 10, (int) ( GetCastDelay().TotalSeconds * 28 ), 0x66C, 3 ); - } + public virtual void SendCastEffect() + { + Caster.FixedEffect(0x37C4, 10, (int)(GetCastDelay().TotalSeconds * 28), 0x66C, 3); + } - public static double GetBaseSkill( Mobile m ) - { - return m.Skills[SkillName.Mysticism].Value; - } + public static double GetBaseSkill(Mobile m) + { + return m.Skills[SkillName.Mysticism].Value; + } - public static double GetBoostSkill( Mobile m ) - { - return Math.Max( m.Skills[SkillName.Imbuing].Value, m.Skills[SkillName.Focus].Value ); - } - } -} + public static double GetBoostSkill(Mobile m) + { + return Math.Max(m.Skills[SkillName.Imbuing].Value, m.Skills[SkillName.Focus].Value); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/NetherCycloneSpell.cs b/Scripts/Spells/Mysticism/NetherCycloneSpell.cs index dafc215a0..ac63b8e72 100644 --- a/Scripts/Spells/Mysticism/NetherCycloneSpell.cs +++ b/Scripts/Spells/Mysticism/NetherCycloneSpell.cs @@ -5,151 +5,153 @@ using Server.Targeting; namespace Server.Spells.Mysticism { - public class NetherCycloneSpell : MysticSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Nether Cyclone", "Grav Hur", - -1, - 9002, - Reagent.MandrakeRoot, - Reagent.Nightshade, - Reagent.SulfurousAsh, - Reagent.Bloodmoss - ); + public class NetherCycloneSpell : MysticSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Nether Cyclone", "Grav Hur", + -1, + 9002, + Reagent.MandrakeRoot, + Reagent.Nightshade, + Reagent.SulfurousAsh, + Reagent.Bloodmoss + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.5 ); + public NetherCycloneSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 83.0; - public override int RequiredMana => 50; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.5); - public NetherCycloneSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 83.0; + public override int RequiredMana => 50; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - /* Summons a gale of lethal winds that strikes all Targets within a radius around - * the Target's Location, dealing chaos damage. In addition to inflicting damage, - * each Target of the Nether Cyclone temporarily loses a percentage of mana and - * stamina. The effectiveness of the Nether Cyclone is determined by a comparison - * between the Caster's Mysticism and either Focus or Imbuing (whichever is greater) - * skills and the Resisting Spells skill of the Target. - */ + public void Target(IPoint3D p) + { + if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + /* Summons a gale of lethal winds that strikes all Targets within a radius around + * the Target's Location, dealing chaos damage. In addition to inflicting damage, + * each Target of the Nether Cyclone temporarily loses a percentage of mana and + * stamina. The effectiveness of the Nether Cyclone is determined by a comparison + * between the Caster's Mysticism and either Focus or Imbuing (whichever is greater) + * skills and the Resisting Spells skill of the Target. + */ - SpellHelper.Turn( Caster, p ); + SpellHelper.Turn(Caster, p); - if ( p is Item ) - p = ( (Item) p ).GetWorldLocation(); + if (p is Item) + p = ((Item)p).GetWorldLocation(); - var targets = new List(); + List targets = new List(); - var map = Caster.Map; + Map map = Caster.Map; - var pvp = false; + bool pvp = false; - if ( map != null ) - { - PlayEffect( p, Caster.Map ); + if (map != null) + { + PlayEffect(p, Caster.Map); - foreach ( var m in map.GetMobilesInRange( new Point3D( p ), 2 ) ) - { - if ( m == Caster ) - continue; + foreach (Mobile m in map.GetMobilesInRange(new Point3D(p), 2)) + { + if (m == Caster) + continue; - if ( SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) && Caster.CanSee( m ) ) - { - if ( !Caster.InLOS( m ) ) - continue; + if (SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false) && Caster.CanSee(m)) + { + if (!Caster.InLOS(m)) + continue; - targets.Add( m ); + targets.Add(m); - if ( m.Player ) - pvp = true; - } - } - } + if (m.Player) + pvp = true; + } + } + } - var damage = GetNewAosDamage( 51, 1, 5, pvp ); - var reduction = ( GetBaseSkill( Caster ) + GetBoostSkill( Caster ) ) / 1200.0; + int damage = GetNewAosDamage(51, 1, 5, pvp); + double reduction = (GetBaseSkill(Caster) + GetBoostSkill(Caster)) / 1200.0; - foreach ( var m in targets ) - { - Caster.DoHarmful( m ); + foreach (Mobile m in targets) + { + Caster.DoHarmful(m); - var types = new int[4]; - types[Utility.Random( types.Length )] = 100; + int[] types = new int[4]; + types[Utility.Random(types.Length)] = 100; - SpellHelper.Damage( this, m, damage, 0, types[0], types[1], types[2], types[3] ); + SpellHelper.Damage(this, m, damage, 0, types[0], types[1], types[2], types[3]); - var resistedReduction = reduction - ( m.Skills[SkillName.MagicResist].Value / 800.0 ); + double resistedReduction = reduction - m.Skills[SkillName.MagicResist].Value / 800.0; - m.Stam -= (int) ( m.StamMax * resistedReduction ); - m.Mana -= (int) ( m.ManaMax * resistedReduction ); - } - } + m.Stam -= (int)(m.StamMax * resistedReduction); + m.Mana -= (int)(m.ManaMax * resistedReduction); + } + } - FinishSequence(); - } + FinishSequence(); + } - private static void PlayEffect( IPoint3D p, Map map ) - { - Effects.PlaySound( p, map, 0x64F ); + private static void PlayEffect(IPoint3D p, Map map) + { + Effects.PlaySound(p, map, 0x64F); - PlaySingleEffect( p, map, -1, 1, -1, 1 ); - PlaySingleEffect( p, map, -2, 0, -3, -1 ); - PlaySingleEffect( p, map, -3, -1, -1, 1 ); - PlaySingleEffect( p, map, 1, 3, -1, 1 ); - PlaySingleEffect( p, map, -1, 1, 1, 3 ); - } + PlaySingleEffect(p, map, -1, 1, -1, 1); + PlaySingleEffect(p, map, -2, 0, -3, -1); + PlaySingleEffect(p, map, -3, -1, -1, 1); + PlaySingleEffect(p, map, 1, 3, -1, 1); + PlaySingleEffect(p, map, -1, 1, 1, 3); + } - private static void PlaySingleEffect( IPoint3D p, Map map, int a, int b, int c, int d ) - { - int x = p.X, y = p.Y, z = p.Z + 18; + private static void PlaySingleEffect(IPoint3D p, Map map, int a, int b, int c, int d) + { + int x = p.X, y = p.Y, z = p.Z + 18; - SendEffectPacket( p, map, new Point3D( x + a, y + c, z ), new Point3D( x + a, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + b, y + c, z ), new Point3D( x + b, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + b, y + d, z ), new Point3D( x + b, y + d, z ) ); - SendEffectPacket( p, map, new Point3D( x + a, y + d, z ), new Point3D( x + a, y + d, z ) ); + SendEffectPacket(p, map, new Point3D(x + a, y + c, z), new Point3D(x + a, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + b, y + c, z), new Point3D(x + b, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + b, y + d, z), new Point3D(x + b, y + d, z)); + SendEffectPacket(p, map, new Point3D(x + a, y + d, z), new Point3D(x + a, y + d, z)); - SendEffectPacket( p, map, new Point3D( x + b, y + c, z ), new Point3D( x + a, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + b, y + d, z ), new Point3D( x + b, y + c, z ) ); - SendEffectPacket( p, map, new Point3D( x + a, y + d, z ), new Point3D( x + b, y + d, z ) ); - SendEffectPacket( p, map, new Point3D( x + a, y + c, z ), new Point3D( x + a, y + d, z ) ); - } + SendEffectPacket(p, map, new Point3D(x + b, y + c, z), new Point3D(x + a, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + b, y + d, z), new Point3D(x + b, y + c, z)); + SendEffectPacket(p, map, new Point3D(x + a, y + d, z), new Point3D(x + b, y + d, z)); + SendEffectPacket(p, map, new Point3D(x + a, y + c, z), new Point3D(x + a, y + d, z)); + } - private static void SendEffectPacket( IPoint3D p, Map map, Point3D orig, Point3D dest ) - { - Effects.SendPacket( p, map, new HuedEffect( EffectType.Moving, Serial.Zero, Serial.Zero, 0x375A, orig, dest, 0, 0, false, false, 0x49A, 0x4 ) ); - } + private static void SendEffectPacket(IPoint3D p, Map map, Point3D orig, Point3D dest) + { + Effects.SendPacket(p, map, + new HuedEffect(EffectType.Moving, Serial.Zero, Serial.Zero, 0x375A, orig, dest, 0, 0, false, false, 0x49A, + 0x4)); + } - private class InternalTarget : Target - { - private NetherCycloneSpell m_Owner; + private class InternalTarget : Target + { + private NetherCycloneSpell m_Owner; - public InternalTarget( NetherCycloneSpell owner ) - : base( 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(NetherCycloneSpell owner) + : base(12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D p ) - m_Owner.Target( p ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D p) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/SpellPlagueSpell.cs b/Scripts/Spells/Mysticism/SpellPlagueSpell.cs index 37c66c86b..397b167d1 100644 --- a/Scripts/Spells/Mysticism/SpellPlagueSpell.cs +++ b/Scripts/Spells/Mysticism/SpellPlagueSpell.cs @@ -4,231 +4,232 @@ using Server.Targeting; namespace Server.Spells.Mysticism { - public class SpellPlagueSpell : MysticSpell - { - public static void Initialize() - { - EventSink.PlayerDeath += OnPlayerDeath; - } + public class SpellPlagueSpell : MysticSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Spell Plague", "Vas Rel Jux Ort", + -1, + 9002, + Reagent.DaemonBone, + Reagent.DragonsBlood, + Reagent.Nightshade, + Reagent.SulfurousAsh + ); - private static SpellInfo m_Info = new SpellInfo( - "Spell Plague", "Vas Rel Jux Ort", - -1, - 9002, - Reagent.DaemonBone, - Reagent.DragonsBlood, - Reagent.Nightshade, - Reagent.SulfurousAsh - ); + private static Dictionary m_Table = new Dictionary(); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.25 ); + public SpellPlagueSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 70.0; - public override int RequiredMana => 40; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.25); - public SpellPlagueSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 70.0; + public override int RequiredMana => 40; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public static void Initialize() + { + EventSink.PlayerDeath += OnPlayerDeath; + } - public void Target( Mobile targeted ) - { - if ( !Caster.CanSee( targeted ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( targeted ) ) - { - SpellHelper.Turn( Caster, targeted ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - SpellHelper.CheckReflect( 6, Caster, ref targeted ); + public void Target(Mobile targeted) + { + if (!Caster.CanSee(targeted)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(targeted)) + { + SpellHelper.Turn(Caster, targeted); - /* The target is hit with an explosion of chaos damage and then inflicted - * with the spell plague curse. Each time the target is damaged while under - * the effect of the spell plague, they may suffer an explosion of chaos - * damage. The initial chance to trigger the explosion starts at 90% and - * reduces by 30% every time an explosion occurs. Once the target is - * afflicted by 3 explosions or 8 seconds have passed, that spell plague - * is removed from the target. Spell Plague will stack with other spell - * plagues so that they are applied one after the other. - */ + SpellHelper.CheckReflect(6, Caster, ref targeted); - VisualEffect( targeted ); + /* The target is hit with an explosion of chaos damage and then inflicted + * with the spell plague curse. Each time the target is damaged while under + * the effect of the spell plague, they may suffer an explosion of chaos + * damage. The initial chance to trigger the explosion starts at 90% and + * reduces by 30% every time an explosion occurs. Once the target is + * afflicted by 3 explosions or 8 seconds have passed, that spell plague + * is removed from the target. Spell Plague will stack with other spell + * plagues so that they are applied one after the other. + */ - var damage = GetNewAosDamage( 33, 1, 5, targeted ); + VisualEffect(targeted); - var types = new int[4]; - types[Utility.Random( types.Length )] = 100; + int damage = GetNewAosDamage(33, 1, 5, targeted); - SpellHelper.Damage( this, targeted, damage, 0, types[0], types[1], types[2], types[3] ); + int[] types = new int[4]; + types[Utility.Random(types.Length)] = 100; - var context = new SpellPlagueContext( this, targeted ); + SpellHelper.Damage(this, targeted, damage, 0, types[0], types[1], types[2], types[3]); - if ( m_Table.ContainsKey( targeted ) ) - { - var oldContext = m_Table[targeted]; - oldContext.SetNext( context ); - } - else - { - m_Table[targeted] = context; - context.Start(); - } - } + SpellPlagueContext context = new SpellPlagueContext(this, targeted); - FinishSequence(); - } + if (m_Table.ContainsKey(targeted)) + { + SpellPlagueContext oldContext = m_Table[targeted]; + oldContext.SetNext(context); + } + else + { + m_Table[targeted] = context; + context.Start(); + } + } - public static bool UnderEffect( Mobile m ) - { - return m_Table.ContainsKey( m ); - } + FinishSequence(); + } - public static void RemoveEffect( Mobile m ) - { - if ( !m_Table.ContainsKey( m ) ) - return; + public static bool UnderEffect(Mobile m) + { + return m_Table.ContainsKey(m); + } - var context = m_Table[m]; + public static void RemoveEffect(Mobile m) + { + if (!m_Table.ContainsKey(m)) + return; - context.EndPlague( false ); - } + SpellPlagueContext context = m_Table[m]; - public static void CheckPlague( Mobile m ) - { - if ( !m_Table.ContainsKey( m ) ) - return; + context.EndPlague(false); + } - var context = m_Table[m]; + public static void CheckPlague(Mobile m) + { + if (!m_Table.ContainsKey(m)) + return; - context.OnDamage(); - } + SpellPlagueContext context = m_Table[m]; - private static void OnPlayerDeath( PlayerDeathEventArgs e ) - { - RemoveEffect( e.Mobile ); - } + context.OnDamage(); + } - private static Dictionary m_Table = new Dictionary(); + private static void OnPlayerDeath(PlayerDeathEventArgs e) + { + RemoveEffect(e.Mobile); + } - protected void VisualEffect( Mobile to ) - { - to.PlaySound( 0x658 ); + protected void VisualEffect(Mobile to) + { + to.PlaySound(0x658); - to.FixedParticles( 0x3728, 1, 13, 0x26B8, 0x47E, 7, EffectLayer.Head, 0 ); - to.FixedParticles( 0x3779, 1, 15, 0x251E, 0x43, 7, EffectLayer.Head, 0 ); - } + to.FixedParticles(0x3728, 1, 13, 0x26B8, 0x47E, 7, EffectLayer.Head, 0); + to.FixedParticles(0x3779, 1, 15, 0x251E, 0x43, 7, EffectLayer.Head, 0); + } - private class SpellPlagueContext - { - private SpellPlagueSpell m_Owner; - private Mobile m_Target; - private DateTime m_LastExploded; - private int m_Explosions; - private Timer m_Timer; - private SpellPlagueContext m_Next; + private class SpellPlagueContext + { + private int m_Explosions; + private DateTime m_LastExploded; + private SpellPlagueContext m_Next; + private SpellPlagueSpell m_Owner; + private Mobile m_Target; + private Timer m_Timer; - public SpellPlagueContext( SpellPlagueSpell owner, Mobile target ) - { - m_Owner = owner; - m_Target = target; - } + public SpellPlagueContext(SpellPlagueSpell owner, Mobile target) + { + m_Owner = owner; + m_Target = target; + } - public void SetNext( SpellPlagueContext context ) - { - if ( m_Next == null ) - m_Next = context; - else - m_Next.SetNext( context ); - } + public void SetNext(SpellPlagueContext context) + { + if (m_Next == null) + m_Next = context; + else + m_Next.SetNext(context); + } - public void Start() - { - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 8.0 ), EndPlague ); - m_Timer.Start(); + public void Start() + { + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(8.0), EndPlague); + m_Timer.Start(); - BuffInfo.AddBuff( m_Target, new BuffInfo( BuffIcon.SpellPlague, 1031690, 1080167, TimeSpan.FromSeconds( 8.5 ), m_Target ) ); - } + BuffInfo.AddBuff(m_Target, + new BuffInfo(BuffIcon.SpellPlague, 1031690, 1080167, TimeSpan.FromSeconds(8.5), m_Target)); + } - public void OnDamage() - { - if ( DateTime.Now > ( m_LastExploded + TimeSpan.FromSeconds( 2.0 ) ) ) - { - var exploChance = 90 - ( m_Explosions * 30 ); + public void OnDamage() + { + if (DateTime.Now > m_LastExploded + TimeSpan.FromSeconds(2.0)) + { + int exploChance = 90 - m_Explosions * 30; - var resist = m_Target.Skills[SkillName.MagicResist].Value; + double resist = m_Target.Skills[SkillName.MagicResist].Value; - if ( resist >= 70 ) - exploChance -= (int) ( ( resist - 70.0 ) * 3.0 / 10.0 ); + if (resist >= 70) + exploChance -= (int)((resist - 70.0) * 3.0 / 10.0); - if ( exploChance > Utility.Random( 100 ) ) - { - m_Owner.VisualEffect( m_Target ); + if (exploChance > Utility.Random(100)) + { + m_Owner.VisualEffect(m_Target); - var damage = m_Owner.GetNewAosDamage( 15 + ( m_Explosions * 3 ), 1, 5, m_Target ); + int damage = m_Owner.GetNewAosDamage(15 + m_Explosions * 3, 1, 5, m_Target); - m_Explosions++; - m_LastExploded = DateTime.Now; + m_Explosions++; + m_LastExploded = DateTime.Now; - var types = new int[4]; - types[Utility.Random( types.Length )] = 100; + int[] types = new int[4]; + types[Utility.Random(types.Length)] = 100; - SpellHelper.Damage( m_Owner, m_Target, damage, 0, types[0], types[1], types[2], types[3] ); + SpellHelper.Damage(m_Owner, m_Target, damage, 0, types[0], types[1], types[2], types[3]); - if ( m_Explosions >= 3 ) - EndPlague(); - } - } - } + if (m_Explosions >= 3) + EndPlague(); + } + } + } - private void EndPlague() - { - EndPlague( true ); - } + private void EndPlague() + { + EndPlague(true); + } - public void EndPlague( bool restart ) - { - m_Timer?.Stop(); + public void EndPlague(bool restart) + { + m_Timer?.Stop(); - if ( restart && m_Next != null ) - { - m_Table[m_Target] = m_Next; - m_Next.Start(); - } - else - { - m_Table.Remove( m_Target ); + if (restart && m_Next != null) + { + m_Table[m_Target] = m_Next; + m_Next.Start(); + } + else + { + m_Table.Remove(m_Target); - BuffInfo.RemoveBuff( m_Target, BuffIcon.SpellPlague ); - } - } - } + BuffInfo.RemoveBuff(m_Target, BuffIcon.SpellPlague); + } + } + } - private class InternalTarget : Target - { - private SpellPlagueSpell m_Owner; + private class InternalTarget : Target + { + private SpellPlagueSpell m_Owner; - public InternalTarget( SpellPlagueSpell owner ) - : base( 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(SpellPlagueSpell owner) + : base(12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Mysticism/StoneFormSpell.cs b/Scripts/Spells/Mysticism/StoneFormSpell.cs index 175bb6c75..4b68f11d8 100644 --- a/Scripts/Spells/Mysticism/StoneFormSpell.cs +++ b/Scripts/Spells/Mysticism/StoneFormSpell.cs @@ -1,162 +1,167 @@ using System; using System.Collections; using System.Collections.Generic; +using Server.Factions; +using Server.Mobiles; using Server.Spells.Fifth; +using Server.Spells.Ninjitsu; using Server.Spells.Seventh; namespace Server.Spells.Mysticism { - public class StoneFormSpell : MysticSpell - { - public static void Initialize() - { - EventSink.PlayerDeath += OnPlayerDeath; - } + public class StoneFormSpell : MysticSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Stone Form", "In Rel Ylem", + -1, + 9002, + Reagent.Bloodmoss, + Reagent.FertileDirt, + Reagent.Garlic + ); - private static SpellInfo m_Info = new SpellInfo( - "Stone Form", "In Rel Ylem", - -1, - 9002, - Reagent.Bloodmoss, - Reagent.FertileDirt, - Reagent.Garlic - ); + private static Hashtable m_Table = new Hashtable(); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public StoneFormSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 33.0; - public override int RequiredMana => 11; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - private static Hashtable m_Table = new Hashtable(); + public override double RequiredSkill => 33.0; + public override int RequiredMana => 11; - public static bool UnderEffect( Mobile m ) - { - return m_Table.Contains( m ); - } + public static void Initialize() + { + EventSink.PlayerDeath += OnPlayerDeath; + } - public StoneFormSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public static bool UnderEffect(Mobile m) + { + return m_Table.Contains(m); + } - public override bool CheckCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } + public override bool CheckCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } - if ( !Caster.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - Caster.SendLocalizedMessage( 1061628 ); // You can't do that while polymorphed. - return false; - } - if ( Ninjitsu.AnimalForm.UnderTransformation( Caster ) ) - { - Caster.SendLocalizedMessage( 1063218 ); // You cannot use that ability in this form. - return false; - } - if ( Caster.Flying ) - { - Caster.SendLocalizedMessage( 1113415 ); // You cannot use this ability while flying. - return false; - } + if (!Caster.CanBeginAction(typeof(PolymorphSpell))) + { + Caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + return false; + } - return base.CheckCast(); - } + if (AnimalForm.UnderTransformation(Caster)) + { + Caster.SendLocalizedMessage(1063218); // You cannot use that ability in this form. + return false; + } - public override void OnCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( !Caster.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - Caster.SendLocalizedMessage( 1061628 ); // You can't do that while polymorphed. - } - else if ( !Caster.CanBeginAction( typeof( IncognitoSpell ) ) || ( Caster.IsBodyMod && !UnderEffect( Caster ) ) ) - { - Caster.SendLocalizedMessage( 1063218 ); // You cannot use that ability in this form. - } - else if ( CheckSequence() ) - { - if ( UnderEffect( Caster ) ) - { - RemoveEffects( Caster ); + if (Caster.Flying) + { + Caster.SendLocalizedMessage(1113415); // You cannot use this ability while flying. + return false; + } - Caster.PlaySound( 0xFA ); - Caster.Delta( MobileDelta.Resistances ); - } - else - { - var mount = Caster.Mount; + return base.CheckCast(); + } - if ( mount != null ) - mount.Rider = null; + public override void OnCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (!Caster.CanBeginAction(typeof(PolymorphSpell))) + { + Caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + } + else if (!Caster.CanBeginAction(typeof(IncognitoSpell)) || Caster.IsBodyMod && !UnderEffect(Caster)) + { + Caster.SendLocalizedMessage(1063218); // You cannot use that ability in this form. + } + else if (CheckSequence()) + { + if (UnderEffect(Caster)) + { + RemoveEffects(Caster); - Caster.BodyMod = 0x2C1; - Caster.HueMod = 0; + Caster.PlaySound(0xFA); + Caster.Delta(MobileDelta.Resistances); + } + else + { + IMount mount = Caster.Mount; - var offset = (int) ( ( GetBaseSkill( Caster ) + GetBoostSkill( Caster ) ) / 24.0 ); + if (mount != null) + mount.Rider = null; - var mods = new List - { - new ResistanceMod( ResistanceType.Physical, offset ), - new ResistanceMod( ResistanceType.Fire, offset ), - new ResistanceMod( ResistanceType.Cold, offset ), - new ResistanceMod( ResistanceType.Poison, offset ), - new ResistanceMod( ResistanceType.Energy, offset ) - }; + Caster.BodyMod = 0x2C1; + Caster.HueMod = 0; - foreach ( var mod in mods ) - Caster.AddResistanceMod( mod ); + int offset = (int)((GetBaseSkill(Caster) + GetBoostSkill(Caster)) / 24.0); - m_Table[Caster] = mods; + List mods = new List + { + new ResistanceMod(ResistanceType.Physical, offset), + new ResistanceMod(ResistanceType.Fire, offset), + new ResistanceMod(ResistanceType.Cold, offset), + new ResistanceMod(ResistanceType.Poison, offset), + new ResistanceMod(ResistanceType.Energy, offset) + }; - Caster.PlaySound( 0x65A ); - Caster.Delta( MobileDelta.Resistances ); + foreach (ResistanceMod mod in mods) + Caster.AddResistanceMod(mod); - BuffInfo.AddBuff( Caster, new BuffInfo( BuffIcon.StoneForm, 1080145, 1080146, - $"-10\t-2\t{offset}\t{GetResistCapBonus(Caster)}\t{GetDIBonus(Caster)}", false ) ); - } - } + m_Table[Caster] = mods; - FinishSequence(); - } + Caster.PlaySound(0x65A); + Caster.Delta(MobileDelta.Resistances); - public static int GetDIBonus( Mobile m ) - { - return (int) ( ( GetBaseSkill( m ) + GetBoostSkill( m ) ) / 12.0 ); - } + BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.StoneForm, 1080145, 1080146, + $"-10\t-2\t{offset}\t{GetResistCapBonus(Caster)}\t{GetDIBonus(Caster)}", false)); + } + } - public static int GetResistCapBonus( Mobile m ) - { - return (int) ( ( GetBaseSkill( m ) + GetBoostSkill( m ) ) / 48.0 ); - } + FinishSequence(); + } - public static void RemoveEffects( Mobile m ) - { - var mods = (List) m_Table[m]; + public static int GetDIBonus(Mobile m) + { + return (int)((GetBaseSkill(m) + GetBoostSkill(m)) / 12.0); + } - foreach ( var mod in mods ) - m.RemoveResistanceMod( mod ); + public static int GetResistCapBonus(Mobile m) + { + return (int)((GetBaseSkill(m) + GetBoostSkill(m)) / 48.0); + } - m.BodyMod = 0; - m.HueMod = -1; + public static void RemoveEffects(Mobile m) + { + List mods = (List)m_Table[m]; - m_Table.Remove( m ); + foreach (ResistanceMod mod in mods) + m.RemoveResistanceMod(mod); - BuffInfo.RemoveBuff( m, BuffIcon.StoneForm ); - } + m.BodyMod = 0; + m.HueMod = -1; - private static void OnPlayerDeath( PlayerDeathEventArgs e ) - { - var m = e.Mobile; + m_Table.Remove(m); - if ( UnderEffect( m ) ) - RemoveEffects( m ); - } - } -} + BuffInfo.RemoveBuff(m, BuffIcon.StoneForm); + } + + private static void OnPlayerDeath(PlayerDeathEventArgs e) + { + Mobile m = e.Mobile; + + if (UnderEffect(m)) + RemoveEffects(m); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/AnimateDeadSpell.cs b/Scripts/Spells/Necromancy/AnimateDeadSpell.cs index 3093992a3..3b18ea952 100644 --- a/Scripts/Spells/Necromancy/AnimateDeadSpell.cs +++ b/Scripts/Spells/Necromancy/AnimateDeadSpell.cs @@ -1,411 +1,419 @@ using System; using System.Collections.Generic; -using Server.Mobiles; -using Server.Targeting; -using Server.Items; using Server.Engines.Quests; using Server.Engines.Quests.Necro; +using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Necromancy { - public class AnimateDeadSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Animate Dead", "Uus Corp", - 203, - 9031, - Reagent.GraveDust, - Reagent.DaemonBlood - ); - - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); - - public override double RequiredSkill => 40.0; - public override int RequiredMana => 23; - - public AnimateDeadSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } - - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - Caster.SendLocalizedMessage( 1061083 ); // Animate what corpse? - } - - private class CreatureGroup - { - public Type[] m_Types; - public SummonEntry[] m_Entries; - - public CreatureGroup( Type[] types, SummonEntry[] entries ) - { - m_Types = types; - m_Entries = entries; - } - } - - private class SummonEntry - { - public Type[] m_ToSummon; - public int m_Requirement; - - public SummonEntry( int requirement, params Type[] toSummon ) - { - m_ToSummon = toSummon; - m_Requirement = requirement; - } - } - - private static CreatureGroup FindGroup( Type type ) - { - for ( int i = 0; i < m_Groups.Length; ++i ) - { - CreatureGroup group = m_Groups[i]; - Type[] types = group.m_Types; - - bool contains = ( types.Length == 0 ); - - for ( int j = 0; !contains && j < types.Length; ++j ) - contains = types[j].IsAssignableFrom( type ); - - if ( contains ) - return group; - } - - return null; - } - - private static CreatureGroup[] m_Groups = { - // Undead group--empty - new CreatureGroup( SlayerGroup.GetEntryByName( SlayerName.Silver ).Types, new SummonEntry[0] ), - // Insects - new CreatureGroup( new[] - { - typeof( DreadSpider ), typeof( FrostSpider ), typeof( GiantSpider ), typeof( GiantBlackWidow ), - typeof( BlackSolenInfiltratorQueen ), typeof( BlackSolenInfiltratorWarrior ), - typeof( BlackSolenQueen ), typeof( BlackSolenWarrior ), typeof( BlackSolenWorker ), - typeof( RedSolenInfiltratorQueen ), typeof( RedSolenInfiltratorWarrior ), - typeof( RedSolenQueen ), typeof( RedSolenWarrior ), typeof( RedSolenWorker ), - typeof( TerathanAvenger ), typeof( TerathanDrone ), typeof( TerathanMatriarch ), - typeof( TerathanWarrior ) - // TODO: Giant beetle? Ant lion? Ophidians? - }, - new[] - { - new SummonEntry( 0, typeof( MoundOfMaggots ) ) - } ), - // Mounts - new CreatureGroup( new[] - { - typeof( Horse ), typeof( Nightmare ), typeof( FireSteed ), - typeof( Kirin ), typeof( Unicorn ) - }, new[] - { - new SummonEntry( 10000, typeof( HellSteed ) ), - new SummonEntry( 0, typeof( SkeletalMount ) ) - } ), - // Elementals - new CreatureGroup( new[] - { - typeof( BloodElemental ), typeof( EarthElemental ), typeof( SummonedEarthElemental ), - typeof( AgapiteElemental ), typeof( BronzeElemental ), typeof( CopperElemental ), - typeof( DullCopperElemental ), typeof( GoldenElemental ), typeof( ShadowIronElemental ), - typeof( ValoriteElemental ), typeof( VeriteElemental ), typeof( PoisonElemental ), - typeof( FireElemental ), typeof( SummonedFireElemental ), typeof( SnowElemental ), - typeof( AirElemental ), typeof( SummonedAirElemental ), typeof( WaterElemental ), - typeof( SummonedAirElemental ), typeof ( AcidElemental ) - }, new[] - { - new SummonEntry( 5000, typeof( WailingBanshee ) ), - new SummonEntry( 0, typeof( Wraith ) ) - } ), - // Dragons - new CreatureGroup( new[] - { - typeof( AncientWyrm ), typeof( Dragon ), typeof( GreaterDragon ), typeof( SerpentineDragon ), - typeof( ShadowWyrm ), typeof( SkeletalDragon ), typeof( WhiteWyrm ), - typeof( Drake ), typeof( Wyvern ), typeof( LesserHiryu ), typeof( Hiryu ) - }, new[] - { - new SummonEntry( 18000, typeof( SkeletalDragon ) ), - new SummonEntry( 10000, typeof( FleshGolem ) ), - new SummonEntry( 5000, typeof( Lich ) ), - new SummonEntry( 3000, typeof( SkeletalKnight ), typeof( BoneKnight ) ), - new SummonEntry( 2000, typeof( Mummy ) ), - new SummonEntry( 1000, typeof( SkeletalMage ), typeof( BoneMagi ) ), - new SummonEntry( 0, typeof( PatchworkSkeleton ) ) - } ), - // Default group - new CreatureGroup( new Type[0], new[] - { - new SummonEntry( 18000, typeof( LichLord ) ), - new SummonEntry( 10000, typeof( FleshGolem ) ), - new SummonEntry( 5000, typeof( Lich ) ), - new SummonEntry( 3000, typeof( SkeletalKnight ), typeof( BoneKnight ) ), - new SummonEntry( 2000, typeof( Mummy ) ), - new SummonEntry( 1000, typeof( SkeletalMage ), typeof( BoneMagi ) ), - new SummonEntry( 0, typeof( PatchworkSkeleton ) ) - } ), - }; - - public void Target( object obj ) - { - MaabusCoffinComponent comp = obj as MaabusCoffinComponent; - - MaabusCoffin addon = comp?.Addon as MaabusCoffin; - - if ( addon != null ) - { - PlayerMobile pm = Caster as PlayerMobile; - - QuestSystem qs = pm?.Quest; - - if ( qs is DarkTidesQuest ) - { - QuestObjective objective = qs.FindObjective( typeof( AnimateMaabusCorpseObjective ) ); - - if ( objective != null && !objective.Completed ) - { - addon.Awake( Caster ); - objective.Complete(); - } - } - - return; - } - - Corpse c = obj as Corpse; - - if ( c == null ) - { - Caster.SendLocalizedMessage( 1061084 ); // You cannot animate that. - } - else - { - Type type = null; - - if ( c.Owner != null ) - { - type = c.Owner.GetType(); - } - - if ( c.ItemID != 0x2006 || c.Animated || type == typeof( PlayerMobile ) || type == null || ( c.Owner != null && c.Owner.Fame < 100 ) || ( c.Owner is BaseCreature && ( ( ( BaseCreature )c.Owner ).Summoned || ( ( BaseCreature )c.Owner ).IsBonded ) ) ) - { - Caster.SendLocalizedMessage( 1061085 ); // There's not enough life force there to animate. - } - else - { - CreatureGroup group = FindGroup( type ); - - if ( group != null ) - { - if ( group.m_Entries.Length == 0 || type == typeof( DemonKnight ) ) - { - Caster.SendLocalizedMessage( 1061086 ); // You cannot animate undead remains. - } - else if ( CheckSequence() ) - { - Point3D p = c.GetWorldLocation(); - Map map = c.Map; - - if ( map != null ) - { - Effects.PlaySound( p, map, 0x1FB ); - Effects.SendLocationParticles( EffectItem.Create( p, map, EffectItem.DefaultDuration ), 0x3789, 1, 40, 0x3F, 3, 9907, 0 ); - - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), new TimerStateCallback( SummonDelay_Callback ), new object[] { Caster, c, p, map, group } ); - } - } - } - } - } - - FinishSequence(); - } - - private static Dictionary> m_Table = new Dictionary>(); - - public static void Unregister( Mobile master, Mobile summoned ) - { - if ( master == null ) - return; - - m_Table.TryGetValue( master, out List list ); - - if ( list == null ) - return; + public class AnimateDeadSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Animate Dead", "Uus Corp", + 203, + 9031, + Reagent.GraveDust, + Reagent.DaemonBlood + ); + + private static CreatureGroup[] m_Groups = + { + // Undead group--empty + new CreatureGroup(SlayerGroup.GetEntryByName(SlayerName.Silver).Types, new SummonEntry[0]), + // Insects + new CreatureGroup(new[] + { + typeof(DreadSpider), typeof(FrostSpider), typeof(GiantSpider), typeof(GiantBlackWidow), + typeof(BlackSolenInfiltratorQueen), typeof(BlackSolenInfiltratorWarrior), + typeof(BlackSolenQueen), typeof(BlackSolenWarrior), typeof(BlackSolenWorker), + typeof(RedSolenInfiltratorQueen), typeof(RedSolenInfiltratorWarrior), + typeof(RedSolenQueen), typeof(RedSolenWarrior), typeof(RedSolenWorker), + typeof(TerathanAvenger), typeof(TerathanDrone), typeof(TerathanMatriarch), + typeof(TerathanWarrior) + // TODO: Giant beetle? Ant lion? Ophidians? + }, + new[] + { + new SummonEntry(0, typeof(MoundOfMaggots)) + }), + // Mounts + new CreatureGroup(new[] + { + typeof(Horse), typeof(Nightmare), typeof(FireSteed), + typeof(Kirin), typeof(Unicorn) + }, new[] + { + new SummonEntry(10000, typeof(HellSteed)), + new SummonEntry(0, typeof(SkeletalMount)) + }), + // Elementals + new CreatureGroup(new[] + { + typeof(BloodElemental), typeof(EarthElemental), typeof(SummonedEarthElemental), + typeof(AgapiteElemental), typeof(BronzeElemental), typeof(CopperElemental), + typeof(DullCopperElemental), typeof(GoldenElemental), typeof(ShadowIronElemental), + typeof(ValoriteElemental), typeof(VeriteElemental), typeof(PoisonElemental), + typeof(FireElemental), typeof(SummonedFireElemental), typeof(SnowElemental), + typeof(AirElemental), typeof(SummonedAirElemental), typeof(WaterElemental), + typeof(SummonedAirElemental), typeof(AcidElemental) + }, new[] + { + new SummonEntry(5000, typeof(WailingBanshee)), + new SummonEntry(0, typeof(Wraith)) + }), + // Dragons + new CreatureGroup(new[] + { + typeof(AncientWyrm), typeof(Dragon), typeof(GreaterDragon), typeof(SerpentineDragon), + typeof(ShadowWyrm), typeof(SkeletalDragon), typeof(WhiteWyrm), + typeof(Drake), typeof(Wyvern), typeof(LesserHiryu), typeof(Hiryu) + }, new[] + { + new SummonEntry(18000, typeof(SkeletalDragon)), + new SummonEntry(10000, typeof(FleshGolem)), + new SummonEntry(5000, typeof(Lich)), + new SummonEntry(3000, typeof(SkeletalKnight), typeof(BoneKnight)), + new SummonEntry(2000, typeof(Mummy)), + new SummonEntry(1000, typeof(SkeletalMage), typeof(BoneMagi)), + new SummonEntry(0, typeof(PatchworkSkeleton)) + }), + // Default group + new CreatureGroup(new Type[0], new[] + { + new SummonEntry(18000, typeof(LichLord)), + new SummonEntry(10000, typeof(FleshGolem)), + new SummonEntry(5000, typeof(Lich)), + new SummonEntry(3000, typeof(SkeletalKnight), typeof(BoneKnight)), + new SummonEntry(2000, typeof(Mummy)), + new SummonEntry(1000, typeof(SkeletalMage), typeof(BoneMagi)), + new SummonEntry(0, typeof(PatchworkSkeleton)) + }) + }; + + private static Dictionary> m_Table = new Dictionary>(); + + public AnimateDeadSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } + + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); + + public override double RequiredSkill => 40.0; + public override int RequiredMana => 23; + + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + Caster.SendLocalizedMessage(1061083); // Animate what corpse? + } + + private static CreatureGroup FindGroup(Type type) + { + for (int i = 0; i < m_Groups.Length; ++i) + { + CreatureGroup group = m_Groups[i]; + Type[] types = group.m_Types; + + bool contains = types.Length == 0; + + for (int j = 0; !contains && j < types.Length; ++j) + contains = types[j].IsAssignableFrom(type); + + if (contains) + return group; + } + + return null; + } + + public void Target(object obj) + { + MaabusCoffinComponent comp = obj as MaabusCoffinComponent; + + MaabusCoffin addon = comp?.Addon as MaabusCoffin; + + if (addon != null) + { + PlayerMobile pm = Caster as PlayerMobile; + + QuestSystem qs = pm?.Quest; + + if (qs is DarkTidesQuest) + { + QuestObjective objective = qs.FindObjective(typeof(AnimateMaabusCorpseObjective)); + + if (objective != null && !objective.Completed) + { + addon.Awake(Caster); + objective.Complete(); + } + } + + return; + } + + Corpse c = obj as Corpse; + + if (c == null) + { + Caster.SendLocalizedMessage(1061084); // You cannot animate that. + } + else + { + Type type = null; + + if (c.Owner != null) type = c.Owner.GetType(); + + if (c.ItemID != 0x2006 || c.Animated || type == typeof(PlayerMobile) || type == null || + c.Owner != null && c.Owner.Fame < 100 || c.Owner is BaseCreature && + (((BaseCreature)c.Owner).Summoned || ((BaseCreature)c.Owner).IsBonded)) + { + Caster.SendLocalizedMessage(1061085); // There's not enough life force there to animate. + } + else + { + CreatureGroup group = FindGroup(type); + + if (group != null) + { + if (group.m_Entries.Length == 0 || type == typeof(DemonKnight)) + { + Caster.SendLocalizedMessage(1061086); // You cannot animate undead remains. + } + else if (CheckSequence()) + { + Point3D p = c.GetWorldLocation(); + Map map = c.Map; + + if (map != null) + { + Effects.PlaySound(p, map, 0x1FB); + Effects.SendLocationParticles(EffectItem.Create(p, map, EffectItem.DefaultDuration), 0x3789, + 1, 40, 0x3F, 3, 9907, 0); - list.Remove( summoned ); + Timer.DelayCall(TimeSpan.FromSeconds(2.0), new TimerStateCallback(SummonDelay_Callback), + new object[] { Caster, c, p, map, group }); + } + } + } + } + } - if ( list.Count == 0 ) - m_Table.Remove( master ); - } + FinishSequence(); + } - public static void Register( Mobile master, Mobile summoned ) - { - if ( master == null ) - return; + public static void Unregister(Mobile master, Mobile summoned) + { + if (master == null) + return; - m_Table.TryGetValue( master, out List list ); + m_Table.TryGetValue(master, out List list); - if ( list == null ) - m_Table[master] = list = new List(); + if (list == null) + return; - for ( int i = list.Count - 1; i >= 0; --i ) - { - if ( i >= list.Count ) - continue; + list.Remove(summoned); - Mobile mob = list[i]; + if (list.Count == 0) + m_Table.Remove(master); + } - if ( mob.Deleted ) - list.RemoveAt( i-- ); - } + public static void Register(Mobile master, Mobile summoned) + { + if (master == null) + return; - list.Add( summoned ); + m_Table.TryGetValue(master, out List list); - if ( list.Count > 3 ) - Timer.DelayCall( TimeSpan.Zero, list[0].Kill ); + if (list == null) + m_Table[master] = list = new List(); - Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), TimeSpan.FromSeconds( 2.0 ), new TimerStateCallback( Summoned_Damage ), summoned ); - } + for (int i = list.Count - 1; i >= 0; --i) + { + if (i >= list.Count) + continue; - private static void Summoned_Damage( object state ) - { - Mobile mob = (Mobile)state; + Mobile mob = list[i]; - if ( mob.Hits > 0 ) - --mob.Hits; - else - mob.Kill(); - } + if (mob.Deleted) + list.RemoveAt(i--); + } - private static void SummonDelay_Callback( object state ) - { - object[] states = (object[])state; + list.Add(summoned); - Mobile caster = (Mobile)states[0]; - Corpse corpse = (Corpse)states[1]; - Point3D loc = (Point3D)states[2]; - Map map = (Map)states[3]; - CreatureGroup group = (CreatureGroup)states[4]; + if (list.Count > 3) + Timer.DelayCall(TimeSpan.Zero, list[0].Kill); - if ( corpse.Animated ) - return; + Timer.DelayCall(TimeSpan.FromSeconds(2.0), TimeSpan.FromSeconds(2.0), new TimerStateCallback(Summoned_Damage), + summoned); + } - Mobile owner = corpse.Owner; + private static void Summoned_Damage(object state) + { + Mobile mob = (Mobile)state; - if ( owner == null ) - return; + if (mob.Hits > 0) + --mob.Hits; + else + mob.Kill(); + } - double necromancy = caster.Skills[SkillName.Necromancy].Value; - double spiritSpeak = caster.Skills[SkillName.SpiritSpeak].Value; + private static void SummonDelay_Callback(object state) + { + object[] states = (object[])state; - int casterAbility = 0; + Mobile caster = (Mobile)states[0]; + Corpse corpse = (Corpse)states[1]; + Point3D loc = (Point3D)states[2]; + Map map = (Map)states[3]; + CreatureGroup group = (CreatureGroup)states[4]; - casterAbility += (int)(necromancy * 30); - casterAbility += (int)(spiritSpeak * 70); - casterAbility /= 10; - casterAbility *= 18; + if (corpse.Animated) + return; - if ( casterAbility > owner.Fame ) - casterAbility = owner.Fame; + Mobile owner = corpse.Owner; - if ( casterAbility < 0 ) - casterAbility = 0; + if (owner == null) + return; - Type toSummon = null; - SummonEntry[] entries = group.m_Entries; + double necromancy = caster.Skills[SkillName.Necromancy].Value; + double spiritSpeak = caster.Skills[SkillName.SpiritSpeak].Value; - for ( int i = 0; toSummon == null && i < entries.Length; ++i ) - { - SummonEntry entry = entries[i]; + int casterAbility = 0; - if ( casterAbility < entry.m_Requirement ) - continue; + casterAbility += (int)(necromancy * 30); + casterAbility += (int)(spiritSpeak * 70); + casterAbility /= 10; + casterAbility *= 18; - Type[] animates = entry.m_ToSummon; + if (casterAbility > owner.Fame) + casterAbility = owner.Fame; - if ( animates.Length >= 0 ) - toSummon = animates[Utility.Random( animates.Length )]; - } + if (casterAbility < 0) + casterAbility = 0; - if ( toSummon == null ) - return; + Type toSummon = null; + SummonEntry[] entries = group.m_Entries; - Mobile summoned = null; + for (int i = 0; toSummon == null && i < entries.Length; ++i) + { + SummonEntry entry = entries[i]; - try{ summoned = Activator.CreateInstance( toSummon ) as Mobile; } - catch{} + if (casterAbility < entry.m_Requirement) + continue; - if ( summoned == null ) - return; + Type[] animates = entry.m_ToSummon; - if ( summoned is BaseCreature ) - { - BaseCreature bc = (BaseCreature)summoned; + if (animates.Length >= 0) + toSummon = animates[Utility.Random(animates.Length)]; + } - // to be sure - bc.Tamable = false; + if (toSummon == null) + return; - if ( bc is BaseMount ) - bc.ControlSlots = 1; - else - bc.ControlSlots = 0; + Mobile summoned = null; - Effects.PlaySound( loc, map, bc.GetAngerSound() ); + try + { + summoned = Activator.CreateInstance(toSummon) as Mobile; + } + catch + { + } - BaseCreature.Summon( (BaseCreature)summoned, false, caster, loc, 0x28, TimeSpan.FromDays( 1.0 ) ); - } + if (summoned == null) + return; - if ( summoned is SkeletalDragon ) - Scale( (SkeletalDragon)summoned, 50 ); // lose 50% hp and strength + if (summoned is BaseCreature) + { + BaseCreature bc = (BaseCreature)summoned; - summoned.Fame = 0; - summoned.Karma = -1500; + // to be sure + bc.Tamable = false; - summoned.MoveToWorld( loc, map ); + if (bc is BaseMount) + bc.ControlSlots = 1; + else + bc.ControlSlots = 0; - corpse.Hue = 1109; - corpse.Animated = true; + Effects.PlaySound(loc, map, bc.GetAngerSound()); - Register( caster, summoned ); - } + BaseCreature.Summon((BaseCreature)summoned, false, caster, loc, 0x28, TimeSpan.FromDays(1.0)); + } - public static void Scale( BaseCreature bc, int scalar ) - { - int toScale; + if (summoned is SkeletalDragon) + Scale((SkeletalDragon)summoned, 50); // lose 50% hp and strength - toScale = bc.RawStr; - bc.RawStr = AOS.Scale( toScale, scalar ); + summoned.Fame = 0; + summoned.Karma = -1500; - toScale = bc.HitsMaxSeed; + summoned.MoveToWorld(loc, map); - if ( toScale > 0 ) - bc.HitsMaxSeed = AOS.Scale( toScale, scalar ); + corpse.Hue = 1109; + corpse.Animated = true; - bc.Hits = bc.Hits; // refresh hits - } + Register(caster, summoned); + } - private class InternalTarget : Target - { - private AnimateDeadSpell m_Owner; + public static void Scale(BaseCreature bc, int scalar) + { + int toScale; - public InternalTarget( AnimateDeadSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + toScale = bc.RawStr; + bc.RawStr = AOS.Scale(toScale, scalar); - protected override void OnTarget( Mobile from, object o ) - { - m_Owner.Target( o ); - } + toScale = bc.HitsMaxSeed; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + if (toScale > 0) + bc.HitsMaxSeed = AOS.Scale(toScale, scalar); + + bc.Hits = bc.Hits; // refresh hits + } + + private class CreatureGroup + { + public SummonEntry[] m_Entries; + public Type[] m_Types; + + public CreatureGroup(Type[] types, SummonEntry[] entries) + { + m_Types = types; + m_Entries = entries; + } + } + + private class SummonEntry + { + public int m_Requirement; + public Type[] m_ToSummon; + + public SummonEntry(int requirement, params Type[] toSummon) + { + m_ToSummon = toSummon; + m_Requirement = requirement; + } + } + + private class InternalTarget : Target + { + private AnimateDeadSpell m_Owner; + + public InternalTarget(AnimateDeadSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } + + protected override void OnTarget(Mobile from, object o) + { + m_Owner.Target(o); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/BloodOathSpell.cs b/Scripts/Spells/Necromancy/BloodOathSpell.cs index 693fa52a5..3a45af9db 100644 --- a/Scripts/Spells/Necromancy/BloodOathSpell.cs +++ b/Scripts/Spells/Necromancy/BloodOathSpell.cs @@ -5,183 +5,184 @@ using Server.Targeting; namespace Server.Spells.Necromancy { - public class BloodOathSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Blood Oath", "In Jux Mani Xen", - 203, - 9031, - Reagent.DaemonBlood - ); + public class BloodOathSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Blood Oath", "In Jux Mani Xen", + 203, + 9031, + Reagent.DaemonBlood + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + private static Hashtable m_OathTable = new Hashtable(); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 20.0; - public override int RequiredMana => 13; + public BloodOathSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public BloodOathSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override double RequiredSkill => 20.0; + public override int RequiredMana => 13; - public void Target( Mobile m ) - { - if ( Caster == m || !(m is PlayerMobile || m is BaseCreature) ) // only PlayerMobile and BaseCreature implement blood oath checking - { - Caster.SendLocalizedMessage( 1060508 ); // You can't curse that. - } - else if ( m_OathTable.Contains( Caster ) ) - { - Caster.SendLocalizedMessage( 1061607 ); // You are already bonded in a Blood Oath. - } - else if ( m_OathTable.Contains( m ) ) - { - if ( m.Player ) - Caster.SendLocalizedMessage( 1061608 ); // That player is already bonded in a Blood Oath. - else - Caster.SendLocalizedMessage( 1061609 ); // That creature is already bonded in a Blood Oath. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - /* Temporarily creates a dark pact between the caster and the target. - * Any damage dealt by the target to the caster is increased, but the target receives the same amount of damage. - * The effect lasts for ((Spirit Speak skill level - target's Resist Magic skill level) / 80 ) + 8 seconds. - * - * NOTE: The above algorithm must be fixed point, it should be: - * ((ss-rm)/8)+8 - */ + public void Target(Mobile m) + { + if (Caster == m || !(m is PlayerMobile || m is BaseCreature) + ) // only PlayerMobile and BaseCreature implement blood oath checking + { + Caster.SendLocalizedMessage(1060508); // You can't curse that. + } + else if (m_OathTable.Contains(Caster)) + { + Caster.SendLocalizedMessage(1061607); // You are already bonded in a Blood Oath. + } + else if (m_OathTable.Contains(m)) + { + if (m.Player) + Caster.SendLocalizedMessage(1061608); // That player is already bonded in a Blood Oath. + else + Caster.SendLocalizedMessage(1061609); // That creature is already bonded in a Blood Oath. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - ExpireTimer timer = (ExpireTimer)m_Table[m]; - timer?.DoExpire(); + /* Temporarily creates a dark pact between the caster and the target. + * Any damage dealt by the target to the caster is increased, but the target receives the same amount of damage. + * The effect lasts for ((Spirit Speak skill level - target's Resist Magic skill level) / 80 ) + 8 seconds. + * + * NOTE: The above algorithm must be fixed point, it should be: + * ((ss-rm)/8)+8 + */ - m_OathTable[Caster] = Caster; - m_OathTable[m] = Caster; + ExpireTimer timer = (ExpireTimer)m_Table[m]; + timer?.DoExpire(); - m.Spell?.OnCasterHurt(); + m_OathTable[Caster] = Caster; + m_OathTable[m] = Caster; - Caster.PlaySound( 0x175 ); + m.Spell?.OnCasterHurt(); - Caster.FixedParticles( 0x375A, 1, 17, 9919, 33, 7, EffectLayer.Waist ); - Caster.FixedParticles( 0x3728, 1, 13, 9502, 33, 7, (EffectLayer)255 ); + Caster.PlaySound(0x175); - m.FixedParticles( 0x375A, 1, 17, 9919, 33, 7, EffectLayer.Waist ); - m.FixedParticles( 0x3728, 1, 13, 9502, 33, 7, (EffectLayer)255 ); + Caster.FixedParticles(0x375A, 1, 17, 9919, 33, 7, EffectLayer.Waist); + Caster.FixedParticles(0x3728, 1, 13, 9502, 33, 7, (EffectLayer)255); - TimeSpan duration = TimeSpan.FromSeconds( ((GetDamageSkill( Caster ) - GetResistSkill( m )) / 8) + 8 ); - m.CheckSkill( SkillName.MagicResist, 0.0, 120.0 ); //Skill check for gain + m.FixedParticles(0x375A, 1, 17, 9919, 33, 7, EffectLayer.Waist); + m.FixedParticles(0x3728, 1, 13, 9502, 33, 7, (EffectLayer)255); - timer = new ExpireTimer ( Caster, m, duration ); - timer.Start (); + TimeSpan duration = TimeSpan.FromSeconds((GetDamageSkill(Caster) - GetResistSkill(m)) / 8 + 8); + m.CheckSkill(SkillName.MagicResist, 0.0, 120.0); //Skill check for gain - BuffInfo.AddBuff ( Caster, new BuffInfo ( BuffIcon.BloodOathCaster, 1075659, duration, Caster, m.Name.ToString () ) ); - BuffInfo.AddBuff ( m, new BuffInfo ( BuffIcon.BloodOathCurse, 1075661, duration, m, Caster.Name.ToString () ) ); + timer = new ExpireTimer(Caster, m, duration); + timer.Start(); - m_Table[m] = timer; - HarmfulSpell( m ); - } + BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.BloodOathCaster, 1075659, duration, Caster, m.Name)); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.BloodOathCurse, 1075661, duration, m, Caster.Name)); - FinishSequence(); - } + m_Table[m] = timer; + HarmfulSpell(m); + } - public static bool RemoveCurse( Mobile m ) - { - ExpireTimer t = (ExpireTimer)m_Table[m]; + FinishSequence(); + } - if ( t == null ) - return false; + public static bool RemoveCurse(Mobile m) + { + ExpireTimer t = (ExpireTimer)m_Table[m]; - t.DoExpire(); - return true; - } + if (t == null) + return false; - private static Hashtable m_OathTable = new Hashtable(); - private static Hashtable m_Table = new Hashtable (); + t.DoExpire(); + return true; + } - public static Mobile GetBloodOath( Mobile m ) - { - if ( m == null ) - return null; + public static Mobile GetBloodOath(Mobile m) + { + if (m == null) + return null; - Mobile oath = (Mobile)m_OathTable[m]; + Mobile oath = (Mobile)m_OathTable[m]; - if ( oath == m ) - oath = null; + if (oath == m) + oath = null; - return oath; - } + return oath; + } - private class ExpireTimer : Timer - { - private Mobile m_Caster; - private Mobile m_Target; - private DateTime m_End; + private class ExpireTimer : Timer + { + private Mobile m_Caster; + private DateTime m_End; + private Mobile m_Target; - public ExpireTimer( Mobile caster, Mobile target, TimeSpan delay ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Caster = caster; - m_Target = target; - m_End = DateTime.UtcNow + delay; + public ExpireTimer(Mobile caster, Mobile target, TimeSpan delay) : base(TimeSpan.FromSeconds(1.0), + TimeSpan.FromSeconds(1.0)) + { + m_Caster = caster; + m_Target = target; + m_End = DateTime.UtcNow + delay; - Priority = TimerPriority.TwoFiftyMS; - } + Priority = TimerPriority.TwoFiftyMS; + } - protected override void OnTick() - { - if ( m_Caster.Deleted || m_Target.Deleted || !m_Caster.Alive || !m_Target.Alive || DateTime.UtcNow >= m_End ) - { - DoExpire (); - } - } - public void DoExpire() - { - if ( m_OathTable.Contains( m_Caster ) ) - { - m_Caster.SendLocalizedMessage( 1061620 ); // Your Blood Oath has been broken. - m_OathTable.Remove ( m_Caster ); - } + protected override void OnTick() + { + if (m_Caster.Deleted || m_Target.Deleted || !m_Caster.Alive || !m_Target.Alive || + DateTime.UtcNow >= m_End) DoExpire(); + } - if ( m_OathTable.Contains( m_Target ) ) - { - m_Target.SendLocalizedMessage( 1061620 ); // Your Blood Oath has been broken. - m_OathTable.Remove ( m_Target ); - } + public void DoExpire() + { + if (m_OathTable.Contains(m_Caster)) + { + m_Caster.SendLocalizedMessage(1061620); // Your Blood Oath has been broken. + m_OathTable.Remove(m_Caster); + } - Stop (); + if (m_OathTable.Contains(m_Target)) + { + m_Target.SendLocalizedMessage(1061620); // Your Blood Oath has been broken. + m_OathTable.Remove(m_Target); + } - BuffInfo.RemoveBuff ( m_Caster, BuffIcon.BloodOathCaster ); - BuffInfo.RemoveBuff ( m_Target, BuffIcon.BloodOathCurse ); + Stop(); - m_Table.Remove ( m_Caster ); - } - } + BuffInfo.RemoveBuff(m_Caster, BuffIcon.BloodOathCaster); + BuffInfo.RemoveBuff(m_Target, BuffIcon.BloodOathCurse); - private class InternalTarget : Target - { - private BloodOathSpell m_Owner; + m_Table.Remove(m_Caster); + } + } - public InternalTarget( BloodOathSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + private class InternalTarget : Target + { + private BloodOathSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - else - from.SendLocalizedMessage( 1060508 ); // You can't curse that. - } + public InternalTarget(BloodOathSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + else + from.SendLocalizedMessage(1060508); // You can't curse that. + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/CorpseSkin.cs b/Scripts/Spells/Necromancy/CorpseSkin.cs index f3cbccd66..eb8b7cd2f 100644 --- a/Scripts/Spells/Necromancy/CorpseSkin.cs +++ b/Scripts/Spells/Necromancy/CorpseSkin.cs @@ -4,151 +4,151 @@ using Server.Targeting; namespace Server.Spells.Necromancy { - public class CorpseSkinSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Corpse Skin", "In Agle Corp Ylem", - 203, - 9051, - Reagent.BatWing, - Reagent.GraveDust - ); + public class CorpseSkinSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Corpse Skin", "In Agle Corp Ylem", + 203, + 9051, + Reagent.BatWing, + Reagent.GraveDust + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 20.0; - public override int RequiredMana => 11; + public CorpseSkinSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public CorpseSkinSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override double RequiredSkill => 20.0; + public override int RequiredMana => 11; - public void Target( Mobile m ) - { - if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - /* Transmogrifies the flesh of the target creature or player to resemble rotted corpse flesh, - * making them more vulnerable to Fire and Poison damage, - * but increasing their resistance to Physical and Cold damage. - * - * The effect lasts for ((Spirit Speak skill level - target's Resist Magic skill level) / 25 ) + 40 seconds. - * - * NOTE: Algorithm above is fixed point, should be: - * ((ss-mr)/2.5) + 40 - * - * NOTE: Resistance is not checked if targeting yourself - */ + public void Target(Mobile m) + { + if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - ExpireTimer timer = (ExpireTimer)m_Table[m]; + /* Transmogrifies the flesh of the target creature or player to resemble rotted corpse flesh, + * making them more vulnerable to Fire and Poison damage, + * but increasing their resistance to Physical and Cold damage. + * + * The effect lasts for ((Spirit Speak skill level - target's Resist Magic skill level) / 25 ) + 40 seconds. + * + * NOTE: Algorithm above is fixed point, should be: + * ((ss-mr)/2.5) + 40 + * + * NOTE: Resistance is not checked if targeting yourself + */ - if ( timer != null ) - timer.DoExpire(); - else - m.SendLocalizedMessage( 1061689 ); // Your skin turns dry and corpselike. + ExpireTimer timer = (ExpireTimer)m_Table[m]; - m.Spell?.OnCasterHurt(); + if (timer != null) + timer.DoExpire(); + else + m.SendLocalizedMessage(1061689); // Your skin turns dry and corpselike. - m.FixedParticles( 0x373A, 1, 15, 9913, 67, 7, EffectLayer.Head ); - m.PlaySound( 0x1BB ); + m.Spell?.OnCasterHurt(); - double ss = GetDamageSkill( Caster ); - double mr = ( Caster == m ? 0.0 : GetResistSkill( m ) ); - m.CheckSkill( SkillName.MagicResist, 0.0, 120.0 ); //Skill check for gain + m.FixedParticles(0x373A, 1, 15, 9913, 67, 7, EffectLayer.Head); + m.PlaySound(0x1BB); - TimeSpan duration = TimeSpan.FromSeconds( ((ss - mr) / 2.5) + 40.0 ); + double ss = GetDamageSkill(Caster); + double mr = Caster == m ? 0.0 : GetResistSkill(m); + m.CheckSkill(SkillName.MagicResist, 0.0, 120.0); //Skill check for gain - ResistanceMod[] mods = new ResistanceMod[4] - { - new ResistanceMod( ResistanceType.Fire, -15 ), - new ResistanceMod( ResistanceType.Poison, -15 ), - new ResistanceMod( ResistanceType.Cold, +10 ), - new ResistanceMod( ResistanceType.Physical, +10 ) - }; + TimeSpan duration = TimeSpan.FromSeconds((ss - mr) / 2.5 + 40.0); - timer = new ExpireTimer( m, mods, duration ); - timer.Start(); + ResistanceMod[] mods = new ResistanceMod[4] + { + new ResistanceMod(ResistanceType.Fire, -15), + new ResistanceMod(ResistanceType.Poison, -15), + new ResistanceMod(ResistanceType.Cold, +10), + new ResistanceMod(ResistanceType.Physical, +10) + }; - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.CorpseSkin, 1075663, duration, m ) ); + timer = new ExpireTimer(m, mods, duration); + timer.Start(); - m_Table[m] = timer; + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.CorpseSkin, 1075663, duration, m)); - for ( int i = 0; i < mods.Length; ++i ) - m.AddResistanceMod( mods[i] ); + m_Table[m] = timer; - HarmfulSpell( m ); - } + for (int i = 0; i < mods.Length; ++i) + m.AddResistanceMod(mods[i]); - FinishSequence(); - } + HarmfulSpell(m); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - public static bool RemoveCurse( Mobile m ) - { - ExpireTimer t = (ExpireTimer)m_Table[m]; + public static bool RemoveCurse(Mobile m) + { + ExpireTimer t = (ExpireTimer)m_Table[m]; - if ( t == null ) - return false; + if (t == null) + return false; - m.SendLocalizedMessage( 1061688 ); // Your skin returns to normal. - t.DoExpire(); - return true; - } + m.SendLocalizedMessage(1061688); // Your skin returns to normal. + t.DoExpire(); + return true; + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; - private ResistanceMod[] m_Mods; + private class ExpireTimer : Timer + { + private Mobile m_Mobile; + private ResistanceMod[] m_Mods; - public ExpireTimer( Mobile m, ResistanceMod[] mods, TimeSpan delay ) : base( delay ) - { - m_Mobile = m; - m_Mods = mods; - } + public ExpireTimer(Mobile m, ResistanceMod[] mods, TimeSpan delay) : base(delay) + { + m_Mobile = m; + m_Mods = mods; + } - public void DoExpire() - { - for ( int i = 0; i < m_Mods.Length; ++i ) - m_Mobile.RemoveResistanceMod( m_Mods[i] ); + public void DoExpire() + { + for (int i = 0; i < m_Mods.Length; ++i) + m_Mobile.RemoveResistanceMod(m_Mods[i]); - Stop(); - BuffInfo.RemoveBuff( m_Mobile, BuffIcon.CorpseSkin ); - m_Table.Remove( m_Mobile ); - } + Stop(); + BuffInfo.RemoveBuff(m_Mobile, BuffIcon.CorpseSkin); + m_Table.Remove(m_Mobile); + } - protected override void OnTick() - { - m_Mobile.SendLocalizedMessage( 1061688 ); // Your skin returns to normal. - DoExpire(); - } - } + protected override void OnTick() + { + m_Mobile.SendLocalizedMessage(1061688); // Your skin returns to normal. + DoExpire(); + } + } - private class InternalTarget : Target - { - private CorpseSkinSpell m_Owner; + private class InternalTarget : Target + { + private CorpseSkinSpell m_Owner; - public InternalTarget( CorpseSkinSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(CorpseSkinSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/CurseWeapon.cs b/Scripts/Spells/Necromancy/CurseWeapon.cs index e297495f1..45272f17a 100644 --- a/Scripts/Spells/Necromancy/CurseWeapon.cs +++ b/Scripts/Spells/Necromancy/CurseWeapon.cs @@ -4,100 +4,100 @@ using Server.Items; namespace Server.Spells.Necromancy { - public class CurseWeaponSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Curse Weapon", "An Sanct Gra Char", - 203, - 9031, - Reagent.PigIron - ); + public class CurseWeaponSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Curse Weapon", "An Sanct Gra Char", + 203, + 9031, + Reagent.PigIron + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.75 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 0.0; - public override int RequiredMana => 7; + public CurseWeaponSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public CurseWeaponSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.75); - public override void OnCast() - { - BaseWeapon weapon = Caster.Weapon as BaseWeapon; + public override double RequiredSkill => 0.0; + public override int RequiredMana => 7; - if ( weapon == null || weapon is Fists ) - { - Caster.SendLocalizedMessage( 501078 ); // You must be holding a weapon. - } - else if ( CheckSequence() ) - { - /* Temporarily imbues a weapon with a life draining effect. - * Half the damage that the weapon inflicts is added to the necromancer's health. - * The effects lasts for (Spirit Speak skill level / 34) + 1 seconds. - * - * NOTE: Above algorithm is fixed point, should be : - * (Spirit Speak skill level / 3.4) + 1 - * - * TODO: What happens if you curse a weapon then give it to someone else? Should they get the drain effect? - */ + public override void OnCast() + { + BaseWeapon weapon = Caster.Weapon as BaseWeapon; - Caster.PlaySound( 0x387 ); - Caster.FixedParticles( 0x3779, 1, 15, 9905, 32, 2, EffectLayer.Head ); - Caster.FixedParticles( 0x37B9, 1, 14, 9502, 32, 5, (EffectLayer)255 ); - new SoundEffectTimer( Caster ).Start(); + if (weapon == null || weapon is Fists) + { + Caster.SendLocalizedMessage(501078); // You must be holding a weapon. + } + else if (CheckSequence()) + { + /* Temporarily imbues a weapon with a life draining effect. + * Half the damage that the weapon inflicts is added to the necromancer's health. + * The effects lasts for (Spirit Speak skill level / 34) + 1 seconds. + * + * NOTE: Above algorithm is fixed point, should be : + * (Spirit Speak skill level / 3.4) + 1 + * + * TODO: What happens if you curse a weapon then give it to someone else? Should they get the drain effect? + */ - TimeSpan duration = TimeSpan.FromSeconds( (Caster.Skills[SkillName.SpiritSpeak].Value / 3.4) + 1.0 ); + Caster.PlaySound(0x387); + Caster.FixedParticles(0x3779, 1, 15, 9905, 32, 2, EffectLayer.Head); + Caster.FixedParticles(0x37B9, 1, 14, 9502, 32, 5, (EffectLayer)255); + new SoundEffectTimer(Caster).Start(); + + TimeSpan duration = TimeSpan.FromSeconds(Caster.Skills[SkillName.SpiritSpeak].Value / 3.4 + 1.0); - Timer t = (Timer)m_Table[weapon]; + Timer t = (Timer)m_Table[weapon]; - t?.Stop(); + t?.Stop(); - weapon.Cursed = true; + weapon.Cursed = true; - m_Table[weapon] = t = new ExpireTimer( weapon, duration ); + m_Table[weapon] = t = new ExpireTimer(weapon, duration); - t.Start(); - } + t.Start(); + } - FinishSequence(); - } + FinishSequence(); + } - private static Hashtable m_Table = new Hashtable(); + private class ExpireTimer : Timer + { + private BaseWeapon m_Weapon; - private class ExpireTimer : Timer - { - private BaseWeapon m_Weapon; + public ExpireTimer(BaseWeapon weapon, TimeSpan delay) : base(delay) + { + m_Weapon = weapon; + Priority = TimerPriority.OneSecond; + } - public ExpireTimer( BaseWeapon weapon, TimeSpan delay ) : base( delay ) - { - m_Weapon = weapon; - Priority = TimerPriority.OneSecond; - } + protected override void OnTick() + { + m_Weapon.Cursed = false; + Effects.PlaySound(m_Weapon.GetWorldLocation(), m_Weapon.Map, 0xFA); + m_Table.Remove(this); + } + } - protected override void OnTick() - { - m_Weapon.Cursed = false; - Effects.PlaySound( m_Weapon.GetWorldLocation(), m_Weapon.Map, 0xFA ); - m_Table.Remove( this ); - } - } + private class SoundEffectTimer : Timer + { + private Mobile m_Mobile; - private class SoundEffectTimer : Timer - { - private Mobile m_Mobile; + public SoundEffectTimer(Mobile m) : base(TimeSpan.FromSeconds(0.75)) + { + m_Mobile = m; + Priority = TimerPriority.FiftyMS; + } - public SoundEffectTimer( Mobile m ) : base( TimeSpan.FromSeconds( 0.75 ) ) - { - m_Mobile = m; - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - m_Mobile.PlaySound( 0xFA ); - } - } - } -} + protected override void OnTick() + { + m_Mobile.PlaySound(0xFA); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/EvilOmen.cs b/Scripts/Spells/Necromancy/EvilOmen.cs index 70be14083..acfc578dd 100644 --- a/Scripts/Spells/Necromancy/EvilOmen.cs +++ b/Scripts/Spells/Necromancy/EvilOmen.cs @@ -5,128 +5,127 @@ using Server.Targeting; namespace Server.Spells.Necromancy { - public class EvilOmenSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Evil Omen", "Pas Tym An Sanct", - 203, - 9031, - Reagent.BatWing, - Reagent.NoxCrystal - ); + public class EvilOmenSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Evil Omen", "Pas Tym An Sanct", + 203, + 9031, + Reagent.BatWing, + Reagent.NoxCrystal + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.75); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 20.0; - public override int RequiredMana => 11; + public EvilOmenSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public EvilOmenSpell(Mobile caster, Item scroll) - : base(caster, scroll, m_Info) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.75); - public override void OnCast() - { - Caster.Target = new InternalTarget(this); - } + public override double RequiredSkill => 20.0; + public override int RequiredMana => 11; - public void Target(Mobile m) - { - if (!(m is BaseCreature || m is PlayerMobile)) - { - Caster.SendLocalizedMessage(1060508); // You can't curse that. - } - else if (CheckHSequence(m)) - { - SpellHelper.Turn(Caster, m); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - /* Curses the target so that the next harmful event that affects them is magnified. - * Damage to the target's hit points is increased 25%, - * the poison level of the attack will be 1 higher - * and the Resist Magic skill of the target will be fixed on 50. - * - * The effect lasts for one harmful event only. - */ + public void Target(Mobile m) + { + if (!(m is BaseCreature || m is PlayerMobile)) + { + Caster.SendLocalizedMessage(1060508); // You can't curse that. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - m.Spell?.OnCasterHurt(); + /* Curses the target so that the next harmful event that affects them is magnified. + * Damage to the target's hit points is increased 25%, + * the poison level of the attack will be 1 higher + * and the Resist Magic skill of the target will be fixed on 50. + * + * The effect lasts for one harmful event only. + */ - m.PlaySound(0xFC); - m.FixedParticles(0x3728, 1, 13, 9912, 1150, 7, EffectLayer.Head); - m.FixedParticles(0x3779, 1, 15, 9502, 67, 7, EffectLayer.Head); + m.Spell?.OnCasterHurt(); - if (!m_Table.Contains(m)) - { - SkillMod mod = new DefaultSkillMod(SkillName.MagicResist, false, 50.0); + m.PlaySound(0xFC); + m.FixedParticles(0x3728, 1, 13, 9912, 1150, 7, EffectLayer.Head); + m.FixedParticles(0x3779, 1, 15, 9502, 67, 7, EffectLayer.Head); - if (m.Skills[SkillName.MagicResist].Base > 50.0) - m.AddSkillMod(mod); + if (!m_Table.Contains(m)) + { + SkillMod mod = new DefaultSkillMod(SkillName.MagicResist, false, 50.0); - m_Table[m] = mod; - } + if (m.Skills[SkillName.MagicResist].Base > 50.0) + m.AddSkillMod(mod); - TimeSpan duration = TimeSpan.FromSeconds((Caster.Skills[SkillName.SpiritSpeak].Value / 12) + 1.0); + m_Table[m] = mod; + } - Timer.DelayCall(duration, new TimerStateCallback(EffectExpire_Callback), m); + TimeSpan duration = TimeSpan.FromSeconds(Caster.Skills[SkillName.SpiritSpeak].Value / 12 + 1.0); - HarmfulSpell( m ); + Timer.DelayCall(duration, new TimerStateCallback(EffectExpire_Callback), m); - BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.EvilOmen, 1075647, 1075648, duration, m)); + HarmfulSpell(m); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.EvilOmen, 1075647, 1075648, duration, m)); + } - FinishSequence(); - } + FinishSequence(); + } - private static Hashtable m_Table = new Hashtable(); + private static void EffectExpire_Callback(object state) + { + TryEndEffect((Mobile)state); + } - private static void EffectExpire_Callback(object state) - { - TryEndEffect((Mobile)state); - } + /* + * The naming here was confusing. Its a 1-off effect spell. + * So, we dont actually "checkeffect"; we endeffect with bool + * return to determine external behaviors. + * + * -refactored. + */ - /* - * The naming here was confusing. Its a 1-off effect spell. - * So, we dont actually "checkeffect"; we endeffect with bool - * return to determine external behaviors. - * - * -refactored. - */ + public static bool TryEndEffect(Mobile m) + { + SkillMod mod = (SkillMod)m_Table[m]; - public static bool TryEndEffect(Mobile m) - { - SkillMod mod = (SkillMod)m_Table[m]; + if (mod == null) + return false; - if (mod == null) - return false; + m_Table.Remove(m); + mod.Remove(); - m_Table.Remove(m); - mod.Remove(); + return true; + } - return true; - } + private class InternalTarget : Target + { + private EvilOmenSpell m_Owner; - private class InternalTarget : Target - { - private EvilOmenSpell m_Owner; + public InternalTarget(EvilOmenSpell owner) + : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - public InternalTarget(EvilOmenSpell owner) - : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) - { - m_Owner = owner; - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + else + from.SendLocalizedMessage(1060508); // You can't curse that. + } - protected override void OnTarget(Mobile from, object o) - { - if (o is Mobile) - m_Owner.Target((Mobile)o); - else - from.SendLocalizedMessage(1060508); // You can't curse that. - } - - protected override void OnTargetFinish(Mobile from) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/Exorcism.cs b/Scripts/Spells/Necromancy/Exorcism.cs index cc7a7aacb..462c72376 100644 --- a/Scripts/Spells/Necromancy/Exorcism.cs +++ b/Scripts/Spells/Necromancy/Exorcism.cs @@ -1,196 +1,202 @@ using System; using System.Collections.Generic; -using Server.Items; using Server.Engines.CannedEvil; -using Server.Guilds; -using Server.Factions; using Server.Engines.PartySystem; +using Server.Factions; +using Server.Guilds; +using Server.Items; using Server.Regions; namespace Server.Spells.Necromancy { - public class ExorcismSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Exorcism", "Ort Corp Grav", - 203, - 9031, - Reagent.NoxCrystal, - Reagent.GraveDust - ); + public class ExorcismSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Exorcism", "Ort Corp Grav", + 203, + 9031, + Reagent.NoxCrystal, + Reagent.GraveDust + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + private static readonly int Range = Core.ML ? 48 : 18; - public override double RequiredSkill => 80.0; - public override int RequiredMana => 40; + private static readonly Point3D[] m_BritanniaLocs = + { + new Point3D(1470, 843, 0), + new Point3D(1857, 865, -1), + new Point3D(4220, 563, 36), + new Point3D(1732, 3528, 0), + new Point3D(1300, 644, 8), + new Point3D(3355, 302, 9), + new Point3D(1606, 2490, 5), + new Point3D(2500, 3931, 3), + new Point3D(4264, 3707, 0) + }; - public ExorcismSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + private static readonly Point3D[] m_IllshLocs = + { + new Point3D(1222, 474, -17), + new Point3D(718, 1360, -60), + new Point3D(297, 1014, -19), + new Point3D(986, 1006, -36), + new Point3D(1180, 1288, -30), + new Point3D(1538, 1341, -3), + new Point3D(528, 223, -38) + }; - public override bool CheckCast() - { - if ( Caster.Skills.SpiritSpeak.Value < 100.0 ) - { - Caster.SendLocalizedMessage( 1072112 ); // You must have GM Spirit Speak to use this spell - return false; - } + private static readonly Point3D[] m_MalasLocs = + { + new Point3D(976, 517, -30) + }; - return base.CheckCast(); - } + private static readonly Point3D[] m_TokunoLocs = + { + new Point3D(710, 1162, 25), + new Point3D(1034, 515, 18), + new Point3D(295, 712, 55) + }; + + public ExorcismSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } + + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); + + public override double RequiredSkill => 80.0; + public override int RequiredMana => 40; - public override bool DelayedDamage => false; + public override bool DelayedDamage => false; - private static readonly int Range = (Core.ML ? 48 : 18); + public override bool CheckCast() + { + if (Caster.Skills.SpiritSpeak.Value < 100.0) + { + Caster.SendLocalizedMessage(1072112); // You must have GM Spirit Speak to use this spell + return false; + } - public override int ComputeKarmaAward() - { - return 0; //no karma lost from this spell! - } + return base.CheckCast(); + } - public override void OnCast() - { - ChampionSpawnRegion r = Caster.Region.GetRegion( typeof( ChampionSpawnRegion ) ) as ChampionSpawnRegion; + public override int ComputeKarmaAward() + { + return 0; //no karma lost from this spell! + } - if ( r == null || !Caster.InRange( r.ChampionSpawn, Range ) ) - { - Caster.SendLocalizedMessage( 1072111 ); // You are not in a valid exorcism region. - } - else if ( CheckSequence() ) - { - Map map = Caster.Map; + public override void OnCast() + { + ChampionSpawnRegion r = Caster.Region.GetRegion(typeof(ChampionSpawnRegion)) as ChampionSpawnRegion; - if ( map != null ) - { - List targets = new List(); + if (r == null || !Caster.InRange(r.ChampionSpawn, Range)) + { + Caster.SendLocalizedMessage(1072111); // You are not in a valid exorcism region. + } + else if (CheckSequence()) + { + Map map = Caster.Map; - foreach( Mobile m in r.ChampionSpawn.GetMobilesInRange( Range ) ) - if ( IsValidTarget( m ) ) - targets.Add( m ); + if (map != null) + { + List targets = new List(); - for( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + foreach (Mobile m in r.ChampionSpawn.GetMobilesInRange(Range)) + if (IsValidTarget(m)) + targets.Add(m); - //Suprisingly, no sparkle type effects + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - m.Location = GetNearestShrine( m ); - } - } - } + //Suprisingly, no sparkle type effects - FinishSequence(); - } + m.Location = GetNearestShrine(m); + } + } + } - private bool IsValidTarget( Mobile m ) - { - if ( !m.Player || m.Alive ) - return false; + FinishSequence(); + } - Corpse c = m.Corpse as Corpse; - Map map = m.Map; + private bool IsValidTarget(Mobile m) + { + if (!m.Player || m.Alive) + return false; - if ( c != null && !c.Deleted && map != null && c.Map == map ) - { - if ( SpellHelper.IsAnyT2A( map, c.Location ) && SpellHelper.IsAnyT2A( map, m.Location ) ) - return false; //Same Map, both in T2A, ie, same 'sub server'. + Corpse c = m.Corpse as Corpse; + Map map = m.Map; - if ( m.Region.IsPartOf( typeof( DungeonRegion ) ) == Region.Find( c.Location, map ).IsPartOf( typeof( DungeonRegion ) ) ) - return false; //Same Map, both in Dungeon region OR They're both NOT in a dungeon region. + if (c != null && !c.Deleted && map != null && c.Map == map) + { + if (SpellHelper.IsAnyT2A(map, c.Location) && SpellHelper.IsAnyT2A(map, m.Location)) + return false; //Same Map, both in T2A, ie, same 'sub server'. - //Just an approximation cause RunUO doens't divide up the world the same way OSI does ;p + if (m.Region.IsPartOf(typeof(DungeonRegion)) == Region.Find(c.Location, map).IsPartOf(typeof(DungeonRegion))) + return false; //Same Map, both in Dungeon region OR They're both NOT in a dungeon region. - } + //Just an approximation cause RunUO doens't divide up the world the same way OSI does ;p + } - Party p = Party.Get( m ); + Party p = Party.Get(m); - if ( p != null && p.Contains( Caster ) ) - return false; + if (p != null && p.Contains(Caster)) + return false; - if ( m.Guild != null && Caster.Guild != null ) - { - Guild mGuild = m.Guild as Guild; - Guild cGuild = Caster.Guild as Guild; + if (m.Guild != null && Caster.Guild != null) + { + Guild mGuild = m.Guild as Guild; + Guild cGuild = Caster.Guild as Guild; - if ( mGuild.IsAlly( cGuild ) ) - return false; + if (mGuild.IsAlly(cGuild)) + return false; - if ( mGuild == cGuild ) - return false; - } + if (mGuild == cGuild) + return false; + } - Faction f = Faction.Find( m ); + Faction f = Faction.Find(m); - if ( Faction.Facet == m.Map && f != null && f == Faction.Find( Caster ) ) - return false; + if (Faction.Facet == m.Map && f != null && f == Faction.Find(Caster)) + return false; - return true; - } + return true; + } - private static Point3D GetNearestShrine( Mobile m ) - { - Map map = m.Map; + private static Point3D GetNearestShrine(Mobile m) + { + Map map = m.Map; - Point3D[] locList; + Point3D[] locList; - if ( map == Map.Felucca || map == Map.Trammel ) - locList = m_BritanniaLocs; - else if ( map == Map.Ilshenar ) - locList = m_IllshLocs; - else if ( map == Map.Tokuno ) - locList = m_TokunoLocs; - else if ( map == Map.Malas ) - locList = m_MalasLocs; - else - locList = new Point3D[0]; + if (map == Map.Felucca || map == Map.Trammel) + locList = m_BritanniaLocs; + else if (map == Map.Ilshenar) + locList = m_IllshLocs; + else if (map == Map.Tokuno) + locList = m_TokunoLocs; + else if (map == Map.Malas) + locList = m_MalasLocs; + else + locList = new Point3D[0]; - Point3D closest = Point3D.Zero; - double minDist = double.MaxValue; + Point3D closest = Point3D.Zero; + double minDist = double.MaxValue; - for( int i = 0; i < locList.Length; i++ ) - { - Point3D p = locList[i]; + for (int i = 0; i < locList.Length; i++) + { + Point3D p = locList[i]; - double dist = m.GetDistanceToSqrt( p ); - if ( minDist > dist ) - { - closest = p; - minDist = dist; - } - } + double dist = m.GetDistanceToSqrt(p); + if (minDist > dist) + { + closest = p; + minDist = dist; + } + } - return closest; - } - - private static readonly Point3D[] m_BritanniaLocs = { - new Point3D( 1470, 843, 0 ), - new Point3D( 1857, 865, -1 ), - new Point3D( 4220, 563, 36 ), - new Point3D( 1732, 3528, 0 ), - new Point3D( 1300, 644, 8 ), - new Point3D( 3355, 302, 9 ), - new Point3D( 1606, 2490, 5 ), - new Point3D( 2500, 3931, 3 ), - new Point3D( 4264, 3707, 0 ) - }; - private static readonly Point3D[] m_IllshLocs = { - new Point3D( 1222, 474, -17 ), - new Point3D( 718, 1360, -60), - new Point3D( 297, 1014, -19 ), - new Point3D( 986, 1006, -36 ), - new Point3D( 1180, 1288, -30 ), - new Point3D( 1538, 1341, -3 ), - new Point3D( 528, 223, -38 ) - }; - private static readonly Point3D[] m_MalasLocs = { - new Point3D ( 976, 517, -30 ) - }; - private static readonly Point3D[] m_TokunoLocs = { - new Point3D( 710, 1162, 25 ), - new Point3D( 1034, 515, 18 ), - new Point3D( 295, 712, 55 ) - }; - } -} + return closest; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/HorrificBeast.cs b/Scripts/Spells/Necromancy/HorrificBeast.cs index b0c9489bb..d2f876c75 100644 --- a/Scripts/Spells/Necromancy/HorrificBeast.cs +++ b/Scripts/Spells/Necromancy/HorrificBeast.cs @@ -2,39 +2,39 @@ using System; namespace Server.Spells.Necromancy { - public class HorrificBeastSpell : TransformationSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Horrific Beast", "Rel Xen Vas Bal", - 203, - 9031, - Reagent.BatWing, - Reagent.DaemonBlood - ); + public class HorrificBeastSpell : TransformationSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Horrific Beast", "Rel Xen Vas Bal", + 203, + 9031, + Reagent.BatWing, + Reagent.DaemonBlood + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public HorrificBeastSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 40.0; - public override int RequiredMana => 11; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public override int Body => 746; + public override double RequiredSkill => 40.0; + public override int RequiredMana => 11; - public HorrificBeastSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override int Body => 746; - public override void DoEffect( Mobile m ) - { - m.PlaySound( 0x165 ); - m.FixedParticles( 0x3728, 1, 13, 9918, 92, 3, EffectLayer.Head ); + public override void DoEffect(Mobile m) + { + m.PlaySound(0x165); + m.FixedParticles(0x3728, 1, 13, 9918, 92, 3, EffectLayer.Head); - m.Delta( MobileDelta.WeaponDamage ); - m.CheckStatTimers(); - } + m.Delta(MobileDelta.WeaponDamage); + m.CheckStatTimers(); + } - public override void RemoveEffect( Mobile m ) - { - m.Delta( MobileDelta.WeaponDamage ); - } - } -} + public override void RemoveEffect(Mobile m) + { + m.Delta(MobileDelta.WeaponDamage); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/LichForm.cs b/Scripts/Spells/Necromancy/LichForm.cs index d25ddec47..2d5ada771 100644 --- a/Scripts/Spells/Necromancy/LichForm.cs +++ b/Scripts/Spells/Necromancy/LichForm.cs @@ -2,43 +2,43 @@ using System; namespace Server.Spells.Necromancy { - public class LichFormSpell : TransformationSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Lich Form", "Rel Xen Corp Ort", - 203, - 9031, - Reagent.GraveDust, - Reagent.DaemonBlood, - Reagent.NoxCrystal - ); + public class LichFormSpell : TransformationSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Lich Form", "Rel Xen Corp Ort", + 203, + 9031, + Reagent.GraveDust, + Reagent.DaemonBlood, + Reagent.NoxCrystal + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public LichFormSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 70.0; - public override int RequiredMana => 23; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public override int Body => 749; + public override double RequiredSkill => 70.0; + public override int RequiredMana => 23; - public override int FireResistOffset => -10; - public override int ColdResistOffset => +10; - public override int PoisResistOffset => +10; + public override int Body => 749; - public override double TickRate => 2.5; + public override int FireResistOffset => -10; + public override int ColdResistOffset => +10; + public override int PoisResistOffset => +10; - public LichFormSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double TickRate => 2.5; - public override void DoEffect( Mobile m ) - { - m.PlaySound( 0x19C ); - m.FixedParticles( 0x3709, 1, 30, 9904, 1108, 6, EffectLayer.RightFoot ); - } + public override void DoEffect(Mobile m) + { + m.PlaySound(0x19C); + m.FixedParticles(0x3709, 1, 30, 9904, 1108, 6, EffectLayer.RightFoot); + } - public override void OnTick( Mobile m ) - { - --m.Hits; - } - } -} + public override void OnTick(Mobile m) + { + --m.Hits; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/MindRot.cs b/Scripts/Spells/Necromancy/MindRot.cs index 122ccb35b..bc4e271e7 100644 --- a/Scripts/Spells/Necromancy/MindRot.cs +++ b/Scripts/Spells/Necromancy/MindRot.cs @@ -4,176 +4,180 @@ using Server.Targeting; namespace Server.Spells.Necromancy { - public class MindRotSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mind Rot", "Wis An Ben", - 203, - 9031, - Reagent.BatWing, - Reagent.PigIron, - Reagent.DaemonBlood - ); + public class MindRotSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mind Rot", "Wis An Ben", + 203, + 9031, + Reagent.BatWing, + Reagent.PigIron, + Reagent.DaemonBlood + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 30.0; - public override int RequiredMana => 17; + public MindRotSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MindRotSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override double RequiredSkill => 30.0; + public override int RequiredMana => 17; - public void Target( Mobile m ) - { - if ( HasMindRotScalar( m ) ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - /* Attempts to place a curse on the Target that increases the mana cost of any spells they cast, - * for a duration based off a comparison between the Caster's Spirit Speak skill and the Target's Resisting Spells skill. - * The effect lasts for ((Spirit Speak skill level - target's Resist Magic skill level) / 50 ) + 20 seconds. - */ + public void Target(Mobile m) + { + if (HasMindRotScalar(m)) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - m.Spell?.OnCasterHurt(); + /* Attempts to place a curse on the Target that increases the mana cost of any spells they cast, + * for a duration based off a comparison between the Caster's Spirit Speak skill and the Target's Resisting Spells skill. + * The effect lasts for ((Spirit Speak skill level - target's Resist Magic skill level) / 50 ) + 20 seconds. + */ - m.PlaySound( 0x1FB ); - m.PlaySound( 0x258 ); - m.FixedParticles( 0x373A, 1, 17, 9903, 15, 4, EffectLayer.Head ); + m.Spell?.OnCasterHurt(); - TimeSpan duration = TimeSpan.FromSeconds( (((GetDamageSkill( Caster ) - GetResistSkill( m )) / 5.0) + 20.0) * (m.Player ? 1.0 : 2.0 ) ); - m.CheckSkill( SkillName.MagicResist, 0.0, 120.0 ); //Skill check for gain + m.PlaySound(0x1FB); + m.PlaySound(0x258); + m.FixedParticles(0x373A, 1, 17, 9903, 15, 4, EffectLayer.Head); - if ( m.Player ) - SetMindRotScalar( Caster, m, 1.25, duration ); - else - SetMindRotScalar( Caster, m, 2.00, duration ); + TimeSpan duration = + TimeSpan.FromSeconds( + ((GetDamageSkill(Caster) - GetResistSkill(m)) / 5.0 + 20.0) * (m.Player ? 1.0 : 2.0)); + m.CheckSkill(SkillName.MagicResist, 0.0, 120.0); //Skill check for gain - HarmfulSpell( m ); - } + if (m.Player) + SetMindRotScalar(Caster, m, 1.25, duration); + else + SetMindRotScalar(Caster, m, 2.00, duration); - FinishSequence(); - } + HarmfulSpell(m); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - public static void ClearMindRotScalar( Mobile m ) - { - if (!m_Table.ContainsKey(m)) - return; + public static void ClearMindRotScalar(Mobile m) + { + if (!m_Table.ContainsKey(m)) + return; - BuffInfo.RemoveBuff( m, BuffIcon.Mindrot ); - MRBucket tmpB = (MRBucket)m_Table[m]; - MRExpireTimer tmpT = (MRExpireTimer)tmpB.m_MRExpireTimer; - tmpT.Stop(); - m_Table.Remove(m); - m.SendLocalizedMessage(1060872); // Your mind feels normal again. - } + BuffInfo.RemoveBuff(m, BuffIcon.Mindrot); + MRBucket tmpB = (MRBucket)m_Table[m]; + MRExpireTimer tmpT = tmpB.m_MRExpireTimer; + tmpT.Stop(); + m_Table.Remove(m); + m.SendLocalizedMessage(1060872); // Your mind feels normal again. + } - public static bool HasMindRotScalar( Mobile m ) - { - return m_Table.ContainsKey(m); - } + public static bool HasMindRotScalar(Mobile m) + { + return m_Table.ContainsKey(m); + } - public static bool GetMindRotScalar( Mobile m, ref double scalar ) - { - if (!m_Table.ContainsKey(m)) - return false; + public static bool GetMindRotScalar(Mobile m, ref double scalar) + { + if (!m_Table.ContainsKey(m)) + return false; - MRBucket tmpB = (MRBucket)m_Table[m]; - scalar = tmpB.m_Scalar; - return true; - } + MRBucket tmpB = (MRBucket)m_Table[m]; + scalar = tmpB.m_Scalar; + return true; + } - public static void SetMindRotScalar( Mobile caster, Mobile target, double scalar, TimeSpan duration ) - { - if (!m_Table.ContainsKey(target)) - { - m_Table.Add(target, new MRBucket(scalar, new MRExpireTimer(caster, target, duration))); - BuffInfo.AddBuff(target, new BuffInfo(BuffIcon.Mindrot, 1075665, duration, target)); - MRBucket tmpB = (MRBucket)m_Table[target]; - MRExpireTimer tmpT = (MRExpireTimer)tmpB.m_MRExpireTimer; - tmpT.Start(); - target.SendLocalizedMessage(1074384); - } - } + public static void SetMindRotScalar(Mobile caster, Mobile target, double scalar, TimeSpan duration) + { + if (!m_Table.ContainsKey(target)) + { + m_Table.Add(target, new MRBucket(scalar, new MRExpireTimer(caster, target, duration))); + BuffInfo.AddBuff(target, new BuffInfo(BuffIcon.Mindrot, 1075665, duration, target)); + MRBucket tmpB = (MRBucket)m_Table[target]; + MRExpireTimer tmpT = tmpB.m_MRExpireTimer; + tmpT.Start(); + target.SendLocalizedMessage(1074384); + } + } - private class InternalTarget : Target - { - private MindRotSpell m_Owner; + private class InternalTarget : Target + { + private MindRotSpell m_Owner; - public InternalTarget( MindRotSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(MindRotSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - else - from.SendLocalizedMessage( 1060508 ); // You can't curse that. - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + else + from.SendLocalizedMessage(1060508); // You can't curse that. + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } - public class MRExpireTimer : Timer - { - private Mobile m_Caster; - private Mobile m_Target; - private DateTime m_End; + public class MRExpireTimer : Timer + { + private Mobile m_Caster; + private DateTime m_End; + private Mobile m_Target; - public MRExpireTimer( Mobile caster, Mobile target, TimeSpan delay ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_Caster = caster; - m_Target = target; - m_End = DateTime.UtcNow + delay; - Priority = TimerPriority.TwoFiftyMS; - } + public MRExpireTimer(Mobile caster, Mobile target, TimeSpan delay) : base(TimeSpan.FromSeconds(1.0), + TimeSpan.FromSeconds(1.0)) + { + m_Caster = caster; + m_Target = target; + m_End = DateTime.UtcNow + delay; + Priority = TimerPriority.TwoFiftyMS; + } - public void RenewDelay(TimeSpan delay) - { - m_End = DateTime.UtcNow + delay; - } + public void RenewDelay(TimeSpan delay) + { + m_End = DateTime.UtcNow + delay; + } - public void Halt() - { - Stop(); - } + public void Halt() + { + Stop(); + } - protected override void OnTick() - { - if ( m_Target.Deleted || !m_Target.Alive || DateTime.UtcNow >= m_End ) - { - MindRotSpell.ClearMindRotScalar( m_Target ); - Stop(); - } - } - } + protected override void OnTick() + { + if (m_Target.Deleted || !m_Target.Alive || DateTime.UtcNow >= m_End) + { + MindRotSpell.ClearMindRotScalar(m_Target); + Stop(); + } + } + } - public class MRBucket - { - public MRBucket(double theScalar, MRExpireTimer theTimer) - { - m_Scalar = theScalar; - m_MRExpireTimer = theTimer; - } + public class MRBucket + { + public MRExpireTimer m_MRExpireTimer; - public double m_Scalar; - public MRExpireTimer m_MRExpireTimer; - } -} + public double m_Scalar; + + public MRBucket(double theScalar, MRExpireTimer theTimer) + { + m_Scalar = theScalar; + m_MRExpireTimer = theTimer; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/NecromancerSpell.cs b/Scripts/Spells/Necromancy/NecromancerSpell.cs index 537cd0e62..a8e70ac97 100644 --- a/Scripts/Spells/Necromancy/NecromancerSpell.cs +++ b/Scripts/Spells/Necromancy/NecromancerSpell.cs @@ -2,56 +2,60 @@ using Server.Items; namespace Server.Spells.Necromancy { - public abstract class NecromancerSpell : Spell - { - public abstract double RequiredSkill{ get; } - public abstract int RequiredMana{ get; } + public abstract class NecromancerSpell : Spell + { + public NecromancerSpell(Mobile caster, Item scroll, SpellInfo info) : base(caster, scroll, info) + { + } - public override SkillName CastSkill => SkillName.Necromancy; - public override SkillName DamageSkill => SkillName.SpiritSpeak; + public abstract double RequiredSkill{ get; } + public abstract int RequiredMana{ get; } - //public override int CastDelayBase => base.CastDelayBase; // Reference, 3 + public override SkillName CastSkill => SkillName.Necromancy; + public override SkillName DamageSkill => SkillName.SpiritSpeak; - public override bool ClearHandsOnCast => false; + //public override int CastDelayBase => base.CastDelayBase; // Reference, 3 - public override double CastDelayFastScalar => (Core.SE? base.CastDelayFastScalar : 0); // Necromancer spells are not affected by fast cast items, though they are by fast cast recovery + public override bool ClearHandsOnCast => false; - public NecromancerSpell( Mobile caster, Item scroll, SpellInfo info ) : base( caster, scroll, info ) - { - } + public override double CastDelayFastScalar => + Core.SE + ? base.CastDelayFastScalar + : 0; // Necromancer spells are not affected by fast cast items, though they are by fast cast recovery - public override int ComputeKarmaAward() - { - //TODO: Verify this formula being that Necro spells don't HAVE a circle. - //int karma = -(70 + (10 * (int)Circle)); - int karma = -(40 + (int)(10 * (CastDelayBase.TotalSeconds / CastDelaySecondsPerTick))); + public override int ComputeKarmaAward() + { + //TODO: Verify this formula being that Necro spells don't HAVE a circle. + //int karma = -(70 + (10 * (int)Circle)); + int karma = -(40 + (int)(10 * (CastDelayBase.TotalSeconds / CastDelaySecondsPerTick))); - if ( Core.ML ) // Pub 36: "Added a new property called Increased Karma Loss which grants higher karma loss for casting necromancy spells." - karma += AOS.Scale( karma, AosAttributes.GetValue( Caster, AosAttribute.IncreasedKarmaLoss ) ); + if (Core.ML + ) // Pub 36: "Added a new property called Increased Karma Loss which grants higher karma loss for casting necromancy spells." + karma += AOS.Scale(karma, AosAttributes.GetValue(Caster, AosAttribute.IncreasedKarmaLoss)); - return karma; - } + return karma; + } - public override void GetCastSkills( out double min, out double max ) - { - min = RequiredSkill; - max = Scroll != null ? min : RequiredSkill + 40.0; - } + public override void GetCastSkills(out double min, out double max) + { + min = RequiredSkill; + max = Scroll != null ? min : RequiredSkill + 40.0; + } - public override bool ConsumeReagents() - { - if ( base.ConsumeReagents() ) - return true; + public override bool ConsumeReagents() + { + if (base.ConsumeReagents()) + return true; - if ( ArcaneGem.ConsumeCharges( Caster, 1 ) ) - return true; + if (ArcaneGem.ConsumeCharges(Caster, 1)) + return true; - return false; - } + return false; + } - public override int GetMana() - { - return RequiredMana; - } - } -} + public override int GetMana() + { + return RequiredMana; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/PainSpike.cs b/Scripts/Spells/Necromancy/PainSpike.cs index f3af9a844..bb90436a0 100644 --- a/Scripts/Spells/Necromancy/PainSpike.cs +++ b/Scripts/Spells/Necromancy/PainSpike.cs @@ -1,138 +1,139 @@ using System; using System.Collections; +using Server.Misc; using Server.Targeting; namespace Server.Spells.Necromancy { - public class PainSpikeSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Pain Spike", "In Sar", - 203, - 9031, - Reagent.GraveDust, - Reagent.PigIron - ); + public class PainSpikeSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Pain Spike", "In Sar", + 203, + 9031, + Reagent.GraveDust, + Reagent.PigIron + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 20.0; - public override int RequiredMana => 5; + public PainSpikeSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public PainSpikeSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override double RequiredSkill => 20.0; + public override int RequiredMana => 5; - public override bool DelayedDamage => false; + public override bool DelayedDamage => false; - public void Target( Mobile m ) - { - if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - //SpellHelper.CheckReflect( (int)this.Circle, Caster, ref m ); //Irrelevent asfter AoS + public void Target(Mobile m) + { + if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Temporarily causes intense physical pain to the target, dealing direct damage. - * After 10 seconds the spell wears off, and if the target is still alive, - * some of the Hit Points lost through Pain Spike are restored. - */ + //SpellHelper.CheckReflect( (int)this.Circle, Caster, ref m ); //Irrelevent asfter AoS - m.FixedParticles( 0x37C4, 1, 8, 9916, 39, 3, EffectLayer.Head ); - m.FixedParticles( 0x37C4, 1, 8, 9502, 39, 4, EffectLayer.Head ); - m.PlaySound( 0x210 ); + /* Temporarily causes intense physical pain to the target, dealing direct damage. + * After 10 seconds the spell wears off, and if the target is still alive, + * some of the Hit Points lost through Pain Spike are restored. + */ - double damage = ((GetDamageSkill( Caster ) - GetResistSkill( m )) / 10) + (m.Player ? 18 : 30); - m.CheckSkill( SkillName.MagicResist, 0.0, 120.0 ); //Skill check for gain + m.FixedParticles(0x37C4, 1, 8, 9916, 39, 3, EffectLayer.Head); + m.FixedParticles(0x37C4, 1, 8, 9502, 39, 4, EffectLayer.Head); + m.PlaySound(0x210); - if ( damage < 1 ) - damage = 1; + double damage = (GetDamageSkill(Caster) - GetResistSkill(m)) / 10 + (m.Player ? 18 : 30); + m.CheckSkill(SkillName.MagicResist, 0.0, 120.0); //Skill check for gain - TimeSpan buffTime = TimeSpan.FromSeconds( 10.0 ); + if (damage < 1) + damage = 1; - if ( m_Table.Contains( m ) ) - { - damage = Utility.RandomMinMax( 3, 7 ); - Timer t = m_Table[m] as Timer; + TimeSpan buffTime = TimeSpan.FromSeconds(10.0); - if ( t != null ) - { - t.Delay += TimeSpan.FromSeconds( 2.0 ); + if (m_Table.Contains(m)) + { + damage = Utility.RandomMinMax(3, 7); + Timer t = m_Table[m] as Timer; - buffTime = t.Next - DateTime.UtcNow; - } - } - else - { - new InternalTimer( m, damage ).Start(); - } + if (t != null) + { + t.Delay += TimeSpan.FromSeconds(2.0); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.PainSpike, 1075667, buffTime, m, Convert.ToString( (int)damage ) ) ); + buffTime = t.Next - DateTime.UtcNow; + } + } + else + { + new InternalTimer(m, damage).Start(); + } - Misc.WeightOverloading.DFA = Misc.DFAlgorithm.PainSpike; - m.Damage( (int) damage, Caster ); - SpellHelper.DoLeech( (int)damage, Caster, m ); - Misc.WeightOverloading.DFA = Misc.DFAlgorithm.Standard; + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.PainSpike, 1075667, buffTime, m, Convert.ToString((int)damage))); - //SpellHelper.Damage( this, m, damage, 100, 0, 0, 0, 0, Misc.DFAlgorithm.PainSpike ); - HarmfulSpell( m ); - } + WeightOverloading.DFA = DFAlgorithm.PainSpike; + m.Damage((int)damage, Caster); + SpellHelper.DoLeech((int)damage, Caster, m); + WeightOverloading.DFA = DFAlgorithm.Standard; - FinishSequence(); - } + //SpellHelper.Damage( this, m, damage, 100, 0, 0, 0, 0, Misc.DFAlgorithm.PainSpike ); + HarmfulSpell(m); + } - private static Hashtable m_Table = new Hashtable(); + FinishSequence(); + } - private class InternalTimer : Timer - { - private Mobile m_Mobile; - private int m_ToRestore; + private class InternalTimer : Timer + { + private Mobile m_Mobile; + private int m_ToRestore; - public InternalTimer( Mobile m, double toRestore ) : base( TimeSpan.FromSeconds( 10.0 ) ) - { - Priority = TimerPriority.OneSecond; + public InternalTimer(Mobile m, double toRestore) : base(TimeSpan.FromSeconds(10.0)) + { + Priority = TimerPriority.OneSecond; - m_Mobile = m; - m_ToRestore = (int)toRestore; + m_Mobile = m; + m_ToRestore = (int)toRestore; - m_Table[m] = this; - } + m_Table[m] = this; + } - protected override void OnTick() - { - m_Table.Remove( m_Mobile ); + protected override void OnTick() + { + m_Table.Remove(m_Mobile); - if ( m_Mobile.Alive && !m_Mobile.IsDeadBondedPet ) - m_Mobile.Hits += m_ToRestore; + if (m_Mobile.Alive && !m_Mobile.IsDeadBondedPet) + m_Mobile.Hits += m_ToRestore; - BuffInfo.RemoveBuff( m_Mobile, BuffIcon.PainSpike ); - } - } + BuffInfo.RemoveBuff(m_Mobile, BuffIcon.PainSpike); + } + } - private class InternalTarget : Target - { - private PainSpikeSpell m_Owner; + private class InternalTarget : Target + { + private PainSpikeSpell m_Owner; - public InternalTarget( PainSpikeSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(PainSpikeSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/PoisonStrike.cs b/Scripts/Spells/Necromancy/PoisonStrike.cs index c73173f4a..4e170854a 100644 --- a/Scripts/Spells/Necromancy/PoisonStrike.cs +++ b/Scripts/Spells/Necromancy/PoisonStrike.cs @@ -1,117 +1,120 @@ using System; using System.Collections.Generic; using Server.Items; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Necromancy { - public class PoisonStrikeSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Poison Strike", "In Vas Nox", - 203, - 9031, - Reagent.NoxCrystal - ); + public class PoisonStrikeSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Poison Strike", "In Vas Nox", + 203, + 9031, + Reagent.NoxCrystal + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( (Core.ML ? 1.75 : 1.5) ); + public PoisonStrikeSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 50.0; - public override int RequiredMana => 17; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(Core.ML ? 1.75 : 1.5); - public PoisonStrikeSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 50.0; + public override int RequiredMana => 17; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => false; - public override bool DelayedDamage => false; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Creates a blast of poisonous energy centered on the target. - * The main target is inflicted with a large amount of Poison damage, and all valid targets in a radius of 2 tiles around the main target are inflicted with a lesser effect. - * One tile from main target receives 50% damage, two tiles from target receives 33% damage. - */ + /* Creates a blast of poisonous energy centered on the target. + * The main target is inflicted with a large amount of Poison damage, and all valid targets in a radius of 2 tiles around the main target are inflicted with a lesser effect. + * One tile from main target receives 50% damage, two tiles from target receives 33% damage. + */ - //CheckResisted( m ); // Check magic resist for skill, but do not use return value //reports from OSI: Necro spells don't give Resist gain + //CheckResisted( m ); // Check magic resist for skill, but do not use return value //reports from OSI: Necro spells don't give Resist gain - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x36B0, 1, 14, 63, 7, 9915, 0 ); - Effects.PlaySound( m.Location, m.Map, 0x229 ); + Effects.SendLocationParticles(EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), 0x36B0, 1, + 14, 63, 7, 9915, 0); + Effects.PlaySound(m.Location, m.Map, 0x229); - double damage = Utility.RandomMinMax( (Core.ML ? 32 : 36), 40 ) * ((300 + (GetDamageSkill( Caster ) * 9)) / 1000); + double damage = Utility.RandomMinMax(Core.ML ? 32 : 36, 40) * ((300 + GetDamageSkill(Caster) * 9) / 1000); - double sdiBonus = (double)AosAttributes.GetValue( Caster, AosAttribute.SpellDamage )/100; - double pvmDamage = damage * (1 + sdiBonus); + double sdiBonus = (double)AosAttributes.GetValue(Caster, AosAttribute.SpellDamage) / 100; + double pvmDamage = damage * (1 + sdiBonus); - if ( Core.ML && sdiBonus > 0.15 ) - sdiBonus = 0.15; - double pvpDamage = damage * (1 + sdiBonus); + if (Core.ML && sdiBonus > 0.15) + sdiBonus = 0.15; + double pvpDamage = damage * (1 + sdiBonus); - Map map = m.Map; + Map map = m.Map; - if ( map != null ) - { - List targets = new List(); + if (map != null) + { + List targets = new List(); - if ( Caster.CanBeHarmful(m, false ) ) - targets.Add( m ); + if (Caster.CanBeHarmful(m, false)) + targets.Add(m); - foreach( Mobile targ in m.GetMobilesInRange( 2 ) ) - if (!(Caster is BaseCreature && targ is BaseCreature )) - if ( ( targ != Caster && m != targ ) && ( SpellHelper.ValidIndirectTarget( Caster, targ ) && Caster.CanBeHarmful( targ, false) ) ) - targets.Add( targ ); + foreach (Mobile targ in m.GetMobilesInRange(2)) + if (!(Caster is BaseCreature && targ is BaseCreature)) + if (targ != Caster && m != targ && SpellHelper.ValidIndirectTarget(Caster, targ) && + Caster.CanBeHarmful(targ, false)) + targets.Add(targ); - for( int i = 0; i < targets.Count; ++i ) - { - Mobile targ = targets[i]; - int num; + for (int i = 0; i < targets.Count; ++i) + { + Mobile targ = targets[i]; + int num; - if ( targ.InRange( m.Location, 0 ) ) - num = 1; - else if ( targ.InRange( m.Location, 1 ) ) - num = 2; - else - num = 3; + if (targ.InRange(m.Location, 0)) + num = 1; + else if (targ.InRange(m.Location, 1)) + num = 2; + else + num = 3; - Caster.DoHarmful( targ ); - SpellHelper.Damage( this, targ, ((m.Player && Caster.Player) ? pvpDamage : pvmDamage) / num, 0, 0, 0, 100, 0 ); - } - } - } + Caster.DoHarmful(targ); + SpellHelper.Damage(this, targ, (m.Player && Caster.Player ? pvpDamage : pvmDamage) / num, 0, 0, 0, + 100, 0); + } + } + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private PoisonStrikeSpell m_Owner; + private class InternalTarget : Target + { + private PoisonStrikeSpell m_Owner; - public InternalTarget( PoisonStrikeSpell owner ) - : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(PoisonStrikeSpell owner) + : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/Strangle.cs b/Scripts/Spells/Necromancy/Strangle.cs index f99304655..7f7c3ced1 100644 --- a/Scripts/Spells/Necromancy/Strangle.cs +++ b/Scripts/Spells/Necromancy/Strangle.cs @@ -4,235 +4,237 @@ using Server.Targeting; namespace Server.Spells.Necromancy { - public class StrangleSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Strangle", "In Bal Nox", - 209, - 9031, - Reagent.DaemonBlood, - Reagent.NoxCrystal - ); + public class StrangleSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Strangle", "In Bal Nox", + 209, + 9031, + Reagent.DaemonBlood, + Reagent.NoxCrystal + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + private static Hashtable m_Table = new Hashtable(); - public override double RequiredSkill => 65.0; - public override int RequiredMana => 29; + public StrangleSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public StrangleSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override double RequiredSkill => 65.0; + public override int RequiredMana => 29; - public void Target( Mobile m ) - { - if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - //SpellHelper.CheckReflect( (int)this.Circle, Caster, ref m ); //Irrelevent after AoS + public void Target(Mobile m) + { + if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Temporarily chokes off the air suply of the target with poisonous fumes. - * The target is inflicted with poison damage over time. - * The amount of damage dealt each "hit" is based off of the caster's Spirit Speak skill and the Target's current Stamina. - * The less Stamina the target has, the more damage is done by Strangle. - * Duration of the effect is Spirit Speak skill level / 10 rounds, with a minimum number of 4 rounds. - * The first round of damage is dealt after 5 seconds, and every next round after that comes 1 second sooner than the one before, until there is only 1 second between rounds. - * The base damage of the effect lies between (Spirit Speak skill level / 10) - 2 and (Spirit Speak skill level / 10) + 1. - * Base damage is multiplied by the following formula: (3 - (target's current Stamina / target's maximum Stamina) * 2). - * Example: - * For a target at full Stamina the damage multiplier is 1, - * for a target at 50% Stamina the damage multiplier is 2 and - * for a target at 20% Stamina the damage multiplier is 2.6 - */ + //SpellHelper.CheckReflect( (int)this.Circle, Caster, ref m ); //Irrelevent after AoS - m.Spell?.OnCasterHurt(); + /* Temporarily chokes off the air suply of the target with poisonous fumes. + * The target is inflicted with poison damage over time. + * The amount of damage dealt each "hit" is based off of the caster's Spirit Speak skill and the Target's current Stamina. + * The less Stamina the target has, the more damage is done by Strangle. + * Duration of the effect is Spirit Speak skill level / 10 rounds, with a minimum number of 4 rounds. + * The first round of damage is dealt after 5 seconds, and every next round after that comes 1 second sooner than the one before, until there is only 1 second between rounds. + * The base damage of the effect lies between (Spirit Speak skill level / 10) - 2 and (Spirit Speak skill level / 10) + 1. + * Base damage is multiplied by the following formula: (3 - (target's current Stamina / target's maximum Stamina) * 2). + * Example: + * For a target at full Stamina the damage multiplier is 1, + * for a target at 50% Stamina the damage multiplier is 2 and + * for a target at 20% Stamina the damage multiplier is 2.6 + */ - m.PlaySound( 0x22F ); - m.FixedParticles( 0x36CB, 1, 9, 9911, 67, 5, EffectLayer.Head ); - m.FixedParticles( 0x374A, 1, 17, 9502, 1108, 4, (EffectLayer)255 ); + m.Spell?.OnCasterHurt(); - if ( !m_Table.Contains( m ) ) - { - Timer t = new InternalTimer( m, Caster ); - t.Start(); + m.PlaySound(0x22F); + m.FixedParticles(0x36CB, 1, 9, 9911, 67, 5, EffectLayer.Head); + m.FixedParticles(0x374A, 1, 17, 9502, 1108, 4, (EffectLayer)255); - m_Table[m] = t; - } + if (!m_Table.Contains(m)) + { + Timer t = new InternalTimer(m, Caster); + t.Start(); - HarmfulSpell( m ); - } + m_Table[m] = t; + } - //Calculations for the buff bar - double spiritlevel = Caster.Skills[SkillName.SpiritSpeak].Value / 10; - if (spiritlevel < 4) - spiritlevel = 4; - int d_MinDamage = 4; - int d_MaxDamage = ((int)spiritlevel + 1) * 3; - string args = $"{d_MinDamage}\t{d_MaxDamage}"; + HarmfulSpell(m); + } - int i_Count = (int)spiritlevel; - int i_MaxCount = i_Count; - int i_HitDelay = 5; - int i_Length = i_HitDelay; + //Calculations for the buff bar + double spiritlevel = Caster.Skills[SkillName.SpiritSpeak].Value / 10; + if (spiritlevel < 4) + spiritlevel = 4; + int d_MinDamage = 4; + int d_MaxDamage = ((int)spiritlevel + 1) * 3; + string args = $"{d_MinDamage}\t{d_MaxDamage}"; - while (i_Count > 1) - { - --i_Count; - if (i_HitDelay > 1) - { - if (i_MaxCount < 5) - { - --i_HitDelay; - } - else - { - int delay = (int)(Math.Ceiling((1.0 + (5 * i_Count)) / i_MaxCount)); + int i_Count = (int)spiritlevel; + int i_MaxCount = i_Count; + int i_HitDelay = 5; + int i_Length = i_HitDelay; - if (delay <= 5) - i_HitDelay = delay; - else - i_HitDelay = 5; - } - } - i_Length += i_HitDelay; - } - TimeSpan t_Duration = TimeSpan.FromSeconds(i_Length); - BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Strangle, 1075794, 1075795, t_Duration, m, args.ToString())); + while (i_Count > 1) + { + --i_Count; + if (i_HitDelay > 1) + { + if (i_MaxCount < 5) + { + --i_HitDelay; + } + else + { + int delay = (int)Math.Ceiling((1.0 + 5 * i_Count) / i_MaxCount); - FinishSequence(); - } + if (delay <= 5) + i_HitDelay = delay; + else + i_HitDelay = 5; + } + } - private static Hashtable m_Table = new Hashtable(); + i_Length += i_HitDelay; + } - public static bool RemoveCurse( Mobile m ) - { - Timer t = (Timer)m_Table[m]; + TimeSpan t_Duration = TimeSpan.FromSeconds(i_Length); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Strangle, 1075794, 1075795, t_Duration, m, args)); - if ( t == null ) - return false; + FinishSequence(); + } - t.Stop(); - m.SendLocalizedMessage( 1061687 ); // You can breath normally again. + public static bool RemoveCurse(Mobile m) + { + Timer t = (Timer)m_Table[m]; - m_Table.Remove( m ); - return true; - } + if (t == null) + return false; - private class InternalTimer : Timer - { - private Mobile m_Target, m_From; - private double m_MinBaseDamage, m_MaxBaseDamage; + t.Stop(); + m.SendLocalizedMessage(1061687); // You can breath normally again. - private DateTime m_NextHit; - private int m_HitDelay; + m_Table.Remove(m); + return true; + } - private int m_Count, m_MaxCount; + private class InternalTimer : Timer + { + private int m_Count, m_MaxCount; + private int m_HitDelay; + private double m_MinBaseDamage, m_MaxBaseDamage; - public InternalTimer( Mobile target, Mobile from ) : base( TimeSpan.FromSeconds( 0.1 ), TimeSpan.FromSeconds( 0.1 ) ) - { - Priority = TimerPriority.FiftyMS; + private DateTime m_NextHit; + private Mobile m_Target, m_From; - m_Target = target; - m_From = from; + public InternalTimer(Mobile target, Mobile from) : base(TimeSpan.FromSeconds(0.1), TimeSpan.FromSeconds(0.1)) + { + Priority = TimerPriority.FiftyMS; - double spiritLevel = from.Skills[SkillName.SpiritSpeak].Value / 10; + m_Target = target; + m_From = from; - m_MinBaseDamage = spiritLevel - 2; - m_MaxBaseDamage = spiritLevel + 1; + double spiritLevel = from.Skills[SkillName.SpiritSpeak].Value / 10; - m_HitDelay = 5; - m_NextHit = DateTime.UtcNow + TimeSpan.FromSeconds( m_HitDelay ); + m_MinBaseDamage = spiritLevel - 2; + m_MaxBaseDamage = spiritLevel + 1; - m_Count = (int)spiritLevel; + m_HitDelay = 5; + m_NextHit = DateTime.UtcNow + TimeSpan.FromSeconds(m_HitDelay); - if ( m_Count < 4 ) - m_Count = 4; + m_Count = (int)spiritLevel; - m_MaxCount = m_Count; - } + if (m_Count < 4) + m_Count = 4; - protected override void OnTick() - { - if ( !m_Target.Alive ) - { - m_Table.Remove( m_Target ); - Stop(); - } + m_MaxCount = m_Count; + } - if ( !m_Target.Alive || DateTime.UtcNow < m_NextHit ) - return; + protected override void OnTick() + { + if (!m_Target.Alive) + { + m_Table.Remove(m_Target); + Stop(); + } - --m_Count; + if (!m_Target.Alive || DateTime.UtcNow < m_NextHit) + return; - if ( m_HitDelay > 1 ) - { - if ( m_MaxCount < 5 ) - { - --m_HitDelay; - } - else - { - int delay = (int)(Math.Ceiling( (1.0 + (5 * m_Count)) / m_MaxCount ) ); + --m_Count; - if ( delay <= 5 ) - m_HitDelay = delay; - else - m_HitDelay = 5; - } - } + if (m_HitDelay > 1) + { + if (m_MaxCount < 5) + { + --m_HitDelay; + } + else + { + int delay = (int)Math.Ceiling((1.0 + 5 * m_Count) / m_MaxCount); - if ( m_Count == 0 ) - { - m_Target.SendLocalizedMessage( 1061687 ); // You can breath normally again. - m_Table.Remove( m_Target ); - Stop(); - } - else - { - m_NextHit = DateTime.UtcNow + TimeSpan.FromSeconds( m_HitDelay ); + if (delay <= 5) + m_HitDelay = delay; + else + m_HitDelay = 5; + } + } - double damage = m_MinBaseDamage + (Utility.RandomDouble() * (m_MaxBaseDamage - m_MinBaseDamage)); + if (m_Count == 0) + { + m_Target.SendLocalizedMessage(1061687); // You can breath normally again. + m_Table.Remove(m_Target); + Stop(); + } + else + { + m_NextHit = DateTime.UtcNow + TimeSpan.FromSeconds(m_HitDelay); - damage *= (3 - (((double)m_Target.Stam / m_Target.StamMax) * 2)); + double damage = m_MinBaseDamage + Utility.RandomDouble() * (m_MaxBaseDamage - m_MinBaseDamage); - if ( damage < 1 ) - damage = 1; + damage *= 3 - (double)m_Target.Stam / m_Target.StamMax * 2; - if ( !m_Target.Player ) - damage *= 1.75; + if (damage < 1) + damage = 1; - AOS.Damage( m_Target, m_From, (int)damage, 0, 0, 0, 100, 0 ); + if (!m_Target.Player) + damage *= 1.75; - if ( 0.60 <= Utility.RandomDouble() ) // OSI: randomly revealed between first and third damage tick, guessing 60% chance - m_Target.RevealingAction(); - } - } - } + AOS.Damage(m_Target, m_From, (int)damage, 0, 0, 0, 100, 0); - private class InternalTarget : Target - { - private StrangleSpell m_Owner; + if (0.60 <= Utility.RandomDouble() + ) // OSI: randomly revealed between first and third damage tick, guessing 60% chance + m_Target.RevealingAction(); + } + } + } - public InternalTarget( StrangleSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + private class InternalTarget : Target + { + private StrangleSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + public InternalTarget(StrangleSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/SummonFamiliar.cs b/Scripts/Spells/Necromancy/SummonFamiliar.cs index a8c8ce0ea..546368457 100644 --- a/Scripts/Spells/Necromancy/SummonFamiliar.cs +++ b/Scripts/Spells/Necromancy/SummonFamiliar.cs @@ -1,203 +1,208 @@ using System; using System.Collections; -using Server.Network; using Server.Gumps; using Server.Mobiles; +using Server.Network; namespace Server.Spells.Necromancy { - public class SummonFamiliarSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Summon Familiar", "Kal Xen Bal", - 203, - 9031, - Reagent.BatWing, - Reagent.GraveDust, - Reagent.DaemonBlood - ); + public class SummonFamiliarSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Summon Familiar", "Kal Xen Bal", + 203, + 9031, + Reagent.BatWing, + Reagent.GraveDust, + Reagent.DaemonBlood + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public SummonFamiliarSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 30.0; - public override int RequiredMana => 17; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public SummonFamiliarSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 30.0; + public override int RequiredMana => 17; - public static Hashtable Table { get; } = new Hashtable(); + public static Hashtable Table{ get; } = new Hashtable(); - public override bool CheckCast() - { - BaseCreature check = (BaseCreature)Table[Caster]; + public static SummonFamiliarEntry[] Entries{ get; } = + { + new SummonFamiliarEntry(typeof(HordeMinionFamiliar), 1060146, 30.0, 30.0), // Horde Minion + new SummonFamiliarEntry(typeof(ShadowWispFamiliar), 1060142, 50.0, 50.0), // Shadow Wisp + new SummonFamiliarEntry(typeof(DarkWolfFamiliar), 1060143, 60.0, 60.0), // Dark Wolf + new SummonFamiliarEntry(typeof(DeathAdder), 1060145, 80.0, 80.0), // Death Adder + new SummonFamiliarEntry(typeof(VampireBatFamiliar), 1060144, 100.0, 100.0) // Vampire Bat + }; - if ( check != null && !check.Deleted ) - { - Caster.SendLocalizedMessage( 1061605 ); // You already have a familiar. - return false; - } + public override bool CheckCast() + { + BaseCreature check = (BaseCreature)Table[Caster]; - return base.CheckCast(); - } + if (check != null && !check.Deleted) + { + Caster.SendLocalizedMessage(1061605); // You already have a familiar. + return false; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.CloseGump( typeof( SummonFamiliarGump ) ); - Caster.SendGump( new SummonFamiliarGump( Caster, Entries, this ) ); - } + return base.CheckCast(); + } - FinishSequence(); - } + public override void OnCast() + { + if (CheckSequence()) + { + Caster.CloseGump(typeof(SummonFamiliarGump)); + Caster.SendGump(new SummonFamiliarGump(Caster, Entries, this)); + } - public static SummonFamiliarEntry[] Entries { get; } = - { - new SummonFamiliarEntry( typeof( HordeMinionFamiliar ), 1060146, 30.0, 30.0 ), // Horde Minion - new SummonFamiliarEntry( typeof( ShadowWispFamiliar ), 1060142, 50.0, 50.0 ), // Shadow Wisp - new SummonFamiliarEntry( typeof( DarkWolfFamiliar ), 1060143, 60.0, 60.0 ), // Dark Wolf - new SummonFamiliarEntry( typeof( DeathAdder ), 1060145, 80.0, 80.0 ), // Death Adder - new SummonFamiliarEntry( typeof( VampireBatFamiliar ), 1060144, 100.0, 100.0 ) // Vampire Bat - }; - } + FinishSequence(); + } + } - public class SummonFamiliarEntry - { - public Type Type { get; } + public class SummonFamiliarEntry + { + public SummonFamiliarEntry(Type type, object name, double reqNecromancy, double reqSpiritSpeak) + { + Type = type; + Name = name; + ReqNecromancy = reqNecromancy; + ReqSpiritSpeak = reqSpiritSpeak; + } - public object Name { get; } + public Type Type{ get; } - public double ReqNecromancy { get; } + public object Name{ get; } - public double ReqSpiritSpeak { get; } + public double ReqNecromancy{ get; } - public SummonFamiliarEntry( Type type, object name, double reqNecromancy, double reqSpiritSpeak ) - { - Type = type; - Name = name; - ReqNecromancy = reqNecromancy; - ReqSpiritSpeak = reqSpiritSpeak; - } - } + public double ReqSpiritSpeak{ get; } + } - public class SummonFamiliarGump : Gump - { - private Mobile m_From; - private SummonFamiliarEntry[] m_Entries; + public class SummonFamiliarGump : Gump + { + private const int EnabledColor16 = 0x0F20; + private const int DisabledColor16 = 0x262A; - private SummonFamiliarSpell m_Spell; + private const int EnabledColor32 = 0x18CD00; + private const int DisabledColor32 = 0x4A8B52; - private const int EnabledColor16 = 0x0F20; - private const int DisabledColor16 = 0x262A; + private static Hashtable m_Table = new Hashtable(); + private SummonFamiliarEntry[] m_Entries; + private Mobile m_From; - private const int EnabledColor32 = 0x18CD00; - private const int DisabledColor32 = 0x4A8B52; + private SummonFamiliarSpell m_Spell; - public SummonFamiliarGump( Mobile from, SummonFamiliarEntry[] entries, SummonFamiliarSpell spell ) : base( 200, 100 ) - { - m_From = from; - m_Entries = entries; - m_Spell = spell; + public SummonFamiliarGump(Mobile from, SummonFamiliarEntry[] entries, SummonFamiliarSpell spell) : base(200, 100) + { + m_From = from; + m_Entries = entries; + m_Spell = spell; - AddPage( 0 ); + AddPage(0); - AddBackground( 10, 10, 250, 178, 9270 ); - AddAlphaRegion( 20, 20, 230, 158 ); + AddBackground(10, 10, 250, 178, 9270); + AddAlphaRegion(20, 20, 230, 158); - AddImage( 220, 20, 10464 ); - AddImage( 220, 72, 10464 ); - AddImage( 220, 124, 10464 ); + AddImage(220, 20, 10464); + AddImage(220, 72, 10464); + AddImage(220, 124, 10464); - AddItem( 188, 16, 6883 ); - AddItem( 198, 168, 6881 ); - AddItem( 8, 15, 6882 ); - AddItem( 2, 168, 6880 ); + AddItem(188, 16, 6883); + AddItem(198, 168, 6881); + AddItem(8, 15, 6882); + AddItem(2, 168, 6880); - AddHtmlLocalized( 30, 26, 200, 20, 1060147, EnabledColor16, false, false ); // Chose thy familiar... + AddHtmlLocalized(30, 26, 200, 20, 1060147, EnabledColor16, false, false); // Chose thy familiar... - double necro = from.Skills[SkillName.Necromancy].Value; - double spirit = from.Skills[SkillName.SpiritSpeak].Value; + double necro = from.Skills[SkillName.Necromancy].Value; + double spirit = from.Skills[SkillName.SpiritSpeak].Value; - for ( int i = 0; i < entries.Length; ++i ) - { - object name = entries[i].Name; + for (int i = 0; i < entries.Length; ++i) + { + object name = entries[i].Name; - bool enabled = ( necro >= entries[i].ReqNecromancy && spirit >= entries[i].ReqSpiritSpeak ); + bool enabled = necro >= entries[i].ReqNecromancy && spirit >= entries[i].ReqSpiritSpeak; - AddButton( 27, 53 + (i * 21), 9702, 9703, i + 1, GumpButtonType.Reply, 0 ); + AddButton(27, 53 + i * 21, 9702, 9703, i + 1, GumpButtonType.Reply, 0); - if ( name is int ) - AddHtmlLocalized( 50, 51 + (i * 21), 150, 20, (int)name, enabled ? EnabledColor16 : DisabledColor16, false, false ); - else if ( name is string ) - AddHtml( 50, 51 + (i * 21), 150, 20, - $"{name}", false, false ); - } - } + if (name is int) + AddHtmlLocalized(50, 51 + i * 21, 150, 20, (int)name, enabled ? EnabledColor16 : DisabledColor16, false, + false); + else if (name is string) + AddHtml(50, 51 + i * 21, 150, 20, + $"{name}", false, + false); + } + } - private static Hashtable m_Table = new Hashtable(); + public override void OnResponse(NetState sender, RelayInfo info) + { + int index = info.ButtonID - 1; - public override void OnResponse( NetState sender, RelayInfo info ) - { - int index = info.ButtonID - 1; + if (index >= 0 && index < m_Entries.Length) + { + SummonFamiliarEntry entry = m_Entries[index]; - if ( index >= 0 && index < m_Entries.Length ) - { - SummonFamiliarEntry entry = m_Entries[index]; + double necro = m_From.Skills[SkillName.Necromancy].Value; + double spirit = m_From.Skills[SkillName.SpiritSpeak].Value; - double necro = m_From.Skills[SkillName.Necromancy].Value; - double spirit = m_From.Skills[SkillName.SpiritSpeak].Value; + BaseCreature check = (BaseCreature)SummonFamiliarSpell.Table[m_From]; - BaseCreature check = (BaseCreature)SummonFamiliarSpell.Table[m_From]; + #region Dueling - #region Dueling - if ( (m_From as PlayerMobile)?.DuelContext != null && !( (PlayerMobile)m_From ).DuelContext.AllowSpellCast( m_From, m_Spell ) ) - { - } - #endregion - else if ( check != null && !check.Deleted ) - { - m_From.SendLocalizedMessage( 1061605 ); // You already have a familiar. - } - else if ( necro < entry.ReqNecromancy || spirit < entry.ReqSpiritSpeak ) - { - // That familiar requires ~1_NECROMANCY~ Necromancy and ~2_SPIRIT~ Spirit Speak. - m_From.SendLocalizedMessage( 1061606, $"{entry.ReqNecromancy:F1}\t{entry.ReqSpiritSpeak:F1}"); + if ((m_From as PlayerMobile)?.DuelContext != null && + !((PlayerMobile)m_From).DuelContext.AllowSpellCast(m_From, m_Spell)) + { + } - m_From.CloseGump( typeof( SummonFamiliarGump ) ); - m_From.SendGump( new SummonFamiliarGump( m_From, SummonFamiliarSpell.Entries, m_Spell ) ); - } - else if ( entry.Type == null ) - { - m_From.SendMessage( "That familiar has not yet been defined." ); + #endregion - m_From.CloseGump( typeof( SummonFamiliarGump ) ); - m_From.SendGump( new SummonFamiliarGump( m_From, SummonFamiliarSpell.Entries, m_Spell ) ); - } - else - { - try - { - BaseCreature bc = (BaseCreature)Activator.CreateInstance( entry.Type ); + else if (check != null && !check.Deleted) + { + m_From.SendLocalizedMessage(1061605); // You already have a familiar. + } + else if (necro < entry.ReqNecromancy || spirit < entry.ReqSpiritSpeak) + { + // That familiar requires ~1_NECROMANCY~ Necromancy and ~2_SPIRIT~ Spirit Speak. + m_From.SendLocalizedMessage(1061606, $"{entry.ReqNecromancy:F1}\t{entry.ReqSpiritSpeak:F1}"); - bc.Skills.MagicResist = m_From.Skills.MagicResist; + m_From.CloseGump(typeof(SummonFamiliarGump)); + m_From.SendGump(new SummonFamiliarGump(m_From, SummonFamiliarSpell.Entries, m_Spell)); + } + else if (entry.Type == null) + { + m_From.SendMessage("That familiar has not yet been defined."); - if ( BaseCreature.Summon( bc, m_From, m_From.Location, -1, TimeSpan.FromDays( 1.0 ) ) ) - { - m_From.FixedParticles( 0x3728, 1, 10, 9910, EffectLayer.Head ); - bc.PlaySound( bc.GetIdleSound() ); - SummonFamiliarSpell.Table[m_From] = bc; - } - } - catch - { - } - } - } - else - { - m_From.SendLocalizedMessage( 1061825 ); // You decide not to summon a familiar. - } - } - } -} + m_From.CloseGump(typeof(SummonFamiliarGump)); + m_From.SendGump(new SummonFamiliarGump(m_From, SummonFamiliarSpell.Entries, m_Spell)); + } + else + { + try + { + BaseCreature bc = (BaseCreature)Activator.CreateInstance(entry.Type); + + bc.Skills.MagicResist = m_From.Skills.MagicResist; + + if (BaseCreature.Summon(bc, m_From, m_From.Location, -1, TimeSpan.FromDays(1.0))) + { + m_From.FixedParticles(0x3728, 1, 10, 9910, EffectLayer.Head); + bc.PlaySound(bc.GetIdleSound()); + SummonFamiliarSpell.Table[m_From] = bc; + } + } + catch + { + } + } + } + else + { + m_From.SendLocalizedMessage(1061825); // You decide not to summon a familiar. + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/TransformationSpell.cs b/Scripts/Spells/Necromancy/TransformationSpell.cs index a15abe2a9..a97434930 100644 --- a/Scripts/Spells/Necromancy/TransformationSpell.cs +++ b/Scripts/Spells/Necromancy/TransformationSpell.cs @@ -1,49 +1,48 @@ namespace Server.Spells.Necromancy { - public abstract class TransformationSpell : NecromancerSpell, ITransformationSpell - { - public abstract int Body{ get; } - public virtual int Hue => 0; + public abstract class TransformationSpell : NecromancerSpell, ITransformationSpell + { + public TransformationSpell(Mobile caster, Item scroll, SpellInfo info) : base(caster, scroll, info) + { + } - public virtual int PhysResistOffset => 0; - public virtual int FireResistOffset => 0; - public virtual int ColdResistOffset => 0; - public virtual int PoisResistOffset => 0; - public virtual int NrgyResistOffset => 0; + public override bool BlockedByHorrificBeast => false; + public abstract int Body{ get; } + public virtual int Hue => 0; - public TransformationSpell( Mobile caster, Item scroll, SpellInfo info ) : base( caster, scroll, info ) - { - } + public virtual int PhysResistOffset => 0; + public virtual int FireResistOffset => 0; + public virtual int ColdResistOffset => 0; + public virtual int PoisResistOffset => 0; + public virtual int NrgyResistOffset => 0; - public override bool BlockedByHorrificBeast => false; + public virtual double TickRate => 1.0; - public override bool CheckCast() - { - if ( !TransformationSpellHelper.CheckCast( Caster, this ) ) - return false; + public virtual void OnTick(Mobile m) + { + } - return base.CheckCast(); - } + public virtual void DoEffect(Mobile m) + { + } - public override void OnCast() - { - TransformationSpellHelper.OnCast( Caster, this ); + public virtual void RemoveEffect(Mobile m) + { + } - FinishSequence(); - } + public override bool CheckCast() + { + if (!TransformationSpellHelper.CheckCast(Caster, this)) + return false; - public virtual double TickRate => 1.0; + return base.CheckCast(); + } - public virtual void OnTick( Mobile m ) - { - } + public override void OnCast() + { + TransformationSpellHelper.OnCast(Caster, this); - public virtual void DoEffect( Mobile m ) - { - } - - public virtual void RemoveEffect( Mobile m ) - { - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/VampiricEmbrace.cs b/Scripts/Spells/Necromancy/VampiricEmbrace.cs index a14e25b71..c9f3cc843 100644 --- a/Scripts/Spells/Necromancy/VampiricEmbrace.cs +++ b/Scripts/Spells/Necromancy/VampiricEmbrace.cs @@ -3,49 +3,51 @@ using Server.Items; namespace Server.Spells.Necromancy { - public class VampiricEmbraceSpell : TransformationSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Vampiric Embrace", "Rel Xen An Sanct", - 203, - 9031, - Reagent.BatWing, - Reagent.NoxCrystal, - Reagent.PigIron - ); + public class VampiricEmbraceSpell : TransformationSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Vampiric Embrace", "Rel Xen An Sanct", + 203, + 9031, + Reagent.BatWing, + Reagent.NoxCrystal, + Reagent.PigIron + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public VampiricEmbraceSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 99.0; - public override int RequiredMana => 23; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public override int Body => Caster.Female ? 745 : 744; - public override int Hue => 0x847E; + public override double RequiredSkill => 99.0; + public override int RequiredMana => 23; - public override int FireResistOffset => -25; + public override int Body => Caster.Female ? 745 : 744; + public override int Hue => 0x847E; - public VampiricEmbraceSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override int FireResistOffset => -25; - public override void GetCastSkills( out double min, out double max ) - { - if ( Caster.Skills[CastSkill].Value >= RequiredSkill ) - { - min = 80.0; - max = 120.0; - } - else - { - base.GetCastSkills( out min, out max ); - } - } + public override void GetCastSkills(out double min, out double max) + { + if (Caster.Skills[CastSkill].Value >= RequiredSkill) + { + min = 80.0; + max = 120.0; + } + else + { + base.GetCastSkills(out min, out max); + } + } - public override void DoEffect( Mobile m ) - { - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x373A, 1, 17, 1108, 7, 9914, 0 ); - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x376A, 1, 22, 67, 7, 9502, 0 ); - Effects.PlaySound( m.Location, m.Map, 0x4B1 ); - } - } -} + public override void DoEffect(Mobile m) + { + Effects.SendLocationParticles(EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), 0x373A, 1, 17, + 1108, 7, 9914, 0); + Effects.SendLocationParticles(EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), 0x376A, 1, 22, + 67, 7, 9502, 0); + Effects.PlaySound(m.Location, m.Map, 0x4B1); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/VengefulSpirit.cs b/Scripts/Spells/Necromancy/VengefulSpirit.cs index bc41748f5..3b65bccf0 100644 --- a/Scripts/Spells/Necromancy/VengefulSpirit.cs +++ b/Scripts/Spells/Necromancy/VengefulSpirit.cs @@ -1,94 +1,95 @@ using System; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Necromancy { - public class VengefulSpiritSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Vengeful Spirit", "Kal Xen Bal Beh", - 203, - 9031, - Reagent.BatWing, - Reagent.GraveDust, - Reagent.PigIron - ); + public class VengefulSpiritSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Vengeful Spirit", "Kal Xen Bal Beh", + 203, + 9031, + Reagent.BatWing, + Reagent.GraveDust, + Reagent.PigIron + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public VengefulSpiritSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 80.0; - public override int RequiredMana => 41; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public VengefulSpiritSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 80.0; + public override int RequiredMana => 41; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 3) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 3 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public void Target( Mobile m ) - { - if ( Caster == m ) - { - Caster.SendLocalizedMessage( 1061832 ); // You cannot exact vengeance on yourself. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (Caster == m) + { + Caster.SendLocalizedMessage(1061832); // You cannot exact vengeance on yourself. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - /* Summons a Revenant which haunts the target until either the target or the Revenant is dead. - * Revenants have the ability to track down their targets wherever they may travel. - * A Revenant's strength is determined by the Necromancy and Spirit Speak skills of the Caster. - * The effect lasts for ((Spirit Speak skill level * 80) / 120) + 10 seconds. - */ + /* Summons a Revenant which haunts the target until either the target or the Revenant is dead. + * Revenants have the ability to track down their targets wherever they may travel. + * A Revenant's strength is determined by the Necromancy and Spirit Speak skills of the Caster. + * The effect lasts for ((Spirit Speak skill level * 80) / 120) + 10 seconds. + */ - TimeSpan duration = TimeSpan.FromSeconds( ((GetDamageSkill( Caster ) * 80) / 120) + 10 ); + TimeSpan duration = TimeSpan.FromSeconds(GetDamageSkill(Caster) * 80 / 120 + 10); - Revenant rev = new Revenant( Caster, m, duration ); + Revenant rev = new Revenant(Caster, m, duration); - if ( BaseCreature.Summon( rev, false, Caster, m.Location, 0x81, TimeSpan.FromSeconds( duration.TotalSeconds + 2.0 ) ) ) - rev.FixedParticles( 0x373A, 1, 15, 9909, EffectLayer.Waist ); - } + if (BaseCreature.Summon(rev, false, Caster, m.Location, 0x81, + TimeSpan.FromSeconds(duration.TotalSeconds + 2.0))) + rev.FixedParticles(0x373A, 1, 15, 9909, EffectLayer.Waist); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private VengefulSpiritSpell m_Owner; + private class InternalTarget : Target + { + private VengefulSpiritSpell m_Owner; - public InternalTarget( VengefulSpiritSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(VengefulSpiritSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/Wither.cs b/Scripts/Spells/Necromancy/Wither.cs index 2e1853bf6..61b9d9376 100644 --- a/Scripts/Spells/Necromancy/Wither.cs +++ b/Scripts/Spells/Necromancy/Wither.cs @@ -5,105 +5,105 @@ using Server.Mobiles; namespace Server.Spells.Necromancy { - public class WitherSpell : NecromancerSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Wither", "Kal Vas An Flam", - 203, - 9031, - Reagent.NoxCrystal, - Reagent.GraveDust, - Reagent.PigIron - ); + public class WitherSpell : NecromancerSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Wither", "Kal Vas An Flam", + 203, + 9031, + Reagent.NoxCrystal, + Reagent.GraveDust, + Reagent.PigIron + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public WitherSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 60.0; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public override int RequiredMana => 23; + public override double RequiredSkill => 60.0; - public WitherSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override int RequiredMana => 23; - public override bool DelayedDamage => false; + public override bool DelayedDamage => false; - public override void OnCast() - { - if ( CheckSequence() ) - { - /* Creates a withering frost around the Caster, - * which deals Cold Damage to all valid targets in a radius of 5 tiles. - */ + public override void OnCast() + { + if (CheckSequence()) + { + /* Creates a withering frost around the Caster, + * which deals Cold Damage to all valid targets in a radius of 5 tiles. + */ - Map map = Caster.Map; + Map map = Caster.Map; - if ( map != null ) - { - List targets = new List(); + if (map != null) + { + List targets = new List(); - BaseCreature cbc = Caster as BaseCreature; - bool isMonster = ( cbc != null && !cbc.Controlled && !cbc.Summoned ); + BaseCreature cbc = Caster as BaseCreature; + bool isMonster = cbc != null && !cbc.Controlled && !cbc.Summoned; - foreach( Mobile m in Caster.GetMobilesInRange( Core.ML ? 4 : 5 ) ) - { - if ( Caster != m && Caster.InLOS( m ) && ( isMonster || SpellHelper.ValidIndirectTarget( Caster, m ) ) && Caster.CanBeHarmful( m, false ) ) - { - if ( isMonster ) - { - if ( m is BaseCreature ) - { - BaseCreature bc = (BaseCreature)m; + foreach (Mobile m in Caster.GetMobilesInRange(Core.ML ? 4 : 5)) + if (Caster != m && Caster.InLOS(m) && (isMonster || SpellHelper.ValidIndirectTarget(Caster, m)) && + Caster.CanBeHarmful(m, false)) + { + if (isMonster) + { + if (m is BaseCreature) + { + BaseCreature bc = (BaseCreature)m; - if ( !bc.Controlled && !bc.Summoned && bc.Team == cbc.Team ) - continue; - } - else if ( !m.Player ) - { - continue; - } - } + if (!bc.Controlled && !bc.Summoned && bc.Team == cbc.Team) + continue; + } + else if (!m.Player) + { + continue; + } + } - targets.Add( m ); - } - } + targets.Add(m); + } - Effects.PlaySound( Caster.Location, map, 0x1FB ); - Effects.PlaySound( Caster.Location, map, 0x10B ); - Effects.SendLocationParticles( EffectItem.Create( Caster.Location, map, EffectItem.DefaultDuration ), 0x37CC, 1, 40, 97, 3, 9917, 0 ); + Effects.PlaySound(Caster.Location, map, 0x1FB); + Effects.PlaySound(Caster.Location, map, 0x10B); + Effects.SendLocationParticles(EffectItem.Create(Caster.Location, map, EffectItem.DefaultDuration), + 0x37CC, 1, 40, 97, 3, 9917, 0); - for( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[ i ]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - Caster.DoHarmful( m ); - m.FixedParticles( 0x374A, 1, 15, 9502, 97, 3, (EffectLayer)255 ); + Caster.DoHarmful(m); + m.FixedParticles(0x374A, 1, 15, 9502, 97, 3, (EffectLayer)255); - double damage = Utility.RandomMinMax( 30, 35 ); + double damage = Utility.RandomMinMax(30, 35); - damage *= ( 300 + ( m.Karma / 100 ) + ( GetDamageSkill( Caster ) * 10 ) ); - damage /= 1000; + damage *= 300 + m.Karma / 100 + GetDamageSkill(Caster) * 10; + damage /= 1000; - int sdiBonus = AosAttributes.GetValue( Caster, AosAttribute.SpellDamage ); + int sdiBonus = AosAttributes.GetValue(Caster, AosAttribute.SpellDamage); - // PvP spell damage increase cap of 15% from an item�s magic property in Publish 33(SE) - if ( Core.SE && m.Player && Caster.Player && sdiBonus > 15 ) - sdiBonus = 15; + // PvP spell damage increase cap of 15% from an item�s magic property in Publish 33(SE) + if (Core.SE && m.Player && Caster.Player && sdiBonus > 15) + sdiBonus = 15; - damage *= ( 100 + sdiBonus ); - damage /= 100; + damage *= 100 + sdiBonus; + damage /= 100; - // TODO: cap? - //if ( damage > 40 ) - // damage = 40; + // TODO: cap? + //if ( damage > 40 ) + // damage = 40; - SpellHelper.Damage( this, m, damage, 0, 0, 100, 0, 0 ); - } - } - } + SpellHelper.Damage(this, m, damage, 0, 0, 100, 0, 0); + } + } + } - FinishSequence(); - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Necromancy/WraithForm.cs b/Scripts/Spells/Necromancy/WraithForm.cs index 1603e045a..ba64c8f22 100644 --- a/Scripts/Spells/Necromancy/WraithForm.cs +++ b/Scripts/Spells/Necromancy/WraithForm.cs @@ -3,47 +3,47 @@ using Server.Mobiles; namespace Server.Spells.Necromancy { - public class WraithFormSpell : TransformationSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Wraith Form", "Rel Xen Um", - 203, - 9031, - Reagent.NoxCrystal, - Reagent.PigIron - ); + public class WraithFormSpell : TransformationSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Wraith Form", "Rel Xen Um", + 203, + 9031, + Reagent.NoxCrystal, + Reagent.PigIron + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public WraithFormSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 20.0; - public override int RequiredMana => 17; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public override int Body => Caster.Female ? 747 : 748; - public override int Hue => Caster.Female ? 0 : 0x4001; + public override double RequiredSkill => 20.0; + public override int RequiredMana => 17; - public override int PhysResistOffset => +15; - public override int FireResistOffset => -5; - public override int ColdResistOffset => 0; - public override int PoisResistOffset => 0; - public override int NrgyResistOffset => -5; + public override int Body => Caster.Female ? 747 : 748; + public override int Hue => Caster.Female ? 0 : 0x4001; - public WraithFormSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override int PhysResistOffset => +15; + public override int FireResistOffset => -5; + public override int ColdResistOffset => 0; + public override int PoisResistOffset => 0; + public override int NrgyResistOffset => -5; - public override void DoEffect( Mobile m ) - { - if ( m is PlayerMobile ) - ((PlayerMobile)m).IgnoreMobiles = true; + public override void DoEffect(Mobile m) + { + if (m is PlayerMobile) + ((PlayerMobile)m).IgnoreMobiles = true; - m.PlaySound( 0x17F ); - m.FixedParticles( 0x374A, 1, 15, 9902, 1108, 4, EffectLayer.Waist ); - } + m.PlaySound(0x17F); + m.FixedParticles(0x374A, 1, 15, 9902, 1108, 4, EffectLayer.Waist); + } - public override void RemoveEffect( Mobile m ) - { - if ( m is PlayerMobile && m.AccessLevel == AccessLevel.Player ) - ((PlayerMobile)m).IgnoreMobiles = false; - } - } -} + public override void RemoveEffect(Mobile m) + { + if (m is PlayerMobile && m.AccessLevel == AccessLevel.Player) + ((PlayerMobile)m).IgnoreMobiles = false; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/AnimalForm.cs b/Scripts/Spells/Ninjitsu/AnimalForm.cs index e8e9f9f2a..a8bf9b784 100644 --- a/Scripts/Spells/Ninjitsu/AnimalForm.cs +++ b/Scripts/Spells/Ninjitsu/AnimalForm.cs @@ -9,607 +9,626 @@ using Server.Spells.Seventh; namespace Server.Spells.Ninjitsu { - public class AnimalForm : NinjaSpell - { - public static void Initialize() - { - EventSink.Login += OnLogin; - } - - public static void OnLogin(LoginEventArgs e) - { - AnimalFormContext context = GetContext(e.Mobile); - - if (context != null && context.SpeedBoost) - e.Mobile.Send(SpeedControl.MountSpeed); - } - - private static SpellInfo m_Info = new SpellInfo( - "Animal Form", null, - -1, - 9002 - ); - - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - - public override double RequiredSkill => 0.0; - public override int RequiredMana => (Core.ML ? 10 : 0); - public override int CastRecoveryBase => (Core.ML ? 10 : base.CastRecoveryBase); - - public override bool BlockedByAnimalForm => false; - - public AnimalForm(Mobile caster, Item scroll) - : base(caster, scroll, m_Info) - { - } - - public override bool CheckCast() - { - if (!Caster.CanBeginAction(typeof(PolymorphSpell))) - { - Caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. - return false; - } - - if (TransformationSpellHelper.UnderTransformation(Caster)) - { - Caster.SendLocalizedMessage(1063219); // You cannot mimic an animal while in that form. - return false; - } - if (DisguiseTimers.IsDisguised(Caster)) - { - Caster.SendLocalizedMessage(1061631); // You can't do that while disguised. - return false; - } - - return base.CheckCast(); - } - - public override bool CheckDisturb(DisturbType type, bool firstCircle, bool resistable) - { - return false; - } - - private bool CasterIsMoving() - { - return (Core.TickCount - Caster.LastMoveTime <= Caster.ComputeMovementSpeed(Caster.Direction)); - } - - private bool m_WasMoving; - - public override void OnBeginCast() - { - base.OnBeginCast(); - - Caster.FixedEffect(0x37C4, 10, 14, 4, 3); - m_WasMoving = CasterIsMoving(); - } - - public override bool CheckFizzle() - { - // Spell is initially always successful, and with no skill gain. - return true; - } - - public override void OnCast() - { - if (!Caster.CanBeginAction(typeof(PolymorphSpell))) - { - Caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. - } - else if (TransformationSpellHelper.UnderTransformation(Caster)) - { - Caster.SendLocalizedMessage(1063219); // You cannot mimic an animal while in that form. - } - else if (!Caster.CanBeginAction(typeof(IncognitoSpell)) || (Caster.IsBodyMod && GetContext(Caster) == null)) - { - DoFizzle(); - } - else if (CheckSequence()) - { - AnimalFormContext context = GetContext(Caster); - - int mana = ScaleMana(RequiredMana); - if (mana > Caster.Mana) - { - Caster.SendLocalizedMessage(1060174, mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - } - else if (context != null) - { - RemoveContext(Caster, context, true); - Caster.Mana -= mana; - } - else if (Caster is PlayerMobile) - { - bool skipGump = (m_WasMoving || CasterIsMoving()); - - if (GetLastAnimalForm(Caster) == -1 || !skipGump) - { - Caster.CloseGump(typeof(AnimalFormGump)); - Caster.SendGump(new AnimalFormGump(Caster, Entries, this)); - } - else - { - if (Morph(Caster, GetLastAnimalForm(Caster)) == MorphResult.Fail) - { - DoFizzle(); - } - else - { - Caster.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); - Caster.Mana -= mana; - } - } - } - else - { - if (Morph(Caster, GetLastAnimalForm(Caster)) == MorphResult.Fail) - { - DoFizzle(); - } - else - { - Caster.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); - Caster.Mana -= mana; - } - } - } - - FinishSequence(); - } - - private static Hashtable m_LastAnimalForms = new Hashtable(); - - public int GetLastAnimalForm(Mobile m) - { - if (m_LastAnimalForms.Contains(m)) - return (int)m_LastAnimalForms[m]; - - return -1; - } - - public enum MorphResult - { - Success, - Fail, - NoSkill - } - - public static MorphResult Morph(Mobile m, int entryID) - { - if (entryID < 0 || entryID >= Entries.Length) - return MorphResult.Fail; - - AnimalFormEntry entry = Entries[entryID]; - - m_LastAnimalForms[m] = entryID; //On OSI, it's the last /attempted/ one not the last succeeded one - - if (m.Skills.Ninjitsu.Value < entry.ReqSkill) - { - string args = $"{entry.ReqSkill.ToString("F1")}\t{SkillName.Ninjitsu}\t "; - m.SendLocalizedMessage(1063013, args); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - return MorphResult.NoSkill; - } - - /* - if ( !m.CheckSkill( SkillName.Ninjitsu, entry.ReqSkill, entry.ReqSkill + 37.5 ) ) - return MorphResult.Fail; - * - * On OSI,it seems you can only gain starting at '0' using Animal form. - */ - - double ninjitsu = m.Skills.Ninjitsu.Value; - - if (ninjitsu < entry.ReqSkill + 37.5) - { - double chance = (ninjitsu - entry.ReqSkill) / 37.5; - - if (chance < Utility.RandomDouble()) - return MorphResult.Fail; - } - - m.CheckSkill(SkillName.Ninjitsu, 0.0, 37.5); - - if (!BaseFormTalisman.EntryEnabled(m, entry.Type)) - return MorphResult.Success; // Still consumes mana, just no effect - - BaseMount.Dismount(m); - - int bodyMod = entry.BodyMod; - int hueMod = entry.HueMod; - - m.BodyMod = bodyMod; - m.HueMod = hueMod; - - if (entry.SpeedBoost) - m.Send(SpeedControl.MountSpeed); - - SkillMod mod = null; - - if (entry.StealthBonus) - { - mod = new DefaultSkillMod(SkillName.Stealth, true, 20.0); - mod.ObeyCap = true; - m.AddSkillMod(mod); - } + public class AnimalForm : NinjaSpell + { + public enum MorphResult + { + Success, + Fail, + NoSkill + } + + private static SpellInfo m_Info = new SpellInfo( + "Animal Form", null, + -1, + 9002 + ); + + private static Hashtable m_LastAnimalForms = new Hashtable(); + + private static Hashtable m_Table = new Hashtable(); + + private bool m_WasMoving; + + public AnimalForm(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } + + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); + + public override double RequiredSkill => 0.0; + public override int RequiredMana => Core.ML ? 10 : 0; + public override int CastRecoveryBase => Core.ML ? 10 : base.CastRecoveryBase; + + public override bool BlockedByAnimalForm => false; + + public static AnimalFormEntry[] Entries{ get; } = + { + new AnimalFormEntry(typeof(Kirin), 1029632, 9632, 0, 1070811, 100.0, 0x84, 0, 0, false, true, false), + new AnimalFormEntry(typeof(Unicorn), 1018214, 9678, 0, 1070812, 100.0, 0x7A, 0, 0, false, true, false), + new AnimalFormEntry(typeof(BakeKitsune), 1030083, 10083, 0, 1070810, 82.5, 0xF6, 0, 0, false, true, false), + new AnimalFormEntry(typeof(GreyWolf), 1028482, 9681, 2309, 1070810, 82.5, 0x19, 0x8FD, 0x90E, false, true, + false), + new AnimalFormEntry(typeof(Llama), 1028438, 8438, 0, 1070809, 70.0, 0xDC, 0, 0, false, true, false), + new AnimalFormEntry(typeof(ForestOstard), 1018273, 8503, 2212, 1070809, 70.0, 0xDB, 0x899, 0x8B0, false, true, + false), + new AnimalFormEntry(typeof(BullFrog), 1028496, 8496, 2003, 1070807, 50.0, 0x51, 0x7D1, 0x7D6, false, false, + false), + new AnimalFormEntry(typeof(GiantSerpent), 1018114, 9663, 2009, 1070808, 50.0, 0x15, 0x7D1, 0x7E2, false, false, + false), + new AnimalFormEntry(typeof(Dog), 1018280, 8476, 2309, 1070806, 40.0, 0xD9, 0x8FD, 0x90E, false, false, false), + new AnimalFormEntry(typeof(Cat), 1018264, 8475, 2309, 1070806, 40.0, 0xC9, 0x8FD, 0x90E, false, false, false), + new AnimalFormEntry(typeof(Rat), 1018294, 8483, 2309, 1070805, 20.0, 0xEE, 0x8FD, 0x90E, true, false, false), + new AnimalFormEntry(typeof(Rabbit), 1028485, 8485, 2309, 1070805, 20.0, 0xCD, 0x8FD, 0x90E, true, false, false), + new AnimalFormEntry(typeof(Squirrel), 1031671, 11671, 0, 0, 20.0, 0x116, 0, 0, false, false, false), + new AnimalFormEntry(typeof(Ferret), 1031672, 11672, 0, 1075220, 40.0, 0x117, 0, 0, false, false, true), + new AnimalFormEntry(typeof(CuSidhe), 1031670, 11670, 0, 1075221, 60.0, 0x115, 0, 0, false, false, false), + new AnimalFormEntry(typeof(Reptalon), 1075202, 11669, 0, 1075222, 90.0, 0x114, 0, 0, false, false, false) + }; + + public static void Initialize() + { + EventSink.Login += OnLogin; + } + + public static void OnLogin(LoginEventArgs e) + { + AnimalFormContext context = GetContext(e.Mobile); + + if (context != null && context.SpeedBoost) + e.Mobile.Send(SpeedControl.MountSpeed); + } + + public override bool CheckCast() + { + if (!Caster.CanBeginAction(typeof(PolymorphSpell))) + { + Caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + return false; + } + + if (TransformationSpellHelper.UnderTransformation(Caster)) + { + Caster.SendLocalizedMessage(1063219); // You cannot mimic an animal while in that form. + return false; + } + + if (DisguiseTimers.IsDisguised(Caster)) + { + Caster.SendLocalizedMessage(1061631); // You can't do that while disguised. + return false; + } + + return base.CheckCast(); + } + + public override bool CheckDisturb(DisturbType type, bool firstCircle, bool resistable) + { + return false; + } + + private bool CasterIsMoving() + { + return Core.TickCount - Caster.LastMoveTime <= Caster.ComputeMovementSpeed(Caster.Direction); + } + + public override void OnBeginCast() + { + base.OnBeginCast(); + + Caster.FixedEffect(0x37C4, 10, 14, 4, 3); + m_WasMoving = CasterIsMoving(); + } + + public override bool CheckFizzle() + { + // Spell is initially always successful, and with no skill gain. + return true; + } + + public override void OnCast() + { + if (!Caster.CanBeginAction(typeof(PolymorphSpell))) + { + Caster.SendLocalizedMessage(1061628); // You can't do that while polymorphed. + } + else if (TransformationSpellHelper.UnderTransformation(Caster)) + { + Caster.SendLocalizedMessage(1063219); // You cannot mimic an animal while in that form. + } + else if (!Caster.CanBeginAction(typeof(IncognitoSpell)) || Caster.IsBodyMod && GetContext(Caster) == null) + { + DoFizzle(); + } + else if (CheckSequence()) + { + AnimalFormContext context = GetContext(Caster); + + int mana = ScaleMana(RequiredMana); + if (mana > Caster.Mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + } + else if (context != null) + { + RemoveContext(Caster, context, true); + Caster.Mana -= mana; + } + else if (Caster is PlayerMobile) + { + bool skipGump = m_WasMoving || CasterIsMoving(); + + if (GetLastAnimalForm(Caster) == -1 || !skipGump) + { + Caster.CloseGump(typeof(AnimalFormGump)); + Caster.SendGump(new AnimalFormGump(Caster, Entries, this)); + } + else + { + if (Morph(Caster, GetLastAnimalForm(Caster)) == MorphResult.Fail) + { + DoFizzle(); + } + else + { + Caster.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); + Caster.Mana -= mana; + } + } + } + else + { + if (Morph(Caster, GetLastAnimalForm(Caster)) == MorphResult.Fail) + { + DoFizzle(); + } + else + { + Caster.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); + Caster.Mana -= mana; + } + } + } + + FinishSequence(); + } + + public int GetLastAnimalForm(Mobile m) + { + if (m_LastAnimalForms.Contains(m)) + return (int)m_LastAnimalForms[m]; + + return -1; + } + + public static MorphResult Morph(Mobile m, int entryID) + { + if (entryID < 0 || entryID >= Entries.Length) + return MorphResult.Fail; + + AnimalFormEntry entry = Entries[entryID]; + + m_LastAnimalForms[m] = entryID; //On OSI, it's the last /attempted/ one not the last succeeded one + + if (m.Skills.Ninjitsu.Value < entry.ReqSkill) + { + string args = $"{entry.ReqSkill.ToString("F1")}\t{SkillName.Ninjitsu}\t "; + m.SendLocalizedMessage(1063013, + args); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + return MorphResult.NoSkill; + } + + /* + if ( !m.CheckSkill( SkillName.Ninjitsu, entry.ReqSkill, entry.ReqSkill + 37.5 ) ) + return MorphResult.Fail; + * + * On OSI,it seems you can only gain starting at '0' using Animal form. + */ + + double ninjitsu = m.Skills.Ninjitsu.Value; + + if (ninjitsu < entry.ReqSkill + 37.5) + { + double chance = (ninjitsu - entry.ReqSkill) / 37.5; + + if (chance < Utility.RandomDouble()) + return MorphResult.Fail; + } + + m.CheckSkill(SkillName.Ninjitsu, 0.0, 37.5); + + if (!BaseFormTalisman.EntryEnabled(m, entry.Type)) + return MorphResult.Success; // Still consumes mana, just no effect + + BaseMount.Dismount(m); + + int bodyMod = entry.BodyMod; + int hueMod = entry.HueMod; + + m.BodyMod = bodyMod; + m.HueMod = hueMod; + + if (entry.SpeedBoost) + m.Send(SpeedControl.MountSpeed); + + SkillMod mod = null; + + if (entry.StealthBonus) + { + mod = new DefaultSkillMod(SkillName.Stealth, true, 20.0); + mod.ObeyCap = true; + m.AddSkillMod(mod); + } + + SkillMod stealingMod = null; + + if (entry.StealingBonus) + { + stealingMod = new DefaultSkillMod(SkillName.Stealing, true, 10.0); + stealingMod.ObeyCap = true; + m.AddSkillMod(stealingMod); + } + + Timer timer = new AnimalFormTimer(m, bodyMod, hueMod); + timer.Start(); + + AddContext(m, new AnimalFormContext(timer, mod, entry.SpeedBoost, entry.Type, stealingMod)); + m.CheckStatTimers(); + return MorphResult.Success; + } + + public static void AddContext(Mobile m, AnimalFormContext context) + { + m_Table[m] = context; - SkillMod stealingMod = null; + if (context.Type == typeof(BakeKitsune) || context.Type == typeof(GreyWolf)) + m.CheckStatTimers(); + } - if (entry.StealingBonus) - { - stealingMod = new DefaultSkillMod(SkillName.Stealing, true, 10.0); - stealingMod.ObeyCap = true; - m.AddSkillMod(stealingMod); - } + public static void RemoveContext(Mobile m, bool resetGraphics) + { + AnimalFormContext context = GetContext(m); - Timer timer = new AnimalFormTimer(m, bodyMod, hueMod); - timer.Start(); + if (context != null) + RemoveContext(m, context, resetGraphics); + } - AddContext(m, new AnimalFormContext(timer, mod, entry.SpeedBoost, entry.Type, stealingMod)); - m.CheckStatTimers(); - return MorphResult.Success; - } + public static void RemoveContext(Mobile m, AnimalFormContext context, bool resetGraphics) + { + m_Table.Remove(m); - private static Hashtable m_Table = new Hashtable(); + if (context.SpeedBoost) + m.Send(SpeedControl.Disable); - public static void AddContext(Mobile m, AnimalFormContext context) - { - m_Table[m] = context; + SkillMod mod = context.Mod; - if (context.Type == typeof(BakeKitsune) || context.Type == typeof(GreyWolf)) - m.CheckStatTimers(); - } + if (mod != null) + m.RemoveSkillMod(mod); - public static void RemoveContext(Mobile m, bool resetGraphics) - { - AnimalFormContext context = GetContext(m); + mod = context.StealingMod; - if (context != null) - RemoveContext(m, context, resetGraphics); - } + if (mod != null) + m.RemoveSkillMod(mod); - public static void RemoveContext(Mobile m, AnimalFormContext context, bool resetGraphics) - { - m_Table.Remove(m); + if (resetGraphics) + { + m.HueMod = -1; + m.BodyMod = 0; + } - if (context.SpeedBoost) - m.Send(SpeedControl.Disable); + m.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); - SkillMod mod = context.Mod; + context.Timer.Stop(); + } - if (mod != null) - m.RemoveSkillMod(mod); + public static AnimalFormContext GetContext(Mobile m) + { + return m_Table[m] as AnimalFormContext; + } - mod = context.StealingMod; + public static bool UnderTransformation(Mobile m) + { + return GetContext(m) != null; + } - if (mod != null) - m.RemoveSkillMod(mod); - - if (resetGraphics) - { - m.HueMod = -1; - m.BodyMod = 0; - } - - m.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); - - context.Timer.Stop(); - } - - public static AnimalFormContext GetContext(Mobile m) - { - return (m_Table[m] as AnimalFormContext); - } - - public static bool UnderTransformation(Mobile m) - { - return (GetContext(m) != null); - } - - public static bool UnderTransformation(Mobile m, Type type) - { - AnimalFormContext context = GetContext(m); - - return (context != null && context.Type == type); - } - - /* - private delegate void AnimalFormCallback( Mobile from ); - private delegate bool AnimalFormRequirementCallback( Mobile from ); - */ - - public class AnimalFormEntry - { - private int m_HueModMin; - private int m_HueModMax; - - public Type Type { get; } - - public TextDefinition Name { get; } - - public int ItemID { get; } - - public int Hue { get; } - - public int Tooltip { get; } - - public double ReqSkill { get; } - - public int BodyMod { get; } - - public int HueMod => Utility.RandomMinMax( m_HueModMin, m_HueModMax ); - public bool StealthBonus { get; } - - public bool SpeedBoost { get; } - - public bool StealingBonus { get; } - /* - private AnimalFormCallback m_TransformCallback; - private AnimalFormCallback m_UntransformCallback; - private AnimalFormRequirementCallback m_RequirementCallback; - */ - - public AnimalFormEntry(Type type, TextDefinition name, int itemID, int hue, int tooltip, double reqSkill, int bodyMod, int hueModMin, int hueModMax, bool stealthBonus, bool speedBoost, bool stealingBonus) - { - Type = type; - Name = name; - ItemID = itemID; - Hue = hue; - Tooltip = tooltip; - ReqSkill = reqSkill; - BodyMod = bodyMod; - m_HueModMin = hueModMin; - m_HueModMax = hueModMax; - StealthBonus = stealthBonus; - SpeedBoost = speedBoost; - StealingBonus = stealingBonus; - } - } - - public static AnimalFormEntry[] Entries { get; } = - { - new AnimalFormEntry( typeof( Kirin ), 1029632, 9632, 0, 1070811, 100.0, 0x84, 0, 0, false, true, false ), - new AnimalFormEntry( typeof( Unicorn ), 1018214, 9678, 0, 1070812, 100.0, 0x7A, 0, 0, false, true, false ), - new AnimalFormEntry( typeof( BakeKitsune ), 1030083, 10083, 0, 1070810, 82.5, 0xF6, 0, 0, false, true, false ), - new AnimalFormEntry( typeof( GreyWolf ), 1028482, 9681, 2309, 1070810, 82.5, 0x19, 0x8FD, 0x90E, false, true, false ), - new AnimalFormEntry( typeof( Llama ), 1028438, 8438, 0, 1070809, 70.0, 0xDC, 0, 0, false, true, false ), - new AnimalFormEntry( typeof( ForestOstard ), 1018273, 8503, 2212, 1070809, 70.0, 0xDB, 0x899, 0x8B0, false, true, false ), - new AnimalFormEntry( typeof( BullFrog ), 1028496, 8496, 2003, 1070807, 50.0, 0x51, 0x7D1, 0x7D6, false, false, false ), - new AnimalFormEntry( typeof( GiantSerpent ), 1018114, 9663, 2009, 1070808, 50.0, 0x15, 0x7D1, 0x7E2, false, false, false ), - new AnimalFormEntry( typeof( Dog ), 1018280, 8476, 2309, 1070806, 40.0, 0xD9, 0x8FD, 0x90E, false, false, false ), - new AnimalFormEntry( typeof( Cat ), 1018264, 8475, 2309, 1070806, 40.0, 0xC9, 0x8FD, 0x90E, false, false, false ), - new AnimalFormEntry( typeof( Rat ), 1018294, 8483, 2309, 1070805, 20.0, 0xEE, 0x8FD, 0x90E, true, false, false ), - new AnimalFormEntry( typeof( Rabbit ), 1028485, 8485, 2309, 1070805, 20.0, 0xCD, 0x8FD, 0x90E, true, false, false ), - new AnimalFormEntry( typeof( Squirrel ), 1031671, 11671, 0, 0, 20.0, 0x116, 0, 0, false, false, false ), - new AnimalFormEntry( typeof( Ferret ), 1031672, 11672, 0, 1075220, 40.0, 0x117, 0, 0, false, false, true ), - new AnimalFormEntry( typeof( CuSidhe ), 1031670, 11670, 0, 1075221, 60.0, 0x115, 0, 0, false, false, false ), - new AnimalFormEntry( typeof( Reptalon ), 1075202, 11669, 0, 1075222, 90.0, 0x114, 0, 0, false, false, false ), - }; - - public class AnimalFormGump : Gump - { - //TODO: Convert this for ML to the BaseImageTileButtonsgump - private Mobile m_Caster; - private AnimalForm m_Spell; - private Item m_Talisman; - - public AnimalFormGump(Mobile caster, AnimalFormEntry[] entries, AnimalForm spell) - : base(50, 50) - { - m_Caster = caster; - m_Spell = spell; - m_Talisman = caster.Talisman; - - AddPage(0); - - AddBackground(0, 0, 520, 404, 0x13BE); - AddImageTiled(10, 10, 500, 20, 0xA40); - AddImageTiled(10, 40, 500, 324, 0xA40); - AddImageTiled(10, 374, 500, 20, 0xA40); - AddAlphaRegion(10, 10, 500, 384); - - AddHtmlLocalized(14, 12, 500, 20, 1063394, 0x7FFF, false, false); //
Polymorph Selection Menu
- - AddButton(10, 374, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); - AddHtmlLocalized(45, 376, 450, 20, 1011012, 0x7FFF, false, false); // CANCEL - - double ninjitsu = caster.Skills.Ninjitsu.Value; - - int current = 0; - - for (int i = 0; i < entries.Length; ++i) - { - bool enabled = (ninjitsu >= entries[i].ReqSkill && BaseFormTalisman.EntryEnabled(caster, entries[i].Type)); - - int page = current / 10 + 1; - int pos = current % 10; - - if (pos == 0) - { - if (page > 1) - { - AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, page); - AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next - } - - AddPage(page); - - if (page > 1) - { - AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1); - AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back - } - } - - if (enabled) - { - int x = (pos % 2 == 0) ? 14 : 264; - int y = (pos / 2) * 64 + 44; - - Rectangle2D b = ItemBounds.Table[entries[i].ItemID]; - - AddImageTiledButton(x, y, 0x918, 0x919, i + 1, GumpButtonType.Reply, 0, entries[i].ItemID, entries[i].Hue, 40 - b.Width / 2 - b.X, 30 - b.Height / 2 - b.Y, entries[i].Tooltip); - AddHtmlLocalized(x + 84, y, 250, 60, entries[i].Name, 0x7FFF, false, false); - - current++; - } - } - } - - public override void OnResponse(NetState sender, RelayInfo info) - { - int entryID = info.ButtonID - 1; - - if (entryID < 0 || entryID >= AnimalForm.Entries.Length) - return; - - int mana = m_Spell.ScaleMana(m_Spell.RequiredMana); - AnimalFormEntry entry = AnimalForm.Entries[entryID]; - - if (mana > m_Caster.Mana) - { - m_Caster.SendLocalizedMessage(1060174, mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - } - else if ( ( m_Caster is PlayerMobile ) && ( m_Caster as PlayerMobile ).MountBlockReason != BlockMountType.None ) - { - m_Caster.SendLocalizedMessage( 1063108 ); // You cannot use this ability right now. - } - else if (BaseFormTalisman.EntryEnabled(sender.Mobile, entry.Type)) - { - #region Dueling - if ( (m_Caster as PlayerMobile)?.DuelContext != null && !((PlayerMobile)m_Caster).DuelContext.AllowSpellCast( m_Caster, m_Spell ) ) - { - } - #endregion - else if (Morph(m_Caster, entryID) == MorphResult.Fail) - { - m_Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 502632 ); // The spell fizzles. - m_Caster.FixedParticles( 0x3735, 1, 30, 9503, EffectLayer.Waist ); - m_Caster.PlaySound( 0x5C ); - } - else - { - m_Caster.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); - m_Caster.Mana -= mana; - } - } - } - } - } - - public class AnimalFormContext - { - public Timer Timer { get; } - - public SkillMod Mod { get; } - - public bool SpeedBoost { get; } - - public Type Type { get; } - - public SkillMod StealingMod { get; } - - public AnimalFormContext(Timer timer, SkillMod mod, bool speedBoost, Type type, SkillMod stealingMod) - { - Timer = timer; - Mod = mod; - SpeedBoost = speedBoost; - Type = type; - StealingMod = stealingMod; - } - } - - public class AnimalFormTimer : Timer - { - private Mobile m_Mobile; - private int m_Body; - private int m_Hue; - private int m_Counter; - private Mobile m_LastTarget; - - public AnimalFormTimer(Mobile from, int body, int hue) - : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) - { - m_Mobile = from; - m_Body = body; - m_Hue = hue; - m_Counter = 0; - - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - if (m_Mobile.Deleted || !m_Mobile.Alive || m_Mobile.Body != m_Body || m_Mobile.Hue != m_Hue) - { - AnimalForm.RemoveContext(m_Mobile, true); - Stop(); - } - else - { - if (m_Body == 0x115) // Cu Sidhe - { - if (m_Counter++ >= 8) - { - if (m_Mobile.Hits < m_Mobile.HitsMax && m_Mobile.Backpack != null) - { - Bandage b = m_Mobile.Backpack.FindItemByType(typeof(Bandage)) as Bandage; - - if (b != null) - { - m_Mobile.Hits += Utility.RandomMinMax(20, 50); - b.Consume(); - } - } - - m_Counter = 0; - } - } - else if (m_Body == 0x114) // Reptalon - { - if (m_Mobile.Combatant != null && m_Mobile.Combatant != m_LastTarget) - { - m_Counter = 1; - m_LastTarget = m_Mobile.Combatant; - } - - if (m_Mobile.Warmode && m_LastTarget != null && m_LastTarget.Alive && !m_LastTarget.Deleted && m_Counter-- <= 0) - { - if (m_Mobile.CanBeHarmful(m_LastTarget) && m_LastTarget.Map == m_Mobile.Map && m_LastTarget.InRange(m_Mobile.Location, BaseCreature.DefaultRangePerception) && m_Mobile.InLOS(m_LastTarget)) - { - m_Mobile.Direction = m_Mobile.GetDirectionTo(m_LastTarget); - m_Mobile.Freeze(TimeSpan.FromSeconds(1)); - m_Mobile.PlaySound(0x16A); - - DelayCall(TimeSpan.FromSeconds(1.3), BreathEffect_Callback, m_LastTarget); - } - - m_Counter = Math.Min((int)m_Mobile.GetDistanceToSqrt(m_LastTarget), 10); - } - } - } - } - - public void BreathEffect_Callback(Mobile target) - { - if (m_Mobile.CanBeHarmful(target)) - { - m_Mobile.RevealingAction(); - m_Mobile.PlaySound(0x227); - Effects.SendMovingEffect(m_Mobile, target, 0x36D4, 5, 0, false, false, 0, 0); - - DelayCall(TimeSpan.FromSeconds(1), BreathDamage_Callback, target); - } - } - - public void BreathDamage_Callback(Mobile target) - { - if (m_Mobile.CanBeHarmful(target)) - { - m_Mobile.RevealingAction(); - m_Mobile.DoHarmful(target); - AOS.Damage(target, m_Mobile, 20, !target.Player, 0, 100, 0, 0, 0); - } - } - } -} + public static bool UnderTransformation(Mobile m, Type type) + { + AnimalFormContext context = GetContext(m); + + return context != null && context.Type == type; + } + + /* + private delegate void AnimalFormCallback( Mobile from ); + private delegate bool AnimalFormRequirementCallback( Mobile from ); + */ + + public class AnimalFormEntry + { + private int m_HueModMax; + + private int m_HueModMin; + /* + private AnimalFormCallback m_TransformCallback; + private AnimalFormCallback m_UntransformCallback; + private AnimalFormRequirementCallback m_RequirementCallback; + */ + + public AnimalFormEntry(Type type, TextDefinition name, int itemID, int hue, int tooltip, double reqSkill, + int bodyMod, int hueModMin, int hueModMax, bool stealthBonus, bool speedBoost, bool stealingBonus) + { + Type = type; + Name = name; + ItemID = itemID; + Hue = hue; + Tooltip = tooltip; + ReqSkill = reqSkill; + BodyMod = bodyMod; + m_HueModMin = hueModMin; + m_HueModMax = hueModMax; + StealthBonus = stealthBonus; + SpeedBoost = speedBoost; + StealingBonus = stealingBonus; + } + + public Type Type{ get; } + + public TextDefinition Name{ get; } + + public int ItemID{ get; } + + public int Hue{ get; } + + public int Tooltip{ get; } + + public double ReqSkill{ get; } + + public int BodyMod{ get; } + + public int HueMod => Utility.RandomMinMax(m_HueModMin, m_HueModMax); + public bool StealthBonus{ get; } + + public bool SpeedBoost{ get; } + + public bool StealingBonus{ get; } + } + + public class AnimalFormGump : Gump + { + //TODO: Convert this for ML to the BaseImageTileButtonsgump + private Mobile m_Caster; + private AnimalForm m_Spell; + private Item m_Talisman; + + public AnimalFormGump(Mobile caster, AnimalFormEntry[] entries, AnimalForm spell) + : base(50, 50) + { + m_Caster = caster; + m_Spell = spell; + m_Talisman = caster.Talisman; + + AddPage(0); + + AddBackground(0, 0, 520, 404, 0x13BE); + AddImageTiled(10, 10, 500, 20, 0xA40); + AddImageTiled(10, 40, 500, 324, 0xA40); + AddImageTiled(10, 374, 500, 20, 0xA40); + AddAlphaRegion(10, 10, 500, 384); + + AddHtmlLocalized(14, 12, 500, 20, 1063394, 0x7FFF, false, + false); //
Polymorph Selection Menu
+ + AddButton(10, 374, 0xFB1, 0xFB2, 0, GumpButtonType.Reply, 0); + AddHtmlLocalized(45, 376, 450, 20, 1011012, 0x7FFF, false, false); // CANCEL + + double ninjitsu = caster.Skills.Ninjitsu.Value; + + int current = 0; + + for (int i = 0; i < entries.Length; ++i) + { + bool enabled = ninjitsu >= entries[i].ReqSkill && BaseFormTalisman.EntryEnabled(caster, entries[i].Type); + + int page = current / 10 + 1; + int pos = current % 10; + + if (pos == 0) + { + if (page > 1) + { + AddButton(400, 374, 0xFA5, 0xFA7, 0, GumpButtonType.Page, page); + AddHtmlLocalized(440, 376, 60, 20, 1043353, 0x7FFF, false, false); // Next + } + + AddPage(page); + + if (page > 1) + { + AddButton(300, 374, 0xFAE, 0xFB0, 0, GumpButtonType.Page, 1); + AddHtmlLocalized(340, 376, 60, 20, 1011393, 0x7FFF, false, false); // Back + } + } + + if (enabled) + { + int x = pos % 2 == 0 ? 14 : 264; + int y = pos / 2 * 64 + 44; + + Rectangle2D b = ItemBounds.Table[entries[i].ItemID]; + + AddImageTiledButton(x, y, 0x918, 0x919, i + 1, GumpButtonType.Reply, 0, entries[i].ItemID, + entries[i].Hue, 40 - b.Width / 2 - b.X, 30 - b.Height / 2 - b.Y, entries[i].Tooltip); + AddHtmlLocalized(x + 84, y, 250, 60, entries[i].Name, 0x7FFF, false, false); + + current++; + } + } + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + int entryID = info.ButtonID - 1; + + if (entryID < 0 || entryID >= AnimalForm.Entries.Length) + return; + + int mana = m_Spell.ScaleMana(m_Spell.RequiredMana); + AnimalFormEntry entry = AnimalForm.Entries[entryID]; + + if (mana > m_Caster.Mana) + { + m_Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + } + else if (m_Caster is PlayerMobile && (m_Caster as PlayerMobile).MountBlockReason != BlockMountType.None) + { + m_Caster.SendLocalizedMessage(1063108); // You cannot use this ability right now. + } + else if (BaseFormTalisman.EntryEnabled(sender.Mobile, entry.Type)) + { + #region Dueling + + if ((m_Caster as PlayerMobile)?.DuelContext != null && + !((PlayerMobile)m_Caster).DuelContext.AllowSpellCast(m_Caster, m_Spell)) + { + } + + #endregion + + else if (Morph(m_Caster, entryID) == MorphResult.Fail) + { + m_Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 502632); // The spell fizzles. + m_Caster.FixedParticles(0x3735, 1, 30, 9503, EffectLayer.Waist); + m_Caster.PlaySound(0x5C); + } + else + { + m_Caster.FixedParticles(0x3728, 10, 13, 2023, EffectLayer.Waist); + m_Caster.Mana -= mana; + } + } + } + } + } + + public class AnimalFormContext + { + public AnimalFormContext(Timer timer, SkillMod mod, bool speedBoost, Type type, SkillMod stealingMod) + { + Timer = timer; + Mod = mod; + SpeedBoost = speedBoost; + Type = type; + StealingMod = stealingMod; + } + + public Timer Timer{ get; } + + public SkillMod Mod{ get; } + + public bool SpeedBoost{ get; } + + public Type Type{ get; } + + public SkillMod StealingMod{ get; } + } + + public class AnimalFormTimer : Timer + { + private int m_Body; + private int m_Counter; + private int m_Hue; + private Mobile m_LastTarget; + private Mobile m_Mobile; + + public AnimalFormTimer(Mobile from, int body, int hue) + : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_Mobile = from; + m_Body = body; + m_Hue = hue; + m_Counter = 0; + + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + if (m_Mobile.Deleted || !m_Mobile.Alive || m_Mobile.Body != m_Body || m_Mobile.Hue != m_Hue) + { + AnimalForm.RemoveContext(m_Mobile, true); + Stop(); + } + else + { + if (m_Body == 0x115) // Cu Sidhe + { + if (m_Counter++ >= 8) + { + if (m_Mobile.Hits < m_Mobile.HitsMax && m_Mobile.Backpack != null) + { + Bandage b = m_Mobile.Backpack.FindItemByType(typeof(Bandage)) as Bandage; + + if (b != null) + { + m_Mobile.Hits += Utility.RandomMinMax(20, 50); + b.Consume(); + } + } + + m_Counter = 0; + } + } + else if (m_Body == 0x114) // Reptalon + { + if (m_Mobile.Combatant != null && m_Mobile.Combatant != m_LastTarget) + { + m_Counter = 1; + m_LastTarget = m_Mobile.Combatant; + } + + if (m_Mobile.Warmode && m_LastTarget != null && m_LastTarget.Alive && !m_LastTarget.Deleted && + m_Counter-- <= 0) + { + if (m_Mobile.CanBeHarmful(m_LastTarget) && m_LastTarget.Map == m_Mobile.Map && + m_LastTarget.InRange(m_Mobile.Location, BaseCreature.DefaultRangePerception) && + m_Mobile.InLOS(m_LastTarget)) + { + m_Mobile.Direction = m_Mobile.GetDirectionTo(m_LastTarget); + m_Mobile.Freeze(TimeSpan.FromSeconds(1)); + m_Mobile.PlaySound(0x16A); + + DelayCall(TimeSpan.FromSeconds(1.3), BreathEffect_Callback, m_LastTarget); + } + + m_Counter = Math.Min((int)m_Mobile.GetDistanceToSqrt(m_LastTarget), 10); + } + } + } + } + + public void BreathEffect_Callback(Mobile target) + { + if (m_Mobile.CanBeHarmful(target)) + { + m_Mobile.RevealingAction(); + m_Mobile.PlaySound(0x227); + Effects.SendMovingEffect(m_Mobile, target, 0x36D4, 5, 0, false, false, 0, 0); + + DelayCall(TimeSpan.FromSeconds(1), BreathDamage_Callback, target); + } + } + + public void BreathDamage_Callback(Mobile target) + { + if (m_Mobile.CanBeHarmful(target)) + { + m_Mobile.RevealingAction(); + m_Mobile.DoHarmful(target); + AOS.Damage(target, m_Mobile, 20, !target.Player, 0, 100, 0, 0, 0); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/Backstab.cs b/Scripts/Spells/Ninjitsu/Backstab.cs index 5dc2258e1..8071f2b5b 100644 --- a/Scripts/Spells/Ninjitsu/Backstab.cs +++ b/Scripts/Spells/Ninjitsu/Backstab.cs @@ -3,73 +3,69 @@ using Server.SkillHandlers; namespace Server.Spells.Ninjitsu { - public class Backstab : NinjaMove - { - public Backstab() - { - } + public class Backstab : NinjaMove + { + public override int BaseMana => 30; + public override double RequiredSkill => Core.ML ? 40.0 : 20.0; - public override int BaseMana => 30; - public override double RequiredSkill => Core.ML ? 40.0 : 20.0; + public override TextDefinition AbilityMessage => + new TextDefinition(1063089); // You prepare to Backstab your opponent. - public override TextDefinition AbilityMessage => new TextDefinition( 1063089 ); // You prepare to Backstab your opponent. + public override bool ValidatesDuringHit => false; - public override double GetDamageScalar( Mobile attacker, Mobile defender ) - { - double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; + public override double GetDamageScalar(Mobile attacker, Mobile defender) + { + double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; - return 1.0 + (ninjitsu / 360) + Tracking.GetStalkingBonus( attacker, defender ) / 100; - } + return 1.0 + ninjitsu / 360 + Tracking.GetStalkingBonus(attacker, defender) / 100; + } - public override bool Validate( Mobile from ) - { - if ( !from.Hidden || from.AllowedStealthSteps <= 0 ) - { - from.SendLocalizedMessage( 1063087 ); // You must be in stealth mode to use this ability. - return false; - } + public override bool Validate(Mobile from) + { + if (!from.Hidden || from.AllowedStealthSteps <= 0) + { + from.SendLocalizedMessage(1063087); // You must be in stealth mode to use this ability. + return false; + } - return base.Validate( from ); - } + return base.Validate(from); + } - public override bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - bool valid = Validate( attacker ) && CheckMana( attacker, true ); + public override bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + bool valid = Validate(attacker) && CheckMana(attacker, true); - if ( valid ) - { - attacker.BeginAction( typeof( Stealth ) ); - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), delegate { attacker.EndAction( typeof( Stealth ) ); } ); - } + if (valid) + { + attacker.BeginAction(typeof(Stealth)); + Timer.DelayCall(TimeSpan.FromSeconds(5.0), delegate { attacker.EndAction(typeof(Stealth)); }); + } - return valid; + return valid; + } - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + //Validates before swing - public override bool ValidatesDuringHit => false; + ClearCurrentMove(attacker); - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - //Validates before swing + attacker.SendLocalizedMessage(1063090); // You quickly stab your opponent as you come out of hiding! - ClearCurrentMove( attacker ); + defender.FixedParticles(0x37B9, 1, 5, 0x251D, 0x651, 0, EffectLayer.Waist); - attacker.SendLocalizedMessage( 1063090 ); // You quickly stab your opponent as you come out of hiding! + attacker.RevealingAction(); - defender.FixedParticles( 0x37B9, 1, 5, 0x251D, 0x651, 0, EffectLayer.Waist ); + CheckGain(attacker); + } - attacker.RevealingAction(); + public override void OnMiss(Mobile attacker, Mobile defender) + { + ClearCurrentMove(attacker); - CheckGain( attacker ); - } + attacker.SendLocalizedMessage(1063161); // You failed to properly use the element of surprise. - public override void OnMiss( Mobile attacker, Mobile defender ) - { - ClearCurrentMove( attacker ); - - attacker.SendLocalizedMessage( 1063161 ); // You failed to properly use the element of surprise. - - attacker.RevealingAction(); - } - } -} + attacker.RevealingAction(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/DeathStrike.cs b/Scripts/Spells/Ninjitsu/DeathStrike.cs index 36451cd6c..02b86819d 100644 --- a/Scripts/Spells/Ninjitsu/DeathStrike.cs +++ b/Scripts/Spells/Ninjitsu/DeathStrike.cs @@ -5,163 +5,162 @@ using Server.SkillHandlers; namespace Server.Spells.Ninjitsu { - public class DeathStrike : NinjaMove - { - public DeathStrike() - { - } + public class DeathStrike : NinjaMove + { + private static Hashtable m_Table = new Hashtable(); - public override int BaseMana => 30; - public override double RequiredSkill => 85.0; + public override int BaseMana => 30; + public override double RequiredSkill => 85.0; - public override TextDefinition AbilityMessage => new TextDefinition( 1063091 ); // You prepare to hit your opponent with a Death Strike. + public override TextDefinition AbilityMessage => + new TextDefinition(1063091); // You prepare to hit your opponent with a Death Strike. - public override double GetDamageScalar( Mobile attacker, Mobile defender ) - { - return 0.5; - } + public override double GetDamageScalar(Mobile attacker, Mobile defender) + { + return 0.5; + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - ClearCurrentMove( attacker ); + ClearCurrentMove(attacker); - double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; + double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; - double chance; - bool isRanged = false; // should be defined onHit method, what if the player hit and remove the weapon before process? ;) + double chance; + bool + isRanged = false; // should be defined onHit method, what if the player hit and remove the weapon before process? ;) - if ( attacker.Weapon is BaseRanged ) - isRanged = true; + if (attacker.Weapon is BaseRanged) + isRanged = true; - if ( ninjitsu < 100 ) //This formula is an approximation from OSI data. TODO: find correct formula - chance = 30 + (ninjitsu - 85) * 2.2; - else - chance = 63 + (ninjitsu - 100) * 1.1; + if (ninjitsu < 100) //This formula is an approximation from OSI data. TODO: find correct formula + chance = 30 + (ninjitsu - 85) * 2.2; + else + chance = 63 + (ninjitsu - 100) * 1.1; - if ( (chance / 100) < Utility.RandomDouble() ) - { - attacker.SendLocalizedMessage( 1070779 ); // You missed your opponent with a Death Strike. - return; - } + if (chance / 100 < Utility.RandomDouble()) + { + attacker.SendLocalizedMessage(1070779); // You missed your opponent with a Death Strike. + return; + } - DeathStrikeInfo info; + DeathStrikeInfo info; - int damageBonus = 0; + int damageBonus = 0; - if ( m_Table.Contains( defender ) ) - { - defender.SendLocalizedMessage( 1063092 ); // Your opponent lands another Death Strike! + if (m_Table.Contains(defender)) + { + defender.SendLocalizedMessage(1063092); // Your opponent lands another Death Strike! - info = (DeathStrikeInfo)m_Table[defender]; + info = (DeathStrikeInfo)m_Table[defender]; - if ( info.m_Steps > 0 ) - damageBonus = attacker.Skills[SkillName.Ninjitsu].Fixed / 150; + if (info.m_Steps > 0) + damageBonus = attacker.Skills[SkillName.Ninjitsu].Fixed / 150; - info.m_Timer?.Stop(); + info.m_Timer?.Stop(); - m_Table.Remove( defender ); - } - else - { - defender.SendLocalizedMessage( 1063093 ); // You have been hit by a Death Strike! Move with caution! - } + m_Table.Remove(defender); + } + else + { + defender.SendLocalizedMessage(1063093); // You have been hit by a Death Strike! Move with caution! + } - attacker.SendLocalizedMessage( 1063094 ); // You inflict a Death Strike upon your opponent! + attacker.SendLocalizedMessage(1063094); // You inflict a Death Strike upon your opponent! - defender.FixedParticles( 0x374A, 1, 17, 0x26BC, EffectLayer.Waist ); - attacker.PlaySound( attacker.Female ? 0x50D : 0x50E ); + defender.FixedParticles(0x374A, 1, 17, 0x26BC, EffectLayer.Waist); + attacker.PlaySound(attacker.Female ? 0x50D : 0x50E); - info = new DeathStrikeInfo( defender, attacker, damageBonus, isRanged ); - info.m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), new TimerStateCallback( ProcessDeathStrike ), defender ); + info = new DeathStrikeInfo(defender, attacker, damageBonus, isRanged); + info.m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5.0), new TimerStateCallback(ProcessDeathStrike), defender); - m_Table[defender] = info; + m_Table[defender] = info; - CheckGain( attacker ); - } + CheckGain(attacker); + } + public static void AddStep(Mobile m) + { + DeathStrikeInfo info = m_Table[m] as DeathStrikeInfo; - private static Hashtable m_Table = new Hashtable(); + if (info == null) + return; - private class DeathStrikeInfo - { - public Mobile m_Target; - public Mobile m_Attacker; - public int m_Steps; - public int m_DamageBonus; - public Timer m_Timer; - public bool m_isRanged; + if (++info.m_Steps >= 5) + ProcessDeathStrike(m); + } - public DeathStrikeInfo( Mobile target, Mobile attacker, int damageBonus, bool isRanged ) - { - m_Target = target; - m_Attacker = attacker; - m_DamageBonus = damageBonus; - m_isRanged = isRanged; - } - } + private static void ProcessDeathStrike(object state) + { + Mobile defender = (Mobile)state; - public static void AddStep( Mobile m ) - { - DeathStrikeInfo info = m_Table[m] as DeathStrikeInfo; + DeathStrikeInfo info = m_Table[defender] as DeathStrikeInfo; - if ( info == null ) - return; + if (info == null) //sanity + return; - if ( ++info.m_Steps >= 5 ) - ProcessDeathStrike( m ); - } + int maxDamage, damage = 0; - private static void ProcessDeathStrike( object state ) - { - Mobile defender = (Mobile)state; + double ninjitsu = info.m_Attacker.Skills[SkillName.Ninjitsu].Value; + double stalkingBonus = Tracking.GetStalkingBonus(info.m_Attacker, info.m_Target); - DeathStrikeInfo info = m_Table[defender] as DeathStrikeInfo; + if (Core.ML) + { + double scalar = (info.m_Attacker.Skills[SkillName.Hiding].Value + + info.m_Attacker.Skills[SkillName.Stealth].Value) / 220; - if ( info == null ) //sanity - return; + if (scalar > 1) + scalar = 1; - int maxDamage, damage = 0; + // New formula doesn't apply DamageBonus anymore, caps must be, directly, 60/30. + if (info.m_Steps >= 5) + damage = (int)Math.Floor(Math.Min(60, ninjitsu / 3 * (0.3 + 0.7 * scalar) + stalkingBonus)); + else + damage = (int)Math.Floor(Math.Min(30, ninjitsu / 9 * (0.3 + 0.7 * scalar) + stalkingBonus)); - double ninjitsu = info.m_Attacker.Skills[SkillName.Ninjitsu].Value; - double stalkingBonus = Tracking.GetStalkingBonus( info.m_Attacker, info.m_Target ); + if (info.m_isRanged) + damage /= 2; + } + else + { + int divisor = info.m_Steps >= 5 ? 30 : 80; + double baseDamage = ninjitsu / divisor * 10; - if ( Core.ML ) - { - double scalar = ( info.m_Attacker.Skills[SkillName.Hiding].Value + info.m_Attacker.Skills[SkillName.Stealth].Value ) / 220; + maxDamage = info.m_Steps >= 5 ? 62 : 22; // DamageBonus is 8 at most. That brings the cap up to 70/30. + damage = Math.Max(0, Math.Min(maxDamage, (int)(baseDamage + stalkingBonus))) + info.m_DamageBonus; + } - if ( scalar > 1 ) - scalar = 1; + if (Core.ML) + info.m_Target.Damage(damage, info.m_Attacker); // Damage is direct. + else + AOS.Damage(info.m_Target, info.m_Attacker, damage, true, 100, 0, 0, 0, 0, 0, 0, false, false, + true); // Damage is physical. - // New formula doesn't apply DamageBonus anymore, caps must be, directly, 60/30. - if ( info.m_Steps >= 5 ) - damage = (int)Math.Floor( Math.Min( 60, ( ninjitsu / 3 ) * ( 0.3 + 0.7 * scalar ) + stalkingBonus ) ); - else - damage = (int)Math.Floor( Math.Min( 30, ( ninjitsu / 9 ) * ( 0.3 + 0.7 * scalar ) + stalkingBonus ) ); + info.m_Timer?.Stop(); - if ( info.m_isRanged ) - damage /= 2; - } - else - { - int divisor = (info.m_Steps >= 5) ? 30 : 80; - double baseDamage = ninjitsu / divisor * 10; + m_Table.Remove(info.m_Target); + } - maxDamage = (info.m_Steps >= 5) ? 62 : 22; // DamageBonus is 8 at most. That brings the cap up to 70/30. - damage = Math.Max( 0, Math.Min( maxDamage, (int)( baseDamage + stalkingBonus ) ) ) + info.m_DamageBonus; - } + private class DeathStrikeInfo + { + public Mobile m_Attacker; + public int m_DamageBonus; + public bool m_isRanged; + public int m_Steps; + public Mobile m_Target; + public Timer m_Timer; - if ( Core.ML ) - info.m_Target.Damage( damage, info.m_Attacker ); // Damage is direct. - else - AOS.Damage( info.m_Target, info.m_Attacker, damage, true, 100, 0, 0, 0, 0, 0, 0, false, false, true ); // Damage is physical. - - info.m_Timer?.Stop(); - - m_Table.Remove( info.m_Target ); - } - } -} + public DeathStrikeInfo(Mobile target, Mobile attacker, int damageBonus, bool isRanged) + { + m_Target = target; + m_Attacker = attacker; + m_DamageBonus = damageBonus; + m_isRanged = isRanged; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/FocusAttack.cs b/Scripts/Spells/Ninjitsu/FocusAttack.cs index 0853237da..edf17468c 100644 --- a/Scripts/Spells/Ninjitsu/FocusAttack.cs +++ b/Scripts/Spells/Ninjitsu/FocusAttack.cs @@ -2,68 +2,65 @@ using Server.Items; namespace Server.Spells.Ninjitsu { - public class FocusAttack : NinjaMove - { - public FocusAttack() - { - } + public class FocusAttack : NinjaMove + { + public override int BaseMana => Core.ML ? 10 : 20; + public override double RequiredSkill => Core.ML ? 30.0 : 60; - public override int BaseMana => Core.ML ? 10 : 20; - public override double RequiredSkill => Core.ML? 30.0 : 60 ; + public override TextDefinition AbilityMessage => + new TextDefinition(1063095); // You prepare to focus all of your abilities into your next strike. - public override TextDefinition AbilityMessage => new TextDefinition( 1063095 ); // You prepare to focus all of your abilities into your next strike. + public override bool Validate(Mobile from) + { + if (from.FindItemOnLayer(Layer.TwoHanded) as BaseShield != null) + { + from.SendLocalizedMessage(1063096); // You cannot use this ability while holding a shield. + return false; + } - public override bool Validate( Mobile from ) - { - if ( from.FindItemOnLayer( Layer.TwoHanded ) as BaseShield != null ) - { - from.SendLocalizedMessage( 1063096 ); // You cannot use this ability while holding a shield. - return false; - } + Item handOne = from.FindItemOnLayer(Layer.OneHanded) as BaseWeapon; - Item handOne = from.FindItemOnLayer( Layer.OneHanded ) as BaseWeapon; + if (handOne != null && !(handOne is BaseRanged)) + return base.Validate(from); - if ( handOne != null && !(handOne is BaseRanged) ) - return base.Validate( from ); + Item handTwo = from.FindItemOnLayer(Layer.TwoHanded) as BaseWeapon; - Item handTwo = from.FindItemOnLayer( Layer.TwoHanded ) as BaseWeapon; + if (handTwo != null && !(handTwo is BaseRanged)) + return base.Validate(from); - if ( handTwo != null && !(handTwo is BaseRanged) ) - return base.Validate( from ); + from.SendLocalizedMessage(1063097); // You must be wielding a melee weapon without a shield to use this ability. + return false; + } - from.SendLocalizedMessage( 1063097 ); // You must be wielding a melee weapon without a shield to use this ability. - return false; - } + public override double GetDamageScalar(Mobile attacker, Mobile defender) + { + double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; - public override double GetDamageScalar( Mobile attacker, Mobile defender ) - { - double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; + return 1.0 + ninjitsu * ninjitsu / 43636; + } - return 1.0 + (ninjitsu * ninjitsu) / 43636; - } + public override double GetPropertyBonus(Mobile attacker) + { + double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; - public override double GetPropertyBonus( Mobile attacker ) - { - double ninjitsu = attacker.Skills[SkillName.Ninjitsu].Value; + double bonus = ninjitsu * ninjitsu / 43636; - double bonus = (ninjitsu * ninjitsu) / 43636; + return 1.0 + (bonus * 3 + 0.01); + } - return 1.0 + (bonus * 3 + 0.01); - } + public override bool OnBeforeDamage(Mobile attacker, Mobile defender) + { + return Validate(attacker) && CheckMana(attacker, true); + } - public override bool OnBeforeDamage( Mobile attacker, Mobile defender ) - { - return Validate( attacker ) && CheckMana( attacker, true ); - } + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + ClearCurrentMove(attacker); - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - ClearCurrentMove( attacker ); + attacker.SendLocalizedMessage(1063098); // You focus all of your abilities and strike with deadly force! + attacker.PlaySound(0x510); - attacker.SendLocalizedMessage( 1063098 ); // You focus all of your abilities and strike with deadly force! - attacker.PlaySound( 0x510 ); - - CheckGain( attacker ); - } - } -} + CheckGain(attacker); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/KiAttack.cs b/Scripts/Spells/Ninjitsu/KiAttack.cs index fe7fbb2e5..598ff3035 100644 --- a/Scripts/Spells/Ninjitsu/KiAttack.cs +++ b/Scripts/Spells/Ninjitsu/KiAttack.cs @@ -4,141 +4,139 @@ using Server.Items; namespace Server.Spells.Ninjitsu { - public class KiAttack : NinjaMove - { - public KiAttack() - { - } + public class KiAttack : NinjaMove + { + private static Hashtable m_Table = new Hashtable(); - public override int BaseMana => 25; - public override double RequiredSkill => 80.0; + public override int BaseMana => 25; + public override double RequiredSkill => 80.0; - public override TextDefinition AbilityMessage => new TextDefinition( 1063099 ); // Your Ki Attack must be complete within 2 seconds for the damage bonus! + public override TextDefinition AbilityMessage => + new TextDefinition(1063099); // Your Ki Attack must be complete within 2 seconds for the damage bonus! - public override void OnUse( Mobile from ) - { - if ( !Validate( from ) ) - return; + public override void OnUse(Mobile from) + { + if (!Validate(from)) + return; - KiAttackInfo info = new KiAttackInfo( from ); - info.m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 2.0 ), new TimerStateCallback( EndKiAttack ), info ); + KiAttackInfo info = new KiAttackInfo(from); + info.m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(2.0), new TimerStateCallback(EndKiAttack), info); - m_Table[from] = info; - } + m_Table[from] = info; + } - public override bool Validate( Mobile from ) - { - if ( from.Hidden && from.AllowedStealthSteps > 0 ) - { - from.SendLocalizedMessage( 1063127 ); // You cannot use this ability while in stealth mode. - return false; - } + public override bool Validate(Mobile from) + { + if (from.Hidden && from.AllowedStealthSteps > 0) + { + from.SendLocalizedMessage(1063127); // You cannot use this ability while in stealth mode. + return false; + } - if ( Core.ML ) - { - BaseRanged ranged = from.Weapon as BaseRanged; + if (Core.ML) + { + BaseRanged ranged = from.Weapon as BaseRanged; - if ( ranged != null ) - { - from.SendLocalizedMessage( 1075858 ); // You can only use this with melee attacks. - return false; - } - } + if (ranged != null) + { + from.SendLocalizedMessage(1075858); // You can only use this with melee attacks. + return false; + } + } - return base.Validate( from ); - } + return base.Validate(from); + } - public override double GetDamageScalar( Mobile attacker, Mobile defender ) - { - if ( attacker.Hidden ) - return 1.0; + public override double GetDamageScalar(Mobile attacker, Mobile defender) + { + if (attacker.Hidden) + return 1.0; - /* - * Pub40 changed pvp damage max to 55% - */ + /* + * Pub40 changed pvp damage max to 55% + */ - return 1.0 + GetBonus(attacker) / ( (Core.ML && attacker.Player && defender.Player) ? 40 : 10 ); - } + return 1.0 + GetBonus(attacker) / (Core.ML && attacker.Player && defender.Player ? 40 : 10); + } - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - if ( !Validate( attacker ) || !CheckMana( attacker, true ) ) - return; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + if (!Validate(attacker) || !CheckMana(attacker, true)) + return; - if ( GetBonus( attacker ) == 0.0 ) - { - attacker.SendLocalizedMessage( 1063101 ); // You were too close to your target to cause any additional damage. - } - else - { - attacker.FixedParticles( 0x37BE, 1, 5, 0x26BD, 0x0, 0x1, EffectLayer.Waist ); - attacker.PlaySound( 0x510 ); + if (GetBonus(attacker) == 0.0) + { + attacker.SendLocalizedMessage(1063101); // You were too close to your target to cause any additional damage. + } + else + { + attacker.FixedParticles(0x37BE, 1, 5, 0x26BD, 0x0, 0x1, EffectLayer.Waist); + attacker.PlaySound(0x510); - attacker.SendLocalizedMessage( 1063100 ); // Your quick flight to your target causes extra damage as you strike! - defender.FixedParticles( 0x37BE, 1, 5, 0x26BD, 0, 0x1, EffectLayer.Waist ); + attacker.SendLocalizedMessage( + 1063100); // Your quick flight to your target causes extra damage as you strike! + defender.FixedParticles(0x37BE, 1, 5, 0x26BD, 0, 0x1, EffectLayer.Waist); - CheckGain( attacker ); - } + CheckGain(attacker); + } - ClearCurrentMove( attacker ); - } + ClearCurrentMove(attacker); + } - public override void OnClearMove( Mobile from ) - { - KiAttackInfo info = m_Table[from] as KiAttackInfo; + public override void OnClearMove(Mobile from) + { + KiAttackInfo info = m_Table[from] as KiAttackInfo; - if ( info != null ) - { - info.m_Timer?.Stop(); + if (info != null) + { + info.m_Timer?.Stop(); - m_Table.Remove( info.m_Mobile ); - } - } + m_Table.Remove(info.m_Mobile); + } + } - private static Hashtable m_Table = new Hashtable(); + public static double GetBonus(Mobile from) + { + KiAttackInfo info = m_Table[from] as KiAttackInfo; - public static double GetBonus( Mobile from ) - { - KiAttackInfo info = m_Table[from] as KiAttackInfo; + if (info == null) + return 0.0; - if ( info == null ) - return 0.0; + int xDelta = info.m_Location.X - from.X; + int yDelta = info.m_Location.Y - from.Y; - int xDelta = info.m_Location.X - from.X; - int yDelta = info.m_Location.Y - from.Y; + double bonus = Math.Sqrt(xDelta * xDelta + yDelta * yDelta); - double bonus = Math.Sqrt( (xDelta * xDelta) + (yDelta * yDelta) ); + if (bonus > 20.0) + bonus = 20.0; - if ( bonus > 20.0 ) - bonus = 20.0; + return bonus; + } - return bonus; - } + private static void EndKiAttack(object state) + { + KiAttackInfo info = (KiAttackInfo)state; - private class KiAttackInfo - { - public Mobile m_Mobile; - public Point3D m_Location; - public Timer m_Timer; + info.m_Timer?.Stop(); - public KiAttackInfo( Mobile m ) - { - m_Mobile = m; - m_Location = m.Location; - } - } + ClearCurrentMove(info.m_Mobile); + info.m_Mobile.SendLocalizedMessage(1063102); // You failed to complete your Ki Attack in time. - private static void EndKiAttack( object state ) - { - KiAttackInfo info = (KiAttackInfo)state; + m_Table.Remove(info.m_Mobile); + } - info.m_Timer?.Stop(); + private class KiAttackInfo + { + public Point3D m_Location; + public Mobile m_Mobile; + public Timer m_Timer; - ClearCurrentMove( info.m_Mobile ); - info.m_Mobile.SendLocalizedMessage( 1063102 ); // You failed to complete your Ki Attack in time. - - m_Table.Remove( info.m_Mobile ); - } - } -} + public KiAttackInfo(Mobile m) + { + m_Mobile = m; + m_Location = m.Location; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/MirrorImage.cs b/Scripts/Spells/Ninjitsu/MirrorImage.cs index de456c2f4..f78043a76 100644 --- a/Scripts/Spells/Ninjitsu/MirrorImage.cs +++ b/Scripts/Spells/Ninjitsu/MirrorImage.cs @@ -8,262 +8,268 @@ using Server.Spells.Ninjitsu; namespace Server.Spells.Ninjitsu { - public class MirrorImage : NinjaSpell - { - private static Dictionary m_CloneCount = new Dictionary(); + public class MirrorImage : NinjaSpell + { + private static Dictionary m_CloneCount = new Dictionary(); - public static bool HasClone( Mobile m ) - { - return m_CloneCount.ContainsKey( m ); - } + private static SpellInfo m_Info = new SpellInfo( + "Mirror Image", null, + -1, + 9002 + ); - public static void AddClone( Mobile m ) - { - if ( m == null ) - return; + public MirrorImage(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - if ( m_CloneCount.ContainsKey( m ) ) - m_CloneCount[m]++; - else - m_CloneCount[m] = 1; - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public static void RemoveClone( Mobile m ) - { - if ( m == null ) - return; + public override double RequiredSkill => Core.ML ? 20.0 : 40.0; + public override int RequiredMana => 10; - if ( m_CloneCount.ContainsKey( m ) ) - { - m_CloneCount[m]--; + public override bool BlockedByAnimalForm => false; - if ( m_CloneCount[m] == 0 ) - m_CloneCount.Remove( m ); - } - } + public static bool HasClone(Mobile m) + { + return m_CloneCount.ContainsKey(m); + } - private static SpellInfo m_Info = new SpellInfo( - "Mirror Image", null, - -1, - 9002 - ); + public static void AddClone(Mobile m) + { + if (m == null) + return; - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + if (m_CloneCount.ContainsKey(m)) + m_CloneCount[m]++; + else + m_CloneCount[m] = 1; + } - public override double RequiredSkill => Core.ML ? 20.0 : 40.0; - public override int RequiredMana => 10; + public static void RemoveClone(Mobile m) + { + if (m == null) + return; - public override bool BlockedByAnimalForm => false; + if (m_CloneCount.ContainsKey(m)) + { + m_CloneCount[m]--; - public MirrorImage( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + if (m_CloneCount[m] == 0) + m_CloneCount.Remove(m); + } + } - public override bool CheckCast() - { - if ( Caster.Mounted ) - { - Caster.SendLocalizedMessage( 1063132 ); // You cannot use this ability while mounted. - return false; - } + public override bool CheckCast() + { + if (Caster.Mounted) + { + Caster.SendLocalizedMessage(1063132); // You cannot use this ability while mounted. + return false; + } - if ( (Caster.Followers + 1) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1063133 ); // You cannot summon a mirror image because you have too many followers. - return false; - } - if ( TransformationSpellHelper.UnderTransformation( Caster, typeof( HorrificBeastSpell ) ) ) - { - Caster.SendLocalizedMessage( 1061091 ); // You cannot cast that spell in this form. - return false; - } + if (Caster.Followers + 1 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage( + 1063133); // You cannot summon a mirror image because you have too many followers. + return false; + } - return base.CheckCast(); - } + if (TransformationSpellHelper.UnderTransformation(Caster, typeof(HorrificBeastSpell))) + { + Caster.SendLocalizedMessage(1061091); // You cannot cast that spell in this form. + return false; + } - public override bool CheckDisturb( DisturbType type, bool firstCircle, bool resistable ) - { - return false; - } + return base.CheckCast(); + } - public override void OnBeginCast() - { - base.OnBeginCast(); + public override bool CheckDisturb(DisturbType type, bool firstCircle, bool resistable) + { + return false; + } - Caster.SendLocalizedMessage( 1063134 ); // You begin to summon a mirror image of yourself. - } + public override void OnBeginCast() + { + base.OnBeginCast(); - public override void OnCast() - { - if ( Caster.Mounted ) - { - Caster.SendLocalizedMessage( 1063132 ); // You cannot use this ability while mounted. - } - else if ( (Caster.Followers + 1) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1063133 ); // You cannot summon a mirror image because you have too many followers. - } - else if ( TransformationSpellHelper.UnderTransformation( Caster, typeof( HorrificBeastSpell ) ) ) - { - Caster.SendLocalizedMessage( 1061091 ); // You cannot cast that spell in this form. - } - else if ( CheckSequence() ) - { - Caster.FixedParticles( 0x376A, 1, 14, 0x13B5, EffectLayer.Waist ); - Caster.PlaySound( 0x511 ); + Caster.SendLocalizedMessage(1063134); // You begin to summon a mirror image of yourself. + } - new Clone( Caster ).MoveToWorld( Caster.Location, Caster.Map ); - } + public override void OnCast() + { + if (Caster.Mounted) + { + Caster.SendLocalizedMessage(1063132); // You cannot use this ability while mounted. + } + else if (Caster.Followers + 1 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage( + 1063133); // You cannot summon a mirror image because you have too many followers. + } + else if (TransformationSpellHelper.UnderTransformation(Caster, typeof(HorrificBeastSpell))) + { + Caster.SendLocalizedMessage(1061091); // You cannot cast that spell in this form. + } + else if (CheckSequence()) + { + Caster.FixedParticles(0x376A, 1, 14, 0x13B5, EffectLayer.Waist); + Caster.PlaySound(0x511); - FinishSequence(); - } - } + new Clone(Caster).MoveToWorld(Caster.Location, Caster.Map); + } + + FinishSequence(); + } + } } namespace Server.Mobiles { - public class Clone : BaseCreature - { - private Mobile m_Caster; + public class Clone : BaseCreature + { + private Mobile m_Caster; - public Clone( Mobile caster ) : base( AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4 ) - { - m_Caster = caster; + public Clone(Mobile caster) : base(AIType.AI_Melee, FightMode.None, 10, 1, 0.2, 0.4) + { + m_Caster = caster; - Body = caster.Body; + Body = caster.Body; - Hue = caster.Hue; - Female = caster.Female; + Hue = caster.Hue; + Female = caster.Female; - Name = caster.Name; - NameHue = caster.NameHue; + Name = caster.Name; + NameHue = caster.NameHue; - Title = caster.Title; - Kills = caster.Kills; + Title = caster.Title; + Kills = caster.Kills; - HairItemID = caster.HairItemID; - HairHue = caster.HairHue; + HairItemID = caster.HairItemID; + HairHue = caster.HairHue; - FacialHairItemID = caster.FacialHairItemID; - FacialHairHue = caster.FacialHairHue; + FacialHairItemID = caster.FacialHairItemID; + FacialHairHue = caster.FacialHairHue; - for ( int i = 0; i < caster.Skills.Length; ++i ) - { - Skills[i].Base = caster.Skills[i].Base; - Skills[i].Cap = caster.Skills[i].Cap; - } + for (int i = 0; i < caster.Skills.Length; ++i) + { + Skills[i].Base = caster.Skills[i].Base; + Skills[i].Cap = caster.Skills[i].Cap; + } - for( int i = 0; i < caster.Items.Count; i++ ) - { - AddItem( CloneItem( caster.Items[i] ) ); - } + for (int i = 0; i < caster.Items.Count; i++) AddItem(CloneItem(caster.Items[i])); - Warmode = true; + Warmode = true; - Summoned = true; - SummonMaster = caster; + Summoned = true; + SummonMaster = caster; - ControlOrder = OrderType.Follow; - ControlTarget = caster; + ControlOrder = OrderType.Follow; + ControlTarget = caster; - TimeSpan duration = TimeSpan.FromSeconds( 30 + caster.Skills.Ninjitsu.Fixed / 40 ); + TimeSpan duration = TimeSpan.FromSeconds(30 + caster.Skills.Ninjitsu.Fixed / 40); - new UnsummonTimer( caster, this, duration ).Start(); - SummonEnd = DateTime.UtcNow + duration; + new UnsummonTimer(caster, this, duration).Start(); + SummonEnd = DateTime.UtcNow + duration; - MirrorImage.AddClone( m_Caster ); - } + MirrorImage.AddClone(m_Caster); + } - protected override BaseAI ForcedAI => new CloneAI( this ); + public Clone(Serial serial) : base(serial) + { + } - public override bool IsHumanInTown() { return false; } + protected override BaseAI ForcedAI => new CloneAI(this); - private Item CloneItem( Item item ) - { - Item newItem = new Item( item.ItemID ); - newItem.Hue = item.Hue; - newItem.Layer = item.Layer; + public override bool DeleteCorpseOnDeath => true; - return newItem; - } + public override bool IsDispellable => false; + public override bool Commandable => false; - public override void OnDamage( int amount, Mobile from, bool willKill ) - { - Delete(); - } + public override bool IsHumanInTown() + { + return false; + } - public override bool DeleteCorpseOnDeath => true; + private Item CloneItem(Item item) + { + Item newItem = new Item(item.ItemID); + newItem.Hue = item.Hue; + newItem.Layer = item.Layer; - public override void OnDelete() - { - Effects.SendLocationParticles( EffectItem.Create( Location, Map, EffectItem.DefaultDuration ), 0x3728, 10, 15, 5042 ); + return newItem; + } - base.OnDelete(); - } + public override void OnDamage(int amount, Mobile from, bool willKill) + { + Delete(); + } - public override void OnAfterDelete() - { - MirrorImage.RemoveClone( m_Caster ); - base.OnAfterDelete(); - } + public override void OnDelete() + { + Effects.SendLocationParticles(EffectItem.Create(Location, Map, EffectItem.DefaultDuration), 0x3728, 10, 15, + 5042); - public override bool IsDispellable => false; - public override bool Commandable => false; + base.OnDelete(); + } - public Clone( Serial serial ) : base( serial ) - { - } + public override void OnAfterDelete() + { + MirrorImage.RemoveClone(m_Caster); + base.OnAfterDelete(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.WriteEncodedInt( 0 ); // version + writer.WriteEncodedInt(0); // version - writer.Write( m_Caster ); - } + writer.Write(m_Caster); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadEncodedInt(); + int version = reader.ReadEncodedInt(); - m_Caster = reader.ReadMobile(); + m_Caster = reader.ReadMobile(); - MirrorImage.AddClone( m_Caster ); - } - } + MirrorImage.AddClone(m_Caster); + } + } } namespace Server.Mobiles { - public class CloneAI : BaseAI - { - public CloneAI( Clone m ) : base ( m ) - { - m.CurrentSpeed = m.ActiveSpeed; - } + public class CloneAI : BaseAI + { + public CloneAI(Clone m) : base(m) + { + m.CurrentSpeed = m.ActiveSpeed; + } - public override bool Think() - { - // Clones only follow their owners - Mobile master = m_Mobile.SummonMaster; + public override bool CanDetectHidden => false; - if ( master != null && master.Map == m_Mobile.Map && master.InRange( m_Mobile, m_Mobile.RangePerception ) ) - { - int iCurrDist = (int)m_Mobile.GetDistanceToSqrt( master ); - bool bRun = (iCurrDist > 5); + public override bool Think() + { + // Clones only follow their owners + Mobile master = m_Mobile.SummonMaster; - WalkMobileRange( master, 2, bRun, 0, 1 ); - } - else - WalkRandom( 2, 2, 1 ); + if (master != null && master.Map == m_Mobile.Map && master.InRange(m_Mobile, m_Mobile.RangePerception)) + { + int iCurrDist = (int)m_Mobile.GetDistanceToSqrt(master); + bool bRun = iCurrDist > 5; - return true; - } + WalkMobileRange(master, 2, bRun, 0, 1); + } + else + { + WalkRandom(2, 2, 1); + } - public override bool CanDetectHidden => false; - } -} + return true; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/NinjaMove.cs b/Scripts/Spells/Ninjitsu/NinjaMove.cs index 4bb6182da..622d6e4e2 100644 --- a/Scripts/Spells/Ninjitsu/NinjaMove.cs +++ b/Scripts/Spells/Ninjitsu/NinjaMove.cs @@ -1,12 +1,12 @@ namespace Server.Spells { - public class NinjaMove : SpecialMove - { - public override SkillName MoveSkill => SkillName.Ninjitsu; + public class NinjaMove : SpecialMove + { + public override SkillName MoveSkill => SkillName.Ninjitsu; - public override void CheckGain( Mobile m ) - { - m.CheckSkill( MoveSkill, RequiredSkill - 12.5, RequiredSkill + 37.5 ); //Per five on friday 02/16/07 - } - } -} + public override void CheckGain(Mobile m) + { + m.CheckSkill(MoveSkill, RequiredSkill - 12.5, RequiredSkill + 37.5); //Per five on friday 02/16/07 + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/NinjaSpell.cs b/Scripts/Spells/Ninjitsu/NinjaSpell.cs index e0b2dff15..63d9627de 100644 --- a/Scripts/Spells/Ninjitsu/NinjaSpell.cs +++ b/Scripts/Spells/Ninjitsu/NinjaSpell.cs @@ -1,103 +1,106 @@ -using System; using Server.Mobiles; namespace Server.Spells.Ninjitsu { - public abstract class NinjaSpell : Spell - { - public abstract double RequiredSkill{ get; } - public abstract int RequiredMana{ get; } + public abstract class NinjaSpell : Spell + { + public NinjaSpell(Mobile caster, Item scroll, SpellInfo info) : base(caster, scroll, info) + { + } - public override SkillName CastSkill => SkillName.Ninjitsu; - public override SkillName DamageSkill => SkillName.Ninjitsu; + public abstract double RequiredSkill{ get; } + public abstract int RequiredMana{ get; } - public override bool RevealOnCast => false; - public override bool ClearHandsOnCast => false; - public override bool ShowHandMovement => false; + public override SkillName CastSkill => SkillName.Ninjitsu; + public override SkillName DamageSkill => SkillName.Ninjitsu; - public override bool BlocksMovement => false; + public override bool RevealOnCast => false; + public override bool ClearHandsOnCast => false; + public override bool ShowHandMovement => false; - //public override int CastDelayBase => 1; + public override bool BlocksMovement => false; - public override int CastRecoveryBase => 7; + //public override int CastDelayBase => 1; - public NinjaSpell( Mobile caster, Item scroll, SpellInfo info ) : base( caster, scroll, info ) - { - } + public override int CastRecoveryBase => 7; - public static bool CheckExpansion( Mobile from ) - { - if ( !( from is PlayerMobile ) ) - return true; + public static bool CheckExpansion(Mobile from) + { + if (!(from is PlayerMobile)) + return true; - if ( from.NetState == null ) - return false; + if (from.NetState == null) + return false; - return from.NetState.SupportsExpansion( Expansion.SE ); - } + return from.NetState.SupportsExpansion(Expansion.SE); + } - public override bool CheckCast() - { - int mana = ScaleMana( RequiredMana ); + public override bool CheckCast() + { + int mana = ScaleMana(RequiredMana); - if ( !base.CheckCast() ) - return false; + if (!base.CheckCast()) + return false; - if ( !CheckExpansion( Caster ) ) - { - Caster.SendLocalizedMessage( 1063456 ); // You must upgrade to Samurai Empire in order to use that ability. - return false; - } + if (!CheckExpansion(Caster)) + { + Caster.SendLocalizedMessage(1063456); // You must upgrade to Samurai Empire in order to use that ability. + return false; + } - if ( Caster.Skills[CastSkill].Value < RequiredSkill ) - { - string args = $"{RequiredSkill.ToString("F1")}\t{CastSkill.ToString()}\t "; - Caster.SendLocalizedMessage( 1063013, args ); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - return false; - } + if (Caster.Skills[CastSkill].Value < RequiredSkill) + { + string args = $"{RequiredSkill.ToString("F1")}\t{CastSkill.ToString()}\t "; + Caster.SendLocalizedMessage(1063013, + args); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + return false; + } - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - return true; - } + return true; + } - public override bool CheckFizzle() - { - int mana = ScaleMana( RequiredMana ); + public override bool CheckFizzle() + { + int mana = ScaleMana(RequiredMana); - if ( Caster.Skills[CastSkill].Value < RequiredSkill ) - { - Caster.SendLocalizedMessage( 1063352, RequiredSkill.ToString( "F1" ) ); // You need ~1_SKILL_REQUIREMENT~ Ninjitsu skill to perform that attack! - return false; - } + if (Caster.Skills[CastSkill].Value < RequiredSkill) + { + Caster.SendLocalizedMessage(1063352, + RequiredSkill.ToString("F1")); // You need ~1_SKILL_REQUIREMENT~ Ninjitsu skill to perform that attack! + return false; + } - if ( Caster.Mana < mana ) - { - Caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (Caster.Mana < mana) + { + Caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - if ( !base.CheckFizzle() ) - return false; + if (!base.CheckFizzle()) + return false; - Caster.Mana -= mana; + Caster.Mana -= mana; - return true; - } + return true; + } - public override void GetCastSkills( out double min, out double max ) - { - min = RequiredSkill - 12.5; //Per 5 on friday 2/16/07 - max = RequiredSkill + 37.5; - } + public override void GetCastSkills(out double min, out double max) + { + min = RequiredSkill - 12.5; //Per 5 on friday 2/16/07 + max = RequiredSkill + 37.5; + } - public override int GetMana() - { - return 0; - } - } -} + public override int GetMana() + { + return 0; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/ShadowJump.cs b/Scripts/Spells/Ninjitsu/ShadowJump.cs index d6432868c..3adf25249 100644 --- a/Scripts/Spells/Ninjitsu/ShadowJump.cs +++ b/Scripts/Spells/Ninjitsu/ShadowJump.cs @@ -1,131 +1,137 @@ using System; +using Server.Factions; using Server.Items; +using Server.Misc; using Server.Mobiles; using Server.Regions; +using Server.SkillHandlers; using Server.Targeting; namespace Server.Spells.Ninjitsu { - public class Shadowjump : NinjaSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Shadowjump", null, - -1, - 9002 - ); + public class Shadowjump : NinjaSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Shadowjump", null, + -1, + 9002 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + public Shadowjump(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 50.0; - public override int RequiredMana => 15; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public override bool BlockedByAnimalForm => false; + public override double RequiredSkill => 50.0; + public override int RequiredMana => 15; - public Shadowjump( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override bool BlockedByAnimalForm => false; - public override bool CheckCast() - { - PlayerMobile pm = Caster as PlayerMobile; // IsStealthing should be moved to Server.Mobiles - if ( !pm.IsStealthing ) - { - Caster.SendLocalizedMessage( 1063087 ); // You must be in stealth mode to use this ability. - return false; - } + public override bool CheckCast() + { + PlayerMobile pm = Caster as PlayerMobile; // IsStealthing should be moved to Server.Mobiles + if (!pm.IsStealthing) + { + Caster.SendLocalizedMessage(1063087); // You must be in stealth mode to use this ability. + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override bool CheckDisturb( DisturbType type, bool firstCircle, bool resistable ) - { - return false; - } + public override bool CheckDisturb(DisturbType type, bool firstCircle, bool resistable) + { + return false; + } - public override void OnCast() - { - Caster.SendLocalizedMessage( 1063088 ); // You prepare to perform a Shadowjump. - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.SendLocalizedMessage(1063088); // You prepare to perform a Shadowjump. + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - IPoint3D orig = p; - Map map = Caster.Map; + public void Target(IPoint3D p) + { + IPoint3D orig = p; + Map map = Caster.Map; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - Point3D from = Caster.Location; - Point3D to = new Point3D( p ); + Point3D from = Caster.Location; + Point3D to = new Point3D(p); - PlayerMobile pm = Caster as PlayerMobile; // IsStealthing should be moved to Server.Mobiles + PlayerMobile pm = Caster as PlayerMobile; // IsStealthing should be moved to Server.Mobiles - if ( !pm.IsStealthing ) - { - Caster.SendLocalizedMessage( 1063087 ); // You must be in stealth mode to use this ability. - } - else if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - } - else if ( !SpellHelper.CheckTravel( Caster, TravelCheckType.TeleportFrom ) || !SpellHelper.CheckTravel( Caster, map, to, TravelCheckType.TeleportTo )) - { - } - else if ( map == null || !map.CanSpawnMobile( p.X, p.Y, p.Z ) ) - { - Caster.SendLocalizedMessage( 502831 ); // Cannot teleport to that spot. - } - else if ( SpellHelper.CheckMulti( to, map, true, 5 ) ) - { - Caster.SendLocalizedMessage( 502831 ); // Cannot teleport to that spot. - } - else if ( Region.Find( to, map ).GetRegion( typeof( HouseRegion ) ) != null ) - { - Caster.SendLocalizedMessage( 502829 ); // Cannot teleport to that spot. - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, orig ); + if (!pm.IsStealthing) + { + Caster.SendLocalizedMessage(1063087); // You must be in stealth mode to use this ability. + } + else if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + } + else if (!SpellHelper.CheckTravel(Caster, TravelCheckType.TeleportFrom) || + !SpellHelper.CheckTravel(Caster, map, to, TravelCheckType.TeleportTo)) + { + } + else if (map == null || !map.CanSpawnMobile(p.X, p.Y, p.Z)) + { + Caster.SendLocalizedMessage(502831); // Cannot teleport to that spot. + } + else if (SpellHelper.CheckMulti(to, map, true, 5)) + { + Caster.SendLocalizedMessage(502831); // Cannot teleport to that spot. + } + else if (Region.Find(to, map).GetRegion(typeof(HouseRegion)) != null) + { + Caster.SendLocalizedMessage(502829); // Cannot teleport to that spot. + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, orig); - Mobile m = Caster; + Mobile m = Caster; - m.Location = to; - m.ProcessDelta(); + m.Location = to; + m.ProcessDelta(); - Effects.SendLocationParticles( EffectItem.Create( from, m.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); + Effects.SendLocationParticles(EffectItem.Create(from, m.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 2023); - m.PlaySound( 0x512 ); + m.PlaySound(0x512); - SkillHandlers.Stealth.OnUse( m ); // stealth check after the a jump - } + Stealth.OnUse(m); // stealth check after the a jump + } - FinishSequence(); - } - public class InternalTarget : Target - { - private Shadowjump m_Owner; + FinishSequence(); + } - public InternalTarget( Shadowjump owner ) : base( 11, true, TargetFlags.None ) - { - m_Owner = owner; - } + public class InternalTarget : Target + { + private Shadowjump m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + public InternalTarget(Shadowjump owner) : base(11, true, TargetFlags.None) + { + m_Owner = owner; + } - if ( p != null ) - m_Owner.Target( p ); - } + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + if (p != null) + m_Owner.Target(p); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Ninjitsu/SurpriseAttack.cs b/Scripts/Spells/Ninjitsu/SurpriseAttack.cs index c551049a5..e7854e830 100644 --- a/Scripts/Spells/Ninjitsu/SurpriseAttack.cs +++ b/Scripts/Spells/Ninjitsu/SurpriseAttack.cs @@ -4,125 +4,119 @@ using Server.SkillHandlers; namespace Server.Spells.Ninjitsu { - public class SurpriseAttack : NinjaMove - { - public SurpriseAttack() - { - } + public class SurpriseAttack : NinjaMove + { + private static Hashtable m_Table = new Hashtable(); - public override int BaseMana => 20; - public override double RequiredSkill => Core.ML ? 60.0 : 30.0; + public override int BaseMana => 20; + public override double RequiredSkill => Core.ML ? 60.0 : 30.0; - public override TextDefinition AbilityMessage => new TextDefinition( 1063128 ); // You prepare to surprise your prey. + public override TextDefinition AbilityMessage => new TextDefinition(1063128); // You prepare to surprise your prey. - public override bool Validate( Mobile from ) - { - if ( !from.Hidden || from.AllowedStealthSteps <= 0 ) - { - from.SendLocalizedMessage( 1063087 ); // You must be in stealth mode to use this ability. - return false; - } + public override bool ValidatesDuringHit => false; - return base.Validate( from ); - } + public override bool Validate(Mobile from) + { + if (!from.Hidden || from.AllowedStealthSteps <= 0) + { + from.SendLocalizedMessage(1063087); // You must be in stealth mode to use this ability. + return false; + } - public override bool OnBeforeSwing( Mobile attacker, Mobile defender ) - { - bool valid = Validate( attacker ) && CheckMana( attacker, true ); + return base.Validate(from); + } - if ( valid ) - { - attacker.BeginAction( typeof( Stealth ) ); - Timer.DelayCall( TimeSpan.FromSeconds( 5.0 ), delegate { attacker.EndAction( typeof( Stealth ) ); } ); - } + public override bool OnBeforeSwing(Mobile attacker, Mobile defender) + { + bool valid = Validate(attacker) && CheckMana(attacker, true); - return valid; + if (valid) + { + attacker.BeginAction(typeof(Stealth)); + Timer.DelayCall(TimeSpan.FromSeconds(5.0), delegate { attacker.EndAction(typeof(Stealth)); }); + } - } + return valid; + } - public override bool ValidatesDuringHit => false; + public override void OnHit(Mobile attacker, Mobile defender, int damage) + { + //Validates before swing - public override void OnHit( Mobile attacker, Mobile defender, int damage ) - { - //Validates before swing + ClearCurrentMove(attacker); - ClearCurrentMove( attacker ); + attacker.SendLocalizedMessage(1063129); // You catch your opponent off guard with your Surprise Attack! + defender.SendLocalizedMessage(1063130); // Your defenses are lowered as your opponent surprises you! - attacker.SendLocalizedMessage( 1063129 ); // You catch your opponent off guard with your Surprise Attack! - defender.SendLocalizedMessage( 1063130 ); // Your defenses are lowered as your opponent surprises you! + defender.FixedParticles(0x37B9, 1, 5, 0x26DA, 0, 3, EffectLayer.Head); - defender.FixedParticles( 0x37B9, 1, 5, 0x26DA, 0, 3, EffectLayer.Head ); + attacker.RevealingAction(); - attacker.RevealingAction(); + SurpriseAttackInfo info; - SurpriseAttackInfo info; + if (m_Table.Contains(defender)) + { + info = (SurpriseAttackInfo)m_Table[defender]; - if ( m_Table.Contains( defender ) ) - { - info = (SurpriseAttackInfo)m_Table[defender]; + info.m_Timer?.Stop(); - info.m_Timer?.Stop(); + m_Table.Remove(defender); + } - m_Table.Remove( defender ); - } + int ninjitsu = attacker.Skills[SkillName.Ninjitsu].Fixed; - int ninjitsu = attacker.Skills[SkillName.Ninjitsu].Fixed; + int malus = ninjitsu / 60 + (int)Tracking.GetStalkingBonus(attacker, defender); - int malus = ninjitsu / 60 + (int)Tracking.GetStalkingBonus( attacker, defender ); + info = new SurpriseAttackInfo(defender, malus); + info.m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(8.0), new TimerStateCallback(EndSurprise), info); - info = new SurpriseAttackInfo( defender, malus ); - info.m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 8.0 ), new TimerStateCallback( EndSurprise ), info ); + m_Table[defender] = info; - m_Table[defender] = info; + CheckGain(attacker); + } - CheckGain( attacker ); - } + public override void OnMiss(Mobile attacker, Mobile defender) + { + ClearCurrentMove(attacker); - public override void OnMiss( Mobile attacker, Mobile defender ) - { - ClearCurrentMove( attacker ); + attacker.SendLocalizedMessage(1063161); // You failed to properly use the element of surprise. - attacker.SendLocalizedMessage( 1063161 ); // You failed to properly use the element of surprise. + attacker.RevealingAction(); + } - attacker.RevealingAction(); - } + public static bool GetMalus(Mobile target, ref int malus) + { + SurpriseAttackInfo info = m_Table[target] as SurpriseAttackInfo; + if (info == null) + return false; - private static Hashtable m_Table = new Hashtable(); + malus = info.m_Malus; + return true; + } - public static bool GetMalus( Mobile target, ref int malus ) - { - SurpriseAttackInfo info = m_Table[target] as SurpriseAttackInfo; + private static void EndSurprise(object state) + { + SurpriseAttackInfo info = (SurpriseAttackInfo)state; - if ( info == null ) - return false; + info.m_Timer?.Stop(); - malus = info.m_Malus; - return true; - } + info.m_Target.SendLocalizedMessage(1063131); // Your defenses have returned to normal. - private class SurpriseAttackInfo - { - public Mobile m_Target; - public int m_Malus; - public Timer m_Timer; + m_Table.Remove(info.m_Target); + } - public SurpriseAttackInfo( Mobile target, int effect ) - { - m_Target = target; - m_Malus = effect; - } - } + private class SurpriseAttackInfo + { + public int m_Malus; + public Mobile m_Target; + public Timer m_Timer; - private static void EndSurprise( object state ) - { - SurpriseAttackInfo info = (SurpriseAttackInfo)state; - - info.m_Timer?.Stop(); - - info.m_Target.SendLocalizedMessage( 1063131 ); // Your defenses have returned to normal. - - m_Table.Remove( info.m_Target ); - } - } -} + public SurpriseAttackInfo(Mobile target, int effect) + { + m_Target = target; + m_Malus = effect; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Reagent.cs b/Scripts/Spells/Reagent.cs index ce3166e8a..8b0a7e0ac 100644 --- a/Scripts/Spells/Reagent.cs +++ b/Scripts/Spells/Reagent.cs @@ -3,130 +3,131 @@ using Server.Items; namespace Server.Spells { - public class Reagent - { - private static Type[] m_Types = { - typeof( BlackPearl ), - typeof( Bloodmoss ), - typeof( Garlic ), - typeof( Ginseng ), - typeof( MandrakeRoot ), - typeof( Nightshade ), - typeof( SulfurousAsh ), - typeof( SpidersSilk ), - typeof( BatWing ), - typeof( GraveDust ), - typeof( DaemonBlood ), - typeof( NoxCrystal ), - typeof( PigIron ), - typeof( Bone ), - typeof( FertileDirt ), - typeof( DragonsBlood ), - typeof( DaemonBone ) - }; + public class Reagent + { + private static Type[] m_Types = + { + typeof(BlackPearl), + typeof(Bloodmoss), + typeof(Garlic), + typeof(Ginseng), + typeof(MandrakeRoot), + typeof(Nightshade), + typeof(SulfurousAsh), + typeof(SpidersSilk), + typeof(BatWing), + typeof(GraveDust), + typeof(DaemonBlood), + typeof(NoxCrystal), + typeof(PigIron), + typeof(Bone), + typeof(FertileDirt), + typeof(DragonsBlood), + typeof(DaemonBone) + }; - public Type[] Types => m_Types; + public Type[] Types => m_Types; - public static Type BlackPearl - { - get => m_Types[0]; - set => m_Types[0] = value; - } + public static Type BlackPearl + { + get => m_Types[0]; + set => m_Types[0] = value; + } - public static Type Bloodmoss - { - get => m_Types[1]; - set => m_Types[1] = value; - } + public static Type Bloodmoss + { + get => m_Types[1]; + set => m_Types[1] = value; + } - public static Type Garlic - { - get => m_Types[2]; - set => m_Types[2] = value; - } + public static Type Garlic + { + get => m_Types[2]; + set => m_Types[2] = value; + } - public static Type Ginseng - { - get => m_Types[3]; - set => m_Types[3] = value; - } + public static Type Ginseng + { + get => m_Types[3]; + set => m_Types[3] = value; + } - public static Type MandrakeRoot - { - get => m_Types[4]; - set => m_Types[4] = value; - } + public static Type MandrakeRoot + { + get => m_Types[4]; + set => m_Types[4] = value; + } - public static Type Nightshade - { - get => m_Types[5]; - set => m_Types[5] = value; - } + public static Type Nightshade + { + get => m_Types[5]; + set => m_Types[5] = value; + } - public static Type SulfurousAsh - { - get => m_Types[6]; - set => m_Types[6] = value; - } + public static Type SulfurousAsh + { + get => m_Types[6]; + set => m_Types[6] = value; + } - public static Type SpidersSilk - { - get => m_Types[7]; - set => m_Types[7] = value; - } + public static Type SpidersSilk + { + get => m_Types[7]; + set => m_Types[7] = value; + } - public static Type BatWing - { - get => m_Types[8]; - set => m_Types[8] = value; - } + public static Type BatWing + { + get => m_Types[8]; + set => m_Types[8] = value; + } - public static Type GraveDust - { - get => m_Types[9]; - set => m_Types[9] = value; - } + public static Type GraveDust + { + get => m_Types[9]; + set => m_Types[9] = value; + } - public static Type DaemonBlood - { - get => m_Types[10]; - set => m_Types[10] = value; - } + public static Type DaemonBlood + { + get => m_Types[10]; + set => m_Types[10] = value; + } - public static Type NoxCrystal - { - get => m_Types[11]; - set => m_Types[11] = value; - } + public static Type NoxCrystal + { + get => m_Types[11]; + set => m_Types[11] = value; + } - public static Type PigIron - { - get => m_Types[12]; - set => m_Types[12] = value; - } + public static Type PigIron + { + get => m_Types[12]; + set => m_Types[12] = value; + } - public static Type Bone - { - get => m_Types[13]; - set => m_Types[13] = value; - } + public static Type Bone + { + get => m_Types[13]; + set => m_Types[13] = value; + } - public static Type FertileDirt - { - get => m_Types[14]; - set => m_Types[14] = value; - } + public static Type FertileDirt + { + get => m_Types[14]; + set => m_Types[14] = value; + } - public static Type DragonsBlood - { - get => m_Types[15]; - set => m_Types[15] = value; - } + public static Type DragonsBlood + { + get => m_Types[15]; + set => m_Types[15] = value; + } - public static Type DaemonBone - { - get => m_Types[16]; - set => m_Types[16] = value; - } - } -} + public static Type DaemonBone + { + get => m_Types[16]; + set => m_Types[16] = value; + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/Agility.cs b/Scripts/Spells/Second/Agility.cs index 270a9e253..4a2941f6c 100644 --- a/Scripts/Spells/Second/Agility.cs +++ b/Scripts/Spells/Second/Agility.cs @@ -1,85 +1,83 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Spells.Second { - public class AgilitySpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Agility", "Ex Uus", - 212, - 9061, - Reagent.Bloodmoss, - Reagent.MandrakeRoot - ); + public class AgilitySpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Agility", "Ex Uus", + 212, + 9061, + Reagent.Bloodmoss, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Second; + public AgilitySpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public AgilitySpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.AddStatBonus( Caster, m, StatType.Dex ); + SpellHelper.AddStatBonus(Caster, m, StatType.Dex); - m.FixedParticles( 0x375A, 10, 15, 5010, EffectLayer.Waist ); - m.PlaySound( 0x1e7 ); + m.FixedParticles(0x375A, 10, 15, 5010, EffectLayer.Waist); + m.PlaySound(0x1e7); - int percentage = (int)(SpellHelper.GetOffsetScalar( Caster, m, false )*100); - TimeSpan length = SpellHelper.GetDuration( Caster, m ); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, false) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Agility, 1075841, length, m, percentage.ToString() ) ); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Agility, 1075841, length, m, percentage.ToString())); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private AgilitySpell m_Owner; + private class InternalTarget : Target + { + private AgilitySpell m_Owner; - public InternalTarget( AgilitySpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(AgilitySpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/Cunning.cs b/Scripts/Spells/Second/Cunning.cs index 6ca9fba93..6b1659e09 100644 --- a/Scripts/Spells/Second/Cunning.cs +++ b/Scripts/Spells/Second/Cunning.cs @@ -1,85 +1,83 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Spells.Second { - public class CunningSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Cunning", "Uus Wis", - 212, - 9061, - Reagent.MandrakeRoot, - Reagent.Nightshade - ); + public class CunningSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Cunning", "Uus Wis", + 212, + 9061, + Reagent.MandrakeRoot, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Second; + public CunningSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public CunningSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.AddStatBonus( Caster, m, StatType.Int ); + SpellHelper.AddStatBonus(Caster, m, StatType.Int); - m.FixedParticles( 0x375A, 10, 15, 5011, EffectLayer.Head ); - m.PlaySound( 0x1EB ); + m.FixedParticles(0x375A, 10, 15, 5011, EffectLayer.Head); + m.PlaySound(0x1EB); - int percentage = (int)(SpellHelper.GetOffsetScalar( Caster, m, false )*100); - TimeSpan length = SpellHelper.GetDuration( Caster, m ); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, false) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Cunning, 1075843, length, m, percentage.ToString() ) ); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Cunning, 1075843, length, m, percentage.ToString())); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private CunningSpell m_Owner; + private class InternalTarget : Target + { + private CunningSpell m_Owner; - public InternalTarget( CunningSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(CunningSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/Cure.cs b/Scripts/Spells/Second/Cure.cs index ee6a3ffa7..56bd9aac5 100644 --- a/Scripts/Spells/Second/Cure.cs +++ b/Scripts/Spells/Second/Cure.cs @@ -1,100 +1,99 @@ +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Spells.Second { - public class CureSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Cure", "An Nox", - 212, - 9061, - Reagent.Garlic, - Reagent.Ginseng - ); + public class CureSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Cure", "An Nox", + 212, + 9061, + Reagent.Garlic, + Reagent.Ginseng + ); - public override SpellCircle Circle => SpellCircle.Second; + public CureSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public CureSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - Poison p = m.Poison; + Poison p = m.Poison; - if ( p != null ) - { - int chanceToCure = 10000 + (int)(Caster.Skills[SkillName.Magery].Value * 75) - ((p.Level + 1) * (Core.AOS ? (p.Level < 4 ? 3300 : 3100) : 1750)); - chanceToCure /= 100; + if (p != null) + { + int chanceToCure = 10000 + (int)(Caster.Skills[SkillName.Magery].Value * 75) - + (p.Level + 1) * (Core.AOS ? p.Level < 4 ? 3300 : 3100 : 1750); + chanceToCure /= 100; - if ( chanceToCure > Utility.Random( 100 ) ) - { - if ( m.CurePoison( Caster ) ) - { - if ( Caster != m ) - Caster.SendLocalizedMessage( 1010058 ); // You have cured the target of all poisons! + if (chanceToCure > Utility.Random(100)) + { + if (m.CurePoison(Caster)) + { + if (Caster != m) + Caster.SendLocalizedMessage(1010058); // You have cured the target of all poisons! - m.SendLocalizedMessage( 1010059 ); // You have been cured of all poisons. - } - } - else - { - m.SendLocalizedMessage( 1010060 ); // You have failed to cure your target! - } - } + m.SendLocalizedMessage(1010059); // You have been cured of all poisons. + } + } + else + { + m.SendLocalizedMessage(1010060); // You have failed to cure your target! + } + } - m.FixedParticles( 0x373A, 10, 15, 5012, EffectLayer.Waist ); - m.PlaySound( 0x1E0 ); - } + m.FixedParticles(0x373A, 10, 15, 5012, EffectLayer.Waist); + m.PlaySound(0x1E0); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private CureSpell m_Owner; + public class InternalTarget : Target + { + private CureSpell m_Owner; - public InternalTarget( CureSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(CureSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/Harm.cs b/Scripts/Spells/Second/Harm.cs index 9708c5616..ef6db5836 100644 --- a/Scripts/Spells/Second/Harm.cs +++ b/Scripts/Spells/Second/Harm.cs @@ -2,111 +2,108 @@ using Server.Targeting; namespace Server.Spells.Second { - public class HarmSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Harm", "An Mani", - 212, - Core.AOS ? 9001 : 9041, - Reagent.Nightshade, - Reagent.SpidersSilk - ); + public class HarmSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Harm", "An Mani", + 212, + Core.AOS ? 9001 : 9041, + Reagent.Nightshade, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Second; + public HarmSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public HarmSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => false; - public override bool DelayedDamage => false; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public override double GetSlayerDamageScalar( Mobile target ) - { - return 1.0; //This spell isn't affected by slayer spellbooks - } + public override double GetSlayerDamageScalar(Mobile target) + { + return 1.0; //This spell isn't affected by slayer spellbooks + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - double damage; + double damage; - if ( Core.AOS ) - { - damage = GetNewAosDamage( 17, 1, 5, m ); - } - else - { - damage = Utility.Random( 1, 15 ); + if (Core.AOS) + { + damage = GetNewAosDamage(17, 1, 5, m); + } + else + { + damage = Utility.Random(1, 15); - if ( CheckResisted( m ) ) - { - damage *= 0.75; + if (CheckResisted(m)) + { + damage *= 0.75; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - damage *= GetDamageScalar( m ); - } + damage *= GetDamageScalar(m); + } - if ( !m.InRange( Caster, 2 ) ) - damage *= 0.25; // 1/4 damage at > 2 tile range - else if ( !m.InRange( Caster, 1 ) ) - damage *= 0.50; // 1/2 damage at 2 tile range + if (!m.InRange(Caster, 2)) + damage *= 0.25; // 1/4 damage at > 2 tile range + else if (!m.InRange(Caster, 1)) + damage *= 0.50; // 1/2 damage at 2 tile range - if ( Core.AOS ) - { - m.FixedParticles( 0x374A, 10, 30, 5013, 1153, 2, EffectLayer.Waist ); - m.PlaySound( 0x0FC ); - } - else - { - m.FixedParticles( 0x374A, 10, 15, 5013, EffectLayer.Waist ); - m.PlaySound( 0x1F1 ); - } + if (Core.AOS) + { + m.FixedParticles(0x374A, 10, 30, 5013, 1153, 2, EffectLayer.Waist); + m.PlaySound(0x0FC); + } + else + { + m.FixedParticles(0x374A, 10, 15, 5013, EffectLayer.Waist); + m.PlaySound(0x1F1); + } - SpellHelper.Damage( this, m, damage, 0, 0, 100, 0, 0 ); - } + SpellHelper.Damage(this, m, damage, 0, 0, 100, 0, 0); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private HarmSpell m_Owner; + private class InternalTarget : Target + { + private HarmSpell m_Owner; - public InternalTarget( HarmSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(HarmSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/MagicTrap.cs b/Scripts/Spells/Second/MagicTrap.cs index 7ee28c2be..06a675ead 100644 --- a/Scripts/Spells/Second/MagicTrap.cs +++ b/Scripts/Spells/Second/MagicTrap.cs @@ -1,87 +1,93 @@ -using Server.Targeting; using Server.Items; +using Server.Targeting; namespace Server.Spells.Second { - public class MagicTrapSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Magic Trap", "In Jux", - 212, - 9001, - Reagent.Garlic, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); + public class MagicTrapSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Magic Trap", "In Jux", + 212, + 9001, + Reagent.Garlic, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Second; + public MagicTrapSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MagicTrapSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( TrappableContainer item ) - { - if ( !Caster.CanSee( item ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( item.TrapType != TrapType.None && item.TrapType != TrapType.MagicTrap ) - { - base.DoFizzle(); - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, item ); + public void Target(TrappableContainer item) + { + if (!Caster.CanSee(item)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (item.TrapType != TrapType.None && item.TrapType != TrapType.MagicTrap) + { + base.DoFizzle(); + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, item); - item.TrapType = TrapType.MagicTrap; - item.TrapPower = Core.AOS ? Utility.RandomMinMax( 10, 50 ) : 1; - item.TrapLevel = 0; + item.TrapType = TrapType.MagicTrap; + item.TrapPower = Core.AOS ? Utility.RandomMinMax(10, 50) : 1; + item.TrapLevel = 0; - Point3D loc = item.GetWorldLocation(); + Point3D loc = item.GetWorldLocation(); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( loc.X + 1, loc.Y, loc.Z ), item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 9502 ); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( loc.X, loc.Y - 1, loc.Z ), item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 9502 ); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( loc.X - 1, loc.Y, loc.Z ), item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 9502 ); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( loc.X, loc.Y + 1, loc.Z ), item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 9502 ); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( loc.X, loc.Y, loc.Z ), item.Map, EffectItem.DefaultDuration ), 0, 0, 0, 5014 ); + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(loc.X + 1, loc.Y, loc.Z), item.Map, EffectItem.DefaultDuration), 0x376A, 9, + 10, 9502); + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(loc.X, loc.Y - 1, loc.Z), item.Map, EffectItem.DefaultDuration), 0x376A, 9, + 10, 9502); + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(loc.X - 1, loc.Y, loc.Z), item.Map, EffectItem.DefaultDuration), 0x376A, 9, + 10, 9502); + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(loc.X, loc.Y + 1, loc.Z), item.Map, EffectItem.DefaultDuration), 0x376A, 9, + 10, 9502); + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(loc.X, loc.Y, loc.Z), item.Map, EffectItem.DefaultDuration), 0, 0, 0, + 5014); - Effects.PlaySound( loc, item.Map, 0x1EF ); - } + Effects.PlaySound(loc, item.Map, 0x1EF); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private MagicTrapSpell m_Owner; + private class InternalTarget : Target + { + private MagicTrapSpell m_Owner; - public InternalTarget( MagicTrapSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(MagicTrapSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is TrappableContainer ) - { - m_Owner.Target( (TrappableContainer)o ); - } - else - { - from.SendMessage( "You can't trap that" ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is TrappableContainer) + m_Owner.Target((TrappableContainer)o); + else + from.SendMessage("You can't trap that"); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/Protection.cs b/Scripts/Spells/Second/Protection.cs index e7050d0e6..62017a187 100644 --- a/Scripts/Spells/Second/Protection.cs +++ b/Scripts/Spells/Second/Protection.cs @@ -3,182 +3,186 @@ using System.Collections; namespace Server.Spells.Second { - public class ProtectionSpell : MagerySpell - { - public static Hashtable Registry { get; } = new Hashtable(); + public class ProtectionSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Protection", "Uus Sanct", + 236, + 9011, + Reagent.Garlic, + Reagent.Ginseng, + Reagent.SulfurousAsh + ); - private static SpellInfo m_Info = new SpellInfo( - "Protection", "Uus Sanct", - 236, - 9011, - Reagent.Garlic, - Reagent.Ginseng, - Reagent.SulfurousAsh - ); + private static Hashtable m_Table = new Hashtable(); - public override SpellCircle Circle => SpellCircle.Second; + public ProtectionSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ProtectionSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public static Hashtable Registry{ get; } = new Hashtable(); - public override bool CheckCast() - { - if ( Core.AOS ) - return true; + public override SpellCircle Circle => SpellCircle.Second; - if ( Registry.ContainsKey( Caster ) ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - return false; - } + public override bool CheckCast() + { + if (Core.AOS) + return true; - if ( !Caster.CanBeginAction( typeof( DefensiveSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - return false; - } + if (Registry.ContainsKey(Caster)) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + return false; + } - return true; - } + if (!Caster.CanBeginAction(typeof(DefensiveSpell))) + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + return false; + } - private static Hashtable m_Table = new Hashtable(); + return true; + } - public static void Toggle( Mobile caster, Mobile target ) - { - /* Players under the protection spell effect can no longer have their spells "disrupted" when hit. - * Players under the protection spell have decreased physical resistance stat value (-15 + (Inscription/20), - * a decreased "resisting spells" skill value by -35 + (Inscription/20), - * and a slower casting speed modifier (technically, a negative "faster cast speed") of 2 points. - * The protection spell has an indefinite duration, becoming active when cast, and deactivated when re-cast. - * Reactive Armor, Protection, and Magic Reflection will stay on�even after logging out, - * even after dying�until you �turn them off� by casting them again. - */ + public static void Toggle(Mobile caster, Mobile target) + { + /* Players under the protection spell effect can no longer have their spells "disrupted" when hit. + * Players under the protection spell have decreased physical resistance stat value (-15 + (Inscription/20), + * a decreased "resisting spells" skill value by -35 + (Inscription/20), + * and a slower casting speed modifier (technically, a negative "faster cast speed") of 2 points. + * The protection spell has an indefinite duration, becoming active when cast, and deactivated when re-cast. + * Reactive Armor, Protection, and Magic Reflection will stay on�even after logging out, + * even after dying�until you �turn them off� by casting them again. + */ - object[] mods = (object[])m_Table[target]; + object[] mods = (object[])m_Table[target]; - if ( mods == null ) - { - target.PlaySound( 0x1E9 ); - target.FixedParticles( 0x375A, 9, 20, 5016, EffectLayer.Waist ); + if (mods == null) + { + target.PlaySound(0x1E9); + target.FixedParticles(0x375A, 9, 20, 5016, EffectLayer.Waist); - mods = new object[2] - { - new ResistanceMod( ResistanceType.Physical, -15 + Math.Min( (int)(caster.Skills[SkillName.Inscribe].Value / 20), 15 ) ), - new DefaultSkillMod( SkillName.MagicResist, true, -35 + Math.Min( (int)(caster.Skills[SkillName.Inscribe].Value / 20), 35 ) ) - }; + mods = new object[2] + { + new ResistanceMod(ResistanceType.Physical, + -15 + Math.Min((int)(caster.Skills[SkillName.Inscribe].Value / 20), 15)), + new DefaultSkillMod(SkillName.MagicResist, true, + -35 + Math.Min((int)(caster.Skills[SkillName.Inscribe].Value / 20), 35)) + }; - m_Table[target] = mods; - Registry[target] = 100.0; + m_Table[target] = mods; + Registry[target] = 100.0; - target.AddResistanceMod( (ResistanceMod)mods[0] ); - target.AddSkillMod( (SkillMod)mods[1] ); + target.AddResistanceMod((ResistanceMod)mods[0]); + target.AddSkillMod((SkillMod)mods[1]); - int physloss = -15 + (int) (caster.Skills[SkillName.Inscribe].Value / 20); - int resistloss = -35 + (int) (caster.Skills[SkillName.Inscribe].Value / 20); - string args = $"{physloss}\t{resistloss}"; - BuffInfo.AddBuff(target, new BuffInfo(BuffIcon.Protection, 1075814, 1075815, args.ToString())); - } - else - { - target.PlaySound( 0x1ED ); - target.FixedParticles( 0x375A, 9, 20, 5016, EffectLayer.Waist ); + int physloss = -15 + (int)(caster.Skills[SkillName.Inscribe].Value / 20); + int resistloss = -35 + (int)(caster.Skills[SkillName.Inscribe].Value / 20); + string args = $"{physloss}\t{resistloss}"; + BuffInfo.AddBuff(target, new BuffInfo(BuffIcon.Protection, 1075814, 1075815, args)); + } + else + { + target.PlaySound(0x1ED); + target.FixedParticles(0x375A, 9, 20, 5016, EffectLayer.Waist); - m_Table.Remove( target ); - Registry.Remove( target ); + m_Table.Remove(target); + Registry.Remove(target); - target.RemoveResistanceMod( (ResistanceMod)mods[0] ); - target.RemoveSkillMod( (SkillMod)mods[1] ); + target.RemoveResistanceMod((ResistanceMod)mods[0]); + target.RemoveSkillMod((SkillMod)mods[1]); - BuffInfo.RemoveBuff(target, BuffIcon.Protection); - } - } + BuffInfo.RemoveBuff(target, BuffIcon.Protection); + } + } - public static void EndProtection( Mobile m ) - { - if ( m_Table.Contains( m ) ) - { - object[] mods = (object[]) m_Table[ m ]; + public static void EndProtection(Mobile m) + { + if (m_Table.Contains(m)) + { + object[] mods = (object[])m_Table[m]; - m_Table.Remove( m ); - Registry.Remove( m ); + m_Table.Remove(m); + Registry.Remove(m); - m.RemoveResistanceMod( (ResistanceMod) mods[ 0 ] ); - m.RemoveSkillMod( (SkillMod) mods[ 1 ] ); + m.RemoveResistanceMod((ResistanceMod)mods[0]); + m.RemoveSkillMod((SkillMod)mods[1]); - BuffInfo.RemoveBuff( m, BuffIcon.Protection ); - } - } + BuffInfo.RemoveBuff(m, BuffIcon.Protection); + } + } - public override void OnCast() - { - if ( Core.AOS ) - { - if ( CheckSequence() ) - Toggle( Caster, Caster ); + public override void OnCast() + { + if (Core.AOS) + { + if (CheckSequence()) + Toggle(Caster, Caster); - FinishSequence(); - } - else - { - if ( Registry.ContainsKey( Caster ) ) - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - else if ( !Caster.CanBeginAction( typeof( DefensiveSpell ) ) ) - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - } - else if ( CheckSequence() ) - { - if ( Caster.BeginAction( typeof( DefensiveSpell ) ) ) - { - double value = (int)(Caster.Skills[SkillName.EvalInt].Value + Caster.Skills[SkillName.Meditation].Value + Caster.Skills[SkillName.Inscribe].Value); - value /= 4; + FinishSequence(); + } + else + { + if (Registry.ContainsKey(Caster)) + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + else if (!Caster.CanBeginAction(typeof(DefensiveSpell))) + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + } + else if (CheckSequence()) + { + if (Caster.BeginAction(typeof(DefensiveSpell))) + { + double value = (int)(Caster.Skills[SkillName.EvalInt].Value + + Caster.Skills[SkillName.Meditation].Value + + Caster.Skills[SkillName.Inscribe].Value); + value /= 4; - if ( value < 0 ) - value = 0; - else if ( value > 75 ) - value = 75.0; + if (value < 0) + value = 0; + else if (value > 75) + value = 75.0; - Registry.Add( Caster, value ); - new InternalTimer( Caster ).Start(); + Registry.Add(Caster, value); + new InternalTimer(Caster).Start(); - Caster.FixedParticles( 0x375A, 9, 20, 5016, EffectLayer.Waist ); - Caster.PlaySound( 0x1ED ); - } - else - { - Caster.SendLocalizedMessage( 1005385 ); // The spell will not adhere to you at this time. - } - } + Caster.FixedParticles(0x375A, 9, 20, 5016, EffectLayer.Waist); + Caster.PlaySound(0x1ED); + } + else + { + Caster.SendLocalizedMessage(1005385); // The spell will not adhere to you at this time. + } + } - FinishSequence(); - } - } + FinishSequence(); + } + } - private class InternalTimer : Timer - { - private Mobile m_Caster; + private class InternalTimer : Timer + { + private Mobile m_Caster; - public InternalTimer( Mobile caster ) : base( TimeSpan.FromSeconds( 0 ) ) - { - double val = caster.Skills[SkillName.Magery].Value * 2.0; - if ( val < 15 ) - val = 15; - else if ( val > 240 ) - val = 240; + public InternalTimer(Mobile caster) : base(TimeSpan.FromSeconds(0)) + { + double val = caster.Skills[SkillName.Magery].Value * 2.0; + if (val < 15) + val = 15; + else if (val > 240) + val = 240; - m_Caster = caster; - Delay = TimeSpan.FromSeconds( val ); - Priority = TimerPriority.OneSecond; - } + m_Caster = caster; + Delay = TimeSpan.FromSeconds(val); + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - Registry.Remove( m_Caster ); - DefensiveSpell.Nullify( m_Caster ); - } - } - } -} + protected override void OnTick() + { + Registry.Remove(m_Caster); + DefensiveSpell.Nullify(m_Caster); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/RemoveTrap.cs b/Scripts/Spells/Second/RemoveTrap.cs index 9d58f61cd..ff652357d 100644 --- a/Scripts/Spells/Second/RemoveTrap.cs +++ b/Scripts/Spells/Second/RemoveTrap.cs @@ -1,82 +1,79 @@ -using Server.Targeting; using Server.Items; +using Server.Targeting; namespace Server.Spells.Second { - public class RemoveTrapSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Remove Trap", "An Jux", - 212, - 9001, - Reagent.Bloodmoss, - Reagent.SulfurousAsh - ); + public class RemoveTrapSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Remove Trap", "An Jux", + 212, + 9001, + Reagent.Bloodmoss, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Second; + public RemoveTrapSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public RemoveTrapSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - Caster.SendMessage( "What do you wish to untrap?" ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + Caster.SendMessage("What do you wish to untrap?"); + } - public void Target( TrappableContainer item ) - { - if ( !Caster.CanSee( item ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( item.TrapType != TrapType.None && item.TrapType != TrapType.MagicTrap ) - { - base.DoFizzle(); - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, item ); + public void Target(TrappableContainer item) + { + if (!Caster.CanSee(item)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (item.TrapType != TrapType.None && item.TrapType != TrapType.MagicTrap) + { + base.DoFizzle(); + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, item); - Point3D loc = item.GetWorldLocation(); + Point3D loc = item.GetWorldLocation(); - Effects.SendLocationParticles( EffectItem.Create( loc, item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5015 ); - Effects.PlaySound( loc, item.Map, 0x1F0 ); + Effects.SendLocationParticles(EffectItem.Create(loc, item.Map, EffectItem.DefaultDuration), 0x376A, 9, 32, + 5015); + Effects.PlaySound(loc, item.Map, 0x1F0); - item.TrapType = TrapType.None; - item.TrapPower = 0; - item.TrapLevel = 0; - } + item.TrapType = TrapType.None; + item.TrapPower = 0; + item.TrapLevel = 0; + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private RemoveTrapSpell m_Owner; + private class InternalTarget : Target + { + private RemoveTrapSpell m_Owner; - public InternalTarget( RemoveTrapSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(RemoveTrapSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is TrappableContainer ) - { - m_Owner.Target( (TrappableContainer)o ); - } - else - { - from.SendMessage( "You can't disarm that" ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is TrappableContainer) + m_Owner.Target((TrappableContainer)o); + else + from.SendMessage("You can't disarm that"); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Second/Strength.cs b/Scripts/Spells/Second/Strength.cs index 66d7dcc83..c6033bb97 100644 --- a/Scripts/Spells/Second/Strength.cs +++ b/Scripts/Spells/Second/Strength.cs @@ -1,85 +1,83 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Spells.Second { - public class StrengthSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Strength", "Uus Mani", - 212, - 9061, - Reagent.MandrakeRoot, - Reagent.Nightshade - ); + public class StrengthSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Strength", "Uus Mani", + 212, + 9061, + Reagent.MandrakeRoot, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Second; + public StrengthSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public StrengthSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Second; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.AddStatBonus( Caster, m, StatType.Str ); + SpellHelper.AddStatBonus(Caster, m, StatType.Str); - m.FixedParticles( 0x375A, 10, 15, 5017, EffectLayer.Waist ); - m.PlaySound( 0x1EE ); + m.FixedParticles(0x375A, 10, 15, 5017, EffectLayer.Waist); + m.PlaySound(0x1EE); - int percentage = (int)(SpellHelper.GetOffsetScalar( Caster, m, false )*100); - TimeSpan length = SpellHelper.GetDuration( Caster, m ); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, false) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Strength, 1075845, length, m, percentage.ToString() ) ); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Strength, 1075845, length, m, percentage.ToString())); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private StrengthSpell m_Owner; + private class InternalTarget : Target + { + private StrengthSpell m_Owner; - public InternalTarget( StrengthSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(StrengthSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/ChainLightning.cs b/Scripts/Spells/Seventh/ChainLightning.cs index b7c928b76..b82a66550 100644 --- a/Scripts/Spells/Seventh/ChainLightning.cs +++ b/Scripts/Spells/Seventh/ChainLightning.cs @@ -3,138 +3,139 @@ using Server.Targeting; namespace Server.Spells.Seventh { - public class ChainLightningSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Chain Lightning", "Vas Ort Grav", - 209, - 9022, - false, - Reagent.BlackPearl, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class ChainLightningSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Chain Lightning", "Vas Ort Grav", + 209, + 9022, + false, + Reagent.BlackPearl, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Seventh; + public ChainLightningSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ChainLightningSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => true; - public override bool DelayedDamage => true; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - if ( p is Item ) - p = ((Item)p).GetWorldLocation(); + if (p is Item) + p = ((Item)p).GetWorldLocation(); - List targets = new List(); + List targets = new List(); - Map map = Caster.Map; + Map map = Caster.Map; - bool playerVsPlayer = false; + bool playerVsPlayer = false; - if ( map != null ) - { - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), 2 ); + if (map != null) + { + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), 2); - foreach ( Mobile m in eable ) - { - if ( Core.AOS && m == Caster ) - continue; + foreach (Mobile m in eable) + { + if (Core.AOS && m == Caster) + continue; - if ( SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) ) - { - if ( Core.AOS && !Caster.InLOS( m ) ) - continue; + if (SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false)) + { + if (Core.AOS && !Caster.InLOS(m)) + continue; - targets.Add( m ); + targets.Add(m); - if ( m.Player ) - playerVsPlayer = true; - } - } + if (m.Player) + playerVsPlayer = true; + } + } - eable.Free(); - } + eable.Free(); + } - double damage; + double damage; - if ( Core.AOS ) - damage = GetNewAosDamage( 51, 1, 5, playerVsPlayer ); - else - damage = Utility.Random( 27, 22 ); + if (Core.AOS) + damage = GetNewAosDamage(51, 1, 5, playerVsPlayer); + else + damage = Utility.Random(27, 22); - if ( targets.Count > 0 ) - { - if ( Core.AOS && targets.Count > 2 ) - damage = (damage * 2) / targets.Count; - else if ( !Core.AOS ) - damage /= targets.Count; + if (targets.Count > 0) + { + if (Core.AOS && targets.Count > 2) + damage = damage * 2 / targets.Count; + else if (!Core.AOS) + damage /= targets.Count; - double toDeal; - for ( int i = 0; i < targets.Count; ++i ) - { - toDeal = damage; - Mobile m = targets[i]; + double toDeal; + for (int i = 0; i < targets.Count; ++i) + { + toDeal = damage; + Mobile m = targets[i]; - if ( !Core.AOS && CheckResisted( m ) ) - { - toDeal *= 0.5; + if (!Core.AOS && CheckResisted(m)) + { + toDeal *= 0.5; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } - toDeal *= GetDamageScalar( m ); - Caster.DoHarmful( m ); - SpellHelper.Damage( this, m, toDeal, 0, 0, 0, 0, 100 ); + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - m.BoltEffect( 0 ); - } - } - else - { - Caster.PlaySound ( 0x29 ); - } - } + toDeal *= GetDamageScalar(m); + Caster.DoHarmful(m); + SpellHelper.Damage(this, m, toDeal, 0, 0, 0, 0, 100); - FinishSequence(); - } + m.BoltEffect(0); + } + } + else + { + Caster.PlaySound(0x29); + } + } - private class InternalTarget : Target - { - private ChainLightningSpell m_Owner; + FinishSequence(); + } - public InternalTarget( ChainLightningSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + private class InternalTarget : Target + { + private ChainLightningSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + public InternalTarget(ChainLightningSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - if ( p != null ) - m_Owner.Target( p ); - } + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + if (p != null) + m_Owner.Target(p); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/EnergyField.cs b/Scripts/Spells/Seventh/EnergyField.cs index 4d4df4a43..71040c27e 100644 --- a/Scripts/Spells/Seventh/EnergyField.cs +++ b/Scripts/Spells/Seventh/EnergyField.cs @@ -1,206 +1,201 @@ using System; -using Server.Targeting; -using Server.Misc; using Server.Items; +using Server.Misc; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Seventh { - public class EnergyFieldSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Energy Field", "In Sanct Grav", - 221, - 9022, - false, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); + public class EnergyFieldSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Energy Field", "In Sanct Grav", + 221, + 9022, + false, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Seventh; + public EnergyFieldSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EnergyFieldSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - int dx = Caster.Location.X - p.X; - int dy = Caster.Location.Y - p.Y; - int rx = (dx - dy) * 44; - int ry = (dx + dy) * 44; + int dx = Caster.Location.X - p.X; + int dy = Caster.Location.Y - p.Y; + int rx = (dx - dy) * 44; + int ry = (dx + dy) * 44; - bool eastToWest; + bool eastToWest; - if ( rx >= 0 && ry >= 0 ) - { - eastToWest = false; - } - else if ( rx >= 0 ) - { - eastToWest = true; - } - else if ( ry >= 0 ) - { - eastToWest = true; - } - else - { - eastToWest = false; - } + if (rx >= 0 && ry >= 0) + eastToWest = false; + else if (rx >= 0) + eastToWest = true; + else if (ry >= 0) + eastToWest = true; + else + eastToWest = false; - Effects.PlaySound( p, Caster.Map, 0x20B ); + Effects.PlaySound(p, Caster.Map, 0x20B); - TimeSpan duration; + TimeSpan duration; - if ( Core.AOS ) - duration = TimeSpan.FromSeconds( (15 + (Caster.Skills.Magery.Fixed / 5)) / 7 ); - else - duration = TimeSpan.FromSeconds( Caster.Skills[SkillName.Magery].Value * 0.28 + 2.0 ); // (28% of magery) + 2.0 seconds + if (Core.AOS) + duration = TimeSpan.FromSeconds((15 + Caster.Skills.Magery.Fixed / 5) / 7); + else + duration = TimeSpan.FromSeconds(Caster.Skills[SkillName.Magery].Value * 0.28 + + 2.0); // (28% of magery) + 2.0 seconds - int itemID = eastToWest ? 0x3946 : 0x3956; + int itemID = eastToWest ? 0x3946 : 0x3956; - for ( int i = -2; i <= 2; ++i ) - { - Point3D loc = new Point3D( eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z ); - bool canFit = SpellHelper.AdjustField( ref loc, Caster.Map, 12, false ); + for (int i = -2; i <= 2; ++i) + { + Point3D loc = new Point3D(eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z); + bool canFit = SpellHelper.AdjustField(ref loc, Caster.Map, 12, false); - if ( !canFit ) - continue; + if (!canFit) + continue; - Item item = new InternalItem( loc, Caster.Map, duration, itemID, Caster ); - item.ProcessDelta(); + Item item = new InternalItem(loc, Caster.Map, duration, itemID, Caster); + item.ProcessDelta(); - Effects.SendLocationParticles( EffectItem.Create( loc, Caster.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 5051 ); - } - } + Effects.SendLocationParticles(EffectItem.Create(loc, Caster.Map, EffectItem.DefaultDuration), 0x376A, 9, + 10, 5051); + } + } - FinishSequence(); - } + FinishSequence(); + } - [DispellableField] - private class InternalItem : Item - { - private Timer m_Timer; - private Mobile m_Caster; + [DispellableField] + private class InternalItem : Item + { + private Mobile m_Caster; + private Timer m_Timer; - public override bool BlocksFit => true; + public InternalItem(Point3D loc, Map map, TimeSpan duration, int itemID, Mobile caster) : base(itemID) + { + Visible = false; + Movable = false; + Light = LightType.Circle300; - public InternalItem( Point3D loc, Map map, TimeSpan duration, int itemID, Mobile caster ) : base( itemID ) - { - Visible = false; - Movable = false; - Light = LightType.Circle300; + MoveToWorld(loc, map); - MoveToWorld( loc, map ); + m_Caster = caster; - m_Caster = caster; + if (caster.InLOS(this)) + Visible = true; + else + Delete(); - if ( caster.InLOS( this ) ) - Visible = true; - else - Delete(); + if (Deleted) + return; - if ( Deleted ) - return; + m_Timer = new InternalTimer(this, duration); + m_Timer.Start(); + } - m_Timer = new InternalTimer( this, duration ); - m_Timer.Start(); - } + public InternalItem(Serial serial) : base(serial) + { + m_Timer = new InternalTimer(this, TimeSpan.FromSeconds(5.0)); + m_Timer.Start(); + } - public InternalItem( Serial serial ) : base( serial ) - { - m_Timer = new InternalTimer( this, TimeSpan.FromSeconds( 5.0 ) ); - m_Timer.Start(); - } + public override bool BlocksFit => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } + int version = reader.ReadInt(); + } - public override bool OnMoveOver( Mobile m ) - { - int noto; + public override bool OnMoveOver(Mobile m) + { + int noto; - if ( m is PlayerMobile ) - { - noto = Notoriety.Compute( m_Caster, m ); - if ( noto == Notoriety.Enemy || noto == Notoriety.Ally ) - return false; - } - return base.OnMoveOver( m ); - } + if (m is PlayerMobile) + { + noto = Notoriety.Compute(m_Caster, m); + if (noto == Notoriety.Enemy || noto == Notoriety.Ally) + return false; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + return base.OnMoveOver(m); + } - m_Timer?.Stop(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - private class InternalTimer : Timer - { - private InternalItem m_Item; + m_Timer?.Stop(); + } - public InternalTimer( InternalItem item, TimeSpan duration ) : base( duration ) - { - Priority = TimerPriority.OneSecond; - m_Item = item; - } + private class InternalTimer : Timer + { + private InternalItem m_Item; - protected override void OnTick() - { - m_Item.Delete(); - } - } - } + public InternalTimer(InternalItem item, TimeSpan duration) : base(duration) + { + Priority = TimerPriority.OneSecond; + m_Item = item; + } - private class InternalTarget : Target - { - private EnergyFieldSpell m_Owner; + protected override void OnTick() + { + m_Item.Delete(); + } + } + } - public InternalTarget( EnergyFieldSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + private class InternalTarget : Target + { + private EnergyFieldSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } + public InternalTarget(EnergyFieldSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/FlameStrike.cs b/Scripts/Spells/Seventh/FlameStrike.cs index c448c8bcd..ae41034e6 100644 --- a/Scripts/Spells/Seventh/FlameStrike.cs +++ b/Scripts/Spells/Seventh/FlameStrike.cs @@ -2,91 +2,88 @@ using Server.Targeting; namespace Server.Spells.Seventh { - public class FlameStrikeSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Flame Strike", "Kal Vas Flam", - 245, - 9042, - Reagent.SpidersSilk, - Reagent.SulfurousAsh - ); + public class FlameStrikeSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Flame Strike", "Kal Vas Flam", + 245, + 9042, + Reagent.SpidersSilk, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Seventh; + public FlameStrikeSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public FlameStrikeSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => true; - public override bool DelayedDamage => true; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - double damage; + double damage; - if ( Core.AOS ) - { - damage = GetNewAosDamage( 48, 1, 5, m ); - } - else - { - damage = Utility.Random( 27, 22 ); + if (Core.AOS) + { + damage = GetNewAosDamage(48, 1, 5, m); + } + else + { + damage = Utility.Random(27, 22); - if ( CheckResisted( m ) ) - { - damage *= 0.6; + if (CheckResisted(m)) + { + damage *= 0.6; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - damage *= GetDamageScalar( m ); - } + damage *= GetDamageScalar(m); + } - m.FixedParticles( 0x3709, 10, 30, 5052, EffectLayer.LeftFoot ); - m.PlaySound( 0x208 ); + m.FixedParticles(0x3709, 10, 30, 5052, EffectLayer.LeftFoot); + m.PlaySound(0x208); - SpellHelper.Damage( this, m, damage, 0, 100, 0, 0, 0 ); - } + SpellHelper.Damage(this, m, damage, 0, 100, 0, 0, 0); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private FlameStrikeSpell m_Owner; + private class InternalTarget : Target + { + private FlameStrikeSpell m_Owner; - public InternalTarget( FlameStrikeSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(FlameStrikeSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/GateTravel.cs b/Scripts/Spells/Seventh/GateTravel.cs index 47e339d16..79e33e82d 100644 --- a/Scripts/Spells/Seventh/GateTravel.cs +++ b/Scripts/Spells/Seventh/GateTravel.cs @@ -1,257 +1,260 @@ using System; -using Server.Network; +using Server.Factions; using Server.Items; -using Server.Targeting; using Server.Misc; using Server.Mobiles; +using Server.Network; +using Server.Targeting; namespace Server.Spells.Seventh { - public class GateTravelSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Gate Travel", "Vas Rel Por", - 263, - 9032, - Reagent.BlackPearl, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class GateTravelSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Gate Travel", "Vas Rel Por", + 263, + 9032, + Reagent.BlackPearl, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Seventh; + private RunebookEntry m_Entry; - private RunebookEntry m_Entry; + public GateTravelSpell(Mobile caster, Item scroll) : this(caster, scroll, null) + { + } - public GateTravelSpell( Mobile caster, Item scroll ) : this( caster, scroll, null ) - { - } + public GateTravelSpell(Mobile caster, Item scroll, RunebookEntry entry) : base(caster, scroll, m_Info) + { + m_Entry = entry; + } - public GateTravelSpell( Mobile caster, Item scroll, RunebookEntry entry ) : base( caster, scroll, m_Info ) - { - m_Entry = entry; - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - if ( m_Entry == null ) - Caster.Target = new InternalTarget( this ); - else - Effect( m_Entry.Location, m_Entry.Map, true ); - } + public override void OnCast() + { + if (m_Entry == null) + Caster.Target = new InternalTarget(this); + else + Effect(m_Entry.Location, m_Entry.Map, true); + } - public override bool CheckCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } + public override bool CheckCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } - if ( Caster.Criminal ) - { - Caster.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - return false; - } - if ( SpellHelper.CheckCombat( Caster ) ) - { - Caster.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - return false; - } + if (Caster.Criminal) + { + Caster.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + return false; + } - return SpellHelper.CheckTravel( Caster, TravelCheckType.GateFrom ); - } + if (SpellHelper.CheckCombat(Caster)) + { + Caster.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + return false; + } - private bool GateExistsAt(Map map, Point3D loc ) - { - bool _gateFound = false; + return SpellHelper.CheckTravel(Caster, TravelCheckType.GateFrom); + } - IPooledEnumerable eable = map.GetItemsInRange( loc, 0 ); - foreach ( Item item in eable ) - { - if ( item is Moongate || item is PublicMoongate ) - { - _gateFound = true; - break; - } - } - eable.Free(); + private bool GateExistsAt(Map map, Point3D loc) + { + bool _gateFound = false; - return _gateFound; - } + IPooledEnumerable eable = map.GetItemsInRange(loc, 0); + foreach (Item item in eable) + if (item is Moongate || item is PublicMoongate) + { + _gateFound = true; + break; + } - public void Effect( Point3D loc, Map map, bool checkMulti ) - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( map == null || (!Core.AOS && Caster.Map != map) ) - { - Caster.SendLocalizedMessage( 1005570 ); // You can not gate to another facet. - } - else if ( !SpellHelper.CheckTravel( Caster, TravelCheckType.GateFrom ) ) - { - } - else if ( !SpellHelper.CheckTravel( Caster, map, loc, TravelCheckType.GateTo ) ) - { - } - else if ( map == Map.Felucca && Caster is PlayerMobile && ((PlayerMobile)Caster).Young ) - { - Caster.SendLocalizedMessage( 1049543 ); // You decide against traveling to Felucca while you are still young. - } - else if ( Caster.Kills >= 5 && map != Map.Felucca ) - { - Caster.SendLocalizedMessage( 1019004 ); // You are not allowed to travel there. - } - else if ( Caster.Criminal ) - { - Caster.SendLocalizedMessage( 1005561, "", 0x22 ); // Thou'rt a criminal and cannot escape so easily. - } - else if ( SpellHelper.CheckCombat( Caster ) ) - { - Caster.SendLocalizedMessage( 1005564, "", 0x22 ); // Wouldst thou flee during the heat of battle?? - } - else if ( !map.CanSpawnMobile( loc.X, loc.Y, loc.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( (checkMulti && SpellHelper.CheckMulti( loc, map )) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( Core.SE && ( GateExistsAt( map, loc ) || GateExistsAt( Caster.Map, Caster.Location ) ) ) // SE restricted stacking gates - { - Caster.SendLocalizedMessage( 1071242 ); // There is already a gate there. - } - else if ( CheckSequence() ) - { - Caster.SendLocalizedMessage( 501024 ); // You open a magical gate to another location + eable.Free(); - Effects.PlaySound( Caster.Location, Caster.Map, 0x20E ); + return _gateFound; + } - InternalItem firstGate = new InternalItem( loc, map ); - firstGate.MoveToWorld( Caster.Location, Caster.Map ); + public void Effect(Point3D loc, Map map, bool checkMulti) + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (map == null || !Core.AOS && Caster.Map != map) + { + Caster.SendLocalizedMessage(1005570); // You can not gate to another facet. + } + else if (!SpellHelper.CheckTravel(Caster, TravelCheckType.GateFrom)) + { + } + else if (!SpellHelper.CheckTravel(Caster, map, loc, TravelCheckType.GateTo)) + { + } + else if (map == Map.Felucca && Caster is PlayerMobile && ((PlayerMobile)Caster).Young) + { + Caster.SendLocalizedMessage(1049543); // You decide against traveling to Felucca while you are still young. + } + else if (Caster.Kills >= 5 && map != Map.Felucca) + { + Caster.SendLocalizedMessage(1019004); // You are not allowed to travel there. + } + else if (Caster.Criminal) + { + Caster.SendLocalizedMessage(1005561, "", 0x22); // Thou'rt a criminal and cannot escape so easily. + } + else if (SpellHelper.CheckCombat(Caster)) + { + Caster.SendLocalizedMessage(1005564, "", 0x22); // Wouldst thou flee during the heat of battle?? + } + else if (!map.CanSpawnMobile(loc.X, loc.Y, loc.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (checkMulti && SpellHelper.CheckMulti(loc, map)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (Core.SE && (GateExistsAt(map, loc) || GateExistsAt(Caster.Map, Caster.Location)) + ) // SE restricted stacking gates + { + Caster.SendLocalizedMessage(1071242); // There is already a gate there. + } + else if (CheckSequence()) + { + Caster.SendLocalizedMessage(501024); // You open a magical gate to another location - Effects.PlaySound( loc, map, 0x20E ); + Effects.PlaySound(Caster.Location, Caster.Map, 0x20E); - InternalItem secondGate = new InternalItem( Caster.Location, Caster.Map ); - secondGate.MoveToWorld( loc, map ); - } + InternalItem firstGate = new InternalItem(loc, map); + firstGate.MoveToWorld(Caster.Location, Caster.Map); - FinishSequence(); - } + Effects.PlaySound(loc, map, 0x20E); - [DispellableField] - private class InternalItem : Moongate - { - public override bool ShowFeluccaWarning => Core.AOS; + InternalItem secondGate = new InternalItem(Caster.Location, Caster.Map); + secondGate.MoveToWorld(loc, map); + } - public InternalItem( Point3D target, Map map ) : base( target, map ) - { - Map = map; + FinishSequence(); + } - if ( ShowFeluccaWarning && map == Map.Felucca ) - ItemID = 0xDDA; + [DispellableField] + private class InternalItem : Moongate + { + public InternalItem(Point3D target, Map map) : base(target, map) + { + Map = map; - Dispellable = true; + if (ShowFeluccaWarning && map == Map.Felucca) + ItemID = 0xDDA; - InternalTimer t = new InternalTimer( this ); - t.Start(); - } + Dispellable = true; - public InternalItem( Serial serial ) : base( serial ) - { - } + InternalTimer t = new InternalTimer(this); + t.Start(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - } + public InternalItem(Serial serial) : base(serial) + { + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override bool ShowFeluccaWarning => Core.AOS; - Delete(); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + } - private class InternalTimer : Timer - { - private Item m_Item; + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - public InternalTimer( Item item ) : base( TimeSpan.FromSeconds( 30.0 ) ) - { - Priority = TimerPriority.OneSecond; - m_Item = item; - } + Delete(); + } - protected override void OnTick() - { - m_Item.Delete(); - } - } - } + private class InternalTimer : Timer + { + private Item m_Item; - private class InternalTarget : Target - { - private GateTravelSpell m_Owner; + public InternalTimer(Item item) : base(TimeSpan.FromSeconds(30.0)) + { + Priority = TimerPriority.OneSecond; + m_Item = item; + } - public InternalTarget( GateTravelSpell owner ) : base( 12, false, TargetFlags.None ) - { - m_Owner = owner; + protected override void OnTick() + { + m_Item.Delete(); + } + } + } - owner.Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501029 ); // Select Marked item. - } + private class InternalTarget : Target + { + private GateTravelSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - if ( o is RecallRune ) - { - RecallRune rune = (RecallRune)o; + public InternalTarget(GateTravelSpell owner) : base(12, false, TargetFlags.None) + { + m_Owner = owner; - if ( rune.Marked ) - m_Owner.Effect( rune.Target, rune.TargetMap, true ); - else - from.SendLocalizedMessage( 501803 ); // That rune is not yet marked. - } - else if ( o is Runebook ) - { - RunebookEntry e = ((Runebook)o).Default; + owner.Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501029); // Select Marked item. + } - if ( e != null ) - m_Owner.Effect( e.Location, e.Map, true ); - else - from.SendLocalizedMessage( 502354 ); // Target is not marked. - } - /*else if ( o is Key && ((Key)o).KeyValue != 0 && ((Key)o).Link is BaseBoat ) - { - BaseBoat boat = ((Key)o).Link as BaseBoat; + protected override void OnTarget(Mobile from, object o) + { + if (o is RecallRune) + { + RecallRune rune = (RecallRune)o; - if ( !boat.Deleted && boat.CheckKey( ((Key)o).KeyValue ) ) - m_Owner.Effect( boat.GetMarkedLocation(), boat.Map, false ); - else - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 501030, from.Name, "" ) ); // I can not gate travel from that object. - }*/ - else if ( o is HouseRaffleDeed && ((HouseRaffleDeed)o).ValidLocation() ) - { - HouseRaffleDeed deed = (HouseRaffleDeed)o; + if (rune.Marked) + m_Owner.Effect(rune.Target, rune.TargetMap, true); + else + from.SendLocalizedMessage(501803); // That rune is not yet marked. + } + else if (o is Runebook) + { + RunebookEntry e = ((Runebook)o).Default; - m_Owner.Effect( deed.PlotLocation, deed.PlotFacet, true ); - } - else - { - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 501030, from.Name, "" ) ); // I can not gate travel from that object. - } - } + if (e != null) + m_Owner.Effect(e.Location, e.Map, true); + else + from.SendLocalizedMessage(502354); // Target is not marked. + } + /*else if ( o is Key && ((Key)o).KeyValue != 0 && ((Key)o).Link is BaseBoat ) + { + BaseBoat boat = ((Key)o).Link as BaseBoat; - protected override void OnNonlocalTarget( Mobile from, object o ) - { - } + if ( !boat.Deleted && boat.CheckKey( ((Key)o).KeyValue ) ) + m_Owner.Effect( boat.GetMarkedLocation(), boat.Map, false ); + else + from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 501030, from.Name, "" ) ); // I can not gate travel from that object. + }*/ + else if (o is HouseRaffleDeed && ((HouseRaffleDeed)o).ValidLocation()) + { + HouseRaffleDeed deed = (HouseRaffleDeed)o; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + m_Owner.Effect(deed.PlotLocation, deed.PlotFacet, true); + } + else + { + from.Send(new MessageLocalized(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 501030, from.Name, + "")); // I can not gate travel from that object. + } + } + + protected override void OnNonlocalTarget(Mobile from, object o) + { + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/ManaVampire.cs b/Scripts/Spells/Seventh/ManaVampire.cs index df6dd1346..3b6043fdb 100644 --- a/Scripts/Spells/Seventh/ManaVampire.cs +++ b/Scripts/Spells/Seventh/ManaVampire.cs @@ -2,118 +2,115 @@ using Server.Targeting; namespace Server.Spells.Seventh { - public class ManaVampireSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mana Vampire", "Ort Sanct", - 221, - 9032, - Reagent.BlackPearl, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SpidersSilk - ); + public class ManaVampireSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mana Vampire", "Ort Sanct", + 221, + 9032, + Reagent.BlackPearl, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Seventh; + public ManaVampireSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ManaVampireSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - int toDrain = 0; + int toDrain = 0; - if ( Core.AOS ) - { - toDrain = (int)(GetDamageSkill( Caster ) - GetResistSkill( m )); + if (Core.AOS) + { + toDrain = (int)(GetDamageSkill(Caster) - GetResistSkill(m)); - if ( !m.Player ) - toDrain /= 2; + if (!m.Player) + toDrain /= 2; - if ( toDrain < 0 ) - toDrain = 0; - else if ( toDrain > m.Mana ) - toDrain = m.Mana; - } - else - { - if ( CheckResisted( m ) ) - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - else - toDrain = m.Mana; - } + if (toDrain < 0) + toDrain = 0; + else if (toDrain > m.Mana) + toDrain = m.Mana; + } + else + { + if (CheckResisted(m)) + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + else + toDrain = m.Mana; + } - if ( toDrain > (Caster.ManaMax - Caster.Mana) ) - toDrain = Caster.ManaMax - Caster.Mana; + if (toDrain > Caster.ManaMax - Caster.Mana) + toDrain = Caster.ManaMax - Caster.Mana; - m.Mana -= toDrain; - Caster.Mana += toDrain; + m.Mana -= toDrain; + Caster.Mana += toDrain; - if ( Core.AOS ) - { - m.FixedParticles( 0x374A, 1, 15, 5054, 23, 7, EffectLayer.Head ); - m.PlaySound( 0x1F9 ); + if (Core.AOS) + { + m.FixedParticles(0x374A, 1, 15, 5054, 23, 7, EffectLayer.Head); + m.PlaySound(0x1F9); - Caster.FixedParticles( 0x0000, 10, 5, 2054, EffectLayer.Head ); - } - else - { - m.FixedParticles( 0x374A, 10, 15, 5054, EffectLayer.Head ); - m.PlaySound( 0x1F9 ); - } + Caster.FixedParticles(0x0000, 10, 5, 2054, EffectLayer.Head); + } + else + { + m.FixedParticles(0x374A, 10, 15, 5054, EffectLayer.Head); + m.PlaySound(0x1F9); + } - HarmfulSpell( m ); - } + HarmfulSpell(m); + } - FinishSequence(); - } + FinishSequence(); + } - public override double GetResistPercent( Mobile target ) - { - return 98.0; - } + public override double GetResistPercent(Mobile target) + { + return 98.0; + } - private class InternalTarget : Target - { - private ManaVampireSpell m_Owner; + private class InternalTarget : Target + { + private ManaVampireSpell m_Owner; - public InternalTarget( ManaVampireSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(ManaVampireSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/MassDispel.cs b/Scripts/Spells/Seventh/MassDispel.cs index c7881be15..016d5c9f4 100644 --- a/Scripts/Spells/Seventh/MassDispel.cs +++ b/Scripts/Spells/Seventh/MassDispel.cs @@ -1,111 +1,113 @@ using System.Collections.Generic; using Server.Items; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Seventh { - public class MassDispelSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mass Dispel", "Vas An Ort", - 263, - 9002, - Reagent.Garlic, - Reagent.MandrakeRoot, - Reagent.BlackPearl, - Reagent.SulfurousAsh - ); + public class MassDispelSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mass Dispel", "Vas An Ort", + 263, + 9002, + Reagent.Garlic, + Reagent.MandrakeRoot, + Reagent.BlackPearl, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Seventh; + public MassDispelSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MassDispelSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - List targets = new List(); + List targets = new List(); - Map map = Caster.Map; + Map map = Caster.Map; - if ( map != null ) - { - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), 8 ); + if (map != null) + { + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), 8); - foreach ( BaseCreature m in eable ) - if ( m.IsDispellable && Caster.CanBeHarmful( m, false ) ) - targets.Add( m ); + foreach (BaseCreature m in eable) + if (m.IsDispellable && Caster.CanBeHarmful(m, false)) + targets.Add(m); - eable.Free(); - } + eable.Free(); + } - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - BaseCreature bc = m as BaseCreature; + BaseCreature bc = m as BaseCreature; - if ( bc == null ) - continue; + if (bc == null) + continue; - double dispelChance = (50.0 + ((100 * (Caster.Skills.Magery.Value - bc.DispelDifficulty)) / (bc.DispelFocus*2))) / 100; + double dispelChance = + (50.0 + 100 * (Caster.Skills.Magery.Value - bc.DispelDifficulty) / (bc.DispelFocus * 2)) / 100; - if ( dispelChance > Utility.RandomDouble() ) - { - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x3728, 8, 20, 5042 ); - Effects.PlaySound( m, m.Map, 0x201 ); + if (dispelChance > Utility.RandomDouble()) + { + Effects.SendLocationParticles(EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), + 0x3728, 8, 20, 5042); + Effects.PlaySound(m, m.Map, 0x201); - m.Delete(); - } - else - { - Caster.DoHarmful( m ); + m.Delete(); + } + else + { + Caster.DoHarmful(m); - m.FixedEffect( 0x3779, 10, 20 ); - } - } - } + m.FixedEffect(0x3779, 10, 20); + } + } + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private MassDispelSpell m_Owner; + private class InternalTarget : Target + { + private MassDispelSpell m_Owner; - public InternalTarget( MassDispelSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(MassDispelSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/MeteorSwarm.cs b/Scripts/Spells/Seventh/MeteorSwarm.cs index be175cf28..8ded421b3 100644 --- a/Scripts/Spells/Seventh/MeteorSwarm.cs +++ b/Scripts/Spells/Seventh/MeteorSwarm.cs @@ -3,134 +3,133 @@ using Server.Targeting; namespace Server.Spells.Seventh { - public class MeteorSwarmSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Meteor Swarm", "Flam Kal Des Ylem", - 233, - 9042, - false, - Reagent.Bloodmoss, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh, - Reagent.SpidersSilk - ); + public class MeteorSwarmSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Meteor Swarm", "Flam Kal Des Ylem", + 233, + 9042, + false, + Reagent.Bloodmoss, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Seventh; + public MeteorSwarmSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MeteorSwarmSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Seventh; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => true; - public override bool DelayedDamage => true; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - if ( p is Item ) - p = ((Item)p).GetWorldLocation(); + if (p is Item) + p = ((Item)p).GetWorldLocation(); - List targets = new List(); + List targets = new List(); - Map map = Caster.Map; + Map map = Caster.Map; - bool playerVsPlayer = false; + bool playerVsPlayer = false; - if ( map != null ) - { - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), 2 ); + if (map != null) + { + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), 2); - foreach ( Mobile m in eable ) - { - if ( Caster != m && SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) ) - { - if ( Core.AOS && !Caster.InLOS( m ) ) - continue; + foreach (Mobile m in eable) + if (Caster != m && SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false)) + { + if (Core.AOS && !Caster.InLOS(m)) + continue; - targets.Add( m ); + targets.Add(m); - if ( m.Player ) - playerVsPlayer = true; - } - } + if (m.Player) + playerVsPlayer = true; + } - eable.Free(); - } + eable.Free(); + } - double damage; + double damage; - if ( Core.AOS ) - damage = GetNewAosDamage( 51, 1, 5, playerVsPlayer ); - else - damage = Utility.Random( 27, 22 ); + if (Core.AOS) + damage = GetNewAosDamage(51, 1, 5, playerVsPlayer); + else + damage = Utility.Random(27, 22); - if ( targets.Count > 0 ) - { - Effects.PlaySound( p, Caster.Map, 0x160 ); + if (targets.Count > 0) + { + Effects.PlaySound(p, Caster.Map, 0x160); - if ( Core.AOS && targets.Count > 2 ) - damage = (damage * 2) / targets.Count; - else if ( !Core.AOS ) - damage /= targets.Count; + if (Core.AOS && targets.Count > 2) + damage = damage * 2 / targets.Count; + else if (!Core.AOS) + damage /= targets.Count; - double toDeal; - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + double toDeal; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - toDeal = damage; + toDeal = damage; - if ( !Core.AOS && CheckResisted( m ) ) - { - damage *= 0.5; + if (!Core.AOS && CheckResisted(m)) + { + damage *= 0.5; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } - toDeal *= GetDamageScalar( m ); - Caster.DoHarmful( m ); - SpellHelper.Damage( this, m, toDeal, 0, 100, 0, 0, 0 ); + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - Caster.MovingParticles( m, 0x36D4, 7, 0, false, true, 9501, 1, 0, 0x100 ); - } - } - } + toDeal *= GetDamageScalar(m); + Caster.DoHarmful(m); + SpellHelper.Damage(this, m, toDeal, 0, 100, 0, 0, 0); - FinishSequence(); - } + Caster.MovingParticles(m, 0x36D4, 7, 0, false, true, 9501, 1, 0, 0x100); + } + } + } - private class InternalTarget : Target - { - private MeteorSwarmSpell m_Owner; + FinishSequence(); + } - public InternalTarget( MeteorSwarmSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + private class InternalTarget : Target + { + private MeteorSwarmSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + public InternalTarget(MeteorSwarmSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - if ( p != null ) - m_Owner.Target( p ); - } + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + if (p != null) + m_Owner.Target(p); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Seventh/Polymorph.cs b/Scripts/Spells/Seventh/Polymorph.cs index 0737539bb..b8254e745 100644 --- a/Scripts/Spells/Seventh/Polymorph.cs +++ b/Scripts/Spells/Seventh/Polymorph.cs @@ -1,215 +1,221 @@ using System; using System.Collections; -using Server.Items; +using Server.Factions; using Server.Gumps; +using Server.Items; +using Server.Mobiles; using Server.Spells.Fifth; namespace Server.Spells.Seventh { - public class PolymorphSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Polymorph", "Vas Ylem Rel", - 221, - 9002, - Reagent.Bloodmoss, - Reagent.SpidersSilk, - Reagent.MandrakeRoot - ); + public class PolymorphSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Polymorph", "Vas Ylem Rel", + 221, + 9002, + Reagent.Bloodmoss, + Reagent.SpidersSilk, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Seventh; + private static Hashtable m_Timers = new Hashtable(); - private int m_NewBody; + private int m_NewBody; - public PolymorphSpell( Mobile caster, Item scroll, int body ) : base( caster, scroll, m_Info ) - { - m_NewBody = body; - } + public PolymorphSpell(Mobile caster, Item scroll, int body) : base(caster, scroll, m_Info) + { + m_NewBody = body; + } - public PolymorphSpell( Mobile caster, Item scroll ) : this(caster,scroll,0) - { - } + public PolymorphSpell(Mobile caster, Item scroll) : this(caster, scroll, 0) + { + } - public override bool CheckCast() - { - /*if ( Caster.Mounted ) - { - Caster.SendLocalizedMessage( 1042561 ); //Please dismount first. - return false; - } - else */ - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1010521 ); // You cannot polymorph while you have a Town Sigil - return false; - } + public override SpellCircle Circle => SpellCircle.Seventh; - if ( TransformationSpellHelper.UnderTransformation( Caster ) ) - { - Caster.SendLocalizedMessage( 1061633 ); // You cannot polymorph while in that form. - return false; - } - if ( DisguiseTimers.IsDisguised( Caster ) ) - { - Caster.SendLocalizedMessage( 502167 ); // You cannot polymorph while disguised. - return false; - } - if ( Caster.BodyMod == 183 || Caster.BodyMod == 184 ) - { - Caster.SendLocalizedMessage( 1042512 ); // You cannot polymorph while wearing body paint - return false; - } - if ( !Caster.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - if ( Core.ML ) - EndPolymorph( Caster ); - else - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - return false; - } - if ( m_NewBody == 0 ) - { - Gump gump; - if ( Core.SE ) - gump = new NewPolymorphGump( Caster, Scroll ); - else - gump = new PolymorphGump( Caster, Scroll ); + public override bool CheckCast() + { + /*if ( Caster.Mounted ) + { + Caster.SendLocalizedMessage( 1042561 ); //Please dismount first. + return false; + } + else */ + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1010521); // You cannot polymorph while you have a Town Sigil + return false; + } - Caster.SendGump( gump ); - return false; - } + if (TransformationSpellHelper.UnderTransformation(Caster)) + { + Caster.SendLocalizedMessage(1061633); // You cannot polymorph while in that form. + return false; + } - return true; - } + if (DisguiseTimers.IsDisguised(Caster)) + { + Caster.SendLocalizedMessage(502167); // You cannot polymorph while disguised. + return false; + } - public override void OnCast() - { - /*if ( Caster.Mounted ) - { - Caster.SendLocalizedMessage( 1042561 ); //Please dismount first. - } - else */ - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1010521 ); // You cannot polymorph while you have a Town Sigil - } - else if ( !Caster.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - if ( Core.ML ) - EndPolymorph( Caster ); - else - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - else if ( TransformationSpellHelper.UnderTransformation( Caster ) ) - { - Caster.SendLocalizedMessage( 1061633 ); // You cannot polymorph while in that form. - } - else if ( DisguiseTimers.IsDisguised( Caster ) ) - { - Caster.SendLocalizedMessage( 502167 ); // You cannot polymorph while disguised. - } - else if ( Caster.BodyMod == 183 || Caster.BodyMod == 184 ) - { - Caster.SendLocalizedMessage( 1042512 ); // You cannot polymorph while wearing body paint - } - else if ( !Caster.CanBeginAction( typeof( IncognitoSpell ) ) || Caster.IsBodyMod ) - { - DoFizzle(); - } - else if ( CheckSequence() ) - { - if ( Caster.BeginAction( typeof( PolymorphSpell ) ) ) - { - if ( m_NewBody != 0 ) - { - if ( !((Body)m_NewBody).IsHuman ) - { - Mobiles.IMount mt = Caster.Mount; + if (Caster.BodyMod == 183 || Caster.BodyMod == 184) + { + Caster.SendLocalizedMessage(1042512); // You cannot polymorph while wearing body paint + return false; + } - if ( mt != null ) - mt.Rider = null; - } + if (!Caster.CanBeginAction(typeof(PolymorphSpell))) + { + if (Core.ML) + EndPolymorph(Caster); + else + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + return false; + } - Caster.BodyMod = m_NewBody; + if (m_NewBody == 0) + { + Gump gump; + if (Core.SE) + gump = new NewPolymorphGump(Caster, Scroll); + else + gump = new PolymorphGump(Caster, Scroll); - if ( m_NewBody == 400 || m_NewBody == 401 ) - Caster.HueMod = Utility.RandomSkinHue(); - else - Caster.HueMod = 0; + Caster.SendGump(gump); + return false; + } - BaseArmor.ValidateMobile( Caster ); - BaseClothing.ValidateMobile( Caster ); + return true; + } - if ( !Core.ML ) - { - StopTimer( Caster ); + public override void OnCast() + { + /*if ( Caster.Mounted ) + { + Caster.SendLocalizedMessage( 1042561 ); //Please dismount first. + } + else */ + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1010521); // You cannot polymorph while you have a Town Sigil + } + else if (!Caster.CanBeginAction(typeof(PolymorphSpell))) + { + if (Core.ML) + EndPolymorph(Caster); + else + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + else if (TransformationSpellHelper.UnderTransformation(Caster)) + { + Caster.SendLocalizedMessage(1061633); // You cannot polymorph while in that form. + } + else if (DisguiseTimers.IsDisguised(Caster)) + { + Caster.SendLocalizedMessage(502167); // You cannot polymorph while disguised. + } + else if (Caster.BodyMod == 183 || Caster.BodyMod == 184) + { + Caster.SendLocalizedMessage(1042512); // You cannot polymorph while wearing body paint + } + else if (!Caster.CanBeginAction(typeof(IncognitoSpell)) || Caster.IsBodyMod) + { + DoFizzle(); + } + else if (CheckSequence()) + { + if (Caster.BeginAction(typeof(PolymorphSpell))) + { + if (m_NewBody != 0) + { + if (!((Body)m_NewBody).IsHuman) + { + IMount mt = Caster.Mount; - Timer t = new InternalTimer( Caster ); + if (mt != null) + mt.Rider = null; + } - m_Timers[Caster] = t; + Caster.BodyMod = m_NewBody; - t.Start(); - } - } - } - else - { - Caster.SendLocalizedMessage( 1005559 ); // This spell is already in effect. - } - } + if (m_NewBody == 400 || m_NewBody == 401) + Caster.HueMod = Utility.RandomSkinHue(); + else + Caster.HueMod = 0; - FinishSequence(); - } + BaseArmor.ValidateMobile(Caster); + BaseClothing.ValidateMobile(Caster); - private static Hashtable m_Timers = new Hashtable(); + if (!Core.ML) + { + StopTimer(Caster); - public static bool StopTimer( Mobile m ) - { - Timer t = (Timer)m_Timers[m]; + Timer t = new InternalTimer(Caster); - if ( t != null ) - { - t.Stop(); - m_Timers.Remove( m ); - } + m_Timers[Caster] = t; - return ( t != null ); - } + t.Start(); + } + } + } + else + { + Caster.SendLocalizedMessage(1005559); // This spell is already in effect. + } + } - private static void EndPolymorph( Mobile m ) - { - if ( !m.CanBeginAction( typeof( PolymorphSpell ) ) ) - { - m.BodyMod = 0; - m.HueMod = -1; - m.EndAction( typeof( PolymorphSpell ) ); + FinishSequence(); + } - BaseArmor.ValidateMobile( m ); - BaseClothing.ValidateMobile( m ); - } - } + public static bool StopTimer(Mobile m) + { + Timer t = (Timer)m_Timers[m]; - private class InternalTimer : Timer - { - private Mobile m_Owner; + if (t != null) + { + t.Stop(); + m_Timers.Remove(m); + } - public InternalTimer( Mobile owner ) : base( TimeSpan.FromSeconds( 0 ) ) - { - m_Owner = owner; + return t != null; + } - int val = (int)owner.Skills[SkillName.Magery].Value; + private static void EndPolymorph(Mobile m) + { + if (!m.CanBeginAction(typeof(PolymorphSpell))) + { + m.BodyMod = 0; + m.HueMod = -1; + m.EndAction(typeof(PolymorphSpell)); - if ( val > 120 ) - val = 120; + BaseArmor.ValidateMobile(m); + BaseClothing.ValidateMobile(m); + } + } - Delay = TimeSpan.FromSeconds( val ); - Priority = TimerPriority.OneSecond; - } + private class InternalTimer : Timer + { + private Mobile m_Owner; - protected override void OnTick() - { - EndPolymorph( m_Owner ); - } - } - } -} + public InternalTimer(Mobile owner) : base(TimeSpan.FromSeconds(0)) + { + m_Owner = owner; + + int val = (int)owner.Skills[SkillName.Magery].Value; + + if (val > 120) + val = 120; + + Delay = TimeSpan.FromSeconds(val); + Priority = TimerPriority.OneSecond; + } + + protected override void OnTick() + { + EndPolymorph(m_Owner); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/Dispel.cs b/Scripts/Spells/Sixth/Dispel.cs index 558093834..bcb39619a 100644 --- a/Scripts/Spells/Sixth/Dispel.cs +++ b/Scripts/Spells/Sixth/Dispel.cs @@ -1,81 +1,83 @@ using Server.Items; -using Server.Targeting; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Sixth { - public class DispelSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Dispel", "An Ort", - 218, - 9002, - Reagent.Garlic, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class DispelSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Dispel", "An Ort", + 218, + 9002, + Reagent.Garlic, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public DispelSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public DispelSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public class InternalTarget : Target - { - private DispelSpell m_Owner; + public class InternalTarget : Target + { + private DispelSpell m_Owner; - public InternalTarget( DispelSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(DispelSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - Mobile m = (Mobile)o; - BaseCreature bc = m as BaseCreature; + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + { + Mobile m = (Mobile)o; + BaseCreature bc = m as BaseCreature; - if ( !from.CanSee( m ) ) - { - from.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( bc == null || !bc.IsDispellable ) - { - from.SendLocalizedMessage( 1005049 ); // That cannot be dispelled. - } - else if ( m_Owner.CheckHSequence( m ) ) - { - SpellHelper.Turn( from, m ); + if (!from.CanSee(m)) + { + from.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (bc == null || !bc.IsDispellable) + { + from.SendLocalizedMessage(1005049); // That cannot be dispelled. + } + else if (m_Owner.CheckHSequence(m)) + { + SpellHelper.Turn(from, m); - double dispelChance = (50.0 + ((100 * (from.Skills.Magery.Value - bc.DispelDifficulty)) / (bc.DispelFocus*2))) / 100; + double dispelChance = + (50.0 + 100 * (from.Skills.Magery.Value - bc.DispelDifficulty) / (bc.DispelFocus * 2)) / 100; - if ( dispelChance > Utility.RandomDouble() ) - { - Effects.SendLocationParticles( EffectItem.Create( m.Location, m.Map, EffectItem.DefaultDuration ), 0x3728, 8, 20, 5042 ); - Effects.PlaySound( m, m.Map, 0x201 ); + if (dispelChance > Utility.RandomDouble()) + { + Effects.SendLocationParticles(EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), + 0x3728, 8, 20, 5042); + Effects.PlaySound(m, m.Map, 0x201); - m.Delete(); - } - else - { - m.FixedEffect( 0x3779, 10, 20 ); - from.SendLocalizedMessage( 1010084 ); // The creature resisted the attempt to dispel it! - } - } - } - } + m.Delete(); + } + else + { + m.FixedEffect(0x3779, 10, 20); + from.SendLocalizedMessage(1010084); // The creature resisted the attempt to dispel it! + } + } + } + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/EnergyBolt.cs b/Scripts/Spells/Sixth/EnergyBolt.cs index 2bffc94b1..b95b5a3d3 100644 --- a/Scripts/Spells/Sixth/EnergyBolt.cs +++ b/Scripts/Spells/Sixth/EnergyBolt.cs @@ -2,94 +2,94 @@ using Server.Targeting; namespace Server.Spells.Sixth { - public class EnergyBoltSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Energy Bolt", "Corp Por", - 230, - 9022, - Reagent.BlackPearl, - Reagent.Nightshade - ); + public class EnergyBoltSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Energy Bolt", "Corp Por", + 230, + 9022, + Reagent.BlackPearl, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public EnergyBoltSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EnergyBoltSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => true; - public override bool DelayedDamage => true; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - Mobile source = Caster; + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + Mobile source = Caster; - SpellHelper.Turn( Caster, m ); + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, ref source, ref m ); + SpellHelper.CheckReflect((int)Circle, ref source, ref m); - double damage; + double damage; - if ( Core.AOS ) - { - damage = GetNewAosDamage( 40, 1, 5, m ); - } - else - { - damage = Utility.Random( 24, 18 ); + if (Core.AOS) + { + damage = GetNewAosDamage(40, 1, 5, m); + } + else + { + damage = Utility.Random(24, 18); - if ( CheckResisted( m ) ) - { - damage *= 0.75; + if (CheckResisted(m)) + { + damage *= 0.75; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - // Scale damage based on evalint and resist - damage *= GetDamageScalar( m ); - } + // Scale damage based on evalint and resist + damage *= GetDamageScalar(m); + } - // Do the effects - source.MovingParticles( m, 0x379F, 7, 0, false, true, 3043, 4043, 0x211 ); - source.PlaySound( 0x20A ); + // Do the effects + source.MovingParticles(m, 0x379F, 7, 0, false, true, 3043, 4043, 0x211); + source.PlaySound(0x20A); - // Deal the damage - SpellHelper.Damage( this, m, damage, 0, 0, 0, 0, 100 ); - } + // Deal the damage + SpellHelper.Damage(this, m, damage, 0, 0, 0, 0, 100); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private EnergyBoltSpell m_Owner; + private class InternalTarget : Target + { + private EnergyBoltSpell m_Owner; - public InternalTarget( EnergyBoltSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(EnergyBoltSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/Explosion.cs b/Scripts/Spells/Sixth/Explosion.cs index 1f35fa7f6..b667bf028 100644 --- a/Scripts/Spells/Sixth/Explosion.cs +++ b/Scripts/Spells/Sixth/Explosion.cs @@ -3,126 +3,126 @@ using Server.Targeting; namespace Server.Spells.Sixth { - public class ExplosionSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Explosion", "Vas Ort Flam", - 230, - 9041, - Reagent.Bloodmoss, - Reagent.MandrakeRoot - ); + public class ExplosionSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Explosion", "Vas Ort Flam", + 230, + 9041, + Reagent.Bloodmoss, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public ExplosionSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public ExplosionSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override bool DelayedDamageStacking => !Core.AOS; + public override bool DelayedDamageStacking => !Core.AOS; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => false; - public override bool DelayedDamage => false; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( Caster.CanBeHarmful( m ) && CheckSequence() ) - { - Mobile attacker = Caster, defender = m; + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (Caster.CanBeHarmful(m) && CheckSequence()) + { + Mobile attacker = Caster, defender = m; - SpellHelper.Turn( Caster, m ); + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int) Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - InternalTimer t = new InternalTimer( this, attacker, defender, m ); - t.Start(); - } + InternalTimer t = new InternalTimer(this, attacker, defender, m); + t.Start(); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTimer : Timer - { - private MagerySpell m_Spell; - private Mobile m_Target; - private Mobile m_Attacker, m_Defender; + private class InternalTimer : Timer + { + private Mobile m_Attacker, m_Defender; + private MagerySpell m_Spell; + private Mobile m_Target; - public InternalTimer( MagerySpell spell, Mobile attacker, Mobile defender, Mobile target ) - : base( TimeSpan.FromSeconds( Core.AOS ? 3.0 : 2.5 ) ) - { - m_Spell = spell; - m_Attacker = attacker; - m_Defender = defender; - m_Target = target; + public InternalTimer(MagerySpell spell, Mobile attacker, Mobile defender, Mobile target) + : base(TimeSpan.FromSeconds(Core.AOS ? 3.0 : 2.5)) + { + m_Spell = spell; + m_Attacker = attacker; + m_Defender = defender; + m_Target = target; - m_Spell?.StartDelayedDamageContext( attacker, this ); + m_Spell?.StartDelayedDamageContext(attacker, this); - Priority = TimerPriority.FiftyMS; - } + Priority = TimerPriority.FiftyMS; + } - protected override void OnTick() - { - if ( m_Attacker.HarmfulCheck( m_Defender ) ) - { - double damage; + protected override void OnTick() + { + if (m_Attacker.HarmfulCheck(m_Defender)) + { + double damage; - if ( Core.AOS ) - { - damage = m_Spell.GetNewAosDamage( 40, 1, 5, m_Defender ); - } - else - { - damage = Utility.Random( 23, 22 ); + if (Core.AOS) + { + damage = m_Spell.GetNewAosDamage(40, 1, 5, m_Defender); + } + else + { + damage = Utility.Random(23, 22); - if ( m_Spell.CheckResisted( m_Target ) ) - { - damage *= 0.75; + if (m_Spell.CheckResisted(m_Target)) + { + damage *= 0.75; - m_Target.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m_Target.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - damage *= m_Spell.GetDamageScalar( m_Target ); - } + damage *= m_Spell.GetDamageScalar(m_Target); + } - m_Target.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); - m_Target.PlaySound( 0x307 ); + m_Target.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); + m_Target.PlaySound(0x307); - SpellHelper.Damage( m_Spell, m_Target, damage, 0, 100, 0, 0, 0 ); + SpellHelper.Damage(m_Spell, m_Target, damage, 0, 100, 0, 0, 0); - m_Spell?.RemoveDelayedDamageContext( m_Attacker ); - } - } - } + m_Spell?.RemoveDelayedDamageContext(m_Attacker); + } + } + } - private class InternalTarget : Target - { - private ExplosionSpell m_Owner; + private class InternalTarget : Target + { + private ExplosionSpell m_Owner; - public InternalTarget( ExplosionSpell owner ) - : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(ExplosionSpell owner) + : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile) o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/Invisibility.cs b/Scripts/Spells/Sixth/Invisibility.cs index 0d8944b35..9f88a2c38 100644 --- a/Scripts/Spells/Sixth/Invisibility.cs +++ b/Scripts/Spells/Sixth/Invisibility.cs @@ -1,136 +1,137 @@ using System; using System.Collections.Generic; -using Server.Targeting; +using Server.Engines.ConPVP; using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Sixth { - public class InvisibilitySpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Invisibility", "An Lor Xen", - 206, - 9002, - Reagent.Bloodmoss, - Reagent.Nightshade - ); + public class InvisibilitySpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Invisibility", "An Lor Xen", + 206, + 9002, + Reagent.Bloodmoss, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Sixth; + private static Dictionary m_Table = new Dictionary(); - public InvisibilitySpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public InvisibilitySpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override SpellCircle Circle => SpellCircle.Sixth; - return base.CheckCast(); - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + return base.CheckCast(); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( m is Mobiles.BaseVendor || m is Mobiles.PlayerVendor || m is Mobiles.PlayerBarkeeper || m.AccessLevel > Caster.AccessLevel ) - { - Caster.SendLocalizedMessage( 501857 ); // This spell won't work on that! - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - Effects.SendLocationParticles( EffectItem.Create( new Point3D( m.X, m.Y, m.Z + 16 ), Caster.Map, EffectItem.DefaultDuration ), 0x376A, 10, 15, 5045 ); - m.PlaySound( 0x3C4 ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (m is BaseVendor || m is PlayerVendor || m is PlayerBarkeeper || m.AccessLevel > Caster.AccessLevel) + { + Caster.SendLocalizedMessage(501857); // This spell won't work on that! + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - m.Hidden = true; - m.Combatant = null; - m.Warmode = false; + Effects.SendLocationParticles( + EffectItem.Create(new Point3D(m.X, m.Y, m.Z + 16), Caster.Map, EffectItem.DefaultDuration), 0x376A, 10, + 15, 5045); + m.PlaySound(0x3C4); - RemoveTimer( m ); + m.Hidden = true; + m.Combatant = null; + m.Warmode = false; - TimeSpan duration = TimeSpan.FromSeconds( (( 1.2 * Caster.Skills.Magery.Fixed) / 10 )); + RemoveTimer(m); - Timer t = new InternalTimer( m, duration ); + TimeSpan duration = TimeSpan.FromSeconds(1.2 * Caster.Skills.Magery.Fixed / 10); - BuffInfo.RemoveBuff( m, BuffIcon.HidingAndOrStealth ); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Invisibility, 1075825, duration, m ) ); //Invisibility/Invisible + Timer t = new InternalTimer(m, duration); - m_Table[m] = t; + BuffInfo.RemoveBuff(m, BuffIcon.HidingAndOrStealth); + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Invisibility, 1075825, duration, m)); //Invisibility/Invisible - t.Start(); - } + m_Table[m] = t; - FinishSequence(); - } + t.Start(); + } - private static Dictionary m_Table = new Dictionary(); + FinishSequence(); + } - public static bool HasTimer( Mobile m ) - { - return m_Table.ContainsKey(m); - } + public static bool HasTimer(Mobile m) + { + return m_Table.ContainsKey(m); + } - public static void RemoveTimer( Mobile m ) - { - m_Table.TryGetValue( m, out Timer t ); + public static void RemoveTimer(Mobile m) + { + m_Table.TryGetValue(m, out Timer t); - if ( t != null ) - { - t.Stop(); - m_Table.Remove( m ); - } - } + if (t != null) + { + t.Stop(); + m_Table.Remove(m); + } + } - private class InternalTimer : Timer - { - private Mobile m_Mobile; + private class InternalTimer : Timer + { + private Mobile m_Mobile; - public InternalTimer( Mobile m, TimeSpan duration ) : base( duration ) - { - Priority = TimerPriority.OneSecond; - m_Mobile = m; - } + public InternalTimer(Mobile m, TimeSpan duration) : base(duration) + { + Priority = TimerPriority.OneSecond; + m_Mobile = m; + } - protected override void OnTick() - { - m_Mobile.RevealingAction(); - RemoveTimer( m_Mobile ); - } - } + protected override void OnTick() + { + m_Mobile.RevealingAction(); + RemoveTimer(m_Mobile); + } + } - public class InternalTarget : Target - { - private InvisibilitySpell m_Owner; + public class InternalTarget : Target + { + private InvisibilitySpell m_Owner; - public InternalTarget( InvisibilitySpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(InvisibilitySpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/Mark.cs b/Scripts/Spells/Sixth/Mark.cs index 85a900cfd..bd053ad10 100644 --- a/Scripts/Spells/Sixth/Mark.cs +++ b/Scripts/Spells/Sixth/Mark.cs @@ -1,92 +1,90 @@ using Server.Items; -using Server.Targeting; using Server.Network; +using Server.Targeting; namespace Server.Spells.Sixth { - public class MarkSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mark", "Kal Por Ylem", - 218, - 9002, - Reagent.BlackPearl, - Reagent.Bloodmoss, - Reagent.MandrakeRoot - ); + public class MarkSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mark", "Kal Por Ylem", + 218, + 9002, + Reagent.BlackPearl, + Reagent.Bloodmoss, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public MarkSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MarkSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - return SpellHelper.CheckTravel( Caster, TravelCheckType.Mark ); - } + return SpellHelper.CheckTravel(Caster, TravelCheckType.Mark); + } - public void Target( RecallRune rune ) - { - if ( !Caster.CanSee( rune ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( !SpellHelper.CheckTravel( Caster, TravelCheckType.Mark ) ) - { - } - else if ( SpellHelper.CheckMulti( Caster.Location, Caster.Map, !Core.AOS ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( !rune.IsChildOf( Caster.Backpack ) ) - { - Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1062422 ); // You must have this rune in your backpack in order to mark it. - } - else if ( CheckSequence() ) - { - rune.Mark( Caster ); + public void Target(RecallRune rune) + { + if (!Caster.CanSee(rune)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (!SpellHelper.CheckTravel(Caster, TravelCheckType.Mark)) + { + } + else if (SpellHelper.CheckMulti(Caster.Location, Caster.Map, !Core.AOS)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (!rune.IsChildOf(Caster.Backpack)) + { + Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 1062422); // You must have this rune in your backpack in order to mark it. + } + else if (CheckSequence()) + { + rune.Mark(Caster); - Caster.PlaySound( 0x1FA ); - Effects.SendLocationEffect( Caster, Caster.Map, 14201, 16 ); - } + Caster.PlaySound(0x1FA); + Effects.SendLocationEffect(Caster, Caster.Map, 14201, 16); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private MarkSpell m_Owner; + private class InternalTarget : Target + { + private MarkSpell m_Owner; - public InternalTarget( MarkSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(MarkSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is RecallRune ) - { - m_Owner.Target( (RecallRune) o ); - } - else - { - from.Send( new MessageLocalized( from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 501797, from.Name, "" ) ); // I cannot mark that object. - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is RecallRune) + m_Owner.Target((RecallRune)o); + else + from.Send(new MessageLocalized(from.Serial, from.Body, MessageType.Regular, 0x3B2, 3, 501797, from.Name, + "")); // I cannot mark that object. + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/MassCurse.cs b/Scripts/Spells/Sixth/MassCurse.cs index 0f2b5d9eb..60042e493 100644 --- a/Scripts/Spells/Sixth/MassCurse.cs +++ b/Scripts/Spells/Sixth/MassCurse.cs @@ -3,103 +3,105 @@ using Server.Targeting; namespace Server.Spells.Sixth { - public class MassCurseSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Mass Curse", "Vas Des Sanct", - 218, - 9031, - false, - Reagent.Garlic, - Reagent.Nightshade, - Reagent.MandrakeRoot, - Reagent.SulfurousAsh - ); + public class MassCurseSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Mass Curse", "Vas Des Sanct", + 218, + 9031, + false, + Reagent.Garlic, + Reagent.Nightshade, + Reagent.MandrakeRoot, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public MassCurseSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MassCurseSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - List targets = new List(); + List targets = new List(); - Map map = Caster.Map; + Map map = Caster.Map; - if ( map != null ) - { - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), 2 ); + if (map != null) + { + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), 2); - foreach ( Mobile m in eable ) - { - if ( Core.AOS && m == Caster ) - continue; + foreach (Mobile m in eable) + { + if (Core.AOS && m == Caster) + continue; - if ( SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanSee( m ) && Caster.CanBeHarmful( m, false ) ) - targets.Add( m ); - } + if (SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanSee(m) && Caster.CanBeHarmful(m, false)) + targets.Add(m); + } - eable.Free(); - } + eable.Free(); + } - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - Caster.DoHarmful( m ); + Caster.DoHarmful(m); - SpellHelper.AddStatCurse( Caster, m, StatType.Str ); SpellHelper.DisableSkillCheck = true; - SpellHelper.AddStatCurse( Caster, m, StatType.Dex ); - SpellHelper.AddStatCurse( Caster, m, StatType.Int ); SpellHelper.DisableSkillCheck = false; + SpellHelper.AddStatCurse(Caster, m, StatType.Str); + SpellHelper.DisableSkillCheck = true; + SpellHelper.AddStatCurse(Caster, m, StatType.Dex); + SpellHelper.AddStatCurse(Caster, m, StatType.Int); + SpellHelper.DisableSkillCheck = false; - m.FixedParticles( 0x374A, 10, 15, 5028, EffectLayer.Waist ); - m.PlaySound( 0x1FB ); + m.FixedParticles(0x374A, 10, 15, 5028, EffectLayer.Waist); + m.PlaySound(0x1FB); - HarmfulSpell( m ); - } - } + HarmfulSpell(m); + } + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private MassCurseSpell m_Owner; + private class InternalTarget : Target + { + private MassCurseSpell m_Owner; - public InternalTarget( MassCurseSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(MassCurseSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/ParalyzeField.cs b/Scripts/Spells/Sixth/ParalyzeField.cs index 6da3cadbf..8bab3ba6a 100644 --- a/Scripts/Spells/Sixth/ParalyzeField.cs +++ b/Scripts/Spells/Sixth/ParalyzeField.cs @@ -1,234 +1,237 @@ using System; -using Server.Targeting; using Server.Items; using Server.Misc; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Sixth { - public class ParalyzeFieldSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Paralyze Field", "In Ex Grav", - 230, - 9012, - false, - Reagent.BlackPearl, - Reagent.Ginseng, - Reagent.SpidersSilk - ); + public class ParalyzeFieldSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Paralyze Field", "In Ex Grav", + 230, + 9012, + false, + Reagent.BlackPearl, + Reagent.Ginseng, + Reagent.SpidersSilk + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public ParalyzeFieldSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public ParalyzeFieldSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - int dx = Caster.Location.X - p.X; - int dy = Caster.Location.Y - p.Y; - int rx = (dx - dy) * 44; - int ry = (dx + dy) * 44; + int dx = Caster.Location.X - p.X; + int dy = Caster.Location.Y - p.Y; + int rx = (dx - dy) * 44; + int ry = (dx + dy) * 44; - bool eastToWest; + bool eastToWest; - if ( rx >= 0 && ry >= 0 ) - eastToWest = false; - else if ( rx >= 0 ) - eastToWest = true; - else if ( ry >= 0 ) - eastToWest = true; - else - eastToWest = false; + if (rx >= 0 && ry >= 0) + eastToWest = false; + else if (rx >= 0) + eastToWest = true; + else if (ry >= 0) + eastToWest = true; + else + eastToWest = false; - Effects.PlaySound( p, Caster.Map, 0x20B ); + Effects.PlaySound(p, Caster.Map, 0x20B); - int itemID = eastToWest ? 0x3967 : 0x3979; + int itemID = eastToWest ? 0x3967 : 0x3979; - TimeSpan duration = TimeSpan.FromSeconds( 3.0 + (Caster.Skills[SkillName.Magery].Value / 3.0) ); + TimeSpan duration = TimeSpan.FromSeconds(3.0 + Caster.Skills[SkillName.Magery].Value / 3.0); - for ( int i = -2; i <= 2; ++i ) - { - Point3D loc = new Point3D( eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z ); - bool canFit = SpellHelper.AdjustField( ref loc, Caster.Map, 12, false ); + for (int i = -2; i <= 2; ++i) + { + Point3D loc = new Point3D(eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z); + bool canFit = SpellHelper.AdjustField(ref loc, Caster.Map, 12, false); - if ( !canFit ) - continue; + if (!canFit) + continue; - Item item = new InternalItem( Caster, itemID, loc, Caster.Map, duration ); - item.ProcessDelta(); + Item item = new InternalItem(Caster, itemID, loc, Caster.Map, duration); + item.ProcessDelta(); - Effects.SendLocationParticles( EffectItem.Create( loc, Caster.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 5048 ); - } - } + Effects.SendLocationParticles(EffectItem.Create(loc, Caster.Map, EffectItem.DefaultDuration), 0x376A, 9, + 10, 5048); + } + } - FinishSequence(); - } + FinishSequence(); + } - [DispellableField] - public class InternalItem : Item - { - private Timer m_Timer; - private Mobile m_Caster; - private DateTime m_End; + [DispellableField] + public class InternalItem : Item + { + private Mobile m_Caster; + private DateTime m_End; + private Timer m_Timer; - public override bool BlocksFit => true; + public InternalItem(Mobile caster, int itemID, Point3D loc, Map map, TimeSpan duration) : base(itemID) + { + Visible = false; + Movable = false; + Light = LightType.Circle300; - public InternalItem( Mobile caster, int itemID, Point3D loc, Map map, TimeSpan duration ) : base( itemID ) - { - Visible = false; - Movable = false; - Light = LightType.Circle300; + MoveToWorld(loc, map); - MoveToWorld( loc, map ); + if (caster.InLOS(this)) + Visible = true; + else + Delete(); - if ( caster.InLOS( this ) ) - Visible = true; - else - Delete(); + if (Deleted) + return; - if ( Deleted ) - return; + m_Caster = caster; - m_Caster = caster; + m_Timer = new InternalTimer(this, duration); + m_Timer.Start(); - m_Timer = new InternalTimer( this, duration ); - m_Timer.Start(); + m_End = DateTime.UtcNow + duration; + } - m_End = DateTime.UtcNow + duration; - } + public InternalItem(Serial serial) : base(serial) + { + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + public override bool BlocksFit => true; - m_Timer?.Stop(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - public InternalItem( Serial serial ) : base( serial ) - { - } + m_Timer?.Stop(); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version + writer.Write(0); // version - writer.Write( m_Caster ); - writer.WriteDeltaTime( m_End ); - } + writer.Write(m_Caster); + writer.WriteDeltaTime(m_End); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 0: - { - m_Caster = reader.ReadMobile(); - m_End = reader.ReadDeltaTime(); + switch (version) + { + case 0: + { + m_Caster = reader.ReadMobile(); + m_End = reader.ReadDeltaTime(); - m_Timer = new InternalTimer( this, m_End - DateTime.UtcNow ); - m_Timer.Start(); + m_Timer = new InternalTimer(this, m_End - DateTime.UtcNow); + m_Timer.Start(); - break; - } - } - } + break; + } + } + } - public override bool OnMoveOver( Mobile m ) - { - if ( Visible && m_Caster != null && (!Core.AOS || m != m_Caster) && SpellHelper.ValidIndirectTarget( m_Caster, m ) && m_Caster.CanBeHarmful( m, false ) ) - { - if ( SpellHelper.CanRevealCaster( m ) ) - m_Caster.RevealingAction(); + public override bool OnMoveOver(Mobile m) + { + if (Visible && m_Caster != null && (!Core.AOS || m != m_Caster) && + SpellHelper.ValidIndirectTarget(m_Caster, m) && m_Caster.CanBeHarmful(m, false)) + { + if (SpellHelper.CanRevealCaster(m)) + m_Caster.RevealingAction(); - m_Caster.DoHarmful( m ); + m_Caster.DoHarmful(m); - double duration; + double duration; - if ( Core.AOS ) - { - duration = 2.0 + ((int)(m_Caster.Skills[SkillName.EvalInt].Value / 10) - (int)(m.Skills[SkillName.MagicResist].Value / 10)); + if (Core.AOS) + { + duration = 2.0 + ((int)(m_Caster.Skills[SkillName.EvalInt].Value / 10) - + (int)(m.Skills[SkillName.MagicResist].Value / 10)); - if ( !m.Player ) - duration *= 3.0; + if (!m.Player) + duration *= 3.0; - if ( duration < 0.0 ) - duration = 0.0; - } - else - { - duration = 7.0 + (m_Caster.Skills[SkillName.Magery].Value * 0.2); - } + if (duration < 0.0) + duration = 0.0; + } + else + { + duration = 7.0 + m_Caster.Skills[SkillName.Magery].Value * 0.2; + } - m.Paralyze( TimeSpan.FromSeconds( duration ) ); + m.Paralyze(TimeSpan.FromSeconds(duration)); - m.PlaySound( 0x204 ); - m.FixedEffect( 0x376A, 10, 16 ); + m.PlaySound(0x204); + m.FixedEffect(0x376A, 10, 16); - (m as BaseCreature)?.OnHarmfulSpell( m_Caster ); - } + (m as BaseCreature)?.OnHarmfulSpell(m_Caster); + } - return true; - } + return true; + } - private class InternalTimer : Timer - { - private Item m_Item; + private class InternalTimer : Timer + { + private Item m_Item; - public InternalTimer( Item item, TimeSpan duration ) : base( duration ) - { - Priority = TimerPriority.OneSecond; - m_Item = item; - } + public InternalTimer(Item item, TimeSpan duration) : base(duration) + { + Priority = TimerPriority.OneSecond; + m_Item = item; + } - protected override void OnTick() - { - m_Item.Delete(); - } - } - } + protected override void OnTick() + { + m_Item.Delete(); + } + } + } - private class InternalTarget : Target - { - private ParalyzeFieldSpell m_Owner; + private class InternalTarget : Target + { + private ParalyzeFieldSpell m_Owner; - public InternalTarget( ParalyzeFieldSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(ParalyzeFieldSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Sixth/Reveal.cs b/Scripts/Spells/Sixth/Reveal.cs index 85a0a4523..4b4faa593 100644 --- a/Scripts/Spells/Sixth/Reveal.cs +++ b/Scripts/Spells/Sixth/Reveal.cs @@ -1,119 +1,122 @@ using System.Collections.Generic; +using Server.Mobiles; using Server.Targeting; namespace Server.Spells.Sixth { - public class RevealSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Reveal", "Wis Quas", - 206, - 9002, - Reagent.Bloodmoss, - Reagent.SulfurousAsh - ); + public class RevealSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Reveal", "Wis Quas", + 206, + 9002, + Reagent.Bloodmoss, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Sixth; + public RevealSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public RevealSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Sixth; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - List targets = new List(); + List targets = new List(); - Map map = Caster.Map; + Map map = Caster.Map; - if ( map != null ) - { - IPooledEnumerable eable = map.GetMobilesInRange( new Point3D( p ), 1 + (int)(Caster.Skills[SkillName.Magery].Value / 20.0) ); + if (map != null) + { + IPooledEnumerable eable = map.GetMobilesInRange(new Point3D(p), + 1 + (int)(Caster.Skills[SkillName.Magery].Value / 20.0)); - foreach ( Mobile m in eable ) - { - if ( m is Mobiles.ShadowKnight && (m.X != p.X || m.Y != p.Y) ) - continue; + foreach (Mobile m in eable) + { + if (m is ShadowKnight && (m.X != p.X || m.Y != p.Y)) + continue; - if ( m.Hidden && (m.AccessLevel == AccessLevel.Player || Caster.AccessLevel > m.AccessLevel) && CheckDifficulty( Caster, m ) ) - targets.Add( m ); - } + if (m.Hidden && (m.AccessLevel == AccessLevel.Player || Caster.AccessLevel > m.AccessLevel) && + CheckDifficulty(Caster, m)) + targets.Add(m); + } - eable.Free(); - } + eable.Free(); + } - for ( int i = 0; i < targets.Count; ++i ) - { - Mobile m = targets[i]; + for (int i = 0; i < targets.Count; ++i) + { + Mobile m = targets[i]; - m.RevealingAction(); + m.RevealingAction(); - m.FixedParticles( 0x375A, 9, 20, 5049, EffectLayer.Head ); - m.PlaySound( 0x1FD ); - } - } + m.FixedParticles(0x375A, 9, 20, 5049, EffectLayer.Head); + m.PlaySound(0x1FD); + } + } - FinishSequence(); - } + FinishSequence(); + } - // Reveal uses magery and detect hidden vs. hide and stealth - private static bool CheckDifficulty( Mobile from, Mobile m ) - { - // Reveal always reveals vs. invisibility spell - if ( !Core.AOS || InvisibilitySpell.HasTimer( m ) ) - return true; + // Reveal uses magery and detect hidden vs. hide and stealth + private static bool CheckDifficulty(Mobile from, Mobile m) + { + // Reveal always reveals vs. invisibility spell + if (!Core.AOS || InvisibilitySpell.HasTimer(m)) + return true; - int magery = from.Skills[SkillName.Magery].Fixed; - int detectHidden = from.Skills[SkillName.DetectHidden].Fixed; + int magery = from.Skills[SkillName.Magery].Fixed; + int detectHidden = from.Skills[SkillName.DetectHidden].Fixed; - int hiding = m.Skills[SkillName.Hiding].Fixed; - int stealth = m.Skills[SkillName.Stealth].Fixed; - int divisor = hiding + stealth; + int hiding = m.Skills[SkillName.Hiding].Fixed; + int stealth = m.Skills[SkillName.Stealth].Fixed; + int divisor = hiding + stealth; - int chance; - if ( divisor > 0 ) - chance = 50 * (magery + detectHidden) / divisor; - else - chance = 100; + int chance; + if (divisor > 0) + chance = 50 * (magery + detectHidden) / divisor; + else + chance = 100; - return chance > Utility.Random( 100 ); - } + return chance > Utility.Random(100); + } - public class InternalTarget : Target - { - private RevealSpell m_Owner; + public class InternalTarget : Target + { + private RevealSpell m_Owner; - public InternalTarget( RevealSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(RevealSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/ArcaneCircle.cs b/Scripts/Spells/Spellweaving/ArcaneCircle.cs index 5c7ee7b3b..5837f47e7 100644 --- a/Scripts/Spells/Spellweaving/ArcaneCircle.cs +++ b/Scripts/Spells/Spellweaving/ArcaneCircle.cs @@ -5,161 +5,164 @@ using Server.Mobiles; namespace Server.Spells.Spellweaving { - public class ArcaneCircleSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Arcane Circle", "Myrshalee", - -1 - ); + public class ArcaneCircleSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Arcane Circle", "Myrshalee", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 0.5 ); + public ArcaneCircleSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 0.0; - public override int RequiredMana => 24; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(0.5); - public ArcaneCircleSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 0.0; + public override int RequiredMana => 24; - public override bool CheckCast() - { - if ( !IsValidLocation( Caster.Location, Caster.Map ) ) - { - Caster.SendLocalizedMessage( 1072705 ); // You must be standing on an arcane circle, pentagram or abbatoir to use this spell. - return false; - } + public override bool CheckCast() + { + if (!IsValidLocation(Caster.Location, Caster.Map)) + { + Caster.SendLocalizedMessage( + 1072705); // You must be standing on an arcane circle, pentagram or abbatoir to use this spell. + return false; + } - if ( GetArcanists().Count < 2 ) - { - Caster.SendLocalizedMessage( 1080452 ); //There are not enough spellweavers present to create an Arcane Focus. - return false; - } + if (GetArcanists().Count < 2) + { + Caster.SendLocalizedMessage(1080452); //There are not enough spellweavers present to create an Arcane Focus. + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.FixedParticles( 0x3779, 10, 20, 0x0, EffectLayer.Waist ); - Caster.PlaySound( 0x5C0 ); + public override void OnCast() + { + if (CheckSequence()) + { + Caster.FixedParticles(0x3779, 10, 20, 0x0, EffectLayer.Waist); + Caster.PlaySound(0x5C0); - List Arcanists = GetArcanists(); + List Arcanists = GetArcanists(); - TimeSpan duration = TimeSpan.FromHours( Math.Max( 1, (int)(Caster.Skills.Spellweaving.Value / 24) ) ); + TimeSpan duration = TimeSpan.FromHours(Math.Max(1, (int)(Caster.Skills.Spellweaving.Value / 24))); - int strengthBonus = Math.Min( Arcanists.Count, IsSanctuary( Caster.Location, Caster.Map ) ? 6 : 5 ); //The Sanctuary is a special, single location place + int strengthBonus = + Math.Min(Arcanists.Count, + IsSanctuary(Caster.Location, Caster.Map) + ? 6 + : 5); //The Sanctuary is a special, single location place - for( int i = 0; i < Arcanists.Count; i++ ) - GiveArcaneFocus( Arcanists[i], duration, strengthBonus ); - } + for (int i = 0; i < Arcanists.Count; i++) + GiveArcaneFocus(Arcanists[i], duration, strengthBonus); + } - FinishSequence(); - } + FinishSequence(); + } - private static bool IsSanctuary( Point3D p, Map m ) - { - return (m == Map.Trammel || m == Map.Felucca) && p.X == 6267 && p.Y == 131; - } + private static bool IsSanctuary(Point3D p, Map m) + { + return (m == Map.Trammel || m == Map.Felucca) && p.X == 6267 && p.Y == 131; + } - private static bool IsValidLocation( Point3D location, Map map ) - { - LandTile lt = map.Tiles.GetLandTile( location.X, location.Y ); // Land Tiles + private static bool IsValidLocation(Point3D location, Map map) + { + LandTile lt = map.Tiles.GetLandTile(location.X, location.Y); // Land Tiles - if ( IsValidTile( lt.ID ) && lt.Z == location.Z ) - return true; + if (IsValidTile(lt.ID) && lt.Z == location.Z) + return true; - StaticTile[] tiles = map.Tiles.GetStaticTiles( location.X, location.Y ); // Static Tiles + StaticTile[] tiles = map.Tiles.GetStaticTiles(location.X, location.Y); // Static Tiles - for( int i = 0; i < tiles.Length; ++i ) - { - StaticTile t = tiles[i]; - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile t = tiles[i]; + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - int tand = t.ID; + int tand = t.ID; - if ( t.Z + id.CalcHeight != location.Z ) - continue; - if ( IsValidTile( tand ) ) - return true; - } + if (t.Z + id.CalcHeight != location.Z) + continue; + if (IsValidTile(tand)) + return true; + } - IPooledEnumerable eable = map.GetItemsInRange( location, 0 ); // Added Tiles + IPooledEnumerable eable = map.GetItemsInRange(location, 0); // Added Tiles - foreach( Item item in eable ) - { - ItemData id = item.ItemData; + foreach (Item item in eable) + { + ItemData id = item.ItemData; - if ( item == null || item.Z + id.CalcHeight != location.Z ) - continue; - if ( IsValidTile( item.ItemID ) ) - { - eable.Free(); - return true; - } - } + if (item == null || item.Z + id.CalcHeight != location.Z) + continue; + if (IsValidTile(item.ItemID)) + { + eable.Free(); + return true; + } + } - eable.Free(); - return false; - } + eable.Free(); + return false; + } - public static bool IsValidTile( int itemID ) - { - //Per OSI, Center tile only - return (itemID == 0xFEA || itemID == 0x1216 || itemID == 0x307F || itemID == 0x1D10 || itemID == 0x1D0F || itemID == 0x1D1F || itemID == 0x1D12 ); // Pentagram center, Abbatoir center, Arcane Circle Center, Bloody Pentagram has 4 tiles at center - } + public static bool IsValidTile(int itemID) + { + //Per OSI, Center tile only + return itemID == 0xFEA || itemID == 0x1216 || itemID == 0x307F || itemID == 0x1D10 || itemID == 0x1D0F || + itemID == 0x1D1F || + itemID == 0x1D12; // Pentagram center, Abbatoir center, Arcane Circle Center, Bloody Pentagram has 4 tiles at center + } - private List GetArcanists() - { - List weavers = new List(); + private List GetArcanists() + { + List weavers = new List(); - weavers.Add( Caster ); + weavers.Add(Caster); - //OSI Verified: Even enemies/combatants count - foreach( Mobile m in Caster.GetMobilesInRange( 1 ) ) //Range verified as 1 - { - if ( m != Caster && m is PlayerMobile && Caster.CanBeBeneficial( m, false ) && Math.Abs( Caster.Skills.Spellweaving.Value - m.Skills.Spellweaving.Value ) <= 20 && !(m is Clone) ) - { - weavers.Add( m ); - } - // Everyone gets the Arcane Focus, power capped elsewhere - } + //OSI Verified: Even enemies/combatants count + foreach (Mobile m in Caster.GetMobilesInRange(1)) //Range verified as 1 + if (m != Caster && m is PlayerMobile && Caster.CanBeBeneficial(m, false) && + Math.Abs(Caster.Skills.Spellweaving.Value - m.Skills.Spellweaving.Value) <= 20 && !(m is Clone)) + weavers.Add(m); + // Everyone gets the Arcane Focus, power capped elsewhere - return weavers; - } + return weavers; + } - private void GiveArcaneFocus( Mobile to, TimeSpan duration, int strengthBonus ) - { - if ( to == null ) //Sanity - return; + private void GiveArcaneFocus(Mobile to, TimeSpan duration, int strengthBonus) + { + if (to == null) //Sanity + return; - ArcaneFocus focus = FindArcaneFocus( to ); + ArcaneFocus focus = FindArcaneFocus(to); - if ( focus == null ) - { - ArcaneFocus f = new ArcaneFocus( duration, strengthBonus ); - if ( to.PlaceInBackpack( f ) ) - { - f.SendTimeRemainingMessage( to ); - to.SendLocalizedMessage( 1072740 ); // An arcane focus appears in your backpack. - } - else - { - f.Delete(); - } - - } - else //OSI renewal rules: the new one will override the old one, always. - { - to.SendLocalizedMessage( 1072828 ); // Your arcane focus is renewed. - focus.LifeSpan = duration; - focus.CreationTime = DateTime.UtcNow; - focus.StrengthBonus = strengthBonus; - focus.InvalidateProperties(); - focus.SendTimeRemainingMessage( to ); - } - } - } -} + if (focus == null) + { + ArcaneFocus f = new ArcaneFocus(duration, strengthBonus); + if (to.PlaceInBackpack(f)) + { + f.SendTimeRemainingMessage(to); + to.SendLocalizedMessage(1072740); // An arcane focus appears in your backpack. + } + else + { + f.Delete(); + } + } + else //OSI renewal rules: the new one will override the old one, always. + { + to.SendLocalizedMessage(1072828); // Your arcane focus is renewed. + focus.LifeSpan = duration; + focus.CreationTime = DateTime.UtcNow; + focus.StrengthBonus = strengthBonus; + focus.InvalidateProperties(); + focus.SendTimeRemainingMessage(to); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/ArcaneForm.cs b/Scripts/Spells/Spellweaving/ArcaneForm.cs index 60bfee2d1..7e158cd09 100644 --- a/Scripts/Spells/Spellweaving/ArcaneForm.cs +++ b/Scripts/Spells/Spellweaving/ArcaneForm.cs @@ -1,47 +1,47 @@ namespace Server.Spells.Spellweaving { - public abstract class ArcaneForm : ArcanistSpell, ITransformationSpell - { - public abstract int Body { get; } - public virtual int Hue => 0; + public abstract class ArcaneForm : ArcanistSpell, ITransformationSpell + { + public ArcaneForm(Mobile caster, Item scroll, SpellInfo info) : base(caster, scroll, info) + { + } - public virtual int PhysResistOffset => 0; - public virtual int FireResistOffset => 0; - public virtual int ColdResistOffset => 0; - public virtual int PoisResistOffset => 0; - public virtual int NrgyResistOffset => 0; + public abstract int Body{ get; } + public virtual int Hue => 0; - public ArcaneForm( Mobile caster, Item scroll, SpellInfo info ) : base( caster, scroll, info ) - { - } + public virtual int PhysResistOffset => 0; + public virtual int FireResistOffset => 0; + public virtual int ColdResistOffset => 0; + public virtual int PoisResistOffset => 0; + public virtual int NrgyResistOffset => 0; - public override bool CheckCast() - { - if ( !TransformationSpellHelper.CheckCast( Caster, this ) ) - return false; + public virtual double TickRate => 1.0; - return base.CheckCast(); - } + public virtual void OnTick(Mobile m) + { + } - public override void OnCast() - { - TransformationSpellHelper.OnCast( Caster, this ); + public virtual void DoEffect(Mobile m) + { + } - FinishSequence(); - } + public virtual void RemoveEffect(Mobile m) + { + } - public virtual double TickRate => 1.0; + public override bool CheckCast() + { + if (!TransformationSpellHelper.CheckCast(Caster, this)) + return false; - public virtual void OnTick( Mobile m ) - { - } + return base.CheckCast(); + } - public virtual void DoEffect( Mobile m ) - { - } + public override void OnCast() + { + TransformationSpellHelper.OnCast(Caster, this); - public virtual void RemoveEffect( Mobile m ) - { - } - } -} + FinishSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/ArcaneSummon.cs b/Scripts/Spells/Spellweaving/ArcaneSummon.cs index 71d2f7223..c582503d0 100644 --- a/Scripts/Spells/Spellweaving/ArcaneSummon.cs +++ b/Scripts/Spells/Spellweaving/ArcaneSummon.cs @@ -3,48 +3,54 @@ using Server.Mobiles; namespace Server.Spells.Spellweaving { - public abstract class ArcaneSummon : ArcanistSpell where T : BaseCreature - { - public abstract int Sound { get; } + public abstract class ArcaneSummon : ArcanistSpell where T : BaseCreature + { + public ArcaneSummon(Mobile caster, Item scroll, SpellInfo info) + : base(caster, scroll, info) + { + } - public ArcaneSummon( Mobile caster, Item scroll, SpellInfo info ) - : base( caster, scroll, info ) - { - } + public abstract int Sound{ get; } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( (Caster.Followers + 1) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1074270 ); // You have too many followers to summon another one. - return false; - } + if (Caster.Followers + 1 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1074270); // You have too many followers to summon another one. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromMinutes( Caster.Skills.Spellweaving.Value /24 + FocusLevel*2 ); - int summons = Math.Min( 1+FocusLevel, Caster.FollowersMax - Caster.Followers ); + public override void OnCast() + { + if (CheckSequence()) + { + TimeSpan duration = TimeSpan.FromMinutes(Caster.Skills.Spellweaving.Value / 24 + FocusLevel * 2); + int summons = Math.Min(1 + FocusLevel, Caster.FollowersMax - Caster.Followers); - for( int i = 0; i < summons; i++ ) - { - BaseCreature bc; + for (int i = 0; i < summons; i++) + { + BaseCreature bc; - try { bc = Activator.CreateInstance(); } - catch { break; } + try + { + bc = Activator.CreateInstance(); + } + catch + { + break; + } - SpellHelper.Summon( bc, Caster, Sound, duration, false, false ); - } + SpellHelper.Summon(bc, Caster, Sound, duration, false, false); + } - FinishSequence(); - } - } - } -} + FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/ArcanistSpell.cs b/Scripts/Spells/Spellweaving/ArcanistSpell.cs index 44fe70005..0ed776797 100644 --- a/Scripts/Spells/Spellweaving/ArcanistSpell.cs +++ b/Scripts/Spells/Spellweaving/ArcanistSpell.cs @@ -1,156 +1,161 @@ -using System; +using Server.Engines.MLQuests; using Server.Items; using Server.Mobiles; -using Server.Engines.MLQuests; namespace Server.Spells.Spellweaving { - public abstract class ArcanistSpell : Spell - { - public abstract double RequiredSkill { get; } - public abstract int RequiredMana { get; } + public abstract class ArcanistSpell : Spell + { + private int m_CastTimeFocusLevel; - public override SkillName CastSkill => SkillName.Spellweaving; - public override SkillName DamageSkill => SkillName.Spellweaving; + public ArcanistSpell(Mobile caster, Item scroll, SpellInfo info) + : base(caster, scroll, info) + { + } - public override bool ClearHandsOnCast => false; + public abstract double RequiredSkill{ get; } + public abstract int RequiredMana{ get; } - private int m_CastTimeFocusLevel; + public override SkillName CastSkill => SkillName.Spellweaving; + public override SkillName DamageSkill => SkillName.Spellweaving; - public ArcanistSpell( Mobile caster, Item scroll, SpellInfo info ) - : base( caster, scroll, info ) - { - } + public override bool ClearHandsOnCast => false; - public virtual int FocusLevel => m_CastTimeFocusLevel; + public virtual int FocusLevel => m_CastTimeFocusLevel; - public static int GetFocusLevel( Mobile from ) - { - ArcaneFocus focus = FindArcaneFocus( from ); + public static int GetFocusLevel(Mobile from) + { + ArcaneFocus focus = FindArcaneFocus(from); - if ( focus == null || focus.Deleted ) - return 0; + if (focus == null || focus.Deleted) + return 0; - return focus.StrengthBonus; - } + return focus.StrengthBonus; + } - public static ArcaneFocus FindArcaneFocus( Mobile from ) - { - if ( from?.Backpack == null ) - return null; + public static ArcaneFocus FindArcaneFocus(Mobile from) + { + if (from?.Backpack == null) + return null; - if ( from.Holding is ArcaneFocus ) - return (ArcaneFocus)from.Holding; + if (from.Holding is ArcaneFocus) + return (ArcaneFocus)from.Holding; - return from.Backpack.FindItemByType(); - } + return from.Backpack.FindItemByType(); + } - public static bool CheckExpansion( Mobile from ) - { - if ( !(from is PlayerMobile) ) - return true; + public static bool CheckExpansion(Mobile from) + { + if (!(from is PlayerMobile)) + return true; - if ( from.NetState == null ) - return false; + if (from.NetState == null) + return false; - return from.NetState.SupportsExpansion( Expansion.ML ); - } + return from.NetState.SupportsExpansion(Expansion.ML); + } - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - Mobile caster = Caster; + Mobile caster = Caster; - if ( !CheckExpansion( caster ) ) - { - caster.SendLocalizedMessage( 1072176 ); // You must upgrade to the Mondain's Legacy Expansion Pack before using that ability - return false; - } + if (!CheckExpansion(caster)) + { + caster.SendLocalizedMessage( + 1072176); // You must upgrade to the Mondain's Legacy Expansion Pack before using that ability + return false; + } - if ( caster is PlayerMobile ) - { - MLQuestContext context = MLQuestSystem.GetContext( (PlayerMobile)caster ); + if (caster is PlayerMobile) + { + MLQuestContext context = MLQuestSystem.GetContext((PlayerMobile)caster); - if ( context == null || !context.Spellweaving ) - { - caster.SendLocalizedMessage( 1073220 ); // You must have completed the epic arcanist quest to use this ability. - return false; - } - } + if (context == null || !context.Spellweaving) + { + caster.SendLocalizedMessage( + 1073220); // You must have completed the epic arcanist quest to use this ability. + return false; + } + } - int mana = ScaleMana( RequiredMana ); + int mana = ScaleMana(RequiredMana); - if ( caster.Mana < mana ) - { - caster.SendLocalizedMessage( 1060174, mana.ToString() ); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. - return false; - } + if (caster.Mana < mana) + { + caster.SendLocalizedMessage(1060174, + mana.ToString()); // You must have at least ~1_MANA_REQUIREMENT~ Mana to use this ability. + return false; + } - if ( caster.Skills[CastSkill].Value < RequiredSkill ) - { - caster.SendLocalizedMessage( 1063013, $"{RequiredSkill.ToString("F1")}\t{"#1044114"}"); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. - return false; - } + if (caster.Skills[CastSkill].Value < RequiredSkill) + { + caster.SendLocalizedMessage(1063013, + $"{RequiredSkill.ToString("F1")}\t{"#1044114"}"); // You need at least ~1_SKILL_REQUIREMENT~ ~2_SKILL_NAME~ skill to use that ability. + return false; + } - return true; - } + return true; + } - public override void GetCastSkills( out double min, out double max ) - { - min = RequiredSkill - 12.5; //per 5 on Friday, 2/16/07 - max = RequiredSkill + 37.5; - } + public override void GetCastSkills(out double min, out double max) + { + min = RequiredSkill - 12.5; //per 5 on Friday, 2/16/07 + max = RequiredSkill + 37.5; + } - public override int GetMana() - { - return RequiredMana; - } + public override int GetMana() + { + return RequiredMana; + } - public override void DoFizzle() - { - Caster.PlaySound( 0x1D6 ); - Caster.NextSpellTime = Core.TickCount; - } + public override void DoFizzle() + { + Caster.PlaySound(0x1D6); + Caster.NextSpellTime = Core.TickCount; + } - public override void DoHurtFizzle() - { - Caster.PlaySound( 0x1D6 ); - } + public override void DoHurtFizzle() + { + Caster.PlaySound(0x1D6); + } - public override void OnDisturb( DisturbType type, bool message ) - { - base.OnDisturb( type, message ); + public override void OnDisturb(DisturbType type, bool message) + { + base.OnDisturb(type, message); - if ( message ) - Caster.PlaySound( 0x1D6 ); - } + if (message) + Caster.PlaySound(0x1D6); + } - public override void OnBeginCast() - { - base.OnBeginCast(); + public override void OnBeginCast() + { + base.OnBeginCast(); - SendCastEffect(); - m_CastTimeFocusLevel = GetFocusLevel( Caster ); - } + SendCastEffect(); + m_CastTimeFocusLevel = GetFocusLevel(Caster); + } - public virtual void SendCastEffect() - { - Caster.FixedEffect( 0x37C4, 10, (int)(GetCastDelay().TotalSeconds * 28), 4, 3 ); - } + public virtual void SendCastEffect() + { + Caster.FixedEffect(0x37C4, 10, (int)(GetCastDelay().TotalSeconds * 28), 4, 3); + } - public virtual bool CheckResisted( Mobile m ) - { - double percent = (50 + 2*(GetResistSkill( m ) - GetDamageSkill( Caster )))/100; //TODO: According to the guide this is it.. but.. is it correct per OSI? + public virtual bool CheckResisted(Mobile m) + { + double percent = + (50 + 2 * (GetResistSkill(m) - GetDamageSkill(Caster))) / + 100; //TODO: According to the guide this is it.. but.. is it correct per OSI? - if ( percent <= 0 ) - return false; + if (percent <= 0) + return false; - if ( percent >= 1.0 ) - return true; + if (percent >= 1.0) + return true; - return (percent >= Utility.RandomDouble()); - } - } -} + return percent >= Utility.RandomDouble(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/AttuneWeapon.cs b/Scripts/Spells/Spellweaving/AttuneWeapon.cs index 9c305cb10..293ead1a4 100644 --- a/Scripts/Spells/Spellweaving/AttuneWeapon.cs +++ b/Scripts/Spells/Spellweaving/AttuneWeapon.cs @@ -3,131 +3,130 @@ using System.Collections.Generic; namespace Server.Spells.Spellweaving { - public class AttuneWeaponSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Attune Weapon", "Haeldril", - -1 - ); + public class AttuneWeaponSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Attune Weapon", "Haeldril", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + private static Dictionary m_Table = new Dictionary(); - public override double RequiredSkill => 0.0; - public override int RequiredMana => 24; + public AttuneWeaponSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public AttuneWeaponSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public override bool CheckCast() - { - if ( m_Table.ContainsKey( Caster ) ) - { - Caster.SendLocalizedMessage( 501775 ); // This spell is already in effect. - return false; - } + public override double RequiredSkill => 0.0; + public override int RequiredMana => 24; - if ( !Caster.CanBeginAction( typeof( AttuneWeaponSpell ) ) ) - { - Caster.SendLocalizedMessage( 1075124 ); // You must wait before casting that spell again. - return false; - } + public override bool CheckCast() + { + if (m_Table.ContainsKey(Caster)) + { + Caster.SendLocalizedMessage(501775); // This spell is already in effect. + return false; + } - return base.CheckCast(); - } + if (!Caster.CanBeginAction(typeof(AttuneWeaponSpell))) + { + Caster.SendLocalizedMessage(1075124); // You must wait before casting that spell again. + return false; + } - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.PlaySound( 0x5C3 ); - Caster.FixedParticles( 0x3728, 1, 13, 0x26B8, 0x455, 7, EffectLayer.Waist ); - Caster.FixedParticles( 0x3779, 1, 15, 0x251E, 0x3F, 7, EffectLayer.Waist ); + return base.CheckCast(); + } - double skill = Caster.Skills[SkillName.Spellweaving].Value; + public override void OnCast() + { + if (CheckSequence()) + { + Caster.PlaySound(0x5C3); + Caster.FixedParticles(0x3728, 1, 13, 0x26B8, 0x455, 7, EffectLayer.Waist); + Caster.FixedParticles(0x3779, 1, 15, 0x251E, 0x3F, 7, EffectLayer.Waist); - int damageAbsorb = (int)(18 + ((skill-10)/10)*3 + (FocusLevel * 6)); - Caster.MeleeDamageAbsorb = damageAbsorb; + double skill = Caster.Skills[SkillName.Spellweaving].Value; - TimeSpan duration = TimeSpan.FromSeconds( 60 + (FocusLevel * 12) ); + int damageAbsorb = (int)(18 + (skill - 10) / 10 * 3 + FocusLevel * 6); + Caster.MeleeDamageAbsorb = damageAbsorb; - ExpireTimer t = new ExpireTimer( Caster, duration ); - t.Start(); + TimeSpan duration = TimeSpan.FromSeconds(60 + FocusLevel * 12); - m_Table[Caster] = t; + ExpireTimer t = new ExpireTimer(Caster, duration); + t.Start(); - Caster.BeginAction( typeof( AttuneWeaponSpell ) ); + m_Table[Caster] = t; - BuffInfo.AddBuff( Caster, new BuffInfo( BuffIcon.AttuneWeapon, 1075798, duration, Caster, damageAbsorb.ToString() ) ); - } + Caster.BeginAction(typeof(AttuneWeaponSpell)); - FinishSequence(); - } + BuffInfo.AddBuff(Caster, + new BuffInfo(BuffIcon.AttuneWeapon, 1075798, duration, Caster, damageAbsorb.ToString())); + } - private static Dictionary m_Table = new Dictionary(); + FinishSequence(); + } - public static void TryAbsorb( Mobile defender, ref int damage ) - { - if ( damage == 0 || !IsAbsorbing( defender ) || defender.MeleeDamageAbsorb <= 0 ) - return; + public static void TryAbsorb(Mobile defender, ref int damage) + { + if (damage == 0 || !IsAbsorbing(defender) || defender.MeleeDamageAbsorb <= 0) + return; - int absorbed = Math.Min( damage, defender.MeleeDamageAbsorb ); + int absorbed = Math.Min(damage, defender.MeleeDamageAbsorb); - damage -= absorbed; - defender.MeleeDamageAbsorb -= absorbed; + damage -= absorbed; + defender.MeleeDamageAbsorb -= absorbed; - defender.SendLocalizedMessage( 1075127, $"{absorbed}\t{defender.MeleeDamageAbsorb}"); // ~1_damage~ point(s) of damage have been absorbed. A total of ~2_remaining~ point(s) of shielding remain. + defender.SendLocalizedMessage(1075127, + $"{absorbed}\t{defender.MeleeDamageAbsorb}"); // ~1_damage~ point(s) of damage have been absorbed. A total of ~2_remaining~ point(s) of shielding remain. - if ( defender.MeleeDamageAbsorb <= 0 ) - StopAbsorbing( defender, true ); - } + if (defender.MeleeDamageAbsorb <= 0) + StopAbsorbing(defender, true); + } - public static bool IsAbsorbing( Mobile m ) - { - return m_Table.ContainsKey( m ); - } + public static bool IsAbsorbing(Mobile m) + { + return m_Table.ContainsKey(m); + } - public static void StopAbsorbing( Mobile m, bool message ) - { - if (m_Table.TryGetValue( m, out ExpireTimer t )) - { - t.DoExpire( message ); - } - } + public static void StopAbsorbing(Mobile m, bool message) + { + if (m_Table.TryGetValue(m, out ExpireTimer t)) t.DoExpire(message); + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; + private class ExpireTimer : Timer + { + private Mobile m_Mobile; - public ExpireTimer( Mobile m, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - } + public ExpireTimer(Mobile m, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + } - protected override void OnTick() - { - DoExpire( true ); - } + protected override void OnTick() + { + DoExpire(true); + } - public void DoExpire( bool message ) - { - Stop(); + public void DoExpire(bool message) + { + Stop(); - m_Mobile.MeleeDamageAbsorb = 0; + m_Mobile.MeleeDamageAbsorb = 0; - if ( message ) - { - m_Mobile.SendLocalizedMessage( 1075126 ); // Your attunement fades. - m_Mobile.PlaySound( 0x1F8 ); - } + if (message) + { + m_Mobile.SendLocalizedMessage(1075126); // Your attunement fades. + m_Mobile.PlaySound(0x1F8); + } - m_Table.Remove( m_Mobile ); + m_Table.Remove(m_Mobile); - DelayCall( TimeSpan.FromSeconds( 120 ), delegate { m_Mobile.EndAction( typeof( AttuneWeaponSpell ) ); } ); - BuffInfo.RemoveBuff( m_Mobile, BuffIcon.AttuneWeapon ); - } - } - } -} + DelayCall(TimeSpan.FromSeconds(120), delegate { m_Mobile.EndAction(typeof(AttuneWeaponSpell)); }); + BuffInfo.RemoveBuff(m_Mobile, BuffIcon.AttuneWeapon); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/EssenceOfWind.cs b/Scripts/Spells/Spellweaving/EssenceOfWind.cs index 06c356edf..8dc8dd454 100644 --- a/Scripts/Spells/Spellweaving/EssenceOfWind.cs +++ b/Scripts/Spells/Spellweaving/EssenceOfWind.cs @@ -3,140 +3,139 @@ using System.Collections.Generic; namespace Server.Spells.Spellweaving { - public class EssenceOfWindSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( "Essence of Wind", "Anathrae", -1 ); + public class EssenceOfWindSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo("Essence of Wind", "Anathrae", -1); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 3.0 ); + private static Dictionary m_Table = new Dictionary(); - public override double RequiredSkill => 52.0; - public override int RequiredMana => 40; + public EssenceOfWindSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public EssenceOfWindSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(3.0); - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.PlaySound( 0x5C6 ); + public override double RequiredSkill => 52.0; + public override int RequiredMana => 40; - int range = 5 + FocusLevel; - int damage = 25 + FocusLevel; + public override void OnCast() + { + if (CheckSequence()) + { + Caster.PlaySound(0x5C6); - double skill = Caster.Skills[SkillName.Spellweaving].Value; + int range = 5 + FocusLevel; + int damage = 25 + FocusLevel; - TimeSpan duration = TimeSpan.FromSeconds( (int)(skill / 24) + FocusLevel ); + double skill = Caster.Skills[SkillName.Spellweaving].Value; - int fcMalus = FocusLevel + 1; - int ssiMalus = 2 * (FocusLevel + 1); + TimeSpan duration = TimeSpan.FromSeconds((int)(skill / 24) + FocusLevel); - List targets = new List(); + int fcMalus = FocusLevel + 1; + int ssiMalus = 2 * (FocusLevel + 1); - foreach( Mobile m in Caster.GetMobilesInRange( range ) ) - { - if ( Caster != m && Caster.InLOS( m ) && SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) ) - targets.Add( m ); - } + List targets = new List(); - for( int i = 0; i < targets.Count; i++ ) - { - Mobile m = targets[i]; + foreach (Mobile m in Caster.GetMobilesInRange(range)) + if (Caster != m && Caster.InLOS(m) && SpellHelper.ValidIndirectTarget(Caster, m) && + Caster.CanBeHarmful(m, false)) + targets.Add(m); - Caster.DoHarmful( m ); + for (int i = 0; i < targets.Count; i++) + { + Mobile m = targets[i]; - SpellHelper.Damage( this, m, damage, 0, 0, 100, 0, 0 ); + Caster.DoHarmful(m); - if ( !CheckResisted( m ) ) //No message on resist - { - m_Table[m] = new EssenceOfWindInfo( m, fcMalus, ssiMalus, duration ); + SpellHelper.Damage(this, m, damage, 0, 0, 100, 0, 0); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.EssenceOfWind, 1075802, duration, m, - $"{fcMalus.ToString()}\t{ssiMalus.ToString()}") ); - } - } - } + if (!CheckResisted(m)) //No message on resist + { + m_Table[m] = new EssenceOfWindInfo(m, fcMalus, ssiMalus, duration); - FinishSequence(); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.EssenceOfWind, 1075802, duration, m, + $"{fcMalus.ToString()}\t{ssiMalus.ToString()}")); + } + } + } - private static Dictionary m_Table = new Dictionary(); + FinishSequence(); + } - private class EssenceOfWindInfo - { - public Mobile Defender { get; } + public static int GetFCMalus(Mobile m) + { + if (m_Table.TryGetValue(m, out EssenceOfWindInfo info)) + return info.FCMalus; - public int FCMalus { get; } + return 0; + } - public int SSIMalus { get; } + public static int GetSSIMalus(Mobile m) + { + if (m_Table.TryGetValue(m, out EssenceOfWindInfo info)) + return info.SSIMalus; - public ExpireTimer Timer { get; } + return 0; + } - public EssenceOfWindInfo( Mobile defender, int fcMalus, int ssiMalus, TimeSpan duration ) - { - Defender = defender; - FCMalus = fcMalus; - SSIMalus = ssiMalus; + public static bool IsDebuffed(Mobile m) + { + return m_Table.ContainsKey(m); + } - Timer = new ExpireTimer( Defender, duration ); - Timer.Start(); - } - } + public static void StopDebuffing(Mobile m, bool message) + { + if (m_Table.TryGetValue(m, out EssenceOfWindInfo info)) + info.Timer.DoExpire(message); + } - public static int GetFCMalus( Mobile m ) - { - if (m_Table.TryGetValue( m, out EssenceOfWindInfo info )) - return info.FCMalus; + private class EssenceOfWindInfo + { + public EssenceOfWindInfo(Mobile defender, int fcMalus, int ssiMalus, TimeSpan duration) + { + Defender = defender; + FCMalus = fcMalus; + SSIMalus = ssiMalus; - return 0; - } + Timer = new ExpireTimer(Defender, duration); + Timer.Start(); + } - public static int GetSSIMalus( Mobile m ) - { - if (m_Table.TryGetValue( m, out EssenceOfWindInfo info )) - return info.SSIMalus; + public Mobile Defender{ get; } - return 0; - } + public int FCMalus{ get; } - public static bool IsDebuffed( Mobile m ) - { - return m_Table.ContainsKey( m ); - } + public int SSIMalus{ get; } - public static void StopDebuffing( Mobile m, bool message ) - { - if (m_Table.TryGetValue( m, out EssenceOfWindInfo info )) - info.Timer.DoExpire( message ); - } + public ExpireTimer Timer{ get; } + } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; + private class ExpireTimer : Timer + { + private Mobile m_Mobile; - public ExpireTimer( Mobile m, TimeSpan delay ) : base( delay ) - { - m_Mobile = m; - } + public ExpireTimer(Mobile m, TimeSpan delay) : base(delay) + { + m_Mobile = m; + } - protected override void OnTick() - { - DoExpire( true ); - } + protected override void OnTick() + { + DoExpire(true); + } - public void DoExpire( bool message ) - { - Stop(); - /* - if ( message ) - { - } - */ - m_Table.Remove( m_Mobile ); + public void DoExpire(bool message) + { + Stop(); + /* + if ( message ) + { + } + */ + m_Table.Remove(m_Mobile); - BuffInfo.RemoveBuff( m_Mobile, BuffIcon.EssenceOfWind ); - } - } - } -} + BuffInfo.RemoveBuff(m_Mobile, BuffIcon.EssenceOfWind); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/EtherealVoyage.cs b/Scripts/Spells/Spellweaving/EtherealVoyage.cs index eb031a26b..feee3769e 100644 --- a/Scripts/Spells/Spellweaving/EtherealVoyage.cs +++ b/Scripts/Spells/Spellweaving/EtherealVoyage.cs @@ -2,87 +2,75 @@ using System; namespace Server.Spells.Spellweaving { - public class EtherealVoyageSpell : ArcaneForm - { - private static SpellInfo m_Info = new SpellInfo( - "Ethereal Voyage", "Orlavdra", - -1 - ); + public class EtherealVoyageSpell : ArcaneForm + { + private static SpellInfo m_Info = new SpellInfo( + "Ethereal Voyage", "Orlavdra", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 3.5 ); + public EtherealVoyageSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 24.0; - public override int RequiredMana => 32; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(3.5); - public override int Body => 0x302; - public override int Hue => 0x48F; + public override double RequiredSkill => 24.0; + public override int RequiredMana => 32; - public EtherealVoyageSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override int Body => 0x302; + public override int Hue => 0x48F; - public static void Initialize() - { - EventSink.AggressiveAction += delegate( AggressiveActionEventArgs e ) - { - if ( TransformationSpellHelper.UnderTransformation( e.Aggressor, typeof( EtherealVoyageSpell ) ) ) - { - TransformationSpellHelper.RemoveContext( e.Aggressor, true ); - } - }; - } + public static void Initialize() + { + EventSink.AggressiveAction += delegate(AggressiveActionEventArgs e) + { + if (TransformationSpellHelper.UnderTransformation(e.Aggressor, typeof(EtherealVoyageSpell))) + TransformationSpellHelper.RemoveContext(e.Aggressor, true); + }; + } - public override bool CheckCast() - { - if ( TransformationSpellHelper.UnderTransformation( Caster, typeof( EtherealVoyageSpell ) ) ) - { - Caster.SendLocalizedMessage( 501775 ); // This spell is already in effect. - } - else if ( !Caster.CanBeginAction( typeof( EtherealVoyageSpell ) ) ) - { - Caster.SendLocalizedMessage( 1075124 ); // You must wait before casting that spell again. - } - else if ( Caster.Combatant != null ) - { - Caster.SendLocalizedMessage( 1072586 ); // You cannot cast Ethereal Voyage while you are in combat. - } - else - { - return base.CheckCast(); - } + public override bool CheckCast() + { + if (TransformationSpellHelper.UnderTransformation(Caster, typeof(EtherealVoyageSpell))) + Caster.SendLocalizedMessage(501775); // This spell is already in effect. + else if (!Caster.CanBeginAction(typeof(EtherealVoyageSpell))) + Caster.SendLocalizedMessage(1075124); // You must wait before casting that spell again. + else if (Caster.Combatant != null) + Caster.SendLocalizedMessage(1072586); // You cannot cast Ethereal Voyage while you are in combat. + else + return base.CheckCast(); - return false; - } + return false; + } - public override void DoEffect( Mobile m ) - { - m.PlaySound( 0x5C8 ); - m.SendLocalizedMessage( 1074770 ); // You are now under the effects of Ethereal Voyage. + public override void DoEffect(Mobile m) + { + m.PlaySound(0x5C8); + m.SendLocalizedMessage(1074770); // You are now under the effects of Ethereal Voyage. - double skill = Caster.Skills.Spellweaving.Value; + double skill = Caster.Skills.Spellweaving.Value; - TimeSpan duration = TimeSpan.FromSeconds( 12 + (int)(skill / 24) + (FocusLevel * 2) ); + TimeSpan duration = TimeSpan.FromSeconds(12 + (int)(skill / 24) + FocusLevel * 2); - Timer.DelayCall( duration, RemoveEffect, Caster ); + Timer.DelayCall(duration, RemoveEffect, Caster); - Caster.BeginAction( typeof( EtherealVoyageSpell ) ); //Cannot cast this spell for another 5 minutes(300sec) after effect removed. + Caster.BeginAction( + typeof(EtherealVoyageSpell)); //Cannot cast this spell for another 5 minutes(300sec) after effect removed. - BuffInfo.AddBuff( Caster, new BuffInfo( BuffIcon.EtherealVoyage, 1031613, 1075805, duration, Caster ) ); - } + BuffInfo.AddBuff(Caster, new BuffInfo(BuffIcon.EtherealVoyage, 1031613, 1075805, duration, Caster)); + } - public override void RemoveEffect( Mobile m ) - { - m.SendLocalizedMessage( 1074771 ); // You are no longer under the effects of Ethereal Voyage. + public override void RemoveEffect(Mobile m) + { + m.SendLocalizedMessage(1074771); // You are no longer under the effects of Ethereal Voyage. - TransformationSpellHelper.RemoveContext( m, true ); + TransformationSpellHelper.RemoveContext(m, true); - Timer.DelayCall( TimeSpan.FromMinutes( 5 ), delegate - { - m.EndAction( typeof( EtherealVoyageSpell ) ); - } ); + Timer.DelayCall(TimeSpan.FromMinutes(5), delegate { m.EndAction(typeof(EtherealVoyageSpell)); }); - BuffInfo.RemoveBuff( m, BuffIcon.EtherealVoyage ); - } - } -} + BuffInfo.RemoveBuff(m, BuffIcon.EtherealVoyage); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/GiftOfLife.cs b/Scripts/Spells/Spellweaving/GiftOfLife.cs index 9348aab98..04c506d1d 100644 --- a/Scripts/Spells/Spellweaving/GiftOfLife.cs +++ b/Scripts/Spells/Spellweaving/GiftOfLife.cs @@ -1,213 +1,205 @@ using System; using System.Collections.Generic; -using Server.Mobiles; using Server.Gumps; +using Server.Mobiles; using Server.Targeting; namespace Server.Spells.Spellweaving { - public class GiftOfLifeSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Gift of Life", "Illorae", - -1 - ); + public class GiftOfLifeSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Gift of Life", "Illorae", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 4.0 ); + private static Dictionary m_Table = new Dictionary(); - public override double RequiredSkill => 38.0; - public override int RequiredMana => 70; + public GiftOfLifeSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public GiftOfLifeSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(4.0); - public static void Initialize() - { - EventSink.PlayerDeath += delegate( PlayerDeathEventArgs e ) - { - HandleDeath( e.Mobile ); - }; - } + public override double RequiredSkill => 38.0; + public override int RequiredMana => 70; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public double HitsScalar => (Caster.Skills.Spellweaving.Value / 2.4 + FocusLevel) / 100; - public void Target( Mobile m ) - { - BaseCreature bc = m as BaseCreature; + public static void Initialize() + { + EventSink.PlayerDeath += delegate(PlayerDeathEventArgs e) { HandleDeath(e.Mobile); }; + } - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( m.IsDeadBondedPet || !m.Alive ) - { - // As per Osi: Nothing happens. - } - else if ( m != Caster && (bc == null || !bc.IsBonded || bc.ControlMaster != Caster) ) - { - Caster.SendLocalizedMessage( 1072077 ); // You may only cast this spell on yourself or a bonded pet. - } - else if ( m_Table.ContainsKey( m ) ) - { - Caster.SendLocalizedMessage( 501775 ); // This spell is already in effect. - } - else if ( CheckBSequence( m ) ) - { - if ( Caster == m ) - { - Caster.SendLocalizedMessage( 1074774 ); // You weave powerful magic, protecting yourself from death. - } - else - { - Caster.SendLocalizedMessage( 1074775 ); // You weave powerful magic, protecting your pet from death. - SpellHelper.Turn( Caster, m ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } + + public void Target(Mobile m) + { + BaseCreature bc = m as BaseCreature; + + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (m.IsDeadBondedPet || !m.Alive) + { + // As per Osi: Nothing happens. + } + else if (m != Caster && (bc == null || !bc.IsBonded || bc.ControlMaster != Caster)) + { + Caster.SendLocalizedMessage(1072077); // You may only cast this spell on yourself or a bonded pet. + } + else if (m_Table.ContainsKey(m)) + { + Caster.SendLocalizedMessage(501775); // This spell is already in effect. + } + else if (CheckBSequence(m)) + { + if (Caster == m) + { + Caster.SendLocalizedMessage(1074774); // You weave powerful magic, protecting yourself from death. + } + else + { + Caster.SendLocalizedMessage(1074775); // You weave powerful magic, protecting your pet from death. + SpellHelper.Turn(Caster, m); + } - m.PlaySound( 0x244 ); - m.FixedParticles( 0x3709, 1, 30, 0x26ED, 5, 2, EffectLayer.Waist ); - m.FixedParticles( 0x376A, 1, 30, 0x251E, 5, 3, EffectLayer.Waist ); + m.PlaySound(0x244); + m.FixedParticles(0x3709, 1, 30, 0x26ED, 5, 2, EffectLayer.Waist); + m.FixedParticles(0x376A, 1, 30, 0x251E, 5, 3, EffectLayer.Waist); - double skill = Caster.Skills[SkillName.Spellweaving].Value; + double skill = Caster.Skills[SkillName.Spellweaving].Value; - TimeSpan duration = TimeSpan.FromMinutes( ((int)(skill / 24))* 2 + FocusLevel ); + TimeSpan duration = TimeSpan.FromMinutes((int)(skill / 24) * 2 + FocusLevel); - ExpireTimer t = new ExpireTimer( m, duration, this ); - t.Start(); + ExpireTimer t = new ExpireTimer(m, duration, this); + t.Start(); - m_Table[m] = t; + m_Table[m] = t; - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.GiftOfLife, 1031615, 1075807, duration, m, null, true ) ); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.GiftOfLife, 1031615, 1075807, duration, m, null, true)); + } - FinishSequence(); - } + FinishSequence(); + } - private static Dictionary m_Table = new Dictionary(); + public static void HandleDeath(Mobile m) + { + if (m_Table.ContainsKey(m)) + Timer.DelayCall(TimeSpan.FromSeconds(Utility.RandomMinMax(2, 4)), HandleDeath_OnCallback, m); + } - public static void HandleDeath( Mobile m ) - { - if ( m_Table.ContainsKey( m ) ) - Timer.DelayCall( TimeSpan.FromSeconds( Utility.RandomMinMax( 2, 4 ) ), HandleDeath_OnCallback, m ); - } + private static void HandleDeath_OnCallback(Mobile m) + { + if (m_Table.TryGetValue(m, out ExpireTimer timer)) + { + double hitsScalar = timer.Spell.HitsScalar; - private static void HandleDeath_OnCallback( Mobile m ) - { - if (m_Table.TryGetValue( m, out ExpireTimer timer )) - { - double hitsScalar = timer.Spell.HitsScalar; + if (m is BaseCreature && m.IsDeadBondedPet) + { + BaseCreature pet = (BaseCreature)m; + Mobile master = pet.GetMaster(); - if ( m is BaseCreature && m.IsDeadBondedPet ) - { - BaseCreature pet = (BaseCreature)m; - Mobile master = pet.GetMaster(); + if (master?.NetState != null && Utility.InUpdateRange(pet, master)) + { + master.CloseGump(typeof(PetResurrectGump)); + master.SendGump(new PetResurrectGump(master, pet, hitsScalar)); + } + else + { + List friends = pet.Friends; - if ( master?.NetState != null && Utility.InUpdateRange( pet, master ) ) - { - master.CloseGump( typeof( PetResurrectGump ) ); - master.SendGump( new PetResurrectGump( master, pet, hitsScalar ) ); - } - else - { - List friends = pet.Friends; + for (int i = 0; friends != null && i < friends.Count; i++) + { + Mobile friend = friends[i]; - for( int i = 0; friends != null && i < friends.Count; i++ ) - { - Mobile friend = friends[i]; + if (friend.NetState != null && Utility.InUpdateRange(pet, friend)) + { + friend.CloseGump(typeof(PetResurrectGump)); + friend.SendGump(new PetResurrectGump(friend, pet)); + break; + } + } + } + } + else + { + m.CloseGump(typeof(ResurrectGump)); + m.SendGump(new ResurrectGump(m, hitsScalar)); + } - if ( friend.NetState != null && Utility.InUpdateRange( pet, friend ) ) - { - friend.CloseGump( typeof( PetResurrectGump ) ); - friend.SendGump( new PetResurrectGump( friend, pet ) ); - break; - } - } - } - } - else - { - m.CloseGump( typeof( ResurrectGump ) ); - m.SendGump( new ResurrectGump( m, hitsScalar ) ); - } + //Per OSI, buff is removed when gump sent, irregardless of online status or acceptence + timer.DoExpire(); + } + } - //Per OSI, buff is removed when gump sent, irregardless of online status or acceptence - timer.DoExpire(); - } + public static void OnLogin(LoginEventArgs e) + { + Mobile m = e.Mobile; - } + if (m == null || m.Alive || m_Table[m] == null) + return; - public double HitsScalar => ((Caster.Skills.Spellweaving.Value/2.4) + FocusLevel)/100; + HandleDeath_OnCallback(m); + } - public static void OnLogin( LoginEventArgs e ) - { - Mobile m = e.Mobile; + private class ExpireTimer : Timer + { + private Mobile m_Mobile; - if ( m == null || m.Alive || m_Table[m] == null ) - return; + public ExpireTimer(Mobile m, TimeSpan delay, GiftOfLifeSpell spell) + : base(delay) + { + m_Mobile = m; + Spell = spell; + } - HandleDeath_OnCallback( m ); - } + public GiftOfLifeSpell Spell{ get; } - private class ExpireTimer : Timer - { - private Mobile m_Mobile; + protected override void OnTick() + { + DoExpire(); + } - public GiftOfLifeSpell Spell { get; } + public void DoExpire() + { + Stop(); - public ExpireTimer( Mobile m, TimeSpan delay, GiftOfLifeSpell spell ) - : base( delay ) - { - m_Mobile = m; - Spell = spell; - } + m_Mobile.SendLocalizedMessage(1074776); // You are no longer protected with Gift of Life. + m_Table.Remove(m_Mobile); - protected override void OnTick() - { - DoExpire(); - } + BuffInfo.RemoveBuff(m_Mobile, BuffIcon.GiftOfLife); + } + } - public void DoExpire() - { - Stop(); + public class InternalTarget : Target + { + private GiftOfLifeSpell m_Owner; - m_Mobile.SendLocalizedMessage( 1074776 ); // You are no longer protected with Gift of Life. - m_Table.Remove( m_Mobile ); + public InternalTarget(GiftOfLifeSpell owner) + : base(10, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - BuffInfo.RemoveBuff( m_Mobile, BuffIcon.GiftOfLife ); - } - } + protected override void OnTarget(Mobile m, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + else + m.SendLocalizedMessage(1072077); // You may only cast this spell on yourself or a bonded pet. + } - public class InternalTarget : Target - { - private GiftOfLifeSpell m_Owner; - - public InternalTarget( GiftOfLifeSpell owner ) - : base( 10, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } - - protected override void OnTarget( Mobile m, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - else - { - m.SendLocalizedMessage( 1072077 ); // You may only cast this spell on yourself or a bonded pet. - } - } - - protected override void OnTargetFinish( Mobile m ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile m) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/GiftOfRenewal.cs b/Scripts/Spells/Spellweaving/GiftOfRenewal.cs index 616f31c26..fc2e24112 100644 --- a/Scripts/Spells/Spellweaving/GiftOfRenewal.cs +++ b/Scripts/Spells/Spellweaving/GiftOfRenewal.cs @@ -4,181 +4,175 @@ using Server.Targeting; namespace Server.Spells.Spellweaving { - public class GiftOfRenewalSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Gift of Renewal", "Olorisstra", - -1 - ); + public class GiftOfRenewalSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Gift of Renewal", "Olorisstra", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 3.0 ); + private static Dictionary m_Table = new Dictionary(); - public override double RequiredSkill => 0.0; - public override int RequiredMana => 24; + public GiftOfRenewalSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public GiftOfRenewalSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(3.0); - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override double RequiredSkill => 0.0; + public override int RequiredMana => 24; - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - if ( m_Table.ContainsKey( m ) ) - { - Caster.SendLocalizedMessage( 501775 ); // This spell is already in effect. - } - else if ( !Caster.CanBeginAction( typeof( GiftOfRenewalSpell ) ) ) - { - Caster.SendLocalizedMessage( 501789 ); // You must wait before trying again. - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - Caster.FixedEffect( 0x374A, 10, 20 ); - Caster.PlaySound( 0x5C9 ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) Caster.SendLocalizedMessage(500237); // Target can not be seen. + if (m_Table.ContainsKey(m)) + { + Caster.SendLocalizedMessage(501775); // This spell is already in effect. + } + else if (!Caster.CanBeginAction(typeof(GiftOfRenewalSpell))) + { + Caster.SendLocalizedMessage(501789); // You must wait before trying again. + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - if ( m.Poisoned ) - { - m.CurePoison( m ); - } - else - { - double skill = Caster.Skills[SkillName.Spellweaving].Value; + Caster.FixedEffect(0x374A, 10, 20); + Caster.PlaySound(0x5C9); - int hitsPerRound = 5 + (int)(skill / 24) + FocusLevel; - TimeSpan duration = TimeSpan.FromSeconds( 30 + (FocusLevel * 10) ); + if (m.Poisoned) + { + m.CurePoison(m); + } + else + { + double skill = Caster.Skills[SkillName.Spellweaving].Value; - GiftOfRenewalInfo info = new GiftOfRenewalInfo( Caster, m, hitsPerRound ); + int hitsPerRound = 5 + (int)(skill / 24) + FocusLevel; + TimeSpan duration = TimeSpan.FromSeconds(30 + FocusLevel * 10); - Timer.DelayCall( duration, - delegate - { - if ( StopEffect( m ) ) - { - m.PlaySound( 0x455 ); - m.SendLocalizedMessage( 1075071 ); // The Gift of Renewal has faded. - } - } ); + GiftOfRenewalInfo info = new GiftOfRenewalInfo(Caster, m, hitsPerRound); + + Timer.DelayCall(duration, + delegate + { + if (StopEffect(m)) + { + m.PlaySound(0x455); + m.SendLocalizedMessage(1075071); // The Gift of Renewal has faded. + } + }); + m_Table[m] = info; - m_Table[m] = info; + Caster.BeginAction(typeof(GiftOfRenewalSpell)); - Caster.BeginAction( typeof( GiftOfRenewalSpell ) ); + BuffInfo.AddBuff(m, + new BuffInfo(BuffIcon.GiftOfRenewal, 1031602, 1075797, duration, m, hitsPerRound.ToString())); + } + } - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.GiftOfRenewal, 1031602, 1075797, duration, m, hitsPerRound.ToString() ) ); - } - } + FinishSequence(); + } - FinishSequence(); - } + public static bool StopEffect(Mobile m) + { + if (m_Table.TryGetValue(m, out GiftOfRenewalInfo info)) + { + m_Table.Remove(m); - private static Dictionary m_Table = new Dictionary(); + info.m_Timer.Stop(); + BuffInfo.RemoveBuff(m, BuffIcon.GiftOfRenewal); - private class GiftOfRenewalInfo - { - public Mobile m_Caster; - public Mobile m_Mobile; - public int m_HitsPerRound; - public InternalTimer m_Timer; + Timer.DelayCall(TimeSpan.FromSeconds(60), delegate { info.m_Caster.EndAction(typeof(GiftOfRenewalSpell)); }); - public GiftOfRenewalInfo( Mobile caster, Mobile mobile, int hitsPerRound ) - { - m_Caster = caster; - m_Mobile = mobile; - m_HitsPerRound = hitsPerRound; + return true; + } - m_Timer = new InternalTimer( this ); - m_Timer.Start(); - } - } + return false; + } - private class InternalTimer : Timer - { - public GiftOfRenewalInfo m_Info; + private class GiftOfRenewalInfo + { + public Mobile m_Caster; + public int m_HitsPerRound; + public Mobile m_Mobile; + public InternalTimer m_Timer; - public InternalTimer( GiftOfRenewalInfo info ) - : base( TimeSpan.FromSeconds( 2.0 ), TimeSpan.FromSeconds( 2.0 ) ) - { - m_Info = info; - } + public GiftOfRenewalInfo(Mobile caster, Mobile mobile, int hitsPerRound) + { + m_Caster = caster; + m_Mobile = mobile; + m_HitsPerRound = hitsPerRound; - protected override void OnTick() - { - Mobile m = m_Info.m_Mobile; + m_Timer = new InternalTimer(this); + m_Timer.Start(); + } + } - if ( !m_Table.ContainsKey( m ) ) - { - Stop(); - return; - } + private class InternalTimer : Timer + { + public GiftOfRenewalInfo m_Info; - if ( !m.Alive ) - { - Stop(); - StopEffect( m ); - return; - } + public InternalTimer(GiftOfRenewalInfo info) + : base(TimeSpan.FromSeconds(2.0), TimeSpan.FromSeconds(2.0)) + { + m_Info = info; + } - if ( m.Hits >= m.HitsMax ) - return; + protected override void OnTick() + { + Mobile m = m_Info.m_Mobile; - int toHeal = m_Info.m_HitsPerRound; + if (!m_Table.ContainsKey(m)) + { + Stop(); + return; + } - SpellHelper.Heal( toHeal, m, m_Info.m_Caster ); - m.FixedParticles( 0x376A, 9, 32, 5005, EffectLayer.Waist ); - } - } + if (!m.Alive) + { + Stop(); + StopEffect(m); + return; + } - public static bool StopEffect( Mobile m ) - { - if (m_Table.TryGetValue( m, out GiftOfRenewalInfo info )) - { - m_Table.Remove( m ); + if (m.Hits >= m.HitsMax) + return; - info.m_Timer.Stop(); - BuffInfo.RemoveBuff( m, BuffIcon.GiftOfRenewal ); + int toHeal = m_Info.m_HitsPerRound; - Timer.DelayCall( TimeSpan.FromSeconds( 60 ), delegate { info.m_Caster.EndAction( typeof( GiftOfRenewalSpell ) ); } ); + SpellHelper.Heal(toHeal, m, m_Info.m_Caster); + m.FixedParticles(0x376A, 9, 32, 5005, EffectLayer.Waist); + } + } - return true; - } + public class InternalTarget : Target + { + private GiftOfRenewalSpell m_Owner; - return false; - } + public InternalTarget(GiftOfRenewalSpell owner) + : base(10, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - public class InternalTarget : Target - { - private GiftOfRenewalSpell m_Owner; + protected override void OnTarget(Mobile m, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - public InternalTarget( GiftOfRenewalSpell owner ) - : base( 10, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } - - protected override void OnTarget( Mobile m, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } - - protected override void OnTargetFinish( Mobile m ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile m) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/ImmolatingWeapon.cs b/Scripts/Spells/Spellweaving/ImmolatingWeapon.cs index 20dd1a8d1..b59770ab2 100644 --- a/Scripts/Spells/Spellweaving/ImmolatingWeapon.cs +++ b/Scripts/Spells/Spellweaving/ImmolatingWeapon.cs @@ -4,130 +4,131 @@ using Server.Items; namespace Server.Spells.Spellweaving { - public class ImmolatingWeaponSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Immolating Weapon", "Thalshara", - -1 - ); + public class ImmolatingWeaponSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Immolating Weapon", "Thalshara", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.0 ); + private static Dictionary m_WeaponDamageTable = + new Dictionary(); - public override double RequiredSkill => 10.0; - public override int RequiredMana => 32; + public ImmolatingWeaponSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public ImmolatingWeaponSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.0); - public override bool CheckCast() - { - BaseWeapon weapon = Caster.Weapon as BaseWeapon; + public override double RequiredSkill => 10.0; + public override int RequiredMana => 32; - if ( weapon == null || weapon is Fists || weapon is BaseRanged ) - { - Caster.SendLocalizedMessage( 1060179 ); // You must be wielding a weapon to use this ability! - return false; - } + public override bool CheckCast() + { + BaseWeapon weapon = Caster.Weapon as BaseWeapon; - return base.CheckCast(); - } + if (weapon == null || weapon is Fists || weapon is BaseRanged) + { + Caster.SendLocalizedMessage(1060179); // You must be wielding a weapon to use this ability! + return false; + } - public override void OnCast() - { - BaseWeapon weapon = Caster.Weapon as BaseWeapon; + return base.CheckCast(); + } - if ( weapon == null || weapon is Fists || weapon is BaseRanged ) - { - Caster.SendLocalizedMessage( 1060179 ); // You must be wielding a weapon to use this ability! - } - else if ( CheckSequence() ) - { - Caster.PlaySound( 0x5CA ); - Caster.FixedParticles( 0x36BD, 20, 10, 5044, EffectLayer.Head ); + public override void OnCast() + { + BaseWeapon weapon = Caster.Weapon as BaseWeapon; - if ( !IsImmolating( weapon ) ) // On OSI, the effect is not re-applied - { - double skill = Caster.Skills.Spellweaving.Value; + if (weapon == null || weapon is Fists || weapon is BaseRanged) + { + Caster.SendLocalizedMessage(1060179); // You must be wielding a weapon to use this ability! + } + else if (CheckSequence()) + { + Caster.PlaySound(0x5CA); + Caster.FixedParticles(0x36BD, 20, 10, 5044, EffectLayer.Head); - int duration = 10 + (int)( skill / 24 ) + FocusLevel; - int damage = 5 + (int)( skill / 24 ) + FocusLevel; + if (!IsImmolating(weapon)) // On OSI, the effect is not re-applied + { + double skill = Caster.Skills.Spellweaving.Value; - Timer stopTimer = Timer.DelayCall( TimeSpan.FromSeconds( duration ), StopImmolating, weapon ); + int duration = 10 + (int)(skill / 24) + FocusLevel; + int damage = 5 + (int)(skill / 24) + FocusLevel; - m_WeaponDamageTable[weapon] = new ImmolatingWeaponEntry( damage, stopTimer, Caster ); - weapon.InvalidateProperties(); - } - } + Timer stopTimer = Timer.DelayCall(TimeSpan.FromSeconds(duration), StopImmolating, weapon); - FinishSequence(); - } + m_WeaponDamageTable[weapon] = new ImmolatingWeaponEntry(damage, stopTimer, Caster); + weapon.InvalidateProperties(); + } + } - private static Dictionary m_WeaponDamageTable = new Dictionary(); + FinishSequence(); + } - public static bool IsImmolating( BaseWeapon weapon ) - { - return m_WeaponDamageTable.ContainsKey( weapon ); - } + public static bool IsImmolating(BaseWeapon weapon) + { + return m_WeaponDamageTable.ContainsKey(weapon); + } - public static int GetImmolatingDamage( BaseWeapon weapon ) - { - if (m_WeaponDamageTable.TryGetValue( weapon, out ImmolatingWeaponEntry entry )) - return entry.m_Damage; + public static int GetImmolatingDamage(BaseWeapon weapon) + { + if (m_WeaponDamageTable.TryGetValue(weapon, out ImmolatingWeaponEntry entry)) + return entry.m_Damage; - return 0; - } + return 0; + } - public static void DoEffect( BaseWeapon weapon, Mobile target ) - { - Timer.DelayCall( TimeSpan.FromSeconds( 0.25 ), FinishEffect, new DelayedEffectEntry( weapon, target ) ); - } + public static void DoEffect(BaseWeapon weapon, Mobile target) + { + Timer.DelayCall(TimeSpan.FromSeconds(0.25), FinishEffect, new DelayedEffectEntry(weapon, target)); + } - private static void FinishEffect( DelayedEffectEntry effect ) - { - if (m_WeaponDamageTable.TryGetValue( effect.m_Weapon, out ImmolatingWeaponEntry entry )) - AOS.Damage( effect.m_Target, entry.m_Caster, entry.m_Damage, 0, 100, 0, 0, 0 ); - } + private static void FinishEffect(DelayedEffectEntry effect) + { + if (m_WeaponDamageTable.TryGetValue(effect.m_Weapon, out ImmolatingWeaponEntry entry)) + AOS.Damage(effect.m_Target, entry.m_Caster, entry.m_Damage, 0, 100, 0, 0, 0); + } - public static void StopImmolating( BaseWeapon weapon ) - { - if (m_WeaponDamageTable.TryGetValue( weapon, out ImmolatingWeaponEntry entry )) - { - entry.m_Caster?.PlaySound( 0x27 ); + public static void StopImmolating(BaseWeapon weapon) + { + if (m_WeaponDamageTable.TryGetValue(weapon, out ImmolatingWeaponEntry entry)) + { + entry.m_Caster?.PlaySound(0x27); - entry.m_Timer.Stop(); + entry.m_Timer.Stop(); - m_WeaponDamageTable.Remove( weapon ); + m_WeaponDamageTable.Remove(weapon); - weapon.InvalidateProperties(); - } - } + weapon.InvalidateProperties(); + } + } - private class ImmolatingWeaponEntry - { - public int m_Damage; - public Timer m_Timer; - public Mobile m_Caster; + private class ImmolatingWeaponEntry + { + public Mobile m_Caster; + public int m_Damage; + public Timer m_Timer; - public ImmolatingWeaponEntry( int damage, Timer stopTimer, Mobile caster ) - { - m_Damage = damage; - m_Timer = stopTimer; - m_Caster = caster; - } - } + public ImmolatingWeaponEntry(int damage, Timer stopTimer, Mobile caster) + { + m_Damage = damage; + m_Timer = stopTimer; + m_Caster = caster; + } + } - private class DelayedEffectEntry - { - public BaseWeapon m_Weapon; - public Mobile m_Target; + private class DelayedEffectEntry + { + public Mobile m_Target; + public BaseWeapon m_Weapon; - public DelayedEffectEntry( BaseWeapon weapon, Mobile target ) - { - m_Weapon = weapon; - m_Target = target; - } - } - } -} + public DelayedEffectEntry(BaseWeapon weapon, Mobile target) + { + m_Weapon = weapon; + m_Target = target; + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/Items/ArcaneFocus.cs b/Scripts/Spells/Spellweaving/Items/ArcaneFocus.cs index 6cfdd1a79..9ef7f5f07 100644 --- a/Scripts/Spells/Spellweaving/Items/ArcaneFocus.cs +++ b/Scripts/Spells/Spellweaving/Items/ArcaneFocus.cs @@ -2,59 +2,59 @@ using System; namespace Server.Items { - public class ArcaneFocus : TransientItem - { - public override int LabelNumber => 1032629; // Arcane Focus + public class ArcaneFocus : TransientItem + { + [Constructible] + public ArcaneFocus() + : this(TimeSpan.FromHours(1), 1) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int StrengthBonus { get; set; } + [Constructible] + public ArcaneFocus(int lifeSpan, int strengthBonus) + : this(TimeSpan.FromSeconds(lifeSpan), strengthBonus) + { + } - [Constructible] - public ArcaneFocus() - : this( TimeSpan.FromHours( 1 ), 1 ) - { - } + public ArcaneFocus(TimeSpan lifeSpan, int strengthBonus) : base(0x3155, lifeSpan) + { + LootType = LootType.Blessed; + StrengthBonus = strengthBonus; + } - [Constructible] - public ArcaneFocus( int lifeSpan, int strengthBonus ) - : this( TimeSpan.FromSeconds( lifeSpan ), strengthBonus ) - { - } + public ArcaneFocus(Serial serial) : base(serial) + { + } - public ArcaneFocus( TimeSpan lifeSpan, int strengthBonus ) : base( 0x3155, lifeSpan ) - { - LootType = LootType.Blessed; - StrengthBonus = strengthBonus; - } + public override int LabelNumber => 1032629; // Arcane Focus - public ArcaneFocus( Serial serial ) : base( serial ) - { - } + [CommandProperty(AccessLevel.GameMaster)] + public int StrengthBonus{ get; set; } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override TextDefinition InvalidTransferMessage => 1073480; // Your arcane focus disappears. + public override bool Nontransferable => true; - list.Add( 1060485, StrengthBonus.ToString() ); // strength bonus ~1_val~ - } + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - public override TextDefinition InvalidTransferMessage => 1073480; // Your arcane focus disappears. - public override bool Nontransferable => true; + list.Add(1060485, StrengthBonus.ToString()); // strength bonus ~1_val~ + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - writer.Write( StrengthBonus ); - } + writer.Write(StrengthBonus); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - StrengthBonus = reader.ReadInt(); - } - } -} + StrengthBonus = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/Items/TransientItem.cs b/Scripts/Spells/Spellweaving/Items/TransientItem.cs index b67098d4b..b72343d8b 100644 --- a/Scripts/Spells/Spellweaving/Items/TransientItem.cs +++ b/Scripts/Spells/Spellweaving/Items/TransientItem.cs @@ -2,100 +2,101 @@ using System; namespace Server.Items { - public class TransientItem : Item - { - [CommandProperty( AccessLevel.GameMaster )] - public TimeSpan LifeSpan { get; set; } + public class TransientItem : Item + { + private Timer m_Timer; - [CommandProperty( AccessLevel.GameMaster )] - public DateTime CreationTime { get; set; } + [Constructible] + public TransientItem(int itemID, TimeSpan lifeSpan) + : base(itemID) + { + CreationTime = DateTime.UtcNow; + LifeSpan = lifeSpan; - private Timer m_Timer; + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(5), CheckExpiry); + } - public override bool Nontransferable => true; - public override void HandleInvalidTransfer( Mobile from ) - { - if ( InvalidTransferMessage != null ) - TextDefinition.SendMessageTo( from, InvalidTransferMessage ); + public TransientItem(Serial serial) + : base(serial) + { + } - Delete(); - } + [CommandProperty(AccessLevel.GameMaster)] + public TimeSpan LifeSpan{ get; set; } - public virtual TextDefinition InvalidTransferMessage => null; + [CommandProperty(AccessLevel.GameMaster)] + public DateTime CreationTime{ get; set; } + + public override bool Nontransferable => true; + + public virtual TextDefinition InvalidTransferMessage => null; + + public override void HandleInvalidTransfer(Mobile from) + { + if (InvalidTransferMessage != null) + TextDefinition.SendMessageTo(from, InvalidTransferMessage); + + Delete(); + } - public virtual void Expire( Mobile parent ) - { - parent?.SendLocalizedMessage( 1072515, Name ?? $"#{LabelNumber}" ); // The ~1_name~ expired... + public virtual void Expire(Mobile parent) + { + parent?.SendLocalizedMessage(1072515, Name ?? $"#{LabelNumber}"); // The ~1_name~ expired... - Effects.PlaySound( GetWorldLocation(), Map, 0x201 ); + Effects.PlaySound(GetWorldLocation(), Map, 0x201); - Delete(); - } + Delete(); + } - public virtual void SendTimeRemainingMessage( Mobile to ) - { - to.SendLocalizedMessage( 1072516, - $"{Name ?? $"#{LabelNumber}"}\t{(int) LifeSpan.TotalSeconds}"); // ~1_name~ will expire in ~2_val~ seconds! - } + public virtual void SendTimeRemainingMessage(Mobile to) + { + to.SendLocalizedMessage(1072516, + $"{Name ?? $"#{LabelNumber}"}\t{(int)LifeSpan.TotalSeconds}"); // ~1_name~ will expire in ~2_val~ seconds! + } - public override void OnDelete() - { - m_Timer?.Stop(); + public override void OnDelete() + { + m_Timer?.Stop(); - base.OnDelete(); - } + base.OnDelete(); + } - public virtual void CheckExpiry() - { - if ( (CreationTime + LifeSpan) < DateTime.UtcNow ) - Expire( RootParent as Mobile ); - else - InvalidateProperties(); - } + public virtual void CheckExpiry() + { + if (CreationTime + LifeSpan < DateTime.UtcNow) + Expire(RootParent as Mobile); + else + InvalidateProperties(); + } - [Constructible] - public TransientItem( int itemID, TimeSpan lifeSpan ) - : base( itemID ) - { - CreationTime = DateTime.UtcNow; - LifeSpan = lifeSpan; + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 5 ), CheckExpiry ); - } + TimeSpan remaining = CreationTime + LifeSpan - DateTime.UtcNow; - public TransientItem( Serial serial ) - : base( serial ) - { - } + list.Add(1072517, ((int)remaining.TotalSeconds).ToString()); // Lifespan: ~1_val~ seconds + } - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); - TimeSpan remaining = ((CreationTime + LifeSpan) - DateTime.UtcNow); + writer.Write(LifeSpan); + writer.Write(CreationTime); + } - list.Add( 1072517, ((int)remaining.TotalSeconds).ToString() ); // Lifespan: ~1_val~ seconds - } + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 ); + LifeSpan = reader.ReadTimeSpan(); + CreationTime = reader.ReadDateTime(); - writer.Write( LifeSpan ); - writer.Write( CreationTime ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - - LifeSpan = reader.ReadTimeSpan(); - CreationTime = reader.ReadDateTime(); - - m_Timer = Timer.DelayCall( TimeSpan.FromSeconds( 5 ), TimeSpan.FromSeconds( 5 ), CheckExpiry ); - } - } -} + m_Timer = Timer.DelayCall(TimeSpan.FromSeconds(5), TimeSpan.FromSeconds(5), CheckExpiry); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/Mobiles/ArcaneFey.cs b/Scripts/Spells/Spellweaving/Mobiles/ArcaneFey.cs index 31a6a6373..a3803d873 100644 --- a/Scripts/Spells/Spellweaving/Mobiles/ArcaneFey.cs +++ b/Scripts/Spells/Spellweaving/Mobiles/ArcaneFey.cs @@ -1,62 +1,62 @@ namespace Server.Mobiles { - public class ArcaneFey : BaseCreature - { - public override string CorpseName => "a pixie corpse"; - public override double DispelDifficulty => 70.0; - public override double DispelFocus => 20.0; + public class ArcaneFey : BaseCreature + { + [Constructible] + public ArcaneFey() : base(AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4) + { + Name = NameList.RandomName("pixie"); + Body = 128; + BaseSoundID = 0x467; - public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; - public override bool InitialInnocent => true; + SetStr(20); + SetDex(150); + SetInt(125); - [Constructible] - public ArcaneFey() : base( AIType.AI_Mage, FightMode.Evil, 10, 1, 0.2, 0.4 ) - { - Name = NameList.RandomName( "pixie" ); - Body = 128; - BaseSoundID = 0x467; + SetDamage(9, 15); - SetStr( 20 ); - SetDex( 150 ); - SetInt( 125 ); + SetDamageType(ResistanceType.Physical, 100); - SetDamage( 9, 15 ); + SetResistance(ResistanceType.Physical, 80, 90); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 40, 50); + SetResistance(ResistanceType.Poison, 40, 50); + SetResistance(ResistanceType.Energy, 40, 50); - SetDamageType( ResistanceType.Physical, 100 ); + SetSkill(SkillName.EvalInt, 70.1, 80.0); + SetSkill(SkillName.Magery, 70.1, 80.0); + SetSkill(SkillName.Meditation, 70.1, 80.0); + SetSkill(SkillName.MagicResist, 50.5, 100.0); + SetSkill(SkillName.Tactics, 10.1, 20.0); + SetSkill(SkillName.Wrestling, 10.1, 12.5); - SetResistance( ResistanceType.Physical, 80, 90 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 40, 50 ); - SetResistance( ResistanceType.Poison, 40, 50 ); - SetResistance( ResistanceType.Energy, 40, 50 ); + Fame = 0; + Karma = 0; - SetSkill( SkillName.EvalInt, 70.1, 80.0 ); - SetSkill( SkillName.Magery, 70.1, 80.0 ); - SetSkill( SkillName.Meditation, 70.1, 80.0 ); - SetSkill( SkillName.MagicResist, 50.5, 100.0 ); - SetSkill( SkillName.Tactics, 10.1, 20.0 ); - SetSkill( SkillName.Wrestling, 10.1, 12.5 ); + ControlSlots = 1; + } - Fame = 0; - Karma = 0; + public ArcaneFey(Serial serial) : base(serial) + { + } - ControlSlots = 1; - } + public override string CorpseName => "a pixie corpse"; + public override double DispelDifficulty => 70.0; + public override double DispelFocus => 20.0; - public ArcaneFey( Serial serial ) : base( serial ) - { - } + public override OppositionGroup OppositionGroup => OppositionGroup.FeyAndUndead; + public override bool InitialInnocent => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/Mobiles/ArcaneFiend.cs b/Scripts/Spells/Spellweaving/Mobiles/ArcaneFiend.cs index 5e231803a..743c6519f 100644 --- a/Scripts/Spells/Spellweaving/Mobiles/ArcaneFiend.cs +++ b/Scripts/Spells/Spellweaving/Mobiles/ArcaneFiend.cs @@ -1,63 +1,63 @@ namespace Server.Mobiles { - public class ArcaneFiend : BaseCreature - { - public override string CorpseName => "an imp corpse"; - public override double DispelDifficulty => 70.0; - public override double DispelFocus => 20.0; + public class ArcaneFiend : BaseCreature + { + [Constructible] + public ArcaneFiend() : base(AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 74; + BaseSoundID = 422; - public override PackInstinct PackInstinct => PackInstinct.Daemon; - public override bool BleedImmune => true; //TODO: Verify on OSI. Guide says this. - public override string DefaultName => "an imp"; + SetStr(55); + SetDex(40); + SetInt(60); - [Constructible] - public ArcaneFiend() : base( AIType.AI_Mage, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 74; - BaseSoundID = 422; + SetDamage(10, 14); - SetStr( 55 ); - SetDex( 40 ); - SetInt( 60 ); + SetDamageType(ResistanceType.Physical, 0); + SetDamageType(ResistanceType.Fire, 50); + SetDamageType(ResistanceType.Poison, 50); - SetDamage( 10, 14 ); + SetResistance(ResistanceType.Physical, 25, 35); + SetResistance(ResistanceType.Fire, 40, 50); + SetResistance(ResistanceType.Cold, 20, 30); + SetResistance(ResistanceType.Poison, 30, 40); + SetResistance(ResistanceType.Energy, 30, 40); - SetDamageType( ResistanceType.Physical, 0 ); - SetDamageType( ResistanceType.Fire, 50 ); - SetDamageType( ResistanceType.Poison, 50 ); + SetSkill(SkillName.EvalInt, 20.1, 30.0); + SetSkill(SkillName.Magery, 60.1, 70.0); + SetSkill(SkillName.MagicResist, 30.1, 50.0); + SetSkill(SkillName.Tactics, 42.1, 50.0); + SetSkill(SkillName.Wrestling, 40.1, 44.0); - SetResistance( ResistanceType.Physical, 25, 35 ); - SetResistance( ResistanceType.Fire, 40, 50 ); - SetResistance( ResistanceType.Cold, 20, 30 ); - SetResistance( ResistanceType.Poison, 30, 40 ); - SetResistance( ResistanceType.Energy, 30, 40 ); + Fame = 0; + Karma = 0; - SetSkill( SkillName.EvalInt, 20.1, 30.0 ); - SetSkill( SkillName.Magery, 60.1, 70.0 ); - SetSkill( SkillName.MagicResist, 30.1, 50.0 ); - SetSkill( SkillName.Tactics, 42.1, 50.0 ); - SetSkill( SkillName.Wrestling, 40.1, 44.0 ); + ControlSlots = 1; + } - Fame = 0; - Karma = 0; + public ArcaneFiend(Serial serial) : base(serial) + { + } - ControlSlots = 1; - } + public override string CorpseName => "an imp corpse"; + public override double DispelDifficulty => 70.0; + public override double DispelFocus => 20.0; - public ArcaneFiend( Serial serial ) : base( serial ) - { - } + public override PackInstinct PackInstinct => PackInstinct.Daemon; + public override bool BleedImmune => true; //TODO: Verify on OSI. Guide says this. + public override string DefaultName => "an imp"; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int) 0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); - } - } -} + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/Mobiles/NatureFury.cs b/Scripts/Spells/Spellweaving/Mobiles/NatureFury.cs index 521a13917..3eab575b0 100644 --- a/Scripts/Spells/Spellweaving/Mobiles/NatureFury.cs +++ b/Scripts/Spells/Spellweaving/Mobiles/NatureFury.cs @@ -2,84 +2,84 @@ using System; namespace Server.Mobiles { - public class NatureFury : BaseCreature - { - public override bool DeleteCorpseOnDeath => Core.AOS; - public override bool IsHouseSummonable => true; + public class NatureFury : BaseCreature + { + [Constructible] + public NatureFury() + : base(AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4) + { + Body = 0x33; + Hue = 0x4001; - public override double DispelDifficulty => 125.0; - public override double DispelFocus => 90.0; + SetStr(150); + SetDex(150); + SetInt(100); - public override bool BleedImmune => true; - public override Poison PoisonImmune => Poison.Lethal; + SetHits(80); + SetStam(250); + SetMana(0); - public override bool AlwaysMurderer => true; - public override string DefaultName => "a nature's fury"; + SetDamage(6, 8); - [Constructible] - public NatureFury() - : base( AIType.AI_Melee, FightMode.Closest, 10, 1, 0.2, 0.4 ) - { - Body = 0x33; - Hue = 0x4001; + SetDamageType(ResistanceType.Poison, 100); + SetDamageType(ResistanceType.Physical, 0); + SetResistance(ResistanceType.Physical, 90); - SetStr( 150 ); - SetDex( 150 ); - SetInt( 100 ); + SetSkill(SkillName.Wrestling, 90.0); + SetSkill(SkillName.MagicResist, 70.0); + SetSkill(SkillName.Tactics, 100.0); - SetHits( 80 ); - SetStam( 250 ); - SetMana( 0 ); + Fame = 0; + Karma = 0; - SetDamage( 6, 8 ); + ControlSlots = 1; + } - SetDamageType( ResistanceType.Poison, 100 ); - SetDamageType( ResistanceType.Physical, 0 ); - SetResistance( ResistanceType.Physical, 90 ); + public NatureFury(Serial serial) + : base(serial) + { + } - SetSkill( SkillName.Wrestling, 90.0 ); - SetSkill( SkillName.MagicResist, 70.0 ); - SetSkill( SkillName.Tactics, 100.0 ); + public override bool DeleteCorpseOnDeath => Core.AOS; + public override bool IsHouseSummonable => true; - Fame = 0; - Karma = 0; + public override double DispelDifficulty => 125.0; + public override double DispelFocus => 90.0; - ControlSlots = 1; - } + public override bool BleedImmune => true; + public override Poison PoisonImmune => Poison.Lethal; - public override void MoveToWorld( Point3D loc, Map map ) - { - base.MoveToWorld( loc, map ); - Timer.DelayCall( TimeSpan.Zero, DoEffects ); - } + public override bool AlwaysMurderer => true; + public override string DefaultName => "a nature's fury"; - public void DoEffects() - { - FixedParticles( 0x91C, 10, 180, 0x2543, 0, 0, EffectLayer.Waist ); - PlaySound( 0xE ); - PlaySound( 0x1BC ); + public override void MoveToWorld(Point3D loc, Map map) + { + base.MoveToWorld(loc, map); + Timer.DelayCall(TimeSpan.Zero, DoEffects); + } - if ( Alive && !Deleted ) - Timer.DelayCall( TimeSpan.FromSeconds( 7.0 ), DoEffects ); - } + public void DoEffects() + { + FixedParticles(0x91C, 10, 180, 0x2543, 0, 0, EffectLayer.Waist); + PlaySound(0xE); + PlaySound(0x1BC); - public NatureFury( Serial serial ) - : base( serial ) - { - } + if (Alive && !Deleted) + Timer.DelayCall(TimeSpan.FromSeconds(7.0), DoEffects); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - writer.Write( (int)0 ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); + writer.Write(0); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - int version = reader.ReadInt(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); + int version = reader.ReadInt(); - Delete(); - } - } -} + Delete(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/NatureFury.cs b/Scripts/Spells/Spellweaving/NatureFury.cs index 2dbfee766..4cd54376e 100644 --- a/Scripts/Spells/Spellweaving/NatureFury.cs +++ b/Scripts/Spells/Spellweaving/NatureFury.cs @@ -1,121 +1,121 @@ using System; using Server.Mobiles; -using Server.Targeting; using Server.Regions; +using Server.Targeting; namespace Server.Spells.Spellweaving { - public class NatureFurySpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Nature's Fury", "Rauvvrae", - -1, - false - ); + public class NatureFurySpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Nature's Fury", "Rauvvrae", + -1, + false + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public NatureFurySpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 0.0; - public override int RequiredMana => 24; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public NatureFurySpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 0.0; + public override int RequiredMana => 24; - public override bool CheckCast() - { - if ( !base.CheckCast() ) - return false; + public override bool CheckCast() + { + if (!base.CheckCast()) + return false; - if ( ( Caster.Followers + 1 ) > Caster.FollowersMax ) - { - Caster.SendLocalizedMessage( 1049645 ); // You have too many followers to summon that creature. - return false; - } + if (Caster.Followers + 1 > Caster.FollowersMax) + { + Caster.SendLocalizedMessage(1049645); // You have too many followers to summon that creature. + return false; + } - return true; - } + return true; + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D point ) - { - Point3D p = new Point3D( point ); - Map map = Caster.Map; + public void Target(IPoint3D point) + { + Point3D p = new Point3D(point); + Map map = Caster.Map; - if ( map == null ) - return; + if (map == null) + return; - HouseRegion r = Region.Find( p, map ).GetRegion( typeof( HouseRegion ) ) as HouseRegion; + HouseRegion r = Region.Find(p, map).GetRegion(typeof(HouseRegion)) as HouseRegion; - if ( r?.House != null && !r.House.IsFriend( Caster ) ) - return; + if (r?.House != null && !r.House.IsFriend(Caster)) + return; - if ( !map.CanSpawnMobile( p.X, p.Y, p.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - TimeSpan duration = TimeSpan.FromSeconds( Caster.Skills.Spellweaving.Value / 24 + 25 + FocusLevel * 2 ); + if (!map.CanSpawnMobile(p.X, p.Y, p.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + TimeSpan duration = TimeSpan.FromSeconds(Caster.Skills.Spellweaving.Value / 24 + 25 + FocusLevel * 2); - NatureFury nf = new NatureFury(); - BaseCreature.Summon( nf, false, Caster, p, 0x5CB, duration ); + NatureFury nf = new NatureFury(); + BaseCreature.Summon(nf, false, Caster, p, 0x5CB, duration); - new InternalTimer( nf ).Start(); - } + new InternalTimer(nf).Start(); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private NatureFurySpell m_Owner; + private class InternalTarget : Target + { + private NatureFurySpell m_Owner; - public InternalTarget( NatureFurySpell owner ) - : base( 10, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(NatureFurySpell owner) + : base(10, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner?.FinishSequence(); - } - } + protected override void OnTargetFinish(Mobile from) + { + m_Owner?.FinishSequence(); + } + } - private class InternalTimer : Timer - { - private NatureFury m_NatureFury; + private class InternalTimer : Timer + { + private NatureFury m_NatureFury; - public InternalTimer( NatureFury nf ) - : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_NatureFury = nf; - } + public InternalTimer(NatureFury nf) + : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + m_NatureFury = nf; + } - protected override void OnTick() - { - if ( m_NatureFury.Deleted || !m_NatureFury.Alive || m_NatureFury.DamageMin > 20 ) - { - Stop(); - } - else - { - ++m_NatureFury.DamageMin; - ++m_NatureFury.DamageMax; - } - } - } - } -} + protected override void OnTick() + { + if (m_NatureFury.Deleted || !m_NatureFury.Alive || m_NatureFury.DamageMin > 20) + { + Stop(); + } + else + { + ++m_NatureFury.DamageMin; + ++m_NatureFury.DamageMax; + } + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/ReaperForm.cs b/Scripts/Spells/Spellweaving/ReaperForm.cs index 913e1f482..27b47e91c 100644 --- a/Scripts/Spells/Spellweaving/ReaperForm.cs +++ b/Scripts/Spells/Spellweaving/ReaperForm.cs @@ -3,53 +3,53 @@ using Server.Network; namespace Server.Spells.Spellweaving { - public class ReaperFormSpell : ArcaneForm - { - private static SpellInfo m_Info = new SpellInfo( "Reaper Form", "Tarisstree", -1 ); + public class ReaperFormSpell : ArcaneForm + { + private static SpellInfo m_Info = new SpellInfo("Reaper Form", "Tarisstree", -1); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.5 ); + public ReaperFormSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public static void Initialize() - { - EventSink.Login += OnLogin; - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.5); - public static void OnLogin( LoginEventArgs e ) - { - TransformContext context = TransformationSpellHelper.GetContext( e.Mobile ); + public override double RequiredSkill => 24.0; + public override int RequiredMana => 34; - if ( context != null && context.Type == typeof( ReaperFormSpell ) ) - e.Mobile.Send( SpeedControl.WalkSpeed ); - } + public override int Body => 0x11D; - public override double RequiredSkill => 24.0; - public override int RequiredMana => 34; + public override int FireResistOffset => -25; + public override int PhysResistOffset => 5 + FocusLevel; + public override int ColdResistOffset => 5 + FocusLevel; + public override int PoisResistOffset => 5 + FocusLevel; + public override int NrgyResistOffset => 5 + FocusLevel; - public override int Body => 0x11D; + public virtual int SwingSpeedBonus => 10 + FocusLevel; + public virtual int SpellDamageBonus => 10 + FocusLevel; - public override int FireResistOffset => -25; - public override int PhysResistOffset => 5 + FocusLevel; - public override int ColdResistOffset => 5 + FocusLevel; - public override int PoisResistOffset => 5 + FocusLevel; - public override int NrgyResistOffset => 5 + FocusLevel; + public static void Initialize() + { + EventSink.Login += OnLogin; + } - public virtual int SwingSpeedBonus => 10 + FocusLevel; - public virtual int SpellDamageBonus => 10 + FocusLevel; + public static void OnLogin(LoginEventArgs e) + { + TransformContext context = TransformationSpellHelper.GetContext(e.Mobile); - public ReaperFormSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + if (context != null && context.Type == typeof(ReaperFormSpell)) + e.Mobile.Send(SpeedControl.WalkSpeed); + } - public override void DoEffect( Mobile m ) - { - m.PlaySound( 0x1BA ); + public override void DoEffect(Mobile m) + { + m.PlaySound(0x1BA); - m.Send( SpeedControl.WalkSpeed ); - } + m.Send(SpeedControl.WalkSpeed); + } - public override void RemoveEffect( Mobile m ) - { - m.Send( SpeedControl.Disable ); - } - } -} + public override void RemoveEffect(Mobile m) + { + m.Send(SpeedControl.Disable); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/SummonFey.cs b/Scripts/Spells/Spellweaving/SummonFey.cs index 5dd8ca5a9..4d0a660d1 100644 --- a/Scripts/Spells/Spellweaving/SummonFey.cs +++ b/Scripts/Spells/Spellweaving/SummonFey.cs @@ -1,45 +1,46 @@ using System; -using Server.Mobiles; using Server.Engines.MLQuests; +using Server.Mobiles; namespace Server.Spells.Spellweaving { - public class SummonFeySpell : ArcaneSummon - { - private static SpellInfo m_Info = new SpellInfo( - "Summon Fey", "Alalithra", - -1 - ); + public class SummonFeySpell : ArcaneSummon + { + private static SpellInfo m_Info = new SpellInfo( + "Summon Fey", "Alalithra", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + public SummonFeySpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 38.0; - public override int RequiredMana => 10; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public SummonFeySpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 38.0; + public override int RequiredMana => 10; - public override int Sound => 0x217; + public override int Sound => 0x217; - public override bool CheckSequence() - { - Mobile caster = Caster; + public override bool CheckSequence() + { + Mobile caster = Caster; - // This is done after casting completes - if ( caster is PlayerMobile ) - { - MLQuestContext context = MLQuestSystem.GetContext( (PlayerMobile)caster ); + // This is done after casting completes + if (caster is PlayerMobile) + { + MLQuestContext context = MLQuestSystem.GetContext((PlayerMobile)caster); - if ( context == null || !context.SummonFey ) - { - caster.SendLocalizedMessage( 1074563 ); // You haven't forged a friendship with the fey and are unable to summon their aid. - return false; - } - } + if (context == null || !context.SummonFey) + { + caster.SendLocalizedMessage( + 1074563); // You haven't forged a friendship with the fey and are unable to summon their aid. + return false; + } + } - return base.CheckSequence(); - } - } -} + return base.CheckSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/SummonFiend.cs b/Scripts/Spells/Spellweaving/SummonFiend.cs index 9a37d9e28..e3619ca9b 100644 --- a/Scripts/Spells/Spellweaving/SummonFiend.cs +++ b/Scripts/Spells/Spellweaving/SummonFiend.cs @@ -1,45 +1,45 @@ using System; -using Server.Mobiles; using Server.Engines.MLQuests; +using Server.Mobiles; namespace Server.Spells.Spellweaving { - public class SummonFiendSpell : ArcaneSummon - { - private static SpellInfo m_Info = new SpellInfo( - "Summon Fiend", "Nylisstra", - -1 - ); + public class SummonFiendSpell : ArcaneSummon + { + private static SpellInfo m_Info = new SpellInfo( + "Summon Fiend", "Nylisstra", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 2.0 ); + public SummonFiendSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 38.0; - public override int RequiredMana => 10; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(2.0); - public SummonFiendSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 38.0; + public override int RequiredMana => 10; - public override int Sound => 0x216; + public override int Sound => 0x216; - public override bool CheckSequence() - { - Mobile caster = Caster; + public override bool CheckSequence() + { + Mobile caster = Caster; - // This is done after casting completes - if ( caster is PlayerMobile ) - { - MLQuestContext context = MLQuestSystem.GetContext( (PlayerMobile)caster ); + // This is done after casting completes + if (caster is PlayerMobile) + { + MLQuestContext context = MLQuestSystem.GetContext((PlayerMobile)caster); - if ( context == null || !context.SummonFiend ) - { - caster.SendLocalizedMessage( 1074564 ); // You haven't demonstrated mastery to summon a fiend. - return false; - } - } + if (context == null || !context.SummonFiend) + { + caster.SendLocalizedMessage(1074564); // You haven't demonstrated mastery to summon a fiend. + return false; + } + } - return base.CheckSequence(); - } - } -} + return base.CheckSequence(); + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/Thunderstorm.cs b/Scripts/Spells/Spellweaving/Thunderstorm.cs index 2ebaa8809..f8ed838e6 100644 --- a/Scripts/Spells/Spellweaving/Thunderstorm.cs +++ b/Scripts/Spells/Spellweaving/Thunderstorm.cs @@ -3,96 +3,94 @@ using System.Collections.Generic; namespace Server.Spells.Spellweaving { - public class ThunderstormSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( - "Thunderstorm", "Erelonia", - -1 - ); + public class ThunderstormSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo( + "Thunderstorm", "Erelonia", + -1 + ); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 1.5 ); + private static Dictionary m_Table = new Dictionary(); - public override double RequiredSkill => 10.0; - public override int RequiredMana => 32; + public ThunderstormSpell(Mobile caster, Item scroll) + : base(caster, scroll, m_Info) + { + } - public ThunderstormSpell( Mobile caster, Item scroll ) - : base( caster, scroll, m_Info ) - { - } + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(1.5); - public override void OnCast() - { - if ( CheckSequence() ) - { - Caster.PlaySound( 0x5CE ); + public override double RequiredSkill => 10.0; + public override int RequiredMana => 32; - double skill = Caster.Skills[SkillName.Spellweaving].Value; + public override void OnCast() + { + if (CheckSequence()) + { + Caster.PlaySound(0x5CE); - int damage = Math.Max( 11, 10 + (int)(skill / 24) ) + FocusLevel; + double skill = Caster.Skills[SkillName.Spellweaving].Value; - int sdiBonus = AosAttributes.GetValue( Caster, AosAttribute.SpellDamage ); + int damage = Math.Max(11, 10 + (int)(skill / 24)) + FocusLevel; - int pvmDamage = damage * ( 100 + sdiBonus ); - pvmDamage /= 100; + int sdiBonus = AosAttributes.GetValue(Caster, AosAttribute.SpellDamage); - if ( sdiBonus > 15 ) - sdiBonus = 15; + int pvmDamage = damage * (100 + sdiBonus); + pvmDamage /= 100; - int pvpDamage = damage * ( 100 + sdiBonus ); - pvpDamage /= 100; + if (sdiBonus > 15) + sdiBonus = 15; - int range = 2 + FocusLevel; - TimeSpan duration = TimeSpan.FromSeconds( 5 + FocusLevel ); + int pvpDamage = damage * (100 + sdiBonus); + pvpDamage /= 100; - List targets = new List(); + int range = 2 + FocusLevel; + TimeSpan duration = TimeSpan.FromSeconds(5 + FocusLevel); - foreach( Mobile m in Caster.GetMobilesInRange( range ) ) - { - if ( Caster != m && SpellHelper.ValidIndirectTarget( Caster, m ) && Caster.CanBeHarmful( m, false ) && Caster.InLOS( m ) ) - targets.Add( m ); - } + List targets = new List(); - for( int i = 0; i < targets.Count; i++ ) - { - Mobile m = targets[i]; + foreach (Mobile m in Caster.GetMobilesInRange(range)) + if (Caster != m && SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false) && + Caster.InLOS(m)) + targets.Add(m); - Caster.DoHarmful( m ); + for (int i = 0; i < targets.Count; i++) + { + Mobile m = targets[i]; - Spell oldSpell = m.Spell as Spell; + Caster.DoHarmful(m); - SpellHelper.Damage( this, m, ( m.Player && Caster.Player ) ? pvpDamage : pvmDamage, 0, 0, 0, 0, 100 ); + Spell oldSpell = m.Spell as Spell; - if ( oldSpell != null && oldSpell != m.Spell ) - { - if ( !CheckResisted( m ) ) - { - m_Table[m] = Timer.DelayCall( duration, DoExpire, m ); + SpellHelper.Damage(this, m, m.Player && Caster.Player ? pvpDamage : pvmDamage, 0, 0, 0, 0, 100); - BuffInfo.AddBuff( m, new BuffInfo( BuffIcon.Thunderstorm, 1075800, duration, m, GetCastRecoveryMalus( m ) ) ); - } - } - } - } + if (oldSpell != null && oldSpell != m.Spell) + if (!CheckResisted(m)) + { + m_Table[m] = Timer.DelayCall(duration, DoExpire, m); - FinishSequence(); - } + BuffInfo.AddBuff(m, + new BuffInfo(BuffIcon.Thunderstorm, 1075800, duration, m, GetCastRecoveryMalus(m))); + } + } + } - private static Dictionary m_Table = new Dictionary(); + FinishSequence(); + } - public static int GetCastRecoveryMalus( Mobile m ) - { - return m_Table.ContainsKey( m ) ? 6 : 0; - } + public static int GetCastRecoveryMalus(Mobile m) + { + return m_Table.ContainsKey(m) ? 6 : 0; + } - public static void DoExpire( Mobile m ) - { - if (m_Table.TryGetValue( m, out Timer t )) - { - t.Stop(); - m_Table.Remove( m ); + public static void DoExpire(Mobile m) + { + if (m_Table.TryGetValue(m, out Timer t)) + { + t.Stop(); + m_Table.Remove(m); - BuffInfo.RemoveBuff( m, BuffIcon.Thunderstorm ); - } - } - } -} + BuffInfo.RemoveBuff(m, BuffIcon.Thunderstorm); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Spellweaving/WordOfDeath.cs b/Scripts/Spells/Spellweaving/WordOfDeath.cs index 80b07bb01..fa16a9760 100644 --- a/Scripts/Spells/Spellweaving/WordOfDeath.cs +++ b/Scripts/Spells/Spellweaving/WordOfDeath.cs @@ -3,90 +3,89 @@ using Server.Targeting; namespace Server.Spells.Spellweaving { - public class WordOfDeathSpell : ArcanistSpell - { - private static SpellInfo m_Info = new SpellInfo( "Word of Death", "Nyraxle", -1 ); + public class WordOfDeathSpell : ArcanistSpell + { + private static SpellInfo m_Info = new SpellInfo("Word of Death", "Nyraxle", -1); - public override TimeSpan CastDelayBase => TimeSpan.FromSeconds( 3.5 ); + public WordOfDeathSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public override double RequiredSkill => 80.0; - public override int RequiredMana => 50; + public override TimeSpan CastDelayBase => TimeSpan.FromSeconds(3.5); - public WordOfDeathSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override double RequiredSkill => 80.0; + public override int RequiredMana => 50; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - Point3D loc = m.Location; - loc.Z += 50; + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + Point3D loc = m.Location; + loc.Z += 50; - m.PlaySound( 0x211 ); - m.FixedParticles( 0x3779, 1, 30, 0x26EC, 0x3, 0x3, EffectLayer.Waist ); + m.PlaySound(0x211); + m.FixedParticles(0x3779, 1, 30, 0x26EC, 0x3, 0x3, EffectLayer.Waist); - Effects.SendMovingParticles( new Entity( Serial.Zero, loc, m.Map ), new Entity( Serial.Zero, m.Location, m.Map ), 0xF5F, 1, 0, true, false, 0x21, 0x3F, 0x251D, 0, 0, EffectLayer.Head, 0 ); + Effects.SendMovingParticles(new Entity(Serial.Zero, loc, m.Map), new Entity(Serial.Zero, m.Location, m.Map), + 0xF5F, 1, 0, true, false, 0x21, 0x3F, 0x251D, 0, 0, EffectLayer.Head, 0); - double percentage = 0.05 * FocusLevel; + double percentage = 0.05 * FocusLevel; - int damage; + int damage; - if ( !m.Player && (((double)m.Hits / (double)m.HitsMax) < percentage )) - { - damage = 300; - } - else - { - int minDamage = (int)Caster.Skills.Spellweaving.Value / 5; - int maxDamage = (int)Caster.Skills.Spellweaving.Value / 3; - damage = Utility.RandomMinMax(minDamage, maxDamage); - int damageBonus = AosAttributes.GetValue( Caster, AosAttribute.SpellDamage ); - if (m.Player && damageBonus > 15) - damageBonus = 15; - damage *= damageBonus + 100; - damage /= 100; - } + if (!m.Player && m.Hits / (double)m.HitsMax < percentage) + { + damage = 300; + } + else + { + int minDamage = (int)Caster.Skills.Spellweaving.Value / 5; + int maxDamage = (int)Caster.Skills.Spellweaving.Value / 3; + damage = Utility.RandomMinMax(minDamage, maxDamage); + int damageBonus = AosAttributes.GetValue(Caster, AosAttribute.SpellDamage); + if (m.Player && damageBonus > 15) + damageBonus = 15; + damage *= damageBonus + 100; + damage /= 100; + } - int[] types = new int[4]; - types[Utility.Random( types.Length )] = 100; + int[] types = new int[4]; + types[Utility.Random(types.Length)] = 100; - SpellHelper.Damage( this, m, damage, 0, types[0], types[1], types[2], types[3] ); //Chaos damage. Random elemental damage - } + SpellHelper.Damage(this, m, damage, 0, types[0], types[1], types[2], + types[3]); //Chaos damage. Random elemental damage + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private WordOfDeathSpell m_Owner; + public class InternalTarget : Target + { + private WordOfDeathSpell m_Owner; - public InternalTarget( WordOfDeathSpell owner ) : base( 10, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(WordOfDeathSpell owner) : base(10, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile m, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile m, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile m ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile m) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/Bless.cs b/Scripts/Spells/Third/Bless.cs index 14ee8e33f..d0ee6aa6a 100644 --- a/Scripts/Spells/Third/Bless.cs +++ b/Scripts/Spells/Third/Bless.cs @@ -1,89 +1,89 @@ using System; +using Server.Engines.ConPVP; using Server.Targeting; namespace Server.Spells.Third { - public class BlessSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Bless", "Rel Sanct", - 203, - 9061, - Reagent.Garlic, - Reagent.MandrakeRoot - ); + public class BlessSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Bless", "Rel Sanct", + 203, + 9061, + Reagent.Garlic, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Third; + public BlessSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public BlessSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override bool CheckCast() - { - if ( Engines.ConPVP.DuelContext.CheckSuddenDeath( Caster ) ) - { - Caster.SendMessage( 0x22, "You cannot cast this spell when in sudden death." ); - return false; - } + public override bool CheckCast() + { + if (DuelContext.CheckSuddenDeath(Caster)) + { + Caster.SendMessage(0x22, "You cannot cast this spell when in sudden death."); + return false; + } - return base.CheckCast(); - } + return base.CheckCast(); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckBSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckBSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.AddStatBonus( Caster, m, StatType.Str ); SpellHelper.DisableSkillCheck = true; - SpellHelper.AddStatBonus( Caster, m, StatType.Dex ); - SpellHelper.AddStatBonus( Caster, m, StatType.Int ); SpellHelper.DisableSkillCheck = false; + SpellHelper.AddStatBonus(Caster, m, StatType.Str); + SpellHelper.DisableSkillCheck = true; + SpellHelper.AddStatBonus(Caster, m, StatType.Dex); + SpellHelper.AddStatBonus(Caster, m, StatType.Int); + SpellHelper.DisableSkillCheck = false; - m.FixedParticles( 0x373A, 10, 15, 5018, EffectLayer.Waist ); - m.PlaySound( 0x1EA ); + m.FixedParticles(0x373A, 10, 15, 5018, EffectLayer.Waist); + m.PlaySound(0x1EA); - int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, false) * 100); - TimeSpan length = SpellHelper.GetDuration(Caster, m); + int percentage = (int)(SpellHelper.GetOffsetScalar(Caster, m, false) * 100); + TimeSpan length = SpellHelper.GetDuration(Caster, m); - string args = $"{percentage}\t{percentage}\t{percentage}"; + string args = $"{percentage}\t{percentage}\t{percentage}"; - BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Bless, 1075847, 1075848, length, m, args.ToString())); - } + BuffInfo.AddBuff(m, new BuffInfo(BuffIcon.Bless, 1075847, 1075848, length, m, args)); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private BlessSpell m_Owner; + private class InternalTarget : Target + { + private BlessSpell m_Owner; - public InternalTarget( BlessSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Beneficial ) - { - m_Owner = owner; - } + public InternalTarget(BlessSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Beneficial) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/Fireball.cs b/Scripts/Spells/Third/Fireball.cs index 75cd90a5b..a9f1c03a5 100644 --- a/Scripts/Spells/Third/Fireball.cs +++ b/Scripts/Spells/Third/Fireball.cs @@ -2,90 +2,90 @@ using Server.Targeting; namespace Server.Spells.Third { - public class FireballSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Fireball", "Vas Flam", - 203, - 9041, - Reagent.BlackPearl - ); + public class FireballSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Fireball", "Vas Flam", + 203, + 9041, + Reagent.BlackPearl + ); - public override SpellCircle Circle => SpellCircle.Third; + public FireballSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public FireballSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override bool DelayedDamage => true; - public override bool DelayedDamage => true; + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - Mobile source = Caster; + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + Mobile source = Caster; - SpellHelper.Turn( source, m ); + SpellHelper.Turn(source, m); - SpellHelper.CheckReflect( (int)Circle, ref source, ref m ); + SpellHelper.CheckReflect((int)Circle, ref source, ref m); - double damage; + double damage; - if ( Core.AOS ) - { - damage = GetNewAosDamage( 19, 1, 5, m ); - } - else - { - damage = Utility.Random( 10, 7 ); + if (Core.AOS) + { + damage = GetNewAosDamage(19, 1, 5, m); + } + else + { + damage = Utility.Random(10, 7); - if ( CheckResisted( m ) ) - { - damage *= 0.75; + if (CheckResisted(m)) + { + damage *= 0.75; - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } - damage *= GetDamageScalar( m ); - } + damage *= GetDamageScalar(m); + } - source.MovingParticles( m, 0x36D4, 7, 0, false, true, 9502, 4019, 0x160 ); - source.PlaySound( Core.AOS ? 0x15E : 0x44B ); + source.MovingParticles(m, 0x36D4, 7, 0, false, true, 9502, 4019, 0x160); + source.PlaySound(Core.AOS ? 0x15E : 0x44B); - SpellHelper.Damage( this, m, damage, 0, 100, 0, 0, 0 ); - } + SpellHelper.Damage(this, m, damage, 0, 100, 0, 0, 0); + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private FireballSpell m_Owner; + private class InternalTarget : Target + { + private FireballSpell m_Owner; - public InternalTarget( FireballSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + public InternalTarget(FireballSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - m_Owner.Target( (Mobile)o ); - } + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) + m_Owner.Target((Mobile)o); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/MagicLock.cs b/Scripts/Spells/Third/MagicLock.cs index 4272f915b..bd6230312 100644 --- a/Scripts/Spells/Third/MagicLock.cs +++ b/Scripts/Spells/Third/MagicLock.cs @@ -1,86 +1,87 @@ -using Server.Targeting; -using Server.Network; using Server.Items; +using Server.Multis; +using Server.Network; +using Server.Targeting; namespace Server.Spells.Third { - public class MagicLockSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Magic Lock", "An Por", - 215, - 9001, - Reagent.Garlic, - Reagent.Bloodmoss, - Reagent.SulfurousAsh - ); + public class MagicLockSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Magic Lock", "An Por", + 215, + 9001, + Reagent.Garlic, + Reagent.Bloodmoss, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Third; + public MagicLockSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public MagicLockSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( LockableContainer targ ) - { - if ( Multis.BaseHouse.CheckLockedDownOrSecured( targ ) ) - { - // You cannot cast this on a locked down item. - Caster.LocalOverheadMessage( MessageType.Regular, 0x22, 501761 ); - } - else if ( targ.Locked || targ.LockLevel == 0 || targ is ParagonChest ) - { - // Target must be an unlocked chest. - Caster.SendLocalizedMessage( 501762 ); - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, targ ); + public void Target(LockableContainer targ) + { + if (BaseHouse.CheckLockedDownOrSecured(targ)) + { + // You cannot cast this on a locked down item. + Caster.LocalOverheadMessage(MessageType.Regular, 0x22, 501761); + } + else if (targ.Locked || targ.LockLevel == 0 || targ is ParagonChest) + { + // Target must be an unlocked chest. + Caster.SendLocalizedMessage(501762); + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, targ); - Point3D loc = targ.GetWorldLocation(); + Point3D loc = targ.GetWorldLocation(); - Effects.SendLocationParticles( - EffectItem.Create( loc, targ.Map, EffectItem.DefaultDuration ), - 0x376A, 9, 32, 5020 ); + Effects.SendLocationParticles( + EffectItem.Create(loc, targ.Map, EffectItem.DefaultDuration), + 0x376A, 9, 32, 5020); - Effects.PlaySound( loc, targ.Map, 0x1FA ); + Effects.PlaySound(loc, targ.Map, 0x1FA); - // The chest is now locked! - Caster.LocalOverheadMessage( MessageType.Regular, 0x3B2, 501763 ); + // The chest is now locked! + Caster.LocalOverheadMessage(MessageType.Regular, 0x3B2, 501763); - targ.LockLevel = -255; // signal magic lock - targ.Locked = true; - } + targ.LockLevel = -255; // signal magic lock + targ.Locked = true; + } - FinishSequence(); - } + FinishSequence(); + } - private class InternalTarget : Target - { - private MagicLockSpell m_Owner; + private class InternalTarget : Target + { + private MagicLockSpell m_Owner; - public InternalTarget( MagicLockSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(MagicLockSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is LockableContainer ) - m_Owner.Target( (LockableContainer)o ); - else - from.SendLocalizedMessage( 501762 ); // Target must be an unlocked chest. - } + protected override void OnTarget(Mobile from, object o) + { + if (o is LockableContainer) + m_Owner.Target((LockableContainer)o); + else + from.SendLocalizedMessage(501762); // Target must be an unlocked chest. + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/Poison.cs b/Scripts/Spells/Third/Poison.cs index 870b04c1e..10ec66e50 100644 --- a/Scripts/Spells/Third/Poison.cs +++ b/Scripts/Spells/Third/Poison.cs @@ -1,144 +1,145 @@ +using Server.Mobiles; using Server.Targeting; namespace Server.Spells.Third { - public class PoisonSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Poison", "In Nox", - 203, - 9051, - Reagent.Nightshade - ); + public class PoisonSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Poison", "In Nox", + 203, + 9051, + Reagent.Nightshade + ); - public override SpellCircle Circle => SpellCircle.Third; + public PoisonSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public PoisonSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( Mobile m ) - { - if ( !Caster.CanSee( m ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( CheckHSequence( m ) ) - { - SpellHelper.Turn( Caster, m ); + public void Target(Mobile m) + { + if (!Caster.CanSee(m)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (CheckHSequence(m)) + { + SpellHelper.Turn(Caster, m); - SpellHelper.CheckReflect( (int)Circle, Caster, ref m ); + SpellHelper.CheckReflect((int)Circle, Caster, ref m); - m.Spell?.OnCasterHurt(); + m.Spell?.OnCasterHurt(); - m.Paralyzed = false; + m.Paralyzed = false; - if ( CheckResisted( m ) ) - { - m.SendLocalizedMessage( 501783 ); // You feel yourself resisting magical energy. - } - else - { - int level; + if (CheckResisted(m)) + { + m.SendLocalizedMessage(501783); // You feel yourself resisting magical energy. + } + else + { + int level; - if ( Core.AOS ) - { - if ( Caster.InRange( m, 2 ) ) - { - int total = (Caster.Skills.Magery.Fixed + Caster.Skills.Poisoning.Fixed) / 2; + if (Core.AOS) + { + if (Caster.InRange(m, 2)) + { + int total = (Caster.Skills.Magery.Fixed + Caster.Skills.Poisoning.Fixed) / 2; - if ( total >= 1000 ) - level = 3; - else if ( total > 850 ) - level = 2; - else if ( total > 650 ) - level = 1; - else - level = 0; - } - else - { - level = 0; - } - } - else - { - //double total = Caster.Skills[SkillName.Magery].Value + Caster.Skills[SkillName.Poisoning].Value; + if (total >= 1000) + level = 3; + else if (total > 850) + level = 2; + else if (total > 650) + level = 1; + else + level = 0; + } + else + { + level = 0; + } + } + else + { + //double total = Caster.Skills[SkillName.Magery].Value + Caster.Skills[SkillName.Poisoning].Value; - #region Dueling - double total = Caster.Skills[SkillName.Magery].Value; + #region Dueling - if ( Caster is Mobiles.PlayerMobile ) - { - Mobiles.PlayerMobile pm = (Mobiles.PlayerMobile)Caster; + double total = Caster.Skills[SkillName.Magery].Value; - if ( pm.DuelContext != null && pm.DuelContext.Started && !pm.DuelContext.Finished && !pm.DuelContext.Ruleset.GetOption( "Skills", "Poisoning" ) ) - { - } - else - { - total += Caster.Skills[SkillName.Poisoning].Value; - } - } - else - { - total += Caster.Skills[SkillName.Poisoning].Value; - } - #endregion + if (Caster is PlayerMobile) + { + PlayerMobile pm = (PlayerMobile)Caster; - double dist = Caster.GetDistanceToSqrt( m ); + if (pm.DuelContext != null && pm.DuelContext.Started && !pm.DuelContext.Finished && + !pm.DuelContext.Ruleset.GetOption("Skills", "Poisoning")) + { + } + else + { + total += Caster.Skills[SkillName.Poisoning].Value; + } + } + else + { + total += Caster.Skills[SkillName.Poisoning].Value; + } - if ( dist >= 3.0 ) - total -= (dist - 3.0) * 10.0; + #endregion - if ( total >= 200.0 && 1 > Utility.Random( 10 ) ) - level = 3; - else if ( total > (Core.AOS ? 170.1 : 170.0) ) - level = 2; - else if ( total > (Core.AOS ? 130.1 : 130.0) ) - level = 1; - else - level = 0; - } + double dist = Caster.GetDistanceToSqrt(m); - m.ApplyPoison( Caster, Poison.GetPoison( level ) ); - } + if (dist >= 3.0) + total -= (dist - 3.0) * 10.0; - m.FixedParticles( 0x374A, 10, 15, 5021, EffectLayer.Waist ); - m.PlaySound( 0x205 ); + if (total >= 200.0 && 1 > Utility.Random(10)) + level = 3; + else if (total > (Core.AOS ? 170.1 : 170.0)) + level = 2; + else if (total > (Core.AOS ? 130.1 : 130.0)) + level = 1; + else + level = 0; + } - HarmfulSpell( m ); - } + m.ApplyPoison(Caster, Poison.GetPoison(level)); + } - FinishSequence(); - } + m.FixedParticles(0x374A, 10, 15, 5021, EffectLayer.Waist); + m.PlaySound(0x205); - private class InternalTarget : Target - { - private PoisonSpell m_Owner; + HarmfulSpell(m); + } - public InternalTarget( PoisonSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.Harmful ) - { - m_Owner = owner; - } + FinishSequence(); + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is Mobile ) - { - m_Owner.Target( (Mobile)o ); - } - } + private class InternalTarget : Target + { + private PoisonSpell m_Owner; - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + public InternalTarget(PoisonSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.Harmful) + { + m_Owner = owner; + } + + protected override void OnTarget(Mobile from, object o) + { + if (o is Mobile) m_Owner.Target((Mobile)o); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/Telekinesis.cs b/Scripts/Spells/Third/Telekinesis.cs index 60cb7c546..cc6dd8d04 100644 --- a/Scripts/Spells/Third/Telekinesis.cs +++ b/Scripts/Spells/Third/Telekinesis.cs @@ -1,106 +1,107 @@ -using Server.Targeting; using Server.Items; +using Server.Targeting; namespace Server.Spells.Third { - public class TelekinesisSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Telekinesis", "Ort Por Ylem", - 203, - 9031, - Reagent.Bloodmoss, - Reagent.MandrakeRoot - ); + public class TelekinesisSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Telekinesis", "Ort Por Ylem", + 203, + 9031, + Reagent.Bloodmoss, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Third; + public TelekinesisSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public TelekinesisSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( ITelekinesisable obj ) - { - if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, obj ); + public void Target(ITelekinesisable obj) + { + if (CheckSequence()) + { + SpellHelper.Turn(Caster, obj); - obj.OnTelekinesis( Caster ); - } + obj.OnTelekinesis(Caster); + } - FinishSequence(); - } + FinishSequence(); + } - public void Target( Container item ) - { - if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, item ); + public void Target(Container item) + { + if (CheckSequence()) + { + SpellHelper.Turn(Caster, item); - object root = item.RootParent; + object root = item.RootParent; - if ( !item.IsAccessibleTo( Caster ) ) - { - item.OnDoubleClickNotAccessible( Caster ); - } - else if ( !item.CheckItemUse( Caster, item ) ) - { - } - else if ( root is Mobile && root != Caster ) - { - item.OnSnoop( Caster ); - } - else if ( item is Corpse && !((Corpse)item).CheckLoot( Caster, null ) ) - { - } - else if ( Caster.Region.OnDoubleClick( Caster, item ) ) - { - Effects.SendLocationParticles( EffectItem.Create( item.Location, item.Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5022 ); - Effects.PlaySound( item.Location, item.Map, 0x1F5 ); + if (!item.IsAccessibleTo(Caster)) + { + item.OnDoubleClickNotAccessible(Caster); + } + else if (!item.CheckItemUse(Caster, item)) + { + } + else if (root is Mobile && root != Caster) + { + item.OnSnoop(Caster); + } + else if (item is Corpse && !((Corpse)item).CheckLoot(Caster, null)) + { + } + else if (Caster.Region.OnDoubleClick(Caster, item)) + { + Effects.SendLocationParticles(EffectItem.Create(item.Location, item.Map, EffectItem.DefaultDuration), + 0x376A, 9, 32, 5022); + Effects.PlaySound(item.Location, item.Map, 0x1F5); - item.OnItemUsed( Caster, item ); - } - } + item.OnItemUsed(Caster, item); + } + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private TelekinesisSpell m_Owner; + public class InternalTarget : Target + { + private TelekinesisSpell m_Owner; - public InternalTarget( TelekinesisSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(TelekinesisSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - if ( o is ITelekinesisable ) - m_Owner.Target( (ITelekinesisable)o ); - else if ( o is Container ) - m_Owner.Target( (Container)o ); - else - from.SendLocalizedMessage( 501857 ); // This spell won't work on that! - } + protected override void OnTarget(Mobile from, object o) + { + if (o is ITelekinesisable) + m_Owner.Target((ITelekinesisable)o); + else if (o is Container) + m_Owner.Target((Container)o); + else + from.SendLocalizedMessage(501857); // This spell won't work on that! + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } } namespace Server { - public interface ITelekinesisable : IPoint3D - { - void OnTelekinesis( Mobile from ); - } -} + public interface ITelekinesisable : IPoint3D + { + void OnTelekinesis(Mobile from); + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/Teleport.cs b/Scripts/Spells/Third/Teleport.cs index 285549a1e..4999d9768 100644 --- a/Scripts/Spells/Third/Teleport.cs +++ b/Scripts/Spells/Third/Teleport.cs @@ -1,139 +1,145 @@ -using Server.Targeting; -using Server.Regions; +using Server.Factions; using Server.Items; +using Server.Misc; +using Server.Regions; +using Server.Spells.Fifth; +using Server.Spells.Fourth; +using Server.Spells.Sixth; +using Server.Targeting; namespace Server.Spells.Third { - public class TeleportSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Teleport", "Rel Por", - 215, - 9031, - Reagent.Bloodmoss, - Reagent.MandrakeRoot - ); + public class TeleportSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Teleport", "Rel Por", + 215, + 9031, + Reagent.Bloodmoss, + Reagent.MandrakeRoot + ); - public override SpellCircle Circle => SpellCircle.Third; + public TeleportSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public TeleportSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override bool CheckCast() - { - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - return false; - } + public override bool CheckCast() + { + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + return false; + } - if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - return false; - } + if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + return false; + } - return SpellHelper.CheckTravel( Caster, TravelCheckType.TeleportFrom ); - } + return SpellHelper.CheckTravel(Caster, TravelCheckType.TeleportFrom); + } - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - IPoint3D orig = p; - Map map = Caster.Map; + public void Target(IPoint3D p) + { + IPoint3D orig = p; + Map map = Caster.Map; - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - Point3D from = Caster.Location; - Point3D to = new Point3D( p ); + Point3D from = Caster.Location; + Point3D to = new Point3D(p); - if ( Factions.Sigil.ExistsOn( Caster ) ) - { - Caster.SendLocalizedMessage( 1061632 ); // You can't do that while carrying the sigil. - } - else if ( Misc.WeightOverloading.IsOverloaded( Caster ) ) - { - Caster.SendLocalizedMessage( 502359, "", 0x22 ); // Thou art too encumbered to move. - } - else if ( !SpellHelper.CheckTravel( Caster, TravelCheckType.TeleportFrom ) ) - { - } - else if ( !SpellHelper.CheckTravel( Caster, map, to, TravelCheckType.TeleportTo ) ) - { - } - else if ( map == null || !map.CanSpawnMobile( p.X, p.Y, p.Z ) ) - { - Caster.SendLocalizedMessage( 501942 ); // That location is blocked. - } - else if ( SpellHelper.CheckMulti( to, map ) ) - { - Caster.SendLocalizedMessage( 502831 ); // Cannot teleport to that spot. - } - else if ( Region.Find( to, map ).GetRegion( typeof( HouseRegion ) ) != null ) - { - Caster.SendLocalizedMessage( 502829 ); // Cannot teleport to that spot. - } - else if ( CheckSequence() ) - { - SpellHelper.Turn( Caster, orig ); + if (Sigil.ExistsOn(Caster)) + { + Caster.SendLocalizedMessage(1061632); // You can't do that while carrying the sigil. + } + else if (WeightOverloading.IsOverloaded(Caster)) + { + Caster.SendLocalizedMessage(502359, "", 0x22); // Thou art too encumbered to move. + } + else if (!SpellHelper.CheckTravel(Caster, TravelCheckType.TeleportFrom)) + { + } + else if (!SpellHelper.CheckTravel(Caster, map, to, TravelCheckType.TeleportTo)) + { + } + else if (map == null || !map.CanSpawnMobile(p.X, p.Y, p.Z)) + { + Caster.SendLocalizedMessage(501942); // That location is blocked. + } + else if (SpellHelper.CheckMulti(to, map)) + { + Caster.SendLocalizedMessage(502831); // Cannot teleport to that spot. + } + else if (Region.Find(to, map).GetRegion(typeof(HouseRegion)) != null) + { + Caster.SendLocalizedMessage(502829); // Cannot teleport to that spot. + } + else if (CheckSequence()) + { + SpellHelper.Turn(Caster, orig); - Mobile m = Caster; + Mobile m = Caster; - m.Location = to; - m.ProcessDelta(); + m.Location = to; + m.ProcessDelta(); - if ( m.Player ) - { - Effects.SendLocationParticles( EffectItem.Create( from, m.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 2023 ); - Effects.SendLocationParticles( EffectItem.Create( to, m.Map, EffectItem.DefaultDuration ), 0x3728, 10, 10, 5023 ); - } - else - { - m.FixedParticles( 0x376A, 9, 32, 0x13AF, EffectLayer.Waist ); - } + if (m.Player) + { + Effects.SendLocationParticles(EffectItem.Create(from, m.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 2023); + Effects.SendLocationParticles(EffectItem.Create(to, m.Map, EffectItem.DefaultDuration), 0x3728, 10, 10, + 5023); + } + else + { + m.FixedParticles(0x376A, 9, 32, 0x13AF, EffectLayer.Waist); + } - m.PlaySound( 0x1FE ); + m.PlaySound(0x1FE); - IPooledEnumerable eable = m.GetItemsInRange( 0 ); + IPooledEnumerable eable = m.GetItemsInRange(0); - foreach ( Item item in eable ) - { - if ( item is Sixth.ParalyzeFieldSpell.InternalItem || item is Fifth.PoisonFieldSpell.InternalItem || item is Fourth.FireFieldSpell.FireFieldItem ) - item.OnMoveOver( m ); - } + foreach (Item item in eable) + if (item is ParalyzeFieldSpell.InternalItem || item is PoisonFieldSpell.InternalItem || + item is FireFieldSpell.FireFieldItem) + item.OnMoveOver(m); - eable.Free(); - } + eable.Free(); + } - FinishSequence(); - } + FinishSequence(); + } - public class InternalTarget : Target - { - private TeleportSpell m_Owner; + public class InternalTarget : Target + { + private TeleportSpell m_Owner; - public InternalTarget( TeleportSpell owner ) : base( Core.ML ? 11 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(TeleportSpell owner) : base(Core.ML ? 11 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - m_Owner.Target( p ); - } + if (p != null) + m_Owner.Target(p); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/Unlock.cs b/Scripts/Spells/Third/Unlock.cs index a8a773c81..164be8f0f 100644 --- a/Scripts/Spells/Third/Unlock.cs +++ b/Scripts/Spells/Third/Unlock.cs @@ -1,88 +1,109 @@ -using Server.Targeting; -using Server.Network; using Server.Items; +using Server.Multis; +using Server.Network; +using Server.Targeting; namespace Server.Spells.Third { - public class UnlockSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Unlock Spell", "Ex Por", - 215, - 9001, - Reagent.Bloodmoss, - Reagent.SulfurousAsh - ); + public class UnlockSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Unlock Spell", "Ex Por", + 215, + 9001, + Reagent.Bloodmoss, + Reagent.SulfurousAsh + ); - public override SpellCircle Circle => SpellCircle.Third; + public UnlockSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public UnlockSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - private class InternalTarget : Target - { - private UnlockSpell m_Owner; + private class InternalTarget : Target + { + private UnlockSpell m_Owner; - public InternalTarget( UnlockSpell owner ) : base( Core.ML ? 10 : 12, false, TargetFlags.None ) - { - m_Owner = owner; - } + public InternalTarget(UnlockSpell owner) : base(Core.ML ? 10 : 12, false, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D loc = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D loc = o as IPoint3D; - if ( loc == null ) - return; + if (loc == null) + return; - if ( m_Owner.CheckSequence() ) { - SpellHelper.Turn( from, o ); + if (m_Owner.CheckSequence()) + { + SpellHelper.Turn(from, o); - Effects.SendLocationParticles( EffectItem.Create( new Point3D( loc ), from.Map, EffectItem.DefaultDuration ), 0x376A, 9, 32, 5024 ); + Effects.SendLocationParticles(EffectItem.Create(new Point3D(loc), from.Map, EffectItem.DefaultDuration), + 0x376A, 9, 32, 5024); - Effects.PlaySound( loc, from.Map, 0x1FF ); + Effects.PlaySound(loc, from.Map, 0x1FF); - if ( o is Mobile ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 503101 ); // That did not need to be unlocked. - else if ( !( o is LockableContainer ) ) - from.SendLocalizedMessage( 501666 ); // You can't unlock that! - else { - LockableContainer cont = (LockableContainer)o; + if (o is Mobile) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 503101); // That did not need to be unlocked. + } + else if (!(o is LockableContainer)) + { + from.SendLocalizedMessage(501666); // You can't unlock that! + } + else + { + LockableContainer cont = (LockableContainer)o; - if ( Multis.BaseHouse.CheckSecured( cont ) ) - from.SendLocalizedMessage( 503098 ); // You cannot cast this on a secure item. - else if ( !cont.Locked ) - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 503101 ); // That did not need to be unlocked. - else if ( cont.LockLevel == 0 ) - from.SendLocalizedMessage( 501666 ); // You can't unlock that! - else { - int level = (int)(from.Skills[SkillName.Magery].Value * 0.8) - 4; + if (BaseHouse.CheckSecured(cont)) + { + from.SendLocalizedMessage(503098); // You cannot cast this on a secure item. + } + else if (!cont.Locked) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 503101); // That did not need to be unlocked. + } + else if (cont.LockLevel == 0) + { + from.SendLocalizedMessage(501666); // You can't unlock that! + } + else + { + int level = (int)(from.Skills[SkillName.Magery].Value * 0.8) - 4; - if ( level >= cont.RequiredSkill && !(cont is TreasureMapChest && ((TreasureMapChest)cont).Level > 2) ) { - cont.Locked = false; + if (level >= cont.RequiredSkill && + !(cont is TreasureMapChest && ((TreasureMapChest)cont).Level > 2)) + { + cont.Locked = false; - if ( cont.LockLevel == -255 ) - cont.LockLevel = cont.RequiredSkill - 10; - } - else - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 503099 ); // My spell does not seem to have an effect on that lock. - } - } - } + if (cont.LockLevel == -255) + cont.LockLevel = cont.RequiredSkill - 10; + } + else + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, + 503099); // My spell does not seem to have an effect on that lock. + } + } + } + } - m_Owner.FinishSequence(); - } + m_Owner.FinishSequence(); + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/Third/WallOfStone.cs b/Scripts/Spells/Third/WallOfStone.cs index 49eccd666..6d4c0302e 100644 --- a/Scripts/Spells/Third/WallOfStone.cs +++ b/Scripts/Spells/Third/WallOfStone.cs @@ -1,223 +1,216 @@ using System; -using Server.Targeting; using Server.Misc; using Server.Mobiles; +using Server.Targeting; namespace Server.Spells.Third { - public class WallOfStoneSpell : MagerySpell - { - private static SpellInfo m_Info = new SpellInfo( - "Wall of Stone", "In Sanct Ylem", - 227, - 9011, - false, - Reagent.Bloodmoss, - Reagent.Garlic - ); + public class WallOfStoneSpell : MagerySpell + { + private static SpellInfo m_Info = new SpellInfo( + "Wall of Stone", "In Sanct Ylem", + 227, + 9011, + false, + Reagent.Bloodmoss, + Reagent.Garlic + ); - public override SpellCircle Circle => SpellCircle.Third; + public WallOfStoneSpell(Mobile caster, Item scroll) : base(caster, scroll, m_Info) + { + } - public WallOfStoneSpell( Mobile caster, Item scroll ) : base( caster, scroll, m_Info ) - { - } + public override SpellCircle Circle => SpellCircle.Third; - public override void OnCast() - { - Caster.Target = new InternalTarget( this ); - } + public override void OnCast() + { + Caster.Target = new InternalTarget(this); + } - public void Target( IPoint3D p ) - { - if ( !Caster.CanSee( p ) ) - { - Caster.SendLocalizedMessage( 500237 ); // Target can not be seen. - } - else if ( SpellHelper.CheckTown( p, Caster ) && CheckSequence() ) - { - SpellHelper.Turn( Caster, p ); + public void Target(IPoint3D p) + { + if (!Caster.CanSee(p)) + { + Caster.SendLocalizedMessage(500237); // Target can not be seen. + } + else if (SpellHelper.CheckTown(p, Caster) && CheckSequence()) + { + SpellHelper.Turn(Caster, p); - SpellHelper.GetSurfaceTop( ref p ); + SpellHelper.GetSurfaceTop(ref p); - int dx = Caster.Location.X - p.X; - int dy = Caster.Location.Y - p.Y; - int rx = (dx - dy) * 44; - int ry = (dx + dy) * 44; + int dx = Caster.Location.X - p.X; + int dy = Caster.Location.Y - p.Y; + int rx = (dx - dy) * 44; + int ry = (dx + dy) * 44; - bool eastToWest; + bool eastToWest; - if ( rx >= 0 && ry >= 0 ) - { - eastToWest = false; - } - else if ( rx >= 0 ) - { - eastToWest = true; - } - else if ( ry >= 0 ) - { - eastToWest = true; - } - else - { - eastToWest = false; - } + if (rx >= 0 && ry >= 0) + eastToWest = false; + else if (rx >= 0) + eastToWest = true; + else if (ry >= 0) + eastToWest = true; + else + eastToWest = false; - Effects.PlaySound( p, Caster.Map, 0x1F6 ); + Effects.PlaySound(p, Caster.Map, 0x1F6); - for ( int i = -1; i <= 1; ++i ) - { - Point3D loc = new Point3D( eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z ); - bool canFit = SpellHelper.AdjustField( ref loc, Caster.Map, 22, true ); + for (int i = -1; i <= 1; ++i) + { + Point3D loc = new Point3D(eastToWest ? p.X + i : p.X, eastToWest ? p.Y : p.Y + i, p.Z); + bool canFit = SpellHelper.AdjustField(ref loc, Caster.Map, 22, true); - //Effects.SendLocationParticles( EffectItem.Create( loc, Caster.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 5025 ); + //Effects.SendLocationParticles( EffectItem.Create( loc, Caster.Map, EffectItem.DefaultDuration ), 0x376A, 9, 10, 5025 ); - if ( !canFit ) - continue; + if (!canFit) + continue; - Item item = new InternalItem( loc, Caster.Map, Caster ); + Item item = new InternalItem(loc, Caster.Map, Caster); - Effects.SendLocationParticles( item, 0x376A, 9, 10, 5025 ); + Effects.SendLocationParticles(item, 0x376A, 9, 10, 5025); - //new InternalItem( loc, Caster.Map, Caster ); - } - } + //new InternalItem( loc, Caster.Map, Caster ); + } + } - FinishSequence(); - } + FinishSequence(); + } - [DispellableField] - private class InternalItem : Item - { - private Timer m_Timer; - private DateTime m_End; - private Mobile m_Caster; + [DispellableField] + private class InternalItem : Item + { + private Mobile m_Caster; + private DateTime m_End; + private Timer m_Timer; - public override bool BlocksFit => true; + public InternalItem(Point3D loc, Map map, Mobile caster) : base(0x82) + { + Visible = false; + Movable = false; - public InternalItem( Point3D loc, Map map, Mobile caster ) : base( 0x82 ) - { - Visible = false; - Movable = false; + MoveToWorld(loc, map); - MoveToWorld( loc, map ); + m_Caster = caster; - m_Caster = caster; + if (caster.InLOS(this)) + Visible = true; + else + Delete(); - if ( caster.InLOS( this ) ) - Visible = true; - else - Delete(); + if (Deleted) + return; - if ( Deleted ) - return; + m_Timer = new InternalTimer(this, TimeSpan.FromSeconds(10.0)); + m_Timer.Start(); - m_Timer = new InternalTimer( this, TimeSpan.FromSeconds( 10.0 ) ); - m_Timer.Start(); + m_End = DateTime.UtcNow + TimeSpan.FromSeconds(10.0); + } - m_End = DateTime.UtcNow + TimeSpan.FromSeconds( 10.0 ); - } + public InternalItem(Serial serial) : base(serial) + { + } - public InternalItem( Serial serial ) : base( serial ) - { - } + public override bool BlocksFit => true; - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version + writer.Write(1); // version - writer.WriteDeltaTime( m_End ); - } + writer.WriteDeltaTime(m_End); + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - switch ( version ) - { - case 1: - { - m_End = reader.ReadDeltaTime(); + switch (version) + { + case 1: + { + m_End = reader.ReadDeltaTime(); - m_Timer = new InternalTimer( this, m_End - DateTime.UtcNow ); - m_Timer.Start(); + m_Timer = new InternalTimer(this, m_End - DateTime.UtcNow); + m_Timer.Start(); - break; - } - case 0: - { - TimeSpan duration = TimeSpan.FromSeconds( 10.0 ); + break; + } + case 0: + { + TimeSpan duration = TimeSpan.FromSeconds(10.0); - m_Timer = new InternalTimer( this, duration ); - m_Timer.Start(); + m_Timer = new InternalTimer(this, duration); + m_Timer.Start(); - m_End = DateTime.UtcNow + duration; + m_End = DateTime.UtcNow + duration; - break; - } - } - } + break; + } + } + } - public override bool OnMoveOver( Mobile m ) - { - int noto; + public override bool OnMoveOver(Mobile m) + { + int noto; - if ( m is PlayerMobile ) - { - noto = Notoriety.Compute( m_Caster, m ); - if ( noto == Notoriety.Enemy || noto == Notoriety.Ally ) - return false; - } - return base.OnMoveOver( m ); - } + if (m is PlayerMobile) + { + noto = Notoriety.Compute(m_Caster, m); + if (noto == Notoriety.Enemy || noto == Notoriety.Ally) + return false; + } - public override void OnAfterDelete() - { - base.OnAfterDelete(); + return base.OnMoveOver(m); + } - m_Timer?.Stop(); - } + public override void OnAfterDelete() + { + base.OnAfterDelete(); - private class InternalTimer : Timer - { - private InternalItem m_Item; + m_Timer?.Stop(); + } - public InternalTimer( InternalItem item, TimeSpan duration ) : base( duration ) - { - Priority = TimerPriority.OneSecond; - m_Item = item; - } + private class InternalTimer : Timer + { + private InternalItem m_Item; - protected override void OnTick() - { - m_Item.Delete(); - } - } - } + public InternalTimer(InternalItem item, TimeSpan duration) : base(duration) + { + Priority = TimerPriority.OneSecond; + m_Item = item; + } - private class InternalTarget : Target - { - private WallOfStoneSpell m_Owner; + protected override void OnTick() + { + m_Item.Delete(); + } + } + } - public InternalTarget( WallOfStoneSpell owner ) : base( Core.ML ? 10 : 12, true, TargetFlags.None ) - { - m_Owner = owner; - } + private class InternalTarget : Target + { + private WallOfStoneSpell m_Owner; - protected override void OnTarget( Mobile from, object o ) - { - if ( o is IPoint3D ) - m_Owner.Target( (IPoint3D)o ); - } + public InternalTarget(WallOfStoneSpell owner) : base(Core.ML ? 10 : 12, true, TargetFlags.None) + { + m_Owner = owner; + } - protected override void OnTargetFinish( Mobile from ) - { - m_Owner.FinishSequence(); - } - } - } -} + protected override void OnTarget(Mobile from, object o) + { + if (o is IPoint3D) + m_Owner.Target((IPoint3D)o); + } + + protected override void OnTargetFinish(Mobile from) + { + m_Owner.FinishSequence(); + } + } + } +} \ No newline at end of file diff --git a/Scripts/Spells/UnsummonTimer.cs b/Scripts/Spells/UnsummonTimer.cs index b20ed4d18..994d48243 100644 --- a/Scripts/Spells/UnsummonTimer.cs +++ b/Scripts/Spells/UnsummonTimer.cs @@ -3,22 +3,22 @@ using Server.Mobiles; namespace Server.Spells { - class UnsummonTimer : Timer - { - private BaseCreature m_Creature; - private Mobile m_Caster; + internal class UnsummonTimer : Timer + { + private Mobile m_Caster; + private BaseCreature m_Creature; - public UnsummonTimer( Mobile caster, BaseCreature creature, TimeSpan delay ) : base( delay ) - { - m_Caster = caster; - m_Creature = creature; - Priority = TimerPriority.OneSecond; - } + public UnsummonTimer(Mobile caster, BaseCreature creature, TimeSpan delay) : base(delay) + { + m_Caster = caster; + m_Creature = creature; + Priority = TimerPriority.OneSecond; + } - protected override void OnTick() - { - if ( !m_Creature.Deleted ) - m_Creature.Delete(); - } - } + protected override void OnTick() + { + if (!m_Creature.Deleted) + m_Creature.Delete(); + } + } } \ No newline at end of file diff --git a/Scripts/Targets/BladedItemTarget.cs b/Scripts/Targets/BladedItemTarget.cs index 8a6372a6e..721ce06b9 100644 --- a/Scripts/Targets/BladedItemTarget.cs +++ b/Scripts/Targets/BladedItemTarget.cs @@ -1,119 +1,120 @@ -using Server.Targeting; -using Server.Items; using Server.Engines.Harvest; -using Server.Mobiles; using Server.Engines.Quests; using Server.Engines.Quests.Hag; +using Server.Items; +using Server.Mobiles; +using Server.Targeting; namespace Server.Targets { - public class BladedItemTarget : Target - { - private Item m_Item; + public class BladedItemTarget : Target + { + private Item m_Item; - public BladedItemTarget( Item item ) : base( 2, false, TargetFlags.None ) - { - m_Item = item; - } + public BladedItemTarget(Item item) : base(2, false, TargetFlags.None) + { + m_Item = item; + } - protected override void OnTargetOutOfRange( Mobile from, object targeted ) - { - if ( targeted is UnholyBone && from.InRange( ((UnholyBone)targeted), 12 ) ) - ((UnholyBone)targeted).Carve( from, m_Item ); - else - base.OnTargetOutOfRange (from, targeted); - } + protected override void OnTargetOutOfRange(Mobile from, object targeted) + { + if (targeted is UnholyBone && from.InRange((UnholyBone)targeted, 12)) + ((UnholyBone)targeted).Carve(from, m_Item); + else + base.OnTargetOutOfRange(from, targeted); + } - protected override void OnTarget( Mobile from, object targeted ) - { - if ( m_Item.Deleted ) - return; + protected override void OnTarget(Mobile from, object targeted) + { + if (m_Item.Deleted) + return; - if ( targeted is ICarvable ) - { - ((ICarvable)targeted).Carve( from, m_Item ); - } - else if ( targeted is SwampDragon && ((SwampDragon)targeted).HasBarding ) - { - SwampDragon pet = (SwampDragon)targeted; + if (targeted is ICarvable) + { + ((ICarvable)targeted).Carve(from, m_Item); + } + else if (targeted is SwampDragon && ((SwampDragon)targeted).HasBarding) + { + SwampDragon pet = (SwampDragon)targeted; - if ( !pet.Controlled || pet.ControlMaster != from ) - from.SendLocalizedMessage( 1053022 ); // You cannot remove barding from a swamp dragon you do not own. - else - pet.HasBarding = false; - } - else - { - if ( targeted is StaticTarget ) - { - int itemID = ((StaticTarget)targeted).ItemID; + if (!pet.Controlled || pet.ControlMaster != from) + from.SendLocalizedMessage(1053022); // You cannot remove barding from a swamp dragon you do not own. + else + pet.HasBarding = false; + } + else + { + if (targeted is StaticTarget) + { + int itemID = ((StaticTarget)targeted).ItemID; - if ( itemID == 0xD15 || itemID == 0xD16 ) // red mushroom - { - PlayerMobile player = from as PlayerMobile; + if (itemID == 0xD15 || itemID == 0xD16) // red mushroom + { + PlayerMobile player = from as PlayerMobile; - QuestSystem qs = player?.Quest; + QuestSystem qs = player?.Quest; - if ( qs is WitchApprenticeQuest ) - { - FindIngredientObjective obj = qs.FindObjective( typeof( FindIngredientObjective ) ) as FindIngredientObjective; + if (qs is WitchApprenticeQuest) + { + FindIngredientObjective obj = + qs.FindObjective(typeof(FindIngredientObjective)) as FindIngredientObjective; - if ( obj != null && !obj.Completed && obj.Ingredient == Ingredient.RedMushrooms ) - { - player.SendLocalizedMessage( 1055036 ); // You slice a red cap mushroom from its stem. - obj.Complete(); - return; - } - } - } - } + if (obj != null && !obj.Completed && obj.Ingredient == Ingredient.RedMushrooms) + { + player.SendLocalizedMessage(1055036); // You slice a red cap mushroom from its stem. + obj.Complete(); + return; + } + } + } + } - HarvestSystem system = Lumberjacking.System; - HarvestDefinition def = Lumberjacking.System.Definition; + HarvestSystem system = Lumberjacking.System; + HarvestDefinition def = Lumberjacking.System.Definition; - int tileID; - Map map; - Point3D loc; + int tileID; + Map map; + Point3D loc; - if ( !system.GetHarvestDetails( from, m_Item, targeted, out tileID, out map, out loc ) ) - { - from.SendLocalizedMessage( 500494 ); // You can't use a bladed item on that! - } - else if ( !def.Validate( tileID ) ) - { - from.SendLocalizedMessage( 500494 ); // You can't use a bladed item on that! - } - else - { - HarvestBank bank = def.GetBank( map, loc.X, loc.Y ); + if (!system.GetHarvestDetails(from, m_Item, targeted, out tileID, out map, out loc)) + { + from.SendLocalizedMessage(500494); // You can't use a bladed item on that! + } + else if (!def.Validate(tileID)) + { + from.SendLocalizedMessage(500494); // You can't use a bladed item on that! + } + else + { + HarvestBank bank = def.GetBank(map, loc.X, loc.Y); - if ( bank == null ) - return; + if (bank == null) + return; - if ( bank.Current < 5 ) - { - from.SendLocalizedMessage( 500493 ); // There's not enough wood here to harvest. - } - else - { - bank.Consume( 5, from ); + if (bank.Current < 5) + { + from.SendLocalizedMessage(500493); // There's not enough wood here to harvest. + } + else + { + bank.Consume(5, from); - Item item = new Kindling(); + Item item = new Kindling(); - if ( from.PlaceInBackpack( item ) ) - { - from.SendLocalizedMessage( 500491 ); // You put some kindling into your backpack. - from.SendLocalizedMessage( 500492 ); // An axe would probably get you more wood. - } - else - { - from.SendLocalizedMessage( 500490 ); // You can't place any kindling into your backpack! + if (from.PlaceInBackpack(item)) + { + from.SendLocalizedMessage(500491); // You put some kindling into your backpack. + from.SendLocalizedMessage(500492); // An axe would probably get you more wood. + } + else + { + from.SendLocalizedMessage(500490); // You can't place any kindling into your backpack! - item.Delete(); - } - } - } - } - } - } + item.Delete(); + } + } + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Targets/MoveTarget.cs b/Scripts/Targets/MoveTarget.cs index 1ebec9d9f..fbe826061 100644 --- a/Scripts/Targets/MoveTarget.cs +++ b/Scripts/Targets/MoveTarget.cs @@ -1,50 +1,51 @@ -using Server.Targeting; using Server.Commands; using Server.Commands.Generic; +using Server.Targeting; namespace Server.Targets { - public class MoveTarget : Target - { - private object m_Object; + public class MoveTarget : Target + { + private object m_Object; - public MoveTarget( object o ) : base( -1, true, TargetFlags.None ) - { - m_Object = o; - } + public MoveTarget(object o) : base(-1, true, TargetFlags.None) + { + m_Object = o; + } - protected override void OnTarget( Mobile from, object o ) - { - IPoint3D p = o as IPoint3D; + protected override void OnTarget(Mobile from, object o) + { + IPoint3D p = o as IPoint3D; - if ( p != null ) - { - if ( !BaseCommand.IsAccessible( from, m_Object ) ) - { - from.SendMessage( "That is not accessible." ); - return; - } + if (p != null) + { + if (!BaseCommand.IsAccessible(from, m_Object)) + { + from.SendMessage("That is not accessible."); + return; + } - if ( p is Item ) - p = ((Item)p).GetWorldTop(); + if (p is Item) + p = ((Item)p).GetWorldTop(); - CommandLogging.WriteLine( from, "{0} {1} moving {2} to {3}", from.AccessLevel, CommandLogging.Format( from ), CommandLogging.Format( m_Object ), new Point3D( p ) ); + CommandLogging.WriteLine(from, "{0} {1} moving {2} to {3}", from.AccessLevel, CommandLogging.Format(from), + CommandLogging.Format(m_Object), new Point3D(p)); - if ( m_Object is Item ) - { - Item item = (Item)m_Object; + if (m_Object is Item) + { + Item item = (Item)m_Object; - if ( !item.Deleted ) - item.MoveToWorld( new Point3D( p ), from.Map ); - } - else if ( m_Object is Mobile ) - { - Mobile m = (Mobile)m_Object; + if (!item.Deleted) + item.MoveToWorld(new Point3D(p), from.Map); + } + else if (m_Object is Mobile) + { + Mobile m = (Mobile)m_Object; - if ( !m.Deleted ) - m.MoveToWorld( new Point3D( p ), from.Map ); - } - } - } - } + if (!m.Deleted) + m.MoveToWorld(new Point3D(p), from.Map); + } + } + } + } } \ No newline at end of file diff --git a/Scripts/Targets/PickMoveTarget.cs b/Scripts/Targets/PickMoveTarget.cs index 4ab5bafb8..8adf5fb4d 100644 --- a/Scripts/Targets/PickMoveTarget.cs +++ b/Scripts/Targets/PickMoveTarget.cs @@ -1,24 +1,24 @@ -using Server.Targeting; using Server.Commands.Generic; +using Server.Targeting; namespace Server.Targets { - public class PickMoveTarget : Target - { - public PickMoveTarget() : base( -1, false, TargetFlags.None ) - { - } + public class PickMoveTarget : Target + { + public PickMoveTarget() : base(-1, false, TargetFlags.None) + { + } - protected override void OnTarget( Mobile from, object o ) - { - if ( !BaseCommand.IsAccessible( from, o ) ) - { - from.SendMessage( "That is not accessible." ); - return; - } + protected override void OnTarget(Mobile from, object o) + { + if (!BaseCommand.IsAccessible(from, o)) + { + from.SendMessage("That is not accessible."); + return; + } - if ( o is Item || o is Mobile ) - from.Target = new MoveTarget( o ); - } - } + if (o is Item || o is Mobile) + from.Target = new MoveTarget(o); + } + } } \ No newline at end of file diff --git a/Server/AggressorInfo.cs b/Server/AggressorInfo.cs index 1716eb004..7adaf6eee 100644 --- a/Server/AggressorInfo.cs +++ b/Server/AggressorInfo.cs @@ -19,187 +19,187 @@ ***************************************************************************/ using System; -using System.IO; using System.Collections.Generic; +using System.Diagnostics; +using System.IO; namespace Server { - public class AggressorInfo - { - private Mobile m_Attacker, m_Defender; - private DateTime m_LastCombatTime; - private bool m_CanReportMurder; - private bool m_Reported; - private bool m_CriminalAggression; + public class AggressorInfo + { + private static Queue m_Pool = new Queue(); + private Mobile m_Attacker, m_Defender; + private bool m_CanReportMurder; + private bool m_CriminalAggression; + private DateTime m_LastCombatTime; - private bool m_Queued; + private bool m_Queued; + private bool m_Reported; - private static Queue m_Pool = new Queue(); + private AggressorInfo(Mobile attacker, Mobile defender, bool criminal) + { + m_Attacker = attacker; + m_Defender = defender; - public static AggressorInfo Create( Mobile attacker, Mobile defender, bool criminal ) - { - AggressorInfo info; + m_CanReportMurder = criminal; + m_CriminalAggression = criminal; - if ( m_Pool.Count > 0 ) - { - info = m_Pool.Dequeue(); + Refresh(); + } - info.m_Attacker = attacker; - info.m_Defender = defender; + public static TimeSpan ExpireDelay{ get; set; } = TimeSpan.FromMinutes(2.0); - info.m_CanReportMurder = criminal; - info.m_CriminalAggression = criminal; + public bool Expired + { + get + { + if (m_Queued) + DumpAccess(); - info.m_Queued = false; + return m_Attacker.Deleted || m_Defender.Deleted || DateTime.UtcNow >= m_LastCombatTime + ExpireDelay; + } + } - info.Refresh(); - } - else - { - info = new AggressorInfo( attacker, defender, criminal ); - } + public bool CriminalAggression + { + get + { + if (m_Queued) + DumpAccess(); - return info; - } + return m_CriminalAggression; + } + set + { + if (m_Queued) + DumpAccess(); - public void Free() - { - if ( m_Queued ) - return; + m_CriminalAggression = value; + } + } - m_Queued = true; - m_Pool.Enqueue( this ); - } + public Mobile Attacker + { + get + { + if (m_Queued) + DumpAccess(); - private AggressorInfo( Mobile attacker, Mobile defender, bool criminal ) - { - m_Attacker = attacker; - m_Defender = defender; + return m_Attacker; + } + } - m_CanReportMurder = criminal; - m_CriminalAggression = criminal; + public Mobile Defender + { + get + { + if (m_Queued) + DumpAccess(); - Refresh(); - } + return m_Defender; + } + } - public static TimeSpan ExpireDelay { get; set; } = TimeSpan.FromMinutes( 2.0 ); + public DateTime LastCombatTime + { + get + { + if (m_Queued) + DumpAccess(); - public static void DumpAccess() - { - using ( StreamWriter op = new StreamWriter( "warnings.log", true ) ) - { - op.WriteLine( "Warning: Access to queued AggressorInfo:" ); - op.WriteLine( new System.Diagnostics.StackTrace() ); - op.WriteLine(); - op.WriteLine(); - } - } + return m_LastCombatTime; + } + } - public bool Expired - { - get - { - if ( m_Queued ) - DumpAccess(); + public bool Reported + { + get + { + if (m_Queued) + DumpAccess(); - return ( m_Attacker.Deleted || m_Defender.Deleted || DateTime.UtcNow >= (m_LastCombatTime + ExpireDelay) ); - } - } + return m_Reported; + } + set + { + if (m_Queued) + DumpAccess(); - public bool CriminalAggression - { - get - { - if ( m_Queued ) - DumpAccess(); + m_Reported = value; + } + } - return m_CriminalAggression; - } - set - { - if ( m_Queued ) - DumpAccess(); + public bool CanReportMurder + { + get + { + if (m_Queued) + DumpAccess(); - m_CriminalAggression = value; - } - } + return m_CanReportMurder; + } + set + { + if (m_Queued) + DumpAccess(); - public Mobile Attacker - { - get - { - if ( m_Queued ) - DumpAccess(); + m_CanReportMurder = value; + } + } - return m_Attacker; - } - } + public static AggressorInfo Create(Mobile attacker, Mobile defender, bool criminal) + { + AggressorInfo info; - public Mobile Defender - { - get - { - if ( m_Queued ) - DumpAccess(); + if (m_Pool.Count > 0) + { + info = m_Pool.Dequeue(); - return m_Defender; - } - } + info.m_Attacker = attacker; + info.m_Defender = defender; - public DateTime LastCombatTime - { - get - { - if ( m_Queued ) - DumpAccess(); + info.m_CanReportMurder = criminal; + info.m_CriminalAggression = criminal; - return m_LastCombatTime; - } - } + info.m_Queued = false; - public bool Reported - { - get - { - if ( m_Queued ) - DumpAccess(); + info.Refresh(); + } + else + { + info = new AggressorInfo(attacker, defender, criminal); + } - return m_Reported; - } - set - { - if ( m_Queued ) - DumpAccess(); + return info; + } - m_Reported = value; - } - } + public void Free() + { + if (m_Queued) + return; - public bool CanReportMurder - { - get - { - if ( m_Queued ) - DumpAccess(); + m_Queued = true; + m_Pool.Enqueue(this); + } - return m_CanReportMurder; - } - set - { - if ( m_Queued ) - DumpAccess(); + public static void DumpAccess() + { + using (StreamWriter op = new StreamWriter("warnings.log", true)) + { + op.WriteLine("Warning: Access to queued AggressorInfo:"); + op.WriteLine(new StackTrace()); + op.WriteLine(); + op.WriteLine(); + } + } - m_CanReportMurder = value; - } - } + public void Refresh() + { + if (m_Queued) + DumpAccess(); - public void Refresh() - { - if ( m_Queued ) - DumpAccess(); - - m_LastCombatTime = DateTime.UtcNow; - m_Reported = false; - } - } + m_LastCombatTime = DateTime.UtcNow; + m_Reported = false; + } + } } \ No newline at end of file diff --git a/Server/AssemblyInfo.cs b/Server/AssemblyInfo.cs index 3472afdbb..d28a05c87 100644 --- a/Server/AssemblyInfo.cs +++ b/Server/AssemblyInfo.cs @@ -26,7 +26,7 @@ using System.Runtime.InteropServices; // set of attributes. Change these attribute values to modify the information // associated with an assembly. // -[assembly: AssemblyTitle("RunUO Server Core")] //Having just RunUO there is reundant, ie, RunUO.exe with the word 'RunUO' under it +[assembly: AssemblyTitle("RunUO Server Core")] //Having just RunUO there is reundant, ie, RunUO.exe with the word 'RunUO' under it [assembly: AssemblyDescription("UO Server Software")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("RunUO")] @@ -77,4 +77,4 @@ using System.Runtime.InteropServices; [assembly: AssemblyKeyFile("")] [assembly: AssemblyKeyName("")] -[assembly: ComVisible(false)] +[assembly: ComVisible(false)] \ No newline at end of file diff --git a/Server/Attributes.cs b/Server/Attributes.cs index 29fa965c9..0aa691314 100644 --- a/Server/Attributes.cs +++ b/Server/Attributes.cs @@ -24,156 +24,142 @@ using System.Reflection; namespace Server { - [AttributeUsage( AttributeTargets.Property )] - public class HueAttribute : Attribute - { - public HueAttribute() - { - } - } + [AttributeUsage(AttributeTargets.Property)] + public class HueAttribute : Attribute + { + } - [AttributeUsage( AttributeTargets.Property )] - public class BodyAttribute : Attribute - { - public BodyAttribute() - { - } - } + [AttributeUsage(AttributeTargets.Property)] + public class BodyAttribute : Attribute + { + } - [AttributeUsage( AttributeTargets.Class | AttributeTargets.Struct )] - public class PropertyObjectAttribute : Attribute - { - public PropertyObjectAttribute() - { - } - } + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct)] + public class PropertyObjectAttribute : Attribute + { + } - [AttributeUsage( AttributeTargets.Class | AttributeTargets.Struct )] - public class NoSortAttribute : Attribute - { - public NoSortAttribute() - { - } - } + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct)] + public class NoSortAttribute : Attribute + { + } - [AttributeUsage( AttributeTargets.Method )] - public class CallPriorityAttribute : Attribute - { - public int Priority { get; set; } + [AttributeUsage(AttributeTargets.Method)] + public class CallPriorityAttribute : Attribute + { + public CallPriorityAttribute(int priority) + { + Priority = priority; + } - public CallPriorityAttribute( int priority ) - { - Priority = priority; - } - } + public int Priority{ get; set; } + } - public class CallPriorityComparer : IComparer - { - public int Compare( MethodInfo x, MethodInfo y ) - { - if ( x == null && y == null ) - return 0; + public class CallPriorityComparer : IComparer + { + public int Compare(MethodInfo x, MethodInfo y) + { + if (x == null && y == null) + return 0; - if ( x == null ) - return 1; + if (x == null) + return 1; - if ( y == null ) - return -1; + if (y == null) + return -1; - var xPriority = GetPriority( x ); - var yPriority = GetPriority( y ); + int xPriority = GetPriority(x); + int yPriority = GetPriority(y); - if ( xPriority > yPriority ) - return 1; + if (xPriority > yPriority) + return 1; - if ( xPriority < yPriority ) - return -1; + if (xPriority < yPriority) + return -1; - return 0; - } + return 0; + } - private int GetPriority( MethodInfo mi ) - { - object[] objs = mi.GetCustomAttributes( typeof( CallPriorityAttribute ), true ); + private int GetPriority(MethodInfo mi) + { + object[] objs = mi.GetCustomAttributes(typeof(CallPriorityAttribute), true); - if ( objs.Length == 0 ) - return 0; + if (objs.Length == 0) + return 0; - if ( !(objs[0] is CallPriorityAttribute attr) ) - return 0; + if (!(objs[0] is CallPriorityAttribute attr)) + return 0; - return attr.Priority; - } - } + return attr.Priority; + } + } - [AttributeUsage( AttributeTargets.Class )] - public class TypeAliasAttribute : Attribute - { - public string[] Aliases { get; } + [AttributeUsage(AttributeTargets.Class)] + public class TypeAliasAttribute : Attribute + { + public TypeAliasAttribute(params string[] aliases) + { + Aliases = aliases; + } - public TypeAliasAttribute( params string[] aliases ) - { - Aliases = aliases; - } - } + public string[] Aliases{ get; } + } - [AttributeUsage( AttributeTargets.Class | AttributeTargets.Struct )] - public class ParsableAttribute : Attribute - { - public ParsableAttribute() - { - } - } + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct)] + public class ParsableAttribute : Attribute + { + } - [AttributeUsage( AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Enum )] - public class CustomEnumAttribute : Attribute - { - public string[] Names { get; } + [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Enum)] + public class CustomEnumAttribute : Attribute + { + public CustomEnumAttribute(string[] names) + { + Names = names; + } - public CustomEnumAttribute( string[] names ) - { - Names = names; - } - } + public string[] Names{ get; } + } - [AttributeUsage( AttributeTargets.Constructor )] - public class ConstructibleAttribute : Attribute - { - public AccessLevel AccessLevel { get; set; } + [AttributeUsage(AttributeTargets.Constructor)] + public class ConstructibleAttribute : Attribute + { + public ConstructibleAttribute() : + this(AccessLevel.Player) //Lowest accesslevel for current functionality (Level determined by access to [add) + { + } - public ConstructibleAttribute() : this( AccessLevel.Player ) //Lowest accesslevel for current functionality (Level determined by access to [add) - { - } + public ConstructibleAttribute(AccessLevel accessLevel) + { + AccessLevel = accessLevel; + } - public ConstructibleAttribute( AccessLevel accessLevel ) - { - AccessLevel = accessLevel; - } - } + public AccessLevel AccessLevel{ get; set; } + } - [AttributeUsage( AttributeTargets.Property )] - public class CommandPropertyAttribute : Attribute - { - public AccessLevel ReadLevel { get; } + [AttributeUsage(AttributeTargets.Property)] + public class CommandPropertyAttribute : Attribute + { + public CommandPropertyAttribute(AccessLevel level, bool readOnly) + { + ReadLevel = level; + ReadOnly = readOnly; + } - public AccessLevel WriteLevel { get; } + public CommandPropertyAttribute(AccessLevel level) : this(level, level) + { + } - public bool ReadOnly { get; } + public CommandPropertyAttribute(AccessLevel readLevel, AccessLevel writeLevel) + { + ReadLevel = readLevel; + WriteLevel = writeLevel; + } - public CommandPropertyAttribute( AccessLevel level, bool readOnly ) - { - ReadLevel = level; - ReadOnly = readOnly; - } + public AccessLevel ReadLevel{ get; } - public CommandPropertyAttribute( AccessLevel level ) : this( level, level ) - { - } + public AccessLevel WriteLevel{ get; } - public CommandPropertyAttribute( AccessLevel readLevel, AccessLevel writeLevel ) - { - ReadLevel = readLevel; - WriteLevel = writeLevel; - } - } -} + public bool ReadOnly{ get; } + } +} \ No newline at end of file diff --git a/Server/BaseVendor.cs b/Server/BaseVendor.cs index 2c20a243c..c4101f302 100644 --- a/Server/BaseVendor.cs +++ b/Server/BaseVendor.cs @@ -22,85 +22,85 @@ using System.Collections.Generic; namespace Server.Mobiles { - public class BuyItemStateComparer : IComparer - { - public int Compare( BuyItemState l, BuyItemState r ) - { - if ( l == null && r == null ) return 0; - if ( l == null ) return -1; - if ( r == null ) return 1; + public class BuyItemStateComparer : IComparer + { + public int Compare(BuyItemState l, BuyItemState r) + { + if (l == null && r == null) return 0; + if (l == null) return -1; + if (r == null) return 1; - return l.MySerial.CompareTo( r.MySerial ); - } - } + return l.MySerial.CompareTo(r.MySerial); + } + } - public class BuyItemResponse - { - public BuyItemResponse( Serial serial, int amount ) - { - Serial = serial; - Amount = amount; - } + public class BuyItemResponse + { + public BuyItemResponse(Serial serial, int amount) + { + Serial = serial; + Amount = amount; + } - public Serial Serial { get; } + public Serial Serial{ get; } - public int Amount { get; } - } + public int Amount{ get; } + } - public class SellItemResponse - { - public SellItemResponse( Item i, int amount ) - { - Item = i; - Amount = amount; - } + public class SellItemResponse + { + public SellItemResponse(Item i, int amount) + { + Item = i; + Amount = amount; + } - public Item Item { get; } + public Item Item{ get; } - public int Amount { get; } - } + public int Amount{ get; } + } - public class SellItemState - { - public SellItemState( Item item, int price, string name ) - { - Item = item; - Price = price; - Name = name; - } + public class SellItemState + { + public SellItemState(Item item, int price, string name) + { + Item = item; + Price = price; + Name = name; + } - public Item Item { get; } + public Item Item{ get; } - public int Price { get; } + public int Price{ get; } - public string Name { get; } - } + public string Name{ get; } + } - public class BuyItemState - { - public BuyItemState( string name, Serial cont, Serial serial, int price, int amount, int itemID, int hue ) - { - Description = name; - ContainerSerial = cont; - MySerial = serial; - Price = price; - Amount = amount; - ItemID = itemID; - Hue = hue; - } + public class BuyItemState + { + public BuyItemState(string name, Serial cont, Serial serial, int price, int amount, int itemID, int hue) + { + Description = name; + ContainerSerial = cont; + MySerial = serial; + Price = price; + Amount = amount; + ItemID = itemID; + Hue = hue; + } - public int Price { get; } + public int Price{ get; } - public Serial MySerial { get; } + public Serial MySerial{ get; } - public Serial ContainerSerial { get; } + public Serial ContainerSerial{ get; } - public int ItemID { get; } + public int ItemID{ get; } - public int Amount { get; } + public int Amount{ get; } - public int Hue { get; } + public int Hue{ get; } - public string Description { get; } - } -} + public string Description{ get; } + } +} \ No newline at end of file diff --git a/Server/Body.cs b/Server/Body.cs index 4dfb96bdd..eed6a14e4 100644 --- a/Server/Body.cs +++ b/Server/Body.cs @@ -23,196 +23,197 @@ using System.IO; namespace Server { - public enum BodyType : byte - { - Empty, - Monster, - Sea, - Animal, - Human, - Equipment - } + public enum BodyType : byte + { + Empty, + Monster, + Sea, + Animal, + Human, + Equipment + } - public struct Body - { - private static BodyType[] m_Types; + public struct Body + { + private static BodyType[] m_Types; - static Body() - { - if ( File.Exists( "Data/bodyTable.cfg" ) ) - { - using ( StreamReader ip = new StreamReader( "Data/bodyTable.cfg" ) ) - { - m_Types = new BodyType[0x1000]; + static Body() + { + if (File.Exists("Data/bodyTable.cfg")) + { + using (StreamReader ip = new StreamReader("Data/bodyTable.cfg")) + { + m_Types = new BodyType[0x1000]; - string line; + string line; - while ( (line = ip.ReadLine()) != null ) - { - if ( line.Length == 0 || line.StartsWith( "#" ) ) - continue; + while ((line = ip.ReadLine()) != null) + { + if (line.Length == 0 || line.StartsWith("#")) + continue; - string[] split = line.Split( '\t' ); + string[] split = line.Split('\t'); - BodyType type; - int bodyID; + BodyType type; + int bodyID; - if ( int.TryParse( split[0], out bodyID ) && Enum.TryParse( split[1], true, out type ) && bodyID >= 0 && bodyID < m_Types.Length ) - { - m_Types[bodyID] = type; - } - else - { - Console.WriteLine( "Warning: Invalid bodyTable entry:" ); - Console.WriteLine( line ); - } - } - } - } - else - { - Console.WriteLine( "Warning: Data/bodyTable.cfg does not exist" ); + if (int.TryParse(split[0], out bodyID) && Enum.TryParse(split[1], true, out type) && bodyID >= 0 && + bodyID < m_Types.Length) + { + m_Types[bodyID] = type; + } + else + { + Console.WriteLine("Warning: Invalid bodyTable entry:"); + Console.WriteLine(line); + } + } + } + } + else + { + Console.WriteLine("Warning: Data/bodyTable.cfg does not exist"); - m_Types = new BodyType[0]; - } - } + m_Types = new BodyType[0]; + } + } - public Body( int bodyID ) - { - BodyID = bodyID; - } + public Body(int bodyID) + { + BodyID = bodyID; + } - public BodyType Type - { - get - { - if ( BodyID >= 0 && BodyID < m_Types.Length ) - return m_Types[BodyID]; - return BodyType.Empty; - } - } + public BodyType Type + { + get + { + if (BodyID >= 0 && BodyID < m_Types.Length) + return m_Types[BodyID]; + return BodyType.Empty; + } + } - public bool IsHuman => BodyID >= 0 - && BodyID < m_Types.Length - && m_Types[BodyID] == BodyType.Human - && BodyID != 402 - && BodyID != 403 - && BodyID != 607 - && BodyID != 608 - && BodyID != 694 - && BodyID != 695 - && BodyID != 970; + public bool IsHuman => BodyID >= 0 + && BodyID < m_Types.Length + && m_Types[BodyID] == BodyType.Human + && BodyID != 402 + && BodyID != 403 + && BodyID != 607 + && BodyID != 608 + && BodyID != 694 + && BodyID != 695 + && BodyID != 970; - public bool IsGargoyle => BodyID == 666 - || BodyID == 667 - || BodyID == 694 - || BodyID == 695; + public bool IsGargoyle => BodyID == 666 + || BodyID == 667 + || BodyID == 694 + || BodyID == 695; - public bool IsMale => BodyID == 183 - || BodyID == 185 - || BodyID == 400 - || BodyID == 402 - || BodyID == 605 - || BodyID == 607 - || BodyID == 666 - || BodyID == 694 - || BodyID == 750; + public bool IsMale => BodyID == 183 + || BodyID == 185 + || BodyID == 400 + || BodyID == 402 + || BodyID == 605 + || BodyID == 607 + || BodyID == 666 + || BodyID == 694 + || BodyID == 750; - public bool IsFemale => BodyID == 184 - || BodyID == 186 - || BodyID == 401 - || BodyID == 403 - || BodyID == 606 - || BodyID == 608 - || BodyID == 667 - || BodyID == 695 - || BodyID == 751; + public bool IsFemale => BodyID == 184 + || BodyID == 186 + || BodyID == 401 + || BodyID == 403 + || BodyID == 606 + || BodyID == 608 + || BodyID == 667 + || BodyID == 695 + || BodyID == 751; - public bool IsGhost => BodyID == 402 - || BodyID == 403 - || BodyID == 607 - || BodyID == 608 - || BodyID == 694 - || BodyID == 695 - || BodyID == 970; + public bool IsGhost => BodyID == 402 + || BodyID == 403 + || BodyID == 607 + || BodyID == 608 + || BodyID == 694 + || BodyID == 695 + || BodyID == 970; - public bool IsMonster => BodyID >= 0 - && BodyID < m_Types.Length - && m_Types[BodyID] == BodyType.Monster; + public bool IsMonster => BodyID >= 0 + && BodyID < m_Types.Length + && m_Types[BodyID] == BodyType.Monster; - public bool IsAnimal => BodyID >= 0 - && BodyID < m_Types.Length - && m_Types[BodyID] == BodyType.Animal; + public bool IsAnimal => BodyID >= 0 + && BodyID < m_Types.Length + && m_Types[BodyID] == BodyType.Animal; - public bool IsEmpty => BodyID >= 0 - && BodyID < m_Types.Length - && m_Types[BodyID] == BodyType.Empty; + public bool IsEmpty => BodyID >= 0 + && BodyID < m_Types.Length + && m_Types[BodyID] == BodyType.Empty; - public bool IsSea => BodyID >= 0 - && BodyID < m_Types.Length - && m_Types[BodyID] == BodyType.Sea; + public bool IsSea => BodyID >= 0 + && BodyID < m_Types.Length + && m_Types[BodyID] == BodyType.Sea; - public bool IsEquipment => BodyID >= 0 - && BodyID < m_Types.Length - && m_Types[BodyID] == BodyType.Equipment; + public bool IsEquipment => BodyID >= 0 + && BodyID < m_Types.Length + && m_Types[BodyID] == BodyType.Equipment; - public int BodyID { get; } + public int BodyID{ get; } - public static implicit operator int( Body a ) - { - return a.BodyID; - } + public static implicit operator int(Body a) + { + return a.BodyID; + } - public static implicit operator Body( int a ) - { - return new Body( a ); - } + public static implicit operator Body(int a) + { + return new Body(a); + } - public override string ToString() - { - return $"0x{BodyID:X}"; - } + public override string ToString() + { + return $"0x{BodyID:X}"; + } - public override int GetHashCode() - { - return BodyID; - } + public override int GetHashCode() + { + return BodyID; + } - public override bool Equals( object o ) - { - if ( !(o is Body) ) return false; + public override bool Equals(object o) + { + if (!(o is Body)) return false; - return ((Body)o).BodyID == BodyID; - } + return ((Body)o).BodyID == BodyID; + } - public static bool operator == ( Body l, Body r ) - { - return l.BodyID == r.BodyID; - } + public static bool operator ==(Body l, Body r) + { + return l.BodyID == r.BodyID; + } - public static bool operator != ( Body l, Body r ) - { - return l.BodyID != r.BodyID; - } + public static bool operator !=(Body l, Body r) + { + return l.BodyID != r.BodyID; + } - public static bool operator > ( Body l, Body r ) - { - return l.BodyID > r.BodyID; - } + public static bool operator >(Body l, Body r) + { + return l.BodyID > r.BodyID; + } - public static bool operator >= ( Body l, Body r ) - { - return l.BodyID >= r.BodyID; - } + public static bool operator >=(Body l, Body r) + { + return l.BodyID >= r.BodyID; + } - public static bool operator < ( Body l, Body r ) - { - return l.BodyID < r.BodyID; - } + public static bool operator <(Body l, Body r) + { + return l.BodyID < r.BodyID; + } - public static bool operator <= ( Body l, Body r ) - { - return l.BodyID <= r.BodyID; - } - } -} + public static bool operator <=(Body l, Body r) + { + return l.BodyID <= r.BodyID; + } + } +} \ No newline at end of file diff --git a/Server/ClientVersion.cs b/Server/ClientVersion.cs index 241e89523..0d4ee6ae2 100644 --- a/Server/ClientVersion.cs +++ b/Server/ClientVersion.cs @@ -19,246 +19,247 @@ ***************************************************************************/ using System; -using System.Text; using System.Collections; +using System.Text; namespace Server { - public enum ClientType - { - Regular, - UOTD, - God, - SA - } + public enum ClientType + { + Regular, + UOTD, + God, + SA + } - public class ClientVersion : IComparable, IComparer - { - public int Major { get; } + public class ClientVersion : IComparable, IComparer + { + public ClientVersion(int maj, int min, int rev, int pat) : this(maj, min, rev, pat, ClientType.Regular) + { + } - public int Minor { get; } + public ClientVersion(int maj, int min, int rev, int pat, ClientType type) + { + Major = maj; + Minor = min; + Revision = rev; + Patch = pat; + Type = type; - public int Revision { get; } + SourceString = _ToStringImpl(); + } - public int Patch { get; } + public ClientVersion(string fmt) + { + SourceString = fmt; - public ClientType Type { get; } + try + { + fmt = fmt.ToLower(); - public string SourceString { get; } + int br1 = fmt.IndexOf('.'); + int br2 = fmt.IndexOf('.', br1 + 1); - public ClientVersion( int maj, int min, int rev, int pat ) : this( maj, min, rev, pat, ClientType.Regular ) - { - } + int br3 = br2 + 1; + while (br3 < fmt.Length && char.IsDigit(fmt, br3)) + br3++; - public ClientVersion( int maj, int min, int rev, int pat, ClientType type ) - { - Major = maj; - Minor = min; - Revision = rev; - Patch = pat; - Type = type; + Major = Utility.ToInt32(fmt.Substring(0, br1)); + Minor = Utility.ToInt32(fmt.Substring(br1 + 1, br2 - br1 - 1)); + Revision = Utility.ToInt32(fmt.Substring(br2 + 1, br3 - br2 - 1)); - SourceString = _ToStringImpl(); - } + if (br3 < fmt.Length) + { + if (Major <= 5 && Minor <= 0 && Revision <= 6) //Anything before 5.0.7 + { + if (!char.IsWhiteSpace(fmt, br3)) + Patch = fmt[br3] - 'a' + 1; + } + else + { + Patch = Utility.ToInt32(fmt.Substring(br3 + 1, fmt.Length - br3 - 1)); + } + } - public static bool operator == ( ClientVersion l, ClientVersion r ) - { - return ( Compare( l, r ) == 0 ); - } + if (fmt.IndexOf("god") >= 0 || fmt.IndexOf("gq") >= 0) + Type = ClientType.God; + else if (fmt.IndexOf("third dawn") >= 0 || fmt.IndexOf("uo:td") >= 0 || fmt.IndexOf("uotd") >= 0 || + fmt.IndexOf("uo3d") >= 0 || fmt.IndexOf("uo:3d") >= 0) + Type = ClientType.UOTD; + else + Type = ClientType.Regular; + } + catch + { + Major = 0; + Minor = 0; + Revision = 0; + Patch = 0; + Type = ClientType.Regular; + } + } - public static bool operator != ( ClientVersion l, ClientVersion r ) - { - return ( Compare( l, r ) != 0 ); - } + public int Major{ get; } - public static bool operator >= ( ClientVersion l, ClientVersion r ) - { - return ( Compare( l, r ) >= 0 ); - } + public int Minor{ get; } - public static bool operator > ( ClientVersion l, ClientVersion r ) - { - return ( Compare( l, r ) > 0 ); - } + public int Revision{ get; } - public static bool operator <= ( ClientVersion l, ClientVersion r ) - { - return ( Compare( l, r ) <= 0 ); - } + public int Patch{ get; } - public static bool operator < ( ClientVersion l, ClientVersion r ) - { - return ( Compare( l, r ) < 0 ); - } + public ClientType Type{ get; } - public override int GetHashCode() - { - return Major ^ Minor ^ Revision ^ Patch ^ (int)Type; - } + public string SourceString{ get; } - public override bool Equals( object obj ) - { - if ( obj == null ) - return false; + public int CompareTo(object obj) + { + if (obj == null) + return 1; - ClientVersion v = obj as ClientVersion; + ClientVersion o = obj as ClientVersion; - if ( v == null ) - return false; + if (o == null) + throw new ArgumentException(); - return Major == v.Major - && Minor == v.Minor - && Revision == v.Revision - && Patch == v.Patch - && Type == v.Type; - } + if (Major > o.Major) + return 1; + if (Major < o.Major) + return -1; + if (Minor > o.Minor) + return 1; + if (Minor < o.Minor) + return -1; + if (Revision > o.Revision) + return 1; + if (Revision < o.Revision) + return -1; + if (Patch > o.Patch) + return 1; + if (Patch < o.Patch) + return -1; + return 0; + } - private string _ToStringImpl() - { - StringBuilder builder = new StringBuilder(16); + public int Compare(object x, object y) + { + if (IsNull(x) && IsNull(y)) + return 0; + if (IsNull(x)) + return -1; + if (IsNull(y)) + return 1; - builder.Append(Major); - builder.Append('.'); - builder.Append(Minor); - builder.Append('.'); - builder.Append(Revision); + ClientVersion a = x as ClientVersion; + ClientVersion b = y as ClientVersion; - if (Major <= 5 && Minor <= 0 && Revision <= 6) //Anything before 5.0.7 - { - if (Patch > 0) - builder.Append((char)('a' + (Patch - 1))); - } - else - { - builder.Append('.'); - builder.Append(Patch); - } + if (IsNull(a) || IsNull(b)) + throw new ArgumentException(); - if (Type != ClientType.Regular) - { - builder.Append(' '); - builder.Append(Type.ToString()); - } + return a.CompareTo(b); + } - return builder.ToString(); - } + public static bool operator ==(ClientVersion l, ClientVersion r) + { + return Compare(l, r) == 0; + } - public override string ToString() - { - return _ToStringImpl(); - } + public static bool operator !=(ClientVersion l, ClientVersion r) + { + return Compare(l, r) != 0; + } - public ClientVersion( string fmt ) - { - SourceString = fmt; + public static bool operator >=(ClientVersion l, ClientVersion r) + { + return Compare(l, r) >= 0; + } - try - { - fmt = fmt.ToLower(); + public static bool operator >(ClientVersion l, ClientVersion r) + { + return Compare(l, r) > 0; + } - int br1 = fmt.IndexOf( '.' ); - int br2 = fmt.IndexOf( '.', br1 + 1 ); + public static bool operator <=(ClientVersion l, ClientVersion r) + { + return Compare(l, r) <= 0; + } - int br3 = br2 + 1; - while ( br3 < fmt.Length && char.IsDigit( fmt, br3 ) ) - br3++; + public static bool operator <(ClientVersion l, ClientVersion r) + { + return Compare(l, r) < 0; + } - Major = Utility.ToInt32( fmt.Substring( 0, br1 ) ); - Minor = Utility.ToInt32( fmt.Substring( br1 + 1, br2 - br1 - 1 ) ); - Revision = Utility.ToInt32( fmt.Substring( br2 + 1, br3 - br2 - 1 ) ); + public override int GetHashCode() + { + return Major ^ Minor ^ Revision ^ Patch ^ (int)Type; + } - if ( br3 < fmt.Length ) - { - if ( Major <= 5 && Minor <= 0 && Revision <= 6 ) //Anything before 5.0.7 - { - if ( !char.IsWhiteSpace( fmt, br3 ) ) - Patch = (fmt[br3] - 'a') + 1; - } - else - { - Patch = Utility.ToInt32( fmt.Substring( br3+1, fmt.Length - br3 - 1 ) ); - } - } + public override bool Equals(object obj) + { + if (obj == null) + return false; - if ( fmt.IndexOf( "god" ) >= 0 || fmt.IndexOf( "gq" ) >= 0 ) - Type = ClientType.God; - else if ( fmt.IndexOf( "third dawn" ) >= 0 || fmt.IndexOf( "uo:td" ) >= 0 || fmt.IndexOf( "uotd" ) >= 0 || fmt.IndexOf( "uo3d" ) >= 0 || fmt.IndexOf( "uo:3d" ) >= 0 ) - Type = ClientType.UOTD; - else - Type = ClientType.Regular; - } - catch - { - Major = 0; - Minor = 0; - Revision = 0; - Patch = 0; - Type = ClientType.Regular; - } - } + ClientVersion v = obj as ClientVersion; - public int CompareTo( object obj ) - { - if ( obj == null ) - return 1; + if (v == null) + return false; - ClientVersion o = obj as ClientVersion; + return Major == v.Major + && Minor == v.Minor + && Revision == v.Revision + && Patch == v.Patch + && Type == v.Type; + } - if ( o == null ) - throw new ArgumentException(); + private string _ToStringImpl() + { + StringBuilder builder = new StringBuilder(16); - if ( Major > o.Major ) - return 1; - if ( Major < o.Major ) - return -1; - if ( Minor > o.Minor ) - return 1; - if ( Minor < o.Minor ) - return -1; - if ( Revision > o.Revision ) - return 1; - if ( Revision < o.Revision ) - return -1; - if ( Patch > o.Patch ) - return 1; - if ( Patch < o.Patch ) - return -1; - return 0; - } + builder.Append(Major); + builder.Append('.'); + builder.Append(Minor); + builder.Append('.'); + builder.Append(Revision); - public static bool IsNull( object x ) - { - return ReferenceEquals( x, null ); - } + if (Major <= 5 && Minor <= 0 && Revision <= 6) //Anything before 5.0.7 + { + if (Patch > 0) + builder.Append((char)('a' + (Patch - 1))); + } + else + { + builder.Append('.'); + builder.Append(Patch); + } - public int Compare( object x, object y ) - { - if ( IsNull( x ) && IsNull( y ) ) - return 0; - if ( IsNull( x ) ) - return -1; - if ( IsNull( y ) ) - return 1; + if (Type != ClientType.Regular) + { + builder.Append(' '); + builder.Append(Type.ToString()); + } - ClientVersion a = x as ClientVersion; - ClientVersion b = y as ClientVersion; + return builder.ToString(); + } - if ( IsNull( a ) || IsNull( b ) ) - throw new ArgumentException(); + public override string ToString() + { + return _ToStringImpl(); + } - return a.CompareTo( b ); - } + public static bool IsNull(object x) + { + return ReferenceEquals(x, null); + } - public static int Compare( ClientVersion a, ClientVersion b ) - { - if ( IsNull( a ) && IsNull( b ) ) - return 0; - if ( IsNull( a ) ) - return -1; - if ( IsNull( b ) ) - return 1; + public static int Compare(ClientVersion a, ClientVersion b) + { + if (IsNull(a) && IsNull(b)) + return 0; + if (IsNull(a)) + return -1; + if (IsNull(b)) + return 1; - return a.CompareTo( b ); - } - } -} + return a.CompareTo(b); + } + } +} \ No newline at end of file diff --git a/Server/Commands.cs b/Server/Commands.cs index 5f5e4a0e2..e46b3fec6 100644 --- a/Server/Commands.cs +++ b/Server/Commands.cs @@ -24,234 +24,230 @@ using Server.Network; namespace Server.Commands { - public delegate void CommandEventHandler( CommandEventArgs e ); + public delegate void CommandEventHandler(CommandEventArgs e); - public class CommandEventArgs : EventArgs - { - public Mobile Mobile { get; } + public class CommandEventArgs : EventArgs + { + public CommandEventArgs(Mobile mobile, string command, string argString, string[] arguments) + { + Mobile = mobile; + Command = command; + ArgString = argString; + Arguments = arguments; + } - public string Command { get; } + public Mobile Mobile{ get; } - public string ArgString { get; } + public string Command{ get; } - public string[] Arguments { get; } + public string ArgString{ get; } - public int Length => Arguments.Length; + public string[] Arguments{ get; } - public string GetString( int index ) - { - if ( index < 0 || index >= Arguments.Length ) - return ""; + public int Length => Arguments.Length; - return Arguments[index]; - } + public string GetString(int index) + { + if (index < 0 || index >= Arguments.Length) + return ""; - public int GetInt32( int index ) - { - if ( index < 0 || index >= Arguments.Length ) - return 0; + return Arguments[index]; + } - return Utility.ToInt32( Arguments[index] ); - } + public int GetInt32(int index) + { + if (index < 0 || index >= Arguments.Length) + return 0; - public bool GetBoolean( int index ) - { - if ( index < 0 || index >= Arguments.Length ) - return false; + return Utility.ToInt32(Arguments[index]); + } - return Utility.ToBoolean( Arguments[index] ); - } + public bool GetBoolean(int index) + { + if (index < 0 || index >= Arguments.Length) + return false; - public double GetDouble( int index ) - { - if ( index < 0 || index >= Arguments.Length ) - return 0.0; + return Utility.ToBoolean(Arguments[index]); + } - return Utility.ToDouble( Arguments[index] ); - } + public double GetDouble(int index) + { + if (index < 0 || index >= Arguments.Length) + return 0.0; - public TimeSpan GetTimeSpan( int index ) - { - if ( index < 0 || index >= Arguments.Length ) - return TimeSpan.Zero; + return Utility.ToDouble(Arguments[index]); + } - return Utility.ToTimeSpan( Arguments[index] ); - } + public TimeSpan GetTimeSpan(int index) + { + if (index < 0 || index >= Arguments.Length) + return TimeSpan.Zero; - public CommandEventArgs( Mobile mobile, string command, string argString, string[] arguments ) - { - Mobile = mobile; - Command = command; - ArgString = argString; - Arguments = arguments; - } - } + return Utility.ToTimeSpan(Arguments[index]); + } + } - public class CommandEntry : IComparable - { - public string Command { get; } + public class CommandEntry : IComparable + { + public CommandEntry(string command, CommandEventHandler handler, AccessLevel accessLevel) + { + Command = command; + Handler = handler; + AccessLevel = accessLevel; + } - public CommandEventHandler Handler { get; } + public string Command{ get; } - public AccessLevel AccessLevel { get; } + public CommandEventHandler Handler{ get; } - public CommandEntry( string command, CommandEventHandler handler, AccessLevel accessLevel ) - { - Command = command; - Handler = handler; - AccessLevel = accessLevel; - } + public AccessLevel AccessLevel{ get; } - public int CompareTo( object obj ) - { - if ( obj == this ) - return 0; - if ( obj == null ) - return 1; + public int CompareTo(object obj) + { + if (obj == this) + return 0; + if (obj == null) + return 1; - if ( !(obj is CommandEntry e) ) - throw new ArgumentException(); + if (!(obj is CommandEntry e)) + throw new ArgumentException(); - return Command.CompareTo( e.Command ); - } - } + return Command.CompareTo(e.Command); + } + } - public static class CommandSystem - { - public static string Prefix { get; set; } = "["; + public static class CommandSystem + { + static CommandSystem() + { + Entries = new Dictionary(StringComparer.OrdinalIgnoreCase); + } - public static string[] Split( string value ) - { - char[] array = value.ToCharArray(); - List list = new List(); + public static string Prefix{ get; set; } = "["; - int start = 0; + public static Dictionary Entries{ get; } - while ( start < array.Length ) - { - char c = array[start]; + public static AccessLevel BadCommandIgnoreLevel{ get; set; } = AccessLevel.Player; - if ( c == '"' ) - { - ++start; - int end = start; + public static string[] Split(string value) + { + char[] array = value.ToCharArray(); + List list = new List(); - while ( end < array.Length ) - { - if ( array[end] != '"' || array[end - 1] == '\\' ) - ++end; - else - break; - } + int start = 0; - list.Add( value.Substring( start, end - start ) ); + while (start < array.Length) + { + char c = array[start]; - start = end + 2; - } - else if ( c != ' ' ) - { - int end = start; + if (c == '"') + { + ++start; + int end = start; - while ( end < array.Length ) - { - if ( array[end] != ' ' ) - ++end; - else - break; - } + while (end < array.Length) + if (array[end] != '"' || array[end - 1] == '\\') + ++end; + else + break; - list.Add( value.Substring( start, end - start ) ); + list.Add(value.Substring(start, end - start)); - start = end + 1; - } - else - { - ++start; - } - } + start = end + 2; + } + else if (c != ' ') + { + int end = start; - return list.ToArray(); - } + while (end < array.Length) + if (array[end] != ' ') + ++end; + else + break; - public static Dictionary Entries { get; } + list.Add(value.Substring(start, end - start)); - static CommandSystem() - { - Entries = new Dictionary( StringComparer.OrdinalIgnoreCase ); - } + start = end + 1; + } + else + { + ++start; + } + } - public static void Register( string command, AccessLevel access, CommandEventHandler handler ) - { - Entries[command] = new CommandEntry( command, handler, access ); - } + return list.ToArray(); + } - public static AccessLevel BadCommandIgnoreLevel { get; set; } = AccessLevel.Player; + public static void Register(string command, AccessLevel access, CommandEventHandler handler) + { + Entries[command] = new CommandEntry(command, handler, access); + } - public static bool Handle( Mobile from, string text ) - { - return Handle( from, text, MessageType.Regular ); - } + public static bool Handle(Mobile from, string text) + { + return Handle(from, text, MessageType.Regular); + } - public static bool Handle( Mobile from, string text, MessageType type ) - { - if ( text.StartsWith( Prefix ) || type == MessageType.Command ) - { - if ( type != MessageType.Command ) - text = text.Substring( Prefix.Length ); + public static bool Handle(Mobile from, string text, MessageType type) + { + if (text.StartsWith(Prefix) || type == MessageType.Command) + { + if (type != MessageType.Command) + text = text.Substring(Prefix.Length); - int indexOf = text.IndexOf( ' ' ); + int indexOf = text.IndexOf(' '); - string command; - string[] args; - string argString; + string command; + string[] args; + string argString; - if ( indexOf >= 0 ) - { - argString = text.Substring( indexOf + 1 ); + if (indexOf >= 0) + { + argString = text.Substring(indexOf + 1); - command = text.Substring( 0, indexOf ); - args = Split( argString ); - } - else - { - argString = ""; - command = text.ToLower(); - args = new string[0]; - } + command = text.Substring(0, indexOf); + args = Split(argString); + } + else + { + argString = ""; + command = text.ToLower(); + args = new string[0]; + } - Entries.TryGetValue( command, out CommandEntry entry ); + Entries.TryGetValue(command, out CommandEntry entry); - if ( entry != null ) - { - if ( from.AccessLevel >= entry.AccessLevel ) - { - if ( entry.Handler != null ) - { - CommandEventArgs e = new CommandEventArgs( from, command, argString, args ); - entry.Handler( e ); - EventSink.InvokeCommand( e ); - } - } - else - { - if ( from.AccessLevel <= BadCommandIgnoreLevel ) - return false; + if (entry != null) + { + if (from.AccessLevel >= entry.AccessLevel) + { + if (entry.Handler != null) + { + CommandEventArgs e = new CommandEventArgs(from, command, argString, args); + entry.Handler(e); + EventSink.InvokeCommand(e); + } + } + else + { + if (from.AccessLevel <= BadCommandIgnoreLevel) + return false; - from.SendMessage( "You do not have access to that command." ); - } - } - else - { - if ( from.AccessLevel <= BadCommandIgnoreLevel ) - return false; + from.SendMessage("You do not have access to that command."); + } + } + else + { + if (from.AccessLevel <= BadCommandIgnoreLevel) + return false; - from.SendMessage( "That is not a valid command." ); - } + from.SendMessage("That is not a valid command."); + } - return true; - } + return true; + } - return false; - } - } -} + return false; + } + } +} \ No newline at end of file diff --git a/Server/ContextMenus/ContextMenu.cs b/Server/ContextMenus/ContextMenu.cs index e619a7c2b..5f3ac4fd2 100644 --- a/Server/ContextMenus/ContextMenu.cs +++ b/Server/ContextMenus/ContextMenu.cs @@ -23,78 +23,69 @@ using System.Collections.Generic; namespace Server.ContextMenus { /// - /// Represents the state of an active context menu. This includes who opened the menu, the menu's focus object, and a list of entries that the menu is composed of. - /// + /// Represents the state of an active context menu. This includes who opened the menu, the menu's focus object, and a list of + /// entries that the menu is composed of. + /// /// public class ContextMenu - { - /// - /// Gets the who opened this ContextMenu. - /// - public Mobile From { get; } + { + /// + /// Instantiates a new ContextMenu instance. + /// + /// + /// The who opened this ContextMenu. + /// + /// + /// + /// The or for which this ContextMenu is on. + /// + /// + public ContextMenu(Mobile from, object target) + { + From = from; + Target = target; - /// - /// Gets an object of the or for which this ContextMenu is on. - /// - public object Target { get; } + List list = new List(); - /// - /// Gets the list of entries contained in this ContextMenu. - /// - public ContextMenuEntry[] Entries { get; } + if (target is Mobile mobile) + mobile.GetContextMenuEntries(from, list); + else if (target is Item item) item.GetContextMenuEntries(from, list); - /// - /// Instantiates a new ContextMenu instance. - /// - /// - /// The who opened this ContextMenu. - /// - /// - /// - /// The or for which this ContextMenu is on. - /// - /// - public ContextMenu( Mobile from, object target ) - { - From = from; - Target = target; + //m_Entries = (ContextMenuEntry[])list.ToArray( typeof( ContextMenuEntry ) ); - List list = new List(); + Entries = list.ToArray(); - if ( target is Mobile mobile ) - { - mobile.GetContextMenuEntries( from, list ); - } - else if ( target is Item item ) - { - item.GetContextMenuEntries( from, list ); - } + for (int i = 0; i < Entries.Length; ++i) Entries[i].Owner = this; + } - //m_Entries = (ContextMenuEntry[])list.ToArray( typeof( ContextMenuEntry ) ); + /// + /// Gets the who opened this ContextMenu. + /// + public Mobile From{ get; } - Entries = list.ToArray(); + /// + /// Gets an object of the or for which this ContextMenu is on. + /// + public object Target{ get; } - for ( int i = 0; i < Entries.Length; ++i ) - { - Entries[i].Owner = this; - } - } + /// + /// Gets the list of entries contained in this ContextMenu. + /// + public ContextMenuEntry[] Entries{ get; } - /// - /// Returns true if this ContextMenu requires packet version 2. - /// - public bool RequiresNewPacket - { - get - { - for ( int i = 0; i < Entries.Length; ++i ) - { - if ( Entries[i].Number < 3000000 || Entries[i].Number > 3032767 ) - return true; - } + /// + /// Returns true if this ContextMenu requires packet version 2. + /// + public bool RequiresNewPacket + { + get + { + for (int i = 0; i < Entries.Length; ++i) + if (Entries[i].Number < 3000000 || Entries[i].Number > 3032767) + return true; - return false; - } - } - } -} + return false; + } + } + } +} \ No newline at end of file diff --git a/Server/ContextMenus/ContextMenuEntry.cs b/Server/ContextMenus/ContextMenuEntry.cs index c4726c39c..675576fa6 100644 --- a/Server/ContextMenus/ContextMenuEntry.cs +++ b/Server/ContextMenus/ContextMenuEntry.cs @@ -23,85 +23,88 @@ using Server.Network; namespace Server.ContextMenus { /// - /// Represents a single entry of a context menu. - /// + /// Represents a single entry of a context menu. + /// /// public class ContextMenuEntry - { - /// - /// Gets or sets additional flags used in client communication. - /// - public CMEFlags Flags { get; set; } + { + /// + /// Instantiates a new ContextMenuEntry with a given localization number ( + /// ). No maximum range is used. + /// + /// + /// The localization number containing the name of this entry. + /// + /// + public ContextMenuEntry(int number) : this(number, -1) + { + } - /// - /// Gets or sets the that owns this entry. - /// - public ContextMenu Owner { get; set; } + /// + /// Instantiates a new ContextMenuEntry with a given localization number () + /// and maximum range (). + /// + /// + /// The localization number containing the name of this entry. + /// + /// + /// + /// The maximum range at which this entry can be used. + /// + /// + public ContextMenuEntry(int number, int range) + { + if (number <= 0x7FFF) // Legacy code support + Number = 3000000 + number; + else + Number = number; - /// - /// Gets or sets the localization number containing the name of this entry. - /// - public int Number { get; set; } + Range = range; + Enabled = true; + Color = 0xFFFF; + } - /// - /// Gets or sets the maximum range at which this entry may be used, in tiles. A value of -1 signifies no maximum range. - /// - public int Range { get; set; } + /// + /// Gets or sets additional flags used in client communication. + /// + public CMEFlags Flags{ get; set; } - /// - /// Gets or sets the color for this entry. Format is A1-R5-G5-B5. - /// - public int Color { get; set; } + /// + /// Gets or sets the that owns this entry. + /// + public ContextMenu Owner{ get; set; } - /// - /// Gets or sets whether this entry is enabled. When false, the entry will appear in a gray hue and will never be invoked. - /// - public bool Enabled { get; set; } + /// + /// Gets or sets the localization number containing the name of this entry. + /// + public int Number{ get; set; } - /// - /// Gets a value indicating if non local use of this entry is permitted. - /// - public virtual bool NonLocalUse => false; + /// + /// Gets or sets the maximum range at which this entry may be used, in tiles. A value of -1 signifies no maximum range. + /// + public int Range{ get; set; } - /// - /// Instantiates a new ContextMenuEntry with a given localization number (). No maximum range is used. - /// - /// - /// The localization number containing the name of this entry. - /// - /// - public ContextMenuEntry( int number ) : this( number, -1 ) - { - } + /// + /// Gets or sets the color for this entry. Format is A1-R5-G5-B5. + /// + public int Color{ get; set; } - /// - /// Instantiates a new ContextMenuEntry with a given localization number () and maximum range (). - /// - /// - /// The localization number containing the name of this entry. - /// - /// - /// - /// The maximum range at which this entry can be used. - /// - /// - public ContextMenuEntry( int number, int range ) - { - if ( number <= 0x7FFF ) // Legacy code support - Number = 3000000 + number; - else - Number = number; + /// + /// Gets or sets whether this entry is enabled. When false, the entry will appear in a gray hue and + /// will never be invoked. + /// + public bool Enabled{ get; set; } - Range = range; - Enabled = true; - Color = 0xFFFF; - } + /// + /// Gets a value indicating if non local use of this entry is permitted. + /// + public virtual bool NonLocalUse => false; - /// - /// Overridable. Virtual event invoked when the entry is clicked. - /// - public virtual void OnClick() - { - } - } -} + /// + /// Overridable. Virtual event invoked when the entry is clicked. + /// + public virtual void OnClick() + { + } + } +} \ No newline at end of file diff --git a/Server/ContextMenus/OpenBackpackEntry.cs b/Server/ContextMenus/OpenBackpackEntry.cs index 920c038d4..81d4b2399 100644 --- a/Server/ContextMenus/OpenBackpackEntry.cs +++ b/Server/ContextMenus/OpenBackpackEntry.cs @@ -20,18 +20,18 @@ namespace Server.ContextMenus { - public class OpenBackpackEntry : ContextMenuEntry - { - private Mobile m_Mobile; + public class OpenBackpackEntry : ContextMenuEntry + { + private Mobile m_Mobile; - public OpenBackpackEntry( Mobile m ) : base( 6145 ) - { - m_Mobile = m; - } + public OpenBackpackEntry(Mobile m) : base(6145) + { + m_Mobile = m; + } - public override void OnClick() - { - m_Mobile.Use( m_Mobile.Backpack ); - } - } + public override void OnClick() + { + m_Mobile.Use(m_Mobile.Backpack); + } + } } \ No newline at end of file diff --git a/Server/ContextMenus/PaperdollEntry.cs b/Server/ContextMenus/PaperdollEntry.cs index d89134542..cd402f4e6 100644 --- a/Server/ContextMenus/PaperdollEntry.cs +++ b/Server/ContextMenus/PaperdollEntry.cs @@ -20,19 +20,19 @@ namespace Server.ContextMenus { - public class PaperdollEntry : ContextMenuEntry - { - private Mobile m_Mobile; + public class PaperdollEntry : ContextMenuEntry + { + private Mobile m_Mobile; - public PaperdollEntry( Mobile m ) : base( 6123, 18 ) - { - m_Mobile = m; - } + public PaperdollEntry(Mobile m) : base(6123, 18) + { + m_Mobile = m; + } - public override void OnClick() - { - if ( m_Mobile.CanPaperdollBeOpenedBy( Owner.From ) ) - m_Mobile.DisplayPaperdollTo( Owner.From ); - } - } + public override void OnClick() + { + if (m_Mobile.CanPaperdollBeOpenedBy(Owner.From)) + m_Mobile.DisplayPaperdollTo(Owner.From); + } + } } \ No newline at end of file diff --git a/Server/Diagnostics/BaseProfile.cs b/Server/Diagnostics/BaseProfile.cs index c3c161bae..bbc7804a5 100644 --- a/Server/Diagnostics/BaseProfile.cs +++ b/Server/Diagnostics/BaseProfile.cs @@ -19,67 +19,70 @@ ***************************************************************************/ using System; -using System.IO; using System.Collections.Generic; using System.Diagnostics; +using System.IO; -namespace Server.Diagnostics { - public abstract class BaseProfile { - public static void WriteAll( TextWriter op, IEnumerable profiles ) where T : BaseProfile { - List list = new List( profiles ); +namespace Server.Diagnostics +{ + public abstract class BaseProfile + { + private Stopwatch _stopwatch; - list.Sort( delegate( T a, T b ) { - return -a.TotalTime.CompareTo( b.TotalTime ); - } ); + protected BaseProfile(string name) + { + Name = name; - foreach ( T prof in list ) { - prof.WriteTo( op ); - op.WriteLine(); - } - } + _stopwatch = new Stopwatch(); + } - private Stopwatch _stopwatch; + public string Name{ get; } - public string Name { get; } + public long Count{ get; private set; } - public long Count { get; private set; } + public TimeSpan AverageTime => TimeSpan.FromTicks(TotalTime.Ticks / Math.Max(1, Count)); - public TimeSpan AverageTime => TimeSpan.FromTicks( TotalTime.Ticks / Math.Max( 1, Count ) ); + public TimeSpan PeakTime{ get; private set; } - public TimeSpan PeakTime { get; private set; } + public TimeSpan TotalTime{ get; private set; } - public TimeSpan TotalTime { get; private set; } + public static void WriteAll(TextWriter op, IEnumerable profiles) where T : BaseProfile + { + List list = new List(profiles); - protected BaseProfile( string name ) { - Name = name; + list.Sort(delegate(T a, T b) { return -a.TotalTime.CompareTo(b.TotalTime); }); - _stopwatch = new Stopwatch(); - } + foreach (T prof in list) + { + prof.WriteTo(op); + op.WriteLine(); + } + } - public virtual void Start() { - if ( _stopwatch.IsRunning ) { - _stopwatch.Reset(); - } + public virtual void Start() + { + if (_stopwatch.IsRunning) _stopwatch.Reset(); - _stopwatch.Start(); - } + _stopwatch.Start(); + } - public virtual void Finish() { - TimeSpan elapsed = _stopwatch.Elapsed; + public virtual void Finish() + { + TimeSpan elapsed = _stopwatch.Elapsed; - TotalTime += elapsed; + TotalTime += elapsed; - if ( elapsed > PeakTime ) { - PeakTime = elapsed; - } + if (elapsed > PeakTime) PeakTime = elapsed; - Count++; + Count++; - _stopwatch.Reset(); - } + _stopwatch.Reset(); + } - public virtual void WriteTo( TextWriter op ) { - op.Write( "{0,-100} {1,12:N0} {2,12:F5} {3,-12:F5} {4,12:F5}", Name, Count, AverageTime.TotalSeconds, PeakTime.TotalSeconds, TotalTime.TotalSeconds ); - } - } + public virtual void WriteTo(TextWriter op) + { + op.Write("{0,-100} {1,12:N0} {2,12:F5} {3,-12:F5} {4,12:F5}", Name, Count, AverageTime.TotalSeconds, + PeakTime.TotalSeconds, TotalTime.TotalSeconds); + } + } } \ No newline at end of file diff --git a/Server/Diagnostics/GumpProfile.cs b/Server/Diagnostics/GumpProfile.cs index 3ba62e302..71be281d5 100644 --- a/Server/Diagnostics/GumpProfile.cs +++ b/Server/Diagnostics/GumpProfile.cs @@ -21,28 +21,28 @@ using System; using System.Collections.Generic; -namespace Server.Diagnostics { - public class GumpProfile : BaseProfile { - private static Dictionary _profiles = new Dictionary(); +namespace Server.Diagnostics +{ + public class GumpProfile : BaseProfile + { + private static Dictionary _profiles = new Dictionary(); - public static IEnumerable Profiles => _profiles.Values; + public GumpProfile(Type type) + : base(type.FullName) + { + } - public static GumpProfile Acquire( Type type ) { - if ( !Core.Profiling ) { - return null; - } + public static IEnumerable Profiles => _profiles.Values; - GumpProfile prof; + public static GumpProfile Acquire(Type type) + { + if (!Core.Profiling) return null; - if ( !_profiles.TryGetValue( type, out prof ) ) { - _profiles.Add( type, prof = new GumpProfile( type ) ); - } + GumpProfile prof; - return prof; - } + if (!_profiles.TryGetValue(type, out prof)) _profiles.Add(type, prof = new GumpProfile(type)); - public GumpProfile( Type type ) - : base( type.FullName ) { - } - } + return prof; + } + } } \ No newline at end of file diff --git a/Server/Diagnostics/PacketProfile.cs b/Server/Diagnostics/PacketProfile.cs index 92f8d88f6..22899de93 100644 --- a/Server/Diagnostics/PacketProfile.cs +++ b/Server/Diagnostics/PacketProfile.cs @@ -20,84 +20,94 @@ using System; using System.Collections.Generic; +using System.IO; using System.Runtime.CompilerServices; using System.Threading; -using System.IO; -namespace Server.Diagnostics { - public abstract class BasePacketProfile : BaseProfile { - public long TotalLength { get; private set; } +namespace Server.Diagnostics +{ + public abstract class BasePacketProfile : BaseProfile + { + protected BasePacketProfile(string name) + : base(name) + { + } - public double AverageLength => ( double ) TotalLength / Math.Max( 1, Count ); + public long TotalLength{ get; private set; } - protected BasePacketProfile(string name) - : base( name ) { - } + public double AverageLength => (double)TotalLength / Math.Max(1, Count); - public void Finish( int length ) { - Finish(); + public void Finish(int length) + { + Finish(); - TotalLength += length; - } + TotalLength += length; + } - public override void WriteTo( TextWriter op ) { - base.WriteTo( op ); + public override void WriteTo(TextWriter op) + { + base.WriteTo(op); - op.Write( "\t{0,12:F2} {1,-12:N0}", AverageLength, TotalLength ); - } - } + op.Write("\t{0,12:F2} {1,-12:N0}", AverageLength, TotalLength); + } + } - public class PacketSendProfile : BasePacketProfile { - private static Dictionary _profiles = new Dictionary(); + public class PacketSendProfile : BasePacketProfile + { + private static Dictionary _profiles = new Dictionary(); - public static IEnumerable Profiles => _profiles.Values; + private long _created; - [MethodImpl(MethodImplOptions.Synchronized)] - public static PacketSendProfile Acquire( Type type ) { - PacketSendProfile prof; + public PacketSendProfile(Type type) + : base(type.FullName) + { + } - if ( !_profiles.TryGetValue( type, out prof ) ) { - _profiles.Add( type, prof = new PacketSendProfile( type ) ); - } + public static IEnumerable Profiles => _profiles.Values; - return prof; - } + [MethodImpl(MethodImplOptions.Synchronized)] + public static PacketSendProfile Acquire(Type type) + { + PacketSendProfile prof; - private long _created; + if (!_profiles.TryGetValue(type, out prof)) _profiles.Add(type, prof = new PacketSendProfile(type)); - public void Increment() { - Interlocked.Increment(ref _created); - } + return prof; + } - public PacketSendProfile( Type type ) - : base( type.FullName ) { - } + public void Increment() + { + Interlocked.Increment(ref _created); + } - public override void WriteTo( TextWriter op ) { - base.WriteTo( op ); + public override void WriteTo(TextWriter op) + { + base.WriteTo(op); - op.Write( "\t{0,12:N0}", _created ); - } - } + op.Write("\t{0,12:N0}", _created); + } + } - public class PacketReceiveProfile : BasePacketProfile { - private static Dictionary _profiles = new Dictionary(); + public class PacketReceiveProfile : BasePacketProfile + { + private static Dictionary _profiles = new Dictionary(); - public static IEnumerable Profiles => _profiles.Values; + public PacketReceiveProfile(int packetId) + : base($"0x{packetId:X2}") + { + } - [MethodImpl(MethodImplOptions.Synchronized)] - public static PacketReceiveProfile Acquire( int packetId ) { - PacketReceiveProfile prof; + public static IEnumerable Profiles => _profiles.Values; - if ( !_profiles.TryGetValue( packetId, out prof ) ) { - _profiles.Add( packetId, prof = new PacketReceiveProfile( packetId ) ); - } + [MethodImpl(MethodImplOptions.Synchronized)] + public static PacketReceiveProfile Acquire(int packetId) + { + PacketReceiveProfile prof; - return prof; - } + if (!_profiles.TryGetValue(packetId, out prof)) + _profiles.Add(packetId, prof = new PacketReceiveProfile(packetId)); - public PacketReceiveProfile( int packetId ) - : base($"0x{packetId:X2}") { - } - } + return prof; + } + } } \ No newline at end of file diff --git a/Server/Diagnostics/TargetProfile.cs b/Server/Diagnostics/TargetProfile.cs index 6089b4b12..480725c4b 100644 --- a/Server/Diagnostics/TargetProfile.cs +++ b/Server/Diagnostics/TargetProfile.cs @@ -21,28 +21,28 @@ using System; using System.Collections.Generic; -namespace Server.Diagnostics { - public class TargetProfile : BaseProfile { - private static Dictionary _profiles = new Dictionary(); +namespace Server.Diagnostics +{ + public class TargetProfile : BaseProfile + { + private static Dictionary _profiles = new Dictionary(); - public static IEnumerable Profiles => _profiles.Values; + public TargetProfile(Type type) + : base(type.FullName) + { + } - public static TargetProfile Acquire( Type type ) { - if ( !Core.Profiling ) { - return null; - } + public static IEnumerable Profiles => _profiles.Values; - TargetProfile prof; + public static TargetProfile Acquire(Type type) + { + if (!Core.Profiling) return null; - if ( !_profiles.TryGetValue( type, out prof ) ) { - _profiles.Add( type, prof = new TargetProfile( type ) ); - } + TargetProfile prof; - return prof; - } + if (!_profiles.TryGetValue(type, out prof)) _profiles.Add(type, prof = new TargetProfile(type)); - public TargetProfile( Type type ) - : base( type.FullName ) { - } - } + return prof; + } + } } \ No newline at end of file diff --git a/Server/Diagnostics/TimerProfile.cs b/Server/Diagnostics/TimerProfile.cs index 2411a4ed7..e0b633772 100644 --- a/Server/Diagnostics/TimerProfile.cs +++ b/Server/Diagnostics/TimerProfile.cs @@ -21,40 +21,41 @@ using System.Collections.Generic; using System.IO; -namespace Server.Diagnostics { - public class TimerProfile : BaseProfile { - private static Dictionary _profiles = new Dictionary(); +namespace Server.Diagnostics +{ + public class TimerProfile : BaseProfile + { + private static Dictionary _profiles = new Dictionary(); - public static IEnumerable Profiles => _profiles.Values; + public TimerProfile(string name) + : base(name) + { + } - public static TimerProfile Acquire( string name ) { - if ( !Core.Profiling ) { - return null; - } + public static IEnumerable Profiles => _profiles.Values; - TimerProfile prof; + public long Created{ get; set; } - if ( !_profiles.TryGetValue( name, out prof ) ) { - _profiles.Add( name, prof = new TimerProfile( name ) ); - } + public long Started{ get; set; } - return prof; - } + public long Stopped{ get; set; } - public long Created { get; set; } + public static TimerProfile Acquire(string name) + { + if (!Core.Profiling) return null; - public long Started { get; set; } + TimerProfile prof; - public long Stopped { get; set; } + if (!_profiles.TryGetValue(name, out prof)) _profiles.Add(name, prof = new TimerProfile(name)); - public TimerProfile( string name ) - : base( name ) { - } + return prof; + } - public override void WriteTo( TextWriter op ) { - base.WriteTo( op ); + public override void WriteTo(TextWriter op) + { + base.WriteTo(op); - op.Write( "\t{0,12:N0} {1,12:N0} {2,-12:N0}", Created, Started, Stopped ); - } - } + op.Write("\t{0,12:N0} {1,12:N0} {2,-12:N0}", Created, Started, Stopped); + } + } } \ No newline at end of file diff --git a/Server/Effects.cs b/Server/Effects.cs index c709eee79..56372489c 100644 --- a/Server/Effects.cs +++ b/Server/Effects.cs @@ -22,354 +22,396 @@ using Server.Network; namespace Server { - public enum EffectLayer - { - Head = 0, - RightHand = 1, - LeftHand = 2, - Waist = 3, - LeftFoot = 4, - RightFoot = 5, - CenterFeet = 7 - } + public enum EffectLayer + { + Head = 0, + RightHand = 1, + LeftHand = 2, + Waist = 3, + LeftFoot = 4, + RightFoot = 5, + CenterFeet = 7 + } - public enum ParticleSupportType - { - Full, - Detect, - None - } + public enum ParticleSupportType + { + Full, + Detect, + None + } + + public static class Effects + { + public static ParticleSupportType ParticleSupportType{ get; set; } = ParticleSupportType.Detect; + + public static bool SendParticlesTo(NetState state) + { + return ParticleSupportType == ParticleSupportType.Full || + ParticleSupportType == ParticleSupportType.Detect && state.IsUOTDClient; + } + + public static void PlaySound(IPoint3D p, Map map, int soundID) + { + if (soundID <= -1) + return; + + if (map != null) + { + Packet playSound = null; + + IPooledEnumerable eable = map.GetClientsInRange(new Point3D(p)); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + + if (playSound == null) + playSound = Packet.Acquire(new PlaySound(soundID, p)); + + state.Send(playSound); + } + + Packet.Release(playSound); + + eable.Free(); + } + } + + public static void SendBoltEffect(IEntity e) + { + SendBoltEffect(e, true, 0); + } + + public static void SendBoltEffect(IEntity e, bool sound) + { + SendBoltEffect(e, sound, 0); + } + + public static void SendBoltEffect(IEntity e, bool sound, int hue) + { + Map map = e.Map; + + if (map == null) + return; + + e.ProcessDelta(); + + Packet preEffect = null, boltEffect = null, playSound = null; + + IPooledEnumerable eable = map.GetClientsInRange(e.Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(e)) + { + if (SendParticlesTo(state)) + { + if (preEffect == null) + preEffect = Packet.Acquire(new TargetParticleEffect(e, 0, 10, 5, 0, 0, 5031, 3, 0)); + + state.Send(preEffect); + } + + if (boltEffect == null) + boltEffect = Packet.Acquire(new BoltEffect(e, hue)); + + state.Send(boltEffect); + + if (sound) + { + if (playSound == null) + playSound = Packet.Acquire(new PlaySound(0x29, e)); + + state.Send(playSound); + } + } + + Packet.Release(preEffect); + Packet.Release(boltEffect); + Packet.Release(playSound); + + eable.Free(); + } + + public static void SendLocationEffect(IPoint3D p, Map map, int itemID, int duration) + { + SendLocationEffect(p, map, itemID, duration, 10, 0, 0); + } + + public static void SendLocationEffect(IPoint3D p, Map map, int itemID, int duration, int speed) + { + SendLocationEffect(p, map, itemID, duration, speed, 0, 0); + } + + public static void SendLocationEffect(IPoint3D p, Map map, int itemID, int duration, int hue, int renderMode) + { + SendLocationEffect(p, map, itemID, duration, 10, hue, renderMode); + } + + public static void SendLocationEffect(IPoint3D p, Map map, int itemID, int duration, int speed, int hue, + int renderMode) + { + SendPacket(p, map, new LocationEffect(p, itemID, speed, duration, hue, renderMode)); + } - public static class Effects - { - public static ParticleSupportType ParticleSupportType { get; set; } = ParticleSupportType.Detect; + public static void SendLocationParticles(IEntity e, int itemID, int speed, int duration, int effect) + { + SendLocationParticles(e, itemID, speed, duration, 0, 0, effect, 0); + } - public static bool SendParticlesTo( NetState state ) - { - return ( ParticleSupportType == ParticleSupportType.Full || (ParticleSupportType == ParticleSupportType.Detect && state.IsUOTDClient) ); - } - - public static void PlaySound( IPoint3D p, Map map, int soundID ) - { - if ( soundID <= -1 ) - return; - - if ( map != null ) - { - Packet playSound = null; - - IPooledEnumerable eable = map.GetClientsInRange( new Point3D( p ) ); - - foreach ( NetState state in eable ) { - state.Mobile.ProcessDelta(); - - if ( playSound == null ) - playSound = Packet.Acquire( new PlaySound( soundID, p ) ); - - state.Send( playSound ); - } - - Packet.Release( playSound ); - - eable.Free(); - } - } - - public static void SendBoltEffect( IEntity e ) - { - SendBoltEffect( e, true, 0 ); - } - - public static void SendBoltEffect( IEntity e, bool sound ) - { - SendBoltEffect( e, sound, 0 ); - } - - public static void SendBoltEffect( IEntity e, bool sound, int hue ) - { - Map map = e.Map; - - if ( map == null ) - return; - - e.ProcessDelta(); - - Packet preEffect = null, boltEffect = null, playSound = null; - - IPooledEnumerable eable = map.GetClientsInRange(e.Location); - - foreach ( NetState state in eable ) { - if ( state.Mobile.CanSee( e ) ) { - if ( SendParticlesTo( state ) ) { - if ( preEffect == null ) - preEffect = Packet.Acquire( new TargetParticleEffect( e, 0, 10, 5, 0, 0, 5031, 3, 0 ) ); - - state.Send( preEffect ); - } - - if ( boltEffect == null ) - boltEffect = Packet.Acquire( new BoltEffect( e, hue ) ); - - state.Send( boltEffect ); - - if ( sound ) { - if ( playSound == null ) - playSound = Packet.Acquire( new PlaySound( 0x29, e ) ); - - state.Send( playSound ); - } - } - } - - Packet.Release( preEffect ); - Packet.Release( boltEffect ); - Packet.Release( playSound ); - - eable.Free(); - } - - public static void SendLocationEffect( IPoint3D p, Map map, int itemID, int duration ) - { - SendLocationEffect( p, map, itemID, duration, 10, 0, 0 ); - } - - public static void SendLocationEffect( IPoint3D p, Map map, int itemID, int duration, int speed ) - { - SendLocationEffect( p, map, itemID, duration, speed, 0, 0 ); - } - - public static void SendLocationEffect( IPoint3D p, Map map, int itemID, int duration, int hue, int renderMode ) - { - SendLocationEffect( p, map, itemID, duration, 10, hue, renderMode ); - } - - public static void SendLocationEffect( IPoint3D p, Map map, int itemID, int duration, int speed, int hue, int renderMode ) - { - SendPacket( p, map, new LocationEffect( p, itemID, speed, duration, hue, renderMode ) ); - } - - public static void SendLocationParticles( IEntity e, int itemID, int speed, int duration, int effect ) - { - SendLocationParticles( e, itemID, speed, duration, 0, 0, effect, 0 ); - } - - public static void SendLocationParticles( IEntity e, int itemID, int speed, int duration, int effect, int unknown ) - { - SendLocationParticles( e, itemID, speed, duration, 0, 0, effect, unknown ); - } - - public static void SendLocationParticles( IEntity e, int itemID, int speed, int duration, int hue, int renderMode, int effect, int unknown ) - { - Map map = e.Map; - - if ( map != null ) - { - Packet particles = null, regular = null; - - IPooledEnumerable eable = map.GetClientsInRange(e.Location); - - foreach ( NetState state in eable ) { - state.Mobile.ProcessDelta(); - - if ( SendParticlesTo( state ) ) { - if ( particles == null ) - particles = Packet.Acquire( new LocationParticleEffect( e, itemID, speed, duration, hue, renderMode, effect, unknown ) ); - - state.Send( particles ); - } else if ( itemID != 0 ) { - if ( regular == null ) - regular = Packet.Acquire( new LocationEffect( e, itemID, speed, duration, hue, renderMode ) ); - - state.Send( regular ); - } - } - - Packet.Release( particles ); - Packet.Release( regular ); - - eable.Free(); - } - //SendPacket( e.Location, e.Map, new LocationParticleEffect( e, itemID, speed, duration, hue, renderMode, effect, unknown ) ); - } - - public static void SendTargetEffect( IEntity target, int itemID, int duration ) - { - SendTargetEffect( target, itemID, duration, 0, 0 ); - } - - public static void SendTargetEffect( IEntity target, int itemID, int speed, int duration ) - { - SendTargetEffect( target, itemID, speed, duration, 0, 0 ); - } - - public static void SendTargetEffect( IEntity target, int itemID, int duration, int hue, int renderMode ) - { - SendTargetEffect( target, itemID, 10, duration, hue, renderMode ); - } - - public static void SendTargetEffect( IEntity target, int itemID, int speed, int duration, int hue, int renderMode ) - { - if ( target is Mobile mobile ) - mobile.ProcessDelta(); - - SendPacket( target.Location, target.Map, new TargetEffect( target, itemID, speed, duration, hue, renderMode ) ); - } - - public static void SendTargetParticles( IEntity target, int itemID, int speed, int duration, int effect, EffectLayer layer ) - { - SendTargetParticles( target, itemID, speed, duration, 0, 0, effect, layer, 0 ); - } - - public static void SendTargetParticles( IEntity target, int itemID, int speed, int duration, int effect, EffectLayer layer, int unknown ) - { - SendTargetParticles( target, itemID, speed, duration, 0, 0, effect, layer, unknown ); - } - - public static void SendTargetParticles( IEntity target, int itemID, int speed, int duration, int hue, int renderMode, int effect, EffectLayer layer, int unknown ) - { - if ( target is Mobile mobile ) - mobile.ProcessDelta(); - - Map map = target.Map; - - if ( map != null ) - { - Packet particles = null, regular = null; - - IPooledEnumerable eable = map.GetClientsInRange(target.Location); - - foreach ( NetState state in eable ) { - state.Mobile.ProcessDelta(); - - if ( SendParticlesTo( state ) ) { - if ( particles == null ) - particles = Packet.Acquire( new TargetParticleEffect( target, itemID, speed, duration, hue, renderMode, effect, (int)layer, unknown ) ); - - state.Send( particles ); - } else if ( itemID != 0 ) { - if ( regular == null ) - regular = Packet.Acquire( new TargetEffect( target, itemID, speed, duration, hue, renderMode ) ); - - state.Send( regular ); - } - } - - Packet.Release( particles ); - Packet.Release( regular ); - - eable.Free(); - } - - //SendPacket( target.Location, target.Map, new TargetParticleEffect( target, itemID, speed, duration, hue, renderMode, effect, (int)layer, unknown ) ); - } - - public static void SendMovingEffect( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes ) - { - SendMovingEffect( from, to, itemID, speed, duration, fixedDirection, explodes, 0, 0 ); - } - - public static void SendMovingEffect( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode ) - { - if ( from is Mobile mobile ) - mobile.ProcessDelta(); - - if ( to is Mobile mobile1 ) - mobile1.ProcessDelta(); - - SendPacket( from.Location, from.Map, new MovingEffect( from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode ) ); - } - - public static void SendMovingParticles( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int effect, int explodeEffect, int explodeSound ) - { - SendMovingParticles( from, to, itemID, speed, duration, fixedDirection, explodes, 0, 0, effect, explodeEffect, explodeSound, 0 ); - } - - public static void SendMovingParticles( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int effect, int explodeEffect, int explodeSound, int unknown ) - { - SendMovingParticles( from, to, itemID, speed, duration, fixedDirection, explodes, 0, 0, effect, explodeEffect, explodeSound, unknown ); - } - - public static void SendMovingParticles( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, int unknown ) - { - SendMovingParticles( from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, (EffectLayer)255, unknown ); - } - - public static void SendMovingParticles( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, EffectLayer layer, int unknown ) - { - if ( from is Mobile mobile ) - mobile.ProcessDelta(); - - if ( to is Mobile mobile1 ) - mobile1.ProcessDelta(); - - Map map = from.Map; - - if ( map != null ) - { - Packet particles = null, regular = null; - - IPooledEnumerable eable = map.GetClientsInRange(from.Location); - - foreach ( NetState state in eable ) { - state.Mobile.ProcessDelta(); - - if ( SendParticlesTo( state ) ) { - if ( particles == null ) - particles = Packet.Acquire( new MovingParticleEffect( from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, layer, unknown ) ); - - state.Send( particles ); - } else if ( itemID > 1 ) { - if ( regular == null ) - regular = Packet.Acquire( new MovingEffect( from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode ) ); - - state.Send( regular ); - } - } - - Packet.Release( particles ); - Packet.Release( regular ); - - eable.Free(); - } - - //SendPacket( from.Location, from.Map, new MovingParticleEffect( from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, unknown ) ); - } - - public static void SendPacket( Point3D origin, Map map, Packet p ) - { - if ( map != null ) { - IPooledEnumerable eable = map.GetClientsInRange(origin); - - p.Acquire(); - - foreach ( NetState state in eable ) { - state.Mobile.ProcessDelta(); - state.Send( p ); - } - - p.Release(); - - eable.Free(); - } - } - - public static void SendPacket( IPoint3D origin, Map map, Packet p ) - { - if ( map != null ) - { - IPooledEnumerable eable = map.GetClientsInRange(new Point3D(origin)); - - p.Acquire(); - - foreach ( NetState state in eable ) { - state.Mobile.ProcessDelta(); - state.Send( p ); - } - - p.Release(); - - eable.Free(); - } - } - } -} + public static void SendLocationParticles(IEntity e, int itemID, int speed, int duration, int effect, int unknown) + { + SendLocationParticles(e, itemID, speed, duration, 0, 0, effect, unknown); + } + + public static void SendLocationParticles(IEntity e, int itemID, int speed, int duration, int hue, int renderMode, + int effect, int unknown) + { + Map map = e.Map; + + if (map != null) + { + Packet particles = null, regular = null; + + IPooledEnumerable eable = map.GetClientsInRange(e.Location); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + + if (SendParticlesTo(state)) + { + if (particles == null) + particles = Packet.Acquire(new LocationParticleEffect(e, itemID, speed, duration, hue, + renderMode, effect, unknown)); + + state.Send(particles); + } + else if (itemID != 0) + { + if (regular == null) + regular = Packet.Acquire(new LocationEffect(e, itemID, speed, duration, hue, renderMode)); + + state.Send(regular); + } + } + + Packet.Release(particles); + Packet.Release(regular); + + eable.Free(); + } + + //SendPacket( e.Location, e.Map, new LocationParticleEffect( e, itemID, speed, duration, hue, renderMode, effect, unknown ) ); + } + + public static void SendTargetEffect(IEntity target, int itemID, int duration) + { + SendTargetEffect(target, itemID, duration, 0, 0); + } + + public static void SendTargetEffect(IEntity target, int itemID, int speed, int duration) + { + SendTargetEffect(target, itemID, speed, duration, 0, 0); + } + + public static void SendTargetEffect(IEntity target, int itemID, int duration, int hue, int renderMode) + { + SendTargetEffect(target, itemID, 10, duration, hue, renderMode); + } + + public static void SendTargetEffect(IEntity target, int itemID, int speed, int duration, int hue, int renderMode) + { + if (target is Mobile mobile) + mobile.ProcessDelta(); + + SendPacket(target.Location, target.Map, new TargetEffect(target, itemID, speed, duration, hue, renderMode)); + } + + public static void SendTargetParticles(IEntity target, int itemID, int speed, int duration, int effect, + EffectLayer layer) + { + SendTargetParticles(target, itemID, speed, duration, 0, 0, effect, layer, 0); + } + + public static void SendTargetParticles(IEntity target, int itemID, int speed, int duration, int effect, + EffectLayer layer, int unknown) + { + SendTargetParticles(target, itemID, speed, duration, 0, 0, effect, layer, unknown); + } + + public static void SendTargetParticles(IEntity target, int itemID, int speed, int duration, int hue, int renderMode, + int effect, EffectLayer layer, int unknown) + { + if (target is Mobile mobile) + mobile.ProcessDelta(); + + Map map = target.Map; + + if (map != null) + { + Packet particles = null, regular = null; + + IPooledEnumerable eable = map.GetClientsInRange(target.Location); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + + if (SendParticlesTo(state)) + { + if (particles == null) + particles = Packet.Acquire(new TargetParticleEffect(target, itemID, speed, duration, hue, + renderMode, effect, (int)layer, unknown)); + + state.Send(particles); + } + else if (itemID != 0) + { + if (regular == null) + regular = Packet.Acquire(new TargetEffect(target, itemID, speed, duration, hue, renderMode)); + + state.Send(regular); + } + } + + Packet.Release(particles); + Packet.Release(regular); + + eable.Free(); + } + + //SendPacket( target.Location, target.Map, new TargetParticleEffect( target, itemID, speed, duration, hue, renderMode, effect, (int)layer, unknown ) ); + } + + public static void SendMovingEffect(IEntity from, IEntity to, int itemID, int speed, int duration, + bool fixedDirection, bool explodes) + { + SendMovingEffect(from, to, itemID, speed, duration, fixedDirection, explodes, 0, 0); + } + + public static void SendMovingEffect(IEntity from, IEntity to, int itemID, int speed, int duration, + bool fixedDirection, bool explodes, int hue, int renderMode) + { + if (from is Mobile mobile) + mobile.ProcessDelta(); + + if (to is Mobile mobile1) + mobile1.ProcessDelta(); + + SendPacket(from.Location, from.Map, + new MovingEffect(from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode)); + } + + public static void SendMovingParticles(IEntity from, IEntity to, int itemID, int speed, int duration, + bool fixedDirection, bool explodes, int effect, int explodeEffect, int explodeSound) + { + SendMovingParticles(from, to, itemID, speed, duration, fixedDirection, explodes, 0, 0, effect, explodeEffect, + explodeSound, 0); + } + + public static void SendMovingParticles(IEntity from, IEntity to, int itemID, int speed, int duration, + bool fixedDirection, bool explodes, int effect, int explodeEffect, int explodeSound, int unknown) + { + SendMovingParticles(from, to, itemID, speed, duration, fixedDirection, explodes, 0, 0, effect, explodeEffect, + explodeSound, unknown); + } + + public static void SendMovingParticles(IEntity from, IEntity to, int itemID, int speed, int duration, + bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, + int unknown) + { + SendMovingParticles(from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, + explodeEffect, explodeSound, (EffectLayer)255, unknown); + } + + public static void SendMovingParticles(IEntity from, IEntity to, int itemID, int speed, int duration, + bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, + EffectLayer layer, int unknown) + { + if (from is Mobile mobile) + mobile.ProcessDelta(); + + if (to is Mobile mobile1) + mobile1.ProcessDelta(); + + Map map = from.Map; + + if (map != null) + { + Packet particles = null, regular = null; + + IPooledEnumerable eable = map.GetClientsInRange(from.Location); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + + if (SendParticlesTo(state)) + { + if (particles == null) + particles = Packet.Acquire(new MovingParticleEffect(from, to, itemID, speed, duration, + fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, layer, + unknown)); + + state.Send(particles); + } + else if (itemID > 1) + { + if (regular == null) + regular = Packet.Acquire(new MovingEffect(from, to, itemID, speed, duration, fixedDirection, + explodes, hue, renderMode)); + + state.Send(regular); + } + } + + Packet.Release(particles); + Packet.Release(regular); + + eable.Free(); + } + + //SendPacket( from.Location, from.Map, new MovingParticleEffect( from, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, unknown ) ); + } + + public static void SendPacket(Point3D origin, Map map, Packet p) + { + if (map != null) + { + IPooledEnumerable eable = map.GetClientsInRange(origin); + + p.Acquire(); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + state.Send(p); + } + + p.Release(); + + eable.Free(); + } + } + + public static void SendPacket(IPoint3D origin, Map map, Packet p) + { + if (map != null) + { + IPooledEnumerable eable = map.GetClientsInRange(new Point3D(origin)); + + p.Acquire(); + + foreach (NetState state in eable) + { + state.Mobile.ProcessDelta(); + state.Send(p); + } + + p.Release(); + + eable.Free(); + } + } + } +} \ No newline at end of file diff --git a/Server/EventLog.cs b/Server/EventLog.cs index 0b29a4365..86599716b 100644 --- a/Server/EventLog.cs +++ b/Server/EventLog.cs @@ -18,50 +18,46 @@ * ***************************************************************************/ -using System; using System.Diagnostics; using DiagELog = System.Diagnostics.EventLog; namespace Server { - public static class EventLog - { - static EventLog() - { - if ( !DiagELog.SourceExists( "RunUO" ) ) - { - DiagELog.CreateEventSource( "RunUO", "Application" ); - } - } + public static class EventLog + { + static EventLog() + { + if (!DiagELog.SourceExists("RunUO")) DiagELog.CreateEventSource("RunUO", "Application"); + } - public static void Error( int eventID, string text ) - { - DiagELog.WriteEntry( "RunUO", text, EventLogEntryType.Error, eventID ); - } + public static void Error(int eventID, string text) + { + DiagELog.WriteEntry("RunUO", text, EventLogEntryType.Error, eventID); + } - public static void Error( int eventID, string format, params object[] args ) - { - Error( eventID, string.Format( format, args ) ); - } + public static void Error(int eventID, string format, params object[] args) + { + Error(eventID, string.Format(format, args)); + } - public static void Warning( int eventID, string text ) - { - DiagELog.WriteEntry( "RunUO", text, EventLogEntryType.Warning, eventID ); - } + public static void Warning(int eventID, string text) + { + DiagELog.WriteEntry("RunUO", text, EventLogEntryType.Warning, eventID); + } - public static void Warning( int eventID, string format, params object[] args ) - { - Warning( eventID, string.Format( format, args ) ); - } + public static void Warning(int eventID, string format, params object[] args) + { + Warning(eventID, string.Format(format, args)); + } - public static void Inform( int eventID, string text ) - { - DiagELog.WriteEntry( "RunUO", text, EventLogEntryType.Information, eventID ); - } + public static void Inform(int eventID, string text) + { + DiagELog.WriteEntry("RunUO", text, EventLogEntryType.Information, eventID); + } - public static void Inform( int eventID, string format, params object[] args ) - { - Inform( eventID, string.Format( format, args ) ); - } - } + public static void Inform(int eventID, string format, params object[] args) + { + Inform(eventID, string.Format(format, args)); + } + } } \ No newline at end of file diff --git a/Server/EventSink.cs b/Server/EventSink.cs index efc93f644..81fbbba74 100644 --- a/Server/EventSink.cs +++ b/Server/EventSink.cs @@ -19,1074 +19,1114 @@ ***************************************************************************/ using System; +using System.Collections.Generic; using System.Net; using System.Net.Sockets; -using System.Collections.Generic; using Server.Accounting; -using Server.Network; -using Server.Guilds; using Server.Commands; +using Server.Guilds; +using Server.Network; namespace Server { - public delegate void CharacterCreatedEventHandler( CharacterCreatedEventArgs e ); - public delegate void OpenDoorMacroEventHandler( OpenDoorMacroEventArgs e ); - public delegate void SpeechEventHandler( SpeechEventArgs e ); - public delegate void LoginEventHandler( LoginEventArgs e ); - public delegate void ServerListEventHandler( ServerListEventArgs e ); - public delegate void MovementEventHandler( MovementEventArgs e ); - public delegate void HungerChangedEventHandler( HungerChangedEventArgs e ); - public delegate void CrashedEventHandler( CrashedEventArgs e ); - public delegate void ShutdownEventHandler( ShutdownEventArgs e ); - public delegate void HelpRequestEventHandler( HelpRequestEventArgs e ); - public delegate void DisarmRequestEventHandler( DisarmRequestEventArgs e ); - public delegate void StunRequestEventHandler( StunRequestEventArgs e ); - public delegate void OpenSpellbookRequestEventHandler( OpenSpellbookRequestEventArgs e ); - public delegate void CastSpellRequestEventHandler( CastSpellRequestEventArgs e ); - public delegate void BandageTargetRequestEventHandler( BandageTargetRequestEventArgs e ); - public delegate void AnimateRequestEventHandler( AnimateRequestEventArgs e ); - public delegate void LogoutEventHandler( LogoutEventArgs e ); - public delegate void SocketConnectEventHandler( SocketConnectEventArgs e ); - public delegate void ConnectedEventHandler( ConnectedEventArgs e ); - public delegate void DisconnectedEventHandler( DisconnectedEventArgs e ); - public delegate void RenameRequestEventHandler( RenameRequestEventArgs e ); - public delegate void PlayerDeathEventHandler( PlayerDeathEventArgs e ); - public delegate void VirtueGumpRequestEventHandler( VirtueGumpRequestEventArgs e ); - public delegate void VirtueItemRequestEventHandler( VirtueItemRequestEventArgs e ); - public delegate void VirtueMacroRequestEventHandler( VirtueMacroRequestEventArgs e ); - public delegate void ChatRequestEventHandler( ChatRequestEventArgs e ); - public delegate void AccountLoginEventHandler( AccountLoginEventArgs e ); - public delegate void PaperdollRequestEventHandler( PaperdollRequestEventArgs e ); - public delegate void ProfileRequestEventHandler( ProfileRequestEventArgs e ); - public delegate void ChangeProfileRequestEventHandler( ChangeProfileRequestEventArgs e ); - public delegate void AggressiveActionEventHandler( AggressiveActionEventArgs e ); - public delegate void GameLoginEventHandler( GameLoginEventArgs e ); - public delegate void DeleteRequestEventHandler( DeleteRequestEventArgs e ); - public delegate void WorldLoadEventHandler(); - public delegate void WorldSaveEventHandler( WorldSaveEventArgs e ); - public delegate void SetAbilityEventHandler( SetAbilityEventArgs e ); - public delegate void FastWalkEventHandler( FastWalkEventArgs e ); - public delegate void ServerStartedEventHandler(); - public delegate void CreateGuildHandler( CreateGuildEventArgs e ); - public delegate void GuildGumpRequestHandler( GuildGumpRequestArgs e ); - public delegate void QuestGumpRequestHandler( QuestGumpRequestArgs e ); - public delegate void ClientVersionReceivedHandler( ClientVersionReceivedArgs e ); - - public class ClientVersionReceivedArgs : EventArgs - { - public NetState State { get; } - - public ClientVersion Version { get; } - - public ClientVersionReceivedArgs( NetState state, ClientVersion cv ) - { - State = state; - Version = cv; - } - } - - public class CreateGuildEventArgs : EventArgs - { - public int Id { get; set; } - - public BaseGuild Guild { get; set; } - - public CreateGuildEventArgs( int id ) - { - Id = id; - } - } - - public class GuildGumpRequestArgs : EventArgs - { - public Mobile Mobile { get; } - - public GuildGumpRequestArgs( Mobile mobile ) - { - Mobile = mobile; - } - } - - public class QuestGumpRequestArgs : EventArgs - { - public Mobile Mobile { get; } - - public QuestGumpRequestArgs( Mobile mobile ) - { - Mobile = mobile; - } - } - - public class SetAbilityEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public int Index { get; } - - public SetAbilityEventArgs( Mobile mobile, int index ) - { - Mobile = mobile; - Index = index; - } - } - - public class DeleteRequestEventArgs : EventArgs - { - public NetState State { get; } - - public int Index { get; } - - public DeleteRequestEventArgs( NetState state, int index ) - { - State = state; - Index = index; - } - } - - public class GameLoginEventArgs : EventArgs - { - public NetState State { get; } - - public string Username { get; } - - public string Password { get; } - - public bool Accepted { get; set; } - - public CityInfo[] CityInfo { get; set; } - - public GameLoginEventArgs( NetState state, string un, string pw ) - { - State = state; - Username = un; - Password = pw; - } - } - - public class AggressiveActionEventArgs : EventArgs - { - public Mobile Aggressed { get; private set; } - - public Mobile Aggressor { get; private set; } - - public bool Criminal { get; private set; } - - private static Queue m_Pool = new Queue(); - - public static AggressiveActionEventArgs Create( Mobile aggressed, Mobile aggressor, bool criminal ) - { - AggressiveActionEventArgs args; + public delegate void CharacterCreatedEventHandler(CharacterCreatedEventArgs e); - if ( m_Pool.Count > 0 ) - { - args = m_Pool.Dequeue(); - - args.Aggressed = aggressed; - args.Aggressor = aggressor; - args.Criminal = criminal; - } - else - { - args = new AggressiveActionEventArgs( aggressed, aggressor, criminal ); - } + public delegate void OpenDoorMacroEventHandler(OpenDoorMacroEventArgs e); - return args; - } - - private AggressiveActionEventArgs( Mobile aggressed, Mobile aggressor, bool criminal ) - { - Aggressed = aggressed; - Aggressor = aggressor; - Criminal = criminal; - } - - public void Free() - { - m_Pool.Enqueue( this ); - } - } + public delegate void SpeechEventHandler(SpeechEventArgs e); - public class ProfileRequestEventArgs : EventArgs - { - public Mobile Beholder { get; } + public delegate void LoginEventHandler(LoginEventArgs e); - public Mobile Beheld { get; } - - public ProfileRequestEventArgs( Mobile beholder, Mobile beheld ) - { - Beholder = beholder; - Beheld = beheld; - } - } - - public class ChangeProfileRequestEventArgs : EventArgs - { - public Mobile Beholder { get; } - - public Mobile Beheld { get; } - - public string Text { get; } - - public ChangeProfileRequestEventArgs( Mobile beholder, Mobile beheld, string text ) - { - Beholder = beholder; - Beheld = beheld; - Text = text; - } - } - - public class PaperdollRequestEventArgs : EventArgs - { - public Mobile Beholder { get; } + public delegate void ServerListEventHandler(ServerListEventArgs e); - public Mobile Beheld { get; } + public delegate void MovementEventHandler(MovementEventArgs e); - public PaperdollRequestEventArgs( Mobile beholder, Mobile beheld ) - { - Beholder = beholder; - Beheld = beheld; - } - } - - public class AccountLoginEventArgs : EventArgs - { - public NetState State { get; } - - public string Username { get; } - - public string Password { get; } - - public bool Accepted { get; set; } - - public ALRReason RejectReason { get; set; } - - public AccountLoginEventArgs( NetState state, string username, string password ) - { - State = state; - Username = username; - Password = password; - } - } - - public class VirtueItemRequestEventArgs : EventArgs - { - public Mobile Beholder { get; } - - public Mobile Beheld { get; } - - public int GumpID { get; } - - public VirtueItemRequestEventArgs( Mobile beholder, Mobile beheld, int gumpID ) - { - Beholder = beholder; - Beheld = beheld; - GumpID = gumpID; - } - } - - public class VirtueGumpRequestEventArgs : EventArgs - { - public Mobile Beholder { get; } - - public Mobile Beheld { get; } - - public VirtueGumpRequestEventArgs( Mobile beholder, Mobile beheld ) - { - Beholder = beholder; - Beheld = beheld; - } - } - - public class VirtueMacroRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public int VirtueID { get; } - - public VirtueMacroRequestEventArgs( Mobile mobile, int virtueID ) - { - Mobile = mobile; - VirtueID = virtueID; - } - } - - public class ChatRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public ChatRequestEventArgs( Mobile mobile ) - { - Mobile = mobile; - } - } - - public class PlayerDeathEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public PlayerDeathEventArgs( Mobile mobile ) - { - Mobile = mobile; - } - } - - public class RenameRequestEventArgs : EventArgs - { - public Mobile From { get; } - - public Mobile Target { get; } - - public string Name { get; } - - public RenameRequestEventArgs( Mobile from, Mobile target, string name ) - { - From = from; - Target = target; - Name = name; - } - } - - public class LogoutEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public LogoutEventArgs( Mobile m ) - { - Mobile = m; - } - } - - public class SocketConnectEventArgs : EventArgs - { - public Socket Socket { get; } - - public bool AllowConnection { get; set; } - - public SocketConnectEventArgs( Socket s ) - { - Socket = s; - AllowConnection = true; - } - } - - public class ConnectedEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public ConnectedEventArgs( Mobile m ) - { - Mobile = m; - } - } - - public class DisconnectedEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public DisconnectedEventArgs( Mobile m ) - { - Mobile = m; - } - } - - public class AnimateRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public string Action { get; } - - public AnimateRequestEventArgs( Mobile m, string action ) - { - Mobile = m; - Action = action; - } - } - - public class CastSpellRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public Item Spellbook { get; } - - public int SpellID { get; } - - public CastSpellRequestEventArgs( Mobile m, int spellID, Item book ) - { - Mobile = m; - Spellbook = book; - SpellID = spellID; - } - } - - public class BandageTargetRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public Item Bandage { get; } - - public Mobile Target { get; } - - public BandageTargetRequestEventArgs(Mobile m, Item bandage, Mobile target) - { - Mobile = m; - Bandage = bandage; - Target = target; - } - } - - public class OpenSpellbookRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public int Type { get; } - - public OpenSpellbookRequestEventArgs( Mobile m, int type ) - { - Mobile = m; - Type = type; - } - } - - public class StunRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public StunRequestEventArgs( Mobile m ) - { - Mobile = m; - } - } - - public class DisarmRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public DisarmRequestEventArgs( Mobile m ) - { - Mobile = m; - } - } - - public class HelpRequestEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public HelpRequestEventArgs( Mobile m ) - { - Mobile = m; - } - } - - public class ShutdownEventArgs : EventArgs - { - public ShutdownEventArgs() - { - } - } - - public class CrashedEventArgs : EventArgs - { - public Exception Exception { get; } - - public bool Close { get; set; } - - public CrashedEventArgs( Exception e ) - { - Exception = e; - } - } - - public class HungerChangedEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public int OldValue { get; } - - public HungerChangedEventArgs( Mobile mobile, int oldValue ) - { - Mobile = mobile; - OldValue = oldValue; - } - } - - public class MovementEventArgs : EventArgs - { - public Mobile Mobile { get; private set; } + public delegate void HungerChangedEventHandler(HungerChangedEventArgs e); - public Direction Direction { get; private set; } + public delegate void CrashedEventHandler(CrashedEventArgs e); - public bool Blocked { get; set; } + public delegate void ShutdownEventHandler(ShutdownEventArgs e); - private static Queue m_Pool = new Queue(); + public delegate void HelpRequestEventHandler(HelpRequestEventArgs e); - public static MovementEventArgs Create( Mobile mobile, Direction dir ) - { - MovementEventArgs args; + public delegate void DisarmRequestEventHandler(DisarmRequestEventArgs e); - if ( m_Pool.Count > 0 ) - { - args = m_Pool.Dequeue(); + public delegate void StunRequestEventHandler(StunRequestEventArgs e); - args.Mobile = mobile; - args.Direction = dir; - args.Blocked = false; - } - else - { - args = new MovementEventArgs( mobile, dir ); - } + public delegate void OpenSpellbookRequestEventHandler(OpenSpellbookRequestEventArgs e); - return args; - } + public delegate void CastSpellRequestEventHandler(CastSpellRequestEventArgs e); - public MovementEventArgs( Mobile mobile, Direction dir ) - { - Mobile = mobile; - Direction = dir; - } + public delegate void BandageTargetRequestEventHandler(BandageTargetRequestEventArgs e); - public void Free() - { - m_Pool.Enqueue( this ); - } - } + public delegate void AnimateRequestEventHandler(AnimateRequestEventArgs e); - public class ServerListEventArgs : EventArgs - { - public NetState State { get; } + public delegate void LogoutEventHandler(LogoutEventArgs e); - public IAccount Account { get; } + public delegate void SocketConnectEventHandler(SocketConnectEventArgs e); - public bool Rejected { get; set; } + public delegate void ConnectedEventHandler(ConnectedEventArgs e); - public List Servers { get; } + public delegate void DisconnectedEventHandler(DisconnectedEventArgs e); - public void AddServer( string name, IPEndPoint address ) - { - AddServer( name, 0, TimeZone.CurrentTimeZone, address ); - } + public delegate void RenameRequestEventHandler(RenameRequestEventArgs e); - public void AddServer( string name, int fullPercent, TimeZone tz, IPEndPoint address ) - { - Servers.Add( new ServerInfo( name, fullPercent, tz, address ) ); - } + public delegate void PlayerDeathEventHandler(PlayerDeathEventArgs e); - public ServerListEventArgs( NetState state, IAccount account ) - { - State = state; - Account = account; - Servers = new List(); - } - } + public delegate void VirtueGumpRequestEventHandler(VirtueGumpRequestEventArgs e); - public struct SkillNameValue - { - public SkillName Name { get; } + public delegate void VirtueItemRequestEventHandler(VirtueItemRequestEventArgs e); - public int Value { get; } + public delegate void VirtueMacroRequestEventHandler(VirtueMacroRequestEventArgs e); - public SkillNameValue( SkillName name, int value ) - { - Name = name; - Value = value; - } - } + public delegate void ChatRequestEventHandler(ChatRequestEventArgs e); - public class CharacterCreatedEventArgs : EventArgs - { - public NetState State { get; } + public delegate void AccountLoginEventHandler(AccountLoginEventArgs e); - public IAccount Account { get; } + public delegate void PaperdollRequestEventHandler(PaperdollRequestEventArgs e); - public Mobile Mobile { get; set; } + public delegate void ProfileRequestEventHandler(ProfileRequestEventArgs e); - public string Name { get; } + public delegate void ChangeProfileRequestEventHandler(ChangeProfileRequestEventArgs e); - public bool Female { get; } + public delegate void AggressiveActionEventHandler(AggressiveActionEventArgs e); - public int Hue { get; } + public delegate void GameLoginEventHandler(GameLoginEventArgs e); - public int Str { get; } + public delegate void DeleteRequestEventHandler(DeleteRequestEventArgs e); - public int Dex { get; } + public delegate void WorldLoadEventHandler(); - public int Int { get; } + public delegate void WorldSaveEventHandler(WorldSaveEventArgs e); - public CityInfo City { get; } + public delegate void SetAbilityEventHandler(SetAbilityEventArgs e); - public SkillNameValue[] Skills { get; } + public delegate void FastWalkEventHandler(FastWalkEventArgs e); - public int ShirtHue { get; } + public delegate void ServerStartedEventHandler(); - public int PantsHue { get; } + public delegate void CreateGuildHandler(CreateGuildEventArgs e); - public int HairID { get; } + public delegate void GuildGumpRequestHandler(GuildGumpRequestArgs e); - public int HairHue { get; } + public delegate void QuestGumpRequestHandler(QuestGumpRequestArgs e); - public int BeardID { get; } + public delegate void ClientVersionReceivedHandler(ClientVersionReceivedArgs e); - public int BeardHue { get; } + public class ClientVersionReceivedArgs : EventArgs + { + public ClientVersionReceivedArgs(NetState state, ClientVersion cv) + { + State = state; + Version = cv; + } - public int Profession { get; set; } + public NetState State{ get; } - public Race Race { get; } + public ClientVersion Version{ get; } + } - public CharacterCreatedEventArgs( NetState state, IAccount a, string name, bool female, int hue, int str, int dex, int intel, CityInfo city, SkillNameValue[] skills, int shirtHue, int pantsHue, int hairID, int hairHue, int beardID, int beardHue, int profession, Race race ) - { - State = state; - Account = a; - Name = name; - Female = female; - Hue = hue; - Str = str; - Dex = dex; - Int = intel; - City = city; - Skills = skills; - ShirtHue = shirtHue; - PantsHue = pantsHue; - HairID = hairID; - HairHue = hairHue; - BeardID = beardID; - BeardHue = beardHue; - Profession = profession; - Race = race; - } - } - - public class OpenDoorMacroEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public OpenDoorMacroEventArgs( Mobile mobile ) - { - Mobile = mobile; - } - } - - public class SpeechEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public string Speech { get; set; } - - public MessageType Type { get; } - - public int Hue { get; } - - public int[] Keywords { get; } - - public bool Handled { get; set; } - - public bool Blocked { get; set; } - - public bool HasKeyword( int keyword ) - { - for ( int i = 0; i < Keywords.Length; ++i ) - if ( Keywords[i] == keyword ) - return true; - - return false; - } - - public SpeechEventArgs( Mobile mobile, string speech, MessageType type, int hue, int[] keywords ) - { - Mobile = mobile; - Speech = speech; - Type = type; - Hue = hue; - Keywords = keywords; - } - } - - public class LoginEventArgs : EventArgs - { - public Mobile Mobile { get; } - - public LoginEventArgs( Mobile mobile ) - { - Mobile = mobile; - } - } - - public class WorldSaveEventArgs : EventArgs - { - public bool Message { get; } - - public WorldSaveEventArgs( bool msg ) - { - Message = msg; - } - } - - public class FastWalkEventArgs : EventArgs - { - public FastWalkEventArgs( NetState state ) - { - NetState = state; - Blocked = false; - } - - public NetState NetState { get; } - - public bool Blocked { get; set; } - } - - public static class EventSink - { - public static event CharacterCreatedEventHandler CharacterCreated; - public static event OpenDoorMacroEventHandler OpenDoorMacroUsed; - public static event SpeechEventHandler Speech; - public static event LoginEventHandler Login; - public static event ServerListEventHandler ServerList; - public static event MovementEventHandler Movement; - public static event HungerChangedEventHandler HungerChanged; - public static event CrashedEventHandler Crashed; - public static event ShutdownEventHandler Shutdown; - public static event HelpRequestEventHandler HelpRequest; - public static event DisarmRequestEventHandler DisarmRequest; - public static event StunRequestEventHandler StunRequest; - public static event OpenSpellbookRequestEventHandler OpenSpellbookRequest; - public static event CastSpellRequestEventHandler CastSpellRequest; - public static event BandageTargetRequestEventHandler BandageTargetRequest; - public static event AnimateRequestEventHandler AnimateRequest; - public static event LogoutEventHandler Logout; - public static event SocketConnectEventHandler SocketConnect; - public static event ConnectedEventHandler Connected; - public static event DisconnectedEventHandler Disconnected; - public static event RenameRequestEventHandler RenameRequest; - public static event PlayerDeathEventHandler PlayerDeath; - public static event VirtueGumpRequestEventHandler VirtueGumpRequest; - public static event VirtueItemRequestEventHandler VirtueItemRequest; - public static event VirtueMacroRequestEventHandler VirtueMacroRequest; - public static event ChatRequestEventHandler ChatRequest; - public static event AccountLoginEventHandler AccountLogin; - public static event PaperdollRequestEventHandler PaperdollRequest; - public static event ProfileRequestEventHandler ProfileRequest; - public static event ChangeProfileRequestEventHandler ChangeProfileRequest; - public static event AggressiveActionEventHandler AggressiveAction; - public static event CommandEventHandler Command; - public static event GameLoginEventHandler GameLogin; - public static event DeleteRequestEventHandler DeleteRequest; - public static event WorldLoadEventHandler WorldLoad; - public static event WorldSaveEventHandler WorldSave; - public static event SetAbilityEventHandler SetAbility; - public static event FastWalkEventHandler FastWalk; - public static event CreateGuildHandler CreateGuild; - public static event ServerStartedEventHandler ServerStarted; - public static event GuildGumpRequestHandler GuildGumpRequest; - public static event QuestGumpRequestHandler QuestGumpRequest; - public static event ClientVersionReceivedHandler ClientVersionReceived; - - /* The following is a .NET 2.0 "Generic EventHandler" implementation. - * It is a breaking change; we would have to refactor all event handlers. - * This style does not appear to be in widespread use. - * We could also look into .NET 4.0 Action/Func implementations. - */ - - /* - public static event EventHandler CharacterCreated; - public static event EventHandler OpenDoorMacroUsed; - public static event EventHandler Speech; - public static event EventHandler Login; - public static event EventHandler ServerList; - public static event EventHandler Movement; - public static event EventHandler HungerChanged; - public static event EventHandler Crashed; - public static event EventHandler Shutdown; - public static event EventHandler HelpRequest; - public static event EventHandler DisarmRequest; - public static event EventHandler StunRequest; - public static event EventHandler OpenSpellbookRequest; - public static event EventHandler CastSpellRequest; - public static event EventHandler BandageTargetRequest; - public static event EventHandler AnimateRequest; - public static event EventHandler Logout; - public static event EventHandler SocketConnect; - public static event EventHandler Connected; - public static event EventHandler Disconnected; - public static event EventHandler RenameRequest; - public static event EventHandler PlayerDeath; - public static event EventHandler VirtueGumpRequest; - public static event EventHandler VirtueItemRequest; - public static event EventHandler VirtueMacroRequest; - public static event EventHandler ChatRequest; - public static event EventHandler AccountLogin; - public static event EventHandler PaperdollRequest; - public static event EventHandler ProfileRequest; - public static event EventHandler ChangeProfileRequest; - public static event EventHandler AggressiveAction; - public static event EventHandler Command; - public static event EventHandler GameLogin; - public static event EventHandler DeleteRequest; - public static event EventHandler WorldLoad; - public static event EventHandler WorldSave; - public static event EventHandler SetAbility; - public static event EventHandler FastWalk; - public static event EventHandler CreateGuild; - public static event EventHandler ServerStarted; - public static event EventHandler GuildGumpRequest; - public static event EventHandler QuestGumpRequest; - public static event EventHandler ClientVersionReceived; - */ - - public static void InvokeClientVersionReceived( ClientVersionReceivedArgs e ) - { - ClientVersionReceived?.Invoke( e ); - } - - public static void InvokeServerStarted() - { - ServerStarted?.Invoke(); - } - - public static void InvokeCreateGuild( CreateGuildEventArgs e ) - { - CreateGuild?.Invoke( e ); - } - - public static void InvokeSetAbility( SetAbilityEventArgs e ) - { - SetAbility?.Invoke( e ); - } - - public static void InvokeGuildGumpRequest( GuildGumpRequestArgs e ) - { - GuildGumpRequest?.Invoke( e ); - } - - public static void InvokeQuestGumpRequest( QuestGumpRequestArgs e ) - { - QuestGumpRequest?.Invoke( e ); - } - - public static void InvokeFastWalk( FastWalkEventArgs e ) - { - FastWalk?.Invoke( e ); - } - - public static void InvokeDeleteRequest( DeleteRequestEventArgs e ) - { - DeleteRequest?.Invoke( e ); - } - - public static void InvokeGameLogin( GameLoginEventArgs e ) - { - GameLogin?.Invoke( e ); - } - - public static void InvokeCommand( CommandEventArgs e ) - { - Command?.Invoke( e ); - } - - public static void InvokeAggressiveAction( AggressiveActionEventArgs e ) - { - AggressiveAction?.Invoke( e ); - } - - public static void InvokeProfileRequest( ProfileRequestEventArgs e ) - { - ProfileRequest?.Invoke( e ); - } - - public static void InvokeChangeProfileRequest( ChangeProfileRequestEventArgs e ) - { - ChangeProfileRequest?.Invoke( e ); - } - - public static void InvokePaperdollRequest( PaperdollRequestEventArgs e ) - { - PaperdollRequest?.Invoke( e ); - } - - public static void InvokeAccountLogin( AccountLoginEventArgs e ) - { - AccountLogin?.Invoke( e ); - } - - public static void InvokeChatRequest( ChatRequestEventArgs e ) - { - ChatRequest?.Invoke( e ); - } - - public static void InvokeVirtueItemRequest( VirtueItemRequestEventArgs e ) - { - VirtueItemRequest?.Invoke( e ); - } - - public static void InvokeVirtueGumpRequest( VirtueGumpRequestEventArgs e ) - { - VirtueGumpRequest?.Invoke( e ); - } - - public static void InvokeVirtueMacroRequest( VirtueMacroRequestEventArgs e ) - { - VirtueMacroRequest?.Invoke( e ); - } - - public static void InvokePlayerDeath( PlayerDeathEventArgs e ) - { - PlayerDeath?.Invoke( e ); - } - - public static void InvokeRenameRequest( RenameRequestEventArgs e ) - { - RenameRequest?.Invoke( e ); - } - - public static void InvokeLogout( LogoutEventArgs e ) - { - Logout?.Invoke( e ); - } - - public static void InvokeSocketConnect( SocketConnectEventArgs e ) - { - SocketConnect?.Invoke( e ); - } - - public static void InvokeConnected( ConnectedEventArgs e ) - { - Connected?.Invoke( e ); - } - - public static void InvokeDisconnected( DisconnectedEventArgs e ) - { - Disconnected?.Invoke( e ); - } - - public static void InvokeAnimateRequest( AnimateRequestEventArgs e ) - { - AnimateRequest?.Invoke( e ); - } - - public static void InvokeCastSpellRequest( CastSpellRequestEventArgs e ) - { - CastSpellRequest?.Invoke( e ); - } - - public static void InvokeBandageTargetRequest( BandageTargetRequestEventArgs e ) - { - BandageTargetRequest?.Invoke( e ); - } - - public static void InvokeOpenSpellbookRequest( OpenSpellbookRequestEventArgs e ) - { - OpenSpellbookRequest?.Invoke( e ); - } - - public static void InvokeDisarmRequest( DisarmRequestEventArgs e ) - { - DisarmRequest?.Invoke( e ); - } - - public static void InvokeStunRequest( StunRequestEventArgs e ) - { - StunRequest?.Invoke( e ); - } - - public static void InvokeHelpRequest( HelpRequestEventArgs e ) - { - HelpRequest?.Invoke( e ); - } - - public static void InvokeShutdown( ShutdownEventArgs e ) - { - Shutdown?.Invoke( e ); - } - - public static void InvokeCrashed( CrashedEventArgs e ) - { - Crashed?.Invoke( e ); - } - - public static void InvokeHungerChanged( HungerChangedEventArgs e ) - { - HungerChanged?.Invoke( e ); - } - - public static void InvokeMovement( MovementEventArgs e ) - { - Movement?.Invoke( e ); - } - - public static void InvokeServerList( ServerListEventArgs e ) - { - ServerList?.Invoke( e ); - } - - public static void InvokeLogin( LoginEventArgs e ) - { - Login?.Invoke( e ); - } - - public static void InvokeSpeech( SpeechEventArgs e ) - { - Speech?.Invoke( e ); - } - - public static void InvokeCharacterCreated( CharacterCreatedEventArgs e ) - { - CharacterCreated?.Invoke( e ); - } - - public static void InvokeOpenDoorMacroUsed( OpenDoorMacroEventArgs e ) - { - OpenDoorMacroUsed?.Invoke( e ); - } - - public static void InvokeWorldLoad() - { - WorldLoad?.Invoke(); - } - - public static void InvokeWorldSave( WorldSaveEventArgs e ) - { - WorldSave?.Invoke( e ); - } - - public static void Reset() - { - CharacterCreated = null; - OpenDoorMacroUsed = null; - Speech = null; - Login = null; - ServerList = null; - Movement = null; - HungerChanged = null; - Crashed = null; - Shutdown = null; - HelpRequest = null; - DisarmRequest = null; - StunRequest = null; - OpenSpellbookRequest = null; - CastSpellRequest = null; - BandageTargetRequest = null; - AnimateRequest = null; - Logout = null; - SocketConnect = null; - Connected = null; - Disconnected = null; - RenameRequest = null; - PlayerDeath = null; - VirtueGumpRequest = null; - VirtueItemRequest = null; - VirtueMacroRequest = null; - ChatRequest = null; - AccountLogin = null; - PaperdollRequest = null; - ProfileRequest = null; - ChangeProfileRequest = null; - AggressiveAction = null; - Command = null; - GameLogin = null; - DeleteRequest = null; - WorldLoad = null; - WorldSave = null; - SetAbility = null; - GuildGumpRequest = null; - QuestGumpRequest = null; - } - } -} + public class CreateGuildEventArgs : EventArgs + { + public CreateGuildEventArgs(int id) + { + Id = id; + } + + public int Id{ get; set; } + + public BaseGuild Guild{ get; set; } + } + + public class GuildGumpRequestArgs : EventArgs + { + public GuildGumpRequestArgs(Mobile mobile) + { + Mobile = mobile; + } + + public Mobile Mobile{ get; } + } + + public class QuestGumpRequestArgs : EventArgs + { + public QuestGumpRequestArgs(Mobile mobile) + { + Mobile = mobile; + } + + public Mobile Mobile{ get; } + } + + public class SetAbilityEventArgs : EventArgs + { + public SetAbilityEventArgs(Mobile mobile, int index) + { + Mobile = mobile; + Index = index; + } + + public Mobile Mobile{ get; } + + public int Index{ get; } + } + + public class DeleteRequestEventArgs : EventArgs + { + public DeleteRequestEventArgs(NetState state, int index) + { + State = state; + Index = index; + } + + public NetState State{ get; } + + public int Index{ get; } + } + + public class GameLoginEventArgs : EventArgs + { + public GameLoginEventArgs(NetState state, string un, string pw) + { + State = state; + Username = un; + Password = pw; + } + + public NetState State{ get; } + + public string Username{ get; } + + public string Password{ get; } + + public bool Accepted{ get; set; } + + public CityInfo[] CityInfo{ get; set; } + } + + public class AggressiveActionEventArgs : EventArgs + { + private static Queue m_Pool = new Queue(); + + private AggressiveActionEventArgs(Mobile aggressed, Mobile aggressor, bool criminal) + { + Aggressed = aggressed; + Aggressor = aggressor; + Criminal = criminal; + } + + public Mobile Aggressed{ get; private set; } + + public Mobile Aggressor{ get; private set; } + + public bool Criminal{ get; private set; } + + public static AggressiveActionEventArgs Create(Mobile aggressed, Mobile aggressor, bool criminal) + { + AggressiveActionEventArgs args; + + if (m_Pool.Count > 0) + { + args = m_Pool.Dequeue(); + + args.Aggressed = aggressed; + args.Aggressor = aggressor; + args.Criminal = criminal; + } + else + { + args = new AggressiveActionEventArgs(aggressed, aggressor, criminal); + } + + return args; + } + + public void Free() + { + m_Pool.Enqueue(this); + } + } + + public class ProfileRequestEventArgs : EventArgs + { + public ProfileRequestEventArgs(Mobile beholder, Mobile beheld) + { + Beholder = beholder; + Beheld = beheld; + } + + public Mobile Beholder{ get; } + + public Mobile Beheld{ get; } + } + + public class ChangeProfileRequestEventArgs : EventArgs + { + public ChangeProfileRequestEventArgs(Mobile beholder, Mobile beheld, string text) + { + Beholder = beholder; + Beheld = beheld; + Text = text; + } + + public Mobile Beholder{ get; } + + public Mobile Beheld{ get; } + + public string Text{ get; } + } + + public class PaperdollRequestEventArgs : EventArgs + { + public PaperdollRequestEventArgs(Mobile beholder, Mobile beheld) + { + Beholder = beholder; + Beheld = beheld; + } + + public Mobile Beholder{ get; } + + public Mobile Beheld{ get; } + } + + public class AccountLoginEventArgs : EventArgs + { + public AccountLoginEventArgs(NetState state, string username, string password) + { + State = state; + Username = username; + Password = password; + } + + public NetState State{ get; } + + public string Username{ get; } + + public string Password{ get; } + + public bool Accepted{ get; set; } + + public ALRReason RejectReason{ get; set; } + } + + public class VirtueItemRequestEventArgs : EventArgs + { + public VirtueItemRequestEventArgs(Mobile beholder, Mobile beheld, int gumpID) + { + Beholder = beholder; + Beheld = beheld; + GumpID = gumpID; + } + + public Mobile Beholder{ get; } + + public Mobile Beheld{ get; } + + public int GumpID{ get; } + } + + public class VirtueGumpRequestEventArgs : EventArgs + { + public VirtueGumpRequestEventArgs(Mobile beholder, Mobile beheld) + { + Beholder = beholder; + Beheld = beheld; + } + + public Mobile Beholder{ get; } + + public Mobile Beheld{ get; } + } + + public class VirtueMacroRequestEventArgs : EventArgs + { + public VirtueMacroRequestEventArgs(Mobile mobile, int virtueID) + { + Mobile = mobile; + VirtueID = virtueID; + } + + public Mobile Mobile{ get; } + + public int VirtueID{ get; } + } + + public class ChatRequestEventArgs : EventArgs + { + public ChatRequestEventArgs(Mobile mobile) + { + Mobile = mobile; + } + + public Mobile Mobile{ get; } + } + + public class PlayerDeathEventArgs : EventArgs + { + public PlayerDeathEventArgs(Mobile mobile) + { + Mobile = mobile; + } + + public Mobile Mobile{ get; } + } + + public class RenameRequestEventArgs : EventArgs + { + public RenameRequestEventArgs(Mobile from, Mobile target, string name) + { + From = from; + Target = target; + Name = name; + } + + public Mobile From{ get; } + + public Mobile Target{ get; } + + public string Name{ get; } + } + + public class LogoutEventArgs : EventArgs + { + public LogoutEventArgs(Mobile m) + { + Mobile = m; + } + + public Mobile Mobile{ get; } + } + + public class SocketConnectEventArgs : EventArgs + { + public SocketConnectEventArgs(Socket s) + { + Socket = s; + AllowConnection = true; + } + + public Socket Socket{ get; } + + public bool AllowConnection{ get; set; } + } + + public class ConnectedEventArgs : EventArgs + { + public ConnectedEventArgs(Mobile m) + { + Mobile = m; + } + + public Mobile Mobile{ get; } + } + + public class DisconnectedEventArgs : EventArgs + { + public DisconnectedEventArgs(Mobile m) + { + Mobile = m; + } + + public Mobile Mobile{ get; } + } + + public class AnimateRequestEventArgs : EventArgs + { + public AnimateRequestEventArgs(Mobile m, string action) + { + Mobile = m; + Action = action; + } + + public Mobile Mobile{ get; } + + public string Action{ get; } + } + + public class CastSpellRequestEventArgs : EventArgs + { + public CastSpellRequestEventArgs(Mobile m, int spellID, Item book) + { + Mobile = m; + Spellbook = book; + SpellID = spellID; + } + + public Mobile Mobile{ get; } + + public Item Spellbook{ get; } + + public int SpellID{ get; } + } + + public class BandageTargetRequestEventArgs : EventArgs + { + public BandageTargetRequestEventArgs(Mobile m, Item bandage, Mobile target) + { + Mobile = m; + Bandage = bandage; + Target = target; + } + + public Mobile Mobile{ get; } + + public Item Bandage{ get; } + + public Mobile Target{ get; } + } + + public class OpenSpellbookRequestEventArgs : EventArgs + { + public OpenSpellbookRequestEventArgs(Mobile m, int type) + { + Mobile = m; + Type = type; + } + + public Mobile Mobile{ get; } + + public int Type{ get; } + } + + public class StunRequestEventArgs : EventArgs + { + public StunRequestEventArgs(Mobile m) + { + Mobile = m; + } + + public Mobile Mobile{ get; } + } + + public class DisarmRequestEventArgs : EventArgs + { + public DisarmRequestEventArgs(Mobile m) + { + Mobile = m; + } + + public Mobile Mobile{ get; } + } + + public class HelpRequestEventArgs : EventArgs + { + public HelpRequestEventArgs(Mobile m) + { + Mobile = m; + } + + public Mobile Mobile{ get; } + } + + public class ShutdownEventArgs : EventArgs + { + } + + public class CrashedEventArgs : EventArgs + { + public CrashedEventArgs(Exception e) + { + Exception = e; + } + + public Exception Exception{ get; } + + public bool Close{ get; set; } + } + + public class HungerChangedEventArgs : EventArgs + { + public HungerChangedEventArgs(Mobile mobile, int oldValue) + { + Mobile = mobile; + OldValue = oldValue; + } + + public Mobile Mobile{ get; } + + public int OldValue{ get; } + } + + public class MovementEventArgs : EventArgs + { + private static Queue m_Pool = new Queue(); + + public MovementEventArgs(Mobile mobile, Direction dir) + { + Mobile = mobile; + Direction = dir; + } + + public Mobile Mobile{ get; private set; } + + public Direction Direction{ get; private set; } + + public bool Blocked{ get; set; } + + public static MovementEventArgs Create(Mobile mobile, Direction dir) + { + MovementEventArgs args; + + if (m_Pool.Count > 0) + { + args = m_Pool.Dequeue(); + + args.Mobile = mobile; + args.Direction = dir; + args.Blocked = false; + } + else + { + args = new MovementEventArgs(mobile, dir); + } + + return args; + } + + public void Free() + { + m_Pool.Enqueue(this); + } + } + + public class ServerListEventArgs : EventArgs + { + public ServerListEventArgs(NetState state, IAccount account) + { + State = state; + Account = account; + Servers = new List(); + } + + public NetState State{ get; } + + public IAccount Account{ get; } + + public bool Rejected{ get; set; } + + public List Servers{ get; } + + public void AddServer(string name, IPEndPoint address) + { + AddServer(name, 0, TimeZone.CurrentTimeZone, address); + } + + public void AddServer(string name, int fullPercent, TimeZone tz, IPEndPoint address) + { + Servers.Add(new ServerInfo(name, fullPercent, tz, address)); + } + } + + public struct SkillNameValue + { + public SkillName Name{ get; } + + public int Value{ get; } + + public SkillNameValue(SkillName name, int value) + { + Name = name; + Value = value; + } + } + + public class CharacterCreatedEventArgs : EventArgs + { + public CharacterCreatedEventArgs(NetState state, IAccount a, string name, bool female, int hue, int str, int dex, + int intel, CityInfo city, SkillNameValue[] skills, int shirtHue, int pantsHue, int hairID, int hairHue, + int beardID, int beardHue, int profession, Race race) + { + State = state; + Account = a; + Name = name; + Female = female; + Hue = hue; + Str = str; + Dex = dex; + Int = intel; + City = city; + Skills = skills; + ShirtHue = shirtHue; + PantsHue = pantsHue; + HairID = hairID; + HairHue = hairHue; + BeardID = beardID; + BeardHue = beardHue; + Profession = profession; + Race = race; + } + + public NetState State{ get; } + + public IAccount Account{ get; } + + public Mobile Mobile{ get; set; } + + public string Name{ get; } + + public bool Female{ get; } + + public int Hue{ get; } + + public int Str{ get; } + + public int Dex{ get; } + + public int Int{ get; } + + public CityInfo City{ get; } + + public SkillNameValue[] Skills{ get; } + + public int ShirtHue{ get; } + + public int PantsHue{ get; } + + public int HairID{ get; } + + public int HairHue{ get; } + + public int BeardID{ get; } + + public int BeardHue{ get; } + + public int Profession{ get; set; } + + public Race Race{ get; } + } + + public class OpenDoorMacroEventArgs : EventArgs + { + public OpenDoorMacroEventArgs(Mobile mobile) + { + Mobile = mobile; + } + + public Mobile Mobile{ get; } + } + + public class SpeechEventArgs : EventArgs + { + public SpeechEventArgs(Mobile mobile, string speech, MessageType type, int hue, int[] keywords) + { + Mobile = mobile; + Speech = speech; + Type = type; + Hue = hue; + Keywords = keywords; + } + + public Mobile Mobile{ get; } + + public string Speech{ get; set; } + + public MessageType Type{ get; } + + public int Hue{ get; } + + public int[] Keywords{ get; } + + public bool Handled{ get; set; } + + public bool Blocked{ get; set; } + + public bool HasKeyword(int keyword) + { + for (int i = 0; i < Keywords.Length; ++i) + if (Keywords[i] == keyword) + return true; + + return false; + } + } + + public class LoginEventArgs : EventArgs + { + public LoginEventArgs(Mobile mobile) + { + Mobile = mobile; + } + + public Mobile Mobile{ get; } + } + + public class WorldSaveEventArgs : EventArgs + { + public WorldSaveEventArgs(bool msg) + { + Message = msg; + } + + public bool Message{ get; } + } + + public class FastWalkEventArgs : EventArgs + { + public FastWalkEventArgs(NetState state) + { + NetState = state; + Blocked = false; + } + + public NetState NetState{ get; } + + public bool Blocked{ get; set; } + } + + public static class EventSink + { + public static event CharacterCreatedEventHandler CharacterCreated; + public static event OpenDoorMacroEventHandler OpenDoorMacroUsed; + public static event SpeechEventHandler Speech; + public static event LoginEventHandler Login; + public static event ServerListEventHandler ServerList; + public static event MovementEventHandler Movement; + public static event HungerChangedEventHandler HungerChanged; + public static event CrashedEventHandler Crashed; + public static event ShutdownEventHandler Shutdown; + public static event HelpRequestEventHandler HelpRequest; + public static event DisarmRequestEventHandler DisarmRequest; + public static event StunRequestEventHandler StunRequest; + public static event OpenSpellbookRequestEventHandler OpenSpellbookRequest; + public static event CastSpellRequestEventHandler CastSpellRequest; + public static event BandageTargetRequestEventHandler BandageTargetRequest; + public static event AnimateRequestEventHandler AnimateRequest; + public static event LogoutEventHandler Logout; + public static event SocketConnectEventHandler SocketConnect; + public static event ConnectedEventHandler Connected; + public static event DisconnectedEventHandler Disconnected; + public static event RenameRequestEventHandler RenameRequest; + public static event PlayerDeathEventHandler PlayerDeath; + public static event VirtueGumpRequestEventHandler VirtueGumpRequest; + public static event VirtueItemRequestEventHandler VirtueItemRequest; + public static event VirtueMacroRequestEventHandler VirtueMacroRequest; + public static event ChatRequestEventHandler ChatRequest; + public static event AccountLoginEventHandler AccountLogin; + public static event PaperdollRequestEventHandler PaperdollRequest; + public static event ProfileRequestEventHandler ProfileRequest; + public static event ChangeProfileRequestEventHandler ChangeProfileRequest; + public static event AggressiveActionEventHandler AggressiveAction; + public static event CommandEventHandler Command; + public static event GameLoginEventHandler GameLogin; + public static event DeleteRequestEventHandler DeleteRequest; + public static event WorldLoadEventHandler WorldLoad; + public static event WorldSaveEventHandler WorldSave; + public static event SetAbilityEventHandler SetAbility; + public static event FastWalkEventHandler FastWalk; + public static event CreateGuildHandler CreateGuild; + public static event ServerStartedEventHandler ServerStarted; + public static event GuildGumpRequestHandler GuildGumpRequest; + public static event QuestGumpRequestHandler QuestGumpRequest; + public static event ClientVersionReceivedHandler ClientVersionReceived; + + /* The following is a .NET 2.0 "Generic EventHandler" implementation. + * It is a breaking change; we would have to refactor all event handlers. + * This style does not appear to be in widespread use. + * We could also look into .NET 4.0 Action/Func implementations. + */ + + /* + public static event EventHandler CharacterCreated; + public static event EventHandler OpenDoorMacroUsed; + public static event EventHandler Speech; + public static event EventHandler Login; + public static event EventHandler ServerList; + public static event EventHandler Movement; + public static event EventHandler HungerChanged; + public static event EventHandler Crashed; + public static event EventHandler Shutdown; + public static event EventHandler HelpRequest; + public static event EventHandler DisarmRequest; + public static event EventHandler StunRequest; + public static event EventHandler OpenSpellbookRequest; + public static event EventHandler CastSpellRequest; + public static event EventHandler BandageTargetRequest; + public static event EventHandler AnimateRequest; + public static event EventHandler Logout; + public static event EventHandler SocketConnect; + public static event EventHandler Connected; + public static event EventHandler Disconnected; + public static event EventHandler RenameRequest; + public static event EventHandler PlayerDeath; + public static event EventHandler VirtueGumpRequest; + public static event EventHandler VirtueItemRequest; + public static event EventHandler VirtueMacroRequest; + public static event EventHandler ChatRequest; + public static event EventHandler AccountLogin; + public static event EventHandler PaperdollRequest; + public static event EventHandler ProfileRequest; + public static event EventHandler ChangeProfileRequest; + public static event EventHandler AggressiveAction; + public static event EventHandler Command; + public static event EventHandler GameLogin; + public static event EventHandler DeleteRequest; + public static event EventHandler WorldLoad; + public static event EventHandler WorldSave; + public static event EventHandler SetAbility; + public static event EventHandler FastWalk; + public static event EventHandler CreateGuild; + public static event EventHandler ServerStarted; + public static event EventHandler GuildGumpRequest; + public static event EventHandler QuestGumpRequest; + public static event EventHandler ClientVersionReceived; + */ + + public static void InvokeClientVersionReceived(ClientVersionReceivedArgs e) + { + ClientVersionReceived?.Invoke(e); + } + + public static void InvokeServerStarted() + { + ServerStarted?.Invoke(); + } + + public static void InvokeCreateGuild(CreateGuildEventArgs e) + { + CreateGuild?.Invoke(e); + } + + public static void InvokeSetAbility(SetAbilityEventArgs e) + { + SetAbility?.Invoke(e); + } + + public static void InvokeGuildGumpRequest(GuildGumpRequestArgs e) + { + GuildGumpRequest?.Invoke(e); + } + + public static void InvokeQuestGumpRequest(QuestGumpRequestArgs e) + { + QuestGumpRequest?.Invoke(e); + } + + public static void InvokeFastWalk(FastWalkEventArgs e) + { + FastWalk?.Invoke(e); + } + + public static void InvokeDeleteRequest(DeleteRequestEventArgs e) + { + DeleteRequest?.Invoke(e); + } + + public static void InvokeGameLogin(GameLoginEventArgs e) + { + GameLogin?.Invoke(e); + } + + public static void InvokeCommand(CommandEventArgs e) + { + Command?.Invoke(e); + } + + public static void InvokeAggressiveAction(AggressiveActionEventArgs e) + { + AggressiveAction?.Invoke(e); + } + + public static void InvokeProfileRequest(ProfileRequestEventArgs e) + { + ProfileRequest?.Invoke(e); + } + + public static void InvokeChangeProfileRequest(ChangeProfileRequestEventArgs e) + { + ChangeProfileRequest?.Invoke(e); + } + + public static void InvokePaperdollRequest(PaperdollRequestEventArgs e) + { + PaperdollRequest?.Invoke(e); + } + + public static void InvokeAccountLogin(AccountLoginEventArgs e) + { + AccountLogin?.Invoke(e); + } + + public static void InvokeChatRequest(ChatRequestEventArgs e) + { + ChatRequest?.Invoke(e); + } + + public static void InvokeVirtueItemRequest(VirtueItemRequestEventArgs e) + { + VirtueItemRequest?.Invoke(e); + } + + public static void InvokeVirtueGumpRequest(VirtueGumpRequestEventArgs e) + { + VirtueGumpRequest?.Invoke(e); + } + + public static void InvokeVirtueMacroRequest(VirtueMacroRequestEventArgs e) + { + VirtueMacroRequest?.Invoke(e); + } + + public static void InvokePlayerDeath(PlayerDeathEventArgs e) + { + PlayerDeath?.Invoke(e); + } + + public static void InvokeRenameRequest(RenameRequestEventArgs e) + { + RenameRequest?.Invoke(e); + } + + public static void InvokeLogout(LogoutEventArgs e) + { + Logout?.Invoke(e); + } + + public static void InvokeSocketConnect(SocketConnectEventArgs e) + { + SocketConnect?.Invoke(e); + } + + public static void InvokeConnected(ConnectedEventArgs e) + { + Connected?.Invoke(e); + } + + public static void InvokeDisconnected(DisconnectedEventArgs e) + { + Disconnected?.Invoke(e); + } + + public static void InvokeAnimateRequest(AnimateRequestEventArgs e) + { + AnimateRequest?.Invoke(e); + } + + public static void InvokeCastSpellRequest(CastSpellRequestEventArgs e) + { + CastSpellRequest?.Invoke(e); + } + + public static void InvokeBandageTargetRequest(BandageTargetRequestEventArgs e) + { + BandageTargetRequest?.Invoke(e); + } + + public static void InvokeOpenSpellbookRequest(OpenSpellbookRequestEventArgs e) + { + OpenSpellbookRequest?.Invoke(e); + } + + public static void InvokeDisarmRequest(DisarmRequestEventArgs e) + { + DisarmRequest?.Invoke(e); + } + + public static void InvokeStunRequest(StunRequestEventArgs e) + { + StunRequest?.Invoke(e); + } + + public static void InvokeHelpRequest(HelpRequestEventArgs e) + { + HelpRequest?.Invoke(e); + } + + public static void InvokeShutdown(ShutdownEventArgs e) + { + Shutdown?.Invoke(e); + } + + public static void InvokeCrashed(CrashedEventArgs e) + { + Crashed?.Invoke(e); + } + + public static void InvokeHungerChanged(HungerChangedEventArgs e) + { + HungerChanged?.Invoke(e); + } + + public static void InvokeMovement(MovementEventArgs e) + { + Movement?.Invoke(e); + } + + public static void InvokeServerList(ServerListEventArgs e) + { + ServerList?.Invoke(e); + } + + public static void InvokeLogin(LoginEventArgs e) + { + Login?.Invoke(e); + } + + public static void InvokeSpeech(SpeechEventArgs e) + { + Speech?.Invoke(e); + } + + public static void InvokeCharacterCreated(CharacterCreatedEventArgs e) + { + CharacterCreated?.Invoke(e); + } + + public static void InvokeOpenDoorMacroUsed(OpenDoorMacroEventArgs e) + { + OpenDoorMacroUsed?.Invoke(e); + } + + public static void InvokeWorldLoad() + { + WorldLoad?.Invoke(); + } + + public static void InvokeWorldSave(WorldSaveEventArgs e) + { + WorldSave?.Invoke(e); + } + + public static void Reset() + { + CharacterCreated = null; + OpenDoorMacroUsed = null; + Speech = null; + Login = null; + ServerList = null; + Movement = null; + HungerChanged = null; + Crashed = null; + Shutdown = null; + HelpRequest = null; + DisarmRequest = null; + StunRequest = null; + OpenSpellbookRequest = null; + CastSpellRequest = null; + BandageTargetRequest = null; + AnimateRequest = null; + Logout = null; + SocketConnect = null; + Connected = null; + Disconnected = null; + RenameRequest = null; + PlayerDeath = null; + VirtueGumpRequest = null; + VirtueItemRequest = null; + VirtueMacroRequest = null; + ChatRequest = null; + AccountLogin = null; + PaperdollRequest = null; + ProfileRequest = null; + ChangeProfileRequest = null; + AggressiveAction = null; + Command = null; + GameLogin = null; + DeleteRequest = null; + WorldLoad = null; + WorldSave = null; + SetAbility = null; + GuildGumpRequest = null; + QuestGumpRequest = null; + } + } +} \ No newline at end of file diff --git a/Server/ExpansionInfo.cs b/Server/ExpansionInfo.cs index d68a42fc0..66ab87894 100644 --- a/Server/ExpansionInfo.cs +++ b/Server/ExpansionInfo.cs @@ -22,331 +22,325 @@ using System; namespace Server { - public enum Expansion - { - None, - T2A, - UOR, - UOTD, - LBR, - AOS, - SE, - ML, - SA, - HS, - TOL - } + public enum Expansion + { + None, + T2A, + UOR, + UOTD, + LBR, + AOS, + SE, + ML, + SA, + HS, + TOL + } - [Flags] - public enum ClientFlags - { - None = 0x00000000, - Felucca = 0x00000001, - Trammel = 0x00000002, - Ilshenar= 0x00000004, - Malas = 0x00000008, - Tokuno = 0x00000010, - TerMur = 0x00000020, - Unk1 = 0x00000040, - Unk2 = 0x00000080, - UOTD = 0x00000100 - } + [Flags] + public enum ClientFlags + { + None = 0x00000000, + Felucca = 0x00000001, + Trammel = 0x00000002, + Ilshenar = 0x00000004, + Malas = 0x00000008, + Tokuno = 0x00000010, + TerMur = 0x00000020, + Unk1 = 0x00000040, + Unk2 = 0x00000080, + UOTD = 0x00000100 + } - [Flags] - public enum FeatureFlags - { - None = 0x00000000, - T2A = 0x00000001, - UOR = 0x00000002, - UOTD = 0x00000004, - LBR = 0x00000008, - AOS = 0x00000010, - SixthCharacterSlot = 0x00000020, - SE = 0x00000040, - ML = 0x00000080, - EigthAge = 0x00000100, - NinthAge = 0x00000200, /* Crystal/Shadow Custom House Tiles */ - TenthAge = 0x00000400, - IncreasedStorage = 0x00000800, /* Increased Housing/Bank Storage */ - SeventhCharacterSlot = 0x00001000, - RoleplayFaces = 0x00002000, - TrialAccount = 0x00004000, - LiveAccount = 0x00008000, - SA = 0x00010000, - HS = 0x00020000, - Gothic = 0x00040000, - Rustic = 0x00080000, - Jungle = 0x00100000, - Shadowguard = 0x00200000, - TOL = 0x00400000, + [Flags] + public enum FeatureFlags + { + None = 0x00000000, + T2A = 0x00000001, + UOR = 0x00000002, + UOTD = 0x00000004, + LBR = 0x00000008, + AOS = 0x00000010, + SixthCharacterSlot = 0x00000020, + SE = 0x00000040, + ML = 0x00000080, + EigthAge = 0x00000100, + NinthAge = 0x00000200, /* Crystal/Shadow Custom House Tiles */ + TenthAge = 0x00000400, + IncreasedStorage = 0x00000800, /* Increased Housing/Bank Storage */ + SeventhCharacterSlot = 0x00001000, + RoleplayFaces = 0x00002000, + TrialAccount = 0x00004000, + LiveAccount = 0x00008000, + SA = 0x00010000, + HS = 0x00020000, + Gothic = 0x00040000, + Rustic = 0x00080000, + Jungle = 0x00100000, + Shadowguard = 0x00200000, + TOL = 0x00400000, - ExpansionNone = None, - ExpansionT2A = T2A, - ExpansionUOR = ExpansionT2A | UOR, - ExpansionUOTD = ExpansionUOR | UOTD, - ExpansionLBR = ExpansionUOTD | LBR, - ExpansionAOS = ExpansionLBR | AOS | LiveAccount, - ExpansionSE = ExpansionAOS | SE, - ExpansionML = ExpansionSE | ML | NinthAge, - ExpansionSA = ExpansionML | SA | Gothic | Rustic, - ExpansionHS = ExpansionSA | HS, - ExpansionTOL = ExpansionHS | TOL | Jungle | Shadowguard - } + ExpansionNone = None, + ExpansionT2A = T2A, + ExpansionUOR = ExpansionT2A | UOR, + ExpansionUOTD = ExpansionUOR | UOTD, + ExpansionLBR = ExpansionUOTD | LBR, + ExpansionAOS = ExpansionLBR | AOS | LiveAccount, + ExpansionSE = ExpansionAOS | SE, + ExpansionML = ExpansionSE | ML | NinthAge, + ExpansionSA = ExpansionML | SA | Gothic | Rustic, + ExpansionHS = ExpansionSA | HS, + ExpansionTOL = ExpansionHS | TOL | Jungle | Shadowguard + } - [Flags] - public enum CharacterListFlags - { - None = 0x00000000, - Unk1 = 0x00000001, - OverwriteConfigButton = 0x00000002, - OneCharacterSlot = 0x00000004, - ContextMenus = 0x00000008, - SlotLimit = 0x00000010, - AOS = 0x00000020, - SixthCharacterSlot = 0x00000040, - SE = 0x00000080, - ML = 0x00000100, - Unk2 = 0x00000200, - UO3DClientType = 0x00000400, - Unk3 = 0x00000800, - SeventhCharacterSlot = 0x00001000, - Unk4 = 0x00002000, - NewMovementSystem = 0x00004000, - NewFeluccaAreas = 0x00008000, + [Flags] + public enum CharacterListFlags + { + None = 0x00000000, + Unk1 = 0x00000001, + OverwriteConfigButton = 0x00000002, + OneCharacterSlot = 0x00000004, + ContextMenus = 0x00000008, + SlotLimit = 0x00000010, + AOS = 0x00000020, + SixthCharacterSlot = 0x00000040, + SE = 0x00000080, + ML = 0x00000100, + Unk2 = 0x00000200, + UO3DClientType = 0x00000400, + Unk3 = 0x00000800, + SeventhCharacterSlot = 0x00001000, + Unk4 = 0x00002000, + NewMovementSystem = 0x00004000, + NewFeluccaAreas = 0x00008000, - ExpansionNone = ContextMenus, // - ExpansionT2A = ContextMenus, // - ExpansionUOR = ContextMenus, // None - ExpansionUOTD = ContextMenus, // - ExpansionLBR = ContextMenus, // - ExpansionAOS = ContextMenus | AOS, - ExpansionSE = ExpansionAOS | SE, - ExpansionML = ExpansionSE | ML, - ExpansionSA = ExpansionML, - ExpansionHS = ExpansionSA, - ExpansionTOL = ExpansionHS - } + ExpansionNone = ContextMenus, // + ExpansionT2A = ContextMenus, // + ExpansionUOR = ContextMenus, // None + ExpansionUOTD = ContextMenus, // + ExpansionLBR = ContextMenus, // + ExpansionAOS = ContextMenus | AOS, + ExpansionSE = ExpansionAOS | SE, + ExpansionML = ExpansionSE | ML, + ExpansionSA = ExpansionML, + ExpansionHS = ExpansionSA, + ExpansionTOL = ExpansionHS + } - [Flags] - public enum HousingFlags - { - None = 0x0, - AOS = 0x10, - SE = 0x40, - ML = 0x80, - Crystal = 0x200, - SA = 0x10000, - HS = 0x20000, - Gothic = 0x40000, - Rustic = 0x80000, - Jungle = 0x100000, - Shadowguard = 0x200000, - TOL = 0x400000, + [Flags] + public enum HousingFlags + { + None = 0x0, + AOS = 0x10, + SE = 0x40, + ML = 0x80, + Crystal = 0x200, + SA = 0x10000, + HS = 0x20000, + Gothic = 0x40000, + Rustic = 0x80000, + Jungle = 0x100000, + Shadowguard = 0x200000, + TOL = 0x400000, - HousingAOS = AOS, - HousingSE = HousingAOS | SE, - HousingML = HousingSE | ML | Crystal, - HousingSA = HousingML | SA | Gothic | Rustic, - HousingHS = HousingSA | HS, - HousingTOL = HousingHS | TOL | Jungle | Shadowguard - } + HousingAOS = AOS, + HousingSE = HousingAOS | SE, + HousingML = HousingSE | ML | Crystal, + HousingSA = HousingML | SA | Gothic | Rustic, + HousingHS = HousingSA | HS, + HousingTOL = HousingHS | TOL | Jungle | Shadowguard + } - public class ExpansionInfo - { - public static ExpansionInfo CoreExpansion => GetInfo(Core.Expansion); + public class ExpansionInfo + { + static ExpansionInfo() + { + Table = new[] + { + new ExpansionInfo( + 0, + "None", + ClientFlags.None, + FeatureFlags.ExpansionNone, + CharacterListFlags.ExpansionNone, + HousingFlags.None), + new ExpansionInfo( + 1, + "The Second Age", + ClientFlags.Felucca, + FeatureFlags.ExpansionT2A, + CharacterListFlags.ExpansionT2A, + HousingFlags.None), + new ExpansionInfo( + 2, + "Renaissance", + ClientFlags.Trammel, + FeatureFlags.ExpansionUOR, + CharacterListFlags.ExpansionUOR, + HousingFlags.None), + new ExpansionInfo( + 3, + "Third Dawn", + ClientFlags.Ilshenar, + FeatureFlags.ExpansionUOTD, + CharacterListFlags.ExpansionUOTD, + HousingFlags.None), + new ExpansionInfo( + 4, + "Blackthorn's Revenge", + ClientFlags.Ilshenar, + FeatureFlags.ExpansionLBR, + CharacterListFlags.ExpansionLBR, + HousingFlags.None), + new ExpansionInfo( + 5, + "Age of Shadows", + ClientFlags.Malas, + FeatureFlags.ExpansionAOS, + CharacterListFlags.ExpansionAOS, + HousingFlags.HousingAOS), + new ExpansionInfo( + 6, + "Samurai Empire", + ClientFlags.Tokuno, + FeatureFlags.ExpansionSE, + CharacterListFlags.ExpansionSE, + HousingFlags.HousingSE), + new ExpansionInfo( + 7, + "Mondain's Legacy", + new ClientVersion("5.0.0a"), + FeatureFlags.ExpansionML, + CharacterListFlags.ExpansionML, + HousingFlags.HousingML), + new ExpansionInfo( + 8, + "Stygian Abyss", + ClientFlags.TerMur, + FeatureFlags.ExpansionSA, + CharacterListFlags.ExpansionSA, + HousingFlags.HousingSA), + new ExpansionInfo( + 9, + "High Seas", + new ClientVersion("7.0.9.0"), + FeatureFlags.ExpansionHS, + CharacterListFlags.ExpansionHS, + HousingFlags.HousingHS), + new ExpansionInfo( + 10, + "Time of Legends", + new ClientVersion("7.0.45.65"), + FeatureFlags.ExpansionTOL, + CharacterListFlags.ExpansionTOL, + HousingFlags.HousingTOL) + }; + } - public static ExpansionInfo[] Table { get; private set; } + public ExpansionInfo( + int id, + string name, + ClientFlags clientFlags, + FeatureFlags supportedFeatures, + CharacterListFlags charListFlags, + HousingFlags customHousingFlag) + : this(id, name, supportedFeatures, charListFlags, customHousingFlag) + { + ClientFlags = clientFlags; + } - static ExpansionInfo() - { - Table = new[] - { - new ExpansionInfo( - 0, - "None", - ClientFlags.None, - FeatureFlags.ExpansionNone, - CharacterListFlags.ExpansionNone, - HousingFlags.None), - new ExpansionInfo( - 1, - "The Second Age", - ClientFlags.Felucca, - FeatureFlags.ExpansionT2A, - CharacterListFlags.ExpansionT2A, - HousingFlags.None), - new ExpansionInfo( - 2, - "Renaissance", - ClientFlags.Trammel, - FeatureFlags.ExpansionUOR, - CharacterListFlags.ExpansionUOR, - HousingFlags.None), - new ExpansionInfo( - 3, - "Third Dawn", - ClientFlags.Ilshenar, - FeatureFlags.ExpansionUOTD, - CharacterListFlags.ExpansionUOTD, - HousingFlags.None), - new ExpansionInfo( - 4, - "Blackthorn's Revenge", - ClientFlags.Ilshenar, - FeatureFlags.ExpansionLBR, - CharacterListFlags.ExpansionLBR, - HousingFlags.None), - new ExpansionInfo( - 5, - "Age of Shadows", - ClientFlags.Malas, - FeatureFlags.ExpansionAOS, - CharacterListFlags.ExpansionAOS, - HousingFlags.HousingAOS), - new ExpansionInfo( - 6, - "Samurai Empire", - ClientFlags.Tokuno, - FeatureFlags.ExpansionSE, - CharacterListFlags.ExpansionSE, - HousingFlags.HousingSE), - new ExpansionInfo( - 7, - "Mondain's Legacy", - new ClientVersion("5.0.0a"), - FeatureFlags.ExpansionML, - CharacterListFlags.ExpansionML, - HousingFlags.HousingML), - new ExpansionInfo( - 8, - "Stygian Abyss", - ClientFlags.TerMur, - FeatureFlags.ExpansionSA, - CharacterListFlags.ExpansionSA, - HousingFlags.HousingSA), - new ExpansionInfo( - 9, - "High Seas", - new ClientVersion("7.0.9.0"), - FeatureFlags.ExpansionHS, - CharacterListFlags.ExpansionHS, - HousingFlags.HousingHS), - new ExpansionInfo( - 10, - "Time of Legends", - new ClientVersion("7.0.45.65"), - FeatureFlags.ExpansionTOL, - CharacterListFlags.ExpansionTOL, - HousingFlags.HousingTOL) - }; - } + public ExpansionInfo( + int id, + string name, + ClientVersion requiredClient, + FeatureFlags supportedFeatures, + CharacterListFlags charListFlags, + HousingFlags customHousingFlag) + : this(id, name, supportedFeatures, charListFlags, customHousingFlag) + { + RequiredClient = requiredClient; + } - public static FeatureFlags GetFeatures(Expansion ex) - { - var info = GetInfo(ex); + private ExpansionInfo( + int id, + string name, + FeatureFlags supportedFeatures, + CharacterListFlags charListFlags, + HousingFlags customHousingFlag) + { + ID = id; + Name = name; - if (info != null) - { - return info.SupportedFeatures; - } + SupportedFeatures = supportedFeatures; + CharacterListFlags = charListFlags; + CustomHousingFlag = customHousingFlag; + } - switch (ex) - { - case Expansion.None: - return FeatureFlags.ExpansionNone; - case Expansion.T2A: - return FeatureFlags.ExpansionT2A; - case Expansion.UOR: - return FeatureFlags.ExpansionUOR; - case Expansion.UOTD: - return FeatureFlags.ExpansionUOTD; - case Expansion.LBR: - return FeatureFlags.ExpansionLBR; - case Expansion.AOS: - return FeatureFlags.ExpansionAOS; - case Expansion.SE: - return FeatureFlags.ExpansionSE; - case Expansion.ML: - return FeatureFlags.ExpansionML; - case Expansion.SA: - return FeatureFlags.ExpansionSA; - case Expansion.HS: - return FeatureFlags.ExpansionHS; - case Expansion.TOL: - return FeatureFlags.ExpansionTOL; - } + public static ExpansionInfo CoreExpansion => GetInfo(Core.Expansion); - return FeatureFlags.ExpansionNone; - } + public static ExpansionInfo[] Table{ get; } - public static ExpansionInfo GetInfo(Expansion ex) - { - return GetInfo((int)ex); - } + public int ID{ get; } + public string Name{ get; set; } - public static ExpansionInfo GetInfo(int ex) - { - var v = ex; + public ClientFlags ClientFlags{ get; set; } + public FeatureFlags SupportedFeatures{ get; set; } + public CharacterListFlags CharacterListFlags{ get; set; } + public ClientVersion RequiredClient{ get; set; } + public HousingFlags CustomHousingFlag{ get; set; } - if (v < 0 || v >= Table.Length) - { - v = 0; - } + public static FeatureFlags GetFeatures(Expansion ex) + { + ExpansionInfo info = GetInfo(ex); - return Table[v]; - } + if (info != null) return info.SupportedFeatures; - public int ID { get; private set; } - public string Name { get; set; } + switch (ex) + { + case Expansion.None: + return FeatureFlags.ExpansionNone; + case Expansion.T2A: + return FeatureFlags.ExpansionT2A; + case Expansion.UOR: + return FeatureFlags.ExpansionUOR; + case Expansion.UOTD: + return FeatureFlags.ExpansionUOTD; + case Expansion.LBR: + return FeatureFlags.ExpansionLBR; + case Expansion.AOS: + return FeatureFlags.ExpansionAOS; + case Expansion.SE: + return FeatureFlags.ExpansionSE; + case Expansion.ML: + return FeatureFlags.ExpansionML; + case Expansion.SA: + return FeatureFlags.ExpansionSA; + case Expansion.HS: + return FeatureFlags.ExpansionHS; + case Expansion.TOL: + return FeatureFlags.ExpansionTOL; + } - public ClientFlags ClientFlags { get; set; } - public FeatureFlags SupportedFeatures { get; set; } - public CharacterListFlags CharacterListFlags { get; set; } - public ClientVersion RequiredClient { get; set; } - public HousingFlags CustomHousingFlag { get; set; } + return FeatureFlags.ExpansionNone; + } - public ExpansionInfo( - int id, - string name, - ClientFlags clientFlags, - FeatureFlags supportedFeatures, - CharacterListFlags charListFlags, - HousingFlags customHousingFlag) - : this(id, name, supportedFeatures, charListFlags, customHousingFlag) - { - ClientFlags = clientFlags; - } + public static ExpansionInfo GetInfo(Expansion ex) + { + return GetInfo((int)ex); + } - public ExpansionInfo( - int id, - string name, - ClientVersion requiredClient, - FeatureFlags supportedFeatures, - CharacterListFlags charListFlags, - HousingFlags customHousingFlag) - : this(id, name, supportedFeatures, charListFlags, customHousingFlag) - { - RequiredClient = requiredClient; - } + public static ExpansionInfo GetInfo(int ex) + { + int v = ex; - private ExpansionInfo( - int id, - string name, - FeatureFlags supportedFeatures, - CharacterListFlags charListFlags, - HousingFlags customHousingFlag) - { - ID = id; - Name = name; + if (v < 0 || v >= Table.Length) v = 0; - SupportedFeatures = supportedFeatures; - CharacterListFlags = charListFlags; - CustomHousingFlag = customHousingFlag; - } + return Table[v]; + } - public override string ToString() - { - return Name; - } - } -} + public override string ToString() + { + return Name; + } + } +} \ No newline at end of file diff --git a/Server/Geometry.cs b/Server/Geometry.cs index 2c515812e..3af3ef7d5 100644 --- a/Server/Geometry.cs +++ b/Server/Geometry.cs @@ -22,510 +22,511 @@ using System; namespace Server { - [Parsable] - public struct Point2D : IPoint2D, IComparable, IComparable - { - internal int m_X; - internal int m_Y; - - public static readonly Point2D Zero = new Point2D( 0, 0 ); - - public Point2D( int x, int y ) - { - m_X = x; - m_Y = y; - } - - public Point2D( IPoint2D p ) : this( p.X, p.Y ) - { - } - - [CommandProperty( AccessLevel.Counselor )] - public int X - { - get => m_X; - set => m_X = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int Y - { - get => m_Y; - set => m_Y = value; - } - - public override string ToString() - { - return $"({m_X}, {m_Y})"; - } - - public static Point2D Parse( string value ) - { - int start = value.IndexOf( '(' ); - int end = value.IndexOf( ',', start + 1 ); - - string param1 = value.Substring( start + 1, end - (start + 1) ).Trim(); - - start = end; - end = value.IndexOf( ')', start + 1 ); - - string param2 = value.Substring( start + 1, end - (start + 1) ).Trim(); - - return new Point2D( Convert.ToInt32( param1 ), Convert.ToInt32( param2 ) ); - } - - public int CompareTo( Point2D other ) - { - int v = ( m_X.CompareTo( other.m_X ) ); - - if ( v == 0 ) - v = ( m_Y.CompareTo( other.m_Y ) ); - - return v; - } - - public int CompareTo( object other ) - { - if ( other is Point2D d ) - return CompareTo( d ); - if ( other == null ) - return -1; - - throw new ArgumentException(); - } - - public override bool Equals( object o ) - { - if ( !(o is IPoint2D) ) return false; - - IPoint2D p = (IPoint2D)o; - - return m_X == p.X && m_Y == p.Y; - } - - public override int GetHashCode() - { - return m_X ^ m_Y; - } - - public static bool operator == ( Point2D l, Point2D r ) - { - return l.m_X == r.m_X && l.m_Y == r.m_Y; - } - - public static bool operator != ( Point2D l, Point2D r ) - { - return l.m_X != r.m_X || l.m_Y != r.m_Y; - } - - public static bool operator == ( Point2D l, IPoint2D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X == r.X && l.m_Y == r.Y; - } - - public static bool operator != ( Point2D l, IPoint2D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X !=r.X || l.m_Y != r.Y; - } - - public static bool operator > ( Point2D l, Point2D r ) - { - return l.m_X > r.m_X && l.m_Y > r.m_Y; - } - - public static bool operator > ( Point2D l, Point3D r ) - { - return l.m_X > r.m_X && l.m_Y > r.m_Y; - } - - public static bool operator > ( Point2D l, IPoint2D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X > r.X && l.m_Y > r.Y; - } - - public static bool operator < ( Point2D l, Point2D r ) - { - return l.m_X < r.m_X && l.m_Y < r.m_Y; - } - - public static bool operator < ( Point2D l, Point3D r ) - { - return l.m_X < r.m_X && l.m_Y < r.m_Y; - } - - public static bool operator < ( Point2D l, IPoint2D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X < r.X && l.m_Y < r.Y; - } - - public static bool operator >= ( Point2D l, Point2D r ) - { - return l.m_X >= r.m_X && l.m_Y >= r.m_Y; - } - - public static bool operator >= ( Point2D l, Point3D r ) - { - return l.m_X >= r.m_X && l.m_Y >= r.m_Y; - } - - public static bool operator >= ( Point2D l, IPoint2D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X >= r.X && l.m_Y >= r.Y; - } - - public static bool operator <= ( Point2D l, Point2D r ) - { - return l.m_X <= r.m_X && l.m_Y <= r.m_Y; - } - - public static bool operator <= ( Point2D l, Point3D r ) - { - return l.m_X <= r.m_X && l.m_Y <= r.m_Y; - } - - public static bool operator <= ( Point2D l, IPoint2D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X <= r.X && l.m_Y <= r.Y; - } - } - - [Parsable] - public struct Point3D : IPoint3D, IComparable, IComparable - { - internal int m_X; - internal int m_Y; - internal int m_Z; - - public static readonly Point3D Zero = new Point3D( 0, 0, 0 ); - - public Point3D( int x, int y, int z ) - { - m_X = x; - m_Y = y; - m_Z = z; - } - - public Point3D( IPoint3D p ) - : this( p.X, p.Y, p.Z ) - { - } - - public Point3D( IPoint2D p, int z ) - : this( p.X, p.Y, z ) - { - } - - [CommandProperty( AccessLevel.Counselor )] - public int X - { - get => m_X; - set => m_X = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int Y - { - get => m_Y; - set => m_Y = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int Z - { - get => m_Z; - set => m_Z = value; - } - - public override string ToString() - { - return $"({m_X}, {m_Y}, {m_Z})"; - } - - public override bool Equals( object o ) - { - if ( !(o is IPoint3D) ) - return false; - - IPoint3D p = (IPoint3D) o; - - return m_X == p.X && m_Y == p.Y && m_Z == p.Z; - } - - public override int GetHashCode() - { - return m_X ^ m_Y ^ m_Z; - } - - public static Point3D Parse( string value ) - { - int start = value.IndexOf( '(' ); - int end = value.IndexOf( ',', start + 1 ); - - string param1 = value.Substring( start + 1, end - ( start + 1 ) ).Trim(); - - start = end; - end = value.IndexOf( ',', start + 1 ); - - string param2 = value.Substring( start + 1, end - ( start + 1 ) ).Trim(); - - start = end; - end = value.IndexOf( ')', start + 1 ); - - string param3 = value.Substring( start + 1, end - ( start + 1 ) ).Trim(); - - return new Point3D( Convert.ToInt32( param1 ), Convert.ToInt32( param2 ), Convert.ToInt32( param3 ) ); - } - - public static bool operator ==( Point3D l, Point3D r ) - { - return l.m_X == r.m_X && l.m_Y == r.m_Y && l.m_Z == r.m_Z; - } - - public static bool operator !=( Point3D l, Point3D r ) - { - return l.m_X != r.m_X || l.m_Y != r.m_Y || l.m_Z != r.m_Z; - } - - public static bool operator ==( Point3D l, IPoint3D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X == r.X && l.m_Y == r.Y && l.m_Z == r.Z; - } - - public static bool operator !=( Point3D l, IPoint3D r ) - { - if ( ReferenceEquals( r, null ) ) - return false; - - return l.m_X != r.X || l.m_Y != r.Y || l.m_Z != r.Z; - } - - public int CompareTo( Point3D other ) - { - int v = ( m_X.CompareTo( other.m_X ) ); - - if ( v == 0 ) - { - v = ( m_Y.CompareTo( other.m_Y ) ); - - if ( v == 0 ) - v = ( m_Z.CompareTo( other.m_Z ) ); - } - - return v; - } - - public int CompareTo( object other ) - { - if ( other is Point3D d ) - return CompareTo( d ); - if ( other == null ) - return -1; - - throw new ArgumentException(); - } - } - - [NoSort] - [Parsable] - [PropertyObject] - public struct Rectangle2D - { - private Point2D m_Start; - private Point2D m_End; - - public Rectangle2D( IPoint2D start, IPoint2D end ) - { - m_Start = new Point2D( start ); - m_End = new Point2D( end ); - } - - public Rectangle2D( int x, int y, int width, int height ) - { - m_Start = new Point2D( x, y ); - m_End = new Point2D( x + width, y + height ); - } - - public void Set( int x, int y, int width, int height ) - { - m_Start = new Point2D( x, y ); - m_End = new Point2D( x + width, y + height ); - } - - public static Rectangle2D Parse( string value ) - { - int start = value.IndexOf( '(' ); - int end = value.IndexOf( ',', start + 1 ); - - string param1 = value.Substring( start + 1, end - (start + 1) ).Trim(); - - start = end; - end = value.IndexOf( ',', start + 1 ); - - string param2 = value.Substring( start + 1, end - (start + 1) ).Trim(); - - start = end; - end = value.IndexOf( ',', start + 1 ); - - string param3 = value.Substring( start + 1, end - (start + 1) ).Trim(); - - start = end; - end = value.IndexOf( ')', start + 1 ); - - string param4 = value.Substring( start + 1, end - (start + 1) ).Trim(); - - return new Rectangle2D( Convert.ToInt32( param1 ), Convert.ToInt32( param2 ), Convert.ToInt32( param3 ), Convert.ToInt32( param4 ) ); - } - - [CommandProperty( AccessLevel.Counselor )] - public Point2D Start - { - get => m_Start; - set => m_Start = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public Point2D End - { - get => m_End; - set => m_End = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int X - { - get => m_Start.m_X; - set => m_Start.m_X = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int Y - { - get => m_Start.m_Y; - set => m_Start.m_Y = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int Width - { - get => m_End.m_X - m_Start.m_X; - set => m_End.m_X = m_Start.m_X + value; - } - - [CommandProperty( AccessLevel.Counselor )] - public int Height - { - get => m_End.m_Y - m_Start.m_Y; - set => m_End.m_Y = m_Start.m_Y + value; - } - - public void MakeHold( Rectangle2D r ) - { - if ( r.m_Start.m_X < m_Start.m_X ) - m_Start.m_X = r.m_Start.m_X; - - if ( r.m_Start.m_Y < m_Start.m_Y ) - m_Start.m_Y = r.m_Start.m_Y; - - if ( r.m_End.m_X > m_End.m_X ) - m_End.m_X = r.m_End.m_X; - - if ( r.m_End.m_Y > m_End.m_Y ) - m_End.m_Y = r.m_End.m_Y; - } - - public bool Contains( Point3D p ) - { - return ( m_Start.m_X <= p.m_X && m_Start.m_Y <= p.m_Y && m_End.m_X > p.m_X && m_End.m_Y > p.m_Y ); - //return ( m_Start <= p && m_End > p ); - } - - public bool Contains( Point2D p ) - { - return ( m_Start.m_X <= p.m_X && m_Start.m_Y <= p.m_Y && m_End.m_X > p.m_X && m_End.m_Y > p.m_Y ); - //return ( m_Start <= p && m_End > p ); - } - - public bool Contains( IPoint2D p ) - { - return ( m_Start <= p && m_End > p ); - } - - public override string ToString() - { - return $"({X}, {Y})+({Width}, {Height})"; - } - } - - [NoSort] - [PropertyObject] - public struct Rectangle3D - { - public Rectangle3D( Point3D start, Point3D end ) - { - Start = start; - End = end; - } - - public Rectangle3D( int x, int y, int z, int width, int height, int depth ) - { - Start = new Point3D( x, y, z ); - End = new Point3D( x + width, y + height, z + depth ); - } - - [CommandProperty( AccessLevel.Counselor )] - public Point3D Start { get; set; } - - [CommandProperty( AccessLevel.Counselor )] - public Point3D End { get; set; } - - [CommandProperty( AccessLevel.Counselor )] - public int Width => End.X - Start.X; - - [CommandProperty( AccessLevel.Counselor )] - public int Height => End.Y - Start.Y; - - [CommandProperty( AccessLevel.Counselor )] - public int Depth => End.Z - Start.Z; - - public bool Contains( Point3D p ) - { - return ( p.m_X >= Start.m_X ) - && ( p.m_X < End.m_X ) - && ( p.m_Y >= Start.m_Y ) - && ( p.m_Y < End.m_Y ) - && ( p.m_Z >= Start.m_Z ) - && ( p.m_Z < End.m_Z ); - } - - public bool Contains( IPoint3D p ) - { - return ( p.X >= Start.m_X ) - && ( p.X < End.m_X ) - && ( p.Y >= Start.m_Y ) - && ( p.Y < End.m_Y ) - && ( p.Z >= Start.m_Z ) - && ( p.Z < End.m_Z ); - } - } -} + [Parsable] + public struct Point2D : IPoint2D, IComparable, IComparable + { + internal int m_X; + internal int m_Y; + + public static readonly Point2D Zero = new Point2D(0, 0); + + public Point2D(int x, int y) + { + m_X = x; + m_Y = y; + } + + public Point2D(IPoint2D p) : this(p.X, p.Y) + { + } + + [CommandProperty(AccessLevel.Counselor)] + public int X + { + get => m_X; + set => m_X = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int Y + { + get => m_Y; + set => m_Y = value; + } + + public override string ToString() + { + return $"({m_X}, {m_Y})"; + } + + public static Point2D Parse(string value) + { + int start = value.IndexOf('('); + int end = value.IndexOf(',', start + 1); + + string param1 = value.Substring(start + 1, end - (start + 1)).Trim(); + + start = end; + end = value.IndexOf(')', start + 1); + + string param2 = value.Substring(start + 1, end - (start + 1)).Trim(); + + return new Point2D(Convert.ToInt32(param1), Convert.ToInt32(param2)); + } + + public int CompareTo(Point2D other) + { + int v = m_X.CompareTo(other.m_X); + + if (v == 0) + v = m_Y.CompareTo(other.m_Y); + + return v; + } + + public int CompareTo(object other) + { + if (other is Point2D d) + return CompareTo(d); + if (other == null) + return -1; + + throw new ArgumentException(); + } + + public override bool Equals(object o) + { + if (!(o is IPoint2D)) return false; + + IPoint2D p = (IPoint2D)o; + + return m_X == p.X && m_Y == p.Y; + } + + public override int GetHashCode() + { + return m_X ^ m_Y; + } + + public static bool operator ==(Point2D l, Point2D r) + { + return l.m_X == r.m_X && l.m_Y == r.m_Y; + } + + public static bool operator !=(Point2D l, Point2D r) + { + return l.m_X != r.m_X || l.m_Y != r.m_Y; + } + + public static bool operator ==(Point2D l, IPoint2D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X == r.X && l.m_Y == r.Y; + } + + public static bool operator !=(Point2D l, IPoint2D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X != r.X || l.m_Y != r.Y; + } + + public static bool operator >(Point2D l, Point2D r) + { + return l.m_X > r.m_X && l.m_Y > r.m_Y; + } + + public static bool operator >(Point2D l, Point3D r) + { + return l.m_X > r.m_X && l.m_Y > r.m_Y; + } + + public static bool operator >(Point2D l, IPoint2D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X > r.X && l.m_Y > r.Y; + } + + public static bool operator <(Point2D l, Point2D r) + { + return l.m_X < r.m_X && l.m_Y < r.m_Y; + } + + public static bool operator <(Point2D l, Point3D r) + { + return l.m_X < r.m_X && l.m_Y < r.m_Y; + } + + public static bool operator <(Point2D l, IPoint2D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X < r.X && l.m_Y < r.Y; + } + + public static bool operator >=(Point2D l, Point2D r) + { + return l.m_X >= r.m_X && l.m_Y >= r.m_Y; + } + + public static bool operator >=(Point2D l, Point3D r) + { + return l.m_X >= r.m_X && l.m_Y >= r.m_Y; + } + + public static bool operator >=(Point2D l, IPoint2D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X >= r.X && l.m_Y >= r.Y; + } + + public static bool operator <=(Point2D l, Point2D r) + { + return l.m_X <= r.m_X && l.m_Y <= r.m_Y; + } + + public static bool operator <=(Point2D l, Point3D r) + { + return l.m_X <= r.m_X && l.m_Y <= r.m_Y; + } + + public static bool operator <=(Point2D l, IPoint2D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X <= r.X && l.m_Y <= r.Y; + } + } + + [Parsable] + public struct Point3D : IPoint3D, IComparable, IComparable + { + internal int m_X; + internal int m_Y; + internal int m_Z; + + public static readonly Point3D Zero = new Point3D(0, 0, 0); + + public Point3D(int x, int y, int z) + { + m_X = x; + m_Y = y; + m_Z = z; + } + + public Point3D(IPoint3D p) + : this(p.X, p.Y, p.Z) + { + } + + public Point3D(IPoint2D p, int z) + : this(p.X, p.Y, z) + { + } + + [CommandProperty(AccessLevel.Counselor)] + public int X + { + get => m_X; + set => m_X = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int Y + { + get => m_Y; + set => m_Y = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int Z + { + get => m_Z; + set => m_Z = value; + } + + public override string ToString() + { + return $"({m_X}, {m_Y}, {m_Z})"; + } + + public override bool Equals(object o) + { + if (!(o is IPoint3D)) + return false; + + IPoint3D p = (IPoint3D)o; + + return m_X == p.X && m_Y == p.Y && m_Z == p.Z; + } + + public override int GetHashCode() + { + return m_X ^ m_Y ^ m_Z; + } + + public static Point3D Parse(string value) + { + int start = value.IndexOf('('); + int end = value.IndexOf(',', start + 1); + + string param1 = value.Substring(start + 1, end - (start + 1)).Trim(); + + start = end; + end = value.IndexOf(',', start + 1); + + string param2 = value.Substring(start + 1, end - (start + 1)).Trim(); + + start = end; + end = value.IndexOf(')', start + 1); + + string param3 = value.Substring(start + 1, end - (start + 1)).Trim(); + + return new Point3D(Convert.ToInt32(param1), Convert.ToInt32(param2), Convert.ToInt32(param3)); + } + + public static bool operator ==(Point3D l, Point3D r) + { + return l.m_X == r.m_X && l.m_Y == r.m_Y && l.m_Z == r.m_Z; + } + + public static bool operator !=(Point3D l, Point3D r) + { + return l.m_X != r.m_X || l.m_Y != r.m_Y || l.m_Z != r.m_Z; + } + + public static bool operator ==(Point3D l, IPoint3D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X == r.X && l.m_Y == r.Y && l.m_Z == r.Z; + } + + public static bool operator !=(Point3D l, IPoint3D r) + { + if (ReferenceEquals(r, null)) + return false; + + return l.m_X != r.X || l.m_Y != r.Y || l.m_Z != r.Z; + } + + public int CompareTo(Point3D other) + { + int v = m_X.CompareTo(other.m_X); + + if (v == 0) + { + v = m_Y.CompareTo(other.m_Y); + + if (v == 0) + v = m_Z.CompareTo(other.m_Z); + } + + return v; + } + + public int CompareTo(object other) + { + if (other is Point3D d) + return CompareTo(d); + if (other == null) + return -1; + + throw new ArgumentException(); + } + } + + [NoSort] + [Parsable] + [PropertyObject] + public struct Rectangle2D + { + private Point2D m_Start; + private Point2D m_End; + + public Rectangle2D(IPoint2D start, IPoint2D end) + { + m_Start = new Point2D(start); + m_End = new Point2D(end); + } + + public Rectangle2D(int x, int y, int width, int height) + { + m_Start = new Point2D(x, y); + m_End = new Point2D(x + width, y + height); + } + + public void Set(int x, int y, int width, int height) + { + m_Start = new Point2D(x, y); + m_End = new Point2D(x + width, y + height); + } + + public static Rectangle2D Parse(string value) + { + int start = value.IndexOf('('); + int end = value.IndexOf(',', start + 1); + + string param1 = value.Substring(start + 1, end - (start + 1)).Trim(); + + start = end; + end = value.IndexOf(',', start + 1); + + string param2 = value.Substring(start + 1, end - (start + 1)).Trim(); + + start = end; + end = value.IndexOf(',', start + 1); + + string param3 = value.Substring(start + 1, end - (start + 1)).Trim(); + + start = end; + end = value.IndexOf(')', start + 1); + + string param4 = value.Substring(start + 1, end - (start + 1)).Trim(); + + return new Rectangle2D(Convert.ToInt32(param1), Convert.ToInt32(param2), Convert.ToInt32(param3), + Convert.ToInt32(param4)); + } + + [CommandProperty(AccessLevel.Counselor)] + public Point2D Start + { + get => m_Start; + set => m_Start = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public Point2D End + { + get => m_End; + set => m_End = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int X + { + get => m_Start.m_X; + set => m_Start.m_X = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int Y + { + get => m_Start.m_Y; + set => m_Start.m_Y = value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int Width + { + get => m_End.m_X - m_Start.m_X; + set => m_End.m_X = m_Start.m_X + value; + } + + [CommandProperty(AccessLevel.Counselor)] + public int Height + { + get => m_End.m_Y - m_Start.m_Y; + set => m_End.m_Y = m_Start.m_Y + value; + } + + public void MakeHold(Rectangle2D r) + { + if (r.m_Start.m_X < m_Start.m_X) + m_Start.m_X = r.m_Start.m_X; + + if (r.m_Start.m_Y < m_Start.m_Y) + m_Start.m_Y = r.m_Start.m_Y; + + if (r.m_End.m_X > m_End.m_X) + m_End.m_X = r.m_End.m_X; + + if (r.m_End.m_Y > m_End.m_Y) + m_End.m_Y = r.m_End.m_Y; + } + + public bool Contains(Point3D p) + { + return m_Start.m_X <= p.m_X && m_Start.m_Y <= p.m_Y && m_End.m_X > p.m_X && m_End.m_Y > p.m_Y; + //return ( m_Start <= p && m_End > p ); + } + + public bool Contains(Point2D p) + { + return m_Start.m_X <= p.m_X && m_Start.m_Y <= p.m_Y && m_End.m_X > p.m_X && m_End.m_Y > p.m_Y; + //return ( m_Start <= p && m_End > p ); + } + + public bool Contains(IPoint2D p) + { + return m_Start <= p && m_End > p; + } + + public override string ToString() + { + return $"({X}, {Y})+({Width}, {Height})"; + } + } + + [NoSort] + [PropertyObject] + public struct Rectangle3D + { + public Rectangle3D(Point3D start, Point3D end) + { + Start = start; + End = end; + } + + public Rectangle3D(int x, int y, int z, int width, int height, int depth) + { + Start = new Point3D(x, y, z); + End = new Point3D(x + width, y + height, z + depth); + } + + [CommandProperty(AccessLevel.Counselor)] + public Point3D Start{ get; set; } + + [CommandProperty(AccessLevel.Counselor)] + public Point3D End{ get; set; } + + [CommandProperty(AccessLevel.Counselor)] + public int Width => End.X - Start.X; + + [CommandProperty(AccessLevel.Counselor)] + public int Height => End.Y - Start.Y; + + [CommandProperty(AccessLevel.Counselor)] + public int Depth => End.Z - Start.Z; + + public bool Contains(Point3D p) + { + return p.m_X >= Start.m_X + && p.m_X < End.m_X + && p.m_Y >= Start.m_Y + && p.m_Y < End.m_Y + && p.m_Z >= Start.m_Z + && p.m_Z < End.m_Z; + } + + public bool Contains(IPoint3D p) + { + return p.X >= Start.m_X + && p.X < End.m_X + && p.Y >= Start.m_Y + && p.Y < End.m_Y + && p.Z >= Start.m_Z + && p.Z < End.m_Z; + } + } +} \ No newline at end of file diff --git a/Server/Guild.cs b/Server/Guild.cs index 2c6fafef6..a13336d34 100644 --- a/Server/Guild.cs +++ b/Server/Guild.cs @@ -18,113 +18,106 @@ * ***************************************************************************/ -using System; using System.Collections.Generic; namespace Server.Guilds { - public enum GuildType - { - Regular, - Chaos, - Order - } + public enum GuildType + { + Regular, + Chaos, + Order + } - public abstract class BaseGuild : ISerializable - { - protected BaseGuild( int Id )//serialization ctor - { - this.Id = Id; - List.Add( this.Id, this ); - if ( this.Id+1 > m_NextID ) - m_NextID = this.Id + 1; - } + public abstract class BaseGuild : ISerializable + { + private static int m_NextID = 1; - protected BaseGuild() - { - Id = m_NextID++; - List.Add( Id, this ); - } + protected BaseGuild(int Id) //serialization ctor + { + this.Id = Id; + List.Add(this.Id, this); + if (this.Id + 1 > m_NextID) + m_NextID = this.Id + 1; + } - [CommandProperty( AccessLevel.Counselor )] - public int Id { get; } + protected BaseGuild() + { + Id = m_NextID++; + List.Add(Id, this); + } - int ISerializable.TypeReference => 0; + [CommandProperty(AccessLevel.Counselor)] + public int Id{ get; } - int ISerializable.SerialIdentity => Id; + public abstract string Abbreviation{ get; set; } + public abstract string Name{ get; set; } + public abstract GuildType Type{ get; set; } + public abstract bool Disbanded{ get; } - public abstract void Deserialize( GenericReader reader ); - public abstract void Serialize( GenericWriter writer ); + public static Dictionary List{ get; } = new Dictionary(); - public abstract string Abbreviation { get; set; } - public abstract string Name { get; set; } - public abstract GuildType Type { get; set; } - public abstract bool Disbanded{ get; } - public abstract void OnDelete( Mobile mob ); + int ISerializable.TypeReference => 0; - private static int m_NextID = 1; + int ISerializable.SerialIdentity => Id; + public abstract void Serialize(GenericWriter writer); - public static Dictionary List { get; } = new Dictionary(); + public abstract void Deserialize(GenericReader reader); + public abstract void OnDelete(Mobile mob); - public static BaseGuild Find( int id ) - { - BaseGuild g; + public static BaseGuild Find(int id) + { + BaseGuild g; - List.TryGetValue( id, out g ); + List.TryGetValue(id, out g); - return g; - } + return g; + } - public static BaseGuild FindByName( string name ) - { - foreach ( BaseGuild g in List.Values ) - { - if ( g.Name == name ) - return g; - } + public static BaseGuild FindByName(string name) + { + foreach (BaseGuild g in List.Values) + if (g.Name == name) + return g; - return null; - } + return null; + } - public static BaseGuild FindByAbbrev( string abbr ) - { - foreach ( BaseGuild g in List.Values ) - { - if ( g.Abbreviation == abbr ) - return g; - } + public static BaseGuild FindByAbbrev(string abbr) + { + foreach (BaseGuild g in List.Values) + if (g.Abbreviation == abbr) + return g; - return null; - } + return null; + } - public static List Search( string find ) - { - string[] words = find.ToLower().Split( ' ' ); - List results = new List(); + public static List Search(string find) + { + string[] words = find.ToLower().Split(' '); + List results = new List(); - foreach ( BaseGuild g in List.Values ) - { - bool match = true; - string name = g.Name.ToLower(); - for (int i=0;i m_Strings; - - internal int m_TextEntries, m_Switches; - - private static int m_NextSerial = 1; - - private int m_Serial; - private int m_X, m_Y; - - private bool m_Dragable = true; - private bool m_Closable = true; - private bool m_Resizable = true; - private bool m_Disposable = true; - - public static int GetTypeID( Type type ) - { - return type.FullName.GetHashCode(); - } - - public Gump( int x, int y ) - { - do - { - m_Serial = m_NextSerial++; - } while ( m_Serial == 0 ); // standard client apparently doesn't send a gump response packet if serial == 0 - - m_X = x; - m_Y = y; - - TypeID = GetTypeID( GetType() ); - - Entries = new List(); - m_Strings = new List(); - } - - public void Invalidate() - { - //if ( m_Strings.Count > 0 ) - // m_Strings.Clear(); - } - - public int TypeID { get; } - - public List Entries { get; } - - public int Serial - { - get => m_Serial; - set - { - if ( m_Serial != value ) - { - m_Serial = value; - Invalidate(); - } - } - } - - public int X - { - get => m_X; - set - { - if ( m_X != value ) - { - m_X = value; - Invalidate(); - } - } - } - - public int Y - { - get => m_Y; - set - { - if ( m_Y != value ) - { - m_Y = value; - Invalidate(); - } - } - } - - public bool Disposable - { - get => m_Disposable; - set - { - if ( m_Disposable != value ) - { - m_Disposable = value; - Invalidate(); - } - } - } - - public bool Resizable - { - get => m_Resizable; - set - { - if ( m_Resizable != value ) - { - m_Resizable = value; - Invalidate(); - } - } - } - - public bool Dragable - { - get => m_Dragable; - set - { - if ( m_Dragable != value ) - { - m_Dragable = value; - Invalidate(); - } - } - } - - public bool Closable - { - get => m_Closable; - set - { - if ( m_Closable != value ) - { - m_Closable = value; - Invalidate(); - } - } - } - - public void AddPage( int page ) - { - Add( new GumpPage( page ) ); - } - - public void AddAlphaRegion( int x, int y, int width, int height ) - { - Add( new GumpAlphaRegion( x, y, width, height ) ); - } - - public void AddBackground( int x, int y, int width, int height, int gumpID ) - { - Add( new GumpBackground( x, y, width, height, gumpID ) ); - } - - public void AddButton( int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param ) - { - Add( new GumpButton( x, y, normalID, pressedID, buttonID, type, param ) ); - } - - public void AddCheck( int x, int y, int inactiveID, int activeID, bool initialState, int switchID ) - { - Add( new GumpCheck( x, y, inactiveID, activeID, initialState, switchID ) ); - } - - public void AddGroup( int group ) - { - Add( new GumpGroup( group ) ); - } - - public void AddTooltip( int number ) - { - Add( new GumpTooltip( number ) ); - } - - public void AddHtml( int x, int y, int width, int height, string text, bool background, bool scrollbar ) - { - Add( new GumpHtml( x, y, width, height, text, background, scrollbar ) ); - } - - public void AddHtmlLocalized( int x, int y, int width, int height, int number, bool background, bool scrollbar ) - { - Add( new GumpHtmlLocalized( x, y, width, height, number, background, scrollbar ) ); - } - - public void AddHtmlLocalized( int x, int y, int width, int height, int number, int color, bool background, bool scrollbar ) - { - Add( new GumpHtmlLocalized( x, y, width, height, number, color, background, scrollbar ) ); - } - - public void AddHtmlLocalized( int x, int y, int width, int height, int number, string args, int color, bool background, bool scrollbar ) - { - Add( new GumpHtmlLocalized( x, y, width, height, number, args, color, background, scrollbar ) ); - } - - public void AddImage( int x, int y, int gumpID ) - { - Add( new GumpImage( x, y, gumpID ) ); - } - - public void AddImage( int x, int y, int gumpID, int hue ) - { - Add( new GumpImage( x, y, gumpID, hue ) ); - } - - public void AddImageTiled( int x, int y, int width, int height, int gumpID ) - { - Add( new GumpImageTiled( x, y, width, height, gumpID ) ); - } - - public void AddImageTiledButton( int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param, int itemID, int hue, int width, int height ) - { - Add( new GumpImageTileButton( x, y, normalID, pressedID, buttonID, type, param, itemID, hue, width, height ) ); - } - public void AddImageTiledButton( int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param, int itemID, int hue, int width, int height, int localizedTooltip ) - { - Add( new GumpImageTileButton( x, y, normalID, pressedID, buttonID, type, param, itemID, hue, width, height, localizedTooltip ) ); - } - - public void AddItem( int x, int y, int itemID ) - { - Add( new GumpItem( x, y, itemID ) ); - } - - public void AddItem( int x, int y, int itemID, int hue ) - { - Add( new GumpItem( x, y, itemID, hue ) ); - } - - public void AddLabel( int x, int y, int hue, string text ) - { - Add( new GumpLabel( x, y, hue, text ) ); - } - - public void AddLabelCropped( int x, int y, int width, int height, int hue, string text ) - { - Add( new GumpLabelCropped( x, y, width, height, hue, text ) ); - } - - public void AddRadio( int x, int y, int inactiveID, int activeID, bool initialState, int switchID ) - { - Add( new GumpRadio( x, y, inactiveID, activeID, initialState, switchID ) ); - } - - public void AddTextEntry( int x, int y, int width, int height, int hue, int entryID, string initialText ) - { - Add( new GumpTextEntry( x, y, width, height, hue, entryID, initialText ) ); - } - - public void AddTextEntry( int x, int y, int width, int height, int hue, int entryID, string initialText, int size ) { - Add( new GumpTextEntryLimited( x, y, width, height, hue, entryID, initialText, size ) ); - } - - public void AddItemProperty( int serial ) - { - Add( new GumpItemProperty( serial ) ); - } - - public void Add( GumpEntry g ) - { - if ( g.Parent != this ) - { - g.Parent = this; - } - else if ( !Entries.Contains( g ) ) - { - Invalidate(); - Entries.Add( g ); - } - } - - public void Remove( GumpEntry g ) - { - if (g == null || !Entries.Contains(g)) - return; - - Invalidate(); - Entries.Remove( g ); - g.Parent = null; - } - - public int Intern( string value ) - { - int indexOf = m_Strings.IndexOf( value ); - - if ( indexOf >= 0 ) - { - return indexOf; - } - - Invalidate(); - m_Strings.Add( value ); - return m_Strings.Count - 1; - } - - public void SendTo( NetState state ) - { - state.AddGump( this ); - state.Send( Compile( state ) ); - } - - public static byte[] StringToBuffer( string str ) - { - return Encoding.ASCII.GetBytes( str ); - } - - private static byte[] m_BeginLayout = StringToBuffer( "{ " ); - private static byte[] m_EndLayout = StringToBuffer( " }" ); - - private static byte[] m_NoMove = StringToBuffer( "{ nomove }" ); - private static byte[] m_NoClose = StringToBuffer( "{ noclose }" ); - private static byte[] m_NoDispose = StringToBuffer( "{ nodispose }" ); - private static byte[] m_NoResize = StringToBuffer( "{ noresize }" ); - - private Packet Compile() - { - return Compile( null ); - } - - private Packet Compile( NetState ns ) - { - IGumpWriter disp; - - if ( ns != null && ns.Unpack ) - disp = new DisplayGumpPacked( this ); - else - disp = new DisplayGumpFast( this ); - - if ( !m_Dragable ) - disp.AppendLayout( m_NoMove ); - - if ( !m_Closable ) - disp.AppendLayout( m_NoClose ); - - if ( !m_Disposable ) - disp.AppendLayout( m_NoDispose ); - - if ( !m_Resizable ) - disp.AppendLayout( m_NoResize ); - - int count = Entries.Count; - GumpEntry e; - - for ( int i = 0; i < count; ++i ) - { - e = Entries[i]; - - disp.AppendLayout( m_BeginLayout ); - e.AppendTo( ns, disp ); - disp.AppendLayout( m_EndLayout ); - } - - disp.WriteStrings( m_Strings ); - - disp.Flush(); - - m_TextEntries = disp.TextEntries; - m_Switches = disp.Switches; - - return disp as Packet; - } - - public virtual void OnResponse( NetState sender, RelayInfo info ) - { - } - - public virtual void OnServerClose( NetState owner ) - { - } - } -} + public class Gump + { + private static int m_NextSerial = 1; + + private static byte[] m_BeginLayout = StringToBuffer("{ "); + private static byte[] m_EndLayout = StringToBuffer(" }"); + + private static byte[] m_NoMove = StringToBuffer("{ nomove }"); + private static byte[] m_NoClose = StringToBuffer("{ noclose }"); + private static byte[] m_NoDispose = StringToBuffer("{ nodispose }"); + private static byte[] m_NoResize = StringToBuffer("{ noresize }"); + private bool m_Closable = true; + private bool m_Disposable = true; + + private bool m_Dragable = true; + private bool m_Resizable = true; + + private int m_Serial; + private List m_Strings; + + internal int m_TextEntries, m_Switches; + private int m_X, m_Y; + + public Gump(int x, int y) + { + do + { + m_Serial = m_NextSerial++; + } while (m_Serial == 0); // standard client apparently doesn't send a gump response packet if serial == 0 + + m_X = x; + m_Y = y; + + TypeID = GetTypeID(GetType()); + + Entries = new List(); + m_Strings = new List(); + } + + public int TypeID{ get; } + + public List Entries{ get; } + + public int Serial + { + get => m_Serial; + set + { + if (m_Serial != value) + { + m_Serial = value; + Invalidate(); + } + } + } + + public int X + { + get => m_X; + set + { + if (m_X != value) + { + m_X = value; + Invalidate(); + } + } + } + + public int Y + { + get => m_Y; + set + { + if (m_Y != value) + { + m_Y = value; + Invalidate(); + } + } + } + + public bool Disposable + { + get => m_Disposable; + set + { + if (m_Disposable != value) + { + m_Disposable = value; + Invalidate(); + } + } + } + + public bool Resizable + { + get => m_Resizable; + set + { + if (m_Resizable != value) + { + m_Resizable = value; + Invalidate(); + } + } + } + + public bool Dragable + { + get => m_Dragable; + set + { + if (m_Dragable != value) + { + m_Dragable = value; + Invalidate(); + } + } + } + + public bool Closable + { + get => m_Closable; + set + { + if (m_Closable != value) + { + m_Closable = value; + Invalidate(); + } + } + } + + public static int GetTypeID(Type type) + { + return type.FullName.GetHashCode(); + } + + public void Invalidate() + { + //if ( m_Strings.Count > 0 ) + // m_Strings.Clear(); + } + + public void AddPage(int page) + { + Add(new GumpPage(page)); + } + + public void AddAlphaRegion(int x, int y, int width, int height) + { + Add(new GumpAlphaRegion(x, y, width, height)); + } + + public void AddBackground(int x, int y, int width, int height, int gumpID) + { + Add(new GumpBackground(x, y, width, height, gumpID)); + } + + public void AddButton(int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param) + { + Add(new GumpButton(x, y, normalID, pressedID, buttonID, type, param)); + } + + public void AddCheck(int x, int y, int inactiveID, int activeID, bool initialState, int switchID) + { + Add(new GumpCheck(x, y, inactiveID, activeID, initialState, switchID)); + } + + public void AddGroup(int group) + { + Add(new GumpGroup(group)); + } + + public void AddTooltip(int number) + { + Add(new GumpTooltip(number)); + } + + public void AddHtml(int x, int y, int width, int height, string text, bool background, bool scrollbar) + { + Add(new GumpHtml(x, y, width, height, text, background, scrollbar)); + } + + public void AddHtmlLocalized(int x, int y, int width, int height, int number, bool background, bool scrollbar) + { + Add(new GumpHtmlLocalized(x, y, width, height, number, background, scrollbar)); + } + + public void AddHtmlLocalized(int x, int y, int width, int height, int number, int color, bool background, + bool scrollbar) + { + Add(new GumpHtmlLocalized(x, y, width, height, number, color, background, scrollbar)); + } + + public void AddHtmlLocalized(int x, int y, int width, int height, int number, string args, int color, + bool background, bool scrollbar) + { + Add(new GumpHtmlLocalized(x, y, width, height, number, args, color, background, scrollbar)); + } + + public void AddImage(int x, int y, int gumpID) + { + Add(new GumpImage(x, y, gumpID)); + } + + public void AddImage(int x, int y, int gumpID, int hue) + { + Add(new GumpImage(x, y, gumpID, hue)); + } + + public void AddImageTiled(int x, int y, int width, int height, int gumpID) + { + Add(new GumpImageTiled(x, y, width, height, gumpID)); + } + + public void AddImageTiledButton(int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, + int param, int itemID, int hue, int width, int height) + { + Add(new GumpImageTileButton(x, y, normalID, pressedID, buttonID, type, param, itemID, hue, width, height)); + } + + public void AddImageTiledButton(int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, + int param, int itemID, int hue, int width, int height, int localizedTooltip) + { + Add(new GumpImageTileButton(x, y, normalID, pressedID, buttonID, type, param, itemID, hue, width, height, + localizedTooltip)); + } + + public void AddItem(int x, int y, int itemID) + { + Add(new GumpItem(x, y, itemID)); + } + + public void AddItem(int x, int y, int itemID, int hue) + { + Add(new GumpItem(x, y, itemID, hue)); + } + + public void AddLabel(int x, int y, int hue, string text) + { + Add(new GumpLabel(x, y, hue, text)); + } + + public void AddLabelCropped(int x, int y, int width, int height, int hue, string text) + { + Add(new GumpLabelCropped(x, y, width, height, hue, text)); + } + + public void AddRadio(int x, int y, int inactiveID, int activeID, bool initialState, int switchID) + { + Add(new GumpRadio(x, y, inactiveID, activeID, initialState, switchID)); + } + + public void AddTextEntry(int x, int y, int width, int height, int hue, int entryID, string initialText) + { + Add(new GumpTextEntry(x, y, width, height, hue, entryID, initialText)); + } + + public void AddTextEntry(int x, int y, int width, int height, int hue, int entryID, string initialText, int size) + { + Add(new GumpTextEntryLimited(x, y, width, height, hue, entryID, initialText, size)); + } + + public void AddItemProperty(int serial) + { + Add(new GumpItemProperty(serial)); + } + + public void Add(GumpEntry g) + { + if (g.Parent != this) + { + g.Parent = this; + } + else if (!Entries.Contains(g)) + { + Invalidate(); + Entries.Add(g); + } + } + + public void Remove(GumpEntry g) + { + if (g == null || !Entries.Contains(g)) + return; + + Invalidate(); + Entries.Remove(g); + g.Parent = null; + } + + public int Intern(string value) + { + int indexOf = m_Strings.IndexOf(value); + + if (indexOf >= 0) return indexOf; + + Invalidate(); + m_Strings.Add(value); + return m_Strings.Count - 1; + } + + public void SendTo(NetState state) + { + state.AddGump(this); + state.Send(Compile(state)); + } + + public static byte[] StringToBuffer(string str) + { + return Encoding.ASCII.GetBytes(str); + } + + private Packet Compile() + { + return Compile(null); + } + + private Packet Compile(NetState ns) + { + IGumpWriter disp; + + if (ns != null && ns.Unpack) + disp = new DisplayGumpPacked(this); + else + disp = new DisplayGumpFast(this); + + if (!m_Dragable) + disp.AppendLayout(m_NoMove); + + if (!m_Closable) + disp.AppendLayout(m_NoClose); + + if (!m_Disposable) + disp.AppendLayout(m_NoDispose); + + if (!m_Resizable) + disp.AppendLayout(m_NoResize); + + int count = Entries.Count; + GumpEntry e; + + for (int i = 0; i < count; ++i) + { + e = Entries[i]; + + disp.AppendLayout(m_BeginLayout); + e.AppendTo(ns, disp); + disp.AppendLayout(m_EndLayout); + } + + disp.WriteStrings(m_Strings); + + disp.Flush(); + + m_TextEntries = disp.TextEntries; + m_Switches = disp.Switches; + + return disp as Packet; + } + + public virtual void OnResponse(NetState sender, RelayInfo info) + { + } + + public virtual void OnServerClose(NetState owner) + { + } + } +} \ No newline at end of file diff --git a/Server/Gumps/GumpAlphaRegion.cs b/Server/Gumps/GumpAlphaRegion.cs index dd278dfed..048fae5a9 100644 --- a/Server/Gumps/GumpAlphaRegion.cs +++ b/Server/Gumps/GumpAlphaRegion.cs @@ -18,62 +18,60 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpAlphaRegion : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; + public class GumpAlphaRegion : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("checkertrans"); + private int m_Width, m_Height; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpAlphaRegion(int x, int y, int width, int height) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public GumpAlphaRegion( int x, int y, int width, int height ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public override string Compile( NetState ns ) - { - return $"{{ checkertrans {m_X} {m_Y} {m_Width} {m_Height} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ checkertrans {m_X} {m_Y} {m_Width} {m_Height} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "checkertrans" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpBackground.cs b/Server/Gumps/GumpBackground.cs index 5b48404dd..8b49f6b85 100644 --- a/Server/Gumps/GumpBackground.cs +++ b/Server/Gumps/GumpBackground.cs @@ -18,71 +18,69 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpBackground : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; - private int m_GumpID; + public class GumpBackground : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("resizepic"); + private int m_GumpID; + private int m_Width, m_Height; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpBackground(int x, int y, int width, int height, int gumpID) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_GumpID = gumpID; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public int GumpID - { - get => m_GumpID; - set => Delta( ref m_GumpID, value ); - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public GumpBackground( int x, int y, int width, int height, int gumpID ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_GumpID = gumpID; - } + public int GumpID + { + get => m_GumpID; + set => Delta(ref m_GumpID, value); + } - public override string Compile( NetState ns ) - { - return $"{{ resizepic {m_X} {m_Y} {m_GumpID} {m_Width} {m_Height} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ resizepic {m_X} {m_Y} {m_GumpID} {m_Width} {m_Height} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "resizepic" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_GumpID ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_GumpID); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpButton.cs b/Server/Gumps/GumpButton.cs index bacecfc83..a3a884d24 100644 --- a/Server/Gumps/GumpButton.cs +++ b/Server/Gumps/GumpButton.cs @@ -18,105 +18,103 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public enum GumpButtonType - { - Page = 0, - Reply = 1 - } + public enum GumpButtonType + { + Page = 0, + Reply = 1 + } - public class GumpButton : GumpEntry - { - private int m_X, m_Y; - private int m_ID1, m_ID2; - private int m_ButtonID; - private GumpButtonType m_Type; - private int m_Param; + public class GumpButton : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("button"); + private int m_ButtonID; + private int m_ID1, m_ID2; + private int m_Param; + private GumpButtonType m_Type; + private int m_X, m_Y; - public GumpButton( int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param ) - { - m_X = x; - m_Y = y; - m_ID1 = normalID; - m_ID2 = pressedID; - m_ButtonID = buttonID; - m_Type = type; - m_Param = param; - } + public GumpButton(int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param) + { + m_X = x; + m_Y = y; + m_ID1 = normalID; + m_ID2 = pressedID; + m_ButtonID = buttonID; + m_Type = type; + m_Param = param; + } - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int NormalID - { - get => m_ID1; - set => Delta( ref m_ID1, value ); - } + public int NormalID + { + get => m_ID1; + set => Delta(ref m_ID1, value); + } - public int PressedID - { - get => m_ID2; - set => Delta( ref m_ID2, value ); - } + public int PressedID + { + get => m_ID2; + set => Delta(ref m_ID2, value); + } - public int ButtonID - { - get => m_ButtonID; - set => Delta( ref m_ButtonID, value ); - } + public int ButtonID + { + get => m_ButtonID; + set => Delta(ref m_ButtonID, value); + } - public GumpButtonType Type - { - get => m_Type; - set - { - if ( m_Type != value ) - { - m_Type = value; + public GumpButtonType Type + { + get => m_Type; + set + { + if (m_Type != value) + { + m_Type = value; - Gump parent = Parent; + Gump parent = Parent; - parent?.Invalidate(); - } - } - } + parent?.Invalidate(); + } + } + } - public int Param - { - get => m_Param; - set => Delta( ref m_Param, value ); - } + public int Param + { + get => m_Param; + set => Delta(ref m_Param, value); + } - public override string Compile( NetState ns ) - { - return $"{{ button {m_X} {m_Y} {m_ID1} {m_ID2} {(int) m_Type} {m_Param} {m_ButtonID} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ button {m_X} {m_Y} {m_ID1} {m_ID2} {(int)m_Type} {m_Param} {m_ButtonID} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "button" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_ID1 ); - disp.AppendLayout( m_ID2 ); - disp.AppendLayout( (int)m_Type ); - disp.AppendLayout( m_Param ); - disp.AppendLayout( m_ButtonID ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_ID1); + disp.AppendLayout(m_ID2); + disp.AppendLayout((int)m_Type); + disp.AppendLayout(m_Param); + disp.AppendLayout(m_ButtonID); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpCheck.cs b/Server/Gumps/GumpCheck.cs index 788503de8..a0e638443 100644 --- a/Server/Gumps/GumpCheck.cs +++ b/Server/Gumps/GumpCheck.cs @@ -18,82 +18,80 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpCheck : GumpEntry - { - private int m_X, m_Y; - private int m_ID1, m_ID2; - private bool m_InitialState; - private int m_SwitchID; + public class GumpCheck : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("checkbox"); + private int m_ID1, m_ID2; + private bool m_InitialState; + private int m_SwitchID; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpCheck(int x, int y, int inactiveID, int activeID, bool initialState, int switchID) + { + m_X = x; + m_Y = y; + m_ID1 = inactiveID; + m_ID2 = activeID; + m_InitialState = initialState; + m_SwitchID = switchID; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int InactiveID - { - get => m_ID1; - set => Delta( ref m_ID1, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int ActiveID - { - get => m_ID2; - set => Delta( ref m_ID2, value ); - } + public int InactiveID + { + get => m_ID1; + set => Delta(ref m_ID1, value); + } - public bool InitialState - { - get => m_InitialState; - set => Delta( ref m_InitialState, value ); - } + public int ActiveID + { + get => m_ID2; + set => Delta(ref m_ID2, value); + } - public int SwitchID - { - get => m_SwitchID; - set => Delta( ref m_SwitchID, value ); - } + public bool InitialState + { + get => m_InitialState; + set => Delta(ref m_InitialState, value); + } - public GumpCheck( int x, int y, int inactiveID, int activeID, bool initialState, int switchID ) - { - m_X = x; - m_Y = y; - m_ID1 = inactiveID; - m_ID2 = activeID; - m_InitialState = initialState; - m_SwitchID = switchID; - } + public int SwitchID + { + get => m_SwitchID; + set => Delta(ref m_SwitchID, value); + } - public override string Compile( NetState ns ) - { - return $"{{ checkbox {m_X} {m_Y} {m_ID1} {m_ID2} {(m_InitialState ? 1 : 0)} {m_SwitchID} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ checkbox {m_X} {m_Y} {m_ID1} {m_ID2} {(m_InitialState ? 1 : 0)} {m_SwitchID} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "checkbox" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_ID1); + disp.AppendLayout(m_ID2); + disp.AppendLayout(m_InitialState); + disp.AppendLayout(m_SwitchID); - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_ID1 ); - disp.AppendLayout( m_ID2 ); - disp.AppendLayout( m_InitialState ); - disp.AppendLayout( m_SwitchID ); - - disp.Switches++; - } - } + disp.Switches++; + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpEntry.cs b/Server/Gumps/GumpEntry.cs index df02aa4d7..e202ad02f 100644 --- a/Server/Gumps/GumpEntry.cs +++ b/Server/Gumps/GumpEntry.cs @@ -22,63 +22,47 @@ using Server.Network; namespace Server.Gumps { - public abstract class GumpEntry - { - private Gump m_Parent; + public abstract class GumpEntry + { + private Gump m_Parent; - protected GumpEntry() - { - } + public Gump Parent + { + get => m_Parent; + set + { + if (m_Parent != value) + { + m_Parent?.Remove(this); - protected void Delta( ref int var, int val ) - { - if ( var != val ) - { - var = val; - } - } + m_Parent = value; - protected void Delta( ref bool var, bool val ) - { - if ( var != val ) - { - var = val; - } - } + m_Parent?.Add(this); + } + } + } - protected void Delta( ref string var, string val ) - { - if ( var != val ) - { - var = val; - } - } + protected void Delta(ref int var, int val) + { + if (var != val) var = val; + } - protected void Delta( ref object[] var, object[] val ) - { - if ( var != val ) - { - var = val; - } - } + protected void Delta(ref bool var, bool val) + { + if (var != val) var = val; + } - public Gump Parent - { - get => m_Parent; - set - { - if ( m_Parent != value ) - { - m_Parent?.Remove( this ); + protected void Delta(ref string var, string val) + { + if (var != val) var = val; + } - m_Parent = value; + protected void Delta(ref object[] var, object[] val) + { + if (var != val) var = val; + } - m_Parent?.Add( this ); - } - } - } - - public abstract string Compile( NetState ns ); - public abstract void AppendTo( NetState ns, IGumpWriter disp ); - } + public abstract string Compile(NetState ns); + public abstract void AppendTo(NetState ns, IGumpWriter disp); + } } \ No newline at end of file diff --git a/Server/Gumps/GumpGroup.cs b/Server/Gumps/GumpGroup.cs index 403ca6995..901e30a09 100644 --- a/Server/Gumps/GumpGroup.cs +++ b/Server/Gumps/GumpGroup.cs @@ -18,37 +18,35 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpGroup : GumpEntry - { - private int m_Group; + public class GumpGroup : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("group"); + private int m_Group; - public GumpGroup( int group ) - { - m_Group = group; - } + public GumpGroup(int group) + { + m_Group = group; + } - public int Group - { - get => m_Group; - set => Delta( ref m_Group, value ); - } + public int Group + { + get => m_Group; + set => Delta(ref m_Group, value); + } - public override string Compile( NetState ns ) - { - return $"{{ group {m_Group} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ group {m_Group} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "group" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_Group ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_Group); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpHtml.cs b/Server/Gumps/GumpHtml.cs index 5fe60d459..9b4d5fab3 100644 --- a/Server/Gumps/GumpHtml.cs +++ b/Server/Gumps/GumpHtml.cs @@ -18,89 +18,87 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpHtml : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; - private string m_Text; - private bool m_Background, m_Scrollbar; + public class GumpHtml : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("htmlgump"); + private bool m_Background, m_Scrollbar; + private string m_Text; + private int m_Width, m_Height; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpHtml(int x, int y, int width, int height, string text, bool background, bool scrollbar) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Text = text; + m_Background = background; + m_Scrollbar = scrollbar; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public string Text - { - get => m_Text; - set => Delta( ref m_Text, value ); - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public bool Background - { - get => m_Background; - set => Delta( ref m_Background, value ); - } + public string Text + { + get => m_Text; + set => Delta(ref m_Text, value); + } - public bool Scrollbar - { - get => m_Scrollbar; - set => Delta( ref m_Scrollbar, value ); - } + public bool Background + { + get => m_Background; + set => Delta(ref m_Background, value); + } - public GumpHtml( int x, int y, int width, int height, string text, bool background, bool scrollbar ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Text = text; - m_Background = background; - m_Scrollbar = scrollbar; - } + public bool Scrollbar + { + get => m_Scrollbar; + set => Delta(ref m_Scrollbar, value); + } - public override string Compile( NetState ns ) - { - return - $"{{ htmlgump {m_X} {m_Y} {m_Width} {m_Height} {Parent.Intern(m_Text)} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} }}"; - } + public override string Compile(NetState ns) + { + return + $"{{ htmlgump {m_X} {m_Y} {m_Width} {m_Height} {Parent.Intern(m_Text)} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "htmlgump" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( Parent.Intern( m_Text ) ); - disp.AppendLayout( m_Background ); - disp.AppendLayout( m_Scrollbar ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(Parent.Intern(m_Text)); + disp.AppendLayout(m_Background); + disp.AppendLayout(m_Scrollbar); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpHtmlLocalized.cs b/Server/Gumps/GumpHtmlLocalized.cs index 22c8a1e75..928878bae 100644 --- a/Server/Gumps/GumpHtmlLocalized.cs +++ b/Server/Gumps/GumpHtmlLocalized.cs @@ -18,215 +18,214 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public enum GumpHtmlLocalizedType - { - Plain, - Color, - Args - } + public enum GumpHtmlLocalizedType + { + Plain, + Color, + Args + } - public class GumpHtmlLocalized : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; - private int m_Number; - private string m_Args; - private int m_Color; - private bool m_Background, m_Scrollbar; + public class GumpHtmlLocalized : GumpEntry + { + private static byte[] m_LayoutNamePlain = Gump.StringToBuffer("xmfhtmlgump"); + private static byte[] m_LayoutNameColor = Gump.StringToBuffer("xmfhtmlgumpcolor"); + private static byte[] m_LayoutNameArgs = Gump.StringToBuffer("xmfhtmltok"); + private string m_Args; + private bool m_Background, m_Scrollbar; + private int m_Color; + private int m_Number; - private GumpHtmlLocalizedType m_Type; + private GumpHtmlLocalizedType m_Type; + private int m_Width, m_Height; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpHtmlLocalized(int x, int y, int width, int height, int number, bool background, bool scrollbar) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Number = number; + m_Background = background; + m_Scrollbar = scrollbar; - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + m_Type = GumpHtmlLocalizedType.Plain; + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public GumpHtmlLocalized(int x, int y, int width, int height, int number, int color, bool background, bool scrollbar) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Number = number; + m_Color = color; + m_Background = background; + m_Scrollbar = scrollbar; - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + m_Type = GumpHtmlLocalizedType.Color; + } - public int Number - { - get => m_Number; - set => Delta( ref m_Number, value ); - } + public GumpHtmlLocalized(int x, int y, int width, int height, int number, string args, int color, bool background, + bool scrollbar) + { + // Are multiple arguments unsupported? And what about non ASCII arguments? - public string Args - { - get => m_Args; - set => Delta( ref m_Args, value ); - } + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Number = number; + m_Args = args; + m_Color = color; + m_Background = background; + m_Scrollbar = scrollbar; - public int Color - { - get => m_Color; - set => Delta( ref m_Color, value ); - } + m_Type = GumpHtmlLocalizedType.Args; + } - public bool Background - { - get => m_Background; - set => Delta( ref m_Background, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public bool Scrollbar - { - get => m_Scrollbar; - set => Delta( ref m_Scrollbar, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public GumpHtmlLocalizedType Type - { - get => m_Type; - set - { - if ( m_Type != value ) - { - m_Type = value; + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - Parent?.Invalidate(); - } - } - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public GumpHtmlLocalized( int x, int y, int width, int height, int number, bool background, bool scrollbar ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Number = number; - m_Background = background; - m_Scrollbar = scrollbar; + public int Number + { + get => m_Number; + set => Delta(ref m_Number, value); + } - m_Type = GumpHtmlLocalizedType.Plain; - } + public string Args + { + get => m_Args; + set => Delta(ref m_Args, value); + } - public GumpHtmlLocalized( int x, int y, int width, int height, int number, int color, bool background, bool scrollbar ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Number = number; - m_Color = color; - m_Background = background; - m_Scrollbar = scrollbar; + public int Color + { + get => m_Color; + set => Delta(ref m_Color, value); + } - m_Type = GumpHtmlLocalizedType.Color; - } + public bool Background + { + get => m_Background; + set => Delta(ref m_Background, value); + } - public GumpHtmlLocalized( int x, int y, int width, int height, int number, string args, int color, bool background, bool scrollbar ) - { - // Are multiple arguments unsupported? And what about non ASCII arguments? + public bool Scrollbar + { + get => m_Scrollbar; + set => Delta(ref m_Scrollbar, value); + } - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Number = number; - m_Args = args; - m_Color = color; - m_Background = background; - m_Scrollbar = scrollbar; + public GumpHtmlLocalizedType Type + { + get => m_Type; + set + { + if (m_Type != value) + { + m_Type = value; - m_Type = GumpHtmlLocalizedType.Args; - } + Parent?.Invalidate(); + } + } + } - public override string Compile( NetState ns ) - { - switch ( m_Type ) - { - case GumpHtmlLocalizedType.Plain: - return - $"{{ xmfhtmlgump {m_X} {m_Y} {m_Width} {m_Height} {m_Number} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} }}"; + public override string Compile(NetState ns) + { + switch (m_Type) + { + case GumpHtmlLocalizedType.Plain: + return + $"{{ xmfhtmlgump {m_X} {m_Y} {m_Width} {m_Height} {m_Number} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} }}"; - case GumpHtmlLocalizedType.Color: - return - $"{{ xmfhtmlgumpcolor {m_X} {m_Y} {m_Width} {m_Height} {m_Number} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} {m_Color} }}"; + case GumpHtmlLocalizedType.Color: + return + $"{{ xmfhtmlgumpcolor {m_X} {m_Y} {m_Width} {m_Height} {m_Number} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} {m_Color} }}"; - default: // GumpHtmlLocalizedType.Args - return - $"{{ xmfhtmltok {m_X} {m_Y} {m_Width} {m_Height} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} {m_Color} {m_Number} @{m_Args}@ }}"; - } - } + default: // GumpHtmlLocalizedType.Args + return + $"{{ xmfhtmltok {m_X} {m_Y} {m_Width} {m_Height} {(m_Background ? 1 : 0)} {(m_Scrollbar ? 1 : 0)} {m_Color} {m_Number} @{m_Args}@ }}"; + } + } - private static byte[] m_LayoutNamePlain = Gump.StringToBuffer( "xmfhtmlgump" ); - private static byte[] m_LayoutNameColor = Gump.StringToBuffer( "xmfhtmlgumpcolor" ); - private static byte[] m_LayoutNameArgs = Gump.StringToBuffer( "xmfhtmltok" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + switch (m_Type) + { + case GumpHtmlLocalizedType.Plain: + { + disp.AppendLayout(m_LayoutNamePlain); - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - switch ( m_Type ) - { - case GumpHtmlLocalizedType.Plain: - { - disp.AppendLayout( m_LayoutNamePlain ); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_Number); + disp.AppendLayout(m_Background); + disp.AppendLayout(m_Scrollbar); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_Number ); - disp.AppendLayout( m_Background ); - disp.AppendLayout( m_Scrollbar ); + break; + } - break; - } + case GumpHtmlLocalizedType.Color: + { + disp.AppendLayout(m_LayoutNameColor); - case GumpHtmlLocalizedType.Color: - { - disp.AppendLayout( m_LayoutNameColor ); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_Number); + disp.AppendLayout(m_Background); + disp.AppendLayout(m_Scrollbar); + disp.AppendLayout(m_Color); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_Number ); - disp.AppendLayout( m_Background ); - disp.AppendLayout( m_Scrollbar ); - disp.AppendLayout( m_Color ); + break; + } - break; - } + case GumpHtmlLocalizedType.Args: + { + disp.AppendLayout(m_LayoutNameArgs); - case GumpHtmlLocalizedType.Args: - { - disp.AppendLayout( m_LayoutNameArgs ); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_Background); + disp.AppendLayout(m_Scrollbar); + disp.AppendLayout(m_Color); + disp.AppendLayout(m_Number); + disp.AppendLayout(m_Args); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_Background ); - disp.AppendLayout( m_Scrollbar ); - disp.AppendLayout( m_Color ); - disp.AppendLayout( m_Number ); - disp.AppendLayout( m_Args ); - - break; - } - } - } - } + break; + } + } + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpImage.cs b/Server/Gumps/GumpImage.cs index b6bccf711..3b64e634b 100644 --- a/Server/Gumps/GumpImage.cs +++ b/Server/Gumps/GumpImage.cs @@ -18,75 +18,73 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpImage : GumpEntry - { - private int m_X, m_Y; - private int m_GumpID; - private int m_Hue; + public class GumpImage : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("gumppic"); + private static byte[] m_HueEquals = Gump.StringToBuffer(" hue="); + private int m_GumpID; + private int m_Hue; + private int m_X, m_Y; - public GumpImage( int x, int y, int gumpID ) : this( x, y, gumpID, 0 ) - { - } + public GumpImage(int x, int y, int gumpID) : this(x, y, gumpID, 0) + { + } - public GumpImage( int x, int y, int gumpID, int hue ) - { - m_X = x; - m_Y = y; - m_GumpID = gumpID; - m_Hue = hue; - } + public GumpImage(int x, int y, int gumpID, int hue) + { + m_X = x; + m_Y = y; + m_GumpID = gumpID; + m_Hue = hue; + } - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int GumpID - { - get => m_GumpID; - set => Delta( ref m_GumpID, value ); - } + public int GumpID + { + get => m_GumpID; + set => Delta(ref m_GumpID, value); + } - public int Hue - { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public override string Compile( NetState ns ) - { - if ( m_Hue == 0 ) - return $"{{ gumppic {m_X} {m_Y} {m_GumpID} }}"; - return $"{{ gumppic {m_X} {m_Y} {m_GumpID} hue={m_Hue} }}"; - } + public override string Compile(NetState ns) + { + if (m_Hue == 0) + return $"{{ gumppic {m_X} {m_Y} {m_GumpID} }}"; + return $"{{ gumppic {m_X} {m_Y} {m_GumpID} hue={m_Hue} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "gumppic" ); - private static byte[] m_HueEquals = Gump.StringToBuffer( " hue=" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_GumpID); - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_GumpID ); - - if ( m_Hue != 0 ) - { - disp.AppendLayout( m_HueEquals ); - disp.AppendLayoutNS( m_Hue ); - } - } - } + if (m_Hue != 0) + { + disp.AppendLayout(m_HueEquals); + disp.AppendLayoutNS(m_Hue); + } + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpImageTileButton.cs b/Server/Gumps/GumpImageTileButton.cs index f8e7e6c17..481731b04 100644 --- a/Server/Gumps/GumpImageTileButton.cs +++ b/Server/Gumps/GumpImageTileButton.cs @@ -18,157 +18,161 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpImageTileButton : GumpEntry - { - //Note, on OSI, The tooltip supports ONLY clilocs as far as I can figure out, and the tooltip ONLY works after the buttonTileArt (as far as I can tell from testing) - private int m_X, m_Y; - private int m_ID1, m_ID2; - private int m_ButtonID; - private GumpButtonType m_Type; - private int m_Param; + public class GumpImageTileButton : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("buttontileart"); + private static byte[] m_LayoutTooltip = Gump.StringToBuffer(" }{ tooltip"); + private int m_ButtonID; + private int m_Height; + private int m_Hue; + private int m_ID1, m_ID2; - private int m_ItemID; - private int m_Hue; - private int m_Width; - private int m_Height; + private int m_ItemID; + private int m_Param; + private GumpButtonType m_Type; - public GumpImageTileButton( int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param, int itemID, int hue, int width, int height ) : this(x, y, normalID, pressedID, buttonID, type, param, itemID, hue, width, height, -1 ) - { - } - public GumpImageTileButton( int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param, int itemID, int hue, int width, int height, int localizedTooltip ) - { - m_X = x; - m_Y = y; - m_ID1 = normalID; - m_ID2 = pressedID; - m_ButtonID = buttonID; - m_Type = type; - m_Param = param; + private int m_Width; - m_ItemID = itemID; - m_Hue = hue; - m_Width = width; - m_Height = height; + //Note, on OSI, The tooltip supports ONLY clilocs as far as I can figure out, and the tooltip ONLY works after the buttonTileArt (as far as I can tell from testing) + private int m_X, m_Y; - LocalizedTooltip = localizedTooltip; - } + public GumpImageTileButton(int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param, + int itemID, int hue, int width, int height) : this(x, y, normalID, pressedID, buttonID, type, param, itemID, hue, + width, height, -1) + { + } - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpImageTileButton(int x, int y, int normalID, int pressedID, int buttonID, GumpButtonType type, int param, + int itemID, int hue, int width, int height, int localizedTooltip) + { + m_X = x; + m_Y = y; + m_ID1 = normalID; + m_ID2 = pressedID; + m_ButtonID = buttonID; + m_Type = type; + m_Param = param; - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + m_ItemID = itemID; + m_Hue = hue; + m_Width = width; + m_Height = height; - public int NormalID - { - get => m_ID1; - set => Delta( ref m_ID1, value ); - } + LocalizedTooltip = localizedTooltip; + } - public int PressedID - { - get => m_ID2; - set => Delta( ref m_ID2, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int ButtonID - { - get => m_ButtonID; - set => Delta( ref m_ButtonID, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public GumpButtonType Type - { - get => m_Type; - set - { - if ( m_Type != value ) - { - m_Type = value; + public int NormalID + { + get => m_ID1; + set => Delta(ref m_ID1, value); + } - Gump parent = Parent; + public int PressedID + { + get => m_ID2; + set => Delta(ref m_ID2, value); + } - parent?.Invalidate(); - } - } - } + public int ButtonID + { + get => m_ButtonID; + set => Delta(ref m_ButtonID, value); + } - public int Param - { - get => m_Param; - set => Delta( ref m_Param, value ); - } + public GumpButtonType Type + { + get => m_Type; + set + { + if (m_Type != value) + { + m_Type = value; - public int ItemID - { - get => m_ItemID; - set => Delta( ref m_ItemID, value ); - } + Gump parent = Parent; - public int Hue - { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + parent?.Invalidate(); + } + } + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Param + { + get => m_Param; + set => Delta(ref m_Param, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int ItemID + { + get => m_ItemID; + set => Delta(ref m_ItemID, value); + } - public int LocalizedTooltip { get; set; } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public override string Compile( NetState ns ) - { - if ( LocalizedTooltip > 0 ) - return - $"{{ buttontileart {m_X} {m_Y} {m_ID1} {m_ID2} {(int) m_Type} {m_Param} {m_ButtonID} {m_ItemID} {m_Hue} {m_Width} {m_Height} }}{{ tooltip {LocalizedTooltip} }}"; - return - $"{{ buttontileart {m_X} {m_Y} {m_ID1} {m_ID2} {(int) m_Type} {m_Param} {m_ButtonID} {m_ItemID} {m_Hue} {m_Width} {m_Height} }}"; - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "buttontileart" ); - private static byte[] m_LayoutTooltip = Gump.StringToBuffer( " }{ tooltip" ); + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_ID1 ); - disp.AppendLayout( m_ID2 ); - disp.AppendLayout( (int)m_Type ); - disp.AppendLayout( m_Param ); - disp.AppendLayout( m_ButtonID ); + public int LocalizedTooltip{ get; set; } - disp.AppendLayout( m_ItemID ); - disp.AppendLayout( m_Hue ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); + public override string Compile(NetState ns) + { + if (LocalizedTooltip > 0) + return + $"{{ buttontileart {m_X} {m_Y} {m_ID1} {m_ID2} {(int)m_Type} {m_Param} {m_ButtonID} {m_ItemID} {m_Hue} {m_Width} {m_Height} }}{{ tooltip {LocalizedTooltip} }}"; + return + $"{{ buttontileart {m_X} {m_Y} {m_ID1} {m_ID2} {(int)m_Type} {m_Param} {m_ButtonID} {m_ItemID} {m_Hue} {m_Width} {m_Height} }}"; + } - if ( LocalizedTooltip > 0 ) - { - disp.AppendLayout( m_LayoutTooltip ); - disp.AppendLayout( LocalizedTooltip ); - } - } - } -} + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_ID1); + disp.AppendLayout(m_ID2); + disp.AppendLayout((int)m_Type); + disp.AppendLayout(m_Param); + disp.AppendLayout(m_ButtonID); + + disp.AppendLayout(m_ItemID); + disp.AppendLayout(m_Hue); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + + if (LocalizedTooltip > 0) + { + disp.AppendLayout(m_LayoutTooltip); + disp.AppendLayout(LocalizedTooltip); + } + } + } +} \ No newline at end of file diff --git a/Server/Gumps/GumpImageTiled.cs b/Server/Gumps/GumpImageTiled.cs index 7a19ec2bc..1ad2a07a6 100644 --- a/Server/Gumps/GumpImageTiled.cs +++ b/Server/Gumps/GumpImageTiled.cs @@ -18,71 +18,69 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpImageTiled : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; - private int m_GumpID; + public class GumpImageTiled : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("gumppictiled"); + private int m_GumpID; + private int m_Width, m_Height; + private int m_X, m_Y; - public GumpImageTiled( int x, int y, int width, int height, int gumpID ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_GumpID = gumpID; - } + public GumpImageTiled(int x, int y, int width, int height, int gumpID) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_GumpID = gumpID; + } - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public int GumpID - { - get => m_GumpID; - set => Delta( ref m_GumpID, value ); - } + public int GumpID + { + get => m_GumpID; + set => Delta(ref m_GumpID, value); + } - public override string Compile( NetState ns ) - { - return $"{{ gumppictiled {m_X} {m_Y} {m_Width} {m_Height} {m_GumpID} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ gumppictiled {m_X} {m_Y} {m_Width} {m_Height} {m_GumpID} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "gumppictiled" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_GumpID ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_GumpID); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpItem.cs b/Server/Gumps/GumpItem.cs index 064161b46..f365df2be 100644 --- a/Server/Gumps/GumpItem.cs +++ b/Server/Gumps/GumpItem.cs @@ -18,72 +18,70 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpItem : GumpEntry - { - private int m_X, m_Y; - private int m_ItemID; - private int m_Hue; + public class GumpItem : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("tilepic"); + private static byte[] m_LayoutNameHue = Gump.StringToBuffer("tilepichue"); + private int m_Hue; + private int m_ItemID; + private int m_X, m_Y; - public GumpItem( int x, int y, int itemID ) : this( x, y, itemID, 0 ) - { - } + public GumpItem(int x, int y, int itemID) : this(x, y, itemID, 0) + { + } - public GumpItem( int x, int y, int itemID, int hue ) - { - m_X = x; - m_Y = y; - m_ItemID = itemID; - m_Hue = hue; - } + public GumpItem(int x, int y, int itemID, int hue) + { + m_X = x; + m_Y = y; + m_ItemID = itemID; + m_Hue = hue; + } - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int ItemID - { - get => m_ItemID; - set => Delta( ref m_ItemID, value ); - } + public int ItemID + { + get => m_ItemID; + set => Delta(ref m_ItemID, value); + } - public int Hue - { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public override string Compile( NetState ns ) - { - if ( m_Hue == 0 ) - return $"{{ tilepic {m_X} {m_Y} {m_ItemID} }}"; - return $"{{ tilepichue {m_X} {m_Y} {m_ItemID} {m_Hue} }}"; - } + public override string Compile(NetState ns) + { + if (m_Hue == 0) + return $"{{ tilepic {m_X} {m_Y} {m_ItemID} }}"; + return $"{{ tilepichue {m_X} {m_Y} {m_ItemID} {m_Hue} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "tilepic" ); - private static byte[] m_LayoutNameHue = Gump.StringToBuffer( "tilepichue" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_Hue == 0 ? m_LayoutName : m_LayoutNameHue); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_ItemID); - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_Hue == 0 ? m_LayoutName : m_LayoutNameHue ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_ItemID ); - - if ( m_Hue != 0 ) - disp.AppendLayout( m_Hue ); - } - } + if (m_Hue != 0) + disp.AppendLayout(m_Hue); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpItemProperty.cs b/Server/Gumps/GumpItemProperty.cs index 5bc099aeb..30338a196 100644 --- a/Server/Gumps/GumpItemProperty.cs +++ b/Server/Gumps/GumpItemProperty.cs @@ -18,37 +18,35 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpItemProperty : GumpEntry - { - private int m_Serial; + public class GumpItemProperty : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("itemproperty"); + private int m_Serial; - public GumpItemProperty( int serial ) - { - m_Serial = serial; - } + public GumpItemProperty(int serial) + { + m_Serial = serial; + } - public int Serial - { - get => m_Serial; - set => Delta( ref m_Serial, value ); - } + public int Serial + { + get => m_Serial; + set => Delta(ref m_Serial, value); + } - public override string Compile( NetState ns ) - { - return $"{{ itemproperty {m_Serial} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ itemproperty {m_Serial} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "itemproperty" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_Serial ); - } - } -} + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_Serial); + } + } +} \ No newline at end of file diff --git a/Server/Gumps/GumpLabel.cs b/Server/Gumps/GumpLabel.cs index 56d531c9c..c92ac700c 100644 --- a/Server/Gumps/GumpLabel.cs +++ b/Server/Gumps/GumpLabel.cs @@ -18,63 +18,61 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpLabel : GumpEntry - { - private int m_X, m_Y; - private int m_Hue; - private string m_Text; + public class GumpLabel : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("text"); + private int m_Hue; + private string m_Text; + private int m_X, m_Y; - public GumpLabel( int x, int y, int hue, string text ) - { - m_X = x; - m_Y = y; - m_Hue = hue; - m_Text = text; - } + public GumpLabel(int x, int y, int hue, string text) + { + m_X = x; + m_Y = y; + m_Hue = hue; + m_Text = text; + } - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Hue - { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public string Text - { - get => m_Text; - set => Delta( ref m_Text, value ); - } + public string Text + { + get => m_Text; + set => Delta(ref m_Text, value); + } - public override string Compile( NetState ns ) - { - return $"{{ text {m_X} {m_Y} {m_Hue} {Parent.Intern(m_Text)} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ text {m_X} {m_Y} {m_Hue} {Parent.Intern(m_Text)} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "text" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Hue ); - disp.AppendLayout( Parent.Intern( m_Text ) ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Hue); + disp.AppendLayout(Parent.Intern(m_Text)); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpLabelCropped.cs b/Server/Gumps/GumpLabelCropped.cs index a86573754..d8aec978f 100644 --- a/Server/Gumps/GumpLabelCropped.cs +++ b/Server/Gumps/GumpLabelCropped.cs @@ -18,80 +18,78 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpLabelCropped : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; - private int m_Hue; - private string m_Text; + public class GumpLabelCropped : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("croppedtext"); + private int m_Hue; + private string m_Text; + private int m_Width, m_Height; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpLabelCropped(int x, int y, int width, int height, int hue, string text) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Hue = hue; + m_Text = text; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public int Hue - { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public string Text - { - get => m_Text; - set => Delta( ref m_Text, value ); - } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public GumpLabelCropped( int x, int y, int width, int height, int hue, string text ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Hue = hue; - m_Text = text; - } + public string Text + { + get => m_Text; + set => Delta(ref m_Text, value); + } - public override string Compile( NetState ns ) - { - return $"{{ croppedtext {m_X} {m_Y} {m_Width} {m_Height} {m_Hue} {Parent.Intern(m_Text)} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ croppedtext {m_X} {m_Y} {m_Width} {m_Height} {m_Hue} {Parent.Intern(m_Text)} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "croppedtext" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_Hue ); - disp.AppendLayout( Parent.Intern( m_Text ) ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_Hue); + disp.AppendLayout(Parent.Intern(m_Text)); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpPage.cs b/Server/Gumps/GumpPage.cs index ff73eb8e1..1fb7bde92 100644 --- a/Server/Gumps/GumpPage.cs +++ b/Server/Gumps/GumpPage.cs @@ -18,37 +18,35 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpPage : GumpEntry - { - private int m_Page; + public class GumpPage : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("page"); + private int m_Page; - public GumpPage( int page ) - { - m_Page = page; - } + public GumpPage(int page) + { + m_Page = page; + } - public int Page - { - get => m_Page; - set => Delta( ref m_Page, value ); - } + public int Page + { + get => m_Page; + set => Delta(ref m_Page, value); + } - public override string Compile( NetState ns ) - { - return $"{{ page {m_Page} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ page {m_Page} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "page" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_Page ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_Page); + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpRadio.cs b/Server/Gumps/GumpRadio.cs index c921ea7b6..5b27e74ef 100644 --- a/Server/Gumps/GumpRadio.cs +++ b/Server/Gumps/GumpRadio.cs @@ -18,82 +18,80 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpRadio : GumpEntry - { - private int m_X, m_Y; - private int m_ID1, m_ID2; - private bool m_InitialState; - private int m_SwitchID; + public class GumpRadio : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("radio"); + private int m_ID1, m_ID2; + private bool m_InitialState; + private int m_SwitchID; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpRadio(int x, int y, int inactiveID, int activeID, bool initialState, int switchID) + { + m_X = x; + m_Y = y; + m_ID1 = inactiveID; + m_ID2 = activeID; + m_InitialState = initialState; + m_SwitchID = switchID; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int InactiveID - { - get => m_ID1; - set => Delta( ref m_ID1, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int ActiveID - { - get => m_ID2; - set => Delta( ref m_ID2, value ); - } + public int InactiveID + { + get => m_ID1; + set => Delta(ref m_ID1, value); + } - public bool InitialState - { - get => m_InitialState; - set => Delta( ref m_InitialState, value ); - } + public int ActiveID + { + get => m_ID2; + set => Delta(ref m_ID2, value); + } - public int SwitchID - { - get => m_SwitchID; - set => Delta( ref m_SwitchID, value ); - } + public bool InitialState + { + get => m_InitialState; + set => Delta(ref m_InitialState, value); + } - public GumpRadio( int x, int y, int inactiveID, int activeID, bool initialState, int switchID ) - { - m_X = x; - m_Y = y; - m_ID1 = inactiveID; - m_ID2 = activeID; - m_InitialState = initialState; - m_SwitchID = switchID; - } + public int SwitchID + { + get => m_SwitchID; + set => Delta(ref m_SwitchID, value); + } - public override string Compile( NetState ns ) - { - return $"{{ radio {m_X} {m_Y} {m_ID1} {m_ID2} {(m_InitialState ? 1 : 0)} {m_SwitchID} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ radio {m_X} {m_Y} {m_ID1} {m_ID2} {(m_InitialState ? 1 : 0)} {m_SwitchID} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "radio" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_ID1); + disp.AppendLayout(m_ID2); + disp.AppendLayout(m_InitialState); + disp.AppendLayout(m_SwitchID); - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_ID1 ); - disp.AppendLayout( m_ID2 ); - disp.AppendLayout( m_InitialState ); - disp.AppendLayout( m_SwitchID ); - - disp.Switches++; - } - } + disp.Switches++; + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpTextEntry.cs b/Server/Gumps/GumpTextEntry.cs index 854d65321..b91cb1b5b 100644 --- a/Server/Gumps/GumpTextEntry.cs +++ b/Server/Gumps/GumpTextEntry.cs @@ -18,92 +18,90 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpTextEntry : GumpEntry - { - private int m_X, m_Y; - private int m_Width, m_Height; - private int m_Hue; - private int m_EntryID; - private string m_InitialText; + public class GumpTextEntry : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("textentry"); + private int m_EntryID; + private int m_Hue; + private string m_InitialText; + private int m_Width, m_Height; + private int m_X, m_Y; - public int X - { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpTextEntry(int x, int y, int width, int height, int hue, int entryID, string initialText) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Hue = hue; + m_EntryID = entryID; + m_InitialText = initialText; + } - public int Y - { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Width - { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Height - { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public int Hue - { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public int EntryID - { - get => m_EntryID; - set => Delta( ref m_EntryID, value ); - } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public string InitialText - { - get => m_InitialText; - set => Delta( ref m_InitialText, value ); - } + public int EntryID + { + get => m_EntryID; + set => Delta(ref m_EntryID, value); + } - public GumpTextEntry( int x, int y, int width, int height, int hue, int entryID, string initialText ) - { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Hue = hue; - m_EntryID = entryID; - m_InitialText = initialText; - } + public string InitialText + { + get => m_InitialText; + set => Delta(ref m_InitialText, value); + } - public override string Compile( NetState ns ) - { - return - $"{{ textentry {m_X} {m_Y} {m_Width} {m_Height} {m_Hue} {m_EntryID} {Parent.Intern(m_InitialText)} }}"; - } + public override string Compile(NetState ns) + { + return + $"{{ textentry {m_X} {m_Y} {m_Width} {m_Height} {m_Hue} {m_EntryID} {Parent.Intern(m_InitialText)} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "textentry" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_Hue); + disp.AppendLayout(m_EntryID); + disp.AppendLayout(Parent.Intern(m_InitialText)); - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_Hue ); - disp.AppendLayout( m_EntryID ); - disp.AppendLayout( Parent.Intern( m_InitialText ) ); - - disp.TextEntries++; - } - } + disp.TextEntries++; + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpTextEntryLimited.cs b/Server/Gumps/GumpTextEntryLimited.cs index 052d8540c..502dcf616 100644 --- a/Server/Gumps/GumpTextEntryLimited.cs +++ b/Server/Gumps/GumpTextEntryLimited.cs @@ -18,88 +18,99 @@ * ***************************************************************************/ -using System; using Server.Network; -namespace Server.Gumps { - public class GumpTextEntryLimited : GumpEntry { - private int m_X, m_Y; - private int m_Width, m_Height; - private int m_Hue; - private int m_EntryID; - private string m_InitialText; - private int m_Size; +namespace Server.Gumps +{ + public class GumpTextEntryLimited : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("textentrylimited"); + private int m_EntryID; + private int m_Hue; + private string m_InitialText; + private int m_Size; + private int m_Width, m_Height; + private int m_X, m_Y; - public int X { - get => m_X; - set => Delta( ref m_X, value ); - } + public GumpTextEntryLimited(int x, int y, int width, int height, int hue, int entryID, string initialText, int size) + { + m_X = x; + m_Y = y; + m_Width = width; + m_Height = height; + m_Hue = hue; + m_EntryID = entryID; + m_InitialText = initialText; + m_Size = size; + } - public int Y { - get => m_Y; - set => Delta( ref m_Y, value ); - } + public int X + { + get => m_X; + set => Delta(ref m_X, value); + } - public int Width { - get => m_Width; - set => Delta( ref m_Width, value ); - } + public int Y + { + get => m_Y; + set => Delta(ref m_Y, value); + } - public int Height { - get => m_Height; - set => Delta( ref m_Height, value ); - } + public int Width + { + get => m_Width; + set => Delta(ref m_Width, value); + } - public int Hue { - get => m_Hue; - set => Delta( ref m_Hue, value ); - } + public int Height + { + get => m_Height; + set => Delta(ref m_Height, value); + } - public int EntryID { - get => m_EntryID; - set => Delta( ref m_EntryID, value ); - } + public int Hue + { + get => m_Hue; + set => Delta(ref m_Hue, value); + } - public string InitialText { - get => m_InitialText; - set => Delta( ref m_InitialText, value ); - } + public int EntryID + { + get => m_EntryID; + set => Delta(ref m_EntryID, value); + } - public int Size { - get => m_Size; - set => Delta( ref m_Size, value ); - } + public string InitialText + { + get => m_InitialText; + set => Delta(ref m_InitialText, value); + } - public GumpTextEntryLimited( int x, int y, int width, int height, int hue, int entryID, string initialText, int size ) { - m_X = x; - m_Y = y; - m_Width = width; - m_Height = height; - m_Hue = hue; - m_EntryID = entryID; - m_InitialText = initialText; - m_Size = size; - } + public int Size + { + get => m_Size; + set => Delta(ref m_Size, value); + } - public override string Compile( NetState ns ) { - return - $"{{ textentrylimited {m_X} {m_Y} {m_Width} {m_Height} {m_Hue} {m_EntryID} {Parent.Intern(m_InitialText)} {m_Size} }}"; - } + public override string Compile(NetState ns) + { + return + $"{{ textentrylimited {m_X} {m_Y} {m_Width} {m_Height} {m_Hue} {m_EntryID} {Parent.Intern(m_InitialText)} {m_Size} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "textentrylimited" ); + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_X); + disp.AppendLayout(m_Y); + disp.AppendLayout(m_Width); + disp.AppendLayout(m_Height); + disp.AppendLayout(m_Hue); + disp.AppendLayout(m_EntryID); + disp.AppendLayout(Parent.Intern(m_InitialText)); + disp.AppendLayout(m_Size); - public override void AppendTo( NetState ns, IGumpWriter disp ) { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_X ); - disp.AppendLayout( m_Y ); - disp.AppendLayout( m_Width ); - disp.AppendLayout( m_Height ); - disp.AppendLayout( m_Hue ); - disp.AppendLayout( m_EntryID ); - disp.AppendLayout( Parent.Intern( m_InitialText ) ); - disp.AppendLayout( m_Size ); - - disp.TextEntries++; - } - } + disp.TextEntries++; + } + } } \ No newline at end of file diff --git a/Server/Gumps/GumpTooltip.cs b/Server/Gumps/GumpTooltip.cs index 930ef205b..3e7ebcbc7 100644 --- a/Server/Gumps/GumpTooltip.cs +++ b/Server/Gumps/GumpTooltip.cs @@ -18,37 +18,35 @@ * ***************************************************************************/ -using System; using Server.Network; namespace Server.Gumps { - public class GumpTooltip : GumpEntry - { - private int m_Number; + public class GumpTooltip : GumpEntry + { + private static byte[] m_LayoutName = Gump.StringToBuffer("tooltip"); + private int m_Number; - public GumpTooltip( int number ) - { - m_Number = number; - } + public GumpTooltip(int number) + { + m_Number = number; + } - public int Number - { - get => m_Number; - set => Delta( ref m_Number, value ); - } + public int Number + { + get => m_Number; + set => Delta(ref m_Number, value); + } - public override string Compile( NetState ns ) - { - return $"{{ tooltip {m_Number} }}"; - } + public override string Compile(NetState ns) + { + return $"{{ tooltip {m_Number} }}"; + } - private static byte[] m_LayoutName = Gump.StringToBuffer( "tooltip" ); - - public override void AppendTo( NetState ns, IGumpWriter disp ) - { - disp.AppendLayout( m_LayoutName ); - disp.AppendLayout( m_Number ); - } - } + public override void AppendTo(NetState ns, IGumpWriter disp) + { + disp.AppendLayout(m_LayoutName); + disp.AppendLayout(m_Number); + } + } } \ No newline at end of file diff --git a/Server/Gumps/RelayInfo.cs b/Server/Gumps/RelayInfo.cs index 21d3bd39b..c8e52eb9b 100644 --- a/Server/Gumps/RelayInfo.cs +++ b/Server/Gumps/RelayInfo.cs @@ -20,58 +20,50 @@ namespace Server.Gumps { - public class TextRelay - { - public TextRelay( int entryID, string text ) - { - EntryID = entryID; - Text = text; - } + public class TextRelay + { + public TextRelay(int entryID, string text) + { + EntryID = entryID; + Text = text; + } - public int EntryID { get; } + public int EntryID{ get; } - public string Text { get; } - } + public string Text{ get; } + } - public class RelayInfo - { - public RelayInfo( int buttonID, int[] switches, TextRelay[] textEntries ) - { - ButtonID = buttonID; - Switches = switches; - TextEntries = textEntries; - } + public class RelayInfo + { + public RelayInfo(int buttonID, int[] switches, TextRelay[] textEntries) + { + ButtonID = buttonID; + Switches = switches; + TextEntries = textEntries; + } - public int ButtonID { get; } + public int ButtonID{ get; } - public int[] Switches { get; } + public int[] Switches{ get; } - public TextRelay[] TextEntries { get; } + public TextRelay[] TextEntries{ get; } - public bool IsSwitched( int switchID ) - { - for ( int i = 0; i < Switches.Length; ++i ) - { - if ( Switches[i] == switchID ) - { - return true; - } - } + public bool IsSwitched(int switchID) + { + for (int i = 0; i < Switches.Length; ++i) + if (Switches[i] == switchID) + return true; - return false; - } + return false; + } - public TextRelay GetTextEntry( int entryID ) - { - for ( int i = 0; i < TextEntries.Length; ++i ) - { - if ( TextEntries[i].EntryID == entryID ) - { - return TextEntries[i]; - } - } + public TextRelay GetTextEntry(int entryID) + { + for (int i = 0; i < TextEntries.Length; ++i) + if (TextEntries[i].EntryID == entryID) + return TextEntries[i]; - return null; - } - } + return null; + } + } } \ No newline at end of file diff --git a/Server/HuePicker.cs b/Server/HuePicker.cs index c0e68d318..a020fb6ff 100644 --- a/Server/HuePicker.cs +++ b/Server/HuePicker.cs @@ -22,32 +22,32 @@ using Server.Network; namespace Server.HuePickers { - public class HuePicker - { - private static int m_NextSerial = 1; + public class HuePicker + { + private static int m_NextSerial = 1; - public int Serial { get; } + public HuePicker(int itemID) + { + do + { + Serial = m_NextSerial++; + } while (Serial == 0); - public int ItemID { get; } + ItemID = itemID; + } - public HuePicker( int itemID ) - { - do - { - Serial = m_NextSerial++; - } while ( Serial == 0 ); + public int Serial{ get; } - ItemID = itemID; - } + public int ItemID{ get; } - public virtual void OnResponse( int hue ) - { - } + public virtual void OnResponse(int hue) + { + } - public void SendTo( NetState state ) - { - state.Send( new DisplayHuePicker( this ) ); - state.AddHuePicker( this ); - } - } + public void SendTo(NetState state) + { + state.Send(new DisplayHuePicker(this)); + state.AddHuePicker(this); + } + } } \ No newline at end of file diff --git a/Server/IAccount.cs b/Server/IAccount.cs index c2be2019a..cbe1cc46d 100644 --- a/Server/IAccount.cs +++ b/Server/IAccount.cs @@ -22,105 +22,105 @@ using System; namespace Server.Accounting { - public static class AccountGold - { - public static bool Enabled = false; + public static class AccountGold + { + public static bool Enabled = false; - /// - /// This amount specifies the value at which point Gold turns to Platinum. - /// By default, when 1,000,000,000 Gold is accumulated, it will transform - /// into 1 Platinum. - /// !!! WARNING !!! - /// The client is designed to perceive the currency threashold at 1,000,000,000 - /// if you change this, it may cause unexpected results when using secure trading. - /// - public static int CurrencyThreshold = 1000000000; + /// + /// This amount specifies the value at which point Gold turns to Platinum. + /// By default, when 1,000,000,000 Gold is accumulated, it will transform + /// into 1 Platinum. + /// !!! WARNING !!! + /// The client is designed to perceive the currency threashold at 1,000,000,000 + /// if you change this, it may cause unexpected results when using secure trading. + /// + public static int CurrencyThreshold = 1000000000; - /// - /// Enables or Disables automatic conversion of Gold and Checks to Bank Currency - /// when they are added to a bank box container. - /// - public static bool ConvertOnBank = true; + /// + /// Enables or Disables automatic conversion of Gold and Checks to Bank Currency + /// when they are added to a bank box container. + /// + public static bool ConvertOnBank = true; - /// - /// Enables or Disables automatic conversion of Gold and Checks to Bank Currency - /// when they are added to a secure trade container. - /// - public static bool ConvertOnTrade = false; - } + /// + /// Enables or Disables automatic conversion of Gold and Checks to Bank Currency + /// when they are added to a secure trade container. + /// + public static bool ConvertOnTrade = false; + } - public interface IGoldAccount - { - /// - /// This amount represents the current amount of Gold owned by the player. - /// The value does not include the value of Platinum and ranges from - /// 0 to 999,999,999 by default. - /// - [CommandProperty(AccessLevel.Administrator)] - int TotalGold { get; } + public interface IGoldAccount + { + /// + /// This amount represents the current amount of Gold owned by the player. + /// The value does not include the value of Platinum and ranges from + /// 0 to 999,999,999 by default. + /// + [CommandProperty(AccessLevel.Administrator)] + int TotalGold{ get; } - /// - /// This amount represents the current amount of Platinum owned by the player. - /// The value does not include the value of Gold and ranges from - /// 0 to 2,147,483,647 by default. - /// One Platinum represents the value of CurrencyThreshold in Gold. - /// - [CommandProperty(AccessLevel.Administrator)] - int TotalPlat { get; } + /// + /// This amount represents the current amount of Platinum owned by the player. + /// The value does not include the value of Gold and ranges from + /// 0 to 2,147,483,647 by default. + /// One Platinum represents the value of CurrencyThreshold in Gold. + /// + [CommandProperty(AccessLevel.Administrator)] + int TotalPlat{ get; } - /// - /// Attempts to deposit the given amount of Gold into this account. - /// If the given amount is greater than the CurrencyThreshold, - /// Platinum will be deposited to offset the difference. - /// - /// Amount to deposit. - /// True if successful, false if amount given is less than or equal to zero. - bool DepositGold(int amount); + /// + /// Attempts to deposit the given amount of Gold into this account. + /// If the given amount is greater than the CurrencyThreshold, + /// Platinum will be deposited to offset the difference. + /// + /// Amount to deposit. + /// True if successful, false if amount given is less than or equal to zero. + bool DepositGold(int amount); - /// - /// Attempts to deposit the given amount of Platinum into this account. - /// - /// Amount to deposit. - /// True if successful, false if amount given is less than or equal to zero. - bool DepositPlat(int amount); + /// + /// Attempts to deposit the given amount of Platinum into this account. + /// + /// Amount to deposit. + /// True if successful, false if amount given is less than or equal to zero. + bool DepositPlat(int amount); - /// - /// Attempts to withdraw the given amount of Gold from this account. - /// If the given amount is greater than the CurrencyThreshold, - /// Platinum will be withdrawn to offset the difference. - /// - /// Amount to withdraw. - /// True if successful, false if balance was too low. - bool WithdrawGold(int amount); + /// + /// Attempts to withdraw the given amount of Gold from this account. + /// If the given amount is greater than the CurrencyThreshold, + /// Platinum will be withdrawn to offset the difference. + /// + /// Amount to withdraw. + /// True if successful, false if balance was too low. + bool WithdrawGold(int amount); - /// - /// Attempts to withdraw the given amount of Platinum from this account. - /// - /// Amount to withdraw. - /// True if successful, false if balance was too low. - bool WithdrawPlat(int amount); + /// + /// Attempts to withdraw the given amount of Platinum from this account. + /// + /// Amount to withdraw. + /// True if successful, false if balance was too low. + bool WithdrawPlat(int amount); - /// - /// Returns total gold inclusive of platinum, capped to Int32. - /// This is strictly for backwards compatibility - /// - /// Total gold, capped at Int32.MaxValue - long GetTotalGold(); - } + /// + /// Returns total gold inclusive of platinum, capped to Int32. + /// This is strictly for backwards compatibility + /// + /// Total gold, capped at Int32.MaxValue + long GetTotalGold(); + } - public interface IAccount : IGoldAccount, IComparable - { - string Username { get; set; } - string Email { get; set; } - AccessLevel AccessLevel { get; set; } + public interface IAccount : IGoldAccount, IComparable + { + string Username{ get; set; } + string Email{ get; set; } + AccessLevel AccessLevel{ get; set; } - int Length { get; } - int Limit { get; } - int Count { get; } - Mobile this[int index] { get; set; } + int Length{ get; } + int Limit{ get; } + int Count{ get; } + Mobile this[int index]{ get; set; } - void Delete(); - void SetPassword( string password ); - bool CheckPassword( string password ); - } -} + void Delete(); + void SetPassword(string password); + bool CheckPassword(string password); + } +} \ No newline at end of file diff --git a/Server/IEntity.cs b/Server/IEntity.cs index 919ad96a9..1661ee785 100644 --- a/Server/IEntity.cs +++ b/Server/IEntity.cs @@ -22,75 +22,75 @@ using System; namespace Server { - public interface IEntity : IPoint3D, IComparable, IComparable - { - Serial Serial{ get; } - Point3D Location{ get; } - Map Map{ get; } - void MoveToWorld(Point3D location, Map map); - bool Deleted { get; } + public interface IEntity : IPoint3D, IComparable, IComparable + { + Serial Serial{ get; } + Point3D Location{ get; } + Map Map{ get; } + bool Deleted{ get; } + void MoveToWorld(Point3D location, Map map); - void Delete(); - void ProcessDelta(); - } + void Delete(); + void ProcessDelta(); + } - public class Entity : IEntity, IComparable - { - public int CompareTo( IEntity other ) - { - if ( other == null ) - return -1; + public class Entity : IEntity, IComparable + { + public Entity(Serial serial, Point3D loc, Map map) + { + Serial = serial; + Location = loc; + Map = map; + Deleted = false; + } - return Serial.CompareTo( other.Serial ); - } + public int CompareTo(Entity other) + { + return CompareTo((IEntity)other); + } - public int CompareTo( Entity other ) - { - return CompareTo( (IEntity) other ); - } + public int CompareTo(IEntity other) + { + if (other == null) + return -1; - public int CompareTo( object other ) - { - if ( other == null || other is IEntity ) - return CompareTo( (IEntity) other ); + return Serial.CompareTo(other.Serial); + } - throw new ArgumentException(); - } + public int CompareTo(object other) + { + if (other == null || other is IEntity) + return CompareTo((IEntity)other); - public Entity( Serial serial, Point3D loc, Map map ) - { - Serial = serial; - Location = loc; - Map = map; - Deleted = false; - } + throw new ArgumentException(); + } - public Serial Serial { get; } + public Serial Serial{ get; } - public Point3D Location { get; private set; } + public Point3D Location{ get; private set; } - public int X => Location.X; + public int X => Location.X; - public int Y => Location.Y; + public int Y => Location.Y; - public int Z => Location.Z; + public int Z => Location.Z; - public Map Map { get; private set; } + public Map Map{ get; private set; } - public virtual void MoveToWorld(Point3D newLocation, Map map) - { - Location = newLocation; - Map = map; - } + public virtual void MoveToWorld(Point3D newLocation, Map map) + { + Location = newLocation; + Map = map; + } - public bool Deleted { get; } + public bool Deleted{ get; } - public void Delete() - { - } + public void Delete() + { + } - public void ProcessDelta() - { - } - } -} + public void ProcessDelta() + { + } + } +} \ No newline at end of file diff --git a/Server/Insensitive.cs b/Server/Insensitive.cs index 49b9e197e..164c758a5 100644 --- a/Server/Insensitive.cs +++ b/Server/Insensitive.cs @@ -22,50 +22,50 @@ using System.Collections; namespace Server { - public static class Insensitive - { - public static IComparer Comparer { get; } = CaseInsensitiveComparer.Default; + public static class Insensitive + { + public static IComparer Comparer{ get; } = CaseInsensitiveComparer.Default; - public static int Compare( string a, string b ) - { - return Comparer.Compare( a, b ); - } + public static int Compare(string a, string b) + { + return Comparer.Compare(a, b); + } - public static bool Equals( string a, string b ) - { - if ( a == null && b == null ) - return true; - if ( a == null || b == null || a.Length != b.Length ) - return false; + public static bool Equals(string a, string b) + { + if (a == null && b == null) + return true; + if (a == null || b == null || a.Length != b.Length) + return false; - return ( Comparer.Compare( a, b ) == 0 ); - } + return Comparer.Compare(a, b) == 0; + } - public static bool StartsWith( string a, string b ) - { - if ( a == null || b == null || a.Length < b.Length ) - return false; + public static bool StartsWith(string a, string b) + { + if (a == null || b == null || a.Length < b.Length) + return false; - return ( Comparer.Compare( a.Substring( 0, b.Length ), b ) == 0 ); - } + return Comparer.Compare(a.Substring(0, b.Length), b) == 0; + } - public static bool EndsWith( string a, string b ) - { - if ( a == null || b == null || a.Length < b.Length ) - return false; + public static bool EndsWith(string a, string b) + { + if (a == null || b == null || a.Length < b.Length) + return false; - return ( Comparer.Compare( a.Substring( a.Length - b.Length ), b ) == 0 ); - } + return Comparer.Compare(a.Substring(a.Length - b.Length), b) == 0; + } - public static bool Contains( string a, string b ) - { - if ( a == null || b == null || a.Length < b.Length ) - return false; + public static bool Contains(string a, string b) + { + if (a == null || b == null || a.Length < b.Length) + return false; - a = a.ToLower(); - b = b.ToLower(); + a = a.ToLower(); + b = b.ToLower(); - return ( a.IndexOf( b ) >= 0 ); - } - } + return a.IndexOf(b) >= 0; + } + } } \ No newline at end of file diff --git a/Server/Interfaces.cs b/Server/Interfaces.cs index 1c233b3ee..24a855285 100644 --- a/Server/Interfaces.cs +++ b/Server/Interfaces.cs @@ -24,93 +24,91 @@ using Server.Mobiles; namespace Server.Mobiles { - public interface IMount - { - Mobile Rider{ get; set; } - void OnRiderDamaged( int amount, Mobile from, bool willKill ); - } + public interface IMount + { + Mobile Rider{ get; set; } + void OnRiderDamaged(int amount, Mobile from, bool willKill); + } - public interface IMountItem - { - IMount Mount{ get; } - } + public interface IMountItem + { + IMount Mount{ get; } + } } namespace Server { - public interface IVendor - { - bool OnBuyItems( Mobile from, List list ); - bool OnSellItems( Mobile from, List list ); + public interface IVendor + { + DateTime LastRestock{ get; set; } + TimeSpan RestockDelay{ get; } + bool OnBuyItems(Mobile from, List list); + bool OnSellItems(Mobile from, List list); + void Restock(); + } - DateTime LastRestock{ get; set; } - TimeSpan RestockDelay{ get; } - void Restock(); - } + public interface IPoint2D + { + int X{ get; } + int Y{ get; } + } - public interface IPoint2D - { - int X{ get; } - int Y{ get; } - } + public interface IPoint3D : IPoint2D + { + int Z{ get; } + } - public interface IPoint3D : IPoint2D - { - int Z{ get; } - } + public interface ICarvable + { + void Carve(Mobile from, Item item); + } - public interface ICarvable - { - void Carve( Mobile from, Item item ); - } + public interface IWeapon + { + int MaxRange{ get; } + void OnBeforeSwing(Mobile attacker, Mobile defender); + TimeSpan OnSwing(Mobile attacker, Mobile defender); + void GetStatusDamage(Mobile from, out int min, out int max); + } - public interface IWeapon - { - int MaxRange{ get; } - void OnBeforeSwing( Mobile attacker, Mobile defender ); - TimeSpan OnSwing( Mobile attacker, Mobile defender ); - void GetStatusDamage( Mobile from, out int min, out int max ); - } + public interface IHued + { + int HuedItemID{ get; } + } - public interface IHued - { - int HuedItemID{ get; } - } + public interface ISpell + { + bool IsCasting{ get; } + void OnCasterHurt(); + void OnCasterKilled(); + void OnConnectionChanged(); + bool OnCasterMoving(Direction d); + bool OnCasterEquipping(Item item); + bool OnCasterUsingObject(object o); + bool OnCastInTown(Region r); + } - public interface ISpell - { - bool IsCasting{ get; } - void OnCasterHurt(); - void OnCasterKilled(); - void OnConnectionChanged(); - bool OnCasterMoving( Direction d ); - bool OnCasterEquiping( Item item ); - bool OnCasterUsingObject( object o ); - bool OnCastInTown( Region r ); - } + public interface IParty + { + void OnStamChanged(Mobile m); + void OnManaChanged(Mobile m); + void OnStatsQuery(Mobile beholder, Mobile beheld); + } - public interface IParty - { - void OnStamChanged( Mobile m ); - void OnManaChanged( Mobile m ); - void OnStatsQuery( Mobile beholder, Mobile beheld ); - } + public interface ISpawner + { + bool UnlinkOnTaming{ get; } + Point3D HomeLocation{ get; } + int HomeRange{ get; } + Region Region{ get; } - public interface ISpawner - { - bool UnlinkOnTaming { get; } - Point3D HomeLocation { get; } - int HomeRange { get; } - Region Region { get; } + void Remove(ISpawnable spawn); + } - void Remove(ISpawnable spawn); - } - - public interface ISpawnable : IEntity - { - void OnBeforeSpawn(Point3D location, Map map); - void OnAfterSpawn(); - - ISpawner Spawner { get; set; } - } -} + public interface ISpawnable : IEntity + { + ISpawner Spawner{ get; set; } + void OnBeforeSpawn(Point3D location, Map map); + void OnAfterSpawn(); + } +} \ No newline at end of file diff --git a/Server/Item.cs b/Server/Item.cs index df45816ff..7e46ac2f9 100644 --- a/Server/Item.cs +++ b/Server/Item.cs @@ -19,4539 +19,4660 @@ ***************************************************************************/ using System; -using System.IO; using System.Collections.Generic; +using System.Diagnostics; +using System.IO; using System.Threading.Tasks; -using Server.Network; -using Server.Items; using Server.ContextMenus; +using Server.Items; +using Server.Network; +using Server.Targeting; namespace Server { - /// - /// Enumeration of item layer values. - /// - public enum Layer : byte - { - /// - /// Invalid layer. - /// - Invalid = 0x00, - /// - /// First valid layer. Equivalent to Layer.OneHanded. - /// - FirstValid = 0x01, - /// - /// One handed weapon. - /// - OneHanded = 0x01, - /// - /// Two handed weapon or shield. - /// - TwoHanded = 0x02, - /// - /// Shoes. - /// - Shoes = 0x03, - /// - /// Pants. - /// - Pants = 0x04, - /// - /// Shirts. - /// - Shirt = 0x05, - /// - /// Helmets, hats, and masks. - /// - Helm = 0x06, - /// - /// Gloves. - /// - Gloves = 0x07, - /// - /// Rings. - /// - Ring = 0x08, - /// - /// Talismans. - /// - Talisman = 0x09, - /// - /// Gorgets and necklaces. - /// - Neck = 0x0A, - /// - /// Hair. - /// - Hair = 0x0B, - /// - /// Half aprons. - /// - Waist = 0x0C, - /// - /// Torso, inner layer. - /// - InnerTorso = 0x0D, - /// - /// Bracelets. - /// - Bracelet = 0x0E, - /// - /// Unused. - /// - Unused_xF = 0x0F, - /// - /// Beards and mustaches. - /// - FacialHair = 0x10, - /// - /// Torso, outer layer. - /// - MiddleTorso = 0x11, - /// - /// Earings. - /// - Earrings = 0x12, - /// - /// Arms and sleeves. - /// - Arms = 0x13, - /// - /// Cloaks. - /// - Cloak = 0x14, - /// - /// Backpacks. - /// - Backpack = 0x15, - /// - /// Torso, outer layer. - /// - OuterTorso = 0x16, - /// - /// Leggings, outer layer. - /// - OuterLegs = 0x17, - /// - /// Leggings, inner layer. - /// - InnerLegs = 0x18, - /// - /// Last valid non-internal layer. Equivalent to Layer.InnerLegs. - /// - LastUserValid= 0x18, - /// - /// Mount item layer. - /// - Mount = 0x19, - /// - /// Vendor 'buy pack' layer. - /// - ShopBuy = 0x1A, - /// - /// Vendor 'resale pack' layer. - /// - ShopResale = 0x1B, - /// - /// Vendor 'sell pack' layer. - /// - ShopSell = 0x1C, - /// - /// Bank box layer. - /// - Bank = 0x1D, - /// - /// Last valid layer. Equivalent to Layer.Bank. - /// - LastValid = 0x1D - } - - /// - /// Internal flags used to signal how the item should be updated and resent to nearby clients. - /// - [Flags] - public enum ItemDelta - { - /// - /// Nothing. - /// - None = 0x00000000, - /// - /// Resend the item. - /// - Update = 0x00000001, - /// - /// Resend the item only if it is equipped. - /// - EquipOnly = 0x00000002, - /// - /// Resend the item's properties. - /// - Properties = 0x00000004 - } - - /// - /// Enumeration containing possible ways to handle item ownership on death. - /// - public enum DeathMoveResult - { - /// - /// The item should be placed onto the corpse. - /// - MoveToCorpse, - /// - /// The item should remain equipped. - /// - RemainEquipped, - /// - /// The item should be placed into the owners backpack. - /// - MoveToBackpack - } - - /// - /// Enumeration containing all possible light types. These are only applicable to light source items, like lanterns, candles, braziers, etc. - /// - public enum LightType - { - /// - /// Window shape, arched, ray shining east. - /// - ArchedWindowEast, - /// - /// Medium circular shape. - /// - Circle225, - /// - /// Small circular shape. - /// - Circle150, - /// - /// Door shape, shining south. - /// - DoorSouth, - /// - /// Door shape, shining east. - /// - DoorEast, - /// - /// Large semicircular shape (180 degrees), north wall. - /// - NorthBig, - /// - /// Large pie shape (90 degrees), north-east corner. - /// - NorthEastBig, - /// - /// Large semicircular shape (180 degrees), east wall. - /// - EastBig, - /// - /// Large semicircular shape (180 degrees), west wall. - /// - WestBig, - /// - /// Large pie shape (90 degrees), south-west corner. - /// - SouthWestBig, - /// - /// Large semicircular shape (180 degrees), south wall. - /// - SouthBig, - /// - /// Medium semicircular shape (180 degrees), north wall. - /// - NorthSmall, - /// - /// Medium pie shape (90 degrees), north-east corner. - /// - NorthEastSmall, - /// - /// Medium semicircular shape (180 degrees), east wall. - /// - EastSmall, - /// - /// Medium semicircular shape (180 degrees), west wall. - /// - WestSmall, - /// - /// Medium semicircular shape (180 degrees), south wall. - /// - SouthSmall, - /// - /// Shaped like a wall decoration, north wall. - /// - DecorationNorth, - /// - /// Shaped like a wall decoration, north-east corner. - /// - DecorationNorthEast, - /// - /// Small semicircular shape (180 degrees), east wall. - /// - EastTiny, - /// - /// Shaped like a wall decoration, west wall. - /// - DecorationWest, - /// - /// Shaped like a wall decoration, south-west corner. - /// - DecorationSouthWest, - /// - /// Small semicircular shape (180 degrees), south wall. - /// - SouthTiny, - /// - /// Window shape, rectangular, no ray, shining south. - /// - RectWindowSouthNoRay, - /// - /// Window shape, rectangular, no ray, shining east. - /// - RectWindowEastNoRay, - /// - /// Window shape, rectangular, ray shining south. - /// - RectWindowSouth, - /// - /// Window shape, rectangular, ray shining east. - /// - RectWindowEast, - /// - /// Window shape, arched, no ray, shining south. - /// - ArchedWindowSouthNoRay, - /// - /// Window shape, arched, no ray, shining east. - /// - ArchedWindowEastNoRay, - /// - /// Window shape, arched, ray shining south. - /// - ArchedWindowSouth, - /// - /// Large circular shape. - /// - Circle300, - /// - /// Large pie shape (90 degrees), north-west corner. - /// - NorthWestBig, - /// - /// Negative light. Medium pie shape (90 degrees), south-east corner. - /// - DarkSouthEast, - /// - /// Negative light. Medium semicircular shape (180 degrees), south wall. - /// - DarkSouth, - /// - /// Negative light. Medium pie shape (90 degrees), north-west corner. - /// - DarkNorthWest, - /// - /// Negative light. Medium pie shape (90 degrees), south-east corner. Equivalent to LightType.SouthEast. - /// - DarkSouthEast2, - /// - /// Negative light. Medium circular shape (180 degrees), east wall. - /// - DarkEast, - /// - /// Negative light. Large circular shape. - /// - DarkCircle300, - /// - /// Opened door shape, shining south. - /// - DoorOpenSouth, - /// - /// Opened door shape, shining east. - /// - DoorOpenEast, - /// - /// Window shape, square, ray shining east. - /// - SquareWindowEast, - /// - /// Window shape, square, no ray, shining east. - /// - SquareWindowEastNoRay, - /// - /// Window shape, square, ray shining south. - /// - SquareWindowSouth, - /// - /// Window shape, square, no ray, shining south. - /// - SquareWindowSouthNoRay, - /// - /// Empty. - /// - Empty, - /// - /// Window shape, skinny, no ray, shining south. - /// - SkinnyWindowSouthNoRay, - /// - /// Window shape, skinny, ray shining east. - /// - SkinnyWindowEast, - /// - /// Window shape, skinny, no ray, shining east. - /// - SkinnyWindowEastNoRay, - /// - /// Shaped like a hole, shining south. - /// - HoleSouth, - /// - /// Shaped like a hole, shining south. - /// - HoleEast, - /// - /// Large circular shape with a moongate graphic embeded. - /// - Moongate, - /// - /// Unknown usage. Many rows of slightly angled lines. - /// - Strips, - /// - /// Shaped like a small hole, shining south. - /// - SmallHoleSouth, - /// - /// Shaped like a small hole, shining east. - /// - SmallHoleEast, - /// - /// Large semicircular shape (180 degrees), north wall. Identical graphic as LightType.NorthBig, but slightly different positioning. - /// - NorthBig2, - /// - /// Large semicircular shape (180 degrees), west wall. Identical graphic as LightType.WestBig, but slightly different positioning. - /// - WestBig2, - /// - /// Large pie shape (90 degrees), north-west corner. Equivalent to LightType.NorthWestBig. - /// - NorthWestBig2 - } - - /// - /// Enumeration of an item's loot and steal state. - /// - public enum LootType : byte - { - /// - /// Stealable. Lootable. - /// - Regular = 0, - /// - /// Unstealable. Unlootable, unless owned by a murderer. - /// - Newbied = 1, - /// - /// Unstealable. Unlootable, always. - /// - Blessed = 2, - /// - /// Stealable. Lootable, always. - /// - Cursed = 3 - } - - public class BounceInfo - { - public Map m_Map; - public Point3D m_Location, m_WorldLoc; - public IEntity m_Parent; - - public BounceInfo( Item item ) - { - m_Map = item.Map; - m_Location = item.Location; - m_WorldLoc = item.GetWorldLocation(); - m_Parent = item.Parent; - } - - private BounceInfo( Map map, Point3D loc, Point3D worldLoc, IEntity parent ) - { - m_Map = map; - m_Location = loc; - m_WorldLoc = worldLoc; - m_Parent = parent; - } - - public static BounceInfo Deserialize( GenericReader reader ) - { - if ( reader.ReadBool() ) - { - Map map = reader.ReadMap(); - Point3D loc = reader.ReadPoint3D(); - Point3D worldLoc = reader.ReadPoint3D(); - - IEntity parent; - - Serial serial = reader.ReadInt(); - - if ( serial.IsItem ) - parent = World.FindItem( serial ); - else if ( serial.IsMobile ) - parent = World.FindMobile( serial ); - else - parent = null; - - return new BounceInfo( map, loc, worldLoc, parent ); - } - - return null; - } - - public static void Serialize( BounceInfo info, GenericWriter writer ) - { - if ( info == null ) - { - writer.Write( false ); - } - else - { - writer.Write( true ); - - writer.Write( info.m_Map ); - writer.Write( info.m_Location ); - writer.Write( info.m_WorldLoc ); - - if ( info.m_Parent is Mobile mobile ) - writer.Write( mobile ); - else if ( info.m_Parent is Item item ) - writer.Write( item ); - else - writer.Write( (Serial) 0 ); - } - } - } - - public enum TotalType - { - Gold, - Items, - Weight, - } - - [Flags] - public enum ExpandFlag - { - None = 0x000, - - Name = 0x001, - Items = 0x002, - Bounce = 0x004, - Holder = 0x008, - Blessed = 0x010, - TempFlag = 0x020, - SaveFlag = 0x040, - Weight = 0x080, - Spawner = 0x100 - } - - public class Item : IEntity, IHued, IComparable, ISerializable, ISpawnable - { - public static readonly List EmptyItems = new List(); - - public int CompareTo( IEntity other ) - { - if ( other == null ) - return -1; - - return Serial.CompareTo( other.Serial ); - } - - public int CompareTo( Item other ) - { - return CompareTo( (IEntity) other ); - } - - public int CompareTo( object other ) - { - if ( other == null || other is IEntity ) - return CompareTo( (IEntity) other ); - - throw new ArgumentException(); - } - - #region Standard fields - - private Point3D m_Location; - private int m_ItemID; - private int m_Hue; - private int m_Amount; - private Layer m_Layer; - private IEntity m_Parent; // Mobile, Item, or null=World - private Map m_Map; - private LootType m_LootType; - private Direction m_Direction; - #endregion - - private ItemDelta m_DeltaFlags; - private ImplFlag m_Flags; - - #region Packet caches - private Packet m_WorldPacket; - private Packet m_WorldPacketSA; - private Packet m_WorldPacketHS; - private Packet m_RemovePacket; - - private Packet m_OPLPacket; - private ObjectPropertyList m_PropertyList; - #endregion - - public int TempFlags - { - get - { - CompactInfo info = LookupCompactInfo(); - - if ( info != null ) - return info.m_TempFlags; - - return 0; - } - set - { - CompactInfo info = AcquireCompactInfo(); - - info.m_TempFlags = value; - - if ( info.m_TempFlags == 0 ) - VerifyCompactInfo(); - } - } - - public int SavedFlags - { - get - { - CompactInfo info = LookupCompactInfo(); - - if ( info != null ) - return info.m_SavedFlags; - - return 0; - } - set - { - CompactInfo info = AcquireCompactInfo(); - - info.m_SavedFlags = value; - - if ( info.m_SavedFlags == 0 ) - VerifyCompactInfo(); - } - } - - /// - /// The who is currently holding this item. - /// - public Mobile HeldBy - { - get - { - CompactInfo info = LookupCompactInfo(); - - return info?.m_HeldBy; - } - set - { - CompactInfo info = AcquireCompactInfo(); - - info.m_HeldBy = value; - - if ( info.m_HeldBy == null ) - VerifyCompactInfo(); - } - } - - [Flags] - private enum ImplFlag : byte - { - None = 0x00, - Visible = 0x01, - Movable = 0x02, - Deleted = 0x04, - Stackable = 0x08, - InQueue = 0x10, - Insured = 0x20, - PaidInsurance = 0x40, - QuestItem = 0x80 - } - - private class CompactInfo - { - public string m_Name; - - public List m_Items; - public BounceInfo m_Bounce; - - public Mobile m_HeldBy; - public Mobile m_BlessedFor; - - public ISpawner m_Spawner; - - public int m_TempFlags; - public int m_SavedFlags; - - public double m_Weight = -1; - } - - private CompactInfo m_CompactInfo; - - public ExpandFlag GetExpandFlags() - { - CompactInfo info = LookupCompactInfo(); - - ExpandFlag flags = 0; + /// + /// Enumeration of item layer values. + /// + public enum Layer : byte + { + /// + /// Invalid layer. + /// + Invalid = 0x00, + + /// + /// First valid layer. Equivalent to Layer.OneHanded. + /// + FirstValid = 0x01, + + /// + /// One handed weapon. + /// + OneHanded = 0x01, + + /// + /// Two handed weapon or shield. + /// + TwoHanded = 0x02, + + /// + /// Shoes. + /// + Shoes = 0x03, + + /// + /// Pants. + /// + Pants = 0x04, + + /// + /// Shirts. + /// + Shirt = 0x05, + + /// + /// Helmets, hats, and masks. + /// + Helm = 0x06, + + /// + /// Gloves. + /// + Gloves = 0x07, + + /// + /// Rings. + /// + Ring = 0x08, + + /// + /// Talismans. + /// + Talisman = 0x09, + + /// + /// Gorgets and necklaces. + /// + Neck = 0x0A, + + /// + /// Hair. + /// + Hair = 0x0B, + + /// + /// Half aprons. + /// + Waist = 0x0C, + + /// + /// Torso, inner layer. + /// + InnerTorso = 0x0D, + + /// + /// Bracelets. + /// + Bracelet = 0x0E, + + /// + /// Unused. + /// + Unused_xF = 0x0F, + + /// + /// Beards and mustaches. + /// + FacialHair = 0x10, + + /// + /// Torso, outer layer. + /// + MiddleTorso = 0x11, + + /// + /// Earings. + /// + Earrings = 0x12, + + /// + /// Arms and sleeves. + /// + Arms = 0x13, + + /// + /// Cloaks. + /// + Cloak = 0x14, + + /// + /// Backpacks. + /// + Backpack = 0x15, + + /// + /// Torso, outer layer. + /// + OuterTorso = 0x16, + + /// + /// Leggings, outer layer. + /// + OuterLegs = 0x17, + + /// + /// Leggings, inner layer. + /// + InnerLegs = 0x18, + + /// + /// Last valid non-internal layer. Equivalent to Layer.InnerLegs. + /// + LastUserValid = 0x18, + + /// + /// Mount item layer. + /// + Mount = 0x19, + + /// + /// Vendor 'buy pack' layer. + /// + ShopBuy = 0x1A, + + /// + /// Vendor 'resale pack' layer. + /// + ShopResale = 0x1B, + + /// + /// Vendor 'sell pack' layer. + /// + ShopSell = 0x1C, + + /// + /// Bank box layer. + /// + Bank = 0x1D, + + /// + /// Last valid layer. Equivalent to Layer.Bank. + /// + LastValid = 0x1D + } + + /// + /// Internal flags used to signal how the item should be updated and resent to nearby clients. + /// + [Flags] + public enum ItemDelta + { + /// + /// Nothing. + /// + None = 0x00000000, + + /// + /// Resend the item. + /// + Update = 0x00000001, + + /// + /// Resend the item only if it is equipped. + /// + EquipOnly = 0x00000002, + + /// + /// Resend the item's properties. + /// + Properties = 0x00000004 + } + + /// + /// Enumeration containing possible ways to handle item ownership on death. + /// + public enum DeathMoveResult + { + /// + /// The item should be placed onto the corpse. + /// + MoveToCorpse, + + /// + /// The item should remain equipped. + /// + RemainEquipped, + + /// + /// The item should be placed into the owners backpack. + /// + MoveToBackpack + } + + /// + /// Enumeration containing all possible light types. These are only applicable to light source items, like lanterns, candles, + /// braziers, etc. + /// + public enum LightType + { + /// + /// Window shape, arched, ray shining east. + /// + ArchedWindowEast, + + /// + /// Medium circular shape. + /// + Circle225, + + /// + /// Small circular shape. + /// + Circle150, + + /// + /// Door shape, shining south. + /// + DoorSouth, + + /// + /// Door shape, shining east. + /// + DoorEast, + + /// + /// Large semicircular shape (180 degrees), north wall. + /// + NorthBig, + + /// + /// Large pie shape (90 degrees), north-east corner. + /// + NorthEastBig, + + /// + /// Large semicircular shape (180 degrees), east wall. + /// + EastBig, + + /// + /// Large semicircular shape (180 degrees), west wall. + /// + WestBig, + + /// + /// Large pie shape (90 degrees), south-west corner. + /// + SouthWestBig, + + /// + /// Large semicircular shape (180 degrees), south wall. + /// + SouthBig, + + /// + /// Medium semicircular shape (180 degrees), north wall. + /// + NorthSmall, + + /// + /// Medium pie shape (90 degrees), north-east corner. + /// + NorthEastSmall, + + /// + /// Medium semicircular shape (180 degrees), east wall. + /// + EastSmall, + + /// + /// Medium semicircular shape (180 degrees), west wall. + /// + WestSmall, + + /// + /// Medium semicircular shape (180 degrees), south wall. + /// + SouthSmall, + + /// + /// Shaped like a wall decoration, north wall. + /// + DecorationNorth, + + /// + /// Shaped like a wall decoration, north-east corner. + /// + DecorationNorthEast, + + /// + /// Small semicircular shape (180 degrees), east wall. + /// + EastTiny, + + /// + /// Shaped like a wall decoration, west wall. + /// + DecorationWest, + + /// + /// Shaped like a wall decoration, south-west corner. + /// + DecorationSouthWest, + + /// + /// Small semicircular shape (180 degrees), south wall. + /// + SouthTiny, + + /// + /// Window shape, rectangular, no ray, shining south. + /// + RectWindowSouthNoRay, + + /// + /// Window shape, rectangular, no ray, shining east. + /// + RectWindowEastNoRay, + + /// + /// Window shape, rectangular, ray shining south. + /// + RectWindowSouth, + + /// + /// Window shape, rectangular, ray shining east. + /// + RectWindowEast, + + /// + /// Window shape, arched, no ray, shining south. + /// + ArchedWindowSouthNoRay, + + /// + /// Window shape, arched, no ray, shining east. + /// + ArchedWindowEastNoRay, + + /// + /// Window shape, arched, ray shining south. + /// + ArchedWindowSouth, + + /// + /// Large circular shape. + /// + Circle300, + + /// + /// Large pie shape (90 degrees), north-west corner. + /// + NorthWestBig, + + /// + /// Negative light. Medium pie shape (90 degrees), south-east corner. + /// + DarkSouthEast, + + /// + /// Negative light. Medium semicircular shape (180 degrees), south wall. + /// + DarkSouth, + + /// + /// Negative light. Medium pie shape (90 degrees), north-west corner. + /// + DarkNorthWest, + + /// + /// Negative light. Medium pie shape (90 degrees), south-east corner. Equivalent to LightType.SouthEast. + /// + DarkSouthEast2, + + /// + /// Negative light. Medium circular shape (180 degrees), east wall. + /// + DarkEast, + + /// + /// Negative light. Large circular shape. + /// + DarkCircle300, + + /// + /// Opened door shape, shining south. + /// + DoorOpenSouth, + + /// + /// Opened door shape, shining east. + /// + DoorOpenEast, + + /// + /// Window shape, square, ray shining east. + /// + SquareWindowEast, + + /// + /// Window shape, square, no ray, shining east. + /// + SquareWindowEastNoRay, + + /// + /// Window shape, square, ray shining south. + /// + SquareWindowSouth, + + /// + /// Window shape, square, no ray, shining south. + /// + SquareWindowSouthNoRay, + + /// + /// Empty. + /// + Empty, + + /// + /// Window shape, skinny, no ray, shining south. + /// + SkinnyWindowSouthNoRay, + + /// + /// Window shape, skinny, ray shining east. + /// + SkinnyWindowEast, + + /// + /// Window shape, skinny, no ray, shining east. + /// + SkinnyWindowEastNoRay, + + /// + /// Shaped like a hole, shining south. + /// + HoleSouth, + + /// + /// Shaped like a hole, shining south. + /// + HoleEast, + + /// + /// Large circular shape with a moongate graphic embeded. + /// + Moongate, + + /// + /// Unknown usage. Many rows of slightly angled lines. + /// + Strips, + + /// + /// Shaped like a small hole, shining south. + /// + SmallHoleSouth, + + /// + /// Shaped like a small hole, shining east. + /// + SmallHoleEast, + + /// + /// Large semicircular shape (180 degrees), north wall. Identical graphic as LightType.NorthBig, but slightly different + /// positioning. + /// + NorthBig2, + + /// + /// Large semicircular shape (180 degrees), west wall. Identical graphic as LightType.WestBig, but slightly different + /// positioning. + /// + WestBig2, + + /// + /// Large pie shape (90 degrees), north-west corner. Equivalent to LightType.NorthWestBig. + /// + NorthWestBig2 + } + + /// + /// Enumeration of an item's loot and steal state. + /// + public enum LootType : byte + { + /// + /// Stealable. Lootable. + /// + Regular = 0, + + /// + /// Unstealable. Unlootable, unless owned by a murderer. + /// + Newbied = 1, + + /// + /// Unstealable. Unlootable, always. + /// + Blessed = 2, + + /// + /// Stealable. Lootable, always. + /// + Cursed = 3 + } + + public class BounceInfo + { + public Point3D m_Location, m_WorldLoc; + public Map m_Map; + public IEntity m_Parent; + + public BounceInfo(Item item) + { + m_Map = item.Map; + m_Location = item.Location; + m_WorldLoc = item.GetWorldLocation(); + m_Parent = item.Parent; + } + + private BounceInfo(Map map, Point3D loc, Point3D worldLoc, IEntity parent) + { + m_Map = map; + m_Location = loc; + m_WorldLoc = worldLoc; + m_Parent = parent; + } + + public static BounceInfo Deserialize(GenericReader reader) + { + if (reader.ReadBool()) + { + Map map = reader.ReadMap(); + Point3D loc = reader.ReadPoint3D(); + Point3D worldLoc = reader.ReadPoint3D(); + + IEntity parent; + + Serial serial = reader.ReadInt(); + + if (serial.IsItem) + parent = World.FindItem(serial); + else if (serial.IsMobile) + parent = World.FindMobile(serial); + else + parent = null; + + return new BounceInfo(map, loc, worldLoc, parent); + } + + return null; + } + + public static void Serialize(BounceInfo info, GenericWriter writer) + { + if (info == null) + { + writer.Write(false); + } + else + { + writer.Write(true); + + writer.Write(info.m_Map); + writer.Write(info.m_Location); + writer.Write(info.m_WorldLoc); + + if (info.m_Parent is Mobile mobile) + writer.Write(mobile); + else if (info.m_Parent is Item item) + writer.Write(item); + else + writer.Write((Serial)0); + } + } + } + + public enum TotalType + { + Gold, + Items, + Weight + } + + [Flags] + public enum ExpandFlag + { + None = 0x000, + + Name = 0x001, + Items = 0x002, + Bounce = 0x004, + Holder = 0x008, + Blessed = 0x010, + TempFlag = 0x020, + SaveFlag = 0x040, + Weight = 0x080, + Spawner = 0x100 + } + + public class Item : IEntity, IHued, IComparable, ISerializable, ISpawnable + { + public const int QuestItemHue = 0x4EA; // Hmmmm... "for EA"? + public static readonly List EmptyItems = new List(); + + private static List m_DeltaQueue = new List(); + + private static bool _processing; + + private static int m_OpenSlots; + + private object _opll = new object(); + + private object _rpl = new object(); + + private object _wpl = new object(); + private object _wplhs = new object(); + private object _wplsa = new object(); + + private CompactInfo m_CompactInfo; + + private ItemDelta m_DeltaFlags; + private ImplFlag m_Flags; + + internal int m_TypeRef; + + public Item() + { + Serial = Serial.NewItem; + + //m_Items = new ArrayList( 1 ); + Visible = true; + Movable = true; + Amount = 1; + m_Map = Map.Internal; + + SetLastMoved(); + + World.AddItem(this); + + Type ourType = GetType(); + m_TypeRef = World.m_ItemTypes.IndexOf(ourType); + + if (m_TypeRef == -1) + { + World.m_ItemTypes.Add(ourType); + m_TypeRef = World.m_ItemTypes.Count - 1; + } + } + + [Constructible] + public Item(int itemID) : this() + { + m_ItemID = itemID; + } + + public Item(Serial serial) + { + Serial = serial; + + Type ourType = GetType(); + m_TypeRef = World.m_ItemTypes.IndexOf(ourType); + + if (m_TypeRef == -1) + { + World.m_ItemTypes.Add(ourType); + m_TypeRef = World.m_ItemTypes.Count - 1; + } + } + + public int TempFlags + { + get + { + CompactInfo info = LookupCompactInfo(); + + if (info != null) + return info.m_TempFlags; + + return 0; + } + set + { + CompactInfo info = AcquireCompactInfo(); + + info.m_TempFlags = value; + + if (info.m_TempFlags == 0) + VerifyCompactInfo(); + } + } + + public int SavedFlags + { + get + { + CompactInfo info = LookupCompactInfo(); + + if (info != null) + return info.m_SavedFlags; + + return 0; + } + set + { + CompactInfo info = AcquireCompactInfo(); + + info.m_SavedFlags = value; + + if (info.m_SavedFlags == 0) + VerifyCompactInfo(); + } + } + + /// + /// The who is currently holding this item. + /// + public Mobile HeldBy + { + get + { + CompactInfo info = LookupCompactInfo(); + + return info?.m_HeldBy; + } + set + { + CompactInfo info = AcquireCompactInfo(); + + info.m_HeldBy = value; + + if (info.m_HeldBy == null) + VerifyCompactInfo(); + } + } + + /// + /// Overridable. Determines whether the item will show . + /// + public virtual bool DisplayWeight + { + get + { + if (!Core.ML) + return false; + + if (!Movable && !(IsLockedDown || IsSecure) && ItemData.Weight == 255) + return false; + + return true; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public LootType LootType + { + get => m_LootType; + set + { + if (m_LootType != value) + { + m_LootType = value; + + if (DisplayLootType) + InvalidateProperties(); + } + } + } + + public static TimeSpan DefaultDecayTime{ get; set; } = TimeSpan.FromHours(1.0); + + [CommandProperty(AccessLevel.GameMaster)] + public virtual TimeSpan DecayTime => DefaultDecayTime; + + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool Decays => Movable && Visible; + + public DateTime LastMoved{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Stackable + { + get => GetFlag(ImplFlag.Stackable); + set => SetFlag(ImplFlag.Stackable, value); + } + + public Packet RemovePacket + { + get + { + if (m_RemovePacket == null) + lock (_rpl) + { + if (m_RemovePacket == null) + { + m_RemovePacket = new RemoveItem(this); + m_RemovePacket.SetStatic(); + } + } + + return m_RemovePacket; + } + } + + public Packet OPLPacket + { + get + { + if (m_OPLPacket == null) + lock (_opll) + { + if (m_OPLPacket == null) + { + m_OPLPacket = new OPLInfo(PropertyList); + m_OPLPacket.SetStatic(); + } + } + + return m_OPLPacket; + } + } + + public ObjectPropertyList PropertyList + { + get + { + if (m_PropertyList == null) + { + m_PropertyList = new ObjectPropertyList(this); + + GetProperties(m_PropertyList); + AppendChildProperties(m_PropertyList); + + m_PropertyList.Terminate(); + m_PropertyList.SetStatic(); + } + + return m_PropertyList; + } + } + + public Packet WorldPacket + { + get + { + // This needs to be invalidated when any of the following changes: + // - ItemID + // - Amount + // - Location + // - Hue + // - Packet Flags + // - Direction + + if (m_WorldPacket == null) + lock (_wpl) + { + if (m_WorldPacket == null) + { + m_WorldPacket = new WorldItem(this); + m_WorldPacket.SetStatic(); + } + } + + return m_WorldPacket; + } + } + + public Packet WorldPacketSA + { + get + { + // This needs to be invalidated when any of the following changes: + // - ItemID + // - Amount + // - Location + // - Hue + // - Packet Flags + // - Direction + + if (m_WorldPacketSA == null) + lock (_wplsa) + { + if (m_WorldPacketSA == null) + { + m_WorldPacketSA = new WorldItemSA(this); + m_WorldPacketSA.SetStatic(); + } + } + + return m_WorldPacketSA; + } + } + + public Packet WorldPacketHS + { + get + { + // This needs to be invalidated when any of the following changes: + // - ItemID + // - Amount + // - Location + // - Hue + // - Packet Flags + // - Direction + + if (m_WorldPacketHS == null) + lock (_wplhs) + { + if (m_WorldPacketHS == null) + { + m_WorldPacketHS = new WorldItemHS(this); + m_WorldPacketHS.SetStatic(); + } + } + + return m_WorldPacketHS; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Visible + { + get => GetFlag(ImplFlag.Visible); + set + { + if (GetFlag(ImplFlag.Visible) != value) + { + SetFlag(ImplFlag.Visible, value); + ReleaseWorldPackets(); + + if (m_Map != null) + { + Point3D worldLoc = GetWorldLocation(); + + IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (!m.CanSee(this) && m.InRange(worldLoc, GetUpdateRange(m))) state.Send(RemovePacket); + } + + eable.Free(); + } + + Delta(ItemDelta.Update); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Movable + { + get => GetFlag(ImplFlag.Movable); + set + { + if (GetFlag(ImplFlag.Movable) != value) + { + SetFlag(ImplFlag.Movable, value); + ReleaseWorldPackets(); + Delta(ItemDelta.Update); + } + } + } + + public virtual bool ForceShowProperties => false; + + public virtual bool HandlesOnMovement => false; + + public static int LockedDownFlag{ get; set; } + + public static int SecureFlag{ get; set; } + + public bool IsLockedDown + { + get => GetTempFlag(LockedDownFlag); + set + { + SetTempFlag(LockedDownFlag, value); + InvalidateProperties(); + } + } + + public bool IsSecure + { + get => GetTempFlag(SecureFlag); + set + { + SetTempFlag(SecureFlag, value); + InvalidateProperties(); + } + } + + public virtual bool IsVirtualItem => false; + + public virtual int LabelNumber + { + get + { + if (m_ItemID < 0x4000) + return 1020000 + m_ItemID; + + return 1078872 + m_ItemID; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int TotalGold => GetTotal(TotalType.Gold); + + [CommandProperty(AccessLevel.GameMaster)] + public int TotalItems => GetTotal(TotalType.Items); + + [CommandProperty(AccessLevel.GameMaster)] + public int TotalWeight => GetTotal(TotalType.Weight); + + public virtual double DefaultWeight + { + get + { + if (m_ItemID < 0 || m_ItemID > TileData.MaxItemValue || this is BaseMulti) + return 0; + + int weight = TileData.ItemTable[m_ItemID].Weight; + + if (weight == 255 || weight == 0) + weight = 1; + + return weight; + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public double Weight + { + get + { + CompactInfo info = LookupCompactInfo(); + + if (info != null && info.m_Weight != -1) + return info.m_Weight; + + return DefaultWeight; + } + set + { + if (Weight != value) + { + CompactInfo info = AcquireCompactInfo(); + + int oldPileWeight = PileWeight; + + info.m_Weight = value; + + if (info.m_Weight == -1) + VerifyCompactInfo(); + + int newPileWeight = PileWeight; + + UpdateTotal(this, TotalType.Weight, newPileWeight - oldPileWeight); + + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int PileWeight => (int)Math.Ceiling(Weight * Amount); + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public virtual int Hue + { + get => m_Hue; + set + { + if (m_Hue != value) + { + m_Hue = value; + ReleaseWorldPackets(); + + Delta(ItemDelta.Update); + } + } + } + + public virtual bool Nontransferable => QuestItem; + + [CommandProperty(AccessLevel.GameMaster)] + public virtual Layer Layer + { + get => m_Layer; + set + { + if (m_Layer != value) + { + m_Layer = value; + + Delta(ItemDelta.EquipOnly); + } + } + } + + public List Items + { + get + { + List items = LookupItems(); + + if (items == null) + items = EmptyItems; + + return items; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public IEntity RootParent + { + get + { + IEntity p = m_Parent; + + while (p is Item) + { + Item item = (Item)p; + + if (item.m_Parent == null) break; + + p = item.m_Parent; + } + + return p; + } + } + + public bool NoMoveHS{ get; set; } + + public virtual int PhysicalResistance => 0; + public virtual int FireResistance => 0; + public virtual int ColdResistance => 0; + public virtual int PoisonResistance => 0; + public virtual int EnergyResistance => 0; + + [CommandProperty(AccessLevel.GameMaster)] + public virtual int ItemID + { + get => m_ItemID; + set + { + if (m_ItemID != value) + { + int oldPileWeight = PileWeight; + + m_ItemID = value; + ReleaseWorldPackets(); + + int newPileWeight = PileWeight; + + UpdateTotal(this, TotalType.Weight, newPileWeight - oldPileWeight); + + InvalidateProperties(); + Delta(ItemDelta.Update); + } + } + } + + public virtual string DefaultName => null; + + [CommandProperty(AccessLevel.GameMaster)] + public string Name + { + get + { + CompactInfo info = LookupCompactInfo(); + + if (info?.m_Name != null) + return info.m_Name; + + return DefaultName; + } + set + { + if (value == null || value != DefaultName) + { + CompactInfo info = AcquireCompactInfo(); + + info.m_Name = value; + + if (info.m_Name == null) + VerifyCompactInfo(); + + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Developer)] + public IEntity Parent + { + get => m_Parent; + set + { + if (m_Parent == value) + return; + + IEntity oldParent = m_Parent; + + m_Parent = value; + + if (m_Map != null) + { + if (oldParent != null && m_Parent == null) + m_Map.OnEnter(this); + else if (m_Parent != null) + m_Map.OnLeave(this); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public LightType Light + { + get => (LightType)m_Direction; + set + { + if ((LightType)m_Direction != value) + { + m_Direction = (Direction)value; + ReleaseWorldPackets(); + + Delta(ItemDelta.Update); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Direction Direction + { + get => m_Direction; + set + { + if (m_Direction != value) + { + m_Direction = value; + ReleaseWorldPackets(); + + Delta(ItemDelta.Update); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Amount + { + get => m_Amount; + set + { + int oldValue = m_Amount; + + if (oldValue != value) + { + int oldPileWeight = PileWeight; + + m_Amount = value; + ReleaseWorldPackets(); + + int newPileWeight = PileWeight; + + UpdateTotal(this, TotalType.Weight, newPileWeight - oldPileWeight); + + OnAmountChange(oldValue); + + Delta(ItemDelta.Update); + + if (oldValue > 1 || value > 1) + InvalidateProperties(); + + if (!Stackable && m_Amount > 1) + Console.WriteLine("Warning: 0x{0:X}: Amount changed for non-stackable item '{2}'. ({1})", + Serial.Value, m_Amount, GetType().Name); + } + } + } + + public virtual bool HandlesOnSpeech => false; + + public virtual bool BlocksFit => false; + + public bool InSecureTrade => GetSecureTradeCont() != null; + + public ItemData ItemData => TileData.ItemTable[m_ItemID & TileData.MaxItemValue]; + + public virtual bool CanTarget => true; + public virtual bool DisplayLootType => true; + + public static bool ScissorCopyLootType{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool QuestItem + { + get => GetFlag(ImplFlag.QuestItem); + set + { + SetFlag(ImplFlag.QuestItem, value); + + InvalidateProperties(); + + ReleaseWorldPackets(); + + Delta(ItemDelta.Update); + } + } + + public bool Insured + { + get => GetFlag(ImplFlag.Insured); + set + { + SetFlag(ImplFlag.Insured, value); + InvalidateProperties(); + } + } + + public bool PaidInsurance + { + get => GetFlag(ImplFlag.PaidInsurance); + set => SetFlag(ImplFlag.PaidInsurance, value); + } - if ( info != null ) - { - if ( info.m_BlessedFor != null ) - flags |= ExpandFlag.Blessed; - - if ( info.m_Bounce != null ) - flags |= ExpandFlag.Bounce; - - if ( info.m_HeldBy != null ) - flags |= ExpandFlag.Holder; - - if ( info.m_Items != null ) - flags |= ExpandFlag.Items; - - if ( info.m_Name != null ) - flags |= ExpandFlag.Name; - - if (info.m_Spawner != null) - flags |= ExpandFlag.Spawner; - - if ( info.m_SavedFlags != 0 ) - flags |= ExpandFlag.SaveFlag; - - if ( info.m_TempFlags != 0 ) - flags |= ExpandFlag.TempFlag; - - if ( info.m_Weight != -1 ) - flags |= ExpandFlag.Weight; - } - - return flags; - } + public Mobile BlessedFor + { + get + { + CompactInfo info = LookupCompactInfo(); - private CompactInfo LookupCompactInfo() - { - return m_CompactInfo; - } + return info?.m_BlessedFor; + } + set + { + CompactInfo info = AcquireCompactInfo(); - private CompactInfo AcquireCompactInfo() - { - if ( m_CompactInfo == null ) - m_CompactInfo = new CompactInfo(); - - return m_CompactInfo; - } - - private void ReleaseCompactInfo() - { - m_CompactInfo = null; - } - - private void VerifyCompactInfo() - { - CompactInfo info = m_CompactInfo; - - if ( info == null ) - return; - - bool isValid = ( info.m_Name != null ) - || ( info.m_Items != null ) - || ( info.m_Bounce != null ) - || ( info.m_HeldBy != null ) - || ( info.m_BlessedFor != null ) - || ( info.m_Spawner != null ) - || ( info.m_TempFlags != 0 ) - || ( info.m_SavedFlags != 0 ) - || ( info.m_Weight != -1 ); - - if ( !isValid ) - ReleaseCompactInfo(); - } - - public List LookupItems() - { - if ( this is Container container ) - return container.m_Items; - - CompactInfo info = LookupCompactInfo(); - - return info?.m_Items; - } - - public List AcquireItems() - { - if ( this is Container cont ) - { - if ( cont.m_Items == null ) - cont.m_Items = new List(); - - return cont.m_Items; - } - - CompactInfo info = AcquireCompactInfo(); - - if ( info.m_Items == null ) - info.m_Items = new List(); - - return info.m_Items; - } - - private void SetFlag( ImplFlag flag, bool value ) - { - if ( value ) - m_Flags |= flag; - else - m_Flags &= ~flag; - } - - private bool GetFlag( ImplFlag flag ) - { - return ( (m_Flags & flag) != 0 ); - } - - public BounceInfo GetBounce() - { - CompactInfo info = LookupCompactInfo(); - - return info?.m_Bounce; - } - - public void RecordBounce() - { - CompactInfo info = AcquireCompactInfo(); - - info.m_Bounce = new BounceInfo( this ); - } - - public void ClearBounce() - { - CompactInfo info = LookupCompactInfo(); - - BounceInfo bounce = info?.m_Bounce; - - if ( bounce != null ) - { - info.m_Bounce = null; - - if ( bounce.m_Parent is Item parentItem ) - { - if ( !parentItem.Deleted ) - parentItem.OnItemBounceCleared( this ); - } - else if ( bounce.m_Parent is Mobile parentMobile ) - { - if ( !parentMobile.Deleted ) - parentMobile.OnItemBounceCleared( this ); - } - - VerifyCompactInfo(); - } - } - - /// - /// Overridable. Virtual event invoked when a client, , invokes a 'help request' for the Item. Seemingly no longer functional in newer clients. - /// - public virtual void OnHelpRequest( Mobile from ) - { - } - - /// - /// Overridable. Method checked to see if the item can be traded. - /// - /// True if the trade is allowed, false if not. - public virtual bool AllowSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when a trade has completed, either successfully or not. - /// - public virtual void OnSecureTrade( Mobile from, Mobile to, Mobile newOwner, bool accepted ) - { - } - - /// - /// Overridable. Method checked to see if the elemental resistances of this Item conflict with another Item on the . - /// - /// - /// - /// - /// True - /// There is a confliction. The elemental resistance bonuses of this Item should not be applied to the - /// - /// - /// False - /// There is no confliction. The bonuses should be applied. - /// - /// - /// - public virtual bool CheckPropertyConfliction( Mobile m ) - { - return false; - } - - /// - /// Overridable. Sends the object property list to . - /// - public virtual void SendPropertiesTo( Mobile from ) - { - from.Send( PropertyList ); - } - - /// - /// Overridable. Adds the name of this item to the given . This method should be overridden if the item requires a complex naming format. - /// - public virtual void AddNameProperty( ObjectPropertyList list ) - { - string name = Name; - - if ( name == null ) - { - if ( m_Amount <= 1 ) - list.Add( LabelNumber ); - else - list.Add( 1050039, "{0}\t#{1}", m_Amount, LabelNumber ); // ~1_NUMBER~ ~2_ITEMNAME~ - } - else - { - if ( m_Amount <= 1 ) - list.Add( name ); - else - list.Add( 1050039, "{0}\t{1}", m_Amount, Name ); // ~1_NUMBER~ ~2_ITEMNAME~ - } - } - - /// - /// Overridable. Adds the loot type of this item to the given . By default, this will be either 'blessed', 'cursed', or 'insured'. - /// - public virtual void AddLootTypeProperty( ObjectPropertyList list ) - { - if ( m_LootType == LootType.Blessed ) - list.Add( 1038021 ); // blessed - else if ( m_LootType == LootType.Cursed ) - list.Add( 1049643 ); // cursed - else if ( Insured ) - list.Add( 1061682 ); // insured - } - - /// - /// Overridable. Adds any elemental resistances of this item to the given . - /// - public virtual void AddResistanceProperties( ObjectPropertyList list ) - { - int v = PhysicalResistance; - - if ( v != 0 ) - list.Add( 1060448, v.ToString() ); // physical resist ~1_val~% - - v = FireResistance; - - if ( v != 0 ) - list.Add( 1060447, v.ToString() ); // fire resist ~1_val~% - - v = ColdResistance; - - if ( v != 0 ) - list.Add( 1060445, v.ToString() ); // cold resist ~1_val~% - - v = PoisonResistance; - - if ( v != 0 ) - list.Add( 1060449, v.ToString() ); // poison resist ~1_val~% - - v = EnergyResistance; - - if ( v != 0 ) - list.Add( 1060446, v.ToString() ); // energy resist ~1_val~% - } - - /// - /// Overridable. Determines whether the item will show . - /// - public virtual bool DisplayWeight - { - get - { - if ( !Core.ML ) - return false; - - if ( !Movable && !( IsLockedDown || IsSecure ) && ItemData.Weight == 255 ) - return false; - - return true; - } - } - - /// - /// Overridable. Displays cliloc 1072788-1072789. - /// - public virtual void AddWeightProperty( ObjectPropertyList list ) - { - int weight = PileWeight + TotalWeight; - - if ( weight == 1 ) { - list.Add( 1072788, weight.ToString() ); //Weight: ~1_WEIGHT~ stone - } else { - list.Add( 1072789, weight.ToString() ); //Weight: ~1_WEIGHT~ stones - } - } - - /// - /// Overridable. Adds header properties. By default, this invokes , (if applicable), and (if ). - /// - public virtual void AddNameProperties( ObjectPropertyList list ) - { - AddNameProperty( list ); - - if ( IsSecure ) - AddSecureProperty( list ); - else if ( IsLockedDown ) - AddLockedDownProperty( list ); - - Mobile blessedFor = BlessedFor; - - if ( blessedFor != null && !blessedFor.Deleted ) - AddBlessedForProperty( list, blessedFor ); - - if ( DisplayLootType ) - AddLootTypeProperty( list ); - - if ( DisplayWeight ) - AddWeightProperty( list ); - - if ( QuestItem ) - AddQuestItemProperty( list ); - - - AppendChildNameProperties( list ); - } - - /// - /// Overridable. Adds the "Quest Item" property to the given . - /// - public virtual void AddQuestItemProperty( ObjectPropertyList list ) - { - list.Add( 1072351 ); // Quest Item - } - - /// - /// Overridable. Adds the "Locked Down & Secure" property to the given . - /// - public virtual void AddSecureProperty( ObjectPropertyList list ) - { - list.Add( 501644 ); // locked down & secure - } - - /// - /// Overridable. Adds the "Locked Down" property to the given . - /// - public virtual void AddLockedDownProperty( ObjectPropertyList list ) - { - list.Add( 501643 ); // locked down - } - - /// - /// Overridable. Adds the "Blessed for ~1_NAME~" property to the given . - /// - public virtual void AddBlessedForProperty( ObjectPropertyList list, Mobile m ) - { - list.Add( 1062203, "{0}", m.Name ); // Blessed for ~1_NAME~ - } - - /// - /// Overridable. Fills an with everything applicable. By default, this invokes , then Item.GetChildProperties or Mobile.GetChildProperties. This method should be overridden to add any custom properties. - /// - public virtual void GetProperties( ObjectPropertyList list ) - { - AddNameProperties( list ); - } - - /// - /// Overridable. Event invoked when a child () is building it's . Recursively calls Item.GetChildProperties or Mobile.GetChildProperties. - /// - public virtual void GetChildProperties( ObjectPropertyList list, Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.GetChildProperties( list, item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.GetChildProperties( list, item ); - } - - /// - /// Overridable. Event invoked when a child () is building it's Name . Recursively calls Item.GetChildNameProperties or Mobile.GetChildNameProperties. - /// - public virtual void GetChildNameProperties( ObjectPropertyList list, Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.GetChildNameProperties( list, item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.GetChildNameProperties( list, item ); - } - - public virtual bool IsChildVisibleTo( Mobile m, Item child ) - { - return true; - } - - public void Bounce( Mobile from ) - { - if ( m_Parent is Item item ) - item.RemoveItem( this ); - else if ( m_Parent is Mobile mobile ) - mobile.RemoveItem( this ); - - m_Parent = null; - - BounceInfo bounce = GetBounce(); - - if ( bounce != null ) - { - IEntity parent = bounce.m_Parent; - - if (parent == null || parent.Deleted) - { - MoveToWorld(bounce.m_WorldLoc, bounce.m_Map); - } - else if ( parent is Item p ) - { - IEntity root = p.RootParent; - - if ( p.IsAccessibleTo( from ) && ( !(root is Mobile mobileRoot) || mobileRoot.CheckNonlocalDrop( from, this, p ) ) ) - { - Location = bounce.m_Location; - p.AddItem( this ); - } - else - { - MoveToWorld( from.Location, from.Map ); - } - } - else if ( parent is Mobile parentMobile ) - { - if (!parentMobile.EquipItem( this )) - MoveToWorld( bounce.m_WorldLoc, bounce.m_Map ); - } - else - { - MoveToWorld( bounce.m_WorldLoc, bounce.m_Map ); - } - - ClearBounce(); - } - else - { - MoveToWorld( from.Location, from.Map ); - } - } - - /// - /// Overridable. Method checked to see if this item may be equipped while casting a spell. By default, this returns false. It is overridden on spellbook and spell channeling weapons or shields. - /// - /// True if it may, false if not. - /// - /// - /// public override bool AllowEquippedCast( Mobile from ) - /// { - /// if ( from.Int >= 100 ) - /// return true; - /// - /// return base.AllowEquippedCast( from ); - /// } - /// - /// When placed in an Item script, the item may be cast when equipped if the has 100 or more intelligence. Otherwise, it will drop to their backpack. - /// - public virtual bool AllowEquippedCast( Mobile from ) - { - return false; - } - - public virtual bool CheckConflictingLayer( Mobile m, Item item, Layer layer ) - { - return ( m_Layer == layer ); - } - - public virtual bool CanEquip( Mobile m ) - { - return ( m_Layer != Layer.Invalid && m.FindItemOnLayer( m_Layer ) == null ); - } - - public virtual void GetChildContextMenuEntries( Mobile from, List list, Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.GetChildContextMenuEntries( from, list, item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.GetChildContextMenuEntries( from, list, item ); - } - - public virtual void GetContextMenuEntries( Mobile from, List list ) - { - if ( m_Parent is Item item ) - item.GetChildContextMenuEntries( from, list, this ); - else if ( m_Parent is Mobile mobile ) - mobile.GetChildContextMenuEntries( from, list, this ); - } - - public virtual bool VerifyMove( Mobile from ) - { - return Movable; - } - - public virtual DeathMoveResult OnParentDeath( Mobile parent ) - { - if ( !Movable ) - return DeathMoveResult.RemainEquipped; - if ( parent.KeepsItemsOnDeath ) - return DeathMoveResult.MoveToBackpack; - if ( CheckBlessed( parent ) ) - return DeathMoveResult.MoveToBackpack; - if ( CheckNewbied() && parent.Kills < 5 ) - return DeathMoveResult.MoveToBackpack; - if ( parent.Player && Nontransferable ) - return DeathMoveResult.MoveToBackpack; - - return DeathMoveResult.MoveToCorpse; - } - - public virtual DeathMoveResult OnInventoryDeath( Mobile parent ) - { - if ( !Movable ) - return DeathMoveResult.MoveToBackpack; - if ( parent.KeepsItemsOnDeath ) - return DeathMoveResult.MoveToBackpack; - if ( CheckBlessed( parent ) ) - return DeathMoveResult.MoveToBackpack; - if ( CheckNewbied() && parent.Kills < 5 ) - return DeathMoveResult.MoveToBackpack; - if ( parent.Player && Nontransferable ) - return DeathMoveResult.MoveToBackpack; - - return DeathMoveResult.MoveToCorpse; - } - - /// - /// Moves the Item to . The Item does not change maps. - /// - public virtual void MoveToWorld( Point3D location ) - { - MoveToWorld( location, m_Map ); - } - - public void LabelTo( Mobile to, int number ) - { - to.Send( new MessageLocalized( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", "" ) ); - } - - public void LabelTo( Mobile to, int number, string args ) - { - to.Send( new MessageLocalized( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", args ) ); - } - - public void LabelTo( Mobile to, string text ) - { - to.Send( new UnicodeMessage( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, "ENU", "", text ) ); - } - - public void LabelTo( Mobile to, string format, params object[] args ) - { - LabelTo( to, string.Format( format, args ) ); - } - - public void LabelToAffix( Mobile to, int number, AffixType type, string affix ) - { - to.Send( new MessageLocalizedAffix( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", type, affix, "" ) ); - } - - public void LabelToAffix( Mobile to, int number, AffixType type, string affix, string args ) - { - to.Send( new MessageLocalizedAffix( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", type, affix, args ) ); - } - - public virtual void LabelLootTypeTo( Mobile to ) - { - if ( m_LootType == LootType.Blessed ) - LabelTo( to, 1041362 ); // (blessed) - else if ( m_LootType == LootType.Cursed ) - LabelTo( to, "(cursed)" ); - } - - public bool AtWorldPoint( int x, int y ) - { - return ( m_Parent == null && m_Location.m_X == x && m_Location.m_Y == y ); - } - - public bool AtPoint( int x, int y ) - { - return ( m_Location.m_X == x && m_Location.m_Y == y ); - } - - /// - /// Moves the Item to a given and . - /// - public void MoveToWorld( Point3D location, Map map ) - { - if ( Deleted ) - return; - - Point3D oldLocation = GetWorldLocation(); - Point3D oldRealLocation = m_Location; - - SetLastMoved(); - - if ( Parent is Mobile mobile ) - mobile.RemoveItem( this ); - else if ( Parent is Item item ) - item.RemoveItem( this ); - - if ( m_Map != map ) - { - Map old = m_Map; - - if ( m_Map != null ) - { - m_Map.OnLeave( this ); - - if ( oldLocation.m_X != 0 ) - { - IPooledEnumerable eable = m_Map.GetClientsInRange(oldLocation, GetMaxUpdateRange()); - - foreach ( NetState state in eable ) { - Mobile m = state.Mobile; - - if ( m.InRange( oldLocation, GetUpdateRange( m ) ) ) { - state.Send( RemovePacket ); - } - } - - eable.Free(); - } - } - - m_Location = location; - OnLocationChange( oldRealLocation ); - - ReleaseWorldPackets(); - - List items = LookupItems(); - - if ( items != null ) - { - for ( int i = 0; i < items.Count; ++i ) - items[i].Map = map; - } - - m_Map = map; - m_Map?.OnEnter( this ); - - OnMapChange(); - - if ( m_Map != null ) - { - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location, GetMaxUpdateRange()); - - foreach (NetState state in eable) { - Mobile m = state.Mobile; + info.m_BlessedFor = value; - if ( m.CanSee( this ) && m.InRange( m_Location, GetUpdateRange( m ) ) ) - SendInfoTo( state ); - } + if (info.m_BlessedFor == null) + VerifyCompactInfo(); - eable.Free(); - } + InvalidateProperties(); + } + } - RemDelta( ItemDelta.Update ); + public int CompareTo(Item other) + { + return CompareTo((IEntity)other); + } - if ( old == null || old == Map.Internal ) - InvalidateProperties(); - } - else if ( m_Map != null ) - { - IPooledEnumerable eable; - - if ( oldLocation.m_X != 0 ) - { - eable = m_Map.GetClientsInRange( oldLocation, GetMaxUpdateRange() ); + public int CompareTo(IEntity other) + { + if (other == null) + return -1; - foreach (NetState state in eable) { - Mobile m = state.Mobile; + return Serial.CompareTo(other.Serial); + } - if ( !m.InRange( location, GetUpdateRange( m ) ) ) { - state.Send( RemovePacket ); - } - } + public int CompareTo(object other) + { + if (other == null || other is IEntity) + return CompareTo((IEntity)other); - eable.Free(); - } + throw new ArgumentException(); + } - Point3D oldInternalLocation = m_Location; + /// + /// Moves the Item to a given and . + /// + public void MoveToWorld(Point3D location, Map map) + { + if (Deleted) + return; - m_Location = location; - OnLocationChange( oldRealLocation ); + Point3D oldLocation = GetWorldLocation(); + Point3D oldRealLocation = m_Location; - ReleaseWorldPackets(); + SetLastMoved(); - eable = m_Map.GetClientsInRange( m_Location, GetMaxUpdateRange() ); + if (Parent is Mobile mobile) + mobile.RemoveItem(this); + else if (Parent is Item item) + item.RemoveItem(this); - foreach (NetState state in eable) { - Mobile m = state.Mobile; + if (m_Map != map) + { + Map old = m_Map; - if ( m.CanSee( this ) && m.InRange( m_Location, GetUpdateRange( m ) ) ) - SendInfoTo( state ); - } + if (m_Map != null) + { + m_Map.OnLeave(this); - eable.Free(); + if (oldLocation.m_X != 0) + { + IPooledEnumerable eable = m_Map.GetClientsInRange(oldLocation, GetMaxUpdateRange()); - m_Map.OnMove( oldInternalLocation, this ); + foreach (NetState state in eable) + { + Mobile m = state.Mobile; - RemDelta( ItemDelta.Update ); - } - else - { - Map = map; - Location = location; - } - } + if (m.InRange(oldLocation, GetUpdateRange(m))) state.Send(RemovePacket); + } - /// - /// Has the item been deleted? - /// - public bool Deleted => GetFlag( ImplFlag.Deleted ); + eable.Free(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public LootType LootType - { - get => m_LootType; - set - { - if ( m_LootType != value ) - { - m_LootType = value; + m_Location = location; + OnLocationChange(oldRealLocation); + + ReleaseWorldPackets(); - if ( DisplayLootType ) - InvalidateProperties(); - } - } - } - - public static TimeSpan DefaultDecayTime { get; set; } = TimeSpan.FromHours( 1.0 ); - - [CommandProperty( AccessLevel.GameMaster )] - public virtual TimeSpan DecayTime => DefaultDecayTime; - - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool Decays => (Movable && Visible/* && Spawner == null*/); - - public virtual bool OnDecay() - { - return ( Decays && Parent == null && Map != Map.Internal && Region.Find( Location, Map ).OnDecay( this ) ); - } - - public void SetLastMoved() - { - LastMoved = DateTime.UtcNow; - } - - public DateTime LastMoved { get; set; } - - public virtual bool CanStackWith( Item dropped ) - { - return dropped.Stackable && Stackable && dropped.GetType() == GetType() && dropped.ItemID == ItemID && dropped.Hue == Hue && dropped.Name == Name && (dropped.Amount + Amount) <= 60000 && dropped != this; - } - - public bool StackWith( Mobile from, Item dropped ) - { - return StackWith( from, dropped, true ); - } - - public virtual bool StackWith( Mobile from, Item dropped, bool playSound ) - { - if ( CanStackWith( dropped ) ) - { - if ( m_LootType != dropped.m_LootType ) - m_LootType = LootType.Regular; - - Amount += dropped.Amount; - dropped.Delete(); - - if ( playSound && from != null ) - { - int soundID = GetDropSound(); - - if ( soundID == -1 ) - soundID = 0x42; - - from.SendSound( soundID, GetWorldLocation() ); - } - - return true; - } - - return false; - } - - public virtual bool OnDragDrop( Mobile from, Item dropped ) - { - bool success = Parent is Container container && container.OnStackAttempt( from, this, dropped ) || - StackWith( from, dropped ); - - if ( success && Spawner != null ) - { - Spawner.Remove( this ); - Spawner = null; - } - - return success; - } - - public Rectangle2D GetGraphicBounds() - { - int itemID = m_ItemID; - bool doubled = m_Amount > 1; - - if ( itemID >= 0xEEA && itemID <= 0xEF2 ) // Are we coins? - { - int coinBase = (itemID - 0xEEA) / 3; - coinBase *= 3; - coinBase += 0xEEA; - - doubled = false; - - if ( m_Amount <= 1 ) - { - // A single coin - itemID = coinBase; - } - else if ( m_Amount <= 5 ) - { - // A stack of coins - itemID = coinBase + 1; - } - else // m_Amount > 5 - { - // A pile of coins - itemID = coinBase + 2; - } - } - - Rectangle2D bounds = ItemBounds.Table[itemID & 0x3FFF]; - - if ( doubled ) - { - bounds.Set( bounds.X, bounds.Y, bounds.Width + 5, bounds.Height + 5 ); - } - - return bounds; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Stackable - { - get => GetFlag( ImplFlag.Stackable ); - set => SetFlag( ImplFlag.Stackable, value ); - } - - private object _rpl = new object(); - - public Packet RemovePacket - { - get - { - if (m_RemovePacket == null) - { - lock (_rpl) - { - if (m_RemovePacket == null) - { - m_RemovePacket = new RemoveItem(this); - m_RemovePacket.SetStatic(); - } - } - } - - return m_RemovePacket; - } - } - - private object _opll = new object(); - - public Packet OPLPacket - { - get - { - if (m_OPLPacket == null) - { - lock (_opll) - { - if (m_OPLPacket == null) - { - m_OPLPacket = new OPLInfo(PropertyList); - m_OPLPacket.SetStatic(); - } - } - } - - return m_OPLPacket; - } - } - - public ObjectPropertyList PropertyList - { - get - { - if ( m_PropertyList == null ) - { - m_PropertyList = new ObjectPropertyList( this ); - - GetProperties( m_PropertyList ); - AppendChildProperties( m_PropertyList ); - - m_PropertyList.Terminate(); - m_PropertyList.SetStatic(); - } - - return m_PropertyList; - } - } - - public virtual void AppendChildProperties( ObjectPropertyList list ) - { - if ( m_Parent is Item item ) - item.GetChildProperties( list, this ); - else if ( m_Parent is Mobile mobile ) - mobile.GetChildProperties( list, this ); - } - - public virtual void AppendChildNameProperties( ObjectPropertyList list ) - { - if ( m_Parent is Item item ) - item.GetChildNameProperties( list, this ); - else if ( m_Parent is Mobile mobile ) - mobile.GetChildNameProperties( list, this ); - } - - public void ClearProperties() - { - Packet.Release( ref m_PropertyList ); - Packet.Release( ref m_OPLPacket ); - } - - public void InvalidateProperties() - { - if ( !ObjectPropertyList.Enabled ) - return; - - if ( m_Map != null && m_Map != Map.Internal && !World.Loading ) - { - ObjectPropertyList oldList = m_PropertyList; - m_PropertyList = null; - ObjectPropertyList newList = PropertyList; - - if ( oldList == null || oldList.Hash != newList.Hash ) - { - Packet.Release( ref m_OPLPacket ); - Delta( ItemDelta.Properties ); - } - } - else - { - ClearProperties(); - } - } - - private object _wpl = new object(); - private object _wplsa = new object(); - private object _wplhs = new object(); - - public Packet WorldPacket - { - get - { - // This needs to be invalidated when any of the following changes: - // - ItemID - // - Amount - // - Location - // - Hue - // - Packet Flags - // - Direction - - if (m_WorldPacket == null) - { - lock (_wpl) - { - if (m_WorldPacket == null) - { - m_WorldPacket = new WorldItem(this); - m_WorldPacket.SetStatic(); - } - } - } - - return m_WorldPacket; - } - } - - public Packet WorldPacketSA - { - get - { - // This needs to be invalidated when any of the following changes: - // - ItemID - // - Amount - // - Location - // - Hue - // - Packet Flags - // - Direction - - if (m_WorldPacketSA == null) - { - lock (_wplsa) - { - if (m_WorldPacketSA == null) - { - m_WorldPacketSA = new WorldItemSA(this); - m_WorldPacketSA.SetStatic(); - } - } - } - - return m_WorldPacketSA; - } - } - - public Packet WorldPacketHS - { - get - { - // This needs to be invalidated when any of the following changes: - // - ItemID - // - Amount - // - Location - // - Hue - // - Packet Flags - // - Direction - - if (m_WorldPacketHS == null) - { - lock (_wplhs) - { - if (m_WorldPacketHS == null) - { - m_WorldPacketHS = new WorldItemHS(this); - m_WorldPacketHS.SetStatic(); - } - } - } - - return m_WorldPacketHS; - } - } - - public void ReleaseWorldPackets() - { - Packet.Release( ref m_WorldPacket ); - Packet.Release( ref m_WorldPacketSA ); - Packet.Release( ref m_WorldPacketHS ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Visible - { - get => GetFlag( ImplFlag.Visible ); - set - { - if ( GetFlag( ImplFlag.Visible ) != value ) - { - SetFlag( ImplFlag.Visible, value ); - ReleaseWorldPackets(); - - if ( m_Map != null ) - { - Point3D worldLoc = GetWorldLocation(); - - IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); - - foreach (NetState state in eable) { - Mobile m = state.Mobile; - - if ( !m.CanSee( this ) && m.InRange( worldLoc, GetUpdateRange( m ) ) ) { - state.Send( RemovePacket ); - } - } - - eable.Free(); - } - - Delta( ItemDelta.Update ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Movable - { - get => GetFlag( ImplFlag.Movable ); - set - { - if ( GetFlag( ImplFlag.Movable ) != value ) - { - SetFlag( ImplFlag.Movable, value ); - ReleaseWorldPackets(); - Delta( ItemDelta.Update ); - } - } - } - - public virtual bool ForceShowProperties => false; - - public virtual int GetPacketFlags() - { - int flags = 0; - - if ( !Visible ) - flags |= 0x80; - - if ( Movable || ForceShowProperties ) - flags |= 0x20; - - return flags; - } - - public virtual bool OnMoveOff( Mobile m ) - { - return true; - } - - public virtual bool OnMoveOver( Mobile m ) - { - return true; - } - - public virtual bool HandlesOnMovement => false; - - public virtual void OnMovement( Mobile m, Point3D oldLocation ) - { - } - - public void Internalize() - { - MoveToWorld( Point3D.Zero, Map.Internal ); - } - - public virtual void OnMapChange() - { - } - - public virtual void OnRemoved( IEntity parent ) - { - } - - public virtual void OnAdded( IEntity parent ) - { - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Map Map - { - get => m_Map; - set - { - if ( m_Map != value ) - { - Map old = m_Map; - - if ( m_Map != null && m_Parent == null ) - { - m_Map.OnLeave( this ); - SendRemovePacket(); - } - - List items = LookupItems(); - - if ( items != null ) - { - for ( int i = 0; i < items.Count; ++i ) - items[i].Map = value; - } - - m_Map = value; - - if ( m_Map != null && m_Parent == null ) - m_Map.OnEnter( this ); - - Delta( ItemDelta.Update ); - - OnMapChange(); - - if ( old == null || old == Map.Internal ) - InvalidateProperties(); - } - } - } - - [Flags] - private enum SaveFlag - { - None = 0x00000000, - Direction = 0x00000001, - Bounce = 0x00000002, - LootType = 0x00000004, - LocationFull = 0x00000008, - ItemID = 0x00000010, - Hue = 0x00000020, - Amount = 0x00000040, - Layer = 0x00000080, - Name = 0x00000100, - Parent = 0x00000200, - Items = 0x00000400, - WeightNot1or0 = 0x00000800, - Map = 0x00001000, - Visible = 0x00002000, - Movable = 0x00004000, - Stackable = 0x00008000, - WeightIs0 = 0x00010000, - LocationSByteZ = 0x00020000, - LocationShortXY = 0x00040000, - LocationByteXY = 0x00080000, - ImplFlags = 0x00100000, - InsuredFor = 0x00200000, - BlessedFor = 0x00400000, - HeldBy = 0x00800000, - IntWeight = 0x01000000, - SavedFlags = 0x02000000, - NullWeight = 0x04000000 - } - - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } - - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } - - int ISerializable.TypeReference => m_TypeRef; - - int ISerializable.SerialIdentity => Serial; - - public virtual void Serialize( GenericWriter writer ) - { - writer.Write( 9 ); // version - - SaveFlag flags = SaveFlag.None; - - int x = m_Location.m_X, y = m_Location.m_Y, z = m_Location.m_Z; - - if ( x != 0 || y != 0 || z != 0 ) - { - if ( x >= short.MinValue && x <= short.MaxValue && y >= short.MinValue && y <= short.MaxValue && z >= sbyte.MinValue && z <= sbyte.MaxValue ) - { - if ( x != 0 || y != 0 ) - { - if ( x >= byte.MinValue && x <= byte.MaxValue && y >= byte.MinValue && y <= byte.MaxValue ) - flags |= SaveFlag.LocationByteXY; - else - flags |= SaveFlag.LocationShortXY; - } - - if ( z != 0 ) - flags |= SaveFlag.LocationSByteZ; - } - else - { - flags |= SaveFlag.LocationFull; - } - } - - CompactInfo info = LookupCompactInfo(); - List items = LookupItems(); - - if ( m_Direction != Direction.North ) - flags |= SaveFlag.Direction; - if ( info?.m_Bounce != null ) - flags |= SaveFlag.Bounce; - if ( m_LootType != LootType.Regular ) - flags |= SaveFlag.LootType; - if ( m_ItemID != 0 ) - flags |= SaveFlag.ItemID; - if ( m_Hue != 0 ) - flags |= SaveFlag.Hue; - if ( m_Amount != 1 ) - flags |= SaveFlag.Amount; - if ( m_Layer != Layer.Invalid ) - flags |= SaveFlag.Layer; - if ( info?.m_Name != null ) - flags |= SaveFlag.Name; - if ( m_Parent != null ) - flags |= SaveFlag.Parent; - if ( items != null && items.Count > 0 ) - flags |= SaveFlag.Items; - if ( m_Map != Map.Internal ) - flags |= SaveFlag.Map; - //if ( m_InsuredFor != null && !m_InsuredFor.Deleted ) - //flags |= SaveFlag.InsuredFor; - - if (info != null) - { - if ( info.m_BlessedFor != null && !info.m_BlessedFor.Deleted ) - flags |= SaveFlag.BlessedFor; - if ( info.m_HeldBy != null && !info.m_HeldBy.Deleted ) - flags |= SaveFlag.HeldBy; - if ( info.m_SavedFlags != 0 ) - flags |= SaveFlag.SavedFlags; - } - - if ( info == null || info.m_Weight == -1 ) - { - flags |= SaveFlag.NullWeight; - } - else - { - if ( info.m_Weight == 0.0 ) - { - flags |= SaveFlag.WeightIs0; - } - else if ( info.m_Weight != 1.0 ) - { - if ( info.m_Weight == (int) info.m_Weight ) - flags |= SaveFlag.IntWeight; - else - flags |= SaveFlag.WeightNot1or0; - } - } - - ImplFlag implFlags = ( m_Flags & ( ImplFlag.Visible | ImplFlag.Movable | ImplFlag.Stackable | ImplFlag.Insured | ImplFlag.PaidInsurance | ImplFlag.QuestItem ) ); - - if ( implFlags != ( ImplFlag.Visible | ImplFlag.Movable ) ) - flags |= SaveFlag.ImplFlags; - - writer.Write( (int) flags ); - - /* begin last moved time optimization */ - long ticks = LastMoved.Ticks; - long now = DateTime.UtcNow.Ticks; - - TimeSpan d; - - try { d = new TimeSpan( ticks - now ); } - catch { if ( ticks < now ) d = TimeSpan.MaxValue; else d = TimeSpan.MaxValue; } - - double minutes = -d.TotalMinutes; - - if ( minutes < int.MinValue ) - minutes = int.MinValue; - else if ( minutes > int.MaxValue ) - minutes = int.MaxValue; - - writer.WriteEncodedInt( (int) minutes ); - /* end */ - - if ( GetSaveFlag( flags, SaveFlag.Direction ) ) - writer.Write( (byte) m_Direction ); - - if ( GetSaveFlag( flags, SaveFlag.Bounce ) ) - BounceInfo.Serialize( info.m_Bounce, writer ); - - if ( GetSaveFlag( flags, SaveFlag.LootType ) ) - writer.Write( (byte) m_LootType ); - - if ( GetSaveFlag( flags, SaveFlag.LocationFull ) ) - { - writer.WriteEncodedInt( x ); - writer.WriteEncodedInt( y ); - writer.WriteEncodedInt( z ); - } - else - { - if ( GetSaveFlag( flags, SaveFlag.LocationByteXY ) ) - { - writer.Write( (byte) x ); - writer.Write( (byte) y ); - } - else if ( GetSaveFlag( flags, SaveFlag.LocationShortXY ) ) - { - writer.Write( (short) x ); - writer.Write( (short) y ); - } - - if ( GetSaveFlag( flags, SaveFlag.LocationSByteZ ) ) - writer.Write( (sbyte) z ); - } - - if ( GetSaveFlag( flags, SaveFlag.ItemID ) ) - writer.WriteEncodedInt( (int) m_ItemID ); - - if ( GetSaveFlag( flags, SaveFlag.Hue ) ) - writer.WriteEncodedInt( (int) m_Hue ); - - if ( GetSaveFlag( flags, SaveFlag.Amount ) ) - writer.WriteEncodedInt( (int) m_Amount ); - - if ( GetSaveFlag( flags, SaveFlag.Layer ) ) - writer.Write( (byte) m_Layer ); + List items = LookupItems(); - if ( GetSaveFlag( flags, SaveFlag.Name ) ) - writer.Write( (string) info.m_Name ); - - if ( GetSaveFlag( flags, SaveFlag.Parent ) ) - { - if (m_Parent != null && !m_Parent.Deleted) - writer.Write(m_Parent.Serial); - else - writer.Write( (int) Serial.MinusOne ); - } + if (items != null) + for (int i = 0; i < items.Count; ++i) + items[i].Map = map; - if ( GetSaveFlag( flags, SaveFlag.Items ) ) - writer.Write( items, false ); + m_Map = map; + m_Map?.OnEnter(this); - if ( GetSaveFlag( flags, SaveFlag.IntWeight ) ) - writer.WriteEncodedInt( (int) info.m_Weight ); - else if ( GetSaveFlag( flags, SaveFlag.WeightNot1or0 ) ) - writer.Write( (double) info.m_Weight ); + OnMapChange(); - if ( GetSaveFlag( flags, SaveFlag.Map ) ) - writer.Write( (Map) m_Map ); + if (m_Map != null) + { + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location, GetMaxUpdateRange()); - if ( GetSaveFlag( flags, SaveFlag.ImplFlags ) ) - writer.WriteEncodedInt( (int) implFlags ); + foreach (NetState state in eable) + { + Mobile m = state.Mobile; - if ( GetSaveFlag( flags, SaveFlag.InsuredFor ) ) - writer.Write( (Mobile) null ); + if (m.CanSee(this) && m.InRange(m_Location, GetUpdateRange(m))) + SendInfoTo(state); + } - if ( GetSaveFlag( flags, SaveFlag.BlessedFor ) ) - writer.Write( info.m_BlessedFor ); + eable.Free(); + } - if ( GetSaveFlag( flags, SaveFlag.HeldBy ) ) - writer.Write( info.m_HeldBy ); + RemDelta(ItemDelta.Update); - if ( GetSaveFlag( flags, SaveFlag.SavedFlags ) ) - writer.WriteEncodedInt( info.m_SavedFlags ); - } + if (old == null || old == Map.Internal) + InvalidateProperties(); + } + else if (m_Map != null) + { + IPooledEnumerable eable; - public IPooledEnumerable GetObjectsInRange( int range ) - { - Map map = m_Map; + if (oldLocation.m_X != 0) + { + eable = m_Map.GetClientsInRange(oldLocation, GetMaxUpdateRange()); - if ( map == null ) - return Map.NullEnumerable.Instance; + foreach (NetState state in eable) + { + Mobile m = state.Mobile; - if ( m_Parent == null ) - return map.GetObjectsInRange( m_Location, range ); + if (!m.InRange(location, GetUpdateRange(m))) state.Send(RemovePacket); + } - return map.GetObjectsInRange( GetWorldLocation(), range ); - } + eable.Free(); + } - public IPooledEnumerable GetItemsInRange( int range ) - { - Map map = m_Map; + Point3D oldInternalLocation = m_Location; - if ( map == null ) - return Map.NullEnumerable.Instance; + m_Location = location; + OnLocationChange(oldRealLocation); - if ( m_Parent == null ) - return map.GetItemsInRange( m_Location, range ); + ReleaseWorldPackets(); - return map.GetItemsInRange( GetWorldLocation(), range ); - } + eable = m_Map.GetClientsInRange(m_Location, GetMaxUpdateRange()); - public IPooledEnumerable GetMobilesInRange( int range ) - { - Map map = m_Map; + foreach (NetState state in eable) + { + Mobile m = state.Mobile; - if ( map == null ) - return Map.NullEnumerable.Instance; + if (m.CanSee(this) && m.InRange(m_Location, GetUpdateRange(m))) + SendInfoTo(state); + } - if ( m_Parent == null ) - return map.GetMobilesInRange( m_Location, range ); + eable.Free(); - return map.GetMobilesInRange( GetWorldLocation(), range ); - } + m_Map.OnMove(oldInternalLocation, this); - public IPooledEnumerable GetClientsInRange( int range ) - { - Map map = m_Map; + RemDelta(ItemDelta.Update); + } + else + { + Map = map; + Location = location; + } + } - if ( map == null ) - return Map.NullEnumerable.Instance; + /// + /// Has the item been deleted? + /// + public bool Deleted => GetFlag(ImplFlag.Deleted); - if ( m_Parent == null ) - return map.GetClientsInRange( m_Location, range ); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Map Map + { + get => m_Map; + set + { + if (m_Map != value) + { + Map old = m_Map; - return map.GetClientsInRange( GetWorldLocation(), range ); - } + if (m_Map != null && m_Parent == null) + { + m_Map.OnLeave(this); + SendRemovePacket(); + } - public static int LockedDownFlag { get; set; } + List items = LookupItems(); - public static int SecureFlag { get; set; } + if (items != null) + for (int i = 0; i < items.Count; ++i) + items[i].Map = value; - public bool IsLockedDown - { - get => GetTempFlag( LockedDownFlag ); - set{ SetTempFlag( LockedDownFlag, value ); InvalidateProperties(); } - } + m_Map = value; - public bool IsSecure - { - get => GetTempFlag( SecureFlag ); - set{ SetTempFlag( SecureFlag, value ); InvalidateProperties(); } - } + if (m_Map != null && m_Parent == null) + m_Map.OnEnter(this); - public bool GetTempFlag( int flag ) - { - CompactInfo info = LookupCompactInfo(); + Delta(ItemDelta.Update); - if ( info == null ) - return false; + OnMapChange(); - return ( (info.m_TempFlags & flag) != 0 ); - } + if (old == null || old == Map.Internal) + InvalidateProperties(); + } + } + } - public void SetTempFlag( int flag, bool value ) - { - CompactInfo info = AcquireCompactInfo(); + public void ProcessDelta() + { + ItemDelta flags = m_DeltaFlags; - if ( value ) - info.m_TempFlags |= flag; - else - info.m_TempFlags &= ~flag; + SetFlag(ImplFlag.InQueue, false); + m_DeltaFlags = ItemDelta.None; - if ( info.m_TempFlags == 0 ) - VerifyCompactInfo(); - } + Map map = m_Map; - public bool GetSavedFlag( int flag ) - { - CompactInfo info = LookupCompactInfo(); + if (map != null && !Deleted) + { + bool sendOPLUpdate = ObjectPropertyList.Enabled && (flags & ItemDelta.Properties) != 0; - if ( info == null ) - return false; + if (m_Parent is Container contParent && !contParent.IsPublicContainer) + if ((flags & ItemDelta.Update) != 0) + { + Point3D worldLoc = GetWorldLocation(); - return ( ( info.m_SavedFlags & flag ) != 0 ); - } + Mobile rootParent = contParent.RootParent as Mobile; + Mobile tradeRecip = null; - public void SetSavedFlag( int flag, bool value ) - { - CompactInfo info = AcquireCompactInfo(); + if (rootParent != null) + { + NetState ns = rootParent.NetState; - if ( value ) - info.m_SavedFlags |= flag; - else - info.m_SavedFlags &= ~flag; + if (ns != null) + if (rootParent.CanSee(this) && rootParent.InRange(worldLoc, GetUpdateRange(rootParent))) + { + if (ns.ContainerGridLines) + ns.Send(new ContainerContentUpdate6017(this)); + else + ns.Send(new ContainerContentUpdate(this)); + + if (ObjectPropertyList.Enabled) + ns.Send(OPLPacket); + } + } + + SecureTradeContainer stc = GetSecureTradeCont(); + + SecureTrade st = stc?.Trade; + + if (st != null) + { + Mobile test = st.From.Mobile; + + if (test != null && test != rootParent) + tradeRecip = test; + + test = st.To.Mobile; + + if (test != null && test != rootParent) + tradeRecip = test; + + NetState ns = tradeRecip?.NetState; + + if (ns != null) + if (tradeRecip.CanSee(this) && tradeRecip.InRange(worldLoc, GetUpdateRange(tradeRecip))) + { + if (ns.ContainerGridLines) + ns.Send(new ContainerContentUpdate6017(this)); + else + ns.Send(new ContainerContentUpdate(this)); + + if (ObjectPropertyList.Enabled) + ns.Send(OPLPacket); + } + } + + List openers = contParent.Openers; + + if (openers != null) + lock (openers) + { + for (int i = 0; i < openers.Count; ++i) + { + Mobile mob = openers[i]; + + int range = GetUpdateRange(mob); + + if (mob.Map != map || !mob.InRange(worldLoc, range)) + { + openers.RemoveAt(i--); + } + else + { + if (mob == rootParent || mob == tradeRecip) + continue; + + NetState ns = mob.NetState; + + if (ns != null) + if (mob.CanSee(this)) + { + if (ns.ContainerGridLines) + ns.Send(new ContainerContentUpdate6017(this)); + else + ns.Send(new ContainerContentUpdate(this)); + + if (ObjectPropertyList.Enabled) + ns.Send(OPLPacket); + } + } + } + + if (openers.Count == 0) + contParent.Openers = null; + } + + return; + } + + if ((flags & ItemDelta.Update) != 0) + { + Packet p = null; + Point3D worldLoc = GetWorldLocation(); + + IPooledEnumerable eable = map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.CanSee(this) && m.InRange(worldLoc, GetUpdateRange(m))) + { + if (m_Parent == null) + { + SendInfoTo(state, ObjectPropertyList.Enabled); + } + else + { + if (p == null) + { + if (m_Parent is Item) + { + if (state.ContainerGridLines) + state.Send(new ContainerContentUpdate6017(this)); + else + state.Send(new ContainerContentUpdate(this)); + } + else if (m_Parent is Mobile) + { + p = new EquipUpdate(this); + p.Acquire(); + + state.Send(p); + } + } + else + { + state.Send(p); + } + + if (ObjectPropertyList.Enabled) state.Send(OPLPacket); + } + } + } + + if (p != null) + Packet.Release(p); + + eable.Free(); + sendOPLUpdate = false; + } + else if ((flags & ItemDelta.EquipOnly) != 0) + { + if (m_Parent is Mobile) + { + Packet p = null; + Point3D worldLoc = GetWorldLocation(); + + IPooledEnumerable eable = map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.CanSee(this) && m.InRange(worldLoc, GetUpdateRange(m))) + { + //if ( sendOPLUpdate ) + // state.Send( RemovePacket ); + + if (p == null) + p = Packet.Acquire(new EquipUpdate(this)); + + state.Send(p); + + if (ObjectPropertyList.Enabled) + state.Send(OPLPacket); + } + } + + Packet.Release(p); + + eable.Free(); + sendOPLUpdate = false; + } + } + + if (sendOPLUpdate) + { + Point3D worldLoc = GetWorldLocation(); + IPooledEnumerable eable = map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.CanSee(this) && m.InRange(worldLoc, GetUpdateRange(m))) + state.Send(OPLPacket); + } + + eable.Free(); + } + } + } + + public virtual void Delete() + { + if (Deleted) + return; + + if (!World.OnDelete(this)) + return; + + OnDelete(); + + List items = LookupItems(); + + if (items != null) + for (int i = items.Count - 1; i >= 0; --i) + if (i < items.Count) + items[i].OnParentDeleted(this); + + SendRemovePacket(); + + SetFlag(ImplFlag.Deleted, true); + + if (Parent is Mobile mobile) + mobile.RemoveItem(this); + else if (Parent is Item item) + item.RemoveItem(this); + + ClearBounce(); + + if (m_Map != null) + { + if (m_Parent == null) + m_Map.OnLeave(this); + m_Map = null; + } + + World.RemoveItem(this); + + OnAfterDelete(); + + FreeCache(); + } + + [CommandProperty(AccessLevel.Counselor)] + public Serial Serial{ get; } + + public virtual int HuedItemID => m_ItemID; + + int ISerializable.TypeReference => m_TypeRef; + + int ISerializable.SerialIdentity => Serial; + + public virtual void Serialize(GenericWriter writer) + { + writer.Write(9); // version + + SaveFlag flags = SaveFlag.None; + + int x = m_Location.m_X, y = m_Location.m_Y, z = m_Location.m_Z; + + if (x != 0 || y != 0 || z != 0) + { + if (x >= short.MinValue && x <= short.MaxValue && y >= short.MinValue && y <= short.MaxValue && + z >= sbyte.MinValue && z <= sbyte.MaxValue) + { + if (x != 0 || y != 0) + { + if (x >= byte.MinValue && x <= byte.MaxValue && y >= byte.MinValue && y <= byte.MaxValue) + flags |= SaveFlag.LocationByteXY; + else + flags |= SaveFlag.LocationShortXY; + } + + if (z != 0) + flags |= SaveFlag.LocationSByteZ; + } + else + { + flags |= SaveFlag.LocationFull; + } + } + + CompactInfo info = LookupCompactInfo(); + List items = LookupItems(); + + if (m_Direction != Direction.North) + flags |= SaveFlag.Direction; + if (info?.m_Bounce != null) + flags |= SaveFlag.Bounce; + if (m_LootType != LootType.Regular) + flags |= SaveFlag.LootType; + if (m_ItemID != 0) + flags |= SaveFlag.ItemID; + if (m_Hue != 0) + flags |= SaveFlag.Hue; + if (m_Amount != 1) + flags |= SaveFlag.Amount; + if (m_Layer != Layer.Invalid) + flags |= SaveFlag.Layer; + if (info?.m_Name != null) + flags |= SaveFlag.Name; + if (m_Parent != null) + flags |= SaveFlag.Parent; + if (items != null && items.Count > 0) + flags |= SaveFlag.Items; + if (m_Map != Map.Internal) + flags |= SaveFlag.Map; + //if ( m_InsuredFor != null && !m_InsuredFor.Deleted ) + //flags |= SaveFlag.InsuredFor; + + if (info != null) + { + if (info.m_BlessedFor != null && !info.m_BlessedFor.Deleted) + flags |= SaveFlag.BlessedFor; + if (info.m_HeldBy != null && !info.m_HeldBy.Deleted) + flags |= SaveFlag.HeldBy; + if (info.m_SavedFlags != 0) + flags |= SaveFlag.SavedFlags; + } + + if (info == null || info.m_Weight == -1) + { + flags |= SaveFlag.NullWeight; + } + else + { + if (info.m_Weight == 0.0) + { + flags |= SaveFlag.WeightIs0; + } + else if (info.m_Weight != 1.0) + { + if (info.m_Weight == (int)info.m_Weight) + flags |= SaveFlag.IntWeight; + else + flags |= SaveFlag.WeightNot1or0; + } + } + + ImplFlag implFlags = m_Flags & (ImplFlag.Visible | ImplFlag.Movable | ImplFlag.Stackable | ImplFlag.Insured | + ImplFlag.PaidInsurance | ImplFlag.QuestItem); + + if (implFlags != (ImplFlag.Visible | ImplFlag.Movable)) + flags |= SaveFlag.ImplFlags; + + writer.Write((int)flags); + + /* begin last moved time optimization */ + long ticks = LastMoved.Ticks; + long now = DateTime.UtcNow.Ticks; + + TimeSpan d; + + try + { + d = new TimeSpan(ticks - now); + } + catch + { + if (ticks < now) d = TimeSpan.MaxValue; + else d = TimeSpan.MaxValue; + } + + double minutes = -d.TotalMinutes; + + if (minutes < int.MinValue) + minutes = int.MinValue; + else if (minutes > int.MaxValue) + minutes = int.MaxValue; + + writer.WriteEncodedInt((int)minutes); + /* end */ + + if (GetSaveFlag(flags, SaveFlag.Direction)) + writer.Write((byte)m_Direction); + + if (GetSaveFlag(flags, SaveFlag.Bounce)) + BounceInfo.Serialize(info.m_Bounce, writer); + + if (GetSaveFlag(flags, SaveFlag.LootType)) + writer.Write((byte)m_LootType); + + if (GetSaveFlag(flags, SaveFlag.LocationFull)) + { + writer.WriteEncodedInt(x); + writer.WriteEncodedInt(y); + writer.WriteEncodedInt(z); + } + else + { + if (GetSaveFlag(flags, SaveFlag.LocationByteXY)) + { + writer.Write((byte)x); + writer.Write((byte)y); + } + else if (GetSaveFlag(flags, SaveFlag.LocationShortXY)) + { + writer.Write((short)x); + writer.Write((short)y); + } + + if (GetSaveFlag(flags, SaveFlag.LocationSByteZ)) + writer.Write((sbyte)z); + } + + if (GetSaveFlag(flags, SaveFlag.ItemID)) + writer.WriteEncodedInt(m_ItemID); + + if (GetSaveFlag(flags, SaveFlag.Hue)) + writer.WriteEncodedInt(m_Hue); + + if (GetSaveFlag(flags, SaveFlag.Amount)) + writer.WriteEncodedInt(m_Amount); + + if (GetSaveFlag(flags, SaveFlag.Layer)) + writer.Write((byte)m_Layer); + + if (GetSaveFlag(flags, SaveFlag.Name)) + writer.Write(info.m_Name); + + if (GetSaveFlag(flags, SaveFlag.Parent)) + { + if (m_Parent != null && !m_Parent.Deleted) + writer.Write(m_Parent.Serial); + else + writer.Write(Serial.MinusOne); + } + + if (GetSaveFlag(flags, SaveFlag.Items)) + writer.Write(items, false); + + if (GetSaveFlag(flags, SaveFlag.IntWeight)) + writer.WriteEncodedInt((int)info.m_Weight); + else if (GetSaveFlag(flags, SaveFlag.WeightNot1or0)) + writer.Write(info.m_Weight); - if ( info.m_SavedFlags == 0 ) - VerifyCompactInfo(); - } - - public virtual void Deserialize( GenericReader reader ) - { - int version = reader.ReadInt(); - - SetLastMoved(); - - switch ( version ) - { - case 9: - case 8: - case 7: - case 6: - { - SaveFlag flags = (SaveFlag)reader.ReadInt(); - - if ( version < 7 ) - { - LastMoved = reader.ReadDeltaTime(); - } - else - { - int minutes = reader.ReadEncodedInt(); - - try{ LastMoved = DateTime.UtcNow - TimeSpan.FromMinutes( minutes ); } - catch{ LastMoved = DateTime.UtcNow; } - } - - if ( GetSaveFlag( flags, SaveFlag.Direction ) ) - m_Direction = (Direction)reader.ReadByte(); - - if ( GetSaveFlag( flags, SaveFlag.Bounce ) ) - AcquireCompactInfo().m_Bounce = BounceInfo.Deserialize( reader ); - - if ( GetSaveFlag( flags, SaveFlag.LootType ) ) - m_LootType = (LootType)reader.ReadByte(); - - int x = 0, y = 0, z = 0; - - if ( GetSaveFlag( flags, SaveFlag.LocationFull ) ) - { - x = reader.ReadEncodedInt(); - y = reader.ReadEncodedInt(); - z = reader.ReadEncodedInt(); - } - else - { - if ( GetSaveFlag( flags, SaveFlag.LocationByteXY ) ) - { - x = reader.ReadByte(); - y = reader.ReadByte(); - } - else if ( GetSaveFlag( flags, SaveFlag.LocationShortXY ) ) - { - x = reader.ReadShort(); - y = reader.ReadShort(); - } - - if ( GetSaveFlag( flags, SaveFlag.LocationSByteZ ) ) - z = reader.ReadSByte(); - } - - m_Location = new Point3D( x, y, z ); - - if ( GetSaveFlag( flags, SaveFlag.ItemID ) ) - m_ItemID = reader.ReadEncodedInt(); - - if ( GetSaveFlag( flags, SaveFlag.Hue ) ) - m_Hue = reader.ReadEncodedInt(); - - if ( GetSaveFlag( flags, SaveFlag.Amount ) ) - m_Amount = reader.ReadEncodedInt(); - else - m_Amount = 1; - - if ( GetSaveFlag( flags, SaveFlag.Layer ) ) - m_Layer = (Layer)reader.ReadByte(); - - if ( GetSaveFlag( flags, SaveFlag.Name ) ) - { - string name = reader.ReadString(); - - if ( name != DefaultName ) - AcquireCompactInfo().m_Name = name; - } - - if ( GetSaveFlag( flags, SaveFlag.Parent ) ) - { - Serial parent = reader.ReadInt(); - - if ( parent.IsMobile ) - m_Parent = World.FindMobile( parent ); - else if ( parent.IsItem ) - m_Parent = World.FindItem( parent ); - else - m_Parent = null; - - if ( m_Parent == null && (parent.IsMobile || parent.IsItem) ) - Delete(); - } - - if ( GetSaveFlag( flags, SaveFlag.Items ) ) - { - List items = reader.ReadStrongItemList(); - - if ( this is Container ) - ( this as Container ).m_Items = items; - else - AcquireCompactInfo().m_Items = items; - } - - if ( version < 8 || !GetSaveFlag( flags, SaveFlag.NullWeight ) ) - { - double weight; - - if ( GetSaveFlag( flags, SaveFlag.IntWeight ) ) - weight = reader.ReadEncodedInt(); - else if ( GetSaveFlag( flags, SaveFlag.WeightNot1or0 ) ) - weight = reader.ReadDouble(); - else if ( GetSaveFlag( flags, SaveFlag.WeightIs0 ) ) - weight = 0.0; - else - weight = 1.0; - - if ( weight != DefaultWeight ) - AcquireCompactInfo().m_Weight = weight; - } - - if ( GetSaveFlag( flags, SaveFlag.Map ) ) - m_Map = reader.ReadMap(); - else - m_Map = Map.Internal; - - if ( GetSaveFlag( flags, SaveFlag.Visible ) ) - SetFlag( ImplFlag.Visible, reader.ReadBool() ); - else - SetFlag( ImplFlag.Visible, true ); - - if ( GetSaveFlag( flags, SaveFlag.Movable ) ) - SetFlag( ImplFlag.Movable, reader.ReadBool() ); - else - SetFlag( ImplFlag.Movable, true ); - - if ( GetSaveFlag( flags, SaveFlag.Stackable ) ) - SetFlag( ImplFlag.Stackable, reader.ReadBool() ); - - if ( GetSaveFlag( flags, SaveFlag.ImplFlags ) ) - m_Flags = (ImplFlag)reader.ReadEncodedInt(); - - if ( GetSaveFlag( flags, SaveFlag.InsuredFor ) ) - /*m_InsuredFor = */reader.ReadMobile(); - - if ( GetSaveFlag( flags, SaveFlag.BlessedFor ) ) - AcquireCompactInfo().m_BlessedFor = reader.ReadMobile(); - - if ( GetSaveFlag( flags, SaveFlag.HeldBy ) ) - AcquireCompactInfo().m_HeldBy = reader.ReadMobile(); - - if ( GetSaveFlag( flags, SaveFlag.SavedFlags ) ) - AcquireCompactInfo().m_SavedFlags = reader.ReadEncodedInt(); - - if ( m_Map != null && m_Parent == null ) - m_Map.OnEnter( this ); - - break; - } - case 5: - { - SaveFlag flags = (SaveFlag)reader.ReadInt(); - - LastMoved = reader.ReadDeltaTime(); - - if ( GetSaveFlag( flags, SaveFlag.Direction ) ) - m_Direction = (Direction)reader.ReadByte(); - - if ( GetSaveFlag( flags, SaveFlag.Bounce ) ) - AcquireCompactInfo().m_Bounce = BounceInfo.Deserialize( reader ); - - if ( GetSaveFlag( flags, SaveFlag.LootType ) ) - m_LootType = (LootType)reader.ReadByte(); - - if ( GetSaveFlag( flags, SaveFlag.LocationFull ) ) - m_Location = reader.ReadPoint3D(); - - if ( GetSaveFlag( flags, SaveFlag.ItemID ) ) - m_ItemID = reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.Hue ) ) - m_Hue = reader.ReadInt(); - - if ( GetSaveFlag( flags, SaveFlag.Amount ) ) - m_Amount = reader.ReadInt(); - else - m_Amount = 1; - - if ( GetSaveFlag( flags, SaveFlag.Layer ) ) - m_Layer = (Layer)reader.ReadByte(); - - if ( GetSaveFlag( flags, SaveFlag.Name ) ) - { - string name = reader.ReadString(); - - if ( name != DefaultName ) - AcquireCompactInfo().m_Name = name; - } - - if ( GetSaveFlag( flags, SaveFlag.Parent ) ) - { - Serial parent = reader.ReadInt(); - - if ( parent.IsMobile ) - m_Parent = World.FindMobile( parent ); - else if ( parent.IsItem ) - m_Parent = World.FindItem( parent ); - else - m_Parent = null; - - if ( m_Parent == null && (parent.IsMobile || parent.IsItem) ) - Delete(); - } - - if ( GetSaveFlag( flags, SaveFlag.Items ) ) - { - List items = reader.ReadStrongItemList(); - - if ( this is Container ) - ( this as Container ).m_Items = items; - else - AcquireCompactInfo().m_Items = items; - } - - double weight; - - if ( GetSaveFlag( flags, SaveFlag.IntWeight ) ) - weight = reader.ReadEncodedInt(); - else if ( GetSaveFlag( flags, SaveFlag.WeightNot1or0 ) ) - weight = reader.ReadDouble(); - else if ( GetSaveFlag( flags, SaveFlag.WeightIs0 ) ) - weight = 0.0; - else - weight = 1.0; - - if ( weight != DefaultWeight ) - AcquireCompactInfo().m_Weight = weight; - - if ( GetSaveFlag( flags, SaveFlag.Map ) ) - m_Map = reader.ReadMap(); - else - m_Map = Map.Internal; - - if ( GetSaveFlag( flags, SaveFlag.Visible ) ) - SetFlag( ImplFlag.Visible, reader.ReadBool() ); - else - SetFlag( ImplFlag.Visible, true ); - - if ( GetSaveFlag( flags, SaveFlag.Movable ) ) - SetFlag( ImplFlag.Movable, reader.ReadBool() ); - else - SetFlag( ImplFlag.Movable, true ); - - if ( GetSaveFlag( flags, SaveFlag.Stackable ) ) - SetFlag( ImplFlag.Stackable, reader.ReadBool() ); - - if ( m_Map != null && m_Parent == null ) - m_Map.OnEnter( this ); - - break; - } - case 4: // Just removed variables - case 3: - { - m_Direction = (Direction)reader.ReadInt(); - - goto case 2; - } - case 2: - { - AcquireCompactInfo().m_Bounce = BounceInfo.Deserialize( reader ); - LastMoved = reader.ReadDeltaTime(); - - goto case 1; - } - case 1: - { - m_LootType = (LootType) reader.ReadByte();//m_Newbied = reader.ReadBool(); - - goto case 0; - } - case 0: - { - m_Location = reader.ReadPoint3D(); - m_ItemID = reader.ReadInt(); - m_Hue = reader.ReadInt(); - m_Amount = reader.ReadInt(); - m_Layer = (Layer) reader.ReadByte(); - - string name = reader.ReadString(); - - if ( name != DefaultName ) - AcquireCompactInfo().m_Name = name; - - Serial parent = reader.ReadInt(); - - if ( parent.IsMobile ) - m_Parent = World.FindMobile( parent ); - else if ( parent.IsItem ) - m_Parent = World.FindItem( parent ); - else - m_Parent = null; - - if ( m_Parent == null && (parent.IsMobile || parent.IsItem) ) - Delete(); - - int count = reader.ReadInt(); - - if ( count > 0 ) - { - List items = new List( count ); - - for ( int i = 0; i < count; ++i ) - { - Item item = reader.ReadItem(); - - if ( item != null ) - items.Add( item ); - } - - if ( this is Container ) - ( this as Container ).m_Items = items; - else - AcquireCompactInfo().m_Items = items; - } - - double weight = reader.ReadDouble(); - - if ( weight != DefaultWeight ) - AcquireCompactInfo().m_Weight = weight; - - if ( version <= 3 ) - { - reader.ReadInt(); - reader.ReadInt(); - reader.ReadInt(); - } - - m_Map = reader.ReadMap(); - SetFlag( ImplFlag.Visible, reader.ReadBool() ); - SetFlag( ImplFlag.Movable, reader.ReadBool() ); - - if ( version <= 3 ) - /*m_Deleted =*/ reader.ReadBool(); - - Stackable = reader.ReadBool(); - - if ( m_Map != null && m_Parent == null ) - m_Map.OnEnter( this ); - - break; - } - } - - if ( HeldBy != null ) - Timer.DelayCall( TimeSpan.Zero, FixHolding_Sandbox ); - - //if ( version < 9 ) - VerifyCompactInfo(); - } - - private void FixHolding_Sandbox() - { - Mobile heldBy = HeldBy; - - if ( heldBy != null ) - { - if ( GetBounce() != null ) - { - Bounce( heldBy ); - } - else - { - heldBy.Holding = null; - heldBy.AddToBackpack( this ); - ClearBounce(); - } - } - } - - public virtual int GetMaxUpdateRange() - { - return 18; - } - - public virtual int GetUpdateRange( Mobile m ) - { - return 18; - } - - public void SendInfoTo( NetState state ) { - SendInfoTo( state, ObjectPropertyList.Enabled ); - } - - public virtual void SendInfoTo( NetState state, bool sendOplPacket ) { - state.Send( GetWorldPacketFor( state ) ); - - if ( sendOplPacket ) { - state.Send( OPLPacket ); - } - } - - protected virtual Packet GetWorldPacketFor( NetState state ) { - if ( state.HighSeas ) - return WorldPacketHS; - if ( state.StygianAbyss ) - return WorldPacketSA; - return WorldPacket; - } - - public virtual bool IsVirtualItem => false; - - public virtual int GetTotal( TotalType type ) - { - return 0; - } - - public virtual void UpdateTotal( Item sender, TotalType type, int delta ) - { - if ( !IsVirtualItem ) - { - if ( m_Parent is Item item ) - item.UpdateTotal( sender, type, delta ); - else if ( m_Parent is Mobile mobile ) - mobile.UpdateTotal( sender, type, delta ); - else - { - HeldBy?.UpdateTotal( sender, type, delta ); - } - } - } - - public virtual void UpdateTotals() - { - } - - public virtual int LabelNumber - { - get - { - if ( m_ItemID < 0x4000 ) - return 1020000 + m_ItemID; - - return 1078872 + m_ItemID; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int TotalGold => GetTotal( TotalType.Gold ); - - [CommandProperty( AccessLevel.GameMaster )] - public int TotalItems => GetTotal( TotalType.Items ); - - [CommandProperty( AccessLevel.GameMaster )] - public int TotalWeight => GetTotal( TotalType.Weight ); - - public virtual double DefaultWeight - { - get - { - if ( m_ItemID < 0 || m_ItemID > TileData.MaxItemValue || this is BaseMulti ) - return 0; - - int weight = TileData.ItemTable[m_ItemID].Weight; - - if ( weight == 255 || weight == 0 ) - weight = 1; - - return weight; - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public double Weight - { - get - { - CompactInfo info = LookupCompactInfo(); - - if ( info != null && info.m_Weight != -1 ) - return info.m_Weight; - - return DefaultWeight; - } - set - { - if ( Weight != value ) - { - CompactInfo info = AcquireCompactInfo(); - - int oldPileWeight = PileWeight; - - info.m_Weight = value; - - if ( info.m_Weight == -1 ) - VerifyCompactInfo(); - - int newPileWeight = PileWeight; - - UpdateTotal( this, TotalType.Weight, newPileWeight - oldPileWeight ); - - InvalidateProperties(); - } - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int PileWeight => (int)Math.Ceiling( Weight * Amount ); - - public virtual int HuedItemID => m_ItemID; - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public virtual int Hue - { - get => m_Hue; - set - { - if ( m_Hue != value ) - { - m_Hue = value; - ReleaseWorldPackets(); - - Delta( ItemDelta.Update ); - } - } - } - - public const int QuestItemHue = 0x4EA; // Hmmmm... "for EA"? - - public virtual bool Nontransferable => QuestItem; - - public virtual void HandleInvalidTransfer( Mobile from ) - { - // OSI sends 1074769, bug! - if ( QuestItem ) - from.SendLocalizedMessage( 1049343 ); // You can only drop quest items into the top-most level of your backpack while you still need them for your quest. - } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual Layer Layer - { - get => m_Layer; - set - { - if ( m_Layer != value ) - { - m_Layer = value; - - Delta( ItemDelta.EquipOnly ); - } - } - } - - public List Items - { - get - { - List items = LookupItems(); - - if ( items == null ) - items = EmptyItems; - - return items; - } - } - - [CommandProperty(AccessLevel.GameMaster)] - public IEntity RootParent - { - get - { - IEntity p = m_Parent; - - while ( p is Item ) - { - Item item = (Item)p; - - if ( item.m_Parent == null ) - { - break; - } - - p = item.m_Parent; - } - - return p; - } - } - - public bool ParentsContain() where T : Item - { - IEntity p = m_Parent; - - while( p is Item ) - { - if ( p is T ) - return true; - - Item item = (Item)p; - - if ( item.m_Parent == null ) - { - break; - } - - p = item.m_Parent; - } - - return false; - } - - public virtual void AddItem( Item item ) - { - if ( item == null || item.Deleted || item.m_Parent == this ) - { - return; - } - - if ( item == this ) - { - Console.WriteLine( "Warning: Adding item to itself: [0x{0:X} {1}].AddItem( [0x{2:X} {3}] )", Serial.Value, GetType().Name, item.Serial.Value, item.GetType().Name ); - Console.WriteLine( new System.Diagnostics.StackTrace() ); - return; - } - - if ( IsChildOf( item ) ) - { - Console.WriteLine( "Warning: Adding parent item to child: [0x{0:X} {1}].AddItem( [0x{2:X} {3}] )", Serial.Value, GetType().Name, item.Serial.Value, item.GetType().Name ); - Console.WriteLine( new System.Diagnostics.StackTrace() ); - return; - } - - if ( item.m_Parent is Mobile parentMobile ) - { - parentMobile.RemoveItem( item ); - } - else if ( item.m_Parent is Item parentItem ) - { - parentItem.RemoveItem( item ); - } - else - { - item.SendRemovePacket(); - } - - item.Parent = this; - item.Map = m_Map; - - List items = AcquireItems(); - - items.Add( item ); - - if ( !item.IsVirtualItem ) - { - UpdateTotal( item, TotalType.Gold, item.TotalGold ); - UpdateTotal( item, TotalType.Items, item.TotalItems + 1 ); - UpdateTotal( item, TotalType.Weight, item.TotalWeight + item.PileWeight ); - } - - item.Delta( ItemDelta.Update ); - - item.OnAdded( this ); - OnItemAdded( item ); - } - - private static List m_DeltaQueue = new List(); - - public void Delta( ItemDelta flags ) - { - if ( m_Map == null || m_Map == Map.Internal ) - return; - - m_DeltaFlags |= flags; - - if ( !GetFlag( ImplFlag.InQueue ) ) - { - SetFlag( ImplFlag.InQueue, true ); - - if (_processing) { - try { - using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) { - op.WriteLine("# {0}", DateTime.UtcNow); - op.WriteLine(new System.Diagnostics.StackTrace()); - op.WriteLine(); - } - } catch { } - } else { - m_DeltaQueue.Add(this); - } - } - - Core.Set(); - } - - public void RemDelta( ItemDelta flags ) - { - m_DeltaFlags &= ~flags; - - if ( GetFlag( ImplFlag.InQueue ) && m_DeltaFlags == ItemDelta.None ) - { - SetFlag( ImplFlag.InQueue, false ); - - if (_processing) { - try { - using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) { - op.WriteLine("# {0}", DateTime.UtcNow); - op.WriteLine(new System.Diagnostics.StackTrace()); - op.WriteLine(); - } - } catch { } - } else { - m_DeltaQueue.Remove( this ); - } - } - } - - public bool NoMoveHS { get; set; } - - public void ProcessDelta() - { - ItemDelta flags = m_DeltaFlags; - - SetFlag( ImplFlag.InQueue, false ); - m_DeltaFlags = ItemDelta.None; - - Map map = m_Map; - - if ( map != null && !Deleted ) - { - bool sendOPLUpdate = ObjectPropertyList.Enabled && (flags & ItemDelta.Properties) != 0; - - if ( m_Parent is Container contParent && !contParent.IsPublicContainer ) - { - if ( (flags & ItemDelta.Update) != 0 ) - { - Point3D worldLoc = GetWorldLocation(); - - Mobile rootParent = contParent.RootParent as Mobile; - Mobile tradeRecip = null; - - if ( rootParent != null ) - { - NetState ns = rootParent.NetState; - - if ( ns != null ) - { - if ( rootParent.CanSee( this ) && rootParent.InRange( worldLoc, GetUpdateRange( rootParent ) ) ) - { - if ( ns.ContainerGridLines ) - ns.Send( new ContainerContentUpdate6017( this ) ); - else - ns.Send( new ContainerContentUpdate( this ) ); - - if ( ObjectPropertyList.Enabled ) - ns.Send( OPLPacket ); - } - } - } - - SecureTradeContainer stc = GetSecureTradeCont(); - - SecureTrade st = stc?.Trade; - - if ( st != null ) - { - Mobile test = st.From.Mobile; - - if ( test != null && test != rootParent ) - tradeRecip = test; - - test = st.To.Mobile; - - if ( test != null && test != rootParent ) - tradeRecip = test; - - NetState ns = tradeRecip?.NetState; - - if ( ns != null ) - { - if ( tradeRecip.CanSee( this ) && tradeRecip.InRange( worldLoc, GetUpdateRange( tradeRecip ) ) ) - { - if ( ns.ContainerGridLines ) - ns.Send( new ContainerContentUpdate6017( this ) ); - else - ns.Send( new ContainerContentUpdate( this ) ); - - if ( ObjectPropertyList.Enabled ) - ns.Send( OPLPacket ); - } - } - } - - List openers = contParent.Openers; - - if ( openers != null ) - { - lock (openers) - { - for (int i = 0; i < openers.Count; ++i) - { - Mobile mob = openers[i]; - - int range = GetUpdateRange(mob); - - if (mob.Map != map || !mob.InRange(worldLoc, range)) - { - openers.RemoveAt(i--); - } - else - { - if (mob == rootParent || mob == tradeRecip) - continue; - - NetState ns = mob.NetState; - - if (ns != null) - { - if (mob.CanSee(this)) - { - if (ns.ContainerGridLines) - ns.Send(new ContainerContentUpdate6017(this)); - else - ns.Send(new ContainerContentUpdate(this)); - - if (ObjectPropertyList.Enabled) - ns.Send(OPLPacket); - } - } - } - } - - if (openers.Count == 0) - contParent.Openers = null; - } - } - return; - } - } - - if ( (flags & ItemDelta.Update) != 0 ) - { - Packet p = null; - Point3D worldLoc = GetWorldLocation(); - - IPooledEnumerable eable = map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); - - foreach ( NetState state in eable ) { - Mobile m = state.Mobile; - - if ( m.CanSee( this ) && m.InRange( worldLoc, GetUpdateRange( m ) ) ) { - if ( m_Parent == null ) { - SendInfoTo( state, ObjectPropertyList.Enabled ); - } else { - if ( p == null ) { - if ( m_Parent is Item ) { - if ( state.ContainerGridLines ) - state.Send( new ContainerContentUpdate6017( this ) ); - else - state.Send( new ContainerContentUpdate( this ) ); - } else if ( m_Parent is Mobile ) { - p = new EquipUpdate(this); - p.Acquire(); - - state.Send( p ); - } - } else { - state.Send( p ); - } - - if ( ObjectPropertyList.Enabled ) { - state.Send( OPLPacket ); - } - } - } - } - - if ( p != null ) - Packet.Release( p ); - - eable.Free(); - sendOPLUpdate = false; - } - else if ( (flags & ItemDelta.EquipOnly ) != 0 ) - { - if ( m_Parent is Mobile ) - { - Packet p = null; - Point3D worldLoc = GetWorldLocation(); - - IPooledEnumerable eable = map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); - - foreach ( NetState state in eable ) { - Mobile m = state.Mobile; - - if ( m.CanSee( this ) && m.InRange( worldLoc, GetUpdateRange( m ) ) ) - { - //if ( sendOPLUpdate ) - // state.Send( RemovePacket ); - - if ( p == null ) - p = Packet.Acquire( new EquipUpdate( this ) ); - - state.Send( p ); - - if ( ObjectPropertyList.Enabled ) - state.Send( OPLPacket ); - } - } - - Packet.Release( p ); - - eable.Free(); - sendOPLUpdate = false; - } - } - - if ( sendOPLUpdate ) - { - Point3D worldLoc = GetWorldLocation(); - IPooledEnumerable eable = map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); - - foreach ( NetState state in eable ) { - Mobile m = state.Mobile; - - if ( m.CanSee( this ) && m.InRange( worldLoc, GetUpdateRange( m ) ) ) - state.Send( OPLPacket ); - } - - eable.Free(); - } - } - } - - private static bool _processing; - - public static void ProcessDeltaQueue() - { - _processing = true; - - if (m_DeltaQueue.Count >= 512) { - Parallel.ForEach(m_DeltaQueue, i => i.ProcessDelta()); - } else { - for (int i = 0; i < m_DeltaQueue.Count; i++) m_DeltaQueue[i].ProcessDelta(); - } - - m_DeltaQueue.Clear(); - - _processing = false; - } - - public virtual void OnDelete() - { - if (Spawner != null) - { - Spawner.Remove(this); - Spawner = null; - } - } - - public virtual void OnParentDeleted( IEntity parent ) - { - Delete(); - } - - public virtual void FreeCache() - { - ReleaseWorldPackets(); - Packet.Release( ref m_RemovePacket ); - Packet.Release( ref m_OPLPacket ); - Packet.Release( ref m_PropertyList ); - } - - public virtual void Delete() - { - if ( Deleted ) - return; - - if ( !World.OnDelete( this ) ) - return; - - OnDelete(); - - List items = LookupItems(); - - if ( items != null ) - { - for ( int i = items.Count - 1; i >= 0; --i ) - { - if ( i < items.Count ) - items[i].OnParentDeleted( this ); - } - } - - SendRemovePacket(); - - SetFlag( ImplFlag.Deleted, true ); - - if ( Parent is Mobile mobile ) - mobile.RemoveItem( this ); - else if ( Parent is Item item ) - item.RemoveItem( this ); + if (GetSaveFlag(flags, SaveFlag.Map)) + writer.Write(m_Map); - ClearBounce(); - - if ( m_Map != null ) - { - if ( m_Parent == null ) - m_Map.OnLeave( this ); - m_Map = null; - } - - World.RemoveItem( this ); - - OnAfterDelete(); - - FreeCache(); - } - - public void PublicOverheadMessage( MessageType type, int hue, bool ascii, string text ) - { - if ( m_Map != null ) - { - Packet p = null; - Point3D worldLoc = GetWorldLocation(); - - IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); - - foreach ( NetState state in eable ) - { - Mobile m = state.Mobile; - - if ( m.CanSee( this ) && m.InRange( worldLoc, GetUpdateRange( m ) ) ) - { - if ( p == null ) - { - if ( ascii ) - p = new AsciiMessage( Serial, m_ItemID, type, hue, 3, Name, text ); - else - p = new UnicodeMessage( Serial, m_ItemID, type, hue, 3, "ENU", Name, text ); - - p.Acquire(); - } - - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - public void PublicOverheadMessage( MessageType type, int hue, int number ) - { - PublicOverheadMessage( type, hue, number, "" ); - } - - public void PublicOverheadMessage( MessageType type, int hue, int number, string args ) - { - if ( m_Map != null ) - { - Packet p = null; - Point3D worldLoc = GetWorldLocation(); - - IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); - - foreach ( NetState state in eable ) - { - Mobile m = state.Mobile; + if (GetSaveFlag(flags, SaveFlag.ImplFlags)) + writer.WriteEncodedInt((int)implFlags); - if ( m.CanSee( this ) && m.InRange( worldLoc, GetUpdateRange( m ) ) ) - { - if ( p == null ) - p = Packet.Acquire( new MessageLocalized( Serial, m_ItemID, type, hue, 3, number, Name, args ) ); - - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - public virtual void OnAfterDelete() - { - } - - public virtual void RemoveItem( Item item ) - { - List items = LookupItems(); - - if ( items != null && items.Contains( item ) ) - { - item.SendRemovePacket(); - - items.Remove( item ); - - if ( !item.IsVirtualItem ) - { - UpdateTotal( item, TotalType.Gold, -item.TotalGold ); - UpdateTotal( item, TotalType.Items, -( item.TotalItems + 1 ) ); - UpdateTotal( item, TotalType.Weight, -( item.TotalWeight + item.PileWeight ) ); - } - - item.Parent = null; - - item.OnRemoved( this ); - OnItemRemoved( item ); - } - } - - public virtual void OnAfterDuped( Item newItem ) - { - } - - public virtual bool OnDragLift( Mobile from ) - { - return true; - } - - public virtual bool OnEquip( Mobile from ) - { - return true; - } - - public ISpawner Spawner - { - get - { - CompactInfo info = LookupCompactInfo(); - - return info?.m_Spawner; - } - set - { - CompactInfo info = AcquireCompactInfo(); - - info.m_Spawner = value; - - if (info.m_Spawner == null) - VerifyCompactInfo(); - } - } - - public virtual void OnBeforeSpawn( Point3D location, Map m ) - { - } - - public virtual void OnAfterSpawn() - { - } - - public virtual int PhysicalResistance => 0; - public virtual int FireResistance => 0; - public virtual int ColdResistance => 0; - public virtual int PoisonResistance => 0; - public virtual int EnergyResistance => 0; - - [CommandProperty( AccessLevel.Counselor )] - public Serial Serial { get; } - - #region Location Location Location! - - public virtual void OnLocationChange( Point3D oldLocation ) - { - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public virtual Point3D Location - { - get => m_Location; - set - { - Point3D oldLocation = m_Location; - - if ( oldLocation != value ) - { - if ( m_Map != null ) - { - if ( m_Parent == null ) - { - IPooledEnumerable eable; - - if ( m_Location.m_X != 0 ) - { - eable = m_Map.GetClientsInRange( oldLocation, GetMaxUpdateRange() ); - - foreach (NetState state in eable) { - Mobile m = state.Mobile; - - if ( !m.InRange( value, GetUpdateRange( m ) ) ) { - state.Send( RemovePacket ); - } - } - - eable.Free(); - } - - Point3D oldLoc = m_Location; - m_Location = value; - ReleaseWorldPackets(); - - SetLastMoved(); - - eable = m_Map.GetClientsInRange( m_Location, GetMaxUpdateRange() ); - - foreach (NetState state in eable) { - Mobile m = state.Mobile; - - if ( m.CanSee( this ) && m.InRange( m_Location, GetUpdateRange( m ) ) && ( !state.HighSeas || !NoMoveHS || ( m_DeltaFlags & ItemDelta.Update ) != 0 || !m.InRange( oldLoc, GetUpdateRange( m ) ) ) ) - SendInfoTo( state ); - } - - eable.Free(); - - RemDelta( ItemDelta.Update ); - } - else if ( m_Parent is Item ) - { - m_Location = value; - ReleaseWorldPackets(); - - Delta( ItemDelta.Update ); - } - else - { - m_Location = value; - ReleaseWorldPackets(); - } - - if ( m_Parent == null ) - m_Map.OnMove( oldLocation, this ); - } - else - { - m_Location = value; - ReleaseWorldPackets(); - } - - OnLocationChange( oldLocation ); - } - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int X - { - get => m_Location.m_X; - set => Location = new Point3D( value, m_Location.m_Y, m_Location.m_Z ); - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Y - { - get => m_Location.m_Y; - set => Location = new Point3D( m_Location.m_X, value, m_Location.m_Z ); - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Z - { - get => m_Location.m_Z; - set => Location = new Point3D( m_Location.m_X, m_Location.m_Y, value ); - } - #endregion - - [CommandProperty( AccessLevel.GameMaster )] - public virtual int ItemID - { - get => m_ItemID; - set - { - if ( m_ItemID != value ) - { - int oldPileWeight = PileWeight; - - m_ItemID = value; - ReleaseWorldPackets(); - - int newPileWeight = PileWeight; - - UpdateTotal( this, TotalType.Weight, newPileWeight - oldPileWeight ); - - InvalidateProperties(); - Delta( ItemDelta.Update ); - } - } - } - - public virtual string DefaultName => null; - - [CommandProperty( AccessLevel.GameMaster )] - public string Name - { - get - { - CompactInfo info = LookupCompactInfo(); - - if ( info?.m_Name != null ) - return info.m_Name; - - return DefaultName; - } - set - { - if ( value == null || value != DefaultName ) - { - CompactInfo info = AcquireCompactInfo(); - - info.m_Name = value; - - if ( info.m_Name == null ) - VerifyCompactInfo(); - - InvalidateProperties(); - } - } - } - - [CommandProperty(AccessLevel.GameMaster, AccessLevel.Developer)] - public IEntity Parent - { - get => m_Parent; - set - { - if ( m_Parent == value ) - return; - - IEntity oldParent = m_Parent; - - m_Parent = value; - - if ( m_Map != null ) - { - if ( oldParent != null && m_Parent == null ) - m_Map.OnEnter( this ); - else if ( m_Parent != null ) - m_Map.OnLeave( this ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public LightType Light - { - get => (LightType)m_Direction; - set - { - if ( (LightType)m_Direction != value ) - { - m_Direction = (Direction)value; - ReleaseWorldPackets(); - - Delta( ItemDelta.Update ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Direction Direction - { - get => m_Direction; - set - { - if ( m_Direction != value ) - { - m_Direction = value; - ReleaseWorldPackets(); - - Delta( ItemDelta.Update ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Amount - { - get => m_Amount; - set - { - int oldValue = m_Amount; - - if ( oldValue != value ) - { - int oldPileWeight = PileWeight; - - m_Amount = value; - ReleaseWorldPackets(); - - int newPileWeight = PileWeight; - - UpdateTotal( this, TotalType.Weight, newPileWeight - oldPileWeight ); - - OnAmountChange( oldValue ); - - Delta( ItemDelta.Update ); - - if ( oldValue > 1 || value > 1 ) - InvalidateProperties(); - - if ( !Stackable && m_Amount > 1 ) - Console.WriteLine( "Warning: 0x{0:X}: Amount changed for non-stackable item '{2}'. ({1})", Serial.Value, m_Amount, GetType().Name ); - } - } - } - - protected virtual void OnAmountChange( int oldValue ) - { - } - - public virtual bool HandlesOnSpeech => false; - - public virtual void OnSpeech( SpeechEventArgs e ) - { - } - - public virtual bool OnDroppedToMobile( Mobile from, Mobile target ) - { - if ( Nontransferable && from.Player ) - { - HandleInvalidTransfer( from ); - return false; - } - - return true; - } - - public virtual bool DropToMobile( Mobile from, Mobile target, Point3D p ) - { - if ( Deleted || from.Deleted || target.Deleted || from.Map != target.Map || from.Map == null || target.Map == null ) - return false; - if ( from.AccessLevel < AccessLevel.GameMaster && !from.InRange( target.Location, 2 ) ) - return false; - if ( !from.CanSee( target ) || !from.InLOS( target ) ) - return false; - if ( !from.OnDroppedItemToMobile( this, target ) ) - return false; - if ( !OnDroppedToMobile( from, target ) ) - return false; - if ( !target.OnDragDrop( from, this ) ) - return false; - - return true; - } - - public virtual bool OnDroppedInto( Mobile from, Container target, Point3D p ) - { - if ( !from.OnDroppedItemInto( this, target, p ) ) - { - return false; - } - - if ( Nontransferable && from.Player && target != from.Backpack ) - { - HandleInvalidTransfer( from ); - return false; - } - - return target.OnDragDropInto( from, this, p ); - } - - public virtual bool OnDroppedOnto( Mobile from, Item target ) - { - if ( Deleted || from.Deleted || target.Deleted || from.Map != target.Map || from.Map == null || target.Map == null ) - return false; - if ( from.AccessLevel < AccessLevel.GameMaster && !from.InRange( target.GetWorldLocation(), 2 ) ) - return false; - if ( !from.CanSee( target ) || !from.InLOS( target ) ) - return false; - if ( !target.IsAccessibleTo( from ) ) - return false; - if ( !from.OnDroppedItemOnto( this, target ) ) - return false; - if ( Nontransferable && from.Player && target != from.Backpack ) - { - HandleInvalidTransfer( from ); - return false; - } - - return target.OnDragDrop( from, this ); - } - - public virtual bool DropToItem( Mobile from, Item target, Point3D p ) - { - if ( Deleted || from.Deleted || target.Deleted || from.Map != target.Map || from.Map == null || target.Map == null ) - return false; - - object root = target.RootParent; - - if ( from.AccessLevel < AccessLevel.GameMaster && !from.InRange( target.GetWorldLocation(), 2 ) ) - return false; - if ( !from.CanSee( target ) || !from.InLOS( target ) ) - return false; - if ( !target.IsAccessibleTo( from ) ) - return false; - if ( root is Mobile mobile && !mobile.CheckNonlocalDrop( from, this, target ) ) - return false; - if ( !from.OnDroppedItemToItem( this, target, p ) ) - return false; - if ( target is Container container && p.m_X != -1 && p.m_Y != -1 ) - return OnDroppedInto( from, container, p ); - - return OnDroppedOnto( from, target ); - } - - public virtual bool OnDroppedToWorld( Mobile from, Point3D p ) - { - if ( Nontransferable && from.Player ) - { - HandleInvalidTransfer( from ); - return false; - } - - return true; - } - - public virtual int GetLiftSound( Mobile from ) - { - return 0x57; - } + if (GetSaveFlag(flags, SaveFlag.InsuredFor)) + writer.Write((Mobile)null); - private static int m_OpenSlots; + if (GetSaveFlag(flags, SaveFlag.BlessedFor)) + writer.Write(info.m_BlessedFor); + + if (GetSaveFlag(flags, SaveFlag.HeldBy)) + writer.Write(info.m_HeldBy); + + if (GetSaveFlag(flags, SaveFlag.SavedFlags)) + writer.WriteEncodedInt(info.m_SavedFlags); + } + + public ISpawner Spawner + { + get + { + CompactInfo info = LookupCompactInfo(); + + return info?.m_Spawner; + } + set + { + CompactInfo info = AcquireCompactInfo(); + + info.m_Spawner = value; + + if (info.m_Spawner == null) + VerifyCompactInfo(); + } + } + + public virtual void OnBeforeSpawn(Point3D location, Map m) + { + } + + public virtual void OnAfterSpawn() + { + } + + public ExpandFlag GetExpandFlags() + { + CompactInfo info = LookupCompactInfo(); + + ExpandFlag flags = 0; - public virtual bool DropToWorld( Mobile from, Point3D p ) - { - if ( Deleted || from.Deleted || from.Map == null ) - return false; + if (info != null) + { + if (info.m_BlessedFor != null) + flags |= ExpandFlag.Blessed; - if ( !from.InRange( p, 2 ) ) - return false; + if (info.m_Bounce != null) + flags |= ExpandFlag.Bounce; - Map map = from.Map; + if (info.m_HeldBy != null) + flags |= ExpandFlag.Holder; - if ( map == null ) - return false; + if (info.m_Items != null) + flags |= ExpandFlag.Items; - int x = p.m_X, y = p.m_Y; - int z = int.MinValue; + if (info.m_Name != null) + flags |= ExpandFlag.Name; - int maxZ = from.Z + 16; + if (info.m_Spawner != null) + flags |= ExpandFlag.Spawner; - LandTile landTile = map.Tiles.GetLandTile( x, y ); - TileFlag landFlags = TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags; + if (info.m_SavedFlags != 0) + flags |= ExpandFlag.SaveFlag; - int landZ = 0, landAvg = 0, landTop = 0; - map.GetAverageZ( x, y, ref landZ, ref landAvg, ref landTop ); + if (info.m_TempFlags != 0) + flags |= ExpandFlag.TempFlag; - if ( !landTile.Ignored && (landFlags & TileFlag.Impassable) == 0 ) - { - if ( landAvg <= maxZ ) - z = landAvg; - } + if (info.m_Weight != -1) + flags |= ExpandFlag.Weight; + } - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y, true ); + return flags; + } - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + private CompactInfo LookupCompactInfo() + { + return m_CompactInfo; + } - if ( !id.Surface ) - continue; + private CompactInfo AcquireCompactInfo() + { + if (m_CompactInfo == null) + m_CompactInfo = new CompactInfo(); - int top = tile.Z + id.CalcHeight; + return m_CompactInfo; + } - if ( top > maxZ || top < z ) - continue; + private void ReleaseCompactInfo() + { + m_CompactInfo = null; + } - z = top; - } + private void VerifyCompactInfo() + { + CompactInfo info = m_CompactInfo; + + if (info == null) + return; + + bool isValid = info.m_Name != null + || info.m_Items != null + || info.m_Bounce != null + || info.m_HeldBy != null + || info.m_BlessedFor != null + || info.m_Spawner != null + || info.m_TempFlags != 0 + || info.m_SavedFlags != 0 + || info.m_Weight != -1; + + if (!isValid) + ReleaseCompactInfo(); + } + + public List LookupItems() + { + if (this is Container container) + return container.m_Items; + + CompactInfo info = LookupCompactInfo(); + + return info?.m_Items; + } + + public List AcquireItems() + { + if (this is Container cont) + { + if (cont.m_Items == null) + cont.m_Items = new List(); + + return cont.m_Items; + } + + CompactInfo info = AcquireCompactInfo(); + + if (info.m_Items == null) + info.m_Items = new List(); + + return info.m_Items; + } + + private void SetFlag(ImplFlag flag, bool value) + { + if (value) + m_Flags |= flag; + else + m_Flags &= ~flag; + } + + private bool GetFlag(ImplFlag flag) + { + return (m_Flags & flag) != 0; + } + + public BounceInfo GetBounce() + { + CompactInfo info = LookupCompactInfo(); + + return info?.m_Bounce; + } + + public void RecordBounce() + { + CompactInfo info = AcquireCompactInfo(); + + info.m_Bounce = new BounceInfo(this); + } + + public void ClearBounce() + { + CompactInfo info = LookupCompactInfo(); + + BounceInfo bounce = info?.m_Bounce; + + if (bounce != null) + { + info.m_Bounce = null; + + if (bounce.m_Parent is Item parentItem) + { + if (!parentItem.Deleted) + parentItem.OnItemBounceCleared(this); + } + else if (bounce.m_Parent is Mobile parentMobile) + { + if (!parentMobile.Deleted) + parentMobile.OnItemBounceCleared(this); + } + + VerifyCompactInfo(); + } + } + + /// + /// Overridable. Virtual event invoked when a client, , invokes a 'help request' for the Item. + /// Seemingly no longer functional in newer clients. + /// + public virtual void OnHelpRequest(Mobile from) + { + } + + /// + /// Overridable. Method checked to see if the item can be traded. + /// + /// True if the trade is allowed, false if not. + public virtual bool AllowSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when a trade has completed, either successfully or not. + /// + public virtual void OnSecureTrade(Mobile from, Mobile to, Mobile newOwner, bool accepted) + { + } + + /// + /// Overridable. Method checked to see if the elemental resistances of this Item conflict with another Item on the + /// . + /// + /// + /// + /// + /// True + /// + /// There is a confliction. The elemental resistance bonuses of this Item should not be applied to the + /// + /// + /// + /// + /// False + /// There is no confliction. The bonuses should be applied. + /// + /// + /// + public virtual bool CheckPropertyConfliction(Mobile m) + { + return false; + } + + /// + /// Overridable. Sends the object property list to . + /// + public virtual void SendPropertiesTo(Mobile from) + { + from.Send(PropertyList); + } + + /// + /// Overridable. Adds the name of this item to the given . This method should be overridden + /// if the item requires a complex naming format. + /// + public virtual void AddNameProperty(ObjectPropertyList list) + { + string name = Name; + + if (name == null) + { + if (m_Amount <= 1) + list.Add(LabelNumber); + else + list.Add(1050039, "{0}\t#{1}", m_Amount, LabelNumber); // ~1_NUMBER~ ~2_ITEMNAME~ + } + else + { + if (m_Amount <= 1) + list.Add(name); + else + list.Add(1050039, "{0}\t{1}", m_Amount, Name); // ~1_NUMBER~ ~2_ITEMNAME~ + } + } + + /// + /// Overridable. Adds the loot type of this item to the given . By default, this will be + /// either 'blessed', 'cursed', or 'insured'. + /// + public virtual void AddLootTypeProperty(ObjectPropertyList list) + { + if (m_LootType == LootType.Blessed) + list.Add(1038021); // blessed + else if (m_LootType == LootType.Cursed) + list.Add(1049643); // cursed + else if (Insured) + list.Add(1061682); // insured + } + + /// + /// Overridable. Adds any elemental resistances of this item to the given . + /// + public virtual void AddResistanceProperties(ObjectPropertyList list) + { + int v = PhysicalResistance; + + if (v != 0) + list.Add(1060448, v.ToString()); // physical resist ~1_val~% + + v = FireResistance; + + if (v != 0) + list.Add(1060447, v.ToString()); // fire resist ~1_val~% + + v = ColdResistance; + + if (v != 0) + list.Add(1060445, v.ToString()); // cold resist ~1_val~% + + v = PoisonResistance; + + if (v != 0) + list.Add(1060449, v.ToString()); // poison resist ~1_val~% + + v = EnergyResistance; + + if (v != 0) + list.Add(1060446, v.ToString()); // energy resist ~1_val~% + } + + /// + /// Overridable. Displays cliloc 1072788-1072789. + /// + public virtual void AddWeightProperty(ObjectPropertyList list) + { + int weight = PileWeight + TotalWeight; + + if (weight == 1) + list.Add(1072788, weight.ToString()); //Weight: ~1_WEIGHT~ stone + else + list.Add(1072789, weight.ToString()); //Weight: ~1_WEIGHT~ stones + } + + /// + /// Overridable. Adds header properties. By default, this invokes , + /// (if applicable), and (if + /// ). + /// + public virtual void AddNameProperties(ObjectPropertyList list) + { + AddNameProperty(list); + + if (IsSecure) + AddSecureProperty(list); + else if (IsLockedDown) + AddLockedDownProperty(list); + + Mobile blessedFor = BlessedFor; + + if (blessedFor != null && !blessedFor.Deleted) + AddBlessedForProperty(list, blessedFor); + + if (DisplayLootType) + AddLootTypeProperty(list); + + if (DisplayWeight) + AddWeightProperty(list); + + if (QuestItem) + AddQuestItemProperty(list); + + + AppendChildNameProperties(list); + } + + /// + /// Overridable. Adds the "Quest Item" property to the given . + /// + public virtual void AddQuestItemProperty(ObjectPropertyList list) + { + list.Add(1072351); // Quest Item + } + + /// + /// Overridable. Adds the "Locked Down & Secure" property to the given . + /// + public virtual void AddSecureProperty(ObjectPropertyList list) + { + list.Add(501644); // locked down & secure + } + + /// + /// Overridable. Adds the "Locked Down" property to the given . + /// + public virtual void AddLockedDownProperty(ObjectPropertyList list) + { + list.Add(501643); // locked down + } + + /// + /// Overridable. Adds the "Blessed for ~1_NAME~" property to the given . + /// + public virtual void AddBlessedForProperty(ObjectPropertyList list, Mobile m) + { + list.Add(1062203, "{0}", m.Name); // Blessed for ~1_NAME~ + } + + /// + /// Overridable. Fills an with everything applicable. By default, this invokes + /// , then Item.GetChildProperties or + /// Mobile.GetChildProperties. This method should be overridden to add any custom + /// properties. + /// + public virtual void GetProperties(ObjectPropertyList list) + { + AddNameProperties(list); + } + + /// + /// Overridable. Event invoked when a child () is building it's . + /// Recursively calls Item.GetChildProperties or + /// Mobile.GetChildProperties. + /// + public virtual void GetChildProperties(ObjectPropertyList list, Item item) + { + if (m_Parent is Item parentItem) + parentItem.GetChildProperties(list, item); + else if (m_Parent is Mobile parentMobile) + parentMobile.GetChildProperties(list, item); + } + + /// + /// Overridable. Event invoked when a child () is building it's Name + /// . Recursively calls Item.GetChildNameProperties or + /// Mobile.GetChildNameProperties. + /// + public virtual void GetChildNameProperties(ObjectPropertyList list, Item item) + { + if (m_Parent is Item parentItem) + parentItem.GetChildNameProperties(list, item); + else if (m_Parent is Mobile parentMobile) + parentMobile.GetChildNameProperties(list, item); + } + + public virtual bool IsChildVisibleTo(Mobile m, Item child) + { + return true; + } + + public void Bounce(Mobile from) + { + if (m_Parent is Item item) + item.RemoveItem(this); + else if (m_Parent is Mobile mobile) + mobile.RemoveItem(this); + + m_Parent = null; + + BounceInfo bounce = GetBounce(); + + if (bounce != null) + { + IEntity parent = bounce.m_Parent; + + if (parent == null || parent.Deleted) + { + MoveToWorld(bounce.m_WorldLoc, bounce.m_Map); + } + else if (parent is Item p) + { + IEntity root = p.RootParent; + + if (p.IsAccessibleTo(from) && + (!(root is Mobile mobileRoot) || mobileRoot.CheckNonlocalDrop(from, this, p))) + { + Location = bounce.m_Location; + p.AddItem(this); + } + else + { + MoveToWorld(from.Location, from.Map); + } + } + else if (parent is Mobile parentMobile) + { + if (!parentMobile.EquipItem(this)) + MoveToWorld(bounce.m_WorldLoc, bounce.m_Map); + } + else + { + MoveToWorld(bounce.m_WorldLoc, bounce.m_Map); + } + + ClearBounce(); + } + else + { + MoveToWorld(from.Location, from.Map); + } + } + + /// + /// Overridable. Method checked to see if this item may be equipped while casting a spell. By default, this returns false. It + /// is overridden on spellbook and spell channeling weapons or shields. + /// + /// True if it may, false if not. + /// + /// + /// public override bool AllowEquippedCast( Mobile from ) + /// { + /// if ( from.Int >= 100 ) + /// return true; + /// + /// return base.AllowEquippedCast( from ); + /// } + /// When placed in an Item script, the item may be cast when equipped if the has 100 or more + /// intelligence. Otherwise, it will drop to their backpack. + /// + public virtual bool AllowEquippedCast(Mobile from) + { + return false; + } + + public virtual bool CheckConflictingLayer(Mobile m, Item item, Layer layer) + { + return m_Layer == layer; + } + + public virtual bool CanEquip(Mobile m) + { + return m_Layer != Layer.Invalid && m.FindItemOnLayer(m_Layer) == null; + } + + public virtual void GetChildContextMenuEntries(Mobile from, List list, Item item) + { + if (m_Parent is Item parentItem) + parentItem.GetChildContextMenuEntries(from, list, item); + else if (m_Parent is Mobile parentMobile) + parentMobile.GetChildContextMenuEntries(from, list, item); + } + + public virtual void GetContextMenuEntries(Mobile from, List list) + { + if (m_Parent is Item item) + item.GetChildContextMenuEntries(from, list, this); + else if (m_Parent is Mobile mobile) + mobile.GetChildContextMenuEntries(from, list, this); + } + + public virtual bool VerifyMove(Mobile from) + { + return Movable; + } + + public virtual DeathMoveResult OnParentDeath(Mobile parent) + { + if (!Movable) + return DeathMoveResult.RemainEquipped; + if (parent.KeepsItemsOnDeath) + return DeathMoveResult.MoveToBackpack; + if (CheckBlessed(parent)) + return DeathMoveResult.MoveToBackpack; + if (CheckNewbied() && parent.Kills < 5) + return DeathMoveResult.MoveToBackpack; + if (parent.Player && Nontransferable) + return DeathMoveResult.MoveToBackpack; + + return DeathMoveResult.MoveToCorpse; + } + + public virtual DeathMoveResult OnInventoryDeath(Mobile parent) + { + if (!Movable) + return DeathMoveResult.MoveToBackpack; + if (parent.KeepsItemsOnDeath) + return DeathMoveResult.MoveToBackpack; + if (CheckBlessed(parent)) + return DeathMoveResult.MoveToBackpack; + if (CheckNewbied() && parent.Kills < 5) + return DeathMoveResult.MoveToBackpack; + if (parent.Player && Nontransferable) + return DeathMoveResult.MoveToBackpack; + + return DeathMoveResult.MoveToCorpse; + } + + /// + /// Moves the Item to . The Item does not change maps. + /// + public virtual void MoveToWorld(Point3D location) + { + MoveToWorld(location, m_Map); + } + + public void LabelTo(Mobile to, int number) + { + to.Send(new MessageLocalized(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", "")); + } + + public void LabelTo(Mobile to, int number, string args) + { + to.Send(new MessageLocalized(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", args)); + } + + public void LabelTo(Mobile to, string text) + { + to.Send(new UnicodeMessage(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, "ENU", "", text)); + } + + public void LabelTo(Mobile to, string format, params object[] args) + { + LabelTo(to, string.Format(format, args)); + } + + public void LabelToAffix(Mobile to, int number, AffixType type, string affix) + { + to.Send(new MessageLocalizedAffix(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", type, affix, "")); + } + + public void LabelToAffix(Mobile to, int number, AffixType type, string affix, string args) + { + to.Send(new MessageLocalizedAffix(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, number, "", type, affix, args)); + } + + public virtual void LabelLootTypeTo(Mobile to) + { + if (m_LootType == LootType.Blessed) + LabelTo(to, 1041362); // (blessed) + else if (m_LootType == LootType.Cursed) + LabelTo(to, "(cursed)"); + } + + public bool AtWorldPoint(int x, int y) + { + return m_Parent == null && m_Location.m_X == x && m_Location.m_Y == y; + } + + public bool AtPoint(int x, int y) + { + return m_Location.m_X == x && m_Location.m_Y == y; + } + + public virtual bool OnDecay() + { + return Decays && Parent == null && Map != Map.Internal && Region.Find(Location, Map).OnDecay(this); + } + + public void SetLastMoved() + { + LastMoved = DateTime.UtcNow; + } + + public virtual bool CanStackWith(Item dropped) + { + return dropped.Stackable && Stackable && dropped.GetType() == GetType() && dropped.ItemID == ItemID && + dropped.Hue == Hue && dropped.Name == Name && dropped.Amount + Amount <= 60000 && dropped != this; + } + + public bool StackWith(Mobile from, Item dropped) + { + return StackWith(from, dropped, true); + } + + public virtual bool StackWith(Mobile from, Item dropped, bool playSound) + { + if (CanStackWith(dropped)) + { + if (m_LootType != dropped.m_LootType) + m_LootType = LootType.Regular; + + Amount += dropped.Amount; + dropped.Delete(); + + if (playSound && from != null) + { + int soundID = GetDropSound(); + + if (soundID == -1) + soundID = 0x42; + + from.SendSound(soundID, GetWorldLocation()); + } + + return true; + } + + return false; + } + + public virtual bool OnDragDrop(Mobile from, Item dropped) + { + bool success = Parent is Container container && container.OnStackAttempt(from, this, dropped) || + StackWith(from, dropped); + + if (success && Spawner != null) + { + Spawner.Remove(this); + Spawner = null; + } + + return success; + } + + public Rectangle2D GetGraphicBounds() + { + int itemID = m_ItemID; + bool doubled = m_Amount > 1; + + if (itemID >= 0xEEA && itemID <= 0xEF2) // Are we coins? + { + int coinBase = (itemID - 0xEEA) / 3; + coinBase *= 3; + coinBase += 0xEEA; + + doubled = false; + + if (m_Amount <= 1) + itemID = coinBase; + else if (m_Amount <= 5) + itemID = coinBase + 1; + else // m_Amount > 5 + itemID = coinBase + 2; + } + + Rectangle2D bounds = ItemBounds.Table[itemID & 0x3FFF]; + + if (doubled) bounds.Set(bounds.X, bounds.Y, bounds.Width + 5, bounds.Height + 5); + + return bounds; + } + + public virtual void AppendChildProperties(ObjectPropertyList list) + { + if (m_Parent is Item item) + item.GetChildProperties(list, this); + else if (m_Parent is Mobile mobile) + mobile.GetChildProperties(list, this); + } + + public virtual void AppendChildNameProperties(ObjectPropertyList list) + { + if (m_Parent is Item item) + item.GetChildNameProperties(list, this); + else if (m_Parent is Mobile mobile) + mobile.GetChildNameProperties(list, this); + } + + public void ClearProperties() + { + Packet.Release(ref m_PropertyList); + Packet.Release(ref m_OPLPacket); + } + + public void InvalidateProperties() + { + if (!ObjectPropertyList.Enabled) + return; + + if (m_Map != null && m_Map != Map.Internal && !World.Loading) + { + ObjectPropertyList oldList = m_PropertyList; + m_PropertyList = null; + ObjectPropertyList newList = PropertyList; + + if (oldList == null || oldList.Hash != newList.Hash) + { + Packet.Release(ref m_OPLPacket); + Delta(ItemDelta.Properties); + } + } + else + { + ClearProperties(); + } + } + + public void ReleaseWorldPackets() + { + Packet.Release(ref m_WorldPacket); + Packet.Release(ref m_WorldPacketSA); + Packet.Release(ref m_WorldPacketHS); + } + + public virtual int GetPacketFlags() + { + int flags = 0; + + if (!Visible) + flags |= 0x80; + + if (Movable || ForceShowProperties) + flags |= 0x20; + + return flags; + } + + public virtual bool OnMoveOff(Mobile m) + { + return true; + } + + public virtual bool OnMoveOver(Mobile m) + { + return true; + } + + public virtual void OnMovement(Mobile m, Point3D oldLocation) + { + } + + public void Internalize() + { + MoveToWorld(Point3D.Zero, Map.Internal); + } + + public virtual void OnMapChange() + { + } + + public virtual void OnRemoved(IEntity parent) + { + } + + public virtual void OnAdded(IEntity parent) + { + } + + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } + + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } + + public IPooledEnumerable GetObjectsInRange(int range) + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + if (m_Parent == null) + return map.GetObjectsInRange(m_Location, range); + + return map.GetObjectsInRange(GetWorldLocation(), range); + } + + public IPooledEnumerable GetItemsInRange(int range) + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + if (m_Parent == null) + return map.GetItemsInRange(m_Location, range); + + return map.GetItemsInRange(GetWorldLocation(), range); + } + + public IPooledEnumerable GetMobilesInRange(int range) + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + if (m_Parent == null) + return map.GetMobilesInRange(m_Location, range); + + return map.GetMobilesInRange(GetWorldLocation(), range); + } + + public IPooledEnumerable GetClientsInRange(int range) + { + Map map = m_Map; - List items = new List(); + if (map == null) + return Map.NullEnumerable.Instance; - IPooledEnumerable eable = map.GetItemsInRange( p, 0 ); + if (m_Parent == null) + return map.GetClientsInRange(m_Location, range); - foreach ( Item item in eable ) - { - if ( item is BaseMulti || item.ItemID > TileData.MaxItemValue ) - continue; + return map.GetClientsInRange(GetWorldLocation(), range); + } + + public bool GetTempFlag(int flag) + { + CompactInfo info = LookupCompactInfo(); + + if (info == null) + return false; + + return (info.m_TempFlags & flag) != 0; + } + + public void SetTempFlag(int flag, bool value) + { + CompactInfo info = AcquireCompactInfo(); + + if (value) + info.m_TempFlags |= flag; + else + info.m_TempFlags &= ~flag; + + if (info.m_TempFlags == 0) + VerifyCompactInfo(); + } + + public bool GetSavedFlag(int flag) + { + CompactInfo info = LookupCompactInfo(); + + if (info == null) + return false; + + return (info.m_SavedFlags & flag) != 0; + } + + public void SetSavedFlag(int flag, bool value) + { + CompactInfo info = AcquireCompactInfo(); + + if (value) + info.m_SavedFlags |= flag; + else + info.m_SavedFlags &= ~flag; + + if (info.m_SavedFlags == 0) + VerifyCompactInfo(); + } + + public virtual void Deserialize(GenericReader reader) + { + int version = reader.ReadInt(); + + SetLastMoved(); + + switch (version) + { + case 9: + case 8: + case 7: + case 6: + { + SaveFlag flags = (SaveFlag)reader.ReadInt(); + + if (version < 7) + { + LastMoved = reader.ReadDeltaTime(); + } + else + { + int minutes = reader.ReadEncodedInt(); + + try + { + LastMoved = DateTime.UtcNow - TimeSpan.FromMinutes(minutes); + } + catch + { + LastMoved = DateTime.UtcNow; + } + } + + if (GetSaveFlag(flags, SaveFlag.Direction)) + m_Direction = (Direction)reader.ReadByte(); + + if (GetSaveFlag(flags, SaveFlag.Bounce)) + AcquireCompactInfo().m_Bounce = BounceInfo.Deserialize(reader); + + if (GetSaveFlag(flags, SaveFlag.LootType)) + m_LootType = (LootType)reader.ReadByte(); + + int x = 0, y = 0, z = 0; + + if (GetSaveFlag(flags, SaveFlag.LocationFull)) + { + x = reader.ReadEncodedInt(); + y = reader.ReadEncodedInt(); + z = reader.ReadEncodedInt(); + } + else + { + if (GetSaveFlag(flags, SaveFlag.LocationByteXY)) + { + x = reader.ReadByte(); + y = reader.ReadByte(); + } + else if (GetSaveFlag(flags, SaveFlag.LocationShortXY)) + { + x = reader.ReadShort(); + y = reader.ReadShort(); + } + + if (GetSaveFlag(flags, SaveFlag.LocationSByteZ)) + z = reader.ReadSByte(); + } + + m_Location = new Point3D(x, y, z); + + if (GetSaveFlag(flags, SaveFlag.ItemID)) + m_ItemID = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Hue)) + m_Hue = reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.Amount)) + m_Amount = reader.ReadEncodedInt(); + else + m_Amount = 1; + + if (GetSaveFlag(flags, SaveFlag.Layer)) + m_Layer = (Layer)reader.ReadByte(); + + if (GetSaveFlag(flags, SaveFlag.Name)) + { + string name = reader.ReadString(); + + if (name != DefaultName) + AcquireCompactInfo().m_Name = name; + } + + if (GetSaveFlag(flags, SaveFlag.Parent)) + { + Serial parent = reader.ReadInt(); + + if (parent.IsMobile) + m_Parent = World.FindMobile(parent); + else if (parent.IsItem) + m_Parent = World.FindItem(parent); + else + m_Parent = null; + + if (m_Parent == null && (parent.IsMobile || parent.IsItem)) + Delete(); + } + + if (GetSaveFlag(flags, SaveFlag.Items)) + { + List items = reader.ReadStrongItemList(); + + if (this is Container) + (this as Container).m_Items = items; + else + AcquireCompactInfo().m_Items = items; + } + + if (version < 8 || !GetSaveFlag(flags, SaveFlag.NullWeight)) + { + double weight; + + if (GetSaveFlag(flags, SaveFlag.IntWeight)) + weight = reader.ReadEncodedInt(); + else if (GetSaveFlag(flags, SaveFlag.WeightNot1or0)) + weight = reader.ReadDouble(); + else if (GetSaveFlag(flags, SaveFlag.WeightIs0)) + weight = 0.0; + else + weight = 1.0; + + if (weight != DefaultWeight) + AcquireCompactInfo().m_Weight = weight; + } + + if (GetSaveFlag(flags, SaveFlag.Map)) + m_Map = reader.ReadMap(); + else + m_Map = Map.Internal; + + if (GetSaveFlag(flags, SaveFlag.Visible)) + SetFlag(ImplFlag.Visible, reader.ReadBool()); + else + SetFlag(ImplFlag.Visible, true); + + if (GetSaveFlag(flags, SaveFlag.Movable)) + SetFlag(ImplFlag.Movable, reader.ReadBool()); + else + SetFlag(ImplFlag.Movable, true); + + if (GetSaveFlag(flags, SaveFlag.Stackable)) + SetFlag(ImplFlag.Stackable, reader.ReadBool()); + + if (GetSaveFlag(flags, SaveFlag.ImplFlags)) + m_Flags = (ImplFlag)reader.ReadEncodedInt(); + + if (GetSaveFlag(flags, SaveFlag.InsuredFor)) + /*m_InsuredFor = */ reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.BlessedFor)) + AcquireCompactInfo().m_BlessedFor = reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.HeldBy)) + AcquireCompactInfo().m_HeldBy = reader.ReadMobile(); + + if (GetSaveFlag(flags, SaveFlag.SavedFlags)) + AcquireCompactInfo().m_SavedFlags = reader.ReadEncodedInt(); + + if (m_Map != null && m_Parent == null) + m_Map.OnEnter(this); + + break; + } + case 5: + { + SaveFlag flags = (SaveFlag)reader.ReadInt(); + + LastMoved = reader.ReadDeltaTime(); + + if (GetSaveFlag(flags, SaveFlag.Direction)) + m_Direction = (Direction)reader.ReadByte(); + + if (GetSaveFlag(flags, SaveFlag.Bounce)) + AcquireCompactInfo().m_Bounce = BounceInfo.Deserialize(reader); + + if (GetSaveFlag(flags, SaveFlag.LootType)) + m_LootType = (LootType)reader.ReadByte(); + + if (GetSaveFlag(flags, SaveFlag.LocationFull)) + m_Location = reader.ReadPoint3D(); + + if (GetSaveFlag(flags, SaveFlag.ItemID)) + m_ItemID = reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.Hue)) + m_Hue = reader.ReadInt(); + + if (GetSaveFlag(flags, SaveFlag.Amount)) + m_Amount = reader.ReadInt(); + else + m_Amount = 1; + + if (GetSaveFlag(flags, SaveFlag.Layer)) + m_Layer = (Layer)reader.ReadByte(); + + if (GetSaveFlag(flags, SaveFlag.Name)) + { + string name = reader.ReadString(); + + if (name != DefaultName) + AcquireCompactInfo().m_Name = name; + } + + if (GetSaveFlag(flags, SaveFlag.Parent)) + { + Serial parent = reader.ReadInt(); + + if (parent.IsMobile) + m_Parent = World.FindMobile(parent); + else if (parent.IsItem) + m_Parent = World.FindItem(parent); + else + m_Parent = null; + + if (m_Parent == null && (parent.IsMobile || parent.IsItem)) + Delete(); + } + + if (GetSaveFlag(flags, SaveFlag.Items)) + { + List items = reader.ReadStrongItemList(); + + if (this is Container) + (this as Container).m_Items = items; + else + AcquireCompactInfo().m_Items = items; + } + + double weight; + + if (GetSaveFlag(flags, SaveFlag.IntWeight)) + weight = reader.ReadEncodedInt(); + else if (GetSaveFlag(flags, SaveFlag.WeightNot1or0)) + weight = reader.ReadDouble(); + else if (GetSaveFlag(flags, SaveFlag.WeightIs0)) + weight = 0.0; + else + weight = 1.0; + + if (weight != DefaultWeight) + AcquireCompactInfo().m_Weight = weight; + + if (GetSaveFlag(flags, SaveFlag.Map)) + m_Map = reader.ReadMap(); + else + m_Map = Map.Internal; + + if (GetSaveFlag(flags, SaveFlag.Visible)) + SetFlag(ImplFlag.Visible, reader.ReadBool()); + else + SetFlag(ImplFlag.Visible, true); + + if (GetSaveFlag(flags, SaveFlag.Movable)) + SetFlag(ImplFlag.Movable, reader.ReadBool()); + else + SetFlag(ImplFlag.Movable, true); + + if (GetSaveFlag(flags, SaveFlag.Stackable)) + SetFlag(ImplFlag.Stackable, reader.ReadBool()); + + if (m_Map != null && m_Parent == null) + m_Map.OnEnter(this); + + break; + } + case 4: // Just removed variables + case 3: + { + m_Direction = (Direction)reader.ReadInt(); + + goto case 2; + } + case 2: + { + AcquireCompactInfo().m_Bounce = BounceInfo.Deserialize(reader); + LastMoved = reader.ReadDeltaTime(); + + goto case 1; + } + case 1: + { + m_LootType = (LootType)reader.ReadByte(); //m_Newbied = reader.ReadBool(); + + goto case 0; + } + case 0: + { + m_Location = reader.ReadPoint3D(); + m_ItemID = reader.ReadInt(); + m_Hue = reader.ReadInt(); + m_Amount = reader.ReadInt(); + m_Layer = (Layer)reader.ReadByte(); + + string name = reader.ReadString(); + + if (name != DefaultName) + AcquireCompactInfo().m_Name = name; + + Serial parent = reader.ReadInt(); + + if (parent.IsMobile) + m_Parent = World.FindMobile(parent); + else if (parent.IsItem) + m_Parent = World.FindItem(parent); + else + m_Parent = null; + + if (m_Parent == null && (parent.IsMobile || parent.IsItem)) + Delete(); + + int count = reader.ReadInt(); + + if (count > 0) + { + List items = new List(count); + + for (int i = 0; i < count; ++i) + { + Item item = reader.ReadItem(); + + if (item != null) + items.Add(item); + } + + if (this is Container) + (this as Container).m_Items = items; + else + AcquireCompactInfo().m_Items = items; + } + + double weight = reader.ReadDouble(); + + if (weight != DefaultWeight) + AcquireCompactInfo().m_Weight = weight; + + if (version <= 3) + { + reader.ReadInt(); + reader.ReadInt(); + reader.ReadInt(); + } + + m_Map = reader.ReadMap(); + SetFlag(ImplFlag.Visible, reader.ReadBool()); + SetFlag(ImplFlag.Movable, reader.ReadBool()); + + if (version <= 3) + /*m_Deleted =*/ reader.ReadBool(); + + Stackable = reader.ReadBool(); + + if (m_Map != null && m_Parent == null) + m_Map.OnEnter(this); + + break; + } + } + + if (HeldBy != null) + Timer.DelayCall(TimeSpan.Zero, FixHolding_Sandbox); + + //if ( version < 9 ) + VerifyCompactInfo(); + } + + private void FixHolding_Sandbox() + { + Mobile heldBy = HeldBy; + + if (heldBy != null) + { + if (GetBounce() != null) + { + Bounce(heldBy); + } + else + { + heldBy.Holding = null; + heldBy.AddToBackpack(this); + ClearBounce(); + } + } + } + + public virtual int GetMaxUpdateRange() + { + return 18; + } + + public virtual int GetUpdateRange(Mobile m) + { + return 18; + } + + public void SendInfoTo(NetState state) + { + SendInfoTo(state, ObjectPropertyList.Enabled); + } + + public virtual void SendInfoTo(NetState state, bool sendOplPacket) + { + state.Send(GetWorldPacketFor(state)); + + if (sendOplPacket) state.Send(OPLPacket); + } + + protected virtual Packet GetWorldPacketFor(NetState state) + { + if (state.HighSeas) + return WorldPacketHS; + if (state.StygianAbyss) + return WorldPacketSA; + return WorldPacket; + } + + public virtual int GetTotal(TotalType type) + { + return 0; + } + + public virtual void UpdateTotal(Item sender, TotalType type, int delta) + { + if (!IsVirtualItem) + { + if (m_Parent is Item item) + item.UpdateTotal(sender, type, delta); + else if (m_Parent is Mobile mobile) + mobile.UpdateTotal(sender, type, delta); + else + HeldBy?.UpdateTotal(sender, type, delta); + } + } + + public virtual void UpdateTotals() + { + } + + public virtual void HandleInvalidTransfer(Mobile from) + { + // OSI sends 1074769, bug! + if (QuestItem) + from.SendLocalizedMessage( + 1049343); // You can only drop quest items into the top-most level of your backpack while you still need them for your quest. + } + + public bool ParentsContain() where T : Item + { + IEntity p = m_Parent; + + while (p is Item) + { + if (p is T) + return true; + + Item item = (Item)p; + + if (item.m_Parent == null) break; + + p = item.m_Parent; + } + + return false; + } + + public virtual void AddItem(Item item) + { + if (item == null || item.Deleted || item.m_Parent == this) return; + + if (item == this) + { + Console.WriteLine("Warning: Adding item to itself: [0x{0:X} {1}].AddItem( [0x{2:X} {3}] )", Serial.Value, + GetType().Name, item.Serial.Value, item.GetType().Name); + Console.WriteLine(new StackTrace()); + return; + } + + if (IsChildOf(item)) + { + Console.WriteLine("Warning: Adding parent item to child: [0x{0:X} {1}].AddItem( [0x{2:X} {3}] )", + Serial.Value, GetType().Name, item.Serial.Value, item.GetType().Name); + Console.WriteLine(new StackTrace()); + return; + } + + if (item.m_Parent is Mobile parentMobile) + parentMobile.RemoveItem(item); + else if (item.m_Parent is Item parentItem) + parentItem.RemoveItem(item); + else + item.SendRemovePacket(); + + item.Parent = this; + item.Map = m_Map; + + List items = AcquireItems(); + + items.Add(item); + + if (!item.IsVirtualItem) + { + UpdateTotal(item, TotalType.Gold, item.TotalGold); + UpdateTotal(item, TotalType.Items, item.TotalItems + 1); + UpdateTotal(item, TotalType.Weight, item.TotalWeight + item.PileWeight); + } + + item.Delta(ItemDelta.Update); + + item.OnAdded(this); + OnItemAdded(item); + } + + public void Delta(ItemDelta flags) + { + if (m_Map == null || m_Map == Map.Internal) + return; + + m_DeltaFlags |= flags; + + if (!GetFlag(ImplFlag.InQueue)) + { + SetFlag(ImplFlag.InQueue, true); + + if (_processing) + try + { + using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) + { + op.WriteLine("# {0}", DateTime.UtcNow); + op.WriteLine(new StackTrace()); + op.WriteLine(); + } + } + catch + { + } + else + m_DeltaQueue.Add(this); + } + + Core.Set(); + } + + public void RemDelta(ItemDelta flags) + { + m_DeltaFlags &= ~flags; + + if (GetFlag(ImplFlag.InQueue) && m_DeltaFlags == ItemDelta.None) + { + SetFlag(ImplFlag.InQueue, false); + + if (_processing) + try + { + using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) + { + op.WriteLine("# {0}", DateTime.UtcNow); + op.WriteLine(new StackTrace()); + op.WriteLine(); + } + } + catch + { + } + else + m_DeltaQueue.Remove(this); + } + } + + public static void ProcessDeltaQueue() + { + _processing = true; + + if (m_DeltaQueue.Count >= 512) + Parallel.ForEach(m_DeltaQueue, i => i.ProcessDelta()); + else + for (int i = 0; i < m_DeltaQueue.Count; i++) + m_DeltaQueue[i].ProcessDelta(); + + m_DeltaQueue.Clear(); + + _processing = false; + } + + public virtual void OnDelete() + { + if (Spawner != null) + { + Spawner.Remove(this); + Spawner = null; + } + } + + public virtual void OnParentDeleted(IEntity parent) + { + Delete(); + } + + public virtual void FreeCache() + { + ReleaseWorldPackets(); + Packet.Release(ref m_RemovePacket); + Packet.Release(ref m_OPLPacket); + Packet.Release(ref m_PropertyList); + } + + public void PublicOverheadMessage(MessageType type, int hue, bool ascii, string text) + { + if (m_Map != null) + { + Packet p = null; + Point3D worldLoc = GetWorldLocation(); + + IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.CanSee(this) && m.InRange(worldLoc, GetUpdateRange(m))) + { + if (p == null) + { + if (ascii) + p = new AsciiMessage(Serial, m_ItemID, type, hue, 3, Name, text); + else + p = new UnicodeMessage(Serial, m_ItemID, type, hue, 3, "ENU", Name, text); + + p.Acquire(); + } + + state.Send(p); + } + } + + Packet.Release(p); + + eable.Free(); + } + } + + public void PublicOverheadMessage(MessageType type, int hue, int number) + { + PublicOverheadMessage(type, hue, number, ""); + } + + public void PublicOverheadMessage(MessageType type, int hue, int number, string args) + { + if (m_Map != null) + { + Packet p = null; + Point3D worldLoc = GetWorldLocation(); + + IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.CanSee(this) && m.InRange(worldLoc, GetUpdateRange(m))) + { + if (p == null) + p = Packet.Acquire(new MessageLocalized(Serial, m_ItemID, type, hue, 3, number, Name, args)); + + state.Send(p); + } + } + + Packet.Release(p); + + eable.Free(); + } + } + + public virtual void OnAfterDelete() + { + } + + public virtual void RemoveItem(Item item) + { + List items = LookupItems(); + + if (items != null && items.Contains(item)) + { + item.SendRemovePacket(); + + items.Remove(item); + + if (!item.IsVirtualItem) + { + UpdateTotal(item, TotalType.Gold, -item.TotalGold); + UpdateTotal(item, TotalType.Items, -(item.TotalItems + 1)); + UpdateTotal(item, TotalType.Weight, -(item.TotalWeight + item.PileWeight)); + } + + item.Parent = null; + + item.OnRemoved(this); + OnItemRemoved(item); + } + } + + public virtual void OnAfterDuped(Item newItem) + { + } + + public virtual bool OnDragLift(Mobile from) + { + return true; + } + + public virtual bool OnEquip(Mobile from) + { + return true; + } + + protected virtual void OnAmountChange(int oldValue) + { + } + + public virtual void OnSpeech(SpeechEventArgs e) + { + } + + public virtual bool OnDroppedToMobile(Mobile from, Mobile target) + { + if (Nontransferable && from.Player) + { + HandleInvalidTransfer(from); + return false; + } + + return true; + } + + public virtual bool DropToMobile(Mobile from, Mobile target, Point3D p) + { + if (Deleted || from.Deleted || target.Deleted || from.Map != target.Map || from.Map == null || + target.Map == null) + return false; + if (from.AccessLevel < AccessLevel.GameMaster && !from.InRange(target.Location, 2)) + return false; + if (!from.CanSee(target) || !from.InLOS(target)) + return false; + if (!from.OnDroppedItemToMobile(this, target)) + return false; + if (!OnDroppedToMobile(from, target)) + return false; + if (!target.OnDragDrop(from, this)) + return false; + + return true; + } + + public virtual bool OnDroppedInto(Mobile from, Container target, Point3D p) + { + if (!from.OnDroppedItemInto(this, target, p)) return false; + + if (Nontransferable && from.Player && target != from.Backpack) + { + HandleInvalidTransfer(from); + return false; + } + + return target.OnDragDropInto(from, this, p); + } + + public virtual bool OnDroppedOnto(Mobile from, Item target) + { + if (Deleted || from.Deleted || target.Deleted || from.Map != target.Map || from.Map == null || + target.Map == null) + return false; + if (from.AccessLevel < AccessLevel.GameMaster && !from.InRange(target.GetWorldLocation(), 2)) + return false; + if (!from.CanSee(target) || !from.InLOS(target)) + return false; + if (!target.IsAccessibleTo(from)) + return false; + if (!from.OnDroppedItemOnto(this, target)) + return false; + if (Nontransferable && from.Player && target != from.Backpack) + { + HandleInvalidTransfer(from); + return false; + } + + return target.OnDragDrop(from, this); + } + + public virtual bool DropToItem(Mobile from, Item target, Point3D p) + { + if (Deleted || from.Deleted || target.Deleted || from.Map != target.Map || from.Map == null || + target.Map == null) + return false; + + object root = target.RootParent; + + if (from.AccessLevel < AccessLevel.GameMaster && !from.InRange(target.GetWorldLocation(), 2)) + return false; + if (!from.CanSee(target) || !from.InLOS(target)) + return false; + if (!target.IsAccessibleTo(from)) + return false; + if (root is Mobile mobile && !mobile.CheckNonlocalDrop(from, this, target)) + return false; + if (!from.OnDroppedItemToItem(this, target, p)) + return false; + if (target is Container container && p.m_X != -1 && p.m_Y != -1) + return OnDroppedInto(from, container, p); + + return OnDroppedOnto(from, target); + } + + public virtual bool OnDroppedToWorld(Mobile from, Point3D p) + { + if (Nontransferable && from.Player) + { + HandleInvalidTransfer(from); + return false; + } + + return true; + } + + public virtual int GetLiftSound(Mobile from) + { + return 0x57; + } - items.Add( item ); + public virtual bool DropToWorld(Mobile from, Point3D p) + { + if (Deleted || from.Deleted || from.Map == null) + return false; - ItemData id = item.ItemData; + if (!from.InRange(p, 2)) + return false; - if ( !id.Surface ) - continue; + Map map = from.Map; - int top = item.Z + id.CalcHeight; + if (map == null) + return false; - if ( top > maxZ || top < z ) - continue; + int x = p.m_X, y = p.m_Y; + int z = int.MinValue; - z = top; - } + int maxZ = from.Z + 16; - eable.Free(); + LandTile landTile = map.Tiles.GetLandTile(x, y); + TileFlag landFlags = TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags; - if ( z == int.MinValue ) - return false; + int landZ = 0, landAvg = 0, landTop = 0; + map.GetAverageZ(x, y, ref landZ, ref landAvg, ref landTop); - if ( z > maxZ ) - return false; + if (!landTile.Ignored && (landFlags & TileFlag.Impassable) == 0) + if (landAvg <= maxZ) + z = landAvg; - m_OpenSlots = (1<<20)-1; + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y, true); - int surfaceZ = z; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + if (!id.Surface) + continue; - int checkZ = tile.Z; - int checkTop = checkZ + id.CalcHeight; + int top = tile.Z + id.CalcHeight; - if ( checkTop == checkZ && !id.Surface ) - ++checkTop; + if (top > maxZ || top < z) + continue; - int zStart = checkZ - z; - int zEnd = checkTop - z; + z = top; + } - if ( zStart >= 20 || zEnd < 0 ) - continue; + List items = new List(); - if ( zStart < 0 ) - zStart = 0; + IPooledEnumerable eable = map.GetItemsInRange(p, 0); - if ( zEnd > 19 ) - zEnd = 19; + foreach (Item item in eable) + { + if (item is BaseMulti || item.ItemID > TileData.MaxItemValue) + continue; - int bitCount = zEnd-zStart; + items.Add(item); - m_OpenSlots &= ~(((1< maxZ || top < z) + continue; - int zStart = checkZ - z; - int zEnd = checkTop - z; + z = top; + } - if ( zStart >= 20 || zEnd < 0 ) - continue; + eable.Free(); - if ( zStart < 0 ) - zStart = 0; + if (z == int.MinValue) + return false; - if ( zEnd > 19 ) - zEnd = 19; + if (z > maxZ) + return false; - int bitCount = zEnd-zStart; + m_OpenSlots = (1 << 20) - 1; - m_OpenSlots &= ~(((1< 30 ) - height = 30; + if (checkTop == checkZ && !id.Surface) + ++checkTop; - int match = (1< 20 ) - match >>= 1; + if (zStart >= 20 || zEnd < 0) + continue; - okay = ((m_OpenSlots>>i)&match) == match; + if (zStart < 0) + zStart = 0; - if ( okay ) - { - z += i; - break; - } - } + if (zEnd > 19) + zEnd = 19; - if ( !okay ) - return false; + int bitCount = zEnd - zStart; - height = ItemData.Height; + m_OpenSlots &= ~(((1 << bitCount) - 1) << zStart); + } - if ( height == 0 ) - ++height; + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + ItemData id = item.ItemData; - if ( landAvg > z && (z + height) > landZ ) - return false; + int checkZ = item.Z; + int checkTop = checkZ + id.CalcHeight; - if ( (landFlags & TileFlag.Impassable) != 0 && landAvg > surfaceZ && (z + height) > landZ ) - return false; + if (checkTop == checkZ && !id.Surface) + ++checkTop; - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + int zStart = checkZ - z; + int zEnd = checkTop - z; - int checkZ = tile.Z; - int checkTop = checkZ + id.CalcHeight; + if (zStart >= 20 || zEnd < 0) + continue; - if ( checkTop > z && (z + height) > checkZ ) - return false; + if (zStart < 0) + zStart = 0; - if ( (id.Surface || id.Impassable) && checkTop > surfaceZ && (z + height) > checkZ ) - return false; - } + if (zEnd > 19) + zEnd = 19; - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - ItemData id = item.ItemData; + int bitCount = zEnd - zStart; - //int checkZ = item.Z; - //int checkTop = checkZ + id.CalcHeight; + m_OpenSlots &= ~(((1 << bitCount) - 1) << zStart); + } - if ( (item.Z + id.CalcHeight) > z && (z + height) > item.Z ) - return false; - } + int height = ItemData.Height; - p = new Point3D( x, y, z ); + if (height == 0) + ++height; - if ( !from.InLOS( new Point3D( x, y, z + 1 ) ) ) - return false; - if ( !from.OnDroppedItemToWorld( this, p ) ) - return false; - if ( !OnDroppedToWorld( from, p ) ) - return false; + if (height > 30) + height = 30; - int soundID = GetDropSound(); + int match = (1 << height) - 1; + bool okay = false; - MoveToWorld( p, from.Map ); + for (int i = 0; i < 20; ++i) + { + if (i + height > 20) + match >>= 1; - from.SendSound( soundID == -1 ? 0x42 : soundID, GetWorldLocation() ); + okay = ((m_OpenSlots >> i) & match) == match; - return true; - } + if (okay) + { + z += i; + break; + } + } - public void SendRemovePacket() - { - if ( !Deleted && m_Map != null ) - { - Point3D worldLoc = GetWorldLocation(); + if (!okay) + return false; - IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + height = ItemData.Height; - foreach (NetState state in eable) { - Mobile m = state.Mobile; + if (height == 0) + ++height; - if ( m.InRange( worldLoc, GetUpdateRange( m ) ) ) { - state.Send( RemovePacket ); - } - } + if (landAvg > z && z + height > landZ) + return false; - eable.Free(); - } - } + if ((landFlags & TileFlag.Impassable) != 0 && landAvg > surfaceZ && z + height > landZ) + return false; - public virtual int GetDropSound() - { - return -1; - } + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - public Point3D GetWorldLocation() - { - IEntity root = RootParent; + int checkZ = tile.Z; + int checkTop = checkZ + id.CalcHeight; - if ( root == null ) - return m_Location; - return root.Location; + if (checkTop > z && z + height > checkZ) + return false; - //return root == null ? m_Location : new Point3D( (IPoint3D) root ); - } + if ((id.Surface || id.Impassable) && checkTop > surfaceZ && z + height > checkZ) + return false; + } - public virtual bool BlocksFit => false; + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + ItemData id = item.ItemData; - public Point3D GetSurfaceTop() - { - IEntity root = RootParent; + //int checkZ = item.Z; + //int checkTop = checkZ + id.CalcHeight; - if ( root == null ) - return new Point3D( m_Location.m_X, m_Location.m_Y, m_Location.m_Z + (ItemData.Surface ? ItemData.CalcHeight : 0) ); + if (item.Z + id.CalcHeight > z && z + height > item.Z) + return false; + } - return root.Location; - } + p = new Point3D(x, y, z); - public Point3D GetWorldTop() - { - IEntity root = RootParent; + if (!from.InLOS(new Point3D(x, y, z + 1))) + return false; + if (!from.OnDroppedItemToWorld(this, p)) + return false; + if (!OnDroppedToWorld(from, p)) + return false; - if ( root == null ) - return new Point3D( m_Location.m_X, m_Location.m_Y, m_Location.m_Z + ItemData.CalcHeight ); + int soundID = GetDropSound(); - return root.Location; - } + MoveToWorld(p, from.Map); - public void SendLocalizedMessageTo( Mobile to, int number ) - { - if ( Deleted || !to.CanSee( this ) ) - return; + from.SendSound(soundID == -1 ? 0x42 : soundID, GetWorldLocation()); - to.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", "" ) ); - } + return true; + } - public void SendLocalizedMessageTo( Mobile to, int number, string args ) - { - if ( Deleted || !to.CanSee( this ) ) - return; - - to.Send( new MessageLocalized( Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", args ) ); - } - - public void SendLocalizedMessageTo( Mobile to, int number, AffixType affixType, string affix, string args ) - { - if ( Deleted || !to.CanSee( this ) ) - return; - - to.Send( new MessageLocalizedAffix( Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", affixType, affix, args ) ); - } - - #region OnDoubleClick[...] - - public virtual void OnDoubleClick( Mobile from ) - { - } - - public virtual void OnDoubleClickOutOfRange( Mobile from ) - { - } - - public virtual void OnDoubleClickCantSee( Mobile from ) - { - } - - public virtual void OnDoubleClickDead( Mobile from ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019048 ); // I am dead and cannot do that. - } - - public virtual void OnDoubleClickNotAccessible( Mobile from ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible. - } - - public virtual void OnDoubleClickSecureTrade( Mobile from ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible. - } - #endregion - - public virtual void OnSnoop( Mobile from ) - { - } - - public bool InSecureTrade => ( GetSecureTradeCont() != null ); - - public SecureTradeContainer GetSecureTradeCont() - { - object p = this; - - while ( p is Item ) - { - if ( p is SecureTradeContainer container ) - return container; - - p = ((Item)p).m_Parent; - } - - return null; - } - - public virtual void OnItemAdded( Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnSubItemAdded( item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnSubItemAdded( item ); - } - - public virtual void OnItemRemoved( Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnSubItemRemoved( item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnSubItemRemoved( item ); - } - - public virtual void OnSubItemAdded( Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnSubItemAdded( item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnSubItemAdded( item ); - } - - public virtual void OnSubItemRemoved( Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnSubItemRemoved( item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnSubItemRemoved( item ); - } - - public virtual void OnItemBounceCleared( Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnSubItemBounceCleared( item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnSubItemBounceCleared( item ); - } - - public virtual void OnSubItemBounceCleared( Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnSubItemBounceCleared( item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnSubItemBounceCleared( item ); - } - - public virtual bool CheckTarget( Mobile from, Targeting.Target targ, object targeted ) - { - if ( m_Parent is Item item ) - return item.CheckTarget( from, targ, targeted ); - if ( m_Parent is Mobile mobile ) - return mobile.CheckTarget( from, targ, targeted ); - - return true; - } - - public virtual bool IsAccessibleTo( Mobile check ) - { - if ( m_Parent is Item item ) - return item.IsAccessibleTo( check ); - - Region reg = Region.Find( GetWorldLocation(), m_Map ); - - return reg.CheckAccessibility( this, check ); - - /*SecureTradeContainer cont = GetSecureTradeCont(); - - if ( cont != null && !cont.IsChildOf( check ) ) - return false; - - return true;*/ - } - - public bool IsChildOf(IEntity o) - { - return IsChildOf( o, false ); - } - - public bool IsChildOf(IEntity o, bool allowNull) - { - IEntity p = m_Parent; - - if ( (p == null || o == null) && !allowNull ) - return false; - - if ( p == o ) - return true; - - while ( p is Item ) - { - Item item = (Item)p; - - if ( item.m_Parent == null ) - break; - - p = item.m_Parent; - - if ( p == o ) - return true; - } - - return false; - } - - public ItemData ItemData => TileData.ItemTable[m_ItemID & TileData.MaxItemValue]; - - public virtual void OnItemUsed( Mobile from, Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnItemUsed( from, item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnItemUsed( from, item ); - } - - public bool CheckItemUse( Mobile from ) - { - return CheckItemUse( from, this ); - } - - public virtual bool CheckItemUse( Mobile from, Item item ) - { - if ( m_Parent is Item parentItem ) - return parentItem.CheckItemUse( from, item ); - if ( m_Parent is Mobile parentMobile ) - return parentMobile.CheckItemUse( from, item ); - return true; - } - - public virtual void OnItemLifted( Mobile from, Item item ) - { - if ( m_Parent is Item parentItem ) - parentItem.OnItemLifted( from, item ); - else if ( m_Parent is Mobile parentMobile ) - parentMobile.OnItemLifted( from, item ); - } - - public bool CheckLift( Mobile from ) - { - LRReason reject = LRReason.Inspecific; - - return CheckLift( from, this, ref reject ); - } - - public virtual bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( m_Parent is Item parentItem ) - return parentItem.CheckLift( from, item, ref reject ); - - if ( m_Parent is Mobile parentMobile ) - return parentMobile.CheckLift( from, item, ref reject ); - - return true; - } - - public virtual bool CanTarget => true; - public virtual bool DisplayLootType => true; - - public virtual void OnSingleClickContained( Mobile from, Item item ) - { - if ( m_Parent is Item item1 ) - item1.OnSingleClickContained( from, item ); - } - - public virtual void OnAosSingleClick( Mobile from ) - { - ObjectPropertyList opl = PropertyList; - - if ( opl.Header > 0 ) - from.Send( new MessageLocalized( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, opl.Header, Name, opl.HeaderArgs ) ); - } - - public virtual void OnSingleClick( Mobile from ) - { - if ( Deleted || !from.CanSee( this ) ) - return; - - if ( DisplayLootType ) - LabelLootTypeTo( from ); - - NetState ns = from.NetState; - - if ( ns != null ) - { - if ( Name == null ) - { - if ( m_Amount <= 1 ) - ns.Send( new MessageLocalized( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, LabelNumber, "", "" ) ); - else - ns.Send( new MessageLocalizedAffix( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, LabelNumber, "", AffixType.Append, - $" : {m_Amount}", "" ) ); - } - else - { - ns.Send( new UnicodeMessage( Serial, m_ItemID, MessageType.Label, 0x3B2, 3, "ENU", "", Name + ( m_Amount > 1 ? " : " + m_Amount : "" ) ) ); - } - } - } - - public static bool ScissorCopyLootType { get; set; } - - public virtual void ScissorHelper( Mobile from, Item newItem, int amountPerOldItem ) - { - ScissorHelper( from, newItem, amountPerOldItem, true ); - } - - public virtual void ScissorHelper( Mobile from, Item newItem, int amountPerOldItem, bool carryHue ) - { - int amount = Amount; - - if ( amount > (60000 / amountPerOldItem) ) // let's not go over 60000 - amount = (60000 / amountPerOldItem); - - Amount -= amount; - - int ourHue = Hue; - Map thisMap = Map; - IEntity thisParent = m_Parent; - Point3D worldLoc = GetWorldLocation(); - LootType type = LootType; - - if ( Amount == 0 ) - Delete(); - - newItem.Amount = amount * amountPerOldItem; - - if ( carryHue ) - newItem.Hue = ourHue; - - if ( ScissorCopyLootType ) - newItem.LootType = type; - - if ( !(thisParent is Container) || !((Container)thisParent).TryDropItem( from, newItem, false ) ) - newItem.MoveToWorld( worldLoc, thisMap ); - } - - public virtual void Consume() - { - Consume( 1 ); - } - - public virtual void Consume( int amount ) - { - Amount -= amount; - - if ( Amount <= 0 ) - Delete(); - } - - public virtual void ReplaceWith( Item newItem ) - { - if ( m_Parent is Container container ) - { - container.AddItem( newItem ); - newItem.Location = m_Location; - } - else - { - newItem.MoveToWorld( GetWorldLocation(), m_Map ); - } - - Delete(); - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool QuestItem - { - get => GetFlag( ImplFlag.QuestItem ); - set - { - SetFlag( ImplFlag.QuestItem, value ); - - InvalidateProperties(); - - ReleaseWorldPackets(); - - Delta( ItemDelta.Update ); - } - } - - public bool Insured - { - get => GetFlag( ImplFlag.Insured ); - set{ SetFlag( ImplFlag.Insured, value ); InvalidateProperties(); } - } - - public bool PaidInsurance - { - get => GetFlag( ImplFlag.PaidInsurance ); - set => SetFlag( ImplFlag.PaidInsurance, value ); - } - - public Mobile BlessedFor - { - get - { - CompactInfo info = LookupCompactInfo(); - - return info?.m_BlessedFor; - } - set - { - CompactInfo info = AcquireCompactInfo(); - - info.m_BlessedFor = value; - - if ( info.m_BlessedFor == null ) - VerifyCompactInfo(); - - InvalidateProperties(); - } - } - - public virtual bool CheckBlessed( object obj ) - { - return CheckBlessed( obj as Mobile ); - } - - public virtual bool CheckBlessed( Mobile m ) - { - if ( m_LootType == LootType.Blessed || (Mobile.InsuranceEnabled && Insured) ) - return true; - - return ( m != null && m == BlessedFor ); - } - - public virtual bool CheckNewbied() - { - return ( m_LootType == LootType.Newbied ); - } - - public virtual bool IsStandardLoot() - { - if ( Mobile.InsuranceEnabled && Insured ) - return false; - - if ( BlessedFor != null ) - return false; - - return ( m_LootType == LootType.Regular ); - } - - public override string ToString() - { - return $"0x{Serial.Value:X} \"{GetType().Name}\""; - } - - internal int m_TypeRef; - - public Item() - { - Serial = Serial.NewItem; - - //m_Items = new ArrayList( 1 ); - Visible = true; - Movable = true; - Amount = 1; - m_Map = Map.Internal; - - SetLastMoved(); - - World.AddItem( this ); - - Type ourType = GetType(); - m_TypeRef = World.m_ItemTypes.IndexOf( ourType ); - - if ( m_TypeRef == -1 ) - { - World.m_ItemTypes.Add( ourType ); - m_TypeRef = World.m_ItemTypes.Count - 1; - } - } - - [Constructible] - public Item( int itemID ) : this() - { - m_ItemID = itemID; - } - - public Item( Serial serial ) - { - Serial = serial; - - Type ourType = GetType(); - m_TypeRef = World.m_ItemTypes.IndexOf( ourType ); - - if ( m_TypeRef == -1 ) - { - World.m_ItemTypes.Add( ourType ); - m_TypeRef = World.m_ItemTypes.Count - 1; - } - } - - public virtual void OnSectorActivate() - { - } - - public virtual void OnSectorDeactivate() - { - } - } -} + public void SendRemovePacket() + { + if (!Deleted && m_Map != null) + { + Point3D worldLoc = GetWorldLocation(); + + IPooledEnumerable eable = m_Map.GetClientsInRange(worldLoc, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.InRange(worldLoc, GetUpdateRange(m))) state.Send(RemovePacket); + } + + eable.Free(); + } + } + + public virtual int GetDropSound() + { + return -1; + } + + public Point3D GetWorldLocation() + { + IEntity root = RootParent; + + if (root == null) + return m_Location; + return root.Location; + + //return root == null ? m_Location : new Point3D( (IPoint3D) root ); + } + + public Point3D GetSurfaceTop() + { + IEntity root = RootParent; + + if (root == null) + return new Point3D(m_Location.m_X, m_Location.m_Y, + m_Location.m_Z + (ItemData.Surface ? ItemData.CalcHeight : 0)); + + return root.Location; + } + + public Point3D GetWorldTop() + { + IEntity root = RootParent; + + if (root == null) + return new Point3D(m_Location.m_X, m_Location.m_Y, m_Location.m_Z + ItemData.CalcHeight); + + return root.Location; + } + + public void SendLocalizedMessageTo(Mobile to, int number) + { + if (Deleted || !to.CanSee(this)) + return; + + to.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", "")); + } + + public void SendLocalizedMessageTo(Mobile to, int number, string args) + { + if (Deleted || !to.CanSee(this)) + return; + + to.Send(new MessageLocalized(Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", args)); + } + + public void SendLocalizedMessageTo(Mobile to, int number, AffixType affixType, string affix, string args) + { + if (Deleted || !to.CanSee(this)) + return; + + to.Send(new MessageLocalizedAffix(Serial, ItemID, MessageType.Regular, 0x3B2, 3, number, "", affixType, affix, + args)); + } + + public virtual void OnSnoop(Mobile from) + { + } + + public SecureTradeContainer GetSecureTradeCont() + { + object p = this; + + while (p is Item) + { + if (p is SecureTradeContainer container) + return container; + + p = ((Item)p).m_Parent; + } + + return null; + } + + public virtual void OnItemAdded(Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnSubItemAdded(item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnSubItemAdded(item); + } + + public virtual void OnItemRemoved(Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnSubItemRemoved(item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnSubItemRemoved(item); + } + + public virtual void OnSubItemAdded(Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnSubItemAdded(item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnSubItemAdded(item); + } + + public virtual void OnSubItemRemoved(Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnSubItemRemoved(item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnSubItemRemoved(item); + } + + public virtual void OnItemBounceCleared(Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnSubItemBounceCleared(item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnSubItemBounceCleared(item); + } + + public virtual void OnSubItemBounceCleared(Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnSubItemBounceCleared(item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnSubItemBounceCleared(item); + } + + public virtual bool CheckTarget(Mobile from, Target targ, object targeted) + { + if (m_Parent is Item item) + return item.CheckTarget(from, targ, targeted); + if (m_Parent is Mobile mobile) + return mobile.CheckTarget(from, targ, targeted); + + return true; + } + + public virtual bool IsAccessibleTo(Mobile check) + { + if (m_Parent is Item item) + return item.IsAccessibleTo(check); + + Region reg = Region.Find(GetWorldLocation(), m_Map); + + return reg.CheckAccessibility(this, check); + + /*SecureTradeContainer cont = GetSecureTradeCont(); + + if ( cont != null && !cont.IsChildOf( check ) ) + return false; + + return true;*/ + } + + public bool IsChildOf(IEntity o) + { + return IsChildOf(o, false); + } + + public bool IsChildOf(IEntity o, bool allowNull) + { + IEntity p = m_Parent; + + if ((p == null || o == null) && !allowNull) + return false; + + if (p == o) + return true; + + while (p is Item) + { + Item item = (Item)p; + + if (item.m_Parent == null) + break; + + p = item.m_Parent; + + if (p == o) + return true; + } + + return false; + } + + public virtual void OnItemUsed(Mobile from, Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnItemUsed(from, item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnItemUsed(from, item); + } + + public bool CheckItemUse(Mobile from) + { + return CheckItemUse(from, this); + } + + public virtual bool CheckItemUse(Mobile from, Item item) + { + if (m_Parent is Item parentItem) + return parentItem.CheckItemUse(from, item); + if (m_Parent is Mobile parentMobile) + return parentMobile.CheckItemUse(from, item); + return true; + } + + public virtual void OnItemLifted(Mobile from, Item item) + { + if (m_Parent is Item parentItem) + parentItem.OnItemLifted(from, item); + else if (m_Parent is Mobile parentMobile) + parentMobile.OnItemLifted(from, item); + } + + public bool CheckLift(Mobile from) + { + LRReason reject = LRReason.Inspecific; + + return CheckLift(from, this, ref reject); + } + + public virtual bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (m_Parent is Item parentItem) + return parentItem.CheckLift(from, item, ref reject); + + if (m_Parent is Mobile parentMobile) + return parentMobile.CheckLift(from, item, ref reject); + + return true; + } + + public virtual void OnSingleClickContained(Mobile from, Item item) + { + if (m_Parent is Item item1) + item1.OnSingleClickContained(from, item); + } + + public virtual void OnAosSingleClick(Mobile from) + { + ObjectPropertyList opl = PropertyList; + + if (opl.Header > 0) + from.Send(new MessageLocalized(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, opl.Header, Name, + opl.HeaderArgs)); + } + + public virtual void OnSingleClick(Mobile from) + { + if (Deleted || !from.CanSee(this)) + return; + + if (DisplayLootType) + LabelLootTypeTo(from); + + NetState ns = from.NetState; + + if (ns != null) + { + if (Name == null) + { + if (m_Amount <= 1) + ns.Send(new MessageLocalized(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, LabelNumber, "", "")); + else + ns.Send(new MessageLocalizedAffix(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, LabelNumber, "", + AffixType.Append, + $" : {m_Amount}", "")); + } + else + { + ns.Send(new UnicodeMessage(Serial, m_ItemID, MessageType.Label, 0x3B2, 3, "ENU", "", + Name + (m_Amount > 1 ? " : " + m_Amount : ""))); + } + } + } + + public virtual void ScissorHelper(Mobile from, Item newItem, int amountPerOldItem) + { + ScissorHelper(from, newItem, amountPerOldItem, true); + } + + public virtual void ScissorHelper(Mobile from, Item newItem, int amountPerOldItem, bool carryHue) + { + int amount = Amount; + + if (amount > 60000 / amountPerOldItem) // let's not go over 60000 + amount = 60000 / amountPerOldItem; + + Amount -= amount; + + int ourHue = Hue; + Map thisMap = Map; + IEntity thisParent = m_Parent; + Point3D worldLoc = GetWorldLocation(); + LootType type = LootType; + + if (Amount == 0) + Delete(); + + newItem.Amount = amount * amountPerOldItem; + + if (carryHue) + newItem.Hue = ourHue; + + if (ScissorCopyLootType) + newItem.LootType = type; + + if (!(thisParent is Container) || !((Container)thisParent).TryDropItem(from, newItem, false)) + newItem.MoveToWorld(worldLoc, thisMap); + } + + public virtual void Consume() + { + Consume(1); + } + + public virtual void Consume(int amount) + { + Amount -= amount; + + if (Amount <= 0) + Delete(); + } + + public virtual void ReplaceWith(Item newItem) + { + if (m_Parent is Container container) + { + container.AddItem(newItem); + newItem.Location = m_Location; + } + else + { + newItem.MoveToWorld(GetWorldLocation(), m_Map); + } + + Delete(); + } + + public virtual bool CheckBlessed(object obj) + { + return CheckBlessed(obj as Mobile); + } + + public virtual bool CheckBlessed(Mobile m) + { + if (m_LootType == LootType.Blessed || Mobile.InsuranceEnabled && Insured) + return true; + + return m != null && m == BlessedFor; + } + + public virtual bool CheckNewbied() + { + return m_LootType == LootType.Newbied; + } + + public virtual bool IsStandardLoot() + { + if (Mobile.InsuranceEnabled && Insured) + return false; + + if (BlessedFor != null) + return false; + + return m_LootType == LootType.Regular; + } + + public override string ToString() + { + return $"0x{Serial.Value:X} \"{GetType().Name}\""; + } + + public virtual void OnSectorActivate() + { + } + + public virtual void OnSectorDeactivate() + { + } + + [Flags] + private enum ImplFlag : byte + { + None = 0x00, + Visible = 0x01, + Movable = 0x02, + Deleted = 0x04, + Stackable = 0x08, + InQueue = 0x10, + Insured = 0x20, + PaidInsurance = 0x40, + QuestItem = 0x80 + } + + private class CompactInfo + { + public Mobile m_BlessedFor; + public BounceInfo m_Bounce; + + public Mobile m_HeldBy; + + public List m_Items; + public string m_Name; + public int m_SavedFlags; + + public ISpawner m_Spawner; + + public int m_TempFlags; + + public double m_Weight = -1; + } + + [Flags] + private enum SaveFlag + { + None = 0x00000000, + Direction = 0x00000001, + Bounce = 0x00000002, + LootType = 0x00000004, + LocationFull = 0x00000008, + ItemID = 0x00000010, + Hue = 0x00000020, + Amount = 0x00000040, + Layer = 0x00000080, + Name = 0x00000100, + Parent = 0x00000200, + Items = 0x00000400, + WeightNot1or0 = 0x00000800, + Map = 0x00001000, + Visible = 0x00002000, + Movable = 0x00004000, + Stackable = 0x00008000, + WeightIs0 = 0x00010000, + LocationSByteZ = 0x00020000, + LocationShortXY = 0x00040000, + LocationByteXY = 0x00080000, + ImplFlags = 0x00100000, + InsuredFor = 0x00200000, + BlessedFor = 0x00400000, + HeldBy = 0x00800000, + IntWeight = 0x01000000, + SavedFlags = 0x02000000, + NullWeight = 0x04000000 + } + + #region Standard fields + + private Point3D m_Location; + private int m_ItemID; + private int m_Hue; + private int m_Amount; + private Layer m_Layer; + private IEntity m_Parent; // Mobile, Item, or null=World + private Map m_Map; + private LootType m_LootType; + private Direction m_Direction; + + #endregion + + #region Packet caches + + private Packet m_WorldPacket; + private Packet m_WorldPacketSA; + private Packet m_WorldPacketHS; + private Packet m_RemovePacket; + + private Packet m_OPLPacket; + private ObjectPropertyList m_PropertyList; + + #endregion + + #region Location Location Location! + + public virtual void OnLocationChange(Point3D oldLocation) + { + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public virtual Point3D Location + { + get => m_Location; + set + { + Point3D oldLocation = m_Location; + + if (oldLocation != value) + { + if (m_Map != null) + { + if (m_Parent == null) + { + IPooledEnumerable eable; + + if (m_Location.m_X != 0) + { + eable = m_Map.GetClientsInRange(oldLocation, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (!m.InRange(value, GetUpdateRange(m))) state.Send(RemovePacket); + } + + eable.Free(); + } + + Point3D oldLoc = m_Location; + m_Location = value; + ReleaseWorldPackets(); + + SetLastMoved(); + + eable = m_Map.GetClientsInRange(m_Location, GetMaxUpdateRange()); + + foreach (NetState state in eable) + { + Mobile m = state.Mobile; + + if (m.CanSee(this) && m.InRange(m_Location, GetUpdateRange(m)) && + (!state.HighSeas || !NoMoveHS || (m_DeltaFlags & ItemDelta.Update) != 0 || + !m.InRange(oldLoc, GetUpdateRange(m)))) + SendInfoTo(state); + } + + eable.Free(); + + RemDelta(ItemDelta.Update); + } + else if (m_Parent is Item) + { + m_Location = value; + ReleaseWorldPackets(); + + Delta(ItemDelta.Update); + } + else + { + m_Location = value; + ReleaseWorldPackets(); + } + + if (m_Parent == null) + m_Map.OnMove(oldLocation, this); + } + else + { + m_Location = value; + ReleaseWorldPackets(); + } + + OnLocationChange(oldLocation); + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int X + { + get => m_Location.m_X; + set => Location = new Point3D(value, m_Location.m_Y, m_Location.m_Z); + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Y + { + get => m_Location.m_Y; + set => Location = new Point3D(m_Location.m_X, value, m_Location.m_Z); + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Z + { + get => m_Location.m_Z; + set => Location = new Point3D(m_Location.m_X, m_Location.m_Y, value); + } + + #endregion + + #region OnDoubleClick[...] + + public virtual void OnDoubleClick(Mobile from) + { + } + + public virtual void OnDoubleClickOutOfRange(Mobile from) + { + } + + public virtual void OnDoubleClickCantSee(Mobile from) + { + } + + public virtual void OnDoubleClickDead(Mobile from) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019048); // I am dead and cannot do that. + } + + public virtual void OnDoubleClickNotAccessible(Mobile from) + { + from.SendLocalizedMessage(500447); // That is not accessible. + } + + public virtual void OnDoubleClickSecureTrade(Mobile from) + { + from.SendLocalizedMessage(500447); // That is not accessible. + } + + #endregion + } +} \ No newline at end of file diff --git a/Server/ItemBounds.cs b/Server/ItemBounds.cs index 46ff1f8ed..422220a42 100644 --- a/Server/ItemBounds.cs +++ b/Server/ItemBounds.cs @@ -23,39 +23,36 @@ using System.IO; namespace Server { - public static class ItemBounds - { - public static Rectangle2D[] Table { get; } + public static class ItemBounds + { + static ItemBounds() + { + Table = new Rectangle2D[TileData.ItemTable.Length]; - static ItemBounds() - { - Table = new Rectangle2D[TileData.ItemTable.Length]; + if (File.Exists("Data/Binary/Bounds.bin")) + using (FileStream fs = new FileStream("Data/Binary/Bounds.bin", FileMode.Open, FileAccess.Read, + FileShare.Read)) + { + BinaryReader bin = new BinaryReader(fs); - if ( File.Exists( "Data/Binary/Bounds.bin" ) ) - { - using ( FileStream fs = new FileStream( "Data/Binary/Bounds.bin", FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - BinaryReader bin = new BinaryReader( fs ); + int count = Math.Min(Table.Length, (int)(fs.Length / 8)); - int count = Math.Min( Table.Length, (int)( fs.Length / 8 ) ); + for (int i = 0; i < count; ++i) + { + int xMin = bin.ReadInt16(); + int yMin = bin.ReadInt16(); + int xMax = bin.ReadInt16(); + int yMax = bin.ReadInt16(); - for ( int i = 0; i < count; ++i ) - { - int xMin = bin.ReadInt16(); - int yMin = bin.ReadInt16(); - int xMax = bin.ReadInt16(); - int yMax = bin.ReadInt16(); + Table[i].Set(xMin, yMin, xMax - xMin + 1, yMax - yMin + 1); + } - Table[i].Set( xMin, yMin, (xMax - xMin) + 1, (yMax - yMin) + 1 ); - } + bin.Close(); + } + else + Console.WriteLine("Warning: Data/Binary/Bounds.bin does not exist"); + } - bin.Close(); - } - } - else - { - Console.WriteLine( "Warning: Data/Binary/Bounds.bin does not exist" ); - } - } - } + public static Rectangle2D[] Table{ get; } + } } \ No newline at end of file diff --git a/Server/Items/BaseMulti.cs b/Server/Items/BaseMulti.cs index 757bfc10c..8501e7039 100644 --- a/Server/Items/BaseMulti.cs +++ b/Server/Items/BaseMulti.cs @@ -22,140 +22,144 @@ using System; namespace Server.Items { - public class BaseMulti : Item - { - [Constructible] - public BaseMulti( int itemID ) : base( itemID ) - { - Movable = false; - } + public class BaseMulti : Item + { + [Constructible] + public BaseMulti(int itemID) : base(itemID) + { + Movable = false; + } - public BaseMulti( Serial serial ) : base( serial ) - { - } + public BaseMulti(Serial serial) : base(serial) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public override int ItemID { - get => base.ItemID; - set { - if ( base.ItemID != value ) { - Map facet = ( Parent == null ? Map : null ); + [CommandProperty(AccessLevel.GameMaster)] + public override int ItemID + { + get => base.ItemID; + set + { + if (base.ItemID != value) + { + Map facet = Parent == null ? Map : null; - facet?.OnLeave( this ); + facet?.OnLeave(this); - base.ItemID = value; + base.ItemID = value; - facet?.OnEnter( this ); - } - } - } + facet?.OnEnter(this); + } + } + } - [Obsolete( "Replace with calls to OnLeave and OnEnter surrounding component invalidation.", true )] - public virtual void RefreshComponents() - { - if ( Parent == null ) { - Map facet = Map; + public override int LabelNumber + { + get + { + MultiComponentList mcl = Components; - if ( facet != null ) { - facet.OnLeave( this ); - facet.OnEnter( this ); - } - } - } + if (mcl.List.Length > 0) + { + int id = mcl.List[0].m_ItemID; - public override int LabelNumber - { - get - { - MultiComponentList mcl = Components; + if (id < 0x4000) + return 1020000 + id; + return 1078872 + id; + } - if ( mcl.List.Length > 0 ) { - int id = mcl.List[0].m_ItemID; + return base.LabelNumber; + } + } - if ( id < 0x4000 ) - return 1020000 + id; - return 1078872 + id; - } + public virtual bool AllowsRelativeDrop => false; - return base.LabelNumber; - } - } + public virtual MultiComponentList Components => MultiData.GetComponents(ItemID); - public virtual bool AllowsRelativeDrop => false; + [Obsolete("Replace with calls to OnLeave and OnEnter surrounding component invalidation.", true)] + public virtual void RefreshComponents() + { + if (Parent == null) + { + Map facet = Map; - public override int GetMaxUpdateRange() - { - return 22; - } + if (facet != null) + { + facet.OnLeave(this); + facet.OnEnter(this); + } + } + } - public override int GetUpdateRange( Mobile m ) - { - return 22; - } + public override int GetMaxUpdateRange() + { + return 22; + } - public virtual MultiComponentList Components => MultiData.GetComponents( ItemID ); + public override int GetUpdateRange(Mobile m) + { + return 22; + } - public virtual bool Contains( Point2D p ) - { - return Contains( p.m_X, p.m_Y ); - } + public virtual bool Contains(Point2D p) + { + return Contains(p.m_X, p.m_Y); + } - public virtual bool Contains( Point3D p ) - { - return Contains( p.m_X, p.m_Y ); - } + public virtual bool Contains(Point3D p) + { + return Contains(p.m_X, p.m_Y); + } - public virtual bool Contains( IPoint3D p ) - { - return Contains( p.X, p.Y ); - } + public virtual bool Contains(IPoint3D p) + { + return Contains(p.X, p.Y); + } - public virtual bool Contains( int x, int y ) - { - MultiComponentList mcl = Components; + public virtual bool Contains(int x, int y) + { + MultiComponentList mcl = Components; - x -= X + mcl.Min.m_X; - y -= Y + mcl.Min.m_Y; + x -= X + mcl.Min.m_X; + y -= Y + mcl.Min.m_Y; - return x >= 0 - && x < mcl.Width - && y >= 0 - && y < mcl.Height - && mcl.Tiles[x][y].Length > 0; - } + return x >= 0 + && x < mcl.Width + && y >= 0 + && y < mcl.Height + && mcl.Tiles[x][y].Length > 0; + } - public bool Contains( Mobile m ) - { - if ( m.Map == Map ) - return Contains( m.X, m.Y ); - return false; - } + public bool Contains(Mobile m) + { + if (m.Map == Map) + return Contains(m.X, m.Y); + return false; + } - public bool Contains( Item item ) - { - if ( item.Map == Map ) - return Contains( item.X, item.Y ); - return false; - } + public bool Contains(Item item) + { + if (item.Map == Map) + return Contains(item.X, item.Y); + return false; + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 1 ); // version - } + writer.Write(1); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); + int version = reader.ReadInt(); - if ( version == 0 ) { - if ( ItemID >= 0x4000 ) { - ItemID -= 0x4000; - } - } - } - } + if (version == 0) + if (ItemID >= 0x4000) + ItemID -= 0x4000; + } + } } \ No newline at end of file diff --git a/Server/Items/Container.cs b/Server/Items/Container.cs index 076f3796f..4c0291b9d 100644 --- a/Server/Items/Container.cs +++ b/Server/Items/Container.cs @@ -26,1838 +26,1837 @@ using Server.Network; namespace Server.Items { - public delegate void OnItemConsumed( Item item, int amount ); - public delegate int CheckItemGroup( Item a, Item b ); - - public delegate void ContainerSnoopHandler( Container cont, Mobile from ); - - public class Container : Item - { - public static ContainerSnoopHandler SnoopHandler { get; set; } - - private ContainerData m_ContainerData; - - private int m_DropSound; - private int m_GumpID; - private int m_MaxItems; - - private int m_TotalItems; - private int m_TotalWeight; - private int m_TotalGold; - - internal List m_Items; - - public ContainerData ContainerData - { - get - { - if ( m_ContainerData == null ) - UpdateContainerData(); - - return m_ContainerData; - } - set => m_ContainerData = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public override int ItemID - { - get => base.ItemID; - set - { - int oldID = ItemID; - - base.ItemID = value; - - if ( ItemID != oldID ) - UpdateContainerData(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int GumpID - { - get => ( m_GumpID == -1 ? DefaultGumpID : m_GumpID ); - set => m_GumpID = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int DropSound - { - get => ( m_DropSound == -1 ? DefaultDropSound : m_DropSound ); - set => m_DropSound = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MaxItems - { - get => ( m_MaxItems == -1 ? DefaultMaxItems : m_MaxItems ); - set{ m_MaxItems = value; InvalidateProperties(); } - } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual int MaxWeight - { - get - { - if ( Parent is Container container && container.MaxWeight == 0 ) - { - return 0; - } - - return DefaultMaxWeight; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool LiftOverride { get; set; } - - public virtual void UpdateContainerData() - { - ContainerData = ContainerData.GetData( ItemID ); - } - - public virtual Rectangle2D Bounds => ContainerData.Bounds; - - [CommandProperty( AccessLevel.GameMaster )] - public virtual int DefaultGumpID => ContainerData.GumpID; - - [CommandProperty( AccessLevel.GameMaster )] - public virtual int DefaultDropSound => ContainerData.DropSound; - - public virtual int DefaultMaxItems => GlobalMaxItems; - public virtual int DefaultMaxWeight => GlobalMaxWeight; - - public virtual bool IsDecoContainer => !Movable && !IsLockedDown && !IsSecure && Parent == null && !LiftOverride; - - public virtual int GetDroppedSound( Item item ) - { - int dropSound = item.GetDropSound(); - - return dropSound != -1 ? dropSound : DropSound; - } - - public override void OnSnoop( Mobile from ) - { - SnoopHandler?.Invoke( this, from ); - } - - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - if ( from.AccessLevel < AccessLevel.GameMaster && IsDecoContainer ) - { - reject = LRReason.CannotLift; - return false; - } - - return base.CheckLift( from, item, ref reject ); - } - - public override bool CheckItemUse( Mobile from, Item item ) - { - if ( item != this && from.AccessLevel < AccessLevel.GameMaster && IsDecoContainer ) - { - from.LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019045 ); // I can't reach that. - return false; - } - - return base.CheckItemUse( from, item ); - } - - public bool CheckHold( Mobile m, Item item, bool message ) - { - return CheckHold( m, item, message, true, 0, 0 ); - } - - public bool CheckHold( Mobile m, Item item, bool message, bool checkItems ) - { - return CheckHold( m, item, message, checkItems, 0, 0 ); - } - - public virtual bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if ( m != null && m.AccessLevel < AccessLevel.GameMaster ) - { - if ( IsDecoContainer ) - { - if ( message ) - SendCantStoreMessage( m, item ); - - return false; - } - - int maxItems = MaxItems; - - if ( checkItems && maxItems != 0 && (TotalItems + plusItems + item.TotalItems + (item.IsVirtualItem ? 0 : 1)) > maxItems ) - { - if ( message ) - SendFullItemsMessage( m, item ); - - return false; - } - - if ( MaxWeight != 0 && (TotalWeight + plusWeight + item.TotalWeight + item.PileWeight) > MaxWeight ) - { - if ( message ) - SendFullWeightMessage( m, item ); + public delegate void OnItemConsumed(Item item, int amount); + + public delegate int CheckItemGroup(Item a, Item b); + + public delegate void ContainerSnoopHandler(Container cont, Mobile from); + + public class Container : Item + { + private static List m_FindItemsList = new List(); + + private ContainerData m_ContainerData; + + private int m_DropSound; + private int m_GumpID; + + internal List m_Items; + private int m_MaxItems; + private int m_TotalGold; - return false; - } - } + private int m_TotalItems; + private int m_TotalWeight; - object parent = Parent; + public Container(int itemID) : base(itemID) + { + m_GumpID = -1; + m_DropSound = -1; + m_MaxItems = -1; - while ( parent != null ) - { - if ( parent is Container container ) - return container.CheckHold( m, item, message, checkItems, plusItems, plusWeight ); + UpdateContainerData(); + } - if ( !(parent is Item parentItem) ) - break; + public Container(Serial serial) : base(serial) + { + } - parent = parentItem.Parent; - } + public static ContainerSnoopHandler SnoopHandler{ get; set; } - return true; - } + public ContainerData ContainerData + { + get + { + if (m_ContainerData == null) + UpdateContainerData(); - public virtual void SendFullItemsMessage( Mobile to, Item item ) - { - to.SendMessage( "That container cannot hold more items." ); - } + return m_ContainerData; + } + set => m_ContainerData = value; + } - public virtual void SendFullWeightMessage( Mobile to, Item item ) - { - to.SendMessage( "That container cannot hold more weight." ); - } - - public virtual void SendCantStoreMessage( Mobile to, Item item ) - { - to.SendLocalizedMessage( 500176 ); // That is not your container, you can't store things here. - } + [CommandProperty(AccessLevel.GameMaster)] + public override int ItemID + { + get => base.ItemID; + set + { + int oldID = ItemID; - public virtual bool OnDragDropInto( Mobile from, Item item, Point3D p ) - { - if ( !CheckHold( from, item, true, true ) ) - return false; + base.ItemID = value; - item.Location = new Point3D( p.m_X, p.m_Y, 0 ); - AddItem( item ); - - from.SendSound( GetDroppedSound( item ), GetWorldLocation() ); + if (ItemID != oldID) + UpdateContainerData(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int GumpID + { + get => m_GumpID == -1 ? DefaultGumpID : m_GumpID; + set => m_GumpID = value; + } - return true; - } + [CommandProperty(AccessLevel.GameMaster)] + public int DropSound + { + get => m_DropSound == -1 ? DefaultDropSound : m_DropSound; + set => m_DropSound = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MaxItems + { + get => m_MaxItems == -1 ? DefaultMaxItems : m_MaxItems; + set + { + m_MaxItems = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public virtual int MaxWeight + { + get + { + if (Parent is Container container && container.MaxWeight == 0) return 0; + + return DefaultMaxWeight; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool LiftOverride{ get; set; } + + public virtual Rectangle2D Bounds => ContainerData.Bounds; + + [CommandProperty(AccessLevel.GameMaster)] + public virtual int DefaultGumpID => ContainerData.GumpID; + + [CommandProperty(AccessLevel.GameMaster)] + public virtual int DefaultDropSound => ContainerData.DropSound; + + public virtual int DefaultMaxItems => GlobalMaxItems; + public virtual int DefaultMaxWeight => GlobalMaxWeight; + + public virtual bool IsDecoContainer => !Movable && !IsLockedDown && !IsSecure && Parent == null && !LiftOverride; + + public static int GlobalMaxItems{ get; set; } = 125; + + public static int GlobalMaxWeight{ get; set; } = 400; + + public virtual bool DisplaysContent => true; + + public List Openers{ get; set; } + + public virtual bool IsPublicContainer => false; + + public virtual void UpdateContainerData() + { + ContainerData = ContainerData.GetData(ItemID); + } + + public virtual int GetDroppedSound(Item item) + { + int dropSound = item.GetDropSound(); + + return dropSound != -1 ? dropSound : DropSound; + } + + public override void OnSnoop(Mobile from) + { + SnoopHandler?.Invoke(this, from); + } + + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + if (from.AccessLevel < AccessLevel.GameMaster && IsDecoContainer) + { + reject = LRReason.CannotLift; + return false; + } + + return base.CheckLift(from, item, ref reject); + } + + public override bool CheckItemUse(Mobile from, Item item) + { + if (item != this && from.AccessLevel < AccessLevel.GameMaster && IsDecoContainer) + { + from.LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019045); // I can't reach that. + return false; + } + + return base.CheckItemUse(from, item); + } + + public bool CheckHold(Mobile m, Item item, bool message) + { + return CheckHold(m, item, message, true, 0, 0); + } - private class GroupComparer : IComparer - { - private CheckItemGroup m_Grouper; + public bool CheckHold(Mobile m, Item item, bool message, bool checkItems) + { + return CheckHold(m, item, message, checkItems, 0, 0); + } - public GroupComparer( CheckItemGroup grouper ) - { - m_Grouper = grouper; - } + public virtual bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (m != null && m.AccessLevel < AccessLevel.GameMaster) + { + if (IsDecoContainer) + { + if (message) + SendCantStoreMessage(m, item); - public int Compare( object x, object y ) - { - Item a = (Item)x; - Item b = (Item)y; + return false; + } - return m_Grouper( a, b ); - } - } + int maxItems = MaxItems; - #region Consume[...] + if (checkItems && maxItems != 0 && + TotalItems + plusItems + item.TotalItems + (item.IsVirtualItem ? 0 : 1) > maxItems) + { + if (message) + SendFullItemsMessage(m, item); - public bool ConsumeTotalGrouped( Type type, int amount, bool recurse, OnItemConsumed callback, CheckItemGroup grouper ) - { - if ( grouper == null ) - throw new ArgumentNullException(); + return false; + } - Item[] typedItems = FindItemsByType( type, recurse ); + if (MaxWeight != 0 && TotalWeight + plusWeight + item.TotalWeight + item.PileWeight > MaxWeight) + { + if (message) + SendFullWeightMessage(m, item); - List> groups = new List>(); - int idx = 0; + return false; + } + } - while ( idx < typedItems.Length ) - { - Item a = typedItems[idx++]; - List group = new List(); + object parent = Parent; - group.Add( a ); + while (parent != null) + { + if (parent is Container container) + return container.CheckHold(m, item, message, checkItems, plusItems, plusWeight); - while ( idx < typedItems.Length ) - { - Item b = typedItems[idx]; - int v = grouper( a, b ); + if (!(parent is Item parentItem)) + break; - if ( v == 0 ) - group.Add( b ); - else - break; + parent = parentItem.Parent; + } - ++idx; - } + return true; + } - groups.Add( group ); - } + public virtual void SendFullItemsMessage(Mobile to, Item item) + { + to.SendMessage("That container cannot hold more items."); + } - Item[][] items = new Item[groups.Count][]; - int[] totals = new int[groups.Count]; + public virtual void SendFullWeightMessage(Mobile to, Item item) + { + to.SendMessage("That container cannot hold more weight."); + } + + public virtual void SendCantStoreMessage(Mobile to, Item item) + { + to.SendLocalizedMessage(500176); // That is not your container, you can't store things here. + } + + public virtual bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (!CheckHold(from, item, true, true)) + return false; + + item.Location = new Point3D(p.m_X, p.m_Y, 0); + AddItem(item); + + from.SendSound(GetDroppedSound(item), GetWorldLocation()); + + return true; + } - bool hasEnough = false; - for ( int i = 0; i < groups.Count; ++i ) - { - items[i] = groups[i].ToArray(); - //items[i] = (Item[])(((ArrayList)groups[i]).ToArray( typeof( Item ) )); + private static bool InTypeList(Item item, Type[] types) + { + Type t = item.GetType(); - for ( int j = 0; j < items[i].Length; ++j ) - totals[i] += items[i][j].Amount; + for (int i = 0; i < types.Length; ++i) + if (types[i].IsAssignableFrom(t)) + return true; - if ( totals[i] >= amount ) - hasEnough = true; - } + return false; + } - if ( !hasEnough ) - return false; + private static void SetSaveFlag(ref SaveFlag flags, SaveFlag toSet, bool setIf) + { + if (setIf) + flags |= toSet; + } - for ( int i = 0; i < items.Length; ++i ) - { - if ( totals[i] >= amount ) - { - int need = amount; + private static bool GetSaveFlag(SaveFlag flags, SaveFlag toGet) + { + return (flags & toGet) != 0; + } - for ( int j = 0; j < items[i].Length; ++j ) - { - Item item = items[i][j]; + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - int theirAmount = item.Amount; + writer.Write(2); // version - if ( theirAmount < need ) - { - callback?.Invoke( item, theirAmount ); + SaveFlag flags = SaveFlag.None; - item.Consume( theirAmount ); - need -= theirAmount; - } - else - { - callback?.Invoke( item, need ); + SetSaveFlag(ref flags, SaveFlag.MaxItems, m_MaxItems != -1); + SetSaveFlag(ref flags, SaveFlag.GumpID, m_GumpID != -1); + SetSaveFlag(ref flags, SaveFlag.DropSound, m_DropSound != -1); + SetSaveFlag(ref flags, SaveFlag.LiftOverride, LiftOverride); - item.Consume( need ); - break; - } - } + writer.Write((byte)flags); - break; - } - } + if (GetSaveFlag(flags, SaveFlag.MaxItems)) + writer.WriteEncodedInt(m_MaxItems); - return true; - } + if (GetSaveFlag(flags, SaveFlag.GumpID)) + writer.WriteEncodedInt(m_GumpID); - public int ConsumeTotalGrouped( Type[] types, int[] amounts, bool recurse, OnItemConsumed callback, CheckItemGroup grouper ) - { - if ( types.Length != amounts.Length ) - throw new ArgumentException(); - if ( grouper == null ) - throw new ArgumentNullException(); + if (GetSaveFlag(flags, SaveFlag.DropSound)) + writer.WriteEncodedInt(m_DropSound); + } + + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - Item[][][] items = new Item[types.Length][][]; - int[][] totals = new int[types.Length][]; + int version = reader.ReadInt(); - for ( int i = 0; i < types.Length; ++i ) - { - Item[] typedItems = FindItemsByType( types[i], recurse ); + switch (version) + { + case 2: + { + SaveFlag flags = (SaveFlag)reader.ReadByte(); - List> groups = new List>(); - int idx = 0; + if (GetSaveFlag(flags, SaveFlag.MaxItems)) + m_MaxItems = reader.ReadEncodedInt(); + else + m_MaxItems = -1; - while ( idx < typedItems.Length ) - { - Item a = typedItems[idx++]; - List group = new List(); + if (GetSaveFlag(flags, SaveFlag.GumpID)) + m_GumpID = reader.ReadEncodedInt(); + else + m_GumpID = -1; - group.Add( a ); + if (GetSaveFlag(flags, SaveFlag.DropSound)) + m_DropSound = reader.ReadEncodedInt(); + else + m_DropSound = -1; - while ( idx < typedItems.Length ) - { - Item b = typedItems[idx]; - int v = grouper( a, b ); + LiftOverride = GetSaveFlag(flags, SaveFlag.LiftOverride); - if ( v == 0 ) - group.Add( b ); - else - break; + break; + } + case 1: + { + m_MaxItems = reader.ReadInt(); + goto case 0; + } + case 0: + { + if (version < 1) + m_MaxItems = GlobalMaxItems; - ++idx; - } + m_GumpID = reader.ReadInt(); + m_DropSound = reader.ReadInt(); - groups.Add( group ); - } + if (m_GumpID == DefaultGumpID) + m_GumpID = -1; - items[i] = new Item[groups.Count][]; - totals[i] = new int[groups.Count]; - - bool hasEnough = false; - - for ( int j = 0; j < groups.Count; ++j ) - { - items[i][j] = groups[j].ToArray(); - //items[i][j] = (Item[])(((ArrayList)groups[j]).ToArray( typeof( Item ) )); - - for ( int k = 0; k < items[i][j].Length; ++k ) - totals[i][j] += items[i][j][k].Amount; - - if ( totals[i][j] >= amounts[i] ) - hasEnough = true; - } - - if ( !hasEnough ) - return i; - } - - for ( int i = 0; i < items.Length; ++i ) - { - for ( int j = 0; j < items[i].Length; ++j ) - { - if ( totals[i][j] >= amounts[i] ) - { - int need = amounts[i]; - - for ( int k = 0; k < items[i][j].Length; ++k ) - { - Item item = items[i][j][k]; - - int theirAmount = item.Amount; - - if ( theirAmount < need ) - { - callback?.Invoke( item, theirAmount ); - - item.Consume( theirAmount ); - need -= theirAmount; - } - else - { - callback?.Invoke( item, need ); - - item.Consume( need ); - break; - } - } - - break; - } - } - } - - return -1; - } - - public int ConsumeTotalGrouped( Type[][] types, int[] amounts, bool recurse, OnItemConsumed callback, CheckItemGroup grouper ) - { - if ( types.Length != amounts.Length ) - throw new ArgumentException(); - if ( grouper == null ) - throw new ArgumentNullException(); - - Item[][][] items = new Item[types.Length][][]; - int[][] totals = new int[types.Length][]; - - for ( int i = 0; i < types.Length; ++i ) - { - Item[] typedItems = FindItemsByType( types[i], recurse ); - - List> groups = new List>(); - int idx = 0; - - while ( idx < typedItems.Length ) - { - Item a = typedItems[idx++]; - List group = new List(); - - group.Add( a ); - - while ( idx < typedItems.Length ) - { - Item b = typedItems[idx]; - int v = grouper( a, b ); - - if ( v == 0 ) - group.Add( b ); - else - break; - - ++idx; - } - - groups.Add( group ); - } - - items[i] = new Item[groups.Count][]; - totals[i] = new int[groups.Count]; - - bool hasEnough = false; - - for ( int j = 0; j < groups.Count; ++j ) - { - items[i][j] = groups[j].ToArray(); - - for ( int k = 0; k < items[i][j].Length; ++k ) - totals[i][j] += items[i][j][k].Amount; - - if ( totals[i][j] >= amounts[i] ) - hasEnough = true; - } - - if ( !hasEnough ) - return i; - } - - for ( int i = 0; i < items.Length; ++i ) - { - for ( int j = 0; j < items[i].Length; ++j ) - { - if ( totals[i][j] >= amounts[i] ) - { - int need = amounts[i]; - - for ( int k = 0; k < items[i][j].Length; ++k ) - { - Item item = items[i][j][k]; - - int theirAmount = item.Amount; - - if ( theirAmount < need ) - { - callback?.Invoke( item, theirAmount ); - - item.Consume( theirAmount ); - need -= theirAmount; - } - else - { - callback?.Invoke( item, need ); - - item.Consume( need ); - break; - } - } - - break; - } - } - } - - return -1; - } - - public int ConsumeTotal( Type[][] types, int[] amounts ) - { - return ConsumeTotal( types, amounts, true, null ); - } - - public int ConsumeTotal( Type[][] types, int[] amounts, bool recurse ) - { - return ConsumeTotal( types, amounts, recurse, null ); - } - - public int ConsumeTotal( Type[][] types, int[] amounts, bool recurse, OnItemConsumed callback ) - { - if ( types.Length != amounts.Length ) - throw new ArgumentException(); - - Item[][] items = new Item[types.Length][]; - int[] totals = new int[types.Length]; - - for ( int i = 0; i < types.Length; ++i ) - { - items[i] = FindItemsByType( types[i], recurse ); - - for ( int j = 0; j < items[i].Length; ++j ) - totals[i] += items[i][j].Amount; - - if ( totals[i] < amounts[i] ) - return i; - } - - for ( int i = 0; i < types.Length; ++i ) - { - int need = amounts[i]; - - for ( int j = 0; j < items[i].Length; ++j ) - { - Item item = items[i][j]; - - int theirAmount = item.Amount; - - if ( theirAmount < need ) - { - callback?.Invoke( item, theirAmount ); - - item.Consume( theirAmount ); - need -= theirAmount; - } - else - { - callback?.Invoke( item, need ); - - item.Consume( need ); - break; - } - } - } - - return -1; - } - - public int ConsumeTotal( Type[] types, int[] amounts ) - { - return ConsumeTotal( types, amounts, true, null ); - } - - public int ConsumeTotal( Type[] types, int[] amounts, bool recurse ) - { - return ConsumeTotal( types, amounts, recurse, null ); - } - - public int ConsumeTotal( Type[] types, int[] amounts, bool recurse, OnItemConsumed callback ) - { - if ( types.Length != amounts.Length ) - throw new ArgumentException(); - - Item[][] items = new Item[types.Length][]; - int[] totals = new int[types.Length]; - - for ( int i = 0; i < types.Length; ++i ) - { - items[i] = FindItemsByType( types[i], recurse ); - - for ( int j = 0; j < items[i].Length; ++j ) - totals[i] += items[i][j].Amount; - - if ( totals[i] < amounts[i] ) - return i; - } - - for ( int i = 0; i < types.Length; ++i ) - { - int need = amounts[i]; - - for ( int j = 0; j < items[i].Length; ++j ) - { - Item item = items[i][j]; - - int theirAmount = item.Amount; - - if ( theirAmount < need ) - { - callback?.Invoke( item, theirAmount ); - - item.Consume( theirAmount ); - need -= theirAmount; - } - else - { - callback?.Invoke( item, need ); - - item.Consume( need ); - break; - } - } - } - - return -1; - } - - public bool ConsumeTotal( Type type, int amount ) - { - return ConsumeTotal( type, amount, true, null ); - } - - public bool ConsumeTotal( Type type, int amount, bool recurse ) - { - return ConsumeTotal( type, amount, recurse, null ); - } - - public bool ConsumeTotal( Type type, int amount, bool recurse, OnItemConsumed callback ) - { - Item[] items = FindItemsByType( type, recurse ); - - // First pass, compute total - int total = 0; - - for( int i = 0; i < items.Length; ++i ) - total += items[i].Amount; - - if ( total >= amount ) - { - // We've enough, so consume it - - int need = amount; - - for( int i = 0; i < items.Length; ++i ) - { - Item item = items[i]; - - int theirAmount = item.Amount; - - if ( theirAmount < need ) - { - callback?.Invoke( item, theirAmount ); - - item.Consume( theirAmount ); - need -= theirAmount; - } - else - { - callback?.Invoke( item, need ); - - item.Consume( need ); - - return true; - } - } - } - - return false; - } - - public int ConsumeUpTo( Type type, int amount ) - { - return ConsumeUpTo( type, amount, true ); - } - - public int ConsumeUpTo( Type type, int amount, bool recurse ) - { - int consumed = 0; - - Queue toDelete = new Queue(); - - RecurseConsumeUpTo( this, type, amount, recurse, ref consumed, toDelete ); - - while( toDelete.Count > 0 ) - toDelete.Dequeue().Delete(); - - return consumed; - } - - private static void RecurseConsumeUpTo( Item current, Type type, int amount, bool recurse, ref int consumed, Queue toDelete ) - { - if ( current != null && current.Items.Count > 0 ) - { - List list = current.Items; - - for( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; - - if ( type.IsAssignableFrom( item.GetType() ) ) - { - int need = amount - consumed; - int theirAmount = item.Amount; - - if ( theirAmount <= need ) - { - toDelete.Enqueue( item ); - consumed += theirAmount; - } - else - { - item.Amount -= need; - consumed += need; - - return; - } - } - else if ( recurse && item is Container ) - { - RecurseConsumeUpTo( item, type, amount, recurse, ref consumed, toDelete ); - } - } - } - } - - #endregion - - #region Get[BestGroup]Amount - public int GetBestGroupAmount( Type type, bool recurse, CheckItemGroup grouper ) - { - if ( grouper == null ) - throw new ArgumentNullException(); - - int best = 0; - - Item[] typedItems = FindItemsByType( type, recurse ); - - List> groups = new List>(); - int idx = 0; - - while( idx < typedItems.Length ) - { - Item a = typedItems[idx++]; - List group = new List(); - - group.Add( a ); - - while( idx < typedItems.Length ) - { - Item b = typedItems[idx]; - int v = grouper( a, b ); - - if ( v == 0 ) - group.Add( b ); - else - break; - - ++idx; - } - - groups.Add( group ); - } - - for( int i = 0; i < groups.Count; ++i ) - { - Item[] items = groups[i].ToArray(); - - //Item[] items = (Item[])(((ArrayList)groups[i]).ToArray( typeof( Item ) )); - int total = 0; - - for( int j = 0; j < items.Length; ++j ) - total += items[j].Amount; - - if ( total >= best ) - best = total; - } - - return best; - } - - public int GetBestGroupAmount( Type[] types, bool recurse, CheckItemGroup grouper ) - { - if ( grouper == null ) - throw new ArgumentNullException(); - - int best = 0; - - Item[] typedItems = FindItemsByType( types, recurse ); - - List> groups = new List>(); - int idx = 0; - - while( idx < typedItems.Length ) - { - Item a = typedItems[idx++]; - List group = new List(); - - group.Add( a ); - - while( idx < typedItems.Length ) - { - Item b = typedItems[idx]; - int v = grouper( a, b ); - - if ( v == 0 ) - group.Add( b ); - else - break; - - ++idx; - } - - groups.Add( group ); - } - - for( int j = 0; j < groups.Count; ++j ) - { - Item[] items = groups[j].ToArray(); - //Item[] items = (Item[])(((ArrayList)groups[j]).ToArray( typeof( Item ) )); - int total = 0; - - for( int k = 0; k < items.Length; ++k ) - total += items[k].Amount; - - if ( total >= best ) - best = total; - } - - return best; - } - - public int GetBestGroupAmount( Type[][] types, bool recurse, CheckItemGroup grouper ) - { - if ( grouper == null ) - throw new ArgumentNullException(); - - int best = 0; - - for( int i = 0; i < types.Length; ++i ) - { - Item[] typedItems = FindItemsByType( types[i], recurse ); - - List> groups = new List>(); - int idx = 0; - - while( idx < typedItems.Length ) - { - Item a = typedItems[idx++]; - List group = new List(); - - group.Add( a ); - - while( idx < typedItems.Length ) - { - Item b = typedItems[idx]; - int v = grouper( a, b ); - - if ( v == 0 ) - group.Add( b ); - else - break; - - ++idx; - } - - groups.Add( group ); - } - - for( int j = 0; j < groups.Count; ++j ) - { - Item[] items = groups[j].ToArray(); - //Item[] items = (Item[])(((ArrayList)groups[j]).ToArray( typeof( Item ) )); - int total = 0; - - for( int k = 0; k < items.Length; ++k ) - total += items[k].Amount; - - if ( total >= best ) - best = total; - } - } - - return best; - } - - public int GetAmount( Type type ) - { - return GetAmount( type, true ); - } - - public int GetAmount( Type type, bool recurse ) - { - Item[] items = FindItemsByType( type, recurse ); - - int amount = 0; - - for ( int i = 0; i < items.Length; ++i ) - amount += items[i].Amount; - - return amount; - } - - public int GetAmount( Type[] types ) - { - return GetAmount( types, true ); - } - - public int GetAmount( Type[] types, bool recurse ) - { - Item[] items = FindItemsByType( types, recurse ); - - int amount = 0; - - for ( int i = 0; i < items.Length; ++i ) - amount += items[i].Amount; - - return amount; - } - #endregion - - private static List m_FindItemsList = new List(); - - #region Non-Generic FindItem[s] by Type - public Item[] FindItemsByType( Type type ) - { - return FindItemsByType( type, true ); - } - - public Item[] FindItemsByType( Type type, bool recurse ) - { - if ( m_FindItemsList.Count > 0 ) - m_FindItemsList.Clear(); - - RecurseFindItemsByType( this, type, recurse, m_FindItemsList ); - - return m_FindItemsList.ToArray(); - } - - private static void RecurseFindItemsByType( Item current, Type type, bool recurse, List list ) - { - if ( current != null && current.Items.Count > 0 ) - { - List items = current.Items; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( type.IsAssignableFrom( item.GetType() ) )// item.GetType().IsAssignableFrom( type ) ) - list.Add( item ); - - if ( recurse && item is Container ) - RecurseFindItemsByType( item, type, recurse, list ); - } - } - } - - public Item[] FindItemsByType( Type[] types ) - { - return FindItemsByType( types, true ); - } - - public Item[] FindItemsByType( Type[] types, bool recurse ) - { - if ( m_FindItemsList.Count > 0 ) - m_FindItemsList.Clear(); - - RecurseFindItemsByType( this, types, recurse, m_FindItemsList ); - - return m_FindItemsList.ToArray(); - } - - private static void RecurseFindItemsByType( Item current, Type[] types, bool recurse, List list ) - { - if ( current != null && current.Items.Count > 0 ) - { - List items = current.Items; - - for( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( InTypeList( item, types ) ) - list.Add( item ); - - if ( recurse && item is Container ) - RecurseFindItemsByType( item, types, recurse, list ); - } - } - } - - public Item FindItemByType( Type type ) - { - return FindItemByType( type, true ); - } - - public Item FindItemByType( Type type, bool recurse ) - { - return RecurseFindItemByType( this, type, recurse ); - } - - private static Item RecurseFindItemByType( Item current, Type type, bool recurse ) - { - if ( current != null && current.Items.Count > 0 ) - { - List list = current.Items; - - for( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; - - if ( type.IsAssignableFrom( item.GetType() ) ) - { - return item; - } - - if ( recurse && item is Container ) - { - Item check = RecurseFindItemByType( item, type, recurse ); - - if ( check != null ) - return check; - } - } - } - - return null; - } - - public Item FindItemByType( Type[] types ) - { - return FindItemByType( types, true ); - } - - public Item FindItemByType( Type[] types, bool recurse ) - { - return RecurseFindItemByType( this, types, recurse ); - } - - private static Item RecurseFindItemByType( Item current, Type[] types, bool recurse ) - { - if ( current != null && current.Items.Count > 0 ) - { - List list = current.Items; - - for( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; - - if ( InTypeList( item, types ) ) - { - return item; - } - - if ( recurse && item is Container ) - { - Item check = RecurseFindItemByType( item, types, recurse ); - - if ( check != null ) - return check; - } - } - } - - return null; - } - - #endregion - - #region Generic FindItem[s] by Type - public List FindItemsByType() where T : Item - { - return FindItemsByType( true, null ); - } - - public List FindItemsByType( bool recurse ) where T : Item - { - return FindItemsByType( recurse, null ); - } - - public List FindItemsByType( Predicate predicate ) where T : Item - { - return FindItemsByType( true, predicate ); - } - - public List FindItemsByType( bool recurse, Predicate predicate ) where T : Item - { - if ( m_FindItemsList.Count > 0 ) - m_FindItemsList.Clear(); - - List list = new List(); - - RecurseFindItemsByType( this, recurse, list, predicate ); - - return list; - } - - private static void RecurseFindItemsByType( Item current, bool recurse, List list, Predicate predicate ) where T : Item - { - if ( current != null && current.Items.Count > 0 ) - { - List items = current.Items; - - for( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( typeof( T ).IsAssignableFrom( item.GetType() ) ) - { - T typedItem = (T)item; - - if ( predicate == null || predicate( typedItem ) ) - list.Add( typedItem ); - } - - if ( recurse && item is Container ) - RecurseFindItemsByType( item, recurse, list, predicate ); - } - } - } - - public T FindItemByType() where T : Item - { - return FindItemByType( true ); - } - - - public T FindItemByType( Predicate predicate ) where T : Item - { - return FindItemByType( true, predicate ); - } - - public T FindItemByType( bool recurse ) where T : Item - { - return FindItemByType( recurse, null ); - } - - public T FindItemByType( bool recurse, Predicate predicate ) where T : Item - { - return RecurseFindItemByType( this, recurse, predicate ); - } - - private static T RecurseFindItemByType( Item current, bool recurse, Predicate predicate ) where T : Item - { - if ( current != null && current.Items.Count > 0 ) - { - List list = current.Items; - - for( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; - - if ( typeof( T ).IsAssignableFrom( item.GetType() ) ) - { - T typedItem = (T)item; - - if ( predicate == null || predicate( typedItem ) ) - return typedItem; - } - else if ( recurse && item is Container ) - { - T check = RecurseFindItemByType( item, recurse, predicate ); - - if ( check != null ) - return check; - } - } - } - - return null; - } - #endregion - - - private static bool InTypeList( Item item, Type[] types ) - { - Type t = item.GetType(); - - for ( int i = 0; i < types.Length; ++i ) - if ( types[i].IsAssignableFrom( t ) ) - return true; - - return false; - } - - private static void SetSaveFlag( ref SaveFlag flags, SaveFlag toSet, bool setIf ) - { - if ( setIf ) - flags |= toSet; - } - - private static bool GetSaveFlag( SaveFlag flags, SaveFlag toGet ) - { - return ( (flags & toGet) != 0 ); - } - - [Flags] - private enum SaveFlag : byte - { - None = 0x00000000, - MaxItems = 0x00000001, - GumpID = 0x00000002, - DropSound = 0x00000004, - LiftOverride = 0x00000008 - } - - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); - - writer.Write( (int) 2 ); // version - - SaveFlag flags = SaveFlag.None; - - SetSaveFlag( ref flags, SaveFlag.MaxItems, m_MaxItems != -1 ); - SetSaveFlag( ref flags, SaveFlag.GumpID, m_GumpID != -1 ); - SetSaveFlag( ref flags, SaveFlag.DropSound, m_DropSound != -1 ); - SetSaveFlag( ref flags, SaveFlag.LiftOverride, LiftOverride ); - - writer.Write( (byte) flags ); - - if ( GetSaveFlag( flags, SaveFlag.MaxItems ) ) - writer.WriteEncodedInt( (int) m_MaxItems ); - - if ( GetSaveFlag( flags, SaveFlag.GumpID ) ) - writer.WriteEncodedInt( (int) m_GumpID ); - - if ( GetSaveFlag( flags, SaveFlag.DropSound ) ) - writer.WriteEncodedInt( (int) m_DropSound ); - } - - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); - - int version = reader.ReadInt(); - - switch ( version ) - { - case 2: - { - SaveFlag flags = (SaveFlag)reader.ReadByte(); - - if ( GetSaveFlag( flags, SaveFlag.MaxItems ) ) - m_MaxItems = reader.ReadEncodedInt(); - else - m_MaxItems = -1; - - if ( GetSaveFlag( flags, SaveFlag.GumpID ) ) - m_GumpID = reader.ReadEncodedInt(); - else - m_GumpID = -1; - - if ( GetSaveFlag( flags, SaveFlag.DropSound ) ) - m_DropSound = reader.ReadEncodedInt(); - else - m_DropSound = -1; - - LiftOverride = GetSaveFlag( flags, SaveFlag.LiftOverride ); - - break; - } - case 1: - { - m_MaxItems = reader.ReadInt(); - goto case 0; - } - case 0: - { - if ( version < 1 ) - m_MaxItems = GlobalMaxItems; - - m_GumpID = reader.ReadInt(); - m_DropSound = reader.ReadInt(); - - if ( m_GumpID == DefaultGumpID ) - m_GumpID = -1; - - if ( m_DropSound == DefaultDropSound ) - m_DropSound = -1; - - if ( m_MaxItems == DefaultMaxItems ) - m_MaxItems = -1; - - //m_Bounds = new Rectangle2D( reader.ReadPoint2D(), reader.ReadPoint2D() ); - reader.ReadPoint2D(); - reader.ReadPoint2D(); - - break; - } - } - - UpdateContainerData(); - } - - public static int GlobalMaxItems { get; set; } = 125; - - public static int GlobalMaxWeight { get; set; } = 400; - - public Container( int itemID ) : base( itemID ) - { - m_GumpID = -1; - m_DropSound = -1; - m_MaxItems = -1; - - UpdateContainerData(); - } - - public override int GetTotal( TotalType type ) - { - switch ( type ) - { - case TotalType.Gold: - return m_TotalGold; - - case TotalType.Items: - return m_TotalItems; - - case TotalType.Weight: - return m_TotalWeight; - } - - return base.GetTotal( type ); - } - - public override void UpdateTotal( Item sender, TotalType type, int delta ) - { - if ( sender != this && delta != 0 && !sender.IsVirtualItem ) - { - switch ( type ) - { - case TotalType.Gold: - m_TotalGold += delta; - break; - - case TotalType.Items: - m_TotalItems += delta; - InvalidateProperties(); - break; - - case TotalType.Weight: - m_TotalWeight += delta; - InvalidateProperties(); - break; - } - } - - base.UpdateTotal( sender, type, delta ); - } - - public override void UpdateTotals() - { - m_TotalGold = 0; - m_TotalItems = 0; - m_TotalWeight = 0; - - List items = m_Items; - - if ( items == null ) - return; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - item.UpdateTotals(); - - if ( item.IsVirtualItem ) - continue; - - m_TotalGold += item.TotalGold; - m_TotalItems += item.TotalItems + 1; - m_TotalWeight += item.TotalWeight + item.PileWeight; - } - } - - public Container( Serial serial ) : base( serial ) - { - } - - public virtual bool OnStackAttempt( Mobile from, Item stack, Item dropped ) - { - return CheckHold( from, dropped, true, false ) && stack.StackWith( from, dropped ); - } - - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( TryDropItem( from, dropped, true ) ) - { - from.SendSound( GetDroppedSound( dropped ), GetWorldLocation() ); - - return true; - } - - return false; - } - - public virtual bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage ) - { - return TryDropItem( from, dropped, sendFullMessage, false ); - } - - public virtual bool TryDropItem( Mobile from, Item dropped, bool sendFullMessage, bool playSound ) - { - List list = Items; - - for ( int i = 0; i < list.Count; ++i ) - { - Item item = list[i]; - - if ( !(item is Container) && CheckHold( from, dropped, false, false ) && item.StackWith( from, dropped, playSound ) ) - return true; - } - - if ( CheckHold( from, dropped, sendFullMessage, true ) ) - { - DropItem( dropped ); - return true; - } - - return false; - } - - public virtual bool TryDropItems( Mobile from, bool sendFullMessage, params Item[] droppedItems ) - { - List dropItems = new List(); - List stackItems = new List(); - - int extraItems = 0; - int extraWeight = 0; + if (m_DropSound == DefaultDropSound) + m_DropSound = -1; + + if (m_MaxItems == DefaultMaxItems) + m_MaxItems = -1; + + //m_Bounds = new Rectangle2D( reader.ReadPoint2D(), reader.ReadPoint2D() ); + reader.ReadPoint2D(); + reader.ReadPoint2D(); + + break; + } + } + + UpdateContainerData(); + } + + public override int GetTotal(TotalType type) + { + switch (type) + { + case TotalType.Gold: + return m_TotalGold; + + case TotalType.Items: + return m_TotalItems; + + case TotalType.Weight: + return m_TotalWeight; + } + + return base.GetTotal(type); + } + + public override void UpdateTotal(Item sender, TotalType type, int delta) + { + if (sender != this && delta != 0 && !sender.IsVirtualItem) + switch (type) + { + case TotalType.Gold: + m_TotalGold += delta; + break; + + case TotalType.Items: + m_TotalItems += delta; + InvalidateProperties(); + break; + + case TotalType.Weight: + m_TotalWeight += delta; + InvalidateProperties(); + break; + } + + base.UpdateTotal(sender, type, delta); + } + + public override void UpdateTotals() + { + m_TotalGold = 0; + m_TotalItems = 0; + m_TotalWeight = 0; + + List items = m_Items; + + if (items == null) + return; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + item.UpdateTotals(); + + if (item.IsVirtualItem) + continue; + + m_TotalGold += item.TotalGold; + m_TotalItems += item.TotalItems + 1; + m_TotalWeight += item.TotalWeight + item.PileWeight; + } + } + + public virtual bool OnStackAttempt(Mobile from, Item stack, Item dropped) + { + return CheckHold(from, dropped, true, false) && stack.StackWith(from, dropped); + } + + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (TryDropItem(from, dropped, true)) + { + from.SendSound(GetDroppedSound(dropped), GetWorldLocation()); + + return true; + } + + return false; + } + + public virtual bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage) + { + return TryDropItem(from, dropped, sendFullMessage, false); + } + + public virtual bool TryDropItem(Mobile from, Item dropped, bool sendFullMessage, bool playSound) + { + List list = Items; + + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; + + if (!(item is Container) && CheckHold(from, dropped, false, false) && + item.StackWith(from, dropped, playSound)) + return true; + } + + if (CheckHold(from, dropped, sendFullMessage, true)) + { + DropItem(dropped); + return true; + } + + return false; + } + + public virtual bool TryDropItems(Mobile from, bool sendFullMessage, params Item[] droppedItems) + { + List dropItems = new List(); + List stackItems = new List(); + + int extraItems = 0; + int extraWeight = 0; // from.SendMessage( String.Format( "There are {0} items in this container.", this.Items.Count ) ); // from.SendMessage( String.Format( "There are {0} items being dropped into this container.", droppedItems.Length ) ); - for ( int i = 0; i < droppedItems.Length; i++ ) - { - Item dropped = droppedItems[i]; - - List list = Items; - - bool stacked = false; - - for ( int j = 0; j < list.Count; ++j ) - { - Item item = list[j]; - - if ( !(item is Container) && CheckHold( from, dropped, false, false, 0, extraWeight ) && item.CanStackWith( dropped ) ) - { - stackItems.Add( new ItemStackEntry( item, dropped ) ); - extraWeight += (int)Math.Ceiling( item.Weight * (item.Amount + dropped.Amount) ) - item.PileWeight; //extra weight delta, do not need TotalWeight as we do not have hybrid stackable container types - stacked = true; - break; - } - } - - if ( !stacked && CheckHold( from, dropped, false, true, extraItems, extraWeight ) ) - { - dropItems.Add( dropped ); - extraItems++; - extraWeight += dropped.TotalWeight + dropped.PileWeight; - } - } - - if ( dropItems.Count + stackItems.Count == droppedItems.Length ) //All good - { - for ( int i = 0; i < dropItems.Count; i++ ) - DropItem( dropItems[i] ); - - for ( int i = 0; i < stackItems.Count; i++ ) - stackItems[i].m_StackItem.StackWith( from, stackItems[i].m_DropItem, false ); - - return true; - } - - return false; - } - - private struct ItemStackEntry - { - public Item m_StackItem; - public Item m_DropItem; - - public ItemStackEntry( Item stack, Item drop ) - { - m_StackItem = stack; - m_DropItem = drop; - } - } - - public virtual void Destroy() - { - Point3D loc = GetWorldLocation(); - Map map = Map; - - for ( int i = Items.Count - 1; i >= 0; --i ) - { - if ( i < Items.Count ) - { - Items[i].SetLastMoved(); - Items[i].MoveToWorld( loc, map ); - } - } - - Delete(); - } - - public virtual void DropItem( Item dropped ) - { - if ( dropped == null ) - return; - - AddItem( dropped ); - - Rectangle2D bounds = dropped.GetGraphicBounds(); - Rectangle2D ourBounds = Bounds; - - int x, y; - - if ( bounds.Width >= ourBounds.Width ) - x = (ourBounds.Width - bounds.Width) / 2; - else - x = Utility.Random( ourBounds.Width - bounds.Width ); - - if ( bounds.Height >= ourBounds.Height ) - y = (ourBounds.Height - bounds.Height) / 2; - else - y = Utility.Random( ourBounds.Height - bounds.Height ); - - x += ourBounds.X; - x -= bounds.X; - - y += ourBounds.Y; - y -= bounds.Y; - - dropped.Location = new Point3D( x, y, 0 ); - } - - public override void OnDoubleClickSecureTrade( Mobile from ) - { - if ( from.InRange( GetWorldLocation(), 2 ) ) - { - DisplayTo( from ); - - SecureTradeContainer cont = GetSecureTradeCont(); - - if ( cont != null ) - { - SecureTrade trade = cont.Trade; - - if ( trade != null && trade.From.Mobile == from ) - DisplayTo( trade.To.Mobile ); - else if ( trade != null && trade.To.Mobile == from ) - DisplayTo( trade.From.Mobile ); - } - } - else - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } - - public virtual bool DisplaysContent => true; - - public virtual bool CheckContentDisplay( Mobile from ) - { - if ( DisplaysContent ) - { - object root = RootParent; - - if ( root == null || root is Item || root == from || from.AccessLevel > AccessLevel.Player ) - return true; - } - - return false; - } - - public override void OnSingleClick( Mobile from ) - { - base.OnSingleClick( from ); - - if ( CheckContentDisplay( from ) ) - LabelTo( from, "({0} item{2}, {1} stones)", TotalItems, TotalWeight, TotalItems != 1 ? "s" : string.Empty ); - //LabelTo( from, 1050044, String.Format( "{0}\t{1}", TotalItems.ToString(), TotalWeight.ToString() ) ); - } - - public List Openers { get; set; } - - public virtual bool IsPublicContainer => false; - - public override void OnDelete() - { - base.OnDelete(); - - Openers = null; - } - - public virtual void DisplayTo( Mobile to ) - { - ProcessOpeners( to ); - - NetState ns = to.NetState; - - if ( ns != null ) - { - if ( ns.HighSeas ) - to.Send( new ContainerDisplayHS( this ) ); - else - to.Send( new ContainerDisplay( this ) ); - - SendContentTo( ns ); - - if ( ObjectPropertyList.Enabled ) - { - List items = Items; - - for ( int i = 0; i < items.Count; ++i ) - to.Send( items[i].OPLPacket ); - } - } - } - - public void ProcessOpeners( Mobile opener ) - { - if ( !IsPublicContainer ) - { - bool contains = false; - - if ( Openers != null ) - { - Point3D worldLoc = GetWorldLocation(); - Map map = Map; - - for ( int i = 0; i < Openers.Count; ++i ) - { - Mobile mob = Openers[i]; - - if ( mob == opener ) - contains = true; - else - { - int range = GetUpdateRange( mob ); - - if ( mob.Map != map || !mob.InRange( worldLoc, range ) ) - Openers.RemoveAt( i-- ); - } - } - } - - if ( !contains ) - { - if ( Openers == null ) - Openers = new List(); - - Openers.Add( opener ); - } - else if ( Openers != null && Openers.Count == 0 ) - Openers = null; - } - } - - public virtual void SendContentTo( NetState state ) - { - if ( state != null && state.ContainerGridLines ) - state.Send( new ContainerContent6017( state.Mobile, this ) ); - else - state.Send( new ContainerContent( state.Mobile, this ) ); - } - - public override void GetProperties( ObjectPropertyList list ) - { - base.GetProperties( list ); - - if ( DisplaysContent )//CheckContentDisplay( from ) ) - { - if ( Core.ML ) - { - if ( ParentsContain() ) //Root Parent is the Mobile. Parent could be another containter. - list.Add( 1073841, "{0}\t{1}\t{2}", TotalItems, MaxItems, TotalWeight ); // Contents: ~1_COUNT~/~2_MAXCOUNT~ items, ~3_WEIGHT~ stones - else - list.Add( 1072241, "{0}\t{1}\t{2}\t{3}", TotalItems, MaxItems, TotalWeight, MaxWeight ); // Contents: ~1_COUNT~/~2_MAXCOUNT~ items, ~3_WEIGHT~/~4_MAXWEIGHT~ stones - - //TODO: Where do the other clilocs come into play? 1073839 & 1073840? - } - else - list.Add( 1050044, "{0}\t{1}", TotalItems, TotalWeight ); // ~1_COUNT~ items, ~2_WEIGHT~ stones - } - } - - public override void OnDoubleClick( Mobile from ) - { - if ( from.AccessLevel > AccessLevel.Player || from.InRange( GetWorldLocation(), 2 ) ) - DisplayTo( from ); - else - from.SendLocalizedMessage( 500446 ); // That is too far away. - } - } - - public class ContainerData - { - static ContainerData() - { - m_Table = new Dictionary(); - - string path = Path.Combine( Core.BaseDirectory, "Data/containers.cfg" ); - - if ( !File.Exists( path ) ) - { - Default = new ContainerData( 0x3C, new Rectangle2D( 44, 65, 142, 94 ), 0x48 ); - return; - } - - using ( StreamReader reader = new StreamReader( path ) ) - { - string line; - - while ( (line = reader.ReadLine()) != null ) - { - line = line.Trim(); - - if ( line.Length == 0 || line.StartsWith( "#" ) ) - continue; - - try - { - string[] split = line.Split( '\t' ); - - if ( split.Length >= 3 ) - { - int gumpID = Utility.ToInt32( split[0] ); - - string[] aRect = split[1].Split( ' ' ); - if ( aRect.Length < 4 ) - continue; - - int x = Utility.ToInt32( aRect[0] ); - int y = Utility.ToInt32( aRect[1] ); - int width = Utility.ToInt32( aRect[2] ); - int height = Utility.ToInt32( aRect[3] ); - - Rectangle2D bounds = new Rectangle2D( x, y, width, height ); - - int dropSound = Utility.ToInt32( split[2] ); - - ContainerData data = new ContainerData( gumpID, bounds, dropSound ); - - if ( Default == null ) - Default = data; - - if ( split.Length >= 4 ) - { - string[] aIDs = split[3].Split( ',' ); - - for ( int i = 0; i < aIDs.Length; i++ ) - { - int id = Utility.ToInt32( aIDs[i] ); - - if ( m_Table.ContainsKey( id ) ) - { - Console.WriteLine( @"Warning: double ItemID entry in Data\containers.cfg" ); - } - else - { - m_Table[id] = data; - } - } - } - } - } - catch - { - } - } - } - - if ( Default == null ) - Default = new ContainerData( 0x3C, new Rectangle2D( 44, 65, 142, 94 ), 0x48 ); - } - - private static Dictionary m_Table; - - public static ContainerData Default { get; set; } - - public static ContainerData GetData( int itemID ) - { - ContainerData data = null; - m_Table.TryGetValue( itemID, out data ); - - if ( data != null ) - return data; - return Default; - } - - public int GumpID { get; } - - public Rectangle2D Bounds { get; } - - public int DropSound { get; } - - public ContainerData( int gumpID, Rectangle2D bounds, int dropSound ) - { - GumpID = gumpID; - Bounds = bounds; - DropSound = dropSound; - } - } -} + for (int i = 0; i < droppedItems.Length; i++) + { + Item dropped = droppedItems[i]; + + List list = Items; + + bool stacked = false; + + for (int j = 0; j < list.Count; ++j) + { + Item item = list[j]; + + if (!(item is Container) && CheckHold(from, dropped, false, false, 0, extraWeight) && + item.CanStackWith(dropped)) + { + stackItems.Add(new ItemStackEntry(item, dropped)); + extraWeight += (int)Math.Ceiling(item.Weight * (item.Amount + dropped.Amount)) - + item.PileWeight; //extra weight delta, do not need TotalWeight as we do not have hybrid stackable container types + stacked = true; + break; + } + } + + if (!stacked && CheckHold(from, dropped, false, true, extraItems, extraWeight)) + { + dropItems.Add(dropped); + extraItems++; + extraWeight += dropped.TotalWeight + dropped.PileWeight; + } + } + + if (dropItems.Count + stackItems.Count == droppedItems.Length) //All good + { + for (int i = 0; i < dropItems.Count; i++) + DropItem(dropItems[i]); + + for (int i = 0; i < stackItems.Count; i++) + stackItems[i].m_StackItem.StackWith(from, stackItems[i].m_DropItem, false); + + return true; + } + + return false; + } + + public virtual void Destroy() + { + Point3D loc = GetWorldLocation(); + Map map = Map; + + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + { + Items[i].SetLastMoved(); + Items[i].MoveToWorld(loc, map); + } + + Delete(); + } + + public virtual void DropItem(Item dropped) + { + if (dropped == null) + return; + + AddItem(dropped); + + Rectangle2D bounds = dropped.GetGraphicBounds(); + Rectangle2D ourBounds = Bounds; + + int x, y; + + if (bounds.Width >= ourBounds.Width) + x = (ourBounds.Width - bounds.Width) / 2; + else + x = Utility.Random(ourBounds.Width - bounds.Width); + + if (bounds.Height >= ourBounds.Height) + y = (ourBounds.Height - bounds.Height) / 2; + else + y = Utility.Random(ourBounds.Height - bounds.Height); + + x += ourBounds.X; + x -= bounds.X; + + y += ourBounds.Y; + y -= bounds.Y; + + dropped.Location = new Point3D(x, y, 0); + } + + public override void OnDoubleClickSecureTrade(Mobile from) + { + if (from.InRange(GetWorldLocation(), 2)) + { + DisplayTo(from); + + SecureTradeContainer cont = GetSecureTradeCont(); + + if (cont != null) + { + SecureTrade trade = cont.Trade; + + if (trade != null && trade.From.Mobile == from) + DisplayTo(trade.To.Mobile); + else if (trade != null && trade.To.Mobile == from) + DisplayTo(trade.From.Mobile); + } + } + else + { + from.SendLocalizedMessage(500446); // That is too far away. + } + } + + public virtual bool CheckContentDisplay(Mobile from) + { + if (DisplaysContent) + { + object root = RootParent; + + if (root == null || root is Item || root == from || from.AccessLevel > AccessLevel.Player) + return true; + } + + return false; + } + + public override void OnSingleClick(Mobile from) + { + base.OnSingleClick(from); + + if (CheckContentDisplay(from)) + LabelTo(from, "({0} item{2}, {1} stones)", TotalItems, TotalWeight, TotalItems != 1 ? "s" : string.Empty); + //LabelTo( from, 1050044, String.Format( "{0}\t{1}", TotalItems.ToString(), TotalWeight.ToString() ) ); + } + + public override void OnDelete() + { + base.OnDelete(); + + Openers = null; + } + + public virtual void DisplayTo(Mobile to) + { + ProcessOpeners(to); + + NetState ns = to.NetState; + + if (ns != null) + { + if (ns.HighSeas) + to.Send(new ContainerDisplayHS(this)); + else + to.Send(new ContainerDisplay(this)); + + SendContentTo(ns); + + if (ObjectPropertyList.Enabled) + { + List items = Items; + + for (int i = 0; i < items.Count; ++i) + to.Send(items[i].OPLPacket); + } + } + } + + public void ProcessOpeners(Mobile opener) + { + if (!IsPublicContainer) + { + bool contains = false; + + if (Openers != null) + { + Point3D worldLoc = GetWorldLocation(); + Map map = Map; + + for (int i = 0; i < Openers.Count; ++i) + { + Mobile mob = Openers[i]; + + if (mob == opener) + { + contains = true; + } + else + { + int range = GetUpdateRange(mob); + + if (mob.Map != map || !mob.InRange(worldLoc, range)) + Openers.RemoveAt(i--); + } + } + } + + if (!contains) + { + if (Openers == null) + Openers = new List(); + + Openers.Add(opener); + } + else if (Openers != null && Openers.Count == 0) + { + Openers = null; + } + } + } + + public virtual void SendContentTo(NetState state) + { + if (state != null && state.ContainerGridLines) + state.Send(new ContainerContent6017(state.Mobile, this)); + else + state.Send(new ContainerContent(state.Mobile, this)); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + if (DisplaysContent) //CheckContentDisplay( from ) ) + { + if (Core.ML) + { + if (ParentsContain()) //Root Parent is the Mobile. Parent could be another containter. + list.Add(1073841, "{0}\t{1}\t{2}", TotalItems, MaxItems, + TotalWeight); // Contents: ~1_COUNT~/~2_MAXCOUNT~ items, ~3_WEIGHT~ stones + else + list.Add(1072241, "{0}\t{1}\t{2}\t{3}", TotalItems, MaxItems, TotalWeight, + MaxWeight); // Contents: ~1_COUNT~/~2_MAXCOUNT~ items, ~3_WEIGHT~/~4_MAXWEIGHT~ stones + + //TODO: Where do the other clilocs come into play? 1073839 & 1073840? + } + else + { + list.Add(1050044, "{0}\t{1}", TotalItems, TotalWeight); // ~1_COUNT~ items, ~2_WEIGHT~ stones + } + } + } + + public override void OnDoubleClick(Mobile from) + { + if (from.AccessLevel > AccessLevel.Player || from.InRange(GetWorldLocation(), 2)) + DisplayTo(from); + else + from.SendLocalizedMessage(500446); // That is too far away. + } + + private class GroupComparer : IComparer + { + private CheckItemGroup m_Grouper; + + public GroupComparer(CheckItemGroup grouper) + { + m_Grouper = grouper; + } + + public int Compare(object x, object y) + { + Item a = (Item)x; + Item b = (Item)y; + + return m_Grouper(a, b); + } + } + + [Flags] + private enum SaveFlag : byte + { + None = 0x00000000, + MaxItems = 0x00000001, + GumpID = 0x00000002, + DropSound = 0x00000004, + LiftOverride = 0x00000008 + } + + private struct ItemStackEntry + { + public Item m_StackItem; + public Item m_DropItem; + + public ItemStackEntry(Item stack, Item drop) + { + m_StackItem = stack; + m_DropItem = drop; + } + } + + #region Consume[...] + + public bool ConsumeTotalGrouped(Type type, int amount, bool recurse, OnItemConsumed callback, CheckItemGroup grouper) + { + if (grouper == null) + throw new ArgumentNullException(); + + Item[] typedItems = FindItemsByType(type, recurse); + + List> groups = new List>(); + int idx = 0; + + while (idx < typedItems.Length) + { + Item a = typedItems[idx++]; + List group = new List(); + + group.Add(a); + + while (idx < typedItems.Length) + { + Item b = typedItems[idx]; + int v = grouper(a, b); + + if (v == 0) + group.Add(b); + else + break; + + ++idx; + } + + groups.Add(group); + } + + Item[][] items = new Item[groups.Count][]; + int[] totals = new int[groups.Count]; + + bool hasEnough = false; + + for (int i = 0; i < groups.Count; ++i) + { + items[i] = groups[i].ToArray(); + //items[i] = (Item[])(((ArrayList)groups[i]).ToArray( typeof( Item ) )); + + for (int j = 0; j < items[i].Length; ++j) + totals[i] += items[i][j].Amount; + + if (totals[i] >= amount) + hasEnough = true; + } + + if (!hasEnough) + return false; + + for (int i = 0; i < items.Length; ++i) + if (totals[i] >= amount) + { + int need = amount; + + for (int j = 0; j < items[i].Length; ++j) + { + Item item = items[i][j]; + + int theirAmount = item.Amount; + + if (theirAmount < need) + { + callback?.Invoke(item, theirAmount); + + item.Consume(theirAmount); + need -= theirAmount; + } + else + { + callback?.Invoke(item, need); + + item.Consume(need); + break; + } + } + + break; + } + + return true; + } + + public int ConsumeTotalGrouped(Type[] types, int[] amounts, bool recurse, OnItemConsumed callback, + CheckItemGroup grouper) + { + if (types.Length != amounts.Length) + throw new ArgumentException(); + if (grouper == null) + throw new ArgumentNullException(); + + Item[][][] items = new Item[types.Length][][]; + int[][] totals = new int[types.Length][]; + + for (int i = 0; i < types.Length; ++i) + { + Item[] typedItems = FindItemsByType(types[i], recurse); + + List> groups = new List>(); + int idx = 0; + + while (idx < typedItems.Length) + { + Item a = typedItems[idx++]; + List group = new List(); + + group.Add(a); + + while (idx < typedItems.Length) + { + Item b = typedItems[idx]; + int v = grouper(a, b); + + if (v == 0) + group.Add(b); + else + break; + + ++idx; + } + + groups.Add(group); + } + + items[i] = new Item[groups.Count][]; + totals[i] = new int[groups.Count]; + + bool hasEnough = false; + + for (int j = 0; j < groups.Count; ++j) + { + items[i][j] = groups[j].ToArray(); + //items[i][j] = (Item[])(((ArrayList)groups[j]).ToArray( typeof( Item ) )); + + for (int k = 0; k < items[i][j].Length; ++k) + totals[i][j] += items[i][j][k].Amount; + + if (totals[i][j] >= amounts[i]) + hasEnough = true; + } + + if (!hasEnough) + return i; + } + + for (int i = 0; i < items.Length; ++i) + for (int j = 0; j < items[i].Length; ++j) + if (totals[i][j] >= amounts[i]) + { + int need = amounts[i]; + + for (int k = 0; k < items[i][j].Length; ++k) + { + Item item = items[i][j][k]; + + int theirAmount = item.Amount; + + if (theirAmount < need) + { + callback?.Invoke(item, theirAmount); + + item.Consume(theirAmount); + need -= theirAmount; + } + else + { + callback?.Invoke(item, need); + + item.Consume(need); + break; + } + } + + break; + } + + return -1; + } + + public int ConsumeTotalGrouped(Type[][] types, int[] amounts, bool recurse, OnItemConsumed callback, + CheckItemGroup grouper) + { + if (types.Length != amounts.Length) + throw new ArgumentException(); + if (grouper == null) + throw new ArgumentNullException(); + + Item[][][] items = new Item[types.Length][][]; + int[][] totals = new int[types.Length][]; + + for (int i = 0; i < types.Length; ++i) + { + Item[] typedItems = FindItemsByType(types[i], recurse); + + List> groups = new List>(); + int idx = 0; + + while (idx < typedItems.Length) + { + Item a = typedItems[idx++]; + List group = new List(); + + group.Add(a); + + while (idx < typedItems.Length) + { + Item b = typedItems[idx]; + int v = grouper(a, b); + + if (v == 0) + group.Add(b); + else + break; + + ++idx; + } + + groups.Add(group); + } + + items[i] = new Item[groups.Count][]; + totals[i] = new int[groups.Count]; + + bool hasEnough = false; + + for (int j = 0; j < groups.Count; ++j) + { + items[i][j] = groups[j].ToArray(); + + for (int k = 0; k < items[i][j].Length; ++k) + totals[i][j] += items[i][j][k].Amount; + + if (totals[i][j] >= amounts[i]) + hasEnough = true; + } + + if (!hasEnough) + return i; + } + + for (int i = 0; i < items.Length; ++i) + for (int j = 0; j < items[i].Length; ++j) + if (totals[i][j] >= amounts[i]) + { + int need = amounts[i]; + + for (int k = 0; k < items[i][j].Length; ++k) + { + Item item = items[i][j][k]; + + int theirAmount = item.Amount; + + if (theirAmount < need) + { + callback?.Invoke(item, theirAmount); + + item.Consume(theirAmount); + need -= theirAmount; + } + else + { + callback?.Invoke(item, need); + + item.Consume(need); + break; + } + } + + break; + } + + return -1; + } + + public int ConsumeTotal(Type[][] types, int[] amounts) + { + return ConsumeTotal(types, amounts, true, null); + } + + public int ConsumeTotal(Type[][] types, int[] amounts, bool recurse) + { + return ConsumeTotal(types, amounts, recurse, null); + } + + public int ConsumeTotal(Type[][] types, int[] amounts, bool recurse, OnItemConsumed callback) + { + if (types.Length != amounts.Length) + throw new ArgumentException(); + + Item[][] items = new Item[types.Length][]; + int[] totals = new int[types.Length]; + + for (int i = 0; i < types.Length; ++i) + { + items[i] = FindItemsByType(types[i], recurse); + + for (int j = 0; j < items[i].Length; ++j) + totals[i] += items[i][j].Amount; + + if (totals[i] < amounts[i]) + return i; + } + + for (int i = 0; i < types.Length; ++i) + { + int need = amounts[i]; + + for (int j = 0; j < items[i].Length; ++j) + { + Item item = items[i][j]; + + int theirAmount = item.Amount; + + if (theirAmount < need) + { + callback?.Invoke(item, theirAmount); + + item.Consume(theirAmount); + need -= theirAmount; + } + else + { + callback?.Invoke(item, need); + + item.Consume(need); + break; + } + } + } + + return -1; + } + + public int ConsumeTotal(Type[] types, int[] amounts) + { + return ConsumeTotal(types, amounts, true, null); + } + + public int ConsumeTotal(Type[] types, int[] amounts, bool recurse) + { + return ConsumeTotal(types, amounts, recurse, null); + } + + public int ConsumeTotal(Type[] types, int[] amounts, bool recurse, OnItemConsumed callback) + { + if (types.Length != amounts.Length) + throw new ArgumentException(); + + Item[][] items = new Item[types.Length][]; + int[] totals = new int[types.Length]; + + for (int i = 0; i < types.Length; ++i) + { + items[i] = FindItemsByType(types[i], recurse); + + for (int j = 0; j < items[i].Length; ++j) + totals[i] += items[i][j].Amount; + + if (totals[i] < amounts[i]) + return i; + } + + for (int i = 0; i < types.Length; ++i) + { + int need = amounts[i]; + + for (int j = 0; j < items[i].Length; ++j) + { + Item item = items[i][j]; + + int theirAmount = item.Amount; + + if (theirAmount < need) + { + callback?.Invoke(item, theirAmount); + + item.Consume(theirAmount); + need -= theirAmount; + } + else + { + callback?.Invoke(item, need); + + item.Consume(need); + break; + } + } + } + + return -1; + } + + public bool ConsumeTotal(Type type, int amount) + { + return ConsumeTotal(type, amount, true, null); + } + + public bool ConsumeTotal(Type type, int amount, bool recurse) + { + return ConsumeTotal(type, amount, recurse, null); + } + + public bool ConsumeTotal(Type type, int amount, bool recurse, OnItemConsumed callback) + { + Item[] items = FindItemsByType(type, recurse); + + // First pass, compute total + int total = 0; + + for (int i = 0; i < items.Length; ++i) + total += items[i].Amount; + + if (total >= amount) + { + // We've enough, so consume it + + int need = amount; + + for (int i = 0; i < items.Length; ++i) + { + Item item = items[i]; + + int theirAmount = item.Amount; + + if (theirAmount < need) + { + callback?.Invoke(item, theirAmount); + + item.Consume(theirAmount); + need -= theirAmount; + } + else + { + callback?.Invoke(item, need); + + item.Consume(need); + + return true; + } + } + } + + return false; + } + + public int ConsumeUpTo(Type type, int amount) + { + return ConsumeUpTo(type, amount, true); + } + + public int ConsumeUpTo(Type type, int amount, bool recurse) + { + int consumed = 0; + + Queue toDelete = new Queue(); + + RecurseConsumeUpTo(this, type, amount, recurse, ref consumed, toDelete); + + while (toDelete.Count > 0) + toDelete.Dequeue().Delete(); + + return consumed; + } + + private static void RecurseConsumeUpTo(Item current, Type type, int amount, bool recurse, ref int consumed, + Queue toDelete) + { + if (current != null && current.Items.Count > 0) + { + List list = current.Items; + + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; + + if (type.IsAssignableFrom(item.GetType())) + { + int need = amount - consumed; + int theirAmount = item.Amount; + + if (theirAmount <= need) + { + toDelete.Enqueue(item); + consumed += theirAmount; + } + else + { + item.Amount -= need; + consumed += need; + + return; + } + } + else if (recurse && item is Container) + { + RecurseConsumeUpTo(item, type, amount, recurse, ref consumed, toDelete); + } + } + } + } + + #endregion + + #region Get[BestGroup]Amount + + public int GetBestGroupAmount(Type type, bool recurse, CheckItemGroup grouper) + { + if (grouper == null) + throw new ArgumentNullException(); + + int best = 0; + + Item[] typedItems = FindItemsByType(type, recurse); + + List> groups = new List>(); + int idx = 0; + + while (idx < typedItems.Length) + { + Item a = typedItems[idx++]; + List group = new List(); + + group.Add(a); + + while (idx < typedItems.Length) + { + Item b = typedItems[idx]; + int v = grouper(a, b); + + if (v == 0) + group.Add(b); + else + break; + + ++idx; + } + + groups.Add(group); + } + + for (int i = 0; i < groups.Count; ++i) + { + Item[] items = groups[i].ToArray(); + + //Item[] items = (Item[])(((ArrayList)groups[i]).ToArray( typeof( Item ) )); + int total = 0; + + for (int j = 0; j < items.Length; ++j) + total += items[j].Amount; + + if (total >= best) + best = total; + } + + return best; + } + + public int GetBestGroupAmount(Type[] types, bool recurse, CheckItemGroup grouper) + { + if (grouper == null) + throw new ArgumentNullException(); + + int best = 0; + + Item[] typedItems = FindItemsByType(types, recurse); + + List> groups = new List>(); + int idx = 0; + + while (idx < typedItems.Length) + { + Item a = typedItems[idx++]; + List group = new List(); + + group.Add(a); + + while (idx < typedItems.Length) + { + Item b = typedItems[idx]; + int v = grouper(a, b); + + if (v == 0) + group.Add(b); + else + break; + + ++idx; + } + + groups.Add(group); + } + + for (int j = 0; j < groups.Count; ++j) + { + Item[] items = groups[j].ToArray(); + //Item[] items = (Item[])(((ArrayList)groups[j]).ToArray( typeof( Item ) )); + int total = 0; + + for (int k = 0; k < items.Length; ++k) + total += items[k].Amount; + + if (total >= best) + best = total; + } + + return best; + } + + public int GetBestGroupAmount(Type[][] types, bool recurse, CheckItemGroup grouper) + { + if (grouper == null) + throw new ArgumentNullException(); + + int best = 0; + + for (int i = 0; i < types.Length; ++i) + { + Item[] typedItems = FindItemsByType(types[i], recurse); + + List> groups = new List>(); + int idx = 0; + + while (idx < typedItems.Length) + { + Item a = typedItems[idx++]; + List group = new List(); + + group.Add(a); + + while (idx < typedItems.Length) + { + Item b = typedItems[idx]; + int v = grouper(a, b); + + if (v == 0) + group.Add(b); + else + break; + + ++idx; + } + + groups.Add(group); + } + + for (int j = 0; j < groups.Count; ++j) + { + Item[] items = groups[j].ToArray(); + //Item[] items = (Item[])(((ArrayList)groups[j]).ToArray( typeof( Item ) )); + int total = 0; + + for (int k = 0; k < items.Length; ++k) + total += items[k].Amount; + + if (total >= best) + best = total; + } + } + + return best; + } + + public int GetAmount(Type type) + { + return GetAmount(type, true); + } + + public int GetAmount(Type type, bool recurse) + { + Item[] items = FindItemsByType(type, recurse); + + int amount = 0; + + for (int i = 0; i < items.Length; ++i) + amount += items[i].Amount; + + return amount; + } + + public int GetAmount(Type[] types) + { + return GetAmount(types, true); + } + + public int GetAmount(Type[] types, bool recurse) + { + Item[] items = FindItemsByType(types, recurse); + + int amount = 0; + + for (int i = 0; i < items.Length; ++i) + amount += items[i].Amount; + + return amount; + } + + #endregion + + #region Non-Generic FindItem[s] by Type + + public Item[] FindItemsByType(Type type) + { + return FindItemsByType(type, true); + } + + public Item[] FindItemsByType(Type type, bool recurse) + { + if (m_FindItemsList.Count > 0) + m_FindItemsList.Clear(); + + RecurseFindItemsByType(this, type, recurse, m_FindItemsList); + + return m_FindItemsList.ToArray(); + } + + private static void RecurseFindItemsByType(Item current, Type type, bool recurse, List list) + { + if (current != null && current.Items.Count > 0) + { + List items = current.Items; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (type.IsAssignableFrom(item.GetType())) // item.GetType().IsAssignableFrom( type ) ) + list.Add(item); + + if (recurse && item is Container) + RecurseFindItemsByType(item, type, recurse, list); + } + } + } + + public Item[] FindItemsByType(Type[] types) + { + return FindItemsByType(types, true); + } + + public Item[] FindItemsByType(Type[] types, bool recurse) + { + if (m_FindItemsList.Count > 0) + m_FindItemsList.Clear(); + + RecurseFindItemsByType(this, types, recurse, m_FindItemsList); + + return m_FindItemsList.ToArray(); + } + + private static void RecurseFindItemsByType(Item current, Type[] types, bool recurse, List list) + { + if (current != null && current.Items.Count > 0) + { + List items = current.Items; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (InTypeList(item, types)) + list.Add(item); + + if (recurse && item is Container) + RecurseFindItemsByType(item, types, recurse, list); + } + } + } + + public Item FindItemByType(Type type) + { + return FindItemByType(type, true); + } + + public Item FindItemByType(Type type, bool recurse) + { + return RecurseFindItemByType(this, type, recurse); + } + + private static Item RecurseFindItemByType(Item current, Type type, bool recurse) + { + if (current != null && current.Items.Count > 0) + { + List list = current.Items; + + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; + + if (type.IsAssignableFrom(item.GetType())) return item; + + if (recurse && item is Container) + { + Item check = RecurseFindItemByType(item, type, recurse); + + if (check != null) + return check; + } + } + } + + return null; + } + + public Item FindItemByType(Type[] types) + { + return FindItemByType(types, true); + } + + public Item FindItemByType(Type[] types, bool recurse) + { + return RecurseFindItemByType(this, types, recurse); + } + + private static Item RecurseFindItemByType(Item current, Type[] types, bool recurse) + { + if (current != null && current.Items.Count > 0) + { + List list = current.Items; + + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; + + if (InTypeList(item, types)) return item; + + if (recurse && item is Container) + { + Item check = RecurseFindItemByType(item, types, recurse); + + if (check != null) + return check; + } + } + } + + return null; + } + + #endregion + + #region Generic FindItem[s] by Type + + public List FindItemsByType() where T : Item + { + return FindItemsByType(true, null); + } + + public List FindItemsByType(bool recurse) where T : Item + { + return FindItemsByType(recurse, null); + } + + public List FindItemsByType(Predicate predicate) where T : Item + { + return FindItemsByType(true, predicate); + } + + public List FindItemsByType(bool recurse, Predicate predicate) where T : Item + { + if (m_FindItemsList.Count > 0) + m_FindItemsList.Clear(); + + List list = new List(); + + RecurseFindItemsByType(this, recurse, list, predicate); + + return list; + } + + private static void RecurseFindItemsByType(Item current, bool recurse, List list, Predicate predicate) + where T : Item + { + if (current != null && current.Items.Count > 0) + { + List items = current.Items; + + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; + + if (typeof(T).IsAssignableFrom(item.GetType())) + { + T typedItem = (T)item; + + if (predicate == null || predicate(typedItem)) + list.Add(typedItem); + } + + if (recurse && item is Container) + RecurseFindItemsByType(item, recurse, list, predicate); + } + } + } + + public T FindItemByType() where T : Item + { + return FindItemByType(true); + } + + + public T FindItemByType(Predicate predicate) where T : Item + { + return FindItemByType(true, predicate); + } + + public T FindItemByType(bool recurse) where T : Item + { + return FindItemByType(recurse, null); + } + + public T FindItemByType(bool recurse, Predicate predicate) where T : Item + { + return RecurseFindItemByType(this, recurse, predicate); + } + + private static T RecurseFindItemByType(Item current, bool recurse, Predicate predicate) where T : Item + { + if (current != null && current.Items.Count > 0) + { + List list = current.Items; + + for (int i = 0; i < list.Count; ++i) + { + Item item = list[i]; + + if (typeof(T).IsAssignableFrom(item.GetType())) + { + T typedItem = (T)item; + + if (predicate == null || predicate(typedItem)) + return typedItem; + } + else if (recurse && item is Container) + { + T check = RecurseFindItemByType(item, recurse, predicate); + + if (check != null) + return check; + } + } + } + + return null; + } + + #endregion + } + + public class ContainerData + { + private static Dictionary m_Table; + + static ContainerData() + { + m_Table = new Dictionary(); + + string path = Path.Combine(Core.BaseDirectory, "Data/containers.cfg"); + + if (!File.Exists(path)) + { + Default = new ContainerData(0x3C, new Rectangle2D(44, 65, 142, 94), 0x48); + return; + } + + using (StreamReader reader = new StreamReader(path)) + { + string line; + + while ((line = reader.ReadLine()) != null) + { + line = line.Trim(); + + if (line.Length == 0 || line.StartsWith("#")) + continue; + + try + { + string[] split = line.Split('\t'); + + if (split.Length >= 3) + { + int gumpID = Utility.ToInt32(split[0]); + + string[] aRect = split[1].Split(' '); + if (aRect.Length < 4) + continue; + + int x = Utility.ToInt32(aRect[0]); + int y = Utility.ToInt32(aRect[1]); + int width = Utility.ToInt32(aRect[2]); + int height = Utility.ToInt32(aRect[3]); + + Rectangle2D bounds = new Rectangle2D(x, y, width, height); + + int dropSound = Utility.ToInt32(split[2]); + + ContainerData data = new ContainerData(gumpID, bounds, dropSound); + + if (Default == null) + Default = data; + + if (split.Length >= 4) + { + string[] aIDs = split[3].Split(','); + + for (int i = 0; i < aIDs.Length; i++) + { + int id = Utility.ToInt32(aIDs[i]); + + if (m_Table.ContainsKey(id)) + Console.WriteLine(@"Warning: double ItemID entry in Data\containers.cfg"); + else + m_Table[id] = data; + } + } + } + } + catch + { + } + } + } + + if (Default == null) + Default = new ContainerData(0x3C, new Rectangle2D(44, 65, 142, 94), 0x48); + } + + public ContainerData(int gumpID, Rectangle2D bounds, int dropSound) + { + GumpID = gumpID; + Bounds = bounds; + DropSound = dropSound; + } + + public static ContainerData Default{ get; set; } + + public int GumpID{ get; } + + public Rectangle2D Bounds{ get; } + + public int DropSound{ get; } + + public static ContainerData GetData(int itemID) + { + ContainerData data = null; + m_Table.TryGetValue(itemID, out data); + + if (data != null) + return data; + return Default; + } + } +} \ No newline at end of file diff --git a/Server/Items/Containers.cs b/Server/Items/Containers.cs index af3f4e61a..6842c67d0 100644 --- a/Server/Items/Containers.cs +++ b/Server/Items/Containers.cs @@ -18,133 +18,128 @@ * ***************************************************************************/ -using System; - using Server.Accounting; using Server.Network; namespace Server.Items { - public class BankBox : Container - { - public override int DefaultMaxWeight => 0; + public class BankBox : Container + { + public BankBox(Serial serial) : base(serial) + { + } - public override bool IsVirtualItem => true; + public BankBox(Mobile owner) : base(0xE7C) + { + Layer = Layer.Bank; + Movable = false; + Owner = owner; + } - public BankBox( Serial serial ) : base( serial ) - { - } + public override int DefaultMaxWeight => 0; - public Mobile Owner { get; private set; } + public override bool IsVirtualItem => true; - public bool Opened { get; private set; } + public Mobile Owner{ get; private set; } - public void Open() - { - Opened = true; + public bool Opened{ get; private set; } - if ( Owner != null ) - { - Owner.PrivateOverheadMessage( MessageType.Regular, 0x3B2, true, - $"Bank container has {TotalItems} items, {TotalWeight} stones", Owner.NetState ); - Owner.Send( new EquipUpdate( this ) ); - DisplayTo( Owner ); - } - } + public static bool SendDeleteOnClose{ get; set; } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public void Open() + { + Opened = true; - writer.Write( (int) 0 ); // version + if (Owner != null) + { + Owner.PrivateOverheadMessage(MessageType.Regular, 0x3B2, true, + $"Bank container has {TotalItems} items, {TotalWeight} stones", Owner.NetState); + Owner.Send(new EquipUpdate(this)); + DisplayTo(Owner); + } + } - writer.Write( (Mobile) Owner ); - writer.Write( (bool) Opened ); - } + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + writer.Write(0); // version - int version = reader.ReadInt(); + writer.Write(Owner); + writer.Write(Opened); + } - switch ( version ) - { - case 0: - { - Owner = reader.ReadMobile(); - Opened = reader.ReadBool(); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - if ( Owner == null ) - Delete(); + int version = reader.ReadInt(); - break; - } - } + switch (version) + { + case 0: + { + Owner = reader.ReadMobile(); + Opened = reader.ReadBool(); - if ( ItemID == 0xE41 ) - ItemID = 0xE7C; - } + if (Owner == null) + Delete(); - public static bool SendDeleteOnClose { get; set; } + break; + } + } - public void Close() - { - Opened = false; + if (ItemID == 0xE41) + ItemID = 0xE7C; + } - if ( Owner != null && SendDeleteOnClose ) - Owner.Send( RemovePacket ); - } + public void Close() + { + Opened = false; - public override void OnSingleClick( Mobile from ) - { - } + if (Owner != null && SendDeleteOnClose) + Owner.Send(RemovePacket); + } - public override void OnDoubleClick( Mobile from ) - { - } + public override void OnSingleClick(Mobile from) + { + } - public override DeathMoveResult OnParentDeath( Mobile parent ) - { - return DeathMoveResult.RemainEquipped; - } + public override void OnDoubleClick(Mobile from) + { + } - public BankBox( Mobile owner ) : base( 0xE7C ) - { - Layer = Layer.Bank; - Movable = false; - Owner = owner; - } + public override DeathMoveResult OnParentDeath(Mobile parent) + { + return DeathMoveResult.RemainEquipped; + } - public override bool IsAccessibleTo(Mobile check) - { - if ( ( check == Owner && Opened ) || check.AccessLevel >= AccessLevel.GameMaster ) - return base.IsAccessibleTo (check); - return false; - } + public override bool IsAccessibleTo(Mobile check) + { + if (check == Owner && Opened || check.AccessLevel >= AccessLevel.GameMaster) + return base.IsAccessibleTo(check); + return false; + } - public override bool OnDragDrop( Mobile from, Item dropped ) - { - if ( ( from == Owner && Opened ) || from.AccessLevel >= AccessLevel.GameMaster ) - return base.OnDragDrop( from, dropped ); - return false; - } + public override bool OnDragDrop(Mobile from, Item dropped) + { + if (from == Owner && Opened || from.AccessLevel >= AccessLevel.GameMaster) + return base.OnDragDrop(from, dropped); + return false; + } - public override bool OnDragDropInto(Mobile from, Item item, Point3D p) - { - if ( ( from == Owner && Opened ) || from.AccessLevel >= AccessLevel.GameMaster ) - return base.OnDragDropInto (from, item, p); - return false; - } + public override bool OnDragDropInto(Mobile from, Item item, Point3D p) + { + if (from == Owner && Opened || from.AccessLevel >= AccessLevel.GameMaster) + return base.OnDragDropInto(from, item, p); + return false; + } - public override int GetTotal(TotalType type) - { - if (AccountGold.Enabled && Owner?.Account != null && type == TotalType.Gold) - { - return Owner.Account.TotalGold; - } + public override int GetTotal(TotalType type) + { + if (AccountGold.Enabled && Owner?.Account != null && type == TotalType.Gold) return Owner.Account.TotalGold; - return base.GetTotal(type); - } - } + return base.GetTotal(type); + } + } } \ No newline at end of file diff --git a/Server/Items/SecureTradeContainer.cs b/Server/Items/SecureTradeContainer.cs index 8fc00c67c..4381f001f 100644 --- a/Server/Items/SecureTradeContainer.cs +++ b/Server/Items/SecureTradeContainer.cs @@ -23,124 +23,100 @@ using Server.Network; namespace Server.Items { - public class SecureTradeContainer : Container - { - public SecureTrade Trade { get; } + public class SecureTradeContainer : Container + { + public SecureTradeContainer(SecureTrade trade) : base(0x1E5E) + { + Trade = trade; - public SecureTradeContainer( SecureTrade trade ) : base( 0x1E5E ) - { - Trade = trade; + Movable = false; + } - Movable = false; - } + public SecureTradeContainer(Serial serial) : base(serial) + { + } - public SecureTradeContainer( Serial serial ) : base( serial ) - { - } + public SecureTrade Trade{ get; } - public override bool CheckHold( Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight ) - { - if (item == Trade.From.VirtualCheck || item == Trade.To.VirtualCheck) - { - return true; - } + public override bool CheckHold(Mobile m, Item item, bool message, bool checkItems, int plusItems, int plusWeight) + { + if (item == Trade.From.VirtualCheck || item == Trade.To.VirtualCheck) return true; - Mobile to; + Mobile to; - if ( Trade.From.Container != this ) - to = Trade.From.Mobile; - else - to = Trade.To.Mobile; + if (Trade.From.Container != this) + to = Trade.From.Mobile; + else + to = Trade.To.Mobile; - return m.CheckTrade( to, item, this, message, checkItems, plusItems, plusWeight ); - } + return m.CheckTrade(to, item, this, message, checkItems, plusItems, plusWeight); + } - public override bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - reject = LRReason.CannotLift; - return false; - } + public override bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + reject = LRReason.CannotLift; + return false; + } - public override bool IsAccessibleTo( Mobile check ) - { - if ( !IsChildOf( check ) || Trade == null || !Trade.Valid ) - return false; + public override bool IsAccessibleTo(Mobile check) + { + if (!IsChildOf(check) || Trade == null || !Trade.Valid) + return false; - return base.IsAccessibleTo( check ); - } + return base.IsAccessibleTo(check); + } - public override void OnItemAdded( Item item ) - { - if ( !(item is VirtualCheck) ) - { - ClearChecks(); - } - } + public override void OnItemAdded(Item item) + { + if (!(item is VirtualCheck)) ClearChecks(); + } - public override void OnItemRemoved( Item item ) - { - if ( !(item is VirtualCheck) ) - { - ClearChecks(); - } - } + public override void OnItemRemoved(Item item) + { + if (!(item is VirtualCheck)) ClearChecks(); + } - public override void OnSubItemAdded( Item item ) - { - if ( !(item is VirtualCheck) ) - { - ClearChecks(); - } - } + public override void OnSubItemAdded(Item item) + { + if (!(item is VirtualCheck)) ClearChecks(); + } - public override void OnSubItemRemoved( Item item ) - { - if ( !(item is VirtualCheck) ) - { - ClearChecks(); - } - } + public override void OnSubItemRemoved(Item item) + { + if (!(item is VirtualCheck)) ClearChecks(); + } - public void ClearChecks( ) - { - if ( Trade != null ) - { - if ( Trade.From != null && !Trade.From.IsDisposed ) - { - Trade.From.Accepted = false; - } + public void ClearChecks() + { + if (Trade != null) + { + if (Trade.From != null && !Trade.From.IsDisposed) Trade.From.Accepted = false; - if ( Trade.To != null && !Trade.To.IsDisposed ) - { - Trade.To.Accepted = false; - } + if (Trade.To != null && !Trade.To.IsDisposed) Trade.To.Accepted = false; - Trade.Update(); - } - } + Trade.Update(); + } + } - public override bool IsChildVisibleTo( Mobile m, Item child ) - { - if (child is VirtualCheck) - { - return AccountGold.Enabled && (m.NetState == null || !m.NetState.NewSecureTrading); - } + public override bool IsChildVisibleTo(Mobile m, Item child) + { + if (child is VirtualCheck) return AccountGold.Enabled && (m.NetState == null || !m.NetState.NewSecureTrading); - return base.IsChildVisibleTo(m, child); - } + return base.IsChildVisibleTo(m, child); + } - public override void Serialize( GenericWriter writer ) - { - base.Serialize( writer ); + public override void Serialize(GenericWriter writer) + { + base.Serialize(writer); - writer.Write( (int) 0 ); // version - } + writer.Write(0); // version + } - public override void Deserialize( GenericReader reader ) - { - base.Deserialize( reader ); + public override void Deserialize(GenericReader reader) + { + base.Deserialize(reader); - int version = reader.ReadInt(); - } - } + int version = reader.ReadInt(); + } + } } \ No newline at end of file diff --git a/Server/Items/VirtualCheck.cs b/Server/Items/VirtualCheck.cs index 27e7d6933..32f546d6a 100644 --- a/Server/Items/VirtualCheck.cs +++ b/Server/Items/VirtualCheck.cs @@ -1,391 +1,367 @@ #region Header + // ********** // ServUO - VirtualCheck.cs // ********** + #endregion #region References -using System; + using System.Drawing; using Server.Gumps; +using Server.Items; using Server.Network; + #endregion namespace Server { - public sealed class VirtualCheck : Item - { - public static bool UseEditGump = false; - - public override bool IsVirtualItem => true; - - public override bool DisplayWeight => false; - public override bool DisplayLootType => false; - - public override double DefaultWeight => 0; - - public override string DefaultName => "Offer Of Currency"; - - public EditGump Editor { get; private set; } - - private int _Plat; - - [CommandProperty(AccessLevel.Administrator)] - public int Plat - { - get => _Plat; - set - { - _Plat = value; - InvalidateProperties(); - } - } - - private int _Gold; - - [CommandProperty(AccessLevel.Administrator)] - public int Gold - { - get => _Gold; - set - { - _Gold = value; - InvalidateProperties(); - } - } - - public VirtualCheck() - : this(0, 0) - { } - - public VirtualCheck(int plat, int gold) - : base(0x14F0) - { - Plat = plat; - Gold = gold; - - Movable = false; - } - - public VirtualCheck(Serial serial) - : base(serial) - { } - - public override bool IsAccessibleTo(Mobile check) - { - var c = GetSecureTradeCont(); - - if (check == null || c == null) - { - return base.IsAccessibleTo(check); - } - - return c.RootParent == check && IsChildOf(c); - } - - public override void OnDoubleClickSecureTrade(Mobile from) - { - if (UseEditGump && IsAccessibleTo(from)) - { - if (Editor?.Check == null || Editor.Check.Deleted) - { - Editor = new EditGump(from, this); - Editor.Send(); - } - else - { - Editor.Refresh(true); - } - } - else - { - if (Editor != null) - { - Editor.Close(); - Editor = null; - } - - base.OnDoubleClickSecureTrade(from); - } - } - - public override void OnSingleClick(Mobile from) - { - LabelTo(from, "Offer: {0:#,0} platinum, {1:#,0} gold", Plat, Gold); - } - - public override void GetProperties(ObjectPropertyList list) - { - base.GetProperties(list); - - list.Add(1060738, $"{Plat:#,0} platinum, {Gold:#,0} gold"); // value: ~1_val~ - } - - public void UpdateTrade(Mobile user) - { - var c = GetSecureTradeCont(); - - if (c?.Trade == null) - { - return; - } - - if (user == c.Trade.From.Mobile) - { - c.Trade.UpdateFromCurrency(); - } - else if (user == c.Trade.To.Mobile) - { - c.Trade.UpdateToCurrency(); - } - - c.ClearChecks(); - } - - public override void OnAfterDelete() - { - base.OnAfterDelete(); - - if (Editor != null) - { - Editor.Close(); - Editor = null; - } - } - - public override void Serialize(GenericWriter writer) - { } - - public override void Deserialize(GenericReader reader) - { - Delete(); - } - - public class EditGump : Gump - { - public enum Buttons - { - Close, - Clear, - Accept, - AllPlat, - AllGold - } - - private int _Plat, _Gold; - - public Mobile User { get; private set; } - public VirtualCheck Check { get; private set; } - - public EditGump(Mobile user, VirtualCheck check) - : base(50, 50) - { - User = user; - Check = check; - - _Plat = Check.Plat; - _Gold = Check.Gold; - - Closable = true; - Disposable = true; - Dragable = true; - Resizable = false; - - User.CloseGump(GetType()); - - CompileLayout(); - } - - public override void OnServerClose(NetState owner) - { - base.OnServerClose(owner); - - if (Check != null && !Check.Deleted) - { - Check.UpdateTrade(User); - } - } - - public void Close() - { - User.CloseGump(GetType()); - - if (Check != null && !Check.Deleted) - { - Check.UpdateTrade(User); - } - else - { - Check = null; - } - } - - public void Send() - { - if (Check != null && !Check.Deleted) - { - User.SendGump(this); - } - else - { - Close(); - } - } - - public void Refresh(bool recompile) - { - if (Check == null || Check.Deleted) - { - Close(); - return; - } - - if (recompile) - { - CompileLayout(); - } - - Close(); - Send(); - } - - private void CompileLayout() - { - if (Check == null || Check.Deleted) - { - return; - } - - Entries.ForEach(e => e.Parent = null); - Entries.Clear(); - - AddPage(0); - - AddBackground(0, 0, 400, 160, 3500); - - // Title - AddImageTiled(25, 35, 350, 3, 96); - AddImage(10, 8, 113); - AddImage(360, 8, 113); - - var title = - $"
BANK OF {User.RawName.ToUpper()}
"; - - AddHtml(40, 15, 320, 20, title, false, false); - - // Platinum Row - AddBackground(15, 60, 175, 20, 9300); - AddBackground(20, 45, 165, 30, 9350); - AddItem(20, 45, 3826); // Plat - AddLabel(60, 50, 0, User.Account.TotalPlat.ToString("#,0")); - - AddButton(195, 50, 95, 95, (int)Buttons.AllPlat, GumpButtonType.Reply, 0); // -> - - AddBackground(210, 60, 175, 20, 9300); - AddBackground(215, 45, 165, 30, 9350); - AddTextEntry(225, 50, 145, 20, 0, 0, _Plat.ToString(), User.Account.TotalPlat.ToString().Length); - - // Gold Row - AddBackground(15, 100, 175, 20, 9300); - AddBackground(20, 85, 165, 30, 9350); - AddItem(20, 85, 3823); // Gold - AddLabel(60, 90, 0, User.Account.TotalGold.ToString("#,0")); - - AddButton(195, 90, 95, 95, (int)Buttons.AllGold, GumpButtonType.Reply, 0); // -> - - AddBackground(210, 100, 175, 20, 9300); - AddBackground(215, 85, 165, 30, 9350); - AddTextEntry(225, 90, 145, 20, 0, 1, _Gold.ToString(), User.Account.TotalGold.ToString().Length); - - // Buttons - AddButton(20, 128, 12006, 12007, (int)Buttons.Close, GumpButtonType.Reply, 0); - AddButton(215, 128, 12003, 12004, (int)Buttons.Clear, GumpButtonType.Reply, 0); - AddButton(305, 128, 12000, 12002, (int)Buttons.Accept, GumpButtonType.Reply, 0); - } - - public override void OnResponse(NetState sender, RelayInfo info) - { - if (Check == null || Check.Deleted || sender.Mobile != User) - { - Close(); - return; - } - - bool refresh = false, updated = false; - - switch ((Buttons)info.ButtonID) - { - case Buttons.Close: - break; - case Buttons.Clear: - { - _Plat = _Gold = 0; - refresh = true; - } - break; - case Buttons.Accept: - { - var platText = info.GetTextEntry(0).Text; - var goldText = info.GetTextEntry(1).Text; - - if (!int.TryParse(platText, out _Plat)) - { - User.SendMessage("That is not a valid amount of platinum."); - refresh = true; - } - else if (!int.TryParse(goldText, out _Gold)) - { - User.SendMessage("That is not a valid amount of gold."); - refresh = true; - } - else - { - int totalPlat = User.Account.TotalPlat; - int totalGold = User.Account.TotalGold; - - if (totalPlat < _Plat || totalGold < _Gold) - { - _Plat = User.Account.TotalPlat; - _Gold = User.Account.TotalGold; - User.SendMessage("You do not have that much currency."); - refresh = true; - } - else - { - Check.Plat = _Plat; - Check.Gold = _Gold; - updated = true; - } - } - } - break; - case Buttons.AllPlat: - { - _Plat = User.Account.TotalPlat; - refresh = true; - } - break; - case Buttons.AllGold: - { - _Gold = User.Account.TotalGold; - refresh = true; - } - break; - } - - if (updated) - { - User.SendMessage("Your offer has been updated."); - } - - if (refresh && Check != null && !Check.Deleted) - { - Refresh(true); - return; - } - - Close(); - } - } - } -} + public sealed class VirtualCheck : Item + { + public static bool UseEditGump = false; + + private int _Gold; + + private int _Plat; + + public VirtualCheck() + : this(0, 0) + { + } + + public VirtualCheck(int plat, int gold) + : base(0x14F0) + { + Plat = plat; + Gold = gold; + + Movable = false; + } + + public VirtualCheck(Serial serial) + : base(serial) + { + } + + public override bool IsVirtualItem => true; + + public override bool DisplayWeight => false; + public override bool DisplayLootType => false; + + public override double DefaultWeight => 0; + + public override string DefaultName => "Offer Of Currency"; + + public EditGump Editor{ get; private set; } + + [CommandProperty(AccessLevel.Administrator)] + public int Plat + { + get => _Plat; + set + { + _Plat = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.Administrator)] + public int Gold + { + get => _Gold; + set + { + _Gold = value; + InvalidateProperties(); + } + } + + public override bool IsAccessibleTo(Mobile check) + { + SecureTradeContainer c = GetSecureTradeCont(); + + if (check == null || c == null) return base.IsAccessibleTo(check); + + return c.RootParent == check && IsChildOf(c); + } + + public override void OnDoubleClickSecureTrade(Mobile from) + { + if (UseEditGump && IsAccessibleTo(from)) + { + if (Editor?.Check == null || Editor.Check.Deleted) + { + Editor = new EditGump(from, this); + Editor.Send(); + } + else + { + Editor.Refresh(true); + } + } + else + { + if (Editor != null) + { + Editor.Close(); + Editor = null; + } + + base.OnDoubleClickSecureTrade(from); + } + } + + public override void OnSingleClick(Mobile from) + { + LabelTo(from, "Offer: {0:#,0} platinum, {1:#,0} gold", Plat, Gold); + } + + public override void GetProperties(ObjectPropertyList list) + { + base.GetProperties(list); + + list.Add(1060738, $"{Plat:#,0} platinum, {Gold:#,0} gold"); // value: ~1_val~ + } + + public void UpdateTrade(Mobile user) + { + SecureTradeContainer c = GetSecureTradeCont(); + + if (c?.Trade == null) return; + + if (user == c.Trade.From.Mobile) + c.Trade.UpdateFromCurrency(); + else if (user == c.Trade.To.Mobile) c.Trade.UpdateToCurrency(); + + c.ClearChecks(); + } + + public override void OnAfterDelete() + { + base.OnAfterDelete(); + + if (Editor != null) + { + Editor.Close(); + Editor = null; + } + } + + public override void Serialize(GenericWriter writer) + { + } + + public override void Deserialize(GenericReader reader) + { + Delete(); + } + + public class EditGump : Gump + { + public enum Buttons + { + Close, + Clear, + Accept, + AllPlat, + AllGold + } + + private int _Plat, _Gold; + + public EditGump(Mobile user, VirtualCheck check) + : base(50, 50) + { + User = user; + Check = check; + + _Plat = Check.Plat; + _Gold = Check.Gold; + + Closable = true; + Disposable = true; + Dragable = true; + Resizable = false; + + User.CloseGump(GetType()); + + CompileLayout(); + } + + public Mobile User{ get; } + public VirtualCheck Check{ get; private set; } + + public override void OnServerClose(NetState owner) + { + base.OnServerClose(owner); + + if (Check != null && !Check.Deleted) Check.UpdateTrade(User); + } + + public void Close() + { + User.CloseGump(GetType()); + + if (Check != null && !Check.Deleted) + Check.UpdateTrade(User); + else + Check = null; + } + + public void Send() + { + if (Check != null && !Check.Deleted) + User.SendGump(this); + else + Close(); + } + + public void Refresh(bool recompile) + { + if (Check == null || Check.Deleted) + { + Close(); + return; + } + + if (recompile) CompileLayout(); + + Close(); + Send(); + } + + private void CompileLayout() + { + if (Check == null || Check.Deleted) return; + + Entries.ForEach(e => e.Parent = null); + Entries.Clear(); + + AddPage(0); + + AddBackground(0, 0, 400, 160, 3500); + + // Title + AddImageTiled(25, 35, 350, 3, 96); + AddImage(10, 8, 113); + AddImage(360, 8, 113); + + string title = + $"
BANK OF {User.RawName.ToUpper()}
"; + + AddHtml(40, 15, 320, 20, title, false, false); + + // Platinum Row + AddBackground(15, 60, 175, 20, 9300); + AddBackground(20, 45, 165, 30, 9350); + AddItem(20, 45, 3826); // Plat + AddLabel(60, 50, 0, User.Account.TotalPlat.ToString("#,0")); + + AddButton(195, 50, 95, 95, (int)Buttons.AllPlat, GumpButtonType.Reply, 0); // -> + + AddBackground(210, 60, 175, 20, 9300); + AddBackground(215, 45, 165, 30, 9350); + AddTextEntry(225, 50, 145, 20, 0, 0, _Plat.ToString(), User.Account.TotalPlat.ToString().Length); + + // Gold Row + AddBackground(15, 100, 175, 20, 9300); + AddBackground(20, 85, 165, 30, 9350); + AddItem(20, 85, 3823); // Gold + AddLabel(60, 90, 0, User.Account.TotalGold.ToString("#,0")); + + AddButton(195, 90, 95, 95, (int)Buttons.AllGold, GumpButtonType.Reply, 0); // -> + + AddBackground(210, 100, 175, 20, 9300); + AddBackground(215, 85, 165, 30, 9350); + AddTextEntry(225, 90, 145, 20, 0, 1, _Gold.ToString(), User.Account.TotalGold.ToString().Length); + + // Buttons + AddButton(20, 128, 12006, 12007, (int)Buttons.Close, GumpButtonType.Reply, 0); + AddButton(215, 128, 12003, 12004, (int)Buttons.Clear, GumpButtonType.Reply, 0); + AddButton(305, 128, 12000, 12002, (int)Buttons.Accept, GumpButtonType.Reply, 0); + } + + public override void OnResponse(NetState sender, RelayInfo info) + { + if (Check == null || Check.Deleted || sender.Mobile != User) + { + Close(); + return; + } + + bool refresh = false, updated = false; + + switch ((Buttons)info.ButtonID) + { + case Buttons.Close: + break; + case Buttons.Clear: + { + _Plat = _Gold = 0; + refresh = true; + } + break; + case Buttons.Accept: + { + string platText = info.GetTextEntry(0).Text; + string goldText = info.GetTextEntry(1).Text; + + if (!int.TryParse(platText, out _Plat)) + { + User.SendMessage("That is not a valid amount of platinum."); + refresh = true; + } + else if (!int.TryParse(goldText, out _Gold)) + { + User.SendMessage("That is not a valid amount of gold."); + refresh = true; + } + else + { + int totalPlat = User.Account.TotalPlat; + int totalGold = User.Account.TotalGold; + + if (totalPlat < _Plat || totalGold < _Gold) + { + _Plat = User.Account.TotalPlat; + _Gold = User.Account.TotalGold; + User.SendMessage("You do not have that much currency."); + refresh = true; + } + else + { + Check.Plat = _Plat; + Check.Gold = _Gold; + updated = true; + } + } + } + break; + case Buttons.AllPlat: + { + _Plat = User.Account.TotalPlat; + refresh = true; + } + break; + case Buttons.AllGold: + { + _Gold = User.Account.TotalGold; + refresh = true; + } + break; + } + + if (updated) User.SendMessage("Your offer has been updated."); + + if (refresh && Check != null && !Check.Deleted) + { + Refresh(true); + return; + } + + Close(); + } + } + } +} \ No newline at end of file diff --git a/Server/Items/VirtualHair.cs b/Server/Items/VirtualHair.cs index cd03fe889..10fbf3547 100644 --- a/Server/Items/VirtualHair.cs +++ b/Server/Items/VirtualHair.cs @@ -22,151 +22,151 @@ using Server.Network; namespace Server { - public abstract class BaseHairInfo - { - [CommandProperty( AccessLevel.GameMaster )] - public int ItemID { get; set; } + public abstract class BaseHairInfo + { + protected BaseHairInfo(int itemid) + : this(itemid, 0) + { + } - [CommandProperty( AccessLevel.GameMaster )] - public int Hue { get; set; } + protected BaseHairInfo(int itemid, int hue) + { + ItemID = itemid; + Hue = hue; + } - protected BaseHairInfo( int itemid ) - : this( itemid, 0 ) - { - } + protected BaseHairInfo(GenericReader reader) + { + int version = reader.ReadInt(); - protected BaseHairInfo( int itemid, int hue ) - { - ItemID = itemid; - Hue = hue; - } + switch (version) + { + case 0: + { + ItemID = reader.ReadInt(); + Hue = reader.ReadInt(); + break; + } + } + } - protected BaseHairInfo( GenericReader reader ) - { - int version = reader.ReadInt(); + [CommandProperty(AccessLevel.GameMaster)] + public int ItemID{ get; set; } - switch( version ) - { - case 0: - { - ItemID = reader.ReadInt(); - Hue = reader.ReadInt(); - break; - } - } - } + [CommandProperty(AccessLevel.GameMaster)] + public int Hue{ get; set; } - public virtual void Serialize( GenericWriter writer ) - { - writer.Write( (int)0 ); //version - writer.Write( (int)ItemID ); - writer.Write( (int)Hue ); - } - } + public virtual void Serialize(GenericWriter writer) + { + writer.Write(0); //version + writer.Write(ItemID); + writer.Write(Hue); + } + } - public class HairInfo : BaseHairInfo - { - public HairInfo( int itemid ) - : base( itemid, 0 ) - { - } + public class HairInfo : BaseHairInfo + { + public HairInfo(int itemid) + : base(itemid, 0) + { + } - public HairInfo( int itemid, int hue ) - : base( itemid, hue ) - { - } + public HairInfo(int itemid, int hue) + : base(itemid, hue) + { + } - public HairInfo( GenericReader reader ) - : base( reader ) - { - } + public HairInfo(GenericReader reader) + : base(reader) + { + } - public static int FakeSerial( Mobile parent ) - { - return (0x7FFFFFFF - 0x400 - (parent.Serial * 4)); - } - } + public static int FakeSerial(Mobile parent) + { + return 0x7FFFFFFF - 0x400 - parent.Serial * 4; + } + } - public class FacialHairInfo : BaseHairInfo - { - public FacialHairInfo( int itemid ) - : base( itemid, 0 ) - { - } + public class FacialHairInfo : BaseHairInfo + { + public FacialHairInfo(int itemid) + : base(itemid, 0) + { + } - public FacialHairInfo( int itemid, int hue ) - : base( itemid, hue ) - { - } + public FacialHairInfo(int itemid, int hue) + : base(itemid, hue) + { + } - public FacialHairInfo( GenericReader reader ) - : base( reader ) - { - } + public FacialHairInfo(GenericReader reader) + : base(reader) + { + } - public static int FakeSerial( Mobile parent ) - { - return (0x7FFFFFFF - 0x400 - 1 - (parent.Serial * 4)); - } - } + public static int FakeSerial(Mobile parent) + { + return 0x7FFFFFFF - 0x400 - 1 - parent.Serial * 4; + } + } - public sealed class HairEquipUpdate : Packet - { - public HairEquipUpdate( Mobile parent ) - : base( 0x2E, 15 ) - { - int hue = parent.HairHue; + public sealed class HairEquipUpdate : Packet + { + public HairEquipUpdate(Mobile parent) + : base(0x2E, 15) + { + int hue = parent.HairHue; - if ( parent.SolidHueOverride >= 0 ) - hue = parent.SolidHueOverride; + if (parent.SolidHueOverride >= 0) + hue = parent.SolidHueOverride; - int hairSerial = HairInfo.FakeSerial( parent ); + int hairSerial = HairInfo.FakeSerial(parent); - m_Stream.Write( (int)hairSerial ); - m_Stream.Write( (short)parent.HairItemID ); - m_Stream.Write( (byte)0 ); - m_Stream.Write( (byte)Layer.Hair ); - m_Stream.Write( (int)parent.Serial ); - m_Stream.Write( (short)hue ); - } - } + m_Stream.Write(hairSerial); + m_Stream.Write((short)parent.HairItemID); + m_Stream.Write((byte)0); + m_Stream.Write((byte)Layer.Hair); + m_Stream.Write(parent.Serial); + m_Stream.Write((short)hue); + } + } - public sealed class FacialHairEquipUpdate : Packet - { - public FacialHairEquipUpdate( Mobile parent ) - : base( 0x2E, 15 ) - { - int hue = parent.FacialHairHue; + public sealed class FacialHairEquipUpdate : Packet + { + public FacialHairEquipUpdate(Mobile parent) + : base(0x2E, 15) + { + int hue = parent.FacialHairHue; - if ( parent.SolidHueOverride >= 0 ) - hue = parent.SolidHueOverride; + if (parent.SolidHueOverride >= 0) + hue = parent.SolidHueOverride; - int hairSerial = FacialHairInfo.FakeSerial( parent ); + int hairSerial = FacialHairInfo.FakeSerial(parent); - m_Stream.Write( (int)hairSerial ); - m_Stream.Write( (short)parent.FacialHairItemID ); - m_Stream.Write( (byte)0 ); - m_Stream.Write( (byte)Layer.FacialHair ); - m_Stream.Write( (int)parent.Serial ); - m_Stream.Write( (short)hue ); - } - } + m_Stream.Write(hairSerial); + m_Stream.Write((short)parent.FacialHairItemID); + m_Stream.Write((byte)0); + m_Stream.Write((byte)Layer.FacialHair); + m_Stream.Write(parent.Serial); + m_Stream.Write((short)hue); + } + } - public sealed class RemoveHair : Packet - { - public RemoveHair( Mobile parent ) - : base( 0x1D, 5 ) - { - m_Stream.Write( (int)HairInfo.FakeSerial( parent ) ); - } - } + public sealed class RemoveHair : Packet + { + public RemoveHair(Mobile parent) + : base(0x1D, 5) + { + m_Stream.Write(HairInfo.FakeSerial(parent)); + } + } - public sealed class RemoveFacialHair : Packet - { - public RemoveFacialHair( Mobile parent ) - : base( 0x1D, 5 ) - { - m_Stream.Write( (int)FacialHairInfo.FakeSerial( parent ) ); - } - } -} + public sealed class RemoveFacialHair : Packet + { + public RemoveFacialHair(Mobile parent) + : base(0x1D, 5) + { + m_Stream.Write(FacialHairInfo.FakeSerial(parent)); + } + } +} \ No newline at end of file diff --git a/Server/KeywordList.cs b/Server/KeywordList.cs index 1746ec63b..a51a296b6 100644 --- a/Server/KeywordList.cs +++ b/Server/KeywordList.cs @@ -20,57 +20,56 @@ namespace Server { - public class KeywordList - { - private int[] m_Keywords; + public class KeywordList + { + private static int[] m_EmptyInts = new int[0]; + private int[] m_Keywords; - public KeywordList() - { - m_Keywords = new int[8]; - Count = 0; - } + public KeywordList() + { + m_Keywords = new int[8]; + Count = 0; + } - public int Count { get; private set; } + public int Count{ get; private set; } - public bool Contains( int keyword ) - { - bool contains = false; + public bool Contains(int keyword) + { + bool contains = false; - for ( int i = 0; !contains && i < Count; ++i ) - contains = ( keyword == m_Keywords[i] ); + for (int i = 0; !contains && i < Count; ++i) + contains = keyword == m_Keywords[i]; - return contains; - } + return contains; + } - public void Add( int keyword ) - { - if ( (Count + 1) > m_Keywords.Length ) - { - int[] old = m_Keywords; - m_Keywords = new int[old.Length * 2]; + public void Add(int keyword) + { + if (Count + 1 > m_Keywords.Length) + { + int[] old = m_Keywords; + m_Keywords = new int[old.Length * 2]; - for ( int i = 0; i < old.Length; ++i ) - m_Keywords[i] = old[i]; - } + for (int i = 0; i < old.Length; ++i) + m_Keywords[i] = old[i]; + } - m_Keywords[Count++] = keyword; - } + m_Keywords[Count++] = keyword; + } - private static int[] m_EmptyInts = new int[0]; + public int[] ToArray() + { + if (Count == 0) + return m_EmptyInts; - public int[] ToArray() - { - if ( Count == 0 ) - return m_EmptyInts; + int[] keywords = new int[Count]; - int[] keywords = new int[Count]; + for (int i = 0; i < Count; ++i) + keywords[i] = m_Keywords[i]; - for ( int i = 0; i < Count; ++i ) - keywords[i] = m_Keywords[i]; + Count = 0; - Count = 0; - - return keywords; - } - } + return keywords; + } + } } \ No newline at end of file diff --git a/Server/Main.cs b/Server/Main.cs index 039ed1d85..8974ebebb 100644 --- a/Server/Main.cs +++ b/Server/Main.cs @@ -24,742 +24,713 @@ using System.Diagnostics; using System.IO; using System.Linq; using System.Reflection; +using System.Runtime; using System.Runtime.InteropServices; using System.Text; using System.Threading; using System.Threading.Tasks; using Server.Network; -using System.Runtime; namespace Server { - public delegate void Slice(); + public delegate void Slice(); - public static class Core - { - private static bool m_Crashed; - private static Thread timerThread; - private static string m_BaseDirectory; - private static string m_ExePath; + public static class Core + { + private static bool m_Crashed; + private static Thread timerThread; + private static string m_BaseDirectory; + private static string m_ExePath; - private static bool m_Cache = true; + private static bool m_Cache = true; - private static bool m_Profiling; - private static DateTime m_ProfileStart; - private static TimeSpan m_ProfileTime; + private static bool m_Profiling; + private static DateTime m_ProfileStart; + private static TimeSpan m_ProfileTime; - public static MessagePump MessagePump { get; set; } + public static Slice Slice; - public static Slice Slice; + /* + * DateTime.Now and DateTime.UtcNow are based on actual system clock time. + * The resolution is acceptable but large clock jumps are possible and cause issues. + * GetTickCount and GetTickCount64 have poor resolution. + * GetTickCount64 is unavailable on Windows XP and Windows Server 2003. + * Stopwatch.GetTimestamp() (QueryPerformanceCounter) is high resolution, but + * somewhat expensive to call because of its defference to DateTime.Now, + * which is why Stopwatch has been used to verify HRT before calling GetTimestamp(), + * enabling the usage of DateTime.UtcNow instead. + */ - public static bool Profiling - { - get => m_Profiling; - set - { - if ( m_Profiling == value ) - return; + private static readonly bool _HighRes = Stopwatch.IsHighResolution; - m_Profiling = value; + private static readonly double _HighFrequency = 1000.0 / Stopwatch.Frequency; + private static readonly double _LowFrequency = 1000.0 / TimeSpan.TicksPerSecond; - if ( m_ProfileStart > DateTime.MinValue ) - m_ProfileTime += DateTime.UtcNow - m_ProfileStart; + private static bool _UseHRT; - m_ProfileStart = (m_Profiling ? DateTime.UtcNow : DateTime.MinValue); - } - } + public static readonly bool Is64Bit = Environment.Is64BitProcess; + internal static ConsoleEventHandler m_ConsoleEventHandler; - public static TimeSpan ProfileTime - { - get - { - if ( m_ProfileStart > DateTime.MinValue ) - return m_ProfileTime + (DateTime.UtcNow - m_ProfileStart); + private static int m_CycleIndex = 1; + private static readonly float[] m_CyclesPerSecond = new float[100]; - return m_ProfileTime; - } - } + private static readonly AutoResetEvent m_Signal = new AutoResetEvent(true); - public static bool Service { get; private set; } + private static int m_ItemCount, m_MobileCount; - public static bool Debug { get; private set; } + private static readonly Type[] m_SerialTypeArray = { typeof(Serial) }; - internal static bool HaltOnWarning { get; private set; } + public static MessagePump MessagePump{ get; set; } - internal static bool VBdotNet { get; private set; } + public static bool Profiling + { + get => m_Profiling; + set + { + if (m_Profiling == value) + return; - public static List DataDirectories { get; } = new List(); + m_Profiling = value; - public static Assembly Assembly { get; set; } + if (m_ProfileStart > DateTime.MinValue) + m_ProfileTime += DateTime.UtcNow - m_ProfileStart; - public static Version Version => Assembly.GetName().Version; - public static Process Process { get; private set; } + m_ProfileStart = m_Profiling ? DateTime.UtcNow : DateTime.MinValue; + } + } - public static Thread Thread { get; private set; } + public static TimeSpan ProfileTime + { + get + { + if (m_ProfileStart > DateTime.MinValue) + return m_ProfileTime + (DateTime.UtcNow - m_ProfileStart); - public static MultiTextWriter MultiConsoleOut { get; private set; } + return m_ProfileTime; + } + } - /* - * DateTime.Now and DateTime.UtcNow are based on actual system clock time. - * The resolution is acceptable but large clock jumps are possible and cause issues. - * GetTickCount and GetTickCount64 have poor resolution. - * GetTickCount64 is unavailable on Windows XP and Windows Server 2003. - * Stopwatch.GetTimestamp() (QueryPerformanceCounter) is high resolution, but - * somewhat expensive to call because of its defference to DateTime.Now, - * which is why Stopwatch has been used to verify HRT before calling GetTimestamp(), - * enabling the usage of DateTime.UtcNow instead. - */ + public static bool Service{ get; private set; } - private static readonly bool _HighRes = Stopwatch.IsHighResolution; + public static bool Debug{ get; private set; } - private static readonly double _HighFrequency = 1000.0 / Stopwatch.Frequency; - private static readonly double _LowFrequency = 1000.0 / TimeSpan.TicksPerSecond; + internal static bool HaltOnWarning{ get; private set; } - private static bool _UseHRT; + internal static bool VBdotNet{ get; private set; } - public static bool UsingHighResolutionTiming => _UseHRT && _HighRes && !Unix; + public static List DataDirectories{ get; } = new List(); - public static long TickCount => (long)Ticks; + public static Assembly Assembly{ get; set; } - public static double Ticks - { - get - { - if (_UseHRT && _HighRes && !Unix) - { - return Stopwatch.GetTimestamp() * _HighFrequency; - } + public static Version Version => Assembly.GetName().Version; + public static Process Process{ get; private set; } - return DateTime.UtcNow.Ticks * _LowFrequency; - } - } + public static Thread Thread{ get; private set; } - public static readonly bool Is64Bit = Environment.Is64BitProcess; + public static MultiTextWriter MultiConsoleOut{ get; private set; } - public static bool MultiProcessor { get; private set; } + public static bool UsingHighResolutionTiming => _UseHRT && _HighRes && !Unix; - public static int ProcessorCount { get; private set; } + public static long TickCount => (long)Ticks; - public static bool Unix { get; private set; } + public static double Ticks + { + get + { + if (_UseHRT && _HighRes && !Unix) return Stopwatch.GetTimestamp() * _HighFrequency; - public static string FindDataFile( string path ) - { - if ( DataDirectories.Count == 0 ) - throw new InvalidOperationException( "Attempted to FindDataFile before DataDirectories list has been filled." ); + return DateTime.UtcNow.Ticks * _LowFrequency; + } + } - string fullPath = null; + public static bool MultiProcessor{ get; private set; } - foreach (string p in DataDirectories) - { - fullPath = Path.Combine( p, path ); + public static int ProcessorCount{ get; private set; } - if ( File.Exists( fullPath ) ) - break; + public static bool Unix{ get; private set; } - fullPath = null; - } + public static string ExePath => m_ExePath ?? (m_ExePath = Assembly.Location); - return fullPath; - } + public static string BaseDirectory + { + get + { + if (m_BaseDirectory == null) + try + { + m_BaseDirectory = ExePath; - public static string FindDataFile( string format, params object[] args ) - { - return FindDataFile( string.Format( format, args ) ); - } + if (m_BaseDirectory.Length > 0) + m_BaseDirectory = Path.GetDirectoryName(m_BaseDirectory); + } + catch + { + m_BaseDirectory = ""; + } - #region Expansions + return m_BaseDirectory; + } + } - public static Expansion Expansion { get; set; } + public static bool Closing{ get; private set; } - public static bool T2A => Expansion >= Expansion.T2A; + public static float CyclesPerSecond => m_CyclesPerSecond[(m_CycleIndex - 1) % m_CyclesPerSecond.Length]; - public static bool UOR => Expansion >= Expansion.UOR; + public static float AverageCPS => m_CyclesPerSecond.Take(m_CycleIndex).Average(); - public static bool UOTD => Expansion >= Expansion.UOTD; + public static string Arguments + { + get + { + StringBuilder sb = new StringBuilder(); - public static bool LBR => Expansion >= Expansion.LBR; + if (Debug) + Utility.Separate(sb, "-debug", " "); - public static bool AOS => Expansion >= Expansion.AOS; + if (Service) + Utility.Separate(sb, "-service", " "); - public static bool SE => Expansion >= Expansion.SE; + if (m_Profiling) + Utility.Separate(sb, "-profile", " "); - public static bool ML => Expansion >= Expansion.ML; + if (!m_Cache) + Utility.Separate(sb, "-nocache", " "); - public static bool SA => Expansion >= Expansion.SA; + if (HaltOnWarning) + Utility.Separate(sb, "-haltonwarning", " "); - public static bool HS => Expansion >= Expansion.HS; + if (VBdotNet) + Utility.Separate(sb, "-vb", " "); - public static bool TOL => Expansion >= Expansion.TOL; + if (_UseHRT) + Utility.Separate(sb, "-usehrt", " "); - #endregion + return sb.ToString(); + } + } - public static string ExePath => m_ExePath ?? (m_ExePath = Assembly.Location); + public static int GlobalUpdateRange{ get; set; } = 18; - public static string BaseDirectory - { - get - { - if ( m_BaseDirectory == null ) - { - try - { - m_BaseDirectory = ExePath; + public static int GlobalMaxUpdateRange{ get; set; } = 24; - if ( m_BaseDirectory.Length > 0 ) - m_BaseDirectory = Path.GetDirectoryName( m_BaseDirectory ); - } - catch - { - m_BaseDirectory = ""; - } - } + public static int ScriptItems => m_ItemCount; + public static int ScriptMobiles => m_MobileCount; - return m_BaseDirectory; - } - } + public static string FindDataFile(string path) + { + if (DataDirectories.Count == 0) + throw new InvalidOperationException( + "Attempted to FindDataFile before DataDirectories list has been filled."); - private static void CurrentDomain_UnhandledException( object sender, UnhandledExceptionEventArgs e ) - { - Console.WriteLine( e.IsTerminating ? "Error:" : "Warning:" ); - Console.WriteLine( e.ExceptionObject ); + string fullPath = null; - if ( e.IsTerminating ) - { - m_Crashed = true; + foreach (string p in DataDirectories) + { + fullPath = Path.Combine(p, path); - bool close = false; + if (File.Exists(fullPath)) + break; - try - { - CrashedEventArgs args = new CrashedEventArgs( e.ExceptionObject as Exception ); + fullPath = null; + } - EventSink.InvokeCrashed( args ); + return fullPath; + } - close = args.Close; - } - catch - { - } + public static string FindDataFile(string format, params object[] args) + { + return FindDataFile(string.Format(format, args)); + } - if ( !close && !Service ) - { - try - { - foreach (Listener l in MessagePump.Listeners) - { - l.Dispose(); - } - } - catch - { - } + private static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e) + { + Console.WriteLine(e.IsTerminating ? "Error:" : "Warning:"); + Console.WriteLine(e.ExceptionObject); - Console.WriteLine( "This exception is fatal, press return to exit" ); - Console.ReadLine(); - } + if (e.IsTerminating) + { + m_Crashed = true; - Kill(); - } - } + bool close = false; - internal enum ConsoleEventType - { - CTRL_C_EVENT, - CTRL_BREAK_EVENT, - CTRL_CLOSE_EVENT, - CTRL_LOGOFF_EVENT=5, - CTRL_SHUTDOWN_EVENT - } + try + { + CrashedEventArgs args = new CrashedEventArgs(e.ExceptionObject as Exception); - internal delegate bool ConsoleEventHandler( ConsoleEventType type ); - internal static ConsoleEventHandler m_ConsoleEventHandler; + EventSink.InvokeCrashed(args); - internal class UnsafeNativeMethods { - [DllImport("Kernel32")] - internal static extern bool SetConsoleCtrlHandler(ConsoleEventHandler callback, bool add); - } - - private static bool OnConsoleEvent( ConsoleEventType type ) - { - if ( World.Saving || ( Service && type == ConsoleEventType.CTRL_LOGOFF_EVENT ) ) - return true; - - Kill(); //Kill -> HandleClosed will handle waiting for the completion of flushing to disk - - return true; - } - - private static void CurrentDomain_ProcessExit( object sender, EventArgs e ) - { - HandleClosed(); - } - - public static bool Closing { get; private set; } - - private static int m_CycleIndex = 1; - private static readonly float[] m_CyclesPerSecond = new float[100]; - - public static float CyclesPerSecond => m_CyclesPerSecond[(m_CycleIndex - 1) % m_CyclesPerSecond.Length]; - - public static float AverageCPS => m_CyclesPerSecond.Take(m_CycleIndex).Average(); - - public static void Kill() - { - Kill( false ); - } - - public static void Kill( bool restart ) - { - HandleClosed(); - - if ( restart ) - Process.Start( ExePath, Arguments ); - - Process.Kill(); - } - - private static void HandleClosed() - { - if ( Closing ) - return; - - Closing = true; - - Console.Write( "Exiting..." ); - - World.WaitForWriteCompletion(); - - if ( !m_Crashed ) - EventSink.InvokeShutdown( new ShutdownEventArgs() ); - - Timer.TimerThread.Set(); - - Console.WriteLine( "done" ); - } - - private static readonly AutoResetEvent m_Signal = new AutoResetEvent( true ); - - public static void Set() { m_Signal.Set(); } - - public static void Main( string[] args ) - { - AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException; - AppDomain.CurrentDomain.ProcessExit += CurrentDomain_ProcessExit; - - foreach (string a in args) - { - if ( Insensitive.Equals( a, "-debug" ) ) - Debug = true; - else if ( Insensitive.Equals( a, "-service" ) ) - Service = true; - else if ( Insensitive.Equals( a, "-profile" ) ) - Profiling = true; - else if ( Insensitive.Equals( a, "-nocache" ) ) - m_Cache = false; - else if ( Insensitive.Equals( a, "-haltonwarning" ) ) - HaltOnWarning = true; - else if ( Insensitive.Equals( a, "-vb" ) ) - VBdotNet = true; - else if ( Insensitive.Equals( a, "-usehrt" ) ) - _UseHRT = true; - } + close = args.Close; + } + catch + { + } - try - { - if ( Service ) - { - if ( !Directory.Exists( "Logs" ) ) - Directory.CreateDirectory( "Logs" ); + if (!close && !Service) + { + try + { + foreach (Listener l in MessagePump.Listeners) l.Dispose(); + } + catch + { + } + + Console.WriteLine("This exception is fatal, press return to exit"); + Console.ReadLine(); + } + + Kill(); + } + } - Console.SetOut( MultiConsoleOut = new MultiTextWriter( new FileLogger( "Logs/Console.log" ) ) ); - } - else - { - Console.SetOut( MultiConsoleOut = new MultiTextWriter( Console.Out ) ); - } - } - catch - { - } + private static bool OnConsoleEvent(ConsoleEventType type) + { + if (World.Saving || Service && type == ConsoleEventType.CTRL_LOGOFF_EVENT) + return true; + + Kill(); //Kill -> HandleClosed will handle waiting for the completion of flushing to disk + + return true; + } + + private static void CurrentDomain_ProcessExit(object sender, EventArgs e) + { + HandleClosed(); + } + + public static void Kill() + { + Kill(false); + } + + public static void Kill(bool restart) + { + HandleClosed(); + + if (restart) + Process.Start(ExePath, Arguments); + + Process.Kill(); + } + + private static void HandleClosed() + { + if (Closing) + return; + + Closing = true; + + Console.Write("Exiting..."); + + World.WaitForWriteCompletion(); + + if (!m_Crashed) + EventSink.InvokeShutdown(new ShutdownEventArgs()); + + Timer.TimerThread.Set(); + + Console.WriteLine("done"); + } + + public static void Set() + { + m_Signal.Set(); + } + + public static void Main(string[] args) + { + AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException; + AppDomain.CurrentDomain.ProcessExit += CurrentDomain_ProcessExit; + + foreach (string a in args) + if (Insensitive.Equals(a, "-debug")) + Debug = true; + else if (Insensitive.Equals(a, "-service")) + Service = true; + else if (Insensitive.Equals(a, "-profile")) + Profiling = true; + else if (Insensitive.Equals(a, "-nocache")) + m_Cache = false; + else if (Insensitive.Equals(a, "-haltonwarning")) + HaltOnWarning = true; + else if (Insensitive.Equals(a, "-vb")) + VBdotNet = true; + else if (Insensitive.Equals(a, "-usehrt")) + _UseHRT = true; + + try + { + if (Service) + { + if (!Directory.Exists("Logs")) + Directory.CreateDirectory("Logs"); + + Console.SetOut(MultiConsoleOut = new MultiTextWriter(new FileLogger("Logs/Console.log"))); + } + else + { + Console.SetOut(MultiConsoleOut = new MultiTextWriter(Console.Out)); + } + } + catch + { + } - Thread = Thread.CurrentThread; - Process = Process.GetCurrentProcess(); - Assembly = Assembly.GetEntryAssembly(); + Thread = Thread.CurrentThread; + Process = Process.GetCurrentProcess(); + Assembly = Assembly.GetEntryAssembly(); - if ( Thread != null ) - Thread.Name = "Core Thread"; + if (Thread != null) + Thread.Name = "Core Thread"; - if ( BaseDirectory.Length > 0 ) - Directory.SetCurrentDirectory( BaseDirectory ); + if (BaseDirectory.Length > 0) + Directory.SetCurrentDirectory(BaseDirectory); - Timer.TimerThread ttObj = new Timer.TimerThread(); - timerThread = new Thread(ttObj.TimerMain) - { - Name = "Timer Thread" - }; + Timer.TimerThread ttObj = new Timer.TimerThread(); + timerThread = new Thread(ttObj.TimerMain) + { + Name = "Timer Thread" + }; - Version ver = Assembly.GetName().Version; + Version ver = Assembly.GetName().Version; - // Added to help future code support on forums, as a 'check' people can ask for to it see if they recompiled core or not - Console.WriteLine("RunUO - [https://github.com/runuo/] Version {0}.{1}.{2}.{3}", ver.Major, ver.Minor, ver.Build, ver.Revision); - Console.WriteLine("Core: Running on .NET Framework Version {0}.{1}.{2}", Environment.Version.Major, Environment.Version.Minor, Environment.Version.Build); + // Added to help future code support on forums, as a 'check' people can ask for to it see if they recompiled core or not + Console.WriteLine("RunUO - [https://github.com/runuo/] Version {0}.{1}.{2}.{3}", ver.Major, ver.Minor, ver.Build, + ver.Revision); + Console.WriteLine("Core: Running on .NET Framework Version {0}.{1}.{2}", Environment.Version.Major, + Environment.Version.Minor, Environment.Version.Build); - string s = Arguments; + string s = Arguments; - if ( s.Length > 0 ) - Console.WriteLine( "Core: Running with arguments: {0}", s ); + if (s.Length > 0) + Console.WriteLine("Core: Running with arguments: {0}", s); - ProcessorCount = Environment.ProcessorCount; + ProcessorCount = Environment.ProcessorCount; - if ( ProcessorCount > 1 ) - MultiProcessor = true; + if (ProcessorCount > 1) + MultiProcessor = true; - if ( MultiProcessor || Is64Bit ) - Console.WriteLine( "Core: Optimizing for {0} {2}processor{1}", ProcessorCount, ProcessorCount == 1 ? "" : "s", Is64Bit ? "64-bit " : "" ); + if (MultiProcessor || Is64Bit) + Console.WriteLine("Core: Optimizing for {0} {2}processor{1}", ProcessorCount, ProcessorCount == 1 ? "" : "s", + Is64Bit ? "64-bit " : ""); - int platform = (int)Environment.OSVersion.Platform; - if ( platform == 4 || platform == 128 ) { // MS 4, MONO 128 - Unix = true; - Console.WriteLine( "Core: Unix environment detected" ); - } - else { - m_ConsoleEventHandler = OnConsoleEvent; - UnsafeNativeMethods.SetConsoleCtrlHandler( m_ConsoleEventHandler, true ); - } + int platform = (int)Environment.OSVersion.Platform; + if (platform == 4 || platform == 128) + { + // MS 4, MONO 128 + Unix = true; + Console.WriteLine("Core: Unix environment detected"); + } + else + { + m_ConsoleEventHandler = OnConsoleEvent; + UnsafeNativeMethods.SetConsoleCtrlHandler(m_ConsoleEventHandler, true); + } - if ( GCSettings.IsServerGC ) - Console.WriteLine("Core: Server garbage collection mode enabled"); + if (GCSettings.IsServerGC) + Console.WriteLine("Core: Server garbage collection mode enabled"); - if (_UseHRT) - Console.WriteLine("Core: Requested high resolution timing ({0})", UsingHighResolutionTiming ? "Supported" : "Unsupported"); + if (_UseHRT) + Console.WriteLine("Core: Requested high resolution timing ({0})", + UsingHighResolutionTiming ? "Supported" : "Unsupported"); - Console.WriteLine("RandomImpl: {0} ({1})", RandomImpl.Type.Name, RandomImpl.IsHardwareRNG ? "Hardware" : "Software"); + Console.WriteLine("RandomImpl: {0} ({1})", RandomImpl.Type.Name, + RandomImpl.IsHardwareRNG ? "Hardware" : "Software"); - while( !ScriptCompiler.Compile( Debug, m_Cache ) ) - { - Console.WriteLine( "Scripts: One or more scripts failed to compile or no script files were found." ); + while (!ScriptCompiler.Compile(Debug, m_Cache)) + { + Console.WriteLine("Scripts: One or more scripts failed to compile or no script files were found."); - if ( Service ) - return; + if (Service) + return; - Console.WriteLine( " - Press return to exit, or R to try again." ); + Console.WriteLine(" - Press return to exit, or R to try again."); - if ( Console.ReadKey( true ).Key != ConsoleKey.R ) - return; - } + if (Console.ReadKey(true).Key != ConsoleKey.R) + return; + } - ScriptCompiler.Invoke( "Configure" ); + ScriptCompiler.Invoke("Configure"); - Region.Load(); - World.Load(); + Region.Load(); + World.Load(); - ScriptCompiler.Invoke( "Initialize" ); + ScriptCompiler.Invoke("Initialize"); - MessagePump messagePump = MessagePump = new MessagePump(); + MessagePump messagePump = MessagePump = new MessagePump(); - timerThread.Start(); + timerThread.Start(); - foreach (Map m in Map.AllMaps) - m.Tiles.Force(); + foreach (Map m in Map.AllMaps) + m.Tiles.Force(); - NetState.Initialize(); + NetState.Initialize(); - EventSink.InvokeServerStarted(); + EventSink.InvokeServerStarted(); - try - { - long last = TickCount; + try + { + long last = TickCount; - const int sampleInterval = 100; - const float ticksPerSecond = 1000.0f * sampleInterval; + const int sampleInterval = 100; + const float ticksPerSecond = 1000.0f * sampleInterval; - long sample = 0; + long sample = 0; - while( !Closing ) - { - m_Signal.WaitOne(); + while (!Closing) + { + m_Signal.WaitOne(); - Task.WaitAll( - Task.Run(() => Mobile.ProcessDeltaQueue()), - Task.Run(() => Item.ProcessDeltaQueue()), - Task.Run(() => Timer.Slice()), - Task.Run(() => messagePump.Slice()) - ); + Task.WaitAll( + Task.Run(() => Mobile.ProcessDeltaQueue()), + Task.Run(() => Item.ProcessDeltaQueue()), + Task.Run(() => Timer.Slice()), + Task.Run(() => messagePump.Slice()) + ); - NetState.FlushAll(); - NetState.ProcessDisposedQueue(); + NetState.FlushAll(); + NetState.ProcessDisposedQueue(); - Slice?.Invoke(); + Slice?.Invoke(); - if (sample++ % sampleInterval != 0) - { - continue; - } + if (sample++ % sampleInterval != 0) continue; - long now = TickCount; - m_CyclesPerSecond[m_CycleIndex++ % m_CyclesPerSecond.Length] = ticksPerSecond / (now - last); - last = now; - } - } - catch( Exception e ) - { - CurrentDomain_UnhandledException( null, new UnhandledExceptionEventArgs( e, true ) ); - } - } + long now = TickCount; + m_CyclesPerSecond[m_CycleIndex++ % m_CyclesPerSecond.Length] = ticksPerSecond / (now - last); + last = now; + } + } + catch (Exception e) + { + CurrentDomain_UnhandledException(null, new UnhandledExceptionEventArgs(e, true)); + } + } - public static string Arguments - { - get - { - StringBuilder sb = new StringBuilder(); + public static void VerifySerialization() + { + m_ItemCount = 0; + m_MobileCount = 0; - if ( Debug ) - Utility.Separate( sb, "-debug", " " ); + Assembly ca = Assembly.GetCallingAssembly(); - if ( Service ) - Utility.Separate( sb, "-service", " " ); + VerifySerialization(ca); - if ( m_Profiling ) - Utility.Separate( sb, "-profile", " " ); + foreach (Assembly a in ScriptCompiler.Assemblies.Where(a => a != ca)) VerifySerialization(a); + } - if ( !m_Cache ) - Utility.Separate( sb, "-nocache", " " ); + private static void VerifyType(Type t) + { + bool isItem = t.IsSubclassOf(typeof(Item)); - if ( HaltOnWarning ) - Utility.Separate( sb, "-haltonwarning", " " ); + if (!isItem && !t.IsSubclassOf(typeof(Mobile))) return; - if ( VBdotNet ) - Utility.Separate( sb, "-vb", " " ); + if (isItem) + Interlocked.Increment(ref m_ItemCount); + else + Interlocked.Increment(ref m_MobileCount); - if ( _UseHRT ) - Utility.Separate( sb, "-usehrt", " " ); + StringBuilder warningSb = null; - return sb.ToString(); - } - } + try + { + if (t.GetConstructor(m_SerialTypeArray) == null) + { + warningSb = new StringBuilder(); - public static int GlobalUpdateRange { get; set; } = 18; + warningSb.AppendLine(" - No serialization constructor"); + } - public static int GlobalMaxUpdateRange { get; set; } = 24; + if ( + t.GetMethod( + "Serialize", + BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.DeclaredOnly) == + null) + { + if (warningSb == null) warningSb = new StringBuilder(); - private static int m_ItemCount, m_MobileCount; - - public static int ScriptItems => m_ItemCount; - public static int ScriptMobiles => m_MobileCount; + warningSb.AppendLine(" - No Serialize() method"); + } - public static void VerifySerialization() - { - m_ItemCount = 0; - m_MobileCount = 0; + if ( + t.GetMethod( + "Deserialize", + BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.DeclaredOnly) == + null) + { + if (warningSb == null) warningSb = new StringBuilder(); - var ca = Assembly.GetCallingAssembly(); + warningSb.AppendLine(" - No Deserialize() method"); + } - VerifySerialization(ca); - - foreach (var a in ScriptCompiler.Assemblies.Where(a => a != ca)) - { - VerifySerialization(a); - } - } - - private static readonly Type[] m_SerialTypeArray = { typeof(Serial) }; - - private static void VerifyType(Type t) - { - var isItem = t.IsSubclassOf(typeof(Item)); - - if (!isItem && !t.IsSubclassOf(typeof(Mobile))) - { - return; - } - - if (isItem) - { - //++_ItemCount; - Interlocked.Increment(ref m_ItemCount); - } - else - { - //++_MobileCount; - Interlocked.Increment(ref m_MobileCount); - } - - StringBuilder warningSb = null; - - try - { - if (t.GetConstructor(m_SerialTypeArray) == null) - { - warningSb = new StringBuilder(); - - warningSb.AppendLine(" - No serialization constructor"); - } - - if ( - t.GetMethod( - "Serialize", - BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.DeclaredOnly) == null) - { - if (warningSb == null) - { - warningSb = new StringBuilder(); - } - - warningSb.AppendLine(" - No Serialize() method"); - } - - if ( - t.GetMethod( - "Deserialize", - BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.DeclaredOnly) == null) - { - if (warningSb == null) - { - warningSb = new StringBuilder(); - } - - warningSb.AppendLine(" - No Deserialize() method"); - } - - if (warningSb != null && warningSb.Length > 0) - { - Console.WriteLine("Warning: {0}\n{1}", t, warningSb); - } - } - catch - { - Console.WriteLine("Warning: Exception in serialization verification of type {0}", t); - } - } - - private static void VerifySerialization(Assembly a) - { - if (a != null) - { - Parallel.ForEach(a.GetTypes(), VerifyType); - } - } - } - - public class FileLogger : TextWriter - { - public const string DateFormat = "[MMMM dd hh:mm:ss.f tt]: "; - - private bool _NewLine; - - public string FileName { get; private set; } - - public FileLogger(string file) - : this(file, false) - { } - - public FileLogger(string file, bool append) - { - FileName = file; - - using ( - var writer = - new StreamWriter( - new FileStream(FileName, append ? FileMode.Append : FileMode.Create, FileAccess.Write, FileShare.Read))) - { - writer.WriteLine(">>>Logging started on {0}.", DateTime.UtcNow.ToString("f")); - //f = Tuesday, April 10, 2001 3:51 PM - } - - _NewLine = true; - } - - public override void Write(char ch) - { - using (var writer = new StreamWriter(new FileStream(FileName, FileMode.Append, FileAccess.Write, FileShare.Read))) - { - if (_NewLine) - { - writer.Write(DateTime.UtcNow.ToString(DateFormat)); - _NewLine = false; - } - - writer.Write(ch); - } - } - - public override void Write(string str) - { - using (var writer = new StreamWriter(new FileStream(FileName, FileMode.Append, FileAccess.Write, FileShare.Read))) - { - if (_NewLine) - { - writer.Write(DateTime.UtcNow.ToString(DateFormat)); - _NewLine = false; - } - - writer.Write(str); - } - } - - public override void WriteLine(string line) - { - using (var writer = new StreamWriter(new FileStream(FileName, FileMode.Append, FileAccess.Write, FileShare.Read))) - { - if (_NewLine) - { - writer.Write(DateTime.UtcNow.ToString(DateFormat)); - } - - writer.WriteLine(line); - _NewLine = true; - } - } - - public override Encoding Encoding => Encoding.Default; - } - - public class MultiTextWriter : TextWriter - { - private readonly List _Streams; - - public MultiTextWriter(params TextWriter[] streams) - { - _Streams = new List(streams); - - if (_Streams.Count < 0) - { - throw new ArgumentException("You must specify at least one stream."); - } - } - - public void Add(TextWriter tw) - { - _Streams.Add(tw); - } - - public void Remove(TextWriter tw) - { - _Streams.Remove(tw); - } - - public override void Write(char ch) - { - foreach (var t in _Streams) - { - t.Write(ch); - } - } - - public override void WriteLine(string line) - { - foreach (var t in _Streams) - { - t.WriteLine(line); - } - } - - public override void WriteLine(string line, params object[] args) - { - WriteLine(string.Format(line, args)); - } - - public override Encoding Encoding => Encoding.Default; - } -} + if (warningSb != null && warningSb.Length > 0) Console.WriteLine("Warning: {0}\n{1}", t, warningSb); + } + catch + { + Console.WriteLine("Warning: Exception in serialization verification of type {0}", t); + } + } + + private static void VerifySerialization(Assembly a) + { + if (a != null) Parallel.ForEach(a.GetTypes(), VerifyType); + } + + internal enum ConsoleEventType + { + CTRL_C_EVENT, + CTRL_BREAK_EVENT, + CTRL_CLOSE_EVENT, + CTRL_LOGOFF_EVENT = 5, + CTRL_SHUTDOWN_EVENT + } + + internal delegate bool ConsoleEventHandler(ConsoleEventType type); + + internal class UnsafeNativeMethods + { + [DllImport("Kernel32")] + internal static extern bool SetConsoleCtrlHandler(ConsoleEventHandler callback, bool add); + } + + #region Expansions + + public static Expansion Expansion{ get; set; } + + public static bool T2A => Expansion >= Expansion.T2A; + + public static bool UOR => Expansion >= Expansion.UOR; + + public static bool UOTD => Expansion >= Expansion.UOTD; + + public static bool LBR => Expansion >= Expansion.LBR; + + public static bool AOS => Expansion >= Expansion.AOS; + + public static bool SE => Expansion >= Expansion.SE; + + public static bool ML => Expansion >= Expansion.ML; + + public static bool SA => Expansion >= Expansion.SA; + + public static bool HS => Expansion >= Expansion.HS; + + public static bool TOL => Expansion >= Expansion.TOL; + + #endregion + } + + public class FileLogger : TextWriter + { + public const string DateFormat = "[MMMM dd hh:mm:ss.f tt]: "; + + private bool _NewLine; + + public FileLogger(string file) + : this(file, false) + { + } + + public FileLogger(string file, bool append) + { + FileName = file; + + using ( + StreamWriter writer = + new StreamWriter( + new FileStream(FileName, append ? FileMode.Append : FileMode.Create, FileAccess.Write, + FileShare.Read))) + { + writer.WriteLine(">>>Logging started on {0}.", DateTime.UtcNow.ToString("f")); + //f = Tuesday, April 10, 2001 3:51 PM + } + + _NewLine = true; + } + + public string FileName{ get; } + + public override Encoding Encoding => Encoding.Default; + + public override void Write(char ch) + { + using (StreamWriter writer = + new StreamWriter(new FileStream(FileName, FileMode.Append, FileAccess.Write, FileShare.Read))) + { + if (_NewLine) + { + writer.Write(DateTime.UtcNow.ToString(DateFormat)); + _NewLine = false; + } + + writer.Write(ch); + } + } + + public override void Write(string str) + { + using (StreamWriter writer = + new StreamWriter(new FileStream(FileName, FileMode.Append, FileAccess.Write, FileShare.Read))) + { + if (_NewLine) + { + writer.Write(DateTime.UtcNow.ToString(DateFormat)); + _NewLine = false; + } + + writer.Write(str); + } + } + + public override void WriteLine(string line) + { + using (StreamWriter writer = + new StreamWriter(new FileStream(FileName, FileMode.Append, FileAccess.Write, FileShare.Read))) + { + if (_NewLine) writer.Write(DateTime.UtcNow.ToString(DateFormat)); + + writer.WriteLine(line); + _NewLine = true; + } + } + } + + public class MultiTextWriter : TextWriter + { + private readonly List _Streams; + + public MultiTextWriter(params TextWriter[] streams) + { + _Streams = new List(streams); + + if (_Streams.Count < 0) throw new ArgumentException("You must specify at least one stream."); + } + + public override Encoding Encoding => Encoding.Default; + + public void Add(TextWriter tw) + { + _Streams.Add(tw); + } + + public void Remove(TextWriter tw) + { + _Streams.Remove(tw); + } + + public override void Write(char ch) + { + foreach (TextWriter t in _Streams) t.Write(ch); + } + + public override void WriteLine(string line) + { + foreach (TextWriter t in _Streams) t.WriteLine(line); + } + + public override void WriteLine(string line, params object[] args) + { + WriteLine(string.Format(line, args)); + } + } +} \ No newline at end of file diff --git a/Server/Map.cs b/Server/Map.cs index f9b53c3fe..d53d1f8ea 100644 --- a/Server/Map.cs +++ b/Server/Map.cs @@ -21,1591 +21,1580 @@ using System; using System.Collections; using System.Collections.Generic; +using System.Linq; using Server.Items; using Server.Network; using Server.Targeting; -using System.Linq; namespace Server { - [Flags] - public enum MapRules - { - None = 0x0000, - Internal = 0x0001, // Internal map (used for dragging, commodity deeds, etc) - FreeMovement = 0x0002, // Anyone can move over anyone else without taking stamina loss - BeneficialRestrictions = 0x0004, // Disallow performing beneficial actions on criminals/murderers - HarmfulRestrictions = 0x0008, // Disallow performing harmful actions on innocents - TrammelRules = FreeMovement | BeneficialRestrictions | HarmfulRestrictions, - FeluccaRules = None - } - - public interface IPooledEnumerable : IEnumerable { - void Free(); - } - - public interface IPooledEnumerable : IPooledEnumerable, IEnumerable { - } - - public static class PooledEnumeration - { - public delegate IEnumerable Selector(Sector sector, Rectangle2D bounds); - - public static Selector ClientSelector { get; set; } - public static Selector EntitySelector { get; set; } - public static Selector MobileSelector { get; set; } - public static Selector ItemSelector { get; set; } - public static Selector MultiSelector { get; set; } - public static Selector MultiTileSelector { get; set; } - - static PooledEnumeration() - { - ClientSelector = SelectClients; - EntitySelector = SelectEntities; - MobileSelector = SelectMobiles; - ItemSelector = SelectItems; - MultiSelector = SelectMultis; - MultiTileSelector = SelectMultiTiles; - } - - public static IEnumerable SelectClients(Sector s, Rectangle2D bounds) - { - return s.Clients.Where(o => o?.Mobile != null && !o.Mobile.Deleted && bounds.Contains(o.Mobile)); - } - - public static IEnumerable SelectEntities(Sector s, Rectangle2D bounds) - { - return SelectEntities(s, true, true, bounds); - } - - public static IEnumerable SelectEntities(Sector s, bool items, bool mobiles, Rectangle2D bounds) - { - IEnumerable eable = Enumerable.Empty(); - if (mobiles) - eable = eable.Union(s.Mobiles.Where(o => o != null && !o.Deleted)); - if (items) - eable = eable.Union(s.Items.Where(o => o != null && !o.Deleted && o.Parent == null)); - - return eable.Where(bounds.Contains); - } - - public static IEnumerable SelectMobiles(Sector s, Rectangle2D bounds) where T : Mobile - { - return s.Mobiles.OfType().Where(o => o != null && !o.Deleted && bounds.Contains(o)); - } - public static IEnumerable SelectItems(Sector s, Rectangle2D bounds) where T : Item - { - return s.Items.OfType().Where(o => o != null && !o.Deleted && o.Parent == null && o is T && bounds.Contains(o)); - } - - public static IEnumerable SelectMultis(Sector s, Rectangle2D bounds) - { - return s.Multis.Where(o => o != null && !o.Deleted && bounds.Contains(o.Location)); - } - - public static IEnumerable SelectMultiTiles(Sector s, Rectangle2D bounds) - { - foreach (var o in s.Multis.Where(o => o != null && !o.Deleted)) - { - var c = o.Components; - - int x, y, xo, yo; - StaticTile[] t, r; - - for (x = bounds.Start.X; x < bounds.End.X; x++) - { - xo = x - (o.X + c.Min.X); - - if (xo < 0 || xo >= c.Width) - { - continue; - } - - for (y = bounds.Start.Y; y < bounds.End.Y; y++) - { - yo = y - (o.Y + c.Min.Y); - - if (yo < 0 || yo >= c.Height) - { - continue; - } - - t = c.Tiles[xo][yo]; - - if (t.Length <= 0) - { - continue; - } - - r = new StaticTile[t.Length]; - - for (var i = 0; i < t.Length; i++) - { - r[i] = t[i]; - r[i].Z += o.Z; - } - - yield return r; - } - } - } - } - - public static Map.PooledEnumerable GetClients(Map map, Rectangle2D bounds) - { - return Map.PooledEnumerable.Instantiate(map, bounds, ClientSelector ?? SelectClients); - } - - public static Map.PooledEnumerable GetEntities(Map map, Rectangle2D bounds) - { - return GetEntities(map, bounds, true, true); - } - - public static Map.PooledEnumerable GetEntities(Map map, Rectangle2D bounds, bool items, bool mobiles) - { - return Map.PooledEnumerable.Instantiate(map, bounds, EntitySelector ?? SelectEntities); - } - - public static Map.PooledEnumerable GetMobiles(Map map, Rectangle2D bounds) - { - return GetMobiles(map, bounds); - } - public static Map.PooledEnumerable GetMobiles(Map map, Rectangle2D bounds) where T : Mobile - { - return Map.PooledEnumerable.Instantiate(map, bounds, SelectMobiles); - } - public static Map.PooledEnumerable GetItems(Map map, Rectangle2D bounds) where T : Item - { - return Map.PooledEnumerable.Instantiate(map, bounds, SelectItems); - } - - public static Map.PooledEnumerable GetMultis(Map map, Rectangle2D bounds) - { - return Map.PooledEnumerable.Instantiate(map, bounds, MultiSelector ?? SelectMultis); - } - - public static Map.PooledEnumerable GetMultiTiles(Map map, Rectangle2D bounds) - { - return Map.PooledEnumerable.Instantiate(map, bounds, MultiTileSelector ?? SelectMultiTiles); - } - - public static IEnumerable EnumerateSectors(Map map, Rectangle2D bounds) - { - if (map == null || map == Map.Internal) - yield break; - - int x1 = bounds.Start.X; - int y1 = bounds.Start.Y; - int x2 = bounds.End.X; - int y2 = bounds.End.Y; - - if (!Bound(map, ref x1, ref y1, ref x2, ref y2, out int xSector, out int ySector)) - yield break; - - var index = 0; - - while (NextSector(map, x1, y1, x2, y2, ref index, ref xSector, ref ySector, out Sector s)) - yield return s; - } - - public static bool Bound( - Map map, - ref int x1, - ref int y1, - ref int x2, - ref int y2, - out int xSector, - out int ySector) - { - if (map == null || map == Map.Internal) - { - xSector = ySector = 0; - return false; - } - - map.Bound(x1, y1, out x1, out y1); - map.Bound(x2 - 1, y2 - 1, out x2, out y2); - - x1 >>= Map.SectorShift; - y1 >>= Map.SectorShift; - x2 >>= Map.SectorShift; - y2 >>= Map.SectorShift; - - xSector = x1; - ySector = y1; - - return true; - } - - private static bool NextSector( - Map map, - int x1, - int y1, - int x2, - int y2, - ref int index, - ref int xSector, - ref int ySector, - out Sector s) - { - if (map == null) - { - s = null; - xSector = ySector = 0; - return false; - } - - if (map == Map.Internal) - { - s = map.InvalidSector; - xSector = ySector = 0; - return false; - } - - if (index++ > 0) - { - if (++ySector > y2) - { - ySector = y1; - - if (++xSector > x2) - { - xSector = x1; - - s = map.InvalidSector; - return false; - } - } - } - - s = map.GetRealSector(xSector, ySector); - return true; - } - } - - [Parsable] - //[CustomEnum( new string[]{ "Felucca", "Trammel", "Ilshenar", "Malas", "Internal" } )] - public sealed class Map : IComparable, IComparable - { - public const int SectorSize = 16; - public const int SectorShift = 4; - public static int SectorActiveRange = 2; - - public static Map[] Maps { get; } = new Map[0x100]; - - public static Map Felucca => Maps[0]; - public static Map Trammel => Maps[1]; - public static Map Ilshenar => Maps[2]; - public static Map Malas => Maps[3]; - public static Map Tokuno => Maps[4]; - public static Map TerMur => Maps[5]; - public static Map Internal => Maps[0x7F]; - - public static List AllMaps { get; } = new List(); - - private int m_FileIndex; - - private int m_SectorsWidth, m_SectorsHeight; - private Region m_DefaultRegion; - - public int Season { get; set; } - - private string m_Name; - private Sector[][] m_Sectors; - - private TileMatrix m_Tiles; - - public static string[] GetMapNames() - { - return Maps.Where(m => m != null).Select(m => m.Name).ToArray(); - } - - public static Map[] GetMapValues() - { - return Maps.Where(m => m != null).ToArray(); - } - - public static Map Parse(string value) - { - if (string.IsNullOrWhiteSpace(value)) - { - return null; - } - - if (Insensitive.Equals(value, "Internal")) - { - return Internal; - } - - if (!int.TryParse(value, out int index)) - { - return Maps.FirstOrDefault(m => m != null && Insensitive.Equals(m.Name, value)); - } - - if (index == 127) - { - return Internal; - } - - return Maps.FirstOrDefault(m => m != null && m.MapIndex == index); - } - - public override string ToString() - { - return Name; - } - - public int GetAverageZ( int x, int y ) - { - int z = 0, avg = 0, top = 0; - - GetAverageZ( x, y, ref z, ref avg, ref top ); - - return avg; - } - - public void GetAverageZ( int x, int y, ref int z, ref int avg, ref int top ) - { - int zTop = Tiles.GetLandTile( x, y ).Z; - int zLeft = Tiles.GetLandTile( x, y + 1 ).Z; - int zRight = Tiles.GetLandTile( x + 1, y ).Z; - int zBottom = Tiles.GetLandTile( x + 1, y + 1 ).Z; - - z = zTop; - if ( zLeft < z ) - z = zLeft; - if ( zRight < z ) - z = zRight; - if ( zBottom < z ) - z = zBottom; - - top = zTop; - if ( zLeft > top ) - top = zLeft; - if ( zRight > top ) - top = zRight; - if ( zBottom > top ) - top = zBottom; - - if ( Math.Abs( zTop - zBottom ) > Math.Abs( zLeft - zRight ) ) - avg = FloorAverage( zLeft, zRight ); - else - avg = FloorAverage( zTop, zBottom ); - } - - private static int FloorAverage( int a, int b ) - { - int v = a + b; - - if ( v < 0 ) - --v; - - return v / 2; - } - - #region Get*InRange/Bounds - public IPooledEnumerable GetObjectsInRange(Point3D p) - { - return GetObjectsInRange(p, Core.GlobalMaxUpdateRange); - } - - public IPooledEnumerable GetObjectsInRange(Point3D p, int range) - { - return GetObjectsInRange(p, range, true, true); - } - - public IPooledEnumerable GetObjectsInRange(Point3D p, int range, bool items, bool mobiles) - { - return GetObjectsInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1), items, mobiles); - } - - public IPooledEnumerable GetObjectsInBounds(Rectangle2D bounds) - { - return GetObjectsInBounds(bounds, true, true); - } - - public IPooledEnumerable GetObjectsInBounds(Rectangle2D bounds, bool items, bool mobiles) - { - return PooledEnumeration.GetEntities(this, bounds, items, mobiles); - } - - public IPooledEnumerable GetClientsInRange(Point3D p) - { - return GetClientsInRange(p, Core.GlobalMaxUpdateRange); - } - - public IPooledEnumerable GetClientsInRange(Point3D p, int range) - { - return GetClientsInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1)); - } - - public IPooledEnumerable GetClientsInBounds(Rectangle2D bounds) - { - return PooledEnumeration.GetClients(this, bounds); - } - - public IPooledEnumerable GetItemsInRange(Point3D p) - { - return GetItemsInRange(p, Core.GlobalMaxUpdateRange); - } - public IPooledEnumerable GetItemsInRange(Point3D p, int range) - { - return GetItemsInRange(p, range); - } - public IPooledEnumerable GetItemsInRange(Point3D p, int range) where T : Item - { - return GetItemsInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1)); - } - public IPooledEnumerable GetItemsInBounds(Rectangle2D bounds) - { - return GetItemsInBounds(bounds); - } - public IPooledEnumerable GetItemsInBounds(Rectangle2D bounds) where T : Item - { - return PooledEnumeration.GetItems(this, bounds); - } - - public IPooledEnumerable GetMobilesInRange(Point3D p) - { - return GetMobilesInRange(p, Core.GlobalMaxUpdateRange); - } - - public IPooledEnumerable GetMobilesInRange(Point3D p, int range) - { - return GetMobilesInRange(p, range); - } - - public IPooledEnumerable GetMobilesInRange(Point3D p, int range) where T : Mobile - { - return GetMobilesInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1)); - } - - public IPooledEnumerable GetMobilesInBounds(Rectangle2D bounds) - { - return GetMobilesInBounds(bounds); - } - - public IPooledEnumerable GetMobilesInBounds(Rectangle2D bounds) where T : Mobile - { - return PooledEnumeration.GetMobiles(this, bounds); - } - #endregion - - public IPooledEnumerable GetMultiTilesAt(int x, int y) - { - return PooledEnumeration.GetMultiTiles(this, new Rectangle2D(x, y, 1, 1)); - } - - #region CanFit - public bool CanFit( Point3D p, int height, bool checkBlocksFit = false, bool checkMobiles = true, bool requireSurface = true ) - { - return CanFit( p.m_X, p.m_Y, p.m_Z, height, checkBlocksFit, checkMobiles, requireSurface ); - } - - public bool CanFit( Point2D p, int z, int height, bool checkBlocksFit = false, bool checkMobiles = true, bool requireSurface = true ) - { - return CanFit( p.m_X, p.m_Y, z, height, checkBlocksFit, checkMobiles, requireSurface ); - } - - public bool CanFit( int x, int y, int z, int height, bool checkBlocksFit = false, bool checkMobiles = true, bool requireSurface = true ) - { - if ( this == Internal ) - return false; - - if ( x < 0 || y < 0 || x >= Width || y >= Height ) - return false; - - bool hasSurface = false; - - LandTile lt = Tiles.GetLandTile( x, y ); - int lowZ = 0, avgZ = 0, topZ = 0; - - GetAverageZ( x, y, ref lowZ, ref avgZ, ref topZ ); - TileFlag landFlags = TileData.LandTable[lt.ID & TileData.MaxLandValue].Flags; - - if ( ( landFlags & TileFlag.Impassable ) != 0 && avgZ > z && ( z + height ) > lowZ ) - return false; - - if ( ( landFlags & TileFlag.Impassable ) == 0 && z == avgZ && !lt.Ignored ) - hasSurface = true; - - StaticTile[] staticTiles = Tiles.GetStaticTiles( x, y, true ); - - bool surface, impassable; - - for ( int i = 0; i < staticTiles.Length; ++i ) - { - ItemData id = TileData.ItemTable[staticTiles[i].ID & TileData.MaxItemValue]; - surface = id.Surface; - impassable = id.Impassable; - - if ( ( surface || impassable ) && ( staticTiles[i].Z + id.CalcHeight ) > z && ( z + height ) > staticTiles[i].Z ) - return false; - - if ( surface && !impassable && z == ( staticTiles[i].Z + id.CalcHeight ) ) - hasSurface = true; - } - - Sector sector = GetSector( x, y ); - List items = sector.Items; - List mobs = sector.Mobiles; - - for ( int i = 0; i < items.Count; ++i ) - { - Item item = items[i]; - - if ( !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint( x, y ) ) - { - ItemData id = item.ItemData; - surface = id.Surface; - impassable = id.Impassable; - - if ( ( surface || impassable || ( checkBlocksFit && item.BlocksFit ) ) && ( item.Z + id.CalcHeight ) > z && ( z + height ) > item.Z ) - return false; - - if ( surface && !impassable && !item.Movable && z == ( item.Z + id.CalcHeight ) ) - hasSurface = true; - } - } - - if ( checkMobiles ) - { - for ( int i = 0; i < mobs.Count; ++i ) - { - Mobile m = mobs[i]; - - if (m.Location.m_X == x && m.Location.m_Y == y && (m.AccessLevel == AccessLevel.Player || !m.Hidden) && m.Z + 16 > z && z + height > m.Z) - return false; - } - } - - return !requireSurface || hasSurface; - } - - #endregion - - #region CanSpawnMobile - public bool CanSpawnMobile( Point3D p ) - { - return CanSpawnMobile( p.m_X, p.m_Y, p.m_Z ); - } + [Flags] + public enum MapRules + { + None = 0x0000, + Internal = 0x0001, // Internal map (used for dragging, commodity deeds, etc) + FreeMovement = 0x0002, // Anyone can move over anyone else without taking stamina loss + BeneficialRestrictions = 0x0004, // Disallow performing beneficial actions on criminals/murderers + HarmfulRestrictions = 0x0008, // Disallow performing harmful actions on innocents + TrammelRules = FreeMovement | BeneficialRestrictions | HarmfulRestrictions, + FeluccaRules = None + } + + public interface IPooledEnumerable : IEnumerable + { + void Free(); + } + + public interface IPooledEnumerable : IPooledEnumerable, IEnumerable + { + } + + public static class PooledEnumeration + { + public delegate IEnumerable Selector(Sector sector, Rectangle2D bounds); + + static PooledEnumeration() + { + ClientSelector = SelectClients; + EntitySelector = SelectEntities; + MobileSelector = SelectMobiles; + ItemSelector = SelectItems; + MultiSelector = SelectMultis; + MultiTileSelector = SelectMultiTiles; + } + + public static Selector ClientSelector{ get; set; } + public static Selector EntitySelector{ get; set; } + public static Selector MobileSelector{ get; set; } + public static Selector ItemSelector{ get; set; } + public static Selector MultiSelector{ get; set; } + public static Selector MultiTileSelector{ get; set; } + + public static IEnumerable SelectClients(Sector s, Rectangle2D bounds) + { + return s.Clients.Where(o => o?.Mobile != null && !o.Mobile.Deleted && bounds.Contains(o.Mobile)); + } + + public static IEnumerable SelectEntities(Sector s, Rectangle2D bounds) + { + return SelectEntities(s, true, true, bounds); + } + + public static IEnumerable SelectEntities(Sector s, bool items, bool mobiles, Rectangle2D bounds) + { + IEnumerable eable = Enumerable.Empty(); + if (mobiles) + eable = eable.Union(s.Mobiles.Where(o => o != null && !o.Deleted)); + if (items) + eable = eable.Union(s.Items.Where(o => o != null && !o.Deleted && o.Parent == null)); + + return eable.Where(bounds.Contains); + } + + public static IEnumerable SelectMobiles(Sector s, Rectangle2D bounds) where T : Mobile + { + return s.Mobiles.OfType().Where(o => o != null && !o.Deleted && bounds.Contains(o)); + } + + public static IEnumerable SelectItems(Sector s, Rectangle2D bounds) where T : Item + { + return s.Items.OfType() + .Where(o => o != null && !o.Deleted && o.Parent == null && o is T && bounds.Contains(o)); + } + + public static IEnumerable SelectMultis(Sector s, Rectangle2D bounds) + { + return s.Multis.Where(o => o != null && !o.Deleted && bounds.Contains(o.Location)); + } + + public static IEnumerable SelectMultiTiles(Sector s, Rectangle2D bounds) + { + foreach (BaseMulti o in s.Multis.Where(o => o != null && !o.Deleted)) + { + MultiComponentList c = o.Components; + + int x, y, xo, yo; + StaticTile[] t, r; + + for (x = bounds.Start.X; x < bounds.End.X; x++) + { + xo = x - (o.X + c.Min.X); + + if (xo < 0 || xo >= c.Width) continue; + + for (y = bounds.Start.Y; y < bounds.End.Y; y++) + { + yo = y - (o.Y + c.Min.Y); + + if (yo < 0 || yo >= c.Height) continue; + + t = c.Tiles[xo][yo]; + + if (t.Length <= 0) continue; + + r = new StaticTile[t.Length]; + + for (int i = 0; i < t.Length; i++) + { + r[i] = t[i]; + r[i].Z += o.Z; + } + + yield return r; + } + } + } + } + + public static Map.PooledEnumerable GetClients(Map map, Rectangle2D bounds) + { + return Map.PooledEnumerable.Instantiate(map, bounds, ClientSelector ?? SelectClients); + } + + public static Map.PooledEnumerable GetEntities(Map map, Rectangle2D bounds) + { + return GetEntities(map, bounds, true, true); + } + + public static Map.PooledEnumerable GetEntities(Map map, Rectangle2D bounds, bool items, bool mobiles) + { + return Map.PooledEnumerable.Instantiate(map, bounds, EntitySelector ?? SelectEntities); + } + + public static Map.PooledEnumerable GetMobiles(Map map, Rectangle2D bounds) + { + return GetMobiles(map, bounds); + } + + public static Map.PooledEnumerable GetMobiles(Map map, Rectangle2D bounds) where T : Mobile + { + return Map.PooledEnumerable.Instantiate(map, bounds, SelectMobiles); + } + + public static Map.PooledEnumerable GetItems(Map map, Rectangle2D bounds) where T : Item + { + return Map.PooledEnumerable.Instantiate(map, bounds, SelectItems); + } + + public static Map.PooledEnumerable GetMultis(Map map, Rectangle2D bounds) + { + return Map.PooledEnumerable.Instantiate(map, bounds, MultiSelector ?? SelectMultis); + } + + public static Map.PooledEnumerable GetMultiTiles(Map map, Rectangle2D bounds) + { + return Map.PooledEnumerable.Instantiate(map, bounds, MultiTileSelector ?? SelectMultiTiles); + } + + public static IEnumerable EnumerateSectors(Map map, Rectangle2D bounds) + { + if (map == null || map == Map.Internal) + yield break; + + int x1 = bounds.Start.X; + int y1 = bounds.Start.Y; + int x2 = bounds.End.X; + int y2 = bounds.End.Y; + + if (!Bound(map, ref x1, ref y1, ref x2, ref y2, out int xSector, out int ySector)) + yield break; + + int index = 0; + + while (NextSector(map, x1, y1, x2, y2, ref index, ref xSector, ref ySector, out Sector s)) + yield return s; + } + + public static bool Bound( + Map map, + ref int x1, + ref int y1, + ref int x2, + ref int y2, + out int xSector, + out int ySector) + { + if (map == null || map == Map.Internal) + { + xSector = ySector = 0; + return false; + } + + map.Bound(x1, y1, out x1, out y1); + map.Bound(x2 - 1, y2 - 1, out x2, out y2); + + x1 >>= Map.SectorShift; + y1 >>= Map.SectorShift; + x2 >>= Map.SectorShift; + y2 >>= Map.SectorShift; + + xSector = x1; + ySector = y1; + + return true; + } + + private static bool NextSector( + Map map, + int x1, + int y1, + int x2, + int y2, + ref int index, + ref int xSector, + ref int ySector, + out Sector s) + { + if (map == null) + { + s = null; + xSector = ySector = 0; + return false; + } + + if (map == Map.Internal) + { + s = map.InvalidSector; + xSector = ySector = 0; + return false; + } + + if (index++ > 0) + if (++ySector > y2) + { + ySector = y1; + + if (++xSector > x2) + { + xSector = x1; + + s = map.InvalidSector; + return false; + } + } + + s = map.GetRealSector(xSector, ySector); + return true; + } + } + + [Parsable] + //[CustomEnum( new string[]{ "Felucca", "Trammel", "Ilshenar", "Malas", "Internal" } )] + public sealed class Map : IComparable, IComparable + { + public const int SectorSize = 16; + public const int SectorShift = 4; + public static int SectorActiveRange = 2; + + private static readonly Queue> _FixPool = new Queue>(128); + + private static readonly List _EmptyFixItems = new List(); + private Region m_DefaultRegion; + + private int m_FileIndex; + + private string m_Name; + private Sector[][] m_Sectors; + + private int m_SectorsWidth, m_SectorsHeight; + + private TileMatrix m_Tiles; + + private object tileLock = new object(); + + public Map(int mapID, int mapIndex, int fileIndex, int width, int height, int season, string name, MapRules rules) + { + MapID = mapID; + MapIndex = mapIndex; + m_FileIndex = fileIndex; + Width = width; + Height = height; + Season = season; + m_Name = name; + Rules = rules; + Regions = new Dictionary(StringComparer.OrdinalIgnoreCase); + InvalidSector = new Sector(0, 0, this); + m_SectorsWidth = width >> SectorShift; + m_SectorsHeight = height >> SectorShift; + m_Sectors = new Sector[m_SectorsWidth][]; + } + + public static Map[] Maps{ get; } = new Map[0x100]; + + public static Map Felucca => Maps[0]; + public static Map Trammel => Maps[1]; + public static Map Ilshenar => Maps[2]; + public static Map Malas => Maps[3]; + public static Map Tokuno => Maps[4]; + public static Map TerMur => Maps[5]; + public static Map Internal => Maps[0x7F]; + + public static List AllMaps{ get; } = new List(); + + public int Season{ get; set; } + + public TileMatrix Tiles + { + get + { + if (m_Tiles == null) + lock (tileLock) + { + m_Tiles = new TileMatrix(this, m_FileIndex, MapID, Width, Height); + } + + return m_Tiles; + } + } + + public int MapID{ get; } + + public int MapIndex{ get; } + + public int Width{ get; } + + public int Height{ get; } - public bool CanSpawnMobile( Point2D p, int z ) - { - return CanSpawnMobile( p.m_X, p.m_Y, z ); - } + public Dictionary Regions{ get; } - public bool CanSpawnMobile( int x, int y, int z ) - { - if ( !Region.Find( new Point3D( x, y, z ), this ).AllowSpawn() ) - return false; + public Region DefaultRegion + { + get + { + if (m_DefaultRegion == null) + m_DefaultRegion = new Region(null, this, 0, new Rectangle3D[0]); - return CanFit( x, y, z, 16 ); - } - #endregion + return m_DefaultRegion; + } + set => m_DefaultRegion = value; + } + + public MapRules Rules{ get; set; } + + public Sector InvalidSector{ get; } + + public string Name + { + get + { + if (this == Internal && m_Name != "Internal") + { + Console.WriteLine("Internal Map Name was changed to '{0}'", m_Name); + + m_Name = "Internal"; + } + + return m_Name; + } + set + { + if (this == Internal && value != "Internal") + { + Console.WriteLine("Attempted to set Internal Map Name to '{0}'", value); + + value = "Internal"; + } + + m_Name = value; + } + } + + public static int[] InvalidLandTiles{ get; set; } = { 0x244 }; + + public int CompareTo(object other) + { + if (other == null || other is Map) + return CompareTo(other); + + throw new ArgumentException(); + } + + public int CompareTo(Map other) + { + if (other == null) + return -1; - private class ZComparer : IComparer - { - public static readonly ZComparer Default = new ZComparer(); + return MapID.CompareTo(other.MapID); + } - public int Compare( Item x, Item y ) - { - return x.Z.CompareTo( y.Z ); - } - } + public static string[] GetMapNames() + { + return Maps.Where(m => m != null).Select(m => m.Name).ToArray(); + } - private static readonly Queue> _FixPool = new Queue>(128); + public static Map[] GetMapValues() + { + return Maps.Where(m => m != null).ToArray(); + } - private static readonly List _EmptyFixItems = new List(); + public static Map Parse(string value) + { + if (string.IsNullOrWhiteSpace(value)) return null; - private static List AcquireFixItems(Map map, int x, int y) - { - if (map == null || map == Internal || x < 0 || x > map.Width || y < 0 || y > map.Height) - { - return _EmptyFixItems; - } + if (Insensitive.Equals(value, "Internal")) return Internal; - List pool = null; + if (!int.TryParse(value, out int index)) + return Maps.FirstOrDefault(m => m != null && Insensitive.Equals(m.Name, value)); - lock (_FixPool) - { - if (_FixPool.Count > 0) - { - pool = _FixPool.Dequeue(); - } - } + if (index == 127) return Internal; - if (pool == null) - { - pool = new List(128); // Arbitrary limit - } + return Maps.FirstOrDefault(m => m != null && m.MapIndex == index); + } - var eable = map.GetItemsInRange(new Point3D(x, y, 0), 0); + public override string ToString() + { + return Name; + } - pool.AddRange( - eable.Where(item => item.ItemID <= TileData.MaxItemValue && !(item is BaseMulti)) - .OrderBy(item => item.Z) - .Take(pool.Capacity)); + public int GetAverageZ(int x, int y) + { + int z = 0, avg = 0, top = 0; - eable.Free(); + GetAverageZ(x, y, ref z, ref avg, ref top); - return pool; - } + return avg; + } - private static void FreeFixItems(List pool) - { - if (pool == _EmptyFixItems) - return; + public void GetAverageZ(int x, int y, ref int z, ref int avg, ref int top) + { + int zTop = Tiles.GetLandTile(x, y).Z; + int zLeft = Tiles.GetLandTile(x, y + 1).Z; + int zRight = Tiles.GetLandTile(x + 1, y).Z; + int zBottom = Tiles.GetLandTile(x + 1, y + 1).Z; - pool.Clear(); + z = zTop; + if (zLeft < z) + z = zLeft; + if (zRight < z) + z = zRight; + if (zBottom < z) + z = zBottom; - lock (_FixPool) - { - if (_FixPool.Count < 128) - { - _FixPool.Enqueue(pool); - } - } - } + top = zTop; + if (zLeft > top) + top = zLeft; + if (zRight > top) + top = zRight; + if (zBottom > top) + top = zBottom; - public void FixColumn(int x, int y) - { - var landTile = Tiles.GetLandTile(x, y); - var tiles = Tiles.GetStaticTiles(x, y, true); + if (Math.Abs(zTop - zBottom) > Math.Abs(zLeft - zRight)) + avg = FloorAverage(zLeft, zRight); + else + avg = FloorAverage(zTop, zBottom); + } - int landZ = 0, landAvg = 0, landTop = 0; - GetAverageZ(x, y, ref landZ, ref landAvg, ref landTop); + private static int FloorAverage(int a, int b) + { + int v = a + b; - var items = AcquireFixItems(this, x, y); + if (v < 0) + --v; - for (var i = 0; i < items.Count; i++) - { - var toFix = items[i]; + return v / 2; + } - if (!toFix.Movable) - continue; + public IPooledEnumerable GetMultiTilesAt(int x, int y) + { + return PooledEnumeration.GetMultiTiles(this, new Rectangle2D(x, y, 1, 1)); + } - var z = int.MinValue; - var currentZ = toFix.Z; + private static List AcquireFixItems(Map map, int x, int y) + { + if (map == null || map == Internal || x < 0 || x > map.Width || y < 0 || y > map.Height) return _EmptyFixItems; - if (!landTile.Ignored && landAvg <= currentZ) - z = landAvg; + List pool = null; - foreach (var tile in tiles) - { - var id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + lock (_FixPool) + { + if (_FixPool.Count > 0) pool = _FixPool.Dequeue(); + } - var checkZ = tile.Z; - var checkTop = checkZ + id.CalcHeight; + if (pool == null) pool = new List(128); // Arbitrary limit - if (checkTop == checkZ && !id.Surface) - ++checkTop; + IPooledEnumerable eable = map.GetItemsInRange(new Point3D(x, y, 0), 0); - if (checkTop > z && checkTop <= currentZ) - z = checkTop; - } + pool.AddRange( + eable.Where(item => item.ItemID <= TileData.MaxItemValue && !(item is BaseMulti)) + .OrderBy(item => item.Z) + .Take(pool.Capacity)); - for (var j = 0; j < items.Count; ++j) - { - if (j == i) - continue; + eable.Free(); - var item = items[j]; - var id = item.ItemData; + return pool; + } - var checkZ = item.Z; - var checkTop = checkZ + id.CalcHeight; + private static void FreeFixItems(List pool) + { + if (pool == _EmptyFixItems) + return; - if (checkTop == checkZ && !id.Surface) - ++checkTop; + pool.Clear(); - if (checkTop > z && checkTop <= currentZ) - z = checkTop; - } + lock (_FixPool) + { + if (_FixPool.Count < 128) _FixPool.Enqueue(pool); + } + } - if (z != int.MinValue) - toFix.Location = new Point3D(toFix.X, toFix.Y, z); - } + public void FixColumn(int x, int y) + { + LandTile landTile = Tiles.GetLandTile(x, y); + StaticTile[] tiles = Tiles.GetStaticTiles(x, y, true); - FreeFixItems(items); - } + int landZ = 0, landAvg = 0, landTop = 0; + GetAverageZ(x, y, ref landZ, ref landAvg, ref landTop); - /* This could probably be re-implemented if necessary (perhaps via an ITile interface?). - public List GetTilesAt( Point2D p, bool items, bool land, bool statics ) - { - List list = new List(); + List items = AcquireFixItems(this, x, y); - if ( this == Internal ) - return list; + for (int i = 0; i < items.Count; i++) + { + Item toFix = items[i]; - if ( land ) - list.Add( Tiles.GetLandTile( p.m_X, p.m_Y ) ); + if (!toFix.Movable) + continue; - if ( statics ) - list.AddRange( Tiles.GetStaticTiles( p.m_X, p.m_Y, true ) ); + int z = int.MinValue; + int currentZ = toFix.Z; - if ( items ) - { - Sector sector = GetSector( p ); + if (!landTile.Ignored && landAvg <= currentZ) + z = landAvg; - foreach ( Item item in sector.Items ) - if ( item.AtWorldPoint( p.m_X, p.m_Y ) ) - list.Add( new StaticTile( (ushort)item.ItemID, (sbyte) item.Z ) ); - } - - return list; - } - */ - - /// - /// Gets the highest surface that is lower than . - /// - /// The reference point. - /// A surface or . - public object GetTopSurface( Point3D p ) - { - if ( this == Internal ) - return null; - - object surface = null; - int surfaceZ = int.MinValue; - - - LandTile lt = Tiles.GetLandTile( p.X, p.Y ); + foreach (StaticTile tile in tiles) + { + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - if ( !lt.Ignored ) - { - int avgZ = GetAverageZ( p.X, p.Y ); - - if ( avgZ <= p.Z ) - { - surface = lt; - surfaceZ = avgZ; - - if ( surfaceZ == p.Z ) - return surface; - } - } - - StaticTile[] staticTiles = Tiles.GetStaticTiles( p.X, p.Y, true ); - - for ( int i = 0; i < staticTiles.Length; i++ ) - { - StaticTile tile = staticTiles[i]; - ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; - - if ( id.Surface || ( id.Flags & TileFlag.Wet ) != 0 ) - { - int tileZ = tile.Z + id.CalcHeight; - - if ( tileZ > surfaceZ && tileZ <= p.Z ) - { - surface = tile; - surfaceZ = tileZ; - - if ( surfaceZ == p.Z ) - return surface; - } - } - } - - Sector sector = GetSector( p.X, p.Y ); - - for ( int i = 0; i < sector.Items.Count; i++ ) - { - Item item = sector.Items[i]; - - if ( !(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint( p.X, p.Y ) && !item.Movable ) - { - ItemData id = item.ItemData; - - if ( id.Surface || ( id.Flags & TileFlag.Wet ) != 0 ) - { - int itemZ = item.Z + id.CalcHeight; - - if ( itemZ > surfaceZ && itemZ <= p.Z ) - { - surface = item; - surfaceZ = itemZ; - - if ( surfaceZ == p.Z ) - return surface; - } - } - } - } - - return surface; - } - - public void Bound( int x, int y, out int newX, out int newY ) - { - if ( x < 0 ) - newX = 0; - else if ( x >= Width ) - newX = Width - 1; - else - newX = x; - - if ( y < 0 ) - newY = 0; - else if ( y >= Height ) - newY = Height - 1; - else - newY = y; - } - - public Point2D Bound( Point2D p ) - { - int x = p.m_X, y = p.m_Y; - - if ( x < 0 ) - x = 0; - else if ( x >= Width ) - x = Width - 1; - - if ( y < 0 ) - y = 0; - else if ( y >= Height ) - y = Height - 1; - - return new Point2D( x, y ); - } - - public Map( int mapID, int mapIndex, int fileIndex, int width, int height, int season, string name, MapRules rules ) - { - MapID = mapID; - MapIndex = mapIndex; - m_FileIndex = fileIndex; - Width = width; - Height = height; - Season = season; - m_Name = name; - Rules = rules; - Regions = new Dictionary( StringComparer.OrdinalIgnoreCase ); - InvalidSector = new Sector( 0, 0, this ); - m_SectorsWidth = width >> SectorShift; - m_SectorsHeight = height >> SectorShift; - m_Sectors = new Sector[m_SectorsWidth][]; - } - - #region GetSector - public Sector GetSector( Point3D p ) - { - return InternalGetSector( p.m_X >> SectorShift, p.m_Y >> SectorShift ); - } - - public Sector GetSector( Point2D p ) - { - return InternalGetSector( p.m_X >> SectorShift, p.m_Y >> SectorShift ); - } - - public Sector GetSector( IPoint2D p ) - { - return InternalGetSector( p.X >> SectorShift, p.Y >> SectorShift ); - } - - public Sector GetSector( int x, int y ) - { - return InternalGetSector( x >> SectorShift, y >> SectorShift ); - } - - public Sector GetRealSector( int x, int y ) - { - return InternalGetSector( x, y ); - } - - private Sector InternalGetSector( int x, int y ) - { - if ( x >= 0 && x < m_SectorsWidth && y >= 0 && y < m_SectorsHeight ) - { - Sector[] xSectors = m_Sectors[x]; - - if ( xSectors == null ) - m_Sectors[x] = xSectors = new Sector[m_SectorsHeight]; - - Sector sec = xSectors[y]; - - if ( sec == null ) - xSectors[y] = sec = new Sector( x, y, this ); - - return sec; - } - - return InvalidSector; - } - #endregion - - public void ActivateSectors( int cx, int cy ) - { - for ( int x = cx - SectorActiveRange; x <= cx + SectorActiveRange; ++x ) - { - for ( int y = cy - SectorActiveRange; y <= cy + SectorActiveRange; ++y ) - { - Sector sect = GetRealSector( x, y ); - if ( sect != InvalidSector ) - sect.Activate(); - } - } - } - - public void DeactivateSectors( int cx, int cy ) - { - for ( int x = cx - SectorActiveRange; x <= cx + SectorActiveRange; ++x ) - { - for ( int y = cy - SectorActiveRange; y <= cy + SectorActiveRange; ++y ) - { - Sector sect = GetRealSector( x, y ); - if ( sect != InvalidSector && !PlayersInRange( sect, SectorActiveRange ) ) - sect.Deactivate(); - } - } - } - - private bool PlayersInRange( Sector sect, int range ) - { - for ( int x = sect.X - range; x <= sect.X + range; ++x ) - { - for ( int y = sect.Y - range; y <= sect.Y + range; ++y ) - { - Sector check = GetRealSector( x, y ); - if ( check != InvalidSector && check.Players.Count > 0 ) - return true; - } - } - - return false; - } - - public void OnClientChange( NetState oldState, NetState newState, Mobile m ) - { - if ( this != Internal ) - GetSector( m ).OnClientChange( oldState, newState ); - } - - public void OnEnter( Mobile m ) - { - if ( this != Internal ) - GetSector( m ).OnEnter( m ); - } - - public void OnEnter( Item item ) - { - if ( this == Internal ) - return; - - GetSector( item ).OnEnter( item ); - - if ( item is BaseMulti m ) - { - MultiComponentList mcl = m.Components; - - Sector start = GetMultiMinSector( m.Location, mcl ); - Sector end = GetMultiMaxSector( m.Location, mcl ); - - AddMulti( m, start, end ); - } - } - - public void OnLeave( Mobile m ) - { - if ( this != Internal ) - GetSector( m ).OnLeave( m ); - } - - public void OnLeave( Item item ) - { - if ( this == Internal ) - return; - - GetSector( item ).OnLeave( item ); - - if ( item is BaseMulti m ) - { - MultiComponentList mcl = m.Components; - - Sector start = GetMultiMinSector( m.Location, mcl ); - Sector end = GetMultiMaxSector( m.Location, mcl ); - - RemoveMulti( m, start, end ); - } - } - - public void RemoveMulti( BaseMulti m, Sector start, Sector end ) - { - if ( this == Internal ) - return; - - for ( int x = start.X; x <= end.X; ++x ) - for ( int y = start.Y; y <= end.Y; ++y ) - InternalGetSector( x, y ).OnMultiLeave( m ); - } - - public void AddMulti( BaseMulti m, Sector start, Sector end ) - { - if ( this == Internal ) - return; - - for ( int x = start.X; x <= end.X; ++x ) - for ( int y = start.Y; y <= end.Y; ++y ) - InternalGetSector( x, y ).OnMultiEnter( m ); - } - - public Sector GetMultiMinSector( Point3D loc, MultiComponentList mcl ) - { - return GetSector( Bound( new Point2D( loc.m_X + mcl.Min.m_X, loc.m_Y + mcl.Min.m_Y ) ) ); - } - - public Sector GetMultiMaxSector( Point3D loc, MultiComponentList mcl ) - { - return GetSector( Bound( new Point2D( loc.m_X + mcl.Max.m_X, loc.m_Y + mcl.Max.m_Y ) ) ); - } - - public void OnMove( Point3D oldLocation, Mobile m ) - { - if ( this == Internal ) - return; - - Sector oldSector = GetSector( oldLocation ); - Sector newSector = GetSector( m.Location ); - - if ( oldSector != newSector ) - { - oldSector.OnLeave( m ); - newSector.OnEnter( m ); - } - } - - public void OnMove( Point3D oldLocation, Item item ) - { - if ( this == Internal ) - return; - - Sector oldSector = GetSector( oldLocation ); - Sector newSector = GetSector( item.Location ); - - if ( oldSector != newSector ) - { - oldSector.OnLeave( item ); - newSector.OnEnter( item ); - } - - if ( item is BaseMulti m ) - { - MultiComponentList mcl = m.Components; - - Sector start = GetMultiMinSector( m.Location, mcl ); - Sector end = GetMultiMaxSector( m.Location, mcl ); - - Sector oldStart = GetMultiMinSector( oldLocation, mcl ); - Sector oldEnd = GetMultiMaxSector( oldLocation, mcl ); - - if ( oldStart != start || oldEnd != end ) - { - RemoveMulti( m, oldStart, oldEnd ); - AddMulti( m, start, end ); - } - } - } - - private object tileLock = new object(); - - public TileMatrix Tiles - { - get - { - if (m_Tiles == null) - lock (tileLock) - m_Tiles = new TileMatrix(this, m_FileIndex, MapID, Width, Height); - - return m_Tiles; - } - } - - public int MapID { get; } - - public int MapIndex { get; } - - public int Width { get; } - - public int Height { get; } - - public Dictionary Regions { get; } - - public void RegisterRegion( Region reg ) - { - string regName = reg.Name; - - if ( regName != null ) - { - if ( Regions.ContainsKey( regName ) ) - Console.WriteLine( "Warning: Duplicate region name '{0}' for map '{1}'", regName, Name ); - else - Regions[regName] = reg; - } - } - - public void UnregisterRegion( Region reg ) - { - string regName = reg.Name; - - if ( regName != null ) - Regions.Remove( regName ); - } - - public Region DefaultRegion - { - get - { - if ( m_DefaultRegion == null ) - m_DefaultRegion = new Region( null, this, 0, new Rectangle3D[0] ); - - return m_DefaultRegion; - } - set => m_DefaultRegion = value; - } - - public MapRules Rules { get; set; } - - public Sector InvalidSector { get; } - - public string Name - { - get - { - if (this == Internal && m_Name != "Internal") - { - Console.WriteLine("Internal Map Name was changed to '{0}'", m_Name); - - m_Name = "Internal"; - } - return m_Name; - } - set - { - if (this == Internal && value != "Internal") - { - Console.WriteLine("Attempted to set Internal Map Name to '{0}'", value); - - value = "Internal"; - } - m_Name = value; - } - } - - public class NullEnumerable : IPooledEnumerable - { - public static readonly NullEnumerable Instance = new NullEnumerable(); - - private readonly IEnumerable _Empty; - - private NullEnumerable() - { - _Empty = Enumerable.Empty(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return _Empty.GetEnumerator(); - } - - public IEnumerator GetEnumerator() - { - return _Empty.GetEnumerator(); - } - - public void Free() - { - } - } - - public sealed class PooledEnumerable : IPooledEnumerable, IDisposable - { - private static readonly Queue> _Buffer = new Queue>(0x400); - - public static PooledEnumerable Instantiate(Map map, Rectangle2D bounds, PooledEnumeration.Selector selector) - { - PooledEnumerable e = null; - - lock (((ICollection)_Buffer).SyncRoot) - { - if (_Buffer.Count > 0) - e = _Buffer.Dequeue(); - } - - var pool = PooledEnumeration.EnumerateSectors(map, bounds).SelectMany(s => selector(s, bounds)); - - if (e != null) - { - e._Pool.AddRange(pool); - return e; - } - - return new PooledEnumerable(pool); - } - - private bool _IsDisposed; - - private List _Pool = new List(0x40); - - public PooledEnumerable(IEnumerable pool) - { - _Pool.AddRange(pool); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return _Pool.GetEnumerator(); - } - - public IEnumerator GetEnumerator() - { - return _Pool.GetEnumerator(); - } - - public void Free() - { - if (_IsDisposed) - return; - - _Pool.Clear(); - _Pool.Capacity = Math.Max(_Pool.Capacity, 0x100); - - lock (((ICollection)_Buffer).SyncRoot) - { - _Buffer.Enqueue(this); - } - } - - public void Dispose() - { - _IsDisposed = true; - - _Pool.Clear(); - _Pool.TrimExcess(); - _Pool = null; - } - } - - public Point3D GetPoint( object o, bool eye ) - { - Point3D p; - - if ( o is Mobile mobile ) - { - p = mobile.Location; - p.Z += 14; //eye ? 15 : 10; - } - else if ( o is Item item ) - { - p = item.GetWorldLocation(); - p.Z += (item.ItemData.Height / 2) + 1; - } - else if ( o is Point3D point3D ) - { - p = point3D; - } - else if ( o is LandTarget target ) - { - p = target.Location; - - int low = 0, avg = 0, top = 0; - GetAverageZ( p.X, p.Y, ref low, ref avg, ref top ); - - p.Z = top + 1; - } - else if ( o is StaticTarget st ) - { - ItemData id = TileData.ItemTable[st.ItemID & TileData.MaxItemValue]; - - p = new Point3D( st.X, st.Y, st.Z - id.CalcHeight + id.Height / 2 + 1 ); - } - else if ( o is IPoint3D d ) - { - p = new Point3D( d ); - } - else - { - Console.WriteLine( "Warning: Invalid object ({0}) in line of sight", o ); - p = Point3D.Zero; - } - - return p; - } - - #region Line Of Sight - - public static int MaxLOSDistance { get; set; } = 25; - - public bool LineOfSight( Point3D org, Point3D dest ) - { - if ( this == Internal ) - return false; - - if ( !Utility.InRange( org, dest, MaxLOSDistance ) ) - return false; - - Point3D end = dest; - - if ( org.X > dest.X || org.X == dest.X && org.Y > dest.Y || org.X == dest.X && org.Y == dest.Y && org.Z > dest.Z ) - { - Point3D swap = org; - org = dest; - dest = swap; - } - - double rise, run, zslp; - double sq3d; - double x, y, z; - int xd, yd, zd; - int ix, iy, iz; - int height; - bool found; - Point3D p; - Point3DList path = new Point3DList(); - TileFlag flags; - - if ( org == dest ) - return true; - - if ( path.Count > 0 ) - path.Clear(); - - xd = dest.m_X - org.m_X; - yd = dest.m_Y - org.m_Y; - zd = dest.m_Z - org.m_Z; - zslp = Math.Sqrt( xd * xd + yd * yd ); - if ( zd != 0 ) - sq3d = Math.Sqrt( zslp * zslp + zd * zd ); - else - sq3d = zslp; - - rise = yd / sq3d; - run = xd / sq3d; - zslp = zd / sq3d; - - y = org.m_Y; - z = org.m_Z; - x = org.m_X; - while ( Utility.NumberBetween( x, dest.m_X, org.m_X, 0.5 ) && Utility.NumberBetween( y, dest.m_Y, org.m_Y, 0.5 ) && Utility.NumberBetween( z, dest.m_Z, org.m_Z, 0.5 ) ) - { - ix = (int)Math.Round( x ); - iy = (int)Math.Round( y ); - iz = (int)Math.Round( z ); - if ( path.Count > 0 ) - { - p = path.Last; - - if ( p.m_X != ix || p.m_Y != iy || p.m_Z != iz ) - path.Add( ix, iy, iz ); - } - else - { - path.Add( ix, iy, iz ); - } - x += run; - y += rise; - z += zslp; - } - - if ( path.Count == 0 ) - return true; //<--should never happen, but to be safe. - - p = path.Last; - - if ( p != dest ) - path.Add( dest ); - - Point3D pTop = org, pBottom = dest; - Utility.FixPoints( ref pTop, ref pBottom ); - - int pathCount = path.Count; - int endTop = end.m_Z + 1; - - for ( int i = 0; i < pathCount; ++i ) - { - Point3D point = path[i]; - int pointTop = point.m_Z + 1; - - LandTile landTile = Tiles.GetLandTile( point.X, point.Y ); - int landZ = 0, landAvg = 0, landTop = 0; - GetAverageZ( point.m_X, point.m_Y, ref landZ, ref landAvg, ref landTop ); - - if ( landZ <= pointTop && landTop >= point.m_Z && (point.m_X != end.m_X || point.m_Y != end.m_Y || landZ > endTop || landTop < end.m_Z) && !landTile.Ignored ) - return false; - - /* --Do land tiles need to be checked? There is never land between two people, always statics.-- - LandTile landTile = Tiles.GetLandTile( point.X, point.Y ); - if ( landTile.Z-1 >= point.Z && landTile.Z+1 <= point.Z && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) != 0 ) - return false; - */ - - StaticTile[] statics = Tiles.GetStaticTiles( point.m_X, point.m_Y, true ); - - bool contains = false; - int ltID = landTile.ID; - - for ( int j = 0; !contains && j < InvalidLandTiles.Length; ++j ) - contains =ltID == InvalidLandTiles[j]; - - if ( contains && statics.Length == 0 ) - { - IPooledEnumerable eable = GetItemsInRange( point, 0 ); - - foreach ( Item item in eable ) - { - if ( item.Visible ) - contains = false; - - if ( !contains ) - break; - } - - eable.Free(); - - if ( contains ) - return false; - } - - for ( int j = 0; j < statics.Length; ++j ) - { - StaticTile t = statics[j]; - - ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; - - flags = id.Flags; - height = id.CalcHeight; - - if ( t.Z <= pointTop && t.Z + height >= point.Z && (flags & (TileFlag.Window | TileFlag.NoShoot)) != 0 ) - { - if ( point.m_X == end.m_X && point.m_Y == end.m_Y && t.Z <= endTop && t.Z + height >= end.m_Z ) - continue; - - return false; - } - - /*if ( t.Z <= point.Z && t.Z+height >= point.Z && (flags&TileFlag.Window)==0 && (flags&TileFlag.NoShoot)!=0 - && ( (flags&TileFlag.Wall)!=0 || (flags&TileFlag.Roof)!=0 || (((flags&TileFlag.Surface)!=0 && zd != 0)) ) )*/ - /*{ - //Console.WriteLine( "LoS: Blocked by Static \"{0}\" Z:{1} T:{3} P:{2} F:x{4:X}", TileData.ItemTable[t.ID&TileData.MaxItemValue].Name, t.Z, point, t.Z+height, flags ); - //Console.WriteLine( "if ( {0} && {1} && {2} && ( {3} || {4} || {5} || ({6} && {7} && {8}) ) )", t.Z <= point.Z, t.Z+height >= point.Z, (flags&TileFlag.Window)==0, (flags&TileFlag.Impassable)!=0, (flags&TileFlag.Wall)!=0, (flags&TileFlag.Roof)!=0, (flags&TileFlag.Surface)!=0, t.Z != dest.Z, zd != 0 ) ; - return false; - }*/ - } - } + int checkZ = tile.Z; + int checkTop = checkZ + id.CalcHeight; - Rectangle2D rect = new Rectangle2D( pTop.m_X, pTop.m_Y, (pBottom.m_X - pTop.m_X) + 1, (pBottom.m_Y - pTop.m_Y) + 1 ); + if (checkTop == checkZ && !id.Surface) + ++checkTop; - IPooledEnumerable area = GetItemsInBounds( rect ); + if (checkTop > z && checkTop <= currentZ) + z = checkTop; + } - foreach ( Item i in area ) - { - if ( !i.Visible ) - continue; + for (int j = 0; j < items.Count; ++j) + { + if (j == i) + continue; - if ( i is BaseMulti || i.ItemID > TileData.MaxItemValue ) - continue; + Item item = items[j]; + ItemData id = item.ItemData; - ItemData id = i.ItemData; - flags = id.Flags; + int checkZ = item.Z; + int checkTop = checkZ + id.CalcHeight; - if ( (flags & (TileFlag.Window | TileFlag.NoShoot)) == 0 ) - continue; + if (checkTop == checkZ && !id.Surface) + ++checkTop; - height = id.CalcHeight; + if (checkTop > z && checkTop <= currentZ) + z = checkTop; + } - found = false; + if (z != int.MinValue) + toFix.Location = new Point3D(toFix.X, toFix.Y, z); + } - int count = path.Count; + FreeFixItems(items); + } - for ( int j = 0; j < count; ++j ) - { - Point3D point = path[j]; - int pointTop = point.m_Z + 1; - Point3D loc = i.Location; + /* This could probably be re-implemented if necessary (perhaps via an ITile interface?). + public List GetTilesAt( Point2D p, bool items, bool land, bool statics ) + { + List list = new List(); - //if ( t.Z <= point.Z && t.Z+height >= point.Z && ( height != 0 || ( t.Z == dest.Z && zd != 0 ) ) ) - if ( loc.m_X == point.m_X && loc.m_Y == point.m_Y && loc.m_Z <= pointTop && loc.m_Z + height >= point.m_Z ) - { - if (loc.m_X != end.m_X || loc.m_Y != end.m_Y || loc.m_Z > endTop || loc.m_Z + height < end.m_Z) - { - found = true; - break; - } - } - } + if ( this == Internal ) + return list; - if ( !found ) - continue; + if ( land ) + list.Add( Tiles.GetLandTile( p.m_X, p.m_Y ) ); - area.Free(); - return false; + if ( statics ) + list.AddRange( Tiles.GetStaticTiles( p.m_X, p.m_Y, true ) ); - /*if ( (flags & (TileFlag.Impassable | TileFlag.Surface | TileFlag.Roof)) != 0 ) + if ( items ) + { + Sector sector = GetSector( p ); - //flags = TileData.ItemTable[i.ItemID&TileData.MaxItemValue].Flags; - //if ( (flags&TileFlag.Window)==0 && (flags&TileFlag.NoShoot)!=0 && ( (flags&TileFlag.Wall)!=0 || (flags&TileFlag.Roof)!=0 || (((flags&TileFlag.Surface)!=0 && zd != 0)) ) ) - { - //height = TileData.ItemTable[i.ItemID&TileData.MaxItemValue].Height; - //Console.WriteLine( "LoS: Blocked by ITEM \"{0}\" P:{1} T:{2} F:x{3:X}", TileData.ItemTable[i.ItemID&TileData.MaxItemValue].Name, i.Location, i.Location.Z+height, flags ); - area.Free(); - return false; - }*/ - } + foreach ( Item item in sector.Items ) + if ( item.AtWorldPoint( p.m_X, p.m_Y ) ) + list.Add( new StaticTile( (ushort)item.ItemID, (sbyte) item.Z ) ); + } + + return list; + } + */ + + /// + /// Gets the highest surface that is lower than . + /// + /// The reference point. + /// A surface or . + public object GetTopSurface(Point3D p) + { + if (this == Internal) + return null; + + object surface = null; + int surfaceZ = int.MinValue; + + + LandTile lt = Tiles.GetLandTile(p.X, p.Y); - area.Free(); - return true; - } + if (!lt.Ignored) + { + int avgZ = GetAverageZ(p.X, p.Y); + + if (avgZ <= p.Z) + { + surface = lt; + surfaceZ = avgZ; + + if (surfaceZ == p.Z) + return surface; + } + } + + StaticTile[] staticTiles = Tiles.GetStaticTiles(p.X, p.Y, true); + + for (int i = 0; i < staticTiles.Length; i++) + { + StaticTile tile = staticTiles[i]; + ItemData id = TileData.ItemTable[tile.ID & TileData.MaxItemValue]; + + if (id.Surface || (id.Flags & TileFlag.Wet) != 0) + { + int tileZ = tile.Z + id.CalcHeight; + + if (tileZ > surfaceZ && tileZ <= p.Z) + { + surface = tile; + surfaceZ = tileZ; + + if (surfaceZ == p.Z) + return surface; + } + } + } + + Sector sector = GetSector(p.X, p.Y); + + for (int i = 0; i < sector.Items.Count; i++) + { + Item item = sector.Items[i]; + + if (!(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint(p.X, p.Y) && + !item.Movable) + { + ItemData id = item.ItemData; + + if (id.Surface || (id.Flags & TileFlag.Wet) != 0) + { + int itemZ = item.Z + id.CalcHeight; + + if (itemZ > surfaceZ && itemZ <= p.Z) + { + surface = item; + surfaceZ = itemZ; + + if (surfaceZ == p.Z) + return surface; + } + } + } + } + + return surface; + } + + public void Bound(int x, int y, out int newX, out int newY) + { + if (x < 0) + newX = 0; + else if (x >= Width) + newX = Width - 1; + else + newX = x; + + if (y < 0) + newY = 0; + else if (y >= Height) + newY = Height - 1; + else + newY = y; + } + + public Point2D Bound(Point2D p) + { + int x = p.m_X, y = p.m_Y; + + if (x < 0) + x = 0; + else if (x >= Width) + x = Width - 1; + + if (y < 0) + y = 0; + else if (y >= Height) + y = Height - 1; + + return new Point2D(x, y); + } + + public void ActivateSectors(int cx, int cy) + { + for (int x = cx - SectorActiveRange; x <= cx + SectorActiveRange; ++x) + for (int y = cy - SectorActiveRange; y <= cy + SectorActiveRange; ++y) + { + Sector sect = GetRealSector(x, y); + if (sect != InvalidSector) + sect.Activate(); + } + } + + public void DeactivateSectors(int cx, int cy) + { + for (int x = cx - SectorActiveRange; x <= cx + SectorActiveRange; ++x) + for (int y = cy - SectorActiveRange; y <= cy + SectorActiveRange; ++y) + { + Sector sect = GetRealSector(x, y); + if (sect != InvalidSector && !PlayersInRange(sect, SectorActiveRange)) + sect.Deactivate(); + } + } + + private bool PlayersInRange(Sector sect, int range) + { + for (int x = sect.X - range; x <= sect.X + range; ++x) + for (int y = sect.Y - range; y <= sect.Y + range; ++y) + { + Sector check = GetRealSector(x, y); + if (check != InvalidSector && check.Players.Count > 0) + return true; + } + + return false; + } + + public void OnClientChange(NetState oldState, NetState newState, Mobile m) + { + if (this != Internal) + GetSector(m).OnClientChange(oldState, newState); + } + + public void OnEnter(Mobile m) + { + if (this != Internal) + GetSector(m).OnEnter(m); + } + + public void OnEnter(Item item) + { + if (this == Internal) + return; + + GetSector(item).OnEnter(item); + + if (item is BaseMulti m) + { + MultiComponentList mcl = m.Components; + + Sector start = GetMultiMinSector(m.Location, mcl); + Sector end = GetMultiMaxSector(m.Location, mcl); + + AddMulti(m, start, end); + } + } + + public void OnLeave(Mobile m) + { + if (this != Internal) + GetSector(m).OnLeave(m); + } + + public void OnLeave(Item item) + { + if (this == Internal) + return; + + GetSector(item).OnLeave(item); + + if (item is BaseMulti m) + { + MultiComponentList mcl = m.Components; + + Sector start = GetMultiMinSector(m.Location, mcl); + Sector end = GetMultiMaxSector(m.Location, mcl); + + RemoveMulti(m, start, end); + } + } + + public void RemoveMulti(BaseMulti m, Sector start, Sector end) + { + if (this == Internal) + return; + + for (int x = start.X; x <= end.X; ++x) + for (int y = start.Y; y <= end.Y; ++y) + InternalGetSector(x, y).OnMultiLeave(m); + } + + public void AddMulti(BaseMulti m, Sector start, Sector end) + { + if (this == Internal) + return; + + for (int x = start.X; x <= end.X; ++x) + for (int y = start.Y; y <= end.Y; ++y) + InternalGetSector(x, y).OnMultiEnter(m); + } + + public Sector GetMultiMinSector(Point3D loc, MultiComponentList mcl) + { + return GetSector(Bound(new Point2D(loc.m_X + mcl.Min.m_X, loc.m_Y + mcl.Min.m_Y))); + } + + public Sector GetMultiMaxSector(Point3D loc, MultiComponentList mcl) + { + return GetSector(Bound(new Point2D(loc.m_X + mcl.Max.m_X, loc.m_Y + mcl.Max.m_Y))); + } + + public void OnMove(Point3D oldLocation, Mobile m) + { + if (this == Internal) + return; + + Sector oldSector = GetSector(oldLocation); + Sector newSector = GetSector(m.Location); + + if (oldSector != newSector) + { + oldSector.OnLeave(m); + newSector.OnEnter(m); + } + } + + public void OnMove(Point3D oldLocation, Item item) + { + if (this == Internal) + return; + + Sector oldSector = GetSector(oldLocation); + Sector newSector = GetSector(item.Location); + + if (oldSector != newSector) + { + oldSector.OnLeave(item); + newSector.OnEnter(item); + } + + if (item is BaseMulti m) + { + MultiComponentList mcl = m.Components; + + Sector start = GetMultiMinSector(m.Location, mcl); + Sector end = GetMultiMaxSector(m.Location, mcl); + + Sector oldStart = GetMultiMinSector(oldLocation, mcl); + Sector oldEnd = GetMultiMaxSector(oldLocation, mcl); + + if (oldStart != start || oldEnd != end) + { + RemoveMulti(m, oldStart, oldEnd); + AddMulti(m, start, end); + } + } + } + + public void RegisterRegion(Region reg) + { + string regName = reg.Name; + + if (regName != null) + { + if (Regions.ContainsKey(regName)) + Console.WriteLine("Warning: Duplicate region name '{0}' for map '{1}'", regName, Name); + else + Regions[regName] = reg; + } + } + + public void UnregisterRegion(Region reg) + { + string regName = reg.Name; + + if (regName != null) + Regions.Remove(regName); + } + + public Point3D GetPoint(object o, bool eye) + { + Point3D p; + + if (o is Mobile mobile) + { + p = mobile.Location; + p.Z += 14; //eye ? 15 : 10; + } + else if (o is Item item) + { + p = item.GetWorldLocation(); + p.Z += item.ItemData.Height / 2 + 1; + } + else if (o is Point3D point3D) + { + p = point3D; + } + else if (o is LandTarget target) + { + p = target.Location; + + int low = 0, avg = 0, top = 0; + GetAverageZ(p.X, p.Y, ref low, ref avg, ref top); + + p.Z = top + 1; + } + else if (o is StaticTarget st) + { + ItemData id = TileData.ItemTable[st.ItemID & TileData.MaxItemValue]; + + p = new Point3D(st.X, st.Y, st.Z - id.CalcHeight + id.Height / 2 + 1); + } + else if (o is IPoint3D d) + { + p = new Point3D(d); + } + else + { + Console.WriteLine("Warning: Invalid object ({0}) in line of sight", o); + p = Point3D.Zero; + } + + return p; + } + + private class ZComparer : IComparer + { + public static readonly ZComparer Default = new ZComparer(); + + public int Compare(Item x, Item y) + { + return x.Z.CompareTo(y.Z); + } + } + + public class NullEnumerable : IPooledEnumerable + { + public static readonly NullEnumerable Instance = new NullEnumerable(); + + private readonly IEnumerable _Empty; + + private NullEnumerable() + { + _Empty = Enumerable.Empty(); + } + + IEnumerator IEnumerable.GetEnumerator() + { + return _Empty.GetEnumerator(); + } + + public IEnumerator GetEnumerator() + { + return _Empty.GetEnumerator(); + } + + public void Free() + { + } + } + + public sealed class PooledEnumerable : IPooledEnumerable, IDisposable + { + private static readonly Queue> _Buffer = new Queue>(0x400); + + private bool _IsDisposed; + + private List _Pool = new List(0x40); + + public PooledEnumerable(IEnumerable pool) + { + _Pool.AddRange(pool); + } + + public void Dispose() + { + _IsDisposed = true; + + _Pool.Clear(); + _Pool.TrimExcess(); + _Pool = null; + } + + IEnumerator IEnumerable.GetEnumerator() + { + return _Pool.GetEnumerator(); + } + + public IEnumerator GetEnumerator() + { + return _Pool.GetEnumerator(); + } + + public void Free() + { + if (_IsDisposed) + return; + + _Pool.Clear(); + _Pool.Capacity = Math.Max(_Pool.Capacity, 0x100); + + lock (((ICollection)_Buffer).SyncRoot) + { + _Buffer.Enqueue(this); + } + } + + public static PooledEnumerable Instantiate(Map map, Rectangle2D bounds, PooledEnumeration.Selector selector) + { + PooledEnumerable e = null; + + lock (((ICollection)_Buffer).SyncRoot) + { + if (_Buffer.Count > 0) + e = _Buffer.Dequeue(); + } + + IEnumerable pool = PooledEnumeration.EnumerateSectors(map, bounds).SelectMany(s => selector(s, bounds)); + + if (e != null) + { + e._Pool.AddRange(pool); + return e; + } + + return new PooledEnumerable(pool); + } + } + + #region Get*InRange/Bounds + + public IPooledEnumerable GetObjectsInRange(Point3D p) + { + return GetObjectsInRange(p, Core.GlobalMaxUpdateRange); + } + + public IPooledEnumerable GetObjectsInRange(Point3D p, int range) + { + return GetObjectsInRange(p, range, true, true); + } + + public IPooledEnumerable GetObjectsInRange(Point3D p, int range, bool items, bool mobiles) + { + return GetObjectsInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1), items, + mobiles); + } + + public IPooledEnumerable GetObjectsInBounds(Rectangle2D bounds) + { + return GetObjectsInBounds(bounds, true, true); + } + + public IPooledEnumerable GetObjectsInBounds(Rectangle2D bounds, bool items, bool mobiles) + { + return PooledEnumeration.GetEntities(this, bounds, items, mobiles); + } + + public IPooledEnumerable GetClientsInRange(Point3D p) + { + return GetClientsInRange(p, Core.GlobalMaxUpdateRange); + } + + public IPooledEnumerable GetClientsInRange(Point3D p, int range) + { + return GetClientsInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1)); + } + + public IPooledEnumerable GetClientsInBounds(Rectangle2D bounds) + { + return PooledEnumeration.GetClients(this, bounds); + } + + public IPooledEnumerable GetItemsInRange(Point3D p) + { + return GetItemsInRange(p, Core.GlobalMaxUpdateRange); + } + + public IPooledEnumerable GetItemsInRange(Point3D p, int range) + { + return GetItemsInRange(p, range); + } + + public IPooledEnumerable GetItemsInRange(Point3D p, int range) where T : Item + { + return GetItemsInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1)); + } + + public IPooledEnumerable GetItemsInBounds(Rectangle2D bounds) + { + return GetItemsInBounds(bounds); + } + + public IPooledEnumerable GetItemsInBounds(Rectangle2D bounds) where T : Item + { + return PooledEnumeration.GetItems(this, bounds); + } + + public IPooledEnumerable GetMobilesInRange(Point3D p) + { + return GetMobilesInRange(p, Core.GlobalMaxUpdateRange); + } + + public IPooledEnumerable GetMobilesInRange(Point3D p, int range) + { + return GetMobilesInRange(p, range); + } + + public IPooledEnumerable GetMobilesInRange(Point3D p, int range) where T : Mobile + { + return GetMobilesInBounds(new Rectangle2D(p.m_X - range, p.m_Y - range, range * 2 + 1, range * 2 + 1)); + } + + public IPooledEnumerable GetMobilesInBounds(Rectangle2D bounds) + { + return GetMobilesInBounds(bounds); + } + + public IPooledEnumerable GetMobilesInBounds(Rectangle2D bounds) where T : Mobile + { + return PooledEnumeration.GetMobiles(this, bounds); + } + + #endregion + + #region CanFit + + public bool CanFit(Point3D p, int height, bool checkBlocksFit = false, bool checkMobiles = true, + bool requireSurface = true) + { + return CanFit(p.m_X, p.m_Y, p.m_Z, height, checkBlocksFit, checkMobiles, requireSurface); + } + + public bool CanFit(Point2D p, int z, int height, bool checkBlocksFit = false, bool checkMobiles = true, + bool requireSurface = true) + { + return CanFit(p.m_X, p.m_Y, z, height, checkBlocksFit, checkMobiles, requireSurface); + } + + public bool CanFit(int x, int y, int z, int height, bool checkBlocksFit = false, bool checkMobiles = true, + bool requireSurface = true) + { + if (this == Internal) + return false; + + if (x < 0 || y < 0 || x >= Width || y >= Height) + return false; + + bool hasSurface = false; + + LandTile lt = Tiles.GetLandTile(x, y); + int lowZ = 0, avgZ = 0, topZ = 0; + + GetAverageZ(x, y, ref lowZ, ref avgZ, ref topZ); + TileFlag landFlags = TileData.LandTable[lt.ID & TileData.MaxLandValue].Flags; + + if ((landFlags & TileFlag.Impassable) != 0 && avgZ > z && z + height > lowZ) + return false; + + if ((landFlags & TileFlag.Impassable) == 0 && z == avgZ && !lt.Ignored) + hasSurface = true; + + StaticTile[] staticTiles = Tiles.GetStaticTiles(x, y, true); + + bool surface, impassable; + + for (int i = 0; i < staticTiles.Length; ++i) + { + ItemData id = TileData.ItemTable[staticTiles[i].ID & TileData.MaxItemValue]; + surface = id.Surface; + impassable = id.Impassable; + + if ((surface || impassable) && staticTiles[i].Z + id.CalcHeight > z && z + height > staticTiles[i].Z) + return false; + + if (surface && !impassable && z == staticTiles[i].Z + id.CalcHeight) + hasSurface = true; + } + + Sector sector = GetSector(x, y); + List items = sector.Items; + List mobs = sector.Mobiles; - public bool LineOfSight( object from, object dest ) - { - return from == dest || (from as Mobile)?.AccessLevel > AccessLevel.Player || - (dest as Item)?.RootParent == from || LineOfSight(GetPoint(from, true), GetPoint(dest, false)); - } + for (int i = 0; i < items.Count; ++i) + { + Item item = items[i]; - public bool LineOfSight( Mobile from, Point3D target ) - { - if ( from.AccessLevel > AccessLevel.Player ) - return true; + if (!(item is BaseMulti) && item.ItemID <= TileData.MaxItemValue && item.AtWorldPoint(x, y)) + { + ItemData id = item.ItemData; + surface = id.Surface; + impassable = id.Impassable; - Point3D eye = from.Location; + if ((surface || impassable || checkBlocksFit && item.BlocksFit) && item.Z + id.CalcHeight > z && + z + height > item.Z) + return false; - eye.Z += 14; + if (surface && !impassable && !item.Movable && z == item.Z + id.CalcHeight) + hasSurface = true; + } + } - return LineOfSight( eye, target ); - } + if (checkMobiles) + for (int i = 0; i < mobs.Count; ++i) + { + Mobile m = mobs[i]; - public bool LineOfSight( Mobile from, Mobile to ) - { - if ( from == to || from.AccessLevel > AccessLevel.Player ) - return true; + if (m.Location.m_X == x && m.Location.m_Y == y && (m.AccessLevel == AccessLevel.Player || !m.Hidden) && + m.Z + 16 > z && z + height > m.Z) + return false; + } - Point3D eye = from.Location; - Point3D target = to.Location; + return !requireSurface || hasSurface; + } - eye.Z += 14; - target.Z += 14; //10; - - return LineOfSight( eye, target ); - } - #endregion + #endregion - public static int[] InvalidLandTiles { get; set; } = { 0x244 }; + #region CanSpawnMobile - public int CompareTo( Map other ) - { - if ( other == null ) - return -1; + public bool CanSpawnMobile(Point3D p) + { + return CanSpawnMobile(p.m_X, p.m_Y, p.m_Z); + } - return MapID.CompareTo( other.MapID ); - } + public bool CanSpawnMobile(Point2D p, int z) + { + return CanSpawnMobile(p.m_X, p.m_Y, z); + } - public int CompareTo( object other ) - { - if ( other == null || other is Map ) - return CompareTo( other ); + public bool CanSpawnMobile(int x, int y, int z) + { + if (!Region.Find(new Point3D(x, y, z), this).AllowSpawn()) + return false; - throw new ArgumentException(); - } - } -} + return CanFit(x, y, z, 16); + } + + #endregion + + #region GetSector + + public Sector GetSector(Point3D p) + { + return InternalGetSector(p.m_X >> SectorShift, p.m_Y >> SectorShift); + } + + public Sector GetSector(Point2D p) + { + return InternalGetSector(p.m_X >> SectorShift, p.m_Y >> SectorShift); + } + + public Sector GetSector(IPoint2D p) + { + return InternalGetSector(p.X >> SectorShift, p.Y >> SectorShift); + } + + public Sector GetSector(int x, int y) + { + return InternalGetSector(x >> SectorShift, y >> SectorShift); + } + + public Sector GetRealSector(int x, int y) + { + return InternalGetSector(x, y); + } + + private Sector InternalGetSector(int x, int y) + { + if (x >= 0 && x < m_SectorsWidth && y >= 0 && y < m_SectorsHeight) + { + Sector[] xSectors = m_Sectors[x]; + + if (xSectors == null) + m_Sectors[x] = xSectors = new Sector[m_SectorsHeight]; + + Sector sec = xSectors[y]; + + if (sec == null) + xSectors[y] = sec = new Sector(x, y, this); + + return sec; + } + + return InvalidSector; + } + + #endregion + + #region Line Of Sight + + public static int MaxLOSDistance{ get; set; } = 25; + + public bool LineOfSight(Point3D org, Point3D dest) + { + if (this == Internal) + return false; + + if (!Utility.InRange(org, dest, MaxLOSDistance)) + return false; + + Point3D end = dest; + + if (org.X > dest.X || org.X == dest.X && org.Y > dest.Y || org.X == dest.X && org.Y == dest.Y && org.Z > dest.Z) + { + Point3D swap = org; + org = dest; + dest = swap; + } + + double rise, run, zslp; + double sq3d; + double x, y, z; + int xd, yd, zd; + int ix, iy, iz; + int height; + bool found; + Point3D p; + Point3DList path = new Point3DList(); + TileFlag flags; + + if (org == dest) + return true; + + if (path.Count > 0) + path.Clear(); + + xd = dest.m_X - org.m_X; + yd = dest.m_Y - org.m_Y; + zd = dest.m_Z - org.m_Z; + zslp = Math.Sqrt(xd * xd + yd * yd); + if (zd != 0) + sq3d = Math.Sqrt(zslp * zslp + zd * zd); + else + sq3d = zslp; + + rise = yd / sq3d; + run = xd / sq3d; + zslp = zd / sq3d; + + y = org.m_Y; + z = org.m_Z; + x = org.m_X; + while (Utility.NumberBetween(x, dest.m_X, org.m_X, 0.5) && Utility.NumberBetween(y, dest.m_Y, org.m_Y, 0.5) && + Utility.NumberBetween(z, dest.m_Z, org.m_Z, 0.5)) + { + ix = (int)Math.Round(x); + iy = (int)Math.Round(y); + iz = (int)Math.Round(z); + if (path.Count > 0) + { + p = path.Last; + + if (p.m_X != ix || p.m_Y != iy || p.m_Z != iz) + path.Add(ix, iy, iz); + } + else + { + path.Add(ix, iy, iz); + } + + x += run; + y += rise; + z += zslp; + } + + if (path.Count == 0) + return true; //<--should never happen, but to be safe. + + p = path.Last; + + if (p != dest) + path.Add(dest); + + Point3D pTop = org, pBottom = dest; + Utility.FixPoints(ref pTop, ref pBottom); + + int pathCount = path.Count; + int endTop = end.m_Z + 1; + + for (int i = 0; i < pathCount; ++i) + { + Point3D point = path[i]; + int pointTop = point.m_Z + 1; + + LandTile landTile = Tiles.GetLandTile(point.X, point.Y); + int landZ = 0, landAvg = 0, landTop = 0; + GetAverageZ(point.m_X, point.m_Y, ref landZ, ref landAvg, ref landTop); + + if (landZ <= pointTop && landTop >= point.m_Z && + (point.m_X != end.m_X || point.m_Y != end.m_Y || landZ > endTop || landTop < end.m_Z) && + !landTile.Ignored) + return false; + + /* --Do land tiles need to be checked? There is never land between two people, always statics.-- + LandTile landTile = Tiles.GetLandTile( point.X, point.Y ); + if ( landTile.Z-1 >= point.Z && landTile.Z+1 <= point.Z && (TileData.LandTable[landTile.ID & TileData.MaxLandValue].Flags & TileFlag.Impassable) != 0 ) + return false; + */ + + StaticTile[] statics = Tiles.GetStaticTiles(point.m_X, point.m_Y, true); + + bool contains = false; + int ltID = landTile.ID; + + for (int j = 0; !contains && j < InvalidLandTiles.Length; ++j) + contains = ltID == InvalidLandTiles[j]; + + if (contains && statics.Length == 0) + { + IPooledEnumerable eable = GetItemsInRange(point, 0); + + foreach (Item item in eable) + { + if (item.Visible) + contains = false; + + if (!contains) + break; + } + + eable.Free(); + + if (contains) + return false; + } + + for (int j = 0; j < statics.Length; ++j) + { + StaticTile t = statics[j]; + + ItemData id = TileData.ItemTable[t.ID & TileData.MaxItemValue]; + + flags = id.Flags; + height = id.CalcHeight; + + if (t.Z <= pointTop && t.Z + height >= point.Z && (flags & (TileFlag.Window | TileFlag.NoShoot)) != 0) + { + if (point.m_X == end.m_X && point.m_Y == end.m_Y && t.Z <= endTop && t.Z + height >= end.m_Z) + continue; + + return false; + } + + /*if ( t.Z <= point.Z && t.Z+height >= point.Z && (flags&TileFlag.Window)==0 && (flags&TileFlag.NoShoot)!=0 + && ( (flags&TileFlag.Wall)!=0 || (flags&TileFlag.Roof)!=0 || (((flags&TileFlag.Surface)!=0 && zd != 0)) ) )*/ + /*{ + //Console.WriteLine( "LoS: Blocked by Static \"{0}\" Z:{1} T:{3} P:{2} F:x{4:X}", TileData.ItemTable[t.ID&TileData.MaxItemValue].Name, t.Z, point, t.Z+height, flags ); + //Console.WriteLine( "if ( {0} && {1} && {2} && ( {3} || {4} || {5} || ({6} && {7} && {8}) ) )", t.Z <= point.Z, t.Z+height >= point.Z, (flags&TileFlag.Window)==0, (flags&TileFlag.Impassable)!=0, (flags&TileFlag.Wall)!=0, (flags&TileFlag.Roof)!=0, (flags&TileFlag.Surface)!=0, t.Z != dest.Z, zd != 0 ) ; + return false; + }*/ + } + } + + Rectangle2D rect = new Rectangle2D(pTop.m_X, pTop.m_Y, pBottom.m_X - pTop.m_X + 1, pBottom.m_Y - pTop.m_Y + 1); + + IPooledEnumerable area = GetItemsInBounds(rect); + + foreach (Item i in area) + { + if (!i.Visible) + continue; + + if (i is BaseMulti || i.ItemID > TileData.MaxItemValue) + continue; + + ItemData id = i.ItemData; + flags = id.Flags; + + if ((flags & (TileFlag.Window | TileFlag.NoShoot)) == 0) + continue; + + height = id.CalcHeight; + + found = false; + + int count = path.Count; + + for (int j = 0; j < count; ++j) + { + Point3D point = path[j]; + int pointTop = point.m_Z + 1; + Point3D loc = i.Location; + + //if ( t.Z <= point.Z && t.Z+height >= point.Z && ( height != 0 || ( t.Z == dest.Z && zd != 0 ) ) ) + if (loc.m_X == point.m_X && loc.m_Y == point.m_Y && loc.m_Z <= pointTop && loc.m_Z + height >= point.m_Z) + if (loc.m_X != end.m_X || loc.m_Y != end.m_Y || loc.m_Z > endTop || loc.m_Z + height < end.m_Z) + { + found = true; + break; + } + } + + if (!found) + continue; + + area.Free(); + return false; + + /*if ( (flags & (TileFlag.Impassable | TileFlag.Surface | TileFlag.Roof)) != 0 ) + + //flags = TileData.ItemTable[i.ItemID&TileData.MaxItemValue].Flags; + //if ( (flags&TileFlag.Window)==0 && (flags&TileFlag.NoShoot)!=0 && ( (flags&TileFlag.Wall)!=0 || (flags&TileFlag.Roof)!=0 || (((flags&TileFlag.Surface)!=0 && zd != 0)) ) ) + { + //height = TileData.ItemTable[i.ItemID&TileData.MaxItemValue].Height; + //Console.WriteLine( "LoS: Blocked by ITEM \"{0}\" P:{1} T:{2} F:x{3:X}", TileData.ItemTable[i.ItemID&TileData.MaxItemValue].Name, i.Location, i.Location.Z+height, flags ); + area.Free(); + return false; + }*/ + } + + area.Free(); + return true; + } + + public bool LineOfSight(object from, object dest) + { + return from == dest || (from as Mobile)?.AccessLevel > AccessLevel.Player || + (dest as Item)?.RootParent == from || LineOfSight(GetPoint(from, true), GetPoint(dest, false)); + } + + public bool LineOfSight(Mobile from, Point3D target) + { + if (from.AccessLevel > AccessLevel.Player) + return true; + + Point3D eye = from.Location; + + eye.Z += 14; + + return LineOfSight(eye, target); + } + + public bool LineOfSight(Mobile from, Mobile to) + { + if (from == to || from.AccessLevel > AccessLevel.Player) + return true; + + Point3D eye = from.Location; + Point3D target = to.Location; + + eye.Z += 14; + target.Z += 14; //10; + + return LineOfSight(eye, target); + } + + #endregion + } +} \ No newline at end of file diff --git a/Server/Menus/IMenu.cs b/Server/Menus/IMenu.cs index fe89561c1..56405f32e 100644 --- a/Server/Menus/IMenu.cs +++ b/Server/Menus/IMenu.cs @@ -22,12 +22,12 @@ using Server.Network; namespace Server.Menus { - public interface IMenu - { - int Serial{ get; } - int EntryLength{ get; } - void SendTo( NetState state ); - void OnCancel( NetState state ); - void OnResponse( NetState state, int index ); - } + public interface IMenu + { + int Serial{ get; } + int EntryLength{ get; } + void SendTo(NetState state); + void OnCancel(NetState state); + void OnResponse(NetState state, int index); + } } \ No newline at end of file diff --git a/Server/Menus/ItemListMenu.cs b/Server/Menus/ItemListMenu.cs index 3d0cfceb2..a456ff5e2 100644 --- a/Server/Menus/ItemListMenu.cs +++ b/Server/Menus/ItemListMenu.cs @@ -22,65 +22,65 @@ using Server.Network; namespace Server.Menus.ItemLists { - public class ItemListEntry - { - public string Name { get; } + public class ItemListEntry + { + public ItemListEntry(string name, int itemID) : this(name, itemID, 0) + { + } - public int ItemID { get; } + public ItemListEntry(string name, int itemID, int hue) + { + Name = name; + ItemID = itemID; + Hue = hue; + } - public int Hue { get; } + public string Name{ get; } - public ItemListEntry( string name, int itemID ) : this( name, itemID, 0 ) - { - } + public int ItemID{ get; } - public ItemListEntry( string name, int itemID, int hue ) - { - Name = name; - ItemID = itemID; - Hue = hue; - } - } + public int Hue{ get; } + } - public class ItemListMenu : IMenu - { - private int m_Serial; - private static int m_NextSerial; + public class ItemListMenu : IMenu + { + private static int m_NextSerial; + private int m_Serial; - int IMenu.Serial => m_Serial; + public ItemListMenu(string question, ItemListEntry[] entries) + { + Question = question; + Entries = entries; - int IMenu.EntryLength => Entries.Length; + do + { + m_Serial = m_NextSerial++; + m_Serial &= 0x7FFFFFFF; + } while (m_Serial == 0); - public string Question { get; } + m_Serial = (int)((uint)m_Serial | 0x80000000); + } - public ItemListEntry[] Entries { get; set; } + public string Question{ get; } - public ItemListMenu( string question, ItemListEntry[] entries ) - { - Question = question; - Entries = entries; + public ItemListEntry[] Entries{ get; set; } - do - { - m_Serial = m_NextSerial++; - m_Serial &= 0x7FFFFFFF; - } while ( m_Serial == 0 ); + int IMenu.Serial => m_Serial; - m_Serial = (int)((uint)m_Serial | 0x80000000); - } + int IMenu.EntryLength => Entries.Length; - public virtual void OnCancel( NetState state ) - { - } + public virtual void OnCancel(NetState state) + { + } - public virtual void OnResponse( NetState state, int index ) - { - } + public virtual void OnResponse(NetState state, int index) + { + } - public void SendTo( NetState state ) - { - state.AddMenu( this ); - state.Send( new DisplayItemListMenu( this ) ); - } - } + public void SendTo(NetState state) + { + state.AddMenu(this); + state.Send(new DisplayItemListMenu(this)); + } + } } \ No newline at end of file diff --git a/Server/Menus/QuestionMenu.cs b/Server/Menus/QuestionMenu.cs index 94212e8c8..0fe6a5aa2 100644 --- a/Server/Menus/QuestionMenu.cs +++ b/Server/Menus/QuestionMenu.cs @@ -22,43 +22,43 @@ using Server.Network; namespace Server.Menus.Questions { - public class QuestionMenu : IMenu - { - private int m_Serial; - private static int m_NextSerial; + public class QuestionMenu : IMenu + { + private static int m_NextSerial; + private int m_Serial; - int IMenu.Serial => m_Serial; + public QuestionMenu(string question, string[] answers) + { + Question = question; + Answers = answers; - int IMenu.EntryLength => Answers.Length; + do + { + m_Serial = ++m_NextSerial; + m_Serial &= 0x7FFFFFFF; + } while (m_Serial == 0); + } - public string Question { get; set; } + public string Question{ get; set; } - public string[] Answers { get; } + public string[] Answers{ get; } - public QuestionMenu( string question, string[] answers ) - { - Question = question; - Answers = answers; + int IMenu.Serial => m_Serial; - do - { - m_Serial = ++m_NextSerial; - m_Serial &= 0x7FFFFFFF; - } while ( m_Serial == 0 ); - } + int IMenu.EntryLength => Answers.Length; - public virtual void OnCancel( NetState state ) - { - } + public virtual void OnCancel(NetState state) + { + } - public virtual void OnResponse( NetState state, int index ) - { - } + public virtual void OnResponse(NetState state, int index) + { + } - public void SendTo( NetState state ) - { - state.AddMenu( this ); - state.Send( new DisplayQuestionMenu( this ) ); - } - } + public void SendTo(NetState state) + { + state.AddMenu(this); + state.Send(new DisplayQuestionMenu(this)); + } + } } \ No newline at end of file diff --git a/Server/Mobile.cs b/Server/Mobile.cs index 0c3f36825..38f01b6a1 100644 --- a/Server/Mobile.cs +++ b/Server/Mobile.cs @@ -20,6 +20,7 @@ using System; using System.Collections.Generic; +using System.Diagnostics; using System.IO; using System.Text; using System.Threading.Tasks; @@ -38,10634 +39,10331 @@ using Server.Targeting; namespace Server { - #region Callbacks - public delegate void TargetCallback( Mobile from, object targeted ); - public delegate void TargetStateCallback( Mobile from, object targeted, object state ); - public delegate void TargetStateCallback( Mobile from, object targeted, T state ); - - public delegate void PromptCallback( Mobile from, string text ); - public delegate void PromptStateCallback( Mobile from, string text, object state ); - public delegate void PromptStateCallback( Mobile from, string text, T state ); - #endregion - - #region [...]Mods - public class TimedSkillMod : SkillMod - { - private DateTime m_Expire; - - public TimedSkillMod( SkillName skill, bool relative, double value, TimeSpan delay ) - : this( skill, relative, value, DateTime.UtcNow + delay ) - { - } - - public TimedSkillMod( SkillName skill, bool relative, double value, DateTime expire ) - : base( skill, relative, value ) - { - m_Expire = expire; - } - - public override bool CheckCondition() - { - return (DateTime.UtcNow < m_Expire); - } - } - - public class EquippedSkillMod : SkillMod - { - private Item m_Item; - private Mobile m_Mobile; - - public EquippedSkillMod( SkillName skill, bool relative, double value, Item item, Mobile mobile ) - : base( skill, relative, value ) - { - m_Item = item; - m_Mobile = mobile; - } - - public override bool CheckCondition() - { - return (!m_Item.Deleted && !m_Mobile.Deleted && m_Item.Parent == m_Mobile); - } - } - - public class DefaultSkillMod : SkillMod - { - public DefaultSkillMod( SkillName skill, bool relative, double value ) - : base( skill, relative, value ) - { - } - - public override bool CheckCondition() - { - return true; - } - } - - public abstract class SkillMod - { - private Mobile m_Owner; - private SkillName m_Skill; - private bool m_Relative; - private double m_Value; - private bool m_ObeyCap; - - protected SkillMod( SkillName skill, bool relative, double value ) - { - m_Skill = skill; - m_Relative = relative; - m_Value = value; - } - - public bool ObeyCap - { - get => m_ObeyCap; - set - { - m_ObeyCap = value; - - Skill sk = m_Owner?.Skills[m_Skill]; - sk?.Update(); - } - } - - public Mobile Owner - { - get => m_Owner; - set - { - if ( m_Owner != value ) - { - m_Owner?.RemoveSkillMod( this ); - - m_Owner = value; - - if ( m_Owner != value ) - m_Owner.AddSkillMod( this ); - } - } - } - - public void Remove() - { - Owner = null; - } - - public SkillName Skill - { - get => m_Skill; - set - { - if ( m_Skill != value ) - { - Skill oldUpdate = m_Owner?.Skills[m_Skill]; - - m_Skill = value; - - Skill sk = m_Owner?.Skills[m_Skill]; - sk?.Update(); - oldUpdate?.Update(); - } - } - } - - public bool Relative - { - get => m_Relative; - set - { - if ( m_Relative != value ) - { - m_Relative = value; - - Skill sk = m_Owner?.Skills[m_Skill]; - sk?.Update(); - } - } - } - - public bool Absolute - { - get => !m_Relative; - set - { - if ( m_Relative == value ) - { - m_Relative = !value; - - Skill sk = m_Owner?.Skills[m_Skill]; - sk?.Update(); - } - } - } - - public double Value - { - get => m_Value; - set - { - if ( m_Value != value ) - { - m_Value = value; - - Skill sk = m_Owner?.Skills[m_Skill]; - sk?.Update(); - } - } - } - - public abstract bool CheckCondition(); - } - - public class ResistanceMod - { - private Mobile m_Owner; - private ResistanceType m_Type; - private int m_Offset; - - public Mobile Owner - { - get => m_Owner; - set => m_Owner = value; - } - - public ResistanceType Type - { - get => m_Type; - set - { - if ( m_Type != value ) - { - m_Type = value; - - m_Owner?.UpdateResistances(); - } - } - } - - public int Offset - { - get => m_Offset; - set - { - if ( m_Offset != value ) - { - m_Offset = value; - - m_Owner?.UpdateResistances(); - } - } - } - - public ResistanceMod( ResistanceType type, int offset ) - { - m_Type = type; - m_Offset = offset; - } - } - - public class StatMod - { - private StatType m_Type; - private string m_Name; - private int m_Offset; - private TimeSpan m_Duration; - private DateTime m_Added; - - public StatType Type => m_Type; - public string Name => m_Name; - public int Offset => m_Offset; - - public bool HasElapsed() - { - if ( m_Duration == TimeSpan.Zero ) - return false; - - return (DateTime.UtcNow - m_Added) >= m_Duration; - } - - public StatMod( StatType type, string name, int offset, TimeSpan duration ) - { - m_Type = type; - m_Name = name; - m_Offset = offset; - m_Duration = duration; - m_Added = DateTime.UtcNow; - } - } - - #endregion - - public class DamageEntry - { - private Mobile m_Damager; - private int m_DamageGiven; - private DateTime m_LastDamage; - private List m_Responsible; - - public Mobile Damager => m_Damager; - public int DamageGiven { get => m_DamageGiven; - set => m_DamageGiven = value; - } - public DateTime LastDamage { get => m_LastDamage; - set => m_LastDamage = value; - } - public bool HasExpired => (DateTime.UtcNow > (m_LastDamage + m_ExpireDelay)); - public List Responsible { get => m_Responsible; - set => m_Responsible = value; - } - - private static TimeSpan m_ExpireDelay = TimeSpan.FromMinutes( 2.0 ); - - public static TimeSpan ExpireDelay - { - get => m_ExpireDelay; - set => m_ExpireDelay = value; - } - - public DamageEntry( Mobile damager ) - { - m_Damager = damager; - } - } - - #region Enums - [Flags] - public enum StatType - { - Str=1, - Dex=2, - Int=4, - All=7 - } - - public enum StatLockType : byte - { - Up, - Down, - Locked - } - - [CustomEnum( new[] { "North", "Right", "East", "Down", "South", "Left", "West", "Up" } )] - [Flags] - public enum Direction : byte - { - North=0x0, - Right=0x1, - East=0x2, - Down=0x3, - South=0x4, - Left=0x5, - West=0x6, - Up=0x7, - - Mask=0x7, - Running=0x80, - ValueMask=0x87 - } - - [Flags] - public enum MobileDelta - { - None= 0x00000000, - Name= 0x00000001, - Flags= 0x00000002, - Hits= 0x00000004, - Mana= 0x00000008, - Stam= 0x00000010, - Stat= 0x00000020, - Noto= 0x00000040, - Gold= 0x00000080, - Weight= 0x00000100, - Direction= 0x00000200, - Hue= 0x00000400, - Body= 0x00000800, - Armor= 0x00001000, - StatCap= 0x00002000, - GhostUpdate= 0x00004000, - Followers= 0x00008000, - Properties= 0x00010000, - TithingPoints= 0x00020000, - Resistances= 0x00040000, - WeaponDamage= 0x00080000, - Hair= 0x00100000, - FacialHair= 0x00200000, - Race= 0x00400000, - HealthbarYellow=0x00800000, - HealthbarPoison=0x01000000, - - Attributes= 0x0000001C - } - - public enum AccessLevel - { - Player, - Counselor, - GameMaster, - Seer, - Administrator, - Developer, - Owner - } - - public enum VisibleDamageType - { - None, - Related, - Everyone, - Selective - } - - public enum ResistanceType - { - Physical, - Fire, - Cold, - Poison, - Energy - } - - public enum ApplyPoisonResult - { - Poisoned, - Immune, - HigherPoisonActive, - Cured - } - #endregion - - [Serializable] - public class MobileNotConnectedException : Exception - { - public MobileNotConnectedException( Mobile source, string message ) - : base( message ) - { - Source = source.ToString(); - } - } - - #region Delegates - - public delegate bool SkillCheckTargetHandler( Mobile from, SkillName skill, object target, double minSkill, double maxSkill ); - public delegate bool SkillCheckLocationHandler( Mobile from, SkillName skill, double minSkill, double maxSkill ); - - public delegate bool SkillCheckDirectTargetHandler( Mobile from, SkillName skill, object target, double chance ); - public delegate bool SkillCheckDirectLocationHandler( Mobile from, SkillName skill, double chance ); - - public delegate TimeSpan RegenRateHandler( Mobile from ); - - public delegate bool AllowBeneficialHandler( Mobile from, Mobile target ); - public delegate bool AllowHarmfulHandler( Mobile from, Mobile target ); - - public delegate Container CreateCorpseHandler( Mobile from, HairInfo hair, FacialHairInfo facialhair, List initialContent, List equippedItems ); - - public delegate int AOSStatusHandler( Mobile from, int index ); - - #endregion - - /// - /// Base class representing players, npcs, and creatures. - /// - public class Mobile : IEntity, IHued, IComparable, ISerializable, ISpawnable - { - #region CompareTo(...) - public int CompareTo( IEntity other ) - { - if ( other == null ) - return -1; - - return m_Serial.CompareTo( other.Serial ); - } - - public int CompareTo( Mobile other ) - { - return CompareTo( (IEntity)other ); - } - - public int CompareTo( object other ) - { - if ( other == null || other is IEntity ) - return CompareTo( (IEntity)other ); - - throw new ArgumentException(); - } - #endregion - - private static bool m_DragEffects = true; - - public static bool DragEffects - { - get => m_DragEffects; - set => m_DragEffects = value; - } - - #region Handlers - - private static AllowBeneficialHandler m_AllowBeneficialHandler; - private static AllowHarmfulHandler m_AllowHarmfulHandler; - - public static AllowBeneficialHandler AllowBeneficialHandler - { - get => m_AllowBeneficialHandler; - set => m_AllowBeneficialHandler = value; - } - - public static AllowHarmfulHandler AllowHarmfulHandler - { - get => m_AllowHarmfulHandler; - set => m_AllowHarmfulHandler = value; - } - - private static SkillCheckTargetHandler m_SkillCheckTargetHandler; - private static SkillCheckLocationHandler m_SkillCheckLocationHandler; - private static SkillCheckDirectTargetHandler m_SkillCheckDirectTargetHandler; - private static SkillCheckDirectLocationHandler m_SkillCheckDirectLocationHandler; - - public static SkillCheckTargetHandler SkillCheckTargetHandler - { - get => m_SkillCheckTargetHandler; - set => m_SkillCheckTargetHandler = value; - } - - public static SkillCheckLocationHandler SkillCheckLocationHandler - { - get => m_SkillCheckLocationHandler; - set => m_SkillCheckLocationHandler = value; - } - - public static SkillCheckDirectTargetHandler SkillCheckDirectTargetHandler - { - get => m_SkillCheckDirectTargetHandler; - set => m_SkillCheckDirectTargetHandler = value; - } - - public static SkillCheckDirectLocationHandler SkillCheckDirectLocationHandler - { - get => m_SkillCheckDirectLocationHandler; - set => m_SkillCheckDirectLocationHandler = value; - } - - private static AOSStatusHandler m_AOSStatusHandler; - - public static AOSStatusHandler AOSStatusHandler - { - get => m_AOSStatusHandler; - set => m_AOSStatusHandler = value; - } - - #endregion - - #region Regeneration - - private static RegenRateHandler m_HitsRegenRate, m_StamRegenRate, m_ManaRegenRate; - private static TimeSpan m_DefaultHitsRate, m_DefaultStamRate, m_DefaultManaRate; - - public static RegenRateHandler HitsRegenRateHandler - { - get => m_HitsRegenRate; - set => m_HitsRegenRate = value; - } - - public static TimeSpan DefaultHitsRate - { - get => m_DefaultHitsRate; - set => m_DefaultHitsRate = value; - } - - public static RegenRateHandler StamRegenRateHandler - { - get => m_StamRegenRate; - set => m_StamRegenRate = value; - } - - public static TimeSpan DefaultStamRate - { - get => m_DefaultStamRate; - set => m_DefaultStamRate = value; - } - - public static RegenRateHandler ManaRegenRateHandler - { - get => m_ManaRegenRate; - set => m_ManaRegenRate = value; - } - - public static TimeSpan DefaultManaRate - { - get => m_DefaultManaRate; - set => m_DefaultManaRate = value; - } - - public static TimeSpan GetHitsRegenRate( Mobile m ) - { - if ( m_HitsRegenRate == null ) - return m_DefaultHitsRate; - return m_HitsRegenRate( m ); - } - - public static TimeSpan GetStamRegenRate( Mobile m ) - { - if ( m_StamRegenRate == null ) - return m_DefaultStamRate; - return m_StamRegenRate( m ); - } - - public static TimeSpan GetManaRegenRate( Mobile m ) - { - if ( m_ManaRegenRate == null ) - return m_DefaultManaRate; - return m_ManaRegenRate( m ); - } - - #endregion - - private class MovementRecord - { - public long m_End; - - private static Queue m_InstancePool = new Queue(); - - public static MovementRecord NewInstance( long end ) - { - MovementRecord r; - - if ( m_InstancePool.Count > 0 ) - { - r = m_InstancePool.Dequeue(); - - r.m_End = end; - } - else - { - r = new MovementRecord( end ); - } - - return r; - } - - private MovementRecord( long end ) - { - m_End = end; - } - - public bool Expired() - { - bool v = (Core.TickCount - m_End >= 0); - - if ( v ) - m_InstancePool.Enqueue( this ); - - return v; - } - } - - #region Var declarations - private Serial m_Serial; - private Map m_Map; - private Point3D m_Location; - private Direction m_Direction; - private Body m_Body; - private int m_Hue; - private Poison m_Poison; - private Timer m_PoisonTimer; - private BaseGuild m_Guild; - private string m_GuildTitle; - private bool m_Criminal; - private string m_Name; - private int m_Kills, m_ShortTermMurders; - private int m_SpeechHue, m_EmoteHue, m_WhisperHue, m_YellHue; - private string m_Language; - private NetState m_NetState; - private bool m_Female, m_Warmode, m_Hidden, m_Blessed, m_Flying; - private int m_StatCap; - private int m_Str, m_Dex, m_Int; - private int m_Hits, m_Stam, m_Mana; - private int m_Fame, m_Karma; - private AccessLevel m_AccessLevel; - private Skills m_Skills; - private List m_Items; - private bool m_Player; - private string m_Title; - private string m_Profile; - private bool m_ProfileLocked; - private int m_LightLevel; - private int m_TotalGold, m_TotalItems, m_TotalWeight; - private List m_StatMods; - private ISpell m_Spell; - private Target m_Target; - private Prompt m_Prompt; - private ContextMenu m_ContextMenu; - private List m_Aggressors, m_Aggressed; - private Mobile m_Combatant; - private List m_Stabled; - private bool m_AutoPageNotify; - private bool m_Meditating; - private bool m_CanHearGhosts; - private bool m_CanSwim, m_CantWalk; - private int m_TithingPoints; - private bool m_DisplayGuildTitle; - private Mobile m_GuildFealty; - private long m_NextSpellTime; - private Timer m_ExpireCombatant; - private Timer m_ExpireCriminal; - private Timer m_ExpireAggrTimer; - private Timer m_LogoutTimer; - private Timer m_CombatTimer; - private Timer m_ManaTimer, m_HitsTimer, m_StamTimer; - private long m_NextSkillTime; - private long m_NextActionTime; - private long m_NextActionMessage; - private bool m_Paralyzed; - private ParalyzedTimer m_ParaTimer; - private bool m_Frozen; - private FrozenTimer m_FrozenTimer; - private int m_AllowedStealthSteps; - private int m_Hunger; - private int m_NameHue = -1; - private Region m_Region; - private bool m_DisarmReady, m_StunReady; - private int m_BaseSoundID; - private int m_VirtualArmor; - private bool m_Squelched; - private int m_MeleeDamageAbsorb; - private int m_MagicDamageAbsorb; - private int m_Followers, m_FollowersMax; - private List _actions; // prefer List over ArrayList for more specific profiling information - private Queue m_MoveRecords; - private int m_WarmodeChanges = 0; - private DateTime m_NextWarmodeChange; - private WarmodeTimer m_WarmodeTimer; - private int m_Thirst, m_BAC; - private int m_VirtualArmorMod; - private VirtueInfo m_Virtues; - private object m_Party; - private List m_SkillMods; - private Body m_BodyMod; - private DateTime m_LastStrGain; - private DateTime m_LastIntGain; - private DateTime m_LastDexGain; - private Race m_Race; - - #endregion - - private static readonly TimeSpan WarmodeSpamCatch = TimeSpan.FromSeconds( (Core.SE ? 1.0 : 0.5) ); - private static readonly TimeSpan WarmodeSpamDelay = TimeSpan.FromSeconds( (Core.SE ? 4.0 : 2.0) ); - private const int WarmodeCatchCount = 4; // Allow four warmode changes in 0.5 seconds, any more will be delay for two seconds - - [CommandProperty( AccessLevel.GameMaster )] - public Race Race - { - get - { - if ( m_Race == null ) - m_Race = Race.DefaultRace; - - return m_Race; - } - set - { - Race oldRace = Race; - - m_Race = value; - - if ( m_Race == null ) - m_Race = Race.DefaultRace; - - Body = m_Race.Body( this ); - UpdateResistances(); - - Delta( MobileDelta.Race ); - - OnRaceChange( oldRace ); - } - } - - protected virtual void OnRaceChange( Race oldRace ) - { - } - - public virtual double RacialSkillBonus => 0; - - private List m_ResistMods; - - private int[] m_Resistances; - - public int[] Resistances => m_Resistances; - - public virtual int BasePhysicalResistance => 0; - public virtual int BaseFireResistance => 0; - public virtual int BaseColdResistance => 0; - public virtual int BasePoisonResistance => 0; - public virtual int BaseEnergyResistance => 0; - - public virtual void ComputeLightLevels( out int global, out int personal ) - { - ComputeBaseLightLevels( out global, out personal ); - - m_Region?.AlterLightLevel( this, ref global, ref personal ); - } - - public virtual void ComputeBaseLightLevels( out int global, out int personal ) - { - global = 0; - personal = m_LightLevel; - } - - public virtual void CheckLightLevels( bool forceResend ) - { - } - - [CommandProperty( AccessLevel.Counselor )] - public virtual int PhysicalResistance => GetResistance( ResistanceType.Physical ); - - [CommandProperty( AccessLevel.Counselor )] - public virtual int FireResistance => GetResistance( ResistanceType.Fire ); - - [CommandProperty( AccessLevel.Counselor )] - public virtual int ColdResistance => GetResistance( ResistanceType.Cold ); - - [CommandProperty( AccessLevel.Counselor )] - public virtual int PoisonResistance => GetResistance( ResistanceType.Poison ); - - [CommandProperty( AccessLevel.Counselor )] - public virtual int EnergyResistance => GetResistance( ResistanceType.Energy ); - - public virtual void UpdateResistances() - { - if ( m_Resistances == null ) - m_Resistances = new int[5] { int.MinValue, int.MinValue, int.MinValue, int.MinValue, int.MinValue }; - - bool delta = false; + #region Callbacks + + public delegate void TargetCallback(Mobile from, object targeted); + + public delegate void TargetStateCallback(Mobile from, object targeted, object state); + + public delegate void TargetStateCallback(Mobile from, object targeted, T state); + + public delegate void PromptCallback(Mobile from, string text); + + public delegate void PromptStateCallback(Mobile from, string text, object state); + + public delegate void PromptStateCallback(Mobile from, string text, T state); + + #endregion + + #region [...]Mods + + public class TimedSkillMod : SkillMod + { + private DateTime m_Expire; + + public TimedSkillMod(SkillName skill, bool relative, double value, TimeSpan delay) + : this(skill, relative, value, DateTime.UtcNow + delay) + { + } + + public TimedSkillMod(SkillName skill, bool relative, double value, DateTime expire) + : base(skill, relative, value) + { + m_Expire = expire; + } + + public override bool CheckCondition() + { + return DateTime.UtcNow < m_Expire; + } + } + + public class EquippedSkillMod : SkillMod + { + private Item m_Item; + private Mobile m_Mobile; + + public EquippedSkillMod(SkillName skill, bool relative, double value, Item item, Mobile mobile) + : base(skill, relative, value) + { + m_Item = item; + m_Mobile = mobile; + } + + public override bool CheckCondition() + { + return !m_Item.Deleted && !m_Mobile.Deleted && m_Item.Parent == m_Mobile; + } + } + + public class DefaultSkillMod : SkillMod + { + public DefaultSkillMod(SkillName skill, bool relative, double value) + : base(skill, relative, value) + { + } + + public override bool CheckCondition() + { + return true; + } + } + + public abstract class SkillMod + { + private bool m_ObeyCap; + private Mobile m_Owner; + private bool m_Relative; + private SkillName m_Skill; + private double m_Value; + + protected SkillMod(SkillName skill, bool relative, double value) + { + m_Skill = skill; + m_Relative = relative; + m_Value = value; + } + + public bool ObeyCap + { + get => m_ObeyCap; + set + { + m_ObeyCap = value; + + Skill sk = m_Owner?.Skills[m_Skill]; + sk?.Update(); + } + } + + public Mobile Owner + { + get => m_Owner; + set + { + if (m_Owner != value) + { + m_Owner?.RemoveSkillMod(this); + + m_Owner = value; + + if (m_Owner != value) + m_Owner.AddSkillMod(this); + } + } + } + + public SkillName Skill + { + get => m_Skill; + set + { + if (m_Skill != value) + { + Skill oldUpdate = m_Owner?.Skills[m_Skill]; + + m_Skill = value; + + Skill sk = m_Owner?.Skills[m_Skill]; + sk?.Update(); + oldUpdate?.Update(); + } + } + } + + public bool Relative + { + get => m_Relative; + set + { + if (m_Relative != value) + { + m_Relative = value; + + Skill sk = m_Owner?.Skills[m_Skill]; + sk?.Update(); + } + } + } + + public bool Absolute + { + get => !m_Relative; + set + { + if (m_Relative == value) + { + m_Relative = !value; + + Skill sk = m_Owner?.Skills[m_Skill]; + sk?.Update(); + } + } + } + + public double Value + { + get => m_Value; + set + { + if (m_Value != value) + { + m_Value = value; + + Skill sk = m_Owner?.Skills[m_Skill]; + sk?.Update(); + } + } + } + + public void Remove() + { + Owner = null; + } + + public abstract bool CheckCondition(); + } + + public class ResistanceMod + { + private int m_Offset; + private ResistanceType m_Type; + + public ResistanceMod(ResistanceType type, int offset) + { + m_Type = type; + m_Offset = offset; + } + + public Mobile Owner{ get; set; } + + public ResistanceType Type + { + get => m_Type; + set + { + if (m_Type != value) + { + m_Type = value; + + Owner?.UpdateResistances(); + } + } + } + + public int Offset + { + get => m_Offset; + set + { + if (m_Offset != value) + { + m_Offset = value; + + Owner?.UpdateResistances(); + } + } + } + } + + public class StatMod + { + private DateTime m_Added; + private TimeSpan m_Duration; + + public StatMod(StatType type, string name, int offset, TimeSpan duration) + { + Type = type; + Name = name; + Offset = offset; + m_Duration = duration; + m_Added = DateTime.UtcNow; + } + + public StatType Type{ get; } + + public string Name{ get; } + + public int Offset{ get; } + + public bool HasElapsed() + { + if (m_Duration == TimeSpan.Zero) + return false; + + return DateTime.UtcNow - m_Added >= m_Duration; + } + } + + #endregion + + public class DamageEntry + { + public DamageEntry(Mobile damager) + { + Damager = damager; + } + + public Mobile Damager{ get; } + + public int DamageGiven{ get; set; } + + public DateTime LastDamage{ get; set; } + + public bool HasExpired => DateTime.UtcNow > LastDamage + ExpireDelay; + + public List Responsible{ get; set; } + + public static TimeSpan ExpireDelay{ get; set; } = TimeSpan.FromMinutes(2.0); + } + + #region Enums + + [Flags] + public enum StatType + { + Str = 1, + Dex = 2, + Int = 4, + All = 7 + } + + public enum StatLockType : byte + { + Up, + Down, + Locked + } + + [CustomEnum(new[] { "North", "Right", "East", "Down", "South", "Left", "West", "Up" })] + [Flags] + public enum Direction : byte + { + North = 0x0, + Right = 0x1, + East = 0x2, + Down = 0x3, + South = 0x4, + Left = 0x5, + West = 0x6, + Up = 0x7, + + Mask = 0x7, + Running = 0x80, + ValueMask = 0x87 + } + + [Flags] + public enum MobileDelta + { + None = 0x00000000, + Name = 0x00000001, + Flags = 0x00000002, + Hits = 0x00000004, + Mana = 0x00000008, + Stam = 0x00000010, + Stat = 0x00000020, + Noto = 0x00000040, + Gold = 0x00000080, + Weight = 0x00000100, + Direction = 0x00000200, + Hue = 0x00000400, + Body = 0x00000800, + Armor = 0x00001000, + StatCap = 0x00002000, + GhostUpdate = 0x00004000, + Followers = 0x00008000, + Properties = 0x00010000, + TithingPoints = 0x00020000, + Resistances = 0x00040000, + WeaponDamage = 0x00080000, + Hair = 0x00100000, + FacialHair = 0x00200000, + Race = 0x00400000, + HealthbarYellow = 0x00800000, + HealthbarPoison = 0x01000000, + + Attributes = 0x0000001C + } + + public enum AccessLevel + { + Player, + Counselor, + GameMaster, + Seer, + Administrator, + Developer, + Owner + } + + public enum VisibleDamageType + { + None, + Related, + Everyone, + Selective + } + + public enum ResistanceType + { + Physical, + Fire, + Cold, + Poison, + Energy + } + + public enum ApplyPoisonResult + { + Poisoned, + Immune, + HigherPoisonActive, + Cured + } + + #endregion + + [Serializable] + public class MobileNotConnectedException : Exception + { + public MobileNotConnectedException(Mobile source, string message) + : base(message) + { + Source = source.ToString(); + } + } + + #region Delegates + + public delegate bool SkillCheckTargetHandler(Mobile from, SkillName skill, object target, double minSkill, + double maxSkill); + + public delegate bool SkillCheckLocationHandler(Mobile from, SkillName skill, double minSkill, double maxSkill); + + public delegate bool SkillCheckDirectTargetHandler(Mobile from, SkillName skill, object target, double chance); + + public delegate bool SkillCheckDirectLocationHandler(Mobile from, SkillName skill, double chance); + + public delegate TimeSpan RegenRateHandler(Mobile from); + + public delegate bool AllowBeneficialHandler(Mobile from, Mobile target); + + public delegate bool AllowHarmfulHandler(Mobile from, Mobile target); + + public delegate Container CreateCorpseHandler(Mobile from, HairInfo hair, FacialHairInfo facialhair, + List initialContent, List equippedItems); + + public delegate int AOSStatusHandler(Mobile from, int index); + + #endregion + + /// + /// Base class representing players, npcs, and creatures. + /// + public class Mobile : IEntity, IHued, IComparable, ISerializable, ISpawnable + { + private const int + WarmodeCatchCount = 4; // Allow four warmode changes in 0.5 seconds, any more will be delay for two seconds + + private static readonly TimeSpan WarmodeSpamCatch = TimeSpan.FromSeconds(Core.SE ? 1.0 : 0.5); + private static readonly TimeSpan WarmodeSpamDelay = TimeSpan.FromSeconds(Core.SE ? 4.0 : 2.0); - for( int i = 0; i < m_Resistances.Length; ++i ) - { - if ( m_Resistances[i] != int.MinValue ) - { - m_Resistances[i] = int.MinValue; - delta = true; - } - } - if ( delta ) - Delta( MobileDelta.Resistances ); - } + private static Packet[][] m_MovingPacketCache = new Packet[2][] + { + new Packet[8], + new Packet[8] + }; - public virtual int GetResistance( ResistanceType type ) - { - if ( m_Resistances == null ) - m_Resistances = new int[5] { int.MinValue, int.MinValue, int.MinValue, int.MinValue, int.MinValue }; + private static List m_MoveList = new List(); + private static List m_MoveClientList = new List(); - int v = (int)type; + private static object m_GhostMutateContext = new object(); - if ( v < 0 || v >= m_Resistances.Length ) - return 0; + private static List m_Hears = new List(); + private static List m_OnSpeech = new List(); - int res = m_Resistances[v]; + public static bool m_DefaultShowVisibleDamage, m_DefaultCanSeeVisibleDamage; - if ( res == int.MinValue ) - { - ComputeResistances(); - res = m_Resistances[v]; - } + private static string[] m_AccessLevelNames = + { + "a player", + "a counselor", + "a game master", + "a seer", + "an administrator", + "a developer", + "an owner" + }; - return res; - } + private static int[] m_InvalidBodies = + { + 32, + 95, + 156, + 197, + 198 + }; - public List ResistanceMods - { - get => m_ResistMods; - set => m_ResistMods = value; - } - - public virtual void AddResistanceMod( ResistanceMod toAdd ) - { - if ( m_ResistMods == null ) { - m_ResistMods = new List(); - } - - m_ResistMods.Add( toAdd ); - UpdateResistances(); - } - - public virtual void RemoveResistanceMod( ResistanceMod toRemove ) - { - if ( m_ResistMods != null ) - { - m_ResistMods.Remove( toRemove ); - - if ( m_ResistMods.Count == 0 ) - m_ResistMods = null; - } - - UpdateResistances(); - } - - private static int m_MaxPlayerResistance = 70; - - public static int MaxPlayerResistance { get => m_MaxPlayerResistance; - set => m_MaxPlayerResistance = value; - } - - public virtual void ComputeResistances() - { - if ( m_Resistances == null ) - m_Resistances = new int[5] { int.MinValue, int.MinValue, int.MinValue, int.MinValue, int.MinValue }; - - for( int i = 0; i < m_Resistances.Length; ++i ) - m_Resistances[i] = 0; - - m_Resistances[0] += BasePhysicalResistance; - m_Resistances[1] += BaseFireResistance; - m_Resistances[2] += BaseColdResistance; - m_Resistances[3] += BasePoisonResistance; - m_Resistances[4] += BaseEnergyResistance; - - for( int i = 0; m_ResistMods != null && i < m_ResistMods.Count; ++i ) - { - ResistanceMod mod = m_ResistMods[i]; - int v = (int)mod.Type; - - if ( v >= 0 && v < m_Resistances.Length ) - m_Resistances[v] += mod.Offset; - } - - for( int i = 0; i < m_Items.Count; ++i ) - { - Item item = m_Items[i]; - - if ( item.CheckPropertyConfliction( this ) ) - continue; - - m_Resistances[0] += item.PhysicalResistance; - m_Resistances[1] += item.FireResistance; - m_Resistances[2] += item.ColdResistance; - m_Resistances[3] += item.PoisonResistance; - m_Resistances[4] += item.EnergyResistance; - } - - for( int i = 0; i < m_Resistances.Length; ++i ) - { - int min = GetMinResistance( (ResistanceType)i ); - int max = GetMaxResistance( (ResistanceType)i ); - - if ( max < min ) - max = min; - - if ( m_Resistances[i] > max ) - m_Resistances[i] = max; - else if ( m_Resistances[i] < min ) - m_Resistances[i] = min; - } - } - - public virtual int GetMinResistance( ResistanceType type ) - { - return int.MinValue; - } - - public virtual int GetMaxResistance( ResistanceType type ) - { - if ( m_Player ) - return m_MaxPlayerResistance; - - return int.MaxValue; - } - - public int GetAOSStatus( int index ) - { - return m_AOSStatusHandler?.Invoke( this, index ) ?? 0; - } - - public virtual void SendPropertiesTo( Mobile from ) - { - from.Send( PropertyList ); - } - - public virtual void OnAosSingleClick( Mobile from ) - { - ObjectPropertyList opl = PropertyList; - - if ( opl.Header > 0 ) - { - int hue; - - if ( m_NameHue != -1 ) - hue = m_NameHue; - else if ( m_AccessLevel > AccessLevel.Player ) - hue = 11; - else - hue = Notoriety.GetHue( Notoriety.Compute( from, this ) ); - - from.Send( new MessageLocalized( m_Serial, Body, MessageType.Label, hue, 3, opl.Header, Name, opl.HeaderArgs ) ); - } - } - - public virtual string ApplyNameSuffix( string suffix ) - { - return suffix; - } - - public virtual void AddNameProperties( ObjectPropertyList list ) - { - string name = Name; - - if ( name == null ) - name = String.Empty; - - string prefix = ""; - - if ( ShowFameTitle && (m_Player || m_Body.IsHuman) && m_Fame >= 10000 ) - prefix = m_Female ? "Lady" : "Lord"; - - string suffix = ""; - - if ( PropertyTitle && !string.IsNullOrEmpty(Title) ) - suffix = Title; - - BaseGuild guild = m_Guild; - - if ( guild != null && (m_Player || m_DisplayGuildTitle) ) - { - if ( suffix.Length > 0 ) - suffix = String.Format( "{0} [{1}]", suffix, Utility.FixHtml( guild.Abbreviation ) ); - else - suffix = String.Format( "[{0}]", Utility.FixHtml( guild.Abbreviation ) ); - } - - suffix = ApplyNameSuffix( suffix ); - - list.Add( 1050045, "{0} \t{1}\t {2}", prefix, name, suffix ); // ~1_PREFIX~~2_NAME~~3_SUFFIX~ - - if ( guild != null && (m_DisplayGuildTitle || (m_Player && guild.Type != GuildType.Regular)) ) - { - string type; - - if ( guild.Type >= 0 && (int)guild.Type < m_GuildTypes.Length ) - type = m_GuildTypes[(int)guild.Type]; - else - type = ""; - - string title = GuildTitle; - - if ( title == null ) - title = ""; - else - title = title.Trim(); - - if ( NewGuildDisplay && title.Length > 0 ) - { - list.Add( "{0}, {1}", Utility.FixHtml( title ), Utility.FixHtml( guild.Name ) ); - } - else - { - if ( title.Length > 0 ) - list.Add( "{0}, {1} Guild{2}", Utility.FixHtml( title ), Utility.FixHtml( guild.Name ), type ); - else - list.Add( Utility.FixHtml( guild.Name ) ); - } - } - } - - public virtual bool NewGuildDisplay => false; - - public virtual void GetProperties( ObjectPropertyList list ) - { - AddNameProperties( list ); - } - - public virtual void GetChildProperties( ObjectPropertyList list, Item item ) - { - } - - public virtual void GetChildNameProperties( ObjectPropertyList list, Item item ) - { - } - - private void UpdateAggrExpire() - { - if ( m_Deleted || (m_Aggressors.Count == 0 && m_Aggressed.Count == 0) ) - { - StopAggrExpire(); - } - else if ( m_ExpireAggrTimer == null ) - { - m_ExpireAggrTimer = new ExpireAggressorsTimer( this ); - m_ExpireAggrTimer.Start(); - } - } - - private void StopAggrExpire() - { - if ( m_ExpireAggrTimer != null ) - m_ExpireAggrTimer.Stop(); - - m_ExpireAggrTimer = null; - } - - private void CheckAggrExpire() - { - for( int i = m_Aggressors.Count - 1; i >= 0; --i ) - { - if ( i >= m_Aggressors.Count ) - continue; - - AggressorInfo info = m_Aggressors[i]; - - if ( info.Expired ) - { - Mobile attacker = info.Attacker; - attacker.RemoveAggressed( this ); - - m_Aggressors.RemoveAt( i ); - info.Free(); - - if ( m_NetState != null && CanSee( attacker ) && Utility.InUpdateRange( m_Location, attacker.m_Location ) ) { - m_NetState.Send(MobileIncoming.Create(m_NetState, this, attacker)); - } - } - } - - for( int i = m_Aggressed.Count - 1; i >= 0; --i ) - { - if ( i >= m_Aggressed.Count ) - continue; - - AggressorInfo info = m_Aggressed[i]; - - if ( info.Expired ) - { - Mobile defender = info.Defender; - defender.RemoveAggressor( this ); - - m_Aggressed.RemoveAt( i ); - info.Free(); - - if ( m_NetState != null && CanSee( defender ) && Utility.InUpdateRange( m_Location, defender.m_Location ) ) { - m_NetState.Send(MobileIncoming.Create(m_NetState, this, defender)); - } - } - } - - UpdateAggrExpire(); - } - - public List Stabled => m_Stabled; - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public VirtueInfo Virtues { get => m_Virtues; - set { } } - - public object Party { get => m_Party; - set => m_Party = value; - } - public List SkillMods => m_SkillMods; - - [CommandProperty( AccessLevel.GameMaster )] - public int VirtualArmorMod - { - get => m_VirtualArmorMod; - set - { - if ( m_VirtualArmorMod != value ) - { - m_VirtualArmorMod = value; - - Delta( MobileDelta.Armor ); - } - } - } - - /// - /// Overridable. Virtual event invoked when changes in some way. - /// - public virtual void OnSkillInvalidated( Skill skill ) - { - } - - public virtual void UpdateSkillMods() - { - ValidateSkillMods(); - - for( int i = 0; i < m_SkillMods.Count; ++i ) - { - SkillMod mod = m_SkillMods[i]; - Skill sk = m_Skills[mod.Skill]; - sk?.Update(); - } - } - - public virtual void ValidateSkillMods() - { - for( int i = 0; i < m_SkillMods.Count; ) - { - SkillMod mod = m_SkillMods[i]; - - if ( mod.CheckCondition() ) - ++i; - else - InternalRemoveSkillMod( mod ); - } - } - - public virtual void AddSkillMod( SkillMod mod ) - { - if ( mod == null ) - return; - - ValidateSkillMods(); - - if ( !m_SkillMods.Contains( mod ) ) - { - m_SkillMods.Add( mod ); - mod.Owner = this; - - Skill sk = m_Skills[mod.Skill]; - sk?.Update(); - } - } - - public virtual void RemoveSkillMod( SkillMod mod ) - { - if ( mod == null ) - return; - - ValidateSkillMods(); - - InternalRemoveSkillMod( mod ); - } - - private void InternalRemoveSkillMod( SkillMod mod ) - { - if ( m_SkillMods.Contains( mod ) ) - { - m_SkillMods.Remove( mod ); - mod.Owner = null; - - Skill sk = m_Skills[mod.Skill]; - sk?.Update(); - } - } - - private class WarmodeTimer : Timer - { - private Mobile m_Mobile; - private bool m_Value; - - public bool Value - { - get => m_Value; - set => m_Value = value; - } - - public WarmodeTimer( Mobile m, bool value ) - : base( WarmodeSpamDelay ) - { - m_Mobile = m; - m_Value = value; - } - - protected override void OnTick() - { - m_Mobile.Warmode = m_Value; - m_Mobile.m_WarmodeChanges = 0; - - m_Mobile.m_WarmodeTimer = null; - } - } - - /// - /// Overridable. Virtual event invoked when a client, , invokes a 'help request' for the Mobile. Seemingly no longer functional in newer clients. - /// - public virtual void OnHelpRequest( Mobile from ) - { - } - - public void DelayChangeWarmode( bool value ) - { - if ( m_WarmodeTimer != null ) - { - m_WarmodeTimer.Value = value; - return; - } - - if ( m_Warmode == value ) - return; - - DateTime now = DateTime.UtcNow, next = m_NextWarmodeChange; - - if ( now > next || m_WarmodeChanges == 0 ) - { - m_WarmodeChanges = 1; - m_NextWarmodeChange = now + WarmodeSpamCatch; - } - else if ( m_WarmodeChanges == WarmodeCatchCount ) - { - m_WarmodeTimer = new WarmodeTimer( this, value ); - m_WarmodeTimer.Start(); - - return; - } - else - { - ++m_WarmodeChanges; - } - - Warmode = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MeleeDamageAbsorb - { - get => m_MeleeDamageAbsorb; - set => m_MeleeDamageAbsorb = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int MagicDamageAbsorb - { - get => m_MagicDamageAbsorb; - set => m_MagicDamageAbsorb = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SkillsTotal => m_Skills?.Total ?? 0; - - [CommandProperty( AccessLevel.GameMaster )] - public int SkillsCap - { - get => m_Skills?.Cap ?? 0; - set - { - if ( m_Skills != null ) - m_Skills.Cap = value; - } - } - - public bool InLOS( Mobile target ) - { - if ( m_Deleted || m_Map == null ) - return false; - if ( target == this || m_AccessLevel > AccessLevel.Player ) - return true; - - return m_Map.LineOfSight( this, target ); - } - - public bool InLOS( object target ) - { - if ( m_Deleted || m_Map == null ) - return false; - if ( target == this || m_AccessLevel > AccessLevel.Player ) - return true; - if ( target is Item item && item.RootParent == this ) - return true; - - return m_Map.LineOfSight( this, target ); - } - - public bool InLOS( Point3D target ) - { - if ( m_Deleted || m_Map == null ) - return false; - if ( m_AccessLevel > AccessLevel.Player ) - return true; - - return m_Map.LineOfSight( this, target ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BaseSoundID - { - get => m_BaseSoundID; - set => m_BaseSoundID = value; - } - - public long NextCombatTime - { - get => m_NextCombatTime; - set => m_NextCombatTime = value; - } - - public bool BeginAction( object toLock ) - { - if ( _actions == null ) { - _actions = new List(); - - _actions.Add( toLock ); - - return true; - } - - if ( !_actions.Contains( toLock ) ) { - _actions.Add( toLock ); - - return true; - } - - return false; - } - - public bool CanBeginAction( object toLock ) - { - return ( _actions == null || !_actions.Contains( toLock ) ); - } - - public void EndAction( object toLock ) - { - if ( _actions != null ) { - _actions.Remove( toLock ); - - if ( _actions.Count == 0 ) { - _actions = null; - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int NameHue - { - get => m_NameHue; - set => m_NameHue = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Hunger - { - get => m_Hunger; - set - { - int oldValue = m_Hunger; - - if ( oldValue != value ) - { - m_Hunger = value; - - EventSink.InvokeHungerChanged( new HungerChangedEventArgs( this, oldValue ) ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Thirst - { - get => m_Thirst; - set => m_Thirst = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int BAC - { - get => m_BAC; - set => m_BAC = value; - } - - private long m_LastMoveTime; - - /// - /// Gets or sets the number of steps this player may take when hidden before being revealed. - /// - [CommandProperty( AccessLevel.GameMaster )] - public int AllowedStealthSteps - { - get => m_AllowedStealthSteps; - set => m_AllowedStealthSteps = value; - } - - /* Logout: - * - * When a client logs into mobile x - * - if ( x is Internalized ) move x to logout location and map - * - * When a client attached to a mobile disconnects - * - LogoutTimer is started - * - Delay is taken from Region.GetLogoutDelay to allow insta-logout regions. - * - OnTick : Location and map are stored, and mobile is internalized - * - * Some things to consider: - * - An internalized person getting killed (say, by poison). Where does the body go? - * - Regions now have a GetLogoutDelay( Mobile m ); virtual function (see above) - */ - private Point3D m_LogoutLocation; - private Map m_LogoutMap; - - public virtual TimeSpan GetLogoutDelay() - { - return Region.GetLogoutDelay( this ); - } - - private StatLockType m_StrLock, m_DexLock, m_IntLock; - - private Item m_Holding; - - public Item Holding - { - get => m_Holding; - set - { - if ( m_Holding != value ) - { - if ( m_Holding != null ) - { - UpdateTotal( m_Holding, TotalType.Weight, -(m_Holding.TotalWeight + m_Holding.PileWeight) ); - - if ( m_Holding.HeldBy == this ) - m_Holding.HeldBy = null; - } - - if ( value != null && m_Holding != null ) - DropHolding(); - - m_Holding = value; - - if ( m_Holding != null ) - { - UpdateTotal( m_Holding, TotalType.Weight, m_Holding.TotalWeight + m_Holding.PileWeight ); - - if ( m_Holding.HeldBy == null ) - m_Holding.HeldBy = this; - } - } - } - } - - public long LastMoveTime - { - get => m_LastMoveTime; - set => m_LastMoveTime = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual bool Paralyzed - { - get => m_Paralyzed; - set - { - if ( m_Paralyzed != value ) - { - m_Paralyzed = value; - Delta( MobileDelta.Flags ); - - SendLocalizedMessage( m_Paralyzed ? 502381 : 502382 ); - - if ( m_ParaTimer != null ) - { - m_ParaTimer.Stop(); - m_ParaTimer = null; - } - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool DisarmReady - { - get => m_DisarmReady; - set => m_DisarmReady = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool StunReady - { - get => m_StunReady; - set => m_StunReady = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Frozen - { - get => m_Frozen; - set - { - if ( m_Frozen != value ) - { - m_Frozen = value; - Delta( MobileDelta.Flags ); - - if ( m_FrozenTimer != null ) - { - m_FrozenTimer.Stop(); - m_FrozenTimer = null; - } - } - } - } - - public void Paralyze( TimeSpan duration ) - { - if ( !m_Paralyzed ) - { - Paralyzed = true; - - m_ParaTimer = new ParalyzedTimer( this, duration ); - m_ParaTimer.Start(); - } - } - - public void Freeze( TimeSpan duration ) - { - if ( !m_Frozen ) - { - Frozen = true; - - m_FrozenTimer = new FrozenTimer( this, duration ); - m_FrozenTimer.Start(); - } - } - - /// - /// Gets or sets the lock state for the property. - /// - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public StatLockType StrLock - { - get => m_StrLock; - set - { - if ( m_StrLock != value ) - { - m_StrLock = value; - - m_NetState?.Send( new StatLockInfo( this ) ); - } - } - } - - /// - /// Gets or sets the lock state for the property. - /// - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public StatLockType DexLock - { - get => m_DexLock; - set - { - if ( m_DexLock != value ) - { - m_DexLock = value; - - m_NetState?.Send( new StatLockInfo( this ) ); - } - } - } - - /// - /// Gets or sets the lock state for the property. - /// - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public StatLockType IntLock - { - get => m_IntLock; - set - { - if ( m_IntLock != value ) - { - m_IntLock = value; - - m_NetState?.Send( new StatLockInfo( this ) ); - } - } - } - - public override string ToString() - { - return String.Format( "0x{0:X} \"{1}\"", m_Serial.Value, Name ); - } - - public long NextActionTime - { - get => m_NextActionTime; - set => m_NextActionTime = value; - } - - public long NextActionMessage - { - get => m_NextActionMessage; - set => m_NextActionMessage = value; - } - - private static int m_ActionMessageDelay = 125; - - public static int ActionMessageDelay - { - get => m_ActionMessageDelay; - set => m_ActionMessageDelay = value; - } - - public virtual void SendSkillMessage() - { - if (m_NextActionMessage - Core.TickCount >= 0) - return; - - m_NextActionMessage = Core.TickCount + m_ActionMessageDelay; - - SendLocalizedMessage( 500118 ); // You must wait a few moments to use another skill. - } - - public virtual void SendActionMessage() - { - if (m_NextActionMessage - Core.TickCount >= 0) - return; - - m_NextActionMessage = Core.TickCount + m_ActionMessageDelay; - - SendLocalizedMessage( 500119 ); // You must wait to perform another action. - } - - public virtual void ClearHands() - { - ClearHand( FindItemOnLayer( Layer.OneHanded ) ); - ClearHand( FindItemOnLayer( Layer.TwoHanded ) ); - } - - public virtual void ClearHand( Item item ) - { - if ( item != null && item.Movable && !item.AllowEquippedCast( this ) ) - { - Container pack = Backpack; - - if ( pack == null ) - AddToBackpack( item ); - else - pack.DropItem( item ); - } - } - - - private static bool m_GlobalRegenThroughPoison = true; - - public static bool GlobalRegenThroughPoison - { - get => m_GlobalRegenThroughPoison; - set => m_GlobalRegenThroughPoison = value; - } - - public virtual bool RegenThroughPoison => m_GlobalRegenThroughPoison; - - public virtual bool CanRegenHits => Alive && (RegenThroughPoison || !Poisoned); - public virtual bool CanRegenStam => Alive; - public virtual bool CanRegenMana => Alive; - - #region Timers - - private class ManaTimer : Timer - { - private Mobile m_Owner; - - public ManaTimer( Mobile m ) - : base( GetManaRegenRate( m ), GetManaRegenRate( m ) ) - { - Priority = TimerPriority.FiftyMS; - m_Owner = m; - } - - protected override void OnTick() - { - if ( m_Owner.CanRegenMana )// m_Owner.Alive ) - m_Owner.Mana++; - - Delay = Interval = GetManaRegenRate( m_Owner ); - } - } - - private class HitsTimer : Timer - { - private Mobile m_Owner; - - public HitsTimer( Mobile m ) - : base( GetHitsRegenRate( m ), GetHitsRegenRate( m ) ) - { - Priority = TimerPriority.FiftyMS; - m_Owner = m; - } - - protected override void OnTick() - { - if ( m_Owner.CanRegenHits )// m_Owner.Alive && !m_Owner.Poisoned ) - m_Owner.Hits++; - - Delay = Interval = GetHitsRegenRate( m_Owner ); - } - } - - private class StamTimer : Timer - { - private Mobile m_Owner; - - public StamTimer( Mobile m ) - : base( GetStamRegenRate( m ), GetStamRegenRate( m ) ) - { - Priority = TimerPriority.FiftyMS; - m_Owner = m; - } - - protected override void OnTick() - { - if ( m_Owner.CanRegenStam )// m_Owner.Alive ) - m_Owner.Stam++; - - Delay = Interval = GetStamRegenRate( m_Owner ); - } - } - - private class LogoutTimer : Timer - { - private Mobile m_Mobile; - - public LogoutTimer( Mobile m ) - : base( TimeSpan.FromDays( 1.0 ) ) - { - Priority = TimerPriority.OneSecond; - m_Mobile = m; - } - - protected override void OnTick() - { - if ( m_Mobile.m_Map != Map.Internal ) - { - EventSink.InvokeLogout( new LogoutEventArgs( m_Mobile ) ); - - m_Mobile.m_LogoutLocation = m_Mobile.m_Location; - m_Mobile.m_LogoutMap = m_Mobile.m_Map; - - m_Mobile.Internalize(); - } - } - } - - private class ParalyzedTimer : Timer - { - private Mobile m_Mobile; - - public ParalyzedTimer( Mobile m, TimeSpan duration ) - : base( duration ) - { - Priority = TimerPriority.TwentyFiveMS; - m_Mobile = m; - } - - protected override void OnTick() - { - m_Mobile.Paralyzed = false; - } - } - - private class FrozenTimer : Timer - { - private Mobile m_Mobile; - - public FrozenTimer( Mobile m, TimeSpan duration ) - : base( duration ) - { - Priority = TimerPriority.TwentyFiveMS; - m_Mobile = m; - } - - protected override void OnTick() - { - m_Mobile.Frozen = false; - } - } - - private class CombatTimer : Timer - { - private Mobile m_Mobile; - - public CombatTimer( Mobile m ) - : base( TimeSpan.FromSeconds( 0.0 ), TimeSpan.FromSeconds( 0.01 ), 0 ) - { - m_Mobile = m; - - if ( !m_Mobile.m_Player && m_Mobile.m_Dex <= 100 ) - Priority = TimerPriority.FiftyMS; - } - - protected override void OnTick() - { - if (Core.TickCount - m_Mobile.m_NextCombatTime >= 0) - { - Mobile combatant = m_Mobile.Combatant; - - // If no combatant, wrong map, one of us is a ghost, or cannot see, or deleted, then stop combat - if ( combatant == null || combatant.m_Deleted || m_Mobile.m_Deleted || combatant.m_Map != m_Mobile.m_Map || !combatant.Alive || !m_Mobile.Alive || !m_Mobile.CanSee( combatant ) || combatant.IsDeadBondedPet || m_Mobile.IsDeadBondedPet ) - { - m_Mobile.Combatant = null; - return; - } - - IWeapon weapon = m_Mobile.Weapon; - - if ( !m_Mobile.InRange( combatant, weapon.MaxRange ) ) - return; - - if ( m_Mobile.InLOS( combatant ) ) - { - weapon.OnBeforeSwing( m_Mobile, combatant ); //OnBeforeSwing for checking in regards to being hidden and whatnot - m_Mobile.RevealingAction(); - m_Mobile.m_NextCombatTime = Core.TickCount + (int)weapon.OnSwing(m_Mobile, combatant).TotalMilliseconds; - } - } - } - } - - private class ExpireCombatantTimer : Timer - { - private Mobile m_Mobile; - - public ExpireCombatantTimer( Mobile m ) - : base( TimeSpan.FromMinutes( 1.0 ) ) - { - Priority = TimerPriority.FiveSeconds; - m_Mobile = m; - } - - protected override void OnTick() - { - m_Mobile.Combatant = null; - } - } - - private static TimeSpan m_ExpireCriminalDelay = TimeSpan.FromMinutes( 2.0 ); - - public static TimeSpan ExpireCriminalDelay - { - get => m_ExpireCriminalDelay; - set => m_ExpireCriminalDelay = value; - } - - private class ExpireCriminalTimer : Timer - { - private Mobile m_Mobile; - - public ExpireCriminalTimer( Mobile m ) - : base( m_ExpireCriminalDelay ) - { - Priority = TimerPriority.FiveSeconds; - m_Mobile = m; - } - - protected override void OnTick() - { - m_Mobile.Criminal = false; - } - } - - private class ExpireAggressorsTimer : Timer - { - private Mobile m_Mobile; - - public ExpireAggressorsTimer( Mobile m ) - : base( TimeSpan.FromSeconds( 5.0 ), TimeSpan.FromSeconds( 5.0 ) ) - { - m_Mobile = m; - Priority = TimerPriority.FiveSeconds; - } - - protected override void OnTick() - { - if ( m_Mobile.Deleted || (m_Mobile.Aggressors.Count == 0 && m_Mobile.Aggressed.Count == 0) ) - m_Mobile.StopAggrExpire(); - else - m_Mobile.CheckAggrExpire(); - } - } - - #endregion - - private long m_NextCombatTime; - - public long NextSkillTime - { - get => m_NextSkillTime; - set => m_NextSkillTime = value; - } - - public List Aggressors => m_Aggressors; - - public List Aggressed => m_Aggressed; - - private int m_ChangingCombatant; - - public bool ChangingCombatant => (m_ChangingCombatant > 0); - - public virtual void Attack( Mobile m ) - { - if ( CheckAttack( m ) ) - Combatant = m; - } - - public virtual bool CheckAttack( Mobile m ) - { - return (Utility.InUpdateRange( this, m ) && CanSee( m ) && InLOS( m )); - } - - /// - /// Overridable. Gets or sets which Mobile that this Mobile is currently engaged in combat with. - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual Mobile Combatant - { - get => m_Combatant; - set - { - if ( m_Deleted ) - return; - - if ( m_Combatant != value && value != this ) - { - Mobile old = m_Combatant; - - ++m_ChangingCombatant; - m_Combatant = value; - - if ( (m_Combatant != null && !CanBeHarmful( m_Combatant, false )) || !Region.OnCombatantChange( this, old, m_Combatant ) ) - { - m_Combatant = old; - --m_ChangingCombatant; - return; - } - - m_NetState?.Send( new ChangeCombatant( m_Combatant ) ); - - if ( m_Combatant == null ) - { - m_ExpireCombatant?.Stop(); - - m_CombatTimer?.Stop(); - - m_ExpireCombatant = null; - m_CombatTimer = null; - } - else - { - if ( m_ExpireCombatant == null ) - m_ExpireCombatant = new ExpireCombatantTimer( this ); - - m_ExpireCombatant.Start(); - - if ( m_CombatTimer == null ) - m_CombatTimer = new CombatTimer( this ); - - m_CombatTimer.Start(); - } - - if ( m_Combatant != null && CanBeHarmful( m_Combatant, false ) ) - { - DoHarmful( m_Combatant ); - - m_Combatant?.PlaySound( m_Combatant.GetAngerSound() ); - } + private static Queue m_DeltaQueue = new Queue(); + private static Queue m_DeltaQueueR = new Queue(); - OnCombatantChange(); - --m_ChangingCombatant; - } - } - } + private static bool _processing; - /// - /// Overridable. Virtual event invoked after the property has changed. - /// - /// - public virtual void OnCombatantChange() - { - } + private static string[] m_GuildTypes = + { + "", + " (Chaos)", + " (Order)" + }; - public double GetDistanceToSqrt( Point3D p ) - { - int xDelta = m_Location.m_X - p.m_X; - int yDelta = m_Location.m_Y - p.m_Y; + private Timer m_AutoManifestTimer; - return Math.Sqrt( (xDelta * xDelta) + (yDelta * yDelta) ); - } + private Container m_Backpack; - public double GetDistanceToSqrt( Mobile m ) - { - int xDelta = m_Location.m_X - m.m_Location.m_X; - int yDelta = m_Location.m_Y - m.m_Location.m_Y; + private BankBox m_BankBox; - return Math.Sqrt( (xDelta * xDelta) + (yDelta * yDelta) ); - } + private int m_ChangingCombatant; - public double GetDistanceToSqrt( IPoint2D p ) - { - int xDelta = m_Location.m_X - p.X; - int yDelta = m_Location.m_Y - p.Y; + private MobileDelta m_DeltaFlags; - return Math.Sqrt( (xDelta * xDelta) + (yDelta * yDelta) ); - } + private long m_EndQueue; - public virtual void AggressiveAction( Mobile aggressor ) - { - AggressiveAction( aggressor, false ); - } + private Item m_Holding; - public virtual void AggressiveAction( Mobile aggressor, bool criminal ) - { - if ( aggressor == this ) - return; + private int m_HueMod = -1; - AggressiveActionEventArgs args = AggressiveActionEventArgs.Create( this, aggressor, criminal ); + private bool m_InDeltaQueue; - EventSink.InvokeAggressiveAction( args ); + /* Logout: + * + * When a client logs into mobile x + * - if ( x is Internalized ) move x to logout location and map + * + * When a client attached to a mobile disconnects + * - LogoutTimer is started + * - Delay is taken from Region.GetLogoutDelay to allow insta-logout regions. + * - OnTick : Location and map are stored, and mobile is internalized + * + * Some things to consider: + * - An internalized person getting killed (say, by poison). Where does the body go? + * - Regions now have a GetLogoutDelay( Mobile m ); virtual function (see above) + */ - args.Free(); + private Item m_MountItem; - if ( Combatant == aggressor ) - { - if ( m_ExpireCombatant == null ) - m_ExpireCombatant = new ExpireCombatantTimer( this ); - else - m_ExpireCombatant.Stop(); + private string m_NameMod; - m_ExpireCombatant.Start(); - } + private Packet m_OPLPacket; - bool addAggressor = true; + private ObjectPropertyList m_PropertyList; - List list = m_Aggressors; + private QuestArrow m_QuestArrow; - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + private Packet m_RemovePacket; - if ( info.Attacker == aggressor ) - { - info.Refresh(); - info.CriminalAggression = criminal; - info.CanReportMurder = criminal; + private int m_SolidHueOverride = -1; - addAggressor = false; - } - } + private StatLockType m_StrLock, m_DexLock, m_IntLock; - list = aggressor.m_Aggressors; + internal int m_TypeRef; - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + private IWeapon m_Weapon; - if ( info.Attacker == this ) - { - info.Refresh(); + private bool m_YellowHealthbar; + private object oplLock = new object(); + private object rpLock = new object(); - addAggressor = false; - } - } + public Mobile(Serial serial) + { + m_Region = Map.Internal.DefaultRegion; + Serial = serial; + Aggressors = new List(); + Aggressed = new List(); + NextSkillTime = Core.TickCount; + DamageEntries = new List(); - bool addAggressed = true; + Type ourType = GetType(); + m_TypeRef = World.m_MobileTypes.IndexOf(ourType); - list = m_Aggressed; + if (m_TypeRef == -1) + { + World.m_MobileTypes.Add(ourType); + m_TypeRef = World.m_MobileTypes.Count - 1; + } + } - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + public Mobile() + { + m_Region = Map.Internal.DefaultRegion; + Serial = Serial.NewMobile; - if ( info.Defender == aggressor ) - { - info.Refresh(); + DefaultMobileInit(); - addAggressed = false; - } - } + World.AddMobile(this); - list = aggressor.m_Aggressed; + Type ourType = GetType(); + m_TypeRef = World.m_MobileTypes.IndexOf(ourType); - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; + if (m_TypeRef == -1) + { + World.m_MobileTypes.Add(ourType); + m_TypeRef = World.m_MobileTypes.Count - 1; + } + } - if ( info.Defender == this ) - { - info.Refresh(); - info.CriminalAggression = criminal; - info.CanReportMurder = criminal; + public static bool DragEffects{ get; set; } = true; - addAggressed = false; - } - } + [CommandProperty(AccessLevel.GameMaster)] + public Race Race + { + get + { + if (m_Race == null) + m_Race = Race.DefaultRace; - bool setCombatant = false; + return m_Race; + } + set + { + Race oldRace = Race; - if ( addAggressor ) - { - m_Aggressors.Add( AggressorInfo.Create( aggressor, this, criminal ) ); // new AggressorInfo( aggressor, this, criminal, true ) ); + m_Race = value; - if ( CanSee( aggressor ) ) { - m_NetState?.Send(MobileIncoming.Create(m_NetState, this, aggressor)); - } + if (m_Race == null) + m_Race = Race.DefaultRace; - if ( Combatant == null ) - setCombatant = true; + Body = m_Race.Body(this); + UpdateResistances(); - UpdateAggrExpire(); - } + Delta(MobileDelta.Race); - if ( addAggressed ) - { - aggressor.m_Aggressed.Add( AggressorInfo.Create( aggressor, this, criminal ) ); // new AggressorInfo( aggressor, this, criminal, false ) ); + OnRaceChange(oldRace); + } + } - if ( CanSee( aggressor ) ) { - m_NetState?.Send(MobileIncoming.Create(m_NetState, this, aggressor)); - } + public virtual double RacialSkillBonus => 0; - if ( Combatant == null ) - setCombatant = true; + public int[] Resistances{ get; private set; } - UpdateAggrExpire(); - } + public virtual int BasePhysicalResistance => 0; + public virtual int BaseFireResistance => 0; + public virtual int BaseColdResistance => 0; + public virtual int BasePoisonResistance => 0; + public virtual int BaseEnergyResistance => 0; - if ( setCombatant ) - Combatant = aggressor; + [CommandProperty(AccessLevel.Counselor)] + public virtual int PhysicalResistance => GetResistance(ResistanceType.Physical); - Region.OnAggressed( aggressor, this, criminal ); - } + [CommandProperty(AccessLevel.Counselor)] + public virtual int FireResistance => GetResistance(ResistanceType.Fire); - public void RemoveAggressed( Mobile aggressed ) - { - if ( m_Deleted ) - return; - - List list = m_Aggressed; - - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; - - if ( info.Defender == aggressed ) - { - m_Aggressed.RemoveAt( i ); - info.Free(); - - if ( m_NetState != null && CanSee( aggressed ) ) { - m_NetState.Send(MobileIncoming.Create(m_NetState, this, aggressed)); - } - - break; - } - } - - UpdateAggrExpire(); - } - - public void RemoveAggressor( Mobile aggressor ) - { - if ( m_Deleted ) - return; - - List list = m_Aggressors; - - for( int i = 0; i < list.Count; ++i ) - { - AggressorInfo info = list[i]; - - if ( info.Attacker == aggressor ) - { - m_Aggressors.RemoveAt( i ); - info.Free(); - - if ( m_NetState != null && CanSee( aggressor ) ) { - m_NetState.Send(MobileIncoming.Create(m_NetState, this, aggressor)); - } - - break; - } - } - - UpdateAggrExpire(); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int TotalGold => GetTotal( TotalType.Gold ); - - [CommandProperty( AccessLevel.GameMaster )] - public int TotalItems => GetTotal( TotalType.Items ); - - [CommandProperty( AccessLevel.GameMaster )] - public int TotalWeight => GetTotal( TotalType.Weight ); - - [CommandProperty( AccessLevel.GameMaster )] - public int TithingPoints - { - get => m_TithingPoints; - set - { - if ( m_TithingPoints != value ) - { - m_TithingPoints = value; - - Delta( MobileDelta.TithingPoints ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Followers - { - get => m_Followers; - set - { - if ( m_Followers != value ) - { - m_Followers = value; - - Delta( MobileDelta.Followers ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int FollowersMax - { - get => m_FollowersMax; - set - { - if ( m_FollowersMax != value ) - { - m_FollowersMax = value; - - Delta( MobileDelta.Followers ); - } - } - } - - public virtual int GetTotal( TotalType type ) - { - switch( type ) - { - case TotalType.Gold: - return m_TotalGold; - - case TotalType.Items: - return m_TotalItems; - - case TotalType.Weight: - return m_TotalWeight; - } - - return 0; - } - - public virtual void UpdateTotal( Item sender, TotalType type, int delta ) - { - if ( delta == 0 || sender.IsVirtualItem ) - return; - - switch( type ) - { - case TotalType.Gold: - m_TotalGold += delta; - Delta( MobileDelta.Gold ); - break; - - case TotalType.Items: - m_TotalItems += delta; - break; - - case TotalType.Weight: - m_TotalWeight += delta; - Delta( MobileDelta.Weight ); - OnWeightChange( m_TotalWeight - delta ); - break; - } - } - - public virtual void UpdateTotals() - { - if ( m_Items == null ) - return; - - int oldWeight = m_TotalWeight; - - m_TotalGold = 0; - m_TotalItems = 0; - m_TotalWeight = 0; - - for( int i = 0; i < m_Items.Count; ++i ) - { - Item item = m_Items[i]; - - item.UpdateTotals(); - - if ( item.IsVirtualItem ) - continue; - - m_TotalGold += item.TotalGold; - m_TotalItems += item.TotalItems + 1; - m_TotalWeight += item.TotalWeight + item.PileWeight; - } - - if ( m_Holding != null ) - m_TotalWeight += m_Holding.TotalWeight + m_Holding.PileWeight; - - if ( m_TotalWeight != oldWeight ) - OnWeightChange( oldWeight ); - } - - public void ClearQuestArrow() - { - m_QuestArrow = null; - } - - public void ClearTarget() - { - m_Target = null; - } - - private bool m_TargetLocked; - - public bool TargetLocked - { - get => m_TargetLocked; - set => m_TargetLocked = value; - } - - private class SimpleTarget : Target - { - private TargetCallback m_Callback; - - public SimpleTarget( int range, TargetFlags flags, bool allowGround, TargetCallback callback ) - : base( range, allowGround, flags ) - { - m_Callback = callback; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - m_Callback?.Invoke( from, targeted ); - } - } - - public Target BeginTarget( int range, bool allowGround, TargetFlags flags, TargetCallback callback ) - { - Target t = new SimpleTarget( range, flags, allowGround, callback ); - - Target = t; - - return t; - } - - private class SimpleStateTarget : Target - { - private TargetStateCallback m_Callback; - private object m_State; - - public SimpleStateTarget( int range, TargetFlags flags, bool allowGround, TargetStateCallback callback, object state ) - : base( range, allowGround, flags ) - { - m_Callback = callback; - m_State = state; - } - - protected override void OnTarget( Mobile from, object targeted ) - { - m_Callback?.Invoke( from, targeted, m_State ); - } - } - - public Target BeginTarget( int range, bool allowGround, TargetFlags flags, TargetStateCallback callback, object state ) - { - Target t = new SimpleStateTarget( range, flags, allowGround, callback, state ); - - Target = t; - - return t; - } - - private class SimpleStateTarget : Target - { - private TargetStateCallback m_Callback; - private T m_State; - - public SimpleStateTarget(int range, TargetFlags flags, bool allowGround, TargetStateCallback callback, T state) - : base(range, allowGround, flags) - { - m_Callback = callback; - m_State = state; - } - - protected override void OnTarget(Mobile from, object targeted) - { - m_Callback?.Invoke(from, targeted, m_State); - } - } - public Target BeginTarget(int range, bool allowGround, TargetFlags flags, TargetStateCallback callback, T state) - { - Target t = new SimpleStateTarget(range, flags, allowGround, callback, state); - - Target = t; - - return t; - } - - public Target Target - { - get => m_Target; - set - { - Target oldTarget = m_Target; - Target newTarget = value; - - if ( oldTarget == newTarget ) - return; - - m_Target = null; - - if ( oldTarget != null && newTarget != null ) - oldTarget.Cancel( this, TargetCancelType.Overridden ); - - m_Target = newTarget; - - if ( newTarget != null && m_NetState != null && !m_TargetLocked ) - m_NetState.Send( newTarget.GetPacketFor( m_NetState ) ); - - OnTargetChange(); - } - } - - /// - /// Overridable. Virtual event invoked after the Target property has changed. - /// - protected virtual void OnTargetChange() - { - } - - public ContextMenu ContextMenu - { - get => m_ContextMenu; - set - { - m_ContextMenu = value; - - if ( m_ContextMenu != null && m_NetState != null ) - { - // Old packet is preferred until assistants catch up - if ( m_NetState.NewHaven && m_ContextMenu.RequiresNewPacket ) - Send( new DisplayContextMenu( m_ContextMenu ) ); - else - Send( new DisplayContextMenuOld( m_ContextMenu ) ); - } - } - } - - public virtual bool CheckContextMenuDisplay( IEntity target ) - { - return true; - } - - #region Prompts - private class SimplePrompt : Prompt - { - private PromptCallback m_Callback; - private PromptCallback m_CancelCallback; - private bool m_CallbackHandlesCancel; - - public SimplePrompt( PromptCallback callback, PromptCallback cancelCallback ) - { - m_Callback = callback; - m_CancelCallback = cancelCallback; - } - - public SimplePrompt( PromptCallback callback, bool callbackHandlesCancel ) - { - m_Callback = callback; - m_CallbackHandlesCancel = callbackHandlesCancel; - } - - public SimplePrompt( PromptCallback callback ) - : this( callback, false ) - { - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Callback != null ) - m_Callback( from, text ); - } - - public override void OnCancel( Mobile from ) - { - if ( m_CallbackHandlesCancel && m_Callback != null ) - m_Callback( from, "" ); - else if ( m_CancelCallback != null ) - m_CancelCallback( from, "" ); - } - } - public Prompt BeginPrompt( PromptCallback callback, PromptCallback cancelCallback ) - { - Prompt p = new SimplePrompt( callback, cancelCallback ); - - Prompt = p; - return p; - } - public Prompt BeginPrompt( PromptCallback callback, bool callbackHandlesCancel ) - { - Prompt p = new SimplePrompt( callback, callbackHandlesCancel ); - - Prompt = p; - return p; - } - public Prompt BeginPrompt( PromptCallback callback ) - { - return BeginPrompt( callback, false ); - } - - private class SimpleStatePrompt : Prompt - { - private PromptStateCallback m_Callback; - private PromptStateCallback m_CancelCallback; - - private bool m_CallbackHandlesCancel; - - private object m_State; - - public SimpleStatePrompt( PromptStateCallback callback, PromptStateCallback cancelCallback, object state ) - { - m_Callback = callback; - m_CancelCallback = cancelCallback; - m_State = state; - } - public SimpleStatePrompt( PromptStateCallback callback, bool callbackHandlesCancel, object state ) - { - m_Callback = callback; - m_State = state; - m_CallbackHandlesCancel = callbackHandlesCancel; - } - public SimpleStatePrompt( PromptStateCallback callback, object state ) - : this( callback, false, state ) - { - } - - public override void OnResponse( Mobile from, string text ) - { - if ( m_Callback != null ) - m_Callback( from, text, m_State ); - } - - public override void OnCancel( Mobile from ) - { - if ( m_CallbackHandlesCancel && m_Callback != null ) - m_Callback( from, "", m_State ); - else if ( m_CancelCallback != null ) - m_CancelCallback( from, "", m_State ); - } - } - public Prompt BeginPrompt( PromptStateCallback callback, PromptStateCallback cancelCallback, object state ) - { - Prompt p = new SimpleStatePrompt( callback, cancelCallback, state ); - - Prompt = p; - return p; - } - public Prompt BeginPrompt( PromptStateCallback callback, bool callbackHandlesCancel, object state ) - { - Prompt p = new SimpleStatePrompt( callback, callbackHandlesCancel, state ); - - Prompt = p; - return p; - } - public Prompt BeginPrompt( PromptStateCallback callback, object state ) - { - return BeginPrompt( callback, false, state ); - } - - private class SimpleStatePrompt : Prompt - { - private PromptStateCallback m_Callback; - private PromptStateCallback m_CancelCallback; - - private bool m_CallbackHandlesCancel; - - private T m_State; - - public SimpleStatePrompt(PromptStateCallback callback, PromptStateCallback cancelCallback, T state) - { - m_Callback = callback; - m_CancelCallback = cancelCallback; - m_State = state; - } - public SimpleStatePrompt(PromptStateCallback callback, bool callbackHandlesCancel, T state) - { - m_Callback = callback; - m_State = state; - m_CallbackHandlesCancel = callbackHandlesCancel; - } - public SimpleStatePrompt(PromptStateCallback callback, T state) - : this(callback, false, state) - { - } - - public override void OnResponse(Mobile from, string text) - { - if (m_Callback != null) - m_Callback(from, text, m_State); - } - - public override void OnCancel(Mobile from) - { - if (m_CallbackHandlesCancel && m_Callback != null) - m_Callback(from, "", m_State); - else if (m_CancelCallback != null) - m_CancelCallback(from, "", m_State); - } - } - public Prompt BeginPrompt(PromptStateCallback callback, PromptStateCallback cancelCallback, T state) - { - Prompt p = new SimpleStatePrompt(callback, cancelCallback, state); - - Prompt = p; - return p; - } - public Prompt BeginPrompt(PromptStateCallback callback, bool callbackHandlesCancel, T state) - { - Prompt p = new SimpleStatePrompt(callback, callbackHandlesCancel, state); - - Prompt = p; - return p; - } - public Prompt BeginPrompt(PromptStateCallback callback, T state) - { - return BeginPrompt(callback, false, state); - } - - public Prompt Prompt - { - get => m_Prompt; - set - { - Prompt oldPrompt = m_Prompt; - Prompt newPrompt = value; - - if ( oldPrompt == newPrompt ) - return; - - m_Prompt = null; - - if ( oldPrompt != null && newPrompt != null ) - oldPrompt.OnCancel( this ); - - m_Prompt = newPrompt; - - if ( newPrompt != null ) - Send( new UnicodePrompt( newPrompt ) ); - } - } - #endregion - - private bool InternalOnMove( Direction d ) - { - if ( !OnMove( d ) ) - return false; - - MovementEventArgs e = MovementEventArgs.Create( this, d ); - - EventSink.InvokeMovement( e ); - - bool ret = !e.Blocked; - - e.Free(); - - return ret; - } - - /// - /// Overridable. Event invoked before the Mobile moves. - /// - /// True if the move is allowed, false if not. - protected virtual bool OnMove( Direction d ) - { - if ( m_Hidden && m_AccessLevel == AccessLevel.Player ) - { - if ( m_AllowedStealthSteps-- <= 0 || (d & Direction.Running) != 0 || Mounted ) - RevealingAction(); - } - - return true; - } - - private static Packet[][] m_MovingPacketCache = new Packet[2][] - { - new Packet[8], - new Packet[8] - }; - - private bool m_Pushing; - - public bool Pushing - { - get => m_Pushing; - set => m_Pushing = value; - } - - private static int m_WalkFoot = 400; - private static int m_RunFoot = 200; - private static int m_WalkMount = 200; - private static int m_RunMount = 100; - - public static int WalkFoot { get => m_WalkFoot; - set => m_WalkFoot = value; - } - public static int RunFoot { get => m_RunFoot; - set => m_RunFoot = value; - } - public static int WalkMount { get => m_WalkMount; - set => m_WalkMount = value; - } - public static int RunMount { get => m_RunMount; - set => m_RunMount = value; - } - - private long m_EndQueue; - - private static List m_MoveList = new List(); - private static List m_MoveClientList = new List(); - - private static AccessLevel m_FwdAccessOverride = AccessLevel.Counselor; - private static bool m_FwdEnabled = true; - private static bool m_FwdUOTDOverride = false; - private static int m_FwdMaxSteps = 4; - - public static AccessLevel FwdAccessOverride { get => m_FwdAccessOverride; - set => m_FwdAccessOverride = value; - } - public static bool FwdEnabled { get => m_FwdEnabled; - set => m_FwdEnabled = value; - } - public static bool FwdUOTDOverride { get => m_FwdUOTDOverride; - set => m_FwdUOTDOverride = value; - } - public static int FwdMaxSteps { get => m_FwdMaxSteps; - set => m_FwdMaxSteps = value; - } - - public virtual void ClearFastwalkStack() - { - if ( m_MoveRecords != null && m_MoveRecords.Count > 0 ) - m_MoveRecords.Clear(); - - m_EndQueue = Core.TickCount; - } - - public virtual bool CheckMovement( Direction d, out int newZ ) - { - return Movement.Movement.CheckMovement( this, d, out newZ ); - } - - public virtual bool Move( Direction d ) - { - if ( m_Deleted ) - return false; - - BankBox box = FindBankNoCreate(); - - if ( box != null && box.Opened ) - box.Close(); - - Point3D newLocation = m_Location; - Point3D oldLocation = newLocation; - - if ( (m_Direction & Direction.Mask) == (d & Direction.Mask) ) - { - // We are actually moving (not just a direction change) - - if ( m_Spell != null && !m_Spell.OnCasterMoving( d ) ) - return false; - - if ( m_Paralyzed || m_Frozen ) - { - SendLocalizedMessage( 500111 ); // You are frozen and can not move. - - return false; - } - - if ( CheckMovement( d, out int newZ ) ) - { - int x = oldLocation.m_X, y = oldLocation.m_Y; - int oldX = x, oldY = y; - int oldZ = oldLocation.m_Z; - - switch( d & Direction.Mask ) - { - case Direction.North: - --y; - break; - case Direction.Right: - ++x; - --y; - break; - case Direction.East: - ++x; - break; - case Direction.Down: - ++x; - ++y; - break; - case Direction.South: - ++y; - break; - case Direction.Left: - --x; - ++y; - break; - case Direction.West: - --x; - break; - case Direction.Up: - --x; - --y; - break; - } - - newLocation.m_X = x; - newLocation.m_Y = y; - newLocation.m_Z = newZ; - - m_Pushing = false; - - Map map = m_Map; - - if ( map != null ) - { - Sector oldSector = map.GetSector( oldX, oldY ); - Sector newSector = map.GetSector( x, y ); - - if ( oldSector != newSector ) - { - for( int i = 0; i < oldSector.Mobiles.Count; ++i ) - { - Mobile m = oldSector.Mobiles[i]; - - if ( m != this && m.X == oldX && m.Y == oldY && (m.Z + 15) > oldZ && (oldZ + 15) > m.Z && !m.OnMoveOff( this ) ) - return false; - } - - for( int i = 0; i < oldSector.Items.Count; ++i ) - { - Item item = oldSector.Items[i]; - - if ( item.AtWorldPoint( oldX, oldY ) && (item.Z == oldZ || ((item.Z + item.ItemData.Height) > oldZ && (oldZ + 15) > item.Z)) && !item.OnMoveOff( this ) ) - return false; - } - - for( int i = 0; i < newSector.Mobiles.Count; ++i ) - { - Mobile m = newSector.Mobiles[i]; - - if ( m.X == x && m.Y == y && (m.Z + 15) > newZ && (newZ + 15) > m.Z && !m.OnMoveOver( this ) ) - return false; - } - - for( int i = 0; i < newSector.Items.Count; ++i ) - { - Item item = newSector.Items[i]; - - if ( item.AtWorldPoint( x, y ) && (item.Z == newZ || ((item.Z + item.ItemData.Height) > newZ && (newZ + 15) > item.Z)) && !item.OnMoveOver( this ) ) - return false; - } - } - else - { - for( int i = 0; i < oldSector.Mobiles.Count; ++i ) - { - Mobile m = oldSector.Mobiles[i]; - - if ( m != this && m.X == oldX && m.Y == oldY && (m.Z + 15) > oldZ && (oldZ + 15) > m.Z && !m.OnMoveOff( this ) ) - return false; - if ( m.X == x && m.Y == y && (m.Z + 15) > newZ && (newZ + 15) > m.Z && !m.OnMoveOver( this ) ) - return false; - } - - for( int i = 0; i < oldSector.Items.Count; ++i ) - { - Item item = oldSector.Items[i]; - - if ( item.AtWorldPoint( oldX, oldY ) && (item.Z == oldZ || ((item.Z + item.ItemData.Height) > oldZ && (oldZ + 15) > item.Z)) && !item.OnMoveOff( this ) ) - return false; - if ( item.AtWorldPoint( x, y ) && (item.Z == newZ || ((item.Z + item.ItemData.Height) > newZ && (newZ + 15) > item.Z)) && !item.OnMoveOver( this ) ) - return false; - } - } - - if ( !Region.CanMove( this, d, newLocation, oldLocation, m_Map ) ) - return false; - } - else - { - return false; - } - - if ( !InternalOnMove( d ) ) - return false; - - if ( m_FwdEnabled && m_NetState != null && m_AccessLevel < m_FwdAccessOverride && (!m_FwdUOTDOverride || !m_NetState.IsUOTDClient) ) - { - if ( m_MoveRecords == null ) - m_MoveRecords = new Queue( 6 ); - - while( m_MoveRecords.Count > 0 ) - { - MovementRecord r = m_MoveRecords.Peek(); - - if ( r.Expired() ) - m_MoveRecords.Dequeue(); - else - break; - } - - if ( m_MoveRecords.Count >= m_FwdMaxSteps ) - { - FastWalkEventArgs fw = new FastWalkEventArgs( m_NetState ); - EventSink.InvokeFastWalk( fw ); - - if ( fw.Blocked ) - return false; - } - - int delay = ComputeMovementSpeed( d ); - - long end; - - if ( m_MoveRecords.Count > 0 ) - end = m_EndQueue + delay; - else - end = Core.TickCount + delay; - - m_MoveRecords.Enqueue( MovementRecord.NewInstance( end ) ); - - m_EndQueue = end; - } - - m_LastMoveTime = Core.TickCount; - } - else - { - return false; - } - - DisruptiveAction(); - } - - m_NetState?.Send( MovementAck.Instantiate( m_NetState.Sequence, this ) );//new MovementAck( m_NetState.Sequence, this ) ); - - SetLocation( newLocation, false ); - SetDirection( d ); - - if ( m_Map != null ) - { - IPooledEnumerable eable = m_Map.GetObjectsInRange( m_Location, Core.GlobalMaxUpdateRange ); - - foreach(IEntity o in eable) { - if (o == this) - continue; - - if (o is Mobile mob) { - if (mob.NetState != null) - m_MoveClientList.Add(mob); - m_MoveList.Add(mob); - } else if (o is Item item && item.HandlesOnMovement) { - m_MoveList.Add(item); - } - } - - eable.Free(); - - Packet[][] cache = m_MovingPacketCache; - - /*for( int i = 0; i < cache.Length; ++i ) - for( int j = 0; j < cache[i].Length; ++j ) - Packet.Release( ref cache[i][j] );*/ - - foreach(Mobile m in m_MoveClientList) { - NetState ns = m.NetState; - - if (ns != null && Utility.InUpdateRange(m_Location, m.m_Location) && m.CanSee(this)) { - if (ns.StygianAbyss) { - Packet p; - int noto = Notoriety.Compute(m, this); - p = cache[0][noto]; - - if (p == null) - cache[0][noto] = p = Packet.Acquire(new MobileMoving(this, noto)); - - ns.Send(p); - } else { - Packet p; - int noto = Notoriety.Compute(m, this); - p = cache[1][noto]; - - if (p == null) - cache[1][noto] = p = Packet.Acquire(new MobileMovingOld(this, noto)); - - ns.Send(p); - } - } - } - - for (int i = 0; i < cache.Length; ++i) - for (int j = 0; j < cache[i].Length; ++j) - Packet.Release(ref cache[i][j]); - - for( int i = 0; i < m_MoveList.Count; ++i ) { - IEntity o = m_MoveList[i]; - - if (o is Mobile mobile) { - mobile.OnMovement( this, oldLocation ); - } else if ( o is Item item ) { - item.OnMovement( this, oldLocation ); - } - } - - if (m_MoveList.Count > 0) - m_MoveList.Clear(); - - if (m_MoveClientList.Count > 0) - m_MoveClientList.Clear(); - } - - OnAfterMove( oldLocation ); - return true; - } - - public virtual void OnAfterMove( Point3D oldLocation ) - { - } - - public int ComputeMovementSpeed() - { - return ComputeMovementSpeed( Direction, false ); - } - - public int ComputeMovementSpeed( Direction dir ) - { - return ComputeMovementSpeed( dir, true ); - } - - public virtual int ComputeMovementSpeed( Direction dir, bool checkTurning ) - { - int delay; - - if ( Mounted ) - delay = (dir & Direction.Running) != 0 ? m_RunMount : m_WalkMount; - else - delay = (dir & Direction.Running) != 0 ? m_RunFoot : m_WalkFoot; - - return delay; - } - - /// - /// Overridable. Virtual event invoked when a Mobile moves off this Mobile. - /// - /// True if the move is allowed, false if not. - public virtual bool OnMoveOff( Mobile m ) - { - return true; - } - - public virtual bool IsDeadBondedPet => false; - - /// - /// Overridable. Event invoked when a Mobile moves over this Mobile. - /// - /// True if the move is allowed, false if not. - public virtual bool OnMoveOver( Mobile m ) - { - if ( m_Map == null || m_Deleted ) - return true; - - return m.CheckShove( this ); - } - - public virtual bool CheckShove( Mobile shoved ) - { - if ( (m_Map.Rules & MapRules.FreeMovement) == 0 ) - { - if ( !shoved.Alive || !Alive || shoved.IsDeadBondedPet || IsDeadBondedPet ) - return true; - if ( shoved.m_Hidden && shoved.m_AccessLevel > AccessLevel.Player ) - return true; - - if ( !m_Pushing ) - { - m_Pushing = true; - - int number; - - if ( AccessLevel > AccessLevel.Player ) - { - number = shoved.m_Hidden ? 1019041 : 1019040; - } - else - { - if ( Stam == StamMax ) - { - number = shoved.m_Hidden ? 1019043 : 1019042; - Stam -= 10; - - RevealingAction(); - } - else - { - return false; - } - } - - SendLocalizedMessage( number ); - } - } - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile sees another Mobile, , move. - /// - public virtual void OnMovement( Mobile m, Point3D oldLocation ) - { - } - - public ISpell Spell - { - get => m_Spell; - set - { - if ( m_Spell != null && value != null ) - Console.WriteLine( "Warning: Spell has been overwritten" ); - - m_Spell = value; - } - } - - [CommandProperty( AccessLevel.Administrator )] - public bool AutoPageNotify - { - get => m_AutoPageNotify; - set => m_AutoPageNotify = value; - } - - public virtual void CriminalAction( bool message ) - { - if ( m_Deleted ) - return; - - Criminal = true; - - Region.OnCriminalAction( this, message ); - } - - public virtual bool IsSnoop( Mobile from ) - { - return (from != this); - } - - /// - /// Overridable. Any call to will silently fail if this method returns false. - /// - /// - public virtual bool CheckResurrect() - { - return true; - } - - /// - /// Overridable. Event invoked before the Mobile is resurrected. - /// - /// - public virtual void OnBeforeResurrect() - { - } - - /// - /// Overridable. Event invoked after the Mobile is resurrected. - /// - /// - public virtual void OnAfterResurrect() - { - } - - public virtual void Resurrect() - { - if ( !Alive ) - { - if ( !Region.OnResurrect( this ) ) - return; - - if ( !CheckResurrect() ) - return; - - OnBeforeResurrect(); - - BankBox box = FindBankNoCreate(); - - if ( box != null && box.Opened ) - box.Close(); - - Poison = null; - - Warmode = false; - - Hits = 10; - Stam = StamMax; - Mana = 0; - - BodyMod = 0; - Body = Race.AliveBody( this ); - - ProcessDeltaQueue(); - - for( int i = m_Items.Count - 1; i >= 0; --i ) - { - if ( i >= m_Items.Count ) - continue; - - Item item = m_Items[i]; + [CommandProperty(AccessLevel.Counselor)] + public virtual int ColdResistance => GetResistance(ResistanceType.Cold); - if ( item.ItemID == 0x204E ) - item.Delete(); - } + [CommandProperty(AccessLevel.Counselor)] + public virtual int PoisonResistance => GetResistance(ResistanceType.Poison); - SendIncomingPacket(); - SendIncomingPacket(); + [CommandProperty(AccessLevel.Counselor)] + public virtual int EnergyResistance => GetResistance(ResistanceType.Energy); + + public List ResistanceMods{ get; set; } + + public static int MaxPlayerResistance{ get; set; } = 70; + + public virtual bool NewGuildDisplay => false; + + public List Stabled{ get; private set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public VirtueInfo Virtues + { + get => m_Virtues; + set { } + } - OnAfterResurrect(); + public object Party{ get; set; } - //Send( new DeathStatus( false ) ); - } - } + public List SkillMods{ get; private set; } - private IAccount m_Account; + [CommandProperty(AccessLevel.GameMaster)] + public int VirtualArmorMod + { + get => m_VirtualArmorMod; + set + { + if (m_VirtualArmorMod != value) + { + m_VirtualArmorMod = value; - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Owner )] - public IAccount Account - { - get => m_Account; - set => m_Account = value; - } + Delta(MobileDelta.Armor); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int MeleeDamageAbsorb{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int MagicDamageAbsorb{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int SkillsTotal => m_Skills?.Total ?? 0; + + [CommandProperty(AccessLevel.GameMaster)] + public int SkillsCap + { + get => m_Skills?.Cap ?? 0; + set + { + if (m_Skills != null) + m_Skills.Cap = value; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int BaseSoundID{ get; set; } + + public long NextCombatTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int NameHue{ get; set; } = -1; + + [CommandProperty(AccessLevel.GameMaster)] + public int Hunger + { + get => m_Hunger; + set + { + int oldValue = m_Hunger; + + if (oldValue != value) + { + m_Hunger = value; + + EventSink.InvokeHungerChanged(new HungerChangedEventArgs(this, oldValue)); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Thirst{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int BAC{ get; set; } + + /// + /// Gets or sets the number of steps this player may take when hidden before being revealed. + /// + [CommandProperty(AccessLevel.GameMaster)] + public int AllowedStealthSteps{ get; set; } + + public Item Holding + { + get => m_Holding; + set + { + if (m_Holding != value) + { + if (m_Holding != null) + { + UpdateTotal(m_Holding, TotalType.Weight, -(m_Holding.TotalWeight + m_Holding.PileWeight)); + + if (m_Holding.HeldBy == this) + m_Holding.HeldBy = null; + } + + if (value != null && m_Holding != null) + DropHolding(); + + m_Holding = value; + + if (m_Holding != null) + { + UpdateTotal(m_Holding, TotalType.Weight, m_Holding.TotalWeight + m_Holding.PileWeight); + + if (m_Holding.HeldBy == null) + m_Holding.HeldBy = this; + } + } + } + } + + public long LastMoveTime{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public virtual bool Paralyzed + { + get => m_Paralyzed; + set + { + if (m_Paralyzed != value) + { + m_Paralyzed = value; + Delta(MobileDelta.Flags); + + SendLocalizedMessage(m_Paralyzed ? 502381 : 502382); + + if (m_ParaTimer != null) + { + m_ParaTimer.Stop(); + m_ParaTimer = null; + } + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DisarmReady{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool StunReady{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Frozen + { + get => m_Frozen; + set + { + if (m_Frozen != value) + { + m_Frozen = value; + Delta(MobileDelta.Flags); + + if (m_FrozenTimer != null) + { + m_FrozenTimer.Stop(); + m_FrozenTimer = null; + } + } + } + } + + /// + /// Gets or sets the lock state for the property. + /// + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public StatLockType StrLock + { + get => m_StrLock; + set + { + if (m_StrLock != value) + { + m_StrLock = value; + + m_NetState?.Send(new StatLockInfo(this)); + } + } + } + + /// + /// Gets or sets the lock state for the property. + /// + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public StatLockType DexLock + { + get => m_DexLock; + set + { + if (m_DexLock != value) + { + m_DexLock = value; + + m_NetState?.Send(new StatLockInfo(this)); + } + } + } + + /// + /// Gets or sets the lock state for the property. + /// + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public StatLockType IntLock + { + get => m_IntLock; + set + { + if (m_IntLock != value) + { + m_IntLock = value; + + m_NetState?.Send(new StatLockInfo(this)); + } + } + } + + public long NextActionTime{ get; set; } + + public long NextActionMessage{ get; set; } + + public static int ActionMessageDelay{ get; set; } = 125; + + public static bool GlobalRegenThroughPoison{ get; set; } = true; + + public virtual bool RegenThroughPoison => GlobalRegenThroughPoison; + + public virtual bool CanRegenHits => Alive && (RegenThroughPoison || !Poisoned); + public virtual bool CanRegenStam => Alive; + public virtual bool CanRegenMana => Alive; + + public long NextSkillTime{ get; set; } + + public List Aggressors{ get; private set; } + + public List Aggressed{ get; private set; } + + public bool ChangingCombatant => m_ChangingCombatant > 0; + + /// + /// Overridable. Gets or sets which Mobile that this Mobile is currently engaged in combat with. + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual Mobile Combatant + { + get => m_Combatant; + set + { + if (Deleted) + return; + + if (m_Combatant != value && value != this) + { + Mobile old = m_Combatant; + + ++m_ChangingCombatant; + m_Combatant = value; + + if (m_Combatant != null && !CanBeHarmful(m_Combatant, false) || + !Region.OnCombatantChange(this, old, m_Combatant)) + { + m_Combatant = old; + --m_ChangingCombatant; + return; + } + + m_NetState?.Send(new ChangeCombatant(m_Combatant)); + + if (m_Combatant == null) + { + m_ExpireCombatant?.Stop(); + + m_CombatTimer?.Stop(); + + m_ExpireCombatant = null; + m_CombatTimer = null; + } + else + { + if (m_ExpireCombatant == null) + m_ExpireCombatant = new ExpireCombatantTimer(this); + + m_ExpireCombatant.Start(); + + if (m_CombatTimer == null) + m_CombatTimer = new CombatTimer(this); + + m_CombatTimer.Start(); + } + + if (m_Combatant != null && CanBeHarmful(m_Combatant, false)) + { + DoHarmful(m_Combatant); + + m_Combatant?.PlaySound(m_Combatant.GetAngerSound()); + } + + OnCombatantChange(); + --m_ChangingCombatant; + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int TotalGold => GetTotal(TotalType.Gold); + + [CommandProperty(AccessLevel.GameMaster)] + public int TotalItems => GetTotal(TotalType.Items); + + [CommandProperty(AccessLevel.GameMaster)] + public int TotalWeight => GetTotal(TotalType.Weight); + + [CommandProperty(AccessLevel.GameMaster)] + public int TithingPoints + { + get => m_TithingPoints; + set + { + if (m_TithingPoints != value) + { + m_TithingPoints = value; - private bool m_Deleted; + Delta(MobileDelta.TithingPoints); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Followers + { + get => m_Followers; + set + { + if (m_Followers != value) + { + m_Followers = value; + + Delta(MobileDelta.Followers); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int FollowersMax + { + get => m_FollowersMax; + set + { + if (m_FollowersMax != value) + { + m_FollowersMax = value; + + Delta(MobileDelta.Followers); + } + } + } + + public bool TargetLocked{ get; set; } + + public Target Target + { + get => m_Target; + set + { + Target oldTarget = m_Target; + Target newTarget = value; + + if (oldTarget == newTarget) + return; + + m_Target = null; + + if (oldTarget != null && newTarget != null) + oldTarget.Cancel(this, TargetCancelType.Overridden); + + m_Target = newTarget; + + if (newTarget != null && m_NetState != null && !TargetLocked) + m_NetState.Send(newTarget.GetPacketFor(m_NetState)); - public bool Deleted => m_Deleted; + OnTargetChange(); + } + } - [CommandProperty( AccessLevel.GameMaster )] - public int VirtualArmor - { - get => m_VirtualArmor; - set - { - if ( m_VirtualArmor != value ) - { - m_VirtualArmor = value; + public ContextMenu ContextMenu + { + get => m_ContextMenu; + set + { + m_ContextMenu = value; - Delta( MobileDelta.Armor ); - } - } - } + if (m_ContextMenu != null && m_NetState != null) + { + // Old packet is preferred until assistants catch up + if (m_NetState.NewHaven && m_ContextMenu.RequiresNewPacket) + Send(new DisplayContextMenu(m_ContextMenu)); + else + Send(new DisplayContextMenuOld(m_ContextMenu)); + } + } + } - [CommandProperty( AccessLevel.GameMaster )] - public virtual double ArmorRating => 0.0; + public bool Pushing{ get; set; } - public void DropHolding() - { - Item holding = m_Holding; + public static int WalkFoot{ get; set; } = 400; - if ( holding != null ) - { - if ( !holding.Deleted && holding.HeldBy == this && holding.Map == Map.Internal ) - AddToBackpack( holding ); + public static int RunFoot{ get; set; } = 200; - Holding = null; - holding.ClearBounce(); - } - } + public static int WalkMount{ get; set; } = 200; - public virtual void Delete() - { - if ( m_Deleted ) - return; + public static int RunMount{ get; set; } = 100; - if ( !World.OnDelete( this ) ) - return; + public static AccessLevel FwdAccessOverride{ get; set; } = AccessLevel.Counselor; - if (m_NetState != null) - { - m_NetState.CancelAllTrades(); - m_NetState.Dispose(); - } + public static bool FwdEnabled{ get; set; } = true; - DropHolding(); + public static bool FwdUOTDOverride{ get; set; } = false; - Region.OnRegionChange( this, m_Region, null ); + public static int FwdMaxSteps{ get; set; } = 4; - m_Region = null; - //Is the above line REALLY needed? The old Region system did NOT have said line - //and worked fine, because of this a LOT of extra checks have to be done everywhere... - //I guess this should be there for Garbage collection purposes, but, still, is it /really/ needed? + public virtual bool IsDeadBondedPet => false; - OnDelete(); + public ISpell Spell + { + get => m_Spell; + set + { + if (m_Spell != null && value != null) + Console.WriteLine("Warning: Spell has been overwritten"); - for( int i = m_Items.Count - 1; i >= 0; --i ) - if ( i < m_Items.Count ) - m_Items[i].OnParentDeleted( this ); + m_Spell = value; + } + } - for( int i = 0; i < m_Stabled.Count; i++ ) - m_Stabled[i].Delete(); + [CommandProperty(AccessLevel.Administrator)] + public bool AutoPageNotify{ get; set; } - SendRemovePacket(); + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Owner)] + public IAccount Account{ get; set; } - m_Guild?.OnDelete( this ); + [CommandProperty(AccessLevel.GameMaster)] + public int VirtualArmor + { + get => m_VirtualArmor; + set + { + if (m_VirtualArmor != value) + { + m_VirtualArmor = value; - m_Deleted = true; + Delta(MobileDelta.Armor); + } + } + } - m_Map?.OnLeave( this ); - m_Map = null; + [CommandProperty(AccessLevel.GameMaster)] + public virtual double ArmorRating => 0.0; - m_Hair = null; - m_FacialHair = null; - m_MountItem = null; + /// + /// Overridable. Returns true if the player is alive, false if otherwise. By default, this is computed by: + /// !Deleted && (!Player || !Body.IsGhost) + /// + [CommandProperty(AccessLevel.Counselor)] + public virtual bool Alive => !Deleted && (!m_Player || !m_Body.IsGhost); - World.RemoveMobile( this ); + public static CreateCorpseHandler CreateCorpseHandler{ get; set; } - OnAfterDelete(); + public virtual bool RetainPackLocsOnDeath => Core.AOS; - FreeCache(); - } + [CommandProperty(AccessLevel.GameMaster)] + public Container Corpse{ get; set; } - /// - /// Overridable. Virtual event invoked before the Mobile is deleted. - /// - public virtual void OnDelete() - { - m_Spawner?.Remove( this ); - m_Spawner = null; - } + public static char[] GhostChars{ get; set; } = new char[2] { 'o', 'O' }; - /// - /// Overridable. Returns true if the player is alive, false if otherwise. By default, this is computed by: !Deleted && (!Player || !Body.IsGhost) - /// - [CommandProperty( AccessLevel.Counselor )] - public virtual bool Alive => !m_Deleted && (!m_Player || !m_Body.IsGhost); + public static bool NoSpeechLOS{ get; set; } - public virtual bool CheckSpellCast( ISpell spell ) - { - return true; - } + public static TimeSpan AutoManifestTimeout{ get; set; } = TimeSpan.FromSeconds(5.0); - /// - /// Overridable. Virtual event invoked when the Mobile casts a . - /// - /// - public virtual void OnSpellCast( ISpell spell ) - { - } + public static bool InsuranceEnabled{ get; set; } - /// - /// Overridable. Virtual event invoked after changes. - /// - public virtual void OnWeightChange( int oldValue ) - { - } + public static int ActionDelay{ get; set; } = 500; - /// - /// Overridable. Virtual event invoked when the or property of changes. - /// - public virtual void OnSkillChange( SkillName skill, double oldBase ) - { - } + public static VisibleDamageType VisibleDamageType{ get; set; } - /// - /// Overridable. Invoked after the mobile is deleted. When overridden, be sure to call the base method. - /// - public virtual void OnAfterDelete() - { - StopAggrExpire(); + public List DamageEntries{ get; private set; } - CheckAggrExpire(); + [CommandProperty(AccessLevel.GameMaster)] + public Mobile LastKiller{ get; set; } - m_PoisonTimer?.Stop(); + public static bool DefaultShowVisibleDamage + { + get => m_DefaultShowVisibleDamage; + set => m_DefaultShowVisibleDamage = value; + } - m_HitsTimer?.Stop(); + public static bool DefaultCanSeeVisibleDamage + { + get => m_DefaultCanSeeVisibleDamage; + set => m_DefaultCanSeeVisibleDamage = value; + } - m_StamTimer?.Stop(); + public virtual bool ShowVisibleDamage => m_DefaultShowVisibleDamage; + public virtual bool CanSeeVisibleDamage => m_DefaultCanSeeVisibleDamage; - m_ManaTimer?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public bool Squelched{ get; set; } - m_CombatTimer?.Stop(); + public virtual bool ShouldCheckStatTimers => true; - m_ExpireCombatant?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public DateTime CreationTime{ get; private set; } - m_LogoutTimer?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public int LightLevel + { + get => m_LightLevel; + set + { + if (m_LightLevel != value) + { + m_LightLevel = value; + + CheckLightLevels(false); + + /*if ( m_NetState != null ) + m_NetState.Send( new PersonalLightLevel( this ) );*/ + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public string Profile{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public bool ProfileLocked{ get; set; } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Administrator)] + public bool Player + { + get => m_Player; + set + { + m_Player = value; + InvalidateProperties(); + + if (!m_Player && m_Dex <= 100 && m_CombatTimer != null) + m_CombatTimer.Priority = TimerPriority.FiftyMS; + else if (m_CombatTimer != null) + m_CombatTimer.Priority = TimerPriority.EveryTick; + + CheckStatTimers(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Title + { + get => m_Title; + set + { + m_Title = value; + InvalidateProperties(); + } + } + + public List Items{ get; private set; } + + public virtual int MaxWeight => int.MaxValue; + + public static IWeapon DefaultWeapon{ get; set; } + + [CommandProperty(AccessLevel.Counselor)] + public Skills Skills + { + get => m_Skills; + set { } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.Administrator)] + public AccessLevel AccessLevel + { + get => m_AccessLevel; + set + { + AccessLevel oldValue = m_AccessLevel; + + if (oldValue != value) + { + m_AccessLevel = value; + Delta(MobileDelta.Noto); + InvalidateProperties(); + + SendMessage("Your access level has been changed. You are now {0}.", GetAccessLevelName(value)); + + ClearScreen(); + SendEverything(); + + OnAccessLevelChanged(oldValue); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Fame + { + get => m_Fame; + set + { + int oldValue = m_Fame; + + if (oldValue != value) + { + m_Fame = value; + + if (ShowFameTitle && (m_Player || m_Body.IsHuman) && oldValue >= 10000 != value >= 10000) + InvalidateProperties(); + + OnFameChange(oldValue); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int Karma + { + get => m_Karma; + set + { + int old = m_Karma; + + if (old != value) + { + m_Karma = value; + OnKarmaChange(old); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Blessed + { + get => m_Blessed; + set + { + if (m_Blessed != value) + { + m_Blessed = value; + Delta(MobileDelta.HealthbarYellow); + } + } + } + + public virtual int Luck => 0; + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public int HueMod + { + get => m_HueMod; + set + { + if (m_HueMod != value) + { + m_HueMod = value; + + Delta(MobileDelta.Hue); + } + } + } + + [Hue] + [CommandProperty(AccessLevel.GameMaster)] + public virtual int Hue + { + get + { + if (m_HueMod != -1) + return m_HueMod; + + return m_Hue; + } + set + { + int oldHue = m_Hue; + + if (oldHue != value) + { + m_Hue = value; + + Delta(MobileDelta.Hue); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Direction Direction + { + get => m_Direction; + set + { + if (m_Direction != value) + { + m_Direction = value; + + Delta(MobileDelta.Direction); + //ProcessDelta(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Female + { + get => m_Female; + set + { + if (m_Female != value) + { + m_Female = value; + Delta(MobileDelta.Flags); + OnGenderChanged(!m_Female); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Flying + { + get => m_Flying; + set + { + if (m_Flying != value) + { + m_Flying = value; + Delta(MobileDelta.Flags); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Warmode + { + get => m_Warmode; + set + { + if (Deleted) + return; + + if (m_Warmode != value) + { + if (m_AutoManifestTimer != null) + { + m_AutoManifestTimer.Stop(); + m_AutoManifestTimer = null; + } + + m_Warmode = value; + Delta(MobileDelta.Flags); + + if (m_NetState != null) + Send(SetWarMode.Instantiate(value)); + + if (!m_Warmode) + Combatant = null; + + if (!Alive) + { + if (value) + Delta(MobileDelta.GhostUpdate); + else + SendRemovePacket(false); + } + + OnWarmodeChanged(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Hidden + { + get => m_Hidden; + set + { + if (m_Hidden != value) + { + m_Hidden = value; + //Delta( MobileDelta.Flags ); + + OnHiddenChanged(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster, AccessLevel.Owner)] + public NetState NetState + { + get + { + if (m_NetState != null && m_NetState.Socket == null && !m_NetState.IsDisposing) NetState = null; + + return m_NetState; + } + set + { + if (m_NetState != value) + { + m_Map?.OnClientChange(m_NetState, value, this); + + m_Target?.Cancel(this, TargetCancelType.Disconnected); + + if (m_QuestArrow != null) + QuestArrow = null; + + m_Spell?.OnConnectionChanged(); + + //if ( m_Spell != null ) + // m_Spell.FinishSequence(); + + m_NetState?.CancelAllTrades(); + + BankBox box = FindBankNoCreate(); + + if (box != null && box.Opened) + box.Close(); + + // REMOVED: + //m_Actions.Clear(); + + m_NetState = value; + + if (m_NetState == null) + { + OnDisconnected(); + EventSink.InvokeDisconnected(new DisconnectedEventArgs(this)); + + // Disconnected, start the logout timer + + if (m_LogoutTimer == null) + m_LogoutTimer = new LogoutTimer(this); + else + m_LogoutTimer.Stop(); + + m_LogoutTimer.Delay = GetLogoutDelay(); + m_LogoutTimer.Start(); + } + else + { + OnConnected(); + EventSink.InvokeConnected(new ConnectedEventArgs(this)); + + // Connected, stop the logout timer and if needed, move to the world + + m_LogoutTimer?.Stop(); + + m_LogoutTimer = null; + + if (m_Map == Map.Internal && LogoutMap != null) + { + Map = LogoutMap; + Location = LogoutLocation; + } + } + + for (int i = Items.Count - 1; i >= 0; --i) + { + if (i >= Items.Count) + continue; + + Item item = Items[i]; + + if (item is SecureTradeContainer) + { + for (int j = item.Items.Count - 1; j >= 0; --j) + if (j < item.Items.Count) + { + item.Items[j].OnSecureTrade(this, this, this, false); + AddToBackpack(item.Items[j]); + } + + Timer.DelayCall(TimeSpan.Zero, delegate { item.Delete(); }); + } + } + + DropHolding(); + OnNetStateChanged(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string Language + { + get => m_Language; + set + { + if (m_Language != value) + m_Language = value; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SpeechHue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int EmoteHue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int WhisperHue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public int YellHue{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string GuildTitle + { + get => m_GuildTitle; + set + { + string old = m_GuildTitle; + + if (old != value) + { + m_GuildTitle = value; + + if (m_Guild != null && !m_Guild.Disbanded && m_GuildTitle != null) + SendLocalizedMessage(1018026, true, m_GuildTitle); // Your guild title has changed : + + InvalidateProperties(); + + OnGuildTitleChange(old); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool DisplayGuildTitle + { + get => m_DisplayGuildTitle; + set + { + m_DisplayGuildTitle = value; + InvalidateProperties(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Mobile GuildFealty{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public string NameMod + { + get => m_NameMod; + set + { + if (m_NameMod != value) + { + m_NameMod = value; + Delta(MobileDelta.Name); + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool YellowHealthbar + { + get => m_YellowHealthbar; + set + { + m_YellowHealthbar = value; + Delta(MobileDelta.HealthbarYellow); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public string RawName + { + get => m_Name; + set => Name = value; + } + + [CommandProperty(AccessLevel.GameMaster)] + public virtual string Name + { + get + { + if (m_NameMod != null) + return m_NameMod; + + return m_Name; + } + set + { + if (m_Name != value) // I'm leaving out the && m_NameMod == null + { + string oldName = m_Name; + m_Name = value; + OnAfterNameChange(oldName, m_Name); + Delta(MobileDelta.Name); + InvalidateProperties(); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastStrGain{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastIntGain{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public DateTime LastDexGain{ get; set; } + + public DateTime LastStatGain + { + get + { + DateTime d = LastStrGain; + + if (LastIntGain > d) + d = LastIntGain; + + if (LastDexGain > d) + d = LastDexGain; + + return d; + } + set + { + LastStrGain = value; + LastIntGain = value; + LastDexGain = value; + } + } + + public BaseGuild Guild + { + get => m_Guild; + set + { + BaseGuild old = m_Guild; + + if (old != value) + { + if (value == null) + GuildTitle = null; + + m_Guild = value; + + Delta(MobileDelta.Noto); + InvalidateProperties(); + + OnGuildChange(old); + } + } + } + + public Region WalkRegion{ get; set; } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Poisoned => m_Poison != null; + + [CommandProperty(AccessLevel.GameMaster)] + public bool IsBodyMod => m_BodyMod.BodyID != 0; + + [CommandProperty(AccessLevel.GameMaster)] + public Body BodyMod + { + get => m_BodyMod; + set + { + if (m_BodyMod != value) + { + m_BodyMod = value; + + Delta(MobileDelta.Body); + InvalidateProperties(); + + CheckStatTimers(); + } + } + } + + [Body] + [CommandProperty(AccessLevel.GameMaster)] + public Body Body + { + get + { + if (IsBodyMod) + return m_BodyMod; + + return m_Body; + } + set + { + if (m_Body != value && !IsBodyMod) + { + m_Body = SafeBody(value); + + Delta(MobileDelta.Body); + InvalidateProperties(); + + CheckStatTimers(); + } + } + } + + [Body] + [CommandProperty(AccessLevel.GameMaster)] + public int BodyValue + { + get => Body.BodyID; + set => Body = value; + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Point3D LogoutLocation{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Map LogoutMap{ get; set; } + + public Region Region + { + get + { + if (m_Region == null) + if (Map == null) + return Map.Internal.DefaultRegion; + else + return Map.DefaultRegion; + return m_Region; + } + } + + public Packet RemovePacket + { + get + { + if (m_RemovePacket == null) + lock (rpLock) + { + if (m_RemovePacket == null) + { + m_RemovePacket = new RemoveMobile(this); + m_RemovePacket.SetStatic(); + } + } + + return m_RemovePacket; + } + } + + public Packet OPLPacket + { + get + { + if (m_OPLPacket == null) + lock (oplLock) + { + if (m_OPLPacket == null) + { + m_OPLPacket = new OPLInfo(PropertyList); + m_OPLPacket.SetStatic(); + } + } + + return m_OPLPacket; + } + } + + public ObjectPropertyList PropertyList + { + get + { + if (m_PropertyList == null) + { + m_PropertyList = new ObjectPropertyList(this); + + GetProperties(m_PropertyList); + + m_PropertyList.Terminate(); + m_PropertyList.SetStatic(); + } + + return m_PropertyList; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int SolidHueOverride + { + get => m_SolidHueOverride; + set + { + if (m_SolidHueOverride == value) return; + m_SolidHueOverride = value; + Delta(MobileDelta.Hue | MobileDelta.Body); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public virtual IWeapon Weapon + { + get + { + if (m_Weapon is Item item && !item.Deleted && item.Parent == this && CanSee(item)) + return m_Weapon; + + m_Weapon = null; + + item = FindItemOnLayer(Layer.OneHanded) ?? FindItemOnLayer(Layer.TwoHanded); + + if (item is IWeapon weapon) + return m_Weapon = weapon; + + return GetDefaultWeapon(); + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public BankBox BankBox + { + get + { + if (m_BankBox != null && !m_BankBox.Deleted && m_BankBox.Parent == this) + return m_BankBox; + + m_BankBox = FindItemOnLayer(Layer.Bank) as BankBox; + + if (m_BankBox == null) + AddItem(m_BankBox = new BankBox(this)); + + return m_BankBox; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public Container Backpack + { + get + { + if (m_Backpack != null && !m_Backpack.Deleted && m_Backpack.Parent == this) + return m_Backpack; + + return m_Backpack = FindItemOnLayer(Layer.Backpack) as Container; + } + } + + public virtual bool KeepsItemsOnDeath => m_AccessLevel > AccessLevel.Player; + + public bool HasTrade + { + get + { + if (m_NetState != null) + return m_NetState.Trades.Count > 0; + + return false; + } + } + + public bool NoMoveHS{ get; set; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Kills + { + get => m_Kills; + set + { + int oldValue = m_Kills; + + if (m_Kills != value) + { + m_Kills = value; + + if (m_Kills < 0) + m_Kills = 0; + + if (oldValue >= 5 != m_Kills >= 5) + { + Delta(MobileDelta.Noto); + InvalidateProperties(); + } + + OnKillsChange(oldValue); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int ShortTermMurders + { + get => m_ShortTermMurders; + set + { + if (m_ShortTermMurders != value) + { + m_ShortTermMurders = value; + + if (m_ShortTermMurders < 0) + m_ShortTermMurders = 0; + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public bool Criminal + { + get => m_Criminal; + set + { + if (m_Criminal != value) + { + m_Criminal = value; + Delta(MobileDelta.Noto); + InvalidateProperties(); + } + + if (m_Criminal) + { + if (m_ExpireCriminal == null) + m_ExpireCriminal = new ExpireCriminalTimer(this); + else + m_ExpireCriminal.Stop(); + + m_ExpireCriminal.Start(); + } + else if (m_ExpireCriminal != null) + { + m_ExpireCriminal.Stop(); + m_ExpireCriminal = null; + } + } + } + + public static bool DisableDismountInWarmode{ get; set; } + + public static int BodyWeight{ get; set; } = 14; + + [CommandProperty(AccessLevel.GameMaster)] + public IMount Mount + { + get + { + Item item = null; + + if (m_MountItem?.Deleted == false && m_MountItem.Parent == this) + item = m_MountItem; + + if (item == null) + item = FindItemOnLayer(Layer.Mount); + + if (!(item is IMountItem mountItem)) + return null; + + m_MountItem = item; + return mountItem.Mount; + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public bool Mounted => Mount != null; + + public QuestArrow QuestArrow + { + get => m_QuestArrow; + set + { + if (m_QuestArrow != value) + { + m_QuestArrow?.Stop(); + + m_QuestArrow = value; + } + } + } + + public virtual bool CanTarget => true; + public virtual bool ClickTitle => true; + + public virtual bool PropertyTitle => OldPropertyTitles ? ClickTitle : true; + + public static bool DisableHiddenSelfClick{ get; set; } = true; + + public static bool AsciiClickMessage{ get; set; } = true; + + public static bool GuildClickMessage{ get; set; } = true; + + public static bool OldPropertyTitles{ get; set; } + + public virtual bool ShowFameTitle //(m_Player || m_Body.IsHuman) && m_Fame >= 10000; } + => true; + + /// + /// Gets or sets the maximum attainable value for , , and . + /// + [CommandProperty(AccessLevel.GameMaster)] + public int StatCap + { + get => m_StatCap; + set + { + if (m_StatCap != value) + { + m_StatCap = value; - m_ExpireCriminal?.Stop(); + Delta(MobileDelta.StatCap); + } + } + } - m_WarmodeTimer?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public bool Meditating{ get; set; } - m_ParaTimer?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public bool CanSwim{ get; set; } - m_FrozenTimer?.Stop(); + [CommandProperty(AccessLevel.GameMaster)] + public bool CantWalk{ get; set; } - m_AutoManifestTimer?.Stop(); - } + [CommandProperty(AccessLevel.GameMaster)] + public bool CanHearGhosts + { + get => m_CanHearGhosts || AccessLevel >= AccessLevel.Counselor; + set => m_CanHearGhosts = value; + } - public virtual bool AllowSkillUse( SkillName name ) - { - return true; - } + [CommandProperty(AccessLevel.GameMaster)] + public int RawStatTotal => RawStr + RawDex + RawInt; - public virtual bool UseSkill( SkillName name ) - { - return Skills.UseSkill( this, name ); - } + public long NextSpellTime{ get; set; } - public virtual bool UseSkill( int skillID ) - { - return Skills.UseSkill( this, skillID ); - } + public bool Deleted{ get; private set; } - private static CreateCorpseHandler m_CreateCorpse; + public virtual void Delete() + { + if (Deleted) + return; - public static CreateCorpseHandler CreateCorpseHandler - { - get => m_CreateCorpse; - set => m_CreateCorpse = value; - } + if (!World.OnDelete(this)) + return; - public virtual DeathMoveResult GetParentMoveResultFor( Item item ) - { - return item.OnParentDeath( this ); - } + if (m_NetState != null) + { + m_NetState.CancelAllTrades(); + m_NetState.Dispose(); + } - public virtual DeathMoveResult GetInventoryMoveResultFor( Item item ) - { - return item.OnInventoryDeath( this ); - } + DropHolding(); - public virtual bool RetainPackLocsOnDeath => Core.AOS; + Region.OnRegionChange(this, m_Region, null); - public virtual void Kill() - { - if ( !CanBeDamaged() ) - return; - if ( !Alive || IsDeadBondedPet ) - return; - if ( m_Deleted ) - return; - if ( !Region.OnBeforeDeath( this ) ) - return; - if ( !OnBeforeDeath() ) - return; + m_Region = null; + //Is the above line REALLY needed? The old Region system did NOT have said line + //and worked fine, because of this a LOT of extra checks have to be done everywhere... + //I guess this should be there for Garbage collection purposes, but, still, is it /really/ needed? - BankBox box = FindBankNoCreate(); + OnDelete(); - if ( box != null && box.Opened ) - box.Close(); + for (int i = Items.Count - 1; i >= 0; --i) + if (i < Items.Count) + Items[i].OnParentDeleted(this); - m_NetState?.CancelAllTrades(); + for (int i = 0; i < Stabled.Count; i++) + Stabled[i].Delete(); - m_Spell?.OnCasterKilled(); - //m_Spell.Disturb( DisturbType.Kill ); + SendRemovePacket(); - m_Target?.Cancel( this, TargetCancelType.Canceled ); + m_Guild?.OnDelete(this); - DisruptiveAction(); + Deleted = true; - Warmode = false; + m_Map?.OnLeave(this); + m_Map = null; - DropHolding(); + m_Hair = null; + m_FacialHair = null; + m_MountItem = null; - Hits = 0; - Stam = 0; - Mana = 0; + World.RemoveMobile(this); - Poison = null; - Combatant = null; + OnAfterDelete(); - if ( Paralyzed ) - { - Paralyzed = false; + FreeCache(); + } - m_ParaTimer?.Stop(); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Map Map + { + get => m_Map; + set + { + if (Deleted) + return; + + if (m_Map != value) + { + m_NetState?.ValidateAllTrades(); - if ( Frozen ) - { - Frozen = false; + Map oldMap = m_Map; - m_FrozenTimer?.Stop(); - } + if (m_Map != null) + { + m_Map.OnLeave(this); - List content = new List(); - List equip = new List(); - List moveToPack = new List(); + ClearScreen(); + SendRemovePacket(); + } - List itemsCopy = new List( m_Items ); + for (int i = 0; i < Items.Count; ++i) + Items[i].Map = value; - Container pack = Backpack; + m_Map = value; - for( int i = 0; i < itemsCopy.Count; ++i ) - { - Item item = itemsCopy[i]; + UpdateRegion(); - if ( item == pack ) - continue; + m_Map?.OnEnter(this); - DeathMoveResult res = GetParentMoveResultFor( item ); + NetState ns = m_NetState; - switch( res ) - { - case DeathMoveResult.MoveToCorpse: - { - content.Add( item ); - equip.Add( item ); - break; - } - case DeathMoveResult.MoveToBackpack: - { - moveToPack.Add( item ); - break; - } - } - } + if (ns != null && m_Map != null) + { + ns.Sequence = 0; + ns.Send(new MapChange(this)); + ns.Send(new MapPatches()); + ns.Send(SeasonChange.Instantiate(GetSeason(), true)); - if ( pack != null ) - { - List packCopy = new List( pack.Items ); + if (ns.StygianAbyss) + ns.Send(new MobileUpdate(this)); + else + ns.Send(new MobileUpdateOld(this)); - for( int i = 0; i < packCopy.Count; ++i ) - { - Item item = packCopy[i]; + ClearFastwalkStack(); + } - DeathMoveResult res = GetInventoryMoveResultFor( item ); + if (ns != null) + { + if (m_Map != null) + ns.Send(new ServerChange(this, m_Map)); - if ( res == DeathMoveResult.MoveToCorpse ) - content.Add( item ); - else - moveToPack.Add( item ); - } + ns.Sequence = 0; + ClearFastwalkStack(); - for( int i = 0; i < moveToPack.Count; ++i ) - { - Item item = moveToPack[i]; + ns.Send(MobileIncoming.Create(ns, this, this)); - if ( RetainPackLocsOnDeath && item.Parent == pack ) - continue; + if (ns.StygianAbyss) + { + ns.Send(new MobileUpdate(this)); + CheckLightLevels(true); + ns.Send(new MobileUpdate(this)); + } + else + { + ns.Send(new MobileUpdateOld(this)); + CheckLightLevels(true); + ns.Send(new MobileUpdateOld(this)); + } + } - pack.DropItem( item ); - } - } + SendEverything(); + SendIncomingPacket(); - HairInfo hair = null; - if ( m_Hair != null ) - hair = new HairInfo( m_Hair.ItemID, m_Hair.Hue ); + if (ns != null) + { + ns.Sequence = 0; + ClearFastwalkStack(); - FacialHairInfo facialhair = null; - if ( m_FacialHair != null ) - facialhair = new FacialHairInfo( m_FacialHair.ItemID, m_FacialHair.Hue ); + ns.Send(MobileIncoming.Create(ns, this, this)); + + if (ns.StygianAbyss) + { + ns.Send(SupportedFeatures.Instantiate(ns)); + ns.Send(new MobileUpdate(this)); + ns.Send(new MobileAttributes(this)); + } + else + { + ns.Send(SupportedFeatures.Instantiate(ns)); + ns.Send(new MobileUpdateOld(this)); + ns.Send(new MobileAttributes(this)); + } + } + + OnMapChange(oldMap); + } + } + } + + [CommandProperty(AccessLevel.Counselor)] + public Serial Serial{ get; } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public Point3D Location + { + get => m_Location; + set => SetLocation(value, true); + } + + public virtual void MoveToWorld(Point3D newLocation, Map map) + { + if (Deleted) + return; + + if (m_Map == map) + { + SetLocation(newLocation, true); + return; + } + + BankBox box = FindBankNoCreate(); + + if (box?.Opened == true) + box.Close(); + + Point3D oldLocation = m_Location; + Map oldMap = m_Map; + + Region oldRegion = m_Region; + + if (oldMap != null) + { + oldMap.OnLeave(this); + + ClearScreen(); + SendRemovePacket(); + } + + for (int i = 0; i < Items.Count; ++i) + Items[i].Map = map; + + m_Map = map; + + m_Location = newLocation; + + NetState ns = m_NetState; + + if (m_Map != null) + { + m_Map.OnEnter(this); + + UpdateRegion(); + + if (ns != null && m_Map != null) + { + ns.Sequence = 0; + ns.Send(new MapChange(this)); + ns.Send(new MapPatches()); + ns.Send(SeasonChange.Instantiate(GetSeason(), true)); + + if (ns.StygianAbyss) + ns.Send(new MobileUpdate(this)); + else + ns.Send(new MobileUpdateOld(this)); + + ClearFastwalkStack(); + } + } + else + { + UpdateRegion(); + } + + if (ns != null) + { + if (m_Map != null) + Send(new ServerChange(this, m_Map)); + + ns.Sequence = 0; + ClearFastwalkStack(); + + ns.Send(MobileIncoming.Create(ns, this, this)); + + if (ns.StygianAbyss) + { + ns.Send(new MobileUpdate(this)); + CheckLightLevels(true); + ns.Send(new MobileUpdate(this)); + } + else + { + ns.Send(new MobileUpdateOld(this)); + CheckLightLevels(true); + ns.Send(new MobileUpdateOld(this)); + } + } + + SendEverything(); + SendIncomingPacket(); + + if (ns != null) + { + ns.Sequence = 0; + ClearFastwalkStack(); + + ns.Send(MobileIncoming.Create(ns, this, this)); + + if (ns.StygianAbyss) + { + ns.Send(SupportedFeatures.Instantiate(ns)); + ns.Send(new MobileUpdate(this)); + ns.Send(new MobileAttributes(this)); + } + else + { + ns.Send(SupportedFeatures.Instantiate(ns)); + ns.Send(new MobileUpdateOld(this)); + ns.Send(new MobileAttributes(this)); + } + } + + OnMapChange(oldMap); + OnLocationChange(oldLocation); + + m_Region?.OnLocationChanged(this, oldLocation); + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int X + { + get => m_Location.m_X; + set => Location = new Point3D(value, m_Location.m_Y, m_Location.m_Z); + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Y + { + get => m_Location.m_Y; + set => Location = new Point3D(m_Location.m_X, value, m_Location.m_Z); + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Z + { + get => m_Location.m_Z; + set => Location = new Point3D(m_Location.m_X, m_Location.m_Y, value); + } + + public virtual void ProcessDelta() + { + Mobile m = this; + MobileDelta delta; + + delta = m.m_DeltaFlags; + + if (delta == MobileDelta.None) + return; + + MobileDelta attrs = delta & MobileDelta.Attributes; + + m.m_DeltaFlags = MobileDelta.None; + m.m_InDeltaQueue = false; + + bool sendHits = false, sendStam = false, sendMana = false, sendAll = false, sendAny = false; + bool sendIncoming = false, sendNonlocalIncoming = false; + bool sendUpdate = false, sendRemove = false; + bool sendPublicStats = false, sendPrivateStats = false; + bool sendMoving = false, sendNonlocalMoving = false; + bool sendOPLUpdate = ObjectPropertyList.Enabled && (delta & MobileDelta.Properties) != 0; + + bool sendHair = false, sendFacialHair = false, removeHair = false, removeFacialHair = false; + + bool sendHealthbarPoison = false, sendHealthbarYellow = false; + + if (attrs != MobileDelta.None) + { + sendAny = true; + + if (attrs == MobileDelta.Attributes) + { + sendAll = true; + } + else + { + sendHits = (attrs & MobileDelta.Hits) != 0; + sendStam = (attrs & MobileDelta.Stam) != 0; + sendMana = (attrs & MobileDelta.Mana) != 0; + } + } + + if ((delta & MobileDelta.GhostUpdate) != 0) sendNonlocalIncoming = true; + + if ((delta & MobileDelta.Hue) != 0) + { + sendNonlocalIncoming = true; + sendUpdate = true; + sendRemove = true; + } + + if ((delta & MobileDelta.Direction) != 0) + { + sendNonlocalMoving = true; + sendUpdate = true; + } + + if ((delta & MobileDelta.Body) != 0) + { + sendUpdate = true; + sendIncoming = true; + } + + /*if ( (delta & MobileDelta.Hue) != 0 ) + { + sendNonlocalIncoming = true; + sendUpdate = true; + } + else if ( (delta & (MobileDelta.Direction | MobileDelta.Body)) != 0 ) + { + sendNonlocalMoving = true; + sendUpdate = true; + } + else*/ + if ((delta & (MobileDelta.Flags | MobileDelta.Noto)) != 0) sendMoving = true; + + if ((delta & MobileDelta.HealthbarPoison) != 0) sendHealthbarPoison = true; + + if ((delta & MobileDelta.HealthbarYellow) != 0) sendHealthbarYellow = true; + + if ((delta & MobileDelta.Name) != 0) + { + sendAll = false; + sendHits = false; + sendAny = sendStam || sendMana; + sendPublicStats = true; + } + + if ((delta & (MobileDelta.WeaponDamage | MobileDelta.Resistances | MobileDelta.Stat | + MobileDelta.Weight | MobileDelta.Gold | MobileDelta.Armor | MobileDelta.StatCap | + MobileDelta.Followers | MobileDelta.TithingPoints | MobileDelta.Race)) != 0) + sendPrivateStats = true; + + if ((delta & MobileDelta.Hair) != 0) + { + if (m.HairItemID <= 0) + removeHair = true; + + sendHair = true; + } + + if ((delta & MobileDelta.FacialHair) != 0) + { + if (m.FacialHairItemID <= 0) + removeFacialHair = true; + + sendFacialHair = true; + } + + Packet[][] cache = new Packet[2][] { new Packet[8], new Packet[8] }; + + NetState ourState = m.m_NetState; + + if (ourState != null) + { + if (sendUpdate) + { + ourState.Sequence = 0; + + if (ourState.StygianAbyss) + ourState.Send(new MobileUpdate(m)); + else + ourState.Send(new MobileUpdateOld(m)); + + ClearFastwalkStack(); + } + + if (sendIncoming) + ourState.Send(MobileIncoming.Create(ourState, m, m)); + + if (ourState.StygianAbyss) + { + if (sendMoving) + { + int noto = Notoriety.Compute(m, m); + ourState.Send(cache[0][noto] = Packet.Acquire(new MobileMoving(m, noto))); + } + + if (sendHealthbarPoison) + ourState.Send(new HealthbarPoison(m)); + + if (sendHealthbarYellow) + ourState.Send(new HealthbarYellow(m)); + } + else + { + if (sendMoving || sendHealthbarPoison || sendHealthbarYellow) + { + int noto = Notoriety.Compute(m, m); + ourState.Send(cache[1][noto] = Packet.Acquire(new MobileMovingOld(m, noto))); + } + } + + if (sendPublicStats || sendPrivateStats) + { + ourState.Send(new MobileStatusExtended(m, m_NetState)); + } + else if (sendAll) + { + ourState.Send(new MobileAttributes(m)); + } + else if (sendAny) + { + if (sendHits) + ourState.Send(new MobileHits(m)); + + if (sendStam) + ourState.Send(new MobileStam(m)); + + if (sendMana) + ourState.Send(new MobileMana(m)); + } + + if (sendStam || sendMana) + if (Party is IParty ip) + { + if (sendStam) + ip.OnStamChanged(this); + + if (sendMana) + ip.OnManaChanged(this); + } + + if (sendHair) + { + if (removeHair) + ourState.Send(new RemoveHair(m)); + else + ourState.Send(new HairEquipUpdate(m)); + } + + if (sendFacialHair) + { + if (removeFacialHair) + ourState.Send(new RemoveFacialHair(m)); + else + ourState.Send(new FacialHairEquipUpdate(m)); + } + + if (sendOPLUpdate) + ourState.Send(OPLPacket); + } + + sendMoving = sendMoving || sendNonlocalMoving; + sendIncoming = sendIncoming || sendNonlocalIncoming; + sendHits = sendHits || sendAll; + + if (m.m_Map != null && (sendRemove || sendIncoming || sendPublicStats || sendHits || sendMoving || + sendOPLUpdate || sendHair || sendFacialHair || sendHealthbarPoison || + sendHealthbarYellow)) + { + Mobile beholder; + + Packet hitsPacket = null; + Packet statPacketTrue = null; + Packet statPacketFalse = null; + Packet deadPacket = null; + Packet hairPacket = null; + Packet facialhairPacket = null; + Packet hbpPacket = null; + Packet hbyPacket = null; + + IPooledEnumerable eable = m.Map.GetClientsInRange(m.m_Location); + + foreach (NetState state in eable) + { + beholder = state.Mobile; + + if (beholder != m && beholder.CanSee(m)) + { + if (sendRemove) + state.Send(RemovePacket); + + if (sendIncoming) + { + state.Send(MobileIncoming.Create(state, beholder, m)); + + if (m.IsDeadBondedPet) + { + if (deadPacket == null) + deadPacket = Packet.Acquire(new BondedStatus(0, m.Serial, 1)); + + state.Send(deadPacket); + } + } + + if (state.StygianAbyss) + { + if (sendMoving) + { + int noto = Notoriety.Compute(beholder, m); + + Packet p = cache[0][noto]; + + if (p == null) + cache[0][noto] = p = Packet.Acquire(new MobileMoving(m, noto)); + + state.Send(p); + } + + if (sendHealthbarPoison) + { + if (hbpPacket == null) + hbpPacket = Packet.Acquire(new HealthbarPoison(m)); + + state.Send(hbpPacket); + } + + if (sendHealthbarYellow) + { + if (hbyPacket == null) + hbyPacket = Packet.Acquire(new HealthbarYellow(m)); + + state.Send(hbyPacket); + } + } + else + { + if (sendMoving || sendHealthbarPoison || sendHealthbarYellow) + { + int noto = Notoriety.Compute(beholder, m); + + Packet p = cache[1][noto]; + + if (p == null) + cache[1][noto] = p = Packet.Acquire(new MobileMovingOld(m, noto)); + + state.Send(p); + } + } + + if (sendPublicStats) + { + if (m.CanBeRenamedBy(beholder)) + { + if (statPacketTrue == null) + statPacketTrue = Packet.Acquire(new MobileStatusCompact(true, m)); + + state.Send(statPacketTrue); + } + else + { + if (statPacketFalse == null) + statPacketFalse = Packet.Acquire(new MobileStatusCompact(false, m)); + + state.Send(statPacketFalse); + } + } + else if (sendHits) + { + if (hitsPacket == null) + hitsPacket = Packet.Acquire(new MobileHitsN(m)); + + state.Send(hitsPacket); + } + + if (sendHair) + { + if (hairPacket == null) + { + if (removeHair) + hairPacket = Packet.Acquire(new RemoveHair(m)); + else + hairPacket = Packet.Acquire(new HairEquipUpdate(m)); + } - Container c = m_CreateCorpse?.Invoke( this, hair, facialhair, content, equip ); + state.Send(hairPacket); + } + if (sendFacialHair) + { + if (facialhairPacket == null) + { + if (removeFacialHair) + facialhairPacket = Packet.Acquire(new RemoveFacialHair(m)); + else + facialhairPacket = Packet.Acquire(new FacialHairEquipUpdate(m)); + } - /*m_Corpse = c; + state.Send(facialhairPacket); + } - for ( int i = 0; c != null && i < content.Count; ++i ) - c.DropItem( (Item)content[i] ); + if (sendOPLUpdate) + state.Send(OPLPacket); + } + } - if ( c != null ) - c.MoveToWorld( this.Location, this.Map );*/ + Packet.Release(hitsPacket); + Packet.Release(statPacketTrue); + Packet.Release(statPacketFalse); + Packet.Release(deadPacket); + Packet.Release(hairPacket); + Packet.Release(facialhairPacket); + Packet.Release(hbpPacket); + Packet.Release(hbyPacket); - if ( m_Map != null ) - { - Packet animPacket = null; + eable.Free(); + } - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + if (sendMoving || sendNonlocalMoving || sendHealthbarPoison || sendHealthbarYellow) + for (int i = 0; i < cache.Length; ++i) + for (int j = 0; j < cache[i].Length; ++j) + Packet.Release(ref cache[i][j]); + } - foreach( NetState state in eable ) { - if ( state != m_NetState ) { - if (animPacket == null) - animPacket = Packet.Acquire( new DeathAnimation( this, c ) );; + public virtual int HuedItemID => m_Female ? 0x2107 : 0x2106; - state.Send( animPacket ); + int ISerializable.TypeReference => m_TypeRef; - if ( !state.Mobile.CanSee( this ) ) { - state.Send( RemovePacket ); - } - } - } + int ISerializable.SerialIdentity => Serial; - Packet.Release( animPacket ); + public virtual void Serialize(GenericWriter writer) + { + writer.Write(32); // version - eable.Free(); - } + writer.WriteDeltaTime(LastStrGain); + writer.WriteDeltaTime(LastIntGain); + writer.WriteDeltaTime(LastDexGain); - Region.OnDeath( this ); - OnDeath( c ); - } + byte hairflag = 0x00; - private Container m_Corpse; + if (m_Hair != null) + hairflag |= 0x01; + if (m_FacialHair != null) + hairflag |= 0x02; - [CommandProperty( AccessLevel.GameMaster )] - public Container Corpse - { - get => m_Corpse; - set => m_Corpse = value; - } + writer.Write(hairflag); - /// - /// Overridable. Event invoked before the Mobile is killed. - /// - /// - /// - /// True to continue with death, false to override it. - public virtual bool OnBeforeDeath() - { - return true; - } + if ((hairflag & 0x01) != 0) + m_Hair.Serialize(writer); + if ((hairflag & 0x02) != 0) + m_FacialHair.Serialize(writer); - /// - /// Overridable. Event invoked after the Mobile is killed. Primarily, this method is responsible for deleting an NPC or turning a PC into a ghost. - /// - /// - /// - public virtual void OnDeath( Container c ) - { - int sound = GetDeathSound(); + writer.Write(Race); - if ( sound >= 0 ) - Effects.PlaySound( this, Map, sound ); + writer.Write(m_TithingPoints); - if ( !m_Player ) - { - Delete(); - } - else - { - Send( DeathStatus.Instantiate( true ) ); + writer.Write(Corpse); - Warmode = false; + writer.Write(CreationTime); - BodyMod = 0; - //Body = this.Female ? 0x193 : 0x192; - Body = Race.GhostBody( this ); + writer.Write(Stabled, true); - Item deathShroud = new Item( 0x204E ); + writer.Write(CantWalk); - deathShroud.Movable = false; - deathShroud.Layer = Layer.OuterTorso; + VirtueInfo.Serialize(writer, m_Virtues); - AddItem( deathShroud ); + writer.Write(Thirst); + writer.Write(BAC); - m_Items.Remove( deathShroud ); - m_Items.Insert( 0, deathShroud ); + writer.Write(m_ShortTermMurders); + //writer.Write( m_ShortTermElapse ); + //writer.Write( m_LongTermElapse ); - Poison = null; - Combatant = null; + //writer.Write( m_Followers ); + writer.Write(m_FollowersMax); - Hits = 0; - Stam = 0; - Mana = 0; + writer.Write(MagicDamageAbsorb); - EventSink.InvokePlayerDeath( new PlayerDeathEventArgs( this ) ); + writer.Write(GuildFealty); - ProcessDeltaQueue(); + writer.Write(m_Guild); - Send( DeathStatus.Instantiate( false ) ); + writer.Write(m_DisplayGuildTitle); - CheckStatTimers(); - } - } + writer.Write(CanSwim); - #region Get*Sound + writer.Write(Squelched); - public virtual int GetAngerSound() - { - if ( m_BaseSoundID != 0 ) - return m_BaseSoundID; + writer.Write(m_Holding); - return -1; - } + writer.Write(m_VirtualArmor); - public virtual int GetIdleSound() - { - if ( m_BaseSoundID != 0 ) - return m_BaseSoundID + 1; + writer.Write(BaseSoundID); - return -1; - } + writer.Write(DisarmReady); + writer.Write(StunReady); - public virtual int GetAttackSound() - { - if ( m_BaseSoundID != 0 ) - return m_BaseSoundID + 2; + //Poison.Serialize( m_Poison, writer ); - return -1; - } - - public virtual int GetHurtSound() - { - if ( m_BaseSoundID != 0 ) - return m_BaseSoundID + 3; - - return -1; - } - - public virtual int GetDeathSound() - { - if ( m_BaseSoundID != 0 ) - { - return m_BaseSoundID + 4; - } - - if ( m_Body.IsHuman ) - { - return Utility.Random( m_Female ? 0x314 : 0x423, m_Female ? 4 : 5 ); - } - return -1; - } - - #endregion - - private static char[] m_GhostChars = new char[2] { 'o', 'O' }; - - public static char[] GhostChars { get => m_GhostChars; - set => m_GhostChars = value; - } + writer.Write(m_StatCap); - private static bool m_NoSpeechLOS; - - public static bool NoSpeechLOS { get => m_NoSpeechLOS; - set => m_NoSpeechLOS = value; - } - - private static TimeSpan m_AutoManifestTimeout = TimeSpan.FromSeconds( 5.0 ); - - public static TimeSpan AutoManifestTimeout { get => m_AutoManifestTimeout; - set => m_AutoManifestTimeout = value; - } - - private Timer m_AutoManifestTimer; - - private class AutoManifestTimer : Timer - { - private Mobile m_Mobile; - - public AutoManifestTimer( Mobile m, TimeSpan delay ) - : base( delay ) - { - m_Mobile = m; - } - - protected override void OnTick() - { - if ( !m_Mobile.Alive ) - m_Mobile.Warmode = false; - } - } - - public virtual bool CheckTarget( Mobile from, Target targ, object targeted ) - { - return true; - } - - private static bool m_InsuranceEnabled; - - public static bool InsuranceEnabled - { - get => m_InsuranceEnabled; - set => m_InsuranceEnabled = value; - } - - public virtual void Use( Item item ) - { - if ( item == null || item.Deleted || item.QuestItem || Deleted ) - return; - - DisruptiveAction(); - - if ( m_Spell != null && !m_Spell.OnCasterUsingObject( item ) ) - return; - - object root = item.RootParent; - bool okay = false; - - if ( !Utility.InUpdateRange( this, item.GetWorldLocation() ) ) - item.OnDoubleClickOutOfRange( this ); - else if ( !CanSee( item ) ) - item.OnDoubleClickCantSee( this ); - else if ( !item.IsAccessibleTo( this ) ) - { - Region reg = Region.Find( item.GetWorldLocation(), item.Map ); - - if ( reg?.SendInaccessibleMessage( item, this ) != true ) - item.OnDoubleClickNotAccessible( this ); - } - else if ( !CheckAlive( false ) ) - item.OnDoubleClickDead( this ); - else if ( item.InSecureTrade ) - item.OnDoubleClickSecureTrade( this ); - else if ( !AllowItemUse( item ) ) - okay = false; - else if ( !item.CheckItemUse( this, item ) ) - okay = false; - else if ( root is Mobile mobile && mobile.IsSnoop( this ) ) - item.OnSnoop( this ); - else if ( Region.OnDoubleClick( this, item ) ) - okay = true; - - if ( okay ) - { - // TODO: Is this correct? - if ( !item.Deleted ) - item.OnItemUsed( this, item ); - - // TODO: Is this correct? - if ( !item.Deleted ) - item.OnDoubleClick( this ); - } - } - - public virtual void Use( Mobile m ) - { - if ( m == null || m.Deleted || Deleted ) - return; - - DisruptiveAction(); - - if ( m_Spell != null && !m_Spell.OnCasterUsingObject( m ) ) - return; - - if ( !Utility.InUpdateRange( this, m ) ) - m.OnDoubleClickOutOfRange( this ); - else if ( !CanSee( m ) ) - m.OnDoubleClickCantSee( this ); - else if ( !CheckAlive( false ) ) - m.OnDoubleClickDead( this ); - else if ( Region.OnDoubleClick( this, m ) && !m.Deleted ) - m.OnDoubleClick( this ); - } - - private static int m_ActionDelay = 500; - - public static int ActionDelay - { - get => m_ActionDelay; - set => m_ActionDelay = value; - } - - public virtual void Lift( Item item, int amount, out bool rejected, out LRReason reject ) - { - rejected = true; - reject = LRReason.Inspecific; - - if ( item == null ) - return; - - Mobile from = this; - NetState state = m_NetState; - - if (from.AccessLevel >= AccessLevel.GameMaster || Core.TickCount - from.NextActionTime >= 0) - { - if ( from.CheckAlive() ) - { - from.DisruptiveAction(); - - if ( from.Holding != null ) - { - reject = LRReason.AreHolding; - } - else if ( from.AccessLevel < AccessLevel.GameMaster && !from.InRange( item.GetWorldLocation(), 2 ) ) - { - reject = LRReason.OutOfRange; - } - else if ( !from.CanSee( item ) || !from.InLOS( item ) ) - { - reject = LRReason.OutOfSight; - } - else if ( !item.VerifyMove( from ) ) - { - reject = LRReason.CannotLift; - } - else if ( !item.IsAccessibleTo( from ) ) - { - reject = LRReason.CannotLift; - } - else if ( item.Nontransferable && amount != item.Amount ) - { - if ( item.QuestItem ) - from.SendLocalizedMessage( 1074868 ); // Stacks of quest items cannot be unstacked. - - reject = LRReason.CannotLift; - } - else if ( !item.CheckLift( from, item, ref reject ) ) - { - } - else - { - object root = item.RootParent; - - if ( root is Mobile mobile && !mobile.CheckNonlocalLift( from, item ) ) - { - reject = LRReason.TryToSteal; - } - else if ( !from.OnDragLift( item ) || !item.OnDragLift( from ) ) - { - reject = LRReason.Inspecific; - } - else if ( !from.CheckAlive() ) - { - reject = LRReason.Inspecific; - } - else - { - item.SetLastMoved(); - - if ( item.Spawner != null ) - { - item.Spawner.Remove( item ); - item.Spawner = null; - } - - if ( amount == 0 ) - amount = 1; - - if ( amount > item.Amount ) - amount = item.Amount; - - int oldAmount = item.Amount; - //item.Amount = amount; //Set in LiftItemDupe - - if ( amount < oldAmount ) - LiftItemDupe( item, amount ); - //item.Dupe( oldAmount - amount ); - - Map map = from.Map; - - if ( m_DragEffects && map != null && (root == null || root is Item) ) - { - IPooledEnumerable eable = map.GetClientsInRange(from.Location); - Packet p = null; - Item rootItem = root as Item; - - foreach( NetState ns in eable ) { - if ( ns.Mobile != from && ns.Mobile.CanSee( from ) && ns.Mobile.InLOS( from ) && ns.Mobile.CanSee( root ) ) { - if (p == null) { - IEntity src = new Entity(rootItem?.Serial ?? Serial.Zero, rootItem?.Location ?? item.Location, map); - - p = Packet.Acquire(new DragEffect(src, from, item.ItemID, item.Hue, amount)); - } - - ns.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - - Point3D fixLoc = item.Location; - Map fixMap = item.Map; - bool shouldFix = (item.Parent == null); - - item.RecordBounce(); - item.OnItemLifted( from, item ); - item.Internalize(); - - from.Holding = item; - - int liftSound = item.GetLiftSound( from ); - - if ( liftSound != -1 ) - from.Send( new PlaySound( liftSound, from ) ); - - from.NextActionTime = Core.TickCount + m_ActionDelay; - - if ( fixMap != null && shouldFix ) - fixMap.FixColumn( fixLoc.m_X, fixLoc.m_Y ); - - reject = LRReason.Inspecific; - rejected = false; - } - } - } - else - { - reject = LRReason.Inspecific; - } - } - else - { - SendActionMessage(); - reject = LRReason.Inspecific; - } - - if ( rejected && state != null ) - { - state.Send( new LiftRej( reject ) ); - - if ( item.Deleted ) - return; - - if ( item.Parent is Item ) { - if ( state.ContainerGridLines ) - state.Send( new ContainerContentUpdate6017( item ) ); - else - state.Send( new ContainerContentUpdate( item ) ); - } else if ( item.Parent is Mobile ) - state.Send( new EquipUpdate( item ) ); - else - item.SendInfoTo( state ); - - if ( ObjectPropertyList.Enabled && item.Parent != null ) - state.Send( item.OPLPacket ); - } - } - - public static Item LiftItemDupe( Item oldItem, int amount ) - { - Item item; - try - { - item = (Item)Activator.CreateInstance( oldItem.GetType() ); - } - catch - { - Console.WriteLine( "Warning: 0x{0:X}: Item must have a zero paramater constructor to be separated from a stack. '{1}'.", oldItem.Serial.Value, oldItem.GetType().Name ); - return null; - } - - item.Visible = oldItem.Visible; - item.Movable = oldItem.Movable; - item.LootType = oldItem.LootType; - item.Direction = oldItem.Direction; - item.Hue = oldItem.Hue; - item.ItemID = oldItem.ItemID; - item.Location = oldItem.Location; - item.Layer = oldItem.Layer; - item.Name = oldItem.Name; - item.Weight = oldItem.Weight; - - item.Amount = oldItem.Amount - amount; - item.Map = oldItem.Map; - - oldItem.Amount = amount; - oldItem.OnAfterDuped( item ); - - if ( oldItem.Parent is Mobile parentMobile ) - { - parentMobile.AddItem( item ); - } - else if ( oldItem.Parent is Item parentItem ) - { - parentItem.AddItem( item ); - } - - item.Delta( ItemDelta.Update ); - - return item; - } - - public virtual void SendDropEffect( Item item ) - { - if ( m_DragEffects && !item.Deleted ) - { - Map map = m_Map; - object root = item.RootParent; - - if ( map != null && (root == null || root is Item) ) - { - IPooledEnumerable eable = map.GetClientsInRange(m_Location); - Packet p = null; - Item rootItem = root as Item; - - foreach(NetState ns in eable) { - if (ns.StygianAbyss) - continue; - - if ( ns.Mobile != this && ns.Mobile.CanSee( this ) && ns.Mobile.InLOS( this ) && ns.Mobile.CanSee( root ) ) { - if (p == null) { - IEntity trg = new Entity(rootItem?.Serial ?? Serial.Zero, rootItem?.Location ?? item.Location, map); - - p = Packet.Acquire(new DragEffect(this, trg, item.ItemID, item.Hue, item.Amount)); - } - - ns.Send( p ); - } - } + writer.Write(NameHue); - Packet.Release( p ); + writer.Write(m_Hunger); - eable.Free(); - } - } - } + writer.Write(m_Location); + writer.Write(m_Body); + writer.Write(m_Name); + writer.Write(m_GuildTitle); + writer.Write(m_Criminal); + writer.Write(m_Kills); + writer.Write(SpeechHue); + writer.Write(EmoteHue); + writer.Write(WhisperHue); + writer.Write(YellHue); + writer.Write(m_Language); + writer.Write(m_Female); + writer.Write(m_Warmode); + writer.Write(m_Hidden); + writer.Write((byte)m_Direction); + writer.Write(m_Hue); + writer.Write(m_Str); + writer.Write(m_Dex); + writer.Write(m_Int); + writer.Write(m_Hits); + writer.Write(m_Stam); + writer.Write(m_Mana); - public virtual bool Drop( Item to, Point3D loc ) - { - Mobile from = this; - Item item = from.Holding; + writer.Write(m_Map); - bool valid = ( item != null && item.HeldBy == from && item.Map == Map.Internal ); + writer.Write(m_Blessed); + writer.Write(m_Fame); + writer.Write(m_Karma); + writer.Write((byte)m_AccessLevel); + m_Skills.Serialize(writer); - from.Holding = null; + writer.Write(Items); - if ( !valid ) { - return false; - } + writer.Write(m_Player); + writer.Write(m_Title); + writer.Write(Profile); + writer.Write(ProfileLocked); + writer.Write(AutoPageNotify); - bool bounced = true; + writer.Write(LogoutLocation); + writer.Write(LogoutMap); - item.SetLastMoved(); + writer.Write((byte)m_StrLock); + writer.Write((byte)m_DexLock); + writer.Write((byte)m_IntLock); + } - if ( to == null || !item.DropToItem( from, to, loc ) ) - item.Bounce( from ); - else - bounced = false; + public ISpawner Spawner{ get; set; } - item.ClearBounce(); + public virtual void OnBeforeSpawn(Point3D location, Map m) + { + } - if ( !bounced ) - SendDropEffect( item ); + public virtual void OnAfterSpawn() + { + } - return !bounced; - } + protected virtual void OnRaceChange(Race oldRace) + { + } - public virtual bool Drop( Point3D loc ) - { - Mobile from = this; - Item item = from.Holding; + public virtual void ComputeLightLevels(out int global, out int personal) + { + ComputeBaseLightLevels(out global, out personal); - bool valid = ( item != null && item.HeldBy == from && item.Map == Map.Internal ); + m_Region?.AlterLightLevel(this, ref global, ref personal); + } - from.Holding = null; + public virtual void ComputeBaseLightLevels(out int global, out int personal) + { + global = 0; + personal = m_LightLevel; + } - if ( !valid ) { - return false; - } + public virtual void CheckLightLevels(bool forceResend) + { + } + + public virtual void UpdateResistances() + { + if (Resistances == null) + Resistances = new int[5] { int.MinValue, int.MinValue, int.MinValue, int.MinValue, int.MinValue }; + + bool delta = false; + + for (int i = 0; i < Resistances.Length; ++i) + if (Resistances[i] != int.MinValue) + { + Resistances[i] = int.MinValue; + delta = true; + } + + if (delta) + Delta(MobileDelta.Resistances); + } + + public virtual int GetResistance(ResistanceType type) + { + if (Resistances == null) + Resistances = new int[5] { int.MinValue, int.MinValue, int.MinValue, int.MinValue, int.MinValue }; + + int v = (int)type; + + if (v < 0 || v >= Resistances.Length) + return 0; + + int res = Resistances[v]; + + if (res == int.MinValue) + { + ComputeResistances(); + res = Resistances[v]; + } + + return res; + } + + public virtual void AddResistanceMod(ResistanceMod toAdd) + { + if (ResistanceMods == null) ResistanceMods = new List(); + + ResistanceMods.Add(toAdd); + UpdateResistances(); + } + + public virtual void RemoveResistanceMod(ResistanceMod toRemove) + { + if (ResistanceMods != null) + { + ResistanceMods.Remove(toRemove); + + if (ResistanceMods.Count == 0) + ResistanceMods = null; + } + + UpdateResistances(); + } + + public virtual void ComputeResistances() + { + if (Resistances == null) + Resistances = new int[5] { int.MinValue, int.MinValue, int.MinValue, int.MinValue, int.MinValue }; + + for (int i = 0; i < Resistances.Length; ++i) + Resistances[i] = 0; + + Resistances[0] += BasePhysicalResistance; + Resistances[1] += BaseFireResistance; + Resistances[2] += BaseColdResistance; + Resistances[3] += BasePoisonResistance; + Resistances[4] += BaseEnergyResistance; + + for (int i = 0; ResistanceMods != null && i < ResistanceMods.Count; ++i) + { + ResistanceMod mod = ResistanceMods[i]; + int v = (int)mod.Type; + + if (v >= 0 && v < Resistances.Length) + Resistances[v] += mod.Offset; + } + + for (int i = 0; i < Items.Count; ++i) + { + Item item = Items[i]; + + if (item.CheckPropertyConfliction(this)) + continue; + + Resistances[0] += item.PhysicalResistance; + Resistances[1] += item.FireResistance; + Resistances[2] += item.ColdResistance; + Resistances[3] += item.PoisonResistance; + Resistances[4] += item.EnergyResistance; + } + + for (int i = 0; i < Resistances.Length; ++i) + { + int min = GetMinResistance((ResistanceType)i); + int max = GetMaxResistance((ResistanceType)i); + + if (max < min) + max = min; + + if (Resistances[i] > max) + Resistances[i] = max; + else if (Resistances[i] < min) + Resistances[i] = min; + } + } + + public virtual int GetMinResistance(ResistanceType type) + { + return int.MinValue; + } + + public virtual int GetMaxResistance(ResistanceType type) + { + if (m_Player) + return MaxPlayerResistance; + + return int.MaxValue; + } + + public int GetAOSStatus(int index) + { + return AOSStatusHandler?.Invoke(this, index) ?? 0; + } + + public virtual void SendPropertiesTo(Mobile from) + { + from.Send(PropertyList); + } + + public virtual void OnAosSingleClick(Mobile from) + { + ObjectPropertyList opl = PropertyList; + + if (opl.Header > 0) + { + int hue; + + if (NameHue != -1) + hue = NameHue; + else if (m_AccessLevel > AccessLevel.Player) + hue = 11; + else + hue = Notoriety.GetHue(Notoriety.Compute(from, this)); + + from.Send(new MessageLocalized(Serial, Body, MessageType.Label, hue, 3, opl.Header, Name, opl.HeaderArgs)); + } + } + + public virtual string ApplyNameSuffix(string suffix) + { + return suffix; + } + + public virtual void AddNameProperties(ObjectPropertyList list) + { + string name = Name; + + if (name == null) + name = string.Empty; + + string prefix = ""; + + if (ShowFameTitle && (m_Player || m_Body.IsHuman) && m_Fame >= 10000) + prefix = m_Female ? "Lady" : "Lord"; + + string suffix = ""; + + if (PropertyTitle && !string.IsNullOrEmpty(Title)) + suffix = Title; + + BaseGuild guild = m_Guild; + + if (guild != null && (m_Player || m_DisplayGuildTitle)) + { + if (suffix.Length > 0) + suffix = string.Format("{0} [{1}]", suffix, Utility.FixHtml(guild.Abbreviation)); + else + suffix = string.Format("[{0}]", Utility.FixHtml(guild.Abbreviation)); + } + + suffix = ApplyNameSuffix(suffix); + + list.Add(1050045, "{0} \t{1}\t {2}", prefix, name, suffix); // ~1_PREFIX~~2_NAME~~3_SUFFIX~ + + if (guild != null && (m_DisplayGuildTitle || m_Player && guild.Type != GuildType.Regular)) + { + string type; + + if (guild.Type >= 0 && (int)guild.Type < m_GuildTypes.Length) + type = m_GuildTypes[(int)guild.Type]; + else + type = ""; + + string title = GuildTitle; + + if (title == null) + title = ""; + else + title = title.Trim(); + + if (NewGuildDisplay && title.Length > 0) + { + list.Add("{0}, {1}", Utility.FixHtml(title), Utility.FixHtml(guild.Name)); + } + else + { + if (title.Length > 0) + list.Add("{0}, {1} Guild{2}", Utility.FixHtml(title), Utility.FixHtml(guild.Name), type); + else + list.Add(Utility.FixHtml(guild.Name)); + } + } + } + + public virtual void GetProperties(ObjectPropertyList list) + { + AddNameProperties(list); + } + + public virtual void GetChildProperties(ObjectPropertyList list, Item item) + { + } + + public virtual void GetChildNameProperties(ObjectPropertyList list, Item item) + { + } + + private void UpdateAggrExpire() + { + if (Deleted || Aggressors.Count == 0 && Aggressed.Count == 0) + { + StopAggrExpire(); + } + else if (m_ExpireAggrTimer == null) + { + m_ExpireAggrTimer = new ExpireAggressorsTimer(this); + m_ExpireAggrTimer.Start(); + } + } + + private void StopAggrExpire() + { + if (m_ExpireAggrTimer != null) + m_ExpireAggrTimer.Stop(); + + m_ExpireAggrTimer = null; + } + + private void CheckAggrExpire() + { + for (int i = Aggressors.Count - 1; i >= 0; --i) + { + if (i >= Aggressors.Count) + continue; + + AggressorInfo info = Aggressors[i]; + + if (info.Expired) + { + Mobile attacker = info.Attacker; + attacker.RemoveAggressed(this); + + Aggressors.RemoveAt(i); + info.Free(); + + if (m_NetState != null && CanSee(attacker) && Utility.InUpdateRange(m_Location, attacker.m_Location)) + m_NetState.Send(MobileIncoming.Create(m_NetState, this, attacker)); + } + } + + for (int i = Aggressed.Count - 1; i >= 0; --i) + { + if (i >= Aggressed.Count) + continue; + + AggressorInfo info = Aggressed[i]; + + if (info.Expired) + { + Mobile defender = info.Defender; + defender.RemoveAggressor(this); + + Aggressed.RemoveAt(i); + info.Free(); + + if (m_NetState != null && CanSee(defender) && Utility.InUpdateRange(m_Location, defender.m_Location)) + m_NetState.Send(MobileIncoming.Create(m_NetState, this, defender)); + } + } + + UpdateAggrExpire(); + } + + /// + /// Overridable. Virtual event invoked when changes in some way. + /// + public virtual void OnSkillInvalidated(Skill skill) + { + } + + public virtual void UpdateSkillMods() + { + ValidateSkillMods(); + + for (int i = 0; i < SkillMods.Count; ++i) + { + SkillMod mod = SkillMods[i]; + Skill sk = m_Skills[mod.Skill]; + sk?.Update(); + } + } + + public virtual void ValidateSkillMods() + { + for (int i = 0; i < SkillMods.Count;) + { + SkillMod mod = SkillMods[i]; + + if (mod.CheckCondition()) + ++i; + else + InternalRemoveSkillMod(mod); + } + } + + public virtual void AddSkillMod(SkillMod mod) + { + if (mod == null) + return; + + ValidateSkillMods(); + + if (!SkillMods.Contains(mod)) + { + SkillMods.Add(mod); + mod.Owner = this; + + Skill sk = m_Skills[mod.Skill]; + sk?.Update(); + } + } + + public virtual void RemoveSkillMod(SkillMod mod) + { + if (mod == null) + return; + + ValidateSkillMods(); + + InternalRemoveSkillMod(mod); + } + + private void InternalRemoveSkillMod(SkillMod mod) + { + if (SkillMods.Contains(mod)) + { + SkillMods.Remove(mod); + mod.Owner = null; + + Skill sk = m_Skills[mod.Skill]; + sk?.Update(); + } + } + + /// + /// Overridable. Virtual event invoked when a client, , invokes a 'help request' for the Mobile. + /// Seemingly no longer functional in newer clients. + /// + public virtual void OnHelpRequest(Mobile from) + { + } + + public void DelayChangeWarmode(bool value) + { + if (m_WarmodeTimer != null) + { + m_WarmodeTimer.Value = value; + return; + } + + if (m_Warmode == value) + return; + + DateTime now = DateTime.UtcNow, next = m_NextWarmodeChange; + + if (now > next || m_WarmodeChanges == 0) + { + m_WarmodeChanges = 1; + m_NextWarmodeChange = now + WarmodeSpamCatch; + } + else if (m_WarmodeChanges == WarmodeCatchCount) + { + m_WarmodeTimer = new WarmodeTimer(this, value); + m_WarmodeTimer.Start(); + + return; + } + else + { + ++m_WarmodeChanges; + } + + Warmode = value; + } + + public bool InLOS(Mobile target) + { + if (Deleted || m_Map == null) + return false; + if (target == this || m_AccessLevel > AccessLevel.Player) + return true; + + return m_Map.LineOfSight(this, target); + } + + public bool InLOS(object target) + { + if (Deleted || m_Map == null) + return false; + if (target == this || m_AccessLevel > AccessLevel.Player) + return true; + if (target is Item item && item.RootParent == this) + return true; + + return m_Map.LineOfSight(this, target); + } + + public bool InLOS(Point3D target) + { + if (Deleted || m_Map == null) + return false; + if (m_AccessLevel > AccessLevel.Player) + return true; + + return m_Map.LineOfSight(this, target); + } + + public bool BeginAction(object toLock) + { + if (_actions == null) + { + _actions = new List(); + + _actions.Add(toLock); + + return true; + } + + if (!_actions.Contains(toLock)) + { + _actions.Add(toLock); + + return true; + } + + return false; + } + + public bool CanBeginAction(object toLock) + { + return _actions == null || !_actions.Contains(toLock); + } + + public void EndAction(object toLock) + { + if (_actions != null) + { + _actions.Remove(toLock); + + if (_actions.Count == 0) _actions = null; + } + } + + public virtual TimeSpan GetLogoutDelay() + { + return Region.GetLogoutDelay(this); + } + + public void Paralyze(TimeSpan duration) + { + if (!m_Paralyzed) + { + Paralyzed = true; + + m_ParaTimer = new ParalyzedTimer(this, duration); + m_ParaTimer.Start(); + } + } + + public void Freeze(TimeSpan duration) + { + if (!m_Frozen) + { + Frozen = true; + + m_FrozenTimer = new FrozenTimer(this, duration); + m_FrozenTimer.Start(); + } + } + + public override string ToString() + { + return string.Format("0x{0:X} \"{1}\"", Serial.Value, Name); + } + + public virtual void SendSkillMessage() + { + if (NextActionMessage - Core.TickCount >= 0) + return; + + NextActionMessage = Core.TickCount + ActionMessageDelay; + + SendLocalizedMessage(500118); // You must wait a few moments to use another skill. + } + + public virtual void SendActionMessage() + { + if (NextActionMessage - Core.TickCount >= 0) + return; + + NextActionMessage = Core.TickCount + ActionMessageDelay; + + SendLocalizedMessage(500119); // You must wait to perform another action. + } + + public virtual void ClearHands() + { + ClearHand(FindItemOnLayer(Layer.OneHanded)); + ClearHand(FindItemOnLayer(Layer.TwoHanded)); + } + + public virtual void ClearHand(Item item) + { + if (item != null && item.Movable && !item.AllowEquippedCast(this)) + { + Container pack = Backpack; + + if (pack == null) + AddToBackpack(item); + else + pack.DropItem(item); + } + } + + public virtual void Attack(Mobile m) + { + if (CheckAttack(m)) + Combatant = m; + } + + public virtual bool CheckAttack(Mobile m) + { + return Utility.InUpdateRange(this, m) && CanSee(m) && InLOS(m); + } + + /// + /// Overridable. Virtual event invoked after the property has changed. + /// + /// + public virtual void OnCombatantChange() + { + } + + public double GetDistanceToSqrt(Point3D p) + { + int xDelta = m_Location.m_X - p.m_X; + int yDelta = m_Location.m_Y - p.m_Y; + + return Math.Sqrt(xDelta * xDelta + yDelta * yDelta); + } + + public double GetDistanceToSqrt(Mobile m) + { + int xDelta = m_Location.m_X - m.m_Location.m_X; + int yDelta = m_Location.m_Y - m.m_Location.m_Y; + + return Math.Sqrt(xDelta * xDelta + yDelta * yDelta); + } + + public double GetDistanceToSqrt(IPoint2D p) + { + int xDelta = m_Location.m_X - p.X; + int yDelta = m_Location.m_Y - p.Y; - bool bounced = true; + return Math.Sqrt(xDelta * xDelta + yDelta * yDelta); + } - item.SetLastMoved(); + public virtual void AggressiveAction(Mobile aggressor) + { + AggressiveAction(aggressor, false); + } - if ( !item.DropToWorld( from, loc ) ) - item.Bounce( from ); - else - bounced = false; + public virtual void AggressiveAction(Mobile aggressor, bool criminal) + { + if (aggressor == this) + return; - item.ClearBounce(); + AggressiveActionEventArgs args = AggressiveActionEventArgs.Create(this, aggressor, criminal); - if ( !bounced ) - SendDropEffect( item ); + EventSink.InvokeAggressiveAction(args); - return !bounced; - } + args.Free(); - public virtual bool Drop( Mobile to, Point3D loc ) - { - Mobile from = this; - Item item = from.Holding; + if (Combatant == aggressor) + { + if (m_ExpireCombatant == null) + m_ExpireCombatant = new ExpireCombatantTimer(this); + else + m_ExpireCombatant.Stop(); - bool valid = ( item != null && item.HeldBy == from && item.Map == Map.Internal ); + m_ExpireCombatant.Start(); + } - from.Holding = null; + bool addAggressor = true; - if ( !valid ) { - return false; - } + List list = Aggressors; - bool bounced = true; + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - item.SetLastMoved(); + if (info.Attacker == aggressor) + { + info.Refresh(); + info.CriminalAggression = criminal; + info.CanReportMurder = criminal; - if ( to == null || !item.DropToMobile( from, to, loc ) ) - item.Bounce( from ); - else - bounced = false; + addAggressor = false; + } + } - item.ClearBounce(); + list = aggressor.Aggressors; - if ( !bounced ) - SendDropEffect( item ); + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - return !bounced; - } + if (info.Attacker == this) + { + info.Refresh(); - private static object m_GhostMutateContext = new object(); + addAggressor = false; + } + } - public virtual bool MutateSpeech( List hears, ref string text, ref object context ) - { - if ( Alive ) - return false; + bool addAggressed = true; - StringBuilder sb = new StringBuilder( text.Length, text.Length ); + list = Aggressed; - for( int i = 0; i < text.Length; ++i ) - { - if ( text[i] != ' ' ) - sb.Append( m_GhostChars[Utility.Random( m_GhostChars.Length )] ); - else - sb.Append( ' ' ); - } + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - text = sb.ToString(); - context = m_GhostMutateContext; - return true; - } + if (info.Defender == aggressor) + { + info.Refresh(); - public virtual void Manifest( TimeSpan delay ) - { - Warmode = true; + addAggressed = false; + } + } - if ( m_AutoManifestTimer == null ) - m_AutoManifestTimer = new AutoManifestTimer( this, delay ); - else - m_AutoManifestTimer.Stop(); + list = aggressor.Aggressed; - m_AutoManifestTimer.Start(); - } + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - public virtual bool CheckSpeechManifest() - { - if ( Alive ) - return false; + if (info.Defender == this) + { + info.Refresh(); + info.CriminalAggression = criminal; + info.CanReportMurder = criminal; - TimeSpan delay = m_AutoManifestTimeout; + addAggressed = false; + } + } - if ( delay > TimeSpan.Zero && (!Warmode || m_AutoManifestTimer != null) ) - { - Manifest( delay ); - return true; - } + bool setCombatant = false; - return false; - } + if (addAggressor) + { + Aggressors.Add(AggressorInfo.Create(aggressor, this, + criminal)); // new AggressorInfo( aggressor, this, criminal, true ) ); - public virtual bool CheckHearsMutatedSpeech( Mobile m, object context ) - { - if ( context == m_GhostMutateContext ) - return (m.Alive && !m.CanHearGhosts); + if (CanSee(aggressor)) m_NetState?.Send(MobileIncoming.Create(m_NetState, this, aggressor)); - return true; - } + if (Combatant == null) + setCombatant = true; - private void AddSpeechItemsFrom(List list, Container cont) - { - for(int i = 0; i < cont.Items.Count; ++i) { - Item item = cont.Items[i]; + UpdateAggrExpire(); + } - if (item.HandlesOnSpeech) - list.Add( item ); + if (addAggressed) + { + aggressor.Aggressed.Add(AggressorInfo.Create(aggressor, this, + criminal)); // new AggressorInfo( aggressor, this, criminal, false ) ); - if (item is Container container) - AddSpeechItemsFrom(list, container); - } - } + if (CanSee(aggressor)) m_NetState?.Send(MobileIncoming.Create(m_NetState, this, aggressor)); - private class LocationComparer : IComparer - { - private static LocationComparer m_Instance; + if (Combatant == null) + setCombatant = true; - public static LocationComparer GetInstance(IEntity relativeTo) - { - if ( m_Instance == null ) - m_Instance = new LocationComparer(relativeTo); - else - m_Instance.m_RelativeTo = relativeTo; + UpdateAggrExpire(); + } - return m_Instance; - } - - private IEntity m_RelativeTo; - - public IEntity RelativeTo - { - get => m_RelativeTo; - set => m_RelativeTo = value; - } - - public LocationComparer(IEntity relativeTo) - { - m_RelativeTo = relativeTo; - } - - private int GetDistance(IEntity p) - { - int x = m_RelativeTo.X - p.X; - int y = m_RelativeTo.Y - p.Y; - int z = m_RelativeTo.Z - p.Z; - - x *= 11; - y *= 11; - - return (x * x) + (y * y) + (z * z); - } - - public int Compare(IEntity x, IEntity y) - { - return GetDistance(x) - GetDistance(y); - } - } - - #region Get*InRange - public IPooledEnumerable GetItemsInRange(int range) - { - return GetItemsInRange(range); - } - public IPooledEnumerable GetItemsInRange( int range ) where T : Item - { - Map map = m_Map; - - if ( map == null ) - return Map.NullEnumerable.Instance; - - return map.GetItemsInRange( m_Location, range ); - } - - public IPooledEnumerable GetObjectsInRange( int range ) - { - Map map = m_Map; - - if ( map == null ) - return Map.NullEnumerable.Instance; - - return map.GetObjectsInRange( m_Location, range ); - } - - public IPooledEnumerable GetMobilesInRange( int range ) - { - return GetMobilesInRange(range); - } - public IPooledEnumerable GetMobilesInRange(int range) where T : Mobile - { - Map map = m_Map; - - if (map == null) - return Map.NullEnumerable.Instance; - - return map.GetMobilesInRange(m_Location, range); - } - - public IPooledEnumerable GetClientsInRange(int range) - { - Map map = m_Map; - - if ( map == null ) - return Map.NullEnumerable.Instance; - - return map.GetClientsInRange( m_Location, range ); - } - - #endregion - - private static List m_Hears = new List(); - private static List m_OnSpeech = new List(); - - public virtual void DoSpeech( string text, int[] keywords, MessageType type, int hue ) - { - if ( m_Deleted || CommandSystem.Handle( this, text, type ) ) - return; - - int range = 15; - - switch( type ) - { - case MessageType.Regular: - m_SpeechHue = hue; - break; - case MessageType.Emote: - m_EmoteHue = hue; - break; - case MessageType.Whisper: - m_WhisperHue = hue; - range = 1; - break; - case MessageType.Yell: - m_YellHue = hue; - range = 18; - break; - default: - type = MessageType.Regular; - break; - } + if (setCombatant) + Combatant = aggressor; - SpeechEventArgs regArgs = new SpeechEventArgs( this, text, type, hue, keywords ); + Region.OnAggressed(aggressor, this, criminal); + } - EventSink.InvokeSpeech( regArgs ); - Region.OnSpeech( regArgs ); - OnSaid( regArgs ); + public void RemoveAggressed(Mobile aggressed) + { + if (Deleted) + return; - if ( regArgs.Blocked ) - return; + List list = Aggressed; - text = regArgs.Speech; + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - if ( string.IsNullOrEmpty( text ) ) - return; - - List hears = m_Hears; - List onSpeech = m_OnSpeech; - - if ( m_Map != null ) - { - IPooledEnumerable eable = m_Map.GetObjectsInRange( m_Location, range ); + if (info.Defender == aggressed) + { + Aggressed.RemoveAt(i); + info.Free(); - foreach(IEntity o in eable) { - if ( o is Mobile heard ) { - if ( heard.CanSee( this ) && (m_NoSpeechLOS || !heard.Player || heard.InLOS( this )) ) - { - if ( heard.m_NetState != null ) - hears.Add( heard ); + if (m_NetState != null && CanSee(aggressed)) + m_NetState.Send(MobileIncoming.Create(m_NetState, this, aggressed)); - if ( heard.HandlesOnSpeech( this ) ) - onSpeech.Add( heard ); + break; + } + } - for( int i = 0; i < heard.Items.Count; ++i ) - { - Item item = heard.Items[i]; + UpdateAggrExpire(); + } - if ( item.HandlesOnSpeech ) - onSpeech.Add( item ); + public void RemoveAggressor(Mobile aggressor) + { + if (Deleted) + return; - if ( item is Container container ) - AddSpeechItemsFrom( onSpeech, container ); - } - } - } - else if ( o is Item item ) - { - if ( item.HandlesOnSpeech ) - onSpeech.Add(item); + List list = Aggressors; - if ( item is Container container ) - AddSpeechItemsFrom( onSpeech, container ); - } - } + for (int i = 0; i < list.Count; ++i) + { + AggressorInfo info = list[i]; - eable.Free(); + if (info.Attacker == aggressor) + { + Aggressors.RemoveAt(i); + info.Free(); - object mutateContext = null; - string mutatedText = text; - SpeechEventArgs mutatedArgs = null; + if (m_NetState != null && CanSee(aggressor)) + m_NetState.Send(MobileIncoming.Create(m_NetState, this, aggressor)); - if ( MutateSpeech( hears, ref mutatedText, ref mutateContext ) ) - mutatedArgs = new SpeechEventArgs( this, mutatedText, type, hue, new int[0] ); - - CheckSpeechManifest(); + break; + } + } - ProcessDelta(); + UpdateAggrExpire(); + } - Packet regp = null; - Packet mutp = null; - - // TODO: Should this be sorted like onSpeech is below? - - for( int i = 0; i < hears.Count; ++i ) { - Mobile heard = hears[i]; - - if ( mutatedArgs == null || !CheckHearsMutatedSpeech( heard, mutateContext ) ) { - heard.OnSpeech( regArgs ); - - NetState ns = heard.NetState; - - if ( ns != null ) { - if ( regp == null ) - regp = Packet.Acquire( new UnicodeMessage( m_Serial, Body, type, hue, 3, m_Language, Name, text ) ); - - ns.Send( regp ); - } - } else { - heard.OnSpeech( mutatedArgs ); - - NetState ns = heard.NetState; - - if ( ns != null ) { - if ( mutp == null ) - mutp = Packet.Acquire( new UnicodeMessage( m_Serial, Body, type, hue, 3, m_Language, Name, mutatedText ) ); + public virtual int GetTotal(TotalType type) + { + switch (type) + { + case TotalType.Gold: + return m_TotalGold; - ns.Send( mutp ); - } - } - } + case TotalType.Items: + return m_TotalItems; - Packet.Release( regp ); - Packet.Release( mutp ); + case TotalType.Weight: + return m_TotalWeight; + } - if ( onSpeech.Count > 1 ) - onSpeech.Sort( LocationComparer.GetInstance( this ) ); + return 0; + } - for( int i = 0; i < onSpeech.Count; ++i ) { - IEntity obj = onSpeech[i]; + public virtual void UpdateTotal(Item sender, TotalType type, int delta) + { + if (delta == 0 || sender.IsVirtualItem) + return; - if ( obj is Mobile heard ) { - if ( mutatedArgs == null || !CheckHearsMutatedSpeech( heard, mutateContext ) ) - heard.OnSpeech( regArgs ); - else - heard.OnSpeech( mutatedArgs ); - } else { - ((Item)obj).OnSpeech( regArgs ); - } - } - - if (m_Hears.Count > 0) - m_Hears.Clear(); - - if (m_OnSpeech.Count > 0) - m_OnSpeech.Clear(); - } - } - - private static VisibleDamageType m_VisibleDamageType; + switch (type) + { + case TotalType.Gold: + m_TotalGold += delta; + Delta(MobileDelta.Gold); + break; - public static VisibleDamageType VisibleDamageType - { - get => m_VisibleDamageType; - set => m_VisibleDamageType = value; - } - - private List m_DamageEntries; - - public List DamageEntries => m_DamageEntries; - - public static Mobile GetDamagerFrom( DamageEntry de ) - { - return (de == null ? null : de.Damager); - } - - public Mobile FindMostRecentDamager( bool allowSelf ) - { - return GetDamagerFrom( FindMostRecentDamageEntry( allowSelf ) ); - } + case TotalType.Items: + m_TotalItems += delta; + break; - public DamageEntry FindMostRecentDamageEntry( bool allowSelf ) - { - for( int i = m_DamageEntries.Count - 1; i >= 0; --i ) - { - if ( i >= m_DamageEntries.Count ) - continue; + case TotalType.Weight: + m_TotalWeight += delta; + Delta(MobileDelta.Weight); + OnWeightChange(m_TotalWeight - delta); + break; + } + } - DamageEntry de = m_DamageEntries[i]; - - if ( de.HasExpired ) - m_DamageEntries.RemoveAt( i ); - else if ( allowSelf || de.Damager != this ) - return de; - } - - return null; - } - - public Mobile FindLeastRecentDamager( bool allowSelf ) - { - return GetDamagerFrom( FindLeastRecentDamageEntry( allowSelf ) ); - } - - public DamageEntry FindLeastRecentDamageEntry( bool allowSelf ) - { - for( int i = 0; i < m_DamageEntries.Count; ++i ) - { - if ( i < 0 ) - continue; - - DamageEntry de = m_DamageEntries[i]; - - if ( de.HasExpired ) - { - m_DamageEntries.RemoveAt( i ); - --i; - } - else if ( allowSelf || de.Damager != this ) - { - return de; - } - } - - return null; - } - - public Mobile FindMostTotalDamger( bool allowSelf ) - { - return GetDamagerFrom( FindMostTotalDamageEntry( allowSelf ) ); - } - - public DamageEntry FindMostTotalDamageEntry( bool allowSelf ) - { - DamageEntry mostTotal = null; - - for( int i = m_DamageEntries.Count - 1; i >= 0; --i ) - { - if ( i >= m_DamageEntries.Count ) - continue; - - DamageEntry de = m_DamageEntries[i]; - - if ( de.HasExpired ) - m_DamageEntries.RemoveAt( i ); - else if ( (allowSelf || de.Damager != this) && (mostTotal == null || de.DamageGiven > mostTotal.DamageGiven) ) - mostTotal = de; - } - - return mostTotal; - } - - public Mobile FindLeastTotalDamger( bool allowSelf ) - { - return GetDamagerFrom( FindLeastTotalDamageEntry( allowSelf ) ); - } - - public DamageEntry FindLeastTotalDamageEntry( bool allowSelf ) - { - DamageEntry mostTotal = null; - - for( int i = m_DamageEntries.Count - 1; i >= 0; --i ) - { - if ( i >= m_DamageEntries.Count ) - continue; - - DamageEntry de = m_DamageEntries[i]; - - if ( de.HasExpired ) - m_DamageEntries.RemoveAt( i ); - else if ( (allowSelf || de.Damager != this) && (mostTotal == null || de.DamageGiven < mostTotal.DamageGiven) ) - mostTotal = de; - } - - return mostTotal; - } - - public DamageEntry FindDamageEntryFor( Mobile m ) - { - for( int i = m_DamageEntries.Count - 1; i >= 0; --i ) - { - if ( i >= m_DamageEntries.Count ) - continue; - - DamageEntry de = m_DamageEntries[i]; - - if ( de.HasExpired ) - m_DamageEntries.RemoveAt( i ); - else if ( de.Damager == m ) - return de; - } - - return null; - } - - public virtual Mobile GetDamageMaster( Mobile damagee ) - { - return null; - } - - public virtual DamageEntry RegisterDamage( int amount, Mobile from ) - { - DamageEntry de = FindDamageEntryFor( from ); - - if ( de == null ) - de = new DamageEntry( from ); - - de.DamageGiven += amount; - de.LastDamage = DateTime.UtcNow; - - m_DamageEntries.Remove( de ); - m_DamageEntries.Add( de ); - - Mobile master = from.GetDamageMaster( this ); - - if ( master != null ) - { - List list = de.Responsible; - - if ( list == null ) - de.Responsible = list = new List(); - - DamageEntry resp = null; - - for( int i = 0; i < list.Count; ++i ) - { - DamageEntry check = list[i]; - - if ( check.Damager == master ) - { - resp = check; - break; - } - } - - if ( resp == null ) - list.Add( resp = new DamageEntry( master ) ); - - resp.DamageGiven += amount; - resp.LastDamage = DateTime.UtcNow; - } - - return de; - } - - private Mobile m_LastKiller; - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile LastKiller - { - get => m_LastKiller; - set => m_LastKiller = value; - } - - /// - /// Overridable. Virtual event invoked when the Mobile is damaged. It is called before hit points are lowered or the Mobile is killed. - /// - /// - /// - /// - public virtual void OnDamage( int amount, Mobile from, bool willKill ) - { - } - - public virtual void Damage( int amount ) - { - Damage( amount, null ); - } - - public virtual bool CanBeDamaged() - { - return !m_Blessed; - } - - public virtual void Damage( int amount, Mobile from ) - { - Damage( amount, from, true ); - } - - public virtual void Damage( int amount, Mobile from, bool informMount ) - { - if ( !CanBeDamaged() || m_Deleted ) - return; - - if ( !Region.OnDamage( this, ref amount ) ) - return; - - if ( amount > 0 ) - { - int oldHits = Hits; - int newHits = oldHits - amount; - - m_Spell?.OnCasterHurt(); - - //if ( m_Spell != null && m_Spell.State == SpellState.Casting ) - // m_Spell.Disturb( DisturbType.Hurt, false, true ); - - if ( from != null ) - RegisterDamage( amount, from ); - - DisruptiveAction(); - - Paralyzed = false; - - switch( m_VisibleDamageType ) - { - case VisibleDamageType.Related: - { - SendVisibleDamageRelated(from, amount); - break; - } - case VisibleDamageType.Everyone: - { - SendVisibleDamageEveryone(amount); - break; - } - case VisibleDamageType.Selective: - { - SendVisibleDamageSelective(from, amount); - break; - } - } - - OnDamage( amount, from, newHits < 0 ); - - IMount m = Mount; - if ( m != null && informMount ) - m.OnRiderDamaged( amount, from, newHits < 0 ); - - if ( newHits < 0 ) - { - m_LastKiller = from; - - Hits = 0; - - if ( oldHits >= 0 ) - Kill(); - } - else - { - Hits = newHits; - } - } - } - - public void SendVisibleDamageRelated(Mobile from, int amount) - { - NetState ourState = m_NetState, theirState = from?.m_NetState; - - if (ourState == null) - { - Mobile master = GetDamageMaster(from); - - if (master != null) - ourState = master.m_NetState; - } - - if (theirState == null && from != null) - { - Mobile master = from.GetDamageMaster(this); - - if (master != null) - theirState = master.m_NetState; - } - - if (amount > 0 && (ourState != null || theirState != null)) - { - Packet p = null;// = new DamagePacket( this, amount ); - - if (ourState != null) - { - if (ourState.DamagePacket) - p = Packet.Acquire(new DamagePacket(this, amount)); - else - p = Packet.Acquire(new DamagePacketOld(this, amount)); - - ourState.Send(p); - } - - if (theirState != null && theirState != ourState) - { - bool newPacket = theirState.DamagePacket; - - if (newPacket && !(p is DamagePacket)) - { - Packet.Release(p); - p = Packet.Acquire(new DamagePacket(this, amount)); - } - else if (!newPacket && !(p is DamagePacketOld)) - { - Packet.Release(p); - p = Packet.Acquire(new DamagePacketOld(this, amount)); - } - - theirState.Send(p); - } - - Packet.Release(p); - } - } - - public void SendVisibleDamageEveryone(int amount) - { - if ( amount < 0 ) - return; - - Map map = m_Map; - - if ( map == null ) - return; - - IPooledEnumerable eable = map.GetClientsInRange(m_Location); - - Packet pNew = null; - Packet pOld = null; - - foreach( NetState ns in eable ) { - if ( ns.Mobile.CanSee( this ) ) { - if ( ns.DamagePacket ) { - if ( pNew == null ) - pNew = Packet.Acquire( new DamagePacket( this, amount ) ); - - ns.Send( pNew ); - } else { - if ( pOld == null ) - pOld = Packet.Acquire( new DamagePacketOld( this, amount ) ); - - ns.Send( pOld ); - } - } - } - - Packet.Release( pNew ); - Packet.Release( pOld ); - - eable.Free(); - } - - public static bool m_DefaultShowVisibleDamage, m_DefaultCanSeeVisibleDamage; - - public static bool DefaultShowVisibleDamage { get => m_DefaultShowVisibleDamage; - set => m_DefaultShowVisibleDamage = value; - } - public static bool DefaultCanSeeVisibleDamage { get => m_DefaultCanSeeVisibleDamage; - set => m_DefaultCanSeeVisibleDamage = value; - } - - public virtual bool ShowVisibleDamage => m_DefaultShowVisibleDamage; - public virtual bool CanSeeVisibleDamage => m_DefaultCanSeeVisibleDamage; - - public void SendVisibleDamageSelective(Mobile from, int amount) - { - NetState ourState = m_NetState, theirState = (from == null ? null : from.m_NetState); - - Mobile damager = from; - Mobile damaged = this; - - if (ourState == null) - { - Mobile master = GetDamageMaster(from); - - if (master != null) - { - damaged = master; - ourState = master.m_NetState; - } - } - - if (!damaged.ShowVisibleDamage) - return; - - if (theirState == null && from != null) - { - Mobile master = from.GetDamageMaster(this); - - if (master != null) - { - damager = master; - theirState = master.m_NetState; - } - } - - if (amount > 0 && (ourState != null || theirState != null)) - { - if (damaged.CanSeeVisibleDamage && ourState != null) - { - if (ourState.DamagePacket) - ourState.Send(new DamagePacket(this, amount)); - else - ourState.Send(new DamagePacketOld(this, amount)); - } - - if (theirState != null && theirState != ourState && damager.CanSeeVisibleDamage) - { - if (theirState.DamagePacket) - theirState.Send(new DamagePacket(this, amount)); - else - theirState.Send(new DamagePacketOld(this, amount)); - } - } - } - - public void Heal( int amount ) - { - Heal( amount, this, true ); - } - - public void Heal( int amount, Mobile from ) - { - Heal( amount, from, true ); - } - - public void Heal( int amount, Mobile from, bool message ) - { - if ( !Alive || IsDeadBondedPet ) - return; - - if ( !Region.OnHeal( this, ref amount ) ) - return; - - OnHeal( ref amount, from ); - - if ( (Hits + amount) > HitsMax ) - { - amount = HitsMax - Hits; - } - - Hits += amount; - - if ( message && amount > 0 ) - m_NetState?.Send( new MessageLocalizedAffix( Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008158, "", AffixType.Append | AffixType.System, amount.ToString(), "" ) ); - } - - public virtual void OnHeal( ref int amount, Mobile from ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Squelched - { - get => m_Squelched; - set => m_Squelched = value; - } - - public virtual void Deserialize( GenericReader reader ) - { - int version = reader.ReadInt(); - - switch( version ) - { - case 32: - { - // Removed StuckMenu - goto case 31; - } - case 31: - { - m_LastStrGain = reader.ReadDeltaTime(); - m_LastIntGain = reader.ReadDeltaTime(); - m_LastDexGain = reader.ReadDeltaTime(); - - goto case 30; - } - case 30: - { - byte hairflag = reader.ReadByte(); - - if ( (hairflag & 0x01) != 0 ) - m_Hair = new HairInfo( reader ); - if ( (hairflag & 0x02) != 0 ) - m_FacialHair = new FacialHairInfo( reader ); - - goto case 29; - } - case 29: - { - m_Race = reader.ReadRace(); - goto case 28; - } - case 28: - { - if ( version <= 30 ) - LastStatGain = reader.ReadDeltaTime(); - - goto case 27; - } - case 27: - { - m_TithingPoints = reader.ReadInt(); - - goto case 26; - } - case 26: - case 25: - case 24: - { - m_Corpse = reader.ReadItem() as Container; - - goto case 23; - } - case 23: - { - m_CreationTime = reader.ReadDateTime(); - - goto case 22; - } - case 22: // Just removed followers - case 21: - { - m_Stabled = reader.ReadStrongMobileList(); - - goto case 20; - } - case 20: - { - m_CantWalk = reader.ReadBool(); - - goto case 19; - } - case 19: // Just removed variables - case 18: - { - m_Virtues = new VirtueInfo( reader ); - - goto case 17; - } - case 17: - { - m_Thirst = reader.ReadInt(); - m_BAC = reader.ReadInt(); - - goto case 16; - } - case 16: - { - m_ShortTermMurders = reader.ReadInt(); - - if ( version <= 24 ) - { - reader.ReadDateTime(); - reader.ReadDateTime(); - } - - goto case 15; - } - case 15: - { - if ( version < 22 ) - reader.ReadInt(); // followers - - m_FollowersMax = reader.ReadInt(); - - goto case 14; - } - case 14: - { - m_MagicDamageAbsorb = reader.ReadInt(); - - goto case 13; - } - case 13: - { - m_GuildFealty = reader.ReadMobile(); - - goto case 12; - } - case 12: - { - m_Guild = reader.ReadGuild(); - - goto case 11; - } - case 11: - { - m_DisplayGuildTitle = reader.ReadBool(); - - goto case 10; - } - case 10: - { - m_CanSwim = reader.ReadBool(); - - goto case 9; - } - case 9: - { - m_Squelched = reader.ReadBool(); - - goto case 8; - } - case 8: - { - m_Holding = reader.ReadItem(); - - goto case 7; - } - case 7: - { - m_VirtualArmor = reader.ReadInt(); - - goto case 6; - } - case 6: - { - m_BaseSoundID = reader.ReadInt(); - - goto case 5; - } - case 5: - { - m_DisarmReady = reader.ReadBool(); - m_StunReady = reader.ReadBool(); - - goto case 4; - } - case 4: - { - if ( version <= 25 ) - { - Poison.Deserialize( reader ); - } - - goto case 3; - } - case 3: - { - m_StatCap = reader.ReadInt(); - - goto case 2; - } - case 2: - { - m_NameHue = reader.ReadInt(); - - goto case 1; - } - case 1: - { - m_Hunger = reader.ReadInt(); - - goto case 0; - } - case 0: - { - if ( version < 21 ) - m_Stabled = new List(); - - if ( version < 18 ) - m_Virtues = new VirtueInfo(); - - if ( version < 11 ) - m_DisplayGuildTitle = true; - - if ( version < 3 ) - m_StatCap = 225; - - if ( version < 15 ) - { - m_Followers = 0; - m_FollowersMax = 5; - } - - m_Location = reader.ReadPoint3D(); - m_Body = new Body( reader.ReadInt() ); - m_Name = reader.ReadString(); - m_GuildTitle = reader.ReadString(); - m_Criminal = reader.ReadBool(); - m_Kills = reader.ReadInt(); - m_SpeechHue = reader.ReadInt(); - m_EmoteHue = reader.ReadInt(); - m_WhisperHue = reader.ReadInt(); - m_YellHue = reader.ReadInt(); - m_Language = reader.ReadString(); - m_Female = reader.ReadBool(); - m_Warmode = reader.ReadBool(); - m_Hidden = reader.ReadBool(); - m_Direction = (Direction)reader.ReadByte(); - m_Hue = reader.ReadInt(); - m_Str = reader.ReadInt(); - m_Dex = reader.ReadInt(); - m_Int = reader.ReadInt(); - m_Hits = reader.ReadInt(); - m_Stam = reader.ReadInt(); - m_Mana = reader.ReadInt(); - m_Map = reader.ReadMap(); - m_Blessed = reader.ReadBool(); - m_Fame = reader.ReadInt(); - m_Karma = reader.ReadInt(); - m_AccessLevel = (AccessLevel)reader.ReadByte(); - - m_Skills = new Skills( this, reader ); - - m_Items = reader.ReadStrongItemList(); - - m_Player = reader.ReadBool(); - m_Title = reader.ReadString(); - m_Profile = reader.ReadString(); - m_ProfileLocked = reader.ReadBool(); - - if ( version <= 18 ) - { - reader.ReadInt(); - reader.ReadInt(); - reader.ReadInt(); - } - - m_AutoPageNotify = reader.ReadBool(); - - m_LogoutLocation = reader.ReadPoint3D(); - m_LogoutMap = reader.ReadMap(); - - m_StrLock = (StatLockType)reader.ReadByte(); - m_DexLock = (StatLockType)reader.ReadByte(); - m_IntLock = (StatLockType)reader.ReadByte(); - - m_StatMods = new List(); - m_SkillMods = new List(); - - if (version < 32) - { - if (reader.ReadBool()) - { - int count = reader.ReadInt(); - for (int i = 0; i < count; ++i) - { - reader.ReadDateTime(); - } - } - } - - if ( m_Player && m_Map != Map.Internal ) - { - m_LogoutLocation = m_Location; - m_LogoutMap = m_Map; - - m_Map = Map.Internal; - } - - m_Map?.OnEnter( this ); - - if ( m_Criminal ) - { - if ( m_ExpireCriminal == null ) - m_ExpireCriminal = new ExpireCriminalTimer( this ); - - m_ExpireCriminal.Start(); - } - - if ( ShouldCheckStatTimers ) - CheckStatTimers(); - - if ( !m_Player && m_Dex <= 100 && m_CombatTimer != null ) - m_CombatTimer.Priority = TimerPriority.FiftyMS; - else if ( m_CombatTimer != null ) - m_CombatTimer.Priority = TimerPriority.EveryTick; - - UpdateRegion(); - - UpdateResistances(); - - break; - } - } - - if ( !m_Player ) - Utility.Intern( ref m_Name ); - - Utility.Intern( ref m_Title ); - Utility.Intern( ref m_Language ); - - /* //Moved into cleanup in scripts. - if ( version < 30 ) - Timer.DelayCall( TimeSpan.Zero, new TimerCallback( ConvertHair ) ); - * */ - - } - - public void ConvertHair() - { - Item hair; - - if ( (hair = FindItemOnLayer( Layer.Hair )) != null ) - { - HairItemID = hair.ItemID; - HairHue = hair.Hue; - hair.Delete(); - } - - if ( (hair = FindItemOnLayer( Layer.FacialHair )) != null ) - { - FacialHairItemID = hair.ItemID; - FacialHairHue = hair.Hue; - hair.Delete(); - } - } - - public virtual bool ShouldCheckStatTimers => true; - - public virtual void CheckStatTimers() - { - if ( m_Deleted ) - return; - - if ( Hits < HitsMax ) - { - if ( CanRegenHits ) - { - if ( m_HitsTimer == null ) - m_HitsTimer = new HitsTimer( this ); - - m_HitsTimer.Start(); - } - else - { - m_HitsTimer?.Stop(); - } - } - else - { - Hits = HitsMax; - } - - if ( Stam < StamMax ) - { - if ( CanRegenStam ) - { - if ( m_StamTimer == null ) - m_StamTimer = new StamTimer( this ); + public virtual void UpdateTotals() + { + if (Items == null) + return; - m_StamTimer.Start(); - } - else - { - m_StamTimer?.Stop(); - } - } - else - { - Stam = StamMax; - } + int oldWeight = m_TotalWeight; - if ( Mana < ManaMax ) - { - if ( CanRegenMana ) - { - if ( m_ManaTimer == null ) - m_ManaTimer = new ManaTimer( this ); + m_TotalGold = 0; + m_TotalItems = 0; + m_TotalWeight = 0; - m_ManaTimer.Start(); - } - else - { - m_ManaTimer?.Stop(); - } - } - else - { - Mana = ManaMax; - } - } + for (int i = 0; i < Items.Count; ++i) + { + Item item = Items[i]; - private DateTime m_CreationTime; + item.UpdateTotals(); - [CommandProperty( AccessLevel.GameMaster )] - public DateTime CreationTime => m_CreationTime; - - int ISerializable.TypeReference => m_TypeRef; - - int ISerializable.SerialIdentity => m_Serial; + if (item.IsVirtualItem) + continue; - public virtual void Serialize( GenericWriter writer ) - { - writer.Write( (int)32 ); // version - - writer.WriteDeltaTime( m_LastStrGain ); - writer.WriteDeltaTime( m_LastIntGain ); - writer.WriteDeltaTime( m_LastDexGain ); - - byte hairflag = 0x00; - - if ( m_Hair != null ) - hairflag |= 0x01; - if ( m_FacialHair != null ) - hairflag |= 0x02; - - writer.Write( (byte)hairflag ); + m_TotalGold += item.TotalGold; + m_TotalItems += item.TotalItems + 1; + m_TotalWeight += item.TotalWeight + item.PileWeight; + } - if ( (hairflag & 0x01) != 0 ) - m_Hair.Serialize( writer ); - if ( (hairflag & 0x02) != 0 ) - m_FacialHair.Serialize( writer ); + if (m_Holding != null) + m_TotalWeight += m_Holding.TotalWeight + m_Holding.PileWeight; - writer.Write( Race ); + if (m_TotalWeight != oldWeight) + OnWeightChange(oldWeight); + } - writer.Write( (int)m_TithingPoints ); + public void ClearQuestArrow() + { + m_QuestArrow = null; + } - writer.Write( m_Corpse ); - - writer.Write( m_CreationTime ); - - writer.Write( m_Stabled, true ); - - writer.Write( m_CantWalk ); - - VirtueInfo.Serialize( writer, m_Virtues ); - - writer.Write( m_Thirst ); - writer.Write( m_BAC ); - - writer.Write( m_ShortTermMurders ); - //writer.Write( m_ShortTermElapse ); - //writer.Write( m_LongTermElapse ); - - //writer.Write( m_Followers ); - writer.Write( m_FollowersMax ); - - writer.Write( m_MagicDamageAbsorb ); + public void ClearTarget() + { + m_Target = null; + } - writer.Write( m_GuildFealty ); + public Target BeginTarget(int range, bool allowGround, TargetFlags flags, TargetCallback callback) + { + Target t = new SimpleTarget(range, flags, allowGround, callback); - writer.Write( m_Guild ); + Target = t; - writer.Write( m_DisplayGuildTitle ); + return t; + } - writer.Write( m_CanSwim ); + public Target BeginTarget(int range, bool allowGround, TargetFlags flags, TargetStateCallback callback, object state) + { + Target t = new SimpleStateTarget(range, flags, allowGround, callback, state); - writer.Write( m_Squelched ); + Target = t; - writer.Write( m_Holding ); - - writer.Write( m_VirtualArmor ); - - writer.Write( m_BaseSoundID ); + return t; + } - writer.Write( m_DisarmReady ); - writer.Write( m_StunReady ); + public Target BeginTarget(int range, bool allowGround, TargetFlags flags, TargetStateCallback callback, + T state) + { + Target t = new SimpleStateTarget(range, flags, allowGround, callback, state); - //Poison.Serialize( m_Poison, writer ); + Target = t; + + return t; + } + + /// + /// Overridable. Virtual event invoked after the Target property has changed. + /// + protected virtual void OnTargetChange() + { + } + + public virtual bool CheckContextMenuDisplay(IEntity target) + { + return true; + } + + private bool InternalOnMove(Direction d) + { + if (!OnMove(d)) + return false; + + MovementEventArgs e = MovementEventArgs.Create(this, d); + + EventSink.InvokeMovement(e); + + bool ret = !e.Blocked; + + e.Free(); + + return ret; + } + + /// + /// Overridable. Event invoked before the Mobile moves. + /// + /// True if the move is allowed, false if not. + protected virtual bool OnMove(Direction d) + { + if (m_Hidden && m_AccessLevel == AccessLevel.Player) + if (AllowedStealthSteps-- <= 0 || (d & Direction.Running) != 0 || Mounted) + RevealingAction(); + + return true; + } + + public virtual void ClearFastwalkStack() + { + if (m_MoveRecords != null && m_MoveRecords.Count > 0) + m_MoveRecords.Clear(); + + m_EndQueue = Core.TickCount; + } + + public virtual bool CheckMovement(Direction d, out int newZ) + { + return Movement.Movement.CheckMovement(this, d, out newZ); + } + + public virtual bool Move(Direction d) + { + if (Deleted) + return false; + + BankBox box = FindBankNoCreate(); + + if (box != null && box.Opened) + box.Close(); + + Point3D newLocation = m_Location; + Point3D oldLocation = newLocation; + + if ((m_Direction & Direction.Mask) == (d & Direction.Mask)) + { + // We are actually moving (not just a direction change) + + if (m_Spell != null && !m_Spell.OnCasterMoving(d)) + return false; + + if (m_Paralyzed || m_Frozen) + { + SendLocalizedMessage(500111); // You are frozen and can not move. + + return false; + } + + if (CheckMovement(d, out int newZ)) + { + int x = oldLocation.m_X, y = oldLocation.m_Y; + int oldX = x, oldY = y; + int oldZ = oldLocation.m_Z; + + switch (d & Direction.Mask) + { + case Direction.North: + --y; + break; + case Direction.Right: + ++x; + --y; + break; + case Direction.East: + ++x; + break; + case Direction.Down: + ++x; + ++y; + break; + case Direction.South: + ++y; + break; + case Direction.Left: + --x; + ++y; + break; + case Direction.West: + --x; + break; + case Direction.Up: + --x; + --y; + break; + } + + newLocation.m_X = x; + newLocation.m_Y = y; + newLocation.m_Z = newZ; + + Pushing = false; + + Map map = m_Map; + + if (map != null) + { + Sector oldSector = map.GetSector(oldX, oldY); + Sector newSector = map.GetSector(x, y); + + if (oldSector != newSector) + { + for (int i = 0; i < oldSector.Mobiles.Count; ++i) + { + Mobile m = oldSector.Mobiles[i]; + + if (m != this && m.X == oldX && m.Y == oldY && m.Z + 15 > oldZ && oldZ + 15 > m.Z && + !m.OnMoveOff(this)) + return false; + } + + for (int i = 0; i < oldSector.Items.Count; ++i) + { + Item item = oldSector.Items[i]; + + if (item.AtWorldPoint(oldX, oldY) && + (item.Z == oldZ || item.Z + item.ItemData.Height > oldZ && oldZ + 15 > item.Z) && + !item.OnMoveOff(this)) + return false; + } + + for (int i = 0; i < newSector.Mobiles.Count; ++i) + { + Mobile m = newSector.Mobiles[i]; + + if (m.X == x && m.Y == y && m.Z + 15 > newZ && newZ + 15 > m.Z && !m.OnMoveOver(this)) + return false; + } + + for (int i = 0; i < newSector.Items.Count; ++i) + { + Item item = newSector.Items[i]; + + if (item.AtWorldPoint(x, y) && + (item.Z == newZ || item.Z + item.ItemData.Height > newZ && newZ + 15 > item.Z) && + !item.OnMoveOver(this)) + return false; + } + } + else + { + for (int i = 0; i < oldSector.Mobiles.Count; ++i) + { + Mobile m = oldSector.Mobiles[i]; + + if (m != this && m.X == oldX && m.Y == oldY && m.Z + 15 > oldZ && oldZ + 15 > m.Z && + !m.OnMoveOff(this)) + return false; + if (m.X == x && m.Y == y && m.Z + 15 > newZ && newZ + 15 > m.Z && !m.OnMoveOver(this)) + return false; + } + + for (int i = 0; i < oldSector.Items.Count; ++i) + { + Item item = oldSector.Items[i]; + + if (item.AtWorldPoint(oldX, oldY) && + (item.Z == oldZ || item.Z + item.ItemData.Height > oldZ && oldZ + 15 > item.Z) && + !item.OnMoveOff(this)) + return false; + if (item.AtWorldPoint(x, y) && + (item.Z == newZ || item.Z + item.ItemData.Height > newZ && newZ + 15 > item.Z) && + !item.OnMoveOver(this)) + return false; + } + } + + if (!Region.CanMove(this, d, newLocation, oldLocation, m_Map)) + return false; + } + else + { + return false; + } + + if (!InternalOnMove(d)) + return false; + + if (FwdEnabled && m_NetState != null && m_AccessLevel < FwdAccessOverride && + (!FwdUOTDOverride || !m_NetState.IsUOTDClient)) + { + if (m_MoveRecords == null) + m_MoveRecords = new Queue(6); + + while (m_MoveRecords.Count > 0) + { + MovementRecord r = m_MoveRecords.Peek(); + + if (r.Expired()) + m_MoveRecords.Dequeue(); + else + break; + } + + if (m_MoveRecords.Count >= FwdMaxSteps) + { + FastWalkEventArgs fw = new FastWalkEventArgs(m_NetState); + EventSink.InvokeFastWalk(fw); + + if (fw.Blocked) + return false; + } + + int delay = ComputeMovementSpeed(d); + + long end; + + if (m_MoveRecords.Count > 0) + end = m_EndQueue + delay; + else + end = Core.TickCount + delay; + + m_MoveRecords.Enqueue(MovementRecord.NewInstance(end)); + + m_EndQueue = end; + } + + LastMoveTime = Core.TickCount; + } + else + { + return false; + } + + DisruptiveAction(); + } + + m_NetState?.Send(MovementAck.Instantiate(m_NetState.Sequence, + this)); //new MovementAck( m_NetState.Sequence, this ) ); + + SetLocation(newLocation, false); + SetDirection(d); + + if (m_Map != null) + { + IPooledEnumerable eable = m_Map.GetObjectsInRange(m_Location, Core.GlobalMaxUpdateRange); + + foreach (IEntity o in eable) + { + if (o == this) + continue; + + if (o is Mobile mob) + { + if (mob.NetState != null) + m_MoveClientList.Add(mob); + m_MoveList.Add(mob); + } + else if (o is Item item && item.HandlesOnMovement) + { + m_MoveList.Add(item); + } + } + + eable.Free(); + + Packet[][] cache = m_MovingPacketCache; + + /*for( int i = 0; i < cache.Length; ++i ) + for( int j = 0; j < cache[i].Length; ++j ) + Packet.Release( ref cache[i][j] );*/ + + foreach (Mobile m in m_MoveClientList) + { + NetState ns = m.NetState; + + if (ns != null && Utility.InUpdateRange(m_Location, m.m_Location) && m.CanSee(this)) + { + if (ns.StygianAbyss) + { + Packet p; + int noto = Notoriety.Compute(m, this); + p = cache[0][noto]; + + if (p == null) + cache[0][noto] = p = Packet.Acquire(new MobileMoving(this, noto)); + + ns.Send(p); + } + else + { + Packet p; + int noto = Notoriety.Compute(m, this); + p = cache[1][noto]; + + if (p == null) + cache[1][noto] = p = Packet.Acquire(new MobileMovingOld(this, noto)); + + ns.Send(p); + } + } + } + + for (int i = 0; i < cache.Length; ++i) + for (int j = 0; j < cache[i].Length; ++j) + Packet.Release(ref cache[i][j]); + + for (int i = 0; i < m_MoveList.Count; ++i) + { + IEntity o = m_MoveList[i]; + + if (o is Mobile mobile) + mobile.OnMovement(this, oldLocation); + else if (o is Item item) item.OnMovement(this, oldLocation); + } + + if (m_MoveList.Count > 0) + m_MoveList.Clear(); + + if (m_MoveClientList.Count > 0) + m_MoveClientList.Clear(); + } + + OnAfterMove(oldLocation); + return true; + } + + public virtual void OnAfterMove(Point3D oldLocation) + { + } + + public int ComputeMovementSpeed() + { + return ComputeMovementSpeed(Direction, false); + } + + public int ComputeMovementSpeed(Direction dir) + { + return ComputeMovementSpeed(dir, true); + } + + public virtual int ComputeMovementSpeed(Direction dir, bool checkTurning) + { + int delay; + + if (Mounted) + delay = (dir & Direction.Running) != 0 ? RunMount : WalkMount; + else + delay = (dir & Direction.Running) != 0 ? RunFoot : WalkFoot; + + return delay; + } + + /// + /// Overridable. Virtual event invoked when a Mobile moves off this Mobile. + /// + /// True if the move is allowed, false if not. + public virtual bool OnMoveOff(Mobile m) + { + return true; + } + + /// + /// Overridable. Event invoked when a Mobile moves over this Mobile. + /// + /// True if the move is allowed, false if not. + public virtual bool OnMoveOver(Mobile m) + { + if (m_Map == null || Deleted) + return true; + + return m.CheckShove(this); + } + + public virtual bool CheckShove(Mobile shoved) + { + if ((m_Map.Rules & MapRules.FreeMovement) == 0) + { + if (!shoved.Alive || !Alive || shoved.IsDeadBondedPet || IsDeadBondedPet) + return true; + if (shoved.m_Hidden && shoved.m_AccessLevel > AccessLevel.Player) + return true; + + if (!Pushing) + { + Pushing = true; + + int number; + + if (AccessLevel > AccessLevel.Player) + { + number = shoved.m_Hidden ? 1019041 : 1019040; + } + else + { + if (Stam == StamMax) + { + number = shoved.m_Hidden ? 1019043 : 1019042; + Stam -= 10; + + RevealingAction(); + } + else + { + return false; + } + } + + SendLocalizedMessage(number); + } + } + + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile sees another Mobile, , move. + /// + public virtual void OnMovement(Mobile m, Point3D oldLocation) + { + } + + public virtual void CriminalAction(bool message) + { + if (Deleted) + return; + + Criminal = true; + + Region.OnCriminalAction(this, message); + } + + public virtual bool IsSnoop(Mobile from) + { + return from != this; + } + + /// + /// Overridable. Any call to will silently fail if this method returns false. + /// + /// + public virtual bool CheckResurrect() + { + return true; + } + + /// + /// Overridable. Event invoked before the Mobile is resurrected. + /// + /// + public virtual void OnBeforeResurrect() + { + } + + /// + /// Overridable. Event invoked after the Mobile is resurrected. + /// + /// + public virtual void OnAfterResurrect() + { + } + + public virtual void Resurrect() + { + if (!Alive) + { + if (!Region.OnResurrect(this)) + return; + + if (!CheckResurrect()) + return; + + OnBeforeResurrect(); + + BankBox box = FindBankNoCreate(); + + if (box != null && box.Opened) + box.Close(); + + Poison = null; + + Warmode = false; + + Hits = 10; + Stam = StamMax; + Mana = 0; + + BodyMod = 0; + Body = Race.AliveBody(this); + + ProcessDeltaQueue(); + + for (int i = Items.Count - 1; i >= 0; --i) + { + if (i >= Items.Count) + continue; - writer.Write( m_StatCap ); + Item item = Items[i]; - writer.Write( m_NameHue ); + if (item.ItemID == 0x204E) + item.Delete(); + } - writer.Write( m_Hunger ); + SendIncomingPacket(); + SendIncomingPacket(); - writer.Write( m_Location ); - writer.Write( (int)m_Body ); - writer.Write( m_Name ); - writer.Write( m_GuildTitle ); - writer.Write( m_Criminal ); - writer.Write( m_Kills ); - writer.Write( m_SpeechHue ); - writer.Write( m_EmoteHue ); - writer.Write( m_WhisperHue ); - writer.Write( m_YellHue ); - writer.Write( m_Language ); - writer.Write( m_Female ); - writer.Write( m_Warmode ); - writer.Write( m_Hidden ); - writer.Write( (byte)m_Direction ); - writer.Write( m_Hue ); - writer.Write( m_Str ); - writer.Write( m_Dex ); - writer.Write( m_Int ); - writer.Write( m_Hits ); - writer.Write( m_Stam ); - writer.Write( m_Mana ); - - writer.Write( m_Map ); - - writer.Write( m_Blessed ); - writer.Write( m_Fame ); - writer.Write( m_Karma ); - writer.Write( (byte)m_AccessLevel ); - m_Skills.Serialize( writer ); - - writer.Write( m_Items ); - - writer.Write( m_Player ); - writer.Write( m_Title ); - writer.Write( m_Profile ); - writer.Write( m_ProfileLocked ); - writer.Write( m_AutoPageNotify ); - - writer.Write( m_LogoutLocation ); - writer.Write( m_LogoutMap ); - - writer.Write( (byte)m_StrLock ); - writer.Write( (byte)m_DexLock ); - writer.Write( (byte)m_IntLock ); - } - - [CommandProperty( AccessLevel.GameMaster )] - public int LightLevel - { - get => m_LightLevel; - set - { - if ( m_LightLevel != value ) - { - m_LightLevel = value; - - CheckLightLevels( false ); - - /*if ( m_NetState != null ) - m_NetState.Send( new PersonalLightLevel( this ) );*/ - } - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public string Profile - { - get => m_Profile; - set => m_Profile = value; - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public bool ProfileLocked - { - get => m_ProfileLocked; - set => m_ProfileLocked = value; - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Administrator )] - public bool Player - { - get => m_Player; - set - { - m_Player = value; - InvalidateProperties(); - - if ( !m_Player && m_Dex <= 100 && m_CombatTimer != null ) - m_CombatTimer.Priority = TimerPriority.FiftyMS; - else if ( m_CombatTimer != null ) - m_CombatTimer.Priority = TimerPriority.EveryTick; - - CheckStatTimers(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string Title - { - get => m_Title; - set - { - m_Title = value; - InvalidateProperties(); - } - } - - private static string[] m_AccessLevelNames = new[] - { - "a player", - "a counselor", - "a game master", - "a seer", - "an administrator", - "a developer", - "an owner" - }; - - public static string GetAccessLevelName( AccessLevel level ) - { - return m_AccessLevelNames[(int)level]; - } - - public virtual bool CanPaperdollBeOpenedBy( Mobile from ) - { - return (Body.IsHuman || Body.IsGhost || IsBodyMod); - } - - public virtual void GetChildContextMenuEntries( Mobile from, List list, Item item ) - { - } - - public virtual void GetContextMenuEntries( Mobile from, List list ) - { - if ( m_Deleted ) - return; - - if ( CanPaperdollBeOpenedBy( from ) ) - list.Add( new PaperdollEntry( this ) ); - - if ( from == this && Backpack != null && CanSee( Backpack ) && CheckAlive( false ) ) - list.Add( new OpenBackpackEntry( this ) ); - } - - public void Internalize() - { - Map = Map.Internal; - } - - public List Items => m_Items; - - /// - /// Overridable. Virtual event invoked when is added from the Mobile, such as when it is equipped. - /// - /// - /// - public virtual void OnItemAdded( Item item ) - { - } - - /// - /// Overridable. Virtual event invoked when is removed from the Mobile. - /// - /// - /// - public virtual void OnItemRemoved( Item item ) - { - } - - /// - /// Overridable. Virtual event invoked when is becomes a child of the Mobile; it's worn or contained at some level of the Mobile's backpack or bank box - /// - /// - /// - public virtual void OnSubItemAdded( Item item ) - { - } - - /// - /// Overridable. Virtual event invoked when is removed from the Mobile, its backpack, or its bank box. - /// - /// - /// - public virtual void OnSubItemRemoved( Item item ) - { - } - - public virtual void OnItemBounceCleared( Item item ) - { - } - - public virtual void OnSubItemBounceCleared( Item item ) - { - } - - public virtual int MaxWeight => int.MaxValue; - - public void AddItem( Item item ) - { - if ( item == null || item.Deleted ) - return; - - if ( item.Parent == this ) - return; - if ( item.Parent is Mobile parentMobile ) - parentMobile.RemoveItem( item ); - else if ( item.Parent is Item parentItem ) - parentItem.RemoveItem( item ); - else - item.SendRemovePacket(); - - item.Parent = this; - item.Map = m_Map; - - m_Items.Add( item ); - - if ( !item.IsVirtualItem ) - { - UpdateTotal( item, TotalType.Gold, item.TotalGold ); - UpdateTotal( item, TotalType.Items, item.TotalItems + 1 ); - UpdateTotal( item, TotalType.Weight, item.TotalWeight + item.PileWeight ); - } - - item.Delta( ItemDelta.Update ); - - item.OnAdded( this ); - OnItemAdded( item ); - - if ( item.PhysicalResistance != 0 || item.FireResistance != 0 || item.ColdResistance != 0 || - item.PoisonResistance != 0 || item.EnergyResistance != 0 ) - UpdateResistances(); - } - - private static IWeapon m_DefaultWeapon; - - public static IWeapon DefaultWeapon - { - get => m_DefaultWeapon; - set => m_DefaultWeapon = value; - } - - public void RemoveItem( Item item ) - { - if ( item == null || m_Items == null ) - return; - - if ( m_Items.Contains( item ) ) - { - item.SendRemovePacket(); - - //int oldCount = m_Items.Count; - - m_Items.Remove( item ); - - if ( !item.IsVirtualItem ) - { - UpdateTotal( item, TotalType.Gold, -item.TotalGold ); - UpdateTotal( item, TotalType.Items, -(item.TotalItems + 1) ); - UpdateTotal( item, TotalType.Weight, -(item.TotalWeight + item.PileWeight) ); - } - - item.Parent = null; - - item.OnRemoved( this ); - OnItemRemoved( item ); - - if ( item.PhysicalResistance != 0 || item.FireResistance != 0 || item.ColdResistance != 0 || - item.PoisonResistance != 0 || item.EnergyResistance != 0 ) - UpdateResistances(); - } - } - - public virtual void Animate( int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay ) - { - Map map = m_Map; - - if ( map != null ) - { - ProcessDelta(); - - Packet p = null; - //Packet pNew = null; - - IPooledEnumerable eable = map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state.Mobile.CanSee( this ) ) { - state.Mobile.ProcessDelta(); - - //if ( state.StygianAbyss ) { - //if ( pNew == null ) - //pNew = Packet.Acquire( new NewMobileAnimation( this, action, frameCount, delay ) ); - - //state.Send( pNew ); - //} else { - if (p == null) - { - #region SA - if (Body.IsGargoyle) - { - frameCount = 10; - - if (Flying) - { - if (action >= 9 && action <= 11) - { - action = 71; - } - else if (action >= 12 && action <= 14) - { - action = 72; - } - else if (action == 20) - { - action = 77; - } - else if (action == 31) - { - action = 71; - } - else if (action == 34) - { - action = 78; - } - else if (action >= 200 && action <= 259) - { - action = 75; - } - else if (action >= 260 && action <= 270) - { - action = 75; - } - } - else - { - if (action >= 200 && action <= 259) - { - action = 17; - } - else if (action >= 260 && action <= 270) - { - action = 16; - } - } - } - #endregion - - p = Packet.Acquire(new MobileAnimation(this, action, frameCount, repeatCount, forward, repeat, delay)); - } - - state.Send( p ); - //} - } - } - - Packet.Release( p ); - //Packet.Release( pNew ); - - eable.Free(); - } - } - - public void SendSound( int soundID ) - { - if ( soundID != -1 && m_NetState != null ) - Send( new PlaySound( soundID, this ) ); - } - - public void SendSound( int soundID, IPoint3D p ) - { - if ( soundID != -1 && m_NetState != null ) - Send( new PlaySound( soundID, p ) ); - } - - public void PlaySound( int soundID ) - { - if ( soundID == -1 ) - return; - - if ( m_Map != null ) - { - Packet p = Packet.Acquire(new PlaySound(soundID, this)); - - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state.Mobile.CanSee( this ) ) { - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - [CommandProperty( AccessLevel.Counselor )] - public Skills Skills - { - get => m_Skills; - set - { - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.Administrator )] - public AccessLevel AccessLevel - { - get => m_AccessLevel; - set - { - AccessLevel oldValue = m_AccessLevel; - - if ( oldValue != value ) - { - m_AccessLevel = value; - Delta( MobileDelta.Noto ); - InvalidateProperties(); - - SendMessage( "Your access level has been changed. You are now {0}.", GetAccessLevelName( value ) ); - - ClearScreen(); - SendEverything(); - - OnAccessLevelChanged( oldValue ); - } - } - } - - public virtual void OnAccessLevelChanged( AccessLevel oldLevel ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Fame - { - get => m_Fame; - set - { - int oldValue = m_Fame; - - if ( oldValue != value ) - { - m_Fame = value; - - if ( ShowFameTitle && (m_Player || m_Body.IsHuman) && (oldValue >= 10000) != (value >= 10000) ) - InvalidateProperties(); - - OnFameChange( oldValue ); - } - } - } - - public virtual void OnFameChange( int oldValue ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public int Karma - { - get => m_Karma; - set - { - int old = m_Karma; - - if ( old != value ) - { - m_Karma = value; - OnKarmaChange( old ); - } - } - } - - public virtual void OnKarmaChange( int oldValue ) - { - } - - // Mobile did something which should unhide him - public virtual void RevealingAction() - { - if ( m_Hidden && m_AccessLevel == AccessLevel.Player ) - Hidden = false; - - DisruptiveAction(); // Anything that unhides you will also distrupt meditation - } - - #region Say/SayTo/Emote/Whisper/Yell - public void SayTo( Mobile to, bool ascii, string text ) - { - PrivateOverheadMessage( MessageType.Regular, m_SpeechHue, ascii, text, to.NetState ); - } - - public void SayTo( Mobile to, string text ) - { - SayTo( to, false, text ); - } - - public void SayTo( Mobile to, string format, params object[] args ) - { - SayTo( to, false, String.Format( format, args ) ); - } - - public void SayTo( Mobile to, bool ascii, string format, params object[] args ) - { - SayTo( to, ascii, String.Format( format, args ) ); - } - - public void SayTo( Mobile to, int number ) - { - to.Send( new MessageLocalized( m_Serial, Body, MessageType.Regular, m_SpeechHue, 3, number, Name, "" ) ); - } - - public void SayTo( Mobile to, int number, string args ) - { - to.Send( new MessageLocalized( m_Serial, Body, MessageType.Regular, m_SpeechHue, 3, number, Name, args ) ); - } - - public void Say( bool ascii, string text ) - { - PublicOverheadMessage( MessageType.Regular, m_SpeechHue, ascii, text ); - } - - public void Say( string text ) - { - PublicOverheadMessage( MessageType.Regular, m_SpeechHue, false, text ); - } - - public void Say( string format, params object[] args ) - { - Say( String.Format( format, args ) ); - } - - public void Say( int number, AffixType type, string affix, string args ) - { - PublicOverheadMessage( MessageType.Regular, m_SpeechHue, number, type, affix, args ); - } - - public void Say( int number ) - { - Say( number, "" ); - } - - public void Say( int number, string args ) - { - PublicOverheadMessage( MessageType.Regular, m_SpeechHue, number, args ); - } - - public void Emote( string text ) - { - PublicOverheadMessage( MessageType.Emote, m_EmoteHue, false, text ); - } - - public void Emote( string format, params object[] args ) - { - Emote( String.Format( format, args ) ); - } - - public void Emote( int number ) - { - Emote( number, "" ); - } - - public void Emote( int number, string args ) - { - PublicOverheadMessage( MessageType.Emote, m_EmoteHue, number, args ); - } - - public void Whisper( string text ) - { - PublicOverheadMessage( MessageType.Whisper, m_WhisperHue, false, text ); - } - - public void Whisper( string format, params object[] args ) - { - Whisper( String.Format( format, args ) ); - } - - public void Whisper( int number ) - { - Whisper( number, "" ); - } - - public void Whisper( int number, string args ) - { - PublicOverheadMessage( MessageType.Whisper, m_WhisperHue, number, args ); - } - - public void Yell( string text ) - { - PublicOverheadMessage( MessageType.Yell, m_YellHue, false, text ); - } - - public void Yell( string format, params object[] args ) - { - Yell( String.Format( format, args ) ); - } - - public void Yell( int number ) - { - Yell( number, "" ); - } - - public void Yell( int number, string args ) - { - PublicOverheadMessage( MessageType.Yell, m_YellHue, number, args ); - } - #endregion - - [CommandProperty( AccessLevel.GameMaster )] - public bool Blessed - { - get => m_Blessed; - set - { - if ( m_Blessed != value ) - { - m_Blessed = value; - Delta( MobileDelta.HealthbarYellow ); - } - } - } - - public void SendRemovePacket() - { - SendRemovePacket( true ); - } - - public void SendRemovePacket( bool everyone ) - { - if ( m_Map != null ) - { - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state != m_NetState && (everyone || !state.Mobile.CanSee( this )) ) - state.Send( RemovePacket ); - } - - eable.Free(); - } - } - - public void ClearScreen() - { - NetState ns = m_NetState; - - if ( m_Map != null && ns != null ) - { - IPooledEnumerable eable = m_Map.GetObjectsInRange( m_Location, Core.GlobalMaxUpdateRange ); - - foreach ( IEntity o in eable ) { - if ( o is Mobile m ) { - if ( m != this && Utility.InUpdateRange( m_Location, m.m_Location ) ) - ns.Send( m.RemovePacket ); - } else if ( o is Item item ) { - if ( InRange( item.Location, item.GetUpdateRange( this ) ) ) - ns.Send( item.RemovePacket ); - } - } - - eable.Free(); - } - } - - public bool Send( Packet p ) { - return Send( p, false ); - } - - public bool Send( Packet p, bool throwOnOffline ) { - if ( m_NetState != null ) { - m_NetState.Send( p ); - return true; - } - if ( throwOnOffline ) { - throw new MobileNotConnectedException( this, "Packet could not be sent." ); - } - - return false; - } - - #region Gumps/Menus - - public bool SendHuePicker( HuePicker p ) { - return SendHuePicker( p, false ); - } - - public bool SendHuePicker( HuePicker p, bool throwOnOffline ) { - if (m_NetState != null) - { - p.SendTo(m_NetState); - return true; - } - - if ( throwOnOffline ) { - throw new MobileNotConnectedException( this, "Hue picker could not be sent." ); - } - - return false; - } - - public Gump FindGump( Type type ) { - NetState ns = m_NetState; - - if ( ns != null ) { - foreach ( Gump gump in ns.Gumps ) { - if ( type.IsInstanceOfType( gump ) ) { - return gump; - } - } - } - - return null; - } - - public bool CloseGump( Type type ) - { - if ( m_NetState != null ) { - Gump gump = FindGump( type ); - - if ( gump != null ) { - m_NetState.Send( new CloseGump( gump.TypeID, 0 ) ); - - m_NetState.RemoveGump( gump ); - - gump.OnServerClose( m_NetState ); - } - - return true; - } - - return false; - } - - [Obsolete( "Use CloseGump( Type ) instead." )] - public bool CloseGump( Type type, int buttonID ) { - return CloseGump( type ); - } - - [Obsolete( "Use CloseGump( Type ) instead." )] - public bool CloseGump( Type type, int buttonID, bool throwOnOffline ) { - return CloseGump( type ); - } - - public bool CloseAllGumps() { - NetState ns = m_NetState; - - if ( ns != null ) { - List gumps = new List( ns.Gumps ); - - ns.ClearGumps(); - - foreach ( Gump gump in gumps ) { - ns.Send( new CloseGump( gump.TypeID, 0 ) ); - - gump.OnServerClose( ns ); - } - - return true; - } - - return false; - } - - [Obsolete( "Use CloseAllGumps() instead.", false )] - public bool CloseAllGumps( bool throwOnOffline ) { - return CloseAllGumps(); - } - - public bool HasGump( Type type ) { - return ( FindGump( type ) != null ); - } - - [Obsolete( "Use HasGump( Type ) instead.", false )] - public bool HasGump( Type type, bool throwOnOffline ) { - return HasGump( type ); - } - - public bool SendGump( Gump g ) { - return SendGump( g, false ); - } - - public bool SendGump( Gump g, bool throwOnOffline ) { - if ( m_NetState != null ) { - g.SendTo( m_NetState ); - return true; - } - - if ( throwOnOffline ) { - throw new MobileNotConnectedException( this, "Gump could not be sent." ); - } - return false; - } - - public bool SendMenu( IMenu m ) { - return SendMenu( m, false ); - } - - public bool SendMenu( IMenu m, bool throwOnOffline ) { - if ( m_NetState != null ) { - m.SendTo( m_NetState ); - return true; - } - - if ( throwOnOffline ) { - throw new MobileNotConnectedException( this, "Menu could not be sent." ); - } - return false; - } - - #endregion - - /// - /// Overridable. Event invoked before the Mobile says something. - /// - /// - public virtual void OnSaid( SpeechEventArgs e ) - { - if ( m_Squelched ) - { - if ( Core.ML ) - SendLocalizedMessage( 500168 ); // You can not say anything, you have been muted. - else - SendMessage( "You can not say anything, you have been squelched." ); //Cliloc ITSELF changed during ML. - - e.Blocked = true; - } - - if ( !e.Blocked ) - RevealingAction(); - } - - public virtual bool HandlesOnSpeech( Mobile from ) - { - return false; - } - - /// - /// Overridable. Virtual event invoked when the Mobile hears speech. This event will only be invoked if returns true. - /// - /// - public virtual void OnSpeech( SpeechEventArgs e ) - { - } - - public void SendEverything() - { - NetState ns = m_NetState; - - if ( m_Map != null && ns != null ) - { - IPooledEnumerable eable = m_Map.GetObjectsInRange( m_Location, Core.GlobalMaxUpdateRange ); - - foreach ( IEntity o in eable ) { - if ( o is Item item ) { - if ( CanSee( item ) && InRange( item.Location, item.GetUpdateRange( this ) ) ) - item.SendInfoTo( ns ); - } else if ( o is Mobile m ) { - if ( CanSee( m ) && Utility.InUpdateRange( m_Location, m.m_Location ) ) - { - ns.Send(MobileIncoming.Create(ns, this, m)); - - if ( ns.StygianAbyss ) { - if ( m.Poisoned ) - ns.Send( new HealthbarPoison( m ) ); - - if ( m.Blessed || m.YellowHealthbar ) - ns.Send( new HealthbarYellow( m ) ); - } - - if ( m.IsDeadBondedPet ) - ns.Send( new BondedStatus( 0, m.m_Serial, 1 ) ); - - if ( ObjectPropertyList.Enabled ) - { - ns.Send( m.OPLPacket ); - - //foreach ( Item item in m.m_Items ) - // ns.Send( item.OPLPacket ); - } - } - } - } - - eable.Free(); - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Map Map - { - get => m_Map; - set - { - if ( m_Deleted ) - return; - - if ( m_Map != value ) - { - m_NetState?.ValidateAllTrades(); - - Map oldMap = m_Map; - - if ( m_Map != null ) - { - m_Map.OnLeave( this ); - - ClearScreen(); - SendRemovePacket(); - } - - for( int i = 0; i < m_Items.Count; ++i ) - m_Items[i].Map = value; - - m_Map = value; - - UpdateRegion(); - - m_Map?.OnEnter( this ); - - NetState ns = m_NetState; - - if ( ns != null && m_Map != null ) - { - ns.Sequence = 0; - ns.Send( new MapChange( this ) ); - ns.Send( new MapPatches() ); - ns.Send( SeasonChange.Instantiate( GetSeason(), true ) ); - - if ( ns.StygianAbyss ) - ns.Send( new MobileUpdate( this ) ); - else - ns.Send( new MobileUpdateOld( this ) ); - - ClearFastwalkStack(); - } - - if ( ns != null ) - { - if ( m_Map != null ) - ns.Send( new ServerChange( this, m_Map ) ); - - ns.Sequence = 0; - ClearFastwalkStack(); - - ns.Send(MobileIncoming.Create(ns, this, this)); - - if ( ns.StygianAbyss ) { - ns.Send( new MobileUpdate( this ) ); - CheckLightLevels( true ); - ns.Send( new MobileUpdate( this ) ); - } else { - ns.Send( new MobileUpdateOld( this ) ); - CheckLightLevels( true ); - ns.Send( new MobileUpdateOld( this ) ); - } - } - - SendEverything(); - SendIncomingPacket(); - - if ( ns != null ) - { - ns.Sequence = 0; - ClearFastwalkStack(); - - ns.Send(MobileIncoming.Create(ns, this, this)); - - if ( ns.StygianAbyss ) { - ns.Send( SupportedFeatures.Instantiate( ns ) ); - ns.Send( new MobileUpdate( this ) ); - ns.Send( new MobileAttributes( this ) ); - } else { - ns.Send( SupportedFeatures.Instantiate( ns ) ); - ns.Send( new MobileUpdateOld( this ) ); - ns.Send( new MobileAttributes( this ) ); - } - } - - OnMapChange( oldMap ); - } - } - } - - public void UpdateRegion() - { - if ( m_Deleted ) - return; - - Region newRegion = Region.Find( m_Location, m_Map ); - - if ( newRegion != m_Region ) - { - Region.OnRegionChange( this, m_Region, newRegion ); - - m_Region = newRegion; - OnRegionChange( m_Region, newRegion ); - } - } - - /// - /// Overridable. Virtual event invoked when changes. - /// - protected virtual void OnMapChange( Map oldMap ) - { - } - - #region Beneficial Checks/Actions - - public virtual bool CanBeBeneficial( Mobile target ) - { - return CanBeBeneficial( target, true, false ); - } - - public virtual bool CanBeBeneficial( Mobile target, bool message ) - { - return CanBeBeneficial( target, message, false ); - } - - public virtual bool CanBeBeneficial( Mobile target, bool message, bool allowDead ) - { - if ( target == null ) - return false; - - if ( m_Deleted || target.m_Deleted || !Alive || IsDeadBondedPet || (!allowDead && (!target.Alive || target.IsDeadBondedPet)) ) - { - if ( message ) - SendLocalizedMessage( 1001017 ); // You can not perform beneficial acts on your target. - - return false; - } - - if ( target == this ) - return true; - - if ( /*m_Player &&*/ !Region.AllowBeneficial( this, target ) ) - { - // TODO: Pets - //if ( !(target.m_Player || target.Body.IsHuman || target.Body.IsAnimal) ) - //{ - if ( message ) - SendLocalizedMessage( 1001017 ); // You can not perform beneficial acts on your target. - - return false; - //} - } - - return true; - } - - public virtual bool IsBeneficialCriminal( Mobile target ) - { - if ( this == target ) - return false; - - int n = Notoriety.Compute( this, target ); - - return (n == Notoriety.Criminal || n == Notoriety.Murderer); - } - - /// - /// Overridable. Event invoked when the Mobile does a beneficial action. - /// - public virtual void OnBeneficialAction( Mobile target, bool isCriminal ) - { - if ( isCriminal ) - CriminalAction( false ); - } - - public virtual void DoBeneficial( Mobile target ) - { - if ( target == null ) - return; - - OnBeneficialAction( target, IsBeneficialCriminal( target ) ); - - Region.OnBeneficialAction( this, target ); - target.Region.OnGotBeneficialAction( this, target ); - } - - public virtual bool BeneficialCheck( Mobile target ) - { - if ( CanBeBeneficial( target, true ) ) - { - DoBeneficial( target ); - return true; - } - - return false; - } - - #endregion - - #region Harmful Checks/Actions - - public virtual bool CanBeHarmful( Mobile target ) - { - return CanBeHarmful( target, true ); - } - - public virtual bool CanBeHarmful( Mobile target, bool message ) - { - return CanBeHarmful( target, message, false ); - } - - public virtual bool CanBeHarmful( Mobile target, bool message, bool ignoreOurBlessedness ) - { - if ( target == null ) - return false; - - if ( m_Deleted || (!ignoreOurBlessedness && m_Blessed) || target.m_Deleted || target.m_Blessed || !Alive || IsDeadBondedPet || !target.Alive || target.IsDeadBondedPet ) - { - if ( message ) - SendLocalizedMessage( 1001018 ); // You can not perform negative acts on your target. - - return false; - } - - if ( target == this ) - return true; - - // TODO: Pets - if ( /*m_Player &&*/ !Region.AllowHarmful( this, target ) )//(target.m_Player || target.Body.IsHuman) && !Region.AllowHarmful( this, target ) ) - { - if ( message ) - SendLocalizedMessage( 1001018 ); // You can not perform negative acts on your target. - - return false; - } - - return true; - } - - public virtual bool IsHarmfulCriminal( Mobile target ) - { - if ( this == target ) - return false; - - return (Notoriety.Compute( this, target ) == Notoriety.Innocent); - } - - /// - /// Overridable. Event invoked when the Mobile does a harmful action. - /// - public virtual void OnHarmfulAction( Mobile target, bool isCriminal ) - { - if ( isCriminal ) - CriminalAction( false ); - } - - public virtual void DoHarmful( Mobile target ) - { - DoHarmful( target, false ); - } - - public virtual void DoHarmful( Mobile target, bool indirect ) - { - if ( target == null || m_Deleted ) - return; - - bool isCriminal = IsHarmfulCriminal( target ); - - OnHarmfulAction( target, isCriminal ); - target.AggressiveAction( this, isCriminal ); - - Region.OnDidHarmful( this, target ); - target.Region.OnGotHarmful( this, target ); - - if ( !indirect ) - Combatant = target; - - if ( m_ExpireCombatant == null ) - m_ExpireCombatant = new ExpireCombatantTimer( this ); - else - m_ExpireCombatant.Stop(); - - m_ExpireCombatant.Start(); - } - - public virtual bool HarmfulCheck( Mobile target ) - { - if ( CanBeHarmful( target ) ) - { - DoHarmful( target ); - return true; - } - - return false; - } - - #endregion - - #region Stats - - /// - /// Gets a list of all StatMod's currently active for the Mobile. - /// - public List StatMods => m_StatMods; - - public bool RemoveStatMod( string name ) - { - for( int i = 0; i < m_StatMods.Count; ++i ) - { - StatMod check = m_StatMods[i]; - - if ( check.Name == name ) - { - m_StatMods.RemoveAt( i ); - CheckStatTimers(); - Delta( MobileDelta.Stat | GetStatDelta( check.Type ) ); - return true; - } - } - - return false; - } - - public StatMod GetStatMod( string name ) - { - for( int i = 0; i < m_StatMods.Count; ++i ) - { - StatMod check = m_StatMods[i]; - - if ( check.Name == name ) - return check; - } - - return null; - } - - public void AddStatMod( StatMod mod ) - { - for( int i = 0; i < m_StatMods.Count; ++i ) - { - StatMod check = m_StatMods[i]; - - if ( check.Name == mod.Name ) - { - Delta( MobileDelta.Stat | GetStatDelta( check.Type ) ); - m_StatMods.RemoveAt( i ); - break; - } - } - - m_StatMods.Add( mod ); - Delta( MobileDelta.Stat | GetStatDelta( mod.Type ) ); - CheckStatTimers(); - } - - private MobileDelta GetStatDelta( StatType type ) - { - MobileDelta delta = 0; - - if ( (type & StatType.Str) != 0 ) - delta |= MobileDelta.Hits; - - if ( (type & StatType.Dex) != 0 ) - delta |= MobileDelta.Stam; - - if ( (type & StatType.Int) != 0 ) - delta |= MobileDelta.Mana; - - return delta; - } - - /// - /// Computes the total modified offset for the specified stat type. Expired instances are removed. - /// - public int GetStatOffset( StatType type ) - { - int offset = 0; - - for( int i = 0; i < m_StatMods.Count; ++i ) - { - StatMod mod = m_StatMods[i]; - - if ( mod.HasElapsed() ) - { - m_StatMods.RemoveAt( i ); - Delta( MobileDelta.Stat | GetStatDelta( mod.Type ) ); - CheckStatTimers(); - - --i; - } - else if ( (mod.Type & type) != 0 ) - { - offset += mod.Offset; - } - } - - return offset; - } - - /// - /// Overridable. Virtual event invoked when the changes. - /// - /// - /// - public virtual void OnRawStrChange( int oldValue ) - { - } - - /// - /// Overridable. Virtual event invoked when changes. - /// - /// - /// - public virtual void OnRawDexChange( int oldValue ) - { - } - - /// - /// Overridable. Virtual event invoked when the changes. - /// - /// - /// - public virtual void OnRawIntChange( int oldValue ) - { - } - - /// - /// Overridable. Virtual event invoked when the , , or changes. - /// - /// - /// - /// - public virtual void OnRawStatChange( StatType stat, int oldValue ) - { - } - - /// - /// Gets or sets the base, unmodified, strength of the Mobile. Ranges from 1 to 65000, inclusive. - /// - /// - /// - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public int RawStr - { - get => m_Str; - set - { - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; - - if ( m_Str != value ) - { - int oldValue = m_Str; - - m_Str = value; - Delta( MobileDelta.Stat | MobileDelta.Hits ); - - if ( Hits < HitsMax ) - { - if ( m_HitsTimer == null ) - m_HitsTimer = new HitsTimer( this ); - - m_HitsTimer.Start(); - } - else if ( Hits > HitsMax ) - { - Hits = HitsMax; - } - - OnRawStrChange( oldValue ); - OnRawStatChange( StatType.Str, oldValue ); - } - } - } - - /// - /// Gets or sets the effective strength of the Mobile. This is the sum of the plus any additional modifiers. Any attempts to set this value when under the influence of a will result in no change. It ranges from 1 to 65000, inclusive. - /// - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual int Str - { - get - { - int value = m_Str + GetStatOffset( StatType.Str ); - - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; - - return value; - } - set - { - if ( m_StatMods.Count == 0 ) - RawStr = value; - } - } - - /// - /// Gets or sets the base, unmodified, dexterity of the Mobile. Ranges from 1 to 65000, inclusive. - /// - /// - /// - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public int RawDex - { - get => m_Dex; - set - { - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; - - if ( m_Dex != value ) - { - int oldValue = m_Dex; - - m_Dex = value; - Delta( MobileDelta.Stat | MobileDelta.Stam ); - - if ( Stam < StamMax ) - { - if ( m_StamTimer == null ) - m_StamTimer = new StamTimer( this ); - - m_StamTimer.Start(); - } - else if ( Stam > StamMax ) - { - Stam = StamMax; - } - - OnRawDexChange( oldValue ); - OnRawStatChange( StatType.Dex, oldValue ); - } - } - } - - /// - /// Gets or sets the effective dexterity of the Mobile. This is the sum of the plus any additional modifiers. Any attempts to set this value when under the influence of a will result in no change. It ranges from 1 to 65000, inclusive. - /// - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual int Dex - { - get - { - int value = m_Dex + GetStatOffset( StatType.Dex ); - - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; - - return value; - } - set - { - if ( m_StatMods.Count == 0 ) - RawDex = value; - } - } - - /// - /// Gets or sets the base, unmodified, intelligence of the Mobile. Ranges from 1 to 65000, inclusive. - /// - /// - /// - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public int RawInt - { - get => m_Int; - set - { - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; - - if ( m_Int != value ) - { - int oldValue = m_Int; - - m_Int = value; - Delta( MobileDelta.Stat | MobileDelta.Mana ); - - if ( Mana < ManaMax ) - { - if ( m_ManaTimer == null ) - m_ManaTimer = new ManaTimer( this ); - - m_ManaTimer.Start(); - } - else if ( Mana > ManaMax ) - { - Mana = ManaMax; - } - - OnRawIntChange( oldValue ); - OnRawStatChange( StatType.Int, oldValue ); - } - } - } - - /// - /// Gets or sets the effective intelligence of the Mobile. This is the sum of the plus any additional modifiers. Any attempts to set this value when under the influence of a will result in no change. It ranges from 1 to 65000, inclusive. - /// - /// - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual int Int - { - get - { - int value = m_Int + GetStatOffset( StatType.Int ); - - if ( value < 1 ) - value = 1; - else if ( value > 65000 ) - value = 65000; - - return value; - } - set - { - if ( m_StatMods.Count == 0 ) - RawInt = value; - } - } - - public virtual void OnHitsChange( int oldValue ) - { - } - - public virtual void OnStamChange( int oldValue ) - { - } - - public virtual void OnManaChange( int oldValue ) - { - } - - /// - /// Gets or sets the current hit point of the Mobile. This value ranges from 0 to , inclusive. When set to the value of , the CanReportMurder flag of all aggressors is reset to false, and the list of damage entries is cleared. - /// - [CommandProperty( AccessLevel.GameMaster )] - public int Hits - { - get => m_Hits; - set - { - if ( m_Deleted ) - return; - - if ( value < 0 ) - { - value = 0; - } - else if ( value >= HitsMax ) - { - value = HitsMax; - - m_HitsTimer?.Stop(); - - for( int i = 0; i < m_Aggressors.Count; i++ ) //reset reports on full HP - m_Aggressors[i].CanReportMurder = false; - - if ( m_DamageEntries.Count > 0 ) - m_DamageEntries.Clear(); // reset damage entries on full HP - } - - if ( value < HitsMax ) - { - if ( CanRegenHits ) - { - if ( m_HitsTimer == null ) - m_HitsTimer = new HitsTimer( this ); - - m_HitsTimer.Start(); - } - else - { - m_HitsTimer?.Stop(); - } - } - - if ( m_Hits != value ) - { - int oldValue = m_Hits; - m_Hits = value; - Delta( MobileDelta.Hits ); - OnHitsChange( oldValue ); - } - } - } - - /// - /// Overridable. Gets the maximum hit point of the Mobile. By default, this returns: 50 + ( / 2) - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual int HitsMax => 50 + (Str / 2); - - /// - /// Gets or sets the current stamina of the Mobile. This value ranges from 0 to , inclusive. - /// - [CommandProperty( AccessLevel.GameMaster )] - public int Stam - { - get => m_Stam; - set - { - if ( m_Deleted ) - return; - - if ( value < 0 ) - { - value = 0; - } - else if ( value >= StamMax ) - { - value = StamMax; - - m_StamTimer?.Stop(); - } - - if ( value < StamMax ) - { - if ( CanRegenStam ) - { - if ( m_StamTimer == null ) - m_StamTimer = new StamTimer( this ); - - m_StamTimer.Start(); - } - else - { - m_StamTimer?.Stop(); - } - } - - if ( m_Stam != value ) - { - int oldValue = m_Stam; - m_Stam = value; - Delta( MobileDelta.Stam ); - OnStamChange( oldValue ); - } - } - } - - /// - /// Overridable. Gets the maximum stamina of the Mobile. By default, this returns: - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual int StamMax => Dex; - - /// - /// Gets or sets the current stamina of the Mobile. This value ranges from 0 to , inclusive. - /// - [CommandProperty( AccessLevel.GameMaster )] - public int Mana - { - get => m_Mana; - set - { - if ( m_Deleted ) - return; - - if ( value < 0 ) - { - value = 0; - } - else if ( value >= ManaMax ) - { - value = ManaMax; - - m_ManaTimer?.Stop(); - - if ( Meditating ) - { - Meditating = false; - SendLocalizedMessage( 501846 ); // You are at peace. - } - } - - if ( value < ManaMax ) - { - if ( CanRegenMana ) - { - if ( m_ManaTimer == null ) - m_ManaTimer = new ManaTimer( this ); - - m_ManaTimer.Start(); - } - else - { - m_ManaTimer?.Stop(); - } - } - - if ( m_Mana != value ) - { - int oldValue = m_Mana; - m_Mana = value; - Delta( MobileDelta.Mana ); - OnManaChange( oldValue ); - } - } - } - - /// - /// Overridable. Gets the maximum mana of the Mobile. By default, this returns: - /// - [CommandProperty( AccessLevel.GameMaster )] - public virtual int ManaMax => Int; - - #endregion - - public virtual int Luck => 0; - - public virtual int HuedItemID => (m_Female ? 0x2107 : 0x2106); - - private int m_HueMod = -1; - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public int HueMod - { - get => m_HueMod; - set - { - if ( m_HueMod != value ) - { - m_HueMod = value; - - Delta( MobileDelta.Hue ); - } - } - } - - [Hue, CommandProperty( AccessLevel.GameMaster )] - public virtual int Hue - { - get - { - if ( m_HueMod != -1 ) - return m_HueMod; - - return m_Hue; - } - set - { - int oldHue = m_Hue; - - if ( oldHue != value ) - { - m_Hue = value; - - Delta( MobileDelta.Hue ); - } - } - } - - - public void SetDirection( Direction dir ) - { - m_Direction = dir; - } - - [CommandProperty( AccessLevel.GameMaster )] - public Direction Direction - { - get => m_Direction; - set - { - if ( m_Direction != value ) - { - m_Direction = value; - - Delta( MobileDelta.Direction ); - //ProcessDelta(); - } - } - } - - public virtual int GetSeason() - { - if ( m_Map != null ) - return m_Map.Season; - - return 1; - } - - public virtual int GetPacketFlags() - { - int flags = 0x0; - - if ( m_Paralyzed || m_Frozen ) - flags |= 0x01; - - if ( m_Female ) - flags |= 0x02; - - if ( m_Flying ) - flags |= 0x04; - - if ( m_Blessed || m_YellowHealthbar ) - flags |= 0x08; - - if ( m_Warmode ) - flags |= 0x40; - - if ( m_Hidden ) - flags |= 0x80; - - return flags; - } - - // Pre-7.0.0.0 Packet Flags - public virtual int GetOldPacketFlags() - { - int flags = 0x0; - - if ( m_Paralyzed || m_Frozen ) - flags |= 0x01; - - if ( m_Female ) - flags |= 0x02; - - if ( m_Poison != null ) - flags |= 0x04; - - if ( m_Blessed || m_YellowHealthbar ) - flags |= 0x08; - - if ( m_Warmode ) - flags |= 0x40; - - if ( m_Hidden ) - flags |= 0x80; - - return flags; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Female - { - get => m_Female; - set - { - if ( m_Female != value ) - { - m_Female = value; - Delta( MobileDelta.Flags ); - OnGenderChanged( !m_Female ); - } - } - } - - public virtual void OnGenderChanged( bool oldFemale ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Flying - { - get => m_Flying; - set - { - if ( m_Flying != value ) - { - m_Flying = value; - Delta( MobileDelta.Flags ); - } - } - } - - public virtual void ToggleFlying() - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Warmode - { - get => m_Warmode; - set - { - if ( m_Deleted ) - return; - - if ( m_Warmode != value ) - { - if ( m_AutoManifestTimer != null ) - { - m_AutoManifestTimer.Stop(); - m_AutoManifestTimer = null; - } - - m_Warmode = value; - Delta( MobileDelta.Flags ); - - if ( m_NetState != null ) - Send( SetWarMode.Instantiate( value ) ); - - if ( !m_Warmode ) - Combatant = null; - - if ( !Alive ) - { - if ( value ) - Delta( MobileDelta.GhostUpdate ); - else - SendRemovePacket( false ); - } - - OnWarmodeChanged(); - } - } - } - - /// - /// Overridable. Virtual event invoked after the Warmode property has changed. - /// - public virtual void OnWarmodeChanged() - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Hidden - { - get => m_Hidden; - set - { - if ( m_Hidden != value ) - { - m_Hidden = value; - //Delta( MobileDelta.Flags ); - - OnHiddenChanged(); - } - } - } - - public virtual void OnHiddenChanged() - { - m_AllowedStealthSteps = 0; - - if (m_Map != null) - { - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach (NetState state in eable) { - if (!state.Mobile.CanSee(this)) { - state.Send(RemovePacket); - } else { - state.Send(MobileIncoming.Create(state, state.Mobile, this)); - - if (IsDeadBondedPet) - state.Send(new BondedStatus(0, m_Serial, 1)); - - if (ObjectPropertyList.Enabled) { - state.Send(OPLPacket); - - //foreach ( Item item in m_Items ) - // state.Send( item.OPLPacket ); - } - } - } - - eable.Free(); - } - } - - public virtual void OnConnected() - { - } - - public virtual void OnDisconnected() - { - } - - public virtual void OnNetStateChanged() - { - } - - [CommandProperty( AccessLevel.GameMaster, AccessLevel.Owner )] - public NetState NetState - { - get - { - if (m_NetState != null && m_NetState.Socket == null && !m_NetState.IsDisposing) - { - NetState = null; - } - - return m_NetState; - } - set - { - if ( m_NetState != value ) - { - m_Map?.OnClientChange( m_NetState, value, this ); - - m_Target?.Cancel( this, TargetCancelType.Disconnected ); - - if ( m_QuestArrow != null ) - QuestArrow = null; - - m_Spell?.OnConnectionChanged(); - - //if ( m_Spell != null ) - // m_Spell.FinishSequence(); - - m_NetState?.CancelAllTrades(); - - BankBox box = FindBankNoCreate(); - - if ( box != null && box.Opened ) - box.Close(); - - // REMOVED: - //m_Actions.Clear(); - - m_NetState = value; - - if ( m_NetState == null ) - { - OnDisconnected(); - EventSink.InvokeDisconnected( new DisconnectedEventArgs( this ) ); - - // Disconnected, start the logout timer - - if ( m_LogoutTimer == null ) - m_LogoutTimer = new LogoutTimer( this ); - else - m_LogoutTimer.Stop(); - - m_LogoutTimer.Delay = GetLogoutDelay(); - m_LogoutTimer.Start(); - } - else - { - OnConnected(); - EventSink.InvokeConnected( new ConnectedEventArgs( this ) ); - - // Connected, stop the logout timer and if needed, move to the world - - m_LogoutTimer?.Stop(); - - m_LogoutTimer = null; - - if ( m_Map == Map.Internal && m_LogoutMap != null ) - { - Map = m_LogoutMap; - Location = m_LogoutLocation; - } - } - - for( int i = m_Items.Count - 1; i >= 0; --i ) - { - if ( i >= m_Items.Count ) - continue; - - Item item = m_Items[i]; - - if ( item is SecureTradeContainer ) - { - for( int j = item.Items.Count - 1; j >= 0; --j ) - { - if ( j < item.Items.Count ) - { - item.Items[j].OnSecureTrade( this, this, this, false ); - AddToBackpack( item.Items[j] ); - } - } - - Timer.DelayCall( TimeSpan.Zero, delegate { item.Delete(); } ); - } - } - - DropHolding(); - OnNetStateChanged(); - } - } - } - - public virtual bool CanSee( object o ) - { - if ( o is Item item ) - { - return CanSee( item ); - } - - if ( o is Mobile mobile ) - { - return CanSee( mobile ); - } - - return true; - } - - public virtual bool CanSee( Item item ) - { - if ( m_Map == Map.Internal ) - return false; - if ( item.Map == Map.Internal ) - return false; - - if ( item.Parent != null ) - { - if ( item.Parent is Item parent ) - { - if ( !(CanSee( parent ) && parent.IsChildVisibleTo( this, item )) ) - return false; - } - else if ( item.Parent is Mobile mobile ) - { - if ( !CanSee( mobile ) ) - return false; - } - } - - if ( item is BankBox box && m_AccessLevel <= AccessLevel.Counselor && (box.Owner != this || !box.Opened) ) - return false; - - if ( item is SecureTradeContainer container ) - { - SecureTrade trade = container.Trade; - - if ( trade != null && trade.From.Mobile != this && trade.To.Mobile != this ) - return false; - } - - return !item.Deleted && item.Map == m_Map && (item.Visible || m_AccessLevel > AccessLevel.Counselor); - } - - public virtual bool CanSee( Mobile m ) - { - if ( m_Deleted || m.m_Deleted || m_Map == Map.Internal || m.m_Map == Map.Internal ) - return false; - - return this == m || ( - m.m_Map == m_Map && - (!m.Hidden || (m_AccessLevel != AccessLevel.Player && (m_AccessLevel >= m.AccessLevel || m_AccessLevel >= AccessLevel.Administrator))) && - ((m.Alive || (Core.SE && Skills.SpiritSpeak.Value >= 100.0)) || !Alive || m_AccessLevel > AccessLevel.Player || m.Warmode)); - - } - - public virtual bool CanBeRenamedBy( Mobile from ) - { - return (from.AccessLevel >= AccessLevel.GameMaster && from.m_AccessLevel > m_AccessLevel); - } - - [CommandProperty( AccessLevel.GameMaster )] - public string Language - { - get => m_Language; - set - { - if ( m_Language != value ) - m_Language = value; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int SpeechHue - { - get => m_SpeechHue; - set => m_SpeechHue = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int EmoteHue - { - get => m_EmoteHue; - set => m_EmoteHue = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int WhisperHue - { - get => m_WhisperHue; - set => m_WhisperHue = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int YellHue - { - get => m_YellHue; - set => m_YellHue = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public string GuildTitle - { - get => m_GuildTitle; - set - { - string old = m_GuildTitle; - - if ( old != value ) - { - m_GuildTitle = value; - - if ( m_Guild != null && !m_Guild.Disbanded && m_GuildTitle != null ) - SendLocalizedMessage( 1018026, true, m_GuildTitle ); // Your guild title has changed : - - InvalidateProperties(); - - OnGuildTitleChange( old ); - } - } - } - - public virtual void OnGuildTitleChange( string oldTitle ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool DisplayGuildTitle - { - get => m_DisplayGuildTitle; - set - { - m_DisplayGuildTitle = value; - InvalidateProperties(); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public Mobile GuildFealty - { - get => m_GuildFealty; - set => m_GuildFealty = value; - } - - private string m_NameMod; - - [CommandProperty( AccessLevel.GameMaster )] - public string NameMod - { - get => m_NameMod; - set - { - if ( m_NameMod != value ) - { - m_NameMod = value; - Delta( MobileDelta.Name ); - InvalidateProperties(); - } - } - } - - private bool m_YellowHealthbar; - - [CommandProperty( AccessLevel.GameMaster )] - public bool YellowHealthbar - { - get => m_YellowHealthbar; - set - { - m_YellowHealthbar = value; - Delta( MobileDelta.HealthbarYellow ); - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public string RawName - { - get => m_Name; - set => Name = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public virtual string Name - { - get - { - if ( m_NameMod != null ) - return m_NameMod; - - return m_Name; - } - set - { - if ( m_Name != value ) // I'm leaving out the && m_NameMod == null - { - string oldName = m_Name; - m_Name = value; - OnAfterNameChange( oldName, m_Name ); - Delta( MobileDelta.Name ); - InvalidateProperties(); - } - } - } - - public virtual void OnAfterNameChange( string oldName, string newName ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastStrGain - { - get => m_LastStrGain; - set => m_LastStrGain = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastIntGain - { - get => m_LastIntGain; - set => m_LastIntGain = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public DateTime LastDexGain - { - get => m_LastDexGain; - set => m_LastDexGain = value; - } - - public DateTime LastStatGain - { - get - { - DateTime d = m_LastStrGain; - - if ( m_LastIntGain > d ) - d = m_LastIntGain; - - if ( m_LastDexGain > d ) - d = m_LastDexGain; - - return d; - } - set - { - m_LastStrGain = value; - m_LastIntGain = value; - m_LastDexGain = value; - } - } - - public BaseGuild Guild - { - get => m_Guild; - set - { - BaseGuild old = m_Guild; - - if ( old != value ) - { - if ( value == null ) - GuildTitle = null; - - m_Guild = value; - - Delta( MobileDelta.Noto ); - InvalidateProperties(); - - OnGuildChange( old ); - } - } - } - - public virtual void OnGuildChange( BaseGuild oldGuild ) - { - } - - #region Poison/Curing - - public Timer PoisonTimer => m_PoisonTimer; - - [CommandProperty( AccessLevel.GameMaster )] - public Poison Poison - { - get => m_Poison; - set - { - /*if ( m_Poison != value && (m_Poison == null || value == null || m_Poison.Level < value.Level) ) - {*/ - m_Poison = value; - Delta( MobileDelta.HealthbarPoison ); - - if ( m_PoisonTimer != null ) - { - m_PoisonTimer.Stop(); - m_PoisonTimer = null; - } - - if ( m_Poison != null ) - { - m_PoisonTimer = m_Poison.ConstructTimer( this ); - - m_PoisonTimer?.Start(); - } - - CheckStatTimers(); - /*}*/ - } - } - - /// - /// Overridable. Event invoked when a call to failed because returned false: the Mobile was resistant to the poison. By default, this broadcasts an overhead message: * The poison seems to have no effect. * - /// - /// - /// - /// - public virtual void OnPoisonImmunity( Mobile from, Poison poison ) - { - PublicOverheadMessage( MessageType.Emote, 0x3B2, 1005534 ); // * The poison seems to have no effect. * - } - - /// - /// Overridable. Virtual event invoked when a call to failed because returned false: the Mobile was already poisoned by an equal or greater strength poison. - /// - /// - /// - /// - public virtual void OnHigherPoison( Mobile from, Poison poison ) - { - } - - /// - /// Overridable. Event invoked when a call to succeeded. By default, this broadcasts an overhead message varying by the level of the poison. Example: * Zippy begins to spasm uncontrollably. * - /// - /// - /// - public virtual void OnPoisoned( Mobile from, Poison poison, Poison oldPoison ) - { - if ( poison != null ) - { - LocalOverheadMessage( MessageType.Regular, 0x21, 1042857 + (poison.Level * 2) ); - NonlocalOverheadMessage( MessageType.Regular, 0x21, 1042858 + (poison.Level * 2), Name ); - } - } - - /// - /// Overridable. Called from , this method checks if the Mobile is immune to some . If true, will be invoked and is returned. - /// - /// - /// - /// - public virtual bool CheckPoisonImmunity( Mobile from, Poison poison ) - { - return false; - } - - /// - /// Overridable. Called from , this method checks if the Mobile is already poisoned by some of equal or greater strength. If true, will be invoked and is returned. - /// - /// - /// - /// - public virtual bool CheckHigherPoison( Mobile from, Poison poison ) - { - return (m_Poison != null && m_Poison.Level >= poison.Level); - } - - /// - /// Overridable. Attempts to apply poison to the Mobile. Checks are made such that no higher poison is active and that the Mobile is not immune to the poison. Provided those assertions are true, the is applied and is invoked. - /// - /// - /// - /// One of four possible values: - /// - /// - /// Cured - /// The parameter was null and so was invoked. - /// - /// - /// HigherPoisonActive - /// The call to returned false. - /// - /// - /// Immune - /// The call to returned false. - /// - /// - /// Poisoned - /// The was successfully applied. - /// - /// - /// - public virtual ApplyPoisonResult ApplyPoison( Mobile from, Poison poison ) - { - if ( poison == null ) - { - CurePoison( from ); - return ApplyPoisonResult.Cured; - } - - if ( CheckHigherPoison( from, poison ) ) - { - OnHigherPoison( from, poison ); - return ApplyPoisonResult.HigherPoisonActive; - } - - if ( CheckPoisonImmunity( from, poison ) ) - { - OnPoisonImmunity( from, poison ); - return ApplyPoisonResult.Immune; - } - - Poison oldPoison = m_Poison; - Poison = poison; - - OnPoisoned( from, poison, oldPoison ); - - return ApplyPoisonResult.Poisoned; - } - - /// - /// Overridable. Called from , this method checks to see that the Mobile can be cured of - /// - /// - /// - public virtual bool CheckCure( Mobile from ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when a call to succeeded. - /// - /// - /// - /// - public virtual void OnCured( Mobile from, Poison oldPoison ) - { - } - - /// - /// Overridable. Virtual event invoked when a call to failed. - /// - /// - /// - /// - public virtual void OnFailedCure( Mobile from ) - { - } - - /// - /// Overridable. Attempts to cure any poison that is currently active. - /// - /// True if poison was cured, false if otherwise. - public virtual bool CurePoison( Mobile from ) - { - if ( CheckCure( from ) ) - { - Poison oldPoison = m_Poison; - Poison = null; - - OnCured( from, oldPoison ); - - return true; - } - - OnFailedCure( from ); - - return false; - } - - #endregion - - private ISpawner m_Spawner; - - public ISpawner Spawner { get => m_Spawner; - set => m_Spawner = value; - } - - private Region m_WalkRegion; - - public Region WalkRegion { get => m_WalkRegion; - set => m_WalkRegion = value; - } - - public virtual void OnBeforeSpawn( Point3D location, Map m ) - { - } - - public virtual void OnAfterSpawn() - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Poisoned => (m_Poison != null); - - [CommandProperty( AccessLevel.GameMaster )] - public bool IsBodyMod => (m_BodyMod.BodyID != 0); - - [CommandProperty( AccessLevel.GameMaster )] - public Body BodyMod - { - get => m_BodyMod; - set - { - if ( m_BodyMod != value ) - { - m_BodyMod = value; - - Delta( MobileDelta.Body ); - InvalidateProperties(); - - CheckStatTimers(); - } - } - } - - private static int[] m_InvalidBodies = new[] - { - 32, - 95, - 156, - 197, - 198, - }; - - [Body, CommandProperty( AccessLevel.GameMaster )] - public Body Body - { - get - { - if ( IsBodyMod ) - return m_BodyMod; - - return m_Body; - } - set - { - if ( m_Body != value && !IsBodyMod ) - { - m_Body = SafeBody( value ); - - Delta( MobileDelta.Body ); - InvalidateProperties(); - - CheckStatTimers(); - } - } - } - - public virtual int SafeBody( int body ) - { - int delta = -1; - - for( int i = 0; delta < 0 && i < m_InvalidBodies.Length; ++i ) - delta = (m_InvalidBodies[i] - body); - - if ( delta != 0 ) - return body; - - return 0; - } - - [Body, CommandProperty( AccessLevel.GameMaster )] - public int BodyValue - { - get => Body.BodyID; - set => Body = value; - } - - [CommandProperty( AccessLevel.Counselor )] - public Serial Serial => m_Serial; - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Point3D Location - { - get => m_Location; - set => SetLocation( value, true ); - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Point3D LogoutLocation - { - get => m_LogoutLocation; - set => m_LogoutLocation = value; - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public Map LogoutMap - { - get => m_LogoutMap; - set => m_LogoutMap = value; - } - - public Region Region - { - get - { - if ( m_Region == null ) - if ( Map == null ) - return Map.Internal.DefaultRegion; - else - return Map.DefaultRegion; - return m_Region; - } - } - - public void FreeCache() - { - Packet.Release( ref m_RemovePacket ); - Packet.Release( ref m_PropertyList ); - Packet.Release( ref m_OPLPacket ); - } - - private Packet m_RemovePacket; - private object rpLock = new object(); - - public Packet RemovePacket - { - get - { - if (m_RemovePacket == null) - { - lock (rpLock) - { - if (m_RemovePacket == null) - { - m_RemovePacket = new RemoveMobile(this); - m_RemovePacket.SetStatic(); - } - } - } - - return m_RemovePacket; - } - } - - private Packet m_OPLPacket; - private object oplLock = new object(); - - public Packet OPLPacket - { - get - { - if (m_OPLPacket == null) - { - lock (oplLock) - { - if (m_OPLPacket == null) - { - m_OPLPacket = new OPLInfo(PropertyList); - m_OPLPacket.SetStatic(); - } - } - } - - return m_OPLPacket; - } - } - - private ObjectPropertyList m_PropertyList; - - public ObjectPropertyList PropertyList - { - get - { - if ( m_PropertyList == null ) - { - m_PropertyList = new ObjectPropertyList( this ); - - GetProperties( m_PropertyList ); - - m_PropertyList.Terminate(); - m_PropertyList.SetStatic(); - } - - return m_PropertyList; - } - } - - public void ClearProperties() - { - Packet.Release( ref m_PropertyList ); - Packet.Release( ref m_OPLPacket ); - } - - public void InvalidateProperties() - { - if ( !ObjectPropertyList.Enabled ) - return; - - if ( m_Map != null && m_Map != Map.Internal && !World.Loading ) - { - ObjectPropertyList oldList = m_PropertyList; - Packet.Release( ref m_PropertyList ); - ObjectPropertyList newList = PropertyList; - - if ( oldList == null || oldList.Hash != newList.Hash ) - { - Packet.Release( ref m_OPLPacket ); - Delta( MobileDelta.Properties ); - } - } - else - { - ClearProperties(); - } - } - - private int m_SolidHueOverride = -1; - - [CommandProperty( AccessLevel.GameMaster )] - public int SolidHueOverride - { - get => m_SolidHueOverride; - set { if ( m_SolidHueOverride == value ) return; m_SolidHueOverride = value; Delta( MobileDelta.Hue | MobileDelta.Body ); } - } - - public virtual void MoveToWorld( Point3D newLocation, Map map ) - { - if ( m_Deleted ) - return; - - if ( m_Map == map ) - { - SetLocation( newLocation, true ); - return; - } - - BankBox box = FindBankNoCreate(); - - if ( box?.Opened == true ) - box.Close(); - - Point3D oldLocation = m_Location; - Map oldMap = m_Map; - - Region oldRegion = m_Region; - - if ( oldMap != null ) - { - oldMap.OnLeave( this ); - - ClearScreen(); - SendRemovePacket(); - } - - for( int i = 0; i < m_Items.Count; ++i ) - m_Items[i].Map = map; - - m_Map = map; - - m_Location = newLocation; - - NetState ns = m_NetState; - - if ( m_Map != null ) - { - m_Map.OnEnter( this ); - - UpdateRegion(); - - if ( ns != null && m_Map != null ) - { - ns.Sequence = 0; - ns.Send( new MapChange( this ) ); - ns.Send( new MapPatches() ); - ns.Send( SeasonChange.Instantiate( GetSeason(), true ) ); - - if ( ns.StygianAbyss ) - ns.Send( new MobileUpdate( this ) ); - else - ns.Send( new MobileUpdateOld( this ) ); - - ClearFastwalkStack(); - } - } - else - { - UpdateRegion(); - } - - if ( ns != null ) - { - if ( m_Map != null ) - Send( new ServerChange( this, m_Map ) ); - - ns.Sequence = 0; - ClearFastwalkStack(); + OnAfterResurrect(); - ns.Send(MobileIncoming.Create(ns, this, this)); - - if ( ns.StygianAbyss ) { - ns.Send( new MobileUpdate( this ) ); - CheckLightLevels( true ); - ns.Send( new MobileUpdate( this ) ); - } else { - ns.Send( new MobileUpdateOld( this ) ); - CheckLightLevels( true ); - ns.Send( new MobileUpdateOld( this ) ); - } - } + //Send( new DeathStatus( false ) ); + } + } - SendEverything(); - SendIncomingPacket(); + public void DropHolding() + { + Item holding = m_Holding; + + if (holding != null) + { + if (!holding.Deleted && holding.HeldBy == this && holding.Map == Map.Internal) + AddToBackpack(holding); - if ( ns != null ) - { - ns.Sequence = 0; - ClearFastwalkStack(); + Holding = null; + holding.ClearBounce(); + } + } - ns.Send(MobileIncoming.Create(ns, this, this)); + /// + /// Overridable. Virtual event invoked before the Mobile is deleted. + /// + public virtual void OnDelete() + { + Spawner?.Remove(this); + Spawner = null; + } + + public virtual bool CheckSpellCast(ISpell spell) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile casts a . + /// + /// + public virtual void OnSpellCast(ISpell spell) + { + } - if ( ns.StygianAbyss ) { - ns.Send( SupportedFeatures.Instantiate( ns ) ); - ns.Send( new MobileUpdate( this ) ); - ns.Send( new MobileAttributes( this ) ); - } else { - ns.Send( SupportedFeatures.Instantiate( ns ) ); - ns.Send( new MobileUpdateOld( this ) ); - ns.Send( new MobileAttributes( this ) ); - } - } + /// + /// Overridable. Virtual event invoked after changes. + /// + public virtual void OnWeightChange(int oldValue) + { + } - OnMapChange( oldMap ); - OnLocationChange( oldLocation ); + /// + /// Overridable. Virtual event invoked when the or property of + /// changes. + /// + public virtual void OnSkillChange(SkillName skill, double oldBase) + { + } - m_Region?.OnLocationChanged( this, oldLocation ); - } + /// + /// Overridable. Invoked after the mobile is deleted. When overridden, be sure to call the base method. + /// + public virtual void OnAfterDelete() + { + StopAggrExpire(); - public virtual void SetLocation( Point3D newLocation, bool isTeleport ) - { - if ( m_Deleted ) - return; + CheckAggrExpire(); - Point3D oldLocation = m_Location; + PoisonTimer?.Stop(); - if ( oldLocation != newLocation ) - { - m_Location = newLocation; - UpdateRegion(); + m_HitsTimer?.Stop(); - BankBox box = FindBankNoCreate(); + m_StamTimer?.Stop(); - if ( box != null && box.Opened ) - box.Close(); + m_ManaTimer?.Stop(); - m_NetState?.ValidateAllTrades(); + m_CombatTimer?.Stop(); - m_Map?.OnMove( oldLocation, this ); + m_ExpireCombatant?.Stop(); - if ( isTeleport && m_NetState != null && ( !m_NetState.HighSeas || !m_NoMoveHS ) ) - { - m_NetState.Sequence = 0; - - if ( m_NetState.StygianAbyss ) - m_NetState.Send( new MobileUpdate( this ) ); - else - m_NetState.Send( new MobileUpdateOld( this ) ); - - ClearFastwalkStack(); - } - - Map map = m_Map; - - if ( map != null ) - { - // First, send a remove message to everyone who can no longer see us. (inOldRange && !inNewRange) - - IPooledEnumerable eable = map.GetClientsInRange(oldLocation); - - foreach( NetState ns in eable ) { - if ( ns != m_NetState && !Utility.InUpdateRange( newLocation, ns.Mobile.Location ) ) { - ns.Send( RemovePacket ); - } - } - - eable.Free(); - - NetState ourState = m_NetState; + m_LogoutTimer?.Stop(); - // Check to see if we are attached to a client - if ( ourState != null ) - { - IPooledEnumerable eeable = map.GetObjectsInRange( newLocation, Core.GlobalMaxUpdateRange ); - - // We are attached to a client, so it's a bit more complex. We need to send new items and people to ourself, and ourself to other clients - - foreach ( IEntity o in eeable ) { - if ( o is Item item ) - { - int range = item.GetUpdateRange( this ); - Point3D loc = item.Location; - - if ( !Utility.InRange( oldLocation, loc, range ) && Utility.InRange( newLocation, loc, range ) && CanSee( item ) ) - item.SendInfoTo( ourState ); - } - else if ( o != this && o is Mobile m ) - { - if ( !Utility.InUpdateRange( newLocation, m.m_Location ) ) - continue; + m_ExpireCriminal?.Stop(); - bool inOldRange = Utility.InUpdateRange( oldLocation, m.m_Location ); + m_WarmodeTimer?.Stop(); - if ( m.m_NetState != null && ( ( isTeleport && ( !m.m_NetState.HighSeas || !m_NoMoveHS ) ) || !inOldRange ) && m.CanSee( this ) ) - { - m.m_NetState.Send(MobileIncoming.Create(m.m_NetState, m, this)); + m_ParaTimer?.Stop(); - if ( m.m_NetState.StygianAbyss ) { - //if ( m_Poison != null ) - m.m_NetState.Send( new HealthbarPoison( this ) ); + m_FrozenTimer?.Stop(); - //if ( m_Blessed || m_YellowHealthbar ) - m.m_NetState.Send( new HealthbarYellow( this ) ); - } - - if ( IsDeadBondedPet ) - m.m_NetState.Send( new BondedStatus( 0, m_Serial, 1 ) ); + m_AutoManifestTimer?.Stop(); + } - if ( ObjectPropertyList.Enabled ) - { - m.m_NetState.Send( OPLPacket ); + public virtual bool AllowSkillUse(SkillName name) + { + return true; + } - //foreach ( Item item in m_Items ) - // m.m_NetState.Send( item.OPLPacket ); - } - } - - if ( !inOldRange && CanSee( m ) ) - { - ourState.Send(MobileIncoming.Create(ourState, this, m)); - - if ( ourState.StygianAbyss ) { - //if ( m.Poisoned ) - ourState.Send( new HealthbarPoison( m ) ); - - //if ( m.Blessed || m.YellowHealthbar ) - ourState.Send( new HealthbarYellow( m ) ); - } - - if ( m.IsDeadBondedPet ) - ourState.Send( new BondedStatus( 0, m.m_Serial, 1 ) ); - - if ( ObjectPropertyList.Enabled ) - { - ourState.Send( m.OPLPacket ); - - //foreach ( Item item in m.m_Items ) - // ourState.Send( item.OPLPacket ); - } - } - } - } - - eeable.Free(); - } - else - { - eable = map.GetClientsInRange( newLocation ); - - // We're not attached to a client, so simply send an Incoming - foreach( NetState ns in eable ) { - if ( ( ( isTeleport && ( !ns.HighSeas || !m_NoMoveHS ) ) || !Utility.InUpdateRange( oldLocation, ns.Mobile.Location )) && ns.Mobile.CanSee( this ) ) - { - ns.Send(MobileIncoming.Create(ns, ns.Mobile, this)); - - if ( ns.StygianAbyss ) { - //if ( m_Poison != null ) - ns.Send( new HealthbarPoison( this ) ); - - //if ( m_Blessed || m_YellowHealthbar ) - ns.Send( new HealthbarYellow( this ) ); - } - - if ( IsDeadBondedPet ) - ns.Send( new BondedStatus( 0, m_Serial, 1 ) ); - - if ( ObjectPropertyList.Enabled ) - { - ns.Send( OPLPacket ); - - //foreach ( Item item in m_Items ) - // ns.Send( item.OPLPacket ); - } - } - } - - eable.Free(); - } - } - - OnLocationChange( oldLocation ); - - Region.OnLocationChanged( this, oldLocation ); - } - } - - /// - /// Overridable. Virtual event invoked when changes. - /// - protected virtual void OnLocationChange( Point3D oldLocation ) - { - } - - #region Hair - - private HairInfo m_Hair; - private FacialHairInfo m_FacialHair; - - [CommandProperty( AccessLevel.GameMaster )] - public int HairItemID - { - get - { - if ( m_Hair == null ) - return 0; - - return m_Hair.ItemID; - } - set - { - if ( m_Hair == null && value > 0 ) - m_Hair = new HairInfo( value ); - else if ( value <= 0 ) - m_Hair = null; - else - m_Hair.ItemID = value; - - Delta( MobileDelta.Hair ); - } - } - - // [CommandProperty( AccessLevel.GameMaster )] - // public int HairSerial { get { return HairInfo.FakeSerial( this ); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int FacialHairItemID - { - get - { - if ( m_FacialHair == null ) - return 0; - - return m_FacialHair.ItemID; - } - set - { - if ( m_FacialHair == null && value > 0 ) - m_FacialHair = new FacialHairInfo( value ); - else if ( value <= 0 ) - m_FacialHair = null; - else - m_FacialHair.ItemID = value; - - Delta( MobileDelta.FacialHair ); - } - } - - // [CommandProperty( AccessLevel.GameMaster )] - // public int FacialHairSerial { get { return FacialHairInfo.FakeSerial( this ); } } - - [CommandProperty( AccessLevel.GameMaster )] - public int HairHue - { - get - { - if ( m_Hair == null ) - return 0; - return m_Hair.Hue; - } - set - { - if ( m_Hair != null ) - { - m_Hair.Hue = value; - Delta( MobileDelta.Hair ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public int FacialHairHue - { - get - { - if ( m_FacialHair == null ) - return 0; - - return m_FacialHair.Hue; - } - set - { - if ( m_FacialHair != null ) - { - m_FacialHair.Hue = value; - Delta( MobileDelta.FacialHair ); - } - } - } - - #endregion - - public bool HasFreeHand() - { - return FindItemOnLayer( Layer.TwoHanded ) == null; - } - - private IWeapon m_Weapon; - - [CommandProperty( AccessLevel.GameMaster )] - public virtual IWeapon Weapon - { - get - { - if ( m_Weapon is Item item && !item.Deleted && item.Parent == this && CanSee( item ) ) - return m_Weapon; - - m_Weapon = null; - - item = FindItemOnLayer( Layer.OneHanded ) ?? FindItemOnLayer( Layer.TwoHanded ); - - if ( item is IWeapon weapon ) - return (m_Weapon = weapon); - - return GetDefaultWeapon(); - } - } - - public virtual IWeapon GetDefaultWeapon() - { - return m_DefaultWeapon; - } - - private BankBox m_BankBox; - - [CommandProperty( AccessLevel.GameMaster )] - public BankBox BankBox - { - get - { - if ( m_BankBox != null && !m_BankBox.Deleted && m_BankBox.Parent == this ) - return m_BankBox; - - m_BankBox = FindItemOnLayer( Layer.Bank ) as BankBox; - - if ( m_BankBox == null ) - AddItem( m_BankBox = new BankBox( this ) ); - - return m_BankBox; - } - } - - public BankBox FindBankNoCreate() - { - if ( m_BankBox != null && !m_BankBox.Deleted && m_BankBox.Parent == this ) - return m_BankBox; - - m_BankBox = FindItemOnLayer( Layer.Bank ) as BankBox; - - return m_BankBox; - } - - private Container m_Backpack; - - [CommandProperty( AccessLevel.GameMaster )] - public Container Backpack - { - get - { - if ( m_Backpack != null && !m_Backpack.Deleted && m_Backpack.Parent == this ) - return m_Backpack; - - return (m_Backpack = (FindItemOnLayer( Layer.Backpack ) as Container)); - } - } - - public virtual bool KeepsItemsOnDeath => m_AccessLevel > AccessLevel.Player; - - public Item FindItemOnLayer( Layer layer ) - { - List eq = m_Items; - int count = eq.Count; - - for( int i = 0; i < count; ++i ) - { - Item item = eq[i]; - - if ( !item.Deleted && item.Layer == layer ) - { - return item; - } - } - - return null; - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int X - { - get => m_Location.m_X; - set => Location = new Point3D( value, m_Location.m_Y, m_Location.m_Z ); - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Y - { - get => m_Location.m_Y; - set => Location = new Point3D( m_Location.m_X, value, m_Location.m_Z ); - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Z - { - get => m_Location.m_Z; - set => Location = new Point3D( m_Location.m_X, m_Location.m_Y, value ); - } - - #region Effects & Particles - - public void MovingEffect( IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode ) - { - Effects.SendMovingEffect( this, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode ); - } - - public void MovingEffect( IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes ) - { - Effects.SendMovingEffect( this, to, itemID, speed, duration, fixedDirection, explodes, 0, 0 ); - } - - public void MovingParticles( IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, EffectLayer layer, int unknown ) - { - Effects.SendMovingParticles( this, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, layer, unknown ); - } - - public void MovingParticles( IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, int unknown ) - { - Effects.SendMovingParticles( this, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, (EffectLayer)255, unknown ); - } - - public void MovingParticles( IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int effect, int explodeEffect, int explodeSound, int unknown ) - { - Effects.SendMovingParticles( this, to, itemID, speed, duration, fixedDirection, explodes, effect, explodeEffect, explodeSound, unknown ); - } - - public void MovingParticles( IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int effect, int explodeEffect, int explodeSound ) - { - Effects.SendMovingParticles( this, to, itemID, speed, duration, fixedDirection, explodes, 0, 0, effect, explodeEffect, explodeSound, 0 ); - } - - public void FixedEffect( int itemID, int speed, int duration, int hue, int renderMode ) - { - Effects.SendTargetEffect( this, itemID, speed, duration, hue, renderMode ); - } - - public void FixedEffect( int itemID, int speed, int duration ) - { - Effects.SendTargetEffect( this, itemID, speed, duration, 0, 0 ); - } - - public void FixedParticles( int itemID, int speed, int duration, int effect, int hue, int renderMode, EffectLayer layer, int unknown ) - { - Effects.SendTargetParticles( this, itemID, speed, duration, hue, renderMode, effect, layer, unknown ); - } - - public void FixedParticles( int itemID, int speed, int duration, int effect, int hue, int renderMode, EffectLayer layer ) - { - Effects.SendTargetParticles( this, itemID, speed, duration, hue, renderMode, effect, layer, 0 ); - } - - public void FixedParticles( int itemID, int speed, int duration, int effect, EffectLayer layer, int unknown ) - { - Effects.SendTargetParticles( this, itemID, speed, duration, 0, 0, effect, layer, unknown ); - } - - public void FixedParticles( int itemID, int speed, int duration, int effect, EffectLayer layer ) - { - Effects.SendTargetParticles( this, itemID, speed, duration, 0, 0, effect, layer, 0 ); - } - - public void BoltEffect( int hue ) - { - Effects.SendBoltEffect( this, true, hue ); - } - - #endregion - - public void SendIncomingPacket() - { - if ( m_Map != null ) - { - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state.Mobile.CanSee( this ) ) - { - state.Send(MobileIncoming.Create(state, state.Mobile, this)); - - if ( state.StygianAbyss ) { - if ( m_Poison != null ) - state.Send( new HealthbarPoison( this ) ); - - if ( m_Blessed || m_YellowHealthbar ) - state.Send( new HealthbarYellow( this ) ); - } - - if ( IsDeadBondedPet ) - state.Send( new BondedStatus( 0, m_Serial, 1 ) ); - - if ( ObjectPropertyList.Enabled ) - { - state.Send( OPLPacket ); - - //foreach ( Item item in m_Items ) - // state.Send( item.OPLPacket ); - } - } - } - - eable.Free(); - } - } - - public bool PlaceInBackpack( Item item ) - { - if ( item.Deleted ) - return false; - - Container pack = Backpack; - - return pack != null && pack.TryDropItem( this, item, false ); - } - - public bool AddToBackpack( Item item ) - { - if ( item.Deleted ) - return false; - - if ( !PlaceInBackpack( item ) ) - { - Point3D loc = m_Location; - Map map = m_Map; - - if ( (map == null || map == Map.Internal) && m_LogoutMap != null ) - { - loc = m_LogoutLocation; - map = m_LogoutMap; - } - - item.MoveToWorld( loc, map ); - return false; - } - - return true; - } - - public virtual bool CheckLift( Mobile from, Item item, ref LRReason reject ) - { - return true; - } - - public virtual bool CheckNonlocalLift( Mobile from, Item item ) - { - if ( from == this || (from.AccessLevel > AccessLevel && from.AccessLevel >= AccessLevel.GameMaster) ) - return true; - - return false; - } - - public bool HasTrade - { - get - { - if ( m_NetState != null ) - return m_NetState.Trades.Count > 0; - - return false; - } - } - - public virtual bool CheckTrade( Mobile to, Item item, SecureTradeContainer cont, bool message, bool checkItems, int plusItems, int plusWeight ) - { - return true; - } - public bool OpenTrade(Mobile from) - { - return OpenTrade(from, null); - } - - public virtual bool OpenTrade(Mobile from, Item offer) - { - if (!from.Player || !Player || !from.Alive || !Alive) - { - return false; - } - - NetState ourState = m_NetState; - NetState theirState = from.m_NetState; - - if (ourState == null || theirState == null) - { - return false; - } - - SecureTradeContainer cont = theirState.FindTradeContainer(this); - - if (!from.CheckTrade(this, offer, cont, true, true, 0, 0)) - { - return false; - } - - if (cont == null) - { - cont = theirState.AddTrade(ourState); - } - - if (offer != null) - { - cont.DropItem(offer); - } - - return true; - } - - /// - /// Overridable. Event invoked when a Mobile () drops an onto the Mobile. - /// - public virtual bool OnDragDrop( Mobile from, Item dropped ) - { - if ( from == this ) - { - Container pack = Backpack; - - if ( pack != null ) - return dropped.DropToItem( from, pack, new Point3D( -1, -1, 0 ) ); - - return false; - } - if ( from.InRange( Location, 2 ) ) - { - return OpenTrade( from, dropped ); - } - return false; - } - - public virtual bool CheckEquip( Item item ) - { - for( int i = 0; i < m_Items.Count; ++i ) - if ( m_Items[i].CheckConflictingLayer( this, item, item.Layer ) || item.CheckConflictingLayer( this, m_Items[i], m_Items[i].Layer ) ) - return false; - - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to wear . - /// - /// True if the request is accepted, false if otherwise. - public virtual bool OnEquip( Item item ) - { - // For some reason OSI allows equipping quest items, but they are unmarked in the process - if ( item.QuestItem ) - { - item.QuestItem = false; - SendLocalizedMessage( 1074769 ); // An item must be in your backpack (and not in a container within) to be toggled as a quest item. - } - - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to lift . - /// - /// True if the lift is allowed, false if otherwise. - /// - /// The following example demonstrates usage. It will disallow any attempts to pick up a pick axe if the Mobile does not have enough strength. - /// - /// public override bool OnDragLift( Item item ) - /// { - /// if ( item is Pickaxe && this.Str < 60 ) - /// { - /// SendMessage( "That is too heavy for you to lift." ); - /// return false; - /// } - /// - /// return base.OnDragLift( item ); - /// } - /// - public virtual bool OnDragLift( Item item ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to drop into a . - /// - /// True if the drop is allowed, false if otherwise. - public virtual bool OnDroppedItemInto( Item item, Container container, Point3D loc ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to drop directly onto another , . This is the case of stacking items. - /// - /// True if the drop is allowed, false if otherwise. - public virtual bool OnDroppedItemOnto( Item item, Item target ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to drop into another , . The target item is most likely a . - /// - /// True if the drop is allowed, false if otherwise. - public virtual bool OnDroppedItemToItem( Item item, Item target, Point3D loc ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to give to a Mobile (). - /// - /// True if the drop is allowed, false if otherwise. - public virtual bool OnDroppedItemToMobile( Item item, Mobile target ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when the Mobile attempts to drop to the world at a . - /// - /// True if the drop is allowed, false if otherwise. - public virtual bool OnDroppedItemToWorld( Item item, Point3D location ) - { - return true; - } - - /// - /// Overridable. Virtual event when successfully uses while it's on this Mobile. - /// - /// - public virtual void OnItemUsed( Mobile from, Item item ) - { - } - - public virtual bool CheckNonlocalDrop( Mobile from, Item item, Item target ) - { - if ( from == this || (from.AccessLevel > AccessLevel && from.AccessLevel >= AccessLevel.GameMaster) ) - return true; - - return false; - } - - public virtual bool CheckItemUse( Mobile from, Item item ) - { - return true; - } - - /// - /// Overridable. Virtual event invoked when successfully lifts from this Mobile. - /// - /// - public virtual void OnItemLifted( Mobile from, Item item ) - { - } - - public virtual bool AllowItemUse( Item item ) - { - return true; - } - - public virtual bool AllowEquipFrom( Mobile mob ) - { - return (mob == this || (mob.AccessLevel >= AccessLevel.GameMaster && mob.AccessLevel > AccessLevel)); - } - - public virtual bool EquipItem( Item item ) - { - if ( item == null || item.Deleted || !item.CanEquip( this ) ) - return false; - - if ( CheckEquip( item ) && OnEquip( item ) && item.OnEquip( this ) ) - { - if ( m_Spell != null && !m_Spell.OnCasterEquiping( item ) ) - return false; - - //if ( m_Spell != null && m_Spell.State == SpellState.Casting ) - // m_Spell.Disturb( DisturbType.EquipRequest ); - - AddItem( item ); - return true; - } - - return false; - } - - internal int m_TypeRef; - - public Mobile( Serial serial ) - { - m_Region = Map.Internal.DefaultRegion; - m_Serial = serial; - m_Aggressors = new List(); - m_Aggressed = new List(); - m_NextSkillTime = Core.TickCount; - m_DamageEntries = new List(); - - Type ourType = GetType(); - m_TypeRef = World.m_MobileTypes.IndexOf( ourType ); - - if ( m_TypeRef == -1 ) - { - World.m_MobileTypes.Add( ourType ); - m_TypeRef = World.m_MobileTypes.Count - 1; - } - } - - public Mobile() - { - m_Region = Map.Internal.DefaultRegion; - m_Serial = Serial.NewMobile; - - DefaultMobileInit(); - - World.AddMobile( this ); - - Type ourType = GetType(); - m_TypeRef = World.m_MobileTypes.IndexOf( ourType ); - - if ( m_TypeRef == -1 ) - { - World.m_MobileTypes.Add( ourType ); - m_TypeRef = World.m_MobileTypes.Count - 1; - } - } - - public void DefaultMobileInit() - { - m_StatCap = 225; - m_FollowersMax = 5; - m_Skills = new Skills( this ); - m_Items = new List(); - m_StatMods = new List(); - m_SkillMods = new List(); - Map = Map.Internal; - m_AutoPageNotify = true; - m_Aggressors = new List(); - m_Aggressed = new List(); - m_Virtues = new VirtueInfo(); - m_Stabled = new List(); - m_DamageEntries = new List(); - - m_NextSkillTime = Core.TickCount; - m_CreationTime = DateTime.UtcNow; - } - - private static Queue m_DeltaQueue = new Queue(); - private static Queue m_DeltaQueueR = new Queue(); - - private bool m_InDeltaQueue; - private MobileDelta m_DeltaFlags; - - public virtual void Delta( MobileDelta flag ) - { - if ( m_Map == null || m_Map == Map.Internal || m_Deleted ) - return; - - m_DeltaFlags |= flag; - - if ( !m_InDeltaQueue ) - { - m_InDeltaQueue = true; - - if (_processing) { - lock (m_DeltaQueueR) { - m_DeltaQueueR.Enqueue(this); - - try { - using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) { - op.WriteLine("# {0}", DateTime.UtcNow); - op.WriteLine(new System.Diagnostics.StackTrace()); - op.WriteLine(); - } - } catch { } - } - } else { - m_DeltaQueue.Enqueue( this ); - } - } - - Core.Set(); - } - - private bool m_NoMoveHS; - - public bool NoMoveHS - { - get => m_NoMoveHS; - set => m_NoMoveHS = value; - } - - #region GetDirectionTo[..] - - public Direction GetDirectionTo( int x, int y ) - { - int dx = m_Location.m_X - x; - int dy = m_Location.m_Y - y; - - int rx = (dx - dy) * 44; - int ry = (dx + dy) * 44; - - int ax = Math.Abs( rx ); - int ay = Math.Abs( ry ); - - Direction ret; - - if ( ((ay >> 1) - ax) >= 0 ) - ret = (ry > 0) ? Direction.Up : Direction.Down; - else if ( ((ax >> 1) - ay) >= 0 ) - ret = (rx > 0) ? Direction.Left : Direction.Right; - else if ( rx >= 0 && ry >= 0 ) - ret = Direction.West; - else if ( rx >= 0 && ry < 0 ) - ret = Direction.South; - else if ( rx < 0 && ry < 0 ) - ret = Direction.East; - else - ret = Direction.North; - - return ret; - } - - public Direction GetDirectionTo( Point2D p ) - { - return GetDirectionTo( p.m_X, p.m_Y ); - } - - public Direction GetDirectionTo( Point3D p ) - { - return GetDirectionTo( p.m_X, p.m_Y ); - } - - public Direction GetDirectionTo( IPoint2D p ) - { - if ( p == null ) - return Direction.North; - - return GetDirectionTo( p.X, p.Y ); - } - - #endregion - - public virtual void ProcessDelta() - { - Mobile m = this; - MobileDelta delta; - - delta = m.m_DeltaFlags; - - if ( delta == MobileDelta.None ) - return; - - MobileDelta attrs = delta & MobileDelta.Attributes; - - m.m_DeltaFlags = MobileDelta.None; - m.m_InDeltaQueue = false; - - bool sendHits = false, sendStam = false, sendMana = false, sendAll = false, sendAny = false; - bool sendIncoming = false, sendNonlocalIncoming = false; - bool sendUpdate = false, sendRemove = false; - bool sendPublicStats = false, sendPrivateStats = false; - bool sendMoving = false, sendNonlocalMoving = false; - bool sendOPLUpdate = ObjectPropertyList.Enabled && (delta & MobileDelta.Properties) != 0; - - bool sendHair = false, sendFacialHair = false, removeHair = false, removeFacialHair = false; - - bool sendHealthbarPoison = false, sendHealthbarYellow = false; - - if ( attrs != MobileDelta.None ) - { - sendAny = true; - - if ( attrs == MobileDelta.Attributes ) - { - sendAll = true; - } - else - { - sendHits = ((attrs & MobileDelta.Hits) != 0); - sendStam = ((attrs & MobileDelta.Stam) != 0); - sendMana = ((attrs & MobileDelta.Mana) != 0); - } - } - - if ( (delta & MobileDelta.GhostUpdate) != 0 ) - { - sendNonlocalIncoming = true; - } - - if ( (delta & MobileDelta.Hue) != 0 ) - { - sendNonlocalIncoming = true; - sendUpdate = true; - sendRemove = true; - } - - if ( (delta & MobileDelta.Direction) != 0 ) - { - sendNonlocalMoving = true; - sendUpdate = true; - } - - if ( (delta & MobileDelta.Body) != 0 ) - { - sendUpdate = true; - sendIncoming = true; - } - - /*if ( (delta & MobileDelta.Hue) != 0 ) - { - sendNonlocalIncoming = true; - sendUpdate = true; - } - else if ( (delta & (MobileDelta.Direction | MobileDelta.Body)) != 0 ) - { - sendNonlocalMoving = true; - sendUpdate = true; - } - else*/ - if ( (delta & (MobileDelta.Flags | MobileDelta.Noto)) != 0 ) - { - sendMoving = true; - } - - if ( (delta & MobileDelta.HealthbarPoison) != 0 ) - { - sendHealthbarPoison = true; - } - - if ( (delta & MobileDelta.HealthbarYellow) != 0 ) - { - sendHealthbarYellow = true; - } - - if ( (delta & MobileDelta.Name) != 0 ) - { - sendAll = false; - sendHits = false; - sendAny = sendStam || sendMana; - sendPublicStats = true; - } - - if ( (delta & (MobileDelta.WeaponDamage | MobileDelta.Resistances | MobileDelta.Stat | - MobileDelta.Weight | MobileDelta.Gold | MobileDelta.Armor | MobileDelta.StatCap | - MobileDelta.Followers | MobileDelta.TithingPoints | MobileDelta.Race)) != 0 ) - { - sendPrivateStats = true; - } - - if ( (delta & MobileDelta.Hair) != 0 ) - { - if ( m.HairItemID <= 0 ) - removeHair = true; - - sendHair = true; - } - - if ( (delta & MobileDelta.FacialHair) != 0 ) - { - if ( m.FacialHairItemID <= 0 ) - removeFacialHair = true; - - sendFacialHair = true; - } - - Packet[][] cache = new Packet[2][] { new Packet[8], new Packet[8] }; - - NetState ourState = m.m_NetState; - - if ( ourState != null ) - { - if ( sendUpdate ) - { - ourState.Sequence = 0; - - if ( ourState.StygianAbyss ) - ourState.Send( new MobileUpdate( m ) ); - else - ourState.Send( new MobileUpdateOld( m ) ); - - ClearFastwalkStack(); - } - - if (sendIncoming) - ourState.Send(MobileIncoming.Create(ourState, m, m)); - - if ( ourState.StygianAbyss ) { - if ( sendMoving ) - { - int noto = Notoriety.Compute( m, m ); - ourState.Send( cache[0][noto] = Packet.Acquire( new MobileMoving( m, noto ) ) ); - } - - if ( sendHealthbarPoison ) - ourState.Send( new HealthbarPoison( m ) ); - - if ( sendHealthbarYellow ) - ourState.Send( new HealthbarYellow( m ) ); - } else { - if ( sendMoving || sendHealthbarPoison || sendHealthbarYellow ) - { - int noto = Notoriety.Compute( m, m ); - ourState.Send( cache[1][noto] = Packet.Acquire( new MobileMovingOld( m, noto ) ) ); - } - } - - if ( sendPublicStats || sendPrivateStats ) - { - ourState.Send( new MobileStatusExtended( m, m_NetState ) ); - } - else if ( sendAll ) - { - ourState.Send( new MobileAttributes( m ) ); - } - else if ( sendAny ) - { - if ( sendHits ) - ourState.Send( new MobileHits( m ) ); - - if ( sendStam ) - ourState.Send( new MobileStam( m ) ); - - if ( sendMana ) - ourState.Send( new MobileMana( m ) ); - } - - if ( sendStam || sendMana ) - { - if (m_Party is IParty ip) - { - if ( sendStam ) - ip.OnStamChanged( this ); - - if ( sendMana ) - ip.OnManaChanged( this ); - } - } - - if ( sendHair ) - { - if ( removeHair ) - ourState.Send( new RemoveHair( m ) ); - else - ourState.Send( new HairEquipUpdate( m ) ); - } - - if ( sendFacialHair ) - { - if ( removeFacialHair ) - ourState.Send( new RemoveFacialHair( m ) ); - else - ourState.Send( new FacialHairEquipUpdate( m ) ); - } - - if ( sendOPLUpdate ) - ourState.Send( OPLPacket ); - } - - sendMoving = sendMoving || sendNonlocalMoving; - sendIncoming = sendIncoming || sendNonlocalIncoming; - sendHits = sendHits || sendAll; - - if ( m.m_Map != null && (sendRemove || sendIncoming || sendPublicStats || sendHits || sendMoving || sendOPLUpdate || sendHair || sendFacialHair || sendHealthbarPoison || sendHealthbarYellow) ) - { - Mobile beholder; - - Packet hitsPacket = null; - Packet statPacketTrue = null; - Packet statPacketFalse = null; - Packet deadPacket = null; - Packet hairPacket = null; - Packet facialhairPacket = null; - Packet hbpPacket = null; - Packet hbyPacket = null; - - IPooledEnumerable eable = m.Map.GetClientsInRange(m.m_Location); - - foreach ( NetState state in eable ) { - beholder = state.Mobile; - - if ( beholder != m && beholder.CanSee( m ) ) - { - if ( sendRemove ) - state.Send(RemovePacket); - - if ( sendIncoming ) - { - state.Send(MobileIncoming.Create(state, beholder, m)); - - if ( m.IsDeadBondedPet ) - { - if (deadPacket == null) - deadPacket = Packet.Acquire(new BondedStatus(0, m.m_Serial, 1)); - - state.Send( deadPacket ); - } - } - - if ( state.StygianAbyss ) { - if ( sendMoving ) - { - int noto = Notoriety.Compute( beholder, m ); - - Packet p = cache[0][noto]; - - if (p == null) - cache[0][noto] = p = Packet.Acquire(new MobileMoving(m, noto)); - - state.Send( p ); - } - - if ( sendHealthbarPoison ) { - if (hbpPacket == null) - hbpPacket = Packet.Acquire(new HealthbarPoison(m)); - - state.Send( hbpPacket ); - } - - if ( sendHealthbarYellow ) { - if (hbyPacket == null) - hbyPacket = Packet.Acquire(new HealthbarYellow(m)); - - state.Send( hbyPacket ); - } - } else { - if ( sendMoving || sendHealthbarPoison || sendHealthbarYellow ) - { - int noto = Notoriety.Compute( beholder, m ); - - Packet p = cache[1][noto]; - - if (p == null) - cache[1][noto] = p = Packet.Acquire(new MobileMovingOld(m, noto)); - - state.Send( p ); - } - } - - if ( sendPublicStats ) - { - if ( m.CanBeRenamedBy( beholder ) ) - { - if (statPacketTrue == null) - statPacketTrue = Packet.Acquire(new MobileStatusCompact(true, m)); - - state.Send( statPacketTrue ); - } - else - { - if (statPacketFalse == null) - statPacketFalse = Packet.Acquire(new MobileStatusCompact(false, m)); - - state.Send( statPacketFalse ); - } - } - else if ( sendHits ) - { - if (hitsPacket == null) - hitsPacket = Packet.Acquire(new MobileHitsN(m)); - - state.Send( hitsPacket ); - } - - if ( sendHair ) - { - if (hairPacket == null) { - if (removeHair) - hairPacket = Packet.Acquire(new RemoveHair(m)); - else - hairPacket = Packet.Acquire(new HairEquipUpdate(m)); - } - - state.Send( hairPacket ); - } - - if ( sendFacialHair ) - { - if (facialhairPacket == null) { - if (removeFacialHair) - facialhairPacket = Packet.Acquire(new RemoveFacialHair(m)); - else - facialhairPacket = Packet.Acquire(new FacialHairEquipUpdate(m)); - } - - state.Send( facialhairPacket ); - } - - if ( sendOPLUpdate ) - state.Send(OPLPacket); - } - } - - Packet.Release( hitsPacket ); - Packet.Release( statPacketTrue ); - Packet.Release( statPacketFalse ); - Packet.Release( deadPacket ); - Packet.Release( hairPacket ); - Packet.Release( facialhairPacket ); - Packet.Release( hbpPacket ); - Packet.Release( hbyPacket ); - - eable.Free(); - } - - if ( sendMoving || sendNonlocalMoving || sendHealthbarPoison || sendHealthbarYellow ) - { - for( int i = 0; i < cache.Length; ++i ) - for( int j = 0; j < cache[i].Length; ++j ) - Packet.Release(ref cache[i][j]); - } - } - - private static bool _processing = false; - - public static void ProcessDeltaQueue() - { - _processing = true; - - if (m_DeltaQueue.Count >= 512) { - Parallel.ForEach(m_DeltaQueue, m => m.ProcessDelta()); - m_DeltaQueue.Clear(); - } else { - while (m_DeltaQueue.Count > 0) m_DeltaQueue.Dequeue().ProcessDelta(); - } - - _processing = false; - - while (m_DeltaQueueR.Count > 0) m_DeltaQueueR.Dequeue().ProcessDelta(); - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Kills - { - get => m_Kills; - set - { - int oldValue = m_Kills; - - if ( m_Kills != value ) - { - m_Kills = value; - - if ( m_Kills < 0 ) - m_Kills = 0; - - if ( (oldValue >= 5) != (m_Kills >= 5) ) - { - Delta( MobileDelta.Noto ); - InvalidateProperties(); - } - - OnKillsChange( oldValue ); - } - } - } - - public virtual void OnKillsChange( int oldValue ) - { - } - - [CommandProperty( AccessLevel.GameMaster )] - public int ShortTermMurders - { - get => m_ShortTermMurders; - set - { - if ( m_ShortTermMurders != value ) - { - m_ShortTermMurders = value; - - if ( m_ShortTermMurders < 0 ) - m_ShortTermMurders = 0; - } - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public bool Criminal - { - get => m_Criminal; - set - { - if ( m_Criminal != value ) - { - m_Criminal = value; - Delta( MobileDelta.Noto ); - InvalidateProperties(); - } - - if ( m_Criminal ) - { - if ( m_ExpireCriminal == null ) - m_ExpireCriminal = new ExpireCriminalTimer( this ); - else - m_ExpireCriminal.Stop(); - - m_ExpireCriminal.Start(); - } - else if ( m_ExpireCriminal != null ) - { - m_ExpireCriminal.Stop(); - m_ExpireCriminal = null; - } - } - } - - public bool CheckAlive() - { - return CheckAlive( true ); - } - - public bool CheckAlive( bool message ) - { - if ( !Alive ) - { - if ( message ) - LocalOverheadMessage( MessageType.Regular, 0x3B2, 1019048 ); // I am dead and cannot do that. - - return false; - } - - return true; - } - - #region Overhead messages - - public void PublicOverheadMessage( MessageType type, int hue, bool ascii, string text ) - { - PublicOverheadMessage( type, hue, ascii, text, true ); - } - - public void PublicOverheadMessage( MessageType type, int hue, bool ascii, string text, bool noLineOfSight ) - { - if ( m_Map != null ) - { - Packet p = null; - - if ( ascii ) - p = new AsciiMessage( m_Serial, Body, type, hue, 3, Name, text ); - else - p = new UnicodeMessage( m_Serial, Body, type, hue, 3, m_Language, Name, text ); - - p.Acquire(); - - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state.Mobile.CanSee( this ) && (noLineOfSight || state.Mobile.InLOS( this )) ) { - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - public void PublicOverheadMessage( MessageType type, int hue, int number ) - { - PublicOverheadMessage( type, hue, number, "", true ); - } - - public void PublicOverheadMessage( MessageType type, int hue, int number, string args ) - { - PublicOverheadMessage( type, hue, number, args, true ); - } - - public void PublicOverheadMessage( MessageType type, int hue, int number, string args, bool noLineOfSight ) - { - if ( m_Map != null ) - { - Packet p = Packet.Acquire( new MessageLocalized( m_Serial, Body, type, hue, 3, number, Name, args ) ); - - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state.Mobile.CanSee( this ) && (noLineOfSight || state.Mobile.InLOS( this )) ) { - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - public void PublicOverheadMessage( MessageType type, int hue, int number, AffixType affixType, string affix, string args ) - { - PublicOverheadMessage( type, hue, number, affixType, affix, args, true ); - } - - public void PublicOverheadMessage( MessageType type, int hue, int number, AffixType affixType, string affix, string args, bool noLineOfSight ) - { - if ( m_Map != null ) - { - Packet p = Packet.Acquire( new MessageLocalizedAffix( m_Serial, Body, type, hue, 3, number, Name, affixType, affix, args ) ); - - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state.Mobile.CanSee( this ) && (noLineOfSight || state.Mobile.InLOS( this )) ) { - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - public void PrivateOverheadMessage( MessageType type, int hue, bool ascii, string text, NetState state ) - { - if ( state == null ) - return; - - if ( ascii ) - state.Send( new AsciiMessage( m_Serial, Body, type, hue, 3, Name, text ) ); - else - state.Send( new UnicodeMessage( m_Serial, Body, type, hue, 3, m_Language, Name, text ) ); - } - - public void PrivateOverheadMessage( MessageType type, int hue, int number, NetState state ) - { - PrivateOverheadMessage( type, hue, number, "", state ); - } - - public void PrivateOverheadMessage( MessageType type, int hue, int number, string args, NetState state ) - { - if ( state == null ) - return; - - state.Send( new MessageLocalized( m_Serial, Body, type, hue, 3, number, Name, args ) ); - } - - public void LocalOverheadMessage( MessageType type, int hue, bool ascii, string text ) - { - NetState ns = m_NetState; - - if ( ns != null ) - { - if ( ascii ) - ns.Send( new AsciiMessage( m_Serial, Body, type, hue, 3, Name, text ) ); - else - ns.Send( new UnicodeMessage( m_Serial, Body, type, hue, 3, m_Language, Name, text ) ); - } - } - - public void LocalOverheadMessage( MessageType type, int hue, int number ) - { - LocalOverheadMessage( type, hue, number, "" ); - } - - public void LocalOverheadMessage( MessageType type, int hue, int number, string args ) - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( new MessageLocalized( m_Serial, Body, type, hue, 3, number, Name, args ) ); - } - - public void NonlocalOverheadMessage( MessageType type, int hue, int number ) - { - NonlocalOverheadMessage( type, hue, number, "" ); - } - - public void NonlocalOverheadMessage( MessageType type, int hue, int number, string args ) - { - if ( m_Map != null ) - { - Packet p = Packet.Acquire( new MessageLocalized( m_Serial, Body, type, hue, 3, number, Name, args ) ); - - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state != m_NetState && state.Mobile.CanSee( this ) ) { - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - public void NonlocalOverheadMessage( MessageType type, int hue, bool ascii, string text ) - { - if ( m_Map != null ) - { - Packet p = null; - - if ( ascii ) - p = new AsciiMessage( m_Serial, Body, type, hue, 3, Name, text ); - else - p = new UnicodeMessage( m_Serial, Body, type, hue, 3, Language, Name, text ); - - p.Acquire(); - - IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); - - foreach( NetState state in eable ) { - if ( state != m_NetState && state.Mobile.CanSee( this ) ) { - state.Send( p ); - } - } - - Packet.Release( p ); - - eable.Free(); - } - } - - #endregion - - #region SendLocalizedMessage - - public void SendLocalizedMessage( int number ) - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( MessageLocalized.InstantiateGeneric( number ) ); - } - - public void SendLocalizedMessage( int number, string args ) - { - SendLocalizedMessage( number, args, 0x3B2 ); - } - - public void SendLocalizedMessage( int number, string args, int hue ) - { - if ( hue == 0x3B2 && (args == null || args.Length == 0) ) - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( MessageLocalized.InstantiateGeneric( number ) ); - } - else - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( new MessageLocalized( Serial.MinusOne, -1, MessageType.Regular, hue, 3, number, "System", args ) ); - } - } - - public void SendLocalizedMessage( int number, bool append, string affix ) - { - SendLocalizedMessage( number, append, affix, "", 0x3B2 ); - } - - public void SendLocalizedMessage( int number, bool append, string affix, string args ) - { - SendLocalizedMessage( number, append, affix, args, 0x3B2 ); - } - - public void SendLocalizedMessage( int number, bool append, string affix, string args, int hue ) - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( new MessageLocalizedAffix( Serial.MinusOne, -1, MessageType.Regular, hue, 3, number, "System", (append ? AffixType.Append : AffixType.Prepend) | AffixType.System, affix, args ) ); - } - - #endregion - - public void LaunchBrowser( string url ) - { - m_NetState?.LaunchBrowser( url ); - } - - #region Send[ASCII]Message - - public void SendMessage( string text ) - { - SendMessage( 0x3B2, text ); - } - - public void SendMessage( string format, params object[] args ) - { - SendMessage( 0x3B2, String.Format( format, args ) ); - } - - public void SendMessage( int hue, string text ) - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( new UnicodeMessage( Serial.MinusOne, -1, MessageType.Regular, hue, 3, "ENU", "System", text ) ); - } - - public void SendMessage( int hue, string format, params object[] args ) - { - SendMessage( hue, String.Format( format, args ) ); - } - - public void SendAsciiMessage( string text ) - { - SendAsciiMessage( 0x3B2, text ); - } - - public void SendAsciiMessage( string format, params object[] args ) - { - SendAsciiMessage( 0x3B2, String.Format( format, args ) ); - } - - public void SendAsciiMessage( int hue, string text ) - { - NetState ns = m_NetState; - - if ( ns != null ) - ns.Send( new AsciiMessage( Serial.MinusOne, -1, MessageType.Regular, hue, 3, "System", text ) ); - } - - public void SendAsciiMessage( int hue, string format, params object[] args ) - { - SendAsciiMessage( hue, String.Format( format, args ) ); - } - - #endregion - - #region InRange - public bool InRange( Point2D p, int range ) - { - return (p.m_X >= (m_Location.m_X - range)) - && (p.m_X <= (m_Location.m_X + range)) - && (p.m_Y >= (m_Location.m_Y - range)) - && (p.m_Y <= (m_Location.m_Y + range)); - } - - public bool InRange( Point3D p, int range ) - { - return (p.m_X >= (m_Location.m_X - range)) - && (p.m_X <= (m_Location.m_X + range)) - && (p.m_Y >= (m_Location.m_Y - range)) - && (p.m_Y <= (m_Location.m_Y + range)); - } - - public bool InRange( IPoint2D p, int range ) - { - return (p.X >= (m_Location.m_X - range)) - && (p.X <= (m_Location.m_X + range)) - && (p.Y >= (m_Location.m_Y - range)) - && (p.Y <= (m_Location.m_Y + range)); - } - #endregion - - public void InitStats( int str, int dex, int intel ) - { - m_Str = str; - m_Dex = dex; - m_Int = intel; - - Hits = HitsMax; - Stam = StamMax; - Mana = ManaMax; - - Delta( MobileDelta.Stat | MobileDelta.Hits | MobileDelta.Stam | MobileDelta.Mana ); - } - - public virtual void DisplayPaperdollTo( Mobile to ) - { - EventSink.InvokePaperdollRequest( new PaperdollRequestEventArgs( to, this ) ); - } - - private static bool m_DisableDismountInWarmode; - - public static bool DisableDismountInWarmode { get => m_DisableDismountInWarmode; - set => m_DisableDismountInWarmode = value; - } - - #region OnDoubleClick[..] - - /// - /// Overridable. Event invoked when the Mobile is double clicked. By default, this method can either dismount or open the paperdoll. - /// - /// - /// - public virtual void OnDoubleClick( Mobile from ) - { - if ( this == from && (!m_DisableDismountInWarmode || !m_Warmode) ) - { - IMount mount = Mount; - - if ( mount != null ) - { - mount.Rider = null; - return; - } - } - - if ( CanPaperdollBeOpenedBy( from ) ) - DisplayPaperdollTo( from ); - } - - /// - /// Overridable. Virtual event invoked when the Mobile is double clicked by someone who is over 18 tiles away. - /// - /// - public virtual void OnDoubleClickOutOfRange( Mobile from ) - { - } - - /// - /// Overridable. Virtual event invoked when the Mobile is double clicked by someone who can no longer see the Mobile. This may happen, for example, using 'Last Object' after the Mobile has hidden. - /// - /// - public virtual void OnDoubleClickCantSee( Mobile from ) - { - } - - /// - /// Overridable. Event invoked when the Mobile is double clicked by someone who is not alive. Similar to , this method will show the paperdoll. It does not, however, provide any dismount functionality. - /// - /// - public virtual void OnDoubleClickDead( Mobile from ) - { - if ( CanPaperdollBeOpenedBy( from ) ) - DisplayPaperdollTo( from ); - } - - #endregion - - /// - /// Overridable. Event invoked when the Mobile requests to open his own paperdoll via the 'Open Paperdoll' macro. - /// - public virtual void OnPaperdollRequest() - { - if ( CanPaperdollBeOpenedBy( this ) ) - DisplayPaperdollTo( this ); - } - - private static int m_BodyWeight = 14; - - public static int BodyWeight { get => m_BodyWeight; - set => m_BodyWeight = value; - } - - /// - /// Overridable. Event invoked when wants to see this Mobile's stats. - /// - /// - public virtual void OnStatsQuery( Mobile from ) - { - if ( from.Map == Map && Utility.InUpdateRange( this, from ) && from.CanSee( this ) ) - from.Send( new MobileStatus( from, this, m_NetState ) ); - - if ( from == this ) - Send( new StatLockInfo( this ) ); - - if ( m_Party is IParty ip ) - ip.OnStatsQuery( from, this ); - } - - /// - /// Overridable. Event invoked when wants to see this Mobile's skills. - /// - public virtual void OnSkillsQuery( Mobile from ) - { - if ( from == this ) - Send( new SkillUpdate( m_Skills ) ); - } - - /// - /// Overridable. Virtual event invoked when changes. - /// - public virtual void OnRegionChange( Region Old, Region New ) - { - } - - private Item m_MountItem; - - [CommandProperty( AccessLevel.GameMaster )] - public IMount Mount - { - get - { - IMountItem mountItem = null; - - if ( m_MountItem?.Deleted == false && m_MountItem.Parent == this ) - mountItem = (IMountItem)m_MountItem; - - if ( mountItem == null ) - m_MountItem = (mountItem = (FindItemOnLayer( Layer.Mount ) as IMountItem)) as Item; - - return mountItem?.Mount; - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Mounted => (Mount != null); - - private QuestArrow m_QuestArrow; - - public QuestArrow QuestArrow - { - get => m_QuestArrow; - set - { - if ( m_QuestArrow != value ) - { - m_QuestArrow?.Stop(); - - m_QuestArrow = value; - } - } - } - - private static string[] m_GuildTypes = new[] - { - "", - " (Chaos)", - " (Order)" - }; - - public virtual bool CanTarget => true; - public virtual bool ClickTitle => true; - - public virtual bool PropertyTitle => m_OldPropertyTitles ? ClickTitle : true; - - private static bool m_DisableHiddenSelfClick = true; - private static bool m_AsciiClickMessage = true; - private static bool m_GuildClickMessage = true; - private static bool m_OldPropertyTitles; - - public static bool DisableHiddenSelfClick { get => m_DisableHiddenSelfClick; - set => m_DisableHiddenSelfClick = value; - } - public static bool AsciiClickMessage { get => m_AsciiClickMessage; - set => m_AsciiClickMessage = value; - } - public static bool GuildClickMessage { get => m_GuildClickMessage; - set => m_GuildClickMessage = value; - } - public static bool OldPropertyTitles { get => m_OldPropertyTitles; - set => m_OldPropertyTitles = value; - } - - public virtual bool ShowFameTitle //(m_Player || m_Body.IsHuman) && m_Fame >= 10000; } - => true; - - /// - /// Overridable. Event invoked when the Mobile is single clicked. - /// - public virtual void OnSingleClick( Mobile from ) - { - if ( m_Deleted ) - return; - if ( AccessLevel == AccessLevel.Player && DisableHiddenSelfClick && Hidden && from == this ) - return; - - if ( m_GuildClickMessage ) - { - BaseGuild guild = m_Guild; - - if ( guild != null && (m_DisplayGuildTitle || (m_Player && guild.Type != GuildType.Regular)) ) - { - string title = GuildTitle; - string type; - - if ( title == null ) - title = ""; - else - title = title.Trim(); - - if ( guild.Type >= 0 && (int)guild.Type < m_GuildTypes.Length ) - type = m_GuildTypes[(int)guild.Type]; - else - type = ""; - - string text = String.Format( title.Length <= 0 ? "[{1}]{2}" : "[{0}, {1}]{2}", title, guild.Abbreviation, type ); - - PrivateOverheadMessage( MessageType.Regular, SpeechHue, true, text, from.NetState ); - } - } - - int hue; - - if ( m_NameHue != -1 ) - hue = m_NameHue; - else if ( AccessLevel > AccessLevel.Player ) - hue = 11; - else - hue = Notoriety.GetHue( Notoriety.Compute( from, this ) ); - - string name = Name; - - if ( name == null ) - name = String.Empty; - - string prefix = ""; - - if ( ShowFameTitle && (m_Player || m_Body.IsHuman) && m_Fame >= 10000 ) - prefix = (m_Female ? "Lady" : "Lord"); - - string suffix = ""; - - if ( ClickTitle && Title != null && Title.Length > 0 ) - suffix = Title; - - suffix = ApplyNameSuffix( suffix ); - - string val; - - if ( prefix.Length > 0 && suffix.Length > 0 ) - val = String.Concat( prefix, " ", name, " ", suffix ); - else if ( prefix.Length > 0 ) - val = String.Concat( prefix, " ", name ); - else if ( suffix.Length > 0 ) - val = String.Concat( name, " ", suffix ); - else - val = name; - - PrivateOverheadMessage( MessageType.Label, hue, m_AsciiClickMessage, val, from.NetState ); - } - - public bool CheckSkill( SkillName skill, double minSkill, double maxSkill ) - { - if ( m_SkillCheckLocationHandler == null ) - return false; - return m_SkillCheckLocationHandler( this, skill, minSkill, maxSkill ); - } - - public bool CheckSkill( SkillName skill, double chance ) - { - if ( m_SkillCheckDirectLocationHandler == null ) - return false; - return m_SkillCheckDirectLocationHandler( this, skill, chance ); - } - - public bool CheckTargetSkill( SkillName skill, object target, double minSkill, double maxSkill ) - { - if ( m_SkillCheckTargetHandler == null ) - return false; - - return m_SkillCheckTargetHandler( this, skill, target, minSkill, maxSkill ); - } - - public bool CheckTargetSkill( SkillName skill, object target, double chance ) - { - if ( m_SkillCheckDirectTargetHandler == null ) - return false; - - return m_SkillCheckDirectTargetHandler( this, skill, target, chance ); - } - - public virtual void DisruptiveAction() - { - if ( Meditating ) - { - Meditating = false; - SendLocalizedMessage( 500134 ); // You stop meditating. - } - } - - #region Armor - public Item ShieldArmor => FindItemOnLayer( Layer.TwoHanded ); - - public Item NeckArmor => FindItemOnLayer( Layer.Neck ); - - public Item HandArmor => FindItemOnLayer( Layer.Gloves ); - - public Item HeadArmor => FindItemOnLayer( Layer.Helm ); - - public Item ArmsArmor => FindItemOnLayer( Layer.Arms ); - - public Item LegsArmor - { - get - { - if ( !(FindItemOnLayer( Layer.InnerLegs ) is Item ar) ) - ar = FindItemOnLayer( Layer.Pants ); - - return ar; - } - } - - public Item ChestArmor - { - get - { - if ( !(FindItemOnLayer( Layer.InnerTorso ) is Item ar) ) - ar = FindItemOnLayer( Layer.Shirt ); - - return ar; - } - } - - public Item Talisman => FindItemOnLayer( Layer.Talisman ); - - #endregion - - /// - /// Gets or sets the maximum attainable value for , , and . - /// - [CommandProperty( AccessLevel.GameMaster )] - public int StatCap - { - get => m_StatCap; - set - { - if ( m_StatCap != value ) - { - m_StatCap = value; - - Delta( MobileDelta.StatCap ); - } - } - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool Meditating - { - get => m_Meditating; - set => m_Meditating = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool CanSwim - { - get => m_CanSwim; - set => m_CanSwim = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool CantWalk - { - get => m_CantWalk; - set => m_CantWalk = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public bool CanHearGhosts - { - get => m_CanHearGhosts || AccessLevel >= AccessLevel.Counselor; - set => m_CanHearGhosts = value; - } - - [CommandProperty( AccessLevel.GameMaster )] - public int RawStatTotal => RawStr + RawDex + RawInt; - - public long NextSpellTime - { - get => m_NextSpellTime; - set => m_NextSpellTime = value; - } - - /// - /// Overridable. Virtual event invoked when the sector this Mobile is in gets activated. - /// - public virtual void OnSectorActivate() - { - } - - /// - /// Overridable. Virtual event invoked when the sector this Mobile is in gets deactivated. - /// - public virtual void OnSectorDeactivate() - { - } - } -} + public virtual bool UseSkill(SkillName name) + { + return Skills.UseSkill(this, name); + } + + public virtual bool UseSkill(int skillID) + { + return Skills.UseSkill(this, skillID); + } + + public virtual DeathMoveResult GetParentMoveResultFor(Item item) + { + return item.OnParentDeath(this); + } + + public virtual DeathMoveResult GetInventoryMoveResultFor(Item item) + { + return item.OnInventoryDeath(this); + } + + public virtual void Kill() + { + if (!CanBeDamaged()) + return; + if (!Alive || IsDeadBondedPet) + return; + if (Deleted) + return; + if (!Region.OnBeforeDeath(this)) + return; + if (!OnBeforeDeath()) + return; + + BankBox box = FindBankNoCreate(); + + if (box != null && box.Opened) + box.Close(); + + m_NetState?.CancelAllTrades(); + + m_Spell?.OnCasterKilled(); + //m_Spell.Disturb( DisturbType.Kill ); + + m_Target?.Cancel(this, TargetCancelType.Canceled); + + DisruptiveAction(); + + Warmode = false; + + DropHolding(); + + Hits = 0; + Stam = 0; + Mana = 0; + + Poison = null; + Combatant = null; + + if (Paralyzed) + { + Paralyzed = false; + + m_ParaTimer?.Stop(); + } + + if (Frozen) + { + Frozen = false; + + m_FrozenTimer?.Stop(); + } + + List content = new List(); + List equip = new List(); + List moveToPack = new List(); + + List itemsCopy = new List(Items); + + Container pack = Backpack; + + for (int i = 0; i < itemsCopy.Count; ++i) + { + Item item = itemsCopy[i]; + + if (item == pack) + continue; + + DeathMoveResult res = GetParentMoveResultFor(item); + + switch (res) + { + case DeathMoveResult.MoveToCorpse: + { + content.Add(item); + equip.Add(item); + break; + } + case DeathMoveResult.MoveToBackpack: + { + moveToPack.Add(item); + break; + } + } + } + + if (pack != null) + { + List packCopy = new List(pack.Items); + + for (int i = 0; i < packCopy.Count; ++i) + { + Item item = packCopy[i]; + + DeathMoveResult res = GetInventoryMoveResultFor(item); + + if (res == DeathMoveResult.MoveToCorpse) + content.Add(item); + else + moveToPack.Add(item); + } + + for (int i = 0; i < moveToPack.Count; ++i) + { + Item item = moveToPack[i]; + + if (RetainPackLocsOnDeath && item.Parent == pack) + continue; + + pack.DropItem(item); + } + } + + HairInfo hair = null; + if (m_Hair != null) + hair = new HairInfo(m_Hair.ItemID, m_Hair.Hue); + + FacialHairInfo facialhair = null; + if (m_FacialHair != null) + facialhair = new FacialHairInfo(m_FacialHair.ItemID, m_FacialHair.Hue); + + Container c = CreateCorpseHandler?.Invoke(this, hair, facialhair, content, equip); + + + /*m_Corpse = c; + + for ( int i = 0; c != null && i < content.Count; ++i ) + c.DropItem( (Item)content[i] ); + + if ( c != null ) + c.MoveToWorld( this.Location, this.Map );*/ + + if (m_Map != null) + { + Packet animPacket = null; + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state != m_NetState) + { + if (animPacket == null) + animPacket = Packet.Acquire(new DeathAnimation(this, c)); + ; + + state.Send(animPacket); + + if (!state.Mobile.CanSee(this)) state.Send(RemovePacket); + } + + Packet.Release(animPacket); + + eable.Free(); + } + + Region.OnDeath(this); + OnDeath(c); + } + + /// + /// Overridable. Event invoked before the Mobile is killed. + /// + /// + /// + /// True to continue with death, false to override it. + public virtual bool OnBeforeDeath() + { + return true; + } + + /// + /// Overridable. Event invoked after the Mobile is killed. Primarily, this method is responsible for + /// deleting an NPC or turning a PC into a ghost. + /// + /// + /// + public virtual void OnDeath(Container c) + { + int sound = GetDeathSound(); + + if (sound >= 0) + Effects.PlaySound(this, Map, sound); + + if (!m_Player) + { + Delete(); + } + else + { + Send(DeathStatus.Instantiate(true)); + + Warmode = false; + + BodyMod = 0; + //Body = this.Female ? 0x193 : 0x192; + Body = Race.GhostBody(this); + + Item deathShroud = new Item(0x204E); + + deathShroud.Movable = false; + deathShroud.Layer = Layer.OuterTorso; + + AddItem(deathShroud); + + Items.Remove(deathShroud); + Items.Insert(0, deathShroud); + + Poison = null; + Combatant = null; + + Hits = 0; + Stam = 0; + Mana = 0; + + EventSink.InvokePlayerDeath(new PlayerDeathEventArgs(this)); + + ProcessDeltaQueue(); + + Send(DeathStatus.Instantiate(false)); + + CheckStatTimers(); + } + } + + public virtual bool CheckTarget(Mobile from, Target targ, object targeted) + { + return true; + } + + public virtual void Use(Item item) + { + if (item == null || item.Deleted || item.QuestItem || Deleted) + return; + + DisruptiveAction(); + + if (m_Spell != null && !m_Spell.OnCasterUsingObject(item)) + return; + + object root = item.RootParent; + bool okay = false; + + if (!Utility.InUpdateRange(this, item.GetWorldLocation())) + { + item.OnDoubleClickOutOfRange(this); + } + else if (!CanSee(item)) + { + item.OnDoubleClickCantSee(this); + } + else if (!item.IsAccessibleTo(this)) + { + Region reg = Region.Find(item.GetWorldLocation(), item.Map); + + if (reg?.SendInaccessibleMessage(item, this) != true) + item.OnDoubleClickNotAccessible(this); + } + else if (!CheckAlive(false)) + { + item.OnDoubleClickDead(this); + } + else if (item.InSecureTrade) + { + item.OnDoubleClickSecureTrade(this); + } + else if (!AllowItemUse(item)) + { + okay = false; + } + else if (!item.CheckItemUse(this, item)) + { + okay = false; + } + else if (root is Mobile mobile && mobile.IsSnoop(this)) + { + item.OnSnoop(this); + } + else if (Region.OnDoubleClick(this, item)) + { + okay = true; + } + + if (okay) + { + // TODO: Is this correct? + if (!item.Deleted) + item.OnItemUsed(this, item); + + // TODO: Is this correct? + if (!item.Deleted) + item.OnDoubleClick(this); + } + } + + public virtual void Use(Mobile m) + { + if (m == null || m.Deleted || Deleted) + return; + + DisruptiveAction(); + + if (m_Spell != null && !m_Spell.OnCasterUsingObject(m)) + return; + + if (!Utility.InUpdateRange(this, m)) + m.OnDoubleClickOutOfRange(this); + else if (!CanSee(m)) + m.OnDoubleClickCantSee(this); + else if (!CheckAlive(false)) + m.OnDoubleClickDead(this); + else if (Region.OnDoubleClick(this, m) && !m.Deleted) + m.OnDoubleClick(this); + } + + public virtual void Lift(Item item, int amount, out bool rejected, out LRReason reject) + { + rejected = true; + reject = LRReason.Inspecific; + + if (item == null) + return; + + Mobile from = this; + NetState state = m_NetState; + + if (from.AccessLevel >= AccessLevel.GameMaster || Core.TickCount - from.NextActionTime >= 0) + { + if (from.CheckAlive()) + { + from.DisruptiveAction(); + + if (from.Holding != null) + { + reject = LRReason.AreHolding; + } + else if (from.AccessLevel < AccessLevel.GameMaster && !from.InRange(item.GetWorldLocation(), 2)) + { + reject = LRReason.OutOfRange; + } + else if (!from.CanSee(item) || !from.InLOS(item)) + { + reject = LRReason.OutOfSight; + } + else if (!item.VerifyMove(from)) + { + reject = LRReason.CannotLift; + } + else if (!item.IsAccessibleTo(from)) + { + reject = LRReason.CannotLift; + } + else if (item.Nontransferable && amount != item.Amount) + { + if (item.QuestItem) + from.SendLocalizedMessage(1074868); // Stacks of quest items cannot be unstacked. + + reject = LRReason.CannotLift; + } + else if (!item.CheckLift(from, item, ref reject)) + { + } + else + { + object root = item.RootParent; + + if (root is Mobile mobile && !mobile.CheckNonlocalLift(from, item)) + { + reject = LRReason.TryToSteal; + } + else if (!from.OnDragLift(item) || !item.OnDragLift(from)) + { + reject = LRReason.Inspecific; + } + else if (!from.CheckAlive()) + { + reject = LRReason.Inspecific; + } + else + { + item.SetLastMoved(); + + if (item.Spawner != null) + { + item.Spawner.Remove(item); + item.Spawner = null; + } + + if (amount == 0) + amount = 1; + + if (amount > item.Amount) + amount = item.Amount; + + int oldAmount = item.Amount; + //item.Amount = amount; //Set in LiftItemDupe + + if (amount < oldAmount) + LiftItemDupe(item, amount); + //item.Dupe( oldAmount - amount ); + + Map map = from.Map; + + if (DragEffects && map != null && (root == null || root is Item)) + { + IPooledEnumerable eable = map.GetClientsInRange(from.Location); + Packet p = null; + Item rootItem = root as Item; + + foreach (NetState ns in eable) + if (ns.Mobile != from && ns.Mobile.CanSee(from) && ns.Mobile.InLOS(from) && + ns.Mobile.CanSee(root)) + { + if (p == null) + { + IEntity src = new Entity(rootItem?.Serial ?? Serial.Zero, + rootItem?.Location ?? item.Location, map); + + p = Packet.Acquire(new DragEffect(src, from, item.ItemID, item.Hue, amount)); + } + + ns.Send(p); + } + + Packet.Release(p); + + eable.Free(); + } + + Point3D fixLoc = item.Location; + Map fixMap = item.Map; + bool shouldFix = item.Parent == null; + + item.RecordBounce(); + item.OnItemLifted(from, item); + item.Internalize(); + + from.Holding = item; + + int liftSound = item.GetLiftSound(from); + + if (liftSound != -1) + from.Send(new PlaySound(liftSound, from)); + + from.NextActionTime = Core.TickCount + ActionDelay; + + if (fixMap != null && shouldFix) + fixMap.FixColumn(fixLoc.m_X, fixLoc.m_Y); + + reject = LRReason.Inspecific; + rejected = false; + } + } + } + else + { + reject = LRReason.Inspecific; + } + } + else + { + SendActionMessage(); + reject = LRReason.Inspecific; + } + + if (rejected && state != null) + { + state.Send(new LiftRej(reject)); + + if (item.Deleted) + return; + + if (item.Parent is Item) + { + if (state.ContainerGridLines) + state.Send(new ContainerContentUpdate6017(item)); + else + state.Send(new ContainerContentUpdate(item)); + } + else if (item.Parent is Mobile) + { + state.Send(new EquipUpdate(item)); + } + else + { + item.SendInfoTo(state); + } + + if (ObjectPropertyList.Enabled && item.Parent != null) + state.Send(item.OPLPacket); + } + } + + public static Item LiftItemDupe(Item oldItem, int amount) + { + Item item; + try + { + item = (Item)Activator.CreateInstance(oldItem.GetType()); + } + catch + { + Console.WriteLine( + "Warning: 0x{0:X}: Item must have a zero paramater constructor to be separated from a stack. '{1}'.", + oldItem.Serial.Value, oldItem.GetType().Name); + return null; + } + + item.Visible = oldItem.Visible; + item.Movable = oldItem.Movable; + item.LootType = oldItem.LootType; + item.Direction = oldItem.Direction; + item.Hue = oldItem.Hue; + item.ItemID = oldItem.ItemID; + item.Location = oldItem.Location; + item.Layer = oldItem.Layer; + item.Name = oldItem.Name; + item.Weight = oldItem.Weight; + + item.Amount = oldItem.Amount - amount; + item.Map = oldItem.Map; + + oldItem.Amount = amount; + oldItem.OnAfterDuped(item); + + if (oldItem.Parent is Mobile parentMobile) + parentMobile.AddItem(item); + else if (oldItem.Parent is Item parentItem) parentItem.AddItem(item); + + item.Delta(ItemDelta.Update); + + return item; + } + + public virtual void SendDropEffect(Item item) + { + if (DragEffects && !item.Deleted) + { + Map map = m_Map; + object root = item.RootParent; + + if (map != null && (root == null || root is Item)) + { + IPooledEnumerable eable = map.GetClientsInRange(m_Location); + Packet p = null; + Item rootItem = root as Item; + + foreach (NetState ns in eable) + { + if (ns.StygianAbyss) + continue; + + if (ns.Mobile != this && ns.Mobile.CanSee(this) && ns.Mobile.InLOS(this) && ns.Mobile.CanSee(root)) + { + if (p == null) + { + IEntity trg = new Entity(rootItem?.Serial ?? Serial.Zero, + rootItem?.Location ?? item.Location, map); + + p = Packet.Acquire(new DragEffect(this, trg, item.ItemID, item.Hue, item.Amount)); + } + + ns.Send(p); + } + } + + Packet.Release(p); + + eable.Free(); + } + } + } + + public virtual bool Drop(Item to, Point3D loc) + { + Mobile from = this; + Item item = from.Holding; + + bool valid = item != null && item.HeldBy == from && item.Map == Map.Internal; + + from.Holding = null; + + if (!valid) return false; + + bool bounced = true; + + item.SetLastMoved(); + + if (to == null || !item.DropToItem(from, to, loc)) + item.Bounce(from); + else + bounced = false; + + item.ClearBounce(); + + if (!bounced) + SendDropEffect(item); + + return !bounced; + } + + public virtual bool Drop(Point3D loc) + { + Mobile from = this; + Item item = from.Holding; + + bool valid = item != null && item.HeldBy == from && item.Map == Map.Internal; + + from.Holding = null; + + if (!valid) return false; + + bool bounced = true; + + item.SetLastMoved(); + + if (!item.DropToWorld(from, loc)) + item.Bounce(from); + else + bounced = false; + + item.ClearBounce(); + + if (!bounced) + SendDropEffect(item); + + return !bounced; + } + + public virtual bool Drop(Mobile to, Point3D loc) + { + Mobile from = this; + Item item = from.Holding; + + bool valid = item != null && item.HeldBy == from && item.Map == Map.Internal; + + from.Holding = null; + + if (!valid) return false; + + bool bounced = true; + + item.SetLastMoved(); + + if (to == null || !item.DropToMobile(from, to, loc)) + item.Bounce(from); + else + bounced = false; + + item.ClearBounce(); + + if (!bounced) + SendDropEffect(item); + + return !bounced; + } + + public virtual bool MutateSpeech(List hears, ref string text, ref object context) + { + if (Alive) + return false; + + StringBuilder sb = new StringBuilder(text.Length, text.Length); + + for (int i = 0; i < text.Length; ++i) + if (text[i] != ' ') + sb.Append(GhostChars[Utility.Random(GhostChars.Length)]); + else + sb.Append(' '); + + text = sb.ToString(); + context = m_GhostMutateContext; + return true; + } + + public virtual void Manifest(TimeSpan delay) + { + Warmode = true; + + if (m_AutoManifestTimer == null) + m_AutoManifestTimer = new AutoManifestTimer(this, delay); + else + m_AutoManifestTimer.Stop(); + + m_AutoManifestTimer.Start(); + } + + public virtual bool CheckSpeechManifest() + { + if (Alive) + return false; + + TimeSpan delay = AutoManifestTimeout; + + if (delay > TimeSpan.Zero && (!Warmode || m_AutoManifestTimer != null)) + { + Manifest(delay); + return true; + } + + return false; + } + + public virtual bool CheckHearsMutatedSpeech(Mobile m, object context) + { + if (context == m_GhostMutateContext) + return m.Alive && !m.CanHearGhosts; + + return true; + } + + private void AddSpeechItemsFrom(List list, Container cont) + { + for (int i = 0; i < cont.Items.Count; ++i) + { + Item item = cont.Items[i]; + + if (item.HandlesOnSpeech) + list.Add(item); + + if (item is Container container) + AddSpeechItemsFrom(list, container); + } + } + + public virtual void DoSpeech(string text, int[] keywords, MessageType type, int hue) + { + if (Deleted || CommandSystem.Handle(this, text, type)) + return; + + int range = 15; + + switch (type) + { + case MessageType.Regular: + SpeechHue = hue; + break; + case MessageType.Emote: + EmoteHue = hue; + break; + case MessageType.Whisper: + WhisperHue = hue; + range = 1; + break; + case MessageType.Yell: + YellHue = hue; + range = 18; + break; + default: + type = MessageType.Regular; + break; + } + + SpeechEventArgs regArgs = new SpeechEventArgs(this, text, type, hue, keywords); + + EventSink.InvokeSpeech(regArgs); + Region.OnSpeech(regArgs); + OnSaid(regArgs); + + if (regArgs.Blocked) + return; + + text = regArgs.Speech; + + if (string.IsNullOrEmpty(text)) + return; + + List hears = m_Hears; + List onSpeech = m_OnSpeech; + + if (m_Map != null) + { + IPooledEnumerable eable = m_Map.GetObjectsInRange(m_Location, range); + + foreach (IEntity o in eable) + if (o is Mobile heard) + { + if (heard.CanSee(this) && (NoSpeechLOS || !heard.Player || heard.InLOS(this))) + { + if (heard.m_NetState != null) + hears.Add(heard); + + if (heard.HandlesOnSpeech(this)) + onSpeech.Add(heard); + + for (int i = 0; i < heard.Items.Count; ++i) + { + Item item = heard.Items[i]; + + if (item.HandlesOnSpeech) + onSpeech.Add(item); + + if (item is Container container) + AddSpeechItemsFrom(onSpeech, container); + } + } + } + else if (o is Item item) + { + if (item.HandlesOnSpeech) + onSpeech.Add(item); + + if (item is Container container) + AddSpeechItemsFrom(onSpeech, container); + } + + eable.Free(); + + object mutateContext = null; + string mutatedText = text; + SpeechEventArgs mutatedArgs = null; + + if (MutateSpeech(hears, ref mutatedText, ref mutateContext)) + mutatedArgs = new SpeechEventArgs(this, mutatedText, type, hue, new int[0]); + + CheckSpeechManifest(); + + ProcessDelta(); + + Packet regp = null; + Packet mutp = null; + + // TODO: Should this be sorted like onSpeech is below? + + for (int i = 0; i < hears.Count; ++i) + { + Mobile heard = hears[i]; + + if (mutatedArgs == null || !CheckHearsMutatedSpeech(heard, mutateContext)) + { + heard.OnSpeech(regArgs); + + NetState ns = heard.NetState; + + if (ns != null) + { + if (regp == null) + regp = Packet.Acquire(new UnicodeMessage(Serial, Body, type, hue, 3, m_Language, Name, + text)); + + ns.Send(regp); + } + } + else + { + heard.OnSpeech(mutatedArgs); + + NetState ns = heard.NetState; + + if (ns != null) + { + if (mutp == null) + mutp = Packet.Acquire(new UnicodeMessage(Serial, Body, type, hue, 3, m_Language, Name, + mutatedText)); + + ns.Send(mutp); + } + } + } + + Packet.Release(regp); + Packet.Release(mutp); + + if (onSpeech.Count > 1) + onSpeech.Sort(LocationComparer.GetInstance(this)); + + for (int i = 0; i < onSpeech.Count; ++i) + { + IEntity obj = onSpeech[i]; + + if (obj is Mobile heard) + { + if (mutatedArgs == null || !CheckHearsMutatedSpeech(heard, mutateContext)) + heard.OnSpeech(regArgs); + else + heard.OnSpeech(mutatedArgs); + } + else + { + ((Item)obj).OnSpeech(regArgs); + } + } + + if (m_Hears.Count > 0) + m_Hears.Clear(); + + if (m_OnSpeech.Count > 0) + m_OnSpeech.Clear(); + } + } + + public static Mobile GetDamagerFrom(DamageEntry de) + { + return de == null ? null : de.Damager; + } + + public Mobile FindMostRecentDamager(bool allowSelf) + { + return GetDamagerFrom(FindMostRecentDamageEntry(allowSelf)); + } + + public DamageEntry FindMostRecentDamageEntry(bool allowSelf) + { + for (int i = DamageEntries.Count - 1; i >= 0; --i) + { + if (i >= DamageEntries.Count) + continue; + + DamageEntry de = DamageEntries[i]; + + if (de.HasExpired) + DamageEntries.RemoveAt(i); + else if (allowSelf || de.Damager != this) + return de; + } + + return null; + } + + public Mobile FindLeastRecentDamager(bool allowSelf) + { + return GetDamagerFrom(FindLeastRecentDamageEntry(allowSelf)); + } + + public DamageEntry FindLeastRecentDamageEntry(bool allowSelf) + { + for (int i = 0; i < DamageEntries.Count; ++i) + { + if (i < 0) + continue; + + DamageEntry de = DamageEntries[i]; + + if (de.HasExpired) + { + DamageEntries.RemoveAt(i); + --i; + } + else if (allowSelf || de.Damager != this) + { + return de; + } + } + + return null; + } + + public Mobile FindMostTotalDamger(bool allowSelf) + { + return GetDamagerFrom(FindMostTotalDamageEntry(allowSelf)); + } + + public DamageEntry FindMostTotalDamageEntry(bool allowSelf) + { + DamageEntry mostTotal = null; + + for (int i = DamageEntries.Count - 1; i >= 0; --i) + { + if (i >= DamageEntries.Count) + continue; + + DamageEntry de = DamageEntries[i]; + + if (de.HasExpired) + DamageEntries.RemoveAt(i); + else if ((allowSelf || de.Damager != this) && (mostTotal == null || de.DamageGiven > mostTotal.DamageGiven)) + mostTotal = de; + } + + return mostTotal; + } + + public Mobile FindLeastTotalDamger(bool allowSelf) + { + return GetDamagerFrom(FindLeastTotalDamageEntry(allowSelf)); + } + + public DamageEntry FindLeastTotalDamageEntry(bool allowSelf) + { + DamageEntry mostTotal = null; + + for (int i = DamageEntries.Count - 1; i >= 0; --i) + { + if (i >= DamageEntries.Count) + continue; + + DamageEntry de = DamageEntries[i]; + + if (de.HasExpired) + DamageEntries.RemoveAt(i); + else if ((allowSelf || de.Damager != this) && (mostTotal == null || de.DamageGiven < mostTotal.DamageGiven)) + mostTotal = de; + } + + return mostTotal; + } + + public DamageEntry FindDamageEntryFor(Mobile m) + { + for (int i = DamageEntries.Count - 1; i >= 0; --i) + { + if (i >= DamageEntries.Count) + continue; + + DamageEntry de = DamageEntries[i]; + + if (de.HasExpired) + DamageEntries.RemoveAt(i); + else if (de.Damager == m) + return de; + } + + return null; + } + + public virtual Mobile GetDamageMaster(Mobile damagee) + { + return null; + } + + public virtual DamageEntry RegisterDamage(int amount, Mobile from) + { + DamageEntry de = FindDamageEntryFor(from); + + if (de == null) + de = new DamageEntry(from); + + de.DamageGiven += amount; + de.LastDamage = DateTime.UtcNow; + + DamageEntries.Remove(de); + DamageEntries.Add(de); + + Mobile master = from.GetDamageMaster(this); + + if (master != null) + { + List list = de.Responsible; + + if (list == null) + de.Responsible = list = new List(); + + DamageEntry resp = null; + + for (int i = 0; i < list.Count; ++i) + { + DamageEntry check = list[i]; + + if (check.Damager == master) + { + resp = check; + break; + } + } + + if (resp == null) + list.Add(resp = new DamageEntry(master)); + + resp.DamageGiven += amount; + resp.LastDamage = DateTime.UtcNow; + } + + return de; + } + + /// + /// Overridable. Virtual event invoked when the Mobile is damaged. It is called before + /// hit points are lowered or the Mobile is killed. + /// + /// + /// + /// + public virtual void OnDamage(int amount, Mobile from, bool willKill) + { + } + + public virtual void Damage(int amount) + { + Damage(amount, null); + } + + public virtual bool CanBeDamaged() + { + return !m_Blessed; + } + + public virtual void Damage(int amount, Mobile from) + { + Damage(amount, from, true); + } + + public virtual void Damage(int amount, Mobile from, bool informMount) + { + if (!CanBeDamaged() || Deleted) + return; + + if (!Region.OnDamage(this, ref amount)) + return; + + if (amount > 0) + { + int oldHits = Hits; + int newHits = oldHits - amount; + + m_Spell?.OnCasterHurt(); + + //if ( m_Spell != null && m_Spell.State == SpellState.Casting ) + // m_Spell.Disturb( DisturbType.Hurt, false, true ); + + if (from != null) + RegisterDamage(amount, from); + + DisruptiveAction(); + + Paralyzed = false; + + switch (VisibleDamageType) + { + case VisibleDamageType.Related: + { + SendVisibleDamageRelated(from, amount); + break; + } + case VisibleDamageType.Everyone: + { + SendVisibleDamageEveryone(amount); + break; + } + case VisibleDamageType.Selective: + { + SendVisibleDamageSelective(from, amount); + break; + } + } + + OnDamage(amount, from, newHits < 0); + + IMount m = Mount; + if (m != null && informMount) + m.OnRiderDamaged(amount, from, newHits < 0); + + if (newHits < 0) + { + LastKiller = from; + + Hits = 0; + + if (oldHits >= 0) + Kill(); + } + else + { + Hits = newHits; + } + } + } + + public void SendVisibleDamageRelated(Mobile from, int amount) + { + NetState ourState = m_NetState, theirState = from?.m_NetState; + + if (ourState == null) + { + Mobile master = GetDamageMaster(from); + + if (master != null) + ourState = master.m_NetState; + } + + if (theirState == null && from != null) + { + Mobile master = from.GetDamageMaster(this); + + if (master != null) + theirState = master.m_NetState; + } + + if (amount > 0 && (ourState != null || theirState != null)) + { + Packet p = null; // = new DamagePacket( this, amount ); + + if (ourState != null) + { + if (ourState.DamagePacket) + p = Packet.Acquire(new DamagePacket(this, amount)); + else + p = Packet.Acquire(new DamagePacketOld(this, amount)); + + ourState.Send(p); + } + + if (theirState != null && theirState != ourState) + { + bool newPacket = theirState.DamagePacket; + + if (newPacket && !(p is DamagePacket)) + { + Packet.Release(p); + p = Packet.Acquire(new DamagePacket(this, amount)); + } + else if (!newPacket && !(p is DamagePacketOld)) + { + Packet.Release(p); + p = Packet.Acquire(new DamagePacketOld(this, amount)); + } + + theirState.Send(p); + } + + Packet.Release(p); + } + } + + public void SendVisibleDamageEveryone(int amount) + { + if (amount < 0) + return; + + Map map = m_Map; + + if (map == null) + return; + + IPooledEnumerable eable = map.GetClientsInRange(m_Location); + + Packet pNew = null; + Packet pOld = null; + + foreach (NetState ns in eable) + if (ns.Mobile.CanSee(this)) + { + if (ns.DamagePacket) + { + if (pNew == null) + pNew = Packet.Acquire(new DamagePacket(this, amount)); + + ns.Send(pNew); + } + else + { + if (pOld == null) + pOld = Packet.Acquire(new DamagePacketOld(this, amount)); + + ns.Send(pOld); + } + } + + Packet.Release(pNew); + Packet.Release(pOld); + + eable.Free(); + } + + public void SendVisibleDamageSelective(Mobile from, int amount) + { + NetState ourState = m_NetState, theirState = from == null ? null : from.m_NetState; + + Mobile damager = from; + Mobile damaged = this; + + if (ourState == null) + { + Mobile master = GetDamageMaster(from); + + if (master != null) + { + damaged = master; + ourState = master.m_NetState; + } + } + + if (!damaged.ShowVisibleDamage) + return; + + if (theirState == null && from != null) + { + Mobile master = from.GetDamageMaster(this); + + if (master != null) + { + damager = master; + theirState = master.m_NetState; + } + } + + if (amount > 0 && (ourState != null || theirState != null)) + { + if (damaged.CanSeeVisibleDamage && ourState != null) + { + if (ourState.DamagePacket) + ourState.Send(new DamagePacket(this, amount)); + else + ourState.Send(new DamagePacketOld(this, amount)); + } + + if (theirState != null && theirState != ourState && damager.CanSeeVisibleDamage) + { + if (theirState.DamagePacket) + theirState.Send(new DamagePacket(this, amount)); + else + theirState.Send(new DamagePacketOld(this, amount)); + } + } + } + + public void Heal(int amount) + { + Heal(amount, this, true); + } + + public void Heal(int amount, Mobile from) + { + Heal(amount, from, true); + } + + public void Heal(int amount, Mobile from, bool message) + { + if (!Alive || IsDeadBondedPet) + return; + + if (!Region.OnHeal(this, ref amount)) + return; + + OnHeal(ref amount, from); + + if (Hits + amount > HitsMax) amount = HitsMax - Hits; + + Hits += amount; + + if (message && amount > 0) + m_NetState?.Send(new MessageLocalizedAffix(Serial.MinusOne, -1, MessageType.Label, 0x3B2, 3, 1008158, "", + AffixType.Append | AffixType.System, amount.ToString(), "")); + } + + public virtual void OnHeal(ref int amount, Mobile from) + { + } + + public virtual void Deserialize(GenericReader reader) + { + int version = reader.ReadInt(); + + switch (version) + { + case 32: + { + // Removed StuckMenu + goto case 31; + } + case 31: + { + LastStrGain = reader.ReadDeltaTime(); + LastIntGain = reader.ReadDeltaTime(); + LastDexGain = reader.ReadDeltaTime(); + + goto case 30; + } + case 30: + { + byte hairflag = reader.ReadByte(); + + if ((hairflag & 0x01) != 0) + m_Hair = new HairInfo(reader); + if ((hairflag & 0x02) != 0) + m_FacialHair = new FacialHairInfo(reader); + + goto case 29; + } + case 29: + { + m_Race = reader.ReadRace(); + goto case 28; + } + case 28: + { + if (version <= 30) + LastStatGain = reader.ReadDeltaTime(); + + goto case 27; + } + case 27: + { + m_TithingPoints = reader.ReadInt(); + + goto case 26; + } + case 26: + case 25: + case 24: + { + Corpse = reader.ReadItem() as Container; + + goto case 23; + } + case 23: + { + CreationTime = reader.ReadDateTime(); + + goto case 22; + } + case 22: // Just removed followers + case 21: + { + Stabled = reader.ReadStrongMobileList(); + + goto case 20; + } + case 20: + { + CantWalk = reader.ReadBool(); + + goto case 19; + } + case 19: // Just removed variables + case 18: + { + m_Virtues = new VirtueInfo(reader); + + goto case 17; + } + case 17: + { + Thirst = reader.ReadInt(); + BAC = reader.ReadInt(); + + goto case 16; + } + case 16: + { + m_ShortTermMurders = reader.ReadInt(); + + if (version <= 24) + { + reader.ReadDateTime(); + reader.ReadDateTime(); + } + + goto case 15; + } + case 15: + { + if (version < 22) + reader.ReadInt(); // followers + + m_FollowersMax = reader.ReadInt(); + + goto case 14; + } + case 14: + { + MagicDamageAbsorb = reader.ReadInt(); + + goto case 13; + } + case 13: + { + GuildFealty = reader.ReadMobile(); + + goto case 12; + } + case 12: + { + m_Guild = reader.ReadGuild(); + + goto case 11; + } + case 11: + { + m_DisplayGuildTitle = reader.ReadBool(); + + goto case 10; + } + case 10: + { + CanSwim = reader.ReadBool(); + + goto case 9; + } + case 9: + { + Squelched = reader.ReadBool(); + + goto case 8; + } + case 8: + { + m_Holding = reader.ReadItem(); + + goto case 7; + } + case 7: + { + m_VirtualArmor = reader.ReadInt(); + + goto case 6; + } + case 6: + { + BaseSoundID = reader.ReadInt(); + + goto case 5; + } + case 5: + { + DisarmReady = reader.ReadBool(); + StunReady = reader.ReadBool(); + + goto case 4; + } + case 4: + { + if (version <= 25) Poison.Deserialize(reader); + + goto case 3; + } + case 3: + { + m_StatCap = reader.ReadInt(); + + goto case 2; + } + case 2: + { + NameHue = reader.ReadInt(); + + goto case 1; + } + case 1: + { + m_Hunger = reader.ReadInt(); + + goto case 0; + } + case 0: + { + if (version < 21) + Stabled = new List(); + + if (version < 18) + m_Virtues = new VirtueInfo(); + + if (version < 11) + m_DisplayGuildTitle = true; + + if (version < 3) + m_StatCap = 225; + + if (version < 15) + { + m_Followers = 0; + m_FollowersMax = 5; + } + + m_Location = reader.ReadPoint3D(); + m_Body = new Body(reader.ReadInt()); + m_Name = reader.ReadString(); + m_GuildTitle = reader.ReadString(); + m_Criminal = reader.ReadBool(); + m_Kills = reader.ReadInt(); + SpeechHue = reader.ReadInt(); + EmoteHue = reader.ReadInt(); + WhisperHue = reader.ReadInt(); + YellHue = reader.ReadInt(); + m_Language = reader.ReadString(); + m_Female = reader.ReadBool(); + m_Warmode = reader.ReadBool(); + m_Hidden = reader.ReadBool(); + m_Direction = (Direction)reader.ReadByte(); + m_Hue = reader.ReadInt(); + m_Str = reader.ReadInt(); + m_Dex = reader.ReadInt(); + m_Int = reader.ReadInt(); + m_Hits = reader.ReadInt(); + m_Stam = reader.ReadInt(); + m_Mana = reader.ReadInt(); + m_Map = reader.ReadMap(); + m_Blessed = reader.ReadBool(); + m_Fame = reader.ReadInt(); + m_Karma = reader.ReadInt(); + m_AccessLevel = (AccessLevel)reader.ReadByte(); + + m_Skills = new Skills(this, reader); + + Items = reader.ReadStrongItemList(); + + m_Player = reader.ReadBool(); + m_Title = reader.ReadString(); + Profile = reader.ReadString(); + ProfileLocked = reader.ReadBool(); + + if (version <= 18) + { + reader.ReadInt(); + reader.ReadInt(); + reader.ReadInt(); + } + + AutoPageNotify = reader.ReadBool(); + + LogoutLocation = reader.ReadPoint3D(); + LogoutMap = reader.ReadMap(); + + m_StrLock = (StatLockType)reader.ReadByte(); + m_DexLock = (StatLockType)reader.ReadByte(); + m_IntLock = (StatLockType)reader.ReadByte(); + + StatMods = new List(); + SkillMods = new List(); + + if (version < 32) + if (reader.ReadBool()) + { + int count = reader.ReadInt(); + for (int i = 0; i < count; ++i) reader.ReadDateTime(); + } + + if (m_Player && m_Map != Map.Internal) + { + LogoutLocation = m_Location; + LogoutMap = m_Map; + + m_Map = Map.Internal; + } + + m_Map?.OnEnter(this); + + if (m_Criminal) + { + if (m_ExpireCriminal == null) + m_ExpireCriminal = new ExpireCriminalTimer(this); + + m_ExpireCriminal.Start(); + } + + if (ShouldCheckStatTimers) + CheckStatTimers(); + + if (!m_Player && m_Dex <= 100 && m_CombatTimer != null) + m_CombatTimer.Priority = TimerPriority.FiftyMS; + else if (m_CombatTimer != null) + m_CombatTimer.Priority = TimerPriority.EveryTick; + + UpdateRegion(); + + UpdateResistances(); + + break; + } + } + + if (!m_Player) + Utility.Intern(ref m_Name); + + Utility.Intern(ref m_Title); + Utility.Intern(ref m_Language); + + /* //Moved into cleanup in scripts. + if ( version < 30 ) + Timer.DelayCall( TimeSpan.Zero, new TimerCallback( ConvertHair ) ); + * */ + } + + public void ConvertHair() + { + Item hair; + + if ((hair = FindItemOnLayer(Layer.Hair)) != null) + { + HairItemID = hair.ItemID; + HairHue = hair.Hue; + hair.Delete(); + } + + if ((hair = FindItemOnLayer(Layer.FacialHair)) != null) + { + FacialHairItemID = hair.ItemID; + FacialHairHue = hair.Hue; + hair.Delete(); + } + } + + public virtual void CheckStatTimers() + { + if (Deleted) + return; + + if (Hits < HitsMax) + { + if (CanRegenHits) + { + if (m_HitsTimer == null) + m_HitsTimer = new HitsTimer(this); + + m_HitsTimer.Start(); + } + else + { + m_HitsTimer?.Stop(); + } + } + else + { + Hits = HitsMax; + } + + if (Stam < StamMax) + { + if (CanRegenStam) + { + if (m_StamTimer == null) + m_StamTimer = new StamTimer(this); + + m_StamTimer.Start(); + } + else + { + m_StamTimer?.Stop(); + } + } + else + { + Stam = StamMax; + } + + if (Mana < ManaMax) + { + if (CanRegenMana) + { + if (m_ManaTimer == null) + m_ManaTimer = new ManaTimer(this); + + m_ManaTimer.Start(); + } + else + { + m_ManaTimer?.Stop(); + } + } + else + { + Mana = ManaMax; + } + } + + public static string GetAccessLevelName(AccessLevel level) + { + return m_AccessLevelNames[(int)level]; + } + + public virtual bool CanPaperdollBeOpenedBy(Mobile from) + { + return Body.IsHuman || Body.IsGhost || IsBodyMod; + } + + public virtual void GetChildContextMenuEntries(Mobile from, List list, Item item) + { + } + + public virtual void GetContextMenuEntries(Mobile from, List list) + { + if (Deleted) + return; + + if (CanPaperdollBeOpenedBy(from)) + list.Add(new PaperdollEntry(this)); + + if (from == this && Backpack != null && CanSee(Backpack) && CheckAlive(false)) + list.Add(new OpenBackpackEntry(this)); + } + + public void Internalize() + { + Map = Map.Internal; + } + + /// + /// Overridable. Virtual event invoked when is added from the Mobile, such + /// as when it is equipped. + /// + /// + /// + public virtual void OnItemAdded(Item item) + { + } + + /// + /// Overridable. Virtual event invoked when is removed from the Mobile. + /// + /// + /// + public virtual void OnItemRemoved(Item item) + { + } + + /// + /// Overridable. Virtual event invoked when is becomes a child of the Mobile; it's worn or contained + /// at some level of the Mobile's backpack or bank box + /// + /// + /// + public virtual void OnSubItemAdded(Item item) + { + } + + /// + /// Overridable. Virtual event invoked when is removed from the Mobile, its + /// backpack, or its bank box. + /// + /// + /// + public virtual void OnSubItemRemoved(Item item) + { + } + + public virtual void OnItemBounceCleared(Item item) + { + } + + public virtual void OnSubItemBounceCleared(Item item) + { + } + + public void AddItem(Item item) + { + if (item == null || item.Deleted) + return; + + if (item.Parent == this) + return; + if (item.Parent is Mobile parentMobile) + parentMobile.RemoveItem(item); + else if (item.Parent is Item parentItem) + parentItem.RemoveItem(item); + else + item.SendRemovePacket(); + + item.Parent = this; + item.Map = m_Map; + + Items.Add(item); + + if (!item.IsVirtualItem) + { + UpdateTotal(item, TotalType.Gold, item.TotalGold); + UpdateTotal(item, TotalType.Items, item.TotalItems + 1); + UpdateTotal(item, TotalType.Weight, item.TotalWeight + item.PileWeight); + } + + item.Delta(ItemDelta.Update); + + item.OnAdded(this); + OnItemAdded(item); + + if (item.PhysicalResistance != 0 || item.FireResistance != 0 || item.ColdResistance != 0 || + item.PoisonResistance != 0 || item.EnergyResistance != 0) + UpdateResistances(); + } + + public void RemoveItem(Item item) + { + if (item == null || Items == null) + return; + + if (Items.Contains(item)) + { + item.SendRemovePacket(); + + //int oldCount = m_Items.Count; + + Items.Remove(item); + + if (!item.IsVirtualItem) + { + UpdateTotal(item, TotalType.Gold, -item.TotalGold); + UpdateTotal(item, TotalType.Items, -(item.TotalItems + 1)); + UpdateTotal(item, TotalType.Weight, -(item.TotalWeight + item.PileWeight)); + } + + item.Parent = null; + + item.OnRemoved(this); + OnItemRemoved(item); + + if (item.PhysicalResistance != 0 || item.FireResistance != 0 || item.ColdResistance != 0 || + item.PoisonResistance != 0 || item.EnergyResistance != 0) + UpdateResistances(); + } + } + + public virtual void Animate(int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay) + { + Map map = m_Map; + + if (map != null) + { + ProcessDelta(); + + Packet p = null; + //Packet pNew = null; + + IPooledEnumerable eable = map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(this)) + { + state.Mobile.ProcessDelta(); + + //if ( state.StygianAbyss ) { + //if ( pNew == null ) + //pNew = Packet.Acquire( new NewMobileAnimation( this, action, frameCount, delay ) ); + + //state.Send( pNew ); + //} else { + if (p == null) + { + #region SA + + if (Body.IsGargoyle) + { + frameCount = 10; + + if (Flying) + { + if (action >= 9 && action <= 11) + action = 71; + else if (action >= 12 && action <= 14) + action = 72; + else if (action == 20) + action = 77; + else if (action == 31) + action = 71; + else if (action == 34) + action = 78; + else if (action >= 200 && action <= 259) + action = 75; + else if (action >= 260 && action <= 270) action = 75; + } + else + { + if (action >= 200 && action <= 259) + action = 17; + else if (action >= 260 && action <= 270) action = 16; + } + } + + #endregion + + p = Packet.Acquire(new MobileAnimation(this, action, frameCount, repeatCount, forward, repeat, + delay)); + } + + state.Send(p); + //} + } + + Packet.Release(p); + //Packet.Release( pNew ); + + eable.Free(); + } + } + + public void SendSound(int soundID) + { + if (soundID != -1 && m_NetState != null) + Send(new PlaySound(soundID, this)); + } + + public void SendSound(int soundID, IPoint3D p) + { + if (soundID != -1 && m_NetState != null) + Send(new PlaySound(soundID, p)); + } + + public void PlaySound(int soundID) + { + if (soundID == -1) + return; + + if (m_Map != null) + { + Packet p = Packet.Acquire(new PlaySound(soundID, this)); + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(this)) + state.Send(p); + + Packet.Release(p); + + eable.Free(); + } + } + + public virtual void OnAccessLevelChanged(AccessLevel oldLevel) + { + } + + public virtual void OnFameChange(int oldValue) + { + } + + public virtual void OnKarmaChange(int oldValue) + { + } + + // Mobile did something which should unhide him + public virtual void RevealingAction() + { + if (m_Hidden && m_AccessLevel == AccessLevel.Player) + Hidden = false; + + DisruptiveAction(); // Anything that unhides you will also distrupt meditation + } + + public void SendRemovePacket() + { + SendRemovePacket(true); + } + + public void SendRemovePacket(bool everyone) + { + if (m_Map != null) + { + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state != m_NetState && (everyone || !state.Mobile.CanSee(this))) + state.Send(RemovePacket); + + eable.Free(); + } + } + + public void ClearScreen() + { + NetState ns = m_NetState; + + if (m_Map != null && ns != null) + { + IPooledEnumerable eable = m_Map.GetObjectsInRange(m_Location, Core.GlobalMaxUpdateRange); + + foreach (IEntity o in eable) + if (o is Mobile m) + { + if (m != this && Utility.InUpdateRange(m_Location, m.m_Location)) + ns.Send(m.RemovePacket); + } + else if (o is Item item) + { + if (InRange(item.Location, item.GetUpdateRange(this))) + ns.Send(item.RemovePacket); + } + + eable.Free(); + } + } + + public bool Send(Packet p) + { + return Send(p, false); + } + + public bool Send(Packet p, bool throwOnOffline) + { + if (m_NetState != null) + { + m_NetState.Send(p); + return true; + } + + if (throwOnOffline) throw new MobileNotConnectedException(this, "Packet could not be sent."); + + return false; + } + + /// + /// Overridable. Event invoked before the Mobile says something. + /// + /// + public virtual void OnSaid(SpeechEventArgs e) + { + if (Squelched) + { + if (Core.ML) + SendLocalizedMessage(500168); // You can not say anything, you have been muted. + else + SendMessage("You can not say anything, you have been squelched."); //Cliloc ITSELF changed during ML. + + e.Blocked = true; + } + + if (!e.Blocked) + RevealingAction(); + } + + public virtual bool HandlesOnSpeech(Mobile from) + { + return false; + } + + /// + /// Overridable. Virtual event invoked when the Mobile hears speech. This event will only be invoked if + /// returns true. + /// + /// + public virtual void OnSpeech(SpeechEventArgs e) + { + } + + public void SendEverything() + { + NetState ns = m_NetState; + + if (m_Map != null && ns != null) + { + IPooledEnumerable eable = m_Map.GetObjectsInRange(m_Location, Core.GlobalMaxUpdateRange); + + foreach (IEntity o in eable) + if (o is Item item) + { + if (CanSee(item) && InRange(item.Location, item.GetUpdateRange(this))) + item.SendInfoTo(ns); + } + else if (o is Mobile m) + { + if (CanSee(m) && Utility.InUpdateRange(m_Location, m.m_Location)) + { + ns.Send(MobileIncoming.Create(ns, this, m)); + + if (ns.StygianAbyss) + { + if (m.Poisoned) + ns.Send(new HealthbarPoison(m)); + + if (m.Blessed || m.YellowHealthbar) + ns.Send(new HealthbarYellow(m)); + } + + if (m.IsDeadBondedPet) + ns.Send(new BondedStatus(0, m.Serial, 1)); + + if (ObjectPropertyList.Enabled) ns.Send(m.OPLPacket); + } + } + + eable.Free(); + } + } + + public void UpdateRegion() + { + if (Deleted) + return; + + Region newRegion = Region.Find(m_Location, m_Map); + + if (newRegion != m_Region) + { + Region.OnRegionChange(this, m_Region, newRegion); + + m_Region = newRegion; + OnRegionChange(m_Region, newRegion); + } + } + + /// + /// Overridable. Virtual event invoked when changes. + /// + protected virtual void OnMapChange(Map oldMap) + { + } + + + public void SetDirection(Direction dir) + { + m_Direction = dir; + } + + public virtual int GetSeason() + { + if (m_Map != null) + return m_Map.Season; + + return 1; + } + + public virtual int GetPacketFlags() + { + int flags = 0x0; + + if (m_Paralyzed || m_Frozen) + flags |= 0x01; + + if (m_Female) + flags |= 0x02; + + if (m_Flying) + flags |= 0x04; + + if (m_Blessed || m_YellowHealthbar) + flags |= 0x08; + + if (m_Warmode) + flags |= 0x40; + + if (m_Hidden) + flags |= 0x80; + + return flags; + } + + // Pre-7.0.0.0 Packet Flags + public virtual int GetOldPacketFlags() + { + int flags = 0x0; + + if (m_Paralyzed || m_Frozen) + flags |= 0x01; + + if (m_Female) + flags |= 0x02; + + if (m_Poison != null) + flags |= 0x04; + + if (m_Blessed || m_YellowHealthbar) + flags |= 0x08; + + if (m_Warmode) + flags |= 0x40; + + if (m_Hidden) + flags |= 0x80; + + return flags; + } + + public virtual void OnGenderChanged(bool oldFemale) + { + } + + public virtual void ToggleFlying() + { + } + + /// + /// Overridable. Virtual event invoked after the Warmode property has changed. + /// + public virtual void OnWarmodeChanged() + { + } + + public virtual void OnHiddenChanged() + { + AllowedStealthSteps = 0; + + if (m_Map != null) + { + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (!state.Mobile.CanSee(this)) + { + state.Send(RemovePacket); + } + else + { + state.Send(MobileIncoming.Create(state, state.Mobile, this)); + + if (IsDeadBondedPet) + state.Send(new BondedStatus(0, Serial, 1)); + + if (ObjectPropertyList.Enabled) state.Send(OPLPacket); + } + + eable.Free(); + } + } + + public virtual void OnConnected() + { + } + + public virtual void OnDisconnected() + { + } + + public virtual void OnNetStateChanged() + { + } + + public virtual bool CanSee(object o) + { + if (o is Item item) return CanSee(item); + + if (o is Mobile mobile) return CanSee(mobile); + + return true; + } + + public virtual bool CanSee(Item item) + { + if (m_Map == Map.Internal) + return false; + if (item.Map == Map.Internal) + return false; + + if (item.Parent != null) + { + if (item.Parent is Item parent) + { + if (!(CanSee(parent) && parent.IsChildVisibleTo(this, item))) + return false; + } + else if (item.Parent is Mobile mobile) + { + if (!CanSee(mobile)) + return false; + } + } + + if (item is BankBox box && m_AccessLevel <= AccessLevel.Counselor && (box.Owner != this || !box.Opened)) + return false; + + if (item is SecureTradeContainer container) + { + SecureTrade trade = container.Trade; + + if (trade != null && trade.From.Mobile != this && trade.To.Mobile != this) + return false; + } + + return !item.Deleted && item.Map == m_Map && (item.Visible || m_AccessLevel > AccessLevel.Counselor); + } + + public virtual bool CanSee(Mobile m) + { + if (Deleted || m.Deleted || m_Map == Map.Internal || m.m_Map == Map.Internal) + return false; + + return this == m || m.m_Map == m_Map && + (!m.Hidden || m_AccessLevel != AccessLevel.Player && + (m_AccessLevel >= m.AccessLevel || m_AccessLevel >= AccessLevel.Administrator)) && + (m.Alive || Core.SE && Skills.SpiritSpeak.Value >= 100.0 || !Alive || + m_AccessLevel > AccessLevel.Player || m.Warmode); + } + + public virtual bool CanBeRenamedBy(Mobile from) + { + return from.AccessLevel >= AccessLevel.GameMaster && from.m_AccessLevel > m_AccessLevel; + } + + public virtual void OnGuildTitleChange(string oldTitle) + { + } + + public virtual void OnAfterNameChange(string oldName, string newName) + { + } + + public virtual void OnGuildChange(BaseGuild oldGuild) + { + } + + public virtual int SafeBody(int body) + { + int delta = -1; + + for (int i = 0; delta < 0 && i < m_InvalidBodies.Length; ++i) + delta = m_InvalidBodies[i] - body; + + if (delta != 0) + return body; + + return 0; + } + + public void FreeCache() + { + Packet.Release(ref m_RemovePacket); + Packet.Release(ref m_PropertyList); + Packet.Release(ref m_OPLPacket); + } + + public void ClearProperties() + { + Packet.Release(ref m_PropertyList); + Packet.Release(ref m_OPLPacket); + } + + public void InvalidateProperties() + { + if (!ObjectPropertyList.Enabled) + return; + + if (m_Map != null && m_Map != Map.Internal && !World.Loading) + { + ObjectPropertyList oldList = m_PropertyList; + Packet.Release(ref m_PropertyList); + ObjectPropertyList newList = PropertyList; + + if (oldList == null || oldList.Hash != newList.Hash) + { + Packet.Release(ref m_OPLPacket); + Delta(MobileDelta.Properties); + } + } + else + { + ClearProperties(); + } + } + + public virtual void SetLocation(Point3D newLocation, bool isTeleport) + { + if (Deleted) + return; + + Point3D oldLocation = m_Location; + + if (oldLocation != newLocation) + { + m_Location = newLocation; + UpdateRegion(); + + BankBox box = FindBankNoCreate(); + + if (box != null && box.Opened) + box.Close(); + + m_NetState?.ValidateAllTrades(); + + m_Map?.OnMove(oldLocation, this); + + if (isTeleport && m_NetState != null && (!m_NetState.HighSeas || !NoMoveHS)) + { + m_NetState.Sequence = 0; + + if (m_NetState.StygianAbyss) + m_NetState.Send(new MobileUpdate(this)); + else + m_NetState.Send(new MobileUpdateOld(this)); + + ClearFastwalkStack(); + } + + Map map = m_Map; + + if (map != null) + { + // First, send a remove message to everyone who can no longer see us. (inOldRange && !inNewRange) + + IPooledEnumerable eable = map.GetClientsInRange(oldLocation); + + foreach (NetState ns in eable) + if (ns != m_NetState && !Utility.InUpdateRange(newLocation, ns.Mobile.Location)) + ns.Send(RemovePacket); + + eable.Free(); + + NetState ourState = m_NetState; + + // Check to see if we are attached to a client + if (ourState != null) + { + IPooledEnumerable eeable = map.GetObjectsInRange(newLocation, Core.GlobalMaxUpdateRange); + + // We are attached to a client, so it's a bit more complex. We need to send new items and people to ourself, and ourself to other clients + + foreach (IEntity o in eeable) + if (o is Item item) + { + int range = item.GetUpdateRange(this); + Point3D loc = item.Location; + + if (!Utility.InRange(oldLocation, loc, range) && Utility.InRange(newLocation, loc, range) && + CanSee(item)) + item.SendInfoTo(ourState); + } + else if (o != this && o is Mobile m) + { + if (!Utility.InUpdateRange(newLocation, m.m_Location)) + continue; + + bool inOldRange = Utility.InUpdateRange(oldLocation, m.m_Location); + + if (m.m_NetState != null && + (isTeleport && (!m.m_NetState.HighSeas || !NoMoveHS) || !inOldRange) && m.CanSee(this)) + { + m.m_NetState.Send(MobileIncoming.Create(m.m_NetState, m, this)); + + if (m.m_NetState.StygianAbyss) + { + //if ( m_Poison != null ) + m.m_NetState.Send(new HealthbarPoison(this)); + + //if ( m_Blessed || m_YellowHealthbar ) + m.m_NetState.Send(new HealthbarYellow(this)); + } + + if (IsDeadBondedPet) + m.m_NetState.Send(new BondedStatus(0, Serial, 1)); + + if (ObjectPropertyList.Enabled) m.m_NetState.Send(OPLPacket); + } + + if (!inOldRange && CanSee(m)) + { + ourState.Send(MobileIncoming.Create(ourState, this, m)); + + if (ourState.StygianAbyss) + { + //if ( m.Poisoned ) + ourState.Send(new HealthbarPoison(m)); + + //if ( m.Blessed || m.YellowHealthbar ) + ourState.Send(new HealthbarYellow(m)); + } + + if (m.IsDeadBondedPet) + ourState.Send(new BondedStatus(0, m.Serial, 1)); + + if (ObjectPropertyList.Enabled) ourState.Send(m.OPLPacket); + } + } + + eeable.Free(); + } + else + { + eable = map.GetClientsInRange(newLocation); + + // We're not attached to a client, so simply send an Incoming + foreach (NetState ns in eable) + if ((isTeleport && (!ns.HighSeas || !NoMoveHS) || + !Utility.InUpdateRange(oldLocation, ns.Mobile.Location)) && ns.Mobile.CanSee(this)) + { + ns.Send(MobileIncoming.Create(ns, ns.Mobile, this)); + + if (ns.StygianAbyss) + { + //if ( m_Poison != null ) + ns.Send(new HealthbarPoison(this)); + + //if ( m_Blessed || m_YellowHealthbar ) + ns.Send(new HealthbarYellow(this)); + } + + if (IsDeadBondedPet) + ns.Send(new BondedStatus(0, Serial, 1)); + + if (ObjectPropertyList.Enabled) ns.Send(OPLPacket); + } + + eable.Free(); + } + } + + OnLocationChange(oldLocation); + + Region.OnLocationChanged(this, oldLocation); + } + } + + /// + /// Overridable. Virtual event invoked when changes. + /// + protected virtual void OnLocationChange(Point3D oldLocation) + { + } + + public bool HasFreeHand() + { + return FindItemOnLayer(Layer.TwoHanded) == null; + } + + public virtual IWeapon GetDefaultWeapon() + { + return DefaultWeapon; + } + + public BankBox FindBankNoCreate() + { + if (m_BankBox != null && !m_BankBox.Deleted && m_BankBox.Parent == this) + return m_BankBox; + + m_BankBox = FindItemOnLayer(Layer.Bank) as BankBox; + + return m_BankBox; + } + + public Item FindItemOnLayer(Layer layer) + { + List eq = Items; + int count = eq.Count; + + for (int i = 0; i < count; ++i) + { + Item item = eq[i]; + + if (!item.Deleted && item.Layer == layer) return item; + } + + return null; + } + + public void SendIncomingPacket() + { + if (m_Map != null) + { + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(this)) + { + state.Send(MobileIncoming.Create(state, state.Mobile, this)); + + if (state.StygianAbyss) + { + if (m_Poison != null) + state.Send(new HealthbarPoison(this)); + + if (m_Blessed || m_YellowHealthbar) + state.Send(new HealthbarYellow(this)); + } + + if (IsDeadBondedPet) + state.Send(new BondedStatus(0, Serial, 1)); + + if (ObjectPropertyList.Enabled) state.Send(OPLPacket); + } + + eable.Free(); + } + } + + public bool PlaceInBackpack(Item item) + { + if (item.Deleted) + return false; + + Container pack = Backpack; + + return pack != null && pack.TryDropItem(this, item, false); + } + + public bool AddToBackpack(Item item) + { + if (item.Deleted) + return false; + + if (!PlaceInBackpack(item)) + { + Point3D loc = m_Location; + Map map = m_Map; + + if ((map == null || map == Map.Internal) && LogoutMap != null) + { + loc = LogoutLocation; + map = LogoutMap; + } + + item.MoveToWorld(loc, map); + return false; + } + + return true; + } + + public virtual bool CheckLift(Mobile from, Item item, ref LRReason reject) + { + return true; + } + + public virtual bool CheckNonlocalLift(Mobile from, Item item) + { + if (from == this || from.AccessLevel > AccessLevel && from.AccessLevel >= AccessLevel.GameMaster) + return true; + + return false; + } + + public virtual bool CheckTrade(Mobile to, Item item, SecureTradeContainer cont, bool message, bool checkItems, + int plusItems, int plusWeight) + { + return true; + } + + public bool OpenTrade(Mobile from) + { + return OpenTrade(from, null); + } + + public virtual bool OpenTrade(Mobile from, Item offer) + { + if (!from.Player || !Player || !from.Alive || !Alive) return false; + + NetState ourState = m_NetState; + NetState theirState = from.m_NetState; + + if (ourState == null || theirState == null) return false; + + SecureTradeContainer cont = theirState.FindTradeContainer(this); + + if (!from.CheckTrade(this, offer, cont, true, true, 0, 0)) return false; + + if (cont == null) cont = theirState.AddTrade(ourState); + + if (offer != null) cont.DropItem(offer); + + return true; + } + + /// + /// Overridable. Event invoked when a Mobile () drops an + /// + /// + /// + /// onto the Mobile. + /// + public virtual bool OnDragDrop(Mobile from, Item dropped) + { + if (from == this) + { + Container pack = Backpack; + + if (pack != null) + return dropped.DropToItem(from, pack, new Point3D(-1, -1, 0)); + + return false; + } + + if (from.InRange(Location, 2)) return OpenTrade(from, dropped); + return false; + } + + public virtual bool CheckEquip(Item item) + { + for (int i = 0; i < Items.Count; ++i) + if (Items[i].CheckConflictingLayer(this, item, item.Layer) || + item.CheckConflictingLayer(this, Items[i], Items[i].Layer)) + return false; + + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to wear . + /// + /// True if the request is accepted, false if otherwise. + public virtual bool OnEquip(Item item) + { + // For some reason OSI allows equipping quest items, but they are unmarked in the process + if (item.QuestItem) + { + item.QuestItem = false; + SendLocalizedMessage( + 1074769); // An item must be in your backpack (and not in a container within) to be toggled as a quest item. + } + + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to lift . + /// + /// True if the lift is allowed, false if otherwise. + /// + /// The following example demonstrates usage. It will disallow any attempts to pick up a pick axe if the Mobile does not have + /// enough strength. + /// + /// public override bool OnDragLift( Item item ) + /// { + /// if ( item is Pickaxe && this.Str < 60 ) + /// { + /// SendMessage( "That is too heavy for you to lift." ); + /// return false; + /// } + /// + /// return base.OnDragLift( item ); + /// } + /// + public virtual bool OnDragLift(Item item) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to drop into a + /// + /// + /// + /// . + /// + /// True if the drop is allowed, false if otherwise. + public virtual bool OnDroppedItemInto(Item item, Container container, Point3D loc) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to drop directly onto another + /// , . This is the case of stacking items. + /// + /// True if the drop is allowed, false if otherwise. + public virtual bool OnDroppedItemOnto(Item item, Item target) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to drop into another + /// , . The target item is most likely a . + /// + /// True if the drop is allowed, false if otherwise. + public virtual bool OnDroppedItemToItem(Item item, Item target, Point3D loc) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to give to a Mobile ( + /// ). + /// + /// True if the drop is allowed, false if otherwise. + public virtual bool OnDroppedItemToMobile(Item item, Mobile target) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when the Mobile attempts to drop to the world at a + /// + /// + /// + /// . + /// + /// True if the drop is allowed, false if otherwise. + public virtual bool OnDroppedItemToWorld(Item item, Point3D location) + { + return true; + } + + /// + /// Overridable. Virtual event when successfully uses while it's on this + /// Mobile. + /// + /// + public virtual void OnItemUsed(Mobile from, Item item) + { + } + + public virtual bool CheckNonlocalDrop(Mobile from, Item item, Item target) + { + if (from == this || from.AccessLevel > AccessLevel && from.AccessLevel >= AccessLevel.GameMaster) + return true; + + return false; + } + + public virtual bool CheckItemUse(Mobile from, Item item) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when successfully lifts from this + /// Mobile. + /// + /// + public virtual void OnItemLifted(Mobile from, Item item) + { + } + + public virtual bool AllowItemUse(Item item) + { + return true; + } + + public virtual bool AllowEquipFrom(Mobile mob) + { + return mob == this || mob.AccessLevel >= AccessLevel.GameMaster && mob.AccessLevel > AccessLevel; + } + + public virtual bool EquipItem(Item item) + { + if (item == null || item.Deleted || !item.CanEquip(this)) + return false; + + if (CheckEquip(item) && OnEquip(item) && item.OnEquip(this)) + { + if (m_Spell != null && !m_Spell.OnCasterEquipping(item)) + return false; + + //if ( m_Spell != null && m_Spell.State == SpellState.Casting ) + // m_Spell.Disturb( DisturbType.EquipRequest ); + + AddItem(item); + return true; + } + + return false; + } + + public void DefaultMobileInit() + { + m_StatCap = 225; + m_FollowersMax = 5; + m_Skills = new Skills(this); + Items = new List(); + StatMods = new List(); + SkillMods = new List(); + Map = Map.Internal; + AutoPageNotify = true; + Aggressors = new List(); + Aggressed = new List(); + m_Virtues = new VirtueInfo(); + Stabled = new List(); + DamageEntries = new List(); + + NextSkillTime = Core.TickCount; + CreationTime = DateTime.UtcNow; + } + + public virtual void Delta(MobileDelta flag) + { + if (m_Map == null || m_Map == Map.Internal || Deleted) + return; + + m_DeltaFlags |= flag; + + if (!m_InDeltaQueue) + { + m_InDeltaQueue = true; + + if (_processing) + lock (m_DeltaQueueR) + { + m_DeltaQueueR.Enqueue(this); + + try + { + using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) + { + op.WriteLine("# {0}", DateTime.UtcNow); + op.WriteLine(new StackTrace()); + op.WriteLine(); + } + } + catch + { + } + } + else + m_DeltaQueue.Enqueue(this); + } + + Core.Set(); + } + + public static void ProcessDeltaQueue() + { + _processing = true; + + if (m_DeltaQueue.Count >= 512) + { + Parallel.ForEach(m_DeltaQueue, m => m.ProcessDelta()); + m_DeltaQueue.Clear(); + } + else + { + while (m_DeltaQueue.Count > 0) m_DeltaQueue.Dequeue().ProcessDelta(); + } + + _processing = false; + + while (m_DeltaQueueR.Count > 0) m_DeltaQueueR.Dequeue().ProcessDelta(); + } + + public virtual void OnKillsChange(int oldValue) + { + } + + public bool CheckAlive() + { + return CheckAlive(true); + } + + public bool CheckAlive(bool message) + { + if (!Alive) + { + if (message) + LocalOverheadMessage(MessageType.Regular, 0x3B2, 1019048); // I am dead and cannot do that. + + return false; + } + + return true; + } + + public void LaunchBrowser(string url) + { + m_NetState?.LaunchBrowser(url); + } + + public void InitStats(int str, int dex, int intel) + { + m_Str = str; + m_Dex = dex; + m_Int = intel; + + Hits = HitsMax; + Stam = StamMax; + Mana = ManaMax; + + Delta(MobileDelta.Stat | MobileDelta.Hits | MobileDelta.Stam | MobileDelta.Mana); + } + + public virtual void DisplayPaperdollTo(Mobile to) + { + EventSink.InvokePaperdollRequest(new PaperdollRequestEventArgs(to, this)); + } + + /// + /// Overridable. Event invoked when the Mobile requests to open his own paperdoll via the 'Open Paperdoll' macro. + /// + public virtual void OnPaperdollRequest() + { + if (CanPaperdollBeOpenedBy(this)) + DisplayPaperdollTo(this); + } + + /// + /// Overridable. Event invoked when wants to see this Mobile's stats. + /// + /// + public virtual void OnStatsQuery(Mobile from) + { + if (from.Map == Map && Utility.InUpdateRange(this, from) && from.CanSee(this)) + from.Send(new MobileStatus(from, this, m_NetState)); + + if (from == this) + Send(new StatLockInfo(this)); + + if (Party is IParty ip) + ip.OnStatsQuery(from, this); + } + + /// + /// Overridable. Event invoked when wants to see this Mobile's skills. + /// + public virtual void OnSkillsQuery(Mobile from) + { + if (from == this) + Send(new SkillUpdate(m_Skills)); + } + + /// + /// Overridable. Virtual event invoked when changes. + /// + public virtual void OnRegionChange(Region Old, Region New) + { + } + + /// + /// Overridable. Event invoked when the Mobile is single clicked. + /// + public virtual void OnSingleClick(Mobile from) + { + if (Deleted) + return; + if (AccessLevel == AccessLevel.Player && DisableHiddenSelfClick && Hidden && from == this) + return; + + if (GuildClickMessage) + { + BaseGuild guild = m_Guild; + + if (guild != null && (m_DisplayGuildTitle || m_Player && guild.Type != GuildType.Regular)) + { + string title = GuildTitle; + string type; + + if (title == null) + title = ""; + else + title = title.Trim(); + + if (guild.Type >= 0 && (int)guild.Type < m_GuildTypes.Length) + type = m_GuildTypes[(int)guild.Type]; + else + type = ""; + + string text = string.Format(title.Length <= 0 ? "[{1}]{2}" : "[{0}, {1}]{2}", title, guild.Abbreviation, + type); + + PrivateOverheadMessage(MessageType.Regular, SpeechHue, true, text, from.NetState); + } + } + + int hue; + + if (NameHue != -1) + hue = NameHue; + else if (AccessLevel > AccessLevel.Player) + hue = 11; + else + hue = Notoriety.GetHue(Notoriety.Compute(from, this)); + + string name = Name; + + if (name == null) + name = string.Empty; + + string prefix = ""; + + if (ShowFameTitle && (m_Player || m_Body.IsHuman) && m_Fame >= 10000) + prefix = m_Female ? "Lady" : "Lord"; + + string suffix = ""; + + if (ClickTitle && Title != null && Title.Length > 0) + suffix = Title; + + suffix = ApplyNameSuffix(suffix); + + string val; + + if (prefix.Length > 0 && suffix.Length > 0) + val = string.Concat(prefix, " ", name, " ", suffix); + else if (prefix.Length > 0) + val = string.Concat(prefix, " ", name); + else if (suffix.Length > 0) + val = string.Concat(name, " ", suffix); + else + val = name; + + PrivateOverheadMessage(MessageType.Label, hue, AsciiClickMessage, val, from.NetState); + } + + public bool CheckSkill(SkillName skill, double minSkill, double maxSkill) + { + if (SkillCheckLocationHandler == null) + return false; + return SkillCheckLocationHandler(this, skill, minSkill, maxSkill); + } + + public bool CheckSkill(SkillName skill, double chance) + { + if (SkillCheckDirectLocationHandler == null) + return false; + return SkillCheckDirectLocationHandler(this, skill, chance); + } + + public bool CheckTargetSkill(SkillName skill, object target, double minSkill, double maxSkill) + { + if (SkillCheckTargetHandler == null) + return false; + + return SkillCheckTargetHandler(this, skill, target, minSkill, maxSkill); + } + + public bool CheckTargetSkill(SkillName skill, object target, double chance) + { + if (SkillCheckDirectTargetHandler == null) + return false; + + return SkillCheckDirectTargetHandler(this, skill, target, chance); + } + + public virtual void DisruptiveAction() + { + if (Meditating) + { + Meditating = false; + SendLocalizedMessage(500134); // You stop meditating. + } + } + + /// + /// Overridable. Virtual event invoked when the sector this Mobile is in gets activated. + /// + public virtual void OnSectorActivate() + { + } + + /// + /// Overridable. Virtual event invoked when the sector this Mobile is in gets deactivated. + /// + public virtual void OnSectorDeactivate() + { + } + + private class MovementRecord + { + private static Queue m_InstancePool = new Queue(); + public long m_End; + + private MovementRecord(long end) + { + m_End = end; + } + + public static MovementRecord NewInstance(long end) + { + MovementRecord r; + + if (m_InstancePool.Count > 0) + { + r = m_InstancePool.Dequeue(); + + r.m_End = end; + } + else + { + r = new MovementRecord(end); + } + + return r; + } + + public bool Expired() + { + bool v = Core.TickCount - m_End >= 0; + + if (v) + m_InstancePool.Enqueue(this); + + return v; + } + } + + private class WarmodeTimer : Timer + { + private Mobile m_Mobile; + + public WarmodeTimer(Mobile m, bool value) + : base(WarmodeSpamDelay) + { + m_Mobile = m; + Value = value; + } + + public bool Value{ get; set; } + + protected override void OnTick() + { + m_Mobile.Warmode = Value; + m_Mobile.m_WarmodeChanges = 0; + + m_Mobile.m_WarmodeTimer = null; + } + } + + private class SimpleTarget : Target + { + private TargetCallback m_Callback; + + public SimpleTarget(int range, TargetFlags flags, bool allowGround, TargetCallback callback) + : base(range, allowGround, flags) + { + m_Callback = callback; + } + + protected override void OnTarget(Mobile from, object targeted) + { + m_Callback?.Invoke(from, targeted); + } + } + + private class SimpleStateTarget : Target + { + private TargetStateCallback m_Callback; + private object m_State; + + public SimpleStateTarget(int range, TargetFlags flags, bool allowGround, TargetStateCallback callback, + object state) + : base(range, allowGround, flags) + { + m_Callback = callback; + m_State = state; + } + + protected override void OnTarget(Mobile from, object targeted) + { + m_Callback?.Invoke(from, targeted, m_State); + } + } + + private class SimpleStateTarget : Target + { + private TargetStateCallback m_Callback; + private T m_State; + + public SimpleStateTarget(int range, TargetFlags flags, bool allowGround, TargetStateCallback callback, + T state) + : base(range, allowGround, flags) + { + m_Callback = callback; + m_State = state; + } + + protected override void OnTarget(Mobile from, object targeted) + { + m_Callback?.Invoke(from, targeted, m_State); + } + } + + private class AutoManifestTimer : Timer + { + private Mobile m_Mobile; + + public AutoManifestTimer(Mobile m, TimeSpan delay) + : base(delay) + { + m_Mobile = m; + } + + protected override void OnTick() + { + if (!m_Mobile.Alive) + m_Mobile.Warmode = false; + } + } + + private class LocationComparer : IComparer + { + private static LocationComparer m_Instance; + + public LocationComparer(IEntity relativeTo) + { + RelativeTo = relativeTo; + } + + public IEntity RelativeTo{ get; set; } + + public int Compare(IEntity x, IEntity y) + { + return GetDistance(x) - GetDistance(y); + } + + public static LocationComparer GetInstance(IEntity relativeTo) + { + if (m_Instance == null) + m_Instance = new LocationComparer(relativeTo); + else + m_Instance.RelativeTo = relativeTo; + + return m_Instance; + } + + private int GetDistance(IEntity p) + { + int x = RelativeTo.X - p.X; + int y = RelativeTo.Y - p.Y; + int z = RelativeTo.Z - p.Z; + + x *= 11; + y *= 11; + + return x * x + y * y + z * z; + } + } + + #region CompareTo(...) + + public int CompareTo(IEntity other) + { + if (other == null) + return -1; + + return Serial.CompareTo(other.Serial); + } + + public int CompareTo(Mobile other) + { + return CompareTo((IEntity)other); + } + + public int CompareTo(object other) + { + if (other == null || other is IEntity) + return CompareTo((IEntity)other); + + throw new ArgumentException(); + } + + #endregion + + #region Handlers + + public static AllowBeneficialHandler AllowBeneficialHandler{ get; set; } + + public static AllowHarmfulHandler AllowHarmfulHandler{ get; set; } + + public static SkillCheckTargetHandler SkillCheckTargetHandler{ get; set; } + + public static SkillCheckLocationHandler SkillCheckLocationHandler{ get; set; } + + public static SkillCheckDirectTargetHandler SkillCheckDirectTargetHandler{ get; set; } + + public static SkillCheckDirectLocationHandler SkillCheckDirectLocationHandler{ get; set; } + + public static AOSStatusHandler AOSStatusHandler{ get; set; } + + #endregion + + #region Regeneration + + public static RegenRateHandler HitsRegenRateHandler{ get; set; } + + public static TimeSpan DefaultHitsRate{ get; set; } + + public static RegenRateHandler StamRegenRateHandler{ get; set; } + + public static TimeSpan DefaultStamRate{ get; set; } + + public static RegenRateHandler ManaRegenRateHandler{ get; set; } + + public static TimeSpan DefaultManaRate{ get; set; } + + public static TimeSpan GetHitsRegenRate(Mobile m) + { + if (HitsRegenRateHandler == null) + return DefaultHitsRate; + return HitsRegenRateHandler(m); + } + + public static TimeSpan GetStamRegenRate(Mobile m) + { + if (StamRegenRateHandler == null) + return DefaultStamRate; + return StamRegenRateHandler(m); + } + + public static TimeSpan GetManaRegenRate(Mobile m) + { + if (ManaRegenRateHandler == null) + return DefaultManaRate; + return ManaRegenRateHandler(m); + } + + #endregion + + #region Var declarations + + private Map m_Map; + private Point3D m_Location; + private Direction m_Direction; + private Body m_Body; + private int m_Hue; + private Poison m_Poison; + private BaseGuild m_Guild; + private string m_GuildTitle; + private bool m_Criminal; + private string m_Name; + private int m_Kills, m_ShortTermMurders; + private string m_Language; + private NetState m_NetState; + private bool m_Female, m_Warmode, m_Hidden, m_Blessed, m_Flying; + private int m_StatCap; + private int m_Str, m_Dex, m_Int; + private int m_Hits, m_Stam, m_Mana; + private int m_Fame, m_Karma; + private AccessLevel m_AccessLevel; + private Skills m_Skills; + private bool m_Player; + private string m_Title; + private int m_LightLevel; + private int m_TotalGold, m_TotalItems, m_TotalWeight; + private ISpell m_Spell; + private Target m_Target; + private Prompt m_Prompt; + private ContextMenu m_ContextMenu; + private Mobile m_Combatant; + private bool m_CanHearGhosts; + private int m_TithingPoints; + private bool m_DisplayGuildTitle; + private Timer m_ExpireCombatant; + private Timer m_ExpireCriminal; + private Timer m_ExpireAggrTimer; + private Timer m_LogoutTimer; + private Timer m_CombatTimer; + private Timer m_ManaTimer, m_HitsTimer, m_StamTimer; + private bool m_Paralyzed; + private ParalyzedTimer m_ParaTimer; + private bool m_Frozen; + private FrozenTimer m_FrozenTimer; + private int m_Hunger; + private Region m_Region; + private int m_VirtualArmor; + private int m_Followers, m_FollowersMax; + private List _actions; // prefer List over ArrayList for more specific profiling information + private Queue m_MoveRecords; + private int m_WarmodeChanges; + private DateTime m_NextWarmodeChange; + private WarmodeTimer m_WarmodeTimer; + private int m_VirtualArmorMod; + private VirtueInfo m_Virtues; + private Body m_BodyMod; + private Race m_Race; + + #endregion + + #region Timers + + private class ManaTimer : Timer + { + private Mobile m_Owner; + + public ManaTimer(Mobile m) + : base(GetManaRegenRate(m), GetManaRegenRate(m)) + { + Priority = TimerPriority.FiftyMS; + m_Owner = m; + } + + protected override void OnTick() + { + if (m_Owner.CanRegenMana) // m_Owner.Alive ) + m_Owner.Mana++; + + Delay = Interval = GetManaRegenRate(m_Owner); + } + } + + private class HitsTimer : Timer + { + private Mobile m_Owner; + + public HitsTimer(Mobile m) + : base(GetHitsRegenRate(m), GetHitsRegenRate(m)) + { + Priority = TimerPriority.FiftyMS; + m_Owner = m; + } + + protected override void OnTick() + { + if (m_Owner.CanRegenHits) // m_Owner.Alive && !m_Owner.Poisoned ) + m_Owner.Hits++; + + Delay = Interval = GetHitsRegenRate(m_Owner); + } + } + + private class StamTimer : Timer + { + private Mobile m_Owner; + + public StamTimer(Mobile m) + : base(GetStamRegenRate(m), GetStamRegenRate(m)) + { + Priority = TimerPriority.FiftyMS; + m_Owner = m; + } + + protected override void OnTick() + { + if (m_Owner.CanRegenStam) // m_Owner.Alive ) + m_Owner.Stam++; + + Delay = Interval = GetStamRegenRate(m_Owner); + } + } + + private class LogoutTimer : Timer + { + private Mobile m_Mobile; + + public LogoutTimer(Mobile m) + : base(TimeSpan.FromDays(1.0)) + { + Priority = TimerPriority.OneSecond; + m_Mobile = m; + } + + protected override void OnTick() + { + if (m_Mobile.m_Map != Map.Internal) + { + EventSink.InvokeLogout(new LogoutEventArgs(m_Mobile)); + + m_Mobile.LogoutLocation = m_Mobile.m_Location; + m_Mobile.LogoutMap = m_Mobile.m_Map; + + m_Mobile.Internalize(); + } + } + } + + private class ParalyzedTimer : Timer + { + private Mobile m_Mobile; + + public ParalyzedTimer(Mobile m, TimeSpan duration) + : base(duration) + { + Priority = TimerPriority.TwentyFiveMS; + m_Mobile = m; + } + + protected override void OnTick() + { + m_Mobile.Paralyzed = false; + } + } + + private class FrozenTimer : Timer + { + private Mobile m_Mobile; + + public FrozenTimer(Mobile m, TimeSpan duration) + : base(duration) + { + Priority = TimerPriority.TwentyFiveMS; + m_Mobile = m; + } + + protected override void OnTick() + { + m_Mobile.Frozen = false; + } + } + + private class CombatTimer : Timer + { + private Mobile m_Mobile; + + public CombatTimer(Mobile m) + : base(TimeSpan.FromSeconds(0.0), TimeSpan.FromSeconds(0.01), 0) + { + m_Mobile = m; + + if (!m_Mobile.m_Player && m_Mobile.m_Dex <= 100) + Priority = TimerPriority.FiftyMS; + } + + protected override void OnTick() + { + if (Core.TickCount - m_Mobile.NextCombatTime >= 0) + { + Mobile combatant = m_Mobile.Combatant; + + // If no combatant, wrong map, one of us is a ghost, or cannot see, or deleted, then stop combat + if (combatant == null || combatant.Deleted || m_Mobile.Deleted || combatant.m_Map != m_Mobile.m_Map || + !combatant.Alive || !m_Mobile.Alive || !m_Mobile.CanSee(combatant) || combatant.IsDeadBondedPet || + m_Mobile.IsDeadBondedPet) + { + m_Mobile.Combatant = null; + return; + } + + IWeapon weapon = m_Mobile.Weapon; + + if (!m_Mobile.InRange(combatant, weapon.MaxRange)) + return; + + if (m_Mobile.InLOS(combatant)) + { + weapon.OnBeforeSwing(m_Mobile, + combatant); //OnBeforeSwing for checking in regards to being hidden and whatnot + m_Mobile.RevealingAction(); + m_Mobile.NextCombatTime = + Core.TickCount + (int)weapon.OnSwing(m_Mobile, combatant).TotalMilliseconds; + } + } + } + } + + private class ExpireCombatantTimer : Timer + { + private Mobile m_Mobile; + + public ExpireCombatantTimer(Mobile m) + : base(TimeSpan.FromMinutes(1.0)) + { + Priority = TimerPriority.FiveSeconds; + m_Mobile = m; + } + + protected override void OnTick() + { + m_Mobile.Combatant = null; + } + } + + public static TimeSpan ExpireCriminalDelay{ get; set; } = TimeSpan.FromMinutes(2.0); + + private class ExpireCriminalTimer : Timer + { + private Mobile m_Mobile; + + public ExpireCriminalTimer(Mobile m) + : base(ExpireCriminalDelay) + { + Priority = TimerPriority.FiveSeconds; + m_Mobile = m; + } + + protected override void OnTick() + { + m_Mobile.Criminal = false; + } + } + + private class ExpireAggressorsTimer : Timer + { + private Mobile m_Mobile; + + public ExpireAggressorsTimer(Mobile m) + : base(TimeSpan.FromSeconds(5.0), TimeSpan.FromSeconds(5.0)) + { + m_Mobile = m; + Priority = TimerPriority.FiveSeconds; + } + + protected override void OnTick() + { + if (m_Mobile.Deleted || m_Mobile.Aggressors.Count == 0 && m_Mobile.Aggressed.Count == 0) + m_Mobile.StopAggrExpire(); + else + m_Mobile.CheckAggrExpire(); + } + } + + #endregion + + #region Prompts + + private class SimplePrompt : Prompt + { + private PromptCallback m_Callback; + private bool m_CallbackHandlesCancel; + private PromptCallback m_CancelCallback; + + public SimplePrompt(PromptCallback callback, PromptCallback cancelCallback) + { + m_Callback = callback; + m_CancelCallback = cancelCallback; + } + + public SimplePrompt(PromptCallback callback, bool callbackHandlesCancel) + { + m_Callback = callback; + m_CallbackHandlesCancel = callbackHandlesCancel; + } + + public SimplePrompt(PromptCallback callback) + : this(callback, false) + { + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Callback != null) + m_Callback(from, text); + } + + public override void OnCancel(Mobile from) + { + if (m_CallbackHandlesCancel && m_Callback != null) + m_Callback(from, ""); + else if (m_CancelCallback != null) + m_CancelCallback(from, ""); + } + } + + public Prompt BeginPrompt(PromptCallback callback, PromptCallback cancelCallback) + { + Prompt p = new SimplePrompt(callback, cancelCallback); + + Prompt = p; + return p; + } + + public Prompt BeginPrompt(PromptCallback callback, bool callbackHandlesCancel) + { + Prompt p = new SimplePrompt(callback, callbackHandlesCancel); + + Prompt = p; + return p; + } + + public Prompt BeginPrompt(PromptCallback callback) + { + return BeginPrompt(callback, false); + } + + private class SimpleStatePrompt : Prompt + { + private PromptStateCallback m_Callback; + + private bool m_CallbackHandlesCancel; + private PromptStateCallback m_CancelCallback; + + private object m_State; + + public SimpleStatePrompt(PromptStateCallback callback, PromptStateCallback cancelCallback, object state) + { + m_Callback = callback; + m_CancelCallback = cancelCallback; + m_State = state; + } + + public SimpleStatePrompt(PromptStateCallback callback, bool callbackHandlesCancel, object state) + { + m_Callback = callback; + m_State = state; + m_CallbackHandlesCancel = callbackHandlesCancel; + } + + public SimpleStatePrompt(PromptStateCallback callback, object state) + : this(callback, false, state) + { + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Callback != null) + m_Callback(from, text, m_State); + } + + public override void OnCancel(Mobile from) + { + if (m_CallbackHandlesCancel && m_Callback != null) + m_Callback(from, "", m_State); + else if (m_CancelCallback != null) + m_CancelCallback(from, "", m_State); + } + } + + public Prompt BeginPrompt(PromptStateCallback callback, PromptStateCallback cancelCallback, object state) + { + Prompt p = new SimpleStatePrompt(callback, cancelCallback, state); + + Prompt = p; + return p; + } + + public Prompt BeginPrompt(PromptStateCallback callback, bool callbackHandlesCancel, object state) + { + Prompt p = new SimpleStatePrompt(callback, callbackHandlesCancel, state); + + Prompt = p; + return p; + } + + public Prompt BeginPrompt(PromptStateCallback callback, object state) + { + return BeginPrompt(callback, false, state); + } + + private class SimpleStatePrompt : Prompt + { + private PromptStateCallback m_Callback; + + private bool m_CallbackHandlesCancel; + private PromptStateCallback m_CancelCallback; + + private T m_State; + + public SimpleStatePrompt(PromptStateCallback callback, PromptStateCallback cancelCallback, T state) + { + m_Callback = callback; + m_CancelCallback = cancelCallback; + m_State = state; + } + + public SimpleStatePrompt(PromptStateCallback callback, bool callbackHandlesCancel, T state) + { + m_Callback = callback; + m_State = state; + m_CallbackHandlesCancel = callbackHandlesCancel; + } + + public SimpleStatePrompt(PromptStateCallback callback, T state) + : this(callback, false, state) + { + } + + public override void OnResponse(Mobile from, string text) + { + if (m_Callback != null) + m_Callback(from, text, m_State); + } + + public override void OnCancel(Mobile from) + { + if (m_CallbackHandlesCancel && m_Callback != null) + m_Callback(from, "", m_State); + else if (m_CancelCallback != null) + m_CancelCallback(from, "", m_State); + } + } + + public Prompt BeginPrompt(PromptStateCallback callback, PromptStateCallback cancelCallback, T state) + { + Prompt p = new SimpleStatePrompt(callback, cancelCallback, state); + + Prompt = p; + return p; + } + + public Prompt BeginPrompt(PromptStateCallback callback, bool callbackHandlesCancel, T state) + { + Prompt p = new SimpleStatePrompt(callback, callbackHandlesCancel, state); + + Prompt = p; + return p; + } + + public Prompt BeginPrompt(PromptStateCallback callback, T state) + { + return BeginPrompt(callback, false, state); + } + + public Prompt Prompt + { + get => m_Prompt; + set + { + Prompt oldPrompt = m_Prompt; + Prompt newPrompt = value; + + if (oldPrompt == newPrompt) + return; + + m_Prompt = null; + + if (oldPrompt != null && newPrompt != null) + oldPrompt.OnCancel(this); + + m_Prompt = newPrompt; + + if (newPrompt != null) + Send(new UnicodePrompt(newPrompt)); + } + } + + #endregion + + #region Get*Sound + + public virtual int GetAngerSound() + { + if (BaseSoundID != 0) + return BaseSoundID; + + return -1; + } + + public virtual int GetIdleSound() + { + if (BaseSoundID != 0) + return BaseSoundID + 1; + + return -1; + } + + public virtual int GetAttackSound() + { + if (BaseSoundID != 0) + return BaseSoundID + 2; + + return -1; + } + + public virtual int GetHurtSound() + { + if (BaseSoundID != 0) + return BaseSoundID + 3; + + return -1; + } + + public virtual int GetDeathSound() + { + if (BaseSoundID != 0) return BaseSoundID + 4; + + if (m_Body.IsHuman) return Utility.Random(m_Female ? 0x314 : 0x423, m_Female ? 4 : 5); + return -1; + } + + #endregion + + #region Get*InRange + + public IPooledEnumerable GetItemsInRange(int range) + { + return GetItemsInRange(range); + } + + public IPooledEnumerable GetItemsInRange(int range) where T : Item + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + return map.GetItemsInRange(m_Location, range); + } + + public IPooledEnumerable GetObjectsInRange(int range) + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + return map.GetObjectsInRange(m_Location, range); + } + + public IPooledEnumerable GetMobilesInRange(int range) + { + return GetMobilesInRange(range); + } + + public IPooledEnumerable GetMobilesInRange(int range) where T : Mobile + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + return map.GetMobilesInRange(m_Location, range); + } + + public IPooledEnumerable GetClientsInRange(int range) + { + Map map = m_Map; + + if (map == null) + return Map.NullEnumerable.Instance; + + return map.GetClientsInRange(m_Location, range); + } + + #endregion + + #region Say/SayTo/Emote/Whisper/Yell + + public void SayTo(Mobile to, bool ascii, string text) + { + PrivateOverheadMessage(MessageType.Regular, SpeechHue, ascii, text, to.NetState); + } + + public void SayTo(Mobile to, string text) + { + SayTo(to, false, text); + } + + public void SayTo(Mobile to, string format, params object[] args) + { + SayTo(to, false, string.Format(format, args)); + } + + public void SayTo(Mobile to, bool ascii, string format, params object[] args) + { + SayTo(to, ascii, string.Format(format, args)); + } + + public void SayTo(Mobile to, int number) + { + to.Send(new MessageLocalized(Serial, Body, MessageType.Regular, SpeechHue, 3, number, Name, "")); + } + + public void SayTo(Mobile to, int number, string args) + { + to.Send(new MessageLocalized(Serial, Body, MessageType.Regular, SpeechHue, 3, number, Name, args)); + } + + public void Say(bool ascii, string text) + { + PublicOverheadMessage(MessageType.Regular, SpeechHue, ascii, text); + } + + public void Say(string text) + { + PublicOverheadMessage(MessageType.Regular, SpeechHue, false, text); + } + + public void Say(string format, params object[] args) + { + Say(string.Format(format, args)); + } + + public void Say(int number, AffixType type, string affix, string args) + { + PublicOverheadMessage(MessageType.Regular, SpeechHue, number, type, affix, args); + } + + public void Say(int number) + { + Say(number, ""); + } + + public void Say(int number, string args) + { + PublicOverheadMessage(MessageType.Regular, SpeechHue, number, args); + } + + public void Emote(string text) + { + PublicOverheadMessage(MessageType.Emote, EmoteHue, false, text); + } + + public void Emote(string format, params object[] args) + { + Emote(string.Format(format, args)); + } + + public void Emote(int number) + { + Emote(number, ""); + } + + public void Emote(int number, string args) + { + PublicOverheadMessage(MessageType.Emote, EmoteHue, number, args); + } + + public void Whisper(string text) + { + PublicOverheadMessage(MessageType.Whisper, WhisperHue, false, text); + } + + public void Whisper(string format, params object[] args) + { + Whisper(string.Format(format, args)); + } + + public void Whisper(int number) + { + Whisper(number, ""); + } + + public void Whisper(int number, string args) + { + PublicOverheadMessage(MessageType.Whisper, WhisperHue, number, args); + } + + public void Yell(string text) + { + PublicOverheadMessage(MessageType.Yell, YellHue, false, text); + } + + public void Yell(string format, params object[] args) + { + Yell(string.Format(format, args)); + } + + public void Yell(int number) + { + Yell(number, ""); + } + + public void Yell(int number, string args) + { + PublicOverheadMessage(MessageType.Yell, YellHue, number, args); + } + + #endregion + + #region Gumps/Menus + + public bool SendHuePicker(HuePicker p) + { + return SendHuePicker(p, false); + } + + public bool SendHuePicker(HuePicker p, bool throwOnOffline) + { + if (m_NetState != null) + { + p.SendTo(m_NetState); + return true; + } + + if (throwOnOffline) throw new MobileNotConnectedException(this, "Hue picker could not be sent."); + + return false; + } + + public Gump FindGump(Type type) + { + NetState ns = m_NetState; + + if (ns != null) + foreach (Gump gump in ns.Gumps) + if (type.IsInstanceOfType(gump)) + return gump; + + return null; + } + + public bool CloseGump(Type type) + { + if (m_NetState != null) + { + Gump gump = FindGump(type); + + if (gump != null) + { + m_NetState.Send(new CloseGump(gump.TypeID, 0)); + + m_NetState.RemoveGump(gump); + + gump.OnServerClose(m_NetState); + } + + return true; + } + + return false; + } + + [Obsolete("Use CloseGump( Type ) instead.")] + public bool CloseGump(Type type, int buttonID) + { + return CloseGump(type); + } + + [Obsolete("Use CloseGump( Type ) instead.")] + public bool CloseGump(Type type, int buttonID, bool throwOnOffline) + { + return CloseGump(type); + } + + public bool CloseAllGumps() + { + NetState ns = m_NetState; + + if (ns != null) + { + List gumps = new List(ns.Gumps); + + ns.ClearGumps(); + + foreach (Gump gump in gumps) + { + ns.Send(new CloseGump(gump.TypeID, 0)); + + gump.OnServerClose(ns); + } + + return true; + } + + return false; + } + + [Obsolete("Use CloseAllGumps() instead.", false)] + public bool CloseAllGumps(bool throwOnOffline) + { + return CloseAllGumps(); + } + + public bool HasGump(Type type) + { + return FindGump(type) != null; + } + + [Obsolete("Use HasGump( Type ) instead.", false)] + public bool HasGump(Type type, bool throwOnOffline) + { + return HasGump(type); + } + + public bool SendGump(Gump g) + { + return SendGump(g, false); + } + + public bool SendGump(Gump g, bool throwOnOffline) + { + if (m_NetState != null) + { + g.SendTo(m_NetState); + return true; + } + + if (throwOnOffline) throw new MobileNotConnectedException(this, "Gump could not be sent."); + return false; + } + + public bool SendMenu(IMenu m) + { + return SendMenu(m, false); + } + + public bool SendMenu(IMenu m, bool throwOnOffline) + { + if (m_NetState != null) + { + m.SendTo(m_NetState); + return true; + } + + if (throwOnOffline) throw new MobileNotConnectedException(this, "Menu could not be sent."); + return false; + } + + #endregion + + #region Beneficial Checks/Actions + + public virtual bool CanBeBeneficial(Mobile target) + { + return CanBeBeneficial(target, true, false); + } + + public virtual bool CanBeBeneficial(Mobile target, bool message) + { + return CanBeBeneficial(target, message, false); + } + + public virtual bool CanBeBeneficial(Mobile target, bool message, bool allowDead) + { + if (target == null) + return false; + + if (Deleted || target.Deleted || !Alive || IsDeadBondedPet || + !allowDead && (!target.Alive || target.IsDeadBondedPet)) + { + if (message) + SendLocalizedMessage(1001017); // You can not perform beneficial acts on your target. + + return false; + } + + if (target == this) + return true; + + if ( /*m_Player &&*/ !Region.AllowBeneficial(this, target)) + { + // TODO: Pets + //if ( !(target.m_Player || target.Body.IsHuman || target.Body.IsAnimal) ) + //{ + if (message) + SendLocalizedMessage(1001017); // You can not perform beneficial acts on your target. + + return false; + //} + } + + return true; + } + + public virtual bool IsBeneficialCriminal(Mobile target) + { + if (this == target) + return false; + + int n = Notoriety.Compute(this, target); + + return n == Notoriety.Criminal || n == Notoriety.Murderer; + } + + /// + /// Overridable. Event invoked when the Mobile does a beneficial action. + /// + public virtual void OnBeneficialAction(Mobile target, bool isCriminal) + { + if (isCriminal) + CriminalAction(false); + } + + public virtual void DoBeneficial(Mobile target) + { + if (target == null) + return; + + OnBeneficialAction(target, IsBeneficialCriminal(target)); + + Region.OnBeneficialAction(this, target); + target.Region.OnGotBeneficialAction(this, target); + } + + public virtual bool BeneficialCheck(Mobile target) + { + if (CanBeBeneficial(target, true)) + { + DoBeneficial(target); + return true; + } + + return false; + } + + #endregion + + #region Harmful Checks/Actions + + public virtual bool CanBeHarmful(Mobile target) + { + return CanBeHarmful(target, true); + } + + public virtual bool CanBeHarmful(Mobile target, bool message) + { + return CanBeHarmful(target, message, false); + } + + public virtual bool CanBeHarmful(Mobile target, bool message, bool ignoreOurBlessedness) + { + if (target == null) + return false; + + if (Deleted || !ignoreOurBlessedness && m_Blessed || target.Deleted || target.m_Blessed || !Alive || + IsDeadBondedPet || !target.Alive || target.IsDeadBondedPet) + { + if (message) + SendLocalizedMessage(1001018); // You can not perform negative acts on your target. + + return false; + } + + if (target == this) + return true; + + // TODO: Pets + if ( /*m_Player &&*/ + !Region.AllowHarmful(this, target) + ) //(target.m_Player || target.Body.IsHuman) && !Region.AllowHarmful( this, target ) ) + { + if (message) + SendLocalizedMessage(1001018); // You can not perform negative acts on your target. + + return false; + } + + return true; + } + + public virtual bool IsHarmfulCriminal(Mobile target) + { + if (this == target) + return false; + + return Notoriety.Compute(this, target) == Notoriety.Innocent; + } + + /// + /// Overridable. Event invoked when the Mobile does a harmful action. + /// + public virtual void OnHarmfulAction(Mobile target, bool isCriminal) + { + if (isCriminal) + CriminalAction(false); + } + + public virtual void DoHarmful(Mobile target) + { + DoHarmful(target, false); + } + + public virtual void DoHarmful(Mobile target, bool indirect) + { + if (target == null || Deleted) + return; + + bool isCriminal = IsHarmfulCriminal(target); + + OnHarmfulAction(target, isCriminal); + target.AggressiveAction(this, isCriminal); + + Region.OnDidHarmful(this, target); + target.Region.OnGotHarmful(this, target); + + if (!indirect) + Combatant = target; + + if (m_ExpireCombatant == null) + m_ExpireCombatant = new ExpireCombatantTimer(this); + else + m_ExpireCombatant.Stop(); + + m_ExpireCombatant.Start(); + } + + public virtual bool HarmfulCheck(Mobile target) + { + if (CanBeHarmful(target)) + { + DoHarmful(target); + return true; + } + + return false; + } + + #endregion + + #region Stats + + /// + /// Gets a list of all StatMod's currently active for the Mobile. + /// + public List StatMods{ get; private set; } + + public bool RemoveStatMod(string name) + { + for (int i = 0; i < StatMods.Count; ++i) + { + StatMod check = StatMods[i]; + + if (check.Name == name) + { + StatMods.RemoveAt(i); + CheckStatTimers(); + Delta(MobileDelta.Stat | GetStatDelta(check.Type)); + return true; + } + } + + return false; + } + + public StatMod GetStatMod(string name) + { + for (int i = 0; i < StatMods.Count; ++i) + { + StatMod check = StatMods[i]; + + if (check.Name == name) + return check; + } + + return null; + } + + public void AddStatMod(StatMod mod) + { + for (int i = 0; i < StatMods.Count; ++i) + { + StatMod check = StatMods[i]; + + if (check.Name == mod.Name) + { + Delta(MobileDelta.Stat | GetStatDelta(check.Type)); + StatMods.RemoveAt(i); + break; + } + } + + StatMods.Add(mod); + Delta(MobileDelta.Stat | GetStatDelta(mod.Type)); + CheckStatTimers(); + } + + private MobileDelta GetStatDelta(StatType type) + { + MobileDelta delta = 0; + + if ((type & StatType.Str) != 0) + delta |= MobileDelta.Hits; + + if ((type & StatType.Dex) != 0) + delta |= MobileDelta.Stam; + + if ((type & StatType.Int) != 0) + delta |= MobileDelta.Mana; + + return delta; + } + + /// + /// Computes the total modified offset for the specified stat type. Expired instances are removed. + /// + public int GetStatOffset(StatType type) + { + int offset = 0; + + for (int i = 0; i < StatMods.Count; ++i) + { + StatMod mod = StatMods[i]; + + if (mod.HasElapsed()) + { + StatMods.RemoveAt(i); + Delta(MobileDelta.Stat | GetStatDelta(mod.Type)); + CheckStatTimers(); + + --i; + } + else if ((mod.Type & type) != 0) + { + offset += mod.Offset; + } + } + + return offset; + } + + /// + /// Overridable. Virtual event invoked when the changes. + /// + /// + /// + public virtual void OnRawStrChange(int oldValue) + { + } + + /// + /// Overridable. Virtual event invoked when changes. + /// + /// + /// + public virtual void OnRawDexChange(int oldValue) + { + } + + /// + /// Overridable. Virtual event invoked when the changes. + /// + /// + /// + public virtual void OnRawIntChange(int oldValue) + { + } + + /// + /// Overridable. Virtual event invoked when the , , or + /// changes. + /// + /// + /// + /// + public virtual void OnRawStatChange(StatType stat, int oldValue) + { + } + + /// + /// Gets or sets the base, unmodified, strength of the Mobile. Ranges from 1 to 65000, inclusive. + /// + /// + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public int RawStr + { + get => m_Str; + set + { + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; + + if (m_Str != value) + { + int oldValue = m_Str; + + m_Str = value; + Delta(MobileDelta.Stat | MobileDelta.Hits); + + if (Hits < HitsMax) + { + if (m_HitsTimer == null) + m_HitsTimer = new HitsTimer(this); + + m_HitsTimer.Start(); + } + else if (Hits > HitsMax) + { + Hits = HitsMax; + } + + OnRawStrChange(oldValue); + OnRawStatChange(StatType.Str, oldValue); + } + } + } + + /// + /// Gets or sets the effective strength of the Mobile. This is the sum of the plus any additional + /// modifiers. Any attempts to set this value when under the influence of a will result in no change. + /// It ranges from 1 to 65000, inclusive. + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual int Str + { + get + { + int value = m_Str + GetStatOffset(StatType.Str); + + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; + + return value; + } + set + { + if (StatMods.Count == 0) + RawStr = value; + } + } + + /// + /// Gets or sets the base, unmodified, dexterity of the Mobile. Ranges from 1 to 65000, inclusive. + /// + /// + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public int RawDex + { + get => m_Dex; + set + { + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; + + if (m_Dex != value) + { + int oldValue = m_Dex; + + m_Dex = value; + Delta(MobileDelta.Stat | MobileDelta.Stam); + + if (Stam < StamMax) + { + if (m_StamTimer == null) + m_StamTimer = new StamTimer(this); + + m_StamTimer.Start(); + } + else if (Stam > StamMax) + { + Stam = StamMax; + } + + OnRawDexChange(oldValue); + OnRawStatChange(StatType.Dex, oldValue); + } + } + } + + /// + /// Gets or sets the effective dexterity of the Mobile. This is the sum of the plus any additional + /// modifiers. Any attempts to set this value when under the influence of a will result in no change. + /// It ranges from 1 to 65000, inclusive. + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual int Dex + { + get + { + int value = m_Dex + GetStatOffset(StatType.Dex); + + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; + + return value; + } + set + { + if (StatMods.Count == 0) + RawDex = value; + } + } + + /// + /// Gets or sets the base, unmodified, intelligence of the Mobile. Ranges from 1 to 65000, inclusive. + /// + /// + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public int RawInt + { + get => m_Int; + set + { + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; + + if (m_Int != value) + { + int oldValue = m_Int; + + m_Int = value; + Delta(MobileDelta.Stat | MobileDelta.Mana); + + if (Mana < ManaMax) + { + if (m_ManaTimer == null) + m_ManaTimer = new ManaTimer(this); + + m_ManaTimer.Start(); + } + else if (Mana > ManaMax) + { + Mana = ManaMax; + } + + OnRawIntChange(oldValue); + OnRawStatChange(StatType.Int, oldValue); + } + } + } + + /// + /// Gets or sets the effective intelligence of the Mobile. This is the sum of the plus any additional + /// modifiers. Any attempts to set this value when under the influence of a will result in no change. + /// It ranges from 1 to 65000, inclusive. + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual int Int + { + get + { + int value = m_Int + GetStatOffset(StatType.Int); + + if (value < 1) + value = 1; + else if (value > 65000) + value = 65000; + + return value; + } + set + { + if (StatMods.Count == 0) + RawInt = value; + } + } + + public virtual void OnHitsChange(int oldValue) + { + } + + public virtual void OnStamChange(int oldValue) + { + } + + public virtual void OnManaChange(int oldValue) + { + } + + /// + /// Gets or sets the current hit point of the Mobile. This value ranges from 0 to , inclusive. When set + /// to the value of , the CanReportMurder flag of all + /// aggressors is reset to false, and the list of damage entries is cleared. + /// + [CommandProperty(AccessLevel.GameMaster)] + public int Hits + { + get => m_Hits; + set + { + if (Deleted) + return; + + if (value < 0) + { + value = 0; + } + else if (value >= HitsMax) + { + value = HitsMax; + + m_HitsTimer?.Stop(); + + for (int i = 0; i < Aggressors.Count; i++) //reset reports on full HP + Aggressors[i].CanReportMurder = false; + + if (DamageEntries.Count > 0) + DamageEntries.Clear(); // reset damage entries on full HP + } + + if (value < HitsMax) + { + if (CanRegenHits) + { + if (m_HitsTimer == null) + m_HitsTimer = new HitsTimer(this); + + m_HitsTimer.Start(); + } + else + { + m_HitsTimer?.Stop(); + } + } + + if (m_Hits != value) + { + int oldValue = m_Hits; + m_Hits = value; + Delta(MobileDelta.Hits); + OnHitsChange(oldValue); + } + } + } + + /// + /// Overridable. Gets the maximum hit point of the Mobile. By default, this returns: 50 + ( / 2) + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual int HitsMax => 50 + Str / 2; + + /// + /// Gets or sets the current stamina of the Mobile. This value ranges from 0 to , inclusive. + /// + [CommandProperty(AccessLevel.GameMaster)] + public int Stam + { + get => m_Stam; + set + { + if (Deleted) + return; + + if (value < 0) + { + value = 0; + } + else if (value >= StamMax) + { + value = StamMax; + + m_StamTimer?.Stop(); + } + + if (value < StamMax) + { + if (CanRegenStam) + { + if (m_StamTimer == null) + m_StamTimer = new StamTimer(this); + + m_StamTimer.Start(); + } + else + { + m_StamTimer?.Stop(); + } + } + + if (m_Stam != value) + { + int oldValue = m_Stam; + m_Stam = value; + Delta(MobileDelta.Stam); + OnStamChange(oldValue); + } + } + } + + /// + /// Overridable. Gets the maximum stamina of the Mobile. By default, this returns: + /// + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual int StamMax => Dex; + + /// + /// Gets or sets the current stamina of the Mobile. This value ranges from 0 to , inclusive. + /// + [CommandProperty(AccessLevel.GameMaster)] + public int Mana + { + get => m_Mana; + set + { + if (Deleted) + return; + + if (value < 0) + { + value = 0; + } + else if (value >= ManaMax) + { + value = ManaMax; + + m_ManaTimer?.Stop(); + + if (Meditating) + { + Meditating = false; + SendLocalizedMessage(501846); // You are at peace. + } + } + + if (value < ManaMax) + { + if (CanRegenMana) + { + if (m_ManaTimer == null) + m_ManaTimer = new ManaTimer(this); + + m_ManaTimer.Start(); + } + else + { + m_ManaTimer?.Stop(); + } + } + + if (m_Mana != value) + { + int oldValue = m_Mana; + m_Mana = value; + Delta(MobileDelta.Mana); + OnManaChange(oldValue); + } + } + } + + /// + /// Overridable. Gets the maximum mana of the Mobile. By default, this returns: + /// + /// + /// + /// + [CommandProperty(AccessLevel.GameMaster)] + public virtual int ManaMax => Int; + + #endregion + + #region Poison/Curing + + public Timer PoisonTimer{ get; private set; } + + [CommandProperty(AccessLevel.GameMaster)] + public Poison Poison + { + get => m_Poison; + set + { + /*if ( m_Poison != value && (m_Poison == null || value == null || m_Poison.Level < value.Level) ) + {*/ + m_Poison = value; + Delta(MobileDelta.HealthbarPoison); + + if (PoisonTimer != null) + { + PoisonTimer.Stop(); + PoisonTimer = null; + } + + if (m_Poison != null) + { + PoisonTimer = m_Poison.ConstructTimer(this); + + PoisonTimer?.Start(); + } + + CheckStatTimers(); + /*}*/ + } + } + + /// + /// Overridable. Event invoked when a call to failed because + /// returned false: the Mobile was resistant to the poison. By default, this broadcasts an overhead message: * The poison + /// seems to have no effect. * + /// + /// + /// + /// + public virtual void OnPoisonImmunity(Mobile from, Poison poison) + { + PublicOverheadMessage(MessageType.Emote, 0x3B2, 1005534); // * The poison seems to have no effect. * + } + + /// + /// Overridable. Virtual event invoked when a call to failed because + /// returned false: the Mobile was already poisoned by an equal or greater strength poison. + /// + /// + /// + /// + public virtual void OnHigherPoison(Mobile from, Poison poison) + { + } + + /// + /// Overridable. Event invoked when a call to succeeded. By default, this broadcasts an overhead + /// message varying by the level of the poison. Example: * Zippy begins to spasm uncontrollably. * + /// + /// + /// + public virtual void OnPoisoned(Mobile from, Poison poison, Poison oldPoison) + { + if (poison != null) + { + LocalOverheadMessage(MessageType.Regular, 0x21, 1042857 + poison.Level * 2); + NonlocalOverheadMessage(MessageType.Regular, 0x21, 1042858 + poison.Level * 2, Name); + } + } + + /// + /// Overridable. Called from , this method checks if the Mobile is immune to some + /// . If true, will be invoked and + /// is returned. + /// + /// + /// + /// + public virtual bool CheckPoisonImmunity(Mobile from, Poison poison) + { + return false; + } + + /// + /// Overridable. Called from , this method checks if the Mobile is already poisoned by some + /// of equal or greater strength. If true, will be invoked and + /// is returned. + /// + /// + /// + /// + public virtual bool CheckHigherPoison(Mobile from, Poison poison) + { + return m_Poison != null && m_Poison.Level >= poison.Level; + } + + /// + /// Overridable. Attempts to apply poison to the Mobile. Checks are made such that no + /// higher poison is active and that the Mobile is not + /// immune to the poison. Provided those assertions are true, the + /// is applied and is invoked. + /// + /// + /// + /// + /// One of four possible values: + /// + /// + /// + /// Cured + /// + /// The parameter was null and so was invoked. + /// + /// + /// + /// HigherPoisonActive + /// + /// The call to returned false. + /// + /// + /// + /// Immune + /// + /// The call to returned false. + /// + /// + /// + /// Poisoned + /// + /// The was successfully applied. + /// + /// + /// + public virtual ApplyPoisonResult ApplyPoison(Mobile from, Poison poison) + { + if (poison == null) + { + CurePoison(from); + return ApplyPoisonResult.Cured; + } + + if (CheckHigherPoison(from, poison)) + { + OnHigherPoison(from, poison); + return ApplyPoisonResult.HigherPoisonActive; + } + + if (CheckPoisonImmunity(from, poison)) + { + OnPoisonImmunity(from, poison); + return ApplyPoisonResult.Immune; + } + + Poison oldPoison = m_Poison; + Poison = poison; + + OnPoisoned(from, poison, oldPoison); + + return ApplyPoisonResult.Poisoned; + } + + /// + /// Overridable. Called from , this method checks to see that the Mobile can be cured of + /// + /// + /// + /// + public virtual bool CheckCure(Mobile from) + { + return true; + } + + /// + /// Overridable. Virtual event invoked when a call to succeeded. + /// + /// + /// + /// + public virtual void OnCured(Mobile from, Poison oldPoison) + { + } + + /// + /// Overridable. Virtual event invoked when a call to failed. + /// + /// + /// + /// + public virtual void OnFailedCure(Mobile from) + { + } + + /// + /// Overridable. Attempts to cure any poison that is currently active. + /// + /// True if poison was cured, false if otherwise. + public virtual bool CurePoison(Mobile from) + { + if (CheckCure(from)) + { + Poison oldPoison = m_Poison; + Poison = null; + + OnCured(from, oldPoison); + + return true; + } + + OnFailedCure(from); + + return false; + } + + #endregion + + #region Hair + + private HairInfo m_Hair; + private FacialHairInfo m_FacialHair; + + [CommandProperty(AccessLevel.GameMaster)] + public int HairItemID + { + get + { + if (m_Hair == null) + return 0; + + return m_Hair.ItemID; + } + set + { + if (m_Hair == null && value > 0) + m_Hair = new HairInfo(value); + else if (value <= 0) + m_Hair = null; + else + m_Hair.ItemID = value; + + Delta(MobileDelta.Hair); + } + } + + // [CommandProperty( AccessLevel.GameMaster )] + // public int HairSerial { get { return HairInfo.FakeSerial( this ); } } + + [CommandProperty(AccessLevel.GameMaster)] + public int FacialHairItemID + { + get + { + if (m_FacialHair == null) + return 0; + + return m_FacialHair.ItemID; + } + set + { + if (m_FacialHair == null && value > 0) + m_FacialHair = new FacialHairInfo(value); + else if (value <= 0) + m_FacialHair = null; + else + m_FacialHair.ItemID = value; + + Delta(MobileDelta.FacialHair); + } + } + + // [CommandProperty( AccessLevel.GameMaster )] + // public int FacialHairSerial { get { return FacialHairInfo.FakeSerial( this ); } } + + [CommandProperty(AccessLevel.GameMaster)] + public int HairHue + { + get + { + if (m_Hair == null) + return 0; + return m_Hair.Hue; + } + set + { + if (m_Hair != null) + { + m_Hair.Hue = value; + Delta(MobileDelta.Hair); + } + } + } + + [CommandProperty(AccessLevel.GameMaster)] + public int FacialHairHue + { + get + { + if (m_FacialHair == null) + return 0; + + return m_FacialHair.Hue; + } + set + { + if (m_FacialHair != null) + { + m_FacialHair.Hue = value; + Delta(MobileDelta.FacialHair); + } + } + } + + #endregion + + #region Effects & Particles + + public void MovingEffect(IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, + int hue, int renderMode) + { + Effects.SendMovingEffect(this, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode); + } + + public void MovingEffect(IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes) + { + Effects.SendMovingEffect(this, to, itemID, speed, duration, fixedDirection, explodes, 0, 0); + } + + public void MovingParticles(IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, + int hue, int renderMode, int effect, int explodeEffect, int explodeSound, EffectLayer layer, int unknown) + { + Effects.SendMovingParticles(this, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, + explodeEffect, explodeSound, layer, unknown); + } + + public void MovingParticles(IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, + int hue, int renderMode, int effect, int explodeEffect, int explodeSound, int unknown) + { + Effects.SendMovingParticles(this, to, itemID, speed, duration, fixedDirection, explodes, hue, renderMode, effect, + explodeEffect, explodeSound, (EffectLayer)255, unknown); + } + + public void MovingParticles(IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, + int effect, int explodeEffect, int explodeSound, int unknown) + { + Effects.SendMovingParticles(this, to, itemID, speed, duration, fixedDirection, explodes, effect, explodeEffect, + explodeSound, unknown); + } + + public void MovingParticles(IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, + int effect, int explodeEffect, int explodeSound) + { + Effects.SendMovingParticles(this, to, itemID, speed, duration, fixedDirection, explodes, 0, 0, effect, + explodeEffect, explodeSound, 0); + } + + public void FixedEffect(int itemID, int speed, int duration, int hue, int renderMode) + { + Effects.SendTargetEffect(this, itemID, speed, duration, hue, renderMode); + } + + public void FixedEffect(int itemID, int speed, int duration) + { + Effects.SendTargetEffect(this, itemID, speed, duration, 0, 0); + } + + public void FixedParticles(int itemID, int speed, int duration, int effect, int hue, int renderMode, + EffectLayer layer, int unknown) + { + Effects.SendTargetParticles(this, itemID, speed, duration, hue, renderMode, effect, layer, unknown); + } + + public void FixedParticles(int itemID, int speed, int duration, int effect, int hue, int renderMode, + EffectLayer layer) + { + Effects.SendTargetParticles(this, itemID, speed, duration, hue, renderMode, effect, layer, 0); + } + + public void FixedParticles(int itemID, int speed, int duration, int effect, EffectLayer layer, int unknown) + { + Effects.SendTargetParticles(this, itemID, speed, duration, 0, 0, effect, layer, unknown); + } + + public void FixedParticles(int itemID, int speed, int duration, int effect, EffectLayer layer) + { + Effects.SendTargetParticles(this, itemID, speed, duration, 0, 0, effect, layer, 0); + } + + public void BoltEffect(int hue) + { + Effects.SendBoltEffect(this, true, hue); + } + + #endregion + + #region GetDirectionTo[..] + + public Direction GetDirectionTo(int x, int y) + { + int dx = m_Location.m_X - x; + int dy = m_Location.m_Y - y; + + int rx = (dx - dy) * 44; + int ry = (dx + dy) * 44; + + int ax = Math.Abs(rx); + int ay = Math.Abs(ry); + + Direction ret; + + if ((ay >> 1) - ax >= 0) + ret = ry > 0 ? Direction.Up : Direction.Down; + else if ((ax >> 1) - ay >= 0) + ret = rx > 0 ? Direction.Left : Direction.Right; + else if (rx >= 0 && ry >= 0) + ret = Direction.West; + else if (rx >= 0 && ry < 0) + ret = Direction.South; + else if (rx < 0 && ry < 0) + ret = Direction.East; + else + ret = Direction.North; + + return ret; + } + + public Direction GetDirectionTo(Point2D p) + { + return GetDirectionTo(p.m_X, p.m_Y); + } + + public Direction GetDirectionTo(Point3D p) + { + return GetDirectionTo(p.m_X, p.m_Y); + } + + public Direction GetDirectionTo(IPoint2D p) + { + if (p == null) + return Direction.North; + + return GetDirectionTo(p.X, p.Y); + } + + #endregion + + #region Overhead messages + + public void PublicOverheadMessage(MessageType type, int hue, bool ascii, string text) + { + PublicOverheadMessage(type, hue, ascii, text, true); + } + + public void PublicOverheadMessage(MessageType type, int hue, bool ascii, string text, bool noLineOfSight) + { + if (m_Map != null) + { + Packet p = null; + + if (ascii) + p = new AsciiMessage(Serial, Body, type, hue, 3, Name, text); + else + p = new UnicodeMessage(Serial, Body, type, hue, 3, m_Language, Name, text); + + p.Acquire(); + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(this) && (noLineOfSight || state.Mobile.InLOS(this))) + state.Send(p); + + Packet.Release(p); + + eable.Free(); + } + } + + public void PublicOverheadMessage(MessageType type, int hue, int number) + { + PublicOverheadMessage(type, hue, number, "", true); + } + + public void PublicOverheadMessage(MessageType type, int hue, int number, string args) + { + PublicOverheadMessage(type, hue, number, args, true); + } + + public void PublicOverheadMessage(MessageType type, int hue, int number, string args, bool noLineOfSight) + { + if (m_Map != null) + { + Packet p = Packet.Acquire(new MessageLocalized(Serial, Body, type, hue, 3, number, Name, args)); + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(this) && (noLineOfSight || state.Mobile.InLOS(this))) + state.Send(p); + + Packet.Release(p); + + eable.Free(); + } + } + + public void PublicOverheadMessage(MessageType type, int hue, int number, AffixType affixType, string affix, + string args) + { + PublicOverheadMessage(type, hue, number, affixType, affix, args, true); + } + + public void PublicOverheadMessage(MessageType type, int hue, int number, AffixType affixType, string affix, + string args, bool noLineOfSight) + { + if (m_Map != null) + { + Packet p = Packet.Acquire(new MessageLocalizedAffix(Serial, Body, type, hue, 3, number, Name, affixType, + affix, args)); + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state.Mobile.CanSee(this) && (noLineOfSight || state.Mobile.InLOS(this))) + state.Send(p); + + Packet.Release(p); + + eable.Free(); + } + } + + public void PrivateOverheadMessage(MessageType type, int hue, bool ascii, string text, NetState state) + { + if (state == null) + return; + + if (ascii) + state.Send(new AsciiMessage(Serial, Body, type, hue, 3, Name, text)); + else + state.Send(new UnicodeMessage(Serial, Body, type, hue, 3, m_Language, Name, text)); + } + + public void PrivateOverheadMessage(MessageType type, int hue, int number, NetState state) + { + PrivateOverheadMessage(type, hue, number, "", state); + } + + public void PrivateOverheadMessage(MessageType type, int hue, int number, string args, NetState state) + { + if (state == null) + return; + + state.Send(new MessageLocalized(Serial, Body, type, hue, 3, number, Name, args)); + } + + public void LocalOverheadMessage(MessageType type, int hue, bool ascii, string text) + { + NetState ns = m_NetState; + + if (ns != null) + { + if (ascii) + ns.Send(new AsciiMessage(Serial, Body, type, hue, 3, Name, text)); + else + ns.Send(new UnicodeMessage(Serial, Body, type, hue, 3, m_Language, Name, text)); + } + } + + public void LocalOverheadMessage(MessageType type, int hue, int number) + { + LocalOverheadMessage(type, hue, number, ""); + } + + public void LocalOverheadMessage(MessageType type, int hue, int number, string args) + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(new MessageLocalized(Serial, Body, type, hue, 3, number, Name, args)); + } + + public void NonlocalOverheadMessage(MessageType type, int hue, int number) + { + NonlocalOverheadMessage(type, hue, number, ""); + } + + public void NonlocalOverheadMessage(MessageType type, int hue, int number, string args) + { + if (m_Map != null) + { + Packet p = Packet.Acquire(new MessageLocalized(Serial, Body, type, hue, 3, number, Name, args)); + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state != m_NetState && state.Mobile.CanSee(this)) + state.Send(p); + + Packet.Release(p); + + eable.Free(); + } + } + + public void NonlocalOverheadMessage(MessageType type, int hue, bool ascii, string text) + { + if (m_Map != null) + { + Packet p = null; + + if (ascii) + p = new AsciiMessage(Serial, Body, type, hue, 3, Name, text); + else + p = new UnicodeMessage(Serial, Body, type, hue, 3, Language, Name, text); + + p.Acquire(); + + IPooledEnumerable eable = m_Map.GetClientsInRange(m_Location); + + foreach (NetState state in eable) + if (state != m_NetState && state.Mobile.CanSee(this)) + state.Send(p); + + Packet.Release(p); + + eable.Free(); + } + } + + #endregion + + #region SendLocalizedMessage + + public void SendLocalizedMessage(int number) + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(MessageLocalized.InstantiateGeneric(number)); + } + + public void SendLocalizedMessage(int number, string args) + { + SendLocalizedMessage(number, args, 0x3B2); + } + + public void SendLocalizedMessage(int number, string args, int hue) + { + if (hue == 0x3B2 && (args == null || args.Length == 0)) + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(MessageLocalized.InstantiateGeneric(number)); + } + else + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(new MessageLocalized(Serial.MinusOne, -1, MessageType.Regular, hue, 3, number, "System", args)); + } + } + + public void SendLocalizedMessage(int number, bool append, string affix) + { + SendLocalizedMessage(number, append, affix, "", 0x3B2); + } + + public void SendLocalizedMessage(int number, bool append, string affix, string args) + { + SendLocalizedMessage(number, append, affix, args, 0x3B2); + } + + public void SendLocalizedMessage(int number, bool append, string affix, string args, int hue) + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(new MessageLocalizedAffix(Serial.MinusOne, -1, MessageType.Regular, hue, 3, number, "System", + (append ? AffixType.Append : AffixType.Prepend) | AffixType.System, affix, args)); + } + + #endregion + + #region Send[ASCII]Message + + public void SendMessage(string text) + { + SendMessage(0x3B2, text); + } + + public void SendMessage(string format, params object[] args) + { + SendMessage(0x3B2, string.Format(format, args)); + } + + public void SendMessage(int hue, string text) + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(new UnicodeMessage(Serial.MinusOne, -1, MessageType.Regular, hue, 3, "ENU", "System", text)); + } + + public void SendMessage(int hue, string format, params object[] args) + { + SendMessage(hue, string.Format(format, args)); + } + + public void SendAsciiMessage(string text) + { + SendAsciiMessage(0x3B2, text); + } + + public void SendAsciiMessage(string format, params object[] args) + { + SendAsciiMessage(0x3B2, string.Format(format, args)); + } + + public void SendAsciiMessage(int hue, string text) + { + NetState ns = m_NetState; + + if (ns != null) + ns.Send(new AsciiMessage(Serial.MinusOne, -1, MessageType.Regular, hue, 3, "System", text)); + } + + public void SendAsciiMessage(int hue, string format, params object[] args) + { + SendAsciiMessage(hue, string.Format(format, args)); + } + + #endregion + + #region InRange + + public bool InRange(Point2D p, int range) + { + return p.m_X >= m_Location.m_X - range + && p.m_X <= m_Location.m_X + range + && p.m_Y >= m_Location.m_Y - range + && p.m_Y <= m_Location.m_Y + range; + } + + public bool InRange(Point3D p, int range) + { + return p.m_X >= m_Location.m_X - range + && p.m_X <= m_Location.m_X + range + && p.m_Y >= m_Location.m_Y - range + && p.m_Y <= m_Location.m_Y + range; + } + + public bool InRange(IPoint2D p, int range) + { + return p.X >= m_Location.m_X - range + && p.X <= m_Location.m_X + range + && p.Y >= m_Location.m_Y - range + && p.Y <= m_Location.m_Y + range; + } + + #endregion + + #region OnDoubleClick[..] + + /// + /// Overridable. Event invoked when the Mobile is double clicked. By default, this method can either dismount or open the + /// paperdoll. + /// + /// + /// + public virtual void OnDoubleClick(Mobile from) + { + if (this == from && (!DisableDismountInWarmode || !m_Warmode)) + { + IMount mount = Mount; + + if (mount != null) + { + mount.Rider = null; + return; + } + } + + if (CanPaperdollBeOpenedBy(from)) + DisplayPaperdollTo(from); + } + + /// + /// Overridable. Virtual event invoked when the Mobile is double clicked by someone who is over 18 tiles away. + /// + /// + public virtual void OnDoubleClickOutOfRange(Mobile from) + { + } + + /// + /// Overridable. Virtual event invoked when the Mobile is double clicked by someone who can no longer see the Mobile. This may + /// happen, for example, using 'Last Object' after the Mobile has hidden. + /// + /// + public virtual void OnDoubleClickCantSee(Mobile from) + { + } + + /// + /// Overridable. Event invoked when the Mobile is double clicked by someone who is not alive. Similar to + /// , this method will show the paperdoll. It does not, however, provide any dismount + /// functionality. + /// + /// + public virtual void OnDoubleClickDead(Mobile from) + { + if (CanPaperdollBeOpenedBy(from)) + DisplayPaperdollTo(from); + } + + #endregion + + #region Armor + + public Item ShieldArmor => FindItemOnLayer(Layer.TwoHanded); + + public Item NeckArmor => FindItemOnLayer(Layer.Neck); + + public Item HandArmor => FindItemOnLayer(Layer.Gloves); + + public Item HeadArmor => FindItemOnLayer(Layer.Helm); + + public Item ArmsArmor => FindItemOnLayer(Layer.Arms); + + public Item LegsArmor + { + get + { + if (!(FindItemOnLayer(Layer.InnerLegs) is Item ar)) + ar = FindItemOnLayer(Layer.Pants); + + return ar; + } + } + + public Item ChestArmor + { + get + { + if (!(FindItemOnLayer(Layer.InnerTorso) is Item ar)) + ar = FindItemOnLayer(Layer.Shirt); + + return ar; + } + } + + public Item Talisman => FindItemOnLayer(Layer.Talisman); + + #endregion + } +} \ No newline at end of file diff --git a/Server/Movement.cs b/Server/Movement.cs index 8f61dbb51..6544f6767 100644 --- a/Server/Movement.cs +++ b/Server/Movement.cs @@ -20,47 +20,67 @@ namespace Server.Movement { - public static class Movement - { - public static IMovementImpl Impl { get; set; } + public static class Movement + { + public static IMovementImpl Impl{ get; set; } - public static bool CheckMovement( Mobile m, Direction d, out int newZ ) - { - if ( Impl != null ) - return Impl.CheckMovement( m, d, out newZ ); + public static bool CheckMovement(Mobile m, Direction d, out int newZ) + { + if (Impl != null) + return Impl.CheckMovement(m, d, out newZ); - newZ = m.Z; - return false; - } + newZ = m.Z; + return false; + } - public static bool CheckMovement( Mobile m, Map map, Point3D loc, Direction d, out int newZ ) - { - if ( Impl != null ) - return Impl.CheckMovement( m, map, loc, d, out newZ ); + public static bool CheckMovement(Mobile m, Map map, Point3D loc, Direction d, out int newZ) + { + if (Impl != null) + return Impl.CheckMovement(m, map, loc, d, out newZ); - newZ = m.Z; - return false; - } + newZ = m.Z; + return false; + } - public static void Offset( Direction d, ref int x, ref int y ) - { - switch ( d & Direction.Mask ) - { - case Direction.North: --y; break; - case Direction.South: ++y; break; - case Direction.West: --x; break; - case Direction.East: ++x; break; - case Direction.Right: ++x; --y; break; - case Direction.Left: --x; ++y; break; - case Direction.Down: ++x; ++y; break; - case Direction.Up: --x; --y; break; - } - } - } + public static void Offset(Direction d, ref int x, ref int y) + { + switch (d & Direction.Mask) + { + case Direction.North: + --y; + break; + case Direction.South: + ++y; + break; + case Direction.West: + --x; + break; + case Direction.East: + ++x; + break; + case Direction.Right: + ++x; + --y; + break; + case Direction.Left: + --x; + ++y; + break; + case Direction.Down: + ++x; + ++y; + break; + case Direction.Up: + --x; + --y; + break; + } + } + } - public interface IMovementImpl - { - bool CheckMovement( Mobile m, Direction d, out int newZ ); - bool CheckMovement( Mobile m, Map map, Point3D loc, Direction d, out int newZ ); - } + public interface IMovementImpl + { + bool CheckMovement(Mobile m, Direction d, out int newZ); + bool CheckMovement(Mobile m, Map map, Point3D loc, Direction d, out int newZ); + } } \ No newline at end of file diff --git a/Server/MultiData.cs b/Server/MultiData.cs index e91a75e62..6015f8813 100644 --- a/Server/MultiData.cs +++ b/Server/MultiData.cs @@ -23,567 +23,561 @@ using System.IO; namespace Server { - public static class MultiData - { - private static MultiComponentList[] m_Components; - - private static FileStream m_Index, m_Stream; - private static BinaryReader m_IndexReader, m_StreamReader; - - public static MultiComponentList GetComponents( int multiID ) - { - MultiComponentList mcl; - - if ( multiID >= 0 && multiID < m_Components.Length ) - { - mcl = m_Components[multiID]; - - if ( mcl == null ) - m_Components[multiID] = mcl = Load( multiID ); - } - else - { - mcl = MultiComponentList.Empty; - } - - return mcl; - } - - public static MultiComponentList Load( int multiID ) - { - try - { - m_IndexReader.BaseStream.Seek( multiID * 12, SeekOrigin.Begin ); - - int lookup = m_IndexReader.ReadInt32(); - int length = m_IndexReader.ReadInt32(); - - if ( lookup < 0 || length <= 0 ) - return MultiComponentList.Empty; - - m_StreamReader.BaseStream.Seek( lookup, SeekOrigin.Begin ); - - return new MultiComponentList( m_StreamReader, length / ( MultiComponentList.PostHSFormat ? 16 : 12 ) ); - } - catch - { - return MultiComponentList.Empty; - } - } - - static MultiData() - { - string idxPath = Core.FindDataFile( "multi.idx" ); - string mulPath = Core.FindDataFile( "multi.mul" ); - - if ( File.Exists( idxPath ) && File.Exists( mulPath ) ) - { - m_Index = new FileStream( idxPath, FileMode.Open, FileAccess.Read, FileShare.Read ); - m_IndexReader = new BinaryReader( m_Index ); - - m_Stream = new FileStream( mulPath, FileMode.Open, FileAccess.Read, FileShare.Read ); - m_StreamReader = new BinaryReader( m_Stream ); - - m_Components = new MultiComponentList[(int)(m_Index.Length / 12)]; - - string vdPath = Core.FindDataFile( "verdata.mul" ); - - if ( File.Exists( vdPath ) ) - { - using ( FileStream fs = new FileStream( vdPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - BinaryReader bin = new BinaryReader( fs ); + public static class MultiData + { + private static MultiComponentList[] m_Components; + + private static FileStream m_Index, m_Stream; + private static BinaryReader m_IndexReader, m_StreamReader; + + static MultiData() + { + string idxPath = Core.FindDataFile("multi.idx"); + string mulPath = Core.FindDataFile("multi.mul"); + + if (File.Exists(idxPath) && File.Exists(mulPath)) + { + m_Index = new FileStream(idxPath, FileMode.Open, FileAccess.Read, FileShare.Read); + m_IndexReader = new BinaryReader(m_Index); + + m_Stream = new FileStream(mulPath, FileMode.Open, FileAccess.Read, FileShare.Read); + m_StreamReader = new BinaryReader(m_Stream); + + m_Components = new MultiComponentList[(int)(m_Index.Length / 12)]; + + string vdPath = Core.FindDataFile("verdata.mul"); + + if (File.Exists(vdPath)) + using (FileStream fs = new FileStream(vdPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader bin = new BinaryReader(fs); + + int count = bin.ReadInt32(); + + for (int i = 0; i < count; ++i) + { + int file = bin.ReadInt32(); + int index = bin.ReadInt32(); + int lookup = bin.ReadInt32(); + int length = bin.ReadInt32(); + int extra = bin.ReadInt32(); + + if (file == 14 && index >= 0 && index < m_Components.Length && lookup >= 0 && length > 0) + { + bin.BaseStream.Seek(lookup, SeekOrigin.Begin); + + m_Components[index] = new MultiComponentList(bin, length / 12); + + bin.BaseStream.Seek(24 + i * 20, SeekOrigin.Begin); + } + } + + bin.Close(); + } + } + else + { + Console.WriteLine("Warning: Multi data files not found"); + + m_Components = new MultiComponentList[0]; + } + } + + public static MultiComponentList GetComponents(int multiID) + { + MultiComponentList mcl; + + if (multiID >= 0 && multiID < m_Components.Length) + { + mcl = m_Components[multiID]; + + if (mcl == null) + m_Components[multiID] = mcl = Load(multiID); + } + else + { + mcl = MultiComponentList.Empty; + } + + return mcl; + } + + public static MultiComponentList Load(int multiID) + { + try + { + m_IndexReader.BaseStream.Seek(multiID * 12, SeekOrigin.Begin); + + int lookup = m_IndexReader.ReadInt32(); + int length = m_IndexReader.ReadInt32(); + + if (lookup < 0 || length <= 0) + return MultiComponentList.Empty; + + m_StreamReader.BaseStream.Seek(lookup, SeekOrigin.Begin); + + return new MultiComponentList(m_StreamReader, length / (MultiComponentList.PostHSFormat ? 16 : 12)); + } + catch + { + return MultiComponentList.Empty; + } + } + } + + public struct MultiTileEntry + { + public ushort m_ItemID; + public short m_OffsetX, m_OffsetY, m_OffsetZ; + public int m_Flags; + + public MultiTileEntry(ushort itemID, short xOffset, short yOffset, short zOffset, int flags) + { + m_ItemID = itemID; + m_OffsetX = xOffset; + m_OffsetY = yOffset; + m_OffsetZ = zOffset; + m_Flags = flags; + } + } + + public sealed class MultiComponentList + { + public static readonly MultiComponentList Empty = new MultiComponentList(); + + private Point2D m_Min, m_Max; + + public MultiComponentList(MultiComponentList toCopy) + { + m_Min = toCopy.m_Min; + m_Max = toCopy.m_Max; + + Center = toCopy.Center; + + Width = toCopy.Width; + Height = toCopy.Height; + + Tiles = new StaticTile[Width][][]; + + for (int x = 0; x < Width; ++x) + { + Tiles[x] = new StaticTile[Height][]; + + for (int y = 0; y < Height; ++y) + { + Tiles[x][y] = new StaticTile[toCopy.Tiles[x][y].Length]; + + for (int i = 0; i < Tiles[x][y].Length; ++i) + Tiles[x][y][i] = toCopy.Tiles[x][y][i]; + } + } + + List = new MultiTileEntry[toCopy.List.Length]; + + for (int i = 0; i < List.Length; ++i) + List[i] = toCopy.List[i]; + } + + public MultiComponentList(GenericReader reader) + { + int version = reader.ReadInt(); + + m_Min = reader.ReadPoint2D(); + m_Max = reader.ReadPoint2D(); + Center = reader.ReadPoint2D(); + Width = reader.ReadInt(); + Height = reader.ReadInt(); + + int length = reader.ReadInt(); + + MultiTileEntry[] allTiles = List = new MultiTileEntry[length]; + + if (version == 0) + for (int i = 0; i < length; ++i) + { + int id = reader.ReadShort(); + if (id >= 0x4000) + id -= 0x4000; + + allTiles[i].m_ItemID = (ushort)id; + allTiles[i].m_OffsetX = reader.ReadShort(); + allTiles[i].m_OffsetY = reader.ReadShort(); + allTiles[i].m_OffsetZ = reader.ReadShort(); + allTiles[i].m_Flags = reader.ReadInt(); + } + else + for (int i = 0; i < length; ++i) + { + allTiles[i].m_ItemID = reader.ReadUShort(); + allTiles[i].m_OffsetX = reader.ReadShort(); + allTiles[i].m_OffsetY = reader.ReadShort(); + allTiles[i].m_OffsetZ = reader.ReadShort(); + allTiles[i].m_Flags = reader.ReadInt(); + } + + TileList[][] tiles = new TileList[Width][]; + Tiles = new StaticTile[Width][][]; + + for (int x = 0; x < Width; ++x) + { + tiles[x] = new TileList[Height]; + Tiles[x] = new StaticTile[Height][]; + + for (int y = 0; y < Height; ++y) + tiles[x][y] = new TileList(); + } + + for (int i = 0; i < allTiles.Length; ++i) + if (i == 0 || allTiles[i].m_Flags != 0) + { + int xOffset = allTiles[i].m_OffsetX + Center.m_X; + int yOffset = allTiles[i].m_OffsetY + Center.m_Y; + + tiles[xOffset][yOffset].Add(allTiles[i].m_ItemID, (sbyte)allTiles[i].m_OffsetZ); + } + + for (int x = 0; x < Width; ++x) + for (int y = 0; y < Height; ++y) + Tiles[x][y] = tiles[x][y].ToArray(); + } - int count = bin.ReadInt32(); + public MultiComponentList(BinaryReader reader, int count) + { + MultiTileEntry[] allTiles = List = new MultiTileEntry[count]; - for ( int i = 0; i < count; ++i ) - { - int file = bin.ReadInt32(); - int index = bin.ReadInt32(); - int lookup = bin.ReadInt32(); - int length = bin.ReadInt32(); - int extra = bin.ReadInt32(); + for (int i = 0; i < count; ++i) + { + allTiles[i].m_ItemID = reader.ReadUInt16(); + allTiles[i].m_OffsetX = reader.ReadInt16(); + allTiles[i].m_OffsetY = reader.ReadInt16(); + allTiles[i].m_OffsetZ = reader.ReadInt16(); + allTiles[i].m_Flags = reader.ReadInt32(); - if ( file == 14 && index >= 0 && index < m_Components.Length && lookup >= 0 && length > 0 ) - { - bin.BaseStream.Seek( lookup, SeekOrigin.Begin ); + if (PostHSFormat) + reader.ReadInt32(); // ?? - m_Components[index] = new MultiComponentList( bin, length / 12 ); + MultiTileEntry e = allTiles[i]; - bin.BaseStream.Seek( 24 + (i * 20), SeekOrigin.Begin ); - } - } + if (i == 0 || e.m_Flags != 0) + { + if (e.m_OffsetX < m_Min.m_X) + m_Min.m_X = e.m_OffsetX; - bin.Close(); - } - } - } - else - { - Console.WriteLine( "Warning: Multi data files not found" ); + if (e.m_OffsetY < m_Min.m_Y) + m_Min.m_Y = e.m_OffsetY; - m_Components = new MultiComponentList[0]; - } - } - } + if (e.m_OffsetX > m_Max.m_X) + m_Max.m_X = e.m_OffsetX; - public struct MultiTileEntry - { - public ushort m_ItemID; - public short m_OffsetX, m_OffsetY, m_OffsetZ; - public int m_Flags; + if (e.m_OffsetY > m_Max.m_Y) + m_Max.m_Y = e.m_OffsetY; + } + } - public MultiTileEntry( ushort itemID, short xOffset, short yOffset, short zOffset, int flags ) - { - m_ItemID = itemID; - m_OffsetX = xOffset; - m_OffsetY = yOffset; - m_OffsetZ = zOffset; - m_Flags = flags; - } - } + Center = new Point2D(-m_Min.m_X, -m_Min.m_Y); + Width = m_Max.m_X - m_Min.m_X + 1; + Height = m_Max.m_Y - m_Min.m_Y + 1; - public sealed class MultiComponentList - { - public static bool PostHSFormat { get; set; } + TileList[][] tiles = new TileList[Width][]; + Tiles = new StaticTile[Width][][]; - private Point2D m_Min, m_Max; + for (int x = 0; x < Width; ++x) + { + tiles[x] = new TileList[Height]; + Tiles[x] = new StaticTile[Height][]; - public static readonly MultiComponentList Empty = new MultiComponentList(); + for (int y = 0; y < Height; ++y) + tiles[x][y] = new TileList(); + } - public Point2D Min => m_Min; - public Point2D Max => m_Max; + for (int i = 0; i < allTiles.Length; ++i) + if (i == 0 || allTiles[i].m_Flags != 0) + { + int xOffset = allTiles[i].m_OffsetX + Center.m_X; + int yOffset = allTiles[i].m_OffsetY + Center.m_Y; - public Point2D Center { get; } + tiles[xOffset][yOffset].Add(allTiles[i].m_ItemID, (sbyte)allTiles[i].m_OffsetZ); + } - public int Width { get; private set; } + for (int x = 0; x < Width; ++x) + for (int y = 0; y < Height; ++y) + Tiles[x][y] = tiles[x][y].ToArray(); + } - public int Height { get; private set; } + private MultiComponentList() + { + Tiles = new StaticTile[0][][]; + List = new MultiTileEntry[0]; + } - public StaticTile[][][] Tiles { get; private set; } + public static bool PostHSFormat{ get; set; } - public MultiTileEntry[] List { get; private set; } + public Point2D Min => m_Min; + public Point2D Max => m_Max; - public void Add( int itemID, int x, int y, int z ) - { - int vx = x + Center.m_X; - int vy = y + Center.m_Y; + public Point2D Center{ get; } - if ( vx >= 0 && vx < Width && vy >= 0 && vy < Height ) - { - StaticTile[] oldTiles = Tiles[vx][vy]; + public int Width{ get; private set; } - for ( int i = oldTiles.Length - 1; i >= 0; --i ) - { - ItemData data = TileData.ItemTable[itemID & TileData.MaxItemValue]; + public int Height{ get; private set; } - if ( oldTiles[i].Z == z && (oldTiles[i].Height > 0 == data.Height > 0 ) ) - { - bool newIsRoof = ( data.Flags & TileFlag.Roof) != 0; - bool oldIsRoof = (TileData.ItemTable[oldTiles[i].ID & TileData.MaxItemValue].Flags & TileFlag.Roof ) != 0; + public StaticTile[][][] Tiles{ get; private set; } - if ( newIsRoof == oldIsRoof ) - Remove( oldTiles[i].ID, x, y, z ); - } - } + public MultiTileEntry[] List{ get; private set; } - oldTiles = Tiles[vx][vy]; + public void Add(int itemID, int x, int y, int z) + { + int vx = x + Center.m_X; + int vy = y + Center.m_Y; - StaticTile[] newTiles = new StaticTile[oldTiles.Length + 1]; + if (vx >= 0 && vx < Width && vy >= 0 && vy < Height) + { + StaticTile[] oldTiles = Tiles[vx][vy]; - for ( int i = 0; i < oldTiles.Length; ++i ) - newTiles[i] = oldTiles[i]; + for (int i = oldTiles.Length - 1; i >= 0; --i) + { + ItemData data = TileData.ItemTable[itemID & TileData.MaxItemValue]; - newTiles[oldTiles.Length] = new StaticTile( (ushort)itemID, (sbyte)z ); + if (oldTiles[i].Z == z && oldTiles[i].Height > 0 == data.Height > 0) + { + bool newIsRoof = (data.Flags & TileFlag.Roof) != 0; + bool oldIsRoof = + (TileData.ItemTable[oldTiles[i].ID & TileData.MaxItemValue].Flags & TileFlag.Roof) != 0; - Tiles[vx][vy] = newTiles; + if (newIsRoof == oldIsRoof) + Remove(oldTiles[i].ID, x, y, z); + } + } - MultiTileEntry[] oldList = List; - MultiTileEntry[] newList = new MultiTileEntry[oldList.Length + 1]; + oldTiles = Tiles[vx][vy]; - for ( int i = 0; i < oldList.Length; ++i ) - newList[i] = oldList[i]; + StaticTile[] newTiles = new StaticTile[oldTiles.Length + 1]; - newList[oldList.Length] = new MultiTileEntry( (ushort)itemID, (short)x, (short)y, (short)z, 1 ); + for (int i = 0; i < oldTiles.Length; ++i) + newTiles[i] = oldTiles[i]; - List = newList; + newTiles[oldTiles.Length] = new StaticTile((ushort)itemID, (sbyte)z); - if ( x < m_Min.m_X ) - m_Min.m_X = x; + Tiles[vx][vy] = newTiles; - if ( y < m_Min.m_Y ) - m_Min.m_Y = y; + MultiTileEntry[] oldList = List; + MultiTileEntry[] newList = new MultiTileEntry[oldList.Length + 1]; - if ( x > m_Max.m_X ) - m_Max.m_X = x; + for (int i = 0; i < oldList.Length; ++i) + newList[i] = oldList[i]; - if ( y > m_Max.m_Y ) - m_Max.m_Y = y; - } - } + newList[oldList.Length] = new MultiTileEntry((ushort)itemID, (short)x, (short)y, (short)z, 1); - public void RemoveXYZH( int x, int y, int z, int minHeight ) - { - int vx = x + Center.m_X; - int vy = y + Center.m_Y; + List = newList; - if ( vx >= 0 && vx < Width && vy >= 0 && vy < Height ) - { - StaticTile[] oldTiles = Tiles[vx][vy]; + if (x < m_Min.m_X) + m_Min.m_X = x; - for ( int i = 0; i < oldTiles.Length; ++i ) - { - StaticTile tile = oldTiles[i]; + if (y < m_Min.m_Y) + m_Min.m_Y = y; - if ( tile.Z == z && tile.Height >= minHeight ) - { - StaticTile[] newTiles = new StaticTile[oldTiles.Length - 1]; + if (x > m_Max.m_X) + m_Max.m_X = x; - for ( int j = 0; j < i; ++j ) - newTiles[j] = oldTiles[j]; + if (y > m_Max.m_Y) + m_Max.m_Y = y; + } + } - for ( int j = i + 1; j < oldTiles.Length; ++j ) - newTiles[j - 1] = oldTiles[j]; + public void RemoveXYZH(int x, int y, int z, int minHeight) + { + int vx = x + Center.m_X; + int vy = y + Center.m_Y; - Tiles[vx][vy] = newTiles; + if (vx >= 0 && vx < Width && vy >= 0 && vy < Height) + { + StaticTile[] oldTiles = Tiles[vx][vy]; - break; - } - } + for (int i = 0; i < oldTiles.Length; ++i) + { + StaticTile tile = oldTiles[i]; - MultiTileEntry[] oldList = List; + if (tile.Z == z && tile.Height >= minHeight) + { + StaticTile[] newTiles = new StaticTile[oldTiles.Length - 1]; - for ( int i = 0; i < oldList.Length; ++i ) - { - MultiTileEntry tile = oldList[i]; + for (int j = 0; j < i; ++j) + newTiles[j] = oldTiles[j]; - if ( tile.m_OffsetX == (short)x && tile.m_OffsetY == (short)y && tile.m_OffsetZ == (short)z && TileData.ItemTable[tile.m_ItemID & TileData.MaxItemValue].Height >= minHeight ) - { - MultiTileEntry[] newList = new MultiTileEntry[oldList.Length - 1]; + for (int j = i + 1; j < oldTiles.Length; ++j) + newTiles[j - 1] = oldTiles[j]; - for ( int j = 0; j < i; ++j ) - newList[j] = oldList[j]; + Tiles[vx][vy] = newTiles; - for ( int j = i + 1; j < oldList.Length; ++j ) - newList[j - 1] = oldList[j]; + break; + } + } - List = newList; + MultiTileEntry[] oldList = List; - break; - } - } - } - } + for (int i = 0; i < oldList.Length; ++i) + { + MultiTileEntry tile = oldList[i]; - public void Remove( int itemID, int x, int y, int z ) - { - int vx = x + Center.m_X; - int vy = y + Center.m_Y; + if (tile.m_OffsetX == (short)x && tile.m_OffsetY == (short)y && tile.m_OffsetZ == (short)z && + TileData.ItemTable[tile.m_ItemID & TileData.MaxItemValue].Height >= minHeight) + { + MultiTileEntry[] newList = new MultiTileEntry[oldList.Length - 1]; - if ( vx >= 0 && vx < Width && vy >= 0 && vy < Height ) - { - StaticTile[] oldTiles = Tiles[vx][vy]; + for (int j = 0; j < i; ++j) + newList[j] = oldList[j]; - for ( int i = 0; i < oldTiles.Length; ++i ) - { - StaticTile tile = oldTiles[i]; + for (int j = i + 1; j < oldList.Length; ++j) + newList[j - 1] = oldList[j]; - if ( tile.ID == itemID && tile.Z == z ) - { - StaticTile[] newTiles = new StaticTile[oldTiles.Length - 1]; + List = newList; - for ( int j = 0; j < i; ++j ) - newTiles[j] = oldTiles[j]; + break; + } + } + } + } - for ( int j = i + 1; j < oldTiles.Length; ++j ) - newTiles[j - 1] = oldTiles[j]; + public void Remove(int itemID, int x, int y, int z) + { + int vx = x + Center.m_X; + int vy = y + Center.m_Y; - Tiles[vx][vy] = newTiles; + if (vx >= 0 && vx < Width && vy >= 0 && vy < Height) + { + StaticTile[] oldTiles = Tiles[vx][vy]; - break; - } - } + for (int i = 0; i < oldTiles.Length; ++i) + { + StaticTile tile = oldTiles[i]; - MultiTileEntry[] oldList = List; + if (tile.ID == itemID && tile.Z == z) + { + StaticTile[] newTiles = new StaticTile[oldTiles.Length - 1]; - for ( int i = 0; i < oldList.Length; ++i ) - { - MultiTileEntry tile = oldList[i]; + for (int j = 0; j < i; ++j) + newTiles[j] = oldTiles[j]; - if ( tile.m_ItemID == itemID && tile.m_OffsetX == (short)x && tile.m_OffsetY == (short)y && tile.m_OffsetZ == (short)z ) - { - MultiTileEntry[] newList = new MultiTileEntry[oldList.Length - 1]; + for (int j = i + 1; j < oldTiles.Length; ++j) + newTiles[j - 1] = oldTiles[j]; - for ( int j = 0; j < i; ++j ) - newList[j] = oldList[j]; + Tiles[vx][vy] = newTiles; - for ( int j = i + 1; j < oldList.Length; ++j ) - newList[j - 1] = oldList[j]; + break; + } + } - List = newList; + MultiTileEntry[] oldList = List; - break; - } - } - } - } + for (int i = 0; i < oldList.Length; ++i) + { + MultiTileEntry tile = oldList[i]; - public void Resize( int newWidth, int newHeight ) - { - int oldWidth = Width, oldHeight = Height; - StaticTile[][][] oldTiles = Tiles; + if (tile.m_ItemID == itemID && tile.m_OffsetX == (short)x && tile.m_OffsetY == (short)y && + tile.m_OffsetZ == (short)z) + { + MultiTileEntry[] newList = new MultiTileEntry[oldList.Length - 1]; - int totalLength = 0; + for (int j = 0; j < i; ++j) + newList[j] = oldList[j]; - StaticTile[][][] newTiles = new StaticTile[newWidth][][]; + for (int j = i + 1; j < oldList.Length; ++j) + newList[j - 1] = oldList[j]; - for ( int x = 0; x < newWidth; ++x ) - { - newTiles[x] = new StaticTile[newHeight][]; + List = newList; - for ( int y = 0; y < newHeight; ++y ) - { - if ( x < oldWidth && y < oldHeight ) - newTiles[x][y] = oldTiles[x][y]; - else - newTiles[x][y] = new StaticTile[0]; + break; + } + } + } + } - totalLength += newTiles[x][y].Length; - } - } + public void Resize(int newWidth, int newHeight) + { + int oldWidth = Width, oldHeight = Height; + StaticTile[][][] oldTiles = Tiles; - Tiles = newTiles; - List = new MultiTileEntry[totalLength]; - Width = newWidth; - Height = newHeight; + int totalLength = 0; - m_Min = Point2D.Zero; - m_Max = Point2D.Zero; + StaticTile[][][] newTiles = new StaticTile[newWidth][][]; - int index = 0; + for (int x = 0; x < newWidth; ++x) + { + newTiles[x] = new StaticTile[newHeight][]; - for ( int x = 0; x < newWidth; ++x ) - { - for ( int y = 0; y < newHeight; ++y ) - { - StaticTile[] tiles = newTiles[x][y]; + for (int y = 0; y < newHeight; ++y) + { + if (x < oldWidth && y < oldHeight) + newTiles[x][y] = oldTiles[x][y]; + else + newTiles[x][y] = new StaticTile[0]; - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; + totalLength += newTiles[x][y].Length; + } + } - int vx = x - Center.X; - int vy = y - Center.Y; + Tiles = newTiles; + List = new MultiTileEntry[totalLength]; + Width = newWidth; + Height = newHeight; - if ( vx < m_Min.m_X ) - m_Min.m_X = vx; + m_Min = Point2D.Zero; + m_Max = Point2D.Zero; - if ( vy < m_Min.m_Y ) - m_Min.m_Y = vy; + int index = 0; - if ( vx > m_Max.m_X ) - m_Max.m_X = vx; + for (int x = 0; x < newWidth; ++x) + for (int y = 0; y < newHeight; ++y) + { + StaticTile[] tiles = newTiles[x][y]; - if ( vy > m_Max.m_Y ) - m_Max.m_Y = vy; + for (int i = 0; i < tiles.Length; ++i) + { + StaticTile tile = tiles[i]; - List[index++] = new MultiTileEntry( (ushort)tile.ID, (short)vx, (short)vy, (short)tile.Z, 1 ); - } - } - } - } + int vx = x - Center.X; + int vy = y - Center.Y; - public MultiComponentList( MultiComponentList toCopy ) - { - m_Min = toCopy.m_Min; - m_Max = toCopy.m_Max; + if (vx < m_Min.m_X) + m_Min.m_X = vx; - Center = toCopy.Center; + if (vy < m_Min.m_Y) + m_Min.m_Y = vy; - Width = toCopy.Width; - Height = toCopy.Height; - - Tiles = new StaticTile[Width][][]; - - for ( int x = 0; x < Width; ++x ) - { - Tiles[x] = new StaticTile[Height][]; - - for ( int y = 0; y < Height; ++y ) - { - Tiles[x][y] = new StaticTile[toCopy.Tiles[x][y].Length]; - - for ( int i = 0; i < Tiles[x][y].Length; ++i ) - Tiles[x][y][i] = toCopy.Tiles[x][y][i]; - } - } - - List = new MultiTileEntry[toCopy.List.Length]; - - for ( int i = 0; i < List.Length; ++i ) - List[i] = toCopy.List[i]; - } - - public void Serialize( GenericWriter writer ) - { - writer.Write( (int) 1 ); // version; - - writer.Write( m_Min ); - writer.Write( m_Max ); - writer.Write( Center ); - - writer.Write( (int) Width ); - writer.Write( (int) Height ); - - writer.Write( (int) List.Length ); - - for ( int i = 0; i < List.Length; ++i ) - { - MultiTileEntry ent = List[i]; - - writer.Write( (ushort) ent.m_ItemID ); - writer.Write( (short) ent.m_OffsetX ); - writer.Write( (short) ent.m_OffsetY ); - writer.Write( (short) ent.m_OffsetZ ); - writer.Write( (int) ent.m_Flags ); - } - } - - public MultiComponentList( GenericReader reader ) - { - int version = reader.ReadInt(); - - m_Min = reader.ReadPoint2D(); - m_Max = reader.ReadPoint2D(); - Center = reader.ReadPoint2D(); - Width = reader.ReadInt(); - Height = reader.ReadInt(); - - int length = reader.ReadInt(); - - MultiTileEntry[] allTiles = List = new MultiTileEntry[length]; - - if ( version == 0 ) { - for ( int i = 0; i < length; ++i ) - { - int id = reader.ReadShort(); - if ( id >= 0x4000 ) - id -= 0x4000; - - allTiles[i].m_ItemID = (ushort)id; - allTiles[i].m_OffsetX = reader.ReadShort(); - allTiles[i].m_OffsetY = reader.ReadShort(); - allTiles[i].m_OffsetZ = reader.ReadShort(); - allTiles[i].m_Flags = reader.ReadInt(); - } - } else { - for ( int i = 0; i < length; ++i ) - { - allTiles[i].m_ItemID = reader.ReadUShort(); - allTiles[i].m_OffsetX = reader.ReadShort(); - allTiles[i].m_OffsetY = reader.ReadShort(); - allTiles[i].m_OffsetZ = reader.ReadShort(); - allTiles[i].m_Flags = reader.ReadInt(); - } - } - - TileList[][] tiles = new TileList[Width][]; - Tiles = new StaticTile[Width][][]; - - for ( int x = 0; x < Width; ++x ) - { - tiles[x] = new TileList[Height]; - Tiles[x] = new StaticTile[Height][]; - - for ( int y = 0; y < Height; ++y ) - tiles[x][y] = new TileList(); - } - - for ( int i = 0; i < allTiles.Length; ++i ) - { - if ( i == 0 || allTiles[i].m_Flags != 0 ) - { - int xOffset = allTiles[i].m_OffsetX + Center.m_X; - int yOffset = allTiles[i].m_OffsetY + Center.m_Y; - - tiles[xOffset][yOffset].Add( (ushort)allTiles[i].m_ItemID, (sbyte)allTiles[i].m_OffsetZ ); - } - } - - for ( int x = 0; x < Width; ++x ) - for ( int y = 0; y < Height; ++y ) - Tiles[x][y] = tiles[x][y].ToArray(); - } - - public MultiComponentList( BinaryReader reader, int count ) - { - MultiTileEntry[] allTiles = List = new MultiTileEntry[count]; - - for ( int i = 0; i < count; ++i ) - { - allTiles[i].m_ItemID = reader.ReadUInt16(); - allTiles[i].m_OffsetX = reader.ReadInt16(); - allTiles[i].m_OffsetY = reader.ReadInt16(); - allTiles[i].m_OffsetZ = reader.ReadInt16(); - allTiles[i].m_Flags = reader.ReadInt32(); - - if ( PostHSFormat ) - reader.ReadInt32(); // ?? - - MultiTileEntry e = allTiles[i]; - - if ( i == 0 || e.m_Flags != 0 ) - { - if ( e.m_OffsetX < m_Min.m_X ) - m_Min.m_X = e.m_OffsetX; - - if ( e.m_OffsetY < m_Min.m_Y ) - m_Min.m_Y = e.m_OffsetY; - - if ( e.m_OffsetX > m_Max.m_X ) - m_Max.m_X = e.m_OffsetX; - - if ( e.m_OffsetY > m_Max.m_Y ) - m_Max.m_Y = e.m_OffsetY; - } - } - - Center = new Point2D( -m_Min.m_X, -m_Min.m_Y ); - Width = (m_Max.m_X - m_Min.m_X) + 1; - Height = (m_Max.m_Y - m_Min.m_Y) + 1; - - TileList[][] tiles = new TileList[Width][]; - Tiles = new StaticTile[Width][][]; - - for ( int x = 0; x < Width; ++x ) - { - tiles[x] = new TileList[Height]; - Tiles[x] = new StaticTile[Height][]; - - for ( int y = 0; y < Height; ++y ) - tiles[x][y] = new TileList(); - } - - for ( int i = 0; i < allTiles.Length; ++i ) - { - if ( i == 0 || allTiles[i].m_Flags != 0 ) - { - int xOffset = allTiles[i].m_OffsetX + Center.m_X; - int yOffset = allTiles[i].m_OffsetY + Center.m_Y; - - tiles[xOffset][yOffset].Add( (ushort)allTiles[i].m_ItemID, (sbyte)allTiles[i].m_OffsetZ ); - } - } - - for ( int x = 0; x < Width; ++x ) - for ( int y = 0; y < Height; ++y ) - Tiles[x][y] = tiles[x][y].ToArray(); - } - - private MultiComponentList() - { - Tiles = new StaticTile[0][][]; - List = new MultiTileEntry[0]; - } - } + if (vx > m_Max.m_X) + m_Max.m_X = vx; + + if (vy > m_Max.m_Y) + m_Max.m_Y = vy; + + List[index++] = new MultiTileEntry((ushort)tile.ID, (short)vx, (short)vy, (short)tile.Z, 1); + } + } + } + + public void Serialize(GenericWriter writer) + { + writer.Write(1); // version; + + writer.Write(m_Min); + writer.Write(m_Max); + writer.Write(Center); + + writer.Write(Width); + writer.Write(Height); + + writer.Write(List.Length); + + for (int i = 0; i < List.Length; ++i) + { + MultiTileEntry ent = List[i]; + + writer.Write(ent.m_ItemID); + writer.Write(ent.m_OffsetX); + writer.Write(ent.m_OffsetY); + writer.Write(ent.m_OffsetZ); + writer.Write(ent.m_Flags); + } + } + } } \ No newline at end of file diff --git a/Server/NativeReader.cs b/Server/NativeReader.cs index dbffdde77..788d9d951 100644 --- a/Server/NativeReader.cs +++ b/Server/NativeReader.cs @@ -22,57 +22,62 @@ using System; using System.Runtime.InteropServices; using System.Threading; -namespace Server { - public static class NativeReader { +namespace Server +{ + public static class NativeReader + { + private static readonly INativeReader m_NativeReader; - private static readonly INativeReader m_NativeReader; + static NativeReader() + { + if (Core.Unix) + m_NativeReader = new NativeReaderUnix(); + else + m_NativeReader = new NativeReaderWin32(); + } - static NativeReader() { - if ( Core.Unix ) - m_NativeReader = new NativeReaderUnix(); - else - m_NativeReader = new NativeReaderWin32(); - } + public static unsafe void Read(IntPtr ptr, void* buffer, int length) + { + m_NativeReader.Read(ptr, buffer, length); + } + } - public static unsafe void Read( IntPtr ptr, void *buffer, int length ) { - m_NativeReader.Read( ptr, buffer, length ); - } - } + public interface INativeReader + { + unsafe void Read(IntPtr ptr, void* buffer, int length); + } - public interface INativeReader { - unsafe void Read( IntPtr ptr, void *buffer, int length ); - } + public sealed class NativeReaderWin32 : INativeReader + { + public unsafe void Read(IntPtr ptr, void* buffer, int length) + { + //UnsafeNativeMethods._lread( ptr, buffer, length ); + uint lpNumberOfBytesRead = 0; + UnsafeNativeMethods.ReadFile(ptr, buffer, (uint)length, ref lpNumberOfBytesRead, null); + } - public sealed class NativeReaderWin32 : INativeReader { - internal class UnsafeNativeMethods { - /*[DllImport("kernel32")] - internal unsafe static extern int _lread(IntPtr hFile, void* lpBuffer, int wBytes);*/ + internal class UnsafeNativeMethods + { + /*[DllImport("kernel32")] + internal unsafe static extern int _lread(IntPtr hFile, void* lpBuffer, int wBytes);*/ - [DllImport("kernel32")] - internal unsafe static extern bool ReadFile(IntPtr hFile, void* lpBuffer, uint nNumberOfBytesToRead, ref uint lpNumberOfBytesRead, NativeOverlapped* lpOverlapped); - } + [DllImport("kernel32")] + internal static extern unsafe bool ReadFile(IntPtr hFile, void* lpBuffer, uint nNumberOfBytesToRead, + ref uint lpNumberOfBytesRead, NativeOverlapped* lpOverlapped); + } + } - public NativeReaderWin32() { - } + public sealed class NativeReaderUnix : INativeReader + { + public unsafe void Read(IntPtr ptr, void* buffer, int length) + { + UnsafeNativeMethods.read(ptr, buffer, length); + } - public unsafe void Read( IntPtr ptr, void *buffer, int length ) { - //UnsafeNativeMethods._lread( ptr, buffer, length ); - uint lpNumberOfBytesRead = 0; - UnsafeNativeMethods.ReadFile(ptr, buffer, (uint)length, ref lpNumberOfBytesRead, null); - } - } - - public sealed class NativeReaderUnix : INativeReader { - internal class UnsafeNativeMethods { - [DllImport("libc")] - internal unsafe static extern int read(IntPtr ptr, void* buffer, int length); - } - - public NativeReaderUnix() { - } - - public unsafe void Read( IntPtr ptr, void *buffer, int length ) { - UnsafeNativeMethods.read( ptr, buffer, length ); - } - } + internal class UnsafeNativeMethods + { + [DllImport("libc")] + internal static extern unsafe int read(IntPtr ptr, void* buffer, int length); + } + } } \ No newline at end of file diff --git a/Server/Network/BufferPool.cs b/Server/Network/BufferPool.cs index 3bdc6deda..84157ddcf 100644 --- a/Server/Network/BufferPool.cs +++ b/Server/Network/BufferPool.cs @@ -22,77 +22,85 @@ using System.Collections.Generic; namespace Server.Network { - public class BufferPool - { - public static List Pools { get; set; } = new List(); + public class BufferPool + { + private int m_BufferSize; - private string m_Name; + private Queue m_FreeBuffers; - private int m_InitialCapacity; - private int m_BufferSize; + private int m_InitialCapacity; - private int m_Misses; + private int m_Misses; - private Queue m_FreeBuffers; + private string m_Name; - public void GetInfo( out string name, out int freeCount, out int initialCapacity, out int currentCapacity, out int bufferSize, out int misses ) - { - lock ( this ) - { - name = m_Name; - freeCount = m_FreeBuffers.Count; - initialCapacity = m_InitialCapacity; - currentCapacity = m_InitialCapacity * (1 + m_Misses); - bufferSize = m_BufferSize; - misses = m_Misses; - } - } + public BufferPool(string name, int initialCapacity, int bufferSize) + { + m_Name = name; - public BufferPool( string name, int initialCapacity, int bufferSize ) - { - m_Name = name; + m_InitialCapacity = initialCapacity; + m_BufferSize = bufferSize; - m_InitialCapacity = initialCapacity; - m_BufferSize = bufferSize; + m_FreeBuffers = new Queue(initialCapacity); - m_FreeBuffers = new Queue( initialCapacity ); + for (int i = 0; i < initialCapacity; ++i) + m_FreeBuffers.Enqueue(new byte[bufferSize]); - for ( int i = 0; i < initialCapacity; ++i ) - m_FreeBuffers.Enqueue( new byte[bufferSize] ); + lock (Pools) + { + Pools.Add(this); + } + } - lock ( Pools ) - Pools.Add( this ); - } + public static List Pools{ get; set; } = new List(); - public byte[] AcquireBuffer() - { - lock ( this ) - { - if ( m_FreeBuffers.Count > 0 ) - return m_FreeBuffers.Dequeue(); + public void GetInfo(out string name, out int freeCount, out int initialCapacity, out int currentCapacity, + out int bufferSize, out int misses) + { + lock (this) + { + name = m_Name; + freeCount = m_FreeBuffers.Count; + initialCapacity = m_InitialCapacity; + currentCapacity = m_InitialCapacity * (1 + m_Misses); + bufferSize = m_BufferSize; + misses = m_Misses; + } + } - ++m_Misses; + public byte[] AcquireBuffer() + { + lock (this) + { + if (m_FreeBuffers.Count > 0) + return m_FreeBuffers.Dequeue(); - for ( int i = 0; i < m_InitialCapacity; ++i ) - m_FreeBuffers.Enqueue( new byte[m_BufferSize] ); + ++m_Misses; - return m_FreeBuffers.Dequeue(); - } - } + for (int i = 0; i < m_InitialCapacity; ++i) + m_FreeBuffers.Enqueue(new byte[m_BufferSize]); - public void ReleaseBuffer( byte[] buffer ) - { - if ( buffer == null ) - return; + return m_FreeBuffers.Dequeue(); + } + } - lock ( this ) - m_FreeBuffers.Enqueue( buffer ); - } + public void ReleaseBuffer(byte[] buffer) + { + if (buffer == null) + return; - public void Free() - { - lock ( Pools ) - Pools.Remove( this ); - } - } + lock (this) + { + m_FreeBuffers.Enqueue(buffer); + } + } + + public void Free() + { + lock (Pools) + { + Pools.Remove(this); + } + } + } } \ No newline at end of file diff --git a/Server/Network/ByteQueue.cs b/Server/Network/ByteQueue.cs index 019afb907..b5dae23fb 100644 --- a/Server/Network/ByteQueue.cs +++ b/Server/Network/ByteQueue.cs @@ -22,130 +22,129 @@ using System; namespace Server.Network { - public class ByteQueue - { - private int m_Head; - private int m_Tail; + public class ByteQueue + { + private byte[] m_Buffer; + private int m_Head; + private int m_Tail; - private byte[] m_Buffer; + public ByteQueue() + { + m_Buffer = new byte[2048]; + } - public int Length { get; private set; } + public int Length{ get; private set; } - public ByteQueue() - { - m_Buffer = new byte[2048]; - } + public void Clear() + { + m_Head = 0; + m_Tail = 0; + Length = 0; + } - public void Clear() - { - m_Head = 0; - m_Tail = 0; - Length = 0; - } + private void SetCapacity(int capacity) + { + byte[] newBuffer = new byte[capacity]; - private void SetCapacity( int capacity ) - { - byte[] newBuffer = new byte[capacity]; + if (Length > 0) + { + if (m_Head < m_Tail) + { + Buffer.BlockCopy(m_Buffer, m_Head, newBuffer, 0, Length); + } + else + { + Buffer.BlockCopy(m_Buffer, m_Head, newBuffer, 0, m_Buffer.Length - m_Head); + Buffer.BlockCopy(m_Buffer, 0, newBuffer, m_Buffer.Length - m_Head, m_Tail); + } + } - if ( Length > 0 ) - { - if ( m_Head < m_Tail ) - { - Buffer.BlockCopy( m_Buffer, m_Head, newBuffer, 0, Length ); - } - else - { - Buffer.BlockCopy( m_Buffer, m_Head, newBuffer, 0, m_Buffer.Length - m_Head ); - Buffer.BlockCopy( m_Buffer, 0, newBuffer, m_Buffer.Length - m_Head, m_Tail ); - } - } + m_Head = 0; + m_Tail = Length; + m_Buffer = newBuffer; + } - m_Head = 0; - m_Tail = Length; - m_Buffer = newBuffer; - } + public byte GetPacketID() + { + if (Length >= 1) + return m_Buffer[m_Head]; - public byte GetPacketID() - { - if ( Length >= 1 ) - return m_Buffer[m_Head]; + return 0xFF; + } - return 0xFF; - } + public int GetPacketLength() + { + if (Length >= 3) + return (m_Buffer[(m_Head + 1) % m_Buffer.Length] << 8) | m_Buffer[(m_Head + 2) % m_Buffer.Length]; - public int GetPacketLength() - { - if ( Length >= 3 ) - return (m_Buffer[(m_Head + 1) % m_Buffer.Length] << 8) | m_Buffer[(m_Head + 2) % m_Buffer.Length]; + return 0; + } - return 0; - } + public int Dequeue(byte[] buffer, int offset, int size) + { + if (size > Length) + size = Length; - public int Dequeue( byte[] buffer, int offset, int size ) - { - if ( size > Length ) - size = Length; + if (size == 0) + return 0; - if ( size == 0 ) - return 0; + if (m_Head < m_Tail) + { + Buffer.BlockCopy(m_Buffer, m_Head, buffer, offset, size); + } + else + { + int rightLength = m_Buffer.Length - m_Head; - if ( m_Head < m_Tail ) - { - Buffer.BlockCopy( m_Buffer, m_Head, buffer, offset, size ); - } - else - { - int rightLength = ( m_Buffer.Length - m_Head ); + if (rightLength >= size) + { + Buffer.BlockCopy(m_Buffer, m_Head, buffer, offset, size); + } + else + { + Buffer.BlockCopy(m_Buffer, m_Head, buffer, offset, rightLength); + Buffer.BlockCopy(m_Buffer, 0, buffer, offset + rightLength, size - rightLength); + } + } - if ( rightLength >= size ) - { - Buffer.BlockCopy( m_Buffer, m_Head, buffer, offset, size ); - } - else - { - Buffer.BlockCopy( m_Buffer, m_Head, buffer, offset, rightLength ); - Buffer.BlockCopy( m_Buffer, 0, buffer, offset + rightLength, size - rightLength ); - } - } + m_Head = (m_Head + size) % m_Buffer.Length; + Length -= size; - m_Head = ( m_Head + size ) % m_Buffer.Length; - Length -= size; + if (Length == 0) + { + m_Head = 0; + m_Tail = 0; + } - if ( Length == 0 ) - { - m_Head = 0; - m_Tail = 0; - } + return size; + } - return size; - } + public void Enqueue(byte[] buffer, int offset, int size) + { + if (Length + size > m_Buffer.Length) + SetCapacity((Length + size + 2047) & ~2047); - public void Enqueue( byte[] buffer, int offset, int size ) - { - if ( (Length + size) > m_Buffer.Length ) - SetCapacity( (Length + size + 2047) & ~2047 ); + if (m_Head < m_Tail) + { + int rightLength = m_Buffer.Length - m_Tail; - if ( m_Head < m_Tail ) - { - int rightLength = ( m_Buffer.Length - m_Tail ); + if (rightLength >= size) + { + Buffer.BlockCopy(buffer, offset, m_Buffer, m_Tail, size); + } + else + { + Buffer.BlockCopy(buffer, offset, m_Buffer, m_Tail, rightLength); + Buffer.BlockCopy(buffer, offset + rightLength, m_Buffer, 0, size - rightLength); + } + } + else + { + Buffer.BlockCopy(buffer, offset, m_Buffer, m_Tail, size); + } - if ( rightLength >= size ) - { - Buffer.BlockCopy( buffer, offset, m_Buffer, m_Tail, size ); - } - else - { - Buffer.BlockCopy( buffer, offset, m_Buffer, m_Tail, rightLength ); - Buffer.BlockCopy( buffer, offset + rightLength, m_Buffer, 0, size - rightLength ); - } - } - else - { - Buffer.BlockCopy( buffer, offset, m_Buffer, m_Tail, size ); - } - - m_Tail = ( m_Tail + size ) % m_Buffer.Length; - Length += size; - } - } + m_Tail = (m_Tail + size) % m_Buffer.Length; + Length += size; + } + } } \ No newline at end of file diff --git a/Server/Network/Compression.cs b/Server/Network/Compression.cs index 06893a90b..5d0803004 100644 --- a/Server/Network/Compression.cs +++ b/Server/Network/Compression.cs @@ -21,371 +21,379 @@ using System; using System.Runtime.InteropServices; -namespace Server.Network { - /// - /// Handles outgoing packet compression for the network. - /// - public static class Compression { - private static int[] _huffmanTable = new int[514] - { - 0x2, 0x000, 0x5, 0x01F, 0x6, 0x022, 0x7, 0x034, 0x7, 0x075, 0x6, 0x028, 0x6, 0x03B, 0x7, 0x032, - 0x8, 0x0E0, 0x8, 0x062, 0x7, 0x056, 0x8, 0x079, 0x9, 0x19D, 0x8, 0x097, 0x6, 0x02A, 0x7, 0x057, - 0x8, 0x071, 0x8, 0x05B, 0x9, 0x1CC, 0x8, 0x0A7, 0x7, 0x025, 0x7, 0x04F, 0x8, 0x066, 0x8, 0x07D, - 0x9, 0x191, 0x9, 0x1CE, 0x7, 0x03F, 0x9, 0x090, 0x8, 0x059, 0x8, 0x07B, 0x8, 0x091, 0x8, 0x0C6, - 0x6, 0x02D, 0x9, 0x186, 0x8, 0x06F, 0x9, 0x093, 0xA, 0x1CC, 0x8, 0x05A, 0xA, 0x1AE, 0xA, 0x1C0, - 0x9, 0x148, 0x9, 0x14A, 0x9, 0x082, 0xA, 0x19F, 0x9, 0x171, 0x9, 0x120, 0x9, 0x0E7, 0xA, 0x1F3, - 0x9, 0x14B, 0x9, 0x100, 0x9, 0x190, 0x6, 0x013, 0x9, 0x161, 0x9, 0x125, 0x9, 0x133, 0x9, 0x195, - 0x9, 0x173, 0x9, 0x1CA, 0x9, 0x086, 0x9, 0x1E9, 0x9, 0x0DB, 0x9, 0x1EC, 0x9, 0x08B, 0x9, 0x085, - 0x5, 0x00A, 0x8, 0x096, 0x8, 0x09C, 0x9, 0x1C3, 0x9, 0x19C, 0x9, 0x08F, 0x9, 0x18F, 0x9, 0x091, - 0x9, 0x087, 0x9, 0x0C6, 0x9, 0x177, 0x9, 0x089, 0x9, 0x0D6, 0x9, 0x08C, 0x9, 0x1EE, 0x9, 0x1EB, - 0x9, 0x084, 0x9, 0x164, 0x9, 0x175, 0x9, 0x1CD, 0x8, 0x05E, 0x9, 0x088, 0x9, 0x12B, 0x9, 0x172, - 0x9, 0x10A, 0x9, 0x08D, 0x9, 0x13A, 0x9, 0x11C, 0xA, 0x1E1, 0xA, 0x1E0, 0x9, 0x187, 0xA, 0x1DC, - 0xA, 0x1DF, 0x7, 0x074, 0x9, 0x19F, 0x8, 0x08D, 0x8, 0x0E4, 0x7, 0x079, 0x9, 0x0EA, 0x9, 0x0E1, - 0x8, 0x040, 0x7, 0x041, 0x9, 0x10B, 0x9, 0x0B0, 0x8, 0x06A, 0x8, 0x0C1, 0x7, 0x071, 0x7, 0x078, - 0x8, 0x0B1, 0x9, 0x14C, 0x7, 0x043, 0x8, 0x076, 0x7, 0x066, 0x7, 0x04D, 0x9, 0x08A, 0x6, 0x02F, - 0x8, 0x0C9, 0x9, 0x0CE, 0x9, 0x149, 0x9, 0x160, 0xA, 0x1BA, 0xA, 0x19E, 0xA, 0x39F, 0x9, 0x0E5, - 0x9, 0x194, 0x9, 0x184, 0x9, 0x126, 0x7, 0x030, 0x8, 0x06C, 0x9, 0x121, 0x9, 0x1E8, 0xA, 0x1C1, - 0xA, 0x11D, 0xA, 0x163, 0xA, 0x385, 0xA, 0x3DB, 0xA, 0x17D, 0xA, 0x106, 0xA, 0x397, 0xA, 0x24E, - 0x7, 0x02E, 0x8, 0x098, 0xA, 0x33C, 0xA, 0x32E, 0xA, 0x1E9, 0x9, 0x0BF, 0xA, 0x3DF, 0xA, 0x1DD, - 0xA, 0x32D, 0xA, 0x2ED, 0xA, 0x30B, 0xA, 0x107, 0xA, 0x2E8, 0xA, 0x3DE, 0xA, 0x125, 0xA, 0x1E8, - 0x9, 0x0E9, 0xA, 0x1CD, 0xA, 0x1B5, 0x9, 0x165, 0xA, 0x232, 0xA, 0x2E1, 0xB, 0x3AE, 0xB, 0x3C6, - 0xB, 0x3E2, 0xA, 0x205, 0xA, 0x29A, 0xA, 0x248, 0xA, 0x2CD, 0xA, 0x23B, 0xB, 0x3C5, 0xA, 0x251, - 0xA, 0x2E9, 0xA, 0x252, 0x9, 0x1EA, 0xB, 0x3A0, 0xB, 0x391, 0xA, 0x23C, 0xB, 0x392, 0xB, 0x3D5, - 0xA, 0x233, 0xA, 0x2CC, 0xB, 0x390, 0xA, 0x1BB, 0xB, 0x3A1, 0xB, 0x3C4, 0xA, 0x211, 0xA, 0x203, - 0x9, 0x12A, 0xA, 0x231, 0xB, 0x3E0, 0xA, 0x29B, 0xB, 0x3D7, 0xA, 0x202, 0xB, 0x3AD, 0xA, 0x213, - 0xA, 0x253, 0xA, 0x32C, 0xA, 0x23D, 0xA, 0x23F, 0xA, 0x32F, 0xA, 0x11C, 0xA, 0x384, 0xA, 0x31C, - 0xA, 0x17C, 0xA, 0x30A, 0xA, 0x2E0, 0xA, 0x276, 0xA, 0x250, 0xB, 0x3E3, 0xA, 0x396, 0xA, 0x18F, - 0xA, 0x204, 0xA, 0x206, 0xA, 0x230, 0xA, 0x265, 0xA, 0x212, 0xA, 0x23E, 0xB, 0x3AC, 0xB, 0x393, - 0xB, 0x3E1, 0xA, 0x1DE, 0xB, 0x3D6, 0xA, 0x31D, 0xB, 0x3E5, 0xB, 0x3E4, 0xA, 0x207, 0xB, 0x3C7, - 0xA, 0x277, 0xB, 0x3D4, 0x8, 0x0C0, 0xA, 0x162, 0xA, 0x3DA, 0xA, 0x124, 0xA, 0x1B4, 0xA, 0x264, - 0xA, 0x33D, 0xA, 0x1D1, 0xA, 0x1AF, 0xA, 0x39E, 0xA, 0x24F, 0xB, 0x373, 0xA, 0x249, 0xB, 0x372, - 0x9, 0x167, 0xA, 0x210, 0xA, 0x23A, 0xA, 0x1B8, 0xB, 0x3AF, 0xA, 0x18E, 0xA, 0x2EC, 0x7, 0x062, - 0x4, 0x00D - }; - - private const int CountIndex = 0; - private const int ValueIndex = 1; - - // UO packets may not exceed 64kb in length - private const int BufferSize = 0x10000; - - // Optimal compression ratio is 2 / 8; worst compression ratio is 11 / 8 - private const int MinimalCodeLength = 2; - private const int MaximalCodeLength = 11; - - // Fixed overhead, in bits, per compression call - private const int TerminalCodeLength = 4; - - // If our input exceeds this length, we cannot possibly compress it within the buffer - private const int DefiniteOverflow = ( ( BufferSize * 8 ) - TerminalCodeLength ) / MinimalCodeLength; - - // If our input exceeds this length, we may potentially overflow the buffer - private const int PossibleOverflow = ( ( BufferSize * 8 ) - TerminalCodeLength ) / MaximalCodeLength; - - public unsafe static void Compress(byte[] input, int offset, int count, byte[] output, ref int length) - { - if (input == null) - { - throw new ArgumentNullException("input"); - } - - if (offset < 0 || offset >= input.Length) - { - throw new ArgumentOutOfRangeException("offset"); - } - if (count < 0 || count > input.Length) - { - throw new ArgumentOutOfRangeException("count"); - } - if ((input.Length - offset) < count) - { - throw new ArgumentException(); - } - - length = 0; - - if (count > DefiniteOverflow) - { - return; - } - - int bitCount = 0; - int bitValue = 0; - - fixed (int* pTable = _huffmanTable) - { - int* pEntry; - - fixed (byte* pInputBuffer = input) - { - byte* pInput = pInputBuffer + offset, pInputEnd = pInput + count; - - fixed (byte* pOutputBuffer = output) - { - byte* pOutput = pOutputBuffer, pOutputEnd = pOutput + BufferSize; - - while (pInput < pInputEnd) - { - pEntry = &pTable[*pInput++ << 1]; - - bitCount += pEntry[CountIndex]; - - bitValue <<= pEntry[CountIndex]; - bitValue |= pEntry[ValueIndex]; - - while (bitCount >= 8) - { - bitCount -= 8; - - if (pOutput < pOutputEnd) - { - *pOutput++ = (byte)(bitValue >> bitCount); - } - else - { - length = 0; - return; - } - } - } - - // terminal code - pEntry = &pTable[0x200]; - - bitCount += pEntry[CountIndex]; - - bitValue <<= pEntry[CountIndex]; - bitValue |= pEntry[ValueIndex]; - - // align on byte boundary - if ((bitCount & 7) != 0) - { - bitValue <<= (8 - (bitCount & 7)); - bitCount += (8 - (bitCount & 7)); - } - - while (bitCount >= 8) - { - bitCount -= 8; - - if (pOutput < pOutputEnd) - { - *pOutput++ = (byte)(bitValue >> bitCount); - } - else - { - length = 0; - return; - } - } - - length = (int)(pOutput - pOutputBuffer); - } - } - } - } - - public static readonly ICompressor Compressor; - - static Compression() { - if ( Core.Unix ) { - if ( Core.Is64Bit ) { - Compressor = new CompressorUnix64(); - } else { - Compressor = new CompressorUnix32(); - } - } else if ( Core.Is64Bit ) { - Compressor = new Compressor64(); - } else { - Compressor = new Compressor32(); - } - } - - public static ZLibError Pack( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return Compressor.Compress( dest, ref destLength, source, sourceLength ); - } - - public static ZLibError Pack( byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality ) { - return Compressor.Compress( dest, ref destLength, source, sourceLength, quality ); - } - - public static ZLibError Unpack( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return Compressor.Decompress( dest, ref destLength, source, sourceLength ); - } - } - - public interface ICompressor { - string Version { - get; - } - - ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength ); - ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality ); - - ZLibError Decompress( byte[] dest, ref int destLength, byte[] source, int sourceLength ); - } - - public sealed class Compressor32 : ICompressor { - internal class SafeNativeMethods { - [DllImport( "zlib32" )] - internal static extern string zlibVersion(); - - [DllImport( "zlib32" )] - internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); - - [DllImport( "zlib32" )] - internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality); - - [DllImport( "zlib32" )] - internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen); - } - - public Compressor32() { - } - - public string Version => SafeNativeMethods.zlibVersion(); - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength); - } - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality ) { - return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality); - } - - public ZLibError Decompress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength); - } - } - - public sealed class Compressor64 : ICompressor { - internal class SafeNativeMethods { - [DllImport("zlib64")] - internal static extern string zlibVersion(); - - [DllImport("zlib64")] - internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); - - [DllImport("zlib64")] - internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality); - - [DllImport("zlib64")] - internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen); - } - - public Compressor64() { - } - - public string Version => SafeNativeMethods.zlibVersion(); - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength); - } - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality ) { - return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality); - } - - public ZLibError Decompress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength); - } - } - - public sealed class CompressorUnix32 : ICompressor { - internal class SafeNativeMethods { - [DllImport("libz")] - internal static extern string zlibVersion(); - - [DllImport("libz")] - internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); - - [DllImport("libz")] - internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality); - - [DllImport("libz")] - internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen); - } - - public CompressorUnix32() { - } - - public string Version => SafeNativeMethods.zlibVersion(); - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength); - } - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality ) { - return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality); - } - - public ZLibError Decompress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength); - } - } - - public sealed class CompressorUnix64 : ICompressor { - internal class SafeNativeMethods { - [DllImport("libz")] - internal static extern string zlibVersion(); - - [DllImport("libz")] - internal static extern ZLibError compress(byte[] dest, ref ulong destLength, byte[] source, int sourceLength); - - [DllImport("libz")] - internal static extern ZLibError compress2(byte[] dest, ref ulong destLength, byte[] source, int sourceLength, ZLibQuality quality); - - [DllImport("libz")] - internal static extern ZLibError uncompress(byte[] dest, ref ulong destLen, byte[] source, int sourceLen); - } - - public CompressorUnix64() { - } - - public string Version => SafeNativeMethods.zlibVersion(); - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - ulong destLengthLong = (ulong)destLength; - ZLibError z = SafeNativeMethods.compress(dest, ref destLengthLong, source, sourceLength); - destLength = (int)destLengthLong; - return z; - } - - public ZLibError Compress( byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality ) { - ulong destLengthLong = (ulong)destLength; - ZLibError z = SafeNativeMethods.compress2(dest, ref destLengthLong, source, sourceLength, quality); - destLength = (int)destLengthLong; - return z; - } - - public ZLibError Decompress( byte[] dest, ref int destLength, byte[] source, int sourceLength ) { - ulong destLengthLong = (ulong)destLength; - ZLibError z = SafeNativeMethods.uncompress(dest, ref destLengthLong, source, sourceLength); - destLength = (int)destLengthLong; - return z; - } - } - - public enum ZLibError : int { - VersionError = -6, - BufferError = -5, - MemoryError = -4, - DataError = -3, - StreamError = -2, - FileError = -1, - - Okay = 0, - - StreamEnd = 1, - NeedDictionary = 2 - } - - public enum ZLibQuality : int { - Default = -1, - - None = 0, - - Speed = 1, - Size = 9 - } +namespace Server.Network +{ + /// + /// Handles outgoing packet compression for the network. + /// + public static class Compression + { + private const int CountIndex = 0; + private const int ValueIndex = 1; + + // UO packets may not exceed 64kb in length + private const int BufferSize = 0x10000; + + // Optimal compression ratio is 2 / 8; worst compression ratio is 11 / 8 + private const int MinimalCodeLength = 2; + private const int MaximalCodeLength = 11; + + // Fixed overhead, in bits, per compression call + private const int TerminalCodeLength = 4; + + // If our input exceeds this length, we cannot possibly compress it within the buffer + private const int DefiniteOverflow = (BufferSize * 8 - TerminalCodeLength) / MinimalCodeLength; + + // If our input exceeds this length, we may potentially overflow the buffer + private const int PossibleOverflow = (BufferSize * 8 - TerminalCodeLength) / MaximalCodeLength; + + private static int[] _huffmanTable = new int[514] + { + 0x2, 0x000, 0x5, 0x01F, 0x6, 0x022, 0x7, 0x034, 0x7, 0x075, 0x6, 0x028, 0x6, 0x03B, 0x7, 0x032, + 0x8, 0x0E0, 0x8, 0x062, 0x7, 0x056, 0x8, 0x079, 0x9, 0x19D, 0x8, 0x097, 0x6, 0x02A, 0x7, 0x057, + 0x8, 0x071, 0x8, 0x05B, 0x9, 0x1CC, 0x8, 0x0A7, 0x7, 0x025, 0x7, 0x04F, 0x8, 0x066, 0x8, 0x07D, + 0x9, 0x191, 0x9, 0x1CE, 0x7, 0x03F, 0x9, 0x090, 0x8, 0x059, 0x8, 0x07B, 0x8, 0x091, 0x8, 0x0C6, + 0x6, 0x02D, 0x9, 0x186, 0x8, 0x06F, 0x9, 0x093, 0xA, 0x1CC, 0x8, 0x05A, 0xA, 0x1AE, 0xA, 0x1C0, + 0x9, 0x148, 0x9, 0x14A, 0x9, 0x082, 0xA, 0x19F, 0x9, 0x171, 0x9, 0x120, 0x9, 0x0E7, 0xA, 0x1F3, + 0x9, 0x14B, 0x9, 0x100, 0x9, 0x190, 0x6, 0x013, 0x9, 0x161, 0x9, 0x125, 0x9, 0x133, 0x9, 0x195, + 0x9, 0x173, 0x9, 0x1CA, 0x9, 0x086, 0x9, 0x1E9, 0x9, 0x0DB, 0x9, 0x1EC, 0x9, 0x08B, 0x9, 0x085, + 0x5, 0x00A, 0x8, 0x096, 0x8, 0x09C, 0x9, 0x1C3, 0x9, 0x19C, 0x9, 0x08F, 0x9, 0x18F, 0x9, 0x091, + 0x9, 0x087, 0x9, 0x0C6, 0x9, 0x177, 0x9, 0x089, 0x9, 0x0D6, 0x9, 0x08C, 0x9, 0x1EE, 0x9, 0x1EB, + 0x9, 0x084, 0x9, 0x164, 0x9, 0x175, 0x9, 0x1CD, 0x8, 0x05E, 0x9, 0x088, 0x9, 0x12B, 0x9, 0x172, + 0x9, 0x10A, 0x9, 0x08D, 0x9, 0x13A, 0x9, 0x11C, 0xA, 0x1E1, 0xA, 0x1E0, 0x9, 0x187, 0xA, 0x1DC, + 0xA, 0x1DF, 0x7, 0x074, 0x9, 0x19F, 0x8, 0x08D, 0x8, 0x0E4, 0x7, 0x079, 0x9, 0x0EA, 0x9, 0x0E1, + 0x8, 0x040, 0x7, 0x041, 0x9, 0x10B, 0x9, 0x0B0, 0x8, 0x06A, 0x8, 0x0C1, 0x7, 0x071, 0x7, 0x078, + 0x8, 0x0B1, 0x9, 0x14C, 0x7, 0x043, 0x8, 0x076, 0x7, 0x066, 0x7, 0x04D, 0x9, 0x08A, 0x6, 0x02F, + 0x8, 0x0C9, 0x9, 0x0CE, 0x9, 0x149, 0x9, 0x160, 0xA, 0x1BA, 0xA, 0x19E, 0xA, 0x39F, 0x9, 0x0E5, + 0x9, 0x194, 0x9, 0x184, 0x9, 0x126, 0x7, 0x030, 0x8, 0x06C, 0x9, 0x121, 0x9, 0x1E8, 0xA, 0x1C1, + 0xA, 0x11D, 0xA, 0x163, 0xA, 0x385, 0xA, 0x3DB, 0xA, 0x17D, 0xA, 0x106, 0xA, 0x397, 0xA, 0x24E, + 0x7, 0x02E, 0x8, 0x098, 0xA, 0x33C, 0xA, 0x32E, 0xA, 0x1E9, 0x9, 0x0BF, 0xA, 0x3DF, 0xA, 0x1DD, + 0xA, 0x32D, 0xA, 0x2ED, 0xA, 0x30B, 0xA, 0x107, 0xA, 0x2E8, 0xA, 0x3DE, 0xA, 0x125, 0xA, 0x1E8, + 0x9, 0x0E9, 0xA, 0x1CD, 0xA, 0x1B5, 0x9, 0x165, 0xA, 0x232, 0xA, 0x2E1, 0xB, 0x3AE, 0xB, 0x3C6, + 0xB, 0x3E2, 0xA, 0x205, 0xA, 0x29A, 0xA, 0x248, 0xA, 0x2CD, 0xA, 0x23B, 0xB, 0x3C5, 0xA, 0x251, + 0xA, 0x2E9, 0xA, 0x252, 0x9, 0x1EA, 0xB, 0x3A0, 0xB, 0x391, 0xA, 0x23C, 0xB, 0x392, 0xB, 0x3D5, + 0xA, 0x233, 0xA, 0x2CC, 0xB, 0x390, 0xA, 0x1BB, 0xB, 0x3A1, 0xB, 0x3C4, 0xA, 0x211, 0xA, 0x203, + 0x9, 0x12A, 0xA, 0x231, 0xB, 0x3E0, 0xA, 0x29B, 0xB, 0x3D7, 0xA, 0x202, 0xB, 0x3AD, 0xA, 0x213, + 0xA, 0x253, 0xA, 0x32C, 0xA, 0x23D, 0xA, 0x23F, 0xA, 0x32F, 0xA, 0x11C, 0xA, 0x384, 0xA, 0x31C, + 0xA, 0x17C, 0xA, 0x30A, 0xA, 0x2E0, 0xA, 0x276, 0xA, 0x250, 0xB, 0x3E3, 0xA, 0x396, 0xA, 0x18F, + 0xA, 0x204, 0xA, 0x206, 0xA, 0x230, 0xA, 0x265, 0xA, 0x212, 0xA, 0x23E, 0xB, 0x3AC, 0xB, 0x393, + 0xB, 0x3E1, 0xA, 0x1DE, 0xB, 0x3D6, 0xA, 0x31D, 0xB, 0x3E5, 0xB, 0x3E4, 0xA, 0x207, 0xB, 0x3C7, + 0xA, 0x277, 0xB, 0x3D4, 0x8, 0x0C0, 0xA, 0x162, 0xA, 0x3DA, 0xA, 0x124, 0xA, 0x1B4, 0xA, 0x264, + 0xA, 0x33D, 0xA, 0x1D1, 0xA, 0x1AF, 0xA, 0x39E, 0xA, 0x24F, 0xB, 0x373, 0xA, 0x249, 0xB, 0x372, + 0x9, 0x167, 0xA, 0x210, 0xA, 0x23A, 0xA, 0x1B8, 0xB, 0x3AF, 0xA, 0x18E, 0xA, 0x2EC, 0x7, 0x062, + 0x4, 0x00D + }; + + public static readonly ICompressor Compressor; + + static Compression() + { + if (Core.Unix) + { + if (Core.Is64Bit) + Compressor = new CompressorUnix64(); + else + Compressor = new CompressorUnix32(); + } + else if (Core.Is64Bit) + { + Compressor = new Compressor64(); + } + else + { + Compressor = new Compressor32(); + } + } + + public static unsafe void Compress(byte[] input, int offset, int count, byte[] output, ref int length) + { + if (input == null) throw new ArgumentNullException("input"); + + if (offset < 0 || offset >= input.Length) throw new ArgumentOutOfRangeException("offset"); + if (count < 0 || count > input.Length) throw new ArgumentOutOfRangeException("count"); + if (input.Length - offset < count) throw new ArgumentException(); + + length = 0; + + if (count > DefiniteOverflow) return; + + int bitCount = 0; + int bitValue = 0; + + fixed (int* pTable = _huffmanTable) + { + int* pEntry; + + fixed (byte* pInputBuffer = input) + { + byte* pInput = pInputBuffer + offset, pInputEnd = pInput + count; + + fixed (byte* pOutputBuffer = output) + { + byte* pOutput = pOutputBuffer, pOutputEnd = pOutput + BufferSize; + + while (pInput < pInputEnd) + { + pEntry = &pTable[*pInput++ << 1]; + + bitCount += pEntry[CountIndex]; + + bitValue <<= pEntry[CountIndex]; + bitValue |= pEntry[ValueIndex]; + + while (bitCount >= 8) + { + bitCount -= 8; + + if (pOutput < pOutputEnd) + { + *pOutput++ = (byte)(bitValue >> bitCount); + } + else + { + length = 0; + return; + } + } + } + + // terminal code + pEntry = &pTable[0x200]; + + bitCount += pEntry[CountIndex]; + + bitValue <<= pEntry[CountIndex]; + bitValue |= pEntry[ValueIndex]; + + // align on byte boundary + if ((bitCount & 7) != 0) + { + bitValue <<= 8 - (bitCount & 7); + bitCount += 8 - (bitCount & 7); + } + + while (bitCount >= 8) + { + bitCount -= 8; + + if (pOutput < pOutputEnd) + { + *pOutput++ = (byte)(bitValue >> bitCount); + } + else + { + length = 0; + return; + } + } + + length = (int)(pOutput - pOutputBuffer); + } + } + } + } + + public static ZLibError Pack(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return Compressor.Compress(dest, ref destLength, source, sourceLength); + } + + public static ZLibError Pack(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality) + { + return Compressor.Compress(dest, ref destLength, source, sourceLength, quality); + } + + public static ZLibError Unpack(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return Compressor.Decompress(dest, ref destLength, source, sourceLength); + } + } + + public interface ICompressor + { + string Version{ get; } + + ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); + ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality); + + ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength); + } + + public sealed class Compressor32 : ICompressor + { + public string Version => SafeNativeMethods.zlibVersion(); + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength); + } + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality) + { + return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality); + } + + public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength); + } + + internal class SafeNativeMethods + { + [DllImport("zlib32")] + internal static extern string zlibVersion(); + + [DllImport("zlib32")] + internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); + + [DllImport("zlib32")] + internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength, + ZLibQuality quality); + + [DllImport("zlib32")] + internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen); + } + } + + public sealed class Compressor64 : ICompressor + { + public string Version => SafeNativeMethods.zlibVersion(); + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength); + } + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality) + { + return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality); + } + + public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength); + } + + internal class SafeNativeMethods + { + [DllImport("zlib64")] + internal static extern string zlibVersion(); + + [DllImport("zlib64")] + internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); + + [DllImport("zlib64")] + internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength, + ZLibQuality quality); + + [DllImport("zlib64")] + internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen); + } + } + + public sealed class CompressorUnix32 : ICompressor + { + public string Version => SafeNativeMethods.zlibVersion(); + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return SafeNativeMethods.compress(dest, ref destLength, source, sourceLength); + } + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality) + { + return SafeNativeMethods.compress2(dest, ref destLength, source, sourceLength, quality); + } + + public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + return SafeNativeMethods.uncompress(dest, ref destLength, source, sourceLength); + } + + internal class SafeNativeMethods + { + [DllImport("libz")] + internal static extern string zlibVersion(); + + [DllImport("libz")] + internal static extern ZLibError compress(byte[] dest, ref int destLength, byte[] source, int sourceLength); + + [DllImport("libz")] + internal static extern ZLibError compress2(byte[] dest, ref int destLength, byte[] source, int sourceLength, + ZLibQuality quality); + + [DllImport("libz")] + internal static extern ZLibError uncompress(byte[] dest, ref int destLen, byte[] source, int sourceLen); + } + } + + public sealed class CompressorUnix64 : ICompressor + { + public string Version => SafeNativeMethods.zlibVersion(); + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + ulong destLengthLong = (ulong)destLength; + ZLibError z = SafeNativeMethods.compress(dest, ref destLengthLong, source, sourceLength); + destLength = (int)destLengthLong; + return z; + } + + public ZLibError Compress(byte[] dest, ref int destLength, byte[] source, int sourceLength, ZLibQuality quality) + { + ulong destLengthLong = (ulong)destLength; + ZLibError z = SafeNativeMethods.compress2(dest, ref destLengthLong, source, sourceLength, quality); + destLength = (int)destLengthLong; + return z; + } + + public ZLibError Decompress(byte[] dest, ref int destLength, byte[] source, int sourceLength) + { + ulong destLengthLong = (ulong)destLength; + ZLibError z = SafeNativeMethods.uncompress(dest, ref destLengthLong, source, sourceLength); + destLength = (int)destLengthLong; + return z; + } + + internal class SafeNativeMethods + { + [DllImport("libz")] + internal static extern string zlibVersion(); + + [DllImport("libz")] + internal static extern ZLibError compress(byte[] dest, ref ulong destLength, byte[] source, int sourceLength); + + [DllImport("libz")] + internal static extern ZLibError compress2(byte[] dest, ref ulong destLength, byte[] source, int sourceLength, + ZLibQuality quality); + + [DllImport("libz")] + internal static extern ZLibError uncompress(byte[] dest, ref ulong destLen, byte[] source, int sourceLen); + } + } + + public enum ZLibError + { + VersionError = -6, + BufferError = -5, + MemoryError = -4, + DataError = -3, + StreamError = -2, + FileError = -1, + + Okay = 0, + + StreamEnd = 1, + NeedDictionary = 2 + } + + public enum ZLibQuality + { + Default = -1, + + None = 0, + + Speed = 1, + Size = 9 + } } \ No newline at end of file diff --git a/Server/Network/EncodedPacketHandler.cs b/Server/Network/EncodedPacketHandler.cs index de79ab0bc..533cc7643 100644 --- a/Server/Network/EncodedPacketHandler.cs +++ b/Server/Network/EncodedPacketHandler.cs @@ -20,21 +20,21 @@ namespace Server.Network { - public delegate void OnEncodedPacketReceive( NetState state, IEntity ent, EncodedReader pvSrc ); + public delegate void OnEncodedPacketReceive(NetState state, IEntity ent, EncodedReader pvSrc); - public class EncodedPacketHandler - { - public EncodedPacketHandler( int packetID, bool ingame, OnEncodedPacketReceive onReceive ) - { - PacketID = packetID; - Ingame = ingame; - OnReceive = onReceive; - } + public class EncodedPacketHandler + { + public EncodedPacketHandler(int packetID, bool ingame, OnEncodedPacketReceive onReceive) + { + PacketID = packetID; + Ingame = ingame; + OnReceive = onReceive; + } - public int PacketID { get; } + public int PacketID{ get; } - public OnEncodedPacketReceive OnReceive { get; } + public OnEncodedPacketReceive OnReceive{ get; } - public bool Ingame { get; } - } + public bool Ingame{ get; } + } } \ No newline at end of file diff --git a/Server/Network/EncodedReader.cs b/Server/Network/EncodedReader.cs index 3eaa1694a..5caf631e5 100644 --- a/Server/Network/EncodedReader.cs +++ b/Server/Network/EncodedReader.cs @@ -20,56 +20,56 @@ namespace Server.Network { - public class EncodedReader - { - private PacketReader m_Reader; + public class EncodedReader + { + private PacketReader m_Reader; - public EncodedReader( PacketReader reader ) - { - m_Reader = reader; - } + public EncodedReader(PacketReader reader) + { + m_Reader = reader; + } - public byte[] Buffer => m_Reader.Buffer; + public byte[] Buffer => m_Reader.Buffer; - public void Trace( NetState state ) - { - m_Reader.Trace( state ); - } + public void Trace(NetState state) + { + m_Reader.Trace(state); + } - public int ReadInt32() - { - if ( m_Reader.ReadByte() != 0 ) - return 0; + public int ReadInt32() + { + if (m_Reader.ReadByte() != 0) + return 0; - return m_Reader.ReadInt32(); - } + return m_Reader.ReadInt32(); + } - public Point3D ReadPoint3D() - { - if ( m_Reader.ReadByte() != 3 ) - return Point3D.Zero; + public Point3D ReadPoint3D() + { + if (m_Reader.ReadByte() != 3) + return Point3D.Zero; - return new Point3D( m_Reader.ReadInt16(), m_Reader.ReadInt16(), m_Reader.ReadByte() ); - } + return new Point3D(m_Reader.ReadInt16(), m_Reader.ReadInt16(), m_Reader.ReadByte()); + } - public string ReadUnicodeStringSafe() - { - if ( m_Reader.ReadByte() != 2 ) - return ""; + public string ReadUnicodeStringSafe() + { + if (m_Reader.ReadByte() != 2) + return ""; - int length = m_Reader.ReadUInt16(); + int length = m_Reader.ReadUInt16(); - return m_Reader.ReadUnicodeStringSafe( length ); - } + return m_Reader.ReadUnicodeStringSafe(length); + } - public string ReadUnicodeString() - { - if ( m_Reader.ReadByte() != 2 ) - return ""; + public string ReadUnicodeString() + { + if (m_Reader.ReadByte() != 2) + return ""; - int length = m_Reader.ReadUInt16(); + int length = m_Reader.ReadUInt16(); - return m_Reader.ReadUnicodeString( length ); - } - } + return m_Reader.ReadUnicodeString(length); + } + } } \ No newline at end of file diff --git a/Server/Network/Listener.cs b/Server/Network/Listener.cs index 3b1efe94c..a45d1e053 100644 --- a/Server/Network/Listener.cs +++ b/Server/Network/Listener.cs @@ -28,39 +28,39 @@ using System.Threading; namespace Server.Network { - public class Listener : IDisposable - { - private Socket m_Listener; + public class Listener : IDisposable + { + private Socket m_Listener; - private Queue m_Accepted; - private object m_AcceptedSyncRoot; + private Queue m_Accepted; + private object m_AcceptedSyncRoot; #if NewAsyncSockets - private SocketAsyncEventArgs m_EventArgs; + private SocketAsyncEventArgs m_EventArgs; #else private AsyncCallback m_OnAccept; #endif - private static Socket[] m_EmptySockets = new Socket[0]; + private static Socket[] m_EmptySockets = new Socket[0]; - public static IPEndPoint[] EndPoints { get; set; } + public static IPEndPoint[] EndPoints{ get; set; } - public Listener( IPEndPoint ipep ) - { - m_Accepted = new Queue(); - m_AcceptedSyncRoot = ((ICollection)m_Accepted).SyncRoot; + public Listener(IPEndPoint ipep) + { + m_Accepted = new Queue(); + m_AcceptedSyncRoot = ((ICollection)m_Accepted).SyncRoot; - m_Listener = Bind( ipep ); + m_Listener = Bind(ipep); - if ( m_Listener == null ) - return; + if (m_Listener == null) + return; - DisplayListener(); + DisplayListener(); #if NewAsyncSockets - m_EventArgs = new SocketAsyncEventArgs(); - m_EventArgs.Completed += Accept_Completion; - Accept_Start(); + m_EventArgs = new SocketAsyncEventArgs(); + m_EventArgs.Completed += Accept_Completion; + Accept_Start(); #else m_OnAccept = new AsyncCallback( OnAccept ); try { @@ -70,111 +70,124 @@ namespace Server.Network } catch ( ObjectDisposedException ) { } #endif - } + } - private Socket Bind( IPEndPoint ipep ) - { - Socket s = new Socket( ipep.AddressFamily, SocketType.Stream, ProtocolType.Tcp ); + private Socket Bind(IPEndPoint ipep) + { + Socket s = new Socket(ipep.AddressFamily, SocketType.Stream, ProtocolType.Tcp); - try - { - s.LingerState.Enabled = false; - s.ExclusiveAddressUse = false; + try + { + s.LingerState.Enabled = false; + s.ExclusiveAddressUse = false; - s.Bind( ipep ); - s.Listen( 8 ); + s.Bind(ipep); + s.Listen(8); - return s; - } - catch ( Exception e ) - { - if ( e is SocketException se ) { - if ( se.ErrorCode == 10048 ) { // WSAEADDRINUSE - Console.WriteLine( "Listener Failed: {0}:{1} (In Use)", ipep.Address, ipep.Port ); - } - else if ( se.ErrorCode == 10049 ) { // WSAEADDRNOTAVAIL - Console.WriteLine( "Listener Failed: {0}:{1} (Unavailable)", ipep.Address, ipep.Port ); - } - else { - Console.WriteLine( "Listener Exception:" ); - Console.WriteLine( e ); - } - } + return s; + } + catch (Exception e) + { + if (e is SocketException se) + { + if (se.ErrorCode == 10048) + { + // WSAEADDRINUSE + Console.WriteLine("Listener Failed: {0}:{1} (In Use)", ipep.Address, ipep.Port); + } + else if (se.ErrorCode == 10049) + { + // WSAEADDRNOTAVAIL + Console.WriteLine("Listener Failed: {0}:{1} (Unavailable)", ipep.Address, ipep.Port); + } + else + { + Console.WriteLine("Listener Exception:"); + Console.WriteLine(e); + } + } - return null; - } - } + return null; + } + } - private void DisplayListener() - { - if ( !(m_Listener.LocalEndPoint is IPEndPoint ipep) ) - return; + private void DisplayListener() + { + if (!(m_Listener.LocalEndPoint is IPEndPoint ipep)) + return; - if ( ipep.Address.Equals( IPAddress.Any ) || ipep.Address.Equals( IPAddress.IPv6Any ) ) { - NetworkInterface[] adapters = NetworkInterface.GetAllNetworkInterfaces(); - foreach ( NetworkInterface adapter in adapters ) { - IPInterfaceProperties properties = adapter.GetIPProperties(); - foreach ( UnicastIPAddressInformation unicast in properties.UnicastAddresses ) { - if ( ipep.AddressFamily == unicast.Address.AddressFamily ) - Console.WriteLine( "Listening: {0}:{1}", unicast.Address, ipep.Port ); - } - } - /* - try { - Console.WriteLine( "Listening: {0}:{1}", IPAddress.Loopback, ipep.Port ); - IPHostEntry iphe = Dns.GetHostEntry( Dns.GetHostName() ); - IPAddress[] ip = iphe.AddressList; - for ( int i = 0; i < ip.Length; ++i ) - Console.WriteLine( "Listening: {0}:{1}", ip[i], ipep.Port ); - } - catch { } - */ - } - else { - Console.WriteLine( "Listening: {0}:{1}", ipep.Address, ipep.Port ); - } - } + if (ipep.Address.Equals(IPAddress.Any) || ipep.Address.Equals(IPAddress.IPv6Any)) + { + NetworkInterface[] adapters = NetworkInterface.GetAllNetworkInterfaces(); + foreach (NetworkInterface adapter in adapters) + { + IPInterfaceProperties properties = adapter.GetIPProperties(); + foreach (UnicastIPAddressInformation unicast in properties.UnicastAddresses) + if (ipep.AddressFamily == unicast.Address.AddressFamily) + Console.WriteLine("Listening: {0}:{1}", unicast.Address, ipep.Port); + } + + /* + try { + Console.WriteLine( "Listening: {0}:{1}", IPAddress.Loopback, ipep.Port ); + IPHostEntry iphe = Dns.GetHostEntry( Dns.GetHostName() ); + IPAddress[] ip = iphe.AddressList; + for ( int i = 0; i < ip.Length; ++i ) + Console.WriteLine( "Listening: {0}:{1}", ip[i], ipep.Port ); + } + catch { } + */ + } + else + { + Console.WriteLine("Listening: {0}:{1}", ipep.Address, ipep.Port); + } + } #if NewAsyncSockets - private void Accept_Start() - { - bool result = false; + private void Accept_Start() + { + bool result = false; - do { - try { - result = !m_Listener.AcceptAsync( m_EventArgs ); - } catch ( SocketException ex ) { - NetState.TraceException( ex ); - break; - } catch ( ObjectDisposedException ) { - break; - } + do + { + try + { + result = !m_Listener.AcceptAsync(m_EventArgs); + } + catch (SocketException ex) + { + NetState.TraceException(ex); + break; + } + catch (ObjectDisposedException) + { + break; + } - if ( result ) - Accept_Process( m_EventArgs ); - } while ( result ); - } + if (result) + Accept_Process(m_EventArgs); + } while (result); + } - private void Accept_Completion( object sender, SocketAsyncEventArgs e ) - { - Accept_Process( e ); + private void Accept_Completion(object sender, SocketAsyncEventArgs e) + { + Accept_Process(e); - Accept_Start(); - } + Accept_Start(); + } - private void Accept_Process( SocketAsyncEventArgs e ) - { - if ( e.SocketError == SocketError.Success && VerifySocket( e.AcceptSocket ) ) { - Enqueue( e.AcceptSocket ); - } else { - Release( e.AcceptSocket ); - } + private void Accept_Process(SocketAsyncEventArgs e) + { + if (e.SocketError == SocketError.Success && VerifySocket(e.AcceptSocket)) + Enqueue(e.AcceptSocket); + else + Release(e.AcceptSocket); - e.AcceptSocket = null; - } + e.AcceptSocket = null; + } #else - private void OnAccept( IAsyncResult asyncResult ) { Socket listener = (Socket) asyncResult.AsyncState; @@ -205,71 +218,85 @@ namespace Server.Network } #endif - private bool VerifySocket( Socket socket ) { - try { - SocketConnectEventArgs args = new SocketConnectEventArgs( socket ); + private bool VerifySocket(Socket socket) + { + try + { + SocketConnectEventArgs args = new SocketConnectEventArgs(socket); - EventSink.InvokeSocketConnect( args ); + EventSink.InvokeSocketConnect(args); - return args.AllowConnection; - } catch ( Exception ex ) { - NetState.TraceException( ex ); + return args.AllowConnection; + } + catch (Exception ex) + { + NetState.TraceException(ex); - return false; - } - } + return false; + } + } - private void Enqueue( Socket socket ) { - lock ( m_AcceptedSyncRoot ) { - m_Accepted.Enqueue( socket ); - } + private void Enqueue(Socket socket) + { + lock (m_AcceptedSyncRoot) + { + m_Accepted.Enqueue(socket); + } - Core.Set(); - } + Core.Set(); + } - private void Release( Socket socket ) { - try { - socket.Shutdown( SocketShutdown.Both ); - } catch ( SocketException ex ) { - NetState.TraceException( ex ); - } + private void Release(Socket socket) + { + try + { + socket.Shutdown(SocketShutdown.Both); + } + catch (SocketException ex) + { + NetState.TraceException(ex); + } - try { - socket.Close(); - } catch ( SocketException ex ) { - NetState.TraceException( ex ); - } - } + try + { + socket.Close(); + } + catch (SocketException ex) + { + NetState.TraceException(ex); + } + } - public Socket[] Slice() - { - Socket[] array; + public Socket[] Slice() + { + Socket[] array; - lock ( m_AcceptedSyncRoot ) - { - if ( m_Accepted.Count == 0 ) - return m_EmptySockets; + lock (m_AcceptedSyncRoot) + { + if (m_Accepted.Count == 0) + return m_EmptySockets; - array = m_Accepted.ToArray(); - m_Accepted.Clear(); - } + array = m_Accepted.ToArray(); + m_Accepted.Clear(); + } - return array; - } + return array; + } - public void Dispose(bool disposing) - { - if (disposing) - { - Socket socket = Interlocked.Exchange(ref m_Listener, null); + public void Dispose(bool disposing) + { + if (disposing) + { + Socket socket = Interlocked.Exchange(ref m_Listener, null); - socket?.Close(); - } - } + socket?.Close(); + } + } - public void Dispose() { - Dispose(true); - GC.SuppressFinalize(this); - } - } -} + public void Dispose() + { + Dispose(true); + GC.SuppressFinalize(this); + } + } +} \ No newline at end of file diff --git a/Server/Network/MessagePump.cs b/Server/Network/MessagePump.cs index 4ffcb997a..05a5042c0 100644 --- a/Server/Network/MessagePump.cs +++ b/Server/Network/MessagePump.cs @@ -27,241 +27,263 @@ using Server.Diagnostics; namespace Server.Network { - public class MessagePump - { - private Queue m_Queue; - private Queue m_WorkingQueue; - private Queue m_Throttled; + public class MessagePump + { + private const int BufferSize = 4096; + private BufferPool m_Buffers = new BufferPool("Processor", 4, BufferSize); + private Queue m_Queue; + private Queue m_Throttled; + private Queue m_WorkingQueue; - public MessagePump() - { - IPEndPoint[] ipep = Listener.EndPoints; + public MessagePump() + { + IPEndPoint[] ipep = Listener.EndPoints; - Listeners = new Listener[ipep.Length]; + Listeners = new Listener[ipep.Length]; - bool success = false; + bool success = false; - do { - for ( int i = 0; i < ipep.Length; i++ ) { - Listener l = new Listener( ipep[i] ); - if ( !success && l != null ) - success = true; - Listeners[i] = l; - } + do + { + for (int i = 0; i < ipep.Length; i++) + { + Listener l = new Listener(ipep[i]); + if (!success) + success = true; + Listeners[i] = l; + } - if ( !success ) { - Console.WriteLine( "Retrying..." ); - Thread.Sleep( 10000 ); - } - } while ( !success ); + if (!success) + { + Console.WriteLine("Retrying..."); + Thread.Sleep(10000); + } + } while (!success); - m_Queue = new Queue(); - m_WorkingQueue = new Queue(); - m_Throttled = new Queue(); - } + m_Queue = new Queue(); + m_WorkingQueue = new Queue(); + m_Throttled = new Queue(); + } - public Listener[] Listeners { get; set; } + public Listener[] Listeners{ get; set; } - public void AddListener( Listener l ) - { - Listener[] old = Listeners; + public void AddListener(Listener l) + { + Listener[] old = Listeners; - Listeners = new Listener[old.Length + 1]; + Listeners = new Listener[old.Length + 1]; - for ( int i = 0; i < old.Length; ++i ) - Listeners[i] = old[i]; + for (int i = 0; i < old.Length; ++i) + Listeners[i] = old[i]; - Listeners[old.Length] = l; - } + Listeners[old.Length] = l; + } - private void CheckListener() - { - for ( int j = 0; j < Listeners.Length; ++j ) - { - Socket[] accepted = Listeners[j].Slice(); + private void CheckListener() + { + for (int j = 0; j < Listeners.Length; ++j) + { + Socket[] accepted = Listeners[j].Slice(); - for ( int i = 0; i < accepted.Length; ++i ) - { - NetState ns = new NetState( accepted[i], this ); - ns.Start(); + for (int i = 0; i < accepted.Length; ++i) + { + NetState ns = new NetState(accepted[i], this); + ns.Start(); - if ( ns.Running ) - Console.WriteLine( "Client: {0}: Connected. [{1} Online]", ns, NetState.Instances.Count ); - } - } - } + if (ns.Running) + Console.WriteLine("Client: {0}: Connected. [{1} Online]", ns, NetState.Instances.Count); + } + } + } - public void OnReceive( NetState ns ) - { - lock ( this ) - m_Queue.Enqueue( ns ); + public void OnReceive(NetState ns) + { + lock (this) + { + m_Queue.Enqueue(ns); + } - Core.Set(); - } + Core.Set(); + } - public void Slice() - { - CheckListener(); + public void Slice() + { + CheckListener(); - lock ( this ) - { - Queue temp = m_WorkingQueue; - m_WorkingQueue = m_Queue; - m_Queue = temp; - } + lock (this) + { + Queue temp = m_WorkingQueue; + m_WorkingQueue = m_Queue; + m_Queue = temp; + } - while ( m_WorkingQueue.Count > 0 ) - { - NetState ns = m_WorkingQueue.Dequeue(); + while (m_WorkingQueue.Count > 0) + { + NetState ns = m_WorkingQueue.Dequeue(); - if ( ns.Running ) - HandleReceive( ns ); - } + if (ns.Running) + HandleReceive(ns); + } - lock ( this ) - { - while ( m_Throttled.Count > 0 ) - m_Queue.Enqueue( m_Throttled.Dequeue() ); - } - } + lock (this) + { + while (m_Throttled.Count > 0) + m_Queue.Enqueue(m_Throttled.Dequeue()); + } + } - private const int BufferSize = 4096; - private BufferPool m_Buffers = new BufferPool( "Processor", 4, BufferSize ); + private bool HandleSeed(NetState ns, ByteQueue buffer) + { + if (buffer.GetPacketID() == 0xEF) + { + // new packet in client 6.0.5.0 replaces the traditional seed method with a seed packet + // 0xEF = 239 = multicast IP, so this should never appear in a normal seed. So this is backwards compatible with older clients. + ns.Seeded = true; + return true; + } - private bool HandleSeed(NetState ns, ByteQueue buffer) { - if (buffer.GetPacketID() == 0xEF) { - // new packet in client 6.0.5.0 replaces the traditional seed method with a seed packet - // 0xEF = 239 = multicast IP, so this should never appear in a normal seed. So this is backwards compatible with older clients. - ns.Seeded = true; - return true; - } + if (buffer.Length >= 4) + { + byte[] m_Peek = new byte[4]; - if (buffer.Length >= 4) { - byte[] m_Peek = new byte[4]; + buffer.Dequeue(m_Peek, 0, 4); - buffer.Dequeue(m_Peek, 0, 4); + int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3]; - int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3]; + if (seed == 0) + { + Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns); + ns.Dispose(); + return false; + } - if (seed == 0) { - Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns); - ns.Dispose(); - return false; - } + ns.m_Seed = seed; + ns.Seeded = true; + return true; + } - ns.m_Seed = seed; - ns.Seeded = true; - return true; - } - return false; - } + return false; + } - private bool CheckEncrypted(NetState ns, int packetID) { - if (!ns.SentFirstPacket && packetID != 0xF0 && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && packetID != 0x91 && packetID != 0xA4 && packetID != 0xEF) { - Console.WriteLine("Client: {0}: Encrypted client detected, disconnecting", ns); - ns.Dispose(); - return true; - } - return false; - } + private bool CheckEncrypted(NetState ns, int packetID) + { + if (!ns.SentFirstPacket && packetID != 0xF0 && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && + packetID != 0x91 && packetID != 0xA4 && packetID != 0xEF) + { + Console.WriteLine("Client: {0}: Encrypted client detected, disconnecting", ns); + ns.Dispose(); + return true; + } - public void HandleReceive( NetState ns ) - { - ByteQueue buffer = ns.Buffer; + return false; + } - if ( buffer == null || buffer.Length <= 0 ) - return; + public void HandleReceive(NetState ns) + { + ByteQueue buffer = ns.Buffer; - lock ( buffer ) - { - if ( !ns.Seeded ) { - if (!HandleSeed(ns, buffer)) - return; - } + if (buffer == null || buffer.Length <= 0) + return; - int length = buffer.Length; + lock (buffer) + { + if (!ns.Seeded) + if (!HandleSeed(ns, buffer)) + return; - while ( length > 0 && ns.Running ) { - int packetID = buffer.GetPacketID(); + int length = buffer.Length; - if (CheckEncrypted(ns, packetID)) - break; + while (length > 0 && ns.Running) + { + int packetID = buffer.GetPacketID(); - PacketHandler handler = ns.GetHandler( packetID ); + if (CheckEncrypted(ns, packetID)) + break; - if ( handler == null ) { - byte[] data = new byte[length]; - length = buffer.Dequeue( data, 0, length ); - new PacketReader( data, length, false ).Trace( ns ); - break; - } + PacketHandler handler = ns.GetHandler(packetID); - int packetLength = handler.Length; + if (handler == null) + { + byte[] data = new byte[length]; + length = buffer.Dequeue(data, 0, length); + new PacketReader(data, length, false).Trace(ns); + break; + } - if ( packetLength <= 0 ) { - if ( length >= 3 ) { - packetLength = buffer.GetPacketLength(); + int packetLength = handler.Length; - if ( packetLength < 3 ) { - ns.Dispose(); - break; - } - } else { - break; - } - } + if (packetLength <= 0) + { + if (length >= 3) + { + packetLength = buffer.GetPacketLength(); - if ( length >= packetLength ) { - if (handler.Ingame) - { - if (ns.Mobile == null ) { - Console.WriteLine( "Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", ns, packetID ); - ns.Dispose(); - break; - } + if (packetLength < 3) + { + ns.Dispose(); + break; + } + } + else + { + break; + } + } - if (ns.Mobile.Deleted) { - ns.Dispose(); - break; - } - } + if (length >= packetLength) + { + if (handler.Ingame) + { + if (ns.Mobile == null) + { + Console.WriteLine( + "Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", ns, + packetID); + ns.Dispose(); + break; + } - ThrottlePacketCallback throttler = handler.ThrottleCallback; + if (ns.Mobile.Deleted) + { + ns.Dispose(); + break; + } + } - if ( throttler != null && !throttler( ns ) ) { - m_Throttled.Enqueue( ns ); - return; - } + ThrottlePacketCallback throttler = handler.ThrottleCallback; - PacketReceiveProfile prof = null; + if (throttler != null && !throttler(ns)) + { + m_Throttled.Enqueue(ns); + return; + } - if (Core.Profiling) prof = PacketReceiveProfile.Acquire( packetID ); + PacketReceiveProfile prof = null; - prof?.Start(); + if (Core.Profiling) prof = PacketReceiveProfile.Acquire(packetID); - byte[] packetBuffer; + prof?.Start(); - if ( BufferSize >= packetLength ) - packetBuffer = m_Buffers.AcquireBuffer(); - else - packetBuffer = new byte[packetLength]; + byte[] packetBuffer = BufferSize >= packetLength ? m_Buffers.AcquireBuffer() : new byte[packetLength]; - packetLength = buffer.Dequeue( packetBuffer, 0, packetLength ); + packetLength = buffer.Dequeue(packetBuffer, 0, packetLength); - PacketReader r = new PacketReader( packetBuffer, packetLength, handler.Length != 0 ); + PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0); - handler.OnReceive( ns, r ); - length = buffer.Length; + handler.OnReceive(ns, r); + length = buffer.Length; - if ( BufferSize >= packetLength ) - m_Buffers.ReleaseBuffer( packetBuffer ); + if (BufferSize >= packetLength) + m_Buffers.ReleaseBuffer(packetBuffer); - prof?.Finish( packetLength ); - } else { - break; - } - } - } - } - } + prof?.Finish(packetLength); + } + else + { + break; + } + } + } + } + } } \ No newline at end of file diff --git a/Server/Network/NetState.cs b/Server/Network/NetState.cs index b67f2c7f8..201eea87c 100644 --- a/Server/Network/NetState.cs +++ b/Server/Network/NetState.cs @@ -20,443 +20,471 @@ using System; using System.Collections.Generic; +using System.Diagnostics; using System.IO; using System.Net; using System.Net.Sockets; using System.Threading; using System.Threading.Tasks; using Server.Accounting; -using Server.Items; -using Server.Gumps; -using Server.Menus; -using Server.HuePickers; using Server.Diagnostics; +using Server.Gumps; +using Server.HuePickers; +using Server.Items; +using Server.Menus; -namespace Server.Network { - public interface IPacketEncoder { - void EncodeOutgoingPacket( NetState to, ref byte[] buffer, ref int length ); - void DecodeIncomingPacket( NetState from, ref byte[] buffer, ref int length ); - } +namespace Server.Network +{ + public interface IPacketEncoder + { + void EncodeOutgoingPacket(NetState to, ref byte[] buffer, ref int length); + void DecodeIncomingPacket(NetState from, ref byte[] buffer, ref int length); + } - public delegate void NetStateCreatedCallback( NetState ns ); + public delegate void NetStateCreatedCallback(NetState ns); - public class NetState : IComparable { - private byte[] m_RecvBuffer; - private SendQueue m_SendQueue; + public class NetState : IComparable + { + private byte[] m_RecvBuffer; + private SendQueue m_SendQueue; #if NewAsyncSockets - private SocketAsyncEventArgs m_ReceiveEventArgs, m_SendEventArgs; + private SocketAsyncEventArgs m_ReceiveEventArgs, m_SendEventArgs; #else private AsyncCallback m_OnReceive, m_OnSend; #endif - private MessagePump m_MessagePump; - private string m_ToString; - private ClientVersion m_Version; - - public DateTime ConnectedOn { get; } - - public TimeSpan ConnectedFor => ( DateTime.UtcNow - ConnectedOn ); - - internal int m_Seed; - internal int m_AuthID; - - public IPAddress Address { get; } - - private static bool m_Paused; - - [Flags] - private enum AsyncState { - Pending = 0x01, - Paused = 0x02 - } - - private AsyncState m_AsyncState; - private object m_AsyncLock = new object(); - - public IPacketEncoder PacketEncoder { get; set; } - - public static NetStateCreatedCallback CreatedCallback { get; set; } - - public bool SentFirstPacket { get; set; } - - public bool BlockAllPackets { get; set; } - - public ClientFlags Flags { get; set; } - - public ClientVersion Version { - get => m_Version; - set { - m_Version = value; - - if ( value >= m_Version704565 ) { - _ProtocolChanges = ProtocolChanges.Version704565; - } else if ( value >= m_Version70331 ) { - _ProtocolChanges = ProtocolChanges.Version70331; - } else if ( value >= m_Version70300 ) { - _ProtocolChanges = ProtocolChanges.Version70300; - } else if ( value >= m_Version70160 ) { - _ProtocolChanges = ProtocolChanges.Version70160; - } else if ( value >= m_Version70130 ) { - _ProtocolChanges = ProtocolChanges.Version70130; - } else if ( value >= m_Version7090 ) { - _ProtocolChanges = ProtocolChanges.Version7090; - } else if ( value >= m_Version7000 ) { - _ProtocolChanges = ProtocolChanges.Version7000; - } else if ( value >= m_Version60142 ) { - _ProtocolChanges = ProtocolChanges.Version60142; - } else if ( value >= m_Version6017 ) { - _ProtocolChanges = ProtocolChanges.Version6017; - } else if ( value >= m_Version6000 ) { - _ProtocolChanges = ProtocolChanges.Version6000; - } else if ( value >= m_Version502b ) { - _ProtocolChanges = ProtocolChanges.Version502b; - } else if ( value >= m_Version500a ) { - _ProtocolChanges = ProtocolChanges.Version500a; - } else if ( value >= m_Version407a ) { - _ProtocolChanges = ProtocolChanges.Version407a; - } else if ( value >= m_Version400a ) { - _ProtocolChanges = ProtocolChanges.Version400a; - } - } - } - - private static ClientVersion m_Version400a = new ClientVersion( "4.0.0a" ); - private static ClientVersion m_Version407a = new ClientVersion( "4.0.7a" ); - private static ClientVersion m_Version500a = new ClientVersion( "5.0.0a" ); - private static ClientVersion m_Version502b = new ClientVersion( "5.0.2b" ); - private static ClientVersion m_Version6000 = new ClientVersion( "6.0.0.0" ); - private static ClientVersion m_Version6017 = new ClientVersion( "6.0.1.7" ); - private static ClientVersion m_Version60142 = new ClientVersion( "6.0.14.2" ); - private static ClientVersion m_Version7000 = new ClientVersion( "7.0.0.0" ); - private static ClientVersion m_Version7090 = new ClientVersion( "7.0.9.0" ); - private static ClientVersion m_Version70130 = new ClientVersion( "7.0.13.0" ); - private static ClientVersion m_Version70160 = new ClientVersion( "7.0.16.0" ); - private static ClientVersion m_Version70300 = new ClientVersion( "7.0.30.0" ); - private static ClientVersion m_Version70331 = new ClientVersion( "7.0.33.1" ); - private static ClientVersion m_Version704565 = new ClientVersion( "7.0.45.65" ); - - private ProtocolChanges _ProtocolChanges; - - private enum ProtocolChanges { - NewSpellbook = 0x00000001, - DamagePacket = 0x00000002, - Unpack = 0x00000004, - BuffIcon = 0x00000008, - NewHaven = 0x00000010, - ContainerGridLines = 0x00000020, - ExtendedSupportedFeatures = 0x00000040, - StygianAbyss = 0x00000080, - HighSeas = 0x00000100, - NewCharacterList = 0x00000200, - NewCharacterCreation = 0x00000400, - ExtendedStatus = 0x00000800, - NewMobileIncoming = 0x00001000, - NewSecureTrading = 0x00002000, - - Version400a = NewSpellbook, - Version407a = Version400a | DamagePacket, - Version500a = Version407a | Unpack, - Version502b = Version500a | BuffIcon, - Version6000 = Version502b | NewHaven, - Version6017 = Version6000 | ContainerGridLines, - Version60142 = Version6017 | ExtendedSupportedFeatures, - Version7000 = Version60142 | StygianAbyss, - Version7090 = Version7000 | HighSeas, - Version70130 = Version7090 | NewCharacterList, - Version70160 = Version70130 | NewCharacterCreation, - Version70300 = Version70160 | ExtendedStatus, - Version70331 = Version70300 | NewMobileIncoming, - Version704565 = Version70331 | NewSecureTrading - } - - public bool NewSpellbook => ((_ProtocolChanges & ProtocolChanges.NewSpellbook) != 0); - public bool DamagePacket => ((_ProtocolChanges & ProtocolChanges.DamagePacket) != 0); - public bool Unpack => ((_ProtocolChanges & ProtocolChanges.Unpack) != 0); - public bool BuffIcon => ((_ProtocolChanges & ProtocolChanges.BuffIcon) != 0); - public bool NewHaven => ((_ProtocolChanges & ProtocolChanges.NewHaven) != 0); - public bool ContainerGridLines => ((_ProtocolChanges & ProtocolChanges.ContainerGridLines) != 0); - public bool ExtendedSupportedFeatures => ((_ProtocolChanges & ProtocolChanges.ExtendedSupportedFeatures) != 0); - public bool StygianAbyss => ((_ProtocolChanges & ProtocolChanges.StygianAbyss) != 0); - public bool HighSeas => ((_ProtocolChanges & ProtocolChanges.HighSeas) != 0); - public bool NewCharacterList => ((_ProtocolChanges & ProtocolChanges.NewCharacterList) != 0); - public bool NewCharacterCreation => ((_ProtocolChanges & ProtocolChanges.NewCharacterCreation) != 0); - public bool ExtendedStatus => ((_ProtocolChanges & ProtocolChanges.ExtendedStatus) != 0); - public bool NewMobileIncoming => ((_ProtocolChanges & ProtocolChanges.NewMobileIncoming) != 0); - public bool NewSecureTrading => ((_ProtocolChanges & ProtocolChanges.NewSecureTrading) != 0); - - public bool IsUOTDClient => ( (Flags & ClientFlags.UOTD) != 0 || ( m_Version != null && m_Version.Type == ClientType.UOTD ) ); - - public bool IsSAClient => ( m_Version != null && m_Version.Type == ClientType.SA ); - - public List Trades { get; } - - public void ValidateAllTrades() { - for ( int i = Trades.Count - 1; i >= 0; --i ) { - if ( i >= Trades.Count ) { - continue; - } - - SecureTrade trade = Trades[i]; - - if ( trade.From.Mobile.Deleted || trade.To.Mobile.Deleted || !trade.From.Mobile.Alive || !trade.To.Mobile.Alive || !trade.From.Mobile.InRange( trade.To.Mobile, 2 ) || trade.From.Mobile.Map != trade.To.Mobile.Map ) { - trade.Cancel(); - } - } - } - - public void CancelAllTrades() { - for ( int i = Trades.Count - 1; i >= 0; --i ) { - if ( i < Trades.Count ) { - Trades[i].Cancel(); - } - } - } - - public void RemoveTrade( SecureTrade trade ) { - Trades.Remove( trade ); - } - - public SecureTrade FindTrade( Mobile m ) { - for ( int i = 0; i < Trades.Count; ++i ) { - SecureTrade trade = Trades[i]; - - if ( trade.From.Mobile == m || trade.To.Mobile == m ) { - return trade; - } - } - - return null; - } - - public SecureTradeContainer FindTradeContainer( Mobile m ) { - for ( int i = 0; i < Trades.Count; ++i ) { - SecureTrade trade = Trades[i]; - - SecureTradeInfo from = trade.From; - SecureTradeInfo to = trade.To; - - if ( from.Mobile == Mobile && to.Mobile == m ) { - return from.Container; - } - - if ( from.Mobile == m && to.Mobile == Mobile ) { - return to.Container; - } - } - - return null; - } - - public SecureTradeContainer AddTrade( NetState state ) { - SecureTrade newTrade = new SecureTrade( Mobile, state.Mobile ); - - Trades.Add( newTrade ); - state.Trades.Add( newTrade ); - - return newTrade.From.Container; - } - - public bool CompressionEnabled { get; set; } - - public int Sequence { get; set; } - - public List Gumps { get; private set; } - - public List HuePickers { get; private set; } - - public List Menus { get; private set; } - - public static int GumpCap { get; set; } = 512; - - public static int HuePickerCap { get; set; } = 512; - - public static int MenuCap { get; set; } = 512; - - public void WriteConsole( string text ) { - Console.WriteLine( "Client: {0}: {1}", this, text ); - } - - public void WriteConsole( string format, params object[] args ) { - WriteConsole( string.Format( format, args ) ); - } + private MessagePump m_MessagePump; + private string m_ToString; + private ClientVersion m_Version; + + public DateTime ConnectedOn{ get; } + + public TimeSpan ConnectedFor => DateTime.UtcNow - ConnectedOn; + + internal int m_Seed; + internal int m_AuthID; + + public IPAddress Address{ get; } + + private static bool m_Paused; + + [Flags] + private enum AsyncState + { + Pending = 0x01, + Paused = 0x02 + } + + private AsyncState m_AsyncState; + private object m_AsyncLock = new object(); + + public IPacketEncoder PacketEncoder{ get; set; } + + public static NetStateCreatedCallback CreatedCallback{ get; set; } + + public bool SentFirstPacket{ get; set; } + + public bool BlockAllPackets{ get; set; } + + public ClientFlags Flags{ get; set; } + + public ClientVersion Version + { + get => m_Version; + set + { + m_Version = value; + + if (value >= m_Version704565) + _ProtocolChanges = ProtocolChanges.Version704565; + else if (value >= m_Version70331) + _ProtocolChanges = ProtocolChanges.Version70331; + else if (value >= m_Version70300) + _ProtocolChanges = ProtocolChanges.Version70300; + else if (value >= m_Version70160) + _ProtocolChanges = ProtocolChanges.Version70160; + else if (value >= m_Version70130) + _ProtocolChanges = ProtocolChanges.Version70130; + else if (value >= m_Version7090) + _ProtocolChanges = ProtocolChanges.Version7090; + else if (value >= m_Version7000) + _ProtocolChanges = ProtocolChanges.Version7000; + else if (value >= m_Version60142) + _ProtocolChanges = ProtocolChanges.Version60142; + else if (value >= m_Version6017) + _ProtocolChanges = ProtocolChanges.Version6017; + else if (value >= m_Version6000) + _ProtocolChanges = ProtocolChanges.Version6000; + else if (value >= m_Version502b) + _ProtocolChanges = ProtocolChanges.Version502b; + else if (value >= m_Version500a) + _ProtocolChanges = ProtocolChanges.Version500a; + else if (value >= m_Version407a) + _ProtocolChanges = ProtocolChanges.Version407a; + else if (value >= m_Version400a) _ProtocolChanges = ProtocolChanges.Version400a; + } + } + + private static ClientVersion m_Version400a = new ClientVersion("4.0.0a"); + private static ClientVersion m_Version407a = new ClientVersion("4.0.7a"); + private static ClientVersion m_Version500a = new ClientVersion("5.0.0a"); + private static ClientVersion m_Version502b = new ClientVersion("5.0.2b"); + private static ClientVersion m_Version6000 = new ClientVersion("6.0.0.0"); + private static ClientVersion m_Version6017 = new ClientVersion("6.0.1.7"); + private static ClientVersion m_Version60142 = new ClientVersion("6.0.14.2"); + private static ClientVersion m_Version7000 = new ClientVersion("7.0.0.0"); + private static ClientVersion m_Version7090 = new ClientVersion("7.0.9.0"); + private static ClientVersion m_Version70130 = new ClientVersion("7.0.13.0"); + private static ClientVersion m_Version70160 = new ClientVersion("7.0.16.0"); + private static ClientVersion m_Version70300 = new ClientVersion("7.0.30.0"); + private static ClientVersion m_Version70331 = new ClientVersion("7.0.33.1"); + private static ClientVersion m_Version704565 = new ClientVersion("7.0.45.65"); + + private ProtocolChanges _ProtocolChanges; + + private enum ProtocolChanges + { + NewSpellbook = 0x00000001, + DamagePacket = 0x00000002, + Unpack = 0x00000004, + BuffIcon = 0x00000008, + NewHaven = 0x00000010, + ContainerGridLines = 0x00000020, + ExtendedSupportedFeatures = 0x00000040, + StygianAbyss = 0x00000080, + HighSeas = 0x00000100, + NewCharacterList = 0x00000200, + NewCharacterCreation = 0x00000400, + ExtendedStatus = 0x00000800, + NewMobileIncoming = 0x00001000, + NewSecureTrading = 0x00002000, + + Version400a = NewSpellbook, + Version407a = Version400a | DamagePacket, + Version500a = Version407a | Unpack, + Version502b = Version500a | BuffIcon, + Version6000 = Version502b | NewHaven, + Version6017 = Version6000 | ContainerGridLines, + Version60142 = Version6017 | ExtendedSupportedFeatures, + Version7000 = Version60142 | StygianAbyss, + Version7090 = Version7000 | HighSeas, + Version70130 = Version7090 | NewCharacterList, + Version70160 = Version70130 | NewCharacterCreation, + Version70300 = Version70160 | ExtendedStatus, + Version70331 = Version70300 | NewMobileIncoming, + Version704565 = Version70331 | NewSecureTrading + } + + public bool NewSpellbook => (_ProtocolChanges & ProtocolChanges.NewSpellbook) != 0; + public bool DamagePacket => (_ProtocolChanges & ProtocolChanges.DamagePacket) != 0; + public bool Unpack => (_ProtocolChanges & ProtocolChanges.Unpack) != 0; + public bool BuffIcon => (_ProtocolChanges & ProtocolChanges.BuffIcon) != 0; + public bool NewHaven => (_ProtocolChanges & ProtocolChanges.NewHaven) != 0; + public bool ContainerGridLines => (_ProtocolChanges & ProtocolChanges.ContainerGridLines) != 0; + public bool ExtendedSupportedFeatures => (_ProtocolChanges & ProtocolChanges.ExtendedSupportedFeatures) != 0; + public bool StygianAbyss => (_ProtocolChanges & ProtocolChanges.StygianAbyss) != 0; + public bool HighSeas => (_ProtocolChanges & ProtocolChanges.HighSeas) != 0; + public bool NewCharacterList => (_ProtocolChanges & ProtocolChanges.NewCharacterList) != 0; + public bool NewCharacterCreation => (_ProtocolChanges & ProtocolChanges.NewCharacterCreation) != 0; + public bool ExtendedStatus => (_ProtocolChanges & ProtocolChanges.ExtendedStatus) != 0; + public bool NewMobileIncoming => (_ProtocolChanges & ProtocolChanges.NewMobileIncoming) != 0; + public bool NewSecureTrading => (_ProtocolChanges & ProtocolChanges.NewSecureTrading) != 0; + + public bool IsUOTDClient => + (Flags & ClientFlags.UOTD) != 0 || m_Version != null && m_Version.Type == ClientType.UOTD; + + public bool IsSAClient => m_Version != null && m_Version.Type == ClientType.SA; + + public List Trades{ get; } + + public void ValidateAllTrades() + { + for (int i = Trades.Count - 1; i >= 0; --i) + { + if (i >= Trades.Count) continue; + + SecureTrade trade = Trades[i]; + + if (trade.From.Mobile.Deleted || trade.To.Mobile.Deleted || !trade.From.Mobile.Alive || + !trade.To.Mobile.Alive || !trade.From.Mobile.InRange(trade.To.Mobile, 2) || + trade.From.Mobile.Map != trade.To.Mobile.Map) trade.Cancel(); + } + } + + public void CancelAllTrades() + { + for (int i = Trades.Count - 1; i >= 0; --i) + if (i < Trades.Count) + Trades[i].Cancel(); + } + + public void RemoveTrade(SecureTrade trade) + { + Trades.Remove(trade); + } + + public SecureTrade FindTrade(Mobile m) + { + for (int i = 0; i < Trades.Count; ++i) + { + SecureTrade trade = Trades[i]; + + if (trade.From.Mobile == m || trade.To.Mobile == m) return trade; + } + + return null; + } + + public SecureTradeContainer FindTradeContainer(Mobile m) + { + for (int i = 0; i < Trades.Count; ++i) + { + SecureTrade trade = Trades[i]; + + SecureTradeInfo from = trade.From; + SecureTradeInfo to = trade.To; + + if (from.Mobile == Mobile && to.Mobile == m) return from.Container; + + if (from.Mobile == m && to.Mobile == Mobile) return to.Container; + } + + return null; + } + + public SecureTradeContainer AddTrade(NetState state) + { + SecureTrade newTrade = new SecureTrade(Mobile, state.Mobile); + + Trades.Add(newTrade); + state.Trades.Add(newTrade); + + return newTrade.From.Container; + } + + public bool CompressionEnabled{ get; set; } + + public int Sequence{ get; set; } + + public List Gumps{ get; private set; } + + public List HuePickers{ get; private set; } + + public List Menus{ get; private set; } + + public static int GumpCap{ get; set; } = 512; + + public static int HuePickerCap{ get; set; } = 512; + + public static int MenuCap{ get; set; } = 512; + + public void WriteConsole(string text) + { + Console.WriteLine("Client: {0}: {1}", this, text); + } + + public void WriteConsole(string format, params object[] args) + { + WriteConsole(string.Format(format, args)); + } + + public void AddMenu(IMenu menu) + { + if (Menus == null) Menus = new List(); + + if (Menus.Count < MenuCap) + { + Menus.Add(menu); + } + else + { + WriteConsole("Exceeded menu cap, disconnecting..."); + Dispose(); + } + } + + public void RemoveMenu(IMenu menu) + { + Menus?.Remove(menu); + } + + public void RemoveMenu(int index) + { + Menus?.RemoveAt(index); + } + + public void ClearMenus() + { + Menus?.Clear(); + } + + public void AddHuePicker(HuePicker huePicker) + { + if (HuePickers == null) HuePickers = new List(); + + if (HuePickers.Count < HuePickerCap) + { + HuePickers.Add(huePicker); + } + else + { + WriteConsole("Exceeded hue picker cap, disconnecting..."); + Dispose(); + } + } + + public void RemoveHuePicker(HuePicker huePicker) + { + HuePickers?.Remove(huePicker); + } + + public void RemoveHuePicker(int index) + { + HuePickers?.RemoveAt(index); + } + + public void ClearHuePickers() + { + HuePickers?.Clear(); + } + + public void AddGump(Gump gump) + { + if (Gumps == null) Gumps = new List(); + + if (Gumps.Count < GumpCap) + { + Gumps.Add(gump); + } + else + { + WriteConsole("Exceeded gump cap, disconnecting..."); + Dispose(); + } + } + + public void RemoveGump(Gump gump) + { + Gumps?.Remove(gump); + } + + public void RemoveGump(int index) + { + Gumps?.RemoveAt(index); + } + + public void ClearGumps() + { + Gumps?.Clear(); + } + + public void LaunchBrowser(string url) + { + Send(new MessageLocalized(Serial.MinusOne, -1, MessageType.Label, 0x35, 3, 501231, "", "")); + Send(new LaunchBrowser(url)); + } + + public CityInfo[] CityInfo{ get; set; } + + public Mobile Mobile{ get; set; } + + public ServerInfo[] ServerInfo{ get; set; } + + public IAccount Account{ get; set; } + + public override string ToString() + { + return m_ToString; + } + + public static List Instances{ get; } = new List(); + + private static BufferPool m_ReceiveBufferPool = new BufferPool("Receive", 2048, 2048); + + public NetState(Socket socket, MessagePump messagePump) + { + Socket = socket; + Buffer = new ByteQueue(); + Seeded = false; + Running = false; + m_RecvBuffer = m_ReceiveBufferPool.AcquireBuffer(); + m_MessagePump = messagePump; + Gumps = new List(); + HuePickers = new List(); + Menus = new List(); + Trades = new List(); + + m_SendQueue = new SendQueue(); + + m_NextCheckActivity = Core.TickCount + 30000; + + Instances.Add(this); + + try + { + Address = Utility.Intern(((IPEndPoint)Socket.RemoteEndPoint).Address); + m_ToString = Address.ToString(); + } + catch (Exception ex) + { + TraceException(ex); + Address = IPAddress.None; + m_ToString = "(error)"; + } + + ConnectedOn = DateTime.UtcNow; + + CreatedCallback?.Invoke(this); + } + + private bool _sending; + private object _sendL = new object(); + + public virtual void Send(Packet p) + { + if (Socket == null || BlockAllPackets) + { + p.OnSend(); + return; + } + + int length; + byte[] buffer = p.Compile(CompressionEnabled, out length); + + if (buffer != null) + { + if (buffer.Length <= 0 || length <= 0) + { + p.OnSend(); + return; + } + + PacketSendProfile prof = null; + + if (Core.Profiling) prof = PacketSendProfile.Acquire(p.GetType()); - public void AddMenu( IMenu menu ) { - if ( Menus == null ) { - Menus = new List(); - } + prof?.Start(); + + PacketEncoder?.EncodeOutgoingPacket(this, ref buffer, ref length); - if ( Menus.Count < MenuCap ) { - Menus.Add( menu ); - } else { - WriteConsole( "Exceeded menu cap, disconnecting..." ); - Dispose(); - } - } - - public void RemoveMenu( IMenu menu ) - { - Menus?.Remove( menu ); - } - - public void RemoveMenu( int index ) - { - Menus?.RemoveAt( index ); - } + try + { + SendQueue.Gram gram; - public void ClearMenus() - { - Menus?.Clear(); - } + lock (_sendL) + { + lock (m_SendQueue) + { + gram = m_SendQueue.Enqueue(buffer, length); + } - public void AddHuePicker( HuePicker huePicker ) { - if ( HuePickers == null ) { - HuePickers = new List(); - } - - if ( HuePickers.Count < HuePickerCap ) { - HuePickers.Add( huePicker ); - } else { - WriteConsole( "Exceeded hue picker cap, disconnecting..." ); - Dispose(); - } - } - - public void RemoveHuePicker( HuePicker huePicker ) - { - HuePickers?.Remove( huePicker ); - } - - public void RemoveHuePicker( int index ) - { - HuePickers?.RemoveAt( index ); - } - - public void ClearHuePickers() - { - HuePickers?.Clear(); - } - - public void AddGump( Gump gump ) { - if ( Gumps == null ) { - Gumps = new List(); - } - - if ( Gumps.Count < GumpCap ) { - Gumps.Add( gump ); - } else { - WriteConsole( "Exceeded gump cap, disconnecting..." ); - Dispose(); - } - } - - public void RemoveGump( Gump gump ) - { - Gumps?.Remove( gump ); - } - - public void RemoveGump( int index ) - { - Gumps?.RemoveAt( index ); - } - - public void ClearGumps() - { - Gumps?.Clear(); - } - - public void LaunchBrowser( string url ) { - Send( new MessageLocalized( Serial.MinusOne, -1, MessageType.Label, 0x35, 3, 501231, "", "" ) ); - Send( new LaunchBrowser( url ) ); - } - - public CityInfo[] CityInfo { get; set; } - - public Mobile Mobile { get; set; } - - public ServerInfo[] ServerInfo { get; set; } - - public IAccount Account { get; set; } - - public override string ToString() { - return m_ToString; - } - - public static List Instances { get; } = new List(); - - private static BufferPool m_ReceiveBufferPool = new BufferPool( "Receive", 2048, 2048 ); - - public NetState( Socket socket, MessagePump messagePump ) - { - Socket = socket; - Buffer = new ByteQueue(); - Seeded = false; - Running = false; - m_RecvBuffer = m_ReceiveBufferPool.AcquireBuffer(); - m_MessagePump = messagePump; - Gumps = new List(); - HuePickers = new List(); - Menus = new List(); - Trades = new List(); - - m_SendQueue = new SendQueue(); - - m_NextCheckActivity = Core.TickCount + 30000; - - Instances.Add( this ); - - try { - Address = Utility.Intern( ( ( IPEndPoint ) Socket.RemoteEndPoint ).Address ); - m_ToString = Address.ToString(); - } catch ( Exception ex ) { - TraceException( ex ); - Address = IPAddress.None; - m_ToString = "(error)"; - } - - ConnectedOn = DateTime.UtcNow; - - CreatedCallback?.Invoke( this ); - } - - private bool _sending; - private object _sendL = new object(); - - public virtual void Send( Packet p ) { - if ( Socket == null || BlockAllPackets ) { - p.OnSend(); - return; - } - - int length; - byte[] buffer = p.Compile( CompressionEnabled, out length ); - - if ( buffer != null ) { - if ( buffer.Length <= 0 || length <= 0 ) { - p.OnSend(); - return; - } - - PacketSendProfile prof = null; - - if (Core.Profiling) prof = PacketSendProfile.Acquire(p.GetType()); - - prof?.Start(); - - PacketEncoder?.EncodeOutgoingPacket( this, ref buffer, ref length ); - - try { - SendQueue.Gram gram; - - lock (_sendL) { - lock (m_SendQueue) - gram = m_SendQueue.Enqueue(buffer, length); - - if (gram != null && !_sending) { - _sending = true; + if (gram != null && !_sending) + { + _sending = true; #if NewAsyncSockets - m_SendEventArgs.SetBuffer( gram.Buffer, 0, gram.Length ); - Send_Start(); + m_SendEventArgs.SetBuffer(gram.Buffer, 0, gram.Length); + Send_Start(); #else try { m_Socket.BeginSend(gram.Buffer, 0, gram.Length, SocketFlags.None, m_OnSend, m_Socket); @@ -466,222 +494,250 @@ namespace Server.Network { Dispose(false); } #endif - } - } - } catch ( CapacityExceededException ) { - Console.WriteLine( "Client: {0}: Too much data pending, disconnecting...", this ); - Dispose( false ); - } + } + } + } + catch (CapacityExceededException) + { + Console.WriteLine("Client: {0}: Too much data pending, disconnecting...", this); + Dispose(false); + } - p.OnSend(); + p.OnSend(); - prof?.Finish( length ); - } else { - Console.WriteLine( "Client: {0}: null buffer send, disconnecting...", this ); - using ( StreamWriter op = new StreamWriter( "null_send.log", true ) ) - { - op.WriteLine( "{0} Client: {1}: null buffer send, disconnecting...", DateTime.UtcNow, this ); - op.WriteLine( new System.Diagnostics.StackTrace() ); - } - Dispose(); - } - } + prof?.Finish(length); + } + else + { + Console.WriteLine("Client: {0}: null buffer send, disconnecting...", this); + using (StreamWriter op = new StreamWriter("null_send.log", true)) + { + op.WriteLine("{0} Client: {1}: null buffer send, disconnecting...", DateTime.UtcNow, this); + op.WriteLine(new StackTrace()); + } + + Dispose(); + } + } #if NewAsyncSockets - public void Start() { - m_ReceiveEventArgs = new SocketAsyncEventArgs(); - m_ReceiveEventArgs.Completed += Receive_Completion; - m_ReceiveEventArgs.SetBuffer( m_RecvBuffer, 0, m_RecvBuffer.Length ); + public void Start() + { + m_ReceiveEventArgs = new SocketAsyncEventArgs(); + m_ReceiveEventArgs.Completed += Receive_Completion; + m_ReceiveEventArgs.SetBuffer(m_RecvBuffer, 0, m_RecvBuffer.Length); - m_SendEventArgs = new SocketAsyncEventArgs(); - m_SendEventArgs.Completed += Send_Completion; + m_SendEventArgs = new SocketAsyncEventArgs(); + m_SendEventArgs.Completed += Send_Completion; - Running = true; + Running = true; - if ( Socket == null || m_Paused ) { - return; - } + if (Socket == null || m_Paused) return; - Receive_Start(); - } + Receive_Start(); + } - private void Receive_Start() - { - try { - bool result = false; + private void Receive_Start() + { + try + { + bool result = false; - do { - lock ( m_AsyncLock ) { - if ( ( m_AsyncState & ( AsyncState.Pending | AsyncState.Paused ) ) == 0 ) { - m_AsyncState |= AsyncState.Pending; - result = !Socket.ReceiveAsync( m_ReceiveEventArgs ); + do + { + lock (m_AsyncLock) + { + if ((m_AsyncState & (AsyncState.Pending | AsyncState.Paused)) == 0) + { + m_AsyncState |= AsyncState.Pending; + result = !Socket.ReceiveAsync(m_ReceiveEventArgs); - if ( result ) - Receive_Process( m_ReceiveEventArgs ); - } - } - } while ( result ); - } catch ( Exception ex ) { - TraceException( ex ); - Dispose( false ); - } - } + if (result) + Receive_Process(m_ReceiveEventArgs); + } + } + } while (result); + } + catch (Exception ex) + { + TraceException(ex); + Dispose(false); + } + } - private void Receive_Completion( object sender, SocketAsyncEventArgs e ) - { - Receive_Process( e ); + private void Receive_Completion(object sender, SocketAsyncEventArgs e) + { + Receive_Process(e); - if ( !IsDisposing ) - Receive_Start(); - } + if (!IsDisposing) + Receive_Start(); + } - private void Receive_Process( SocketAsyncEventArgs e ) - { - int byteCount = e.BytesTransferred; + private void Receive_Process(SocketAsyncEventArgs e) + { + int byteCount = e.BytesTransferred; - if ( e.SocketError != SocketError.Success || byteCount <= 0 ) { - Dispose( false ); - return; - } + if (e.SocketError != SocketError.Success || byteCount <= 0) + { + Dispose(false); + return; + } - if ( IsDisposing ) { - return; - } + if (IsDisposing) return; - m_NextCheckActivity = Core.TickCount + 90000; + m_NextCheckActivity = Core.TickCount + 90000; - byte[] buffer = m_RecvBuffer; + byte[] buffer = m_RecvBuffer; - PacketEncoder?.DecodeIncomingPacket( this, ref buffer, ref byteCount ); + PacketEncoder?.DecodeIncomingPacket(this, ref buffer, ref byteCount); - lock ( Buffer ) - Buffer.Enqueue( buffer, 0, byteCount ); + lock (Buffer) + { + Buffer.Enqueue(buffer, 0, byteCount); + } - m_MessagePump.OnReceive( this ); + m_MessagePump.OnReceive(this); - lock ( m_AsyncLock ) { - m_AsyncState &= ~AsyncState.Pending; - } - } + lock (m_AsyncLock) + { + m_AsyncState &= ~AsyncState.Pending; + } + } - private void Send_Start() - { - try { - bool result = false; + private void Send_Start() + { + try + { + bool result = false; - do { - result = !Socket.SendAsync( m_SendEventArgs ); + do + { + result = !Socket.SendAsync(m_SendEventArgs); - if ( result ) - Send_Process( m_SendEventArgs ); - } while ( result ); - } catch ( Exception ex ) { - TraceException( ex ); - Dispose( false ); - } - } + if (result) + Send_Process(m_SendEventArgs); + } while (result); + } + catch (Exception ex) + { + TraceException(ex); + Dispose(false); + } + } - private void Send_Completion( object sender, SocketAsyncEventArgs e ) - { - Send_Process( e ); + private void Send_Completion(object sender, SocketAsyncEventArgs e) + { + Send_Process(e); - if ( IsDisposing ) - return; + if (IsDisposing) + return; - if ( CoalesceSleep >= 0 ) { - Thread.Sleep( CoalesceSleep ); - } + if (CoalesceSleep >= 0) Thread.Sleep(CoalesceSleep); - SendQueue.Gram gram; + SendQueue.Gram gram; - lock ( m_SendQueue ) { - gram = m_SendQueue.Dequeue(); + lock (m_SendQueue) + { + gram = m_SendQueue.Dequeue(); - if (gram == null && m_SendQueue.IsFlushReady) - gram = m_SendQueue.CheckFlushReady(); - } + if (gram == null && m_SendQueue.IsFlushReady) + gram = m_SendQueue.CheckFlushReady(); + } - if ( gram != null ) { - m_SendEventArgs.SetBuffer( gram.Buffer, 0, gram.Length ); - Send_Start(); - } else { - lock (_sendL) - _sending = false; - } - } + if (gram != null) + { + m_SendEventArgs.SetBuffer(gram.Buffer, 0, gram.Length); + Send_Start(); + } + else + { + lock (_sendL) + { + _sending = false; + } + } + } - private void Send_Process( SocketAsyncEventArgs e ) - { - int bytes = e.BytesTransferred; + private void Send_Process(SocketAsyncEventArgs e) + { + int bytes = e.BytesTransferred; - if ( e.SocketError != SocketError.Success || bytes <= 0 ) { - Dispose( false ); - return; - } + if (e.SocketError != SocketError.Success || bytes <= 0) + { + Dispose(false); + return; + } - m_NextCheckActivity = Core.TickCount + 90000; - } + m_NextCheckActivity = Core.TickCount + 90000; + } - public static void Pause() { - m_Paused = true; + public static void Pause() + { + m_Paused = true; - for ( int i = 0; i < Instances.Count; ++i ) { - NetState ns = Instances[i]; + for (int i = 0; i < Instances.Count; ++i) + { + NetState ns = Instances[i]; - lock ( ns.m_AsyncLock ) { - ns.m_AsyncState |= AsyncState.Paused; - } - } - } + lock (ns.m_AsyncLock) + { + ns.m_AsyncState |= AsyncState.Paused; + } + } + } - public static void Resume() { - m_Paused = false; + public static void Resume() + { + m_Paused = false; - for ( int i = 0; i < Instances.Count; ++i ) { - NetState ns = Instances[i]; + for (int i = 0; i < Instances.Count; ++i) + { + NetState ns = Instances[i]; - if ( ns.Socket == null ) { - continue; - } + if (ns.Socket == null) continue; - lock ( ns.m_AsyncLock ) { - ns.m_AsyncState &= ~AsyncState.Paused; + lock (ns.m_AsyncLock) + { + ns.m_AsyncState &= ~AsyncState.Paused; - if ( ( ns.m_AsyncState & AsyncState.Pending ) == 0 ) - ns.Receive_Start(); - } - } - } + if ((ns.m_AsyncState & AsyncState.Pending) == 0) + ns.Receive_Start(); + } + } + } - public bool Flush() { - if ( Socket == null ) - return false; + public bool Flush() + { + if (Socket == null) + return false; - lock (_sendL) { - if (_sending) - return false; + lock (_sendL) + { + if (_sending) + return false; - SendQueue.Gram gram; + SendQueue.Gram gram; - lock ( m_SendQueue ) { - if (!m_SendQueue.IsFlushReady) - return false; + lock (m_SendQueue) + { + if (!m_SendQueue.IsFlushReady) + return false; - gram = m_SendQueue.CheckFlushReady(); - } + gram = m_SendQueue.CheckFlushReady(); + } - if ( gram != null ) { - _sending = true; - m_SendEventArgs.SetBuffer( gram.Buffer, 0, gram.Length ); - Send_Start(); - } - } + if (gram != null) + { + _sending = true; + m_SendEventArgs.SetBuffer(gram.Buffer, 0, gram.Length); + Send_Start(); + } + } - return false; - } + return false; + } #else - public void Start() { m_OnReceive = new AsyncCallback( OnReceive ); m_OnSend = new AsyncCallback( OnSend ); @@ -860,224 +916,255 @@ namespace Server.Network { } #endif - public PacketHandler GetHandler( int packetID ) - { - if ( ContainerGridLines ) - return PacketHandlers.Get6017Handler( packetID ); - return PacketHandlers.GetHandler( packetID ); - } + public PacketHandler GetHandler(int packetID) + { + if (ContainerGridLines) + return PacketHandlers.Get6017Handler(packetID); + return PacketHandlers.GetHandler(packetID); + } - public static void FlushAll() { - if (Instances.Count >= 1024) - Parallel.ForEach(Instances, ns => ns.Flush()); - else - for ( int i = 0; i < Instances.Count; ++i ) { - Instances[i].Flush(); - } - } + public static void FlushAll() + { + if (Instances.Count >= 1024) + Parallel.ForEach(Instances, ns => ns.Flush()); + else + for (int i = 0; i < Instances.Count; ++i) + Instances[i].Flush(); + } - public static int CoalesceSleep { get; set; } = -1; + public static int CoalesceSleep{ get; set; } = -1; - private long m_NextCheckActivity; + private long m_NextCheckActivity; - public void CheckAlive(long curTicks) { - if ( Socket == null ) - return; + public void CheckAlive(long curTicks) + { + if (Socket == null) + return; - if (m_NextCheckActivity - curTicks >= 0) { - return; - } + if (m_NextCheckActivity - curTicks >= 0) return; - Console.WriteLine( "Client: {0}: Disconnecting due to inactivity...", this ); + Console.WriteLine("Client: {0}: Disconnecting due to inactivity...", this); - Dispose(); - } + Dispose(); + } - public static void TraceException( Exception ex ) { - if (!Core.Debug) - return; + public static void TraceException(Exception ex) + { + if (!Core.Debug) + return; - try { - using ( StreamWriter op = new StreamWriter( "network-errors.log", true ) ) { - op.WriteLine("# {0}", DateTime.UtcNow); + try + { + using (StreamWriter op = new StreamWriter("network-errors.log", true)) + { + op.WriteLine("# {0}", DateTime.UtcNow); - op.WriteLine( ex ); + op.WriteLine(ex); - op.WriteLine(); - op.WriteLine(); - } - } catch { - } + op.WriteLine(); + op.WriteLine(); + } + } + catch + { + } - try { - Console.WriteLine( ex ); - } catch { - } - } + try + { + Console.WriteLine(ex); + } + catch + { + } + } - public bool IsDisposing { get; private set; } + public bool IsDisposing{ get; private set; } - public void Dispose() { - Dispose( true ); - } + public void Dispose() + { + Dispose(true); + } - public virtual void Dispose( bool flush ) { - if ( Socket == null || IsDisposing ) { - return; - } + public virtual void Dispose(bool flush) + { + if (Socket == null || IsDisposing) return; - IsDisposing = true; + IsDisposing = true; - if ( flush ) - flush = Flush(); + if (flush) + flush = Flush(); - try { - Socket.Shutdown( SocketShutdown.Both ); - } catch ( SocketException ex ) { - TraceException( ex ); - } + try + { + Socket.Shutdown(SocketShutdown.Both); + } + catch (SocketException ex) + { + TraceException(ex); + } - try { - Socket.Close(); - } catch ( SocketException ex ) { - TraceException( ex ); - } + try + { + Socket.Close(); + } + catch (SocketException ex) + { + TraceException(ex); + } - if ( m_RecvBuffer != null ) { - lock (m_ReceiveBufferPool) - m_ReceiveBufferPool.ReleaseBuffer( m_RecvBuffer ); - } + if (m_RecvBuffer != null) + lock (m_ReceiveBufferPool) + { + m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer); + } - Socket = null; + Socket = null; - Buffer = null; - m_RecvBuffer = null; + Buffer = null; + m_RecvBuffer = null; #if NewAsyncSockets - m_ReceiveEventArgs = null; - m_SendEventArgs = null; + m_ReceiveEventArgs = null; + m_SendEventArgs = null; #else m_OnReceive = null; m_OnSend = null; #endif - Running = false; + Running = false; - lock (m_Disposed) - m_Disposed.Enqueue( this ); + lock (m_Disposed) + { + m_Disposed.Enqueue(this); + } - lock (m_SendQueue) - if ( /*!flush &&*/ !m_SendQueue.IsEmpty ) { - m_SendQueue.Clear(); - } - } + lock (m_SendQueue) + { + if ( /*!flush &&*/ !m_SendQueue.IsEmpty) + m_SendQueue.Clear(); + } + } - public static void Initialize() { - Timer.DelayCall( TimeSpan.FromMinutes( 1.0 ), TimeSpan.FromMinutes( 1.5 ), CheckAllAlive ); - } + public static void Initialize() + { + Timer.DelayCall(TimeSpan.FromMinutes(1.0), TimeSpan.FromMinutes(1.5), CheckAllAlive); + } - public static void CheckAllAlive() { - try { - long curTicks = Core.TickCount; + public static void CheckAllAlive() + { + try + { + long curTicks = Core.TickCount; - if (Instances.Count >= 1024) - Parallel.ForEach(Instances, ns => ns.CheckAlive(curTicks)); - else - for ( int i = 0; i < Instances.Count; ++i ) { - Instances[i].CheckAlive(curTicks); - } - } catch ( Exception ex ) { - TraceException( ex ); - } - } + if (Instances.Count >= 1024) + Parallel.ForEach(Instances, ns => ns.CheckAlive(curTicks)); + else + for (int i = 0; i < Instances.Count; ++i) + Instances[i].CheckAlive(curTicks); + } + catch (Exception ex) + { + TraceException(ex); + } + } - private static Queue m_Disposed = new Queue(); + private static Queue m_Disposed = new Queue(); - public static void ProcessDisposedQueue() { - lock (m_Disposed) { - int breakout = 0; + public static void ProcessDisposedQueue() + { + lock (m_Disposed) + { + int breakout = 0; - while ( breakout < 200 && m_Disposed.Count > 0 ) { - ++breakout; - NetState ns = m_Disposed.Dequeue(); + while (breakout < 200 && m_Disposed.Count > 0) + { + ++breakout; + NetState ns = m_Disposed.Dequeue(); - Mobile m = ns.Mobile; - IAccount a = ns.Account; + Mobile m = ns.Mobile; + IAccount a = ns.Account; - if ( m != null ) { - m.NetState = null; - ns.Mobile = null; - } + if (m != null) + { + m.NetState = null; + ns.Mobile = null; + } - ns.Gumps.Clear(); - ns.Menus.Clear(); - ns.HuePickers.Clear(); - ns.Account = null; - ns.ServerInfo = null; - ns.CityInfo = null; + ns.Gumps.Clear(); + ns.Menus.Clear(); + ns.HuePickers.Clear(); + ns.Account = null; + ns.ServerInfo = null; + ns.CityInfo = null; - Instances.Remove( ns ); + Instances.Remove(ns); - if ( a != null ) { - ns.WriteConsole( "Disconnected. [{0} Online] [{1}]", Instances.Count, a ); - } else { - ns.WriteConsole( "Disconnected. [{0} Online]", Instances.Count ); - } - } - } - } + if (a != null) + ns.WriteConsole("Disconnected. [{0} Online] [{1}]", Instances.Count, a); + else + ns.WriteConsole("Disconnected. [{0} Online]", Instances.Count); + } + } + } - public bool Running { get; private set; } + public bool Running{ get; private set; } - public bool Seeded { get; set; } + public bool Seeded{ get; set; } - public Socket Socket { get; private set; } + public Socket Socket{ get; private set; } - public ByteQueue Buffer { get; private set; } + public ByteQueue Buffer{ get; private set; } - public ExpansionInfo ExpansionInfo { - get { - for ( int i = ExpansionInfo.Table.Length - 1; i >= 0; i-- ) { - ExpansionInfo info = ExpansionInfo.Table[i]; + public ExpansionInfo ExpansionInfo + { + get + { + for (int i = ExpansionInfo.Table.Length - 1; i >= 0; i--) + { + ExpansionInfo info = ExpansionInfo.Table[i]; - if ( ( info.RequiredClient != null && Version >= info.RequiredClient ) || ( ( Flags & info.ClientFlags ) != 0 ) ) { - return info; - } - } + if (info.RequiredClient != null && Version >= info.RequiredClient || (Flags & info.ClientFlags) != 0) + return info; + } - return ExpansionInfo.GetInfo( Expansion.None ); - } - } + return ExpansionInfo.GetInfo(Expansion.None); + } + } - public Expansion Expansion => ( Expansion ) ExpansionInfo.ID; + public Expansion Expansion => (Expansion)ExpansionInfo.ID; - public bool SupportsExpansion( ExpansionInfo info, bool checkCoreExpansion ) { - if ( info == null || ( checkCoreExpansion && ( int ) Core.Expansion < info.ID ) ) - return false; + public bool SupportsExpansion(ExpansionInfo info, bool checkCoreExpansion) + { + if (info == null || checkCoreExpansion && (int)Core.Expansion < info.ID) + return false; - if ( info.RequiredClient != null ) - return ( Version >= info.RequiredClient ); + if (info.RequiredClient != null) + return Version >= info.RequiredClient; - return ( ( Flags & info.ClientFlags ) != 0 ); - } + return (Flags & info.ClientFlags) != 0; + } - public bool SupportsExpansion( Expansion ex, bool checkCoreExpansion ) { - return SupportsExpansion( ExpansionInfo.GetInfo( ex ), checkCoreExpansion ); - } + public bool SupportsExpansion(Expansion ex, bool checkCoreExpansion) + { + return SupportsExpansion(ExpansionInfo.GetInfo(ex), checkCoreExpansion); + } - public bool SupportsExpansion( Expansion ex ) { - return SupportsExpansion( ex, true ); - } + public bool SupportsExpansion(Expansion ex) + { + return SupportsExpansion(ex, true); + } - public bool SupportsExpansion( ExpansionInfo info ) { - return SupportsExpansion( info, true ); - } + public bool SupportsExpansion(ExpansionInfo info) + { + return SupportsExpansion(info, true); + } - public int CompareTo( NetState other ) { - if ( other == null ) - return 1; + public int CompareTo(NetState other) + { + if (other == null) + return 1; - return m_ToString.CompareTo( other.m_ToString ); - } - } -} + return m_ToString.CompareTo(other.m_ToString); + } + } +} \ No newline at end of file diff --git a/Server/Network/PacketHandler.cs b/Server/Network/PacketHandler.cs index 844cedacb..f2268a65e 100644 --- a/Server/Network/PacketHandler.cs +++ b/Server/Network/PacketHandler.cs @@ -20,27 +20,28 @@ namespace Server.Network { - public delegate void OnPacketReceive( NetState state, PacketReader pvSrc ); - public delegate bool ThrottlePacketCallback( NetState state ); + public delegate void OnPacketReceive(NetState state, PacketReader pvSrc); - public class PacketHandler - { - public PacketHandler( int packetID, int length, bool ingame, OnPacketReceive onReceive ) - { - PacketID = packetID; - Length = length; - Ingame = ingame; - OnReceive = onReceive; - } + public delegate bool ThrottlePacketCallback(NetState state); - public int PacketID { get; } + public class PacketHandler + { + public PacketHandler(int packetID, int length, bool ingame, OnPacketReceive onReceive) + { + PacketID = packetID; + Length = length; + Ingame = ingame; + OnReceive = onReceive; + } - public int Length { get; } + public int PacketID{ get; } - public OnPacketReceive OnReceive { get; } + public int Length{ get; } - public ThrottlePacketCallback ThrottleCallback { get; set; } + public OnPacketReceive OnReceive{ get; } - public bool Ingame { get; } - } + public ThrottlePacketCallback ThrottleCallback{ get; set; } + + public bool Ingame{ get; } + } } \ No newline at end of file diff --git a/Server/Network/PacketHandlers.cs b/Server/Network/PacketHandlers.cs index 2b27156f4..ae0fe9bf9 100644 --- a/Server/Network/PacketHandlers.cs +++ b/Server/Network/PacketHandlers.cs @@ -22,2660 +22,2696 @@ using System; using System.Collections.Generic; using System.IO; using Server.Accounting; +using Server.ContextMenus; +using Server.Diagnostics; using Server.Gumps; -using Server.Targeting; +using Server.HuePickers; using Server.Items; using Server.Menus; using Server.Mobiles; using Server.Prompts; -using Server.HuePickers; -using Server.ContextMenus; -using Server.Diagnostics; +using Server.Targeting; using CV = Server.ClientVersion; namespace Server.Network { - public enum MessageType - { - Regular = 0x00, - System = 0x01, - Emote = 0x02, - Label = 0x06, - Focus = 0x07, - Whisper = 0x08, - Yell = 0x09, - Spell = 0x0A, - - Guild = 0x0D, - Alliance = 0x0E, - Command = 0x0F, - - Encoded = 0xC0 - } - - public static class PacketHandlers - { - private static PacketHandler[] m_6017Handlers; - - private static PacketHandler[] m_ExtendedHandlersLow; - private static Dictionary m_ExtendedHandlersHigh; - - private static EncodedPacketHandler[] m_EncodedHandlersLow; - private static Dictionary m_EncodedHandlersHigh; - - public static PacketHandler[] Handlers { get; } - - static PacketHandlers() - { - Handlers = new PacketHandler[0x100]; - m_6017Handlers = new PacketHandler[0x100]; - - m_ExtendedHandlersLow = new PacketHandler[0x100]; - m_ExtendedHandlersHigh = new Dictionary(); - - m_EncodedHandlersLow = new EncodedPacketHandler[0x100]; - m_EncodedHandlersHigh = new Dictionary(); - - Register( 0x00, 104, false, CreateCharacter ); - Register( 0x01, 5, false, Disconnect ); - Register( 0x02, 7, true, MovementReq ); - Register( 0x03, 0, true, AsciiSpeech ); - Register( 0x04, 2, true, GodModeRequest ); - Register( 0x05, 5, true, AttackReq ); - Register( 0x06, 5, true, UseReq ); - Register( 0x07, 7, true, LiftReq ); - Register( 0x08, 14, true, DropReq ); - Register( 0x09, 5, true, LookReq ); - Register( 0x0A, 11, true, Edit ); - Register( 0x12, 0, true, TextCommand ); - Register( 0x13, 10, true, EquipReq ); - Register( 0x14, 6, true, ChangeZ ); - Register( 0x22, 3, true, Resynchronize ); - Register( 0x2C, 2, true, DeathStatusResponse ); - Register( 0x34, 10, true, MobileQuery ); - Register( 0x3A, 0, true, ChangeSkillLock ); - Register( 0x3B, 0, true, VendorBuyReply ); - Register( 0x47, 11, true, NewTerrain ); - Register( 0x48, 73, true, NewAnimData ); - Register( 0x58, 106, true, NewRegion ); - Register( 0x5D, 73, false, PlayCharacter ); - Register( 0x61, 9, true, DeleteStatic ); - Register( 0x6C, 19, true, TargetResponse ); - Register( 0x6F, 0, true, SecureTrade ); - Register( 0x72, 5, true, SetWarMode ); - Register( 0x73, 2, false, PingReq ); - Register( 0x75, 35, true, RenameRequest ); - Register( 0x79, 9, true, ResourceQuery ); - Register( 0x7E, 2, true, GodviewQuery ); - Register( 0x7D, 13, true, MenuResponse ); - Register( 0x80, 62, false, AccountLogin ); - Register( 0x83, 39, false, DeleteCharacter ); - Register( 0x91, 65, false, GameLogin ); - Register( 0x95, 9, true, HuePickerResponse ); - Register( 0x96, 0, true, GameCentralMoniter ); - Register( 0x98, 0, true, MobileNameRequest ); - Register( 0x9A, 0, true, AsciiPromptResponse ); - Register( 0x9B, 258, true, HelpRequest ); - Register( 0x9D, 51, true, GMSingle ); - Register( 0x9F, 0, true, VendorSellReply ); - Register( 0xA0, 3, false, PlayServer ); - Register( 0xA4, 149, false, SystemInfo ); - Register( 0xA7, 4, true, RequestScrollWindow ); - Register( 0xAD, 0, true, UnicodeSpeech ); - Register( 0xB1, 0, true, DisplayGumpResponse ); - Register( 0xB5, 64, true, ChatRequest ); - Register( 0xB6, 9, true, ObjectHelpRequest ); - Register( 0xB8, 0, true, ProfileReq ); - Register( 0xBB, 9, false, AccountID ); - Register( 0xBD, 0, false, ClientVersion ); - Register( 0xBE, 0, true, AssistVersion ); - Register( 0xBF, 0, true, ExtendedCommand ); - Register( 0xC2, 0, true, UnicodePromptResponse ); - Register( 0xC8, 2, true, SetUpdateRange ); - Register( 0xC9, 6, true, TripTime ); - Register( 0xCA, 6, true, UTripTime ); - Register( 0xCF, 0, false, AccountLogin ); - Register( 0xD0, 0, true, ConfigurationFile ); - Register( 0xD1, 2, true, LogoutReq ); - Register( 0xD6, 0, true, BatchQueryProperties ); - Register( 0xD7, 0, true, EncodedCommand ); - Register( 0xE1, 0, false, ClientType ); - Register( 0xEF, 21, false, LoginServerSeed ); - Register( 0xF4, 0, false, CrashReport ); - Register( 0xF8, 106, false, CreateCharacter70160 ); - - Register6017( 0x08, 15, true, DropReq6017 ); - - RegisterExtended( 0x05, false, ScreenSize ); - RegisterExtended( 0x06, true, PartyMessage ); - RegisterExtended( 0x07, true, QuestArrow ); - RegisterExtended( 0x09, true, DisarmRequest ); - RegisterExtended( 0x0A, true, StunRequest ); - RegisterExtended( 0x0B, false, Language ); - RegisterExtended( 0x0C, true, CloseStatus ); - RegisterExtended( 0x0E, true, Animate ); - RegisterExtended( 0x0F, false, Empty ); // What's this? - RegisterExtended( 0x10, true, QueryProperties ); - RegisterExtended( 0x13, true, ContextMenuRequest ); - RegisterExtended( 0x15, true, ContextMenuResponse ); - RegisterExtended( 0x1A, true, StatLockChange ); - RegisterExtended( 0x1C, true, CastSpell ); - RegisterExtended( 0x24, false, UnhandledBF ); - RegisterExtended( 0x2C, true, BandageTarget ); - RegisterExtended( 0x32, true, ToggleFlying ); - - RegisterEncoded( 0x19, true, SetAbility ); - RegisterEncoded( 0x28, true, GuildGumpRequest ); - - RegisterEncoded( 0x32, true, QuestGumpRequest ); - } - - public static void Register( int packetID, int length, bool ingame, OnPacketReceive onReceive ) - { - Handlers[packetID] = new PacketHandler( packetID, length, ingame, onReceive ); - - if ( m_6017Handlers[packetID] == null ) - m_6017Handlers[packetID] = new PacketHandler( packetID, length, ingame, onReceive ); - } - - public static PacketHandler GetHandler( int packetID ) - { - return Handlers[packetID]; - } - - public static void Register6017( int packetID, int length, bool ingame, OnPacketReceive onReceive ) - { - m_6017Handlers[packetID] = new PacketHandler( packetID, length, ingame, onReceive ); - } - - public static PacketHandler Get6017Handler( int packetID ) - { - return m_6017Handlers[packetID]; - } - - public static void RegisterExtended( int packetID, bool ingame, OnPacketReceive onReceive ) - { - if ( packetID >= 0 && packetID < 0x100 ) - m_ExtendedHandlersLow[packetID] = new PacketHandler( packetID, 0, ingame, onReceive ); - else - m_ExtendedHandlersHigh[packetID] = new PacketHandler( packetID, 0, ingame, onReceive ); - } - - public static PacketHandler GetExtendedHandler( int packetID ) - { - if ( packetID >= 0 && packetID < 0x100 ) - return m_ExtendedHandlersLow[packetID]; - - m_ExtendedHandlersHigh.TryGetValue( packetID, out PacketHandler handler ); - return handler; - } - - public static void RemoveExtendedHandler( int packetID ) - { - if ( packetID >= 0 && packetID < 0x100 ) - m_ExtendedHandlersLow[packetID] = null; - else - m_ExtendedHandlersHigh.Remove( packetID ); - } - - public static void RegisterEncoded( int packetID, bool ingame, OnEncodedPacketReceive onReceive ) - { - if ( packetID >= 0 && packetID < 0x100 ) - m_EncodedHandlersLow[packetID] = new EncodedPacketHandler( packetID, ingame, onReceive ); - else - m_EncodedHandlersHigh[packetID] = new EncodedPacketHandler( packetID, ingame, onReceive ); - } - - public static EncodedPacketHandler GetEncodedHandler( int packetID ) - { - if ( packetID >= 0 && packetID < 0x100 ) - return m_EncodedHandlersLow[packetID]; - - m_EncodedHandlersHigh.TryGetValue( packetID, out EncodedPacketHandler handler ); - return handler; - } - - public static void RemoveEncodedHandler( int packetID ) - { - if ( packetID >= 0 && packetID < 0x100 ) - m_EncodedHandlersLow[packetID] = null; - else - m_EncodedHandlersHigh.Remove( packetID ); - } - - public static void RegisterThrottler( int packetID, ThrottlePacketCallback t ) - { - PacketHandler ph = GetHandler( packetID ); - - if ( ph != null ) - ph.ThrottleCallback = t; - - ph = Get6017Handler( packetID ); - - if ( ph != null ) - ph.ThrottleCallback = t; - } - - private static void UnhandledBF( NetState state, PacketReader pvSrc ) - { - } - - public static void Empty( NetState state, PacketReader pvSrc ) - { - } - - public static void SetAbility( NetState state, IEntity e, EncodedReader reader ) - { - EventSink.InvokeSetAbility( new SetAbilityEventArgs( state.Mobile, reader.ReadInt32() ) ); - } - - public static void GuildGumpRequest( NetState state, IEntity e, EncodedReader reader ) - { - EventSink.InvokeGuildGumpRequest( new GuildGumpRequestArgs( state.Mobile ) ); - } - - public static void QuestGumpRequest( NetState state, IEntity e, EncodedReader reader ) - { - EventSink.InvokeQuestGumpRequest( new QuestGumpRequestArgs( state.Mobile ) ); - } - - public static void EncodedCommand( NetState state, PacketReader pvSrc ) - { - IEntity e = World.FindEntity( pvSrc.ReadInt32() ); - int packetID = pvSrc.ReadUInt16(); - - EncodedPacketHandler ph = GetEncodedHandler( packetID ); - - if ( ph != null ) - { - if ( ph.Ingame && state.Mobile == null ) - { - Console.WriteLine( "Client: {0}: Sent ingame packet (0xD7x{1:X2}) before having been attached to a mobile", state, packetID ); - state.Dispose(); - } - else if ( ph.Ingame && state.Mobile.Deleted ) - { - state.Dispose(); - } - else - { - ph.OnReceive( state, e, new EncodedReader( pvSrc ) ); - } - } - else - { - pvSrc.Trace( state ); - } - } - - public static void RenameRequest( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - Mobile targ = World.FindMobile( pvSrc.ReadInt32() ); - - if ( targ != null ) - EventSink.InvokeRenameRequest( new RenameRequestEventArgs( from, targ, pvSrc.ReadStringSafe() ) ); - } - - public static void ChatRequest( NetState state, PacketReader pvSrc ) - { - EventSink.InvokeChatRequest( new ChatRequestEventArgs( state.Mobile ) ); - } - - public static void SecureTrade( NetState state, PacketReader pvSrc ) - { - switch ( pvSrc.ReadByte() ) - { - case 1: // Cancel - { - Serial serial = pvSrc.ReadInt32(); - - if ( World.FindItem( serial ) is SecureTradeContainer cont && cont.Trade != null && (cont.Trade.From.Mobile == state.Mobile || cont.Trade.To.Mobile == state.Mobile) ) - cont.Trade.Cancel(); - - break; - } - case 2: // Check - { - Serial serial = pvSrc.ReadInt32(); - - if ( World.FindItem( serial ) is SecureTradeContainer cont ) - { - SecureTrade trade = cont.Trade; - - bool value = ( pvSrc.ReadInt32() != 0 ); - - if ( trade != null && trade.From.Mobile == state.Mobile ) - { - trade.From.Accepted = value; - trade.Update(); - } - else if ( trade != null && trade.To.Mobile == state.Mobile ) - { - trade.To.Accepted = value; - trade.Update(); - } - } - - break; - } - case 3: // Update Gold - { - Serial serial = pvSrc.ReadInt32(); - - if (World.FindItem(serial) is SecureTradeContainer cont) - { - int gold = pvSrc.ReadInt32(); - int plat = pvSrc.ReadInt32(); - - SecureTrade trade = cont.Trade; - - if (trade != null) - { - if (trade.From.Mobile == state.Mobile) - { - trade.From.Gold = gold; - trade.From.Plat = plat; - trade.UpdateFromCurrency(); - } - else if (trade.To.Mobile == state.Mobile) - { - trade.To.Gold = gold; - trade.To.Plat = plat; - trade.UpdateToCurrency(); - } - } - } - } - break; - } - } - - public static void VendorBuyReply( NetState state, PacketReader pvSrc ) - { - pvSrc.Seek( 1, SeekOrigin.Begin ); - - int msgSize = pvSrc.ReadUInt16(); - Mobile vendor = World.FindMobile( pvSrc.ReadInt32() ); - byte flag = pvSrc.ReadByte(); - - if ( vendor == null ) - { - return; - } - - if ( vendor.Deleted || !Utility.RangeCheck( vendor.Location, state.Mobile.Location, 10 ) ) - { - state.Send( new EndVendorBuy( vendor ) ); - return; - } - - if ( flag == 0x02 ) - { - msgSize -= 1+2+4+1; - - if ( (msgSize / 7) > 100 ) - return; - - List buyList = new List( msgSize / 7 ); - while ( msgSize > 0 ) - { - byte layer = pvSrc.ReadByte(); - Serial serial = pvSrc.ReadInt32(); - int amount = pvSrc.ReadInt16(); - - buyList.Add( new BuyItemResponse( serial, amount ) ); - msgSize -= 7; - } - - if ( buyList.Count > 0 && vendor is IVendor v && v.OnBuyItems( state.Mobile, buyList ) ) - state.Send( new EndVendorBuy( vendor ) ); - } - else - { - state.Send( new EndVendorBuy( vendor ) ); - } - } - - public static void VendorSellReply( NetState state, PacketReader pvSrc ) - { - Serial serial = pvSrc.ReadInt32(); - Mobile vendor = World.FindMobile( serial ); - - if ( vendor == null ) - { - return; - } - - if ( vendor.Deleted || !Utility.RangeCheck( vendor.Location, state.Mobile.Location, 10 ) ) - { - state.Send( new EndVendorSell( vendor ) ); - return; - } - - int count = pvSrc.ReadUInt16(); - if ( count < 100 && pvSrc.Size == (1+2+4+2+(count*6)) ) - { - List sellList = new List( count ); - - for (int i=0;i 0 ) - sellList.Add( new SellItemResponse( item, Amount ) ); - } - - if ( sellList.Count > 0 && vendor is IVendor v && v.OnSellItems( state.Mobile, sellList ) ) - state.Send( new EndVendorSell( vendor ) ); - } - } - - public static void DeleteCharacter( NetState state, PacketReader pvSrc ) - { - pvSrc.Seek( 30, SeekOrigin.Current ); - int index = pvSrc.ReadInt32(); - - EventSink.InvokeDeleteRequest( new DeleteRequestEventArgs( state, index ) ); - } - - public static void ResourceQuery( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - } - } - - public static void GameCentralMoniter( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - int type = pvSrc.ReadByte(); - int num1 = pvSrc.ReadInt32(); - - Console.WriteLine( "God Client: {0}: Game central moniter", state ); - Console.WriteLine( " - Type: {0}", type ); - Console.WriteLine( " - Number: {0}", num1 ); - - pvSrc.Trace( state ); - } - } - - public static void GodviewQuery( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - Console.WriteLine( "God Client: {0}: Godview query 0x{1:X}", state, pvSrc.ReadByte() ); - } - } - - public static void GMSingle( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - pvSrc.Trace( state ); - } - - public static void DeathStatusResponse( NetState state, PacketReader pvSrc ) - { - // Ignored - } - - public static void ObjectHelpRequest( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - Serial serial = pvSrc.ReadInt32(); - int unk = pvSrc.ReadByte(); - string lang = pvSrc.ReadString( 3 ); - - if ( serial.IsItem ) - { - Item item = World.FindItem( serial ); - - if ( item != null && from.Map == item.Map && Utility.InUpdateRange( item.GetWorldLocation(), from.Location ) && from.CanSee( item ) ) - item.OnHelpRequest( from ); - } - else if ( serial.IsMobile ) - { - Mobile m = World.FindMobile( serial ); - - if ( m != null && from.Map == m.Map && Utility.InUpdateRange( m.Location, from.Location ) && from.CanSee( m ) ) - m.OnHelpRequest( m ); - } - } - - public static void MobileNameRequest( NetState state, PacketReader pvSrc ) - { - Mobile m = World.FindMobile( pvSrc.ReadInt32() ); - - if ( m != null && Utility.InUpdateRange( state.Mobile, m ) && state.Mobile.CanSee( m ) ) - state.Send( new MobileName( m ) ); - } - - public static void RequestScrollWindow( NetState state, PacketReader pvSrc ) - { - int lastTip = pvSrc.ReadInt16(); - int type = pvSrc.ReadByte(); - } - - public static void AttackReq( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - Mobile m = World.FindMobile( pvSrc.ReadInt32() ); - - if ( m != null ) - from.Attack( m ); - } - - public static void HuePickerResponse( NetState state, PacketReader pvSrc ) { - int serial = pvSrc.ReadInt32(); - int value = pvSrc.ReadInt16(); - int hue = pvSrc.ReadInt16() & 0x3FFF; - - hue = Utility.ClipDyedHue( hue ); - - foreach ( HuePicker huePicker in state.HuePickers ) { - if ( huePicker.Serial == serial ) { - state.RemoveHuePicker( huePicker ); - - huePicker.OnResponse( hue ); - - break; - } - } - } - - public static void TripTime( NetState state, PacketReader pvSrc ) - { - int unk1 = pvSrc.ReadByte(); - int unk2 = pvSrc.ReadInt32(); - - state.Send( new TripTimeResponse( unk1 ) ); - } - - public static void UTripTime( NetState state, PacketReader pvSrc ) - { - int unk1 = pvSrc.ReadByte(); - int unk2 = pvSrc.ReadInt32(); - - state.Send( new UTripTimeResponse( unk1 ) ); - } - - public static void ChangeZ( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int z = pvSrc.ReadSByte(); - - Console.WriteLine( "God Client: {0}: Change Z ({1}, {2}, {3})", state, x, y, z ); - } - } - - public static void SystemInfo( NetState state, PacketReader pvSrc ) - { - int v1 = pvSrc.ReadByte(); - int v2 = pvSrc.ReadUInt16(); - int v3 = pvSrc.ReadByte(); - string s1 = pvSrc.ReadString( 32 ); - string s2 = pvSrc.ReadString( 32 ); - string s3 = pvSrc.ReadString( 32 ); - string s4 = pvSrc.ReadString( 32 ); - int v4 = pvSrc.ReadUInt16(); - int v5 = pvSrc.ReadUInt16(); - int v6 = pvSrc.ReadInt32(); - int v7 = pvSrc.ReadInt32(); - int v8 = pvSrc.ReadInt32(); - } - - public static void Edit( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - int type = pvSrc.ReadByte(); // 10 = static, 7 = npc, 4 = dynamic - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int id = pvSrc.ReadInt16(); - int z = pvSrc.ReadSByte(); - int hue = pvSrc.ReadUInt16(); - - Console.WriteLine( "God Client: {0}: Edit {6} ({1}, {2}, {3}) 0x{4:X} (0x{5:X})", state, x, y, z, id, hue, type ); - } - } - - public static void DeleteStatic( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int z = pvSrc.ReadInt16(); - int id = pvSrc.ReadUInt16(); - - Console.WriteLine( "God Client: {0}: Delete Static ({1}, {2}, {3}) 0x{4:X}", state, x, y, z, id ); - } - } - - public static void NewAnimData( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - Console.WriteLine( "God Client: {0}: New tile animation", state ); - - pvSrc.Trace( state ); - } - } - - public static void NewTerrain( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int id = pvSrc.ReadUInt16(); - int width = pvSrc.ReadInt16(); - int height = pvSrc.ReadInt16(); - - Console.WriteLine( "God Client: {0}: New Terrain ({1}, {2})+({3}, {4}) 0x{5:X4}", state, x, y, width, height, id ); - } - } - - public static void NewRegion( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - string name = pvSrc.ReadString( 40 ); - int unk = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int width = pvSrc.ReadInt16(); - int height = pvSrc.ReadInt16(); - int zStart = pvSrc.ReadInt16(); - int zEnd = pvSrc.ReadInt16(); - string desc = pvSrc.ReadString( 40 ); - int soundFX = pvSrc.ReadInt16(); - int music = pvSrc.ReadInt16(); - int nightFX = pvSrc.ReadInt16(); - int dungeon = pvSrc.ReadByte(); - int light = pvSrc.ReadInt16(); - - Console.WriteLine( "God Client: {0}: New Region '{1}' ('{2}')", state, name, desc ); - } - } - - public static void AccountID( NetState state, PacketReader pvSrc ) - { - } - - public static bool VerifyGC( NetState state ) - { - if ( state.Mobile == null || state.Mobile.AccessLevel <= AccessLevel.Counselor ) - { - if ( state.Running ) - Console.WriteLine( "Warning: {0}: Player using godclient, disconnecting", state ); - - state.Dispose(); - return false; - } - - return true; - } - - public static void TextCommand( NetState state, PacketReader pvSrc ) - { - int type = pvSrc.ReadByte(); - string command = pvSrc.ReadString(); - - Mobile m = state.Mobile; - - switch ( type ) - { - case 0x00: // Go - { - if ( VerifyGC( state ) ) - { - try - { - string[] split = command.Split( ' ' ); - - int x = Utility.ToInt32( split[0] ); - int y = Utility.ToInt32( split[1] ); - - int z; - - if ( split.Length >= 3 ) - z = Utility.ToInt32( split[2] ); - else if ( m.Map != null ) - z = m.Map.GetAverageZ( x, y ); - else - z = 0; - - m.Location = new Point3D( x, y, z ); - } - catch - { - } - } - - break; - } - case 0xC7: // Animate - { - EventSink.InvokeAnimateRequest( new AnimateRequestEventArgs( m, command ) ); - - break; - } - case 0x24: // Use skill - { - if ( !int.TryParse( command.Split( ' ' )[0], out int skillIndex ) ) - break; - - Skills.UseSkill( m, skillIndex ); - - break; - } - case 0x43: // Open spellbook - { - if ( !int.TryParse( command, out int booktype ) ) - booktype = 1; - - EventSink.InvokeOpenSpellbookRequest( new OpenSpellbookRequestEventArgs( m, booktype ) ); - - break; - } - case 0x27: // Cast spell from book - { - string[] split = command.Split( ' ' ); - - if ( split.Length > 0 ) - { - int spellID = Utility.ToInt32( split[0] ) - 1; - int serial = split.Length > 1 ? Utility.ToInt32( split[1] ) : -1; - - EventSink.InvokeCastSpellRequest( new CastSpellRequestEventArgs( m, spellID, World.FindItem( serial ) ) ); - } - - break; - } - case 0x58: // Open door - { - EventSink.InvokeOpenDoorMacroUsed( new OpenDoorMacroEventArgs( m ) ); - - break; - } - case 0x56: // Cast spell from macro - { - int spellID = Utility.ToInt32( command ) - 1; - - EventSink.InvokeCastSpellRequest( new CastSpellRequestEventArgs( m, spellID, null ) ); - - break; - } - case 0xF4: // Invoke virtues from macro - { - int virtueID = Utility.ToInt32( command ) - 1; - - EventSink.InvokeVirtueMacroRequest( new VirtueMacroRequestEventArgs( m, virtueID ) ); - - break; - } - case 0x2F: // Old scroll double click - { - /* - * This command is still sent for items 0xEF3 - 0xEF9 - * - * Command is one of three, depending on the item ID of the scroll: - * - [scroll serial] - * - [scroll serial] [target serial] - * - [scroll serial] [x] [y] [z] - */ - break; - } - default: - { - Console.WriteLine( "Client: {0}: Unknown text-command type 0x{1:X2}: {2}", state, type, command ); - break; - } - } - } - - public static void GodModeRequest( NetState state, PacketReader pvSrc ) - { - if ( VerifyGC( state ) ) - { - state.Send( new GodModeReply( pvSrc.ReadBoolean() ) ); - } - } - - public static void AsciiPromptResponse( NetState state, PacketReader pvSrc ) - { - int serial = pvSrc.ReadInt32(); - int prompt = pvSrc.ReadInt32(); - int type = pvSrc.ReadInt32(); - string text = pvSrc.ReadStringSafe(); - - if ( text.Length > 128 ) - return; - - Mobile from = state.Mobile; - Prompt p = from.Prompt; - - if ( p != null && p.Serial == serial && p.Serial == prompt ) - { - from.Prompt = null; - - if ( type == 0 ) - p.OnCancel( from ); - else - p.OnResponse( from, text ); - } - } - - public static void UnicodePromptResponse( NetState state, PacketReader pvSrc ) - { - int serial = pvSrc.ReadInt32(); - int prompt = pvSrc.ReadInt32(); - int type = pvSrc.ReadInt32(); - string lang = pvSrc.ReadString( 4 ); - string text = pvSrc.ReadUnicodeStringLESafe(); - - if ( text.Length > 128 ) - return; - - Mobile from = state.Mobile; - Prompt p = from.Prompt; - - if ( p != null && p.Serial == serial && p.Serial == prompt ) - { - from.Prompt = null; - - if ( type == 0 ) - p.OnCancel( from ); - else - p.OnResponse( from, text ); - } - } - - public static void MenuResponse( NetState state, PacketReader pvSrc ) { - int serial = pvSrc.ReadInt32(); - int menuID = pvSrc.ReadInt16(); // unused in our implementation - int index = pvSrc.ReadInt16(); - int itemID = pvSrc.ReadInt16(); - int hue = pvSrc.ReadInt16(); - - index -= 1; // convert from 1-based to 0-based - - foreach ( IMenu menu in state.Menus ) { - if ( menu.Serial == serial ) { - state.RemoveMenu( menu ); - - if ( index >= 0 && index < menu.EntryLength ) { - menu.OnResponse( state, index ); - } else { - menu.OnCancel( state ); - } - - break; - } - } - } - - public static void ProfileReq( NetState state, PacketReader pvSrc ) - { - int type = pvSrc.ReadByte(); - Serial serial = pvSrc.ReadInt32(); - - Mobile beholder = state.Mobile; - Mobile beheld = World.FindMobile( serial ); - - if ( beheld == null ) - return; - - switch ( type ) - { - case 0x00: // display request - { - EventSink.InvokeProfileRequest( new ProfileRequestEventArgs( beholder, beheld ) ); - - break; - } - case 0x01: // edit request - { - pvSrc.ReadInt16(); // Skip - int length = pvSrc.ReadUInt16(); - - if ( length > 511 ) - return; - - string text = pvSrc.ReadUnicodeString( length ); - - EventSink.InvokeChangeProfileRequest( new ChangeProfileRequestEventArgs( beholder, beheld, text ) ); - - break; - } - } - } - - public static void Disconnect( NetState state, PacketReader pvSrc ) - { - int minusOne = pvSrc.ReadInt32(); - } - - public static void LiftReq( NetState state, PacketReader pvSrc ) - { - Serial serial = pvSrc.ReadInt32(); - int amount = pvSrc.ReadUInt16(); - Item item = World.FindItem( serial ); - - bool rejected; - LRReason reject; - - state.Mobile.Lift( item, amount, out rejected, out reject ); - } - - public static void EquipReq( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - Item item = from.Holding; - - bool valid = ( item != null && item.HeldBy == from && item.Map == Map.Internal ); - - from.Holding = null; - - if ( !valid ) { - return; - } - - pvSrc.Seek( 5, SeekOrigin.Current ); - Mobile to = World.FindMobile( pvSrc.ReadInt32() ); - - if ( to == null ) - to = from; - - if ( !to.AllowEquipFrom( from ) || !to.EquipItem( item ) ) - item.Bounce( from ); - - item.ClearBounce(); - } - - public static void DropReq( NetState state, PacketReader pvSrc ) - { - pvSrc.ReadInt32(); // serial, ignored - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int z = pvSrc.ReadSByte(); - Serial dest = pvSrc.ReadInt32(); - - Point3D loc = new Point3D( x, y, z ); - - Mobile from = state.Mobile; - - if ( dest.IsMobile ) - { - from.Drop( World.FindMobile( dest ), loc ); - } - else if ( dest.IsItem ) - { - Item item = World.FindItem( dest ); - - if ( item is BaseMulti multi && multi.AllowsRelativeDrop ) - { - loc.m_X += multi.X; - loc.m_Y += multi.Y; - from.Drop( loc ); - } - else - { - from.Drop( item, loc ); - } - } - else - { - from.Drop( loc ); - } - } - - public static void DropReq6017( NetState state, PacketReader pvSrc ) - { - pvSrc.ReadInt32(); // serial, ignored - int x = pvSrc.ReadInt16(); - int y = pvSrc.ReadInt16(); - int z = pvSrc.ReadSByte(); - pvSrc.ReadByte(); // Grid Location? - Serial dest = pvSrc.ReadInt32(); - - Point3D loc = new Point3D( x, y, z ); - - Mobile from = state.Mobile; - - if ( dest.IsMobile ) - { - from.Drop( World.FindMobile( dest ), loc ); - } - else if ( dest.IsItem ) - { - Item item = World.FindItem( dest ); - - if ( item is BaseMulti multi && multi.AllowsRelativeDrop ) - { - loc.m_X += multi.X; - loc.m_Y += multi.Y; - from.Drop( loc ); - } - else - { - from.Drop( item, loc ); - } - } - else - { - from.Drop( loc ); - } - } - - public static void ConfigurationFile( NetState state, PacketReader pvSrc ) - { - } - - public static void LogoutReq( NetState state, PacketReader pvSrc ) - { - state.Send( new LogoutAck() ); - } - - public static void ChangeSkillLock( NetState state, PacketReader pvSrc ) - { - Skill s = state.Mobile.Skills[pvSrc.ReadInt16()]; - - s?.SetLockNoRelay( (SkillLock)pvSrc.ReadByte() ); - } - - public static void HelpRequest( NetState state, PacketReader pvSrc ) - { - EventSink.InvokeHelpRequest( new HelpRequestEventArgs( state.Mobile ) ); - } - - public static void TargetResponse( NetState state, PacketReader pvSrc ) - { - int type = pvSrc.ReadByte(); - int targetID = pvSrc.ReadInt32(); - int flags = pvSrc.ReadByte(); - Serial serial = pvSrc.ReadInt32(); - int x = pvSrc.ReadInt16(), y = pvSrc.ReadInt16(), z = pvSrc.ReadInt16(); - int graphic = pvSrc.ReadUInt16(); - - if ( targetID == unchecked( (int) 0xDEADBEEF ) ) - return; - - Mobile from = state.Mobile; - - Target t = from.Target; - - if (t == null) - return; - - TargetProfile prof = TargetProfile.Acquire( t.GetType() ); - prof?.Start(); - - try { - if ( x == -1 && y == -1 && !serial.IsValid ) - { - // User pressed escape - t.Cancel( from, TargetCancelType.Canceled ); - } - else if ( Target.TargetIDValidation && t.TargetID != targetID ) - { - // Sanity, prevent fake target - } - else - { - object toTarget; - - if ( type == 1 ) - { - if ( graphic == 0 ) - { - toTarget = new LandTarget( new Point3D( x, y, z ), from.Map ); - } - else - { - Map map = from.Map; - - if ( map == null || map == Map.Internal ) - { - t.Cancel( from, TargetCancelType.Canceled ); - return; - } - else - { - StaticTile[] tiles = map.Tiles.GetStaticTiles( x, y, !t.DisallowMultis ); - - bool valid = false; - - if ( state.HighSeas ) { - ItemData id = TileData.ItemTable[graphic&TileData.MaxItemValue]; - if ( id.Surface ) { - z -= id.Height; - } - } - - for ( int i = 0; !valid && i < tiles.Length; ++i ) - { - if ( tiles[i].Z == z && tiles[i].ID == graphic ) - valid = true; - } - - if ( !valid ) - { - t.Cancel( from, TargetCancelType.Canceled ); - return; - } - else - { - toTarget = new StaticTarget( new Point3D( x, y, z ), graphic ); - } - } - } - } - else if ( serial.IsMobile ) - { - toTarget = World.FindMobile( serial ); - } - else if ( serial.IsItem ) - { - toTarget = World.FindItem( serial ); - } - else - { - t.Cancel( from, TargetCancelType.Canceled ); - return; - } - - t.Invoke( from, toTarget ); - } - } finally - { - prof?.Finish(); - } - } - - public static void DisplayGumpResponse( NetState state, PacketReader pvSrc ) { - int serial = pvSrc.ReadInt32(); - int typeID = pvSrc.ReadInt32(); - int buttonID = pvSrc.ReadInt32(); - - foreach ( Gump gump in state.Gumps ) { - if ( gump.Serial == serial && gump.TypeID == typeID ) { - var buttonExists = buttonID == 0; // 0 is always 'close' - - if (!buttonExists) - { - foreach (var e in gump.Entries) - { - if (e is GumpButton button && button.ButtonID == buttonID) - { - buttonExists = true; - break; - } - - if (e is GumpImageTileButton tileButton && tileButton.ButtonID == buttonID) - { - buttonExists = true; - break; - } - } - } - - if (!buttonExists) - { - state.WriteConsole("Invalid gump response, disconnecting..."); - state.Dispose(); - return; - } - - int switchCount = pvSrc.ReadInt32(); - - if ( switchCount < 0 || switchCount > gump.m_Switches ) { - state.WriteConsole( "Invalid gump response, disconnecting..." ); - state.Dispose(); - return; - } - - int[] switches = new int[switchCount]; - - for ( int j = 0; j < switches.Length; ++j ) - switches[j] = pvSrc.ReadInt32(); - - int textCount = pvSrc.ReadInt32(); - - if ( textCount < 0 || textCount > gump.m_TextEntries ) { - state.WriteConsole( "Invalid gump response, disconnecting..." ); - state.Dispose(); - return; - } - - TextRelay[] textEntries = new TextRelay[textCount]; - - for ( int j = 0; j < textEntries.Length; ++j ) { - int entryID = pvSrc.ReadUInt16(); - int textLength = pvSrc.ReadUInt16(); - - if ( textLength > 239 ) { - state.WriteConsole( "Invalid gump response, disconnecting..." ); - state.Dispose(); - return; - } - - string text = pvSrc.ReadUnicodeStringSafe( textLength ); - textEntries[j] = new TextRelay( entryID, text ); - } - - state.RemoveGump( gump ); - - GumpProfile prof = GumpProfile.Acquire( gump.GetType() ); - - prof?.Start(); - - gump.OnResponse( state, new RelayInfo( buttonID, switches, textEntries ) ); - - prof?.Finish(); - - return; - } - } - - if ( typeID == 461 ) { // Virtue gump - int switchCount = pvSrc.ReadInt32(); - - if ( buttonID == 1 && switchCount > 0 ) { - Mobile beheld = World.FindMobile( pvSrc.ReadInt32() ); - - if ( beheld != null ) { - EventSink.InvokeVirtueGumpRequest( new VirtueGumpRequestEventArgs( state.Mobile, beheld ) ); - } - } else { - Mobile beheld = World.FindMobile( serial ); - - if ( beheld != null ) { - EventSink.InvokeVirtueItemRequest( new VirtueItemRequestEventArgs( state.Mobile, beheld, buttonID ) ); - } - } - } - } + public enum MessageType + { + Regular = 0x00, + System = 0x01, + Emote = 0x02, + Label = 0x06, + Focus = 0x07, + Whisper = 0x08, + Yell = 0x09, + Spell = 0x0A, + + Guild = 0x0D, + Alliance = 0x0E, + Command = 0x0F, + + Encoded = 0xC0 + } + + public static class PacketHandlers + { + public delegate void PlayCharCallback(NetState state, bool val); + + private const int BadFood = unchecked((int)0xBAADF00D); + private const int BadUOTD = unchecked((int)0xFFCEFFCE); + + private const int m_AuthIDWindowSize = 128; + private static PacketHandler[] m_6017Handlers; + + private static PacketHandler[] m_ExtendedHandlersLow; + private static Dictionary m_ExtendedHandlersHigh; + + private static EncodedPacketHandler[] m_EncodedHandlersLow; + private static Dictionary m_EncodedHandlersHigh; + + private static int[] m_EmptyInts = new int[0]; + + private static KeywordList m_KeywordList = new KeywordList(); + + public static int[] m_ValidAnimations = + { + 6, 21, 32, 33, + 100, 101, 102, + 103, 104, 105, + 106, 107, 108, + 109, 110, 111, + 112, 113, 114, + 115, 116, 117, + 118, 119, 120, + 121, 123, 124, + 125, 126, 127, + 128 + }; + + public static PlayCharCallback ThirdPartyAuthCallback = null, ThirdPartyHackedCallback = null; + + private static byte[] m_ThirdPartyAuthKey = + { + 0x9, 0x11, 0x83, (byte)'+', 0x4, 0x17, 0x83, + 0x5, 0x24, 0x85, + 0x7, 0x17, 0x87, + 0x6, 0x19, 0x88 + }; + + private static Dictionary m_AuthIDWindow = + new Dictionary(m_AuthIDWindowSize); + + static PacketHandlers() + { + Handlers = new PacketHandler[0x100]; + m_6017Handlers = new PacketHandler[0x100]; + + m_ExtendedHandlersLow = new PacketHandler[0x100]; + m_ExtendedHandlersHigh = new Dictionary(); + + m_EncodedHandlersLow = new EncodedPacketHandler[0x100]; + m_EncodedHandlersHigh = new Dictionary(); + + Register(0x00, 104, false, CreateCharacter); + Register(0x01, 5, false, Disconnect); + Register(0x02, 7, true, MovementReq); + Register(0x03, 0, true, AsciiSpeech); + Register(0x04, 2, true, GodModeRequest); + Register(0x05, 5, true, AttackReq); + Register(0x06, 5, true, UseReq); + Register(0x07, 7, true, LiftReq); + Register(0x08, 14, true, DropReq); + Register(0x09, 5, true, LookReq); + Register(0x0A, 11, true, Edit); + Register(0x12, 0, true, TextCommand); + Register(0x13, 10, true, EquipReq); + Register(0x14, 6, true, ChangeZ); + Register(0x22, 3, true, Resynchronize); + Register(0x2C, 2, true, DeathStatusResponse); + Register(0x34, 10, true, MobileQuery); + Register(0x3A, 0, true, ChangeSkillLock); + Register(0x3B, 0, true, VendorBuyReply); + Register(0x47, 11, true, NewTerrain); + Register(0x48, 73, true, NewAnimData); + Register(0x58, 106, true, NewRegion); + Register(0x5D, 73, false, PlayCharacter); + Register(0x61, 9, true, DeleteStatic); + Register(0x6C, 19, true, TargetResponse); + Register(0x6F, 0, true, SecureTrade); + Register(0x72, 5, true, SetWarMode); + Register(0x73, 2, false, PingReq); + Register(0x75, 35, true, RenameRequest); + Register(0x79, 9, true, ResourceQuery); + Register(0x7E, 2, true, GodviewQuery); + Register(0x7D, 13, true, MenuResponse); + Register(0x80, 62, false, AccountLogin); + Register(0x83, 39, false, DeleteCharacter); + Register(0x91, 65, false, GameLogin); + Register(0x95, 9, true, HuePickerResponse); + Register(0x96, 0, true, GameCentralMoniter); + Register(0x98, 0, true, MobileNameRequest); + Register(0x9A, 0, true, AsciiPromptResponse); + Register(0x9B, 258, true, HelpRequest); + Register(0x9D, 51, true, GMSingle); + Register(0x9F, 0, true, VendorSellReply); + Register(0xA0, 3, false, PlayServer); + Register(0xA4, 149, false, SystemInfo); + Register(0xA7, 4, true, RequestScrollWindow); + Register(0xAD, 0, true, UnicodeSpeech); + Register(0xB1, 0, true, DisplayGumpResponse); + Register(0xB5, 64, true, ChatRequest); + Register(0xB6, 9, true, ObjectHelpRequest); + Register(0xB8, 0, true, ProfileReq); + Register(0xBB, 9, false, AccountID); + Register(0xBD, 0, false, ClientVersion); + Register(0xBE, 0, true, AssistVersion); + Register(0xBF, 0, true, ExtendedCommand); + Register(0xC2, 0, true, UnicodePromptResponse); + Register(0xC8, 2, true, SetUpdateRange); + Register(0xC9, 6, true, TripTime); + Register(0xCA, 6, true, UTripTime); + Register(0xCF, 0, false, AccountLogin); + Register(0xD0, 0, true, ConfigurationFile); + Register(0xD1, 2, true, LogoutReq); + Register(0xD6, 0, true, BatchQueryProperties); + Register(0xD7, 0, true, EncodedCommand); + Register(0xE1, 0, false, ClientType); + Register(0xEF, 21, false, LoginServerSeed); + Register(0xF4, 0, false, CrashReport); + Register(0xF8, 106, false, CreateCharacter70160); + + Register6017(0x08, 15, true, DropReq6017); + + RegisterExtended(0x05, false, ScreenSize); + RegisterExtended(0x06, true, PartyMessage); + RegisterExtended(0x07, true, QuestArrow); + RegisterExtended(0x09, true, DisarmRequest); + RegisterExtended(0x0A, true, StunRequest); + RegisterExtended(0x0B, false, Language); + RegisterExtended(0x0C, true, CloseStatus); + RegisterExtended(0x0E, true, Animate); + RegisterExtended(0x0F, false, Empty); // What's this? + RegisterExtended(0x10, true, QueryProperties); + RegisterExtended(0x13, true, ContextMenuRequest); + RegisterExtended(0x15, true, ContextMenuResponse); + RegisterExtended(0x1A, true, StatLockChange); + RegisterExtended(0x1C, true, CastSpell); + RegisterExtended(0x24, false, UnhandledBF); + RegisterExtended(0x2C, true, BandageTarget); + RegisterExtended(0x32, true, ToggleFlying); + + RegisterEncoded(0x19, true, SetAbility); + RegisterEncoded(0x28, true, GuildGumpRequest); + + RegisterEncoded(0x32, true, QuestGumpRequest); + } + + public static PacketHandler[] Handlers{ get; } + + public static bool SingleClickProps{ get; set; } + + public static int[] ValidAnimations + { + get => m_ValidAnimations; + set => m_ValidAnimations = value; + } + + public static bool ClientVerification{ get; set; } = true; + + public static void Register(int packetID, int length, bool ingame, OnPacketReceive onReceive) + { + Handlers[packetID] = new PacketHandler(packetID, length, ingame, onReceive); + + if (m_6017Handlers[packetID] == null) + m_6017Handlers[packetID] = new PacketHandler(packetID, length, ingame, onReceive); + } + + public static PacketHandler GetHandler(int packetID) + { + return Handlers[packetID]; + } + + public static void Register6017(int packetID, int length, bool ingame, OnPacketReceive onReceive) + { + m_6017Handlers[packetID] = new PacketHandler(packetID, length, ingame, onReceive); + } + + public static PacketHandler Get6017Handler(int packetID) + { + return m_6017Handlers[packetID]; + } + + public static void RegisterExtended(int packetID, bool ingame, OnPacketReceive onReceive) + { + if (packetID >= 0 && packetID < 0x100) + m_ExtendedHandlersLow[packetID] = new PacketHandler(packetID, 0, ingame, onReceive); + else + m_ExtendedHandlersHigh[packetID] = new PacketHandler(packetID, 0, ingame, onReceive); + } + + public static PacketHandler GetExtendedHandler(int packetID) + { + if (packetID >= 0 && packetID < 0x100) + return m_ExtendedHandlersLow[packetID]; + + m_ExtendedHandlersHigh.TryGetValue(packetID, out PacketHandler handler); + return handler; + } + + public static void RemoveExtendedHandler(int packetID) + { + if (packetID >= 0 && packetID < 0x100) + m_ExtendedHandlersLow[packetID] = null; + else + m_ExtendedHandlersHigh.Remove(packetID); + } + + public static void RegisterEncoded(int packetID, bool ingame, OnEncodedPacketReceive onReceive) + { + if (packetID >= 0 && packetID < 0x100) + m_EncodedHandlersLow[packetID] = new EncodedPacketHandler(packetID, ingame, onReceive); + else + m_EncodedHandlersHigh[packetID] = new EncodedPacketHandler(packetID, ingame, onReceive); + } + + public static EncodedPacketHandler GetEncodedHandler(int packetID) + { + if (packetID >= 0 && packetID < 0x100) + return m_EncodedHandlersLow[packetID]; + + m_EncodedHandlersHigh.TryGetValue(packetID, out EncodedPacketHandler handler); + return handler; + } + + public static void RemoveEncodedHandler(int packetID) + { + if (packetID >= 0 && packetID < 0x100) + m_EncodedHandlersLow[packetID] = null; + else + m_EncodedHandlersHigh.Remove(packetID); + } + + public static void RegisterThrottler(int packetID, ThrottlePacketCallback t) + { + PacketHandler ph = GetHandler(packetID); + + if (ph != null) + ph.ThrottleCallback = t; + + ph = Get6017Handler(packetID); + + if (ph != null) + ph.ThrottleCallback = t; + } + + private static void UnhandledBF(NetState state, PacketReader pvSrc) + { + } + + public static void Empty(NetState state, PacketReader pvSrc) + { + } + + public static void SetAbility(NetState state, IEntity e, EncodedReader reader) + { + EventSink.InvokeSetAbility(new SetAbilityEventArgs(state.Mobile, reader.ReadInt32())); + } + + public static void GuildGumpRequest(NetState state, IEntity e, EncodedReader reader) + { + EventSink.InvokeGuildGumpRequest(new GuildGumpRequestArgs(state.Mobile)); + } + + public static void QuestGumpRequest(NetState state, IEntity e, EncodedReader reader) + { + EventSink.InvokeQuestGumpRequest(new QuestGumpRequestArgs(state.Mobile)); + } + + public static void EncodedCommand(NetState state, PacketReader pvSrc) + { + IEntity e = World.FindEntity(pvSrc.ReadInt32()); + int packetID = pvSrc.ReadUInt16(); + + EncodedPacketHandler ph = GetEncodedHandler(packetID); + + if (ph != null) + { + if (ph.Ingame && state.Mobile == null) + { + Console.WriteLine( + "Client: {0}: Sent ingame packet (0xD7x{1:X2}) before having been attached to a mobile", state, + packetID); + state.Dispose(); + } + else if (ph.Ingame && state.Mobile.Deleted) + { + state.Dispose(); + } + else + { + ph.OnReceive(state, e, new EncodedReader(pvSrc)); + } + } + else + { + pvSrc.Trace(state); + } + } + + public static void RenameRequest(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + Mobile targ = World.FindMobile(pvSrc.ReadInt32()); + + if (targ != null) + EventSink.InvokeRenameRequest(new RenameRequestEventArgs(from, targ, pvSrc.ReadStringSafe())); + } + + public static void ChatRequest(NetState state, PacketReader pvSrc) + { + EventSink.InvokeChatRequest(new ChatRequestEventArgs(state.Mobile)); + } + + public static void SecureTrade(NetState state, PacketReader pvSrc) + { + switch (pvSrc.ReadByte()) + { + case 1: // Cancel + { + Serial serial = pvSrc.ReadInt32(); + + if (World.FindItem(serial) is SecureTradeContainer cont && cont.Trade != null && + (cont.Trade.From.Mobile == state.Mobile || cont.Trade.To.Mobile == state.Mobile)) + cont.Trade.Cancel(); + + break; + } + case 2: // Check + { + Serial serial = pvSrc.ReadInt32(); + + if (World.FindItem(serial) is SecureTradeContainer cont) + { + SecureTrade trade = cont.Trade; + + bool value = pvSrc.ReadInt32() != 0; + + if (trade != null && trade.From.Mobile == state.Mobile) + { + trade.From.Accepted = value; + trade.Update(); + } + else if (trade != null && trade.To.Mobile == state.Mobile) + { + trade.To.Accepted = value; + trade.Update(); + } + } + + break; + } + case 3: // Update Gold + { + Serial serial = pvSrc.ReadInt32(); + + if (World.FindItem(serial) is SecureTradeContainer cont) + { + int gold = pvSrc.ReadInt32(); + int plat = pvSrc.ReadInt32(); + + SecureTrade trade = cont.Trade; + + if (trade != null) + { + if (trade.From.Mobile == state.Mobile) + { + trade.From.Gold = gold; + trade.From.Plat = plat; + trade.UpdateFromCurrency(); + } + else if (trade.To.Mobile == state.Mobile) + { + trade.To.Gold = gold; + trade.To.Plat = plat; + trade.UpdateToCurrency(); + } + } + } + } + break; + } + } + + public static void VendorBuyReply(NetState state, PacketReader pvSrc) + { + pvSrc.Seek(1, SeekOrigin.Begin); + + int msgSize = pvSrc.ReadUInt16(); + Mobile vendor = World.FindMobile(pvSrc.ReadInt32()); + byte flag = pvSrc.ReadByte(); + + if (vendor == null) return; + + if (vendor.Deleted || !Utility.RangeCheck(vendor.Location, state.Mobile.Location, 10)) + { + state.Send(new EndVendorBuy(vendor)); + return; + } + + if (flag == 0x02) + { + msgSize -= 1 + 2 + 4 + 1; + + if (msgSize / 7 > 100) + return; + + List buyList = new List(msgSize / 7); + while (msgSize > 0) + { + byte layer = pvSrc.ReadByte(); + Serial serial = pvSrc.ReadInt32(); + int amount = pvSrc.ReadInt16(); + + buyList.Add(new BuyItemResponse(serial, amount)); + msgSize -= 7; + } + + if (buyList.Count > 0 && vendor is IVendor v && v.OnBuyItems(state.Mobile, buyList)) + state.Send(new EndVendorBuy(vendor)); + } + else + { + state.Send(new EndVendorBuy(vendor)); + } + } + + public static void VendorSellReply(NetState state, PacketReader pvSrc) + { + Serial serial = pvSrc.ReadInt32(); + Mobile vendor = World.FindMobile(serial); + + if (vendor == null) return; + + if (vendor.Deleted || !Utility.RangeCheck(vendor.Location, state.Mobile.Location, 10)) + { + state.Send(new EndVendorSell(vendor)); + return; + } + + int count = pvSrc.ReadUInt16(); + if (count < 100 && pvSrc.Size == 1 + 2 + 4 + 2 + count * 6) + { + List sellList = new List(count); + + for (int i = 0; i < count; i++) + { + Item item = World.FindItem(pvSrc.ReadInt32()); + int Amount = pvSrc.ReadInt16(); + + if (item != null && Amount > 0) + sellList.Add(new SellItemResponse(item, Amount)); + } + + if (sellList.Count > 0 && vendor is IVendor v && v.OnSellItems(state.Mobile, sellList)) + state.Send(new EndVendorSell(vendor)); + } + } + + public static void DeleteCharacter(NetState state, PacketReader pvSrc) + { + pvSrc.Seek(30, SeekOrigin.Current); + int index = pvSrc.ReadInt32(); + + EventSink.InvokeDeleteRequest(new DeleteRequestEventArgs(state, index)); + } + + public static void ResourceQuery(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + } + } + + public static void GameCentralMoniter(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + int type = pvSrc.ReadByte(); + int num1 = pvSrc.ReadInt32(); + + Console.WriteLine("God Client: {0}: Game central moniter", state); + Console.WriteLine(" - Type: {0}", type); + Console.WriteLine(" - Number: {0}", num1); + + pvSrc.Trace(state); + } + } + + public static void GodviewQuery(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) Console.WriteLine("God Client: {0}: Godview query 0x{1:X}", state, pvSrc.ReadByte()); + } + + public static void GMSingle(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + pvSrc.Trace(state); + } + + public static void DeathStatusResponse(NetState state, PacketReader pvSrc) + { + // Ignored + } + + public static void ObjectHelpRequest(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + Serial serial = pvSrc.ReadInt32(); + int unk = pvSrc.ReadByte(); + string lang = pvSrc.ReadString(3); + + if (serial.IsItem) + { + Item item = World.FindItem(serial); + + if (item != null && from.Map == item.Map && Utility.InUpdateRange(item.GetWorldLocation(), from.Location) && + from.CanSee(item)) + item.OnHelpRequest(from); + } + else if (serial.IsMobile) + { + Mobile m = World.FindMobile(serial); + + if (m != null && from.Map == m.Map && Utility.InUpdateRange(m.Location, from.Location) && from.CanSee(m)) + m.OnHelpRequest(m); + } + } + + public static void MobileNameRequest(NetState state, PacketReader pvSrc) + { + Mobile m = World.FindMobile(pvSrc.ReadInt32()); + + if (m != null && Utility.InUpdateRange(state.Mobile, m) && state.Mobile.CanSee(m)) + state.Send(new MobileName(m)); + } + + public static void RequestScrollWindow(NetState state, PacketReader pvSrc) + { + int lastTip = pvSrc.ReadInt16(); + int type = pvSrc.ReadByte(); + } + + public static void AttackReq(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + Mobile m = World.FindMobile(pvSrc.ReadInt32()); + + if (m != null) + from.Attack(m); + } + + public static void HuePickerResponse(NetState state, PacketReader pvSrc) + { + int serial = pvSrc.ReadInt32(); + int value = pvSrc.ReadInt16(); + int hue = pvSrc.ReadInt16() & 0x3FFF; + + hue = Utility.ClipDyedHue(hue); + + foreach (HuePicker huePicker in state.HuePickers) + if (huePicker.Serial == serial) + { + state.RemoveHuePicker(huePicker); + + huePicker.OnResponse(hue); + + break; + } + } + + public static void TripTime(NetState state, PacketReader pvSrc) + { + int unk1 = pvSrc.ReadByte(); + int unk2 = pvSrc.ReadInt32(); + + state.Send(new TripTimeResponse(unk1)); + } + + public static void UTripTime(NetState state, PacketReader pvSrc) + { + int unk1 = pvSrc.ReadByte(); + int unk2 = pvSrc.ReadInt32(); + + state.Send(new UTripTimeResponse(unk1)); + } + + public static void ChangeZ(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int z = pvSrc.ReadSByte(); + + Console.WriteLine("God Client: {0}: Change Z ({1}, {2}, {3})", state, x, y, z); + } + } + + public static void SystemInfo(NetState state, PacketReader pvSrc) + { + int v1 = pvSrc.ReadByte(); + int v2 = pvSrc.ReadUInt16(); + int v3 = pvSrc.ReadByte(); + string s1 = pvSrc.ReadString(32); + string s2 = pvSrc.ReadString(32); + string s3 = pvSrc.ReadString(32); + string s4 = pvSrc.ReadString(32); + int v4 = pvSrc.ReadUInt16(); + int v5 = pvSrc.ReadUInt16(); + int v6 = pvSrc.ReadInt32(); + int v7 = pvSrc.ReadInt32(); + int v8 = pvSrc.ReadInt32(); + } + + public static void Edit(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + int type = pvSrc.ReadByte(); // 10 = static, 7 = npc, 4 = dynamic + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int id = pvSrc.ReadInt16(); + int z = pvSrc.ReadSByte(); + int hue = pvSrc.ReadUInt16(); + + Console.WriteLine("God Client: {0}: Edit {6} ({1}, {2}, {3}) 0x{4:X} (0x{5:X})", state, x, y, z, id, hue, + type); + } + } + + public static void DeleteStatic(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int z = pvSrc.ReadInt16(); + int id = pvSrc.ReadUInt16(); + + Console.WriteLine("God Client: {0}: Delete Static ({1}, {2}, {3}) 0x{4:X}", state, x, y, z, id); + } + } + + public static void NewAnimData(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + Console.WriteLine("God Client: {0}: New tile animation", state); + + pvSrc.Trace(state); + } + } + + public static void NewTerrain(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int id = pvSrc.ReadUInt16(); + int width = pvSrc.ReadInt16(); + int height = pvSrc.ReadInt16(); + + Console.WriteLine("God Client: {0}: New Terrain ({1}, {2})+({3}, {4}) 0x{5:X4}", state, x, y, width, height, + id); + } + } + + public static void NewRegion(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) + { + string name = pvSrc.ReadString(40); + int unk = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int width = pvSrc.ReadInt16(); + int height = pvSrc.ReadInt16(); + int zStart = pvSrc.ReadInt16(); + int zEnd = pvSrc.ReadInt16(); + string desc = pvSrc.ReadString(40); + int soundFX = pvSrc.ReadInt16(); + int music = pvSrc.ReadInt16(); + int nightFX = pvSrc.ReadInt16(); + int dungeon = pvSrc.ReadByte(); + int light = pvSrc.ReadInt16(); + + Console.WriteLine("God Client: {0}: New Region '{1}' ('{2}')", state, name, desc); + } + } + + public static void AccountID(NetState state, PacketReader pvSrc) + { + } + + public static bool VerifyGC(NetState state) + { + if (state.Mobile == null || state.Mobile.AccessLevel <= AccessLevel.Counselor) + { + if (state.Running) + Console.WriteLine("Warning: {0}: Player using godclient, disconnecting", state); + + state.Dispose(); + return false; + } + + return true; + } + + public static void TextCommand(NetState state, PacketReader pvSrc) + { + int type = pvSrc.ReadByte(); + string command = pvSrc.ReadString(); + + Mobile m = state.Mobile; + + switch (type) + { + case 0x00: // Go + { + if (VerifyGC(state)) + try + { + string[] split = command.Split(' '); + + int x = Utility.ToInt32(split[0]); + int y = Utility.ToInt32(split[1]); + + int z; + + if (split.Length >= 3) + z = Utility.ToInt32(split[2]); + else if (m.Map != null) + z = m.Map.GetAverageZ(x, y); + else + z = 0; + + m.Location = new Point3D(x, y, z); + } + catch + { + } + + break; + } + case 0xC7: // Animate + { + EventSink.InvokeAnimateRequest(new AnimateRequestEventArgs(m, command)); + + break; + } + case 0x24: // Use skill + { + if (!int.TryParse(command.Split(' ')[0], out int skillIndex)) + break; + + Skills.UseSkill(m, skillIndex); + + break; + } + case 0x43: // Open spellbook + { + if (!int.TryParse(command, out int booktype)) + booktype = 1; + + EventSink.InvokeOpenSpellbookRequest(new OpenSpellbookRequestEventArgs(m, booktype)); + + break; + } + case 0x27: // Cast spell from book + { + string[] split = command.Split(' '); + + if (split.Length > 0) + { + int spellID = Utility.ToInt32(split[0]) - 1; + int serial = split.Length > 1 ? Utility.ToInt32(split[1]) : -1; + + EventSink.InvokeCastSpellRequest(new CastSpellRequestEventArgs(m, spellID, World.FindItem(serial))); + } + + break; + } + case 0x58: // Open door + { + EventSink.InvokeOpenDoorMacroUsed(new OpenDoorMacroEventArgs(m)); + + break; + } + case 0x56: // Cast spell from macro + { + int spellID = Utility.ToInt32(command) - 1; + + EventSink.InvokeCastSpellRequest(new CastSpellRequestEventArgs(m, spellID, null)); + + break; + } + case 0xF4: // Invoke virtues from macro + { + int virtueID = Utility.ToInt32(command) - 1; + + EventSink.InvokeVirtueMacroRequest(new VirtueMacroRequestEventArgs(m, virtueID)); + + break; + } + case 0x2F: // Old scroll double click + { + /* + * This command is still sent for items 0xEF3 - 0xEF9 + * + * Command is one of three, depending on the item ID of the scroll: + * - [scroll serial] + * - [scroll serial] [target serial] + * - [scroll serial] [x] [y] [z] + */ + break; + } + default: + { + Console.WriteLine("Client: {0}: Unknown text-command type 0x{1:X2}: {2}", state, type, command); + break; + } + } + } + + public static void GodModeRequest(NetState state, PacketReader pvSrc) + { + if (VerifyGC(state)) state.Send(new GodModeReply(pvSrc.ReadBoolean())); + } + + public static void AsciiPromptResponse(NetState state, PacketReader pvSrc) + { + int serial = pvSrc.ReadInt32(); + int prompt = pvSrc.ReadInt32(); + int type = pvSrc.ReadInt32(); + string text = pvSrc.ReadStringSafe(); + + if (text.Length > 128) + return; + + Mobile from = state.Mobile; + Prompt p = from.Prompt; + + if (p != null && p.Serial == serial && p.Serial == prompt) + { + from.Prompt = null; + + if (type == 0) + p.OnCancel(from); + else + p.OnResponse(from, text); + } + } + + public static void UnicodePromptResponse(NetState state, PacketReader pvSrc) + { + int serial = pvSrc.ReadInt32(); + int prompt = pvSrc.ReadInt32(); + int type = pvSrc.ReadInt32(); + string lang = pvSrc.ReadString(4); + string text = pvSrc.ReadUnicodeStringLESafe(); + + if (text.Length > 128) + return; + + Mobile from = state.Mobile; + Prompt p = from.Prompt; + + if (p != null && p.Serial == serial && p.Serial == prompt) + { + from.Prompt = null; + + if (type == 0) + p.OnCancel(from); + else + p.OnResponse(from, text); + } + } + + public static void MenuResponse(NetState state, PacketReader pvSrc) + { + int serial = pvSrc.ReadInt32(); + int menuID = pvSrc.ReadInt16(); // unused in our implementation + int index = pvSrc.ReadInt16(); + int itemID = pvSrc.ReadInt16(); + int hue = pvSrc.ReadInt16(); + + index -= 1; // convert from 1-based to 0-based + + foreach (IMenu menu in state.Menus) + if (menu.Serial == serial) + { + state.RemoveMenu(menu); + + if (index >= 0 && index < menu.EntryLength) + menu.OnResponse(state, index); + else + menu.OnCancel(state); + + break; + } + } + + public static void ProfileReq(NetState state, PacketReader pvSrc) + { + int type = pvSrc.ReadByte(); + Serial serial = pvSrc.ReadInt32(); + + Mobile beholder = state.Mobile; + Mobile beheld = World.FindMobile(serial); + + if (beheld == null) + return; + + switch (type) + { + case 0x00: // display request + { + EventSink.InvokeProfileRequest(new ProfileRequestEventArgs(beholder, beheld)); + + break; + } + case 0x01: // edit request + { + pvSrc.ReadInt16(); // Skip + int length = pvSrc.ReadUInt16(); + + if (length > 511) + return; + + string text = pvSrc.ReadUnicodeString(length); + + EventSink.InvokeChangeProfileRequest(new ChangeProfileRequestEventArgs(beholder, beheld, text)); + + break; + } + } + } + + public static void Disconnect(NetState state, PacketReader pvSrc) + { + int minusOne = pvSrc.ReadInt32(); + } + + public static void LiftReq(NetState state, PacketReader pvSrc) + { + Serial serial = pvSrc.ReadInt32(); + int amount = pvSrc.ReadUInt16(); + Item item = World.FindItem(serial); + + bool rejected; + LRReason reject; + + state.Mobile.Lift(item, amount, out rejected, out reject); + } + + public static void EquipReq(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + Item item = from.Holding; + + bool valid = item != null && item.HeldBy == from && item.Map == Map.Internal; + + from.Holding = null; + + if (!valid) return; + + pvSrc.Seek(5, SeekOrigin.Current); + Mobile to = World.FindMobile(pvSrc.ReadInt32()); + + if (to == null) + to = from; + + if (!to.AllowEquipFrom(from) || !to.EquipItem(item)) + item.Bounce(from); + + item.ClearBounce(); + } + + public static void DropReq(NetState state, PacketReader pvSrc) + { + pvSrc.ReadInt32(); // serial, ignored + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int z = pvSrc.ReadSByte(); + Serial dest = pvSrc.ReadInt32(); + + Point3D loc = new Point3D(x, y, z); + + Mobile from = state.Mobile; + + if (dest.IsMobile) + { + from.Drop(World.FindMobile(dest), loc); + } + else if (dest.IsItem) + { + Item item = World.FindItem(dest); + + if (item is BaseMulti multi && multi.AllowsRelativeDrop) + { + loc.m_X += multi.X; + loc.m_Y += multi.Y; + from.Drop(loc); + } + else + { + from.Drop(item, loc); + } + } + else + { + from.Drop(loc); + } + } + + public static void DropReq6017(NetState state, PacketReader pvSrc) + { + pvSrc.ReadInt32(); // serial, ignored + int x = pvSrc.ReadInt16(); + int y = pvSrc.ReadInt16(); + int z = pvSrc.ReadSByte(); + pvSrc.ReadByte(); // Grid Location? + Serial dest = pvSrc.ReadInt32(); + + Point3D loc = new Point3D(x, y, z); + + Mobile from = state.Mobile; + + if (dest.IsMobile) + { + from.Drop(World.FindMobile(dest), loc); + } + else if (dest.IsItem) + { + Item item = World.FindItem(dest); + + if (item is BaseMulti multi && multi.AllowsRelativeDrop) + { + loc.m_X += multi.X; + loc.m_Y += multi.Y; + from.Drop(loc); + } + else + { + from.Drop(item, loc); + } + } + else + { + from.Drop(loc); + } + } + + public static void ConfigurationFile(NetState state, PacketReader pvSrc) + { + } + + public static void LogoutReq(NetState state, PacketReader pvSrc) + { + state.Send(new LogoutAck()); + } + + public static void ChangeSkillLock(NetState state, PacketReader pvSrc) + { + Skill s = state.Mobile.Skills[pvSrc.ReadInt16()]; + + s?.SetLockNoRelay((SkillLock)pvSrc.ReadByte()); + } + + public static void HelpRequest(NetState state, PacketReader pvSrc) + { + EventSink.InvokeHelpRequest(new HelpRequestEventArgs(state.Mobile)); + } + + public static void TargetResponse(NetState state, PacketReader pvSrc) + { + int type = pvSrc.ReadByte(); + int targetID = pvSrc.ReadInt32(); + int flags = pvSrc.ReadByte(); + Serial serial = pvSrc.ReadInt32(); + int x = pvSrc.ReadInt16(), y = pvSrc.ReadInt16(), z = pvSrc.ReadInt16(); + int graphic = pvSrc.ReadUInt16(); + + if (targetID == unchecked((int)0xDEADBEEF)) + return; + + Mobile from = state.Mobile; + + Target t = from.Target; + + if (t == null) + return; + + TargetProfile prof = TargetProfile.Acquire(t.GetType()); + prof?.Start(); + + try + { + if (x == -1 && y == -1 && !serial.IsValid) + { + // User pressed escape + t.Cancel(from, TargetCancelType.Canceled); + } + else if (Target.TargetIDValidation && t.TargetID != targetID) + { + // Sanity, prevent fake target + } + else + { + object toTarget; + + if (type == 1) + { + if (graphic == 0) + { + toTarget = new LandTarget(new Point3D(x, y, z), from.Map); + } + else + { + Map map = from.Map; + + if (map == null || map == Map.Internal) + { + t.Cancel(from, TargetCancelType.Canceled); + return; + } + else + { + StaticTile[] tiles = map.Tiles.GetStaticTiles(x, y, !t.DisallowMultis); + + bool valid = false; + + if (state.HighSeas) + { + ItemData id = TileData.ItemTable[graphic & TileData.MaxItemValue]; + if (id.Surface) z -= id.Height; + } + + for (int i = 0; !valid && i < tiles.Length; ++i) + if (tiles[i].Z == z && tiles[i].ID == graphic) + valid = true; + + if (!valid) + { + t.Cancel(from, TargetCancelType.Canceled); + return; + } + else + { + toTarget = new StaticTarget(new Point3D(x, y, z), graphic); + } + } + } + } + else if (serial.IsMobile) + { + toTarget = World.FindMobile(serial); + } + else if (serial.IsItem) + { + toTarget = World.FindItem(serial); + } + else + { + t.Cancel(from, TargetCancelType.Canceled); + return; + } + + t.Invoke(from, toTarget); + } + } + finally + { + prof?.Finish(); + } + } + + public static void DisplayGumpResponse(NetState state, PacketReader pvSrc) + { + int serial = pvSrc.ReadInt32(); + int typeID = pvSrc.ReadInt32(); + int buttonID = pvSrc.ReadInt32(); + + foreach (Gump gump in state.Gumps) + if (gump.Serial == serial && gump.TypeID == typeID) + { + bool buttonExists = buttonID == 0; // 0 is always 'close' + + if (!buttonExists) + foreach (GumpEntry e in gump.Entries) + { + if (e is GumpButton button && button.ButtonID == buttonID) + { + buttonExists = true; + break; + } + + if (e is GumpImageTileButton tileButton && tileButton.ButtonID == buttonID) + { + buttonExists = true; + break; + } + } + + if (!buttonExists) + { + state.WriteConsole("Invalid gump response, disconnecting..."); + state.Dispose(); + return; + } + + int switchCount = pvSrc.ReadInt32(); + + if (switchCount < 0 || switchCount > gump.m_Switches) + { + state.WriteConsole("Invalid gump response, disconnecting..."); + state.Dispose(); + return; + } + + int[] switches = new int[switchCount]; + + for (int j = 0; j < switches.Length; ++j) + switches[j] = pvSrc.ReadInt32(); + + int textCount = pvSrc.ReadInt32(); + + if (textCount < 0 || textCount > gump.m_TextEntries) + { + state.WriteConsole("Invalid gump response, disconnecting..."); + state.Dispose(); + return; + } + + TextRelay[] textEntries = new TextRelay[textCount]; + + for (int j = 0; j < textEntries.Length; ++j) + { + int entryID = pvSrc.ReadUInt16(); + int textLength = pvSrc.ReadUInt16(); + + if (textLength > 239) + { + state.WriteConsole("Invalid gump response, disconnecting..."); + state.Dispose(); + return; + } + + string text = pvSrc.ReadUnicodeStringSafe(textLength); + textEntries[j] = new TextRelay(entryID, text); + } + + state.RemoveGump(gump); + + GumpProfile prof = GumpProfile.Acquire(gump.GetType()); + + prof?.Start(); + + gump.OnResponse(state, new RelayInfo(buttonID, switches, textEntries)); + + prof?.Finish(); + + return; + } + + if (typeID == 461) + { + // Virtue gump + int switchCount = pvSrc.ReadInt32(); + + if (buttonID == 1 && switchCount > 0) + { + Mobile beheld = World.FindMobile(pvSrc.ReadInt32()); + + if (beheld != null) + EventSink.InvokeVirtueGumpRequest(new VirtueGumpRequestEventArgs(state.Mobile, beheld)); + } + else + { + Mobile beheld = World.FindMobile(serial); + + if (beheld != null) + EventSink.InvokeVirtueItemRequest(new VirtueItemRequestEventArgs(state.Mobile, beheld, buttonID)); + } + } + } + + public static void SetWarMode(NetState state, PacketReader pvSrc) + { + state.Mobile.DelayChangeWarmode(pvSrc.ReadBoolean()); + } - public static void SetWarMode( NetState state, PacketReader pvSrc ) - { - state.Mobile.DelayChangeWarmode( pvSrc.ReadBoolean() ); - } + public static void Resynchronize(NetState state, PacketReader pvSrc) + { + Mobile m = state.Mobile; - public static void Resynchronize( NetState state, PacketReader pvSrc ) - { - Mobile m = state.Mobile; + if (state.StygianAbyss) + state.Send(new MobileUpdate(m)); + else + state.Send(new MobileUpdateOld(m)); - if ( state.StygianAbyss ) { - state.Send( new MobileUpdate( m ) ); - } else { - state.Send( new MobileUpdateOld( m ) ); - } + state.Send(MobileIncoming.Create(state, m, m)); - state.Send(MobileIncoming.Create(state, m, m)); + m.SendEverything(); - m.SendEverything(); + state.Sequence = 0; - state.Sequence = 0; + m.ClearFastwalkStack(); + } - m.ClearFastwalkStack(); - } + public static void AsciiSpeech(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; - private static int[] m_EmptyInts = new int[0]; + MessageType type = (MessageType)pvSrc.ReadByte(); + int hue = pvSrc.ReadInt16(); + pvSrc.ReadInt16(); // font + string text = pvSrc.ReadStringSafe().Trim(); - public static void AsciiSpeech( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; + if (text.Length <= 0 || text.Length > 128) + return; - MessageType type = (MessageType)pvSrc.ReadByte(); - int hue = pvSrc.ReadInt16(); - pvSrc.ReadInt16(); // font - string text = pvSrc.ReadStringSafe().Trim(); + if (!Enum.IsDefined(typeof(MessageType), type)) + type = MessageType.Regular; - if ( text.Length <= 0 || text.Length > 128 ) - return; + from.DoSpeech(text, m_EmptyInts, type, Utility.ClipDyedHue(hue)); + } + + public static void UnicodeSpeech(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; - if ( !Enum.IsDefined( typeof( MessageType ), type ) ) - type = MessageType.Regular; + MessageType type = (MessageType)pvSrc.ReadByte(); + int hue = pvSrc.ReadInt16(); + pvSrc.ReadInt16(); // font + string lang = pvSrc.ReadString(4); + string text; + + bool isEncoded = (type & MessageType.Encoded) != 0; + int[] keywords; + + if (isEncoded) + { + int value = pvSrc.ReadInt16(); + int count = (value & 0xFFF0) >> 4; + int hold = value & 0xF; - from.DoSpeech( text, m_EmptyInts, type, Utility.ClipDyedHue( hue ) ); - } + if (count < 0 || count > 50) + return; - private static KeywordList m_KeywordList = new KeywordList(); + KeywordList keyList = m_KeywordList; - public static void UnicodeSpeech( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; + for (int i = 0; i < count; ++i) + { + int speechID; + + if ((i & 1) == 0) + { + hold <<= 8; + hold |= pvSrc.ReadByte(); + speechID = hold; + hold = 0; + } + else + { + value = pvSrc.ReadInt16(); + speechID = (value & 0xFFF0) >> 4; + hold = value & 0xF; + } + + if (!keyList.Contains(speechID)) + keyList.Add(speechID); + } + + text = pvSrc.ReadUTF8StringSafe(); + + keywords = keyList.ToArray(); + } + else + { + text = pvSrc.ReadUnicodeStringSafe(); + + keywords = m_EmptyInts; + } + + text = text.Trim(); + + if (text.Length <= 0 || text.Length > 128) + return; + + type &= ~MessageType.Encoded; + + if (!Enum.IsDefined(typeof(MessageType), type)) + type = MessageType.Regular; + + from.Language = lang; + from.DoSpeech(text, keywords, type, Utility.ClipDyedHue(hue)); + } + + public static void UseReq(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (from.AccessLevel >= AccessLevel.Counselor || Core.TickCount - from.NextActionTime >= 0) + { + int value = pvSrc.ReadInt32(); + + if ((value & ~0x7FFFFFFF) != 0) + { + from.OnPaperdollRequest(); + } + else + { + Serial s = value; + + if (s.IsMobile) + { + Mobile m = World.FindMobile(s); + + if (m != null && !m.Deleted) + from.Use(m); + } + else if (s.IsItem) + { + Item item = World.FindItem(s); + + if (item != null && !item.Deleted) + from.Use(item); + } + } + + from.NextActionTime = Core.TickCount + Mobile.ActionDelay; + } + else + { + from.SendActionMessage(); + } + } + + public static void LookReq(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + Serial s = pvSrc.ReadInt32(); + + if (s.IsMobile) + { + Mobile m = World.FindMobile(s); + + if (m != null && from.CanSee(m) && Utility.InUpdateRange(from, m)) + { + if (SingleClickProps) + { + m.OnAosSingleClick(from); + } + else + { + if (from.Region.OnSingleClick(from, m)) + m.OnSingleClick(from); + } + } + } + else if (s.IsItem) + { + Item item = World.FindItem(s); + + if (item != null && !item.Deleted && from.CanSee(item) && + Utility.InUpdateRange(from.Location, item.GetWorldLocation())) + { + if (SingleClickProps) + { + item.OnAosSingleClick(from); + } + else if (from.Region.OnSingleClick(from, item)) + { + if (item.Parent is Item item1) + item1.OnSingleClickContained(from, item); + + item.OnSingleClick(from); + } + } + } + } + + public static void PingReq(NetState state, PacketReader pvSrc) + { + state.Send(PingAck.Instantiate(pvSrc.ReadByte())); + } + + public static void SetUpdateRange(NetState state, PacketReader pvSrc) + { + state.Send(ChangeUpdateRange.Instantiate(18)); + } + + public static void MovementReq(NetState state, PacketReader pvSrc) + { + Direction dir = (Direction)pvSrc.ReadByte(); + int seq = pvSrc.ReadByte(); + int key = pvSrc.ReadInt32(); + + Mobile m = state.Mobile; + + if (state.Sequence == 0 && seq != 0 || !m.Move(dir)) + { + state.Send(new MovementRej(seq, m)); + state.Sequence = 0; + + m.ClearFastwalkStack(); + } + else + { + ++seq; + + if (seq == 256) + seq = 1; + + state.Sequence = seq; + } + } + + public static void Animate(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + int action = pvSrc.ReadInt32(); + + bool ok = false; + + for (int i = 0; !ok && i < m_ValidAnimations.Length; ++i) + ok = action == m_ValidAnimations[i]; + + if (from != null && ok && from.Alive && from.Body.IsHuman && !from.Mounted) + from.Animate(action, 7, 1, true, false, 0); + } + + public static void QuestArrow(NetState state, PacketReader pvSrc) + { + bool rightClick = pvSrc.ReadBoolean(); + Mobile from = state.Mobile; + + from?.QuestArrow?.OnClick(rightClick); + } + + public static void ExtendedCommand(NetState state, PacketReader pvSrc) + { + int packetID = pvSrc.ReadUInt16(); + + PacketHandler ph = GetExtendedHandler(packetID); + + if (ph != null) + { + if (ph.Ingame && state.Mobile == null) + { + Console.WriteLine( + "Client: {0}: Sent ingame packet (0xBFx{1:X2}) before having been attached to a mobile", state, + packetID); + state.Dispose(); + } + else if (ph.Ingame && state.Mobile.Deleted) + { + state.Dispose(); + } + else + { + ph.OnReceive(state, pvSrc); + } + } + else + { + pvSrc.Trace(state); + } + } + + public static void CastSpell(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (from == null) + return; + + Item spellbook = null; + + if (pvSrc.ReadInt16() == 1) + spellbook = World.FindItem(pvSrc.ReadInt32()); + + int spellID = pvSrc.ReadInt16() - 1; + + EventSink.InvokeCastSpellRequest(new CastSpellRequestEventArgs(from, spellID, spellbook)); + } + + public static void BandageTarget(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (from == null) + return; + + if (from.AccessLevel >= AccessLevel.Counselor || Core.TickCount - from.NextActionTime >= 0) + { + Item bandage = World.FindItem(pvSrc.ReadInt32()); + + if (bandage == null) + return; + + Mobile target = World.FindMobile(pvSrc.ReadInt32()); + + if (target == null) + return; + + EventSink.InvokeBandageTargetRequest(new BandageTargetRequestEventArgs(from, bandage, target)); + + from.NextActionTime = Core.TickCount + Mobile.ActionDelay; + } + else + { + from.SendActionMessage(); + } + } + + public static void ToggleFlying(NetState state, PacketReader pvSrc) + { + state.Mobile.ToggleFlying(); + } + + public static void BatchQueryProperties(NetState state, PacketReader pvSrc) + { + if (!ObjectPropertyList.Enabled) + return; + + Mobile from = state.Mobile; + + int length = pvSrc.Size - 3; + + if (length < 0 || length % 4 != 0) + return; + + int count = length / 4; + + for (int i = 0; i < count; ++i) + { + Serial s = pvSrc.ReadInt32(); + + if (s.IsMobile) + { + Mobile m = World.FindMobile(s); + + if (m != null && from.CanSee(m) && Utility.InUpdateRange(from, m)) + m.SendPropertiesTo(from); + } + else if (s.IsItem) + { + Item item = World.FindItem(s); + + if (item != null && !item.Deleted && from.CanSee(item) && + Utility.InUpdateRange(from.Location, item.GetWorldLocation())) + item.SendPropertiesTo(from); + } + } + } + + public static void QueryProperties(NetState state, PacketReader pvSrc) + { + if (!ObjectPropertyList.Enabled) + return; + + Mobile from = state.Mobile; + + Serial s = pvSrc.ReadInt32(); + + if (s.IsMobile) + { + Mobile m = World.FindMobile(s); + + if (m != null && from.CanSee(m) && Utility.InUpdateRange(from, m)) + m.SendPropertiesTo(from); + } + else if (s.IsItem) + { + Item item = World.FindItem(s); + + if (item != null && !item.Deleted && from.CanSee(item) && + Utility.InUpdateRange(from.Location, item.GetWorldLocation())) + item.SendPropertiesTo(from); + } + } + + public static void PartyMessage(NetState state, PacketReader pvSrc) + { + if (state.Mobile == null) + return; + + switch (pvSrc.ReadByte()) + { + case 0x01: + PartyMessage_AddMember(state, pvSrc); + break; + case 0x02: + PartyMessage_RemoveMember(state, pvSrc); + break; + case 0x03: + PartyMessage_PrivateMessage(state, pvSrc); + break; + case 0x04: + PartyMessage_PublicMessage(state, pvSrc); + break; + case 0x06: + PartyMessage_SetCanLoot(state, pvSrc); + break; + case 0x08: + PartyMessage_Accept(state, pvSrc); + break; + case 0x09: + PartyMessage_Decline(state, pvSrc); + break; + default: + pvSrc.Trace(state); + break; + } + } + + public static void PartyMessage_AddMember(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnAdd(state.Mobile); + } + + public static void PartyMessage_RemoveMember(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnRemove(state.Mobile, World.FindMobile(pvSrc.ReadInt32())); + } + + public static void PartyMessage_PrivateMessage(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnPrivateMessage(state.Mobile, World.FindMobile(pvSrc.ReadInt32()), + pvSrc.ReadUnicodeStringSafe()); + } + + public static void PartyMessage_PublicMessage(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnPublicMessage(state.Mobile, pvSrc.ReadUnicodeStringSafe()); + } + + public static void PartyMessage_SetCanLoot(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnSetCanLoot(state.Mobile, pvSrc.ReadBoolean()); + } + + public static void PartyMessage_Accept(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnAccept(state.Mobile, World.FindMobile(pvSrc.ReadInt32())); + } + + public static void PartyMessage_Decline(NetState state, PacketReader pvSrc) + { + if (PartyCommands.Handler != null) + PartyCommands.Handler.OnDecline(state.Mobile, World.FindMobile(pvSrc.ReadInt32())); + } + + public static void StunRequest(NetState state, PacketReader pvSrc) + { + EventSink.InvokeStunRequest(new StunRequestEventArgs(state.Mobile)); + } + + public static void DisarmRequest(NetState state, PacketReader pvSrc) + { + EventSink.InvokeDisarmRequest(new DisarmRequestEventArgs(state.Mobile)); + } + + public static void StatLockChange(NetState state, PacketReader pvSrc) + { + int stat = pvSrc.ReadByte(); + int lockValue = pvSrc.ReadByte(); + + if (lockValue > 2) lockValue = 0; + + Mobile m = state.Mobile; + + if (m != null) + switch (stat) + { + case 0: + m.StrLock = (StatLockType)lockValue; + break; + case 1: + m.DexLock = (StatLockType)lockValue; + break; + case 2: + m.IntLock = (StatLockType)lockValue; + break; + } + } + + public static void ScreenSize(NetState state, PacketReader pvSrc) + { + int width = pvSrc.ReadInt32(); + int unk = pvSrc.ReadInt32(); + } + + public static void ContextMenuResponse(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + if (from != null) + { + ContextMenu menu = from.ContextMenu; + + from.ContextMenu = null; + + if (menu != null && from == menu.From) + { + IEntity entity = World.FindEntity(pvSrc.ReadInt32()); + + if (entity != null && entity == menu.Target && from.CanSee(entity)) + { + Point3D p; + + if (entity is Mobile) + p = entity.Location; + else if (entity is Item item) + p = item.GetWorldLocation(); + else + return; + + int index = pvSrc.ReadUInt16(); + + if (index >= 0 && index < menu.Entries.Length) + { + ContextMenuEntry e = menu.Entries[index]; + + int range = e.Range; + + if (range == -1) + range = 18; + + if (e.Enabled && from.InRange(p, range)) + e.OnClick(); + } + } + } + } + } + + public static void ContextMenuRequest(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + IEntity target = World.FindEntity(pvSrc.ReadInt32()); + + if (from != null && target != null && from.Map == target.Map && from.CanSee(target)) + { + if (target is Mobile && !Utility.InUpdateRange(from.Location, target.Location)) + return; + + Item item = target as Item; + + if (item != null && !Utility.InUpdateRange(from.Location, item.GetWorldLocation())) + return; + + if (!from.CheckContextMenuDisplay(target)) + return; + + ContextMenu c = new ContextMenu(from, target); + + if (c.Entries.Length > 0) + { + if (item?.RootParent is Mobile mobile && mobile != from && mobile.AccessLevel >= from.AccessLevel) + for (int i = 0; i < c.Entries.Length; ++i) + if (!c.Entries[i].NonLocalUse) + c.Entries[i].Enabled = false; + + from.ContextMenu = c; + } + } + } + + public static void CloseStatus(NetState state, PacketReader pvSrc) + { + Serial serial = pvSrc.ReadInt32(); + } + + public static void Language(NetState state, PacketReader pvSrc) + { + string lang = pvSrc.ReadString(4); + + if (state.Mobile != null) + state.Mobile.Language = lang; + } + + public static void AssistVersion(NetState state, PacketReader pvSrc) + { + int unk = pvSrc.ReadInt32(); + string av = pvSrc.ReadString(); + } + + public static void ClientVersion(NetState state, PacketReader pvSrc) + { + CV version = state.Version = new CV(pvSrc.ReadString()); + + EventSink.InvokeClientVersionReceived(new ClientVersionReceivedArgs(state, version)); + } + + public static void ClientType(NetState state, PacketReader pvSrc) + { + pvSrc.ReadUInt16(); + + int type = pvSrc.ReadUInt16(); + CV version = state.Version = new CV(pvSrc.ReadString()); + + //EventSink.InvokeClientVersionReceived( new ClientVersionReceivedArgs( state, version ) );//todo + } + + public static void MobileQuery(NetState state, PacketReader pvSrc) + { + Mobile from = state.Mobile; + + pvSrc.ReadInt32(); // 0xEDEDEDED + int type = pvSrc.ReadByte(); + Mobile m = World.FindMobile(pvSrc.ReadInt32()); + + if (m != null) + switch (type) + { + case 0x00: // Unknown, sent by godclient + { + if (VerifyGC(state)) + Console.WriteLine("God Client: {0}: Query 0x{1:X2} on {2} '{3}'", state, type, m.Serial, m.Name); + + break; + } + case 0x04: // Stats + { + m.OnStatsQuery(from); + break; + } + case 0x05: + { + m.OnSkillsQuery(from); + break; + } + default: + { + pvSrc.Trace(state); + break; + } + } + } + + public static void PlayCharacter(NetState state, PacketReader pvSrc) + { + pvSrc.ReadInt32(); // 0xEDEDEDED + + string name = pvSrc.ReadString(30); + + pvSrc.Seek(2, SeekOrigin.Current); + int flags = pvSrc.ReadInt32(); + + if (FeatureProtection.DisabledFeatures != 0 && ThirdPartyAuthCallback != null) + { + bool authOK = false; + + ulong razorFeatures = ((ulong)pvSrc.ReadUInt32() << 32) | pvSrc.ReadUInt32(); + + if (razorFeatures == (ulong)FeatureProtection.DisabledFeatures) + { + bool doesNotMatch = false; + for (int i = 0; !doesNotMatch && i < m_ThirdPartyAuthKey.Length; i++) + doesNotMatch = pvSrc.ReadByte() != m_ThirdPartyAuthKey[i]; + + if (!doesNotMatch) + authOK = true; + } + else + { + pvSrc.Seek(16, SeekOrigin.Current); + } + + ThirdPartyAuthCallback(state, authOK); + } + else + { + pvSrc.Seek(24, SeekOrigin.Current); + } + + if (ThirdPartyHackedCallback != null) + { + pvSrc.Seek(-2, SeekOrigin.Current); + if (pvSrc.ReadUInt16() == 0xDEAD) + ThirdPartyHackedCallback(state, true); + } + + if (!state.Running) + return; + + int charSlot = pvSrc.ReadInt32(); + int clientIP = pvSrc.ReadInt32(); + + IAccount a = state.Account; + + if (a == null || charSlot < 0 || charSlot >= a.Length) + { + state.Dispose(); + } + else + { + Mobile m = a[charSlot]; + + // Check if anyone is using this account + for (int i = 0; i < a.Length; ++i) + { + Mobile check = a[i]; + + if (check != null && check.Map != Map.Internal && check != m) + { + Console.WriteLine("Login: {0}: Account in use", state); + state.Send(new PopupMessage(PMMessage.CharInWorld)); + return; + } + } + + if (m == null) + { + state.Dispose(); + return; + } + + + m.NetState?.Dispose(); + + // TODO: Make this wait one tick so we don't have to call it unnecessarily + NetState.ProcessDisposedQueue(); + + state.Send(new ClientVersionReq()); + + state.BlockAllPackets = true; + + state.Flags = (ClientFlags)flags; + + state.Mobile = m; + m.NetState = state; - MessageType type = (MessageType)pvSrc.ReadByte(); - int hue = pvSrc.ReadInt16(); - pvSrc.ReadInt16(); // font - string lang = pvSrc.ReadString( 4 ); - string text; + new LoginTimer(state, m).Start(); + } + } - bool isEncoded = (type & MessageType.Encoded) != 0; - int[] keywords; + public static void DoLogin(NetState state, Mobile m) + { + state.Send(new LoginConfirm(m)); - if ( isEncoded ) - { - int value = pvSrc.ReadInt16(); - int count = (value & 0xFFF0) >> 4; - int hold = value & 0xF; + if (m.Map != null) + state.Send(new MapChange(m)); - if ( count < 0 || count > 50 ) - return; + state.Send(new MapPatches()); - KeywordList keyList = m_KeywordList; + state.Send(SeasonChange.Instantiate(m.GetSeason(), true)); - for ( int i = 0; i < count; ++i ) - { - int speechID; - - if ( (i & 1) == 0 ) - { - hold <<= 8; - hold |= pvSrc.ReadByte(); - speechID = hold; - hold = 0; - } - else - { - value = pvSrc.ReadInt16(); - speechID = (value & 0xFFF0) >> 4; - hold = value & 0xF; - } - - if ( !keyList.Contains( speechID ) ) - keyList.Add( speechID ); - } - - text = pvSrc.ReadUTF8StringSafe(); - - keywords = keyList.ToArray(); - } - else - { - text = pvSrc.ReadUnicodeStringSafe(); - - keywords = m_EmptyInts; - } - - text = text.Trim(); - - if ( text.Length <= 0 || text.Length > 128 ) - return; - - type &= ~MessageType.Encoded; - - if ( !Enum.IsDefined( typeof( MessageType ), type ) ) - type = MessageType.Regular; - - from.Language = lang; - from.DoSpeech( text, keywords, type, Utility.ClipDyedHue( hue ) ); - } - - public static void UseReq( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if (from.AccessLevel >= AccessLevel.Counselor || Core.TickCount - from.NextActionTime >= 0) - { - int value = pvSrc.ReadInt32(); - - if ( (value & ~0x7FFFFFFF) != 0 ) - { - from.OnPaperdollRequest(); - } - else - { - Serial s = value; - - if ( s.IsMobile ) - { - Mobile m = World.FindMobile( s ); - - if ( m != null && !m.Deleted ) - from.Use( m ); - } - else if ( s.IsItem ) - { - Item item = World.FindItem( s ); - - if ( item != null && !item.Deleted ) - from.Use( item ); - } - } - - from.NextActionTime = Core.TickCount + Mobile.ActionDelay; - } - else - { - from.SendActionMessage(); - } - } - - public static bool SingleClickProps { get; set; } - - public static void LookReq( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - Serial s = pvSrc.ReadInt32(); - - if ( s.IsMobile ) - { - Mobile m = World.FindMobile( s ); - - if ( m != null && from.CanSee( m ) && Utility.InUpdateRange( from, m ) ) - { - if ( SingleClickProps ) - { - m.OnAosSingleClick( from ); - } - else - { - if ( from.Region.OnSingleClick( from, m ) ) - m.OnSingleClick( from ); - } - } - } - else if ( s.IsItem ) - { - Item item = World.FindItem( s ); - - if ( item != null && !item.Deleted && from.CanSee( item ) && Utility.InUpdateRange( from.Location, item.GetWorldLocation() ) ) - { - if ( SingleClickProps ) - { - item.OnAosSingleClick( from ); - } - else if ( from.Region.OnSingleClick( from, item ) ) - { - if ( item.Parent is Item item1 ) - item1.OnSingleClickContained( from, item ); - - item.OnSingleClick( from ); - } - } - } - } - - public static void PingReq( NetState state, PacketReader pvSrc ) - { - state.Send( PingAck.Instantiate( pvSrc.ReadByte() ) ); - } - - public static void SetUpdateRange( NetState state, PacketReader pvSrc ) - { - state.Send( ChangeUpdateRange.Instantiate( 18 ) ); - } - - private const int BadFood = unchecked( (int)0xBAADF00D ); - private const int BadUOTD = unchecked( (int)0xFFCEFFCE ); - - public static void MovementReq( NetState state, PacketReader pvSrc ) - { - Direction dir = (Direction)pvSrc.ReadByte(); - int seq = pvSrc.ReadByte(); - int key = pvSrc.ReadInt32(); - - Mobile m = state.Mobile; - - if ( (state.Sequence == 0 && seq != 0) || !m.Move( dir ) ) - { - state.Send( new MovementRej( seq, m ) ); - state.Sequence = 0; - - m.ClearFastwalkStack(); - } - else - { - ++seq; - - if ( seq == 256 ) - seq = 1; - - state.Sequence = seq; - } - } - - public static int[] m_ValidAnimations = { - 6, 21, 32, 33, - 100, 101, 102, - 103, 104, 105, - 106, 107, 108, - 109, 110, 111, - 112, 113, 114, - 115, 116, 117, - 118, 119, 120, - 121, 123, 124, - 125, 126, 127, - 128 - }; - - public static int[] ValidAnimations{ get => m_ValidAnimations; - set => m_ValidAnimations = value; - } - - public static void Animate( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - int action = pvSrc.ReadInt32(); - - bool ok = false; - - for ( int i = 0; !ok && i < m_ValidAnimations.Length; ++i ) - ok = ( action == m_ValidAnimations[i] ); - - if ( from != null && ok && from.Alive && from.Body.IsHuman && !from.Mounted ) - from.Animate( action, 7, 1, true, false, 0 ); - } - - public static void QuestArrow( NetState state, PacketReader pvSrc ) - { - bool rightClick = pvSrc.ReadBoolean(); - Mobile from = state.Mobile; - - from?.QuestArrow?.OnClick( rightClick ); - } - - public static void ExtendedCommand( NetState state, PacketReader pvSrc ) - { - int packetID = pvSrc.ReadUInt16(); - - PacketHandler ph = GetExtendedHandler( packetID ); - - if ( ph != null ) - { - if ( ph.Ingame && state.Mobile == null ) - { - Console.WriteLine( "Client: {0}: Sent ingame packet (0xBFx{1:X2}) before having been attached to a mobile", state, packetID ); - state.Dispose(); - } - else if ( ph.Ingame && state.Mobile.Deleted ) - { - state.Dispose(); - } - else - { - ph.OnReceive( state, pvSrc ); - } - } - else - { - pvSrc.Trace( state ); - } - } - - public static void CastSpell( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if ( from == null ) - return; - - Item spellbook = null; - - if ( pvSrc.ReadInt16() == 1 ) - spellbook = World.FindItem( pvSrc.ReadInt32() ); - - int spellID = pvSrc.ReadInt16() - 1; - - EventSink.InvokeCastSpellRequest( new CastSpellRequestEventArgs( from, spellID, spellbook ) ); - } - - public static void BandageTarget(NetState state, PacketReader pvSrc) - { - Mobile from = state.Mobile; - - if (from == null) - return; - - if (from.AccessLevel >= AccessLevel.Counselor || Core.TickCount - from.NextActionTime >= 0) - { - Item bandage = World.FindItem(pvSrc.ReadInt32()); - - if (bandage == null) - return; - - Mobile target = World.FindMobile(pvSrc.ReadInt32()); - - if (target == null) - return; - - EventSink.InvokeBandageTargetRequest(new BandageTargetRequestEventArgs(from, bandage, target)); - - from.NextActionTime = Core.TickCount + Mobile.ActionDelay; - } - else - { - from.SendActionMessage(); - } - } - - public static void ToggleFlying(NetState state, PacketReader pvSrc) - { - state.Mobile.ToggleFlying(); - } - public static void BatchQueryProperties( NetState state, PacketReader pvSrc ) - { - if ( !ObjectPropertyList.Enabled ) - return; - - Mobile from = state.Mobile; - - int length = pvSrc.Size-3; - - if ( length < 0 || (length%4) != 0 ) - return; - - int count = length/4; - - for ( int i = 0; i < count; ++i ) - { - Serial s = pvSrc.ReadInt32(); - - if ( s.IsMobile ) - { - Mobile m = World.FindMobile( s ); - - if ( m != null && from.CanSee( m ) && Utility.InUpdateRange( from, m ) ) - m.SendPropertiesTo( from ); - } - else if ( s.IsItem ) - { - Item item = World.FindItem( s ); - - if ( item != null && !item.Deleted && from.CanSee( item ) && Utility.InUpdateRange( from.Location, item.GetWorldLocation() ) ) - item.SendPropertiesTo( from ); - } - } - } - - public static void QueryProperties( NetState state, PacketReader pvSrc ) - { - if ( !ObjectPropertyList.Enabled ) - return; - - Mobile from = state.Mobile; - - Serial s = pvSrc.ReadInt32(); - - if ( s.IsMobile ) - { - Mobile m = World.FindMobile( s ); - - if ( m != null && from.CanSee( m ) && Utility.InUpdateRange( from, m ) ) - m.SendPropertiesTo( from ); - } - else if ( s.IsItem ) - { - Item item = World.FindItem( s ); - - if ( item != null && !item.Deleted && from.CanSee( item ) && Utility.InUpdateRange( from.Location, item.GetWorldLocation() ) ) - item.SendPropertiesTo( from ); - } - } - - public static void PartyMessage( NetState state, PacketReader pvSrc ) - { - if ( state.Mobile == null ) - return; - - switch ( pvSrc.ReadByte() ) - { - case 0x01: PartyMessage_AddMember( state, pvSrc ); break; - case 0x02: PartyMessage_RemoveMember( state, pvSrc ); break; - case 0x03: PartyMessage_PrivateMessage( state, pvSrc ); break; - case 0x04: PartyMessage_PublicMessage( state, pvSrc ); break; - case 0x06: PartyMessage_SetCanLoot( state, pvSrc ); break; - case 0x08: PartyMessage_Accept( state, pvSrc ); break; - case 0x09: PartyMessage_Decline( state, pvSrc ); break; - default: pvSrc.Trace( state ); break; - } - } - - public static void PartyMessage_AddMember( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnAdd( state.Mobile ); - } - - public static void PartyMessage_RemoveMember( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnRemove( state.Mobile, World.FindMobile( pvSrc.ReadInt32() ) ); - } - - public static void PartyMessage_PrivateMessage( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnPrivateMessage( state.Mobile, World.FindMobile( pvSrc.ReadInt32() ), pvSrc.ReadUnicodeStringSafe() ); - } - - public static void PartyMessage_PublicMessage( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnPublicMessage( state.Mobile, pvSrc.ReadUnicodeStringSafe() ); - } - - public static void PartyMessage_SetCanLoot( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnSetCanLoot( state.Mobile, pvSrc.ReadBoolean() ); - } - - public static void PartyMessage_Accept( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnAccept( state.Mobile, World.FindMobile( pvSrc.ReadInt32() ) ); - } - - public static void PartyMessage_Decline( NetState state, PacketReader pvSrc ) - { - if ( PartyCommands.Handler != null ) - PartyCommands.Handler.OnDecline( state.Mobile, World.FindMobile( pvSrc.ReadInt32() ) ); - } - - public static void StunRequest( NetState state, PacketReader pvSrc ) - { - EventSink.InvokeStunRequest( new StunRequestEventArgs( state.Mobile ) ); - } - - public static void DisarmRequest( NetState state, PacketReader pvSrc ) - { - EventSink.InvokeDisarmRequest( new DisarmRequestEventArgs( state.Mobile ) ); - } - - public static void StatLockChange( NetState state, PacketReader pvSrc ) - { - int stat = pvSrc.ReadByte(); - int lockValue = pvSrc.ReadByte(); - - if ( lockValue > 2 ) lockValue = 0; - - Mobile m = state.Mobile; - - if ( m != null ) - { - switch ( stat ) - { - case 0: m.StrLock = (StatLockType)lockValue; break; - case 1: m.DexLock = (StatLockType)lockValue; break; - case 2: m.IntLock = (StatLockType)lockValue; break; - } - } - } - - public static void ScreenSize( NetState state, PacketReader pvSrc ) - { - int width = pvSrc.ReadInt32(); - int unk = pvSrc.ReadInt32(); - } - - public static void ContextMenuResponse( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - if ( from != null ) - { - ContextMenu menu = from.ContextMenu; - - from.ContextMenu = null; - - if ( menu != null && from == menu.From ) - { - IEntity entity = World.FindEntity( pvSrc.ReadInt32() ); - - if ( entity != null && entity == menu.Target && from.CanSee( entity ) ) - { - Point3D p; - - if ( entity is Mobile ) - p = entity.Location; - else if ( entity is Item item ) - p = item.GetWorldLocation(); - else - return; - - int index = pvSrc.ReadUInt16(); - - if ( index >= 0 && index < menu.Entries.Length ) - { - ContextMenuEntry e = menu.Entries[index]; - - int range = e.Range; - - if ( range == -1 ) - range = 18; - - if ( e.Enabled && from.InRange( p, range ) ) - e.OnClick(); - } - } - } - } - } - - public static void ContextMenuRequest( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - IEntity target = World.FindEntity( pvSrc.ReadInt32() ); - - if ( from != null && target != null && from.Map == target.Map && from.CanSee( target ) ) - { - if ( target is Mobile && !Utility.InUpdateRange( from.Location, target.Location ) ) - return; - - Item item = target as Item; - - if ( item != null && !Utility.InUpdateRange( from.Location, item.GetWorldLocation() ) ) - return; - - if ( !from.CheckContextMenuDisplay( target ) ) - return; - - ContextMenu c = new ContextMenu( from, target ); - - if ( c.Entries.Length > 0 ) - { - if ( item?.RootParent is Mobile mobile && mobile != from && mobile.AccessLevel >= from.AccessLevel ) - { - for ( int i = 0; i < c.Entries.Length; ++i ) - { - if ( !c.Entries[i].NonLocalUse ) - c.Entries[i].Enabled = false; - } - } - - from.ContextMenu = c; - } - } - } - - public static void CloseStatus( NetState state, PacketReader pvSrc ) - { - Serial serial = pvSrc.ReadInt32(); - } - - public static void Language( NetState state, PacketReader pvSrc ) - { - string lang = pvSrc.ReadString( 4 ); - - if ( state.Mobile != null ) - state.Mobile.Language = lang; - } - - public static void AssistVersion( NetState state, PacketReader pvSrc ) - { - int unk = pvSrc.ReadInt32(); - string av = pvSrc.ReadString(); - } - - public static void ClientVersion( NetState state, PacketReader pvSrc ) - { - CV version = state.Version = new CV( pvSrc.ReadString() ); - - EventSink.InvokeClientVersionReceived( new ClientVersionReceivedArgs( state, version ) ); - } - - public static void ClientType( NetState state, PacketReader pvSrc ) - { - pvSrc.ReadUInt16(); - - int type = pvSrc.ReadUInt16(); - CV version = state.Version = new CV( pvSrc.ReadString() ); - - //EventSink.InvokeClientVersionReceived( new ClientVersionReceivedArgs( state, version ) );//todo - } - - public static void MobileQuery( NetState state, PacketReader pvSrc ) - { - Mobile from = state.Mobile; - - pvSrc.ReadInt32(); // 0xEDEDEDED - int type = pvSrc.ReadByte(); - Mobile m = World.FindMobile( pvSrc.ReadInt32() ); - - if ( m != null ) - { - switch ( type ) - { - case 0x00: // Unknown, sent by godclient - { - if ( VerifyGC( state ) ) - Console.WriteLine( "God Client: {0}: Query 0x{1:X2} on {2} '{3}'", state, type, m.Serial, m.Name ); - - break; - } - case 0x04: // Stats - { - m.OnStatsQuery( from ); - break; - } - case 0x05: - { - m.OnSkillsQuery( from ); - break; - } - default: - { - pvSrc.Trace( state ); - break; - } - } - } - } - - public delegate void PlayCharCallback( NetState state, bool val ); - - public static PlayCharCallback ThirdPartyAuthCallback = null, ThirdPartyHackedCallback = null; - - private static byte[] m_ThirdPartyAuthKey = { - 0x9, 0x11, 0x83, (byte)'+', 0x4, 0x17, 0x83, - 0x5, 0x24, 0x85, - 0x7, 0x17, 0x87, - 0x6, 0x19, 0x88, - }; - - private class LoginTimer : Timer - { - private NetState m_State; - private Mobile m_Mobile; - - public LoginTimer( NetState state, Mobile m ) : base( TimeSpan.FromSeconds( 1.0 ), TimeSpan.FromSeconds( 1.0 ) ) - { - m_State = state; - m_Mobile = m; - } - - protected override void OnTick() - { - if ( m_State == null ) - Stop(); - if ( m_State.Version != null ) - { - m_State.BlockAllPackets = false; - DoLogin( m_State, m_Mobile ); - Stop(); - } - } - } - - public static void PlayCharacter( NetState state, PacketReader pvSrc ) - { - pvSrc.ReadInt32(); // 0xEDEDEDED - - string name = pvSrc.ReadString( 30 ); - - pvSrc.Seek( 2, SeekOrigin.Current ); - int flags = pvSrc.ReadInt32(); - - if ( FeatureProtection.DisabledFeatures != 0 && ThirdPartyAuthCallback != null ) - { - bool authOK = false; - - ulong razorFeatures = (((ulong)pvSrc.ReadUInt32())<<32) | ((ulong)pvSrc.ReadUInt32()); - - if ( razorFeatures == (ulong)FeatureProtection.DisabledFeatures ) - { - bool doesNotMatch; - for ( int i = 0; !doesNotMatch && i < m_ThirdPartyAuthKey.Length; i++ ) - doesNotMatch = pvSrc.ReadByte() != m_ThirdPartyAuthKey[i]; - - if ( !doesNotMatch ) - authOK = true; - } - else - { - pvSrc.Seek( 16, SeekOrigin.Current ); - } - - ThirdPartyAuthCallback( state, authOK ); - } - else - { - pvSrc.Seek( 24, SeekOrigin.Current ); - } - - if ( ThirdPartyHackedCallback != null ) - { - pvSrc.Seek( -2, SeekOrigin.Current ); - if ( pvSrc.ReadUInt16() == 0xDEAD ) - ThirdPartyHackedCallback( state, true ); - } - - if ( !state.Running ) - return; - - int charSlot = pvSrc.ReadInt32(); - int clientIP = pvSrc.ReadInt32(); - - IAccount a = state.Account; - - if ( a == null || charSlot < 0 || charSlot >= a.Length ) - { - state.Dispose(); - } - else - { - Mobile m = a[charSlot]; - - // Check if anyone is using this account - for ( int i = 0; i < a.Length; ++i ) - { - Mobile check = a[i]; + state.Send(SupportedFeatures.Instantiate(state)); - if ( check != null && check.Map != Map.Internal && check != m ) - { - Console.WriteLine( "Login: {0}: Account in use", state ); - state.Send( new PopupMessage( PMMessage.CharInWorld ) ); - return; - } - } - - if ( m == null ) - { - state.Dispose(); - return; - } - - - m.NetState?.Dispose(); - - // TODO: Make this wait one tick so we don't have to call it unnecessarily - NetState.ProcessDisposedQueue(); + state.Sequence = 0; - state.Send( new ClientVersionReq() ); - - state.BlockAllPackets = true; - - state.Flags = (ClientFlags)flags; - - state.Mobile = m; - m.NetState = state; - - new LoginTimer( state, m ).Start(); - } - } - - public static void DoLogin( NetState state, Mobile m ) - { - state.Send( new LoginConfirm( m ) ); - - if ( m.Map != null ) - state.Send( new MapChange( m ) ); - - state.Send( new MapPatches() ); - - state.Send( SeasonChange.Instantiate( m.GetSeason(), true ) ); - - state.Send( SupportedFeatures.Instantiate( state ) ); - - state.Sequence = 0; - - if (state.NewMobileIncoming) { - state.Send(new MobileUpdate(m)); - state.Send(new MobileUpdate(m)); - - m.CheckLightLevels(true); - - state.Send(new MobileUpdate(m)); - - state.Send(new MobileIncoming(m, m)); - //state.Send( new MobileAttributes( m ) ); - state.Send(new MobileStatus(m, m)); - state.Send(Network.SetWarMode.Instantiate(m.Warmode)); - - m.SendEverything(); - - state.Send(SupportedFeatures.Instantiate(state)); - state.Send(new MobileUpdate(m)); - //state.Send( new MobileAttributes( m ) ); - state.Send(new MobileStatus(m, m)); - state.Send(Network.SetWarMode.Instantiate(m.Warmode)); - state.Send(new MobileIncoming(m, m)); - } else if ( state.StygianAbyss ) { - state.Send( new MobileUpdate( m ) ); - state.Send( new MobileUpdate( m ) ); - - m.CheckLightLevels( true ); - - state.Send( new MobileUpdate( m ) ); - - state.Send( new MobileIncomingSA( m, m ) ); - //state.Send( new MobileAttributes( m ) ); - state.Send( new MobileStatus( m, m ) ); - state.Send( Network.SetWarMode.Instantiate( m.Warmode ) ); - - m.SendEverything(); - - state.Send( SupportedFeatures.Instantiate( state ) ); - state.Send( new MobileUpdate( m ) ); - //state.Send( new MobileAttributes( m ) ); - state.Send( new MobileStatus( m, m ) ); - state.Send( Network.SetWarMode.Instantiate( m.Warmode ) ); - state.Send( new MobileIncomingSA( m, m ) ); - } else { - state.Send( new MobileUpdateOld( m ) ); - state.Send( new MobileUpdateOld( m ) ); - - m.CheckLightLevels( true ); - - state.Send( new MobileUpdateOld( m ) ); - - state.Send( new MobileIncomingOld( m, m ) ); - //state.Send( new MobileAttributes( m ) ); - state.Send( new MobileStatus( m, m ) ); - state.Send( Network.SetWarMode.Instantiate( m.Warmode ) ); - - m.SendEverything(); - - state.Send( SupportedFeatures.Instantiate( state ) ); - state.Send( new MobileUpdateOld( m ) ); - //state.Send( new MobileAttributes( m ) ); - state.Send( new MobileStatus( m, m ) ); - state.Send( Network.SetWarMode.Instantiate( m.Warmode ) ); - state.Send( new MobileIncomingOld( m, m ) ); - } - - state.Send( LoginComplete.Instance ); - state.Send( new CurrentTime() ); - state.Send( SeasonChange.Instantiate( m.GetSeason(), true ) ); - state.Send( new MapChange( m ) ); - - EventSink.InvokeLogin( new LoginEventArgs( m ) ); - - m.ClearFastwalkStack(); - } - - public static void CreateCharacter( NetState state, PacketReader pvSrc ) - { - int unk1 = pvSrc.ReadInt32(); - int unk2 = pvSrc.ReadInt32(); - int unk3 = pvSrc.ReadByte(); - string name = pvSrc.ReadString( 30 ); - - pvSrc.Seek( 2, SeekOrigin.Current ); - int flags = pvSrc.ReadInt32(); - pvSrc.Seek( 8, SeekOrigin.Current ); - int prof = pvSrc.ReadByte(); - pvSrc.Seek( 15, SeekOrigin.Current ); - - //bool female = pvSrc.ReadBoolean(); - - int genderRace = pvSrc.ReadByte(); - - int str = pvSrc.ReadByte(); - int dex = pvSrc.ReadByte(); - int intl= pvSrc.ReadByte(); - int is1 = pvSrc.ReadByte(); - int vs1 = pvSrc.ReadByte(); - int is2 = pvSrc.ReadByte(); - int vs2 = pvSrc.ReadByte(); - int is3 = pvSrc.ReadByte(); - int vs3 = pvSrc.ReadByte(); - int hue = pvSrc.ReadUInt16(); - int hairVal = pvSrc.ReadInt16(); - int hairHue = pvSrc.ReadInt16(); - int hairValf= pvSrc.ReadInt16(); - int hairHuef= pvSrc.ReadInt16(); - pvSrc.ReadByte(); - int cityIndex = pvSrc.ReadByte(); - int charSlot = pvSrc.ReadInt32(); - int clientIP = pvSrc.ReadInt32(); - int shirtHue = pvSrc.ReadInt16(); - int pantsHue = pvSrc.ReadInt16(); - - /* - Pre-7.0.0.0: - 0x00, 0x01 -> Human Male, Human Female - 0x02, 0x03 -> Elf Male, Elf Female - - Post-7.0.0.0: - 0x00, 0x01 - 0x02, 0x03 -> Human Male, Human Female - 0x04, 0x05 -> Elf Male, Elf Female - 0x05, 0x06 -> Gargoyle Male, Gargoyle Female - */ - - bool female = ((genderRace % 2) != 0); - - Race race; - - if ( state.StygianAbyss ) { - byte raceID = (byte)(genderRace < 4 ? 0 : ((genderRace / 2) - 1)); - race = Race.Races[raceID]; - } else { - race = Race.Races[(byte)(genderRace / 2)]; - } - - if( race == null ) - race = Race.DefaultRace; - - CityInfo[] info = state.CityInfo; - IAccount a = state.Account; - - if ( info == null || a == null || cityIndex < 0 || cityIndex >= info.Length ) - { - state.Dispose(); - } - else - { - // Check if anyone is using this account - for ( int i = 0; i < a.Length; ++i ) - { - Mobile check = a[i]; - - if ( check != null && check.Map != Map.Internal ) - { - Console.WriteLine( "Login: {0}: Account in use", state ); - state.Send( new PopupMessage( PMMessage.CharInWorld ) ); - return; - } - } - - state.Flags = (ClientFlags)flags; - - CharacterCreatedEventArgs args = new CharacterCreatedEventArgs( - state, a, - name, female, hue, - str, dex, intl, - info[cityIndex], - new SkillNameValue[3] - { - new SkillNameValue( (SkillName)is1, vs1 ), - new SkillNameValue( (SkillName)is2, vs2 ), - new SkillNameValue( (SkillName)is3, vs3 ), - }, - shirtHue, pantsHue, - hairVal, hairHue, - hairValf, hairHuef, - prof, - race - ); - - state.Send( new ClientVersionReq() ); - - state.BlockAllPackets = true; - - EventSink.InvokeCharacterCreated( args ); - - Mobile m = args.Mobile; - - if ( m != null ) - { - state.Mobile = m; - m.NetState = state; - new LoginTimer( state, m ).Start(); - } - else - { - state.BlockAllPackets = false; - state.Dispose(); - } - } - } - - public static void CreateCharacter70160( NetState state, PacketReader pvSrc ) - { - int unk1 = pvSrc.ReadInt32(); - int unk2 = pvSrc.ReadInt32(); - int unk3 = pvSrc.ReadByte(); - string name = pvSrc.ReadString( 30 ); - - pvSrc.Seek( 2, SeekOrigin.Current ); - int flags = pvSrc.ReadInt32(); - pvSrc.Seek( 8, SeekOrigin.Current ); - int prof = pvSrc.ReadByte(); - pvSrc.Seek( 15, SeekOrigin.Current ); - - int genderRace = pvSrc.ReadByte(); - - int str = pvSrc.ReadByte(); - int dex = pvSrc.ReadByte(); - int intl= pvSrc.ReadByte(); - int is1 = pvSrc.ReadByte(); - int vs1 = pvSrc.ReadByte(); - int is2 = pvSrc.ReadByte(); - int vs2 = pvSrc.ReadByte(); - int is3 = pvSrc.ReadByte(); - int vs3 = pvSrc.ReadByte(); - int is4 = pvSrc.ReadByte(); - int vs4 = pvSrc.ReadByte(); - - int hue = pvSrc.ReadUInt16(); - int hairVal = pvSrc.ReadInt16(); - int hairHue = pvSrc.ReadInt16(); - int hairValf= pvSrc.ReadInt16(); - int hairHuef= pvSrc.ReadInt16(); - pvSrc.ReadByte(); - int cityIndex = pvSrc.ReadByte(); - int charSlot = pvSrc.ReadInt32(); - int clientIP = pvSrc.ReadInt32(); - int shirtHue = pvSrc.ReadInt16(); - int pantsHue = pvSrc.ReadInt16(); - - /* - 0x00, 0x01 - 0x02, 0x03 -> Human Male, Human Female - 0x04, 0x05 -> Elf Male, Elf Female - 0x05, 0x06 -> Gargoyle Male, Gargoyle Female - */ - - bool female = ((genderRace % 2) != 0); - - Race race = null; - - byte raceID = (byte)(genderRace < 4 ? 0 : ((genderRace / 2) - 1)); - race = Race.Races[raceID]; - - if( race == null ) - race = Race.DefaultRace; - - CityInfo[] info = state.CityInfo; - IAccount a = state.Account; - - if ( info == null || a == null || cityIndex < 0 || cityIndex >= info.Length ) - { - state.Dispose(); - } - else - { - // Check if anyone is using this account - for ( int i = 0; i < a.Length; ++i ) - { - Mobile check = a[i]; - - if ( check != null && check.Map != Map.Internal ) - { - Console.WriteLine( "Login: {0}: Account in use", state ); - state.Send( new PopupMessage( PMMessage.CharInWorld ) ); - return; - } - } - - state.Flags = (ClientFlags)flags; - - CharacterCreatedEventArgs args = new CharacterCreatedEventArgs( - state, a, - name, female, hue, - str, dex, intl, - info[cityIndex], - new SkillNameValue[4] - { - new SkillNameValue( (SkillName)is1, vs1 ), - new SkillNameValue( (SkillName)is2, vs2 ), - new SkillNameValue( (SkillName)is3, vs3 ), - new SkillNameValue( (SkillName)is4, vs4 ), - }, - shirtHue, pantsHue, - hairVal, hairHue, - hairValf, hairHuef, - prof, - race - ); - - state.Send( new ClientVersionReq() ); - - state.BlockAllPackets = true; - - EventSink.InvokeCharacterCreated( args ); - - Mobile m = args.Mobile; - - if ( m != null ) - { - state.Mobile = m; - m.NetState = state; - new LoginTimer( state, m ).Start(); - } - else - { - state.BlockAllPackets = false; - state.Dispose(); - } - } - } - - public static bool ClientVerification { get; set; } = true; - - internal struct AuthIDPersistence { - public DateTime Age; - public ClientVersion Version; - - public AuthIDPersistence( ClientVersion v ) { - Age = DateTime.UtcNow; - Version = v; - } - } - - private const int m_AuthIDWindowSize = 128; - private static Dictionary m_AuthIDWindow = new Dictionary( m_AuthIDWindowSize ); - - private static int GenerateAuthID( NetState state ) - { - if ( m_AuthIDWindow.Count == m_AuthIDWindowSize ) { - int oldestID = 0; - DateTime oldest = DateTime.MaxValue; - - foreach ( KeyValuePair kvp in m_AuthIDWindow ) { - if ( kvp.Value.Age < oldest ) { - oldestID = kvp.Key; - oldest = kvp.Value.Age; - } - } - - m_AuthIDWindow.Remove( oldestID ); - } - - int authID; - - do { - authID = Utility.Random( 1, int.MaxValue - 1 ); - - if ( Utility.RandomBool() ) - authID |= 1<<31; - } while ( m_AuthIDWindow.ContainsKey( authID ) ); - - m_AuthIDWindow[authID] = new AuthIDPersistence( state.Version ); - - return authID; - } - - public static void GameLogin( NetState state, PacketReader pvSrc ) - { - if ( state.SentFirstPacket ) - { - state.Dispose(); - return; - } - - state.SentFirstPacket = true; - - int authID = pvSrc.ReadInt32(); - - if ( m_AuthIDWindow.ContainsKey( authID ) ) { - AuthIDPersistence ap = m_AuthIDWindow[authID]; - m_AuthIDWindow.Remove( authID ); - - state.Version = ap.Version; - } else if ( ClientVerification ) { - Console.WriteLine( "Login: {0}: Invalid client detected, disconnecting", state ); - state.Dispose(); - return; - } - - if ( state.m_AuthID != 0 && authID != state.m_AuthID ) - { - Console.WriteLine( "Login: {0}: Invalid client detected, disconnecting", state ); - state.Dispose(); - return; - } - - if ( state.m_AuthID == 0 && authID != state.m_Seed ) - { - Console.WriteLine( "Login: {0}: Invalid client detected, disconnecting", state ); - state.Dispose(); - return; - } - - string username = pvSrc.ReadString( 30 ); - string password = pvSrc.ReadString( 30 ); - - GameLoginEventArgs e = new GameLoginEventArgs( state, username, password ); - - EventSink.InvokeGameLogin( e ); - - if ( e.Accepted ) - { - state.CityInfo = e.CityInfo; - state.CompressionEnabled = true; - - state.Send( SupportedFeatures.Instantiate( state ) ); - - if ( state.NewCharacterList ) { - state.Send( new CharacterList( state.Account, state.CityInfo ) ); - } else { - state.Send( new CharacterListOld( state.Account, state.CityInfo ) ); - } - } - else - { - state.Dispose(); - } - } - - public static void PlayServer( NetState state, PacketReader pvSrc ) - { - int index = pvSrc.ReadInt16(); - ServerInfo[] info = state.ServerInfo; - IAccount a = state.Account; - - if ( info == null || a == null || index < 0 || index >= info.Length ) - { - state.Dispose(); - } - else - { - ServerInfo si = info[index]; - - state.m_AuthID = PlayServerAck.m_AuthID = GenerateAuthID( state ); - - state.SentFirstPacket = false; - state.Send( new PlayServerAck( si ) ); - } - } - - public static void LoginServerSeed( NetState state, PacketReader pvSrc ) - { - state.m_Seed = pvSrc.ReadInt32(); - state.Seeded = true; - - if ( state.m_Seed == 0 ) - { - Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", state); - state.Dispose(); - return; - } - - int clientMaj = pvSrc.ReadInt32(); - int clientMin = pvSrc.ReadInt32(); - int clientRev = pvSrc.ReadInt32(); - int clientPat = pvSrc.ReadInt32(); - - state.Version = new ClientVersion( clientMaj, clientMin, clientRev, clientPat ); - } - - public static void CrashReport(NetState state, PacketReader pvSrc) - { - byte clientMaj = pvSrc.ReadByte(); - byte clientMin = pvSrc.ReadByte(); - byte clientRev = pvSrc.ReadByte(); - byte clientPat = pvSrc.ReadByte(); - - ushort x = pvSrc.ReadUInt16(); - ushort y = pvSrc.ReadUInt16(); - sbyte z = pvSrc.ReadSByte(); - byte map = pvSrc.ReadByte(); - - string account = pvSrc.ReadString(32); - string character = pvSrc.ReadString(32); - string ip = pvSrc.ReadString(15); - - int unk1 = pvSrc.ReadInt32(); - int exception = pvSrc.ReadInt32(); - - string process = pvSrc.ReadString(100); - string report = pvSrc.ReadString(100); - - pvSrc.ReadByte(); // 0x00 - - int offset = pvSrc.ReadInt32(); - - int count = (int)pvSrc.ReadByte(); - - for (int i = 0; i < count; i++) { - int address = pvSrc.ReadInt32(); - } - } - - public static void AccountLogin(NetState state, PacketReader pvSrc) - { - if ( state.SentFirstPacket ) - { - state.Dispose(); - return; - } - - state.SentFirstPacket = true; - - string username = pvSrc.ReadString( 30 ); - string password = pvSrc.ReadString( 30 ); - - AccountLoginEventArgs e = new AccountLoginEventArgs( state, username, password ); - - EventSink.InvokeAccountLogin( e ); - - if ( e.Accepted ) - AccountLogin_ReplyAck( state ); - else - AccountLogin_ReplyRej( state, e.RejectReason ); - } - - public static void AccountLogin_ReplyAck( NetState state ) - { - ServerListEventArgs e = new ServerListEventArgs( state, state.Account ); - - EventSink.InvokeServerList( e ); - - if ( e.Rejected ) - { - state.Account = null; - state.Send( new AccountLoginRej( ALRReason.BadComm ) ); - state.Dispose(); - } - else - { - ServerInfo[] info = e.Servers.ToArray(); - - state.ServerInfo = info; - - state.Send( new AccountLoginAck( info ) ); - } - } - - public static void AccountLogin_ReplyRej( NetState state, ALRReason reason ) - { - state.Send( new AccountLoginRej( reason ) ); - state.Dispose(); - } - } -} + if (state.NewMobileIncoming) + { + state.Send(new MobileUpdate(m)); + state.Send(new MobileUpdate(m)); + + m.CheckLightLevels(true); + + state.Send(new MobileUpdate(m)); + + state.Send(new MobileIncoming(m, m)); + //state.Send( new MobileAttributes( m ) ); + state.Send(new MobileStatus(m, m)); + state.Send(Network.SetWarMode.Instantiate(m.Warmode)); + + m.SendEverything(); + + state.Send(SupportedFeatures.Instantiate(state)); + state.Send(new MobileUpdate(m)); + //state.Send( new MobileAttributes( m ) ); + state.Send(new MobileStatus(m, m)); + state.Send(Network.SetWarMode.Instantiate(m.Warmode)); + state.Send(new MobileIncoming(m, m)); + } + else if (state.StygianAbyss) + { + state.Send(new MobileUpdate(m)); + state.Send(new MobileUpdate(m)); + + m.CheckLightLevels(true); + + state.Send(new MobileUpdate(m)); + + state.Send(new MobileIncomingSA(m, m)); + //state.Send( new MobileAttributes( m ) ); + state.Send(new MobileStatus(m, m)); + state.Send(Network.SetWarMode.Instantiate(m.Warmode)); + + m.SendEverything(); + + state.Send(SupportedFeatures.Instantiate(state)); + state.Send(new MobileUpdate(m)); + //state.Send( new MobileAttributes( m ) ); + state.Send(new MobileStatus(m, m)); + state.Send(Network.SetWarMode.Instantiate(m.Warmode)); + state.Send(new MobileIncomingSA(m, m)); + } + else + { + state.Send(new MobileUpdateOld(m)); + state.Send(new MobileUpdateOld(m)); + + m.CheckLightLevels(true); + + state.Send(new MobileUpdateOld(m)); + + state.Send(new MobileIncomingOld(m, m)); + //state.Send( new MobileAttributes( m ) ); + state.Send(new MobileStatus(m, m)); + state.Send(Network.SetWarMode.Instantiate(m.Warmode)); + + m.SendEverything(); + + state.Send(SupportedFeatures.Instantiate(state)); + state.Send(new MobileUpdateOld(m)); + //state.Send( new MobileAttributes( m ) ); + state.Send(new MobileStatus(m, m)); + state.Send(Network.SetWarMode.Instantiate(m.Warmode)); + state.Send(new MobileIncomingOld(m, m)); + } + + state.Send(LoginComplete.Instance); + state.Send(new CurrentTime()); + state.Send(SeasonChange.Instantiate(m.GetSeason(), true)); + state.Send(new MapChange(m)); + + EventSink.InvokeLogin(new LoginEventArgs(m)); + + m.ClearFastwalkStack(); + } + + public static void CreateCharacter(NetState state, PacketReader pvSrc) + { + int unk1 = pvSrc.ReadInt32(); + int unk2 = pvSrc.ReadInt32(); + int unk3 = pvSrc.ReadByte(); + string name = pvSrc.ReadString(30); + + pvSrc.Seek(2, SeekOrigin.Current); + int flags = pvSrc.ReadInt32(); + pvSrc.Seek(8, SeekOrigin.Current); + int prof = pvSrc.ReadByte(); + pvSrc.Seek(15, SeekOrigin.Current); + + //bool female = pvSrc.ReadBoolean(); + + int genderRace = pvSrc.ReadByte(); + + int str = pvSrc.ReadByte(); + int dex = pvSrc.ReadByte(); + int intl = pvSrc.ReadByte(); + int is1 = pvSrc.ReadByte(); + int vs1 = pvSrc.ReadByte(); + int is2 = pvSrc.ReadByte(); + int vs2 = pvSrc.ReadByte(); + int is3 = pvSrc.ReadByte(); + int vs3 = pvSrc.ReadByte(); + int hue = pvSrc.ReadUInt16(); + int hairVal = pvSrc.ReadInt16(); + int hairHue = pvSrc.ReadInt16(); + int hairValf = pvSrc.ReadInt16(); + int hairHuef = pvSrc.ReadInt16(); + pvSrc.ReadByte(); + int cityIndex = pvSrc.ReadByte(); + int charSlot = pvSrc.ReadInt32(); + int clientIP = pvSrc.ReadInt32(); + int shirtHue = pvSrc.ReadInt16(); + int pantsHue = pvSrc.ReadInt16(); + + /* + Pre-7.0.0.0: + 0x00, 0x01 -> Human Male, Human Female + 0x02, 0x03 -> Elf Male, Elf Female + + Post-7.0.0.0: + 0x00, 0x01 + 0x02, 0x03 -> Human Male, Human Female + 0x04, 0x05 -> Elf Male, Elf Female + 0x05, 0x06 -> Gargoyle Male, Gargoyle Female + */ + + bool female = genderRace % 2 != 0; + + Race race; + + if (state.StygianAbyss) + { + byte raceID = (byte)(genderRace < 4 ? 0 : genderRace / 2 - 1); + race = Race.Races[raceID]; + } + else + { + race = Race.Races[(byte)(genderRace / 2)]; + } + + if (race == null) + race = Race.DefaultRace; + + CityInfo[] info = state.CityInfo; + IAccount a = state.Account; + + if (info == null || a == null || cityIndex < 0 || cityIndex >= info.Length) + { + state.Dispose(); + } + else + { + // Check if anyone is using this account + for (int i = 0; i < a.Length; ++i) + { + Mobile check = a[i]; + + if (check != null && check.Map != Map.Internal) + { + Console.WriteLine("Login: {0}: Account in use", state); + state.Send(new PopupMessage(PMMessage.CharInWorld)); + return; + } + } + + state.Flags = (ClientFlags)flags; + + CharacterCreatedEventArgs args = new CharacterCreatedEventArgs( + state, a, + name, female, hue, + str, dex, intl, + info[cityIndex], + new SkillNameValue[3] + { + new SkillNameValue((SkillName)is1, vs1), + new SkillNameValue((SkillName)is2, vs2), + new SkillNameValue((SkillName)is3, vs3) + }, + shirtHue, pantsHue, + hairVal, hairHue, + hairValf, hairHuef, + prof, + race + ); + + state.Send(new ClientVersionReq()); + + state.BlockAllPackets = true; + + EventSink.InvokeCharacterCreated(args); + + Mobile m = args.Mobile; + + if (m != null) + { + state.Mobile = m; + m.NetState = state; + new LoginTimer(state, m).Start(); + } + else + { + state.BlockAllPackets = false; + state.Dispose(); + } + } + } + + public static void CreateCharacter70160(NetState state, PacketReader pvSrc) + { + int unk1 = pvSrc.ReadInt32(); + int unk2 = pvSrc.ReadInt32(); + int unk3 = pvSrc.ReadByte(); + string name = pvSrc.ReadString(30); + + pvSrc.Seek(2, SeekOrigin.Current); + int flags = pvSrc.ReadInt32(); + pvSrc.Seek(8, SeekOrigin.Current); + int prof = pvSrc.ReadByte(); + pvSrc.Seek(15, SeekOrigin.Current); + + int genderRace = pvSrc.ReadByte(); + + int str = pvSrc.ReadByte(); + int dex = pvSrc.ReadByte(); + int intl = pvSrc.ReadByte(); + int is1 = pvSrc.ReadByte(); + int vs1 = pvSrc.ReadByte(); + int is2 = pvSrc.ReadByte(); + int vs2 = pvSrc.ReadByte(); + int is3 = pvSrc.ReadByte(); + int vs3 = pvSrc.ReadByte(); + int is4 = pvSrc.ReadByte(); + int vs4 = pvSrc.ReadByte(); + + int hue = pvSrc.ReadUInt16(); + int hairVal = pvSrc.ReadInt16(); + int hairHue = pvSrc.ReadInt16(); + int hairValf = pvSrc.ReadInt16(); + int hairHuef = pvSrc.ReadInt16(); + pvSrc.ReadByte(); + int cityIndex = pvSrc.ReadByte(); + int charSlot = pvSrc.ReadInt32(); + int clientIP = pvSrc.ReadInt32(); + int shirtHue = pvSrc.ReadInt16(); + int pantsHue = pvSrc.ReadInt16(); + + /* + 0x00, 0x01 + 0x02, 0x03 -> Human Male, Human Female + 0x04, 0x05 -> Elf Male, Elf Female + 0x05, 0x06 -> Gargoyle Male, Gargoyle Female + */ + + bool female = genderRace % 2 != 0; + + Race race = null; + + byte raceID = (byte)(genderRace < 4 ? 0 : genderRace / 2 - 1); + race = Race.Races[raceID]; + + if (race == null) + race = Race.DefaultRace; + + CityInfo[] info = state.CityInfo; + IAccount a = state.Account; + + if (info == null || a == null || cityIndex < 0 || cityIndex >= info.Length) + { + state.Dispose(); + } + else + { + // Check if anyone is using this account + for (int i = 0; i < a.Length; ++i) + { + Mobile check = a[i]; + + if (check != null && check.Map != Map.Internal) + { + Console.WriteLine("Login: {0}: Account in use", state); + state.Send(new PopupMessage(PMMessage.CharInWorld)); + return; + } + } + + state.Flags = (ClientFlags)flags; + + CharacterCreatedEventArgs args = new CharacterCreatedEventArgs( + state, a, + name, female, hue, + str, dex, intl, + info[cityIndex], + new SkillNameValue[4] + { + new SkillNameValue((SkillName)is1, vs1), + new SkillNameValue((SkillName)is2, vs2), + new SkillNameValue((SkillName)is3, vs3), + new SkillNameValue((SkillName)is4, vs4) + }, + shirtHue, pantsHue, + hairVal, hairHue, + hairValf, hairHuef, + prof, + race + ); + + state.Send(new ClientVersionReq()); + + state.BlockAllPackets = true; + + EventSink.InvokeCharacterCreated(args); + + Mobile m = args.Mobile; + + if (m != null) + { + state.Mobile = m; + m.NetState = state; + new LoginTimer(state, m).Start(); + } + else + { + state.BlockAllPackets = false; + state.Dispose(); + } + } + } + + private static int GenerateAuthID(NetState state) + { + if (m_AuthIDWindow.Count == m_AuthIDWindowSize) + { + int oldestID = 0; + DateTime oldest = DateTime.MaxValue; + + foreach (KeyValuePair kvp in m_AuthIDWindow) + if (kvp.Value.Age < oldest) + { + oldestID = kvp.Key; + oldest = kvp.Value.Age; + } + + m_AuthIDWindow.Remove(oldestID); + } + + int authID; + + do + { + authID = Utility.Random(1, int.MaxValue - 1); + + if (Utility.RandomBool()) + authID |= 1 << 31; + } while (m_AuthIDWindow.ContainsKey(authID)); + + m_AuthIDWindow[authID] = new AuthIDPersistence(state.Version); + + return authID; + } + + public static void GameLogin(NetState state, PacketReader pvSrc) + { + if (state.SentFirstPacket) + { + state.Dispose(); + return; + } + + state.SentFirstPacket = true; + + int authID = pvSrc.ReadInt32(); + + if (m_AuthIDWindow.ContainsKey(authID)) + { + AuthIDPersistence ap = m_AuthIDWindow[authID]; + m_AuthIDWindow.Remove(authID); + + state.Version = ap.Version; + } + else if (ClientVerification) + { + Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", state); + state.Dispose(); + return; + } + + if (state.m_AuthID != 0 && authID != state.m_AuthID) + { + Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", state); + state.Dispose(); + return; + } + + if (state.m_AuthID == 0 && authID != state.m_Seed) + { + Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", state); + state.Dispose(); + return; + } + + string username = pvSrc.ReadString(30); + string password = pvSrc.ReadString(30); + + GameLoginEventArgs e = new GameLoginEventArgs(state, username, password); + + EventSink.InvokeGameLogin(e); + + if (e.Accepted) + { + state.CityInfo = e.CityInfo; + state.CompressionEnabled = true; + + state.Send(SupportedFeatures.Instantiate(state)); + + if (state.NewCharacterList) + state.Send(new CharacterList(state.Account, state.CityInfo)); + else + state.Send(new CharacterListOld(state.Account, state.CityInfo)); + } + else + { + state.Dispose(); + } + } + + public static void PlayServer(NetState state, PacketReader pvSrc) + { + int index = pvSrc.ReadInt16(); + ServerInfo[] info = state.ServerInfo; + IAccount a = state.Account; + + if (info == null || a == null || index < 0 || index >= info.Length) + { + state.Dispose(); + } + else + { + ServerInfo si = info[index]; + + state.m_AuthID = PlayServerAck.m_AuthID = GenerateAuthID(state); + + state.SentFirstPacket = false; + state.Send(new PlayServerAck(si)); + } + } + + public static void LoginServerSeed(NetState state, PacketReader pvSrc) + { + state.m_Seed = pvSrc.ReadInt32(); + state.Seeded = true; + + if (state.m_Seed == 0) + { + Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", state); + state.Dispose(); + return; + } + + int clientMaj = pvSrc.ReadInt32(); + int clientMin = pvSrc.ReadInt32(); + int clientRev = pvSrc.ReadInt32(); + int clientPat = pvSrc.ReadInt32(); + + state.Version = new ClientVersion(clientMaj, clientMin, clientRev, clientPat); + } + + public static void CrashReport(NetState state, PacketReader pvSrc) + { + byte clientMaj = pvSrc.ReadByte(); + byte clientMin = pvSrc.ReadByte(); + byte clientRev = pvSrc.ReadByte(); + byte clientPat = pvSrc.ReadByte(); + + ushort x = pvSrc.ReadUInt16(); + ushort y = pvSrc.ReadUInt16(); + sbyte z = pvSrc.ReadSByte(); + byte map = pvSrc.ReadByte(); + + string account = pvSrc.ReadString(32); + string character = pvSrc.ReadString(32); + string ip = pvSrc.ReadString(15); + + int unk1 = pvSrc.ReadInt32(); + int exception = pvSrc.ReadInt32(); + + string process = pvSrc.ReadString(100); + string report = pvSrc.ReadString(100); + + pvSrc.ReadByte(); // 0x00 + + int offset = pvSrc.ReadInt32(); + + int count = pvSrc.ReadByte(); + + for (int i = 0; i < count; i++) + { + int address = pvSrc.ReadInt32(); + } + } + + public static void AccountLogin(NetState state, PacketReader pvSrc) + { + if (state.SentFirstPacket) + { + state.Dispose(); + return; + } + + state.SentFirstPacket = true; + + string username = pvSrc.ReadString(30); + string password = pvSrc.ReadString(30); + + AccountLoginEventArgs e = new AccountLoginEventArgs(state, username, password); + + EventSink.InvokeAccountLogin(e); + + if (e.Accepted) + AccountLogin_ReplyAck(state); + else + AccountLogin_ReplyRej(state, e.RejectReason); + } + + public static void AccountLogin_ReplyAck(NetState state) + { + ServerListEventArgs e = new ServerListEventArgs(state, state.Account); + + EventSink.InvokeServerList(e); + + if (e.Rejected) + { + state.Account = null; + state.Send(new AccountLoginRej(ALRReason.BadComm)); + state.Dispose(); + } + else + { + ServerInfo[] info = e.Servers.ToArray(); + + state.ServerInfo = info; + + state.Send(new AccountLoginAck(info)); + } + } + + public static void AccountLogin_ReplyRej(NetState state, ALRReason reason) + { + state.Send(new AccountLoginRej(reason)); + state.Dispose(); + } + + private class LoginTimer : Timer + { + private Mobile m_Mobile; + private NetState m_State; + + public LoginTimer(NetState state, Mobile m) : base(TimeSpan.FromSeconds(1.0), TimeSpan.FromSeconds(1.0)) + { + m_State = state; + m_Mobile = m; + } + + protected override void OnTick() + { + if (m_State == null) + Stop(); + if (m_State.Version != null) + { + m_State.BlockAllPackets = false; + DoLogin(m_State, m_Mobile); + Stop(); + } + } + } + + internal struct AuthIDPersistence + { + public DateTime Age; + public ClientVersion Version; + + public AuthIDPersistence(ClientVersion v) + { + Age = DateTime.UtcNow; + Version = v; + } + } + } +} \ No newline at end of file diff --git a/Server/Network/PacketReader.cs b/Server/Network/PacketReader.cs index 6fd2b50e1..cda8dbc86 100644 --- a/Server/Network/PacketReader.cs +++ b/Server/Network/PacketReader.cs @@ -18,426 +18,420 @@ * ***************************************************************************/ -using System; -using System.Text; using System.IO; +using System.Text; namespace Server.Network { - public class PacketReader - { - private int m_Index; - - public PacketReader( byte[] data, int size, bool fixedSize ) - { - Buffer = data; - Size = size; - m_Index = fixedSize ? 1 : 3; - } - - public byte[] Buffer { get; } - - public int Size { get; } - - public void Trace( NetState state ) - { - try - { - using ( StreamWriter sw = new StreamWriter( "Packets.log", true ) ) - { - byte[] buffer = Buffer; - - if ( buffer.Length > 0 ) - sw.WriteLine( "Client: {0}: Unhandled packet 0x{1:X2}", state, buffer[0] ); - - using ( MemoryStream ms = new MemoryStream( buffer ) ) - Utility.FormatBuffer( sw, ms, buffer.Length ); - - sw.WriteLine(); - sw.WriteLine(); - } - } - catch - { - } - } - - public int Seek( int offset, SeekOrigin origin ) - { - switch ( origin ) - { - case SeekOrigin.Begin: m_Index = offset; break; - case SeekOrigin.Current: m_Index += offset; break; - case SeekOrigin.End: m_Index = Size - offset; break; - } - - return m_Index; - } + public class PacketReader + { + private int m_Index; + + public PacketReader(byte[] data, int size, bool fixedSize) + { + Buffer = data; + Size = size; + m_Index = fixedSize ? 1 : 3; + } + + public byte[] Buffer{ get; } + + public int Size{ get; } + + public void Trace(NetState state) + { + try + { + using (StreamWriter sw = new StreamWriter("Packets.log", true)) + { + byte[] buffer = Buffer; + + if (buffer.Length > 0) + sw.WriteLine("Client: {0}: Unhandled packet 0x{1:X2}", state, buffer[0]); + + using (MemoryStream ms = new MemoryStream(buffer)) + { + Utility.FormatBuffer(sw, ms, buffer.Length); + } + + sw.WriteLine(); + sw.WriteLine(); + } + } + catch + { + } + } + + public int Seek(int offset, SeekOrigin origin) + { + switch (origin) + { + case SeekOrigin.Begin: + m_Index = offset; + break; + case SeekOrigin.Current: + m_Index += offset; + break; + case SeekOrigin.End: + m_Index = Size - offset; + break; + } + + return m_Index; + } + + public int ReadInt32() + { + if (m_Index + 4 > Size) + return 0; + + return (Buffer[m_Index++] << 24) + | (Buffer[m_Index++] << 16) + | (Buffer[m_Index++] << 8) + | Buffer[m_Index++]; + } + + public short ReadInt16() + { + if (m_Index + 2 > Size) + return 0; + + return (short)((Buffer[m_Index++] << 8) | Buffer[m_Index++]); + } + + public byte ReadByte() + { + if (m_Index + 1 > Size) + return 0; + + return Buffer[m_Index++]; + } + + public uint ReadUInt32() + { + if (m_Index + 4 > Size) + return 0; - public int ReadInt32() - { - if ( (m_Index + 4) > Size ) - return 0; - - return (Buffer[m_Index++] << 24) - | (Buffer[m_Index++] << 16) - | (Buffer[m_Index++] << 8) - | Buffer[m_Index++]; - } - - public short ReadInt16() - { - if ( (m_Index + 2) > Size ) - return 0; + return (uint)((Buffer[m_Index++] << 24) | (Buffer[m_Index++] << 16) | (Buffer[m_Index++] << 8) | + Buffer[m_Index++]); + } - return (short)((Buffer[m_Index++] << 8) | Buffer[m_Index++]); - } - - public byte ReadByte() - { - if ( (m_Index + 1) > Size ) - return 0; + public ushort ReadUInt16() + { + if (m_Index + 2 > Size) + return 0; + + return (ushort)((Buffer[m_Index++] << 8) | Buffer[m_Index++]); + } + + public sbyte ReadSByte() + { + if (m_Index + 1 > Size) + return 0; + + return (sbyte)Buffer[m_Index++]; + } - return Buffer[m_Index++]; - } - - public uint ReadUInt32() - { - if ( (m_Index + 4) > Size ) - return 0; + public bool ReadBoolean() + { + if (m_Index + 1 > Size) + return false; - return (uint)((Buffer[m_Index++] << 24) | (Buffer[m_Index++] << 16) | (Buffer[m_Index++] << 8) | Buffer[m_Index++]); - } + return Buffer[m_Index++] != 0; + } - public ushort ReadUInt16() - { - if ( (m_Index + 2) > Size ) - return 0; + public string ReadUnicodeStringLE() + { + StringBuilder sb = new StringBuilder(); - return (ushort)((Buffer[m_Index++] << 8) | Buffer[m_Index++]); - } + int c; - public sbyte ReadSByte() - { - if ( (m_Index + 1) > Size ) - return 0; - - return (sbyte)Buffer[m_Index++]; - } - - public bool ReadBoolean() - { - if ( (m_Index + 1) > Size ) - return false; + while (m_Index + 1 < Size && (c = Buffer[m_Index++] | (Buffer[m_Index++] << 8)) != 0) + sb.Append((char)c); - return ( Buffer[m_Index++] != 0 ); - } + return sb.ToString(); + } - public string ReadUnicodeStringLE() - { - StringBuilder sb = new StringBuilder(); + public string ReadUnicodeStringLESafe(int fixedLength) + { + int bound = m_Index + (fixedLength << 1); + int end = bound; - int c; + if (bound > Size) + bound = Size; - while ( (m_Index + 1) < Size && (c = (Buffer[m_Index++] | (Buffer[m_Index++] << 8))) != 0 ) - sb.Append( (char)c ); + StringBuilder sb = new StringBuilder(); - return sb.ToString(); - } + int c; - public string ReadUnicodeStringLESafe( int fixedLength ) - { - int bound = m_Index + (fixedLength << 1); - int end = bound; + while (m_Index + 1 < bound && (c = Buffer[m_Index++] | (Buffer[m_Index++] << 8)) != 0) + if (IsSafeChar(c)) + sb.Append((char)c); - if ( bound > Size ) - bound = Size; + m_Index = end; - StringBuilder sb = new StringBuilder(); + return sb.ToString(); + } - int c; + public string ReadUnicodeStringLESafe() + { + StringBuilder sb = new StringBuilder(); - while ( (m_Index + 1) < bound && (c = (Buffer[m_Index++] | (Buffer[m_Index++] << 8))) != 0 ) - { - if ( IsSafeChar( c ) ) - sb.Append( (char)c ); - } + int c; - m_Index = end; + while (m_Index + 1 < Size && (c = Buffer[m_Index++] | (Buffer[m_Index++] << 8)) != 0) + if (IsSafeChar(c)) + sb.Append((char)c); - return sb.ToString(); - } + return sb.ToString(); + } - public string ReadUnicodeStringLESafe() - { - StringBuilder sb = new StringBuilder(); + public string ReadUnicodeStringSafe() + { + StringBuilder sb = new StringBuilder(); - int c; + int c; - while ( (m_Index + 1) < Size && (c = (Buffer[m_Index++] | (Buffer[m_Index++] << 8))) != 0 ) - { - if ( IsSafeChar( c ) ) - sb.Append( (char)c ); - } + while (m_Index + 1 < Size && (c = (Buffer[m_Index++] << 8) | Buffer[m_Index++]) != 0) + if (IsSafeChar(c)) + sb.Append((char)c); - return sb.ToString(); - } + return sb.ToString(); + } - public string ReadUnicodeStringSafe() - { - StringBuilder sb = new StringBuilder(); + public string ReadUnicodeString() + { + StringBuilder sb = new StringBuilder(); - int c; + int c; - while ( (m_Index + 1) < Size && (c = ((Buffer[m_Index++] << 8) | Buffer[m_Index++])) != 0 ) - { - if ( IsSafeChar( c ) ) - sb.Append( (char)c ); - } + while (m_Index + 1 < Size && (c = (Buffer[m_Index++] << 8) | Buffer[m_Index++]) != 0) + sb.Append((char)c); - return sb.ToString(); - } + return sb.ToString(); + } - public string ReadUnicodeString() - { - StringBuilder sb = new StringBuilder(); + public bool IsSafeChar(int c) + { + return c >= 0x20 && c < 0xFFFE; + } - int c; + public string ReadUTF8StringSafe(int fixedLength) + { + if (m_Index >= Size) + { + m_Index += fixedLength; + return string.Empty; + } - while ( (m_Index + 1) < Size && (c = ((Buffer[m_Index++] << 8) | Buffer[m_Index++])) != 0 ) - sb.Append( (char)c ); + int bound = m_Index + fixedLength; + //int end = bound; - return sb.ToString(); - } + if (bound > Size) + bound = Size; - public bool IsSafeChar( int c ) - { - return ( c >= 0x20 && c < 0xFFFE ); - } + int count = 0; + int index = m_Index; + int start = m_Index; - public string ReadUTF8StringSafe( int fixedLength ) - { - if ( m_Index >= Size ) - { - m_Index += fixedLength; - return string.Empty; - } + while (index < bound && Buffer[index++] != 0) + ++count; - int bound = m_Index + fixedLength; - //int end = bound; + index = 0; - if ( bound > Size ) - bound = Size; + byte[] buffer = new byte[count]; + int value = 0; - int count = 0; - int index = m_Index; - int start = m_Index; + while (m_Index < bound && (value = Buffer[m_Index++]) != 0) + buffer[index++] = (byte)value; - while ( index < bound && Buffer[index++] != 0 ) - ++count; + string s = Utility.UTF8.GetString(buffer); - index = 0; + bool isSafe = true; - byte[] buffer = new byte[count]; - int value = 0; + for (int i = 0; isSafe && i < s.Length; ++i) + isSafe = IsSafeChar(s[i]); - while ( m_Index < bound && (value = Buffer[m_Index++]) != 0 ) - buffer[index++] = (byte)value; + m_Index = start + fixedLength; - string s = Utility.UTF8.GetString( buffer ); + if (isSafe) + return s; - bool isSafe = true; + StringBuilder sb = new StringBuilder(s.Length); - for ( int i = 0; isSafe && i < s.Length; ++i ) - isSafe = IsSafeChar( (int) s[i] ); + for (int i = 0; i < s.Length; ++i) + if (IsSafeChar(s[i])) + sb.Append(s[i]); - m_Index = start + fixedLength; + return sb.ToString(); + } - if ( isSafe ) - return s; + public string ReadUTF8StringSafe() + { + if (m_Index >= Size) + return string.Empty; - StringBuilder sb = new StringBuilder( s.Length ); + int count = 0; + int index = m_Index; - for ( int i = 0; i < s.Length; ++i ) - if ( IsSafeChar( (int) s[i] ) ) - sb.Append( s[i] ); + while (index < Size && Buffer[index++] != 0) + ++count; - return sb.ToString(); - } + index = 0; - public string ReadUTF8StringSafe() - { - if ( m_Index >= Size ) - return string.Empty; + byte[] buffer = new byte[count]; + int value = 0; - int count = 0; - int index = m_Index; + while (m_Index < Size && (value = Buffer[m_Index++]) != 0) + buffer[index++] = (byte)value; - while ( index < Size && Buffer[index++] != 0 ) - ++count; + string s = Utility.UTF8.GetString(buffer); - index = 0; + bool isSafe = true; - byte[] buffer = new byte[count]; - int value = 0; + for (int i = 0; isSafe && i < s.Length; ++i) + isSafe = IsSafeChar(s[i]); - while ( m_Index < Size && (value = Buffer[m_Index++]) != 0 ) - buffer[index++] = (byte)value; + if (isSafe) + return s; - string s = Utility.UTF8.GetString( buffer ); + StringBuilder sb = new StringBuilder(s.Length); - bool isSafe = true; + for (int i = 0; i < s.Length; ++i) + if (IsSafeChar(s[i])) + sb.Append(s[i]); - for ( int i = 0; isSafe && i < s.Length; ++i ) - isSafe = IsSafeChar( (int) s[i] ); + return sb.ToString(); + } - if ( isSafe ) - return s; + public string ReadUTF8String() + { + if (m_Index >= Size) + return string.Empty; - StringBuilder sb = new StringBuilder( s.Length ); + int count = 0; + int index = m_Index; - for ( int i = 0; i < s.Length; ++i ) - { - if ( IsSafeChar( (int) s[i] ) ) - sb.Append( s[i] ); - } + while (index < Size && Buffer[index++] != 0) + ++count; - return sb.ToString(); - } + index = 0; - public string ReadUTF8String() - { - if ( m_Index >= Size ) - return string.Empty; + byte[] buffer = new byte[count]; + int value = 0; - int count = 0; - int index = m_Index; + while (m_Index < Size && (value = Buffer[m_Index++]) != 0) + buffer[index++] = (byte)value; - while ( index < Size && Buffer[index++] != 0 ) - ++count; + return Utility.UTF8.GetString(buffer); + } - index = 0; + public string ReadString() + { + StringBuilder sb = new StringBuilder(); - byte[] buffer = new byte[count]; - int value = 0; + int c; - while ( m_Index < Size && (value = Buffer[m_Index++]) != 0 ) - buffer[index++] = (byte)value; + while (m_Index < Size && (c = Buffer[m_Index++]) != 0) + sb.Append((char)c); - return Utility.UTF8.GetString( buffer ); - } + return sb.ToString(); + } - public string ReadString() - { - StringBuilder sb = new StringBuilder(); + public string ReadStringSafe() + { + StringBuilder sb = new StringBuilder(); - int c; + int c; - while ( m_Index < Size && (c = Buffer[m_Index++]) != 0 ) - sb.Append( (char)c ); + while (m_Index < Size && (c = Buffer[m_Index++]) != 0) + if (IsSafeChar(c)) + sb.Append((char)c); - return sb.ToString(); - } + return sb.ToString(); + } - public string ReadStringSafe() - { - StringBuilder sb = new StringBuilder(); + public string ReadUnicodeStringSafe(int fixedLength) + { + int bound = m_Index + (fixedLength << 1); + int end = bound; - int c; + if (bound > Size) + bound = Size; - while ( m_Index < Size && (c = Buffer[m_Index++]) != 0 ) - { - if ( IsSafeChar( c ) ) - sb.Append( (char)c ); - } + StringBuilder sb = new StringBuilder(); - return sb.ToString(); - } + int c; - public string ReadUnicodeStringSafe( int fixedLength ) - { - int bound = m_Index + (fixedLength << 1); - int end = bound; + while (m_Index + 1 < bound && (c = (Buffer[m_Index++] << 8) | Buffer[m_Index++]) != 0) + if (IsSafeChar(c)) + sb.Append((char)c); - if ( bound > Size ) - bound = Size; + m_Index = end; - StringBuilder sb = new StringBuilder(); + return sb.ToString(); + } - int c; + public string ReadUnicodeString(int fixedLength) + { + int bound = m_Index + (fixedLength << 1); + int end = bound; - while ( (m_Index + 1) < bound && (c = ((Buffer[m_Index++] << 8) | Buffer[m_Index++])) != 0 ) - { - if ( IsSafeChar( c ) ) - sb.Append( (char)c ); - } + if (bound > Size) + bound = Size; - m_Index = end; + StringBuilder sb = new StringBuilder(); - return sb.ToString(); - } + int c; - public string ReadUnicodeString( int fixedLength ) - { - int bound = m_Index + (fixedLength << 1); - int end = bound; + while (m_Index + 1 < bound && (c = (Buffer[m_Index++] << 8) | Buffer[m_Index++]) != 0) + sb.Append((char)c); - if ( bound > Size ) - bound = Size; + m_Index = end; - StringBuilder sb = new StringBuilder(); + return sb.ToString(); + } - int c; + public string ReadStringSafe(int fixedLength) + { + int bound = m_Index + fixedLength; + int end = bound; - while ( (m_Index + 1) < bound && (c = ((Buffer[m_Index++] << 8) | Buffer[m_Index++])) != 0 ) - sb.Append( (char)c ); + if (bound > Size) + bound = Size; - m_Index = end; + StringBuilder sb = new StringBuilder(); - return sb.ToString(); - } + int c; - public string ReadStringSafe( int fixedLength ) - { - int bound = m_Index + fixedLength; - int end = bound; + while (m_Index < bound && (c = Buffer[m_Index++]) != 0) + if (IsSafeChar(c)) + sb.Append((char)c); - if ( bound > Size ) - bound = Size; + m_Index = end; - StringBuilder sb = new StringBuilder(); + return sb.ToString(); + } - int c; + public string ReadString(int fixedLength) + { + int bound = m_Index + fixedLength; + int end = bound; - while ( m_Index < bound && (c = Buffer[m_Index++]) != 0 ) - { - if ( IsSafeChar( c ) ) - sb.Append( (char)c ); - } + if (bound > Size) + bound = Size; - m_Index = end; + StringBuilder sb = new StringBuilder(); - return sb.ToString(); - } + int c; - public string ReadString( int fixedLength ) - { - int bound = m_Index + fixedLength; - int end = bound; + while (m_Index < bound && (c = Buffer[m_Index++]) != 0) + sb.Append((char)c); - if ( bound > Size ) - bound = Size; + m_Index = end; - StringBuilder sb = new StringBuilder(); - - int c; - - while ( m_Index < bound && (c = Buffer[m_Index++]) != 0 ) - sb.Append( (char)c ); - - m_Index = end; - - return sb.ToString(); - } - } + return sb.ToString(); + } + } } \ No newline at end of file diff --git a/Server/Network/PacketWriter.cs b/Server/Network/PacketWriter.cs index 65bb1ce2b..3aabd432e 100644 --- a/Server/Network/PacketWriter.cs +++ b/Server/Network/PacketWriter.cs @@ -19,433 +19,441 @@ ***************************************************************************/ using System; +using System.Collections.Generic; using System.IO; using System.Text; -using System.Collections.Generic; namespace Server.Network { - /// - /// Provides functionality for writing primitive binary data. - /// - public class PacketWriter - { - private static Stack m_Pool = new Stack(); - - public static PacketWriter CreateInstance() - { - return CreateInstance( 32 ); - } - - public static PacketWriter CreateInstance( int capacity ) - { - PacketWriter pw = null; - - lock ( m_Pool ) - { - if ( m_Pool.Count > 0 ) - { - pw = m_Pool.Pop(); - - if ( pw != null ) - { - pw.m_Capacity = capacity; - pw.m_Stream.SetLength( 0 ); - } - } - } - - if ( pw == null ) - pw = new PacketWriter( capacity ); - - return pw; - } - - public static void ReleaseInstance( PacketWriter pw ) - { - lock ( m_Pool ) - { - if ( !m_Pool.Contains( pw ) ) - { - m_Pool.Push( pw ); - } - else - { - try - { - using ( StreamWriter op = new StreamWriter( "neterr.log" ) ) - { - op.WriteLine("{0}\tInstance pool contains writer", DateTime.UtcNow); - } - } - catch - { - Console.WriteLine( "net error" ); - } - } - } - } - - /// - /// Internal stream which holds the entire packet. - /// - private MemoryStream m_Stream; - - private int m_Capacity; - - /// - /// Internal format buffer. - /// - private byte[] m_Buffer = new byte[4]; - - /// - /// Instantiates a new PacketWriter instance with the default capacity of 4 bytes. - /// - public PacketWriter() : this( 32 ) - { - } - - /// - /// Instantiates a new PacketWriter instance with a given capacity. - /// - /// Initial capacity for the internal stream. - public PacketWriter( int capacity ) - { - m_Stream = new MemoryStream( capacity ); - m_Capacity = capacity; - } - - /// - /// Writes a 1-byte boolean value to the underlying stream. False is represented by 0, true by 1. - /// - public void Write( bool value ) - { - m_Stream.WriteByte( (byte)(value ? 1 : 0) ); - } - - /// - /// Writes a 1-byte unsigned integer value to the underlying stream. - /// - public void Write( byte value ) - { - m_Stream.WriteByte( value ); - } - - /// - /// Writes a 1-byte signed integer value to the underlying stream. - /// - public void Write( sbyte value ) - { - m_Stream.WriteByte( (byte) value ); - } - - /// - /// Writes a 2-byte signed integer value to the underlying stream. - /// - public void Write( short value ) - { - m_Buffer[0] = (byte)(value >> 8); - m_Buffer[1] = (byte) value; - - m_Stream.Write( m_Buffer, 0, 2 ); - } - - /// - /// Writes a 2-byte unsigned integer value to the underlying stream. - /// - public void Write( ushort value ) - { - m_Buffer[0] = (byte)(value >> 8); - m_Buffer[1] = (byte) value; - - m_Stream.Write( m_Buffer, 0, 2 ); - } - - /// - /// Writes a 4-byte signed integer value to the underlying stream. - /// - public void Write( int value ) - { - m_Buffer[0] = (byte)(value >> 24); - m_Buffer[1] = (byte)(value >> 16); - m_Buffer[2] = (byte)(value >> 8); - m_Buffer[3] = (byte) value; - - m_Stream.Write( m_Buffer, 0, 4 ); - } - - /// - /// Writes a 4-byte unsigned integer value to the underlying stream. - /// - public void Write( uint value ) - { - m_Buffer[0] = (byte)(value >> 24); - m_Buffer[1] = (byte)(value >> 16); - m_Buffer[2] = (byte)(value >> 8); - m_Buffer[3] = (byte) value; - - m_Stream.Write( m_Buffer, 0, 4 ); - } - - /// - /// Writes a sequence of bytes to the underlying stream - /// - public void Write( byte[] buffer, int offset, int size ) - { - m_Stream.Write( buffer, offset, size ); - } - - /// - /// Writes a fixed-length ASCII-encoded string value to the underlying stream. To fit (size), the string content is either truncated or padded with null characters. - /// - public void WriteAsciiFixed( string value, int size ) - { - if ( value == null ) - { - Console.WriteLine( "Network: Attempted to WriteAsciiFixed() with null value" ); - value = string.Empty; - } - - int length = value.Length; - - m_Stream.SetLength( m_Stream.Length + size ); - - if ( length >= size ) - m_Stream.Position += Encoding.ASCII.GetBytes( value, 0, size, m_Stream.GetBuffer(), (int)m_Stream.Position ); - else - { - Encoding.ASCII.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - m_Stream.Position += size; - } - - /*byte[] buffer = Encoding.ASCII.GetBytes( value ); - - if ( buffer.Length >= size ) - { - m_Stream.Write( buffer, 0, size ); - } - else - { - m_Stream.Write( buffer, 0, buffer.Length ); - Fill( size - buffer.Length ); - }*/ - } - - /// - /// Writes a dynamic-length ASCII-encoded string value to the underlying stream, followed by a 1-byte null character. - /// - public void WriteAsciiNull( string value ) - { - if ( value == null ) - { - Console.WriteLine( "Network: Attempted to WriteAsciiNull() with null value" ); - value = string.Empty; - } - - int length = value.Length; - - m_Stream.SetLength( m_Stream.Length + length + 1 ); - - Encoding.ASCII.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - m_Stream.Position += length + 1; - - /*byte[] buffer = Encoding.ASCII.GetBytes( value ); - - m_Stream.Write( buffer, 0, buffer.Length ); - m_Stream.WriteByte( 0 );*/ - } - - /// - /// Writes a dynamic-length little-endian unicode string value to the underlying stream, followed by a 2-byte null character. - /// - public void WriteLittleUniNull( string value ) - { - if ( value == null ) - { - Console.WriteLine( "Network: Attempted to WriteLittleUniNull() with null value" ); - value = string.Empty; - } - - int length = value.Length; - - m_Stream.SetLength( m_Stream.Length + ( ( length + 1 ) * 2 ) ); - - m_Stream.Position += Encoding.Unicode.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - m_Stream.Position += 2; - - /*byte[] buffer = Encoding.Unicode.GetBytes( value ); - - m_Stream.Write( buffer, 0, buffer.Length ); - - m_Buffer[0] = 0; - m_Buffer[1] = 0; - m_Stream.Write( m_Buffer, 0, 2 );*/ - } - - /// - /// Writes a fixed-length little-endian unicode string value to the underlying stream. To fit (size), the string content is either truncated or padded with null characters. - /// - public void WriteLittleUniFixed( string value, int size ) - { - if ( value == null ) - { - Console.WriteLine( "Network: Attempted to WriteLittleUniFixed() with null value" ); - value = string.Empty; - } - - size *= 2; - - int length = value.Length; - - m_Stream.SetLength( m_Stream.Length + size ); - - if ( ( length * 2 ) >= size ) - m_Stream.Position += Encoding.Unicode.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - else - { - Encoding.Unicode.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - m_Stream.Position += size; - } - - /*size *= 2; - - byte[] buffer = Encoding.Unicode.GetBytes( value ); - - if ( buffer.Length >= size ) - { - m_Stream.Write( buffer, 0, size ); - } - else - { - m_Stream.Write( buffer, 0, buffer.Length ); - Fill( size - buffer.Length ); - }*/ - } - - /// - /// Writes a dynamic-length big-endian unicode string value to the underlying stream, followed by a 2-byte null character. - /// - public void WriteBigUniNull( string value ) - { - if ( value == null ) - { - Console.WriteLine( "Network: Attempted to WriteBigUniNull() with null value" ); - value = string.Empty; - } - - int length = value.Length; - - m_Stream.SetLength( m_Stream.Length + ( ( length + 1 ) * 2 ) ); - - m_Stream.Position += Encoding.BigEndianUnicode.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - m_Stream.Position += 2; - - /*byte[] buffer = Encoding.BigEndianUnicode.GetBytes( value ); - - m_Stream.Write( buffer, 0, buffer.Length ); - - m_Buffer[0] = 0; - m_Buffer[1] = 0; - m_Stream.Write( m_Buffer, 0, 2 );*/ - } - - /// - /// Writes a fixed-length big-endian unicode string value to the underlying stream. To fit (size), the string content is either truncated or padded with null characters. - /// - public void WriteBigUniFixed( string value, int size ) - { - if ( value == null ) - { - Console.WriteLine( "Network: Attempted to WriteBigUniFixed() with null value" ); - value = string.Empty; - } - - size *= 2; - - int length = value.Length; - - m_Stream.SetLength( m_Stream.Length + size ); - - if ( ( length * 2 ) >= size ) - m_Stream.Position += Encoding.BigEndianUnicode.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - else - { - Encoding.BigEndianUnicode.GetBytes( value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position ); - m_Stream.Position += size; - } - - /*size *= 2; - - byte[] buffer = Encoding.BigEndianUnicode.GetBytes( value ); - - if ( buffer.Length >= size ) - { - m_Stream.Write( buffer, 0, size ); - } - else - { - m_Stream.Write( buffer, 0, buffer.Length ); - Fill( size - buffer.Length ); - }*/ - } - - /// - /// Fills the stream from the current position up to (capacity) with 0x00's - /// - public void Fill() - { - Fill( (int) (m_Capacity - m_Stream.Length) ); - } - - /// - /// Writes a number of 0x00 byte values to the underlying stream. - /// - public void Fill( int length ) - { - if ( m_Stream.Position == m_Stream.Length ) - { - m_Stream.SetLength( m_Stream.Length + length ); - m_Stream.Seek( 0, SeekOrigin.End ); - } - else - { - m_Stream.Write( new byte[length], 0, length ); - } - } - - /// - /// Gets the total stream length. - /// - public long Length => m_Stream.Length; - - /// - /// Gets or sets the current stream position. - /// - public long Position - { - get => m_Stream.Position; - set => m_Stream.Position = value; - } - - /// - /// The internal stream used by this PacketWriter instance. - /// - public MemoryStream UnderlyingStream => m_Stream; - - /// - /// Offsets the current position from an origin. - /// - public long Seek( long offset, SeekOrigin origin ) - { - return m_Stream.Seek( offset, origin ); - } - - /// - /// Gets the entire stream content as a byte array. - /// - public byte[] ToArray() - { - return m_Stream.ToArray(); - } - } + /// + /// Provides functionality for writing primitive binary data. + /// + public class PacketWriter + { + private static Stack m_Pool = new Stack(); + + /// + /// Internal format buffer. + /// + private byte[] m_Buffer = new byte[4]; + + private int m_Capacity; + + /// + /// Internal stream which holds the entire packet. + /// + private MemoryStream m_Stream; + + /// + /// Instantiates a new PacketWriter instance with the default capacity of 4 bytes. + /// + public PacketWriter() : this(32) + { + } + + /// + /// Instantiates a new PacketWriter instance with a given capacity. + /// + /// Initial capacity for the internal stream. + public PacketWriter(int capacity) + { + m_Stream = new MemoryStream(capacity); + m_Capacity = capacity; + } + + /// + /// Gets the total stream length. + /// + public long Length => m_Stream.Length; + + /// + /// Gets or sets the current stream position. + /// + public long Position + { + get => m_Stream.Position; + set => m_Stream.Position = value; + } + + /// + /// The internal stream used by this PacketWriter instance. + /// + public MemoryStream UnderlyingStream => m_Stream; + + public static PacketWriter CreateInstance() + { + return CreateInstance(32); + } + + public static PacketWriter CreateInstance(int capacity) + { + PacketWriter pw = null; + + lock (m_Pool) + { + if (m_Pool.Count > 0) + { + pw = m_Pool.Pop(); + + if (pw != null) + { + pw.m_Capacity = capacity; + pw.m_Stream.SetLength(0); + } + } + } + + if (pw == null) + pw = new PacketWriter(capacity); + + return pw; + } + + public static void ReleaseInstance(PacketWriter pw) + { + lock (m_Pool) + { + if (!m_Pool.Contains(pw)) + m_Pool.Push(pw); + else + try + { + using (StreamWriter op = new StreamWriter("neterr.log")) + { + op.WriteLine("{0}\tInstance pool contains writer", DateTime.UtcNow); + } + } + catch + { + Console.WriteLine("net error"); + } + } + } + + /// + /// Writes a 1-byte boolean value to the underlying stream. False is represented by 0, true by 1. + /// + public void Write(bool value) + { + m_Stream.WriteByte((byte)(value ? 1 : 0)); + } + + /// + /// Writes a 1-byte unsigned integer value to the underlying stream. + /// + public void Write(byte value) + { + m_Stream.WriteByte(value); + } + + /// + /// Writes a 1-byte signed integer value to the underlying stream. + /// + public void Write(sbyte value) + { + m_Stream.WriteByte((byte)value); + } + + /// + /// Writes a 2-byte signed integer value to the underlying stream. + /// + public void Write(short value) + { + m_Buffer[0] = (byte)(value >> 8); + m_Buffer[1] = (byte)value; + + m_Stream.Write(m_Buffer, 0, 2); + } + + /// + /// Writes a 2-byte unsigned integer value to the underlying stream. + /// + public void Write(ushort value) + { + m_Buffer[0] = (byte)(value >> 8); + m_Buffer[1] = (byte)value; + + m_Stream.Write(m_Buffer, 0, 2); + } + + /// + /// Writes a 4-byte signed integer value to the underlying stream. + /// + public void Write(int value) + { + m_Buffer[0] = (byte)(value >> 24); + m_Buffer[1] = (byte)(value >> 16); + m_Buffer[2] = (byte)(value >> 8); + m_Buffer[3] = (byte)value; + + m_Stream.Write(m_Buffer, 0, 4); + } + + /// + /// Writes a 4-byte unsigned integer value to the underlying stream. + /// + public void Write(uint value) + { + m_Buffer[0] = (byte)(value >> 24); + m_Buffer[1] = (byte)(value >> 16); + m_Buffer[2] = (byte)(value >> 8); + m_Buffer[3] = (byte)value; + + m_Stream.Write(m_Buffer, 0, 4); + } + + /// + /// Writes a sequence of bytes to the underlying stream + /// + public void Write(byte[] buffer, int offset, int size) + { + m_Stream.Write(buffer, offset, size); + } + + /// + /// Writes a fixed-length ASCII-encoded string value to the underlying stream. To fit (size), the string content is either + /// truncated or padded with null characters. + /// + public void WriteAsciiFixed(string value, int size) + { + if (value == null) + { + Console.WriteLine("Network: Attempted to WriteAsciiFixed() with null value"); + value = string.Empty; + } + + int length = value.Length; + + m_Stream.SetLength(m_Stream.Length + size); + + if (length >= size) + { + m_Stream.Position += Encoding.ASCII.GetBytes(value, 0, size, m_Stream.GetBuffer(), (int)m_Stream.Position); + } + else + { + Encoding.ASCII.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + m_Stream.Position += size; + } + + /*byte[] buffer = Encoding.ASCII.GetBytes( value ); + + if ( buffer.Length >= size ) + { + m_Stream.Write( buffer, 0, size ); + } + else + { + m_Stream.Write( buffer, 0, buffer.Length ); + Fill( size - buffer.Length ); + }*/ + } + + /// + /// Writes a dynamic-length ASCII-encoded string value to the underlying stream, followed by a 1-byte null character. + /// + public void WriteAsciiNull(string value) + { + if (value == null) + { + Console.WriteLine("Network: Attempted to WriteAsciiNull() with null value"); + value = string.Empty; + } + + int length = value.Length; + + m_Stream.SetLength(m_Stream.Length + length + 1); + + Encoding.ASCII.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + m_Stream.Position += length + 1; + + /*byte[] buffer = Encoding.ASCII.GetBytes( value ); + + m_Stream.Write( buffer, 0, buffer.Length ); + m_Stream.WriteByte( 0 );*/ + } + + /// + /// Writes a dynamic-length little-endian unicode string value to the underlying stream, followed by a 2-byte null character. + /// + public void WriteLittleUniNull(string value) + { + if (value == null) + { + Console.WriteLine("Network: Attempted to WriteLittleUniNull() with null value"); + value = string.Empty; + } + + int length = value.Length; + + m_Stream.SetLength(m_Stream.Length + (length + 1) * 2); + + m_Stream.Position += Encoding.Unicode.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + m_Stream.Position += 2; + + /*byte[] buffer = Encoding.Unicode.GetBytes( value ); + + m_Stream.Write( buffer, 0, buffer.Length ); + + m_Buffer[0] = 0; + m_Buffer[1] = 0; + m_Stream.Write( m_Buffer, 0, 2 );*/ + } + + /// + /// Writes a fixed-length little-endian unicode string value to the underlying stream. To fit (size), the string content is + /// either truncated or padded with null characters. + /// + public void WriteLittleUniFixed(string value, int size) + { + if (value == null) + { + Console.WriteLine("Network: Attempted to WriteLittleUniFixed() with null value"); + value = string.Empty; + } + + size *= 2; + + int length = value.Length; + + m_Stream.SetLength(m_Stream.Length + size); + + if (length * 2 >= size) + { + m_Stream.Position += + Encoding.Unicode.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + } + else + { + Encoding.Unicode.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + m_Stream.Position += size; + } + + /*size *= 2; + + byte[] buffer = Encoding.Unicode.GetBytes( value ); + + if ( buffer.Length >= size ) + { + m_Stream.Write( buffer, 0, size ); + } + else + { + m_Stream.Write( buffer, 0, buffer.Length ); + Fill( size - buffer.Length ); + }*/ + } + + /// + /// Writes a dynamic-length big-endian unicode string value to the underlying stream, followed by a 2-byte null character. + /// + public void WriteBigUniNull(string value) + { + if (value == null) + { + Console.WriteLine("Network: Attempted to WriteBigUniNull() with null value"); + value = string.Empty; + } + + int length = value.Length; + + m_Stream.SetLength(m_Stream.Length + (length + 1) * 2); + + m_Stream.Position += + Encoding.BigEndianUnicode.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + m_Stream.Position += 2; + + /*byte[] buffer = Encoding.BigEndianUnicode.GetBytes( value ); + + m_Stream.Write( buffer, 0, buffer.Length ); + + m_Buffer[0] = 0; + m_Buffer[1] = 0; + m_Stream.Write( m_Buffer, 0, 2 );*/ + } + + /// + /// Writes a fixed-length big-endian unicode string value to the underlying stream. To fit (size), the string content is + /// either truncated or padded with null characters. + /// + public void WriteBigUniFixed(string value, int size) + { + if (value == null) + { + Console.WriteLine("Network: Attempted to WriteBigUniFixed() with null value"); + value = string.Empty; + } + + size *= 2; + + int length = value.Length; + + m_Stream.SetLength(m_Stream.Length + size); + + if (length * 2 >= size) + { + m_Stream.Position += + Encoding.BigEndianUnicode.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + } + else + { + Encoding.BigEndianUnicode.GetBytes(value, 0, length, m_Stream.GetBuffer(), (int)m_Stream.Position); + m_Stream.Position += size; + } + + /*size *= 2; + + byte[] buffer = Encoding.BigEndianUnicode.GetBytes( value ); + + if ( buffer.Length >= size ) + { + m_Stream.Write( buffer, 0, size ); + } + else + { + m_Stream.Write( buffer, 0, buffer.Length ); + Fill( size - buffer.Length ); + }*/ + } + + /// + /// Fills the stream from the current position up to (capacity) with 0x00's + /// + public void Fill() + { + Fill((int)(m_Capacity - m_Stream.Length)); + } + + /// + /// Writes a number of 0x00 byte values to the underlying stream. + /// + public void Fill(int length) + { + if (m_Stream.Position == m_Stream.Length) + { + m_Stream.SetLength(m_Stream.Length + length); + m_Stream.Seek(0, SeekOrigin.End); + } + else + { + m_Stream.Write(new byte[length], 0, length); + } + } + + /// + /// Offsets the current position from an origin. + /// + public long Seek(long offset, SeekOrigin origin) + { + return m_Stream.Seek(offset, origin); + } + + /// + /// Gets the entire stream content as a byte array. + /// + public byte[] ToArray() + { + return m_Stream.ToArray(); + } + } } \ No newline at end of file diff --git a/Server/Network/Packets.cs b/Server/Network/Packets.cs index d9bab22da..67d7bd8ee 100644 --- a/Server/Network/Packets.cs +++ b/Server/Network/Packets.cs @@ -20,4567 +20,4590 @@ using System; using System.Collections.Generic; +using System.Diagnostics; using System.IO; using System.Net; +using System.Security.Cryptography; +using System.Text; using System.Threading; using Server.Accounting; -using Server.Targeting; -using Server.Items; -using Server.Mobiles; +using Server.ContextMenus; +using Server.Diagnostics; using Server.Gumps; +using Server.HuePickers; +using Server.Items; using Server.Menus; using Server.Menus.ItemLists; using Server.Menus.Questions; +using Server.Mobiles; using Server.Prompts; -using Server.HuePickers; -using Server.ContextMenus; -using Server.Diagnostics; +using Server.Targeting; namespace Server.Network { - public enum PMMessage : byte - { - CharNoExist = 1, - CharExists = 2, - CharInWorld = 5, - LoginSyncError = 6, - IdleWarning = 7 - } - - public enum LRReason : byte - { - CannotLift = 0, - OutOfRange = 1, - OutOfSight = 2, - TryToSteal = 3, - AreHolding = 4, - Inspecific = 5 - } - - /*public enum CMEFlags - { - None = 0x00, - Locked = 0x01, - Arrow = 0x02, - x0004 = 0x04, - Color = 0x20, - x0040 = 0x40, - x0080 = 0x80 - }*/ - - public sealed class DamagePacketOld : Packet - { - public DamagePacketOld( Mobile m, int amount ) : base( 0xBF ) - { - EnsureCapacity( 11 ); - - m_Stream.Write( (short) 0x22 ); - m_Stream.Write( (byte) 1 ); - m_Stream.Write( (int) m.Serial ); - - if ( amount > 255 ) - amount = 255; - else if ( amount < 0 ) - amount = 0; - - m_Stream.Write( (byte)amount ); - } - } - - public sealed class DamagePacket : Packet - { - public DamagePacket( Mobile m, int amount ) : base( 0x0B, 7 ) - { - m_Stream.Write( (int) m.Serial ); - - if ( amount > 0xFFFF ) - amount = 0xFFFF; - else if ( amount < 0 ) - amount = 0; - - m_Stream.Write( (ushort) amount ); - } - - /*public DamagePacket( Mobile m, int amount ) : base( 0xBF ) - { - EnsureCapacity( 11 ); - - m_Stream.Write( (short) 0x22 ); - m_Stream.Write( (byte) 1 ); - m_Stream.Write( (int) m.Serial ); - - if ( amount > 255 ) - amount = 255; - else if ( amount < 0 ) - amount = 0; - - m_Stream.Write( (byte)amount ); - }*/ - } - - public sealed class CancelArrow : Packet - { - public CancelArrow() : base( 0xBA, 6 ) - { - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) -1 ); - m_Stream.Write( (short) -1 ); - } - } - - public sealed class SetArrow : Packet - { - public SetArrow( int x, int y ) : base( 0xBA, 6 ) - { - m_Stream.Write( (byte) 1 ); - m_Stream.Write( (short) x ); - m_Stream.Write( (short) y ); - } - } - - public sealed class CancelArrowHS : Packet - { - public CancelArrowHS( int x, int y, Serial s ) : base( 0xBA, 10 ) - { - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) x ); - m_Stream.Write( (short) y ); - m_Stream.Write( (int) s ); - } - } - - public sealed class SetArrowHS : Packet - { - public SetArrowHS( int x, int y, Serial s ) : base( 0xBA, 10 ) - { - m_Stream.Write( (byte) 1 ); - m_Stream.Write( (short) x ); - m_Stream.Write( (short) y ); - m_Stream.Write( (int) s ); - } - } - - public sealed class DisplaySecureTrade : Packet - { - public DisplaySecureTrade(Mobile them, Container first, Container second, string name) - : base(0x6F) - { - if (name == null) - { - name = ""; - } - - EnsureCapacity(18 + name.Length); - - m_Stream.Write((byte)0); // Display - m_Stream.Write(them.Serial); - m_Stream.Write(first.Serial); - m_Stream.Write(second.Serial); - m_Stream.Write(true); - - m_Stream.WriteAsciiFixed(name, 30); - } - } - - public sealed class CloseSecureTrade : Packet - { - public CloseSecureTrade(Container cont) - : base(0x6F) - { - EnsureCapacity(8); - - m_Stream.Write((byte)1); // Close - m_Stream.Write(cont.Serial); - } - } - - public enum TradeFlag : byte - { - Display = 0x0, - Close = 0x1, - Update = 0x2, - UpdateGold = 0x3, - UpdateLedger = 0x4 - } - - public sealed class UpdateSecureTrade : Packet - { - public UpdateSecureTrade(Container cont, bool first, bool second) - : this(cont, TradeFlag.Update, first ? 1 : 0, second ? 1 : 0) - { } - - public UpdateSecureTrade(Container cont, TradeFlag flag, int first, int second) - : base(0x6F) - { - EnsureCapacity(17); - - m_Stream.Write((byte)flag); - m_Stream.Write(cont.Serial); - m_Stream.Write(first); - m_Stream.Write(second); - } - } - - public sealed class SecureTradeEquip : Packet - { - public SecureTradeEquip( Item item, Mobile m ) : base( 0x25, 20 ) - { - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (short) item.ItemID ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) item.Amount ); - m_Stream.Write( (short) item.X ); - m_Stream.Write( (short) item.Y ); - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) item.Hue ); - } - } - - public sealed class SecureTradeEquip6017 : Packet - { - public SecureTradeEquip6017( Item item, Mobile m ) : base( 0x25, 21 ) - { - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (short) item.ItemID ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) item.Amount ); - m_Stream.Write( (short) item.X ); - m_Stream.Write( (short) item.Y ); - m_Stream.Write( (byte) 0 ); // Grid Location? - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) item.Hue ); - } - } - - public sealed class MapPatches : Packet - { - public MapPatches() : base( 0xBF ) - { - EnsureCapacity( 9 + (3 * 8) ); - - m_Stream.Write( (short) 0x0018 ); - - m_Stream.Write( (int) 4 ); - - m_Stream.Write( (int) Map.Felucca.Tiles.Patch.StaticBlocks ); - m_Stream.Write( (int) Map.Felucca.Tiles.Patch.LandBlocks ); - - m_Stream.Write( (int) Map.Trammel.Tiles.Patch.StaticBlocks ); - m_Stream.Write( (int) Map.Trammel.Tiles.Patch.LandBlocks ); - - m_Stream.Write( (int) Map.Ilshenar.Tiles.Patch.StaticBlocks ); - m_Stream.Write( (int) Map.Ilshenar.Tiles.Patch.LandBlocks ); - - m_Stream.Write( (int) Map.Malas.Tiles.Patch.StaticBlocks ); - m_Stream.Write( (int) Map.Malas.Tiles.Patch.LandBlocks ); - } - } - - public sealed class ObjectHelpResponse : Packet - { - public ObjectHelpResponse( IEntity e, string text ) : base( 0xB7 ) - { - EnsureCapacity( 9 + (text.Length * 2) ); - - m_Stream.Write( (int) e.Serial ); - m_Stream.WriteBigUniNull( text ); - } - } - - public sealed class VendorBuyContent : Packet - { - public VendorBuyContent( List list ) - : base( 0x3c ) - { - EnsureCapacity( list.Count*19 + 5 ); - - m_Stream.Write( (short)list.Count ); - - //The client sorts these by their X/Y value. - //OSI sends these in wierd order. X/Y highest to lowest and serial loest to highest - //These are already sorted by serial (done by the vendor class) but we have to send them by x/y - //(the x74 packet is sent in 'correct' order.) - for ( int i = list.Count - 1; i >= 0; --i ) - { - BuyItemState bis = (BuyItemState)list[i]; - - m_Stream.Write( (int)bis.MySerial ); - m_Stream.Write( (ushort)bis.ItemID ); - m_Stream.Write( (byte)0 );//itemid offset - m_Stream.Write( (ushort)bis.Amount ); - m_Stream.Write( (short)(i+1) );//x - m_Stream.Write( (short)1 );//y - m_Stream.Write( (int)bis.ContainerSerial ); - m_Stream.Write( (ushort)bis.Hue ); - } - } - } - - public sealed class VendorBuyContent6017 : Packet - { - public VendorBuyContent6017( List list ) : base( 0x3c ) - { - EnsureCapacity( list.Count*20 + 5 ); - - m_Stream.Write( (short)list.Count ); - - //The client sorts these by their X/Y value. - //OSI sends these in wierd order. X/Y highest to lowest and serial loest to highest - //These are already sorted by serial (done by the vendor class) but we have to send them by x/y - //(the x74 packet is sent in 'correct' order.) - for ( int i = list.Count - 1; i >= 0; --i ) - { - BuyItemState bis = (BuyItemState)list[i]; - - m_Stream.Write( (int)bis.MySerial ); - m_Stream.Write( (ushort)bis.ItemID ); - m_Stream.Write( (byte)0 );//itemid offset - m_Stream.Write( (ushort)bis.Amount ); - m_Stream.Write( (short)(i+1) );//x - m_Stream.Write( (short)1 );//y - m_Stream.Write( (byte)0 ); // Grid Location? - m_Stream.Write( (int)bis.ContainerSerial ); - m_Stream.Write( (ushort)bis.Hue ); - } - } - } - - public sealed class DisplayBuyList : Packet - { - public DisplayBuyList( Mobile vendor ) : base( 0x24, 7 ) - { - m_Stream.Write( (int)vendor.Serial ); - m_Stream.Write( (short) 0x30 ); // buy window id? - } - } - - public sealed class DisplayBuyListHS : Packet - { - public DisplayBuyListHS( Mobile vendor ) : base( 0x24, 9 ) - { - m_Stream.Write( (int)vendor.Serial ); - m_Stream.Write( (short) 0x30 ); // buy window id? - m_Stream.Write( (short) 0x00 ); - } - } - - public sealed class VendorBuyList : Packet - { - public VendorBuyList( Mobile vendor, List list ) - : base( 0x74 ) - { - EnsureCapacity( 256 ); - - m_Stream.Write( (int)(!(vendor.FindItemOnLayer( Layer.ShopBuy ) is Container BuyPack) ? Serial.MinusOne : BuyPack.Serial) ); - - m_Stream.Write( (byte)list.Count ); - - for ( int i = 0; i < list.Count; ++i ) - { - BuyItemState bis = list[i]; - - m_Stream.Write( (int) bis.Price ); - - string desc = bis.Description; - - if ( desc == null ) - desc = ""; - - m_Stream.Write( (byte)(desc.Length + 1) ); - m_Stream.WriteAsciiNull( desc ); - } - } - } - - public sealed class VendorSellList : Packet - { - public VendorSellList( Mobile shopkeeper, ICollection sis ) : base( 0x9E ) - { - EnsureCapacity( 256 ); - - m_Stream.Write( (int) shopkeeper.Serial ); - - m_Stream.Write( (ushort) sis.Count); - - foreach (SellItemState state in sis) - { - m_Stream.Write( (int) state.Item.Serial ); - m_Stream.Write( (ushort) state.Item.ItemID ); - m_Stream.Write( (ushort) state.Item.Hue ); - m_Stream.Write( (ushort) state.Item.Amount ); - m_Stream.Write( (ushort) state.Price ); - - string name = state.Item.Name; - - if ( name == null || (name = name.Trim()).Length <= 0 ) - name = state.Name; - - if ( name == null ) - name = ""; - - m_Stream.Write( (ushort) (name.Length) ); - m_Stream.WriteAsciiFixed( name, (ushort) (name.Length) ); - } - } - } - - public sealed class EndVendorSell : Packet - { - public EndVendorSell( Mobile Vendor ) : base( 0x3B, 8 ) - { - m_Stream.Write( (ushort)8 );//length - m_Stream.Write( (int)Vendor.Serial ); - m_Stream.Write( (byte)0 ); - } - } - - public sealed class EndVendorBuy : Packet - { - public EndVendorBuy( Mobile Vendor ) : base( 0x3B, 8 ) - { - m_Stream.Write( (ushort)8 );//length - m_Stream.Write( (int)Vendor.Serial ); - m_Stream.Write( (byte)0 ); - } - } - - public sealed class DeathAnimation : Packet - { - public DeathAnimation( Mobile killed, Item corpse ) : base( 0xAF, 13 ) - { - m_Stream.Write( (int) killed.Serial ); - m_Stream.Write( (int) (corpse?.Serial ?? Serial.Zero) ); - m_Stream.Write( (int) 0 ) ; - } - } - - public sealed class StatLockInfo : Packet - { - public StatLockInfo( Mobile m ) : base( 0xBF ) - { - EnsureCapacity( 12 ); - - m_Stream.Write( (short) 0x19 ); - m_Stream.Write( (byte) 2 ); - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (byte) 0 ); - - int lockBits = 0; - - lockBits |= (int)m.StrLock << 4; - lockBits |= (int)m.DexLock << 2; - lockBits |= (int)m.IntLock; - - m_Stream.Write( (byte) lockBits ); - } - } - - public class EquipInfoAttribute - { - public int Number { get; } - - public int Charges { get; } - - public EquipInfoAttribute( int number ) : this( number, -1 ) - { - } - - public EquipInfoAttribute( int number, int charges ) - { - Number = number; - Charges = charges; - } - } - - public class EquipmentInfo - { - public int Number { get; } - - public Mobile Crafter { get; } - - public bool Unidentified { get; } - - public EquipInfoAttribute[] Attributes { get; } - - public EquipmentInfo( int number, Mobile crafter, bool unidentified, EquipInfoAttribute[] attributes ) - { - Number = number; - Crafter = crafter; - Unidentified = unidentified; - Attributes = attributes; - } - } - - public sealed class DisplayEquipmentInfo : Packet - { - public DisplayEquipmentInfo( Item item, EquipmentInfo info ) : base( 0xBF ) - { - EquipInfoAttribute[] attrs = info.Attributes; - - EnsureCapacity( 17 + (info.Crafter == null ? 0 : 6 + info.Crafter.Name == null ? 0 : info.Crafter.Name.Length) + (info.Unidentified ? 4 : 0) + (attrs.Length * 6) ); - - m_Stream.Write( (short) 0x10 ); - m_Stream.Write( (int) item.Serial ); - - m_Stream.Write( (int) info.Number ); - - if ( info.Crafter != null ) - { - string name = info.Crafter.Name; - - m_Stream.Write( (int) -3 ); - - if ( name == null ) - m_Stream.Write( (ushort) 0 ); - else - { - int length = name.Length; - m_Stream.Write( (ushort) length ); - m_Stream.WriteAsciiFixed( name, length ); - } - } - - if ( info.Unidentified ) - { - m_Stream.Write( (int) -4 ); - } - - for ( int i = 0; i < attrs.Length; ++i ) - { - m_Stream.Write( (int) attrs[i].Number ); - m_Stream.Write( (short) attrs[i].Charges ); - } - - m_Stream.Write( (int) -1 ); - } - } - - public sealed class ChangeUpdateRange : Packet - { - private static ChangeUpdateRange[] m_Cache = new ChangeUpdateRange[0x100]; - - public static ChangeUpdateRange Instantiate( int range ) - { - byte idx = (byte)range; - ChangeUpdateRange p = m_Cache[idx]; - - if ( p == null ) - { - m_Cache[idx] = p = new ChangeUpdateRange( range ); - p.SetStatic(); - } - - return p; - } - - public ChangeUpdateRange( int range ) : base( 0xC8, 2 ) - { - m_Stream.Write( (byte) range ); - } - } - - public sealed class ChangeCombatant : Packet - { - public ChangeCombatant( Mobile combatant ) : base( 0xAA, 5 ) - { - m_Stream.Write( combatant?.Serial ?? Serial.Zero ); - } - } - - public sealed class DisplayHuePicker : Packet - { - public DisplayHuePicker( HuePicker huePicker ) : base( 0x95, 9 ) - { - m_Stream.Write( (int) huePicker.Serial ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) huePicker.ItemID ); - } - } - - public sealed class TripTimeResponse : Packet - { - public TripTimeResponse( int unk ) : base( 0xC9, 6 ) - { - m_Stream.Write( (byte) unk ); - m_Stream.Write( (int) Environment.TickCount ); - } - } - - public sealed class UTripTimeResponse : Packet - { - public UTripTimeResponse( int unk ) : base( 0xCA, 6 ) - { - m_Stream.Write( (byte) unk ); - m_Stream.Write( (int) Environment.TickCount ); - } - } - - public sealed class UnicodePrompt : Packet - { - public UnicodePrompt( Prompt prompt ) : base( 0xC2 ) - { - EnsureCapacity( 21 ); - - m_Stream.Write( (int) prompt.Serial ); - m_Stream.Write( (int) prompt.Serial ); - m_Stream.Write( (int) 0 ); - m_Stream.Write( (int) 0 ); - m_Stream.Write( (short) 0 ); - } - } - - public sealed class ChangeCharacter : Packet - { - public ChangeCharacter( IAccount a ) : base( 0x81 ) - { - EnsureCapacity( 305 ); - - int count = 0; - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] != null ) - ++count; - } - - m_Stream.Write( (byte) count ); - m_Stream.Write( (byte) 0 ); - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] != null ) - { - string name = a[i].Name; - - if ( name == null ) - name = "-null-"; - else if ( (name = name.Trim()).Length == 0 ) - name = "-empty-"; - - m_Stream.WriteAsciiFixed( name, 30 ); - m_Stream.Fill( 30 ); // password - } - else - { - m_Stream.Fill( 60 ); - } - } - } - } - - public sealed class DeathStatus : Packet - { - public static readonly Packet Dead = SetStatic( new DeathStatus( true ) ); - public static readonly Packet Alive = SetStatic( new DeathStatus( false ) ); - - public static Packet Instantiate( bool dead ) - { - return ( dead ? Dead : Alive ); - } - - public DeathStatus( bool dead ) : base( 0x2C, 2 ) - { - m_Stream.Write( (byte) (dead ? 0 : 2) ); - } - } - - public sealed class SpeedControl : Packet - { - public static readonly Packet WalkSpeed = SetStatic( new SpeedControl( 2 ) ); - public static readonly Packet MountSpeed = SetStatic( new SpeedControl( 1 ) ); - public static readonly Packet Disable = SetStatic( new SpeedControl( 0 ) ); - - public SpeedControl( int speedControl ) - : base( 0xBF ) - { - EnsureCapacity( 3 ); - - m_Stream.Write( (short)0x26 ); - m_Stream.Write( (byte)speedControl ); - } - } - - public sealed class InvalidMapEnable : Packet - { - public InvalidMapEnable() : base( 0xC6, 1 ) - { - } - } - - public sealed class BondedStatus : Packet - { - public BondedStatus( int val1, Serial serial, int val2 ) : base( 0xBF ) - { - EnsureCapacity( 11 ); - - m_Stream.Write( (short) 0x19 ); - m_Stream.Write( (byte) val1 ); - m_Stream.Write( (int) serial ); - m_Stream.Write( (byte) val2 ); - } - } - - public sealed class ToggleSpecialAbility : Packet - { - public ToggleSpecialAbility( int abilityID, bool active ) - : base( 0xBF ) - { - EnsureCapacity( 7 ); - - m_Stream.Write( (short)0x25 ); - - m_Stream.Write( (short)abilityID ); - m_Stream.Write( (bool)active ); - } - } - - public sealed class DisplayItemListMenu : Packet - { - public DisplayItemListMenu( ItemListMenu menu ) : base( 0x7C ) - { - EnsureCapacity( 256 ); - - m_Stream.Write( (int) ((IMenu)menu).Serial ); - m_Stream.Write( (short) 0 ); - - string question = menu.Question; - - if ( question == null ) - m_Stream.Write( (byte) 0 ); - else - { - int questionLength = question.Length; - m_Stream.Write( (byte) questionLength ); - m_Stream.WriteAsciiFixed( question, questionLength ); - } - - ItemListEntry[] entries = menu.Entries; - - int entriesLength = (byte)entries.Length; - - m_Stream.Write( (byte) entriesLength ); - - for ( int i = 0; i < entriesLength; ++i ) - { - ItemListEntry e = entries[i]; - - m_Stream.Write( (ushort) e.ItemID ); - m_Stream.Write( (short) e.Hue ); - - string name = e.Name; - - if ( name == null ) - m_Stream.Write( (byte) 0 ); - else - { - int nameLength = name.Length; - m_Stream.Write( (byte) nameLength ); - m_Stream.WriteAsciiFixed( name, nameLength ); - } - } - } - } - - public sealed class DisplayQuestionMenu : Packet - { - public DisplayQuestionMenu( QuestionMenu menu ) : base( 0x7C ) - { - EnsureCapacity( 256 ); - - m_Stream.Write( (int) ((IMenu)menu).Serial ); - m_Stream.Write( (short) 0 ); - - string question = menu.Question; - - if ( question == null ) - m_Stream.Write( (byte) 0 ); - else - { - int questionLength = question.Length; - m_Stream.Write( (byte) questionLength ); - m_Stream.WriteAsciiFixed( question, questionLength ); - } - - string[] answers = menu.Answers; - - int answersLength = (byte)answers.Length; - - m_Stream.Write( (byte) answersLength ); - - for ( int i = 0; i < answersLength; ++i ) - { - m_Stream.Write( (int) 0 ); - - string answer = answers[i]; - - if ( answer == null ) - m_Stream.Write( (byte) 0 ); - else - { - int answerLength = answer.Length; - m_Stream.Write( (byte) answerLength ); - m_Stream.WriteAsciiFixed( answer, answerLength ); - } - } - } - } - - public sealed class GlobalLightLevel : Packet - { - private static GlobalLightLevel[] m_Cache = new GlobalLightLevel[0x100]; - - public static GlobalLightLevel Instantiate( int level ) - { - byte lvl = (byte)level; - GlobalLightLevel p = m_Cache[lvl]; - - if ( p == null ) - { - m_Cache[lvl] = p = new GlobalLightLevel( level ); - p.SetStatic(); - } - - return p; - } - - public GlobalLightLevel( int level ) : base( 0x4F, 2 ) - { - m_Stream.Write( (sbyte) level ); - } - } + public enum PMMessage : byte + { + CharNoExist = 1, + CharExists = 2, + CharInWorld = 5, + LoginSyncError = 6, + IdleWarning = 7 + } + + public enum LRReason : byte + { + CannotLift = 0, + OutOfRange = 1, + OutOfSight = 2, + TryToSteal = 3, + AreHolding = 4, + Inspecific = 5 + } + + /*public enum CMEFlags + { + None = 0x00, + Locked = 0x01, + Arrow = 0x02, + x0004 = 0x04, + Color = 0x20, + x0040 = 0x40, + x0080 = 0x80 + }*/ + + public sealed class DamagePacketOld : Packet + { + public DamagePacketOld(Mobile m, int amount) : base(0xBF) + { + EnsureCapacity(11); + + m_Stream.Write((short)0x22); + m_Stream.Write((byte)1); + m_Stream.Write(m.Serial); + + if (amount > 255) + amount = 255; + else if (amount < 0) + amount = 0; + + m_Stream.Write((byte)amount); + } + } + + public sealed class DamagePacket : Packet + { + public DamagePacket(Mobile m, int amount) : base(0x0B, 7) + { + m_Stream.Write(m.Serial); + + if (amount > 0xFFFF) + amount = 0xFFFF; + else if (amount < 0) + amount = 0; + + m_Stream.Write((ushort)amount); + } + + /*public DamagePacket( Mobile m, int amount ) : base( 0xBF ) + { + EnsureCapacity( 11 ); + + m_Stream.Write( (short) 0x22 ); + m_Stream.Write( (byte) 1 ); + m_Stream.Write( (int) m.Serial ); + + if ( amount > 255 ) + amount = 255; + else if ( amount < 0 ) + amount = 0; + + m_Stream.Write( (byte)amount ); + }*/ + } + + public sealed class CancelArrow : Packet + { + public CancelArrow() : base(0xBA, 6) + { + m_Stream.Write((byte)0); + m_Stream.Write((short)-1); + m_Stream.Write((short)-1); + } + } + + public sealed class SetArrow : Packet + { + public SetArrow(int x, int y) : base(0xBA, 6) + { + m_Stream.Write((byte)1); + m_Stream.Write((short)x); + m_Stream.Write((short)y); + } + } + + public sealed class CancelArrowHS : Packet + { + public CancelArrowHS(int x, int y, Serial s) : base(0xBA, 10) + { + m_Stream.Write((byte)0); + m_Stream.Write((short)x); + m_Stream.Write((short)y); + m_Stream.Write(s); + } + } + + public sealed class SetArrowHS : Packet + { + public SetArrowHS(int x, int y, Serial s) : base(0xBA, 10) + { + m_Stream.Write((byte)1); + m_Stream.Write((short)x); + m_Stream.Write((short)y); + m_Stream.Write(s); + } + } + + public sealed class DisplaySecureTrade : Packet + { + public DisplaySecureTrade(Mobile them, Container first, Container second, string name) + : base(0x6F) + { + if (name == null) name = ""; + + EnsureCapacity(18 + name.Length); + + m_Stream.Write((byte)0); // Display + m_Stream.Write(them.Serial); + m_Stream.Write(first.Serial); + m_Stream.Write(second.Serial); + m_Stream.Write(true); + + m_Stream.WriteAsciiFixed(name, 30); + } + } + + public sealed class CloseSecureTrade : Packet + { + public CloseSecureTrade(Container cont) + : base(0x6F) + { + EnsureCapacity(8); + + m_Stream.Write((byte)1); // Close + m_Stream.Write(cont.Serial); + } + } + + public enum TradeFlag : byte + { + Display = 0x0, + Close = 0x1, + Update = 0x2, + UpdateGold = 0x3, + UpdateLedger = 0x4 + } + + public sealed class UpdateSecureTrade : Packet + { + public UpdateSecureTrade(Container cont, bool first, bool second) + : this(cont, TradeFlag.Update, first ? 1 : 0, second ? 1 : 0) + { + } + + public UpdateSecureTrade(Container cont, TradeFlag flag, int first, int second) + : base(0x6F) + { + EnsureCapacity(17); + + m_Stream.Write((byte)flag); + m_Stream.Write(cont.Serial); + m_Stream.Write(first); + m_Stream.Write(second); + } + } + + public sealed class SecureTradeEquip : Packet + { + public SecureTradeEquip(Item item, Mobile m) : base(0x25, 20) + { + m_Stream.Write(item.Serial); + m_Stream.Write((short)item.ItemID); + m_Stream.Write((byte)0); + m_Stream.Write((short)item.Amount); + m_Stream.Write((short)item.X); + m_Stream.Write((short)item.Y); + m_Stream.Write(m.Serial); + m_Stream.Write((short)item.Hue); + } + } + + public sealed class SecureTradeEquip6017 : Packet + { + public SecureTradeEquip6017(Item item, Mobile m) : base(0x25, 21) + { + m_Stream.Write(item.Serial); + m_Stream.Write((short)item.ItemID); + m_Stream.Write((byte)0); + m_Stream.Write((short)item.Amount); + m_Stream.Write((short)item.X); + m_Stream.Write((short)item.Y); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(m.Serial); + m_Stream.Write((short)item.Hue); + } + } + + public sealed class MapPatches : Packet + { + public MapPatches() : base(0xBF) + { + EnsureCapacity(9 + 3 * 8); + + m_Stream.Write((short)0x0018); + + m_Stream.Write(4); + + m_Stream.Write(Map.Felucca.Tiles.Patch.StaticBlocks); + m_Stream.Write(Map.Felucca.Tiles.Patch.LandBlocks); + + m_Stream.Write(Map.Trammel.Tiles.Patch.StaticBlocks); + m_Stream.Write(Map.Trammel.Tiles.Patch.LandBlocks); + + m_Stream.Write(Map.Ilshenar.Tiles.Patch.StaticBlocks); + m_Stream.Write(Map.Ilshenar.Tiles.Patch.LandBlocks); + + m_Stream.Write(Map.Malas.Tiles.Patch.StaticBlocks); + m_Stream.Write(Map.Malas.Tiles.Patch.LandBlocks); + } + } + + public sealed class ObjectHelpResponse : Packet + { + public ObjectHelpResponse(IEntity e, string text) : base(0xB7) + { + EnsureCapacity(9 + text.Length * 2); + + m_Stream.Write(e.Serial); + m_Stream.WriteBigUniNull(text); + } + } + + public sealed class VendorBuyContent : Packet + { + public VendorBuyContent(List list) + : base(0x3c) + { + EnsureCapacity(list.Count * 19 + 5); + + m_Stream.Write((short)list.Count); + + //The client sorts these by their X/Y value. + //OSI sends these in wierd order. X/Y highest to lowest and serial loest to highest + //These are already sorted by serial (done by the vendor class) but we have to send them by x/y + //(the x74 packet is sent in 'correct' order.) + for (int i = list.Count - 1; i >= 0; --i) + { + BuyItemState bis = list[i]; + + m_Stream.Write(bis.MySerial); + m_Stream.Write((ushort)bis.ItemID); + m_Stream.Write((byte)0); //itemid offset + m_Stream.Write((ushort)bis.Amount); + m_Stream.Write((short)(i + 1)); //x + m_Stream.Write((short)1); //y + m_Stream.Write(bis.ContainerSerial); + m_Stream.Write((ushort)bis.Hue); + } + } + } + + public sealed class VendorBuyContent6017 : Packet + { + public VendorBuyContent6017(List list) : base(0x3c) + { + EnsureCapacity(list.Count * 20 + 5); + + m_Stream.Write((short)list.Count); + + //The client sorts these by their X/Y value. + //OSI sends these in wierd order. X/Y highest to lowest and serial loest to highest + //These are already sorted by serial (done by the vendor class) but we have to send them by x/y + //(the x74 packet is sent in 'correct' order.) + for (int i = list.Count - 1; i >= 0; --i) + { + BuyItemState bis = list[i]; + + m_Stream.Write(bis.MySerial); + m_Stream.Write((ushort)bis.ItemID); + m_Stream.Write((byte)0); //itemid offset + m_Stream.Write((ushort)bis.Amount); + m_Stream.Write((short)(i + 1)); //x + m_Stream.Write((short)1); //y + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(bis.ContainerSerial); + m_Stream.Write((ushort)bis.Hue); + } + } + } + + public sealed class DisplayBuyList : Packet + { + public DisplayBuyList(Mobile vendor) : base(0x24, 7) + { + m_Stream.Write(vendor.Serial); + m_Stream.Write((short)0x30); // buy window id? + } + } + + public sealed class DisplayBuyListHS : Packet + { + public DisplayBuyListHS(Mobile vendor) : base(0x24, 9) + { + m_Stream.Write(vendor.Serial); + m_Stream.Write((short)0x30); // buy window id? + m_Stream.Write((short)0x00); + } + } + + public sealed class VendorBuyList : Packet + { + public VendorBuyList(Mobile vendor, List list) + : base(0x74) + { + EnsureCapacity(256); + + m_Stream.Write(!(vendor.FindItemOnLayer(Layer.ShopBuy) is Container BuyPack) ? Serial.MinusOne : BuyPack.Serial); + + m_Stream.Write((byte)list.Count); + + for (int i = 0; i < list.Count; ++i) + { + BuyItemState bis = list[i]; + + m_Stream.Write(bis.Price); + + string desc = bis.Description; + + if (desc == null) + desc = ""; + + m_Stream.Write((byte)(desc.Length + 1)); + m_Stream.WriteAsciiNull(desc); + } + } + } + + public sealed class VendorSellList : Packet + { + public VendorSellList(Mobile shopkeeper, ICollection sis) : base(0x9E) + { + EnsureCapacity(256); + + m_Stream.Write(shopkeeper.Serial); + + m_Stream.Write((ushort)sis.Count); + + foreach (SellItemState state in sis) + { + m_Stream.Write(state.Item.Serial); + m_Stream.Write((ushort)state.Item.ItemID); + m_Stream.Write((ushort)state.Item.Hue); + m_Stream.Write((ushort)state.Item.Amount); + m_Stream.Write((ushort)state.Price); + + string name = state.Item.Name; + + if (name == null || (name = name.Trim()).Length <= 0) + name = state.Name; + + if (name == null) + name = ""; + + m_Stream.Write((ushort)name.Length); + m_Stream.WriteAsciiFixed(name, (ushort)name.Length); + } + } + } + + public sealed class EndVendorSell : Packet + { + public EndVendorSell(Mobile Vendor) : base(0x3B, 8) + { + m_Stream.Write((ushort)8); //length + m_Stream.Write(Vendor.Serial); + m_Stream.Write((byte)0); + } + } + + public sealed class EndVendorBuy : Packet + { + public EndVendorBuy(Mobile Vendor) : base(0x3B, 8) + { + m_Stream.Write((ushort)8); //length + m_Stream.Write(Vendor.Serial); + m_Stream.Write((byte)0); + } + } + + public sealed class DeathAnimation : Packet + { + public DeathAnimation(Mobile killed, Item corpse) : base(0xAF, 13) + { + m_Stream.Write(killed.Serial); + m_Stream.Write(corpse?.Serial ?? Serial.Zero); + m_Stream.Write(0); + } + } + + public sealed class StatLockInfo : Packet + { + public StatLockInfo(Mobile m) : base(0xBF) + { + EnsureCapacity(12); + + m_Stream.Write((short)0x19); + m_Stream.Write((byte)2); + m_Stream.Write(m.Serial); + m_Stream.Write((byte)0); + + int lockBits = 0; + + lockBits |= (int)m.StrLock << 4; + lockBits |= (int)m.DexLock << 2; + lockBits |= (int)m.IntLock; + + m_Stream.Write((byte)lockBits); + } + } + + public class EquipInfoAttribute + { + public EquipInfoAttribute(int number) : this(number, -1) + { + } + + public EquipInfoAttribute(int number, int charges) + { + Number = number; + Charges = charges; + } + + public int Number{ get; } + + public int Charges{ get; } + } + + public class EquipmentInfo + { + public EquipmentInfo(int number, Mobile crafter, bool unidentified, EquipInfoAttribute[] attributes) + { + Number = number; + Crafter = crafter; + Unidentified = unidentified; + Attributes = attributes; + } + + public int Number{ get; } + + public Mobile Crafter{ get; } + + public bool Unidentified{ get; } + + public EquipInfoAttribute[] Attributes{ get; } + } + + public sealed class DisplayEquipmentInfo : Packet + { + public DisplayEquipmentInfo(Item item, EquipmentInfo info) : base(0xBF) + { + EquipInfoAttribute[] attrs = info.Attributes; + + EnsureCapacity(17 + (info.Crafter == null ? 0 : 6 + info.Crafter.Name == null ? 0 : info.Crafter.Name.Length) + + (info.Unidentified ? 4 : 0) + attrs.Length * 6); + + m_Stream.Write((short)0x10); + m_Stream.Write(item.Serial); + + m_Stream.Write(info.Number); + + if (info.Crafter != null) + { + string name = info.Crafter.Name; + + m_Stream.Write(-3); + + if (name == null) + { + m_Stream.Write((ushort)0); + } + else + { + int length = name.Length; + m_Stream.Write((ushort)length); + m_Stream.WriteAsciiFixed(name, length); + } + } + + if (info.Unidentified) m_Stream.Write(-4); + + for (int i = 0; i < attrs.Length; ++i) + { + m_Stream.Write(attrs[i].Number); + m_Stream.Write((short)attrs[i].Charges); + } + + m_Stream.Write(-1); + } + } + + public sealed class ChangeUpdateRange : Packet + { + private static ChangeUpdateRange[] m_Cache = new ChangeUpdateRange[0x100]; + + public ChangeUpdateRange(int range) : base(0xC8, 2) + { + m_Stream.Write((byte)range); + } + + public static ChangeUpdateRange Instantiate(int range) + { + byte idx = (byte)range; + ChangeUpdateRange p = m_Cache[idx]; + + if (p == null) + { + m_Cache[idx] = p = new ChangeUpdateRange(range); + p.SetStatic(); + } + + return p; + } + } + + public sealed class ChangeCombatant : Packet + { + public ChangeCombatant(Mobile combatant) : base(0xAA, 5) + { + m_Stream.Write(combatant?.Serial ?? Serial.Zero); + } + } + + public sealed class DisplayHuePicker : Packet + { + public DisplayHuePicker(HuePicker huePicker) : base(0x95, 9) + { + m_Stream.Write(huePicker.Serial); + m_Stream.Write((short)0); + m_Stream.Write((short)huePicker.ItemID); + } + } + + public sealed class TripTimeResponse : Packet + { + public TripTimeResponse(int unk) : base(0xC9, 6) + { + m_Stream.Write((byte)unk); + m_Stream.Write(Environment.TickCount); + } + } + + public sealed class UTripTimeResponse : Packet + { + public UTripTimeResponse(int unk) : base(0xCA, 6) + { + m_Stream.Write((byte)unk); + m_Stream.Write(Environment.TickCount); + } + } + + public sealed class UnicodePrompt : Packet + { + public UnicodePrompt(Prompt prompt) : base(0xC2) + { + EnsureCapacity(21); + + m_Stream.Write(prompt.Serial); + m_Stream.Write(prompt.Serial); + m_Stream.Write(0); + m_Stream.Write(0); + m_Stream.Write((short)0); + } + } + + public sealed class ChangeCharacter : Packet + { + public ChangeCharacter(IAccount a) : base(0x81) + { + EnsureCapacity(305); + + int count = 0; + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null) + ++count; + + m_Stream.Write((byte)count); + m_Stream.Write((byte)0); + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null) + { + string name = a[i].Name; + + if (name == null) + name = "-null-"; + else if ((name = name.Trim()).Length == 0) + name = "-empty-"; + + m_Stream.WriteAsciiFixed(name, 30); + m_Stream.Fill(30); // password + } + else + { + m_Stream.Fill(60); + } + } + } + + public sealed class DeathStatus : Packet + { + public static readonly Packet Dead = SetStatic(new DeathStatus(true)); + public static readonly Packet Alive = SetStatic(new DeathStatus(false)); + + public DeathStatus(bool dead) : base(0x2C, 2) + { + m_Stream.Write((byte)(dead ? 0 : 2)); + } + + public static Packet Instantiate(bool dead) + { + return dead ? Dead : Alive; + } + } + + public sealed class SpeedControl : Packet + { + public static readonly Packet WalkSpeed = SetStatic(new SpeedControl(2)); + public static readonly Packet MountSpeed = SetStatic(new SpeedControl(1)); + public static readonly Packet Disable = SetStatic(new SpeedControl(0)); + + public SpeedControl(int speedControl) + : base(0xBF) + { + EnsureCapacity(3); + + m_Stream.Write((short)0x26); + m_Stream.Write((byte)speedControl); + } + } + + public sealed class InvalidMapEnable : Packet + { + public InvalidMapEnable() : base(0xC6, 1) + { + } + } + + public sealed class BondedStatus : Packet + { + public BondedStatus(int val1, Serial serial, int val2) : base(0xBF) + { + EnsureCapacity(11); + + m_Stream.Write((short)0x19); + m_Stream.Write((byte)val1); + m_Stream.Write(serial); + m_Stream.Write((byte)val2); + } + } + + public sealed class ToggleSpecialAbility : Packet + { + public ToggleSpecialAbility(int abilityID, bool active) + : base(0xBF) + { + EnsureCapacity(7); + + m_Stream.Write((short)0x25); + + m_Stream.Write((short)abilityID); + m_Stream.Write(active); + } + } + + public sealed class DisplayItemListMenu : Packet + { + public DisplayItemListMenu(ItemListMenu menu) : base(0x7C) + { + EnsureCapacity(256); + + m_Stream.Write(((IMenu)menu).Serial); + m_Stream.Write((short)0); + + string question = menu.Question; + + if (question == null) + { + m_Stream.Write((byte)0); + } + else + { + int questionLength = question.Length; + m_Stream.Write((byte)questionLength); + m_Stream.WriteAsciiFixed(question, questionLength); + } + + ItemListEntry[] entries = menu.Entries; + + int entriesLength = (byte)entries.Length; + + m_Stream.Write((byte)entriesLength); + + for (int i = 0; i < entriesLength; ++i) + { + ItemListEntry e = entries[i]; + + m_Stream.Write((ushort)e.ItemID); + m_Stream.Write((short)e.Hue); + + string name = e.Name; + + if (name == null) + { + m_Stream.Write((byte)0); + } + else + { + int nameLength = name.Length; + m_Stream.Write((byte)nameLength); + m_Stream.WriteAsciiFixed(name, nameLength); + } + } + } + } + + public sealed class DisplayQuestionMenu : Packet + { + public DisplayQuestionMenu(QuestionMenu menu) : base(0x7C) + { + EnsureCapacity(256); + + m_Stream.Write(((IMenu)menu).Serial); + m_Stream.Write((short)0); + + string question = menu.Question; + + if (question == null) + { + m_Stream.Write((byte)0); + } + else + { + int questionLength = question.Length; + m_Stream.Write((byte)questionLength); + m_Stream.WriteAsciiFixed(question, questionLength); + } + + string[] answers = menu.Answers; + + int answersLength = (byte)answers.Length; + + m_Stream.Write((byte)answersLength); + + for (int i = 0; i < answersLength; ++i) + { + m_Stream.Write(0); + + string answer = answers[i]; + + if (answer == null) + { + m_Stream.Write((byte)0); + } + else + { + int answerLength = answer.Length; + m_Stream.Write((byte)answerLength); + m_Stream.WriteAsciiFixed(answer, answerLength); + } + } + } + } + + public sealed class GlobalLightLevel : Packet + { + private static GlobalLightLevel[] m_Cache = new GlobalLightLevel[0x100]; + + public GlobalLightLevel(int level) : base(0x4F, 2) + { + m_Stream.Write((sbyte)level); + } + + public static GlobalLightLevel Instantiate(int level) + { + byte lvl = (byte)level; + GlobalLightLevel p = m_Cache[lvl]; + + if (p == null) + { + m_Cache[lvl] = p = new GlobalLightLevel(level); + p.SetStatic(); + } + + return p; + } + } + + public sealed class PersonalLightLevel : Packet + { + public PersonalLightLevel(Mobile m) : this(m, m.LightLevel) + { + } + + public PersonalLightLevel(Mobile m, int level) : base(0x4E, 6) + { + m_Stream.Write(m.Serial); + m_Stream.Write((sbyte)level); + } + } + + public sealed class PersonalLightLevelZero : Packet + { + public PersonalLightLevelZero(Mobile m) : base(0x4E, 6) + { + m_Stream.Write(m.Serial); + m_Stream.Write((sbyte)0); + } + } + + [Flags] + public enum CMEFlags + { + None = 0x00, + Disabled = 0x01, + Arrow = 0x02, + Highlighted = 0x04, + Colored = 0x20 + } - public sealed class PersonalLightLevel : Packet - { - public PersonalLightLevel( Mobile m ) : this( m, m.LightLevel ) - { - } + public sealed class DisplayContextMenu : Packet + { + public DisplayContextMenu(ContextMenu menu) : base(0xBF) + { + ContextMenuEntry[] entries = menu.Entries; - public PersonalLightLevel( Mobile m, int level ) : base( 0x4E, 6 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (sbyte) level ); - } - } - - public sealed class PersonalLightLevelZero : Packet - { - public PersonalLightLevelZero( Mobile m ) : base( 0x4E, 6 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (sbyte) 0 ); - } - } - - [Flags] - public enum CMEFlags - { - None = 0x00, - Disabled = 0x01, - Arrow = 0x02, - Highlighted = 0x04, - Colored = 0x20 - } + int length = (byte)entries.Length; - public sealed class DisplayContextMenu : Packet - { - public DisplayContextMenu( ContextMenu menu ) : base( 0xBF ) - { - ContextMenuEntry[] entries = menu.Entries; + EnsureCapacity(12 + length * 8); - int length = (byte) entries.Length; + m_Stream.Write((short)0x14); + m_Stream.Write((short)0x02); - EnsureCapacity( 12 + (length * 8) ); + IEntity target = menu.Target as IEntity; - m_Stream.Write( (short) 0x14 ); - m_Stream.Write( (short) 0x02 ); + m_Stream.Write(target?.Serial ?? Serial.MinusOne); - IEntity target = menu.Target as IEntity; + m_Stream.Write((byte)length); - m_Stream.Write( (int) (target?.Serial ?? Serial.MinusOne) ); + Point3D p; - m_Stream.Write( (byte) length ); + if (target is Mobile) + p = target.Location; + else if (target is Item item) + p = item.GetWorldLocation(); + else + p = Point3D.Zero; - Point3D p; + for (int i = 0; i < length; ++i) + { + ContextMenuEntry e = entries[i]; - if ( target is Mobile ) - p = target.Location; - else if ( target is Item item ) - p = item.GetWorldLocation(); - else - p = Point3D.Zero; + m_Stream.Write(e.Number); + m_Stream.Write((short)i); - for ( int i = 0; i < length; ++i ) - { - ContextMenuEntry e = entries[i]; + int range = e.Range; - m_Stream.Write( (int) e.Number ); - m_Stream.Write( (short) i ); + if (range == -1) + range = 18; - int range = e.Range; + CMEFlags flags = e.Enabled && menu.From.InRange(p, range) ? CMEFlags.None : CMEFlags.Disabled; - if ( range == -1 ) - range = 18; + flags |= e.Flags; - CMEFlags flags = (e.Enabled && menu.From.InRange( p, range )) ? CMEFlags.None : CMEFlags.Disabled; + m_Stream.Write((short)flags); + } + } + } - flags |= e.Flags; + public sealed class DisplayContextMenuOld : Packet + { + public DisplayContextMenuOld(ContextMenu menu) : base(0xBF) + { + ContextMenuEntry[] entries = menu.Entries; - m_Stream.Write( (short) flags ); - } - } - } + int length = (byte)entries.Length; - public sealed class DisplayContextMenuOld : Packet - { - public DisplayContextMenuOld( ContextMenu menu ) : base( 0xBF ) - { - ContextMenuEntry[] entries = menu.Entries; + EnsureCapacity(12 + length * 8); - int length = (byte) entries.Length; + m_Stream.Write((short)0x14); + m_Stream.Write((short)0x01); - EnsureCapacity( 12 + (length * 8) ); + IEntity target = menu.Target as IEntity; - m_Stream.Write( (short) 0x14 ); - m_Stream.Write( (short) 0x01 ); + m_Stream.Write(target?.Serial ?? Serial.MinusOne); - IEntity target = menu.Target as IEntity; + m_Stream.Write((byte)length); - m_Stream.Write( (int) (target?.Serial ?? Serial.MinusOne) ); + Point3D p; - m_Stream.Write( (byte) length ); + if (target is Mobile) + p = target.Location; + else if (target is Item item) + p = item.GetWorldLocation(); + else + p = Point3D.Zero; - Point3D p; + for (int i = 0; i < length; ++i) + { + ContextMenuEntry e = entries[i]; - if ( target is Mobile ) - p = target.Location; - else if ( target is Item item ) - p = item.GetWorldLocation(); - else - p = Point3D.Zero; + m_Stream.Write((short)i); + m_Stream.Write((ushort)(e.Number - 3000000)); - for ( int i = 0; i < length; ++i ) - { - ContextMenuEntry e = entries[i]; + int range = e.Range; - m_Stream.Write( (short) i ); - m_Stream.Write( (ushort) ( e.Number - 3000000 ) ); + if (range == -1) + range = 18; - int range = e.Range; + CMEFlags flags = e.Enabled && menu.From.InRange(p, range) ? CMEFlags.None : CMEFlags.Disabled; - if ( range == -1 ) - range = 18; + int color = e.Color & 0xFFFF; - CMEFlags flags = (e.Enabled && menu.From.InRange( p, range )) ? CMEFlags.None : CMEFlags.Disabled; + if (color != 0xFFFF) + flags |= CMEFlags.Colored; - int color = e.Color & 0xFFFF; + flags |= e.Flags; - if ( color != 0xFFFF ) - flags |= CMEFlags.Colored; + m_Stream.Write((short)flags); - flags |= e.Flags; + if ((flags & CMEFlags.Colored) != 0) + m_Stream.Write((short)color); + } + } + } - m_Stream.Write( (short) flags ); + public sealed class DisplayProfile : Packet + { + public DisplayProfile(bool realSerial, Mobile m, string header, string body, string footer) : base(0xB8) + { + if (header == null) + header = ""; - if ( (flags & CMEFlags.Colored) != 0 ) - m_Stream.Write( (short) color ); - } - } - } + if (body == null) + body = ""; - public sealed class DisplayProfile : Packet - { - public DisplayProfile( bool realSerial, Mobile m, string header, string body, string footer ) : base( 0xB8 ) - { - if ( header == null ) - header = ""; + if (footer == null) + footer = ""; - if ( body == null ) - body = ""; - - if ( footer == null ) - footer = ""; + EnsureCapacity(12 + header.Length + footer.Length * 2 + body.Length * 2); - EnsureCapacity( 12 + header.Length + (footer.Length * 2) + (body.Length * 2) ); - - m_Stream.Write( (int) (realSerial ? m.Serial : Serial.Zero) ); - m_Stream.WriteAsciiNull( header ); - m_Stream.WriteBigUniNull( footer ); - m_Stream.WriteBigUniNull( body ); - } - } + m_Stream.Write(realSerial ? m.Serial : Serial.Zero); + m_Stream.WriteAsciiNull(header); + m_Stream.WriteBigUniNull(footer); + m_Stream.WriteBigUniNull(body); + } + } - public sealed class CloseGump : Packet - { - public CloseGump( int typeID, int buttonID ) : base( 0xBF ) - { - EnsureCapacity( 13 ); + public sealed class CloseGump : Packet + { + public CloseGump(int typeID, int buttonID) : base(0xBF) + { + EnsureCapacity(13); - m_Stream.Write( (short) 0x04 ); - m_Stream.Write( (int) typeID ); - m_Stream.Write( (int) buttonID ); - } - } + m_Stream.Write((short)0x04); + m_Stream.Write(typeID); + m_Stream.Write(buttonID); + } + } - public sealed class EquipUpdate : Packet - { - public EquipUpdate( Item item ) : base( 0x2E, 15 ) - { - Serial parentSerial; - - Mobile parent = item.Parent as Mobile; + public sealed class EquipUpdate : Packet + { + public EquipUpdate(Item item) : base(0x2E, 15) + { + Serial parentSerial; - if ( parent != null ) - { - parentSerial = parent.Serial; - } - else - { - Console.WriteLine( "Warning: EquipUpdate on item with !(parent is Mobile)" ); - parentSerial = Serial.Zero; - } - - int hue = item.Hue; - - if ( parent != null ) - { - if ( parent.SolidHueOverride >= 0 ) - hue = parent.SolidHueOverride; - } - - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (short) item.ItemID ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) item.Layer ); - m_Stream.Write( (int) parentSerial ); - m_Stream.Write( (short) hue ); - } - } - - public sealed class WorldItem : Packet - { - public WorldItem( Item item ) : base( 0x1A ) - { - EnsureCapacity( 20 ); + Mobile parent = item.Parent as Mobile; - // 14 base length - // +2 - Amount - // +2 - Hue - // +1 - Flags + if (parent != null) + { + parentSerial = parent.Serial; + } + else + { + Console.WriteLine("Warning: EquipUpdate on item with !(parent is Mobile)"); + parentSerial = Serial.Zero; + } - uint serial = (uint)item.Serial.Value; - int itemID = item.ItemID & 0x3FFF; - int amount = item.Amount; - Point3D loc = item.Location; - int x = loc.m_X; - int y = loc.m_Y; - int hue = item.Hue; - int flags = item.GetPacketFlags(); - int direction = (int)item.Direction; + int hue = item.Hue; - if ( amount != 0 ) - { - serial |= 0x80000000; - } - else - { - serial &= 0x7FFFFFFF; - } - - m_Stream.Write( (uint) serial ); - - if ( item is BaseMulti ) - m_Stream.Write( (short) (itemID | 0x4000) ); - else - m_Stream.Write( (short) itemID ); - - if ( amount != 0 ) - { - m_Stream.Write( (short) amount ); - } - - x &= 0x7FFF; - - if ( direction != 0 ) - { - x |= 0x8000; - } - - m_Stream.Write( (short) x ); + if (parent != null) + if (parent.SolidHueOverride >= 0) + hue = parent.SolidHueOverride; - y &= 0x3FFF; + m_Stream.Write(item.Serial); + m_Stream.Write((short)item.ItemID); + m_Stream.Write((byte)0); + m_Stream.Write((byte)item.Layer); + m_Stream.Write(parentSerial); + m_Stream.Write((short)hue); + } + } - if ( hue != 0 ) - { - y |= 0x8000; - } + public sealed class WorldItem : Packet + { + public WorldItem(Item item) : base(0x1A) + { + EnsureCapacity(20); - if ( flags != 0 ) - { - y |= 0x4000; - } + // 14 base length + // +2 - Amount + // +2 - Hue + // +1 - Flags - m_Stream.Write( (short) y ); + uint serial = (uint)item.Serial.Value; + int itemID = item.ItemID & 0x3FFF; + int amount = item.Amount; + Point3D loc = item.Location; + int x = loc.m_X; + int y = loc.m_Y; + int hue = item.Hue; + int flags = item.GetPacketFlags(); + int direction = (int)item.Direction; + + if (amount != 0) + serial |= 0x80000000; + else + serial &= 0x7FFFFFFF; + + m_Stream.Write(serial); + + if (item is BaseMulti) + m_Stream.Write((short)(itemID | 0x4000)); + else + m_Stream.Write((short)itemID); + + if (amount != 0) m_Stream.Write((short)amount); + + x &= 0x7FFF; - if ( direction != 0 ) - m_Stream.Write( (byte) direction ); + if (direction != 0) x |= 0x8000; - m_Stream.Write( (sbyte) loc.m_Z ); + m_Stream.Write((short)x); - if ( hue != 0 ) - m_Stream.Write( (ushort) hue ); + y &= 0x3FFF; - if ( flags != 0 ) - m_Stream.Write( (byte) flags ); - } - } + if (hue != 0) y |= 0x8000; + + if (flags != 0) y |= 0x4000; + + m_Stream.Write((short)y); + + if (direction != 0) + m_Stream.Write((byte)direction); + + m_Stream.Write((sbyte)loc.m_Z); + + if (hue != 0) + m_Stream.Write((ushort)hue); + + if (flags != 0) + m_Stream.Write((byte)flags); + } + } - public sealed class WorldItemSA : Packet - { - public WorldItemSA( Item item ) : base( 0xF3, 24 ) - { - m_Stream.Write( (short) 0x1 ); + public sealed class WorldItemSA : Packet + { + public WorldItemSA(Item item) : base(0xF3, 24) + { + m_Stream.Write((short)0x1); - int itemID = item.ItemID; + int itemID = item.ItemID; - if ( item is BaseMulti ) { - m_Stream.Write( (byte) 0x02 ); + if (item is BaseMulti) + { + m_Stream.Write((byte)0x02); - m_Stream.Write( (int) item.Serial ); + m_Stream.Write(item.Serial); - itemID &= 0x3FFF; + itemID &= 0x3FFF; - m_Stream.Write( (short) itemID ); + m_Stream.Write((short)itemID); - m_Stream.Write( (byte) 0 ); - /*} else if ( ) { - m_Stream.Write( (byte) 0x01 ); + m_Stream.Write((byte)0); + /*} else if ( ) { + m_Stream.Write( (byte) 0x01 ); + + m_Stream.Write( (int) item.Serial ); + + m_Stream.Write( (short) itemID ); + + m_Stream.Write( (byte) item.Direction );*/ + } + else + { + m_Stream.Write((byte)0x00); + + m_Stream.Write(item.Serial); - m_Stream.Write( (int) item.Serial ); + itemID &= 0x7FFF; - m_Stream.Write( (short) itemID ); + m_Stream.Write((short)itemID); - m_Stream.Write( (byte) item.Direction );*/ - } else { - m_Stream.Write( (byte) 0x00 ); + m_Stream.Write((byte)0); + } + + int amount = item.Amount; + m_Stream.Write((short)amount); + m_Stream.Write((short)amount); + + Point3D loc = item.Location; + int x = loc.m_X & 0x7FFF; + int y = loc.m_Y & 0x3FFF; + m_Stream.Write((short)x); + m_Stream.Write((short)y); + m_Stream.Write((sbyte)loc.m_Z); + + m_Stream.Write((byte)item.Light); + m_Stream.Write((short)item.Hue); + m_Stream.Write((byte)item.GetPacketFlags()); + } + } + + public sealed class WorldItemHS : Packet + { + public WorldItemHS(Item item) : base(0xF3, 26) + { + m_Stream.Write((short)0x1); + + int itemID = item.ItemID; + + if (item is BaseMulti) + { + m_Stream.Write((byte)0x02); + + m_Stream.Write(item.Serial); + + itemID &= 0x3FFF; + + m_Stream.Write((ushort)itemID); + + m_Stream.Write((byte)0); + /*} else if ( ) { + m_Stream.Write( (byte) 0x01 ); + + m_Stream.Write( (int) item.Serial ); + + m_Stream.Write( (ushort) itemID ); + + m_Stream.Write( (byte) item.Direction );*/ + } + else + { + m_Stream.Write((byte)0x00); + + m_Stream.Write(item.Serial); + + itemID &= 0xFFFF; + + m_Stream.Write((ushort)itemID); + + m_Stream.Write((byte)0); + } + + int amount = item.Amount; + m_Stream.Write((short)amount); + m_Stream.Write((short)amount); + + Point3D loc = item.Location; + int x = loc.m_X & 0x7FFF; + int y = loc.m_Y & 0x3FFF; + m_Stream.Write((short)x); + m_Stream.Write((short)y); + m_Stream.Write((sbyte)loc.m_Z); + + m_Stream.Write((byte)item.Light); + m_Stream.Write((short)item.Hue); + m_Stream.Write((byte)item.GetPacketFlags()); + + m_Stream.Write((short)0x00); // ?? + } + } + + public sealed class LiftRej : Packet + { + public LiftRej(LRReason reason) : base(0x27, 2) + { + m_Stream.Write((byte)reason); + } + } + + public sealed class LogoutAck : Packet + { + public LogoutAck() : base(0xD1, 2) + { + m_Stream.Write((byte)0x01); + } + } + + public sealed class Weather : Packet + { + public Weather(int v1, int v2, int v3) : base(0x65, 4) + { + m_Stream.Write((byte)v1); + m_Stream.Write((byte)v2); + m_Stream.Write((byte)v3); + } + } + + public sealed class UnkD3 : Packet + { + public UnkD3(Mobile beholder, Mobile beheld) : base(0xD3) + { + EnsureCapacity(256); + + //int + //short + //short + //short + //byte + //byte + //short + //byte + //byte + //short + //short + //short + //while ( int != 0 ) + //{ + //short + //byte + //short + //} + + m_Stream.Write(beheld.Serial); + m_Stream.Write((short)beheld.Body); + m_Stream.Write((short)beheld.X); + m_Stream.Write((short)beheld.Y); + m_Stream.Write((sbyte)beheld.Z); + m_Stream.Write((byte)beheld.Direction); + m_Stream.Write((ushort)beheld.Hue); + m_Stream.Write((byte)beheld.GetPacketFlags()); + m_Stream.Write((byte)Notoriety.Compute(beholder, beheld)); + + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + + m_Stream.Write(0); + } + } + + public sealed class GQRequest : Packet + { + public GQRequest() : base(0xC3) + { + EnsureCapacity(256); + + m_Stream.Write(1); + m_Stream.Write(2); // ID + m_Stream.Write(3); // Customer ? (this) + m_Stream.Write(4); // Customer this (?) + m_Stream.Write(0); + m_Stream.Write((short)0); + m_Stream.Write((short)6); + m_Stream.Write((byte)'r'); + m_Stream.Write((byte)'e'); + m_Stream.Write((byte)'g'); + m_Stream.Write((byte)'i'); + m_Stream.Write((byte)'o'); + m_Stream.Write((byte)'n'); + m_Stream.Write(7); // Call time in seconds + m_Stream.Write((short)2); // Map (0=fel,1=tram,2=ilsh) + m_Stream.Write(8); // X + m_Stream.Write(9); // Y + m_Stream.Write(10); // Z + m_Stream.Write(11); // Volume + m_Stream.Write(12); // Rank + m_Stream.Write(-1); + m_Stream.Write(1); // type + } + } + + /// + /// Causes the client to walk in a given direction. It does not send a movement request. + /// + public sealed class PlayerMove : Packet + { + public PlayerMove(Direction d) : base(0x97, 2) + { + m_Stream.Write((byte)d); + + // @4C63B0 + } + } + + /// + /// Displays a message "There are currently [count] available calls in the global queue.". + /// + public sealed class GQCount : Packet + { + public GQCount(int unk, int count) : base(0xCB, 7) + { + m_Stream.Write((short)unk); + m_Stream.Write(count); + } + } + + /// + /// Asks the client for it's version + /// + public sealed class ClientVersionReq : Packet + { + public ClientVersionReq() : base(0xBD) + { + EnsureCapacity(3); + } + } + + /// + /// Asks the client for it's "assist version". (Perhaps for UOAssist?) + /// + public sealed class AssistVersionReq : Packet + { + public AssistVersionReq(int unk) : base(0xBE) + { + EnsureCapacity(7); + + m_Stream.Write(unk); + } + } + + public enum EffectType + { + Moving = 0x00, + Lightning = 0x01, + FixedXYZ = 0x02, + FixedFrom = 0x03 + } + + public class ParticleEffect : Packet + { + public ParticleEffect(EffectType type, Serial from, Serial to, int itemID, Point3D fromPoint, Point3D toPoint, + int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode, int effect, + int explodeEffect, int explodeSound, Serial serial, int layer, int unknown) : base(0xC7, 49) + { + m_Stream.Write((byte)type); + m_Stream.Write(from); + m_Stream.Write(to); + m_Stream.Write((short)itemID); + m_Stream.Write((short)fromPoint.m_X); + m_Stream.Write((short)fromPoint.m_Y); + m_Stream.Write((sbyte)fromPoint.m_Z); + m_Stream.Write((short)toPoint.m_X); + m_Stream.Write((short)toPoint.m_Y); + m_Stream.Write((sbyte)toPoint.m_Z); + m_Stream.Write((byte)speed); + m_Stream.Write((byte)duration); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0); + m_Stream.Write(fixedDirection); + m_Stream.Write(explode); + m_Stream.Write(hue); + m_Stream.Write(renderMode); + m_Stream.Write((short)effect); + m_Stream.Write((short)explodeEffect); + m_Stream.Write((short)explodeSound); + m_Stream.Write(serial); + m_Stream.Write((byte)layer); + m_Stream.Write((short)unknown); + } + + public ParticleEffect(EffectType type, Serial from, Serial to, int itemID, IPoint3D fromPoint, IPoint3D toPoint, + int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode, int effect, + int explodeEffect, int explodeSound, Serial serial, int layer, int unknown) : base(0xC7, 49) + { + m_Stream.Write((byte)type); + m_Stream.Write(from); + m_Stream.Write(to); + m_Stream.Write((short)itemID); + m_Stream.Write((short)fromPoint.X); + m_Stream.Write((short)fromPoint.Y); + m_Stream.Write((sbyte)fromPoint.Z); + m_Stream.Write((short)toPoint.X); + m_Stream.Write((short)toPoint.Y); + m_Stream.Write((sbyte)toPoint.Z); + m_Stream.Write((byte)speed); + m_Stream.Write((byte)duration); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0); + m_Stream.Write(fixedDirection); + m_Stream.Write(explode); + m_Stream.Write(hue); + m_Stream.Write(renderMode); + m_Stream.Write((short)effect); + m_Stream.Write((short)explodeEffect); + m_Stream.Write((short)explodeSound); + m_Stream.Write(serial); + m_Stream.Write((byte)layer); + m_Stream.Write((short)unknown); + } + } + + public class HuedEffect : Packet + { + public HuedEffect(EffectType type, Serial from, Serial to, int itemID, Point3D fromPoint, Point3D toPoint, int speed, + int duration, bool fixedDirection, bool explode, int hue, int renderMode) : base(0xC0, 36) + { + m_Stream.Write((byte)type); + m_Stream.Write(from); + m_Stream.Write(to); + m_Stream.Write((short)itemID); + m_Stream.Write((short)fromPoint.m_X); + m_Stream.Write((short)fromPoint.m_Y); + m_Stream.Write((sbyte)fromPoint.m_Z); + m_Stream.Write((short)toPoint.m_X); + m_Stream.Write((short)toPoint.m_Y); + m_Stream.Write((sbyte)toPoint.m_Z); + m_Stream.Write((byte)speed); + m_Stream.Write((byte)duration); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0); + m_Stream.Write(fixedDirection); + m_Stream.Write(explode); + m_Stream.Write(hue); + m_Stream.Write(renderMode); + } + + public HuedEffect(EffectType type, Serial from, Serial to, int itemID, IPoint3D fromPoint, IPoint3D toPoint, + int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode) : base(0xC0, 36) + { + m_Stream.Write((byte)type); + m_Stream.Write(from); + m_Stream.Write(to); + m_Stream.Write((short)itemID); + m_Stream.Write((short)fromPoint.X); + m_Stream.Write((short)fromPoint.Y); + m_Stream.Write((sbyte)fromPoint.Z); + m_Stream.Write((short)toPoint.X); + m_Stream.Write((short)toPoint.Y); + m_Stream.Write((sbyte)toPoint.Z); + m_Stream.Write((byte)speed); + m_Stream.Write((byte)duration); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0); + m_Stream.Write(fixedDirection); + m_Stream.Write(explode); + m_Stream.Write(hue); + m_Stream.Write(renderMode); + } + } + + public sealed class TargetParticleEffect : ParticleEffect + { + public TargetParticleEffect(IEntity e, int itemID, int speed, int duration, int hue, int renderMode, int effect, + int layer, int unknown) : base(EffectType.FixedFrom, e.Serial, Serial.Zero, itemID, e.Location, e.Location, + speed, duration, true, false, hue, renderMode, effect, 1, 0, e.Serial, layer, unknown) + { + } + } + + public sealed class TargetEffect : HuedEffect + { + public TargetEffect(IEntity e, int itemID, int speed, int duration, int hue, int renderMode) : base( + EffectType.FixedFrom, e.Serial, Serial.Zero, itemID, e.Location, e.Location, speed, duration, true, false, hue, + renderMode) + { + } + } + + public sealed class LocationParticleEffect : ParticleEffect + { + public LocationParticleEffect(IEntity e, int itemID, int speed, int duration, int hue, int renderMode, int effect, + int unknown) : base(EffectType.FixedXYZ, e.Serial, Serial.Zero, itemID, e.Location, e.Location, speed, duration, + true, false, hue, renderMode, effect, 1, 0, e.Serial, 255, unknown) + { + } + } + + public sealed class LocationEffect : HuedEffect + { + public LocationEffect(IPoint3D p, int itemID, int speed, int duration, int hue, int renderMode) : base( + EffectType.FixedXYZ, Serial.Zero, Serial.Zero, itemID, p, p, speed, duration, true, false, hue, renderMode) + { + } + } + + public sealed class MovingParticleEffect : ParticleEffect + { + public MovingParticleEffect(IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, + bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, EffectLayer layer, + int unknown) : base(EffectType.Moving, from.Serial, to.Serial, itemID, from.Location, to.Location, speed, + duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, Serial.Zero, + (int)layer, unknown) + { + } + } + + public sealed class MovingEffect : HuedEffect + { + public MovingEffect(IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, + bool explodes, int hue, int renderMode) : base(EffectType.Moving, from.Serial, to.Serial, itemID, from.Location, + to.Location, speed, duration, fixedDirection, explodes, hue, renderMode) + { + } + } + + public enum ScreenEffectType + { + FadeOut = 0x00, + FadeIn = 0x01, + LightFlash = 0x02, + FadeInOut = 0x03, + DarkFlash = 0x04 + } + + public class ScreenEffect : Packet + { + public ScreenEffect(ScreenEffectType type) + : base(0x70, 28) + { + m_Stream.Write((byte)0x04); + m_Stream.Fill(8); + m_Stream.Write((short)type); + m_Stream.Fill(16); + } + } + + public sealed class ScreenFadeOut : ScreenEffect + { + public static readonly Packet Instance = SetStatic(new ScreenFadeOut()); + + public ScreenFadeOut() + : base(ScreenEffectType.FadeOut) + { + } + } + + public sealed class ScreenFadeIn : ScreenEffect + { + public static readonly Packet Instance = SetStatic(new ScreenFadeIn()); + + public ScreenFadeIn() + : base(ScreenEffectType.FadeIn) + { + } + } + + public sealed class ScreenFadeInOut : ScreenEffect + { + public static readonly Packet Instance = SetStatic(new ScreenFadeInOut()); + + public ScreenFadeInOut() + : base(ScreenEffectType.FadeInOut) + { + } + } + + public sealed class ScreenLightFlash : ScreenEffect + { + public static readonly Packet Instance = SetStatic(new ScreenLightFlash()); + + public ScreenLightFlash() + : base(ScreenEffectType.LightFlash) + { + } + } + + public sealed class ScreenDarkFlash : ScreenEffect + { + public static readonly Packet Instance = SetStatic(new ScreenDarkFlash()); + + public ScreenDarkFlash() + : base(ScreenEffectType.DarkFlash) + { + } + } + + public enum DeleteResultType + { + PasswordInvalid, + CharNotExist, + CharBeingPlayed, + CharTooYoung, + CharQueued, + BadRequest + } + + public sealed class DeleteResult : Packet + { + public DeleteResult(DeleteResultType res) : base(0x85, 2) + { + m_Stream.Write((byte)res); + } + } + + /*public sealed class MovingEffect : Packet + { + public MovingEffect( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool turn, int hue, int renderMode ) : base( 0xC0, 36 ) + { + m_Stream.Write( (byte) 0x00 ); + m_Stream.Write( (int) from.Serial ); + m_Stream.Write( (int) to.Serial ); + m_Stream.Write( (short) itemID ); + m_Stream.Write( (short) from.Location.m_X ); + m_Stream.Write( (short) from.Location.m_Y ); + m_Stream.Write( (sbyte) from.Location.m_Z ); + m_Stream.Write( (short) to.Location.m_X ); + m_Stream.Write( (short) to.Location.m_Y ); + m_Stream.Write( (sbyte) to.Location.m_Z ); + m_Stream.Write( (byte) speed ); + m_Stream.Write( (byte) duration ); + m_Stream.Write( (byte) 0 ); + m_Stream.Write( (byte) 0 ); + m_Stream.Write( (bool) fixedDirection ); + m_Stream.Write( (bool) turn ); + m_Stream.Write( (int) hue ); + m_Stream.Write( (int) renderMode ); + } + }*/ + + /*public sealed class LocationEffect : Packet + { + public LocationEffect( IPoint3D p, int itemID, int duration, int hue, int renderMode ) : base( 0xC0, 36 ) + { + m_Stream.Write( (byte) 0x02 ); + m_Stream.Write( (int) Serial.Zero ); + m_Stream.Write( (int) Serial.Zero ); + m_Stream.Write( (short) itemID ); + m_Stream.Write( (short) p.X ); + m_Stream.Write( (short) p.Y ); + m_Stream.Write( (sbyte) p.Z ); + m_Stream.Write( (short) p.X ); + m_Stream.Write( (short) p.Y ); + m_Stream.Write( (sbyte) p.Z ); + m_Stream.Write( (byte) 10 ); + m_Stream.Write( (byte) duration ); + m_Stream.Write( (byte) 0 ); + m_Stream.Write( (byte) 0 ); + m_Stream.Write( (byte) 1 ); + m_Stream.Write( (byte) 0 ); + m_Stream.Write( (int) hue ); + m_Stream.Write( (int) renderMode ); + } + }*/ + + public sealed class BoltEffect : Packet + { + public BoltEffect(IEntity target, int hue) : base(0xC0, 36) + { + m_Stream.Write((byte)0x01); // type + m_Stream.Write(target.Serial); + m_Stream.Write(Serial.Zero); + m_Stream.Write((short)0); // itemID + m_Stream.Write((short)target.X); + m_Stream.Write((short)target.Y); + m_Stream.Write((sbyte)target.Z); + m_Stream.Write((short)target.X); + m_Stream.Write((short)target.Y); + m_Stream.Write((sbyte)target.Z); + m_Stream.Write((byte)0); // speed + m_Stream.Write((byte)0); // duration + m_Stream.Write((short)0); // unk + m_Stream.Write(false); // fixed direction + m_Stream.Write(false); // explode + m_Stream.Write(hue); + m_Stream.Write(0); // render mode + } + } + + public sealed class DisplaySpellbook : Packet + { + public DisplaySpellbook(Item book) : base(0x24, 7) + { + m_Stream.Write(book.Serial); + m_Stream.Write((short)-1); + } + } + + public sealed class DisplaySpellbookHS : Packet + { + public DisplaySpellbookHS(Item book) : base(0x24, 9) + { + m_Stream.Write(book.Serial); + m_Stream.Write((short)-1); + m_Stream.Write((short)0x7D); + } + } + + public sealed class NewSpellbookContent : Packet + { + public NewSpellbookContent(Item item, int graphic, int offset, ulong content) : base(0xBF) + { + EnsureCapacity(23); + + m_Stream.Write((short)0x1B); + m_Stream.Write((short)0x01); + + m_Stream.Write(item.Serial); + m_Stream.Write((short)graphic); + m_Stream.Write((short)offset); + + for (int i = 0; i < 8; ++i) + m_Stream.Write((byte)(content >> (i * 8))); + } + } + + public sealed class SpellbookContent : Packet + { + public SpellbookContent(int count, int offset, ulong content, Item item) : base(0x3C) + { + EnsureCapacity(5 + count * 19); + + int written = 0; + + m_Stream.Write((ushort)0); + + ulong mask = 1; + + for (int i = 0; i < 64; ++i, mask <<= 1) + if ((content & mask) != 0) + { + m_Stream.Write(0x7FFFFFFF - i); + m_Stream.Write((ushort)0); + m_Stream.Write((byte)0); + m_Stream.Write((ushort)(i + offset)); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write(item.Serial); + m_Stream.Write((short)0); + + ++written; + } + + m_Stream.Seek(3, SeekOrigin.Begin); + m_Stream.Write((ushort)written); + } + } + + public sealed class SpellbookContent6017 : Packet + { + public SpellbookContent6017(int count, int offset, ulong content, Item item) : base(0x3C) + { + EnsureCapacity(5 + count * 20); + + int written = 0; + + m_Stream.Write((ushort)0); + + ulong mask = 1; + + for (int i = 0; i < 64; ++i, mask <<= 1) + if ((content & mask) != 0) + { + m_Stream.Write(0x7FFFFFFF - i); + m_Stream.Write((ushort)0); + m_Stream.Write((byte)0); + m_Stream.Write((ushort)(i + offset)); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(item.Serial); + m_Stream.Write((short)0); + + ++written; + } + + m_Stream.Seek(3, SeekOrigin.Begin); + m_Stream.Write((ushort)written); + } + } + + public sealed class ContainerDisplay : Packet + { + public ContainerDisplay(Container c) : base(0x24, 7) + { + m_Stream.Write(c.Serial); + m_Stream.Write((short)c.GumpID); + } + } + + public sealed class ContainerDisplayHS : Packet + { + public ContainerDisplayHS(Container c) : base(0x24, 9) + { + m_Stream.Write(c.Serial); + m_Stream.Write((short)c.GumpID); + m_Stream.Write((short)0x7D); + } + } + + public sealed class ContainerContentUpdate : Packet + { + public ContainerContentUpdate(Item item) : base(0x25, 20) + { + Serial parentSerial; + + if (item.Parent is Item parentItem) + { + parentSerial = parentItem.Serial; + } + else + { + Console.WriteLine("Warning: ContainerContentUpdate on item with !(parent is Item)"); + parentSerial = Serial.Zero; + } + + m_Stream.Write(item.Serial); + m_Stream.Write((ushort)item.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)item.Amount); + m_Stream.Write((short)item.X); + m_Stream.Write((short)item.Y); + m_Stream.Write(parentSerial); + m_Stream.Write((ushort)(item.QuestItem ? Item.QuestItemHue : item.Hue)); + } + } + + public sealed class ContainerContentUpdate6017 : Packet + { + public ContainerContentUpdate6017(Item item) : base(0x25, 21) + { + Serial parentSerial; + + if (item.Parent is Item parentItem) + { + parentSerial = parentItem.Serial; + } + else + { + Console.WriteLine("Warning: ContainerContentUpdate on item with !(parent is Item)"); + parentSerial = Serial.Zero; + } + + m_Stream.Write(item.Serial); + m_Stream.Write((ushort)item.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)item.Amount); + m_Stream.Write((short)item.X); + m_Stream.Write((short)item.Y); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(parentSerial); + m_Stream.Write((ushort)(item.QuestItem ? Item.QuestItemHue : item.Hue)); + } + } + + public sealed class ContainerContent : Packet + { + public ContainerContent(Mobile beholder, Item beheld) : base(0x3C) + { + List items = beheld.Items; + int count = items.Count; + + EnsureCapacity(5 + count * 19); + + long pos = m_Stream.Position; + + int written = 0; + + m_Stream.Write((ushort)0); + + for (int i = 0; i < count; ++i) + { + Item child = items[i]; + + if (!child.Deleted && beholder.CanSee(child)) + { + Point3D loc = child.Location; + + m_Stream.Write(child.Serial); + m_Stream.Write((ushort)child.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)child.Amount); + m_Stream.Write((short)loc.m_X); + m_Stream.Write((short)loc.m_Y); + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)(child.QuestItem ? Item.QuestItemHue : child.Hue)); + + ++written; + } + } + + m_Stream.Seek(pos, SeekOrigin.Begin); + m_Stream.Write((ushort)written); + } + } + + public sealed class ContainerContent6017 : Packet + { + public ContainerContent6017(Mobile beholder, Item beheld) : base(0x3C) + { + List items = beheld.Items; + int count = items.Count; + + EnsureCapacity(5 + count * 20); + + long pos = m_Stream.Position; + + int written = 0; + + m_Stream.Write((ushort)0); + + for (int i = 0; i < count; ++i) + { + Item child = items[i]; + + if (!child.Deleted && beholder.CanSee(child)) + { + Point3D loc = child.Location; + + m_Stream.Write(child.Serial); + m_Stream.Write((ushort)child.ItemID); + m_Stream.Write((byte)0); // signed, itemID offset + m_Stream.Write((ushort)child.Amount); + m_Stream.Write((short)loc.m_X); + m_Stream.Write((short)loc.m_Y); + m_Stream.Write((byte)0); // Grid Location? + m_Stream.Write(beheld.Serial); + m_Stream.Write((ushort)(child.QuestItem ? Item.QuestItemHue : child.Hue)); + + ++written; + } + } + + m_Stream.Seek(pos, SeekOrigin.Begin); + m_Stream.Write((ushort)written); + } + } + + public sealed class SetWarMode : Packet + { + public static readonly Packet InWarMode = SetStatic(new SetWarMode(true)); + public static readonly Packet InPeaceMode = SetStatic(new SetWarMode(false)); + + public SetWarMode(bool mode) : base(0x72, 5) + { + m_Stream.Write(mode); + m_Stream.Write((byte)0x00); + m_Stream.Write((byte)0x32); + m_Stream.Write((byte)0x00); + //m_Stream.Fill(); + } + + public static Packet Instantiate(bool mode) + { + return mode ? InWarMode : InPeaceMode; + } + } + + public sealed class Swing : Packet + { + public Swing(int flag, Mobile attacker, Mobile defender) : base(0x2F, 10) + { + m_Stream.Write((byte)flag); + m_Stream.Write(attacker.Serial); + m_Stream.Write(defender.Serial); + } + } + + public sealed class NullFastwalkStack : Packet + { + public NullFastwalkStack() : base(0xBF) + { + EnsureCapacity(256); + m_Stream.Write((short)0x1); + m_Stream.Write(0x0); + m_Stream.Write(0x0); + m_Stream.Write(0x0); + m_Stream.Write(0x0); + m_Stream.Write(0x0); + m_Stream.Write(0x0); + } + } + + public sealed class RemoveItem : Packet + { + public RemoveItem(Item item) : base(0x1D, 5) + { + m_Stream.Write(item.Serial); + } + } + + public sealed class RemoveMobile : Packet + { + public RemoveMobile(Mobile m) : base(0x1D, 5) + { + m_Stream.Write(m.Serial); + } + } + + public sealed class ServerChange : Packet + { + public ServerChange(Mobile m, Map map) : base(0x76, 16) + { + m_Stream.Write((short)m.X); + m_Stream.Write((short)m.Y); + m_Stream.Write((short)m.Z); + m_Stream.Write((byte)0); + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write((short)map.Width); + m_Stream.Write((short)map.Height); + } + } + + public sealed class SkillUpdate : Packet + { + public SkillUpdate(Skills skills) : base(0x3A) + { + EnsureCapacity(6 + skills.Length * 9); + + m_Stream.Write((byte)0x02); // type: absolute, capped + + for (int i = 0; i < skills.Length; ++i) + { + Skill s = skills[i]; + + double v = s.NonRacialValue; + int uv = (int)(v * 10); + + if (uv < 0) + uv = 0; + else if (uv >= 0x10000) + uv = 0xFFFF; + + m_Stream.Write((ushort)(s.Info.SkillID + 1)); + m_Stream.Write((ushort)uv); + m_Stream.Write((ushort)s.BaseFixedPoint); + m_Stream.Write((byte)s.Lock); + m_Stream.Write((ushort)s.CapFixedPoint); + } + + m_Stream.Write((short)0); // terminate + } + } + + public sealed class Sequence : Packet + { + public Sequence(int num) : base(0x7B, 2) + { + m_Stream.Write((byte)num); + } + } + + public sealed class SkillChange : Packet + { + public SkillChange(Skill skill) : base(0x3A) + { + EnsureCapacity(13); + + double v = skill.NonRacialValue; + int uv = (int)(v * 10); + + if (uv < 0) + uv = 0; + else if (uv >= 0x10000) + uv = 0xFFFF; + + m_Stream.Write((byte)0xDF); // type: delta, capped + m_Stream.Write((ushort)skill.Info.SkillID); + m_Stream.Write((ushort)uv); + m_Stream.Write((ushort)skill.BaseFixedPoint); + m_Stream.Write((byte)skill.Lock); + m_Stream.Write((ushort)skill.CapFixedPoint); + + /*m_Stream.Write( (short) skill.Info.SkillID ); + m_Stream.Write( (short) (skill.Value * 10.0) ); + m_Stream.Write( (short) (skill.Base * 10.0) ); + m_Stream.Write( (byte) skill.Lock ); + m_Stream.Write( (short) skill.CapFixedPoint );*/ + } + } + + public sealed class LaunchBrowser : Packet + { + public LaunchBrowser(string url) : base(0xA5) + { + if (url == null) url = ""; + + EnsureCapacity(4 + url.Length); + + m_Stream.WriteAsciiNull(url); + } + } + + public sealed class MessageLocalized : Packet + { + private static MessageLocalized[] m_Cache_IntLoc = new MessageLocalized[15000]; + private static MessageLocalized[] m_Cache_CliLoc = new MessageLocalized[100000]; + private static MessageLocalized[] m_Cache_CliLocCmp = new MessageLocalized[5000]; + + public MessageLocalized(Serial serial, int graphic, MessageType type, int hue, int font, int number, string name, + string args) : base(0xC1) + { + if (name == null) name = ""; + if (args == null) args = ""; + + if (hue == 0) + hue = 0x3B2; + + EnsureCapacity(50 + args.Length * 2); + + m_Stream.Write(serial); + m_Stream.Write((short)graphic); + m_Stream.Write((byte)type); + m_Stream.Write((short)hue); + m_Stream.Write((short)font); + m_Stream.Write(number); + m_Stream.WriteAsciiFixed(name, 30); + m_Stream.WriteLittleUniNull(args); + } + + public static MessageLocalized InstantiateGeneric(int number) + { + MessageLocalized[] cache = null; + int index = 0; + + if (number >= 3000000) + { + cache = m_Cache_IntLoc; + index = number - 3000000; + } + else if (number >= 1000000) + { + cache = m_Cache_CliLoc; + index = number - 1000000; + } + else if (number >= 500000) + { + cache = m_Cache_CliLocCmp; + index = number - 500000; + } + + MessageLocalized p; + + if (cache != null && index >= 0 && index < cache.Length) + { + p = cache[index]; + + if (p == null) + { + cache[index] = p = new MessageLocalized(Serial.MinusOne, -1, MessageType.Regular, 0x3B2, 3, number, + "System", ""); + p.SetStatic(); + } + } + else + { + p = new MessageLocalized(Serial.MinusOne, -1, MessageType.Regular, 0x3B2, 3, number, "System", ""); + } + + return p; + } + } + + public sealed class MobileMoving : Packet + { + public MobileMoving(Mobile m, int noto) : base(0x77, 17) + { + Point3D loc = m.Location; + + int hue = m.Hue; + + if (m.SolidHueOverride >= 0) + hue = m.SolidHueOverride; + + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.Body); + m_Stream.Write((short)loc.m_X); + m_Stream.Write((short)loc.m_Y); + m_Stream.Write((sbyte)loc.m_Z); + m_Stream.Write((byte)m.Direction); + m_Stream.Write((short)hue); + m_Stream.Write((byte)m.GetPacketFlags()); + m_Stream.Write((byte)noto); + } + } + + // Pre-7.0.0.0 Mobile Moving + public sealed class MobileMovingOld : Packet + { + public MobileMovingOld(Mobile m, int noto) : base(0x77, 17) + { + Point3D loc = m.Location; + + int hue = m.Hue; + + if (m.SolidHueOverride >= 0) + hue = m.SolidHueOverride; + + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.Body); + m_Stream.Write((short)loc.m_X); + m_Stream.Write((short)loc.m_Y); + m_Stream.Write((sbyte)loc.m_Z); + m_Stream.Write((byte)m.Direction); + m_Stream.Write((short)hue); + m_Stream.Write((byte)m.GetOldPacketFlags()); + m_Stream.Write((byte)noto); + } + } + + public sealed class MultiTargetReqHS : Packet + { + public MultiTargetReqHS(MultiTarget t) : base(0x99, 30) + { + m_Stream.Write(t.AllowGround); + m_Stream.Write(t.TargetID); + m_Stream.Write((byte)t.Flags); + + m_Stream.Fill(); + + m_Stream.Seek(18, SeekOrigin.Begin); + m_Stream.Write((short)t.MultiID); + m_Stream.Write((short)t.Offset.X); + m_Stream.Write((short)t.Offset.Y); + m_Stream.Write((short)t.Offset.Z); + + // DWORD Hue + } + } + + public sealed class MultiTargetReq : Packet + { + public MultiTargetReq(MultiTarget t) : base(0x99, 26) + { + m_Stream.Write(t.AllowGround); + m_Stream.Write(t.TargetID); + m_Stream.Write((byte)t.Flags); + + m_Stream.Fill(); + + m_Stream.Seek(18, SeekOrigin.Begin); + m_Stream.Write((short)t.MultiID); + m_Stream.Write((short)t.Offset.X); + m_Stream.Write((short)t.Offset.Y); + m_Stream.Write((short)t.Offset.Z); + } + } + + public sealed class CancelTarget : Packet + { + public static readonly Packet Instance = SetStatic(new CancelTarget()); + + public CancelTarget() : base(0x6C, 19) + { + m_Stream.Write((byte)0); + m_Stream.Write(0); + m_Stream.Write((byte)3); + m_Stream.Fill(); + } + } + + public sealed class TargetReq : Packet + { + public TargetReq(Target t) : base(0x6C, 19) + { + m_Stream.Write(t.AllowGround); + m_Stream.Write(t.TargetID); + m_Stream.Write((byte)t.Flags); + m_Stream.Fill(); + } + } + + public sealed class DragEffect : Packet + { + public DragEffect(IEntity src, IEntity trg, int itemID, int hue, int amount) : base(0x23, 26) + { + m_Stream.Write((short)itemID); + m_Stream.Write((byte)0); + m_Stream.Write((short)hue); + m_Stream.Write((short)amount); + m_Stream.Write(src.Serial); + m_Stream.Write((short)src.X); + m_Stream.Write((short)src.Y); + m_Stream.Write((sbyte)src.Z); + m_Stream.Write(trg.Serial); + m_Stream.Write((short)trg.X); + m_Stream.Write((short)trg.Y); + m_Stream.Write((sbyte)trg.Z); + } + } + + public interface IGumpWriter + { + int TextEntries{ get; set; } + int Switches{ get; set; } + + void AppendLayout(bool val); + void AppendLayout(int val); + void AppendLayoutNS(int val); + void AppendLayout(string text); + void AppendLayout(byte[] buffer); + void WriteStrings(List strings); + void Flush(); + } + + public sealed class DisplayGumpPacked : Packet, IGumpWriter + { + private const int GumpBufferSize = 0x5000; + + private static byte[] m_True = Gump.StringToBuffer(" 1"); + private static byte[] m_False = Gump.StringToBuffer(" 0"); + + private static byte[] m_BeginTextSeparator = Gump.StringToBuffer(" @"); + private static byte[] m_EndTextSeparator = Gump.StringToBuffer("@"); + + private static byte[] m_Buffer = new byte[48]; + private static BufferPool m_PackBuffers = new BufferPool("Gump", 4, GumpBufferSize); + + private Gump m_Gump; + + private PacketWriter m_Layout; + + private int m_StringCount; + private PacketWriter m_Strings; + + static DisplayGumpPacked() + { + m_Buffer[0] = (byte)' '; + } + + public DisplayGumpPacked(Gump gump) + : base(0xDD) + { + m_Gump = gump; + + m_Layout = PacketWriter.CreateInstance(8192); + m_Strings = PacketWriter.CreateInstance(8192); + } + + public int TextEntries{ get; set; } + + public int Switches{ get; set; } + + public void AppendLayout(bool val) + { + AppendLayout(val ? m_True : m_False); + } + + public void AppendLayout(int val) + { + string toString = val.ToString(); + int bytes = Encoding.ASCII.GetBytes(toString, 0, toString.Length, m_Buffer, 1) + 1; + + m_Layout.Write(m_Buffer, 0, bytes); + } + + public void AppendLayoutNS(int val) + { + string toString = val.ToString(); + int bytes = Encoding.ASCII.GetBytes(toString, 0, toString.Length, m_Buffer, 1); + + m_Layout.Write(m_Buffer, 1, bytes); + } + + public void AppendLayout(string text) + { + AppendLayout(m_BeginTextSeparator); + + m_Layout.WriteAsciiFixed(text, text.Length); + + AppendLayout(m_EndTextSeparator); + } + + public void AppendLayout(byte[] buffer) + { + m_Layout.Write(buffer, 0, buffer.Length); + } + + public void WriteStrings(List strings) + { + m_StringCount = strings.Count; - m_Stream.Write( (int) item.Serial ); + for (int i = 0; i < strings.Count; ++i) + { + string v = strings[i]; - itemID &= 0x7FFF; + if (v == null) + v = string.Empty; - m_Stream.Write( (short) itemID ); + m_Strings.Write((ushort)v.Length); + m_Strings.WriteBigUniFixed(v, v.Length); + } + } - m_Stream.Write( (byte) 0 ); - } + public void Flush() + { + EnsureCapacity(28 + (int)m_Layout.Length + (int)m_Strings.Length); - int amount = item.Amount; - m_Stream.Write( (short) amount ); - m_Stream.Write( (short) amount ); + m_Stream.Write(m_Gump.Serial); + m_Stream.Write(m_Gump.TypeID); + m_Stream.Write(m_Gump.X); + m_Stream.Write(m_Gump.Y); - Point3D loc = item.Location; - int x = loc.m_X & 0x7FFF; - int y = loc.m_Y & 0x3FFF; - m_Stream.Write( (short) x ); - m_Stream.Write( (short) y ); - m_Stream.Write( (sbyte) loc.m_Z ); + // Note: layout MUST be null terminated (don't listen to krrios) + m_Layout.Write((byte)0); + WritePacked(m_Layout); - m_Stream.Write( (byte) item.Light ); - m_Stream.Write( (short) item.Hue ); - m_Stream.Write( (byte) item.GetPacketFlags() ); - } - } + m_Stream.Write(m_StringCount); - public sealed class WorldItemHS : Packet - { - public WorldItemHS( Item item ) : base( 0xF3, 26 ) - { - m_Stream.Write( (short) 0x1 ); + WritePacked(m_Strings); - int itemID = item.ItemID; + PacketWriter.ReleaseInstance(m_Layout); + PacketWriter.ReleaseInstance(m_Strings); + } - if ( item is BaseMulti ) { - m_Stream.Write( (byte) 0x02 ); + private void WritePacked(PacketWriter src) + { + byte[] buffer = src.UnderlyingStream.GetBuffer(); + int length = (int)src.Length; - m_Stream.Write( (int) item.Serial ); + if (length == 0) + { + m_Stream.Write(0); + return; + } - itemID &= 0x3FFF; + int wantLength = 1 + buffer.Length * 1024 / 1000; - m_Stream.Write( (ushort) itemID ); - - m_Stream.Write( (byte) 0 ); - /*} else if ( ) { - m_Stream.Write( (byte) 0x01 ); - - m_Stream.Write( (int) item.Serial ); - - m_Stream.Write( (ushort) itemID ); - - m_Stream.Write( (byte) item.Direction );*/ - } else { - m_Stream.Write( (byte) 0x00 ); - - m_Stream.Write( (int) item.Serial ); - - itemID &= 0xFFFF; - - m_Stream.Write( (ushort) itemID ); - - m_Stream.Write( (byte) 0 ); - } - - int amount = item.Amount; - m_Stream.Write( (short) amount ); - m_Stream.Write( (short) amount ); - - Point3D loc = item.Location; - int x = loc.m_X & 0x7FFF; - int y = loc.m_Y & 0x3FFF; - m_Stream.Write( (short) x ); - m_Stream.Write( (short) y ); - m_Stream.Write( (sbyte) loc.m_Z ); - - m_Stream.Write( (byte) item.Light ); - m_Stream.Write( (short) item.Hue ); - m_Stream.Write( (byte) item.GetPacketFlags() ); - - m_Stream.Write( (short) 0x00 ); // ?? - } - } - - public sealed class LiftRej : Packet - { - public LiftRej( LRReason reason ) : base( 0x27, 2 ) - { - m_Stream.Write( (byte) reason ); - } - } - - public sealed class LogoutAck : Packet - { - public LogoutAck() : base( 0xD1, 2 ) - { - m_Stream.Write( (byte) 0x01 ); - } - } - - public sealed class Weather : Packet - { - public Weather( int v1, int v2, int v3 ) : base( 0x65, 4 ) - { - m_Stream.Write( (byte) v1 ); - m_Stream.Write( (byte) v2 ); - m_Stream.Write( (byte) v3 ); - } - } - - public sealed class UnkD3 : Packet - { - public UnkD3( Mobile beholder, Mobile beheld ) : base( 0xD3 ) - { - EnsureCapacity( 256 ); - - //int - //short - //short - //short - //byte - //byte - //short - //byte - //byte - //short - //short - //short - //while ( int != 0 ) - //{ - //short - //byte - //short - //} - - m_Stream.Write( (int) beheld.Serial ); - m_Stream.Write( (short) beheld.Body ); - m_Stream.Write( (short) beheld.X ); - m_Stream.Write( (short) beheld.Y ); - m_Stream.Write( (sbyte) beheld.Z ); - m_Stream.Write( (byte) beheld.Direction ); - m_Stream.Write( (ushort) beheld.Hue ); - m_Stream.Write( (byte) beheld.GetPacketFlags() ); - m_Stream.Write( (byte) Notoriety.Compute( beholder, beheld ) ); - - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 0 ); - - m_Stream.Write( (int) 0 ); - } - } - - public sealed class GQRequest : Packet - { - public GQRequest() : base( 0xC3 ) - { - EnsureCapacity( 256 ); - - m_Stream.Write( (int) 1 ); - m_Stream.Write( (int) 2 ); // ID - m_Stream.Write( (int) 3 ); // Customer ? (this) - m_Stream.Write( (int) 4 ); // Customer this (?) - m_Stream.Write( (int) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 6 ); - m_Stream.Write( (byte) 'r' ); - m_Stream.Write( (byte) 'e' ); - m_Stream.Write( (byte) 'g' ); - m_Stream.Write( (byte) 'i' ); - m_Stream.Write( (byte) 'o' ); - m_Stream.Write( (byte) 'n' ); - m_Stream.Write( (int) 7 ); // Call time in seconds - m_Stream.Write( (short) 2 ); // Map (0=fel,1=tram,2=ilsh) - m_Stream.Write( (int) 8 ); // X - m_Stream.Write( (int) 9 ); // Y - m_Stream.Write( (int) 10 ); // Z - m_Stream.Write( (int) 11 ); // Volume - m_Stream.Write( (int) 12 ); // Rank - m_Stream.Write( (int) -1 ); - m_Stream.Write( (int) 1 ); // type - } - } - - /// - /// Causes the client to walk in a given direction. It does not send a movement request. - /// - public sealed class PlayerMove : Packet - { - public PlayerMove( Direction d ) : base( 0x97, 2 ) - { - m_Stream.Write( (byte) d ); - - // @4C63B0 - } - } - - /// - /// Displays a message "There are currently [count] available calls in the global queue.". - /// - public sealed class GQCount : Packet - { - public GQCount( int unk, int count ) : base( 0xCB, 7 ) - { - m_Stream.Write( (short) unk ); - m_Stream.Write( (int) count ); - } - } - - /// - /// Asks the client for it's version - /// - public sealed class ClientVersionReq : Packet - { - public ClientVersionReq() : base( 0xBD ) - { - EnsureCapacity( 3 ); - } - } - - /// - /// Asks the client for it's "assist version". (Perhaps for UOAssist?) - /// - public sealed class AssistVersionReq : Packet - { - public AssistVersionReq( int unk ) : base( 0xBE ) - { - EnsureCapacity( 7 ); - - m_Stream.Write( (int) unk ); - } - } - - public enum EffectType - { - Moving = 0x00, - Lightning = 0x01, - FixedXYZ = 0x02, - FixedFrom = 0x03 - } - - public class ParticleEffect : Packet - { - public ParticleEffect( EffectType type, Serial from, Serial to, int itemID, Point3D fromPoint, Point3D toPoint, int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, Serial serial, int layer, int unknown ) : base( 0xC7, 49 ) - { - m_Stream.Write( (byte) type ); - m_Stream.Write( (int) from ); - m_Stream.Write( (int) to ); - m_Stream.Write( (short) itemID ); - m_Stream.Write( (short) fromPoint.m_X ); - m_Stream.Write( (short) fromPoint.m_Y ); - m_Stream.Write( (sbyte) fromPoint.m_Z ); - m_Stream.Write( (short) toPoint.m_X ); - m_Stream.Write( (short) toPoint.m_Y ); - m_Stream.Write( (sbyte) toPoint.m_Z ); - m_Stream.Write( (byte) speed ); - m_Stream.Write( (byte) duration ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (bool) fixedDirection ); - m_Stream.Write( (bool) explode ); - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) renderMode ); - m_Stream.Write( (short) effect ); - m_Stream.Write( (short) explodeEffect ); - m_Stream.Write( (short) explodeSound ); - m_Stream.Write( (int) serial ); - m_Stream.Write( (byte) layer ); - m_Stream.Write( (short) unknown ); - } - - public ParticleEffect( EffectType type, Serial from, Serial to, int itemID, IPoint3D fromPoint, IPoint3D toPoint, int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, Serial serial, int layer, int unknown ) : base( 0xC7, 49 ) - { - m_Stream.Write( (byte) type ); - m_Stream.Write( (int) from ); - m_Stream.Write( (int) to ); - m_Stream.Write( (short) itemID ); - m_Stream.Write( (short) fromPoint.X ); - m_Stream.Write( (short) fromPoint.Y ); - m_Stream.Write( (sbyte) fromPoint.Z ); - m_Stream.Write( (short) toPoint.X ); - m_Stream.Write( (short) toPoint.Y ); - m_Stream.Write( (sbyte) toPoint.Z ); - m_Stream.Write( (byte) speed ); - m_Stream.Write( (byte) duration ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (bool) fixedDirection ); - m_Stream.Write( (bool) explode ); - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) renderMode ); - m_Stream.Write( (short) effect ); - m_Stream.Write( (short) explodeEffect ); - m_Stream.Write( (short) explodeSound ); - m_Stream.Write( (int) serial ); - m_Stream.Write( (byte) layer ); - m_Stream.Write( (short) unknown ); - } - } - - public class HuedEffect : Packet - { - public HuedEffect( EffectType type, Serial from, Serial to, int itemID, Point3D fromPoint, Point3D toPoint, int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode ) : base( 0xC0, 36 ) - { - m_Stream.Write( (byte) type ); - m_Stream.Write( (int) from ); - m_Stream.Write( (int) to ); - m_Stream.Write( (short) itemID ); - m_Stream.Write( (short) fromPoint.m_X ); - m_Stream.Write( (short) fromPoint.m_Y ); - m_Stream.Write( (sbyte) fromPoint.m_Z ); - m_Stream.Write( (short) toPoint.m_X ); - m_Stream.Write( (short) toPoint.m_Y ); - m_Stream.Write( (sbyte) toPoint.m_Z ); - m_Stream.Write( (byte) speed ); - m_Stream.Write( (byte) duration ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (bool) fixedDirection ); - m_Stream.Write( (bool) explode ); - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) renderMode ); - } - - public HuedEffect( EffectType type, Serial from, Serial to, int itemID, IPoint3D fromPoint, IPoint3D toPoint, int speed, int duration, bool fixedDirection, bool explode, int hue, int renderMode ) : base( 0xC0, 36 ) - { - m_Stream.Write( (byte) type ); - m_Stream.Write( (int) from ); - m_Stream.Write( (int) to ); - m_Stream.Write( (short) itemID ); - m_Stream.Write( (short) fromPoint.X ); - m_Stream.Write( (short) fromPoint.Y ); - m_Stream.Write( (sbyte) fromPoint.Z ); - m_Stream.Write( (short) toPoint.X ); - m_Stream.Write( (short) toPoint.Y ); - m_Stream.Write( (sbyte) toPoint.Z ); - m_Stream.Write( (byte) speed ); - m_Stream.Write( (byte) duration ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (bool) fixedDirection ); - m_Stream.Write( (bool) explode ); - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) renderMode ); - } - } - - public sealed class TargetParticleEffect : ParticleEffect - { - public TargetParticleEffect( IEntity e, int itemID, int speed, int duration, int hue, int renderMode, int effect, int layer, int unknown ) : base( EffectType.FixedFrom, e.Serial, Serial.Zero, itemID, e.Location, e.Location, speed, duration, true, false, hue, renderMode, effect, 1, 0, e.Serial, layer, unknown ) - { - } - } - - public sealed class TargetEffect : HuedEffect - { - public TargetEffect( IEntity e, int itemID, int speed, int duration, int hue, int renderMode ) : base( EffectType.FixedFrom, e.Serial, Serial.Zero, itemID, e.Location, e.Location, speed, duration, true, false, hue, renderMode ) - { - } - } - - public sealed class LocationParticleEffect : ParticleEffect - { - public LocationParticleEffect( IEntity e, int itemID, int speed, int duration, int hue, int renderMode, int effect, int unknown ) : base( EffectType.FixedXYZ, e.Serial, Serial.Zero, itemID, e.Location, e.Location, speed, duration, true, false, hue, renderMode, effect, 1, 0, e.Serial, 255, unknown ) - { - } - } - - public sealed class LocationEffect : HuedEffect - { - public LocationEffect( IPoint3D p, int itemID, int speed, int duration, int hue, int renderMode ) : base( EffectType.FixedXYZ, Serial.Zero, Serial.Zero, itemID, p, p, speed, duration, true, false, hue, renderMode ) - { - } - } - - public sealed class MovingParticleEffect : ParticleEffect - { - public MovingParticleEffect( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode, int effect, int explodeEffect, int explodeSound, EffectLayer layer, int unknown ) : base( EffectType.Moving, from.Serial, to.Serial, itemID, from.Location, to.Location, speed, duration, fixedDirection, explodes, hue, renderMode, effect, explodeEffect, explodeSound, Serial.Zero, (int)layer, unknown ) - { - } - } - - public sealed class MovingEffect : HuedEffect - { - public MovingEffect( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool explodes, int hue, int renderMode ) : base( EffectType.Moving, from.Serial, to.Serial, itemID, from.Location, to.Location, speed, duration, fixedDirection, explodes, hue, renderMode ) - { - } - } - - public enum ScreenEffectType - { - FadeOut = 0x00, - FadeIn = 0x01, - LightFlash = 0x02, - FadeInOut = 0x03, - DarkFlash = 0x04 - } - - public class ScreenEffect : Packet - { - public ScreenEffect( ScreenEffectType type ) - : base( 0x70, 28 ) - { - m_Stream.Write( (byte)0x04 ); - m_Stream.Fill( 8 ); - m_Stream.Write( (short)type ); - m_Stream.Fill( 16 ); - } - } - - public sealed class ScreenFadeOut : ScreenEffect - { - public static readonly Packet Instance = SetStatic( new ScreenFadeOut() ); - - public ScreenFadeOut() - : base( ScreenEffectType.FadeOut ) - { - } - } - - public sealed class ScreenFadeIn : ScreenEffect - { - public static readonly Packet Instance = SetStatic( new ScreenFadeIn() ); - - public ScreenFadeIn() - : base( ScreenEffectType.FadeIn ) - { - } - } - - public sealed class ScreenFadeInOut : ScreenEffect - { - public static readonly Packet Instance = SetStatic( new ScreenFadeInOut() ); - - public ScreenFadeInOut() - : base( ScreenEffectType.FadeInOut ) - { - } - } - - public sealed class ScreenLightFlash : ScreenEffect - { - public static readonly Packet Instance = SetStatic( new ScreenLightFlash() ); - - public ScreenLightFlash() - : base( ScreenEffectType.LightFlash ) - { - } - } - - public sealed class ScreenDarkFlash : ScreenEffect - { - public static readonly Packet Instance = SetStatic( new ScreenDarkFlash() ); - - public ScreenDarkFlash() - : base( ScreenEffectType.DarkFlash ) - { - } - } - - public enum DeleteResultType - { - PasswordInvalid, - CharNotExist, - CharBeingPlayed, - CharTooYoung, - CharQueued, - BadRequest - } - - public sealed class DeleteResult : Packet - { - public DeleteResult( DeleteResultType res ) : base( 0x85, 2 ) - { - m_Stream.Write( (byte) res ); - } - } - - /*public sealed class MovingEffect : Packet - { - public MovingEffect( IEntity from, IEntity to, int itemID, int speed, int duration, bool fixedDirection, bool turn, int hue, int renderMode ) : base( 0xC0, 36 ) - { - m_Stream.Write( (byte) 0x00 ); - m_Stream.Write( (int) from.Serial ); - m_Stream.Write( (int) to.Serial ); - m_Stream.Write( (short) itemID ); - m_Stream.Write( (short) from.Location.m_X ); - m_Stream.Write( (short) from.Location.m_Y ); - m_Stream.Write( (sbyte) from.Location.m_Z ); - m_Stream.Write( (short) to.Location.m_X ); - m_Stream.Write( (short) to.Location.m_Y ); - m_Stream.Write( (sbyte) to.Location.m_Z ); - m_Stream.Write( (byte) speed ); - m_Stream.Write( (byte) duration ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (bool) fixedDirection ); - m_Stream.Write( (bool) turn ); - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) renderMode ); - } - }*/ - - /*public sealed class LocationEffect : Packet - { - public LocationEffect( IPoint3D p, int itemID, int duration, int hue, int renderMode ) : base( 0xC0, 36 ) - { - m_Stream.Write( (byte) 0x02 ); - m_Stream.Write( (int) Serial.Zero ); - m_Stream.Write( (int) Serial.Zero ); - m_Stream.Write( (short) itemID ); - m_Stream.Write( (short) p.X ); - m_Stream.Write( (short) p.Y ); - m_Stream.Write( (sbyte) p.Z ); - m_Stream.Write( (short) p.X ); - m_Stream.Write( (short) p.Y ); - m_Stream.Write( (sbyte) p.Z ); - m_Stream.Write( (byte) 10 ); - m_Stream.Write( (byte) duration ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 1 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) renderMode ); - } - }*/ - - public sealed class BoltEffect : Packet - { - public BoltEffect( IEntity target, int hue ) : base( 0xC0, 36 ) - { - m_Stream.Write( (byte) 0x01 ); // type - m_Stream.Write( (int) target.Serial ); - m_Stream.Write( (int) Serial.Zero ); - m_Stream.Write( (short) 0 ); // itemID - m_Stream.Write( (short) target.X ); - m_Stream.Write( (short) target.Y ); - m_Stream.Write( (sbyte) target.Z ); - m_Stream.Write( (short) target.X ); - m_Stream.Write( (short) target.Y ); - m_Stream.Write( (sbyte) target.Z ); - m_Stream.Write( (byte) 0 ); // speed - m_Stream.Write( (byte) 0 ); // duration - m_Stream.Write( (short) 0 ); // unk - m_Stream.Write( false ); // fixed direction - m_Stream.Write( false ); // explode - m_Stream.Write( (int) hue ); - m_Stream.Write( (int) 0 ); // render mode - } - } - - public sealed class DisplaySpellbook : Packet - { - public DisplaySpellbook( Item book ) : base( 0x24, 7 ) - { - m_Stream.Write( (int) book.Serial ); - m_Stream.Write( (short) -1 ); - } - } - - public sealed class DisplaySpellbookHS : Packet - { - public DisplaySpellbookHS( Item book ) : base( 0x24, 9 ) - { - m_Stream.Write( (int) book.Serial ); - m_Stream.Write( (short) -1 ); - m_Stream.Write( (short) 0x7D ); - } - } - - public sealed class NewSpellbookContent : Packet - { - public NewSpellbookContent( Item item, int graphic, int offset, ulong content ) : base( 0xBF ) - { - EnsureCapacity( 23 ); - - m_Stream.Write( (short) 0x1B ); - m_Stream.Write( (short) 0x01 ); - - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (short) graphic ); - m_Stream.Write( (short) offset ); - - for ( int i = 0; i < 8; ++i ) - m_Stream.Write( (byte)(content >> (i * 8)) ); - } - } - - public sealed class SpellbookContent : Packet - { - public SpellbookContent( int count, int offset, ulong content, Item item ) : base( 0x3C ) - { - EnsureCapacity( 5 + (count * 19) ); - - int written = 0; - - m_Stream.Write( (ushort) 0 ); - - ulong mask = 1; - - for ( int i = 0; i < 64; ++i, mask <<= 1 ) - { - if ( (content & mask) != 0 ) - { - m_Stream.Write( (int) (0x7FFFFFFF - i) ); - m_Stream.Write( (ushort) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (ushort) (i + offset) ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (short) 0 ); - - ++written; - } - } - - m_Stream.Seek( 3, SeekOrigin.Begin ); - m_Stream.Write( (ushort) written ); - } - } - - public sealed class SpellbookContent6017 : Packet - { - public SpellbookContent6017( int count, int offset, ulong content, Item item ) : base( 0x3C ) - { - EnsureCapacity( 5 + (count * 20) ); - - int written = 0; - - m_Stream.Write( (ushort) 0 ); - - ulong mask = 1; - - for ( int i = 0; i < 64; ++i, mask <<= 1 ) - { - if ( (content & mask) != 0 ) - { - m_Stream.Write( (int) (0x7FFFFFFF - i) ); - m_Stream.Write( (ushort) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (ushort) (i + offset) ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (byte) 0 ); // Grid Location? - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (short) 0 ); - - ++written; - } - } - - m_Stream.Seek( 3, SeekOrigin.Begin ); - m_Stream.Write( (ushort) written ); - } - } - - public sealed class ContainerDisplay : Packet - { - public ContainerDisplay( Container c ) : base( 0x24, 7 ) - { - m_Stream.Write( (int) c.Serial ); - m_Stream.Write( (short) c.GumpID ); - } - } - - public sealed class ContainerDisplayHS : Packet - { - public ContainerDisplayHS( Container c ) : base( 0x24, 9 ) - { - m_Stream.Write( (int) c.Serial ); - m_Stream.Write( (short) c.GumpID ); - m_Stream.Write( (short) 0x7D ); - } - } - - public sealed class ContainerContentUpdate : Packet - { - public ContainerContentUpdate( Item item ) : base( 0x25, 20 ) - { - Serial parentSerial; - - if ( item.Parent is Item parentItem ) - { - parentSerial = parentItem.Serial; - } - else - { - Console.WriteLine( "Warning: ContainerContentUpdate on item with !(parent is Item)" ); - parentSerial = Serial.Zero; - } - - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (ushort) item.ItemID ); - m_Stream.Write( (byte) 0 ); // signed, itemID offset - m_Stream.Write( (ushort) item.Amount ); - m_Stream.Write( (short) item.X ); - m_Stream.Write( (short) item.Y ); - m_Stream.Write( (int) parentSerial ); - m_Stream.Write( (ushort) ( item.QuestItem ? Item.QuestItemHue : item.Hue ) ); - } - } - - public sealed class ContainerContentUpdate6017 : Packet - { - public ContainerContentUpdate6017( Item item ) : base( 0x25, 21 ) - { - Serial parentSerial; - - if ( item.Parent is Item parentItem ) - { - parentSerial = parentItem.Serial; - } - else - { - Console.WriteLine( "Warning: ContainerContentUpdate on item with !(parent is Item)" ); - parentSerial = Serial.Zero; - } - - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (ushort) item.ItemID ); - m_Stream.Write( (byte) 0 ); // signed, itemID offset - m_Stream.Write( (ushort) item.Amount ); - m_Stream.Write( (short) item.X ); - m_Stream.Write( (short) item.Y ); - m_Stream.Write( (byte) 0 ); // Grid Location? - m_Stream.Write( (int) parentSerial ); - m_Stream.Write( (ushort) ( item.QuestItem ? Item.QuestItemHue : item.Hue ) ); - } - } - - public sealed class ContainerContent : Packet - { - public ContainerContent( Mobile beholder, Item beheld ) : base( 0x3C ) - { - List items = beheld.Items; - int count = items.Count; - - EnsureCapacity( 5 + (count * 19) ); - - long pos = m_Stream.Position; - - int written = 0; - - m_Stream.Write( (ushort) 0 ); - - for ( int i = 0; i < count; ++i ) - { - Item child = items[i]; - - if ( !child.Deleted && beholder.CanSee( child ) ) - { - Point3D loc = child.Location; - - m_Stream.Write( (int) child.Serial ); - m_Stream.Write( (ushort) child.ItemID ); - m_Stream.Write( (byte) 0 ); // signed, itemID offset - m_Stream.Write( (ushort) child.Amount ); - m_Stream.Write( (short) loc.m_X ); - m_Stream.Write( (short) loc.m_Y ); - m_Stream.Write( (int) beheld.Serial ); - m_Stream.Write( (ushort) ( child.QuestItem ? Item.QuestItemHue : child.Hue ) ); - - ++written; - } - } - - m_Stream.Seek( pos, SeekOrigin.Begin ); - m_Stream.Write( (ushort) written ); - } - } - - public sealed class ContainerContent6017 : Packet - { - public ContainerContent6017( Mobile beholder, Item beheld ) : base( 0x3C ) - { - List items = beheld.Items; - int count = items.Count; - - EnsureCapacity( 5 + (count * 20) ); - - long pos = m_Stream.Position; - - int written = 0; - - m_Stream.Write( (ushort) 0 ); - - for ( int i = 0; i < count; ++i ) - { - Item child = items[i]; - - if ( !child.Deleted && beholder.CanSee( child ) ) - { - Point3D loc = child.Location; - - m_Stream.Write( (int) child.Serial ); - m_Stream.Write( (ushort) child.ItemID ); - m_Stream.Write( (byte) 0 ); // signed, itemID offset - m_Stream.Write( (ushort) child.Amount ); - m_Stream.Write( (short) loc.m_X ); - m_Stream.Write( (short) loc.m_Y ); - m_Stream.Write( (byte) 0 ); // Grid Location? - m_Stream.Write( (int) beheld.Serial ); - m_Stream.Write( (ushort) ( child.QuestItem ? Item.QuestItemHue : child.Hue ) ); - - ++written; - } - } - - m_Stream.Seek( pos, SeekOrigin.Begin ); - m_Stream.Write( (ushort) written ); - } - } - - public sealed class SetWarMode : Packet - { - public static readonly Packet InWarMode = SetStatic( new SetWarMode( true ) ); - public static readonly Packet InPeaceMode = SetStatic( new SetWarMode( false ) ); - - public static Packet Instantiate( bool mode ) - { - return ( mode ? InWarMode : InPeaceMode ); - } - - public SetWarMode( bool mode ) : base( 0x72, 5 ) - { - m_Stream.Write( mode ); - m_Stream.Write( (byte) 0x00 ); - m_Stream.Write( (byte) 0x32 ); - m_Stream.Write( (byte) 0x00 ); - //m_Stream.Fill(); - } - } - - public sealed class Swing : Packet - { - public Swing( int flag, Mobile attacker, Mobile defender ) : base( 0x2F, 10 ) - { - m_Stream.Write( (byte) flag ); - m_Stream.Write( (int) attacker.Serial ); - m_Stream.Write( (int) defender.Serial ); - } - } - - public sealed class NullFastwalkStack : Packet - { - public NullFastwalkStack() : base( 0xBF ) - { - EnsureCapacity(256); - m_Stream.Write( (short) 0x1 ); - m_Stream.Write( (int) 0x0 ); - m_Stream.Write( (int) 0x0 ); - m_Stream.Write( (int) 0x0 ); - m_Stream.Write( (int) 0x0 ); - m_Stream.Write( (int) 0x0 ); - m_Stream.Write( (int) 0x0 ); - } - } - - public sealed class RemoveItem : Packet - { - public RemoveItem( Item item ) : base( 0x1D, 5 ) - { - m_Stream.Write( (int) item.Serial ); - } - } - - public sealed class RemoveMobile : Packet - { - public RemoveMobile( Mobile m ) : base( 0x1D, 5 ) - { - m_Stream.Write( (int) m.Serial ); - } - } - - public sealed class ServerChange : Packet - { - public ServerChange( Mobile m, Map map ) : base( 0x76, 16 ) - { - m_Stream.Write( (short) m.X ); - m_Stream.Write( (short) m.Y ); - m_Stream.Write( (short) m.Z ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) map.Width ); - m_Stream.Write( (short) map.Height ); - } - } - - public sealed class SkillUpdate : Packet - { - public SkillUpdate( Skills skills ) : base( 0x3A ) - { - EnsureCapacity( 6 + (skills.Length * 9) ); - - m_Stream.Write( (byte) 0x02 ); // type: absolute, capped - - for ( int i = 0; i < skills.Length; ++i ) - { - Skill s = skills[i]; - - double v = s.NonRacialValue; - int uv = (int)(v * 10); - - if ( uv < 0 ) - uv = 0; - else if ( uv >= 0x10000 ) - uv = 0xFFFF; - - m_Stream.Write( (ushort) (s.Info.SkillID + 1) ); - m_Stream.Write( (ushort) uv ); - m_Stream.Write( (ushort) s.BaseFixedPoint ); - m_Stream.Write( (byte) s.Lock ); - m_Stream.Write( (ushort) s.CapFixedPoint ); - } - - m_Stream.Write( (short) 0 ); // terminate - } - } - - public sealed class Sequence : Packet - { - public Sequence( int num ) : base( 0x7B, 2 ) - { - m_Stream.Write( (byte)num ); - } - } - - public sealed class SkillChange : Packet - { - public SkillChange( Skill skill ) : base( 0x3A ) - { - EnsureCapacity( 13 ); - - double v = skill.NonRacialValue; - int uv = (int)(v * 10); - - if ( uv < 0 ) - uv = 0; - else if ( uv >= 0x10000 ) - uv = 0xFFFF; - - m_Stream.Write( (byte) 0xDF ); // type: delta, capped - m_Stream.Write( (ushort) skill.Info.SkillID ); - m_Stream.Write( (ushort) uv ); - m_Stream.Write( (ushort) skill.BaseFixedPoint ); - m_Stream.Write( (byte) skill.Lock ); - m_Stream.Write( (ushort) skill.CapFixedPoint ); - - /*m_Stream.Write( (short) skill.Info.SkillID ); - m_Stream.Write( (short) (skill.Value * 10.0) ); - m_Stream.Write( (short) (skill.Base * 10.0) ); - m_Stream.Write( (byte) skill.Lock ); - m_Stream.Write( (short) skill.CapFixedPoint );*/ - } - } - - public sealed class LaunchBrowser : Packet - { - public LaunchBrowser( string url ) : base( 0xA5 ) - { - if ( url == null ) url = ""; - - EnsureCapacity( 4 + url.Length ); - - m_Stream.WriteAsciiNull( url ); - } - } - - public sealed class MessageLocalized : Packet - { - private static MessageLocalized[] m_Cache_IntLoc = new MessageLocalized[15000]; - private static MessageLocalized[] m_Cache_CliLoc = new MessageLocalized[100000]; - private static MessageLocalized[] m_Cache_CliLocCmp = new MessageLocalized[5000]; - - public static MessageLocalized InstantiateGeneric( int number ) - { - MessageLocalized[] cache = null; - int index = 0; - - if ( number >= 3000000 ) - { - cache = m_Cache_IntLoc; - index = number - 3000000; - } - else if ( number >= 1000000 ) - { - cache = m_Cache_CliLoc; - index = number - 1000000; - } - else if ( number >= 500000 ) - { - cache = m_Cache_CliLocCmp; - index = number - 500000; - } - - MessageLocalized p; - - if ( cache != null && index >= 0 && index < cache.Length ) - { - p = cache[index]; - - if ( p == null ) - { - cache[index] = p = new MessageLocalized( Serial.MinusOne, -1, MessageType.Regular, 0x3B2, 3, number, "System", "" ); - p.SetStatic(); - } - } - else - { - p = new MessageLocalized( Serial.MinusOne, -1, MessageType.Regular, 0x3B2, 3, number, "System", "" ); - } - - return p; - } - - public MessageLocalized( Serial serial, int graphic, MessageType type, int hue, int font, int number, string name, string args ) : base( 0xC1 ) - { - if ( name == null ) name = ""; - if ( args == null ) args = ""; - - if ( hue == 0 ) - hue = 0x3B2; - - EnsureCapacity( 50 + (args.Length * 2) ); - - m_Stream.Write( (int) serial ); - m_Stream.Write( (short) graphic ); - m_Stream.Write( (byte) type ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (short) font ); - m_Stream.Write( (int) number ); - m_Stream.WriteAsciiFixed( name, 30 ); - m_Stream.WriteLittleUniNull( args ); - } - } - - public sealed class MobileMoving : Packet - { - public MobileMoving( Mobile m, int noto ) : base( 0x77, 17 ) - { - Point3D loc = m.Location; - - int hue = m.Hue; - - if ( m.SolidHueOverride >= 0 ) - hue = m.SolidHueOverride; - - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.Body ); - m_Stream.Write( (short) loc.m_X ); - m_Stream.Write( (short) loc.m_Y ); - m_Stream.Write( (sbyte) loc.m_Z ); - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (byte) m.GetPacketFlags() ); - m_Stream.Write( (byte) noto ); - } - } - - // Pre-7.0.0.0 Mobile Moving - public sealed class MobileMovingOld : Packet - { - public MobileMovingOld( Mobile m, int noto ) : base( 0x77, 17 ) - { - Point3D loc = m.Location; - - int hue = m.Hue; - - if ( m.SolidHueOverride >= 0 ) - hue = m.SolidHueOverride; - - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.Body ); - m_Stream.Write( (short) loc.m_X ); - m_Stream.Write( (short) loc.m_Y ); - m_Stream.Write( (sbyte) loc.m_Z ); - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (byte) m.GetOldPacketFlags() ); - m_Stream.Write( (byte) noto ); - } - } - - public sealed class MultiTargetReqHS : Packet - { - public MultiTargetReqHS( MultiTarget t ) : base( 0x99, 30 ) - { - m_Stream.Write( (bool) t.AllowGround ); - m_Stream.Write( (int) t.TargetID ); - m_Stream.Write( (byte) t.Flags ); - - m_Stream.Fill(); - - m_Stream.Seek( 18, SeekOrigin.Begin ); - m_Stream.Write( (short) t.MultiID ); - m_Stream.Write( (short) t.Offset.X ); - m_Stream.Write( (short) t.Offset.Y ); - m_Stream.Write( (short) t.Offset.Z ); - - // DWORD Hue - } - } - - public sealed class MultiTargetReq : Packet - { - public MultiTargetReq( MultiTarget t ) : base( 0x99, 26 ) - { - m_Stream.Write( (bool) t.AllowGround ); - m_Stream.Write( (int) t.TargetID ); - m_Stream.Write( (byte) t.Flags ); - - m_Stream.Fill(); - - m_Stream.Seek( 18, SeekOrigin.Begin ); - m_Stream.Write( (short) t.MultiID ); - m_Stream.Write( (short) t.Offset.X ); - m_Stream.Write( (short) t.Offset.Y ); - m_Stream.Write( (short) t.Offset.Z ); - } - } - - public sealed class CancelTarget : Packet - { - public static readonly Packet Instance = SetStatic( new CancelTarget() ); - - public CancelTarget() : base( 0x6C, 19 ) - { - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (int) 0 ); - m_Stream.Write( (byte) 3 ); - m_Stream.Fill(); - } - } - - public sealed class TargetReq : Packet - { - public TargetReq( Target t ) : base( 0x6C, 19 ) - { - m_Stream.Write( (bool) t.AllowGround ); - m_Stream.Write( (int) t.TargetID ); - m_Stream.Write( (byte) t.Flags ); - m_Stream.Fill(); - } - } - - public sealed class DragEffect : Packet - { - public DragEffect( IEntity src, IEntity trg, int itemID, int hue, int amount ) : base( 0x23, 26 ) - { - m_Stream.Write( (short) itemID ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (short) amount ); - m_Stream.Write( (int) src.Serial ); - m_Stream.Write( (short) src.X ); - m_Stream.Write( (short) src.Y ); - m_Stream.Write( (sbyte) src.Z ); - m_Stream.Write( (int) trg.Serial ); - m_Stream.Write( (short) trg.X ); - m_Stream.Write( (short) trg.Y ); - m_Stream.Write( (sbyte) trg.Z ); - } - } - - public interface IGumpWriter - { - int TextEntries { get; set; } - int Switches { get; set; } - - void AppendLayout( bool val ); - void AppendLayout( int val ); - void AppendLayoutNS( int val ); - void AppendLayout( string text ); - void AppendLayout( byte[] buffer ); - void WriteStrings( List strings ); - void Flush(); - } - - public sealed class DisplayGumpPacked : Packet, IGumpWriter - { - public int TextEntries { get; set; } - - public int Switches { get; set; } - - private Gump m_Gump; - - private PacketWriter m_Layout; - private PacketWriter m_Strings; - - private int m_StringCount; - - public DisplayGumpPacked( Gump gump ) - : base( 0xDD ) - { - m_Gump = gump; - - m_Layout = PacketWriter.CreateInstance( 8192 ); - m_Strings = PacketWriter.CreateInstance( 8192 ); - } - - private static byte[] m_True = Gump.StringToBuffer( " 1" ); - private static byte[] m_False = Gump.StringToBuffer( " 0" ); - - private static byte[] m_BeginTextSeparator = Gump.StringToBuffer( " @" ); - private static byte[] m_EndTextSeparator = Gump.StringToBuffer( "@" ); - - private static byte[] m_Buffer = new byte[48]; - - static DisplayGumpPacked() - { - m_Buffer[0] = (byte)' '; - } - - public void AppendLayout( bool val ) - { - AppendLayout( val ? m_True : m_False ); - } - - public void AppendLayout( int val ) - { - string toString = val.ToString(); - int bytes = System.Text.Encoding.ASCII.GetBytes( toString, 0, toString.Length, m_Buffer, 1 ) + 1; - - m_Layout.Write( m_Buffer, 0, bytes ); - } - - public void AppendLayoutNS( int val ) - { - string toString = val.ToString(); - int bytes = System.Text.Encoding.ASCII.GetBytes( toString, 0, toString.Length, m_Buffer, 1 ); - - m_Layout.Write( m_Buffer, 1, bytes ); - } - - public void AppendLayout( string text ) - { - AppendLayout( m_BeginTextSeparator ); - - m_Layout.WriteAsciiFixed( text, text.Length ); - - AppendLayout( m_EndTextSeparator ); - } + wantLength += 4095; + wantLength &= ~4095; - public void AppendLayout( byte[] buffer ) - { - m_Layout.Write( buffer, 0, buffer.Length ); - } + byte[] m_PackBuffer; + lock (m_PackBuffers) + { + m_PackBuffer = m_PackBuffers.AcquireBuffer(); + } - public void WriteStrings( List strings ) - { - m_StringCount = strings.Count; + if (m_PackBuffer.Length < wantLength) + { + Console.WriteLine("Notice: DisplayGumpPacked creating new {0} byte buffer", wantLength); + m_PackBuffer = new byte[wantLength]; + } - for ( int i = 0; i < strings.Count; ++i ) - { - string v = strings[i]; + int packLength = m_PackBuffer.Length; - if ( v == null ) - v = string.Empty; + Compression.Pack(m_PackBuffer, ref packLength, buffer, length, ZLibQuality.Default); - m_Strings.Write( (ushort) v.Length ); - m_Strings.WriteBigUniFixed( v, v.Length ); - } - } + m_Stream.Write(4 + packLength); + m_Stream.Write(length); + m_Stream.Write(m_PackBuffer, 0, packLength); - public void Flush() - { - EnsureCapacity( 28 + (int) m_Layout.Length + (int) m_Strings.Length ); + lock (m_PackBuffers) + { + m_PackBuffers.ReleaseBuffer(m_PackBuffer); + } + } + } - m_Stream.Write( (int) m_Gump.Serial ); - m_Stream.Write( (int) m_Gump.TypeID ); - m_Stream.Write( (int) m_Gump.X ); - m_Stream.Write( (int) m_Gump.Y ); + public sealed class DisplayGumpFast : Packet, IGumpWriter + { + private static byte[] m_True = Gump.StringToBuffer(" 1"); + private static byte[] m_False = Gump.StringToBuffer(" 0"); - // Note: layout MUST be null terminated (don't listen to krrios) - m_Layout.Write( (byte) 0 ); - WritePacked( m_Layout ); + private static byte[] m_BeginTextSeparator = Gump.StringToBuffer(" @"); + private static byte[] m_EndTextSeparator = Gump.StringToBuffer("@"); - m_Stream.Write( (int) m_StringCount ); + private byte[] m_Buffer = new byte[48]; + private int m_LayoutLength; - WritePacked( m_Strings ); + public DisplayGumpFast(Gump g) : base(0xB0) + { + m_Buffer[0] = (byte)' '; - PacketWriter.ReleaseInstance( m_Layout ); - PacketWriter.ReleaseInstance( m_Strings ); - } + EnsureCapacity(4096); - private const int GumpBufferSize = 0x5000; - private static BufferPool m_PackBuffers = new BufferPool("Gump", 4, GumpBufferSize); + m_Stream.Write(g.Serial); + m_Stream.Write(g.TypeID); + m_Stream.Write(g.X); + m_Stream.Write(g.Y); + m_Stream.Write((ushort)0xFFFF); + } - private void WritePacked( PacketWriter src ) - { - byte[] buffer = src.UnderlyingStream.GetBuffer(); - int length = (int) src.Length; + public int TextEntries{ get; set; } - if ( length == 0 ) - { - m_Stream.Write( (int) 0 ); - return; - } + public int Switches{ get; set; } - int wantLength = 1 + ( ( buffer.Length * 1024 ) / 1000 ); + public void AppendLayout(bool val) + { + AppendLayout(val ? m_True : m_False); + } - wantLength += 4095; - wantLength &= ~4095; + public void AppendLayout(int val) + { + string toString = val.ToString(); + int bytes = Encoding.ASCII.GetBytes(toString, 0, toString.Length, m_Buffer, 1) + 1; - byte[] m_PackBuffer; - lock (m_PackBuffers) - m_PackBuffer = m_PackBuffers.AcquireBuffer(); + m_Stream.Write(m_Buffer, 0, bytes); + m_LayoutLength += bytes; + } - if (m_PackBuffer.Length < wantLength) - { - Console.WriteLine("Notice: DisplayGumpPacked creating new {0} byte buffer", wantLength); - m_PackBuffer = new byte[wantLength]; - } + public void AppendLayoutNS(int val) + { + string toString = val.ToString(); + int bytes = Encoding.ASCII.GetBytes(toString, 0, toString.Length, m_Buffer, 1); - int packLength = m_PackBuffer.Length; + m_Stream.Write(m_Buffer, 1, bytes); + m_LayoutLength += bytes; + } + + public void AppendLayout(string text) + { + AppendLayout(m_BeginTextSeparator); + + int length = text.Length; + m_Stream.WriteAsciiFixed(text, length); + m_LayoutLength += length; + + AppendLayout(m_EndTextSeparator); + } + + public void AppendLayout(byte[] buffer) + { + int length = buffer.Length; + m_Stream.Write(buffer, 0, length); + m_LayoutLength += length; + } + + public void WriteStrings(List text) + { + m_Stream.Seek(19, SeekOrigin.Begin); + m_Stream.Write((ushort)m_LayoutLength); + m_Stream.Seek(0, SeekOrigin.End); + + m_Stream.Write((ushort)text.Count); + + for (int i = 0; i < text.Count; ++i) + { + string v = text[i]; + + if (v == null) + v = string.Empty; + + int length = (ushort)v.Length; + + m_Stream.Write((ushort)length); + m_Stream.WriteBigUniFixed(v, length); + } + } + + public void Flush() + { + } + } + + public sealed class DisplayGump : Packet + { + public DisplayGump(Gump g, string layout, string[] text) : base(0xB0) + { + if (layout == null) layout = ""; + + EnsureCapacity(256); + + m_Stream.Write(g.Serial); + m_Stream.Write(g.TypeID); + m_Stream.Write(g.X); + m_Stream.Write(g.Y); + m_Stream.Write((ushort)(layout.Length + 1)); + m_Stream.WriteAsciiNull(layout); + + m_Stream.Write((ushort)text.Length); + + for (int i = 0; i < text.Length; ++i) + { + string v = text[i]; + + if (v == null) v = ""; + + int length = (ushort)v.Length; + + m_Stream.Write((ushort)length); + m_Stream.WriteBigUniFixed(v, length); + } + } + } + + public sealed class DisplayPaperdoll : Packet + { + public DisplayPaperdoll(Mobile m, string text, bool canLift) : base(0x88, 66) + { + byte flags = 0x00; + + if (m.Warmode) + flags |= 0x01; + + if (canLift) + flags |= 0x02; + + m_Stream.Write(m.Serial); + m_Stream.WriteAsciiFixed(text, 60); + m_Stream.Write(flags); + } + } + + public sealed class PopupMessage : Packet + { + public PopupMessage(PMMessage msg) : base(0x53, 2) + { + m_Stream.Write((byte)msg); + } + } + + public sealed class PlaySound : Packet + { + public PlaySound(int soundID, IPoint3D target) : base(0x54, 12) + { + m_Stream.Write((byte)1); // flags + m_Stream.Write((short)soundID); + m_Stream.Write((short)0); // volume + m_Stream.Write((short)target.X); + m_Stream.Write((short)target.Y); + m_Stream.Write((short)target.Z); + } + } + + public sealed class PlayMusic : Packet + { + public static readonly Packet InvalidInstance = SetStatic(new PlayMusic(MusicName.Invalid)); + + private static Packet[] m_Instances = new Packet[60]; + + public PlayMusic(MusicName name) : base(0x6D, 3) + { + m_Stream.Write((short)name); + } + + public static Packet GetInstance(MusicName name) + { + if (name == MusicName.Invalid) + return InvalidInstance; + + int v = (int)name; + Packet p; + + if (v >= 0 && v < m_Instances.Length) + { + p = m_Instances[v]; + + if (p == null) + m_Instances[v] = p = SetStatic(new PlayMusic(name)); + } + else + { + p = new PlayMusic(name); + } + + return p; + } + } + + public sealed class ScrollMessage : Packet + { + public ScrollMessage(int type, int tip, string text) : base(0xA6) + { + if (text == null) text = ""; + + EnsureCapacity(10 + text.Length); + + m_Stream.Write((byte)type); + m_Stream.Write(tip); + m_Stream.Write((ushort)text.Length); + m_Stream.WriteAsciiFixed(text, text.Length); + } + } + + public sealed class CurrentTime : Packet + { + public CurrentTime() : base(0x5B, 4) + { + DateTime now = DateTime.UtcNow; + + m_Stream.Write((byte)now.Hour); + m_Stream.Write((byte)now.Minute); + m_Stream.Write((byte)now.Second); + } + } + + public sealed class MapChange : Packet + { + public MapChange(Mobile m) : base(0xBF) + { + EnsureCapacity(6); + + m_Stream.Write((short)0x08); + m_Stream.Write((byte)(m.Map?.MapID ?? 0)); + } + } + + public sealed class SeasonChange : Packet + { + private static SeasonChange[][] m_Cache = new SeasonChange[5][] + { + new SeasonChange[2], + new SeasonChange[2], + new SeasonChange[2], + new SeasonChange[2], + new SeasonChange[2] + }; + + public SeasonChange(int season) : this(season, true) + { + } + + public SeasonChange(int season, bool playSound) : base(0xBC, 3) + { + m_Stream.Write((byte)season); + m_Stream.Write(playSound); + } + + public static SeasonChange Instantiate(int season) + { + return Instantiate(season, true); + } + + public static SeasonChange Instantiate(int season, bool playSound) + { + if (season >= 0 && season < m_Cache.Length) + { + int idx = playSound ? 1 : 0; + + SeasonChange p = m_Cache[season][idx]; + + if (p == null) + { + m_Cache[season][idx] = p = new SeasonChange(season, playSound); + p.SetStatic(); + } + + return p; + } + + return new SeasonChange(season, playSound); + } + } + + public sealed class SupportedFeatures : Packet + { + public SupportedFeatures(NetState ns) : base(0xB9, ns.ExtendedSupportedFeatures ? 5 : 3) + { + FeatureFlags flags = ExpansionInfo.CoreExpansion.SupportedFeatures; + + flags |= Value; + + if (ns.Account is IAccount acct && acct.Limit >= 6) + { + flags |= FeatureFlags.LiveAccount; + flags &= ~FeatureFlags.UOTD; + + if (acct.Limit > 6) + flags |= FeatureFlags.SeventhCharacterSlot; + else + flags |= FeatureFlags.SixthCharacterSlot; + } + + if (ns.ExtendedSupportedFeatures) + m_Stream.Write((uint)flags); + else + m_Stream.Write((ushort)flags); + } + + public static FeatureFlags Value{ get; set; } + + public static SupportedFeatures Instantiate(NetState ns) + { + return new SupportedFeatures(ns); + } + } + + public static class AttributeNormalizer + { + public static int Maximum{ get; set; } = 25; + + public static bool Enabled{ get; set; } = true; + + public static void Write(PacketWriter stream, int cur, int max) + { + if (Enabled && max != 0) + { + stream.Write((short)Maximum); + stream.Write((short)(cur * Maximum / max)); + } + else + { + stream.Write((short)max); + stream.Write((short)cur); + } + } + + public static void WriteReverse(PacketWriter stream, int cur, int max) + { + if (Enabled && max != 0) + { + stream.Write((short)(cur * Maximum / max)); + stream.Write((short)Maximum); + } + else + { + stream.Write((short)cur); + stream.Write((short)max); + } + } + } + + public sealed class MobileHits : Packet + { + public MobileHits(Mobile m) : base(0xA1, 9) + { + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.HitsMax); + m_Stream.Write((short)m.Hits); + } + } + + public sealed class MobileHitsN : Packet + { + public MobileHitsN(Mobile m) : base(0xA1, 9) + { + m_Stream.Write(m.Serial); + AttributeNormalizer.Write(m_Stream, m.Hits, m.HitsMax); + } + } + + public sealed class MobileMana : Packet + { + public MobileMana(Mobile m) : base(0xA2, 9) + { + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.ManaMax); + m_Stream.Write((short)m.Mana); + } + } + + public sealed class MobileManaN : Packet + { + public MobileManaN(Mobile m) : base(0xA2, 9) + { + m_Stream.Write(m.Serial); + AttributeNormalizer.Write(m_Stream, m.Mana, m.ManaMax); + } + } + + public sealed class MobileStam : Packet + { + public MobileStam(Mobile m) : base(0xA3, 9) + { + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.StamMax); + m_Stream.Write((short)m.Stam); + } + } + + public sealed class MobileStamN : Packet + { + public MobileStamN(Mobile m) : base(0xA3, 9) + { + m_Stream.Write(m.Serial); + AttributeNormalizer.Write(m_Stream, m.Stam, m.StamMax); + } + } + + public sealed class MobileAttributes : Packet + { + public MobileAttributes(Mobile m) : base(0x2D, 17) + { + m_Stream.Write(m.Serial); + + m_Stream.Write((short)m.HitsMax); + m_Stream.Write((short)m.Hits); + + m_Stream.Write((short)m.ManaMax); + m_Stream.Write((short)m.Mana); + + m_Stream.Write((short)m.StamMax); + m_Stream.Write((short)m.Stam); + } + } + + public sealed class MobileAttributesN : Packet + { + public MobileAttributesN(Mobile m) : base(0x2D, 17) + { + m_Stream.Write(m.Serial); + + AttributeNormalizer.Write(m_Stream, m.Hits, m.HitsMax); + AttributeNormalizer.Write(m_Stream, m.Mana, m.ManaMax); + AttributeNormalizer.Write(m_Stream, m.Stam, m.StamMax); + } + } + + public sealed class PathfindMessage : Packet + { + public PathfindMessage(IPoint3D p) : base(0x38, 7) + { + m_Stream.Write((short)p.X); + m_Stream.Write((short)p.Y); + m_Stream.Write((short)p.Z); + } + } + + // unsure of proper format, client crashes + public sealed class MobileName : Packet + { + public MobileName(Mobile m) : base(0x98) + { + string name = m.Name; + + if (name == null) name = ""; + + EnsureCapacity(37); + + m_Stream.Write(m.Serial); + m_Stream.WriteAsciiFixed(name, 30); + } + } + + public sealed class MobileAnimation : Packet + { + public MobileAnimation(Mobile m, int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay) : + base(0x6E, 14) + { + m_Stream.Write(m.Serial); + m_Stream.Write((short)action); + m_Stream.Write((short)frameCount); + m_Stream.Write((short)repeatCount); + m_Stream.Write(!forward); // protocol has really "reverse" but I find this more intuitive + m_Stream.Write(repeat); + m_Stream.Write((byte)delay); + } + } + + public sealed class NewMobileAnimation : Packet + { + public NewMobileAnimation(Mobile m, int action, int frameCount, int delay) : base(0xE2, 10) + { + m_Stream.Write(m.Serial); + m_Stream.Write((short)action); + m_Stream.Write((short)frameCount); + m_Stream.Write((byte)delay); + } + } + + public sealed class MobileStatusCompact : Packet + { + public MobileStatusCompact(bool canBeRenamed, Mobile m) : base(0x11) + { + string name = m.Name; + if (name == null) name = ""; + + EnsureCapacity(43); + + m_Stream.Write(m.Serial); + m_Stream.WriteAsciiFixed(name, 30); + + AttributeNormalizer.WriteReverse(m_Stream, m.Hits, m.HitsMax); + + m_Stream.Write(canBeRenamed); + + m_Stream.Write((byte)0); // type + } + } + + public sealed class MobileStatusExtended : Packet + { + public MobileStatusExtended(Mobile m) : this(m, m.NetState) + { + } + + public MobileStatusExtended(Mobile m, NetState ns) : base(0x11) + { + string name = m.Name; + if (name == null) name = ""; + + int type; + + if (Core.HS && ns != null && ns.ExtendedStatus) + { + type = 6; + EnsureCapacity(121); + } + else if (Core.ML && ns != null && ns.SupportsExpansion(Expansion.ML)) + { + type = 5; + EnsureCapacity(91); + } + else + { + type = Core.AOS ? 4 : 3; + EnsureCapacity(88); + } + + m_Stream.Write(m.Serial); + m_Stream.WriteAsciiFixed(name, 30); + + m_Stream.Write((short)m.Hits); + m_Stream.Write((short)m.HitsMax); + + m_Stream.Write(m.CanBeRenamedBy(m)); + + m_Stream.Write((byte)type); + + m_Stream.Write(m.Female); + + m_Stream.Write((short)m.Str); + m_Stream.Write((short)m.Dex); + m_Stream.Write((short)m.Int); + + m_Stream.Write((short)m.Stam); + m_Stream.Write((short)m.StamMax); + + m_Stream.Write((short)m.Mana); + m_Stream.Write((short)m.ManaMax); + + m_Stream.Write(m.TotalGold); + m_Stream.Write((short)(Core.AOS ? m.PhysicalResistance : (int)(m.ArmorRating + 0.5))); + m_Stream.Write((short)(Mobile.BodyWeight + m.TotalWeight)); + + if (type >= 5) + { + m_Stream.Write((short)m.MaxWeight); + m_Stream.Write((byte)(m.Race.RaceID + 1)); // Would be 0x00 if it's a non-ML enabled account but... + } + + m_Stream.Write((short)m.StatCap); + + m_Stream.Write((byte)m.Followers); + m_Stream.Write((byte)m.FollowersMax); + + if (type >= 4) + { + m_Stream.Write((short)m.FireResistance); // Fire + m_Stream.Write((short)m.ColdResistance); // Cold + m_Stream.Write((short)m.PoisonResistance); // Poison + m_Stream.Write((short)m.EnergyResistance); // Energy + m_Stream.Write((short)m.Luck); // Luck + + IWeapon weapon = m.Weapon; + + int min = 0, max = 0; + + weapon?.GetStatusDamage(m, out min, out max); - Compression.Pack( m_PackBuffer, ref packLength, buffer, length, ZLibQuality.Default ); + m_Stream.Write((short)min); // Damage min + m_Stream.Write((short)max); // Damage max - m_Stream.Write( (int) ( 4 + packLength ) ); - m_Stream.Write( (int) length ); - m_Stream.Write( m_PackBuffer, 0, packLength ); + m_Stream.Write(m.TithingPoints); + } - lock (m_PackBuffers) - m_PackBuffers.ReleaseBuffer(m_PackBuffer); - } - } + if (type >= 6) + for (int i = 0; i < 15; ++i) + m_Stream.Write((short)m.GetAOSStatus(i)); + } + } - public sealed class DisplayGumpFast : Packet, IGumpWriter - { - private int m_LayoutLength; + public sealed class MobileStatus : Packet + { + public MobileStatus(Mobile beholder, Mobile beheld) : this(beholder, beheld, beheld.NetState) + { + } + + public MobileStatus(Mobile beholder, Mobile beheld, NetState ns) : base(0x11) + { + string name = beheld.Name; + if (name == null) name = ""; + + int type; + + if (beholder != beheld) + { + type = 0; + EnsureCapacity(43); + } + else if (Core.HS && ns != null && ns.ExtendedStatus) + { + type = 6; + EnsureCapacity(121); + } + else if (Core.ML && ns != null && ns.SupportsExpansion(Expansion.ML)) + { + type = 5; + EnsureCapacity(91); + } + else + { + type = Core.AOS ? 4 : 3; + EnsureCapacity(88); + } - public int TextEntries { get; set; } + m_Stream.Write(beheld.Serial); - public int Switches { get; set; } + m_Stream.WriteAsciiFixed(name, 30); - public DisplayGumpFast( Gump g ) : base( 0xB0 ) - { - m_Buffer[0] = (byte)' '; + if (beholder == beheld) + WriteAttr(beheld.Hits, beheld.HitsMax); + else + WriteAttrNorm(beheld.Hits, beheld.HitsMax); - EnsureCapacity( 4096 ); + m_Stream.Write(beheld.CanBeRenamedBy(beholder)); - m_Stream.Write( (int) g.Serial ); - m_Stream.Write( (int) g.TypeID ); - m_Stream.Write( (int) g.X ); - m_Stream.Write( (int) g.Y ); - m_Stream.Write( (ushort) 0xFFFF ); - } + m_Stream.Write((byte)type); + + if (type > 0) + { + m_Stream.Write(beheld.Female); + + m_Stream.Write((short)beheld.Str); + m_Stream.Write((short)beheld.Dex); + m_Stream.Write((short)beheld.Int); + + WriteAttr(beheld.Stam, beheld.StamMax); + WriteAttr(beheld.Mana, beheld.ManaMax); + + m_Stream.Write(beheld.TotalGold); + m_Stream.Write((short)(Core.AOS ? beheld.PhysicalResistance : (int)(beheld.ArmorRating + 0.5))); + m_Stream.Write((short)(Mobile.BodyWeight + beheld.TotalWeight)); + + if (type >= 5) + { + m_Stream.Write((short)beheld.MaxWeight); + m_Stream.Write((byte)(beheld.Race.RaceID + 1)); // Would be 0x00 if it's a non-ML enabled account but... + } + + m_Stream.Write((short)beheld.StatCap); + + m_Stream.Write((byte)beheld.Followers); + m_Stream.Write((byte)beheld.FollowersMax); + + if (type >= 4) + { + m_Stream.Write((short)beheld.FireResistance); // Fire + m_Stream.Write((short)beheld.ColdResistance); // Cold + m_Stream.Write((short)beheld.PoisonResistance); // Poison + m_Stream.Write((short)beheld.EnergyResistance); // Energy + m_Stream.Write((short)beheld.Luck); // Luck + + IWeapon weapon = beheld.Weapon; + + int min = 0, max = 0; + + weapon?.GetStatusDamage(beheld, out min, out max); + + m_Stream.Write((short)min); // Damage min + m_Stream.Write((short)max); // Damage max + + m_Stream.Write(beheld.TithingPoints); + } + + if (type >= 6) + for (int i = 0; i < 15; ++i) + m_Stream.Write((short)beheld.GetAOSStatus(i)); + } + } + + private void WriteAttr(int current, int maximum) + { + m_Stream.Write((short)current); + m_Stream.Write((short)maximum); + } + + private void WriteAttrNorm(int current, int maximum) + { + AttributeNormalizer.WriteReverse(m_Stream, current, maximum); + } + } + + public sealed class HealthbarPoison : Packet + { + public HealthbarPoison(Mobile m) : base(0x17) + { + EnsureCapacity(12); + + m_Stream.Write(m.Serial); + m_Stream.Write((short)1); + + m_Stream.Write((short)1); + + Poison p = m.Poison; + + if (p != null) + m_Stream.Write((byte)(p.Level + 1)); + else + m_Stream.Write((byte)0); + } + } + + public sealed class HealthbarYellow : Packet + { + public HealthbarYellow(Mobile m) : base(0x17) + { + EnsureCapacity(12); + + m_Stream.Write(m.Serial); + m_Stream.Write((short)1); + + m_Stream.Write((short)2); + + if (m.Blessed || m.YellowHealthbar) + m_Stream.Write((byte)1); + else + m_Stream.Write((byte)0); + } + } + + public sealed class MobileUpdate : Packet + { + public MobileUpdate(Mobile m) : base(0x20, 19) + { + int hue = m.Hue; + + if (m.SolidHueOverride >= 0) + hue = m.SolidHueOverride; + + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.Body); + m_Stream.Write((byte)0); + m_Stream.Write((short)hue); + m_Stream.Write((byte)m.GetPacketFlags()); + m_Stream.Write((short)m.X); + m_Stream.Write((short)m.Y); + m_Stream.Write((short)0); + m_Stream.Write((byte)m.Direction); + m_Stream.Write((sbyte)m.Z); + } + } + + // Pre-7.0.0.0 Mobile Update + public sealed class MobileUpdateOld : Packet + { + public MobileUpdateOld(Mobile m) : base(0x20, 19) + { + int hue = m.Hue; + + if (m.SolidHueOverride >= 0) + hue = m.SolidHueOverride; + + m_Stream.Write(m.Serial); + m_Stream.Write((short)m.Body); + m_Stream.Write((byte)0); + m_Stream.Write((short)hue); + m_Stream.Write((byte)m.GetOldPacketFlags()); + m_Stream.Write((short)m.X); + m_Stream.Write((short)m.Y); + m_Stream.Write((short)0); + m_Stream.Write((byte)m.Direction); + m_Stream.Write((sbyte)m.Z); + } + } + + public sealed class MobileIncoming : Packet + { + private static ThreadLocal m_DupedLayersTL = new ThreadLocal(() => { return new int[256]; }); + private static ThreadLocal m_VersionTL = new ThreadLocal(); + + public Mobile m_Beheld; + + public MobileIncoming(Mobile beholder, Mobile beheld) : base(0x78) + { + m_Beheld = beheld; + + int m_Version = ++m_VersionTL.Value; + int[] m_DupedLayers = m_DupedLayersTL.Value; + + List eq = beheld.Items; + int count = eq.Count; + + if (beheld.HairItemID > 0) + count++; + if (beheld.FacialHairItemID > 0) + count++; + + EnsureCapacity(23 + count * 9); + + int hue = beheld.Hue; + + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; + + m_Stream.Write(beheld.Serial); + m_Stream.Write((short)beheld.Body); + m_Stream.Write((short)beheld.X); + m_Stream.Write((short)beheld.Y); + m_Stream.Write((sbyte)beheld.Z); + m_Stream.Write((byte)beheld.Direction); + m_Stream.Write((short)hue); + m_Stream.Write((byte)beheld.GetPacketFlags()); + m_Stream.Write((byte)Notoriety.Compute(beholder, beheld)); + + for (int i = 0; i < eq.Count; ++i) + { + Item item = eq[i]; + + byte layer = (byte)item.Layer; + + if (!item.Deleted && beholder.CanSee(item) && m_DupedLayers[layer] != m_Version) + { + m_DupedLayers[layer] = m_Version; + + hue = item.Hue; + + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; + + int itemID = item.ItemID & 0xFFFF; + + m_Stream.Write(item.Serial); + m_Stream.Write((ushort)itemID); + m_Stream.Write(layer); + + m_Stream.Write((short)hue); + } + } + + if (beheld.HairItemID > 0) + if (m_DupedLayers[(int)Layer.Hair] != m_Version) + { + m_DupedLayers[(int)Layer.Hair] = m_Version; + hue = beheld.HairHue; - private static byte[] m_True = Gump.StringToBuffer( " 1" ); - private static byte[] m_False = Gump.StringToBuffer( " 0" ); + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - private static byte[] m_BeginTextSeparator = Gump.StringToBuffer( " @" ); - private static byte[] m_EndTextSeparator = Gump.StringToBuffer( "@" ); + int itemID = beheld.HairItemID & 0xFFFF; - private byte[] m_Buffer = new byte[48]; + m_Stream.Write(HairInfo.FakeSerial(beheld)); + m_Stream.Write((ushort)itemID); + m_Stream.Write((byte)Layer.Hair); - public void AppendLayout( bool val ) - { - AppendLayout( val ? m_True : m_False ); - } + m_Stream.Write((short)hue); + } - public void AppendLayout( int val ) - { - string toString = val.ToString(); - int bytes = System.Text.Encoding.ASCII.GetBytes( toString, 0, toString.Length, m_Buffer, 1 ) + 1; + if (beheld.FacialHairItemID > 0) + if (m_DupedLayers[(int)Layer.FacialHair] != m_Version) + { + m_DupedLayers[(int)Layer.FacialHair] = m_Version; + hue = beheld.FacialHairHue; - m_Stream.Write( m_Buffer, 0, bytes ); - m_LayoutLength += bytes; - } + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - public void AppendLayoutNS( int val ) - { - string toString = val.ToString(); - int bytes = System.Text.Encoding.ASCII.GetBytes( toString, 0, toString.Length, m_Buffer, 1 ); + int itemID = beheld.FacialHairItemID & 0xFFFF; - m_Stream.Write( m_Buffer, 1, bytes ); - m_LayoutLength += bytes; - } + m_Stream.Write(FacialHairInfo.FakeSerial(beheld)); + m_Stream.Write((ushort)itemID); + m_Stream.Write((byte)Layer.FacialHair); - public void AppendLayout( string text ) - { - AppendLayout( m_BeginTextSeparator ); + m_Stream.Write((short)hue); + } - int length = text.Length; - m_Stream.WriteAsciiFixed( text, length ); - m_LayoutLength += length; - - AppendLayout( m_EndTextSeparator ); - } - - public void AppendLayout( byte[] buffer ) - { - int length = buffer.Length; - m_Stream.Write( buffer, 0, length ); - m_LayoutLength += length; - } - - public void WriteStrings( List text ) - { - m_Stream.Seek( 19, SeekOrigin.Begin ); - m_Stream.Write( (ushort) m_LayoutLength ); - m_Stream.Seek( 0, SeekOrigin.End ); - - m_Stream.Write( (ushort) text.Count ); - - for ( int i = 0; i < text.Count; ++i ) - { - string v = text[i]; - - if ( v == null ) - v = string.Empty; - - int length = (ushort) v.Length; - - m_Stream.Write( (ushort) length ); - m_Stream.WriteBigUniFixed( v, length ); - } - } - - public void Flush() - { - } - } - - public sealed class DisplayGump : Packet - { - public DisplayGump( Gump g, string layout, string[] text ) : base( 0xB0 ) - { - if ( layout == null ) layout = ""; - - EnsureCapacity( 256 ); - - m_Stream.Write( (int) g.Serial ); - m_Stream.Write( (int) g.TypeID ); - m_Stream.Write( (int) g.X ); - m_Stream.Write( (int) g.Y ); - m_Stream.Write( (ushort) (layout.Length + 1) ); - m_Stream.WriteAsciiNull( layout ); - - m_Stream.Write( (ushort) text.Length ); - - for ( int i = 0; i < text.Length; ++i ) - { - string v = text[i]; - - if ( v == null ) v = ""; - - int length = (ushort) v.Length; - - m_Stream.Write( (ushort) length ); - m_Stream.WriteBigUniFixed( v, length ); - } - } - } - - public sealed class DisplayPaperdoll : Packet - { - public DisplayPaperdoll( Mobile m, string text, bool canLift ) : base( 0x88, 66 ) - { - byte flags = 0x00; - - if ( m.Warmode ) - flags |= 0x01; - - if ( canLift ) - flags |= 0x02; - - m_Stream.Write( (int) m.Serial ); - m_Stream.WriteAsciiFixed( text, 60 ); - m_Stream.Write( (byte) flags ); - } - } - - public sealed class PopupMessage : Packet - { - public PopupMessage( PMMessage msg ) : base( 0x53, 2 ) - { - m_Stream.Write( (byte)msg ); - } - } - - public sealed class PlaySound : Packet - { - public PlaySound( int soundID, IPoint3D target ) : base( 0x54, 12 ) - { - m_Stream.Write( (byte) 1 ); // flags - m_Stream.Write( (short) soundID ); - m_Stream.Write( (short) 0 ); // volume - m_Stream.Write( (short) target.X ); - m_Stream.Write( (short) target.Y ); - m_Stream.Write( (short) target.Z ); - } - } - - public sealed class PlayMusic : Packet - { - public static readonly Packet InvalidInstance = SetStatic( new PlayMusic( MusicName.Invalid ) ); - - private static Packet[] m_Instances = new Packet[60]; - - public static Packet GetInstance( MusicName name ) - { - if ( name == MusicName.Invalid ) - return InvalidInstance; - - int v = (int)name; - Packet p; - - if ( v >= 0 && v < m_Instances.Length ) - { - p = m_Instances[v]; - - if ( p == null ) - m_Instances[v] = p = SetStatic( new PlayMusic( name ) ); - } - else - { - p = new PlayMusic( name ); - } - - return p; - } - - public PlayMusic( MusicName name ) : base( 0x6D, 3 ) - { - m_Stream.Write( (short)name ); - } - } - - public sealed class ScrollMessage : Packet - { - public ScrollMessage( int type, int tip, string text ) : base( 0xA6 ) - { - if ( text == null ) text = ""; - - EnsureCapacity( 10 + text.Length ); - - m_Stream.Write( (byte) type ); - m_Stream.Write( (int) tip ); - m_Stream.Write( (ushort) text.Length ); - m_Stream.WriteAsciiFixed( text, text.Length ); - } - } - - public sealed class CurrentTime : Packet - { - public CurrentTime() : base( 0x5B, 4 ) - { - DateTime now = DateTime.UtcNow; - - m_Stream.Write( (byte) now.Hour ); - m_Stream.Write( (byte) now.Minute ); - m_Stream.Write( (byte) now.Second ); - } - } - - public sealed class MapChange : Packet - { - public MapChange( Mobile m ) : base( 0xBF ) - { - EnsureCapacity( 6 ); - - m_Stream.Write( (short) 0x08 ); - m_Stream.Write( (byte) (m.Map?.MapID ?? 0) ); - } - } - - public sealed class SeasonChange : Packet - { - private static SeasonChange[][] m_Cache = new SeasonChange[5][] - { - new SeasonChange[2], - new SeasonChange[2], - new SeasonChange[2], - new SeasonChange[2], - new SeasonChange[2] - }; - - public static SeasonChange Instantiate( int season ) - { - return Instantiate( season, true ); - } - - public static SeasonChange Instantiate( int season, bool playSound ) - { - if ( season >= 0 && season < m_Cache.Length ) - { - int idx = playSound ? 1 : 0; - - SeasonChange p = m_Cache[season][idx]; - - if ( p == null ) - { - m_Cache[season][idx] = p = new SeasonChange( season, playSound ); - p.SetStatic(); - } - - return p; - } - - return new SeasonChange( season, playSound ); - } - - public SeasonChange( int season ) : this( season, true ) - { - } - - public SeasonChange( int season, bool playSound ) : base( 0xBC, 3 ) - { - m_Stream.Write( (byte) season ); - m_Stream.Write( (bool) playSound ); - } - } - - public sealed class SupportedFeatures : Packet - { - public static FeatureFlags Value { get; set; } - - public static SupportedFeatures Instantiate( NetState ns ) - { - return new SupportedFeatures( ns ); - } - - public SupportedFeatures( NetState ns ) : base( 0xB9, ns.ExtendedSupportedFeatures ? 5 : 3 ) - { - FeatureFlags flags = ExpansionInfo.CoreExpansion.SupportedFeatures; - - flags |= Value; - - if ( ns.Account is IAccount acct && acct.Limit >= 6 ) - { - flags |= FeatureFlags.LiveAccount; - flags &= ~FeatureFlags.UOTD; - - if ( acct.Limit > 6 ) - flags |= FeatureFlags.SeventhCharacterSlot; - else - flags |= FeatureFlags.SixthCharacterSlot; - } - - if ( ns.ExtendedSupportedFeatures ) { - m_Stream.Write( (uint) flags ); - } else { - m_Stream.Write( (ushort) flags ); - } - } - } - - public static class AttributeNormalizer - { - public static int Maximum { get; set; } = 25; - - public static bool Enabled { get; set; } = true; - - public static void Write( PacketWriter stream, int cur, int max ) - { - if ( Enabled && max != 0 ) - { - stream.Write( (short) Maximum ); - stream.Write( (short) ((cur * Maximum) / max) ); - } - else - { - stream.Write( (short) max ); - stream.Write( (short) cur ); - } - } - - public static void WriteReverse( PacketWriter stream, int cur, int max ) - { - if ( Enabled && max != 0 ) - { - stream.Write( (short) ((cur * Maximum) / max) ); - stream.Write( (short) Maximum ); - } - else - { - stream.Write( (short) cur ); - stream.Write( (short) max ); - } - } - } - - public sealed class MobileHits : Packet - { - public MobileHits( Mobile m ) : base( 0xA1, 9 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.HitsMax ); - m_Stream.Write( (short) m.Hits ); - } - } - - public sealed class MobileHitsN : Packet - { - public MobileHitsN( Mobile m ) : base( 0xA1, 9 ) - { - m_Stream.Write( (int) m.Serial ); - AttributeNormalizer.Write( m_Stream, m.Hits, m.HitsMax ); - } - } - - public sealed class MobileMana : Packet - { - public MobileMana( Mobile m ) : base( 0xA2, 9 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.ManaMax ); - m_Stream.Write( (short) m.Mana ); - } - } - - public sealed class MobileManaN : Packet - { - public MobileManaN( Mobile m ) : base( 0xA2, 9 ) - { - m_Stream.Write( (int) m.Serial ); - AttributeNormalizer.Write( m_Stream, m.Mana, m.ManaMax ); - } - } - - public sealed class MobileStam : Packet - { - public MobileStam( Mobile m ) : base( 0xA3, 9 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.StamMax ); - m_Stream.Write( (short) m.Stam ); - } - } - - public sealed class MobileStamN : Packet - { - public MobileStamN( Mobile m ) : base( 0xA3, 9 ) - { - m_Stream.Write( (int) m.Serial ); - AttributeNormalizer.Write( m_Stream, m.Stam, m.StamMax ); - } - } - - public sealed class MobileAttributes : Packet - { - public MobileAttributes( Mobile m ) : base( 0x2D, 17 ) - { - m_Stream.Write( m.Serial ); - - m_Stream.Write( (short) m.HitsMax ); - m_Stream.Write( (short) m.Hits ); - - m_Stream.Write( (short) m.ManaMax ); - m_Stream.Write( (short) m.Mana ); - - m_Stream.Write( (short) m.StamMax ); - m_Stream.Write( (short) m.Stam ); - } - } - - public sealed class MobileAttributesN : Packet - { - public MobileAttributesN( Mobile m ) : base( 0x2D, 17 ) - { - m_Stream.Write( m.Serial ); - - AttributeNormalizer.Write( m_Stream, m.Hits, m.HitsMax ); - AttributeNormalizer.Write( m_Stream, m.Mana, m.ManaMax ); - AttributeNormalizer.Write( m_Stream, m.Stam, m.StamMax ); - } - } - - public sealed class PathfindMessage : Packet - { - public PathfindMessage( IPoint3D p ) : base( 0x38, 7 ) - { - m_Stream.Write( (short) p.X ); - m_Stream.Write( (short) p.Y ); - m_Stream.Write( (short) p.Z ); - } - } - - // unsure of proper format, client crashes - public sealed class MobileName : Packet - { - public MobileName( Mobile m ) : base( 0x98 ) - { - string name = m.Name; - - if ( name == null ) name = ""; - - EnsureCapacity( 37 ); - - m_Stream.Write( (int) m.Serial ); - m_Stream.WriteAsciiFixed( name, 30 ); - } - } - - public sealed class MobileAnimation : Packet - { - public MobileAnimation( Mobile m, int action, int frameCount, int repeatCount, bool forward, bool repeat, int delay ) : base( 0x6E, 14 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) action ); - m_Stream.Write( (short) frameCount ); - m_Stream.Write( (short) repeatCount ); - m_Stream.Write( (bool) !forward ); // protocol has really "reverse" but I find this more intuitive - m_Stream.Write( (bool) repeat ); - m_Stream.Write( (byte) delay ); - } - } - - public sealed class NewMobileAnimation : Packet - { - public NewMobileAnimation( Mobile m, int action, int frameCount, int delay ) : base( 0xE2, 10 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) action ); - m_Stream.Write( (short) frameCount ); - m_Stream.Write( (byte) delay ); - } - } - - public sealed class MobileStatusCompact : Packet - { - public MobileStatusCompact( bool canBeRenamed, Mobile m ) : base( 0x11 ) - { - string name = m.Name; - if ( name == null ) name = ""; - - EnsureCapacity( 43 ); - - m_Stream.Write( (int) m.Serial ); - m_Stream.WriteAsciiFixed( name, 30 ); - - AttributeNormalizer.WriteReverse( m_Stream, m.Hits, m.HitsMax ); - - m_Stream.Write( canBeRenamed ); - - m_Stream.Write( (byte) 0 ); // type - } - } - - public sealed class MobileStatusExtended : Packet - { - public MobileStatusExtended( Mobile m ) : this( m, m.NetState ) - { - } - - public MobileStatusExtended( Mobile m, NetState ns ) : base( 0x11 ) - { - string name = m.Name; - if ( name == null ) name = ""; - - int type; - - if ( Core.HS && ns != null && ns.ExtendedStatus ) - { - type = 6; - EnsureCapacity( 121 ); - } - else if ( Core.ML && ns != null && ns.SupportsExpansion( Expansion.ML ) ) - { - type = 5; - EnsureCapacity( 91 ); - } - else - { - type = Core.AOS ? 4 : 3; - EnsureCapacity( 88 ); - } - - m_Stream.Write( (int) m.Serial ); - m_Stream.WriteAsciiFixed( name, 30 ); - - m_Stream.Write( (short) m.Hits ); - m_Stream.Write( (short) m.HitsMax ); - - m_Stream.Write( m.CanBeRenamedBy( m ) ); - - m_Stream.Write( (byte) type ); - - m_Stream.Write( m.Female ); - - m_Stream.Write( (short) m.Str ); - m_Stream.Write( (short) m.Dex ); - m_Stream.Write( (short) m.Int ); - - m_Stream.Write( (short) m.Stam ); - m_Stream.Write( (short) m.StamMax ); - - m_Stream.Write( (short) m.Mana ); - m_Stream.Write( (short) m.ManaMax ); - - m_Stream.Write( (int) m.TotalGold ); - m_Stream.Write( (short) (Core.AOS ? m.PhysicalResistance : (int)(m.ArmorRating + 0.5)) ); - m_Stream.Write( (short) (Mobile.BodyWeight + m.TotalWeight) ); - - if ( type >= 5 ) - { - m_Stream.Write( (short)m.MaxWeight ); - m_Stream.Write( (byte)(m.Race.RaceID + 1)); // Would be 0x00 if it's a non-ML enabled account but... - } - - m_Stream.Write( (short) m.StatCap ); - - m_Stream.Write( (byte) m.Followers ); - m_Stream.Write( (byte) m.FollowersMax ); - - if ( type >= 4 ) - { - m_Stream.Write( (short) m.FireResistance ); // Fire - m_Stream.Write( (short) m.ColdResistance ); // Cold - m_Stream.Write( (short) m.PoisonResistance ); // Poison - m_Stream.Write( (short) m.EnergyResistance ); // Energy - m_Stream.Write( (short) m.Luck ); // Luck - - IWeapon weapon = m.Weapon; - - int min = 0, max = 0; - - weapon?.GetStatusDamage( m, out min, out max ); - - m_Stream.Write( (short) min ); // Damage min - m_Stream.Write( (short) max ); // Damage max - - m_Stream.Write( (int) m.TithingPoints ); - } + m_Stream.Write(0); // terminate + } - if ( type >= 6 ) - { - for ( int i = 0; i < 15; ++i ) - m_Stream.Write( (short) m.GetAOSStatus( i ) ); - } - } - } - - public sealed class MobileStatus : Packet - { - public MobileStatus( Mobile beholder, Mobile beheld ) : this( beholder, beheld, beheld.NetState ) - { - } - - public MobileStatus( Mobile beholder, Mobile beheld, NetState ns ) : base( 0x11 ) - { - string name = beheld.Name; - if ( name == null ) name = ""; - - int type; - - if ( beholder != beheld ) - { - type = 0; - EnsureCapacity( 43 ); - } - else if ( Core.HS && ns != null && ns.ExtendedStatus ) - { - type = 6; - EnsureCapacity( 121 ); - } - else if ( Core.ML && ns != null && ns.SupportsExpansion( Expansion.ML ) ) - { - type = 5; - EnsureCapacity( 91 ); - } - else - { - type = Core.AOS ? 4 : 3; - EnsureCapacity( 88 ); - } + public static Packet Create(NetState ns, Mobile beholder, Mobile beheld) + { + if (ns.NewMobileIncoming) + return new MobileIncoming(beholder, beheld); + if (ns.StygianAbyss) + return new MobileIncomingSA(beholder, beheld); + return new MobileIncomingOld(beholder, beheld); + } + } - m_Stream.Write( beheld.Serial ); - - m_Stream.WriteAsciiFixed( name, 30 ); - - if ( beholder == beheld ) - WriteAttr( beheld.Hits, beheld.HitsMax ); - else - WriteAttrNorm( beheld.Hits, beheld.HitsMax ); - - m_Stream.Write( beheld.CanBeRenamedBy( beholder ) ); - - m_Stream.Write( (byte) type ); - - if ( type > 0 ) - { - m_Stream.Write( beheld.Female ); - - m_Stream.Write( (short) beheld.Str ); - m_Stream.Write( (short) beheld.Dex ); - m_Stream.Write( (short) beheld.Int ); - - WriteAttr( beheld.Stam, beheld.StamMax ); - WriteAttr( beheld.Mana, beheld.ManaMax ); - - m_Stream.Write( (int) beheld.TotalGold ); - m_Stream.Write( (short) (Core.AOS ? beheld.PhysicalResistance : (int)(beheld.ArmorRating + 0.5)) ); - m_Stream.Write( (short) (Mobile.BodyWeight + beheld.TotalWeight) ); - - if ( type >= 5 ) - { - m_Stream.Write( (short)beheld.MaxWeight ); - m_Stream.Write( (byte)(beheld.Race.RaceID + 1) ); // Would be 0x00 if it's a non-ML enabled account but... - } - - m_Stream.Write( (short) beheld.StatCap ); - - m_Stream.Write( (byte) beheld.Followers ); - m_Stream.Write( (byte) beheld.FollowersMax ); - - if ( type >= 4 ) - { - m_Stream.Write( (short) beheld.FireResistance ); // Fire - m_Stream.Write( (short) beheld.ColdResistance ); // Cold - m_Stream.Write( (short) beheld.PoisonResistance ); // Poison - m_Stream.Write( (short) beheld.EnergyResistance ); // Energy - m_Stream.Write( (short) beheld.Luck ); // Luck - - IWeapon weapon = beheld.Weapon; - - int min = 0, max = 0; - - weapon?.GetStatusDamage( beheld, out min, out max ); - - m_Stream.Write( (short) min ); // Damage min - m_Stream.Write( (short) max ); // Damage max - - m_Stream.Write( (int) beheld.TithingPoints ); - } - - if ( type >= 6 ) - { - for ( int i = 0; i < 15; ++i ) - m_Stream.Write( (short) beheld.GetAOSStatus( i ) ); - } - } - } - - private void WriteAttr( int current, int maximum ) - { - m_Stream.Write( (short) current ); - m_Stream.Write( (short) maximum ); - } - - private void WriteAttrNorm( int current, int maximum ) - { - AttributeNormalizer.WriteReverse( m_Stream, current, maximum ); - } - } - - public sealed class HealthbarPoison : Packet - { - public HealthbarPoison( Mobile m ) : base( 0x17 ) - { - EnsureCapacity( 12 ); - - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) 1 ); - - m_Stream.Write( (short) 1 ); - - Poison p = m.Poison; - - if ( p != null ) { - m_Stream.Write( (byte) (p.Level + 1) ); - } else { - m_Stream.Write( (byte) 0 ); - } - } - } - - public sealed class HealthbarYellow : Packet - { - public HealthbarYellow( Mobile m ) : base( 0x17 ) - { - EnsureCapacity( 12 ); - - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) 1 ); - - m_Stream.Write( (short) 2 ); - - if ( m.Blessed || m.YellowHealthbar ) { - m_Stream.Write( (byte) 1 ); - } else { - m_Stream.Write( (byte) 0 ); - } - } - } - - public sealed class MobileUpdate : Packet - { - public MobileUpdate( Mobile m ) : base( 0x20, 19 ) - { - int hue = m.Hue; - - if ( m.SolidHueOverride >= 0 ) - hue = m.SolidHueOverride; - - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.Body ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (byte) m.GetPacketFlags() ); - m_Stream.Write( (short) m.X ); - m_Stream.Write( (short) m.Y ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (sbyte) m.Z ); - } - } - - // Pre-7.0.0.0 Mobile Update - public sealed class MobileUpdateOld : Packet - { - public MobileUpdateOld( Mobile m ) : base( 0x20, 19 ) - { - int hue = m.Hue; - - if ( m.SolidHueOverride >= 0 ) - hue = m.SolidHueOverride; - - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (short) m.Body ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (byte) m.GetOldPacketFlags() ); - m_Stream.Write( (short) m.X ); - m_Stream.Write( (short) m.Y ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (sbyte) m.Z ); - } - } - - public sealed class MobileIncoming : Packet - { - public static Packet Create(NetState ns, Mobile beholder, Mobile beheld) - { - if (ns.NewMobileIncoming) - return new MobileIncoming(beholder, beheld); - if (ns.StygianAbyss) - return new MobileIncomingSA(beholder, beheld); - return new MobileIncomingOld(beholder, beheld); - } - - private static ThreadLocal m_DupedLayersTL = new ThreadLocal(() => {return new int[256];}); - private static ThreadLocal m_VersionTL = new ThreadLocal(); - - public Mobile m_Beheld; - - public MobileIncoming(Mobile beholder, Mobile beheld) : base(0x78) - { - m_Beheld = beheld; - - int m_Version = ++(m_VersionTL.Value); - int[] m_DupedLayers = m_DupedLayersTL.Value; - - List eq = beheld.Items; - int count = eq.Count; - - if (beheld.HairItemID > 0) - count++; - if (beheld.FacialHairItemID > 0) - count++; - - EnsureCapacity(23 + (count * 9)); - - int hue = beheld.Hue; - - if (beheld.SolidHueOverride >= 0) - hue = beheld.SolidHueOverride; - - m_Stream.Write((int)beheld.Serial); - m_Stream.Write((short)beheld.Body); - m_Stream.Write((short)beheld.X); - m_Stream.Write((short)beheld.Y); - m_Stream.Write((sbyte)beheld.Z); - m_Stream.Write((byte)beheld.Direction); - m_Stream.Write((short)hue); - m_Stream.Write((byte)beheld.GetPacketFlags()); - m_Stream.Write((byte)Notoriety.Compute(beholder, beheld)); - - for (int i = 0; i < eq.Count; ++i) - { - Item item = eq[i]; - - byte layer = (byte)item.Layer; - - if (!item.Deleted && beholder.CanSee(item) && m_DupedLayers[layer] != m_Version) - { - m_DupedLayers[layer] = m_Version; - - hue = item.Hue; - - if (beheld.SolidHueOverride >= 0) - hue = beheld.SolidHueOverride; - - int itemID = item.ItemID & 0xFFFF; - - m_Stream.Write((int)item.Serial); - m_Stream.Write((ushort)itemID); - m_Stream.Write((byte)layer); - - m_Stream.Write((short)hue); - } - } - - if (beheld.HairItemID > 0) - { - if (m_DupedLayers[(int)Layer.Hair] != m_Version) - { - m_DupedLayers[(int)Layer.Hair] = m_Version; - hue = beheld.HairHue; + public sealed class MobileIncomingSA : Packet + { + private static ThreadLocal m_DupedLayersTL = new ThreadLocal(() => { return new int[256]; }); + private static ThreadLocal m_VersionTL = new ThreadLocal(); - if (beheld.SolidHueOverride >= 0) - hue = beheld.SolidHueOverride; + public Mobile m_Beheld; - int itemID = beheld.HairItemID & 0xFFFF; + public MobileIncomingSA(Mobile beholder, Mobile beheld) : base(0x78) + { + m_Beheld = beheld; - m_Stream.Write((int)HairInfo.FakeSerial(beheld)); - m_Stream.Write((ushort)itemID); - m_Stream.Write((byte)Layer.Hair); + int m_Version = ++m_VersionTL.Value; + int[] m_DupedLayers = m_DupedLayersTL.Value; - m_Stream.Write((short)hue); - } - } + List eq = beheld.Items; + int count = eq.Count; - if (beheld.FacialHairItemID > 0) - { - if (m_DupedLayers[(int)Layer.FacialHair] != m_Version) - { - m_DupedLayers[(int)Layer.FacialHair] = m_Version; - hue = beheld.FacialHairHue; + if (beheld.HairItemID > 0) + count++; + if (beheld.FacialHairItemID > 0) + count++; - if (beheld.SolidHueOverride >= 0) - hue = beheld.SolidHueOverride; + EnsureCapacity(23 + count * 9); - int itemID = beheld.FacialHairItemID & 0xFFFF; + int hue = beheld.Hue; - m_Stream.Write((int)FacialHairInfo.FakeSerial(beheld)); - m_Stream.Write((ushort)itemID); - m_Stream.Write((byte)Layer.FacialHair); + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - m_Stream.Write((short)hue); - } - } + m_Stream.Write(beheld.Serial); + m_Stream.Write((short)beheld.Body); + m_Stream.Write((short)beheld.X); + m_Stream.Write((short)beheld.Y); + m_Stream.Write((sbyte)beheld.Z); + m_Stream.Write((byte)beheld.Direction); + m_Stream.Write((short)hue); + m_Stream.Write((byte)beheld.GetPacketFlags()); + m_Stream.Write((byte)Notoriety.Compute(beholder, beheld)); - m_Stream.Write((int)0); // terminate - } - } + for (int i = 0; i < eq.Count; ++i) + { + Item item = eq[i]; - public sealed class MobileIncomingSA : Packet - { - private static ThreadLocal m_DupedLayersTL = new ThreadLocal(() => {return new int[256];}); - private static ThreadLocal m_VersionTL = new ThreadLocal(); + byte layer = (byte)item.Layer; - public Mobile m_Beheld; + if (!item.Deleted && beholder.CanSee(item) && m_DupedLayers[layer] != m_Version) + { + m_DupedLayers[layer] = m_Version; - public MobileIncomingSA(Mobile beholder, Mobile beheld) : base(0x78) - { - m_Beheld = beheld; + hue = item.Hue; - int m_Version = ++(m_VersionTL.Value); - int[] m_DupedLayers = m_DupedLayersTL.Value; + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - List eq = beheld.Items; - int count = eq.Count; + int itemID = item.ItemID & 0x7FFF; + bool writeHue = hue != 0; - if ( beheld.HairItemID > 0 ) - count++; - if ( beheld.FacialHairItemID > 0 ) - count++; + if (writeHue) + itemID |= 0x8000; - EnsureCapacity( 23 + (count * 9) ); + m_Stream.Write(item.Serial); + m_Stream.Write((ushort)itemID); + m_Stream.Write(layer); - int hue = beheld.Hue; + if (writeHue) + m_Stream.Write((short)hue); + } + } - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; + if (beheld.HairItemID > 0) + if (m_DupedLayers[(int)Layer.Hair] != m_Version) + { + m_DupedLayers[(int)Layer.Hair] = m_Version; + hue = beheld.HairHue; - m_Stream.Write( (int) beheld.Serial ); - m_Stream.Write( (short) beheld.Body ); - m_Stream.Write( (short) beheld.X ); - m_Stream.Write( (short) beheld.Y ); - m_Stream.Write( (sbyte) beheld.Z ); - m_Stream.Write( (byte) beheld.Direction ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (byte) beheld.GetPacketFlags() ); - m_Stream.Write( (byte) Notoriety.Compute( beholder, beheld ) ); + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - for ( int i = 0; i < eq.Count; ++i ) - { - Item item = eq[i]; + int itemID = beheld.HairItemID & 0x7FFF; - byte layer = (byte) item.Layer; + bool writeHue = hue != 0; - if ( !item.Deleted && beholder.CanSee( item ) && m_DupedLayers[layer] != m_Version ) - { - m_DupedLayers[layer] = m_Version; + if (writeHue) + itemID |= 0x8000; - hue = item.Hue; + m_Stream.Write(HairInfo.FakeSerial(beheld)); + m_Stream.Write((ushort)itemID); + m_Stream.Write((byte)Layer.Hair); - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; + if (writeHue) + m_Stream.Write((short)hue); + } - int itemID = item.ItemID & 0x7FFF; - bool writeHue = ( hue != 0 ); + if (beheld.FacialHairItemID > 0) + if (m_DupedLayers[(int)Layer.FacialHair] != m_Version) + { + m_DupedLayers[(int)Layer.FacialHair] = m_Version; + hue = beheld.FacialHairHue; - if ( writeHue ) - itemID |= 0x8000; + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (ushort) itemID ); - m_Stream.Write( (byte) layer ); + int itemID = beheld.FacialHairItemID & 0x7FFF; - if ( writeHue ) - m_Stream.Write( (short) hue ); - } - } + bool writeHue = hue != 0; - if ( beheld.HairItemID > 0 ) - { - if ( m_DupedLayers[(int)Layer.Hair] != m_Version ) - { - m_DupedLayers[(int)Layer.Hair] = m_Version; - hue = beheld.HairHue; + if (writeHue) + itemID |= 0x8000; - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; + m_Stream.Write(FacialHairInfo.FakeSerial(beheld)); + m_Stream.Write((ushort)itemID); + m_Stream.Write((byte)Layer.FacialHair); - int itemID = beheld.HairItemID & 0x7FFF; + if (writeHue) + m_Stream.Write((short)hue); + } - bool writeHue = (hue != 0); + m_Stream.Write(0); // terminate + } + } - if ( writeHue ) - itemID |= 0x8000; + // Pre-7.0.0.0 Mobile Incoming + public sealed class MobileIncomingOld : Packet + { + private static ThreadLocal m_DupedLayersTL = new ThreadLocal(() => { return new int[256]; }); + private static ThreadLocal m_VersionTL = new ThreadLocal(); - m_Stream.Write( (int)HairInfo.FakeSerial( beheld ) ); - m_Stream.Write( (ushort)itemID ); - m_Stream.Write( (byte)Layer.Hair ); + public Mobile m_Beheld; - if ( writeHue ) - m_Stream.Write( (short)hue ); - } - } + public MobileIncomingOld(Mobile beholder, Mobile beheld) : base(0x78) + { + m_Beheld = beheld; - if ( beheld.FacialHairItemID > 0 ) - { - if ( m_DupedLayers[(int)Layer.FacialHair] != m_Version ) - { - m_DupedLayers[(int)Layer.FacialHair] = m_Version; - hue = beheld.FacialHairHue; + int m_Version = ++m_VersionTL.Value; + int[] m_DupedLayers = m_DupedLayersTL.Value; - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; + List eq = beheld.Items; + int count = eq.Count; - int itemID = beheld.FacialHairItemID & 0x7FFF; + if (beheld.HairItemID > 0) + count++; + if (beheld.FacialHairItemID > 0) + count++; - bool writeHue = (hue != 0); + EnsureCapacity(23 + count * 9); - if ( writeHue ) - itemID |= 0x8000; + int hue = beheld.Hue; - m_Stream.Write( (int)FacialHairInfo.FakeSerial( beheld ) ); - m_Stream.Write( (ushort)itemID ); - m_Stream.Write( (byte)Layer.FacialHair ); + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - if ( writeHue ) - m_Stream.Write( (short)hue ); - } - } + m_Stream.Write(beheld.Serial); + m_Stream.Write((short)beheld.Body); + m_Stream.Write((short)beheld.X); + m_Stream.Write((short)beheld.Y); + m_Stream.Write((sbyte)beheld.Z); + m_Stream.Write((byte)beheld.Direction); + m_Stream.Write((short)hue); + m_Stream.Write((byte)beheld.GetOldPacketFlags()); + m_Stream.Write((byte)Notoriety.Compute(beholder, beheld)); - m_Stream.Write( (int) 0 ); // terminate - } - } + for (int i = 0; i < eq.Count; ++i) + { + Item item = eq[i]; - // Pre-7.0.0.0 Mobile Incoming - public sealed class MobileIncomingOld : Packet - { - private static ThreadLocal m_DupedLayersTL = new ThreadLocal(() => {return new int[256];}); - private static ThreadLocal m_VersionTL = new ThreadLocal(); + byte layer = (byte)item.Layer; - public Mobile m_Beheld; + if (!item.Deleted && beholder.CanSee(item) && m_DupedLayers[layer] != m_Version) + { + m_DupedLayers[layer] = m_Version; - public MobileIncomingOld( Mobile beholder, Mobile beheld ) : base( 0x78 ) - { - m_Beheld = beheld; + hue = item.Hue; - int m_Version = ++(m_VersionTL.Value); - int[] m_DupedLayers = m_DupedLayersTL.Value; + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - List eq = beheld.Items; - int count = eq.Count; + int itemID = item.ItemID & 0x7FFF; + bool writeHue = hue != 0; - if ( beheld.HairItemID > 0 ) - count++; - if ( beheld.FacialHairItemID > 0 ) - count++; + if (writeHue) + itemID |= 0x8000; - EnsureCapacity( 23 + (count * 9) ); + m_Stream.Write(item.Serial); + m_Stream.Write((ushort)itemID); + m_Stream.Write(layer); - int hue = beheld.Hue; + if (writeHue) + m_Stream.Write((short)hue); + } + } - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; + if (beheld.HairItemID > 0) + if (m_DupedLayers[(int)Layer.Hair] != m_Version) + { + m_DupedLayers[(int)Layer.Hair] = m_Version; + hue = beheld.HairHue; - m_Stream.Write( (int) beheld.Serial ); - m_Stream.Write( (short) beheld.Body ); - m_Stream.Write( (short) beheld.X ); - m_Stream.Write( (short) beheld.Y ); - m_Stream.Write( (sbyte) beheld.Z ); - m_Stream.Write( (byte) beheld.Direction ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (byte) beheld.GetOldPacketFlags() ); - m_Stream.Write( (byte) Notoriety.Compute( beholder, beheld ) ); + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; - for ( int i = 0; i < eq.Count; ++i ) - { - Item item = eq[i]; + int itemID = beheld.HairItemID & 0x7FFF; - byte layer = (byte) item.Layer; + bool writeHue = hue != 0; - if ( !item.Deleted && beholder.CanSee( item ) && m_DupedLayers[layer] != m_Version ) - { - m_DupedLayers[layer] = m_Version; + if (writeHue) + itemID |= 0x8000; - hue = item.Hue; - - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; - - int itemID = item.ItemID & 0x7FFF; - bool writeHue = ( hue != 0 ); - - if ( writeHue ) - itemID |= 0x8000; - - m_Stream.Write( (int) item.Serial ); - m_Stream.Write( (ushort) itemID ); - m_Stream.Write( (byte) layer ); - - if ( writeHue ) - m_Stream.Write( (short) hue ); - } - } - - if ( beheld.HairItemID > 0 ) - { - if ( m_DupedLayers[(int)Layer.Hair] != m_Version ) - { - m_DupedLayers[(int)Layer.Hair] = m_Version; - hue = beheld.HairHue; - - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; - - int itemID = beheld.HairItemID & 0x7FFF; - - bool writeHue = (hue != 0); - - if ( writeHue ) - itemID |= 0x8000; - - m_Stream.Write( (int)HairInfo.FakeSerial( beheld ) ); - m_Stream.Write( (ushort)itemID ); - m_Stream.Write( (byte)Layer.Hair ); - - if ( writeHue ) - m_Stream.Write( (short)hue ); - } - } - - if ( beheld.FacialHairItemID > 0 ) - { - if ( m_DupedLayers[(int)Layer.FacialHair] != m_Version ) - { - m_DupedLayers[(int)Layer.FacialHair] = m_Version; - hue = beheld.FacialHairHue; - - if ( beheld.SolidHueOverride >= 0 ) - hue = beheld.SolidHueOverride; - - int itemID = beheld.FacialHairItemID & 0x7FFF; - - bool writeHue = (hue != 0); - - if ( writeHue ) - itemID |= 0x8000; - - m_Stream.Write( (int)FacialHairInfo.FakeSerial( beheld ) ); - m_Stream.Write( (ushort)itemID ); - m_Stream.Write( (byte)Layer.FacialHair ); - - if ( writeHue ) - m_Stream.Write( (short)hue ); - } - } - - m_Stream.Write( (int) 0 ); // terminate - } - } - - public sealed class AsciiMessage : Packet - { - public AsciiMessage( Serial serial, int graphic, MessageType type, int hue, int font, string name, string text ) : base( 0x1C ) - { - if ( name == null ) - name = ""; - - if ( text == null ) - text = ""; - - if ( hue == 0 ) - hue = 0x3B2; - - EnsureCapacity( 45 + text.Length ); - - m_Stream.Write( (int) serial ); - m_Stream.Write( (short) graphic ); - m_Stream.Write( (byte) type ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (short) font ); - m_Stream.WriteAsciiFixed( name, 30 ); - m_Stream.WriteAsciiNull( text ); - } - } - - public sealed class UnicodeMessage : Packet - { - public UnicodeMessage( Serial serial, int graphic, MessageType type, int hue, int font, string lang, string name, string text ) : base( 0xAE ) - { - if ( string.IsNullOrEmpty( lang ) ) lang = "ENU"; - if ( name == null ) name = ""; - if ( text == null ) text = ""; - - if ( hue == 0 ) - hue = 0x3B2; - - EnsureCapacity( 50 + (text.Length * 2) ); - - m_Stream.Write( (int) serial ); - m_Stream.Write( (short) graphic ); - m_Stream.Write( (byte) type ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (short) font ); - m_Stream.WriteAsciiFixed( lang, 4 ); - m_Stream.WriteAsciiFixed( name, 30 ); - m_Stream.WriteBigUniNull( text ); - } - } - - public sealed class PingAck : Packet - { - private static PingAck[] m_Cache = new PingAck[0x100]; - - public static PingAck Instantiate( byte ping ) - { - PingAck p = m_Cache[ping]; - - if ( p == null ) - { - m_Cache[ping] = p = new PingAck( ping ); - p.SetStatic(); - } - - return p; - } - - public PingAck( byte ping ) : base( 0x73, 2 ) - { - m_Stream.Write( ping ); - } - } - - public sealed class MovementRej : Packet - { - public MovementRej( int seq, Mobile m ) : base( 0x21, 8 ) - { - m_Stream.Write( (byte) seq ); - m_Stream.Write( (short) m.X ); - m_Stream.Write( (short) m.Y ); - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (sbyte) m.Z ); - } - } - - public sealed class MovementAck : Packet - { - private static MovementAck[][] m_Cache = new MovementAck[8][] - { - new MovementAck[256], - new MovementAck[256], - new MovementAck[256], - new MovementAck[256], - new MovementAck[256], - new MovementAck[256], - new MovementAck[256], - new MovementAck[256] - }; - - public static MovementAck Instantiate( int seq, Mobile m ) - { - int noto = Notoriety.Compute( m, m ); - - MovementAck p = m_Cache[noto][seq]; - - if ( p == null ) - { - m_Cache[noto][seq] = p = new MovementAck( seq, noto ); - p.SetStatic(); - } - - return p; - } - - private MovementAck( int seq, int noto ) : base( 0x22, 3 ) - { - m_Stream.Write( (byte) seq ); - m_Stream.Write( (byte) noto ); - } - } - - public sealed class LoginConfirm : Packet - { - public LoginConfirm( Mobile m ) : base( 0x1B, 37 ) - { - m_Stream.Write( (int) m.Serial ); - m_Stream.Write( (int) 0 ); - m_Stream.Write( (short) m.Body ); - m_Stream.Write( (short) m.X ); - m_Stream.Write( (short) m.Y ); - m_Stream.Write( (short) m.Z ); - m_Stream.Write( (byte) m.Direction ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (int) -1 ); - - Map map = m.Map; - - if ( map == null || map == Map.Internal ) - map = m.LogoutMap; - - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) 0 ); - m_Stream.Write( (short) (map?.Width ?? 6144) ); - m_Stream.Write( (short) (map?.Height ?? 4096) ); - - m_Stream.Fill(); - } - } - - public sealed class LoginComplete : Packet - { - public static readonly Packet Instance = SetStatic( new LoginComplete() ); - - public LoginComplete() : base( 0x55, 1 ) - { - } - } - - public sealed class CityInfo - { - private Point3D m_Location; - - public CityInfo( string city, string building, int description, int x, int y, int z, Map m ) - { - City = city; - Building = building; - Description = description; - m_Location = new Point3D( x, y, z ); - Map = m; - } - - public CityInfo( string city, string building, int x, int y, int z, Map m ) : this( city, building, 0, x, y, z, m ) - { - } - - public CityInfo( string city, string building, int description, int x, int y, int z ) : this( city, building, description, x, y, z, Map.Trammel ) - { - } - - public CityInfo( string city, string building, int x, int y, int z ) : this( city, building, 0, x, y, z, Map.Trammel ) - { - } - - public string City { get; set; } - - public string Building { get; set; } - - public int Description { get; set; } - - public int X - { - get => m_Location.X; - set => m_Location.X = value; - } - - public int Y - { - get => m_Location.Y; - set => m_Location.Y = value; - } - - public int Z - { - get => m_Location.Z; - set => m_Location.Z = value; - } - - public Point3D Location - { - get => m_Location; - set => m_Location = value; - } - - public Map Map { get; set; } - } - - public sealed class CharacterListUpdate : Packet - { - public CharacterListUpdate( IAccount a ) : base( 0x86 ) - { - EnsureCapacity( 4 + (a.Length * 60) ); - - int highSlot = -1; - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] != null ) - highSlot = i; - } - - int count = Math.Max( Math.Max( highSlot + 1, a.Limit ), 5 ); - - m_Stream.Write( (byte) count ); - - for ( int i = 0; i < count; ++i ) - { - Mobile m = a[i]; - - if ( m != null ) - { - m_Stream.WriteAsciiFixed( m.Name, 30 ); - m_Stream.Fill( 30 ); // password - } - else - { - m_Stream.Fill( 60 ); - } - } - } - } - - [Flags] - public enum ThirdPartyFeature : ulong - { - FilterWeather = 1 << 0, - FilterLight = 1 << 1, - - SmartTarget = 1 << 2, - RangedTarget = 1 << 3, - - AutoOpenDoors = 1 << 4, - - DequipOnCast = 1 << 5, - AutoPotionEquip = 1 << 6, - - ProtectHeals = 1 << 7, - - LoopedMacros = 1 << 8, - - UseOnceAgent = 1 << 9, - RestockAgent = 1 << 10, - SellAgent = 1 << 11, - BuyAgent = 1 << 12, - - PotionHotkeys = 1 << 13, - - RandomTargets = 1 << 14, - ClosestTargets = 1 << 15, // All closest target hotkeys - OverheadHealth = 1 << 16, // Health and Mana/Stam messages shown over player's heads - - AutolootAgent = 1 << 17, - BoneCutterAgent = 1 << 18, - AdvancedMacros = 1 << 19, - AutoRemount = 1 << 20, - AutoBandage = 1 << 21, - EnemyTargetShare = 1 << 22, - FilterSeason = 1 << 23, - SpellTargetShare = 1 << 24, - - All = ulong.MaxValue - } - - public static class FeatureProtection - { - public static ThirdPartyFeature DisabledFeatures { get; private set; } = 0; - - public static void Disable( ThirdPartyFeature feature ) - { - SetDisabled( feature, true ); - } - - public static void Enable( ThirdPartyFeature feature ) - { - SetDisabled( feature, false ); - } - - public static void SetDisabled( ThirdPartyFeature feature, bool value ) - { - if ( value ) - DisabledFeatures |= feature; - else - DisabledFeatures &= ~feature; - } - } - - public sealed class CharacterList : Packet - { - public CharacterList( IAccount a, CityInfo[] info ) : base( 0xA9 ) - { - EnsureCapacity( 11 + (a.Length * 60) + (info.Length * 89) ); - - int highSlot = -1; - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] != null ) - highSlot = i; - } - - int count = Math.Max( Math.Max( highSlot + 1, a.Limit ), 5 ); - - m_Stream.Write( (byte) count ); - - for ( int i = 0; i < count; ++i ) - { - if ( a[i] != null ) - { - m_Stream.WriteAsciiFixed( a[i].Name, 30 ); - m_Stream.Fill( 30 ); // password - } - else - { - m_Stream.Fill( 60 ); - } - } - - m_Stream.Write( (byte) info.Length ); - - for ( int i = 0; i < info.Length; ++i ) - { - CityInfo ci = info[i]; - - m_Stream.Write( (byte) i ); - m_Stream.WriteAsciiFixed( ci.City, 32 ); - m_Stream.WriteAsciiFixed( ci.Building, 32 ); - m_Stream.Write( (int) ci.X ); - m_Stream.Write( (int) ci.Y ); - m_Stream.Write( (int) ci.Z ); - m_Stream.Write( (int) ci.Map.MapID ); - m_Stream.Write( (int) ci.Description ); - m_Stream.Write( (int) 0 ); - } - - CharacterListFlags flags = ExpansionInfo.CoreExpansion.CharacterListFlags; - - if ( count > 6 ) - flags |= (CharacterListFlags.SeventhCharacterSlot | CharacterListFlags.SixthCharacterSlot); // 7th Character Slot - TODO: Is SixthCharacterSlot Required? - else if ( count == 6 ) - flags |= CharacterListFlags.SixthCharacterSlot; // 6th Character Slot - else if ( a.Limit == 1 ) - flags |= (CharacterListFlags.SlotLimit & CharacterListFlags.OneCharacterSlot); // Limit Characters & One Character - - m_Stream.Write( (int)(flags | AdditionalFlags) ); // Additional Flags - - m_Stream.Write( (short) -1 ); - - ThirdPartyFeature disabled = FeatureProtection.DisabledFeatures; - - if ( disabled != 0 ) - { - if ( m_MD5Provider == null ) - m_MD5Provider = new System.Security.Cryptography.MD5CryptoServiceProvider(); - - m_Stream.UnderlyingStream.Flush(); - - byte[] hashCode = m_MD5Provider.ComputeHash( m_Stream.UnderlyingStream.GetBuffer(), 0, (int) m_Stream.UnderlyingStream.Length ); - byte[] buffer = new byte[28]; - - for ( int i = 0; i < count; ++i ) - { - Utility.RandomBytes( buffer ); - - m_Stream.Seek( 35 + ( i * 60 ), SeekOrigin.Begin ); - m_Stream.Write( buffer, 0, buffer.Length ); - } - - m_Stream.Seek( 35, SeekOrigin.Begin ); - m_Stream.Write( (int) ((long)disabled>>32) ); - m_Stream.Write( (int) disabled ); - - m_Stream.Seek( 95, SeekOrigin.Begin ); - m_Stream.Write( hashCode, 0, hashCode.Length ); - } - } - - private static System.Security.Cryptography.MD5CryptoServiceProvider m_MD5Provider; - - public static CharacterListFlags AdditionalFlags { get; set; } - } - - public sealed class CharacterListOld : Packet - { - public CharacterListOld( IAccount a, CityInfo[] info ) : base( 0xA9 ) - { - EnsureCapacity( 9 + (a.Length * 60) + (info.Length * 63) ); - - int highSlot = -1; - - for ( int i = 0; i < a.Length; ++i ) - { - if ( a[i] != null ) - highSlot = i; - } - - int count = Math.Max( Math.Max( highSlot + 1, a.Limit ), 5 ); - - m_Stream.Write( (byte) count ); - - for ( int i = 0; i < count; ++i ) - { - if ( a[i] != null ) - { - m_Stream.WriteAsciiFixed( a[i].Name, 30 ); - m_Stream.Fill( 30 ); // password - } - else - { - m_Stream.Fill( 60 ); - } - } - - m_Stream.Write( (byte) info.Length ); - - for ( int i = 0; i < info.Length; ++i ) - { - CityInfo ci = info[i]; - - m_Stream.Write( (byte) i ); - m_Stream.WriteAsciiFixed( ci.City, 31 ); - m_Stream.WriteAsciiFixed( ci.Building, 31 ); - } - - CharacterListFlags flags = ExpansionInfo.CoreExpansion.CharacterListFlags; - - if ( count > 6 ) - flags |= (CharacterListFlags.SeventhCharacterSlot | CharacterListFlags.SixthCharacterSlot); // 7th Character Slot - TODO: Is SixthCharacterSlot Required? - else if ( count == 6 ) - flags |= CharacterListFlags.SixthCharacterSlot; // 6th Character Slot - else if ( a.Limit == 1 ) - flags |= (CharacterListFlags.SlotLimit & CharacterListFlags.OneCharacterSlot); // Limit Characters & One Character - - m_Stream.Write( (int)(flags | CharacterList.AdditionalFlags) ); // Additional Flags - - ThirdPartyFeature disabled = FeatureProtection.DisabledFeatures; - - if ( disabled != 0 ) - { - if ( m_MD5Provider == null ) - m_MD5Provider = new System.Security.Cryptography.MD5CryptoServiceProvider(); - - m_Stream.UnderlyingStream.Flush(); - - byte[] hashCode = m_MD5Provider.ComputeHash( m_Stream.UnderlyingStream.GetBuffer(), 0, (int) m_Stream.UnderlyingStream.Length ); - byte[] buffer = new byte[28]; - - for ( int i = 0; i < count; ++i ) - { - Utility.RandomBytes( buffer ); - - m_Stream.Seek( 35 + ( i * 60 ), SeekOrigin.Begin ); - m_Stream.Write( buffer, 0, buffer.Length ); - } - - m_Stream.Seek( 35, SeekOrigin.Begin ); - m_Stream.Write( (int) ((long)disabled>>32) ); - m_Stream.Write( (int) disabled ); - - m_Stream.Seek( 95, SeekOrigin.Begin ); - m_Stream.Write( hashCode, 0, hashCode.Length ); - } - } - - private static System.Security.Cryptography.MD5CryptoServiceProvider m_MD5Provider; - } - - public sealed class ClearWeaponAbility : Packet - { - public static readonly Packet Instance = SetStatic( new ClearWeaponAbility() ); - - public ClearWeaponAbility() : base( 0xBF ) - { - EnsureCapacity( 5 ); - - m_Stream.Write( (short) 0x21 ); - } - } - - public enum ALRReason : byte - { - Invalid = 0x00, - InUse = 0x01, - Blocked = 0x02, - BadPass = 0x03, - Idle = 0xFE, - BadComm = 0xFF - } - - public sealed class AccountLoginRej : Packet - { - public AccountLoginRej( ALRReason reason ) : base( 0x82, 2 ) - { - m_Stream.Write( (byte)reason ); - } - } - - public enum AffixType : byte - { - Append = 0x00, - Prepend = 0x01, - System = 0x02 - } - - public sealed class MessageLocalizedAffix : Packet - { - public MessageLocalizedAffix( Serial serial, int graphic, MessageType messageType, int hue, int font, int number, string name, AffixType affixType, string affix, string args ) : base( 0xCC ) - { - if ( name == null ) name = ""; - if ( affix == null ) affix = ""; - if ( args == null ) args = ""; - - if ( hue == 0 ) - hue = 0x3B2; - - EnsureCapacity( 52 + affix.Length + (args.Length * 2) ); - - m_Stream.Write( (int) serial ); - m_Stream.Write( (short) graphic ); - m_Stream.Write( (byte) messageType ); - m_Stream.Write( (short) hue ); - m_Stream.Write( (short) font ); - m_Stream.Write( (int) number ); - m_Stream.Write( (byte) affixType ); - m_Stream.WriteAsciiFixed( name, 30 ); - m_Stream.WriteAsciiNull( affix ); - m_Stream.WriteBigUniNull( args ); - } - } - - public sealed class ServerInfo - { - public string Name { get; set; } - - public int FullPercent { get; set; } - - public int TimeZone { get; set; } - - public IPEndPoint Address { get; set; } - - public ServerInfo( string name, int fullPercent, TimeZone tz, IPEndPoint address ) - { - Name = name; - FullPercent = fullPercent; - TimeZone = tz.GetUtcOffset( DateTime.Now ).Hours; - Address = address; - } - } - - public sealed class FollowMessage : Packet - { - public FollowMessage( Serial serial1, Serial serial2 ) : base( 0x15, 9 ) - { - m_Stream.Write( (int) serial1 ); - m_Stream.Write( (int) serial2 ); - } - } - - public sealed class AccountLoginAck : Packet - { - public AccountLoginAck( ServerInfo[] info ) : base( 0xA8 ) - { - EnsureCapacity( 6 + (info.Length * 40) ); - - m_Stream.Write( (byte) 0x5D ); // Unknown - - m_Stream.Write( (ushort) info.Length ); - - for ( int i = 0; i < info.Length; ++i ) - { - ServerInfo si = info[i]; - - m_Stream.Write( (ushort) i ); - m_Stream.WriteAsciiFixed( si.Name, 32 ); - m_Stream.Write( (byte) si.FullPercent ); - m_Stream.Write( (sbyte) si.TimeZone ); - m_Stream.Write( (int) Utility.GetAddressValue( si.Address.Address ) ); - } - } - } - - public sealed class DisplaySignGump : Packet - { - public DisplaySignGump( Serial serial, int gumpID, string unknown, string caption ) : base( 0x8B ) - { - if ( unknown == null ) unknown = ""; - if ( caption == null ) caption = ""; - - EnsureCapacity( 16 + unknown.Length + caption.Length ); - - m_Stream.Write( (int) serial ); - m_Stream.Write( (short) gumpID ); - m_Stream.Write( (short) (unknown.Length) ); - m_Stream.WriteAsciiFixed( unknown, unknown.Length ); - m_Stream.Write( (short) (caption.Length + 1) ); - m_Stream.WriteAsciiFixed( caption, caption.Length + 1 ); - } - } - - public sealed class GodModeReply : Packet - { - public GodModeReply( bool reply ) : base( 0x2B, 2 ) - { - m_Stream.Write( reply ); - } - } - - public sealed class PlayServerAck : Packet - { - internal static int m_AuthID = -1; - - public PlayServerAck( ServerInfo si ) : base( 0x8C, 11 ) - { - int addr = Utility.GetAddressValue( si.Address.Address ); - - m_Stream.Write( (byte) addr ); - m_Stream.Write( (byte)(addr >> 8) ); - m_Stream.Write( (byte)(addr >> 16) ); - m_Stream.Write( (byte)(addr >> 24) ); - - m_Stream.Write( (short) si.Address.Port ); - m_Stream.Write( (int) m_AuthID ); - } - } - - public abstract class Packet - { - [Flags] - private enum State - { - Inactive = 0x00, - Static = 0x01, - Acquired = 0x02, - Accessed = 0x04, - Buffered = 0x08, - Warned = 0x10 - } - - protected PacketWriter m_Stream; - private int m_Length; - private State m_State; - - public int PacketID { get; } - - protected Packet( int packetID ) - { - PacketID = packetID; - - if (Core.Profiling) { - PacketSendProfile prof = PacketSendProfile.Acquire( GetType() ); - prof.Increment(); - } - } - - public void EnsureCapacity( int length ) - { - m_Stream = PacketWriter.CreateInstance( length );// new PacketWriter( length ); - m_Stream.Write( (byte) PacketID ); - m_Stream.Write( (short) 0 ); - } - - protected Packet( int packetID, int length ) - { - PacketID = packetID; - m_Length = length; - - m_Stream = PacketWriter.CreateInstance( length );// new PacketWriter( length ); - m_Stream.Write( ( byte ) packetID ); - - if (Core.Profiling) { - PacketSendProfile prof = PacketSendProfile.Acquire( GetType() ); - prof.Increment(); - } - } - - public PacketWriter UnderlyingStream => m_Stream; - - private const int CompressorBufferSize = 0x10000; - private static BufferPool m_CompressorBuffers = new BufferPool("Compressor", 4, CompressorBufferSize); - - private const int BufferSize = 4096; - private static BufferPool m_Buffers = new BufferPool( "Compressed", 16, BufferSize ); - - public static Packet SetStatic( Packet p ) - { - p.SetStatic(); - return p; - } - - public static Packet Acquire( Packet p ) - { - p.Acquire(); - return p; - } - - public static void Release( ref ObjectPropertyList p ) - { - p?.Release(); - - p = null; - } - - public static void Release( ref RemoveItem p ) - { - p?.Release(); - - p = null; - } - - public static void Release( ref RemoveMobile p ) - { - p?.Release(); - - p = null; - } - - public static void Release( ref OPLInfo p ) - { - p?.Release(); - - p = null; - } - - public static void Release( ref Packet p ) - { - p?.Release(); - - p = null; - } - - public static void Release( Packet p ) - { - p?.Release(); - } - - public void SetStatic() - { - m_State |= State.Static | State.Acquired; - } - - public void Acquire() - { - m_State |= State.Acquired; - } - - public void OnSend() - { - Core.Set(); - - lock (this) { - if ((m_State & (State.Acquired | State.Static)) == 0) - Free(); - } - } - - private void Free() - { - if ( m_CompiledBuffer == null ) - return; - - if ((m_State & State.Buffered) != 0) - m_Buffers.ReleaseBuffer(m_CompiledBuffer); - - m_State &= ~(State.Static | State.Acquired | State.Buffered); - - m_CompiledBuffer = null; - } - - public void Release() - { - if ((m_State & State.Acquired) != 0) - Free(); - } - - private byte[] m_CompiledBuffer; - private int m_CompiledLength; - - public byte[] Compile( bool compress, out int length ) - { - lock (this) - { - if (m_CompiledBuffer == null) - { - if ((m_State & State.Accessed) == 0) - { - m_State |= State.Accessed; - } - else - { - if ((m_State & State.Warned) == 0) - { - m_State |= State.Warned; - - try - { - using (StreamWriter op = new StreamWriter("net_opt.log", true)) - { - op.WriteLine("Redundant compile for packet {0}, use Acquire() and Release()", GetType()); - op.WriteLine(new System.Diagnostics.StackTrace()); - } - } - catch - { - } - } - - m_CompiledBuffer = new byte[0]; - m_CompiledLength = 0; - - length = m_CompiledLength; - return m_CompiledBuffer; - } - - InternalCompile(compress); - } - - length = m_CompiledLength; - return m_CompiledBuffer; - } - } - - private void InternalCompile( bool compress ) - { - if ( m_Length == 0 ) - { - long streamLen = m_Stream.Length; - - m_Stream.Seek( 1, SeekOrigin.Begin ); - m_Stream.Write( (ushort) streamLen ); - } - else if ( m_Stream.Length != m_Length ) - { - int diff = (int)m_Stream.Length - m_Length; - - Console.WriteLine( "Packet: 0x{0:X2}: Bad packet length! ({1}{2} bytes)", PacketID, diff >= 0 ? "+" : "", diff ); - } - - MemoryStream ms = m_Stream.UnderlyingStream; - - m_CompiledBuffer = ms.GetBuffer(); - int length = (int)ms.Length; - - if ( compress ) { - byte[] buffer; - lock (m_CompressorBuffers) - buffer = m_CompressorBuffers.AcquireBuffer(); - - Compression.Compress(m_CompiledBuffer, 0, length, buffer, ref length); - - if (length <= 0) { - Console.WriteLine("Warning: Compression buffer overflowed on packet 0x{0:X2} ('{1}') (length={2})", PacketID, GetType().Name, length); - using (StreamWriter op = new StreamWriter("compression_overflow.log", true)) - { - op.WriteLine("{0} Warning: Compression buffer overflowed on packet 0x{1:X2} ('{2}') (length={3})", DateTime.UtcNow, PacketID, GetType().Name, length); - op.WriteLine(new System.Diagnostics.StackTrace()); - } - } else { - m_CompiledLength = length; - - if (length > BufferSize || (m_State & State.Static) != 0) { - m_CompiledBuffer = new byte[length]; - } else { - lock (m_Buffers) - m_CompiledBuffer = m_Buffers.AcquireBuffer(); - m_State |= State.Buffered; - } - - Buffer.BlockCopy(buffer, 0, m_CompiledBuffer, 0, length); - - lock (m_CompressorBuffers) - m_CompressorBuffers.ReleaseBuffer(buffer); - } - } else if (length > 0) { - byte[] old = m_CompiledBuffer; - m_CompiledLength = length; - - if ( length > BufferSize || (m_State & State.Static) != 0 ) { - m_CompiledBuffer = new byte[length]; - } else { - lock (m_Buffers) - m_CompiledBuffer = m_Buffers.AcquireBuffer(); - m_State |= State.Buffered; - } - - Buffer.BlockCopy(old, 0, m_CompiledBuffer, 0, length); - } - - PacketWriter.ReleaseInstance( m_Stream ); - m_Stream = null; - } - } -} + m_Stream.Write(HairInfo.FakeSerial(beheld)); + m_Stream.Write((ushort)itemID); + m_Stream.Write((byte)Layer.Hair); + + if (writeHue) + m_Stream.Write((short)hue); + } + + if (beheld.FacialHairItemID > 0) + if (m_DupedLayers[(int)Layer.FacialHair] != m_Version) + { + m_DupedLayers[(int)Layer.FacialHair] = m_Version; + hue = beheld.FacialHairHue; + + if (beheld.SolidHueOverride >= 0) + hue = beheld.SolidHueOverride; + + int itemID = beheld.FacialHairItemID & 0x7FFF; + + bool writeHue = hue != 0; + + if (writeHue) + itemID |= 0x8000; + + m_Stream.Write(FacialHairInfo.FakeSerial(beheld)); + m_Stream.Write((ushort)itemID); + m_Stream.Write((byte)Layer.FacialHair); + + if (writeHue) + m_Stream.Write((short)hue); + } + + m_Stream.Write(0); // terminate + } + } + + public sealed class AsciiMessage : Packet + { + public AsciiMessage(Serial serial, int graphic, MessageType type, int hue, int font, string name, string text) : + base(0x1C) + { + if (name == null) + name = ""; + + if (text == null) + text = ""; + + if (hue == 0) + hue = 0x3B2; + + EnsureCapacity(45 + text.Length); + + m_Stream.Write(serial); + m_Stream.Write((short)graphic); + m_Stream.Write((byte)type); + m_Stream.Write((short)hue); + m_Stream.Write((short)font); + m_Stream.WriteAsciiFixed(name, 30); + m_Stream.WriteAsciiNull(text); + } + } + + public sealed class UnicodeMessage : Packet + { + public UnicodeMessage(Serial serial, int graphic, MessageType type, int hue, int font, string lang, string name, + string text) : base(0xAE) + { + if (string.IsNullOrEmpty(lang)) lang = "ENU"; + if (name == null) name = ""; + if (text == null) text = ""; + + if (hue == 0) + hue = 0x3B2; + + EnsureCapacity(50 + text.Length * 2); + + m_Stream.Write(serial); + m_Stream.Write((short)graphic); + m_Stream.Write((byte)type); + m_Stream.Write((short)hue); + m_Stream.Write((short)font); + m_Stream.WriteAsciiFixed(lang, 4); + m_Stream.WriteAsciiFixed(name, 30); + m_Stream.WriteBigUniNull(text); + } + } + + public sealed class PingAck : Packet + { + private static PingAck[] m_Cache = new PingAck[0x100]; + + public PingAck(byte ping) : base(0x73, 2) + { + m_Stream.Write(ping); + } + + public static PingAck Instantiate(byte ping) + { + PingAck p = m_Cache[ping]; + + if (p == null) + { + m_Cache[ping] = p = new PingAck(ping); + p.SetStatic(); + } + + return p; + } + } + + public sealed class MovementRej : Packet + { + public MovementRej(int seq, Mobile m) : base(0x21, 8) + { + m_Stream.Write((byte)seq); + m_Stream.Write((short)m.X); + m_Stream.Write((short)m.Y); + m_Stream.Write((byte)m.Direction); + m_Stream.Write((sbyte)m.Z); + } + } + + public sealed class MovementAck : Packet + { + private static MovementAck[][] m_Cache = new MovementAck[8][] + { + new MovementAck[256], + new MovementAck[256], + new MovementAck[256], + new MovementAck[256], + new MovementAck[256], + new MovementAck[256], + new MovementAck[256], + new MovementAck[256] + }; + + private MovementAck(int seq, int noto) : base(0x22, 3) + { + m_Stream.Write((byte)seq); + m_Stream.Write((byte)noto); + } + + public static MovementAck Instantiate(int seq, Mobile m) + { + int noto = Notoriety.Compute(m, m); + + MovementAck p = m_Cache[noto][seq]; + + if (p == null) + { + m_Cache[noto][seq] = p = new MovementAck(seq, noto); + p.SetStatic(); + } + + return p; + } + } + + public sealed class LoginConfirm : Packet + { + public LoginConfirm(Mobile m) : base(0x1B, 37) + { + m_Stream.Write(m.Serial); + m_Stream.Write(0); + m_Stream.Write((short)m.Body); + m_Stream.Write((short)m.X); + m_Stream.Write((short)m.Y); + m_Stream.Write((short)m.Z); + m_Stream.Write((byte)m.Direction); + m_Stream.Write((byte)0); + m_Stream.Write(-1); + + Map map = m.Map; + + if (map == null || map == Map.Internal) + map = m.LogoutMap; + + m_Stream.Write((short)0); + m_Stream.Write((short)0); + m_Stream.Write((short)(map?.Width ?? 6144)); + m_Stream.Write((short)(map?.Height ?? 4096)); + + m_Stream.Fill(); + } + } + + public sealed class LoginComplete : Packet + { + public static readonly Packet Instance = SetStatic(new LoginComplete()); + + public LoginComplete() : base(0x55, 1) + { + } + } + + public sealed class CityInfo + { + private Point3D m_Location; + + public CityInfo(string city, string building, int description, int x, int y, int z, Map m) + { + City = city; + Building = building; + Description = description; + m_Location = new Point3D(x, y, z); + Map = m; + } + + public CityInfo(string city, string building, int x, int y, int z, Map m) : this(city, building, 0, x, y, z, m) + { + } + + public CityInfo(string city, string building, int description, int x, int y, int z) : this(city, building, + description, x, y, z, Map.Trammel) + { + } + + public CityInfo(string city, string building, int x, int y, int z) : this(city, building, 0, x, y, z, Map.Trammel) + { + } + + public string City{ get; set; } + + public string Building{ get; set; } + + public int Description{ get; set; } + + public int X + { + get => m_Location.X; + set => m_Location.X = value; + } + + public int Y + { + get => m_Location.Y; + set => m_Location.Y = value; + } + + public int Z + { + get => m_Location.Z; + set => m_Location.Z = value; + } + + public Point3D Location + { + get => m_Location; + set => m_Location = value; + } + + public Map Map{ get; set; } + } + + public sealed class CharacterListUpdate : Packet + { + public CharacterListUpdate(IAccount a) : base(0x86) + { + EnsureCapacity(4 + a.Length * 60); + + int highSlot = -1; + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null) + highSlot = i; + + int count = Math.Max(Math.Max(highSlot + 1, a.Limit), 5); + + m_Stream.Write((byte)count); + + for (int i = 0; i < count; ++i) + { + Mobile m = a[i]; + + if (m != null) + { + m_Stream.WriteAsciiFixed(m.Name, 30); + m_Stream.Fill(30); // password + } + else + { + m_Stream.Fill(60); + } + } + } + } + + [Flags] + public enum ThirdPartyFeature : ulong + { + FilterWeather = 1 << 0, + FilterLight = 1 << 1, + + SmartTarget = 1 << 2, + RangedTarget = 1 << 3, + + AutoOpenDoors = 1 << 4, + + DequipOnCast = 1 << 5, + AutoPotionEquip = 1 << 6, + + ProtectHeals = 1 << 7, + + LoopedMacros = 1 << 8, + + UseOnceAgent = 1 << 9, + RestockAgent = 1 << 10, + SellAgent = 1 << 11, + BuyAgent = 1 << 12, + + PotionHotkeys = 1 << 13, + + RandomTargets = 1 << 14, + ClosestTargets = 1 << 15, // All closest target hotkeys + OverheadHealth = 1 << 16, // Health and Mana/Stam messages shown over player's heads + + AutolootAgent = 1 << 17, + BoneCutterAgent = 1 << 18, + AdvancedMacros = 1 << 19, + AutoRemount = 1 << 20, + AutoBandage = 1 << 21, + EnemyTargetShare = 1 << 22, + FilterSeason = 1 << 23, + SpellTargetShare = 1 << 24, + + All = ulong.MaxValue + } + + public static class FeatureProtection + { + public static ThirdPartyFeature DisabledFeatures{ get; private set; } = 0; + + public static void Disable(ThirdPartyFeature feature) + { + SetDisabled(feature, true); + } + + public static void Enable(ThirdPartyFeature feature) + { + SetDisabled(feature, false); + } + + public static void SetDisabled(ThirdPartyFeature feature, bool value) + { + if (value) + DisabledFeatures |= feature; + else + DisabledFeatures &= ~feature; + } + } + + public sealed class CharacterList : Packet + { + private static MD5CryptoServiceProvider m_MD5Provider; + + public CharacterList(IAccount a, CityInfo[] info) : base(0xA9) + { + EnsureCapacity(11 + a.Length * 60 + info.Length * 89); + + int highSlot = -1; + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null) + highSlot = i; + + int count = Math.Max(Math.Max(highSlot + 1, a.Limit), 5); + + m_Stream.Write((byte)count); + + for (int i = 0; i < count; ++i) + if (a[i] != null) + { + m_Stream.WriteAsciiFixed(a[i].Name, 30); + m_Stream.Fill(30); // password + } + else + { + m_Stream.Fill(60); + } + + m_Stream.Write((byte)info.Length); + + for (int i = 0; i < info.Length; ++i) + { + CityInfo ci = info[i]; + + m_Stream.Write((byte)i); + m_Stream.WriteAsciiFixed(ci.City, 32); + m_Stream.WriteAsciiFixed(ci.Building, 32); + m_Stream.Write(ci.X); + m_Stream.Write(ci.Y); + m_Stream.Write(ci.Z); + m_Stream.Write(ci.Map.MapID); + m_Stream.Write(ci.Description); + m_Stream.Write(0); + } + + CharacterListFlags flags = ExpansionInfo.CoreExpansion.CharacterListFlags; + + if (count > 6) + flags |= CharacterListFlags.SeventhCharacterSlot | + CharacterListFlags.SixthCharacterSlot; // 7th Character Slot - TODO: Is SixthCharacterSlot Required? + else if (count == 6) + flags |= CharacterListFlags.SixthCharacterSlot; // 6th Character Slot + else if (a.Limit == 1) + flags |= CharacterListFlags.SlotLimit & + CharacterListFlags.OneCharacterSlot; // Limit Characters & One Character + + m_Stream.Write((int)(flags | AdditionalFlags)); // Additional Flags + + m_Stream.Write((short)-1); + + ThirdPartyFeature disabled = FeatureProtection.DisabledFeatures; + + if (disabled != 0) + { + if (m_MD5Provider == null) + m_MD5Provider = new MD5CryptoServiceProvider(); + + m_Stream.UnderlyingStream.Flush(); + + byte[] hashCode = m_MD5Provider.ComputeHash(m_Stream.UnderlyingStream.GetBuffer(), 0, + (int)m_Stream.UnderlyingStream.Length); + byte[] buffer = new byte[28]; + + for (int i = 0; i < count; ++i) + { + Utility.RandomBytes(buffer); + + m_Stream.Seek(35 + i * 60, SeekOrigin.Begin); + m_Stream.Write(buffer, 0, buffer.Length); + } + + m_Stream.Seek(35, SeekOrigin.Begin); + m_Stream.Write((int)((long)disabled >> 32)); + m_Stream.Write((int)disabled); + + m_Stream.Seek(95, SeekOrigin.Begin); + m_Stream.Write(hashCode, 0, hashCode.Length); + } + } + + public static CharacterListFlags AdditionalFlags{ get; set; } + } + + public sealed class CharacterListOld : Packet + { + private static MD5CryptoServiceProvider m_MD5Provider; + + public CharacterListOld(IAccount a, CityInfo[] info) : base(0xA9) + { + EnsureCapacity(9 + a.Length * 60 + info.Length * 63); + + int highSlot = -1; + + for (int i = 0; i < a.Length; ++i) + if (a[i] != null) + highSlot = i; + + int count = Math.Max(Math.Max(highSlot + 1, a.Limit), 5); + + m_Stream.Write((byte)count); + + for (int i = 0; i < count; ++i) + if (a[i] != null) + { + m_Stream.WriteAsciiFixed(a[i].Name, 30); + m_Stream.Fill(30); // password + } + else + { + m_Stream.Fill(60); + } + + m_Stream.Write((byte)info.Length); + + for (int i = 0; i < info.Length; ++i) + { + CityInfo ci = info[i]; + + m_Stream.Write((byte)i); + m_Stream.WriteAsciiFixed(ci.City, 31); + m_Stream.WriteAsciiFixed(ci.Building, 31); + } + + CharacterListFlags flags = ExpansionInfo.CoreExpansion.CharacterListFlags; + + if (count > 6) + flags |= CharacterListFlags.SeventhCharacterSlot | + CharacterListFlags.SixthCharacterSlot; // 7th Character Slot - TODO: Is SixthCharacterSlot Required? + else if (count == 6) + flags |= CharacterListFlags.SixthCharacterSlot; // 6th Character Slot + else if (a.Limit == 1) + flags |= CharacterListFlags.SlotLimit & + CharacterListFlags.OneCharacterSlot; // Limit Characters & One Character + + m_Stream.Write((int)(flags | CharacterList.AdditionalFlags)); // Additional Flags + + ThirdPartyFeature disabled = FeatureProtection.DisabledFeatures; + + if (disabled != 0) + { + if (m_MD5Provider == null) + m_MD5Provider = new MD5CryptoServiceProvider(); + + m_Stream.UnderlyingStream.Flush(); + + byte[] hashCode = m_MD5Provider.ComputeHash(m_Stream.UnderlyingStream.GetBuffer(), 0, + (int)m_Stream.UnderlyingStream.Length); + byte[] buffer = new byte[28]; + + for (int i = 0; i < count; ++i) + { + Utility.RandomBytes(buffer); + + m_Stream.Seek(35 + i * 60, SeekOrigin.Begin); + m_Stream.Write(buffer, 0, buffer.Length); + } + + m_Stream.Seek(35, SeekOrigin.Begin); + m_Stream.Write((int)((long)disabled >> 32)); + m_Stream.Write((int)disabled); + + m_Stream.Seek(95, SeekOrigin.Begin); + m_Stream.Write(hashCode, 0, hashCode.Length); + } + } + } + + public sealed class ClearWeaponAbility : Packet + { + public static readonly Packet Instance = SetStatic(new ClearWeaponAbility()); + + public ClearWeaponAbility() : base(0xBF) + { + EnsureCapacity(5); + + m_Stream.Write((short)0x21); + } + } + + public enum ALRReason : byte + { + Invalid = 0x00, + InUse = 0x01, + Blocked = 0x02, + BadPass = 0x03, + Idle = 0xFE, + BadComm = 0xFF + } + + public sealed class AccountLoginRej : Packet + { + public AccountLoginRej(ALRReason reason) : base(0x82, 2) + { + m_Stream.Write((byte)reason); + } + } + + public enum AffixType : byte + { + Append = 0x00, + Prepend = 0x01, + System = 0x02 + } + + public sealed class MessageLocalizedAffix : Packet + { + public MessageLocalizedAffix(Serial serial, int graphic, MessageType messageType, int hue, int font, int number, + string name, AffixType affixType, string affix, string args) : base(0xCC) + { + if (name == null) name = ""; + if (affix == null) affix = ""; + if (args == null) args = ""; + + if (hue == 0) + hue = 0x3B2; + + EnsureCapacity(52 + affix.Length + args.Length * 2); + + m_Stream.Write(serial); + m_Stream.Write((short)graphic); + m_Stream.Write((byte)messageType); + m_Stream.Write((short)hue); + m_Stream.Write((short)font); + m_Stream.Write(number); + m_Stream.Write((byte)affixType); + m_Stream.WriteAsciiFixed(name, 30); + m_Stream.WriteAsciiNull(affix); + m_Stream.WriteBigUniNull(args); + } + } + + public sealed class ServerInfo + { + public ServerInfo(string name, int fullPercent, TimeZone tz, IPEndPoint address) + { + Name = name; + FullPercent = fullPercent; + TimeZone = tz.GetUtcOffset(DateTime.Now).Hours; + Address = address; + } + + public string Name{ get; set; } + + public int FullPercent{ get; set; } + + public int TimeZone{ get; set; } + + public IPEndPoint Address{ get; set; } + } + + public sealed class FollowMessage : Packet + { + public FollowMessage(Serial serial1, Serial serial2) : base(0x15, 9) + { + m_Stream.Write(serial1); + m_Stream.Write(serial2); + } + } + + public sealed class AccountLoginAck : Packet + { + public AccountLoginAck(ServerInfo[] info) : base(0xA8) + { + EnsureCapacity(6 + info.Length * 40); + + m_Stream.Write((byte)0x5D); // Unknown + + m_Stream.Write((ushort)info.Length); + + for (int i = 0; i < info.Length; ++i) + { + ServerInfo si = info[i]; + + m_Stream.Write((ushort)i); + m_Stream.WriteAsciiFixed(si.Name, 32); + m_Stream.Write((byte)si.FullPercent); + m_Stream.Write((sbyte)si.TimeZone); + m_Stream.Write(Utility.GetAddressValue(si.Address.Address)); + } + } + } + + public sealed class DisplaySignGump : Packet + { + public DisplaySignGump(Serial serial, int gumpID, string unknown, string caption) : base(0x8B) + { + if (unknown == null) unknown = ""; + if (caption == null) caption = ""; + + EnsureCapacity(16 + unknown.Length + caption.Length); + + m_Stream.Write(serial); + m_Stream.Write((short)gumpID); + m_Stream.Write((short)unknown.Length); + m_Stream.WriteAsciiFixed(unknown, unknown.Length); + m_Stream.Write((short)(caption.Length + 1)); + m_Stream.WriteAsciiFixed(caption, caption.Length + 1); + } + } + + public sealed class GodModeReply : Packet + { + public GodModeReply(bool reply) : base(0x2B, 2) + { + m_Stream.Write(reply); + } + } + + public sealed class PlayServerAck : Packet + { + internal static int m_AuthID = -1; + + public PlayServerAck(ServerInfo si) : base(0x8C, 11) + { + int addr = Utility.GetAddressValue(si.Address.Address); + + m_Stream.Write((byte)addr); + m_Stream.Write((byte)(addr >> 8)); + m_Stream.Write((byte)(addr >> 16)); + m_Stream.Write((byte)(addr >> 24)); + + m_Stream.Write((short)si.Address.Port); + m_Stream.Write(m_AuthID); + } + } + + public abstract class Packet + { + private const int CompressorBufferSize = 0x10000; + + private const int BufferSize = 4096; + private static BufferPool m_CompressorBuffers = new BufferPool("Compressor", 4, CompressorBufferSize); + private static BufferPool m_Buffers = new BufferPool("Compressed", 16, BufferSize); + + private byte[] m_CompiledBuffer; + private int m_CompiledLength; + private int m_Length; + private State m_State; + + protected PacketWriter m_Stream; + + protected Packet(int packetID) + { + PacketID = packetID; + + if (Core.Profiling) + { + PacketSendProfile prof = PacketSendProfile.Acquire(GetType()); + prof.Increment(); + } + } + + protected Packet(int packetID, int length) + { + PacketID = packetID; + m_Length = length; + + m_Stream = PacketWriter.CreateInstance(length); // new PacketWriter( length ); + m_Stream.Write((byte)packetID); + + if (Core.Profiling) + { + PacketSendProfile prof = PacketSendProfile.Acquire(GetType()); + prof.Increment(); + } + } + + public int PacketID{ get; } + + public PacketWriter UnderlyingStream => m_Stream; + + public void EnsureCapacity(int length) + { + m_Stream = PacketWriter.CreateInstance(length); // new PacketWriter( length ); + m_Stream.Write((byte)PacketID); + m_Stream.Write((short)0); + } + + public static Packet SetStatic(Packet p) + { + p.SetStatic(); + return p; + } + + public static Packet Acquire(Packet p) + { + p.Acquire(); + return p; + } + + public static void Release(ref ObjectPropertyList p) + { + p?.Release(); + + p = null; + } + + public static void Release(ref RemoveItem p) + { + p?.Release(); + + p = null; + } + + public static void Release(ref RemoveMobile p) + { + p?.Release(); + + p = null; + } + + public static void Release(ref OPLInfo p) + { + p?.Release(); + + p = null; + } + + public static void Release(ref Packet p) + { + p?.Release(); + + p = null; + } + + public static void Release(Packet p) + { + p?.Release(); + } + + public void SetStatic() + { + m_State |= State.Static | State.Acquired; + } + + public void Acquire() + { + m_State |= State.Acquired; + } + + public void OnSend() + { + Core.Set(); + + lock (this) + { + if ((m_State & (State.Acquired | State.Static)) == 0) + Free(); + } + } + + private void Free() + { + if (m_CompiledBuffer == null) + return; + + if ((m_State & State.Buffered) != 0) + m_Buffers.ReleaseBuffer(m_CompiledBuffer); + + m_State &= ~(State.Static | State.Acquired | State.Buffered); + + m_CompiledBuffer = null; + } + + public void Release() + { + if ((m_State & State.Acquired) != 0) + Free(); + } + + public byte[] Compile(bool compress, out int length) + { + lock (this) + { + if (m_CompiledBuffer == null) + { + if ((m_State & State.Accessed) == 0) + { + m_State |= State.Accessed; + } + else + { + if ((m_State & State.Warned) == 0) + { + m_State |= State.Warned; + + try + { + using (StreamWriter op = new StreamWriter("net_opt.log", true)) + { + op.WriteLine("Redundant compile for packet {0}, use Acquire() and Release()", GetType()); + op.WriteLine(new StackTrace()); + } + } + catch + { + } + } + + m_CompiledBuffer = new byte[0]; + m_CompiledLength = 0; + + length = m_CompiledLength; + return m_CompiledBuffer; + } + + InternalCompile(compress); + } + + length = m_CompiledLength; + return m_CompiledBuffer; + } + } + + private void InternalCompile(bool compress) + { + if (m_Length == 0) + { + long streamLen = m_Stream.Length; + + m_Stream.Seek(1, SeekOrigin.Begin); + m_Stream.Write((ushort)streamLen); + } + else if (m_Stream.Length != m_Length) + { + int diff = (int)m_Stream.Length - m_Length; + + Console.WriteLine("Packet: 0x{0:X2}: Bad packet length! ({1}{2} bytes)", PacketID, diff >= 0 ? "+" : "", + diff); + } + + MemoryStream ms = m_Stream.UnderlyingStream; + + m_CompiledBuffer = ms.GetBuffer(); + int length = (int)ms.Length; + + if (compress) + { + byte[] buffer; + lock (m_CompressorBuffers) + { + buffer = m_CompressorBuffers.AcquireBuffer(); + } + + Compression.Compress(m_CompiledBuffer, 0, length, buffer, ref length); + + if (length <= 0) + { + Console.WriteLine("Warning: Compression buffer overflowed on packet 0x{0:X2} ('{1}') (length={2})", + PacketID, GetType().Name, length); + using (StreamWriter op = new StreamWriter("compression_overflow.log", true)) + { + op.WriteLine("{0} Warning: Compression buffer overflowed on packet 0x{1:X2} ('{2}') (length={3})", + DateTime.UtcNow, PacketID, GetType().Name, length); + op.WriteLine(new StackTrace()); + } + } + else + { + m_CompiledLength = length; + + if (length > BufferSize || (m_State & State.Static) != 0) + { + m_CompiledBuffer = new byte[length]; + } + else + { + lock (m_Buffers) + { + m_CompiledBuffer = m_Buffers.AcquireBuffer(); + } + + m_State |= State.Buffered; + } + + Buffer.BlockCopy(buffer, 0, m_CompiledBuffer, 0, length); + + lock (m_CompressorBuffers) + { + m_CompressorBuffers.ReleaseBuffer(buffer); + } + } + } + else if (length > 0) + { + byte[] old = m_CompiledBuffer; + m_CompiledLength = length; + + if (length > BufferSize || (m_State & State.Static) != 0) + { + m_CompiledBuffer = new byte[length]; + } + else + { + lock (m_Buffers) + { + m_CompiledBuffer = m_Buffers.AcquireBuffer(); + } + + m_State |= State.Buffered; + } + + Buffer.BlockCopy(old, 0, m_CompiledBuffer, 0, length); + } + + PacketWriter.ReleaseInstance(m_Stream); + m_Stream = null; + } + + [Flags] + private enum State + { + Inactive = 0x00, + Static = 0x01, + Acquired = 0x02, + Accessed = 0x04, + Buffered = 0x08, + Warned = 0x10 + } + } +} \ No newline at end of file diff --git a/Server/Network/SendQueue.cs b/Server/Network/SendQueue.cs index d5a24f166..78f98fe87 100644 --- a/Server/Network/SendQueue.cs +++ b/Server/Network/SendQueue.cs @@ -21,189 +21,205 @@ using System; using System.Collections.Generic; -namespace Server.Network { - public class SendQueue { - public class Gram { - private static Stack _pool = new Stack(); +namespace Server.Network +{ + public class SendQueue + { + private const int PendingCap = 256 * 1024; - public static Gram Acquire() { - lock ( _pool ) { - Gram gram; + private static int m_CoalesceBufferSize = 512; + private static BufferPool m_UnusedBuffers = new BufferPool("Coalesced", 2048, m_CoalesceBufferSize); - if ( _pool.Count > 0 ) { - gram = _pool.Pop(); - } else { - gram = new Gram(); - } + private Gram _buffered; - gram.Buffer = AcquireBuffer(); - gram.Length = 0; + private Queue _pending; - return gram; - } - } + public SendQueue() + { + _pending = new Queue(); + } - public byte[] Buffer { get; private set; } + public static int CoalesceBufferSize + { + get => m_CoalesceBufferSize; + set + { + if (m_CoalesceBufferSize == value) + return; - public int Length { get; private set; } + BufferPool old = m_UnusedBuffers; - public int Available => ( Buffer.Length - Length ); + lock (old) + { + m_UnusedBuffers?.Free(); - public bool IsFull => ( Length == Buffer.Length ); + m_CoalesceBufferSize = value; + m_UnusedBuffers = new BufferPool("Coalesced", 2048, m_CoalesceBufferSize); + } + } + } - private Gram() { - } + public bool IsFlushReady => _pending.Count == 0 && _buffered != null; - public int Write( byte[] buffer, int offset, int length ) { - int write = Math.Min( length, Available ); + public bool IsEmpty => _pending.Count == 0 && _buffered == null; - System.Buffer.BlockCopy( buffer, offset, Buffer, Length, write ); + public static byte[] AcquireBuffer() + { + lock (m_UnusedBuffers) + { + return m_UnusedBuffers.AcquireBuffer(); + } + } - Length += write; + public static void ReleaseBuffer(byte[] buffer) + { + lock (m_UnusedBuffers) + { + if (buffer != null && buffer.Length == m_CoalesceBufferSize) + m_UnusedBuffers.ReleaseBuffer(buffer); + } + } - return write; - } + public Gram CheckFlushReady() + { + Gram gram = _buffered; + _pending.Enqueue(_buffered); + _buffered = null; + return gram; + } - public void Release() { - lock ( _pool ) { - _pool.Push( this ); - ReleaseBuffer( Buffer ); - } - } - } + public Gram Dequeue() + { + Gram gram = null; - private static int m_CoalesceBufferSize = 512; - private static BufferPool m_UnusedBuffers = new BufferPool( "Coalesced", 2048, m_CoalesceBufferSize ); + if (_pending.Count > 0) + { + _pending.Dequeue().Release(); - public static int CoalesceBufferSize { - get => m_CoalesceBufferSize; - set { - if ( m_CoalesceBufferSize == value ) - return; + if (_pending.Count > 0) gram = _pending.Peek(); + } - BufferPool old = m_UnusedBuffers; + return gram; + } - lock (old) { - m_UnusedBuffers?.Free(); + public Gram Enqueue(byte[] buffer, int length) + { + return Enqueue(buffer, 0, length); + } - m_CoalesceBufferSize = value; - m_UnusedBuffers = new BufferPool( "Coalesced", 2048, m_CoalesceBufferSize ); - } - } - } + public Gram Enqueue(byte[] buffer, int offset, int length) + { + if (buffer == null) throw new ArgumentNullException("buffer"); - public static byte[] AcquireBuffer() { - lock (m_UnusedBuffers) - return m_UnusedBuffers.AcquireBuffer(); - } + if (!(offset >= 0 && offset < buffer.Length)) + throw new ArgumentOutOfRangeException("offset", offset, + "Offset must be greater than or equal to zero and less than the size of the buffer."); + if (length < 0 || length > buffer.Length) + throw new ArgumentOutOfRangeException("length", length, + "Length cannot be less than zero or greater than the size of the buffer."); + if (buffer.Length - offset < length) + throw new ArgumentException("Offset and length do not point to a valid segment within the buffer."); - public static void ReleaseBuffer( byte[] buffer ) { - lock (m_UnusedBuffers) - if ( buffer != null && buffer.Length == m_CoalesceBufferSize ) - m_UnusedBuffers.ReleaseBuffer( buffer ); - } + int existingBytes = _pending.Count * m_CoalesceBufferSize + (_buffered?.Length ?? 0); - private Queue _pending; + if (existingBytes + length > PendingCap) throw new CapacityExceededException(); - private Gram _buffered; + Gram gram = null; - public bool IsFlushReady => ( _pending.Count == 0 && _buffered != null ); + while (length > 0) + { + if (_buffered == null) _buffered = Gram.Acquire(); - public bool IsEmpty => ( _pending.Count == 0 && _buffered == null ); + int bytesWritten = _buffered.Write(buffer, offset, length); - public SendQueue() { - _pending = new Queue(); - } + offset += bytesWritten; + length -= bytesWritten; - public Gram CheckFlushReady() { - Gram gram = _buffered; - _pending.Enqueue(_buffered); - _buffered = null; - return gram; - } + if (_buffered.IsFull) + { + if (_pending.Count == 0) gram = _buffered; - public Gram Dequeue() { - Gram gram = null; + _pending.Enqueue(_buffered); + _buffered = null; + } + } - if ( _pending.Count > 0 ) { - _pending.Dequeue().Release(); + return gram; + } - if ( _pending.Count > 0 ) { - gram = _pending.Peek(); - } - } + public void Clear() + { + if (_buffered != null) + { + _buffered.Release(); + _buffered = null; + } - return gram; - } + while (_pending.Count > 0) _pending.Dequeue().Release(); + } - private const int PendingCap = 256 * 1024; + public class Gram + { + private static Stack _pool = new Stack(); - public Gram Enqueue( byte[] buffer, int length ) { - return Enqueue( buffer, 0, length ); - } + private Gram() + { + } - public Gram Enqueue( byte[] buffer, int offset, int length ) { - if ( buffer == null ) { - throw new ArgumentNullException( "buffer" ); - } + public byte[] Buffer{ get; private set; } - if ( !(offset >= 0 && offset < buffer.Length) ) { - throw new ArgumentOutOfRangeException( "offset", offset, "Offset must be greater than or equal to zero and less than the size of the buffer." ); - } - if ( length < 0 || length > buffer.Length ) { - throw new ArgumentOutOfRangeException( "length", length, "Length cannot be less than zero or greater than the size of the buffer." ); - } - if ( ( buffer.Length - offset ) < length ) { - throw new ArgumentException( "Offset and length do not point to a valid segment within the buffer." ); - } + public int Length{ get; private set; } - int existingBytes = ( _pending.Count * m_CoalesceBufferSize ) + (_buffered?.Length ?? 0); + public int Available => Buffer.Length - Length; - if ( ( existingBytes + length ) > PendingCap ) { - throw new CapacityExceededException(); - } + public bool IsFull => Length == Buffer.Length; - Gram gram = null; + public static Gram Acquire() + { + lock (_pool) + { + Gram gram; - while ( length > 0 ) { - if ( _buffered == null ) { // nothing yet buffered - _buffered = Gram.Acquire(); - } + if (_pool.Count > 0) + gram = _pool.Pop(); + else + gram = new Gram(); - int bytesWritten = _buffered.Write( buffer, offset, length ); + gram.Buffer = AcquireBuffer(); + gram.Length = 0; - offset += bytesWritten; - length -= bytesWritten; + return gram; + } + } - if ( _buffered.IsFull ) { - if ( _pending.Count == 0 ) { - gram = _buffered; - } + public int Write(byte[] buffer, int offset, int length) + { + int write = Math.Min(length, Available); - _pending.Enqueue( _buffered ); - _buffered = null; - } - } + System.Buffer.BlockCopy(buffer, offset, Buffer, Length, write); - return gram; - } + Length += write; - public void Clear() { - if ( _buffered != null ) { - _buffered.Release(); - _buffered = null; - } + return write; + } - while ( _pending.Count > 0 ) { - _pending.Dequeue().Release(); - } - } - } + public void Release() + { + lock (_pool) + { + _pool.Push(this); + ReleaseBuffer(Buffer); + } + } + } + } - [Serializable] - public sealed class CapacityExceededException : Exception { - public CapacityExceededException() - : base( "Too much data pending." ) { - } - } + [Serializable] + public sealed class CapacityExceededException : Exception + { + public CapacityExceededException() + : base("Too much data pending.") + { + } + } } \ No newline at end of file diff --git a/Server/Notoriety.cs b/Server/Notoriety.cs index f310b3884..33ece5b9f 100644 --- a/Server/Notoriety.cs +++ b/Server/Notoriety.cs @@ -20,43 +20,43 @@ namespace Server { - public delegate int NotorietyHandler( Mobile source, Mobile target ); + public delegate int NotorietyHandler(Mobile source, Mobile target); - public static class Notoriety - { - public const int Innocent = 1; - public const int Ally = 2; - public const int CanBeAttacked = 3; - public const int Criminal = 4; - public const int Enemy = 5; - public const int Murderer = 6; - public const int Invulnerable = 7; + public static class Notoriety + { + public const int Innocent = 1; + public const int Ally = 2; + public const int CanBeAttacked = 3; + public const int Criminal = 4; + public const int Enemy = 5; + public const int Murderer = 6; + public const int Invulnerable = 7; - public static NotorietyHandler Handler { get; set; } + public static NotorietyHandler Handler{ get; set; } - public static int[] Hues { get; set; } = - { - 0x000, - 0x059, - 0x03F, - 0x3B2, - 0x3B2, - 0x090, - 0x022, - 0x035 - }; + public static int[] Hues{ get; set; } = + { + 0x000, + 0x059, + 0x03F, + 0x3B2, + 0x3B2, + 0x090, + 0x022, + 0x035 + }; - public static int GetHue( int noto ) - { - if ( noto < 0 || noto >= Hues.Length ) - return 0; + public static int GetHue(int noto) + { + if (noto < 0 || noto >= Hues.Length) + return 0; - return Hues[noto]; - } + return Hues[noto]; + } - public static int Compute( Mobile source, Mobile target ) - { - return Handler?.Invoke( source, target ) ?? CanBeAttacked; - } - } + public static int Compute(Mobile source, Mobile target) + { + return Handler?.Invoke(source, target) ?? CanBeAttacked; + } + } } \ No newline at end of file diff --git a/Server/ObjectPropertyList.cs b/Server/ObjectPropertyList.cs index 552102b08..756147113 100644 --- a/Server/ObjectPropertyList.cs +++ b/Server/ObjectPropertyList.cs @@ -18,176 +18,177 @@ * ***************************************************************************/ -using System; +using System.IO; using System.Text; using Server.Network; namespace Server { - public sealed class ObjectPropertyList : Packet - { - private int m_Hash; - private int m_Strings; + public sealed class ObjectPropertyList : Packet + { + private static byte[] m_Buffer = new byte[1024]; + private static Encoding m_Encoding = Encoding.Unicode; - public IEntity Entity { get; } + // Each of these are localized to "~1_NOTHING~" which allows the string argument to be used + private static int[] m_StringNumbers = + { + 1042971, + 1070722 + }; - public int Hash => 0x40000000 + m_Hash; + private int m_Hash; + private int m_Strings; - public int Header { get; set; } + public ObjectPropertyList(IEntity e) : base(0xD6) + { + EnsureCapacity(128); - public string HeaderArgs { get; set; } + Entity = e; - public static bool Enabled { get; set; } + m_Stream.Write((short)1); + m_Stream.Write(e.Serial); + m_Stream.Write((byte)0); + m_Stream.Write((byte)0); + m_Stream.Write(e.Serial); + } - public ObjectPropertyList( IEntity e ) : base( 0xD6 ) - { - EnsureCapacity( 128 ); + public IEntity Entity{ get; } - Entity = e; + public int Hash => 0x40000000 + m_Hash; - m_Stream.Write( (short) 1 ); - m_Stream.Write( (int) e.Serial ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (byte) 0 ); - m_Stream.Write( (int) e.Serial ); - } + public int Header{ get; set; } - public void Add( int number ) - { - if ( number == 0 ) - return; + public string HeaderArgs{ get; set; } - AddHash( number ); + public static bool Enabled{ get; set; } - if ( Header == 0 ) - { - Header = number; - HeaderArgs = ""; - } + public void Add(int number) + { + if (number == 0) + return; - m_Stream.Write( number ); - m_Stream.Write( (short) 0 ); - } + AddHash(number); - public void Terminate() - { - m_Stream.Write( (int) 0 ); + if (Header == 0) + { + Header = number; + HeaderArgs = ""; + } - m_Stream.Seek( 11, System.IO.SeekOrigin.Begin ); - m_Stream.Write( (int) m_Hash ); - } + m_Stream.Write(number); + m_Stream.Write((short)0); + } - private static byte[] m_Buffer = new byte[1024]; - private static Encoding m_Encoding = Encoding.Unicode; + public void Terminate() + { + m_Stream.Write(0); - public void AddHash( int val ) - { - m_Hash ^= (val & 0x3FFFFFF); - m_Hash ^= (val >> 26) & 0x3F; - } + m_Stream.Seek(11, SeekOrigin.Begin); + m_Stream.Write(m_Hash); + } - public void Add( int number, string arguments ) - { - if ( number == 0 ) - return; + public void AddHash(int val) + { + m_Hash ^= val & 0x3FFFFFF; + m_Hash ^= (val >> 26) & 0x3F; + } - if ( arguments == null ) - arguments = ""; + public void Add(int number, string arguments) + { + if (number == 0) + return; - if ( Header == 0 ) - { - Header = number; - HeaderArgs = arguments; - } + if (arguments == null) + arguments = ""; - AddHash( number ); - AddHash( arguments.GetHashCode() ); + if (Header == 0) + { + Header = number; + HeaderArgs = arguments; + } - m_Stream.Write( number ); + AddHash(number); + AddHash(arguments.GetHashCode()); - int byteCount = m_Encoding.GetByteCount( arguments ); + m_Stream.Write(number); - if ( byteCount > m_Buffer.Length ) - m_Buffer = new byte[byteCount]; + int byteCount = m_Encoding.GetByteCount(arguments); - byteCount = m_Encoding.GetBytes( arguments, 0, arguments.Length, m_Buffer, 0 ); + if (byteCount > m_Buffer.Length) + m_Buffer = new byte[byteCount]; - m_Stream.Write( (short) byteCount ); - m_Stream.Write( m_Buffer, 0, byteCount ); - } + byteCount = m_Encoding.GetBytes(arguments, 0, arguments.Length, m_Buffer, 0); - public void Add( int number, string format, object arg0 ) - { - Add( number, string.Format( format, arg0 ) ); - } + m_Stream.Write((short)byteCount); + m_Stream.Write(m_Buffer, 0, byteCount); + } - public void Add( int number, string format, object arg0, object arg1 ) - { - Add( number, string.Format( format, arg0, arg1 ) ); - } + public void Add(int number, string format, object arg0) + { + Add(number, string.Format(format, arg0)); + } - public void Add( int number, string format, object arg0, object arg1, object arg2 ) - { - Add( number, string.Format( format, arg0, arg1, arg2 ) ); - } + public void Add(int number, string format, object arg0, object arg1) + { + Add(number, string.Format(format, arg0, arg1)); + } - public void Add( int number, string format, params object[] args ) - { - Add( number, string.Format( format, args ) ); - } + public void Add(int number, string format, object arg0, object arg1, object arg2) + { + Add(number, string.Format(format, arg0, arg1, arg2)); + } - // Each of these are localized to "~1_NOTHING~" which allows the string argument to be used - private static int[] m_StringNumbers = { - 1042971, - 1070722 - }; + public void Add(int number, string format, params object[] args) + { + Add(number, string.Format(format, args)); + } - private int GetStringNumber() - { - return m_StringNumbers[m_Strings++ % m_StringNumbers.Length]; - } + private int GetStringNumber() + { + return m_StringNumbers[m_Strings++ % m_StringNumbers.Length]; + } - public void Add( string text ) - { - Add( GetStringNumber(), text ); - } + public void Add(string text) + { + Add(GetStringNumber(), text); + } - public void Add( string format, string arg0 ) - { - Add( GetStringNumber(), string.Format( format, arg0 ) ); - } + public void Add(string format, string arg0) + { + Add(GetStringNumber(), string.Format(format, arg0)); + } - public void Add( string format, string arg0, string arg1 ) - { - Add( GetStringNumber(), string.Format( format, arg0, arg1 ) ); - } + public void Add(string format, string arg0, string arg1) + { + Add(GetStringNumber(), string.Format(format, arg0, arg1)); + } - public void Add( string format, string arg0, string arg1, string arg2 ) - { - Add( GetStringNumber(), string.Format( format, arg0, arg1, arg2 ) ); - } + public void Add(string format, string arg0, string arg1, string arg2) + { + Add(GetStringNumber(), string.Format(format, arg0, arg1, arg2)); + } - public void Add( string format, params object[] args ) - { - Add( GetStringNumber(), string.Format( format, args ) ); - } - } + public void Add(string format, params object[] args) + { + Add(GetStringNumber(), string.Format(format, args)); + } + } - public sealed class OPLInfo : Packet - { - /*public OPLInfo( ObjectPropertyList list ) : base( 0xBF ) - { - EnsureCapacity( 13 ); + public sealed class OPLInfo : Packet + { + /*public OPLInfo( ObjectPropertyList list ) : base( 0xBF ) + { + EnsureCapacity( 13 ); - m_Stream.Write( (short) 0x10 ); - m_Stream.Write( (int) list.Entity.Serial ); - m_Stream.Write( (int) list.Hash ); - }*/ + m_Stream.Write( (short) 0x10 ); + m_Stream.Write( (int) list.Entity.Serial ); + m_Stream.Write( (int) list.Hash ); + }*/ - public OPLInfo( ObjectPropertyList list ) : base( 0xDC, 9 ) - { - m_Stream.Write( (int) list.Entity.Serial ); - m_Stream.Write( (int) list.Hash ); - } - } + public OPLInfo(ObjectPropertyList list) : base(0xDC, 9) + { + m_Stream.Write(list.Entity.Serial); + m_Stream.Write(list.Hash); + } + } } \ No newline at end of file diff --git a/Server/Party.cs b/Server/Party.cs index 0bac2a1bb..66739216e 100644 --- a/Server/Party.cs +++ b/Server/Party.cs @@ -20,16 +20,16 @@ namespace Server { - public abstract class PartyCommands - { - public static PartyCommands Handler { get; set; } + public abstract class PartyCommands + { + public static PartyCommands Handler{ get; set; } - public abstract void OnAdd( Mobile from ); - public abstract void OnRemove( Mobile from, Mobile target ); - public abstract void OnPrivateMessage( Mobile from, Mobile target, string text ); - public abstract void OnPublicMessage( Mobile from, string text ); - public abstract void OnSetCanLoot( Mobile from, bool canLoot ); - public abstract void OnAccept( Mobile from, Mobile leader ); - public abstract void OnDecline( Mobile from, Mobile leader ); - } + public abstract void OnAdd(Mobile from); + public abstract void OnRemove(Mobile from, Mobile target); + public abstract void OnPrivateMessage(Mobile from, Mobile target, string text); + public abstract void OnPublicMessage(Mobile from, string text); + public abstract void OnSetCanLoot(Mobile from, bool canLoot); + public abstract void OnAccept(Mobile from, Mobile leader); + public abstract void OnDecline(Mobile from, Mobile leader); + } } \ No newline at end of file diff --git a/Server/Persistence/BinaryMemoryWriter.cs b/Server/Persistence/BinaryMemoryWriter.cs index e7a483bd0..83dc64214 100644 --- a/Server/Persistence/BinaryMemoryWriter.cs +++ b/Server/Persistence/BinaryMemoryWriter.cs @@ -20,62 +20,63 @@ using System.IO; -namespace Server { - public sealed class BinaryMemoryWriter : BinaryFileWriter { - private MemoryStream stream; +namespace Server +{ + public sealed class BinaryMemoryWriter : BinaryFileWriter + { + private static byte[] indexBuffer; + private MemoryStream stream; - protected override int BufferSize => 512; + public BinaryMemoryWriter() + : base(new MemoryStream(512), true) + { + stream = UnderlyingStream as MemoryStream; + } - public BinaryMemoryWriter() - : base( new MemoryStream( 512 ), true ) { - stream = UnderlyingStream as MemoryStream; - } + protected override int BufferSize => 512; - private static byte[] indexBuffer; + public int CommitTo(SequentialFileWriter dataFile, SequentialFileWriter indexFile, int typeCode, int serial) + { + Flush(); - public int CommitTo( SequentialFileWriter dataFile, SequentialFileWriter indexFile, int typeCode, int serial ) { - Flush(); + byte[] buffer = stream.GetBuffer(); + int length = (int)stream.Length; - byte[] buffer = stream.GetBuffer(); - int length = ( int ) stream.Length; + long position = dataFile.Position; - long position = dataFile.Position; + dataFile.Write(buffer, 0, length); - dataFile.Write( buffer, 0, length ); + if (indexBuffer == null) indexBuffer = new byte[20]; - if ( indexBuffer == null ) { - indexBuffer = new byte[20]; - } + indexBuffer[0] = (byte)typeCode; + indexBuffer[1] = (byte)(typeCode >> 8); + indexBuffer[2] = (byte)(typeCode >> 16); + indexBuffer[3] = (byte)(typeCode >> 24); - indexBuffer[0] = ( byte ) ( typeCode ); - indexBuffer[1] = ( byte ) ( typeCode >> 8 ); - indexBuffer[2] = ( byte ) ( typeCode >> 16 ); - indexBuffer[3] = ( byte ) ( typeCode >> 24 ); + indexBuffer[4] = (byte)serial; + indexBuffer[5] = (byte)(serial >> 8); + indexBuffer[6] = (byte)(serial >> 16); + indexBuffer[7] = (byte)(serial >> 24); - indexBuffer[4] = ( byte ) ( serial ); - indexBuffer[5] = ( byte ) ( serial >> 8 ); - indexBuffer[6] = ( byte ) ( serial >> 16 ); - indexBuffer[7] = ( byte ) ( serial >> 24 ); + indexBuffer[8] = (byte)position; + indexBuffer[9] = (byte)(position >> 8); + indexBuffer[10] = (byte)(position >> 16); + indexBuffer[11] = (byte)(position >> 24); + indexBuffer[12] = (byte)(position >> 32); + indexBuffer[13] = (byte)(position >> 40); + indexBuffer[14] = (byte)(position >> 48); + indexBuffer[15] = (byte)(position >> 56); - indexBuffer[8] = ( byte ) ( position ); - indexBuffer[9] = ( byte ) ( position >> 8 ); - indexBuffer[10] = ( byte ) ( position >> 16 ); - indexBuffer[11] = ( byte ) ( position >> 24 ); - indexBuffer[12] = ( byte ) ( position >> 32 ); - indexBuffer[13] = ( byte ) ( position >> 40 ); - indexBuffer[14] = ( byte ) ( position >> 48 ); - indexBuffer[15] = ( byte ) ( position >> 56 ); + indexBuffer[16] = (byte)length; + indexBuffer[17] = (byte)(length >> 8); + indexBuffer[18] = (byte)(length >> 16); + indexBuffer[19] = (byte)(length >> 24); - indexBuffer[16] = ( byte ) ( length ); - indexBuffer[17] = ( byte ) ( length >> 8 ); - indexBuffer[18] = ( byte ) ( length >> 16 ); - indexBuffer[19] = ( byte ) ( length >> 24 ); + indexFile.Write(indexBuffer, 0, indexBuffer.Length); - indexFile.Write( indexBuffer, 0, indexBuffer.Length ); + stream.SetLength(0); - stream.SetLength( 0 ); - - return length; - } - } + return length; + } + } } \ No newline at end of file diff --git a/Server/Persistence/DualSaveStrategy.cs b/Server/Persistence/DualSaveStrategy.cs index bc6287a22..cd93949f3 100644 --- a/Server/Persistence/DualSaveStrategy.cs +++ b/Server/Persistence/DualSaveStrategy.cs @@ -20,31 +20,29 @@ using System.Threading; -namespace Server { - public sealed class DualSaveStrategy : StandardSaveStrategy { - public override string Name => "Dual"; +namespace Server +{ + public sealed class DualSaveStrategy : StandardSaveStrategy + { + public override string Name => "Dual"; - public DualSaveStrategy() { - } + public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) + { + PermitBackgroundWrite = permitBackgroundWrite; - public override void Save( SaveMetrics metrics, bool permitBackgroundWrite ) - { - PermitBackgroundWrite = permitBackgroundWrite; + Thread saveThread = new Thread(delegate() { SaveItems(metrics); }); - Thread saveThread = new Thread( delegate() { - SaveItems(metrics); - } ); + saveThread.Name = "Item Save Subset"; + saveThread.Start(); - saveThread.Name = "Item Save Subset"; - saveThread.Start(); + SaveMobiles(metrics); + SaveGuilds(metrics); - SaveMobiles(metrics); - SaveGuilds(metrics); + saveThread.Join(); - saveThread.Join(); - - if (permitBackgroundWrite && UseSequentialWriters) //If we're permitted to write in the background, but we don't anyways, then notify. - World.NotifyDiskWriteComplete(); - } - } -} + if (permitBackgroundWrite && UseSequentialWriters + ) //If we're permitted to write in the background, but we don't anyways, then notify. + World.NotifyDiskWriteComplete(); + } + } +} \ No newline at end of file diff --git a/Server/Persistence/DynamicSaveStrategy.cs b/Server/Persistence/DynamicSaveStrategy.cs index 3ce16093c..60565b937 100644 --- a/Server/Persistence/DynamicSaveStrategy.cs +++ b/Server/Persistence/DynamicSaveStrategy.cs @@ -20,278 +20,270 @@ using System; +using System.Collections.Concurrent; using System.Collections.Generic; using System.Threading.Tasks; -using System.Collections.Concurrent; using Server.Guilds; namespace Server { - public sealed class DynamicSaveStrategy : SaveStrategy - { - public override string Name => "Dynamic"; - - private SaveMetrics _metrics; - - private SequentialFileWriter _itemData, _itemIndex; - private SequentialFileWriter _mobileData, _mobileIndex; - private SequentialFileWriter _guildData, _guildIndex; - - private ConcurrentBag _decayBag; - - private BlockingCollection _itemThreadWriters; - private BlockingCollection _mobileThreadWriters; - private BlockingCollection _guildThreadWriters; - - public DynamicSaveStrategy() - { - _decayBag = new ConcurrentBag(); - _itemThreadWriters = new BlockingCollection(); - _mobileThreadWriters = new BlockingCollection(); - _guildThreadWriters = new BlockingCollection(); - } - - public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) - { - _metrics = metrics; - - OpenFiles(); - - Task[] saveTasks = new Task[3]; - - saveTasks[0] = SaveItems(); - saveTasks[1] = SaveMobiles(); - saveTasks[2] = SaveGuilds(); - - SaveTypeDatabases(); + public sealed class DynamicSaveStrategy : SaveStrategy + { + private ConcurrentBag _decayBag; + private SequentialFileWriter _guildData, _guildIndex; + private BlockingCollection _guildThreadWriters; + + private SequentialFileWriter _itemData, _itemIndex; + + private BlockingCollection _itemThreadWriters; + + private SaveMetrics _metrics; + private SequentialFileWriter _mobileData, _mobileIndex; + private BlockingCollection _mobileThreadWriters; + + public DynamicSaveStrategy() + { + _decayBag = new ConcurrentBag(); + _itemThreadWriters = new BlockingCollection(); + _mobileThreadWriters = new BlockingCollection(); + _guildThreadWriters = new BlockingCollection(); + } + + public override string Name => "Dynamic"; + + public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) + { + _metrics = metrics; + + OpenFiles(); + + Task[] saveTasks = new Task[3]; + + saveTasks[0] = SaveItems(); + saveTasks[1] = SaveMobiles(); + saveTasks[2] = SaveGuilds(); - if (permitBackgroundWrite) - { - //This option makes it finish the writing to disk in the background, continuing even after Save() returns. - Task.Factory.ContinueWhenAll(saveTasks, _ => - { - CloseFiles(); + SaveTypeDatabases(); - World.NotifyDiskWriteComplete(); - }); - } - else - { - Task.WaitAll(saveTasks); //Waits for the completion of all of the tasks(committing to disk) - CloseFiles(); - } - } + if (permitBackgroundWrite) + { + //This option makes it finish the writing to disk in the background, continuing even after Save() returns. + Task.Factory.ContinueWhenAll(saveTasks, _ => + { + CloseFiles(); - private Task StartCommitTask(BlockingCollection threadWriter, SequentialFileWriter data, SequentialFileWriter index) - { - Task commitTask = Task.Factory.StartNew(() => - { - while (!(threadWriter.IsCompleted)) - { - QueuedMemoryWriter writer; + World.NotifyDiskWriteComplete(); + }); + } + else + { + Task.WaitAll(saveTasks); //Waits for the completion of all of the tasks(committing to disk) + CloseFiles(); + } + } - try - { - writer = threadWriter.Take(); - } - catch (InvalidOperationException) - { - //Per MSDN, it's fine if we're here, successful completion of adding can rarely put us into this state. - break; - } + private Task StartCommitTask(BlockingCollection threadWriter, SequentialFileWriter data, + SequentialFileWriter index) + { + Task commitTask = Task.Factory.StartNew(() => + { + while (!threadWriter.IsCompleted) + { + QueuedMemoryWriter writer; - writer.CommitTo(data, index); - } - }); + try + { + writer = threadWriter.Take(); + } + catch (InvalidOperationException) + { + //Per MSDN, it's fine if we're here, successful completion of adding can rarely put us into this state. + break; + } - return commitTask; - } + writer.CommitTo(data, index); + } + }); - private Task SaveItems() - { - //Start the blocking consumer; this runs in background. - Task commitTask = StartCommitTask(_itemThreadWriters, _itemData, _itemIndex); + return commitTask; + } - IEnumerable items = World.Items.Values; + private Task SaveItems() + { + //Start the blocking consumer; this runs in background. + Task commitTask = StartCommitTask(_itemThreadWriters, _itemData, _itemIndex); - //Start the producer. - Parallel.ForEach(items, () => new QueuedMemoryWriter(), - (Item item, ParallelLoopState state, QueuedMemoryWriter writer) => - { - long startPosition = writer.Position; + IEnumerable items = World.Items.Values; - item.Serialize(writer); + //Start the producer. + Parallel.ForEach(items, () => new QueuedMemoryWriter(), + (item, state, writer) => + { + long startPosition = writer.Position; - int size = (int)(writer.Position - startPosition); + item.Serialize(writer); - writer.QueueForIndex(item, size); + int size = (int)(writer.Position - startPosition); - if (item.Decays && item.Parent == null && item.Map != Map.Internal && DateTime.UtcNow > (item.LastMoved + item.DecayTime)) - { - _decayBag.Add(item); - } + writer.QueueForIndex(item, size); - _metrics?.OnItemSaved(size); + if (item.Decays && item.Parent == null && item.Map != Map.Internal && + DateTime.UtcNow > item.LastMoved + item.DecayTime) _decayBag.Add(item); - return writer; - }, - (writer) => - { - writer.Flush(); + _metrics?.OnItemSaved(size); - _itemThreadWriters.Add(writer); - }); + return writer; + }, + writer => + { + writer.Flush(); - _itemThreadWriters.CompleteAdding(); //We only get here after the Parallel.ForEach completes. Lets our task + _itemThreadWriters.Add(writer); + }); - return commitTask; - } + _itemThreadWriters.CompleteAdding(); //We only get here after the Parallel.ForEach completes. Lets our task - private Task SaveMobiles() - { - //Start the blocking consumer; this runs in background. - Task commitTask = StartCommitTask( _mobileThreadWriters, _mobileData, _mobileIndex ); + return commitTask; + } - IEnumerable mobiles = World.Mobiles.Values; + private Task SaveMobiles() + { + //Start the blocking consumer; this runs in background. + Task commitTask = StartCommitTask(_mobileThreadWriters, _mobileData, _mobileIndex); - //Start the producer. - Parallel.ForEach(mobiles, () => new QueuedMemoryWriter(), - (Mobile mobile, ParallelLoopState state, QueuedMemoryWriter writer) => - { - long startPosition = writer.Position; + IEnumerable mobiles = World.Mobiles.Values; - mobile.Serialize(writer); + //Start the producer. + Parallel.ForEach(mobiles, () => new QueuedMemoryWriter(), + (mobile, state, writer) => + { + long startPosition = writer.Position; - int size = (int)(writer.Position - startPosition); + mobile.Serialize(writer); - writer.QueueForIndex(mobile, size); + int size = (int)(writer.Position - startPosition); - _metrics?.OnMobileSaved(size); + writer.QueueForIndex(mobile, size); - return writer; - }, - (writer) => - { - writer.Flush(); + _metrics?.OnMobileSaved(size); - _mobileThreadWriters.Add(writer); - }); + return writer; + }, + writer => + { + writer.Flush(); - _mobileThreadWriters.CompleteAdding(); //We only get here after the Parallel.ForEach completes. Lets our task tell the consumer that we're done + _mobileThreadWriters.Add(writer); + }); - return commitTask; - } + _mobileThreadWriters + .CompleteAdding(); //We only get here after the Parallel.ForEach completes. Lets our task tell the consumer that we're done - private Task SaveGuilds() - { - //Start the blocking consumer; this runs in background. - Task commitTask = StartCommitTask(_guildThreadWriters, _guildData, _guildIndex); + return commitTask; + } - IEnumerable guilds = BaseGuild.List.Values; + private Task SaveGuilds() + { + //Start the blocking consumer; this runs in background. + Task commitTask = StartCommitTask(_guildThreadWriters, _guildData, _guildIndex); - //Start the producer. - Parallel.ForEach(guilds, () => new QueuedMemoryWriter(), - (BaseGuild guild, ParallelLoopState state, QueuedMemoryWriter writer) => - { - long startPosition = writer.Position; + IEnumerable guilds = BaseGuild.List.Values; - guild.Serialize(writer); + //Start the producer. + Parallel.ForEach(guilds, () => new QueuedMemoryWriter(), + (guild, state, writer) => + { + long startPosition = writer.Position; - int size = (int)(writer.Position - startPosition ); + guild.Serialize(writer); - writer.QueueForIndex(guild, size); + int size = (int)(writer.Position - startPosition); - _metrics?.OnGuildSaved(size); + writer.QueueForIndex(guild, size); - return writer; - }, - (writer) => - { - writer.Flush(); + _metrics?.OnGuildSaved(size); - _guildThreadWriters.Add(writer); - }); + return writer; + }, + writer => + { + writer.Flush(); - _guildThreadWriters.CompleteAdding(); //We only get here after the Parallel.ForEach completes. Lets our task + _guildThreadWriters.Add(writer); + }); - return commitTask; - } + _guildThreadWriters.CompleteAdding(); //We only get here after the Parallel.ForEach completes. Lets our task - public override void ProcessDecay() - { - Item item; + return commitTask; + } - while( _decayBag.TryTake( out item ) ) - { - if ( item.OnDecay() ) - { - item.Delete(); - } - } - } + public override void ProcessDecay() + { + Item item; - private void OpenFiles() - { - _itemData = new SequentialFileWriter(World.ItemDataPath, _metrics); - _itemIndex = new SequentialFileWriter(World.ItemIndexPath, _metrics); + while (_decayBag.TryTake(out item)) + if (item.OnDecay()) + item.Delete(); + } - _mobileData = new SequentialFileWriter(World.MobileDataPath, _metrics); - _mobileIndex = new SequentialFileWriter(World.MobileIndexPath, _metrics); + private void OpenFiles() + { + _itemData = new SequentialFileWriter(World.ItemDataPath, _metrics); + _itemIndex = new SequentialFileWriter(World.ItemIndexPath, _metrics); - _guildData = new SequentialFileWriter(World.GuildDataPath, _metrics); - _guildIndex = new SequentialFileWriter(World.GuildIndexPath, _metrics); + _mobileData = new SequentialFileWriter(World.MobileDataPath, _metrics); + _mobileIndex = new SequentialFileWriter(World.MobileIndexPath, _metrics); - WriteCount(_itemIndex, World.Items.Count); - WriteCount(_mobileIndex, World.Mobiles.Count); - WriteCount(_guildIndex, BaseGuild.List.Count); - } + _guildData = new SequentialFileWriter(World.GuildDataPath, _metrics); + _guildIndex = new SequentialFileWriter(World.GuildIndexPath, _metrics); - private void CloseFiles() - { - _itemData.Close(); - _itemIndex.Close(); + WriteCount(_itemIndex, World.Items.Count); + WriteCount(_mobileIndex, World.Mobiles.Count); + WriteCount(_guildIndex, BaseGuild.List.Count); + } - _mobileData.Close(); - _mobileIndex.Close(); + private void CloseFiles() + { + _itemData.Close(); + _itemIndex.Close(); - _guildData.Close(); - _guildIndex.Close(); - } + _mobileData.Close(); + _mobileIndex.Close(); - private void WriteCount(SequentialFileWriter indexFile, int count) - { - //Equiv to GenericWriter.Write( (int)count ); - byte[] buffer = new byte[4]; + _guildData.Close(); + _guildIndex.Close(); + } - buffer[0] = (byte)(count); - buffer[1] = (byte)(count >> 8); - buffer[2] = (byte)(count >> 16); - buffer[3] = (byte)(count >> 24); + private void WriteCount(SequentialFileWriter indexFile, int count) + { + //Equiv to GenericWriter.Write( (int)count ); + byte[] buffer = new byte[4]; - indexFile.Write(buffer, 0, buffer.Length); - } + buffer[0] = (byte)count; + buffer[1] = (byte)(count >> 8); + buffer[2] = (byte)(count >> 16); + buffer[3] = (byte)(count >> 24); - private void SaveTypeDatabases() - { - SaveTypeDatabase(World.ItemTypesPath, World.m_ItemTypes); - SaveTypeDatabase(World.MobileTypesPath, World.m_MobileTypes); - } + indexFile.Write(buffer, 0, buffer.Length); + } - private void SaveTypeDatabase(string path, List types) - { - BinaryFileWriter bfw = new BinaryFileWriter(path, false); + private void SaveTypeDatabases() + { + SaveTypeDatabase(World.ItemTypesPath, World.m_ItemTypes); + SaveTypeDatabase(World.MobileTypesPath, World.m_MobileTypes); + } - bfw.Write(types.Count); + private void SaveTypeDatabase(string path, List types) + { + BinaryFileWriter bfw = new BinaryFileWriter(path, false); - foreach (Type type in types) - { - bfw.Write(type.FullName); - } + bfw.Write(types.Count); - bfw.Flush(); + foreach (Type type in types) bfw.Write(type.FullName); - bfw.Close(); - } - } + bfw.Flush(); -} + bfw.Close(); + } + } +} \ No newline at end of file diff --git a/Server/Persistence/FileOperations.cs b/Server/Persistence/FileOperations.cs index 7f7c08b94..2d484d849 100644 --- a/Server/Persistence/FileOperations.cs +++ b/Server/Persistence/FileOperations.cs @@ -24,83 +24,89 @@ using System.IO; #if !MONO using System.Runtime.InteropServices; using Microsoft.Win32.SafeHandles; + #endif -namespace Server { - public static class FileOperations { - public const int KB = 1024; - public const int MB = 1024 * KB; +namespace Server +{ + public static class FileOperations + { + public const int KB = 1024; + public const int MB = 1024 * KB; -#if !MONO - private const FileOptions NoBuffering = ( FileOptions ) 0x20000000; + public static int BufferSize{ get; set; } = 1 * MB; - internal static class UnsafeNativeMethods { - [DllImport("Kernel32", CharSet = CharSet.Unicode, SetLastError = true)] - internal static extern SafeFileHandle CreateFile(string lpFileName, int dwDesiredAccess, FileShare dwShareMode, IntPtr securityAttrs, FileMode dwCreationDisposition, int dwFlagsAndAttributes, IntPtr hTemplateFile); - } -#endif + public static int Concurrency{ get; set; } = 1; - public static int BufferSize { get; set; } = 1 * MB; + public static bool Unbuffered{ get; set; } = true; - public static int Concurrency { get; set; } = 1; + public static bool AreSynchronous => Concurrency < 1; - public static bool Unbuffered { get; set; } = true; + public static bool AreAsynchronous => Concurrency > 0; - public static bool AreSynchronous => ( Concurrency < 1 ); + public static FileStream OpenSequentialStream(string path, FileMode mode, FileAccess access, FileShare share) + { + FileOptions options = FileOptions.SequentialScan; - public static bool AreAsynchronous => ( Concurrency > 0 ); - - public static FileStream OpenSequentialStream( string path, FileMode mode, FileAccess access, FileShare share ) { - FileOptions options = FileOptions.SequentialScan; - - if ( Concurrency > 0 ) { - options |= FileOptions.Asynchronous; - } + if (Concurrency > 0) options |= FileOptions.Asynchronous; #if MONO return new FileStream( path, mode, access, share, bufferSize, options ); #else - if ( Unbuffered ) { - options |= NoBuffering; - } else { - return new FileStream( path, mode, access, share, BufferSize, options ); - } + if (Unbuffered) + options |= NoBuffering; + else + return new FileStream(path, mode, access, share, BufferSize, options); - SafeFileHandle fileHandle = UnsafeNativeMethods.CreateFile(path, (int)access, share, IntPtr.Zero, mode, (int)options, IntPtr.Zero); + SafeFileHandle fileHandle = + UnsafeNativeMethods.CreateFile(path, (int)access, share, IntPtr.Zero, mode, (int)options, IntPtr.Zero); - if ( fileHandle.IsInvalid ) { - throw new IOException(); - } + if (fileHandle.IsInvalid) throw new IOException(); - return new UnbufferedFileStream( fileHandle, access, BufferSize, ( Concurrency > 0 ) ); + return new UnbufferedFileStream(fileHandle, access, BufferSize, Concurrency > 0); #endif - } + } #if !MONO - private class UnbufferedFileStream : FileStream { - private SafeFileHandle fileHandle; + private class UnbufferedFileStream : FileStream + { + private SafeFileHandle fileHandle; - public UnbufferedFileStream( SafeFileHandle fileHandle, FileAccess access, int bufferSize, bool isAsync ) - : base( fileHandle, access, bufferSize, isAsync ) { - this.fileHandle = fileHandle; - } + public UnbufferedFileStream(SafeFileHandle fileHandle, FileAccess access, int bufferSize, bool isAsync) + : base(fileHandle, access, bufferSize, isAsync) + { + this.fileHandle = fileHandle; + } - public override void Write( byte[] array, int offset, int count ) { - base.Write( array, offset, BufferSize ); - } + public override void Write(byte[] array, int offset, int count) + { + base.Write(array, offset, BufferSize); + } - public override IAsyncResult BeginWrite( byte[] array, int offset, int numBytes, AsyncCallback userCallback, object stateObject ) { - return base.BeginWrite( array, offset, BufferSize, userCallback, stateObject ); - } + public override IAsyncResult BeginWrite(byte[] array, int offset, int numBytes, AsyncCallback userCallback, + object stateObject) + { + return base.BeginWrite(array, offset, BufferSize, userCallback, stateObject); + } - protected override void Dispose( bool disposing ) { - if ( !fileHandle.IsClosed ) { - fileHandle.Close(); - } + protected override void Dispose(bool disposing) + { + if (!fileHandle.IsClosed) fileHandle.Close(); - base.Dispose( disposing ); - } - } + base.Dispose(disposing); + } + } #endif - } -} + +#if !MONO + private const FileOptions NoBuffering = (FileOptions)0x20000000; + + internal static class UnsafeNativeMethods + { + [DllImport("Kernel32", CharSet = CharSet.Unicode, SetLastError = true)] + internal static extern SafeFileHandle CreateFile(string lpFileName, int dwDesiredAccess, FileShare dwShareMode, + IntPtr securityAttrs, FileMode dwCreationDisposition, int dwFlagsAndAttributes, IntPtr hTemplateFile); + } +#endif + } +} \ No newline at end of file diff --git a/Server/Persistence/FileQueue.cs b/Server/Persistence/FileQueue.cs index f9787bfa3..21c44eda5 100644 --- a/Server/Persistence/FileQueue.cs +++ b/Server/Persistence/FileQueue.cs @@ -23,212 +23,210 @@ using System.Collections.Generic; using System.Threading; using Server.Network; -namespace Server { - public delegate void FileCommitCallback( FileQueue.Chunk chunk ); +namespace Server +{ + public delegate void FileCommitCallback(FileQueue.Chunk chunk); - public sealed class FileQueue : IDisposable { - public sealed class Chunk { - private FileQueue owner; - private int slot; + public sealed class FileQueue : IDisposable + { + private static int bufferSize; + private static BufferPool bufferPool; - private int offset; + private Chunk[] active; + private int activeCount; + private Page buffered; - public byte[] Buffer { get; } + private FileCommitCallback callback; - public int Offset => 0; + private ManualResetEvent idle; - public int Size { get; } + private Queue pending; - public Chunk( FileQueue owner, int slot, byte[] buffer, int offset, int size ) { - this.owner = owner; - this.slot = slot; + private object syncRoot; - this.Buffer = buffer; - this.offset = offset; - this.Size = size; - } + static FileQueue() + { + bufferSize = FileOperations.BufferSize; + bufferPool = new BufferPool("File Buffers", 64, bufferSize); + } - public void Commit() { - owner.Commit( this, slot ); - } - } + public FileQueue(int concurrentWrites, FileCommitCallback callback) + { + if (concurrentWrites < 1) throw new ArgumentOutOfRangeException("concurrentWrites"); - private struct Page { - public byte[] buffer; - public int length; - } + if (bufferSize < 1) throw new ArgumentOutOfRangeException("bufferSize"); + if (callback == null) throw new ArgumentNullException("callback"); - private static int bufferSize; - private static BufferPool bufferPool; + syncRoot = new object(); - static FileQueue() { - bufferSize = FileOperations.BufferSize; - bufferPool = new BufferPool( "File Buffers", 64, bufferSize ); - } + active = new Chunk[concurrentWrites]; + pending = new Queue(); - private object syncRoot; + this.callback = callback; - private Chunk[] active; - private int activeCount; + idle = new ManualResetEvent(true); + } - private Queue pending; - private Page buffered; + public long Position{ get; private set; } - private FileCommitCallback callback; + public void Dispose() + { + if (idle != null) + { + idle.Close(); + idle = null; + } + } - private ManualResetEvent idle; + private void Append(Page page) + { + lock (syncRoot) + { + if (activeCount == 0) idle.Reset(); - public long Position { get; private set; } + ++activeCount; - public FileQueue( int concurrentWrites, FileCommitCallback callback ) { - if ( concurrentWrites < 1 ) { - throw new ArgumentOutOfRangeException( "concurrentWrites" ); - } + for (int slot = 0; slot < active.Length; ++slot) + if (active[slot] == null) + { + active[slot] = new Chunk(this, slot, page.buffer, 0, page.length); - if ( bufferSize < 1 ) { - throw new ArgumentOutOfRangeException( "bufferSize" ); - } - if ( callback == null ) { - throw new ArgumentNullException( "callback" ); - } + callback(active[slot]); - syncRoot = new object(); + return; + } - active = new Chunk[concurrentWrites]; - pending = new Queue(); + pending.Enqueue(page); + } + } - this.callback = callback; + public void Flush() + { + if (buffered.buffer != null) + { + Append(buffered); - idle = new ManualResetEvent( true ); - } + buffered.buffer = null; + buffered.length = 0; + } - private void Append( Page page ) { - lock ( syncRoot ) { - if ( activeCount == 0 ) { - idle.Reset(); - } + /*lock ( syncRoot ) { + if ( pending.Count > 0 ) { + idle.Reset(); + } - ++activeCount; + for ( int slot = 0; slot < active.Length && pending.Count > 0; ++slot ) { + if ( active[slot] == null ) { + Page page = pending.Dequeue(); - for ( int slot = 0; slot < active.Length; ++slot ) { - if ( active[slot] == null ) { - active[slot] = new Chunk( this, slot, page.buffer, 0, page.length ); + active[slot] = new Chunk( this, slot, page.buffer, 0, page.length ); - callback( active[slot] ); + ++activeCount; - return; - } - } + callback( active[slot] ); + } + } + }*/ - pending.Enqueue( page ); - } - } + idle.WaitOne(); + } - public void Dispose() { - if ( idle != null ) { - idle.Close(); - idle = null; - } - } + private void Commit(Chunk chunk, int slot) + { + if (slot < 0 || slot >= active.Length) throw new ArgumentOutOfRangeException("slot"); - public void Flush() { - if ( buffered.buffer != null ) { - Append( buffered ); + lock (syncRoot) + { + if (active[slot] != chunk) throw new ArgumentException(); - buffered.buffer = null; - buffered.length = 0; - } + bufferPool.ReleaseBuffer(chunk.Buffer); - /*lock ( syncRoot ) { - if ( pending.Count > 0 ) { - idle.Reset(); - } + if (pending.Count > 0) + { + Page page = pending.Dequeue(); - for ( int slot = 0; slot < active.Length && pending.Count > 0; ++slot ) { - if ( active[slot] == null ) { - Page page = pending.Dequeue(); + active[slot] = new Chunk(this, slot, page.buffer, 0, page.length); - active[slot] = new Chunk( this, slot, page.buffer, 0, page.length ); + callback(active[slot]); + } + else + { + active[slot] = null; + } - ++activeCount; + --activeCount; - callback( active[slot] ); - } - } - }*/ + if (activeCount == 0) idle.Set(); + } + } - idle.WaitOne(); - } + public void Enqueue(byte[] buffer, int offset, int size) + { + if (buffer == null) throw new ArgumentNullException("buffer"); - private void Commit( Chunk chunk, int slot ) { - if ( slot < 0 || slot >= active.Length ) { - throw new ArgumentOutOfRangeException( "slot" ); - } + if (offset < 0) throw new ArgumentOutOfRangeException("offset"); + if (size < 0) throw new ArgumentOutOfRangeException("size"); + if (buffer.Length - offset < size) throw new ArgumentException(); - lock ( syncRoot ) { - if ( active[slot] != chunk ) { - throw new ArgumentException(); - } + Position += size; - bufferPool.ReleaseBuffer( chunk.Buffer ); + while (size > 0) + { + if (buffered.buffer == null) buffered.buffer = bufferPool.AcquireBuffer(); - if ( pending.Count > 0 ) { - Page page = pending.Dequeue(); + byte[] page = buffered.buffer; // buffer page + int pageSpace = page.Length - buffered.length; // available bytes in page + int byteCount = size > pageSpace ? pageSpace : size; // how many bytes we can copy over - active[slot] = new Chunk( this, slot, page.buffer, 0, page.length ); + Buffer.BlockCopy(buffer, offset, page, buffered.length, byteCount); - callback( active[slot] ); - } else { - active[slot] = null; - } + buffered.length += byteCount; + offset += byteCount; + size -= byteCount; - --activeCount; + if (buffered.length == page.Length) + { + // page full + Append(buffered); - if ( activeCount == 0 ) { - idle.Set(); - } - } - } + buffered.buffer = null; + buffered.length = 0; + } + } + } - public void Enqueue( byte[] buffer, int offset, int size ) { - if ( buffer == null ) { - throw new ArgumentNullException( "buffer" ); - } + public sealed class Chunk + { + private int offset; + private FileQueue owner; + private int slot; - if ( offset < 0 ) { - throw new ArgumentOutOfRangeException( "offset" ); - } - if ( size < 0 ) { - throw new ArgumentOutOfRangeException( "size" ); - } - if ( ( buffer.Length - offset ) < size ) { - throw new ArgumentException(); - } + public Chunk(FileQueue owner, int slot, byte[] buffer, int offset, int size) + { + this.owner = owner; + this.slot = slot; - Position += size; + Buffer = buffer; + this.offset = offset; + Size = size; + } - while ( size > 0 ) { - if ( buffered.buffer == null ) { // nothing yet buffered - buffered.buffer = bufferPool.AcquireBuffer(); - } + public byte[] Buffer{ get; } - byte[] page = buffered.buffer; // buffer page - int pageSpace = page.Length - buffered.length; // available bytes in page - int byteCount = ( size > pageSpace ? pageSpace : size ); // how many bytes we can copy over + public int Offset => 0; - Buffer.BlockCopy( buffer, offset, page, buffered.length, byteCount ); + public int Size{ get; } - buffered.length += byteCount; - offset += byteCount; - size -= byteCount; + public void Commit() + { + owner.Commit(this, slot); + } + } - if ( buffered.length == page.Length ) { // page full - Append( buffered ); - - buffered.buffer = null; - buffered.length = 0; - } - } - } - } + private struct Page + { + public byte[] buffer; + public int length; + } + } } \ No newline at end of file diff --git a/Server/Persistence/ParallelSaveStrategy.cs b/Server/Persistence/ParallelSaveStrategy.cs index 90746234c..c5737f67c 100644 --- a/Server/Persistence/ParallelSaveStrategy.cs +++ b/Server/Persistence/ParallelSaveStrategy.cs @@ -24,299 +24,312 @@ using System.Collections.Generic; using System.Threading; using Server.Guilds; -namespace Server { - public sealed class ParallelSaveStrategy : SaveStrategy { - public override string Name => "Parallel"; +namespace Server +{ + public sealed class ParallelSaveStrategy : SaveStrategy + { + private Queue _decayQueue; - private int processorCount; + private Consumer[] consumers; + private int cycle; - public ParallelSaveStrategy( int processorCount ) { - this.processorCount = processorCount; + private bool finished; + private SequentialFileWriter guildData, guildIndex; - _decayQueue = new Queue(); - } + private SequentialFileWriter itemData, itemIndex; - private int GetThreadCount() { - return processorCount - 1; - } + private SaveMetrics metrics; + private SequentialFileWriter mobileData, mobileIndex; - private SaveMetrics metrics; + private int processorCount; - private SequentialFileWriter itemData, itemIndex; - private SequentialFileWriter mobileData, mobileIndex; - private SequentialFileWriter guildData, guildIndex; + public ParallelSaveStrategy(int processorCount) + { + this.processorCount = processorCount; - private Queue _decayQueue; + _decayQueue = new Queue(); + } - private Consumer[] consumers; - private int cycle; + public override string Name => "Parallel"; - private bool finished; + private int GetThreadCount() + { + return processorCount - 1; + } - public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) - { - this.metrics = metrics; + public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) + { + this.metrics = metrics; - OpenFiles(); + OpenFiles(); - consumers = new Consumer[GetThreadCount()]; + consumers = new Consumer[GetThreadCount()]; - for ( int i = 0; i < consumers.Length; ++i ) { - consumers[i] = new Consumer( this, 256 ); - } + for (int i = 0; i < consumers.Length; ++i) consumers[i] = new Consumer(this, 256); - IEnumerable collection = new Producer(); + IEnumerable collection = new Producer(); - foreach ( ISerializable value in collection ) { - while ( !Enqueue( value ) ) { - if ( !Commit() ) { - Thread.Sleep( 0 ); - } - } - } + foreach (ISerializable value in collection) + while (!Enqueue(value)) + if (!Commit()) + Thread.Sleep(0); - finished = true; + finished = true; - SaveTypeDatabases(); + SaveTypeDatabases(); - WaitHandle.WaitAll( - Array.ConvertAll( - consumers, - delegate( Consumer input ) { - return input.completionEvent; - } - ) - ); + WaitHandle.WaitAll( + Array.ConvertAll( + consumers, + delegate(Consumer input) { return input.completionEvent; } + ) + ); - Commit(); + Commit(); - CloseFiles(); - } + CloseFiles(); + } - public override void ProcessDecay() { - while ( _decayQueue.Count > 0 ) { - Item item = _decayQueue.Dequeue(); + public override void ProcessDecay() + { + while (_decayQueue.Count > 0) + { + Item item = _decayQueue.Dequeue(); - if ( item.OnDecay() ) { - item.Delete(); - } - } - } + if (item.OnDecay()) item.Delete(); + } + } - private void SaveTypeDatabases() { - SaveTypeDatabase( World.ItemTypesPath, World.m_ItemTypes ); - SaveTypeDatabase( World.MobileTypesPath, World.m_MobileTypes ); - } + private void SaveTypeDatabases() + { + SaveTypeDatabase(World.ItemTypesPath, World.m_ItemTypes); + SaveTypeDatabase(World.MobileTypesPath, World.m_MobileTypes); + } - private void SaveTypeDatabase( string path, List types ) { - BinaryFileWriter bfw = new BinaryFileWriter( path, false ); + private void SaveTypeDatabase(string path, List types) + { + BinaryFileWriter bfw = new BinaryFileWriter(path, false); - bfw.Write( types.Count ); + bfw.Write(types.Count); - foreach ( Type type in types ) { - bfw.Write( type.FullName ); - } + foreach (Type type in types) bfw.Write(type.FullName); - bfw.Flush(); + bfw.Flush(); - bfw.Close(); - } + bfw.Close(); + } - private void OpenFiles() { - itemData = new SequentialFileWriter( World.ItemDataPath, metrics ); - itemIndex = new SequentialFileWriter( World.ItemIndexPath, metrics ); + private void OpenFiles() + { + itemData = new SequentialFileWriter(World.ItemDataPath, metrics); + itemIndex = new SequentialFileWriter(World.ItemIndexPath, metrics); - mobileData = new SequentialFileWriter( World.MobileDataPath, metrics ); - mobileIndex = new SequentialFileWriter( World.MobileIndexPath, metrics ); + mobileData = new SequentialFileWriter(World.MobileDataPath, metrics); + mobileIndex = new SequentialFileWriter(World.MobileIndexPath, metrics); - guildData = new SequentialFileWriter( World.GuildDataPath, metrics ); - guildIndex = new SequentialFileWriter( World.GuildIndexPath, metrics ); + guildData = new SequentialFileWriter(World.GuildDataPath, metrics); + guildIndex = new SequentialFileWriter(World.GuildIndexPath, metrics); - WriteCount( itemIndex, World.Items.Count ); - WriteCount( mobileIndex, World.Mobiles.Count ); - WriteCount( guildIndex, BaseGuild.List.Count ); - } + WriteCount(itemIndex, World.Items.Count); + WriteCount(mobileIndex, World.Mobiles.Count); + WriteCount(guildIndex, BaseGuild.List.Count); + } - private void WriteCount( SequentialFileWriter indexFile, int count ) { - byte[] buffer = new byte[4]; + private void WriteCount(SequentialFileWriter indexFile, int count) + { + byte[] buffer = new byte[4]; - buffer[0] = ( byte ) ( count ); - buffer[1] = ( byte ) ( count >> 8 ); - buffer[2] = ( byte ) ( count >> 16 ); - buffer[3] = ( byte ) ( count >> 24 ); + buffer[0] = (byte)count; + buffer[1] = (byte)(count >> 8); + buffer[2] = (byte)(count >> 16); + buffer[3] = (byte)(count >> 24); - indexFile.Write( buffer, 0, buffer.Length ); - } + indexFile.Write(buffer, 0, buffer.Length); + } - private void CloseFiles() { - itemData.Close(); - itemIndex.Close(); + private void CloseFiles() + { + itemData.Close(); + itemIndex.Close(); - mobileData.Close(); - mobileIndex.Close(); + mobileData.Close(); + mobileIndex.Close(); - guildData.Close(); - guildIndex.Close(); + guildData.Close(); + guildIndex.Close(); - World.NotifyDiskWriteComplete(); - } + World.NotifyDiskWriteComplete(); + } - private void OnSerialized( ConsumableEntry entry ) { - ISerializable value = entry.value; - BinaryMemoryWriter writer = entry.writer; + private void OnSerialized(ConsumableEntry entry) + { + ISerializable value = entry.value; + BinaryMemoryWriter writer = entry.writer; - if ( value is Item item ) - Save( item, writer ); - else if ( value is Mobile mob ) - Save( mob, writer ); - else if ( value is BaseGuild guild ) - Save( guild, writer ); - } + if (value is Item item) + Save(item, writer); + else if (value is Mobile mob) + Save(mob, writer); + else if (value is BaseGuild guild) + Save(guild, writer); + } - private void Save( Item item, BinaryMemoryWriter writer ) { - int length = writer.CommitTo( itemData, itemIndex, item.m_TypeRef, item.Serial ); + private void Save(Item item, BinaryMemoryWriter writer) + { + int length = writer.CommitTo(itemData, itemIndex, item.m_TypeRef, item.Serial); - metrics?.OnItemSaved( length ); + metrics?.OnItemSaved(length); - if (item.Decays && item.Parent == null && item.Map != Map.Internal && DateTime.UtcNow > (item.LastMoved + item.DecayTime)) - { - _decayQueue.Enqueue( item ); - } - } + if (item.Decays && item.Parent == null && item.Map != Map.Internal && + DateTime.UtcNow > item.LastMoved + item.DecayTime) _decayQueue.Enqueue(item); + } - private void Save( Mobile mob, BinaryMemoryWriter writer ) { - int length = writer.CommitTo( mobileData, mobileIndex, mob.m_TypeRef, mob.Serial ); + private void Save(Mobile mob, BinaryMemoryWriter writer) + { + int length = writer.CommitTo(mobileData, mobileIndex, mob.m_TypeRef, mob.Serial); - metrics?.OnMobileSaved( length ); - } + metrics?.OnMobileSaved(length); + } - private void Save( BaseGuild guild, BinaryMemoryWriter writer ) { - int length = writer.CommitTo( guildData, guildIndex, 0, guild.Id ); + private void Save(BaseGuild guild, BinaryMemoryWriter writer) + { + int length = writer.CommitTo(guildData, guildIndex, 0, guild.Id); - metrics?.OnGuildSaved( length ); - } + metrics?.OnGuildSaved(length); + } - private bool Enqueue( ISerializable value ) { - for ( int i = 0; i < consumers.Length; ++i ) { - Consumer consumer = consumers[cycle++ % consumers.Length]; + private bool Enqueue(ISerializable value) + { + for (int i = 0; i < consumers.Length; ++i) + { + Consumer consumer = consumers[cycle++ % consumers.Length]; - if ( ( consumer.tail - consumer.head ) < consumer.buffer.Length ) { - consumer.buffer[consumer.tail % consumer.buffer.Length].value = value; - consumer.tail++; + if (consumer.tail - consumer.head < consumer.buffer.Length) + { + consumer.buffer[consumer.tail % consumer.buffer.Length].value = value; + consumer.tail++; - return true; - } - } + return true; + } + } - return false; - } + return false; + } - private bool Commit() { - bool committed = false; + private bool Commit() + { + bool committed = false; + + for (int i = 0; i < consumers.Length; ++i) + { + Consumer consumer = consumers[i]; - for ( int i = 0; i < consumers.Length; ++i ) { - Consumer consumer = consumers[i]; + while (consumer.head < consumer.done) + { + OnSerialized(consumer.buffer[consumer.head % consumer.buffer.Length]); + consumer.head++; - while ( consumer.head < consumer.done ) { - OnSerialized( consumer.buffer[consumer.head % consumer.buffer.Length] ); - consumer.head++; + committed = true; + } + } + + return committed; + } + + private sealed class Producer : IEnumerable + { + private IEnumerable guilds; + private IEnumerable items; + private IEnumerable mobiles; + + public Producer() + { + items = World.Items.Values; + mobiles = World.Mobiles.Values; + guilds = BaseGuild.List.Values; + } + + public IEnumerator GetEnumerator() + { + foreach (Item item in items) yield return item; + + foreach (Mobile mob in mobiles) yield return mob; - committed = true; - } - } + foreach (BaseGuild guild in guilds) yield return guild; + } + + IEnumerator IEnumerable.GetEnumerator() + { + throw new NotImplementedException(); + } + } + + private struct ConsumableEntry + { + public ISerializable value; + public BinaryMemoryWriter writer; + } + + private sealed class Consumer + { + public ConsumableEntry[] buffer; - return committed; - } + public ManualResetEvent completionEvent; + public int head, done, tail; + private ParallelSaveStrategy owner; - private sealed class Producer : IEnumerable { - private IEnumerable items; - private IEnumerable mobiles; - private IEnumerable guilds; + private Thread thread; - public Producer() { - items = World.Items.Values; - mobiles = World.Mobiles.Values; - guilds = BaseGuild.List.Values; - } + public Consumer(ParallelSaveStrategy owner, int bufferSize) + { + this.owner = owner; - public IEnumerator GetEnumerator() { - foreach ( Item item in items ) { - yield return item; - } + buffer = new ConsumableEntry[bufferSize]; + + for (int i = 0; i < buffer.Length; ++i) buffer[i].writer = new BinaryMemoryWriter(); - foreach ( Mobile mob in mobiles ) { - yield return mob; - } + completionEvent = new ManualResetEvent(false); + + thread = new Thread(Processor); + + thread.Name = "Parallel Serialization Thread"; + + thread.Start(); + } + + private void Processor() + { + try + { + while (!owner.finished) + { + Process(); + Thread.Sleep(0); + } - foreach ( BaseGuild guild in guilds ) { - yield return guild; - } - } + Process(); - IEnumerator IEnumerable.GetEnumerator() { - throw new NotImplementedException(); - } - } + completionEvent.Set(); + } + catch (Exception ex) + { + Console.WriteLine(ex); + } + } + + private void Process() + { + ConsumableEntry entry; + + while (done < tail) + { + entry = buffer[done % buffer.Length]; + + entry.value.Serialize(entry.writer); - private struct ConsumableEntry { - public ISerializable value; - public BinaryMemoryWriter writer; - } - - private sealed class Consumer { - private ParallelSaveStrategy owner; - - public ManualResetEvent completionEvent; - - public ConsumableEntry[] buffer; - public int head, done, tail; - - private Thread thread; - - public Consumer( ParallelSaveStrategy owner, int bufferSize ) { - this.owner = owner; - - buffer = new ConsumableEntry[bufferSize]; - - for ( int i = 0; i < buffer.Length; ++i ) { - buffer[i].writer = new BinaryMemoryWriter(); - } - - completionEvent = new ManualResetEvent( false ); - - thread = new Thread( Processor ); - - thread.Name = "Parallel Serialization Thread"; - - thread.Start(); - } - - private void Processor() { - try { - while ( !owner.finished ) { - Process(); - Thread.Sleep( 0 ); - } - - Process(); - - completionEvent.Set(); - } catch ( Exception ex ) { - Console.WriteLine( ex ); - } - } - - private void Process() { - ConsumableEntry entry; - - while ( done < tail ) { - entry = buffer[done % buffer.Length]; - - entry.value.Serialize( entry.writer ); - - ++done; - } - } - } - } -} + ++done; + } + } + } + } +} \ No newline at end of file diff --git a/Server/Persistence/Persistence.cs b/Server/Persistence/Persistence.cs index fb7ca2cc4..1da7d14e4 100644 --- a/Server/Persistence/Persistence.cs +++ b/Server/Persistence/Persistence.cs @@ -1,117 +1,105 @@ #region References + using System; using System.IO; + #endregion namespace Server { - public static class Persistence - { - public static void Serialize(string path, Action serializer) - { - Serialize(new FileInfo(path), serializer); - } + public static class Persistence + { + public static void Serialize(string path, Action serializer) + { + Serialize(new FileInfo(path), serializer); + } - public static void Serialize(FileInfo file, Action serializer) - { - file.Refresh(); + public static void Serialize(FileInfo file, Action serializer) + { + file.Refresh(); - if (file.Directory != null && !file.Directory.Exists) - { - file.Directory.Create(); - } + if (file.Directory != null && !file.Directory.Exists) file.Directory.Create(); - if (!file.Exists) - { - file.Create().Close(); - } - - file.Refresh(); + if (!file.Exists) file.Create().Close(); - using (var fs = file.OpenWrite()) - { - var writer = new BinaryFileWriter(fs, true); + file.Refresh(); - try - { - serializer(writer); - } - finally - { - writer.Flush(); - writer.Close(); - } - } - } + using (FileStream fs = file.OpenWrite()) + { + BinaryFileWriter writer = new BinaryFileWriter(fs, true); - public static void Deserialize(string path, Action deserializer) - { - Deserialize(path, deserializer, true); - } + try + { + serializer(writer); + } + finally + { + writer.Flush(); + writer.Close(); + } + } + } - public static void Deserialize(FileInfo file, Action deserializer) - { - Deserialize(file, deserializer, true); - } + public static void Deserialize(string path, Action deserializer) + { + Deserialize(path, deserializer, true); + } - public static void Deserialize(string path, Action deserializer, bool ensure) - { - Deserialize(new FileInfo(path), deserializer, ensure); - } + public static void Deserialize(FileInfo file, Action deserializer) + { + Deserialize(file, deserializer, true); + } - public static void Deserialize(FileInfo file, Action deserializer, bool ensure) - { - file.Refresh(); + public static void Deserialize(string path, Action deserializer, bool ensure) + { + Deserialize(new FileInfo(path), deserializer, ensure); + } - if (file.Directory != null && !file.Directory.Exists) - { - if (!ensure) - { - throw new DirectoryNotFoundException(); - } + public static void Deserialize(FileInfo file, Action deserializer, bool ensure) + { + file.Refresh(); - file.Directory.Create(); - } - - if (!file.Exists) - { - if (!ensure) - { - throw new FileNotFoundException - { - Source = file.FullName - }; - } + if (file.Directory != null && !file.Directory.Exists) + { + if (!ensure) throw new DirectoryNotFoundException(); - file.Create().Close(); - } - - file.Refresh(); + file.Directory.Create(); + } - using (var fs = file.OpenRead()) - { - var reader = new BinaryFileReader(new BinaryReader(fs)); + if (!file.Exists) + { + if (!ensure) + throw new FileNotFoundException + { + Source = file.FullName + }; - try - { - deserializer(reader); - } - catch (EndOfStreamException eos) - { - if (file.Length > 0) - { - Console.WriteLine("[Persistence]: {0}", eos); - } - } - catch (Exception e) - { - Console.WriteLine("[Persistence]: {0}", e); - } - finally - { - reader.Close(); - } - } - } - } + file.Create().Close(); + } + + file.Refresh(); + + using (FileStream fs = file.OpenRead()) + { + BinaryFileReader reader = new BinaryFileReader(new BinaryReader(fs)); + + try + { + deserializer(reader); + } + catch (EndOfStreamException eos) + { + if (file.Length > 0) Console.WriteLine("[Persistence]: {0}", eos); + } + catch (Exception e) + { + Console.WriteLine("[Persistence]: {0}", e); + } + finally + { + reader.Close(); + } + } + } + } } \ No newline at end of file diff --git a/Server/Persistence/QueuedMemoryWriter.cs b/Server/Persistence/QueuedMemoryWriter.cs index a111e377a..f4ad4981a 100644 --- a/Server/Persistence/QueuedMemoryWriter.cs +++ b/Server/Persistence/QueuedMemoryWriter.cs @@ -18,104 +18,104 @@ * ***************************************************************************/ -using System.IO; using System.Collections.Generic; +using System.IO; namespace Server { - public sealed class QueuedMemoryWriter : BinaryFileWriter - { - private struct IndexInfo - { - public int size; - public int typeCode; - public int serial; - } + public sealed class QueuedMemoryWriter : BinaryFileWriter + { + private MemoryStream _memStream; + private List _orderedIndexInfo = new List(); - private MemoryStream _memStream; - private List _orderedIndexInfo = new List(); + public QueuedMemoryWriter() + : base(new MemoryStream(1024 * 1024), true) + { + _memStream = UnderlyingStream as MemoryStream; + } - protected override int BufferSize => 512; + protected override int BufferSize => 512; - public QueuedMemoryWriter() - : base(new MemoryStream(1024 * 1024), true) - { - _memStream = UnderlyingStream as MemoryStream; - } + public void QueueForIndex(ISerializable serializable, int size) + { + IndexInfo info; - public void QueueForIndex(ISerializable serializable, int size) - { - IndexInfo info; + info.size = size; - info.size = size; + info.typeCode = serializable.TypeReference; //For guilds, this will automagically be zero. + info.serial = serializable.SerialIdentity; - info.typeCode = serializable.TypeReference; //For guilds, this will automagically be zero. - info.serial = serializable.SerialIdentity; + _orderedIndexInfo.Add(info); + } - _orderedIndexInfo.Add(info); - } + public void CommitTo(SequentialFileWriter dataFile, SequentialFileWriter indexFile) + { + Flush(); - public void CommitTo(SequentialFileWriter dataFile, SequentialFileWriter indexFile) - { - Flush(); + int memLength = (int)_memStream.Position; - int memLength = (int)_memStream.Position; + if (memLength > 0) + { + byte[] memBuffer = _memStream.GetBuffer(); - if (memLength > 0) - { - byte[] memBuffer = _memStream.GetBuffer(); + long actualPosition = dataFile.Position; - long actualPosition = dataFile.Position; + dataFile.Write(memBuffer, 0, memLength); //The buffer contains the data from many items. - dataFile.Write(memBuffer, 0, memLength); //The buffer contains the data from many items. + //Console.WriteLine("Writing {0} bytes starting at {1}, with {2} things", memLength, actualPosition, _orderedIndexInfo.Count); - //Console.WriteLine("Writing {0} bytes starting at {1}, with {2} things", memLength, actualPosition, _orderedIndexInfo.Count); + byte[] indexBuffer = new byte[20]; - byte[] indexBuffer = new byte[20]; + //int indexWritten = _orderedIndexInfo.Count * indexBuffer.Length; + //int totalWritten = memLength + indexWritten - //int indexWritten = _orderedIndexInfo.Count * indexBuffer.Length; - //int totalWritten = memLength + indexWritten + for (int i = 0; i < _orderedIndexInfo.Count; i++) + { + IndexInfo info = _orderedIndexInfo[i]; - for (int i = 0; i < _orderedIndexInfo.Count; i++) - { - IndexInfo info = _orderedIndexInfo[i]; - - int typeCode = info.typeCode; - int serial = info.serial; - int length = info.size; + int typeCode = info.typeCode; + int serial = info.serial; + int length = info.size; - indexBuffer[0] = (byte)(info.typeCode); - indexBuffer[1] = (byte)(info.typeCode >> 8); - indexBuffer[2] = (byte)(info.typeCode >> 16); - indexBuffer[3] = (byte)(info.typeCode >> 24); + indexBuffer[0] = (byte)info.typeCode; + indexBuffer[1] = (byte)(info.typeCode >> 8); + indexBuffer[2] = (byte)(info.typeCode >> 16); + indexBuffer[3] = (byte)(info.typeCode >> 24); - indexBuffer[4] = (byte)(info.serial); - indexBuffer[5] = (byte)(info.serial >> 8); - indexBuffer[6] = (byte)(info.serial >> 16); - indexBuffer[7] = (byte)(info.serial >> 24); + indexBuffer[4] = (byte)info.serial; + indexBuffer[5] = (byte)(info.serial >> 8); + indexBuffer[6] = (byte)(info.serial >> 16); + indexBuffer[7] = (byte)(info.serial >> 24); - indexBuffer[8] = (byte)(actualPosition); - indexBuffer[9] = (byte)(actualPosition >> 8); - indexBuffer[10] = (byte)(actualPosition >> 16); - indexBuffer[11] = (byte)(actualPosition >> 24); - indexBuffer[12] = (byte)(actualPosition >> 32); - indexBuffer[13] = (byte)(actualPosition >> 40); - indexBuffer[14] = (byte)(actualPosition >> 48); - indexBuffer[15] = (byte)(actualPosition >> 56); + indexBuffer[8] = (byte)actualPosition; + indexBuffer[9] = (byte)(actualPosition >> 8); + indexBuffer[10] = (byte)(actualPosition >> 16); + indexBuffer[11] = (byte)(actualPosition >> 24); + indexBuffer[12] = (byte)(actualPosition >> 32); + indexBuffer[13] = (byte)(actualPosition >> 40); + indexBuffer[14] = (byte)(actualPosition >> 48); + indexBuffer[15] = (byte)(actualPosition >> 56); - indexBuffer[16] = (byte)(info.size); - indexBuffer[17] = (byte)(info.size >> 8); - indexBuffer[18] = (byte)(info.size >> 16); - indexBuffer[19] = (byte)(info.size >> 24); + indexBuffer[16] = (byte)info.size; + indexBuffer[17] = (byte)(info.size >> 8); + indexBuffer[18] = (byte)(info.size >> 16); + indexBuffer[19] = (byte)(info.size >> 24); - indexFile.Write(indexBuffer, 0, indexBuffer.Length); + indexFile.Write(indexBuffer, 0, indexBuffer.Length); - actualPosition += info.size; - } - } + actualPosition += info.size; + } + } - Close(); //We're done with this writer. - } - } + Close(); //We're done with this writer. + } + + private struct IndexInfo + { + public int size; + public int typeCode; + public int serial; + } + } } \ No newline at end of file diff --git a/Server/Persistence/SaveMetrics.cs b/Server/Persistence/SaveMetrics.cs index 52e1f3e71..0ee2136d6 100644 --- a/Server/Persistence/SaveMetrics.cs +++ b/Server/Persistence/SaveMetrics.cs @@ -21,109 +21,120 @@ using System; using System.Diagnostics; -namespace Server { - public sealed class SaveMetrics : IDisposable { - private const string PerformanceCategoryName = "RunUO 2.1"; - private const string PerformanceCategoryDesc = "Performance counters for RunUO 2.1."; +namespace Server +{ + public sealed class SaveMetrics : IDisposable + { + private const string PerformanceCategoryName = "RunUO 2.1"; + private const string PerformanceCategoryDesc = "Performance counters for RunUO 2.1."; - private PerformanceCounter numberOfWorldSaves; + private bool isDisposed; - private PerformanceCounter itemsPerSecond; - private PerformanceCounter mobilesPerSecond; + private PerformanceCounter itemsPerSecond; + private PerformanceCounter mobilesPerSecond; - private PerformanceCounter serializedBytesPerSecond; - private PerformanceCounter writtenBytesPerSecond; + private PerformanceCounter numberOfWorldSaves; - public SaveMetrics() { - if ( !PerformanceCounterCategory.Exists( PerformanceCategoryName ) ) { - CounterCreationDataCollection counters = new CounterCreationDataCollection(); + private PerformanceCounter serializedBytesPerSecond; + private PerformanceCounter writtenBytesPerSecond; - counters.Add( new CounterCreationData( - "Save - Count", - "Number of world saves.", - PerformanceCounterType.NumberOfItems32 - ) - ); + public SaveMetrics() + { + if (!PerformanceCounterCategory.Exists(PerformanceCategoryName)) + { + CounterCreationDataCollection counters = new CounterCreationDataCollection(); - counters.Add( new CounterCreationData( - "Save - Items/sec", - "Number of items saved per second.", - PerformanceCounterType.RateOfCountsPerSecond32 - ) - ); + counters.Add(new CounterCreationData( + "Save - Count", + "Number of world saves.", + PerformanceCounterType.NumberOfItems32 + ) + ); - counters.Add( new CounterCreationData( - "Save - Mobiles/sec", - "Number of mobiles saved per second.", - PerformanceCounterType.RateOfCountsPerSecond32 - ) - ); + counters.Add(new CounterCreationData( + "Save - Items/sec", + "Number of items saved per second.", + PerformanceCounterType.RateOfCountsPerSecond32 + ) + ); - counters.Add( new CounterCreationData( - "Save - Serialized bytes/sec", - "Amount of world-save bytes serialized per second.", - PerformanceCounterType.RateOfCountsPerSecond32 - ) - ); + counters.Add(new CounterCreationData( + "Save - Mobiles/sec", + "Number of mobiles saved per second.", + PerformanceCounterType.RateOfCountsPerSecond32 + ) + ); - counters.Add( new CounterCreationData( - "Save - Written bytes/sec", - "Amount of world-save bytes written to disk per second.", - PerformanceCounterType.RateOfCountsPerSecond32 - ) - ); + counters.Add(new CounterCreationData( + "Save - Serialized bytes/sec", + "Amount of world-save bytes serialized per second.", + PerformanceCounterType.RateOfCountsPerSecond32 + ) + ); + + counters.Add(new CounterCreationData( + "Save - Written bytes/sec", + "Amount of world-save bytes written to disk per second.", + PerformanceCounterType.RateOfCountsPerSecond32 + ) + ); #if !MONO - PerformanceCounterCategory.Create( PerformanceCategoryName, PerformanceCategoryDesc, PerformanceCounterCategoryType.SingleInstance, counters ); + PerformanceCounterCategory.Create(PerformanceCategoryName, PerformanceCategoryDesc, + PerformanceCounterCategoryType.SingleInstance, counters); #endif - } + } - numberOfWorldSaves = new PerformanceCounter( PerformanceCategoryName, "Save - Count", false ); + numberOfWorldSaves = new PerformanceCounter(PerformanceCategoryName, "Save - Count", false); - itemsPerSecond = new PerformanceCounter( PerformanceCategoryName, "Save - Items/sec", false ); - mobilesPerSecond = new PerformanceCounter( PerformanceCategoryName, "Save - Mobiles/sec", false ); + itemsPerSecond = new PerformanceCounter(PerformanceCategoryName, "Save - Items/sec", false); + mobilesPerSecond = new PerformanceCounter(PerformanceCategoryName, "Save - Mobiles/sec", false); - serializedBytesPerSecond = new PerformanceCounter( PerformanceCategoryName, "Save - Serialized bytes/sec", false ); - writtenBytesPerSecond = new PerformanceCounter( PerformanceCategoryName, "Save - Written bytes/sec", false ); + serializedBytesPerSecond = new PerformanceCounter(PerformanceCategoryName, "Save - Serialized bytes/sec", false); + writtenBytesPerSecond = new PerformanceCounter(PerformanceCategoryName, "Save - Written bytes/sec", false); - // increment number of world saves - numberOfWorldSaves.Increment(); - } + // increment number of world saves + numberOfWorldSaves.Increment(); + } - public void OnItemSaved( int numberOfBytes ) { - itemsPerSecond.Increment(); + public void Dispose() + { + if (!isDisposed) + { + isDisposed = true; - serializedBytesPerSecond.IncrementBy( numberOfBytes ); - } + numberOfWorldSaves.Dispose(); - public void OnMobileSaved( int numberOfBytes ) { - mobilesPerSecond.Increment(); + itemsPerSecond.Dispose(); + mobilesPerSecond.Dispose(); - serializedBytesPerSecond.IncrementBy( numberOfBytes ); - } + serializedBytesPerSecond.Dispose(); + writtenBytesPerSecond.Dispose(); + } + } - public void OnGuildSaved( int numberOfBytes ) { - serializedBytesPerSecond.IncrementBy( numberOfBytes ); - } + public void OnItemSaved(int numberOfBytes) + { + itemsPerSecond.Increment(); - public void OnFileWritten( int numberOfBytes ) { - writtenBytesPerSecond.IncrementBy( numberOfBytes ); - } + serializedBytesPerSecond.IncrementBy(numberOfBytes); + } - private bool isDisposed; + public void OnMobileSaved(int numberOfBytes) + { + mobilesPerSecond.Increment(); - public void Dispose() { - if ( !isDisposed ) { - isDisposed = true; + serializedBytesPerSecond.IncrementBy(numberOfBytes); + } - numberOfWorldSaves.Dispose(); + public void OnGuildSaved(int numberOfBytes) + { + serializedBytesPerSecond.IncrementBy(numberOfBytes); + } - itemsPerSecond.Dispose(); - mobilesPerSecond.Dispose(); - - serializedBytesPerSecond.Dispose(); - writtenBytesPerSecond.Dispose(); - } - } - } -} + public void OnFileWritten(int numberOfBytes) + { + writtenBytesPerSecond.IncrementBy(numberOfBytes); + } + } +} \ No newline at end of file diff --git a/Server/Persistence/SaveStrategy.cs b/Server/Persistence/SaveStrategy.cs index 94bb4e6a4..9da97f2e5 100644 --- a/Server/Persistence/SaveStrategy.cs +++ b/Server/Persistence/SaveStrategy.cs @@ -20,28 +20,28 @@ namespace Server { - public abstract class SaveStrategy - { - public static SaveStrategy Acquire() - { - if (Core.MultiProcessor) - { - int processorCount = Core.ProcessorCount; + public abstract class SaveStrategy + { + public abstract string Name{ get; } - if (processorCount > 2) - { - return new DualSaveStrategy(); // return new DynamicSaveStrategy(); (4.0 or return new ParallelSaveStrategy(processorCount); (2.0) - } + public static SaveStrategy Acquire() + { + if (Core.MultiProcessor) + { + int processorCount = Core.ProcessorCount; - return new DualSaveStrategy(); - } + if (processorCount > 2) + return + new DualSaveStrategy(); // return new DynamicSaveStrategy(); (4.0 or return new ParallelSaveStrategy(processorCount); (2.0) - return new StandardSaveStrategy(); - } + return new DualSaveStrategy(); + } - public abstract string Name { get; } - public abstract void Save(SaveMetrics metrics, bool permitBackgroundWrite); + return new StandardSaveStrategy(); + } - public abstract void ProcessDecay(); - } + public abstract void Save(SaveMetrics metrics, bool permitBackgroundWrite); + + public abstract void ProcessDecay(); + } } \ No newline at end of file diff --git a/Server/Persistence/SequentialFileWriter.cs b/Server/Persistence/SequentialFileWriter.cs index 55e09a9eb..be4b569e9 100644 --- a/Server/Persistence/SequentialFileWriter.cs +++ b/Server/Persistence/SequentialFileWriter.cs @@ -21,102 +21,114 @@ using System; using System.IO; -namespace Server { - public sealed class SequentialFileWriter : Stream { - private FileStream fileStream; - private FileQueue fileQueue; +namespace Server +{ + public sealed class SequentialFileWriter : Stream + { + private FileQueue fileQueue; + private FileStream fileStream; - private AsyncCallback writeCallback; + private SaveMetrics metrics; - private SaveMetrics metrics; + private AsyncCallback writeCallback; - public SequentialFileWriter( string path, SaveMetrics metrics ) { - if ( path == null ) { - throw new ArgumentNullException( "path" ); - } + public SequentialFileWriter(string path, SaveMetrics metrics) + { + if (path == null) throw new ArgumentNullException("path"); - this.metrics = metrics; + this.metrics = metrics; - fileStream = FileOperations.OpenSequentialStream( path, FileMode.Create, FileAccess.Write, FileShare.None ); + fileStream = FileOperations.OpenSequentialStream(path, FileMode.Create, FileAccess.Write, FileShare.None); - fileQueue = new FileQueue( - Math.Max( 1, FileOperations.Concurrency ), - FileCallback - ); - } + fileQueue = new FileQueue( + Math.Max(1, FileOperations.Concurrency), + FileCallback + ); + } - public override long Position { - get => fileQueue.Position; - set => throw new InvalidOperationException(); - } + public override long Position + { + get => fileQueue.Position; + set => throw new InvalidOperationException(); + } - private void FileCallback( FileQueue.Chunk chunk ) { - if ( FileOperations.AreSynchronous ) { - fileStream.Write( chunk.Buffer, chunk.Offset, chunk.Size ); + public override bool CanRead => false; - metrics?.OnFileWritten( chunk.Size ); + public override bool CanSeek => false; - chunk.Commit(); - } else { - if ( writeCallback == null ) { - writeCallback = OnWrite; - } + public override bool CanWrite => true; - fileStream.BeginWrite( chunk.Buffer, chunk.Offset, chunk.Size, writeCallback, chunk ); - } - } + public override long Length => Position; - private void OnWrite( IAsyncResult asyncResult ) { - FileQueue.Chunk chunk = asyncResult.AsyncState as FileQueue.Chunk; + private void FileCallback(FileQueue.Chunk chunk) + { + if (FileOperations.AreSynchronous) + { + fileStream.Write(chunk.Buffer, chunk.Offset, chunk.Size); - fileStream.EndWrite( asyncResult ); + metrics?.OnFileWritten(chunk.Size); - metrics?.OnFileWritten( chunk.Size ); + chunk.Commit(); + } + else + { + if (writeCallback == null) writeCallback = OnWrite; - chunk.Commit(); - } + fileStream.BeginWrite(chunk.Buffer, chunk.Offset, chunk.Size, writeCallback, chunk); + } + } - public override void Write( byte[] buffer, int offset, int size ) { - fileQueue.Enqueue( buffer, offset, size ); - } + private void OnWrite(IAsyncResult asyncResult) + { + FileQueue.Chunk chunk = asyncResult.AsyncState as FileQueue.Chunk; - public override void Flush() { - fileQueue.Flush(); - fileStream.Flush(); - } + fileStream.EndWrite(asyncResult); - protected override void Dispose( bool disposing ) { - if ( fileStream != null ) { - Flush(); + metrics?.OnFileWritten(chunk.Size); - fileQueue.Dispose(); - fileQueue = null; + chunk.Commit(); + } - fileStream.Close(); - fileStream = null; - } + public override void Write(byte[] buffer, int offset, int size) + { + fileQueue.Enqueue(buffer, offset, size); + } - base.Dispose( disposing ); - } + public override void Flush() + { + fileQueue.Flush(); + fileStream.Flush(); + } - public override bool CanRead => false; + protected override void Dispose(bool disposing) + { + if (fileStream != null) + { + Flush(); - public override bool CanSeek => false; + fileQueue.Dispose(); + fileQueue = null; - public override bool CanWrite => true; + fileStream.Close(); + fileStream = null; + } - public override long Length => Position; + base.Dispose(disposing); + } - public override int Read( byte[] buffer, int offset, int count ) { - throw new InvalidOperationException(); - } + public override int Read(byte[] buffer, int offset, int count) + { + throw new InvalidOperationException(); + } - public override long Seek( long offset, SeekOrigin origin ) { - throw new InvalidOperationException(); - } + public override long Seek(long offset, SeekOrigin origin) + { + throw new InvalidOperationException(); + } - public override void SetLength( long value ) { - fileStream.SetLength( value ); - } - } -} + public override void SetLength(long value) + { + fileStream.SetLength(value); + } + } +} \ No newline at end of file diff --git a/Server/Persistence/StandardSaveStrategy.cs b/Server/Persistence/StandardSaveStrategy.cs index 2356427f5..0894434a7 100644 --- a/Server/Persistence/StandardSaveStrategy.cs +++ b/Server/Persistence/StandardSaveStrategy.cs @@ -22,180 +22,191 @@ using System; using System.Collections.Generic; using Server.Guilds; -namespace Server { - public class StandardSaveStrategy : SaveStrategy { - public enum SaveOption - { - Normal, - Threaded - } +namespace Server +{ + public class StandardSaveStrategy : SaveStrategy + { + public enum SaveOption + { + Normal, + Threaded + } - public static SaveOption SaveType = SaveOption.Normal; + public static SaveOption SaveType = SaveOption.Normal; - public override string Name => "Standard"; + private Queue _decayQueue; - private Queue _decayQueue; + public StandardSaveStrategy() + { + _decayQueue = new Queue(); + } - public StandardSaveStrategy() { - _decayQueue = new Queue(); - } + public override string Name => "Standard"; - protected bool PermitBackgroundWrite { get; set; } + protected bool PermitBackgroundWrite{ get; set; } - protected bool UseSequentialWriters => (SaveType == SaveOption.Normal || !PermitBackgroundWrite); + protected bool UseSequentialWriters => SaveType == SaveOption.Normal || !PermitBackgroundWrite; - public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) - { - PermitBackgroundWrite = permitBackgroundWrite; + public override void Save(SaveMetrics metrics, bool permitBackgroundWrite) + { + PermitBackgroundWrite = permitBackgroundWrite; - SaveMobiles(metrics); - SaveItems(metrics); - SaveGuilds(metrics); + SaveMobiles(metrics); + SaveItems(metrics); + SaveGuilds(metrics); - if (permitBackgroundWrite && UseSequentialWriters) //If we're permitted to write in the background, but we don't anyways, then notify. - World.NotifyDiskWriteComplete(); - } + if (permitBackgroundWrite && UseSequentialWriters + ) //If we're permitted to write in the background, but we don't anyways, then notify. + World.NotifyDiskWriteComplete(); + } - protected void SaveMobiles(SaveMetrics metrics) - { - Dictionary mobiles = World.Mobiles; + protected void SaveMobiles(SaveMetrics metrics) + { + Dictionary mobiles = World.Mobiles; - GenericWriter idx; - GenericWriter tdb; - GenericWriter bin; + GenericWriter idx; + GenericWriter tdb; + GenericWriter bin; - if (UseSequentialWriters) - { - idx = new BinaryFileWriter( World.MobileIndexPath, false ); - tdb = new BinaryFileWriter( World.MobileTypesPath, false ); - bin = new BinaryFileWriter( World.MobileDataPath, true ); - } else { - idx = new AsyncWriter( World.MobileIndexPath, false ); - tdb = new AsyncWriter( World.MobileTypesPath, false ); - bin = new AsyncWriter( World.MobileDataPath, true ); - } + if (UseSequentialWriters) + { + idx = new BinaryFileWriter(World.MobileIndexPath, false); + tdb = new BinaryFileWriter(World.MobileTypesPath, false); + bin = new BinaryFileWriter(World.MobileDataPath, true); + } + else + { + idx = new AsyncWriter(World.MobileIndexPath, false); + tdb = new AsyncWriter(World.MobileTypesPath, false); + bin = new AsyncWriter(World.MobileDataPath, true); + } - idx.Write( ( int ) mobiles.Count ); - foreach ( Mobile m in mobiles.Values ) { - long start = bin.Position; + idx.Write(mobiles.Count); + foreach (Mobile m in mobiles.Values) + { + long start = bin.Position; - idx.Write( ( int ) m.m_TypeRef ); - idx.Write( ( int ) m.Serial ); - idx.Write( ( long ) start ); + idx.Write(m.m_TypeRef); + idx.Write(m.Serial); + idx.Write(start); - m.Serialize( bin ); + m.Serialize(bin); - metrics?.OnMobileSaved( ( int ) ( bin.Position - start ) ); + metrics?.OnMobileSaved((int)(bin.Position - start)); - idx.Write( ( int ) ( bin.Position - start ) ); + idx.Write((int)(bin.Position - start)); - m.FreeCache(); - } + m.FreeCache(); + } - tdb.Write( ( int ) World.m_MobileTypes.Count ); + tdb.Write(World.m_MobileTypes.Count); - for ( int i = 0; i < World.m_MobileTypes.Count; ++i ) - tdb.Write( World.m_MobileTypes[i].FullName ); + for (int i = 0; i < World.m_MobileTypes.Count; ++i) + tdb.Write(World.m_MobileTypes[i].FullName); - idx.Close(); - tdb.Close(); - bin.Close(); - } + idx.Close(); + tdb.Close(); + bin.Close(); + } - protected void SaveItems(SaveMetrics metrics) - { - Dictionary items = World.Items; + protected void SaveItems(SaveMetrics metrics) + { + Dictionary items = World.Items; - GenericWriter idx; - GenericWriter tdb; - GenericWriter bin; + GenericWriter idx; + GenericWriter tdb; + GenericWriter bin; - if (UseSequentialWriters) - { - idx = new BinaryFileWriter( World.ItemIndexPath, false ); - tdb = new BinaryFileWriter( World.ItemTypesPath, false ); - bin = new BinaryFileWriter( World.ItemDataPath, true ); - } else { - idx = new AsyncWriter( World.ItemIndexPath, false ); - tdb = new AsyncWriter( World.ItemTypesPath, false ); - bin = new AsyncWriter( World.ItemDataPath, true ); - } + if (UseSequentialWriters) + { + idx = new BinaryFileWriter(World.ItemIndexPath, false); + tdb = new BinaryFileWriter(World.ItemTypesPath, false); + bin = new BinaryFileWriter(World.ItemDataPath, true); + } + else + { + idx = new AsyncWriter(World.ItemIndexPath, false); + tdb = new AsyncWriter(World.ItemTypesPath, false); + bin = new AsyncWriter(World.ItemDataPath, true); + } - idx.Write( ( int ) items.Count ); + idx.Write(items.Count); - DateTime n = DateTime.UtcNow; + DateTime n = DateTime.UtcNow; - foreach ( Item item in items.Values ) { - if (item.Decays && item.Parent == null && item.Map != Map.Internal && (item.LastMoved + item.DecayTime) <= n) - { - _decayQueue.Enqueue( item ); - } + foreach (Item item in items.Values) + { + if (item.Decays && item.Parent == null && item.Map != Map.Internal && item.LastMoved + item.DecayTime <= n) + _decayQueue.Enqueue(item); - long start = bin.Position; + long start = bin.Position; - idx.Write( ( int ) item.m_TypeRef ); - idx.Write( ( int ) item.Serial ); - idx.Write( ( long ) start ); + idx.Write(item.m_TypeRef); + idx.Write(item.Serial); + idx.Write(start); - item.Serialize( bin ); + item.Serialize(bin); - metrics?.OnItemSaved( ( int ) ( bin.Position - start ) ); + metrics?.OnItemSaved((int)(bin.Position - start)); - idx.Write( ( int ) ( bin.Position - start ) ); + idx.Write((int)(bin.Position - start)); - item.FreeCache(); - } + item.FreeCache(); + } - tdb.Write( ( int ) World.m_ItemTypes.Count ); - for ( int i = 0; i < World.m_ItemTypes.Count; ++i ) - tdb.Write( World.m_ItemTypes[i].FullName ); + tdb.Write(World.m_ItemTypes.Count); + for (int i = 0; i < World.m_ItemTypes.Count; ++i) + tdb.Write(World.m_ItemTypes[i].FullName); - idx.Close(); - tdb.Close(); - bin.Close(); - } + idx.Close(); + tdb.Close(); + bin.Close(); + } - protected void SaveGuilds(SaveMetrics metrics) - { - GenericWriter idx; - GenericWriter bin; + protected void SaveGuilds(SaveMetrics metrics) + { + GenericWriter idx; + GenericWriter bin; - if (UseSequentialWriters) - { - idx = new BinaryFileWriter( World.GuildIndexPath, false ); - bin = new BinaryFileWriter( World.GuildDataPath, true ); - } else { - idx = new AsyncWriter( World.GuildIndexPath, false ); - bin = new AsyncWriter( World.GuildDataPath, true ); - } + if (UseSequentialWriters) + { + idx = new BinaryFileWriter(World.GuildIndexPath, false); + bin = new BinaryFileWriter(World.GuildDataPath, true); + } + else + { + idx = new AsyncWriter(World.GuildIndexPath, false); + bin = new AsyncWriter(World.GuildDataPath, true); + } - idx.Write( ( int ) BaseGuild.List.Count ); - foreach ( BaseGuild guild in BaseGuild.List.Values ) { - long start = bin.Position; + idx.Write(BaseGuild.List.Count); + foreach (BaseGuild guild in BaseGuild.List.Values) + { + long start = bin.Position; - idx.Write( ( int ) 0 );//guilds have no typeid - idx.Write( ( int ) guild.Id ); - idx.Write( ( long ) start ); + idx.Write(0); //guilds have no typeid + idx.Write(guild.Id); + idx.Write(start); - guild.Serialize( bin ); + guild.Serialize(bin); - metrics?.OnGuildSaved( ( int ) ( bin.Position - start ) ); + metrics?.OnGuildSaved((int)(bin.Position - start)); - idx.Write( ( int ) ( bin.Position - start ) ); - } + idx.Write((int)(bin.Position - start)); + } - idx.Close(); - bin.Close(); - } + idx.Close(); + bin.Close(); + } - public override void ProcessDecay() { - while ( _decayQueue.Count > 0 ) { - Item item = _decayQueue.Dequeue(); + public override void ProcessDecay() + { + while (_decayQueue.Count > 0) + { + Item item = _decayQueue.Dequeue(); - if ( item.OnDecay() ) { - item.Delete(); - } - } - } - } -} + if (item.OnDecay()) item.Delete(); + } + } + } +} \ No newline at end of file diff --git a/Server/Point3DList.cs b/Server/Point3DList.cs index 2309c04de..635121987 100644 --- a/Server/Point3DList.cs +++ b/Server/Point3DList.cs @@ -20,76 +20,75 @@ namespace Server { - public class Point3DList - { - private Point3D[] m_List; + public class Point3DList + { + private static Point3D[] m_EmptyList = new Point3D[0]; + private Point3D[] m_List; - public Point3DList() - { - m_List = new Point3D[8]; - Count = 0; - } + public Point3DList() + { + m_List = new Point3D[8]; + Count = 0; + } - public int Count { get; private set; } + public int Count{ get; private set; } - public void Clear() - { - Count = 0; - } + public Point3D Last => m_List[Count - 1]; - public Point3D Last => m_List[Count - 1]; + public Point3D this[int index] => m_List[index]; - public Point3D this[int index] => m_List[index]; + public void Clear() + { + Count = 0; + } - public void Add( int x, int y, int z ) - { - if ( (Count + 1) > m_List.Length ) - { - Point3D[] old = m_List; - m_List = new Point3D[old.Length * 2]; + public void Add(int x, int y, int z) + { + if (Count + 1 > m_List.Length) + { + Point3D[] old = m_List; + m_List = new Point3D[old.Length * 2]; - for ( int i = 0; i < old.Length; ++i ) - m_List[i] = old[i]; - } + for (int i = 0; i < old.Length; ++i) + m_List[i] = old[i]; + } - m_List[Count].m_X = x; - m_List[Count].m_Y = y; - m_List[Count].m_Z = z; - ++Count; - } + m_List[Count].m_X = x; + m_List[Count].m_Y = y; + m_List[Count].m_Z = z; + ++Count; + } - public void Add( Point3D p ) - { - if ( (Count + 1) > m_List.Length ) - { - Point3D[] old = m_List; - m_List = new Point3D[old.Length * 2]; + public void Add(Point3D p) + { + if (Count + 1 > m_List.Length) + { + Point3D[] old = m_List; + m_List = new Point3D[old.Length * 2]; - for ( int i = 0; i < old.Length; ++i ) - m_List[i] = old[i]; - } + for (int i = 0; i < old.Length; ++i) + m_List[i] = old[i]; + } - m_List[Count].m_X = p.m_X; - m_List[Count].m_Y = p.m_Y; - m_List[Count].m_Z = p.m_Z; - ++Count; - } + m_List[Count].m_X = p.m_X; + m_List[Count].m_Y = p.m_Y; + m_List[Count].m_Z = p.m_Z; + ++Count; + } - private static Point3D[] m_EmptyList = new Point3D[0]; + public Point3D[] ToArray() + { + if (Count == 0) + return m_EmptyList; - public Point3D[] ToArray() - { - if ( Count == 0 ) - return m_EmptyList; + Point3D[] list = new Point3D[Count]; - Point3D[] list = new Point3D[Count]; + for (int i = 0; i < Count; ++i) + list[i] = m_List[i]; - for ( int i = 0; i < Count; ++i ) - list[i] = m_List[i]; + Count = 0; - Count = 0; - - return list; - } - } + return list; + } + } } \ No newline at end of file diff --git a/Server/Poison.cs b/Server/Poison.cs index 4b9879a07..75188097f 100644 --- a/Server/Poison.cs +++ b/Server/Poison.cs @@ -23,113 +23,115 @@ using System.Collections.Generic; namespace Server { - [Parsable] - public abstract class Poison + [Parsable] + public abstract class Poison + { + /*public abstract TimeSpan Interval{ get; } + public abstract TimeSpan Duration{ get; }*/ + public abstract string Name{ get; } + public abstract int Level{ get; } + + public static Poison Lesser => GetPoison("Lesser"); + public static Poison Regular => GetPoison("Regular"); + public static Poison Greater => GetPoison("Greater"); + public static Poison Deadly => GetPoison("Deadly"); + public static Poison Lethal => GetPoison("Lethal"); + + public static List Poisons{ get; } = new List(); + + public abstract Timer ConstructTimer(Mobile m); + /*public abstract void OnDamage( Mobile m, ref object state );*/ + + public override string ToString() { - /*public abstract TimeSpan Interval{ get; } - public abstract TimeSpan Duration{ get; }*/ - public abstract string Name { get; } - public abstract int Level { get; } - public abstract Timer ConstructTimer( Mobile m ); - /*public abstract void OnDamage( Mobile m, ref object state );*/ - - public override string ToString() - { - return Name; - } - - - public static void Register( Poison reg ) - { - string regName = reg.Name.ToLower(); - - for ( int i = 0; i < Poisons.Count; i++ ) - { - if ( reg.Level == Poisons[i].Level ) - throw new Exception( "A poison with that level already exists." ); - if ( regName == Poisons[i].Name.ToLower() ) - throw new Exception( "A poison with that name already exists." ); - } - - Poisons.Add( reg ); - } - - public static Poison Lesser => GetPoison( "Lesser" ); - public static Poison Regular => GetPoison( "Regular" ); - public static Poison Greater => GetPoison( "Greater" ); - public static Poison Deadly => GetPoison( "Deadly" ); - public static Poison Lethal => GetPoison( "Lethal" ); - - public static List Poisons { get; } = new List(); - - public static Poison Parse( string value ) - { - Poison p = null; - - int plevel; - - if ( int.TryParse( value, out plevel ) ) - p = GetPoison( plevel ); - - if ( p == null ) - p = GetPoison( value ); - - return p; - } - - public static Poison GetPoison( int level ) - { - for ( int i = 0; i < Poisons.Count; ++i ) - { - Poison p = Poisons[i]; - - if ( p.Level == level ) - return p; - } - - return null; - } - - public static Poison GetPoison( string name ) - { - for ( int i = 0; i < Poisons.Count; ++i ) - { - Poison p = Poisons[i]; - - if ( Utility.InsensitiveCompare( p.Name, name ) == 0 ) - return p; - } - - return null; - } - - public static void Serialize( Poison p, GenericWriter writer ) - { - if ( p == null ) - { - writer.Write( (byte)0 ); - } - else - { - writer.Write( (byte)1 ); - writer.Write( (byte)p.Level ); - } - } - - public static Poison Deserialize( GenericReader reader ) - { - switch ( reader.ReadByte() ) - { - case 1: return GetPoison( reader.ReadByte() ); - case 2: - //no longer used, safe to remove? - reader.ReadInt(); - reader.ReadDouble(); - reader.ReadInt(); - reader.ReadTimeSpan(); - break; - } - return null; - } + return Name; } -} + + + public static void Register(Poison reg) + { + string regName = reg.Name.ToLower(); + + for (int i = 0; i < Poisons.Count; i++) + { + if (reg.Level == Poisons[i].Level) + throw new Exception("A poison with that level already exists."); + if (regName == Poisons[i].Name.ToLower()) + throw new Exception("A poison with that name already exists."); + } + + Poisons.Add(reg); + } + + public static Poison Parse(string value) + { + Poison p = null; + + int plevel; + + if (int.TryParse(value, out plevel)) + p = GetPoison(plevel); + + if (p == null) + p = GetPoison(value); + + return p; + } + + public static Poison GetPoison(int level) + { + for (int i = 0; i < Poisons.Count; ++i) + { + Poison p = Poisons[i]; + + if (p.Level == level) + return p; + } + + return null; + } + + public static Poison GetPoison(string name) + { + for (int i = 0; i < Poisons.Count; ++i) + { + Poison p = Poisons[i]; + + if (Utility.InsensitiveCompare(p.Name, name) == 0) + return p; + } + + return null; + } + + public static void Serialize(Poison p, GenericWriter writer) + { + if (p == null) + { + writer.Write((byte)0); + } + else + { + writer.Write((byte)1); + writer.Write((byte)p.Level); + } + } + + public static Poison Deserialize(GenericReader reader) + { + switch (reader.ReadByte()) + { + case 1: return GetPoison(reader.ReadByte()); + case 2: + //no longer used, safe to remove? + reader.ReadInt(); + reader.ReadDouble(); + reader.ReadInt(); + reader.ReadTimeSpan(); + break; + } + + return null; + } + } +} \ No newline at end of file diff --git a/Server/Prompt.cs b/Server/Prompt.cs index eb975c9e9..36c9de092 100644 --- a/Server/Prompt.cs +++ b/Server/Prompt.cs @@ -20,26 +20,26 @@ namespace Server.Prompts { - public abstract class Prompt - { - private static int m_Serials; + public abstract class Prompt + { + private static int m_Serials; - public int Serial { get; } + protected Prompt() + { + do + { + Serial = ++m_Serials; + } while (Serial == 0); + } - protected Prompt() - { - do - { - Serial = ++m_Serials; - } while ( Serial == 0 ); - } + public int Serial{ get; } - public virtual void OnCancel( Mobile from ) - { - } + public virtual void OnCancel(Mobile from) + { + } - public virtual void OnResponse( Mobile from, string text ) - { - } - } + public virtual void OnResponse(Mobile from, string text) + { + } + } } \ No newline at end of file diff --git a/Server/QuestArrow.cs b/Server/QuestArrow.cs index e83d1e4d4..5dd3cef2e 100644 --- a/Server/QuestArrow.cs +++ b/Server/QuestArrow.cs @@ -22,78 +22,79 @@ using Server.Network; namespace Server { - public class QuestArrow - { - public Mobile Mobile { get; } + public class QuestArrow + { + public QuestArrow(Mobile m, Mobile t) + { + Running = true; + Mobile = m; + Target = t; + } - public Mobile Target { get; } + public QuestArrow(Mobile m, Mobile t, int x, int y) : this(m, t) + { + Update(x, y); + } - public bool Running { get; private set; } + public Mobile Mobile{ get; } - public void Update() - { - Update( Target.X, Target.Y ); - } + public Mobile Target{ get; } - public void Update( int x, int y ) - { - if ( !Running ) - return; + public bool Running{ get; private set; } - NetState ns = Mobile.NetState; + public void Update() + { + Update(Target.X, Target.Y); + } - if ( ns == null ) - return; + public void Update(int x, int y) + { + if (!Running) + return; - if ( ns.HighSeas ) - ns.Send( new SetArrowHS( x, y, Target.Serial ) ); - else - ns.Send( new SetArrow( x, y ) ); - } + NetState ns = Mobile.NetState; - public void Stop() - { - Stop( Target.X, Target.Y ); - } + if (ns == null) + return; - public void Stop( int x, int y ) - { - if ( !Running ) - return; + if (ns.HighSeas) + ns.Send(new SetArrowHS(x, y, Target.Serial)); + else + ns.Send(new SetArrow(x, y)); + } - Mobile.ClearQuestArrow(); + public void Stop() + { + Stop(Target.X, Target.Y); + } - NetState ns = Mobile.NetState; + public void Stop(int x, int y) + { + if (!Running) + return; - if ( ns != null ) { - if ( ns.HighSeas ) - ns.Send( new CancelArrowHS( x, y, Target.Serial ) ); - else - ns.Send( new CancelArrow() ); - } + Mobile.ClearQuestArrow(); - Running = false; - OnStop(); - } + NetState ns = Mobile.NetState; - public virtual void OnStop() - { - } + if (ns != null) + { + if (ns.HighSeas) + ns.Send(new CancelArrowHS(x, y, Target.Serial)); + else + ns.Send(new CancelArrow()); + } - public virtual void OnClick( bool rightClick ) - { - } + Running = false; + OnStop(); + } - public QuestArrow( Mobile m, Mobile t ) - { - Running = true; - Mobile = m; - Target = t; - } + public virtual void OnStop() + { + } - public QuestArrow( Mobile m, Mobile t, int x, int y ) : this( m, t ) - { - Update( x, y ); - } - } + public virtual void OnClick(bool rightClick) + { + } + } } \ No newline at end of file diff --git a/Server/Race.cs b/Server/Race.cs index c5ece6643..e7d567d2e 100644 --- a/Server/Race.cs +++ b/Server/Race.cs @@ -23,146 +23,163 @@ using System.Collections.Generic; namespace Server { - [Parsable] - public abstract class Race - { - public static Race DefaultRace => Races[0]; + [Parsable] + public abstract class Race + { + private static string[] m_RaceNames; + private static Race[] m_RaceValues; - public static Race[] Races { get; } = new Race[0x100]; + protected Race(int raceID, int raceIndex, string name, string pluralName, int maleBody, int femaleBody, + int maleGhostBody, int femaleGhostBody, Expansion requiredExpansion) + { + RaceID = raceID; + RaceIndex = raceIndex; - public static Race Human => Races[0]; - public static Race Elf => Races[1]; - public static Race Gargoyle => Races[2]; + Name = name; - public static List AllRaces { get; } = new List(); + MaleBody = maleBody; + FemaleBody = femaleBody; + MaleGhostBody = maleGhostBody; + FemaleGhostBody = femaleGhostBody; - private static string[] m_RaceNames; - private static Race[] m_RaceValues; + RequiredExpansion = requiredExpansion; + PluralName = pluralName; + } - public static string[] GetRaceNames() - { - CheckNamesAndValues(); - return m_RaceNames; - } + public static Race DefaultRace => Races[0]; - public static Race[] GetRaceValues() - { - CheckNamesAndValues(); - return m_RaceValues; - } + public static Race[] Races{ get; } = new Race[0x100]; - public static Race Parse( string value ) - { - CheckNamesAndValues(); + public static Race Human => Races[0]; + public static Race Elf => Races[1]; + public static Race Gargoyle => Races[2]; - for( int i = 0; i < m_RaceNames.Length; ++i ) - { - if ( Insensitive.Equals( m_RaceNames[i], value ) ) - return m_RaceValues[i]; - } + public static List AllRaces{ get; } = new List(); - int index; - if ( int.TryParse( value, out index ) ) - { - if ( index >= 0 && index < Races.Length && Races[index] != null ) - return Races[index]; - } + public Expansion RequiredExpansion{ get; } - throw new ArgumentException( "Invalid race name" ); - } + public int MaleBody{ get; } - private static void CheckNamesAndValues() - { - if ( m_RaceNames != null && m_RaceNames.Length == AllRaces.Count ) - return; + public int MaleGhostBody{ get; } - m_RaceNames = new string[AllRaces.Count]; - m_RaceValues = new Race[AllRaces.Count]; + public int FemaleBody{ get; } - for( int i = 0; i < AllRaces.Count; ++i ) - { - Race race = AllRaces[i]; + public int FemaleGhostBody{ get; } - m_RaceNames[i] = race.Name; - m_RaceValues[i] = race; - } - } + public int RaceID{ get; } - public override string ToString() - { - return Name; - } + public int RaceIndex{ get; } - public Expansion RequiredExpansion { get; } + public string Name{ get; set; } - public int MaleBody { get; } + public string PluralName{ get; set; } - public int MaleGhostBody { get; } + public static string[] GetRaceNames() + { + CheckNamesAndValues(); + return m_RaceNames; + } - public int FemaleBody { get; } + public static Race[] GetRaceValues() + { + CheckNamesAndValues(); + return m_RaceValues; + } - public int FemaleGhostBody { get; } + public static Race Parse(string value) + { + CheckNamesAndValues(); - protected Race( int raceID, int raceIndex, string name, string pluralName, int maleBody, int femaleBody, int maleGhostBody, int femaleGhostBody, Expansion requiredExpansion ) - { - RaceID = raceID; - RaceIndex = raceIndex; + for (int i = 0; i < m_RaceNames.Length; ++i) + if (Insensitive.Equals(m_RaceNames[i], value)) + return m_RaceValues[i]; - Name = name; + if (int.TryParse(value, out int index)) + if (index >= 0 && index < Races.Length && Races[index] != null) + return Races[index]; - MaleBody = maleBody; - FemaleBody = femaleBody; - MaleGhostBody = maleGhostBody; - FemaleGhostBody = femaleGhostBody; + throw new ArgumentException("Invalid race name"); + } - RequiredExpansion = requiredExpansion; - PluralName = pluralName; - } + private static void CheckNamesAndValues() + { + if (m_RaceNames != null && m_RaceNames.Length == AllRaces.Count) + return; - public virtual bool ValidateHair( Mobile m, int itemID ) { return ValidateHair( m.Female, itemID ); } - public abstract bool ValidateHair( bool female, int itemID ); + m_RaceNames = new string[AllRaces.Count]; + m_RaceValues = new Race[AllRaces.Count]; - public virtual int RandomHair( Mobile m ) { return RandomHair( m.Female ); } - public abstract int RandomHair( bool female ); + for (int i = 0; i < AllRaces.Count; ++i) + { + Race race = AllRaces[i]; - public virtual bool ValidateFacialHair( Mobile m, int itemID ) { return ValidateFacialHair( m.Female, itemID ); } - public abstract bool ValidateFacialHair( bool female, int itemID ); + m_RaceNames[i] = race.Name; + m_RaceValues[i] = race; + } + } - public virtual int RandomFacialHair( Mobile m ) { return RandomFacialHair( m.Female ); } - public abstract int RandomFacialHair( bool female ); //For the *ahem* bearded ladies + public override string ToString() + { + return Name; + } - public abstract int ClipSkinHue( int hue ); - public abstract int RandomSkinHue(); + public virtual bool ValidateHair(Mobile m, int itemID) + { + return ValidateHair(m.Female, itemID); + } - public abstract int ClipHairHue( int hue ); - public abstract int RandomHairHue(); + public abstract bool ValidateHair(bool female, int itemID); - public virtual int Body( Mobile m ) - { - if ( m.Alive ) - return AliveBody( m.Female ); + public virtual int RandomHair(Mobile m) + { + return RandomHair(m.Female); + } - return GhostBody( m.Female ); - } + public abstract int RandomHair(bool female); - public virtual int AliveBody( Mobile m ) { return AliveBody( m.Female ); } - public virtual int AliveBody( bool female ) - { - return (female ? FemaleBody : MaleBody); - } + public virtual bool ValidateFacialHair(Mobile m, int itemID) + { + return ValidateFacialHair(m.Female, itemID); + } - public virtual int GhostBody( Mobile m ) { return GhostBody( m.Female ); } - public virtual int GhostBody( bool female ) - { - return (female ? FemaleGhostBody : MaleGhostBody); - } + public abstract bool ValidateFacialHair(bool female, int itemID); - public int RaceID { get; } + public virtual int RandomFacialHair(Mobile m) + { + return RandomFacialHair(m.Female); + } - public int RaceIndex { get; } + public abstract int RandomFacialHair(bool female); //For the *ahem* bearded ladies - public string Name { get; set; } + public abstract int ClipSkinHue(int hue); + public abstract int RandomSkinHue(); - public string PluralName { get; set; } - } -} + public abstract int ClipHairHue(int hue); + public abstract int RandomHairHue(); + + public virtual int Body(Mobile m) + { + return m.Alive ? AliveBody(m.Female) : GhostBody(m.Female); + } + + public virtual int AliveBody(Mobile m) + { + return AliveBody(m.Female); + } + + public virtual int AliveBody(bool female) + { + return female ? FemaleBody : MaleBody; + } + + public virtual int GhostBody(Mobile m) + { + return GhostBody(m.Female); + } + + public virtual int GhostBody(bool female) + { + return female ? FemaleGhostBody : MaleGhostBody; + } + } +} \ No newline at end of file diff --git a/Server/Random.cs b/Server/Random.cs index 7b539a143..f4720b1e2 100644 --- a/Server/Random.cs +++ b/Server/Random.cs @@ -13,588 +13,678 @@ using System.Runtime.InteropServices; using System.Security.Cryptography; using System.Threading; -namespace Server { - /// - /// Handles random number generation. - /// - public static class RandomImpl { - private static readonly IRandomImpl _Random; - - static RandomImpl() { - if (Core.Unix && File.Exists("rdrand.so")) { - _Random = new RDRandUnix(); - } else if (Core.Is64Bit && File.Exists("rdrand64.dll")) { - _Random = new RDRand64(); - } else if (File.Exists("rdrand.dll")) { - _Random = new RDRand32(); - } else { - _Random = new CSPRandom(); - } - - if (_Random is IHardwareRNG rng && !rng.IsSupported()) { - _Random = new CSPRandom(); - } - } - - public static bool IsHardwareRNG => _Random is IHardwareRNG; - - public static Type Type => _Random.GetType(); - - public static int Next(int c) { - return _Random.Next(c); - } - - public static bool NextBool() { - return _Random.NextBool(); - } - - public static void NextBytes(byte[] b) { - _Random.NextBytes(b); - } - - public static double NextDouble() { - return _Random.NextDouble(); - } - } - - public interface IRandomImpl { - int Next(int c); - bool NextBool(); - void NextBytes(byte[] b); - double NextDouble(); - } - - public interface IHardwareRNG { - bool IsSupported(); - } - - public sealed class SimpleRandom : IRandomImpl { - private Random m_Random = new Random(); - - public SimpleRandom() { - } - - public int Next(int c) { - int r; - lock (m_Random) - r = m_Random.Next(c); - return r; - } - - public bool NextBool() { - return NextDouble() >= .5; - } - - public void NextBytes(byte[] b) { - lock (m_Random) - m_Random.NextBytes(b); - } - - public double NextDouble() { - double r; - lock (m_Random) - r = m_Random.NextDouble(); - return r; - } - } - - public sealed class CSPRandom : IRandomImpl { - private RNGCryptoServiceProvider _CSP = new RNGCryptoServiceProvider(); - - private static int BUFFER_SIZE = 0x4000; - private static int LARGE_REQUEST = 0x40; - - private byte[] _Working = new byte[BUFFER_SIZE]; - private byte[] _Buffer = new byte[BUFFER_SIZE]; - - private int _Index; - - private object _sync = new object(); - - private ManualResetEvent _filled = new ManualResetEvent(false); - - public CSPRandom() { - _CSP.GetBytes(_Working); - ThreadPool.QueueUserWorkItem(Fill); - } - - private void CheckSwap(int c) { - if (_Index + c < BUFFER_SIZE) - return; - - _filled.WaitOne(); - - byte[] b = _Working; - _Working = _Buffer; - _Buffer = b; - _Index = 0; - - _filled.Reset(); - - ThreadPool.QueueUserWorkItem(Fill); - } - - private void Fill(object o) { - lock (_CSP) - _CSP.GetBytes(_Buffer); - - _filled.Set(); - } - - private void _GetBytes(byte[] b) { - int c = b.Length; - - lock (_sync) { - CheckSwap(c); - Buffer.BlockCopy(_Working, _Index, b, 0, c); - _Index += c; - } - } - - private void _GetBytes(byte[] b, int offset, int count) { - lock (_sync) { - CheckSwap(count); - Buffer.BlockCopy(_Working, _Index, b, offset, count); - _Index += count; - } - } - - public int Next(int c) { - return (int)(c * NextDouble()); - } - - public bool NextBool() { - return (NextByte() & 1) == 1; - } - - private byte NextByte() { - lock (_sync) { - CheckSwap(1); - return _Working[_Index++]; - } - } - - public void NextBytes(byte[] b) { - int c = b.Length; - - if (c >= LARGE_REQUEST) { - lock (_CSP) - _CSP.GetBytes(b); - return; - } - _GetBytes(b); - } - - public unsafe double NextDouble() { - byte[] b = new byte[8]; - - if (BitConverter.IsLittleEndian) { - b[7] = 0; - _GetBytes(b, 0, 7); - } else { - b[0] = 0; - _GetBytes(b, 1, 7); - } - - ulong r = 0; - fixed(byte* buf = b) - r = *(ulong*)(&buf[0]) >> 3; - - /* double: 53 bits of significand precision - * ulong.MaxValue >> 11 = 9007199254740991 - * 2^53 = 9007199254740992 - */ - - return (double)r / 9007199254740992; - } - } - - public sealed class RDRandUnix : IRandomImpl, IHardwareRNG - { - internal class SafeNativeMethods - { - [DllImport("rdrand.so")] - internal static extern RDRandError rdrand_32(ref uint rand, bool retry); - - [DllImport("rdrand.so")] - internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer); - } - - private static int BUFFER_SIZE = 0x10000; - private static int LARGE_REQUEST = 0x40; - - private byte[] _Working = new byte[BUFFER_SIZE]; - private byte[] _Buffer = new byte[BUFFER_SIZE]; - - private int _Index; - - private object _sync = new object(); - - private ManualResetEvent _filled = new ManualResetEvent(false); - - public RDRandUnix() - { - SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working); - ThreadPool.QueueUserWorkItem(Fill); - } - - public bool IsSupported() - { - uint r = 0; - return SafeNativeMethods.rdrand_32(ref r, true) == RDRandError.Success; - } - - private void CheckSwap(int c) - { - if (_Index + c < BUFFER_SIZE) - return; - - _filled.WaitOne(); - - byte[] b = _Working; - _Working = _Buffer; - _Buffer = b; - _Index = 0; - - _filled.Reset(); - - ThreadPool.QueueUserWorkItem(Fill); - } - - private void Fill(object o) - { - SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer); - _filled.Set(); - } - - private void _GetBytes(byte[] b) - { - int c = b.Length; - - lock (_sync) - { - CheckSwap(c); - Buffer.BlockCopy(_Working, _Index, b, 0, c); - _Index += c; - } - } - - private void _GetBytes(byte[] b, int offset, int count) - { - lock (_sync) - { - CheckSwap(count); - Buffer.BlockCopy(_Working, _Index, b, offset, count); - _Index += count; - } - } - - public int Next(int c) - { - return (int)(c * NextDouble()); - } - - public bool NextBool() - { - return (NextByte() & 1) == 1; - } - - private byte NextByte() - { - lock (_sync) - { - CheckSwap(1); - return _Working[_Index++]; - } - } - - public void NextBytes(byte[] b) - { - int c = b.Length; - - if (c >= LARGE_REQUEST) - { - SafeNativeMethods.rdrand_get_bytes(c, b); - return; - } - _GetBytes(b); - } - - public unsafe double NextDouble() - { - byte[] b = new byte[8]; - - if (BitConverter.IsLittleEndian) - { - b[7] = 0; - _GetBytes(b, 0, 7); - } - else - { - b[0] = 0; - _GetBytes(b, 1, 7); - } - - ulong r = 0; - fixed (byte* buf = b) - r = *(ulong*)(&buf[0]) >> 3; - - /* double: 53 bits of significand precision - * ulong.MaxValue >> 11 = 9007199254740991 - * 2^53 = 9007199254740992 - */ - - return (double)r / 9007199254740992; - } - } - - public sealed class RDRand32 : IRandomImpl, IHardwareRNG { - internal class SafeNativeMethods - { - [DllImport("rdrand32")] - internal static extern RDRandError rdrand_32(ref uint rand, bool retry); - - [DllImport("rdrand32")] - internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer); - } - - private static int BUFFER_SIZE = 0x10000; - private static int LARGE_REQUEST = 0x40; - - private byte[] _Working = new byte[BUFFER_SIZE]; - private byte[] _Buffer = new byte[BUFFER_SIZE]; - - private int _Index; - - private object _sync = new object(); - - private ManualResetEvent _filled = new ManualResetEvent(false); - - public RDRand32() { - SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working); - ThreadPool.QueueUserWorkItem(Fill); - } - - public bool IsSupported() { - uint r = 0; - return SafeNativeMethods.rdrand_32(ref r, true) == RDRandError.Success; - } - - private void CheckSwap(int c) { - if (_Index + c < BUFFER_SIZE) - return; - - _filled.WaitOne(); - - byte[] b = _Working; - _Working = _Buffer; - _Buffer = b; - _Index = 0; - - _filled.Reset(); - - ThreadPool.QueueUserWorkItem(Fill); - } - - private void Fill(object o) { - SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer); - _filled.Set(); - } - - private void _GetBytes(byte[] b) { - int c = b.Length; - - lock (_sync) { - CheckSwap(c); - Buffer.BlockCopy(_Working, _Index, b, 0, c); - _Index += c; - } - } - - private void _GetBytes(byte[] b, int offset, int count) { - lock (_sync) { - CheckSwap(count); - Buffer.BlockCopy(_Working, _Index, b, offset, count); - _Index += count; - } - } - - public int Next(int c) { - return (int)(c * NextDouble()); - } - - public bool NextBool() { - return (NextByte() & 1) == 1; - } - - private byte NextByte() { - lock (_sync) { - CheckSwap(1); - return _Working[_Index++]; - } - } - - public void NextBytes(byte[] b) { - int c = b.Length; - - if (c >= LARGE_REQUEST) { - SafeNativeMethods.rdrand_get_bytes(c, b); - return; - } - _GetBytes(b); - } - - public unsafe double NextDouble() { - byte[] b = new byte[8]; - - if (BitConverter.IsLittleEndian) { - b[7] = 0; - _GetBytes(b, 0, 7); - } else { - b[0] = 0; - _GetBytes(b, 1, 7); - } - - ulong r = 0; - fixed(byte* buf = b) - r = *(ulong*)(&buf[0]) >> 3; - - /* double: 53 bits of significand precision - * ulong.MaxValue >> 11 = 9007199254740991 - * 2^53 = 9007199254740992 - */ - - return (double)r / 9007199254740992; - } - } - - public sealed class RDRand64 : IRandomImpl, IHardwareRNG { - internal class SafeNativeMethods { - [DllImport("rdrand64")] - internal static extern RDRandError rdrand_64(ref ulong rand, bool retry); - - [DllImport("rdrand64")] - internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer); - } - - private static int BUFFER_SIZE = 0x10000; - private static int LARGE_REQUEST = 0x40; - - private byte[] _Working = new byte[BUFFER_SIZE]; - private byte[] _Buffer = new byte[BUFFER_SIZE]; - - private int _Index; - - private object _sync = new object(); - - private ManualResetEvent _filled = new ManualResetEvent(false); - - public RDRand64() { - SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working); - ThreadPool.QueueUserWorkItem(Fill); - } - - public bool IsSupported() { - ulong r = 0; - return SafeNativeMethods.rdrand_64(ref r, true) == RDRandError.Success; - } - - private void CheckSwap(int c) { - if (_Index + c < BUFFER_SIZE) - return; - - _filled.WaitOne(); - - byte[] b = _Working; - _Working = _Buffer; - _Buffer = b; - _Index = 0; - - _filled.Reset(); - - ThreadPool.QueueUserWorkItem(Fill); - } - - private void Fill(object o) { - SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer); - _filled.Set(); - } - - private void _GetBytes(byte[] b) { - int c = b.Length; - - lock (_sync) { - CheckSwap(c); - Buffer.BlockCopy(_Working, _Index, b, 0, c); - _Index += c; - } - } - - private void _GetBytes(byte[] b, int offset, int count) { - lock (_sync) { - CheckSwap(count); - Buffer.BlockCopy(_Working, _Index, b, offset, count); - _Index += count; - } - } - - public int Next(int c) { - return (int)(c * NextDouble()); - } - - public bool NextBool() { - return (NextByte() & 1) == 1; - } - - private byte NextByte() { - lock (_sync) { - CheckSwap(1); - return _Working[_Index++]; - } - } - - public void NextBytes(byte[] b) { - int c = b.Length; - - if (c >= LARGE_REQUEST) { - SafeNativeMethods.rdrand_get_bytes(c, b); - return; - } - _GetBytes(b); - } - - public unsafe double NextDouble() { - byte[] b = new byte[8]; - - if (BitConverter.IsLittleEndian) { - b[7] = 0; - _GetBytes(b, 0, 7); - } else { - b[0] = 0; - _GetBytes(b, 1, 7); - } - - ulong r = 0; - fixed(byte* buf = b) - r = *(ulong*)(&buf[0]) >> 3; - - /* double: 53 bits of significand precision - * ulong.MaxValue >> 11 = 9007199254740991 - * 2^53 = 9007199254740992 - */ - - return (double)r / 9007199254740992; - } - } - - public enum RDRandError : int { - Unknown = -4, - Unsupported = -3, - Supported = -2, - NotReady = -1, - - Failure = 0, - - Success = 1, - } -} +namespace Server +{ + /// + /// Handles random number generation. + /// + public static class RandomImpl + { + private static readonly IRandomImpl _Random; + + static RandomImpl() + { + if (Core.Unix && File.Exists("rdrand.so")) + _Random = new RDRandUnix(); + else if (Core.Is64Bit && File.Exists("rdrand64.dll")) + _Random = new RDRand64(); + else if (File.Exists("rdrand.dll")) + _Random = new RDRand32(); + else + _Random = new CSPRandom(); + + if (_Random is IHardwareRNG rng && !rng.IsSupported()) _Random = new CSPRandom(); + } + + public static bool IsHardwareRNG => _Random is IHardwareRNG; + + public static Type Type => _Random.GetType(); + + public static int Next(int c) + { + return _Random.Next(c); + } + + public static bool NextBool() + { + return _Random.NextBool(); + } + + public static void NextBytes(byte[] b) + { + _Random.NextBytes(b); + } + + public static double NextDouble() + { + return _Random.NextDouble(); + } + } + + public interface IRandomImpl + { + int Next(int c); + bool NextBool(); + void NextBytes(byte[] b); + double NextDouble(); + } + + public interface IHardwareRNG + { + bool IsSupported(); + } + + public sealed class SimpleRandom : IRandomImpl + { + private Random m_Random = new Random(); + + public int Next(int c) + { + int r; + lock (m_Random) + { + r = m_Random.Next(c); + } + + return r; + } + + public bool NextBool() + { + return NextDouble() >= .5; + } + + public void NextBytes(byte[] b) + { + lock (m_Random) + { + m_Random.NextBytes(b); + } + } + + public double NextDouble() + { + double r; + lock (m_Random) + { + r = m_Random.NextDouble(); + } + + return r; + } + } + + public sealed class CSPRandom : IRandomImpl + { + private static int BUFFER_SIZE = 0x4000; + private static int LARGE_REQUEST = 0x40; + private byte[] _Buffer = new byte[BUFFER_SIZE]; + private RNGCryptoServiceProvider _CSP = new RNGCryptoServiceProvider(); + + private ManualResetEvent _filled = new ManualResetEvent(false); + + private int _Index; + + private object _sync = new object(); + + private byte[] _Working = new byte[BUFFER_SIZE]; + + public CSPRandom() + { + _CSP.GetBytes(_Working); + ThreadPool.QueueUserWorkItem(Fill); + } + + public int Next(int c) + { + return (int)(c * NextDouble()); + } + + public bool NextBool() + { + return (NextByte() & 1) == 1; + } + + public void NextBytes(byte[] b) + { + int c = b.Length; + + if (c >= LARGE_REQUEST) + { + lock (_CSP) + { + _CSP.GetBytes(b); + } + + return; + } + + _GetBytes(b); + } + + public unsafe double NextDouble() + { + byte[] b = new byte[8]; + + if (BitConverter.IsLittleEndian) + { + b[7] = 0; + _GetBytes(b, 0, 7); + } + else + { + b[0] = 0; + _GetBytes(b, 1, 7); + } + + ulong r = 0; + fixed (byte* buf = b) + { + r = *(ulong*)&buf[0] >> 3; + } + + /* double: 53 bits of significand precision + * ulong.MaxValue >> 11 = 9007199254740991 + * 2^53 = 9007199254740992 + */ + + return (double)r / 9007199254740992; + } + + private void CheckSwap(int c) + { + if (_Index + c < BUFFER_SIZE) + return; + + _filled.WaitOne(); + + byte[] b = _Working; + _Working = _Buffer; + _Buffer = b; + _Index = 0; + + _filled.Reset(); + + ThreadPool.QueueUserWorkItem(Fill); + } + + private void Fill(object o) + { + lock (_CSP) + { + _CSP.GetBytes(_Buffer); + } + + _filled.Set(); + } + + private void _GetBytes(byte[] b) + { + int c = b.Length; + + lock (_sync) + { + CheckSwap(c); + Buffer.BlockCopy(_Working, _Index, b, 0, c); + _Index += c; + } + } + + private void _GetBytes(byte[] b, int offset, int count) + { + lock (_sync) + { + CheckSwap(count); + Buffer.BlockCopy(_Working, _Index, b, offset, count); + _Index += count; + } + } + + private byte NextByte() + { + lock (_sync) + { + CheckSwap(1); + return _Working[_Index++]; + } + } + } + + public sealed class RDRandUnix : IRandomImpl, IHardwareRNG + { + private static int BUFFER_SIZE = 0x10000; + private static int LARGE_REQUEST = 0x40; + private byte[] _Buffer = new byte[BUFFER_SIZE]; + + private ManualResetEvent _filled = new ManualResetEvent(false); + + private int _Index; + + private object _sync = new object(); + + private byte[] _Working = new byte[BUFFER_SIZE]; + + public RDRandUnix() + { + SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working); + ThreadPool.QueueUserWorkItem(Fill); + } + + public bool IsSupported() + { + uint r = 0; + return SafeNativeMethods.rdrand_32(ref r, true) == RDRandError.Success; + } + + public int Next(int c) + { + return (int)(c * NextDouble()); + } + + public bool NextBool() + { + return (NextByte() & 1) == 1; + } + + public void NextBytes(byte[] b) + { + int c = b.Length; + + if (c >= LARGE_REQUEST) + { + SafeNativeMethods.rdrand_get_bytes(c, b); + return; + } + + _GetBytes(b); + } + + public unsafe double NextDouble() + { + byte[] b = new byte[8]; + + if (BitConverter.IsLittleEndian) + { + b[7] = 0; + _GetBytes(b, 0, 7); + } + else + { + b[0] = 0; + _GetBytes(b, 1, 7); + } + + ulong r = 0; + fixed (byte* buf = b) + { + r = *(ulong*)&buf[0] >> 3; + } + + /* double: 53 bits of significand precision + * ulong.MaxValue >> 11 = 9007199254740991 + * 2^53 = 9007199254740992 + */ + + return (double)r / 9007199254740992; + } + + private void CheckSwap(int c) + { + if (_Index + c < BUFFER_SIZE) + return; + + _filled.WaitOne(); + + byte[] b = _Working; + _Working = _Buffer; + _Buffer = b; + _Index = 0; + + _filled.Reset(); + + ThreadPool.QueueUserWorkItem(Fill); + } + + private void Fill(object o) + { + SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer); + _filled.Set(); + } + + private void _GetBytes(byte[] b) + { + int c = b.Length; + + lock (_sync) + { + CheckSwap(c); + Buffer.BlockCopy(_Working, _Index, b, 0, c); + _Index += c; + } + } + + private void _GetBytes(byte[] b, int offset, int count) + { + lock (_sync) + { + CheckSwap(count); + Buffer.BlockCopy(_Working, _Index, b, offset, count); + _Index += count; + } + } + + private byte NextByte() + { + lock (_sync) + { + CheckSwap(1); + return _Working[_Index++]; + } + } + + internal class SafeNativeMethods + { + [DllImport("rdrand.so")] + internal static extern RDRandError rdrand_32(ref uint rand, bool retry); + + [DllImport("rdrand.so")] + internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer); + } + } + + public sealed class RDRand32 : IRandomImpl, IHardwareRNG + { + private static int BUFFER_SIZE = 0x10000; + private static int LARGE_REQUEST = 0x40; + private byte[] _Buffer = new byte[BUFFER_SIZE]; + + private ManualResetEvent _filled = new ManualResetEvent(false); + + private int _Index; + + private object _sync = new object(); + + private byte[] _Working = new byte[BUFFER_SIZE]; + + public RDRand32() + { + SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working); + ThreadPool.QueueUserWorkItem(Fill); + } + + public bool IsSupported() + { + uint r = 0; + return SafeNativeMethods.rdrand_32(ref r, true) == RDRandError.Success; + } + + public int Next(int c) + { + return (int)(c * NextDouble()); + } + + public bool NextBool() + { + return (NextByte() & 1) == 1; + } + + public void NextBytes(byte[] b) + { + int c = b.Length; + + if (c >= LARGE_REQUEST) + { + SafeNativeMethods.rdrand_get_bytes(c, b); + return; + } + + _GetBytes(b); + } + + public unsafe double NextDouble() + { + byte[] b = new byte[8]; + + if (BitConverter.IsLittleEndian) + { + b[7] = 0; + _GetBytes(b, 0, 7); + } + else + { + b[0] = 0; + _GetBytes(b, 1, 7); + } + + ulong r = 0; + fixed (byte* buf = b) + { + r = *(ulong*)&buf[0] >> 3; + } + + /* double: 53 bits of significand precision + * ulong.MaxValue >> 11 = 9007199254740991 + * 2^53 = 9007199254740992 + */ + + return (double)r / 9007199254740992; + } + + private void CheckSwap(int c) + { + if (_Index + c < BUFFER_SIZE) + return; + + _filled.WaitOne(); + + byte[] b = _Working; + _Working = _Buffer; + _Buffer = b; + _Index = 0; + + _filled.Reset(); + + ThreadPool.QueueUserWorkItem(Fill); + } + + private void Fill(object o) + { + SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer); + _filled.Set(); + } + + private void _GetBytes(byte[] b) + { + int c = b.Length; + + lock (_sync) + { + CheckSwap(c); + Buffer.BlockCopy(_Working, _Index, b, 0, c); + _Index += c; + } + } + + private void _GetBytes(byte[] b, int offset, int count) + { + lock (_sync) + { + CheckSwap(count); + Buffer.BlockCopy(_Working, _Index, b, offset, count); + _Index += count; + } + } + + private byte NextByte() + { + lock (_sync) + { + CheckSwap(1); + return _Working[_Index++]; + } + } + + internal class SafeNativeMethods + { + [DllImport("rdrand32")] + internal static extern RDRandError rdrand_32(ref uint rand, bool retry); + + [DllImport("rdrand32")] + internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer); + } + } + + public sealed class RDRand64 : IRandomImpl, IHardwareRNG + { + private static int BUFFER_SIZE = 0x10000; + private static int LARGE_REQUEST = 0x40; + private byte[] _Buffer = new byte[BUFFER_SIZE]; + + private ManualResetEvent _filled = new ManualResetEvent(false); + + private int _Index; + + private object _sync = new object(); + + private byte[] _Working = new byte[BUFFER_SIZE]; + + public RDRand64() + { + SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Working); + ThreadPool.QueueUserWorkItem(Fill); + } + + public bool IsSupported() + { + ulong r = 0; + return SafeNativeMethods.rdrand_64(ref r, true) == RDRandError.Success; + } + + public int Next(int c) + { + return (int)(c * NextDouble()); + } + + public bool NextBool() + { + return (NextByte() & 1) == 1; + } + + public void NextBytes(byte[] b) + { + int c = b.Length; + + if (c >= LARGE_REQUEST) + { + SafeNativeMethods.rdrand_get_bytes(c, b); + return; + } + + _GetBytes(b); + } + + public unsafe double NextDouble() + { + byte[] b = new byte[8]; + + if (BitConverter.IsLittleEndian) + { + b[7] = 0; + _GetBytes(b, 0, 7); + } + else + { + b[0] = 0; + _GetBytes(b, 1, 7); + } + + ulong r = 0; + fixed (byte* buf = b) + { + r = *(ulong*)&buf[0] >> 3; + } + + /* double: 53 bits of significand precision + * ulong.MaxValue >> 11 = 9007199254740991 + * 2^53 = 9007199254740992 + */ + + return (double)r / 9007199254740992; + } + + private void CheckSwap(int c) + { + if (_Index + c < BUFFER_SIZE) + return; + + _filled.WaitOne(); + + byte[] b = _Working; + _Working = _Buffer; + _Buffer = b; + _Index = 0; + + _filled.Reset(); + + ThreadPool.QueueUserWorkItem(Fill); + } + + private void Fill(object o) + { + SafeNativeMethods.rdrand_get_bytes(BUFFER_SIZE, _Buffer); + _filled.Set(); + } + + private void _GetBytes(byte[] b) + { + int c = b.Length; + + lock (_sync) + { + CheckSwap(c); + Buffer.BlockCopy(_Working, _Index, b, 0, c); + _Index += c; + } + } + + private void _GetBytes(byte[] b, int offset, int count) + { + lock (_sync) + { + CheckSwap(count); + Buffer.BlockCopy(_Working, _Index, b, offset, count); + _Index += count; + } + } + + private byte NextByte() + { + lock (_sync) + { + CheckSwap(1); + return _Working[_Index++]; + } + } + + internal class SafeNativeMethods + { + [DllImport("rdrand64")] + internal static extern RDRandError rdrand_64(ref ulong rand, bool retry); + + [DllImport("rdrand64")] + internal static extern RDRandError rdrand_get_bytes(int n, byte[] buffer); + } + } + + public enum RDRandError + { + Unknown = -4, + Unsupported = -3, + Supported = -2, + NotReady = -1, + + Failure = 0, + + Success = 1 + } +} \ No newline at end of file diff --git a/Server/Region.cs b/Server/Region.cs index b54b67862..662f769f2 100644 --- a/Server/Region.cs +++ b/Server/Region.cs @@ -20,1240 +20,1211 @@ using System; using System.Collections.Generic; +using System.IO; using System.Xml; using Server.Network; using Server.Targeting; namespace Server { - public enum MusicName - { - Invalid = -1, - OldUlt01 = 0, - Create1, - DragFlit, - OldUlt02, - OldUlt03, - OldUlt04, - OldUlt05, - OldUlt06, - Stones2, - Britain1, - Britain2, - Bucsden, - Jhelom, - LBCastle, - Linelle, - Magincia, - Minoc, - Ocllo, - Samlethe, - Serpents, - Skarabra, - Trinsic, - Vesper, - Wind, - Yew, - Cave01, - Dungeon9, - Forest_a, - InTown01, - Jungle_a, - Mountn_a, - Plains_a, - Sailing, - Swamp_a, - Tavern01, - Tavern02, - Tavern03, - Tavern04, - Combat1, - Combat2, - Combat3, - Approach, - Death, - Victory, - BTCastle, - Nujelm, - Dungeon2, - Cove, - Moonglow, - Zento, - TokunoDungeon, - Taiko, - DreadHornArea, - ElfCity, - GrizzleDungeon, - MelisandesLair, - ParoxysmusLair, - GwennoConversation, - GoodEndGame, - GoodVsEvil, - GreatEarthSerpents, - Humanoids_U9, - MinocNegative, - Paws, - SelimsBar, - SerpentIsleCombat_U7, - ValoriaShips - } - - public class Region : IComparable - { - public static List Regions { get; } = new List(); - - public static Region Find( Point3D p, Map map ) - { - if ( map == null ) - return Map.Internal.DefaultRegion; - - Sector sector = map.GetSector( p ); - List list = sector.RegionRects; - - for ( int i = 0; i < list.Count; ++i ) - { - RegionRect regRect = list[i]; - - if ( regRect.Contains( p ) ) - return regRect.Region; - } - - return map.DefaultRegion; - } - - public static Type DefaultRegionType { get; set; } = typeof( Region ); - - public static TimeSpan StaffLogoutDelay { get; set; } = TimeSpan.Zero; - - public static TimeSpan DefaultLogoutDelay { get; set; } = TimeSpan.FromMinutes( 5.0 ); - - public static readonly int DefaultPriority = 50; - - public static readonly int MinZ = sbyte.MinValue; - public static readonly int MaxZ = sbyte.MaxValue + 1; - - public static Rectangle3D ConvertTo3D( Rectangle2D rect ) - { - return new Rectangle3D( new Point3D( rect.Start, MinZ ), new Point3D( rect.End, MaxZ ) ); - } - - public static Rectangle3D[] ConvertTo3D( Rectangle2D[] rects ) - { - Rectangle3D[] ret = new Rectangle3D[rects.Length]; - - for ( int i = 0; i < ret.Length; i++ ) - { - ret[i] = ConvertTo3D( rects[i] ); - } - - return ret; - } - - - private string m_Name; - private int m_Priority; - - private Point3D m_GoLocation; - - public string Name => m_Name; - public Map Map { get; } - - public Region Parent { get; } - - public List Children { get; } = new List(); - - public Rectangle3D[] Area { get; } - - public Sector[] Sectors { get; private set; } - - public bool Dynamic { get; } - - public int Priority => m_Priority; - public int ChildLevel { get; } + public enum MusicName + { + Invalid = -1, + OldUlt01 = 0, + Create1, + DragFlit, + OldUlt02, + OldUlt03, + OldUlt04, + OldUlt05, + OldUlt06, + Stones2, + Britain1, + Britain2, + Bucsden, + Jhelom, + LBCastle, + Linelle, + Magincia, + Minoc, + Ocllo, + Samlethe, + Serpents, + Skarabra, + Trinsic, + Vesper, + Wind, + Yew, + Cave01, + Dungeon9, + Forest_a, + InTown01, + Jungle_a, + Mountn_a, + Plains_a, + Sailing, + Swamp_a, + Tavern01, + Tavern02, + Tavern03, + Tavern04, + Combat1, + Combat2, + Combat3, + Approach, + Death, + Victory, + BTCastle, + Nujelm, + Dungeon2, + Cove, + Moonglow, + Zento, + TokunoDungeon, + Taiko, + DreadHornArea, + ElfCity, + GrizzleDungeon, + MelisandesLair, + ParoxysmusLair, + GwennoConversation, + GoodEndGame, + GoodVsEvil, + GreatEarthSerpents, + Humanoids_U9, + MinocNegative, + Paws, + SelimsBar, + SerpentIsleCombat_U7, + ValoriaShips + } + + public class Region : IComparable + { + public static readonly int DefaultPriority = 50; + + public static readonly int MinZ = sbyte.MinValue; + public static readonly int MaxZ = sbyte.MaxValue + 1; + + private Point3D m_GoLocation; + + + private string m_Name; + private int m_Priority; + + public Region(string name, Map map, int priority, params Rectangle2D[] area) : this(name, map, priority, + ConvertTo3D(area)) + { + } + + public Region(string name, Map map, int priority, params Rectangle3D[] area) : this(name, map, null, area) + { + m_Priority = priority; + } + + public Region(string name, Map map, Region parent, params Rectangle2D[] area) : this(name, map, parent, + ConvertTo3D(area)) + { + } + + public Region(string name, Map map, Region parent, params Rectangle3D[] area) + { + m_Name = name; + Map = map; + Parent = parent; + Area = area; + Dynamic = true; + Music = DefaultMusic; + + if (Parent == null) + { + ChildLevel = 0; + m_Priority = DefaultPriority; + } + else + { + ChildLevel = Parent.ChildLevel + 1; + m_Priority = Parent.Priority; + } + } + + public Region(XmlElement xml, Map map, Region parent) + { + Map = map; + Parent = parent; + Dynamic = false; + + if (Parent == null) + { + ChildLevel = 0; + m_Priority = DefaultPriority; + } + else + { + ChildLevel = Parent.ChildLevel + 1; + m_Priority = Parent.Priority; + } + + ReadString(xml, "name", ref m_Name, false); + + if (parent == null) + ReadInt32(xml, "priority", ref m_Priority, false); + + + int minZ = MinZ; + int maxZ = MaxZ; - public bool Registered { get; private set; } + XmlElement zrange = xml["zrange"]; + ReadInt32(zrange, "min", ref minZ, false); + ReadInt32(zrange, "max", ref maxZ, false); - public Point3D GoLocation{ get => m_GoLocation; - set => m_GoLocation = value; - } - public MusicName Music { get; set; } - public bool IsDefault => Map.DefaultRegion == this; - public virtual MusicName DefaultMusic => Parent?.Music ?? MusicName.Invalid; + List area = new List(); + foreach (XmlElement xmlRect in xml.SelectNodes("rect")) + { + Rectangle3D rect = new Rectangle3D(); + if (ReadRectangle3D(xmlRect, minZ, maxZ, ref rect)) + area.Add(rect); + } - public Region( string name, Map map, int priority, params Rectangle2D[] area ) : this( name, map, priority, ConvertTo3D( area ) ) - { - } + Area = area.ToArray(); - public Region( string name, Map map, int priority, params Rectangle3D[] area ) : this( name, map, null, area ) - { - m_Priority = priority; - } + if (Area.Length == 0) + Console.WriteLine("Empty area for region '{0}'", this); - public Region( string name, Map map, Region parent, params Rectangle2D[] area ) : this( name, map, parent, ConvertTo3D( area ) ) - { - } - public Region( string name, Map map, Region parent, params Rectangle3D[] area ) - { - m_Name = name; - Map = map; - Parent = parent; - Area = area; - Dynamic = true; - Music = DefaultMusic; + if (!ReadPoint3D(xml["go"], map, ref m_GoLocation, false) && Area.Length > 0) + { + Point3D start = Area[0].Start; + Point3D end = Area[0].End; - if ( Parent == null ) - { - ChildLevel = 0; - m_Priority = DefaultPriority; - } - else - { - ChildLevel = Parent.ChildLevel + 1; - m_Priority = Parent.Priority; - } - } + int x = start.X + (end.X - start.X) / 2; + int y = start.Y + (end.Y - start.Y) / 2; - public void Register() - { - if ( Registered ) - return; + m_GoLocation = new Point3D(x, y, Map.GetAverageZ(x, y)); + } - OnRegister(); - Registered = true; + MusicName music = DefaultMusic; - if ( Parent != null ) - { - Parent.Children.Add( this ); - Parent.OnChildAdded( this ); - } + ReadEnum(xml["music"], "name", ref music, false); - Regions.Add( this ); + Music = music; + } - Map.RegisterRegion( this ); + public static List Regions{ get; } = new List(); - List sectors = new List(); + public static Type DefaultRegionType{ get; set; } = typeof(Region); - for ( int i = 0; i < Area.Length; i++ ) - { - Rectangle3D rect = Area[i]; + public static TimeSpan StaffLogoutDelay{ get; set; } = TimeSpan.Zero; - Point2D start = Map.Bound( new Point2D( rect.Start ) ); - Point2D end = Map.Bound( new Point2D( rect.End ) ); + public static TimeSpan DefaultLogoutDelay{ get; set; } = TimeSpan.FromMinutes(5.0); - Sector startSector = Map.GetSector( start ); - Sector endSector = Map.GetSector( end ); + public string Name => m_Name; + public Map Map{ get; } - for ( int x = startSector.X; x <= endSector.X; x++ ) - { - for ( int y = startSector.Y; y <= endSector.Y; y++ ) - { - Sector sector = Map.GetRealSector( x, y ); + public Region Parent{ get; } - sector.OnEnter( this, rect ); + public List Children{ get; } = new List(); - if ( !sectors.Contains( sector ) ) - sectors.Add( sector ); - } - } - } + public Rectangle3D[] Area{ get; } - Sectors = sectors.ToArray(); - } + public Sector[] Sectors{ get; private set; } - public void Unregister() - { - if ( !Registered ) - return; + public bool Dynamic{ get; } - OnUnregister(); + public int Priority => m_Priority; + public int ChildLevel{ get; } - Registered = false; + public bool Registered{ get; private set; } - if ( Children.Count > 0 ) - Console.WriteLine( "Warning: Unregistering region '{0}' with children", this ); + public Point3D GoLocation + { + get => m_GoLocation; + set => m_GoLocation = value; + } - if ( Parent != null ) - { - Parent.Children.Remove( this ); - Parent.OnChildRemoved( this ); - } + public MusicName Music{ get; set; } - Regions.Remove( this ); + public bool IsDefault => Map.DefaultRegion == this; + public virtual MusicName DefaultMusic => Parent?.Music ?? MusicName.Invalid; - Map.UnregisterRegion( this ); + int IComparable.CompareTo(object obj) + { + if (obj == null) + return 1; - if ( Sectors != null ) - { - for ( int i = 0; i < Sectors.Length; i++ ) - Sectors[i].OnLeave( this ); - } + if (!(obj is Region reg)) + throw new ArgumentException("obj is not a Region", nameof(obj)); - Sectors = null; - } + // Dynamic regions go first + if (Dynamic) + { + if (!reg.Dynamic) + return -1; + } + else if (reg.Dynamic) + { + return 1; + } - public bool Contains( Point3D p ) - { - for ( int i = 0; i < Area.Length; i++ ) - { - Rectangle3D rect = Area[i]; + int thisPriority = Priority; + int regPriority = reg.Priority; - if ( rect.Contains( p ) ) - return true; - } + if (thisPriority != regPriority) + return regPriority - thisPriority; - return false; - } + return reg.ChildLevel - ChildLevel; + } - public bool IsChildOf( Region region ) - { - if ( region == null ) - return false; + public static Region Find(Point3D p, Map map) + { + if (map == null) + return Map.Internal.DefaultRegion; - Region p = Parent; + Sector sector = map.GetSector(p); + List list = sector.RegionRects; - while ( p != null ) - { - if ( p == region ) - return true; + for (int i = 0; i < list.Count; ++i) + { + RegionRect regRect = list[i]; - p = p.Parent; - } + if (regRect.Contains(p)) + return regRect.Region; + } - return false; - } + return map.DefaultRegion; + } - public Region GetRegion( Type regionType ) - { - if ( regionType == null ) - return null; + public static Rectangle3D ConvertTo3D(Rectangle2D rect) + { + return new Rectangle3D(new Point3D(rect.Start, MinZ), new Point3D(rect.End, MaxZ)); + } - Region r = this; + public static Rectangle3D[] ConvertTo3D(Rectangle2D[] rects) + { + Rectangle3D[] ret = new Rectangle3D[rects.Length]; - do - { - if ( regionType.IsAssignableFrom( r.GetType() ) ) - return r; + for (int i = 0; i < ret.Length; i++) ret[i] = ConvertTo3D(rects[i]); - r = r.Parent; - } - while ( r != null ); + return ret; + } - return null; - } - - public Region GetRegion( string regionName ) - { - if ( regionName == null ) - return null; - - Region r = this; - - do - { - if ( r.m_Name == regionName ) - return r; - - r = r.Parent; - } - while ( r != null ); - - return null; - } - - public bool IsPartOf( Region region ) - { - if ( this == region ) - return true; - - return IsChildOf( region ); - } - - public bool IsPartOf( Type regionType ) - { - return ( GetRegion( regionType ) != null ); - } - - public bool IsPartOf( string regionName ) - { - return ( GetRegion( regionName ) != null ); - } - - public virtual bool AcceptsSpawnsFrom( Region region ) - { - if ( !AllowSpawn() ) - return false; - - if ( region == this ) - return true; - - if ( Parent != null ) - return Parent.AcceptsSpawnsFrom( region ); - - return false; - } - - public List GetPlayers() - { - List list = new List(); - - if ( Sectors != null ) - { - for ( int i = 0; i < Sectors.Length; i++ ) - { - Sector sector = Sectors[i]; - - foreach ( Mobile player in sector.Players ) - { - if ( player.Region.IsPartOf( this ) ) - list.Add( player ); - } - } - } - - return list; - } - - public int GetPlayerCount() - { - int count = 0; - - if ( Sectors != null ) - { - for ( int i = 0; i < Sectors.Length; i++ ) - { - Sector sector = Sectors[i]; - - foreach ( Mobile player in sector.Players ) - { - if ( player.Region.IsPartOf( this ) ) - count++; - } - } - } - - return count; - } - - public List GetMobiles() - { - List list = new List(); - - if ( Sectors != null ) - { - for ( int i = 0; i < Sectors.Length; i++ ) - { - Sector sector = Sectors[i]; - - foreach ( Mobile mobile in sector.Mobiles ) - { - if ( mobile.Region.IsPartOf( this ) ) - list.Add( mobile ); - } - } - } - - return list; - } - - public int GetMobileCount() - { - int count = 0; - - if ( Sectors != null ) - { - for ( int i = 0; i < Sectors.Length; i++ ) - { - Sector sector = Sectors[i]; - - foreach ( Mobile mobile in sector.Mobiles ) - { - if ( mobile.Region.IsPartOf( this ) ) - count++; - } - } - } - - return count; - } - - int IComparable.CompareTo( object obj ) - { - if ( obj == null ) - return 1; - - if ( !(obj is Region reg) ) - throw new ArgumentException( "obj is not a Region", nameof(obj) ); - - // Dynamic regions go first - if ( Dynamic ) - { - if ( !reg.Dynamic ) - return -1; - } - else if ( reg.Dynamic ) - { - return 1; - } - - int thisPriority = Priority; - int regPriority = reg.Priority; - - if ( thisPriority != regPriority ) - return ( regPriority - thisPriority ); - - return ( reg.ChildLevel - ChildLevel ); - } - - public override string ToString() - { - if ( m_Name != null ) - return m_Name; - return GetType().Name; - } - - - public virtual void OnRegister() - { - } - - public virtual void OnUnregister() - { - } - - public virtual void OnChildAdded( Region child ) - { - } - - public virtual void OnChildRemoved( Region child ) - { - } - - public virtual bool OnMoveInto( Mobile m, Direction d, Point3D newLocation, Point3D oldLocation ) - { - return ( m.WalkRegion == null || AcceptsSpawnsFrom( m.WalkRegion ) ); - } - - public virtual void OnEnter( Mobile m ) - { - } - - public virtual void OnExit( Mobile m ) - { - } - - public virtual void MakeGuard( Mobile focus ) - { - Parent?.MakeGuard( focus ); - } - - public virtual Type GetResource( Type type ) - { - if ( Parent != null ) - return Parent.GetResource( type ); - - return type; - } - - public virtual bool CanUseStuckMenu( Mobile m ) - { - if ( Parent != null ) - return Parent.CanUseStuckMenu( m ); - - return true; - } - - public virtual void OnAggressed( Mobile aggressor, Mobile aggressed, bool criminal ) - { - Parent?.OnAggressed( aggressor, aggressed, criminal ); - } - - public virtual void OnDidHarmful( Mobile harmer, Mobile harmed ) - { - Parent?.OnDidHarmful( harmer, harmed ); - } - - public virtual void OnGotHarmful( Mobile harmer, Mobile harmed ) - { - Parent?.OnGotHarmful( harmer, harmed ); - } - - public virtual void OnLocationChanged( Mobile m, Point3D oldLocation ) - { - Parent?.OnLocationChanged( m, oldLocation ); - } - - public virtual bool OnTarget( Mobile m, Target t, object o ) - { - if ( Parent != null ) - return Parent.OnTarget( m, t, o ); - - return true; - } - - public virtual bool OnCombatantChange( Mobile m, Mobile Old, Mobile New ) - { - if ( Parent != null ) - return Parent.OnCombatantChange( m, Old, New ); - - return true; - } - - public virtual bool AllowHousing( Mobile from, Point3D p ) - { - if ( Parent != null ) - return Parent.AllowHousing( from, p ); - - return true; - } - - public virtual bool SendInaccessibleMessage( Item item, Mobile from ) - { - if ( Parent != null ) - return Parent.SendInaccessibleMessage( item, from ); - - return false; - } - - public virtual bool CheckAccessibility( Item item, Mobile from ) - { - if ( Parent != null ) - return Parent.CheckAccessibility( item, from ); - - return true; - } - - public virtual bool OnDecay( Item item ) - { - if ( Parent != null ) - return Parent.OnDecay( item ); - - return true; - } - - public virtual bool AllowHarmful( Mobile from, Mobile target ) - { - if ( Parent != null ) - return Parent.AllowHarmful( from, target ); - - if ( Mobile.AllowHarmfulHandler != null ) - return Mobile.AllowHarmfulHandler( from, target ); - - return true; - } - - public virtual void OnCriminalAction( Mobile m, bool message ) - { - if ( Parent != null ) - Parent.OnCriminalAction( m, message ); - else if ( message ) - m.SendLocalizedMessage( 1005040 ); // You've committed a criminal act!! - } - - public virtual bool AllowBeneficial( Mobile from, Mobile target ) - { - if ( Parent != null ) - return Parent.AllowBeneficial( from, target ); - - if ( Mobile.AllowBeneficialHandler != null ) - return Mobile.AllowBeneficialHandler( from, target ); - - return true; - } - - public virtual void OnBeneficialAction( Mobile helper, Mobile target ) - { - Parent?.OnBeneficialAction( helper, target ); - } - - public virtual void OnGotBeneficialAction( Mobile helper, Mobile target ) - { - Parent?.OnGotBeneficialAction( helper, target ); - } - - public virtual void SpellDamageScalar( Mobile caster, Mobile target, ref double damage ) - { - Parent?.SpellDamageScalar( caster, target, ref damage ); - } - - public virtual void OnSpeech( SpeechEventArgs args ) - { - Parent?.OnSpeech( args ); - } - - public virtual bool OnSkillUse( Mobile m, int Skill ) - { - if ( Parent != null ) - return Parent.OnSkillUse( m, Skill ); - - return true; - } - - public virtual bool OnBeginSpellCast( Mobile m, ISpell s ) - { - if ( Parent != null ) - return Parent.OnBeginSpellCast( m, s ); - - return true; - } - - public virtual void OnSpellCast( Mobile m, ISpell s ) - { - Parent?.OnSpellCast( m, s ); - } - - public virtual bool OnResurrect( Mobile m ) - { - if ( Parent != null ) - return Parent.OnResurrect( m ); - - return true; - } - - public virtual bool OnBeforeDeath( Mobile m ) - { - if ( Parent != null ) - return Parent.OnBeforeDeath( m ); - - return true; - } - - public virtual void OnDeath( Mobile m ) - { - Parent?.OnDeath( m ); - } - - public virtual bool OnDamage( Mobile m, ref int Damage ) - { - if ( Parent != null ) - return Parent.OnDamage( m, ref Damage ); - - return true; - } - - public virtual bool OnHeal( Mobile m, ref int Heal ) - { - if ( Parent != null ) - return Parent.OnHeal( m, ref Heal ); - - return true; - } - - public virtual bool OnDoubleClick( Mobile m, object o ) - { - if ( Parent != null ) - return Parent.OnDoubleClick( m, o ); - - return true; - } - - public virtual bool OnSingleClick( Mobile m, object o ) - { - if ( Parent != null ) - return Parent.OnSingleClick( m, o ); - - return true; - } - - public virtual bool AllowSpawn() - { - if ( Parent != null ) - return Parent.AllowSpawn(); - - return true; - } - - public virtual void AlterLightLevel( Mobile m, ref int global, ref int personal ) - { - Parent?.AlterLightLevel( m, ref global, ref personal ); - } - - public virtual TimeSpan GetLogoutDelay( Mobile m ) - { - if ( Parent != null ) - return Parent.GetLogoutDelay( m ); - if ( m.AccessLevel > AccessLevel.Player ) - return StaffLogoutDelay; - return DefaultLogoutDelay; - } - - - internal static bool CanMove( Mobile m, Direction d, Point3D newLocation, Point3D oldLocation, Map map ) - { - Region oldRegion = m.Region; - Region newRegion = Find( newLocation, map ); - - while ( oldRegion != newRegion ) - { - if ( !newRegion.OnMoveInto( m, d, newLocation, oldLocation ) ) - return false; - - if ( newRegion.Parent == null ) - return true; - - newRegion = newRegion.Parent; - } - - return true; - } - - internal static void OnRegionChange( Mobile m, Region oldRegion, Region newRegion ) - { - if ( newRegion != null && m.NetState != null ) - { - m.CheckLightLevels( false ); - - if ( oldRegion == null || oldRegion.Music != newRegion.Music ) - { - m.Send( PlayMusic.GetInstance( newRegion.Music ) ); - } - } - - Region oldR = oldRegion; - Region newR = newRegion; - - while ( oldR != newR ) - { - int oldRChild = oldR?.ChildLevel ?? -1; - int newRChild = newR?.ChildLevel ?? -1; - - if ( oldRChild >= newRChild ) - { - oldR.OnExit( m ); - oldR = oldR.Parent; - } - - if ( newRChild >= oldRChild ) - { - newR.OnEnter( m ); - newR = newR.Parent; - } - } - } - - - internal static void Load() - { - if ( !System.IO.File.Exists( "Data/Regions.xml" ) ) - { - Console.WriteLine( "Error: Data/Regions.xml does not exist" ); - return; - } - - Console.Write( "Regions: Loading..." ); - - XmlDocument doc = new XmlDocument(); - doc.Load( System.IO.Path.Combine( Core.BaseDirectory, "Data/Regions.xml" ) ); - - XmlElement root = doc["ServerRegions"]; - - if ( root == null ) - { - Console.WriteLine( "Could not find root element 'ServerRegions' in Regions.xml" ); - } - else - { - foreach ( XmlElement facet in root.SelectNodes( "Facet" ) ) - { - Map map = null; - if ( ReadMap( facet, "name", ref map ) ) - { - if ( map == Map.Internal ) - Console.WriteLine( "Invalid internal map in a facet element" ); - else - LoadRegions( facet, map, null ); - } - } - } - - Console.WriteLine( "done" ); - } - - private static void LoadRegions( XmlElement xml, Map map, Region parent ) - { - foreach ( XmlElement xmlReg in xml.SelectNodes( "region" ) ) - { - Type type = DefaultRegionType; - - ReadType( xmlReg, "type", ref type, false ); - - if ( !typeof( Region ).IsAssignableFrom( type ) ) - { - Console.WriteLine( "Invalid region type '{0}' in regions.xml", type.FullName ); - continue; - } - - Region region = null; - try - { - region = (Region) Activator.CreateInstance( type, new object[] { xmlReg, map, parent } ); - } - catch ( Exception ex ) - { - Console.WriteLine( "Error during the creation of region type '{0}': {1}", type.FullName, ex ); - continue; - } - - region.Register(); - - LoadRegions( xmlReg, map, region ); - } - } - - public Region( XmlElement xml, Map map, Region parent ) - { - Map = map; - Parent = parent; - Dynamic = false; - - if ( Parent == null ) - { - ChildLevel = 0; - m_Priority = DefaultPriority; - } - else - { - ChildLevel = Parent.ChildLevel + 1; - m_Priority = Parent.Priority; - } - - ReadString( xml, "name", ref m_Name, false ); - - if ( parent == null ) - ReadInt32( xml, "priority", ref m_Priority, false ); - - - int minZ = MinZ; - int maxZ = MaxZ; - - XmlElement zrange = xml["zrange"]; - ReadInt32( zrange, "min", ref minZ, false ); - ReadInt32( zrange, "max", ref maxZ, false ); - - - List area = new List(); - foreach ( XmlElement xmlRect in xml.SelectNodes( "rect" ) ) - { - Rectangle3D rect = new Rectangle3D(); - if ( ReadRectangle3D( xmlRect, minZ, maxZ, ref rect ) ) - area.Add( rect ); - } - - Area = area.ToArray(); - - if ( Area.Length == 0 ) - Console.WriteLine( "Empty area for region '{0}'", this ); - - - if ( !ReadPoint3D( xml["go"], map, ref m_GoLocation, false ) && Area.Length > 0 ) - { - Point3D start = Area[0].Start; - Point3D end = Area[0].End; - - int x = start.X + (end.X - start.X) / 2; - int y = start.Y + (end.Y - start.Y) / 2; - - m_GoLocation = new Point3D( x, y, Map.GetAverageZ( x, y ) ); - } - - - MusicName music = DefaultMusic; - - ReadEnum( xml["music"], "name", ref music, false ); - - Music = music; - } - - protected static string GetAttribute( XmlElement xml, string attribute, bool mandatory ) - { - if ( xml == null ) - { - if ( mandatory ) - Console.WriteLine( "Missing element for attribute '{0}'", attribute ); - - return null; - } - - if ( xml.HasAttribute( attribute ) ) - { - return xml.GetAttribute( attribute ); - } - if ( mandatory ) - Console.WriteLine( "Missing attribute '{0}' in element '{1}'", attribute, xml.Name ); - - return null; - } - - public static bool ReadString( XmlElement xml, string attribute, ref string value ) - { - return ReadString( xml, attribute, ref value, true ); - } - - public static bool ReadString( XmlElement xml, string attribute, ref string value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - value = s; - return true; - } - - public static bool ReadInt32( XmlElement xml, string attribute, ref int value ) - { - return ReadInt32( xml, attribute, ref value, true ); - } - - public static bool ReadInt32( XmlElement xml, string attribute, ref int value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - try - { - value = XmlConvert.ToInt32( s ); - } - catch - { - Console.WriteLine( "Could not parse integer attribute '{0}' in element '{1}'", attribute, xml.Name ); - return false; - } + public void Register() + { + if (Registered) + return; - return true; - } - - public static bool ReadBoolean( XmlElement xml, string attribute, ref bool value ) - { - return ReadBoolean( xml, attribute, ref value, true ); - } - - public static bool ReadBoolean( XmlElement xml, string attribute, ref bool value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - try - { - value = XmlConvert.ToBoolean( s ); - } - catch - { - Console.WriteLine( "Could not parse boolean attribute '{0}' in element '{1}'", attribute, xml.Name ); - return false; - } - - return true; - } - - public static bool ReadDateTime( XmlElement xml, string attribute, ref DateTime value ) - { - return ReadDateTime( xml, attribute, ref value, true ); - } - - public static bool ReadDateTime( XmlElement xml, string attribute, ref DateTime value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - try - { - value = XmlConvert.ToDateTime( s, XmlDateTimeSerializationMode.Utc ); - } - catch - { - Console.WriteLine( "Could not parse DateTime attribute '{0}' in element '{1}'", attribute, xml.Name ); - return false; - } - - return true; - } - - public static bool ReadTimeSpan( XmlElement xml, string attribute, ref TimeSpan value ) - { - return ReadTimeSpan( xml, attribute, ref value, true ); - } - - public static bool ReadTimeSpan( XmlElement xml, string attribute, ref TimeSpan value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - try - { - value = XmlConvert.ToTimeSpan( s ); - } - catch - { - Console.WriteLine( "Could not parse TimeSpan attribute '{0}' in element '{1}'", attribute, xml.Name ); - return false; - } - - return true; - } - - public static bool ReadEnum( XmlElement xml, string attribute, ref T value ) where T : struct - { - return ReadEnum( xml, attribute, ref value, true ); - } - - public static bool ReadEnum( XmlElement xml, string attribute, ref T value, bool mandatory ) where T : struct // We can't limit the where clause to Enums only - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - Type type = typeof(T); - - T tempVal; - - if ( type.IsEnum && Enum.TryParse( s, true, out tempVal ) ) - { - value = tempVal; - return true; - } - - Console.WriteLine( "Could not parse {0} enum attribute '{1}' in element '{2}'", type, attribute, xml.Name ); - return false; - } - - public static bool ReadMap( XmlElement xml, string attribute, ref Map value ) - { - return ReadMap( xml, attribute, ref value, true ); - } - - public static bool ReadMap( XmlElement xml, string attribute, ref Map value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - try - { - value = Map.Parse( s ); - } - catch - { - Console.WriteLine( "Could not parse Map attribute '{0}' in element '{1}'", attribute, xml.Name ); - return false; - } - - return true; - } - - public static bool ReadType( XmlElement xml, string attribute, ref Type value ) - { - return ReadType( xml, attribute, ref value, true ); - } - - public static bool ReadType( XmlElement xml, string attribute, ref Type value, bool mandatory ) - { - string s = GetAttribute( xml, attribute, mandatory ); - - if ( s == null ) - return false; - - Type type; - try - { - type = ScriptCompiler.FindTypeByName( s, false ); - } - catch - { - Console.WriteLine( "Could not parse Type attribute '{0}' in element '{1}'", attribute, xml.Name ); - return false; - } - - if ( type == null ) - { - Console.WriteLine( "Could not find Type '{0}'", s ); - return false; - } - - value = type; - return true; - } - - public static bool ReadPoint3D( XmlElement xml, Map map, ref Point3D value ) - { - return ReadPoint3D( xml, map, ref value, true ); - } - - public static bool ReadPoint3D( XmlElement xml, Map map, ref Point3D value, bool mandatory ) - { - int x = 0, y = 0, z = 0; - - bool xyOk = ReadInt32( xml, "x", ref x, mandatory ) & ReadInt32( xml, "y", ref y, mandatory ); - bool zOk = ReadInt32( xml, "z", ref z, mandatory && map == null ); - - if ( xyOk && ( zOk || map != null ) ) - { - if ( !zOk ) - z = map.GetAverageZ( x, y ); - - value = new Point3D( x, y, z ); - return true; - } - - return false; - } - - public static bool ReadRectangle3D( XmlElement xml, int defaultMinZ, int defaultMaxZ, ref Rectangle3D value ) - { - return ReadRectangle3D( xml, defaultMinZ, defaultMaxZ, ref value, true ); - } - - public static bool ReadRectangle3D( XmlElement xml, int defaultMinZ, int defaultMaxZ, ref Rectangle3D value, bool mandatory ) - { - int x1 = 0, y1 = 0, x2 = 0, y2 = 0; - - if ( xml.HasAttribute( "x" ) ) - { - if ( ReadInt32( xml, "x", ref x1, mandatory ) - & ReadInt32( xml, "y", ref y1, mandatory ) - & ReadInt32( xml, "width", ref x2, mandatory ) - & ReadInt32( xml, "height", ref y2, mandatory ) ) - { - x2 += x1; - y2 += y1; - } - else - { - return false; - } - } - else - { - if ( !ReadInt32( xml, "x1", ref x1, mandatory ) - | !ReadInt32( xml, "y1", ref y1, mandatory ) - | !ReadInt32( xml, "x2", ref x2, mandatory ) - | !ReadInt32( xml, "y2", ref y2, mandatory ) ) - { - return false; - } - } - - int z1 = defaultMinZ; - int z2 = defaultMaxZ; - - ReadInt32( xml, "zmin", ref z1, false ); - ReadInt32( xml, "zmax", ref z2, false ); - - value = new Rectangle3D( new Point3D( x1, y1, z1 ), new Point3D( x2, y2, z2 ) ); - - return true; - } - } -} + OnRegister(); + + Registered = true; + + if (Parent != null) + { + Parent.Children.Add(this); + Parent.OnChildAdded(this); + } + + Regions.Add(this); + + Map.RegisterRegion(this); + + List sectors = new List(); + + for (int i = 0; i < Area.Length; i++) + { + Rectangle3D rect = Area[i]; + + Point2D start = Map.Bound(new Point2D(rect.Start)); + Point2D end = Map.Bound(new Point2D(rect.End)); + + Sector startSector = Map.GetSector(start); + Sector endSector = Map.GetSector(end); + + for (int x = startSector.X; x <= endSector.X; x++) + for (int y = startSector.Y; y <= endSector.Y; y++) + { + Sector sector = Map.GetRealSector(x, y); + + sector.OnEnter(this, rect); + + if (!sectors.Contains(sector)) + sectors.Add(sector); + } + } + + Sectors = sectors.ToArray(); + } + + public void Unregister() + { + if (!Registered) + return; + + OnUnregister(); + + Registered = false; + + if (Children.Count > 0) + Console.WriteLine("Warning: Unregistering region '{0}' with children", this); + + if (Parent != null) + { + Parent.Children.Remove(this); + Parent.OnChildRemoved(this); + } + + Regions.Remove(this); + + Map.UnregisterRegion(this); + + if (Sectors != null) + for (int i = 0; i < Sectors.Length; i++) + Sectors[i].OnLeave(this); + + Sectors = null; + } + + public bool Contains(Point3D p) + { + for (int i = 0; i < Area.Length; i++) + { + Rectangle3D rect = Area[i]; + + if (rect.Contains(p)) + return true; + } + + return false; + } + + public bool IsChildOf(Region region) + { + if (region == null) + return false; + + Region p = Parent; + + while (p != null) + { + if (p == region) + return true; + + p = p.Parent; + } + + return false; + } + + public Region GetRegion(Type regionType) + { + if (regionType == null) + return null; + + Region r = this; + + do + { + if (regionType.IsAssignableFrom(r.GetType())) + return r; + + r = r.Parent; + } while (r != null); + + return null; + } + + public Region GetRegion(string regionName) + { + if (regionName == null) + return null; + + Region r = this; + + do + { + if (r.m_Name == regionName) + return r; + + r = r.Parent; + } while (r != null); + + return null; + } + + public bool IsPartOf(Region region) + { + if (this == region) + return true; + + return IsChildOf(region); + } + + public bool IsPartOf(Type regionType) + { + return GetRegion(regionType) != null; + } + + public bool IsPartOf(string regionName) + { + return GetRegion(regionName) != null; + } + + public virtual bool AcceptsSpawnsFrom(Region region) + { + if (!AllowSpawn()) + return false; + + if (region == this) + return true; + + if (Parent != null) + return Parent.AcceptsSpawnsFrom(region); + + return false; + } + + public List GetPlayers() + { + List list = new List(); + + if (Sectors != null) + for (int i = 0; i < Sectors.Length; i++) + { + Sector sector = Sectors[i]; + + foreach (Mobile player in sector.Players) + if (player.Region.IsPartOf(this)) + list.Add(player); + } + + return list; + } + + public int GetPlayerCount() + { + int count = 0; + + if (Sectors != null) + for (int i = 0; i < Sectors.Length; i++) + { + Sector sector = Sectors[i]; + + foreach (Mobile player in sector.Players) + if (player.Region.IsPartOf(this)) + count++; + } + + return count; + } + + public List GetMobiles() + { + List list = new List(); + + if (Sectors != null) + for (int i = 0; i < Sectors.Length; i++) + { + Sector sector = Sectors[i]; + + foreach (Mobile mobile in sector.Mobiles) + if (mobile.Region.IsPartOf(this)) + list.Add(mobile); + } + + return list; + } + + public int GetMobileCount() + { + int count = 0; + + if (Sectors != null) + for (int i = 0; i < Sectors.Length; i++) + { + Sector sector = Sectors[i]; + + foreach (Mobile mobile in sector.Mobiles) + if (mobile.Region.IsPartOf(this)) + count++; + } + + return count; + } + + public override string ToString() + { + if (m_Name != null) + return m_Name; + return GetType().Name; + } + + + public virtual void OnRegister() + { + } + + public virtual void OnUnregister() + { + } + + public virtual void OnChildAdded(Region child) + { + } + + public virtual void OnChildRemoved(Region child) + { + } + + public virtual bool OnMoveInto(Mobile m, Direction d, Point3D newLocation, Point3D oldLocation) + { + return m.WalkRegion == null || AcceptsSpawnsFrom(m.WalkRegion); + } + + public virtual void OnEnter(Mobile m) + { + } + + public virtual void OnExit(Mobile m) + { + } + + public virtual void MakeGuard(Mobile focus) + { + Parent?.MakeGuard(focus); + } + + public virtual Type GetResource(Type type) + { + if (Parent != null) + return Parent.GetResource(type); + + return type; + } + + public virtual bool CanUseStuckMenu(Mobile m) + { + if (Parent != null) + return Parent.CanUseStuckMenu(m); + + return true; + } + + public virtual void OnAggressed(Mobile aggressor, Mobile aggressed, bool criminal) + { + Parent?.OnAggressed(aggressor, aggressed, criminal); + } + + public virtual void OnDidHarmful(Mobile harmer, Mobile harmed) + { + Parent?.OnDidHarmful(harmer, harmed); + } + + public virtual void OnGotHarmful(Mobile harmer, Mobile harmed) + { + Parent?.OnGotHarmful(harmer, harmed); + } + + public virtual void OnLocationChanged(Mobile m, Point3D oldLocation) + { + Parent?.OnLocationChanged(m, oldLocation); + } + + public virtual bool OnTarget(Mobile m, Target t, object o) + { + if (Parent != null) + return Parent.OnTarget(m, t, o); + + return true; + } + + public virtual bool OnCombatantChange(Mobile m, Mobile Old, Mobile New) + { + if (Parent != null) + return Parent.OnCombatantChange(m, Old, New); + + return true; + } + + public virtual bool AllowHousing(Mobile from, Point3D p) + { + if (Parent != null) + return Parent.AllowHousing(from, p); + + return true; + } + + public virtual bool SendInaccessibleMessage(Item item, Mobile from) + { + if (Parent != null) + return Parent.SendInaccessibleMessage(item, from); + + return false; + } + + public virtual bool CheckAccessibility(Item item, Mobile from) + { + if (Parent != null) + return Parent.CheckAccessibility(item, from); + + return true; + } + + public virtual bool OnDecay(Item item) + { + if (Parent != null) + return Parent.OnDecay(item); + + return true; + } + + public virtual bool AllowHarmful(Mobile from, Mobile target) + { + if (Parent != null) + return Parent.AllowHarmful(from, target); + + if (Mobile.AllowHarmfulHandler != null) + return Mobile.AllowHarmfulHandler(from, target); + + return true; + } + + public virtual void OnCriminalAction(Mobile m, bool message) + { + if (Parent != null) + Parent.OnCriminalAction(m, message); + else if (message) + m.SendLocalizedMessage(1005040); // You've committed a criminal act!! + } + + public virtual bool AllowBeneficial(Mobile from, Mobile target) + { + if (Parent != null) + return Parent.AllowBeneficial(from, target); + + if (Mobile.AllowBeneficialHandler != null) + return Mobile.AllowBeneficialHandler(from, target); + + return true; + } + + public virtual void OnBeneficialAction(Mobile helper, Mobile target) + { + Parent?.OnBeneficialAction(helper, target); + } + + public virtual void OnGotBeneficialAction(Mobile helper, Mobile target) + { + Parent?.OnGotBeneficialAction(helper, target); + } + + public virtual void SpellDamageScalar(Mobile caster, Mobile target, ref double damage) + { + Parent?.SpellDamageScalar(caster, target, ref damage); + } + + public virtual void OnSpeech(SpeechEventArgs args) + { + Parent?.OnSpeech(args); + } + + public virtual bool OnSkillUse(Mobile m, int Skill) + { + if (Parent != null) + return Parent.OnSkillUse(m, Skill); + + return true; + } + + public virtual bool OnBeginSpellCast(Mobile m, ISpell s) + { + if (Parent != null) + return Parent.OnBeginSpellCast(m, s); + + return true; + } + + public virtual void OnSpellCast(Mobile m, ISpell s) + { + Parent?.OnSpellCast(m, s); + } + + public virtual bool OnResurrect(Mobile m) + { + if (Parent != null) + return Parent.OnResurrect(m); + + return true; + } + + public virtual bool OnBeforeDeath(Mobile m) + { + if (Parent != null) + return Parent.OnBeforeDeath(m); + + return true; + } + + public virtual void OnDeath(Mobile m) + { + Parent?.OnDeath(m); + } + + public virtual bool OnDamage(Mobile m, ref int Damage) + { + if (Parent != null) + return Parent.OnDamage(m, ref Damage); + + return true; + } + + public virtual bool OnHeal(Mobile m, ref int Heal) + { + if (Parent != null) + return Parent.OnHeal(m, ref Heal); + + return true; + } + + public virtual bool OnDoubleClick(Mobile m, object o) + { + if (Parent != null) + return Parent.OnDoubleClick(m, o); + + return true; + } + + public virtual bool OnSingleClick(Mobile m, object o) + { + if (Parent != null) + return Parent.OnSingleClick(m, o); + + return true; + } + + public virtual bool AllowSpawn() + { + if (Parent != null) + return Parent.AllowSpawn(); + + return true; + } + + public virtual void AlterLightLevel(Mobile m, ref int global, ref int personal) + { + Parent?.AlterLightLevel(m, ref global, ref personal); + } + + public virtual TimeSpan GetLogoutDelay(Mobile m) + { + if (Parent != null) + return Parent.GetLogoutDelay(m); + if (m.AccessLevel > AccessLevel.Player) + return StaffLogoutDelay; + return DefaultLogoutDelay; + } + + + internal static bool CanMove(Mobile m, Direction d, Point3D newLocation, Point3D oldLocation, Map map) + { + Region oldRegion = m.Region; + Region newRegion = Find(newLocation, map); + + while (oldRegion != newRegion) + { + if (!newRegion.OnMoveInto(m, d, newLocation, oldLocation)) + return false; + + if (newRegion.Parent == null) + return true; + + newRegion = newRegion.Parent; + } + + return true; + } + + internal static void OnRegionChange(Mobile m, Region oldRegion, Region newRegion) + { + if (newRegion != null && m.NetState != null) + { + m.CheckLightLevels(false); + + if (oldRegion == null || oldRegion.Music != newRegion.Music) m.Send(PlayMusic.GetInstance(newRegion.Music)); + } + + Region oldR = oldRegion; + Region newR = newRegion; + + while (oldR != newR) + { + int oldRChild = oldR?.ChildLevel ?? -1; + int newRChild = newR?.ChildLevel ?? -1; + + if (oldRChild >= newRChild) + { + oldR.OnExit(m); + oldR = oldR.Parent; + } + + if (newRChild >= oldRChild) + { + newR.OnEnter(m); + newR = newR.Parent; + } + } + } + + + internal static void Load() + { + if (!File.Exists("Data/Regions.xml")) + { + Console.WriteLine("Error: Data/Regions.xml does not exist"); + return; + } + + Console.Write("Regions: Loading..."); + + XmlDocument doc = new XmlDocument(); + doc.Load(Path.Combine(Core.BaseDirectory, "Data/Regions.xml")); + + XmlElement root = doc["ServerRegions"]; + + if (root == null) + Console.WriteLine("Could not find root element 'ServerRegions' in Regions.xml"); + else + foreach (XmlElement facet in root.SelectNodes("Facet")) + { + Map map = null; + if (ReadMap(facet, "name", ref map)) + { + if (map == Map.Internal) + Console.WriteLine("Invalid internal map in a facet element"); + else + LoadRegions(facet, map, null); + } + } + + Console.WriteLine("done"); + } + + private static void LoadRegions(XmlElement xml, Map map, Region parent) + { + foreach (XmlElement xmlReg in xml.SelectNodes("region")) + { + Type type = DefaultRegionType; + + ReadType(xmlReg, "type", ref type, false); + + if (!typeof(Region).IsAssignableFrom(type)) + { + Console.WriteLine("Invalid region type '{0}' in regions.xml", type.FullName); + continue; + } + + Region region = null; + try + { + region = (Region)Activator.CreateInstance(type, xmlReg, map, parent); + } + catch (Exception ex) + { + Console.WriteLine("Error during the creation of region type '{0}': {1}", type.FullName, ex); + continue; + } + + region.Register(); + + LoadRegions(xmlReg, map, region); + } + } + + protected static string GetAttribute(XmlElement xml, string attribute, bool mandatory) + { + if (xml == null) + { + if (mandatory) + Console.WriteLine("Missing element for attribute '{0}'", attribute); + + return null; + } + + if (xml.HasAttribute(attribute)) return xml.GetAttribute(attribute); + if (mandatory) + Console.WriteLine("Missing attribute '{0}' in element '{1}'", attribute, xml.Name); + + return null; + } + + public static bool ReadString(XmlElement xml, string attribute, ref string value) + { + return ReadString(xml, attribute, ref value, true); + } + + public static bool ReadString(XmlElement xml, string attribute, ref string value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + value = s; + return true; + } + + public static bool ReadInt32(XmlElement xml, string attribute, ref int value) + { + return ReadInt32(xml, attribute, ref value, true); + } + + public static bool ReadInt32(XmlElement xml, string attribute, ref int value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + try + { + value = XmlConvert.ToInt32(s); + } + catch + { + Console.WriteLine("Could not parse integer attribute '{0}' in element '{1}'", attribute, xml.Name); + return false; + } + + return true; + } + + public static bool ReadBoolean(XmlElement xml, string attribute, ref bool value) + { + return ReadBoolean(xml, attribute, ref value, true); + } + + public static bool ReadBoolean(XmlElement xml, string attribute, ref bool value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + try + { + value = XmlConvert.ToBoolean(s); + } + catch + { + Console.WriteLine("Could not parse boolean attribute '{0}' in element '{1}'", attribute, xml.Name); + return false; + } + + return true; + } + + public static bool ReadDateTime(XmlElement xml, string attribute, ref DateTime value) + { + return ReadDateTime(xml, attribute, ref value, true); + } + + public static bool ReadDateTime(XmlElement xml, string attribute, ref DateTime value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + try + { + value = XmlConvert.ToDateTime(s, XmlDateTimeSerializationMode.Utc); + } + catch + { + Console.WriteLine("Could not parse DateTime attribute '{0}' in element '{1}'", attribute, xml.Name); + return false; + } + + return true; + } + + public static bool ReadTimeSpan(XmlElement xml, string attribute, ref TimeSpan value) + { + return ReadTimeSpan(xml, attribute, ref value, true); + } + + public static bool ReadTimeSpan(XmlElement xml, string attribute, ref TimeSpan value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + try + { + value = XmlConvert.ToTimeSpan(s); + } + catch + { + Console.WriteLine("Could not parse TimeSpan attribute '{0}' in element '{1}'", attribute, xml.Name); + return false; + } + + return true; + } + + public static bool ReadEnum(XmlElement xml, string attribute, ref T value) where T : struct + { + return ReadEnum(xml, attribute, ref value, true); + } + + public static bool ReadEnum(XmlElement xml, string attribute, ref T value, bool mandatory) + where T : struct // We can't limit the where clause to Enums only + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + Type type = typeof(T); + + T tempVal; + + if (type.IsEnum && Enum.TryParse(s, true, out tempVal)) + { + value = tempVal; + return true; + } + + Console.WriteLine("Could not parse {0} enum attribute '{1}' in element '{2}'", type, attribute, xml.Name); + return false; + } + + public static bool ReadMap(XmlElement xml, string attribute, ref Map value) + { + return ReadMap(xml, attribute, ref value, true); + } + + public static bool ReadMap(XmlElement xml, string attribute, ref Map value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + try + { + value = Map.Parse(s); + } + catch + { + Console.WriteLine("Could not parse Map attribute '{0}' in element '{1}'", attribute, xml.Name); + return false; + } + + return true; + } + + public static bool ReadType(XmlElement xml, string attribute, ref Type value) + { + return ReadType(xml, attribute, ref value, true); + } + + public static bool ReadType(XmlElement xml, string attribute, ref Type value, bool mandatory) + { + string s = GetAttribute(xml, attribute, mandatory); + + if (s == null) + return false; + + Type type; + try + { + type = ScriptCompiler.FindTypeByName(s, false); + } + catch + { + Console.WriteLine("Could not parse Type attribute '{0}' in element '{1}'", attribute, xml.Name); + return false; + } + + if (type == null) + { + Console.WriteLine("Could not find Type '{0}'", s); + return false; + } + + value = type; + return true; + } + + public static bool ReadPoint3D(XmlElement xml, Map map, ref Point3D value) + { + return ReadPoint3D(xml, map, ref value, true); + } + + public static bool ReadPoint3D(XmlElement xml, Map map, ref Point3D value, bool mandatory) + { + int x = 0, y = 0, z = 0; + + bool xyOk = ReadInt32(xml, "x", ref x, mandatory) & ReadInt32(xml, "y", ref y, mandatory); + bool zOk = ReadInt32(xml, "z", ref z, mandatory && map == null); + + if (xyOk && (zOk || map != null)) + { + if (!zOk) + z = map.GetAverageZ(x, y); + + value = new Point3D(x, y, z); + return true; + } + + return false; + } + + public static bool ReadRectangle3D(XmlElement xml, int defaultMinZ, int defaultMaxZ, ref Rectangle3D value) + { + return ReadRectangle3D(xml, defaultMinZ, defaultMaxZ, ref value, true); + } + + public static bool ReadRectangle3D(XmlElement xml, int defaultMinZ, int defaultMaxZ, ref Rectangle3D value, + bool mandatory) + { + int x1 = 0, y1 = 0, x2 = 0, y2 = 0; + + if (xml.HasAttribute("x")) + { + if (ReadInt32(xml, "x", ref x1, mandatory) + & ReadInt32(xml, "y", ref y1, mandatory) + & ReadInt32(xml, "width", ref x2, mandatory) + & ReadInt32(xml, "height", ref y2, mandatory)) + { + x2 += x1; + y2 += y1; + } + else + { + return false; + } + } + else + { + if (!ReadInt32(xml, "x1", ref x1, mandatory) + | !ReadInt32(xml, "y1", ref y1, mandatory) + | !ReadInt32(xml, "x2", ref x2, mandatory) + | !ReadInt32(xml, "y2", ref y2, mandatory)) + return false; + } + + int z1 = defaultMinZ; + int z2 = defaultMaxZ; + + ReadInt32(xml, "zmin", ref z1, false); + ReadInt32(xml, "zmax", ref z2, false); + + value = new Rectangle3D(new Point3D(x1, y1, z1), new Point3D(x2, y2, z2)); + + return true; + } + } +} \ No newline at end of file diff --git a/Server/ScriptCompiler.cs b/Server/ScriptCompiler.cs index fbbdcdaf2..145069a41 100644 --- a/Server/ScriptCompiler.cs +++ b/Server/ScriptCompiler.cs @@ -21,776 +21,752 @@ using System; using System.CodeDom.Compiler; using System.Collections.Generic; +using System.Diagnostics; using System.IO; -using System.Text; using System.Reflection; using System.Security.Cryptography; -using System.Diagnostics; +using System.Text; namespace Server { - public static class ScriptCompiler - { - public static Assembly[] Assemblies { get; set; } + public static class ScriptCompiler + { + private static List m_AdditionalReferences = new List(); - private static List m_AdditionalReferences = new List(); + private static Dictionary m_TypeCaches = new Dictionary(); + private static TypeCache m_NullCache; + public static Assembly[] Assemblies{ get; set; } - public static string[] GetReferenceAssemblies() - { - List list = new List(); + public static string[] GetReferenceAssemblies() + { + List list = new List(); - string path = Path.Combine( Core.BaseDirectory, "Data/Assemblies.cfg" ); + string path = Path.Combine(Core.BaseDirectory, "Data/Assemblies.cfg"); - if ( File.Exists( path ) ) - { - using( StreamReader ip = new StreamReader( path ) ) - { - string line; + if (File.Exists(path)) + using (StreamReader ip = new StreamReader(path)) + { + string line; - while( (line = ip.ReadLine()) != null ) - { - if ( line.Length > 0 && !line.StartsWith( "#" ) ) - list.Add( line ); - } - } - } + while ((line = ip.ReadLine()) != null) + if (line.Length > 0 && !line.StartsWith("#")) + list.Add(line); + } - list.Add( Core.ExePath ); + list.Add(Core.ExePath); - list.AddRange( m_AdditionalReferences ); + list.AddRange(m_AdditionalReferences); - return list.ToArray(); - } + return list.ToArray(); + } - public static string GetCompilerOptions( bool debug ) - { - StringBuilder sb = null; + public static string GetCompilerOptions(bool debug) + { + StringBuilder sb = null; - AppendCompilerOption( ref sb, "/unsafe" ); + AppendCompilerOption(ref sb, "/unsafe"); - if ( !debug ) - AppendCompilerOption( ref sb, "/optimize" ); + if (!debug) + AppendCompilerOption(ref sb, "/optimize"); #if MONO AppendCompilerOption( ref sb, "/d:MONO" ); #endif - if ( Core.Is64Bit ) - AppendCompilerOption( ref sb, "/d:x64" ); + if (Core.Is64Bit) + AppendCompilerOption(ref sb, "/d:x64"); #if NEWTIMERS - AppendCompilerOption(ref sb, "/d:NEWTIMERS"); + AppendCompilerOption(ref sb, "/d:NEWTIMERS"); #endif #if NEWPARENT - AppendCompilerOption(ref sb, "/d:NEWPARENT"); + AppendCompilerOption(ref sb, "/d:NEWPARENT"); #endif - return sb?.ToString(); - } - - private static void AppendCompilerOption( ref StringBuilder sb, string define ) - { - if ( sb == null ) - sb = new StringBuilder(); - else - sb.Append( ' ' ); - - sb.Append( define ); - } - - private static byte[] GetHashCode( string compiledFile, string[] scriptFiles, bool debug ) - { - using( MemoryStream ms = new MemoryStream() ) - { - using( BinaryWriter bin = new BinaryWriter( ms ) ) - { - FileInfo fileInfo = new FileInfo( compiledFile ); - - bin.Write( fileInfo.LastWriteTimeUtc.Ticks ); - - foreach( string scriptFile in scriptFiles ) - { - fileInfo = new FileInfo( scriptFile ); - - bin.Write( fileInfo.LastWriteTimeUtc.Ticks ); - } - - bin.Write( debug ); - bin.Write( Core.Version.ToString() ); - - ms.Position = 0; - - using( SHA1 sha1 = SHA1.Create() ) - { - return sha1.ComputeHash( ms ); - } - } - } - } - - public static bool CompileCSScripts( out Assembly assembly ) - { - return CompileCSScripts( false, true, out assembly ); - } - - public static bool CompileCSScripts( bool debug, out Assembly assembly ) - { - return CompileCSScripts( debug, true, out assembly ); - } - - public static bool CompileCSScripts( bool debug, bool cache, out Assembly assembly ) - { - Console.Write( "Scripts: Compiling C# scripts..." ); - string[] files = GetScripts( "*.cs" ); - - if ( files.Length == 0 ) - { - Console.WriteLine( "no files found." ); - assembly = null; - return true; - } - - if ( File.Exists( "Scripts/Output/Scripts.CS.dll" ) ) - { - if ( cache && File.Exists( "Scripts/Output/Scripts.CS.hash" ) ) - { - try - { - byte[] hashCode = GetHashCode( "Scripts/Output/Scripts.CS.dll", files, debug ); - - using( FileStream fs = new FileStream( "Scripts/Output/Scripts.CS.hash", FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - using( BinaryReader bin = new BinaryReader( fs ) ) - { - byte[] bytes = bin.ReadBytes( hashCode.Length ); - - if ( bytes.Length == hashCode.Length ) - { - bool valid = true; - - for( int i = 0; i < bytes.Length; ++i ) - { - if ( bytes[i] != hashCode[i] ) - { - valid = false; - break; - } - } - - if ( valid ) - { - assembly = Assembly.LoadFrom( "Scripts/Output/Scripts.CS.dll" ); - - if ( !m_AdditionalReferences.Contains( assembly.Location ) ) - { - m_AdditionalReferences.Add( assembly.Location ); - } - - Console.WriteLine( "done (cached)" ); - - return true; - } - } - } - } - } - catch - { - } - } - } - - DeleteFiles( "Scripts.CS*.dll" ); - - using (CodeDomProvider provider = CodeDomProvider.CreateProvider("CSharp")) - { - string path = GetUnusedPath( "Scripts.CS" ); - - CompilerParameters parms = new CompilerParameters( GetReferenceAssemblies(), path, debug ); - - string options = GetCompilerOptions( debug ); - - if ( options != null ) - parms.CompilerOptions = options; - - if ( Core.HaltOnWarning ) - parms.WarningLevel = 4; - - if (Core.Unix) - { - parms.CompilerOptions = $"{parms.CompilerOptions} /nowarn:169,219,414 /recurse:Scripts/*.cs"; - files = new string[0]; - } - - CompilerResults results = provider.CompileAssemblyFromFile( parms, files ); - m_AdditionalReferences.Add( path ); - - Display( results ); - - if ( results.Errors.Count > 0 ) - { - if (!Core.Unix) { - assembly = null; - return false; - } - - foreach (CompilerError err in results.Errors) - { - if (!err.IsWarning) - { - assembly = null; - return false; - } - } - } - - - if ( cache && Path.GetFileName( path ) == "Scripts.CS.dll" ) - { - try - { - byte[] hashCode = GetHashCode( path, files, debug ); - - using( FileStream fs = new FileStream( "Scripts/Output/Scripts.CS.hash", FileMode.Create, FileAccess.Write, FileShare.None ) ) - { - using( BinaryWriter bin = new BinaryWriter( fs ) ) - { - bin.Write( hashCode, 0, hashCode.Length ); - } - } - } - catch - { - } - } - - assembly = results.CompiledAssembly; - return true; - } - } - - public static bool CompileVBScripts( out Assembly assembly ) - { - return CompileVBScripts( false, out assembly ); - } - - public static bool CompileVBScripts( bool debug, out Assembly assembly ) - { - return CompileVBScripts( debug, true, out assembly ); - } - - public static bool CompileVBScripts( bool debug, bool cache, out Assembly assembly ) - { - Console.Write( "Scripts: Compiling VB.NET scripts..." ); - string[] files = GetScripts( "*.vb" ); - - if ( files.Length == 0 ) - { - Console.WriteLine( "no files found." ); - assembly = null; - return true; - } - - if ( File.Exists( "Scripts/Output/Scripts.VB.dll" ) ) - { - if ( cache && File.Exists( "Scripts/Output/Scripts.VB.hash" ) ) - { - byte[] hashCode = GetHashCode( "Scripts/Output/Scripts.VB.dll", files, debug ); - - try - { - using( FileStream fs = new FileStream( "Scripts/Output/Scripts.VB.hash", FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - using( BinaryReader bin = new BinaryReader( fs ) ) - { - byte[] bytes = bin.ReadBytes( hashCode.Length ); - - if ( bytes.Length == hashCode.Length ) - { - bool valid = true; - - for( int i = 0; i < bytes.Length; ++i ) - { - if ( bytes[i] != hashCode[i] ) - { - valid = false; - break; - } - } - - if ( valid ) - { - assembly = Assembly.LoadFrom( "Scripts/Output/Scripts.VB.dll" ); - - if ( !m_AdditionalReferences.Contains( assembly.Location ) ) - { - m_AdditionalReferences.Add( assembly.Location ); - } - - Console.WriteLine( "done (cached)" ); - - return true; - } - } - } - } - } - catch - { - } - } - } - - DeleteFiles( "Scripts.VB*.dll" ); - - using (CodeDomProvider provider = CodeDomProvider.CreateProvider("VisualBasic")) - { - string path = GetUnusedPath( "Scripts.VB" ); - - CompilerParameters parms = new CompilerParameters( GetReferenceAssemblies(), path, debug ); - - string options = GetCompilerOptions( debug ); - - if ( options != null ) - parms.CompilerOptions = options; - - if ( Core.HaltOnWarning ) - parms.WarningLevel = 4; - - if (Core.Unix) - { - parms.CompilerOptions = $"{parms.CompilerOptions} /nowarn:169,219,414 /recurse:Scripts/*.vb"; - files = new string[0]; - } - - CompilerResults results = provider.CompileAssemblyFromFile( parms, files ); - m_AdditionalReferences.Add( path ); - - Display( results ); - - if ( results.Errors.Count > 0 ) - { - if (!Core.Unix) { - assembly = null; - return false; - } - - foreach (CompilerError err in results.Errors) - { - if (!err.IsWarning) - { - assembly = null; - return false; - } - } - } - - if ( cache && Path.GetFileName( path ) == "Scripts.VB.dll" ) - { - try - { - byte[] hashCode = GetHashCode( path, files, debug ); - - using( FileStream fs = new FileStream( "Scripts/Output/Scripts.VB.hash", FileMode.Create, FileAccess.Write, FileShare.None ) ) - { - using( BinaryWriter bin = new BinaryWriter( fs ) ) - { - bin.Write( hashCode, 0, hashCode.Length ); - } - } - } - catch - { - } - } - - assembly = results.CompiledAssembly; - return true; - } - } - - public static void Display( CompilerResults results ) - { - if ( results.Errors.Count > 0 ) - { - Dictionary> errors = new Dictionary>( results.Errors.Count, StringComparer.OrdinalIgnoreCase ); - Dictionary> warnings = new Dictionary>( results.Errors.Count, StringComparer.OrdinalIgnoreCase ); - - foreach( CompilerError e in results.Errors ) - { - string file = e.FileName; - - // Ridiculous. FileName is null if the warning/error is internally generated in csc. - if ( string.IsNullOrEmpty( file ) ) { - Console.WriteLine( "ScriptCompiler: {0}: {1}", e.ErrorNumber, e.ErrorText ); - continue; - } - - Dictionary> table = (e.IsWarning ? warnings : errors); - - List list = null; - table.TryGetValue( file, out list ); - - if ( list == null ) - table[file] = list = new List(); - - list.Add( e ); - } - - if ( errors.Count > 0 ) - Console.WriteLine( "failed ({0} errors, {1} warnings)", errors.Count, warnings.Count ); - else - Console.WriteLine( "done ({0} errors, {1} warnings)", errors.Count, warnings.Count ); - - string scriptRoot = Path.GetFullPath( Path.Combine( Core.BaseDirectory, "Scripts" + Path.DirectorySeparatorChar ) ); - Uri scriptRootUri = new Uri( scriptRoot ); - - Utility.PushColor( ConsoleColor.Yellow ); - - if ( warnings.Count > 0 ) - Console.WriteLine( "Warnings:" ); - - foreach( KeyValuePair> kvp in warnings ) - { - string fileName = kvp.Key; - List list = kvp.Value; - - string fullPath = Path.GetFullPath( fileName ); - string usedPath = Uri.UnescapeDataString( scriptRootUri.MakeRelativeUri( new Uri( fullPath ) ).OriginalString ); - - Console.WriteLine( " + {0}:", usedPath ); - - Utility.PushColor( ConsoleColor.DarkYellow ); - - foreach( CompilerError e in list ) - Console.WriteLine( " {0}: Line {1}: {2}", e.ErrorNumber, e.Line, e.ErrorText ); - - Utility.PopColor(); - } - - Utility.PopColor(); - - Utility.PushColor( ConsoleColor.Red ); - - if ( errors.Count > 0 ) - Console.WriteLine( "Errors:" ); - - foreach( KeyValuePair> kvp in errors ) - { - string fileName = kvp.Key; - List list = kvp.Value; - - string fullPath = Path.GetFullPath( fileName ); - string usedPath = Uri.UnescapeDataString( scriptRootUri.MakeRelativeUri( new Uri( fullPath ) ).OriginalString ); - - Console.WriteLine( " + {0}:", usedPath ); - - Utility.PushColor( ConsoleColor.DarkRed ); - - foreach( CompilerError e in list ) - Console.WriteLine( " {0}: Line {1}: {2}", e.ErrorNumber, e.Line, e.ErrorText ); - - Utility.PopColor(); - } - - Utility.PopColor(); - } - else - { - Console.WriteLine( "done (0 errors, 0 warnings)" ); - } - } + return sb?.ToString(); + } + + private static void AppendCompilerOption(ref StringBuilder sb, string define) + { + if (sb == null) + sb = new StringBuilder(); + else + sb.Append(' '); + + sb.Append(define); + } + + private static byte[] GetHashCode(string compiledFile, string[] scriptFiles, bool debug) + { + using (MemoryStream ms = new MemoryStream()) + { + using (BinaryWriter bin = new BinaryWriter(ms)) + { + FileInfo fileInfo = new FileInfo(compiledFile); + + bin.Write(fileInfo.LastWriteTimeUtc.Ticks); + + foreach (string scriptFile in scriptFiles) + { + fileInfo = new FileInfo(scriptFile); + + bin.Write(fileInfo.LastWriteTimeUtc.Ticks); + } + + bin.Write(debug); + bin.Write(Core.Version.ToString()); + + ms.Position = 0; + + using (SHA1 sha1 = SHA1.Create()) + { + return sha1.ComputeHash(ms); + } + } + } + } + + public static bool CompileCSScripts(out Assembly assembly) + { + return CompileCSScripts(false, true, out assembly); + } + + public static bool CompileCSScripts(bool debug, out Assembly assembly) + { + return CompileCSScripts(debug, true, out assembly); + } + + public static bool CompileCSScripts(bool debug, bool cache, out Assembly assembly) + { + Console.Write("Scripts: Compiling C# scripts..."); + string[] files = GetScripts("*.cs"); + + if (files.Length == 0) + { + Console.WriteLine("no files found."); + assembly = null; + return true; + } + + if (File.Exists("Scripts/Output/Scripts.CS.dll")) + if (cache && File.Exists("Scripts/Output/Scripts.CS.hash")) + try + { + byte[] hashCode = GetHashCode("Scripts/Output/Scripts.CS.dll", files, debug); + + using (FileStream fs = new FileStream("Scripts/Output/Scripts.CS.hash", FileMode.Open, + FileAccess.Read, FileShare.Read)) + { + using (BinaryReader bin = new BinaryReader(fs)) + { + byte[] bytes = bin.ReadBytes(hashCode.Length); + + if (bytes.Length == hashCode.Length) + { + bool valid = true; + + for (int i = 0; i < bytes.Length; ++i) + if (bytes[i] != hashCode[i]) + { + valid = false; + break; + } + + if (valid) + { + assembly = Assembly.LoadFrom("Scripts/Output/Scripts.CS.dll"); + + if (!m_AdditionalReferences.Contains(assembly.Location)) + m_AdditionalReferences.Add(assembly.Location); + + Console.WriteLine("done (cached)"); + + return true; + } + } + } + } + } + catch + { + } + + DeleteFiles("Scripts.CS*.dll"); + + using (CodeDomProvider provider = CodeDomProvider.CreateProvider("CSharp")) + { + string path = GetUnusedPath("Scripts.CS"); + + CompilerParameters parms = new CompilerParameters(GetReferenceAssemblies(), path, debug); + + string options = GetCompilerOptions(debug); + + if (options != null) + parms.CompilerOptions = options; + + if (Core.HaltOnWarning) + parms.WarningLevel = 4; + + if (Core.Unix) + { + parms.CompilerOptions = $"{parms.CompilerOptions} /nowarn:169,219,414 /recurse:Scripts/*.cs"; + files = new string[0]; + } + + CompilerResults results = provider.CompileAssemblyFromFile(parms, files); + m_AdditionalReferences.Add(path); + + Display(results); + + if (results.Errors.Count > 0) + { + if (!Core.Unix) + { + assembly = null; + return false; + } + + foreach (CompilerError err in results.Errors) + if (!err.IsWarning) + { + assembly = null; + return false; + } + } + + + if (cache && Path.GetFileName(path) == "Scripts.CS.dll") + try + { + byte[] hashCode = GetHashCode(path, files, debug); + + using (FileStream fs = new FileStream("Scripts/Output/Scripts.CS.hash", FileMode.Create, + FileAccess.Write, FileShare.None)) + { + using (BinaryWriter bin = new BinaryWriter(fs)) + { + bin.Write(hashCode, 0, hashCode.Length); + } + } + } + catch + { + } + + assembly = results.CompiledAssembly; + return true; + } + } + + public static bool CompileVBScripts(out Assembly assembly) + { + return CompileVBScripts(false, out assembly); + } + + public static bool CompileVBScripts(bool debug, out Assembly assembly) + { + return CompileVBScripts(debug, true, out assembly); + } + + public static bool CompileVBScripts(bool debug, bool cache, out Assembly assembly) + { + Console.Write("Scripts: Compiling VB.NET scripts..."); + string[] files = GetScripts("*.vb"); + + if (files.Length == 0) + { + Console.WriteLine("no files found."); + assembly = null; + return true; + } + + if (File.Exists("Scripts/Output/Scripts.VB.dll")) + if (cache && File.Exists("Scripts/Output/Scripts.VB.hash")) + { + byte[] hashCode = GetHashCode("Scripts/Output/Scripts.VB.dll", files, debug); + + try + { + using (FileStream fs = new FileStream("Scripts/Output/Scripts.VB.hash", FileMode.Open, + FileAccess.Read, FileShare.Read)) + { + using (BinaryReader bin = new BinaryReader(fs)) + { + byte[] bytes = bin.ReadBytes(hashCode.Length); + + if (bytes.Length == hashCode.Length) + { + bool valid = true; + + for (int i = 0; i < bytes.Length; ++i) + if (bytes[i] != hashCode[i]) + { + valid = false; + break; + } + + if (valid) + { + assembly = Assembly.LoadFrom("Scripts/Output/Scripts.VB.dll"); + + if (!m_AdditionalReferences.Contains(assembly.Location)) + m_AdditionalReferences.Add(assembly.Location); + + Console.WriteLine("done (cached)"); + + return true; + } + } + } + } + } + catch + { + } + } + + DeleteFiles("Scripts.VB*.dll"); + + using (CodeDomProvider provider = CodeDomProvider.CreateProvider("VisualBasic")) + { + string path = GetUnusedPath("Scripts.VB"); + + CompilerParameters parms = new CompilerParameters(GetReferenceAssemblies(), path, debug); + + string options = GetCompilerOptions(debug); + + if (options != null) + parms.CompilerOptions = options; + + if (Core.HaltOnWarning) + parms.WarningLevel = 4; + + if (Core.Unix) + { + parms.CompilerOptions = $"{parms.CompilerOptions} /nowarn:169,219,414 /recurse:Scripts/*.vb"; + files = new string[0]; + } + + CompilerResults results = provider.CompileAssemblyFromFile(parms, files); + m_AdditionalReferences.Add(path); + + Display(results); + + if (results.Errors.Count > 0) + { + if (!Core.Unix) + { + assembly = null; + return false; + } + + foreach (CompilerError err in results.Errors) + if (!err.IsWarning) + { + assembly = null; + return false; + } + } + + if (cache && Path.GetFileName(path) == "Scripts.VB.dll") + try + { + byte[] hashCode = GetHashCode(path, files, debug); + + using (FileStream fs = new FileStream("Scripts/Output/Scripts.VB.hash", FileMode.Create, + FileAccess.Write, FileShare.None)) + { + using (BinaryWriter bin = new BinaryWriter(fs)) + { + bin.Write(hashCode, 0, hashCode.Length); + } + } + } + catch + { + } + + assembly = results.CompiledAssembly; + return true; + } + } + + public static void Display(CompilerResults results) + { + if (results.Errors.Count > 0) + { + Dictionary> errors = + new Dictionary>(results.Errors.Count, StringComparer.OrdinalIgnoreCase); + Dictionary> warnings = + new Dictionary>(results.Errors.Count, StringComparer.OrdinalIgnoreCase); + + foreach (CompilerError e in results.Errors) + { + string file = e.FileName; + + // Ridiculous. FileName is null if the warning/error is internally generated in csc. + if (string.IsNullOrEmpty(file)) + { + Console.WriteLine("ScriptCompiler: {0}: {1}", e.ErrorNumber, e.ErrorText); + continue; + } + + Dictionary> table = e.IsWarning ? warnings : errors; + + List list = null; + table.TryGetValue(file, out list); + + if (list == null) + table[file] = list = new List(); + + list.Add(e); + } + + if (errors.Count > 0) + Console.WriteLine("failed ({0} errors, {1} warnings)", errors.Count, warnings.Count); + else + Console.WriteLine("done ({0} errors, {1} warnings)", errors.Count, warnings.Count); + + string scriptRoot = + Path.GetFullPath(Path.Combine(Core.BaseDirectory, "Scripts" + Path.DirectorySeparatorChar)); + Uri scriptRootUri = new Uri(scriptRoot); + + Utility.PushColor(ConsoleColor.Yellow); + + if (warnings.Count > 0) + Console.WriteLine("Warnings:"); + + foreach (KeyValuePair> kvp in warnings) + { + string fileName = kvp.Key; + List list = kvp.Value; + + string fullPath = Path.GetFullPath(fileName); + string usedPath = + Uri.UnescapeDataString(scriptRootUri.MakeRelativeUri(new Uri(fullPath)).OriginalString); + + Console.WriteLine(" + {0}:", usedPath); + + Utility.PushColor(ConsoleColor.DarkYellow); + + foreach (CompilerError e in list) + Console.WriteLine(" {0}: Line {1}: {2}", e.ErrorNumber, e.Line, e.ErrorText); + + Utility.PopColor(); + } + + Utility.PopColor(); + + Utility.PushColor(ConsoleColor.Red); + + if (errors.Count > 0) + Console.WriteLine("Errors:"); + + foreach (KeyValuePair> kvp in errors) + { + string fileName = kvp.Key; + List list = kvp.Value; + + string fullPath = Path.GetFullPath(fileName); + string usedPath = + Uri.UnescapeDataString(scriptRootUri.MakeRelativeUri(new Uri(fullPath)).OriginalString); + + Console.WriteLine(" + {0}:", usedPath); + + Utility.PushColor(ConsoleColor.DarkRed); + + foreach (CompilerError e in list) + Console.WriteLine(" {0}: Line {1}: {2}", e.ErrorNumber, e.Line, e.ErrorText); + + Utility.PopColor(); + } + + Utility.PopColor(); + } + else + { + Console.WriteLine("done (0 errors, 0 warnings)"); + } + } - public static string GetUnusedPath( string name ) - { - string path = Path.Combine( Core.BaseDirectory, $"Scripts/Output/{name}.dll"); + public static string GetUnusedPath(string name) + { + string path = Path.Combine(Core.BaseDirectory, $"Scripts/Output/{name}.dll"); - for( int i = 2; File.Exists( path ) && i <= 1000; ++i ) - path = Path.Combine( Core.BaseDirectory, $"Scripts/Output/{name}.{i}.dll"); + for (int i = 2; File.Exists(path) && i <= 1000; ++i) + path = Path.Combine(Core.BaseDirectory, $"Scripts/Output/{name}.{i}.dll"); - return path; - } + return path; + } - public static void DeleteFiles( string mask ) - { - try - { - string[] files = Directory.GetFiles( Path.Combine( Core.BaseDirectory, "Scripts/Output" ), mask ); + public static void DeleteFiles(string mask) + { + try + { + string[] files = Directory.GetFiles(Path.Combine(Core.BaseDirectory, "Scripts/Output"), mask); - foreach( string file in files ) - { - try { File.Delete( file ); } - catch { } - } - } - catch - { - } - } + foreach (string file in files) + try + { + File.Delete(file); + } + catch + { + } + } + catch + { + } + } - private delegate CompilerResults Compiler( bool debug ); + public static bool Compile() + { + return Compile(false); + } - public static bool Compile() - { - return Compile( false ); - } + public static bool Compile(bool debug) + { + return Compile(debug, true); + } - public static bool Compile( bool debug ) - { - return Compile( debug, true ); - } + public static bool Compile(bool debug, bool cache) + { + EnsureDirectory("Scripts/"); + EnsureDirectory("Scripts/Output/"); - public static bool Compile( bool debug, bool cache ) - { - EnsureDirectory( "Scripts/" ); - EnsureDirectory( "Scripts/Output/" ); + if (m_AdditionalReferences.Count > 0) + m_AdditionalReferences.Clear(); - if ( m_AdditionalReferences.Count > 0 ) - m_AdditionalReferences.Clear(); + List assemblies = new List(); - List assemblies = new List(); + Assembly assembly; - Assembly assembly; + if (CompileCSScripts(debug, cache, out assembly)) + { + if (assembly != null) assemblies.Add(assembly); + } + else + { + return false; + } - if ( CompileCSScripts( debug, cache, out assembly ) ) - { - if ( assembly != null ) - { - assemblies.Add( assembly ); - } - } - else - { - return false; - } + if (Core.VBdotNet) + { + if (CompileVBScripts(debug, cache, out assembly)) + { + if (assembly != null) assemblies.Add(assembly); + } + else + { + return false; + } + } + else + { + Console.WriteLine("Scripts: Skipping VB.NET Scripts...done (use -vb to enable)"); + } - if ( Core.VBdotNet ) - { - if ( CompileVBScripts( debug, cache, out assembly ) ) - { - if ( assembly != null ) - { - assemblies.Add( assembly ); - } - } - else - { - return false; - } - } - else - { - Console.WriteLine( "Scripts: Skipping VB.NET Scripts...done (use -vb to enable)"); - } - - if ( assemblies.Count == 0 ) - { - return false; - } - - Assemblies = assemblies.ToArray(); - - Console.Write( "Scripts: Verifying..." ); - - Stopwatch watch = Stopwatch.StartNew(); - - Core.VerifySerialization(); - - watch.Stop(); - - Console.WriteLine("done ({0} items, {1} mobiles) ({2:F2} seconds)", Core.ScriptItems, Core.ScriptMobiles, watch.Elapsed.TotalSeconds); - - return true; - } - - public static void Invoke( string method ) - { - List invoke = new List(); - - for( int a = 0; a < Assemblies.Length; ++a ) - { - Type[] types = Assemblies[a].GetTypes(); - - for( int i = 0; i < types.Length; ++i ) - { - MethodInfo m = types[i].GetMethod( method, BindingFlags.Static | BindingFlags.Public ); - - if ( m != null ) - invoke.Add( m ); - } - } + if (assemblies.Count == 0) return false; + + Assemblies = assemblies.ToArray(); - invoke.Sort( new CallPriorityComparer() ); + Console.Write("Scripts: Verifying..."); + + Stopwatch watch = Stopwatch.StartNew(); + + Core.VerifySerialization(); + + watch.Stop(); + + Console.WriteLine("done ({0} items, {1} mobiles) ({2:F2} seconds)", Core.ScriptItems, Core.ScriptMobiles, + watch.Elapsed.TotalSeconds); + + return true; + } + + public static void Invoke(string method) + { + List invoke = new List(); - for( int i = 0; i < invoke.Count; ++i ) - invoke[i].Invoke( null, null ); - } + for (int a = 0; a < Assemblies.Length; ++a) + { + Type[] types = Assemblies[a].GetTypes(); - private static Dictionary m_TypeCaches = new Dictionary(); - private static TypeCache m_NullCache; + for (int i = 0; i < types.Length; ++i) + { + MethodInfo m = types[i].GetMethod(method, BindingFlags.Static | BindingFlags.Public); + + if (m != null) + invoke.Add(m); + } + } + + invoke.Sort(new CallPriorityComparer()); + + for (int i = 0; i < invoke.Count; ++i) + invoke[i].Invoke(null, null); + } + + public static TypeCache GetTypeCache(Assembly asm) + { + if (asm == null) + { + if (m_NullCache == null) + m_NullCache = new TypeCache(null); - public static TypeCache GetTypeCache( Assembly asm ) - { - if ( asm == null ) - { - if ( m_NullCache == null ) - m_NullCache = new TypeCache( null ); + return m_NullCache; + } - return m_NullCache; - } + TypeCache c = null; + m_TypeCaches.TryGetValue(asm, out c); - TypeCache c = null; - m_TypeCaches.TryGetValue( asm, out c ); + if (c == null) + m_TypeCaches[asm] = c = new TypeCache(asm); - if ( c == null ) - m_TypeCaches[asm] = c = new TypeCache( asm ); + return c; + } - return c; - } + public static Type FindTypeByFullName(string fullName) + { + return FindTypeByFullName(fullName, true); + } - public static Type FindTypeByFullName( string fullName ) - { - return FindTypeByFullName( fullName, true ); - } + public static Type FindTypeByFullName(string fullName, bool ignoreCase) + { + Type type = null; - public static Type FindTypeByFullName( string fullName, bool ignoreCase ) - { - Type type = null; + for (int i = 0; type == null && i < Assemblies.Length; ++i) + type = GetTypeCache(Assemblies[i]).GetTypeByFullName(fullName, ignoreCase); - for( int i = 0; type == null && i < Assemblies.Length; ++i ) - type = GetTypeCache( Assemblies[i] ).GetTypeByFullName( fullName, ignoreCase ); + if (type == null) + type = GetTypeCache(Core.Assembly).GetTypeByFullName(fullName, ignoreCase); - if ( type == null ) - type = GetTypeCache( Core.Assembly ).GetTypeByFullName( fullName, ignoreCase ); + return type; + } - return type; - } + public static Type FindTypeByName(string name) + { + return FindTypeByName(name, true); + } - public static Type FindTypeByName( string name ) - { - return FindTypeByName( name, true ); - } + public static Type FindTypeByName(string name, bool ignoreCase) + { + Type type = null; - public static Type FindTypeByName( string name, bool ignoreCase ) - { - Type type = null; + for (int i = 0; type == null && i < Assemblies.Length; ++i) + type = GetTypeCache(Assemblies[i]).GetTypeByName(name, ignoreCase); - for( int i = 0; type == null && i < Assemblies.Length; ++i ) - type = GetTypeCache( Assemblies[i] ).GetTypeByName( name, ignoreCase ); + if (type == null) + type = GetTypeCache(Core.Assembly).GetTypeByName(name, ignoreCase); - if ( type == null ) - type = GetTypeCache( Core.Assembly ).GetTypeByName( name, ignoreCase ); + return type; + } - return type; - } + public static void EnsureDirectory(string dir) + { + string path = Path.Combine(Core.BaseDirectory, dir); - public static void EnsureDirectory( string dir ) - { - string path = Path.Combine( Core.BaseDirectory, dir ); + if (!Directory.Exists(path)) + Directory.CreateDirectory(path); + } - if ( !Directory.Exists( path ) ) - Directory.CreateDirectory( path ); - } + public static string[] GetScripts(string filter) + { + List list = new List(); - public static string[] GetScripts( string filter ) - { - List list = new List(); + GetScripts(list, Path.Combine(Core.BaseDirectory, "Scripts"), filter); - GetScripts( list, Path.Combine( Core.BaseDirectory, "Scripts" ), filter ); + return list.ToArray(); + } - return list.ToArray(); - } - - public static void GetScripts( List list, string path, string filter ) - { - foreach( string dir in Directory.GetDirectories( path ) ) - GetScripts( list, dir, filter ); - - list.AddRange( Directory.GetFiles( path, filter ) ); - } - } - - public class TypeCache - { - public Type[] Types { get; } - - public TypeTable Names { get; } - - public TypeTable FullNames { get; } - - public Type GetTypeByName( string name, bool ignoreCase ) - { - return Names.Get( name, ignoreCase ); - } - - public Type GetTypeByFullName( string fullName, bool ignoreCase ) - { - return FullNames.Get( fullName, ignoreCase ); - } - - public TypeCache( Assembly asm ) - { - if ( asm == null ) - Types = Type.EmptyTypes; - else - Types = asm.GetTypes(); + public static void GetScripts(List list, string path, string filter) + { + foreach (string dir in Directory.GetDirectories(path)) + GetScripts(list, dir, filter); - Names = new TypeTable( Types.Length ); - FullNames = new TypeTable( Types.Length ); - - Type typeofTypeAliasAttribute = typeof( TypeAliasAttribute ); - - for( int i = 0; i < Types.Length; ++i ) - { - Type type = Types[i]; - - Names.Add( type.Name, type ); - FullNames.Add( type.FullName, type ); - - if ( type.IsDefined( typeofTypeAliasAttribute, false ) ) - { - object[] attrs = type.GetCustomAttributes( typeofTypeAliasAttribute, false ); - - if ( attrs != null && attrs.Length > 0 ) - { - if ( attrs[0] is TypeAliasAttribute attr ) - { - for( int j = 0; j < attr.Aliases.Length; ++j ) - FullNames.Add( attr.Aliases[j], type ); - } - } - } - } - } - } - - public class TypeTable - { - private Dictionary m_Sensitive, m_Insensitive; - - public void Add( string key, Type type ) - { - m_Sensitive[key] = type; - m_Insensitive[key] = type; - } - - public Type Get( string key, bool ignoreCase ) - { - Type t = null; - - if ( ignoreCase ) - m_Insensitive.TryGetValue( key, out t ); - else - m_Sensitive.TryGetValue( key, out t ); - - return t; - } - - public TypeTable( int capacity ) - { - m_Sensitive = new Dictionary( capacity ); - m_Insensitive = new Dictionary( capacity, StringComparer.OrdinalIgnoreCase ); - } - } -} + list.AddRange(Directory.GetFiles(path, filter)); + } + + private delegate CompilerResults Compiler(bool debug); + } + + public class TypeCache + { + public TypeCache(Assembly asm) + { + if (asm == null) + Types = Type.EmptyTypes; + else + Types = asm.GetTypes(); + + Names = new TypeTable(Types.Length); + FullNames = new TypeTable(Types.Length); + + Type typeofTypeAliasAttribute = typeof(TypeAliasAttribute); + + for (int i = 0; i < Types.Length; ++i) + { + Type type = Types[i]; + + Names.Add(type.Name, type); + FullNames.Add(type.FullName, type); + + if (type.IsDefined(typeofTypeAliasAttribute, false)) + { + object[] attrs = type.GetCustomAttributes(typeofTypeAliasAttribute, false); + + if (attrs != null && attrs.Length > 0) + if (attrs[0] is TypeAliasAttribute attr) + for (int j = 0; j < attr.Aliases.Length; ++j) + FullNames.Add(attr.Aliases[j], type); + } + } + } + + public Type[] Types{ get; } + + public TypeTable Names{ get; } + + public TypeTable FullNames{ get; } + + public Type GetTypeByName(string name, bool ignoreCase) + { + return Names.Get(name, ignoreCase); + } + + public Type GetTypeByFullName(string fullName, bool ignoreCase) + { + return FullNames.Get(fullName, ignoreCase); + } + } + + public class TypeTable + { + private Dictionary m_Sensitive, m_Insensitive; + + public TypeTable(int capacity) + { + m_Sensitive = new Dictionary(capacity); + m_Insensitive = new Dictionary(capacity, StringComparer.OrdinalIgnoreCase); + } + + public void Add(string key, Type type) + { + m_Sensitive[key] = type; + m_Insensitive[key] = type; + } + + public Type Get(string key, bool ignoreCase) + { + Type t = null; + + if (ignoreCase) + m_Insensitive.TryGetValue(key, out t); + else + m_Sensitive.TryGetValue(key, out t); + + return t; + } + } +} \ No newline at end of file diff --git a/Server/Sector.cs b/Server/Sector.cs index d88c6c581..e4e22c13a 100644 --- a/Server/Sector.cs +++ b/Server/Sector.cs @@ -23,276 +23,295 @@ using System.Collections.Generic; using Server.Items; using Server.Network; -namespace Server { - public class RegionRect : IComparable { - private Rectangle3D m_Rect; +namespace Server +{ + public class RegionRect : IComparable + { + private Rectangle3D m_Rect; - public Region Region { get; } + public RegionRect(Region region, Rectangle3D rect) + { + Region = region; + m_Rect = rect; + } - public Rectangle3D Rect => m_Rect; + public Region Region{ get; } - public RegionRect( Region region, Rectangle3D rect ) { - Region = region; - m_Rect = rect; - } + public Rectangle3D Rect => m_Rect; - public bool Contains( Point3D loc ) { - return m_Rect.Contains( loc ); - } + int IComparable.CompareTo(object obj) + { + if (obj == null) + return 1; - int IComparable.CompareTo( object obj ) { - if ( obj == null ) - return 1; + if (!(obj is RegionRect regRect)) + throw new ArgumentException("obj is not a RegionRect", nameof(obj)); - if ( !(obj is RegionRect regRect) ) - throw new ArgumentException( "obj is not a RegionRect", nameof(obj) ); + return ((IComparable)Region).CompareTo(regRect.Region); + } - return ( ( IComparable ) Region ).CompareTo( regRect.Region ); - } - } + public bool Contains(Point3D loc) + { + return m_Rect.Contains(loc); + } + } - public class Sector { - private List m_Mobiles; - private List m_Players; - private List m_Items; - private List m_Clients; - private List m_Multis; - private List m_RegionRects; - private bool m_Active; + public class Sector + { + // TODO: Can we avoid this? + private static List m_DefaultMobileList = new List(); + private static List m_DefaultItemList = new List(); + private static List m_DefaultClientList = new List(); + private static List m_DefaultMultiList = new List(); + private static List m_DefaultRectList = new List(); + private bool m_Active; + private List m_Clients; + private List m_Items; + private List m_Mobiles; + private List m_Multis; + private List m_Players; + private List m_RegionRects; - // TODO: Can we avoid this? - private static List m_DefaultMobileList = new List(); - private static List m_DefaultItemList = new List(); - private static List m_DefaultClientList = new List(); - private static List m_DefaultMultiList = new List(); - private static List m_DefaultRectList = new List(); + public Sector(int x, int y, Map owner) + { + X = x; + Y = y; + Owner = owner; + m_Active = false; + } - public Sector( int x, int y, Map owner ) { - X = x; - Y = y; - Owner = owner; - m_Active = false; - } + public List RegionRects + { + get + { + if (m_RegionRects == null) + return m_DefaultRectList; - private void Add( ref List list, T value ) { - if ( list == null ) { - list = new List(); - } + return m_RegionRects; + } + } - list.Add( value ); - } + public List Multis + { + get + { + if (m_Multis == null) + return m_DefaultMultiList; - private void Remove( ref List list, T value ) { - if ( list != null ) { - list.Remove( value ); + return m_Multis; + } + } - if ( list.Count == 0 ) { - list = null; - } - } - } + public List Mobiles + { + get + { + if (m_Mobiles == null) + return m_DefaultMobileList; - private void Replace( ref List list, T oldValue, T newValue ) { - if ( oldValue != null && newValue != null ) { - int index = list?.IndexOf( oldValue ) ?? -1; + return m_Mobiles; + } + } - if ( index >= 0 ) { - list[index] = newValue; - } else { - Add( ref list, newValue ); - } - } else if ( oldValue != null ) { - Remove( ref list, oldValue ); - } else if ( newValue != null ) { - Add( ref list, newValue ); - } - } + public List Items + { + get + { + if (m_Items == null) + return m_DefaultItemList; - public void OnClientChange( NetState oldState, NetState newState ) { - Replace( ref m_Clients, oldState, newState ); - } + return m_Items; + } + } - public void OnEnter( Item item ) { - Add( ref m_Items, item ); - } + public List Clients + { + get + { + if (m_Clients == null) + return m_DefaultClientList; - public void OnLeave( Item item ) { - Remove( ref m_Items, item ); - } + return m_Clients; + } + } - public void OnEnter( Mobile mob ) { - Add( ref m_Mobiles, mob ); + public List Players + { + get + { + if (m_Players == null) + return m_DefaultMobileList; - if ( mob.NetState != null ) { - Add( ref m_Clients, mob.NetState ); - } + return m_Players; + } + } - if ( mob.Player ) { - if ( m_Players == null ) { - Owner.ActivateSectors( X, Y ); - } + public bool Active => m_Active && Owner != Map.Internal; - Add( ref m_Players, mob ); - } - } + public Map Owner{ get; } - public void OnLeave( Mobile mob ) { - Remove( ref m_Mobiles, mob ); + public int X{ get; } - if ( mob.NetState != null ) { - Remove( ref m_Clients, mob.NetState ); - } + public int Y{ get; } - if ( mob.Player && m_Players != null ) { - Remove( ref m_Players, mob ); + private void Add(ref List list, T value) + { + if (list == null) list = new List(); - if ( m_Players == null ) { - Owner.DeactivateSectors( X, Y ); - } - } - } + list.Add(value); + } - public void OnEnter( Region region, Rectangle3D rect ) { - Add( ref m_RegionRects, new RegionRect( region, rect ) ); + private void Remove(ref List list, T value) + { + if (list != null) + { + list.Remove(value); - m_RegionRects.Sort(); + if (list.Count == 0) list = null; + } + } - UpdateMobileRegions(); - } + private void Replace(ref List list, T oldValue, T newValue) + { + if (oldValue != null && newValue != null) + { + int index = list?.IndexOf(oldValue) ?? -1; - public void OnLeave( Region region ) { - if ( m_RegionRects != null ) { - for ( int i = m_RegionRects.Count - 1; i >= 0; i-- ) { - RegionRect regRect = m_RegionRects[i]; + if (index >= 0) + list[index] = newValue; + else + Add(ref list, newValue); + } + else if (oldValue != null) + { + Remove(ref list, oldValue); + } + else if (newValue != null) + { + Add(ref list, newValue); + } + } - if ( regRect.Region == region ) { - m_RegionRects.RemoveAt( i ); - } - } + public void OnClientChange(NetState oldState, NetState newState) + { + Replace(ref m_Clients, oldState, newState); + } - if ( m_RegionRects.Count == 0 ) { - m_RegionRects = null; - } - } + public void OnEnter(Item item) + { + Add(ref m_Items, item); + } - UpdateMobileRegions(); - } + public void OnLeave(Item item) + { + Remove(ref m_Items, item); + } - private void UpdateMobileRegions() { - if ( m_Mobiles != null ) { - List sandbox = new List( m_Mobiles ); + public void OnEnter(Mobile mob) + { + Add(ref m_Mobiles, mob); - foreach ( Mobile mob in sandbox ) { - mob.UpdateRegion(); - } - } - } + if (mob.NetState != null) Add(ref m_Clients, mob.NetState); - public void OnMultiEnter( BaseMulti multi ) { - Add( ref m_Multis, multi ); - } + if (mob.Player) + { + if (m_Players == null) Owner.ActivateSectors(X, Y); - public void OnMultiLeave( BaseMulti multi ) { - Remove( ref m_Multis, multi ); - } + Add(ref m_Players, mob); + } + } - public void Activate() { - if ( !Active && Owner != Map.Internal ) { - if ( m_Items != null ) { - foreach ( Item item in m_Items ) { - item.OnSectorActivate(); - } - } + public void OnLeave(Mobile mob) + { + Remove(ref m_Mobiles, mob); - if ( m_Mobiles != null ) { - foreach ( Mobile mob in m_Mobiles ) { - mob.OnSectorActivate(); - } - } + if (mob.NetState != null) Remove(ref m_Clients, mob.NetState); - m_Active = true; - } - } + if (mob.Player && m_Players != null) + { + Remove(ref m_Players, mob); - public void Deactivate() { - if ( Active ) { - if ( m_Items != null ) { - foreach ( Item item in m_Items ) { - item.OnSectorDeactivate(); - } - } + if (m_Players == null) Owner.DeactivateSectors(X, Y); + } + } - if ( m_Mobiles != null ) { - foreach ( Mobile mob in m_Mobiles ) { - mob.OnSectorDeactivate(); - } - } + public void OnEnter(Region region, Rectangle3D rect) + { + Add(ref m_RegionRects, new RegionRect(region, rect)); - m_Active = false; - } - } + m_RegionRects.Sort(); - public List RegionRects { - get { - if ( m_RegionRects == null ) - return m_DefaultRectList; + UpdateMobileRegions(); + } - return m_RegionRects; - } - } + public void OnLeave(Region region) + { + if (m_RegionRects != null) + { + for (int i = m_RegionRects.Count - 1; i >= 0; i--) + { + RegionRect regRect = m_RegionRects[i]; - public List Multis { - get { - if ( m_Multis == null ) - return m_DefaultMultiList; + if (regRect.Region == region) m_RegionRects.RemoveAt(i); + } - return m_Multis; - } - } + if (m_RegionRects.Count == 0) m_RegionRects = null; + } - public List Mobiles { - get { - if ( m_Mobiles == null ) - return m_DefaultMobileList; + UpdateMobileRegions(); + } - return m_Mobiles; - } - } + private void UpdateMobileRegions() + { + if (m_Mobiles != null) + { + List sandbox = new List(m_Mobiles); - public List Items { - get { - if ( m_Items == null ) - return m_DefaultItemList; + foreach (Mobile mob in sandbox) mob.UpdateRegion(); + } + } - return m_Items; - } - } + public void OnMultiEnter(BaseMulti multi) + { + Add(ref m_Multis, multi); + } - public List Clients { - get { - if ( m_Clients == null ) - return m_DefaultClientList; + public void OnMultiLeave(BaseMulti multi) + { + Remove(ref m_Multis, multi); + } - return m_Clients; - } - } + public void Activate() + { + if (!Active && Owner != Map.Internal) + { + if (m_Items != null) + foreach (Item item in m_Items) + item.OnSectorActivate(); - public List Players { - get { - if ( m_Players == null ) - return m_DefaultMobileList; + if (m_Mobiles != null) + foreach (Mobile mob in m_Mobiles) + mob.OnSectorActivate(); - return m_Players; - } - } + m_Active = true; + } + } - public bool Active => ( m_Active && Owner != Map.Internal ); + public void Deactivate() + { + if (Active) + { + if (m_Items != null) + foreach (Item item in m_Items) + item.OnSectorDeactivate(); - public Map Owner { get; } + if (m_Mobiles != null) + foreach (Mobile mob in m_Mobiles) + mob.OnSectorDeactivate(); - public int X { get; } - - public int Y { get; } - } -} + m_Active = false; + } + } + } +} \ No newline at end of file diff --git a/Server/SecureTrade.cs b/Server/SecureTrade.cs index 37a8c7245..c023b5732 100644 --- a/Server/SecureTrade.cs +++ b/Server/SecureTrade.cs @@ -19,484 +19,388 @@ ***************************************************************************/ #region References -using System; +using System; +using System.Collections.Generic; using Server.Accounting; using Server.Items; using Server.Network; + #endregion namespace Server { - public class SecureTrade - { - public SecureTrade(Mobile from, Mobile to) - { - Valid = true; - - From = new SecureTradeInfo(this, from, new SecureTradeContainer(this)); - To = new SecureTradeInfo(this, to, new SecureTradeContainer(this)); - - var from6017 = (from.NetState != null && from.NetState.ContainerGridLines); - var to6017 = (to.NetState != null && to.NetState.ContainerGridLines); - - var from704565 = (from.NetState != null && from.NetState.NewSecureTrading); - var to704565 = (to.NetState != null && to.NetState.NewSecureTrading); - - from.Send(new MobileStatus(from, to)); - from.Send(new UpdateSecureTrade(From.Container, false, false)); - - if (from6017) - { - from.Send(new SecureTradeEquip6017(To.Container, to)); - } - else - { - from.Send(new SecureTradeEquip(To.Container, to)); - } - - from.Send(new UpdateSecureTrade(From.Container, false, false)); - - if (from6017) - { - from.Send(new SecureTradeEquip6017(From.Container, from)); - } - else - { - from.Send(new SecureTradeEquip(From.Container, from)); - } - - from.Send(new DisplaySecureTrade(to, From.Container, To.Container, to.Name)); - from.Send(new UpdateSecureTrade(From.Container, false, false)); - - if (from.Account != null && from704565) - { - from.Send( - new UpdateSecureTrade(From.Container, TradeFlag.UpdateLedger, from.Account.TotalGold, from.Account.TotalPlat)); - } - - to.Send(new MobileStatus(to, from)); - to.Send(new UpdateSecureTrade(To.Container, false, false)); - - if (to6017) - { - to.Send(new SecureTradeEquip6017(From.Container, from)); - } - else - { - to.Send(new SecureTradeEquip(From.Container, from)); - } - - to.Send(new UpdateSecureTrade(To.Container, false, false)); - - if (to6017) - { - to.Send(new SecureTradeEquip6017(To.Container, to)); - } - else - { - to.Send(new SecureTradeEquip(To.Container, to)); - } - - to.Send(new DisplaySecureTrade(from, To.Container, From.Container, from.Name)); - to.Send(new UpdateSecureTrade(To.Container, false, false)); - - if (to.Account != null && to704565) - { - to.Send(new UpdateSecureTrade(To.Container, TradeFlag.UpdateLedger, to.Account.TotalGold, to.Account.TotalPlat)); - } - } - - public SecureTradeInfo From { get; } - - public SecureTradeInfo To { get; } - - public bool Valid { get; private set; } - - public void Cancel() - { - if (!Valid) - { - return; - } - - var list = From.Container.Items; - - for (var i = list.Count - 1; i >= 0; --i) - { - if (i < list.Count) - { - var item = list[i]; - - if (item == From.VirtualCheck) - { - continue; - } - - item.OnSecureTrade(From.Mobile, To.Mobile, From.Mobile, false); - - if (!item.Deleted) - { - From.Mobile.AddToBackpack(item); - } - } - } - - list = To.Container.Items; - - for (var i = list.Count - 1; i >= 0; --i) - { - if (i < list.Count) - { - var item = list[i]; - - if (item == To.VirtualCheck) - { - continue; - } - - item.OnSecureTrade(To.Mobile, From.Mobile, To.Mobile, false); - - if (!item.Deleted) - { - To.Mobile.AddToBackpack(item); - } - } - } - - Close(); - } - - public void Close() - { - if (!Valid) - { - return; - } - - From.Mobile.Send(new CloseSecureTrade(From.Container)); - To.Mobile.Send(new CloseSecureTrade(To.Container)); - - Valid = false; - - var ns = From.Mobile.NetState; - - ns?.RemoveTrade(this); - - ns = To.Mobile.NetState; - - ns?.RemoveTrade(this); - - Timer.DelayCall(From.Dispose); - Timer.DelayCall(To.Dispose); - } - - public void UpdateFromCurrency() - { - UpdateCurrency(From, To); - } - - public void UpdateToCurrency() - { - UpdateCurrency(To, From); - } - - private static void UpdateCurrency(SecureTradeInfo left, SecureTradeInfo right) - { - if (left.Mobile.NetState != null && left.Mobile.NetState.NewSecureTrading) - { - var plat = left.Mobile.Account.TotalPlat; - var gold = left.Mobile.Account.TotalGold; - - left.Mobile.Send(new UpdateSecureTrade(left.Container, TradeFlag.UpdateLedger, gold, plat)); - } - - if (right.Mobile.NetState != null && right.Mobile.NetState.NewSecureTrading) - { - right.Mobile.Send(new UpdateSecureTrade(right.Container, TradeFlag.UpdateGold, left.Gold, left.Plat)); - } - } - - public void Update() - { - if (!Valid) - { - return; - } - - if (!From.IsDisposed && From.Accepted && !To.IsDisposed && To.Accepted) - { - var list = From.Container.Items; - - var allowed = true; - - for (var i = list.Count - 1; allowed && i >= 0; --i) - { - if (i < list.Count) - { - var item = list[i]; - - if (item == From.VirtualCheck) - { - continue; - } - - if (!item.AllowSecureTrade(From.Mobile, To.Mobile, To.Mobile, true)) - { - allowed = false; - } - } - } - - list = To.Container.Items; - - for (var i = list.Count - 1; allowed && i >= 0; --i) - { - if (i < list.Count) - { - var item = list[i]; - - if (item == To.VirtualCheck) - { - continue; - } - - if (!item.AllowSecureTrade(To.Mobile, From.Mobile, From.Mobile, true)) - { - allowed = false; - } - } - } - - if (AccountGold.Enabled) - { - if (From.Mobile.Account != null) - { - int totalPlat = From.Mobile.Account.TotalPlat; - int totalGold = From.Mobile.Account.TotalGold; - - if (totalPlat < From.Plat || totalGold < From.Gold) - { - allowed = false; - From.Mobile.SendMessage("You do not have enough currency to complete this trade."); - } - } - - if (To.Mobile.Account != null) - { - int totalPlat = To.Mobile.Account.TotalPlat; - int totalGold = To.Mobile.Account.TotalGold; - - if (totalPlat < To.Plat || totalGold < To.Gold) - { - allowed = false; - To.Mobile.SendMessage("You do not have enough currency to complete this trade."); - } - } - } - - if (!allowed) - { - From.Accepted = false; - To.Accepted = false; - - From.Mobile.Send(new UpdateSecureTrade(From.Container, From.Accepted, To.Accepted)); - To.Mobile.Send(new UpdateSecureTrade(To.Container, To.Accepted, From.Accepted)); - - return; - } - - if (AccountGold.Enabled && From.Mobile.Account != null && To.Mobile.Account != null) - { - HandleAccountGoldTrade(); - } - - list = From.Container.Items; - - for (var i = list.Count - 1; i >= 0; --i) - { - if (i < list.Count) - { - var item = list[i]; - - if (item == From.VirtualCheck) - { - continue; - } - - item.OnSecureTrade(From.Mobile, To.Mobile, To.Mobile, true); - - if (!item.Deleted) - { - To.Mobile.AddToBackpack(item); - } - } - } - - list = To.Container.Items; - - for (var i = list.Count - 1; i >= 0; --i) - { - if (i < list.Count) - { - var item = list[i]; - - if (item == To.VirtualCheck) - { - continue; - } - - item.OnSecureTrade(To.Mobile, From.Mobile, From.Mobile, true); - - if (!item.Deleted) - { - From.Mobile.AddToBackpack(item); - } - } - } - - Close(); - } - else if (!From.IsDisposed && !To.IsDisposed) - { - From.Mobile.Send(new UpdateSecureTrade(From.Container, From.Accepted, To.Accepted)); - To.Mobile.Send(new UpdateSecureTrade(To.Container, To.Accepted, From.Accepted)); - } - } - - private void HandleAccountGoldTrade() - { - int fromPlatSend = 0, fromGoldSend = 0, fromPlatRecv = 0, fromGoldRecv = 0; - int toPlatSend = 0, toGoldSend = 0, toPlatRecv = 0, toGoldRecv = 0; - - if (From.Plat > 0 & From.Mobile.Account.WithdrawPlat(From.Plat)) - { - fromPlatSend = From.Plat; - - if (To.Mobile.Account.DepositPlat(From.Plat)) - { - toPlatRecv = fromPlatSend; - } - } - - if (From.Gold > 0 & From.Mobile.Account.WithdrawGold(From.Gold)) - { - fromGoldSend = From.Gold; - - if (To.Mobile.Account.DepositGold(From.Gold)) - { - toGoldRecv = fromGoldSend; - } - } - - if (To.Plat > 0 & To.Mobile.Account.WithdrawPlat(To.Plat)) - { - toPlatSend = To.Plat; - - if (From.Mobile.Account.DepositPlat(To.Plat)) - { - fromPlatRecv = toPlatSend; - } - } - - if (To.Gold > 0 & To.Mobile.Account.WithdrawGold(To.Gold)) - { - toGoldSend = To.Gold; - - if (From.Mobile.Account.DepositGold(To.Gold)) - { - fromGoldRecv = toGoldSend; - } - } - - HandleAccountGoldTrade(From.Mobile, To.Mobile, fromPlatSend, fromGoldSend, fromPlatRecv, fromGoldRecv); - HandleAccountGoldTrade(To.Mobile, From.Mobile, toPlatSend, toGoldSend, toPlatRecv, toGoldRecv); - } - - private static void HandleAccountGoldTrade( - Mobile left, - Mobile right, - int platSend, - int goldSend, - int platRecv, - int goldRecv) - { - if (platSend > 0 || goldSend > 0) - { - if (platSend > 0 && goldSend > 0) - { - left.SendMessage("You traded {0:#,0} platinum and {1:#,0} gold to {2}.", platSend, goldSend, right.RawName); - } - else if (platSend > 0) - { - left.SendMessage("You traded {0:#,0} platinum to {1}.", platSend, right.RawName); - } - else if (goldSend > 0) - { - left.SendMessage("You traded {0:#,0} gold to {1}.", goldSend, right.RawName); - } - } - - if (platRecv > 0 || goldRecv > 0) - { - if (platRecv > 0 && goldRecv > 0) - { - left.SendMessage("You received {0:#,0} platinum and {1:#,0} gold from {2}.", platRecv, goldRecv, right.RawName); - } - else if (platRecv > 0) - { - left.SendMessage("You received {0:#,0} platinum from {1}.", platRecv, right.RawName); - } - else if (goldRecv > 0) - { - left.SendMessage("You received {0:#,0} gold from {1}.", goldRecv, right.RawName); - } - } - } - } - - public class SecureTradeInfo : IDisposable - { - public SecureTrade Owner { get; private set; } - public Mobile Mobile { get; private set; } - public SecureTradeContainer Container { get; private set; } - public VirtualCheck VirtualCheck { get; private set; } - - public int Gold { get => VirtualCheck.Gold; - set => VirtualCheck.Gold = value; - } - public int Plat { get => VirtualCheck.Plat; - set => VirtualCheck.Plat = value; - } - - public bool Accepted { get; set; } - - public bool IsDisposed { get; private set; } - - public SecureTradeInfo(SecureTrade owner, Mobile m, SecureTradeContainer c) - { - Owner = owner; - Mobile = m; - Container = c; - - Mobile.AddItem(Container); - - VirtualCheck = new VirtualCheck(0, 0); - Container.DropItem(VirtualCheck); - } - - public void Dispose() - { - VirtualCheck.Delete(); - VirtualCheck = null; - - Container.Delete(); - Container = null; - - Mobile = null; - Owner = null; - - IsDisposed = true; - } - } -} + public class SecureTrade + { + public SecureTrade(Mobile from, Mobile to) + { + Valid = true; + + From = new SecureTradeInfo(this, from, new SecureTradeContainer(this)); + To = new SecureTradeInfo(this, to, new SecureTradeContainer(this)); + + bool from6017 = from.NetState != null && from.NetState.ContainerGridLines; + bool to6017 = to.NetState != null && to.NetState.ContainerGridLines; + + bool from704565 = from.NetState != null && from.NetState.NewSecureTrading; + bool to704565 = to.NetState != null && to.NetState.NewSecureTrading; + + from.Send(new MobileStatus(from, to)); + from.Send(new UpdateSecureTrade(From.Container, false, false)); + + if (from6017) + from.Send(new SecureTradeEquip6017(To.Container, to)); + else + from.Send(new SecureTradeEquip(To.Container, to)); + + from.Send(new UpdateSecureTrade(From.Container, false, false)); + + if (from6017) + from.Send(new SecureTradeEquip6017(From.Container, from)); + else + from.Send(new SecureTradeEquip(From.Container, from)); + + from.Send(new DisplaySecureTrade(to, From.Container, To.Container, to.Name)); + from.Send(new UpdateSecureTrade(From.Container, false, false)); + + if (from.Account != null && from704565) + from.Send( + new UpdateSecureTrade(From.Container, TradeFlag.UpdateLedger, from.Account.TotalGold, + from.Account.TotalPlat)); + + to.Send(new MobileStatus(to, from)); + to.Send(new UpdateSecureTrade(To.Container, false, false)); + + if (to6017) + to.Send(new SecureTradeEquip6017(From.Container, from)); + else + to.Send(new SecureTradeEquip(From.Container, from)); + + to.Send(new UpdateSecureTrade(To.Container, false, false)); + + if (to6017) + to.Send(new SecureTradeEquip6017(To.Container, to)); + else + to.Send(new SecureTradeEquip(To.Container, to)); + + to.Send(new DisplaySecureTrade(from, To.Container, From.Container, from.Name)); + to.Send(new UpdateSecureTrade(To.Container, false, false)); + + if (to.Account != null && to704565) + to.Send(new UpdateSecureTrade(To.Container, TradeFlag.UpdateLedger, to.Account.TotalGold, + to.Account.TotalPlat)); + } + + public SecureTradeInfo From{ get; } + + public SecureTradeInfo To{ get; } + + public bool Valid{ get; private set; } + + public void Cancel() + { + if (!Valid) return; + + List list = From.Container.Items; + + for (int i = list.Count - 1; i >= 0; --i) + if (i < list.Count) + { + Item item = list[i]; + + if (item == From.VirtualCheck) continue; + + item.OnSecureTrade(From.Mobile, To.Mobile, From.Mobile, false); + + if (!item.Deleted) From.Mobile.AddToBackpack(item); + } + + list = To.Container.Items; + + for (int i = list.Count - 1; i >= 0; --i) + if (i < list.Count) + { + Item item = list[i]; + + if (item == To.VirtualCheck) continue; + + item.OnSecureTrade(To.Mobile, From.Mobile, To.Mobile, false); + + if (!item.Deleted) To.Mobile.AddToBackpack(item); + } + + Close(); + } + + public void Close() + { + if (!Valid) return; + + From.Mobile.Send(new CloseSecureTrade(From.Container)); + To.Mobile.Send(new CloseSecureTrade(To.Container)); + + Valid = false; + + NetState ns = From.Mobile.NetState; + + ns?.RemoveTrade(this); + + ns = To.Mobile.NetState; + + ns?.RemoveTrade(this); + + Timer.DelayCall(From.Dispose); + Timer.DelayCall(To.Dispose); + } + + public void UpdateFromCurrency() + { + UpdateCurrency(From, To); + } + + public void UpdateToCurrency() + { + UpdateCurrency(To, From); + } + + private static void UpdateCurrency(SecureTradeInfo left, SecureTradeInfo right) + { + if (left.Mobile.NetState != null && left.Mobile.NetState.NewSecureTrading) + { + int plat = left.Mobile.Account.TotalPlat; + int gold = left.Mobile.Account.TotalGold; + + left.Mobile.Send(new UpdateSecureTrade(left.Container, TradeFlag.UpdateLedger, gold, plat)); + } + + if (right.Mobile.NetState != null && right.Mobile.NetState.NewSecureTrading) + right.Mobile.Send(new UpdateSecureTrade(right.Container, TradeFlag.UpdateGold, left.Gold, left.Plat)); + } + + public void Update() + { + if (!Valid) return; + + if (!From.IsDisposed && From.Accepted && !To.IsDisposed && To.Accepted) + { + List list = From.Container.Items; + + bool allowed = true; + + for (int i = list.Count - 1; allowed && i >= 0; --i) + if (i < list.Count) + { + Item item = list[i]; + + if (item == From.VirtualCheck) continue; + + if (!item.AllowSecureTrade(From.Mobile, To.Mobile, To.Mobile, true)) allowed = false; + } + + list = To.Container.Items; + + for (int i = list.Count - 1; allowed && i >= 0; --i) + if (i < list.Count) + { + Item item = list[i]; + + if (item == To.VirtualCheck) continue; + + if (!item.AllowSecureTrade(To.Mobile, From.Mobile, From.Mobile, true)) allowed = false; + } + + if (AccountGold.Enabled) + { + if (From.Mobile.Account != null) + { + int totalPlat = From.Mobile.Account.TotalPlat; + int totalGold = From.Mobile.Account.TotalGold; + + if (totalPlat < From.Plat || totalGold < From.Gold) + { + allowed = false; + From.Mobile.SendMessage("You do not have enough currency to complete this trade."); + } + } + + if (To.Mobile.Account != null) + { + int totalPlat = To.Mobile.Account.TotalPlat; + int totalGold = To.Mobile.Account.TotalGold; + + if (totalPlat < To.Plat || totalGold < To.Gold) + { + allowed = false; + To.Mobile.SendMessage("You do not have enough currency to complete this trade."); + } + } + } + + if (!allowed) + { + From.Accepted = false; + To.Accepted = false; + + From.Mobile.Send(new UpdateSecureTrade(From.Container, From.Accepted, To.Accepted)); + To.Mobile.Send(new UpdateSecureTrade(To.Container, To.Accepted, From.Accepted)); + + return; + } + + if (AccountGold.Enabled && From.Mobile.Account != null && To.Mobile.Account != null) + HandleAccountGoldTrade(); + + list = From.Container.Items; + + for (int i = list.Count - 1; i >= 0; --i) + if (i < list.Count) + { + Item item = list[i]; + + if (item == From.VirtualCheck) continue; + + item.OnSecureTrade(From.Mobile, To.Mobile, To.Mobile, true); + + if (!item.Deleted) To.Mobile.AddToBackpack(item); + } + + list = To.Container.Items; + + for (int i = list.Count - 1; i >= 0; --i) + if (i < list.Count) + { + Item item = list[i]; + + if (item == To.VirtualCheck) continue; + + item.OnSecureTrade(To.Mobile, From.Mobile, From.Mobile, true); + + if (!item.Deleted) From.Mobile.AddToBackpack(item); + } + + Close(); + } + else if (!From.IsDisposed && !To.IsDisposed) + { + From.Mobile.Send(new UpdateSecureTrade(From.Container, From.Accepted, To.Accepted)); + To.Mobile.Send(new UpdateSecureTrade(To.Container, To.Accepted, From.Accepted)); + } + } + + private void HandleAccountGoldTrade() + { + int fromPlatSend = 0, fromGoldSend = 0, fromPlatRecv = 0, fromGoldRecv = 0; + int toPlatSend = 0, toGoldSend = 0, toPlatRecv = 0, toGoldRecv = 0; + + if ((From.Plat > 0) & From.Mobile.Account.WithdrawPlat(From.Plat)) + { + fromPlatSend = From.Plat; + + if (To.Mobile.Account.DepositPlat(From.Plat)) toPlatRecv = fromPlatSend; + } + + if ((From.Gold > 0) & From.Mobile.Account.WithdrawGold(From.Gold)) + { + fromGoldSend = From.Gold; + + if (To.Mobile.Account.DepositGold(From.Gold)) toGoldRecv = fromGoldSend; + } + + if ((To.Plat > 0) & To.Mobile.Account.WithdrawPlat(To.Plat)) + { + toPlatSend = To.Plat; + + if (From.Mobile.Account.DepositPlat(To.Plat)) fromPlatRecv = toPlatSend; + } + + if ((To.Gold > 0) & To.Mobile.Account.WithdrawGold(To.Gold)) + { + toGoldSend = To.Gold; + + if (From.Mobile.Account.DepositGold(To.Gold)) fromGoldRecv = toGoldSend; + } + + HandleAccountGoldTrade(From.Mobile, To.Mobile, fromPlatSend, fromGoldSend, fromPlatRecv, fromGoldRecv); + HandleAccountGoldTrade(To.Mobile, From.Mobile, toPlatSend, toGoldSend, toPlatRecv, toGoldRecv); + } + + private static void HandleAccountGoldTrade( + Mobile left, + Mobile right, + int platSend, + int goldSend, + int platRecv, + int goldRecv) + { + if (platSend > 0 || goldSend > 0) + { + if (platSend > 0 && goldSend > 0) + left.SendMessage("You traded {0:#,0} platinum and {1:#,0} gold to {2}.", platSend, goldSend, + right.RawName); + else if (platSend > 0) + left.SendMessage("You traded {0:#,0} platinum to {1}.", platSend, right.RawName); + else if (goldSend > 0) left.SendMessage("You traded {0:#,0} gold to {1}.", goldSend, right.RawName); + } + + if (platRecv > 0 || goldRecv > 0) + { + if (platRecv > 0 && goldRecv > 0) + left.SendMessage("You received {0:#,0} platinum and {1:#,0} gold from {2}.", platRecv, goldRecv, + right.RawName); + else if (platRecv > 0) + left.SendMessage("You received {0:#,0} platinum from {1}.", platRecv, right.RawName); + else if (goldRecv > 0) left.SendMessage("You received {0:#,0} gold from {1}.", goldRecv, right.RawName); + } + } + } + + public class SecureTradeInfo : IDisposable + { + public SecureTradeInfo(SecureTrade owner, Mobile m, SecureTradeContainer c) + { + Owner = owner; + Mobile = m; + Container = c; + + Mobile.AddItem(Container); + + VirtualCheck = new VirtualCheck(0, 0); + Container.DropItem(VirtualCheck); + } + + public SecureTrade Owner{ get; private set; } + public Mobile Mobile{ get; private set; } + public SecureTradeContainer Container{ get; private set; } + public VirtualCheck VirtualCheck{ get; private set; } + + public int Gold + { + get => VirtualCheck.Gold; + set => VirtualCheck.Gold = value; + } + + public int Plat + { + get => VirtualCheck.Plat; + set => VirtualCheck.Plat = value; + } + + public bool Accepted{ get; set; } + + public bool IsDisposed{ get; private set; } + + public void Dispose() + { + VirtualCheck.Delete(); + VirtualCheck = null; + + Container.Delete(); + Container = null; + + Mobile = null; + Owner = null; + + IsDisposed = true; + } + } +} \ No newline at end of file diff --git a/Server/Serial.cs b/Server/Serial.cs index 87fc3a204..f0a0f9e75 100644 --- a/Server/Serial.cs +++ b/Server/Serial.cs @@ -22,125 +22,129 @@ using System; namespace Server { - public struct Serial : IComparable, IComparable - { - public static Serial LastMobile { get; private set; } = Zero; + public struct Serial : IComparable, IComparable + { + public static readonly Serial MinusOne = new Serial(-1); + public static readonly Serial Zero = new Serial(0); - public static Serial LastItem { get; private set; } = 0x40000000; + public static Serial LastMobile{ get; private set; } = Zero; - public static readonly Serial MinusOne = new Serial( -1 ); - public static readonly Serial Zero = new Serial( 0 ); + public static Serial LastItem{ get; private set; } = 0x40000000; - public static Serial NewMobile - { - get - { - while ( World.FindMobile( LastMobile = (LastMobile + 1) ) != null ); + public static Serial NewMobile + { + get + { + while (World.FindMobile(LastMobile = LastMobile + 1) != null) + { + } - return LastMobile; - } - } + return LastMobile; + } + } - public static Serial NewItem - { - get - { - while ( World.FindItem( LastItem = (LastItem + 1) ) != null ); + public static Serial NewItem + { + get + { + while (World.FindItem(LastItem = LastItem + 1) != null) + { + } - return LastItem; - } - } + return LastItem; + } + } - private Serial( int serial ) - { - Value = serial; - } + private Serial(int serial) + { + Value = serial; + } - public int Value { get; } + public int Value{ get; } - public bool IsMobile => ( Value > 0 && Value < 0x40000000 ); + public bool IsMobile => Value > 0 && Value < 0x40000000; - public bool IsItem => ( Value >= 0x40000000 && Value <= 0x7FFFFFFF ); + public bool IsItem => Value >= 0x40000000 && Value <= 0x7FFFFFFF; - public bool IsValid => ( Value > 0 ); + public bool IsValid => Value > 0; - public override int GetHashCode() - { - return Value; - } + public override int GetHashCode() + { + return Value; + } - public int CompareTo( Serial other ) - { - return Value.CompareTo( other.Value ); - } + public int CompareTo(Serial other) + { + return Value.CompareTo(other.Value); + } - public int CompareTo( object other ) - { - if ( other is Serial serial ) - return CompareTo( serial ); + public int CompareTo(object other) + { + if (other is Serial serial) + return CompareTo(serial); - if ( other == null ) - return -1; + if (other == null) + return -1; - throw new ArgumentException(); - } + throw new ArgumentException(); + } - public override bool Equals( object o ) - { - if ( !(o is Serial serial) ) - return false; + public override bool Equals(object o) + { + if (!(o is Serial serial)) + return false; - return serial.Value == Value; - } + return serial.Value == Value; + } - public static bool operator == ( Serial l, Serial r ) - { - return l.Value == r.Value; - } + public static bool operator ==(Serial l, Serial r) + { + return l.Value == r.Value; + } - public static bool operator != ( Serial l, Serial r ) - { - return l.Value != r.Value; - } + public static bool operator !=(Serial l, Serial r) + { + return l.Value != r.Value; + } - public static bool operator > ( Serial l, Serial r ) - { - return l.Value > r.Value; - } + public static bool operator >(Serial l, Serial r) + { + return l.Value > r.Value; + } - public static bool operator < ( Serial l, Serial r ) - { - return l.Value < r.Value; - } + public static bool operator <(Serial l, Serial r) + { + return l.Value < r.Value; + } - public static bool operator >= ( Serial l, Serial r ) - { - return l.Value >= r.Value; - } + public static bool operator >=(Serial l, Serial r) + { + return l.Value >= r.Value; + } - public static bool operator <= ( Serial l, Serial r ) - { - return l.Value <= r.Value; - } + public static bool operator <=(Serial l, Serial r) + { + return l.Value <= r.Value; + } - /*public static Serial operator ++ ( Serial l ) - { - return new Serial( l + 1 ); - }*/ + /*public static Serial operator ++ ( Serial l ) + { + return new Serial( l + 1 ); + }*/ - public override string ToString() - { - return $"0x{Value:X8}"; - } + public override string ToString() + { + return $"0x{Value:X8}"; + } - public static implicit operator int( Serial a ) - { - return a.Value; - } + public static implicit operator int(Serial a) + { + return a.Value; + } - public static implicit operator Serial( int a ) - { - return new Serial( a ); - } - } -} + public static implicit operator Serial(int a) + { + return new Serial(a); + } + } +} \ No newline at end of file diff --git a/Server/Serialization.cs b/Server/Serialization.cs index 57c2c5acb..69542bfde 100644 --- a/Server/Serialization.cs +++ b/Server/Serialization.cs @@ -19,2057 +19,1954 @@ ***************************************************************************/ using System; -using System.IO; using System.Collections; using System.Collections.Generic; +using System.IO; +using System.Net; using System.Text; using System.Threading; -using System.Net; using Server.Guilds; namespace Server { - public abstract class GenericReader - { - protected GenericReader() { } - - public abstract string ReadString(); - public abstract DateTime ReadDateTime(); - public abstract DateTimeOffset ReadDateTimeOffset(); - public abstract TimeSpan ReadTimeSpan(); - public abstract DateTime ReadDeltaTime(); - public abstract decimal ReadDecimal(); - public abstract long ReadLong(); - public abstract ulong ReadULong(); - public abstract int ReadInt(); - public abstract uint ReadUInt(); - public abstract short ReadShort(); - public abstract ushort ReadUShort(); - public abstract double ReadDouble(); - public abstract float ReadFloat(); - public abstract char ReadChar(); - public abstract byte ReadByte(); - public abstract sbyte ReadSByte(); - public abstract bool ReadBool(); - public abstract int ReadEncodedInt(); - public abstract IPAddress ReadIPAddress(); - - public abstract Point3D ReadPoint3D(); - public abstract Point2D ReadPoint2D(); - public abstract Rectangle2D ReadRect2D(); - public abstract Rectangle3D ReadRect3D(); - public abstract Map ReadMap(); - - public abstract IEntity ReadEntity(); - public abstract Item ReadItem(); - public abstract Mobile ReadMobile(); - public abstract BaseGuild ReadGuild(); - - public abstract T ReadItem() where T : Item; - public abstract T ReadMobile() where T : Mobile; - public abstract T ReadGuild() where T : BaseGuild; - - public abstract ArrayList ReadItemList(); - public abstract ArrayList ReadMobileList(); - public abstract ArrayList ReadGuildList(); - - public abstract List ReadStrongItemList(); - public abstract List ReadStrongItemList() where T : Item; - - public abstract List ReadStrongMobileList(); - public abstract List ReadStrongMobileList() where T : Mobile; - - public abstract List ReadStrongGuildList(); - public abstract List ReadStrongGuildList() where T : BaseGuild; - - public abstract HashSet ReadItemSet(); - public abstract HashSet ReadItemSet() where T: Item; - - public abstract HashSet ReadMobileSet(); - public abstract HashSet ReadMobileSet() where T : Mobile; - - public abstract HashSet ReadGuildSet(); - public abstract HashSet ReadGuildSet() where T : BaseGuild; - - public abstract Race ReadRace(); - - public abstract bool End(); - } - - public abstract class GenericWriter - { - protected GenericWriter() { } + public abstract class GenericReader + { + public abstract string ReadString(); + public abstract DateTime ReadDateTime(); + public abstract DateTimeOffset ReadDateTimeOffset(); + public abstract TimeSpan ReadTimeSpan(); + public abstract DateTime ReadDeltaTime(); + public abstract decimal ReadDecimal(); + public abstract long ReadLong(); + public abstract ulong ReadULong(); + public abstract int ReadInt(); + public abstract uint ReadUInt(); + public abstract short ReadShort(); + public abstract ushort ReadUShort(); + public abstract double ReadDouble(); + public abstract float ReadFloat(); + public abstract char ReadChar(); + public abstract byte ReadByte(); + public abstract sbyte ReadSByte(); + public abstract bool ReadBool(); + public abstract int ReadEncodedInt(); + public abstract IPAddress ReadIPAddress(); + + public abstract Point3D ReadPoint3D(); + public abstract Point2D ReadPoint2D(); + public abstract Rectangle2D ReadRect2D(); + public abstract Rectangle3D ReadRect3D(); + public abstract Map ReadMap(); + + public abstract IEntity ReadEntity(); + public abstract Item ReadItem(); + public abstract Mobile ReadMobile(); + public abstract BaseGuild ReadGuild(); + + public abstract T ReadItem() where T : Item; + public abstract T ReadMobile() where T : Mobile; + public abstract T ReadGuild() where T : BaseGuild; + + public abstract ArrayList ReadItemList(); + public abstract ArrayList ReadMobileList(); + public abstract ArrayList ReadGuildList(); + + public abstract List ReadStrongItemList(); + public abstract List ReadStrongItemList() where T : Item; + + public abstract List ReadStrongMobileList(); + public abstract List ReadStrongMobileList() where T : Mobile; + + public abstract List ReadStrongGuildList(); + public abstract List ReadStrongGuildList() where T : BaseGuild; + + public abstract HashSet ReadItemSet(); + public abstract HashSet ReadItemSet() where T : Item; + + public abstract HashSet ReadMobileSet(); + public abstract HashSet ReadMobileSet() where T : Mobile; + + public abstract HashSet ReadGuildSet(); + public abstract HashSet ReadGuildSet() where T : BaseGuild; + + public abstract Race ReadRace(); + + public abstract bool End(); + } + + public abstract class GenericWriter + { + public abstract long Position{ get; } + + public abstract void Close(); + + public abstract void Write(string value); + public abstract void Write(DateTime value); + public abstract void Write(DateTimeOffset value); + public abstract void Write(TimeSpan value); + public abstract void Write(decimal value); + public abstract void Write(long value); + public abstract void Write(ulong value); + public abstract void Write(int value); + public abstract void Write(uint value); + public abstract void Write(short value); + public abstract void Write(ushort value); + public abstract void Write(double value); + public abstract void Write(float value); + public abstract void Write(char value); + public abstract void Write(byte value); + public abstract void Write(sbyte value); + public abstract void Write(bool value); + public abstract void WriteEncodedInt(int value); + public abstract void Write(IPAddress value); + + public abstract void WriteDeltaTime(DateTime value); + + public abstract void Write(Point3D value); + public abstract void Write(Point2D value); + public abstract void Write(Rectangle2D value); + public abstract void Write(Rectangle3D value); + public abstract void Write(Map value); + + public abstract void WriteEntity(IEntity value); + public abstract void Write(Item value); + public abstract void Write(Mobile value); + public abstract void Write(BaseGuild value); + + public abstract void WriteItem(T value) where T : Item; + public abstract void WriteMobile(T value) where T : Mobile; + public abstract void WriteGuild(T value) where T : BaseGuild; - public abstract void Close(); + public abstract void Write(Race value); - public abstract long Position { get; } + public abstract void WriteItemList(ArrayList list); + public abstract void WriteItemList(ArrayList list, bool tidy); - public abstract void Write( string value ); - public abstract void Write( DateTime value ); - public abstract void Write( DateTimeOffset value ); - public abstract void Write( TimeSpan value ); - public abstract void Write( decimal value ); - public abstract void Write( long value ); - public abstract void Write( ulong value ); - public abstract void Write( int value ); - public abstract void Write( uint value ); - public abstract void Write( short value ); - public abstract void Write( ushort value ); - public abstract void Write( double value ); - public abstract void Write( float value ); - public abstract void Write( char value ); - public abstract void Write( byte value ); - public abstract void Write( sbyte value ); - public abstract void Write( bool value ); - public abstract void WriteEncodedInt( int value ); - public abstract void Write( IPAddress value ); - - public abstract void WriteDeltaTime( DateTime value ); - - public abstract void Write( Point3D value ); - public abstract void Write( Point2D value ); - public abstract void Write( Rectangle2D value ); - public abstract void Write( Rectangle3D value ); - public abstract void Write( Map value ); - - public abstract void WriteEntity( IEntity value ); - public abstract void Write( Item value ); - public abstract void Write( Mobile value ); - public abstract void Write( BaseGuild value ); - - public abstract void WriteItem( T value ) where T : Item; - public abstract void WriteMobile( T value ) where T : Mobile; - public abstract void WriteGuild( T value ) where T : BaseGuild; - - public abstract void Write( Race value ); + public abstract void WriteMobileList(ArrayList list); + public abstract void WriteMobileList(ArrayList list, bool tidy); - public abstract void WriteItemList( ArrayList list ); - public abstract void WriteItemList( ArrayList list, bool tidy ); + public abstract void WriteGuildList(ArrayList list); + public abstract void WriteGuildList(ArrayList list, bool tidy); - public abstract void WriteMobileList( ArrayList list ); - public abstract void WriteMobileList( ArrayList list, bool tidy ); + public abstract void Write(List list); + public abstract void Write(List list, bool tidy); - public abstract void WriteGuildList( ArrayList list ); - public abstract void WriteGuildList( ArrayList list, bool tidy ); + public abstract void WriteItemList(List list) where T : Item; + public abstract void WriteItemList(List list, bool tidy) where T : Item; - public abstract void Write( List list ); - public abstract void Write( List list, bool tidy ); + public abstract void Write(HashSet list); + public abstract void Write(HashSet list, bool tidy); - public abstract void WriteItemList( List list ) where T : Item; - public abstract void WriteItemList( List list, bool tidy ) where T : Item; + public abstract void WriteItemSet(HashSet set) where T : Item; + public abstract void WriteItemSet(HashSet set, bool tidy) where T : Item; - public abstract void Write( HashSet list ); - public abstract void Write( HashSet list, bool tidy ); + public abstract void Write(List list); + public abstract void Write(List list, bool tidy); - public abstract void WriteItemSet( HashSet set ) where T : Item; - public abstract void WriteItemSet( HashSet set, bool tidy ) where T : Item; + public abstract void WriteMobileList(List list) where T : Mobile; + public abstract void WriteMobileList(List list, bool tidy) where T : Mobile; - public abstract void Write( List list ); - public abstract void Write( List list, bool tidy ); + public abstract void Write(HashSet list); + public abstract void Write(HashSet list, bool tidy); - public abstract void WriteMobileList( List list ) where T : Mobile; - public abstract void WriteMobileList( List list, bool tidy ) where T : Mobile; + public abstract void WriteMobileSet(HashSet set) where T : Mobile; + public abstract void WriteMobileSet(HashSet set, bool tidy) where T : Mobile; - public abstract void Write( HashSet list ); - public abstract void Write( HashSet list, bool tidy ); + public abstract void Write(List list); + public abstract void Write(List list, bool tidy); - public abstract void WriteMobileSet( HashSet set ) where T : Mobile; - public abstract void WriteMobileSet( HashSet set, bool tidy ) where T : Mobile; + public abstract void WriteGuildList(List list) where T : BaseGuild; + public abstract void WriteGuildList(List list, bool tidy) where T : BaseGuild; - public abstract void Write( List list ); - public abstract void Write( List list, bool tidy ); + public abstract void Write(HashSet list); + public abstract void Write(HashSet list, bool tidy); - public abstract void WriteGuildList( List list ) where T : BaseGuild; - public abstract void WriteGuildList( List list, bool tidy ) where T : BaseGuild; + public abstract void WriteGuildSet(HashSet set) where T : BaseGuild; + public abstract void WriteGuildSet(HashSet set, bool tidy) where T : BaseGuild; - public abstract void Write( HashSet list ); - public abstract void Write( HashSet list, bool tidy ); + // Compiler won't notice there 'where' to differentiate the generic methods. + } - public abstract void WriteGuildSet( HashSet set ) where T : BaseGuild; - public abstract void WriteGuildSet( HashSet set, bool tidy ) where T : BaseGuild; + public class BinaryFileWriter : GenericWriter + { + private const int LargeByteBufferSize = 256; - // Compiler won't notice there 'where' to differentiate the generic methods. - } + private byte[] m_Buffer; - public class BinaryFileWriter : GenericWriter - { - private bool PrefixStrings; - private Stream m_File; + private byte[] m_CharacterBuffer; - protected virtual int BufferSize => 64 * 1024; + private Encoding m_Encoding; + private Stream m_File; - private byte[] m_Buffer; + private int m_Index; + private int m_MaxBufferChars; - private int m_Index; + private long m_Position; - private Encoding m_Encoding; + private char[] m_SingleCharBuffer = new char[1]; + private bool PrefixStrings; - public BinaryFileWriter( Stream strm, bool prefixStr ) - { - PrefixStrings = prefixStr; - m_Encoding = Utility.UTF8; - m_Buffer = new byte[BufferSize]; - m_File = strm; - } + public BinaryFileWriter(Stream strm, bool prefixStr) + { + PrefixStrings = prefixStr; + m_Encoding = Utility.UTF8; + m_Buffer = new byte[BufferSize]; + m_File = strm; + } - public BinaryFileWriter( string filename, bool prefixStr ) - { - PrefixStrings = prefixStr; - m_Buffer = new byte[BufferSize]; - m_File = new FileStream( filename, FileMode.Create, FileAccess.Write, FileShare.None ); - m_Encoding = Utility.UTF8WithEncoding; - } + public BinaryFileWriter(string filename, bool prefixStr) + { + PrefixStrings = prefixStr; + m_Buffer = new byte[BufferSize]; + m_File = new FileStream(filename, FileMode.Create, FileAccess.Write, FileShare.None); + m_Encoding = Utility.UTF8WithEncoding; + } - public void Flush() - { - if ( m_Index > 0 ) - { - m_Position += m_Index; + protected virtual int BufferSize => 64 * 1024; - m_File.Write( m_Buffer, 0, m_Index ); - m_Index = 0; - } - } + public override long Position => m_Position + m_Index; - private long m_Position; + public Stream UnderlyingStream + { + get + { + if (m_Index > 0) + Flush(); - public override long Position => m_Position + m_Index; + return m_File; + } + } - public Stream UnderlyingStream - { - get - { - if ( m_Index > 0 ) - Flush(); + public void Flush() + { + if (m_Index > 0) + { + m_Position += m_Index; - return m_File; - } - } + m_File.Write(m_Buffer, 0, m_Index); + m_Index = 0; + } + } - public override void Close() - { - if ( m_Index > 0 ) - Flush(); - - m_File.Close(); - } - - public override void WriteEncodedInt( int value ) - { - uint v = (uint)value; - - while( v >= 0x80 ) - { - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = (byte)(v | 0x80); - v >>= 7; - } - - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = (byte)v; - } - - private byte[] m_CharacterBuffer; - private int m_MaxBufferChars; - private const int LargeByteBufferSize = 256; - - internal void InternalWriteString( string value ) - { - int length = m_Encoding.GetByteCount( value ); - - WriteEncodedInt( length ); - - if ( m_CharacterBuffer == null ) - { - m_CharacterBuffer = new byte[LargeByteBufferSize]; - m_MaxBufferChars = LargeByteBufferSize / m_Encoding.GetMaxByteCount( 1 ); - } - - if ( length > LargeByteBufferSize ) - { - int current = 0; - int charsLeft = value.Length; - - while( charsLeft > 0 ) - { - int charCount = (charsLeft > m_MaxBufferChars) ? m_MaxBufferChars : charsLeft; - int byteLength = m_Encoding.GetBytes( value, current, charCount, m_CharacterBuffer, 0 ); - - if ( (m_Index + byteLength) > m_Buffer.Length ) - Flush(); - - Buffer.BlockCopy( m_CharacterBuffer, 0, m_Buffer, m_Index, byteLength ); - m_Index += byteLength; - - current += charCount; - charsLeft -= charCount; - } - } - else - { - int byteLength = m_Encoding.GetBytes( value, 0, value.Length, m_CharacterBuffer, 0 ); - - if ( (m_Index + byteLength) > m_Buffer.Length ) - Flush(); - - Buffer.BlockCopy( m_CharacterBuffer, 0, m_Buffer, m_Index, byteLength ); - m_Index += byteLength; - } - } - - public override void Write( string value ) - { - if ( PrefixStrings ) - { - if ( value == null ) - { - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = 0; - } - else - { - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = 1; - - InternalWriteString( value ); - } - } - else - { - InternalWriteString( value ); - } - } - - public override void Write( DateTime value ) - { - Write( value.Ticks ); - } - - public override void Write( DateTimeOffset value ) - { - Write( value.Ticks ); - Write( value.Offset.Ticks ); - } - - public override void WriteDeltaTime( DateTime value ) - { - long ticks = value.Ticks; - long now = DateTime.UtcNow.Ticks; - - TimeSpan d; - - try { d = new TimeSpan( ticks-now ); } - catch { if ( ticks < now ) d = TimeSpan.MaxValue; else d = TimeSpan.MaxValue; } - - Write( d ); - } - - public override void Write( IPAddress value ) - { - Write( Utility.GetLongAddressValue( value ) ); - } - - public override void Write( TimeSpan value ) - { - Write( value.Ticks ); - } - - public override void Write( decimal value ) - { - int[] bits = decimal.GetBits( value ); - - for( int i = 0; i < bits.Length; ++i ) - Write( bits[i] ); - } - - public override void Write( long value ) - { - if ( (m_Index + 8) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index] = (byte)value; - m_Buffer[m_Index + 1] = (byte)(value >> 8); - m_Buffer[m_Index + 2] = (byte)(value >> 16); - m_Buffer[m_Index + 3] = (byte)(value >> 24); - m_Buffer[m_Index + 4] = (byte)(value >> 32); - m_Buffer[m_Index + 5] = (byte)(value >> 40); - m_Buffer[m_Index + 6] = (byte)(value >> 48); - m_Buffer[m_Index + 7] = (byte)(value >> 56); - m_Index += 8; - } - - public override void Write( ulong value ) - { - if ( (m_Index + 8) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index] = (byte)value; - m_Buffer[m_Index + 1] = (byte)(value >> 8); - m_Buffer[m_Index + 2] = (byte)(value >> 16); - m_Buffer[m_Index + 3] = (byte)(value >> 24); - m_Buffer[m_Index + 4] = (byte)(value >> 32); - m_Buffer[m_Index + 5] = (byte)(value >> 40); - m_Buffer[m_Index + 6] = (byte)(value >> 48); - m_Buffer[m_Index + 7] = (byte)(value >> 56); - m_Index += 8; - } - - public override void Write( int value ) - { - if ( (m_Index + 4) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index] = (byte)value; - m_Buffer[m_Index + 1] = (byte)(value >> 8); - m_Buffer[m_Index + 2] = (byte)(value >> 16); - m_Buffer[m_Index + 3] = (byte)(value >> 24); - m_Index += 4; - } - - public override void Write( uint value ) - { - if ( (m_Index + 4) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index] = (byte)value; - m_Buffer[m_Index + 1] = (byte)(value >> 8); - m_Buffer[m_Index + 2] = (byte)(value >> 16); - m_Buffer[m_Index + 3] = (byte)(value >> 24); - m_Index += 4; - } - - public override void Write( short value ) - { - if ( (m_Index + 2) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index] = (byte)value; - m_Buffer[m_Index + 1] = (byte)(value >> 8); - m_Index += 2; - } - - public override void Write( ushort value ) - { - if ( (m_Index + 2) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index] = (byte)value; - m_Buffer[m_Index + 1] = (byte)(value >> 8); - m_Index += 2; - } - - public unsafe override void Write( double value ) - { - if ( (m_Index + 8) > m_Buffer.Length ) - Flush(); + public override void Close() + { + if (m_Index > 0) + Flush(); + + m_File.Close(); + } + + public override void WriteEncodedInt(int value) + { + uint v = (uint)value; + + while (v >= 0x80) + { + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = (byte)(v | 0x80); + v >>= 7; + } + + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = (byte)v; + } + + internal void InternalWriteString(string value) + { + int length = m_Encoding.GetByteCount(value); + + WriteEncodedInt(length); + + if (m_CharacterBuffer == null) + { + m_CharacterBuffer = new byte[LargeByteBufferSize]; + m_MaxBufferChars = LargeByteBufferSize / m_Encoding.GetMaxByteCount(1); + } + + if (length > LargeByteBufferSize) + { + int current = 0; + int charsLeft = value.Length; + + while (charsLeft > 0) + { + int charCount = charsLeft > m_MaxBufferChars ? m_MaxBufferChars : charsLeft; + int byteLength = m_Encoding.GetBytes(value, current, charCount, m_CharacterBuffer, 0); + + if (m_Index + byteLength > m_Buffer.Length) + Flush(); + + Buffer.BlockCopy(m_CharacterBuffer, 0, m_Buffer, m_Index, byteLength); + m_Index += byteLength; + + current += charCount; + charsLeft -= charCount; + } + } + else + { + int byteLength = m_Encoding.GetBytes(value, 0, value.Length, m_CharacterBuffer, 0); + + if (m_Index + byteLength > m_Buffer.Length) + Flush(); + + Buffer.BlockCopy(m_CharacterBuffer, 0, m_Buffer, m_Index, byteLength); + m_Index += byteLength; + } + } + + public override void Write(string value) + { + if (PrefixStrings) + { + if (value == null) + { + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = 0; + } + else + { + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = 1; + + InternalWriteString(value); + } + } + else + { + InternalWriteString(value); + } + } + + public override void Write(DateTime value) + { + Write(value.Ticks); + } + + public override void Write(DateTimeOffset value) + { + Write(value.Ticks); + Write(value.Offset.Ticks); + } + + public override void WriteDeltaTime(DateTime value) + { + long ticks = value.Ticks; + long now = DateTime.UtcNow.Ticks; + + TimeSpan d; + + try + { + d = new TimeSpan(ticks - now); + } + catch + { + if (ticks < now) d = TimeSpan.MaxValue; + else d = TimeSpan.MaxValue; + } + + Write(d); + } + + public override void Write(IPAddress value) + { + Write(Utility.GetLongAddressValue(value)); + } + + public override void Write(TimeSpan value) + { + Write(value.Ticks); + } + + public override void Write(decimal value) + { + int[] bits = decimal.GetBits(value); + + for (int i = 0; i < bits.Length; ++i) + Write(bits[i]); + } + + public override void Write(long value) + { + if (m_Index + 8 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index] = (byte)value; + m_Buffer[m_Index + 1] = (byte)(value >> 8); + m_Buffer[m_Index + 2] = (byte)(value >> 16); + m_Buffer[m_Index + 3] = (byte)(value >> 24); + m_Buffer[m_Index + 4] = (byte)(value >> 32); + m_Buffer[m_Index + 5] = (byte)(value >> 40); + m_Buffer[m_Index + 6] = (byte)(value >> 48); + m_Buffer[m_Index + 7] = (byte)(value >> 56); + m_Index += 8; + } + + public override void Write(ulong value) + { + if (m_Index + 8 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index] = (byte)value; + m_Buffer[m_Index + 1] = (byte)(value >> 8); + m_Buffer[m_Index + 2] = (byte)(value >> 16); + m_Buffer[m_Index + 3] = (byte)(value >> 24); + m_Buffer[m_Index + 4] = (byte)(value >> 32); + m_Buffer[m_Index + 5] = (byte)(value >> 40); + m_Buffer[m_Index + 6] = (byte)(value >> 48); + m_Buffer[m_Index + 7] = (byte)(value >> 56); + m_Index += 8; + } + + public override void Write(int value) + { + if (m_Index + 4 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index] = (byte)value; + m_Buffer[m_Index + 1] = (byte)(value >> 8); + m_Buffer[m_Index + 2] = (byte)(value >> 16); + m_Buffer[m_Index + 3] = (byte)(value >> 24); + m_Index += 4; + } + + public override void Write(uint value) + { + if (m_Index + 4 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index] = (byte)value; + m_Buffer[m_Index + 1] = (byte)(value >> 8); + m_Buffer[m_Index + 2] = (byte)(value >> 16); + m_Buffer[m_Index + 3] = (byte)(value >> 24); + m_Index += 4; + } + + public override void Write(short value) + { + if (m_Index + 2 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index] = (byte)value; + m_Buffer[m_Index + 1] = (byte)(value >> 8); + m_Index += 2; + } + + public override void Write(ushort value) + { + if (m_Index + 2 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index] = (byte)value; + m_Buffer[m_Index + 1] = (byte)(value >> 8); + m_Index += 2; + } + + public override unsafe void Write(double value) + { + if (m_Index + 8 > m_Buffer.Length) + Flush(); #if MONO byte[] bytes = BitConverter.GetBytes(value); for(int i = 0; i < bytes.Length; i++) m_Buffer[m_Index++] = bytes[i]; #else - fixed( byte* pBuffer = m_Buffer ) - *((double*)(pBuffer + m_Index)) = value; + fixed (byte* pBuffer = m_Buffer) + { + *(double*)(pBuffer + m_Index) = value; + } - m_Index += 8; + m_Index += 8; #endif - } + } - public unsafe override void Write( float value ) - { - if ( (m_Index + 4) > m_Buffer.Length ) - Flush(); + public override unsafe void Write(float value) + { + if (m_Index + 4 > m_Buffer.Length) + Flush(); #if MONO byte[] bytes = BitConverter.GetBytes(value); for(int i = 0; i < bytes.Length; i++) m_Buffer[m_Index++] = bytes[i]; #else - fixed ( byte* pBuffer = m_Buffer ) - *((float*)(pBuffer + m_Index)) = value; + fixed (byte* pBuffer = m_Buffer) + { + *(float*)(pBuffer + m_Index) = value; + } - m_Index += 4; + m_Index += 4; #endif - } - - private char[] m_SingleCharBuffer = new char[1]; - - public override void Write( char value ) - { - if ( (m_Index + 8) > m_Buffer.Length ) - Flush(); - - m_SingleCharBuffer[0] = value; - - int byteCount = m_Encoding.GetBytes( m_SingleCharBuffer, 0, 1, m_Buffer, m_Index ); - m_Index += byteCount; - } - - public override void Write( byte value ) - { - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = value; - } - - public override void Write( sbyte value ) - { - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = (byte)value; - } - - public override void Write( bool value ) - { - if ( (m_Index + 1) > m_Buffer.Length ) - Flush(); - - m_Buffer[m_Index++] = (byte)(value ? 1 : 0); - } - - public override void Write( Point3D value ) - { - Write( value.m_X ); - Write( value.m_Y ); - Write( value.m_Z ); - } - - public override void Write( Point2D value ) - { - Write( value.m_X ); - Write( value.m_Y ); - } - - public override void Write( Rectangle2D value ) - { - Write( value.Start ); - Write( value.End ); - } - - public override void Write( Rectangle3D value ) - { - Write( value.Start ); - Write( value.End ); - } - - public override void Write( Map value ) - { - if ( value != null ) - Write( (byte)value.MapIndex ); - else - Write( (byte)0xFF ); - } - - public override void Write( Race value ) - { - if ( value != null ) - Write( (byte)value.RaceIndex ); - else - Write( (byte)0xFF ); - } - - public override void WriteEntity( IEntity value ) - { - if ( value == null || value.Deleted ) - Write( Serial.MinusOne ); - else - Write( value.Serial ); - } - - public override void Write( Item value ) - { - if ( value == null || value.Deleted ) - Write( Serial.MinusOne ); - else - Write( value.Serial ); - } - - public override void Write( Mobile value ) - { - if ( value == null || value.Deleted ) - Write( Serial.MinusOne ); - else - Write( value.Serial ); - } - - public override void Write( BaseGuild value ) - { - if ( value == null ) - Write( 0 ); - else - Write( value.Id ); - } - - public override void WriteItem( T value ) - { - Write( value ); - } - - public override void WriteMobile( T value ) - { - Write( value ); - } - - public override void WriteGuild( T value ) - { - Write( value ); - } - - public override void WriteMobileList( ArrayList list ) - { - WriteMobileList( list, false ); - } - public override void WriteMobileList( ArrayList list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( ((Mobile)list[i]).Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( (Mobile)list[i] ); - } - - public override void WriteItemList( ArrayList list ) - { - WriteItemList( list, false ); - } - public override void WriteItemList( ArrayList list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( ((Item)list[i]).Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( (Item)list[i] ); - } - - public override void WriteGuildList( ArrayList list ) - { - WriteGuildList( list, false ); - } - public override void WriteGuildList( ArrayList list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( ((BaseGuild)list[i]).Disbanded ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( (BaseGuild)list[i] ); - } - - public override void Write( List list ) - { - Write( list, false ); - } - public override void Write( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void WriteItemList( List list ) - { - WriteItemList( list, false ); - } - public override void WriteItemList( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void Write( HashSet set ) - { - Write( set, false ); - } - public override void Write( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( item => item.Deleted ); - } - - Write( set.Count ); - - foreach( Item item in set ) - { - Write( item ); - } - } - - public override void WriteItemSet( HashSet set ) - { - WriteItemSet( set, false ); - } - public override void WriteItemSet( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( item => item.Deleted ); - } - - Write( set.Count ); - - foreach( Item item in set ) - { - Write( item ); - } - } - - public override void Write( List list ) - { - Write( list, false ); - } - public override void Write( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void WriteMobileList( List list ) - { - WriteMobileList( list, false ); - } - public override void WriteMobileList( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void Write( HashSet set ) - { - Write( set, false ); - } - public override void Write( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( mobile => mobile.Deleted ); - } - - Write( set.Count ); - - foreach( Mobile mob in set ) - { - Write( mob ); - } - } - - public override void WriteMobileSet( HashSet set ) - { - WriteMobileSet( set, false ); - } - public override void WriteMobileSet( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( mob => mob.Deleted ); - } - - Write( set.Count ); - - foreach( Mobile mob in set ) - { - Write( mob ); - } - } - - public override void Write( List list ) - { - Write( list, false ); - } - public override void Write( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Disbanded ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void WriteGuildList( List list ) - { - WriteGuildList( list, false ); - } - public override void WriteGuildList( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Disbanded ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void Write( HashSet set ) - { - Write( set, false ); - } - public override void Write( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( guild => guild.Disbanded ); - } - - Write( set.Count ); - - foreach( BaseGuild guild in set ) - { - Write( guild ); - } - } - - public override void WriteGuildSet( HashSet set ) - { - WriteGuildSet( set, false ); - } - public override void WriteGuildSet( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( guild => guild.Disbanded ); - } - - Write( set.Count ); - - foreach( BaseGuild guild in set ) - { - Write( guild ); - } - } - } - - public sealed class BinaryFileReader : GenericReader - { - private BinaryReader m_File; - - public BinaryFileReader( BinaryReader br ) { m_File = br; } - - public void Close() - { - m_File.Close(); - } - - public long Position => m_File.BaseStream.Position; - - public long Seek( long offset, SeekOrigin origin ) - { - return m_File.BaseStream.Seek( offset, origin ); - } - - public override string ReadString() - { - if ( ReadByte() != 0 ) - return m_File.ReadString(); - return null; - } - - public override DateTime ReadDeltaTime() - { - long ticks = m_File.ReadInt64(); - long now = DateTime.UtcNow.Ticks; - - if ( ticks > 0 && (ticks+now) < 0 ) - return DateTime.MaxValue; - if ( ticks < 0 && (ticks+now) < 0 ) - return DateTime.MinValue; - - try { return new DateTime( now+ticks ); } - catch - { - if ( ticks > 0 ) return DateTime.MaxValue; - return DateTime.MinValue; - } - } - - public override IPAddress ReadIPAddress() - { - return new IPAddress( m_File.ReadInt64() ); - } - - public override int ReadEncodedInt() - { - int v = 0, shift = 0; - byte b; - - do - { - b = m_File.ReadByte(); - v |= (b & 0x7F) << shift; - shift += 7; - } while( b >= 0x80 ); - - return v; - } - - public override DateTime ReadDateTime() - { - return new DateTime( m_File.ReadInt64() ); - } - - public override DateTimeOffset ReadDateTimeOffset() - { - long ticks = m_File.ReadInt64(); - TimeSpan offset = new TimeSpan( m_File.ReadInt64() ); - - return new DateTimeOffset( ticks, offset ); - } - - public override TimeSpan ReadTimeSpan() - { - return new TimeSpan( m_File.ReadInt64() ); - } - - public override decimal ReadDecimal() - { - return m_File.ReadDecimal(); - } - - public override long ReadLong() - { - return m_File.ReadInt64(); - } - - public override ulong ReadULong() - { - return m_File.ReadUInt64(); - } - - public override int ReadInt() - { - return m_File.ReadInt32(); - } - - public override uint ReadUInt() - { - return m_File.ReadUInt32(); - } - - public override short ReadShort() - { - return m_File.ReadInt16(); - } - - public override ushort ReadUShort() - { - return m_File.ReadUInt16(); - } - - public override double ReadDouble() - { - return m_File.ReadDouble(); - } - - public override float ReadFloat() - { - return m_File.ReadSingle(); - } - - public override char ReadChar() - { - return m_File.ReadChar(); - } - - public override byte ReadByte() - { - return m_File.ReadByte(); - } - - public override sbyte ReadSByte() - { - return m_File.ReadSByte(); - } - - public override bool ReadBool() - { - return m_File.ReadBoolean(); - } - - public override Point3D ReadPoint3D() - { - return new Point3D( ReadInt(), ReadInt(), ReadInt() ); - } - - public override Point2D ReadPoint2D() - { - return new Point2D( ReadInt(), ReadInt() ); - } - - public override Rectangle2D ReadRect2D() - { - return new Rectangle2D( ReadPoint2D(), ReadPoint2D() ); - } - - public override Rectangle3D ReadRect3D() - { - return new Rectangle3D( ReadPoint3D(), ReadPoint3D() ); - } - - public override Map ReadMap() - { - return Map.Maps[ReadByte()]; - } - - public override IEntity ReadEntity() - { - Serial serial = ReadInt(); - IEntity entity = World.FindEntity( serial ); - if ( entity == null ) - return new Entity( serial, new Point3D( 0, 0, 0 ), Map.Internal ); - return entity; - } - - public override Item ReadItem() - { - return World.FindItem( ReadInt() ); - } - - public override Mobile ReadMobile() - { - return World.FindMobile( ReadInt() ); - } - - public override BaseGuild ReadGuild() - { - return BaseGuild.Find( ReadInt() ); - } - - public override T ReadItem() - { - return ReadItem() as T; - } - - public override T ReadMobile() - { - return ReadMobile() as T; - } - - public override T ReadGuild() - { - return ReadGuild() as T; - } - - public override ArrayList ReadItemList() - { - int count = ReadInt(); - - if ( count > 0 ) { - ArrayList list = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) { - Item item = ReadItem(); - - if ( item != null ) { - list.Add( item ); - } - } - - return list; - } - - return new ArrayList(); - } - - public override ArrayList ReadMobileList() - { - int count = ReadInt(); - - if ( count > 0 ) { - ArrayList list = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) { - Mobile m = ReadMobile(); - - if ( m != null ) { - list.Add( m ); - } - } - - return list; - } - - return new ArrayList(); - } - - public override ArrayList ReadGuildList() - { - int count = ReadInt(); - - if ( count > 0 ) { - ArrayList list = new ArrayList( count ); - - for ( int i = 0; i < count; ++i ) { - BaseGuild g = ReadGuild(); - - if ( g != null ) { - list.Add( g ); - } - } - - return list; - } - - return new ArrayList(); - } - - public override List ReadStrongItemList() - { - return ReadStrongItemList(); - } - - public override List ReadStrongItemList() - { - int count = ReadInt(); - - if ( count > 0 ) { - List list = new List( count ); - - for ( int i = 0; i < count; ++i ) { - if ( ReadItem() is T item ) { - list.Add( item ); - } - } - - return list; - } - return new List(); - } - - public override HashSet ReadItemSet() - { - return ReadItemSet(); - } - - public override HashSet ReadItemSet() - { - int count = ReadInt(); + } + + public override void Write(char value) + { + if (m_Index + 8 > m_Buffer.Length) + Flush(); + + m_SingleCharBuffer[0] = value; + + int byteCount = m_Encoding.GetBytes(m_SingleCharBuffer, 0, 1, m_Buffer, m_Index); + m_Index += byteCount; + } + + public override void Write(byte value) + { + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = value; + } + + public override void Write(sbyte value) + { + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = (byte)value; + } + + public override void Write(bool value) + { + if (m_Index + 1 > m_Buffer.Length) + Flush(); + + m_Buffer[m_Index++] = (byte)(value ? 1 : 0); + } + + public override void Write(Point3D value) + { + Write(value.m_X); + Write(value.m_Y); + Write(value.m_Z); + } + + public override void Write(Point2D value) + { + Write(value.m_X); + Write(value.m_Y); + } + + public override void Write(Rectangle2D value) + { + Write(value.Start); + Write(value.End); + } + + public override void Write(Rectangle3D value) + { + Write(value.Start); + Write(value.End); + } + + public override void Write(Map value) + { + if (value != null) + Write((byte)value.MapIndex); + else + Write((byte)0xFF); + } + + public override void Write(Race value) + { + if (value != null) + Write((byte)value.RaceIndex); + else + Write((byte)0xFF); + } + + public override void WriteEntity(IEntity value) + { + if (value == null || value.Deleted) + Write(Serial.MinusOne); + else + Write(value.Serial); + } + + public override void Write(Item value) + { + if (value == null || value.Deleted) + Write(Serial.MinusOne); + else + Write(value.Serial); + } + + public override void Write(Mobile value) + { + if (value == null || value.Deleted) + Write(Serial.MinusOne); + else + Write(value.Serial); + } + + public override void Write(BaseGuild value) + { + if (value == null) + Write(0); + else + Write(value.Id); + } + + public override void WriteItem(T value) + { + Write(value); + } + + public override void WriteMobile(T value) + { + Write(value); + } + + public override void WriteGuild(T value) + { + Write(value); + } + + public override void WriteMobileList(ArrayList list) + { + WriteMobileList(list, false); + } + + public override void WriteMobileList(ArrayList list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (((Mobile)list[i]).Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write((Mobile)list[i]); + } + + public override void WriteItemList(ArrayList list) + { + WriteItemList(list, false); + } + + public override void WriteItemList(ArrayList list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (((Item)list[i]).Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write((Item)list[i]); + } + + public override void WriteGuildList(ArrayList list) + { + WriteGuildList(list, false); + } + + public override void WriteGuildList(ArrayList list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (((BaseGuild)list[i]).Disbanded) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write((BaseGuild)list[i]); + } + + public override void Write(List list) + { + Write(list, false); + } + + public override void Write(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void WriteItemList(List list) + { + WriteItemList(list, false); + } + + public override void WriteItemList(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void Write(HashSet set) + { + Write(set, false); + } + + public override void Write(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(item => item.Deleted); + + Write(set.Count); + + foreach (Item item in set) Write(item); + } + + public override void WriteItemSet(HashSet set) + { + WriteItemSet(set, false); + } + + public override void WriteItemSet(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(item => item.Deleted); + + Write(set.Count); + + foreach (Item item in set) Write(item); + } + + public override void Write(List list) + { + Write(list, false); + } + + public override void Write(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void WriteMobileList(List list) + { + WriteMobileList(list, false); + } + + public override void WriteMobileList(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void Write(HashSet set) + { + Write(set, false); + } + + public override void Write(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(mobile => mobile.Deleted); + + Write(set.Count); + + foreach (Mobile mob in set) Write(mob); + } + + public override void WriteMobileSet(HashSet set) + { + WriteMobileSet(set, false); + } + + public override void WriteMobileSet(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(mob => mob.Deleted); + + Write(set.Count); + + foreach (Mobile mob in set) Write(mob); + } + + public override void Write(List list) + { + Write(list, false); + } + + public override void Write(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Disbanded) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void WriteGuildList(List list) + { + WriteGuildList(list, false); + } + + public override void WriteGuildList(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Disbanded) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void Write(HashSet set) + { + Write(set, false); + } + + public override void Write(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(guild => guild.Disbanded); + + Write(set.Count); + + foreach (BaseGuild guild in set) Write(guild); + } + + public override void WriteGuildSet(HashSet set) + { + WriteGuildSet(set, false); + } + + public override void WriteGuildSet(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(guild => guild.Disbanded); + + Write(set.Count); + + foreach (BaseGuild guild in set) Write(guild); + } + } + + public sealed class BinaryFileReader : GenericReader + { + private BinaryReader m_File; + + public BinaryFileReader(BinaryReader br) + { + m_File = br; + } + + public long Position => m_File.BaseStream.Position; + + public void Close() + { + m_File.Close(); + } + + public long Seek(long offset, SeekOrigin origin) + { + return m_File.BaseStream.Seek(offset, origin); + } + + public override string ReadString() + { + if (ReadByte() != 0) + return m_File.ReadString(); + return null; + } + + public override DateTime ReadDeltaTime() + { + long ticks = m_File.ReadInt64(); + long now = DateTime.UtcNow.Ticks; + + if (ticks > 0 && ticks + now < 0) + return DateTime.MaxValue; + if (ticks < 0 && ticks + now < 0) + return DateTime.MinValue; + + try + { + return new DateTime(now + ticks); + } + catch + { + if (ticks > 0) return DateTime.MaxValue; + return DateTime.MinValue; + } + } + + public override IPAddress ReadIPAddress() + { + return new IPAddress(m_File.ReadInt64()); + } + + public override int ReadEncodedInt() + { + int v = 0, shift = 0; + byte b; + + do + { + b = m_File.ReadByte(); + v |= (b & 0x7F) << shift; + shift += 7; + } while (b >= 0x80); + + return v; + } + + public override DateTime ReadDateTime() + { + return new DateTime(m_File.ReadInt64()); + } + + public override DateTimeOffset ReadDateTimeOffset() + { + long ticks = m_File.ReadInt64(); + TimeSpan offset = new TimeSpan(m_File.ReadInt64()); + + return new DateTimeOffset(ticks, offset); + } + + public override TimeSpan ReadTimeSpan() + { + return new TimeSpan(m_File.ReadInt64()); + } + + public override decimal ReadDecimal() + { + return m_File.ReadDecimal(); + } + + public override long ReadLong() + { + return m_File.ReadInt64(); + } + + public override ulong ReadULong() + { + return m_File.ReadUInt64(); + } + + public override int ReadInt() + { + return m_File.ReadInt32(); + } + + public override uint ReadUInt() + { + return m_File.ReadUInt32(); + } + + public override short ReadShort() + { + return m_File.ReadInt16(); + } + + public override ushort ReadUShort() + { + return m_File.ReadUInt16(); + } + + public override double ReadDouble() + { + return m_File.ReadDouble(); + } + + public override float ReadFloat() + { + return m_File.ReadSingle(); + } + + public override char ReadChar() + { + return m_File.ReadChar(); + } + + public override byte ReadByte() + { + return m_File.ReadByte(); + } + + public override sbyte ReadSByte() + { + return m_File.ReadSByte(); + } + + public override bool ReadBool() + { + return m_File.ReadBoolean(); + } + + public override Point3D ReadPoint3D() + { + return new Point3D(ReadInt(), ReadInt(), ReadInt()); + } + + public override Point2D ReadPoint2D() + { + return new Point2D(ReadInt(), ReadInt()); + } + + public override Rectangle2D ReadRect2D() + { + return new Rectangle2D(ReadPoint2D(), ReadPoint2D()); + } + + public override Rectangle3D ReadRect3D() + { + return new Rectangle3D(ReadPoint3D(), ReadPoint3D()); + } + + public override Map ReadMap() + { + return Map.Maps[ReadByte()]; + } + + public override IEntity ReadEntity() + { + Serial serial = ReadInt(); + IEntity entity = World.FindEntity(serial); + if (entity == null) + return new Entity(serial, new Point3D(0, 0, 0), Map.Internal); + return entity; + } + + public override Item ReadItem() + { + return World.FindItem(ReadInt()); + } + + public override Mobile ReadMobile() + { + return World.FindMobile(ReadInt()); + } + + public override BaseGuild ReadGuild() + { + return BaseGuild.Find(ReadInt()); + } + + public override T ReadItem() + { + return ReadItem() as T; + } + + public override T ReadMobile() + { + return ReadMobile() as T; + } + + public override T ReadGuild() + { + return ReadGuild() as T; + } + + public override ArrayList ReadItemList() + { + int count = ReadInt(); + + if (count > 0) + { + ArrayList list = new ArrayList(count); + + for (int i = 0; i < count; ++i) + { + Item item = ReadItem(); + + if (item != null) list.Add(item); + } + + return list; + } + + return new ArrayList(); + } + + public override ArrayList ReadMobileList() + { + int count = ReadInt(); + + if (count > 0) + { + ArrayList list = new ArrayList(count); + + for (int i = 0; i < count; ++i) + { + Mobile m = ReadMobile(); + + if (m != null) list.Add(m); + } + + return list; + } + + return new ArrayList(); + } + + public override ArrayList ReadGuildList() + { + int count = ReadInt(); - if ( count > 0 ) - { - HashSet set = new HashSet(); + if (count > 0) + { + ArrayList list = new ArrayList(count); - for( int i = 0; i < count; ++i ) - { - if ( ReadItem() is T item ) - { - set.Add( item ); - } - } - - return set; - } - - return new HashSet(); - } - - public override List ReadStrongMobileList() - { - return ReadStrongMobileList(); - } - - public override List ReadStrongMobileList() - { - int count = ReadInt(); - - if ( count > 0 ) { - List list = new List( count ); - - for ( int i = 0; i < count; ++i ) { - if ( ReadMobile() is T m ) { - list.Add( m ); - } - } - - return list; - } - - return new List(); - } - - public override HashSet ReadMobileSet() - { - return ReadMobileSet(); - } - - public override HashSet ReadMobileSet() - { - int count = ReadInt(); - - if ( count > 0 ) - { - HashSet set = new HashSet(); - - for( int i = 0; i < count; ++i ) - { - if ( ReadMobile() is T item ) - { - set.Add( item ); - } - } - - return set; - } - - return new HashSet(); - } - - public override List ReadStrongGuildList() - { - return ReadStrongGuildList(); - } - - public override List ReadStrongGuildList() - { - int count = ReadInt(); - - if ( count > 0 ) { - List list = new List( count ); - - for ( int i = 0; i < count; ++i ) { - if ( ReadGuild() is T g ) { - list.Add( g ); - } - } - - return list; - } - - return new List(); - } - - public override HashSet ReadGuildSet() - { - return ReadGuildSet(); - } - - public override HashSet ReadGuildSet() - { - int count = ReadInt(); - - if ( count > 0 ) - { - HashSet set = new HashSet(); - - for( int i = 0; i < count; ++i ) - { - if ( ReadGuild() is T item ) - { - set.Add( item ); - } - } - - return set; - } - - return new HashSet(); - } - - public override Race ReadRace() - { - return Race.Races[ReadByte()]; - } - - public override bool End() - { - return m_File.PeekChar() == -1; - } - } - - public sealed class AsyncWriter : GenericWriter - { - public static int ThreadCount { get; private set; } - - private int BufferSize; - - private long m_LastPos, m_CurPos; - private bool m_Closed; - private bool PrefixStrings; - - private MemoryStream m_Mem; - private BinaryWriter m_Bin; - private FileStream m_File; - - private Queue m_WriteQueue; - private Thread m_WorkerThread; - - public AsyncWriter( string filename, bool prefix ) - : this( filename, 1048576, prefix )//1 mb buffer - { - } - - public AsyncWriter( string filename, int buffSize, bool prefix ) - { - PrefixStrings = prefix; - m_Closed = false; - m_WriteQueue = new Queue(); - BufferSize = buffSize; - - m_File = new FileStream( filename, FileMode.Create, FileAccess.Write, FileShare.None ); - m_Mem = new MemoryStream( BufferSize + 1024 ); - m_Bin = new BinaryWriter( m_Mem, Utility.UTF8WithEncoding ); - } - - private void Enqueue( MemoryStream mem ) - { - lock (m_WriteQueue) - m_WriteQueue.Enqueue( mem ); - - if ( m_WorkerThread == null || !m_WorkerThread.IsAlive ) - { - m_WorkerThread = new Thread( new WorkerThread( this ).Worker ); - m_WorkerThread.Priority = ThreadPriority.BelowNormal; - m_WorkerThread.Start(); - } - } - - private class WorkerThread - { - private AsyncWriter m_Owner; - - public WorkerThread( AsyncWriter owner ) - { - m_Owner = owner; - } - - public void Worker() - { - ThreadCount++; - - int lastCount = 0; - - do { - MemoryStream mem = null; - - lock (m_Owner.m_WriteQueue) { - if ((lastCount = m_Owner.m_WriteQueue.Count) > 0) - mem = m_Owner.m_WriteQueue.Dequeue(); - } - - if (mem != null && mem.Length > 0) - mem.WriteTo(m_Owner.m_File); - } while (lastCount > 1); - - if ( m_Owner.m_Closed ) - m_Owner.m_File.Close(); - - ThreadCount--; - - if (ThreadCount <= 0) - World.NotifyDiskWriteComplete(); - } - } - - private void OnWrite() - { - long curlen = m_Mem.Length; - m_CurPos += curlen - m_LastPos; - m_LastPos = curlen; - if ( curlen >= BufferSize ) - { - Enqueue( m_Mem ); - m_Mem = new MemoryStream( BufferSize + 1024 ); - m_Bin = new BinaryWriter( m_Mem, Utility.UTF8WithEncoding ); - m_LastPos = 0; - } - } - - public MemoryStream MemStream - { - get => m_Mem; - set - { - if ( m_Mem.Length > 0 ) - Enqueue( m_Mem ); - - m_Mem = value; - m_Bin = new BinaryWriter( m_Mem, Utility.UTF8WithEncoding ); - m_LastPos = 0; - m_CurPos = m_Mem.Length; - m_Mem.Seek( 0, SeekOrigin.End ); - } - } - - public override void Close() - { - Enqueue( m_Mem ); - m_Closed = true; - } - - public override long Position => m_CurPos; - - public override void Write( IPAddress value ) - { - m_Bin.Write( Utility.GetLongAddressValue( value ) ); - OnWrite(); - } - - public override void Write( string value ) - { - if ( PrefixStrings ) - { - if ( value == null ) - { - m_Bin.Write( (byte)0 ); - } - else - { - m_Bin.Write( (byte)1 ); - m_Bin.Write( value ); - } - } - else - { - m_Bin.Write( value ); - } - OnWrite(); - } - - public override void WriteDeltaTime( DateTime value ) - { - long ticks = value.Ticks; - long now = DateTime.UtcNow.Ticks; - - TimeSpan d; - - try { d = new TimeSpan( ticks-now ); } - catch { if ( ticks < now ) d = TimeSpan.MaxValue; else d = TimeSpan.MaxValue; } - - Write( d ); - } - - public override void Write( DateTime value ) - { - m_Bin.Write( value.Ticks ); - OnWrite(); - } - - public override void Write( DateTimeOffset value ) - { - m_Bin.Write( value.Ticks ); - m_Bin.Write( value.Offset.Ticks ); - OnWrite(); - } - - public override void Write( TimeSpan value ) - { - m_Bin.Write( value.Ticks ); - OnWrite(); - } - - public override void Write( decimal value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( long value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( ulong value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void WriteEncodedInt( int value ) - { - uint v = (uint)value; - - while( v >= 0x80 ) - { - m_Bin.Write( (byte)(v | 0x80) ); - v >>= 7; - } - - m_Bin.Write( (byte)v ); - OnWrite(); - } - - public override void Write( int value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( uint value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( short value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( ushort value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( double value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( float value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( char value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( byte value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( sbyte value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( bool value ) - { - m_Bin.Write( value ); - OnWrite(); - } - - public override void Write( Point3D value ) - { - Write( value.m_X ); - Write( value.m_Y ); - Write( value.m_Z ); - } - - public override void Write( Point2D value ) - { - Write( value.m_X ); - Write( value.m_Y ); - } - - public override void Write( Rectangle2D value ) - { - Write( value.Start ); - Write( value.End ); - } - - public override void Write( Rectangle3D value ) - { - Write( value.Start ); - Write( value.End ); - } - - public override void Write( Map value ) - { - if ( value != null ) - Write( (byte)value.MapIndex ); - else - Write( (byte)0xFF ); - } - - public override void Write( Race value ) - { - if ( value != null ) - Write( (byte)value.RaceIndex ); - else - Write( (byte)0xFF ); - } - - public override void WriteEntity( IEntity value ) - { - if ( value == null || value.Deleted ) - Write( Serial.MinusOne ); - else - Write( value.Serial ); - } - - public override void Write( Item value ) - { - if ( value == null || value.Deleted ) - Write( Serial.MinusOne ); - else - Write( value.Serial ); - } - - public override void Write( Mobile value ) - { - if ( value == null || value.Deleted ) - Write( Serial.MinusOne ); - else - Write( value.Serial ); - } - - public override void Write( BaseGuild value ) - { - if ( value == null ) - Write( 0 ); - else - Write( value.Id ); - } - - public override void WriteItem( T value ) - { - Write( value ); - } - - public override void WriteMobile( T value ) - { - Write( value ); - } - - public override void WriteGuild( T value ) - { - Write( value ); - } - - public override void WriteMobileList( ArrayList list ) - { - WriteMobileList( list, false ); - } - public override void WriteMobileList( ArrayList list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( ((Mobile)list[i]).Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( (Mobile)list[i] ); - } - - public override void WriteItemList( ArrayList list ) - { - WriteItemList( list, false ); - } - public override void WriteItemList( ArrayList list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( ((Item)list[i]).Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( (Item)list[i] ); - } - - public override void WriteGuildList( ArrayList list ) - { - WriteGuildList( list, false ); - } - public override void WriteGuildList( ArrayList list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( ((BaseGuild)list[i]).Disbanded ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( (BaseGuild)list[i] ); - } - - public override void Write( List list ) - { - Write( list, false ); - } - public override void Write( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void WriteItemList( List list ) - { - WriteItemList( list, false ); - } - public override void WriteItemList( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void Write( HashSet set ) - { - Write( set, false ); - } - public override void Write( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( item => item.Deleted ); - } - - Write( set.Count ); - - foreach( Item item in set ) - { - Write( item ); - } - } - - public override void WriteItemSet( HashSet set ) - { - WriteItemSet( set, false ); - } - public override void WriteItemSet( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( item => item.Deleted ); - } - - Write( set.Count ); - - foreach( Item item in set ) - { - Write( item ); - } - } - - public override void Write( List list ) - { - Write( list, false ); - } - public override void Write( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void WriteMobileList( List list ) - { - WriteMobileList( list, false ); - } - public override void WriteMobileList( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Deleted ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void Write( HashSet set ) - { - Write( set, false ); - } - public override void Write( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( mobile => mobile.Deleted ); - } - - Write( set.Count ); - - foreach( Mobile mob in set ) - { - Write( mob ); - } - } - - public override void WriteMobileSet( HashSet set ) - { - WriteMobileSet( set, false ); - } - public override void WriteMobileSet( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( mob => mob.Deleted ); - } - - Write( set.Count ); - - foreach( Mobile mob in set ) - { - Write( mob ); - } - } - - public override void Write( List list ) - { - Write( list, false ); - } - public override void Write( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Disbanded ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void WriteGuildList( List list ) - { - WriteGuildList( list, false ); - } - public override void WriteGuildList( List list, bool tidy ) - { - if ( tidy ) - { - for( int i = 0; i < list.Count; ) - { - if ( list[i].Disbanded ) - list.RemoveAt( i ); - else - ++i; - } - } - - Write( list.Count ); - - for( int i = 0; i < list.Count; ++i ) - Write( list[i] ); - } - - public override void Write( HashSet set ) - { - Write( set, false ); - } - public override void Write( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( guild => guild.Disbanded ); - } - - Write( set.Count ); - - foreach( BaseGuild guild in set ) - { - Write( guild ); - } - } - - public override void WriteGuildSet( HashSet set ) - { - WriteGuildSet( set, false ); - } - public override void WriteGuildSet( HashSet set, bool tidy ) - { - if ( tidy ) - { - set.RemoveWhere( guild => guild.Disbanded ); - } - - Write( set.Count ); - - foreach( BaseGuild guild in set ) - { - Write( guild ); - } - } - } - - public interface ISerializable - { - int TypeReference { get; } - int SerialIdentity { get; } - void Serialize( GenericWriter writer ); - } -} + for (int i = 0; i < count; ++i) + { + BaseGuild g = ReadGuild(); + + if (g != null) list.Add(g); + } + + return list; + } + + return new ArrayList(); + } + + public override List ReadStrongItemList() + { + return ReadStrongItemList(); + } + + public override List ReadStrongItemList() + { + int count = ReadInt(); + + if (count > 0) + { + List list = new List(count); + + for (int i = 0; i < count; ++i) + if (ReadItem() is T item) + list.Add(item); + + return list; + } + + return new List(); + } + + public override HashSet ReadItemSet() + { + return ReadItemSet(); + } + + public override HashSet ReadItemSet() + { + int count = ReadInt(); + + if (count > 0) + { + HashSet set = new HashSet(); + + for (int i = 0; i < count; ++i) + if (ReadItem() is T item) + set.Add(item); + + return set; + } + + return new HashSet(); + } + + public override List ReadStrongMobileList() + { + return ReadStrongMobileList(); + } + + public override List ReadStrongMobileList() + { + int count = ReadInt(); + + if (count > 0) + { + List list = new List(count); + + for (int i = 0; i < count; ++i) + if (ReadMobile() is T m) + list.Add(m); + + return list; + } + + return new List(); + } + + public override HashSet ReadMobileSet() + { + return ReadMobileSet(); + } + + public override HashSet ReadMobileSet() + { + int count = ReadInt(); + + if (count > 0) + { + HashSet set = new HashSet(); + + for (int i = 0; i < count; ++i) + if (ReadMobile() is T item) + set.Add(item); + + return set; + } + + return new HashSet(); + } + + public override List ReadStrongGuildList() + { + return ReadStrongGuildList(); + } + + public override List ReadStrongGuildList() + { + int count = ReadInt(); + + if (count > 0) + { + List list = new List(count); + + for (int i = 0; i < count; ++i) + if (ReadGuild() is T g) + list.Add(g); + + return list; + } + + return new List(); + } + + public override HashSet ReadGuildSet() + { + return ReadGuildSet(); + } + + public override HashSet ReadGuildSet() + { + int count = ReadInt(); + + if (count > 0) + { + HashSet set = new HashSet(); + + for (int i = 0; i < count; ++i) + if (ReadGuild() is T item) + set.Add(item); + + return set; + } + + return new HashSet(); + } + + public override Race ReadRace() + { + return Race.Races[ReadByte()]; + } + + public override bool End() + { + return m_File.PeekChar() == -1; + } + } + + public sealed class AsyncWriter : GenericWriter + { + private int BufferSize; + private BinaryWriter m_Bin; + private bool m_Closed; + private FileStream m_File; + + private long m_LastPos, m_CurPos; + + private MemoryStream m_Mem; + private Thread m_WorkerThread; + + private Queue m_WriteQueue; + private bool PrefixStrings; + + public AsyncWriter(string filename, bool prefix) + : this(filename, 1048576, prefix) //1 mb buffer + { + } + + public AsyncWriter(string filename, int buffSize, bool prefix) + { + PrefixStrings = prefix; + m_Closed = false; + m_WriteQueue = new Queue(); + BufferSize = buffSize; + + m_File = new FileStream(filename, FileMode.Create, FileAccess.Write, FileShare.None); + m_Mem = new MemoryStream(BufferSize + 1024); + m_Bin = new BinaryWriter(m_Mem, Utility.UTF8WithEncoding); + } + + public static int ThreadCount{ get; private set; } + + public MemoryStream MemStream + { + get => m_Mem; + set + { + if (m_Mem.Length > 0) + Enqueue(m_Mem); + + m_Mem = value; + m_Bin = new BinaryWriter(m_Mem, Utility.UTF8WithEncoding); + m_LastPos = 0; + m_CurPos = m_Mem.Length; + m_Mem.Seek(0, SeekOrigin.End); + } + } + + public override long Position => m_CurPos; + + private void Enqueue(MemoryStream mem) + { + lock (m_WriteQueue) + { + m_WriteQueue.Enqueue(mem); + } + + if (m_WorkerThread == null || !m_WorkerThread.IsAlive) + { + m_WorkerThread = new Thread(new WorkerThread(this).Worker); + m_WorkerThread.Priority = ThreadPriority.BelowNormal; + m_WorkerThread.Start(); + } + } + + private void OnWrite() + { + long curlen = m_Mem.Length; + m_CurPos += curlen - m_LastPos; + m_LastPos = curlen; + if (curlen >= BufferSize) + { + Enqueue(m_Mem); + m_Mem = new MemoryStream(BufferSize + 1024); + m_Bin = new BinaryWriter(m_Mem, Utility.UTF8WithEncoding); + m_LastPos = 0; + } + } + + public override void Close() + { + Enqueue(m_Mem); + m_Closed = true; + } + + public override void Write(IPAddress value) + { + m_Bin.Write(Utility.GetLongAddressValue(value)); + OnWrite(); + } + + public override void Write(string value) + { + if (PrefixStrings) + { + if (value == null) + { + m_Bin.Write((byte)0); + } + else + { + m_Bin.Write((byte)1); + m_Bin.Write(value); + } + } + else + { + m_Bin.Write(value); + } + + OnWrite(); + } + + public override void WriteDeltaTime(DateTime value) + { + long ticks = value.Ticks; + long now = DateTime.UtcNow.Ticks; + + TimeSpan d; + + try + { + d = new TimeSpan(ticks - now); + } + catch + { + if (ticks < now) d = TimeSpan.MaxValue; + else d = TimeSpan.MaxValue; + } + + Write(d); + } + + public override void Write(DateTime value) + { + m_Bin.Write(value.Ticks); + OnWrite(); + } + + public override void Write(DateTimeOffset value) + { + m_Bin.Write(value.Ticks); + m_Bin.Write(value.Offset.Ticks); + OnWrite(); + } + + public override void Write(TimeSpan value) + { + m_Bin.Write(value.Ticks); + OnWrite(); + } + + public override void Write(decimal value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(long value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(ulong value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void WriteEncodedInt(int value) + { + uint v = (uint)value; + + while (v >= 0x80) + { + m_Bin.Write((byte)(v | 0x80)); + v >>= 7; + } + + m_Bin.Write((byte)v); + OnWrite(); + } + + public override void Write(int value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(uint value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(short value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(ushort value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(double value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(float value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(char value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(byte value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(sbyte value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(bool value) + { + m_Bin.Write(value); + OnWrite(); + } + + public override void Write(Point3D value) + { + Write(value.m_X); + Write(value.m_Y); + Write(value.m_Z); + } + + public override void Write(Point2D value) + { + Write(value.m_X); + Write(value.m_Y); + } + + public override void Write(Rectangle2D value) + { + Write(value.Start); + Write(value.End); + } + + public override void Write(Rectangle3D value) + { + Write(value.Start); + Write(value.End); + } + + public override void Write(Map value) + { + if (value != null) + Write((byte)value.MapIndex); + else + Write((byte)0xFF); + } + + public override void Write(Race value) + { + if (value != null) + Write((byte)value.RaceIndex); + else + Write((byte)0xFF); + } + + public override void WriteEntity(IEntity value) + { + if (value == null || value.Deleted) + Write(Serial.MinusOne); + else + Write(value.Serial); + } + + public override void Write(Item value) + { + if (value == null || value.Deleted) + Write(Serial.MinusOne); + else + Write(value.Serial); + } + + public override void Write(Mobile value) + { + if (value == null || value.Deleted) + Write(Serial.MinusOne); + else + Write(value.Serial); + } + + public override void Write(BaseGuild value) + { + if (value == null) + Write(0); + else + Write(value.Id); + } + + public override void WriteItem(T value) + { + Write(value); + } + + public override void WriteMobile(T value) + { + Write(value); + } + + public override void WriteGuild(T value) + { + Write(value); + } + + public override void WriteMobileList(ArrayList list) + { + WriteMobileList(list, false); + } + + public override void WriteMobileList(ArrayList list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (((Mobile)list[i]).Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write((Mobile)list[i]); + } + + public override void WriteItemList(ArrayList list) + { + WriteItemList(list, false); + } + + public override void WriteItemList(ArrayList list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (((Item)list[i]).Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write((Item)list[i]); + } + + public override void WriteGuildList(ArrayList list) + { + WriteGuildList(list, false); + } + + public override void WriteGuildList(ArrayList list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (((BaseGuild)list[i]).Disbanded) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write((BaseGuild)list[i]); + } + + public override void Write(List list) + { + Write(list, false); + } + + public override void Write(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void WriteItemList(List list) + { + WriteItemList(list, false); + } + + public override void WriteItemList(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void Write(HashSet set) + { + Write(set, false); + } + + public override void Write(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(item => item.Deleted); + + Write(set.Count); + + foreach (Item item in set) Write(item); + } + + public override void WriteItemSet(HashSet set) + { + WriteItemSet(set, false); + } + + public override void WriteItemSet(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(item => item.Deleted); + + Write(set.Count); + + foreach (Item item in set) Write(item); + } + + public override void Write(List list) + { + Write(list, false); + } + + public override void Write(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void WriteMobileList(List list) + { + WriteMobileList(list, false); + } + + public override void WriteMobileList(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Deleted) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void Write(HashSet set) + { + Write(set, false); + } + + public override void Write(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(mobile => mobile.Deleted); + + Write(set.Count); + + foreach (Mobile mob in set) Write(mob); + } + + public override void WriteMobileSet(HashSet set) + { + WriteMobileSet(set, false); + } + + public override void WriteMobileSet(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(mob => mob.Deleted); + + Write(set.Count); + + foreach (Mobile mob in set) Write(mob); + } + + public override void Write(List list) + { + Write(list, false); + } + + public override void Write(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Disbanded) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void WriteGuildList(List list) + { + WriteGuildList(list, false); + } + + public override void WriteGuildList(List list, bool tidy) + { + if (tidy) + for (int i = 0; i < list.Count;) + if (list[i].Disbanded) + list.RemoveAt(i); + else + ++i; + + Write(list.Count); + + for (int i = 0; i < list.Count; ++i) + Write(list[i]); + } + + public override void Write(HashSet set) + { + Write(set, false); + } + + public override void Write(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(guild => guild.Disbanded); + + Write(set.Count); + + foreach (BaseGuild guild in set) Write(guild); + } + + public override void WriteGuildSet(HashSet set) + { + WriteGuildSet(set, false); + } + + public override void WriteGuildSet(HashSet set, bool tidy) + { + if (tidy) set.RemoveWhere(guild => guild.Disbanded); + + Write(set.Count); + + foreach (BaseGuild guild in set) Write(guild); + } + + private class WorkerThread + { + private AsyncWriter m_Owner; + + public WorkerThread(AsyncWriter owner) + { + m_Owner = owner; + } + + public void Worker() + { + ThreadCount++; + + int lastCount = 0; + + do + { + MemoryStream mem = null; + + lock (m_Owner.m_WriteQueue) + { + if ((lastCount = m_Owner.m_WriteQueue.Count) > 0) + mem = m_Owner.m_WriteQueue.Dequeue(); + } + + if (mem != null && mem.Length > 0) + mem.WriteTo(m_Owner.m_File); + } while (lastCount > 1); + + if (m_Owner.m_Closed) + m_Owner.m_File.Close(); + + ThreadCount--; + + if (ThreadCount <= 0) + World.NotifyDiskWriteComplete(); + } + } + } + + public interface ISerializable + { + int TypeReference{ get; } + int SerialIdentity{ get; } + void Serialize(GenericWriter writer); + } +} \ No newline at end of file diff --git a/Server/Skills.cs b/Server/Skills.cs index 18db94d74..3f1f7cd5e 100644 --- a/Server/Skills.cs +++ b/Server/Skills.cs @@ -22,933 +22,1108 @@ using System; using System.Collections; using System.Collections.Generic; using System.Linq; - using Server.Network; namespace Server { - public delegate TimeSpan SkillUseCallback( Mobile user ); - - public enum SkillLock : byte - { - Up = 0, - Down = 1, - Locked = 2 - } - - public enum SkillName - { - Alchemy = 0, - Anatomy = 1, - AnimalLore = 2, - ItemID = 3, - ArmsLore = 4, - Parry = 5, - Begging = 6, - Blacksmith = 7, - Fletching = 8, - Peacemaking = 9, - Camping = 10, - Carpentry = 11, - Cartography = 12, - Cooking = 13, - DetectHidden = 14, - Discordance = 15, - EvalInt = 16, - Healing = 17, - Fishing = 18, - Forensics = 19, - Herding = 20, - Hiding = 21, - Provocation = 22, - Inscribe = 23, - Lockpicking = 24, - Magery = 25, - MagicResist = 26, - Tactics = 27, - Snooping = 28, - Musicianship = 29, - Poisoning = 30, - Archery = 31, - SpiritSpeak = 32, - Stealing = 33, - Tailoring = 34, - AnimalTaming = 35, - TasteID = 36, - Tinkering = 37, - Tracking = 38, - Veterinary = 39, - Swords = 40, - Macing = 41, - Fencing = 42, - Wrestling = 43, - Lumberjacking = 44, - Mining = 45, - Meditation = 46, - Stealth = 47, - RemoveTrap = 48, - Necromancy = 49, - Focus = 50, - Chivalry = 51, - Bushido = 52, - Ninjitsu = 53, - Spellweaving = 54, - Mysticism = 55, - Imbuing = 56, - Throwing = 57 - } - - [PropertyObject] - public class Skill - { - private ushort m_Base; - private ushort m_Cap; - - public override string ToString() - { - return $"[{Name}: {Base}]"; - } - - public Skill( Skills owner, SkillInfo info, GenericReader reader ) - { - Owner = owner; - Info = info; - - int version = reader.ReadByte(); - - switch ( version ) - { - case 0: - { - m_Base = reader.ReadUShort(); - m_Cap = reader.ReadUShort(); - Lock = (SkillLock)reader.ReadByte(); - - break; - } - case 0xFF: - { - m_Base = 0; - m_Cap = 1000; - Lock = SkillLock.Up; - - break; - } - default: - { - if ( (version & 0xC0) == 0x00 ) - { - if ( (version & 0x1) != 0 ) - m_Base = reader.ReadUShort(); - - if ( (version & 0x2) != 0 ) - m_Cap = reader.ReadUShort(); - else - m_Cap = 1000; - - if ( (version & 0x4) != 0 ) - Lock = (SkillLock)reader.ReadByte(); - } - - break; - } - } - - if ( Lock < SkillLock.Up || Lock > SkillLock.Locked ) - { - Console.WriteLine( "Bad skill lock -> {0}.{1}", owner.Owner, Lock ); - Lock = SkillLock.Up; - } - } - - public Skill( Skills owner, SkillInfo info, int baseValue, int cap, SkillLock skillLock ) - { - Owner = owner; - Info = info; - m_Base = (ushort)baseValue; - m_Cap = (ushort)cap; - Lock = skillLock; - } - - public void SetLockNoRelay( SkillLock skillLock ) - { - if ( skillLock < SkillLock.Up || skillLock > SkillLock.Locked ) - return; - - Lock = skillLock; - } - - public void Serialize( GenericWriter writer ) - { - if ( m_Base == 0 && m_Cap == 1000 && Lock == SkillLock.Up ) - { - writer.Write( (byte) 0xFF ); // default - } - else - { - int flags = 0x0; - - if ( m_Base != 0 ) - flags |= 0x1; - - if ( m_Cap != 1000 ) - flags |= 0x2; - - if ( Lock != SkillLock.Up ) - flags |= 0x4; - - writer.Write( (byte) flags ); // version - - if ( m_Base != 0 ) - writer.Write( (short) m_Base ); - - if ( m_Cap != 1000 ) - writer.Write( (short) m_Cap ); - - if ( Lock != SkillLock.Up ) - writer.Write( (byte) Lock ); - } - } - - public Skills Owner { get; } - - public SkillName SkillName => (SkillName)Info.SkillID; - - public int SkillID => Info.SkillID; - - [CommandProperty( AccessLevel.Counselor )] - public string Name => Info.Name; - - public SkillInfo Info { get; } - - [CommandProperty( AccessLevel.Counselor )] - public SkillLock Lock { get; private set; } - - public int BaseFixedPoint - { - get => m_Base; - set - { - if ( value < 0 ) - value = 0; - else if ( value >= 0x10000 ) - value = 0xFFFF; + public delegate TimeSpan SkillUseCallback(Mobile user); + + public enum SkillLock : byte + { + Up = 0, + Down = 1, + Locked = 2 + } + + public enum SkillName + { + Alchemy = 0, + Anatomy = 1, + AnimalLore = 2, + ItemID = 3, + ArmsLore = 4, + Parry = 5, + Begging = 6, + Blacksmith = 7, + Fletching = 8, + Peacemaking = 9, + Camping = 10, + Carpentry = 11, + Cartography = 12, + Cooking = 13, + DetectHidden = 14, + Discordance = 15, + EvalInt = 16, + Healing = 17, + Fishing = 18, + Forensics = 19, + Herding = 20, + Hiding = 21, + Provocation = 22, + Inscribe = 23, + Lockpicking = 24, + Magery = 25, + MagicResist = 26, + Tactics = 27, + Snooping = 28, + Musicianship = 29, + Poisoning = 30, + Archery = 31, + SpiritSpeak = 32, + Stealing = 33, + Tailoring = 34, + AnimalTaming = 35, + TasteID = 36, + Tinkering = 37, + Tracking = 38, + Veterinary = 39, + Swords = 40, + Macing = 41, + Fencing = 42, + Wrestling = 43, + Lumberjacking = 44, + Mining = 45, + Meditation = 46, + Stealth = 47, + RemoveTrap = 48, + Necromancy = 49, + Focus = 50, + Chivalry = 51, + Bushido = 52, + Ninjitsu = 53, + Spellweaving = 54, + Mysticism = 55, + Imbuing = 56, + Throwing = 57 + } + + [PropertyObject] + public class Skill + { + private ushort m_Base; + private ushort m_Cap; + + public Skill(Skills owner, SkillInfo info, GenericReader reader) + { + Owner = owner; + Info = info; + + int version = reader.ReadByte(); + + switch (version) + { + case 0: + { + m_Base = reader.ReadUShort(); + m_Cap = reader.ReadUShort(); + Lock = (SkillLock)reader.ReadByte(); + + break; + } + case 0xFF: + { + m_Base = 0; + m_Cap = 1000; + Lock = SkillLock.Up; + + break; + } + default: + { + if ((version & 0xC0) == 0x00) + { + if ((version & 0x1) != 0) + m_Base = reader.ReadUShort(); + + if ((version & 0x2) != 0) + m_Cap = reader.ReadUShort(); + else + m_Cap = 1000; + + if ((version & 0x4) != 0) + Lock = (SkillLock)reader.ReadByte(); + } + + break; + } + } + + if (Lock < SkillLock.Up || Lock > SkillLock.Locked) + { + Console.WriteLine("Bad skill lock -> {0}.{1}", owner.Owner, Lock); + Lock = SkillLock.Up; + } + } + + public Skill(Skills owner, SkillInfo info, int baseValue, int cap, SkillLock skillLock) + { + Owner = owner; + Info = info; + m_Base = (ushort)baseValue; + m_Cap = (ushort)cap; + Lock = skillLock; + } + + public Skills Owner{ get; } + + public SkillName SkillName => (SkillName)Info.SkillID; + + public int SkillID => Info.SkillID; + + [CommandProperty(AccessLevel.Counselor)] + public string Name => Info.Name; + + public SkillInfo Info{ get; } + + [CommandProperty(AccessLevel.Counselor)] + public SkillLock Lock{ get; private set; } + + public int BaseFixedPoint + { + get => m_Base; + set + { + if (value < 0) + value = 0; + else if (value >= 0x10000) + value = 0xFFFF; + + ushort sv = (ushort)value; + + int oldBase = m_Base; + + if (m_Base != sv) + { + Owner.Total = Owner.Total - m_Base + sv; + + m_Base = sv; + + Owner.OnSkillChange(this); + + Mobile m = Owner.Owner; + + m?.OnSkillChange(SkillName, (double)oldBase / 10); + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public double Base + { + get => m_Base / 10.0; + set => BaseFixedPoint = (int)(value * 10.0); + } + + public int CapFixedPoint + { + get => m_Cap; + set + { + if (value < 0) + value = 0; + else if (value >= 0x10000) + value = 0xFFFF; + + ushort sv = (ushort)value; + + if (m_Cap != sv) + { + m_Cap = sv; + + Owner.OnSkillChange(this); + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public double Cap + { + get => m_Cap / 10.0; + set => CapFixedPoint = (int)(value * 10.0); + } + + public static bool UseStatMods{ get; set; } + + public int Fixed => (int)(Value * 10); + + [CommandProperty(AccessLevel.Counselor)] + public double Value + { + get + { + //There has to be this distinction between the racial values and not to account for gaining skills and these skills aren't displayed nor Totaled up. + double value = NonRacialValue; + + double raceBonus = Owner.Owner.RacialSkillBonus; + + if (raceBonus > value) + value = raceBonus; + + return value; + } + } - ushort sv = (ushort)value; + [CommandProperty(AccessLevel.Counselor)] + public double NonRacialValue + { + get + { + double baseValue = Base; + double inv = 100.0 - baseValue; + + if (inv < 0.0) inv = 0.0; + + inv /= 100.0; + + double statsOffset = (UseStatMods ? Owner.Owner.Str : Owner.Owner.RawStr) * Info.StrScale + + (UseStatMods ? Owner.Owner.Dex : Owner.Owner.RawDex) * Info.DexScale + + (UseStatMods ? Owner.Owner.Int : Owner.Owner.RawInt) * Info.IntScale; + double statTotal = Info.StatTotal * inv; + + statsOffset *= inv; + + if (statsOffset > statTotal) + statsOffset = statTotal; + + double value = baseValue + statsOffset; + + Owner.Owner.ValidateSkillMods(); + + List mods = Owner.Owner.SkillMods; + + double bonusObey = 0.0, bonusNotObey = 0.0; + + for (int i = 0; i < mods.Count; ++i) + { + SkillMod mod = mods[i]; + + if (mod.Skill == (SkillName)Info.SkillID) + { + if (mod.Relative) + { + if (mod.ObeyCap) + bonusObey += mod.Value; + else + bonusNotObey += mod.Value; + } + else + { + bonusObey = 0.0; + bonusNotObey = 0.0; + value = mod.Value; + } + } + } + + value += bonusNotObey; + + if (value < Cap) + { + value += bonusObey; - int oldBase = m_Base; + if (value > Cap) + value = Cap; + } - if ( m_Base != sv ) - { - Owner.Total = (Owner.Total - m_Base) + sv; + return value; + } + } - m_Base = sv; + public override string ToString() + { + return $"[{Name}: {Base}]"; + } - Owner.OnSkillChange( this ); - - Mobile m = Owner.Owner; - - m?.OnSkillChange( SkillName, (double)oldBase / 10 ); - } - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public double Base - { - get => ((double)m_Base / 10.0); - set => BaseFixedPoint = (int)(value * 10.0); - } - - public int CapFixedPoint - { - get => m_Cap; - set - { - if ( value < 0 ) - value = 0; - else if ( value >= 0x10000 ) - value = 0xFFFF; - - ushort sv = (ushort)value; - - if ( m_Cap != sv ) - { - m_Cap = sv; - - Owner.OnSkillChange( this ); - } - } - } - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public double Cap - { - get => ((double)m_Cap / 10.0); - set => CapFixedPoint = (int)(value * 10.0); - } - - public static bool UseStatMods { get; set; } - - public int Fixed => (int)(Value * 10); - - [CommandProperty( AccessLevel.Counselor )] - public double Value - { - get - { - //There has to be this distinction between the racial values and not to account for gaining skills and these skills aren't displayed nor Totaled up. - double value = NonRacialValue; - - double raceBonus = Owner.Owner.RacialSkillBonus; - - if ( raceBonus > value ) - value = raceBonus; - - return value; - } - } - - [CommandProperty( AccessLevel.Counselor )] - public double NonRacialValue - { - get - { - double baseValue = Base; - double inv = 100.0 - baseValue; - - if ( inv < 0.0 ) inv = 0.0; - - inv /= 100.0; - - double statsOffset = ((UseStatMods ? Owner.Owner.Str : Owner.Owner.RawStr) * Info.StrScale) + ((UseStatMods ? Owner.Owner.Dex : Owner.Owner.RawDex) * Info.DexScale) + ((UseStatMods ? Owner.Owner.Int : Owner.Owner.RawInt) * Info.IntScale); - double statTotal = Info.StatTotal * inv; - - statsOffset *= inv; - - if ( statsOffset > statTotal ) - statsOffset = statTotal; - - double value = baseValue + statsOffset; - - Owner.Owner.ValidateSkillMods(); - - List mods = Owner.Owner.SkillMods; - - double bonusObey = 0.0, bonusNotObey = 0.0; - - for( int i = 0; i < mods.Count; ++i ) - { - SkillMod mod = mods[i]; - - if ( mod.Skill == (SkillName)Info.SkillID ) - { - if ( mod.Relative ) - { - if ( mod.ObeyCap ) - bonusObey += mod.Value; - else - bonusNotObey += mod.Value; - } - else - { - bonusObey = 0.0; - bonusNotObey = 0.0; - value = mod.Value; - } - } - } - - value += bonusNotObey; - - if ( value < Cap ) - { - value += bonusObey; - - if ( value > Cap ) - value = Cap; - } - - return value; - } - } - - public void Update() - { - Owner.OnSkillChange( this ); - } - } - - public class SkillInfo - { - public SkillInfo( int skillID, string name, double strScale, double dexScale, double intScale, string title, SkillUseCallback callback, double strGain, double dexGain, double intGain, double gainFactor ) - { - Name = name; - Title = title; - SkillID = skillID; - StrScale = strScale / 100.0; - DexScale = dexScale / 100.0; - IntScale = intScale / 100.0; - Callback = callback; - StrGain = strGain; - DexGain = dexGain; - IntGain = intGain; - GainFactor = gainFactor; - - StatTotal = strScale + dexScale + intScale; - } - - public SkillUseCallback Callback { get; set; } - - public int SkillID { get; } - - public string Name { get; set; } - - public string Title { get; set; } - - public double StrScale { get; set; } - - public double DexScale { get; set; } - - public double IntScale { get; set; } - - public double StatTotal { get; set; } - - public double StrGain { get; set; } - - public double DexGain { get; set; } - - public double IntGain { get; set; } - - public double GainFactor { get; set; } - - public static SkillInfo[] Table { get; set; } = new SkillInfo[58] - { - new SkillInfo( 0, "Alchemy", 0.0, 5.0, 5.0, "Alchemist", null, 0.0, 0.5, 0.5, 1.0 ), - new SkillInfo( 1, "Anatomy", 0.0, 0.0, 0.0, "Biologist", null, 0.15, 0.15, 0.7, 1.0 ), - new SkillInfo( 2, "Animal Lore", 0.0, 0.0, 0.0, "Naturalist", null, 0.0, 0.0, 1.0, 1.0 ), - new SkillInfo( 3, "Item Identification", 0.0, 0.0, 0.0, "Merchant", null, 0.0, 0.0, 1.0, 1.0 ), - new SkillInfo( 4, "Arms Lore", 0.0, 0.0, 0.0, "Weapon Master", null, 0.75, 0.15, 0.1, 1.0 ), - new SkillInfo( 5, "Parrying", 7.5, 2.5, 0.0, "Duelist", null, 0.75, 0.25, 0.0, 1.0 ), - new SkillInfo( 6, "Begging", 0.0, 0.0, 0.0, "Beggar", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 7, "Blacksmithy", 10.0, 0.0, 0.0, "Blacksmith", null, 1.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 8, "Bowcraft/Fletching", 6.0, 16.0, 0.0, "Bowyer", null, 0.6, 1.6, 0.0, 1.0 ), - new SkillInfo( 9, "Peacemaking", 0.0, 0.0, 0.0, "Pacifier", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 10, "Camping", 20.0, 15.0, 15.0, "Explorer", null, 2.0, 1.5, 1.5, 1.0 ), - new SkillInfo( 11, "Carpentry", 20.0, 5.0, 0.0, "Carpenter", null, 2.0, 0.5, 0.0, 1.0 ), - new SkillInfo( 12, "Cartography", 0.0, 7.5, 7.5, "Cartographer", null, 0.0, 0.75, 0.75, 1.0 ), - new SkillInfo( 13, "Cooking", 0.0, 20.0, 30.0, "Chef", null, 0.0, 2.0, 3.0, 1.0 ), - new SkillInfo( 14, "Detecting Hidden", 0.0, 0.0, 0.0, "Scout", null, 0.0, 0.4, 0.6, 1.0 ), - new SkillInfo( 15, "Discordance", 0.0, 2.5, 2.5, "Demoralizer", null, 0.0, 0.25, 0.25, 1.0 ), - new SkillInfo( 16, "Evaluating Intelligence", 0.0, 0.0, 0.0, "Scholar", null, 0.0, 0.0, 1.0, 1.0 ), - new SkillInfo( 17, "Healing", 6.0, 6.0, 8.0, "Healer", null, 0.6, 0.6, 0.8, 1.0 ), - new SkillInfo( 18, "Fishing", 0.0, 0.0, 0.0, "Fisherman", null, 0.5, 0.5, 0.0, 1.0 ), - new SkillInfo( 19, "Forensic Evaluation", 0.0, 0.0, 0.0, "Detective", null, 0.0, 0.2, 0.8, 1.0 ), - new SkillInfo( 20, "Herding", 16.25, 6.25, 2.5, "Shepherd", null, 1.625, 0.625, 0.25, 1.0 ), - new SkillInfo( 21, "Hiding", 0.0, 0.0, 0.0, "Shade", null, 0.0, 0.8, 0.2, 1.0 ), - new SkillInfo( 22, "Provocation", 0.0, 4.5, 0.5, "Rouser", null, 0.0, 0.45, 0.05, 1.0 ), - new SkillInfo( 23, "Inscription", 0.0, 2.0, 8.0, "Scribe", null, 0.0, 0.2, 0.8, 1.0 ), - new SkillInfo( 24, "Lockpicking", 0.0, 25.0, 0.0, "Infiltrator", null, 0.0, 2.0, 0.0, 1.0 ), - new SkillInfo( 25, "Magery", 0.0, 0.0, 15.0, "Mage", null, 0.0, 0.0, 1.5, 1.0 ), - new SkillInfo( 26, "Resisting Spells", 0.0, 0.0, 0.0, "Warder", null, 0.25, 0.25, 0.5, 1.0 ), - new SkillInfo( 27, "Tactics", 0.0, 0.0, 0.0, "Tactician", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 28, "Snooping", 0.0, 25.0, 0.0, "Spy", null, 0.0, 2.5, 0.0, 1.0 ), - new SkillInfo( 29, "Musicianship", 0.0, 0.0, 0.0, "Bard", null, 0.0, 0.8, 0.2, 1.0 ), - new SkillInfo( 30, "Poisoning", 0.0, 4.0, 16.0, "Assassin", null, 0.0, 0.4, 1.6, 1.0 ), - new SkillInfo( 31, "Archery", 2.5, 7.5, 0.0, "Archer", null, 0.25, 0.75, 0.0, 1.0 ), - new SkillInfo( 32, "Spirit Speak", 0.0, 0.0, 0.0, "Medium", null, 0.0, 0.0, 1.0, 1.0 ), - new SkillInfo( 33, "Stealing", 0.0, 10.0, 0.0, "Pickpocket", null, 0.0, 1.0, 0.0, 1.0 ), - new SkillInfo( 34, "Tailoring", 3.75, 16.25, 5.0, "Tailor", null, 0.38, 1.63, 0.5, 1.0 ), - new SkillInfo( 35, "Animal Taming", 14.0, 2.0, 4.0, "Tamer", null, 1.4, 0.2, 0.4, 1.0 ), - new SkillInfo( 36, "Taste Identification", 0.0, 0.0, 0.0, "Praegustator", null, 0.2, 0.0, 0.8, 1.0 ), - new SkillInfo( 37, "Tinkering", 5.0, 2.0, 3.0, "Tinker", null, 0.5, 0.2, 0.3, 1.0 ), - new SkillInfo( 38, "Tracking", 0.0, 12.5, 12.5, "Ranger", null, 0.0, 1.25, 1.25, 1.0 ), - new SkillInfo( 39, "Veterinary", 8.0, 4.0, 8.0, "Veterinarian", null, 0.8, 0.4, 0.8, 1.0 ), - new SkillInfo( 40, "Swordsmanship", 7.5, 2.5, 0.0, "Swordsman", null, 0.75, 0.25, 0.0, 1.0 ), - new SkillInfo( 41, "Mace Fighting", 9.0, 1.0, 0.0, "Armsman", null, 0.9, 0.1, 0.0, 1.0 ), - new SkillInfo( 42, "Fencing", 4.5, 5.5, 0.0, "Fencer", null, 0.45, 0.55, 0.0, 1.0 ), - new SkillInfo( 43, "Wrestling", 9.0, 1.0, 0.0, "Wrestler", null, 0.9, 0.1, 0.0, 1.0 ), - new SkillInfo( 44, "Lumberjacking", 20.0, 0.0, 0.0, "Lumberjack", null, 2.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 45, "Mining", 20.0, 0.0, 0.0, "Miner", null, 2.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 46, "Meditation", 0.0, 0.0, 0.0, "Stoic", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 47, "Stealth", 0.0, 0.0, 0.0, "Rogue", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 48, "Remove Trap", 0.0, 0.0, 0.0, "Trap Specialist", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 49, "Necromancy", 0.0, 0.0, 0.0, "Necromancer", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 50, "Focus", 0.0, 0.0, 0.0, "Driven", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 51, "Chivalry", 0.0, 0.0, 0.0, "Paladin", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 52, "Bushido", 0.0, 0.0, 0.0, "Samurai", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 53, "Ninjitsu", 0.0, 0.0, 0.0, "Ninja", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 54, "Spellweaving", 0.0, 0.0, 0.0, "Arcanist", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 55, "Mysticism", 0.0, 0.0, 0.0, "Mystic", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 56, "Imbuing", 0.0, 0.0, 0.0, "Artificer", null, 0.0, 0.0, 0.0, 1.0 ), - new SkillInfo( 57, "Throwing", 0.0, 0.0, 0.0, "Bladeweaver", null, 0.0, 0.0, 0.0, 1.0 ), - }; - } - - [PropertyObject] - public class Skills : IEnumerable - { - private Skill[] m_Skills; - private Skill m_Highest; - - #region Skill Getters & Setters - [CommandProperty( AccessLevel.Counselor )] - public Skill Alchemy{ get => this[SkillName.Alchemy]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Anatomy{ get => this[SkillName.Anatomy]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill AnimalLore{ get => this[SkillName.AnimalLore]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill ItemID{ get => this[SkillName.ItemID]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill ArmsLore{ get => this[SkillName.ArmsLore]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Parry{ get => this[SkillName.Parry]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Begging{ get => this[SkillName.Begging]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Blacksmith{ get => this[SkillName.Blacksmith]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Fletching{ get => this[SkillName.Fletching]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Peacemaking{ get => this[SkillName.Peacemaking]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Camping{ get => this[SkillName.Camping]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Carpentry{ get => this[SkillName.Carpentry]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Cartography{ get => this[SkillName.Cartography]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Cooking{ get => this[SkillName.Cooking]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill DetectHidden{ get => this[SkillName.DetectHidden]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Discordance{ get => this[SkillName.Discordance]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill EvalInt{ get => this[SkillName.EvalInt]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Healing{ get => this[SkillName.Healing]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Fishing{ get => this[SkillName.Fishing]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Forensics{ get => this[SkillName.Forensics]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Herding{ get => this[SkillName.Herding]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Hiding{ get => this[SkillName.Hiding]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Provocation{ get => this[SkillName.Provocation]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Inscribe{ get => this[SkillName.Inscribe]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Lockpicking{ get => this[SkillName.Lockpicking]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Magery{ get => this[SkillName.Magery]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill MagicResist{ get => this[SkillName.MagicResist]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Tactics{ get => this[SkillName.Tactics]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Snooping{ get => this[SkillName.Snooping]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Musicianship{ get => this[SkillName.Musicianship]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Poisoning{ get => this[SkillName.Poisoning]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Archery{ get => this[SkillName.Archery]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill SpiritSpeak{ get => this[SkillName.SpiritSpeak]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Stealing{ get => this[SkillName.Stealing]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Tailoring{ get => this[SkillName.Tailoring]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill AnimalTaming{ get => this[SkillName.AnimalTaming]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill TasteID{ get => this[SkillName.TasteID]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Tinkering{ get => this[SkillName.Tinkering]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Tracking{ get => this[SkillName.Tracking]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Veterinary{ get => this[SkillName.Veterinary]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Swords{ get => this[SkillName.Swords]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Macing{ get => this[SkillName.Macing]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Fencing{ get => this[SkillName.Fencing]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Wrestling{ get => this[SkillName.Wrestling]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Lumberjacking{ get => this[SkillName.Lumberjacking]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Mining{ get => this[SkillName.Mining]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Meditation{ get => this[SkillName.Meditation]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Stealth{ get => this[SkillName.Stealth]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill RemoveTrap{ get => this[SkillName.RemoveTrap]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Necromancy{ get => this[SkillName.Necromancy]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Focus{ get => this[SkillName.Focus]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Chivalry{ get => this[SkillName.Chivalry]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Bushido{ get => this[SkillName.Bushido]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Ninjitsu{ get => this[SkillName.Ninjitsu]; - set{} } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Spellweaving { get => this[SkillName.Spellweaving]; - set { } } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Mysticism { get => this[SkillName.Mysticism]; - set { } } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Imbuing { get => this[SkillName.Imbuing]; - set { } } - - [CommandProperty( AccessLevel.Counselor )] - public Skill Throwing { get => this[SkillName.Throwing]; - set { } } - - #endregion - - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Cap { get; set; } - - public int Total { get; set; } - - public Mobile Owner { get; } - - public int Length => m_Skills.Length; - - public Skill this[SkillName name] => this[(int)name]; - - public Skill this[int skillID] - { - get - { - if ( skillID < 0 || skillID >= m_Skills.Length ) - return null; - - Skill sk = m_Skills[skillID]; - - if ( sk == null ) - m_Skills[skillID] = sk = new Skill( this, SkillInfo.Table[skillID], 0, 1000, SkillLock.Up ); - - return sk; - } - } - - public override string ToString() - { - return "..."; - } - - public static bool UseSkill( Mobile from, SkillName name ) - { - return UseSkill( from, (int)name ); - } - - public static bool UseSkill( Mobile from, int skillID ) - { - if ( !from.CheckAlive() ) - return false; - if ( !from.Region.OnSkillUse( from, skillID ) ) - return false; - if ( !from.AllowSkillUse( (SkillName)skillID ) ) - return false; - - if ( skillID >= 0 && skillID < SkillInfo.Table.Length ) - { - SkillInfo info = SkillInfo.Table[skillID]; - - if ( info.Callback != null ) - { - if (Core.TickCount - from.NextSkillTime >= 0 && from.Spell == null) - { - from.DisruptiveAction(); - - from.NextSkillTime = Core.TickCount + (int)(info.Callback(from)).TotalMilliseconds; - - return true; - } - - from.SendSkillMessage(); - } - else - { - from.SendLocalizedMessage( 500014 ); // That skill cannot be used directly. - } - } - - return false; - } - - public Skill Highest - { - get - { - if ( m_Highest == null ) - { - Skill highest = null; - int value = int.MinValue; - - for ( int i = 0; i < m_Skills.Length; ++i ) - { - Skill sk = m_Skills[i]; - - if ( sk != null && sk.BaseFixedPoint > value ) - { - value = sk.BaseFixedPoint; - highest = sk; - } - } - - if ( highest == null && m_Skills.Length > 0 ) - highest = this[0]; - - m_Highest = highest; - } - - return m_Highest; - } - } - - public void Serialize( GenericWriter writer ) - { - Total = 0; - - writer.Write( (int) 3 ); // version - - writer.Write( (int) Cap ); - writer.Write( (int) m_Skills.Length ); - - for ( int i = 0; i < m_Skills.Length; ++i ) - { - Skill sk = m_Skills[i]; - - if ( sk == null ) - { - writer.Write( (byte) 0xFF ); - } - else - { - sk.Serialize( writer ); - Total += sk.BaseFixedPoint; - } - } - } - - public Skills( Mobile owner ) - { - Owner = owner; - Cap = 7000; - - SkillInfo[] info = SkillInfo.Table; - - m_Skills = new Skill[info.Length]; - - //for ( int i = 0; i < info.Length; ++i ) - // m_Skills[i] = new Skill( this, info[i], 0, 1000, SkillLock.Up ); - } - - public Skills( Mobile owner, GenericReader reader ) - { - Owner = owner; - - int version = reader.ReadInt(); - - switch ( version ) - { - case 3: - case 2: - { - Cap = reader.ReadInt(); - - goto case 1; - } - case 1: - { - if ( version < 2 ) - Cap = 7000; - - if ( version < 3 ) - /*m_Total =*/ reader.ReadInt(); - - SkillInfo[] info = SkillInfo.Table; - - m_Skills = new Skill[info.Length]; - - int count = reader.ReadInt(); - - for ( int i = 0; i < count; ++i ) - { - if ( i < info.Length ) - { - Skill sk = new Skill( this, info[i], reader ); - - if ( sk.BaseFixedPoint != 0 || sk.CapFixedPoint != 1000 || sk.Lock != SkillLock.Up ) - { - m_Skills[i] = sk; - Total += sk.BaseFixedPoint; - } - } - else - { - new Skill( this, null, reader ); - } - } - - //for ( int i = count; i < info.Length; ++i ) - // m_Skills[i] = new Skill( this, info[i], 0, 1000, SkillLock.Up ); - - break; - } - case 0: - { - reader.ReadInt(); - - goto case 1; - } - } - } - - public void OnSkillChange( Skill skill ) - { - if ( skill == m_Highest ) // could be downgrading the skill, force a recalc - m_Highest = null; - else if ( m_Highest != null && skill.BaseFixedPoint > m_Highest.BaseFixedPoint ) - m_Highest = skill; - - Owner.OnSkillInvalidated( skill ); - - NetState ns = Owner.NetState; - - ns?.Send( new SkillChange( skill ) ); - } - - public IEnumerator GetEnumerator() - { - return m_Skills.Where(s => s != null).GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return m_Skills.Where(s => s != null).GetEnumerator(); - } - } -} + public void SetLockNoRelay(SkillLock skillLock) + { + if (skillLock < SkillLock.Up || skillLock > SkillLock.Locked) + return; + + Lock = skillLock; + } + + public void Serialize(GenericWriter writer) + { + if (m_Base == 0 && m_Cap == 1000 && Lock == SkillLock.Up) + { + writer.Write((byte)0xFF); // default + } + else + { + int flags = 0x0; + + if (m_Base != 0) + flags |= 0x1; + + if (m_Cap != 1000) + flags |= 0x2; + + if (Lock != SkillLock.Up) + flags |= 0x4; + + writer.Write((byte)flags); // version + + if (m_Base != 0) + writer.Write((short)m_Base); + + if (m_Cap != 1000) + writer.Write((short)m_Cap); + + if (Lock != SkillLock.Up) + writer.Write((byte)Lock); + } + } + + public void Update() + { + Owner.OnSkillChange(this); + } + } + + public class SkillInfo + { + public SkillInfo(int skillID, string name, double strScale, double dexScale, double intScale, string title, + SkillUseCallback callback, double strGain, double dexGain, double intGain, double gainFactor) + { + Name = name; + Title = title; + SkillID = skillID; + StrScale = strScale / 100.0; + DexScale = dexScale / 100.0; + IntScale = intScale / 100.0; + Callback = callback; + StrGain = strGain; + DexGain = dexGain; + IntGain = intGain; + GainFactor = gainFactor; + + StatTotal = strScale + dexScale + intScale; + } + + public SkillUseCallback Callback{ get; set; } + + public int SkillID{ get; } + + public string Name{ get; set; } + + public string Title{ get; set; } + + public double StrScale{ get; set; } + + public double DexScale{ get; set; } + + public double IntScale{ get; set; } + + public double StatTotal{ get; set; } + + public double StrGain{ get; set; } + + public double DexGain{ get; set; } + + public double IntGain{ get; set; } + + public double GainFactor{ get; set; } + + public static SkillInfo[] Table{ get; set; } = new SkillInfo[58] + { + new SkillInfo(0, "Alchemy", 0.0, 5.0, 5.0, "Alchemist", null, 0.0, 0.5, 0.5, 1.0), + new SkillInfo(1, "Anatomy", 0.0, 0.0, 0.0, "Biologist", null, 0.15, 0.15, 0.7, 1.0), + new SkillInfo(2, "Animal Lore", 0.0, 0.0, 0.0, "Naturalist", null, 0.0, 0.0, 1.0, 1.0), + new SkillInfo(3, "Item Identification", 0.0, 0.0, 0.0, "Merchant", null, 0.0, 0.0, 1.0, 1.0), + new SkillInfo(4, "Arms Lore", 0.0, 0.0, 0.0, "Weapon Master", null, 0.75, 0.15, 0.1, 1.0), + new SkillInfo(5, "Parrying", 7.5, 2.5, 0.0, "Duelist", null, 0.75, 0.25, 0.0, 1.0), + new SkillInfo(6, "Begging", 0.0, 0.0, 0.0, "Beggar", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(7, "Blacksmithy", 10.0, 0.0, 0.0, "Blacksmith", null, 1.0, 0.0, 0.0, 1.0), + new SkillInfo(8, "Bowcraft/Fletching", 6.0, 16.0, 0.0, "Bowyer", null, 0.6, 1.6, 0.0, 1.0), + new SkillInfo(9, "Peacemaking", 0.0, 0.0, 0.0, "Pacifier", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(10, "Camping", 20.0, 15.0, 15.0, "Explorer", null, 2.0, 1.5, 1.5, 1.0), + new SkillInfo(11, "Carpentry", 20.0, 5.0, 0.0, "Carpenter", null, 2.0, 0.5, 0.0, 1.0), + new SkillInfo(12, "Cartography", 0.0, 7.5, 7.5, "Cartographer", null, 0.0, 0.75, 0.75, 1.0), + new SkillInfo(13, "Cooking", 0.0, 20.0, 30.0, "Chef", null, 0.0, 2.0, 3.0, 1.0), + new SkillInfo(14, "Detecting Hidden", 0.0, 0.0, 0.0, "Scout", null, 0.0, 0.4, 0.6, 1.0), + new SkillInfo(15, "Discordance", 0.0, 2.5, 2.5, "Demoralizer", null, 0.0, 0.25, 0.25, 1.0), + new SkillInfo(16, "Evaluating Intelligence", 0.0, 0.0, 0.0, "Scholar", null, 0.0, 0.0, 1.0, 1.0), + new SkillInfo(17, "Healing", 6.0, 6.0, 8.0, "Healer", null, 0.6, 0.6, 0.8, 1.0), + new SkillInfo(18, "Fishing", 0.0, 0.0, 0.0, "Fisherman", null, 0.5, 0.5, 0.0, 1.0), + new SkillInfo(19, "Forensic Evaluation", 0.0, 0.0, 0.0, "Detective", null, 0.0, 0.2, 0.8, 1.0), + new SkillInfo(20, "Herding", 16.25, 6.25, 2.5, "Shepherd", null, 1.625, 0.625, 0.25, 1.0), + new SkillInfo(21, "Hiding", 0.0, 0.0, 0.0, "Shade", null, 0.0, 0.8, 0.2, 1.0), + new SkillInfo(22, "Provocation", 0.0, 4.5, 0.5, "Rouser", null, 0.0, 0.45, 0.05, 1.0), + new SkillInfo(23, "Inscription", 0.0, 2.0, 8.0, "Scribe", null, 0.0, 0.2, 0.8, 1.0), + new SkillInfo(24, "Lockpicking", 0.0, 25.0, 0.0, "Infiltrator", null, 0.0, 2.0, 0.0, 1.0), + new SkillInfo(25, "Magery", 0.0, 0.0, 15.0, "Mage", null, 0.0, 0.0, 1.5, 1.0), + new SkillInfo(26, "Resisting Spells", 0.0, 0.0, 0.0, "Warder", null, 0.25, 0.25, 0.5, 1.0), + new SkillInfo(27, "Tactics", 0.0, 0.0, 0.0, "Tactician", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(28, "Snooping", 0.0, 25.0, 0.0, "Spy", null, 0.0, 2.5, 0.0, 1.0), + new SkillInfo(29, "Musicianship", 0.0, 0.0, 0.0, "Bard", null, 0.0, 0.8, 0.2, 1.0), + new SkillInfo(30, "Poisoning", 0.0, 4.0, 16.0, "Assassin", null, 0.0, 0.4, 1.6, 1.0), + new SkillInfo(31, "Archery", 2.5, 7.5, 0.0, "Archer", null, 0.25, 0.75, 0.0, 1.0), + new SkillInfo(32, "Spirit Speak", 0.0, 0.0, 0.0, "Medium", null, 0.0, 0.0, 1.0, 1.0), + new SkillInfo(33, "Stealing", 0.0, 10.0, 0.0, "Pickpocket", null, 0.0, 1.0, 0.0, 1.0), + new SkillInfo(34, "Tailoring", 3.75, 16.25, 5.0, "Tailor", null, 0.38, 1.63, 0.5, 1.0), + new SkillInfo(35, "Animal Taming", 14.0, 2.0, 4.0, "Tamer", null, 1.4, 0.2, 0.4, 1.0), + new SkillInfo(36, "Taste Identification", 0.0, 0.0, 0.0, "Praegustator", null, 0.2, 0.0, 0.8, 1.0), + new SkillInfo(37, "Tinkering", 5.0, 2.0, 3.0, "Tinker", null, 0.5, 0.2, 0.3, 1.0), + new SkillInfo(38, "Tracking", 0.0, 12.5, 12.5, "Ranger", null, 0.0, 1.25, 1.25, 1.0), + new SkillInfo(39, "Veterinary", 8.0, 4.0, 8.0, "Veterinarian", null, 0.8, 0.4, 0.8, 1.0), + new SkillInfo(40, "Swordsmanship", 7.5, 2.5, 0.0, "Swordsman", null, 0.75, 0.25, 0.0, 1.0), + new SkillInfo(41, "Mace Fighting", 9.0, 1.0, 0.0, "Armsman", null, 0.9, 0.1, 0.0, 1.0), + new SkillInfo(42, "Fencing", 4.5, 5.5, 0.0, "Fencer", null, 0.45, 0.55, 0.0, 1.0), + new SkillInfo(43, "Wrestling", 9.0, 1.0, 0.0, "Wrestler", null, 0.9, 0.1, 0.0, 1.0), + new SkillInfo(44, "Lumberjacking", 20.0, 0.0, 0.0, "Lumberjack", null, 2.0, 0.0, 0.0, 1.0), + new SkillInfo(45, "Mining", 20.0, 0.0, 0.0, "Miner", null, 2.0, 0.0, 0.0, 1.0), + new SkillInfo(46, "Meditation", 0.0, 0.0, 0.0, "Stoic", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(47, "Stealth", 0.0, 0.0, 0.0, "Rogue", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(48, "Remove Trap", 0.0, 0.0, 0.0, "Trap Specialist", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(49, "Necromancy", 0.0, 0.0, 0.0, "Necromancer", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(50, "Focus", 0.0, 0.0, 0.0, "Driven", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(51, "Chivalry", 0.0, 0.0, 0.0, "Paladin", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(52, "Bushido", 0.0, 0.0, 0.0, "Samurai", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(53, "Ninjitsu", 0.0, 0.0, 0.0, "Ninja", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(54, "Spellweaving", 0.0, 0.0, 0.0, "Arcanist", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(55, "Mysticism", 0.0, 0.0, 0.0, "Mystic", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(56, "Imbuing", 0.0, 0.0, 0.0, "Artificer", null, 0.0, 0.0, 0.0, 1.0), + new SkillInfo(57, "Throwing", 0.0, 0.0, 0.0, "Bladeweaver", null, 0.0, 0.0, 0.0, 1.0) + }; + } + + [PropertyObject] + public class Skills : IEnumerable + { + private Skill m_Highest; + private Skill[] m_Skills; + + public Skills(Mobile owner) + { + Owner = owner; + Cap = 7000; + + SkillInfo[] info = SkillInfo.Table; + + m_Skills = new Skill[info.Length]; + + //for ( int i = 0; i < info.Length; ++i ) + // m_Skills[i] = new Skill( this, info[i], 0, 1000, SkillLock.Up ); + } + + public Skills(Mobile owner, GenericReader reader) + { + Owner = owner; + + int version = reader.ReadInt(); + + switch (version) + { + case 3: + case 2: + { + Cap = reader.ReadInt(); + + goto case 1; + } + case 1: + { + if (version < 2) + Cap = 7000; + + if (version < 3) + /*m_Total =*/ reader.ReadInt(); + + SkillInfo[] info = SkillInfo.Table; + + m_Skills = new Skill[info.Length]; + + int count = reader.ReadInt(); + + for (int i = 0; i < count; ++i) + if (i < info.Length) + { + Skill sk = new Skill(this, info[i], reader); + + if (sk.BaseFixedPoint != 0 || sk.CapFixedPoint != 1000 || sk.Lock != SkillLock.Up) + { + m_Skills[i] = sk; + Total += sk.BaseFixedPoint; + } + } + else + { + new Skill(this, null, reader); + } + + //for ( int i = count; i < info.Length; ++i ) + // m_Skills[i] = new Skill( this, info[i], 0, 1000, SkillLock.Up ); + + break; + } + case 0: + { + reader.ReadInt(); + + goto case 1; + } + } + } + + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Cap{ get; set; } + + public int Total{ get; set; } + + public Mobile Owner{ get; } + + public int Length => m_Skills.Length; + + public Skill this[SkillName name] => this[(int)name]; + + public Skill this[int skillID] + { + get + { + if (skillID < 0 || skillID >= m_Skills.Length) + return null; + + Skill sk = m_Skills[skillID]; + + if (sk == null) + m_Skills[skillID] = sk = new Skill(this, SkillInfo.Table[skillID], 0, 1000, SkillLock.Up); + + return sk; + } + } + + public Skill Highest + { + get + { + if (m_Highest == null) + { + Skill highest = null; + int value = int.MinValue; + + for (int i = 0; i < m_Skills.Length; ++i) + { + Skill sk = m_Skills[i]; + + if (sk != null && sk.BaseFixedPoint > value) + { + value = sk.BaseFixedPoint; + highest = sk; + } + } + + if (highest == null && m_Skills.Length > 0) + highest = this[0]; + + m_Highest = highest; + } + + return m_Highest; + } + } + + public IEnumerator GetEnumerator() + { + return m_Skills.Where(s => s != null).GetEnumerator(); + } + + IEnumerator IEnumerable.GetEnumerator() + { + return m_Skills.Where(s => s != null).GetEnumerator(); + } + + public override string ToString() + { + return "..."; + } + + public static bool UseSkill(Mobile from, SkillName name) + { + return UseSkill(from, (int)name); + } + + public static bool UseSkill(Mobile from, int skillID) + { + if (!from.CheckAlive()) + return false; + if (!from.Region.OnSkillUse(from, skillID)) + return false; + if (!from.AllowSkillUse((SkillName)skillID)) + return false; + + if (skillID >= 0 && skillID < SkillInfo.Table.Length) + { + SkillInfo info = SkillInfo.Table[skillID]; + + if (info.Callback != null) + { + if (Core.TickCount - from.NextSkillTime >= 0 && from.Spell == null) + { + from.DisruptiveAction(); + + from.NextSkillTime = Core.TickCount + (int)info.Callback(from).TotalMilliseconds; + + return true; + } + + from.SendSkillMessage(); + } + else + { + from.SendLocalizedMessage(500014); // That skill cannot be used directly. + } + } + + return false; + } + + public void Serialize(GenericWriter writer) + { + Total = 0; + + writer.Write(3); // version + + writer.Write(Cap); + writer.Write(m_Skills.Length); + + for (int i = 0; i < m_Skills.Length; ++i) + { + Skill sk = m_Skills[i]; + + if (sk == null) + { + writer.Write((byte)0xFF); + } + else + { + sk.Serialize(writer); + Total += sk.BaseFixedPoint; + } + } + } + + public void OnSkillChange(Skill skill) + { + if (skill == m_Highest) // could be downgrading the skill, force a recalc + m_Highest = null; + else if (m_Highest != null && skill.BaseFixedPoint > m_Highest.BaseFixedPoint) + m_Highest = skill; + + Owner.OnSkillInvalidated(skill); + + NetState ns = Owner.NetState; + + ns?.Send(new SkillChange(skill)); + } + + #region Skill Getters & Setters + + [CommandProperty(AccessLevel.Counselor)] + public Skill Alchemy + { + get => this[SkillName.Alchemy]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Anatomy + { + get => this[SkillName.Anatomy]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill AnimalLore + { + get => this[SkillName.AnimalLore]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill ItemID + { + get => this[SkillName.ItemID]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill ArmsLore + { + get => this[SkillName.ArmsLore]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Parry + { + get => this[SkillName.Parry]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Begging + { + get => this[SkillName.Begging]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Blacksmith + { + get => this[SkillName.Blacksmith]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Fletching + { + get => this[SkillName.Fletching]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Peacemaking + { + get => this[SkillName.Peacemaking]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Camping + { + get => this[SkillName.Camping]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Carpentry + { + get => this[SkillName.Carpentry]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Cartography + { + get => this[SkillName.Cartography]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Cooking + { + get => this[SkillName.Cooking]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill DetectHidden + { + get => this[SkillName.DetectHidden]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Discordance + { + get => this[SkillName.Discordance]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill EvalInt + { + get => this[SkillName.EvalInt]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Healing + { + get => this[SkillName.Healing]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Fishing + { + get => this[SkillName.Fishing]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Forensics + { + get => this[SkillName.Forensics]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Herding + { + get => this[SkillName.Herding]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Hiding + { + get => this[SkillName.Hiding]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Provocation + { + get => this[SkillName.Provocation]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Inscribe + { + get => this[SkillName.Inscribe]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Lockpicking + { + get => this[SkillName.Lockpicking]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Magery + { + get => this[SkillName.Magery]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill MagicResist + { + get => this[SkillName.MagicResist]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Tactics + { + get => this[SkillName.Tactics]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Snooping + { + get => this[SkillName.Snooping]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Musicianship + { + get => this[SkillName.Musicianship]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Poisoning + { + get => this[SkillName.Poisoning]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Archery + { + get => this[SkillName.Archery]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill SpiritSpeak + { + get => this[SkillName.SpiritSpeak]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Stealing + { + get => this[SkillName.Stealing]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Tailoring + { + get => this[SkillName.Tailoring]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill AnimalTaming + { + get => this[SkillName.AnimalTaming]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill TasteID + { + get => this[SkillName.TasteID]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Tinkering + { + get => this[SkillName.Tinkering]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Tracking + { + get => this[SkillName.Tracking]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Veterinary + { + get => this[SkillName.Veterinary]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Swords + { + get => this[SkillName.Swords]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Macing + { + get => this[SkillName.Macing]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Fencing + { + get => this[SkillName.Fencing]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Wrestling + { + get => this[SkillName.Wrestling]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Lumberjacking + { + get => this[SkillName.Lumberjacking]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Mining + { + get => this[SkillName.Mining]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Meditation + { + get => this[SkillName.Meditation]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Stealth + { + get => this[SkillName.Stealth]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill RemoveTrap + { + get => this[SkillName.RemoveTrap]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Necromancy + { + get => this[SkillName.Necromancy]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Focus + { + get => this[SkillName.Focus]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Chivalry + { + get => this[SkillName.Chivalry]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Bushido + { + get => this[SkillName.Bushido]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Ninjitsu + { + get => this[SkillName.Ninjitsu]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Spellweaving + { + get => this[SkillName.Spellweaving]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Mysticism + { + get => this[SkillName.Mysticism]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Imbuing + { + get => this[SkillName.Imbuing]; + set { } + } + + [CommandProperty(AccessLevel.Counselor)] + public Skill Throwing + { + get => this[SkillName.Throwing]; + set { } + } + + #endregion + } +} \ No newline at end of file diff --git a/Server/Targeting/LandTarget.cs b/Server/Targeting/LandTarget.cs index 1ff2fe0cb..d8e66dcdc 100644 --- a/Server/Targeting/LandTarget.cs +++ b/Server/Targeting/LandTarget.cs @@ -20,40 +20,40 @@ namespace Server.Targeting { - public class LandTarget : IPoint3D - { - private Point3D m_Location; + public class LandTarget : IPoint3D + { + private Point3D m_Location; - public LandTarget( Point3D location, Map map ) - { - m_Location = location; + public LandTarget(Point3D location, Map map) + { + m_Location = location; - if ( map != null ) - { - m_Location.Z = map.GetAverageZ( m_Location.X, m_Location.Y ); - TileID = map.Tiles.GetLandTile( m_Location.X, m_Location.Y ).ID & TileData.MaxLandValue; - } - } + if (map != null) + { + m_Location.Z = map.GetAverageZ(m_Location.X, m_Location.Y); + TileID = map.Tiles.GetLandTile(m_Location.X, m_Location.Y).ID & TileData.MaxLandValue; + } + } - [CommandProperty( AccessLevel.Counselor )] - public string Name => TileData.LandTable[TileID].Name; + [CommandProperty(AccessLevel.Counselor)] + public string Name => TileData.LandTable[TileID].Name; - [CommandProperty( AccessLevel.Counselor )] - public TileFlag Flags => TileData.LandTable[TileID].Flags; + [CommandProperty(AccessLevel.Counselor)] + public TileFlag Flags => TileData.LandTable[TileID].Flags; - [CommandProperty( AccessLevel.Counselor )] - public int TileID { get; } + [CommandProperty(AccessLevel.Counselor)] + public int TileID{ get; } - [CommandProperty( AccessLevel.Counselor )] - public Point3D Location => m_Location; + [CommandProperty(AccessLevel.Counselor)] + public Point3D Location => m_Location; - [CommandProperty( AccessLevel.Counselor )] - public int X => m_Location.X; + [CommandProperty(AccessLevel.Counselor)] + public int X => m_Location.X; - [CommandProperty( AccessLevel.Counselor )] - public int Y => m_Location.Y; + [CommandProperty(AccessLevel.Counselor)] + public int Y => m_Location.Y; - [CommandProperty( AccessLevel.Counselor )] - public int Z => m_Location.Z; - } + [CommandProperty(AccessLevel.Counselor)] + public int Z => m_Location.Z; + } } \ No newline at end of file diff --git a/Server/Targeting/MultiTarget.cs b/Server/Targeting/MultiTarget.cs index 71ef0b54a..0d3c2fcaf 100644 --- a/Server/Targeting/MultiTarget.cs +++ b/Server/Targeting/MultiTarget.cs @@ -22,29 +22,29 @@ using Server.Network; namespace Server.Targeting { - public abstract class MultiTarget : Target - { - public int MultiID { get; set; } + public abstract class MultiTarget : Target + { + protected MultiTarget(int multiID, Point3D offset) + : this(multiID, offset, 10, true, TargetFlags.None) + { + } - public Point3D Offset { get; set; } + protected MultiTarget(int multiID, Point3D offset, int range, bool allowGround, TargetFlags flags) + : base(range, allowGround, flags) + { + MultiID = multiID; + Offset = offset; + } - protected MultiTarget( int multiID, Point3D offset ) - : this( multiID, offset, 10, true, TargetFlags.None ) - { - } + public int MultiID{ get; set; } - protected MultiTarget( int multiID, Point3D offset, int range, bool allowGround, TargetFlags flags ) - : base( range, allowGround, flags ) - { - MultiID = multiID; - Offset = offset; - } + public Point3D Offset{ get; set; } - public override Packet GetPacketFor( NetState ns ) - { - if ( ns.HighSeas ) - return new MultiTargetReqHS( this ); - return new MultiTargetReq( this ); - } - } + public override Packet GetPacketFor(NetState ns) + { + if (ns.HighSeas) + return new MultiTargetReqHS(this); + return new MultiTargetReq(this); + } + } } \ No newline at end of file diff --git a/Server/Targeting/StaticTarget.cs b/Server/Targeting/StaticTarget.cs index 7ef2de9ca..e2dcec088 100644 --- a/Server/Targeting/StaticTarget.cs +++ b/Server/Targeting/StaticTarget.cs @@ -20,36 +20,36 @@ namespace Server.Targeting { - public class StaticTarget : IPoint3D - { - private Point3D m_Location; + public class StaticTarget : IPoint3D + { + private Point3D m_Location; - public StaticTarget( Point3D location, int itemID ) - { - m_Location = location; - ItemID = itemID & TileData.MaxItemValue; - m_Location.Z += TileData.ItemTable[ItemID].CalcHeight; - } + public StaticTarget(Point3D location, int itemID) + { + m_Location = location; + ItemID = itemID & TileData.MaxItemValue; + m_Location.Z += TileData.ItemTable[ItemID].CalcHeight; + } - [CommandProperty( AccessLevel.Counselor )] - public Point3D Location => m_Location; + [CommandProperty(AccessLevel.Counselor)] + public Point3D Location => m_Location; - [CommandProperty( AccessLevel.Counselor )] - public string Name => TileData.ItemTable[ItemID].Name; + [CommandProperty(AccessLevel.Counselor)] + public string Name => TileData.ItemTable[ItemID].Name; - [CommandProperty( AccessLevel.Counselor )] - public TileFlag Flags => TileData.ItemTable[ItemID].Flags; + [CommandProperty(AccessLevel.Counselor)] + public TileFlag Flags => TileData.ItemTable[ItemID].Flags; - [CommandProperty( AccessLevel.Counselor )] - public int X => m_Location.X; + [CommandProperty(AccessLevel.Counselor)] + public int ItemID{ get; } - [CommandProperty( AccessLevel.Counselor )] - public int Y => m_Location.Y; + [CommandProperty(AccessLevel.Counselor)] + public int X => m_Location.X; - [CommandProperty( AccessLevel.Counselor )] - public int Z => m_Location.Z; + [CommandProperty(AccessLevel.Counselor)] + public int Y => m_Location.Y; - [CommandProperty( AccessLevel.Counselor )] - public int ItemID { get; } - } + [CommandProperty(AccessLevel.Counselor)] + public int Z => m_Location.Z; + } } \ No newline at end of file diff --git a/Server/Targeting/Target.cs b/Server/Targeting/Target.cs index b9c73c951..4e00064d0 100644 --- a/Server/Targeting/Target.cs +++ b/Server/Targeting/Target.cs @@ -23,280 +23,279 @@ using Server.Network; namespace Server.Targeting { - public abstract class Target - { - private static int m_NextTargetID; + public abstract class Target + { + private static int m_NextTargetID; - public static bool TargetIDValidation { get; set; } = true; + private Timer m_TimeoutTimer; - public DateTime TimeoutTime { get; private set; } + protected Target(int range, bool allowGround, TargetFlags flags) + { + TargetID = ++m_NextTargetID; + Range = range; + AllowGround = allowGround; + Flags = flags; - protected Target( int range, bool allowGround, TargetFlags flags ) - { - TargetID = ++m_NextTargetID; - Range = range; - AllowGround = allowGround; - Flags = flags; + CheckLOS = true; + } - CheckLOS = true; - } + public static bool TargetIDValidation{ get; set; } = true; - public static void Cancel( Mobile m ) - { - NetState ns = m.NetState; + public DateTime TimeoutTime{ get; private set; } - ns?.Send( CancelTarget.Instance ); + public bool CheckLOS{ get; set; } - Target targ = m.Target; + public bool DisallowMultis{ get; set; } - targ?.OnTargetCancel( m, TargetCancelType.Canceled ); - } + public bool AllowNonlocal{ get; set; } - private Timer m_TimeoutTimer; + public int TargetID{ get; } - public void BeginTimeout( Mobile from, TimeSpan delay ) - { - TimeoutTime = DateTime.UtcNow + delay; + public int Range{ get; set; } - m_TimeoutTimer?.Stop(); + public bool AllowGround{ get; set; } - m_TimeoutTimer = new TimeoutTimer( this, from, delay ); - m_TimeoutTimer.Start(); - } + public TargetFlags Flags{ get; set; } - public void CancelTimeout() - { - m_TimeoutTimer?.Stop(); + public static void Cancel(Mobile m) + { + NetState ns = m.NetState; - m_TimeoutTimer = null; - } + ns?.Send(CancelTarget.Instance); - public void Timeout( Mobile from ) - { - CancelTimeout(); - from.ClearTarget(); + Target targ = m.Target; - Cancel( from ); + targ?.OnTargetCancel(m, TargetCancelType.Canceled); + } - OnTargetCancel( from, TargetCancelType.Timeout ); - OnTargetFinish( from ); - } + public void BeginTimeout(Mobile from, TimeSpan delay) + { + TimeoutTime = DateTime.UtcNow + delay; - private class TimeoutTimer : Timer - { - private Target m_Target; - private Mobile m_Mobile; + m_TimeoutTimer?.Stop(); - private static TimeSpan ThirtySeconds = TimeSpan.FromSeconds( 30.0 ); - private static TimeSpan TenSeconds = TimeSpan.FromSeconds( 10.0 ); - private static TimeSpan OneSecond = TimeSpan.FromSeconds( 1.0 ); + m_TimeoutTimer = new TimeoutTimer(this, from, delay); + m_TimeoutTimer.Start(); + } - public TimeoutTimer( Target target, Mobile m, TimeSpan delay ) : base( delay ) - { - m_Target = target; - m_Mobile = m; + public void CancelTimeout() + { + m_TimeoutTimer?.Stop(); - if ( delay >= ThirtySeconds ) - Priority = TimerPriority.FiveSeconds; - else if ( delay >= TenSeconds ) - Priority = TimerPriority.OneSecond; - else if ( delay >= OneSecond ) - Priority = TimerPriority.TwoFiftyMS; - else - Priority = TimerPriority.TwentyFiveMS; - } + m_TimeoutTimer = null; + } - protected override void OnTick() - { - if ( m_Mobile.Target == m_Target ) - m_Target.Timeout( m_Mobile ); - } - } + public void Timeout(Mobile from) + { + CancelTimeout(); + from.ClearTarget(); - public bool CheckLOS { get; set; } + Cancel(from); - public bool DisallowMultis { get; set; } + OnTargetCancel(from, TargetCancelType.Timeout); + OnTargetFinish(from); + } - public bool AllowNonlocal { get; set; } + public virtual Packet GetPacketFor(NetState ns) + { + return new TargetReq(this); + } - public int TargetID { get; } + public void Cancel(Mobile from, TargetCancelType type) + { + CancelTimeout(); + from.ClearTarget(); - public virtual Packet GetPacketFor( NetState ns ) - { - return new TargetReq( this ); - } + OnTargetCancel(from, type); + OnTargetFinish(from); + } - public void Cancel( Mobile from, TargetCancelType type ) - { - CancelTimeout(); - from.ClearTarget(); + public void Invoke(Mobile from, object targeted) + { + CancelTimeout(); + from.ClearTarget(); - OnTargetCancel( from, type ); - OnTargetFinish( from ); - } + if (from.Deleted) + { + OnTargetCancel(from, TargetCancelType.Canceled); + OnTargetFinish(from); + return; + } - public void Invoke( Mobile from, object targeted ) - { - CancelTimeout(); - from.ClearTarget(); + Point3D loc; + Map map; - if ( from.Deleted ) - { - OnTargetCancel( from, TargetCancelType.Canceled ); - OnTargetFinish( from ); - return; - } + Item item = targeted as Item; + Mobile mobile = targeted as Mobile; - Point3D loc; - Map map; + if (targeted is LandTarget target) + { + loc = target.Location; + map = from.Map; + } + else if (targeted is StaticTarget staticTarget) + { + loc = staticTarget.Location; + map = from.Map; + } + else if (mobile != null) + { + if (mobile.Deleted) + { + OnTargetDeleted(from, mobile); + OnTargetFinish(from); + return; + } - Item item = targeted as Item; - Mobile mobile = targeted as Mobile; + if (!mobile.CanTarget) + { + OnTargetUntargetable(from, mobile); + OnTargetFinish(from); + return; + } - if ( targeted is LandTarget target ) - { - loc = target.Location; - map = from.Map; - } - else if ( targeted is StaticTarget staticTarget ) - { - loc = staticTarget.Location; - map = from.Map; - } - else if ( mobile != null ) - { - if ( mobile.Deleted ) - { - OnTargetDeleted( from, mobile ); - OnTargetFinish( from ); - return; - } + loc = mobile.Location; + map = mobile.Map; + } + else if (item != null) + { + if (item.Deleted) + { + OnTargetDeleted(from, item); + OnTargetFinish(from); + return; + } - if ( !mobile.CanTarget ) - { - OnTargetUntargetable( from, mobile ); - OnTargetFinish( from ); - return; - } + if (!item.CanTarget) + { + OnTargetUntargetable(from, item); + OnTargetFinish(from); + return; + } - loc = mobile.Location; - map = mobile.Map; - } - else if ( item != null ) - { - if ( item.Deleted ) - { - OnTargetDeleted( from, item ); - OnTargetFinish( from ); - return; - } + object root = item.RootParent; - if ( !item.CanTarget ) - { - OnTargetUntargetable( from, item ); - OnTargetFinish( from ); - return; - } + if (!AllowNonlocal && root is Mobile && root != from && from.AccessLevel == AccessLevel.Player) + { + OnNonlocalTarget(from, item); + OnTargetFinish(from); + return; + } - object root = item.RootParent; + loc = item.GetWorldLocation(); + map = item.Map; + } + else + { + OnTargetCancel(from, TargetCancelType.Canceled); + OnTargetFinish(from); + return; + } - if ( !AllowNonlocal && root is Mobile && root != from && from.AccessLevel == AccessLevel.Player ) - { - OnNonlocalTarget( from, item ); - OnTargetFinish( from ); - return; - } + if (map == null || map != from.Map || Range != -1 && !from.InRange(loc, Range)) + { + OnTargetOutOfRange(from, targeted); + } + else + { + if (!from.CanSee(targeted)) + OnCantSeeTarget(from, targeted); + else if (CheckLOS && !from.InLOS(targeted)) + OnTargetOutOfLOS(from, targeted); + else if (item?.InSecureTrade == true) + OnTargetInSecureTrade(from, targeted); + else if (item?.IsAccessibleTo(from) == true) + OnTargetNotAccessible(from, targeted); + else if (item?.CheckTarget(from, this, targeted) == true) + OnTargetUntargetable(from, targeted); + else if (mobile?.CheckTarget(from, this, mobile) != true) + OnTargetUntargetable(from, mobile); + else if (from.Region.OnTarget(from, this, targeted)) + OnTarget(from, targeted); + } - loc = item.GetWorldLocation(); - map = item.Map; - } - else - { - OnTargetCancel( from, TargetCancelType.Canceled ); - OnTargetFinish( from ); - return; - } + OnTargetFinish(from); + } - if ( map == null || map != from.Map || ( Range != -1 && !from.InRange( loc, Range ) ) ) - { - OnTargetOutOfRange( from, targeted ); - } - else - { - if ( !from.CanSee( targeted ) ) - OnCantSeeTarget( from, targeted ); - else if ( CheckLOS && !from.InLOS( targeted ) ) - OnTargetOutOfLOS( from, targeted ); - else if ( item?.InSecureTrade == true ) - OnTargetInSecureTrade( from, targeted ); - else if ( item?.IsAccessibleTo( from ) == true ) - OnTargetNotAccessible( from, targeted ); - else if ( item?.CheckTarget( from, this, targeted ) == true ) - OnTargetUntargetable( from, targeted ); - else if ( mobile?.CheckTarget( from, this, mobile ) != true ) - OnTargetUntargetable( from, mobile ); - else if ( from.Region.OnTarget( from, this, targeted ) ) - OnTarget( from, targeted ); - } + protected virtual void OnTarget(Mobile from, object targeted) + { + } - OnTargetFinish( from ); - } + protected virtual void OnTargetNotAccessible(Mobile from, object targeted) + { + from.SendLocalizedMessage(500447); // That is not accessible. + } - protected virtual void OnTarget( Mobile from, object targeted ) - { - } + protected virtual void OnTargetInSecureTrade(Mobile from, object targeted) + { + from.SendLocalizedMessage(500447); // That is not accessible. + } - protected virtual void OnTargetNotAccessible( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible. - } + protected virtual void OnNonlocalTarget(Mobile from, object targeted) + { + from.SendLocalizedMessage(500447); // That is not accessible. + } - protected virtual void OnTargetInSecureTrade( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible. - } + protected virtual void OnCantSeeTarget(Mobile from, object targeted) + { + from.SendLocalizedMessage(500237); // Target can not be seen. + } - protected virtual void OnNonlocalTarget( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible. - } + protected virtual void OnTargetOutOfLOS(Mobile from, object targeted) + { + from.SendLocalizedMessage(500237); // Target can not be seen. + } - protected virtual void OnCantSeeTarget( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500237 ); // Target can not be seen. - } + protected virtual void OnTargetOutOfRange(Mobile from, object targeted) + { + from.SendLocalizedMessage(500446); // That is too far away. + } - protected virtual void OnTargetOutOfLOS( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500237 ); // Target can not be seen. - } + protected virtual void OnTargetDeleted(Mobile from, object targeted) + { + } - protected virtual void OnTargetOutOfRange( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500446 ); // That is too far away. - } + protected virtual void OnTargetUntargetable(Mobile from, object targeted) + { + from.SendLocalizedMessage(500447); // That is not accessible. + } - protected virtual void OnTargetDeleted( Mobile from, object targeted ) - { - } + protected virtual void OnTargetCancel(Mobile from, TargetCancelType cancelType) + { + } - protected virtual void OnTargetUntargetable( Mobile from, object targeted ) - { - from.SendLocalizedMessage( 500447 ); // That is not accessible. - } + protected virtual void OnTargetFinish(Mobile from) + { + } - protected virtual void OnTargetCancel( Mobile from, TargetCancelType cancelType ) - { - } + private class TimeoutTimer : Timer + { + private static TimeSpan ThirtySeconds = TimeSpan.FromSeconds(30.0); + private static TimeSpan TenSeconds = TimeSpan.FromSeconds(10.0); + private static TimeSpan OneSecond = TimeSpan.FromSeconds(1.0); + private Mobile m_Mobile; + private Target m_Target; - protected virtual void OnTargetFinish( Mobile from ) - { - } + public TimeoutTimer(Target target, Mobile m, TimeSpan delay) : base(delay) + { + m_Target = target; + m_Mobile = m; - public int Range { get; set; } + if (delay >= ThirtySeconds) + Priority = TimerPriority.FiveSeconds; + else if (delay >= TenSeconds) + Priority = TimerPriority.OneSecond; + else if (delay >= OneSecond) + Priority = TimerPriority.TwoFiftyMS; + else + Priority = TimerPriority.TwentyFiveMS; + } - public bool AllowGround { get; set; } - - public TargetFlags Flags { get; set; } - } -} + protected override void OnTick() + { + if (m_Mobile.Target == m_Target) + m_Target.Timeout(m_Mobile); + } + } + } +} \ No newline at end of file diff --git a/Server/Targeting/TargetCancelType.cs b/Server/Targeting/TargetCancelType.cs index 8e436c11d..f906a7fbd 100644 --- a/Server/Targeting/TargetCancelType.cs +++ b/Server/Targeting/TargetCancelType.cs @@ -20,11 +20,11 @@ namespace Server.Targeting { - public enum TargetCancelType - { - Overridden, - Canceled, - Disconnected, - Timeout - } + public enum TargetCancelType + { + Overridden, + Canceled, + Disconnected, + Timeout + } } \ No newline at end of file diff --git a/Server/Targeting/TargetFlags.cs b/Server/Targeting/TargetFlags.cs index eb897d64d..c665b17d5 100644 --- a/Server/Targeting/TargetFlags.cs +++ b/Server/Targeting/TargetFlags.cs @@ -20,10 +20,10 @@ namespace Server.Targeting { - public enum TargetFlags : byte - { - None = 0x00, - Harmful = 0x01, - Beneficial = 0x02, - } + public enum TargetFlags : byte + { + None = 0x00, + Harmful = 0x01, + Beneficial = 0x02 + } } \ No newline at end of file diff --git a/Server/TileData.cs b/Server/TileData.cs index 797b9e17f..ce23abc0c 100644 --- a/Server/TileData.cs +++ b/Server/TileData.cs @@ -24,305 +24,301 @@ using System.Text; namespace Server { - public struct LandData - { - public LandData( string name, TileFlag flags ) - { - Name = name; - Flags = flags; - } + public struct LandData + { + public LandData(string name, TileFlag flags) + { + Name = name; + Flags = flags; + } - public string Name { get; set; } + public string Name{ get; set; } - public TileFlag Flags { get; set; } - } + public TileFlag Flags{ get; set; } + } - public struct ItemData - { - private byte m_Weight; - private byte m_Quality; - private byte m_Quantity; - private byte m_Value; - private byte m_Height; + public struct ItemData + { + private byte m_Weight; + private byte m_Quality; + private byte m_Quantity; + private byte m_Value; + private byte m_Height; - public ItemData( string name, TileFlag flags, int weight, int quality, int quantity, int value, int height ) - { - Name = name; - Flags = flags; - m_Weight = (byte)weight; - m_Quality = (byte)quality; - m_Quantity = (byte)quantity; - m_Value = (byte)value; - m_Height = (byte)height; - } + public ItemData(string name, TileFlag flags, int weight, int quality, int quantity, int value, int height) + { + Name = name; + Flags = flags; + m_Weight = (byte)weight; + m_Quality = (byte)quality; + m_Quantity = (byte)quantity; + m_Value = (byte)value; + m_Height = (byte)height; + } - public string Name { get; set; } + public string Name{ get; set; } - public TileFlag Flags { get; set; } + public TileFlag Flags{ get; set; } - public bool Bridge - { - get => (Flags & TileFlag.Bridge) != 0; - set - { - if ( value ) - Flags |= TileFlag.Bridge; - else - Flags &= ~TileFlag.Bridge; - } - } + public bool Bridge + { + get => (Flags & TileFlag.Bridge) != 0; + set + { + if (value) + Flags |= TileFlag.Bridge; + else + Flags &= ~TileFlag.Bridge; + } + } - public bool Impassable - { - get => (Flags & TileFlag.Impassable) != 0; - set - { - if ( value ) - Flags |= TileFlag.Impassable; - else - Flags &= ~TileFlag.Impassable; - } - } + public bool Impassable + { + get => (Flags & TileFlag.Impassable) != 0; + set + { + if (value) + Flags |= TileFlag.Impassable; + else + Flags &= ~TileFlag.Impassable; + } + } - public bool Surface - { - get => (Flags & TileFlag.Surface) != 0; - set - { - if ( value ) - Flags |= TileFlag.Surface; - else - Flags &= ~TileFlag.Surface; - } - } + public bool Surface + { + get => (Flags & TileFlag.Surface) != 0; + set + { + if (value) + Flags |= TileFlag.Surface; + else + Flags &= ~TileFlag.Surface; + } + } - public int Weight - { - get => m_Weight; - set => m_Weight = (byte)value; - } + public int Weight + { + get => m_Weight; + set => m_Weight = (byte)value; + } - public int Quality - { - get => m_Quality; - set => m_Quality = (byte)value; - } + public int Quality + { + get => m_Quality; + set => m_Quality = (byte)value; + } - public int Quantity - { - get => m_Quantity; - set => m_Quantity = (byte)value; - } + public int Quantity + { + get => m_Quantity; + set => m_Quantity = (byte)value; + } - public int Value - { - get => m_Value; - set => m_Value = (byte)value; - } + public int Value + { + get => m_Value; + set => m_Value = (byte)value; + } - public int Height - { - get => m_Height; - set => m_Height = (byte)value; - } + public int Height + { + get => m_Height; + set => m_Height = (byte)value; + } - public int CalcHeight - { - get - { - if ( (Flags & TileFlag.Bridge) != 0 ) - return m_Height / 2; - return m_Height; - } - } - } + public int CalcHeight + { + get + { + if ((Flags & TileFlag.Bridge) != 0) + return m_Height / 2; + return m_Height; + } + } + } - [Flags] - public enum TileFlag : long - { - None = 0x00000000, - Background = 0x00000001, - Weapon = 0x00000002, - Transparent = 0x00000004, - Translucent = 0x00000008, - Wall = 0x00000010, - Damaging = 0x00000020, - Impassable = 0x00000040, - Wet = 0x00000080, - Unknown1 = 0x00000100, - Surface = 0x00000200, - Bridge = 0x00000400, - Generic = 0x00000800, - Window = 0x00001000, - NoShoot = 0x00002000, - ArticleA = 0x00004000, - ArticleAn = 0x00008000, - Internal = 0x00010000, - Foliage = 0x00020000, - PartialHue = 0x00040000, - Unknown2 = 0x00080000, - Map = 0x00100000, - Container = 0x00200000, - Wearable = 0x00400000, - LightSource = 0x00800000, - Animation = 0x01000000, - NoDiagonal = 0x02000000, - Unknown3 = 0x04000000, - Armor = 0x08000000, - Roof = 0x10000000, - Door = 0x20000000, - StairBack = 0x40000000, - StairRight = 0x80000000 - } + [Flags] + public enum TileFlag : long + { + None = 0x00000000, + Background = 0x00000001, + Weapon = 0x00000002, + Transparent = 0x00000004, + Translucent = 0x00000008, + Wall = 0x00000010, + Damaging = 0x00000020, + Impassable = 0x00000040, + Wet = 0x00000080, + Unknown1 = 0x00000100, + Surface = 0x00000200, + Bridge = 0x00000400, + Generic = 0x00000800, + Window = 0x00001000, + NoShoot = 0x00002000, + ArticleA = 0x00004000, + ArticleAn = 0x00008000, + Internal = 0x00010000, + Foliage = 0x00020000, + PartialHue = 0x00040000, + Unknown2 = 0x00080000, + Map = 0x00100000, + Container = 0x00200000, + Wearable = 0x00400000, + LightSource = 0x00800000, + Animation = 0x01000000, + NoDiagonal = 0x02000000, + Unknown3 = 0x04000000, + Armor = 0x08000000, + Roof = 0x10000000, + Door = 0x20000000, + StairBack = 0x40000000, + StairRight = 0x80000000 + } - public static class TileData - { - public static LandData[] LandTable { get; } + public static class TileData + { + private static byte[] m_StringBuffer = new byte[20]; - public static ItemData[] ItemTable { get; } + static TileData() + { + string filePath = Core.FindDataFile("tiledata.mul"); - public static int MaxLandValue { get; } + if (File.Exists(filePath)) + { + using (FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader bin = new BinaryReader(fs); - public static int MaxItemValue { get; } + if (fs.Length == 3188736) + { + // 7.0.9.0 + LandTable = new LandData[0x4000]; - private static byte[] m_StringBuffer = new byte[20]; + for (int i = 0; i < 0x4000; ++i) + { + if (i == 1 || i > 0 && (i & 0x1F) == 0) bin.ReadInt32(); // header - private static string ReadNameString( BinaryReader bin ) - { - bin.Read( m_StringBuffer, 0, 20 ); + TileFlag flags = (TileFlag)bin.ReadInt64(); + bin.ReadInt16(); // skip 2 bytes -- textureID - int count; + LandTable[i] = new LandData(ReadNameString(bin), flags); + } - for ( count = 0; count < 20 && m_StringBuffer[count] != 0; ++count ); + ItemTable = new ItemData[0x10000]; - return Encoding.ASCII.GetString( m_StringBuffer, 0, count ); - } + for (int i = 0; i < 0x10000; ++i) + { + if ((i & 0x1F) == 0) bin.ReadInt32(); // header - static TileData() - { - string filePath = Core.FindDataFile( "tiledata.mul" ); + TileFlag flags = (TileFlag)bin.ReadInt64(); + int weight = bin.ReadByte(); + int quality = bin.ReadByte(); + bin.ReadInt16(); + bin.ReadByte(); + int quantity = bin.ReadByte(); + bin.ReadInt32(); + bin.ReadByte(); + int value = bin.ReadByte(); + int height = bin.ReadByte(); - if ( File.Exists( filePath ) ) - { - using ( FileStream fs = new FileStream( filePath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - BinaryReader bin = new BinaryReader( fs ); + ItemTable[i] = new ItemData(ReadNameString(bin), flags, weight, quality, quantity, value, + height); + } + } + else + { + LandTable = new LandData[0x4000]; - if ( fs.Length == 3188736 ) { // 7.0.9.0 - LandTable = new LandData[0x4000]; + for (int i = 0; i < 0x4000; ++i) + { + if ((i & 0x1F) == 0) bin.ReadInt32(); // header - for ( int i = 0; i < 0x4000; ++i ) - { - if ( i == 1 || ( i > 0 && (i & 0x1F) == 0 ) ) - { - bin.ReadInt32(); // header - } + TileFlag flags = (TileFlag)bin.ReadInt32(); + bin.ReadInt16(); // skip 2 bytes -- textureID - TileFlag flags = (TileFlag)bin.ReadInt64(); - bin.ReadInt16(); // skip 2 bytes -- textureID + LandTable[i] = new LandData(ReadNameString(bin), flags); + } - LandTable[i] = new LandData( ReadNameString( bin ), flags ); - } + if (fs.Length == 1644544) + { + // 7.0.0.0 + ItemTable = new ItemData[0x8000]; - ItemTable = new ItemData[0x10000]; + for (int i = 0; i < 0x8000; ++i) + { + if ((i & 0x1F) == 0) bin.ReadInt32(); // header - for ( int i = 0; i < 0x10000; ++i ) - { - if ( (i & 0x1F) == 0 ) - { - bin.ReadInt32(); // header - } + TileFlag flags = (TileFlag)bin.ReadInt32(); + int weight = bin.ReadByte(); + int quality = bin.ReadByte(); + bin.ReadInt16(); + bin.ReadByte(); + int quantity = bin.ReadByte(); + bin.ReadInt32(); + bin.ReadByte(); + int value = bin.ReadByte(); + int height = bin.ReadByte(); - TileFlag flags = (TileFlag)bin.ReadInt64(); - int weight = bin.ReadByte(); - int quality = bin.ReadByte(); - bin.ReadInt16(); - bin.ReadByte(); - int quantity = bin.ReadByte(); - bin.ReadInt32(); - bin.ReadByte(); - int value = bin.ReadByte(); - int height = bin.ReadByte(); + ItemTable[i] = new ItemData(ReadNameString(bin), flags, weight, quality, quantity, value, + height); + } + } + else + { + ItemTable = new ItemData[0x4000]; - ItemTable[i] = new ItemData( ReadNameString( bin ), flags, weight, quality, quantity, value, height ); - } - } else { - LandTable = new LandData[0x4000]; + for (int i = 0; i < 0x4000; ++i) + { + if ((i & 0x1F) == 0) bin.ReadInt32(); // header - for ( int i = 0; i < 0x4000; ++i ) - { - if ( (i & 0x1F) == 0 ) - { - bin.ReadInt32(); // header - } + TileFlag flags = (TileFlag)bin.ReadInt32(); + int weight = bin.ReadByte(); + int quality = bin.ReadByte(); + bin.ReadInt16(); + bin.ReadByte(); + int quantity = bin.ReadByte(); + bin.ReadInt32(); + bin.ReadByte(); + int value = bin.ReadByte(); + int height = bin.ReadByte(); - TileFlag flags = (TileFlag)bin.ReadInt32(); - bin.ReadInt16(); // skip 2 bytes -- textureID + ItemTable[i] = new ItemData(ReadNameString(bin), flags, weight, quality, quantity, value, + height); + } + } + } + } - LandTable[i] = new LandData( ReadNameString( bin ), flags ); - } + MaxLandValue = LandTable.Length - 1; + MaxItemValue = ItemTable.Length - 1; + } + else + { + Console.WriteLine("tiledata.mul was not found"); + Console.WriteLine("Make sure your Scripts/Misc/DataPath.cs is properly configured"); + Console.WriteLine("After pressing return an exception will be thrown and the server will terminate"); - if ( fs.Length == 1644544 ) { // 7.0.0.0 - ItemTable = new ItemData[0x8000]; + throw new Exception($"TileData: {filePath} not found"); + } + } - for ( int i = 0; i < 0x8000; ++i ) - { - if ( (i & 0x1F) == 0 ) - { - bin.ReadInt32(); // header - } + public static LandData[] LandTable{ get; } - TileFlag flags = (TileFlag)bin.ReadInt32(); - int weight = bin.ReadByte(); - int quality = bin.ReadByte(); - bin.ReadInt16(); - bin.ReadByte(); - int quantity = bin.ReadByte(); - bin.ReadInt32(); - bin.ReadByte(); - int value = bin.ReadByte(); - int height = bin.ReadByte(); + public static ItemData[] ItemTable{ get; } - ItemTable[i] = new ItemData( ReadNameString( bin ), flags, weight, quality, quantity, value, height ); - } - } else { - ItemTable = new ItemData[0x4000]; + public static int MaxLandValue{ get; } - for ( int i = 0; i < 0x4000; ++i ) - { - if ( (i & 0x1F) == 0 ) - { - bin.ReadInt32(); // header - } + public static int MaxItemValue{ get; } - TileFlag flags = (TileFlag)bin.ReadInt32(); - int weight = bin.ReadByte(); - int quality = bin.ReadByte(); - bin.ReadInt16(); - bin.ReadByte(); - int quantity = bin.ReadByte(); - bin.ReadInt32(); - bin.ReadByte(); - int value = bin.ReadByte(); - int height = bin.ReadByte(); + private static string ReadNameString(BinaryReader bin) + { + bin.Read(m_StringBuffer, 0, 20); - ItemTable[i] = new ItemData( ReadNameString( bin ), flags, weight, quality, quantity, value, height ); - } - } - } - } + int count; - MaxLandValue = LandTable.Length - 1; - MaxItemValue = ItemTable.Length - 1; - } - else - { - Console.WriteLine( "tiledata.mul was not found" ); - Console.WriteLine( "Make sure your Scripts/Misc/DataPath.cs is properly configured" ); - Console.WriteLine( "After pressing return an exception will be thrown and the server will terminate" ); + for (count = 0; count < 20 && m_StringBuffer[count] != 0; ++count) ; - throw new Exception($"TileData: {filePath} not found"); - } - } - } -} + return Encoding.ASCII.GetString(m_StringBuffer, 0, count); + } + } +} \ No newline at end of file diff --git a/Server/TileList.cs b/Server/TileList.cs index ff0f5a5c3..1097c3c37 100644 --- a/Server/TileList.cs +++ b/Server/TileList.cs @@ -20,64 +20,63 @@ namespace Server { - public class TileList - { - private StaticTile[] m_Tiles; + public class TileList + { + private static StaticTile[] m_EmptyTiles = new StaticTile[0]; + private StaticTile[] m_Tiles; - public TileList() - { - m_Tiles = new StaticTile[8]; - Count = 0; - } + public TileList() + { + m_Tiles = new StaticTile[8]; + Count = 0; + } - public int Count { get; private set; } + public int Count{ get; private set; } - public void AddRange( StaticTile[] tiles ) - { - if ( (Count + tiles.Length) > m_Tiles.Length ) - { - StaticTile[] old = m_Tiles; - m_Tiles = new StaticTile[(Count + tiles.Length) * 2]; + public void AddRange(StaticTile[] tiles) + { + if (Count + tiles.Length > m_Tiles.Length) + { + StaticTile[] old = m_Tiles; + m_Tiles = new StaticTile[(Count + tiles.Length) * 2]; - for ( int i = 0; i < old.Length; ++i ) - m_Tiles[i] = old[i]; - } + for (int i = 0; i < old.Length; ++i) + m_Tiles[i] = old[i]; + } - for ( int i = 0; i < tiles.Length; ++i ) - m_Tiles[Count++] = tiles[i]; - } + for (int i = 0; i < tiles.Length; ++i) + m_Tiles[Count++] = tiles[i]; + } - public void Add( ushort id, sbyte z ) - { - if ( (Count + 1) > m_Tiles.Length ) - { - StaticTile[] old = m_Tiles; - m_Tiles = new StaticTile[old.Length * 2]; + public void Add(ushort id, sbyte z) + { + if (Count + 1 > m_Tiles.Length) + { + StaticTile[] old = m_Tiles; + m_Tiles = new StaticTile[old.Length * 2]; - for ( int i = 0; i < old.Length; ++i ) - m_Tiles[i] = old[i]; - } + for (int i = 0; i < old.Length; ++i) + m_Tiles[i] = old[i]; + } - m_Tiles[Count].m_ID = id; - m_Tiles[Count].m_Z = z; - ++Count; - } + m_Tiles[Count].m_ID = id; + m_Tiles[Count].m_Z = z; + ++Count; + } - private static StaticTile[] m_EmptyTiles = new StaticTile[0]; + public StaticTile[] ToArray() + { + if (Count == 0) + return m_EmptyTiles; - public StaticTile[] ToArray() - { - if ( Count == 0 ) - return m_EmptyTiles; + StaticTile[] tiles = new StaticTile[Count]; - StaticTile[] tiles = new StaticTile[Count]; + for (int i = 0; i < Count; ++i) + tiles[i] = m_Tiles[i]; - for ( int i = 0; i < Count; ++i ) - tiles[i] = m_Tiles[i]; + Count = 0; - Count = 0; - - return tiles; - } - } + return tiles; + } + } } \ No newline at end of file diff --git a/Server/TileMatrix.cs b/Server/TileMatrix.cs index 50f1b948c..f96ff514a 100644 --- a/Server/TileMatrix.cs +++ b/Server/TileMatrix.cs @@ -21,705 +21,700 @@ using System; using System.Collections.Generic; using System.IO; -using System.Runtime.InteropServices; using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; namespace Server { - public class TileMatrix - { - private StaticTile[][][][][] m_StaticTiles; - private LandTile[][][] m_LandTiles; - - private LandTile[] m_InvalidLandBlock; + public class TileMatrix + { + private static List m_Instances = new List(); - private UOPIndex m_MapIndex; - - private int m_FileIndex; - private int m_Width, m_Height; - - private Map m_Owner; - - private int[][] m_StaticPatches; - private int[][] m_LandPatches; - - /*public Map Owner - { - get - { - return m_Owner; - } - }*/ - - public TileMatrixPatch Patch { get; } + private int m_FileIndex; + private List m_FileShare = new List(); - public int BlockWidth { get; } + private LandTile[] m_InvalidLandBlock; + private int[][] m_LandPatches; + private LandTile[][][] m_LandTiles; - public int BlockHeight { get; } + private TileList[][] m_Lists; - /*public int Width - { - get - { - return m_Width; - } - } + private UOPIndex m_MapIndex; + private DateTime m_NextLandWarning; + + private DateTime m_NextStaticWarning; + + private Map m_Owner; + + private int[][] m_StaticPatches; + private StaticTile[][][][][] m_StaticTiles; - public int Height - { - get - { - return m_Height; - } - }*/ + private StaticTile[] m_TileBuffer = new StaticTile[128]; - public FileStream MapStream { get; set; } + private TileList m_TilesList = new TileList(); + private int m_Width, m_Height; - /*public bool MapUOPPacked - { - get{ return ( m_MapIndex != null ); } - }*/ + public TileMatrix(Map owner, int fileIndex, int mapID, int width, int height) + { + lock (m_Instances) + { + for (int i = 0; i < m_Instances.Count; ++i) + { + TileMatrix tm = m_Instances[i]; + + if (tm.m_FileIndex == fileIndex) + lock (m_FileShare) + { + lock (tm.m_FileShare) + { + tm.m_FileShare.Add(this); + m_FileShare.Add(tm); + } + } + } + + m_Instances.Add(this); + } - public FileStream IndexStream { get; set; } + m_FileIndex = fileIndex; + m_Width = width; + m_Height = height; + BlockWidth = width >> 3; + BlockHeight = height >> 3; - public FileStream DataStream { get; set; } + m_Owner = owner; - public BinaryReader IndexReader { get; set; } + if (fileIndex != 0x7F) + { + string mapPath = Core.FindDataFile("map{0}.mul", fileIndex); - public bool Exists => ( MapStream != null && IndexStream != null && DataStream != null ); + if (File.Exists(mapPath)) + { + MapStream = new FileStream(mapPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); + } + else + { + mapPath = Core.FindDataFile("map{0}LegacyMUL.uop", fileIndex); - private static List m_Instances = new List(); - private List m_FileShare = new List(); + if (File.Exists(mapPath)) + { + MapStream = new FileStream(mapPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); + m_MapIndex = new UOPIndex(MapStream); + } + } - public TileMatrix( Map owner, int fileIndex, int mapID, int width, int height ) - { - lock (m_Instances) { - for ( int i = 0; i < m_Instances.Count; ++i ) - { - TileMatrix tm = m_Instances[i]; + string indexPath = Core.FindDataFile("staidx{0}.mul", fileIndex); - if ( tm.m_FileIndex == fileIndex ) - { - lock (m_FileShare) { - lock (tm.m_FileShare) { - tm.m_FileShare.Add( this ); - m_FileShare.Add( tm ); - } - } - } - } + if (File.Exists(indexPath)) + { + IndexStream = new FileStream(indexPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); + IndexReader = new BinaryReader(IndexStream); + } - m_Instances.Add( this ); - } + string staticsPath = Core.FindDataFile("statics{0}.mul", fileIndex); - m_FileIndex = fileIndex; - m_Width = width; - m_Height = height; - BlockWidth = width >> 3; - BlockHeight = height >> 3; + if (File.Exists(staticsPath)) + DataStream = new FileStream(staticsPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite); + } - m_Owner = owner; + EmptyStaticBlock = new StaticTile[8][][]; - if ( fileIndex != 0x7F ) - { - string mapPath = Core.FindDataFile( "map{0}.mul", fileIndex ); + for (int i = 0; i < 8; ++i) + { + EmptyStaticBlock[i] = new StaticTile[8][]; - if ( File.Exists( mapPath ) ) - { - MapStream = new FileStream( mapPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite ); - } - else - { - mapPath = Core.FindDataFile( "map{0}LegacyMUL.uop", fileIndex ); + for (int j = 0; j < 8; ++j) + EmptyStaticBlock[i][j] = new StaticTile[0]; + } - if ( File.Exists( mapPath ) ) - { - MapStream = new FileStream( mapPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite ); - m_MapIndex = new UOPIndex( MapStream ); - } - } + m_InvalidLandBlock = new LandTile[196]; - string indexPath = Core.FindDataFile( "staidx{0}.mul", fileIndex ); - - if ( File.Exists( indexPath ) ) - { - IndexStream = new FileStream( indexPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite ); - IndexReader = new BinaryReader( IndexStream ); - } + m_LandTiles = new LandTile[BlockWidth][][]; + m_StaticTiles = new StaticTile[BlockWidth][][][][]; + m_StaticPatches = new int[BlockWidth][]; + m_LandPatches = new int[BlockWidth][]; - string staticsPath = Core.FindDataFile( "statics{0}.mul", fileIndex ); + Patch = new TileMatrixPatch(this, mapID); + } - if ( File.Exists( staticsPath ) ) - DataStream = new FileStream( staticsPath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite ); - } + /*public Map Owner + { + get + { + return m_Owner; + } + }*/ + + public TileMatrixPatch Patch{ get; } + + public int BlockWidth{ get; } + + public int BlockHeight{ get; } + + /*public int Width + { + get + { + return m_Width; + } + } + + public int Height + { + get + { + return m_Height; + } + }*/ - EmptyStaticBlock = new StaticTile[8][][]; + public FileStream MapStream{ get; set; } - for ( int i = 0; i < 8; ++i ) - { - EmptyStaticBlock[i] = new StaticTile[8][]; - - for ( int j = 0; j < 8; ++j ) - EmptyStaticBlock[i][j] = new StaticTile[0]; - } + /*public bool MapUOPPacked + { + get{ return ( m_MapIndex != null ); } + }*/ - m_InvalidLandBlock = new LandTile[196]; + public FileStream IndexStream{ get; set; } - m_LandTiles = new LandTile[BlockWidth][][]; - m_StaticTiles = new StaticTile[BlockWidth][][][][]; - m_StaticPatches = new int[BlockWidth][]; - m_LandPatches = new int[BlockWidth][]; + public FileStream DataStream{ get; set; } - Patch = new TileMatrixPatch( this, mapID ); - } + public BinaryReader IndexReader{ get; set; } - public StaticTile[][][] EmptyStaticBlock { get; } + public bool Exists => MapStream != null && IndexStream != null && DataStream != null; - [MethodImpl(MethodImplOptions.Synchronized)] - public void SetStaticBlock( int x, int y, StaticTile[][][] value ) - { - if ( x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight ) - return; + public StaticTile[][][] EmptyStaticBlock{ get; } - if ( m_StaticTiles[x] == null ) - m_StaticTiles[x] = new StaticTile[BlockHeight][][][]; + [MethodImpl(MethodImplOptions.Synchronized)] + public void SetStaticBlock(int x, int y, StaticTile[][][] value) + { + if (x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight) + return; - m_StaticTiles[x][y] = value; + if (m_StaticTiles[x] == null) + m_StaticTiles[x] = new StaticTile[BlockHeight][][][]; - if ( m_StaticPatches[x] == null ) - m_StaticPatches[x] = new int[(BlockHeight + 31) >> 5]; + m_StaticTiles[x][y] = value; - m_StaticPatches[x][y >> 5] |= 1 << (y & 0x1F); - } + if (m_StaticPatches[x] == null) + m_StaticPatches[x] = new int[(BlockHeight + 31) >> 5]; - [MethodImpl(MethodImplOptions.Synchronized)] - public StaticTile[][][] GetStaticBlock( int x, int y ) - { - if ( x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight || DataStream == null || IndexStream == null ) - return EmptyStaticBlock; + m_StaticPatches[x][y >> 5] |= 1 << (y & 0x1F); + } - if ( m_StaticTiles[x] == null ) - m_StaticTiles[x] = new StaticTile[BlockHeight][][][]; + [MethodImpl(MethodImplOptions.Synchronized)] + public StaticTile[][][] GetStaticBlock(int x, int y) + { + if (x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight || DataStream == null || IndexStream == null) + return EmptyStaticBlock; - StaticTile[][][] tiles = m_StaticTiles[x][y]; + if (m_StaticTiles[x] == null) + m_StaticTiles[x] = new StaticTile[BlockHeight][][][]; - if ( tiles == null ) - { - lock (m_FileShare) { - for ( int i = 0; tiles == null && i < m_FileShare.Count; ++i ) - { - TileMatrix shared = m_FileShare[i]; + StaticTile[][][] tiles = m_StaticTiles[x][y]; - lock (shared) { - if ( x >= 0 && x < shared.BlockWidth && y >= 0 && y < shared.BlockHeight ) - { - StaticTile[][][][] theirTiles = shared.m_StaticTiles[x]; + if (tiles == null) + { + lock (m_FileShare) + { + for (int i = 0; tiles == null && i < m_FileShare.Count; ++i) + { + TileMatrix shared = m_FileShare[i]; - if ( theirTiles != null ) - tiles = theirTiles[y]; + lock (shared) + { + if (x >= 0 && x < shared.BlockWidth && y >= 0 && y < shared.BlockHeight) + { + StaticTile[][][][] theirTiles = shared.m_StaticTiles[x]; - if ( tiles != null ) - { - int[] theirBits = shared.m_StaticPatches[x]; + if (theirTiles != null) + tiles = theirTiles[y]; - if ( theirBits != null && (theirBits[y >> 5] & (1 << (y & 0x1F))) != 0 ) - tiles = null; - } - } - } - } - } + if (tiles != null) + { + int[] theirBits = shared.m_StaticPatches[x]; - if ( tiles == null ) - tiles = ReadStaticBlock( x, y ); + if (theirBits != null && (theirBits[y >> 5] & (1 << (y & 0x1F))) != 0) + tiles = null; + } + } + } + } + } - m_StaticTiles[x][y] = tiles; - } + if (tiles == null) + tiles = ReadStaticBlock(x, y); - return tiles; - } + m_StaticTiles[x][y] = tiles; + } - public StaticTile[] GetStaticTiles( int x, int y ) - { - StaticTile[][][] tiles = GetStaticBlock( x >> 3, y >> 3 ); + return tiles; + } - return tiles[x & 0x7][y & 0x7]; - } + public StaticTile[] GetStaticTiles(int x, int y) + { + StaticTile[][][] tiles = GetStaticBlock(x >> 3, y >> 3); - private TileList m_TilesList = new TileList(); + return tiles[x & 0x7][y & 0x7]; + } - [MethodImpl(MethodImplOptions.Synchronized)] - public StaticTile[] GetStaticTiles( int x, int y, bool multis ) - { - StaticTile[][][] tiles = GetStaticBlock( x >> 3, y >> 3 ); + [MethodImpl(MethodImplOptions.Synchronized)] + public StaticTile[] GetStaticTiles(int x, int y, bool multis) + { + StaticTile[][][] tiles = GetStaticBlock(x >> 3, y >> 3); - if ( multis ) - { - IPooledEnumerable eable = m_Owner.GetMultiTilesAt( x, y ); + if (multis) + { + IPooledEnumerable eable = m_Owner.GetMultiTilesAt(x, y); - if ( eable == Map.NullEnumerable.Instance ) - return tiles[x & 0x7][y & 0x7]; + if (eable == Map.NullEnumerable.Instance) + return tiles[x & 0x7][y & 0x7]; - bool any = false; + bool any = false; - foreach ( StaticTile[] multiTiles in eable ) - { - if ( !any ) - any = true; + foreach (StaticTile[] multiTiles in eable) + { + if (!any) + any = true; - m_TilesList.AddRange( multiTiles ); - } + m_TilesList.AddRange(multiTiles); + } - eable.Free(); + eable.Free(); - if ( !any ) - return tiles[x & 0x7][y & 0x7]; + if (!any) + return tiles[x & 0x7][y & 0x7]; - m_TilesList.AddRange( tiles[x & 0x7][y & 0x7] ); + m_TilesList.AddRange(tiles[x & 0x7][y & 0x7]); - return m_TilesList.ToArray(); - } + return m_TilesList.ToArray(); + } - return tiles[x & 0x7][y & 0x7]; - } + return tiles[x & 0x7][y & 0x7]; + } - [MethodImpl(MethodImplOptions.Synchronized)] - public void SetLandBlock( int x, int y, LandTile[] value ) - { - if ( x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight ) - return; + [MethodImpl(MethodImplOptions.Synchronized)] + public void SetLandBlock(int x, int y, LandTile[] value) + { + if (x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight) + return; - if ( m_LandTiles[x] == null ) - m_LandTiles[x] = new LandTile[BlockHeight][]; + if (m_LandTiles[x] == null) + m_LandTiles[x] = new LandTile[BlockHeight][]; - m_LandTiles[x][y] = value; + m_LandTiles[x][y] = value; - if ( m_LandPatches[x] == null ) - m_LandPatches[x] = new int[(BlockHeight + 31) >> 5]; + if (m_LandPatches[x] == null) + m_LandPatches[x] = new int[(BlockHeight + 31) >> 5]; - m_LandPatches[x][y >> 5] |= 1 << (y & 0x1F); - } + m_LandPatches[x][y >> 5] |= 1 << (y & 0x1F); + } - [MethodImpl(MethodImplOptions.Synchronized)] - public LandTile[] GetLandBlock( int x, int y ) - { - if ( x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight || MapStream == null ) - return m_InvalidLandBlock; + [MethodImpl(MethodImplOptions.Synchronized)] + public LandTile[] GetLandBlock(int x, int y) + { + if (x < 0 || y < 0 || x >= BlockWidth || y >= BlockHeight || MapStream == null) + return m_InvalidLandBlock; - if ( m_LandTiles[x] == null ) - m_LandTiles[x] = new LandTile[BlockHeight][]; + if (m_LandTiles[x] == null) + m_LandTiles[x] = new LandTile[BlockHeight][]; - LandTile[] tiles = m_LandTiles[x][y]; + LandTile[] tiles = m_LandTiles[x][y]; - if ( tiles == null ) - { - lock (m_FileShare) { - for ( int i = 0; tiles == null && i < m_FileShare.Count; ++i ) - { - TileMatrix shared = m_FileShare[i]; + if (tiles == null) + { + lock (m_FileShare) + { + for (int i = 0; tiles == null && i < m_FileShare.Count; ++i) + { + TileMatrix shared = m_FileShare[i]; - lock (shared) { - if ( x >= 0 && x < shared.BlockWidth && y >= 0 && y < shared.BlockHeight ) - { - LandTile[][] theirTiles = shared.m_LandTiles[x]; + lock (shared) + { + if (x >= 0 && x < shared.BlockWidth && y >= 0 && y < shared.BlockHeight) + { + LandTile[][] theirTiles = shared.m_LandTiles[x]; - if ( theirTiles != null ) - tiles = theirTiles[y]; + if (theirTiles != null) + tiles = theirTiles[y]; - if ( tiles != null ) - { - int[] theirBits = shared.m_LandPatches[x]; + if (tiles != null) + { + int[] theirBits = shared.m_LandPatches[x]; - if ( theirBits != null && (theirBits[y >> 5] & (1 << (y & 0x1F))) != 0 ) - tiles = null; - } - } - } - } - } + if (theirBits != null && (theirBits[y >> 5] & (1 << (y & 0x1F))) != 0) + tiles = null; + } + } + } + } + } - if ( tiles == null ) - tiles = ReadLandBlock( x, y ); + if (tiles == null) + tiles = ReadLandBlock(x, y); - m_LandTiles[x][y] = tiles; - } + m_LandTiles[x][y] = tiles; + } - return tiles; - } + return tiles; + } - public LandTile GetLandTile( int x, int y ) - { - LandTile[] tiles = GetLandBlock( x >> 3, y >> 3 ); + public LandTile GetLandTile(int x, int y) + { + LandTile[] tiles = GetLandBlock(x >> 3, y >> 3); - return tiles[((y & 0x7) << 3) + (x & 0x7)]; - } + return tiles[((y & 0x7) << 3) + (x & 0x7)]; + } - private TileList[][] m_Lists; + [MethodImpl(MethodImplOptions.Synchronized)] + private unsafe StaticTile[][][] ReadStaticBlock(int x, int y) + { + try + { + IndexReader.BaseStream.Seek((x * BlockHeight + y) * 12, SeekOrigin.Begin); - private StaticTile[] m_TileBuffer = new StaticTile[128]; + int lookup = IndexReader.ReadInt32(); + int length = IndexReader.ReadInt32(); - [MethodImpl(MethodImplOptions.Synchronized)] - private unsafe StaticTile[][][] ReadStaticBlock( int x, int y ) - { - try - { - IndexReader.BaseStream.Seek( ((x * BlockHeight) + y) * 12, SeekOrigin.Begin ); + if (lookup < 0 || length <= 0) return EmptyStaticBlock; - int lookup = IndexReader.ReadInt32(); - int length = IndexReader.ReadInt32(); + int count = length / 7; - if ( lookup < 0 || length <= 0 ) - { - return EmptyStaticBlock; - } + DataStream.Seek(lookup, SeekOrigin.Begin); - int count = length / 7; + if (m_TileBuffer.Length < count) + m_TileBuffer = new StaticTile[count]; - DataStream.Seek( lookup, SeekOrigin.Begin ); + StaticTile[] staTiles = m_TileBuffer; //new StaticTile[tileCount]; - if ( m_TileBuffer.Length < count ) - m_TileBuffer = new StaticTile[count]; - - StaticTile[] staTiles = m_TileBuffer;//new StaticTile[tileCount]; - - fixed ( StaticTile *pTiles = staTiles ) - { + fixed (StaticTile* pTiles = staTiles) + { #if !MONO - NativeReader.Read( DataStream.SafeFileHandle.DangerousGetHandle(), pTiles, length ); + NativeReader.Read(DataStream.SafeFileHandle.DangerousGetHandle(), pTiles, length); #else NativeReader.Read( m_Statics.Handle, pTiles, length ); #endif - if ( m_Lists == null ) - { - m_Lists = new TileList[8][]; + if (m_Lists == null) + { + m_Lists = new TileList[8][]; - for ( int i = 0; i < 8; ++i ) - { - m_Lists[i] = new TileList[8]; + for (int i = 0; i < 8; ++i) + { + m_Lists[i] = new TileList[8]; - for ( int j = 0; j < 8; ++j ) - m_Lists[i][j] = new TileList(); - } - } + for (int j = 0; j < 8; ++j) + m_Lists[i][j] = new TileList(); + } + } - TileList[][] lists = m_Lists; + TileList[][] lists = m_Lists; - StaticTile *pCur = pTiles, pEnd = pTiles + count; + StaticTile* pCur = pTiles, pEnd = pTiles + count; - while ( pCur < pEnd ) - { - lists[pCur->m_X & 0x7][pCur->m_Y & 0x7].Add( pCur->m_ID, pCur->m_Z ); - pCur = pCur + 1; - } + while (pCur < pEnd) + { + lists[pCur->m_X & 0x7][pCur->m_Y & 0x7].Add(pCur->m_ID, pCur->m_Z); + pCur = pCur + 1; + } - StaticTile[][][] tiles = new StaticTile[8][][]; + StaticTile[][][] tiles = new StaticTile[8][][]; - for ( int i = 0; i < 8; ++i ) - { - tiles[i] = new StaticTile[8][]; + for (int i = 0; i < 8; ++i) + { + tiles[i] = new StaticTile[8][]; - for ( int j = 0; j < 8; ++j ) - tiles[i][j] = lists[i][j].ToArray(); - } + for (int j = 0; j < 8; ++j) + tiles[i][j] = lists[i][j].ToArray(); + } - return tiles; - } - } - catch ( EndOfStreamException ) - { - if ( DateTime.UtcNow >= m_NextStaticWarning ) - { - Console.WriteLine( "Warning: Static EOS for {0} ({1}, {2})", m_Owner, x, y ); - m_NextStaticWarning = DateTime.UtcNow + TimeSpan.FromMinutes( 1.0 ); - } + return tiles; + } + } + catch (EndOfStreamException) + { + if (DateTime.UtcNow >= m_NextStaticWarning) + { + Console.WriteLine("Warning: Static EOS for {0} ({1}, {2})", m_Owner, x, y); + m_NextStaticWarning = DateTime.UtcNow + TimeSpan.FromMinutes(1.0); + } - return EmptyStaticBlock; - } - } + return EmptyStaticBlock; + } + } - private DateTime m_NextStaticWarning; - private DateTime m_NextLandWarning; + public void Force() + { + if (ScriptCompiler.Assemblies == null || ScriptCompiler.Assemblies.Length == 0) + throw new Exception(); + } - public void Force() - { - if ( ScriptCompiler.Assemblies == null || ScriptCompiler.Assemblies.Length == 0 ) - throw new Exception(); - } + [MethodImpl(MethodImplOptions.Synchronized)] + private unsafe LandTile[] ReadLandBlock(int x, int y) + { + try + { + int offset = (x * BlockHeight + y) * 196 + 4; - [MethodImpl(MethodImplOptions.Synchronized)] - private unsafe LandTile[] ReadLandBlock( int x, int y ) - { - try - { - int offset = ((x * BlockHeight) + y) * 196 + 4; + if (m_MapIndex != null) + offset = m_MapIndex.Lookup(offset); - if ( m_MapIndex != null ) - offset = m_MapIndex.Lookup( offset ); + MapStream.Seek(offset, SeekOrigin.Begin); - MapStream.Seek( offset, SeekOrigin.Begin ); + LandTile[] tiles = new LandTile[64]; - LandTile[] tiles = new LandTile[64]; - - fixed ( LandTile *pTiles = tiles ) - { + fixed (LandTile* pTiles = tiles) + { #if !MONO - NativeReader.Read( MapStream.SafeFileHandle.DangerousGetHandle(), pTiles, 192 ); + NativeReader.Read(MapStream.SafeFileHandle.DangerousGetHandle(), pTiles, 192); #else NativeReader.Read( m_Map.Handle, pTiles, 192 ); #endif - } + } - return tiles; - } - catch - { - if ( DateTime.UtcNow >= m_NextLandWarning ) - { - Console.WriteLine( "Warning: Land EOS for {0} ({1}, {2})", m_Owner, x, y ); - m_NextLandWarning = DateTime.UtcNow + TimeSpan.FromMinutes( 1.0 ); - } + return tiles; + } + catch + { + if (DateTime.UtcNow >= m_NextLandWarning) + { + Console.WriteLine("Warning: Land EOS for {0} ({1}, {2})", m_Owner, x, y); + m_NextLandWarning = DateTime.UtcNow + TimeSpan.FromMinutes(1.0); + } - return m_InvalidLandBlock; - } - } + return m_InvalidLandBlock; + } + } - public void Dispose() - { - if ( m_MapIndex != null ) - m_MapIndex.Close(); - else - { - MapStream?.Close(); - } + public void Dispose() + { + if (m_MapIndex != null) + m_MapIndex.Close(); + else + MapStream?.Close(); - DataStream?.Close(); + DataStream?.Close(); - IndexReader?.Close(); - } - } + IndexReader?.Close(); + } + } - [StructLayout(LayoutKind.Sequential, Pack=1)] - public struct LandTile - { - internal short m_ID; - internal sbyte m_Z; + [StructLayout(LayoutKind.Sequential, Pack = 1)] + public struct LandTile + { + internal short m_ID; + internal sbyte m_Z; - public int ID => m_ID; + public int ID => m_ID; - public int Z - { - get => m_Z; - set => m_Z = (sbyte)value; - } + public int Z + { + get => m_Z; + set => m_Z = (sbyte)value; + } - public int Height => 0; + public int Height => 0; - public bool Ignored => ( m_ID == 2 || m_ID == 0x1DB || ( m_ID >= 0x1AE && m_ID <= 0x1B5 ) ); + public bool Ignored => m_ID == 2 || m_ID == 0x1DB || m_ID >= 0x1AE && m_ID <= 0x1B5; - public LandTile( short id, sbyte z ) - { - m_ID = id; - m_Z = z; - } + public LandTile(short id, sbyte z) + { + m_ID = id; + m_Z = z; + } - public void Set( short id, sbyte z ) - { - m_ID = id; - m_Z = z; - } - } + public void Set(short id, sbyte z) + { + m_ID = id; + m_Z = z; + } + } - [StructLayout(LayoutKind.Sequential, Pack=1)] - public struct StaticTile - { - internal ushort m_ID; - internal byte m_X; - internal byte m_Y; - internal sbyte m_Z; - internal short m_Hue; + [StructLayout(LayoutKind.Sequential, Pack = 1)] + public struct StaticTile + { + internal ushort m_ID; + internal byte m_X; + internal byte m_Y; + internal sbyte m_Z; + internal short m_Hue; - public int ID => m_ID; + public int ID => m_ID; - public int X - { - get => m_X; - set => m_X = (byte)value; - } + public int X + { + get => m_X; + set => m_X = (byte)value; + } - public int Y - { - get => m_Y; - set => m_Y = (byte)value; - } + public int Y + { + get => m_Y; + set => m_Y = (byte)value; + } - public int Z - { - get => m_Z; - set => m_Z = (sbyte)value; - } + public int Z + { + get => m_Z; + set => m_Z = (sbyte)value; + } - public int Hue - { - get => m_Hue; - set => m_Hue = (short)value; - } + public int Hue + { + get => m_Hue; + set => m_Hue = (short)value; + } - public int Height => TileData.ItemTable[m_ID & TileData.MaxItemValue].Height; + public int Height => TileData.ItemTable[m_ID & TileData.MaxItemValue].Height; - public StaticTile( ushort id, sbyte z ) - { - m_ID = id; - m_Z = z; + public StaticTile(ushort id, sbyte z) + { + m_ID = id; + m_Z = z; - m_X = 0; - m_Y = 0; - m_Hue = 0; - } + m_X = 0; + m_Y = 0; + m_Hue = 0; + } - public StaticTile( ushort id, byte x, byte y, sbyte z, short hue ) - { - m_ID = id; - m_X = x; - m_Y = y; - m_Z = z; - m_Hue = hue; - } + public StaticTile(ushort id, byte x, byte y, sbyte z, short hue) + { + m_ID = id; + m_X = x; + m_Y = y; + m_Z = z; + m_Hue = hue; + } - public void Set( ushort id, sbyte z ) - { - m_ID = id; - m_Z = z; - } + public void Set(ushort id, sbyte z) + { + m_ID = id; + m_Z = z; + } - public void Set( ushort id, byte x, byte y, sbyte z, short hue ) - { - m_ID = id; - m_X = x; - m_Y = y; - m_Z = z; - m_Hue = hue; - } - } + public void Set(ushort id, byte x, byte y, sbyte z, short hue) + { + m_ID = id; + m_X = x; + m_Y = y; + m_Z = z; + m_Hue = hue; + } + } - public class UOPIndex - { - private class UOPEntry : IComparable - { - public int m_Offset; - public int m_Length; - public int m_Order; + public class UOPIndex + { + private UOPEntry[] m_Entries; + private int m_Length; - public UOPEntry( int offset, int length ) - { - m_Offset = offset; - m_Length = length; - m_Order = 0; - } + private BinaryReader m_Reader; - public int CompareTo( UOPEntry other ) - { - return m_Order.CompareTo( other.m_Order ); - } - } + public UOPIndex(FileStream stream) + { + m_Reader = new BinaryReader(stream); + m_Length = (int)stream.Length; - private class OffsetComparer : IComparer - { - public static readonly IComparer Instance = new OffsetComparer(); + if (m_Reader.ReadInt32() != 0x50594D) + throw new ArgumentException("Invalid UOP file."); - public OffsetComparer() - { - } + Version = m_Reader.ReadInt32(); + m_Reader.ReadInt32(); + int nextTable = m_Reader.ReadInt32(); - public int Compare( UOPEntry x, UOPEntry y ) - { - return x.m_Offset.CompareTo( y.m_Offset ); - } - } + List entries = new List(); - private BinaryReader m_Reader; - private int m_Length; - private UOPEntry[] m_Entries; + do + { + stream.Seek(nextTable, SeekOrigin.Begin); + int count = m_Reader.ReadInt32(); + nextTable = m_Reader.ReadInt32(); + m_Reader.ReadInt32(); - public int Version { get; } + for (int i = 0; i < count; ++i) + { + int offset = m_Reader.ReadInt32(); - public UOPIndex( FileStream stream ) - { - m_Reader = new BinaryReader( stream ); - m_Length = (int)stream.Length; + if (offset == 0) + { + stream.Seek(30, SeekOrigin.Current); + continue; + } - if ( m_Reader.ReadInt32() != 0x50594D ) - throw new ArgumentException( "Invalid UOP file." ); + m_Reader.ReadInt64(); + int length = m_Reader.ReadInt32(); - Version = m_Reader.ReadInt32(); - m_Reader.ReadInt32(); - int nextTable = m_Reader.ReadInt32(); + entries.Add(new UOPEntry(offset, length)); - List entries = new List(); + stream.Seek(18, SeekOrigin.Current); + } + } while (nextTable != 0 && nextTable < m_Length); - do - { - stream.Seek( nextTable, SeekOrigin.Begin ); - int count = m_Reader.ReadInt32(); - nextTable = m_Reader.ReadInt32(); - m_Reader.ReadInt32(); + entries.Sort(OffsetComparer.Instance); - for ( int i = 0; i < count; ++i ) - { - int offset = m_Reader.ReadInt32(); + for (int i = 0; i < entries.Count; ++i) + { + stream.Seek(entries[i].m_Offset + 2, SeekOrigin.Begin); - if ( offset == 0 ) - { - stream.Seek( 30, SeekOrigin.Current ); - continue; - } + int dataOffset = m_Reader.ReadInt16(); + entries[i].m_Offset += 4 + dataOffset; - m_Reader.ReadInt64(); - int length = m_Reader.ReadInt32(); + stream.Seek(dataOffset, SeekOrigin.Current); + entries[i].m_Order = m_Reader.ReadInt32(); + } - entries.Add( new UOPEntry( offset, length ) ); + entries.Sort(); + m_Entries = entries.ToArray(); + } - stream.Seek( 18, SeekOrigin.Current ); - } - } - while ( nextTable != 0 && nextTable < m_Length ); + public int Version{ get; } - entries.Sort( OffsetComparer.Instance ); + public int Lookup(int offset) + { + int total = 0; - for ( int i = 0; i < entries.Count; ++i ) - { - stream.Seek( entries[i].m_Offset + 2, SeekOrigin.Begin ); + for (int i = 0; i < m_Entries.Length; ++i) + { + int newTotal = total + m_Entries[i].m_Length; - int dataOffset = m_Reader.ReadInt16(); - entries[i].m_Offset += 4 + dataOffset; + if (offset < newTotal) + return m_Entries[i].m_Offset + (offset - total); - stream.Seek( dataOffset, SeekOrigin.Current ); - entries[i].m_Order = m_Reader.ReadInt32(); - } + total = newTotal; + } - entries.Sort(); - m_Entries = entries.ToArray(); - } + return m_Length; + } - public int Lookup( int offset ) - { - int total = 0; + public void Close() + { + m_Reader.Close(); + } - for ( int i = 0; i < m_Entries.Length; ++i ) - { - int newTotal = total + m_Entries[i].m_Length; + private class UOPEntry : IComparable + { + public int m_Length; + public int m_Offset; + public int m_Order; - if ( offset < newTotal ) - return m_Entries[i].m_Offset + ( offset - total ); + public UOPEntry(int offset, int length) + { + m_Offset = offset; + m_Length = length; + m_Order = 0; + } - total = newTotal; - } + public int CompareTo(UOPEntry other) + { + return m_Order.CompareTo(other.m_Order); + } + } - return m_Length; - } + private class OffsetComparer : IComparer + { + public static readonly IComparer Instance = new OffsetComparer(); - public void Close() - { - m_Reader.Close(); - } - } -} + public int Compare(UOPEntry x, UOPEntry y) + { + return x.m_Offset.CompareTo(y.m_Offset); + } + } + } +} \ No newline at end of file diff --git a/Server/TileMatrixPatch.cs b/Server/TileMatrixPatch.cs index 0ec2644a5..cff17809f 100644 --- a/Server/TileMatrixPatch.cs +++ b/Server/TileMatrixPatch.cs @@ -23,176 +23,180 @@ using System.Runtime.CompilerServices; namespace Server { - public class TileMatrixPatch - { - private int m_LandBlocks, m_StaticBlocks; + public class TileMatrixPatch + { + private int m_LandBlocks, m_StaticBlocks; - public static bool Enabled { get; set; } = true; + private StaticTile[] m_TileBuffer = new StaticTile[128]; - public int LandBlocks - { - get - { - lock (this) - return m_LandBlocks; - } - } + public TileMatrixPatch(TileMatrix matrix, int index) + { + if (!Enabled) + return; - public int StaticBlocks - { - get - { - lock (this) - return m_StaticBlocks; - } - } + string mapDataPath = Core.FindDataFile("mapdif{0}.mul", index); + string mapIndexPath = Core.FindDataFile("mapdifl{0}.mul", index); - public TileMatrixPatch( TileMatrix matrix, int index ) - { - if ( !Enabled ) - return; + if (File.Exists(mapDataPath) && File.Exists(mapIndexPath)) + m_LandBlocks = PatchLand(matrix, mapDataPath, mapIndexPath); - string mapDataPath = Core.FindDataFile( "mapdif{0}.mul", index ); - string mapIndexPath = Core.FindDataFile( "mapdifl{0}.mul", index ); + string staDataPath = Core.FindDataFile("stadif{0}.mul", index); + string staIndexPath = Core.FindDataFile("stadifl{0}.mul", index); + string staLookupPath = Core.FindDataFile("stadifi{0}.mul", index); - if ( File.Exists( mapDataPath ) && File.Exists( mapIndexPath ) ) - m_LandBlocks = PatchLand( matrix, mapDataPath, mapIndexPath ); + if (File.Exists(staDataPath) && File.Exists(staIndexPath) && File.Exists(staLookupPath)) + m_StaticBlocks = PatchStatics(matrix, staDataPath, staIndexPath, staLookupPath); + } - string staDataPath = Core.FindDataFile( "stadif{0}.mul", index ); - string staIndexPath = Core.FindDataFile( "stadifl{0}.mul", index ); - string staLookupPath = Core.FindDataFile( "stadifi{0}.mul", index ); + public static bool Enabled{ get; set; } = true; - if ( File.Exists( staDataPath ) && File.Exists( staIndexPath ) && File.Exists( staLookupPath ) ) - m_StaticBlocks = PatchStatics( matrix, staDataPath, staIndexPath, staLookupPath ); - } + public int LandBlocks + { + get + { + lock (this) + { + return m_LandBlocks; + } + } + } - [MethodImpl(MethodImplOptions.Synchronized)] - private unsafe int PatchLand( TileMatrix matrix, string dataPath, string indexPath ) - { - using ( FileStream fsData = new FileStream( dataPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - using ( FileStream fsIndex = new FileStream( indexPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - BinaryReader indexReader = new BinaryReader( fsIndex ); + public int StaticBlocks + { + get + { + lock (this) + { + return m_StaticBlocks; + } + } + } - int count = (int)(indexReader.BaseStream.Length / 4); + [MethodImpl(MethodImplOptions.Synchronized)] + private unsafe int PatchLand(TileMatrix matrix, string dataPath, string indexPath) + { + using (FileStream fsData = new FileStream(dataPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + using (FileStream fsIndex = new FileStream(indexPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader indexReader = new BinaryReader(fsIndex); - for ( int i = 0; i < count; ++i ) - { - int blockID = indexReader.ReadInt32(); - int x = blockID / matrix.BlockHeight; - int y = blockID % matrix.BlockHeight; + int count = (int)(indexReader.BaseStream.Length / 4); - fsData.Seek( 4, SeekOrigin.Current ); + for (int i = 0; i < count; ++i) + { + int blockID = indexReader.ReadInt32(); + int x = blockID / matrix.BlockHeight; + int y = blockID % matrix.BlockHeight; - LandTile[] tiles = new LandTile[64]; + fsData.Seek(4, SeekOrigin.Current); - fixed ( LandTile *pTiles = tiles ) - { + LandTile[] tiles = new LandTile[64]; + + fixed (LandTile* pTiles = tiles) + { #if !MONO - NativeReader.Read( fsData.SafeFileHandle.DangerousGetHandle(), pTiles, 192 ); + NativeReader.Read(fsData.SafeFileHandle.DangerousGetHandle(), pTiles, 192); #else NativeReader.Read( fsData.Handle, pTiles, 192 ); #endif - } + } - matrix.SetLandBlock( x, y, tiles ); - } - - indexReader.Close(); + matrix.SetLandBlock(x, y, tiles); + } - return count; - } - } - } + indexReader.Close(); - private StaticTile[] m_TileBuffer = new StaticTile[128]; + return count; + } + } + } - [MethodImpl(MethodImplOptions.Synchronized)] - private unsafe int PatchStatics( TileMatrix matrix, string dataPath, string indexPath, string lookupPath ) - { - using ( FileStream fsData = new FileStream( dataPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - using ( FileStream fsIndex = new FileStream( indexPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - using ( FileStream fsLookup = new FileStream( lookupPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) - { - BinaryReader indexReader = new BinaryReader( fsIndex ); - BinaryReader lookupReader = new BinaryReader( fsLookup ); + [MethodImpl(MethodImplOptions.Synchronized)] + private unsafe int PatchStatics(TileMatrix matrix, string dataPath, string indexPath, string lookupPath) + { + using (FileStream fsData = new FileStream(dataPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + using (FileStream fsIndex = new FileStream(indexPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + using (FileStream fsLookup = new FileStream(lookupPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader indexReader = new BinaryReader(fsIndex); + BinaryReader lookupReader = new BinaryReader(fsLookup); - int count = (int)(indexReader.BaseStream.Length / 4); + int count = (int)(indexReader.BaseStream.Length / 4); - TileList[][] lists = new TileList[8][]; + TileList[][] lists = new TileList[8][]; - for ( int x = 0; x < 8; ++x ) - { - lists[x] = new TileList[8]; + for (int x = 0; x < 8; ++x) + { + lists[x] = new TileList[8]; - for ( int y = 0; y < 8; ++y ) - lists[x][y] = new TileList(); - } + for (int y = 0; y < 8; ++y) + lists[x][y] = new TileList(); + } - for ( int i = 0; i < count; ++i ) - { - int blockID = indexReader.ReadInt32(); - int blockX = blockID / matrix.BlockHeight; - int blockY = blockID % matrix.BlockHeight; + for (int i = 0; i < count; ++i) + { + int blockID = indexReader.ReadInt32(); + int blockX = blockID / matrix.BlockHeight; + int blockY = blockID % matrix.BlockHeight; - int offset = lookupReader.ReadInt32(); - int length = lookupReader.ReadInt32(); - lookupReader.ReadInt32(); // Extra + int offset = lookupReader.ReadInt32(); + int length = lookupReader.ReadInt32(); + lookupReader.ReadInt32(); // Extra - if ( offset < 0 || length <= 0 ) - { - matrix.SetStaticBlock( blockX, blockY, matrix.EmptyStaticBlock ); - continue; - } + if (offset < 0 || length <= 0) + { + matrix.SetStaticBlock(blockX, blockY, matrix.EmptyStaticBlock); + continue; + } - fsData.Seek( offset, SeekOrigin.Begin ); + fsData.Seek(offset, SeekOrigin.Begin); - int tileCount = length / 7; + int tileCount = length / 7; - if ( m_TileBuffer.Length < tileCount ) - m_TileBuffer = new StaticTile[tileCount]; + if (m_TileBuffer.Length < tileCount) + m_TileBuffer = new StaticTile[tileCount]; - StaticTile[] staTiles = m_TileBuffer; + StaticTile[] staTiles = m_TileBuffer; - fixed ( StaticTile *pTiles = staTiles ) - { + fixed (StaticTile* pTiles = staTiles) + { #if !MONO - NativeReader.Read( fsData.SafeFileHandle.DangerousGetHandle(), pTiles, length ); + NativeReader.Read(fsData.SafeFileHandle.DangerousGetHandle(), pTiles, length); #else NativeReader.Read( fsData.Handle, pTiles, length ); #endif - StaticTile *pCur = pTiles, pEnd = pTiles + tileCount; + StaticTile* pCur = pTiles, pEnd = pTiles + tileCount; - while ( pCur < pEnd ) - { - lists[pCur->m_X & 0x7][pCur->m_Y & 0x7].Add( (ushort)pCur->m_ID, pCur->m_Z ); - pCur = pCur + 1; - } + while (pCur < pEnd) + { + lists[pCur->m_X & 0x7][pCur->m_Y & 0x7].Add(pCur->m_ID, pCur->m_Z); + pCur = pCur + 1; + } - StaticTile[][][] tiles = new StaticTile[8][][]; + StaticTile[][][] tiles = new StaticTile[8][][]; - for ( int x = 0; x < 8; ++x ) - { - tiles[x] = new StaticTile[8][]; + for (int x = 0; x < 8; ++x) + { + tiles[x] = new StaticTile[8][]; - for ( int y = 0; y < 8; ++y ) - tiles[x][y] = lists[x][y].ToArray(); - } + for (int y = 0; y < 8; ++y) + tiles[x][y] = lists[x][y].ToArray(); + } - matrix.SetStaticBlock( blockX, blockY, tiles ); - } - } + matrix.SetStaticBlock(blockX, blockY, tiles); + } + } - indexReader.Close(); - lookupReader.Close(); + indexReader.Close(); + lookupReader.Close(); - return count; - } - } - } - } - } + return count; + } + } + } + } + } } \ No newline at end of file diff --git a/Server/Timer.cs b/Server/Timer.cs index 2d45d5ae3..230de2a9f 100644 --- a/Server/Timer.cs +++ b/Server/Timer.cs @@ -26,636 +26,647 @@ using Server.Diagnostics; namespace Server { - public enum TimerPriority - { - EveryTick, - TenMS, - TwentyFiveMS, - FiftyMS, - TwoFiftyMS, - OneSecond, - FiveSeconds, - OneMinute - } - - public delegate void TimerCallback(); - public delegate void TimerStateCallback( object state ); - public delegate void TimerStateCallback( T state ); - - public class Timer - { - private long m_Next; - private long m_Delay; - private long m_Interval; - private bool m_Running; - private int m_Index, m_Count; - private TimerPriority m_Priority; - private List m_List; - private bool m_PrioritySet; - - private static string FormatDelegate( Delegate callback ) - { - if ( callback == null ) - return "null"; - - return $"{callback.Method.DeclaringType.FullName}.{callback.Method.Name}"; - } - - public static void DumpInfo( TextWriter tw ) - { - TimerThread.DumpInfo( tw ); - } - - public TimerPriority Priority - { - get => m_Priority; - set - { - if ( !m_PrioritySet ) - m_PrioritySet = true; - - if ( m_Priority != value ) - { - m_Priority = value; - - if ( m_Running ) - TimerThread.PriorityChange( this, (int)m_Priority ); - } - } - } - - public DateTime Next => DateTime.UtcNow + TimeSpan.FromMilliseconds(m_Next-Core.TickCount); - - public TimeSpan Delay - { - get => TimeSpan.FromMilliseconds(m_Delay); - set => m_Delay = (long)value.TotalMilliseconds; - } - - public TimeSpan Interval - { - get => TimeSpan.FromMilliseconds(m_Interval); - set => m_Interval = (long)value.TotalMilliseconds; - } - - public bool Running - { - get => m_Running; - set { - if ( value ) { - Start(); - } else { - Stop(); - } - } - } - - public TimerProfile GetProfile() - { - if ( !Core.Profiling ) { - return null; - } - - string name = ToString(); - - if ( name == null ) { - name = "null"; - } - - return TimerProfile.Acquire( name ); - } - - public class TimerThread - { - private static Dictionary m_Changed = new Dictionary(); - - private static long[] m_NextPriorities = new long[8]; - private static long[] m_PriorityDelays = new long[8] - { - 0, - 10, - 25, - 50, - 250, - 1000, - 5000, - 60000 - }; - - private static List[] m_Timers = new List[8] - { - new List(), - new List(), - new List(), - new List(), - new List(), - new List(), - new List(), - new List(), - }; - - public static void DumpInfo( TextWriter tw ) - { - for ( int i = 0; i < 8; ++i ) - { - tw.WriteLine( "Priority: {0}", (TimerPriority)i ); - tw.WriteLine(); - - Dictionary> hash = new Dictionary>(); - - for ( int j = 0; j < m_Timers[i].Count; ++j ) - { - Timer t = m_Timers[i][j]; - - string key = t.ToString(); - - List list; - hash.TryGetValue( key, out list ); - - if ( list == null ) - hash[key] = list = new List(); - - list.Add( t ); - } - - foreach ( KeyValuePair> kv in hash ) - { - string key = kv.Key; - List list = kv.Value; - - tw.WriteLine( "Type: {0}; Count: {1}; Percent: {2}%", key, list.Count, (int)(100 * (list.Count / (double)m_Timers[i].Count)) ); - } - - tw.WriteLine(); - tw.WriteLine(); - } - } - - private class TimerChangeEntry - { - public Timer m_Timer; - public int m_NewIndex; - public bool m_IsAdd; - - private TimerChangeEntry( Timer t, int newIndex, bool isAdd ) - { - m_Timer = t; - m_NewIndex = newIndex; - m_IsAdd = isAdd; - } - - public void Free() - { - lock (m_InstancePool) { - if (m_InstancePool.Count < 200) // Arbitrary - m_InstancePool.Enqueue( this ); - } - } - - private static Queue m_InstancePool = new Queue(); - - public static TimerChangeEntry GetInstance( Timer t, int newIndex, bool isAdd ) - { - TimerChangeEntry e = null; - - lock (m_InstancePool) { - if ( m_InstancePool.Count > 0 ) { - e = m_InstancePool.Dequeue(); - } - } - - if (e != null) { - e.m_Timer = t; - e.m_NewIndex = newIndex; - e.m_IsAdd = isAdd; - } else { - e = new TimerChangeEntry( t, newIndex, isAdd ); - } - - return e; - } - } - - public TimerThread() - { - } - - public static void Change( Timer t, int newIndex, bool isAdd ) - { - lock (m_Changed) - m_Changed[t] = TimerChangeEntry.GetInstance(t, newIndex, isAdd); - m_Signal.Set(); - } - - public static void AddTimer( Timer t ) - { - Change( t, (int)t.Priority, true ); - } - - public static void PriorityChange( Timer t, int newPrio ) - { - Change( t, newPrio, false ); - } - - public static void RemoveTimer( Timer t ) - { - Change( t, -1, false ); - } - - private static void ProcessChanged() - { - lock (m_Changed) { - long curTicks = Core.TickCount; - - foreach (TimerChangeEntry tce in m_Changed.Values) { - Timer timer = tce.m_Timer; - int newIndex = tce.m_NewIndex; - - timer.m_List?.Remove(timer); - - if (tce.m_IsAdd) { - timer.m_Next = curTicks + timer.m_Delay; - timer.m_Index = 0; - } - - if (newIndex >= 0) { - timer.m_List = m_Timers[newIndex]; - timer.m_List.Add(timer); - } else { - timer.m_List = null; - } - - tce.Free(); - } - - m_Changed.Clear(); - } - } - - private static AutoResetEvent m_Signal = new AutoResetEvent( false ); - public static void Set() { m_Signal.Set(); } - - public void TimerMain() - { - long now; - int i, j; - bool loaded; - - while ( !Core.Closing ) - { - if (World.Loading || World.Saving) - { - m_Signal.WaitOne(1, false); - continue; - } - - ProcessChanged(); - - loaded = false; - - for ( i = 0; i < m_Timers.Length; i++) - { - now = Core.TickCount; - if ( now < m_NextPriorities[i] ) - break; - - m_NextPriorities[i] = now + m_PriorityDelays[i]; - - for ( j = 0; j < m_Timers[i].Count; j++) - { - Timer t = m_Timers[i][j]; - - if ( !t.m_Queued && now > t.m_Next ) - { - t.m_Queued = true; - - lock ( m_Queue ) - m_Queue.Enqueue( t ); - - loaded = true; - - if ( t.m_Count != 0 && (++t.m_Index >= t.m_Count) ) - { - t.Stop(); - } - else - { - t.m_Next = now + t.m_Interval; - } - } - } - } - - if ( loaded ) - Core.Set(); - - m_Signal.WaitOne(1, false); - } - } - } + public enum TimerPriority + { + EveryTick, + TenMS, + TwentyFiveMS, + FiftyMS, + TwoFiftyMS, + OneSecond, + FiveSeconds, + OneMinute + } + + public delegate void TimerCallback(); + + public delegate void TimerStateCallback(object state); + + public delegate void TimerStateCallback(T state); + + public class Timer + { + private static Queue m_Queue = new Queue(); + + private static int m_QueueCountAtSlice; + private long m_Delay; + private int m_Index, m_Count; + private long m_Interval; + private List m_List; + private long m_Next; + private TimerPriority m_Priority; + private bool m_PrioritySet; + + private bool m_Queued; + private bool m_Running; + + public Timer(TimeSpan delay) : this(delay, TimeSpan.Zero, 1) + { + } + + public Timer(TimeSpan delay, TimeSpan interval) : this(delay, interval, 0) + { + } + + public Timer(TimeSpan delay, TimeSpan interval, int count) + { + m_Delay = (long)delay.TotalMilliseconds; + m_Interval = (long)interval.TotalMilliseconds; + m_Count = count; + + if (!m_PrioritySet) + { + if (count == 1) + m_Priority = ComputePriority(delay); + else + m_Priority = ComputePriority(interval); + m_PrioritySet = true; + } + + if (DefRegCreation) + RegCreation(); + } + + public TimerPriority Priority + { + get => m_Priority; + set + { + if (!m_PrioritySet) + m_PrioritySet = true; + + if (m_Priority != value) + { + m_Priority = value; + + if (m_Running) + TimerThread.PriorityChange(this, (int)m_Priority); + } + } + } + + public DateTime Next => DateTime.UtcNow + TimeSpan.FromMilliseconds(m_Next - Core.TickCount); + + public TimeSpan Delay + { + get => TimeSpan.FromMilliseconds(m_Delay); + set => m_Delay = (long)value.TotalMilliseconds; + } + + public TimeSpan Interval + { + get => TimeSpan.FromMilliseconds(m_Interval); + set => m_Interval = (long)value.TotalMilliseconds; + } + + public bool Running + { + get => m_Running; + set + { + if (value) + Start(); + else + Stop(); + } + } + + public static int BreakCount{ get; set; } = 20000; + + public virtual bool DefRegCreation => true; + + private static string FormatDelegate(Delegate callback) + { + if (callback == null) + return "null"; + + return $"{callback.Method.DeclaringType.FullName}.{callback.Method.Name}"; + } + + public static void DumpInfo(TextWriter tw) + { + TimerThread.DumpInfo(tw); + } + + public TimerProfile GetProfile() + { + if (!Core.Profiling) return null; + + string name = ToString(); + + if (name == null) name = "null"; + + return TimerProfile.Acquire(name); + } + + public static void Slice() + { + lock (m_Queue) + { + m_QueueCountAtSlice = m_Queue.Count; + + int index = 0; + + while (index < BreakCount && m_Queue.Count != 0) + { + Timer t = m_Queue.Dequeue(); + TimerProfile prof = t.GetProfile(); + + prof?.Start(); + + t.OnTick(); + t.m_Queued = false; + ++index; + + prof?.Finish(); + } + } + } + + public void RegCreation() + { + TimerProfile prof = GetProfile(); + + if (prof != null) prof.Created++; + } + + public override string ToString() + { + return GetType().FullName; + } + + public static TimerPriority ComputePriority(TimeSpan ts) + { + if (ts >= TimeSpan.FromMinutes(1.0)) + return TimerPriority.FiveSeconds; + + if (ts >= TimeSpan.FromSeconds(10.0)) + return TimerPriority.OneSecond; + + if (ts >= TimeSpan.FromSeconds(5.0)) + return TimerPriority.TwoFiftyMS; + + if (ts >= TimeSpan.FromSeconds(2.5)) + return TimerPriority.FiftyMS; + + if (ts >= TimeSpan.FromSeconds(1.0)) + return TimerPriority.TwentyFiveMS; + + if (ts >= TimeSpan.FromSeconds(0.5)) + return TimerPriority.TenMS; + + return TimerPriority.EveryTick; + } + + public void Start() + { + if (!m_Running) + { + m_Running = true; + TimerThread.AddTimer(this); + + TimerProfile prof = GetProfile(); + + if (prof != null) prof.Started++; + } + } - private static Queue m_Queue = new Queue(); + public void Stop() + { + if (m_Running) + { + m_Running = false; + TimerThread.RemoveTimer(this); + + TimerProfile prof = GetProfile(); + + if (prof != null) prof.Stopped++; + } + } + + protected virtual void OnTick() + { + } + + public class TimerThread + { + private static Dictionary m_Changed = new Dictionary(); + + private static long[] m_NextPriorities = new long[8]; + + private static long[] m_PriorityDelays = new long[8] + { + 0, + 10, + 25, + 50, + 250, + 1000, + 5000, + 60000 + }; + + private static List[] m_Timers = new List[8] + { + new List(), + new List(), + new List(), + new List(), + new List(), + new List(), + new List(), + new List() + }; + + private static AutoResetEvent m_Signal = new AutoResetEvent(false); + + public static void DumpInfo(TextWriter tw) + { + for (int i = 0; i < 8; ++i) + { + tw.WriteLine("Priority: {0}", (TimerPriority)i); + tw.WriteLine(); + + Dictionary> hash = new Dictionary>(); + + for (int j = 0; j < m_Timers[i].Count; ++j) + { + Timer t = m_Timers[i][j]; + + string key = t.ToString(); + + List list; + hash.TryGetValue(key, out list); + + if (list == null) + hash[key] = list = new List(); + + list.Add(t); + } + + foreach (KeyValuePair> kv in hash) + { + string key = kv.Key; + List list = kv.Value; + + tw.WriteLine("Type: {0}; Count: {1}; Percent: {2}%", key, list.Count, + (int)(100 * (list.Count / (double)m_Timers[i].Count))); + } + + tw.WriteLine(); + tw.WriteLine(); + } + } + + public static void Change(Timer t, int newIndex, bool isAdd) + { + lock (m_Changed) + { + m_Changed[t] = TimerChangeEntry.GetInstance(t, newIndex, isAdd); + } + + m_Signal.Set(); + } + + public static void AddTimer(Timer t) + { + Change(t, (int)t.Priority, true); + } + + public static void PriorityChange(Timer t, int newPrio) + { + Change(t, newPrio, false); + } + + public static void RemoveTimer(Timer t) + { + Change(t, -1, false); + } + + private static void ProcessChanged() + { + lock (m_Changed) + { + long curTicks = Core.TickCount; + + foreach (TimerChangeEntry tce in m_Changed.Values) + { + Timer timer = tce.m_Timer; + int newIndex = tce.m_NewIndex; + + timer.m_List?.Remove(timer); + + if (tce.m_IsAdd) + { + timer.m_Next = curTicks + timer.m_Delay; + timer.m_Index = 0; + } + + if (newIndex >= 0) + { + timer.m_List = m_Timers[newIndex]; + timer.m_List.Add(timer); + } + else + { + timer.m_List = null; + } + + tce.Free(); + } + + m_Changed.Clear(); + } + } + + public static void Set() + { + m_Signal.Set(); + } + + public void TimerMain() + { + long now; + int i, j; + bool loaded; + + while (!Core.Closing) + { + if (World.Loading || World.Saving) + { + m_Signal.WaitOne(1, false); + continue; + } + + ProcessChanged(); + + loaded = false; + + for (i = 0; i < m_Timers.Length; i++) + { + now = Core.TickCount; + if (now < m_NextPriorities[i]) + break; + + m_NextPriorities[i] = now + m_PriorityDelays[i]; + + for (j = 0; j < m_Timers[i].Count; j++) + { + Timer t = m_Timers[i][j]; + + if (!t.m_Queued && now > t.m_Next) + { + t.m_Queued = true; + + lock (m_Queue) + { + m_Queue.Enqueue(t); + } + + loaded = true; + + if (t.m_Count != 0 && ++t.m_Index >= t.m_Count) + t.Stop(); + else + t.m_Next = now + t.m_Interval; + } + } + } + + if (loaded) + Core.Set(); + + m_Signal.WaitOne(1, false); + } + } + + private class TimerChangeEntry + { + private static Queue m_InstancePool = new Queue(); + public bool m_IsAdd; + public int m_NewIndex; + public Timer m_Timer; + + private TimerChangeEntry(Timer t, int newIndex, bool isAdd) + { + m_Timer = t; + m_NewIndex = newIndex; + m_IsAdd = isAdd; + } + + public void Free() + { + lock (m_InstancePool) + { + if (m_InstancePool.Count < 200) // Arbitrary + m_InstancePool.Enqueue(this); + } + } + + public static TimerChangeEntry GetInstance(Timer t, int newIndex, bool isAdd) + { + TimerChangeEntry e = null; + + lock (m_InstancePool) + { + if (m_InstancePool.Count > 0) e = m_InstancePool.Dequeue(); + } + + if (e != null) + { + e.m_Timer = t; + e.m_NewIndex = newIndex; + e.m_IsAdd = isAdd; + } + else + { + e = new TimerChangeEntry(t, newIndex, isAdd); + } + + return e; + } + } + } + + #region DelayCall(..) + + public static Timer DelayCall(TimerCallback callback) + { + return DelayCall(TimeSpan.Zero, TimeSpan.Zero, 1, callback); + } + + public static Timer DelayCall(TimeSpan delay, TimerCallback callback) + { + return DelayCall(delay, TimeSpan.Zero, 1, callback); + } + + public static Timer DelayCall(TimeSpan delay, TimeSpan interval, TimerCallback callback) + { + return DelayCall(delay, interval, 0, callback); + } + + public static Timer DelayCall(TimeSpan delay, TimeSpan interval, int count, TimerCallback callback) + { + Timer t = new DelayCallTimer(delay, interval, count, callback); + + if (count == 1) + t.Priority = ComputePriority(delay); + else + t.Priority = ComputePriority(interval); + + t.Start(); + + return t; + } + + public static Timer DelayCall(TimerStateCallback callback, object state) + { + return DelayCall(TimeSpan.Zero, TimeSpan.Zero, 1, callback, state); + } + + public static Timer DelayCall(TimeSpan delay, TimerStateCallback callback, object state) + { + return DelayCall(delay, TimeSpan.Zero, 1, callback, state); + } + + public static Timer DelayCall(TimeSpan delay, TimeSpan interval, TimerStateCallback callback, object state) + { + return DelayCall(delay, interval, 0, callback, state); + } + + public static Timer DelayCall(TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, + object state) + { + Timer t = new DelayStateCallTimer(delay, interval, count, callback, state); + + if (count == 1) + t.Priority = ComputePriority(delay); + else + t.Priority = ComputePriority(interval); + + t.Start(); + + return t; + } + + #endregion + + #region DelayCall(..) + + public static Timer DelayCall(TimerStateCallback callback, T state) + { + return DelayCall(TimeSpan.Zero, TimeSpan.Zero, 1, callback, state); + } + + public static Timer DelayCall(TimeSpan delay, TimerStateCallback callback, T state) + { + return DelayCall(delay, TimeSpan.Zero, 1, callback, state); + } + + public static Timer DelayCall(TimeSpan delay, TimeSpan interval, TimerStateCallback callback, T state) + { + return DelayCall(delay, interval, 0, callback, state); + } + + public static Timer DelayCall(TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, + T state) + { + Timer t = new DelayStateCallTimer(delay, interval, count, callback, state); + + if (count == 1) + t.Priority = ComputePriority(delay); + else + t.Priority = ComputePriority(interval); + + t.Start(); - public static int BreakCount { get; set; } = 20000; - - private static int m_QueueCountAtSlice; + return t; + } - private bool m_Queued; + #endregion - public static void Slice() - { - lock ( m_Queue ) - { - m_QueueCountAtSlice = m_Queue.Count; - - int index = 0; + #region DelayCall Timers - while ( index < BreakCount && m_Queue.Count != 0 ) - { - Timer t = m_Queue.Dequeue(); - TimerProfile prof = t.GetProfile(); - - prof?.Start(); - - t.OnTick(); - t.m_Queued = false; - ++index; + private class DelayCallTimer : Timer + { + public DelayCallTimer(TimeSpan delay, TimeSpan interval, int count, TimerCallback callback) : base(delay, + interval, count) + { + Callback = callback; + RegCreation(); + } - prof?.Finish(); - } - } - } + public TimerCallback Callback{ get; } - public Timer( TimeSpan delay ) : this( delay, TimeSpan.Zero, 1 ) - { - } + public override bool DefRegCreation => false; - public Timer( TimeSpan delay, TimeSpan interval ) : this( delay, interval, 0 ) - { - } + protected override void OnTick() + { + Callback?.Invoke(); + } - public virtual bool DefRegCreation => true; - - public void RegCreation() - { - TimerProfile prof = GetProfile(); + public override string ToString() + { + return $"DelayCallTimer[{FormatDelegate(Callback)}]"; + } + } - if ( prof != null ) { - prof.Created++; - } - } + private class DelayStateCallTimer : Timer + { + private object m_State; - public Timer( TimeSpan delay, TimeSpan interval, int count ) - { - m_Delay = (long)delay.TotalMilliseconds; - m_Interval = (long)interval.TotalMilliseconds; - m_Count = count; + public DelayStateCallTimer(TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, + object state) : base(delay, interval, count) + { + Callback = callback; + m_State = state; - if ( !m_PrioritySet ) { - if ( count == 1 ) { - m_Priority = ComputePriority( delay ); - } else { - m_Priority = ComputePriority( interval ); - } - m_PrioritySet = true; - } + RegCreation(); + } - if ( DefRegCreation ) - RegCreation(); - } + public TimerStateCallback Callback{ get; } - public override string ToString() - { - return GetType().FullName; - } + public override bool DefRegCreation => false; - public static TimerPriority ComputePriority( TimeSpan ts ) - { - if ( ts >= TimeSpan.FromMinutes( 1.0 ) ) - return TimerPriority.FiveSeconds; - - if ( ts >= TimeSpan.FromSeconds( 10.0 ) ) - return TimerPriority.OneSecond; - - if ( ts >= TimeSpan.FromSeconds( 5.0 ) ) - return TimerPriority.TwoFiftyMS; + protected override void OnTick() + { + Callback?.Invoke(m_State); + } - if ( ts >= TimeSpan.FromSeconds( 2.5 ) ) - return TimerPriority.FiftyMS; + public override string ToString() + { + return $"DelayStateCall[{FormatDelegate(Callback)}]"; + } + } - if ( ts >= TimeSpan.FromSeconds( 1.0 ) ) - return TimerPriority.TwentyFiveMS; + private class DelayStateCallTimer : Timer + { + private T m_State; - if ( ts >= TimeSpan.FromSeconds( 0.5 ) ) - return TimerPriority.TenMS; + public DelayStateCallTimer(TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, T state) + : base(delay, interval, count) + { + Callback = callback; + m_State = state; - return TimerPriority.EveryTick; - } + RegCreation(); + } - #region DelayCall(..) + public TimerStateCallback Callback{ get; } + + public override bool DefRegCreation => false; - public static Timer DelayCall( TimerCallback callback ) - { - return DelayCall( TimeSpan.Zero, TimeSpan.Zero, 1, callback ); - } - - public static Timer DelayCall( TimeSpan delay, TimerCallback callback ) - { - return DelayCall( delay, TimeSpan.Zero, 1, callback ); - } - - public static Timer DelayCall( TimeSpan delay, TimeSpan interval, TimerCallback callback ) - { - return DelayCall( delay, interval, 0, callback ); - } - - public static Timer DelayCall( TimeSpan delay, TimeSpan interval, int count, TimerCallback callback ) - { - Timer t = new DelayCallTimer( delay, interval, count, callback ); - - if ( count == 1 ) - t.Priority = ComputePriority( delay ); - else - t.Priority = ComputePriority( interval ); - - t.Start(); - - return t; - } - - public static Timer DelayCall( TimerStateCallback callback, object state ) - { - return DelayCall( TimeSpan.Zero, TimeSpan.Zero, 1, callback, state ); - } - - public static Timer DelayCall( TimeSpan delay, TimerStateCallback callback, object state ) - { - return DelayCall( delay, TimeSpan.Zero, 1, callback, state ); - } - - public static Timer DelayCall( TimeSpan delay, TimeSpan interval, TimerStateCallback callback, object state ) - { - return DelayCall( delay, interval, 0, callback, state ); - } - - public static Timer DelayCall( TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, object state ) - { - Timer t = new DelayStateCallTimer( delay, interval, count, callback, state ); - - if ( count == 1 ) - t.Priority = ComputePriority( delay ); - else - t.Priority = ComputePriority( interval ); - - t.Start(); - - return t; - } - #endregion - - #region DelayCall(..) - public static Timer DelayCall( TimerStateCallback callback, T state ) - { - return DelayCall( TimeSpan.Zero, TimeSpan.Zero, 1, callback, state ); - } + protected override void OnTick() + { + Callback?.Invoke(m_State); + } - public static Timer DelayCall( TimeSpan delay, TimerStateCallback callback, T state ) - { - return DelayCall( delay, TimeSpan.Zero, 1, callback, state ); - } + public override string ToString() + { + return $"DelayStateCall[{FormatDelegate(Callback)}]"; + } + } - public static Timer DelayCall( TimeSpan delay, TimeSpan interval, TimerStateCallback callback, T state ) - { - return DelayCall( delay, interval, 0, callback, state ); - } - - public static Timer DelayCall( TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, T state ) - { - Timer t = new DelayStateCallTimer( delay, interval, count, callback, state ); - - if ( count == 1 ) - t.Priority = ComputePriority( delay ); - else - t.Priority = ComputePriority( interval ); - - t.Start(); - - return t; - } - #endregion - - #region DelayCall Timers - private class DelayCallTimer : Timer - { - public TimerCallback Callback { get; } - - public override bool DefRegCreation => false; - - public DelayCallTimer( TimeSpan delay, TimeSpan interval, int count, TimerCallback callback ) : base( delay, interval, count ) - { - Callback = callback; - RegCreation(); - } - - protected override void OnTick() - { - Callback?.Invoke(); - } - - public override string ToString() - { - return $"DelayCallTimer[{FormatDelegate(Callback)}]"; - } - } - - private class DelayStateCallTimer : Timer - { - private object m_State; - - public TimerStateCallback Callback { get; } - - public override bool DefRegCreation => false; - - public DelayStateCallTimer( TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, object state ) : base( delay, interval, count ) - { - Callback = callback; - m_State = state; - - RegCreation(); - } - - protected override void OnTick() - { - Callback?.Invoke( m_State ); - } - - public override string ToString() - { - return $"DelayStateCall[{FormatDelegate(Callback)}]"; - } - } - - private class DelayStateCallTimer : Timer - { - private T m_State; - - public TimerStateCallback Callback { get; } - - public override bool DefRegCreation => false; - - public DelayStateCallTimer( TimeSpan delay, TimeSpan interval, int count, TimerStateCallback callback, T state ) - : base( delay, interval, count ) - { - Callback = callback; - m_State = state; - - RegCreation(); - } - - protected override void OnTick() - { - Callback?.Invoke( m_State ); - } - - public override string ToString() - { - return $"DelayStateCall[{FormatDelegate(Callback)}]"; - } - } - #endregion - - public void Start() - { - if ( !m_Running ) - { - m_Running = true; - TimerThread.AddTimer( this ); - - TimerProfile prof = GetProfile(); - - if ( prof != null ) { - prof.Started++; - } - } - } - - public void Stop() - { - if ( m_Running ) - { - m_Running = false; - TimerThread.RemoveTimer( this ); - - TimerProfile prof = GetProfile(); - - if ( prof != null ) { - prof.Stopped++; - } - } - } - - protected virtual void OnTick() - { - } - } -} + #endregion + } +} \ No newline at end of file diff --git a/Server/Utility.cs b/Server/Utility.cs index 84a45dda9..ebe2b0fa7 100644 --- a/Server/Utility.cs +++ b/Server/Utility.cs @@ -30,691 +30,580 @@ using System.Xml; namespace Server { - public static class Utility - { - private static Encoding m_UTF8, m_UTF8WithEncoding; + public static class Utility + { + private static Encoding m_UTF8, m_UTF8WithEncoding; + + private static Dictionary _ipAddressTable; + + private static SkillName[] m_AllSkills = + { + SkillName.Alchemy, + SkillName.Anatomy, + SkillName.AnimalLore, + SkillName.ItemID, + SkillName.ArmsLore, + SkillName.Parry, + SkillName.Begging, + SkillName.Blacksmith, + SkillName.Fletching, + SkillName.Peacemaking, + SkillName.Camping, + SkillName.Carpentry, + SkillName.Cartography, + SkillName.Cooking, + SkillName.DetectHidden, + SkillName.Discordance, + SkillName.EvalInt, + SkillName.Healing, + SkillName.Fishing, + SkillName.Forensics, + SkillName.Herding, + SkillName.Hiding, + SkillName.Provocation, + SkillName.Inscribe, + SkillName.Lockpicking, + SkillName.Magery, + SkillName.MagicResist, + SkillName.Tactics, + SkillName.Snooping, + SkillName.Musicianship, + SkillName.Poisoning, + SkillName.Archery, + SkillName.SpiritSpeak, + SkillName.Stealing, + SkillName.Tailoring, + SkillName.AnimalTaming, + SkillName.TasteID, + SkillName.Tinkering, + SkillName.Tracking, + SkillName.Veterinary, + SkillName.Swords, + SkillName.Macing, + SkillName.Fencing, + SkillName.Wrestling, + SkillName.Lumberjacking, + SkillName.Mining, + SkillName.Meditation, + SkillName.Stealth, + SkillName.RemoveTrap, + SkillName.Necromancy, + SkillName.Focus, + SkillName.Chivalry, + SkillName.Bushido, + SkillName.Ninjitsu, + SkillName.Spellweaving + }; + + private static SkillName[] m_CombatSkills = + { + SkillName.Archery, + SkillName.Swords, + SkillName.Macing, + SkillName.Fencing, + SkillName.Wrestling + }; + + private static SkillName[] m_CraftSkills = + { + SkillName.Alchemy, + SkillName.Blacksmith, + SkillName.Fletching, + SkillName.Carpentry, + SkillName.Cartography, + SkillName.Cooking, + SkillName.Inscribe, + SkillName.Tailoring, + SkillName.Tinkering + }; + + private static Stack m_ConsoleColors = new Stack(); + + public static Encoding UTF8 + { + get + { + if (m_UTF8 == null) + m_UTF8 = new UTF8Encoding(false, false); + + return m_UTF8; + } + } + + public static Encoding UTF8WithEncoding + { + get + { + if (m_UTF8WithEncoding == null) + m_UTF8WithEncoding = new UTF8Encoding(true, false); + + return m_UTF8WithEncoding; + } + } + + public static void Separate(StringBuilder sb, string value, string separator) + { + if (sb.Length > 0) + sb.Append(separator); + + sb.Append(value); + } + + public static string Intern(string str) + { + if (str == null) + return null; + if (str.Length == 0) + return string.Empty; + + return string.Intern(str); + } + + public static void Intern(ref string str) + { + str = Intern(str); + } + + public static IPAddress Intern(IPAddress ipAddress) + { + if (_ipAddressTable == null) _ipAddressTable = new Dictionary(); + + IPAddress interned; + + if (!_ipAddressTable.TryGetValue(ipAddress, out interned)) + { + interned = ipAddress; + _ipAddressTable[ipAddress] = interned; + } + + return interned; + } + + public static void Intern(ref IPAddress ipAddress) + { + ipAddress = Intern(ipAddress); + } - public static Encoding UTF8 - { - get - { - if ( m_UTF8 == null ) - m_UTF8 = new UTF8Encoding( false, false ); + public static bool IsValidIP(string text) + { + bool valid = true; - return m_UTF8; - } - } + IPMatch(text, IPAddress.None, ref valid); - public static Encoding UTF8WithEncoding - { - get - { - if ( m_UTF8WithEncoding == null ) - m_UTF8WithEncoding = new UTF8Encoding( true, false ); + return valid; + } - return m_UTF8WithEncoding; - } - } + public static bool IPMatch(string val, IPAddress ip) + { + bool valid = true; - public static void Separate( StringBuilder sb, string value, string separator ) - { - if ( sb.Length > 0 ) - sb.Append( separator ); + return IPMatch(val, ip, ref valid); + } - sb.Append( value ); - } + public static string FixHtml(string str) + { + if (str == null) + return ""; + + bool hasOpen = str.IndexOf('<') >= 0; + bool hasClose = str.IndexOf('>') >= 0; + bool hasPound = str.IndexOf('#') >= 0; - public static string Intern( string str ) - { - if ( str == null ) - return null; - if ( str.Length == 0 ) - return string.Empty; + if (!hasOpen && !hasClose && !hasPound) + return str; - return string.Intern( str ); - } + StringBuilder sb = new StringBuilder(str); - public static void Intern( ref string str ) - { - str = Intern( str ); - } + if (hasOpen) + sb.Replace('<', '('); - private static Dictionary _ipAddressTable; - - public static IPAddress Intern( IPAddress ipAddress ) { - if ( _ipAddressTable == null ) { - _ipAddressTable = new Dictionary(); - } - - IPAddress interned; - - if ( !_ipAddressTable.TryGetValue( ipAddress, out interned ) ) { - interned = ipAddress; - _ipAddressTable[ipAddress] = interned; - } - - return interned; - } - - public static void Intern( ref IPAddress ipAddress ) { - ipAddress = Intern( ipAddress ); - } - - public static bool IsValidIP( string text ) - { - bool valid = true; - - IPMatch( text, IPAddress.None, ref valid ); - - return valid; - } - - public static bool IPMatch( string val, IPAddress ip ) - { - bool valid = true; - - return IPMatch( val, ip, ref valid ); - } - - public static string FixHtml( string str ) - { - if ( str == null ) - return ""; - - bool hasOpen = ( str.IndexOf( '<' ) >= 0 ); - bool hasClose = ( str.IndexOf( '>' ) >= 0 ); - bool hasPound = ( str.IndexOf( '#' ) >= 0 ); - - if ( !hasOpen && !hasClose && !hasPound ) - return str; - - StringBuilder sb = new StringBuilder( str ); - - if ( hasOpen ) - sb.Replace( '<', '(' ); - - if ( hasClose ) - sb.Replace( '>', ')' ); - - if ( hasPound ) - sb.Replace( '#', '-' ); - - return sb.ToString(); - } - - public static bool IPMatchCIDR( string cidr, IPAddress ip ) - { - if ( ip == null || ip.AddressFamily == AddressFamily.InterNetworkV6 ) - return false; //Just worry about IPv4 for now - - - /* - string[] str = cidr.Split( '/' ); - - if ( str.Length != 2 ) - return false; - - /* ************************************************** - IPAddress cidrPrefix; - - if ( !IPAddress.TryParse( str[0], out cidrPrefix ) ) - return false; - * */ - - /* - string[] dotSplit = str[0].Split( '.' ); - - if ( dotSplit.Length != 4 ) //At this point and time, and for speed sake, we'll only worry about IPv4 - return false; - - byte[] bytes = new byte[4]; - - for ( int i = 0; i < 4; i++ ) - { - byte.TryParse( dotSplit[i], out bytes[i] ); - } - - uint cidrPrefix = OrderedAddressValue( bytes ); - - int cidrLength = Utility.ToInt32( str[1] ); - //The below solution is the fastest solution of the three - - */ - - byte[] bytes = new byte[4]; - string[] split = cidr.Split( '.' ); - bool cidrBits = false; - int cidrLength = 0; - - for ( int i = 0; i < 4; i++ ) - { - int part = 0; - - int partBase = 10; - - string pattern = split[i]; - - for ( int j = 0; j < pattern.Length; j++ ) - { - char c = (char)pattern[j]; - - - if ( c == 'x' || c == 'X' ) - { - partBase = 16; - } - else if ( c >= '0' && c <= '9' ) - { - int offset = c - '0'; - - if ( cidrBits ) - { - cidrLength *= partBase; - cidrLength += offset; - } - else - { - part *= partBase; - part += offset; - } - } - else if ( c >= 'a' && c <= 'f' ) - { - int offset = 10 + ( c - 'a' ); - - if ( cidrBits ) - { - cidrLength *= partBase; - cidrLength += offset; - } - else - { - part *= partBase; - part += offset; - } - } - else if ( c >= 'A' && c <= 'F' ) - { - int offset = 10 + ( c - 'A' ); - - if ( cidrBits ) - { - cidrLength *= partBase; - cidrLength += offset; - } - else - { - part *= partBase; - part += offset; - } - } - else if ( c == '/' ) - { - if ( cidrBits || i != 3 ) //If there's two '/' or the '/' isn't in the last byte - { - return false; - } - - partBase = 10; - cidrBits = true; - } - else - { - return false; - } - } - - bytes[i] = (byte)part; - } - - uint cidrPrefix = OrderedAddressValue( bytes ); - - return IPMatchCIDR( cidrPrefix, ip, cidrLength ); - } - - public static bool IPMatchCIDR( IPAddress cidrPrefix, IPAddress ip, int cidrLength ) - { - if ( cidrPrefix == null || ip == null || cidrPrefix.AddressFamily == AddressFamily.InterNetworkV6 ) //Ignore IPv6 for now - return false; - - uint cidrValue = SwapUnsignedInt( (uint)GetLongAddressValue( cidrPrefix ) ); - uint ipValue = SwapUnsignedInt( (uint)GetLongAddressValue( ip ) ); - - return IPMatchCIDR( cidrValue, ipValue, cidrLength ); - } - - public static bool IPMatchCIDR( uint cidrPrefixValue, IPAddress ip, int cidrLength ) - { - if ( ip == null || ip.AddressFamily == AddressFamily.InterNetworkV6) - return false; - - uint ipValue = SwapUnsignedInt( (uint)GetLongAddressValue( ip ) ); - - return IPMatchCIDR( cidrPrefixValue, ipValue, cidrLength ); - } - - public static bool IPMatchCIDR( uint cidrPrefixValue, uint ipValue, int cidrLength ) - { - if ( cidrLength <= 0 || cidrLength >= 32 ) //if invalid cidr Length, just compare IPs - return cidrPrefixValue == ipValue; - - uint mask = uint.MaxValue << 32-cidrLength; - - return ( ( cidrPrefixValue & mask ) == ( ipValue & mask ) ); - } - - private static uint OrderedAddressValue( byte[] bytes ) - { - if ( bytes.Length != 4 ) - return 0; - - return (uint)(((( bytes[0] << 0x18 ) | (bytes[1] << 0x10)) | (bytes[2] << 8)) | bytes[3]) & ((uint)0xffffffff); - } - - private static uint SwapUnsignedInt( uint source ) - { - return (uint)( ( ( ( source & 0x000000FF ) << 0x18 ) - | ( ( source & 0x0000FF00 ) << 8 ) - | ( ( source & 0x00FF0000 ) >> 8 ) - | ( ( source & 0xFF000000 ) >> 0x18 ) ) ); - } - - public static bool TryConvertIPv6toIPv4( ref IPAddress address ) - { - if ( !Socket.OSSupportsIPv6 || address.AddressFamily == AddressFamily.InterNetwork ) - return true; - - byte[] addr = address.GetAddressBytes(); - if ( addr.Length == 16 ) //sanity 0 - 15 //10 11 //12 13 14 15 - { - if ( addr[10] != 0xFF || addr[11] != 0xFF ) - return false; - - for ( int i = 0; i < 10; i++ ) - { - if ( addr[i] != 0 ) - return false; - } - - byte[] v4Addr = new byte[4]; - - for ( int i = 0; i < 4; i++ ) - { - v4Addr[i] = addr[12 + i]; - } - - address = new IPAddress( v4Addr ); - return true; - } - - return false; - } - - public static bool IPMatch( string val, IPAddress ip, ref bool valid ) - { - valid = true; - - string[] split = val.Split( '.' ); - - for ( int i = 0; i < 4; ++i ) - { - int lowPart, highPart; - - if ( i >= split.Length ) - { - lowPart = 0; - highPart = 255; - } - else - { - string pattern = split[i]; - - if ( pattern == "*" ) - { - lowPart = 0; - highPart = 255; - } - else - { - lowPart = 0; - highPart = 0; - - bool highOnly = false; - int lowBase = 10; - int highBase = 10; - - for ( int j = 0; j < pattern.Length; ++j ) - { - char c = (char)pattern[j]; - - if ( c == '?' ) - { - if ( !highOnly ) - { - lowPart *= lowBase; - lowPart += 0; - } - - highPart *= highBase; - highPart += highBase - 1; - } - else if ( c == '-' ) - { - highOnly = true; - highPart = 0; - } - else if ( c == 'x' || c == 'X' ) - { - lowBase = 16; - highBase = 16; - } - else if ( c >= '0' && c <= '9' ) - { - int offset = c - '0'; - - if ( !highOnly ) - { - lowPart *= lowBase; - lowPart += offset; - } - - highPart *= highBase; - highPart += offset; - } - else if ( c >= 'a' && c <= 'f' ) - { - int offset = 10 + (c - 'a'); - - if ( !highOnly ) - { - lowPart *= lowBase; - lowPart += offset; - } - - highPart *= highBase; - highPart += offset; - } - else if ( c >= 'A' && c <= 'F' ) - { - int offset = 10 + (c - 'A'); - - if ( !highOnly ) - { - lowPart *= lowBase; - lowPart += offset; - } - - highPart *= highBase; - highPart += offset; - } - else - { - valid = false; //high & lowpart would be 0 if it got to here. - } - } - } - } - - int b = (byte)(GetAddressValue( ip ) >> (i * 8)); - - if ( b < lowPart || b > highPart ) - return false; - } - - return true; - } - - public static bool IPMatchClassC( IPAddress ip1, IPAddress ip2 ) - { - return ( (GetAddressValue( ip1 ) & 0xFFFFFF) == (GetAddressValue( ip2 ) & 0xFFFFFF) ); - } - - public static int InsensitiveCompare( string first, string second ) - { - return Insensitive.Compare( first, second ); - } - - public static bool InsensitiveStartsWith( string first, string second ) - { - return Insensitive.StartsWith( first, second ); - } - - #region To[Something] - public static bool ToBoolean( string value ) - { - bool b; - bool.TryParse( value, out b ); - - return b; - } - - public static double ToDouble( string value ) - { - double d; - double.TryParse( value, out d ); - - return d; - } - - public static TimeSpan ToTimeSpan( string value ) - { - TimeSpan t; - TimeSpan.TryParse( value, out t ); - - return t; - } - - public static int ToInt32( string value ) - { - int i; - - if ( value.StartsWith( "0x" ) ) - int.TryParse( value.Substring( 2 ), NumberStyles.HexNumber, null, out i ); - else - int.TryParse( value, out i ); - - return i; - } - #endregion - - #region Get[Something] - public static double GetXMLDouble(string doubleString, double defaultValue) - { - try - { - return XmlConvert.ToDouble(doubleString); - } - catch - { - double val; - if (double.TryParse(doubleString, out val)) - return val; - - return defaultValue; - } - } - - public static int GetXMLInt32( string intString, int defaultValue ) - { - try - { - return XmlConvert.ToInt32( intString ); - } - catch - { - int val; - if ( int.TryParse( intString, out val ) ) - return val; - - return defaultValue; - } - } - - public static DateTime GetXMLDateTime( string dateTimeString, DateTime defaultValue ) - { - try - { - return XmlConvert.ToDateTime( dateTimeString, XmlDateTimeSerializationMode.Utc ); - } - catch - { - DateTime d; - - if ( DateTime.TryParse( dateTimeString, out d ) ) - return d; - - return defaultValue; - } - } - - public static DateTimeOffset GetXMLDateTimeOffset( string dateTimeOffsetString, DateTimeOffset defaultValue ) - { - try - { - return XmlConvert.ToDateTimeOffset( dateTimeOffsetString ); - } - catch - { - DateTimeOffset d; - - if ( DateTimeOffset.TryParse( dateTimeOffsetString, out d ) ) - return d; - - return defaultValue; - } - } - - public static TimeSpan GetXMLTimeSpan( string timeSpanString, TimeSpan defaultValue ) - { - try - { - return XmlConvert.ToTimeSpan( timeSpanString ); - } - catch - { - return defaultValue; - } - } - - public static string GetAttribute( XmlElement node, string attributeName ) - { - return GetAttribute( node, attributeName, null ); - } - - public static string GetAttribute( XmlElement node, string attributeName, string defaultValue ) - { - if ( node == null ) - return defaultValue; - - XmlAttribute attr = node.Attributes[attributeName]; - - if ( attr == null ) - return defaultValue; - - return attr.Value; - } - - public static string GetText( XmlElement node, string defaultValue ) - { - if ( node == null ) - return defaultValue; - - return node.InnerText; - } - - public static int GetAddressValue( IPAddress address ) - { -#pragma warning disable 618 - return (int)address.Address; -#pragma warning restore 618 - } - - public static long GetLongAddressValue( IPAddress address ) - { -#pragma warning disable 618 - return address.Address; -#pragma warning restore 618 - } - #endregion - - #region In[...]Range - public static bool InRange( Point3D p1, Point3D p2, int range ) - { - return ( p1.m_X >= (p2.m_X - range) ) - && ( p1.m_X <= (p2.m_X + range) ) - && ( p1.m_Y >= (p2.m_Y - range) ) - && ( p1.m_Y <= (p2.m_Y + range) ); - } - - public static bool InUpdateRange( Point3D p1, Point3D p2 ) - { - return ( p1.m_X >= (p2.m_X - 18) ) - && ( p1.m_X <= (p2.m_X + 18) ) - && ( p1.m_Y >= (p2.m_Y - 18) ) - && ( p1.m_Y <= (p2.m_Y + 18) ); - } - - public static bool InUpdateRange( Point2D p1, Point2D p2 ) - { - return ( p1.m_X >= (p2.m_X - 18) ) - && ( p1.m_X <= (p2.m_X + 18) ) - && ( p1.m_Y >= (p2.m_Y - 18) ) - && ( p1.m_Y <= (p2.m_Y + 18) ); - } - - public static bool InUpdateRange( IPoint2D p1, IPoint2D p2 ) - { - return ( p1.X >= (p2.X - 18) ) - && ( p1.X <= (p2.X + 18) ) - && ( p1.Y >= (p2.Y - 18) ) - && ( p1.Y <= (p2.Y + 18) ); - } - #endregion - - public static Direction GetDirection( IPoint2D from, IPoint2D to ) - { - int dx = to.X - from.X; - int dy = to.Y - from.Y; - - int adx = Math.Abs( dx ); - int ady = Math.Abs( dy ); - - if ( adx >= ady * 3 ) - { - if ( dx > 0 ) - return Direction.East; - return Direction.West; - } - - if ( ady >= adx * 3 ) - { - if ( dy > 0 ) - return Direction.South; - return Direction.North; - } - if ( dx > 0 ) - { - if ( dy > 0 ) - return Direction.Down; - return Direction.Right; - } - if ( dy > 0 ) - return Direction.Left; - return Direction.Up; - } - - /* Should probably be rewritten to use an ITile interface - - public static bool CanMobileFit( int z, StaticTile[] tiles ) - { - int checkHeight = 15; - int checkZ = z; - - for ( int i = 0; i < tiles.Length; ++i ) - { - StaticTile tile = tiles[i]; - - if ( ((checkZ + checkHeight) > tile.Z && checkZ < (tile.Z + tile.Height))*//* || (tile.Z < (checkZ + checkHeight) && (tile.Z + tile.Height) > checkZ)*//* ) + if (hasClose) + sb.Replace('>', ')'); + + if (hasPound) + sb.Replace('#', '-'); + + return sb.ToString(); + } + + public static bool IPMatchCIDR(string cidr, IPAddress ip) + { + if (ip == null || ip.AddressFamily == AddressFamily.InterNetworkV6) + return false; //Just worry about IPv4 for now + + + /* + string[] str = cidr.Split( '/' ); + + if ( str.Length != 2 ) + return false; + + /* ************************************************** + IPAddress cidrPrefix; + + if ( !IPAddress.TryParse( str[0], out cidrPrefix ) ) + return false; + * */ + + /* + string[] dotSplit = str[0].Split( '.' ); + + if ( dotSplit.Length != 4 ) //At this point and time, and for speed sake, we'll only worry about IPv4 + return false; + + byte[] bytes = new byte[4]; + + for ( int i = 0; i < 4; i++ ) + { + byte.TryParse( dotSplit[i], out bytes[i] ); + } + + uint cidrPrefix = OrderedAddressValue( bytes ); + + int cidrLength = Utility.ToInt32( str[1] ); + //The below solution is the fastest solution of the three + + */ + + byte[] bytes = new byte[4]; + string[] split = cidr.Split('.'); + bool cidrBits = false; + int cidrLength = 0; + + for (int i = 0; i < 4; i++) + { + int part = 0; + + int partBase = 10; + + string pattern = split[i]; + + for (int j = 0; j < pattern.Length; j++) + { + char c = pattern[j]; + + + if (c == 'x' || c == 'X') + { + partBase = 16; + } + else if (c >= '0' && c <= '9') + { + int offset = c - '0'; + + if (cidrBits) + { + cidrLength *= partBase; + cidrLength += offset; + } + else + { + part *= partBase; + part += offset; + } + } + else if (c >= 'a' && c <= 'f') + { + int offset = 10 + (c - 'a'); + + if (cidrBits) + { + cidrLength *= partBase; + cidrLength += offset; + } + else + { + part *= partBase; + part += offset; + } + } + else if (c >= 'A' && c <= 'F') + { + int offset = 10 + (c - 'A'); + + if (cidrBits) + { + cidrLength *= partBase; + cidrLength += offset; + } + else + { + part *= partBase; + part += offset; + } + } + else if (c == '/') + { + if (cidrBits || i != 3) //If there's two '/' or the '/' isn't in the last byte + return false; + + partBase = 10; + cidrBits = true; + } + else + { + return false; + } + } + + bytes[i] = (byte)part; + } + + uint cidrPrefix = OrderedAddressValue(bytes); + + return IPMatchCIDR(cidrPrefix, ip, cidrLength); + } + + public static bool IPMatchCIDR(IPAddress cidrPrefix, IPAddress ip, int cidrLength) + { + if (cidrPrefix == null || ip == null || cidrPrefix.AddressFamily == AddressFamily.InterNetworkV6 + ) //Ignore IPv6 for now + return false; + + uint cidrValue = SwapUnsignedInt((uint)GetLongAddressValue(cidrPrefix)); + uint ipValue = SwapUnsignedInt((uint)GetLongAddressValue(ip)); + + return IPMatchCIDR(cidrValue, ipValue, cidrLength); + } + + public static bool IPMatchCIDR(uint cidrPrefixValue, IPAddress ip, int cidrLength) + { + if (ip == null || ip.AddressFamily == AddressFamily.InterNetworkV6) + return false; + + uint ipValue = SwapUnsignedInt((uint)GetLongAddressValue(ip)); + + return IPMatchCIDR(cidrPrefixValue, ipValue, cidrLength); + } + + public static bool IPMatchCIDR(uint cidrPrefixValue, uint ipValue, int cidrLength) + { + if (cidrLength <= 0 || cidrLength >= 32) //if invalid cidr Length, just compare IPs + return cidrPrefixValue == ipValue; + + uint mask = uint.MaxValue << (32 - cidrLength); + + return (cidrPrefixValue & mask) == (ipValue & mask); + } + + private static uint OrderedAddressValue(byte[] bytes) + { + if (bytes.Length != 4) + return 0; + + return (uint)((bytes[0] << 0x18) | (bytes[1] << 0x10) | (bytes[2] << 8) | bytes[3]) & 0xffffffff; + } + + private static uint SwapUnsignedInt(uint source) + { + return ((source & 0x000000FF) << 0x18) + | ((source & 0x0000FF00) << 8) + | ((source & 0x00FF0000) >> 8) + | ((source & 0xFF000000) >> 0x18); + } + + public static bool TryConvertIPv6toIPv4(ref IPAddress address) + { + if (!Socket.OSSupportsIPv6 || address.AddressFamily == AddressFamily.InterNetwork) + return true; + + byte[] addr = address.GetAddressBytes(); + if (addr.Length == 16) //sanity 0 - 15 //10 11 //12 13 14 15 + { + if (addr[10] != 0xFF || addr[11] != 0xFF) + return false; + + for (int i = 0; i < 10; i++) + if (addr[i] != 0) + return false; + + byte[] v4Addr = new byte[4]; + + for (int i = 0; i < 4; i++) v4Addr[i] = addr[12 + i]; + + address = new IPAddress(v4Addr); + return true; + } + + return false; + } + + public static bool IPMatch(string val, IPAddress ip, ref bool valid) + { + valid = true; + + string[] split = val.Split('.'); + + for (int i = 0; i < 4; ++i) + { + int lowPart, highPart; + + if (i >= split.Length) + { + lowPart = 0; + highPart = 255; + } + else + { + string pattern = split[i]; + + if (pattern == "*") + { + lowPart = 0; + highPart = 255; + } + else + { + lowPart = 0; + highPart = 0; + + bool highOnly = false; + int lowBase = 10; + int highBase = 10; + + for (int j = 0; j < pattern.Length; ++j) + { + char c = pattern[j]; + + if (c == '?') + { + if (!highOnly) + { + lowPart *= lowBase; + lowPart += 0; + } + + highPart *= highBase; + highPart += highBase - 1; + } + else if (c == '-') + { + highOnly = true; + highPart = 0; + } + else if (c == 'x' || c == 'X') + { + lowBase = 16; + highBase = 16; + } + else if (c >= '0' && c <= '9') + { + int offset = c - '0'; + + if (!highOnly) + { + lowPart *= lowBase; + lowPart += offset; + } + + highPart *= highBase; + highPart += offset; + } + else if (c >= 'a' && c <= 'f') + { + int offset = 10 + (c - 'a'); + + if (!highOnly) + { + lowPart *= lowBase; + lowPart += offset; + } + + highPart *= highBase; + highPart += offset; + } + else if (c >= 'A' && c <= 'F') + { + int offset = 10 + (c - 'A'); + + if (!highOnly) + { + lowPart *= lowBase; + lowPart += offset; + } + + highPart *= highBase; + highPart += offset; + } + else + { + valid = false; //high & lowpart would be 0 if it got to here. + } + } + } + } + + int b = (byte)(GetAddressValue(ip) >> (i * 8)); + + if (b < lowPart || b > highPart) + return false; + } + + return true; + } + + public static bool IPMatchClassC(IPAddress ip1, IPAddress ip2) + { + return (GetAddressValue(ip1) & 0xFFFFFF) == (GetAddressValue(ip2) & 0xFFFFFF); + } + + public static int InsensitiveCompare(string first, string second) + { + return Insensitive.Compare(first, second); + } + + public static bool InsensitiveStartsWith(string first, string second) + { + return Insensitive.StartsWith(first, second); + } + + public static Direction GetDirection(IPoint2D from, IPoint2D to) + { + int dx = to.X - from.X; + int dy = to.Y - from.Y; + + int adx = Math.Abs(dx); + int ady = Math.Abs(dy); + + if (adx >= ady * 3) + { + if (dx > 0) + return Direction.East; + return Direction.West; + } + + if (ady >= adx * 3) + { + if (dy > 0) + return Direction.South; + return Direction.North; + } + + if (dx > 0) + { + if (dy > 0) + return Direction.Down; + return Direction.Right; + } + + if (dy > 0) + return Direction.Left; + return Direction.Up; + } + + /* Should probably be rewritten to use an ITile interface + + public static bool CanMobileFit( int z, StaticTile[] tiles ) + { + int checkHeight = 15; + int checkZ = z; + + for ( int i = 0; i < tiles.Length; ++i ) + { + StaticTile tile = tiles[i]; + + if ( ((checkZ + checkHeight) > tile.Z && checkZ < (tile.Z + tile.Height))*/ + /* || (tile.Z < (checkZ + checkHeight) && (tile.Z + tile.Height) > checkZ)*/ /* ) { return false; } @@ -736,7 +625,8 @@ namespace Server { StaticTile tile = tiles[i]; - if ( ((checkZ + checkHeight) > tile.Z && checkZ < (tile.Z + tile.Height))*//* || (tile.Z < (checkZ + checkHeight) && (tile.Z + tile.Height) > checkZ)*//* ) + if ( ((checkZ + checkHeight) > tile.Z && checkZ < (tile.Z + tile.Height))*/ + /* || (tile.Z < (checkZ + checkHeight) && (tile.Z + tile.Height) > checkZ)*/ /* ) { return true; } @@ -750,599 +640,689 @@ namespace Server } */ - public static object GetArrayCap( Array array, int index ) - { - return GetArrayCap( array, index, null ); - } - - public static object GetArrayCap( Array array, int index, object emptyValue ) - { - if ( array.Length > 0 ) - { - if ( index < 0 ) - { - index = 0; - } - else if ( index >= array.Length ) - { - index = array.Length - 1; - } - - return array.GetValue( index ); - } - - return emptyValue; - } - - #region Random - //4d6+8 would be: Utility.Dice( 4, 6, 8 ) - public static int Dice( int numDice, int numSides, int bonus ) - { - int total = 0; - - for (int i = 0; i < numDice; ++i) - total += RandomImpl.Next(numSides) + 1; - - total += bonus; - return total; - } - - public static int RandomList( params int[] list ) - { - return list[RandomImpl.Next(list.Length)]; - } - - public static bool RandomBool() - { - return RandomImpl.NextBool(); - } - - public static int RandomMinMax( int min, int max ) - { - if ( min > max ) - { - int copy = min; - min = max; - max = copy; - } - else if ( min == max ) - { - return min; - } - - return min + RandomImpl.Next((max - min) + 1); - } - - public static int Random( int from, int count ) - { - if ( count == 0 ) { - return from; - } - - if ( count > 0 ) { - return from + RandomImpl.Next(count); - } - return from - RandomImpl.Next(-count); - } - - public static int Random( int count ) - { - return RandomImpl.Next(count); - } - - public static void RandomBytes( byte[] buffer ) - { - RandomImpl.NextBytes(buffer); - } - - public static double RandomDouble() - { - return RandomImpl.NextDouble(); - } - #endregion - - #region Random Hues - - /// - /// Random pink, blue, green, orange, red or yellow hue - /// - public static int RandomNondyedHue() - { - switch ( Random( 6 ) ) - { - case 0: return RandomPinkHue(); - case 1: return RandomBlueHue(); - case 2: return RandomGreenHue(); - case 3: return RandomOrangeHue(); - case 4: return RandomRedHue(); - case 5: return RandomYellowHue(); - } - - return 0; - } - - /// - /// Random hue in the range 1201-1254 - /// - public static int RandomPinkHue() - { - return Random( 1201, 54 ); - } - - /// - /// Random hue in the range 1301-1354 - /// - public static int RandomBlueHue() - { - return Random( 1301, 54 ); - } - - /// - /// Random hue in the range 1401-1454 - /// - public static int RandomGreenHue() - { - return Random( 1401, 54 ); - } - - /// - /// Random hue in the range 1501-1554 - /// - public static int RandomOrangeHue() - { - return Random( 1501, 54 ); - } - - /// - /// Random hue in the range 1601-1654 - /// - public static int RandomRedHue() - { - return Random( 1601, 54 ); - } - - /// - /// Random hue in the range 1701-1754 - /// - public static int RandomYellowHue() - { - return Random( 1701, 54 ); - } - - /// - /// Random hue in the range 1801-1908 - /// - public static int RandomNeutralHue() - { - return Random( 1801, 108 ); - } - - /// - /// Random hue in the range 2001-2018 - /// - public static int RandomSnakeHue() - { - return Random( 2001, 18 ); - } - - /// - /// Random hue in the range 2101-2130 - /// - public static int RandomBirdHue() - { - return Random( 2101, 30 ); - } - - /// - /// Random hue in the range 2201-2224 - /// - public static int RandomSlimeHue() - { - return Random( 2201, 24 ); - } - - /// - /// Random hue in the range 2301-2318 - /// - public static int RandomAnimalHue() - { - return Random( 2301, 18 ); - } - - /// - /// Random hue in the range 2401-2430 - /// - public static int RandomMetalHue() - { - return Random( 2401, 30 ); - } - - public static int ClipDyedHue( int hue ) - { - if ( hue < 2 ) - return 2; - if ( hue > 1001 ) - return 1001; - return hue; - } - - /// - /// Random hue in the range 2-1001 - /// - public static int RandomDyedHue() - { - return Random( 2, 1000 ); - } - - /// - /// Random hue from 0x62, 0x71, 0x03, 0x0D, 0x13, 0x1C, 0x21, 0x30, 0x37, 0x3A, 0x44, 0x59 - /// - public static int RandomBrightHue() - { - if ( RandomDouble() < 0.1 ) - return RandomList( 0x62, 0x71 ); - - return RandomList( 0x03, 0x0D, 0x13, 0x1C, 0x21, 0x30, 0x37, 0x3A, 0x44, 0x59 ); - } - - //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] - public static int ClipSkinHue( int hue ) - { - if ( hue < 1002 ) - return 1002; - if ( hue > 1058 ) - return 1058; - return hue; - } - - //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] - public static int RandomSkinHue() - { - return Random( 1002, 57 ) | 0x8000; - } - - //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] - public static int ClipHairHue( int hue ) - { - if ( hue < 1102 ) - return 1102; - if ( hue > 1149 ) - return 1149; - return hue; - } - - //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] - public static int RandomHairHue() - { - return Random( 1102, 48 ); - } - - #endregion - - private static SkillName[] m_AllSkills = { - SkillName.Alchemy, - SkillName.Anatomy, - SkillName.AnimalLore, - SkillName.ItemID, - SkillName.ArmsLore, - SkillName.Parry, - SkillName.Begging, - SkillName.Blacksmith, - SkillName.Fletching, - SkillName.Peacemaking, - SkillName.Camping, - SkillName.Carpentry, - SkillName.Cartography, - SkillName.Cooking, - SkillName.DetectHidden, - SkillName.Discordance, - SkillName.EvalInt, - SkillName.Healing, - SkillName.Fishing, - SkillName.Forensics, - SkillName.Herding, - SkillName.Hiding, - SkillName.Provocation, - SkillName.Inscribe, - SkillName.Lockpicking, - SkillName.Magery, - SkillName.MagicResist, - SkillName.Tactics, - SkillName.Snooping, - SkillName.Musicianship, - SkillName.Poisoning, - SkillName.Archery, - SkillName.SpiritSpeak, - SkillName.Stealing, - SkillName.Tailoring, - SkillName.AnimalTaming, - SkillName.TasteID, - SkillName.Tinkering, - SkillName.Tracking, - SkillName.Veterinary, - SkillName.Swords, - SkillName.Macing, - SkillName.Fencing, - SkillName.Wrestling, - SkillName.Lumberjacking, - SkillName.Mining, - SkillName.Meditation, - SkillName.Stealth, - SkillName.RemoveTrap, - SkillName.Necromancy, - SkillName.Focus, - SkillName.Chivalry, - SkillName.Bushido, - SkillName.Ninjitsu, - SkillName.Spellweaving - }; - - private static SkillName[] m_CombatSkills = { - SkillName.Archery, - SkillName.Swords, - SkillName.Macing, - SkillName.Fencing, - SkillName.Wrestling - }; - - private static SkillName[] m_CraftSkills = { - SkillName.Alchemy, - SkillName.Blacksmith, - SkillName.Fletching, - SkillName.Carpentry, - SkillName.Cartography, - SkillName.Cooking, - SkillName.Inscribe, - SkillName.Tailoring, - SkillName.Tinkering - }; - - public static SkillName RandomSkill() - { - return m_AllSkills[Random(m_AllSkills.Length - ( Core.ML ? 0 : Core.SE ? 1 : Core.AOS ? 3 : 6 ) )]; - } - - public static SkillName RandomCombatSkill() - { - return m_CombatSkills[Random(m_CombatSkills.Length)]; - } - - public static SkillName RandomCraftSkill() - { - return m_CraftSkills[Random(m_CraftSkills.Length)]; - } - - public static void FixPoints( ref Point3D top, ref Point3D bottom ) - { - if ( bottom.m_X < top.m_X ) - { - int swap = top.m_X; - top.m_X = bottom.m_X; - bottom.m_X = swap; - } - - if ( bottom.m_Y < top.m_Y ) - { - int swap = top.m_Y; - top.m_Y = bottom.m_Y; - bottom.m_Y = swap; - } - - if ( bottom.m_Z < top.m_Z ) - { - int swap = top.m_Z; - top.m_Z = bottom.m_Z; - bottom.m_Z = swap; - } - } - - public static ArrayList BuildArrayList( IEnumerable enumerable ) - { - IEnumerator e = enumerable.GetEnumerator(); - - ArrayList list = new ArrayList(); - - while ( e.MoveNext() ) - { - list.Add( e.Current ); - } - - return list; - } - - public static bool RangeCheck( IPoint2D p1, IPoint2D p2, int range ) - { - return ( p1.X >= (p2.X - range) ) - && ( p1.X <= (p2.X + range) ) - && ( p1.Y >= (p2.Y - range) ) - && ( p2.Y <= (p2.Y + range) ); - } - - public static void FormatBuffer( TextWriter output, Stream input, int length ) - { - output.WriteLine( " 0 1 2 3 4 5 6 7 8 9 A B C D E F" ); - output.WriteLine( " -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --" ); - - int byteIndex = 0; - - int whole = length >> 4; - int rem = length & 0xF; - - for ( int i = 0; i < whole; ++i, byteIndex += 16 ) - { - StringBuilder bytes = new StringBuilder( 49 ); - StringBuilder chars = new StringBuilder( 16 ); - - for ( int j = 0; j < 16; ++j ) - { - int c = input.ReadByte(); - - bytes.Append( c.ToString( "X2" ) ); - - if ( j != 7 ) - { - bytes.Append( ' ' ); - } - else - { - bytes.Append( " " ); - } - - if ( c >= 0x20 && c < 0x7F ) - { - chars.Append( (char)c ); - } - else - { - chars.Append( '.' ); - } - } - - output.Write( byteIndex.ToString( "X4" ) ); - output.Write( " " ); - output.Write( bytes.ToString() ); - output.Write( " " ); - output.WriteLine( chars.ToString() ); - } - - if ( rem != 0 ) - { - StringBuilder bytes = new StringBuilder( 49 ); - StringBuilder chars = new StringBuilder( rem ); - - for ( int j = 0; j < 16; ++j ) - { - if ( j < rem ) - { - int c = input.ReadByte(); - - bytes.Append( c.ToString( "X2" ) ); - - if ( j != 7 ) - { - bytes.Append( ' ' ); - } - else - { - bytes.Append( " " ); - } - - if ( c >= 0x20 && c < 0x7F ) - { - chars.Append( (char)c ); - } - else - { - chars.Append( '.' ); - } - } - else - { - bytes.Append( " " ); - } - } - - output.Write( byteIndex.ToString( "X4" ) ); - output.Write( " " ); - output.Write( bytes.ToString() ); - output.Write( " " ); - output.WriteLine( chars.ToString() ); - } - } - - private static Stack m_ConsoleColors = new Stack(); - - public static void PushColor( ConsoleColor color ) - { - try - { - m_ConsoleColors.Push( Console.ForegroundColor ); - Console.ForegroundColor = color; - } - catch - { - } - } - - public static void PopColor() - { - try - { - Console.ForegroundColor = m_ConsoleColors.Pop(); - } - catch - { - } - } - - public static bool NumberBetween( double num, int bound1, int bound2, double allowance ) - { - if ( bound1 > bound2 ) - { - int i = bound1; - bound1 = bound2; - bound2 = i; - } - - return ( numbound1-allowance ); - } - - public static void AssignRandomHair( Mobile m ) - { - AssignRandomHair( m, true ); - } - - public static void AssignRandomHair( Mobile m, int hue ) - { - m.HairItemID = m.Race.RandomHair( m ); - m.HairHue = hue; - } - - public static void AssignRandomHair( Mobile m, bool randomHue ) - { - m.HairItemID = m.Race.RandomHair( m ); - - if ( randomHue ) - m.HairHue = m.Race.RandomHairHue(); - } - - public static void AssignRandomFacialHair( Mobile m ) - { - AssignRandomFacialHair( m, true ); - } - - public static void AssignRandomFacialHair( Mobile m, int hue ) - { - m.FacialHairItemID = m.Race.RandomFacialHair( m ); - m.FacialHairHue = hue; - } - - public static void AssignRandomFacialHair( Mobile m, bool randomHue ) - { - m.FacialHairItemID = m.Race.RandomFacialHair( m ); - - if ( randomHue ) - m.FacialHairHue = m.Race.RandomHairHue(); - } - - public static List CastConvertList( List list ) where TOutput : TInput - { - return list.ConvertAll( delegate( TInput value ) { return (TOutput)value; } ); - } - - public static List SafeConvertList( List list ) where TOutput : class - { - List output = new List( list.Capacity ); - - for( int i = 0; i < list.Count; i++ ) - { - TOutput t = list[i] as TOutput; - - if ( t != null ) - output.Add( t ); - } - - return output; - } - } -} + public static object GetArrayCap(Array array, int index) + { + return GetArrayCap(array, index, null); + } + + public static object GetArrayCap(Array array, int index, object emptyValue) + { + if (array.Length > 0) + { + if (index < 0) + index = 0; + else if (index >= array.Length) index = array.Length - 1; + + return array.GetValue(index); + } + + return emptyValue; + } + + public static SkillName RandomSkill() + { + return m_AllSkills[Random(m_AllSkills.Length - (Core.ML ? 0 : Core.SE ? 1 : Core.AOS ? 3 : 6))]; + } + + public static SkillName RandomCombatSkill() + { + return m_CombatSkills[Random(m_CombatSkills.Length)]; + } + + public static SkillName RandomCraftSkill() + { + return m_CraftSkills[Random(m_CraftSkills.Length)]; + } + + public static void FixPoints(ref Point3D top, ref Point3D bottom) + { + if (bottom.m_X < top.m_X) + { + int swap = top.m_X; + top.m_X = bottom.m_X; + bottom.m_X = swap; + } + + if (bottom.m_Y < top.m_Y) + { + int swap = top.m_Y; + top.m_Y = bottom.m_Y; + bottom.m_Y = swap; + } + + if (bottom.m_Z < top.m_Z) + { + int swap = top.m_Z; + top.m_Z = bottom.m_Z; + bottom.m_Z = swap; + } + } + + public static ArrayList BuildArrayList(IEnumerable enumerable) + { + IEnumerator e = enumerable.GetEnumerator(); + + ArrayList list = new ArrayList(); + + while (e.MoveNext()) list.Add(e.Current); + + return list; + } + + public static bool RangeCheck(IPoint2D p1, IPoint2D p2, int range) + { + return p1.X >= p2.X - range + && p1.X <= p2.X + range + && p1.Y >= p2.Y - range + && p2.Y <= p2.Y + range; + } + + public static void FormatBuffer(TextWriter output, Stream input, int length) + { + output.WriteLine(" 0 1 2 3 4 5 6 7 8 9 A B C D E F"); + output.WriteLine(" -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --"); + + int byteIndex = 0; + + int whole = length >> 4; + int rem = length & 0xF; + + for (int i = 0; i < whole; ++i, byteIndex += 16) + { + StringBuilder bytes = new StringBuilder(49); + StringBuilder chars = new StringBuilder(16); + + for (int j = 0; j < 16; ++j) + { + int c = input.ReadByte(); + + bytes.Append(c.ToString("X2")); + + if (j != 7) + bytes.Append(' '); + else + bytes.Append(" "); + + if (c >= 0x20 && c < 0x7F) + chars.Append((char)c); + else + chars.Append('.'); + } + + output.Write(byteIndex.ToString("X4")); + output.Write(" "); + output.Write(bytes.ToString()); + output.Write(" "); + output.WriteLine(chars.ToString()); + } + + if (rem != 0) + { + StringBuilder bytes = new StringBuilder(49); + StringBuilder chars = new StringBuilder(rem); + + for (int j = 0; j < 16; ++j) + if (j < rem) + { + int c = input.ReadByte(); + + bytes.Append(c.ToString("X2")); + + if (j != 7) + bytes.Append(' '); + else + bytes.Append(" "); + + if (c >= 0x20 && c < 0x7F) + chars.Append((char)c); + else + chars.Append('.'); + } + else + { + bytes.Append(" "); + } + + output.Write(byteIndex.ToString("X4")); + output.Write(" "); + output.Write(bytes.ToString()); + output.Write(" "); + output.WriteLine(chars.ToString()); + } + } + + public static void PushColor(ConsoleColor color) + { + try + { + m_ConsoleColors.Push(Console.ForegroundColor); + Console.ForegroundColor = color; + } + catch + { + } + } + + public static void PopColor() + { + try + { + Console.ForegroundColor = m_ConsoleColors.Pop(); + } + catch + { + } + } + + public static bool NumberBetween(double num, int bound1, int bound2, double allowance) + { + if (bound1 > bound2) + { + int i = bound1; + bound1 = bound2; + bound2 = i; + } + + return num < bound2 + allowance && num > bound1 - allowance; + } + + public static void AssignRandomHair(Mobile m) + { + AssignRandomHair(m, true); + } + + public static void AssignRandomHair(Mobile m, int hue) + { + m.HairItemID = m.Race.RandomHair(m); + m.HairHue = hue; + } + + public static void AssignRandomHair(Mobile m, bool randomHue) + { + m.HairItemID = m.Race.RandomHair(m); + + if (randomHue) + m.HairHue = m.Race.RandomHairHue(); + } + + public static void AssignRandomFacialHair(Mobile m) + { + AssignRandomFacialHair(m, true); + } + + public static void AssignRandomFacialHair(Mobile m, int hue) + { + m.FacialHairItemID = m.Race.RandomFacialHair(m); + m.FacialHairHue = hue; + } + + public static void AssignRandomFacialHair(Mobile m, bool randomHue) + { + m.FacialHairItemID = m.Race.RandomFacialHair(m); + + if (randomHue) + m.FacialHairHue = m.Race.RandomHairHue(); + } + + public static List CastConvertList(List list) where TOutput : TInput + { + return list.ConvertAll(delegate(TInput value) { return (TOutput)value; }); + } + + public static List SafeConvertList(List list) where TOutput : class + { + List output = new List(list.Capacity); + + for (int i = 0; i < list.Count; i++) + { + TOutput t = list[i] as TOutput; + + if (t != null) + output.Add(t); + } + + return output; + } + + #region To[Something] + + public static bool ToBoolean(string value) + { + bool b; + bool.TryParse(value, out b); + + return b; + } + + public static double ToDouble(string value) + { + double d; + double.TryParse(value, out d); + + return d; + } + + public static TimeSpan ToTimeSpan(string value) + { + TimeSpan t; + TimeSpan.TryParse(value, out t); + + return t; + } + + public static int ToInt32(string value) + { + int i; + + if (value.StartsWith("0x")) + int.TryParse(value.Substring(2), NumberStyles.HexNumber, null, out i); + else + int.TryParse(value, out i); + + return i; + } + + #endregion + + #region Get[Something] + + public static double GetXMLDouble(string doubleString, double defaultValue) + { + try + { + return XmlConvert.ToDouble(doubleString); + } + catch + { + double val; + if (double.TryParse(doubleString, out val)) + return val; + + return defaultValue; + } + } + + public static int GetXMLInt32(string intString, int defaultValue) + { + try + { + return XmlConvert.ToInt32(intString); + } + catch + { + int val; + if (int.TryParse(intString, out val)) + return val; + + return defaultValue; + } + } + + public static DateTime GetXMLDateTime(string dateTimeString, DateTime defaultValue) + { + try + { + return XmlConvert.ToDateTime(dateTimeString, XmlDateTimeSerializationMode.Utc); + } + catch + { + DateTime d; + + if (DateTime.TryParse(dateTimeString, out d)) + return d; + + return defaultValue; + } + } + + public static DateTimeOffset GetXMLDateTimeOffset(string dateTimeOffsetString, DateTimeOffset defaultValue) + { + try + { + return XmlConvert.ToDateTimeOffset(dateTimeOffsetString); + } + catch + { + DateTimeOffset d; + + if (DateTimeOffset.TryParse(dateTimeOffsetString, out d)) + return d; + + return defaultValue; + } + } + + public static TimeSpan GetXMLTimeSpan(string timeSpanString, TimeSpan defaultValue) + { + try + { + return XmlConvert.ToTimeSpan(timeSpanString); + } + catch + { + return defaultValue; + } + } + + public static string GetAttribute(XmlElement node, string attributeName) + { + return GetAttribute(node, attributeName, null); + } + + public static string GetAttribute(XmlElement node, string attributeName, string defaultValue) + { + if (node == null) + return defaultValue; + + XmlAttribute attr = node.Attributes[attributeName]; + + if (attr == null) + return defaultValue; + + return attr.Value; + } + + public static string GetText(XmlElement node, string defaultValue) + { + if (node == null) + return defaultValue; + + return node.InnerText; + } + + public static int GetAddressValue(IPAddress address) + { +#pragma warning disable 618 + return (int)address.Address; +#pragma warning restore 618 + } + + public static long GetLongAddressValue(IPAddress address) + { +#pragma warning disable 618 + return address.Address; +#pragma warning restore 618 + } + + #endregion + + #region In[...]Range + + public static bool InRange(Point3D p1, Point3D p2, int range) + { + return p1.m_X >= p2.m_X - range + && p1.m_X <= p2.m_X + range + && p1.m_Y >= p2.m_Y - range + && p1.m_Y <= p2.m_Y + range; + } + + public static bool InUpdateRange(Point3D p1, Point3D p2) + { + return p1.m_X >= p2.m_X - 18 + && p1.m_X <= p2.m_X + 18 + && p1.m_Y >= p2.m_Y - 18 + && p1.m_Y <= p2.m_Y + 18; + } + + public static bool InUpdateRange(Point2D p1, Point2D p2) + { + return p1.m_X >= p2.m_X - 18 + && p1.m_X <= p2.m_X + 18 + && p1.m_Y >= p2.m_Y - 18 + && p1.m_Y <= p2.m_Y + 18; + } + + public static bool InUpdateRange(IPoint2D p1, IPoint2D p2) + { + return p1.X >= p2.X - 18 + && p1.X <= p2.X + 18 + && p1.Y >= p2.Y - 18 + && p1.Y <= p2.Y + 18; + } + + #endregion + + #region Random + + //4d6+8 would be: Utility.Dice( 4, 6, 8 ) + public static int Dice(int numDice, int numSides, int bonus) + { + int total = 0; + + for (int i = 0; i < numDice; ++i) + total += RandomImpl.Next(numSides) + 1; + + total += bonus; + return total; + } + + public static int RandomList(params int[] list) + { + return list[RandomImpl.Next(list.Length)]; + } + + public static bool RandomBool() + { + return RandomImpl.NextBool(); + } + + public static int RandomMinMax(int min, int max) + { + if (min > max) + { + int copy = min; + min = max; + max = copy; + } + else if (min == max) + { + return min; + } + + return min + RandomImpl.Next(max - min + 1); + } + + public static int Random(int from, int count) + { + if (count == 0) return from; + + if (count > 0) return from + RandomImpl.Next(count); + return from - RandomImpl.Next(-count); + } + + public static int Random(int count) + { + return RandomImpl.Next(count); + } + + public static void RandomBytes(byte[] buffer) + { + RandomImpl.NextBytes(buffer); + } + + public static double RandomDouble() + { + return RandomImpl.NextDouble(); + } + + #endregion + + #region Random Hues + + /// + /// Random pink, blue, green, orange, red or yellow hue + /// + public static int RandomNondyedHue() + { + switch (Random(6)) + { + case 0: return RandomPinkHue(); + case 1: return RandomBlueHue(); + case 2: return RandomGreenHue(); + case 3: return RandomOrangeHue(); + case 4: return RandomRedHue(); + case 5: return RandomYellowHue(); + } + + return 0; + } + + /// + /// Random hue in the range 1201-1254 + /// + public static int RandomPinkHue() + { + return Random(1201, 54); + } + + /// + /// Random hue in the range 1301-1354 + /// + public static int RandomBlueHue() + { + return Random(1301, 54); + } + + /// + /// Random hue in the range 1401-1454 + /// + public static int RandomGreenHue() + { + return Random(1401, 54); + } + + /// + /// Random hue in the range 1501-1554 + /// + public static int RandomOrangeHue() + { + return Random(1501, 54); + } + + /// + /// Random hue in the range 1601-1654 + /// + public static int RandomRedHue() + { + return Random(1601, 54); + } + + /// + /// Random hue in the range 1701-1754 + /// + public static int RandomYellowHue() + { + return Random(1701, 54); + } + + /// + /// Random hue in the range 1801-1908 + /// + public static int RandomNeutralHue() + { + return Random(1801, 108); + } + + /// + /// Random hue in the range 2001-2018 + /// + public static int RandomSnakeHue() + { + return Random(2001, 18); + } + + /// + /// Random hue in the range 2101-2130 + /// + public static int RandomBirdHue() + { + return Random(2101, 30); + } + + /// + /// Random hue in the range 2201-2224 + /// + public static int RandomSlimeHue() + { + return Random(2201, 24); + } + + /// + /// Random hue in the range 2301-2318 + /// + public static int RandomAnimalHue() + { + return Random(2301, 18); + } + + /// + /// Random hue in the range 2401-2430 + /// + public static int RandomMetalHue() + { + return Random(2401, 30); + } + + public static int ClipDyedHue(int hue) + { + if (hue < 2) + return 2; + if (hue > 1001) + return 1001; + return hue; + } + + /// + /// Random hue in the range 2-1001 + /// + public static int RandomDyedHue() + { + return Random(2, 1000); + } + + /// + /// Random hue from 0x62, 0x71, 0x03, 0x0D, 0x13, 0x1C, 0x21, 0x30, 0x37, 0x3A, 0x44, 0x59 + /// + public static int RandomBrightHue() + { + if (RandomDouble() < 0.1) + return RandomList(0x62, 0x71); + + return RandomList(0x03, 0x0D, 0x13, 0x1C, 0x21, 0x30, 0x37, 0x3A, 0x44, 0x59); + } + + //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] + public static int ClipSkinHue(int hue) + { + if (hue < 1002) + return 1002; + if (hue > 1058) + return 1058; + return hue; + } + + //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] + public static int RandomSkinHue() + { + return Random(1002, 57) | 0x8000; + } + + //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] + public static int ClipHairHue(int hue) + { + if (hue < 1102) + return 1102; + if (hue > 1149) + return 1149; + return hue; + } + + //[Obsolete( "Depreciated, use the methods for the Mobile's race", false )] + public static int RandomHairHue() + { + return Random(1102, 48); + } + + #endregion + } +} \ No newline at end of file diff --git a/Server/VirtueInfo.cs b/Server/VirtueInfo.cs index 6b28b8fe3..2a0281e9b 100644 --- a/Server/VirtueInfo.cs +++ b/Server/VirtueInfo.cs @@ -20,133 +20,149 @@ namespace Server { - [PropertyObject] - public class VirtueInfo - { - public int[] Values { get; private set; } + [PropertyObject] + public class VirtueInfo + { + public VirtueInfo() + { + } - public int GetValue( int index ) - { - if ( Values == null ) - return 0; - return Values[index]; - } + public VirtueInfo(GenericReader reader) + { + int version = reader.ReadByte(); - public void SetValue( int index, int value ) - { - if ( Values == null ) - Values = new int[8]; + switch (version) + { + case 1: //Changed the values throughout the virtue system + case 0: + { + int mask = reader.ReadByte(); - Values[index] = value; - } + if (mask != 0) + { + Values = new int[8]; - public override string ToString() - { - return "..."; - } + for (int i = 0; i < 8; ++i) + if ((mask & (1 << i)) != 0) + Values[i] = reader.ReadInt(); + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Humility{ get => GetValue( 0 ); - set => SetValue( 0, value ); - } + break; + } + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Sacrifice{ get => GetValue( 1 ); - set => SetValue( 1, value ); - } + if (version == 0) + { + Compassion *= 200; + Sacrifice *= 250; //Even though 40 (the max) only gives 10k, It's because it was formerly too easy - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Compassion{ get => GetValue( 2 ); - set => SetValue( 2, value ); - } + //No direct conversion factor for Justice, this is just an approximation + Justice *= 500; - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Spirituality{ get => GetValue( 3 ); - set => SetValue( 3, value ); - } + //All the other virtues haven't been defined at 'version 0' point in time in the scripts. + } + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Valor{ get => GetValue( 4 ); - set => SetValue( 4, value ); - } + public int[] Values{ get; private set; } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Honor{ get => GetValue( 5 ); - set => SetValue( 5, value ); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Humility + { + get => GetValue(0); + set => SetValue(0, value); + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Justice{ get => GetValue( 6 ); - set => SetValue( 6, value ); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Sacrifice + { + get => GetValue(1); + set => SetValue(1, value); + } - [CommandProperty( AccessLevel.Counselor, AccessLevel.GameMaster )] - public int Honesty{ get => GetValue( 7 ); - set => SetValue( 7, value ); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Compassion + { + get => GetValue(2); + set => SetValue(2, value); + } - public VirtueInfo() - { - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Spirituality + { + get => GetValue(3); + set => SetValue(3, value); + } - public VirtueInfo( GenericReader reader ) - { - int version = reader.ReadByte(); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Valor + { + get => GetValue(4); + set => SetValue(4, value); + } - switch ( version ) - { - case 1: //Changed the values throughout the virtue system - case 0: - { - int mask = reader.ReadByte(); + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Honor + { + get => GetValue(5); + set => SetValue(5, value); + } - if ( mask != 0 ) - { - Values = new int[8]; + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Justice + { + get => GetValue(6); + set => SetValue(6, value); + } - for ( int i = 0; i < 8; ++i ) - if ( (mask & (1 << i)) != 0 ) - Values[i] = reader.ReadInt(); - } + [CommandProperty(AccessLevel.Counselor, AccessLevel.GameMaster)] + public int Honesty + { + get => GetValue(7); + set => SetValue(7, value); + } - break; - } - } + public int GetValue(int index) + { + if (Values == null) + return 0; + return Values[index]; + } - if ( version == 0 ) - { - Compassion *= 200; - Sacrifice *= 250; //Even though 40 (the max) only gives 10k, It's because it was formerly too easy + public void SetValue(int index, int value) + { + if (Values == null) + Values = new int[8]; - //No direct conversion factor for Justice, this is just an approximation - Justice *= 500; + Values[index] = value; + } - //All the other virtues haven't been defined at 'version 0' point in time in the scripts. - } - } + public override string ToString() + { + return "..."; + } - public static void Serialize( GenericWriter writer, VirtueInfo info ) - { - writer.Write( (byte) 1 ); // version + public static void Serialize(GenericWriter writer, VirtueInfo info) + { + writer.Write((byte)1); // version - if ( info.Values == null ) - { - writer.Write( (byte) 0 ); - } - else - { - int mask = 0; + if (info.Values == null) + { + writer.Write((byte)0); + } + else + { + int mask = 0; - for ( int i = 0; i < 8; ++i ) - if ( info.Values[i] != 0 ) - mask |= 1 << i; + for (int i = 0; i < 8; ++i) + if (info.Values[i] != 0) + mask |= 1 << i; - writer.Write( (byte) mask ); + writer.Write((byte)mask); - for ( int i = 0; i < 8; ++i ) - if ( info.Values[i] != 0 ) - writer.Write( (int) info.Values[i] ); - } - } - } -} + for (int i = 0; i < 8; ++i) + if (info.Values[i] != 0) + writer.Write(info.Values[i]); + } + } + } +} \ No newline at end of file diff --git a/Server/World.cs b/Server/World.cs index 2011250fd..f0a309621 100644 --- a/Server/World.cs +++ b/Server/World.cs @@ -19,737 +19,807 @@ ***************************************************************************/ using System; -using System.IO; using System.Collections.Generic; +using System.Diagnostics; +using System.IO; using System.Reflection; using System.Threading; -using System.Diagnostics; -using Server.Network; using Server.Guilds; +using Server.Network; -namespace Server { - public static class World { - private static ManualResetEvent m_DiskWriteHandle = new ManualResetEvent(true); +namespace Server +{ + public static class World + { + private static ManualResetEvent m_DiskWriteHandle = new ManualResetEvent(true); - private static Queue _addQueue, _deleteQueue; + private static Queue _addQueue, _deleteQueue; - public static bool Saving { get; private set; } + public static readonly string MobileIndexPath = Path.Combine("Saves/Mobiles/", "Mobiles.idx"); + public static readonly string MobileTypesPath = Path.Combine("Saves/Mobiles/", "Mobiles.tdb"); + public static readonly string MobileDataPath = Path.Combine("Saves/Mobiles/", "Mobiles.bin"); - public static bool Loaded { get; private set; } + public static readonly string ItemIndexPath = Path.Combine("Saves/Items/", "Items.idx"); + public static readonly string ItemTypesPath = Path.Combine("Saves/Items/", "Items.tdb"); + public static readonly string ItemDataPath = Path.Combine("Saves/Items/", "Items.bin"); - public static bool Loading { get; private set; } + public static readonly string GuildIndexPath = Path.Combine("Saves/Guilds/", "Guilds.idx"); + public static readonly string GuildDataPath = Path.Combine("Saves/Guilds/", "Guilds.bin"); - public readonly static string MobileIndexPath = Path.Combine( "Saves/Mobiles/", "Mobiles.idx" ); - public readonly static string MobileTypesPath = Path.Combine( "Saves/Mobiles/", "Mobiles.tdb" ); - public readonly static string MobileDataPath = Path.Combine( "Saves/Mobiles/", "Mobiles.bin" ); + private static readonly Type[] m_SerialTypeArray = new Type[1] { typeof(Serial) }; - public readonly static string ItemIndexPath = Path.Combine( "Saves/Items/", "Items.idx" ); - public readonly static string ItemTypesPath = Path.Combine( "Saves/Items/", "Items.tdb" ); - public readonly static string ItemDataPath = Path.Combine( "Saves/Items/", "Items.bin" ); + internal static int m_Saves; - public readonly static string GuildIndexPath = Path.Combine( "Saves/Guilds/", "Guilds.idx" ); - public readonly static string GuildDataPath = Path.Combine( "Saves/Guilds/", "Guilds.bin" ); + internal static List m_ItemTypes = new List(); + internal static List m_MobileTypes = new List(); - public static void NotifyDiskWriteComplete() - { - if ( m_DiskWriteHandle.Set()) - { - Console.WriteLine("Closing Save Files. "); - } - } + public static bool Saving{ get; private set; } - public static void WaitForWriteCompletion() - { - m_DiskWriteHandle.WaitOne(); - } + public static bool Loaded{ get; private set; } - public static Dictionary Mobiles { get; private set; } + public static bool Loading{ get; private set; } - public static Dictionary Items { get; private set; } + public static Dictionary Mobiles{ get; private set; } - public static bool OnDelete( IEntity entity ) { - if ( Saving || Loading ) { - if ( Saving ) { - AppendSafetyLog( "delete", entity ); - } + public static Dictionary Items{ get; private set; } - _deleteQueue.Enqueue( entity ); + public static string LoadingType{ get; private set; } - return false; - } + public static void NotifyDiskWriteComplete() + { + if (m_DiskWriteHandle.Set()) Console.WriteLine("Closing Save Files. "); + } - return true; - } + public static void WaitForWriteCompletion() + { + m_DiskWriteHandle.WaitOne(); + } - public static void Broadcast( int hue, bool ascii, string text ) { - Packet p; + public static bool OnDelete(IEntity entity) + { + if (Saving || Loading) + { + if (Saving) AppendSafetyLog("delete", entity); - if ( ascii ) - p = new AsciiMessage( Serial.MinusOne, -1, MessageType.Regular, hue, 3, "System", text ); - else - p = new UnicodeMessage( Serial.MinusOne, -1, MessageType.Regular, hue, 3, "ENU", "System", text ); + _deleteQueue.Enqueue(entity); - List list = NetState.Instances; + return false; + } - p.Acquire(); + return true; + } - for ( int i = 0; i < list.Count; ++i ) { - if ( list[i].Mobile != null ) - list[i].Send( p ); - } + public static void Broadcast(int hue, bool ascii, string text) + { + Packet p; - p.Release(); + if (ascii) + p = new AsciiMessage(Serial.MinusOne, -1, MessageType.Regular, hue, 3, "System", text); + else + p = new UnicodeMessage(Serial.MinusOne, -1, MessageType.Regular, hue, 3, "ENU", "System", text); - NetState.FlushAll(); - } + List list = NetState.Instances; - public static void Broadcast( int hue, bool ascii, string format, params object[] args ) { - Broadcast( hue, ascii, string.Format( format, args ) ); - } + p.Acquire(); - private interface IEntityEntry { - Serial Serial { get; } - int TypeID { get; } - long Position { get; } - int Length { get; } - } + for (int i = 0; i < list.Count; ++i) + if (list[i].Mobile != null) + list[i].Send(p); - private sealed class GuildEntry : IEntityEntry { - public BaseGuild Guild { get; } + p.Release(); - public Serial Serial => Guild?.Id ?? 0; + NetState.FlushAll(); + } - public int TypeID => 0; + public static void Broadcast(int hue, bool ascii, string format, params object[] args) + { + Broadcast(hue, ascii, string.Format(format, args)); + } - public long Position { get; } + private static List> ReadTypes(BinaryReader tdbReader) + { + int count = tdbReader.ReadInt32(); - public int Length { get; } + List> types = new List>(count); - public GuildEntry( BaseGuild g, long pos, int length ) { - Guild = g; - Position = pos; - Length = length; - } - } + for (int i = 0; i < count; ++i) + { + string typeName = tdbReader.ReadString(); - private sealed class ItemEntry : IEntityEntry { - public Item Item { get; } + Type t = ScriptCompiler.FindTypeByFullName(typeName); - public Serial Serial => Item?.Serial ?? Serial.MinusOne; + if (t == null) + { + Console.WriteLine("failed"); - public int TypeID { get; } + if (!Core.Service) + { + Console.WriteLine("Error: Type '{0}' was not found. Delete all of those types? (y/n)", typeName); - public string TypeName { get; } + if (Console.ReadKey(true).Key == ConsoleKey.Y) + { + types.Add(null); + Console.Write("World: Loading..."); + continue; + } - public long Position { get; } + Console.WriteLine("Types will not be deleted. An exception will be thrown."); + } + else + { + Console.WriteLine("Error: Type '{0}' was not found.", typeName); + } - public int Length { get; } + throw new Exception($"Bad type '{typeName}'"); + } - public ItemEntry( Item item, int typeID, string typeName, long pos, int length ) { - Item = item; - TypeID = typeID; - TypeName = typeName; - Position = pos; - Length = length; - } - } + ConstructorInfo ctor = t.GetConstructor(m_SerialTypeArray); - private sealed class MobileEntry : IEntityEntry { - public Mobile Mobile { get; } + if (ctor != null) + types.Add(new Tuple(ctor, typeName)); + else + throw new Exception($"Type '{t}' does not have a serialization constructor"); + } - public Serial Serial => Mobile?.Serial ?? Serial.MinusOne; + return types; + } - public int TypeID { get; } + public static void Load() + { + if (Loaded) + return; - public string TypeName { get; } + Loaded = true; + LoadingType = null; - public long Position { get; } + Console.Write("World: Loading..."); - public int Length { get; } + Stopwatch watch = Stopwatch.StartNew(); - public MobileEntry( Mobile mobile, int typeID, string typeName, long pos, int length ) { - Mobile = mobile; - TypeID = typeID; - TypeName = typeName; - Position = pos; - Length = length; - } - } + Loading = true; - public static string LoadingType { get; private set; } + _addQueue = new Queue(); + _deleteQueue = new Queue(); - private static readonly Type[] m_SerialTypeArray = new Type[1] { typeof(Serial) }; + int mobileCount = 0, itemCount = 0, guildCount = 0; - private static List> ReadTypes( BinaryReader tdbReader ) - { - int count = tdbReader.ReadInt32(); + object[] ctorArgs = new object[1]; - List> types = new List>( count ); + List items = new List(); + List mobiles = new List(); + List guilds = new List(); - for (int i = 0; i < count; ++i) - { - string typeName = tdbReader.ReadString(); + if (File.Exists(MobileIndexPath) && File.Exists(MobileTypesPath)) + using (FileStream idx = new FileStream(MobileIndexPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader idxReader = new BinaryReader(idx); - Type t = ScriptCompiler.FindTypeByFullName(typeName); + using (FileStream tdb = new FileStream(MobileTypesPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader tdbReader = new BinaryReader(tdb); - if (t == null) - { - Console.WriteLine("failed"); + List> types = ReadTypes(tdbReader); - if (!Core.Service) - { - Console.WriteLine("Error: Type '{0}' was not found. Delete all of those types? (y/n)", typeName); + mobileCount = idxReader.ReadInt32(); - if (Console.ReadKey(true).Key == ConsoleKey.Y) - { - types.Add(null); - Console.Write("World: Loading..."); - continue; - } + Mobiles = new Dictionary(mobileCount); - Console.WriteLine("Types will not be deleted. An exception will be thrown."); - } - else - { - Console.WriteLine("Error: Type '{0}' was not found.", typeName); - } + for (int i = 0; i < mobileCount; ++i) + { + int typeID = idxReader.ReadInt32(); + int serial = idxReader.ReadInt32(); + long pos = idxReader.ReadInt64(); + int length = idxReader.ReadInt32(); - throw new Exception($"Bad type '{typeName}'"); - } + Tuple objs = types[typeID]; - ConstructorInfo ctor = t.GetConstructor(m_SerialTypeArray); + if (objs == null) + continue; - if (ctor != null) - { - types.Add( new Tuple( ctor, typeName ) ); - } - else - { - throw new Exception($"Type '{t}' does not have a serialization constructor"); - } - } + Mobile m = null; + ConstructorInfo ctor = objs.Item1; + string typeName = objs.Item2; - return types; - } + try + { + ctorArgs[0] = (Serial)serial; + m = (Mobile)ctor.Invoke(ctorArgs); + } + catch + { + } + + if (m != null) + { + mobiles.Add(new MobileEntry(m, typeID, typeName, pos, length)); + AddMobile(m); + } + } + + tdbReader.Close(); + } + + idxReader.Close(); + } + else + Mobiles = new Dictionary(); + + if (File.Exists(ItemIndexPath) && File.Exists(ItemTypesPath)) + using (FileStream idx = new FileStream(ItemIndexPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader idxReader = new BinaryReader(idx); - public static void Load() { - if ( Loaded ) - return; + using (FileStream tdb = new FileStream(ItemTypesPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader tdbReader = new BinaryReader(tdb); + + List> types = ReadTypes(tdbReader); + + itemCount = idxReader.ReadInt32(); + + Items = new Dictionary(itemCount); + + for (int i = 0; i < itemCount; ++i) + { + int typeID = idxReader.ReadInt32(); + int serial = idxReader.ReadInt32(); + long pos = idxReader.ReadInt64(); + int length = idxReader.ReadInt32(); + + Tuple objs = types[typeID]; + + if (objs == null) + continue; + + Item item = null; + ConstructorInfo ctor = objs.Item1; + string typeName = objs.Item2; + + try + { + ctorArgs[0] = (Serial)serial; + item = (Item)ctor.Invoke(ctorArgs); + } + catch + { + } + + if (item != null) + { + items.Add(new ItemEntry(item, typeID, typeName, pos, length)); + AddItem(item); + } + } + + tdbReader.Close(); + } + + idxReader.Close(); + } + else + Items = new Dictionary(); + + if (File.Exists(GuildIndexPath)) + using (FileStream idx = new FileStream(GuildIndexPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryReader idxReader = new BinaryReader(idx); + + guildCount = idxReader.ReadInt32(); + + CreateGuildEventArgs createEventArgs = new CreateGuildEventArgs(-1); + for (int i = 0; i < guildCount; ++i) + { + idxReader.ReadInt32(); //no typeid for guilds + int id = idxReader.ReadInt32(); + long pos = idxReader.ReadInt64(); + int length = idxReader.ReadInt32(); + + createEventArgs.Id = id; + EventSink.InvokeCreateGuild(createEventArgs); + BaseGuild guild = createEventArgs.Guild; + if (guild != null) + guilds.Add(new GuildEntry(guild, pos, length)); + } + + idxReader.Close(); + } + + bool failedMobiles = false, failedItems = false, failedGuilds = false; + Type failedType = null; + Serial failedSerial = Serial.Zero; + Exception failed = null; + int failedTypeID = 0; + + if (File.Exists(MobileDataPath)) + using (FileStream bin = new FileStream(MobileDataPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryFileReader reader = new BinaryFileReader(new BinaryReader(bin)); + + for (int i = 0; i < mobiles.Count; ++i) + { + MobileEntry entry = mobiles[i]; + Mobile m = entry.Mobile; + + if (m != null) + { + reader.Seek(entry.Position, SeekOrigin.Begin); + + try + { + LoadingType = entry.TypeName; + m.Deserialize(reader); + + if (reader.Position != entry.Position + entry.Length) + throw new Exception($"***** Bad serialize on {m.GetType()} *****"); + } + catch (Exception e) + { + mobiles.RemoveAt(i); + + failed = e; + failedMobiles = true; + failedType = m.GetType(); + failedTypeID = entry.TypeID; + failedSerial = m.Serial; + + break; + } + } + } + + reader.Close(); + } + + if (!failedMobiles && File.Exists(ItemDataPath)) + using (FileStream bin = new FileStream(ItemDataPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryFileReader reader = new BinaryFileReader(new BinaryReader(bin)); + + for (int i = 0; i < items.Count; ++i) + { + ItemEntry entry = items[i]; + Item item = entry.Item; + + if (item != null) + { + reader.Seek(entry.Position, SeekOrigin.Begin); + + try + { + LoadingType = entry.TypeName; + item.Deserialize(reader); + + if (reader.Position != entry.Position + entry.Length) + throw new Exception($"***** Bad serialize on {item.GetType()} *****"); + } + catch (Exception e) + { + items.RemoveAt(i); + + failed = e; + failedItems = true; + failedType = item.GetType(); + failedTypeID = entry.TypeID; + failedSerial = item.Serial; + + break; + } + } + } + + reader.Close(); + } + + LoadingType = null; + + if (!failedMobiles && !failedItems && File.Exists(GuildDataPath)) + using (FileStream bin = new FileStream(GuildDataPath, FileMode.Open, FileAccess.Read, FileShare.Read)) + { + BinaryFileReader reader = new BinaryFileReader(new BinaryReader(bin)); + + for (int i = 0; i < guilds.Count; ++i) + { + GuildEntry entry = guilds[i]; + BaseGuild g = entry.Guild; + + if (g != null) + { + reader.Seek(entry.Position, SeekOrigin.Begin); + + try + { + g.Deserialize(reader); + + if (reader.Position != entry.Position + entry.Length) + throw new Exception($"***** Bad serialize on Guild {g.Id} *****"); + } + catch (Exception e) + { + guilds.RemoveAt(i); + + failed = e; + failedGuilds = true; + failedType = typeof(BaseGuild); + failedTypeID = g.Id; + failedSerial = g.Id; + + break; + } + } + } + + reader.Close(); + } + + if (failedItems || failedMobiles || failedGuilds) + { + Console.WriteLine("An error was encountered while loading a saved object"); + + Console.WriteLine(" - Type: {0}", failedType); + Console.WriteLine(" - Serial: {0}", failedSerial); + + if (!Core.Service) + { + Console.WriteLine("Delete the object? (y/n)"); + + if (Console.ReadKey(true).Key == ConsoleKey.Y) + { + if (failedType != typeof(BaseGuild)) + { + Console.WriteLine("Delete all objects of that type? (y/n)"); + + if (Console.ReadKey(true).Key == ConsoleKey.Y) + { + if (failedMobiles) + for (int i = 0; i < mobiles.Count;) + if (mobiles[i].TypeID == failedTypeID) + mobiles.RemoveAt(i); + else + ++i; + else if (failedItems) + for (int i = 0; i < items.Count;) + if (items[i].TypeID == failedTypeID) + items.RemoveAt(i); + else + ++i; + } + } + + SaveIndex(mobiles, MobileIndexPath); + SaveIndex(items, ItemIndexPath); + SaveIndex(guilds, GuildIndexPath); + } + + Console.WriteLine("After pressing return an exception will be thrown and the server will terminate."); + Console.ReadLine(); + } + else + { + Console.WriteLine("An exception will be thrown and the server will terminate."); + } + + throw new Exception( + $"Load failed (items={failedItems}, mobiles={failedMobiles}, guilds={failedGuilds}, type={failedType}, serial={failedSerial})", + failed); + } + + EventSink.InvokeWorldLoad(); + + Loading = false; + + ProcessSafetyQueues(); + + foreach (Item item in Items.Values) + { + if (item.Parent == null) + item.UpdateTotals(); + + item.ClearProperties(); + } + + foreach (Mobile m in Mobiles.Values) + { + m.UpdateRegion(); // Is this really needed? + m.UpdateTotals(); + + m.ClearProperties(); + } + + watch.Stop(); + + Console.WriteLine("done ({1} items, {2} mobiles) ({0:F2} seconds)", watch.Elapsed.TotalSeconds, Items.Count, + Mobiles.Count); + } + + private static void ProcessSafetyQueues() + { + while (_addQueue.Count > 0) + { + IEntity entity = _addQueue.Dequeue(); + + if (entity is Item item) + AddItem(item); + else if (entity is Mobile mob) + AddMobile(mob); + } + + while (_deleteQueue.Count > 0) + { + IEntity entity = _deleteQueue.Dequeue(); + + if (entity is Item item) + item.Delete(); + else if (entity is Mobile mob) + mob.Delete(); + } + } + + private static void AppendSafetyLog(string action, IEntity entity) + { + string message = string.Format("Warning: Attempted to {1} {2} during world save." + + "{0}This action could cause inconsistent state." + + "{0}It is strongly advised that the offending scripts be corrected.", + Environment.NewLine, + action, entity + ); + + Console.WriteLine(message); + + try + { + using (StreamWriter op = new StreamWriter("world-save-errors.log", true)) + { + op.WriteLine("{0}\t{1}", DateTime.UtcNow, message); + op.WriteLine(new StackTrace(2).ToString()); + op.WriteLine(); + } + } + catch + { + } + } - Loaded = true; - LoadingType = null; + private static void SaveIndex(List list, string path) where T : IEntityEntry + { + if (!Directory.Exists("Saves/Mobiles/")) + Directory.CreateDirectory("Saves/Mobiles/"); - Console.Write( "World: Loading..." ); + if (!Directory.Exists("Saves/Items/")) + Directory.CreateDirectory("Saves/Items/"); - Stopwatch watch = Stopwatch.StartNew(); + if (!Directory.Exists("Saves/Guilds/")) + Directory.CreateDirectory("Saves/Guilds/"); - Loading = true; + using (FileStream idx = new FileStream(path, FileMode.Create, FileAccess.Write, FileShare.None)) + { + BinaryWriter idxWriter = new BinaryWriter(idx); - _addQueue = new Queue(); - _deleteQueue = new Queue(); + idxWriter.Write(list.Count); - int mobileCount = 0, itemCount = 0, guildCount = 0; + for (int i = 0; i < list.Count; ++i) + { + T e = list[i]; - object[] ctorArgs = new object[1]; + idxWriter.Write(e.TypeID); + idxWriter.Write(e.Serial); + idxWriter.Write(e.Position); + idxWriter.Write(e.Length); + } - List items = new List(); - List mobiles = new List(); - List guilds = new List(); + idxWriter.Close(); + } + } + + public static void Save() + { + Save(true, false); + } + + public static void Save(bool message, bool permitBackgroundWrite) + { + if (Saving) + return; - if ( File.Exists( MobileIndexPath ) && File.Exists( MobileTypesPath ) ) { - using ( FileStream idx = new FileStream( MobileIndexPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryReader idxReader = new BinaryReader( idx ); + ++m_Saves; - using ( FileStream tdb = new FileStream( MobileTypesPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryReader tdbReader = new BinaryReader( tdb ); + NetState.FlushAll(); + NetState.Pause(); - List> types = ReadTypes( tdbReader ); + WaitForWriteCompletion(); //Blocks Save until current disk flush is done. + + Saving = true; + + m_DiskWriteHandle.Reset(); + + if (message) + Broadcast(0x35, true, "The world is saving, please wait."); + + SaveStrategy strategy = SaveStrategy.Acquire(); + Console.WriteLine("Core: Using {0} save strategy", strategy.Name.ToLowerInvariant()); + + Console.Write("World: Saving..."); + + Stopwatch watch = Stopwatch.StartNew(); + + if (!Directory.Exists("Saves/Mobiles/")) + Directory.CreateDirectory("Saves/Mobiles/"); + if (!Directory.Exists("Saves/Items/")) + Directory.CreateDirectory("Saves/Items/"); + if (!Directory.Exists("Saves/Guilds/")) + Directory.CreateDirectory("Saves/Guilds/"); + + + /*using ( SaveMetrics metrics = new SaveMetrics() ) {*/ + strategy.Save(null, permitBackgroundWrite); + /*}*/ + + try + { + EventSink.InvokeWorldSave(new WorldSaveEventArgs(message)); + } + catch (Exception e) + { + throw new Exception("World Save event threw an exception. Save failed!", e); + } + + watch.Stop(); + + Saving = false; + + if (!permitBackgroundWrite) + NotifyDiskWriteComplete(); //Sets the DiskWriteHandle. If we allow background writes, we leave this upto the individual save strategies. + + ProcessSafetyQueues(); - mobileCount = idxReader.ReadInt32(); + strategy.ProcessDecay(); - Mobiles = new Dictionary( mobileCount ); + Console.WriteLine("Save done in {0:F2} seconds.", watch.Elapsed.TotalSeconds); - for ( int i = 0; i < mobileCount; ++i ) { - int typeID = idxReader.ReadInt32(); - int serial = idxReader.ReadInt32(); - long pos = idxReader.ReadInt64(); - int length = idxReader.ReadInt32(); + if (message) + Broadcast(0x35, true, "World save complete. The entire process took {0:F1} seconds.", + watch.Elapsed.TotalSeconds); - Tuple objs = types[typeID]; + NetState.Resume(); + } - if ( objs == null ) - continue; + public static IEntity FindEntity(Serial serial) + { + if (serial.IsItem) + return FindItem(serial); + if (serial.IsMobile) + return FindMobile(serial); - Mobile m = null; - ConstructorInfo ctor = objs.Item1; - string typeName = objs.Item2; + return null; + } - try { - ctorArgs[0] = ( Serial ) serial; - m = ( Mobile ) ( ctor.Invoke( ctorArgs ) ); - } catch { - } + public static Mobile FindMobile(Serial serial) + { + Mobile mob; - if ( m != null ) { - mobiles.Add( new MobileEntry( m, typeID, typeName, pos, length ) ); - AddMobile( m ); - } - } + Mobiles.TryGetValue(serial, out mob); - tdbReader.Close(); - } + return mob; + } - idxReader.Close(); - } - } else { - Mobiles = new Dictionary(); - } + public static void AddMobile(Mobile m) + { + if (Saving) + { + AppendSafetyLog("add", m); + _addQueue.Enqueue(m); + } + else + { + Mobiles[m.Serial] = m; + } + } - if ( File.Exists( ItemIndexPath ) && File.Exists( ItemTypesPath ) ) { - using ( FileStream idx = new FileStream( ItemIndexPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryReader idxReader = new BinaryReader( idx ); + public static Item FindItem(Serial serial) + { + Item item; - using ( FileStream tdb = new FileStream( ItemTypesPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryReader tdbReader = new BinaryReader( tdb ); + Items.TryGetValue(serial, out item); - List> types = ReadTypes( tdbReader ); + return item; + } - itemCount = idxReader.ReadInt32(); + public static void AddItem(Item item) + { + if (Saving) + { + AppendSafetyLog("add", item); + _addQueue.Enqueue(item); + } + else + { + Items[item.Serial] = item; + } + } - Items = new Dictionary( itemCount ); + public static void RemoveMobile(Mobile m) + { + Mobiles.Remove(m.Serial); + } - for ( int i = 0; i < itemCount; ++i ) { - int typeID = idxReader.ReadInt32(); - int serial = idxReader.ReadInt32(); - long pos = idxReader.ReadInt64(); - int length = idxReader.ReadInt32(); + public static void RemoveItem(Item item) + { + Items.Remove(item.Serial); + } - Tuple objs = types[typeID]; + private interface IEntityEntry + { + Serial Serial{ get; } + int TypeID{ get; } + long Position{ get; } + int Length{ get; } + } + + private sealed class GuildEntry : IEntityEntry + { + public GuildEntry(BaseGuild g, long pos, int length) + { + Guild = g; + Position = pos; + Length = length; + } - if ( objs == null ) - continue; + public BaseGuild Guild{ get; } - Item item = null; - ConstructorInfo ctor = objs.Item1; - string typeName = objs.Item2; + public Serial Serial => Guild?.Id ?? 0; + + public int TypeID => 0; - try { - ctorArgs[0] = ( Serial ) serial; - item = ( Item ) ( ctor.Invoke( ctorArgs ) ); - } catch { - } + public long Position{ get; } + + public int Length{ get; } + } + + private sealed class ItemEntry : IEntityEntry + { + public ItemEntry(Item item, int typeID, string typeName, long pos, int length) + { + Item = item; + TypeID = typeID; + TypeName = typeName; + Position = pos; + Length = length; + } + + public Item Item{ get; } + + public string TypeName{ get; } + + public Serial Serial => Item?.Serial ?? Serial.MinusOne; + + public int TypeID{ get; } + + public long Position{ get; } + + public int Length{ get; } + } + + private sealed class MobileEntry : IEntityEntry + { + public MobileEntry(Mobile mobile, int typeID, string typeName, long pos, int length) + { + Mobile = mobile; + TypeID = typeID; + TypeName = typeName; + Position = pos; + Length = length; + } + + public Mobile Mobile{ get; } + + public string TypeName{ get; } - if ( item != null ) { - items.Add( new ItemEntry( item, typeID, typeName, pos, length ) ); - AddItem( item ); - } - } + public Serial Serial => Mobile?.Serial ?? Serial.MinusOne; + + public int TypeID{ get; } - tdbReader.Close(); - } - - idxReader.Close(); - } - } else { - Items = new Dictionary(); - } - - if ( File.Exists( GuildIndexPath ) ) { - using ( FileStream idx = new FileStream( GuildIndexPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryReader idxReader = new BinaryReader( idx ); - - guildCount = idxReader.ReadInt32(); - - CreateGuildEventArgs createEventArgs = new CreateGuildEventArgs( -1 ); - for ( int i = 0; i < guildCount; ++i ) { - idxReader.ReadInt32();//no typeid for guilds - int id = idxReader.ReadInt32(); - long pos = idxReader.ReadInt64(); - int length = idxReader.ReadInt32(); - - createEventArgs.Id = id; - EventSink.InvokeCreateGuild(createEventArgs); - BaseGuild guild = createEventArgs.Guild; - if ( guild != null ) - guilds.Add( new GuildEntry( guild, pos, length ) ); - } - - idxReader.Close(); - } - } - - bool failedMobiles = false, failedItems = false, failedGuilds = false; - Type failedType = null; - Serial failedSerial = Serial.Zero; - Exception failed = null; - int failedTypeID = 0; - - if ( File.Exists( MobileDataPath ) ) { - using ( FileStream bin = new FileStream( MobileDataPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryFileReader reader = new BinaryFileReader( new BinaryReader( bin ) ); - - for ( int i = 0; i < mobiles.Count; ++i ) { - MobileEntry entry = mobiles[i]; - Mobile m = entry.Mobile; - - if ( m != null ) { - reader.Seek( entry.Position, SeekOrigin.Begin ); - - try { - LoadingType = entry.TypeName; - m.Deserialize( reader ); - - if ( reader.Position != ( entry.Position + entry.Length ) ) - throw new Exception($"***** Bad serialize on {m.GetType()} *****"); - } catch ( Exception e ) { - mobiles.RemoveAt( i ); - - failed = e; - failedMobiles = true; - failedType = m.GetType(); - failedTypeID = entry.TypeID; - failedSerial = m.Serial; - - break; - } - } - } - - reader.Close(); - } - } - - if ( !failedMobiles && File.Exists( ItemDataPath ) ) { - using ( FileStream bin = new FileStream( ItemDataPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryFileReader reader = new BinaryFileReader( new BinaryReader( bin ) ); - - for ( int i = 0; i < items.Count; ++i ) { - ItemEntry entry = items[i]; - Item item = entry.Item; - - if ( item != null ) { - reader.Seek( entry.Position, SeekOrigin.Begin ); - - try { - LoadingType = entry.TypeName; - item.Deserialize( reader ); - - if ( reader.Position != ( entry.Position + entry.Length ) ) - throw new Exception($"***** Bad serialize on {item.GetType()} *****"); - } catch ( Exception e ) { - items.RemoveAt( i ); - - failed = e; - failedItems = true; - failedType = item.GetType(); - failedTypeID = entry.TypeID; - failedSerial = item.Serial; - - break; - } - } - } - - reader.Close(); - } - } - - LoadingType = null; - - if ( !failedMobiles && !failedItems && File.Exists( GuildDataPath ) ) { - using ( FileStream bin = new FileStream( GuildDataPath, FileMode.Open, FileAccess.Read, FileShare.Read ) ) { - BinaryFileReader reader = new BinaryFileReader( new BinaryReader( bin ) ); - - for ( int i = 0; i < guilds.Count; ++i ) { - GuildEntry entry = guilds[i]; - BaseGuild g = entry.Guild; - - if ( g != null ) { - reader.Seek( entry.Position, SeekOrigin.Begin ); - - try { - g.Deserialize( reader ); - - if ( reader.Position != ( entry.Position + entry.Length ) ) - throw new Exception($"***** Bad serialize on Guild {g.Id} *****"); - } catch ( Exception e ) { - guilds.RemoveAt( i ); - - failed = e; - failedGuilds = true; - failedType = typeof( BaseGuild ); - failedTypeID = g.Id; - failedSerial = g.Id; - - break; - } - } - } - - reader.Close(); - } - } - - if ( failedItems || failedMobiles || failedGuilds ) { - Console.WriteLine( "An error was encountered while loading a saved object" ); - - Console.WriteLine( " - Type: {0}", failedType ); - Console.WriteLine( " - Serial: {0}", failedSerial ); - - if ( !Core.Service ) { - Console.WriteLine( "Delete the object? (y/n)" ); - - if ( Console.ReadKey( true ).Key == ConsoleKey.Y ) { - if ( failedType != typeof( BaseGuild ) ) { - Console.WriteLine( "Delete all objects of that type? (y/n)" ); - - if ( Console.ReadKey( true ).Key == ConsoleKey.Y ) { - if ( failedMobiles ) { - for ( int i = 0; i < mobiles.Count; ) { - if ( mobiles[i].TypeID == failedTypeID ) - mobiles.RemoveAt( i ); - else - ++i; - } - } else if ( failedItems ) { - for ( int i = 0; i < items.Count; ) { - if ( items[i].TypeID == failedTypeID ) - items.RemoveAt( i ); - else - ++i; - } - } - } - } - - SaveIndex( mobiles, MobileIndexPath ); - SaveIndex( items, ItemIndexPath ); - SaveIndex( guilds, GuildIndexPath ); - } - - Console.WriteLine( "After pressing return an exception will be thrown and the server will terminate." ); - Console.ReadLine(); - } else { - Console.WriteLine( "An exception will be thrown and the server will terminate." ); - } - - throw new Exception( - $"Load failed (items={failedItems}, mobiles={failedMobiles}, guilds={failedGuilds}, type={failedType}, serial={failedSerial})", failed ); - } - - EventSink.InvokeWorldLoad(); - - Loading = false; - - ProcessSafetyQueues(); - - foreach ( Item item in Items.Values ) { - if ( item.Parent == null ) - item.UpdateTotals(); - - item.ClearProperties(); - } - - foreach ( Mobile m in Mobiles.Values ) { - m.UpdateRegion(); // Is this really needed? - m.UpdateTotals(); - - m.ClearProperties(); - } - - watch.Stop(); - - Console.WriteLine( "done ({1} items, {2} mobiles) ({0:F2} seconds)", watch.Elapsed.TotalSeconds, Items.Count, Mobiles.Count ); - } - - private static void ProcessSafetyQueues() { - while ( _addQueue.Count > 0 ) { - IEntity entity = _addQueue.Dequeue(); - - if ( entity is Item item ) - AddItem( item ); - else if ( entity is Mobile mob ) - AddMobile( mob ); - } - - while ( _deleteQueue.Count > 0 ) { - IEntity entity = _deleteQueue.Dequeue(); - - if ( entity is Item item ) - item.Delete(); - else if ( entity is Mobile mob ) - mob.Delete(); - } - } - - private static void AppendSafetyLog( string action, IEntity entity ) { - string message = string.Format( "Warning: Attempted to {1} {2} during world save." + - "{0}This action could cause inconsistent state." + - "{0}It is strongly advised that the offending scripts be corrected.", - Environment.NewLine, - action, entity - ); - - Console.WriteLine( message ); - - try { - using ( StreamWriter op = new StreamWriter( "world-save-errors.log", true ) ) { - op.WriteLine( "{0}\t{1}", DateTime.UtcNow, message ); - op.WriteLine( new StackTrace( 2 ).ToString() ); - op.WriteLine(); - } - } catch { - } - } - - private static void SaveIndex( List list, string path ) where T : IEntityEntry { - if ( !Directory.Exists( "Saves/Mobiles/" ) ) - Directory.CreateDirectory( "Saves/Mobiles/" ); - - if ( !Directory.Exists( "Saves/Items/" ) ) - Directory.CreateDirectory( "Saves/Items/" ); - - if ( !Directory.Exists( "Saves/Guilds/" ) ) - Directory.CreateDirectory( "Saves/Guilds/" ); - - using ( FileStream idx = new FileStream( path, FileMode.Create, FileAccess.Write, FileShare.None ) ) { - BinaryWriter idxWriter = new BinaryWriter( idx ); - - idxWriter.Write( list.Count ); - - for ( int i = 0; i < list.Count; ++i ) { - T e = list[i]; - - idxWriter.Write( e.TypeID ); - idxWriter.Write( e.Serial ); - idxWriter.Write( e.Position ); - idxWriter.Write( e.Length ); - } - - idxWriter.Close(); - } - } - - internal static int m_Saves; - - public static void Save() { - Save( true, false ); - } - - public static void Save( bool message, bool permitBackgroundWrite ) { - if ( Saving ) - return; - - ++m_Saves; - - NetState.FlushAll(); - NetState.Pause(); - - WaitForWriteCompletion();//Blocks Save until current disk flush is done. - - Saving = true; - - m_DiskWriteHandle.Reset(); - - if ( message ) - Broadcast( 0x35, true, "The world is saving, please wait." ); - - SaveStrategy strategy = SaveStrategy.Acquire(); - Console.WriteLine( "Core: Using {0} save strategy", strategy.Name.ToLowerInvariant() ); - - Console.Write( "World: Saving..." ); - - Stopwatch watch = Stopwatch.StartNew(); - - if ( !Directory.Exists( "Saves/Mobiles/" ) ) - Directory.CreateDirectory( "Saves/Mobiles/" ); - if ( !Directory.Exists( "Saves/Items/" ) ) - Directory.CreateDirectory( "Saves/Items/" ); - if ( !Directory.Exists( "Saves/Guilds/" ) ) - Directory.CreateDirectory( "Saves/Guilds/" ); - - - /*using ( SaveMetrics metrics = new SaveMetrics() ) {*/ - strategy.Save( null, permitBackgroundWrite ); - /*}*/ - - try { - EventSink.InvokeWorldSave( new WorldSaveEventArgs( message ) ); - } catch ( Exception e ) { - throw new Exception( "World Save event threw an exception. Save failed!", e ); - } - - watch.Stop(); - - Saving = false; - - if (!permitBackgroundWrite) - NotifyDiskWriteComplete(); //Sets the DiskWriteHandle. If we allow background writes, we leave this upto the individual save strategies. - - ProcessSafetyQueues(); - - strategy.ProcessDecay(); - - Console.WriteLine( "Save done in {0:F2} seconds.", watch.Elapsed.TotalSeconds ); - - if ( message ) - Broadcast( 0x35, true, "World save complete. The entire process took {0:F1} seconds.", watch.Elapsed.TotalSeconds ); - - NetState.Resume(); - } - - internal static List m_ItemTypes = new List(); - internal static List m_MobileTypes = new List(); - - public static IEntity FindEntity( Serial serial ) { - if ( serial.IsItem ) - return FindItem( serial ); - if ( serial.IsMobile ) - return FindMobile( serial ); - - return null; - } - - public static Mobile FindMobile( Serial serial ) { - Mobile mob; - - Mobiles.TryGetValue( serial, out mob ); - - return mob; - } - - public static void AddMobile( Mobile m ) { - if ( Saving ) { - AppendSafetyLog( "add", m ); - _addQueue.Enqueue( m ); - } else { - Mobiles[m.Serial] = m; - } - } - - public static Item FindItem( Serial serial ) { - Item item; - - Items.TryGetValue( serial, out item ); - - return item; - } - - public static void AddItem( Item item ) { - if ( Saving ) { - AppendSafetyLog( "add", item ); - _addQueue.Enqueue( item ); - } else { - Items[item.Serial] = item; - } - } - - public static void RemoveMobile( Mobile m ) { - Mobiles.Remove( m.Serial ); - } - - public static void RemoveItem( Item item ) { - Items.Remove( item.Serial ); - } - } -} + public long Position{ get; } + + public int Length{ get; } + } + } +} \ No newline at end of file